diff --git a/shared/docker/docker.go b/shared/docker/docker.go index e08ec95e7..5952bcd78 100644 --- a/shared/docker/docker.go +++ b/shared/docker/docker.go @@ -38,14 +38,14 @@ func Run(client dockerclient.Client, conf *dockerclient.ContainerConfig, name st func RunDaemon(client dockerclient.Client, conf *dockerclient.ContainerConfig, name string) (*dockerclient.ContainerInfo, error) { // attempts to create the contianer - id, err := client.CreateContainer(conf, name) + id, err := client.CreateContainer(conf, name, nil) if err != nil { // and pull the image and re-create if that fails err = client.PullImage(conf.Image, nil) if err != nil { return nil, err } - id, err = client.CreateContainer(conf, name) + id, err = client.CreateContainer(conf, name, nil) if err != nil { client.RemoveContainer(id, true, true) return nil, err diff --git a/vendor/github.com/getsentry/raven-go/LICENSE b/vendor/code.google.com/p/go.crypto/LICENSE similarity index 87% rename from vendor/github.com/getsentry/raven-go/LICENSE rename to vendor/code.google.com/p/go.crypto/LICENSE index b0301b57e..6a66aea5e 100644 --- a/vendor/github.com/getsentry/raven-go/LICENSE +++ b/vendor/code.google.com/p/go.crypto/LICENSE @@ -1,5 +1,4 @@ -Copyright (c) 2013 Apollic Software, LLC. All rights reserved. -Copyright (c) 2015 Functional Software, Inc. All rights reserved. +Copyright (c) 2009 The Go Authors. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are @@ -11,7 +10,7 @@ notice, this list of conditions and the following disclaimer. copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. - * Neither the name of Apollic Software, LLC nor the names of its + * Neither the name of Google Inc. nor the names of its contributors may be used to endorse or promote products derived from this software without specific prior written permission. diff --git a/vendor/code.google.com/p/go.crypto/PATENTS b/vendor/code.google.com/p/go.crypto/PATENTS new file mode 100644 index 000000000..733099041 --- /dev/null +++ b/vendor/code.google.com/p/go.crypto/PATENTS @@ -0,0 +1,22 @@ +Additional IP Rights Grant (Patents) + +"This implementation" means the copyrightable works distributed by +Google as part of the Go project. + +Google hereby grants to You a perpetual, worldwide, non-exclusive, +no-charge, royalty-free, irrevocable (except as stated in this section) +patent license to make, have made, use, offer to sell, sell, import, +transfer and otherwise run, modify and propagate the contents of this +implementation of Go, where such license applies only to those patent +claims, both currently owned or controlled by Google and acquired in +the future, licensable by Google that are necessarily infringed by this +implementation of Go. This grant does not include claims that would be +infringed only as a consequence of further modification of this +implementation. If you or your agent or exclusive licensee institute or +order or agree to the institution of patent litigation against any +entity (including a cross-claim or counterclaim in a lawsuit) alleging +that this implementation of Go or any code incorporated within this +implementation of Go constitutes direct or contributory patent +infringement, or inducement of patent infringement, then any patent +rights granted to you under this License for this implementation of Go +shall terminate as of the date such litigation is filed. diff --git a/vendor/code.google.com/p/go.crypto/ssh/buffer_test.go b/vendor/code.google.com/p/go.crypto/ssh/buffer_test.go deleted file mode 100644 index 135c4aec0..000000000 --- a/vendor/code.google.com/p/go.crypto/ssh/buffer_test.go +++ /dev/null @@ -1,87 +0,0 @@ -// Copyright 2011 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package ssh - -import ( - "io" - "testing" -) - -var BYTES = []byte("abcdefghijklmnopqrstuvwxyz") - -func TestBufferReadwrite(t *testing.T) { - b := newBuffer() - b.write(BYTES[:10]) - r, _ := b.Read(make([]byte, 10)) - if r != 10 { - t.Fatalf("Expected written == read == 10, written: 10, read %d", r) - } - - b = newBuffer() - b.write(BYTES[:5]) - r, _ = b.Read(make([]byte, 10)) - if r != 5 { - t.Fatalf("Expected written == read == 5, written: 5, read %d", r) - } - - b = newBuffer() - b.write(BYTES[:10]) - r, _ = b.Read(make([]byte, 5)) - if r != 5 { - t.Fatalf("Expected written == 10, read == 5, written: 10, read %d", r) - } - - b = newBuffer() - b.write(BYTES[:5]) - b.write(BYTES[5:15]) - r, _ = b.Read(make([]byte, 10)) - r2, _ := b.Read(make([]byte, 10)) - if r != 10 || r2 != 5 || 15 != r+r2 { - t.Fatal("Expected written == read == 15") - } -} - -func TestBufferClose(t *testing.T) { - b := newBuffer() - b.write(BYTES[:10]) - b.eof() - _, err := b.Read(make([]byte, 5)) - if err != nil { - t.Fatal("expected read of 5 to not return EOF") - } - b = newBuffer() - b.write(BYTES[:10]) - b.eof() - r, err := b.Read(make([]byte, 5)) - r2, err2 := b.Read(make([]byte, 10)) - if r != 5 || r2 != 5 || err != nil || err2 != nil { - t.Fatal("expected reads of 5 and 5") - } - - b = newBuffer() - b.write(BYTES[:10]) - b.eof() - r, err = b.Read(make([]byte, 5)) - r2, err2 = b.Read(make([]byte, 10)) - r3, err3 := b.Read(make([]byte, 10)) - if r != 5 || r2 != 5 || r3 != 0 || err != nil || err2 != nil || err3 != io.EOF { - t.Fatal("expected reads of 5 and 5 and 0, with EOF") - } - - b = newBuffer() - b.write(make([]byte, 5)) - b.write(make([]byte, 10)) - b.eof() - r, err = b.Read(make([]byte, 9)) - r2, err2 = b.Read(make([]byte, 3)) - r3, err3 = b.Read(make([]byte, 3)) - r4, err4 := b.Read(make([]byte, 10)) - if err != nil || err2 != nil || err3 != nil || err4 != io.EOF { - t.Fatalf("Expected EOF on forth read only, err=%v, err2=%v, err3=%v, err4=%v", err, err2, err3, err4) - } - if r != 9 || r2 != 3 || r3 != 3 || r4 != 0 { - t.Fatal("Expected written == read == 15", r, r2, r3, r4) - } -} diff --git a/vendor/code.google.com/p/go.crypto/ssh/certs_test.go b/vendor/code.google.com/p/go.crypto/ssh/certs_test.go deleted file mode 100644 index 3cec28ec1..000000000 --- a/vendor/code.google.com/p/go.crypto/ssh/certs_test.go +++ /dev/null @@ -1,55 +0,0 @@ -// Copyright 2013 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package ssh - -import ( - "bytes" - "testing" -) - -// Cert generated by ssh-keygen 6.0p1 Debian-4. -// % ssh-keygen -s ca-key -I test user-key -var exampleSSHCert = `ssh-rsa-cert-v01@openssh.com AAAAHHNzaC1yc2EtY2VydC12MDFAb3BlbnNzaC5jb20AAAAgb1srW/W3ZDjYAO45xLYAwzHBDLsJ4Ux6ICFIkTjb1LEAAAADAQABAAAAYQCkoR51poH0wE8w72cqSB8Sszx+vAhzcMdCO0wqHTj7UNENHWEXGrU0E0UQekD7U+yhkhtoyjbPOVIP7hNa6aRk/ezdh/iUnCIt4Jt1v3Z1h1P+hA4QuYFMHNB+rmjPwAcAAAAAAAAAAAAAAAEAAAAEdGVzdAAAAAAAAAAAAAAAAP//////////AAAAAAAAAIIAAAAVcGVybWl0LVgxMS1mb3J3YXJkaW5nAAAAAAAAABdwZXJtaXQtYWdlbnQtZm9yd2FyZGluZwAAAAAAAAAWcGVybWl0LXBvcnQtZm9yd2FyZGluZwAAAAAAAAAKcGVybWl0LXB0eQAAAAAAAAAOcGVybWl0LXVzZXItcmMAAAAAAAAAAAAAAHcAAAAHc3NoLXJzYQAAAAMBAAEAAABhANFS2kaktpSGc+CcmEKPyw9mJC4nZKxHKTgLVZeaGbFZOvJTNzBspQHdy7Q1uKSfktxpgjZnksiu/tFF9ngyY2KFoc+U88ya95IZUycBGCUbBQ8+bhDtw/icdDGQD5WnUwAAAG8AAAAHc3NoLXJzYQAAAGC8Y9Z2LQKhIhxf52773XaWrXdxP0t3GBVo4A10vUWiYoAGepr6rQIoGGXFxT4B9Gp+nEBJjOwKDXPrAevow0T9ca8gZN+0ykbhSrXLE5Ao48rqr3zP4O1/9P7e6gp0gw8=` - -func TestParseCert(t *testing.T) { - authKeyBytes := []byte(exampleSSHCert) - - key, _, _, rest, ok := ParseAuthorizedKey(authKeyBytes) - if !ok { - t.Fatalf("could not parse certificate") - } - if len(rest) > 0 { - t.Errorf("rest: got %q, want empty", rest) - } - - if _, ok = key.(*OpenSSHCertV01); !ok { - t.Fatalf("got %#v, want *OpenSSHCertV01", key) - } - - marshaled := MarshalAuthorizedKey(key) - // Before comparison, remove the trailing newline that - // MarshalAuthorizedKey adds. - marshaled = marshaled[:len(marshaled)-1] - if !bytes.Equal(authKeyBytes, marshaled) { - t.Errorf("marshaled certificate does not match original: got %q, want %q", marshaled, authKeyBytes) - } -} - -func TestVerifyCert(t *testing.T) { - key, _, _, _, _ := ParseAuthorizedKey([]byte(exampleSSHCert)) - validCert := key.(*OpenSSHCertV01) - if ok := validateOpenSSHCertV01Signature(validCert); !ok { - t.Error("Unable to validate certificate!") - } - - invalidCert := &OpenSSHCertV01{ - Key: rsaKey.PublicKey(), - SignatureKey: ecdsaKey.PublicKey(), - Signature: &signature{}, - } - if ok := validateOpenSSHCertV01Signature(invalidCert); ok { - t.Error("Invalid cert signature passed validation!") - } -} diff --git a/vendor/code.google.com/p/go.crypto/ssh/cipher_test.go b/vendor/code.google.com/p/go.crypto/ssh/cipher_test.go deleted file mode 100644 index ea27bd8a8..000000000 --- a/vendor/code.google.com/p/go.crypto/ssh/cipher_test.go +++ /dev/null @@ -1,62 +0,0 @@ -// Copyright 2011 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package ssh - -import ( - "bytes" - "testing" -) - -// TestCipherReversal tests that each cipher factory produces ciphers that can -// encrypt and decrypt some data successfully. -func TestCipherReversal(t *testing.T) { - testData := []byte("abcdefghijklmnopqrstuvwxyz012345") - testKey := []byte("AbCdEfGhIjKlMnOpQrStUvWxYz012345") - testIv := []byte("sdflkjhsadflkjhasdflkjhsadfklhsa") - - cryptBuffer := make([]byte, 32) - - for name, cipherMode := range cipherModes { - encrypter, err := cipherMode.createCipher(testKey, testIv) - if err != nil { - t.Errorf("failed to create encrypter for %q: %s", name, err) - continue - } - decrypter, err := cipherMode.createCipher(testKey, testIv) - if err != nil { - t.Errorf("failed to create decrypter for %q: %s", name, err) - continue - } - - copy(cryptBuffer, testData) - - encrypter.XORKeyStream(cryptBuffer, cryptBuffer) - if name == "none" { - if !bytes.Equal(cryptBuffer, testData) { - t.Errorf("encryption made change with 'none' cipher") - continue - } - } else { - if bytes.Equal(cryptBuffer, testData) { - t.Errorf("encryption made no change with %q", name) - continue - } - } - - decrypter.XORKeyStream(cryptBuffer, cryptBuffer) - if !bytes.Equal(cryptBuffer, testData) { - t.Errorf("decrypted bytes not equal to input with %q", name) - continue - } - } -} - -func TestDefaultCiphersExist(t *testing.T) { - for _, cipherAlgo := range DefaultCipherOrder { - if _, ok := cipherModes[cipherAlgo]; !ok { - t.Errorf("default cipher %q is unknown", cipherAlgo) - } - } -} diff --git a/vendor/code.google.com/p/go.crypto/ssh/client_auth_test.go b/vendor/code.google.com/p/go.crypto/ssh/client_auth_test.go deleted file mode 100644 index f2fc9c646..000000000 --- a/vendor/code.google.com/p/go.crypto/ssh/client_auth_test.go +++ /dev/null @@ -1,368 +0,0 @@ -// Copyright 2011 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package ssh - -import ( - "bytes" - "crypto/dsa" - "io" - "io/ioutil" - "math/big" - "strings" - "testing" - - _ "crypto/sha1" -) - -// private key for mock server -const testServerPrivateKey = `-----BEGIN RSA PRIVATE KEY----- -MIIEpAIBAAKCAQEA19lGVsTqIT5iiNYRgnoY1CwkbETW5cq+Rzk5v/kTlf31XpSU -70HVWkbTERECjaYdXM2gGcbb+sxpq6GtXf1M3kVomycqhxwhPv4Cr6Xp4WT/jkFx -9z+FFzpeodGJWjOH6L2H5uX1Cvr9EDdQp9t9/J32/qBFntY8GwoUI/y/1MSTmMiF -tupdMODN064vd3gyMKTwrlQ8tZM6aYuyOPsutLlUY7M5x5FwMDYvnPDSeyT/Iw0z -s3B+NCyqeeMd2T7YzQFnRATj0M7rM5LoSs7DVqVriOEABssFyLj31PboaoLhOKgc -qoM9khkNzr7FHVvi+DhYM2jD0DwvqZLN6NmnLwIDAQABAoIBAQCGVj+kuSFOV1lT -+IclQYA6bM6uY5mroqcSBNegVxCNhWU03BxlW//BE9tA/+kq53vWylMeN9mpGZea -riEMIh25KFGWXqXlOOioH8bkMsqA8S7sBmc7jljyv+0toQ9vCCtJ+sueNPhxQQxH -D2YvUjfzBQ04I9+wn30BByDJ1QA/FoPsunxIOUCcRBE/7jxuLYcpR+JvEF68yYIh -atXRld4W4in7T65YDR8jK1Uj9XAcNeDYNpT/M6oFLx1aPIlkG86aCWRO19S1jLPT -b1ZAKHHxPMCVkSYW0RqvIgLXQOR62D0Zne6/2wtzJkk5UCjkSQ2z7ZzJpMkWgDgN -ifCULFPBAoGBAPoMZ5q1w+zB+knXUD33n1J+niN6TZHJulpf2w5zsW+m2K6Zn62M -MXndXlVAHtk6p02q9kxHdgov34Uo8VpuNjbS1+abGFTI8NZgFo+bsDxJdItemwC4 -KJ7L1iz39hRN/ZylMRLz5uTYRGddCkeIHhiG2h7zohH/MaYzUacXEEy3AoGBANz8 -e/msleB+iXC0cXKwds26N4hyMdAFE5qAqJXvV3S2W8JZnmU+sS7vPAWMYPlERPk1 -D8Q2eXqdPIkAWBhrx4RxD7rNc5qFNcQWEhCIxC9fccluH1y5g2M+4jpMX2CT8Uv+ -3z+NoJ5uDTXZTnLCfoZzgZ4nCZVZ+6iU5U1+YXFJAoGBANLPpIV920n/nJmmquMj -orI1R/QXR9Cy56cMC65agezlGOfTYxk5Cfl5Ve+/2IJCfgzwJyjWUsFx7RviEeGw -64o7JoUom1HX+5xxdHPsyZ96OoTJ5RqtKKoApnhRMamau0fWydH1yeOEJd+TRHhc -XStGfhz8QNa1dVFvENczja1vAoGABGWhsd4VPVpHMc7lUvrf4kgKQtTC2PjA4xoc -QJ96hf/642sVE76jl+N6tkGMzGjnVm4P2j+bOy1VvwQavKGoXqJBRd5Apppv727g -/SM7hBXKFc/zH80xKBBgP/i1DR7kdjakCoeu4ngeGywvu2jTS6mQsqzkK+yWbUxJ -I7mYBsECgYB/KNXlTEpXtz/kwWCHFSYA8U74l7zZbVD8ul0e56JDK+lLcJ0tJffk -gqnBycHj6AhEycjda75cs+0zybZvN4x65KZHOGW/O/7OAWEcZP5TPb3zf9ned3Hl -NsZoFj52ponUM6+99A2CmezFCN16c4mbA//luWF+k3VVqR6BpkrhKw== ------END RSA PRIVATE KEY-----` - -const testClientPrivateKey = `-----BEGIN RSA PRIVATE KEY----- -MIIBOwIBAAJBALdGZxkXDAjsYk10ihwU6Id2KeILz1TAJuoq4tOgDWxEEGeTrcld -r/ZwVaFzjWzxaf6zQIJbfaSEAhqD5yo72+sCAwEAAQJBAK8PEVU23Wj8mV0QjwcJ -tZ4GcTUYQL7cF4+ezTCE9a1NrGnCP2RuQkHEKxuTVrxXt+6OF15/1/fuXnxKjmJC -nxkCIQDaXvPPBi0c7vAxGwNY9726x01/dNbHCE0CBtcotobxpwIhANbbQbh3JHVW -2haQh4fAG5mhesZKAGcxTyv4mQ7uMSQdAiAj+4dzMpJWdSzQ+qGHlHMIBvVHLkqB -y2VdEyF7DPCZewIhAI7GOI/6LDIFOvtPo6Bj2nNmyQ1HU6k/LRtNIXi4c9NJAiAr -rrxx26itVhJmcvoUhOjwuzSlP2bE5VHAvkGB352YBg== ------END RSA PRIVATE KEY-----` - -// keychain implements the ClientKeyring interface -type keychain struct { - keys []Signer -} - -func (k *keychain) Key(i int) (PublicKey, error) { - if i < 0 || i >= len(k.keys) { - return nil, nil - } - - return k.keys[i].PublicKey(), nil -} - -func (k *keychain) Sign(i int, rand io.Reader, data []byte) (sig []byte, err error) { - return k.keys[i].Sign(rand, data) -} - -func (k *keychain) add(key Signer) { - k.keys = append(k.keys, key) -} - -func (k *keychain) loadPEM(file string) error { - buf, err := ioutil.ReadFile(file) - if err != nil { - return err - } - key, err := ParsePrivateKey(buf) - if err != nil { - return err - } - k.add(key) - return nil -} - -// password implements the ClientPassword interface -type password string - -func (p password) Password(user string) (string, error) { - return string(p), nil -} - -type keyboardInteractive map[string]string - -func (cr *keyboardInteractive) Challenge(user string, instruction string, questions []string, echos []bool) ([]string, error) { - var answers []string - for _, q := range questions { - answers = append(answers, (*cr)[q]) - } - return answers, nil -} - -// reused internally by tests -var ( - rsaKey Signer - dsaKey Signer - clientKeychain = new(keychain) - clientPassword = password("tiger") - serverConfig = &ServerConfig{ - PasswordCallback: func(conn *ServerConn, user, pass string) bool { - return user == "testuser" && pass == string(clientPassword) - }, - PublicKeyCallback: func(conn *ServerConn, user, algo string, pubkey []byte) bool { - key, _ := clientKeychain.Key(0) - expected := MarshalPublicKey(key) - algoname := key.PublicKeyAlgo() - return user == "testuser" && algo == algoname && bytes.Equal(pubkey, expected) - }, - KeyboardInteractiveCallback: func(conn *ServerConn, user string, client ClientKeyboardInteractive) bool { - ans, err := client.Challenge("user", - "instruction", - []string{"question1", "question2"}, - []bool{true, true}) - if err != nil { - return false - } - ok := user == "testuser" && ans[0] == "answer1" && ans[1] == "answer2" - client.Challenge("user", "motd", nil, nil) - return ok - }, - } -) - -func init() { - var err error - rsaKey, err = ParsePrivateKey([]byte(testServerPrivateKey)) - if err != nil { - panic("unable to set private key: " + err.Error()) - } - rawDSAKey := new(dsa.PrivateKey) - - // taken from crypto/dsa/dsa_test.go - rawDSAKey.P, _ = new(big.Int).SetString("A9B5B793FB4785793D246BAE77E8FF63CA52F442DA763C440259919FE1BC1D6065A9350637A04F75A2F039401D49F08E066C4D275A5A65DA5684BC563C14289D7AB8A67163BFBF79D85972619AD2CFF55AB0EE77A9002B0EF96293BDD0F42685EBB2C66C327079F6C98000FBCB79AACDE1BC6F9D5C7B1A97E3D9D54ED7951FEF", 16) - rawDSAKey.Q, _ = new(big.Int).SetString("E1D3391245933D68A0714ED34BBCB7A1F422B9C1", 16) - rawDSAKey.G, _ = new(big.Int).SetString("634364FC25248933D01D1993ECABD0657CC0CB2CEED7ED2E3E8AECDFCDC4A25C3B15E9E3B163ACA2984B5539181F3EFF1A5E8903D71D5B95DA4F27202B77D2C44B430BB53741A8D59A8F86887525C9F2A6A5980A195EAA7F2FF910064301DEF89D3AA213E1FAC7768D89365318E370AF54A112EFBA9246D9158386BA1B4EEFDA", 16) - rawDSAKey.Y, _ = new(big.Int).SetString("32969E5780CFE1C849A1C276D7AEB4F38A23B591739AA2FE197349AEEBD31366AEE5EB7E6C6DDB7C57D02432B30DB5AA66D9884299FAA72568944E4EEDC92EA3FBC6F39F53412FBCC563208F7C15B737AC8910DBC2D9C9B8C001E72FDC40EB694AB1F06A5A2DBD18D9E36C66F31F566742F11EC0A52E9F7B89355C02FB5D32D2", 16) - rawDSAKey.X, _ = new(big.Int).SetString("5078D4D29795CBE76D3AACFE48C9AF0BCDBEE91A", 16) - - dsaKey, err = NewSignerFromKey(rawDSAKey) - if err != nil { - panic("NewSignerFromKey: " + err.Error()) - } - clientKeychain.add(rsaKey) - serverConfig.AddHostKey(rsaKey) -} - -// newMockAuthServer creates a new Server bound to -// the loopback interface. The server exits after -// processing one handshake. -func newMockAuthServer(t *testing.T) string { - l, err := Listen("tcp", "127.0.0.1:0", serverConfig) - if err != nil { - t.Fatalf("unable to newMockAuthServer: %s", err) - } - go func() { - defer l.Close() - c, err := l.Accept() - if err != nil { - t.Errorf("Unable to accept incoming connection: %v", err) - return - } - if err := c.Handshake(); err != nil { - // not Errorf because this is expected to - // fail for some tests. - t.Logf("Handshaking error: %v", err) - return - } - defer c.Close() - }() - return l.Addr().String() -} - -func TestClientAuthPublicKey(t *testing.T) { - config := &ClientConfig{ - User: "testuser", - Auth: []ClientAuth{ - ClientAuthKeyring(clientKeychain), - }, - } - c, err := Dial("tcp", newMockAuthServer(t), config) - if err != nil { - t.Fatalf("unable to dial remote side: %s", err) - } - c.Close() -} - -func TestClientAuthPassword(t *testing.T) { - config := &ClientConfig{ - User: "testuser", - Auth: []ClientAuth{ - ClientAuthPassword(clientPassword), - }, - } - - c, err := Dial("tcp", newMockAuthServer(t), config) - if err != nil { - t.Fatalf("unable to dial remote side: %s", err) - } - c.Close() -} - -func TestClientAuthWrongPassword(t *testing.T) { - wrongPw := password("wrong") - config := &ClientConfig{ - User: "testuser", - Auth: []ClientAuth{ - ClientAuthPassword(wrongPw), - ClientAuthKeyring(clientKeychain), - }, - } - - c, err := Dial("tcp", newMockAuthServer(t), config) - if err != nil { - t.Fatalf("unable to dial remote side: %s", err) - } - c.Close() -} - -func TestClientAuthKeyboardInteractive(t *testing.T) { - answers := keyboardInteractive(map[string]string{ - "question1": "answer1", - "question2": "answer2", - }) - config := &ClientConfig{ - User: "testuser", - Auth: []ClientAuth{ - ClientAuthKeyboardInteractive(&answers), - }, - } - - c, err := Dial("tcp", newMockAuthServer(t), config) - if err != nil { - t.Fatalf("unable to dial remote side: %s", err) - } - c.Close() -} - -func TestClientAuthWrongKeyboardInteractive(t *testing.T) { - answers := keyboardInteractive(map[string]string{ - "question1": "answer1", - "question2": "WRONG", - }) - config := &ClientConfig{ - User: "testuser", - Auth: []ClientAuth{ - ClientAuthKeyboardInteractive(&answers), - }, - } - - c, err := Dial("tcp", newMockAuthServer(t), config) - if err == nil { - c.Close() - t.Fatalf("wrong answers should not have authenticated with KeyboardInteractive") - } -} - -// the mock server will only authenticate ssh-rsa keys -func TestClientAuthInvalidPublicKey(t *testing.T) { - kc := new(keychain) - - kc.add(dsaKey) - config := &ClientConfig{ - User: "testuser", - Auth: []ClientAuth{ - ClientAuthKeyring(kc), - }, - } - - c, err := Dial("tcp", newMockAuthServer(t), config) - if err == nil { - c.Close() - t.Fatalf("dsa private key should not have authenticated with rsa public key") - } -} - -// the client should authenticate with the second key -func TestClientAuthRSAandDSA(t *testing.T) { - kc := new(keychain) - kc.add(dsaKey) - kc.add(rsaKey) - config := &ClientConfig{ - User: "testuser", - Auth: []ClientAuth{ - ClientAuthKeyring(kc), - }, - } - c, err := Dial("tcp", newMockAuthServer(t), config) - if err != nil { - t.Fatalf("client could not authenticate with rsa key: %v", err) - } - c.Close() -} - -func TestClientHMAC(t *testing.T) { - kc := new(keychain) - kc.add(rsaKey) - for _, mac := range DefaultMACOrder { - config := &ClientConfig{ - User: "testuser", - Auth: []ClientAuth{ - ClientAuthKeyring(kc), - }, - Crypto: CryptoConfig{ - MACs: []string{mac}, - }, - } - c, err := Dial("tcp", newMockAuthServer(t), config) - if err != nil { - t.Fatalf("client could not authenticate with mac algo %s: %v", mac, err) - } - c.Close() - } -} - -// issue 4285. -func TestClientUnsupportedCipher(t *testing.T) { - kc := new(keychain) - config := &ClientConfig{ - User: "testuser", - Auth: []ClientAuth{ - ClientAuthKeyring(kc), - }, - Crypto: CryptoConfig{ - Ciphers: []string{"aes128-cbc"}, // not currently supported - }, - } - c, err := Dial("tcp", newMockAuthServer(t), config) - if err == nil { - t.Errorf("expected no ciphers in common") - c.Close() - } -} - -func TestClientUnsupportedKex(t *testing.T) { - kc := new(keychain) - config := &ClientConfig{ - User: "testuser", - Auth: []ClientAuth{ - ClientAuthKeyring(kc), - }, - Crypto: CryptoConfig{ - KeyExchanges: []string{"diffie-hellman-group-exchange-sha256"}, // not currently supported - }, - } - c, err := Dial("tcp", newMockAuthServer(t), config) - if err == nil || !strings.Contains(err.Error(), "no common algorithms") { - t.Errorf("got %v, expected 'no common algorithms'", err) - } - if c != nil { - c.Close() - } -} diff --git a/vendor/code.google.com/p/go.crypto/ssh/client_test.go b/vendor/code.google.com/p/go.crypto/ssh/client_test.go deleted file mode 100644 index f6c11b958..000000000 --- a/vendor/code.google.com/p/go.crypto/ssh/client_test.go +++ /dev/null @@ -1,34 +0,0 @@ -package ssh - -import ( - "net" - "testing" -) - -func testClientVersion(t *testing.T, config *ClientConfig, expected string) { - clientConn, serverConn := net.Pipe() - receivedVersion := make(chan string, 1) - go func() { - version, err := readVersion(serverConn) - if err != nil { - receivedVersion <- "" - } else { - receivedVersion <- string(version) - } - serverConn.Close() - }() - Client(clientConn, config) - actual := <-receivedVersion - if actual != expected { - t.Fatalf("got %s; want %s", actual, expected) - } -} - -func TestCustomClientVersion(t *testing.T) { - version := "Test-Client-Version-0.0" - testClientVersion(t, &ClientConfig{ClientVersion: version}, version) -} - -func TestDefaultClientVersion(t *testing.T) { - testClientVersion(t, &ClientConfig{}, packageVersion) -} diff --git a/vendor/code.google.com/p/go.crypto/ssh/common_test.go b/vendor/code.google.com/p/go.crypto/ssh/common_test.go deleted file mode 100644 index d9df56fab..000000000 --- a/vendor/code.google.com/p/go.crypto/ssh/common_test.go +++ /dev/null @@ -1,57 +0,0 @@ -// Copyright 2011 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package ssh - -import ( - "io" - "net" - "testing" -) - -func TestSafeString(t *testing.T) { - strings := map[string]string{ - "\x20\x0d\x0a": "\x20\x0d\x0a", - "flibble": "flibble", - "new\x20line": "new\x20line", - "123456\x07789": "123456 789", - "\t\t\x10\r\n": "\t\t \r\n", - } - - for s, expected := range strings { - actual := safeString(s) - if expected != actual { - t.Errorf("expected: %v, actual: %v", []byte(expected), []byte(actual)) - } - } -} - -// Make sure Read/Write are not exposed. -func TestConnHideRWMethods(t *testing.T) { - for _, c := range []interface{}{new(ServerConn), new(ClientConn)} { - if _, ok := c.(io.Reader); ok { - t.Errorf("%T implements io.Reader", c) - } - if _, ok := c.(io.Writer); ok { - t.Errorf("%T implements io.Writer", c) - } - } -} - -func TestConnSupportsLocalRemoteMethods(t *testing.T) { - type LocalAddr interface { - LocalAddr() net.Addr - } - type RemoteAddr interface { - RemoteAddr() net.Addr - } - for _, c := range []interface{}{new(ServerConn), new(ClientConn)} { - if _, ok := c.(LocalAddr); !ok { - t.Errorf("%T does not implement LocalAddr", c) - } - if _, ok := c.(RemoteAddr); !ok { - t.Errorf("%T does not implement RemoteAddr", c) - } - } -} diff --git a/vendor/code.google.com/p/go.crypto/ssh/example_test.go b/vendor/code.google.com/p/go.crypto/ssh/example_test.go deleted file mode 100644 index a88a6773d..000000000 --- a/vendor/code.google.com/p/go.crypto/ssh/example_test.go +++ /dev/null @@ -1,191 +0,0 @@ -// Copyright 2011 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package ssh - -import ( - "bytes" - "fmt" - "io/ioutil" - "log" - "net/http" - - "code.google.com/p/go.crypto/ssh/terminal" -) - -func ExampleListen() { - // An SSH server is represented by a ServerConfig, which holds - // certificate details and handles authentication of ServerConns. - config := &ServerConfig{ - PasswordCallback: func(conn *ServerConn, user, pass string) bool { - return user == "testuser" && pass == "tiger" - }, - } - - privateBytes, err := ioutil.ReadFile("id_rsa") - if err != nil { - panic("Failed to load private key") - } - - private, err := ParsePrivateKey(privateBytes) - if err != nil { - panic("Failed to parse private key") - } - - config.AddHostKey(private) - - // Once a ServerConfig has been configured, connections can be - // accepted. - listener, err := Listen("tcp", "0.0.0.0:2022", config) - if err != nil { - panic("failed to listen for connection") - } - sConn, err := listener.Accept() - if err != nil { - panic("failed to accept incoming connection") - } - if err := sConn.Handshake(); err != nil { - panic("failed to handshake") - } - - // A ServerConn multiplexes several channels, which must - // themselves be Accepted. - for { - // Accept reads from the connection, demultiplexes packets - // to their corresponding channels and returns when a new - // channel request is seen. Some goroutine must always be - // calling Accept; otherwise no messages will be forwarded - // to the channels. - channel, err := sConn.Accept() - if err != nil { - panic("error from Accept") - } - - // Channels have a type, depending on the application level - // protocol intended. In the case of a shell, the type is - // "session" and ServerShell may be used to present a simple - // terminal interface. - if channel.ChannelType() != "session" { - channel.Reject(UnknownChannelType, "unknown channel type") - continue - } - channel.Accept() - - term := terminal.NewTerminal(channel, "> ") - serverTerm := &ServerTerminal{ - Term: term, - Channel: channel, - } - go func() { - defer channel.Close() - for { - line, err := serverTerm.ReadLine() - if err != nil { - break - } - fmt.Println(line) - } - }() - } -} - -func ExampleDial() { - // An SSH client is represented with a ClientConn. Currently only - // the "password" authentication method is supported. - // - // To authenticate with the remote server you must pass at least one - // implementation of ClientAuth via the Auth field in ClientConfig. - config := &ClientConfig{ - User: "username", - Auth: []ClientAuth{ - // ClientAuthPassword wraps a ClientPassword implementation - // in a type that implements ClientAuth. - ClientAuthPassword(password("yourpassword")), - }, - } - client, err := Dial("tcp", "yourserver.com:22", config) - if err != nil { - panic("Failed to dial: " + err.Error()) - } - - // Each ClientConn can support multiple interactive sessions, - // represented by a Session. - session, err := client.NewSession() - if err != nil { - panic("Failed to create session: " + err.Error()) - } - defer session.Close() - - // Once a Session is created, you can execute a single command on - // the remote side using the Run method. - var b bytes.Buffer - session.Stdout = &b - if err := session.Run("/usr/bin/whoami"); err != nil { - panic("Failed to run: " + err.Error()) - } - fmt.Println(b.String()) -} - -func ExampleClientConn_Listen() { - config := &ClientConfig{ - User: "username", - Auth: []ClientAuth{ - ClientAuthPassword(password("password")), - }, - } - // Dial your ssh server. - conn, err := Dial("tcp", "localhost:22", config) - if err != nil { - log.Fatalf("unable to connect: %s", err) - } - defer conn.Close() - - // Request the remote side to open port 8080 on all interfaces. - l, err := conn.Listen("tcp", "0.0.0.0:8080") - if err != nil { - log.Fatalf("unable to register tcp forward: %v", err) - } - defer l.Close() - - // Serve HTTP with your SSH server acting as a reverse proxy. - http.Serve(l, http.HandlerFunc(func(resp http.ResponseWriter, req *http.Request) { - fmt.Fprintf(resp, "Hello world!\n") - })) -} - -func ExampleSession_RequestPty() { - // Create client config - config := &ClientConfig{ - User: "username", - Auth: []ClientAuth{ - ClientAuthPassword(password("password")), - }, - } - // Connect to ssh server - conn, err := Dial("tcp", "localhost:22", config) - if err != nil { - log.Fatalf("unable to connect: %s", err) - } - defer conn.Close() - // Create a session - session, err := conn.NewSession() - if err != nil { - log.Fatalf("unable to create session: %s", err) - } - defer session.Close() - // Set up terminal modes - modes := TerminalModes{ - ECHO: 0, // disable echoing - TTY_OP_ISPEED: 14400, // input speed = 14.4kbaud - TTY_OP_OSPEED: 14400, // output speed = 14.4kbaud - } - // Request pseudo terminal - if err := session.RequestPty("xterm", 80, 40, modes); err != nil { - log.Fatalf("request for pseudo terminal failed: %s", err) - } - // Start remote shell - if err := session.Shell(); err != nil { - log.Fatalf("failed to start shell: %s", err) - } -} diff --git a/vendor/code.google.com/p/go.crypto/ssh/kex_test.go b/vendor/code.google.com/p/go.crypto/ssh/kex_test.go deleted file mode 100644 index 1e931a313..000000000 --- a/vendor/code.google.com/p/go.crypto/ssh/kex_test.go +++ /dev/null @@ -1,48 +0,0 @@ -// Copyright 2013 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package ssh - -// Key exchange tests. - -import ( - "crypto/rand" - "reflect" - "testing" -) - -func TestKexes(t *testing.T) { - type kexResultErr struct { - result *kexResult - err error - } - - for name, kex := range kexAlgoMap { - a, b := memPipe() - - s := make(chan kexResultErr, 1) - c := make(chan kexResultErr, 1) - var magics handshakeMagics - go func() { - r, e := kex.Client(a, rand.Reader, &magics) - c <- kexResultErr{r, e} - }() - go func() { - r, e := kex.Server(b, rand.Reader, &magics, ecdsaKey) - s <- kexResultErr{r, e} - }() - - clientRes := <-c - serverRes := <-s - if clientRes.err != nil { - t.Errorf("client: %v", clientRes.err) - } - if serverRes.err != nil { - t.Errorf("server: %v", serverRes.err) - } - if !reflect.DeepEqual(clientRes.result, serverRes.result) { - t.Errorf("kex %q: mismatch %#v, %#v", name, clientRes.result, serverRes.result) - } - } -} diff --git a/vendor/code.google.com/p/go.crypto/ssh/keys_test.go b/vendor/code.google.com/p/go.crypto/ssh/keys_test.go deleted file mode 100644 index 3c4b73515..000000000 --- a/vendor/code.google.com/p/go.crypto/ssh/keys_test.go +++ /dev/null @@ -1,214 +0,0 @@ -package ssh - -import ( - "crypto/dsa" - "crypto/ecdsa" - "crypto/elliptic" - "crypto/rand" - "crypto/rsa" - "reflect" - "strings" - "testing" -) - -var ( - ecdsaKey Signer - ecdsa384Key Signer - ecdsa521Key Signer - testCertKey Signer -) - -type testSigner struct { - Signer - pub PublicKey -} - -func (ts *testSigner) PublicKey() PublicKey { - if ts.pub != nil { - return ts.pub - } - return ts.Signer.PublicKey() -} - -func init() { - raw256, _ := ecdsa.GenerateKey(elliptic.P256(), rand.Reader) - ecdsaKey, _ = NewSignerFromKey(raw256) - - raw384, _ := ecdsa.GenerateKey(elliptic.P384(), rand.Reader) - ecdsa384Key, _ = NewSignerFromKey(raw384) - - raw521, _ := ecdsa.GenerateKey(elliptic.P521(), rand.Reader) - ecdsa521Key, _ = NewSignerFromKey(raw521) - - // Create a cert and sign it for use in tests. - testCert := &OpenSSHCertV01{ - Nonce: []byte{}, // To pass reflect.DeepEqual after marshal & parse, this must be non-nil - Key: ecdsaKey.PublicKey(), - ValidPrincipals: []string{"gopher1", "gopher2"}, // increases test coverage - ValidAfter: 0, // unix epoch - ValidBefore: maxUint64, // The end of currently representable time. - Reserved: []byte{}, // To pass reflect.DeepEqual after marshal & parse, this must be non-nil - SignatureKey: rsaKey.PublicKey(), - } - sigBytes, _ := rsaKey.Sign(rand.Reader, testCert.BytesForSigning()) - testCert.Signature = &signature{ - Format: testCert.SignatureKey.PublicKeyAlgo(), - Blob: sigBytes, - } - testCertKey = &testSigner{ - Signer: ecdsaKey, - pub: testCert, - } -} - -func rawKey(pub PublicKey) interface{} { - switch k := pub.(type) { - case *rsaPublicKey: - return (*rsa.PublicKey)(k) - case *dsaPublicKey: - return (*dsa.PublicKey)(k) - case *ecdsaPublicKey: - return (*ecdsa.PublicKey)(k) - case *OpenSSHCertV01: - return k - } - panic("unknown key type") -} - -func TestKeyMarshalParse(t *testing.T) { - keys := []Signer{rsaKey, dsaKey, ecdsaKey, ecdsa384Key, ecdsa521Key, testCertKey} - for _, priv := range keys { - pub := priv.PublicKey() - roundtrip, rest, ok := ParsePublicKey(MarshalPublicKey(pub)) - if !ok { - t.Errorf("ParsePublicKey(%T) failed", pub) - } - - if len(rest) > 0 { - t.Errorf("ParsePublicKey(%T): trailing junk", pub) - } - - k1 := rawKey(pub) - k2 := rawKey(roundtrip) - - if !reflect.DeepEqual(k1, k2) { - t.Errorf("got %#v in roundtrip, want %#v", k2, k1) - } - } -} - -func TestUnsupportedCurves(t *testing.T) { - raw, err := ecdsa.GenerateKey(elliptic.P224(), rand.Reader) - if err != nil { - t.Fatalf("GenerateKey: %v", err) - } - - if _, err = NewSignerFromKey(raw); err == nil || !strings.Contains(err.Error(), "only P256") { - t.Fatalf("NewPrivateKey should not succeed with P224, got: %v", err) - } - - if _, err = NewPublicKey(&raw.PublicKey); err == nil || !strings.Contains(err.Error(), "only P256") { - t.Fatalf("NewPublicKey should not succeed with P224, got: %v", err) - } -} - -func TestNewPublicKey(t *testing.T) { - keys := []Signer{rsaKey, dsaKey, ecdsaKey} - for _, k := range keys { - raw := rawKey(k.PublicKey()) - pub, err := NewPublicKey(raw) - if err != nil { - t.Errorf("NewPublicKey(%#v): %v", raw, err) - } - if !reflect.DeepEqual(k.PublicKey(), pub) { - t.Errorf("NewPublicKey(%#v) = %#v, want %#v", raw, pub, k.PublicKey()) - } - } -} - -func TestKeySignVerify(t *testing.T) { - keys := []Signer{rsaKey, dsaKey, ecdsaKey, testCertKey} - for _, priv := range keys { - pub := priv.PublicKey() - - data := []byte("sign me") - sig, err := priv.Sign(rand.Reader, data) - if err != nil { - t.Fatalf("Sign(%T): %v", priv, err) - } - - if !pub.Verify(data, sig) { - t.Errorf("publicKey.Verify(%T) failed", priv) - } - } -} - -func TestParseRSAPrivateKey(t *testing.T) { - key, err := ParsePrivateKey([]byte(testServerPrivateKey)) - if err != nil { - t.Fatalf("ParsePrivateKey: %v", err) - } - - rsa, ok := key.(*rsaPrivateKey) - if !ok { - t.Fatalf("got %T, want *rsa.PrivateKey", rsa) - } - - if err := rsa.Validate(); err != nil { - t.Errorf("Validate: %v", err) - } -} - -func TestParseECPrivateKey(t *testing.T) { - // Taken from the data in test/ . - pem := []byte(`-----BEGIN EC PRIVATE KEY----- -MHcCAQEEINGWx0zo6fhJ/0EAfrPzVFyFC9s18lBt3cRoEDhS3ARooAoGCCqGSM49 -AwEHoUQDQgAEi9Hdw6KvZcWxfg2IDhA7UkpDtzzt6ZqJXSsFdLd+Kx4S3Sx4cVO+ -6/ZOXRnPmNAlLUqjShUsUBBngG0u2fqEqA== ------END EC PRIVATE KEY-----`) - - key, err := ParsePrivateKey(pem) - if err != nil { - t.Fatalf("ParsePrivateKey: %v", err) - } - - ecKey, ok := key.(*ecdsaPrivateKey) - if !ok { - t.Fatalf("got %T, want *ecdsaPrivateKey", ecKey) - } - - if !validateECPublicKey(ecKey.Curve, ecKey.X, ecKey.Y) { - t.Fatalf("public key does not validate.") - } -} - -// ssh-keygen -t dsa -f /tmp/idsa.pem -var dsaPEM = `-----BEGIN DSA PRIVATE KEY----- -MIIBuwIBAAKBgQD6PDSEyXiI9jfNs97WuM46MSDCYlOqWw80ajN16AohtBncs1YB -lHk//dQOvCYOsYaE+gNix2jtoRjwXhDsc25/IqQbU1ahb7mB8/rsaILRGIbA5WH3 -EgFtJmXFovDz3if6F6TzvhFpHgJRmLYVR8cqsezL3hEZOvvs2iH7MorkxwIVAJHD -nD82+lxh2fb4PMsIiaXudAsBAoGAQRf7Q/iaPRn43ZquUhd6WwvirqUj+tkIu6eV -2nZWYmXLlqFQKEy4Tejl7Wkyzr2OSYvbXLzo7TNxLKoWor6ips0phYPPMyXld14r -juhT24CrhOzuLMhDduMDi032wDIZG4Y+K7ElU8Oufn8Sj5Wge8r6ANmmVgmFfynr -FhdYCngCgYEA3ucGJ93/Mx4q4eKRDxcWD3QzWyqpbRVRRV1Vmih9Ha/qC994nJFz -DQIdjxDIT2Rk2AGzMqFEB68Zc3O+Wcsmz5eWWzEwFxaTwOGWTyDqsDRLm3fD+QYj -nOwuxb0Kce+gWI8voWcqC9cyRm09jGzu2Ab3Bhtpg8JJ8L7gS3MRZK4CFEx4UAfY -Fmsr0W6fHB9nhS4/UXM8 ------END DSA PRIVATE KEY-----` - -func TestParseDSA(t *testing.T) { - s, err := ParsePrivateKey([]byte(dsaPEM)) - if err != nil { - t.Fatalf("ParsePrivateKey returned error: %s", err) - } - - data := []byte("sign me") - sig, err := s.Sign(rand.Reader, data) - if err != nil { - t.Fatalf("dsa.Sign: %v", err) - } - - if !s.PublicKey().Verify(data, sig) { - t.Error("Verify failed.") - } -} diff --git a/vendor/code.google.com/p/go.crypto/ssh/mempipe_test.go b/vendor/code.google.com/p/go.crypto/ssh/mempipe_test.go deleted file mode 100644 index ec1b854ec..000000000 --- a/vendor/code.google.com/p/go.crypto/ssh/mempipe_test.go +++ /dev/null @@ -1,102 +0,0 @@ -// Copyright 2013 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package ssh - -import ( - "io" - "sync" - "testing" -) - -// An in-memory packetConn. It is safe to call Close and writePacket -// from different goroutines. -type memTransport struct { - eof bool - pending [][]byte - write *memTransport - sync.Mutex - *sync.Cond -} - -func (t *memTransport) readPacket() ([]byte, error) { - t.Lock() - defer t.Unlock() - for { - if len(t.pending) > 0 { - r := t.pending[0] - t.pending = t.pending[1:] - return r, nil - } - if t.eof { - return nil, io.EOF - } - t.Cond.Wait() - } -} - -func (t *memTransport) Close() error { - t.write.Lock() - defer t.write.Unlock() - if t.write.eof { - return io.EOF - } - t.write.eof = true - t.write.Cond.Broadcast() - return nil -} - -func (t *memTransport) writePacket(p []byte) error { - t.write.Lock() - defer t.write.Unlock() - if t.write.eof { - return io.EOF - } - t.write.pending = append(t.write.pending, p) - t.write.Cond.Signal() - return nil -} - -func memPipe() (a, b packetConn) { - t1 := memTransport{} - t2 := memTransport{} - t1.write = &t2 - t2.write = &t1 - t1.Cond = sync.NewCond(&t1.Mutex) - t2.Cond = sync.NewCond(&t2.Mutex) - return &t1, &t2 -} - -func TestmemPipe(t *testing.T) { - a, b := memPipe() - if err := a.writePacket([]byte{42}); err != nil { - t.Fatalf("writePacket: %v", err) - } - if err := a.Close(); err != nil { - t.Fatal("Close: ", err) - } - p, err := b.readPacket() - if err != nil { - t.Fatal("readPacket: ", err) - } - if len(p) != 1 || p[0] != 42 { - t.Fatalf("got %v, want {42}", p) - } - p, err = b.readPacket() - if err != io.EOF { - t.Fatalf("got %v, %v, want EOF", p, err) - } -} - -func TestDoubleClose(t *testing.T) { - a, _ := memPipe() - err := a.Close() - if err != nil { - t.Errorf("Close: %v", err) - } - err = a.Close() - if err != io.EOF { - t.Errorf("expect EOF on double close.") - } -} diff --git a/vendor/code.google.com/p/go.crypto/ssh/messages_test.go b/vendor/code.google.com/p/go.crypto/ssh/messages_test.go deleted file mode 100644 index ec1d7be6f..000000000 --- a/vendor/code.google.com/p/go.crypto/ssh/messages_test.go +++ /dev/null @@ -1,232 +0,0 @@ -// Copyright 2011 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package ssh - -import ( - "math/big" - "math/rand" - "reflect" - "testing" - "testing/quick" -) - -var intLengthTests = []struct { - val, length int -}{ - {0, 4 + 0}, - {1, 4 + 1}, - {127, 4 + 1}, - {128, 4 + 2}, - {-1, 4 + 1}, -} - -func TestIntLength(t *testing.T) { - for _, test := range intLengthTests { - v := new(big.Int).SetInt64(int64(test.val)) - length := intLength(v) - if length != test.length { - t.Errorf("For %d, got length %d but expected %d", test.val, length, test.length) - } - } -} - -var messageTypes = []interface{}{ - &kexInitMsg{}, - &kexDHInitMsg{}, - &serviceRequestMsg{}, - &serviceAcceptMsg{}, - &userAuthRequestMsg{}, - &channelOpenMsg{}, - &channelOpenConfirmMsg{}, - &channelOpenFailureMsg{}, - &channelRequestMsg{}, - &channelRequestSuccessMsg{}, -} - -func TestMarshalUnmarshal(t *testing.T) { - rand := rand.New(rand.NewSource(0)) - for i, iface := range messageTypes { - ty := reflect.ValueOf(iface).Type() - - n := 100 - if testing.Short() { - n = 5 - } - for j := 0; j < n; j++ { - v, ok := quick.Value(ty, rand) - if !ok { - t.Errorf("#%d: failed to create value", i) - break - } - - m1 := v.Elem().Interface() - m2 := iface - - marshaled := marshal(msgIgnore, m1) - if err := unmarshal(m2, marshaled, msgIgnore); err != nil { - t.Errorf("#%d failed to unmarshal %#v: %s", i, m1, err) - break - } - - if !reflect.DeepEqual(v.Interface(), m2) { - t.Errorf("#%d\ngot: %#v\nwant:%#v\n%x", i, m2, m1, marshaled) - break - } - } - } -} - -func TestUnmarshalEmptyPacket(t *testing.T) { - var b []byte - var m channelRequestSuccessMsg - err := unmarshal(&m, b, msgChannelRequest) - want := ParseError{msgChannelRequest} - if _, ok := err.(ParseError); !ok { - t.Fatalf("got %T, want %T", err, want) - } - if got := err.(ParseError); want != got { - t.Fatal("got %#v, want %#v", got, want) - } -} - -func TestUnmarshalUnexpectedPacket(t *testing.T) { - type S struct { - I uint32 - S string - B bool - } - - s := S{42, "hello", true} - packet := marshal(42, s) - roundtrip := S{} - err := unmarshal(&roundtrip, packet, 43) - if err == nil { - t.Fatal("expected error, not nil") - } - want := UnexpectedMessageError{43, 42} - if got, ok := err.(UnexpectedMessageError); !ok || want != got { - t.Fatal("expected %q, got %q", want, got) - } -} - -func TestBareMarshalUnmarshal(t *testing.T) { - type S struct { - I uint32 - S string - B bool - } - - s := S{42, "hello", true} - packet := marshal(0, s) - roundtrip := S{} - unmarshal(&roundtrip, packet, 0) - - if !reflect.DeepEqual(s, roundtrip) { - t.Errorf("got %#v, want %#v", roundtrip, s) - } -} - -func TestBareMarshal(t *testing.T) { - type S2 struct { - I uint32 - } - s := S2{42} - packet := marshal(0, s) - i, rest, ok := parseUint32(packet) - if len(rest) > 0 || !ok { - t.Errorf("parseInt(%q): parse error", packet) - } - if i != s.I { - t.Errorf("got %d, want %d", i, s.I) - } -} - -func randomBytes(out []byte, rand *rand.Rand) { - for i := 0; i < len(out); i++ { - out[i] = byte(rand.Int31()) - } -} - -func randomNameList(rand *rand.Rand) []string { - ret := make([]string, rand.Int31()&15) - for i := range ret { - s := make([]byte, 1+(rand.Int31()&15)) - for j := range s { - s[j] = 'a' + uint8(rand.Int31()&15) - } - ret[i] = string(s) - } - return ret -} - -func randomInt(rand *rand.Rand) *big.Int { - return new(big.Int).SetInt64(int64(int32(rand.Uint32()))) -} - -func (*kexInitMsg) Generate(rand *rand.Rand, size int) reflect.Value { - ki := &kexInitMsg{} - randomBytes(ki.Cookie[:], rand) - ki.KexAlgos = randomNameList(rand) - ki.ServerHostKeyAlgos = randomNameList(rand) - ki.CiphersClientServer = randomNameList(rand) - ki.CiphersServerClient = randomNameList(rand) - ki.MACsClientServer = randomNameList(rand) - ki.MACsServerClient = randomNameList(rand) - ki.CompressionClientServer = randomNameList(rand) - ki.CompressionServerClient = randomNameList(rand) - ki.LanguagesClientServer = randomNameList(rand) - ki.LanguagesServerClient = randomNameList(rand) - if rand.Int31()&1 == 1 { - ki.FirstKexFollows = true - } - return reflect.ValueOf(ki) -} - -func (*kexDHInitMsg) Generate(rand *rand.Rand, size int) reflect.Value { - dhi := &kexDHInitMsg{} - dhi.X = randomInt(rand) - return reflect.ValueOf(dhi) -} - -// TODO(dfc) maybe this can be removed in the future if testing/quick can handle -// derived basic types. -func (RejectionReason) Generate(rand *rand.Rand, size int) reflect.Value { - m := RejectionReason(Prohibited) - return reflect.ValueOf(m) -} - -var ( - _kexInitMsg = new(kexInitMsg).Generate(rand.New(rand.NewSource(0)), 10).Elem().Interface() - _kexDHInitMsg = new(kexDHInitMsg).Generate(rand.New(rand.NewSource(0)), 10).Elem().Interface() - - _kexInit = marshal(msgKexInit, _kexInitMsg) - _kexDHInit = marshal(msgKexDHInit, _kexDHInitMsg) -) - -func BenchmarkMarshalKexInitMsg(b *testing.B) { - for i := 0; i < b.N; i++ { - marshal(msgKexInit, _kexInitMsg) - } -} - -func BenchmarkUnmarshalKexInitMsg(b *testing.B) { - m := new(kexInitMsg) - for i := 0; i < b.N; i++ { - unmarshal(m, _kexInit, msgKexInit) - } -} - -func BenchmarkMarshalKexDHInitMsg(b *testing.B) { - for i := 0; i < b.N; i++ { - marshal(msgKexDHInit, _kexDHInitMsg) - } -} - -func BenchmarkUnmarshalKexDHInitMsg(b *testing.B) { - m := new(kexDHInitMsg) - for i := 0; i < b.N; i++ { - unmarshal(m, _kexDHInit, msgKexDHInit) - } -} diff --git a/vendor/code.google.com/p/go.crypto/ssh/session_test.go b/vendor/code.google.com/p/go.crypto/ssh/session_test.go deleted file mode 100644 index 5cff58a9f..000000000 --- a/vendor/code.google.com/p/go.crypto/ssh/session_test.go +++ /dev/null @@ -1,789 +0,0 @@ -// Copyright 2011 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package ssh - -// Session tests. - -import ( - "bytes" - crypto_rand "crypto/rand" - "io" - "io/ioutil" - "math/rand" - "net" - "testing" - - "code.google.com/p/go.crypto/ssh/terminal" -) - -type serverType func(*serverChan, *testing.T) - -// dial constructs a new test server and returns a *ClientConn. -func dial(handler serverType, t *testing.T) *ClientConn { - l, err := Listen("tcp", "127.0.0.1:0", serverConfig) - if err != nil { - t.Fatalf("unable to listen: %v", err) - } - go func() { - defer l.Close() - conn, err := l.Accept() - if err != nil { - t.Errorf("Unable to accept: %v", err) - return - } - defer conn.Close() - if err := conn.Handshake(); err != nil { - t.Errorf("Unable to handshake: %v", err) - return - } - done := make(chan struct{}) - for { - ch, err := conn.Accept() - if err == io.EOF || err == io.ErrUnexpectedEOF { - return - } - // We sometimes get ECONNRESET rather than EOF. - if _, ok := err.(*net.OpError); ok { - return - } - if err != nil { - t.Errorf("Unable to accept incoming channel request: %v", err) - return - } - if ch.ChannelType() != "session" { - ch.Reject(UnknownChannelType, "unknown channel type") - continue - } - ch.Accept() - go func() { - defer close(done) - handler(ch.(*serverChan), t) - }() - } - <-done - }() - - config := &ClientConfig{ - User: "testuser", - Auth: []ClientAuth{ - ClientAuthPassword(clientPassword), - }, - } - - c, err := Dial("tcp", l.Addr().String(), config) - if err != nil { - t.Fatalf("unable to dial remote side: %v", err) - } - return c -} - -// Test a simple string is returned to session.Stdout. -func TestSessionShell(t *testing.T) { - conn := dial(shellHandler, t) - defer conn.Close() - session, err := conn.NewSession() - if err != nil { - t.Fatalf("Unable to request new session: %v", err) - } - defer session.Close() - stdout := new(bytes.Buffer) - session.Stdout = stdout - if err := session.Shell(); err != nil { - t.Fatalf("Unable to execute command: %s", err) - } - if err := session.Wait(); err != nil { - t.Fatalf("Remote command did not exit cleanly: %v", err) - } - actual := stdout.String() - if actual != "golang" { - t.Fatalf("Remote shell did not return expected string: expected=golang, actual=%s", actual) - } -} - -// TODO(dfc) add support for Std{in,err}Pipe when the Server supports it. - -// Test a simple string is returned via StdoutPipe. -func TestSessionStdoutPipe(t *testing.T) { - conn := dial(shellHandler, t) - defer conn.Close() - session, err := conn.NewSession() - if err != nil { - t.Fatalf("Unable to request new session: %v", err) - } - defer session.Close() - stdout, err := session.StdoutPipe() - if err != nil { - t.Fatalf("Unable to request StdoutPipe(): %v", err) - } - var buf bytes.Buffer - if err := session.Shell(); err != nil { - t.Fatalf("Unable to execute command: %v", err) - } - done := make(chan bool, 1) - go func() { - if _, err := io.Copy(&buf, stdout); err != nil { - t.Errorf("Copy of stdout failed: %v", err) - } - done <- true - }() - if err := session.Wait(); err != nil { - t.Fatalf("Remote command did not exit cleanly: %v", err) - } - <-done - actual := buf.String() - if actual != "golang" { - t.Fatalf("Remote shell did not return expected string: expected=golang, actual=%s", actual) - } -} - -// Test that a simple string is returned via the Output helper, -// and that stderr is discarded. -func TestSessionOutput(t *testing.T) { - conn := dial(fixedOutputHandler, t) - defer conn.Close() - session, err := conn.NewSession() - if err != nil { - t.Fatalf("Unable to request new session: %v", err) - } - defer session.Close() - - buf, err := session.Output("") // cmd is ignored by fixedOutputHandler - if err != nil { - t.Error("Remote command did not exit cleanly:", err) - } - w := "this-is-stdout." - g := string(buf) - if g != w { - t.Error("Remote command did not return expected string:") - t.Logf("want %q", w) - t.Logf("got %q", g) - } -} - -// Test that both stdout and stderr are returned -// via the CombinedOutput helper. -func TestSessionCombinedOutput(t *testing.T) { - conn := dial(fixedOutputHandler, t) - defer conn.Close() - session, err := conn.NewSession() - if err != nil { - t.Fatalf("Unable to request new session: %v", err) - } - defer session.Close() - - buf, err := session.CombinedOutput("") // cmd is ignored by fixedOutputHandler - if err != nil { - t.Error("Remote command did not exit cleanly:", err) - } - const stdout = "this-is-stdout." - const stderr = "this-is-stderr." - g := string(buf) - if g != stdout+stderr && g != stderr+stdout { - t.Error("Remote command did not return expected string:") - t.Logf("want %q, or %q", stdout+stderr, stderr+stdout) - t.Logf("got %q", g) - } -} - -// Test non-0 exit status is returned correctly. -func TestExitStatusNonZero(t *testing.T) { - conn := dial(exitStatusNonZeroHandler, t) - defer conn.Close() - session, err := conn.NewSession() - if err != nil { - t.Fatalf("Unable to request new session: %v", err) - } - defer session.Close() - if err := session.Shell(); err != nil { - t.Fatalf("Unable to execute command: %v", err) - } - err = session.Wait() - if err == nil { - t.Fatalf("expected command to fail but it didn't") - } - e, ok := err.(*ExitError) - if !ok { - t.Fatalf("expected *ExitError but got %T", err) - } - if e.ExitStatus() != 15 { - t.Fatalf("expected command to exit with 15 but got %v", e.ExitStatus()) - } -} - -// Test 0 exit status is returned correctly. -func TestExitStatusZero(t *testing.T) { - conn := dial(exitStatusZeroHandler, t) - defer conn.Close() - session, err := conn.NewSession() - if err != nil { - t.Fatalf("Unable to request new session: %v", err) - } - defer session.Close() - - if err := session.Shell(); err != nil { - t.Fatalf("Unable to execute command: %v", err) - } - err = session.Wait() - if err != nil { - t.Fatalf("expected nil but got %v", err) - } -} - -// Test exit signal and status are both returned correctly. -func TestExitSignalAndStatus(t *testing.T) { - conn := dial(exitSignalAndStatusHandler, t) - defer conn.Close() - session, err := conn.NewSession() - if err != nil { - t.Fatalf("Unable to request new session: %v", err) - } - defer session.Close() - if err := session.Shell(); err != nil { - t.Fatalf("Unable to execute command: %v", err) - } - err = session.Wait() - if err == nil { - t.Fatalf("expected command to fail but it didn't") - } - e, ok := err.(*ExitError) - if !ok { - t.Fatalf("expected *ExitError but got %T", err) - } - if e.Signal() != "TERM" || e.ExitStatus() != 15 { - t.Fatalf("expected command to exit with signal TERM and status 15 but got signal %s and status %v", e.Signal(), e.ExitStatus()) - } -} - -// Test exit signal and status are both returned correctly. -func TestKnownExitSignalOnly(t *testing.T) { - conn := dial(exitSignalHandler, t) - defer conn.Close() - session, err := conn.NewSession() - if err != nil { - t.Fatalf("Unable to request new session: %v", err) - } - defer session.Close() - if err := session.Shell(); err != nil { - t.Fatalf("Unable to execute command: %v", err) - } - err = session.Wait() - if err == nil { - t.Fatalf("expected command to fail but it didn't") - } - e, ok := err.(*ExitError) - if !ok { - t.Fatalf("expected *ExitError but got %T", err) - } - if e.Signal() != "TERM" || e.ExitStatus() != 143 { - t.Fatalf("expected command to exit with signal TERM and status 143 but got signal %s and status %v", e.Signal(), e.ExitStatus()) - } -} - -// Test exit signal and status are both returned correctly. -func TestUnknownExitSignal(t *testing.T) { - conn := dial(exitSignalUnknownHandler, t) - defer conn.Close() - session, err := conn.NewSession() - if err != nil { - t.Fatalf("Unable to request new session: %v", err) - } - defer session.Close() - if err := session.Shell(); err != nil { - t.Fatalf("Unable to execute command: %v", err) - } - err = session.Wait() - if err == nil { - t.Fatalf("expected command to fail but it didn't") - } - e, ok := err.(*ExitError) - if !ok { - t.Fatalf("expected *ExitError but got %T", err) - } - if e.Signal() != "SYS" || e.ExitStatus() != 128 { - t.Fatalf("expected command to exit with signal SYS and status 128 but got signal %s and status %v", e.Signal(), e.ExitStatus()) - } -} - -// Test WaitMsg is not returned if the channel closes abruptly. -func TestExitWithoutStatusOrSignal(t *testing.T) { - conn := dial(exitWithoutSignalOrStatus, t) - defer conn.Close() - session, err := conn.NewSession() - if err != nil { - t.Fatalf("Unable to request new session: %v", err) - } - defer session.Close() - if err := session.Shell(); err != nil { - t.Fatalf("Unable to execute command: %v", err) - } - err = session.Wait() - if err == nil { - t.Fatalf("expected command to fail but it didn't") - } - _, ok := err.(*ExitError) - if ok { - // you can't actually test for errors.errorString - // because it's not exported. - t.Fatalf("expected *errorString but got %T", err) - } -} - -func TestInvalidServerMessage(t *testing.T) { - conn := dial(sendInvalidRecord, t) - defer conn.Close() - session, err := conn.NewSession() - if err != nil { - t.Fatalf("Unable to request new session: %v", err) - } - // Make sure that we closed all the clientChans when the connection - // failed. - session.wait() - - defer session.Close() -} - -// In the wild some clients (and servers) send zero sized window updates. -// Test that the client can continue after receiving a zero sized update. -func TestClientZeroWindowAdjust(t *testing.T) { - conn := dial(sendZeroWindowAdjust, t) - defer conn.Close() - session, err := conn.NewSession() - if err != nil { - t.Fatalf("Unable to request new session: %v", err) - } - defer session.Close() - - if err := session.Shell(); err != nil { - t.Fatalf("Unable to execute command: %v", err) - } - err = session.Wait() - if err != nil { - t.Fatalf("expected nil but got %v", err) - } -} - -// In the wild some clients (and servers) send zero sized window updates. -// Test that the server can continue after receiving a zero size update. -func TestServerZeroWindowAdjust(t *testing.T) { - conn := dial(exitStatusZeroHandler, t) - defer conn.Close() - session, err := conn.NewSession() - if err != nil { - t.Fatalf("Unable to request new session: %v", err) - } - defer session.Close() - - if err := session.Shell(); err != nil { - t.Fatalf("Unable to execute command: %v", err) - } - - // send a bogus zero sized window update - session.clientChan.sendWindowAdj(0) - - err = session.Wait() - if err != nil { - t.Fatalf("expected nil but got %v", err) - } -} - -// Verify that the client never sends a packet larger than maxpacket. -func TestClientStdinRespectsMaxPacketSize(t *testing.T) { - conn := dial(discardHandler, t) - defer conn.Close() - session, err := conn.NewSession() - if err != nil { - t.Fatalf("failed to request new session: %v", err) - } - defer session.Close() - stdin, err := session.StdinPipe() - if err != nil { - t.Fatalf("failed to obtain stdinpipe: %v", err) - } - const size = 100 * 1000 - for i := 0; i < 10; i++ { - n, err := stdin.Write(make([]byte, size)) - if n != size || err != nil { - t.Fatalf("failed to write: %d, %v", n, err) - } - } -} - -// Verify that the client never accepts a packet larger than maxpacket. -func TestServerStdoutRespectsMaxPacketSize(t *testing.T) { - conn := dial(largeSendHandler, t) - defer conn.Close() - session, err := conn.NewSession() - if err != nil { - t.Fatalf("Unable to request new session: %v", err) - } - defer session.Close() - out, err := session.StdoutPipe() - if err != nil { - t.Fatalf("Unable to connect to Stdout: %v", err) - } - if err := session.Shell(); err != nil { - t.Fatalf("Unable to execute command: %v", err) - } - if _, err := ioutil.ReadAll(out); err != nil { - t.Fatalf("failed to read: %v", err) - } -} - -func TestClientCannotSendAfterEOF(t *testing.T) { - conn := dial(exitWithoutSignalOrStatus, t) - defer conn.Close() - session, err := conn.NewSession() - if err != nil { - t.Fatalf("Unable to request new session: %v", err) - } - defer session.Close() - in, err := session.StdinPipe() - if err != nil { - t.Fatalf("Unable to connect channel stdin: %v", err) - } - if err := session.Shell(); err != nil { - t.Fatalf("Unable to execute command: %v", err) - } - if err := in.Close(); err != nil { - t.Fatalf("Unable to close stdin: %v", err) - } - if _, err := in.Write([]byte("foo")); err == nil { - t.Fatalf("Session write should fail") - } -} - -func TestClientCannotSendAfterClose(t *testing.T) { - conn := dial(exitWithoutSignalOrStatus, t) - defer conn.Close() - session, err := conn.NewSession() - if err != nil { - t.Fatalf("Unable to request new session: %v", err) - } - defer session.Close() - in, err := session.StdinPipe() - if err != nil { - t.Fatalf("Unable to connect channel stdin: %v", err) - } - if err := session.Shell(); err != nil { - t.Fatalf("Unable to execute command: %v", err) - } - // close underlying channel - if err := session.channel.Close(); err != nil { - t.Fatalf("Unable to close session: %v", err) - } - if _, err := in.Write([]byte("foo")); err == nil { - t.Fatalf("Session write should fail") - } -} - -func TestClientCannotSendHugePacket(t *testing.T) { - // client and server use the same transport write code so this - // test suffices for both. - conn := dial(shellHandler, t) - defer conn.Close() - if err := conn.transport.writePacket(make([]byte, maxPacket*2)); err == nil { - t.Fatalf("huge packet write should fail") - } -} - -// windowTestBytes is the number of bytes that we'll send to the SSH server. -const windowTestBytes = 16000 * 200 - -// TestServerWindow writes random data to the server. The server is expected to echo -// the same data back, which is compared against the original. -func TestServerWindow(t *testing.T) { - origBuf := bytes.NewBuffer(make([]byte, 0, windowTestBytes)) - io.CopyN(origBuf, crypto_rand.Reader, windowTestBytes) - origBytes := origBuf.Bytes() - - conn := dial(echoHandler, t) - defer conn.Close() - session, err := conn.NewSession() - if err != nil { - t.Fatal(err) - } - defer session.Close() - result := make(chan []byte) - - go func() { - defer close(result) - echoedBuf := bytes.NewBuffer(make([]byte, 0, windowTestBytes)) - serverStdout, err := session.StdoutPipe() - if err != nil { - t.Errorf("StdoutPipe failed: %v", err) - return - } - n, err := copyNRandomly("stdout", echoedBuf, serverStdout, windowTestBytes) - if err != nil && err != io.EOF { - t.Errorf("Read only %d bytes from server, expected %d: %v", n, windowTestBytes, err) - } - result <- echoedBuf.Bytes() - }() - - serverStdin, err := session.StdinPipe() - if err != nil { - t.Fatalf("StdinPipe failed: %v", err) - } - written, err := copyNRandomly("stdin", serverStdin, origBuf, windowTestBytes) - if err != nil { - t.Fatalf("failed to copy origBuf to serverStdin: %v", err) - } - if written != windowTestBytes { - t.Fatalf("Wrote only %d of %d bytes to server", written, windowTestBytes) - } - - echoedBytes := <-result - - if !bytes.Equal(origBytes, echoedBytes) { - t.Fatalf("Echoed buffer differed from original, orig %d, echoed %d", len(origBytes), len(echoedBytes)) - } -} - -// Verify the client can handle a keepalive packet from the server. -func TestClientHandlesKeepalives(t *testing.T) { - conn := dial(channelKeepaliveSender, t) - defer conn.Close() - session, err := conn.NewSession() - if err != nil { - t.Fatal(err) - } - defer session.Close() - if err := session.Shell(); err != nil { - t.Fatalf("Unable to execute command: %v", err) - } - err = session.Wait() - if err != nil { - t.Fatalf("expected nil but got: %v", err) - } -} - -type exitStatusMsg struct { - PeersId uint32 - Request string - WantReply bool - Status uint32 -} - -type exitSignalMsg struct { - PeersId uint32 - Request string - WantReply bool - Signal string - CoreDumped bool - Errmsg string - Lang string -} - -func newServerShell(ch *serverChan, prompt string) *ServerTerminal { - term := terminal.NewTerminal(ch, prompt) - return &ServerTerminal{ - Term: term, - Channel: ch, - } -} - -func exitStatusZeroHandler(ch *serverChan, t *testing.T) { - defer ch.Close() - // this string is returned to stdout - shell := newServerShell(ch, "> ") - readLine(shell, t) - sendStatus(0, ch, t) -} - -func exitStatusNonZeroHandler(ch *serverChan, t *testing.T) { - defer ch.Close() - shell := newServerShell(ch, "> ") - readLine(shell, t) - sendStatus(15, ch, t) -} - -func exitSignalAndStatusHandler(ch *serverChan, t *testing.T) { - defer ch.Close() - shell := newServerShell(ch, "> ") - readLine(shell, t) - sendStatus(15, ch, t) - sendSignal("TERM", ch, t) -} - -func exitSignalHandler(ch *serverChan, t *testing.T) { - defer ch.Close() - shell := newServerShell(ch, "> ") - readLine(shell, t) - sendSignal("TERM", ch, t) -} - -func exitSignalUnknownHandler(ch *serverChan, t *testing.T) { - defer ch.Close() - shell := newServerShell(ch, "> ") - readLine(shell, t) - sendSignal("SYS", ch, t) -} - -func exitWithoutSignalOrStatus(ch *serverChan, t *testing.T) { - defer ch.Close() - shell := newServerShell(ch, "> ") - readLine(shell, t) -} - -func shellHandler(ch *serverChan, t *testing.T) { - defer ch.Close() - // this string is returned to stdout - shell := newServerShell(ch, "golang") - readLine(shell, t) - sendStatus(0, ch, t) -} - -// Ignores the command, writes fixed strings to stderr and stdout. -// Strings are "this-is-stdout." and "this-is-stderr.". -func fixedOutputHandler(ch *serverChan, t *testing.T) { - defer ch.Close() - - _, err := ch.Read(make([]byte, 0)) - if _, ok := err.(ChannelRequest); !ok { - t.Fatalf("error: expected channel request, got: %#v", err) - return - } - // ignore request, always send some text - ch.AckRequest(true) - - _, err = io.WriteString(ch, "this-is-stdout.") - if err != nil { - t.Fatalf("error writing on server: %v", err) - } - _, err = io.WriteString(ch.Stderr(), "this-is-stderr.") - if err != nil { - t.Fatalf("error writing on server: %v", err) - } - sendStatus(0, ch, t) -} - -func readLine(shell *ServerTerminal, t *testing.T) { - if _, err := shell.ReadLine(); err != nil && err != io.EOF { - t.Errorf("unable to read line: %v", err) - } -} - -func sendStatus(status uint32, ch *serverChan, t *testing.T) { - msg := exitStatusMsg{ - PeersId: ch.remoteId, - Request: "exit-status", - WantReply: false, - Status: status, - } - if err := ch.writePacket(marshal(msgChannelRequest, msg)); err != nil { - t.Errorf("unable to send status: %v", err) - } -} - -func sendSignal(signal string, ch *serverChan, t *testing.T) { - sig := exitSignalMsg{ - PeersId: ch.remoteId, - Request: "exit-signal", - WantReply: false, - Signal: signal, - CoreDumped: false, - Errmsg: "Process terminated", - Lang: "en-GB-oed", - } - if err := ch.writePacket(marshal(msgChannelRequest, sig)); err != nil { - t.Errorf("unable to send signal: %v", err) - } -} - -func sendInvalidRecord(ch *serverChan, t *testing.T) { - defer ch.Close() - packet := make([]byte, 1+4+4+1) - packet[0] = msgChannelData - marshalUint32(packet[1:], 29348723 /* invalid channel id */) - marshalUint32(packet[5:], 1) - packet[9] = 42 - - if err := ch.writePacket(packet); err != nil { - t.Errorf("unable send invalid record: %v", err) - } -} - -func sendZeroWindowAdjust(ch *serverChan, t *testing.T) { - defer ch.Close() - // send a bogus zero sized window update - ch.sendWindowAdj(0) - shell := newServerShell(ch, "> ") - readLine(shell, t) - sendStatus(0, ch, t) -} - -func discardHandler(ch *serverChan, t *testing.T) { - defer ch.Close() - // grow the window to avoid being fooled by - // the initial 1 << 14 window. - ch.sendWindowAdj(1024 * 1024) - io.Copy(ioutil.Discard, ch) -} - -func largeSendHandler(ch *serverChan, t *testing.T) { - defer ch.Close() - // grow the window to avoid being fooled by - // the initial 1 << 14 window. - ch.sendWindowAdj(1024 * 1024) - shell := newServerShell(ch, "> ") - readLine(shell, t) - // try to send more than the 32k window - // will allow - if err := ch.writePacket(make([]byte, 128*1024)); err == nil { - t.Errorf("wrote packet larger than 32k") - } -} - -func echoHandler(ch *serverChan, t *testing.T) { - defer ch.Close() - if n, err := copyNRandomly("echohandler", ch, ch, windowTestBytes); err != nil { - t.Errorf("short write, wrote %d, expected %d: %v ", n, windowTestBytes, err) - } -} - -// copyNRandomly copies n bytes from src to dst. It uses a variable, and random, -// buffer size to exercise more code paths. -func copyNRandomly(title string, dst io.Writer, src io.Reader, n int) (int, error) { - var ( - buf = make([]byte, 32*1024) - written int - remaining = n - ) - for remaining > 0 { - l := rand.Intn(1 << 15) - if remaining < l { - l = remaining - } - nr, er := src.Read(buf[:l]) - nw, ew := dst.Write(buf[:nr]) - remaining -= nw - written += nw - if ew != nil { - return written, ew - } - if nr != nw { - return written, io.ErrShortWrite - } - if er != nil && er != io.EOF { - return written, er - } - } - return written, nil -} - -func channelKeepaliveSender(ch *serverChan, t *testing.T) { - defer ch.Close() - shell := newServerShell(ch, "> ") - readLine(shell, t) - msg := channelRequestMsg{ - PeersId: ch.remoteId, - Request: "keepalive@openssh.com", - WantReply: true, - } - if err := ch.writePacket(marshal(msgChannelRequest, msg)); err != nil { - t.Errorf("unable to send channel keepalive request: %v", err) - } - sendStatus(0, ch, t) -} diff --git a/vendor/code.google.com/p/go.crypto/ssh/tcpip_test.go b/vendor/code.google.com/p/go.crypto/ssh/tcpip_test.go deleted file mode 100644 index 7fa9fc43f..000000000 --- a/vendor/code.google.com/p/go.crypto/ssh/tcpip_test.go +++ /dev/null @@ -1,16 +0,0 @@ -package ssh - -import ( - "testing" -) - -func TestAutoPortListenBroken(t *testing.T) { - broken := "SSH-2.0-OpenSSH_5.9hh11" - works := "SSH-2.0-OpenSSH_6.1" - if !isBrokenOpenSSHVersion(broken) { - t.Errorf("version %q not marked as broken", broken) - } - if isBrokenOpenSSHVersion(works) { - t.Errorf("version %q marked as broken", works) - } -} diff --git a/vendor/code.google.com/p/go.crypto/ssh/terminal/terminal.go b/vendor/code.google.com/p/go.crypto/ssh/terminal/terminal.go deleted file mode 100644 index 86853d6b3..000000000 --- a/vendor/code.google.com/p/go.crypto/ssh/terminal/terminal.go +++ /dev/null @@ -1,699 +0,0 @@ -// Copyright 2011 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package terminal - -import ( - "io" - "sync" - "unicode/utf8" -) - -// EscapeCodes contains escape sequences that can be written to the terminal in -// order to achieve different styles of text. -type EscapeCodes struct { - // Foreground colors - Black, Red, Green, Yellow, Blue, Magenta, Cyan, White []byte - - // Reset all attributes - Reset []byte -} - -var vt100EscapeCodes = EscapeCodes{ - Black: []byte{keyEscape, '[', '3', '0', 'm'}, - Red: []byte{keyEscape, '[', '3', '1', 'm'}, - Green: []byte{keyEscape, '[', '3', '2', 'm'}, - Yellow: []byte{keyEscape, '[', '3', '3', 'm'}, - Blue: []byte{keyEscape, '[', '3', '4', 'm'}, - Magenta: []byte{keyEscape, '[', '3', '5', 'm'}, - Cyan: []byte{keyEscape, '[', '3', '6', 'm'}, - White: []byte{keyEscape, '[', '3', '7', 'm'}, - - Reset: []byte{keyEscape, '[', '0', 'm'}, -} - -// Terminal contains the state for running a VT100 terminal that is capable of -// reading lines of input. -type Terminal struct { - // AutoCompleteCallback, if non-null, is called for each keypress with - // the full input line and the current position of the cursor (in - // bytes, as an index into |line|). If it returns ok=false, the key - // press is processed normally. Otherwise it returns a replacement line - // and the new cursor position. - AutoCompleteCallback func(line string, pos int, key rune) (newLine string, newPos int, ok bool) - - // Escape contains a pointer to the escape codes for this terminal. - // It's always a valid pointer, although the escape codes themselves - // may be empty if the terminal doesn't support them. - Escape *EscapeCodes - - // lock protects the terminal and the state in this object from - // concurrent processing of a key press and a Write() call. - lock sync.Mutex - - c io.ReadWriter - prompt string - - // line is the current line being entered. - line []rune - // pos is the logical position of the cursor in line - pos int - // echo is true if local echo is enabled - echo bool - - // cursorX contains the current X value of the cursor where the left - // edge is 0. cursorY contains the row number where the first row of - // the current line is 0. - cursorX, cursorY int - // maxLine is the greatest value of cursorY so far. - maxLine int - - termWidth, termHeight int - - // outBuf contains the terminal data to be sent. - outBuf []byte - // remainder contains the remainder of any partial key sequences after - // a read. It aliases into inBuf. - remainder []byte - inBuf [256]byte - - // history contains previously entered commands so that they can be - // accessed with the up and down keys. - history stRingBuffer - // historyIndex stores the currently accessed history entry, where zero - // means the immediately previous entry. - historyIndex int - // When navigating up and down the history it's possible to return to - // the incomplete, initial line. That value is stored in - // historyPending. - historyPending string -} - -// NewTerminal runs a VT100 terminal on the given ReadWriter. If the ReadWriter is -// a local terminal, that terminal must first have been put into raw mode. -// prompt is a string that is written at the start of each input line (i.e. -// "> "). -func NewTerminal(c io.ReadWriter, prompt string) *Terminal { - return &Terminal{ - Escape: &vt100EscapeCodes, - c: c, - prompt: prompt, - termWidth: 80, - termHeight: 24, - echo: true, - historyIndex: -1, - } -} - -const ( - keyCtrlD = 4 - keyEnter = '\r' - keyEscape = 27 - keyBackspace = 127 - keyUnknown = 0xd800 /* UTF-16 surrogate area */ + iota - keyUp - keyDown - keyLeft - keyRight - keyAltLeft - keyAltRight - keyHome - keyEnd - keyDeleteWord - keyDeleteLine -) - -// bytesToKey tries to parse a key sequence from b. If successful, it returns -// the key and the remainder of the input. Otherwise it returns utf8.RuneError. -func bytesToKey(b []byte) (rune, []byte) { - if len(b) == 0 { - return utf8.RuneError, nil - } - - switch b[0] { - case 1: // ^A - return keyHome, b[1:] - case 5: // ^E - return keyEnd, b[1:] - case 8: // ^H - return keyBackspace, b[1:] - case 11: // ^K - return keyDeleteLine, b[1:] - case 23: // ^W - return keyDeleteWord, b[1:] - } - - if b[0] != keyEscape { - if !utf8.FullRune(b) { - return utf8.RuneError, b - } - r, l := utf8.DecodeRune(b) - return r, b[l:] - } - - if len(b) >= 3 && b[0] == keyEscape && b[1] == '[' { - switch b[2] { - case 'A': - return keyUp, b[3:] - case 'B': - return keyDown, b[3:] - case 'C': - return keyRight, b[3:] - case 'D': - return keyLeft, b[3:] - } - } - - if len(b) >= 3 && b[0] == keyEscape && b[1] == 'O' { - switch b[2] { - case 'H': - return keyHome, b[3:] - case 'F': - return keyEnd, b[3:] - } - } - - if len(b) >= 6 && b[0] == keyEscape && b[1] == '[' && b[2] == '1' && b[3] == ';' && b[4] == '3' { - switch b[5] { - case 'C': - return keyAltRight, b[6:] - case 'D': - return keyAltLeft, b[6:] - } - } - - // If we get here then we have a key that we don't recognise, or a - // partial sequence. It's not clear how one should find the end of a - // sequence without knowing them all, but it seems that [a-zA-Z] only - // appears at the end of a sequence. - for i, c := range b[0:] { - if c >= 'a' && c <= 'z' || c >= 'A' && c <= 'Z' { - return keyUnknown, b[i+1:] - } - } - - return utf8.RuneError, b -} - -// queue appends data to the end of t.outBuf -func (t *Terminal) queue(data []rune) { - t.outBuf = append(t.outBuf, []byte(string(data))...) -} - -var eraseUnderCursor = []rune{' ', keyEscape, '[', 'D'} -var space = []rune{' '} - -func isPrintable(key rune) bool { - isInSurrogateArea := key >= 0xd800 && key <= 0xdbff - return key >= 32 && !isInSurrogateArea -} - -// moveCursorToPos appends data to t.outBuf which will move the cursor to the -// given, logical position in the text. -func (t *Terminal) moveCursorToPos(pos int) { - if !t.echo { - return - } - - x := len(t.prompt) + pos - y := x / t.termWidth - x = x % t.termWidth - - up := 0 - if y < t.cursorY { - up = t.cursorY - y - } - - down := 0 - if y > t.cursorY { - down = y - t.cursorY - } - - left := 0 - if x < t.cursorX { - left = t.cursorX - x - } - - right := 0 - if x > t.cursorX { - right = x - t.cursorX - } - - t.cursorX = x - t.cursorY = y - t.move(up, down, left, right) -} - -func (t *Terminal) move(up, down, left, right int) { - movement := make([]rune, 3*(up+down+left+right)) - m := movement - for i := 0; i < up; i++ { - m[0] = keyEscape - m[1] = '[' - m[2] = 'A' - m = m[3:] - } - for i := 0; i < down; i++ { - m[0] = keyEscape - m[1] = '[' - m[2] = 'B' - m = m[3:] - } - for i := 0; i < left; i++ { - m[0] = keyEscape - m[1] = '[' - m[2] = 'D' - m = m[3:] - } - for i := 0; i < right; i++ { - m[0] = keyEscape - m[1] = '[' - m[2] = 'C' - m = m[3:] - } - - t.queue(movement) -} - -func (t *Terminal) clearLineToRight() { - op := []rune{keyEscape, '[', 'K'} - t.queue(op) -} - -const maxLineLength = 4096 - -func (t *Terminal) setLine(newLine []rune, newPos int) { - if t.echo { - t.moveCursorToPos(0) - t.writeLine(newLine) - for i := len(newLine); i < len(t.line); i++ { - t.writeLine(space) - } - t.moveCursorToPos(newPos) - } - t.line = newLine - t.pos = newPos -} - -func (t *Terminal) eraseNPreviousChars(n int) { - if n == 0 { - return - } - - if t.pos < n { - n = t.pos - } - t.pos -= n - t.moveCursorToPos(t.pos) - - copy(t.line[t.pos:], t.line[n+t.pos:]) - t.line = t.line[:len(t.line)-n] - if t.echo { - t.writeLine(t.line[t.pos:]) - for i := 0; i < n; i++ { - t.queue(space) - } - t.cursorX += n - t.moveCursorToPos(t.pos) - } -} - -// countToLeftWord returns then number of characters from the cursor to the -// start of the previous word. -func (t *Terminal) countToLeftWord() int { - if t.pos == 0 { - return 0 - } - - pos := t.pos - 1 - for pos > 0 { - if t.line[pos] != ' ' { - break - } - pos-- - } - for pos > 0 { - if t.line[pos] == ' ' { - pos++ - break - } - pos-- - } - - return t.pos - pos -} - -// countToRightWord returns then number of characters from the cursor to the -// start of the next word. -func (t *Terminal) countToRightWord() int { - pos := t.pos - for pos < len(t.line) { - if t.line[pos] == ' ' { - break - } - pos++ - } - for pos < len(t.line) { - if t.line[pos] != ' ' { - break - } - pos++ - } - return pos - t.pos -} - -// handleKey processes the given key and, optionally, returns a line of text -// that the user has entered. -func (t *Terminal) handleKey(key rune) (line string, ok bool) { - switch key { - case keyBackspace: - if t.pos == 0 { - return - } - t.eraseNPreviousChars(1) - case keyAltLeft: - // move left by a word. - t.pos -= t.countToLeftWord() - t.moveCursorToPos(t.pos) - case keyAltRight: - // move right by a word. - t.pos += t.countToRightWord() - t.moveCursorToPos(t.pos) - case keyLeft: - if t.pos == 0 { - return - } - t.pos-- - t.moveCursorToPos(t.pos) - case keyRight: - if t.pos == len(t.line) { - return - } - t.pos++ - t.moveCursorToPos(t.pos) - case keyHome: - if t.pos == 0 { - return - } - t.pos = 0 - t.moveCursorToPos(t.pos) - case keyEnd: - if t.pos == len(t.line) { - return - } - t.pos = len(t.line) - t.moveCursorToPos(t.pos) - case keyUp: - entry, ok := t.history.NthPreviousEntry(t.historyIndex + 1) - if !ok { - return "", false - } - if t.historyIndex == -1 { - t.historyPending = string(t.line) - } - t.historyIndex++ - runes := []rune(entry) - t.setLine(runes, len(runes)) - case keyDown: - switch t.historyIndex { - case -1: - return - case 0: - runes := []rune(t.historyPending) - t.setLine(runes, len(runes)) - t.historyIndex-- - default: - entry, ok := t.history.NthPreviousEntry(t.historyIndex - 1) - if ok { - t.historyIndex-- - runes := []rune(entry) - t.setLine(runes, len(runes)) - } - } - case keyEnter: - t.moveCursorToPos(len(t.line)) - t.queue([]rune("\r\n")) - line = string(t.line) - ok = true - t.line = t.line[:0] - t.pos = 0 - t.cursorX = 0 - t.cursorY = 0 - t.maxLine = 0 - case keyDeleteWord: - // Delete zero or more spaces and then one or more characters. - t.eraseNPreviousChars(t.countToLeftWord()) - case keyDeleteLine: - // Delete everything from the current cursor position to the - // end of line. - for i := t.pos; i < len(t.line); i++ { - t.queue(space) - t.cursorX++ - } - t.line = t.line[:t.pos] - t.moveCursorToPos(t.pos) - default: - if t.AutoCompleteCallback != nil { - prefix := string(t.line[:t.pos]) - suffix := string(t.line[t.pos:]) - - t.lock.Unlock() - newLine, newPos, completeOk := t.AutoCompleteCallback(prefix+suffix, len(prefix), key) - t.lock.Lock() - - if completeOk { - t.setLine([]rune(newLine), utf8.RuneCount([]byte(newLine)[:newPos])) - return - } - } - if !isPrintable(key) { - return - } - if len(t.line) == maxLineLength { - return - } - if len(t.line) == cap(t.line) { - newLine := make([]rune, len(t.line), 2*(1+len(t.line))) - copy(newLine, t.line) - t.line = newLine - } - t.line = t.line[:len(t.line)+1] - copy(t.line[t.pos+1:], t.line[t.pos:]) - t.line[t.pos] = key - if t.echo { - t.writeLine(t.line[t.pos:]) - } - t.pos++ - t.moveCursorToPos(t.pos) - } - return -} - -func (t *Terminal) writeLine(line []rune) { - for len(line) != 0 { - remainingOnLine := t.termWidth - t.cursorX - todo := len(line) - if todo > remainingOnLine { - todo = remainingOnLine - } - t.queue(line[:todo]) - t.cursorX += todo - line = line[todo:] - - if t.cursorX == t.termWidth { - t.cursorX = 0 - t.cursorY++ - if t.cursorY > t.maxLine { - t.maxLine = t.cursorY - } - } - } -} - -func (t *Terminal) Write(buf []byte) (n int, err error) { - t.lock.Lock() - defer t.lock.Unlock() - - if t.cursorX == 0 && t.cursorY == 0 { - // This is the easy case: there's nothing on the screen that we - // have to move out of the way. - return t.c.Write(buf) - } - - // We have a prompt and possibly user input on the screen. We - // have to clear it first. - t.move(0 /* up */, 0 /* down */, t.cursorX /* left */, 0 /* right */) - t.cursorX = 0 - t.clearLineToRight() - - for t.cursorY > 0 { - t.move(1 /* up */, 0, 0, 0) - t.cursorY-- - t.clearLineToRight() - } - - if _, err = t.c.Write(t.outBuf); err != nil { - return - } - t.outBuf = t.outBuf[:0] - - if n, err = t.c.Write(buf); err != nil { - return - } - - t.queue([]rune(t.prompt)) - chars := len(t.prompt) - if t.echo { - t.queue(t.line) - chars += len(t.line) - } - t.cursorX = chars % t.termWidth - t.cursorY = chars / t.termWidth - t.moveCursorToPos(t.pos) - - if _, err = t.c.Write(t.outBuf); err != nil { - return - } - t.outBuf = t.outBuf[:0] - return -} - -// ReadPassword temporarily changes the prompt and reads a password, without -// echo, from the terminal. -func (t *Terminal) ReadPassword(prompt string) (line string, err error) { - t.lock.Lock() - defer t.lock.Unlock() - - oldPrompt := t.prompt - t.prompt = prompt - t.echo = false - - line, err = t.readLine() - - t.prompt = oldPrompt - t.echo = true - - return -} - -// ReadLine returns a line of input from the terminal. -func (t *Terminal) ReadLine() (line string, err error) { - t.lock.Lock() - defer t.lock.Unlock() - - return t.readLine() -} - -func (t *Terminal) readLine() (line string, err error) { - // t.lock must be held at this point - - if t.cursorX == 0 && t.cursorY == 0 { - t.writeLine([]rune(t.prompt)) - t.c.Write(t.outBuf) - t.outBuf = t.outBuf[:0] - } - - for { - rest := t.remainder - lineOk := false - for !lineOk { - var key rune - key, rest = bytesToKey(rest) - if key == utf8.RuneError { - break - } - if key == keyCtrlD { - return "", io.EOF - } - line, lineOk = t.handleKey(key) - } - if len(rest) > 0 { - n := copy(t.inBuf[:], rest) - t.remainder = t.inBuf[:n] - } else { - t.remainder = nil - } - t.c.Write(t.outBuf) - t.outBuf = t.outBuf[:0] - if lineOk { - if t.echo { - t.historyIndex = -1 - t.history.Add(line) - } - return - } - - // t.remainder is a slice at the beginning of t.inBuf - // containing a partial key sequence - readBuf := t.inBuf[len(t.remainder):] - var n int - - t.lock.Unlock() - n, err = t.c.Read(readBuf) - t.lock.Lock() - - if err != nil { - return - } - - t.remainder = t.inBuf[:n+len(t.remainder)] - } - - panic("unreachable") // for Go 1.0. -} - -// SetPrompt sets the prompt to be used when reading subsequent lines. -func (t *Terminal) SetPrompt(prompt string) { - t.lock.Lock() - defer t.lock.Unlock() - - t.prompt = prompt -} - -func (t *Terminal) SetSize(width, height int) { - t.lock.Lock() - defer t.lock.Unlock() - - t.termWidth, t.termHeight = width, height -} - -// stRingBuffer is a ring buffer of strings. -type stRingBuffer struct { - // entries contains max elements. - entries []string - max int - // head contains the index of the element most recently added to the ring. - head int - // size contains the number of elements in the ring. - size int -} - -func (s *stRingBuffer) Add(a string) { - if s.entries == nil { - const defaultNumEntries = 100 - s.entries = make([]string, defaultNumEntries) - s.max = defaultNumEntries - } - - s.head = (s.head + 1) % s.max - s.entries[s.head] = a - if s.size < s.max { - s.size++ - } -} - -// NthPreviousEntry returns the value passed to the nth previous call to Add. -// If n is zero then the immediately prior value is returned, if one, then the -// next most recent, and so on. If such an element doesn't exist then ok is -// false. -func (s *stRingBuffer) NthPreviousEntry(n int) (value string, ok bool) { - if n >= s.size { - return "", false - } - index := s.head - n - if index < 0 { - index += s.max - } - return s.entries[index], true -} diff --git a/vendor/code.google.com/p/go.crypto/ssh/terminal/terminal_test.go b/vendor/code.google.com/p/go.crypto/ssh/terminal/terminal_test.go deleted file mode 100644 index 641576c88..000000000 --- a/vendor/code.google.com/p/go.crypto/ssh/terminal/terminal_test.go +++ /dev/null @@ -1,209 +0,0 @@ -// Copyright 2011 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package terminal - -import ( - "io" - "testing" -) - -type MockTerminal struct { - toSend []byte - bytesPerRead int - received []byte -} - -func (c *MockTerminal) Read(data []byte) (n int, err error) { - n = len(data) - if n == 0 { - return - } - if n > len(c.toSend) { - n = len(c.toSend) - } - if n == 0 { - return 0, io.EOF - } - if c.bytesPerRead > 0 && n > c.bytesPerRead { - n = c.bytesPerRead - } - copy(data, c.toSend[:n]) - c.toSend = c.toSend[n:] - return -} - -func (c *MockTerminal) Write(data []byte) (n int, err error) { - c.received = append(c.received, data...) - return len(data), nil -} - -func TestClose(t *testing.T) { - c := &MockTerminal{} - ss := NewTerminal(c, "> ") - line, err := ss.ReadLine() - if line != "" { - t.Errorf("Expected empty line but got: %s", line) - } - if err != io.EOF { - t.Errorf("Error should have been EOF but got: %s", err) - } -} - -var keyPressTests = []struct { - in string - line string - err error - throwAwayLines int -}{ - { - err: io.EOF, - }, - { - in: "\r", - line: "", - }, - { - in: "foo\r", - line: "foo", - }, - { - in: "a\x1b[Cb\r", // right - line: "ab", - }, - { - in: "a\x1b[Db\r", // left - line: "ba", - }, - { - in: "a\177b\r", // backspace - line: "b", - }, - { - in: "\x1b[A\r", // up - }, - { - in: "\x1b[B\r", // down - }, - { - in: "line\x1b[A\x1b[B\r", // up then down - line: "line", - }, - { - in: "line1\rline2\x1b[A\r", // recall previous line. - line: "line1", - throwAwayLines: 1, - }, - { - // recall two previous lines and append. - in: "line1\rline2\rline3\x1b[A\x1b[Axxx\r", - line: "line1xxx", - throwAwayLines: 2, - }, - { - // Ctrl-A to move to beginning of line followed by ^K to kill - // line. - in: "a b \001\013\r", - line: "", - }, - { - // Ctrl-A to move to beginning of line, Ctrl-E to move to end, - // finally ^K to kill nothing. - in: "a b \001\005\013\r", - line: "a b ", - }, - { - in: "\027\r", - line: "", - }, - { - in: "a\027\r", - line: "", - }, - { - in: "a \027\r", - line: "", - }, - { - in: "a b\027\r", - line: "a ", - }, - { - in: "a b \027\r", - line: "a ", - }, - { - in: "one two thr\x1b[D\027\r", - line: "one two r", - }, - { - in: "\013\r", - line: "", - }, - { - in: "a\013\r", - line: "a", - }, - { - in: "ab\x1b[D\013\r", - line: "a", - }, - { - in: "Ξεσκεπάζω\r", - line: "Ξεσκεπάζω", - }, - { - in: "£\r\x1b[A\177\r", // non-ASCII char, enter, up, backspace. - line: "", - throwAwayLines: 1, - }, - { - in: "£\r££\x1b[A\x1b[B\177\r", // non-ASCII char, enter, 2x non-ASCII, up, down, backspace, enter. - line: "£", - throwAwayLines: 1, - }, -} - -func TestKeyPresses(t *testing.T) { - for i, test := range keyPressTests { - for j := 1; j < len(test.in); j++ { - c := &MockTerminal{ - toSend: []byte(test.in), - bytesPerRead: j, - } - ss := NewTerminal(c, "> ") - for k := 0; k < test.throwAwayLines; k++ { - _, err := ss.ReadLine() - if err != nil { - t.Errorf("Throwaway line %d from test %d resulted in error: %s", k, i, err) - } - } - line, err := ss.ReadLine() - if line != test.line { - t.Errorf("Line resulting from test %d (%d bytes per read) was '%s', expected '%s'", i, j, line, test.line) - break - } - if err != test.err { - t.Errorf("Error resulting from test %d (%d bytes per read) was '%v', expected '%v'", i, j, err, test.err) - break - } - } - } -} - -func TestPasswordNotSaved(t *testing.T) { - c := &MockTerminal{ - toSend: []byte("password\r\x1b[A\r"), - bytesPerRead: 1, - } - ss := NewTerminal(c, "> ") - pw, _ := ss.ReadPassword("> ") - if pw != "password" { - t.Fatalf("failed to read password, got %s", pw) - } - line, _ := ss.ReadLine() - if len(line) > 0 { - t.Fatalf("password was saved in history") - } -} diff --git a/vendor/code.google.com/p/go.crypto/ssh/terminal/util.go b/vendor/code.google.com/p/go.crypto/ssh/terminal/util.go deleted file mode 100644 index 8df94f5d6..000000000 --- a/vendor/code.google.com/p/go.crypto/ssh/terminal/util.go +++ /dev/null @@ -1,128 +0,0 @@ -// Copyright 2011 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -// +build linux,!appengine darwin - -// Package terminal provides support functions for dealing with terminals, as -// commonly found on UNIX systems. -// -// Putting a terminal into raw mode is the most common requirement: -// -// oldState, err := terminal.MakeRaw(0) -// if err != nil { -// panic(err) -// } -// defer terminal.Restore(0, oldState) -package terminal - -import ( - "io" - "syscall" - "unsafe" -) - -// State contains the state of a terminal. -type State struct { - termios syscall.Termios -} - -// IsTerminal returns true if the given file descriptor is a terminal. -func IsTerminal(fd int) bool { - var termios syscall.Termios - _, _, err := syscall.Syscall6(syscall.SYS_IOCTL, uintptr(fd), ioctlReadTermios, uintptr(unsafe.Pointer(&termios)), 0, 0, 0) - return err == 0 -} - -// MakeRaw put the terminal connected to the given file descriptor into raw -// mode and returns the previous state of the terminal so that it can be -// restored. -func MakeRaw(fd int) (*State, error) { - var oldState State - if _, _, err := syscall.Syscall6(syscall.SYS_IOCTL, uintptr(fd), ioctlReadTermios, uintptr(unsafe.Pointer(&oldState.termios)), 0, 0, 0); err != 0 { - return nil, err - } - - newState := oldState.termios - newState.Iflag &^= syscall.ISTRIP | syscall.INLCR | syscall.ICRNL | syscall.IGNCR | syscall.IXON | syscall.IXOFF - newState.Lflag &^= syscall.ECHO | syscall.ICANON | syscall.ISIG - if _, _, err := syscall.Syscall6(syscall.SYS_IOCTL, uintptr(fd), ioctlWriteTermios, uintptr(unsafe.Pointer(&newState)), 0, 0, 0); err != 0 { - return nil, err - } - - return &oldState, nil -} - -// GetState returns the current state of a terminal which may be useful to -// restore the terminal after a signal. -func GetState(fd int) (*State, error) { - var oldState State - if _, _, err := syscall.Syscall6(syscall.SYS_IOCTL, uintptr(fd), ioctlReadTermios, uintptr(unsafe.Pointer(&oldState.termios)), 0, 0, 0); err != 0 { - return nil, err - } - - return &oldState, nil -} - -// Restore restores the terminal connected to the given file descriptor to a -// previous state. -func Restore(fd int, state *State) error { - _, _, err := syscall.Syscall6(syscall.SYS_IOCTL, uintptr(fd), ioctlWriteTermios, uintptr(unsafe.Pointer(&state.termios)), 0, 0, 0) - return err -} - -// GetSize returns the dimensions of the given terminal. -func GetSize(fd int) (width, height int, err error) { - var dimensions [4]uint16 - - if _, _, err := syscall.Syscall6(syscall.SYS_IOCTL, uintptr(fd), uintptr(syscall.TIOCGWINSZ), uintptr(unsafe.Pointer(&dimensions)), 0, 0, 0); err != 0 { - return -1, -1, err - } - return int(dimensions[1]), int(dimensions[0]), nil -} - -// ReadPassword reads a line of input from a terminal without local echo. This -// is commonly used for inputting passwords and other sensitive data. The slice -// returned does not include the \n. -func ReadPassword(fd int) ([]byte, error) { - var oldState syscall.Termios - if _, _, err := syscall.Syscall6(syscall.SYS_IOCTL, uintptr(fd), ioctlReadTermios, uintptr(unsafe.Pointer(&oldState)), 0, 0, 0); err != 0 { - return nil, err - } - - newState := oldState - newState.Lflag &^= syscall.ECHO - newState.Lflag |= syscall.ICANON | syscall.ISIG - newState.Iflag |= syscall.ICRNL - if _, _, err := syscall.Syscall6(syscall.SYS_IOCTL, uintptr(fd), ioctlWriteTermios, uintptr(unsafe.Pointer(&newState)), 0, 0, 0); err != 0 { - return nil, err - } - - defer func() { - syscall.Syscall6(syscall.SYS_IOCTL, uintptr(fd), ioctlWriteTermios, uintptr(unsafe.Pointer(&oldState)), 0, 0, 0) - }() - - var buf [16]byte - var ret []byte - for { - n, err := syscall.Read(fd, buf[:]) - if err != nil { - return nil, err - } - if n == 0 { - if len(ret) == 0 { - return nil, io.EOF - } - break - } - if buf[n-1] == '\n' { - n-- - } - ret = append(ret, buf[:n]...) - if n < len(buf) { - break - } - } - - return ret, nil -} diff --git a/vendor/code.google.com/p/go.crypto/ssh/terminal/util_bsd.go b/vendor/code.google.com/p/go.crypto/ssh/terminal/util_bsd.go deleted file mode 100644 index 1654453bd..000000000 --- a/vendor/code.google.com/p/go.crypto/ssh/terminal/util_bsd.go +++ /dev/null @@ -1,12 +0,0 @@ -// Copyright 2013 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -// +build darwin - -package terminal - -import "syscall" - -const ioctlReadTermios = syscall.TIOCGETA -const ioctlWriteTermios = syscall.TIOCSETA diff --git a/vendor/code.google.com/p/go.crypto/ssh/terminal/util_linux.go b/vendor/code.google.com/p/go.crypto/ssh/terminal/util_linux.go deleted file mode 100644 index 283144b7b..000000000 --- a/vendor/code.google.com/p/go.crypto/ssh/terminal/util_linux.go +++ /dev/null @@ -1,12 +0,0 @@ -// Copyright 2013 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -// +build linux - -package terminal - -import "syscall" - -const ioctlReadTermios = syscall.TCGETS -const ioctlWriteTermios = syscall.TCSETS diff --git a/vendor/code.google.com/p/go.crypto/ssh/test/doc.go b/vendor/code.google.com/p/go.crypto/ssh/test/doc.go deleted file mode 100644 index 787b8fa20..000000000 --- a/vendor/code.google.com/p/go.crypto/ssh/test/doc.go +++ /dev/null @@ -1,7 +0,0 @@ -// Copyright 2012 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -// This package contains integration tests for the -// code.google.com/p/go.crypto/ssh package. -package test diff --git a/vendor/code.google.com/p/go.crypto/ssh/test/forward_unix_test.go b/vendor/code.google.com/p/go.crypto/ssh/test/forward_unix_test.go deleted file mode 100644 index 3a57c100c..000000000 --- a/vendor/code.google.com/p/go.crypto/ssh/test/forward_unix_test.go +++ /dev/null @@ -1,160 +0,0 @@ -// Copyright 2012 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -// +build darwin freebsd linux netbsd openbsd plan9 - -package test - -import ( - "bytes" - "io" - "io/ioutil" - "math/rand" - "net" - "testing" - "time" -) - -func TestPortForward(t *testing.T) { - server := newServer(t) - defer server.Shutdown() - conn := server.Dial(clientConfig()) - defer conn.Close() - - sshListener, err := conn.Listen("tcp", "localhost:0") - if err != nil { - t.Fatal(err) - } - - go func() { - sshConn, err := sshListener.Accept() - if err != nil { - t.Fatalf("listen.Accept failed: %v", err) - } - - _, err = io.Copy(sshConn, sshConn) - if err != nil && err != io.EOF { - t.Fatalf("ssh client copy: %v", err) - } - sshConn.Close() - }() - - forwardedAddr := sshListener.Addr().String() - tcpConn, err := net.Dial("tcp", forwardedAddr) - if err != nil { - t.Fatalf("TCP dial failed: %v", err) - } - - readChan := make(chan []byte) - go func() { - data, _ := ioutil.ReadAll(tcpConn) - readChan <- data - }() - - // Invent some data. - data := make([]byte, 100*1000) - for i := range data { - data[i] = byte(i % 255) - } - - var sent []byte - for len(sent) < 1000*1000 { - // Send random sized chunks - m := rand.Intn(len(data)) - n, err := tcpConn.Write(data[:m]) - if err != nil { - break - } - sent = append(sent, data[:n]...) - } - if err := tcpConn.(*net.TCPConn).CloseWrite(); err != nil { - t.Errorf("tcpConn.CloseWrite: %v", err) - } - - read := <-readChan - - if len(sent) != len(read) { - t.Fatalf("got %d bytes, want %d", len(read), len(sent)) - } - if bytes.Compare(sent, read) != 0 { - t.Fatalf("read back data does not match") - } - - if err := sshListener.Close(); err != nil { - t.Fatalf("sshListener.Close: %v", err) - } - - // Check that the forward disappeared. - tcpConn, err = net.Dial("tcp", forwardedAddr) - if err == nil { - tcpConn.Close() - t.Errorf("still listening to %s after closing", forwardedAddr) - } -} - -func TestAcceptClose(t *testing.T) { - server := newServer(t) - defer server.Shutdown() - conn := server.Dial(clientConfig()) - - sshListener, err := conn.Listen("tcp", "localhost:0") - if err != nil { - t.Fatal(err) - } - - quit := make(chan error, 1) - go func() { - for { - c, err := sshListener.Accept() - if err != nil { - quit <- err - break - } - c.Close() - } - }() - sshListener.Close() - - select { - case <-time.After(1 * time.Second): - t.Errorf("timeout: listener did not close.") - case err := <-quit: - t.Logf("quit as expected (error %v)", err) - } -} - -// Check that listeners exit if the underlying client transport dies. -func TestPortForwardConnectionClose(t *testing.T) { - server := newServer(t) - defer server.Shutdown() - conn := server.Dial(clientConfig()) - - sshListener, err := conn.Listen("tcp", "localhost:0") - if err != nil { - t.Fatal(err) - } - - quit := make(chan error, 1) - go func() { - for { - c, err := sshListener.Accept() - if err != nil { - quit <- err - break - } - c.Close() - } - }() - - // It would be even nicer if we closed the server side, but it - // is more involved as the fd for that side is dup()ed. - server.clientConn.Close() - - select { - case <-time.After(1 * time.Second): - t.Errorf("timeout: listener did not close.") - case err := <-quit: - t.Logf("quit as expected (error %v)", err) - } -} diff --git a/vendor/code.google.com/p/go.crypto/ssh/test/keys_test.go b/vendor/code.google.com/p/go.crypto/ssh/test/keys_test.go deleted file mode 100644 index b1164220e..000000000 --- a/vendor/code.google.com/p/go.crypto/ssh/test/keys_test.go +++ /dev/null @@ -1,246 +0,0 @@ -package test - -import ( - "reflect" - "strings" - "testing" - - "code.google.com/p/go.crypto/ssh" -) - -var ( - validKey = `AAAAB3NzaC1yc2EAAAADAQABAAABAQDEX/dPu4PmtvgK3La9zioCEDrJ` + - `yUr6xEIK7Pr+rLgydcqWTU/kt7w7gKjOw4vvzgHfjKl09CWyvgb+y5dCiTk` + - `9MxI+erGNhs3pwaoS+EavAbawB7iEqYyTep3YaJK+4RJ4OX7ZlXMAIMrTL+` + - `UVrK89t56hCkFYaAgo3VY+z6rb/b3bDBYtE1Y2tS7C3au73aDgeb9psIrSV` + - `86ucKBTl5X62FnYiyGd++xCnLB6uLximM5OKXfLzJQNS/QyZyk12g3D8y69` + - `Xw1GzCSKX1u1+MQboyf0HJcG2ryUCLHdcDVppApyHx2OLq53hlkQ/yxdflD` + - `qCqAE4j+doagSsIfC1T2T` - - authWithOptions = []string{ - `# comments to ignore before any keys...`, - ``, - `env="HOME=/home/root",no-port-forwarding ssh-rsa ` + validKey + ` user@host`, - `# comments to ignore, along with a blank line`, - ``, - `env="HOME=/home/root2" ssh-rsa ` + validKey + ` user2@host2`, - ``, - `# more comments, plus a invalid entry`, - `ssh-rsa data-that-will-not-parse user@host3`, - } - - authOptions = strings.Join(authWithOptions, "\n") - authWithCRLF = strings.Join(authWithOptions, "\r\n") - authInvalid = []byte(`ssh-rsa`) - authWithQuotedCommaInEnv = []byte(`env="HOME=/home/root,dir",no-port-forwarding ssh-rsa ` + validKey + ` user@host`) - authWithQuotedSpaceInEnv = []byte(`env="HOME=/home/root dir",no-port-forwarding ssh-rsa ` + validKey + ` user@host`) - authWithQuotedQuoteInEnv = []byte(`env="HOME=/home/\"root dir",no-port-forwarding` + "\t" + `ssh-rsa` + "\t" + validKey + ` user@host`) - - authWithDoubleQuotedQuote = []byte(`no-port-forwarding,env="HOME=/home/ \"root dir\"" ssh-rsa ` + validKey + "\t" + `user@host`) - authWithInvalidSpace = []byte(`env="HOME=/home/root dir", no-port-forwarding ssh-rsa ` + validKey + ` user@host -#more to follow but still no valid keys`) - authWithMissingQuote = []byte(`env="HOME=/home/root,no-port-forwarding ssh-rsa ` + validKey + ` user@host -env="HOME=/home/root",shared-control ssh-rsa ` + validKey + ` user@host`) - - testClientPrivateKey = `-----BEGIN RSA PRIVATE KEY----- -MIIEowIBAAKCAQEAxF/3T7uD5rb4Cty2vc4qAhA6yclK+sRCCuz6/qy4MnXKlk1P -5Le8O4CozsOL784B34ypdPQlsr4G/suXQok5PTMSPnqxjYbN6cGqEvhGrwG2sAe4 -hKmMk3qd2GiSvuESeDl+2ZVzACDK0y/lFayvPbeeoQpBWGgIKN1WPs+q2/292wwW -LRNWNrUuwt2ru92g4Hm/abCK0lfOrnCgU5eV+thZ2IshnfvsQpyweri8YpjOTil3 -y8yUDUv0MmcpNdoNw/MuvV8NRswkil9btfjEG6Mn9ByXBtq8lAix3XA1aaQKch8d -ji6ud4ZZEP8sXX5Q6gqgBOI/naGoErCHwtU9kwIDAQABAoIBAFJRKAp0QEZmTHPB -MZk+4r0asIoFpziXLFgIHu7C2DPOzK1Umzj1DCKlPB3wOqi7Ym2jOSWdcnAK2EPW -dAGgJC5TSkKGjAcXixmB5RkumfKidUI0+lQh/puTurcMnvcEwglDkLkEvMBA/sSo -Pw9m486rOgOnmNzGPyViItURmD2+0yDdLl/vOsO/L1p76GCd0q0J3LqnmsQmawi7 -Zwj2Stm6BIrggG5GsF204Iet5219TYLo4g1Qb2AlJ9C8P1FtAWhMwJalDxH9Os2/ -KCDjnaq5n3bXbIU+3QjskjeVXL/Fnbhjnh4zs1EA7eHzl9dCGbcZ2LOimo2PRo8q -wVQmz4ECgYEA9dhiu74TxRVoaO5N2X+FsMzRO8gZdP3Z9IrV4jVN8WT4Vdp0snoF -gkVkqqbQUNKUb5K6B3Js/qNKfcjLbCNq9fewTcT6WsHQdtPbX/QA6Pa2Z29wrlA2 -wrIYaAkmVaHny7wsOmgX01aOnuf2MlUnksK43sjZHdIo/m+sDKwwY1cCgYEAzHx4 -mwUDMdRF4qpDKJhthraBNejRextNQQYsHVnNaMwZ4aeQcH5l85Cgjm7VpGlbVyBQ -h4zwFvllImp3D2U3mjVkV8Tm9ID98eWvw2YDzBnS3P3SysajD23Z+BXSG9GNv/8k -oAm+bVlvnJy4haK2AcIMk1YFuDuAOmy73abk7iUCgYEAj4qVM1sq/eKfAM1LJRfg -/jbIX+hYfMePD8pUUWygIra6jJ4tjtvSBZrwyPb3IImjY3W/KoP0AcVjxAeORohz -dkP1a6L8LiuFxSuzpdW5BkyuebxGhXCOWKVVvMDC4jLTPVCUXlHSv3GFemCjjgXM -QlNxT5rjsha4Gr8nLIsJAacCgYA4VA1Q/pd7sXKy1p37X8nD8yAyvnh+Be5I/C9I -woUP2jFC9MqYAmmJJ4ziz2swiAkuPeuQ+2Tjnz2ZtmQnrIUdiJmkh8vrDGFnshKx -q7deELsCPzVCwGcIiAUkDra7DQWUHu9y2lxHePyC0rUNst2aLF8UcvzOXC2danhx -vViQtQKBgCmZ7YavE/GNWww8N3xHBJ6UPmUuhQlnAbgNCcdyz30MevBg/JbyUTs2 -slftTH15QusJ1UoITnnZuFJ40LqDvh8UhiK09ffM/IbUx839/m2vUOdFZB/WNn9g -Cy0LzddU4KE8JZ/tlk68+hM5fjLLA0aqSunaql5CKfplwLu8x1hL ------END RSA PRIVATE KEY----- -` - keys = map[string]string{ - "ssh_host_dsa_key": `-----BEGIN DSA PRIVATE KEY----- -MIIBugIBAAKBgQDe2SIKvZdBp+InawtSXH0NotiMPhm3udyu4hh/E+icMz264kDX -v+sV7ddnSQGQWZ/eVU7Jtx29dCMD1VlFpEd7yGKzmdwJIeA+YquNWoqBRQEJsWWS -7Fsfvv83dA/DTNIQfOY3+TIs6Mb9vagbgQMU3JUWEhbLE9LCEU6UwwRlpQIVAL4p -JF83SwpE8Jx6KnDpR89npkl/AoGAAy00TdDnAXvStwrZiAFbjZi8xDmPa9WwpfhJ -Rkno45TthDLrS+WmqY8/LTwlqZdOBtoBAynMJfKkUiZM21lWWpL1hRKYdwBlIBy5 -XdR2/6wcPSuZ0tCQhDBTstX0Q3P1j198KGKvzy7q9vILKQwtSRqLS1y4JJERafdO -E+9CnGwCgYBz0WwBe2EZtGhGhBdnelTIBeo7PIsr0PzqxQj+dc8PBl8K9FfhRyOp -U39stUvoUxE9vaIFrY1P5xENjLFnPf+hlcuf40GUWEssW9YWPOaBp8afa9hY5Sxs -pvNR6eZFEFOJnx/ZgcA4g+vbrgGi5cM0W470mbGw2CkfJQUafdoIgAIUF+2I9kZe -2FTBuC9uacqczDlc+0k= ------END DSA PRIVATE KEY-----`, - "ssh_host_rsa_key": `-----BEGIN RSA PRIVATE KEY----- -MIIEowIBAAKCAQEAuf76Ue2Wtae9oDtaS6rIJgO7iCFTsZUTW9LBsvx/2nli6jKU -d9tUbBRzgdbnRLJ32UljXhERuB/axlrX8/lBzUZ+oYiM0KkEEOXY1z/bcMxdRxGF -XHuf4uXvyC2XyA4+ZvBeS4j1QFyIHZ62o7gAlKMTjiek3B4AQEJAlCLmhH3jB8wc -K/IYXAOlNGM5G44/ZLQpTi8diOV6DLs7tJ7rtEQedOEJfZng5rwp0USFkqcbfDbe -9/hk0J32jZvOtZNBokYtBb4YEdIiWBzzNtHzU3Dzw61+TKVXaH5HaIvzL9iMrw9f -kJbJyogfZk9BJfemEN+xqP72jlhE8LXNhpTxFQIDAQABAoIBAHbdf+Y5+5XuNF6h -b8xpwW2h9whBnDYiOnP1VfroKWFbMB7R4lZS4joMO+FfkP8zOyqvHwTvza4pFWys -g9SUmDvy8FyVYsC7MzEFYzX0xm3o/Te898ip7P1Zy4rXsGeWysSImwqU5X+TYx3i -33/zyNM1APtZVJ+jwK9QZ+sD/uPuZK2yS03HGSMZq6ebdoOSaYhluKrxXllSLO1J -KJxDiDdy2lEFw0W8HcI3ly1lg6OI+TRqqaCcLVNF4fNJmYIFM+2VEI9BdgynIh0Q -pMZlJKgaEBcSqCymnTK81ohYD1cV4st2B0km3Sw35Rl04Ij5ITeiya3hp8VfE6UY -PljkA6UCgYEA4811FTFj+kzNZ86C4OW1T5sM4NZt8gcz6CSvVnl+bDzbEOMMyzP7 -2I9zKsR5ApdodH2m8d+RUw1Oe0bNGW5xig/DH/hn9lLQaO52JAi0we8A94dUUMSq -fUk9jKZEXpP/MlfTdJaPos9mxT7z8jREQxIiqH9AV0rLVDOCfDbSWj8CgYEA0QTE -IAUuki3UUqYKzLQrh/QmhY5KTx5amNW9XZ2VGtJvDPJrtBSBZlPEuXZAc4eBWEc7 -U3Y9QwsalzupU6Yi6+gmofaXs8xJnj+jKth1DnJvrbLLGlSmf2Ijnwt22TyFUOtt -UAknpjHutDjQPf7pUGWaCPgwwKFsdB8EBjpJF6sCgYAfXesBQAvEK08dPBJJZVfR -3kenrd71tIgxLtv1zETcIoUHjjv0vvOunhH9kZAYC0EWyTZzl5UrGmn0D4uuNMbt -e74iaNHn2P9Zc3xQ+eHp0j8P1lKFzI6tMaiH9Vz0qOw6wl0bcJ/WizhbcI+migvc -MGMVUHBLlMDqly0gbWwJgQKBgQCgtb9ut01FjANSwORQ3L8Tu3/a9Lrh9n7GQKFn -V4CLrP1BwStavOF5ojMCPo/zxF6JV8ufsqwL3n/FhFP/QyBarpb1tTqTPiHkkR2O -Ffx67TY9IdnUFv4lt3mYEiKBiW0f+MSF42Qe/wmAfKZw5IzUCirTdrFVi0huSGK5 -vxrwHQKBgHZ7RoC3I2f6F5fflA2ZAe9oJYC7XT624rY7VeOBwK0W0F47iV3euPi/ -pKvLIBLcWL1Lboo+girnmSZtIYg2iLS3b4T9VFcKWg0y4AVwmhMWe9jWIltfWAAX -9l0lNikMRGAx3eXudKXEtbGt3/cUzPVaQUHy5LiBxkxnFxgaJPXs ------END RSA PRIVATE KEY-----`, - "ssh_host_ecdsa_key": `-----BEGIN EC PRIVATE KEY----- -MHcCAQEEINGWx0zo6fhJ/0EAfrPzVFyFC9s18lBt3cRoEDhS3ARooAoGCCqGSM49 -AwEHoUQDQgAEi9Hdw6KvZcWxfg2IDhA7UkpDtzzt6ZqJXSsFdLd+Kx4S3Sx4cVO+ -6/ZOXRnPmNAlLUqjShUsUBBngG0u2fqEqA== ------END EC PRIVATE KEY-----`, - "authorized_keys": `ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDEX/dPu4PmtvgK3La9zioCEDrJyUr6xEIK7Pr+rLgydcqWTU/kt7w7gKjOw4vvzgHfjKl09CWyvgb+y5dCiTk9MxI+erGNhs3pwaoS+EavAbawB7iEqYyTep3YaJK+4RJ4OX7ZlXMAIMrTL+UVrK89t56hCkFYaAgo3VY+z6rb/b3bDBYtE1Y2tS7C3au73aDgeb9psIrSV86ucKBTl5X62FnYiyGd++xCnLB6uLximM5OKXfLzJQNS/QyZyk12g3D8y69Xw1GzCSKX1u1+MQboyf0HJcG2ryUCLHdcDVppApyHx2OLq53hlkQ/yxdflDqCqAE4j+doagSsIfC1T2T user@host`, - } -) - -func TestMarshalParsePublicKey(t *testing.T) { - pub := getTestPublicKey(t) - - authKeys := ssh.MarshalAuthorizedKey(pub) - actualFields := strings.Fields(string(authKeys)) - if len(actualFields) == 0 { - t.Fatalf("failed authKeys: %v", authKeys) - } - - // drop the comment - expectedFields := strings.Fields(keys["authorized_keys"])[0:2] - - if !reflect.DeepEqual(actualFields, expectedFields) { - t.Errorf("got %v, expected %v", actualFields, expectedFields) - } - - actPub, _, _, _, ok := ssh.ParseAuthorizedKey([]byte(keys["authorized_keys"])) - if !ok { - t.Fatalf("cannot parse %v", keys["authorized_keys"]) - } - if !reflect.DeepEqual(actPub, pub) { - t.Errorf("got %v, expected %v", actPub, pub) - } -} - -type authResult struct { - pubKey interface{} //*rsa.PublicKey - options []string - comments string - rest string - ok bool -} - -func testAuthorizedKeys(t *testing.T, authKeys []byte, expected []authResult) { - rest := authKeys - var values []authResult - for len(rest) > 0 { - var r authResult - r.pubKey, r.comments, r.options, rest, r.ok = ssh.ParseAuthorizedKey(rest) - r.rest = string(rest) - values = append(values, r) - } - - if !reflect.DeepEqual(values, expected) { - t.Errorf("got %q, expected %q", values, expected) - } - -} - -func getTestPublicKey(t *testing.T) ssh.PublicKey { - priv, err := ssh.ParsePrivateKey([]byte(testClientPrivateKey)) - if err != nil { - t.Fatalf("ParsePrivateKey: %v", err) - } - - return priv.PublicKey() -} - -func TestAuth(t *testing.T) { - pub := getTestPublicKey(t) - rest2 := strings.Join(authWithOptions[3:], "\n") - rest3 := strings.Join(authWithOptions[6:], "\n") - testAuthorizedKeys(t, []byte(authOptions), []authResult{ - {pub, []string{`env="HOME=/home/root"`, "no-port-forwarding"}, "user@host", rest2, true}, - {pub, []string{`env="HOME=/home/root2"`}, "user2@host2", rest3, true}, - {nil, nil, "", "", false}, - }) -} - -func TestAuthWithCRLF(t *testing.T) { - pub := getTestPublicKey(t) - rest2 := strings.Join(authWithOptions[3:], "\r\n") - rest3 := strings.Join(authWithOptions[6:], "\r\n") - testAuthorizedKeys(t, []byte(authWithCRLF), []authResult{ - {pub, []string{`env="HOME=/home/root"`, "no-port-forwarding"}, "user@host", rest2, true}, - {pub, []string{`env="HOME=/home/root2"`}, "user2@host2", rest3, true}, - {nil, nil, "", "", false}, - }) -} - -func TestAuthWithQuotedSpaceInEnv(t *testing.T) { - pub := getTestPublicKey(t) - testAuthorizedKeys(t, []byte(authWithQuotedSpaceInEnv), []authResult{ - {pub, []string{`env="HOME=/home/root dir"`, "no-port-forwarding"}, "user@host", "", true}, - }) -} - -func TestAuthWithQuotedCommaInEnv(t *testing.T) { - pub := getTestPublicKey(t) - testAuthorizedKeys(t, []byte(authWithQuotedCommaInEnv), []authResult{ - {pub, []string{`env="HOME=/home/root,dir"`, "no-port-forwarding"}, "user@host", "", true}, - }) -} - -func TestAuthWithQuotedQuoteInEnv(t *testing.T) { - pub := getTestPublicKey(t) - testAuthorizedKeys(t, []byte(authWithQuotedQuoteInEnv), []authResult{ - {pub, []string{`env="HOME=/home/\"root dir"`, "no-port-forwarding"}, "user@host", "", true}, - }) - - testAuthorizedKeys(t, []byte(authWithDoubleQuotedQuote), []authResult{ - {pub, []string{"no-port-forwarding", `env="HOME=/home/ \"root dir\""`}, "user@host", "", true}, - }) - -} - -func TestAuthWithInvalidSpace(t *testing.T) { - testAuthorizedKeys(t, []byte(authWithInvalidSpace), []authResult{ - {nil, nil, "", "", false}, - }) -} - -func TestAuthWithMissingQuote(t *testing.T) { - pub := getTestPublicKey(t) - testAuthorizedKeys(t, []byte(authWithMissingQuote), []authResult{ - {pub, []string{`env="HOME=/home/root"`, `shared-control`}, "user@host", "", true}, - }) -} - -func TestInvalidEntry(t *testing.T) { - _, _, _, _, ok := ssh.ParseAuthorizedKey(authInvalid) - if ok { - t.Errorf("Expected invalid entry, returned valid entry") - } -} diff --git a/vendor/code.google.com/p/go.crypto/ssh/test/session_test.go b/vendor/code.google.com/p/go.crypto/ssh/test/session_test.go deleted file mode 100644 index bd7307dd3..000000000 --- a/vendor/code.google.com/p/go.crypto/ssh/test/session_test.go +++ /dev/null @@ -1,185 +0,0 @@ -// Copyright 2012 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -// +build !windows - -package test - -// Session functional tests. - -import ( - "bytes" - "code.google.com/p/go.crypto/ssh" - "io" - "strings" - "testing" -) - -func TestRunCommandSuccess(t *testing.T) { - server := newServer(t) - defer server.Shutdown() - conn := server.Dial(clientConfig()) - defer conn.Close() - - session, err := conn.NewSession() - if err != nil { - t.Fatalf("session failed: %v", err) - } - defer session.Close() - err = session.Run("true") - if err != nil { - t.Fatalf("session failed: %v", err) - } -} - -func TestHostKeyCheck(t *testing.T) { - server := newServer(t) - defer server.Shutdown() - - conf := clientConfig() - k := conf.HostKeyChecker.(*storedHostKey) - - // change the keys. - k.keys[ssh.KeyAlgoRSA][25]++ - k.keys[ssh.KeyAlgoDSA][25]++ - k.keys[ssh.KeyAlgoECDSA256][25]++ - - conn, err := server.TryDial(conf) - if err == nil { - conn.Close() - t.Fatalf("dial should have failed.") - } else if !strings.Contains(err.Error(), "host key mismatch") { - t.Fatalf("'host key mismatch' not found in %v", err) - } -} - -func TestRunCommandFailed(t *testing.T) { - server := newServer(t) - defer server.Shutdown() - conn := server.Dial(clientConfig()) - defer conn.Close() - - session, err := conn.NewSession() - if err != nil { - t.Fatalf("session failed: %v", err) - } - defer session.Close() - err = session.Run(`bash -c "kill -9 $$"`) - if err == nil { - t.Fatalf("session succeeded: %v", err) - } -} - -func TestRunCommandWeClosed(t *testing.T) { - server := newServer(t) - defer server.Shutdown() - conn := server.Dial(clientConfig()) - defer conn.Close() - - session, err := conn.NewSession() - if err != nil { - t.Fatalf("session failed: %v", err) - } - err = session.Shell() - if err != nil { - t.Fatalf("shell failed: %v", err) - } - err = session.Close() - if err != nil { - t.Fatalf("shell failed: %v", err) - } -} - -func TestFuncLargeRead(t *testing.T) { - server := newServer(t) - defer server.Shutdown() - conn := server.Dial(clientConfig()) - defer conn.Close() - - session, err := conn.NewSession() - if err != nil { - t.Fatalf("unable to create new session: %s", err) - } - - stdout, err := session.StdoutPipe() - if err != nil { - t.Fatalf("unable to acquire stdout pipe: %s", err) - } - - err = session.Start("dd if=/dev/urandom bs=2048 count=1") - if err != nil { - t.Fatalf("unable to execute remote command: %s", err) - } - - buf := new(bytes.Buffer) - n, err := io.Copy(buf, stdout) - if err != nil { - t.Fatalf("error reading from remote stdout: %s", err) - } - - if n != 2048 { - t.Fatalf("Expected %d bytes but read only %d from remote command", 2048, n) - } -} - -func TestInvalidTerminalMode(t *testing.T) { - server := newServer(t) - defer server.Shutdown() - conn := server.Dial(clientConfig()) - defer conn.Close() - - session, err := conn.NewSession() - if err != nil { - t.Fatalf("session failed: %v", err) - } - defer session.Close() - - if err = session.RequestPty("vt100", 80, 40, ssh.TerminalModes{255: 1984}); err == nil { - t.Fatalf("req-pty failed: successful request with invalid mode") - } -} - -func TestValidTerminalMode(t *testing.T) { - server := newServer(t) - defer server.Shutdown() - conn := server.Dial(clientConfig()) - defer conn.Close() - - session, err := conn.NewSession() - if err != nil { - t.Fatalf("session failed: %v", err) - } - defer session.Close() - - stdout, err := session.StdoutPipe() - if err != nil { - t.Fatalf("unable to acquire stdout pipe: %s", err) - } - - stdin, err := session.StdinPipe() - if err != nil { - t.Fatalf("unable to acquire stdin pipe: %s", err) - } - - tm := ssh.TerminalModes{ssh.ECHO: 0} - if err = session.RequestPty("xterm", 80, 40, tm); err != nil { - t.Fatalf("req-pty failed: %s", err) - } - - err = session.Shell() - if err != nil { - t.Fatalf("session failed: %s", err) - } - - stdin.Write([]byte("stty -a && exit\n")) - - var buf bytes.Buffer - if _, err := io.Copy(&buf, stdout); err != nil { - t.Fatalf("reading failed: %s", err) - } - - if sttyOutput := buf.String(); !strings.Contains(sttyOutput, "-echo ") { - t.Fatalf("terminal mode failure: expected -echo in stty output, got %s", sttyOutput) - } -} diff --git a/vendor/code.google.com/p/go.crypto/ssh/test/tcpip_test.go b/vendor/code.google.com/p/go.crypto/ssh/test/tcpip_test.go deleted file mode 100644 index ee06b60b6..000000000 --- a/vendor/code.google.com/p/go.crypto/ssh/test/tcpip_test.go +++ /dev/null @@ -1,47 +0,0 @@ -// Copyright 2012 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -// +build !windows - -package test - -// direct-tcpip functional tests - -import ( - "net" - "net/http" - "testing" -) - -func TestTCPIPHTTP(t *testing.T) { - // google.com will generate at least one redirect, possibly three - // depending on your location. - doTest(t, "http://google.com") -} - -func TestTCPIPHTTPS(t *testing.T) { - doTest(t, "https://encrypted.google.com/") -} - -func doTest(t *testing.T, url string) { - server := newServer(t) - defer server.Shutdown() - conn := server.Dial(clientConfig()) - defer conn.Close() - - tr := &http.Transport{ - Dial: func(n, addr string) (net.Conn, error) { - return conn.Dial(n, addr) - }, - } - client := &http.Client{ - Transport: tr, - } - resp, err := client.Get(url) - if err != nil { - t.Fatalf("unable to proxy: %s", err) - } - // got a body without error - t.Log(resp) -} diff --git a/vendor/code.google.com/p/go.crypto/ssh/test/test_unix_test.go b/vendor/code.google.com/p/go.crypto/ssh/test/test_unix_test.go deleted file mode 100644 index 86df3f480..000000000 --- a/vendor/code.google.com/p/go.crypto/ssh/test/test_unix_test.go +++ /dev/null @@ -1,296 +0,0 @@ -// Copyright 2012 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -// +build darwin freebsd linux netbsd openbsd plan9 - -package test - -// functional test harness for unix. - -import ( - "bytes" - "fmt" - "io" - "io/ioutil" - "log" - "net" - "os" - "os/exec" - "os/user" - "path/filepath" - "testing" - "text/template" - - "code.google.com/p/go.crypto/ssh" -) - -const sshd_config = ` -Protocol 2 -HostKey {{.Dir}}/ssh_host_rsa_key -HostKey {{.Dir}}/ssh_host_dsa_key -HostKey {{.Dir}}/ssh_host_ecdsa_key -Pidfile {{.Dir}}/sshd.pid -#UsePrivilegeSeparation no -KeyRegenerationInterval 3600 -ServerKeyBits 768 -SyslogFacility AUTH -LogLevel DEBUG2 -LoginGraceTime 120 -PermitRootLogin no -StrictModes no -RSAAuthentication yes -PubkeyAuthentication yes -AuthorizedKeysFile {{.Dir}}/authorized_keys -IgnoreRhosts yes -RhostsRSAAuthentication no -HostbasedAuthentication no -` - -var ( - configTmpl template.Template - privateKey ssh.Signer - hostKeyRSA ssh.Signer - hostKeyECDSA ssh.Signer - hostKeyDSA ssh.Signer -) - -func init() { - template.Must(configTmpl.Parse(sshd_config)) - - for n, k := range map[string]*ssh.Signer{ - "ssh_host_ecdsa_key": &hostKeyECDSA, - "ssh_host_rsa_key": &hostKeyRSA, - "ssh_host_dsa_key": &hostKeyDSA, - } { - var err error - *k, err = ssh.ParsePrivateKey([]byte(keys[n])) - if err != nil { - panic(fmt.Sprintf("ParsePrivateKey(%q): %v", n, err)) - } - } - - var err error - privateKey, err = ssh.ParsePrivateKey([]byte(testClientPrivateKey)) - if err != nil { - panic(fmt.Sprintf("ParsePrivateKey: %v", err)) - } -} - -type server struct { - t *testing.T - cleanup func() // executed during Shutdown - configfile string - cmd *exec.Cmd - output bytes.Buffer // holds stderr from sshd process - - // Client half of the network connection. - clientConn net.Conn -} - -func username() string { - var username string - if user, err := user.Current(); err == nil { - username = user.Username - } else { - // user.Current() currently requires cgo. If an error is - // returned attempt to get the username from the environment. - log.Printf("user.Current: %v; falling back on $USER", err) - username = os.Getenv("USER") - } - if username == "" { - panic("Unable to get username") - } - return username -} - -type storedHostKey struct { - // keys map from an algorithm string to binary key data. - keys map[string][]byte -} - -func (k *storedHostKey) Add(key ssh.PublicKey) { - if k.keys == nil { - k.keys = map[string][]byte{} - } - k.keys[key.PublicKeyAlgo()] = ssh.MarshalPublicKey(key) -} - -func (k *storedHostKey) Check(addr string, remote net.Addr, algo string, key []byte) error { - if k.keys == nil || bytes.Compare(key, k.keys[algo]) != 0 { - return fmt.Errorf("host key mismatch. Got %q, want %q", key, k.keys[algo]) - } - return nil -} - -func clientConfig() *ssh.ClientConfig { - keyChecker := storedHostKey{} - keyChecker.Add(hostKeyECDSA.PublicKey()) - keyChecker.Add(hostKeyRSA.PublicKey()) - keyChecker.Add(hostKeyDSA.PublicKey()) - - kc := new(keychain) - kc.keys = append(kc.keys, privateKey) - config := &ssh.ClientConfig{ - User: username(), - Auth: []ssh.ClientAuth{ - ssh.ClientAuthKeyring(kc), - }, - HostKeyChecker: &keyChecker, - } - return config -} - -// unixConnection creates two halves of a connected net.UnixConn. It -// is used for connecting the Go SSH client with sshd without opening -// ports. -func unixConnection() (*net.UnixConn, *net.UnixConn, error) { - dir, err := ioutil.TempDir("", "unixConnection") - if err != nil { - return nil, nil, err - } - defer os.Remove(dir) - - addr := filepath.Join(dir, "ssh") - listener, err := net.Listen("unix", addr) - if err != nil { - return nil, nil, err - } - defer listener.Close() - c1, err := net.Dial("unix", addr) - if err != nil { - return nil, nil, err - } - - c2, err := listener.Accept() - if err != nil { - c1.Close() - return nil, nil, err - } - - return c1.(*net.UnixConn), c2.(*net.UnixConn), nil -} - -func (s *server) TryDial(config *ssh.ClientConfig) (*ssh.ClientConn, error) { - sshd, err := exec.LookPath("sshd") - if err != nil { - s.t.Skipf("skipping test: %v", err) - } - - c1, c2, err := unixConnection() - if err != nil { - s.t.Fatalf("unixConnection: %v", err) - } - - s.cmd = exec.Command(sshd, "-f", s.configfile, "-i", "-e") - f, err := c2.File() - if err != nil { - s.t.Fatalf("UnixConn.File: %v", err) - } - defer f.Close() - s.cmd.Stdin = f - s.cmd.Stdout = f - s.cmd.Stderr = &s.output - if err := s.cmd.Start(); err != nil { - s.t.Fail() - s.Shutdown() - s.t.Fatalf("s.cmd.Start: %v", err) - } - s.clientConn = c1 - return ssh.Client(c1, config) -} - -func (s *server) Dial(config *ssh.ClientConfig) *ssh.ClientConn { - conn, err := s.TryDial(config) - if err != nil { - s.t.Fail() - s.Shutdown() - s.t.Fatalf("ssh.Client: %v", err) - } - return conn -} - -func (s *server) Shutdown() { - if s.cmd != nil && s.cmd.Process != nil { - // Don't check for errors; if it fails it's most - // likely "os: process already finished", and we don't - // care about that. Use os.Interrupt, so child - // processes are killed too. - s.cmd.Process.Signal(os.Interrupt) - s.cmd.Wait() - } - if s.t.Failed() { - // log any output from sshd process - s.t.Logf("sshd: %s", s.output.String()) - } - s.cleanup() -} - -// newServer returns a new mock ssh server. -func newServer(t *testing.T) *server { - dir, err := ioutil.TempDir("", "sshtest") - if err != nil { - t.Fatal(err) - } - f, err := os.Create(filepath.Join(dir, "sshd_config")) - if err != nil { - t.Fatal(err) - } - err = configTmpl.Execute(f, map[string]string{ - "Dir": dir, - }) - if err != nil { - t.Fatal(err) - } - f.Close() - - for k, v := range keys { - f, err := os.OpenFile(filepath.Join(dir, k), os.O_WRONLY|os.O_TRUNC|os.O_CREATE, 0600) - if err != nil { - t.Fatal(err) - } - if _, err := f.Write([]byte(v)); err != nil { - t.Fatal(err) - } - f.Close() - } - - return &server{ - t: t, - configfile: f.Name(), - cleanup: func() { - if err := os.RemoveAll(dir); err != nil { - t.Error(err) - } - }, - } -} - -// keychain implements the ClientKeyring interface. -type keychain struct { - keys []ssh.Signer -} - -func (k *keychain) Key(i int) (ssh.PublicKey, error) { - if i < 0 || i >= len(k.keys) { - return nil, nil - } - return k.keys[i].PublicKey(), nil -} - -func (k *keychain) Sign(i int, rand io.Reader, data []byte) (sig []byte, err error) { - return k.keys[i].Sign(rand, data) -} - -func (k *keychain) loadPEM(file string) error { - buf, err := ioutil.ReadFile(file) - if err != nil { - return err - } - key, err := ssh.ParsePrivateKey(buf) - if err != nil { - return err - } - k.keys = append(k.keys, key) - return nil -} diff --git a/vendor/code.google.com/p/go.crypto/ssh/transport_test.go b/vendor/code.google.com/p/go.crypto/ssh/transport_test.go deleted file mode 100644 index 332011460..000000000 --- a/vendor/code.google.com/p/go.crypto/ssh/transport_test.go +++ /dev/null @@ -1,69 +0,0 @@ -// Copyright 2011 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package ssh - -import ( - "bytes" - "strings" - "testing" -) - -func TestReadVersion(t *testing.T) { - longversion := strings.Repeat("SSH-2.0-bla", 50)[:253] - cases := map[string]string{ - "SSH-2.0-bla\r\n": "SSH-2.0-bla", - "SSH-2.0-bla\n": "SSH-2.0-bla", - longversion + "\r\n": longversion, - } - - for in, want := range cases { - result, err := readVersion(bytes.NewBufferString(in)) - if err != nil { - t.Errorf("readVersion(%q): %s", in, err) - } - got := string(result) - if got != want { - t.Errorf("got %q, want %q", got, want) - } - } -} - -func TestReadVersionError(t *testing.T) { - longversion := strings.Repeat("SSH-2.0-bla", 50)[:253] - cases := []string{ - longversion + "too-long\r\n", - } - for _, in := range cases { - if _, err := readVersion(bytes.NewBufferString(in)); err == nil { - t.Errorf("readVersion(%q) should have failed", in) - } - } -} - -func TestExchangeVersionsBasic(t *testing.T) { - v := "SSH-2.0-bla" - buf := bytes.NewBufferString(v + "\r\n") - them, err := exchangeVersions(buf, []byte("xyz")) - if err != nil { - t.Errorf("exchangeVersions: %v", err) - } - - if want := "SSH-2.0-bla"; string(them) != want { - t.Errorf("got %q want %q for our version", them, want) - } -} - -func TestExchangeVersions(t *testing.T) { - cases := []string{ - "not\x000allowed", - "not allowed\n", - } - for _, c := range cases { - buf := bytes.NewBufferString("SSH-2.0-bla\r\n") - if _, err := exchangeVersions(buf, []byte(c)); err == nil { - t.Errorf("exchangeVersions(%q): should have failed", c) - } - } -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/Makefile b/vendor/github.com/Bugagazavr/go-gitlab-client/Makefile deleted file mode 100644 index b1ee855db..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/Makefile +++ /dev/null @@ -1,8 +0,0 @@ -all:deps test - -deps: - go get github.com/stretchr/testify - go get ./... - -test: - go test -cover -short ./... diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/README.md b/vendor/github.com/Bugagazavr/go-gitlab-client/README.md deleted file mode 100644 index 7920c5c4b..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/README.md +++ /dev/null @@ -1,81 +0,0 @@ -go-gitlab-client -================ - -This is a fork of project https://github.com/plouc/go-gitlab-client - -go-gitlab-client is a simple client written in golang to consume gitlab API. - -[![Build Status](https://travis-ci.org/Bugagazavr/go-gitlab-client.svg?branch=master)](https://travis-ci.org/Bugagazavr/go-gitlab-client) - - -##features - -* - ###Session [gitlab api doc](http://doc.gitlab.com/ce/api/session.html) - * get session - -* - ###Projects [gitlab api doc](http://doc.gitlab.com/ce/api/projects.html) - * list projects - * get single project - * list project merge requests - * list notes on merge requests - * add comments to merge requests - -* - ###Repositories [gitlab api doc](http://doc.gitlab.com/ce/api/repositories.html) - * list repository branches - * get single repository branch - * list project repository tags - * list repository commits - * list project hooks - * add/get/edit/rm project hook - -* - ###Users [gitlab api doc](http://doc.gitlab.com/ce/api/users.html) - * get single user - * manage user keys - -* - ###Deploy Keys [gitlab api doc](http://doc.gitlab.com/ce/api/deploy_keys.html) - * list project deploy keys - * add/get/rm project deploy key - - - - -##Installation - -To install go-gitlab-client, use `go get`: - - go get github.com/bugagazavr/go-gitlab-client - -Import the `go-gitlab-client` package into your code: - -```go -package whatever - -import ( - "github.com/bugagazavr/go-gitlab-client" -) -``` - - -##Update - -To update `go-gitlab-client`, use `go get -u`: - - go get -u github.com/bugagazavr/go-gitlab-client - - -##Documentation - -Visit the docs at http://godoc.org/github.com/Bugagazavr/go-gitlab-client - - -## Examples - -You can play with the examples located in the `examples` directory - -* [projects](https://github.com/Bugagazavr/go-gitlab-client/tree/master/examples/projects) -* [repositories](https://github.com/Bugagazavr/go-gitlab-client/tree/master/examples/repositories) diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/deploy_keys.go b/vendor/github.com/Bugagazavr/go-gitlab-client/deploy_keys.go deleted file mode 100644 index 38fe671c3..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/deploy_keys.go +++ /dev/null @@ -1,118 +0,0 @@ -package gogitlab - -import ( - "encoding/json" - "net/url" -) - -const ( - // ID - project_url_deploy_keys = "/projects/:id/keys" // Get list of project deploy keys - // PROJECT ID AND KEY ID - project_url_deploy_key = "/projects/:id/keys/:key_id" // Get single project deploy key -) - -/* -Get list of project deploy keys. - - GET /projects/:id/keys - -Parameters: - - id The ID of a project - -*/ -func (g *Gitlab) ProjectDeployKeys(id string) ([]*PublicKey, error) { - - url, opaque := g.ResourceUrlRaw(project_url_deploy_keys, map[string]string{":id": id}) - - var deployKeys []*PublicKey - - contents, err := g.buildAndExecRequestRaw("GET", url, opaque, nil) - if err == nil { - err = json.Unmarshal(contents, &deployKeys) - } - - return deployKeys, err -} - -/* -Get single project deploy key. - - GET /projects/:id/keys/:key_id - -Parameters: - - id The ID of a project - key_id The ID of a key - -*/ -func (g *Gitlab) ProjectDeployKey(id, key_id string) (*PublicKey, error) { - - url, opaque := g.ResourceUrlRaw(project_url_deploy_key, map[string]string{ - ":id": id, - ":key_id": key_id, - }) - - var deployKey *PublicKey - - contents, err := g.buildAndExecRequestRaw("GET", url, opaque, nil) - if err == nil { - err = json.Unmarshal(contents, &deployKey) - } - - return deployKey, err -} - -/* -Add deploy key to project. - - POST /projects/:id/keys - -Parameters: - - id The ID of a project - title The key title - key The key value - -*/ -func (g *Gitlab) AddProjectDeployKey(id, title, key string) error { - var err error - - path, opaque := g.ResourceUrlRaw(project_url_deploy_keys, map[string]string{":id": id}) - - v := url.Values{} - v.Set("title", title) - v.Set("key", key) - - body := v.Encode() - - _, err = g.buildAndExecRequestRaw("POST", path, opaque, []byte(body)) - - return err -} - -/* -Remove deploy key from project - - DELETE /projects/:id/keys/:key_id - -Parameters: - - id The ID of a project - key_id The ID of a key - -*/ -func (g *Gitlab) RemoveProjectDeployKey(id, key_id string) error { - - url, opaque := g.ResourceUrlRaw(project_url_deploy_key, map[string]string{ - ":id": id, - ":key_id": key_id, - }) - - var err error - - _, err = g.buildAndExecRequestRaw("DELETE", url, opaque, nil) - - return err -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/events.go b/vendor/github.com/Bugagazavr/go-gitlab-client/events.go deleted file mode 100644 index 82ac9c78f..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/events.go +++ /dev/null @@ -1,72 +0,0 @@ -package gogitlab - -import ( - "encoding/xml" - "fmt" - "time" -) - -type Person struct { - Name string `xml:"name"json:"name"` - Email string `xml:"email"json:"email"` -} - -type Link struct { - Rel string `xml:"rel,attr,omitempty"json:"rel"` - Href string `xml:"href,attr"json:"href"` -} - -type ActivityFeed struct { - Title string `xml:"title"json:"title"` - Id string `xml:"id"json:"id"` - Link []Link `xml:"link"json:"link"` - Updated time.Time `xml:"updated,attr"json:"updated"` - Entries []*FeedCommit `xml:"entry"json:"entries"` -} - -type FeedCommit struct { - Id string `xml:"id"json:"id"` - Title string `xml:"title"json:"title"` - Link []Link `xml:"link"json:"link"` - Updated time.Time `xml:"updated"json:"updated"` - Author Person `xml:"author"json:"author"` - Summary string `xml:"summary"json:"summary"` - // -} - -func (g *Gitlab) Activity() (ActivityFeed, error) { - - url := g.BaseUrl + dasboard_feed_path + "?private_token=" + g.Token - fmt.Println(url) - - contents, err := g.buildAndExecRequest("GET", url, nil) - if err != nil { - fmt.Println("%s", err) - } - - var activity ActivityFeed - err = xml.Unmarshal(contents, &activity) - if err != nil { - fmt.Println("%s", err) - } - - return activity, err -} - -func (g *Gitlab) RepoActivityFeed(feedPath string) ActivityFeed { - - url := g.BaseUrl + g.RepoFeedPath + "?private_token=" + g.Token - - contents, err := g.buildAndExecRequest("GET", url, nil) - if err != nil { - fmt.Println("%s", err) - } - - var activity ActivityFeed - err = xml.Unmarshal(contents, &activity) - if err != nil { - fmt.Println("%s", err) - } - - return activity -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/examples/config.json.sample b/vendor/github.com/Bugagazavr/go-gitlab-client/examples/config.json.sample deleted file mode 100644 index b7285af65..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/examples/config.json.sample +++ /dev/null @@ -1,5 +0,0 @@ -{ - "host": "https://gitlab.domain.com", - "api_path": "/api/v3", - "token": "TOKEN" -} \ No newline at end of file diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/examples/projects/main.go b/vendor/github.com/Bugagazavr/go-gitlab-client/examples/projects/main.go deleted file mode 100644 index 4eb0b0a6e..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/examples/projects/main.go +++ /dev/null @@ -1,246 +0,0 @@ -package main - -import ( - "encoding/json" - "flag" - "fmt" - "github.com/bugagazavr/go-gitlab-client" - "io/ioutil" - "os" - "strconv" - "time" -) - -type Config struct { - Host string `json:"host"` - ApiPath string `json:"api_path"` - Token string `json:"token"` -} - -func main() { - help := flag.Bool("help", false, "Show usage") - - file, e := ioutil.ReadFile("../config.json") - if e != nil { - fmt.Printf("Config file error: %v\n", e) - os.Exit(1) - } - - var config Config - json.Unmarshal(file, &config) - fmt.Printf("Results: %+v\n", config) - - var gitlab *gogitlab.Gitlab - - gitlab = gogitlab.NewGitlab(config.Host, config.ApiPath, config.Token) - - var method string - flag.StringVar(&method, "m", "", "Specify method to retrieve projects infos, available methods:\n"+ - " > -m projects\n"+ - " > -m project -id PROJECT_ID\n"+ - " > -m hooks -id PROJECT_ID\n"+ - " > -m branches -id PROJECT_ID\n"+ - " > -m merge_requests -id PROJECT_ID\n"+ - " > -m merge_request_notes -id PROJECT_ID -merge_id MERGE_REQUEST_ID\n"+ - " > -m merge_request_comment -id PROJECT_ID -merge_id MERGE_REQUEST_ID -comment COMMENT_BODY\n"+ - " > -m team -id PROJECT_ID") - - var id string - flag.StringVar(&id, "id", "", "Specify repository id") - - var merge_id string - flag.StringVar(&merge_id, "merge_id", "", "Specify merge request id") - - var comment string - flag.StringVar(&comment, "comment", "", "The body of the new comment") - - flag.Usage = func() { - fmt.Printf("Usage:\n") - flag.PrintDefaults() - } - flag.Parse() - - if *help == true || method == "" { - flag.Usage() - return - } - - startedAt := time.Now() - defer func() { - fmt.Printf("processed in %v\n", time.Now().Sub(startedAt)) - }() - - switch method { - case "projects": - fmt.Println("Fetching projects…") - - projects, err := gitlab.Projects(1, 100) - if err != nil { - fmt.Println(err.Error()) - return - } - - for _, project := range projects { - fmt.Printf("> %6d | %s\n", project.Id, project.Name) - } - - case "project": - fmt.Println("Fetching project…") - - if id == "" { - flag.Usage() - return - } - - project, err := gitlab.Project(id) - if err != nil { - fmt.Println(err.Error()) - return - } - - format := "> %-23s: %s\n" - - fmt.Printf("%s\n", project.Name) - fmt.Printf(format, "id", strconv.Itoa(project.Id)) - fmt.Printf(format, "name", project.Name) - fmt.Printf(format, "description", project.Description) - fmt.Printf(format, "default branch", project.DefaultBranch) - if project.Owner != nil { - fmt.Printf(format, "owner.name", project.Owner.Username) - } - fmt.Printf(format, "public", strconv.FormatBool(project.Public)) - fmt.Printf(format, "path", project.Path) - fmt.Printf(format, "path with namespace", project.PathWithNamespace) - fmt.Printf(format, "issues enabled", strconv.FormatBool(project.IssuesEnabled)) - fmt.Printf(format, "merge requests enabled", strconv.FormatBool(project.MergeRequestsEnabled)) - fmt.Printf(format, "wall enabled", strconv.FormatBool(project.WallEnabled)) - fmt.Printf(format, "wiki enabled", strconv.FormatBool(project.WikiEnabled)) - fmt.Printf(format, "created at", project.CreatedAtRaw) - //fmt.Printf(format, "namespace", project.Namespace) - - case "branches": - fmt.Println("Fetching project branches…") - - if id == "" { - flag.Usage() - return - } - - branches, err := gitlab.ProjectBranches(id) - if err != nil { - fmt.Println(err.Error()) - return - } - - for _, branch := range branches { - fmt.Printf("> %s\n", branch.Name) - } - - case "merge_requests": - fmt.Println("Fetching project merge_requests…") - - if id == "" { - flag.Usage() - return - } - - mrs, err := gitlab.ProjectMergeRequests(id, 0, 30, "opened") - if err != nil { - fmt.Println(err.Error()) - return - } - - for _, mr := range mrs { - author := "" - if mr.Author != nil { - author = mr.Author.Username - } - assignee := "" - if mr.Assignee != nil { - assignee = mr.Assignee.Username - } - fmt.Printf(" (#%d) %s -> %s [%s] author[%s] assignee[%s]\n", - mr.Id, mr.SourceBranch, mr.TargetBranch, mr.State, - author, assignee) - } - - case "merge_request_notes": - fmt.Println("Fetching merge_request notes…") - - if id == "" { - flag.Usage() - return - } - - notes, err := gitlab.MergeRequestNotes(id, merge_id, 0, 30) - if err != nil { - fmt.Println(err.Error()) - return - } - - for _, note := range notes { - author := "" - if note.Author != nil { - author = note.Author.Username - } - fmt.Printf(" [%d] author: %s <%s> %s\n", - note.Id, author, note.CreatedAt, note.Body) - } - - case "merge_request_comment": - fmt.Println("Sending new merge_request comment…") - - if id == "" { - flag.Usage() - return - } - - note, err := gitlab.SendMergeRequestComment(id, merge_id, comment) - if err != nil { - fmt.Println(err.Error()) - return - } - author := "" - if note.Author != nil { - author = note.Author.Username - } - fmt.Printf(" [%d] author: %s <%s> %s\n", - note.Id, author, note.CreatedAt, note.Body) - - case "hooks": - fmt.Println("Fetching project hooks…") - - if id == "" { - flag.Usage() - return - } - - hooks, err := gitlab.ProjectHooks(id) - if err != nil { - fmt.Println(err.Error()) - return - } - - for _, hook := range hooks { - fmt.Printf("> [%d] %s, created on %s\n", hook.Id, hook.Url, hook.CreatedAtRaw) - } - - case "team": - fmt.Println("Fetching project team members…") - - if id == "" { - flag.Usage() - return - } - - members, err := gitlab.ProjectMembers(id) - if err != nil { - fmt.Println(err.Error()) - return - } - - for _, member := range members { - fmt.Printf("> [%d] %s (%s) since %s\n", member.Id, member.Username, member.Name, member.CreatedAt) - } - } -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/examples/repositories/main.go b/vendor/github.com/Bugagazavr/go-gitlab-client/examples/repositories/main.go deleted file mode 100644 index 8a250204c..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/examples/repositories/main.go +++ /dev/null @@ -1,124 +0,0 @@ -package main - -import ( - "encoding/json" - "flag" - "fmt" - "github.com/bugagazavr/go-gitlab-client" - "io/ioutil" - "os" - "time" -) - -type Config struct { - Host string `json:"host"` - ApiPath string `json:"api_path"` - Token string `json:"token"` -} - -func main() { - help := flag.Bool("help", false, "Show usage") - - file, e := ioutil.ReadFile("../config.json") - if e != nil { - fmt.Printf("Config file error: %v\n", e) - os.Exit(1) - } - - var config Config - json.Unmarshal(file, &config) - fmt.Printf("Results: %+v\n", config) - - gitlab := gogitlab.NewGitlab(config.Host, config.ApiPath, config.Token) - - var method string - flag.StringVar(&method, "m", "", "Specify method to retrieve repositories, available methods:\n"+ - " > branches\n"+ - " > branch\n"+ - " > tags\n"+ - " > commits\n"+ - " > commit_comments -sha COMMIT_SHA\n"+ - " > comment_a_commit -sha COMMIT_SHA -comment COMMENT_BODY") - - var id string - flag.StringVar(&id, "id", "", "Specify repository id") - - var sha string - flag.StringVar(&sha, "sha", "", "Specify commit sha") - - var comment string - flag.StringVar(&comment, "comment", "", "The body of the new comment") - - flag.Usage = func() { - fmt.Printf("Usage:\n") - flag.PrintDefaults() - } - flag.Parse() - - if *help == true || method == "" || id == "" { - flag.Usage() - return - } - - startedAt := time.Now() - defer func() { - fmt.Printf("processed in %v\n", time.Now().Sub(startedAt)) - }() - - switch method { - case "branches": - fmt.Println("Fetching repository branches…") - - branches, err := gitlab.RepoBranches(id) - if err != nil { - fmt.Println(err.Error()) - } - - for _, branch := range branches { - fmt.Printf("> %s\n", branch.Name) - } - case "branch": - case "tags": - fmt.Println("Fetching repository tags…") - - tags, err := gitlab.RepoTags(id) - if err != nil { - fmt.Println(err.Error()) - } - - for _, tag := range tags { - fmt.Printf("> %s\n", tag.Name) - } - case "commits": - fmt.Println("Fetching repository commits…") - - commits, err := gitlab.RepoCommits(id) - if err != nil { - fmt.Println(err.Error()) - } - - for _, commit := range commits { - fmt.Printf("(%s) %s > [%s] %s\n", commit.Id, commit.CreatedAt.Format("Mon 02 Jan 15:04"), commit.Author_Name, commit.Title) - } - case "commit_comments": - fmt.Println("Fetching comments on a repository commit…") - - comments, err := gitlab.RepoCommitComments(id, sha) - if err != nil { - fmt.Println(err.Error()) - } - - for _, c := range comments { - fmt.Printf("[%s] %s\n", c.Author.Username, c.Note) - } - case "comment_a_commit": - fmt.Println("Sending a new comment on a repository commit…") - - c, err := gitlab.SendRepoCommitComment(id, sha, comment) - if err != nil { - fmt.Println(err.Error()) - } - - fmt.Printf("[%s] %s\n", c.Author.Username, c.Note) - } -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/gitlab.go b/vendor/github.com/Bugagazavr/go-gitlab-client/gitlab.go deleted file mode 100644 index dceb17541..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/gitlab.go +++ /dev/null @@ -1,220 +0,0 @@ -// Package github implements a simple client to consume gitlab API. -package gogitlab - -import ( - "bytes" - "crypto/tls" - "flag" - "fmt" - "io/ioutil" - "net/http" - "net/url" - "strings" -) - -const ( - dasboard_feed_path = "/dashboard.atom" -) - -type Gitlab struct { - BaseUrl string - ApiPath string - RepoFeedPath string - Token string - Bearer bool - Client *http.Client -} - -const ( - dateLayout = "2006-01-02T15:04:05-07:00" -) - -var ( - skipCertVerify = flag.Bool("gitlab.skip-cert-check", false, - `If set to true, gitlab client will skip certificate checking for https, possibly exposing your system to MITM attack.`) -) - -func NewGitlab(baseUrl, apiPath, token string) *Gitlab { - return NewGitlabCert(baseUrl, apiPath, token, *skipCertVerify) -} - -func NewGitlabCert(baseUrl, apiPath, token string, skipVerify bool) *Gitlab { - config := &tls.Config{InsecureSkipVerify: skipVerify} - tr := &http.Transport{ - Proxy: http.ProxyFromEnvironment, - TLSClientConfig: config, - } - client := &http.Client{Transport: tr} - - return &Gitlab{ - BaseUrl: baseUrl, - ApiPath: apiPath, - Token: token, - Client: client, - } -} - -func (g *Gitlab) ResourceUrl(url string, params map[string]string) string { - - if params != nil { - for key, val := range params { - url = strings.Replace(url, key, encodeParameter(val), -1) - } - } - - url = g.BaseUrl + g.ApiPath + url - if !g.Bearer { - url = url + "?private_token=" + g.Token - } - return url -} - -func (g *Gitlab) buildAndExecRequest(method, url string, body []byte) ([]byte, error) { - - var req *http.Request - var err error - - if body != nil { - reader := bytes.NewReader(body) - req, err = http.NewRequest(method, url, reader) - } else { - req, err = http.NewRequest(method, url, nil) - } - if err != nil { - panic("Error while building gitlab request") - } - - if g.Bearer { - req.Header.Set("Authorization", fmt.Sprintf("Bearer %s", g.Token)) - } - - resp, err := g.Client.Do(req) - if err != nil { - return nil, fmt.Errorf("Client.Do error: %q", err) - } - defer resp.Body.Close() - contents, err := ioutil.ReadAll(resp.Body) - if err != nil { - fmt.Printf("%s", err) - } - - if resp.StatusCode >= 400 { - err = fmt.Errorf("*Gitlab.buildAndExecRequest failed: <%d> %s", resp.StatusCode, req.URL) - } - - return contents, err -} - -func (g *Gitlab) ResourceUrlQuery(u string, params, query map[string]string) string { - if params != nil { - for key, val := range params { - u = strings.Replace(u, key, encodeParameter(val), -1) - } - } - - query_params := url.Values{} - if !g.Bearer { - query_params.Add("private_token", g.Token) - } - - if query != nil { - for key, val := range query { - query_params.Set(key, val) - } - } - - u = g.BaseUrl + g.ApiPath + u + "?" + query_params.Encode() - return u - -} - -func (g *Gitlab) ResourceUrlQueryRaw(u string, params, query map[string]string) (string, string) { - if params != nil { - for key, val := range params { - u = strings.Replace(u, key, encodeParameter(val), -1) - } - } - - query_params := url.Values{} - if !g.Bearer { - query_params.Add("private_token", g.Token) - } - - if query != nil { - for key, val := range query { - query_params.Set(key, val) - } - } - - u = g.BaseUrl + g.ApiPath + u + "?" + query_params.Encode() - p, err := url.Parse(u) - if err != nil { - return u, "" - } - - opaque := "//" + p.Host + p.Path - return u, opaque - -} - -func (g *Gitlab) ResourceUrlRaw(u string, params map[string]string) (string, string) { - - if params != nil { - for key, val := range params { - u = strings.Replace(u, key, encodeParameter(val), -1) - } - } - - path := u - u = g.BaseUrl + g.ApiPath + path - if !g.Bearer { - u = u + "?private_token=" + g.Token - } - - p, err := url.Parse(u) - if err != nil { - return u, "" - } - opaque := "//" + p.Host + p.Path - return u, opaque -} - -func (g *Gitlab) buildAndExecRequestRaw(method, url, opaque string, body []byte) ([]byte, error) { - - var req *http.Request - var err error - - if body != nil { - reader := bytes.NewReader(body) - req, err = http.NewRequest(method, url, reader) - } else { - req, err = http.NewRequest(method, url, nil) - } - if err != nil { - panic("Error while building gitlab request") - } - - if g.Bearer { - req.Header.Set("Authorization", fmt.Sprintf("Bearer %s", g.Token)) - } - - if len(opaque) > 0 { - req.URL.Opaque = opaque - } - - resp, err := g.Client.Do(req) - if err != nil { - return nil, fmt.Errorf("Client.Do error: %q", err) - } - defer resp.Body.Close() - contents, err := ioutil.ReadAll(resp.Body) - if err != nil { - fmt.Printf("%s", err) - } - - if resp.StatusCode >= 400 { - err = fmt.Errorf("*Gitlab.buildAndExecRequestRaw failed: <%d> %s", resp.StatusCode, req.URL) - } - - return contents, err -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/gitlab_test.go b/vendor/github.com/Bugagazavr/go-gitlab-client/gitlab_test.go deleted file mode 100644 index f4088e457..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/gitlab_test.go +++ /dev/null @@ -1,13 +0,0 @@ -package gogitlab - -import ( - "github.com/stretchr/testify/assert" - "testing" -) - -func TestResourceUrl(t *testing.T) { - gitlab := NewGitlab("http://base_url/", "api_path", "token") - - assert.Equal(t, gitlab.ResourceUrl(projects_url, nil), "http://base_url/api_path/projects?private_token=token") - assert.Equal(t, gitlab.ResourceUrl(project_url, map[string]string{":id": "123"}), "http://base_url/api_path/projects/123?private_token=token") -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/helper_test.go b/vendor/github.com/Bugagazavr/go-gitlab-client/helper_test.go deleted file mode 100644 index 2bac5df5e..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/helper_test.go +++ /dev/null @@ -1,16 +0,0 @@ -package gogitlab - -import ( - "io/ioutil" - "net/http" - "net/http/httptest" -) - -func Stub(filename string) (*httptest.Server, *Gitlab) { - stub, _ := ioutil.ReadFile(filename) - ts := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { - w.Write([]byte(stub)) - })) - gitlab := NewGitlab(ts.URL, "", "") - return ts, gitlab -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/hook_payload.go b/vendor/github.com/Bugagazavr/go-gitlab-client/hook_payload.go deleted file mode 100644 index b778e1fb9..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/hook_payload.go +++ /dev/null @@ -1,156 +0,0 @@ -package gogitlab - -import ( - "encoding/json" - "fmt" - "strings" -) - -type HookObjAttr struct { - Id int `json:"id,omitempty"` - Title string `json:"title,omitempty"` - AssigneeId int `json:"assignee_id,omitempty"` - AuthorId int `json:"author_id,omitempty"` - ProjectId int `json:"project_id,omitempty"` - CreatedAt string `json:"created_at,omitempty"` - UpdatedAt string `json:"updated_at,omitempty"` - Position int `json:"position,omitempty"` - BranchName string `json:"branch_name,omitempty"` - Description string `json:"description,omitempty"` - MilestoneId int `json:"milestone_id,omitempty"` - State string `json:"state,omitempty"` - IId int `json:"iid,omitempty"` - TargetBranch string `json:"target_branch,omitempty"` - SourceBranch string `json:"source_branch,omitempty"` - SourceProjectId int `json:"source_project_id,omitempty"` - StCommits string `json:"st_commits,omitempty"` - StDiffs string `json:"st_diffs,omitempty"` - MergeStatus string `json:"merge_status,omitempty"` - TargetProjectId int `json:"target_project_id,omitempty"` - Url string `json:"url,omiyempty"` - Source *hProject `json:"source,omitempty"` - Target *hProject `json:"target,omitempty"` - LastCommit *hCommit `json:"last_commit,omitempty"` -} - -type hProject struct { - Name string `json:"name"` - SshUrl string `json:"ssh_url"` - HttpUrl string `json:"http_url"` - VisibilityLevel int `json:"visibility_level"` - WebUrl string `json:"web_url"` - Namespace string `json:"namespace"` -} - -type hRepository struct { - Name string `json:"name,omitempty"` - URL string `json:"url,omitempty"` - Description string `json:"description,omitempty"` - Homepage string `json:"homepage,omitempty"` - GitHttpUrl string `json:"git_http_url,omitempty"` - GitSshUrl string `json:"git_ssh_url,omitempty"` - VisibilityLevel int `json:"visibility_level,omitempty"` -} - -type hCommit struct { - Id string `json:"id,omitempty"` - Message string `json:"message,omitempty"` - Timestamp string `json:"timestamp,omitempty"` - URL string `json:"url,omitempty"` - Author *Person `json:"author,omitempty"` -} - -type HookPayload struct { - Before string `json:"before,omitempty"` - After string `json:"after,omitempty"` - Ref string `json:"ref,omitempty"` - UserId int `json:"user_id,omitempty"` - UserName string `json:"user_name,omitempty"` - ProjectId int `json:"project_id,omitempty"` - Repository *hRepository `json:"repository,omitempty"` - Commits []hCommit `json:"commits,omitempty"` - TotalCommitsCount int `json:"total_commits_count,omitempty"` - ObjectKind string `json:"object_kind,omitempty"` - ObjectAttributes *HookObjAttr `json:"object_attributes,omitempty"` -} - -// ParseHook parses hook payload from GitLab -func ParseHook(payload []byte) (*HookPayload, error) { - hp := HookPayload{} - if err := json.Unmarshal(payload, &hp); err != nil { - return nil, err - } - - // Basic sanity check - switch { - case len(hp.ObjectKind) == 0: - // Assume this is a post-receive within repository - if len(hp.After) == 0 { - return nil, fmt.Errorf("Invalid hook received, commit hash not found.") - } - case hp.ObjectKind == "push": - if hp.Repository == nil { - return nil, fmt.Errorf("Invalid push hook received, attributes not found") - } - case hp.ObjectKind == "tag_push": - if hp.Repository == nil { - return nil, fmt.Errorf("Invalid tag push hook received, attributes not found") - } - case hp.ObjectKind == "issue": - fallthrough - case hp.ObjectKind == "merge_request": - if hp.ObjectAttributes == nil { - return nil, fmt.Errorf("Invalid hook received, attributes not found.") - } - default: - return nil, fmt.Errorf("Invalid hook received, payload format not recognized.") - } - - return &hp, nil -} - -// Type return current event type -// This function returns "unknown" type if event not supported -func (h *HookPayload) Type() string { - switch { - case strings.HasPrefix(h.Ref, "refs/heads/") && len(h.After) == 0: - return "branch_deleted" - case strings.HasPrefix(h.Ref, "refs/heads/") && len(h.Before) == 0: - return "branch" - case strings.HasPrefix(h.Ref, "refs/heads/"): - return "commit" - case strings.HasPrefix(h.Ref, "refs/tags/") && len(h.After) == 0: - return "tag_deleted" - case strings.HasPrefix(h.Ref, "refs/tags/"): - return "tag" - case h.ObjectKind == "issue": - return "issue" - case h.ObjectKind == "merge_request": - return "merge_request" - default: - return "unknown" - } -} - -// Tag returns current tag for push event hook payload -// This function returns empty string for any other events -func (h *HookPayload) Tag() string { - return strings.TrimPrefix(h.Ref, "refs/tags/") -} - -// Branch returns current branch for push event hook payload -// This function returns empty string for any other events -func (h *HookPayload) Branch() string { - return strings.TrimPrefix(h.Ref, "refs/heads/") -} - -// Head returns the latest changeset for push event hook payload -func (h *HookPayload) Head() hCommit { - c := hCommit{} - for _, cm := range h.Commits { - if h.After == cm.Id { - return cm - } - } - return c -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/hook_payload_test.go b/vendor/github.com/Bugagazavr/go-gitlab-client/hook_payload_test.go deleted file mode 100644 index 483d1bbae..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/hook_payload_test.go +++ /dev/null @@ -1,45 +0,0 @@ -package gogitlab - -import ( - "github.com/stretchr/testify/assert" - "io/ioutil" - "testing" -) - -func TestParsePushHook(t *testing.T) { - stub, _ := ioutil.ReadFile("stubs/hook_payloads/push.json") - p, err := ParseHook([]byte(stub)) - - assert.Equal(t, err, nil) - assert.Equal(t, p.ObjectKind, "push") - assert.IsType(t, new(HookPayload), p) - assert.Equal(t, p.After, "da1560886d4f094c3e6c9ef40349f7d38b5d27d7") - assert.Equal(t, p.Repository.URL, "git@example.com:mike/diasporadiaspora.git") - assert.Equal(t, p.Repository.GitHttpUrl, "http://example.com/mike/diaspora.git") - assert.Equal(t, p.Repository.GitSshUrl, "git@example.com:mike/diaspora.git") - assert.Equal(t, p.Repository.VisibilityLevel, 0) - assert.Equal(t, len(p.Commits), 2) - assert.Equal(t, p.Commits[0].Author.Email, "jordi@softcatala.org") - assert.Equal(t, p.Commits[1].Id, "da1560886d4f094c3e6c9ef40349f7d38b5d27d7") - assert.Equal(t, p.Branch(), "master") - assert.Equal(t, p.Head().Message, "fixed readme") -} - -func TestParseIssueHook(t *testing.T) { - stub, _ := ioutil.ReadFile("stubs/hook_payloads/issue.json") - p, err := ParseHook([]byte(stub)) - - assert.Equal(t, err, nil) - assert.Equal(t, p.ObjectKind, "issue") - assert.Equal(t, p.ObjectAttributes.Id, 301) -} - -func TestParseMergeRequestHook(t *testing.T) { - stub, _ := ioutil.ReadFile("stubs/hook_payloads/merge_request.json") - p, err := ParseHook([]byte(stub)) - - assert.Equal(t, err, nil) - assert.Equal(t, p.ObjectKind, "merge_request") - assert.Equal(t, p.ObjectAttributes.TargetBranch, "master") - assert.Equal(t, p.ObjectAttributes.SourceProjectId, p.ObjectAttributes.TargetProjectId) -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/hooks.go b/vendor/github.com/Bugagazavr/go-gitlab-client/hooks.go deleted file mode 100644 index 3f19de7eb..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/hooks.go +++ /dev/null @@ -1,187 +0,0 @@ -package gogitlab - -import ( - "encoding/json" - "net/url" -) - -const ( - project_url_hooks = "/projects/:id/hooks" // Get list of project hooks - project_url_hook = "/projects/:id/hooks/:hook_id" // Get single project hook -) - -type Hook struct { - Id int `json:"id,omitempty"` - Url string `json:"url,omitempty"` - CreatedAtRaw string `json:"created_at,omitempty"` -} - -/* -Get list of project hooks. - - GET /projects/:id/hooks - -Parameters: - - id The ID of a project - -*/ -func (g *Gitlab) ProjectHooks(id string) ([]*Hook, error) { - - url, opaque := g.ResourceUrlRaw(project_url_hooks, map[string]string{":id": id}) - - var err error - var hooks []*Hook - - contents, err := g.buildAndExecRequestRaw("GET", url, opaque, nil) - if err != nil { - return hooks, err - } - - err = json.Unmarshal(contents, &hooks) - - return hooks, err -} - -/* -Get single project hook. - - GET /projects/:id/hooks/:hook_id - -Parameters: - - id The ID of a project - hook_id The ID of a hook - -*/ -func (g *Gitlab) ProjectHook(id, hook_id string) (*Hook, error) { - - url, opaque := g.ResourceUrlRaw(project_url_hook, map[string]string{ - ":id": id, - ":hook_id": hook_id, - }) - - var err error - hook := new(Hook) - - contents, err := g.buildAndExecRequestRaw("GET", url, opaque, nil) - if err != nil { - return hook, err - } - - err = json.Unmarshal(contents, &hook) - - return hook, err -} - -/* -Add new project hook. - - POST /projects/:id/hooks - -Parameters: - - id The ID or NAMESPACE/PROJECT_NAME of a project - hook_url The hook URL - push_events Trigger hook on push events - issues_events Trigger hook on issues events - merge_requests_events Trigger hook on merge_requests events - -*/ -func (g *Gitlab) AddProjectHook(id, hook_url string, push_events, issues_events, merge_requests_events, tag_events bool) error { - - url, opaque := g.ResourceUrlRaw(project_url_hooks, map[string]string{":id": id}) - - var err error - - body := buildHookQuery(hook_url, push_events, issues_events, merge_requests_events, tag_events) - _, err = g.buildAndExecRequestRaw("POST", url, opaque, []byte(body)) - - return err -} - -/* -Edit existing project hook. - - PUT /projects/:id/hooks/:hook_id - -Parameters: - - id The ID or NAMESPACE/PROJECT_NAME of a project - hook_id The ID of a project hook - hook_url The hook URL - push_events Trigger hook on push events - issues_events Trigger hook on issues events - merge_requests_events Trigger hook on merge_requests events - -*/ -func (g *Gitlab) EditProjectHook(id, hook_id, hook_url string, push_events, issues_events, merge_requests_events, tag_events bool) error { - - url, opaque := g.ResourceUrlRaw(project_url_hook, map[string]string{ - ":id": id, - ":hook_id": hook_id, - }) - - var err error - - body := buildHookQuery(hook_url, push_events, issues_events, merge_requests_events, tag_events) - _, err = g.buildAndExecRequestRaw("PUT", url, opaque, []byte(body)) - - return err -} - -/* -Remove hook from project. - - DELETE /projects/:id/hooks/:hook_id - -Parameters: - - id The ID or NAMESPACE/PROJECT_NAME of a project - hook_id The ID of hook to delete - -*/ -func (g *Gitlab) RemoveProjectHook(id, hook_id string) error { - - url, opaque := g.ResourceUrlRaw(project_url_hook, map[string]string{ - ":id": id, - ":hook_id": hook_id, - }) - - var err error - - _, err = g.buildAndExecRequestRaw("DELETE", url, opaque, nil) - - return err -} - -/* -Build HTTP query to add or edit hook -*/ -func buildHookQuery(hook_url string, push_events, issues_events, merge_requests_events, tag_events bool) string { - - v := url.Values{} - v.Set("url", hook_url) - - if push_events { - v.Set("push_events", "true") - } else { - v.Set("push_events", "false") - } - if issues_events { - v.Set("issues_events", "true") - } else { - v.Set("issues_events", "false") - } - if merge_requests_events { - v.Set("merge_requests_events", "true") - } else { - v.Set("merge_requests_events", "false") - } - if tag_events { - v.Set("tag_push_events", "true") - } else { - v.Set("tag_push_events", "false") - } - return v.Encode() -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/hooks_test.go b/vendor/github.com/Bugagazavr/go-gitlab-client/hooks_test.go deleted file mode 100644 index 18ae7fc1f..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/hooks_test.go +++ /dev/null @@ -1,16 +0,0 @@ -package gogitlab - -import ( - "github.com/stretchr/testify/assert" - "testing" -) - -func TestHook(t *testing.T) { - ts, gitlab := Stub("stubs/hooks/show.json") - hook, err := gitlab.ProjectHook("1", "2") - - assert.Equal(t, err, nil) - assert.IsType(t, new(Hook), hook) - assert.Equal(t, hook.Url, "http://example.com/hook") - defer ts.Close() -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/projects.go b/vendor/github.com/Bugagazavr/go-gitlab-client/projects.go deleted file mode 100644 index b470f57e3..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/projects.go +++ /dev/null @@ -1,292 +0,0 @@ -package gogitlab - -import ( - "encoding/json" - "fmt" - "strconv" - "strings" -) - -const ( - projects_url = "/projects" // Get a list of projects owned by the authenticated user - projects_search_url = "/projects/search/:query" // Search for projects by name - project_url = "/projects/:id" // Get a specific project, identified by project ID or NAME - project_url_events = "/projects/:id/events" // Get project events - project_url_branches = "/projects/:id/repository/branches" // Lists all branches of a project - project_url_members = "/projects/:id/members" // List project team members - project_url_member = "/projects/:id/members/:user_id" // Get project team member - project_url_merge_requests = "/projects/:id/merge_requests" // List all merge requests of a project - merge_request_url_notes = "/projects/:id/merge_requests/:merge_request_id/notes" // Manage comments for a given merge request -) - -type Member struct { - Id int - Username string - Email string - Name string - State string - CreatedAt string `json:"created_at,omitempty"` - // AccessLevel int -} - -type Namespace struct { - Id int - Name string - Path string - Description string - Owner_Id int - Created_At string - Updated_At string -} - -type ProjectAccess struct { - AccessLevel int `json:"access_level,omitempty"` - NotificationLevel int `json:"notification_level,omitempty"` -} - -type GroupAccess struct { - AccessLevel int `json:"access_level,omitempty"` - NotificationLevel int `json:"notification_level,omitempty"` -} - -type Permissions struct { - ProjectAccess *ProjectAccess `json:"project_access,omitempty"` - GroupAccess *GroupAccess `json:"group_access,omitempty"` -} - -// A gitlab project -type Project struct { - Id int `json:"id,omitempty"` - Name string `json:"name,omitempty"` - Description string `json:"description,omitempty"` - DefaultBranch string `json:"default_branch,omitempty"` - Owner *Member `json:"owner,omitempty"` - Public bool `json:"public,omitempty"` - Path string `json:"path,omitempty"` - PathWithNamespace string `json:"path_with_namespace,omitempty"` - IssuesEnabled bool `json:"issues_enabled,omitempty"` - MergeRequestsEnabled bool `json:"merge_requests_enabled,omitempty"` - WallEnabled bool `json:"wall_enabled,omitempty"` - WikiEnabled bool `json:"wiki_enabled,omitempty"` - CreatedAtRaw string `json:"created_at,omitempty"` - Namespace *Namespace `json:"namespace,omitempty"` - SshRepoUrl string `json:"ssh_url_to_repo"` - HttpRepoUrl string `json:"http_url_to_repo"` - Url string `json:"web_url"` - Permissions *Permissions `json:"permissions,omitempty"` -} - -type MergeRequest struct { - Id int `json:"id,omitempty"` - // IId - TargetBranch string `json:"target_branch,omitempty"` - SourceBranch string `json:"source_branch,omitempty"` - ProjectId int `json:"project_id,omitempty"` - Title string `json:"title,omitempty"` - State string `json:"state,omitempty"` - Upvotes int `json:"upvotes,omitempty"` - Downvotes int `json:"downvotes,omitempty"` - Author *Member `json:"author,omitempty"` - Assignee *Member `json:"assignee,omitempty"` - Description string `json:"description,omitempty"` -} - -type MergeRequestNote struct { - Attachment interface{} `json:"attachment"` - Body string `json:"body"` - CreatedAt string `json:"created_at"` - Id int `json:"id"` - Author *Member `json:"author"` -} - -/* -Get a list of all projects owned by the authenticated user. -*/ -func (g *Gitlab) AllProjects() ([]*Project, error) { - var per_page = 100 - var projects []*Project - - for i := 1; true; i++ { - contents, err := g.Projects(i, per_page) - if err != nil { - return projects, err - } - - for _, value := range contents { - projects = append(projects, value) - } - - if len(projects) == 0 { - break - } - - if len(projects)/i < per_page { - break - } - } - - return projects, nil -} - -/* -Get a list of projects owned by the authenticated user. -*/ -func (g *Gitlab) Projects(page int, per_page int) ([]*Project, error) { - - url := g.ResourceUrlQuery(projects_url, nil, map[string]string{"page": strconv.Itoa(page), "per_page": strconv.Itoa(per_page)}) - - var projects []*Project - - contents, err := g.buildAndExecRequest("GET", url, nil) - if err == nil { - err = json.Unmarshal(contents, &projects) - } - - return projects, err -} - -/* -Get a specific project, identified by project ID or NAME, -which is owned by the authentication user. -Namespaced project may be retrieved by specifying the namespace -and its project name like this: - - `namespace%2Fproject-name` - -*/ -func (g *Gitlab) Project(id string) (*Project, error) { - - url, opaque := g.ResourceUrlRaw(project_url, map[string]string{":id": id}) - - var project *Project - - contents, err := g.buildAndExecRequestRaw("GET", url, opaque, nil) - if err == nil { - err = json.Unmarshal(contents, &project) - } - - return project, err -} - -/* -Lists all branches of a project. -*/ -func (g *Gitlab) ProjectBranches(id string) ([]*Branch, error) { - - url, opaque := g.ResourceUrlRaw(project_url_branches, map[string]string{":id": id}) - - var branches []*Branch - - contents, err := g.buildAndExecRequestRaw("GET", url, opaque, nil) - if err == nil { - err = json.Unmarshal(contents, &branches) - } - - return branches, err -} - -func (g *Gitlab) ProjectMembers(id string) ([]*Member, error) { - url, opaque := g.ResourceUrlRaw(project_url_members, map[string]string{":id": id}) - - var members []*Member - - contents, err := g.buildAndExecRequestRaw("GET", url, opaque, nil) - if err == nil { - err = json.Unmarshal(contents, &members) - } - - return members, err -} - -/* -Lists all merge requests of a project. -*/ -func (g *Gitlab) ProjectMergeRequests(id string, page int, per_page int, state string) ([]*MergeRequest, error) { - par := map[string]string{":id": id} - qry := map[string]string{ - "state": state, - "page": strconv.Itoa(page), - "per_page": strconv.Itoa(per_page)} - url := g.ResourceUrlQuery(project_url_merge_requests, par, qry) - - var mr []*MergeRequest - - contents, err := g.buildAndExecRequest("GET", url, nil) - if err == nil { - err = json.Unmarshal(contents, &mr) - } - - return mr, err -} - -/* -Lists all comments on merge request. -*/ -func (g *Gitlab) MergeRequestNotes(id string, merge_request_id string, page int, per_page int) ([]*MergeRequestNote, error) { - par := map[string]string{":id": id, ":merge_request_id": merge_request_id} - qry := map[string]string{ - "page": strconv.Itoa(page), - "per_page": strconv.Itoa(per_page)} - url := g.ResourceUrlQuery(merge_request_url_notes, par, qry) - - var mr []*MergeRequestNote - - contents, err := g.buildAndExecRequest("GET", url, nil) - if err == nil { - err = json.Unmarshal(contents, &mr) - } - - return mr, err -} - -/* -Creates a new comment on a merge request. -*/ -func (g *Gitlab) SendMergeRequestComment(id string, merge_request_id string, comment string) (*MergeRequestNote, error) { - par := map[string]string{":id": id, ":merge_request_id": merge_request_id} - url := g.ResourceUrlQuery(merge_request_url_notes, par, map[string]string{}) - - var mr *MergeRequestNote - - contents, err := g.buildAndExecRequest("POST", url, []byte(fmt.Sprintf("body=%s", comment))) - if err == nil { - err = json.Unmarshal(contents, &mr) - } - - return mr, err -} - -/* -Get single project id. - - GET /projects/search/:query - -Parameters: - - namespace The namespace of a project - name The id of a project - -*/ -func (g *Gitlab) SearchProjectId(namespace string, name string) (id int, err error) { - - url, opaque := g.ResourceUrlRaw(projects_search_url, map[string]string{ - ":query": strings.ToLower(name), - }) - - var projects []*Project - - contents, err := g.buildAndExecRequestRaw("GET", url, opaque, nil) - if err == nil { - err = json.Unmarshal(contents, &projects) - } else { - return id, err - } - - for _, project := range projects { - if project.Namespace.Name == namespace && strings.ToLower(project.Name) == strings.ToLower(name) { - id = project.Id - } - } - - return id, err -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/projects_test.go b/vendor/github.com/Bugagazavr/go-gitlab-client/projects_test.go deleted file mode 100644 index b1230dedf..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/projects_test.go +++ /dev/null @@ -1,85 +0,0 @@ -package gogitlab - -import ( - "github.com/stretchr/testify/assert" - "testing" -) - -func TestALlProjects(t *testing.T) { - ts, gitlab := Stub("stubs/projects/index.json") - projects, err := gitlab.AllProjects() - - assert.Equal(t, err, nil) - assert.Equal(t, len(projects), 2) - defer ts.Close() -} - -func TestProjects(t *testing.T) { - ts, gitlab := Stub("stubs/projects/index.json") - projects, err := gitlab.Projects(1, 100) - - assert.Equal(t, err, nil) - assert.Equal(t, len(projects), 2) - defer ts.Close() -} - -func TestProject(t *testing.T) { - ts, gitlab := Stub("stubs/projects/show.json") - project, err := gitlab.Project("1") - - assert.Equal(t, err, nil) - assert.IsType(t, new(Project), project) - assert.Equal(t, project.SshRepoUrl, "git@example.com:diaspora/diaspora-project-site.git") - assert.Equal(t, project.HttpRepoUrl, "http://example.com/diaspora/diaspora-project-site.git") - defer ts.Close() -} - -func TestProjectBranches(t *testing.T) { - ts, gitlab := Stub("stubs/projects/branches/index.json") - branches, err := gitlab.ProjectBranches("1") - - assert.Equal(t, err, nil) - assert.Equal(t, len(branches), 2) - defer ts.Close() -} - -func TestProjectMergeRequests(t *testing.T) { - ts, gitlab := Stub("stubs/projects/merge_requests/index.json") - defer ts.Close() - mr, err := gitlab.ProjectMergeRequests("1", 0, 30, "all") - - assert.Equal(t, err, nil) - assert.Equal(t, len(mr), 1) - - if len(mr) > 0 { - assert.Equal(t, mr[0].TargetBranch, "master") - assert.Equal(t, mr[0].SourceBranch, "test1") - } -} - -func TestMergeRequestNotes(t *testing.T) { - ts, gitlab := Stub("stubs/projects/merge_requests/notes/index.json") - defer ts.Close() - notes, err := gitlab.MergeRequestNotes("1", "1", 0, 30) - - assert.Equal(t, err, nil) - assert.Equal(t, len(notes), 1) - - if len(notes) > 0 { - assert.Equal(t, notes[0].Id, 301) - assert.Equal(t, notes[0].Body, "Comment for MR") - assert.Equal(t, notes[0].Author.Username, "pipin") - } -} - -func TestSearchProjectId(t *testing.T) { - ts, gitlab := Stub("stubs/projects/index.json") - - namespace := "Brightbox" - name := "Puppet" - id, err := gitlab.SearchProjectId(namespace, name) - - assert.Equal(t, err, nil) - assert.Equal(t, id, 6) - defer ts.Close() -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/public_keys.go b/vendor/github.com/Bugagazavr/go-gitlab-client/public_keys.go deleted file mode 100644 index e3b7156b8..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/public_keys.go +++ /dev/null @@ -1,69 +0,0 @@ -package gogitlab - -import ( - "encoding/json" - "net/url" -) - -const ( - // ID - user_keys = "/user/keys" // Get current user keys - user_key = "/user/keys/:id" // Get user key by id - custom_user_keys = "/user/:id/keys" // Create key for user with :id -) - -type PublicKey struct { - Id int `json:"id,omitempty"` - Title string `json:"title,omitempty"` - Key string `json:"key,omitempty"` - CreatedAtRaw string `json:"created_at,omitempty"` -} - -func (g *Gitlab) UserKeys() ([]*PublicKey, error) { - url := g.ResourceUrl(user_keys, nil) - var keys []*PublicKey - contents, err := g.buildAndExecRequest("GET", url, nil) - if err == nil { - err = json.Unmarshal(contents, &keys) - } - return keys, err -} - -func (g *Gitlab) UserKey(id string) (*PublicKey, error) { - url := g.ResourceUrl(user_key, map[string]string{":id": id}) - var key *PublicKey - contents, err := g.buildAndExecRequest("GET", url, nil) - if err == nil { - err = json.Unmarshal(contents, &key) - } - return key, err -} - -func (g *Gitlab) AddKey(title, key string) error { - path := g.ResourceUrl(user_keys, nil) - var err error - v := url.Values{} - v.Set("title", title) - v.Set("key", key) - body := v.Encode() - _, err = g.buildAndExecRequest("POST", path, []byte(body)) - return err -} - -func (g *Gitlab) AddUserKey(id, title, key string) error { - path := g.ResourceUrl(user_keys, map[string]string{":id": id}) - var err error - v := url.Values{} - v.Set("title", title) - v.Set("key", key) - body := v.Encode() - _, err = g.buildAndExecRequest("POST", path, []byte(body)) - return err -} - -func (g *Gitlab) DeleteKey(id string) error { - url := g.ResourceUrl(user_key, map[string]string{":id": id}) - var err error - _, err = g.buildAndExecRequest("DELETE", url, nil) - return err -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/public_keys_test.go b/vendor/github.com/Bugagazavr/go-gitlab-client/public_keys_test.go deleted file mode 100644 index d3be64a1f..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/public_keys_test.go +++ /dev/null @@ -1,50 +0,0 @@ -package gogitlab - -import ( - "github.com/stretchr/testify/assert" - "testing" -) - -func TestGetUserKeys(t *testing.T) { - ts, gitlab := Stub("stubs/public_keys/index.json") - keys, err := gitlab.UserKeys() - - assert.Equal(t, err, nil) - assert.Equal(t, len(keys), 2) - defer ts.Close() -} - -func TestGetUserKey(t *testing.T) { - ts, gitlab := Stub("stubs/public_keys/show.json") - key, err := gitlab.UserKey("1") - - assert.Equal(t, err, nil) - assert.IsType(t, new(PublicKey), key) - assert.Equal(t, key.Title, "Public key") - assert.Equal(t, key.Key, "ssh-rsa AAAAB3NzaC1yc2EAAAABJQAAAIEAiPWx6WM4lhHNedGfBpPJNPpZ7yKu+dnn1SJejgt4596k6YjzGGphH2TUxwKzxcKDKKezwkpfnxPkSMkuEspGRt/aZZ9wa++Oi7Qkr8prgHc4soW6NUlfDzpvZK2H5E7eQaSeP3SAwGmQKUFHCddNaP0L+hM7zhFNzjFvpaMgJw0=") - defer ts.Close() -} - -func TestAddKey(t *testing.T) { - ts, gitlab := Stub("") - err := gitlab.AddKey("Public key", "stubbed key") - - assert.Equal(t, err, nil) - defer ts.Close() -} - -func TestAddUserKey(t *testing.T) { - ts, gitlab := Stub("") - err := gitlab.AddUserKey("1", "Public key", "stubbed key") - - assert.Equal(t, err, nil) - defer ts.Close() -} - -func TestDeleteKey(t *testing.T) { - ts, gitlab := Stub("") - err := gitlab.DeleteKey("1") - - assert.Equal(t, err, nil) - defer ts.Close() -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/repositories.go b/vendor/github.com/Bugagazavr/go-gitlab-client/repositories.go deleted file mode 100644 index 47d54b706..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/repositories.go +++ /dev/null @@ -1,323 +0,0 @@ -package gogitlab - -import ( - "encoding/json" - "fmt" - "net/url" - "time" -) - -const ( - repo_url_branches = "/projects/:id/repository/branches" // List repository branches - repo_url_branch = "/projects/:id/repository/branches/:branch" // Get a specific branch of a project. - repo_url_tags = "/projects/:id/repository/tags" // List project repository tags - repo_url_commits = "/projects/:id/repository/commits" // List repository commits - repo_url_commit_comments = "/projects/:id/repository/commits/:sha/comments" // New comment or list of commit comments - repo_url_tree = "/projects/:id/repository/tree" // List repository tree - repo_url_raw_file = "/projects/:id/repository/blobs/:sha" // Get raw file content for specific commit/branch -) - -type BranchCommit struct { - Id string `json:"id,omitempty"` - Tree string `json:"tree,omitempty"` - AuthoredDateRaw string `json:"authored_date,omitempty"` - CommittedDateRaw string `json:"committed_date,omitempty"` - Message string `json:"message,omitempty"` - Author *Person `json:"author,omitempty"` - Committer *Person `json:"committer,omitempty"` - /* - "parents": [ - {"id": "9b0c4b08e7890337fc8111e66f809c8bbec467a9"}, - {"id": "3ac634dca850cab70ab14b43ad6073d1e0a7827f"} - ] - */ -} - -type Branch struct { - Name string `json:"name,omitempty"` - Protected bool `json:"protected,omitempty"` - Commit *BranchCommit `json:"commit,omitempty"` -} - -type Tag struct { - Name string `json:"name,omitempty"` - Protected bool `json:"protected,omitempty"` - Commit *BranchCommit `json:"commit,omitempty"` -} - -type Commit struct { - Id string - Short_Id string - Title string - Author_Name string - Author_Email string - Created_At string - CreatedAt time.Time -} - -type File struct { - Id string `json:"id,omitempty"` - Name string `json:"name,omitempty"` - Type string `json:"type,omitempty"` - Mode string `json:"mode,omitempty"` - - Children []*File -} - -type CommitComment struct { - Author *Member `json:"author,omitempty"` - Line int `json:"line,omitempty"` - LineType string `json:"line_type,omitempty"` - Note string `json:"note,omitempty"` - Path string `json:"path,omitempty"` -} - -/* -Get a list of repository branches from a project, sorted by name alphabetically. - - GET /projects/:id/repository/branches - -Parameters: - - id The ID of a project - -Usage: - - branches, err := gitlab.RepoBranches("your_projet_id") - if err != nil { - fmt.Println(err.Error()) - } - for _, branch := range branches { - fmt.Printf("%+v\n", branch) - } -*/ -func (g *Gitlab) RepoBranches(id string) ([]*Branch, error) { - - url, opaque := g.ResourceUrlRaw(repo_url_branches, map[string]string{":id": id}) - - var branches []*Branch - - contents, err := g.buildAndExecRequestRaw("GET", url, opaque, nil) - if err == nil { - err = json.Unmarshal(contents, &branches) - } - - return branches, err -} - -/* -Get a single project repository branch. - - GET /projects/:id/repository/branches/:branch - -Parameters: - - id The ID of a project - branch The name of the branch - -*/ -func (g *Gitlab) RepoBranch(id, refName string) (*Branch, error) { - - url, opaque := g.ResourceUrlRaw(repo_url_branch, map[string]string{ - ":id": id, - ":branch": refName, - }) - - branch := new(Branch) - - contents, err := g.buildAndExecRequestRaw("GET", url, opaque, nil) - if err == nil { - err = json.Unmarshal(contents, &branch) - } - return branch, err -} - -/* -Get a list of repository tags from a project, sorted by name in reverse alphabetical order. - - GET /projects/:id/repository/tags - -Parameters: - - id The ID of a project - -Usage: - - tags, err := gitlab.RepoTags("your_projet_id") - if err != nil { - fmt.Println(err.Error()) - } - for _, tag := range tags { - fmt.Printf("%+v\n", tag) - } -*/ -func (g *Gitlab) RepoTags(id string) ([]*Tag, error) { - - url, opaque := g.ResourceUrlRaw(repo_url_tags, map[string]string{":id": id}) - - var tags []*Tag - - contents, err := g.buildAndExecRequestRaw("GET", url, opaque, nil) - if err == nil { - err = json.Unmarshal(contents, &tags) - } - - return tags, err -} - -/* -Get a list of repository commits in a project. - - GET /projects/:id/repository/commits - -Parameters: - - id The ID of a project - refName The name of a repository branch or tag or if not given the default branch - -Usage: - - commits, err := gitlab.RepoCommits("your_projet_id") - if err != nil { - fmt.Println(err.Error()) - } - for _, commit := range commits { - fmt.Printf("%+v\n", commit) - } -*/ -func (g *Gitlab) RepoCommits(id string) ([]*Commit, error) { - - url, opaque := g.ResourceUrlRaw(repo_url_commits, map[string]string{":id": id}) - - var commits []*Commit - - contents, err := g.buildAndExecRequestRaw("GET", url, opaque, nil) - if err == nil { - err = json.Unmarshal(contents, &commits) - if err == nil { - for _, commit := range commits { - t, _ := time.Parse(dateLayout, commit.Created_At) - commit.CreatedAt = t - } - } - } - - return commits, err -} - -/* -Get a list of comments in a repository commit. - - GET /projects/:id/repository/commits/:sha/comments - -Parameters: - - id The ID of a project - sha The sha of the commit - -Usage: - - comments, err := gitlab.RepoCommitComments("your_projet_id", "commit_sha") - if err != nil { - fmt.Println(err.Error()) - } - for _, comment := range comments { - fmt.Printf("%+v\n", comment) - } -*/ -func (g *Gitlab) RepoCommitComments(id string, sha string) ([]*CommitComment, error) { - - url, opaque := g.ResourceUrlRaw(repo_url_commit_comments, map[string]string{":id": id, ":sha": sha}) - - var comments []*CommitComment - - contents, err := g.buildAndExecRequestRaw("GET", url, opaque, nil) - if err == nil { - err = json.Unmarshal(contents, &comments) - } - - return comments, err -} - -/* -Create a comment in a repository commit. - - POST /projects/:id/repository/commits/:sha/comments - -Parameters: - - id The ID of a project - sha The sha of the commit - body The body of the comment - -Usage: - - comment, err := gitlab.SendRepoCommitComment("your_projet_id", "commit_sha", "your comment goes here") - if err != nil { - fmt.Println(err.Error()) - } - fmt.Printf("%+v\n", comment) -*/ -func (g *Gitlab) SendRepoCommitComment(id string, sha string, body string) (*CommitComment, error) { - - url, opaque := g.ResourceUrlRaw(repo_url_commit_comments, map[string]string{":id": id, ":sha": sha}) - - var comment *CommitComment - - contents, err := g.buildAndExecRequestRaw("POST", url, opaque, []byte(fmt.Sprintf("note=%s", body))) - if err == nil { - err = json.Unmarshal(contents, &comment) - } - - return comment, err -} - -/* -Get Raw file content -*/ -func (g *Gitlab) RepoRawFile(id, sha, filepath string) ([]byte, error) { - url_ := g.ResourceUrlQuery(repo_url_raw_file, map[string]string{ - ":id": id, - ":sha": sha, - }, map[string]string{ - "filepath": filepath, - }) - - p, err := url.Parse(url_) - if err != nil { - return nil, err - } - - opaque := "//" + p.Host + p.Path - contents, err := g.buildAndExecRequestRaw("GET", url_, opaque, nil) - - return contents, err -} - -/* -Get Raw file content -*/ -func (g *Gitlab) RepoTree(id, ref, path string) ([]*File, error) { - - url := g.ResourceUrlQuery(repo_url_tree, map[string]string{ - ":id": id, - }, map[string]string{ - "ref": ref, - "path": path, - }) - - var files []*File - - contents, err := g.buildAndExecRequest("GET", url, nil) - if err == nil { - err = json.Unmarshal(contents, &files) - } - - for _, f := range files { - if f.Type == "tree" { - f.Children, err = g.RepoTree(id, ref, path+"/"+f.Name) - } - } - - return files, err -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/repositories_test.go b/vendor/github.com/Bugagazavr/go-gitlab-client/repositories_test.go deleted file mode 100644 index d55ffd0dc..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/repositories_test.go +++ /dev/null @@ -1,52 +0,0 @@ -package gogitlab - -import ( - "github.com/stretchr/testify/assert" - "testing" -) - -func TestRepoBranches(t *testing.T) { - ts, gitlab := Stub("stubs/branches/index.json") - branches, err := gitlab.RepoBranches("1") - - assert.Equal(t, err, nil) - assert.Equal(t, len(branches), 1) - defer ts.Close() -} - -func TestRepoBranch(t *testing.T) { - ts, gitlab := Stub("stubs/branches/show.json") - branch, err := gitlab.RepoBranch("1", "master") - - assert.Equal(t, err, nil) - assert.IsType(t, new(Branch), branch) - assert.Equal(t, branch.Name, "master") - defer ts.Close() -} - -func TestRepoTags(t *testing.T) { - ts, gitlab := Stub("stubs/tags/index.json") - tags, err := gitlab.RepoTags("1") - - assert.Equal(t, err, nil) - assert.Equal(t, len(tags), 1) - defer ts.Close() -} - -func TestRepoCommits(t *testing.T) { - ts, gitlab := Stub("stubs/commits/index.json") - commits, err := gitlab.RepoCommits("1") - - assert.Equal(t, err, nil) - assert.Equal(t, len(commits), 2) - defer ts.Close() -} - -func TestRepoCommitComments(t *testing.T) { - ts, gitlab := Stub("stubs/commits/comments/index.json") - comments, err := gitlab.RepoCommitComments("1", "a9e6a5io4e695923c995ed2e836789b50oi77e0b") - - assert.Equal(t, err, nil) - assert.Equal(t, len(comments), 1) - defer ts.Close() -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/services.go b/vendor/github.com/Bugagazavr/go-gitlab-client/services.go deleted file mode 100644 index 6ef79c283..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/services.go +++ /dev/null @@ -1,19 +0,0 @@ -package gogitlab - -const ( - drone_service_url = "/projects/:id/services/drone-ci" -) - -func (g *Gitlab) AddDroneService(id string, params map[string]string) error { - url, opaque := g.ResourceUrlQueryRaw(drone_service_url, map[string]string{":id": id}, params) - - _, err := g.buildAndExecRequestRaw("PUT", url, opaque, nil) - return err -} - -func (g *Gitlab) DeleteDroneService(id string) error { - url, opaque := g.ResourceUrlQueryRaw(drone_service_url, map[string]string{":id": id}, nil) - - _, err := g.buildAndExecRequestRaw("DELETE", url, opaque, nil) - return err -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/session.go b/vendor/github.com/Bugagazavr/go-gitlab-client/session.go deleted file mode 100644 index 5626ade26..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/session.go +++ /dev/null @@ -1,54 +0,0 @@ -package gogitlab - -import ( - "encoding/json" - "net/url" -) - -const ( - session_path = "/session" -) - -type Session struct { - Id int `json:"id"` - UserName string `json:"username"` - Name string `json:"name"` - Blocked bool `json:"blocked"` - State string `json:"state"` - AvatarURL string `json:"avatar_url",omitempty` - IsAdmin bool `json:"is_admin"` - Bio string `json:"bio",omitempty` - Email string `json:"email"` - ThemeId int `json:"theme_id",omitempty` - ColorSchemeId int `json:"color_scheme_id",omitempty` - ExternUid string `json:"extern_uid",omitempty` - Provider string `json:"provider",omitempty` - CanCreateGroup bool `json:"can_create_group"` - CanCreateProject bool `json:"can_create_project"` - Skype string `json:"skype",omitempty` - Twitter string `json:"twitter",omitempty` - LinkedIn string `json:"linkedin",omitempty` - WebsiteURL string `json:"website_url",omitempty` - PrivateToken string `json:"private_token"` -} - -func (g *Gitlab) GetSession(email string, password string) (*Session, error) { - session_url := g.ResourceUrl(session_path, map[string]string{}) - - var session *Session - - v := url.Values{} - v.Set("email", email) - v.Set("password", password) - - body := v.Encode() - - contents, err := g.buildAndExecRequest("POST", session_url, []byte(body)) - if err != nil { - return session, err - } - - err = json.Unmarshal(contents, &session) - - return session, err -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/session_test.go b/vendor/github.com/Bugagazavr/go-gitlab-client/session_test.go deleted file mode 100644 index 28665563b..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/session_test.go +++ /dev/null @@ -1,33 +0,0 @@ -package gogitlab - -import ( - "github.com/stretchr/testify/assert" - "testing" -) - -func TestGetSesison(t *testing.T) { - ts, gitlab := Stub("stubs/session/index.json") - session, err := gitlab.GetSession("john@example.com", "samplepassword") - - assert.Equal(t, err, nil) - assert.Equal(t, session.Id, 1) - assert.Equal(t, session.UserName, "john_smith") - assert.Equal(t, session.Name, "John Smith") - assert.Equal(t, session.State, "active") - assert.Equal(t, session.AvatarURL, "http://someurl.com/avatar.png") - assert.Equal(t, session.IsAdmin, false) - assert.Equal(t, session.Bio, "somebio") - assert.Equal(t, session.Skype, "someskype") - assert.Equal(t, session.LinkedIn, "somelinkedin") - assert.Equal(t, session.Twitter, "sometwitter") - assert.Equal(t, session.WebsiteURL, "http://example.com") - assert.Equal(t, session.Email, "john@example.com") - assert.Equal(t, session.ThemeId, 1) - assert.Equal(t, session.ColorSchemeId, 1) - assert.Equal(t, session.ExternUid, "someuid") - assert.Equal(t, session.Provider, "github.com") - assert.Equal(t, session.CanCreateGroup, true) - assert.Equal(t, session.CanCreateProject, true) - assert.Equal(t, session.PrivateToken, "dd34asd13as") - defer ts.Close() -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/branches/index.json b/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/branches/index.json deleted file mode 100644 index c3f72112b..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/branches/index.json +++ /dev/null @@ -1,26 +0,0 @@ -[ - { - "name": "master", - "commit": { - "id": "7b5c3cc8be40ee161ae89a06bba6229da1032a0c", - "parents": [ - { - "id": "4ad91d3c1144c406e50c7b33bae684bd6837faf8" - } - ], - "tree": "46e82de44b1061621357f24c05515327f2795a95", - "message": "add projects API", - "author": { - "name": "John Smith", - "email": "john@example.com" - }, - "committer": { - "name": "John Smith", - "email": "john@example.com" - }, - "authored_date": "2012-06-27T05:51:39-07:00", - "committed_date": "2012-06-28T03:44:20-07:00" - }, - "protected": true - } -] \ No newline at end of file diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/branches/show.json b/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/branches/show.json deleted file mode 100644 index 4bf5b39ef..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/branches/show.json +++ /dev/null @@ -1,24 +0,0 @@ -{ - "name": "master", - "commit": { - "id": "7b5c3cc8be40ee161ae89a06bba6229da1032a0c", - "parents": [ - { - "id": "4ad91d3c1144c406e50c7b33bae684bd6837faf8" - } - ], - "tree": "46e82de44b1061621357f24c05515327f2795a95", - "message": "add projects API", - "author": { - "name": "John Smith", - "email": "john@example.com" - }, - "committer": { - "name": "John Smith", - "email": "john@example.com" - }, - "authored_date": "2012-06-27T05:51:39-07:00", - "committed_date": "2012-06-28T03:44:20-07:00" - }, - "protected": true -} \ No newline at end of file diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/commits/comments/index.json b/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/commits/comments/index.json deleted file mode 100644 index f3886f5c4..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/commits/comments/index.json +++ /dev/null @@ -1,16 +0,0 @@ -[ - { - "author": { - "id": 1, - "username": "admin", - "email": "admin@local.host", - "name": "Administrator", - "blocked": false, - "created_at": "2012-04-29T08:46:00Z" - }, - "note": "text1", - "path": "example.rb", - "line": 5, - "line_type": "new" - } -] \ No newline at end of file diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/commits/index.json b/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/commits/index.json deleted file mode 100644 index 53eb0c558..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/commits/index.json +++ /dev/null @@ -1,18 +0,0 @@ -[ - { - "id": "ed899a2f4b50b4370feeea94676502b42383c746", - "short_id": "ed899a2f4b5", - "title": "Replace sanitize with escape once", - "author_name": "Dmitriy Zaporozhets", - "author_email": "dzaporozhets@sphereconsultinginc.com", - "created_at": "2012-09-20T11:50:22+03:00" - }, - { - "id": "6104942438c14ec7bd21c6cd5bd995272b3faff6", - "short_id": "6104942438c", - "title": "Sanitize for network graph", - "author_name": "randx", - "author_email": "dmitriy.zaporozhets@gmail.com", - "created_at": "2012-09-20T09:06:12+03:00" - } -] \ No newline at end of file diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/hook_payloads/issue.json b/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/hook_payloads/issue.json deleted file mode 100644 index e0842c1c9..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/hook_payloads/issue.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "object_kind": "issue", - "object_attributes": { - "id": 301, - "title": "New API: create/update/delete file", - "assignee_id": 51, - "author_id": 51, - "project_id": 14, - "created_at": "2013-12-03T17:15:43Z", - "updated_at": "2013-12-03T17:15:43Z", - "position": 0, - "branch_name": null, - "description": "Create new API for manipulations with repository", - "milestone_id": null, - "state": "opened", - "iid": 23 - } -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/hook_payloads/merge_request.json b/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/hook_payloads/merge_request.json deleted file mode 100644 index 490719e63..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/hook_payloads/merge_request.json +++ /dev/null @@ -1,22 +0,0 @@ -{ - "object_kind": "merge_request", - "object_attributes": { - "id": 99, - "target_branch": "master", - "source_branch": "ms-viewport", - "source_project_id": 14, - "author_id": 51, - "assignee_id": 6, - "title": "MS-Viewport", - "created_at": "2013-12-03T17:23:34Z", - "updated_at": "2013-12-03T17:23:34Z", - "st_commits": null, - "st_diffs": null, - "milestone_id": null, - "state": "opened", - "merge_status": "unchecked", - "target_project_id": 14, - "iid": 1, - "description": "" - } -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/hook_payloads/push.json b/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/hook_payloads/push.json deleted file mode 100644 index 02e7f6485..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/hook_payloads/push.json +++ /dev/null @@ -1,42 +0,0 @@ -{ - "object_kind": "push", - "before": "95790bf891e76fee5e1747ab589903a6a1f80f22", - "after": "da1560886d4f094c3e6c9ef40349f7d38b5d27d7", - "ref": "refs/heads/master", - "user_id": 4, - "user_name": "John Smith", - "user_email": "john@example.com", - "project_id": 15, - "repository": { - "name": "Diaspora", - "url": "git@example.com:mike/diasporadiaspora.git", - "description": "", - "homepage": "http://example.com/mike/diaspora", - "git_http_url":"http://example.com/mike/diaspora.git", - "git_ssh_url":"git@example.com:mike/diaspora.git", - "visibility_level":0 - }, - "commits": [ - { - "id": "b6568db1bc1dcd7f8b4d5a946b0b91f9dacd7327", - "message": "Update Catalan translation to e38cb41.", - "timestamp": "2011-12-12T14:27:31+02:00", - "url": "http://example.com/mike/diaspora/commit/b6568db1bc1dcd7f8b4d5a946b0b91f9dacd7327", - "author": { - "name": "Jordi Mallach", - "email": "jordi@softcatala.org" - } - }, - { - "id": "da1560886d4f094c3e6c9ef40349f7d38b5d27d7", - "message": "fixed readme", - "timestamp": "2012-01-03T23:36:29+02:00", - "url": "http://example.com/mike/diaspora/commit/da1560886d4f094c3e6c9ef40349f7d38b5d27d7", - "author": { - "name": "GitLab dev user", - "email": "gitlabdev@dv6700.(none)" - } - } - ], - "total_commits_count": 4 -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/hooks/show.json b/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/hooks/show.json deleted file mode 100644 index ce7f3aca2..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/hooks/show.json +++ /dev/null @@ -1,9 +0,0 @@ -{ - "id": 1, - "url": "http://example.com/hook", - "project_id": 3, - "push_events": "true", - "issues_events": "true", - "merge_requests_events": "true", - "created_at": "2012-10-12T17:04:47Z" -} \ No newline at end of file diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/projects/branches/index.json b/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/projects/branches/index.json deleted file mode 100644 index 0e62917a0..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/projects/branches/index.json +++ /dev/null @@ -1,50 +0,0 @@ -[ - { - "name": "async", - "commit": { - "id": "a2b702edecdf41f07b42653eb1abe30ce98b9fca", - "parents": [ - { - "id": "3f94fc7c85061973edc9906ae170cc269b07ca55" - } - ], - "tree": "c68537c6534a02cc2b176ca1549f4ffa190b58ee", - "message": "give caolan credit where it's due (up top)", - "author": { - "name": "Jeremy Ashkenas", - "email": "jashkenas@example.com" - }, - "committer": { - "name": "Jeremy Ashkenas", - "email": "jashkenas@example.com" - }, - "authored_date": "2010-12-08T21:28:50+00:00", - "committed_date": "2010-12-08T21:28:50+00:00" - }, - "protected": false - }, - { - "name": "gh-pages", - "commit": { - "id": "101c10a60019fe870d21868835f65c25d64968fc", - "parents": [ - { - "id": "9c15d2e26945a665131af5d7b6d30a06ba338aaa" - } - ], - "tree": "fb5cc9d45da3014b17a876ad539976a0fb9b352a", - "message": "Underscore.js 1.5.2", - "author": { - "name": "Jeremy Ashkenas", - "email": "jashkenas@example.com" - }, - "committer": { - "name": "Jeremy Ashkenas", - "email": "jashkenas@example.com" - }, - "authored_date": "2013-09-07T12: 58: 21+00: 00", - "committed_date": "2013-09-07T12: 58: 21+00: 00" - }, - "protected": false - } -] \ No newline at end of file diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/projects/index.json b/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/projects/index.json deleted file mode 100644 index 6528d6cc4..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/projects/index.json +++ /dev/null @@ -1,72 +0,0 @@ -[ - { - "id": 4, - "description": null, - "default_branch": "master", - "public": false, - "visibility_level": 0, - "ssh_url_to_repo": "git@example.com:diaspora/diaspora-client.git", - "http_url_to_repo": "http://example.com/diaspora/diaspora-client.git", - "web_url": "http://example.com/diaspora/diaspora-client", - "owner": { - "id": 3, - "name": "Diaspora", - "created_at": "2013-09-30T13: 46: 02Z" - }, - "name": "Diaspora Client", - "name_with_namespace": "Diaspora / Diaspora Client", - "path": "diaspora-client", - "path_with_namespace": "diaspora/diaspora-client", - "issues_enabled": true, - "merge_requests_enabled": true, - "wall_enabled": false, - "wiki_enabled": true, - "snippets_enabled": false, - "created_at": "2013-09-30T13: 46: 02Z", - "last_activity_at": "2013-09-30T13: 46: 02Z", - "namespace": { - "created_at": "2013-09-30T13: 46: 02Z", - "description": "", - "id": 3, - "name": "Diaspora", - "owner_id": 1, - "path": "diaspora", - "updated_at": "2013-09-30T13: 46: 02Z" - } - }, - { - "id": 6, - "description": null, - "default_branch": "master", - "public": false, - "visibility_level": 0, - "ssh_url_to_repo": "git@example.com:brightbox/puppet.git", - "http_url_to_repo": "http://example.com/brightbox/puppet.git", - "web_url": "http://example.com/brightbox/puppet", - "owner": { - "id": 4, - "name": "Brightbox", - "created_at": "2013-09-30T13:46:02Z" - }, - "name": "Puppet", - "name_with_namespace": "Brightbox / Puppet", - "path": "puppet", - "path_with_namespace": "brightbox/puppet", - "issues_enabled": true, - "merge_requests_enabled": true, - "wall_enabled": false, - "wiki_enabled": true, - "snippets_enabled": false, - "created_at": "2013-09-30T13:46:02Z", - "last_activity_at": "2013-09-30T13:46:02Z", - "namespace": { - "created_at": "2013-09-30T13:46:02Z", - "description": "", - "id": 4, - "name": "Brightbox", - "owner_id": 1, - "path": "brightbox", - "updated_at": "2013-09-30T13:46:02Z" - } - } -] \ No newline at end of file diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/projects/merge_requests/index.json b/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/projects/merge_requests/index.json deleted file mode 100644 index b9cbbe5a5..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/projects/merge_requests/index.json +++ /dev/null @@ -1,30 +0,0 @@ -[ - { - "id": 1, - "iid": 1, - "target_branch": "master", - "source_branch": "test1", - "project_id": 3, - "title": "test1", - "state": "opened", - "upvotes": 0, - "downvotes": 0, - "author": { - "id": 1, - "username": "admin", - "email": "admin@example.com", - "name": "Administrator", - "state": "active", - "created_at": "2012-04-29T08:46:00Z" - }, - "assignee": { - "id": 1, - "username": "admin", - "email": "admin@example.com", - "name": "Administrator", - "state": "active", - "created_at": "2012-04-29T08:46:00Z" - }, - "description":"fixed login page css paddings" - } -] diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/projects/merge_requests/notes/index.json b/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/projects/merge_requests/notes/index.json deleted file mode 100644 index 52f57e809..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/projects/merge_requests/notes/index.json +++ /dev/null @@ -1,16 +0,0 @@ -[ - { - "id": 301, - "body": "Comment for MR", - "attachment": null, - "author": { - "id": 1, - "username": "pipin", - "email": "admin@example.com", - "name": "Pip", - "state": "active", - "created_at": "2013-09-30T13:46:01Z" - }, - "created_at": "2013-10-02T08:57:14Z" - } -] \ No newline at end of file diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/projects/show.json b/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/projects/show.json deleted file mode 100644 index cabb359ec..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/projects/show.json +++ /dev/null @@ -1,45 +0,0 @@ -{ - "id": 3, - "description": null, - "default_branch": "master", - "public": false, - "visibility_level": 0, - "ssh_url_to_repo": "git@example.com:diaspora/diaspora-project-site.git", - "http_url_to_repo": "http://example.com/diaspora/diaspora-project-site.git", - "web_url": "http://example.com/diaspora/diaspora-project-site", - "owner": { - "id": 3, - "name": "Diaspora", - "created_at": "2013-09-30T13: 46: 02Z" - }, - "name": "Diaspora Project Site", - "name_with_namespace": "Diaspora / Diaspora Project Site", - "path": "diaspora-project-site", - "path_with_namespace": "diaspora/diaspora-project-site", - "issues_enabled": true, - "merge_requests_enabled": true, - "wall_enabled": false, - "wiki_enabled": true, - "snippets_enabled": false, - "created_at": "2013-09-30T13: 46: 02Z", - "last_activity_at": "2013-09-30T13: 46: 02Z", - "namespace": { - "created_at": "2013-09-30T13: 46: 02Z", - "description": "", - "id": 3, - "name": "Diaspora", - "owner_id": 1, - "path": "diaspora", - "updated_at": "2013-09-30T13: 46: 02Z" - }, - "permissions": { - "project_access": { - "access_level": 10, - "notification_level": 3 - }, - "group_access": { - "access_level": 50, - "notification_level": 3 - } - } -} \ No newline at end of file diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/public_keys/index.json b/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/public_keys/index.json deleted file mode 100644 index 67a9f4795..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/public_keys/index.json +++ /dev/null @@ -1,12 +0,0 @@ -[ - { - "id": 1, - "title": "Public key", - "key": "ssh-rsa AAAAB3NzaC1yc2EAAAABJQAAAIEAiPWx6WM4lhHNedGfBpPJNPpZ7yKu+dnn1SJejgt4596k6YjzGGphH2TUxwKzxcKDKKezwkpfnxPkSMkuEspGRt/aZZ9wa++Oi7Qkr8prgHc4soW6NUlfDzpvZK2H5E7eQaSeP3SAwGmQKUFHCddNaP0L+hM7zhFNzjFvpaMgJw0=" - }, - { - "id": 3, - "title": "Another Public key", - "key": "ssh-rsa AAAAB3NzaC1yc2EAAAABJQAAAIEAiPWx6WM4lhHNedGfBpPJNPpZ7yKu+dnn1SJejgt4596k6YjzGGphH2TUxwKzxcKDKKezwkpfnxPkSMkuEspGRt/aZZ9wa++Oi7Qkr8prgHc4soW6NUlfDzpvZK2H5E7eQaSeP3SAwGmQKUFHCddNaP0L+hM7zhFNzjFvpaMgJw0=" - } -] \ No newline at end of file diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/public_keys/show.json b/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/public_keys/show.json deleted file mode 100644 index ef2868b36..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/public_keys/show.json +++ /dev/null @@ -1,5 +0,0 @@ -{ - "id": 1, - "title": "Public key", - "key": "ssh-rsa AAAAB3NzaC1yc2EAAAABJQAAAIEAiPWx6WM4lhHNedGfBpPJNPpZ7yKu+dnn1SJejgt4596k6YjzGGphH2TUxwKzxcKDKKezwkpfnxPkSMkuEspGRt/aZZ9wa++Oi7Qkr8prgHc4soW6NUlfDzpvZK2H5E7eQaSeP3SAwGmQKUFHCddNaP0L+hM7zhFNzjFvpaMgJw0=" -} \ No newline at end of file diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/session/index.json b/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/session/index.json deleted file mode 100644 index bf55d8bd0..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/session/index.json +++ /dev/null @@ -1,23 +0,0 @@ -{ - "id": 1, - "username": "john_smith", - "email": "john@example.com", - "name": "John Smith", - "avatar_url": "http://someurl.com/avatar.png", - "state": "active", - "created_at": "2012-05-23T08:00:58Z", - "bio": "somebio", - "skype": "someskype", - "linkedin": "somelinkedin", - "twitter": "sometwitter", - "website_url": "http://example.com", - "theme_id": 1, - "color_scheme_id": 1, - "extern_uid": "someuid", - "provider": "github.com", - "is_admin": false, - "can_create_group": true, - "can_create_team": true, - "can_create_project": true, - "private_token": "dd34asd13as" -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/tags/index.json b/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/tags/index.json deleted file mode 100644 index 0e7474cbf..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/tags/index.json +++ /dev/null @@ -1,22 +0,0 @@ -[ - { - "name": "v1.0.0", - "commit": { - "id": "2695effb5807a22ff3d138d593fd856244e155e7", - "parents": [], - "tree": "38017f2f189336fe4497e9d230c5bb1bf873f08d", - "message": "Initial commit", - "author": { - "name": "John Smith", - "email": "john@example.com" - }, - "committer": { - "name": "Jack Smith", - "email": "jack@example.com" - }, - "authored_date": "2012-05-28T04:42:42-07:00", - "committed_date": "2012-05-28T04:42:42-07:00" - }, - "protected": null - } -] \ No newline at end of file diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/users/current.json b/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/users/current.json deleted file mode 100644 index e39d69667..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/users/current.json +++ /dev/null @@ -1,19 +0,0 @@ -{ - "id": 1, - "username": "john_smith", - "email": "john@example.com", - "name": "John Smith", - "private_token": "dd34asd13as", - "state": "active", - "created_at": "2012-05-23T08:00:58Z", - "bio": null, - "skype": "", - "linkedin": "", - "twitter": "", - "website_url": "", - "theme_id": 1, - "color_scheme_id": 2, - "is_admin": false, - "can_create_group": true, - "can_create_project": true -} \ No newline at end of file diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/users/index.json b/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/users/index.json deleted file mode 100644 index 5a14aa5d5..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/users/index.json +++ /dev/null @@ -1,41 +0,0 @@ -[ - { - "id": 1, - "username": "john_smith", - "email": "john@example.com", - "name": "John Smith", - "state": "active", - "created_at": "2012-05-23T08:00:58Z", - "bio": null, - "skype": "", - "linkedin": "", - "twitter": "", - "website_url": "", - "extern_uid": "john.smith", - "provider": "provider_name", - "theme_id": 1, - "color_scheme_id": 2, - "is_admin": false, - "can_create_group": true - }, - { - "id": 2, - "username": "jack_smith", - "email": "jack@example.com", - "name": "Jack Smith", - "state": "blocked", - "created_at": "2012-05-23T08:01:01Z", - "bio": null, - "skype": "", - "linkedin": "", - "twitter": "", - "website_url": "", - "extern_uid": "jack.smith", - "provider": "provider_name", - "theme_id": 1, - "color_scheme_id": 3, - "is_admin": false, - "can_create_group": true, - "can_create_project": true - } -] \ No newline at end of file diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/users/show.json b/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/users/show.json deleted file mode 100644 index af1d2d1bb..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/stubs/users/show.json +++ /dev/null @@ -1,15 +0,0 @@ -{ - "id": 6, - "username": "plouc", - "email": "plouc@plouc.com", - "name": "Raphaël Benitte", - "bio": null, - "skype": "", - "linkedin": "", - "twitter": "", - "theme_id": 2, - "state": "active", - "created_at": "2001-01-01T00:00:00Z", - "extern_uid": "uid=plouc", - "provider": "ldap" -} \ No newline at end of file diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/users.go b/vendor/github.com/Bugagazavr/go-gitlab-client/users.go deleted file mode 100644 index 6c2c9460f..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/users.go +++ /dev/null @@ -1,97 +0,0 @@ -package gogitlab - -import ( - "encoding/json" - "strconv" -) - -const ( - users_url = "/users" // Get users list - user_url = "/users/:id" // Get a single user. - current_user_url = "/user" // Get current user -) - -type User struct { - Id int `json:"id,omitempty"` - Username string `json:"username,omitempty"` - Email string `json:"email,omitempty"` - AvatarUrl string `json:"avatar_url,omitempty"` - Name string `json:"name,omitempty"` - State string `json:"state,omitempty"` - CreatedAt string `json:"created_at,omitempty"` - Bio string `json:"bio,omitempty"` - Skype string `json:"skype,omitempty"` - LinkedIn string `json:"linkedin,omitempty"` - Twitter string `json:"twitter,omitempty"` - ExternUid string `json:"extern_uid,omitempty"` - Provider string `json:"provider,omitempty"` - ThemeId int `json:"theme_id,omitempty"` - ColorSchemeId int `json:"color_scheme_id,color_scheme_id"` -} - -func (g *Gitlab) Users(page int, per_page int) ([]*User, error) { - - qry := map[string]string{ - "page": strconv.Itoa(page), - "per_page": strconv.Itoa(per_page)} - url := g.ResourceUrlQuery(users_url, nil, qry) - - var users []*User - - contents, err := g.buildAndExecRequest("GET", url, nil) - if err == nil { - err = json.Unmarshal(contents, &users) - } - - return users, err -} - -/* -Get a single user. - - GET /users/:id - -Parameters: - - id The ID of a user - -Usage: - - user, err := gitlab.User("your_user_id") - if err != nil { - fmt.Println(err.Error()) - } - fmt.Printf("%+v\n", user) -*/ -func (g *Gitlab) User(id string) (*User, error) { - - url := g.ResourceUrl(user_url, map[string]string{":id": id}) - - user := new(User) - - contents, err := g.buildAndExecRequest("GET", url, nil) - if err == nil { - err = json.Unmarshal(contents, &user) - } - - return user, err -} - -func (g *Gitlab) DeleteUser(id string) error { - url := g.ResourceUrl(user_url, map[string]string{":id": id}) - var err error - _, err = g.buildAndExecRequest("DELETE", url, nil) - return err -} - -func (g *Gitlab) CurrentUser() (User, error) { - url := g.ResourceUrl(current_user_url, nil) - var user User - - contents, err := g.buildAndExecRequest("GET", url, nil) - if err == nil { - err = json.Unmarshal(contents, &user) - } - - return user, err -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/users_test.go b/vendor/github.com/Bugagazavr/go-gitlab-client/users_test.go deleted file mode 100644 index 0102697a5..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/users_test.go +++ /dev/null @@ -1,53 +0,0 @@ -package gogitlab - -import ( - "github.com/stretchr/testify/assert" - "testing" -) - -func TestUsers(t *testing.T) { - ts, gitlab := Stub("stubs/users/index.json") - users, err := gitlab.Users(0, 100) - - assert.Equal(t, err, nil) - assert.Equal(t, len(users), 2) - defer ts.Close() -} - -func TestUser(t *testing.T) { - ts, gitlab := Stub("stubs/users/show.json") - user, err := gitlab.User("plouc") - - assert.Equal(t, err, nil) - assert.IsType(t, new(User), user) - assert.Equal(t, user.Id, 6) - assert.Equal(t, user.Username, "plouc") - assert.Equal(t, user.Name, "Raphaël Benitte") - assert.Equal(t, user.Bio, "") - assert.Equal(t, user.Skype, "") - assert.Equal(t, user.LinkedIn, "") - assert.Equal(t, user.Twitter, "") - assert.Equal(t, user.ThemeId, 2) - assert.Equal(t, user.State, "active") - assert.Equal(t, user.CreatedAt, "2001-01-01T00:00:00Z") - assert.Equal(t, user.ExternUid, "uid=plouc") - assert.Equal(t, user.Provider, "ldap") - defer ts.Close() -} - -func TestDeleteUser(t *testing.T) { - ts, gitlab := Stub("") - err := gitlab.DeleteUser("1") - - assert.Equal(t, err, nil) - defer ts.Close() -} - -func TestCurrentUser(t *testing.T) { - ts, gitlab := Stub("stubs/users/current.json") - user, err := gitlab.CurrentUser() - - assert.Equal(t, err, nil) - assert.Equal(t, user.Username, "john_smith") - defer ts.Close() -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/util.go b/vendor/github.com/Bugagazavr/go-gitlab-client/util.go deleted file mode 100644 index 8e47c681f..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/util.go +++ /dev/null @@ -1,10 +0,0 @@ -package gogitlab - -import ( - "net/url" - "strings" -) - -func encodeParameter(value string) string { - return strings.Replace(url.QueryEscape(value), "/", "%2F", 0) -} diff --git a/vendor/github.com/Bugagazavr/go-gitlab-client/util_test.go b/vendor/github.com/Bugagazavr/go-gitlab-client/util_test.go deleted file mode 100644 index fdaed9cd3..000000000 --- a/vendor/github.com/Bugagazavr/go-gitlab-client/util_test.go +++ /dev/null @@ -1,11 +0,0 @@ -package gogitlab - -import ( - "github.com/stretchr/testify/assert" - "testing" -) - -func TestParameterEncoding(t *testing.T) { - assert.Equal(t, encodeParameter("namespace/project"), "namespace%2Fproject") - assert.Equal(t, encodeParameter("14"), "14") -} diff --git a/vendor/github.com/Sirupsen/logrus/entry_test.go b/vendor/github.com/Sirupsen/logrus/entry_test.go deleted file mode 100644 index 98717df49..000000000 --- a/vendor/github.com/Sirupsen/logrus/entry_test.go +++ /dev/null @@ -1,53 +0,0 @@ -package logrus - -import ( - "bytes" - "fmt" - "testing" - - "github.com/stretchr/testify/assert" -) - -func TestEntryPanicln(t *testing.T) { - errBoom := fmt.Errorf("boom time") - - defer func() { - p := recover() - assert.NotNil(t, p) - - switch pVal := p.(type) { - case *Entry: - assert.Equal(t, "kaboom", pVal.Message) - assert.Equal(t, errBoom, pVal.Data["err"]) - default: - t.Fatalf("want type *Entry, got %T: %#v", pVal, pVal) - } - }() - - logger := New() - logger.Out = &bytes.Buffer{} - entry := NewEntry(logger) - entry.WithField("err", errBoom).Panicln("kaboom") -} - -func TestEntryPanicf(t *testing.T) { - errBoom := fmt.Errorf("boom again") - - defer func() { - p := recover() - assert.NotNil(t, p) - - switch pVal := p.(type) { - case *Entry: - assert.Equal(t, "kaboom true", pVal.Message) - assert.Equal(t, errBoom, pVal.Data["err"]) - default: - t.Fatalf("want type *Entry, got %T: %#v", pVal, pVal) - } - }() - - logger := New() - logger.Out = &bytes.Buffer{} - entry := NewEntry(logger) - entry.WithField("err", errBoom).Panicf("kaboom %v", true) -} diff --git a/vendor/github.com/Sirupsen/logrus/examples/basic/basic.go b/vendor/github.com/Sirupsen/logrus/examples/basic/basic.go deleted file mode 100644 index a62ba45de..000000000 --- a/vendor/github.com/Sirupsen/logrus/examples/basic/basic.go +++ /dev/null @@ -1,40 +0,0 @@ -package main - -import ( - "github.com/Sirupsen/logrus" -) - -var log = logrus.New() - -func init() { - log.Formatter = new(logrus.JSONFormatter) - log.Formatter = new(logrus.TextFormatter) // default -} - -func main() { - defer func() { - err := recover() - if err != nil { - log.WithFields(logrus.Fields{ - "omg": true, - "err": err, - "number": 100, - }).Fatal("The ice breaks!") - } - }() - - log.WithFields(logrus.Fields{ - "animal": "walrus", - "size": 10, - }).Info("A group of walrus emerges from the ocean") - - log.WithFields(logrus.Fields{ - "omg": true, - "number": 122, - }).Warn("The group's number increased tremendously!") - - log.WithFields(logrus.Fields{ - "animal": "orca", - "size": 9009, - }).Panic("It's over 9000!") -} diff --git a/vendor/github.com/Sirupsen/logrus/examples/hook/hook.go b/vendor/github.com/Sirupsen/logrus/examples/hook/hook.go deleted file mode 100644 index 42e7a4c98..000000000 --- a/vendor/github.com/Sirupsen/logrus/examples/hook/hook.go +++ /dev/null @@ -1,35 +0,0 @@ -package main - -import ( - "github.com/Sirupsen/logrus" - "github.com/Sirupsen/logrus/hooks/airbrake" - "github.com/tobi/airbrake-go" -) - -var log = logrus.New() - -func init() { - log.Formatter = new(logrus.TextFormatter) // default - log.Hooks.Add(new(logrus_airbrake.AirbrakeHook)) -} - -func main() { - airbrake.Endpoint = "https://exceptions.whatever.com/notifier_api/v2/notices.xml" - airbrake.ApiKey = "whatever" - airbrake.Environment = "production" - - log.WithFields(logrus.Fields{ - "animal": "walrus", - "size": 10, - }).Info("A group of walrus emerges from the ocean") - - log.WithFields(logrus.Fields{ - "omg": true, - "number": 122, - }).Warn("The group's number increased tremendously!") - - log.WithFields(logrus.Fields{ - "omg": true, - "number": 100, - }).Fatal("The ice breaks!") -} diff --git a/vendor/github.com/Sirupsen/logrus/formatter_bench_test.go b/vendor/github.com/Sirupsen/logrus/formatter_bench_test.go deleted file mode 100644 index 77989da62..000000000 --- a/vendor/github.com/Sirupsen/logrus/formatter_bench_test.go +++ /dev/null @@ -1,88 +0,0 @@ -package logrus - -import ( - "testing" - "time" -) - -// smallFields is a small size data set for benchmarking -var smallFields = Fields{ - "foo": "bar", - "baz": "qux", - "one": "two", - "three": "four", -} - -// largeFields is a large size data set for benchmarking -var largeFields = Fields{ - "foo": "bar", - "baz": "qux", - "one": "two", - "three": "four", - "five": "six", - "seven": "eight", - "nine": "ten", - "eleven": "twelve", - "thirteen": "fourteen", - "fifteen": "sixteen", - "seventeen": "eighteen", - "nineteen": "twenty", - "a": "b", - "c": "d", - "e": "f", - "g": "h", - "i": "j", - "k": "l", - "m": "n", - "o": "p", - "q": "r", - "s": "t", - "u": "v", - "w": "x", - "y": "z", - "this": "will", - "make": "thirty", - "entries": "yeah", -} - -func BenchmarkSmallTextFormatter(b *testing.B) { - doBenchmark(b, &TextFormatter{DisableColors: true}, smallFields) -} - -func BenchmarkLargeTextFormatter(b *testing.B) { - doBenchmark(b, &TextFormatter{DisableColors: true}, largeFields) -} - -func BenchmarkSmallColoredTextFormatter(b *testing.B) { - doBenchmark(b, &TextFormatter{ForceColors: true}, smallFields) -} - -func BenchmarkLargeColoredTextFormatter(b *testing.B) { - doBenchmark(b, &TextFormatter{ForceColors: true}, largeFields) -} - -func BenchmarkSmallJSONFormatter(b *testing.B) { - doBenchmark(b, &JSONFormatter{}, smallFields) -} - -func BenchmarkLargeJSONFormatter(b *testing.B) { - doBenchmark(b, &JSONFormatter{}, largeFields) -} - -func doBenchmark(b *testing.B, formatter Formatter, fields Fields) { - entry := &Entry{ - Time: time.Time{}, - Level: InfoLevel, - Message: "message", - Data: fields, - } - var d []byte - var err error - for i := 0; i < b.N; i++ { - d, err = formatter.Format(entry) - if err != nil { - b.Fatal(err) - } - b.SetBytes(int64(len(d))) - } -} diff --git a/vendor/github.com/Sirupsen/logrus/hook_test.go b/vendor/github.com/Sirupsen/logrus/hook_test.go deleted file mode 100644 index 13f34cb6f..000000000 --- a/vendor/github.com/Sirupsen/logrus/hook_test.go +++ /dev/null @@ -1,122 +0,0 @@ -package logrus - -import ( - "testing" - - "github.com/stretchr/testify/assert" -) - -type TestHook struct { - Fired bool -} - -func (hook *TestHook) Fire(entry *Entry) error { - hook.Fired = true - return nil -} - -func (hook *TestHook) Levels() []Level { - return []Level{ - DebugLevel, - InfoLevel, - WarnLevel, - ErrorLevel, - FatalLevel, - PanicLevel, - } -} - -func TestHookFires(t *testing.T) { - hook := new(TestHook) - - LogAndAssertJSON(t, func(log *Logger) { - log.Hooks.Add(hook) - assert.Equal(t, hook.Fired, false) - - log.Print("test") - }, func(fields Fields) { - assert.Equal(t, hook.Fired, true) - }) -} - -type ModifyHook struct { -} - -func (hook *ModifyHook) Fire(entry *Entry) error { - entry.Data["wow"] = "whale" - return nil -} - -func (hook *ModifyHook) Levels() []Level { - return []Level{ - DebugLevel, - InfoLevel, - WarnLevel, - ErrorLevel, - FatalLevel, - PanicLevel, - } -} - -func TestHookCanModifyEntry(t *testing.T) { - hook := new(ModifyHook) - - LogAndAssertJSON(t, func(log *Logger) { - log.Hooks.Add(hook) - log.WithField("wow", "elephant").Print("test") - }, func(fields Fields) { - assert.Equal(t, fields["wow"], "whale") - }) -} - -func TestCanFireMultipleHooks(t *testing.T) { - hook1 := new(ModifyHook) - hook2 := new(TestHook) - - LogAndAssertJSON(t, func(log *Logger) { - log.Hooks.Add(hook1) - log.Hooks.Add(hook2) - - log.WithField("wow", "elephant").Print("test") - }, func(fields Fields) { - assert.Equal(t, fields["wow"], "whale") - assert.Equal(t, hook2.Fired, true) - }) -} - -type ErrorHook struct { - Fired bool -} - -func (hook *ErrorHook) Fire(entry *Entry) error { - hook.Fired = true - return nil -} - -func (hook *ErrorHook) Levels() []Level { - return []Level{ - ErrorLevel, - } -} - -func TestErrorHookShouldntFireOnInfo(t *testing.T) { - hook := new(ErrorHook) - - LogAndAssertJSON(t, func(log *Logger) { - log.Hooks.Add(hook) - log.Info("test") - }, func(fields Fields) { - assert.Equal(t, hook.Fired, false) - }) -} - -func TestErrorHookShouldFireOnError(t *testing.T) { - hook := new(ErrorHook) - - LogAndAssertJSON(t, func(log *Logger) { - log.Hooks.Add(hook) - log.Error("test") - }, func(fields Fields) { - assert.Equal(t, hook.Fired, true) - }) -} diff --git a/vendor/github.com/Sirupsen/logrus/hooks/airbrake/airbrake.go b/vendor/github.com/Sirupsen/logrus/hooks/airbrake/airbrake.go deleted file mode 100644 index 880d21ecd..000000000 --- a/vendor/github.com/Sirupsen/logrus/hooks/airbrake/airbrake.go +++ /dev/null @@ -1,54 +0,0 @@ -package logrus_airbrake - -import ( - "github.com/Sirupsen/logrus" - "github.com/tobi/airbrake-go" -) - -// AirbrakeHook to send exceptions to an exception-tracking service compatible -// with the Airbrake API. You must set: -// * airbrake.Endpoint -// * airbrake.ApiKey -// * airbrake.Environment (only sends exceptions when set to "production") -// -// Before using this hook, to send an error. Entries that trigger an Error, -// Fatal or Panic should now include an "error" field to send to Airbrake. -type AirbrakeHook struct{} - -func (hook *AirbrakeHook) Fire(entry *logrus.Entry) error { - if entry.Data["error"] == nil { - entry.Logger.WithFields(logrus.Fields{ - "source": "airbrake", - "endpoint": airbrake.Endpoint, - }).Warn("Exceptions sent to Airbrake must have an 'error' key with the error") - return nil - } - - err, ok := entry.Data["error"].(error) - if !ok { - entry.Logger.WithFields(logrus.Fields{ - "source": "airbrake", - "endpoint": airbrake.Endpoint, - }).Warn("Exceptions sent to Airbrake must have an `error` key of type `error`") - return nil - } - - airErr := airbrake.Notify(err) - if airErr != nil { - entry.Logger.WithFields(logrus.Fields{ - "source": "airbrake", - "endpoint": airbrake.Endpoint, - "error": airErr, - }).Warn("Failed to send error to Airbrake") - } - - return nil -} - -func (hook *AirbrakeHook) Levels() []logrus.Level { - return []logrus.Level{ - logrus.ErrorLevel, - logrus.FatalLevel, - logrus.PanicLevel, - } -} diff --git a/vendor/github.com/Sirupsen/logrus/hooks/papertrail/README.md b/vendor/github.com/Sirupsen/logrus/hooks/papertrail/README.md deleted file mode 100644 index ae61e9229..000000000 --- a/vendor/github.com/Sirupsen/logrus/hooks/papertrail/README.md +++ /dev/null @@ -1,28 +0,0 @@ -# Papertrail Hook for Logrus :walrus: - -[Papertrail](https://papertrailapp.com) provides hosted log management. Once stored in Papertrail, you can [group](http://help.papertrailapp.com/kb/how-it-works/groups/) your logs on various dimensions, [search](http://help.papertrailapp.com/kb/how-it-works/search-syntax) them, and trigger [alerts](http://help.papertrailapp.com/kb/how-it-works/alerts). - -In most deployments, you'll want to send logs to Papertrail via their [remote_syslog](http://help.papertrailapp.com/kb/configuration/configuring-centralized-logging-from-text-log-files-in-unix/) daemon, which requires no application-specific configuration. This hook is intended for relatively low-volume logging, likely in managed cloud hosting deployments where installing `remote_syslog` is not possible. - -## Usage - -You can find your Papertrail UDP port on your [Papertrail account page](https://papertrailapp.com/account/destinations). Substitute it below for `YOUR_PAPERTRAIL_UDP_PORT`. - -For `YOUR_APP_NAME`, substitute a short string that will readily identify your application or service in the logs. - -```go -import ( - "log/syslog" - "github.com/Sirupsen/logrus" - "github.com/Sirupsen/logrus/hooks/papertrail" -) - -func main() { - log := logrus.New() - hook, err := logrus_papertrail.NewPapertrailHook("logs.papertrailapp.com", YOUR_PAPERTRAIL_UDP_PORT, YOUR_APP_NAME) - - if err == nil { - log.Hooks.Add(hook) - } -} -``` diff --git a/vendor/github.com/Sirupsen/logrus/hooks/papertrail/papertrail.go b/vendor/github.com/Sirupsen/logrus/hooks/papertrail/papertrail.go deleted file mode 100644 index c0f10c1bd..000000000 --- a/vendor/github.com/Sirupsen/logrus/hooks/papertrail/papertrail.go +++ /dev/null @@ -1,55 +0,0 @@ -package logrus_papertrail - -import ( - "fmt" - "net" - "os" - "time" - - "github.com/Sirupsen/logrus" -) - -const ( - format = "Jan 2 15:04:05" -) - -// PapertrailHook to send logs to a logging service compatible with the Papertrail API. -type PapertrailHook struct { - Host string - Port int - AppName string - UDPConn net.Conn -} - -// NewPapertrailHook creates a hook to be added to an instance of logger. -func NewPapertrailHook(host string, port int, appName string) (*PapertrailHook, error) { - conn, err := net.Dial("udp", fmt.Sprintf("%s:%d", host, port)) - return &PapertrailHook{host, port, appName, conn}, err -} - -// Fire is called when a log event is fired. -func (hook *PapertrailHook) Fire(entry *logrus.Entry) error { - date := time.Now().Format(format) - msg, _ := entry.String() - payload := fmt.Sprintf("<22> %s %s: %s", date, hook.AppName, msg) - - bytesWritten, err := hook.UDPConn.Write([]byte(payload)) - if err != nil { - fmt.Fprintf(os.Stderr, "Unable to send log line to Papertrail via UDP. Wrote %d bytes before error: %v", bytesWritten, err) - return err - } - - return nil -} - -// Levels returns the available logging levels. -func (hook *PapertrailHook) Levels() []logrus.Level { - return []logrus.Level{ - logrus.PanicLevel, - logrus.FatalLevel, - logrus.ErrorLevel, - logrus.WarnLevel, - logrus.InfoLevel, - logrus.DebugLevel, - } -} diff --git a/vendor/github.com/Sirupsen/logrus/hooks/papertrail/papertrail_test.go b/vendor/github.com/Sirupsen/logrus/hooks/papertrail/papertrail_test.go deleted file mode 100644 index 96318d003..000000000 --- a/vendor/github.com/Sirupsen/logrus/hooks/papertrail/papertrail_test.go +++ /dev/null @@ -1,26 +0,0 @@ -package logrus_papertrail - -import ( - "fmt" - "testing" - - "github.com/Sirupsen/logrus" - "github.com/stvp/go-udp-testing" -) - -func TestWritingToUDP(t *testing.T) { - port := 16661 - udp.SetAddr(fmt.Sprintf(":%d", port)) - - hook, err := NewPapertrailHook("localhost", port, "test") - if err != nil { - t.Errorf("Unable to connect to local UDP server.") - } - - log := logrus.New() - log.Hooks.Add(hook) - - udp.ShouldReceive(t, "foo", func() { - log.Info("foo") - }) -} diff --git a/vendor/github.com/Sirupsen/logrus/hooks/sentry/README.md b/vendor/github.com/Sirupsen/logrus/hooks/sentry/README.md deleted file mode 100644 index a409f3b04..000000000 --- a/vendor/github.com/Sirupsen/logrus/hooks/sentry/README.md +++ /dev/null @@ -1,61 +0,0 @@ -# Sentry Hook for Logrus :walrus: - -[Sentry](https://getsentry.com) provides both self-hosted and hosted -solutions for exception tracking. -Both client and server are -[open source](https://github.com/getsentry/sentry). - -## Usage - -Every sentry application defined on the server gets a different -[DSN](https://www.getsentry.com/docs/). In the example below replace -`YOUR_DSN` with the one created for your application. - -```go -import ( - "github.com/Sirupsen/logrus" - "github.com/Sirupsen/logrus/hooks/sentry" -) - -func main() { - log := logrus.New() - hook, err := logrus_sentry.NewSentryHook(YOUR_DSN, []logrus.Level{ - logrus.PanicLevel, - logrus.FatalLevel, - logrus.ErrorLevel, - }) - - if err == nil { - log.Hooks.Add(hook) - } -} -``` - -## Special fields - -Some logrus fields have a special meaning in this hook, -these are server_name and logger. -When logs are sent to sentry these fields are treated differently. -- server_name (also known as hostname) is the name of the server which -is logging the event (hostname.example.com) -- logger is the part of the application which is logging the event. -In go this usually means setting it to the name of the package. - -## Timeout - -`Timeout` is the time the sentry hook will wait for a response -from the sentry server. - -If this time elapses with no response from -the server an error will be returned. - -If `Timeout` is set to 0 the SentryHook will not wait for a reply -and will assume a correct delivery. - -The SentryHook has a default timeout of `100 milliseconds` when created -with a call to `NewSentryHook`. This can be changed by assigning a value to the `Timeout` field: - -```go -hook, _ := logrus_sentry.NewSentryHook(...) -hook.Timeout = 20*time.Seconds -``` diff --git a/vendor/github.com/Sirupsen/logrus/hooks/sentry/sentry.go b/vendor/github.com/Sirupsen/logrus/hooks/sentry/sentry.go deleted file mode 100644 index 379f281c5..000000000 --- a/vendor/github.com/Sirupsen/logrus/hooks/sentry/sentry.go +++ /dev/null @@ -1,100 +0,0 @@ -package logrus_sentry - -import ( - "fmt" - "time" - - "github.com/Sirupsen/logrus" - "github.com/getsentry/raven-go" -) - -var ( - severityMap = map[logrus.Level]raven.Severity{ - logrus.DebugLevel: raven.DEBUG, - logrus.InfoLevel: raven.INFO, - logrus.WarnLevel: raven.WARNING, - logrus.ErrorLevel: raven.ERROR, - logrus.FatalLevel: raven.FATAL, - logrus.PanicLevel: raven.FATAL, - } -) - -func getAndDel(d logrus.Fields, key string) (string, bool) { - var ( - ok bool - v interface{} - val string - ) - if v, ok = d[key]; !ok { - return "", false - } - - if val, ok = v.(string); !ok { - return "", false - } - delete(d, key) - return val, true -} - -// SentryHook delivers logs to a sentry server. -type SentryHook struct { - // Timeout sets the time to wait for a delivery error from the sentry server. - // If this is set to zero the server will not wait for any response and will - // consider the message correctly sent - Timeout time.Duration - - client *raven.Client - levels []logrus.Level -} - -// NewSentryHook creates a hook to be added to an instance of logger -// and initializes the raven client. -// This method sets the timeout to 100 milliseconds. -func NewSentryHook(DSN string, levels []logrus.Level) (*SentryHook, error) { - client, err := raven.NewClient(DSN, nil) - if err != nil { - return nil, err - } - return &SentryHook{100 * time.Millisecond, client, levels}, nil -} - -// Called when an event should be sent to sentry -// Special fields that sentry uses to give more information to the server -// are extracted from entry.Data (if they are found) -// These fields are: logger and server_name -func (hook *SentryHook) Fire(entry *logrus.Entry) error { - packet := &raven.Packet{ - Message: entry.Message, - Timestamp: raven.Timestamp(entry.Time), - Level: severityMap[entry.Level], - Platform: "go", - } - - d := entry.Data - - if logger, ok := getAndDel(d, "logger"); ok { - packet.Logger = logger - } - if serverName, ok := getAndDel(d, "server_name"); ok { - packet.ServerName = serverName - } - packet.Extra = map[string]interface{}(d) - - _, errCh := hook.client.Capture(packet, nil) - timeout := hook.Timeout - if timeout != 0 { - timeoutCh := time.After(timeout) - select { - case err := <-errCh: - return err - case <-timeoutCh: - return fmt.Errorf("no response from sentry server in %s", timeout) - } - } - return nil -} - -// Levels returns the available logging levels. -func (hook *SentryHook) Levels() []logrus.Level { - return hook.levels -} diff --git a/vendor/github.com/Sirupsen/logrus/hooks/sentry/sentry_test.go b/vendor/github.com/Sirupsen/logrus/hooks/sentry/sentry_test.go deleted file mode 100644 index 45f18d170..000000000 --- a/vendor/github.com/Sirupsen/logrus/hooks/sentry/sentry_test.go +++ /dev/null @@ -1,97 +0,0 @@ -package logrus_sentry - -import ( - "encoding/json" - "fmt" - "io/ioutil" - "net/http" - "net/http/httptest" - "strings" - "testing" - - "github.com/Sirupsen/logrus" - "github.com/getsentry/raven-go" -) - -const ( - message = "error message" - server_name = "testserver.internal" - logger_name = "test.logger" -) - -func getTestLogger() *logrus.Logger { - l := logrus.New() - l.Out = ioutil.Discard - return l -} - -func WithTestDSN(t *testing.T, tf func(string, <-chan *raven.Packet)) { - pch := make(chan *raven.Packet, 1) - s := httptest.NewServer(http.HandlerFunc(func(rw http.ResponseWriter, req *http.Request) { - defer req.Body.Close() - d := json.NewDecoder(req.Body) - p := &raven.Packet{} - err := d.Decode(p) - if err != nil { - t.Fatal(err.Error()) - } - - pch <- p - })) - defer s.Close() - - fragments := strings.SplitN(s.URL, "://", 2) - dsn := fmt.Sprintf( - "%s://public:secret@%s/sentry/project-id", - fragments[0], - fragments[1], - ) - tf(dsn, pch) -} - -func TestSpecialFields(t *testing.T) { - WithTestDSN(t, func(dsn string, pch <-chan *raven.Packet) { - logger := getTestLogger() - - hook, err := NewSentryHook(dsn, []logrus.Level{ - logrus.ErrorLevel, - }) - - if err != nil { - t.Fatal(err.Error()) - } - logger.Hooks.Add(hook) - logger.WithFields(logrus.Fields{ - "server_name": server_name, - "logger": logger_name, - }).Error(message) - - packet := <-pch - if packet.Logger != logger_name { - t.Errorf("logger should have been %s, was %s", logger_name, packet.Logger) - } - - if packet.ServerName != server_name { - t.Errorf("server_name should have been %s, was %s", server_name, packet.ServerName) - } - }) -} - -func TestSentryHandler(t *testing.T) { - WithTestDSN(t, func(dsn string, pch <-chan *raven.Packet) { - logger := getTestLogger() - hook, err := NewSentryHook(dsn, []logrus.Level{ - logrus.ErrorLevel, - }) - if err != nil { - t.Fatal(err.Error()) - } - logger.Hooks.Add(hook) - - logger.Error(message) - packet := <-pch - if packet.Message != message { - t.Errorf("message should have been %s, was %s", message, packet.Message) - } - }) -} diff --git a/vendor/github.com/Sirupsen/logrus/hooks/syslog/README.md b/vendor/github.com/Sirupsen/logrus/hooks/syslog/README.md deleted file mode 100644 index 4dbb8e729..000000000 --- a/vendor/github.com/Sirupsen/logrus/hooks/syslog/README.md +++ /dev/null @@ -1,20 +0,0 @@ -# Syslog Hooks for Logrus :walrus: - -## Usage - -```go -import ( - "log/syslog" - "github.com/Sirupsen/logrus" - logrus_syslog "github.com/Sirupsen/logrus/hooks/syslog" -) - -func main() { - log := logrus.New() - hook, err := logrus_syslog.NewSyslogHook("udp", "localhost:514", syslog.LOG_INFO, "") - - if err == nil { - log.Hooks.Add(hook) - } -} -``` diff --git a/vendor/github.com/Sirupsen/logrus/hooks/syslog/syslog.go b/vendor/github.com/Sirupsen/logrus/hooks/syslog/syslog.go deleted file mode 100644 index b6fa37462..000000000 --- a/vendor/github.com/Sirupsen/logrus/hooks/syslog/syslog.go +++ /dev/null @@ -1,59 +0,0 @@ -package logrus_syslog - -import ( - "fmt" - "github.com/Sirupsen/logrus" - "log/syslog" - "os" -) - -// SyslogHook to send logs via syslog. -type SyslogHook struct { - Writer *syslog.Writer - SyslogNetwork string - SyslogRaddr string -} - -// Creates a hook to be added to an instance of logger. This is called with -// `hook, err := NewSyslogHook("udp", "localhost:514", syslog.LOG_DEBUG, "")` -// `if err == nil { log.Hooks.Add(hook) }` -func NewSyslogHook(network, raddr string, priority syslog.Priority, tag string) (*SyslogHook, error) { - w, err := syslog.Dial(network, raddr, priority, tag) - return &SyslogHook{w, network, raddr}, err -} - -func (hook *SyslogHook) Fire(entry *logrus.Entry) error { - line, err := entry.String() - if err != nil { - fmt.Fprintf(os.Stderr, "Unable to read entry, %v", err) - return err - } - - switch entry.Level { - case logrus.PanicLevel: - return hook.Writer.Crit(line) - case logrus.FatalLevel: - return hook.Writer.Crit(line) - case logrus.ErrorLevel: - return hook.Writer.Err(line) - case logrus.WarnLevel: - return hook.Writer.Warning(line) - case logrus.InfoLevel: - return hook.Writer.Info(line) - case logrus.DebugLevel: - return hook.Writer.Debug(line) - default: - return nil - } -} - -func (hook *SyslogHook) Levels() []logrus.Level { - return []logrus.Level{ - logrus.PanicLevel, - logrus.FatalLevel, - logrus.ErrorLevel, - logrus.WarnLevel, - logrus.InfoLevel, - logrus.DebugLevel, - } -} diff --git a/vendor/github.com/Sirupsen/logrus/hooks/syslog/syslog_test.go b/vendor/github.com/Sirupsen/logrus/hooks/syslog/syslog_test.go deleted file mode 100644 index 42762dc10..000000000 --- a/vendor/github.com/Sirupsen/logrus/hooks/syslog/syslog_test.go +++ /dev/null @@ -1,26 +0,0 @@ -package logrus_syslog - -import ( - "github.com/Sirupsen/logrus" - "log/syslog" - "testing" -) - -func TestLocalhostAddAndPrint(t *testing.T) { - log := logrus.New() - hook, err := NewSyslogHook("udp", "localhost:514", syslog.LOG_INFO, "") - - if err != nil { - t.Errorf("Unable to connect to local syslog.") - } - - log.Hooks.Add(hook) - - for _, level := range hook.Levels() { - if len(log.Hooks[level]) != 1 { - t.Errorf("SyslogHook was not added. The length of log.Hooks[%v]: %v", level, len(log.Hooks[level])) - } - } - - log.Info("Congratulations!") -} diff --git a/vendor/github.com/Sirupsen/logrus/logrus_test.go b/vendor/github.com/Sirupsen/logrus/logrus_test.go deleted file mode 100644 index 7f52c6fbc..000000000 --- a/vendor/github.com/Sirupsen/logrus/logrus_test.go +++ /dev/null @@ -1,283 +0,0 @@ -package logrus - -import ( - "bytes" - "encoding/json" - "strconv" - "strings" - "testing" - - "github.com/stretchr/testify/assert" -) - -func LogAndAssertJSON(t *testing.T, log func(*Logger), assertions func(fields Fields)) { - var buffer bytes.Buffer - var fields Fields - - logger := New() - logger.Out = &buffer - logger.Formatter = new(JSONFormatter) - - log(logger) - - err := json.Unmarshal(buffer.Bytes(), &fields) - assert.Nil(t, err) - - assertions(fields) -} - -func LogAndAssertText(t *testing.T, log func(*Logger), assertions func(fields map[string]string)) { - var buffer bytes.Buffer - - logger := New() - logger.Out = &buffer - logger.Formatter = &TextFormatter{ - DisableColors: true, - } - - log(logger) - - fields := make(map[string]string) - for _, kv := range strings.Split(buffer.String(), " ") { - if !strings.Contains(kv, "=") { - continue - } - kvArr := strings.Split(kv, "=") - key := strings.TrimSpace(kvArr[0]) - val := kvArr[1] - if kvArr[1][0] == '"' { - var err error - val, err = strconv.Unquote(val) - assert.NoError(t, err) - } - fields[key] = val - } - assertions(fields) -} - -func TestPrint(t *testing.T) { - LogAndAssertJSON(t, func(log *Logger) { - log.Print("test") - }, func(fields Fields) { - assert.Equal(t, fields["msg"], "test") - assert.Equal(t, fields["level"], "info") - }) -} - -func TestInfo(t *testing.T) { - LogAndAssertJSON(t, func(log *Logger) { - log.Info("test") - }, func(fields Fields) { - assert.Equal(t, fields["msg"], "test") - assert.Equal(t, fields["level"], "info") - }) -} - -func TestWarn(t *testing.T) { - LogAndAssertJSON(t, func(log *Logger) { - log.Warn("test") - }, func(fields Fields) { - assert.Equal(t, fields["msg"], "test") - assert.Equal(t, fields["level"], "warning") - }) -} - -func TestInfolnShouldAddSpacesBetweenStrings(t *testing.T) { - LogAndAssertJSON(t, func(log *Logger) { - log.Infoln("test", "test") - }, func(fields Fields) { - assert.Equal(t, fields["msg"], "test test") - }) -} - -func TestInfolnShouldAddSpacesBetweenStringAndNonstring(t *testing.T) { - LogAndAssertJSON(t, func(log *Logger) { - log.Infoln("test", 10) - }, func(fields Fields) { - assert.Equal(t, fields["msg"], "test 10") - }) -} - -func TestInfolnShouldAddSpacesBetweenTwoNonStrings(t *testing.T) { - LogAndAssertJSON(t, func(log *Logger) { - log.Infoln(10, 10) - }, func(fields Fields) { - assert.Equal(t, fields["msg"], "10 10") - }) -} - -func TestInfoShouldAddSpacesBetweenTwoNonStrings(t *testing.T) { - LogAndAssertJSON(t, func(log *Logger) { - log.Infoln(10, 10) - }, func(fields Fields) { - assert.Equal(t, fields["msg"], "10 10") - }) -} - -func TestInfoShouldNotAddSpacesBetweenStringAndNonstring(t *testing.T) { - LogAndAssertJSON(t, func(log *Logger) { - log.Info("test", 10) - }, func(fields Fields) { - assert.Equal(t, fields["msg"], "test10") - }) -} - -func TestInfoShouldNotAddSpacesBetweenStrings(t *testing.T) { - LogAndAssertJSON(t, func(log *Logger) { - log.Info("test", "test") - }, func(fields Fields) { - assert.Equal(t, fields["msg"], "testtest") - }) -} - -func TestWithFieldsShouldAllowAssignments(t *testing.T) { - var buffer bytes.Buffer - var fields Fields - - logger := New() - logger.Out = &buffer - logger.Formatter = new(JSONFormatter) - - localLog := logger.WithFields(Fields{ - "key1": "value1", - }) - - localLog.WithField("key2", "value2").Info("test") - err := json.Unmarshal(buffer.Bytes(), &fields) - assert.Nil(t, err) - - assert.Equal(t, "value2", fields["key2"]) - assert.Equal(t, "value1", fields["key1"]) - - buffer = bytes.Buffer{} - fields = Fields{} - localLog.Info("test") - err = json.Unmarshal(buffer.Bytes(), &fields) - assert.Nil(t, err) - - _, ok := fields["key2"] - assert.Equal(t, false, ok) - assert.Equal(t, "value1", fields["key1"]) -} - -func TestUserSuppliedFieldDoesNotOverwriteDefaults(t *testing.T) { - LogAndAssertJSON(t, func(log *Logger) { - log.WithField("msg", "hello").Info("test") - }, func(fields Fields) { - assert.Equal(t, fields["msg"], "test") - }) -} - -func TestUserSuppliedMsgFieldHasPrefix(t *testing.T) { - LogAndAssertJSON(t, func(log *Logger) { - log.WithField("msg", "hello").Info("test") - }, func(fields Fields) { - assert.Equal(t, fields["msg"], "test") - assert.Equal(t, fields["fields.msg"], "hello") - }) -} - -func TestUserSuppliedTimeFieldHasPrefix(t *testing.T) { - LogAndAssertJSON(t, func(log *Logger) { - log.WithField("time", "hello").Info("test") - }, func(fields Fields) { - assert.Equal(t, fields["fields.time"], "hello") - }) -} - -func TestUserSuppliedLevelFieldHasPrefix(t *testing.T) { - LogAndAssertJSON(t, func(log *Logger) { - log.WithField("level", 1).Info("test") - }, func(fields Fields) { - assert.Equal(t, fields["level"], "info") - assert.Equal(t, fields["fields.level"], 1) - }) -} - -func TestDefaultFieldsAreNotPrefixed(t *testing.T) { - LogAndAssertText(t, func(log *Logger) { - ll := log.WithField("herp", "derp") - ll.Info("hello") - ll.Info("bye") - }, func(fields map[string]string) { - for _, fieldName := range []string{"fields.level", "fields.time", "fields.msg"} { - if _, ok := fields[fieldName]; ok { - t.Fatalf("should not have prefixed %q: %v", fieldName, fields) - } - } - }) -} - -func TestDoubleLoggingDoesntPrefixPreviousFields(t *testing.T) { - - var buffer bytes.Buffer - var fields Fields - - logger := New() - logger.Out = &buffer - logger.Formatter = new(JSONFormatter) - - llog := logger.WithField("context", "eating raw fish") - - llog.Info("looks delicious") - - err := json.Unmarshal(buffer.Bytes(), &fields) - assert.NoError(t, err, "should have decoded first message") - assert.Equal(t, len(fields), 4, "should only have msg/time/level/context fields") - assert.Equal(t, fields["msg"], "looks delicious") - assert.Equal(t, fields["context"], "eating raw fish") - - buffer.Reset() - - llog.Warn("omg it is!") - - err = json.Unmarshal(buffer.Bytes(), &fields) - assert.NoError(t, err, "should have decoded second message") - assert.Equal(t, len(fields), 4, "should only have msg/time/level/context fields") - assert.Equal(t, fields["msg"], "omg it is!") - assert.Equal(t, fields["context"], "eating raw fish") - assert.Nil(t, fields["fields.msg"], "should not have prefixed previous `msg` entry") - -} - -func TestConvertLevelToString(t *testing.T) { - assert.Equal(t, "debug", DebugLevel.String()) - assert.Equal(t, "info", InfoLevel.String()) - assert.Equal(t, "warning", WarnLevel.String()) - assert.Equal(t, "error", ErrorLevel.String()) - assert.Equal(t, "fatal", FatalLevel.String()) - assert.Equal(t, "panic", PanicLevel.String()) -} - -func TestParseLevel(t *testing.T) { - l, err := ParseLevel("panic") - assert.Nil(t, err) - assert.Equal(t, PanicLevel, l) - - l, err = ParseLevel("fatal") - assert.Nil(t, err) - assert.Equal(t, FatalLevel, l) - - l, err = ParseLevel("error") - assert.Nil(t, err) - assert.Equal(t, ErrorLevel, l) - - l, err = ParseLevel("warn") - assert.Nil(t, err) - assert.Equal(t, WarnLevel, l) - - l, err = ParseLevel("warning") - assert.Nil(t, err) - assert.Equal(t, WarnLevel, l) - - l, err = ParseLevel("info") - assert.Nil(t, err) - assert.Equal(t, InfoLevel, l) - - l, err = ParseLevel("debug") - assert.Nil(t, err) - assert.Equal(t, DebugLevel, l) - - l, err = ParseLevel("invalid") - assert.Equal(t, "not a valid logrus Level: \"invalid\"", err.Error()) -} diff --git a/vendor/github.com/Sirupsen/logrus/text_formatter_test.go b/vendor/github.com/Sirupsen/logrus/text_formatter_test.go deleted file mode 100644 index f604f1b00..000000000 --- a/vendor/github.com/Sirupsen/logrus/text_formatter_test.go +++ /dev/null @@ -1,33 +0,0 @@ -package logrus - -import ( - "bytes" - "errors" - - "testing" -) - -func TestQuoting(t *testing.T) { - tf := &TextFormatter{DisableColors: true} - - checkQuoting := func(q bool, value interface{}) { - b, _ := tf.Format(WithField("test", value)) - idx := bytes.Index(b, ([]byte)("test=")) - cont := bytes.Contains(b[idx+5:], []byte{'"'}) - if cont != q { - if q { - t.Errorf("quoting expected for: %#v", value) - } else { - t.Errorf("quoting not expected for: %#v", value) - } - } - } - - checkQuoting(false, "abcd") - checkQuoting(false, "v1.0") - checkQuoting(true, "/foobar") - checkQuoting(true, "x y") - checkQuoting(true, "x,y") - checkQuoting(false, errors.New("invalid")) - checkQuoting(true, errors.New("invalid argument")) -} diff --git a/vendor/github.com/codegangsta/cli/LICENSE b/vendor/github.com/codegangsta/cli/LICENSE deleted file mode 100644 index 5515ccfb7..000000000 --- a/vendor/github.com/codegangsta/cli/LICENSE +++ /dev/null @@ -1,21 +0,0 @@ -Copyright (C) 2013 Jeremy Saenz -All Rights Reserved. - -MIT LICENSE - -Permission is hereby granted, free of charge, to any person obtaining a copy of -this software and associated documentation files (the "Software"), to deal in -the Software without restriction, including without limitation the rights to -use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of -the Software, and to permit persons to whom the Software is furnished to do so, -subject to the following conditions: - -The above copyright notice and this permission notice shall be included in all -copies or substantial portions of the Software. - -THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR -IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS -FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR -COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER -IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN -CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/vendor/github.com/codegangsta/cli/README.md b/vendor/github.com/codegangsta/cli/README.md deleted file mode 100644 index 0e8327b8b..000000000 --- a/vendor/github.com/codegangsta/cli/README.md +++ /dev/null @@ -1,298 +0,0 @@ -[![Build Status](https://travis-ci.org/codegangsta/cli.png?branch=master)](https://travis-ci.org/codegangsta/cli) - -# cli.go -cli.go is simple, fast, and fun package for building command line apps in Go. The goal is to enable developers to write fast and distributable command line applications in an expressive way. - -You can view the API docs here: -http://godoc.org/github.com/codegangsta/cli - -## Overview -Command line apps are usually so tiny that there is absolutely no reason why your code should *not* be self-documenting. Things like generating help text and parsing command flags/options should not hinder productivity when writing a command line app. - -**This is where cli.go comes into play.** cli.go makes command line programming fun, organized, and expressive! - -## Installation -Make sure you have a working Go environment (go 1.1 is *required*). [See the install instructions](http://golang.org/doc/install.html). - -To install `cli.go`, simply run: -``` -$ go get github.com/codegangsta/cli -``` - -Make sure your `PATH` includes to the `$GOPATH/bin` directory so your commands can be easily used: -``` -export PATH=$PATH:$GOPATH/bin -``` - -## Getting Started -One of the philosophies behind cli.go is that an API should be playful and full of discovery. So a cli.go app can be as little as one line of code in `main()`. - -``` go -package main - -import ( - "os" - "github.com/codegangsta/cli" -) - -func main() { - cli.NewApp().Run(os.Args) -} -``` - -This app will run and show help text, but is not very useful. Let's give an action to execute and some help documentation: - -``` go -package main - -import ( - "os" - "github.com/codegangsta/cli" -) - -func main() { - app := cli.NewApp() - app.Name = "boom" - app.Usage = "make an explosive entrance" - app.Action = func(c *cli.Context) { - println("boom! I say!") - } - - app.Run(os.Args) -} -``` - -Running this already gives you a ton of functionality, plus support for things like subcommands and flags, which are covered below. - -## Example - -Being a programmer can be a lonely job. Thankfully by the power of automation that is not the case! Let's create a greeter app to fend off our demons of loneliness! - -Start by creating a directory named `greet`, and within it, add a file, `greet.go` with the following code in it: - -``` go -package main - -import ( - "os" - "github.com/codegangsta/cli" -) - -func main() { - app := cli.NewApp() - app.Name = "greet" - app.Usage = "fight the loneliness!" - app.Action = func(c *cli.Context) { - println("Hello friend!") - } - - app.Run(os.Args) -} -``` - -Install our command to the `$GOPATH/bin` directory: - -``` -$ go install -``` - -Finally run our new command: - -``` -$ greet -Hello friend! -``` - -cli.go also generates some bitchass help text: -``` -$ greet help -NAME: - greet - fight the loneliness! - -USAGE: - greet [global options] command [command options] [arguments...] - -VERSION: - 0.0.0 - -COMMANDS: - help, h Shows a list of commands or help for one command - -GLOBAL OPTIONS - --version Shows version information -``` - -### Arguments -You can lookup arguments by calling the `Args` function on `cli.Context`. - -``` go -... -app.Action = func(c *cli.Context) { - println("Hello", c.Args()[0]) -} -... -``` - -### Flags -Setting and querying flags is simple. -``` go -... -app.Flags = []cli.Flag { - cli.StringFlag{ - Name: "lang", - Value: "english", - Usage: "language for the greeting", - }, -} -app.Action = func(c *cli.Context) { - name := "someone" - if len(c.Args()) > 0 { - name = c.Args()[0] - } - if c.String("lang") == "spanish" { - println("Hola", name) - } else { - println("Hello", name) - } -} -... -``` - -#### Alternate Names - -You can set alternate (or short) names for flags by providing a comma-delimited list for the `Name`. e.g. - -``` go -app.Flags = []cli.Flag { - cli.StringFlag{ - Name: "lang, l", - Value: "english", - Usage: "language for the greeting", - }, -} -``` - -That flag can then be set with `--lang spanish` or `-l spanish`. Note that giving two different forms of the same flag in the same command invocation is an error. - -#### Values from the Environment - -You can also have the default value set from the environment via `EnvVar`. e.g. - -``` go -app.Flags = []cli.Flag { - cli.StringFlag{ - Name: "lang, l", - Value: "english", - Usage: "language for the greeting", - EnvVar: "APP_LANG", - }, -} -``` - -The `EnvVar` may also be given as a comma-delimited "cascade", where the first environment variable that resolves is used as the default. - -``` go -app.Flags = []cli.Flag { - cli.StringFlag{ - Name: "lang, l", - Value: "english", - Usage: "language for the greeting", - EnvVar: "LEGACY_COMPAT_LANG,APP_LANG,LANG", - }, -} -``` - -### Subcommands - -Subcommands can be defined for a more git-like command line app. -```go -... -app.Commands = []cli.Command{ - { - Name: "add", - ShortName: "a", - Usage: "add a task to the list", - Action: func(c *cli.Context) { - println("added task: ", c.Args().First()) - }, - }, - { - Name: "complete", - ShortName: "c", - Usage: "complete a task on the list", - Action: func(c *cli.Context) { - println("completed task: ", c.Args().First()) - }, - }, - { - Name: "template", - ShortName: "r", - Usage: "options for task templates", - Subcommands: []cli.Command{ - { - Name: "add", - Usage: "add a new template", - Action: func(c *cli.Context) { - println("new task template: ", c.Args().First()) - }, - }, - { - Name: "remove", - Usage: "remove an existing template", - Action: func(c *cli.Context) { - println("removed task template: ", c.Args().First()) - }, - }, - }, - }, -} -... -``` - -### Bash Completion - -You can enable completion commands by setting the `EnableBashCompletion` -flag on the `App` object. By default, this setting will only auto-complete to -show an app's subcommands, but you can write your own completion methods for -the App or its subcommands. -```go -... -var tasks = []string{"cook", "clean", "laundry", "eat", "sleep", "code"} -app := cli.NewApp() -app.EnableBashCompletion = true -app.Commands = []cli.Command{ - { - Name: "complete", - ShortName: "c", - Usage: "complete a task on the list", - Action: func(c *cli.Context) { - println("completed task: ", c.Args().First()) - }, - BashComplete: func(c *cli.Context) { - // This will complete if no args are passed - if len(c.Args()) > 0 { - return - } - for _, t := range tasks { - fmt.Println(t) - } - }, - } -} -... -``` - -#### To Enable - -Source the `autocomplete/bash_autocomplete` file in your `.bashrc` file while -setting the `PROG` variable to the name of your program: - -`PROG=myprogram source /.../cli/autocomplete/bash_autocomplete` - - -## Contribution Guidelines -Feel free to put up a pull request to fix a bug or maybe add a feature. I will give it a code review and make sure that it does not break backwards compatibility. If I or any other collaborators agree that it is in line with the vision of the project, we will work with you to get the code into a mergeable state and merge it into the master branch. - -If you are have contributed something significant to the project, I will most likely add you as a collaborator. As a collaborator you are given the ability to merge others pull requests. It is very important that new code does not break existing code, so be careful about what code you do choose to merge. If you have any questions feel free to link @codegangsta to the issue in question and we can review it together. - -If you feel like you have contributed to the project but have not yet been added as a collaborator, I probably forgot to add you. Hit @codegangsta up over email and we will get it figured out. diff --git a/vendor/github.com/codegangsta/cli/app.go b/vendor/github.com/codegangsta/cli/app.go deleted file mode 100644 index edf02fbc0..000000000 --- a/vendor/github.com/codegangsta/cli/app.go +++ /dev/null @@ -1,275 +0,0 @@ -package cli - -import ( - "fmt" - "io" - "io/ioutil" - "os" - "text/tabwriter" - "text/template" - "time" -) - -// App is the main structure of a cli application. It is recomended that -// and app be created with the cli.NewApp() function -type App struct { - // The name of the program. Defaults to os.Args[0] - Name string - // Description of the program. - Usage string - // Version of the program - Version string - // List of commands to execute - Commands []Command - // List of flags to parse - Flags []Flag - // Boolean to enable bash completion commands - EnableBashCompletion bool - // Boolean to hide built-in help command - HideHelp bool - // Boolean to hide built-in version flag - HideVersion bool - // An action to execute when the bash-completion flag is set - BashComplete func(context *Context) - // An action to execute before any subcommands are run, but after the context is ready - // If a non-nil error is returned, no subcommands are run - Before func(context *Context) error - // The action to execute when no subcommands are specified - Action func(context *Context) - // Execute this function if the proper command cannot be found - CommandNotFound func(context *Context, command string) - // Compilation date - Compiled time.Time - // Author - Author string - // Author e-mail - Email string - // Writer writer to write output to - Writer io.Writer -} - -// Tries to find out when this binary was compiled. -// Returns the current time if it fails to find it. -func compileTime() time.Time { - info, err := os.Stat(os.Args[0]) - if err != nil { - return time.Now() - } - return info.ModTime() -} - -// Creates a new cli Application with some reasonable defaults for Name, Usage, Version and Action. -func NewApp() *App { - return &App{ - Name: os.Args[0], - Usage: "A new cli application", - Version: "0.0.0", - BashComplete: DefaultAppComplete, - Action: helpCommand.Action, - Compiled: compileTime(), - Author: "Author", - Email: "unknown@email", - Writer: os.Stdout, - } -} - -// Entry point to the cli app. Parses the arguments slice and routes to the proper flag/args combination -func (a *App) Run(arguments []string) error { - if HelpPrinter == nil { - defer func() { - HelpPrinter = nil - }() - - HelpPrinter = func(templ string, data interface{}) { - w := tabwriter.NewWriter(a.Writer, 0, 8, 1, '\t', 0) - t := template.Must(template.New("help").Parse(templ)) - err := t.Execute(w, data) - if err != nil { - panic(err) - } - w.Flush() - } - } - - // append help to commands - if a.Command(helpCommand.Name) == nil && !a.HideHelp { - a.Commands = append(a.Commands, helpCommand) - a.appendFlag(HelpFlag) - } - - //append version/help flags - if a.EnableBashCompletion { - a.appendFlag(BashCompletionFlag) - } - - if !a.HideVersion { - a.appendFlag(VersionFlag) - } - - // parse flags - set := flagSet(a.Name, a.Flags) - set.SetOutput(ioutil.Discard) - err := set.Parse(arguments[1:]) - nerr := normalizeFlags(a.Flags, set) - if nerr != nil { - fmt.Fprintln(a.Writer, nerr) - context := NewContext(a, set, set) - ShowAppHelp(context) - fmt.Fprintln(a.Writer) - return nerr - } - context := NewContext(a, set, set) - - if err != nil { - fmt.Fprintf(a.Writer, "Incorrect Usage.\n\n") - ShowAppHelp(context) - fmt.Fprintln(a.Writer) - return err - } - - if checkCompletions(context) { - return nil - } - - if checkHelp(context) { - return nil - } - - if checkVersion(context) { - return nil - } - - if a.Before != nil { - err := a.Before(context) - if err != nil { - return err - } - } - - args := context.Args() - if args.Present() { - name := args.First() - c := a.Command(name) - if c != nil { - return c.Run(context) - } - } - - // Run default Action - a.Action(context) - return nil -} - -// Another entry point to the cli app, takes care of passing arguments and error handling -func (a *App) RunAndExitOnError() { - if err := a.Run(os.Args); err != nil { - fmt.Fprintln(os.Stderr, err) - os.Exit(1) - } -} - -// Invokes the subcommand given the context, parses ctx.Args() to generate command-specific flags -func (a *App) RunAsSubcommand(ctx *Context) error { - // append help to commands - if len(a.Commands) > 0 { - if a.Command(helpCommand.Name) == nil && !a.HideHelp { - a.Commands = append(a.Commands, helpCommand) - a.appendFlag(HelpFlag) - } - } - - // append flags - if a.EnableBashCompletion { - a.appendFlag(BashCompletionFlag) - } - - // parse flags - set := flagSet(a.Name, a.Flags) - set.SetOutput(ioutil.Discard) - err := set.Parse(ctx.Args().Tail()) - nerr := normalizeFlags(a.Flags, set) - context := NewContext(a, set, ctx.globalSet) - - if nerr != nil { - fmt.Fprintln(a.Writer, nerr) - if len(a.Commands) > 0 { - ShowSubcommandHelp(context) - } else { - ShowCommandHelp(ctx, context.Args().First()) - } - fmt.Fprintln(a.Writer) - return nerr - } - - if err != nil { - fmt.Fprintf(a.Writer, "Incorrect Usage.\n\n") - ShowSubcommandHelp(context) - return err - } - - if checkCompletions(context) { - return nil - } - - if len(a.Commands) > 0 { - if checkSubcommandHelp(context) { - return nil - } - } else { - if checkCommandHelp(ctx, context.Args().First()) { - return nil - } - } - - if a.Before != nil { - err := a.Before(context) - if err != nil { - return err - } - } - - args := context.Args() - if args.Present() { - name := args.First() - c := a.Command(name) - if c != nil { - return c.Run(context) - } - } - - // Run default Action - if len(a.Commands) > 0 { - a.Action(context) - } else { - a.Action(ctx) - } - - return nil -} - -// Returns the named command on App. Returns nil if the command does not exist -func (a *App) Command(name string) *Command { - for _, c := range a.Commands { - if c.HasName(name) { - return &c - } - } - - return nil -} - -func (a *App) hasFlag(flag Flag) bool { - for _, f := range a.Flags { - if flag == f { - return true - } - } - - return false -} - -func (a *App) appendFlag(flag Flag) { - if !a.hasFlag(flag) { - a.Flags = append(a.Flags, flag) - } -} diff --git a/vendor/github.com/codegangsta/cli/app_test.go b/vendor/github.com/codegangsta/cli/app_test.go deleted file mode 100644 index 141319940..000000000 --- a/vendor/github.com/codegangsta/cli/app_test.go +++ /dev/null @@ -1,467 +0,0 @@ -package cli_test - -import ( - "fmt" - "os" - "testing" - - "github.com/codegangsta/cli" -) - -func ExampleApp() { - // set args for examples sake - os.Args = []string{"greet", "--name", "Jeremy"} - - app := cli.NewApp() - app.Name = "greet" - app.Flags = []cli.Flag{ - cli.StringFlag{Name: "name", Value: "bob", Usage: "a name to say"}, - } - app.Action = func(c *cli.Context) { - fmt.Printf("Hello %v\n", c.String("name")) - } - app.Run(os.Args) - // Output: - // Hello Jeremy -} - -func ExampleAppSubcommand() { - // set args for examples sake - os.Args = []string{"say", "hi", "english", "--name", "Jeremy"} - app := cli.NewApp() - app.Name = "say" - app.Commands = []cli.Command{ - { - Name: "hello", - ShortName: "hi", - Usage: "use it to see a description", - Description: "This is how we describe hello the function", - Subcommands: []cli.Command{ - { - Name: "english", - ShortName: "en", - Usage: "sends a greeting in english", - Description: "greets someone in english", - Flags: []cli.Flag{ - cli.StringFlag{ - Name: "name", - Value: "Bob", - Usage: "Name of the person to greet", - }, - }, - Action: func(c *cli.Context) { - fmt.Println("Hello,", c.String("name")) - }, - }, - }, - }, - } - - app.Run(os.Args) - // Output: - // Hello, Jeremy -} - -func ExampleAppHelp() { - // set args for examples sake - os.Args = []string{"greet", "h", "describeit"} - - app := cli.NewApp() - app.Name = "greet" - app.Flags = []cli.Flag{ - cli.StringFlag{Name: "name", Value: "bob", Usage: "a name to say"}, - } - app.Commands = []cli.Command{ - { - Name: "describeit", - ShortName: "d", - Usage: "use it to see a description", - Description: "This is how we describe describeit the function", - Action: func(c *cli.Context) { - fmt.Printf("i like to describe things") - }, - }, - } - app.Run(os.Args) - // Output: - // NAME: - // describeit - use it to see a description - // - // USAGE: - // command describeit [arguments...] - // - // DESCRIPTION: - // This is how we describe describeit the function -} - -func ExampleAppBashComplete() { - // set args for examples sake - os.Args = []string{"greet", "--generate-bash-completion"} - - app := cli.NewApp() - app.Name = "greet" - app.EnableBashCompletion = true - app.Commands = []cli.Command{ - { - Name: "describeit", - ShortName: "d", - Usage: "use it to see a description", - Description: "This is how we describe describeit the function", - Action: func(c *cli.Context) { - fmt.Printf("i like to describe things") - }, - }, { - Name: "next", - Usage: "next example", - Description: "more stuff to see when generating bash completion", - Action: func(c *cli.Context) { - fmt.Printf("the next example") - }, - }, - } - - app.Run(os.Args) - // Output: - // describeit - // d - // next - // help - // h -} - -func TestApp_Run(t *testing.T) { - s := "" - - app := cli.NewApp() - app.Action = func(c *cli.Context) { - s = s + c.Args().First() - } - - err := app.Run([]string{"command", "foo"}) - expect(t, err, nil) - err = app.Run([]string{"command", "bar"}) - expect(t, err, nil) - expect(t, s, "foobar") -} - -var commandAppTests = []struct { - name string - expected bool -}{ - {"foobar", true}, - {"batbaz", true}, - {"b", true}, - {"f", true}, - {"bat", false}, - {"nothing", false}, -} - -func TestApp_Command(t *testing.T) { - app := cli.NewApp() - fooCommand := cli.Command{Name: "foobar", ShortName: "f"} - batCommand := cli.Command{Name: "batbaz", ShortName: "b"} - app.Commands = []cli.Command{ - fooCommand, - batCommand, - } - - for _, test := range commandAppTests { - expect(t, app.Command(test.name) != nil, test.expected) - } -} - -func TestApp_CommandWithArgBeforeFlags(t *testing.T) { - var parsedOption, firstArg string - - app := cli.NewApp() - command := cli.Command{ - Name: "cmd", - Flags: []cli.Flag{ - cli.StringFlag{Name: "option", Value: "", Usage: "some option"}, - }, - Action: func(c *cli.Context) { - parsedOption = c.String("option") - firstArg = c.Args().First() - }, - } - app.Commands = []cli.Command{command} - - app.Run([]string{"", "cmd", "my-arg", "--option", "my-option"}) - - expect(t, parsedOption, "my-option") - expect(t, firstArg, "my-arg") -} - -func TestApp_Float64Flag(t *testing.T) { - var meters float64 - - app := cli.NewApp() - app.Flags = []cli.Flag{ - cli.Float64Flag{Name: "height", Value: 1.5, Usage: "Set the height, in meters"}, - } - app.Action = func(c *cli.Context) { - meters = c.Float64("height") - } - - app.Run([]string{"", "--height", "1.93"}) - expect(t, meters, 1.93) -} - -func TestApp_ParseSliceFlags(t *testing.T) { - var parsedOption, firstArg string - var parsedIntSlice []int - var parsedStringSlice []string - - app := cli.NewApp() - command := cli.Command{ - Name: "cmd", - Flags: []cli.Flag{ - cli.IntSliceFlag{Name: "p", Value: &cli.IntSlice{}, Usage: "set one or more ip addr"}, - cli.StringSliceFlag{Name: "ip", Value: &cli.StringSlice{}, Usage: "set one or more ports to open"}, - }, - Action: func(c *cli.Context) { - parsedIntSlice = c.IntSlice("p") - parsedStringSlice = c.StringSlice("ip") - parsedOption = c.String("option") - firstArg = c.Args().First() - }, - } - app.Commands = []cli.Command{command} - - app.Run([]string{"", "cmd", "my-arg", "-p", "22", "-p", "80", "-ip", "8.8.8.8", "-ip", "8.8.4.4"}) - - IntsEquals := func(a, b []int) bool { - if len(a) != len(b) { - return false - } - for i, v := range a { - if v != b[i] { - return false - } - } - return true - } - - StrsEquals := func(a, b []string) bool { - if len(a) != len(b) { - return false - } - for i, v := range a { - if v != b[i] { - return false - } - } - return true - } - var expectedIntSlice = []int{22, 80} - var expectedStringSlice = []string{"8.8.8.8", "8.8.4.4"} - - if !IntsEquals(parsedIntSlice, expectedIntSlice) { - t.Errorf("%v does not match %v", parsedIntSlice, expectedIntSlice) - } - - if !StrsEquals(parsedStringSlice, expectedStringSlice) { - t.Errorf("%v does not match %v", parsedStringSlice, expectedStringSlice) - } -} - -func TestApp_DefaultStdout(t *testing.T) { - app := cli.NewApp() - - if app.Writer != os.Stdout { - t.Error("Default output writer not set.") - } -} - -type mockWriter struct { - written []byte -} - -func (fw *mockWriter) Write(p []byte) (n int, err error) { - if fw.written == nil { - fw.written = p - } else { - fw.written = append(fw.written, p...) - } - - return len(p), nil -} - -func (fw *mockWriter) GetWritten() (b []byte) { - return fw.written -} - -func TestApp_SetStdout(t *testing.T) { - w := &mockWriter{} - - app := cli.NewApp() - app.Name = "test" - app.Writer = w - - err := app.Run([]string{"help"}) - - if err != nil { - t.Fatalf("Run error: %s", err) - } - - if len(w.written) == 0 { - t.Error("App did not write output to desired writer.") - } -} - -func TestApp_BeforeFunc(t *testing.T) { - beforeRun, subcommandRun := false, false - beforeError := fmt.Errorf("fail") - var err error - - app := cli.NewApp() - - app.Before = func(c *cli.Context) error { - beforeRun = true - s := c.String("opt") - if s == "fail" { - return beforeError - } - - return nil - } - - app.Commands = []cli.Command{ - cli.Command{ - Name: "sub", - Action: func(c *cli.Context) { - subcommandRun = true - }, - }, - } - - app.Flags = []cli.Flag{ - cli.StringFlag{Name: "opt"}, - } - - // run with the Before() func succeeding - err = app.Run([]string{"command", "--opt", "succeed", "sub"}) - - if err != nil { - t.Fatalf("Run error: %s", err) - } - - if beforeRun == false { - t.Errorf("Before() not executed when expected") - } - - if subcommandRun == false { - t.Errorf("Subcommand not executed when expected") - } - - // reset - beforeRun, subcommandRun = false, false - - // run with the Before() func failing - err = app.Run([]string{"command", "--opt", "fail", "sub"}) - - // should be the same error produced by the Before func - if err != beforeError { - t.Errorf("Run error expected, but not received") - } - - if beforeRun == false { - t.Errorf("Before() not executed when expected") - } - - if subcommandRun == true { - t.Errorf("Subcommand executed when NOT expected") - } - -} - -func TestAppHelpPrinter(t *testing.T) { - oldPrinter := cli.HelpPrinter - defer func() { - cli.HelpPrinter = oldPrinter - }() - - var wasCalled = false - cli.HelpPrinter = func(template string, data interface{}) { - wasCalled = true - } - - app := cli.NewApp() - app.Run([]string{"-h"}) - - if wasCalled == false { - t.Errorf("Help printer expected to be called, but was not") - } -} - -func TestAppVersionPrinter(t *testing.T) { - oldPrinter := cli.VersionPrinter - defer func() { - cli.VersionPrinter = oldPrinter - }() - - var wasCalled = false - cli.VersionPrinter = func(c *cli.Context) { - wasCalled = true - } - - app := cli.NewApp() - ctx := cli.NewContext(app, nil, nil) - cli.ShowVersion(ctx) - - if wasCalled == false { - t.Errorf("Version printer expected to be called, but was not") - } -} - -func TestAppCommandNotFound(t *testing.T) { - beforeRun, subcommandRun := false, false - app := cli.NewApp() - - app.CommandNotFound = func(c *cli.Context, command string) { - beforeRun = true - } - - app.Commands = []cli.Command{ - cli.Command{ - Name: "bar", - Action: func(c *cli.Context) { - subcommandRun = true - }, - }, - } - - app.Run([]string{"command", "foo"}) - - expect(t, beforeRun, true) - expect(t, subcommandRun, false) -} - -func TestGlobalFlagsInSubcommands(t *testing.T) { - subcommandRun := false - app := cli.NewApp() - - app.Flags = []cli.Flag{ - cli.BoolFlag{Name: "debug, d", Usage: "Enable debugging"}, - } - - app.Commands = []cli.Command{ - cli.Command{ - Name: "foo", - Subcommands: []cli.Command{ - { - Name: "bar", - Action: func(c *cli.Context) { - if c.GlobalBool("debug") { - subcommandRun = true - } - }, - }, - }, - }, - } - - app.Run([]string{"command", "-d", "foo", "bar"}) - - expect(t, subcommandRun, true) -} diff --git a/vendor/github.com/codegangsta/cli/autocomplete/bash_autocomplete b/vendor/github.com/codegangsta/cli/autocomplete/bash_autocomplete deleted file mode 100644 index 9b55dd990..000000000 --- a/vendor/github.com/codegangsta/cli/autocomplete/bash_autocomplete +++ /dev/null @@ -1,13 +0,0 @@ -#! /bin/bash - -_cli_bash_autocomplete() { - local cur prev opts base - COMPREPLY=() - cur="${COMP_WORDS[COMP_CWORD]}" - prev="${COMP_WORDS[COMP_CWORD-1]}" - opts=$( ${COMP_WORDS[@]:0:$COMP_CWORD} --generate-bash-completion ) - COMPREPLY=( $(compgen -W "${opts}" -- ${cur}) ) - return 0 - } - - complete -F _cli_bash_autocomplete $PROG \ No newline at end of file diff --git a/vendor/github.com/codegangsta/cli/autocomplete/zsh_autocomplete b/vendor/github.com/codegangsta/cli/autocomplete/zsh_autocomplete deleted file mode 100644 index 5430a18f9..000000000 --- a/vendor/github.com/codegangsta/cli/autocomplete/zsh_autocomplete +++ /dev/null @@ -1,5 +0,0 @@ -autoload -U compinit && compinit -autoload -U bashcompinit && bashcompinit - -script_dir=$(dirname $0) -source ${script_dir}/bash_autocomplete diff --git a/vendor/github.com/codegangsta/cli/cli.go b/vendor/github.com/codegangsta/cli/cli.go deleted file mode 100644 index b74254581..000000000 --- a/vendor/github.com/codegangsta/cli/cli.go +++ /dev/null @@ -1,19 +0,0 @@ -// Package cli provides a minimal framework for creating and organizing command line -// Go applications. cli is designed to be easy to understand and write, the most simple -// cli application can be written as follows: -// func main() { -// cli.NewApp().Run(os.Args) -// } -// -// Of course this application does not do much, so let's make this an actual application: -// func main() { -// app := cli.NewApp() -// app.Name = "greet" -// app.Usage = "say a greeting" -// app.Action = func(c *cli.Context) { -// println("Greetings") -// } -// -// app.Run(os.Args) -// } -package cli diff --git a/vendor/github.com/codegangsta/cli/cli_test.go b/vendor/github.com/codegangsta/cli/cli_test.go deleted file mode 100644 index 879a793dc..000000000 --- a/vendor/github.com/codegangsta/cli/cli_test.go +++ /dev/null @@ -1,100 +0,0 @@ -package cli_test - -import ( - "os" - - "github.com/codegangsta/cli" -) - -func Example() { - app := cli.NewApp() - app.Name = "todo" - app.Usage = "task list on the command line" - app.Commands = []cli.Command{ - { - Name: "add", - ShortName: "a", - Usage: "add a task to the list", - Action: func(c *cli.Context) { - println("added task: ", c.Args().First()) - }, - }, - { - Name: "complete", - ShortName: "c", - Usage: "complete a task on the list", - Action: func(c *cli.Context) { - println("completed task: ", c.Args().First()) - }, - }, - } - - app.Run(os.Args) -} - -func ExampleSubcommand() { - app := cli.NewApp() - app.Name = "say" - app.Commands = []cli.Command{ - { - Name: "hello", - ShortName: "hi", - Usage: "use it to see a description", - Description: "This is how we describe hello the function", - Subcommands: []cli.Command{ - { - Name: "english", - ShortName: "en", - Usage: "sends a greeting in english", - Description: "greets someone in english", - Flags: []cli.Flag{ - cli.StringFlag{ - Name: "name", - Value: "Bob", - Usage: "Name of the person to greet", - }, - }, - Action: func(c *cli.Context) { - println("Hello, ", c.String("name")) - }, - }, { - Name: "spanish", - ShortName: "sp", - Usage: "sends a greeting in spanish", - Flags: []cli.Flag{ - cli.StringFlag{ - Name: "surname", - Value: "Jones", - Usage: "Surname of the person to greet", - }, - }, - Action: func(c *cli.Context) { - println("Hola, ", c.String("surname")) - }, - }, { - Name: "french", - ShortName: "fr", - Usage: "sends a greeting in french", - Flags: []cli.Flag{ - cli.StringFlag{ - Name: "nickname", - Value: "Stevie", - Usage: "Nickname of the person to greet", - }, - }, - Action: func(c *cli.Context) { - println("Bonjour, ", c.String("nickname")) - }, - }, - }, - }, { - Name: "bye", - Usage: "says goodbye", - Action: func(c *cli.Context) { - println("bye") - }, - }, - } - - app.Run(os.Args) -} diff --git a/vendor/github.com/codegangsta/cli/command.go b/vendor/github.com/codegangsta/cli/command.go deleted file mode 100644 index 1536b15e2..000000000 --- a/vendor/github.com/codegangsta/cli/command.go +++ /dev/null @@ -1,144 +0,0 @@ -package cli - -import ( - "fmt" - "io/ioutil" - "strings" -) - -// Command is a subcommand for a cli.App. -type Command struct { - // The name of the command - Name string - // short name of the command. Typically one character - ShortName string - // A short description of the usage of this command - Usage string - // A longer explanation of how the command works - Description string - // The function to call when checking for bash command completions - BashComplete func(context *Context) - // An action to execute before any sub-subcommands are run, but after the context is ready - // If a non-nil error is returned, no sub-subcommands are run - Before func(context *Context) error - // The function to call when this command is invoked - Action func(context *Context) - // List of child commands - Subcommands []Command - // List of flags to parse - Flags []Flag - // Treat all flags as normal arguments if true - SkipFlagParsing bool - // Boolean to hide built-in help command - HideHelp bool -} - -// Invokes the command given the context, parses ctx.Args() to generate command-specific flags -func (c Command) Run(ctx *Context) error { - - if len(c.Subcommands) > 0 || c.Before != nil { - return c.startApp(ctx) - } - - if !c.HideHelp { - // append help to flags - c.Flags = append( - c.Flags, - HelpFlag, - ) - } - - if ctx.App.EnableBashCompletion { - c.Flags = append(c.Flags, BashCompletionFlag) - } - - set := flagSet(c.Name, c.Flags) - set.SetOutput(ioutil.Discard) - - firstFlagIndex := -1 - for index, arg := range ctx.Args() { - if strings.HasPrefix(arg, "-") { - firstFlagIndex = index - break - } - } - - var err error - if firstFlagIndex > -1 && !c.SkipFlagParsing { - args := ctx.Args() - regularArgs := args[1:firstFlagIndex] - flagArgs := args[firstFlagIndex:] - err = set.Parse(append(flagArgs, regularArgs...)) - } else { - err = set.Parse(ctx.Args().Tail()) - } - - if err != nil { - fmt.Fprint(ctx.App.Writer, "Incorrect Usage.\n\n") - ShowCommandHelp(ctx, c.Name) - fmt.Fprintln(ctx.App.Writer) - return err - } - - nerr := normalizeFlags(c.Flags, set) - if nerr != nil { - fmt.Fprintln(ctx.App.Writer, nerr) - fmt.Fprintln(ctx.App.Writer) - ShowCommandHelp(ctx, c.Name) - fmt.Fprintln(ctx.App.Writer) - return nerr - } - context := NewContext(ctx.App, set, ctx.globalSet) - - if checkCommandCompletions(context, c.Name) { - return nil - } - - if checkCommandHelp(context, c.Name) { - return nil - } - context.Command = c - c.Action(context) - return nil -} - -// Returns true if Command.Name or Command.ShortName matches given name -func (c Command) HasName(name string) bool { - return c.Name == name || c.ShortName == name -} - -func (c Command) startApp(ctx *Context) error { - app := NewApp() - - // set the name and usage - app.Name = fmt.Sprintf("%s %s", ctx.App.Name, c.Name) - if c.Description != "" { - app.Usage = c.Description - } else { - app.Usage = c.Usage - } - - // set CommandNotFound - app.CommandNotFound = ctx.App.CommandNotFound - - // set the flags and commands - app.Commands = c.Subcommands - app.Flags = c.Flags - app.HideHelp = c.HideHelp - - // bash completion - app.EnableBashCompletion = ctx.App.EnableBashCompletion - if c.BashComplete != nil { - app.BashComplete = c.BashComplete - } - - // set the actions - app.Before = c.Before - if c.Action != nil { - app.Action = c.Action - } else { - app.Action = helpSubcommand.Action - } - - return app.RunAsSubcommand(ctx) -} diff --git a/vendor/github.com/codegangsta/cli/command_test.go b/vendor/github.com/codegangsta/cli/command_test.go deleted file mode 100644 index c0f556ad2..000000000 --- a/vendor/github.com/codegangsta/cli/command_test.go +++ /dev/null @@ -1,49 +0,0 @@ -package cli_test - -import ( - "flag" - "testing" - - "github.com/codegangsta/cli" -) - -func TestCommandDoNotIgnoreFlags(t *testing.T) { - app := cli.NewApp() - set := flag.NewFlagSet("test", 0) - test := []string{"blah", "blah", "-break"} - set.Parse(test) - - c := cli.NewContext(app, set, set) - - command := cli.Command{ - Name: "test-cmd", - ShortName: "tc", - Usage: "this is for testing", - Description: "testing", - Action: func(_ *cli.Context) {}, - } - err := command.Run(c) - - expect(t, err.Error(), "flag provided but not defined: -break") -} - -func TestCommandIgnoreFlags(t *testing.T) { - app := cli.NewApp() - set := flag.NewFlagSet("test", 0) - test := []string{"blah", "blah"} - set.Parse(test) - - c := cli.NewContext(app, set, set) - - command := cli.Command{ - Name: "test-cmd", - ShortName: "tc", - Usage: "this is for testing", - Description: "testing", - Action: func(_ *cli.Context) {}, - SkipFlagParsing: true, - } - err := command.Run(c) - - expect(t, err, nil) -} diff --git a/vendor/github.com/codegangsta/cli/context.go b/vendor/github.com/codegangsta/cli/context.go deleted file mode 100644 index c9f645b18..000000000 --- a/vendor/github.com/codegangsta/cli/context.go +++ /dev/null @@ -1,339 +0,0 @@ -package cli - -import ( - "errors" - "flag" - "strconv" - "strings" - "time" -) - -// Context is a type that is passed through to -// each Handler action in a cli application. Context -// can be used to retrieve context-specific Args and -// parsed command-line options. -type Context struct { - App *App - Command Command - flagSet *flag.FlagSet - globalSet *flag.FlagSet - setFlags map[string]bool - globalSetFlags map[string]bool -} - -// Creates a new context. For use in when invoking an App or Command action. -func NewContext(app *App, set *flag.FlagSet, globalSet *flag.FlagSet) *Context { - return &Context{App: app, flagSet: set, globalSet: globalSet} -} - -// Looks up the value of a local int flag, returns 0 if no int flag exists -func (c *Context) Int(name string) int { - return lookupInt(name, c.flagSet) -} - -// Looks up the value of a local time.Duration flag, returns 0 if no time.Duration flag exists -func (c *Context) Duration(name string) time.Duration { - return lookupDuration(name, c.flagSet) -} - -// Looks up the value of a local float64 flag, returns 0 if no float64 flag exists -func (c *Context) Float64(name string) float64 { - return lookupFloat64(name, c.flagSet) -} - -// Looks up the value of a local bool flag, returns false if no bool flag exists -func (c *Context) Bool(name string) bool { - return lookupBool(name, c.flagSet) -} - -// Looks up the value of a local boolT flag, returns false if no bool flag exists -func (c *Context) BoolT(name string) bool { - return lookupBoolT(name, c.flagSet) -} - -// Looks up the value of a local string flag, returns "" if no string flag exists -func (c *Context) String(name string) string { - return lookupString(name, c.flagSet) -} - -// Looks up the value of a local string slice flag, returns nil if no string slice flag exists -func (c *Context) StringSlice(name string) []string { - return lookupStringSlice(name, c.flagSet) -} - -// Looks up the value of a local int slice flag, returns nil if no int slice flag exists -func (c *Context) IntSlice(name string) []int { - return lookupIntSlice(name, c.flagSet) -} - -// Looks up the value of a local generic flag, returns nil if no generic flag exists -func (c *Context) Generic(name string) interface{} { - return lookupGeneric(name, c.flagSet) -} - -// Looks up the value of a global int flag, returns 0 if no int flag exists -func (c *Context) GlobalInt(name string) int { - return lookupInt(name, c.globalSet) -} - -// Looks up the value of a global time.Duration flag, returns 0 if no time.Duration flag exists -func (c *Context) GlobalDuration(name string) time.Duration { - return lookupDuration(name, c.globalSet) -} - -// Looks up the value of a global bool flag, returns false if no bool flag exists -func (c *Context) GlobalBool(name string) bool { - return lookupBool(name, c.globalSet) -} - -// Looks up the value of a global string flag, returns "" if no string flag exists -func (c *Context) GlobalString(name string) string { - return lookupString(name, c.globalSet) -} - -// Looks up the value of a global string slice flag, returns nil if no string slice flag exists -func (c *Context) GlobalStringSlice(name string) []string { - return lookupStringSlice(name, c.globalSet) -} - -// Looks up the value of a global int slice flag, returns nil if no int slice flag exists -func (c *Context) GlobalIntSlice(name string) []int { - return lookupIntSlice(name, c.globalSet) -} - -// Looks up the value of a global generic flag, returns nil if no generic flag exists -func (c *Context) GlobalGeneric(name string) interface{} { - return lookupGeneric(name, c.globalSet) -} - -// Determines if the flag was actually set -func (c *Context) IsSet(name string) bool { - if c.setFlags == nil { - c.setFlags = make(map[string]bool) - c.flagSet.Visit(func(f *flag.Flag) { - c.setFlags[f.Name] = true - }) - } - return c.setFlags[name] == true -} - -// Determines if the global flag was actually set -func (c *Context) GlobalIsSet(name string) bool { - if c.globalSetFlags == nil { - c.globalSetFlags = make(map[string]bool) - c.globalSet.Visit(func(f *flag.Flag) { - c.globalSetFlags[f.Name] = true - }) - } - return c.globalSetFlags[name] == true -} - -// Returns a slice of flag names used in this context. -func (c *Context) FlagNames() (names []string) { - for _, flag := range c.Command.Flags { - name := strings.Split(flag.getName(), ",")[0] - if name == "help" { - continue - } - names = append(names, name) - } - return -} - -// Returns a slice of global flag names used by the app. -func (c *Context) GlobalFlagNames() (names []string) { - for _, flag := range c.App.Flags { - name := strings.Split(flag.getName(), ",")[0] - if name == "help" || name == "version" { - continue - } - names = append(names, name) - } - return -} - -type Args []string - -// Returns the command line arguments associated with the context. -func (c *Context) Args() Args { - args := Args(c.flagSet.Args()) - return args -} - -// Returns the nth argument, or else a blank string -func (a Args) Get(n int) string { - if len(a) > n { - return a[n] - } - return "" -} - -// Returns the first argument, or else a blank string -func (a Args) First() string { - return a.Get(0) -} - -// Return the rest of the arguments (not the first one) -// or else an empty string slice -func (a Args) Tail() []string { - if len(a) >= 2 { - return []string(a)[1:] - } - return []string{} -} - -// Checks if there are any arguments present -func (a Args) Present() bool { - return len(a) != 0 -} - -// Swaps arguments at the given indexes -func (a Args) Swap(from, to int) error { - if from >= len(a) || to >= len(a) { - return errors.New("index out of range") - } - a[from], a[to] = a[to], a[from] - return nil -} - -func lookupInt(name string, set *flag.FlagSet) int { - f := set.Lookup(name) - if f != nil { - val, err := strconv.Atoi(f.Value.String()) - if err != nil { - return 0 - } - return val - } - - return 0 -} - -func lookupDuration(name string, set *flag.FlagSet) time.Duration { - f := set.Lookup(name) - if f != nil { - val, err := time.ParseDuration(f.Value.String()) - if err == nil { - return val - } - } - - return 0 -} - -func lookupFloat64(name string, set *flag.FlagSet) float64 { - f := set.Lookup(name) - if f != nil { - val, err := strconv.ParseFloat(f.Value.String(), 64) - if err != nil { - return 0 - } - return val - } - - return 0 -} - -func lookupString(name string, set *flag.FlagSet) string { - f := set.Lookup(name) - if f != nil { - return f.Value.String() - } - - return "" -} - -func lookupStringSlice(name string, set *flag.FlagSet) []string { - f := set.Lookup(name) - if f != nil { - return (f.Value.(*StringSlice)).Value() - - } - - return nil -} - -func lookupIntSlice(name string, set *flag.FlagSet) []int { - f := set.Lookup(name) - if f != nil { - return (f.Value.(*IntSlice)).Value() - - } - - return nil -} - -func lookupGeneric(name string, set *flag.FlagSet) interface{} { - f := set.Lookup(name) - if f != nil { - return f.Value - } - return nil -} - -func lookupBool(name string, set *flag.FlagSet) bool { - f := set.Lookup(name) - if f != nil { - val, err := strconv.ParseBool(f.Value.String()) - if err != nil { - return false - } - return val - } - - return false -} - -func lookupBoolT(name string, set *flag.FlagSet) bool { - f := set.Lookup(name) - if f != nil { - val, err := strconv.ParseBool(f.Value.String()) - if err != nil { - return true - } - return val - } - - return false -} - -func copyFlag(name string, ff *flag.Flag, set *flag.FlagSet) { - switch ff.Value.(type) { - case *StringSlice: - default: - set.Set(name, ff.Value.String()) - } -} - -func normalizeFlags(flags []Flag, set *flag.FlagSet) error { - visited := make(map[string]bool) - set.Visit(func(f *flag.Flag) { - visited[f.Name] = true - }) - for _, f := range flags { - parts := strings.Split(f.getName(), ",") - if len(parts) == 1 { - continue - } - var ff *flag.Flag - for _, name := range parts { - name = strings.Trim(name, " ") - if visited[name] { - if ff != nil { - return errors.New("Cannot use two forms of the same flag: " + name + " " + ff.Name) - } - ff = set.Lookup(name) - } - } - if ff == nil { - continue - } - for _, name := range parts { - name = strings.Trim(name, " ") - if !visited[name] { - copyFlag(name, ff, set) - } - } - } - return nil -} diff --git a/vendor/github.com/codegangsta/cli/context_test.go b/vendor/github.com/codegangsta/cli/context_test.go deleted file mode 100644 index 7c9a4436f..000000000 --- a/vendor/github.com/codegangsta/cli/context_test.go +++ /dev/null @@ -1,99 +0,0 @@ -package cli_test - -import ( - "flag" - "testing" - "time" - - "github.com/codegangsta/cli" -) - -func TestNewContext(t *testing.T) { - set := flag.NewFlagSet("test", 0) - set.Int("myflag", 12, "doc") - globalSet := flag.NewFlagSet("test", 0) - globalSet.Int("myflag", 42, "doc") - command := cli.Command{Name: "mycommand"} - c := cli.NewContext(nil, set, globalSet) - c.Command = command - expect(t, c.Int("myflag"), 12) - expect(t, c.GlobalInt("myflag"), 42) - expect(t, c.Command.Name, "mycommand") -} - -func TestContext_Int(t *testing.T) { - set := flag.NewFlagSet("test", 0) - set.Int("myflag", 12, "doc") - c := cli.NewContext(nil, set, set) - expect(t, c.Int("myflag"), 12) -} - -func TestContext_Duration(t *testing.T) { - set := flag.NewFlagSet("test", 0) - set.Duration("myflag", time.Duration(12*time.Second), "doc") - c := cli.NewContext(nil, set, set) - expect(t, c.Duration("myflag"), time.Duration(12*time.Second)) -} - -func TestContext_String(t *testing.T) { - set := flag.NewFlagSet("test", 0) - set.String("myflag", "hello world", "doc") - c := cli.NewContext(nil, set, set) - expect(t, c.String("myflag"), "hello world") -} - -func TestContext_Bool(t *testing.T) { - set := flag.NewFlagSet("test", 0) - set.Bool("myflag", false, "doc") - c := cli.NewContext(nil, set, set) - expect(t, c.Bool("myflag"), false) -} - -func TestContext_BoolT(t *testing.T) { - set := flag.NewFlagSet("test", 0) - set.Bool("myflag", true, "doc") - c := cli.NewContext(nil, set, set) - expect(t, c.BoolT("myflag"), true) -} - -func TestContext_Args(t *testing.T) { - set := flag.NewFlagSet("test", 0) - set.Bool("myflag", false, "doc") - c := cli.NewContext(nil, set, set) - set.Parse([]string{"--myflag", "bat", "baz"}) - expect(t, len(c.Args()), 2) - expect(t, c.Bool("myflag"), true) -} - -func TestContext_IsSet(t *testing.T) { - set := flag.NewFlagSet("test", 0) - set.Bool("myflag", false, "doc") - set.String("otherflag", "hello world", "doc") - globalSet := flag.NewFlagSet("test", 0) - globalSet.Bool("myflagGlobal", true, "doc") - c := cli.NewContext(nil, set, globalSet) - set.Parse([]string{"--myflag", "bat", "baz"}) - globalSet.Parse([]string{"--myflagGlobal", "bat", "baz"}) - expect(t, c.IsSet("myflag"), true) - expect(t, c.IsSet("otherflag"), false) - expect(t, c.IsSet("bogusflag"), false) - expect(t, c.IsSet("myflagGlobal"), false) -} - -func TestContext_GlobalIsSet(t *testing.T) { - set := flag.NewFlagSet("test", 0) - set.Bool("myflag", false, "doc") - set.String("otherflag", "hello world", "doc") - globalSet := flag.NewFlagSet("test", 0) - globalSet.Bool("myflagGlobal", true, "doc") - globalSet.Bool("myflagGlobalUnset", true, "doc") - c := cli.NewContext(nil, set, globalSet) - set.Parse([]string{"--myflag", "bat", "baz"}) - globalSet.Parse([]string{"--myflagGlobal", "bat", "baz"}) - expect(t, c.GlobalIsSet("myflag"), false) - expect(t, c.GlobalIsSet("otherflag"), false) - expect(t, c.GlobalIsSet("bogusflag"), false) - expect(t, c.GlobalIsSet("myflagGlobal"), true) - expect(t, c.GlobalIsSet("myflagGlobalUnset"), false) - expect(t, c.GlobalIsSet("bogusGlobal"), false) -} diff --git a/vendor/github.com/codegangsta/cli/flag.go b/vendor/github.com/codegangsta/cli/flag.go deleted file mode 100644 index ddd6ef8a7..000000000 --- a/vendor/github.com/codegangsta/cli/flag.go +++ /dev/null @@ -1,447 +0,0 @@ -package cli - -import ( - "flag" - "fmt" - "os" - "strconv" - "strings" - "time" -) - -// This flag enables bash-completion for all commands and subcommands -var BashCompletionFlag = BoolFlag{ - Name: "generate-bash-completion", -} - -// This flag prints the version for the application -var VersionFlag = BoolFlag{ - Name: "version, v", - Usage: "print the version", -} - -// This flag prints the help for all commands and subcommands -var HelpFlag = BoolFlag{ - Name: "help, h", - Usage: "show help", -} - -// Flag is a common interface related to parsing flags in cli. -// For more advanced flag parsing techniques, it is recomended that -// this interface be implemented. -type Flag interface { - fmt.Stringer - // Apply Flag settings to the given flag set - Apply(*flag.FlagSet) - getName() string -} - -func flagSet(name string, flags []Flag) *flag.FlagSet { - set := flag.NewFlagSet(name, flag.ContinueOnError) - - for _, f := range flags { - f.Apply(set) - } - return set -} - -func eachName(longName string, fn func(string)) { - parts := strings.Split(longName, ",") - for _, name := range parts { - name = strings.Trim(name, " ") - fn(name) - } -} - -// Generic is a generic parseable type identified by a specific flag -type Generic interface { - Set(value string) error - String() string -} - -// GenericFlag is the flag type for types implementing Generic -type GenericFlag struct { - Name string - Value Generic - Usage string - EnvVar string -} - -func (f GenericFlag) String() string { - return withEnvHint(f.EnvVar, fmt.Sprintf("%s%s %v\t`%v` %s", prefixFor(f.Name), f.Name, f.Value, "-"+f.Name+" option -"+f.Name+" option", f.Usage)) -} - -func (f GenericFlag) Apply(set *flag.FlagSet) { - val := f.Value - if f.EnvVar != "" { - for _, envVar := range strings.Split(f.EnvVar, ",") { - envVar = strings.TrimSpace(envVar) - if envVal := os.Getenv(envVar); envVal != "" { - val.Set(envVal) - break - } - } - } - - eachName(f.Name, func(name string) { - set.Var(f.Value, name, f.Usage) - }) -} - -func (f GenericFlag) getName() string { - return f.Name -} - -type StringSlice []string - -func (f *StringSlice) Set(value string) error { - *f = append(*f, value) - return nil -} - -func (f *StringSlice) String() string { - return fmt.Sprintf("%s", *f) -} - -func (f *StringSlice) Value() []string { - return *f -} - -type StringSliceFlag struct { - Name string - Value *StringSlice - Usage string - EnvVar string -} - -func (f StringSliceFlag) String() string { - firstName := strings.Trim(strings.Split(f.Name, ",")[0], " ") - pref := prefixFor(firstName) - return withEnvHint(f.EnvVar, fmt.Sprintf("%s '%v'\t%v", prefixedNames(f.Name), pref+firstName+" option "+pref+firstName+" option", f.Usage)) -} - -func (f StringSliceFlag) Apply(set *flag.FlagSet) { - if f.EnvVar != "" { - for _, envVar := range strings.Split(f.EnvVar, ",") { - envVar = strings.TrimSpace(envVar) - if envVal := os.Getenv(envVar); envVal != "" { - newVal := &StringSlice{} - for _, s := range strings.Split(envVal, ",") { - s = strings.TrimSpace(s) - newVal.Set(s) - } - f.Value = newVal - break - } - } - } - - eachName(f.Name, func(name string) { - set.Var(f.Value, name, f.Usage) - }) -} - -func (f StringSliceFlag) getName() string { - return f.Name -} - -type IntSlice []int - -func (f *IntSlice) Set(value string) error { - - tmp, err := strconv.Atoi(value) - if err != nil { - return err - } else { - *f = append(*f, tmp) - } - return nil -} - -func (f *IntSlice) String() string { - return fmt.Sprintf("%d", *f) -} - -func (f *IntSlice) Value() []int { - return *f -} - -type IntSliceFlag struct { - Name string - Value *IntSlice - Usage string - EnvVar string -} - -func (f IntSliceFlag) String() string { - firstName := strings.Trim(strings.Split(f.Name, ",")[0], " ") - pref := prefixFor(firstName) - return withEnvHint(f.EnvVar, fmt.Sprintf("%s '%v'\t%v", prefixedNames(f.Name), pref+firstName+" option "+pref+firstName+" option", f.Usage)) -} - -func (f IntSliceFlag) Apply(set *flag.FlagSet) { - if f.EnvVar != "" { - for _, envVar := range strings.Split(f.EnvVar, ",") { - envVar = strings.TrimSpace(envVar) - if envVal := os.Getenv(envVar); envVal != "" { - newVal := &IntSlice{} - for _, s := range strings.Split(envVal, ",") { - s = strings.TrimSpace(s) - err := newVal.Set(s) - if err != nil { - fmt.Fprintf(os.Stderr, err.Error()) - } - } - f.Value = newVal - break - } - } - } - - eachName(f.Name, func(name string) { - set.Var(f.Value, name, f.Usage) - }) -} - -func (f IntSliceFlag) getName() string { - return f.Name -} - -type BoolFlag struct { - Name string - Usage string - EnvVar string -} - -func (f BoolFlag) String() string { - return withEnvHint(f.EnvVar, fmt.Sprintf("%s\t%v", prefixedNames(f.Name), f.Usage)) -} - -func (f BoolFlag) Apply(set *flag.FlagSet) { - val := false - if f.EnvVar != "" { - for _, envVar := range strings.Split(f.EnvVar, ",") { - envVar = strings.TrimSpace(envVar) - if envVal := os.Getenv(envVar); envVal != "" { - envValBool, err := strconv.ParseBool(envVal) - if err == nil { - val = envValBool - } - break - } - } - } - - eachName(f.Name, func(name string) { - set.Bool(name, val, f.Usage) - }) -} - -func (f BoolFlag) getName() string { - return f.Name -} - -type BoolTFlag struct { - Name string - Usage string - EnvVar string -} - -func (f BoolTFlag) String() string { - return withEnvHint(f.EnvVar, fmt.Sprintf("%s\t%v", prefixedNames(f.Name), f.Usage)) -} - -func (f BoolTFlag) Apply(set *flag.FlagSet) { - val := true - if f.EnvVar != "" { - for _, envVar := range strings.Split(f.EnvVar, ",") { - envVar = strings.TrimSpace(envVar) - if envVal := os.Getenv(envVar); envVal != "" { - envValBool, err := strconv.ParseBool(envVal) - if err == nil { - val = envValBool - break - } - } - } - } - - eachName(f.Name, func(name string) { - set.Bool(name, val, f.Usage) - }) -} - -func (f BoolTFlag) getName() string { - return f.Name -} - -type StringFlag struct { - Name string - Value string - Usage string - EnvVar string -} - -func (f StringFlag) String() string { - var fmtString string - fmtString = "%s %v\t%v" - - if len(f.Value) > 0 { - fmtString = "%s '%v'\t%v" - } else { - fmtString = "%s %v\t%v" - } - - return withEnvHint(f.EnvVar, fmt.Sprintf(fmtString, prefixedNames(f.Name), f.Value, f.Usage)) -} - -func (f StringFlag) Apply(set *flag.FlagSet) { - if f.EnvVar != "" { - for _, envVar := range strings.Split(f.EnvVar, ",") { - envVar = strings.TrimSpace(envVar) - if envVal := os.Getenv(envVar); envVal != "" { - f.Value = envVal - break - } - } - } - - eachName(f.Name, func(name string) { - set.String(name, f.Value, f.Usage) - }) -} - -func (f StringFlag) getName() string { - return f.Name -} - -type IntFlag struct { - Name string - Value int - Usage string - EnvVar string -} - -func (f IntFlag) String() string { - return withEnvHint(f.EnvVar, fmt.Sprintf("%s '%v'\t%v", prefixedNames(f.Name), f.Value, f.Usage)) -} - -func (f IntFlag) Apply(set *flag.FlagSet) { - if f.EnvVar != "" { - for _, envVar := range strings.Split(f.EnvVar, ",") { - envVar = strings.TrimSpace(envVar) - if envVal := os.Getenv(envVar); envVal != "" { - envValInt, err := strconv.ParseUint(envVal, 10, 64) - if err == nil { - f.Value = int(envValInt) - break - } - } - } - } - - eachName(f.Name, func(name string) { - set.Int(name, f.Value, f.Usage) - }) -} - -func (f IntFlag) getName() string { - return f.Name -} - -type DurationFlag struct { - Name string - Value time.Duration - Usage string - EnvVar string -} - -func (f DurationFlag) String() string { - return withEnvHint(f.EnvVar, fmt.Sprintf("%s '%v'\t%v", prefixedNames(f.Name), f.Value, f.Usage)) -} - -func (f DurationFlag) Apply(set *flag.FlagSet) { - if f.EnvVar != "" { - for _, envVar := range strings.Split(f.EnvVar, ",") { - envVar = strings.TrimSpace(envVar) - if envVal := os.Getenv(envVar); envVal != "" { - envValDuration, err := time.ParseDuration(envVal) - if err == nil { - f.Value = envValDuration - break - } - } - } - } - - eachName(f.Name, func(name string) { - set.Duration(name, f.Value, f.Usage) - }) -} - -func (f DurationFlag) getName() string { - return f.Name -} - -type Float64Flag struct { - Name string - Value float64 - Usage string - EnvVar string -} - -func (f Float64Flag) String() string { - return withEnvHint(f.EnvVar, fmt.Sprintf("%s '%v'\t%v", prefixedNames(f.Name), f.Value, f.Usage)) -} - -func (f Float64Flag) Apply(set *flag.FlagSet) { - if f.EnvVar != "" { - for _, envVar := range strings.Split(f.EnvVar, ",") { - envVar = strings.TrimSpace(envVar) - if envVal := os.Getenv(envVar); envVal != "" { - envValFloat, err := strconv.ParseFloat(envVal, 10) - if err == nil { - f.Value = float64(envValFloat) - } - } - } - } - - eachName(f.Name, func(name string) { - set.Float64(name, f.Value, f.Usage) - }) -} - -func (f Float64Flag) getName() string { - return f.Name -} - -func prefixFor(name string) (prefix string) { - if len(name) == 1 { - prefix = "-" - } else { - prefix = "--" - } - - return -} - -func prefixedNames(fullName string) (prefixed string) { - parts := strings.Split(fullName, ",") - for i, name := range parts { - name = strings.Trim(name, " ") - prefixed += prefixFor(name) + name - if i < len(parts)-1 { - prefixed += ", " - } - } - return -} - -func withEnvHint(envVar, str string) string { - envText := "" - if envVar != "" { - envText = fmt.Sprintf(" [$%s]", strings.Join(strings.Split(envVar, ","), ", $")) - } - return str + envText -} diff --git a/vendor/github.com/codegangsta/cli/flag_test.go b/vendor/github.com/codegangsta/cli/flag_test.go deleted file mode 100644 index 4f0ba555b..000000000 --- a/vendor/github.com/codegangsta/cli/flag_test.go +++ /dev/null @@ -1,743 +0,0 @@ -package cli_test - -import ( - "fmt" - "os" - "reflect" - "strings" - "testing" - - "github.com/codegangsta/cli" -) - -var boolFlagTests = []struct { - name string - expected string -}{ - {"help", "--help\t"}, - {"h", "-h\t"}, -} - -func TestBoolFlagHelpOutput(t *testing.T) { - - for _, test := range boolFlagTests { - flag := cli.BoolFlag{Name: test.name} - output := flag.String() - - if output != test.expected { - t.Errorf("%s does not match %s", output, test.expected) - } - } -} - -var stringFlagTests = []struct { - name string - value string - expected string -}{ - {"help", "", "--help \t"}, - {"h", "", "-h \t"}, - {"h", "", "-h \t"}, - {"test", "Something", "--test 'Something'\t"}, -} - -func TestStringFlagHelpOutput(t *testing.T) { - - for _, test := range stringFlagTests { - flag := cli.StringFlag{Name: test.name, Value: test.value} - output := flag.String() - - if output != test.expected { - t.Errorf("%s does not match %s", output, test.expected) - } - } -} - -func TestStringFlagWithEnvVarHelpOutput(t *testing.T) { - os.Clearenv() - os.Setenv("APP_FOO", "derp") - for _, test := range stringFlagTests { - flag := cli.StringFlag{Name: test.name, Value: test.value, EnvVar: "APP_FOO"} - output := flag.String() - - if !strings.HasSuffix(output, " [$APP_FOO]") { - t.Errorf("%s does not end with [$APP_FOO]", output) - } - } -} - -var stringSliceFlagTests = []struct { - name string - value *cli.StringSlice - expected string -}{ - {"help", func() *cli.StringSlice { - s := &cli.StringSlice{} - s.Set("") - return s - }(), "--help '--help option --help option'\t"}, - {"h", func() *cli.StringSlice { - s := &cli.StringSlice{} - s.Set("") - return s - }(), "-h '-h option -h option'\t"}, - {"h", func() *cli.StringSlice { - s := &cli.StringSlice{} - s.Set("") - return s - }(), "-h '-h option -h option'\t"}, - {"test", func() *cli.StringSlice { - s := &cli.StringSlice{} - s.Set("Something") - return s - }(), "--test '--test option --test option'\t"}, -} - -func TestStringSliceFlagHelpOutput(t *testing.T) { - - for _, test := range stringSliceFlagTests { - flag := cli.StringSliceFlag{Name: test.name, Value: test.value} - output := flag.String() - - if output != test.expected { - t.Errorf("%q does not match %q", output, test.expected) - } - } -} - -func TestStringSliceFlagWithEnvVarHelpOutput(t *testing.T) { - os.Clearenv() - os.Setenv("APP_QWWX", "11,4") - for _, test := range stringSliceFlagTests { - flag := cli.StringSliceFlag{Name: test.name, Value: test.value, EnvVar: "APP_QWWX"} - output := flag.String() - - if !strings.HasSuffix(output, " [$APP_QWWX]") { - t.Errorf("%q does not end with [$APP_QWWX]", output) - } - } -} - -var intFlagTests = []struct { - name string - expected string -}{ - {"help", "--help '0'\t"}, - {"h", "-h '0'\t"}, -} - -func TestIntFlagHelpOutput(t *testing.T) { - - for _, test := range intFlagTests { - flag := cli.IntFlag{Name: test.name} - output := flag.String() - - if output != test.expected { - t.Errorf("%s does not match %s", output, test.expected) - } - } -} - -func TestIntFlagWithEnvVarHelpOutput(t *testing.T) { - os.Clearenv() - os.Setenv("APP_BAR", "2") - for _, test := range intFlagTests { - flag := cli.IntFlag{Name: test.name, EnvVar: "APP_BAR"} - output := flag.String() - - if !strings.HasSuffix(output, " [$APP_BAR]") { - t.Errorf("%s does not end with [$APP_BAR]", output) - } - } -} - -var durationFlagTests = []struct { - name string - expected string -}{ - {"help", "--help '0'\t"}, - {"h", "-h '0'\t"}, -} - -func TestDurationFlagHelpOutput(t *testing.T) { - - for _, test := range durationFlagTests { - flag := cli.DurationFlag{Name: test.name} - output := flag.String() - - if output != test.expected { - t.Errorf("%s does not match %s", output, test.expected) - } - } -} - -func TestDurationFlagWithEnvVarHelpOutput(t *testing.T) { - os.Clearenv() - os.Setenv("APP_BAR", "2h3m6s") - for _, test := range durationFlagTests { - flag := cli.DurationFlag{Name: test.name, EnvVar: "APP_BAR"} - output := flag.String() - - if !strings.HasSuffix(output, " [$APP_BAR]") { - t.Errorf("%s does not end with [$APP_BAR]", output) - } - } -} - -var intSliceFlagTests = []struct { - name string - value *cli.IntSlice - expected string -}{ - {"help", &cli.IntSlice{}, "--help '--help option --help option'\t"}, - {"h", &cli.IntSlice{}, "-h '-h option -h option'\t"}, - {"h", &cli.IntSlice{}, "-h '-h option -h option'\t"}, - {"test", func() *cli.IntSlice { - i := &cli.IntSlice{} - i.Set("9") - return i - }(), "--test '--test option --test option'\t"}, -} - -func TestIntSliceFlagHelpOutput(t *testing.T) { - - for _, test := range intSliceFlagTests { - flag := cli.IntSliceFlag{Name: test.name, Value: test.value} - output := flag.String() - - if output != test.expected { - t.Errorf("%q does not match %q", output, test.expected) - } - } -} - -func TestIntSliceFlagWithEnvVarHelpOutput(t *testing.T) { - os.Clearenv() - os.Setenv("APP_SMURF", "42,3") - for _, test := range intSliceFlagTests { - flag := cli.IntSliceFlag{Name: test.name, Value: test.value, EnvVar: "APP_SMURF"} - output := flag.String() - - if !strings.HasSuffix(output, " [$APP_SMURF]") { - t.Errorf("%q does not end with [$APP_SMURF]", output) - } - } -} - -var float64FlagTests = []struct { - name string - expected string -}{ - {"help", "--help '0'\t"}, - {"h", "-h '0'\t"}, -} - -func TestFloat64FlagHelpOutput(t *testing.T) { - - for _, test := range float64FlagTests { - flag := cli.Float64Flag{Name: test.name} - output := flag.String() - - if output != test.expected { - t.Errorf("%s does not match %s", output, test.expected) - } - } -} - -func TestFloat64FlagWithEnvVarHelpOutput(t *testing.T) { - os.Clearenv() - os.Setenv("APP_BAZ", "99.4") - for _, test := range float64FlagTests { - flag := cli.Float64Flag{Name: test.name, EnvVar: "APP_BAZ"} - output := flag.String() - - if !strings.HasSuffix(output, " [$APP_BAZ]") { - t.Errorf("%s does not end with [$APP_BAZ]", output) - } - } -} - -var genericFlagTests = []struct { - name string - value cli.Generic - expected string -}{ - {"help", &Parser{}, "--help \t`-help option -help option` "}, - {"h", &Parser{}, "-h \t`-h option -h option` "}, - {"test", &Parser{}, "--test \t`-test option -test option` "}, -} - -func TestGenericFlagHelpOutput(t *testing.T) { - - for _, test := range genericFlagTests { - flag := cli.GenericFlag{Name: test.name} - output := flag.String() - - if output != test.expected { - t.Errorf("%q does not match %q", output, test.expected) - } - } -} - -func TestGenericFlagWithEnvVarHelpOutput(t *testing.T) { - os.Clearenv() - os.Setenv("APP_ZAP", "3") - for _, test := range genericFlagTests { - flag := cli.GenericFlag{Name: test.name, EnvVar: "APP_ZAP"} - output := flag.String() - - if !strings.HasSuffix(output, " [$APP_ZAP]") { - t.Errorf("%s does not end with [$APP_ZAP]", output) - } - } -} - -func TestParseMultiString(t *testing.T) { - (&cli.App{ - Flags: []cli.Flag{ - cli.StringFlag{Name: "serve, s"}, - }, - Action: func(ctx *cli.Context) { - if ctx.String("serve") != "10" { - t.Errorf("main name not set") - } - if ctx.String("s") != "10" { - t.Errorf("short name not set") - } - }, - }).Run([]string{"run", "-s", "10"}) -} - -func TestParseMultiStringFromEnv(t *testing.T) { - os.Clearenv() - os.Setenv("APP_COUNT", "20") - (&cli.App{ - Flags: []cli.Flag{ - cli.StringFlag{Name: "count, c", EnvVar: "APP_COUNT"}, - }, - Action: func(ctx *cli.Context) { - if ctx.String("count") != "20" { - t.Errorf("main name not set") - } - if ctx.String("c") != "20" { - t.Errorf("short name not set") - } - }, - }).Run([]string{"run"}) -} - -func TestParseMultiStringFromEnvCascade(t *testing.T) { - os.Clearenv() - os.Setenv("APP_COUNT", "20") - (&cli.App{ - Flags: []cli.Flag{ - cli.StringFlag{Name: "count, c", EnvVar: "COMPAT_COUNT,APP_COUNT"}, - }, - Action: func(ctx *cli.Context) { - if ctx.String("count") != "20" { - t.Errorf("main name not set") - } - if ctx.String("c") != "20" { - t.Errorf("short name not set") - } - }, - }).Run([]string{"run"}) -} - -func TestParseMultiStringSlice(t *testing.T) { - (&cli.App{ - Flags: []cli.Flag{ - cli.StringSliceFlag{Name: "serve, s", Value: &cli.StringSlice{}}, - }, - Action: func(ctx *cli.Context) { - if !reflect.DeepEqual(ctx.StringSlice("serve"), []string{"10", "20"}) { - t.Errorf("main name not set") - } - if !reflect.DeepEqual(ctx.StringSlice("s"), []string{"10", "20"}) { - t.Errorf("short name not set") - } - }, - }).Run([]string{"run", "-s", "10", "-s", "20"}) -} - -func TestParseMultiStringSliceFromEnv(t *testing.T) { - os.Clearenv() - os.Setenv("APP_INTERVALS", "20,30,40") - - (&cli.App{ - Flags: []cli.Flag{ - cli.StringSliceFlag{Name: "intervals, i", Value: &cli.StringSlice{}, EnvVar: "APP_INTERVALS"}, - }, - Action: func(ctx *cli.Context) { - if !reflect.DeepEqual(ctx.StringSlice("intervals"), []string{"20", "30", "40"}) { - t.Errorf("main name not set from env") - } - if !reflect.DeepEqual(ctx.StringSlice("i"), []string{"20", "30", "40"}) { - t.Errorf("short name not set from env") - } - }, - }).Run([]string{"run"}) -} - -func TestParseMultiStringSliceFromEnvCascade(t *testing.T) { - os.Clearenv() - os.Setenv("APP_INTERVALS", "20,30,40") - - (&cli.App{ - Flags: []cli.Flag{ - cli.StringSliceFlag{Name: "intervals, i", Value: &cli.StringSlice{}, EnvVar: "COMPAT_INTERVALS,APP_INTERVALS"}, - }, - Action: func(ctx *cli.Context) { - if !reflect.DeepEqual(ctx.StringSlice("intervals"), []string{"20", "30", "40"}) { - t.Errorf("main name not set from env") - } - if !reflect.DeepEqual(ctx.StringSlice("i"), []string{"20", "30", "40"}) { - t.Errorf("short name not set from env") - } - }, - }).Run([]string{"run"}) -} - -func TestParseMultiInt(t *testing.T) { - a := cli.App{ - Flags: []cli.Flag{ - cli.IntFlag{Name: "serve, s"}, - }, - Action: func(ctx *cli.Context) { - if ctx.Int("serve") != 10 { - t.Errorf("main name not set") - } - if ctx.Int("s") != 10 { - t.Errorf("short name not set") - } - }, - } - a.Run([]string{"run", "-s", "10"}) -} - -func TestParseMultiIntFromEnv(t *testing.T) { - os.Clearenv() - os.Setenv("APP_TIMEOUT_SECONDS", "10") - a := cli.App{ - Flags: []cli.Flag{ - cli.IntFlag{Name: "timeout, t", EnvVar: "APP_TIMEOUT_SECONDS"}, - }, - Action: func(ctx *cli.Context) { - if ctx.Int("timeout") != 10 { - t.Errorf("main name not set") - } - if ctx.Int("t") != 10 { - t.Errorf("short name not set") - } - }, - } - a.Run([]string{"run"}) -} - -func TestParseMultiIntFromEnvCascade(t *testing.T) { - os.Clearenv() - os.Setenv("APP_TIMEOUT_SECONDS", "10") - a := cli.App{ - Flags: []cli.Flag{ - cli.IntFlag{Name: "timeout, t", EnvVar: "COMPAT_TIMEOUT_SECONDS,APP_TIMEOUT_SECONDS"}, - }, - Action: func(ctx *cli.Context) { - if ctx.Int("timeout") != 10 { - t.Errorf("main name not set") - } - if ctx.Int("t") != 10 { - t.Errorf("short name not set") - } - }, - } - a.Run([]string{"run"}) -} - -func TestParseMultiIntSlice(t *testing.T) { - (&cli.App{ - Flags: []cli.Flag{ - cli.IntSliceFlag{Name: "serve, s", Value: &cli.IntSlice{}}, - }, - Action: func(ctx *cli.Context) { - if !reflect.DeepEqual(ctx.IntSlice("serve"), []int{10, 20}) { - t.Errorf("main name not set") - } - if !reflect.DeepEqual(ctx.IntSlice("s"), []int{10, 20}) { - t.Errorf("short name not set") - } - }, - }).Run([]string{"run", "-s", "10", "-s", "20"}) -} - -func TestParseMultiIntSliceFromEnv(t *testing.T) { - os.Clearenv() - os.Setenv("APP_INTERVALS", "20,30,40") - - (&cli.App{ - Flags: []cli.Flag{ - cli.IntSliceFlag{Name: "intervals, i", Value: &cli.IntSlice{}, EnvVar: "APP_INTERVALS"}, - }, - Action: func(ctx *cli.Context) { - if !reflect.DeepEqual(ctx.IntSlice("intervals"), []int{20, 30, 40}) { - t.Errorf("main name not set from env") - } - if !reflect.DeepEqual(ctx.IntSlice("i"), []int{20, 30, 40}) { - t.Errorf("short name not set from env") - } - }, - }).Run([]string{"run"}) -} - -func TestParseMultiIntSliceFromEnvCascade(t *testing.T) { - os.Clearenv() - os.Setenv("APP_INTERVALS", "20,30,40") - - (&cli.App{ - Flags: []cli.Flag{ - cli.IntSliceFlag{Name: "intervals, i", Value: &cli.IntSlice{}, EnvVar: "COMPAT_INTERVALS,APP_INTERVALS"}, - }, - Action: func(ctx *cli.Context) { - if !reflect.DeepEqual(ctx.IntSlice("intervals"), []int{20, 30, 40}) { - t.Errorf("main name not set from env") - } - if !reflect.DeepEqual(ctx.IntSlice("i"), []int{20, 30, 40}) { - t.Errorf("short name not set from env") - } - }, - }).Run([]string{"run"}) -} - -func TestParseMultiFloat64(t *testing.T) { - a := cli.App{ - Flags: []cli.Flag{ - cli.Float64Flag{Name: "serve, s"}, - }, - Action: func(ctx *cli.Context) { - if ctx.Float64("serve") != 10.2 { - t.Errorf("main name not set") - } - if ctx.Float64("s") != 10.2 { - t.Errorf("short name not set") - } - }, - } - a.Run([]string{"run", "-s", "10.2"}) -} - -func TestParseMultiFloat64FromEnv(t *testing.T) { - os.Clearenv() - os.Setenv("APP_TIMEOUT_SECONDS", "15.5") - a := cli.App{ - Flags: []cli.Flag{ - cli.Float64Flag{Name: "timeout, t", EnvVar: "APP_TIMEOUT_SECONDS"}, - }, - Action: func(ctx *cli.Context) { - if ctx.Float64("timeout") != 15.5 { - t.Errorf("main name not set") - } - if ctx.Float64("t") != 15.5 { - t.Errorf("short name not set") - } - }, - } - a.Run([]string{"run"}) -} - -func TestParseMultiFloat64FromEnvCascade(t *testing.T) { - os.Clearenv() - os.Setenv("APP_TIMEOUT_SECONDS", "15.5") - a := cli.App{ - Flags: []cli.Flag{ - cli.Float64Flag{Name: "timeout, t", EnvVar: "COMPAT_TIMEOUT_SECONDS,APP_TIMEOUT_SECONDS"}, - }, - Action: func(ctx *cli.Context) { - if ctx.Float64("timeout") != 15.5 { - t.Errorf("main name not set") - } - if ctx.Float64("t") != 15.5 { - t.Errorf("short name not set") - } - }, - } - a.Run([]string{"run"}) -} - -func TestParseMultiBool(t *testing.T) { - a := cli.App{ - Flags: []cli.Flag{ - cli.BoolFlag{Name: "serve, s"}, - }, - Action: func(ctx *cli.Context) { - if ctx.Bool("serve") != true { - t.Errorf("main name not set") - } - if ctx.Bool("s") != true { - t.Errorf("short name not set") - } - }, - } - a.Run([]string{"run", "--serve"}) -} - -func TestParseMultiBoolFromEnv(t *testing.T) { - os.Clearenv() - os.Setenv("APP_DEBUG", "1") - a := cli.App{ - Flags: []cli.Flag{ - cli.BoolFlag{Name: "debug, d", EnvVar: "APP_DEBUG"}, - }, - Action: func(ctx *cli.Context) { - if ctx.Bool("debug") != true { - t.Errorf("main name not set from env") - } - if ctx.Bool("d") != true { - t.Errorf("short name not set from env") - } - }, - } - a.Run([]string{"run"}) -} - -func TestParseMultiBoolFromEnvCascade(t *testing.T) { - os.Clearenv() - os.Setenv("APP_DEBUG", "1") - a := cli.App{ - Flags: []cli.Flag{ - cli.BoolFlag{Name: "debug, d", EnvVar: "COMPAT_DEBUG,APP_DEBUG"}, - }, - Action: func(ctx *cli.Context) { - if ctx.Bool("debug") != true { - t.Errorf("main name not set from env") - } - if ctx.Bool("d") != true { - t.Errorf("short name not set from env") - } - }, - } - a.Run([]string{"run"}) -} - -func TestParseMultiBoolT(t *testing.T) { - a := cli.App{ - Flags: []cli.Flag{ - cli.BoolTFlag{Name: "serve, s"}, - }, - Action: func(ctx *cli.Context) { - if ctx.BoolT("serve") != true { - t.Errorf("main name not set") - } - if ctx.BoolT("s") != true { - t.Errorf("short name not set") - } - }, - } - a.Run([]string{"run", "--serve"}) -} - -func TestParseMultiBoolTFromEnv(t *testing.T) { - os.Clearenv() - os.Setenv("APP_DEBUG", "0") - a := cli.App{ - Flags: []cli.Flag{ - cli.BoolTFlag{Name: "debug, d", EnvVar: "APP_DEBUG"}, - }, - Action: func(ctx *cli.Context) { - if ctx.BoolT("debug") != false { - t.Errorf("main name not set from env") - } - if ctx.BoolT("d") != false { - t.Errorf("short name not set from env") - } - }, - } - a.Run([]string{"run"}) -} - -func TestParseMultiBoolTFromEnvCascade(t *testing.T) { - os.Clearenv() - os.Setenv("APP_DEBUG", "0") - a := cli.App{ - Flags: []cli.Flag{ - cli.BoolTFlag{Name: "debug, d", EnvVar: "COMPAT_DEBUG,APP_DEBUG"}, - }, - Action: func(ctx *cli.Context) { - if ctx.BoolT("debug") != false { - t.Errorf("main name not set from env") - } - if ctx.BoolT("d") != false { - t.Errorf("short name not set from env") - } - }, - } - a.Run([]string{"run"}) -} - -type Parser [2]string - -func (p *Parser) Set(value string) error { - parts := strings.Split(value, ",") - if len(parts) != 2 { - return fmt.Errorf("invalid format") - } - - (*p)[0] = parts[0] - (*p)[1] = parts[1] - - return nil -} - -func (p *Parser) String() string { - return fmt.Sprintf("%s,%s", p[0], p[1]) -} - -func TestParseGeneric(t *testing.T) { - a := cli.App{ - Flags: []cli.Flag{ - cli.GenericFlag{Name: "serve, s", Value: &Parser{}}, - }, - Action: func(ctx *cli.Context) { - if !reflect.DeepEqual(ctx.Generic("serve"), &Parser{"10", "20"}) { - t.Errorf("main name not set") - } - if !reflect.DeepEqual(ctx.Generic("s"), &Parser{"10", "20"}) { - t.Errorf("short name not set") - } - }, - } - a.Run([]string{"run", "-s", "10,20"}) -} - -func TestParseGenericFromEnv(t *testing.T) { - os.Clearenv() - os.Setenv("APP_SERVE", "20,30") - a := cli.App{ - Flags: []cli.Flag{ - cli.GenericFlag{Name: "serve, s", Value: &Parser{}, EnvVar: "APP_SERVE"}, - }, - Action: func(ctx *cli.Context) { - if !reflect.DeepEqual(ctx.Generic("serve"), &Parser{"20", "30"}) { - t.Errorf("main name not set from env") - } - if !reflect.DeepEqual(ctx.Generic("s"), &Parser{"20", "30"}) { - t.Errorf("short name not set from env") - } - }, - } - a.Run([]string{"run"}) -} - -func TestParseGenericFromEnvCascade(t *testing.T) { - os.Clearenv() - os.Setenv("APP_FOO", "99,2000") - a := cli.App{ - Flags: []cli.Flag{ - cli.GenericFlag{Name: "foos", Value: &Parser{}, EnvVar: "COMPAT_FOO,APP_FOO"}, - }, - Action: func(ctx *cli.Context) { - if !reflect.DeepEqual(ctx.Generic("foos"), &Parser{"99", "2000"}) { - t.Errorf("value not set from env") - } - }, - } - a.Run([]string{"run"}) -} diff --git a/vendor/github.com/codegangsta/cli/help.go b/vendor/github.com/codegangsta/cli/help.go deleted file mode 100644 index bfb278851..000000000 --- a/vendor/github.com/codegangsta/cli/help.go +++ /dev/null @@ -1,211 +0,0 @@ -package cli - -import "fmt" - -// The text template for the Default help topic. -// cli.go uses text/template to render templates. You can -// render custom help text by setting this variable. -var AppHelpTemplate = `NAME: - {{.Name}} - {{.Usage}} - -USAGE: - {{.Name}} {{if .Flags}}[global options] {{end}}command{{if .Flags}} [command options]{{end}} [arguments...] - -VERSION: - {{.Version}}{{if or .Author .Email}} - -AUTHOR:{{if .Author}} - {{.Author}}{{if .Email}} - <{{.Email}}>{{end}}{{else}} - {{.Email}}{{end}}{{end}} - -COMMANDS: - {{range .Commands}}{{.Name}}{{with .ShortName}}, {{.}}{{end}}{{ "\t" }}{{.Usage}} - {{end}}{{if .Flags}} -GLOBAL OPTIONS: - {{range .Flags}}{{.}} - {{end}}{{end}} -` - -// The text template for the command help topic. -// cli.go uses text/template to render templates. You can -// render custom help text by setting this variable. -var CommandHelpTemplate = `NAME: - {{.Name}} - {{.Usage}} - -USAGE: - command {{.Name}}{{if .Flags}} [command options]{{end}} [arguments...]{{if .Description}} - -DESCRIPTION: - {{.Description}}{{end}}{{if .Flags}} - -OPTIONS: - {{range .Flags}}{{.}} - {{end}}{{ end }} -` - -// The text template for the subcommand help topic. -// cli.go uses text/template to render templates. You can -// render custom help text by setting this variable. -var SubcommandHelpTemplate = `NAME: - {{.Name}} - {{.Usage}} - -USAGE: - {{.Name}} command{{if .Flags}} [command options]{{end}} [arguments...] - -COMMANDS: - {{range .Commands}}{{.Name}}{{with .ShortName}}, {{.}}{{end}}{{ "\t" }}{{.Usage}} - {{end}}{{if .Flags}} -OPTIONS: - {{range .Flags}}{{.}} - {{end}}{{end}} -` - -var helpCommand = Command{ - Name: "help", - ShortName: "h", - Usage: "Shows a list of commands or help for one command", - Action: func(c *Context) { - args := c.Args() - if args.Present() { - ShowCommandHelp(c, args.First()) - } else { - ShowAppHelp(c) - } - }, -} - -var helpSubcommand = Command{ - Name: "help", - ShortName: "h", - Usage: "Shows a list of commands or help for one command", - Action: func(c *Context) { - args := c.Args() - if args.Present() { - ShowCommandHelp(c, args.First()) - } else { - ShowSubcommandHelp(c) - } - }, -} - -// Prints help for the App -type helpPrinter func(templ string, data interface{}) - -var HelpPrinter helpPrinter = nil - -// Prints version for the App -var VersionPrinter = printVersion - -func ShowAppHelp(c *Context) { - HelpPrinter(AppHelpTemplate, c.App) -} - -// Prints the list of subcommands as the default app completion method -func DefaultAppComplete(c *Context) { - for _, command := range c.App.Commands { - fmt.Fprintln(c.App.Writer, command.Name) - if command.ShortName != "" { - fmt.Fprintln(c.App.Writer, command.ShortName) - } - } -} - -// Prints help for the given command -func ShowCommandHelp(c *Context, command string) { - for _, c := range c.App.Commands { - if c.HasName(command) { - HelpPrinter(CommandHelpTemplate, c) - return - } - } - - if c.App.CommandNotFound != nil { - c.App.CommandNotFound(c, command) - } else { - fmt.Fprintf(c.App.Writer, "No help topic for '%v'\n", command) - } -} - -// Prints help for the given subcommand -func ShowSubcommandHelp(c *Context) { - ShowCommandHelp(c, c.Command.Name) -} - -// Prints the version number of the App -func ShowVersion(c *Context) { - VersionPrinter(c) -} - -func printVersion(c *Context) { - fmt.Fprintf(c.App.Writer, "%v version %v\n", c.App.Name, c.App.Version) -} - -// Prints the lists of commands within a given context -func ShowCompletions(c *Context) { - a := c.App - if a != nil && a.BashComplete != nil { - a.BashComplete(c) - } -} - -// Prints the custom completions for a given command -func ShowCommandCompletions(ctx *Context, command string) { - c := ctx.App.Command(command) - if c != nil && c.BashComplete != nil { - c.BashComplete(ctx) - } -} - -func checkVersion(c *Context) bool { - if c.GlobalBool("version") { - ShowVersion(c) - return true - } - - return false -} - -func checkHelp(c *Context) bool { - if c.GlobalBool("h") || c.GlobalBool("help") { - ShowAppHelp(c) - return true - } - - return false -} - -func checkCommandHelp(c *Context, name string) bool { - if c.Bool("h") || c.Bool("help") { - ShowCommandHelp(c, name) - return true - } - - return false -} - -func checkSubcommandHelp(c *Context) bool { - if c.GlobalBool("h") || c.GlobalBool("help") { - ShowSubcommandHelp(c) - return true - } - - return false -} - -func checkCompletions(c *Context) bool { - if (c.GlobalBool(BashCompletionFlag.Name) || c.Bool(BashCompletionFlag.Name)) && c.App.EnableBashCompletion { - ShowCompletions(c) - return true - } - - return false -} - -func checkCommandCompletions(c *Context, name string) bool { - if c.Bool(BashCompletionFlag.Name) && c.App.EnableBashCompletion { - ShowCommandCompletions(c, name) - return true - } - - return false -} diff --git a/vendor/github.com/codegangsta/cli/helpers_test.go b/vendor/github.com/codegangsta/cli/helpers_test.go deleted file mode 100644 index cdc4feb2f..000000000 --- a/vendor/github.com/codegangsta/cli/helpers_test.go +++ /dev/null @@ -1,19 +0,0 @@ -package cli_test - -import ( - "reflect" - "testing" -) - -/* Test Helpers */ -func expect(t *testing.T, a interface{}, b interface{}) { - if a != b { - t.Errorf("Expected %v (type %v) - Got %v (type %v)", b, reflect.TypeOf(b), a, reflect.TypeOf(a)) - } -} - -func refute(t *testing.T, a interface{}, b interface{}) { - if a == b { - t.Errorf("Did not expect %v (type %v) - Got %v (type %v)", b, reflect.TypeOf(b), a, reflect.TypeOf(a)) - } -} diff --git a/vendor/github.com/davecgh/go-spew/LICENSE b/vendor/github.com/davecgh/go-spew/LICENSE new file mode 100644 index 000000000..2a7cfd2bf --- /dev/null +++ b/vendor/github.com/davecgh/go-spew/LICENSE @@ -0,0 +1,13 @@ +Copyright (c) 2012-2013 Dave Collins + +Permission to use, copy, modify, and distribute this software for any +purpose with or without fee is hereby granted, provided that the above +copyright notice and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES +WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF +MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR +ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES +WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN +ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF +OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. diff --git a/vendor/github.com/davecgh/go-spew/spew/bypass.go b/vendor/github.com/davecgh/go-spew/spew/bypass.go new file mode 100644 index 000000000..a8d27a3f6 --- /dev/null +++ b/vendor/github.com/davecgh/go-spew/spew/bypass.go @@ -0,0 +1,136 @@ +// Copyright (c) 2015 Dave Collins +// +// Permission to use, copy, modify, and distribute this software for any +// purpose with or without fee is hereby granted, provided that the above +// copyright notice and this permission notice appear in all copies. +// +// THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES +// WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF +// MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR +// ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES +// WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN +// ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF +// OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + +// NOTE: Due to the following build constraints, this file will only be compiled +// when the code is not running on Google App Engine and "-tags disableunsafe" +// is not added to the go build command line. +// +build !appengine,!disableunsafe + +package spew + +import ( + "reflect" + "unsafe" +) + +const ( + // UnsafeDisabled is a build-time constant which specifies whether or + // not access to the unsafe package is available. + UnsafeDisabled = false + + // ptrSize is the size of a pointer on the current arch. + ptrSize = unsafe.Sizeof((*byte)(nil)) +) + +var ( + // offsetPtr, offsetScalar, and offsetFlag are the offsets for the + // internal reflect.Value fields. These values are valid before golang + // commit ecccf07e7f9d which changed the format. The are also valid + // after commit 82f48826c6c7 which changed the format again to mirror + // the original format. Code in the init function updates these offsets + // as necessary. + offsetPtr = uintptr(ptrSize) + offsetScalar = uintptr(0) + offsetFlag = uintptr(ptrSize * 2) + + // flagKindWidth and flagKindShift indicate various bits that the + // reflect package uses internally to track kind information. + // + // flagRO indicates whether or not the value field of a reflect.Value is + // read-only. + // + // flagIndir indicates whether the value field of a reflect.Value is + // the actual data or a pointer to the data. + // + // These values are valid before golang commit 90a7c3c86944 which + // changed their positions. Code in the init function updates these + // flags as necessary. + flagKindWidth = uintptr(5) + flagKindShift = uintptr(flagKindWidth - 1) + flagRO = uintptr(1 << 0) + flagIndir = uintptr(1 << 1) +) + +func init() { + // Older versions of reflect.Value stored small integers directly in the + // ptr field (which is named val in the older versions). Versions + // between commits ecccf07e7f9d and 82f48826c6c7 added a new field named + // scalar for this purpose which unfortunately came before the flag + // field, so the offset of the flag field is different for those + // versions. + // + // This code constructs a new reflect.Value from a known small integer + // and checks if the size of the reflect.Value struct indicates it has + // the scalar field. When it does, the offsets are updated accordingly. + vv := reflect.ValueOf(0xf00) + if unsafe.Sizeof(vv) == (ptrSize * 4) { + offsetScalar = ptrSize * 2 + offsetFlag = ptrSize * 3 + } + + // Commit 90a7c3c86944 changed the flag positions such that the low + // order bits are the kind. This code extracts the kind from the flags + // field and ensures it's the correct type. When it's not, the flag + // order has been changed to the newer format, so the flags are updated + // accordingly. + upf := unsafe.Pointer(uintptr(unsafe.Pointer(&vv)) + offsetFlag) + upfv := *(*uintptr)(upf) + flagKindMask := uintptr((1<>flagKindShift != uintptr(reflect.Int) { + flagKindShift = 0 + flagRO = 1 << 5 + flagIndir = 1 << 6 + } +} + +// unsafeReflectValue converts the passed reflect.Value into a one that bypasses +// the typical safety restrictions preventing access to unaddressable and +// unexported data. It works by digging the raw pointer to the underlying +// value out of the protected value and generating a new unprotected (unsafe) +// reflect.Value to it. +// +// This allows us to check for implementations of the Stringer and error +// interfaces to be used for pretty printing ordinarily unaddressable and +// inaccessible values such as unexported struct fields. +func unsafeReflectValue(v reflect.Value) (rv reflect.Value) { + indirects := 1 + vt := v.Type() + upv := unsafe.Pointer(uintptr(unsafe.Pointer(&v)) + offsetPtr) + rvf := *(*uintptr)(unsafe.Pointer(uintptr(unsafe.Pointer(&v)) + offsetFlag)) + if rvf&flagIndir != 0 { + vt = reflect.PtrTo(v.Type()) + indirects++ + } else if offsetScalar != 0 { + // The value is in the scalar field when it's not one of the + // reference types. + switch vt.Kind() { + case reflect.Uintptr: + case reflect.Chan: + case reflect.Func: + case reflect.Map: + case reflect.Ptr: + case reflect.UnsafePointer: + default: + upv = unsafe.Pointer(uintptr(unsafe.Pointer(&v)) + + offsetScalar) + } + } + + pv := reflect.NewAt(vt, upv) + rv = pv + for i := 0; i < indirects; i++ { + rv = rv.Elem() + } + return rv +} diff --git a/vendor/github.com/davecgh/go-spew/spew/bypasssafe.go b/vendor/github.com/davecgh/go-spew/spew/bypasssafe.go new file mode 100644 index 000000000..457e41235 --- /dev/null +++ b/vendor/github.com/davecgh/go-spew/spew/bypasssafe.go @@ -0,0 +1,37 @@ +// Copyright (c) 2015 Dave Collins +// +// Permission to use, copy, modify, and distribute this software for any +// purpose with or without fee is hereby granted, provided that the above +// copyright notice and this permission notice appear in all copies. +// +// THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES +// WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF +// MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR +// ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES +// WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN +// ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF +// OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + +// NOTE: Due to the following build constraints, this file will only be compiled +// when either the code is running on Google App Engine or "-tags disableunsafe" +// is added to the go build command line. +// +build appengine disableunsafe + +package spew + +import "reflect" + +const ( + // UnsafeDisabled is a build-time constant which specifies whether or + // not access to the unsafe package is available. + UnsafeDisabled = true +) + +// unsafeReflectValue typically converts the passed reflect.Value into a one +// that bypasses the typical safety restrictions preventing access to +// unaddressable and unexported data. However, doing this relies on access to +// the unsafe package. This is a stub version which simply returns the passed +// reflect.Value when the unsafe package is not available. +func unsafeReflectValue(v reflect.Value) reflect.Value { + return v +} diff --git a/vendor/github.com/davecgh/go-spew/spew/common.go b/vendor/github.com/davecgh/go-spew/spew/common.go new file mode 100644 index 000000000..14f02dc15 --- /dev/null +++ b/vendor/github.com/davecgh/go-spew/spew/common.go @@ -0,0 +1,341 @@ +/* + * Copyright (c) 2013 Dave Collins + * + * Permission to use, copy, modify, and distribute this software for any + * purpose with or without fee is hereby granted, provided that the above + * copyright notice and this permission notice appear in all copies. + * + * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES + * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR + * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES + * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN + * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF + * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + */ + +package spew + +import ( + "bytes" + "fmt" + "io" + "reflect" + "sort" + "strconv" +) + +// Some constants in the form of bytes to avoid string overhead. This mirrors +// the technique used in the fmt package. +var ( + panicBytes = []byte("(PANIC=") + plusBytes = []byte("+") + iBytes = []byte("i") + trueBytes = []byte("true") + falseBytes = []byte("false") + interfaceBytes = []byte("(interface {})") + commaNewlineBytes = []byte(",\n") + newlineBytes = []byte("\n") + openBraceBytes = []byte("{") + openBraceNewlineBytes = []byte("{\n") + closeBraceBytes = []byte("}") + asteriskBytes = []byte("*") + colonBytes = []byte(":") + colonSpaceBytes = []byte(": ") + openParenBytes = []byte("(") + closeParenBytes = []byte(")") + spaceBytes = []byte(" ") + pointerChainBytes = []byte("->") + nilAngleBytes = []byte("") + maxNewlineBytes = []byte("\n") + maxShortBytes = []byte("") + circularBytes = []byte("") + circularShortBytes = []byte("") + invalidAngleBytes = []byte("") + openBracketBytes = []byte("[") + closeBracketBytes = []byte("]") + percentBytes = []byte("%") + precisionBytes = []byte(".") + openAngleBytes = []byte("<") + closeAngleBytes = []byte(">") + openMapBytes = []byte("map[") + closeMapBytes = []byte("]") + lenEqualsBytes = []byte("len=") + capEqualsBytes = []byte("cap=") +) + +// hexDigits is used to map a decimal value to a hex digit. +var hexDigits = "0123456789abcdef" + +// catchPanic handles any panics that might occur during the handleMethods +// calls. +func catchPanic(w io.Writer, v reflect.Value) { + if err := recover(); err != nil { + w.Write(panicBytes) + fmt.Fprintf(w, "%v", err) + w.Write(closeParenBytes) + } +} + +// handleMethods attempts to call the Error and String methods on the underlying +// type the passed reflect.Value represents and outputes the result to Writer w. +// +// It handles panics in any called methods by catching and displaying the error +// as the formatted value. +func handleMethods(cs *ConfigState, w io.Writer, v reflect.Value) (handled bool) { + // We need an interface to check if the type implements the error or + // Stringer interface. However, the reflect package won't give us an + // interface on certain things like unexported struct fields in order + // to enforce visibility rules. We use unsafe, when it's available, + // to bypass these restrictions since this package does not mutate the + // values. + if !v.CanInterface() { + if UnsafeDisabled { + return false + } + + v = unsafeReflectValue(v) + } + + // Choose whether or not to do error and Stringer interface lookups against + // the base type or a pointer to the base type depending on settings. + // Technically calling one of these methods with a pointer receiver can + // mutate the value, however, types which choose to satisify an error or + // Stringer interface with a pointer receiver should not be mutating their + // state inside these interface methods. + if !cs.DisablePointerMethods && !UnsafeDisabled && !v.CanAddr() { + v = unsafeReflectValue(v) + } + if v.CanAddr() { + v = v.Addr() + } + + // Is it an error or Stringer? + switch iface := v.Interface().(type) { + case error: + defer catchPanic(w, v) + if cs.ContinueOnMethod { + w.Write(openParenBytes) + w.Write([]byte(iface.Error())) + w.Write(closeParenBytes) + w.Write(spaceBytes) + return false + } + + w.Write([]byte(iface.Error())) + return true + + case fmt.Stringer: + defer catchPanic(w, v) + if cs.ContinueOnMethod { + w.Write(openParenBytes) + w.Write([]byte(iface.String())) + w.Write(closeParenBytes) + w.Write(spaceBytes) + return false + } + w.Write([]byte(iface.String())) + return true + } + return false +} + +// printBool outputs a boolean value as true or false to Writer w. +func printBool(w io.Writer, val bool) { + if val { + w.Write(trueBytes) + } else { + w.Write(falseBytes) + } +} + +// printInt outputs a signed integer value to Writer w. +func printInt(w io.Writer, val int64, base int) { + w.Write([]byte(strconv.FormatInt(val, base))) +} + +// printUint outputs an unsigned integer value to Writer w. +func printUint(w io.Writer, val uint64, base int) { + w.Write([]byte(strconv.FormatUint(val, base))) +} + +// printFloat outputs a floating point value using the specified precision, +// which is expected to be 32 or 64bit, to Writer w. +func printFloat(w io.Writer, val float64, precision int) { + w.Write([]byte(strconv.FormatFloat(val, 'g', -1, precision))) +} + +// printComplex outputs a complex value using the specified float precision +// for the real and imaginary parts to Writer w. +func printComplex(w io.Writer, c complex128, floatPrecision int) { + r := real(c) + w.Write(openParenBytes) + w.Write([]byte(strconv.FormatFloat(r, 'g', -1, floatPrecision))) + i := imag(c) + if i >= 0 { + w.Write(plusBytes) + } + w.Write([]byte(strconv.FormatFloat(i, 'g', -1, floatPrecision))) + w.Write(iBytes) + w.Write(closeParenBytes) +} + +// printHexPtr outputs a uintptr formatted as hexidecimal with a leading '0x' +// prefix to Writer w. +func printHexPtr(w io.Writer, p uintptr) { + // Null pointer. + num := uint64(p) + if num == 0 { + w.Write(nilAngleBytes) + return + } + + // Max uint64 is 16 bytes in hex + 2 bytes for '0x' prefix + buf := make([]byte, 18) + + // It's simpler to construct the hex string right to left. + base := uint64(16) + i := len(buf) - 1 + for num >= base { + buf[i] = hexDigits[num%base] + num /= base + i-- + } + buf[i] = hexDigits[num] + + // Add '0x' prefix. + i-- + buf[i] = 'x' + i-- + buf[i] = '0' + + // Strip unused leading bytes. + buf = buf[i:] + w.Write(buf) +} + +// valuesSorter implements sort.Interface to allow a slice of reflect.Value +// elements to be sorted. +type valuesSorter struct { + values []reflect.Value + strings []string // either nil or same len and values + cs *ConfigState +} + +// newValuesSorter initializes a valuesSorter instance, which holds a set of +// surrogate keys on which the data should be sorted. It uses flags in +// ConfigState to decide if and how to populate those surrogate keys. +func newValuesSorter(values []reflect.Value, cs *ConfigState) sort.Interface { + vs := &valuesSorter{values: values, cs: cs} + if canSortSimply(vs.values[0].Kind()) { + return vs + } + if !cs.DisableMethods { + vs.strings = make([]string, len(values)) + for i := range vs.values { + b := bytes.Buffer{} + if !handleMethods(cs, &b, vs.values[i]) { + vs.strings = nil + break + } + vs.strings[i] = b.String() + } + } + if vs.strings == nil && cs.SpewKeys { + vs.strings = make([]string, len(values)) + for i := range vs.values { + vs.strings[i] = Sprintf("%#v", vs.values[i].Interface()) + } + } + return vs +} + +// canSortSimply tests whether a reflect.Kind is a primitive that can be sorted +// directly, or whether it should be considered for sorting by surrogate keys +// (if the ConfigState allows it). +func canSortSimply(kind reflect.Kind) bool { + // This switch parallels valueSortLess, except for the default case. + switch kind { + case reflect.Bool: + return true + case reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64, reflect.Int: + return true + case reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uint: + return true + case reflect.Float32, reflect.Float64: + return true + case reflect.String: + return true + case reflect.Uintptr: + return true + case reflect.Array: + return true + } + return false +} + +// Len returns the number of values in the slice. It is part of the +// sort.Interface implementation. +func (s *valuesSorter) Len() int { + return len(s.values) +} + +// Swap swaps the values at the passed indices. It is part of the +// sort.Interface implementation. +func (s *valuesSorter) Swap(i, j int) { + s.values[i], s.values[j] = s.values[j], s.values[i] + if s.strings != nil { + s.strings[i], s.strings[j] = s.strings[j], s.strings[i] + } +} + +// valueSortLess returns whether the first value should sort before the second +// value. It is used by valueSorter.Less as part of the sort.Interface +// implementation. +func valueSortLess(a, b reflect.Value) bool { + switch a.Kind() { + case reflect.Bool: + return !a.Bool() && b.Bool() + case reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64, reflect.Int: + return a.Int() < b.Int() + case reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uint: + return a.Uint() < b.Uint() + case reflect.Float32, reflect.Float64: + return a.Float() < b.Float() + case reflect.String: + return a.String() < b.String() + case reflect.Uintptr: + return a.Uint() < b.Uint() + case reflect.Array: + // Compare the contents of both arrays. + l := a.Len() + for i := 0; i < l; i++ { + av := a.Index(i) + bv := b.Index(i) + if av.Interface() == bv.Interface() { + continue + } + return valueSortLess(av, bv) + } + } + return a.String() < b.String() +} + +// Less returns whether the value at index i should sort before the +// value at index j. It is part of the sort.Interface implementation. +func (s *valuesSorter) Less(i, j int) bool { + if s.strings == nil { + return valueSortLess(s.values[i], s.values[j]) + } + return s.strings[i] < s.strings[j] +} + +// sortValues is a sort function that handles both native types and any type that +// can be converted to error or Stringer. Other inputs are sorted according to +// their Value.String() value to ensure display stability. +func sortValues(values []reflect.Value, cs *ConfigState) { + if len(values) == 0 { + return + } + sort.Sort(newValuesSorter(values, cs)) +} diff --git a/vendor/github.com/davecgh/go-spew/spew/config.go b/vendor/github.com/davecgh/go-spew/spew/config.go new file mode 100644 index 000000000..ee1ab07b3 --- /dev/null +++ b/vendor/github.com/davecgh/go-spew/spew/config.go @@ -0,0 +1,297 @@ +/* + * Copyright (c) 2013 Dave Collins + * + * Permission to use, copy, modify, and distribute this software for any + * purpose with or without fee is hereby granted, provided that the above + * copyright notice and this permission notice appear in all copies. + * + * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES + * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR + * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES + * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN + * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF + * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + */ + +package spew + +import ( + "bytes" + "fmt" + "io" + "os" +) + +// ConfigState houses the configuration options used by spew to format and +// display values. There is a global instance, Config, that is used to control +// all top-level Formatter and Dump functionality. Each ConfigState instance +// provides methods equivalent to the top-level functions. +// +// The zero value for ConfigState provides no indentation. You would typically +// want to set it to a space or a tab. +// +// Alternatively, you can use NewDefaultConfig to get a ConfigState instance +// with default settings. See the documentation of NewDefaultConfig for default +// values. +type ConfigState struct { + // Indent specifies the string to use for each indentation level. The + // global config instance that all top-level functions use set this to a + // single space by default. If you would like more indentation, you might + // set this to a tab with "\t" or perhaps two spaces with " ". + Indent string + + // MaxDepth controls the maximum number of levels to descend into nested + // data structures. The default, 0, means there is no limit. + // + // NOTE: Circular data structures are properly detected, so it is not + // necessary to set this value unless you specifically want to limit deeply + // nested data structures. + MaxDepth int + + // DisableMethods specifies whether or not error and Stringer interfaces are + // invoked for types that implement them. + DisableMethods bool + + // DisablePointerMethods specifies whether or not to check for and invoke + // error and Stringer interfaces on types which only accept a pointer + // receiver when the current type is not a pointer. + // + // NOTE: This might be an unsafe action since calling one of these methods + // with a pointer receiver could technically mutate the value, however, + // in practice, types which choose to satisify an error or Stringer + // interface with a pointer receiver should not be mutating their state + // inside these interface methods. As a result, this option relies on + // access to the unsafe package, so it will not have any effect when + // running in environments without access to the unsafe package such as + // Google App Engine or with the "disableunsafe" build tag specified. + DisablePointerMethods bool + + // ContinueOnMethod specifies whether or not recursion should continue once + // a custom error or Stringer interface is invoked. The default, false, + // means it will print the results of invoking the custom error or Stringer + // interface and return immediately instead of continuing to recurse into + // the internals of the data type. + // + // NOTE: This flag does not have any effect if method invocation is disabled + // via the DisableMethods or DisablePointerMethods options. + ContinueOnMethod bool + + // SortKeys specifies map keys should be sorted before being printed. Use + // this to have a more deterministic, diffable output. Note that only + // native types (bool, int, uint, floats, uintptr and string) and types + // that support the error or Stringer interfaces (if methods are + // enabled) are supported, with other types sorted according to the + // reflect.Value.String() output which guarantees display stability. + SortKeys bool + + // SpewKeys specifies that, as a last resort attempt, map keys should + // be spewed to strings and sorted by those strings. This is only + // considered if SortKeys is true. + SpewKeys bool +} + +// Config is the active configuration of the top-level functions. +// The configuration can be changed by modifying the contents of spew.Config. +var Config = ConfigState{Indent: " "} + +// Errorf is a wrapper for fmt.Errorf that treats each argument as if it were +// passed with a Formatter interface returned by c.NewFormatter. It returns +// the formatted string as a value that satisfies error. See NewFormatter +// for formatting details. +// +// This function is shorthand for the following syntax: +// +// fmt.Errorf(format, c.NewFormatter(a), c.NewFormatter(b)) +func (c *ConfigState) Errorf(format string, a ...interface{}) (err error) { + return fmt.Errorf(format, c.convertArgs(a)...) +} + +// Fprint is a wrapper for fmt.Fprint that treats each argument as if it were +// passed with a Formatter interface returned by c.NewFormatter. It returns +// the number of bytes written and any write error encountered. See +// NewFormatter for formatting details. +// +// This function is shorthand for the following syntax: +// +// fmt.Fprint(w, c.NewFormatter(a), c.NewFormatter(b)) +func (c *ConfigState) Fprint(w io.Writer, a ...interface{}) (n int, err error) { + return fmt.Fprint(w, c.convertArgs(a)...) +} + +// Fprintf is a wrapper for fmt.Fprintf that treats each argument as if it were +// passed with a Formatter interface returned by c.NewFormatter. It returns +// the number of bytes written and any write error encountered. See +// NewFormatter for formatting details. +// +// This function is shorthand for the following syntax: +// +// fmt.Fprintf(w, format, c.NewFormatter(a), c.NewFormatter(b)) +func (c *ConfigState) Fprintf(w io.Writer, format string, a ...interface{}) (n int, err error) { + return fmt.Fprintf(w, format, c.convertArgs(a)...) +} + +// Fprintln is a wrapper for fmt.Fprintln that treats each argument as if it +// passed with a Formatter interface returned by c.NewFormatter. See +// NewFormatter for formatting details. +// +// This function is shorthand for the following syntax: +// +// fmt.Fprintln(w, c.NewFormatter(a), c.NewFormatter(b)) +func (c *ConfigState) Fprintln(w io.Writer, a ...interface{}) (n int, err error) { + return fmt.Fprintln(w, c.convertArgs(a)...) +} + +// Print is a wrapper for fmt.Print that treats each argument as if it were +// passed with a Formatter interface returned by c.NewFormatter. It returns +// the number of bytes written and any write error encountered. See +// NewFormatter for formatting details. +// +// This function is shorthand for the following syntax: +// +// fmt.Print(c.NewFormatter(a), c.NewFormatter(b)) +func (c *ConfigState) Print(a ...interface{}) (n int, err error) { + return fmt.Print(c.convertArgs(a)...) +} + +// Printf is a wrapper for fmt.Printf that treats each argument as if it were +// passed with a Formatter interface returned by c.NewFormatter. It returns +// the number of bytes written and any write error encountered. See +// NewFormatter for formatting details. +// +// This function is shorthand for the following syntax: +// +// fmt.Printf(format, c.NewFormatter(a), c.NewFormatter(b)) +func (c *ConfigState) Printf(format string, a ...interface{}) (n int, err error) { + return fmt.Printf(format, c.convertArgs(a)...) +} + +// Println is a wrapper for fmt.Println that treats each argument as if it were +// passed with a Formatter interface returned by c.NewFormatter. It returns +// the number of bytes written and any write error encountered. See +// NewFormatter for formatting details. +// +// This function is shorthand for the following syntax: +// +// fmt.Println(c.NewFormatter(a), c.NewFormatter(b)) +func (c *ConfigState) Println(a ...interface{}) (n int, err error) { + return fmt.Println(c.convertArgs(a)...) +} + +// Sprint is a wrapper for fmt.Sprint that treats each argument as if it were +// passed with a Formatter interface returned by c.NewFormatter. It returns +// the resulting string. See NewFormatter for formatting details. +// +// This function is shorthand for the following syntax: +// +// fmt.Sprint(c.NewFormatter(a), c.NewFormatter(b)) +func (c *ConfigState) Sprint(a ...interface{}) string { + return fmt.Sprint(c.convertArgs(a)...) +} + +// Sprintf is a wrapper for fmt.Sprintf that treats each argument as if it were +// passed with a Formatter interface returned by c.NewFormatter. It returns +// the resulting string. See NewFormatter for formatting details. +// +// This function is shorthand for the following syntax: +// +// fmt.Sprintf(format, c.NewFormatter(a), c.NewFormatter(b)) +func (c *ConfigState) Sprintf(format string, a ...interface{}) string { + return fmt.Sprintf(format, c.convertArgs(a)...) +} + +// Sprintln is a wrapper for fmt.Sprintln that treats each argument as if it +// were passed with a Formatter interface returned by c.NewFormatter. It +// returns the resulting string. See NewFormatter for formatting details. +// +// This function is shorthand for the following syntax: +// +// fmt.Sprintln(c.NewFormatter(a), c.NewFormatter(b)) +func (c *ConfigState) Sprintln(a ...interface{}) string { + return fmt.Sprintln(c.convertArgs(a)...) +} + +/* +NewFormatter returns a custom formatter that satisfies the fmt.Formatter +interface. As a result, it integrates cleanly with standard fmt package +printing functions. The formatter is useful for inline printing of smaller data +types similar to the standard %v format specifier. + +The custom formatter only responds to the %v (most compact), %+v (adds pointer +addresses), %#v (adds types), and %#+v (adds types and pointer addresses) verb +combinations. Any other verbs such as %x and %q will be sent to the the +standard fmt package for formatting. In addition, the custom formatter ignores +the width and precision arguments (however they will still work on the format +specifiers not handled by the custom formatter). + +Typically this function shouldn't be called directly. It is much easier to make +use of the custom formatter by calling one of the convenience functions such as +c.Printf, c.Println, or c.Printf. +*/ +func (c *ConfigState) NewFormatter(v interface{}) fmt.Formatter { + return newFormatter(c, v) +} + +// Fdump formats and displays the passed arguments to io.Writer w. It formats +// exactly the same as Dump. +func (c *ConfigState) Fdump(w io.Writer, a ...interface{}) { + fdump(c, w, a...) +} + +/* +Dump displays the passed parameters to standard out with newlines, customizable +indentation, and additional debug information such as complete types and all +pointer addresses used to indirect to the final value. It provides the +following features over the built-in printing facilities provided by the fmt +package: + + * Pointers are dereferenced and followed + * Circular data structures are detected and handled properly + * Custom Stringer/error interfaces are optionally invoked, including + on unexported types + * Custom types which only implement the Stringer/error interfaces via + a pointer receiver are optionally invoked when passing non-pointer + variables + * Byte arrays and slices are dumped like the hexdump -C command which + includes offsets, byte values in hex, and ASCII output + +The configuration options are controlled by modifying the public members +of c. See ConfigState for options documentation. + +See Fdump if you would prefer dumping to an arbitrary io.Writer or Sdump to +get the formatted result as a string. +*/ +func (c *ConfigState) Dump(a ...interface{}) { + fdump(c, os.Stdout, a...) +} + +// Sdump returns a string with the passed arguments formatted exactly the same +// as Dump. +func (c *ConfigState) Sdump(a ...interface{}) string { + var buf bytes.Buffer + fdump(c, &buf, a...) + return buf.String() +} + +// convertArgs accepts a slice of arguments and returns a slice of the same +// length with each argument converted to a spew Formatter interface using +// the ConfigState associated with s. +func (c *ConfigState) convertArgs(args []interface{}) (formatters []interface{}) { + formatters = make([]interface{}, len(args)) + for index, arg := range args { + formatters[index] = newFormatter(c, arg) + } + return formatters +} + +// NewDefaultConfig returns a ConfigState with the following default settings. +// +// Indent: " " +// MaxDepth: 0 +// DisableMethods: false +// DisablePointerMethods: false +// ContinueOnMethod: false +// SortKeys: false +func NewDefaultConfig() *ConfigState { + return &ConfigState{Indent: " "} +} diff --git a/vendor/github.com/davecgh/go-spew/spew/doc.go b/vendor/github.com/davecgh/go-spew/spew/doc.go new file mode 100644 index 000000000..5be0c4060 --- /dev/null +++ b/vendor/github.com/davecgh/go-spew/spew/doc.go @@ -0,0 +1,202 @@ +/* + * Copyright (c) 2013 Dave Collins + * + * Permission to use, copy, modify, and distribute this software for any + * purpose with or without fee is hereby granted, provided that the above + * copyright notice and this permission notice appear in all copies. + * + * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES + * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR + * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES + * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN + * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF + * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + */ + +/* +Package spew implements a deep pretty printer for Go data structures to aid in +debugging. + +A quick overview of the additional features spew provides over the built-in +printing facilities for Go data types are as follows: + + * Pointers are dereferenced and followed + * Circular data structures are detected and handled properly + * Custom Stringer/error interfaces are optionally invoked, including + on unexported types + * Custom types which only implement the Stringer/error interfaces via + a pointer receiver are optionally invoked when passing non-pointer + variables + * Byte arrays and slices are dumped like the hexdump -C command which + includes offsets, byte values in hex, and ASCII output (only when using + Dump style) + +There are two different approaches spew allows for dumping Go data structures: + + * Dump style which prints with newlines, customizable indentation, + and additional debug information such as types and all pointer addresses + used to indirect to the final value + * A custom Formatter interface that integrates cleanly with the standard fmt + package and replaces %v, %+v, %#v, and %#+v to provide inline printing + similar to the default %v while providing the additional functionality + outlined above and passing unsupported format verbs such as %x and %q + along to fmt + +Quick Start + +This section demonstrates how to quickly get started with spew. See the +sections below for further details on formatting and configuration options. + +To dump a variable with full newlines, indentation, type, and pointer +information use Dump, Fdump, or Sdump: + spew.Dump(myVar1, myVar2, ...) + spew.Fdump(someWriter, myVar1, myVar2, ...) + str := spew.Sdump(myVar1, myVar2, ...) + +Alternatively, if you would prefer to use format strings with a compacted inline +printing style, use the convenience wrappers Printf, Fprintf, etc with +%v (most compact), %+v (adds pointer addresses), %#v (adds types), or +%#+v (adds types and pointer addresses): + spew.Printf("myVar1: %v -- myVar2: %+v", myVar1, myVar2) + spew.Printf("myVar3: %#v -- myVar4: %#+v", myVar3, myVar4) + spew.Fprintf(someWriter, "myVar1: %v -- myVar2: %+v", myVar1, myVar2) + spew.Fprintf(someWriter, "myVar3: %#v -- myVar4: %#+v", myVar3, myVar4) + +Configuration Options + +Configuration of spew is handled by fields in the ConfigState type. For +convenience, all of the top-level functions use a global state available +via the spew.Config global. + +It is also possible to create a ConfigState instance that provides methods +equivalent to the top-level functions. This allows concurrent configuration +options. See the ConfigState documentation for more details. + +The following configuration options are available: + * Indent + String to use for each indentation level for Dump functions. + It is a single space by default. A popular alternative is "\t". + + * MaxDepth + Maximum number of levels to descend into nested data structures. + There is no limit by default. + + * DisableMethods + Disables invocation of error and Stringer interface methods. + Method invocation is enabled by default. + + * DisablePointerMethods + Disables invocation of error and Stringer interface methods on types + which only accept pointer receivers from non-pointer variables. + Pointer method invocation is enabled by default. + + * ContinueOnMethod + Enables recursion into types after invoking error and Stringer interface + methods. Recursion after method invocation is disabled by default. + + * SortKeys + Specifies map keys should be sorted before being printed. Use + this to have a more deterministic, diffable output. Note that + only native types (bool, int, uint, floats, uintptr and string) + and types which implement error or Stringer interfaces are + supported with other types sorted according to the + reflect.Value.String() output which guarantees display + stability. Natural map order is used by default. + + * SpewKeys + Specifies that, as a last resort attempt, map keys should be + spewed to strings and sorted by those strings. This is only + considered if SortKeys is true. + +Dump Usage + +Simply call spew.Dump with a list of variables you want to dump: + + spew.Dump(myVar1, myVar2, ...) + +You may also call spew.Fdump if you would prefer to output to an arbitrary +io.Writer. For example, to dump to standard error: + + spew.Fdump(os.Stderr, myVar1, myVar2, ...) + +A third option is to call spew.Sdump to get the formatted output as a string: + + str := spew.Sdump(myVar1, myVar2, ...) + +Sample Dump Output + +See the Dump example for details on the setup of the types and variables being +shown here. + + (main.Foo) { + unexportedField: (*main.Bar)(0xf84002e210)({ + flag: (main.Flag) flagTwo, + data: (uintptr) + }), + ExportedField: (map[interface {}]interface {}) (len=1) { + (string) (len=3) "one": (bool) true + } + } + +Byte (and uint8) arrays and slices are displayed uniquely like the hexdump -C +command as shown. + ([]uint8) (len=32 cap=32) { + 00000000 11 12 13 14 15 16 17 18 19 1a 1b 1c 1d 1e 1f 20 |............... | + 00000010 21 22 23 24 25 26 27 28 29 2a 2b 2c 2d 2e 2f 30 |!"#$%&'()*+,-./0| + 00000020 31 32 |12| + } + +Custom Formatter + +Spew provides a custom formatter that implements the fmt.Formatter interface +so that it integrates cleanly with standard fmt package printing functions. The +formatter is useful for inline printing of smaller data types similar to the +standard %v format specifier. + +The custom formatter only responds to the %v (most compact), %+v (adds pointer +addresses), %#v (adds types), or %#+v (adds types and pointer addresses) verb +combinations. Any other verbs such as %x and %q will be sent to the the +standard fmt package for formatting. In addition, the custom formatter ignores +the width and precision arguments (however they will still work on the format +specifiers not handled by the custom formatter). + +Custom Formatter Usage + +The simplest way to make use of the spew custom formatter is to call one of the +convenience functions such as spew.Printf, spew.Println, or spew.Printf. The +functions have syntax you are most likely already familiar with: + + spew.Printf("myVar1: %v -- myVar2: %+v", myVar1, myVar2) + spew.Printf("myVar3: %#v -- myVar4: %#+v", myVar3, myVar4) + spew.Println(myVar, myVar2) + spew.Fprintf(os.Stderr, "myVar1: %v -- myVar2: %+v", myVar1, myVar2) + spew.Fprintf(os.Stderr, "myVar3: %#v -- myVar4: %#+v", myVar3, myVar4) + +See the Index for the full list convenience functions. + +Sample Formatter Output + +Double pointer to a uint8: + %v: <**>5 + %+v: <**>(0xf8400420d0->0xf8400420c8)5 + %#v: (**uint8)5 + %#+v: (**uint8)(0xf8400420d0->0xf8400420c8)5 + +Pointer to circular struct with a uint8 field and a pointer to itself: + %v: <*>{1 <*>} + %+v: <*>(0xf84003e260){ui8:1 c:<*>(0xf84003e260)} + %#v: (*main.circular){ui8:(uint8)1 c:(*main.circular)} + %#+v: (*main.circular)(0xf84003e260){ui8:(uint8)1 c:(*main.circular)(0xf84003e260)} + +See the Printf example for details on the setup of variables being shown +here. + +Errors + +Since it is possible for custom Stringer/error interfaces to panic, spew +detects them and handles them internally by printing the panic information +inline with the output. Since spew is intended to provide deep pretty printing +capabilities on structures, it intentionally does not return any errors. +*/ +package spew diff --git a/vendor/github.com/davecgh/go-spew/spew/dump.go b/vendor/github.com/davecgh/go-spew/spew/dump.go new file mode 100644 index 000000000..36a2b6cc9 --- /dev/null +++ b/vendor/github.com/davecgh/go-spew/spew/dump.go @@ -0,0 +1,511 @@ +/* + * Copyright (c) 2013 Dave Collins + * + * Permission to use, copy, modify, and distribute this software for any + * purpose with or without fee is hereby granted, provided that the above + * copyright notice and this permission notice appear in all copies. + * + * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES + * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR + * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES + * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN + * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF + * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + */ + +package spew + +import ( + "bytes" + "encoding/hex" + "fmt" + "io" + "os" + "reflect" + "regexp" + "strconv" + "strings" +) + +var ( + // uint8Type is a reflect.Type representing a uint8. It is used to + // convert cgo types to uint8 slices for hexdumping. + uint8Type = reflect.TypeOf(uint8(0)) + + // cCharRE is a regular expression that matches a cgo char. + // It is used to detect character arrays to hexdump them. + cCharRE = regexp.MustCompile("^.*\\._Ctype_char$") + + // cUnsignedCharRE is a regular expression that matches a cgo unsigned + // char. It is used to detect unsigned character arrays to hexdump + // them. + cUnsignedCharRE = regexp.MustCompile("^.*\\._Ctype_unsignedchar$") + + // cUint8tCharRE is a regular expression that matches a cgo uint8_t. + // It is used to detect uint8_t arrays to hexdump them. + cUint8tCharRE = regexp.MustCompile("^.*\\._Ctype_uint8_t$") +) + +// dumpState contains information about the state of a dump operation. +type dumpState struct { + w io.Writer + depth int + pointers map[uintptr]int + ignoreNextType bool + ignoreNextIndent bool + cs *ConfigState +} + +// indent performs indentation according to the depth level and cs.Indent +// option. +func (d *dumpState) indent() { + if d.ignoreNextIndent { + d.ignoreNextIndent = false + return + } + d.w.Write(bytes.Repeat([]byte(d.cs.Indent), d.depth)) +} + +// unpackValue returns values inside of non-nil interfaces when possible. +// This is useful for data types like structs, arrays, slices, and maps which +// can contain varying types packed inside an interface. +func (d *dumpState) unpackValue(v reflect.Value) reflect.Value { + if v.Kind() == reflect.Interface && !v.IsNil() { + v = v.Elem() + } + return v +} + +// dumpPtr handles formatting of pointers by indirecting them as necessary. +func (d *dumpState) dumpPtr(v reflect.Value) { + // Remove pointers at or below the current depth from map used to detect + // circular refs. + for k, depth := range d.pointers { + if depth >= d.depth { + delete(d.pointers, k) + } + } + + // Keep list of all dereferenced pointers to show later. + pointerChain := make([]uintptr, 0) + + // Figure out how many levels of indirection there are by dereferencing + // pointers and unpacking interfaces down the chain while detecting circular + // references. + nilFound := false + cycleFound := false + indirects := 0 + ve := v + for ve.Kind() == reflect.Ptr { + if ve.IsNil() { + nilFound = true + break + } + indirects++ + addr := ve.Pointer() + pointerChain = append(pointerChain, addr) + if pd, ok := d.pointers[addr]; ok && pd < d.depth { + cycleFound = true + indirects-- + break + } + d.pointers[addr] = d.depth + + ve = ve.Elem() + if ve.Kind() == reflect.Interface { + if ve.IsNil() { + nilFound = true + break + } + ve = ve.Elem() + } + } + + // Display type information. + d.w.Write(openParenBytes) + d.w.Write(bytes.Repeat(asteriskBytes, indirects)) + d.w.Write([]byte(ve.Type().String())) + d.w.Write(closeParenBytes) + + // Display pointer information. + if len(pointerChain) > 0 { + d.w.Write(openParenBytes) + for i, addr := range pointerChain { + if i > 0 { + d.w.Write(pointerChainBytes) + } + printHexPtr(d.w, addr) + } + d.w.Write(closeParenBytes) + } + + // Display dereferenced value. + d.w.Write(openParenBytes) + switch { + case nilFound == true: + d.w.Write(nilAngleBytes) + + case cycleFound == true: + d.w.Write(circularBytes) + + default: + d.ignoreNextType = true + d.dump(ve) + } + d.w.Write(closeParenBytes) +} + +// dumpSlice handles formatting of arrays and slices. Byte (uint8 under +// reflection) arrays and slices are dumped in hexdump -C fashion. +func (d *dumpState) dumpSlice(v reflect.Value) { + // Determine whether this type should be hex dumped or not. Also, + // for types which should be hexdumped, try to use the underlying data + // first, then fall back to trying to convert them to a uint8 slice. + var buf []uint8 + doConvert := false + doHexDump := false + numEntries := v.Len() + if numEntries > 0 { + vt := v.Index(0).Type() + vts := vt.String() + switch { + // C types that need to be converted. + case cCharRE.MatchString(vts): + fallthrough + case cUnsignedCharRE.MatchString(vts): + fallthrough + case cUint8tCharRE.MatchString(vts): + doConvert = true + + // Try to use existing uint8 slices and fall back to converting + // and copying if that fails. + case vt.Kind() == reflect.Uint8: + // TODO(davec): Fix up the disableUnsafe bits... + + // We need an addressable interface to convert the type + // to a byte slice. However, the reflect package won't + // give us an interface on certain things like + // unexported struct fields in order to enforce + // visibility rules. We use unsafe, when available, to + // bypass these restrictions since this package does not + // mutate the values. + vs := v + if !vs.CanInterface() || !vs.CanAddr() { + vs = unsafeReflectValue(vs) + } + if !UnsafeDisabled { + vs = vs.Slice(0, numEntries) + + // Use the existing uint8 slice if it can be + // type asserted. + iface := vs.Interface() + if slice, ok := iface.([]uint8); ok { + buf = slice + doHexDump = true + break + } + } + + // The underlying data needs to be converted if it can't + // be type asserted to a uint8 slice. + doConvert = true + } + + // Copy and convert the underlying type if needed. + if doConvert && vt.ConvertibleTo(uint8Type) { + // Convert and copy each element into a uint8 byte + // slice. + buf = make([]uint8, numEntries) + for i := 0; i < numEntries; i++ { + vv := v.Index(i) + buf[i] = uint8(vv.Convert(uint8Type).Uint()) + } + doHexDump = true + } + } + + // Hexdump the entire slice as needed. + if doHexDump { + indent := strings.Repeat(d.cs.Indent, d.depth) + str := indent + hex.Dump(buf) + str = strings.Replace(str, "\n", "\n"+indent, -1) + str = strings.TrimRight(str, d.cs.Indent) + d.w.Write([]byte(str)) + return + } + + // Recursively call dump for each item. + for i := 0; i < numEntries; i++ { + d.dump(d.unpackValue(v.Index(i))) + if i < (numEntries - 1) { + d.w.Write(commaNewlineBytes) + } else { + d.w.Write(newlineBytes) + } + } +} + +// dump is the main workhorse for dumping a value. It uses the passed reflect +// value to figure out what kind of object we are dealing with and formats it +// appropriately. It is a recursive function, however circular data structures +// are detected and handled properly. +func (d *dumpState) dump(v reflect.Value) { + // Handle invalid reflect values immediately. + kind := v.Kind() + if kind == reflect.Invalid { + d.w.Write(invalidAngleBytes) + return + } + + // Handle pointers specially. + if kind == reflect.Ptr { + d.indent() + d.dumpPtr(v) + return + } + + // Print type information unless already handled elsewhere. + if !d.ignoreNextType { + d.indent() + d.w.Write(openParenBytes) + d.w.Write([]byte(v.Type().String())) + d.w.Write(closeParenBytes) + d.w.Write(spaceBytes) + } + d.ignoreNextType = false + + // Display length and capacity if the built-in len and cap functions + // work with the value's kind and the len/cap itself is non-zero. + valueLen, valueCap := 0, 0 + switch v.Kind() { + case reflect.Array, reflect.Slice, reflect.Chan: + valueLen, valueCap = v.Len(), v.Cap() + case reflect.Map, reflect.String: + valueLen = v.Len() + } + if valueLen != 0 || valueCap != 0 { + d.w.Write(openParenBytes) + if valueLen != 0 { + d.w.Write(lenEqualsBytes) + printInt(d.w, int64(valueLen), 10) + } + if valueCap != 0 { + if valueLen != 0 { + d.w.Write(spaceBytes) + } + d.w.Write(capEqualsBytes) + printInt(d.w, int64(valueCap), 10) + } + d.w.Write(closeParenBytes) + d.w.Write(spaceBytes) + } + + // Call Stringer/error interfaces if they exist and the handle methods flag + // is enabled + if !d.cs.DisableMethods { + if (kind != reflect.Invalid) && (kind != reflect.Interface) { + if handled := handleMethods(d.cs, d.w, v); handled { + return + } + } + } + + switch kind { + case reflect.Invalid: + // Do nothing. We should never get here since invalid has already + // been handled above. + + case reflect.Bool: + printBool(d.w, v.Bool()) + + case reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64, reflect.Int: + printInt(d.w, v.Int(), 10) + + case reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uint: + printUint(d.w, v.Uint(), 10) + + case reflect.Float32: + printFloat(d.w, v.Float(), 32) + + case reflect.Float64: + printFloat(d.w, v.Float(), 64) + + case reflect.Complex64: + printComplex(d.w, v.Complex(), 32) + + case reflect.Complex128: + printComplex(d.w, v.Complex(), 64) + + case reflect.Slice: + if v.IsNil() { + d.w.Write(nilAngleBytes) + break + } + fallthrough + + case reflect.Array: + d.w.Write(openBraceNewlineBytes) + d.depth++ + if (d.cs.MaxDepth != 0) && (d.depth > d.cs.MaxDepth) { + d.indent() + d.w.Write(maxNewlineBytes) + } else { + d.dumpSlice(v) + } + d.depth-- + d.indent() + d.w.Write(closeBraceBytes) + + case reflect.String: + d.w.Write([]byte(strconv.Quote(v.String()))) + + case reflect.Interface: + // The only time we should get here is for nil interfaces due to + // unpackValue calls. + if v.IsNil() { + d.w.Write(nilAngleBytes) + } + + case reflect.Ptr: + // Do nothing. We should never get here since pointers have already + // been handled above. + + case reflect.Map: + // nil maps should be indicated as different than empty maps + if v.IsNil() { + d.w.Write(nilAngleBytes) + break + } + + d.w.Write(openBraceNewlineBytes) + d.depth++ + if (d.cs.MaxDepth != 0) && (d.depth > d.cs.MaxDepth) { + d.indent() + d.w.Write(maxNewlineBytes) + } else { + numEntries := v.Len() + keys := v.MapKeys() + if d.cs.SortKeys { + sortValues(keys, d.cs) + } + for i, key := range keys { + d.dump(d.unpackValue(key)) + d.w.Write(colonSpaceBytes) + d.ignoreNextIndent = true + d.dump(d.unpackValue(v.MapIndex(key))) + if i < (numEntries - 1) { + d.w.Write(commaNewlineBytes) + } else { + d.w.Write(newlineBytes) + } + } + } + d.depth-- + d.indent() + d.w.Write(closeBraceBytes) + + case reflect.Struct: + d.w.Write(openBraceNewlineBytes) + d.depth++ + if (d.cs.MaxDepth != 0) && (d.depth > d.cs.MaxDepth) { + d.indent() + d.w.Write(maxNewlineBytes) + } else { + vt := v.Type() + numFields := v.NumField() + for i := 0; i < numFields; i++ { + d.indent() + vtf := vt.Field(i) + d.w.Write([]byte(vtf.Name)) + d.w.Write(colonSpaceBytes) + d.ignoreNextIndent = true + d.dump(d.unpackValue(v.Field(i))) + if i < (numFields - 1) { + d.w.Write(commaNewlineBytes) + } else { + d.w.Write(newlineBytes) + } + } + } + d.depth-- + d.indent() + d.w.Write(closeBraceBytes) + + case reflect.Uintptr: + printHexPtr(d.w, uintptr(v.Uint())) + + case reflect.UnsafePointer, reflect.Chan, reflect.Func: + printHexPtr(d.w, v.Pointer()) + + // There were not any other types at the time this code was written, but + // fall back to letting the default fmt package handle it in case any new + // types are added. + default: + if v.CanInterface() { + fmt.Fprintf(d.w, "%v", v.Interface()) + } else { + fmt.Fprintf(d.w, "%v", v.String()) + } + } +} + +// fdump is a helper function to consolidate the logic from the various public +// methods which take varying writers and config states. +func fdump(cs *ConfigState, w io.Writer, a ...interface{}) { + for _, arg := range a { + if arg == nil { + w.Write(interfaceBytes) + w.Write(spaceBytes) + w.Write(nilAngleBytes) + w.Write(newlineBytes) + continue + } + + d := dumpState{w: w, cs: cs} + d.pointers = make(map[uintptr]int) + d.dump(reflect.ValueOf(arg)) + d.w.Write(newlineBytes) + } +} + +// Fdump formats and displays the passed arguments to io.Writer w. It formats +// exactly the same as Dump. +func Fdump(w io.Writer, a ...interface{}) { + fdump(&Config, w, a...) +} + +// Sdump returns a string with the passed arguments formatted exactly the same +// as Dump. +func Sdump(a ...interface{}) string { + var buf bytes.Buffer + fdump(&Config, &buf, a...) + return buf.String() +} + +/* +Dump displays the passed parameters to standard out with newlines, customizable +indentation, and additional debug information such as complete types and all +pointer addresses used to indirect to the final value. It provides the +following features over the built-in printing facilities provided by the fmt +package: + + * Pointers are dereferenced and followed + * Circular data structures are detected and handled properly + * Custom Stringer/error interfaces are optionally invoked, including + on unexported types + * Custom types which only implement the Stringer/error interfaces via + a pointer receiver are optionally invoked when passing non-pointer + variables + * Byte arrays and slices are dumped like the hexdump -C command which + includes offsets, byte values in hex, and ASCII output + +The configuration options are controlled by an exported package global, +spew.Config. See ConfigState for options documentation. + +See Fdump if you would prefer dumping to an arbitrary io.Writer or Sdump to +get the formatted result as a string. +*/ +func Dump(a ...interface{}) { + fdump(&Config, os.Stdout, a...) +} diff --git a/vendor/github.com/davecgh/go-spew/spew/format.go b/vendor/github.com/davecgh/go-spew/spew/format.go new file mode 100644 index 000000000..ecf3b80e2 --- /dev/null +++ b/vendor/github.com/davecgh/go-spew/spew/format.go @@ -0,0 +1,419 @@ +/* + * Copyright (c) 2013 Dave Collins + * + * Permission to use, copy, modify, and distribute this software for any + * purpose with or without fee is hereby granted, provided that the above + * copyright notice and this permission notice appear in all copies. + * + * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES + * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR + * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES + * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN + * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF + * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + */ + +package spew + +import ( + "bytes" + "fmt" + "reflect" + "strconv" + "strings" +) + +// supportedFlags is a list of all the character flags supported by fmt package. +const supportedFlags = "0-+# " + +// formatState implements the fmt.Formatter interface and contains information +// about the state of a formatting operation. The NewFormatter function can +// be used to get a new Formatter which can be used directly as arguments +// in standard fmt package printing calls. +type formatState struct { + value interface{} + fs fmt.State + depth int + pointers map[uintptr]int + ignoreNextType bool + cs *ConfigState +} + +// buildDefaultFormat recreates the original format string without precision +// and width information to pass in to fmt.Sprintf in the case of an +// unrecognized type. Unless new types are added to the language, this +// function won't ever be called. +func (f *formatState) buildDefaultFormat() (format string) { + buf := bytes.NewBuffer(percentBytes) + + for _, flag := range supportedFlags { + if f.fs.Flag(int(flag)) { + buf.WriteRune(flag) + } + } + + buf.WriteRune('v') + + format = buf.String() + return format +} + +// constructOrigFormat recreates the original format string including precision +// and width information to pass along to the standard fmt package. This allows +// automatic deferral of all format strings this package doesn't support. +func (f *formatState) constructOrigFormat(verb rune) (format string) { + buf := bytes.NewBuffer(percentBytes) + + for _, flag := range supportedFlags { + if f.fs.Flag(int(flag)) { + buf.WriteRune(flag) + } + } + + if width, ok := f.fs.Width(); ok { + buf.WriteString(strconv.Itoa(width)) + } + + if precision, ok := f.fs.Precision(); ok { + buf.Write(precisionBytes) + buf.WriteString(strconv.Itoa(precision)) + } + + buf.WriteRune(verb) + + format = buf.String() + return format +} + +// unpackValue returns values inside of non-nil interfaces when possible and +// ensures that types for values which have been unpacked from an interface +// are displayed when the show types flag is also set. +// This is useful for data types like structs, arrays, slices, and maps which +// can contain varying types packed inside an interface. +func (f *formatState) unpackValue(v reflect.Value) reflect.Value { + if v.Kind() == reflect.Interface { + f.ignoreNextType = false + if !v.IsNil() { + v = v.Elem() + } + } + return v +} + +// formatPtr handles formatting of pointers by indirecting them as necessary. +func (f *formatState) formatPtr(v reflect.Value) { + // Display nil if top level pointer is nil. + showTypes := f.fs.Flag('#') + if v.IsNil() && (!showTypes || f.ignoreNextType) { + f.fs.Write(nilAngleBytes) + return + } + + // Remove pointers at or below the current depth from map used to detect + // circular refs. + for k, depth := range f.pointers { + if depth >= f.depth { + delete(f.pointers, k) + } + } + + // Keep list of all dereferenced pointers to possibly show later. + pointerChain := make([]uintptr, 0) + + // Figure out how many levels of indirection there are by derferencing + // pointers and unpacking interfaces down the chain while detecting circular + // references. + nilFound := false + cycleFound := false + indirects := 0 + ve := v + for ve.Kind() == reflect.Ptr { + if ve.IsNil() { + nilFound = true + break + } + indirects++ + addr := ve.Pointer() + pointerChain = append(pointerChain, addr) + if pd, ok := f.pointers[addr]; ok && pd < f.depth { + cycleFound = true + indirects-- + break + } + f.pointers[addr] = f.depth + + ve = ve.Elem() + if ve.Kind() == reflect.Interface { + if ve.IsNil() { + nilFound = true + break + } + ve = ve.Elem() + } + } + + // Display type or indirection level depending on flags. + if showTypes && !f.ignoreNextType { + f.fs.Write(openParenBytes) + f.fs.Write(bytes.Repeat(asteriskBytes, indirects)) + f.fs.Write([]byte(ve.Type().String())) + f.fs.Write(closeParenBytes) + } else { + if nilFound || cycleFound { + indirects += strings.Count(ve.Type().String(), "*") + } + f.fs.Write(openAngleBytes) + f.fs.Write([]byte(strings.Repeat("*", indirects))) + f.fs.Write(closeAngleBytes) + } + + // Display pointer information depending on flags. + if f.fs.Flag('+') && (len(pointerChain) > 0) { + f.fs.Write(openParenBytes) + for i, addr := range pointerChain { + if i > 0 { + f.fs.Write(pointerChainBytes) + } + printHexPtr(f.fs, addr) + } + f.fs.Write(closeParenBytes) + } + + // Display dereferenced value. + switch { + case nilFound == true: + f.fs.Write(nilAngleBytes) + + case cycleFound == true: + f.fs.Write(circularShortBytes) + + default: + f.ignoreNextType = true + f.format(ve) + } +} + +// format is the main workhorse for providing the Formatter interface. It +// uses the passed reflect value to figure out what kind of object we are +// dealing with and formats it appropriately. It is a recursive function, +// however circular data structures are detected and handled properly. +func (f *formatState) format(v reflect.Value) { + // Handle invalid reflect values immediately. + kind := v.Kind() + if kind == reflect.Invalid { + f.fs.Write(invalidAngleBytes) + return + } + + // Handle pointers specially. + if kind == reflect.Ptr { + f.formatPtr(v) + return + } + + // Print type information unless already handled elsewhere. + if !f.ignoreNextType && f.fs.Flag('#') { + f.fs.Write(openParenBytes) + f.fs.Write([]byte(v.Type().String())) + f.fs.Write(closeParenBytes) + } + f.ignoreNextType = false + + // Call Stringer/error interfaces if they exist and the handle methods + // flag is enabled. + if !f.cs.DisableMethods { + if (kind != reflect.Invalid) && (kind != reflect.Interface) { + if handled := handleMethods(f.cs, f.fs, v); handled { + return + } + } + } + + switch kind { + case reflect.Invalid: + // Do nothing. We should never get here since invalid has already + // been handled above. + + case reflect.Bool: + printBool(f.fs, v.Bool()) + + case reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64, reflect.Int: + printInt(f.fs, v.Int(), 10) + + case reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uint: + printUint(f.fs, v.Uint(), 10) + + case reflect.Float32: + printFloat(f.fs, v.Float(), 32) + + case reflect.Float64: + printFloat(f.fs, v.Float(), 64) + + case reflect.Complex64: + printComplex(f.fs, v.Complex(), 32) + + case reflect.Complex128: + printComplex(f.fs, v.Complex(), 64) + + case reflect.Slice: + if v.IsNil() { + f.fs.Write(nilAngleBytes) + break + } + fallthrough + + case reflect.Array: + f.fs.Write(openBracketBytes) + f.depth++ + if (f.cs.MaxDepth != 0) && (f.depth > f.cs.MaxDepth) { + f.fs.Write(maxShortBytes) + } else { + numEntries := v.Len() + for i := 0; i < numEntries; i++ { + if i > 0 { + f.fs.Write(spaceBytes) + } + f.ignoreNextType = true + f.format(f.unpackValue(v.Index(i))) + } + } + f.depth-- + f.fs.Write(closeBracketBytes) + + case reflect.String: + f.fs.Write([]byte(v.String())) + + case reflect.Interface: + // The only time we should get here is for nil interfaces due to + // unpackValue calls. + if v.IsNil() { + f.fs.Write(nilAngleBytes) + } + + case reflect.Ptr: + // Do nothing. We should never get here since pointers have already + // been handled above. + + case reflect.Map: + // nil maps should be indicated as different than empty maps + if v.IsNil() { + f.fs.Write(nilAngleBytes) + break + } + + f.fs.Write(openMapBytes) + f.depth++ + if (f.cs.MaxDepth != 0) && (f.depth > f.cs.MaxDepth) { + f.fs.Write(maxShortBytes) + } else { + keys := v.MapKeys() + if f.cs.SortKeys { + sortValues(keys, f.cs) + } + for i, key := range keys { + if i > 0 { + f.fs.Write(spaceBytes) + } + f.ignoreNextType = true + f.format(f.unpackValue(key)) + f.fs.Write(colonBytes) + f.ignoreNextType = true + f.format(f.unpackValue(v.MapIndex(key))) + } + } + f.depth-- + f.fs.Write(closeMapBytes) + + case reflect.Struct: + numFields := v.NumField() + f.fs.Write(openBraceBytes) + f.depth++ + if (f.cs.MaxDepth != 0) && (f.depth > f.cs.MaxDepth) { + f.fs.Write(maxShortBytes) + } else { + vt := v.Type() + for i := 0; i < numFields; i++ { + if i > 0 { + f.fs.Write(spaceBytes) + } + vtf := vt.Field(i) + if f.fs.Flag('+') || f.fs.Flag('#') { + f.fs.Write([]byte(vtf.Name)) + f.fs.Write(colonBytes) + } + f.format(f.unpackValue(v.Field(i))) + } + } + f.depth-- + f.fs.Write(closeBraceBytes) + + case reflect.Uintptr: + printHexPtr(f.fs, uintptr(v.Uint())) + + case reflect.UnsafePointer, reflect.Chan, reflect.Func: + printHexPtr(f.fs, v.Pointer()) + + // There were not any other types at the time this code was written, but + // fall back to letting the default fmt package handle it if any get added. + default: + format := f.buildDefaultFormat() + if v.CanInterface() { + fmt.Fprintf(f.fs, format, v.Interface()) + } else { + fmt.Fprintf(f.fs, format, v.String()) + } + } +} + +// Format satisfies the fmt.Formatter interface. See NewFormatter for usage +// details. +func (f *formatState) Format(fs fmt.State, verb rune) { + f.fs = fs + + // Use standard formatting for verbs that are not v. + if verb != 'v' { + format := f.constructOrigFormat(verb) + fmt.Fprintf(fs, format, f.value) + return + } + + if f.value == nil { + if fs.Flag('#') { + fs.Write(interfaceBytes) + } + fs.Write(nilAngleBytes) + return + } + + f.format(reflect.ValueOf(f.value)) +} + +// newFormatter is a helper function to consolidate the logic from the various +// public methods which take varying config states. +func newFormatter(cs *ConfigState, v interface{}) fmt.Formatter { + fs := &formatState{value: v, cs: cs} + fs.pointers = make(map[uintptr]int) + return fs +} + +/* +NewFormatter returns a custom formatter that satisfies the fmt.Formatter +interface. As a result, it integrates cleanly with standard fmt package +printing functions. The formatter is useful for inline printing of smaller data +types similar to the standard %v format specifier. + +The custom formatter only responds to the %v (most compact), %+v (adds pointer +addresses), %#v (adds types), or %#+v (adds types and pointer addresses) verb +combinations. Any other verbs such as %x and %q will be sent to the the +standard fmt package for formatting. In addition, the custom formatter ignores +the width and precision arguments (however they will still work on the format +specifiers not handled by the custom formatter). + +Typically this function shouldn't be called directly. It is much easier to make +use of the custom formatter by calling one of the convenience functions such as +Printf, Println, or Fprintf. +*/ +func NewFormatter(v interface{}) fmt.Formatter { + return newFormatter(&Config, v) +} diff --git a/vendor/github.com/davecgh/go-spew/spew/spew.go b/vendor/github.com/davecgh/go-spew/spew/spew.go new file mode 100644 index 000000000..d8233f542 --- /dev/null +++ b/vendor/github.com/davecgh/go-spew/spew/spew.go @@ -0,0 +1,148 @@ +/* + * Copyright (c) 2013 Dave Collins + * + * Permission to use, copy, modify, and distribute this software for any + * purpose with or without fee is hereby granted, provided that the above + * copyright notice and this permission notice appear in all copies. + * + * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES + * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR + * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES + * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN + * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF + * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + */ + +package spew + +import ( + "fmt" + "io" +) + +// Errorf is a wrapper for fmt.Errorf that treats each argument as if it were +// passed with a default Formatter interface returned by NewFormatter. It +// returns the formatted string as a value that satisfies error. See +// NewFormatter for formatting details. +// +// This function is shorthand for the following syntax: +// +// fmt.Errorf(format, spew.NewFormatter(a), spew.NewFormatter(b)) +func Errorf(format string, a ...interface{}) (err error) { + return fmt.Errorf(format, convertArgs(a)...) +} + +// Fprint is a wrapper for fmt.Fprint that treats each argument as if it were +// passed with a default Formatter interface returned by NewFormatter. It +// returns the number of bytes written and any write error encountered. See +// NewFormatter for formatting details. +// +// This function is shorthand for the following syntax: +// +// fmt.Fprint(w, spew.NewFormatter(a), spew.NewFormatter(b)) +func Fprint(w io.Writer, a ...interface{}) (n int, err error) { + return fmt.Fprint(w, convertArgs(a)...) +} + +// Fprintf is a wrapper for fmt.Fprintf that treats each argument as if it were +// passed with a default Formatter interface returned by NewFormatter. It +// returns the number of bytes written and any write error encountered. See +// NewFormatter for formatting details. +// +// This function is shorthand for the following syntax: +// +// fmt.Fprintf(w, format, spew.NewFormatter(a), spew.NewFormatter(b)) +func Fprintf(w io.Writer, format string, a ...interface{}) (n int, err error) { + return fmt.Fprintf(w, format, convertArgs(a)...) +} + +// Fprintln is a wrapper for fmt.Fprintln that treats each argument as if it +// passed with a default Formatter interface returned by NewFormatter. See +// NewFormatter for formatting details. +// +// This function is shorthand for the following syntax: +// +// fmt.Fprintln(w, spew.NewFormatter(a), spew.NewFormatter(b)) +func Fprintln(w io.Writer, a ...interface{}) (n int, err error) { + return fmt.Fprintln(w, convertArgs(a)...) +} + +// Print is a wrapper for fmt.Print that treats each argument as if it were +// passed with a default Formatter interface returned by NewFormatter. It +// returns the number of bytes written and any write error encountered. See +// NewFormatter for formatting details. +// +// This function is shorthand for the following syntax: +// +// fmt.Print(spew.NewFormatter(a), spew.NewFormatter(b)) +func Print(a ...interface{}) (n int, err error) { + return fmt.Print(convertArgs(a)...) +} + +// Printf is a wrapper for fmt.Printf that treats each argument as if it were +// passed with a default Formatter interface returned by NewFormatter. It +// returns the number of bytes written and any write error encountered. See +// NewFormatter for formatting details. +// +// This function is shorthand for the following syntax: +// +// fmt.Printf(format, spew.NewFormatter(a), spew.NewFormatter(b)) +func Printf(format string, a ...interface{}) (n int, err error) { + return fmt.Printf(format, convertArgs(a)...) +} + +// Println is a wrapper for fmt.Println that treats each argument as if it were +// passed with a default Formatter interface returned by NewFormatter. It +// returns the number of bytes written and any write error encountered. See +// NewFormatter for formatting details. +// +// This function is shorthand for the following syntax: +// +// fmt.Println(spew.NewFormatter(a), spew.NewFormatter(b)) +func Println(a ...interface{}) (n int, err error) { + return fmt.Println(convertArgs(a)...) +} + +// Sprint is a wrapper for fmt.Sprint that treats each argument as if it were +// passed with a default Formatter interface returned by NewFormatter. It +// returns the resulting string. See NewFormatter for formatting details. +// +// This function is shorthand for the following syntax: +// +// fmt.Sprint(spew.NewFormatter(a), spew.NewFormatter(b)) +func Sprint(a ...interface{}) string { + return fmt.Sprint(convertArgs(a)...) +} + +// Sprintf is a wrapper for fmt.Sprintf that treats each argument as if it were +// passed with a default Formatter interface returned by NewFormatter. It +// returns the resulting string. See NewFormatter for formatting details. +// +// This function is shorthand for the following syntax: +// +// fmt.Sprintf(format, spew.NewFormatter(a), spew.NewFormatter(b)) +func Sprintf(format string, a ...interface{}) string { + return fmt.Sprintf(format, convertArgs(a)...) +} + +// Sprintln is a wrapper for fmt.Sprintln that treats each argument as if it +// were passed with a default Formatter interface returned by NewFormatter. It +// returns the resulting string. See NewFormatter for formatting details. +// +// This function is shorthand for the following syntax: +// +// fmt.Sprintln(spew.NewFormatter(a), spew.NewFormatter(b)) +func Sprintln(a ...interface{}) string { + return fmt.Sprintln(convertArgs(a)...) +} + +// convertArgs accepts a slice of arguments and returns a slice of the same +// length with each argument converted to a default spew Formatter interface. +func convertArgs(args []interface{}) (formatters []interface{}) { + formatters = make([]interface{}, len(args)) + for index, arg := range args { + formatters[index] = NewFormatter(arg) + } + return formatters +} diff --git a/vendor/github.com/denisenkom/go-mssqldb/README.md b/vendor/github.com/denisenkom/go-mssqldb/README.md deleted file mode 100644 index 50e659209..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/README.md +++ /dev/null @@ -1,83 +0,0 @@ -# A pure Go MSSQL driver for Go's database/sql package - -## Install - - go get github.com/denisenkom/go-mssqldb - -## Tests - -`go test` is used for testing. A running instance of MSSQL server is required. -Environment variables are used to pass login information. - -Example: - - env HOST=localhost SQLUSER=sa SQLPASSWORD=sa DATABASE=test go test - -## Connection Parameters - -* "server" - host or host\instance (default localhost) -* "port" - used only when there is no instance in server (default 1433) -* "failoverpartner" - host or host\instance (default is no partner). Used only until a successful connection has been made; thereafter, the partner provided in the first successful connection is used. -* "failoverport" - used only when there is no instance in failoverpartner (default 1433) -* "user id" - enter the SQL Server Authentication user id or the Windows Authentication user id in the DOMAIN\User format. On Windows, if user id is empty or missing Single-Sign-On is used. -* "password" -* "database" -* "connection timeout" - in seconds (default is 30) -* "dial timeout" - in seconds (default is 5) -* "keepAlive" - in seconds; 0 to disable (default is 0) -* "log" - logging flags (default 0/no logging, 63 for full logging) - * 1 log errors - * 2 log messages - * 4 log rows affected - * 8 trace sql statements - * 16 log statement parameters - * 32 log transaction begin/end -* "encrypt" - * disable - Data send between client and server is not encrypted. - * false - Data sent between client and server is not encrypted beyond the login packet. (Default) - * true - Data sent between client and server is encrypted. -* "TrustServerCertificate" - * false - Server certificate is checked. Default is false if encypt is specified. - * true - Server certificate is not checked. Default is true if encrypt is not specified. If trust server certificate is true, driver accepts any certificate presented by the server and any host name in that certificate. In this mode, TLS is susceptible to man-in-the-middle attacks. This should be used only for testing. -* "certificate" - The file that contains the public key certificate of the CA that signed the SQL Server certificate. The specified certificate overrides the go platform specific CA certificates. -* "hostNameInCertificate" - Specifies the Common Name (CN) in the server certificate. Default value is the server host. -* "ServerSPN" - The kerberos SPN (Service Principal Name) for the server. Default is MSSQLSvc/host:port. -* "Workstation ID" - The workstation name (default is the host name) -* "app name" - The application name (default is go-mssqldb) -* "ApplicationIntent" - Can be given the value "ReadOnly" to initiate a read-only connection to an Availability Group listener. - -Example: - -```go - db, err := sql.Open("mssql", "server=localhost;user id=sa") -``` - -## Statement Parameters - -In the SQL statement text, literals may be replaced by a parameter that matches one of the following: - -* ? -* ?nnn -* :nnn -* $nnn - -where nnn represents an integer. - -## Features - -* Can be used with SQL Server 2005 or newer -* Can be used with Microsoft Azure SQL Database -* Can be used on all go supported platforms (e.g. Linux, Mac OS X and Windows) -* Supports new date/time types: date, time, datetime2, datetimeoffset -* Supports string parameters longer than 8000 characters -* Supports encryption using SSL/TLS -* Supports SQL Server and Windows Authentication -* Supports Single-Sign-On on Windows -* Supports connections to AlwaysOn Availability Group listeners, including re-direction to read-only replicas. - -## Known Issues - -* SQL Server 2008 and 2008 R2 engine cannot handle login records when SSL encryption is not disabled. -To fix SQL Server 2008 R2 issue, install SQL Server 2008 R2 Service Pack 2. -To fix SQL Server 2008 issue, install Microsoft SQL Server 2008 Service Pack 3 and Cumulative update package 3 for SQL Server 2008 SP3. -More information: http://support.microsoft.com/kb/2653857 diff --git a/vendor/github.com/denisenkom/go-mssqldb/buf.go b/vendor/github.com/denisenkom/go-mssqldb/buf.go deleted file mode 100644 index 4fb2c4798..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/buf.go +++ /dev/null @@ -1,212 +0,0 @@ -package mssql - -import ( - "encoding/binary" - "io" -) - -type header struct { - PacketType uint8 - Status uint8 - Size uint16 - Spid uint16 - PacketNo uint8 - Pad uint8 -} - -type tdsBuffer struct { - buf []byte - pos uint16 - transport io.ReadWriteCloser - size uint16 - final bool - packet_type uint8 - afterFirst func() -} - -func newTdsBuffer(bufsize int, transport io.ReadWriteCloser) *tdsBuffer { - buf := make([]byte, bufsize) - w := new(tdsBuffer) - w.buf = buf - w.pos = 8 - w.transport = transport - w.size = 0 - return w -} - -func (w *tdsBuffer) flush() (err error) { - binary.BigEndian.PutUint16(w.buf[2:], w.pos) - if _, err = w.transport.Write(w.buf[:w.pos]); err != nil { - return err - } - if w.afterFirst != nil { - w.afterFirst() - w.afterFirst = nil - } - w.pos = 8 - w.buf[6] += 1 - return nil -} - -func (w *tdsBuffer) Write(p []byte) (nn int, err error) { - total := 0 - for { - copied := copy(w.buf[w.pos:], p) - w.pos += uint16(copied) - total += copied - if copied == len(p) { - break - } - if err = w.flush(); err != nil { - return total, err - } - p = p[copied:] - } - return total, nil -} - -func (w *tdsBuffer) WriteByte(b byte) error { - if int(w.pos) == len(w.buf) { - if err := w.flush(); err != nil { - return err - } - } - w.buf[w.pos] = b - w.pos += 1 - return nil -} - -func (w *tdsBuffer) BeginPacket(packet_type byte) { - w.buf[0] = packet_type - w.buf[1] = 0 // packet is incomplete - w.buf[4] = 0 // spid - w.buf[5] = 0 - w.buf[6] = 1 // packet id - w.buf[7] = 0 // window - w.pos = 8 -} - -func (w *tdsBuffer) FinishPacket() (err error) { - w.buf[1] = 1 // packet is complete - binary.BigEndian.PutUint16(w.buf[2:], w.pos) - _, err = w.transport.Write(w.buf[:w.pos]) - if w.afterFirst != nil { - w.afterFirst() - w.afterFirst = nil - } - return err -} - -func (r *tdsBuffer) readNextPacket() error { - header := header{} - var err error - err = binary.Read(r.transport, binary.BigEndian, &header) - if err != nil { - return err - } - offset := uint16(binary.Size(header)) - _, err = io.ReadFull(r.transport, r.buf[offset:header.Size]) - if err != nil { - return err - } - r.pos = offset - r.size = header.Size - r.final = header.Status != 0 - r.packet_type = header.PacketType - return nil -} - -func (r *tdsBuffer) BeginRead() (uint8, error) { - err := r.readNextPacket() - if err != nil { - return 0, err - } - return r.packet_type, nil -} - -func (r *tdsBuffer) ReadByte() (res byte, err error) { - if r.pos == r.size { - if r.final { - return 0, io.EOF - } - err = r.readNextPacket() - if err != nil { - return 0, err - } - } - res = r.buf[r.pos] - r.pos++ - return res, nil -} - -func (r *tdsBuffer) byte() byte { - b, err := r.ReadByte() - if err != nil { - badStreamPanic(err) - } - return b -} - -func (r *tdsBuffer) ReadFull(buf []byte) { - _, err := io.ReadFull(r, buf[:]) - if err != nil { - badStreamPanic(err) - } -} - -func (r *tdsBuffer) uint64() uint64 { - var buf [8]byte - r.ReadFull(buf[:]) - return binary.LittleEndian.Uint64(buf[:]) -} - -func (r *tdsBuffer) int32() int32 { - return int32(r.uint32()) -} - -func (r *tdsBuffer) uint32() uint32 { - var buf [4]byte - r.ReadFull(buf[:]) - return binary.LittleEndian.Uint32(buf[:]) -} - -func (r *tdsBuffer) uint16() uint16 { - var buf [2]byte - r.ReadFull(buf[:]) - return binary.LittleEndian.Uint16(buf[:]) -} - -func (r *tdsBuffer) BVarChar() string { - l := int(r.byte()) - return r.readUcs2(l) -} - -func (r *tdsBuffer) UsVarChar() string { - l := int(r.uint16()) - return r.readUcs2(l) -} - -func (r *tdsBuffer) readUcs2(numchars int) string { - b := make([]byte, numchars*2) - r.ReadFull(b) - res, err := ucs22str(b) - if err != nil { - badStreamPanic(err) - } - return res -} - -func (r *tdsBuffer) Read(buf []byte) (n int, err error) { - if r.pos == r.size { - if r.final { - return 0, io.EOF - } - err = r.readNextPacket() - if err != nil { - return 0, err - } - } - copied := copy(buf, r.buf[r.pos:r.size]) - r.pos += uint16(copied) - return copied, nil -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/charset.go b/vendor/github.com/denisenkom/go-mssqldb/charset.go deleted file mode 100644 index f1cc247a9..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/charset.go +++ /dev/null @@ -1,113 +0,0 @@ -package mssql - -type charsetMap struct { - sb [256]rune // single byte runes, -1 for a double byte character lead byte - db map[int]rune // double byte runes -} - -func collation2charset(col collation) *charsetMap { - // http://msdn.microsoft.com/en-us/library/ms144250.aspx - // http://msdn.microsoft.com/en-us/library/ms144250(v=sql.105).aspx - switch col.sortId { - case 30, 31, 32, 33, 34: - return cp437 - case 40, 41, 42, 44, 49, 55, 56, 57, 58, 59, 60, 61: - return cp850 - case 50, 51, 52, 53, 54, 71, 72, 73, 74, 75: - return cp1252 - case 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96: - return cp1250 - case 104, 105, 106, 107, 108: - return cp1251 - case 112, 113, 114, 121, 124: - return cp1253 - case 128, 129, 130: - return cp1254 - case 136, 137, 138: - return cp1255 - case 144, 145, 146: - return cp1256 - case 152, 153, 154, 155, 156, 157, 158, 159, 160: - return cp1257 - case 183, 184, 185, 186: - return cp1252 - case 192, 193: - return cp932 - case 194, 195: - return cp949 - case 196, 197: - return cp950 - case 198, 199: - return cp936 - case 200: - return cp932 - case 201: - return cp949 - case 202: - return cp950 - case 203: - return cp936 - case 204, 205, 206: - return cp874 - case 210, 211, 212, 213, 214, 215, 216, 217: - return cp1252 - } - // http://technet.microsoft.com/en-us/library/aa176553(v=sql.80).aspx - switch col.getLcid() { - case 0x001e, 0x041e: - return cp874 - case 0x0411, 0x10411: - return cp932 - case 0x0804, 0x1004, 0x20804: - return cp936 - case 0x0012, 0x0412: - return cp949 - case 0x0404, 0x1404, 0x0c04, 0x7c04, 0x30404: - return cp950 - case 0x041c, 0x041a, 0x0405, 0x040e, 0x104e, 0x0415, 0x0418, 0x041b, 0x0424, 0x1040e: - return cp1250 - case 0x0423, 0x0402, 0x042f, 0x0419, 0x081a, 0x0c1a, 0x0422, 0x043f, 0x0444, 0x082c: - return cp1251 - case 0x0408: - return cp1253 - case 0x041f, 0x042c, 0x0443: - return cp1254 - case 0x040d: - return cp1255 - case 0x0401, 0x0801, 0xc01, 0x1001, 0x1401, 0x1801, 0x1c01, 0x2001, 0x2401, 0x2801, 0x2c01, 0x3001, 0x3401, 0x3801, 0x3c01, 0x4001, 0x0429, 0x0420: - return cp1256 - case 0x0425, 0x0426, 0x0427, 0x0827: - return cp1257 - case 0x042a: - return cp1258 - case 0x0439, 0x045a, 0x0465: - return nil - } - return cp1252 -} - -func charset2utf8(col collation, s []byte) string { - cm := collation2charset(col) - if cm == nil { - return string(s) - } - buf := make([]rune, 0, len(s)) - for i := 0; i < len(s); i++ { - ch := cm.sb[s[i]] - if ch == -1 { - if i+1 == len(s) { - ch = 0xfffd - } else { - n := int(s[i+1]) + (int(s[i]) << 8) - i++ - var ok bool - ch, ok = cm.db[n] - if !ok { - ch = 0xfffd - } - } - } - buf = append(buf, ch) - } - return string(buf) -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/collation.go b/vendor/github.com/denisenkom/go-mssqldb/collation.go deleted file mode 100644 index ac9cf20b7..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/collation.go +++ /dev/null @@ -1,39 +0,0 @@ -package mssql - -import ( - "encoding/binary" - "io" -) - -// http://msdn.microsoft.com/en-us/library/dd340437.aspx - -type collation struct { - lcidAndFlags uint32 - sortId uint8 -} - -func (c collation) getLcid() uint32 { - return c.lcidAndFlags & 0x000fffff -} - -func (c collation) getFlags() uint32 { - return (c.lcidAndFlags & 0x0ff00000) >> 20 -} - -func (c collation) getVersion() uint32 { - return (c.lcidAndFlags & 0xf0000000) >> 28 -} - -func readCollation(r *tdsBuffer) (res collation) { - res.lcidAndFlags = r.uint32() - res.sortId = r.byte() - return -} - -func writeCollation(w io.Writer, col collation) (err error) { - if err = binary.Write(w, binary.LittleEndian, col.lcidAndFlags); err != nil { - return - } - err = binary.Write(w, binary.LittleEndian, col.sortId) - return -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/cp1250.go b/vendor/github.com/denisenkom/go-mssqldb/cp1250.go deleted file mode 100644 index 8207366be..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/cp1250.go +++ /dev/null @@ -1,262 +0,0 @@ -package mssql - -var cp1250 *charsetMap = &charsetMap{ - sb: [256]rune{ - 0x0000, //NULL - 0x0001, //START OF HEADING - 0x0002, //START OF TEXT - 0x0003, //END OF TEXT - 0x0004, //END OF TRANSMISSION - 0x0005, //ENQUIRY - 0x0006, //ACKNOWLEDGE - 0x0007, //BELL - 0x0008, //BACKSPACE - 0x0009, //HORIZONTAL TABULATION - 0x000A, //LINE FEED - 0x000B, //VERTICAL TABULATION - 0x000C, //FORM FEED - 0x000D, //CARRIAGE RETURN - 0x000E, //SHIFT OUT - 0x000F, //SHIFT IN - 0x0010, //DATA LINK ESCAPE - 0x0011, //DEVICE CONTROL ONE - 0x0012, //DEVICE CONTROL TWO - 0x0013, //DEVICE CONTROL THREE - 0x0014, //DEVICE CONTROL FOUR - 0x0015, //NEGATIVE ACKNOWLEDGE - 0x0016, //SYNCHRONOUS IDLE - 0x0017, //END OF TRANSMISSION BLOCK - 0x0018, //CANCEL - 0x0019, //END OF MEDIUM - 0x001A, //SUBSTITUTE - 0x001B, //ESCAPE - 0x001C, //FILE SEPARATOR - 0x001D, //GROUP SEPARATOR - 0x001E, //RECORD SEPARATOR - 0x001F, //UNIT SEPARATOR - 0x0020, //SPACE - 0x0021, //EXCLAMATION MARK - 0x0022, //QUOTATION MARK - 0x0023, //NUMBER SIGN - 0x0024, //DOLLAR SIGN - 0x0025, //PERCENT SIGN - 0x0026, //AMPERSAND - 0x0027, //APOSTROPHE - 0x0028, //LEFT PARENTHESIS - 0x0029, //RIGHT PARENTHESIS - 0x002A, //ASTERISK - 0x002B, //PLUS SIGN - 0x002C, //COMMA - 0x002D, //HYPHEN-MINUS - 0x002E, //FULL STOP - 0x002F, //SOLIDUS - 0x0030, //DIGIT ZERO - 0x0031, //DIGIT ONE - 0x0032, //DIGIT TWO - 0x0033, //DIGIT THREE - 0x0034, //DIGIT FOUR - 0x0035, //DIGIT FIVE - 0x0036, //DIGIT SIX - 0x0037, //DIGIT SEVEN - 0x0038, //DIGIT EIGHT - 0x0039, //DIGIT NINE - 0x003A, //COLON - 0x003B, //SEMICOLON - 0x003C, //LESS-THAN SIGN - 0x003D, //EQUALS SIGN - 0x003E, //GREATER-THAN SIGN - 0x003F, //QUESTION MARK - 0x0040, //COMMERCIAL AT - 0x0041, //LATIN CAPITAL LETTER A - 0x0042, //LATIN CAPITAL LETTER B - 0x0043, //LATIN CAPITAL LETTER C - 0x0044, //LATIN CAPITAL LETTER D - 0x0045, //LATIN CAPITAL LETTER E - 0x0046, //LATIN CAPITAL LETTER F - 0x0047, //LATIN CAPITAL LETTER G - 0x0048, //LATIN CAPITAL LETTER H - 0x0049, //LATIN CAPITAL LETTER I - 0x004A, //LATIN CAPITAL LETTER J - 0x004B, //LATIN CAPITAL LETTER K - 0x004C, //LATIN CAPITAL LETTER L - 0x004D, //LATIN CAPITAL LETTER M - 0x004E, //LATIN CAPITAL LETTER N - 0x004F, //LATIN CAPITAL LETTER O - 0x0050, //LATIN CAPITAL LETTER P - 0x0051, //LATIN CAPITAL LETTER Q - 0x0052, //LATIN CAPITAL LETTER R - 0x0053, //LATIN CAPITAL LETTER S - 0x0054, //LATIN CAPITAL LETTER T - 0x0055, //LATIN CAPITAL LETTER U - 0x0056, //LATIN CAPITAL LETTER V - 0x0057, //LATIN CAPITAL LETTER W - 0x0058, //LATIN CAPITAL LETTER X - 0x0059, //LATIN CAPITAL LETTER Y - 0x005A, //LATIN CAPITAL LETTER Z - 0x005B, //LEFT SQUARE BRACKET - 0x005C, //REVERSE SOLIDUS - 0x005D, //RIGHT SQUARE BRACKET - 0x005E, //CIRCUMFLEX ACCENT - 0x005F, //LOW LINE - 0x0060, //GRAVE ACCENT - 0x0061, //LATIN SMALL LETTER A - 0x0062, //LATIN SMALL LETTER B - 0x0063, //LATIN SMALL LETTER C - 0x0064, //LATIN SMALL LETTER D - 0x0065, //LATIN SMALL LETTER E - 0x0066, //LATIN SMALL LETTER F - 0x0067, //LATIN SMALL LETTER G - 0x0068, //LATIN SMALL LETTER H - 0x0069, //LATIN SMALL LETTER I - 0x006A, //LATIN SMALL LETTER J - 0x006B, //LATIN SMALL LETTER K - 0x006C, //LATIN SMALL LETTER L - 0x006D, //LATIN SMALL LETTER M - 0x006E, //LATIN SMALL LETTER N - 0x006F, //LATIN SMALL LETTER O - 0x0070, //LATIN SMALL LETTER P - 0x0071, //LATIN SMALL LETTER Q - 0x0072, //LATIN SMALL LETTER R - 0x0073, //LATIN SMALL LETTER S - 0x0074, //LATIN SMALL LETTER T - 0x0075, //LATIN SMALL LETTER U - 0x0076, //LATIN SMALL LETTER V - 0x0077, //LATIN SMALL LETTER W - 0x0078, //LATIN SMALL LETTER X - 0x0079, //LATIN SMALL LETTER Y - 0x007A, //LATIN SMALL LETTER Z - 0x007B, //LEFT CURLY BRACKET - 0x007C, //VERTICAL LINE - 0x007D, //RIGHT CURLY BRACKET - 0x007E, //TILDE - 0x007F, //DELETE - 0x20AC, //EURO SIGN - 0xFFFD, //UNDEFINED - 0x201A, //SINGLE LOW-9 QUOTATION MARK - 0xFFFD, //UNDEFINED - 0x201E, //DOUBLE LOW-9 QUOTATION MARK - 0x2026, //HORIZONTAL ELLIPSIS - 0x2020, //DAGGER - 0x2021, //DOUBLE DAGGER - 0xFFFD, //UNDEFINED - 0x2030, //PER MILLE SIGN - 0x0160, //LATIN CAPITAL LETTER S WITH CARON - 0x2039, //SINGLE LEFT-POINTING ANGLE QUOTATION MARK - 0x015A, //LATIN CAPITAL LETTER S WITH ACUTE - 0x0164, //LATIN CAPITAL LETTER T WITH CARON - 0x017D, //LATIN CAPITAL LETTER Z WITH CARON - 0x0179, //LATIN CAPITAL LETTER Z WITH ACUTE - 0xFFFD, //UNDEFINED - 0x2018, //LEFT SINGLE QUOTATION MARK - 0x2019, //RIGHT SINGLE QUOTATION MARK - 0x201C, //LEFT DOUBLE QUOTATION MARK - 0x201D, //RIGHT DOUBLE QUOTATION MARK - 0x2022, //BULLET - 0x2013, //EN DASH - 0x2014, //EM DASH - 0xFFFD, //UNDEFINED - 0x2122, //TRADE MARK SIGN - 0x0161, //LATIN SMALL LETTER S WITH CARON - 0x203A, //SINGLE RIGHT-POINTING ANGLE QUOTATION MARK - 0x015B, //LATIN SMALL LETTER S WITH ACUTE - 0x0165, //LATIN SMALL LETTER T WITH CARON - 0x017E, //LATIN SMALL LETTER Z WITH CARON - 0x017A, //LATIN SMALL LETTER Z WITH ACUTE - 0x00A0, //NO-BREAK SPACE - 0x02C7, //CARON - 0x02D8, //BREVE - 0x0141, //LATIN CAPITAL LETTER L WITH STROKE - 0x00A4, //CURRENCY SIGN - 0x0104, //LATIN CAPITAL LETTER A WITH OGONEK - 0x00A6, //BROKEN BAR - 0x00A7, //SECTION SIGN - 0x00A8, //DIAERESIS - 0x00A9, //COPYRIGHT SIGN - 0x015E, //LATIN CAPITAL LETTER S WITH CEDILLA - 0x00AB, //LEFT-POINTING DOUBLE ANGLE QUOTATION MARK - 0x00AC, //NOT SIGN - 0x00AD, //SOFT HYPHEN - 0x00AE, //REGISTERED SIGN - 0x017B, //LATIN CAPITAL LETTER Z WITH DOT ABOVE - 0x00B0, //DEGREE SIGN - 0x00B1, //PLUS-MINUS SIGN - 0x02DB, //OGONEK - 0x0142, //LATIN SMALL LETTER L WITH STROKE - 0x00B4, //ACUTE ACCENT - 0x00B5, //MICRO SIGN - 0x00B6, //PILCROW SIGN - 0x00B7, //MIDDLE DOT - 0x00B8, //CEDILLA - 0x0105, //LATIN SMALL LETTER A WITH OGONEK - 0x015F, //LATIN SMALL LETTER S WITH CEDILLA - 0x00BB, //RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK - 0x013D, //LATIN CAPITAL LETTER L WITH CARON - 0x02DD, //DOUBLE ACUTE ACCENT - 0x013E, //LATIN SMALL LETTER L WITH CARON - 0x017C, //LATIN SMALL LETTER Z WITH DOT ABOVE - 0x0154, //LATIN CAPITAL LETTER R WITH ACUTE - 0x00C1, //LATIN CAPITAL LETTER A WITH ACUTE - 0x00C2, //LATIN CAPITAL LETTER A WITH CIRCUMFLEX - 0x0102, //LATIN CAPITAL LETTER A WITH BREVE - 0x00C4, //LATIN CAPITAL LETTER A WITH DIAERESIS - 0x0139, //LATIN CAPITAL LETTER L WITH ACUTE - 0x0106, //LATIN CAPITAL LETTER C WITH ACUTE - 0x00C7, //LATIN CAPITAL LETTER C WITH CEDILLA - 0x010C, //LATIN CAPITAL LETTER C WITH CARON - 0x00C9, //LATIN CAPITAL LETTER E WITH ACUTE - 0x0118, //LATIN CAPITAL LETTER E WITH OGONEK - 0x00CB, //LATIN CAPITAL LETTER E WITH DIAERESIS - 0x011A, //LATIN CAPITAL LETTER E WITH CARON - 0x00CD, //LATIN CAPITAL LETTER I WITH ACUTE - 0x00CE, //LATIN CAPITAL LETTER I WITH CIRCUMFLEX - 0x010E, //LATIN CAPITAL LETTER D WITH CARON - 0x0110, //LATIN CAPITAL LETTER D WITH STROKE - 0x0143, //LATIN CAPITAL LETTER N WITH ACUTE - 0x0147, //LATIN CAPITAL LETTER N WITH CARON - 0x00D3, //LATIN CAPITAL LETTER O WITH ACUTE - 0x00D4, //LATIN CAPITAL LETTER O WITH CIRCUMFLEX - 0x0150, //LATIN CAPITAL LETTER O WITH DOUBLE ACUTE - 0x00D6, //LATIN CAPITAL LETTER O WITH DIAERESIS - 0x00D7, //MULTIPLICATION SIGN - 0x0158, //LATIN CAPITAL LETTER R WITH CARON - 0x016E, //LATIN CAPITAL LETTER U WITH RING ABOVE - 0x00DA, //LATIN CAPITAL LETTER U WITH ACUTE - 0x0170, //LATIN CAPITAL LETTER U WITH DOUBLE ACUTE - 0x00DC, //LATIN CAPITAL LETTER U WITH DIAERESIS - 0x00DD, //LATIN CAPITAL LETTER Y WITH ACUTE - 0x0162, //LATIN CAPITAL LETTER T WITH CEDILLA - 0x00DF, //LATIN SMALL LETTER SHARP S - 0x0155, //LATIN SMALL LETTER R WITH ACUTE - 0x00E1, //LATIN SMALL LETTER A WITH ACUTE - 0x00E2, //LATIN SMALL LETTER A WITH CIRCUMFLEX - 0x0103, //LATIN SMALL LETTER A WITH BREVE - 0x00E4, //LATIN SMALL LETTER A WITH DIAERESIS - 0x013A, //LATIN SMALL LETTER L WITH ACUTE - 0x0107, //LATIN SMALL LETTER C WITH ACUTE - 0x00E7, //LATIN SMALL LETTER C WITH CEDILLA - 0x010D, //LATIN SMALL LETTER C WITH CARON - 0x00E9, //LATIN SMALL LETTER E WITH ACUTE - 0x0119, //LATIN SMALL LETTER E WITH OGONEK - 0x00EB, //LATIN SMALL LETTER E WITH DIAERESIS - 0x011B, //LATIN SMALL LETTER E WITH CARON - 0x00ED, //LATIN SMALL LETTER I WITH ACUTE - 0x00EE, //LATIN SMALL LETTER I WITH CIRCUMFLEX - 0x010F, //LATIN SMALL LETTER D WITH CARON - 0x0111, //LATIN SMALL LETTER D WITH STROKE - 0x0144, //LATIN SMALL LETTER N WITH ACUTE - 0x0148, //LATIN SMALL LETTER N WITH CARON - 0x00F3, //LATIN SMALL LETTER O WITH ACUTE - 0x00F4, //LATIN SMALL LETTER O WITH CIRCUMFLEX - 0x0151, //LATIN SMALL LETTER O WITH DOUBLE ACUTE - 0x00F6, //LATIN SMALL LETTER O WITH DIAERESIS - 0x00F7, //DIVISION SIGN - 0x0159, //LATIN SMALL LETTER R WITH CARON - 0x016F, //LATIN SMALL LETTER U WITH RING ABOVE - 0x00FA, //LATIN SMALL LETTER U WITH ACUTE - 0x0171, //LATIN SMALL LETTER U WITH DOUBLE ACUTE - 0x00FC, //LATIN SMALL LETTER U WITH DIAERESIS - 0x00FD, //LATIN SMALL LETTER Y WITH ACUTE - 0x0163, //LATIN SMALL LETTER T WITH CEDILLA - 0x02D9, //DOT ABOVE - }, -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/cp1251.go b/vendor/github.com/denisenkom/go-mssqldb/cp1251.go deleted file mode 100644 index f5b81c393..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/cp1251.go +++ /dev/null @@ -1,262 +0,0 @@ -package mssql - -var cp1251 *charsetMap = &charsetMap{ - sb: [256]rune{ - 0x0000, //NULL - 0x0001, //START OF HEADING - 0x0002, //START OF TEXT - 0x0003, //END OF TEXT - 0x0004, //END OF TRANSMISSION - 0x0005, //ENQUIRY - 0x0006, //ACKNOWLEDGE - 0x0007, //BELL - 0x0008, //BACKSPACE - 0x0009, //HORIZONTAL TABULATION - 0x000A, //LINE FEED - 0x000B, //VERTICAL TABULATION - 0x000C, //FORM FEED - 0x000D, //CARRIAGE RETURN - 0x000E, //SHIFT OUT - 0x000F, //SHIFT IN - 0x0010, //DATA LINK ESCAPE - 0x0011, //DEVICE CONTROL ONE - 0x0012, //DEVICE CONTROL TWO - 0x0013, //DEVICE CONTROL THREE - 0x0014, //DEVICE CONTROL FOUR - 0x0015, //NEGATIVE ACKNOWLEDGE - 0x0016, //SYNCHRONOUS IDLE - 0x0017, //END OF TRANSMISSION BLOCK - 0x0018, //CANCEL - 0x0019, //END OF MEDIUM - 0x001A, //SUBSTITUTE - 0x001B, //ESCAPE - 0x001C, //FILE SEPARATOR - 0x001D, //GROUP SEPARATOR - 0x001E, //RECORD SEPARATOR - 0x001F, //UNIT SEPARATOR - 0x0020, //SPACE - 0x0021, //EXCLAMATION MARK - 0x0022, //QUOTATION MARK - 0x0023, //NUMBER SIGN - 0x0024, //DOLLAR SIGN - 0x0025, //PERCENT SIGN - 0x0026, //AMPERSAND - 0x0027, //APOSTROPHE - 0x0028, //LEFT PARENTHESIS - 0x0029, //RIGHT PARENTHESIS - 0x002A, //ASTERISK - 0x002B, //PLUS SIGN - 0x002C, //COMMA - 0x002D, //HYPHEN-MINUS - 0x002E, //FULL STOP - 0x002F, //SOLIDUS - 0x0030, //DIGIT ZERO - 0x0031, //DIGIT ONE - 0x0032, //DIGIT TWO - 0x0033, //DIGIT THREE - 0x0034, //DIGIT FOUR - 0x0035, //DIGIT FIVE - 0x0036, //DIGIT SIX - 0x0037, //DIGIT SEVEN - 0x0038, //DIGIT EIGHT - 0x0039, //DIGIT NINE - 0x003A, //COLON - 0x003B, //SEMICOLON - 0x003C, //LESS-THAN SIGN - 0x003D, //EQUALS SIGN - 0x003E, //GREATER-THAN SIGN - 0x003F, //QUESTION MARK - 0x0040, //COMMERCIAL AT - 0x0041, //LATIN CAPITAL LETTER A - 0x0042, //LATIN CAPITAL LETTER B - 0x0043, //LATIN CAPITAL LETTER C - 0x0044, //LATIN CAPITAL LETTER D - 0x0045, //LATIN CAPITAL LETTER E - 0x0046, //LATIN CAPITAL LETTER F - 0x0047, //LATIN CAPITAL LETTER G - 0x0048, //LATIN CAPITAL LETTER H - 0x0049, //LATIN CAPITAL LETTER I - 0x004A, //LATIN CAPITAL LETTER J - 0x004B, //LATIN CAPITAL LETTER K - 0x004C, //LATIN CAPITAL LETTER L - 0x004D, //LATIN CAPITAL LETTER M - 0x004E, //LATIN CAPITAL LETTER N - 0x004F, //LATIN CAPITAL LETTER O - 0x0050, //LATIN CAPITAL LETTER P - 0x0051, //LATIN CAPITAL LETTER Q - 0x0052, //LATIN CAPITAL LETTER R - 0x0053, //LATIN CAPITAL LETTER S - 0x0054, //LATIN CAPITAL LETTER T - 0x0055, //LATIN CAPITAL LETTER U - 0x0056, //LATIN CAPITAL LETTER V - 0x0057, //LATIN CAPITAL LETTER W - 0x0058, //LATIN CAPITAL LETTER X - 0x0059, //LATIN CAPITAL LETTER Y - 0x005A, //LATIN CAPITAL LETTER Z - 0x005B, //LEFT SQUARE BRACKET - 0x005C, //REVERSE SOLIDUS - 0x005D, //RIGHT SQUARE BRACKET - 0x005E, //CIRCUMFLEX ACCENT - 0x005F, //LOW LINE - 0x0060, //GRAVE ACCENT - 0x0061, //LATIN SMALL LETTER A - 0x0062, //LATIN SMALL LETTER B - 0x0063, //LATIN SMALL LETTER C - 0x0064, //LATIN SMALL LETTER D - 0x0065, //LATIN SMALL LETTER E - 0x0066, //LATIN SMALL LETTER F - 0x0067, //LATIN SMALL LETTER G - 0x0068, //LATIN SMALL LETTER H - 0x0069, //LATIN SMALL LETTER I - 0x006A, //LATIN SMALL LETTER J - 0x006B, //LATIN SMALL LETTER K - 0x006C, //LATIN SMALL LETTER L - 0x006D, //LATIN SMALL LETTER M - 0x006E, //LATIN SMALL LETTER N - 0x006F, //LATIN SMALL LETTER O - 0x0070, //LATIN SMALL LETTER P - 0x0071, //LATIN SMALL LETTER Q - 0x0072, //LATIN SMALL LETTER R - 0x0073, //LATIN SMALL LETTER S - 0x0074, //LATIN SMALL LETTER T - 0x0075, //LATIN SMALL LETTER U - 0x0076, //LATIN SMALL LETTER V - 0x0077, //LATIN SMALL LETTER W - 0x0078, //LATIN SMALL LETTER X - 0x0079, //LATIN SMALL LETTER Y - 0x007A, //LATIN SMALL LETTER Z - 0x007B, //LEFT CURLY BRACKET - 0x007C, //VERTICAL LINE - 0x007D, //RIGHT CURLY BRACKET - 0x007E, //TILDE - 0x007F, //DELETE - 0x0402, //CYRILLIC CAPITAL LETTER DJE - 0x0403, //CYRILLIC CAPITAL LETTER GJE - 0x201A, //SINGLE LOW-9 QUOTATION MARK - 0x0453, //CYRILLIC SMALL LETTER GJE - 0x201E, //DOUBLE LOW-9 QUOTATION MARK - 0x2026, //HORIZONTAL ELLIPSIS - 0x2020, //DAGGER - 0x2021, //DOUBLE DAGGER - 0x20AC, //EURO SIGN - 0x2030, //PER MILLE SIGN - 0x0409, //CYRILLIC CAPITAL LETTER LJE - 0x2039, //SINGLE LEFT-POINTING ANGLE QUOTATION MARK - 0x040A, //CYRILLIC CAPITAL LETTER NJE - 0x040C, //CYRILLIC CAPITAL LETTER KJE - 0x040B, //CYRILLIC CAPITAL LETTER TSHE - 0x040F, //CYRILLIC CAPITAL LETTER DZHE - 0x0452, //CYRILLIC SMALL LETTER DJE - 0x2018, //LEFT SINGLE QUOTATION MARK - 0x2019, //RIGHT SINGLE QUOTATION MARK - 0x201C, //LEFT DOUBLE QUOTATION MARK - 0x201D, //RIGHT DOUBLE QUOTATION MARK - 0x2022, //BULLET - 0x2013, //EN DASH - 0x2014, //EM DASH - 0xFFFD, //UNDEFINED - 0x2122, //TRADE MARK SIGN - 0x0459, //CYRILLIC SMALL LETTER LJE - 0x203A, //SINGLE RIGHT-POINTING ANGLE QUOTATION MARK - 0x045A, //CYRILLIC SMALL LETTER NJE - 0x045C, //CYRILLIC SMALL LETTER KJE - 0x045B, //CYRILLIC SMALL LETTER TSHE - 0x045F, //CYRILLIC SMALL LETTER DZHE - 0x00A0, //NO-BREAK SPACE - 0x040E, //CYRILLIC CAPITAL LETTER SHORT U - 0x045E, //CYRILLIC SMALL LETTER SHORT U - 0x0408, //CYRILLIC CAPITAL LETTER JE - 0x00A4, //CURRENCY SIGN - 0x0490, //CYRILLIC CAPITAL LETTER GHE WITH UPTURN - 0x00A6, //BROKEN BAR - 0x00A7, //SECTION SIGN - 0x0401, //CYRILLIC CAPITAL LETTER IO - 0x00A9, //COPYRIGHT SIGN - 0x0404, //CYRILLIC CAPITAL LETTER UKRAINIAN IE - 0x00AB, //LEFT-POINTING DOUBLE ANGLE QUOTATION MARK - 0x00AC, //NOT SIGN - 0x00AD, //SOFT HYPHEN - 0x00AE, //REGISTERED SIGN - 0x0407, //CYRILLIC CAPITAL LETTER YI - 0x00B0, //DEGREE SIGN - 0x00B1, //PLUS-MINUS SIGN - 0x0406, //CYRILLIC CAPITAL LETTER BYELORUSSIAN-UKRAINIAN I - 0x0456, //CYRILLIC SMALL LETTER BYELORUSSIAN-UKRAINIAN I - 0x0491, //CYRILLIC SMALL LETTER GHE WITH UPTURN - 0x00B5, //MICRO SIGN - 0x00B6, //PILCROW SIGN - 0x00B7, //MIDDLE DOT - 0x0451, //CYRILLIC SMALL LETTER IO - 0x2116, //NUMERO SIGN - 0x0454, //CYRILLIC SMALL LETTER UKRAINIAN IE - 0x00BB, //RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK - 0x0458, //CYRILLIC SMALL LETTER JE - 0x0405, //CYRILLIC CAPITAL LETTER DZE - 0x0455, //CYRILLIC SMALL LETTER DZE - 0x0457, //CYRILLIC SMALL LETTER YI - 0x0410, //CYRILLIC CAPITAL LETTER A - 0x0411, //CYRILLIC CAPITAL LETTER BE - 0x0412, //CYRILLIC CAPITAL LETTER VE - 0x0413, //CYRILLIC CAPITAL LETTER GHE - 0x0414, //CYRILLIC CAPITAL LETTER DE - 0x0415, //CYRILLIC CAPITAL LETTER IE - 0x0416, //CYRILLIC CAPITAL LETTER ZHE - 0x0417, //CYRILLIC CAPITAL LETTER ZE - 0x0418, //CYRILLIC CAPITAL LETTER I - 0x0419, //CYRILLIC CAPITAL LETTER SHORT I - 0x041A, //CYRILLIC CAPITAL LETTER KA - 0x041B, //CYRILLIC CAPITAL LETTER EL - 0x041C, //CYRILLIC CAPITAL LETTER EM - 0x041D, //CYRILLIC CAPITAL LETTER EN - 0x041E, //CYRILLIC CAPITAL LETTER O - 0x041F, //CYRILLIC CAPITAL LETTER PE - 0x0420, //CYRILLIC CAPITAL LETTER ER - 0x0421, //CYRILLIC CAPITAL LETTER ES - 0x0422, //CYRILLIC CAPITAL LETTER TE - 0x0423, //CYRILLIC CAPITAL LETTER U - 0x0424, //CYRILLIC CAPITAL LETTER EF - 0x0425, //CYRILLIC CAPITAL LETTER HA - 0x0426, //CYRILLIC CAPITAL LETTER TSE - 0x0427, //CYRILLIC CAPITAL LETTER CHE - 0x0428, //CYRILLIC CAPITAL LETTER SHA - 0x0429, //CYRILLIC CAPITAL LETTER SHCHA - 0x042A, //CYRILLIC CAPITAL LETTER HARD SIGN - 0x042B, //CYRILLIC CAPITAL LETTER YERU - 0x042C, //CYRILLIC CAPITAL LETTER SOFT SIGN - 0x042D, //CYRILLIC CAPITAL LETTER E - 0x042E, //CYRILLIC CAPITAL LETTER YU - 0x042F, //CYRILLIC CAPITAL LETTER YA - 0x0430, //CYRILLIC SMALL LETTER A - 0x0431, //CYRILLIC SMALL LETTER BE - 0x0432, //CYRILLIC SMALL LETTER VE - 0x0433, //CYRILLIC SMALL LETTER GHE - 0x0434, //CYRILLIC SMALL LETTER DE - 0x0435, //CYRILLIC SMALL LETTER IE - 0x0436, //CYRILLIC SMALL LETTER ZHE - 0x0437, //CYRILLIC SMALL LETTER ZE - 0x0438, //CYRILLIC SMALL LETTER I - 0x0439, //CYRILLIC SMALL LETTER SHORT I - 0x043A, //CYRILLIC SMALL LETTER KA - 0x043B, //CYRILLIC SMALL LETTER EL - 0x043C, //CYRILLIC SMALL LETTER EM - 0x043D, //CYRILLIC SMALL LETTER EN - 0x043E, //CYRILLIC SMALL LETTER O - 0x043F, //CYRILLIC SMALL LETTER PE - 0x0440, //CYRILLIC SMALL LETTER ER - 0x0441, //CYRILLIC SMALL LETTER ES - 0x0442, //CYRILLIC SMALL LETTER TE - 0x0443, //CYRILLIC SMALL LETTER U - 0x0444, //CYRILLIC SMALL LETTER EF - 0x0445, //CYRILLIC SMALL LETTER HA - 0x0446, //CYRILLIC SMALL LETTER TSE - 0x0447, //CYRILLIC SMALL LETTER CHE - 0x0448, //CYRILLIC SMALL LETTER SHA - 0x0449, //CYRILLIC SMALL LETTER SHCHA - 0x044A, //CYRILLIC SMALL LETTER HARD SIGN - 0x044B, //CYRILLIC SMALL LETTER YERU - 0x044C, //CYRILLIC SMALL LETTER SOFT SIGN - 0x044D, //CYRILLIC SMALL LETTER E - 0x044E, //CYRILLIC SMALL LETTER YU - 0x044F, //CYRILLIC SMALL LETTER YA - }, -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/cp1252.go b/vendor/github.com/denisenkom/go-mssqldb/cp1252.go deleted file mode 100644 index ed705d35a..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/cp1252.go +++ /dev/null @@ -1,262 +0,0 @@ -package mssql - -var cp1252 *charsetMap = &charsetMap{ - sb: [256]rune{ - 0x0000, //NULL - 0x0001, //START OF HEADING - 0x0002, //START OF TEXT - 0x0003, //END OF TEXT - 0x0004, //END OF TRANSMISSION - 0x0005, //ENQUIRY - 0x0006, //ACKNOWLEDGE - 0x0007, //BELL - 0x0008, //BACKSPACE - 0x0009, //HORIZONTAL TABULATION - 0x000A, //LINE FEED - 0x000B, //VERTICAL TABULATION - 0x000C, //FORM FEED - 0x000D, //CARRIAGE RETURN - 0x000E, //SHIFT OUT - 0x000F, //SHIFT IN - 0x0010, //DATA LINK ESCAPE - 0x0011, //DEVICE CONTROL ONE - 0x0012, //DEVICE CONTROL TWO - 0x0013, //DEVICE CONTROL THREE - 0x0014, //DEVICE CONTROL FOUR - 0x0015, //NEGATIVE ACKNOWLEDGE - 0x0016, //SYNCHRONOUS IDLE - 0x0017, //END OF TRANSMISSION BLOCK - 0x0018, //CANCEL - 0x0019, //END OF MEDIUM - 0x001A, //SUBSTITUTE - 0x001B, //ESCAPE - 0x001C, //FILE SEPARATOR - 0x001D, //GROUP SEPARATOR - 0x001E, //RECORD SEPARATOR - 0x001F, //UNIT SEPARATOR - 0x0020, //SPACE - 0x0021, //EXCLAMATION MARK - 0x0022, //QUOTATION MARK - 0x0023, //NUMBER SIGN - 0x0024, //DOLLAR SIGN - 0x0025, //PERCENT SIGN - 0x0026, //AMPERSAND - 0x0027, //APOSTROPHE - 0x0028, //LEFT PARENTHESIS - 0x0029, //RIGHT PARENTHESIS - 0x002A, //ASTERISK - 0x002B, //PLUS SIGN - 0x002C, //COMMA - 0x002D, //HYPHEN-MINUS - 0x002E, //FULL STOP - 0x002F, //SOLIDUS - 0x0030, //DIGIT ZERO - 0x0031, //DIGIT ONE - 0x0032, //DIGIT TWO - 0x0033, //DIGIT THREE - 0x0034, //DIGIT FOUR - 0x0035, //DIGIT FIVE - 0x0036, //DIGIT SIX - 0x0037, //DIGIT SEVEN - 0x0038, //DIGIT EIGHT - 0x0039, //DIGIT NINE - 0x003A, //COLON - 0x003B, //SEMICOLON - 0x003C, //LESS-THAN SIGN - 0x003D, //EQUALS SIGN - 0x003E, //GREATER-THAN SIGN - 0x003F, //QUESTION MARK - 0x0040, //COMMERCIAL AT - 0x0041, //LATIN CAPITAL LETTER A - 0x0042, //LATIN CAPITAL LETTER B - 0x0043, //LATIN CAPITAL LETTER C - 0x0044, //LATIN CAPITAL LETTER D - 0x0045, //LATIN CAPITAL LETTER E - 0x0046, //LATIN CAPITAL LETTER F - 0x0047, //LATIN CAPITAL LETTER G - 0x0048, //LATIN CAPITAL LETTER H - 0x0049, //LATIN CAPITAL LETTER I - 0x004A, //LATIN CAPITAL LETTER J - 0x004B, //LATIN CAPITAL LETTER K - 0x004C, //LATIN CAPITAL LETTER L - 0x004D, //LATIN CAPITAL LETTER M - 0x004E, //LATIN CAPITAL LETTER N - 0x004F, //LATIN CAPITAL LETTER O - 0x0050, //LATIN CAPITAL LETTER P - 0x0051, //LATIN CAPITAL LETTER Q - 0x0052, //LATIN CAPITAL LETTER R - 0x0053, //LATIN CAPITAL LETTER S - 0x0054, //LATIN CAPITAL LETTER T - 0x0055, //LATIN CAPITAL LETTER U - 0x0056, //LATIN CAPITAL LETTER V - 0x0057, //LATIN CAPITAL LETTER W - 0x0058, //LATIN CAPITAL LETTER X - 0x0059, //LATIN CAPITAL LETTER Y - 0x005A, //LATIN CAPITAL LETTER Z - 0x005B, //LEFT SQUARE BRACKET - 0x005C, //REVERSE SOLIDUS - 0x005D, //RIGHT SQUARE BRACKET - 0x005E, //CIRCUMFLEX ACCENT - 0x005F, //LOW LINE - 0x0060, //GRAVE ACCENT - 0x0061, //LATIN SMALL LETTER A - 0x0062, //LATIN SMALL LETTER B - 0x0063, //LATIN SMALL LETTER C - 0x0064, //LATIN SMALL LETTER D - 0x0065, //LATIN SMALL LETTER E - 0x0066, //LATIN SMALL LETTER F - 0x0067, //LATIN SMALL LETTER G - 0x0068, //LATIN SMALL LETTER H - 0x0069, //LATIN SMALL LETTER I - 0x006A, //LATIN SMALL LETTER J - 0x006B, //LATIN SMALL LETTER K - 0x006C, //LATIN SMALL LETTER L - 0x006D, //LATIN SMALL LETTER M - 0x006E, //LATIN SMALL LETTER N - 0x006F, //LATIN SMALL LETTER O - 0x0070, //LATIN SMALL LETTER P - 0x0071, //LATIN SMALL LETTER Q - 0x0072, //LATIN SMALL LETTER R - 0x0073, //LATIN SMALL LETTER S - 0x0074, //LATIN SMALL LETTER T - 0x0075, //LATIN SMALL LETTER U - 0x0076, //LATIN SMALL LETTER V - 0x0077, //LATIN SMALL LETTER W - 0x0078, //LATIN SMALL LETTER X - 0x0079, //LATIN SMALL LETTER Y - 0x007A, //LATIN SMALL LETTER Z - 0x007B, //LEFT CURLY BRACKET - 0x007C, //VERTICAL LINE - 0x007D, //RIGHT CURLY BRACKET - 0x007E, //TILDE - 0x007F, //DELETE - 0x20AC, //EURO SIGN - 0xFFFD, //UNDEFINED - 0x201A, //SINGLE LOW-9 QUOTATION MARK - 0x0192, //LATIN SMALL LETTER F WITH HOOK - 0x201E, //DOUBLE LOW-9 QUOTATION MARK - 0x2026, //HORIZONTAL ELLIPSIS - 0x2020, //DAGGER - 0x2021, //DOUBLE DAGGER - 0x02C6, //MODIFIER LETTER CIRCUMFLEX ACCENT - 0x2030, //PER MILLE SIGN - 0x0160, //LATIN CAPITAL LETTER S WITH CARON - 0x2039, //SINGLE LEFT-POINTING ANGLE QUOTATION MARK - 0x0152, //LATIN CAPITAL LIGATURE OE - 0xFFFD, //UNDEFINED - 0x017D, //LATIN CAPITAL LETTER Z WITH CARON - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0x2018, //LEFT SINGLE QUOTATION MARK - 0x2019, //RIGHT SINGLE QUOTATION MARK - 0x201C, //LEFT DOUBLE QUOTATION MARK - 0x201D, //RIGHT DOUBLE QUOTATION MARK - 0x2022, //BULLET - 0x2013, //EN DASH - 0x2014, //EM DASH - 0x02DC, //SMALL TILDE - 0x2122, //TRADE MARK SIGN - 0x0161, //LATIN SMALL LETTER S WITH CARON - 0x203A, //SINGLE RIGHT-POINTING ANGLE QUOTATION MARK - 0x0153, //LATIN SMALL LIGATURE OE - 0xFFFD, //UNDEFINED - 0x017E, //LATIN SMALL LETTER Z WITH CARON - 0x0178, //LATIN CAPITAL LETTER Y WITH DIAERESIS - 0x00A0, //NO-BREAK SPACE - 0x00A1, //INVERTED EXCLAMATION MARK - 0x00A2, //CENT SIGN - 0x00A3, //POUND SIGN - 0x00A4, //CURRENCY SIGN - 0x00A5, //YEN SIGN - 0x00A6, //BROKEN BAR - 0x00A7, //SECTION SIGN - 0x00A8, //DIAERESIS - 0x00A9, //COPYRIGHT SIGN - 0x00AA, //FEMININE ORDINAL INDICATOR - 0x00AB, //LEFT-POINTING DOUBLE ANGLE QUOTATION MARK - 0x00AC, //NOT SIGN - 0x00AD, //SOFT HYPHEN - 0x00AE, //REGISTERED SIGN - 0x00AF, //MACRON - 0x00B0, //DEGREE SIGN - 0x00B1, //PLUS-MINUS SIGN - 0x00B2, //SUPERSCRIPT TWO - 0x00B3, //SUPERSCRIPT THREE - 0x00B4, //ACUTE ACCENT - 0x00B5, //MICRO SIGN - 0x00B6, //PILCROW SIGN - 0x00B7, //MIDDLE DOT - 0x00B8, //CEDILLA - 0x00B9, //SUPERSCRIPT ONE - 0x00BA, //MASCULINE ORDINAL INDICATOR - 0x00BB, //RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK - 0x00BC, //VULGAR FRACTION ONE QUARTER - 0x00BD, //VULGAR FRACTION ONE HALF - 0x00BE, //VULGAR FRACTION THREE QUARTERS - 0x00BF, //INVERTED QUESTION MARK - 0x00C0, //LATIN CAPITAL LETTER A WITH GRAVE - 0x00C1, //LATIN CAPITAL LETTER A WITH ACUTE - 0x00C2, //LATIN CAPITAL LETTER A WITH CIRCUMFLEX - 0x00C3, //LATIN CAPITAL LETTER A WITH TILDE - 0x00C4, //LATIN CAPITAL LETTER A WITH DIAERESIS - 0x00C5, //LATIN CAPITAL LETTER A WITH RING ABOVE - 0x00C6, //LATIN CAPITAL LETTER AE - 0x00C7, //LATIN CAPITAL LETTER C WITH CEDILLA - 0x00C8, //LATIN CAPITAL LETTER E WITH GRAVE - 0x00C9, //LATIN CAPITAL LETTER E WITH ACUTE - 0x00CA, //LATIN CAPITAL LETTER E WITH CIRCUMFLEX - 0x00CB, //LATIN CAPITAL LETTER E WITH DIAERESIS - 0x00CC, //LATIN CAPITAL LETTER I WITH GRAVE - 0x00CD, //LATIN CAPITAL LETTER I WITH ACUTE - 0x00CE, //LATIN CAPITAL LETTER I WITH CIRCUMFLEX - 0x00CF, //LATIN CAPITAL LETTER I WITH DIAERESIS - 0x00D0, //LATIN CAPITAL LETTER ETH - 0x00D1, //LATIN CAPITAL LETTER N WITH TILDE - 0x00D2, //LATIN CAPITAL LETTER O WITH GRAVE - 0x00D3, //LATIN CAPITAL LETTER O WITH ACUTE - 0x00D4, //LATIN CAPITAL LETTER O WITH CIRCUMFLEX - 0x00D5, //LATIN CAPITAL LETTER O WITH TILDE - 0x00D6, //LATIN CAPITAL LETTER O WITH DIAERESIS - 0x00D7, //MULTIPLICATION SIGN - 0x00D8, //LATIN CAPITAL LETTER O WITH STROKE - 0x00D9, //LATIN CAPITAL LETTER U WITH GRAVE - 0x00DA, //LATIN CAPITAL LETTER U WITH ACUTE - 0x00DB, //LATIN CAPITAL LETTER U WITH CIRCUMFLEX - 0x00DC, //LATIN CAPITAL LETTER U WITH DIAERESIS - 0x00DD, //LATIN CAPITAL LETTER Y WITH ACUTE - 0x00DE, //LATIN CAPITAL LETTER THORN - 0x00DF, //LATIN SMALL LETTER SHARP S - 0x00E0, //LATIN SMALL LETTER A WITH GRAVE - 0x00E1, //LATIN SMALL LETTER A WITH ACUTE - 0x00E2, //LATIN SMALL LETTER A WITH CIRCUMFLEX - 0x00E3, //LATIN SMALL LETTER A WITH TILDE - 0x00E4, //LATIN SMALL LETTER A WITH DIAERESIS - 0x00E5, //LATIN SMALL LETTER A WITH RING ABOVE - 0x00E6, //LATIN SMALL LETTER AE - 0x00E7, //LATIN SMALL LETTER C WITH CEDILLA - 0x00E8, //LATIN SMALL LETTER E WITH GRAVE - 0x00E9, //LATIN SMALL LETTER E WITH ACUTE - 0x00EA, //LATIN SMALL LETTER E WITH CIRCUMFLEX - 0x00EB, //LATIN SMALL LETTER E WITH DIAERESIS - 0x00EC, //LATIN SMALL LETTER I WITH GRAVE - 0x00ED, //LATIN SMALL LETTER I WITH ACUTE - 0x00EE, //LATIN SMALL LETTER I WITH CIRCUMFLEX - 0x00EF, //LATIN SMALL LETTER I WITH DIAERESIS - 0x00F0, //LATIN SMALL LETTER ETH - 0x00F1, //LATIN SMALL LETTER N WITH TILDE - 0x00F2, //LATIN SMALL LETTER O WITH GRAVE - 0x00F3, //LATIN SMALL LETTER O WITH ACUTE - 0x00F4, //LATIN SMALL LETTER O WITH CIRCUMFLEX - 0x00F5, //LATIN SMALL LETTER O WITH TILDE - 0x00F6, //LATIN SMALL LETTER O WITH DIAERESIS - 0x00F7, //DIVISION SIGN - 0x00F8, //LATIN SMALL LETTER O WITH STROKE - 0x00F9, //LATIN SMALL LETTER U WITH GRAVE - 0x00FA, //LATIN SMALL LETTER U WITH ACUTE - 0x00FB, //LATIN SMALL LETTER U WITH CIRCUMFLEX - 0x00FC, //LATIN SMALL LETTER U WITH DIAERESIS - 0x00FD, //LATIN SMALL LETTER Y WITH ACUTE - 0x00FE, //LATIN SMALL LETTER THORN - 0x00FF, //LATIN SMALL LETTER Y WITH DIAERESIS - }, -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/cp1253.go b/vendor/github.com/denisenkom/go-mssqldb/cp1253.go deleted file mode 100644 index cb1e1a762..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/cp1253.go +++ /dev/null @@ -1,262 +0,0 @@ -package mssql - -var cp1253 *charsetMap = &charsetMap{ - sb: [256]rune{ - 0x0000, //NULL - 0x0001, //START OF HEADING - 0x0002, //START OF TEXT - 0x0003, //END OF TEXT - 0x0004, //END OF TRANSMISSION - 0x0005, //ENQUIRY - 0x0006, //ACKNOWLEDGE - 0x0007, //BELL - 0x0008, //BACKSPACE - 0x0009, //HORIZONTAL TABULATION - 0x000A, //LINE FEED - 0x000B, //VERTICAL TABULATION - 0x000C, //FORM FEED - 0x000D, //CARRIAGE RETURN - 0x000E, //SHIFT OUT - 0x000F, //SHIFT IN - 0x0010, //DATA LINK ESCAPE - 0x0011, //DEVICE CONTROL ONE - 0x0012, //DEVICE CONTROL TWO - 0x0013, //DEVICE CONTROL THREE - 0x0014, //DEVICE CONTROL FOUR - 0x0015, //NEGATIVE ACKNOWLEDGE - 0x0016, //SYNCHRONOUS IDLE - 0x0017, //END OF TRANSMISSION BLOCK - 0x0018, //CANCEL - 0x0019, //END OF MEDIUM - 0x001A, //SUBSTITUTE - 0x001B, //ESCAPE - 0x001C, //FILE SEPARATOR - 0x001D, //GROUP SEPARATOR - 0x001E, //RECORD SEPARATOR - 0x001F, //UNIT SEPARATOR - 0x0020, //SPACE - 0x0021, //EXCLAMATION MARK - 0x0022, //QUOTATION MARK - 0x0023, //NUMBER SIGN - 0x0024, //DOLLAR SIGN - 0x0025, //PERCENT SIGN - 0x0026, //AMPERSAND - 0x0027, //APOSTROPHE - 0x0028, //LEFT PARENTHESIS - 0x0029, //RIGHT PARENTHESIS - 0x002A, //ASTERISK - 0x002B, //PLUS SIGN - 0x002C, //COMMA - 0x002D, //HYPHEN-MINUS - 0x002E, //FULL STOP - 0x002F, //SOLIDUS - 0x0030, //DIGIT ZERO - 0x0031, //DIGIT ONE - 0x0032, //DIGIT TWO - 0x0033, //DIGIT THREE - 0x0034, //DIGIT FOUR - 0x0035, //DIGIT FIVE - 0x0036, //DIGIT SIX - 0x0037, //DIGIT SEVEN - 0x0038, //DIGIT EIGHT - 0x0039, //DIGIT NINE - 0x003A, //COLON - 0x003B, //SEMICOLON - 0x003C, //LESS-THAN SIGN - 0x003D, //EQUALS SIGN - 0x003E, //GREATER-THAN SIGN - 0x003F, //QUESTION MARK - 0x0040, //COMMERCIAL AT - 0x0041, //LATIN CAPITAL LETTER A - 0x0042, //LATIN CAPITAL LETTER B - 0x0043, //LATIN CAPITAL LETTER C - 0x0044, //LATIN CAPITAL LETTER D - 0x0045, //LATIN CAPITAL LETTER E - 0x0046, //LATIN CAPITAL LETTER F - 0x0047, //LATIN CAPITAL LETTER G - 0x0048, //LATIN CAPITAL LETTER H - 0x0049, //LATIN CAPITAL LETTER I - 0x004A, //LATIN CAPITAL LETTER J - 0x004B, //LATIN CAPITAL LETTER K - 0x004C, //LATIN CAPITAL LETTER L - 0x004D, //LATIN CAPITAL LETTER M - 0x004E, //LATIN CAPITAL LETTER N - 0x004F, //LATIN CAPITAL LETTER O - 0x0050, //LATIN CAPITAL LETTER P - 0x0051, //LATIN CAPITAL LETTER Q - 0x0052, //LATIN CAPITAL LETTER R - 0x0053, //LATIN CAPITAL LETTER S - 0x0054, //LATIN CAPITAL LETTER T - 0x0055, //LATIN CAPITAL LETTER U - 0x0056, //LATIN CAPITAL LETTER V - 0x0057, //LATIN CAPITAL LETTER W - 0x0058, //LATIN CAPITAL LETTER X - 0x0059, //LATIN CAPITAL LETTER Y - 0x005A, //LATIN CAPITAL LETTER Z - 0x005B, //LEFT SQUARE BRACKET - 0x005C, //REVERSE SOLIDUS - 0x005D, //RIGHT SQUARE BRACKET - 0x005E, //CIRCUMFLEX ACCENT - 0x005F, //LOW LINE - 0x0060, //GRAVE ACCENT - 0x0061, //LATIN SMALL LETTER A - 0x0062, //LATIN SMALL LETTER B - 0x0063, //LATIN SMALL LETTER C - 0x0064, //LATIN SMALL LETTER D - 0x0065, //LATIN SMALL LETTER E - 0x0066, //LATIN SMALL LETTER F - 0x0067, //LATIN SMALL LETTER G - 0x0068, //LATIN SMALL LETTER H - 0x0069, //LATIN SMALL LETTER I - 0x006A, //LATIN SMALL LETTER J - 0x006B, //LATIN SMALL LETTER K - 0x006C, //LATIN SMALL LETTER L - 0x006D, //LATIN SMALL LETTER M - 0x006E, //LATIN SMALL LETTER N - 0x006F, //LATIN SMALL LETTER O - 0x0070, //LATIN SMALL LETTER P - 0x0071, //LATIN SMALL LETTER Q - 0x0072, //LATIN SMALL LETTER R - 0x0073, //LATIN SMALL LETTER S - 0x0074, //LATIN SMALL LETTER T - 0x0075, //LATIN SMALL LETTER U - 0x0076, //LATIN SMALL LETTER V - 0x0077, //LATIN SMALL LETTER W - 0x0078, //LATIN SMALL LETTER X - 0x0079, //LATIN SMALL LETTER Y - 0x007A, //LATIN SMALL LETTER Z - 0x007B, //LEFT CURLY BRACKET - 0x007C, //VERTICAL LINE - 0x007D, //RIGHT CURLY BRACKET - 0x007E, //TILDE - 0x007F, //DELETE - 0x20AC, //EURO SIGN - 0xFFFD, //UNDEFINED - 0x201A, //SINGLE LOW-9 QUOTATION MARK - 0x0192, //LATIN SMALL LETTER F WITH HOOK - 0x201E, //DOUBLE LOW-9 QUOTATION MARK - 0x2026, //HORIZONTAL ELLIPSIS - 0x2020, //DAGGER - 0x2021, //DOUBLE DAGGER - 0xFFFD, //UNDEFINED - 0x2030, //PER MILLE SIGN - 0xFFFD, //UNDEFINED - 0x2039, //SINGLE LEFT-POINTING ANGLE QUOTATION MARK - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0x2018, //LEFT SINGLE QUOTATION MARK - 0x2019, //RIGHT SINGLE QUOTATION MARK - 0x201C, //LEFT DOUBLE QUOTATION MARK - 0x201D, //RIGHT DOUBLE QUOTATION MARK - 0x2022, //BULLET - 0x2013, //EN DASH - 0x2014, //EM DASH - 0xFFFD, //UNDEFINED - 0x2122, //TRADE MARK SIGN - 0xFFFD, //UNDEFINED - 0x203A, //SINGLE RIGHT-POINTING ANGLE QUOTATION MARK - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0x00A0, //NO-BREAK SPACE - 0x0385, //GREEK DIALYTIKA TONOS - 0x0386, //GREEK CAPITAL LETTER ALPHA WITH TONOS - 0x00A3, //POUND SIGN - 0x00A4, //CURRENCY SIGN - 0x00A5, //YEN SIGN - 0x00A6, //BROKEN BAR - 0x00A7, //SECTION SIGN - 0x00A8, //DIAERESIS - 0x00A9, //COPYRIGHT SIGN - 0xFFFD, //UNDEFINED - 0x00AB, //LEFT-POINTING DOUBLE ANGLE QUOTATION MARK - 0x00AC, //NOT SIGN - 0x00AD, //SOFT HYPHEN - 0x00AE, //REGISTERED SIGN - 0x2015, //HORIZONTAL BAR - 0x00B0, //DEGREE SIGN - 0x00B1, //PLUS-MINUS SIGN - 0x00B2, //SUPERSCRIPT TWO - 0x00B3, //SUPERSCRIPT THREE - 0x0384, //GREEK TONOS - 0x00B5, //MICRO SIGN - 0x00B6, //PILCROW SIGN - 0x00B7, //MIDDLE DOT - 0x0388, //GREEK CAPITAL LETTER EPSILON WITH TONOS - 0x0389, //GREEK CAPITAL LETTER ETA WITH TONOS - 0x038A, //GREEK CAPITAL LETTER IOTA WITH TONOS - 0x00BB, //RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK - 0x038C, //GREEK CAPITAL LETTER OMICRON WITH TONOS - 0x00BD, //VULGAR FRACTION ONE HALF - 0x038E, //GREEK CAPITAL LETTER UPSILON WITH TONOS - 0x038F, //GREEK CAPITAL LETTER OMEGA WITH TONOS - 0x0390, //GREEK SMALL LETTER IOTA WITH DIALYTIKA AND TONOS - 0x0391, //GREEK CAPITAL LETTER ALPHA - 0x0392, //GREEK CAPITAL LETTER BETA - 0x0393, //GREEK CAPITAL LETTER GAMMA - 0x0394, //GREEK CAPITAL LETTER DELTA - 0x0395, //GREEK CAPITAL LETTER EPSILON - 0x0396, //GREEK CAPITAL LETTER ZETA - 0x0397, //GREEK CAPITAL LETTER ETA - 0x0398, //GREEK CAPITAL LETTER THETA - 0x0399, //GREEK CAPITAL LETTER IOTA - 0x039A, //GREEK CAPITAL LETTER KAPPA - 0x039B, //GREEK CAPITAL LETTER LAMDA - 0x039C, //GREEK CAPITAL LETTER MU - 0x039D, //GREEK CAPITAL LETTER NU - 0x039E, //GREEK CAPITAL LETTER XI - 0x039F, //GREEK CAPITAL LETTER OMICRON - 0x03A0, //GREEK CAPITAL LETTER PI - 0x03A1, //GREEK CAPITAL LETTER RHO - 0xFFFD, //UNDEFINED - 0x03A3, //GREEK CAPITAL LETTER SIGMA - 0x03A4, //GREEK CAPITAL LETTER TAU - 0x03A5, //GREEK CAPITAL LETTER UPSILON - 0x03A6, //GREEK CAPITAL LETTER PHI - 0x03A7, //GREEK CAPITAL LETTER CHI - 0x03A8, //GREEK CAPITAL LETTER PSI - 0x03A9, //GREEK CAPITAL LETTER OMEGA - 0x03AA, //GREEK CAPITAL LETTER IOTA WITH DIALYTIKA - 0x03AB, //GREEK CAPITAL LETTER UPSILON WITH DIALYTIKA - 0x03AC, //GREEK SMALL LETTER ALPHA WITH TONOS - 0x03AD, //GREEK SMALL LETTER EPSILON WITH TONOS - 0x03AE, //GREEK SMALL LETTER ETA WITH TONOS - 0x03AF, //GREEK SMALL LETTER IOTA WITH TONOS - 0x03B0, //GREEK SMALL LETTER UPSILON WITH DIALYTIKA AND TONOS - 0x03B1, //GREEK SMALL LETTER ALPHA - 0x03B2, //GREEK SMALL LETTER BETA - 0x03B3, //GREEK SMALL LETTER GAMMA - 0x03B4, //GREEK SMALL LETTER DELTA - 0x03B5, //GREEK SMALL LETTER EPSILON - 0x03B6, //GREEK SMALL LETTER ZETA - 0x03B7, //GREEK SMALL LETTER ETA - 0x03B8, //GREEK SMALL LETTER THETA - 0x03B9, //GREEK SMALL LETTER IOTA - 0x03BA, //GREEK SMALL LETTER KAPPA - 0x03BB, //GREEK SMALL LETTER LAMDA - 0x03BC, //GREEK SMALL LETTER MU - 0x03BD, //GREEK SMALL LETTER NU - 0x03BE, //GREEK SMALL LETTER XI - 0x03BF, //GREEK SMALL LETTER OMICRON - 0x03C0, //GREEK SMALL LETTER PI - 0x03C1, //GREEK SMALL LETTER RHO - 0x03C2, //GREEK SMALL LETTER FINAL SIGMA - 0x03C3, //GREEK SMALL LETTER SIGMA - 0x03C4, //GREEK SMALL LETTER TAU - 0x03C5, //GREEK SMALL LETTER UPSILON - 0x03C6, //GREEK SMALL LETTER PHI - 0x03C7, //GREEK SMALL LETTER CHI - 0x03C8, //GREEK SMALL LETTER PSI - 0x03C9, //GREEK SMALL LETTER OMEGA - 0x03CA, //GREEK SMALL LETTER IOTA WITH DIALYTIKA - 0x03CB, //GREEK SMALL LETTER UPSILON WITH DIALYTIKA - 0x03CC, //GREEK SMALL LETTER OMICRON WITH TONOS - 0x03CD, //GREEK SMALL LETTER UPSILON WITH TONOS - 0x03CE, //GREEK SMALL LETTER OMEGA WITH TONOS - 0xFFFD, //UNDEFINED - }, -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/cp1254.go b/vendor/github.com/denisenkom/go-mssqldb/cp1254.go deleted file mode 100644 index a4b09bb44..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/cp1254.go +++ /dev/null @@ -1,262 +0,0 @@ -package mssql - -var cp1254 *charsetMap = &charsetMap{ - sb: [256]rune{ - 0x0000, //NULL - 0x0001, //START OF HEADING - 0x0002, //START OF TEXT - 0x0003, //END OF TEXT - 0x0004, //END OF TRANSMISSION - 0x0005, //ENQUIRY - 0x0006, //ACKNOWLEDGE - 0x0007, //BELL - 0x0008, //BACKSPACE - 0x0009, //HORIZONTAL TABULATION - 0x000A, //LINE FEED - 0x000B, //VERTICAL TABULATION - 0x000C, //FORM FEED - 0x000D, //CARRIAGE RETURN - 0x000E, //SHIFT OUT - 0x000F, //SHIFT IN - 0x0010, //DATA LINK ESCAPE - 0x0011, //DEVICE CONTROL ONE - 0x0012, //DEVICE CONTROL TWO - 0x0013, //DEVICE CONTROL THREE - 0x0014, //DEVICE CONTROL FOUR - 0x0015, //NEGATIVE ACKNOWLEDGE - 0x0016, //SYNCHRONOUS IDLE - 0x0017, //END OF TRANSMISSION BLOCK - 0x0018, //CANCEL - 0x0019, //END OF MEDIUM - 0x001A, //SUBSTITUTE - 0x001B, //ESCAPE - 0x001C, //FILE SEPARATOR - 0x001D, //GROUP SEPARATOR - 0x001E, //RECORD SEPARATOR - 0x001F, //UNIT SEPARATOR - 0x0020, //SPACE - 0x0021, //EXCLAMATION MARK - 0x0022, //QUOTATION MARK - 0x0023, //NUMBER SIGN - 0x0024, //DOLLAR SIGN - 0x0025, //PERCENT SIGN - 0x0026, //AMPERSAND - 0x0027, //APOSTROPHE - 0x0028, //LEFT PARENTHESIS - 0x0029, //RIGHT PARENTHESIS - 0x002A, //ASTERISK - 0x002B, //PLUS SIGN - 0x002C, //COMMA - 0x002D, //HYPHEN-MINUS - 0x002E, //FULL STOP - 0x002F, //SOLIDUS - 0x0030, //DIGIT ZERO - 0x0031, //DIGIT ONE - 0x0032, //DIGIT TWO - 0x0033, //DIGIT THREE - 0x0034, //DIGIT FOUR - 0x0035, //DIGIT FIVE - 0x0036, //DIGIT SIX - 0x0037, //DIGIT SEVEN - 0x0038, //DIGIT EIGHT - 0x0039, //DIGIT NINE - 0x003A, //COLON - 0x003B, //SEMICOLON - 0x003C, //LESS-THAN SIGN - 0x003D, //EQUALS SIGN - 0x003E, //GREATER-THAN SIGN - 0x003F, //QUESTION MARK - 0x0040, //COMMERCIAL AT - 0x0041, //LATIN CAPITAL LETTER A - 0x0042, //LATIN CAPITAL LETTER B - 0x0043, //LATIN CAPITAL LETTER C - 0x0044, //LATIN CAPITAL LETTER D - 0x0045, //LATIN CAPITAL LETTER E - 0x0046, //LATIN CAPITAL LETTER F - 0x0047, //LATIN CAPITAL LETTER G - 0x0048, //LATIN CAPITAL LETTER H - 0x0049, //LATIN CAPITAL LETTER I - 0x004A, //LATIN CAPITAL LETTER J - 0x004B, //LATIN CAPITAL LETTER K - 0x004C, //LATIN CAPITAL LETTER L - 0x004D, //LATIN CAPITAL LETTER M - 0x004E, //LATIN CAPITAL LETTER N - 0x004F, //LATIN CAPITAL LETTER O - 0x0050, //LATIN CAPITAL LETTER P - 0x0051, //LATIN CAPITAL LETTER Q - 0x0052, //LATIN CAPITAL LETTER R - 0x0053, //LATIN CAPITAL LETTER S - 0x0054, //LATIN CAPITAL LETTER T - 0x0055, //LATIN CAPITAL LETTER U - 0x0056, //LATIN CAPITAL LETTER V - 0x0057, //LATIN CAPITAL LETTER W - 0x0058, //LATIN CAPITAL LETTER X - 0x0059, //LATIN CAPITAL LETTER Y - 0x005A, //LATIN CAPITAL LETTER Z - 0x005B, //LEFT SQUARE BRACKET - 0x005C, //REVERSE SOLIDUS - 0x005D, //RIGHT SQUARE BRACKET - 0x005E, //CIRCUMFLEX ACCENT - 0x005F, //LOW LINE - 0x0060, //GRAVE ACCENT - 0x0061, //LATIN SMALL LETTER A - 0x0062, //LATIN SMALL LETTER B - 0x0063, //LATIN SMALL LETTER C - 0x0064, //LATIN SMALL LETTER D - 0x0065, //LATIN SMALL LETTER E - 0x0066, //LATIN SMALL LETTER F - 0x0067, //LATIN SMALL LETTER G - 0x0068, //LATIN SMALL LETTER H - 0x0069, //LATIN SMALL LETTER I - 0x006A, //LATIN SMALL LETTER J - 0x006B, //LATIN SMALL LETTER K - 0x006C, //LATIN SMALL LETTER L - 0x006D, //LATIN SMALL LETTER M - 0x006E, //LATIN SMALL LETTER N - 0x006F, //LATIN SMALL LETTER O - 0x0070, //LATIN SMALL LETTER P - 0x0071, //LATIN SMALL LETTER Q - 0x0072, //LATIN SMALL LETTER R - 0x0073, //LATIN SMALL LETTER S - 0x0074, //LATIN SMALL LETTER T - 0x0075, //LATIN SMALL LETTER U - 0x0076, //LATIN SMALL LETTER V - 0x0077, //LATIN SMALL LETTER W - 0x0078, //LATIN SMALL LETTER X - 0x0079, //LATIN SMALL LETTER Y - 0x007A, //LATIN SMALL LETTER Z - 0x007B, //LEFT CURLY BRACKET - 0x007C, //VERTICAL LINE - 0x007D, //RIGHT CURLY BRACKET - 0x007E, //TILDE - 0x007F, //DELETE - 0x20AC, //EURO SIGN - 0xFFFD, //UNDEFINED - 0x201A, //SINGLE LOW-9 QUOTATION MARK - 0x0192, //LATIN SMALL LETTER F WITH HOOK - 0x201E, //DOUBLE LOW-9 QUOTATION MARK - 0x2026, //HORIZONTAL ELLIPSIS - 0x2020, //DAGGER - 0x2021, //DOUBLE DAGGER - 0x02C6, //MODIFIER LETTER CIRCUMFLEX ACCENT - 0x2030, //PER MILLE SIGN - 0x0160, //LATIN CAPITAL LETTER S WITH CARON - 0x2039, //SINGLE LEFT-POINTING ANGLE QUOTATION MARK - 0x0152, //LATIN CAPITAL LIGATURE OE - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0x2018, //LEFT SINGLE QUOTATION MARK - 0x2019, //RIGHT SINGLE QUOTATION MARK - 0x201C, //LEFT DOUBLE QUOTATION MARK - 0x201D, //RIGHT DOUBLE QUOTATION MARK - 0x2022, //BULLET - 0x2013, //EN DASH - 0x2014, //EM DASH - 0x02DC, //SMALL TILDE - 0x2122, //TRADE MARK SIGN - 0x0161, //LATIN SMALL LETTER S WITH CARON - 0x203A, //SINGLE RIGHT-POINTING ANGLE QUOTATION MARK - 0x0153, //LATIN SMALL LIGATURE OE - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0x0178, //LATIN CAPITAL LETTER Y WITH DIAERESIS - 0x00A0, //NO-BREAK SPACE - 0x00A1, //INVERTED EXCLAMATION MARK - 0x00A2, //CENT SIGN - 0x00A3, //POUND SIGN - 0x00A4, //CURRENCY SIGN - 0x00A5, //YEN SIGN - 0x00A6, //BROKEN BAR - 0x00A7, //SECTION SIGN - 0x00A8, //DIAERESIS - 0x00A9, //COPYRIGHT SIGN - 0x00AA, //FEMININE ORDINAL INDICATOR - 0x00AB, //LEFT-POINTING DOUBLE ANGLE QUOTATION MARK - 0x00AC, //NOT SIGN - 0x00AD, //SOFT HYPHEN - 0x00AE, //REGISTERED SIGN - 0x00AF, //MACRON - 0x00B0, //DEGREE SIGN - 0x00B1, //PLUS-MINUS SIGN - 0x00B2, //SUPERSCRIPT TWO - 0x00B3, //SUPERSCRIPT THREE - 0x00B4, //ACUTE ACCENT - 0x00B5, //MICRO SIGN - 0x00B6, //PILCROW SIGN - 0x00B7, //MIDDLE DOT - 0x00B8, //CEDILLA - 0x00B9, //SUPERSCRIPT ONE - 0x00BA, //MASCULINE ORDINAL INDICATOR - 0x00BB, //RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK - 0x00BC, //VULGAR FRACTION ONE QUARTER - 0x00BD, //VULGAR FRACTION ONE HALF - 0x00BE, //VULGAR FRACTION THREE QUARTERS - 0x00BF, //INVERTED QUESTION MARK - 0x00C0, //LATIN CAPITAL LETTER A WITH GRAVE - 0x00C1, //LATIN CAPITAL LETTER A WITH ACUTE - 0x00C2, //LATIN CAPITAL LETTER A WITH CIRCUMFLEX - 0x00C3, //LATIN CAPITAL LETTER A WITH TILDE - 0x00C4, //LATIN CAPITAL LETTER A WITH DIAERESIS - 0x00C5, //LATIN CAPITAL LETTER A WITH RING ABOVE - 0x00C6, //LATIN CAPITAL LETTER AE - 0x00C7, //LATIN CAPITAL LETTER C WITH CEDILLA - 0x00C8, //LATIN CAPITAL LETTER E WITH GRAVE - 0x00C9, //LATIN CAPITAL LETTER E WITH ACUTE - 0x00CA, //LATIN CAPITAL LETTER E WITH CIRCUMFLEX - 0x00CB, //LATIN CAPITAL LETTER E WITH DIAERESIS - 0x00CC, //LATIN CAPITAL LETTER I WITH GRAVE - 0x00CD, //LATIN CAPITAL LETTER I WITH ACUTE - 0x00CE, //LATIN CAPITAL LETTER I WITH CIRCUMFLEX - 0x00CF, //LATIN CAPITAL LETTER I WITH DIAERESIS - 0x011E, //LATIN CAPITAL LETTER G WITH BREVE - 0x00D1, //LATIN CAPITAL LETTER N WITH TILDE - 0x00D2, //LATIN CAPITAL LETTER O WITH GRAVE - 0x00D3, //LATIN CAPITAL LETTER O WITH ACUTE - 0x00D4, //LATIN CAPITAL LETTER O WITH CIRCUMFLEX - 0x00D5, //LATIN CAPITAL LETTER O WITH TILDE - 0x00D6, //LATIN CAPITAL LETTER O WITH DIAERESIS - 0x00D7, //MULTIPLICATION SIGN - 0x00D8, //LATIN CAPITAL LETTER O WITH STROKE - 0x00D9, //LATIN CAPITAL LETTER U WITH GRAVE - 0x00DA, //LATIN CAPITAL LETTER U WITH ACUTE - 0x00DB, //LATIN CAPITAL LETTER U WITH CIRCUMFLEX - 0x00DC, //LATIN CAPITAL LETTER U WITH DIAERESIS - 0x0130, //LATIN CAPITAL LETTER I WITH DOT ABOVE - 0x015E, //LATIN CAPITAL LETTER S WITH CEDILLA - 0x00DF, //LATIN SMALL LETTER SHARP S - 0x00E0, //LATIN SMALL LETTER A WITH GRAVE - 0x00E1, //LATIN SMALL LETTER A WITH ACUTE - 0x00E2, //LATIN SMALL LETTER A WITH CIRCUMFLEX - 0x00E3, //LATIN SMALL LETTER A WITH TILDE - 0x00E4, //LATIN SMALL LETTER A WITH DIAERESIS - 0x00E5, //LATIN SMALL LETTER A WITH RING ABOVE - 0x00E6, //LATIN SMALL LETTER AE - 0x00E7, //LATIN SMALL LETTER C WITH CEDILLA - 0x00E8, //LATIN SMALL LETTER E WITH GRAVE - 0x00E9, //LATIN SMALL LETTER E WITH ACUTE - 0x00EA, //LATIN SMALL LETTER E WITH CIRCUMFLEX - 0x00EB, //LATIN SMALL LETTER E WITH DIAERESIS - 0x00EC, //LATIN SMALL LETTER I WITH GRAVE - 0x00ED, //LATIN SMALL LETTER I WITH ACUTE - 0x00EE, //LATIN SMALL LETTER I WITH CIRCUMFLEX - 0x00EF, //LATIN SMALL LETTER I WITH DIAERESIS - 0x011F, //LATIN SMALL LETTER G WITH BREVE - 0x00F1, //LATIN SMALL LETTER N WITH TILDE - 0x00F2, //LATIN SMALL LETTER O WITH GRAVE - 0x00F3, //LATIN SMALL LETTER O WITH ACUTE - 0x00F4, //LATIN SMALL LETTER O WITH CIRCUMFLEX - 0x00F5, //LATIN SMALL LETTER O WITH TILDE - 0x00F6, //LATIN SMALL LETTER O WITH DIAERESIS - 0x00F7, //DIVISION SIGN - 0x00F8, //LATIN SMALL LETTER O WITH STROKE - 0x00F9, //LATIN SMALL LETTER U WITH GRAVE - 0x00FA, //LATIN SMALL LETTER U WITH ACUTE - 0x00FB, //LATIN SMALL LETTER U WITH CIRCUMFLEX - 0x00FC, //LATIN SMALL LETTER U WITH DIAERESIS - 0x0131, //LATIN SMALL LETTER DOTLESS I - 0x015F, //LATIN SMALL LETTER S WITH CEDILLA - 0x00FF, //LATIN SMALL LETTER Y WITH DIAERESIS - }, -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/cp1255.go b/vendor/github.com/denisenkom/go-mssqldb/cp1255.go deleted file mode 100644 index 97f9ee9e9..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/cp1255.go +++ /dev/null @@ -1,262 +0,0 @@ -package mssql - -var cp1255 *charsetMap = &charsetMap{ - sb: [256]rune{ - 0x0000, //NULL - 0x0001, //START OF HEADING - 0x0002, //START OF TEXT - 0x0003, //END OF TEXT - 0x0004, //END OF TRANSMISSION - 0x0005, //ENQUIRY - 0x0006, //ACKNOWLEDGE - 0x0007, //BELL - 0x0008, //BACKSPACE - 0x0009, //HORIZONTAL TABULATION - 0x000A, //LINE FEED - 0x000B, //VERTICAL TABULATION - 0x000C, //FORM FEED - 0x000D, //CARRIAGE RETURN - 0x000E, //SHIFT OUT - 0x000F, //SHIFT IN - 0x0010, //DATA LINK ESCAPE - 0x0011, //DEVICE CONTROL ONE - 0x0012, //DEVICE CONTROL TWO - 0x0013, //DEVICE CONTROL THREE - 0x0014, //DEVICE CONTROL FOUR - 0x0015, //NEGATIVE ACKNOWLEDGE - 0x0016, //SYNCHRONOUS IDLE - 0x0017, //END OF TRANSMISSION BLOCK - 0x0018, //CANCEL - 0x0019, //END OF MEDIUM - 0x001A, //SUBSTITUTE - 0x001B, //ESCAPE - 0x001C, //FILE SEPARATOR - 0x001D, //GROUP SEPARATOR - 0x001E, //RECORD SEPARATOR - 0x001F, //UNIT SEPARATOR - 0x0020, //SPACE - 0x0021, //EXCLAMATION MARK - 0x0022, //QUOTATION MARK - 0x0023, //NUMBER SIGN - 0x0024, //DOLLAR SIGN - 0x0025, //PERCENT SIGN - 0x0026, //AMPERSAND - 0x0027, //APOSTROPHE - 0x0028, //LEFT PARENTHESIS - 0x0029, //RIGHT PARENTHESIS - 0x002A, //ASTERISK - 0x002B, //PLUS SIGN - 0x002C, //COMMA - 0x002D, //HYPHEN-MINUS - 0x002E, //FULL STOP - 0x002F, //SOLIDUS - 0x0030, //DIGIT ZERO - 0x0031, //DIGIT ONE - 0x0032, //DIGIT TWO - 0x0033, //DIGIT THREE - 0x0034, //DIGIT FOUR - 0x0035, //DIGIT FIVE - 0x0036, //DIGIT SIX - 0x0037, //DIGIT SEVEN - 0x0038, //DIGIT EIGHT - 0x0039, //DIGIT NINE - 0x003A, //COLON - 0x003B, //SEMICOLON - 0x003C, //LESS-THAN SIGN - 0x003D, //EQUALS SIGN - 0x003E, //GREATER-THAN SIGN - 0x003F, //QUESTION MARK - 0x0040, //COMMERCIAL AT - 0x0041, //LATIN CAPITAL LETTER A - 0x0042, //LATIN CAPITAL LETTER B - 0x0043, //LATIN CAPITAL LETTER C - 0x0044, //LATIN CAPITAL LETTER D - 0x0045, //LATIN CAPITAL LETTER E - 0x0046, //LATIN CAPITAL LETTER F - 0x0047, //LATIN CAPITAL LETTER G - 0x0048, //LATIN CAPITAL LETTER H - 0x0049, //LATIN CAPITAL LETTER I - 0x004A, //LATIN CAPITAL LETTER J - 0x004B, //LATIN CAPITAL LETTER K - 0x004C, //LATIN CAPITAL LETTER L - 0x004D, //LATIN CAPITAL LETTER M - 0x004E, //LATIN CAPITAL LETTER N - 0x004F, //LATIN CAPITAL LETTER O - 0x0050, //LATIN CAPITAL LETTER P - 0x0051, //LATIN CAPITAL LETTER Q - 0x0052, //LATIN CAPITAL LETTER R - 0x0053, //LATIN CAPITAL LETTER S - 0x0054, //LATIN CAPITAL LETTER T - 0x0055, //LATIN CAPITAL LETTER U - 0x0056, //LATIN CAPITAL LETTER V - 0x0057, //LATIN CAPITAL LETTER W - 0x0058, //LATIN CAPITAL LETTER X - 0x0059, //LATIN CAPITAL LETTER Y - 0x005A, //LATIN CAPITAL LETTER Z - 0x005B, //LEFT SQUARE BRACKET - 0x005C, //REVERSE SOLIDUS - 0x005D, //RIGHT SQUARE BRACKET - 0x005E, //CIRCUMFLEX ACCENT - 0x005F, //LOW LINE - 0x0060, //GRAVE ACCENT - 0x0061, //LATIN SMALL LETTER A - 0x0062, //LATIN SMALL LETTER B - 0x0063, //LATIN SMALL LETTER C - 0x0064, //LATIN SMALL LETTER D - 0x0065, //LATIN SMALL LETTER E - 0x0066, //LATIN SMALL LETTER F - 0x0067, //LATIN SMALL LETTER G - 0x0068, //LATIN SMALL LETTER H - 0x0069, //LATIN SMALL LETTER I - 0x006A, //LATIN SMALL LETTER J - 0x006B, //LATIN SMALL LETTER K - 0x006C, //LATIN SMALL LETTER L - 0x006D, //LATIN SMALL LETTER M - 0x006E, //LATIN SMALL LETTER N - 0x006F, //LATIN SMALL LETTER O - 0x0070, //LATIN SMALL LETTER P - 0x0071, //LATIN SMALL LETTER Q - 0x0072, //LATIN SMALL LETTER R - 0x0073, //LATIN SMALL LETTER S - 0x0074, //LATIN SMALL LETTER T - 0x0075, //LATIN SMALL LETTER U - 0x0076, //LATIN SMALL LETTER V - 0x0077, //LATIN SMALL LETTER W - 0x0078, //LATIN SMALL LETTER X - 0x0079, //LATIN SMALL LETTER Y - 0x007A, //LATIN SMALL LETTER Z - 0x007B, //LEFT CURLY BRACKET - 0x007C, //VERTICAL LINE - 0x007D, //RIGHT CURLY BRACKET - 0x007E, //TILDE - 0x007F, //DELETE - 0x20AC, //EURO SIGN - 0xFFFD, //UNDEFINED - 0x201A, //SINGLE LOW-9 QUOTATION MARK - 0x0192, //LATIN SMALL LETTER F WITH HOOK - 0x201E, //DOUBLE LOW-9 QUOTATION MARK - 0x2026, //HORIZONTAL ELLIPSIS - 0x2020, //DAGGER - 0x2021, //DOUBLE DAGGER - 0x02C6, //MODIFIER LETTER CIRCUMFLEX ACCENT - 0x2030, //PER MILLE SIGN - 0xFFFD, //UNDEFINED - 0x2039, //SINGLE LEFT-POINTING ANGLE QUOTATION MARK - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0x2018, //LEFT SINGLE QUOTATION MARK - 0x2019, //RIGHT SINGLE QUOTATION MARK - 0x201C, //LEFT DOUBLE QUOTATION MARK - 0x201D, //RIGHT DOUBLE QUOTATION MARK - 0x2022, //BULLET - 0x2013, //EN DASH - 0x2014, //EM DASH - 0x02DC, //SMALL TILDE - 0x2122, //TRADE MARK SIGN - 0xFFFD, //UNDEFINED - 0x203A, //SINGLE RIGHT-POINTING ANGLE QUOTATION MARK - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0x00A0, //NO-BREAK SPACE - 0x00A1, //INVERTED EXCLAMATION MARK - 0x00A2, //CENT SIGN - 0x00A3, //POUND SIGN - 0x20AA, //NEW SHEQEL SIGN - 0x00A5, //YEN SIGN - 0x00A6, //BROKEN BAR - 0x00A7, //SECTION SIGN - 0x00A8, //DIAERESIS - 0x00A9, //COPYRIGHT SIGN - 0x00D7, //MULTIPLICATION SIGN - 0x00AB, //LEFT-POINTING DOUBLE ANGLE QUOTATION MARK - 0x00AC, //NOT SIGN - 0x00AD, //SOFT HYPHEN - 0x00AE, //REGISTERED SIGN - 0x00AF, //MACRON - 0x00B0, //DEGREE SIGN - 0x00B1, //PLUS-MINUS SIGN - 0x00B2, //SUPERSCRIPT TWO - 0x00B3, //SUPERSCRIPT THREE - 0x00B4, //ACUTE ACCENT - 0x00B5, //MICRO SIGN - 0x00B6, //PILCROW SIGN - 0x00B7, //MIDDLE DOT - 0x00B8, //CEDILLA - 0x00B9, //SUPERSCRIPT ONE - 0x00F7, //DIVISION SIGN - 0x00BB, //RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK - 0x00BC, //VULGAR FRACTION ONE QUARTER - 0x00BD, //VULGAR FRACTION ONE HALF - 0x00BE, //VULGAR FRACTION THREE QUARTERS - 0x00BF, //INVERTED QUESTION MARK - 0x05B0, //HEBREW POINT SHEVA - 0x05B1, //HEBREW POINT HATAF SEGOL - 0x05B2, //HEBREW POINT HATAF PATAH - 0x05B3, //HEBREW POINT HATAF QAMATS - 0x05B4, //HEBREW POINT HIRIQ - 0x05B5, //HEBREW POINT TSERE - 0x05B6, //HEBREW POINT SEGOL - 0x05B7, //HEBREW POINT PATAH - 0x05B8, //HEBREW POINT QAMATS - 0x05B9, //HEBREW POINT HOLAM - 0xFFFD, //UNDEFINED - 0x05BB, //HEBREW POINT QUBUTS - 0x05BC, //HEBREW POINT DAGESH OR MAPIQ - 0x05BD, //HEBREW POINT METEG - 0x05BE, //HEBREW PUNCTUATION MAQAF - 0x05BF, //HEBREW POINT RAFE - 0x05C0, //HEBREW PUNCTUATION PASEQ - 0x05C1, //HEBREW POINT SHIN DOT - 0x05C2, //HEBREW POINT SIN DOT - 0x05C3, //HEBREW PUNCTUATION SOF PASUQ - 0x05F0, //HEBREW LIGATURE YIDDISH DOUBLE VAV - 0x05F1, //HEBREW LIGATURE YIDDISH VAV YOD - 0x05F2, //HEBREW LIGATURE YIDDISH DOUBLE YOD - 0x05F3, //HEBREW PUNCTUATION GERESH - 0x05F4, //HEBREW PUNCTUATION GERSHAYIM - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0x05D0, //HEBREW LETTER ALEF - 0x05D1, //HEBREW LETTER BET - 0x05D2, //HEBREW LETTER GIMEL - 0x05D3, //HEBREW LETTER DALET - 0x05D4, //HEBREW LETTER HE - 0x05D5, //HEBREW LETTER VAV - 0x05D6, //HEBREW LETTER ZAYIN - 0x05D7, //HEBREW LETTER HET - 0x05D8, //HEBREW LETTER TET - 0x05D9, //HEBREW LETTER YOD - 0x05DA, //HEBREW LETTER FINAL KAF - 0x05DB, //HEBREW LETTER KAF - 0x05DC, //HEBREW LETTER LAMED - 0x05DD, //HEBREW LETTER FINAL MEM - 0x05DE, //HEBREW LETTER MEM - 0x05DF, //HEBREW LETTER FINAL NUN - 0x05E0, //HEBREW LETTER NUN - 0x05E1, //HEBREW LETTER SAMEKH - 0x05E2, //HEBREW LETTER AYIN - 0x05E3, //HEBREW LETTER FINAL PE - 0x05E4, //HEBREW LETTER PE - 0x05E5, //HEBREW LETTER FINAL TSADI - 0x05E6, //HEBREW LETTER TSADI - 0x05E7, //HEBREW LETTER QOF - 0x05E8, //HEBREW LETTER RESH - 0x05E9, //HEBREW LETTER SHIN - 0x05EA, //HEBREW LETTER TAV - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0x200E, //LEFT-TO-RIGHT MARK - 0x200F, //RIGHT-TO-LEFT MARK - 0xFFFD, //UNDEFINED - }, -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/cp1256.go b/vendor/github.com/denisenkom/go-mssqldb/cp1256.go deleted file mode 100644 index e91241b44..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/cp1256.go +++ /dev/null @@ -1,262 +0,0 @@ -package mssql - -var cp1256 *charsetMap = &charsetMap{ - sb: [256]rune{ - 0x0000, //NULL - 0x0001, //START OF HEADING - 0x0002, //START OF TEXT - 0x0003, //END OF TEXT - 0x0004, //END OF TRANSMISSION - 0x0005, //ENQUIRY - 0x0006, //ACKNOWLEDGE - 0x0007, //BELL - 0x0008, //BACKSPACE - 0x0009, //HORIZONTAL TABULATION - 0x000A, //LINE FEED - 0x000B, //VERTICAL TABULATION - 0x000C, //FORM FEED - 0x000D, //CARRIAGE RETURN - 0x000E, //SHIFT OUT - 0x000F, //SHIFT IN - 0x0010, //DATA LINK ESCAPE - 0x0011, //DEVICE CONTROL ONE - 0x0012, //DEVICE CONTROL TWO - 0x0013, //DEVICE CONTROL THREE - 0x0014, //DEVICE CONTROL FOUR - 0x0015, //NEGATIVE ACKNOWLEDGE - 0x0016, //SYNCHRONOUS IDLE - 0x0017, //END OF TRANSMISSION BLOCK - 0x0018, //CANCEL - 0x0019, //END OF MEDIUM - 0x001A, //SUBSTITUTE - 0x001B, //ESCAPE - 0x001C, //FILE SEPARATOR - 0x001D, //GROUP SEPARATOR - 0x001E, //RECORD SEPARATOR - 0x001F, //UNIT SEPARATOR - 0x0020, //SPACE - 0x0021, //EXCLAMATION MARK - 0x0022, //QUOTATION MARK - 0x0023, //NUMBER SIGN - 0x0024, //DOLLAR SIGN - 0x0025, //PERCENT SIGN - 0x0026, //AMPERSAND - 0x0027, //APOSTROPHE - 0x0028, //LEFT PARENTHESIS - 0x0029, //RIGHT PARENTHESIS - 0x002A, //ASTERISK - 0x002B, //PLUS SIGN - 0x002C, //COMMA - 0x002D, //HYPHEN-MINUS - 0x002E, //FULL STOP - 0x002F, //SOLIDUS - 0x0030, //DIGIT ZERO - 0x0031, //DIGIT ONE - 0x0032, //DIGIT TWO - 0x0033, //DIGIT THREE - 0x0034, //DIGIT FOUR - 0x0035, //DIGIT FIVE - 0x0036, //DIGIT SIX - 0x0037, //DIGIT SEVEN - 0x0038, //DIGIT EIGHT - 0x0039, //DIGIT NINE - 0x003A, //COLON - 0x003B, //SEMICOLON - 0x003C, //LESS-THAN SIGN - 0x003D, //EQUALS SIGN - 0x003E, //GREATER-THAN SIGN - 0x003F, //QUESTION MARK - 0x0040, //COMMERCIAL AT - 0x0041, //LATIN CAPITAL LETTER A - 0x0042, //LATIN CAPITAL LETTER B - 0x0043, //LATIN CAPITAL LETTER C - 0x0044, //LATIN CAPITAL LETTER D - 0x0045, //LATIN CAPITAL LETTER E - 0x0046, //LATIN CAPITAL LETTER F - 0x0047, //LATIN CAPITAL LETTER G - 0x0048, //LATIN CAPITAL LETTER H - 0x0049, //LATIN CAPITAL LETTER I - 0x004A, //LATIN CAPITAL LETTER J - 0x004B, //LATIN CAPITAL LETTER K - 0x004C, //LATIN CAPITAL LETTER L - 0x004D, //LATIN CAPITAL LETTER M - 0x004E, //LATIN CAPITAL LETTER N - 0x004F, //LATIN CAPITAL LETTER O - 0x0050, //LATIN CAPITAL LETTER P - 0x0051, //LATIN CAPITAL LETTER Q - 0x0052, //LATIN CAPITAL LETTER R - 0x0053, //LATIN CAPITAL LETTER S - 0x0054, //LATIN CAPITAL LETTER T - 0x0055, //LATIN CAPITAL LETTER U - 0x0056, //LATIN CAPITAL LETTER V - 0x0057, //LATIN CAPITAL LETTER W - 0x0058, //LATIN CAPITAL LETTER X - 0x0059, //LATIN CAPITAL LETTER Y - 0x005A, //LATIN CAPITAL LETTER Z - 0x005B, //LEFT SQUARE BRACKET - 0x005C, //REVERSE SOLIDUS - 0x005D, //RIGHT SQUARE BRACKET - 0x005E, //CIRCUMFLEX ACCENT - 0x005F, //LOW LINE - 0x0060, //GRAVE ACCENT - 0x0061, //LATIN SMALL LETTER A - 0x0062, //LATIN SMALL LETTER B - 0x0063, //LATIN SMALL LETTER C - 0x0064, //LATIN SMALL LETTER D - 0x0065, //LATIN SMALL LETTER E - 0x0066, //LATIN SMALL LETTER F - 0x0067, //LATIN SMALL LETTER G - 0x0068, //LATIN SMALL LETTER H - 0x0069, //LATIN SMALL LETTER I - 0x006A, //LATIN SMALL LETTER J - 0x006B, //LATIN SMALL LETTER K - 0x006C, //LATIN SMALL LETTER L - 0x006D, //LATIN SMALL LETTER M - 0x006E, //LATIN SMALL LETTER N - 0x006F, //LATIN SMALL LETTER O - 0x0070, //LATIN SMALL LETTER P - 0x0071, //LATIN SMALL LETTER Q - 0x0072, //LATIN SMALL LETTER R - 0x0073, //LATIN SMALL LETTER S - 0x0074, //LATIN SMALL LETTER T - 0x0075, //LATIN SMALL LETTER U - 0x0076, //LATIN SMALL LETTER V - 0x0077, //LATIN SMALL LETTER W - 0x0078, //LATIN SMALL LETTER X - 0x0079, //LATIN SMALL LETTER Y - 0x007A, //LATIN SMALL LETTER Z - 0x007B, //LEFT CURLY BRACKET - 0x007C, //VERTICAL LINE - 0x007D, //RIGHT CURLY BRACKET - 0x007E, //TILDE - 0x007F, //DELETE - 0x20AC, //EURO SIGN - 0x067E, //ARABIC LETTER PEH - 0x201A, //SINGLE LOW-9 QUOTATION MARK - 0x0192, //LATIN SMALL LETTER F WITH HOOK - 0x201E, //DOUBLE LOW-9 QUOTATION MARK - 0x2026, //HORIZONTAL ELLIPSIS - 0x2020, //DAGGER - 0x2021, //DOUBLE DAGGER - 0x02C6, //MODIFIER LETTER CIRCUMFLEX ACCENT - 0x2030, //PER MILLE SIGN - 0x0679, //ARABIC LETTER TTEH - 0x2039, //SINGLE LEFT-POINTING ANGLE QUOTATION MARK - 0x0152, //LATIN CAPITAL LIGATURE OE - 0x0686, //ARABIC LETTER TCHEH - 0x0698, //ARABIC LETTER JEH - 0x0688, //ARABIC LETTER DDAL - 0x06AF, //ARABIC LETTER GAF - 0x2018, //LEFT SINGLE QUOTATION MARK - 0x2019, //RIGHT SINGLE QUOTATION MARK - 0x201C, //LEFT DOUBLE QUOTATION MARK - 0x201D, //RIGHT DOUBLE QUOTATION MARK - 0x2022, //BULLET - 0x2013, //EN DASH - 0x2014, //EM DASH - 0x06A9, //ARABIC LETTER KEHEH - 0x2122, //TRADE MARK SIGN - 0x0691, //ARABIC LETTER RREH - 0x203A, //SINGLE RIGHT-POINTING ANGLE QUOTATION MARK - 0x0153, //LATIN SMALL LIGATURE OE - 0x200C, //ZERO WIDTH NON-JOINER - 0x200D, //ZERO WIDTH JOINER - 0x06BA, //ARABIC LETTER NOON GHUNNA - 0x00A0, //NO-BREAK SPACE - 0x060C, //ARABIC COMMA - 0x00A2, //CENT SIGN - 0x00A3, //POUND SIGN - 0x00A4, //CURRENCY SIGN - 0x00A5, //YEN SIGN - 0x00A6, //BROKEN BAR - 0x00A7, //SECTION SIGN - 0x00A8, //DIAERESIS - 0x00A9, //COPYRIGHT SIGN - 0x06BE, //ARABIC LETTER HEH DOACHASHMEE - 0x00AB, //LEFT-POINTING DOUBLE ANGLE QUOTATION MARK - 0x00AC, //NOT SIGN - 0x00AD, //SOFT HYPHEN - 0x00AE, //REGISTERED SIGN - 0x00AF, //MACRON - 0x00B0, //DEGREE SIGN - 0x00B1, //PLUS-MINUS SIGN - 0x00B2, //SUPERSCRIPT TWO - 0x00B3, //SUPERSCRIPT THREE - 0x00B4, //ACUTE ACCENT - 0x00B5, //MICRO SIGN - 0x00B6, //PILCROW SIGN - 0x00B7, //MIDDLE DOT - 0x00B8, //CEDILLA - 0x00B9, //SUPERSCRIPT ONE - 0x061B, //ARABIC SEMICOLON - 0x00BB, //RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK - 0x00BC, //VULGAR FRACTION ONE QUARTER - 0x00BD, //VULGAR FRACTION ONE HALF - 0x00BE, //VULGAR FRACTION THREE QUARTERS - 0x061F, //ARABIC QUESTION MARK - 0x06C1, //ARABIC LETTER HEH GOAL - 0x0621, //ARABIC LETTER HAMZA - 0x0622, //ARABIC LETTER ALEF WITH MADDA ABOVE - 0x0623, //ARABIC LETTER ALEF WITH HAMZA ABOVE - 0x0624, //ARABIC LETTER WAW WITH HAMZA ABOVE - 0x0625, //ARABIC LETTER ALEF WITH HAMZA BELOW - 0x0626, //ARABIC LETTER YEH WITH HAMZA ABOVE - 0x0627, //ARABIC LETTER ALEF - 0x0628, //ARABIC LETTER BEH - 0x0629, //ARABIC LETTER TEH MARBUTA - 0x062A, //ARABIC LETTER TEH - 0x062B, //ARABIC LETTER THEH - 0x062C, //ARABIC LETTER JEEM - 0x062D, //ARABIC LETTER HAH - 0x062E, //ARABIC LETTER KHAH - 0x062F, //ARABIC LETTER DAL - 0x0630, //ARABIC LETTER THAL - 0x0631, //ARABIC LETTER REH - 0x0632, //ARABIC LETTER ZAIN - 0x0633, //ARABIC LETTER SEEN - 0x0634, //ARABIC LETTER SHEEN - 0x0635, //ARABIC LETTER SAD - 0x0636, //ARABIC LETTER DAD - 0x00D7, //MULTIPLICATION SIGN - 0x0637, //ARABIC LETTER TAH - 0x0638, //ARABIC LETTER ZAH - 0x0639, //ARABIC LETTER AIN - 0x063A, //ARABIC LETTER GHAIN - 0x0640, //ARABIC TATWEEL - 0x0641, //ARABIC LETTER FEH - 0x0642, //ARABIC LETTER QAF - 0x0643, //ARABIC LETTER KAF - 0x00E0, //LATIN SMALL LETTER A WITH GRAVE - 0x0644, //ARABIC LETTER LAM - 0x00E2, //LATIN SMALL LETTER A WITH CIRCUMFLEX - 0x0645, //ARABIC LETTER MEEM - 0x0646, //ARABIC LETTER NOON - 0x0647, //ARABIC LETTER HEH - 0x0648, //ARABIC LETTER WAW - 0x00E7, //LATIN SMALL LETTER C WITH CEDILLA - 0x00E8, //LATIN SMALL LETTER E WITH GRAVE - 0x00E9, //LATIN SMALL LETTER E WITH ACUTE - 0x00EA, //LATIN SMALL LETTER E WITH CIRCUMFLEX - 0x00EB, //LATIN SMALL LETTER E WITH DIAERESIS - 0x0649, //ARABIC LETTER ALEF MAKSURA - 0x064A, //ARABIC LETTER YEH - 0x00EE, //LATIN SMALL LETTER I WITH CIRCUMFLEX - 0x00EF, //LATIN SMALL LETTER I WITH DIAERESIS - 0x064B, //ARABIC FATHATAN - 0x064C, //ARABIC DAMMATAN - 0x064D, //ARABIC KASRATAN - 0x064E, //ARABIC FATHA - 0x00F4, //LATIN SMALL LETTER O WITH CIRCUMFLEX - 0x064F, //ARABIC DAMMA - 0x0650, //ARABIC KASRA - 0x00F7, //DIVISION SIGN - 0x0651, //ARABIC SHADDA - 0x00F9, //LATIN SMALL LETTER U WITH GRAVE - 0x0652, //ARABIC SUKUN - 0x00FB, //LATIN SMALL LETTER U WITH CIRCUMFLEX - 0x00FC, //LATIN SMALL LETTER U WITH DIAERESIS - 0x200E, //LEFT-TO-RIGHT MARK - 0x200F, //RIGHT-TO-LEFT MARK - 0x06D2, //ARABIC LETTER YEH BARREE - }, -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/cp1257.go b/vendor/github.com/denisenkom/go-mssqldb/cp1257.go deleted file mode 100644 index bd93e6f89..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/cp1257.go +++ /dev/null @@ -1,262 +0,0 @@ -package mssql - -var cp1257 *charsetMap = &charsetMap{ - sb: [256]rune{ - 0x0000, //NULL - 0x0001, //START OF HEADING - 0x0002, //START OF TEXT - 0x0003, //END OF TEXT - 0x0004, //END OF TRANSMISSION - 0x0005, //ENQUIRY - 0x0006, //ACKNOWLEDGE - 0x0007, //BELL - 0x0008, //BACKSPACE - 0x0009, //HORIZONTAL TABULATION - 0x000A, //LINE FEED - 0x000B, //VERTICAL TABULATION - 0x000C, //FORM FEED - 0x000D, //CARRIAGE RETURN - 0x000E, //SHIFT OUT - 0x000F, //SHIFT IN - 0x0010, //DATA LINK ESCAPE - 0x0011, //DEVICE CONTROL ONE - 0x0012, //DEVICE CONTROL TWO - 0x0013, //DEVICE CONTROL THREE - 0x0014, //DEVICE CONTROL FOUR - 0x0015, //NEGATIVE ACKNOWLEDGE - 0x0016, //SYNCHRONOUS IDLE - 0x0017, //END OF TRANSMISSION BLOCK - 0x0018, //CANCEL - 0x0019, //END OF MEDIUM - 0x001A, //SUBSTITUTE - 0x001B, //ESCAPE - 0x001C, //FILE SEPARATOR - 0x001D, //GROUP SEPARATOR - 0x001E, //RECORD SEPARATOR - 0x001F, //UNIT SEPARATOR - 0x0020, //SPACE - 0x0021, //EXCLAMATION MARK - 0x0022, //QUOTATION MARK - 0x0023, //NUMBER SIGN - 0x0024, //DOLLAR SIGN - 0x0025, //PERCENT SIGN - 0x0026, //AMPERSAND - 0x0027, //APOSTROPHE - 0x0028, //LEFT PARENTHESIS - 0x0029, //RIGHT PARENTHESIS - 0x002A, //ASTERISK - 0x002B, //PLUS SIGN - 0x002C, //COMMA - 0x002D, //HYPHEN-MINUS - 0x002E, //FULL STOP - 0x002F, //SOLIDUS - 0x0030, //DIGIT ZERO - 0x0031, //DIGIT ONE - 0x0032, //DIGIT TWO - 0x0033, //DIGIT THREE - 0x0034, //DIGIT FOUR - 0x0035, //DIGIT FIVE - 0x0036, //DIGIT SIX - 0x0037, //DIGIT SEVEN - 0x0038, //DIGIT EIGHT - 0x0039, //DIGIT NINE - 0x003A, //COLON - 0x003B, //SEMICOLON - 0x003C, //LESS-THAN SIGN - 0x003D, //EQUALS SIGN - 0x003E, //GREATER-THAN SIGN - 0x003F, //QUESTION MARK - 0x0040, //COMMERCIAL AT - 0x0041, //LATIN CAPITAL LETTER A - 0x0042, //LATIN CAPITAL LETTER B - 0x0043, //LATIN CAPITAL LETTER C - 0x0044, //LATIN CAPITAL LETTER D - 0x0045, //LATIN CAPITAL LETTER E - 0x0046, //LATIN CAPITAL LETTER F - 0x0047, //LATIN CAPITAL LETTER G - 0x0048, //LATIN CAPITAL LETTER H - 0x0049, //LATIN CAPITAL LETTER I - 0x004A, //LATIN CAPITAL LETTER J - 0x004B, //LATIN CAPITAL LETTER K - 0x004C, //LATIN CAPITAL LETTER L - 0x004D, //LATIN CAPITAL LETTER M - 0x004E, //LATIN CAPITAL LETTER N - 0x004F, //LATIN CAPITAL LETTER O - 0x0050, //LATIN CAPITAL LETTER P - 0x0051, //LATIN CAPITAL LETTER Q - 0x0052, //LATIN CAPITAL LETTER R - 0x0053, //LATIN CAPITAL LETTER S - 0x0054, //LATIN CAPITAL LETTER T - 0x0055, //LATIN CAPITAL LETTER U - 0x0056, //LATIN CAPITAL LETTER V - 0x0057, //LATIN CAPITAL LETTER W - 0x0058, //LATIN CAPITAL LETTER X - 0x0059, //LATIN CAPITAL LETTER Y - 0x005A, //LATIN CAPITAL LETTER Z - 0x005B, //LEFT SQUARE BRACKET - 0x005C, //REVERSE SOLIDUS - 0x005D, //RIGHT SQUARE BRACKET - 0x005E, //CIRCUMFLEX ACCENT - 0x005F, //LOW LINE - 0x0060, //GRAVE ACCENT - 0x0061, //LATIN SMALL LETTER A - 0x0062, //LATIN SMALL LETTER B - 0x0063, //LATIN SMALL LETTER C - 0x0064, //LATIN SMALL LETTER D - 0x0065, //LATIN SMALL LETTER E - 0x0066, //LATIN SMALL LETTER F - 0x0067, //LATIN SMALL LETTER G - 0x0068, //LATIN SMALL LETTER H - 0x0069, //LATIN SMALL LETTER I - 0x006A, //LATIN SMALL LETTER J - 0x006B, //LATIN SMALL LETTER K - 0x006C, //LATIN SMALL LETTER L - 0x006D, //LATIN SMALL LETTER M - 0x006E, //LATIN SMALL LETTER N - 0x006F, //LATIN SMALL LETTER O - 0x0070, //LATIN SMALL LETTER P - 0x0071, //LATIN SMALL LETTER Q - 0x0072, //LATIN SMALL LETTER R - 0x0073, //LATIN SMALL LETTER S - 0x0074, //LATIN SMALL LETTER T - 0x0075, //LATIN SMALL LETTER U - 0x0076, //LATIN SMALL LETTER V - 0x0077, //LATIN SMALL LETTER W - 0x0078, //LATIN SMALL LETTER X - 0x0079, //LATIN SMALL LETTER Y - 0x007A, //LATIN SMALL LETTER Z - 0x007B, //LEFT CURLY BRACKET - 0x007C, //VERTICAL LINE - 0x007D, //RIGHT CURLY BRACKET - 0x007E, //TILDE - 0x007F, //DELETE - 0x20AC, //EURO SIGN - 0xFFFD, //UNDEFINED - 0x201A, //SINGLE LOW-9 QUOTATION MARK - 0xFFFD, //UNDEFINED - 0x201E, //DOUBLE LOW-9 QUOTATION MARK - 0x2026, //HORIZONTAL ELLIPSIS - 0x2020, //DAGGER - 0x2021, //DOUBLE DAGGER - 0xFFFD, //UNDEFINED - 0x2030, //PER MILLE SIGN - 0xFFFD, //UNDEFINED - 0x2039, //SINGLE LEFT-POINTING ANGLE QUOTATION MARK - 0xFFFD, //UNDEFINED - 0x00A8, //DIAERESIS - 0x02C7, //CARON - 0x00B8, //CEDILLA - 0xFFFD, //UNDEFINED - 0x2018, //LEFT SINGLE QUOTATION MARK - 0x2019, //RIGHT SINGLE QUOTATION MARK - 0x201C, //LEFT DOUBLE QUOTATION MARK - 0x201D, //RIGHT DOUBLE QUOTATION MARK - 0x2022, //BULLET - 0x2013, //EN DASH - 0x2014, //EM DASH - 0xFFFD, //UNDEFINED - 0x2122, //TRADE MARK SIGN - 0xFFFD, //UNDEFINED - 0x203A, //SINGLE RIGHT-POINTING ANGLE QUOTATION MARK - 0xFFFD, //UNDEFINED - 0x00AF, //MACRON - 0x02DB, //OGONEK - 0xFFFD, //UNDEFINED - 0x00A0, //NO-BREAK SPACE - 0xFFFD, //UNDEFINED - 0x00A2, //CENT SIGN - 0x00A3, //POUND SIGN - 0x00A4, //CURRENCY SIGN - 0xFFFD, //UNDEFINED - 0x00A6, //BROKEN BAR - 0x00A7, //SECTION SIGN - 0x00D8, //LATIN CAPITAL LETTER O WITH STROKE - 0x00A9, //COPYRIGHT SIGN - 0x0156, //LATIN CAPITAL LETTER R WITH CEDILLA - 0x00AB, //LEFT-POINTING DOUBLE ANGLE QUOTATION MARK - 0x00AC, //NOT SIGN - 0x00AD, //SOFT HYPHEN - 0x00AE, //REGISTERED SIGN - 0x00C6, //LATIN CAPITAL LETTER AE - 0x00B0, //DEGREE SIGN - 0x00B1, //PLUS-MINUS SIGN - 0x00B2, //SUPERSCRIPT TWO - 0x00B3, //SUPERSCRIPT THREE - 0x00B4, //ACUTE ACCENT - 0x00B5, //MICRO SIGN - 0x00B6, //PILCROW SIGN - 0x00B7, //MIDDLE DOT - 0x00F8, //LATIN SMALL LETTER O WITH STROKE - 0x00B9, //SUPERSCRIPT ONE - 0x0157, //LATIN SMALL LETTER R WITH CEDILLA - 0x00BB, //RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK - 0x00BC, //VULGAR FRACTION ONE QUARTER - 0x00BD, //VULGAR FRACTION ONE HALF - 0x00BE, //VULGAR FRACTION THREE QUARTERS - 0x00E6, //LATIN SMALL LETTER AE - 0x0104, //LATIN CAPITAL LETTER A WITH OGONEK - 0x012E, //LATIN CAPITAL LETTER I WITH OGONEK - 0x0100, //LATIN CAPITAL LETTER A WITH MACRON - 0x0106, //LATIN CAPITAL LETTER C WITH ACUTE - 0x00C4, //LATIN CAPITAL LETTER A WITH DIAERESIS - 0x00C5, //LATIN CAPITAL LETTER A WITH RING ABOVE - 0x0118, //LATIN CAPITAL LETTER E WITH OGONEK - 0x0112, //LATIN CAPITAL LETTER E WITH MACRON - 0x010C, //LATIN CAPITAL LETTER C WITH CARON - 0x00C9, //LATIN CAPITAL LETTER E WITH ACUTE - 0x0179, //LATIN CAPITAL LETTER Z WITH ACUTE - 0x0116, //LATIN CAPITAL LETTER E WITH DOT ABOVE - 0x0122, //LATIN CAPITAL LETTER G WITH CEDILLA - 0x0136, //LATIN CAPITAL LETTER K WITH CEDILLA - 0x012A, //LATIN CAPITAL LETTER I WITH MACRON - 0x013B, //LATIN CAPITAL LETTER L WITH CEDILLA - 0x0160, //LATIN CAPITAL LETTER S WITH CARON - 0x0143, //LATIN CAPITAL LETTER N WITH ACUTE - 0x0145, //LATIN CAPITAL LETTER N WITH CEDILLA - 0x00D3, //LATIN CAPITAL LETTER O WITH ACUTE - 0x014C, //LATIN CAPITAL LETTER O WITH MACRON - 0x00D5, //LATIN CAPITAL LETTER O WITH TILDE - 0x00D6, //LATIN CAPITAL LETTER O WITH DIAERESIS - 0x00D7, //MULTIPLICATION SIGN - 0x0172, //LATIN CAPITAL LETTER U WITH OGONEK - 0x0141, //LATIN CAPITAL LETTER L WITH STROKE - 0x015A, //LATIN CAPITAL LETTER S WITH ACUTE - 0x016A, //LATIN CAPITAL LETTER U WITH MACRON - 0x00DC, //LATIN CAPITAL LETTER U WITH DIAERESIS - 0x017B, //LATIN CAPITAL LETTER Z WITH DOT ABOVE - 0x017D, //LATIN CAPITAL LETTER Z WITH CARON - 0x00DF, //LATIN SMALL LETTER SHARP S - 0x0105, //LATIN SMALL LETTER A WITH OGONEK - 0x012F, //LATIN SMALL LETTER I WITH OGONEK - 0x0101, //LATIN SMALL LETTER A WITH MACRON - 0x0107, //LATIN SMALL LETTER C WITH ACUTE - 0x00E4, //LATIN SMALL LETTER A WITH DIAERESIS - 0x00E5, //LATIN SMALL LETTER A WITH RING ABOVE - 0x0119, //LATIN SMALL LETTER E WITH OGONEK - 0x0113, //LATIN SMALL LETTER E WITH MACRON - 0x010D, //LATIN SMALL LETTER C WITH CARON - 0x00E9, //LATIN SMALL LETTER E WITH ACUTE - 0x017A, //LATIN SMALL LETTER Z WITH ACUTE - 0x0117, //LATIN SMALL LETTER E WITH DOT ABOVE - 0x0123, //LATIN SMALL LETTER G WITH CEDILLA - 0x0137, //LATIN SMALL LETTER K WITH CEDILLA - 0x012B, //LATIN SMALL LETTER I WITH MACRON - 0x013C, //LATIN SMALL LETTER L WITH CEDILLA - 0x0161, //LATIN SMALL LETTER S WITH CARON - 0x0144, //LATIN SMALL LETTER N WITH ACUTE - 0x0146, //LATIN SMALL LETTER N WITH CEDILLA - 0x00F3, //LATIN SMALL LETTER O WITH ACUTE - 0x014D, //LATIN SMALL LETTER O WITH MACRON - 0x00F5, //LATIN SMALL LETTER O WITH TILDE - 0x00F6, //LATIN SMALL LETTER O WITH DIAERESIS - 0x00F7, //DIVISION SIGN - 0x0173, //LATIN SMALL LETTER U WITH OGONEK - 0x0142, //LATIN SMALL LETTER L WITH STROKE - 0x015B, //LATIN SMALL LETTER S WITH ACUTE - 0x016B, //LATIN SMALL LETTER U WITH MACRON - 0x00FC, //LATIN SMALL LETTER U WITH DIAERESIS - 0x017C, //LATIN SMALL LETTER Z WITH DOT ABOVE - 0x017E, //LATIN SMALL LETTER Z WITH CARON - 0x02D9, //DOT ABOVE - }, -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/cp1258.go b/vendor/github.com/denisenkom/go-mssqldb/cp1258.go deleted file mode 100644 index 4e1f8ac94..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/cp1258.go +++ /dev/null @@ -1,262 +0,0 @@ -package mssql - -var cp1258 *charsetMap = &charsetMap{ - sb: [256]rune{ - 0x0000, //NULL - 0x0001, //START OF HEADING - 0x0002, //START OF TEXT - 0x0003, //END OF TEXT - 0x0004, //END OF TRANSMISSION - 0x0005, //ENQUIRY - 0x0006, //ACKNOWLEDGE - 0x0007, //BELL - 0x0008, //BACKSPACE - 0x0009, //HORIZONTAL TABULATION - 0x000A, //LINE FEED - 0x000B, //VERTICAL TABULATION - 0x000C, //FORM FEED - 0x000D, //CARRIAGE RETURN - 0x000E, //SHIFT OUT - 0x000F, //SHIFT IN - 0x0010, //DATA LINK ESCAPE - 0x0011, //DEVICE CONTROL ONE - 0x0012, //DEVICE CONTROL TWO - 0x0013, //DEVICE CONTROL THREE - 0x0014, //DEVICE CONTROL FOUR - 0x0015, //NEGATIVE ACKNOWLEDGE - 0x0016, //SYNCHRONOUS IDLE - 0x0017, //END OF TRANSMISSION BLOCK - 0x0018, //CANCEL - 0x0019, //END OF MEDIUM - 0x001A, //SUBSTITUTE - 0x001B, //ESCAPE - 0x001C, //FILE SEPARATOR - 0x001D, //GROUP SEPARATOR - 0x001E, //RECORD SEPARATOR - 0x001F, //UNIT SEPARATOR - 0x0020, //SPACE - 0x0021, //EXCLAMATION MARK - 0x0022, //QUOTATION MARK - 0x0023, //NUMBER SIGN - 0x0024, //DOLLAR SIGN - 0x0025, //PERCENT SIGN - 0x0026, //AMPERSAND - 0x0027, //APOSTROPHE - 0x0028, //LEFT PARENTHESIS - 0x0029, //RIGHT PARENTHESIS - 0x002A, //ASTERISK - 0x002B, //PLUS SIGN - 0x002C, //COMMA - 0x002D, //HYPHEN-MINUS - 0x002E, //FULL STOP - 0x002F, //SOLIDUS - 0x0030, //DIGIT ZERO - 0x0031, //DIGIT ONE - 0x0032, //DIGIT TWO - 0x0033, //DIGIT THREE - 0x0034, //DIGIT FOUR - 0x0035, //DIGIT FIVE - 0x0036, //DIGIT SIX - 0x0037, //DIGIT SEVEN - 0x0038, //DIGIT EIGHT - 0x0039, //DIGIT NINE - 0x003A, //COLON - 0x003B, //SEMICOLON - 0x003C, //LESS-THAN SIGN - 0x003D, //EQUALS SIGN - 0x003E, //GREATER-THAN SIGN - 0x003F, //QUESTION MARK - 0x0040, //COMMERCIAL AT - 0x0041, //LATIN CAPITAL LETTER A - 0x0042, //LATIN CAPITAL LETTER B - 0x0043, //LATIN CAPITAL LETTER C - 0x0044, //LATIN CAPITAL LETTER D - 0x0045, //LATIN CAPITAL LETTER E - 0x0046, //LATIN CAPITAL LETTER F - 0x0047, //LATIN CAPITAL LETTER G - 0x0048, //LATIN CAPITAL LETTER H - 0x0049, //LATIN CAPITAL LETTER I - 0x004A, //LATIN CAPITAL LETTER J - 0x004B, //LATIN CAPITAL LETTER K - 0x004C, //LATIN CAPITAL LETTER L - 0x004D, //LATIN CAPITAL LETTER M - 0x004E, //LATIN CAPITAL LETTER N - 0x004F, //LATIN CAPITAL LETTER O - 0x0050, //LATIN CAPITAL LETTER P - 0x0051, //LATIN CAPITAL LETTER Q - 0x0052, //LATIN CAPITAL LETTER R - 0x0053, //LATIN CAPITAL LETTER S - 0x0054, //LATIN CAPITAL LETTER T - 0x0055, //LATIN CAPITAL LETTER U - 0x0056, //LATIN CAPITAL LETTER V - 0x0057, //LATIN CAPITAL LETTER W - 0x0058, //LATIN CAPITAL LETTER X - 0x0059, //LATIN CAPITAL LETTER Y - 0x005A, //LATIN CAPITAL LETTER Z - 0x005B, //LEFT SQUARE BRACKET - 0x005C, //REVERSE SOLIDUS - 0x005D, //RIGHT SQUARE BRACKET - 0x005E, //CIRCUMFLEX ACCENT - 0x005F, //LOW LINE - 0x0060, //GRAVE ACCENT - 0x0061, //LATIN SMALL LETTER A - 0x0062, //LATIN SMALL LETTER B - 0x0063, //LATIN SMALL LETTER C - 0x0064, //LATIN SMALL LETTER D - 0x0065, //LATIN SMALL LETTER E - 0x0066, //LATIN SMALL LETTER F - 0x0067, //LATIN SMALL LETTER G - 0x0068, //LATIN SMALL LETTER H - 0x0069, //LATIN SMALL LETTER I - 0x006A, //LATIN SMALL LETTER J - 0x006B, //LATIN SMALL LETTER K - 0x006C, //LATIN SMALL LETTER L - 0x006D, //LATIN SMALL LETTER M - 0x006E, //LATIN SMALL LETTER N - 0x006F, //LATIN SMALL LETTER O - 0x0070, //LATIN SMALL LETTER P - 0x0071, //LATIN SMALL LETTER Q - 0x0072, //LATIN SMALL LETTER R - 0x0073, //LATIN SMALL LETTER S - 0x0074, //LATIN SMALL LETTER T - 0x0075, //LATIN SMALL LETTER U - 0x0076, //LATIN SMALL LETTER V - 0x0077, //LATIN SMALL LETTER W - 0x0078, //LATIN SMALL LETTER X - 0x0079, //LATIN SMALL LETTER Y - 0x007A, //LATIN SMALL LETTER Z - 0x007B, //LEFT CURLY BRACKET - 0x007C, //VERTICAL LINE - 0x007D, //RIGHT CURLY BRACKET - 0x007E, //TILDE - 0x007F, //DELETE - 0x20AC, //EURO SIGN - 0xFFFD, //UNDEFINED - 0x201A, //SINGLE LOW-9 QUOTATION MARK - 0x0192, //LATIN SMALL LETTER F WITH HOOK - 0x201E, //DOUBLE LOW-9 QUOTATION MARK - 0x2026, //HORIZONTAL ELLIPSIS - 0x2020, //DAGGER - 0x2021, //DOUBLE DAGGER - 0x02C6, //MODIFIER LETTER CIRCUMFLEX ACCENT - 0x2030, //PER MILLE SIGN - 0xFFFD, //UNDEFINED - 0x2039, //SINGLE LEFT-POINTING ANGLE QUOTATION MARK - 0x0152, //LATIN CAPITAL LIGATURE OE - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0x2018, //LEFT SINGLE QUOTATION MARK - 0x2019, //RIGHT SINGLE QUOTATION MARK - 0x201C, //LEFT DOUBLE QUOTATION MARK - 0x201D, //RIGHT DOUBLE QUOTATION MARK - 0x2022, //BULLET - 0x2013, //EN DASH - 0x2014, //EM DASH - 0x02DC, //SMALL TILDE - 0x2122, //TRADE MARK SIGN - 0xFFFD, //UNDEFINED - 0x203A, //SINGLE RIGHT-POINTING ANGLE QUOTATION MARK - 0x0153, //LATIN SMALL LIGATURE OE - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0x0178, //LATIN CAPITAL LETTER Y WITH DIAERESIS - 0x00A0, //NO-BREAK SPACE - 0x00A1, //INVERTED EXCLAMATION MARK - 0x00A2, //CENT SIGN - 0x00A3, //POUND SIGN - 0x00A4, //CURRENCY SIGN - 0x00A5, //YEN SIGN - 0x00A6, //BROKEN BAR - 0x00A7, //SECTION SIGN - 0x00A8, //DIAERESIS - 0x00A9, //COPYRIGHT SIGN - 0x00AA, //FEMININE ORDINAL INDICATOR - 0x00AB, //LEFT-POINTING DOUBLE ANGLE QUOTATION MARK - 0x00AC, //NOT SIGN - 0x00AD, //SOFT HYPHEN - 0x00AE, //REGISTERED SIGN - 0x00AF, //MACRON - 0x00B0, //DEGREE SIGN - 0x00B1, //PLUS-MINUS SIGN - 0x00B2, //SUPERSCRIPT TWO - 0x00B3, //SUPERSCRIPT THREE - 0x00B4, //ACUTE ACCENT - 0x00B5, //MICRO SIGN - 0x00B6, //PILCROW SIGN - 0x00B7, //MIDDLE DOT - 0x00B8, //CEDILLA - 0x00B9, //SUPERSCRIPT ONE - 0x00BA, //MASCULINE ORDINAL INDICATOR - 0x00BB, //RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK - 0x00BC, //VULGAR FRACTION ONE QUARTER - 0x00BD, //VULGAR FRACTION ONE HALF - 0x00BE, //VULGAR FRACTION THREE QUARTERS - 0x00BF, //INVERTED QUESTION MARK - 0x00C0, //LATIN CAPITAL LETTER A WITH GRAVE - 0x00C1, //LATIN CAPITAL LETTER A WITH ACUTE - 0x00C2, //LATIN CAPITAL LETTER A WITH CIRCUMFLEX - 0x0102, //LATIN CAPITAL LETTER A WITH BREVE - 0x00C4, //LATIN CAPITAL LETTER A WITH DIAERESIS - 0x00C5, //LATIN CAPITAL LETTER A WITH RING ABOVE - 0x00C6, //LATIN CAPITAL LETTER AE - 0x00C7, //LATIN CAPITAL LETTER C WITH CEDILLA - 0x00C8, //LATIN CAPITAL LETTER E WITH GRAVE - 0x00C9, //LATIN CAPITAL LETTER E WITH ACUTE - 0x00CA, //LATIN CAPITAL LETTER E WITH CIRCUMFLEX - 0x00CB, //LATIN CAPITAL LETTER E WITH DIAERESIS - 0x0300, //COMBINING GRAVE ACCENT - 0x00CD, //LATIN CAPITAL LETTER I WITH ACUTE - 0x00CE, //LATIN CAPITAL LETTER I WITH CIRCUMFLEX - 0x00CF, //LATIN CAPITAL LETTER I WITH DIAERESIS - 0x0110, //LATIN CAPITAL LETTER D WITH STROKE - 0x00D1, //LATIN CAPITAL LETTER N WITH TILDE - 0x0309, //COMBINING HOOK ABOVE - 0x00D3, //LATIN CAPITAL LETTER O WITH ACUTE - 0x00D4, //LATIN CAPITAL LETTER O WITH CIRCUMFLEX - 0x01A0, //LATIN CAPITAL LETTER O WITH HORN - 0x00D6, //LATIN CAPITAL LETTER O WITH DIAERESIS - 0x00D7, //MULTIPLICATION SIGN - 0x00D8, //LATIN CAPITAL LETTER O WITH STROKE - 0x00D9, //LATIN CAPITAL LETTER U WITH GRAVE - 0x00DA, //LATIN CAPITAL LETTER U WITH ACUTE - 0x00DB, //LATIN CAPITAL LETTER U WITH CIRCUMFLEX - 0x00DC, //LATIN CAPITAL LETTER U WITH DIAERESIS - 0x01AF, //LATIN CAPITAL LETTER U WITH HORN - 0x0303, //COMBINING TILDE - 0x00DF, //LATIN SMALL LETTER SHARP S - 0x00E0, //LATIN SMALL LETTER A WITH GRAVE - 0x00E1, //LATIN SMALL LETTER A WITH ACUTE - 0x00E2, //LATIN SMALL LETTER A WITH CIRCUMFLEX - 0x0103, //LATIN SMALL LETTER A WITH BREVE - 0x00E4, //LATIN SMALL LETTER A WITH DIAERESIS - 0x00E5, //LATIN SMALL LETTER A WITH RING ABOVE - 0x00E6, //LATIN SMALL LETTER AE - 0x00E7, //LATIN SMALL LETTER C WITH CEDILLA - 0x00E8, //LATIN SMALL LETTER E WITH GRAVE - 0x00E9, //LATIN SMALL LETTER E WITH ACUTE - 0x00EA, //LATIN SMALL LETTER E WITH CIRCUMFLEX - 0x00EB, //LATIN SMALL LETTER E WITH DIAERESIS - 0x0301, //COMBINING ACUTE ACCENT - 0x00ED, //LATIN SMALL LETTER I WITH ACUTE - 0x00EE, //LATIN SMALL LETTER I WITH CIRCUMFLEX - 0x00EF, //LATIN SMALL LETTER I WITH DIAERESIS - 0x0111, //LATIN SMALL LETTER D WITH STROKE - 0x00F1, //LATIN SMALL LETTER N WITH TILDE - 0x0323, //COMBINING DOT BELOW - 0x00F3, //LATIN SMALL LETTER O WITH ACUTE - 0x00F4, //LATIN SMALL LETTER O WITH CIRCUMFLEX - 0x01A1, //LATIN SMALL LETTER O WITH HORN - 0x00F6, //LATIN SMALL LETTER O WITH DIAERESIS - 0x00F7, //DIVISION SIGN - 0x00F8, //LATIN SMALL LETTER O WITH STROKE - 0x00F9, //LATIN SMALL LETTER U WITH GRAVE - 0x00FA, //LATIN SMALL LETTER U WITH ACUTE - 0x00FB, //LATIN SMALL LETTER U WITH CIRCUMFLEX - 0x00FC, //LATIN SMALL LETTER U WITH DIAERESIS - 0x01B0, //LATIN SMALL LETTER U WITH HORN - 0x20AB, //DONG SIGN - 0x00FF, //LATIN SMALL LETTER Y WITH DIAERESIS - }, -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/cp437.go b/vendor/github.com/denisenkom/go-mssqldb/cp437.go deleted file mode 100644 index f47f8ecc7..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/cp437.go +++ /dev/null @@ -1,262 +0,0 @@ -package mssql - -var cp437 *charsetMap = &charsetMap{ - sb: [256]rune{ - 0x0000, //NULL - 0x0001, //START OF HEADING - 0x0002, //START OF TEXT - 0x0003, //END OF TEXT - 0x0004, //END OF TRANSMISSION - 0x0005, //ENQUIRY - 0x0006, //ACKNOWLEDGE - 0x0007, //BELL - 0x0008, //BACKSPACE - 0x0009, //HORIZONTAL TABULATION - 0x000a, //LINE FEED - 0x000b, //VERTICAL TABULATION - 0x000c, //FORM FEED - 0x000d, //CARRIAGE RETURN - 0x000e, //SHIFT OUT - 0x000f, //SHIFT IN - 0x0010, //DATA LINK ESCAPE - 0x0011, //DEVICE CONTROL ONE - 0x0012, //DEVICE CONTROL TWO - 0x0013, //DEVICE CONTROL THREE - 0x0014, //DEVICE CONTROL FOUR - 0x0015, //NEGATIVE ACKNOWLEDGE - 0x0016, //SYNCHRONOUS IDLE - 0x0017, //END OF TRANSMISSION BLOCK - 0x0018, //CANCEL - 0x0019, //END OF MEDIUM - 0x001a, //SUBSTITUTE - 0x001b, //ESCAPE - 0x001c, //FILE SEPARATOR - 0x001d, //GROUP SEPARATOR - 0x001e, //RECORD SEPARATOR - 0x001f, //UNIT SEPARATOR - 0x0020, //SPACE - 0x0021, //EXCLAMATION MARK - 0x0022, //QUOTATION MARK - 0x0023, //NUMBER SIGN - 0x0024, //DOLLAR SIGN - 0x0025, //PERCENT SIGN - 0x0026, //AMPERSAND - 0x0027, //APOSTROPHE - 0x0028, //LEFT PARENTHESIS - 0x0029, //RIGHT PARENTHESIS - 0x002a, //ASTERISK - 0x002b, //PLUS SIGN - 0x002c, //COMMA - 0x002d, //HYPHEN-MINUS - 0x002e, //FULL STOP - 0x002f, //SOLIDUS - 0x0030, //DIGIT ZERO - 0x0031, //DIGIT ONE - 0x0032, //DIGIT TWO - 0x0033, //DIGIT THREE - 0x0034, //DIGIT FOUR - 0x0035, //DIGIT FIVE - 0x0036, //DIGIT SIX - 0x0037, //DIGIT SEVEN - 0x0038, //DIGIT EIGHT - 0x0039, //DIGIT NINE - 0x003a, //COLON - 0x003b, //SEMICOLON - 0x003c, //LESS-THAN SIGN - 0x003d, //EQUALS SIGN - 0x003e, //GREATER-THAN SIGN - 0x003f, //QUESTION MARK - 0x0040, //COMMERCIAL AT - 0x0041, //LATIN CAPITAL LETTER A - 0x0042, //LATIN CAPITAL LETTER B - 0x0043, //LATIN CAPITAL LETTER C - 0x0044, //LATIN CAPITAL LETTER D - 0x0045, //LATIN CAPITAL LETTER E - 0x0046, //LATIN CAPITAL LETTER F - 0x0047, //LATIN CAPITAL LETTER G - 0x0048, //LATIN CAPITAL LETTER H - 0x0049, //LATIN CAPITAL LETTER I - 0x004a, //LATIN CAPITAL LETTER J - 0x004b, //LATIN CAPITAL LETTER K - 0x004c, //LATIN CAPITAL LETTER L - 0x004d, //LATIN CAPITAL LETTER M - 0x004e, //LATIN CAPITAL LETTER N - 0x004f, //LATIN CAPITAL LETTER O - 0x0050, //LATIN CAPITAL LETTER P - 0x0051, //LATIN CAPITAL LETTER Q - 0x0052, //LATIN CAPITAL LETTER R - 0x0053, //LATIN CAPITAL LETTER S - 0x0054, //LATIN CAPITAL LETTER T - 0x0055, //LATIN CAPITAL LETTER U - 0x0056, //LATIN CAPITAL LETTER V - 0x0057, //LATIN CAPITAL LETTER W - 0x0058, //LATIN CAPITAL LETTER X - 0x0059, //LATIN CAPITAL LETTER Y - 0x005a, //LATIN CAPITAL LETTER Z - 0x005b, //LEFT SQUARE BRACKET - 0x005c, //REVERSE SOLIDUS - 0x005d, //RIGHT SQUARE BRACKET - 0x005e, //CIRCUMFLEX ACCENT - 0x005f, //LOW LINE - 0x0060, //GRAVE ACCENT - 0x0061, //LATIN SMALL LETTER A - 0x0062, //LATIN SMALL LETTER B - 0x0063, //LATIN SMALL LETTER C - 0x0064, //LATIN SMALL LETTER D - 0x0065, //LATIN SMALL LETTER E - 0x0066, //LATIN SMALL LETTER F - 0x0067, //LATIN SMALL LETTER G - 0x0068, //LATIN SMALL LETTER H - 0x0069, //LATIN SMALL LETTER I - 0x006a, //LATIN SMALL LETTER J - 0x006b, //LATIN SMALL LETTER K - 0x006c, //LATIN SMALL LETTER L - 0x006d, //LATIN SMALL LETTER M - 0x006e, //LATIN SMALL LETTER N - 0x006f, //LATIN SMALL LETTER O - 0x0070, //LATIN SMALL LETTER P - 0x0071, //LATIN SMALL LETTER Q - 0x0072, //LATIN SMALL LETTER R - 0x0073, //LATIN SMALL LETTER S - 0x0074, //LATIN SMALL LETTER T - 0x0075, //LATIN SMALL LETTER U - 0x0076, //LATIN SMALL LETTER V - 0x0077, //LATIN SMALL LETTER W - 0x0078, //LATIN SMALL LETTER X - 0x0079, //LATIN SMALL LETTER Y - 0x007a, //LATIN SMALL LETTER Z - 0x007b, //LEFT CURLY BRACKET - 0x007c, //VERTICAL LINE - 0x007d, //RIGHT CURLY BRACKET - 0x007e, //TILDE - 0x007f, //DELETE - 0x00c7, //LATIN CAPITAL LETTER C WITH CEDILLA - 0x00fc, //LATIN SMALL LETTER U WITH DIAERESIS - 0x00e9, //LATIN SMALL LETTER E WITH ACUTE - 0x00e2, //LATIN SMALL LETTER A WITH CIRCUMFLEX - 0x00e4, //LATIN SMALL LETTER A WITH DIAERESIS - 0x00e0, //LATIN SMALL LETTER A WITH GRAVE - 0x00e5, //LATIN SMALL LETTER A WITH RING ABOVE - 0x00e7, //LATIN SMALL LETTER C WITH CEDILLA - 0x00ea, //LATIN SMALL LETTER E WITH CIRCUMFLEX - 0x00eb, //LATIN SMALL LETTER E WITH DIAERESIS - 0x00e8, //LATIN SMALL LETTER E WITH GRAVE - 0x00ef, //LATIN SMALL LETTER I WITH DIAERESIS - 0x00ee, //LATIN SMALL LETTER I WITH CIRCUMFLEX - 0x00ec, //LATIN SMALL LETTER I WITH GRAVE - 0x00c4, //LATIN CAPITAL LETTER A WITH DIAERESIS - 0x00c5, //LATIN CAPITAL LETTER A WITH RING ABOVE - 0x00c9, //LATIN CAPITAL LETTER E WITH ACUTE - 0x00e6, //LATIN SMALL LIGATURE AE - 0x00c6, //LATIN CAPITAL LIGATURE AE - 0x00f4, //LATIN SMALL LETTER O WITH CIRCUMFLEX - 0x00f6, //LATIN SMALL LETTER O WITH DIAERESIS - 0x00f2, //LATIN SMALL LETTER O WITH GRAVE - 0x00fb, //LATIN SMALL LETTER U WITH CIRCUMFLEX - 0x00f9, //LATIN SMALL LETTER U WITH GRAVE - 0x00ff, //LATIN SMALL LETTER Y WITH DIAERESIS - 0x00d6, //LATIN CAPITAL LETTER O WITH DIAERESIS - 0x00dc, //LATIN CAPITAL LETTER U WITH DIAERESIS - 0x00a2, //CENT SIGN - 0x00a3, //POUND SIGN - 0x00a5, //YEN SIGN - 0x20a7, //PESETA SIGN - 0x0192, //LATIN SMALL LETTER F WITH HOOK - 0x00e1, //LATIN SMALL LETTER A WITH ACUTE - 0x00ed, //LATIN SMALL LETTER I WITH ACUTE - 0x00f3, //LATIN SMALL LETTER O WITH ACUTE - 0x00fa, //LATIN SMALL LETTER U WITH ACUTE - 0x00f1, //LATIN SMALL LETTER N WITH TILDE - 0x00d1, //LATIN CAPITAL LETTER N WITH TILDE - 0x00aa, //FEMININE ORDINAL INDICATOR - 0x00ba, //MASCULINE ORDINAL INDICATOR - 0x00bf, //INVERTED QUESTION MARK - 0x2310, //REVERSED NOT SIGN - 0x00ac, //NOT SIGN - 0x00bd, //VULGAR FRACTION ONE HALF - 0x00bc, //VULGAR FRACTION ONE QUARTER - 0x00a1, //INVERTED EXCLAMATION MARK - 0x00ab, //LEFT-POINTING DOUBLE ANGLE QUOTATION MARK - 0x00bb, //RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK - 0x2591, //LIGHT SHADE - 0x2592, //MEDIUM SHADE - 0x2593, //DARK SHADE - 0x2502, //BOX DRAWINGS LIGHT VERTICAL - 0x2524, //BOX DRAWINGS LIGHT VERTICAL AND LEFT - 0x2561, //BOX DRAWINGS VERTICAL SINGLE AND LEFT DOUBLE - 0x2562, //BOX DRAWINGS VERTICAL DOUBLE AND LEFT SINGLE - 0x2556, //BOX DRAWINGS DOWN DOUBLE AND LEFT SINGLE - 0x2555, //BOX DRAWINGS DOWN SINGLE AND LEFT DOUBLE - 0x2563, //BOX DRAWINGS DOUBLE VERTICAL AND LEFT - 0x2551, //BOX DRAWINGS DOUBLE VERTICAL - 0x2557, //BOX DRAWINGS DOUBLE DOWN AND LEFT - 0x255d, //BOX DRAWINGS DOUBLE UP AND LEFT - 0x255c, //BOX DRAWINGS UP DOUBLE AND LEFT SINGLE - 0x255b, //BOX DRAWINGS UP SINGLE AND LEFT DOUBLE - 0x2510, //BOX DRAWINGS LIGHT DOWN AND LEFT - 0x2514, //BOX DRAWINGS LIGHT UP AND RIGHT - 0x2534, //BOX DRAWINGS LIGHT UP AND HORIZONTAL - 0x252c, //BOX DRAWINGS LIGHT DOWN AND HORIZONTAL - 0x251c, //BOX DRAWINGS LIGHT VERTICAL AND RIGHT - 0x2500, //BOX DRAWINGS LIGHT HORIZONTAL - 0x253c, //BOX DRAWINGS LIGHT VERTICAL AND HORIZONTAL - 0x255e, //BOX DRAWINGS VERTICAL SINGLE AND RIGHT DOUBLE - 0x255f, //BOX DRAWINGS VERTICAL DOUBLE AND RIGHT SINGLE - 0x255a, //BOX DRAWINGS DOUBLE UP AND RIGHT - 0x2554, //BOX DRAWINGS DOUBLE DOWN AND RIGHT - 0x2569, //BOX DRAWINGS DOUBLE UP AND HORIZONTAL - 0x2566, //BOX DRAWINGS DOUBLE DOWN AND HORIZONTAL - 0x2560, //BOX DRAWINGS DOUBLE VERTICAL AND RIGHT - 0x2550, //BOX DRAWINGS DOUBLE HORIZONTAL - 0x256c, //BOX DRAWINGS DOUBLE VERTICAL AND HORIZONTAL - 0x2567, //BOX DRAWINGS UP SINGLE AND HORIZONTAL DOUBLE - 0x2568, //BOX DRAWINGS UP DOUBLE AND HORIZONTAL SINGLE - 0x2564, //BOX DRAWINGS DOWN SINGLE AND HORIZONTAL DOUBLE - 0x2565, //BOX DRAWINGS DOWN DOUBLE AND HORIZONTAL SINGLE - 0x2559, //BOX DRAWINGS UP DOUBLE AND RIGHT SINGLE - 0x2558, //BOX DRAWINGS UP SINGLE AND RIGHT DOUBLE - 0x2552, //BOX DRAWINGS DOWN SINGLE AND RIGHT DOUBLE - 0x2553, //BOX DRAWINGS DOWN DOUBLE AND RIGHT SINGLE - 0x256b, //BOX DRAWINGS VERTICAL DOUBLE AND HORIZONTAL SINGLE - 0x256a, //BOX DRAWINGS VERTICAL SINGLE AND HORIZONTAL DOUBLE - 0x2518, //BOX DRAWINGS LIGHT UP AND LEFT - 0x250c, //BOX DRAWINGS LIGHT DOWN AND RIGHT - 0x2588, //FULL BLOCK - 0x2584, //LOWER HALF BLOCK - 0x258c, //LEFT HALF BLOCK - 0x2590, //RIGHT HALF BLOCK - 0x2580, //UPPER HALF BLOCK - 0x03b1, //GREEK SMALL LETTER ALPHA - 0x00df, //LATIN SMALL LETTER SHARP S - 0x0393, //GREEK CAPITAL LETTER GAMMA - 0x03c0, //GREEK SMALL LETTER PI - 0x03a3, //GREEK CAPITAL LETTER SIGMA - 0x03c3, //GREEK SMALL LETTER SIGMA - 0x00b5, //MICRO SIGN - 0x03c4, //GREEK SMALL LETTER TAU - 0x03a6, //GREEK CAPITAL LETTER PHI - 0x0398, //GREEK CAPITAL LETTER THETA - 0x03a9, //GREEK CAPITAL LETTER OMEGA - 0x03b4, //GREEK SMALL LETTER DELTA - 0x221e, //INFINITY - 0x03c6, //GREEK SMALL LETTER PHI - 0x03b5, //GREEK SMALL LETTER EPSILON - 0x2229, //INTERSECTION - 0x2261, //IDENTICAL TO - 0x00b1, //PLUS-MINUS SIGN - 0x2265, //GREATER-THAN OR EQUAL TO - 0x2264, //LESS-THAN OR EQUAL TO - 0x2320, //TOP HALF INTEGRAL - 0x2321, //BOTTOM HALF INTEGRAL - 0x00f7, //DIVISION SIGN - 0x2248, //ALMOST EQUAL TO - 0x00b0, //DEGREE SIGN - 0x2219, //BULLET OPERATOR - 0x00b7, //MIDDLE DOT - 0x221a, //SQUARE ROOT - 0x207f, //SUPERSCRIPT LATIN SMALL LETTER N - 0x00b2, //SUPERSCRIPT TWO - 0x25a0, //BLACK SQUARE - 0x00a0, //NO-BREAK SPACE - }, -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/cp850.go b/vendor/github.com/denisenkom/go-mssqldb/cp850.go deleted file mode 100644 index e6b3d1690..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/cp850.go +++ /dev/null @@ -1,262 +0,0 @@ -package mssql - -var cp850 *charsetMap = &charsetMap{ - sb: [256]rune{ - 0x0000, //NULL - 0x0001, //START OF HEADING - 0x0002, //START OF TEXT - 0x0003, //END OF TEXT - 0x0004, //END OF TRANSMISSION - 0x0005, //ENQUIRY - 0x0006, //ACKNOWLEDGE - 0x0007, //BELL - 0x0008, //BACKSPACE - 0x0009, //HORIZONTAL TABULATION - 0x000a, //LINE FEED - 0x000b, //VERTICAL TABULATION - 0x000c, //FORM FEED - 0x000d, //CARRIAGE RETURN - 0x000e, //SHIFT OUT - 0x000f, //SHIFT IN - 0x0010, //DATA LINK ESCAPE - 0x0011, //DEVICE CONTROL ONE - 0x0012, //DEVICE CONTROL TWO - 0x0013, //DEVICE CONTROL THREE - 0x0014, //DEVICE CONTROL FOUR - 0x0015, //NEGATIVE ACKNOWLEDGE - 0x0016, //SYNCHRONOUS IDLE - 0x0017, //END OF TRANSMISSION BLOCK - 0x0018, //CANCEL - 0x0019, //END OF MEDIUM - 0x001a, //SUBSTITUTE - 0x001b, //ESCAPE - 0x001c, //FILE SEPARATOR - 0x001d, //GROUP SEPARATOR - 0x001e, //RECORD SEPARATOR - 0x001f, //UNIT SEPARATOR - 0x0020, //SPACE - 0x0021, //EXCLAMATION MARK - 0x0022, //QUOTATION MARK - 0x0023, //NUMBER SIGN - 0x0024, //DOLLAR SIGN - 0x0025, //PERCENT SIGN - 0x0026, //AMPERSAND - 0x0027, //APOSTROPHE - 0x0028, //LEFT PARENTHESIS - 0x0029, //RIGHT PARENTHESIS - 0x002a, //ASTERISK - 0x002b, //PLUS SIGN - 0x002c, //COMMA - 0x002d, //HYPHEN-MINUS - 0x002e, //FULL STOP - 0x002f, //SOLIDUS - 0x0030, //DIGIT ZERO - 0x0031, //DIGIT ONE - 0x0032, //DIGIT TWO - 0x0033, //DIGIT THREE - 0x0034, //DIGIT FOUR - 0x0035, //DIGIT FIVE - 0x0036, //DIGIT SIX - 0x0037, //DIGIT SEVEN - 0x0038, //DIGIT EIGHT - 0x0039, //DIGIT NINE - 0x003a, //COLON - 0x003b, //SEMICOLON - 0x003c, //LESS-THAN SIGN - 0x003d, //EQUALS SIGN - 0x003e, //GREATER-THAN SIGN - 0x003f, //QUESTION MARK - 0x0040, //COMMERCIAL AT - 0x0041, //LATIN CAPITAL LETTER A - 0x0042, //LATIN CAPITAL LETTER B - 0x0043, //LATIN CAPITAL LETTER C - 0x0044, //LATIN CAPITAL LETTER D - 0x0045, //LATIN CAPITAL LETTER E - 0x0046, //LATIN CAPITAL LETTER F - 0x0047, //LATIN CAPITAL LETTER G - 0x0048, //LATIN CAPITAL LETTER H - 0x0049, //LATIN CAPITAL LETTER I - 0x004a, //LATIN CAPITAL LETTER J - 0x004b, //LATIN CAPITAL LETTER K - 0x004c, //LATIN CAPITAL LETTER L - 0x004d, //LATIN CAPITAL LETTER M - 0x004e, //LATIN CAPITAL LETTER N - 0x004f, //LATIN CAPITAL LETTER O - 0x0050, //LATIN CAPITAL LETTER P - 0x0051, //LATIN CAPITAL LETTER Q - 0x0052, //LATIN CAPITAL LETTER R - 0x0053, //LATIN CAPITAL LETTER S - 0x0054, //LATIN CAPITAL LETTER T - 0x0055, //LATIN CAPITAL LETTER U - 0x0056, //LATIN CAPITAL LETTER V - 0x0057, //LATIN CAPITAL LETTER W - 0x0058, //LATIN CAPITAL LETTER X - 0x0059, //LATIN CAPITAL LETTER Y - 0x005a, //LATIN CAPITAL LETTER Z - 0x005b, //LEFT SQUARE BRACKET - 0x005c, //REVERSE SOLIDUS - 0x005d, //RIGHT SQUARE BRACKET - 0x005e, //CIRCUMFLEX ACCENT - 0x005f, //LOW LINE - 0x0060, //GRAVE ACCENT - 0x0061, //LATIN SMALL LETTER A - 0x0062, //LATIN SMALL LETTER B - 0x0063, //LATIN SMALL LETTER C - 0x0064, //LATIN SMALL LETTER D - 0x0065, //LATIN SMALL LETTER E - 0x0066, //LATIN SMALL LETTER F - 0x0067, //LATIN SMALL LETTER G - 0x0068, //LATIN SMALL LETTER H - 0x0069, //LATIN SMALL LETTER I - 0x006a, //LATIN SMALL LETTER J - 0x006b, //LATIN SMALL LETTER K - 0x006c, //LATIN SMALL LETTER L - 0x006d, //LATIN SMALL LETTER M - 0x006e, //LATIN SMALL LETTER N - 0x006f, //LATIN SMALL LETTER O - 0x0070, //LATIN SMALL LETTER P - 0x0071, //LATIN SMALL LETTER Q - 0x0072, //LATIN SMALL LETTER R - 0x0073, //LATIN SMALL LETTER S - 0x0074, //LATIN SMALL LETTER T - 0x0075, //LATIN SMALL LETTER U - 0x0076, //LATIN SMALL LETTER V - 0x0077, //LATIN SMALL LETTER W - 0x0078, //LATIN SMALL LETTER X - 0x0079, //LATIN SMALL LETTER Y - 0x007a, //LATIN SMALL LETTER Z - 0x007b, //LEFT CURLY BRACKET - 0x007c, //VERTICAL LINE - 0x007d, //RIGHT CURLY BRACKET - 0x007e, //TILDE - 0x007f, //DELETE - 0x00c7, //LATIN CAPITAL LETTER C WITH CEDILLA - 0x00fc, //LATIN SMALL LETTER U WITH DIAERESIS - 0x00e9, //LATIN SMALL LETTER E WITH ACUTE - 0x00e2, //LATIN SMALL LETTER A WITH CIRCUMFLEX - 0x00e4, //LATIN SMALL LETTER A WITH DIAERESIS - 0x00e0, //LATIN SMALL LETTER A WITH GRAVE - 0x00e5, //LATIN SMALL LETTER A WITH RING ABOVE - 0x00e7, //LATIN SMALL LETTER C WITH CEDILLA - 0x00ea, //LATIN SMALL LETTER E WITH CIRCUMFLEX - 0x00eb, //LATIN SMALL LETTER E WITH DIAERESIS - 0x00e8, //LATIN SMALL LETTER E WITH GRAVE - 0x00ef, //LATIN SMALL LETTER I WITH DIAERESIS - 0x00ee, //LATIN SMALL LETTER I WITH CIRCUMFLEX - 0x00ec, //LATIN SMALL LETTER I WITH GRAVE - 0x00c4, //LATIN CAPITAL LETTER A WITH DIAERESIS - 0x00c5, //LATIN CAPITAL LETTER A WITH RING ABOVE - 0x00c9, //LATIN CAPITAL LETTER E WITH ACUTE - 0x00e6, //LATIN SMALL LIGATURE AE - 0x00c6, //LATIN CAPITAL LIGATURE AE - 0x00f4, //LATIN SMALL LETTER O WITH CIRCUMFLEX - 0x00f6, //LATIN SMALL LETTER O WITH DIAERESIS - 0x00f2, //LATIN SMALL LETTER O WITH GRAVE - 0x00fb, //LATIN SMALL LETTER U WITH CIRCUMFLEX - 0x00f9, //LATIN SMALL LETTER U WITH GRAVE - 0x00ff, //LATIN SMALL LETTER Y WITH DIAERESIS - 0x00d6, //LATIN CAPITAL LETTER O WITH DIAERESIS - 0x00dc, //LATIN CAPITAL LETTER U WITH DIAERESIS - 0x00f8, //LATIN SMALL LETTER O WITH STROKE - 0x00a3, //POUND SIGN - 0x00d8, //LATIN CAPITAL LETTER O WITH STROKE - 0x00d7, //MULTIPLICATION SIGN - 0x0192, //LATIN SMALL LETTER F WITH HOOK - 0x00e1, //LATIN SMALL LETTER A WITH ACUTE - 0x00ed, //LATIN SMALL LETTER I WITH ACUTE - 0x00f3, //LATIN SMALL LETTER O WITH ACUTE - 0x00fa, //LATIN SMALL LETTER U WITH ACUTE - 0x00f1, //LATIN SMALL LETTER N WITH TILDE - 0x00d1, //LATIN CAPITAL LETTER N WITH TILDE - 0x00aa, //FEMININE ORDINAL INDICATOR - 0x00ba, //MASCULINE ORDINAL INDICATOR - 0x00bf, //INVERTED QUESTION MARK - 0x00ae, //REGISTERED SIGN - 0x00ac, //NOT SIGN - 0x00bd, //VULGAR FRACTION ONE HALF - 0x00bc, //VULGAR FRACTION ONE QUARTER - 0x00a1, //INVERTED EXCLAMATION MARK - 0x00ab, //LEFT-POINTING DOUBLE ANGLE QUOTATION MARK - 0x00bb, //RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK - 0x2591, //LIGHT SHADE - 0x2592, //MEDIUM SHADE - 0x2593, //DARK SHADE - 0x2502, //BOX DRAWINGS LIGHT VERTICAL - 0x2524, //BOX DRAWINGS LIGHT VERTICAL AND LEFT - 0x00c1, //LATIN CAPITAL LETTER A WITH ACUTE - 0x00c2, //LATIN CAPITAL LETTER A WITH CIRCUMFLEX - 0x00c0, //LATIN CAPITAL LETTER A WITH GRAVE - 0x00a9, //COPYRIGHT SIGN - 0x2563, //BOX DRAWINGS DOUBLE VERTICAL AND LEFT - 0x2551, //BOX DRAWINGS DOUBLE VERTICAL - 0x2557, //BOX DRAWINGS DOUBLE DOWN AND LEFT - 0x255d, //BOX DRAWINGS DOUBLE UP AND LEFT - 0x00a2, //CENT SIGN - 0x00a5, //YEN SIGN - 0x2510, //BOX DRAWINGS LIGHT DOWN AND LEFT - 0x2514, //BOX DRAWINGS LIGHT UP AND RIGHT - 0x2534, //BOX DRAWINGS LIGHT UP AND HORIZONTAL - 0x252c, //BOX DRAWINGS LIGHT DOWN AND HORIZONTAL - 0x251c, //BOX DRAWINGS LIGHT VERTICAL AND RIGHT - 0x2500, //BOX DRAWINGS LIGHT HORIZONTAL - 0x253c, //BOX DRAWINGS LIGHT VERTICAL AND HORIZONTAL - 0x00e3, //LATIN SMALL LETTER A WITH TILDE - 0x00c3, //LATIN CAPITAL LETTER A WITH TILDE - 0x255a, //BOX DRAWINGS DOUBLE UP AND RIGHT - 0x2554, //BOX DRAWINGS DOUBLE DOWN AND RIGHT - 0x2569, //BOX DRAWINGS DOUBLE UP AND HORIZONTAL - 0x2566, //BOX DRAWINGS DOUBLE DOWN AND HORIZONTAL - 0x2560, //BOX DRAWINGS DOUBLE VERTICAL AND RIGHT - 0x2550, //BOX DRAWINGS DOUBLE HORIZONTAL - 0x256c, //BOX DRAWINGS DOUBLE VERTICAL AND HORIZONTAL - 0x00a4, //CURRENCY SIGN - 0x00f0, //LATIN SMALL LETTER ETH - 0x00d0, //LATIN CAPITAL LETTER ETH - 0x00ca, //LATIN CAPITAL LETTER E WITH CIRCUMFLEX - 0x00cb, //LATIN CAPITAL LETTER E WITH DIAERESIS - 0x00c8, //LATIN CAPITAL LETTER E WITH GRAVE - 0x0131, //LATIN SMALL LETTER DOTLESS I - 0x00cd, //LATIN CAPITAL LETTER I WITH ACUTE - 0x00ce, //LATIN CAPITAL LETTER I WITH CIRCUMFLEX - 0x00cf, //LATIN CAPITAL LETTER I WITH DIAERESIS - 0x2518, //BOX DRAWINGS LIGHT UP AND LEFT - 0x250c, //BOX DRAWINGS LIGHT DOWN AND RIGHT - 0x2588, //FULL BLOCK - 0x2584, //LOWER HALF BLOCK - 0x00a6, //BROKEN BAR - 0x00cc, //LATIN CAPITAL LETTER I WITH GRAVE - 0x2580, //UPPER HALF BLOCK - 0x00d3, //LATIN CAPITAL LETTER O WITH ACUTE - 0x00df, //LATIN SMALL LETTER SHARP S - 0x00d4, //LATIN CAPITAL LETTER O WITH CIRCUMFLEX - 0x00d2, //LATIN CAPITAL LETTER O WITH GRAVE - 0x00f5, //LATIN SMALL LETTER O WITH TILDE - 0x00d5, //LATIN CAPITAL LETTER O WITH TILDE - 0x00b5, //MICRO SIGN - 0x00fe, //LATIN SMALL LETTER THORN - 0x00de, //LATIN CAPITAL LETTER THORN - 0x00da, //LATIN CAPITAL LETTER U WITH ACUTE - 0x00db, //LATIN CAPITAL LETTER U WITH CIRCUMFLEX - 0x00d9, //LATIN CAPITAL LETTER U WITH GRAVE - 0x00fd, //LATIN SMALL LETTER Y WITH ACUTE - 0x00dd, //LATIN CAPITAL LETTER Y WITH ACUTE - 0x00af, //MACRON - 0x00b4, //ACUTE ACCENT - 0x00ad, //SOFT HYPHEN - 0x00b1, //PLUS-MINUS SIGN - 0x2017, //DOUBLE LOW LINE - 0x00be, //VULGAR FRACTION THREE QUARTERS - 0x00b6, //PILCROW SIGN - 0x00a7, //SECTION SIGN - 0x00f7, //DIVISION SIGN - 0x00b8, //CEDILLA - 0x00b0, //DEGREE SIGN - 0x00a8, //DIAERESIS - 0x00b7, //MIDDLE DOT - 0x00b9, //SUPERSCRIPT ONE - 0x00b3, //SUPERSCRIPT THREE - 0x00b2, //SUPERSCRIPT TWO - 0x25a0, //BLACK SQUARE - 0x00a0, //NO-BREAK SPACE - }, -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/cp874.go b/vendor/github.com/denisenkom/go-mssqldb/cp874.go deleted file mode 100644 index 9d691a1a5..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/cp874.go +++ /dev/null @@ -1,262 +0,0 @@ -package mssql - -var cp874 *charsetMap = &charsetMap{ - sb: [256]rune{ - 0x0000, //NULL - 0x0001, //START OF HEADING - 0x0002, //START OF TEXT - 0x0003, //END OF TEXT - 0x0004, //END OF TRANSMISSION - 0x0005, //ENQUIRY - 0x0006, //ACKNOWLEDGE - 0x0007, //BELL - 0x0008, //BACKSPACE - 0x0009, //HORIZONTAL TABULATION - 0x000A, //LINE FEED - 0x000B, //VERTICAL TABULATION - 0x000C, //FORM FEED - 0x000D, //CARRIAGE RETURN - 0x000E, //SHIFT OUT - 0x000F, //SHIFT IN - 0x0010, //DATA LINK ESCAPE - 0x0011, //DEVICE CONTROL ONE - 0x0012, //DEVICE CONTROL TWO - 0x0013, //DEVICE CONTROL THREE - 0x0014, //DEVICE CONTROL FOUR - 0x0015, //NEGATIVE ACKNOWLEDGE - 0x0016, //SYNCHRONOUS IDLE - 0x0017, //END OF TRANSMISSION BLOCK - 0x0018, //CANCEL - 0x0019, //END OF MEDIUM - 0x001A, //SUBSTITUTE - 0x001B, //ESCAPE - 0x001C, //FILE SEPARATOR - 0x001D, //GROUP SEPARATOR - 0x001E, //RECORD SEPARATOR - 0x001F, //UNIT SEPARATOR - 0x0020, //SPACE - 0x0021, //EXCLAMATION MARK - 0x0022, //QUOTATION MARK - 0x0023, //NUMBER SIGN - 0x0024, //DOLLAR SIGN - 0x0025, //PERCENT SIGN - 0x0026, //AMPERSAND - 0x0027, //APOSTROPHE - 0x0028, //LEFT PARENTHESIS - 0x0029, //RIGHT PARENTHESIS - 0x002A, //ASTERISK - 0x002B, //PLUS SIGN - 0x002C, //COMMA - 0x002D, //HYPHEN-MINUS - 0x002E, //FULL STOP - 0x002F, //SOLIDUS - 0x0030, //DIGIT ZERO - 0x0031, //DIGIT ONE - 0x0032, //DIGIT TWO - 0x0033, //DIGIT THREE - 0x0034, //DIGIT FOUR - 0x0035, //DIGIT FIVE - 0x0036, //DIGIT SIX - 0x0037, //DIGIT SEVEN - 0x0038, //DIGIT EIGHT - 0x0039, //DIGIT NINE - 0x003A, //COLON - 0x003B, //SEMICOLON - 0x003C, //LESS-THAN SIGN - 0x003D, //EQUALS SIGN - 0x003E, //GREATER-THAN SIGN - 0x003F, //QUESTION MARK - 0x0040, //COMMERCIAL AT - 0x0041, //LATIN CAPITAL LETTER A - 0x0042, //LATIN CAPITAL LETTER B - 0x0043, //LATIN CAPITAL LETTER C - 0x0044, //LATIN CAPITAL LETTER D - 0x0045, //LATIN CAPITAL LETTER E - 0x0046, //LATIN CAPITAL LETTER F - 0x0047, //LATIN CAPITAL LETTER G - 0x0048, //LATIN CAPITAL LETTER H - 0x0049, //LATIN CAPITAL LETTER I - 0x004A, //LATIN CAPITAL LETTER J - 0x004B, //LATIN CAPITAL LETTER K - 0x004C, //LATIN CAPITAL LETTER L - 0x004D, //LATIN CAPITAL LETTER M - 0x004E, //LATIN CAPITAL LETTER N - 0x004F, //LATIN CAPITAL LETTER O - 0x0050, //LATIN CAPITAL LETTER P - 0x0051, //LATIN CAPITAL LETTER Q - 0x0052, //LATIN CAPITAL LETTER R - 0x0053, //LATIN CAPITAL LETTER S - 0x0054, //LATIN CAPITAL LETTER T - 0x0055, //LATIN CAPITAL LETTER U - 0x0056, //LATIN CAPITAL LETTER V - 0x0057, //LATIN CAPITAL LETTER W - 0x0058, //LATIN CAPITAL LETTER X - 0x0059, //LATIN CAPITAL LETTER Y - 0x005A, //LATIN CAPITAL LETTER Z - 0x005B, //LEFT SQUARE BRACKET - 0x005C, //REVERSE SOLIDUS - 0x005D, //RIGHT SQUARE BRACKET - 0x005E, //CIRCUMFLEX ACCENT - 0x005F, //LOW LINE - 0x0060, //GRAVE ACCENT - 0x0061, //LATIN SMALL LETTER A - 0x0062, //LATIN SMALL LETTER B - 0x0063, //LATIN SMALL LETTER C - 0x0064, //LATIN SMALL LETTER D - 0x0065, //LATIN SMALL LETTER E - 0x0066, //LATIN SMALL LETTER F - 0x0067, //LATIN SMALL LETTER G - 0x0068, //LATIN SMALL LETTER H - 0x0069, //LATIN SMALL LETTER I - 0x006A, //LATIN SMALL LETTER J - 0x006B, //LATIN SMALL LETTER K - 0x006C, //LATIN SMALL LETTER L - 0x006D, //LATIN SMALL LETTER M - 0x006E, //LATIN SMALL LETTER N - 0x006F, //LATIN SMALL LETTER O - 0x0070, //LATIN SMALL LETTER P - 0x0071, //LATIN SMALL LETTER Q - 0x0072, //LATIN SMALL LETTER R - 0x0073, //LATIN SMALL LETTER S - 0x0074, //LATIN SMALL LETTER T - 0x0075, //LATIN SMALL LETTER U - 0x0076, //LATIN SMALL LETTER V - 0x0077, //LATIN SMALL LETTER W - 0x0078, //LATIN SMALL LETTER X - 0x0079, //LATIN SMALL LETTER Y - 0x007A, //LATIN SMALL LETTER Z - 0x007B, //LEFT CURLY BRACKET - 0x007C, //VERTICAL LINE - 0x007D, //RIGHT CURLY BRACKET - 0x007E, //TILDE - 0x007F, //DELETE - 0x20AC, //EURO SIGN - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0x2026, //HORIZONTAL ELLIPSIS - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0x2018, //LEFT SINGLE QUOTATION MARK - 0x2019, //RIGHT SINGLE QUOTATION MARK - 0x201C, //LEFT DOUBLE QUOTATION MARK - 0x201D, //RIGHT DOUBLE QUOTATION MARK - 0x2022, //BULLET - 0x2013, //EN DASH - 0x2014, //EM DASH - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0x00A0, //NO-BREAK SPACE - 0x0E01, //THAI CHARACTER KO KAI - 0x0E02, //THAI CHARACTER KHO KHAI - 0x0E03, //THAI CHARACTER KHO KHUAT - 0x0E04, //THAI CHARACTER KHO KHWAI - 0x0E05, //THAI CHARACTER KHO KHON - 0x0E06, //THAI CHARACTER KHO RAKHANG - 0x0E07, //THAI CHARACTER NGO NGU - 0x0E08, //THAI CHARACTER CHO CHAN - 0x0E09, //THAI CHARACTER CHO CHING - 0x0E0A, //THAI CHARACTER CHO CHANG - 0x0E0B, //THAI CHARACTER SO SO - 0x0E0C, //THAI CHARACTER CHO CHOE - 0x0E0D, //THAI CHARACTER YO YING - 0x0E0E, //THAI CHARACTER DO CHADA - 0x0E0F, //THAI CHARACTER TO PATAK - 0x0E10, //THAI CHARACTER THO THAN - 0x0E11, //THAI CHARACTER THO NANGMONTHO - 0x0E12, //THAI CHARACTER THO PHUTHAO - 0x0E13, //THAI CHARACTER NO NEN - 0x0E14, //THAI CHARACTER DO DEK - 0x0E15, //THAI CHARACTER TO TAO - 0x0E16, //THAI CHARACTER THO THUNG - 0x0E17, //THAI CHARACTER THO THAHAN - 0x0E18, //THAI CHARACTER THO THONG - 0x0E19, //THAI CHARACTER NO NU - 0x0E1A, //THAI CHARACTER BO BAIMAI - 0x0E1B, //THAI CHARACTER PO PLA - 0x0E1C, //THAI CHARACTER PHO PHUNG - 0x0E1D, //THAI CHARACTER FO FA - 0x0E1E, //THAI CHARACTER PHO PHAN - 0x0E1F, //THAI CHARACTER FO FAN - 0x0E20, //THAI CHARACTER PHO SAMPHAO - 0x0E21, //THAI CHARACTER MO MA - 0x0E22, //THAI CHARACTER YO YAK - 0x0E23, //THAI CHARACTER RO RUA - 0x0E24, //THAI CHARACTER RU - 0x0E25, //THAI CHARACTER LO LING - 0x0E26, //THAI CHARACTER LU - 0x0E27, //THAI CHARACTER WO WAEN - 0x0E28, //THAI CHARACTER SO SALA - 0x0E29, //THAI CHARACTER SO RUSI - 0x0E2A, //THAI CHARACTER SO SUA - 0x0E2B, //THAI CHARACTER HO HIP - 0x0E2C, //THAI CHARACTER LO CHULA - 0x0E2D, //THAI CHARACTER O ANG - 0x0E2E, //THAI CHARACTER HO NOKHUK - 0x0E2F, //THAI CHARACTER PAIYANNOI - 0x0E30, //THAI CHARACTER SARA A - 0x0E31, //THAI CHARACTER MAI HAN-AKAT - 0x0E32, //THAI CHARACTER SARA AA - 0x0E33, //THAI CHARACTER SARA AM - 0x0E34, //THAI CHARACTER SARA I - 0x0E35, //THAI CHARACTER SARA II - 0x0E36, //THAI CHARACTER SARA UE - 0x0E37, //THAI CHARACTER SARA UEE - 0x0E38, //THAI CHARACTER SARA U - 0x0E39, //THAI CHARACTER SARA UU - 0x0E3A, //THAI CHARACTER PHINTHU - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0x0E3F, //THAI CURRENCY SYMBOL BAHT - 0x0E40, //THAI CHARACTER SARA E - 0x0E41, //THAI CHARACTER SARA AE - 0x0E42, //THAI CHARACTER SARA O - 0x0E43, //THAI CHARACTER SARA AI MAIMUAN - 0x0E44, //THAI CHARACTER SARA AI MAIMALAI - 0x0E45, //THAI CHARACTER LAKKHANGYAO - 0x0E46, //THAI CHARACTER MAIYAMOK - 0x0E47, //THAI CHARACTER MAITAIKHU - 0x0E48, //THAI CHARACTER MAI EK - 0x0E49, //THAI CHARACTER MAI THO - 0x0E4A, //THAI CHARACTER MAI TRI - 0x0E4B, //THAI CHARACTER MAI CHATTAWA - 0x0E4C, //THAI CHARACTER THANTHAKHAT - 0x0E4D, //THAI CHARACTER NIKHAHIT - 0x0E4E, //THAI CHARACTER YAMAKKAN - 0x0E4F, //THAI CHARACTER FONGMAN - 0x0E50, //THAI DIGIT ZERO - 0x0E51, //THAI DIGIT ONE - 0x0E52, //THAI DIGIT TWO - 0x0E53, //THAI DIGIT THREE - 0x0E54, //THAI DIGIT FOUR - 0x0E55, //THAI DIGIT FIVE - 0x0E56, //THAI DIGIT SIX - 0x0E57, //THAI DIGIT SEVEN - 0x0E58, //THAI DIGIT EIGHT - 0x0E59, //THAI DIGIT NINE - 0x0E5A, //THAI CHARACTER ANGKHANKHU - 0x0E5B, //THAI CHARACTER KHOMUT - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - }, -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/cp932.go b/vendor/github.com/denisenkom/go-mssqldb/cp932.go deleted file mode 100644 index 980c55d81..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/cp932.go +++ /dev/null @@ -1,7988 +0,0 @@ -package mssql - -var cp932 *charsetMap = &charsetMap{ - sb: [256]rune{ - 0x0000, //NULL - 0x0001, //START OF HEADING - 0x0002, //START OF TEXT - 0x0003, //END OF TEXT - 0x0004, //END OF TRANSMISSION - 0x0005, //ENQUIRY - 0x0006, //ACKNOWLEDGE - 0x0007, //BELL - 0x0008, //BACKSPACE - 0x0009, //HORIZONTAL TABULATION - 0x000A, //LINE FEED - 0x000B, //VERTICAL TABULATION - 0x000C, //FORM FEED - 0x000D, //CARRIAGE RETURN - 0x000E, //SHIFT OUT - 0x000F, //SHIFT IN - 0x0010, //DATA LINK ESCAPE - 0x0011, //DEVICE CONTROL ONE - 0x0012, //DEVICE CONTROL TWO - 0x0013, //DEVICE CONTROL THREE - 0x0014, //DEVICE CONTROL FOUR - 0x0015, //NEGATIVE ACKNOWLEDGE - 0x0016, //SYNCHRONOUS IDLE - 0x0017, //END OF TRANSMISSION BLOCK - 0x0018, //CANCEL - 0x0019, //END OF MEDIUM - 0x001A, //SUBSTITUTE - 0x001B, //ESCAPE - 0x001C, //FILE SEPARATOR - 0x001D, //GROUP SEPARATOR - 0x001E, //RECORD SEPARATOR - 0x001F, //UNIT SEPARATOR - 0x0020, //SPACE - 0x0021, //EXCLAMATION MARK - 0x0022, //QUOTATION MARK - 0x0023, //NUMBER SIGN - 0x0024, //DOLLAR SIGN - 0x0025, //PERCENT SIGN - 0x0026, //AMPERSAND - 0x0027, //APOSTROPHE - 0x0028, //LEFT PARENTHESIS - 0x0029, //RIGHT PARENTHESIS - 0x002A, //ASTERISK - 0x002B, //PLUS SIGN - 0x002C, //COMMA - 0x002D, //HYPHEN-MINUS - 0x002E, //FULL STOP - 0x002F, //SOLIDUS - 0x0030, //DIGIT ZERO - 0x0031, //DIGIT ONE - 0x0032, //DIGIT TWO - 0x0033, //DIGIT THREE - 0x0034, //DIGIT FOUR - 0x0035, //DIGIT FIVE - 0x0036, //DIGIT SIX - 0x0037, //DIGIT SEVEN - 0x0038, //DIGIT EIGHT - 0x0039, //DIGIT NINE - 0x003A, //COLON - 0x003B, //SEMICOLON - 0x003C, //LESS-THAN SIGN - 0x003D, //EQUALS SIGN - 0x003E, //GREATER-THAN SIGN - 0x003F, //QUESTION MARK - 0x0040, //COMMERCIAL AT - 0x0041, //LATIN CAPITAL LETTER A - 0x0042, //LATIN CAPITAL LETTER B - 0x0043, //LATIN CAPITAL LETTER C - 0x0044, //LATIN CAPITAL LETTER D - 0x0045, //LATIN CAPITAL LETTER E - 0x0046, //LATIN CAPITAL LETTER F - 0x0047, //LATIN CAPITAL LETTER G - 0x0048, //LATIN CAPITAL LETTER H - 0x0049, //LATIN CAPITAL LETTER I - 0x004A, //LATIN CAPITAL LETTER J - 0x004B, //LATIN CAPITAL LETTER K - 0x004C, //LATIN CAPITAL LETTER L - 0x004D, //LATIN CAPITAL LETTER M - 0x004E, //LATIN CAPITAL LETTER N - 0x004F, //LATIN CAPITAL LETTER O - 0x0050, //LATIN CAPITAL LETTER P - 0x0051, //LATIN CAPITAL LETTER Q - 0x0052, //LATIN CAPITAL LETTER R - 0x0053, //LATIN CAPITAL LETTER S - 0x0054, //LATIN CAPITAL LETTER T - 0x0055, //LATIN CAPITAL LETTER U - 0x0056, //LATIN CAPITAL LETTER V - 0x0057, //LATIN CAPITAL LETTER W - 0x0058, //LATIN CAPITAL LETTER X - 0x0059, //LATIN CAPITAL LETTER Y - 0x005A, //LATIN CAPITAL LETTER Z - 0x005B, //LEFT SQUARE BRACKET - 0x005C, //REVERSE SOLIDUS - 0x005D, //RIGHT SQUARE BRACKET - 0x005E, //CIRCUMFLEX ACCENT - 0x005F, //LOW LINE - 0x0060, //GRAVE ACCENT - 0x0061, //LATIN SMALL LETTER A - 0x0062, //LATIN SMALL LETTER B - 0x0063, //LATIN SMALL LETTER C - 0x0064, //LATIN SMALL LETTER D - 0x0065, //LATIN SMALL LETTER E - 0x0066, //LATIN SMALL LETTER F - 0x0067, //LATIN SMALL LETTER G - 0x0068, //LATIN SMALL LETTER H - 0x0069, //LATIN SMALL LETTER I - 0x006A, //LATIN SMALL LETTER J - 0x006B, //LATIN SMALL LETTER K - 0x006C, //LATIN SMALL LETTER L - 0x006D, //LATIN SMALL LETTER M - 0x006E, //LATIN SMALL LETTER N - 0x006F, //LATIN SMALL LETTER O - 0x0070, //LATIN SMALL LETTER P - 0x0071, //LATIN SMALL LETTER Q - 0x0072, //LATIN SMALL LETTER R - 0x0073, //LATIN SMALL LETTER S - 0x0074, //LATIN SMALL LETTER T - 0x0075, //LATIN SMALL LETTER U - 0x0076, //LATIN SMALL LETTER V - 0x0077, //LATIN SMALL LETTER W - 0x0078, //LATIN SMALL LETTER X - 0x0079, //LATIN SMALL LETTER Y - 0x007A, //LATIN SMALL LETTER Z - 0x007B, //LEFT CURLY BRACKET - 0x007C, //VERTICAL LINE - 0x007D, //RIGHT CURLY BRACKET - 0x007E, //TILDE - 0x007F, //DELETE - 0xFFFD, //UNDEFINED - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - 0xFFFD, //UNDEFINED - 0xFF61, //HALFWIDTH IDEOGRAPHIC FULL STOP - 0xFF62, //HALFWIDTH LEFT CORNER BRACKET - 0xFF63, //HALFWIDTH RIGHT CORNER BRACKET - 0xFF64, //HALFWIDTH IDEOGRAPHIC COMMA - 0xFF65, //HALFWIDTH KATAKANA MIDDLE DOT - 0xFF66, //HALFWIDTH KATAKANA LETTER WO - 0xFF67, //HALFWIDTH KATAKANA LETTER SMALL A - 0xFF68, //HALFWIDTH KATAKANA LETTER SMALL I - 0xFF69, //HALFWIDTH KATAKANA LETTER SMALL U - 0xFF6A, //HALFWIDTH KATAKANA LETTER SMALL E - 0xFF6B, //HALFWIDTH KATAKANA LETTER SMALL O - 0xFF6C, //HALFWIDTH KATAKANA LETTER SMALL YA - 0xFF6D, //HALFWIDTH KATAKANA LETTER SMALL YU - 0xFF6E, //HALFWIDTH KATAKANA LETTER SMALL YO - 0xFF6F, //HALFWIDTH KATAKANA LETTER SMALL TU - 0xFF70, //HALFWIDTH KATAKANA-HIRAGANA PROLONGED SOUND MARK - 0xFF71, //HALFWIDTH KATAKANA LETTER A - 0xFF72, //HALFWIDTH KATAKANA LETTER I - 0xFF73, //HALFWIDTH KATAKANA LETTER U - 0xFF74, //HALFWIDTH KATAKANA LETTER E - 0xFF75, //HALFWIDTH KATAKANA LETTER O - 0xFF76, //HALFWIDTH KATAKANA LETTER KA - 0xFF77, //HALFWIDTH KATAKANA LETTER KI - 0xFF78, //HALFWIDTH KATAKANA LETTER KU - 0xFF79, //HALFWIDTH KATAKANA LETTER KE - 0xFF7A, //HALFWIDTH KATAKANA LETTER KO - 0xFF7B, //HALFWIDTH KATAKANA LETTER SA - 0xFF7C, //HALFWIDTH KATAKANA LETTER SI - 0xFF7D, //HALFWIDTH KATAKANA LETTER SU - 0xFF7E, //HALFWIDTH KATAKANA LETTER SE - 0xFF7F, //HALFWIDTH KATAKANA LETTER SO - 0xFF80, //HALFWIDTH KATAKANA LETTER TA - 0xFF81, //HALFWIDTH KATAKANA LETTER TI - 0xFF82, //HALFWIDTH KATAKANA LETTER TU - 0xFF83, //HALFWIDTH KATAKANA LETTER TE - 0xFF84, //HALFWIDTH KATAKANA LETTER TO - 0xFF85, //HALFWIDTH KATAKANA LETTER NA - 0xFF86, //HALFWIDTH KATAKANA LETTER NI - 0xFF87, //HALFWIDTH KATAKANA LETTER NU - 0xFF88, //HALFWIDTH KATAKANA LETTER NE - 0xFF89, //HALFWIDTH KATAKANA LETTER NO - 0xFF8A, //HALFWIDTH KATAKANA LETTER HA - 0xFF8B, //HALFWIDTH KATAKANA LETTER HI - 0xFF8C, //HALFWIDTH KATAKANA LETTER HU - 0xFF8D, //HALFWIDTH KATAKANA LETTER HE - 0xFF8E, //HALFWIDTH KATAKANA LETTER HO - 0xFF8F, //HALFWIDTH KATAKANA LETTER MA - 0xFF90, //HALFWIDTH KATAKANA LETTER MI - 0xFF91, //HALFWIDTH KATAKANA LETTER MU - 0xFF92, //HALFWIDTH KATAKANA LETTER ME - 0xFF93, //HALFWIDTH KATAKANA LETTER MO - 0xFF94, //HALFWIDTH KATAKANA LETTER YA - 0xFF95, //HALFWIDTH KATAKANA LETTER YU - 0xFF96, //HALFWIDTH KATAKANA LETTER YO - 0xFF97, //HALFWIDTH KATAKANA LETTER RA - 0xFF98, //HALFWIDTH KATAKANA LETTER RI - 0xFF99, //HALFWIDTH KATAKANA LETTER RU - 0xFF9A, //HALFWIDTH KATAKANA LETTER RE - 0xFF9B, //HALFWIDTH KATAKANA LETTER RO - 0xFF9C, //HALFWIDTH KATAKANA LETTER WA - 0xFF9D, //HALFWIDTH KATAKANA LETTER N - 0xFF9E, //HALFWIDTH KATAKANA VOICED SOUND MARK - 0xFF9F, //HALFWIDTH KATAKANA SEMI-VOICED SOUND MARK - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - 0xFFFD, //UNDEFINED - }, - db: map[int]rune{ - 0x8140: 0x3000, //IDEOGRAPHIC SPACE - 0x8141: 0x3001, //IDEOGRAPHIC COMMA - 0x8142: 0x3002, //IDEOGRAPHIC FULL STOP - 0x8143: 0xFF0C, //FULLWIDTH COMMA - 0x8144: 0xFF0E, //FULLWIDTH FULL STOP - 0x8145: 0x30FB, //KATAKANA MIDDLE DOT - 0x8146: 0xFF1A, //FULLWIDTH COLON - 0x8147: 0xFF1B, //FULLWIDTH SEMICOLON - 0x8148: 0xFF1F, //FULLWIDTH QUESTION MARK - 0x8149: 0xFF01, //FULLWIDTH EXCLAMATION MARK - 0x814A: 0x309B, //KATAKANA-HIRAGANA VOICED SOUND MARK - 0x814B: 0x309C, //KATAKANA-HIRAGANA SEMI-VOICED SOUND MARK - 0x814C: 0x00B4, //ACUTE ACCENT - 0x814D: 0xFF40, //FULLWIDTH GRAVE ACCENT - 0x814E: 0x00A8, //DIAERESIS - 0x814F: 0xFF3E, //FULLWIDTH CIRCUMFLEX ACCENT - 0x8150: 0xFFE3, //FULLWIDTH MACRON - 0x8151: 0xFF3F, //FULLWIDTH LOW LINE - 0x8152: 0x30FD, //KATAKANA ITERATION MARK - 0x8153: 0x30FE, //KATAKANA VOICED ITERATION MARK - 0x8154: 0x309D, //HIRAGANA ITERATION MARK - 0x8155: 0x309E, //HIRAGANA VOICED ITERATION MARK - 0x8156: 0x3003, //DITTO MARK - 0x8157: 0x4EDD, //CJK UNIFIED IDEOGRAPH - 0x8158: 0x3005, //IDEOGRAPHIC ITERATION MARK - 0x8159: 0x3006, //IDEOGRAPHIC CLOSING MARK - 0x815A: 0x3007, //IDEOGRAPHIC NUMBER ZERO - 0x815B: 0x30FC, //KATAKANA-HIRAGANA PROLONGED SOUND MARK - 0x815C: 0x2015, //HORIZONTAL BAR - 0x815D: 0x2010, //HYPHEN - 0x815E: 0xFF0F, //FULLWIDTH SOLIDUS - 0x815F: 0xFF3C, //FULLWIDTH REVERSE SOLIDUS - 0x8160: 0xFF5E, //FULLWIDTH TILDE - 0x8161: 0x2225, //PARALLEL TO - 0x8162: 0xFF5C, //FULLWIDTH VERTICAL LINE - 0x8163: 0x2026, //HORIZONTAL ELLIPSIS - 0x8164: 0x2025, //TWO DOT LEADER - 0x8165: 0x2018, //LEFT SINGLE QUOTATION MARK - 0x8166: 0x2019, //RIGHT SINGLE QUOTATION MARK - 0x8167: 0x201C, //LEFT DOUBLE QUOTATION MARK - 0x8168: 0x201D, //RIGHT DOUBLE QUOTATION MARK - 0x8169: 0xFF08, //FULLWIDTH LEFT PARENTHESIS - 0x816A: 0xFF09, //FULLWIDTH RIGHT PARENTHESIS - 0x816B: 0x3014, //LEFT TORTOISE SHELL BRACKET - 0x816C: 0x3015, //RIGHT TORTOISE SHELL BRACKET - 0x816D: 0xFF3B, //FULLWIDTH LEFT SQUARE BRACKET - 0x816E: 0xFF3D, //FULLWIDTH RIGHT SQUARE BRACKET - 0x816F: 0xFF5B, //FULLWIDTH LEFT CURLY BRACKET - 0x8170: 0xFF5D, //FULLWIDTH RIGHT CURLY BRACKET - 0x8171: 0x3008, //LEFT ANGLE BRACKET - 0x8172: 0x3009, //RIGHT ANGLE BRACKET - 0x8173: 0x300A, //LEFT DOUBLE ANGLE BRACKET - 0x8174: 0x300B, //RIGHT DOUBLE ANGLE BRACKET - 0x8175: 0x300C, //LEFT CORNER BRACKET - 0x8176: 0x300D, //RIGHT CORNER BRACKET - 0x8177: 0x300E, //LEFT WHITE CORNER BRACKET - 0x8178: 0x300F, //RIGHT WHITE CORNER BRACKET - 0x8179: 0x3010, //LEFT BLACK LENTICULAR BRACKET - 0x817A: 0x3011, //RIGHT BLACK LENTICULAR BRACKET - 0x817B: 0xFF0B, //FULLWIDTH PLUS SIGN - 0x817C: 0xFF0D, //FULLWIDTH HYPHEN-MINUS - 0x817D: 0x00B1, //PLUS-MINUS SIGN - 0x817E: 0x00D7, //MULTIPLICATION SIGN - 0x8180: 0x00F7, //DIVISION SIGN - 0x8181: 0xFF1D, //FULLWIDTH EQUALS SIGN - 0x8182: 0x2260, //NOT EQUAL TO - 0x8183: 0xFF1C, //FULLWIDTH LESS-THAN SIGN - 0x8184: 0xFF1E, //FULLWIDTH GREATER-THAN SIGN - 0x8185: 0x2266, //LESS-THAN OVER EQUAL TO - 0x8186: 0x2267, //GREATER-THAN OVER EQUAL TO - 0x8187: 0x221E, //INFINITY - 0x8188: 0x2234, //THEREFORE - 0x8189: 0x2642, //MALE SIGN - 0x818A: 0x2640, //FEMALE SIGN - 0x818B: 0x00B0, //DEGREE SIGN - 0x818C: 0x2032, //PRIME - 0x818D: 0x2033, //DOUBLE PRIME - 0x818E: 0x2103, //DEGREE CELSIUS - 0x818F: 0xFFE5, //FULLWIDTH YEN SIGN - 0x8190: 0xFF04, //FULLWIDTH DOLLAR SIGN - 0x8191: 0xFFE0, //FULLWIDTH CENT SIGN - 0x8192: 0xFFE1, //FULLWIDTH POUND SIGN - 0x8193: 0xFF05, //FULLWIDTH PERCENT SIGN - 0x8194: 0xFF03, //FULLWIDTH NUMBER SIGN - 0x8195: 0xFF06, //FULLWIDTH AMPERSAND - 0x8196: 0xFF0A, //FULLWIDTH ASTERISK - 0x8197: 0xFF20, //FULLWIDTH COMMERCIAL AT - 0x8198: 0x00A7, //SECTION SIGN - 0x8199: 0x2606, //WHITE STAR - 0x819A: 0x2605, //BLACK STAR - 0x819B: 0x25CB, //WHITE CIRCLE - 0x819C: 0x25CF, //BLACK CIRCLE - 0x819D: 0x25CE, //BULLSEYE - 0x819E: 0x25C7, //WHITE DIAMOND - 0x819F: 0x25C6, //BLACK DIAMOND - 0x81A0: 0x25A1, //WHITE SQUARE - 0x81A1: 0x25A0, //BLACK SQUARE - 0x81A2: 0x25B3, //WHITE UP-POINTING TRIANGLE - 0x81A3: 0x25B2, //BLACK UP-POINTING TRIANGLE - 0x81A4: 0x25BD, //WHITE DOWN-POINTING TRIANGLE - 0x81A5: 0x25BC, //BLACK DOWN-POINTING TRIANGLE - 0x81A6: 0x203B, //REFERENCE MARK - 0x81A7: 0x3012, //POSTAL MARK - 0x81A8: 0x2192, //RIGHTWARDS ARROW - 0x81A9: 0x2190, //LEFTWARDS ARROW - 0x81AA: 0x2191, //UPWARDS ARROW - 0x81AB: 0x2193, //DOWNWARDS ARROW - 0x81AC: 0x3013, //GETA MARK - 0x81B8: 0x2208, //ELEMENT OF - 0x81B9: 0x220B, //CONTAINS AS MEMBER - 0x81BA: 0x2286, //SUBSET OF OR EQUAL TO - 0x81BB: 0x2287, //SUPERSET OF OR EQUAL TO - 0x81BC: 0x2282, //SUBSET OF - 0x81BD: 0x2283, //SUPERSET OF - 0x81BE: 0x222A, //UNION - 0x81BF: 0x2229, //INTERSECTION - 0x81C8: 0x2227, //LOGICAL AND - 0x81C9: 0x2228, //LOGICAL OR - 0x81CA: 0xFFE2, //FULLWIDTH NOT SIGN - 0x81CB: 0x21D2, //RIGHTWARDS DOUBLE ARROW - 0x81CC: 0x21D4, //LEFT RIGHT DOUBLE ARROW - 0x81CD: 0x2200, //FOR ALL - 0x81CE: 0x2203, //THERE EXISTS - 0x81DA: 0x2220, //ANGLE - 0x81DB: 0x22A5, //UP TACK - 0x81DC: 0x2312, //ARC - 0x81DD: 0x2202, //PARTIAL DIFFERENTIAL - 0x81DE: 0x2207, //NABLA - 0x81DF: 0x2261, //IDENTICAL TO - 0x81E0: 0x2252, //APPROXIMATELY EQUAL TO OR THE IMAGE OF - 0x81E1: 0x226A, //MUCH LESS-THAN - 0x81E2: 0x226B, //MUCH GREATER-THAN - 0x81E3: 0x221A, //SQUARE ROOT - 0x81E4: 0x223D, //REVERSED TILDE - 0x81E5: 0x221D, //PROPORTIONAL TO - 0x81E6: 0x2235, //BECAUSE - 0x81E7: 0x222B, //INTEGRAL - 0x81E8: 0x222C, //DOUBLE INTEGRAL - 0x81F0: 0x212B, //ANGSTROM SIGN - 0x81F1: 0x2030, //PER MILLE SIGN - 0x81F2: 0x266F, //MUSIC SHARP SIGN - 0x81F3: 0x266D, //MUSIC FLAT SIGN - 0x81F4: 0x266A, //EIGHTH NOTE - 0x81F5: 0x2020, //DAGGER - 0x81F6: 0x2021, //DOUBLE DAGGER - 0x81F7: 0x00B6, //PILCROW SIGN - 0x81FC: 0x25EF, //LARGE CIRCLE - 0x824F: 0xFF10, //FULLWIDTH DIGIT ZERO - 0x8250: 0xFF11, //FULLWIDTH DIGIT ONE - 0x8251: 0xFF12, //FULLWIDTH DIGIT TWO - 0x8252: 0xFF13, //FULLWIDTH DIGIT THREE - 0x8253: 0xFF14, //FULLWIDTH DIGIT FOUR - 0x8254: 0xFF15, //FULLWIDTH DIGIT FIVE - 0x8255: 0xFF16, //FULLWIDTH DIGIT SIX - 0x8256: 0xFF17, //FULLWIDTH DIGIT SEVEN - 0x8257: 0xFF18, //FULLWIDTH DIGIT EIGHT - 0x8258: 0xFF19, //FULLWIDTH DIGIT NINE - 0x8260: 0xFF21, //FULLWIDTH LATIN CAPITAL LETTER A - 0x8261: 0xFF22, //FULLWIDTH LATIN CAPITAL LETTER B - 0x8262: 0xFF23, //FULLWIDTH LATIN CAPITAL LETTER C - 0x8263: 0xFF24, //FULLWIDTH LATIN CAPITAL LETTER D - 0x8264: 0xFF25, //FULLWIDTH LATIN CAPITAL LETTER E - 0x8265: 0xFF26, //FULLWIDTH LATIN CAPITAL LETTER F - 0x8266: 0xFF27, //FULLWIDTH LATIN CAPITAL LETTER G - 0x8267: 0xFF28, //FULLWIDTH LATIN CAPITAL LETTER H - 0x8268: 0xFF29, //FULLWIDTH LATIN CAPITAL LETTER I - 0x8269: 0xFF2A, //FULLWIDTH LATIN CAPITAL LETTER J - 0x826A: 0xFF2B, //FULLWIDTH LATIN CAPITAL LETTER K - 0x826B: 0xFF2C, //FULLWIDTH LATIN CAPITAL LETTER L - 0x826C: 0xFF2D, //FULLWIDTH LATIN CAPITAL LETTER M - 0x826D: 0xFF2E, //FULLWIDTH LATIN CAPITAL LETTER N - 0x826E: 0xFF2F, //FULLWIDTH LATIN CAPITAL LETTER O - 0x826F: 0xFF30, //FULLWIDTH LATIN CAPITAL LETTER P - 0x8270: 0xFF31, //FULLWIDTH LATIN CAPITAL LETTER Q - 0x8271: 0xFF32, //FULLWIDTH LATIN CAPITAL LETTER R - 0x8272: 0xFF33, //FULLWIDTH LATIN CAPITAL LETTER S - 0x8273: 0xFF34, //FULLWIDTH LATIN CAPITAL LETTER T - 0x8274: 0xFF35, //FULLWIDTH LATIN CAPITAL LETTER U - 0x8275: 0xFF36, //FULLWIDTH LATIN CAPITAL LETTER V - 0x8276: 0xFF37, //FULLWIDTH LATIN CAPITAL LETTER W - 0x8277: 0xFF38, //FULLWIDTH LATIN CAPITAL LETTER X - 0x8278: 0xFF39, //FULLWIDTH LATIN CAPITAL LETTER Y - 0x8279: 0xFF3A, //FULLWIDTH LATIN CAPITAL LETTER Z - 0x8281: 0xFF41, //FULLWIDTH LATIN SMALL LETTER A - 0x8282: 0xFF42, //FULLWIDTH LATIN SMALL LETTER B - 0x8283: 0xFF43, //FULLWIDTH LATIN SMALL LETTER C - 0x8284: 0xFF44, //FULLWIDTH LATIN SMALL LETTER D - 0x8285: 0xFF45, //FULLWIDTH LATIN SMALL LETTER E - 0x8286: 0xFF46, //FULLWIDTH LATIN SMALL LETTER F - 0x8287: 0xFF47, //FULLWIDTH LATIN SMALL LETTER G - 0x8288: 0xFF48, //FULLWIDTH LATIN SMALL LETTER H - 0x8289: 0xFF49, //FULLWIDTH LATIN SMALL LETTER I - 0x828A: 0xFF4A, //FULLWIDTH LATIN SMALL LETTER J - 0x828B: 0xFF4B, //FULLWIDTH LATIN SMALL LETTER K - 0x828C: 0xFF4C, //FULLWIDTH LATIN SMALL LETTER L - 0x828D: 0xFF4D, //FULLWIDTH LATIN SMALL LETTER M - 0x828E: 0xFF4E, //FULLWIDTH LATIN SMALL LETTER N - 0x828F: 0xFF4F, //FULLWIDTH LATIN SMALL LETTER O - 0x8290: 0xFF50, //FULLWIDTH LATIN SMALL LETTER P - 0x8291: 0xFF51, //FULLWIDTH LATIN SMALL LETTER Q - 0x8292: 0xFF52, //FULLWIDTH LATIN SMALL LETTER R - 0x8293: 0xFF53, //FULLWIDTH LATIN SMALL LETTER S - 0x8294: 0xFF54, //FULLWIDTH LATIN SMALL LETTER T - 0x8295: 0xFF55, //FULLWIDTH LATIN SMALL LETTER U - 0x8296: 0xFF56, //FULLWIDTH LATIN SMALL LETTER V - 0x8297: 0xFF57, //FULLWIDTH LATIN SMALL LETTER W - 0x8298: 0xFF58, //FULLWIDTH LATIN SMALL LETTER X - 0x8299: 0xFF59, //FULLWIDTH LATIN SMALL LETTER Y - 0x829A: 0xFF5A, //FULLWIDTH LATIN SMALL LETTER Z - 0x829F: 0x3041, //HIRAGANA LETTER SMALL A - 0x82A0: 0x3042, //HIRAGANA LETTER A - 0x82A1: 0x3043, //HIRAGANA LETTER SMALL I - 0x82A2: 0x3044, //HIRAGANA LETTER I - 0x82A3: 0x3045, //HIRAGANA LETTER SMALL U - 0x82A4: 0x3046, //HIRAGANA LETTER U - 0x82A5: 0x3047, //HIRAGANA LETTER SMALL E - 0x82A6: 0x3048, //HIRAGANA LETTER E - 0x82A7: 0x3049, //HIRAGANA LETTER SMALL O - 0x82A8: 0x304A, //HIRAGANA LETTER O - 0x82A9: 0x304B, //HIRAGANA LETTER KA - 0x82AA: 0x304C, //HIRAGANA LETTER GA - 0x82AB: 0x304D, //HIRAGANA LETTER KI - 0x82AC: 0x304E, //HIRAGANA LETTER GI - 0x82AD: 0x304F, //HIRAGANA LETTER KU - 0x82AE: 0x3050, //HIRAGANA LETTER GU - 0x82AF: 0x3051, //HIRAGANA LETTER KE - 0x82B0: 0x3052, //HIRAGANA LETTER GE - 0x82B1: 0x3053, //HIRAGANA LETTER KO - 0x82B2: 0x3054, //HIRAGANA LETTER GO - 0x82B3: 0x3055, //HIRAGANA LETTER SA - 0x82B4: 0x3056, //HIRAGANA LETTER ZA - 0x82B5: 0x3057, //HIRAGANA LETTER SI - 0x82B6: 0x3058, //HIRAGANA LETTER ZI - 0x82B7: 0x3059, //HIRAGANA LETTER SU - 0x82B8: 0x305A, //HIRAGANA LETTER ZU - 0x82B9: 0x305B, //HIRAGANA LETTER SE - 0x82BA: 0x305C, //HIRAGANA LETTER ZE - 0x82BB: 0x305D, //HIRAGANA LETTER SO - 0x82BC: 0x305E, //HIRAGANA LETTER ZO - 0x82BD: 0x305F, //HIRAGANA LETTER TA - 0x82BE: 0x3060, //HIRAGANA LETTER DA - 0x82BF: 0x3061, //HIRAGANA LETTER TI - 0x82C0: 0x3062, //HIRAGANA LETTER DI - 0x82C1: 0x3063, //HIRAGANA LETTER SMALL TU - 0x82C2: 0x3064, //HIRAGANA LETTER TU - 0x82C3: 0x3065, //HIRAGANA LETTER DU - 0x82C4: 0x3066, //HIRAGANA LETTER TE - 0x82C5: 0x3067, //HIRAGANA LETTER DE - 0x82C6: 0x3068, //HIRAGANA LETTER TO - 0x82C7: 0x3069, //HIRAGANA LETTER DO - 0x82C8: 0x306A, //HIRAGANA LETTER NA - 0x82C9: 0x306B, //HIRAGANA LETTER NI - 0x82CA: 0x306C, //HIRAGANA LETTER NU - 0x82CB: 0x306D, //HIRAGANA LETTER NE - 0x82CC: 0x306E, //HIRAGANA LETTER NO - 0x82CD: 0x306F, //HIRAGANA LETTER HA - 0x82CE: 0x3070, //HIRAGANA LETTER BA - 0x82CF: 0x3071, //HIRAGANA LETTER PA - 0x82D0: 0x3072, //HIRAGANA LETTER HI - 0x82D1: 0x3073, //HIRAGANA LETTER BI - 0x82D2: 0x3074, //HIRAGANA LETTER PI - 0x82D3: 0x3075, //HIRAGANA LETTER HU - 0x82D4: 0x3076, //HIRAGANA LETTER BU - 0x82D5: 0x3077, //HIRAGANA LETTER PU - 0x82D6: 0x3078, //HIRAGANA LETTER HE - 0x82D7: 0x3079, //HIRAGANA LETTER BE - 0x82D8: 0x307A, //HIRAGANA LETTER PE - 0x82D9: 0x307B, //HIRAGANA LETTER HO - 0x82DA: 0x307C, //HIRAGANA LETTER BO - 0x82DB: 0x307D, //HIRAGANA LETTER PO - 0x82DC: 0x307E, //HIRAGANA LETTER MA - 0x82DD: 0x307F, //HIRAGANA LETTER MI - 0x82DE: 0x3080, //HIRAGANA LETTER MU - 0x82DF: 0x3081, //HIRAGANA LETTER ME - 0x82E0: 0x3082, //HIRAGANA LETTER MO - 0x82E1: 0x3083, //HIRAGANA LETTER SMALL YA - 0x82E2: 0x3084, //HIRAGANA LETTER YA - 0x82E3: 0x3085, //HIRAGANA LETTER SMALL YU - 0x82E4: 0x3086, //HIRAGANA LETTER YU - 0x82E5: 0x3087, //HIRAGANA LETTER SMALL YO - 0x82E6: 0x3088, //HIRAGANA LETTER YO - 0x82E7: 0x3089, //HIRAGANA LETTER RA - 0x82E8: 0x308A, //HIRAGANA LETTER RI - 0x82E9: 0x308B, //HIRAGANA LETTER RU - 0x82EA: 0x308C, //HIRAGANA LETTER RE - 0x82EB: 0x308D, //HIRAGANA LETTER RO - 0x82EC: 0x308E, //HIRAGANA LETTER SMALL WA - 0x82ED: 0x308F, //HIRAGANA LETTER WA - 0x82EE: 0x3090, //HIRAGANA LETTER WI - 0x82EF: 0x3091, //HIRAGANA LETTER WE - 0x82F0: 0x3092, //HIRAGANA LETTER WO - 0x82F1: 0x3093, //HIRAGANA LETTER N - 0x8340: 0x30A1, //KATAKANA LETTER SMALL A - 0x8341: 0x30A2, //KATAKANA LETTER A - 0x8342: 0x30A3, //KATAKANA LETTER SMALL I - 0x8343: 0x30A4, //KATAKANA LETTER I - 0x8344: 0x30A5, //KATAKANA LETTER SMALL U - 0x8345: 0x30A6, //KATAKANA LETTER U - 0x8346: 0x30A7, //KATAKANA LETTER SMALL E - 0x8347: 0x30A8, //KATAKANA LETTER E - 0x8348: 0x30A9, //KATAKANA LETTER SMALL O - 0x8349: 0x30AA, //KATAKANA LETTER O - 0x834A: 0x30AB, //KATAKANA LETTER KA - 0x834B: 0x30AC, //KATAKANA LETTER GA - 0x834C: 0x30AD, //KATAKANA LETTER KI - 0x834D: 0x30AE, //KATAKANA LETTER GI - 0x834E: 0x30AF, //KATAKANA LETTER KU - 0x834F: 0x30B0, //KATAKANA LETTER GU - 0x8350: 0x30B1, //KATAKANA LETTER KE - 0x8351: 0x30B2, //KATAKANA LETTER GE - 0x8352: 0x30B3, //KATAKANA LETTER KO - 0x8353: 0x30B4, //KATAKANA LETTER GO - 0x8354: 0x30B5, //KATAKANA LETTER SA - 0x8355: 0x30B6, //KATAKANA LETTER ZA - 0x8356: 0x30B7, //KATAKANA LETTER SI - 0x8357: 0x30B8, //KATAKANA LETTER ZI - 0x8358: 0x30B9, //KATAKANA LETTER SU - 0x8359: 0x30BA, //KATAKANA LETTER ZU - 0x835A: 0x30BB, //KATAKANA LETTER SE - 0x835B: 0x30BC, //KATAKANA LETTER ZE - 0x835C: 0x30BD, //KATAKANA LETTER SO - 0x835D: 0x30BE, //KATAKANA LETTER ZO - 0x835E: 0x30BF, //KATAKANA LETTER TA - 0x835F: 0x30C0, //KATAKANA LETTER DA - 0x8360: 0x30C1, //KATAKANA LETTER TI - 0x8361: 0x30C2, //KATAKANA LETTER DI - 0x8362: 0x30C3, //KATAKANA LETTER SMALL TU - 0x8363: 0x30C4, //KATAKANA LETTER TU - 0x8364: 0x30C5, //KATAKANA LETTER DU - 0x8365: 0x30C6, //KATAKANA LETTER TE - 0x8366: 0x30C7, //KATAKANA LETTER DE - 0x8367: 0x30C8, //KATAKANA LETTER TO - 0x8368: 0x30C9, //KATAKANA LETTER DO - 0x8369: 0x30CA, //KATAKANA LETTER NA - 0x836A: 0x30CB, //KATAKANA LETTER NI - 0x836B: 0x30CC, //KATAKANA LETTER NU - 0x836C: 0x30CD, //KATAKANA LETTER NE - 0x836D: 0x30CE, //KATAKANA LETTER NO - 0x836E: 0x30CF, //KATAKANA LETTER HA - 0x836F: 0x30D0, //KATAKANA LETTER BA - 0x8370: 0x30D1, //KATAKANA LETTER PA - 0x8371: 0x30D2, //KATAKANA LETTER HI - 0x8372: 0x30D3, //KATAKANA LETTER BI - 0x8373: 0x30D4, //KATAKANA LETTER PI - 0x8374: 0x30D5, //KATAKANA LETTER HU - 0x8375: 0x30D6, //KATAKANA LETTER BU - 0x8376: 0x30D7, //KATAKANA LETTER PU - 0x8377: 0x30D8, //KATAKANA LETTER HE - 0x8378: 0x30D9, //KATAKANA LETTER BE - 0x8379: 0x30DA, //KATAKANA LETTER PE - 0x837A: 0x30DB, //KATAKANA LETTER HO - 0x837B: 0x30DC, //KATAKANA LETTER BO - 0x837C: 0x30DD, //KATAKANA LETTER PO - 0x837D: 0x30DE, //KATAKANA LETTER MA - 0x837E: 0x30DF, //KATAKANA LETTER MI - 0x8380: 0x30E0, //KATAKANA LETTER MU - 0x8381: 0x30E1, //KATAKANA LETTER ME - 0x8382: 0x30E2, //KATAKANA LETTER MO - 0x8383: 0x30E3, //KATAKANA LETTER SMALL YA - 0x8384: 0x30E4, //KATAKANA LETTER YA - 0x8385: 0x30E5, //KATAKANA LETTER SMALL YU - 0x8386: 0x30E6, //KATAKANA LETTER YU - 0x8387: 0x30E7, //KATAKANA LETTER SMALL YO - 0x8388: 0x30E8, //KATAKANA LETTER YO - 0x8389: 0x30E9, //KATAKANA LETTER RA - 0x838A: 0x30EA, //KATAKANA LETTER RI - 0x838B: 0x30EB, //KATAKANA LETTER RU - 0x838C: 0x30EC, //KATAKANA LETTER RE - 0x838D: 0x30ED, //KATAKANA LETTER RO - 0x838E: 0x30EE, //KATAKANA LETTER SMALL WA - 0x838F: 0x30EF, //KATAKANA LETTER WA - 0x8390: 0x30F0, //KATAKANA LETTER WI - 0x8391: 0x30F1, //KATAKANA LETTER WE - 0x8392: 0x30F2, //KATAKANA LETTER WO - 0x8393: 0x30F3, //KATAKANA LETTER N - 0x8394: 0x30F4, //KATAKANA LETTER VU - 0x8395: 0x30F5, //KATAKANA LETTER SMALL KA - 0x8396: 0x30F6, //KATAKANA LETTER SMALL KE - 0x839F: 0x0391, //GREEK CAPITAL LETTER ALPHA - 0x83A0: 0x0392, //GREEK CAPITAL LETTER BETA - 0x83A1: 0x0393, //GREEK CAPITAL LETTER GAMMA - 0x83A2: 0x0394, //GREEK CAPITAL LETTER DELTA - 0x83A3: 0x0395, //GREEK CAPITAL LETTER EPSILON - 0x83A4: 0x0396, //GREEK CAPITAL LETTER ZETA - 0x83A5: 0x0397, //GREEK CAPITAL LETTER ETA - 0x83A6: 0x0398, //GREEK CAPITAL LETTER THETA - 0x83A7: 0x0399, //GREEK CAPITAL LETTER IOTA - 0x83A8: 0x039A, //GREEK CAPITAL LETTER KAPPA - 0x83A9: 0x039B, //GREEK CAPITAL LETTER LAMDA - 0x83AA: 0x039C, //GREEK CAPITAL LETTER MU - 0x83AB: 0x039D, //GREEK CAPITAL LETTER NU - 0x83AC: 0x039E, //GREEK CAPITAL LETTER XI - 0x83AD: 0x039F, //GREEK CAPITAL LETTER OMICRON - 0x83AE: 0x03A0, //GREEK CAPITAL LETTER PI - 0x83AF: 0x03A1, //GREEK CAPITAL LETTER RHO - 0x83B0: 0x03A3, //GREEK CAPITAL LETTER SIGMA - 0x83B1: 0x03A4, //GREEK CAPITAL LETTER TAU - 0x83B2: 0x03A5, //GREEK CAPITAL LETTER UPSILON - 0x83B3: 0x03A6, //GREEK CAPITAL LETTER PHI - 0x83B4: 0x03A7, //GREEK CAPITAL LETTER CHI - 0x83B5: 0x03A8, //GREEK CAPITAL LETTER PSI - 0x83B6: 0x03A9, //GREEK CAPITAL LETTER OMEGA - 0x83BF: 0x03B1, //GREEK SMALL LETTER ALPHA - 0x83C0: 0x03B2, //GREEK SMALL LETTER BETA - 0x83C1: 0x03B3, //GREEK SMALL LETTER GAMMA - 0x83C2: 0x03B4, //GREEK SMALL LETTER DELTA - 0x83C3: 0x03B5, //GREEK SMALL LETTER EPSILON - 0x83C4: 0x03B6, //GREEK SMALL LETTER ZETA - 0x83C5: 0x03B7, //GREEK SMALL LETTER ETA - 0x83C6: 0x03B8, //GREEK SMALL LETTER THETA - 0x83C7: 0x03B9, //GREEK SMALL LETTER IOTA - 0x83C8: 0x03BA, //GREEK SMALL LETTER KAPPA - 0x83C9: 0x03BB, //GREEK SMALL LETTER LAMDA - 0x83CA: 0x03BC, //GREEK SMALL LETTER MU - 0x83CB: 0x03BD, //GREEK SMALL LETTER NU - 0x83CC: 0x03BE, //GREEK SMALL LETTER XI - 0x83CD: 0x03BF, //GREEK SMALL LETTER OMICRON - 0x83CE: 0x03C0, //GREEK SMALL LETTER PI - 0x83CF: 0x03C1, //GREEK SMALL LETTER RHO - 0x83D0: 0x03C3, //GREEK SMALL LETTER SIGMA - 0x83D1: 0x03C4, //GREEK SMALL LETTER TAU - 0x83D2: 0x03C5, //GREEK SMALL LETTER UPSILON - 0x83D3: 0x03C6, //GREEK SMALL LETTER PHI - 0x83D4: 0x03C7, //GREEK SMALL LETTER CHI - 0x83D5: 0x03C8, //GREEK SMALL LETTER PSI - 0x83D6: 0x03C9, //GREEK SMALL LETTER OMEGA - 0x8440: 0x0410, //CYRILLIC CAPITAL LETTER A - 0x8441: 0x0411, //CYRILLIC CAPITAL LETTER BE - 0x8442: 0x0412, //CYRILLIC CAPITAL LETTER VE - 0x8443: 0x0413, //CYRILLIC CAPITAL LETTER GHE - 0x8444: 0x0414, //CYRILLIC CAPITAL LETTER DE - 0x8445: 0x0415, //CYRILLIC CAPITAL LETTER IE - 0x8446: 0x0401, //CYRILLIC CAPITAL LETTER IO - 0x8447: 0x0416, //CYRILLIC CAPITAL LETTER ZHE - 0x8448: 0x0417, //CYRILLIC CAPITAL LETTER ZE - 0x8449: 0x0418, //CYRILLIC CAPITAL LETTER I - 0x844A: 0x0419, //CYRILLIC CAPITAL LETTER SHORT I - 0x844B: 0x041A, //CYRILLIC CAPITAL LETTER KA - 0x844C: 0x041B, //CYRILLIC CAPITAL LETTER EL - 0x844D: 0x041C, //CYRILLIC CAPITAL LETTER EM - 0x844E: 0x041D, //CYRILLIC CAPITAL LETTER EN - 0x844F: 0x041E, //CYRILLIC CAPITAL LETTER O - 0x8450: 0x041F, //CYRILLIC CAPITAL LETTER PE - 0x8451: 0x0420, //CYRILLIC CAPITAL LETTER ER - 0x8452: 0x0421, //CYRILLIC CAPITAL LETTER ES - 0x8453: 0x0422, //CYRILLIC CAPITAL LETTER TE - 0x8454: 0x0423, //CYRILLIC CAPITAL LETTER U - 0x8455: 0x0424, //CYRILLIC CAPITAL LETTER EF - 0x8456: 0x0425, //CYRILLIC CAPITAL LETTER HA - 0x8457: 0x0426, //CYRILLIC CAPITAL LETTER TSE - 0x8458: 0x0427, //CYRILLIC CAPITAL LETTER CHE - 0x8459: 0x0428, //CYRILLIC CAPITAL LETTER SHA - 0x845A: 0x0429, //CYRILLIC CAPITAL LETTER SHCHA - 0x845B: 0x042A, //CYRILLIC CAPITAL LETTER HARD SIGN - 0x845C: 0x042B, //CYRILLIC CAPITAL LETTER YERU - 0x845D: 0x042C, //CYRILLIC CAPITAL LETTER SOFT SIGN - 0x845E: 0x042D, //CYRILLIC CAPITAL LETTER E - 0x845F: 0x042E, //CYRILLIC CAPITAL LETTER YU - 0x8460: 0x042F, //CYRILLIC CAPITAL LETTER YA - 0x8470: 0x0430, //CYRILLIC SMALL LETTER A - 0x8471: 0x0431, //CYRILLIC SMALL LETTER BE - 0x8472: 0x0432, //CYRILLIC SMALL LETTER VE - 0x8473: 0x0433, //CYRILLIC SMALL LETTER GHE - 0x8474: 0x0434, //CYRILLIC SMALL LETTER DE - 0x8475: 0x0435, //CYRILLIC SMALL LETTER IE - 0x8476: 0x0451, //CYRILLIC SMALL LETTER IO - 0x8477: 0x0436, //CYRILLIC SMALL LETTER ZHE - 0x8478: 0x0437, //CYRILLIC SMALL LETTER ZE - 0x8479: 0x0438, //CYRILLIC SMALL LETTER I - 0x847A: 0x0439, //CYRILLIC SMALL LETTER SHORT I - 0x847B: 0x043A, //CYRILLIC SMALL LETTER KA - 0x847C: 0x043B, //CYRILLIC SMALL LETTER EL - 0x847D: 0x043C, //CYRILLIC SMALL LETTER EM - 0x847E: 0x043D, //CYRILLIC SMALL LETTER EN - 0x8480: 0x043E, //CYRILLIC SMALL LETTER O - 0x8481: 0x043F, //CYRILLIC SMALL LETTER PE - 0x8482: 0x0440, //CYRILLIC SMALL LETTER ER - 0x8483: 0x0441, //CYRILLIC SMALL LETTER ES - 0x8484: 0x0442, //CYRILLIC SMALL LETTER TE - 0x8485: 0x0443, //CYRILLIC SMALL LETTER U - 0x8486: 0x0444, //CYRILLIC SMALL LETTER EF - 0x8487: 0x0445, //CYRILLIC SMALL LETTER HA - 0x8488: 0x0446, //CYRILLIC SMALL LETTER TSE - 0x8489: 0x0447, //CYRILLIC SMALL LETTER CHE - 0x848A: 0x0448, //CYRILLIC SMALL LETTER SHA - 0x848B: 0x0449, //CYRILLIC SMALL LETTER SHCHA - 0x848C: 0x044A, //CYRILLIC SMALL LETTER HARD SIGN - 0x848D: 0x044B, //CYRILLIC SMALL LETTER YERU - 0x848E: 0x044C, //CYRILLIC SMALL LETTER SOFT SIGN - 0x848F: 0x044D, //CYRILLIC SMALL LETTER E - 0x8490: 0x044E, //CYRILLIC SMALL LETTER YU - 0x8491: 0x044F, //CYRILLIC SMALL LETTER YA - 0x849F: 0x2500, //BOX DRAWINGS LIGHT HORIZONTAL - 0x84A0: 0x2502, //BOX DRAWINGS LIGHT VERTICAL - 0x84A1: 0x250C, //BOX DRAWINGS LIGHT DOWN AND RIGHT - 0x84A2: 0x2510, //BOX DRAWINGS LIGHT DOWN AND LEFT - 0x84A3: 0x2518, //BOX DRAWINGS LIGHT UP AND LEFT - 0x84A4: 0x2514, //BOX DRAWINGS LIGHT UP AND RIGHT - 0x84A5: 0x251C, //BOX DRAWINGS LIGHT VERTICAL AND RIGHT - 0x84A6: 0x252C, //BOX DRAWINGS LIGHT DOWN AND HORIZONTAL - 0x84A7: 0x2524, //BOX DRAWINGS LIGHT VERTICAL AND LEFT - 0x84A8: 0x2534, //BOX DRAWINGS LIGHT UP AND HORIZONTAL - 0x84A9: 0x253C, //BOX DRAWINGS LIGHT VERTICAL AND HORIZONTAL - 0x84AA: 0x2501, //BOX DRAWINGS HEAVY HORIZONTAL - 0x84AB: 0x2503, //BOX DRAWINGS HEAVY VERTICAL - 0x84AC: 0x250F, //BOX DRAWINGS HEAVY DOWN AND RIGHT - 0x84AD: 0x2513, //BOX DRAWINGS HEAVY DOWN AND LEFT - 0x84AE: 0x251B, //BOX DRAWINGS HEAVY UP AND LEFT - 0x84AF: 0x2517, //BOX DRAWINGS HEAVY UP AND RIGHT - 0x84B0: 0x2523, //BOX DRAWINGS HEAVY VERTICAL AND RIGHT - 0x84B1: 0x2533, //BOX DRAWINGS HEAVY DOWN AND HORIZONTAL - 0x84B2: 0x252B, //BOX DRAWINGS HEAVY VERTICAL AND LEFT - 0x84B3: 0x253B, //BOX DRAWINGS HEAVY UP AND HORIZONTAL - 0x84B4: 0x254B, //BOX DRAWINGS HEAVY VERTICAL AND HORIZONTAL - 0x84B5: 0x2520, //BOX DRAWINGS VERTICAL HEAVY AND RIGHT LIGHT - 0x84B6: 0x252F, //BOX DRAWINGS DOWN LIGHT AND HORIZONTAL HEAVY - 0x84B7: 0x2528, //BOX DRAWINGS VERTICAL HEAVY AND LEFT LIGHT - 0x84B8: 0x2537, //BOX DRAWINGS UP LIGHT AND HORIZONTAL HEAVY - 0x84B9: 0x253F, //BOX DRAWINGS VERTICAL LIGHT AND HORIZONTAL HEAVY - 0x84BA: 0x251D, //BOX DRAWINGS VERTICAL LIGHT AND RIGHT HEAVY - 0x84BB: 0x2530, //BOX DRAWINGS DOWN HEAVY AND HORIZONTAL LIGHT - 0x84BC: 0x2525, //BOX DRAWINGS VERTICAL LIGHT AND LEFT HEAVY - 0x84BD: 0x2538, //BOX DRAWINGS UP HEAVY AND HORIZONTAL LIGHT - 0x84BE: 0x2542, //BOX DRAWINGS VERTICAL HEAVY AND HORIZONTAL LIGHT - 0x8740: 0x2460, //CIRCLED DIGIT ONE - 0x8741: 0x2461, //CIRCLED DIGIT TWO - 0x8742: 0x2462, //CIRCLED DIGIT THREE - 0x8743: 0x2463, //CIRCLED DIGIT FOUR - 0x8744: 0x2464, //CIRCLED DIGIT FIVE - 0x8745: 0x2465, //CIRCLED DIGIT SIX - 0x8746: 0x2466, //CIRCLED DIGIT SEVEN - 0x8747: 0x2467, //CIRCLED DIGIT EIGHT - 0x8748: 0x2468, //CIRCLED DIGIT NINE - 0x8749: 0x2469, //CIRCLED NUMBER TEN - 0x874A: 0x246A, //CIRCLED NUMBER ELEVEN - 0x874B: 0x246B, //CIRCLED NUMBER TWELVE - 0x874C: 0x246C, //CIRCLED NUMBER THIRTEEN - 0x874D: 0x246D, //CIRCLED NUMBER FOURTEEN - 0x874E: 0x246E, //CIRCLED NUMBER FIFTEEN - 0x874F: 0x246F, //CIRCLED NUMBER SIXTEEN - 0x8750: 0x2470, //CIRCLED NUMBER SEVENTEEN - 0x8751: 0x2471, //CIRCLED NUMBER EIGHTEEN - 0x8752: 0x2472, //CIRCLED NUMBER NINETEEN - 0x8753: 0x2473, //CIRCLED NUMBER TWENTY - 0x8754: 0x2160, //ROMAN NUMERAL ONE - 0x8755: 0x2161, //ROMAN NUMERAL TWO - 0x8756: 0x2162, //ROMAN NUMERAL THREE - 0x8757: 0x2163, //ROMAN NUMERAL FOUR - 0x8758: 0x2164, //ROMAN NUMERAL FIVE - 0x8759: 0x2165, //ROMAN NUMERAL SIX - 0x875A: 0x2166, //ROMAN NUMERAL SEVEN - 0x875B: 0x2167, //ROMAN NUMERAL EIGHT - 0x875C: 0x2168, //ROMAN NUMERAL NINE - 0x875D: 0x2169, //ROMAN NUMERAL TEN - 0x875F: 0x3349, //SQUARE MIRI - 0x8760: 0x3314, //SQUARE KIRO - 0x8761: 0x3322, //SQUARE SENTI - 0x8762: 0x334D, //SQUARE MEETORU - 0x8763: 0x3318, //SQUARE GURAMU - 0x8764: 0x3327, //SQUARE TON - 0x8765: 0x3303, //SQUARE AARU - 0x8766: 0x3336, //SQUARE HEKUTAARU - 0x8767: 0x3351, //SQUARE RITTORU - 0x8768: 0x3357, //SQUARE WATTO - 0x8769: 0x330D, //SQUARE KARORII - 0x876A: 0x3326, //SQUARE DORU - 0x876B: 0x3323, //SQUARE SENTO - 0x876C: 0x332B, //SQUARE PAASENTO - 0x876D: 0x334A, //SQUARE MIRIBAARU - 0x876E: 0x333B, //SQUARE PEEZI - 0x876F: 0x339C, //SQUARE MM - 0x8770: 0x339D, //SQUARE CM - 0x8771: 0x339E, //SQUARE KM - 0x8772: 0x338E, //SQUARE MG - 0x8773: 0x338F, //SQUARE KG - 0x8774: 0x33C4, //SQUARE CC - 0x8775: 0x33A1, //SQUARE M SQUARED - 0x877E: 0x337B, //SQUARE ERA NAME HEISEI - 0x8780: 0x301D, //REVERSED DOUBLE PRIME QUOTATION MARK - 0x8781: 0x301F, //LOW DOUBLE PRIME QUOTATION MARK - 0x8782: 0x2116, //NUMERO SIGN - 0x8783: 0x33CD, //SQUARE KK - 0x8784: 0x2121, //TELEPHONE SIGN - 0x8785: 0x32A4, //CIRCLED IDEOGRAPH HIGH - 0x8786: 0x32A5, //CIRCLED IDEOGRAPH CENTRE - 0x8787: 0x32A6, //CIRCLED IDEOGRAPH LOW - 0x8788: 0x32A7, //CIRCLED IDEOGRAPH LEFT - 0x8789: 0x32A8, //CIRCLED IDEOGRAPH RIGHT - 0x878A: 0x3231, //PARENTHESIZED IDEOGRAPH STOCK - 0x878B: 0x3232, //PARENTHESIZED IDEOGRAPH HAVE - 0x878C: 0x3239, //PARENTHESIZED IDEOGRAPH REPRESENT - 0x878D: 0x337E, //SQUARE ERA NAME MEIZI - 0x878E: 0x337D, //SQUARE ERA NAME TAISYOU - 0x878F: 0x337C, //SQUARE ERA NAME SYOUWA - 0x8790: 0x2252, //APPROXIMATELY EQUAL TO OR THE IMAGE OF - 0x8791: 0x2261, //IDENTICAL TO - 0x8792: 0x222B, //INTEGRAL - 0x8793: 0x222E, //CONTOUR INTEGRAL - 0x8794: 0x2211, //N-ARY SUMMATION - 0x8795: 0x221A, //SQUARE ROOT - 0x8796: 0x22A5, //UP TACK - 0x8797: 0x2220, //ANGLE - 0x8798: 0x221F, //RIGHT ANGLE - 0x8799: 0x22BF, //RIGHT TRIANGLE - 0x879A: 0x2235, //BECAUSE - 0x879B: 0x2229, //INTERSECTION - 0x879C: 0x222A, //UNION - 0x889F: 0x4E9C, //CJK UNIFIED IDEOGRAPH - 0x88A0: 0x5516, //CJK UNIFIED IDEOGRAPH - 0x88A1: 0x5A03, //CJK UNIFIED IDEOGRAPH - 0x88A2: 0x963F, //CJK UNIFIED IDEOGRAPH - 0x88A3: 0x54C0, //CJK UNIFIED IDEOGRAPH - 0x88A4: 0x611B, //CJK UNIFIED IDEOGRAPH - 0x88A5: 0x6328, //CJK UNIFIED IDEOGRAPH - 0x88A6: 0x59F6, //CJK UNIFIED IDEOGRAPH - 0x88A7: 0x9022, //CJK UNIFIED IDEOGRAPH - 0x88A8: 0x8475, //CJK UNIFIED IDEOGRAPH - 0x88A9: 0x831C, //CJK UNIFIED IDEOGRAPH - 0x88AA: 0x7A50, //CJK UNIFIED IDEOGRAPH - 0x88AB: 0x60AA, //CJK UNIFIED IDEOGRAPH - 0x88AC: 0x63E1, //CJK UNIFIED IDEOGRAPH - 0x88AD: 0x6E25, //CJK UNIFIED IDEOGRAPH - 0x88AE: 0x65ED, //CJK UNIFIED IDEOGRAPH - 0x88AF: 0x8466, //CJK UNIFIED IDEOGRAPH - 0x88B0: 0x82A6, //CJK UNIFIED IDEOGRAPH - 0x88B1: 0x9BF5, //CJK UNIFIED IDEOGRAPH - 0x88B2: 0x6893, //CJK UNIFIED IDEOGRAPH - 0x88B3: 0x5727, //CJK UNIFIED IDEOGRAPH - 0x88B4: 0x65A1, //CJK UNIFIED IDEOGRAPH - 0x88B5: 0x6271, //CJK UNIFIED IDEOGRAPH - 0x88B6: 0x5B9B, //CJK UNIFIED IDEOGRAPH - 0x88B7: 0x59D0, //CJK UNIFIED IDEOGRAPH - 0x88B8: 0x867B, //CJK UNIFIED IDEOGRAPH - 0x88B9: 0x98F4, //CJK UNIFIED IDEOGRAPH - 0x88BA: 0x7D62, //CJK UNIFIED IDEOGRAPH - 0x88BB: 0x7DBE, //CJK UNIFIED IDEOGRAPH - 0x88BC: 0x9B8E, //CJK UNIFIED IDEOGRAPH - 0x88BD: 0x6216, //CJK UNIFIED IDEOGRAPH - 0x88BE: 0x7C9F, //CJK UNIFIED IDEOGRAPH - 0x88BF: 0x88B7, //CJK UNIFIED IDEOGRAPH - 0x88C0: 0x5B89, //CJK UNIFIED IDEOGRAPH - 0x88C1: 0x5EB5, //CJK UNIFIED IDEOGRAPH - 0x88C2: 0x6309, //CJK UNIFIED IDEOGRAPH - 0x88C3: 0x6697, //CJK UNIFIED IDEOGRAPH - 0x88C4: 0x6848, //CJK UNIFIED IDEOGRAPH - 0x88C5: 0x95C7, //CJK UNIFIED IDEOGRAPH - 0x88C6: 0x978D, //CJK UNIFIED IDEOGRAPH - 0x88C7: 0x674F, //CJK UNIFIED IDEOGRAPH - 0x88C8: 0x4EE5, //CJK UNIFIED IDEOGRAPH - 0x88C9: 0x4F0A, //CJK UNIFIED IDEOGRAPH - 0x88CA: 0x4F4D, //CJK UNIFIED IDEOGRAPH - 0x88CB: 0x4F9D, //CJK UNIFIED IDEOGRAPH - 0x88CC: 0x5049, //CJK UNIFIED IDEOGRAPH - 0x88CD: 0x56F2, //CJK UNIFIED IDEOGRAPH - 0x88CE: 0x5937, //CJK UNIFIED IDEOGRAPH - 0x88CF: 0x59D4, //CJK UNIFIED IDEOGRAPH - 0x88D0: 0x5A01, //CJK UNIFIED IDEOGRAPH - 0x88D1: 0x5C09, //CJK UNIFIED IDEOGRAPH - 0x88D2: 0x60DF, //CJK UNIFIED IDEOGRAPH - 0x88D3: 0x610F, //CJK UNIFIED IDEOGRAPH - 0x88D4: 0x6170, //CJK UNIFIED IDEOGRAPH - 0x88D5: 0x6613, //CJK UNIFIED IDEOGRAPH - 0x88D6: 0x6905, //CJK UNIFIED IDEOGRAPH - 0x88D7: 0x70BA, //CJK UNIFIED IDEOGRAPH - 0x88D8: 0x754F, //CJK UNIFIED IDEOGRAPH - 0x88D9: 0x7570, //CJK UNIFIED IDEOGRAPH - 0x88DA: 0x79FB, //CJK UNIFIED IDEOGRAPH - 0x88DB: 0x7DAD, //CJK UNIFIED IDEOGRAPH - 0x88DC: 0x7DEF, //CJK UNIFIED IDEOGRAPH - 0x88DD: 0x80C3, //CJK UNIFIED IDEOGRAPH - 0x88DE: 0x840E, //CJK UNIFIED IDEOGRAPH - 0x88DF: 0x8863, //CJK UNIFIED IDEOGRAPH - 0x88E0: 0x8B02, //CJK UNIFIED IDEOGRAPH - 0x88E1: 0x9055, //CJK UNIFIED IDEOGRAPH - 0x88E2: 0x907A, //CJK UNIFIED IDEOGRAPH - 0x88E3: 0x533B, //CJK UNIFIED IDEOGRAPH - 0x88E4: 0x4E95, //CJK UNIFIED IDEOGRAPH - 0x88E5: 0x4EA5, //CJK UNIFIED IDEOGRAPH - 0x88E6: 0x57DF, //CJK UNIFIED IDEOGRAPH - 0x88E7: 0x80B2, //CJK UNIFIED IDEOGRAPH - 0x88E8: 0x90C1, //CJK UNIFIED IDEOGRAPH - 0x88E9: 0x78EF, //CJK UNIFIED IDEOGRAPH - 0x88EA: 0x4E00, //CJK UNIFIED IDEOGRAPH - 0x88EB: 0x58F1, //CJK UNIFIED IDEOGRAPH - 0x88EC: 0x6EA2, //CJK UNIFIED IDEOGRAPH - 0x88ED: 0x9038, //CJK UNIFIED IDEOGRAPH - 0x88EE: 0x7A32, //CJK UNIFIED IDEOGRAPH - 0x88EF: 0x8328, //CJK UNIFIED IDEOGRAPH - 0x88F0: 0x828B, //CJK UNIFIED IDEOGRAPH - 0x88F1: 0x9C2F, //CJK UNIFIED IDEOGRAPH - 0x88F2: 0x5141, //CJK UNIFIED IDEOGRAPH - 0x88F3: 0x5370, //CJK UNIFIED IDEOGRAPH - 0x88F4: 0x54BD, //CJK UNIFIED IDEOGRAPH - 0x88F5: 0x54E1, //CJK UNIFIED IDEOGRAPH - 0x88F6: 0x56E0, //CJK UNIFIED IDEOGRAPH - 0x88F7: 0x59FB, //CJK UNIFIED IDEOGRAPH - 0x88F8: 0x5F15, //CJK UNIFIED IDEOGRAPH - 0x88F9: 0x98F2, //CJK UNIFIED IDEOGRAPH - 0x88FA: 0x6DEB, //CJK UNIFIED IDEOGRAPH - 0x88FB: 0x80E4, //CJK UNIFIED IDEOGRAPH - 0x88FC: 0x852D, //CJK UNIFIED IDEOGRAPH - 0x8940: 0x9662, //CJK UNIFIED IDEOGRAPH - 0x8941: 0x9670, //CJK UNIFIED IDEOGRAPH - 0x8942: 0x96A0, //CJK UNIFIED IDEOGRAPH - 0x8943: 0x97FB, //CJK UNIFIED IDEOGRAPH - 0x8944: 0x540B, //CJK UNIFIED IDEOGRAPH - 0x8945: 0x53F3, //CJK UNIFIED IDEOGRAPH - 0x8946: 0x5B87, //CJK UNIFIED IDEOGRAPH - 0x8947: 0x70CF, //CJK UNIFIED IDEOGRAPH - 0x8948: 0x7FBD, //CJK UNIFIED IDEOGRAPH - 0x8949: 0x8FC2, //CJK UNIFIED IDEOGRAPH - 0x894A: 0x96E8, //CJK UNIFIED IDEOGRAPH - 0x894B: 0x536F, //CJK UNIFIED IDEOGRAPH - 0x894C: 0x9D5C, //CJK UNIFIED IDEOGRAPH - 0x894D: 0x7ABA, //CJK UNIFIED IDEOGRAPH - 0x894E: 0x4E11, //CJK UNIFIED IDEOGRAPH - 0x894F: 0x7893, //CJK UNIFIED IDEOGRAPH - 0x8950: 0x81FC, //CJK UNIFIED IDEOGRAPH - 0x8951: 0x6E26, //CJK UNIFIED IDEOGRAPH - 0x8952: 0x5618, //CJK UNIFIED IDEOGRAPH - 0x8953: 0x5504, //CJK UNIFIED IDEOGRAPH - 0x8954: 0x6B1D, //CJK UNIFIED IDEOGRAPH - 0x8955: 0x851A, //CJK UNIFIED IDEOGRAPH - 0x8956: 0x9C3B, //CJK UNIFIED IDEOGRAPH - 0x8957: 0x59E5, //CJK UNIFIED IDEOGRAPH - 0x8958: 0x53A9, //CJK UNIFIED IDEOGRAPH - 0x8959: 0x6D66, //CJK UNIFIED IDEOGRAPH - 0x895A: 0x74DC, //CJK UNIFIED IDEOGRAPH - 0x895B: 0x958F, //CJK UNIFIED IDEOGRAPH - 0x895C: 0x5642, //CJK UNIFIED IDEOGRAPH - 0x895D: 0x4E91, //CJK UNIFIED IDEOGRAPH - 0x895E: 0x904B, //CJK UNIFIED IDEOGRAPH - 0x895F: 0x96F2, //CJK UNIFIED IDEOGRAPH - 0x8960: 0x834F, //CJK UNIFIED IDEOGRAPH - 0x8961: 0x990C, //CJK UNIFIED IDEOGRAPH - 0x8962: 0x53E1, //CJK UNIFIED IDEOGRAPH - 0x8963: 0x55B6, //CJK UNIFIED IDEOGRAPH - 0x8964: 0x5B30, //CJK UNIFIED IDEOGRAPH - 0x8965: 0x5F71, //CJK UNIFIED IDEOGRAPH - 0x8966: 0x6620, //CJK UNIFIED IDEOGRAPH - 0x8967: 0x66F3, //CJK UNIFIED IDEOGRAPH - 0x8968: 0x6804, //CJK UNIFIED IDEOGRAPH - 0x8969: 0x6C38, //CJK UNIFIED IDEOGRAPH - 0x896A: 0x6CF3, //CJK UNIFIED IDEOGRAPH - 0x896B: 0x6D29, //CJK UNIFIED IDEOGRAPH - 0x896C: 0x745B, //CJK UNIFIED IDEOGRAPH - 0x896D: 0x76C8, //CJK UNIFIED IDEOGRAPH - 0x896E: 0x7A4E, //CJK UNIFIED IDEOGRAPH - 0x896F: 0x9834, //CJK UNIFIED IDEOGRAPH - 0x8970: 0x82F1, //CJK UNIFIED IDEOGRAPH - 0x8971: 0x885B, //CJK UNIFIED IDEOGRAPH - 0x8972: 0x8A60, //CJK UNIFIED IDEOGRAPH - 0x8973: 0x92ED, //CJK UNIFIED IDEOGRAPH - 0x8974: 0x6DB2, //CJK UNIFIED IDEOGRAPH - 0x8975: 0x75AB, //CJK UNIFIED IDEOGRAPH - 0x8976: 0x76CA, //CJK UNIFIED IDEOGRAPH - 0x8977: 0x99C5, //CJK UNIFIED IDEOGRAPH - 0x8978: 0x60A6, //CJK UNIFIED IDEOGRAPH - 0x8979: 0x8B01, //CJK UNIFIED IDEOGRAPH - 0x897A: 0x8D8A, //CJK UNIFIED IDEOGRAPH - 0x897B: 0x95B2, //CJK UNIFIED IDEOGRAPH - 0x897C: 0x698E, //CJK UNIFIED IDEOGRAPH - 0x897D: 0x53AD, //CJK UNIFIED IDEOGRAPH - 0x897E: 0x5186, //CJK UNIFIED IDEOGRAPH - 0x8980: 0x5712, //CJK UNIFIED IDEOGRAPH - 0x8981: 0x5830, //CJK UNIFIED IDEOGRAPH - 0x8982: 0x5944, //CJK UNIFIED IDEOGRAPH - 0x8983: 0x5BB4, //CJK UNIFIED IDEOGRAPH - 0x8984: 0x5EF6, //CJK UNIFIED IDEOGRAPH - 0x8985: 0x6028, //CJK UNIFIED IDEOGRAPH - 0x8986: 0x63A9, //CJK UNIFIED IDEOGRAPH - 0x8987: 0x63F4, //CJK UNIFIED IDEOGRAPH - 0x8988: 0x6CBF, //CJK UNIFIED IDEOGRAPH - 0x8989: 0x6F14, //CJK UNIFIED IDEOGRAPH - 0x898A: 0x708E, //CJK UNIFIED IDEOGRAPH - 0x898B: 0x7114, //CJK UNIFIED IDEOGRAPH - 0x898C: 0x7159, //CJK UNIFIED IDEOGRAPH - 0x898D: 0x71D5, //CJK UNIFIED IDEOGRAPH - 0x898E: 0x733F, //CJK UNIFIED IDEOGRAPH - 0x898F: 0x7E01, //CJK UNIFIED IDEOGRAPH - 0x8990: 0x8276, //CJK UNIFIED IDEOGRAPH - 0x8991: 0x82D1, //CJK UNIFIED IDEOGRAPH - 0x8992: 0x8597, //CJK UNIFIED IDEOGRAPH - 0x8993: 0x9060, //CJK UNIFIED IDEOGRAPH - 0x8994: 0x925B, //CJK UNIFIED IDEOGRAPH - 0x8995: 0x9D1B, //CJK UNIFIED IDEOGRAPH - 0x8996: 0x5869, //CJK UNIFIED IDEOGRAPH - 0x8997: 0x65BC, //CJK UNIFIED IDEOGRAPH - 0x8998: 0x6C5A, //CJK UNIFIED IDEOGRAPH - 0x8999: 0x7525, //CJK UNIFIED IDEOGRAPH - 0x899A: 0x51F9, //CJK UNIFIED IDEOGRAPH - 0x899B: 0x592E, //CJK UNIFIED IDEOGRAPH - 0x899C: 0x5965, //CJK UNIFIED IDEOGRAPH - 0x899D: 0x5F80, //CJK UNIFIED IDEOGRAPH - 0x899E: 0x5FDC, //CJK UNIFIED IDEOGRAPH - 0x899F: 0x62BC, //CJK UNIFIED IDEOGRAPH - 0x89A0: 0x65FA, //CJK UNIFIED IDEOGRAPH - 0x89A1: 0x6A2A, //CJK UNIFIED IDEOGRAPH - 0x89A2: 0x6B27, //CJK UNIFIED IDEOGRAPH - 0x89A3: 0x6BB4, //CJK UNIFIED IDEOGRAPH - 0x89A4: 0x738B, //CJK UNIFIED IDEOGRAPH - 0x89A5: 0x7FC1, //CJK UNIFIED IDEOGRAPH - 0x89A6: 0x8956, //CJK UNIFIED IDEOGRAPH - 0x89A7: 0x9D2C, //CJK UNIFIED IDEOGRAPH - 0x89A8: 0x9D0E, //CJK UNIFIED IDEOGRAPH - 0x89A9: 0x9EC4, //CJK UNIFIED IDEOGRAPH - 0x89AA: 0x5CA1, //CJK UNIFIED IDEOGRAPH - 0x89AB: 0x6C96, //CJK UNIFIED IDEOGRAPH - 0x89AC: 0x837B, //CJK UNIFIED IDEOGRAPH - 0x89AD: 0x5104, //CJK UNIFIED IDEOGRAPH - 0x89AE: 0x5C4B, //CJK UNIFIED IDEOGRAPH - 0x89AF: 0x61B6, //CJK UNIFIED IDEOGRAPH - 0x89B0: 0x81C6, //CJK UNIFIED IDEOGRAPH - 0x89B1: 0x6876, //CJK UNIFIED IDEOGRAPH - 0x89B2: 0x7261, //CJK UNIFIED IDEOGRAPH - 0x89B3: 0x4E59, //CJK UNIFIED IDEOGRAPH - 0x89B4: 0x4FFA, //CJK UNIFIED IDEOGRAPH - 0x89B5: 0x5378, //CJK UNIFIED IDEOGRAPH - 0x89B6: 0x6069, //CJK UNIFIED IDEOGRAPH - 0x89B7: 0x6E29, //CJK UNIFIED IDEOGRAPH - 0x89B8: 0x7A4F, //CJK UNIFIED IDEOGRAPH - 0x89B9: 0x97F3, //CJK UNIFIED IDEOGRAPH - 0x89BA: 0x4E0B, //CJK UNIFIED IDEOGRAPH - 0x89BB: 0x5316, //CJK UNIFIED IDEOGRAPH - 0x89BC: 0x4EEE, //CJK UNIFIED IDEOGRAPH - 0x89BD: 0x4F55, //CJK UNIFIED IDEOGRAPH - 0x89BE: 0x4F3D, //CJK UNIFIED IDEOGRAPH - 0x89BF: 0x4FA1, //CJK UNIFIED IDEOGRAPH - 0x89C0: 0x4F73, //CJK UNIFIED IDEOGRAPH - 0x89C1: 0x52A0, //CJK UNIFIED IDEOGRAPH - 0x89C2: 0x53EF, //CJK UNIFIED IDEOGRAPH - 0x89C3: 0x5609, //CJK UNIFIED IDEOGRAPH - 0x89C4: 0x590F, //CJK UNIFIED IDEOGRAPH - 0x89C5: 0x5AC1, //CJK UNIFIED IDEOGRAPH - 0x89C6: 0x5BB6, //CJK UNIFIED IDEOGRAPH - 0x89C7: 0x5BE1, //CJK UNIFIED IDEOGRAPH - 0x89C8: 0x79D1, //CJK UNIFIED IDEOGRAPH - 0x89C9: 0x6687, //CJK UNIFIED IDEOGRAPH - 0x89CA: 0x679C, //CJK UNIFIED IDEOGRAPH - 0x89CB: 0x67B6, //CJK UNIFIED IDEOGRAPH - 0x89CC: 0x6B4C, //CJK UNIFIED IDEOGRAPH - 0x89CD: 0x6CB3, //CJK UNIFIED IDEOGRAPH - 0x89CE: 0x706B, //CJK UNIFIED IDEOGRAPH - 0x89CF: 0x73C2, //CJK UNIFIED IDEOGRAPH - 0x89D0: 0x798D, //CJK UNIFIED IDEOGRAPH - 0x89D1: 0x79BE, //CJK UNIFIED IDEOGRAPH - 0x89D2: 0x7A3C, //CJK UNIFIED IDEOGRAPH - 0x89D3: 0x7B87, //CJK UNIFIED IDEOGRAPH - 0x89D4: 0x82B1, //CJK UNIFIED IDEOGRAPH - 0x89D5: 0x82DB, //CJK UNIFIED IDEOGRAPH - 0x89D6: 0x8304, //CJK UNIFIED IDEOGRAPH - 0x89D7: 0x8377, //CJK UNIFIED IDEOGRAPH - 0x89D8: 0x83EF, //CJK UNIFIED IDEOGRAPH - 0x89D9: 0x83D3, //CJK UNIFIED IDEOGRAPH - 0x89DA: 0x8766, //CJK UNIFIED IDEOGRAPH - 0x89DB: 0x8AB2, //CJK UNIFIED IDEOGRAPH - 0x89DC: 0x5629, //CJK UNIFIED IDEOGRAPH - 0x89DD: 0x8CA8, //CJK UNIFIED IDEOGRAPH - 0x89DE: 0x8FE6, //CJK UNIFIED IDEOGRAPH - 0x89DF: 0x904E, //CJK UNIFIED IDEOGRAPH - 0x89E0: 0x971E, //CJK UNIFIED IDEOGRAPH - 0x89E1: 0x868A, //CJK UNIFIED IDEOGRAPH - 0x89E2: 0x4FC4, //CJK UNIFIED IDEOGRAPH - 0x89E3: 0x5CE8, //CJK UNIFIED IDEOGRAPH - 0x89E4: 0x6211, //CJK UNIFIED IDEOGRAPH - 0x89E5: 0x7259, //CJK UNIFIED IDEOGRAPH - 0x89E6: 0x753B, //CJK UNIFIED IDEOGRAPH - 0x89E7: 0x81E5, //CJK UNIFIED IDEOGRAPH - 0x89E8: 0x82BD, //CJK UNIFIED IDEOGRAPH - 0x89E9: 0x86FE, //CJK UNIFIED IDEOGRAPH - 0x89EA: 0x8CC0, //CJK UNIFIED IDEOGRAPH - 0x89EB: 0x96C5, //CJK UNIFIED IDEOGRAPH - 0x89EC: 0x9913, //CJK UNIFIED IDEOGRAPH - 0x89ED: 0x99D5, //CJK UNIFIED IDEOGRAPH - 0x89EE: 0x4ECB, //CJK UNIFIED IDEOGRAPH - 0x89EF: 0x4F1A, //CJK UNIFIED IDEOGRAPH - 0x89F0: 0x89E3, //CJK UNIFIED IDEOGRAPH - 0x89F1: 0x56DE, //CJK UNIFIED IDEOGRAPH - 0x89F2: 0x584A, //CJK UNIFIED IDEOGRAPH - 0x89F3: 0x58CA, //CJK UNIFIED IDEOGRAPH - 0x89F4: 0x5EFB, //CJK UNIFIED IDEOGRAPH - 0x89F5: 0x5FEB, //CJK UNIFIED IDEOGRAPH - 0x89F6: 0x602A, //CJK UNIFIED IDEOGRAPH - 0x89F7: 0x6094, //CJK UNIFIED IDEOGRAPH - 0x89F8: 0x6062, //CJK UNIFIED IDEOGRAPH - 0x89F9: 0x61D0, //CJK UNIFIED IDEOGRAPH - 0x89FA: 0x6212, //CJK UNIFIED IDEOGRAPH - 0x89FB: 0x62D0, //CJK UNIFIED IDEOGRAPH - 0x89FC: 0x6539, //CJK UNIFIED IDEOGRAPH - 0x8A40: 0x9B41, //CJK UNIFIED IDEOGRAPH - 0x8A41: 0x6666, //CJK UNIFIED IDEOGRAPH - 0x8A42: 0x68B0, //CJK UNIFIED IDEOGRAPH - 0x8A43: 0x6D77, //CJK UNIFIED IDEOGRAPH - 0x8A44: 0x7070, //CJK UNIFIED IDEOGRAPH - 0x8A45: 0x754C, //CJK UNIFIED IDEOGRAPH - 0x8A46: 0x7686, //CJK UNIFIED IDEOGRAPH - 0x8A47: 0x7D75, //CJK UNIFIED IDEOGRAPH - 0x8A48: 0x82A5, //CJK UNIFIED IDEOGRAPH - 0x8A49: 0x87F9, //CJK UNIFIED IDEOGRAPH - 0x8A4A: 0x958B, //CJK UNIFIED IDEOGRAPH - 0x8A4B: 0x968E, //CJK UNIFIED IDEOGRAPH - 0x8A4C: 0x8C9D, //CJK UNIFIED IDEOGRAPH - 0x8A4D: 0x51F1, //CJK UNIFIED IDEOGRAPH - 0x8A4E: 0x52BE, //CJK UNIFIED IDEOGRAPH - 0x8A4F: 0x5916, //CJK UNIFIED IDEOGRAPH - 0x8A50: 0x54B3, //CJK UNIFIED IDEOGRAPH - 0x8A51: 0x5BB3, //CJK UNIFIED IDEOGRAPH - 0x8A52: 0x5D16, //CJK UNIFIED IDEOGRAPH - 0x8A53: 0x6168, //CJK UNIFIED IDEOGRAPH - 0x8A54: 0x6982, //CJK UNIFIED IDEOGRAPH - 0x8A55: 0x6DAF, //CJK UNIFIED IDEOGRAPH - 0x8A56: 0x788D, //CJK UNIFIED IDEOGRAPH - 0x8A57: 0x84CB, //CJK UNIFIED IDEOGRAPH - 0x8A58: 0x8857, //CJK UNIFIED IDEOGRAPH - 0x8A59: 0x8A72, //CJK UNIFIED IDEOGRAPH - 0x8A5A: 0x93A7, //CJK UNIFIED IDEOGRAPH - 0x8A5B: 0x9AB8, //CJK UNIFIED IDEOGRAPH - 0x8A5C: 0x6D6C, //CJK UNIFIED IDEOGRAPH - 0x8A5D: 0x99A8, //CJK UNIFIED IDEOGRAPH - 0x8A5E: 0x86D9, //CJK UNIFIED IDEOGRAPH - 0x8A5F: 0x57A3, //CJK UNIFIED IDEOGRAPH - 0x8A60: 0x67FF, //CJK UNIFIED IDEOGRAPH - 0x8A61: 0x86CE, //CJK UNIFIED IDEOGRAPH - 0x8A62: 0x920E, //CJK UNIFIED IDEOGRAPH - 0x8A63: 0x5283, //CJK UNIFIED IDEOGRAPH - 0x8A64: 0x5687, //CJK UNIFIED IDEOGRAPH - 0x8A65: 0x5404, //CJK UNIFIED IDEOGRAPH - 0x8A66: 0x5ED3, //CJK UNIFIED IDEOGRAPH - 0x8A67: 0x62E1, //CJK UNIFIED IDEOGRAPH - 0x8A68: 0x64B9, //CJK UNIFIED IDEOGRAPH - 0x8A69: 0x683C, //CJK UNIFIED IDEOGRAPH - 0x8A6A: 0x6838, //CJK UNIFIED IDEOGRAPH - 0x8A6B: 0x6BBB, //CJK UNIFIED IDEOGRAPH - 0x8A6C: 0x7372, //CJK UNIFIED IDEOGRAPH - 0x8A6D: 0x78BA, //CJK UNIFIED IDEOGRAPH - 0x8A6E: 0x7A6B, //CJK UNIFIED IDEOGRAPH - 0x8A6F: 0x899A, //CJK UNIFIED IDEOGRAPH - 0x8A70: 0x89D2, //CJK UNIFIED IDEOGRAPH - 0x8A71: 0x8D6B, //CJK UNIFIED IDEOGRAPH - 0x8A72: 0x8F03, //CJK UNIFIED IDEOGRAPH - 0x8A73: 0x90ED, //CJK UNIFIED IDEOGRAPH - 0x8A74: 0x95A3, //CJK UNIFIED IDEOGRAPH - 0x8A75: 0x9694, //CJK UNIFIED IDEOGRAPH - 0x8A76: 0x9769, //CJK UNIFIED IDEOGRAPH - 0x8A77: 0x5B66, //CJK UNIFIED IDEOGRAPH - 0x8A78: 0x5CB3, //CJK UNIFIED IDEOGRAPH - 0x8A79: 0x697D, //CJK UNIFIED IDEOGRAPH - 0x8A7A: 0x984D, //CJK UNIFIED IDEOGRAPH - 0x8A7B: 0x984E, //CJK UNIFIED IDEOGRAPH - 0x8A7C: 0x639B, //CJK UNIFIED IDEOGRAPH - 0x8A7D: 0x7B20, //CJK UNIFIED IDEOGRAPH - 0x8A7E: 0x6A2B, //CJK UNIFIED IDEOGRAPH - 0x8A80: 0x6A7F, //CJK UNIFIED IDEOGRAPH - 0x8A81: 0x68B6, //CJK UNIFIED IDEOGRAPH - 0x8A82: 0x9C0D, //CJK UNIFIED IDEOGRAPH - 0x8A83: 0x6F5F, //CJK UNIFIED IDEOGRAPH - 0x8A84: 0x5272, //CJK UNIFIED IDEOGRAPH - 0x8A85: 0x559D, //CJK UNIFIED IDEOGRAPH - 0x8A86: 0x6070, //CJK UNIFIED IDEOGRAPH - 0x8A87: 0x62EC, //CJK UNIFIED IDEOGRAPH - 0x8A88: 0x6D3B, //CJK UNIFIED IDEOGRAPH - 0x8A89: 0x6E07, //CJK UNIFIED IDEOGRAPH - 0x8A8A: 0x6ED1, //CJK UNIFIED IDEOGRAPH - 0x8A8B: 0x845B, //CJK UNIFIED IDEOGRAPH - 0x8A8C: 0x8910, //CJK UNIFIED IDEOGRAPH - 0x8A8D: 0x8F44, //CJK UNIFIED IDEOGRAPH - 0x8A8E: 0x4E14, //CJK UNIFIED IDEOGRAPH - 0x8A8F: 0x9C39, //CJK UNIFIED IDEOGRAPH - 0x8A90: 0x53F6, //CJK UNIFIED IDEOGRAPH - 0x8A91: 0x691B, //CJK UNIFIED IDEOGRAPH - 0x8A92: 0x6A3A, //CJK UNIFIED IDEOGRAPH - 0x8A93: 0x9784, //CJK UNIFIED IDEOGRAPH - 0x8A94: 0x682A, //CJK UNIFIED IDEOGRAPH - 0x8A95: 0x515C, //CJK UNIFIED IDEOGRAPH - 0x8A96: 0x7AC3, //CJK UNIFIED IDEOGRAPH - 0x8A97: 0x84B2, //CJK UNIFIED IDEOGRAPH - 0x8A98: 0x91DC, //CJK UNIFIED IDEOGRAPH - 0x8A99: 0x938C, //CJK UNIFIED IDEOGRAPH - 0x8A9A: 0x565B, //CJK UNIFIED IDEOGRAPH - 0x8A9B: 0x9D28, //CJK UNIFIED IDEOGRAPH - 0x8A9C: 0x6822, //CJK UNIFIED IDEOGRAPH - 0x8A9D: 0x8305, //CJK UNIFIED IDEOGRAPH - 0x8A9E: 0x8431, //CJK UNIFIED IDEOGRAPH - 0x8A9F: 0x7CA5, //CJK UNIFIED IDEOGRAPH - 0x8AA0: 0x5208, //CJK UNIFIED IDEOGRAPH - 0x8AA1: 0x82C5, //CJK UNIFIED IDEOGRAPH - 0x8AA2: 0x74E6, //CJK UNIFIED IDEOGRAPH - 0x8AA3: 0x4E7E, //CJK UNIFIED IDEOGRAPH - 0x8AA4: 0x4F83, //CJK UNIFIED IDEOGRAPH - 0x8AA5: 0x51A0, //CJK UNIFIED IDEOGRAPH - 0x8AA6: 0x5BD2, //CJK UNIFIED IDEOGRAPH - 0x8AA7: 0x520A, //CJK UNIFIED IDEOGRAPH - 0x8AA8: 0x52D8, //CJK UNIFIED IDEOGRAPH - 0x8AA9: 0x52E7, //CJK UNIFIED IDEOGRAPH - 0x8AAA: 0x5DFB, //CJK UNIFIED IDEOGRAPH - 0x8AAB: 0x559A, //CJK UNIFIED IDEOGRAPH - 0x8AAC: 0x582A, //CJK UNIFIED IDEOGRAPH - 0x8AAD: 0x59E6, //CJK UNIFIED IDEOGRAPH - 0x8AAE: 0x5B8C, //CJK UNIFIED IDEOGRAPH - 0x8AAF: 0x5B98, //CJK UNIFIED IDEOGRAPH - 0x8AB0: 0x5BDB, //CJK UNIFIED IDEOGRAPH - 0x8AB1: 0x5E72, //CJK UNIFIED IDEOGRAPH - 0x8AB2: 0x5E79, //CJK UNIFIED IDEOGRAPH - 0x8AB3: 0x60A3, //CJK UNIFIED IDEOGRAPH - 0x8AB4: 0x611F, //CJK UNIFIED IDEOGRAPH - 0x8AB5: 0x6163, //CJK UNIFIED IDEOGRAPH - 0x8AB6: 0x61BE, //CJK UNIFIED IDEOGRAPH - 0x8AB7: 0x63DB, //CJK UNIFIED IDEOGRAPH - 0x8AB8: 0x6562, //CJK UNIFIED IDEOGRAPH - 0x8AB9: 0x67D1, //CJK UNIFIED IDEOGRAPH - 0x8ABA: 0x6853, //CJK UNIFIED IDEOGRAPH - 0x8ABB: 0x68FA, //CJK UNIFIED IDEOGRAPH - 0x8ABC: 0x6B3E, //CJK UNIFIED IDEOGRAPH - 0x8ABD: 0x6B53, //CJK UNIFIED IDEOGRAPH - 0x8ABE: 0x6C57, //CJK UNIFIED IDEOGRAPH - 0x8ABF: 0x6F22, //CJK UNIFIED IDEOGRAPH - 0x8AC0: 0x6F97, //CJK UNIFIED IDEOGRAPH - 0x8AC1: 0x6F45, //CJK UNIFIED IDEOGRAPH - 0x8AC2: 0x74B0, //CJK UNIFIED IDEOGRAPH - 0x8AC3: 0x7518, //CJK UNIFIED IDEOGRAPH - 0x8AC4: 0x76E3, //CJK UNIFIED IDEOGRAPH - 0x8AC5: 0x770B, //CJK UNIFIED IDEOGRAPH - 0x8AC6: 0x7AFF, //CJK UNIFIED IDEOGRAPH - 0x8AC7: 0x7BA1, //CJK UNIFIED IDEOGRAPH - 0x8AC8: 0x7C21, //CJK UNIFIED IDEOGRAPH - 0x8AC9: 0x7DE9, //CJK UNIFIED IDEOGRAPH - 0x8ACA: 0x7F36, //CJK UNIFIED IDEOGRAPH - 0x8ACB: 0x7FF0, //CJK UNIFIED IDEOGRAPH - 0x8ACC: 0x809D, //CJK UNIFIED IDEOGRAPH - 0x8ACD: 0x8266, //CJK UNIFIED IDEOGRAPH - 0x8ACE: 0x839E, //CJK UNIFIED IDEOGRAPH - 0x8ACF: 0x89B3, //CJK UNIFIED IDEOGRAPH - 0x8AD0: 0x8ACC, //CJK UNIFIED IDEOGRAPH - 0x8AD1: 0x8CAB, //CJK UNIFIED IDEOGRAPH - 0x8AD2: 0x9084, //CJK UNIFIED IDEOGRAPH - 0x8AD3: 0x9451, //CJK UNIFIED IDEOGRAPH - 0x8AD4: 0x9593, //CJK UNIFIED IDEOGRAPH - 0x8AD5: 0x9591, //CJK UNIFIED IDEOGRAPH - 0x8AD6: 0x95A2, //CJK UNIFIED IDEOGRAPH - 0x8AD7: 0x9665, //CJK UNIFIED IDEOGRAPH - 0x8AD8: 0x97D3, //CJK UNIFIED IDEOGRAPH - 0x8AD9: 0x9928, //CJK UNIFIED IDEOGRAPH - 0x8ADA: 0x8218, //CJK UNIFIED IDEOGRAPH - 0x8ADB: 0x4E38, //CJK UNIFIED IDEOGRAPH - 0x8ADC: 0x542B, //CJK UNIFIED IDEOGRAPH - 0x8ADD: 0x5CB8, //CJK UNIFIED IDEOGRAPH - 0x8ADE: 0x5DCC, //CJK UNIFIED IDEOGRAPH - 0x8ADF: 0x73A9, //CJK UNIFIED IDEOGRAPH - 0x8AE0: 0x764C, //CJK UNIFIED IDEOGRAPH - 0x8AE1: 0x773C, //CJK UNIFIED IDEOGRAPH - 0x8AE2: 0x5CA9, //CJK UNIFIED IDEOGRAPH - 0x8AE3: 0x7FEB, //CJK UNIFIED IDEOGRAPH - 0x8AE4: 0x8D0B, //CJK UNIFIED IDEOGRAPH - 0x8AE5: 0x96C1, //CJK UNIFIED IDEOGRAPH - 0x8AE6: 0x9811, //CJK UNIFIED IDEOGRAPH - 0x8AE7: 0x9854, //CJK UNIFIED IDEOGRAPH - 0x8AE8: 0x9858, //CJK UNIFIED IDEOGRAPH - 0x8AE9: 0x4F01, //CJK UNIFIED IDEOGRAPH - 0x8AEA: 0x4F0E, //CJK UNIFIED IDEOGRAPH - 0x8AEB: 0x5371, //CJK UNIFIED IDEOGRAPH - 0x8AEC: 0x559C, //CJK UNIFIED IDEOGRAPH - 0x8AED: 0x5668, //CJK UNIFIED IDEOGRAPH - 0x8AEE: 0x57FA, //CJK UNIFIED IDEOGRAPH - 0x8AEF: 0x5947, //CJK UNIFIED IDEOGRAPH - 0x8AF0: 0x5B09, //CJK UNIFIED IDEOGRAPH - 0x8AF1: 0x5BC4, //CJK UNIFIED IDEOGRAPH - 0x8AF2: 0x5C90, //CJK UNIFIED IDEOGRAPH - 0x8AF3: 0x5E0C, //CJK UNIFIED IDEOGRAPH - 0x8AF4: 0x5E7E, //CJK UNIFIED IDEOGRAPH - 0x8AF5: 0x5FCC, //CJK UNIFIED IDEOGRAPH - 0x8AF6: 0x63EE, //CJK UNIFIED IDEOGRAPH - 0x8AF7: 0x673A, //CJK UNIFIED IDEOGRAPH - 0x8AF8: 0x65D7, //CJK UNIFIED IDEOGRAPH - 0x8AF9: 0x65E2, //CJK UNIFIED IDEOGRAPH - 0x8AFA: 0x671F, //CJK UNIFIED IDEOGRAPH - 0x8AFB: 0x68CB, //CJK UNIFIED IDEOGRAPH - 0x8AFC: 0x68C4, //CJK UNIFIED IDEOGRAPH - 0x8B40: 0x6A5F, //CJK UNIFIED IDEOGRAPH - 0x8B41: 0x5E30, //CJK UNIFIED IDEOGRAPH - 0x8B42: 0x6BC5, //CJK UNIFIED IDEOGRAPH - 0x8B43: 0x6C17, //CJK UNIFIED IDEOGRAPH - 0x8B44: 0x6C7D, //CJK UNIFIED IDEOGRAPH - 0x8B45: 0x757F, //CJK UNIFIED IDEOGRAPH - 0x8B46: 0x7948, //CJK UNIFIED IDEOGRAPH - 0x8B47: 0x5B63, //CJK UNIFIED IDEOGRAPH - 0x8B48: 0x7A00, //CJK UNIFIED IDEOGRAPH - 0x8B49: 0x7D00, //CJK UNIFIED IDEOGRAPH - 0x8B4A: 0x5FBD, //CJK UNIFIED IDEOGRAPH - 0x8B4B: 0x898F, //CJK UNIFIED IDEOGRAPH - 0x8B4C: 0x8A18, //CJK UNIFIED IDEOGRAPH - 0x8B4D: 0x8CB4, //CJK UNIFIED IDEOGRAPH - 0x8B4E: 0x8D77, //CJK UNIFIED IDEOGRAPH - 0x8B4F: 0x8ECC, //CJK UNIFIED IDEOGRAPH - 0x8B50: 0x8F1D, //CJK UNIFIED IDEOGRAPH - 0x8B51: 0x98E2, //CJK UNIFIED IDEOGRAPH - 0x8B52: 0x9A0E, //CJK UNIFIED IDEOGRAPH - 0x8B53: 0x9B3C, //CJK UNIFIED IDEOGRAPH - 0x8B54: 0x4E80, //CJK UNIFIED IDEOGRAPH - 0x8B55: 0x507D, //CJK UNIFIED IDEOGRAPH - 0x8B56: 0x5100, //CJK UNIFIED IDEOGRAPH - 0x8B57: 0x5993, //CJK UNIFIED IDEOGRAPH - 0x8B58: 0x5B9C, //CJK UNIFIED IDEOGRAPH - 0x8B59: 0x622F, //CJK UNIFIED IDEOGRAPH - 0x8B5A: 0x6280, //CJK UNIFIED IDEOGRAPH - 0x8B5B: 0x64EC, //CJK UNIFIED IDEOGRAPH - 0x8B5C: 0x6B3A, //CJK UNIFIED IDEOGRAPH - 0x8B5D: 0x72A0, //CJK UNIFIED IDEOGRAPH - 0x8B5E: 0x7591, //CJK UNIFIED IDEOGRAPH - 0x8B5F: 0x7947, //CJK UNIFIED IDEOGRAPH - 0x8B60: 0x7FA9, //CJK UNIFIED IDEOGRAPH - 0x8B61: 0x87FB, //CJK UNIFIED IDEOGRAPH - 0x8B62: 0x8ABC, //CJK UNIFIED IDEOGRAPH - 0x8B63: 0x8B70, //CJK UNIFIED IDEOGRAPH - 0x8B64: 0x63AC, //CJK UNIFIED IDEOGRAPH - 0x8B65: 0x83CA, //CJK UNIFIED IDEOGRAPH - 0x8B66: 0x97A0, //CJK UNIFIED IDEOGRAPH - 0x8B67: 0x5409, //CJK UNIFIED IDEOGRAPH - 0x8B68: 0x5403, //CJK UNIFIED IDEOGRAPH - 0x8B69: 0x55AB, //CJK UNIFIED IDEOGRAPH - 0x8B6A: 0x6854, //CJK UNIFIED IDEOGRAPH - 0x8B6B: 0x6A58, //CJK UNIFIED IDEOGRAPH - 0x8B6C: 0x8A70, //CJK UNIFIED IDEOGRAPH - 0x8B6D: 0x7827, //CJK UNIFIED IDEOGRAPH - 0x8B6E: 0x6775, //CJK UNIFIED IDEOGRAPH - 0x8B6F: 0x9ECD, //CJK UNIFIED IDEOGRAPH - 0x8B70: 0x5374, //CJK UNIFIED IDEOGRAPH - 0x8B71: 0x5BA2, //CJK UNIFIED IDEOGRAPH - 0x8B72: 0x811A, //CJK UNIFIED IDEOGRAPH - 0x8B73: 0x8650, //CJK UNIFIED IDEOGRAPH - 0x8B74: 0x9006, //CJK UNIFIED IDEOGRAPH - 0x8B75: 0x4E18, //CJK UNIFIED IDEOGRAPH - 0x8B76: 0x4E45, //CJK UNIFIED IDEOGRAPH - 0x8B77: 0x4EC7, //CJK UNIFIED IDEOGRAPH - 0x8B78: 0x4F11, //CJK UNIFIED IDEOGRAPH - 0x8B79: 0x53CA, //CJK UNIFIED IDEOGRAPH - 0x8B7A: 0x5438, //CJK UNIFIED IDEOGRAPH - 0x8B7B: 0x5BAE, //CJK UNIFIED IDEOGRAPH - 0x8B7C: 0x5F13, //CJK UNIFIED IDEOGRAPH - 0x8B7D: 0x6025, //CJK UNIFIED IDEOGRAPH - 0x8B7E: 0x6551, //CJK UNIFIED IDEOGRAPH - 0x8B80: 0x673D, //CJK UNIFIED IDEOGRAPH - 0x8B81: 0x6C42, //CJK UNIFIED IDEOGRAPH - 0x8B82: 0x6C72, //CJK UNIFIED IDEOGRAPH - 0x8B83: 0x6CE3, //CJK UNIFIED IDEOGRAPH - 0x8B84: 0x7078, //CJK UNIFIED IDEOGRAPH - 0x8B85: 0x7403, //CJK UNIFIED IDEOGRAPH - 0x8B86: 0x7A76, //CJK UNIFIED IDEOGRAPH - 0x8B87: 0x7AAE, //CJK UNIFIED IDEOGRAPH - 0x8B88: 0x7B08, //CJK UNIFIED IDEOGRAPH - 0x8B89: 0x7D1A, //CJK UNIFIED IDEOGRAPH - 0x8B8A: 0x7CFE, //CJK UNIFIED IDEOGRAPH - 0x8B8B: 0x7D66, //CJK UNIFIED IDEOGRAPH - 0x8B8C: 0x65E7, //CJK UNIFIED IDEOGRAPH - 0x8B8D: 0x725B, //CJK UNIFIED IDEOGRAPH - 0x8B8E: 0x53BB, //CJK UNIFIED IDEOGRAPH - 0x8B8F: 0x5C45, //CJK UNIFIED IDEOGRAPH - 0x8B90: 0x5DE8, //CJK UNIFIED IDEOGRAPH - 0x8B91: 0x62D2, //CJK UNIFIED IDEOGRAPH - 0x8B92: 0x62E0, //CJK UNIFIED IDEOGRAPH - 0x8B93: 0x6319, //CJK UNIFIED IDEOGRAPH - 0x8B94: 0x6E20, //CJK UNIFIED IDEOGRAPH - 0x8B95: 0x865A, //CJK UNIFIED IDEOGRAPH - 0x8B96: 0x8A31, //CJK UNIFIED IDEOGRAPH - 0x8B97: 0x8DDD, //CJK UNIFIED IDEOGRAPH - 0x8B98: 0x92F8, //CJK UNIFIED IDEOGRAPH - 0x8B99: 0x6F01, //CJK UNIFIED IDEOGRAPH - 0x8B9A: 0x79A6, //CJK UNIFIED IDEOGRAPH - 0x8B9B: 0x9B5A, //CJK UNIFIED IDEOGRAPH - 0x8B9C: 0x4EA8, //CJK UNIFIED IDEOGRAPH - 0x8B9D: 0x4EAB, //CJK UNIFIED IDEOGRAPH - 0x8B9E: 0x4EAC, //CJK UNIFIED IDEOGRAPH - 0x8B9F: 0x4F9B, //CJK UNIFIED IDEOGRAPH - 0x8BA0: 0x4FA0, //CJK UNIFIED IDEOGRAPH - 0x8BA1: 0x50D1, //CJK UNIFIED IDEOGRAPH - 0x8BA2: 0x5147, //CJK UNIFIED IDEOGRAPH - 0x8BA3: 0x7AF6, //CJK UNIFIED IDEOGRAPH - 0x8BA4: 0x5171, //CJK UNIFIED IDEOGRAPH - 0x8BA5: 0x51F6, //CJK UNIFIED IDEOGRAPH - 0x8BA6: 0x5354, //CJK UNIFIED IDEOGRAPH - 0x8BA7: 0x5321, //CJK UNIFIED IDEOGRAPH - 0x8BA8: 0x537F, //CJK UNIFIED IDEOGRAPH - 0x8BA9: 0x53EB, //CJK UNIFIED IDEOGRAPH - 0x8BAA: 0x55AC, //CJK UNIFIED IDEOGRAPH - 0x8BAB: 0x5883, //CJK UNIFIED IDEOGRAPH - 0x8BAC: 0x5CE1, //CJK UNIFIED IDEOGRAPH - 0x8BAD: 0x5F37, //CJK UNIFIED IDEOGRAPH - 0x8BAE: 0x5F4A, //CJK UNIFIED IDEOGRAPH - 0x8BAF: 0x602F, //CJK UNIFIED IDEOGRAPH - 0x8BB0: 0x6050, //CJK UNIFIED IDEOGRAPH - 0x8BB1: 0x606D, //CJK UNIFIED IDEOGRAPH - 0x8BB2: 0x631F, //CJK UNIFIED IDEOGRAPH - 0x8BB3: 0x6559, //CJK UNIFIED IDEOGRAPH - 0x8BB4: 0x6A4B, //CJK UNIFIED IDEOGRAPH - 0x8BB5: 0x6CC1, //CJK UNIFIED IDEOGRAPH - 0x8BB6: 0x72C2, //CJK UNIFIED IDEOGRAPH - 0x8BB7: 0x72ED, //CJK UNIFIED IDEOGRAPH - 0x8BB8: 0x77EF, //CJK UNIFIED IDEOGRAPH - 0x8BB9: 0x80F8, //CJK UNIFIED IDEOGRAPH - 0x8BBA: 0x8105, //CJK UNIFIED IDEOGRAPH - 0x8BBB: 0x8208, //CJK UNIFIED IDEOGRAPH - 0x8BBC: 0x854E, //CJK UNIFIED IDEOGRAPH - 0x8BBD: 0x90F7, //CJK UNIFIED IDEOGRAPH - 0x8BBE: 0x93E1, //CJK UNIFIED IDEOGRAPH - 0x8BBF: 0x97FF, //CJK UNIFIED IDEOGRAPH - 0x8BC0: 0x9957, //CJK UNIFIED IDEOGRAPH - 0x8BC1: 0x9A5A, //CJK UNIFIED IDEOGRAPH - 0x8BC2: 0x4EF0, //CJK UNIFIED IDEOGRAPH - 0x8BC3: 0x51DD, //CJK UNIFIED IDEOGRAPH - 0x8BC4: 0x5C2D, //CJK UNIFIED IDEOGRAPH - 0x8BC5: 0x6681, //CJK UNIFIED IDEOGRAPH - 0x8BC6: 0x696D, //CJK UNIFIED IDEOGRAPH - 0x8BC7: 0x5C40, //CJK UNIFIED IDEOGRAPH - 0x8BC8: 0x66F2, //CJK UNIFIED IDEOGRAPH - 0x8BC9: 0x6975, //CJK UNIFIED IDEOGRAPH - 0x8BCA: 0x7389, //CJK UNIFIED IDEOGRAPH - 0x8BCB: 0x6850, //CJK UNIFIED IDEOGRAPH - 0x8BCC: 0x7C81, //CJK UNIFIED IDEOGRAPH - 0x8BCD: 0x50C5, //CJK UNIFIED IDEOGRAPH - 0x8BCE: 0x52E4, //CJK UNIFIED IDEOGRAPH - 0x8BCF: 0x5747, //CJK UNIFIED IDEOGRAPH - 0x8BD0: 0x5DFE, //CJK UNIFIED IDEOGRAPH - 0x8BD1: 0x9326, //CJK UNIFIED IDEOGRAPH - 0x8BD2: 0x65A4, //CJK UNIFIED IDEOGRAPH - 0x8BD3: 0x6B23, //CJK UNIFIED IDEOGRAPH - 0x8BD4: 0x6B3D, //CJK UNIFIED IDEOGRAPH - 0x8BD5: 0x7434, //CJK UNIFIED IDEOGRAPH - 0x8BD6: 0x7981, //CJK UNIFIED IDEOGRAPH - 0x8BD7: 0x79BD, //CJK UNIFIED IDEOGRAPH - 0x8BD8: 0x7B4B, //CJK UNIFIED IDEOGRAPH - 0x8BD9: 0x7DCA, //CJK UNIFIED IDEOGRAPH - 0x8BDA: 0x82B9, //CJK UNIFIED IDEOGRAPH - 0x8BDB: 0x83CC, //CJK UNIFIED IDEOGRAPH - 0x8BDC: 0x887F, //CJK UNIFIED IDEOGRAPH - 0x8BDD: 0x895F, //CJK UNIFIED IDEOGRAPH - 0x8BDE: 0x8B39, //CJK UNIFIED IDEOGRAPH - 0x8BDF: 0x8FD1, //CJK UNIFIED IDEOGRAPH - 0x8BE0: 0x91D1, //CJK UNIFIED IDEOGRAPH - 0x8BE1: 0x541F, //CJK UNIFIED IDEOGRAPH - 0x8BE2: 0x9280, //CJK UNIFIED IDEOGRAPH - 0x8BE3: 0x4E5D, //CJK UNIFIED IDEOGRAPH - 0x8BE4: 0x5036, //CJK UNIFIED IDEOGRAPH - 0x8BE5: 0x53E5, //CJK UNIFIED IDEOGRAPH - 0x8BE6: 0x533A, //CJK UNIFIED IDEOGRAPH - 0x8BE7: 0x72D7, //CJK UNIFIED IDEOGRAPH - 0x8BE8: 0x7396, //CJK UNIFIED IDEOGRAPH - 0x8BE9: 0x77E9, //CJK UNIFIED IDEOGRAPH - 0x8BEA: 0x82E6, //CJK UNIFIED IDEOGRAPH - 0x8BEB: 0x8EAF, //CJK UNIFIED IDEOGRAPH - 0x8BEC: 0x99C6, //CJK UNIFIED IDEOGRAPH - 0x8BED: 0x99C8, //CJK UNIFIED IDEOGRAPH - 0x8BEE: 0x99D2, //CJK UNIFIED IDEOGRAPH - 0x8BEF: 0x5177, //CJK UNIFIED IDEOGRAPH - 0x8BF0: 0x611A, //CJK UNIFIED IDEOGRAPH - 0x8BF1: 0x865E, //CJK UNIFIED IDEOGRAPH - 0x8BF2: 0x55B0, //CJK UNIFIED IDEOGRAPH - 0x8BF3: 0x7A7A, //CJK UNIFIED IDEOGRAPH - 0x8BF4: 0x5076, //CJK UNIFIED IDEOGRAPH - 0x8BF5: 0x5BD3, //CJK UNIFIED IDEOGRAPH - 0x8BF6: 0x9047, //CJK UNIFIED IDEOGRAPH - 0x8BF7: 0x9685, //CJK UNIFIED IDEOGRAPH - 0x8BF8: 0x4E32, //CJK UNIFIED IDEOGRAPH - 0x8BF9: 0x6ADB, //CJK UNIFIED IDEOGRAPH - 0x8BFA: 0x91E7, //CJK UNIFIED IDEOGRAPH - 0x8BFB: 0x5C51, //CJK UNIFIED IDEOGRAPH - 0x8BFC: 0x5C48, //CJK UNIFIED IDEOGRAPH - 0x8C40: 0x6398, //CJK UNIFIED IDEOGRAPH - 0x8C41: 0x7A9F, //CJK UNIFIED IDEOGRAPH - 0x8C42: 0x6C93, //CJK UNIFIED IDEOGRAPH - 0x8C43: 0x9774, //CJK UNIFIED IDEOGRAPH - 0x8C44: 0x8F61, //CJK UNIFIED IDEOGRAPH - 0x8C45: 0x7AAA, //CJK UNIFIED IDEOGRAPH - 0x8C46: 0x718A, //CJK UNIFIED IDEOGRAPH - 0x8C47: 0x9688, //CJK UNIFIED IDEOGRAPH - 0x8C48: 0x7C82, //CJK UNIFIED IDEOGRAPH - 0x8C49: 0x6817, //CJK UNIFIED IDEOGRAPH - 0x8C4A: 0x7E70, //CJK UNIFIED IDEOGRAPH - 0x8C4B: 0x6851, //CJK UNIFIED IDEOGRAPH - 0x8C4C: 0x936C, //CJK UNIFIED IDEOGRAPH - 0x8C4D: 0x52F2, //CJK UNIFIED IDEOGRAPH - 0x8C4E: 0x541B, //CJK UNIFIED IDEOGRAPH - 0x8C4F: 0x85AB, //CJK UNIFIED IDEOGRAPH - 0x8C50: 0x8A13, //CJK UNIFIED IDEOGRAPH - 0x8C51: 0x7FA4, //CJK UNIFIED IDEOGRAPH - 0x8C52: 0x8ECD, //CJK UNIFIED IDEOGRAPH - 0x8C53: 0x90E1, //CJK UNIFIED IDEOGRAPH - 0x8C54: 0x5366, //CJK UNIFIED IDEOGRAPH - 0x8C55: 0x8888, //CJK UNIFIED IDEOGRAPH - 0x8C56: 0x7941, //CJK UNIFIED IDEOGRAPH - 0x8C57: 0x4FC2, //CJK UNIFIED IDEOGRAPH - 0x8C58: 0x50BE, //CJK UNIFIED IDEOGRAPH - 0x8C59: 0x5211, //CJK UNIFIED IDEOGRAPH - 0x8C5A: 0x5144, //CJK UNIFIED IDEOGRAPH - 0x8C5B: 0x5553, //CJK UNIFIED IDEOGRAPH - 0x8C5C: 0x572D, //CJK UNIFIED IDEOGRAPH - 0x8C5D: 0x73EA, //CJK UNIFIED IDEOGRAPH - 0x8C5E: 0x578B, //CJK UNIFIED IDEOGRAPH - 0x8C5F: 0x5951, //CJK UNIFIED IDEOGRAPH - 0x8C60: 0x5F62, //CJK UNIFIED IDEOGRAPH - 0x8C61: 0x5F84, //CJK UNIFIED IDEOGRAPH - 0x8C62: 0x6075, //CJK UNIFIED IDEOGRAPH - 0x8C63: 0x6176, //CJK UNIFIED IDEOGRAPH - 0x8C64: 0x6167, //CJK UNIFIED IDEOGRAPH - 0x8C65: 0x61A9, //CJK UNIFIED IDEOGRAPH - 0x8C66: 0x63B2, //CJK UNIFIED IDEOGRAPH - 0x8C67: 0x643A, //CJK UNIFIED IDEOGRAPH - 0x8C68: 0x656C, //CJK UNIFIED IDEOGRAPH - 0x8C69: 0x666F, //CJK UNIFIED IDEOGRAPH - 0x8C6A: 0x6842, //CJK UNIFIED IDEOGRAPH - 0x8C6B: 0x6E13, //CJK UNIFIED IDEOGRAPH - 0x8C6C: 0x7566, //CJK UNIFIED IDEOGRAPH - 0x8C6D: 0x7A3D, //CJK UNIFIED IDEOGRAPH - 0x8C6E: 0x7CFB, //CJK UNIFIED IDEOGRAPH - 0x8C6F: 0x7D4C, //CJK UNIFIED IDEOGRAPH - 0x8C70: 0x7D99, //CJK UNIFIED IDEOGRAPH - 0x8C71: 0x7E4B, //CJK UNIFIED IDEOGRAPH - 0x8C72: 0x7F6B, //CJK UNIFIED IDEOGRAPH - 0x8C73: 0x830E, //CJK UNIFIED IDEOGRAPH - 0x8C74: 0x834A, //CJK UNIFIED IDEOGRAPH - 0x8C75: 0x86CD, //CJK UNIFIED IDEOGRAPH - 0x8C76: 0x8A08, //CJK UNIFIED IDEOGRAPH - 0x8C77: 0x8A63, //CJK UNIFIED IDEOGRAPH - 0x8C78: 0x8B66, //CJK UNIFIED IDEOGRAPH - 0x8C79: 0x8EFD, //CJK UNIFIED IDEOGRAPH - 0x8C7A: 0x981A, //CJK UNIFIED IDEOGRAPH - 0x8C7B: 0x9D8F, //CJK UNIFIED IDEOGRAPH - 0x8C7C: 0x82B8, //CJK UNIFIED IDEOGRAPH - 0x8C7D: 0x8FCE, //CJK UNIFIED IDEOGRAPH - 0x8C7E: 0x9BE8, //CJK UNIFIED IDEOGRAPH - 0x8C80: 0x5287, //CJK UNIFIED IDEOGRAPH - 0x8C81: 0x621F, //CJK UNIFIED IDEOGRAPH - 0x8C82: 0x6483, //CJK UNIFIED IDEOGRAPH - 0x8C83: 0x6FC0, //CJK UNIFIED IDEOGRAPH - 0x8C84: 0x9699, //CJK UNIFIED IDEOGRAPH - 0x8C85: 0x6841, //CJK UNIFIED IDEOGRAPH - 0x8C86: 0x5091, //CJK UNIFIED IDEOGRAPH - 0x8C87: 0x6B20, //CJK UNIFIED IDEOGRAPH - 0x8C88: 0x6C7A, //CJK UNIFIED IDEOGRAPH - 0x8C89: 0x6F54, //CJK UNIFIED IDEOGRAPH - 0x8C8A: 0x7A74, //CJK UNIFIED IDEOGRAPH - 0x8C8B: 0x7D50, //CJK UNIFIED IDEOGRAPH - 0x8C8C: 0x8840, //CJK UNIFIED IDEOGRAPH - 0x8C8D: 0x8A23, //CJK UNIFIED IDEOGRAPH - 0x8C8E: 0x6708, //CJK UNIFIED IDEOGRAPH - 0x8C8F: 0x4EF6, //CJK UNIFIED IDEOGRAPH - 0x8C90: 0x5039, //CJK UNIFIED IDEOGRAPH - 0x8C91: 0x5026, //CJK UNIFIED IDEOGRAPH - 0x8C92: 0x5065, //CJK UNIFIED IDEOGRAPH - 0x8C93: 0x517C, //CJK UNIFIED IDEOGRAPH - 0x8C94: 0x5238, //CJK UNIFIED IDEOGRAPH - 0x8C95: 0x5263, //CJK UNIFIED IDEOGRAPH - 0x8C96: 0x55A7, //CJK UNIFIED IDEOGRAPH - 0x8C97: 0x570F, //CJK UNIFIED IDEOGRAPH - 0x8C98: 0x5805, //CJK UNIFIED IDEOGRAPH - 0x8C99: 0x5ACC, //CJK UNIFIED IDEOGRAPH - 0x8C9A: 0x5EFA, //CJK UNIFIED IDEOGRAPH - 0x8C9B: 0x61B2, //CJK UNIFIED IDEOGRAPH - 0x8C9C: 0x61F8, //CJK UNIFIED IDEOGRAPH - 0x8C9D: 0x62F3, //CJK UNIFIED IDEOGRAPH - 0x8C9E: 0x6372, //CJK UNIFIED IDEOGRAPH - 0x8C9F: 0x691C, //CJK UNIFIED IDEOGRAPH - 0x8CA0: 0x6A29, //CJK UNIFIED IDEOGRAPH - 0x8CA1: 0x727D, //CJK UNIFIED IDEOGRAPH - 0x8CA2: 0x72AC, //CJK UNIFIED IDEOGRAPH - 0x8CA3: 0x732E, //CJK UNIFIED IDEOGRAPH - 0x8CA4: 0x7814, //CJK UNIFIED IDEOGRAPH - 0x8CA5: 0x786F, //CJK UNIFIED IDEOGRAPH - 0x8CA6: 0x7D79, //CJK UNIFIED IDEOGRAPH - 0x8CA7: 0x770C, //CJK UNIFIED IDEOGRAPH - 0x8CA8: 0x80A9, //CJK UNIFIED IDEOGRAPH - 0x8CA9: 0x898B, //CJK UNIFIED IDEOGRAPH - 0x8CAA: 0x8B19, //CJK UNIFIED IDEOGRAPH - 0x8CAB: 0x8CE2, //CJK UNIFIED IDEOGRAPH - 0x8CAC: 0x8ED2, //CJK UNIFIED IDEOGRAPH - 0x8CAD: 0x9063, //CJK UNIFIED IDEOGRAPH - 0x8CAE: 0x9375, //CJK UNIFIED IDEOGRAPH - 0x8CAF: 0x967A, //CJK UNIFIED IDEOGRAPH - 0x8CB0: 0x9855, //CJK UNIFIED IDEOGRAPH - 0x8CB1: 0x9A13, //CJK UNIFIED IDEOGRAPH - 0x8CB2: 0x9E78, //CJK UNIFIED IDEOGRAPH - 0x8CB3: 0x5143, //CJK UNIFIED IDEOGRAPH - 0x8CB4: 0x539F, //CJK UNIFIED IDEOGRAPH - 0x8CB5: 0x53B3, //CJK UNIFIED IDEOGRAPH - 0x8CB6: 0x5E7B, //CJK UNIFIED IDEOGRAPH - 0x8CB7: 0x5F26, //CJK UNIFIED IDEOGRAPH - 0x8CB8: 0x6E1B, //CJK UNIFIED IDEOGRAPH - 0x8CB9: 0x6E90, //CJK UNIFIED IDEOGRAPH - 0x8CBA: 0x7384, //CJK UNIFIED IDEOGRAPH - 0x8CBB: 0x73FE, //CJK UNIFIED IDEOGRAPH - 0x8CBC: 0x7D43, //CJK UNIFIED IDEOGRAPH - 0x8CBD: 0x8237, //CJK UNIFIED IDEOGRAPH - 0x8CBE: 0x8A00, //CJK UNIFIED IDEOGRAPH - 0x8CBF: 0x8AFA, //CJK UNIFIED IDEOGRAPH - 0x8CC0: 0x9650, //CJK UNIFIED IDEOGRAPH - 0x8CC1: 0x4E4E, //CJK UNIFIED IDEOGRAPH - 0x8CC2: 0x500B, //CJK UNIFIED IDEOGRAPH - 0x8CC3: 0x53E4, //CJK UNIFIED IDEOGRAPH - 0x8CC4: 0x547C, //CJK UNIFIED IDEOGRAPH - 0x8CC5: 0x56FA, //CJK UNIFIED IDEOGRAPH - 0x8CC6: 0x59D1, //CJK UNIFIED IDEOGRAPH - 0x8CC7: 0x5B64, //CJK UNIFIED IDEOGRAPH - 0x8CC8: 0x5DF1, //CJK UNIFIED IDEOGRAPH - 0x8CC9: 0x5EAB, //CJK UNIFIED IDEOGRAPH - 0x8CCA: 0x5F27, //CJK UNIFIED IDEOGRAPH - 0x8CCB: 0x6238, //CJK UNIFIED IDEOGRAPH - 0x8CCC: 0x6545, //CJK UNIFIED IDEOGRAPH - 0x8CCD: 0x67AF, //CJK UNIFIED IDEOGRAPH - 0x8CCE: 0x6E56, //CJK UNIFIED IDEOGRAPH - 0x8CCF: 0x72D0, //CJK UNIFIED IDEOGRAPH - 0x8CD0: 0x7CCA, //CJK UNIFIED IDEOGRAPH - 0x8CD1: 0x88B4, //CJK UNIFIED IDEOGRAPH - 0x8CD2: 0x80A1, //CJK UNIFIED IDEOGRAPH - 0x8CD3: 0x80E1, //CJK UNIFIED IDEOGRAPH - 0x8CD4: 0x83F0, //CJK UNIFIED IDEOGRAPH - 0x8CD5: 0x864E, //CJK UNIFIED IDEOGRAPH - 0x8CD6: 0x8A87, //CJK UNIFIED IDEOGRAPH - 0x8CD7: 0x8DE8, //CJK UNIFIED IDEOGRAPH - 0x8CD8: 0x9237, //CJK UNIFIED IDEOGRAPH - 0x8CD9: 0x96C7, //CJK UNIFIED IDEOGRAPH - 0x8CDA: 0x9867, //CJK UNIFIED IDEOGRAPH - 0x8CDB: 0x9F13, //CJK UNIFIED IDEOGRAPH - 0x8CDC: 0x4E94, //CJK UNIFIED IDEOGRAPH - 0x8CDD: 0x4E92, //CJK UNIFIED IDEOGRAPH - 0x8CDE: 0x4F0D, //CJK UNIFIED IDEOGRAPH - 0x8CDF: 0x5348, //CJK UNIFIED IDEOGRAPH - 0x8CE0: 0x5449, //CJK UNIFIED IDEOGRAPH - 0x8CE1: 0x543E, //CJK UNIFIED IDEOGRAPH - 0x8CE2: 0x5A2F, //CJK UNIFIED IDEOGRAPH - 0x8CE3: 0x5F8C, //CJK UNIFIED IDEOGRAPH - 0x8CE4: 0x5FA1, //CJK UNIFIED IDEOGRAPH - 0x8CE5: 0x609F, //CJK UNIFIED IDEOGRAPH - 0x8CE6: 0x68A7, //CJK UNIFIED IDEOGRAPH - 0x8CE7: 0x6A8E, //CJK UNIFIED IDEOGRAPH - 0x8CE8: 0x745A, //CJK UNIFIED IDEOGRAPH - 0x8CE9: 0x7881, //CJK UNIFIED IDEOGRAPH - 0x8CEA: 0x8A9E, //CJK UNIFIED IDEOGRAPH - 0x8CEB: 0x8AA4, //CJK UNIFIED IDEOGRAPH - 0x8CEC: 0x8B77, //CJK UNIFIED IDEOGRAPH - 0x8CED: 0x9190, //CJK UNIFIED IDEOGRAPH - 0x8CEE: 0x4E5E, //CJK UNIFIED IDEOGRAPH - 0x8CEF: 0x9BC9, //CJK UNIFIED IDEOGRAPH - 0x8CF0: 0x4EA4, //CJK UNIFIED IDEOGRAPH - 0x8CF1: 0x4F7C, //CJK UNIFIED IDEOGRAPH - 0x8CF2: 0x4FAF, //CJK UNIFIED IDEOGRAPH - 0x8CF3: 0x5019, //CJK UNIFIED IDEOGRAPH - 0x8CF4: 0x5016, //CJK UNIFIED IDEOGRAPH - 0x8CF5: 0x5149, //CJK UNIFIED IDEOGRAPH - 0x8CF6: 0x516C, //CJK UNIFIED IDEOGRAPH - 0x8CF7: 0x529F, //CJK UNIFIED IDEOGRAPH - 0x8CF8: 0x52B9, //CJK UNIFIED IDEOGRAPH - 0x8CF9: 0x52FE, //CJK UNIFIED IDEOGRAPH - 0x8CFA: 0x539A, //CJK UNIFIED IDEOGRAPH - 0x8CFB: 0x53E3, //CJK UNIFIED IDEOGRAPH - 0x8CFC: 0x5411, //CJK UNIFIED IDEOGRAPH - 0x8D40: 0x540E, //CJK UNIFIED IDEOGRAPH - 0x8D41: 0x5589, //CJK UNIFIED IDEOGRAPH - 0x8D42: 0x5751, //CJK UNIFIED IDEOGRAPH - 0x8D43: 0x57A2, //CJK UNIFIED IDEOGRAPH - 0x8D44: 0x597D, //CJK UNIFIED IDEOGRAPH - 0x8D45: 0x5B54, //CJK UNIFIED IDEOGRAPH - 0x8D46: 0x5B5D, //CJK UNIFIED IDEOGRAPH - 0x8D47: 0x5B8F, //CJK UNIFIED IDEOGRAPH - 0x8D48: 0x5DE5, //CJK UNIFIED IDEOGRAPH - 0x8D49: 0x5DE7, //CJK UNIFIED IDEOGRAPH - 0x8D4A: 0x5DF7, //CJK UNIFIED IDEOGRAPH - 0x8D4B: 0x5E78, //CJK UNIFIED IDEOGRAPH - 0x8D4C: 0x5E83, //CJK UNIFIED IDEOGRAPH - 0x8D4D: 0x5E9A, //CJK UNIFIED IDEOGRAPH - 0x8D4E: 0x5EB7, //CJK UNIFIED IDEOGRAPH - 0x8D4F: 0x5F18, //CJK UNIFIED IDEOGRAPH - 0x8D50: 0x6052, //CJK UNIFIED IDEOGRAPH - 0x8D51: 0x614C, //CJK UNIFIED IDEOGRAPH - 0x8D52: 0x6297, //CJK UNIFIED IDEOGRAPH - 0x8D53: 0x62D8, //CJK UNIFIED IDEOGRAPH - 0x8D54: 0x63A7, //CJK UNIFIED IDEOGRAPH - 0x8D55: 0x653B, //CJK UNIFIED IDEOGRAPH - 0x8D56: 0x6602, //CJK UNIFIED IDEOGRAPH - 0x8D57: 0x6643, //CJK UNIFIED IDEOGRAPH - 0x8D58: 0x66F4, //CJK UNIFIED IDEOGRAPH - 0x8D59: 0x676D, //CJK UNIFIED IDEOGRAPH - 0x8D5A: 0x6821, //CJK UNIFIED IDEOGRAPH - 0x8D5B: 0x6897, //CJK UNIFIED IDEOGRAPH - 0x8D5C: 0x69CB, //CJK UNIFIED IDEOGRAPH - 0x8D5D: 0x6C5F, //CJK UNIFIED IDEOGRAPH - 0x8D5E: 0x6D2A, //CJK UNIFIED IDEOGRAPH - 0x8D5F: 0x6D69, //CJK UNIFIED IDEOGRAPH - 0x8D60: 0x6E2F, //CJK UNIFIED IDEOGRAPH - 0x8D61: 0x6E9D, //CJK UNIFIED IDEOGRAPH - 0x8D62: 0x7532, //CJK UNIFIED IDEOGRAPH - 0x8D63: 0x7687, //CJK UNIFIED IDEOGRAPH - 0x8D64: 0x786C, //CJK UNIFIED IDEOGRAPH - 0x8D65: 0x7A3F, //CJK UNIFIED IDEOGRAPH - 0x8D66: 0x7CE0, //CJK UNIFIED IDEOGRAPH - 0x8D67: 0x7D05, //CJK UNIFIED IDEOGRAPH - 0x8D68: 0x7D18, //CJK UNIFIED IDEOGRAPH - 0x8D69: 0x7D5E, //CJK UNIFIED IDEOGRAPH - 0x8D6A: 0x7DB1, //CJK UNIFIED IDEOGRAPH - 0x8D6B: 0x8015, //CJK UNIFIED IDEOGRAPH - 0x8D6C: 0x8003, //CJK UNIFIED IDEOGRAPH - 0x8D6D: 0x80AF, //CJK UNIFIED IDEOGRAPH - 0x8D6E: 0x80B1, //CJK UNIFIED IDEOGRAPH - 0x8D6F: 0x8154, //CJK UNIFIED IDEOGRAPH - 0x8D70: 0x818F, //CJK UNIFIED IDEOGRAPH - 0x8D71: 0x822A, //CJK UNIFIED IDEOGRAPH - 0x8D72: 0x8352, //CJK UNIFIED IDEOGRAPH - 0x8D73: 0x884C, //CJK UNIFIED IDEOGRAPH - 0x8D74: 0x8861, //CJK UNIFIED IDEOGRAPH - 0x8D75: 0x8B1B, //CJK UNIFIED IDEOGRAPH - 0x8D76: 0x8CA2, //CJK UNIFIED IDEOGRAPH - 0x8D77: 0x8CFC, //CJK UNIFIED IDEOGRAPH - 0x8D78: 0x90CA, //CJK UNIFIED IDEOGRAPH - 0x8D79: 0x9175, //CJK UNIFIED IDEOGRAPH - 0x8D7A: 0x9271, //CJK UNIFIED IDEOGRAPH - 0x8D7B: 0x783F, //CJK UNIFIED IDEOGRAPH - 0x8D7C: 0x92FC, //CJK UNIFIED IDEOGRAPH - 0x8D7D: 0x95A4, //CJK UNIFIED IDEOGRAPH - 0x8D7E: 0x964D, //CJK UNIFIED IDEOGRAPH - 0x8D80: 0x9805, //CJK UNIFIED IDEOGRAPH - 0x8D81: 0x9999, //CJK UNIFIED IDEOGRAPH - 0x8D82: 0x9AD8, //CJK UNIFIED IDEOGRAPH - 0x8D83: 0x9D3B, //CJK UNIFIED IDEOGRAPH - 0x8D84: 0x525B, //CJK UNIFIED IDEOGRAPH - 0x8D85: 0x52AB, //CJK UNIFIED IDEOGRAPH - 0x8D86: 0x53F7, //CJK UNIFIED IDEOGRAPH - 0x8D87: 0x5408, //CJK UNIFIED IDEOGRAPH - 0x8D88: 0x58D5, //CJK UNIFIED IDEOGRAPH - 0x8D89: 0x62F7, //CJK UNIFIED IDEOGRAPH - 0x8D8A: 0x6FE0, //CJK UNIFIED IDEOGRAPH - 0x8D8B: 0x8C6A, //CJK UNIFIED IDEOGRAPH - 0x8D8C: 0x8F5F, //CJK UNIFIED IDEOGRAPH - 0x8D8D: 0x9EB9, //CJK UNIFIED IDEOGRAPH - 0x8D8E: 0x514B, //CJK UNIFIED IDEOGRAPH - 0x8D8F: 0x523B, //CJK UNIFIED IDEOGRAPH - 0x8D90: 0x544A, //CJK UNIFIED IDEOGRAPH - 0x8D91: 0x56FD, //CJK UNIFIED IDEOGRAPH - 0x8D92: 0x7A40, //CJK UNIFIED IDEOGRAPH - 0x8D93: 0x9177, //CJK UNIFIED IDEOGRAPH - 0x8D94: 0x9D60, //CJK UNIFIED IDEOGRAPH - 0x8D95: 0x9ED2, //CJK UNIFIED IDEOGRAPH - 0x8D96: 0x7344, //CJK UNIFIED IDEOGRAPH - 0x8D97: 0x6F09, //CJK UNIFIED IDEOGRAPH - 0x8D98: 0x8170, //CJK UNIFIED IDEOGRAPH - 0x8D99: 0x7511, //CJK UNIFIED IDEOGRAPH - 0x8D9A: 0x5FFD, //CJK UNIFIED IDEOGRAPH - 0x8D9B: 0x60DA, //CJK UNIFIED IDEOGRAPH - 0x8D9C: 0x9AA8, //CJK UNIFIED IDEOGRAPH - 0x8D9D: 0x72DB, //CJK UNIFIED IDEOGRAPH - 0x8D9E: 0x8FBC, //CJK UNIFIED IDEOGRAPH - 0x8D9F: 0x6B64, //CJK UNIFIED IDEOGRAPH - 0x8DA0: 0x9803, //CJK UNIFIED IDEOGRAPH - 0x8DA1: 0x4ECA, //CJK UNIFIED IDEOGRAPH - 0x8DA2: 0x56F0, //CJK UNIFIED IDEOGRAPH - 0x8DA3: 0x5764, //CJK UNIFIED IDEOGRAPH - 0x8DA4: 0x58BE, //CJK UNIFIED IDEOGRAPH - 0x8DA5: 0x5A5A, //CJK UNIFIED IDEOGRAPH - 0x8DA6: 0x6068, //CJK UNIFIED IDEOGRAPH - 0x8DA7: 0x61C7, //CJK UNIFIED IDEOGRAPH - 0x8DA8: 0x660F, //CJK UNIFIED IDEOGRAPH - 0x8DA9: 0x6606, //CJK UNIFIED IDEOGRAPH - 0x8DAA: 0x6839, //CJK UNIFIED IDEOGRAPH - 0x8DAB: 0x68B1, //CJK UNIFIED IDEOGRAPH - 0x8DAC: 0x6DF7, //CJK UNIFIED IDEOGRAPH - 0x8DAD: 0x75D5, //CJK UNIFIED IDEOGRAPH - 0x8DAE: 0x7D3A, //CJK UNIFIED IDEOGRAPH - 0x8DAF: 0x826E, //CJK UNIFIED IDEOGRAPH - 0x8DB0: 0x9B42, //CJK UNIFIED IDEOGRAPH - 0x8DB1: 0x4E9B, //CJK UNIFIED IDEOGRAPH - 0x8DB2: 0x4F50, //CJK UNIFIED IDEOGRAPH - 0x8DB3: 0x53C9, //CJK UNIFIED IDEOGRAPH - 0x8DB4: 0x5506, //CJK UNIFIED IDEOGRAPH - 0x8DB5: 0x5D6F, //CJK UNIFIED IDEOGRAPH - 0x8DB6: 0x5DE6, //CJK UNIFIED IDEOGRAPH - 0x8DB7: 0x5DEE, //CJK UNIFIED IDEOGRAPH - 0x8DB8: 0x67FB, //CJK UNIFIED IDEOGRAPH - 0x8DB9: 0x6C99, //CJK UNIFIED IDEOGRAPH - 0x8DBA: 0x7473, //CJK UNIFIED IDEOGRAPH - 0x8DBB: 0x7802, //CJK UNIFIED IDEOGRAPH - 0x8DBC: 0x8A50, //CJK UNIFIED IDEOGRAPH - 0x8DBD: 0x9396, //CJK UNIFIED IDEOGRAPH - 0x8DBE: 0x88DF, //CJK UNIFIED IDEOGRAPH - 0x8DBF: 0x5750, //CJK UNIFIED IDEOGRAPH - 0x8DC0: 0x5EA7, //CJK UNIFIED IDEOGRAPH - 0x8DC1: 0x632B, //CJK UNIFIED IDEOGRAPH - 0x8DC2: 0x50B5, //CJK UNIFIED IDEOGRAPH - 0x8DC3: 0x50AC, //CJK UNIFIED IDEOGRAPH - 0x8DC4: 0x518D, //CJK UNIFIED IDEOGRAPH - 0x8DC5: 0x6700, //CJK UNIFIED IDEOGRAPH - 0x8DC6: 0x54C9, //CJK UNIFIED IDEOGRAPH - 0x8DC7: 0x585E, //CJK UNIFIED IDEOGRAPH - 0x8DC8: 0x59BB, //CJK UNIFIED IDEOGRAPH - 0x8DC9: 0x5BB0, //CJK UNIFIED IDEOGRAPH - 0x8DCA: 0x5F69, //CJK UNIFIED IDEOGRAPH - 0x8DCB: 0x624D, //CJK UNIFIED IDEOGRAPH - 0x8DCC: 0x63A1, //CJK UNIFIED IDEOGRAPH - 0x8DCD: 0x683D, //CJK UNIFIED IDEOGRAPH - 0x8DCE: 0x6B73, //CJK UNIFIED IDEOGRAPH - 0x8DCF: 0x6E08, //CJK UNIFIED IDEOGRAPH - 0x8DD0: 0x707D, //CJK UNIFIED IDEOGRAPH - 0x8DD1: 0x91C7, //CJK UNIFIED IDEOGRAPH - 0x8DD2: 0x7280, //CJK UNIFIED IDEOGRAPH - 0x8DD3: 0x7815, //CJK UNIFIED IDEOGRAPH - 0x8DD4: 0x7826, //CJK UNIFIED IDEOGRAPH - 0x8DD5: 0x796D, //CJK UNIFIED IDEOGRAPH - 0x8DD6: 0x658E, //CJK UNIFIED IDEOGRAPH - 0x8DD7: 0x7D30, //CJK UNIFIED IDEOGRAPH - 0x8DD8: 0x83DC, //CJK UNIFIED IDEOGRAPH - 0x8DD9: 0x88C1, //CJK UNIFIED IDEOGRAPH - 0x8DDA: 0x8F09, //CJK UNIFIED IDEOGRAPH - 0x8DDB: 0x969B, //CJK UNIFIED IDEOGRAPH - 0x8DDC: 0x5264, //CJK UNIFIED IDEOGRAPH - 0x8DDD: 0x5728, //CJK UNIFIED IDEOGRAPH - 0x8DDE: 0x6750, //CJK UNIFIED IDEOGRAPH - 0x8DDF: 0x7F6A, //CJK UNIFIED IDEOGRAPH - 0x8DE0: 0x8CA1, //CJK UNIFIED IDEOGRAPH - 0x8DE1: 0x51B4, //CJK UNIFIED IDEOGRAPH - 0x8DE2: 0x5742, //CJK UNIFIED IDEOGRAPH - 0x8DE3: 0x962A, //CJK UNIFIED IDEOGRAPH - 0x8DE4: 0x583A, //CJK UNIFIED IDEOGRAPH - 0x8DE5: 0x698A, //CJK UNIFIED IDEOGRAPH - 0x8DE6: 0x80B4, //CJK UNIFIED IDEOGRAPH - 0x8DE7: 0x54B2, //CJK UNIFIED IDEOGRAPH - 0x8DE8: 0x5D0E, //CJK UNIFIED IDEOGRAPH - 0x8DE9: 0x57FC, //CJK UNIFIED IDEOGRAPH - 0x8DEA: 0x7895, //CJK UNIFIED IDEOGRAPH - 0x8DEB: 0x9DFA, //CJK UNIFIED IDEOGRAPH - 0x8DEC: 0x4F5C, //CJK UNIFIED IDEOGRAPH - 0x8DED: 0x524A, //CJK UNIFIED IDEOGRAPH - 0x8DEE: 0x548B, //CJK UNIFIED IDEOGRAPH - 0x8DEF: 0x643E, //CJK UNIFIED IDEOGRAPH - 0x8DF0: 0x6628, //CJK UNIFIED IDEOGRAPH - 0x8DF1: 0x6714, //CJK UNIFIED IDEOGRAPH - 0x8DF2: 0x67F5, //CJK UNIFIED IDEOGRAPH - 0x8DF3: 0x7A84, //CJK UNIFIED IDEOGRAPH - 0x8DF4: 0x7B56, //CJK UNIFIED IDEOGRAPH - 0x8DF5: 0x7D22, //CJK UNIFIED IDEOGRAPH - 0x8DF6: 0x932F, //CJK UNIFIED IDEOGRAPH - 0x8DF7: 0x685C, //CJK UNIFIED IDEOGRAPH - 0x8DF8: 0x9BAD, //CJK UNIFIED IDEOGRAPH - 0x8DF9: 0x7B39, //CJK UNIFIED IDEOGRAPH - 0x8DFA: 0x5319, //CJK UNIFIED IDEOGRAPH - 0x8DFB: 0x518A, //CJK UNIFIED IDEOGRAPH - 0x8DFC: 0x5237, //CJK UNIFIED IDEOGRAPH - 0x8E40: 0x5BDF, //CJK UNIFIED IDEOGRAPH - 0x8E41: 0x62F6, //CJK UNIFIED IDEOGRAPH - 0x8E42: 0x64AE, //CJK UNIFIED IDEOGRAPH - 0x8E43: 0x64E6, //CJK UNIFIED IDEOGRAPH - 0x8E44: 0x672D, //CJK UNIFIED IDEOGRAPH - 0x8E45: 0x6BBA, //CJK UNIFIED IDEOGRAPH - 0x8E46: 0x85A9, //CJK UNIFIED IDEOGRAPH - 0x8E47: 0x96D1, //CJK UNIFIED IDEOGRAPH - 0x8E48: 0x7690, //CJK UNIFIED IDEOGRAPH - 0x8E49: 0x9BD6, //CJK UNIFIED IDEOGRAPH - 0x8E4A: 0x634C, //CJK UNIFIED IDEOGRAPH - 0x8E4B: 0x9306, //CJK UNIFIED IDEOGRAPH - 0x8E4C: 0x9BAB, //CJK UNIFIED IDEOGRAPH - 0x8E4D: 0x76BF, //CJK UNIFIED IDEOGRAPH - 0x8E4E: 0x6652, //CJK UNIFIED IDEOGRAPH - 0x8E4F: 0x4E09, //CJK UNIFIED IDEOGRAPH - 0x8E50: 0x5098, //CJK UNIFIED IDEOGRAPH - 0x8E51: 0x53C2, //CJK UNIFIED IDEOGRAPH - 0x8E52: 0x5C71, //CJK UNIFIED IDEOGRAPH - 0x8E53: 0x60E8, //CJK UNIFIED IDEOGRAPH - 0x8E54: 0x6492, //CJK UNIFIED IDEOGRAPH - 0x8E55: 0x6563, //CJK UNIFIED IDEOGRAPH - 0x8E56: 0x685F, //CJK UNIFIED IDEOGRAPH - 0x8E57: 0x71E6, //CJK UNIFIED IDEOGRAPH - 0x8E58: 0x73CA, //CJK UNIFIED IDEOGRAPH - 0x8E59: 0x7523, //CJK UNIFIED IDEOGRAPH - 0x8E5A: 0x7B97, //CJK UNIFIED IDEOGRAPH - 0x8E5B: 0x7E82, //CJK UNIFIED IDEOGRAPH - 0x8E5C: 0x8695, //CJK UNIFIED IDEOGRAPH - 0x8E5D: 0x8B83, //CJK UNIFIED IDEOGRAPH - 0x8E5E: 0x8CDB, //CJK UNIFIED IDEOGRAPH - 0x8E5F: 0x9178, //CJK UNIFIED IDEOGRAPH - 0x8E60: 0x9910, //CJK UNIFIED IDEOGRAPH - 0x8E61: 0x65AC, //CJK UNIFIED IDEOGRAPH - 0x8E62: 0x66AB, //CJK UNIFIED IDEOGRAPH - 0x8E63: 0x6B8B, //CJK UNIFIED IDEOGRAPH - 0x8E64: 0x4ED5, //CJK UNIFIED IDEOGRAPH - 0x8E65: 0x4ED4, //CJK UNIFIED IDEOGRAPH - 0x8E66: 0x4F3A, //CJK UNIFIED IDEOGRAPH - 0x8E67: 0x4F7F, //CJK UNIFIED IDEOGRAPH - 0x8E68: 0x523A, //CJK UNIFIED IDEOGRAPH - 0x8E69: 0x53F8, //CJK UNIFIED IDEOGRAPH - 0x8E6A: 0x53F2, //CJK UNIFIED IDEOGRAPH - 0x8E6B: 0x55E3, //CJK UNIFIED IDEOGRAPH - 0x8E6C: 0x56DB, //CJK UNIFIED IDEOGRAPH - 0x8E6D: 0x58EB, //CJK UNIFIED IDEOGRAPH - 0x8E6E: 0x59CB, //CJK UNIFIED IDEOGRAPH - 0x8E6F: 0x59C9, //CJK UNIFIED IDEOGRAPH - 0x8E70: 0x59FF, //CJK UNIFIED IDEOGRAPH - 0x8E71: 0x5B50, //CJK UNIFIED IDEOGRAPH - 0x8E72: 0x5C4D, //CJK UNIFIED IDEOGRAPH - 0x8E73: 0x5E02, //CJK UNIFIED IDEOGRAPH - 0x8E74: 0x5E2B, //CJK UNIFIED IDEOGRAPH - 0x8E75: 0x5FD7, //CJK UNIFIED IDEOGRAPH - 0x8E76: 0x601D, //CJK UNIFIED IDEOGRAPH - 0x8E77: 0x6307, //CJK UNIFIED IDEOGRAPH - 0x8E78: 0x652F, //CJK UNIFIED IDEOGRAPH - 0x8E79: 0x5B5C, //CJK UNIFIED IDEOGRAPH - 0x8E7A: 0x65AF, //CJK UNIFIED IDEOGRAPH - 0x8E7B: 0x65BD, //CJK UNIFIED IDEOGRAPH - 0x8E7C: 0x65E8, //CJK UNIFIED IDEOGRAPH - 0x8E7D: 0x679D, //CJK UNIFIED IDEOGRAPH - 0x8E7E: 0x6B62, //CJK UNIFIED IDEOGRAPH - 0x8E80: 0x6B7B, //CJK UNIFIED IDEOGRAPH - 0x8E81: 0x6C0F, //CJK UNIFIED IDEOGRAPH - 0x8E82: 0x7345, //CJK UNIFIED IDEOGRAPH - 0x8E83: 0x7949, //CJK UNIFIED IDEOGRAPH - 0x8E84: 0x79C1, //CJK UNIFIED IDEOGRAPH - 0x8E85: 0x7CF8, //CJK UNIFIED IDEOGRAPH - 0x8E86: 0x7D19, //CJK UNIFIED IDEOGRAPH - 0x8E87: 0x7D2B, //CJK UNIFIED IDEOGRAPH - 0x8E88: 0x80A2, //CJK UNIFIED IDEOGRAPH - 0x8E89: 0x8102, //CJK UNIFIED IDEOGRAPH - 0x8E8A: 0x81F3, //CJK UNIFIED IDEOGRAPH - 0x8E8B: 0x8996, //CJK UNIFIED IDEOGRAPH - 0x8E8C: 0x8A5E, //CJK UNIFIED IDEOGRAPH - 0x8E8D: 0x8A69, //CJK UNIFIED IDEOGRAPH - 0x8E8E: 0x8A66, //CJK UNIFIED IDEOGRAPH - 0x8E8F: 0x8A8C, //CJK UNIFIED IDEOGRAPH - 0x8E90: 0x8AEE, //CJK UNIFIED IDEOGRAPH - 0x8E91: 0x8CC7, //CJK UNIFIED IDEOGRAPH - 0x8E92: 0x8CDC, //CJK UNIFIED IDEOGRAPH - 0x8E93: 0x96CC, //CJK UNIFIED IDEOGRAPH - 0x8E94: 0x98FC, //CJK UNIFIED IDEOGRAPH - 0x8E95: 0x6B6F, //CJK UNIFIED IDEOGRAPH - 0x8E96: 0x4E8B, //CJK UNIFIED IDEOGRAPH - 0x8E97: 0x4F3C, //CJK UNIFIED IDEOGRAPH - 0x8E98: 0x4F8D, //CJK UNIFIED IDEOGRAPH - 0x8E99: 0x5150, //CJK UNIFIED IDEOGRAPH - 0x8E9A: 0x5B57, //CJK UNIFIED IDEOGRAPH - 0x8E9B: 0x5BFA, //CJK UNIFIED IDEOGRAPH - 0x8E9C: 0x6148, //CJK UNIFIED IDEOGRAPH - 0x8E9D: 0x6301, //CJK UNIFIED IDEOGRAPH - 0x8E9E: 0x6642, //CJK UNIFIED IDEOGRAPH - 0x8E9F: 0x6B21, //CJK UNIFIED IDEOGRAPH - 0x8EA0: 0x6ECB, //CJK UNIFIED IDEOGRAPH - 0x8EA1: 0x6CBB, //CJK UNIFIED IDEOGRAPH - 0x8EA2: 0x723E, //CJK UNIFIED IDEOGRAPH - 0x8EA3: 0x74BD, //CJK UNIFIED IDEOGRAPH - 0x8EA4: 0x75D4, //CJK UNIFIED IDEOGRAPH - 0x8EA5: 0x78C1, //CJK UNIFIED IDEOGRAPH - 0x8EA6: 0x793A, //CJK UNIFIED IDEOGRAPH - 0x8EA7: 0x800C, //CJK UNIFIED IDEOGRAPH - 0x8EA8: 0x8033, //CJK UNIFIED IDEOGRAPH - 0x8EA9: 0x81EA, //CJK UNIFIED IDEOGRAPH - 0x8EAA: 0x8494, //CJK UNIFIED IDEOGRAPH - 0x8EAB: 0x8F9E, //CJK UNIFIED IDEOGRAPH - 0x8EAC: 0x6C50, //CJK UNIFIED IDEOGRAPH - 0x8EAD: 0x9E7F, //CJK UNIFIED IDEOGRAPH - 0x8EAE: 0x5F0F, //CJK UNIFIED IDEOGRAPH - 0x8EAF: 0x8B58, //CJK UNIFIED IDEOGRAPH - 0x8EB0: 0x9D2B, //CJK UNIFIED IDEOGRAPH - 0x8EB1: 0x7AFA, //CJK UNIFIED IDEOGRAPH - 0x8EB2: 0x8EF8, //CJK UNIFIED IDEOGRAPH - 0x8EB3: 0x5B8D, //CJK UNIFIED IDEOGRAPH - 0x8EB4: 0x96EB, //CJK UNIFIED IDEOGRAPH - 0x8EB5: 0x4E03, //CJK UNIFIED IDEOGRAPH - 0x8EB6: 0x53F1, //CJK UNIFIED IDEOGRAPH - 0x8EB7: 0x57F7, //CJK UNIFIED IDEOGRAPH - 0x8EB8: 0x5931, //CJK UNIFIED IDEOGRAPH - 0x8EB9: 0x5AC9, //CJK UNIFIED IDEOGRAPH - 0x8EBA: 0x5BA4, //CJK UNIFIED IDEOGRAPH - 0x8EBB: 0x6089, //CJK UNIFIED IDEOGRAPH - 0x8EBC: 0x6E7F, //CJK UNIFIED IDEOGRAPH - 0x8EBD: 0x6F06, //CJK UNIFIED IDEOGRAPH - 0x8EBE: 0x75BE, //CJK UNIFIED IDEOGRAPH - 0x8EBF: 0x8CEA, //CJK UNIFIED IDEOGRAPH - 0x8EC0: 0x5B9F, //CJK UNIFIED IDEOGRAPH - 0x8EC1: 0x8500, //CJK UNIFIED IDEOGRAPH - 0x8EC2: 0x7BE0, //CJK UNIFIED IDEOGRAPH - 0x8EC3: 0x5072, //CJK UNIFIED IDEOGRAPH - 0x8EC4: 0x67F4, //CJK UNIFIED IDEOGRAPH - 0x8EC5: 0x829D, //CJK UNIFIED IDEOGRAPH - 0x8EC6: 0x5C61, //CJK UNIFIED IDEOGRAPH - 0x8EC7: 0x854A, //CJK UNIFIED IDEOGRAPH - 0x8EC8: 0x7E1E, //CJK UNIFIED IDEOGRAPH - 0x8EC9: 0x820E, //CJK UNIFIED IDEOGRAPH - 0x8ECA: 0x5199, //CJK UNIFIED IDEOGRAPH - 0x8ECB: 0x5C04, //CJK UNIFIED IDEOGRAPH - 0x8ECC: 0x6368, //CJK UNIFIED IDEOGRAPH - 0x8ECD: 0x8D66, //CJK UNIFIED IDEOGRAPH - 0x8ECE: 0x659C, //CJK UNIFIED IDEOGRAPH - 0x8ECF: 0x716E, //CJK UNIFIED IDEOGRAPH - 0x8ED0: 0x793E, //CJK UNIFIED IDEOGRAPH - 0x8ED1: 0x7D17, //CJK UNIFIED IDEOGRAPH - 0x8ED2: 0x8005, //CJK UNIFIED IDEOGRAPH - 0x8ED3: 0x8B1D, //CJK UNIFIED IDEOGRAPH - 0x8ED4: 0x8ECA, //CJK UNIFIED IDEOGRAPH - 0x8ED5: 0x906E, //CJK UNIFIED IDEOGRAPH - 0x8ED6: 0x86C7, //CJK UNIFIED IDEOGRAPH - 0x8ED7: 0x90AA, //CJK UNIFIED IDEOGRAPH - 0x8ED8: 0x501F, //CJK UNIFIED IDEOGRAPH - 0x8ED9: 0x52FA, //CJK UNIFIED IDEOGRAPH - 0x8EDA: 0x5C3A, //CJK UNIFIED IDEOGRAPH - 0x8EDB: 0x6753, //CJK UNIFIED IDEOGRAPH - 0x8EDC: 0x707C, //CJK UNIFIED IDEOGRAPH - 0x8EDD: 0x7235, //CJK UNIFIED IDEOGRAPH - 0x8EDE: 0x914C, //CJK UNIFIED IDEOGRAPH - 0x8EDF: 0x91C8, //CJK UNIFIED IDEOGRAPH - 0x8EE0: 0x932B, //CJK UNIFIED IDEOGRAPH - 0x8EE1: 0x82E5, //CJK UNIFIED IDEOGRAPH - 0x8EE2: 0x5BC2, //CJK UNIFIED IDEOGRAPH - 0x8EE3: 0x5F31, //CJK UNIFIED IDEOGRAPH - 0x8EE4: 0x60F9, //CJK UNIFIED IDEOGRAPH - 0x8EE5: 0x4E3B, //CJK UNIFIED IDEOGRAPH - 0x8EE6: 0x53D6, //CJK UNIFIED IDEOGRAPH - 0x8EE7: 0x5B88, //CJK UNIFIED IDEOGRAPH - 0x8EE8: 0x624B, //CJK UNIFIED IDEOGRAPH - 0x8EE9: 0x6731, //CJK UNIFIED IDEOGRAPH - 0x8EEA: 0x6B8A, //CJK UNIFIED IDEOGRAPH - 0x8EEB: 0x72E9, //CJK UNIFIED IDEOGRAPH - 0x8EEC: 0x73E0, //CJK UNIFIED IDEOGRAPH - 0x8EED: 0x7A2E, //CJK UNIFIED IDEOGRAPH - 0x8EEE: 0x816B, //CJK UNIFIED IDEOGRAPH - 0x8EEF: 0x8DA3, //CJK UNIFIED IDEOGRAPH - 0x8EF0: 0x9152, //CJK UNIFIED IDEOGRAPH - 0x8EF1: 0x9996, //CJK UNIFIED IDEOGRAPH - 0x8EF2: 0x5112, //CJK UNIFIED IDEOGRAPH - 0x8EF3: 0x53D7, //CJK UNIFIED IDEOGRAPH - 0x8EF4: 0x546A, //CJK UNIFIED IDEOGRAPH - 0x8EF5: 0x5BFF, //CJK UNIFIED IDEOGRAPH - 0x8EF6: 0x6388, //CJK UNIFIED IDEOGRAPH - 0x8EF7: 0x6A39, //CJK UNIFIED IDEOGRAPH - 0x8EF8: 0x7DAC, //CJK UNIFIED IDEOGRAPH - 0x8EF9: 0x9700, //CJK UNIFIED IDEOGRAPH - 0x8EFA: 0x56DA, //CJK UNIFIED IDEOGRAPH - 0x8EFB: 0x53CE, //CJK UNIFIED IDEOGRAPH - 0x8EFC: 0x5468, //CJK UNIFIED IDEOGRAPH - 0x8F40: 0x5B97, //CJK UNIFIED IDEOGRAPH - 0x8F41: 0x5C31, //CJK UNIFIED IDEOGRAPH - 0x8F42: 0x5DDE, //CJK UNIFIED IDEOGRAPH - 0x8F43: 0x4FEE, //CJK UNIFIED IDEOGRAPH - 0x8F44: 0x6101, //CJK UNIFIED IDEOGRAPH - 0x8F45: 0x62FE, //CJK UNIFIED IDEOGRAPH - 0x8F46: 0x6D32, //CJK UNIFIED IDEOGRAPH - 0x8F47: 0x79C0, //CJK UNIFIED IDEOGRAPH - 0x8F48: 0x79CB, //CJK UNIFIED IDEOGRAPH - 0x8F49: 0x7D42, //CJK UNIFIED IDEOGRAPH - 0x8F4A: 0x7E4D, //CJK UNIFIED IDEOGRAPH - 0x8F4B: 0x7FD2, //CJK UNIFIED IDEOGRAPH - 0x8F4C: 0x81ED, //CJK UNIFIED IDEOGRAPH - 0x8F4D: 0x821F, //CJK UNIFIED IDEOGRAPH - 0x8F4E: 0x8490, //CJK UNIFIED IDEOGRAPH - 0x8F4F: 0x8846, //CJK UNIFIED IDEOGRAPH - 0x8F50: 0x8972, //CJK UNIFIED IDEOGRAPH - 0x8F51: 0x8B90, //CJK UNIFIED IDEOGRAPH - 0x8F52: 0x8E74, //CJK UNIFIED IDEOGRAPH - 0x8F53: 0x8F2F, //CJK UNIFIED IDEOGRAPH - 0x8F54: 0x9031, //CJK UNIFIED IDEOGRAPH - 0x8F55: 0x914B, //CJK UNIFIED IDEOGRAPH - 0x8F56: 0x916C, //CJK UNIFIED IDEOGRAPH - 0x8F57: 0x96C6, //CJK UNIFIED IDEOGRAPH - 0x8F58: 0x919C, //CJK UNIFIED IDEOGRAPH - 0x8F59: 0x4EC0, //CJK UNIFIED IDEOGRAPH - 0x8F5A: 0x4F4F, //CJK UNIFIED IDEOGRAPH - 0x8F5B: 0x5145, //CJK UNIFIED IDEOGRAPH - 0x8F5C: 0x5341, //CJK UNIFIED IDEOGRAPH - 0x8F5D: 0x5F93, //CJK UNIFIED IDEOGRAPH - 0x8F5E: 0x620E, //CJK UNIFIED IDEOGRAPH - 0x8F5F: 0x67D4, //CJK UNIFIED IDEOGRAPH - 0x8F60: 0x6C41, //CJK UNIFIED IDEOGRAPH - 0x8F61: 0x6E0B, //CJK UNIFIED IDEOGRAPH - 0x8F62: 0x7363, //CJK UNIFIED IDEOGRAPH - 0x8F63: 0x7E26, //CJK UNIFIED IDEOGRAPH - 0x8F64: 0x91CD, //CJK UNIFIED IDEOGRAPH - 0x8F65: 0x9283, //CJK UNIFIED IDEOGRAPH - 0x8F66: 0x53D4, //CJK UNIFIED IDEOGRAPH - 0x8F67: 0x5919, //CJK UNIFIED IDEOGRAPH - 0x8F68: 0x5BBF, //CJK UNIFIED IDEOGRAPH - 0x8F69: 0x6DD1, //CJK UNIFIED IDEOGRAPH - 0x8F6A: 0x795D, //CJK UNIFIED IDEOGRAPH - 0x8F6B: 0x7E2E, //CJK UNIFIED IDEOGRAPH - 0x8F6C: 0x7C9B, //CJK UNIFIED IDEOGRAPH - 0x8F6D: 0x587E, //CJK UNIFIED IDEOGRAPH - 0x8F6E: 0x719F, //CJK UNIFIED IDEOGRAPH - 0x8F6F: 0x51FA, //CJK UNIFIED IDEOGRAPH - 0x8F70: 0x8853, //CJK UNIFIED IDEOGRAPH - 0x8F71: 0x8FF0, //CJK UNIFIED IDEOGRAPH - 0x8F72: 0x4FCA, //CJK UNIFIED IDEOGRAPH - 0x8F73: 0x5CFB, //CJK UNIFIED IDEOGRAPH - 0x8F74: 0x6625, //CJK UNIFIED IDEOGRAPH - 0x8F75: 0x77AC, //CJK UNIFIED IDEOGRAPH - 0x8F76: 0x7AE3, //CJK UNIFIED IDEOGRAPH - 0x8F77: 0x821C, //CJK UNIFIED IDEOGRAPH - 0x8F78: 0x99FF, //CJK UNIFIED IDEOGRAPH - 0x8F79: 0x51C6, //CJK UNIFIED IDEOGRAPH - 0x8F7A: 0x5FAA, //CJK UNIFIED IDEOGRAPH - 0x8F7B: 0x65EC, //CJK UNIFIED IDEOGRAPH - 0x8F7C: 0x696F, //CJK UNIFIED IDEOGRAPH - 0x8F7D: 0x6B89, //CJK UNIFIED IDEOGRAPH - 0x8F7E: 0x6DF3, //CJK UNIFIED IDEOGRAPH - 0x8F80: 0x6E96, //CJK UNIFIED IDEOGRAPH - 0x8F81: 0x6F64, //CJK UNIFIED IDEOGRAPH - 0x8F82: 0x76FE, //CJK UNIFIED IDEOGRAPH - 0x8F83: 0x7D14, //CJK UNIFIED IDEOGRAPH - 0x8F84: 0x5DE1, //CJK UNIFIED IDEOGRAPH - 0x8F85: 0x9075, //CJK UNIFIED IDEOGRAPH - 0x8F86: 0x9187, //CJK UNIFIED IDEOGRAPH - 0x8F87: 0x9806, //CJK UNIFIED IDEOGRAPH - 0x8F88: 0x51E6, //CJK UNIFIED IDEOGRAPH - 0x8F89: 0x521D, //CJK UNIFIED IDEOGRAPH - 0x8F8A: 0x6240, //CJK UNIFIED IDEOGRAPH - 0x8F8B: 0x6691, //CJK UNIFIED IDEOGRAPH - 0x8F8C: 0x66D9, //CJK UNIFIED IDEOGRAPH - 0x8F8D: 0x6E1A, //CJK UNIFIED IDEOGRAPH - 0x8F8E: 0x5EB6, //CJK UNIFIED IDEOGRAPH - 0x8F8F: 0x7DD2, //CJK UNIFIED IDEOGRAPH - 0x8F90: 0x7F72, //CJK UNIFIED IDEOGRAPH - 0x8F91: 0x66F8, //CJK UNIFIED IDEOGRAPH - 0x8F92: 0x85AF, //CJK UNIFIED IDEOGRAPH - 0x8F93: 0x85F7, //CJK UNIFIED IDEOGRAPH - 0x8F94: 0x8AF8, //CJK UNIFIED IDEOGRAPH - 0x8F95: 0x52A9, //CJK UNIFIED IDEOGRAPH - 0x8F96: 0x53D9, //CJK UNIFIED IDEOGRAPH - 0x8F97: 0x5973, //CJK UNIFIED IDEOGRAPH - 0x8F98: 0x5E8F, //CJK UNIFIED IDEOGRAPH - 0x8F99: 0x5F90, //CJK UNIFIED IDEOGRAPH - 0x8F9A: 0x6055, //CJK UNIFIED IDEOGRAPH - 0x8F9B: 0x92E4, //CJK UNIFIED IDEOGRAPH - 0x8F9C: 0x9664, //CJK UNIFIED IDEOGRAPH - 0x8F9D: 0x50B7, //CJK UNIFIED IDEOGRAPH - 0x8F9E: 0x511F, //CJK UNIFIED IDEOGRAPH - 0x8F9F: 0x52DD, //CJK UNIFIED IDEOGRAPH - 0x8FA0: 0x5320, //CJK UNIFIED IDEOGRAPH - 0x8FA1: 0x5347, //CJK UNIFIED IDEOGRAPH - 0x8FA2: 0x53EC, //CJK UNIFIED IDEOGRAPH - 0x8FA3: 0x54E8, //CJK UNIFIED IDEOGRAPH - 0x8FA4: 0x5546, //CJK UNIFIED IDEOGRAPH - 0x8FA5: 0x5531, //CJK UNIFIED IDEOGRAPH - 0x8FA6: 0x5617, //CJK UNIFIED IDEOGRAPH - 0x8FA7: 0x5968, //CJK UNIFIED IDEOGRAPH - 0x8FA8: 0x59BE, //CJK UNIFIED IDEOGRAPH - 0x8FA9: 0x5A3C, //CJK UNIFIED IDEOGRAPH - 0x8FAA: 0x5BB5, //CJK UNIFIED IDEOGRAPH - 0x8FAB: 0x5C06, //CJK UNIFIED IDEOGRAPH - 0x8FAC: 0x5C0F, //CJK UNIFIED IDEOGRAPH - 0x8FAD: 0x5C11, //CJK UNIFIED IDEOGRAPH - 0x8FAE: 0x5C1A, //CJK UNIFIED IDEOGRAPH - 0x8FAF: 0x5E84, //CJK UNIFIED IDEOGRAPH - 0x8FB0: 0x5E8A, //CJK UNIFIED IDEOGRAPH - 0x8FB1: 0x5EE0, //CJK UNIFIED IDEOGRAPH - 0x8FB2: 0x5F70, //CJK UNIFIED IDEOGRAPH - 0x8FB3: 0x627F, //CJK UNIFIED IDEOGRAPH - 0x8FB4: 0x6284, //CJK UNIFIED IDEOGRAPH - 0x8FB5: 0x62DB, //CJK UNIFIED IDEOGRAPH - 0x8FB6: 0x638C, //CJK UNIFIED IDEOGRAPH - 0x8FB7: 0x6377, //CJK UNIFIED IDEOGRAPH - 0x8FB8: 0x6607, //CJK UNIFIED IDEOGRAPH - 0x8FB9: 0x660C, //CJK UNIFIED IDEOGRAPH - 0x8FBA: 0x662D, //CJK UNIFIED IDEOGRAPH - 0x8FBB: 0x6676, //CJK UNIFIED IDEOGRAPH - 0x8FBC: 0x677E, //CJK UNIFIED IDEOGRAPH - 0x8FBD: 0x68A2, //CJK UNIFIED IDEOGRAPH - 0x8FBE: 0x6A1F, //CJK UNIFIED IDEOGRAPH - 0x8FBF: 0x6A35, //CJK UNIFIED IDEOGRAPH - 0x8FC0: 0x6CBC, //CJK UNIFIED IDEOGRAPH - 0x8FC1: 0x6D88, //CJK UNIFIED IDEOGRAPH - 0x8FC2: 0x6E09, //CJK UNIFIED IDEOGRAPH - 0x8FC3: 0x6E58, //CJK UNIFIED IDEOGRAPH - 0x8FC4: 0x713C, //CJK UNIFIED IDEOGRAPH - 0x8FC5: 0x7126, //CJK UNIFIED IDEOGRAPH - 0x8FC6: 0x7167, //CJK UNIFIED IDEOGRAPH - 0x8FC7: 0x75C7, //CJK UNIFIED IDEOGRAPH - 0x8FC8: 0x7701, //CJK UNIFIED IDEOGRAPH - 0x8FC9: 0x785D, //CJK UNIFIED IDEOGRAPH - 0x8FCA: 0x7901, //CJK UNIFIED IDEOGRAPH - 0x8FCB: 0x7965, //CJK UNIFIED IDEOGRAPH - 0x8FCC: 0x79F0, //CJK UNIFIED IDEOGRAPH - 0x8FCD: 0x7AE0, //CJK UNIFIED IDEOGRAPH - 0x8FCE: 0x7B11, //CJK UNIFIED IDEOGRAPH - 0x8FCF: 0x7CA7, //CJK UNIFIED IDEOGRAPH - 0x8FD0: 0x7D39, //CJK UNIFIED IDEOGRAPH - 0x8FD1: 0x8096, //CJK UNIFIED IDEOGRAPH - 0x8FD2: 0x83D6, //CJK UNIFIED IDEOGRAPH - 0x8FD3: 0x848B, //CJK UNIFIED IDEOGRAPH - 0x8FD4: 0x8549, //CJK UNIFIED IDEOGRAPH - 0x8FD5: 0x885D, //CJK UNIFIED IDEOGRAPH - 0x8FD6: 0x88F3, //CJK UNIFIED IDEOGRAPH - 0x8FD7: 0x8A1F, //CJK UNIFIED IDEOGRAPH - 0x8FD8: 0x8A3C, //CJK UNIFIED IDEOGRAPH - 0x8FD9: 0x8A54, //CJK UNIFIED IDEOGRAPH - 0x8FDA: 0x8A73, //CJK UNIFIED IDEOGRAPH - 0x8FDB: 0x8C61, //CJK UNIFIED IDEOGRAPH - 0x8FDC: 0x8CDE, //CJK UNIFIED IDEOGRAPH - 0x8FDD: 0x91A4, //CJK UNIFIED IDEOGRAPH - 0x8FDE: 0x9266, //CJK UNIFIED IDEOGRAPH - 0x8FDF: 0x937E, //CJK UNIFIED IDEOGRAPH - 0x8FE0: 0x9418, //CJK UNIFIED IDEOGRAPH - 0x8FE1: 0x969C, //CJK UNIFIED IDEOGRAPH - 0x8FE2: 0x9798, //CJK UNIFIED IDEOGRAPH - 0x8FE3: 0x4E0A, //CJK UNIFIED IDEOGRAPH - 0x8FE4: 0x4E08, //CJK UNIFIED IDEOGRAPH - 0x8FE5: 0x4E1E, //CJK UNIFIED IDEOGRAPH - 0x8FE6: 0x4E57, //CJK UNIFIED IDEOGRAPH - 0x8FE7: 0x5197, //CJK UNIFIED IDEOGRAPH - 0x8FE8: 0x5270, //CJK UNIFIED IDEOGRAPH - 0x8FE9: 0x57CE, //CJK UNIFIED IDEOGRAPH - 0x8FEA: 0x5834, //CJK UNIFIED IDEOGRAPH - 0x8FEB: 0x58CC, //CJK UNIFIED IDEOGRAPH - 0x8FEC: 0x5B22, //CJK UNIFIED IDEOGRAPH - 0x8FED: 0x5E38, //CJK UNIFIED IDEOGRAPH - 0x8FEE: 0x60C5, //CJK UNIFIED IDEOGRAPH - 0x8FEF: 0x64FE, //CJK UNIFIED IDEOGRAPH - 0x8FF0: 0x6761, //CJK UNIFIED IDEOGRAPH - 0x8FF1: 0x6756, //CJK UNIFIED IDEOGRAPH - 0x8FF2: 0x6D44, //CJK UNIFIED IDEOGRAPH - 0x8FF3: 0x72B6, //CJK UNIFIED IDEOGRAPH - 0x8FF4: 0x7573, //CJK UNIFIED IDEOGRAPH - 0x8FF5: 0x7A63, //CJK UNIFIED IDEOGRAPH - 0x8FF6: 0x84B8, //CJK UNIFIED IDEOGRAPH - 0x8FF7: 0x8B72, //CJK UNIFIED IDEOGRAPH - 0x8FF8: 0x91B8, //CJK UNIFIED IDEOGRAPH - 0x8FF9: 0x9320, //CJK UNIFIED IDEOGRAPH - 0x8FFA: 0x5631, //CJK UNIFIED IDEOGRAPH - 0x8FFB: 0x57F4, //CJK UNIFIED IDEOGRAPH - 0x8FFC: 0x98FE, //CJK UNIFIED IDEOGRAPH - 0x9040: 0x62ED, //CJK UNIFIED IDEOGRAPH - 0x9041: 0x690D, //CJK UNIFIED IDEOGRAPH - 0x9042: 0x6B96, //CJK UNIFIED IDEOGRAPH - 0x9043: 0x71ED, //CJK UNIFIED IDEOGRAPH - 0x9044: 0x7E54, //CJK UNIFIED IDEOGRAPH - 0x9045: 0x8077, //CJK UNIFIED IDEOGRAPH - 0x9046: 0x8272, //CJK UNIFIED IDEOGRAPH - 0x9047: 0x89E6, //CJK UNIFIED IDEOGRAPH - 0x9048: 0x98DF, //CJK UNIFIED IDEOGRAPH - 0x9049: 0x8755, //CJK UNIFIED IDEOGRAPH - 0x904A: 0x8FB1, //CJK UNIFIED IDEOGRAPH - 0x904B: 0x5C3B, //CJK UNIFIED IDEOGRAPH - 0x904C: 0x4F38, //CJK UNIFIED IDEOGRAPH - 0x904D: 0x4FE1, //CJK UNIFIED IDEOGRAPH - 0x904E: 0x4FB5, //CJK UNIFIED IDEOGRAPH - 0x904F: 0x5507, //CJK UNIFIED IDEOGRAPH - 0x9050: 0x5A20, //CJK UNIFIED IDEOGRAPH - 0x9051: 0x5BDD, //CJK UNIFIED IDEOGRAPH - 0x9052: 0x5BE9, //CJK UNIFIED IDEOGRAPH - 0x9053: 0x5FC3, //CJK UNIFIED IDEOGRAPH - 0x9054: 0x614E, //CJK UNIFIED IDEOGRAPH - 0x9055: 0x632F, //CJK UNIFIED IDEOGRAPH - 0x9056: 0x65B0, //CJK UNIFIED IDEOGRAPH - 0x9057: 0x664B, //CJK UNIFIED IDEOGRAPH - 0x9058: 0x68EE, //CJK UNIFIED IDEOGRAPH - 0x9059: 0x699B, //CJK UNIFIED IDEOGRAPH - 0x905A: 0x6D78, //CJK UNIFIED IDEOGRAPH - 0x905B: 0x6DF1, //CJK UNIFIED IDEOGRAPH - 0x905C: 0x7533, //CJK UNIFIED IDEOGRAPH - 0x905D: 0x75B9, //CJK UNIFIED IDEOGRAPH - 0x905E: 0x771F, //CJK UNIFIED IDEOGRAPH - 0x905F: 0x795E, //CJK UNIFIED IDEOGRAPH - 0x9060: 0x79E6, //CJK UNIFIED IDEOGRAPH - 0x9061: 0x7D33, //CJK UNIFIED IDEOGRAPH - 0x9062: 0x81E3, //CJK UNIFIED IDEOGRAPH - 0x9063: 0x82AF, //CJK UNIFIED IDEOGRAPH - 0x9064: 0x85AA, //CJK UNIFIED IDEOGRAPH - 0x9065: 0x89AA, //CJK UNIFIED IDEOGRAPH - 0x9066: 0x8A3A, //CJK UNIFIED IDEOGRAPH - 0x9067: 0x8EAB, //CJK UNIFIED IDEOGRAPH - 0x9068: 0x8F9B, //CJK UNIFIED IDEOGRAPH - 0x9069: 0x9032, //CJK UNIFIED IDEOGRAPH - 0x906A: 0x91DD, //CJK UNIFIED IDEOGRAPH - 0x906B: 0x9707, //CJK UNIFIED IDEOGRAPH - 0x906C: 0x4EBA, //CJK UNIFIED IDEOGRAPH - 0x906D: 0x4EC1, //CJK UNIFIED IDEOGRAPH - 0x906E: 0x5203, //CJK UNIFIED IDEOGRAPH - 0x906F: 0x5875, //CJK UNIFIED IDEOGRAPH - 0x9070: 0x58EC, //CJK UNIFIED IDEOGRAPH - 0x9071: 0x5C0B, //CJK UNIFIED IDEOGRAPH - 0x9072: 0x751A, //CJK UNIFIED IDEOGRAPH - 0x9073: 0x5C3D, //CJK UNIFIED IDEOGRAPH - 0x9074: 0x814E, //CJK UNIFIED IDEOGRAPH - 0x9075: 0x8A0A, //CJK UNIFIED IDEOGRAPH - 0x9076: 0x8FC5, //CJK UNIFIED IDEOGRAPH - 0x9077: 0x9663, //CJK UNIFIED IDEOGRAPH - 0x9078: 0x976D, //CJK UNIFIED IDEOGRAPH - 0x9079: 0x7B25, //CJK UNIFIED IDEOGRAPH - 0x907A: 0x8ACF, //CJK UNIFIED IDEOGRAPH - 0x907B: 0x9808, //CJK UNIFIED IDEOGRAPH - 0x907C: 0x9162, //CJK UNIFIED IDEOGRAPH - 0x907D: 0x56F3, //CJK UNIFIED IDEOGRAPH - 0x907E: 0x53A8, //CJK UNIFIED IDEOGRAPH - 0x9080: 0x9017, //CJK UNIFIED IDEOGRAPH - 0x9081: 0x5439, //CJK UNIFIED IDEOGRAPH - 0x9082: 0x5782, //CJK UNIFIED IDEOGRAPH - 0x9083: 0x5E25, //CJK UNIFIED IDEOGRAPH - 0x9084: 0x63A8, //CJK UNIFIED IDEOGRAPH - 0x9085: 0x6C34, //CJK UNIFIED IDEOGRAPH - 0x9086: 0x708A, //CJK UNIFIED IDEOGRAPH - 0x9087: 0x7761, //CJK UNIFIED IDEOGRAPH - 0x9088: 0x7C8B, //CJK UNIFIED IDEOGRAPH - 0x9089: 0x7FE0, //CJK UNIFIED IDEOGRAPH - 0x908A: 0x8870, //CJK UNIFIED IDEOGRAPH - 0x908B: 0x9042, //CJK UNIFIED IDEOGRAPH - 0x908C: 0x9154, //CJK UNIFIED IDEOGRAPH - 0x908D: 0x9310, //CJK UNIFIED IDEOGRAPH - 0x908E: 0x9318, //CJK UNIFIED IDEOGRAPH - 0x908F: 0x968F, //CJK UNIFIED IDEOGRAPH - 0x9090: 0x745E, //CJK UNIFIED IDEOGRAPH - 0x9091: 0x9AC4, //CJK UNIFIED IDEOGRAPH - 0x9092: 0x5D07, //CJK UNIFIED IDEOGRAPH - 0x9093: 0x5D69, //CJK UNIFIED IDEOGRAPH - 0x9094: 0x6570, //CJK UNIFIED IDEOGRAPH - 0x9095: 0x67A2, //CJK UNIFIED IDEOGRAPH - 0x9096: 0x8DA8, //CJK UNIFIED IDEOGRAPH - 0x9097: 0x96DB, //CJK UNIFIED IDEOGRAPH - 0x9098: 0x636E, //CJK UNIFIED IDEOGRAPH - 0x9099: 0x6749, //CJK UNIFIED IDEOGRAPH - 0x909A: 0x6919, //CJK UNIFIED IDEOGRAPH - 0x909B: 0x83C5, //CJK UNIFIED IDEOGRAPH - 0x909C: 0x9817, //CJK UNIFIED IDEOGRAPH - 0x909D: 0x96C0, //CJK UNIFIED IDEOGRAPH - 0x909E: 0x88FE, //CJK UNIFIED IDEOGRAPH - 0x909F: 0x6F84, //CJK UNIFIED IDEOGRAPH - 0x90A0: 0x647A, //CJK UNIFIED IDEOGRAPH - 0x90A1: 0x5BF8, //CJK UNIFIED IDEOGRAPH - 0x90A2: 0x4E16, //CJK UNIFIED IDEOGRAPH - 0x90A3: 0x702C, //CJK UNIFIED IDEOGRAPH - 0x90A4: 0x755D, //CJK UNIFIED IDEOGRAPH - 0x90A5: 0x662F, //CJK UNIFIED IDEOGRAPH - 0x90A6: 0x51C4, //CJK UNIFIED IDEOGRAPH - 0x90A7: 0x5236, //CJK UNIFIED IDEOGRAPH - 0x90A8: 0x52E2, //CJK UNIFIED IDEOGRAPH - 0x90A9: 0x59D3, //CJK UNIFIED IDEOGRAPH - 0x90AA: 0x5F81, //CJK UNIFIED IDEOGRAPH - 0x90AB: 0x6027, //CJK UNIFIED IDEOGRAPH - 0x90AC: 0x6210, //CJK UNIFIED IDEOGRAPH - 0x90AD: 0x653F, //CJK UNIFIED IDEOGRAPH - 0x90AE: 0x6574, //CJK UNIFIED IDEOGRAPH - 0x90AF: 0x661F, //CJK UNIFIED IDEOGRAPH - 0x90B0: 0x6674, //CJK UNIFIED IDEOGRAPH - 0x90B1: 0x68F2, //CJK UNIFIED IDEOGRAPH - 0x90B2: 0x6816, //CJK UNIFIED IDEOGRAPH - 0x90B3: 0x6B63, //CJK UNIFIED IDEOGRAPH - 0x90B4: 0x6E05, //CJK UNIFIED IDEOGRAPH - 0x90B5: 0x7272, //CJK UNIFIED IDEOGRAPH - 0x90B6: 0x751F, //CJK UNIFIED IDEOGRAPH - 0x90B7: 0x76DB, //CJK UNIFIED IDEOGRAPH - 0x90B8: 0x7CBE, //CJK UNIFIED IDEOGRAPH - 0x90B9: 0x8056, //CJK UNIFIED IDEOGRAPH - 0x90BA: 0x58F0, //CJK UNIFIED IDEOGRAPH - 0x90BB: 0x88FD, //CJK UNIFIED IDEOGRAPH - 0x90BC: 0x897F, //CJK UNIFIED IDEOGRAPH - 0x90BD: 0x8AA0, //CJK UNIFIED IDEOGRAPH - 0x90BE: 0x8A93, //CJK UNIFIED IDEOGRAPH - 0x90BF: 0x8ACB, //CJK UNIFIED IDEOGRAPH - 0x90C0: 0x901D, //CJK UNIFIED IDEOGRAPH - 0x90C1: 0x9192, //CJK UNIFIED IDEOGRAPH - 0x90C2: 0x9752, //CJK UNIFIED IDEOGRAPH - 0x90C3: 0x9759, //CJK UNIFIED IDEOGRAPH - 0x90C4: 0x6589, //CJK UNIFIED IDEOGRAPH - 0x90C5: 0x7A0E, //CJK UNIFIED IDEOGRAPH - 0x90C6: 0x8106, //CJK UNIFIED IDEOGRAPH - 0x90C7: 0x96BB, //CJK UNIFIED IDEOGRAPH - 0x90C8: 0x5E2D, //CJK UNIFIED IDEOGRAPH - 0x90C9: 0x60DC, //CJK UNIFIED IDEOGRAPH - 0x90CA: 0x621A, //CJK UNIFIED IDEOGRAPH - 0x90CB: 0x65A5, //CJK UNIFIED IDEOGRAPH - 0x90CC: 0x6614, //CJK UNIFIED IDEOGRAPH - 0x90CD: 0x6790, //CJK UNIFIED IDEOGRAPH - 0x90CE: 0x77F3, //CJK UNIFIED IDEOGRAPH - 0x90CF: 0x7A4D, //CJK UNIFIED IDEOGRAPH - 0x90D0: 0x7C4D, //CJK UNIFIED IDEOGRAPH - 0x90D1: 0x7E3E, //CJK UNIFIED IDEOGRAPH - 0x90D2: 0x810A, //CJK UNIFIED IDEOGRAPH - 0x90D3: 0x8CAC, //CJK UNIFIED IDEOGRAPH - 0x90D4: 0x8D64, //CJK UNIFIED IDEOGRAPH - 0x90D5: 0x8DE1, //CJK UNIFIED IDEOGRAPH - 0x90D6: 0x8E5F, //CJK UNIFIED IDEOGRAPH - 0x90D7: 0x78A9, //CJK UNIFIED IDEOGRAPH - 0x90D8: 0x5207, //CJK UNIFIED IDEOGRAPH - 0x90D9: 0x62D9, //CJK UNIFIED IDEOGRAPH - 0x90DA: 0x63A5, //CJK UNIFIED IDEOGRAPH - 0x90DB: 0x6442, //CJK UNIFIED IDEOGRAPH - 0x90DC: 0x6298, //CJK UNIFIED IDEOGRAPH - 0x90DD: 0x8A2D, //CJK UNIFIED IDEOGRAPH - 0x90DE: 0x7A83, //CJK UNIFIED IDEOGRAPH - 0x90DF: 0x7BC0, //CJK UNIFIED IDEOGRAPH - 0x90E0: 0x8AAC, //CJK UNIFIED IDEOGRAPH - 0x90E1: 0x96EA, //CJK UNIFIED IDEOGRAPH - 0x90E2: 0x7D76, //CJK UNIFIED IDEOGRAPH - 0x90E3: 0x820C, //CJK UNIFIED IDEOGRAPH - 0x90E4: 0x8749, //CJK UNIFIED IDEOGRAPH - 0x90E5: 0x4ED9, //CJK UNIFIED IDEOGRAPH - 0x90E6: 0x5148, //CJK UNIFIED IDEOGRAPH - 0x90E7: 0x5343, //CJK UNIFIED IDEOGRAPH - 0x90E8: 0x5360, //CJK UNIFIED IDEOGRAPH - 0x90E9: 0x5BA3, //CJK UNIFIED IDEOGRAPH - 0x90EA: 0x5C02, //CJK UNIFIED IDEOGRAPH - 0x90EB: 0x5C16, //CJK UNIFIED IDEOGRAPH - 0x90EC: 0x5DDD, //CJK UNIFIED IDEOGRAPH - 0x90ED: 0x6226, //CJK UNIFIED IDEOGRAPH - 0x90EE: 0x6247, //CJK UNIFIED IDEOGRAPH - 0x90EF: 0x64B0, //CJK UNIFIED IDEOGRAPH - 0x90F0: 0x6813, //CJK UNIFIED IDEOGRAPH - 0x90F1: 0x6834, //CJK UNIFIED IDEOGRAPH - 0x90F2: 0x6CC9, //CJK UNIFIED IDEOGRAPH - 0x90F3: 0x6D45, //CJK UNIFIED IDEOGRAPH - 0x90F4: 0x6D17, //CJK UNIFIED IDEOGRAPH - 0x90F5: 0x67D3, //CJK UNIFIED IDEOGRAPH - 0x90F6: 0x6F5C, //CJK UNIFIED IDEOGRAPH - 0x90F7: 0x714E, //CJK UNIFIED IDEOGRAPH - 0x90F8: 0x717D, //CJK UNIFIED IDEOGRAPH - 0x90F9: 0x65CB, //CJK UNIFIED IDEOGRAPH - 0x90FA: 0x7A7F, //CJK UNIFIED IDEOGRAPH - 0x90FB: 0x7BAD, //CJK UNIFIED IDEOGRAPH - 0x90FC: 0x7DDA, //CJK UNIFIED IDEOGRAPH - 0x9140: 0x7E4A, //CJK UNIFIED IDEOGRAPH - 0x9141: 0x7FA8, //CJK UNIFIED IDEOGRAPH - 0x9142: 0x817A, //CJK UNIFIED IDEOGRAPH - 0x9143: 0x821B, //CJK UNIFIED IDEOGRAPH - 0x9144: 0x8239, //CJK UNIFIED IDEOGRAPH - 0x9145: 0x85A6, //CJK UNIFIED IDEOGRAPH - 0x9146: 0x8A6E, //CJK UNIFIED IDEOGRAPH - 0x9147: 0x8CCE, //CJK UNIFIED IDEOGRAPH - 0x9148: 0x8DF5, //CJK UNIFIED IDEOGRAPH - 0x9149: 0x9078, //CJK UNIFIED IDEOGRAPH - 0x914A: 0x9077, //CJK UNIFIED IDEOGRAPH - 0x914B: 0x92AD, //CJK UNIFIED IDEOGRAPH - 0x914C: 0x9291, //CJK UNIFIED IDEOGRAPH - 0x914D: 0x9583, //CJK UNIFIED IDEOGRAPH - 0x914E: 0x9BAE, //CJK UNIFIED IDEOGRAPH - 0x914F: 0x524D, //CJK UNIFIED IDEOGRAPH - 0x9150: 0x5584, //CJK UNIFIED IDEOGRAPH - 0x9151: 0x6F38, //CJK UNIFIED IDEOGRAPH - 0x9152: 0x7136, //CJK UNIFIED IDEOGRAPH - 0x9153: 0x5168, //CJK UNIFIED IDEOGRAPH - 0x9154: 0x7985, //CJK UNIFIED IDEOGRAPH - 0x9155: 0x7E55, //CJK UNIFIED IDEOGRAPH - 0x9156: 0x81B3, //CJK UNIFIED IDEOGRAPH - 0x9157: 0x7CCE, //CJK UNIFIED IDEOGRAPH - 0x9158: 0x564C, //CJK UNIFIED IDEOGRAPH - 0x9159: 0x5851, //CJK UNIFIED IDEOGRAPH - 0x915A: 0x5CA8, //CJK UNIFIED IDEOGRAPH - 0x915B: 0x63AA, //CJK UNIFIED IDEOGRAPH - 0x915C: 0x66FE, //CJK UNIFIED IDEOGRAPH - 0x915D: 0x66FD, //CJK UNIFIED IDEOGRAPH - 0x915E: 0x695A, //CJK UNIFIED IDEOGRAPH - 0x915F: 0x72D9, //CJK UNIFIED IDEOGRAPH - 0x9160: 0x758F, //CJK UNIFIED IDEOGRAPH - 0x9161: 0x758E, //CJK UNIFIED IDEOGRAPH - 0x9162: 0x790E, //CJK UNIFIED IDEOGRAPH - 0x9163: 0x7956, //CJK UNIFIED IDEOGRAPH - 0x9164: 0x79DF, //CJK UNIFIED IDEOGRAPH - 0x9165: 0x7C97, //CJK UNIFIED IDEOGRAPH - 0x9166: 0x7D20, //CJK UNIFIED IDEOGRAPH - 0x9167: 0x7D44, //CJK UNIFIED IDEOGRAPH - 0x9168: 0x8607, //CJK UNIFIED IDEOGRAPH - 0x9169: 0x8A34, //CJK UNIFIED IDEOGRAPH - 0x916A: 0x963B, //CJK UNIFIED IDEOGRAPH - 0x916B: 0x9061, //CJK UNIFIED IDEOGRAPH - 0x916C: 0x9F20, //CJK UNIFIED IDEOGRAPH - 0x916D: 0x50E7, //CJK UNIFIED IDEOGRAPH - 0x916E: 0x5275, //CJK UNIFIED IDEOGRAPH - 0x916F: 0x53CC, //CJK UNIFIED IDEOGRAPH - 0x9170: 0x53E2, //CJK UNIFIED IDEOGRAPH - 0x9171: 0x5009, //CJK UNIFIED IDEOGRAPH - 0x9172: 0x55AA, //CJK UNIFIED IDEOGRAPH - 0x9173: 0x58EE, //CJK UNIFIED IDEOGRAPH - 0x9174: 0x594F, //CJK UNIFIED IDEOGRAPH - 0x9175: 0x723D, //CJK UNIFIED IDEOGRAPH - 0x9176: 0x5B8B, //CJK UNIFIED IDEOGRAPH - 0x9177: 0x5C64, //CJK UNIFIED IDEOGRAPH - 0x9178: 0x531D, //CJK UNIFIED IDEOGRAPH - 0x9179: 0x60E3, //CJK UNIFIED IDEOGRAPH - 0x917A: 0x60F3, //CJK UNIFIED IDEOGRAPH - 0x917B: 0x635C, //CJK UNIFIED IDEOGRAPH - 0x917C: 0x6383, //CJK UNIFIED IDEOGRAPH - 0x917D: 0x633F, //CJK UNIFIED IDEOGRAPH - 0x917E: 0x63BB, //CJK UNIFIED IDEOGRAPH - 0x9180: 0x64CD, //CJK UNIFIED IDEOGRAPH - 0x9181: 0x65E9, //CJK UNIFIED IDEOGRAPH - 0x9182: 0x66F9, //CJK UNIFIED IDEOGRAPH - 0x9183: 0x5DE3, //CJK UNIFIED IDEOGRAPH - 0x9184: 0x69CD, //CJK UNIFIED IDEOGRAPH - 0x9185: 0x69FD, //CJK UNIFIED IDEOGRAPH - 0x9186: 0x6F15, //CJK UNIFIED IDEOGRAPH - 0x9187: 0x71E5, //CJK UNIFIED IDEOGRAPH - 0x9188: 0x4E89, //CJK UNIFIED IDEOGRAPH - 0x9189: 0x75E9, //CJK UNIFIED IDEOGRAPH - 0x918A: 0x76F8, //CJK UNIFIED IDEOGRAPH - 0x918B: 0x7A93, //CJK UNIFIED IDEOGRAPH - 0x918C: 0x7CDF, //CJK UNIFIED IDEOGRAPH - 0x918D: 0x7DCF, //CJK UNIFIED IDEOGRAPH - 0x918E: 0x7D9C, //CJK UNIFIED IDEOGRAPH - 0x918F: 0x8061, //CJK UNIFIED IDEOGRAPH - 0x9190: 0x8349, //CJK UNIFIED IDEOGRAPH - 0x9191: 0x8358, //CJK UNIFIED IDEOGRAPH - 0x9192: 0x846C, //CJK UNIFIED IDEOGRAPH - 0x9193: 0x84BC, //CJK UNIFIED IDEOGRAPH - 0x9194: 0x85FB, //CJK UNIFIED IDEOGRAPH - 0x9195: 0x88C5, //CJK UNIFIED IDEOGRAPH - 0x9196: 0x8D70, //CJK UNIFIED IDEOGRAPH - 0x9197: 0x9001, //CJK UNIFIED IDEOGRAPH - 0x9198: 0x906D, //CJK UNIFIED IDEOGRAPH - 0x9199: 0x9397, //CJK UNIFIED IDEOGRAPH - 0x919A: 0x971C, //CJK UNIFIED IDEOGRAPH - 0x919B: 0x9A12, //CJK UNIFIED IDEOGRAPH - 0x919C: 0x50CF, //CJK UNIFIED IDEOGRAPH - 0x919D: 0x5897, //CJK UNIFIED IDEOGRAPH - 0x919E: 0x618E, //CJK UNIFIED IDEOGRAPH - 0x919F: 0x81D3, //CJK UNIFIED IDEOGRAPH - 0x91A0: 0x8535, //CJK UNIFIED IDEOGRAPH - 0x91A1: 0x8D08, //CJK UNIFIED IDEOGRAPH - 0x91A2: 0x9020, //CJK UNIFIED IDEOGRAPH - 0x91A3: 0x4FC3, //CJK UNIFIED IDEOGRAPH - 0x91A4: 0x5074, //CJK UNIFIED IDEOGRAPH - 0x91A5: 0x5247, //CJK UNIFIED IDEOGRAPH - 0x91A6: 0x5373, //CJK UNIFIED IDEOGRAPH - 0x91A7: 0x606F, //CJK UNIFIED IDEOGRAPH - 0x91A8: 0x6349, //CJK UNIFIED IDEOGRAPH - 0x91A9: 0x675F, //CJK UNIFIED IDEOGRAPH - 0x91AA: 0x6E2C, //CJK UNIFIED IDEOGRAPH - 0x91AB: 0x8DB3, //CJK UNIFIED IDEOGRAPH - 0x91AC: 0x901F, //CJK UNIFIED IDEOGRAPH - 0x91AD: 0x4FD7, //CJK UNIFIED IDEOGRAPH - 0x91AE: 0x5C5E, //CJK UNIFIED IDEOGRAPH - 0x91AF: 0x8CCA, //CJK UNIFIED IDEOGRAPH - 0x91B0: 0x65CF, //CJK UNIFIED IDEOGRAPH - 0x91B1: 0x7D9A, //CJK UNIFIED IDEOGRAPH - 0x91B2: 0x5352, //CJK UNIFIED IDEOGRAPH - 0x91B3: 0x8896, //CJK UNIFIED IDEOGRAPH - 0x91B4: 0x5176, //CJK UNIFIED IDEOGRAPH - 0x91B5: 0x63C3, //CJK UNIFIED IDEOGRAPH - 0x91B6: 0x5B58, //CJK UNIFIED IDEOGRAPH - 0x91B7: 0x5B6B, //CJK UNIFIED IDEOGRAPH - 0x91B8: 0x5C0A, //CJK UNIFIED IDEOGRAPH - 0x91B9: 0x640D, //CJK UNIFIED IDEOGRAPH - 0x91BA: 0x6751, //CJK UNIFIED IDEOGRAPH - 0x91BB: 0x905C, //CJK UNIFIED IDEOGRAPH - 0x91BC: 0x4ED6, //CJK UNIFIED IDEOGRAPH - 0x91BD: 0x591A, //CJK UNIFIED IDEOGRAPH - 0x91BE: 0x592A, //CJK UNIFIED IDEOGRAPH - 0x91BF: 0x6C70, //CJK UNIFIED IDEOGRAPH - 0x91C0: 0x8A51, //CJK UNIFIED IDEOGRAPH - 0x91C1: 0x553E, //CJK UNIFIED IDEOGRAPH - 0x91C2: 0x5815, //CJK UNIFIED IDEOGRAPH - 0x91C3: 0x59A5, //CJK UNIFIED IDEOGRAPH - 0x91C4: 0x60F0, //CJK UNIFIED IDEOGRAPH - 0x91C5: 0x6253, //CJK UNIFIED IDEOGRAPH - 0x91C6: 0x67C1, //CJK UNIFIED IDEOGRAPH - 0x91C7: 0x8235, //CJK UNIFIED IDEOGRAPH - 0x91C8: 0x6955, //CJK UNIFIED IDEOGRAPH - 0x91C9: 0x9640, //CJK UNIFIED IDEOGRAPH - 0x91CA: 0x99C4, //CJK UNIFIED IDEOGRAPH - 0x91CB: 0x9A28, //CJK UNIFIED IDEOGRAPH - 0x91CC: 0x4F53, //CJK UNIFIED IDEOGRAPH - 0x91CD: 0x5806, //CJK UNIFIED IDEOGRAPH - 0x91CE: 0x5BFE, //CJK UNIFIED IDEOGRAPH - 0x91CF: 0x8010, //CJK UNIFIED IDEOGRAPH - 0x91D0: 0x5CB1, //CJK UNIFIED IDEOGRAPH - 0x91D1: 0x5E2F, //CJK UNIFIED IDEOGRAPH - 0x91D2: 0x5F85, //CJK UNIFIED IDEOGRAPH - 0x91D3: 0x6020, //CJK UNIFIED IDEOGRAPH - 0x91D4: 0x614B, //CJK UNIFIED IDEOGRAPH - 0x91D5: 0x6234, //CJK UNIFIED IDEOGRAPH - 0x91D6: 0x66FF, //CJK UNIFIED IDEOGRAPH - 0x91D7: 0x6CF0, //CJK UNIFIED IDEOGRAPH - 0x91D8: 0x6EDE, //CJK UNIFIED IDEOGRAPH - 0x91D9: 0x80CE, //CJK UNIFIED IDEOGRAPH - 0x91DA: 0x817F, //CJK UNIFIED IDEOGRAPH - 0x91DB: 0x82D4, //CJK UNIFIED IDEOGRAPH - 0x91DC: 0x888B, //CJK UNIFIED IDEOGRAPH - 0x91DD: 0x8CB8, //CJK UNIFIED IDEOGRAPH - 0x91DE: 0x9000, //CJK UNIFIED IDEOGRAPH - 0x91DF: 0x902E, //CJK UNIFIED IDEOGRAPH - 0x91E0: 0x968A, //CJK UNIFIED IDEOGRAPH - 0x91E1: 0x9EDB, //CJK UNIFIED IDEOGRAPH - 0x91E2: 0x9BDB, //CJK UNIFIED IDEOGRAPH - 0x91E3: 0x4EE3, //CJK UNIFIED IDEOGRAPH - 0x91E4: 0x53F0, //CJK UNIFIED IDEOGRAPH - 0x91E5: 0x5927, //CJK UNIFIED IDEOGRAPH - 0x91E6: 0x7B2C, //CJK UNIFIED IDEOGRAPH - 0x91E7: 0x918D, //CJK UNIFIED IDEOGRAPH - 0x91E8: 0x984C, //CJK UNIFIED IDEOGRAPH - 0x91E9: 0x9DF9, //CJK UNIFIED IDEOGRAPH - 0x91EA: 0x6EDD, //CJK UNIFIED IDEOGRAPH - 0x91EB: 0x7027, //CJK UNIFIED IDEOGRAPH - 0x91EC: 0x5353, //CJK UNIFIED IDEOGRAPH - 0x91ED: 0x5544, //CJK UNIFIED IDEOGRAPH - 0x91EE: 0x5B85, //CJK UNIFIED IDEOGRAPH - 0x91EF: 0x6258, //CJK UNIFIED IDEOGRAPH - 0x91F0: 0x629E, //CJK UNIFIED IDEOGRAPH - 0x91F1: 0x62D3, //CJK UNIFIED IDEOGRAPH - 0x91F2: 0x6CA2, //CJK UNIFIED IDEOGRAPH - 0x91F3: 0x6FEF, //CJK UNIFIED IDEOGRAPH - 0x91F4: 0x7422, //CJK UNIFIED IDEOGRAPH - 0x91F5: 0x8A17, //CJK UNIFIED IDEOGRAPH - 0x91F6: 0x9438, //CJK UNIFIED IDEOGRAPH - 0x91F7: 0x6FC1, //CJK UNIFIED IDEOGRAPH - 0x91F8: 0x8AFE, //CJK UNIFIED IDEOGRAPH - 0x91F9: 0x8338, //CJK UNIFIED IDEOGRAPH - 0x91FA: 0x51E7, //CJK UNIFIED IDEOGRAPH - 0x91FB: 0x86F8, //CJK UNIFIED IDEOGRAPH - 0x91FC: 0x53EA, //CJK UNIFIED IDEOGRAPH - 0x9240: 0x53E9, //CJK UNIFIED IDEOGRAPH - 0x9241: 0x4F46, //CJK UNIFIED IDEOGRAPH - 0x9242: 0x9054, //CJK UNIFIED IDEOGRAPH - 0x9243: 0x8FB0, //CJK UNIFIED IDEOGRAPH - 0x9244: 0x596A, //CJK UNIFIED IDEOGRAPH - 0x9245: 0x8131, //CJK UNIFIED IDEOGRAPH - 0x9246: 0x5DFD, //CJK UNIFIED IDEOGRAPH - 0x9247: 0x7AEA, //CJK UNIFIED IDEOGRAPH - 0x9248: 0x8FBF, //CJK UNIFIED IDEOGRAPH - 0x9249: 0x68DA, //CJK UNIFIED IDEOGRAPH - 0x924A: 0x8C37, //CJK UNIFIED IDEOGRAPH - 0x924B: 0x72F8, //CJK UNIFIED IDEOGRAPH - 0x924C: 0x9C48, //CJK UNIFIED IDEOGRAPH - 0x924D: 0x6A3D, //CJK UNIFIED IDEOGRAPH - 0x924E: 0x8AB0, //CJK UNIFIED IDEOGRAPH - 0x924F: 0x4E39, //CJK UNIFIED IDEOGRAPH - 0x9250: 0x5358, //CJK UNIFIED IDEOGRAPH - 0x9251: 0x5606, //CJK UNIFIED IDEOGRAPH - 0x9252: 0x5766, //CJK UNIFIED IDEOGRAPH - 0x9253: 0x62C5, //CJK UNIFIED IDEOGRAPH - 0x9254: 0x63A2, //CJK UNIFIED IDEOGRAPH - 0x9255: 0x65E6, //CJK UNIFIED IDEOGRAPH - 0x9256: 0x6B4E, //CJK UNIFIED IDEOGRAPH - 0x9257: 0x6DE1, //CJK UNIFIED IDEOGRAPH - 0x9258: 0x6E5B, //CJK UNIFIED IDEOGRAPH - 0x9259: 0x70AD, //CJK UNIFIED IDEOGRAPH - 0x925A: 0x77ED, //CJK UNIFIED IDEOGRAPH - 0x925B: 0x7AEF, //CJK UNIFIED IDEOGRAPH - 0x925C: 0x7BAA, //CJK UNIFIED IDEOGRAPH - 0x925D: 0x7DBB, //CJK UNIFIED IDEOGRAPH - 0x925E: 0x803D, //CJK UNIFIED IDEOGRAPH - 0x925F: 0x80C6, //CJK UNIFIED IDEOGRAPH - 0x9260: 0x86CB, //CJK UNIFIED IDEOGRAPH - 0x9261: 0x8A95, //CJK UNIFIED IDEOGRAPH - 0x9262: 0x935B, //CJK UNIFIED IDEOGRAPH - 0x9263: 0x56E3, //CJK UNIFIED IDEOGRAPH - 0x9264: 0x58C7, //CJK UNIFIED IDEOGRAPH - 0x9265: 0x5F3E, //CJK UNIFIED IDEOGRAPH - 0x9266: 0x65AD, //CJK UNIFIED IDEOGRAPH - 0x9267: 0x6696, //CJK UNIFIED IDEOGRAPH - 0x9268: 0x6A80, //CJK UNIFIED IDEOGRAPH - 0x9269: 0x6BB5, //CJK UNIFIED IDEOGRAPH - 0x926A: 0x7537, //CJK UNIFIED IDEOGRAPH - 0x926B: 0x8AC7, //CJK UNIFIED IDEOGRAPH - 0x926C: 0x5024, //CJK UNIFIED IDEOGRAPH - 0x926D: 0x77E5, //CJK UNIFIED IDEOGRAPH - 0x926E: 0x5730, //CJK UNIFIED IDEOGRAPH - 0x926F: 0x5F1B, //CJK UNIFIED IDEOGRAPH - 0x9270: 0x6065, //CJK UNIFIED IDEOGRAPH - 0x9271: 0x667A, //CJK UNIFIED IDEOGRAPH - 0x9272: 0x6C60, //CJK UNIFIED IDEOGRAPH - 0x9273: 0x75F4, //CJK UNIFIED IDEOGRAPH - 0x9274: 0x7A1A, //CJK UNIFIED IDEOGRAPH - 0x9275: 0x7F6E, //CJK UNIFIED IDEOGRAPH - 0x9276: 0x81F4, //CJK UNIFIED IDEOGRAPH - 0x9277: 0x8718, //CJK UNIFIED IDEOGRAPH - 0x9278: 0x9045, //CJK UNIFIED IDEOGRAPH - 0x9279: 0x99B3, //CJK UNIFIED IDEOGRAPH - 0x927A: 0x7BC9, //CJK UNIFIED IDEOGRAPH - 0x927B: 0x755C, //CJK UNIFIED IDEOGRAPH - 0x927C: 0x7AF9, //CJK UNIFIED IDEOGRAPH - 0x927D: 0x7B51, //CJK UNIFIED IDEOGRAPH - 0x927E: 0x84C4, //CJK UNIFIED IDEOGRAPH - 0x9280: 0x9010, //CJK UNIFIED IDEOGRAPH - 0x9281: 0x79E9, //CJK UNIFIED IDEOGRAPH - 0x9282: 0x7A92, //CJK UNIFIED IDEOGRAPH - 0x9283: 0x8336, //CJK UNIFIED IDEOGRAPH - 0x9284: 0x5AE1, //CJK UNIFIED IDEOGRAPH - 0x9285: 0x7740, //CJK UNIFIED IDEOGRAPH - 0x9286: 0x4E2D, //CJK UNIFIED IDEOGRAPH - 0x9287: 0x4EF2, //CJK UNIFIED IDEOGRAPH - 0x9288: 0x5B99, //CJK UNIFIED IDEOGRAPH - 0x9289: 0x5FE0, //CJK UNIFIED IDEOGRAPH - 0x928A: 0x62BD, //CJK UNIFIED IDEOGRAPH - 0x928B: 0x663C, //CJK UNIFIED IDEOGRAPH - 0x928C: 0x67F1, //CJK UNIFIED IDEOGRAPH - 0x928D: 0x6CE8, //CJK UNIFIED IDEOGRAPH - 0x928E: 0x866B, //CJK UNIFIED IDEOGRAPH - 0x928F: 0x8877, //CJK UNIFIED IDEOGRAPH - 0x9290: 0x8A3B, //CJK UNIFIED IDEOGRAPH - 0x9291: 0x914E, //CJK UNIFIED IDEOGRAPH - 0x9292: 0x92F3, //CJK UNIFIED IDEOGRAPH - 0x9293: 0x99D0, //CJK UNIFIED IDEOGRAPH - 0x9294: 0x6A17, //CJK UNIFIED IDEOGRAPH - 0x9295: 0x7026, //CJK UNIFIED IDEOGRAPH - 0x9296: 0x732A, //CJK UNIFIED IDEOGRAPH - 0x9297: 0x82E7, //CJK UNIFIED IDEOGRAPH - 0x9298: 0x8457, //CJK UNIFIED IDEOGRAPH - 0x9299: 0x8CAF, //CJK UNIFIED IDEOGRAPH - 0x929A: 0x4E01, //CJK UNIFIED IDEOGRAPH - 0x929B: 0x5146, //CJK UNIFIED IDEOGRAPH - 0x929C: 0x51CB, //CJK UNIFIED IDEOGRAPH - 0x929D: 0x558B, //CJK UNIFIED IDEOGRAPH - 0x929E: 0x5BF5, //CJK UNIFIED IDEOGRAPH - 0x929F: 0x5E16, //CJK UNIFIED IDEOGRAPH - 0x92A0: 0x5E33, //CJK UNIFIED IDEOGRAPH - 0x92A1: 0x5E81, //CJK UNIFIED IDEOGRAPH - 0x92A2: 0x5F14, //CJK UNIFIED IDEOGRAPH - 0x92A3: 0x5F35, //CJK UNIFIED IDEOGRAPH - 0x92A4: 0x5F6B, //CJK UNIFIED IDEOGRAPH - 0x92A5: 0x5FB4, //CJK UNIFIED IDEOGRAPH - 0x92A6: 0x61F2, //CJK UNIFIED IDEOGRAPH - 0x92A7: 0x6311, //CJK UNIFIED IDEOGRAPH - 0x92A8: 0x66A2, //CJK UNIFIED IDEOGRAPH - 0x92A9: 0x671D, //CJK UNIFIED IDEOGRAPH - 0x92AA: 0x6F6E, //CJK UNIFIED IDEOGRAPH - 0x92AB: 0x7252, //CJK UNIFIED IDEOGRAPH - 0x92AC: 0x753A, //CJK UNIFIED IDEOGRAPH - 0x92AD: 0x773A, //CJK UNIFIED IDEOGRAPH - 0x92AE: 0x8074, //CJK UNIFIED IDEOGRAPH - 0x92AF: 0x8139, //CJK UNIFIED IDEOGRAPH - 0x92B0: 0x8178, //CJK UNIFIED IDEOGRAPH - 0x92B1: 0x8776, //CJK UNIFIED IDEOGRAPH - 0x92B2: 0x8ABF, //CJK UNIFIED IDEOGRAPH - 0x92B3: 0x8ADC, //CJK UNIFIED IDEOGRAPH - 0x92B4: 0x8D85, //CJK UNIFIED IDEOGRAPH - 0x92B5: 0x8DF3, //CJK UNIFIED IDEOGRAPH - 0x92B6: 0x929A, //CJK UNIFIED IDEOGRAPH - 0x92B7: 0x9577, //CJK UNIFIED IDEOGRAPH - 0x92B8: 0x9802, //CJK UNIFIED IDEOGRAPH - 0x92B9: 0x9CE5, //CJK UNIFIED IDEOGRAPH - 0x92BA: 0x52C5, //CJK UNIFIED IDEOGRAPH - 0x92BB: 0x6357, //CJK UNIFIED IDEOGRAPH - 0x92BC: 0x76F4, //CJK UNIFIED IDEOGRAPH - 0x92BD: 0x6715, //CJK UNIFIED IDEOGRAPH - 0x92BE: 0x6C88, //CJK UNIFIED IDEOGRAPH - 0x92BF: 0x73CD, //CJK UNIFIED IDEOGRAPH - 0x92C0: 0x8CC3, //CJK UNIFIED IDEOGRAPH - 0x92C1: 0x93AE, //CJK UNIFIED IDEOGRAPH - 0x92C2: 0x9673, //CJK UNIFIED IDEOGRAPH - 0x92C3: 0x6D25, //CJK UNIFIED IDEOGRAPH - 0x92C4: 0x589C, //CJK UNIFIED IDEOGRAPH - 0x92C5: 0x690E, //CJK UNIFIED IDEOGRAPH - 0x92C6: 0x69CC, //CJK UNIFIED IDEOGRAPH - 0x92C7: 0x8FFD, //CJK UNIFIED IDEOGRAPH - 0x92C8: 0x939A, //CJK UNIFIED IDEOGRAPH - 0x92C9: 0x75DB, //CJK UNIFIED IDEOGRAPH - 0x92CA: 0x901A, //CJK UNIFIED IDEOGRAPH - 0x92CB: 0x585A, //CJK UNIFIED IDEOGRAPH - 0x92CC: 0x6802, //CJK UNIFIED IDEOGRAPH - 0x92CD: 0x63B4, //CJK UNIFIED IDEOGRAPH - 0x92CE: 0x69FB, //CJK UNIFIED IDEOGRAPH - 0x92CF: 0x4F43, //CJK UNIFIED IDEOGRAPH - 0x92D0: 0x6F2C, //CJK UNIFIED IDEOGRAPH - 0x92D1: 0x67D8, //CJK UNIFIED IDEOGRAPH - 0x92D2: 0x8FBB, //CJK UNIFIED IDEOGRAPH - 0x92D3: 0x8526, //CJK UNIFIED IDEOGRAPH - 0x92D4: 0x7DB4, //CJK UNIFIED IDEOGRAPH - 0x92D5: 0x9354, //CJK UNIFIED IDEOGRAPH - 0x92D6: 0x693F, //CJK UNIFIED IDEOGRAPH - 0x92D7: 0x6F70, //CJK UNIFIED IDEOGRAPH - 0x92D8: 0x576A, //CJK UNIFIED IDEOGRAPH - 0x92D9: 0x58F7, //CJK UNIFIED IDEOGRAPH - 0x92DA: 0x5B2C, //CJK UNIFIED IDEOGRAPH - 0x92DB: 0x7D2C, //CJK UNIFIED IDEOGRAPH - 0x92DC: 0x722A, //CJK UNIFIED IDEOGRAPH - 0x92DD: 0x540A, //CJK UNIFIED IDEOGRAPH - 0x92DE: 0x91E3, //CJK UNIFIED IDEOGRAPH - 0x92DF: 0x9DB4, //CJK UNIFIED IDEOGRAPH - 0x92E0: 0x4EAD, //CJK UNIFIED IDEOGRAPH - 0x92E1: 0x4F4E, //CJK UNIFIED IDEOGRAPH - 0x92E2: 0x505C, //CJK UNIFIED IDEOGRAPH - 0x92E3: 0x5075, //CJK UNIFIED IDEOGRAPH - 0x92E4: 0x5243, //CJK UNIFIED IDEOGRAPH - 0x92E5: 0x8C9E, //CJK UNIFIED IDEOGRAPH - 0x92E6: 0x5448, //CJK UNIFIED IDEOGRAPH - 0x92E7: 0x5824, //CJK UNIFIED IDEOGRAPH - 0x92E8: 0x5B9A, //CJK UNIFIED IDEOGRAPH - 0x92E9: 0x5E1D, //CJK UNIFIED IDEOGRAPH - 0x92EA: 0x5E95, //CJK UNIFIED IDEOGRAPH - 0x92EB: 0x5EAD, //CJK UNIFIED IDEOGRAPH - 0x92EC: 0x5EF7, //CJK UNIFIED IDEOGRAPH - 0x92ED: 0x5F1F, //CJK UNIFIED IDEOGRAPH - 0x92EE: 0x608C, //CJK UNIFIED IDEOGRAPH - 0x92EF: 0x62B5, //CJK UNIFIED IDEOGRAPH - 0x92F0: 0x633A, //CJK UNIFIED IDEOGRAPH - 0x92F1: 0x63D0, //CJK UNIFIED IDEOGRAPH - 0x92F2: 0x68AF, //CJK UNIFIED IDEOGRAPH - 0x92F3: 0x6C40, //CJK UNIFIED IDEOGRAPH - 0x92F4: 0x7887, //CJK UNIFIED IDEOGRAPH - 0x92F5: 0x798E, //CJK UNIFIED IDEOGRAPH - 0x92F6: 0x7A0B, //CJK UNIFIED IDEOGRAPH - 0x92F7: 0x7DE0, //CJK UNIFIED IDEOGRAPH - 0x92F8: 0x8247, //CJK UNIFIED IDEOGRAPH - 0x92F9: 0x8A02, //CJK UNIFIED IDEOGRAPH - 0x92FA: 0x8AE6, //CJK UNIFIED IDEOGRAPH - 0x92FB: 0x8E44, //CJK UNIFIED IDEOGRAPH - 0x92FC: 0x9013, //CJK UNIFIED IDEOGRAPH - 0x9340: 0x90B8, //CJK UNIFIED IDEOGRAPH - 0x9341: 0x912D, //CJK UNIFIED IDEOGRAPH - 0x9342: 0x91D8, //CJK UNIFIED IDEOGRAPH - 0x9343: 0x9F0E, //CJK UNIFIED IDEOGRAPH - 0x9344: 0x6CE5, //CJK UNIFIED IDEOGRAPH - 0x9345: 0x6458, //CJK UNIFIED IDEOGRAPH - 0x9346: 0x64E2, //CJK UNIFIED IDEOGRAPH - 0x9347: 0x6575, //CJK UNIFIED IDEOGRAPH - 0x9348: 0x6EF4, //CJK UNIFIED IDEOGRAPH - 0x9349: 0x7684, //CJK UNIFIED IDEOGRAPH - 0x934A: 0x7B1B, //CJK UNIFIED IDEOGRAPH - 0x934B: 0x9069, //CJK UNIFIED IDEOGRAPH - 0x934C: 0x93D1, //CJK UNIFIED IDEOGRAPH - 0x934D: 0x6EBA, //CJK UNIFIED IDEOGRAPH - 0x934E: 0x54F2, //CJK UNIFIED IDEOGRAPH - 0x934F: 0x5FB9, //CJK UNIFIED IDEOGRAPH - 0x9350: 0x64A4, //CJK UNIFIED IDEOGRAPH - 0x9351: 0x8F4D, //CJK UNIFIED IDEOGRAPH - 0x9352: 0x8FED, //CJK UNIFIED IDEOGRAPH - 0x9353: 0x9244, //CJK UNIFIED IDEOGRAPH - 0x9354: 0x5178, //CJK UNIFIED IDEOGRAPH - 0x9355: 0x586B, //CJK UNIFIED IDEOGRAPH - 0x9356: 0x5929, //CJK UNIFIED IDEOGRAPH - 0x9357: 0x5C55, //CJK UNIFIED IDEOGRAPH - 0x9358: 0x5E97, //CJK UNIFIED IDEOGRAPH - 0x9359: 0x6DFB, //CJK UNIFIED IDEOGRAPH - 0x935A: 0x7E8F, //CJK UNIFIED IDEOGRAPH - 0x935B: 0x751C, //CJK UNIFIED IDEOGRAPH - 0x935C: 0x8CBC, //CJK UNIFIED IDEOGRAPH - 0x935D: 0x8EE2, //CJK UNIFIED IDEOGRAPH - 0x935E: 0x985B, //CJK UNIFIED IDEOGRAPH - 0x935F: 0x70B9, //CJK UNIFIED IDEOGRAPH - 0x9360: 0x4F1D, //CJK UNIFIED IDEOGRAPH - 0x9361: 0x6BBF, //CJK UNIFIED IDEOGRAPH - 0x9362: 0x6FB1, //CJK UNIFIED IDEOGRAPH - 0x9363: 0x7530, //CJK UNIFIED IDEOGRAPH - 0x9364: 0x96FB, //CJK UNIFIED IDEOGRAPH - 0x9365: 0x514E, //CJK UNIFIED IDEOGRAPH - 0x9366: 0x5410, //CJK UNIFIED IDEOGRAPH - 0x9367: 0x5835, //CJK UNIFIED IDEOGRAPH - 0x9368: 0x5857, //CJK UNIFIED IDEOGRAPH - 0x9369: 0x59AC, //CJK UNIFIED IDEOGRAPH - 0x936A: 0x5C60, //CJK UNIFIED IDEOGRAPH - 0x936B: 0x5F92, //CJK UNIFIED IDEOGRAPH - 0x936C: 0x6597, //CJK UNIFIED IDEOGRAPH - 0x936D: 0x675C, //CJK UNIFIED IDEOGRAPH - 0x936E: 0x6E21, //CJK UNIFIED IDEOGRAPH - 0x936F: 0x767B, //CJK UNIFIED IDEOGRAPH - 0x9370: 0x83DF, //CJK UNIFIED IDEOGRAPH - 0x9371: 0x8CED, //CJK UNIFIED IDEOGRAPH - 0x9372: 0x9014, //CJK UNIFIED IDEOGRAPH - 0x9373: 0x90FD, //CJK UNIFIED IDEOGRAPH - 0x9374: 0x934D, //CJK UNIFIED IDEOGRAPH - 0x9375: 0x7825, //CJK UNIFIED IDEOGRAPH - 0x9376: 0x783A, //CJK UNIFIED IDEOGRAPH - 0x9377: 0x52AA, //CJK UNIFIED IDEOGRAPH - 0x9378: 0x5EA6, //CJK UNIFIED IDEOGRAPH - 0x9379: 0x571F, //CJK UNIFIED IDEOGRAPH - 0x937A: 0x5974, //CJK UNIFIED IDEOGRAPH - 0x937B: 0x6012, //CJK UNIFIED IDEOGRAPH - 0x937C: 0x5012, //CJK UNIFIED IDEOGRAPH - 0x937D: 0x515A, //CJK UNIFIED IDEOGRAPH - 0x937E: 0x51AC, //CJK UNIFIED IDEOGRAPH - 0x9380: 0x51CD, //CJK UNIFIED IDEOGRAPH - 0x9381: 0x5200, //CJK UNIFIED IDEOGRAPH - 0x9382: 0x5510, //CJK UNIFIED IDEOGRAPH - 0x9383: 0x5854, //CJK UNIFIED IDEOGRAPH - 0x9384: 0x5858, //CJK UNIFIED IDEOGRAPH - 0x9385: 0x5957, //CJK UNIFIED IDEOGRAPH - 0x9386: 0x5B95, //CJK UNIFIED IDEOGRAPH - 0x9387: 0x5CF6, //CJK UNIFIED IDEOGRAPH - 0x9388: 0x5D8B, //CJK UNIFIED IDEOGRAPH - 0x9389: 0x60BC, //CJK UNIFIED IDEOGRAPH - 0x938A: 0x6295, //CJK UNIFIED IDEOGRAPH - 0x938B: 0x642D, //CJK UNIFIED IDEOGRAPH - 0x938C: 0x6771, //CJK UNIFIED IDEOGRAPH - 0x938D: 0x6843, //CJK UNIFIED IDEOGRAPH - 0x938E: 0x68BC, //CJK UNIFIED IDEOGRAPH - 0x938F: 0x68DF, //CJK UNIFIED IDEOGRAPH - 0x9390: 0x76D7, //CJK UNIFIED IDEOGRAPH - 0x9391: 0x6DD8, //CJK UNIFIED IDEOGRAPH - 0x9392: 0x6E6F, //CJK UNIFIED IDEOGRAPH - 0x9393: 0x6D9B, //CJK UNIFIED IDEOGRAPH - 0x9394: 0x706F, //CJK UNIFIED IDEOGRAPH - 0x9395: 0x71C8, //CJK UNIFIED IDEOGRAPH - 0x9396: 0x5F53, //CJK UNIFIED IDEOGRAPH - 0x9397: 0x75D8, //CJK UNIFIED IDEOGRAPH - 0x9398: 0x7977, //CJK UNIFIED IDEOGRAPH - 0x9399: 0x7B49, //CJK UNIFIED IDEOGRAPH - 0x939A: 0x7B54, //CJK UNIFIED IDEOGRAPH - 0x939B: 0x7B52, //CJK UNIFIED IDEOGRAPH - 0x939C: 0x7CD6, //CJK UNIFIED IDEOGRAPH - 0x939D: 0x7D71, //CJK UNIFIED IDEOGRAPH - 0x939E: 0x5230, //CJK UNIFIED IDEOGRAPH - 0x939F: 0x8463, //CJK UNIFIED IDEOGRAPH - 0x93A0: 0x8569, //CJK UNIFIED IDEOGRAPH - 0x93A1: 0x85E4, //CJK UNIFIED IDEOGRAPH - 0x93A2: 0x8A0E, //CJK UNIFIED IDEOGRAPH - 0x93A3: 0x8B04, //CJK UNIFIED IDEOGRAPH - 0x93A4: 0x8C46, //CJK UNIFIED IDEOGRAPH - 0x93A5: 0x8E0F, //CJK UNIFIED IDEOGRAPH - 0x93A6: 0x9003, //CJK UNIFIED IDEOGRAPH - 0x93A7: 0x900F, //CJK UNIFIED IDEOGRAPH - 0x93A8: 0x9419, //CJK UNIFIED IDEOGRAPH - 0x93A9: 0x9676, //CJK UNIFIED IDEOGRAPH - 0x93AA: 0x982D, //CJK UNIFIED IDEOGRAPH - 0x93AB: 0x9A30, //CJK UNIFIED IDEOGRAPH - 0x93AC: 0x95D8, //CJK UNIFIED IDEOGRAPH - 0x93AD: 0x50CD, //CJK UNIFIED IDEOGRAPH - 0x93AE: 0x52D5, //CJK UNIFIED IDEOGRAPH - 0x93AF: 0x540C, //CJK UNIFIED IDEOGRAPH - 0x93B0: 0x5802, //CJK UNIFIED IDEOGRAPH - 0x93B1: 0x5C0E, //CJK UNIFIED IDEOGRAPH - 0x93B2: 0x61A7, //CJK UNIFIED IDEOGRAPH - 0x93B3: 0x649E, //CJK UNIFIED IDEOGRAPH - 0x93B4: 0x6D1E, //CJK UNIFIED IDEOGRAPH - 0x93B5: 0x77B3, //CJK UNIFIED IDEOGRAPH - 0x93B6: 0x7AE5, //CJK UNIFIED IDEOGRAPH - 0x93B7: 0x80F4, //CJK UNIFIED IDEOGRAPH - 0x93B8: 0x8404, //CJK UNIFIED IDEOGRAPH - 0x93B9: 0x9053, //CJK UNIFIED IDEOGRAPH - 0x93BA: 0x9285, //CJK UNIFIED IDEOGRAPH - 0x93BB: 0x5CE0, //CJK UNIFIED IDEOGRAPH - 0x93BC: 0x9D07, //CJK UNIFIED IDEOGRAPH - 0x93BD: 0x533F, //CJK UNIFIED IDEOGRAPH - 0x93BE: 0x5F97, //CJK UNIFIED IDEOGRAPH - 0x93BF: 0x5FB3, //CJK UNIFIED IDEOGRAPH - 0x93C0: 0x6D9C, //CJK UNIFIED IDEOGRAPH - 0x93C1: 0x7279, //CJK UNIFIED IDEOGRAPH - 0x93C2: 0x7763, //CJK UNIFIED IDEOGRAPH - 0x93C3: 0x79BF, //CJK UNIFIED IDEOGRAPH - 0x93C4: 0x7BE4, //CJK UNIFIED IDEOGRAPH - 0x93C5: 0x6BD2, //CJK UNIFIED IDEOGRAPH - 0x93C6: 0x72EC, //CJK UNIFIED IDEOGRAPH - 0x93C7: 0x8AAD, //CJK UNIFIED IDEOGRAPH - 0x93C8: 0x6803, //CJK UNIFIED IDEOGRAPH - 0x93C9: 0x6A61, //CJK UNIFIED IDEOGRAPH - 0x93CA: 0x51F8, //CJK UNIFIED IDEOGRAPH - 0x93CB: 0x7A81, //CJK UNIFIED IDEOGRAPH - 0x93CC: 0x6934, //CJK UNIFIED IDEOGRAPH - 0x93CD: 0x5C4A, //CJK UNIFIED IDEOGRAPH - 0x93CE: 0x9CF6, //CJK UNIFIED IDEOGRAPH - 0x93CF: 0x82EB, //CJK UNIFIED IDEOGRAPH - 0x93D0: 0x5BC5, //CJK UNIFIED IDEOGRAPH - 0x93D1: 0x9149, //CJK UNIFIED IDEOGRAPH - 0x93D2: 0x701E, //CJK UNIFIED IDEOGRAPH - 0x93D3: 0x5678, //CJK UNIFIED IDEOGRAPH - 0x93D4: 0x5C6F, //CJK UNIFIED IDEOGRAPH - 0x93D5: 0x60C7, //CJK UNIFIED IDEOGRAPH - 0x93D6: 0x6566, //CJK UNIFIED IDEOGRAPH - 0x93D7: 0x6C8C, //CJK UNIFIED IDEOGRAPH - 0x93D8: 0x8C5A, //CJK UNIFIED IDEOGRAPH - 0x93D9: 0x9041, //CJK UNIFIED IDEOGRAPH - 0x93DA: 0x9813, //CJK UNIFIED IDEOGRAPH - 0x93DB: 0x5451, //CJK UNIFIED IDEOGRAPH - 0x93DC: 0x66C7, //CJK UNIFIED IDEOGRAPH - 0x93DD: 0x920D, //CJK UNIFIED IDEOGRAPH - 0x93DE: 0x5948, //CJK UNIFIED IDEOGRAPH - 0x93DF: 0x90A3, //CJK UNIFIED IDEOGRAPH - 0x93E0: 0x5185, //CJK UNIFIED IDEOGRAPH - 0x93E1: 0x4E4D, //CJK UNIFIED IDEOGRAPH - 0x93E2: 0x51EA, //CJK UNIFIED IDEOGRAPH - 0x93E3: 0x8599, //CJK UNIFIED IDEOGRAPH - 0x93E4: 0x8B0E, //CJK UNIFIED IDEOGRAPH - 0x93E5: 0x7058, //CJK UNIFIED IDEOGRAPH - 0x93E6: 0x637A, //CJK UNIFIED IDEOGRAPH - 0x93E7: 0x934B, //CJK UNIFIED IDEOGRAPH - 0x93E8: 0x6962, //CJK UNIFIED IDEOGRAPH - 0x93E9: 0x99B4, //CJK UNIFIED IDEOGRAPH - 0x93EA: 0x7E04, //CJK UNIFIED IDEOGRAPH - 0x93EB: 0x7577, //CJK UNIFIED IDEOGRAPH - 0x93EC: 0x5357, //CJK UNIFIED IDEOGRAPH - 0x93ED: 0x6960, //CJK UNIFIED IDEOGRAPH - 0x93EE: 0x8EDF, //CJK UNIFIED IDEOGRAPH - 0x93EF: 0x96E3, //CJK UNIFIED IDEOGRAPH - 0x93F0: 0x6C5D, //CJK UNIFIED IDEOGRAPH - 0x93F1: 0x4E8C, //CJK UNIFIED IDEOGRAPH - 0x93F2: 0x5C3C, //CJK UNIFIED IDEOGRAPH - 0x93F3: 0x5F10, //CJK UNIFIED IDEOGRAPH - 0x93F4: 0x8FE9, //CJK UNIFIED IDEOGRAPH - 0x93F5: 0x5302, //CJK UNIFIED IDEOGRAPH - 0x93F6: 0x8CD1, //CJK UNIFIED IDEOGRAPH - 0x93F7: 0x8089, //CJK UNIFIED IDEOGRAPH - 0x93F8: 0x8679, //CJK UNIFIED IDEOGRAPH - 0x93F9: 0x5EFF, //CJK UNIFIED IDEOGRAPH - 0x93FA: 0x65E5, //CJK UNIFIED IDEOGRAPH - 0x93FB: 0x4E73, //CJK UNIFIED IDEOGRAPH - 0x93FC: 0x5165, //CJK UNIFIED IDEOGRAPH - 0x9440: 0x5982, //CJK UNIFIED IDEOGRAPH - 0x9441: 0x5C3F, //CJK UNIFIED IDEOGRAPH - 0x9442: 0x97EE, //CJK UNIFIED IDEOGRAPH - 0x9443: 0x4EFB, //CJK UNIFIED IDEOGRAPH - 0x9444: 0x598A, //CJK UNIFIED IDEOGRAPH - 0x9445: 0x5FCD, //CJK UNIFIED IDEOGRAPH - 0x9446: 0x8A8D, //CJK UNIFIED IDEOGRAPH - 0x9447: 0x6FE1, //CJK UNIFIED IDEOGRAPH - 0x9448: 0x79B0, //CJK UNIFIED IDEOGRAPH - 0x9449: 0x7962, //CJK UNIFIED IDEOGRAPH - 0x944A: 0x5BE7, //CJK UNIFIED IDEOGRAPH - 0x944B: 0x8471, //CJK UNIFIED IDEOGRAPH - 0x944C: 0x732B, //CJK UNIFIED IDEOGRAPH - 0x944D: 0x71B1, //CJK UNIFIED IDEOGRAPH - 0x944E: 0x5E74, //CJK UNIFIED IDEOGRAPH - 0x944F: 0x5FF5, //CJK UNIFIED IDEOGRAPH - 0x9450: 0x637B, //CJK UNIFIED IDEOGRAPH - 0x9451: 0x649A, //CJK UNIFIED IDEOGRAPH - 0x9452: 0x71C3, //CJK UNIFIED IDEOGRAPH - 0x9453: 0x7C98, //CJK UNIFIED IDEOGRAPH - 0x9454: 0x4E43, //CJK UNIFIED IDEOGRAPH - 0x9455: 0x5EFC, //CJK UNIFIED IDEOGRAPH - 0x9456: 0x4E4B, //CJK UNIFIED IDEOGRAPH - 0x9457: 0x57DC, //CJK UNIFIED IDEOGRAPH - 0x9458: 0x56A2, //CJK UNIFIED IDEOGRAPH - 0x9459: 0x60A9, //CJK UNIFIED IDEOGRAPH - 0x945A: 0x6FC3, //CJK UNIFIED IDEOGRAPH - 0x945B: 0x7D0D, //CJK UNIFIED IDEOGRAPH - 0x945C: 0x80FD, //CJK UNIFIED IDEOGRAPH - 0x945D: 0x8133, //CJK UNIFIED IDEOGRAPH - 0x945E: 0x81BF, //CJK UNIFIED IDEOGRAPH - 0x945F: 0x8FB2, //CJK UNIFIED IDEOGRAPH - 0x9460: 0x8997, //CJK UNIFIED IDEOGRAPH - 0x9461: 0x86A4, //CJK UNIFIED IDEOGRAPH - 0x9462: 0x5DF4, //CJK UNIFIED IDEOGRAPH - 0x9463: 0x628A, //CJK UNIFIED IDEOGRAPH - 0x9464: 0x64AD, //CJK UNIFIED IDEOGRAPH - 0x9465: 0x8987, //CJK UNIFIED IDEOGRAPH - 0x9466: 0x6777, //CJK UNIFIED IDEOGRAPH - 0x9467: 0x6CE2, //CJK UNIFIED IDEOGRAPH - 0x9468: 0x6D3E, //CJK UNIFIED IDEOGRAPH - 0x9469: 0x7436, //CJK UNIFIED IDEOGRAPH - 0x946A: 0x7834, //CJK UNIFIED IDEOGRAPH - 0x946B: 0x5A46, //CJK UNIFIED IDEOGRAPH - 0x946C: 0x7F75, //CJK UNIFIED IDEOGRAPH - 0x946D: 0x82AD, //CJK UNIFIED IDEOGRAPH - 0x946E: 0x99AC, //CJK UNIFIED IDEOGRAPH - 0x946F: 0x4FF3, //CJK UNIFIED IDEOGRAPH - 0x9470: 0x5EC3, //CJK UNIFIED IDEOGRAPH - 0x9471: 0x62DD, //CJK UNIFIED IDEOGRAPH - 0x9472: 0x6392, //CJK UNIFIED IDEOGRAPH - 0x9473: 0x6557, //CJK UNIFIED IDEOGRAPH - 0x9474: 0x676F, //CJK UNIFIED IDEOGRAPH - 0x9475: 0x76C3, //CJK UNIFIED IDEOGRAPH - 0x9476: 0x724C, //CJK UNIFIED IDEOGRAPH - 0x9477: 0x80CC, //CJK UNIFIED IDEOGRAPH - 0x9478: 0x80BA, //CJK UNIFIED IDEOGRAPH - 0x9479: 0x8F29, //CJK UNIFIED IDEOGRAPH - 0x947A: 0x914D, //CJK UNIFIED IDEOGRAPH - 0x947B: 0x500D, //CJK UNIFIED IDEOGRAPH - 0x947C: 0x57F9, //CJK UNIFIED IDEOGRAPH - 0x947D: 0x5A92, //CJK UNIFIED IDEOGRAPH - 0x947E: 0x6885, //CJK UNIFIED IDEOGRAPH - 0x9480: 0x6973, //CJK UNIFIED IDEOGRAPH - 0x9481: 0x7164, //CJK UNIFIED IDEOGRAPH - 0x9482: 0x72FD, //CJK UNIFIED IDEOGRAPH - 0x9483: 0x8CB7, //CJK UNIFIED IDEOGRAPH - 0x9484: 0x58F2, //CJK UNIFIED IDEOGRAPH - 0x9485: 0x8CE0, //CJK UNIFIED IDEOGRAPH - 0x9486: 0x966A, //CJK UNIFIED IDEOGRAPH - 0x9487: 0x9019, //CJK UNIFIED IDEOGRAPH - 0x9488: 0x877F, //CJK UNIFIED IDEOGRAPH - 0x9489: 0x79E4, //CJK UNIFIED IDEOGRAPH - 0x948A: 0x77E7, //CJK UNIFIED IDEOGRAPH - 0x948B: 0x8429, //CJK UNIFIED IDEOGRAPH - 0x948C: 0x4F2F, //CJK UNIFIED IDEOGRAPH - 0x948D: 0x5265, //CJK UNIFIED IDEOGRAPH - 0x948E: 0x535A, //CJK UNIFIED IDEOGRAPH - 0x948F: 0x62CD, //CJK UNIFIED IDEOGRAPH - 0x9490: 0x67CF, //CJK UNIFIED IDEOGRAPH - 0x9491: 0x6CCA, //CJK UNIFIED IDEOGRAPH - 0x9492: 0x767D, //CJK UNIFIED IDEOGRAPH - 0x9493: 0x7B94, //CJK UNIFIED IDEOGRAPH - 0x9494: 0x7C95, //CJK UNIFIED IDEOGRAPH - 0x9495: 0x8236, //CJK UNIFIED IDEOGRAPH - 0x9496: 0x8584, //CJK UNIFIED IDEOGRAPH - 0x9497: 0x8FEB, //CJK UNIFIED IDEOGRAPH - 0x9498: 0x66DD, //CJK UNIFIED IDEOGRAPH - 0x9499: 0x6F20, //CJK UNIFIED IDEOGRAPH - 0x949A: 0x7206, //CJK UNIFIED IDEOGRAPH - 0x949B: 0x7E1B, //CJK UNIFIED IDEOGRAPH - 0x949C: 0x83AB, //CJK UNIFIED IDEOGRAPH - 0x949D: 0x99C1, //CJK UNIFIED IDEOGRAPH - 0x949E: 0x9EA6, //CJK UNIFIED IDEOGRAPH - 0x949F: 0x51FD, //CJK UNIFIED IDEOGRAPH - 0x94A0: 0x7BB1, //CJK UNIFIED IDEOGRAPH - 0x94A1: 0x7872, //CJK UNIFIED IDEOGRAPH - 0x94A2: 0x7BB8, //CJK UNIFIED IDEOGRAPH - 0x94A3: 0x8087, //CJK UNIFIED IDEOGRAPH - 0x94A4: 0x7B48, //CJK UNIFIED IDEOGRAPH - 0x94A5: 0x6AE8, //CJK UNIFIED IDEOGRAPH - 0x94A6: 0x5E61, //CJK UNIFIED IDEOGRAPH - 0x94A7: 0x808C, //CJK UNIFIED IDEOGRAPH - 0x94A8: 0x7551, //CJK UNIFIED IDEOGRAPH - 0x94A9: 0x7560, //CJK UNIFIED IDEOGRAPH - 0x94AA: 0x516B, //CJK UNIFIED IDEOGRAPH - 0x94AB: 0x9262, //CJK UNIFIED IDEOGRAPH - 0x94AC: 0x6E8C, //CJK UNIFIED IDEOGRAPH - 0x94AD: 0x767A, //CJK UNIFIED IDEOGRAPH - 0x94AE: 0x9197, //CJK UNIFIED IDEOGRAPH - 0x94AF: 0x9AEA, //CJK UNIFIED IDEOGRAPH - 0x94B0: 0x4F10, //CJK UNIFIED IDEOGRAPH - 0x94B1: 0x7F70, //CJK UNIFIED IDEOGRAPH - 0x94B2: 0x629C, //CJK UNIFIED IDEOGRAPH - 0x94B3: 0x7B4F, //CJK UNIFIED IDEOGRAPH - 0x94B4: 0x95A5, //CJK UNIFIED IDEOGRAPH - 0x94B5: 0x9CE9, //CJK UNIFIED IDEOGRAPH - 0x94B6: 0x567A, //CJK UNIFIED IDEOGRAPH - 0x94B7: 0x5859, //CJK UNIFIED IDEOGRAPH - 0x94B8: 0x86E4, //CJK UNIFIED IDEOGRAPH - 0x94B9: 0x96BC, //CJK UNIFIED IDEOGRAPH - 0x94BA: 0x4F34, //CJK UNIFIED IDEOGRAPH - 0x94BB: 0x5224, //CJK UNIFIED IDEOGRAPH - 0x94BC: 0x534A, //CJK UNIFIED IDEOGRAPH - 0x94BD: 0x53CD, //CJK UNIFIED IDEOGRAPH - 0x94BE: 0x53DB, //CJK UNIFIED IDEOGRAPH - 0x94BF: 0x5E06, //CJK UNIFIED IDEOGRAPH - 0x94C0: 0x642C, //CJK UNIFIED IDEOGRAPH - 0x94C1: 0x6591, //CJK UNIFIED IDEOGRAPH - 0x94C2: 0x677F, //CJK UNIFIED IDEOGRAPH - 0x94C3: 0x6C3E, //CJK UNIFIED IDEOGRAPH - 0x94C4: 0x6C4E, //CJK UNIFIED IDEOGRAPH - 0x94C5: 0x7248, //CJK UNIFIED IDEOGRAPH - 0x94C6: 0x72AF, //CJK UNIFIED IDEOGRAPH - 0x94C7: 0x73ED, //CJK UNIFIED IDEOGRAPH - 0x94C8: 0x7554, //CJK UNIFIED IDEOGRAPH - 0x94C9: 0x7E41, //CJK UNIFIED IDEOGRAPH - 0x94CA: 0x822C, //CJK UNIFIED IDEOGRAPH - 0x94CB: 0x85E9, //CJK UNIFIED IDEOGRAPH - 0x94CC: 0x8CA9, //CJK UNIFIED IDEOGRAPH - 0x94CD: 0x7BC4, //CJK UNIFIED IDEOGRAPH - 0x94CE: 0x91C6, //CJK UNIFIED IDEOGRAPH - 0x94CF: 0x7169, //CJK UNIFIED IDEOGRAPH - 0x94D0: 0x9812, //CJK UNIFIED IDEOGRAPH - 0x94D1: 0x98EF, //CJK UNIFIED IDEOGRAPH - 0x94D2: 0x633D, //CJK UNIFIED IDEOGRAPH - 0x94D3: 0x6669, //CJK UNIFIED IDEOGRAPH - 0x94D4: 0x756A, //CJK UNIFIED IDEOGRAPH - 0x94D5: 0x76E4, //CJK UNIFIED IDEOGRAPH - 0x94D6: 0x78D0, //CJK UNIFIED IDEOGRAPH - 0x94D7: 0x8543, //CJK UNIFIED IDEOGRAPH - 0x94D8: 0x86EE, //CJK UNIFIED IDEOGRAPH - 0x94D9: 0x532A, //CJK UNIFIED IDEOGRAPH - 0x94DA: 0x5351, //CJK UNIFIED IDEOGRAPH - 0x94DB: 0x5426, //CJK UNIFIED IDEOGRAPH - 0x94DC: 0x5983, //CJK UNIFIED IDEOGRAPH - 0x94DD: 0x5E87, //CJK UNIFIED IDEOGRAPH - 0x94DE: 0x5F7C, //CJK UNIFIED IDEOGRAPH - 0x94DF: 0x60B2, //CJK UNIFIED IDEOGRAPH - 0x94E0: 0x6249, //CJK UNIFIED IDEOGRAPH - 0x94E1: 0x6279, //CJK UNIFIED IDEOGRAPH - 0x94E2: 0x62AB, //CJK UNIFIED IDEOGRAPH - 0x94E3: 0x6590, //CJK UNIFIED IDEOGRAPH - 0x94E4: 0x6BD4, //CJK UNIFIED IDEOGRAPH - 0x94E5: 0x6CCC, //CJK UNIFIED IDEOGRAPH - 0x94E6: 0x75B2, //CJK UNIFIED IDEOGRAPH - 0x94E7: 0x76AE, //CJK UNIFIED IDEOGRAPH - 0x94E8: 0x7891, //CJK UNIFIED IDEOGRAPH - 0x94E9: 0x79D8, //CJK UNIFIED IDEOGRAPH - 0x94EA: 0x7DCB, //CJK UNIFIED IDEOGRAPH - 0x94EB: 0x7F77, //CJK UNIFIED IDEOGRAPH - 0x94EC: 0x80A5, //CJK UNIFIED IDEOGRAPH - 0x94ED: 0x88AB, //CJK UNIFIED IDEOGRAPH - 0x94EE: 0x8AB9, //CJK UNIFIED IDEOGRAPH - 0x94EF: 0x8CBB, //CJK UNIFIED IDEOGRAPH - 0x94F0: 0x907F, //CJK UNIFIED IDEOGRAPH - 0x94F1: 0x975E, //CJK UNIFIED IDEOGRAPH - 0x94F2: 0x98DB, //CJK UNIFIED IDEOGRAPH - 0x94F3: 0x6A0B, //CJK UNIFIED IDEOGRAPH - 0x94F4: 0x7C38, //CJK UNIFIED IDEOGRAPH - 0x94F5: 0x5099, //CJK UNIFIED IDEOGRAPH - 0x94F6: 0x5C3E, //CJK UNIFIED IDEOGRAPH - 0x94F7: 0x5FAE, //CJK UNIFIED IDEOGRAPH - 0x94F8: 0x6787, //CJK UNIFIED IDEOGRAPH - 0x94F9: 0x6BD8, //CJK UNIFIED IDEOGRAPH - 0x94FA: 0x7435, //CJK UNIFIED IDEOGRAPH - 0x94FB: 0x7709, //CJK UNIFIED IDEOGRAPH - 0x94FC: 0x7F8E, //CJK UNIFIED IDEOGRAPH - 0x9540: 0x9F3B, //CJK UNIFIED IDEOGRAPH - 0x9541: 0x67CA, //CJK UNIFIED IDEOGRAPH - 0x9542: 0x7A17, //CJK UNIFIED IDEOGRAPH - 0x9543: 0x5339, //CJK UNIFIED IDEOGRAPH - 0x9544: 0x758B, //CJK UNIFIED IDEOGRAPH - 0x9545: 0x9AED, //CJK UNIFIED IDEOGRAPH - 0x9546: 0x5F66, //CJK UNIFIED IDEOGRAPH - 0x9547: 0x819D, //CJK UNIFIED IDEOGRAPH - 0x9548: 0x83F1, //CJK UNIFIED IDEOGRAPH - 0x9549: 0x8098, //CJK UNIFIED IDEOGRAPH - 0x954A: 0x5F3C, //CJK UNIFIED IDEOGRAPH - 0x954B: 0x5FC5, //CJK UNIFIED IDEOGRAPH - 0x954C: 0x7562, //CJK UNIFIED IDEOGRAPH - 0x954D: 0x7B46, //CJK UNIFIED IDEOGRAPH - 0x954E: 0x903C, //CJK UNIFIED IDEOGRAPH - 0x954F: 0x6867, //CJK UNIFIED IDEOGRAPH - 0x9550: 0x59EB, //CJK UNIFIED IDEOGRAPH - 0x9551: 0x5A9B, //CJK UNIFIED IDEOGRAPH - 0x9552: 0x7D10, //CJK UNIFIED IDEOGRAPH - 0x9553: 0x767E, //CJK UNIFIED IDEOGRAPH - 0x9554: 0x8B2C, //CJK UNIFIED IDEOGRAPH - 0x9555: 0x4FF5, //CJK UNIFIED IDEOGRAPH - 0x9556: 0x5F6A, //CJK UNIFIED IDEOGRAPH - 0x9557: 0x6A19, //CJK UNIFIED IDEOGRAPH - 0x9558: 0x6C37, //CJK UNIFIED IDEOGRAPH - 0x9559: 0x6F02, //CJK UNIFIED IDEOGRAPH - 0x955A: 0x74E2, //CJK UNIFIED IDEOGRAPH - 0x955B: 0x7968, //CJK UNIFIED IDEOGRAPH - 0x955C: 0x8868, //CJK UNIFIED IDEOGRAPH - 0x955D: 0x8A55, //CJK UNIFIED IDEOGRAPH - 0x955E: 0x8C79, //CJK UNIFIED IDEOGRAPH - 0x955F: 0x5EDF, //CJK UNIFIED IDEOGRAPH - 0x9560: 0x63CF, //CJK UNIFIED IDEOGRAPH - 0x9561: 0x75C5, //CJK UNIFIED IDEOGRAPH - 0x9562: 0x79D2, //CJK UNIFIED IDEOGRAPH - 0x9563: 0x82D7, //CJK UNIFIED IDEOGRAPH - 0x9564: 0x9328, //CJK UNIFIED IDEOGRAPH - 0x9565: 0x92F2, //CJK UNIFIED IDEOGRAPH - 0x9566: 0x849C, //CJK UNIFIED IDEOGRAPH - 0x9567: 0x86ED, //CJK UNIFIED IDEOGRAPH - 0x9568: 0x9C2D, //CJK UNIFIED IDEOGRAPH - 0x9569: 0x54C1, //CJK UNIFIED IDEOGRAPH - 0x956A: 0x5F6C, //CJK UNIFIED IDEOGRAPH - 0x956B: 0x658C, //CJK UNIFIED IDEOGRAPH - 0x956C: 0x6D5C, //CJK UNIFIED IDEOGRAPH - 0x956D: 0x7015, //CJK UNIFIED IDEOGRAPH - 0x956E: 0x8CA7, //CJK UNIFIED IDEOGRAPH - 0x956F: 0x8CD3, //CJK UNIFIED IDEOGRAPH - 0x9570: 0x983B, //CJK UNIFIED IDEOGRAPH - 0x9571: 0x654F, //CJK UNIFIED IDEOGRAPH - 0x9572: 0x74F6, //CJK UNIFIED IDEOGRAPH - 0x9573: 0x4E0D, //CJK UNIFIED IDEOGRAPH - 0x9574: 0x4ED8, //CJK UNIFIED IDEOGRAPH - 0x9575: 0x57E0, //CJK UNIFIED IDEOGRAPH - 0x9576: 0x592B, //CJK UNIFIED IDEOGRAPH - 0x9577: 0x5A66, //CJK UNIFIED IDEOGRAPH - 0x9578: 0x5BCC, //CJK UNIFIED IDEOGRAPH - 0x9579: 0x51A8, //CJK UNIFIED IDEOGRAPH - 0x957A: 0x5E03, //CJK UNIFIED IDEOGRAPH - 0x957B: 0x5E9C, //CJK UNIFIED IDEOGRAPH - 0x957C: 0x6016, //CJK UNIFIED IDEOGRAPH - 0x957D: 0x6276, //CJK UNIFIED IDEOGRAPH - 0x957E: 0x6577, //CJK UNIFIED IDEOGRAPH - 0x9580: 0x65A7, //CJK UNIFIED IDEOGRAPH - 0x9581: 0x666E, //CJK UNIFIED IDEOGRAPH - 0x9582: 0x6D6E, //CJK UNIFIED IDEOGRAPH - 0x9583: 0x7236, //CJK UNIFIED IDEOGRAPH - 0x9584: 0x7B26, //CJK UNIFIED IDEOGRAPH - 0x9585: 0x8150, //CJK UNIFIED IDEOGRAPH - 0x9586: 0x819A, //CJK UNIFIED IDEOGRAPH - 0x9587: 0x8299, //CJK UNIFIED IDEOGRAPH - 0x9588: 0x8B5C, //CJK UNIFIED IDEOGRAPH - 0x9589: 0x8CA0, //CJK UNIFIED IDEOGRAPH - 0x958A: 0x8CE6, //CJK UNIFIED IDEOGRAPH - 0x958B: 0x8D74, //CJK UNIFIED IDEOGRAPH - 0x958C: 0x961C, //CJK UNIFIED IDEOGRAPH - 0x958D: 0x9644, //CJK UNIFIED IDEOGRAPH - 0x958E: 0x4FAE, //CJK UNIFIED IDEOGRAPH - 0x958F: 0x64AB, //CJK UNIFIED IDEOGRAPH - 0x9590: 0x6B66, //CJK UNIFIED IDEOGRAPH - 0x9591: 0x821E, //CJK UNIFIED IDEOGRAPH - 0x9592: 0x8461, //CJK UNIFIED IDEOGRAPH - 0x9593: 0x856A, //CJK UNIFIED IDEOGRAPH - 0x9594: 0x90E8, //CJK UNIFIED IDEOGRAPH - 0x9595: 0x5C01, //CJK UNIFIED IDEOGRAPH - 0x9596: 0x6953, //CJK UNIFIED IDEOGRAPH - 0x9597: 0x98A8, //CJK UNIFIED IDEOGRAPH - 0x9598: 0x847A, //CJK UNIFIED IDEOGRAPH - 0x9599: 0x8557, //CJK UNIFIED IDEOGRAPH - 0x959A: 0x4F0F, //CJK UNIFIED IDEOGRAPH - 0x959B: 0x526F, //CJK UNIFIED IDEOGRAPH - 0x959C: 0x5FA9, //CJK UNIFIED IDEOGRAPH - 0x959D: 0x5E45, //CJK UNIFIED IDEOGRAPH - 0x959E: 0x670D, //CJK UNIFIED IDEOGRAPH - 0x959F: 0x798F, //CJK UNIFIED IDEOGRAPH - 0x95A0: 0x8179, //CJK UNIFIED IDEOGRAPH - 0x95A1: 0x8907, //CJK UNIFIED IDEOGRAPH - 0x95A2: 0x8986, //CJK UNIFIED IDEOGRAPH - 0x95A3: 0x6DF5, //CJK UNIFIED IDEOGRAPH - 0x95A4: 0x5F17, //CJK UNIFIED IDEOGRAPH - 0x95A5: 0x6255, //CJK UNIFIED IDEOGRAPH - 0x95A6: 0x6CB8, //CJK UNIFIED IDEOGRAPH - 0x95A7: 0x4ECF, //CJK UNIFIED IDEOGRAPH - 0x95A8: 0x7269, //CJK UNIFIED IDEOGRAPH - 0x95A9: 0x9B92, //CJK UNIFIED IDEOGRAPH - 0x95AA: 0x5206, //CJK UNIFIED IDEOGRAPH - 0x95AB: 0x543B, //CJK UNIFIED IDEOGRAPH - 0x95AC: 0x5674, //CJK UNIFIED IDEOGRAPH - 0x95AD: 0x58B3, //CJK UNIFIED IDEOGRAPH - 0x95AE: 0x61A4, //CJK UNIFIED IDEOGRAPH - 0x95AF: 0x626E, //CJK UNIFIED IDEOGRAPH - 0x95B0: 0x711A, //CJK UNIFIED IDEOGRAPH - 0x95B1: 0x596E, //CJK UNIFIED IDEOGRAPH - 0x95B2: 0x7C89, //CJK UNIFIED IDEOGRAPH - 0x95B3: 0x7CDE, //CJK UNIFIED IDEOGRAPH - 0x95B4: 0x7D1B, //CJK UNIFIED IDEOGRAPH - 0x95B5: 0x96F0, //CJK UNIFIED IDEOGRAPH - 0x95B6: 0x6587, //CJK UNIFIED IDEOGRAPH - 0x95B7: 0x805E, //CJK UNIFIED IDEOGRAPH - 0x95B8: 0x4E19, //CJK UNIFIED IDEOGRAPH - 0x95B9: 0x4F75, //CJK UNIFIED IDEOGRAPH - 0x95BA: 0x5175, //CJK UNIFIED IDEOGRAPH - 0x95BB: 0x5840, //CJK UNIFIED IDEOGRAPH - 0x95BC: 0x5E63, //CJK UNIFIED IDEOGRAPH - 0x95BD: 0x5E73, //CJK UNIFIED IDEOGRAPH - 0x95BE: 0x5F0A, //CJK UNIFIED IDEOGRAPH - 0x95BF: 0x67C4, //CJK UNIFIED IDEOGRAPH - 0x95C0: 0x4E26, //CJK UNIFIED IDEOGRAPH - 0x95C1: 0x853D, //CJK UNIFIED IDEOGRAPH - 0x95C2: 0x9589, //CJK UNIFIED IDEOGRAPH - 0x95C3: 0x965B, //CJK UNIFIED IDEOGRAPH - 0x95C4: 0x7C73, //CJK UNIFIED IDEOGRAPH - 0x95C5: 0x9801, //CJK UNIFIED IDEOGRAPH - 0x95C6: 0x50FB, //CJK UNIFIED IDEOGRAPH - 0x95C7: 0x58C1, //CJK UNIFIED IDEOGRAPH - 0x95C8: 0x7656, //CJK UNIFIED IDEOGRAPH - 0x95C9: 0x78A7, //CJK UNIFIED IDEOGRAPH - 0x95CA: 0x5225, //CJK UNIFIED IDEOGRAPH - 0x95CB: 0x77A5, //CJK UNIFIED IDEOGRAPH - 0x95CC: 0x8511, //CJK UNIFIED IDEOGRAPH - 0x95CD: 0x7B86, //CJK UNIFIED IDEOGRAPH - 0x95CE: 0x504F, //CJK UNIFIED IDEOGRAPH - 0x95CF: 0x5909, //CJK UNIFIED IDEOGRAPH - 0x95D0: 0x7247, //CJK UNIFIED IDEOGRAPH - 0x95D1: 0x7BC7, //CJK UNIFIED IDEOGRAPH - 0x95D2: 0x7DE8, //CJK UNIFIED IDEOGRAPH - 0x95D3: 0x8FBA, //CJK UNIFIED IDEOGRAPH - 0x95D4: 0x8FD4, //CJK UNIFIED IDEOGRAPH - 0x95D5: 0x904D, //CJK UNIFIED IDEOGRAPH - 0x95D6: 0x4FBF, //CJK UNIFIED IDEOGRAPH - 0x95D7: 0x52C9, //CJK UNIFIED IDEOGRAPH - 0x95D8: 0x5A29, //CJK UNIFIED IDEOGRAPH - 0x95D9: 0x5F01, //CJK UNIFIED IDEOGRAPH - 0x95DA: 0x97AD, //CJK UNIFIED IDEOGRAPH - 0x95DB: 0x4FDD, //CJK UNIFIED IDEOGRAPH - 0x95DC: 0x8217, //CJK UNIFIED IDEOGRAPH - 0x95DD: 0x92EA, //CJK UNIFIED IDEOGRAPH - 0x95DE: 0x5703, //CJK UNIFIED IDEOGRAPH - 0x95DF: 0x6355, //CJK UNIFIED IDEOGRAPH - 0x95E0: 0x6B69, //CJK UNIFIED IDEOGRAPH - 0x95E1: 0x752B, //CJK UNIFIED IDEOGRAPH - 0x95E2: 0x88DC, //CJK UNIFIED IDEOGRAPH - 0x95E3: 0x8F14, //CJK UNIFIED IDEOGRAPH - 0x95E4: 0x7A42, //CJK UNIFIED IDEOGRAPH - 0x95E5: 0x52DF, //CJK UNIFIED IDEOGRAPH - 0x95E6: 0x5893, //CJK UNIFIED IDEOGRAPH - 0x95E7: 0x6155, //CJK UNIFIED IDEOGRAPH - 0x95E8: 0x620A, //CJK UNIFIED IDEOGRAPH - 0x95E9: 0x66AE, //CJK UNIFIED IDEOGRAPH - 0x95EA: 0x6BCD, //CJK UNIFIED IDEOGRAPH - 0x95EB: 0x7C3F, //CJK UNIFIED IDEOGRAPH - 0x95EC: 0x83E9, //CJK UNIFIED IDEOGRAPH - 0x95ED: 0x5023, //CJK UNIFIED IDEOGRAPH - 0x95EE: 0x4FF8, //CJK UNIFIED IDEOGRAPH - 0x95EF: 0x5305, //CJK UNIFIED IDEOGRAPH - 0x95F0: 0x5446, //CJK UNIFIED IDEOGRAPH - 0x95F1: 0x5831, //CJK UNIFIED IDEOGRAPH - 0x95F2: 0x5949, //CJK UNIFIED IDEOGRAPH - 0x95F3: 0x5B9D, //CJK UNIFIED IDEOGRAPH - 0x95F4: 0x5CF0, //CJK UNIFIED IDEOGRAPH - 0x95F5: 0x5CEF, //CJK UNIFIED IDEOGRAPH - 0x95F6: 0x5D29, //CJK UNIFIED IDEOGRAPH - 0x95F7: 0x5E96, //CJK UNIFIED IDEOGRAPH - 0x95F8: 0x62B1, //CJK UNIFIED IDEOGRAPH - 0x95F9: 0x6367, //CJK UNIFIED IDEOGRAPH - 0x95FA: 0x653E, //CJK UNIFIED IDEOGRAPH - 0x95FB: 0x65B9, //CJK UNIFIED IDEOGRAPH - 0x95FC: 0x670B, //CJK UNIFIED IDEOGRAPH - 0x9640: 0x6CD5, //CJK UNIFIED IDEOGRAPH - 0x9641: 0x6CE1, //CJK UNIFIED IDEOGRAPH - 0x9642: 0x70F9, //CJK UNIFIED IDEOGRAPH - 0x9643: 0x7832, //CJK UNIFIED IDEOGRAPH - 0x9644: 0x7E2B, //CJK UNIFIED IDEOGRAPH - 0x9645: 0x80DE, //CJK UNIFIED IDEOGRAPH - 0x9646: 0x82B3, //CJK UNIFIED IDEOGRAPH - 0x9647: 0x840C, //CJK UNIFIED IDEOGRAPH - 0x9648: 0x84EC, //CJK UNIFIED IDEOGRAPH - 0x9649: 0x8702, //CJK UNIFIED IDEOGRAPH - 0x964A: 0x8912, //CJK UNIFIED IDEOGRAPH - 0x964B: 0x8A2A, //CJK UNIFIED IDEOGRAPH - 0x964C: 0x8C4A, //CJK UNIFIED IDEOGRAPH - 0x964D: 0x90A6, //CJK UNIFIED IDEOGRAPH - 0x964E: 0x92D2, //CJK UNIFIED IDEOGRAPH - 0x964F: 0x98FD, //CJK UNIFIED IDEOGRAPH - 0x9650: 0x9CF3, //CJK UNIFIED IDEOGRAPH - 0x9651: 0x9D6C, //CJK UNIFIED IDEOGRAPH - 0x9652: 0x4E4F, //CJK UNIFIED IDEOGRAPH - 0x9653: 0x4EA1, //CJK UNIFIED IDEOGRAPH - 0x9654: 0x508D, //CJK UNIFIED IDEOGRAPH - 0x9655: 0x5256, //CJK UNIFIED IDEOGRAPH - 0x9656: 0x574A, //CJK UNIFIED IDEOGRAPH - 0x9657: 0x59A8, //CJK UNIFIED IDEOGRAPH - 0x9658: 0x5E3D, //CJK UNIFIED IDEOGRAPH - 0x9659: 0x5FD8, //CJK UNIFIED IDEOGRAPH - 0x965A: 0x5FD9, //CJK UNIFIED IDEOGRAPH - 0x965B: 0x623F, //CJK UNIFIED IDEOGRAPH - 0x965C: 0x66B4, //CJK UNIFIED IDEOGRAPH - 0x965D: 0x671B, //CJK UNIFIED IDEOGRAPH - 0x965E: 0x67D0, //CJK UNIFIED IDEOGRAPH - 0x965F: 0x68D2, //CJK UNIFIED IDEOGRAPH - 0x9660: 0x5192, //CJK UNIFIED IDEOGRAPH - 0x9661: 0x7D21, //CJK UNIFIED IDEOGRAPH - 0x9662: 0x80AA, //CJK UNIFIED IDEOGRAPH - 0x9663: 0x81A8, //CJK UNIFIED IDEOGRAPH - 0x9664: 0x8B00, //CJK UNIFIED IDEOGRAPH - 0x9665: 0x8C8C, //CJK UNIFIED IDEOGRAPH - 0x9666: 0x8CBF, //CJK UNIFIED IDEOGRAPH - 0x9667: 0x927E, //CJK UNIFIED IDEOGRAPH - 0x9668: 0x9632, //CJK UNIFIED IDEOGRAPH - 0x9669: 0x5420, //CJK UNIFIED IDEOGRAPH - 0x966A: 0x982C, //CJK UNIFIED IDEOGRAPH - 0x966B: 0x5317, //CJK UNIFIED IDEOGRAPH - 0x966C: 0x50D5, //CJK UNIFIED IDEOGRAPH - 0x966D: 0x535C, //CJK UNIFIED IDEOGRAPH - 0x966E: 0x58A8, //CJK UNIFIED IDEOGRAPH - 0x966F: 0x64B2, //CJK UNIFIED IDEOGRAPH - 0x9670: 0x6734, //CJK UNIFIED IDEOGRAPH - 0x9671: 0x7267, //CJK UNIFIED IDEOGRAPH - 0x9672: 0x7766, //CJK UNIFIED IDEOGRAPH - 0x9673: 0x7A46, //CJK UNIFIED IDEOGRAPH - 0x9674: 0x91E6, //CJK UNIFIED IDEOGRAPH - 0x9675: 0x52C3, //CJK UNIFIED IDEOGRAPH - 0x9676: 0x6CA1, //CJK UNIFIED IDEOGRAPH - 0x9677: 0x6B86, //CJK UNIFIED IDEOGRAPH - 0x9678: 0x5800, //CJK UNIFIED IDEOGRAPH - 0x9679: 0x5E4C, //CJK UNIFIED IDEOGRAPH - 0x967A: 0x5954, //CJK UNIFIED IDEOGRAPH - 0x967B: 0x672C, //CJK UNIFIED IDEOGRAPH - 0x967C: 0x7FFB, //CJK UNIFIED IDEOGRAPH - 0x967D: 0x51E1, //CJK UNIFIED IDEOGRAPH - 0x967E: 0x76C6, //CJK UNIFIED IDEOGRAPH - 0x9680: 0x6469, //CJK UNIFIED IDEOGRAPH - 0x9681: 0x78E8, //CJK UNIFIED IDEOGRAPH - 0x9682: 0x9B54, //CJK UNIFIED IDEOGRAPH - 0x9683: 0x9EBB, //CJK UNIFIED IDEOGRAPH - 0x9684: 0x57CB, //CJK UNIFIED IDEOGRAPH - 0x9685: 0x59B9, //CJK UNIFIED IDEOGRAPH - 0x9686: 0x6627, //CJK UNIFIED IDEOGRAPH - 0x9687: 0x679A, //CJK UNIFIED IDEOGRAPH - 0x9688: 0x6BCE, //CJK UNIFIED IDEOGRAPH - 0x9689: 0x54E9, //CJK UNIFIED IDEOGRAPH - 0x968A: 0x69D9, //CJK UNIFIED IDEOGRAPH - 0x968B: 0x5E55, //CJK UNIFIED IDEOGRAPH - 0x968C: 0x819C, //CJK UNIFIED IDEOGRAPH - 0x968D: 0x6795, //CJK UNIFIED IDEOGRAPH - 0x968E: 0x9BAA, //CJK UNIFIED IDEOGRAPH - 0x968F: 0x67FE, //CJK UNIFIED IDEOGRAPH - 0x9690: 0x9C52, //CJK UNIFIED IDEOGRAPH - 0x9691: 0x685D, //CJK UNIFIED IDEOGRAPH - 0x9692: 0x4EA6, //CJK UNIFIED IDEOGRAPH - 0x9693: 0x4FE3, //CJK UNIFIED IDEOGRAPH - 0x9694: 0x53C8, //CJK UNIFIED IDEOGRAPH - 0x9695: 0x62B9, //CJK UNIFIED IDEOGRAPH - 0x9696: 0x672B, //CJK UNIFIED IDEOGRAPH - 0x9697: 0x6CAB, //CJK UNIFIED IDEOGRAPH - 0x9698: 0x8FC4, //CJK UNIFIED IDEOGRAPH - 0x9699: 0x4FAD, //CJK UNIFIED IDEOGRAPH - 0x969A: 0x7E6D, //CJK UNIFIED IDEOGRAPH - 0x969B: 0x9EBF, //CJK UNIFIED IDEOGRAPH - 0x969C: 0x4E07, //CJK UNIFIED IDEOGRAPH - 0x969D: 0x6162, //CJK UNIFIED IDEOGRAPH - 0x969E: 0x6E80, //CJK UNIFIED IDEOGRAPH - 0x969F: 0x6F2B, //CJK UNIFIED IDEOGRAPH - 0x96A0: 0x8513, //CJK UNIFIED IDEOGRAPH - 0x96A1: 0x5473, //CJK UNIFIED IDEOGRAPH - 0x96A2: 0x672A, //CJK UNIFIED IDEOGRAPH - 0x96A3: 0x9B45, //CJK UNIFIED IDEOGRAPH - 0x96A4: 0x5DF3, //CJK UNIFIED IDEOGRAPH - 0x96A5: 0x7B95, //CJK UNIFIED IDEOGRAPH - 0x96A6: 0x5CAC, //CJK UNIFIED IDEOGRAPH - 0x96A7: 0x5BC6, //CJK UNIFIED IDEOGRAPH - 0x96A8: 0x871C, //CJK UNIFIED IDEOGRAPH - 0x96A9: 0x6E4A, //CJK UNIFIED IDEOGRAPH - 0x96AA: 0x84D1, //CJK UNIFIED IDEOGRAPH - 0x96AB: 0x7A14, //CJK UNIFIED IDEOGRAPH - 0x96AC: 0x8108, //CJK UNIFIED IDEOGRAPH - 0x96AD: 0x5999, //CJK UNIFIED IDEOGRAPH - 0x96AE: 0x7C8D, //CJK UNIFIED IDEOGRAPH - 0x96AF: 0x6C11, //CJK UNIFIED IDEOGRAPH - 0x96B0: 0x7720, //CJK UNIFIED IDEOGRAPH - 0x96B1: 0x52D9, //CJK UNIFIED IDEOGRAPH - 0x96B2: 0x5922, //CJK UNIFIED IDEOGRAPH - 0x96B3: 0x7121, //CJK UNIFIED IDEOGRAPH - 0x96B4: 0x725F, //CJK UNIFIED IDEOGRAPH - 0x96B5: 0x77DB, //CJK UNIFIED IDEOGRAPH - 0x96B6: 0x9727, //CJK UNIFIED IDEOGRAPH - 0x96B7: 0x9D61, //CJK UNIFIED IDEOGRAPH - 0x96B8: 0x690B, //CJK UNIFIED IDEOGRAPH - 0x96B9: 0x5A7F, //CJK UNIFIED IDEOGRAPH - 0x96BA: 0x5A18, //CJK UNIFIED IDEOGRAPH - 0x96BB: 0x51A5, //CJK UNIFIED IDEOGRAPH - 0x96BC: 0x540D, //CJK UNIFIED IDEOGRAPH - 0x96BD: 0x547D, //CJK UNIFIED IDEOGRAPH - 0x96BE: 0x660E, //CJK UNIFIED IDEOGRAPH - 0x96BF: 0x76DF, //CJK UNIFIED IDEOGRAPH - 0x96C0: 0x8FF7, //CJK UNIFIED IDEOGRAPH - 0x96C1: 0x9298, //CJK UNIFIED IDEOGRAPH - 0x96C2: 0x9CF4, //CJK UNIFIED IDEOGRAPH - 0x96C3: 0x59EA, //CJK UNIFIED IDEOGRAPH - 0x96C4: 0x725D, //CJK UNIFIED IDEOGRAPH - 0x96C5: 0x6EC5, //CJK UNIFIED IDEOGRAPH - 0x96C6: 0x514D, //CJK UNIFIED IDEOGRAPH - 0x96C7: 0x68C9, //CJK UNIFIED IDEOGRAPH - 0x96C8: 0x7DBF, //CJK UNIFIED IDEOGRAPH - 0x96C9: 0x7DEC, //CJK UNIFIED IDEOGRAPH - 0x96CA: 0x9762, //CJK UNIFIED IDEOGRAPH - 0x96CB: 0x9EBA, //CJK UNIFIED IDEOGRAPH - 0x96CC: 0x6478, //CJK UNIFIED IDEOGRAPH - 0x96CD: 0x6A21, //CJK UNIFIED IDEOGRAPH - 0x96CE: 0x8302, //CJK UNIFIED IDEOGRAPH - 0x96CF: 0x5984, //CJK UNIFIED IDEOGRAPH - 0x96D0: 0x5B5F, //CJK UNIFIED IDEOGRAPH - 0x96D1: 0x6BDB, //CJK UNIFIED IDEOGRAPH - 0x96D2: 0x731B, //CJK UNIFIED IDEOGRAPH - 0x96D3: 0x76F2, //CJK UNIFIED IDEOGRAPH - 0x96D4: 0x7DB2, //CJK UNIFIED IDEOGRAPH - 0x96D5: 0x8017, //CJK UNIFIED IDEOGRAPH - 0x96D6: 0x8499, //CJK UNIFIED IDEOGRAPH - 0x96D7: 0x5132, //CJK UNIFIED IDEOGRAPH - 0x96D8: 0x6728, //CJK UNIFIED IDEOGRAPH - 0x96D9: 0x9ED9, //CJK UNIFIED IDEOGRAPH - 0x96DA: 0x76EE, //CJK UNIFIED IDEOGRAPH - 0x96DB: 0x6762, //CJK UNIFIED IDEOGRAPH - 0x96DC: 0x52FF, //CJK UNIFIED IDEOGRAPH - 0x96DD: 0x9905, //CJK UNIFIED IDEOGRAPH - 0x96DE: 0x5C24, //CJK UNIFIED IDEOGRAPH - 0x96DF: 0x623B, //CJK UNIFIED IDEOGRAPH - 0x96E0: 0x7C7E, //CJK UNIFIED IDEOGRAPH - 0x96E1: 0x8CB0, //CJK UNIFIED IDEOGRAPH - 0x96E2: 0x554F, //CJK UNIFIED IDEOGRAPH - 0x96E3: 0x60B6, //CJK UNIFIED IDEOGRAPH - 0x96E4: 0x7D0B, //CJK UNIFIED IDEOGRAPH - 0x96E5: 0x9580, //CJK UNIFIED IDEOGRAPH - 0x96E6: 0x5301, //CJK UNIFIED IDEOGRAPH - 0x96E7: 0x4E5F, //CJK UNIFIED IDEOGRAPH - 0x96E8: 0x51B6, //CJK UNIFIED IDEOGRAPH - 0x96E9: 0x591C, //CJK UNIFIED IDEOGRAPH - 0x96EA: 0x723A, //CJK UNIFIED IDEOGRAPH - 0x96EB: 0x8036, //CJK UNIFIED IDEOGRAPH - 0x96EC: 0x91CE, //CJK UNIFIED IDEOGRAPH - 0x96ED: 0x5F25, //CJK UNIFIED IDEOGRAPH - 0x96EE: 0x77E2, //CJK UNIFIED IDEOGRAPH - 0x96EF: 0x5384, //CJK UNIFIED IDEOGRAPH - 0x96F0: 0x5F79, //CJK UNIFIED IDEOGRAPH - 0x96F1: 0x7D04, //CJK UNIFIED IDEOGRAPH - 0x96F2: 0x85AC, //CJK UNIFIED IDEOGRAPH - 0x96F3: 0x8A33, //CJK UNIFIED IDEOGRAPH - 0x96F4: 0x8E8D, //CJK UNIFIED IDEOGRAPH - 0x96F5: 0x9756, //CJK UNIFIED IDEOGRAPH - 0x96F6: 0x67F3, //CJK UNIFIED IDEOGRAPH - 0x96F7: 0x85AE, //CJK UNIFIED IDEOGRAPH - 0x96F8: 0x9453, //CJK UNIFIED IDEOGRAPH - 0x96F9: 0x6109, //CJK UNIFIED IDEOGRAPH - 0x96FA: 0x6108, //CJK UNIFIED IDEOGRAPH - 0x96FB: 0x6CB9, //CJK UNIFIED IDEOGRAPH - 0x96FC: 0x7652, //CJK UNIFIED IDEOGRAPH - 0x9740: 0x8AED, //CJK UNIFIED IDEOGRAPH - 0x9741: 0x8F38, //CJK UNIFIED IDEOGRAPH - 0x9742: 0x552F, //CJK UNIFIED IDEOGRAPH - 0x9743: 0x4F51, //CJK UNIFIED IDEOGRAPH - 0x9744: 0x512A, //CJK UNIFIED IDEOGRAPH - 0x9745: 0x52C7, //CJK UNIFIED IDEOGRAPH - 0x9746: 0x53CB, //CJK UNIFIED IDEOGRAPH - 0x9747: 0x5BA5, //CJK UNIFIED IDEOGRAPH - 0x9748: 0x5E7D, //CJK UNIFIED IDEOGRAPH - 0x9749: 0x60A0, //CJK UNIFIED IDEOGRAPH - 0x974A: 0x6182, //CJK UNIFIED IDEOGRAPH - 0x974B: 0x63D6, //CJK UNIFIED IDEOGRAPH - 0x974C: 0x6709, //CJK UNIFIED IDEOGRAPH - 0x974D: 0x67DA, //CJK UNIFIED IDEOGRAPH - 0x974E: 0x6E67, //CJK UNIFIED IDEOGRAPH - 0x974F: 0x6D8C, //CJK UNIFIED IDEOGRAPH - 0x9750: 0x7336, //CJK UNIFIED IDEOGRAPH - 0x9751: 0x7337, //CJK UNIFIED IDEOGRAPH - 0x9752: 0x7531, //CJK UNIFIED IDEOGRAPH - 0x9753: 0x7950, //CJK UNIFIED IDEOGRAPH - 0x9754: 0x88D5, //CJK UNIFIED IDEOGRAPH - 0x9755: 0x8A98, //CJK UNIFIED IDEOGRAPH - 0x9756: 0x904A, //CJK UNIFIED IDEOGRAPH - 0x9757: 0x9091, //CJK UNIFIED IDEOGRAPH - 0x9758: 0x90F5, //CJK UNIFIED IDEOGRAPH - 0x9759: 0x96C4, //CJK UNIFIED IDEOGRAPH - 0x975A: 0x878D, //CJK UNIFIED IDEOGRAPH - 0x975B: 0x5915, //CJK UNIFIED IDEOGRAPH - 0x975C: 0x4E88, //CJK UNIFIED IDEOGRAPH - 0x975D: 0x4F59, //CJK UNIFIED IDEOGRAPH - 0x975E: 0x4E0E, //CJK UNIFIED IDEOGRAPH - 0x975F: 0x8A89, //CJK UNIFIED IDEOGRAPH - 0x9760: 0x8F3F, //CJK UNIFIED IDEOGRAPH - 0x9761: 0x9810, //CJK UNIFIED IDEOGRAPH - 0x9762: 0x50AD, //CJK UNIFIED IDEOGRAPH - 0x9763: 0x5E7C, //CJK UNIFIED IDEOGRAPH - 0x9764: 0x5996, //CJK UNIFIED IDEOGRAPH - 0x9765: 0x5BB9, //CJK UNIFIED IDEOGRAPH - 0x9766: 0x5EB8, //CJK UNIFIED IDEOGRAPH - 0x9767: 0x63DA, //CJK UNIFIED IDEOGRAPH - 0x9768: 0x63FA, //CJK UNIFIED IDEOGRAPH - 0x9769: 0x64C1, //CJK UNIFIED IDEOGRAPH - 0x976A: 0x66DC, //CJK UNIFIED IDEOGRAPH - 0x976B: 0x694A, //CJK UNIFIED IDEOGRAPH - 0x976C: 0x69D8, //CJK UNIFIED IDEOGRAPH - 0x976D: 0x6D0B, //CJK UNIFIED IDEOGRAPH - 0x976E: 0x6EB6, //CJK UNIFIED IDEOGRAPH - 0x976F: 0x7194, //CJK UNIFIED IDEOGRAPH - 0x9770: 0x7528, //CJK UNIFIED IDEOGRAPH - 0x9771: 0x7AAF, //CJK UNIFIED IDEOGRAPH - 0x9772: 0x7F8A, //CJK UNIFIED IDEOGRAPH - 0x9773: 0x8000, //CJK UNIFIED IDEOGRAPH - 0x9774: 0x8449, //CJK UNIFIED IDEOGRAPH - 0x9775: 0x84C9, //CJK UNIFIED IDEOGRAPH - 0x9776: 0x8981, //CJK UNIFIED IDEOGRAPH - 0x9777: 0x8B21, //CJK UNIFIED IDEOGRAPH - 0x9778: 0x8E0A, //CJK UNIFIED IDEOGRAPH - 0x9779: 0x9065, //CJK UNIFIED IDEOGRAPH - 0x977A: 0x967D, //CJK UNIFIED IDEOGRAPH - 0x977B: 0x990A, //CJK UNIFIED IDEOGRAPH - 0x977C: 0x617E, //CJK UNIFIED IDEOGRAPH - 0x977D: 0x6291, //CJK UNIFIED IDEOGRAPH - 0x977E: 0x6B32, //CJK UNIFIED IDEOGRAPH - 0x9780: 0x6C83, //CJK UNIFIED IDEOGRAPH - 0x9781: 0x6D74, //CJK UNIFIED IDEOGRAPH - 0x9782: 0x7FCC, //CJK UNIFIED IDEOGRAPH - 0x9783: 0x7FFC, //CJK UNIFIED IDEOGRAPH - 0x9784: 0x6DC0, //CJK UNIFIED IDEOGRAPH - 0x9785: 0x7F85, //CJK UNIFIED IDEOGRAPH - 0x9786: 0x87BA, //CJK UNIFIED IDEOGRAPH - 0x9787: 0x88F8, //CJK UNIFIED IDEOGRAPH - 0x9788: 0x6765, //CJK UNIFIED IDEOGRAPH - 0x9789: 0x83B1, //CJK UNIFIED IDEOGRAPH - 0x978A: 0x983C, //CJK UNIFIED IDEOGRAPH - 0x978B: 0x96F7, //CJK UNIFIED IDEOGRAPH - 0x978C: 0x6D1B, //CJK UNIFIED IDEOGRAPH - 0x978D: 0x7D61, //CJK UNIFIED IDEOGRAPH - 0x978E: 0x843D, //CJK UNIFIED IDEOGRAPH - 0x978F: 0x916A, //CJK UNIFIED IDEOGRAPH - 0x9790: 0x4E71, //CJK UNIFIED IDEOGRAPH - 0x9791: 0x5375, //CJK UNIFIED IDEOGRAPH - 0x9792: 0x5D50, //CJK UNIFIED IDEOGRAPH - 0x9793: 0x6B04, //CJK UNIFIED IDEOGRAPH - 0x9794: 0x6FEB, //CJK UNIFIED IDEOGRAPH - 0x9795: 0x85CD, //CJK UNIFIED IDEOGRAPH - 0x9796: 0x862D, //CJK UNIFIED IDEOGRAPH - 0x9797: 0x89A7, //CJK UNIFIED IDEOGRAPH - 0x9798: 0x5229, //CJK UNIFIED IDEOGRAPH - 0x9799: 0x540F, //CJK UNIFIED IDEOGRAPH - 0x979A: 0x5C65, //CJK UNIFIED IDEOGRAPH - 0x979B: 0x674E, //CJK UNIFIED IDEOGRAPH - 0x979C: 0x68A8, //CJK UNIFIED IDEOGRAPH - 0x979D: 0x7406, //CJK UNIFIED IDEOGRAPH - 0x979E: 0x7483, //CJK UNIFIED IDEOGRAPH - 0x979F: 0x75E2, //CJK UNIFIED IDEOGRAPH - 0x97A0: 0x88CF, //CJK UNIFIED IDEOGRAPH - 0x97A1: 0x88E1, //CJK UNIFIED IDEOGRAPH - 0x97A2: 0x91CC, //CJK UNIFIED IDEOGRAPH - 0x97A3: 0x96E2, //CJK UNIFIED IDEOGRAPH - 0x97A4: 0x9678, //CJK UNIFIED IDEOGRAPH - 0x97A5: 0x5F8B, //CJK UNIFIED IDEOGRAPH - 0x97A6: 0x7387, //CJK UNIFIED IDEOGRAPH - 0x97A7: 0x7ACB, //CJK UNIFIED IDEOGRAPH - 0x97A8: 0x844E, //CJK UNIFIED IDEOGRAPH - 0x97A9: 0x63A0, //CJK UNIFIED IDEOGRAPH - 0x97AA: 0x7565, //CJK UNIFIED IDEOGRAPH - 0x97AB: 0x5289, //CJK UNIFIED IDEOGRAPH - 0x97AC: 0x6D41, //CJK UNIFIED IDEOGRAPH - 0x97AD: 0x6E9C, //CJK UNIFIED IDEOGRAPH - 0x97AE: 0x7409, //CJK UNIFIED IDEOGRAPH - 0x97AF: 0x7559, //CJK UNIFIED IDEOGRAPH - 0x97B0: 0x786B, //CJK UNIFIED IDEOGRAPH - 0x97B1: 0x7C92, //CJK UNIFIED IDEOGRAPH - 0x97B2: 0x9686, //CJK UNIFIED IDEOGRAPH - 0x97B3: 0x7ADC, //CJK UNIFIED IDEOGRAPH - 0x97B4: 0x9F8D, //CJK UNIFIED IDEOGRAPH - 0x97B5: 0x4FB6, //CJK UNIFIED IDEOGRAPH - 0x97B6: 0x616E, //CJK UNIFIED IDEOGRAPH - 0x97B7: 0x65C5, //CJK UNIFIED IDEOGRAPH - 0x97B8: 0x865C, //CJK UNIFIED IDEOGRAPH - 0x97B9: 0x4E86, //CJK UNIFIED IDEOGRAPH - 0x97BA: 0x4EAE, //CJK UNIFIED IDEOGRAPH - 0x97BB: 0x50DA, //CJK UNIFIED IDEOGRAPH - 0x97BC: 0x4E21, //CJK UNIFIED IDEOGRAPH - 0x97BD: 0x51CC, //CJK UNIFIED IDEOGRAPH - 0x97BE: 0x5BEE, //CJK UNIFIED IDEOGRAPH - 0x97BF: 0x6599, //CJK UNIFIED IDEOGRAPH - 0x97C0: 0x6881, //CJK UNIFIED IDEOGRAPH - 0x97C1: 0x6DBC, //CJK UNIFIED IDEOGRAPH - 0x97C2: 0x731F, //CJK UNIFIED IDEOGRAPH - 0x97C3: 0x7642, //CJK UNIFIED IDEOGRAPH - 0x97C4: 0x77AD, //CJK UNIFIED IDEOGRAPH - 0x97C5: 0x7A1C, //CJK UNIFIED IDEOGRAPH - 0x97C6: 0x7CE7, //CJK UNIFIED IDEOGRAPH - 0x97C7: 0x826F, //CJK UNIFIED IDEOGRAPH - 0x97C8: 0x8AD2, //CJK UNIFIED IDEOGRAPH - 0x97C9: 0x907C, //CJK UNIFIED IDEOGRAPH - 0x97CA: 0x91CF, //CJK UNIFIED IDEOGRAPH - 0x97CB: 0x9675, //CJK UNIFIED IDEOGRAPH - 0x97CC: 0x9818, //CJK UNIFIED IDEOGRAPH - 0x97CD: 0x529B, //CJK UNIFIED IDEOGRAPH - 0x97CE: 0x7DD1, //CJK UNIFIED IDEOGRAPH - 0x97CF: 0x502B, //CJK UNIFIED IDEOGRAPH - 0x97D0: 0x5398, //CJK UNIFIED IDEOGRAPH - 0x97D1: 0x6797, //CJK UNIFIED IDEOGRAPH - 0x97D2: 0x6DCB, //CJK UNIFIED IDEOGRAPH - 0x97D3: 0x71D0, //CJK UNIFIED IDEOGRAPH - 0x97D4: 0x7433, //CJK UNIFIED IDEOGRAPH - 0x97D5: 0x81E8, //CJK UNIFIED IDEOGRAPH - 0x97D6: 0x8F2A, //CJK UNIFIED IDEOGRAPH - 0x97D7: 0x96A3, //CJK UNIFIED IDEOGRAPH - 0x97D8: 0x9C57, //CJK UNIFIED IDEOGRAPH - 0x97D9: 0x9E9F, //CJK UNIFIED IDEOGRAPH - 0x97DA: 0x7460, //CJK UNIFIED IDEOGRAPH - 0x97DB: 0x5841, //CJK UNIFIED IDEOGRAPH - 0x97DC: 0x6D99, //CJK UNIFIED IDEOGRAPH - 0x97DD: 0x7D2F, //CJK UNIFIED IDEOGRAPH - 0x97DE: 0x985E, //CJK UNIFIED IDEOGRAPH - 0x97DF: 0x4EE4, //CJK UNIFIED IDEOGRAPH - 0x97E0: 0x4F36, //CJK UNIFIED IDEOGRAPH - 0x97E1: 0x4F8B, //CJK UNIFIED IDEOGRAPH - 0x97E2: 0x51B7, //CJK UNIFIED IDEOGRAPH - 0x97E3: 0x52B1, //CJK UNIFIED IDEOGRAPH - 0x97E4: 0x5DBA, //CJK UNIFIED IDEOGRAPH - 0x97E5: 0x601C, //CJK UNIFIED IDEOGRAPH - 0x97E6: 0x73B2, //CJK UNIFIED IDEOGRAPH - 0x97E7: 0x793C, //CJK UNIFIED IDEOGRAPH - 0x97E8: 0x82D3, //CJK UNIFIED IDEOGRAPH - 0x97E9: 0x9234, //CJK UNIFIED IDEOGRAPH - 0x97EA: 0x96B7, //CJK UNIFIED IDEOGRAPH - 0x97EB: 0x96F6, //CJK UNIFIED IDEOGRAPH - 0x97EC: 0x970A, //CJK UNIFIED IDEOGRAPH - 0x97ED: 0x9E97, //CJK UNIFIED IDEOGRAPH - 0x97EE: 0x9F62, //CJK UNIFIED IDEOGRAPH - 0x97EF: 0x66A6, //CJK UNIFIED IDEOGRAPH - 0x97F0: 0x6B74, //CJK UNIFIED IDEOGRAPH - 0x97F1: 0x5217, //CJK UNIFIED IDEOGRAPH - 0x97F2: 0x52A3, //CJK UNIFIED IDEOGRAPH - 0x97F3: 0x70C8, //CJK UNIFIED IDEOGRAPH - 0x97F4: 0x88C2, //CJK UNIFIED IDEOGRAPH - 0x97F5: 0x5EC9, //CJK UNIFIED IDEOGRAPH - 0x97F6: 0x604B, //CJK UNIFIED IDEOGRAPH - 0x97F7: 0x6190, //CJK UNIFIED IDEOGRAPH - 0x97F8: 0x6F23, //CJK UNIFIED IDEOGRAPH - 0x97F9: 0x7149, //CJK UNIFIED IDEOGRAPH - 0x97FA: 0x7C3E, //CJK UNIFIED IDEOGRAPH - 0x97FB: 0x7DF4, //CJK UNIFIED IDEOGRAPH - 0x97FC: 0x806F, //CJK UNIFIED IDEOGRAPH - 0x9840: 0x84EE, //CJK UNIFIED IDEOGRAPH - 0x9841: 0x9023, //CJK UNIFIED IDEOGRAPH - 0x9842: 0x932C, //CJK UNIFIED IDEOGRAPH - 0x9843: 0x5442, //CJK UNIFIED IDEOGRAPH - 0x9844: 0x9B6F, //CJK UNIFIED IDEOGRAPH - 0x9845: 0x6AD3, //CJK UNIFIED IDEOGRAPH - 0x9846: 0x7089, //CJK UNIFIED IDEOGRAPH - 0x9847: 0x8CC2, //CJK UNIFIED IDEOGRAPH - 0x9848: 0x8DEF, //CJK UNIFIED IDEOGRAPH - 0x9849: 0x9732, //CJK UNIFIED IDEOGRAPH - 0x984A: 0x52B4, //CJK UNIFIED IDEOGRAPH - 0x984B: 0x5A41, //CJK UNIFIED IDEOGRAPH - 0x984C: 0x5ECA, //CJK UNIFIED IDEOGRAPH - 0x984D: 0x5F04, //CJK UNIFIED IDEOGRAPH - 0x984E: 0x6717, //CJK UNIFIED IDEOGRAPH - 0x984F: 0x697C, //CJK UNIFIED IDEOGRAPH - 0x9850: 0x6994, //CJK UNIFIED IDEOGRAPH - 0x9851: 0x6D6A, //CJK UNIFIED IDEOGRAPH - 0x9852: 0x6F0F, //CJK UNIFIED IDEOGRAPH - 0x9853: 0x7262, //CJK UNIFIED IDEOGRAPH - 0x9854: 0x72FC, //CJK UNIFIED IDEOGRAPH - 0x9855: 0x7BED, //CJK UNIFIED IDEOGRAPH - 0x9856: 0x8001, //CJK UNIFIED IDEOGRAPH - 0x9857: 0x807E, //CJK UNIFIED IDEOGRAPH - 0x9858: 0x874B, //CJK UNIFIED IDEOGRAPH - 0x9859: 0x90CE, //CJK UNIFIED IDEOGRAPH - 0x985A: 0x516D, //CJK UNIFIED IDEOGRAPH - 0x985B: 0x9E93, //CJK UNIFIED IDEOGRAPH - 0x985C: 0x7984, //CJK UNIFIED IDEOGRAPH - 0x985D: 0x808B, //CJK UNIFIED IDEOGRAPH - 0x985E: 0x9332, //CJK UNIFIED IDEOGRAPH - 0x985F: 0x8AD6, //CJK UNIFIED IDEOGRAPH - 0x9860: 0x502D, //CJK UNIFIED IDEOGRAPH - 0x9861: 0x548C, //CJK UNIFIED IDEOGRAPH - 0x9862: 0x8A71, //CJK UNIFIED IDEOGRAPH - 0x9863: 0x6B6A, //CJK UNIFIED IDEOGRAPH - 0x9864: 0x8CC4, //CJK UNIFIED IDEOGRAPH - 0x9865: 0x8107, //CJK UNIFIED IDEOGRAPH - 0x9866: 0x60D1, //CJK UNIFIED IDEOGRAPH - 0x9867: 0x67A0, //CJK UNIFIED IDEOGRAPH - 0x9868: 0x9DF2, //CJK UNIFIED IDEOGRAPH - 0x9869: 0x4E99, //CJK UNIFIED IDEOGRAPH - 0x986A: 0x4E98, //CJK UNIFIED IDEOGRAPH - 0x986B: 0x9C10, //CJK UNIFIED IDEOGRAPH - 0x986C: 0x8A6B, //CJK UNIFIED IDEOGRAPH - 0x986D: 0x85C1, //CJK UNIFIED IDEOGRAPH - 0x986E: 0x8568, //CJK UNIFIED IDEOGRAPH - 0x986F: 0x6900, //CJK UNIFIED IDEOGRAPH - 0x9870: 0x6E7E, //CJK UNIFIED IDEOGRAPH - 0x9871: 0x7897, //CJK UNIFIED IDEOGRAPH - 0x9872: 0x8155, //CJK UNIFIED IDEOGRAPH - 0x989F: 0x5F0C, //CJK UNIFIED IDEOGRAPH - 0x98A0: 0x4E10, //CJK UNIFIED IDEOGRAPH - 0x98A1: 0x4E15, //CJK UNIFIED IDEOGRAPH - 0x98A2: 0x4E2A, //CJK UNIFIED IDEOGRAPH - 0x98A3: 0x4E31, //CJK UNIFIED IDEOGRAPH - 0x98A4: 0x4E36, //CJK UNIFIED IDEOGRAPH - 0x98A5: 0x4E3C, //CJK UNIFIED IDEOGRAPH - 0x98A6: 0x4E3F, //CJK UNIFIED IDEOGRAPH - 0x98A7: 0x4E42, //CJK UNIFIED IDEOGRAPH - 0x98A8: 0x4E56, //CJK UNIFIED IDEOGRAPH - 0x98A9: 0x4E58, //CJK UNIFIED IDEOGRAPH - 0x98AA: 0x4E82, //CJK UNIFIED IDEOGRAPH - 0x98AB: 0x4E85, //CJK UNIFIED IDEOGRAPH - 0x98AC: 0x8C6B, //CJK UNIFIED IDEOGRAPH - 0x98AD: 0x4E8A, //CJK UNIFIED IDEOGRAPH - 0x98AE: 0x8212, //CJK UNIFIED IDEOGRAPH - 0x98AF: 0x5F0D, //CJK UNIFIED IDEOGRAPH - 0x98B0: 0x4E8E, //CJK UNIFIED IDEOGRAPH - 0x98B1: 0x4E9E, //CJK UNIFIED IDEOGRAPH - 0x98B2: 0x4E9F, //CJK UNIFIED IDEOGRAPH - 0x98B3: 0x4EA0, //CJK UNIFIED IDEOGRAPH - 0x98B4: 0x4EA2, //CJK UNIFIED IDEOGRAPH - 0x98B5: 0x4EB0, //CJK UNIFIED IDEOGRAPH - 0x98B6: 0x4EB3, //CJK UNIFIED IDEOGRAPH - 0x98B7: 0x4EB6, //CJK UNIFIED IDEOGRAPH - 0x98B8: 0x4ECE, //CJK UNIFIED IDEOGRAPH - 0x98B9: 0x4ECD, //CJK UNIFIED IDEOGRAPH - 0x98BA: 0x4EC4, //CJK UNIFIED IDEOGRAPH - 0x98BB: 0x4EC6, //CJK UNIFIED IDEOGRAPH - 0x98BC: 0x4EC2, //CJK UNIFIED IDEOGRAPH - 0x98BD: 0x4ED7, //CJK UNIFIED IDEOGRAPH - 0x98BE: 0x4EDE, //CJK UNIFIED IDEOGRAPH - 0x98BF: 0x4EED, //CJK UNIFIED IDEOGRAPH - 0x98C0: 0x4EDF, //CJK UNIFIED IDEOGRAPH - 0x98C1: 0x4EF7, //CJK UNIFIED IDEOGRAPH - 0x98C2: 0x4F09, //CJK UNIFIED IDEOGRAPH - 0x98C3: 0x4F5A, //CJK UNIFIED IDEOGRAPH - 0x98C4: 0x4F30, //CJK UNIFIED IDEOGRAPH - 0x98C5: 0x4F5B, //CJK UNIFIED IDEOGRAPH - 0x98C6: 0x4F5D, //CJK UNIFIED IDEOGRAPH - 0x98C7: 0x4F57, //CJK UNIFIED IDEOGRAPH - 0x98C8: 0x4F47, //CJK UNIFIED IDEOGRAPH - 0x98C9: 0x4F76, //CJK UNIFIED IDEOGRAPH - 0x98CA: 0x4F88, //CJK UNIFIED IDEOGRAPH - 0x98CB: 0x4F8F, //CJK UNIFIED IDEOGRAPH - 0x98CC: 0x4F98, //CJK UNIFIED IDEOGRAPH - 0x98CD: 0x4F7B, //CJK UNIFIED IDEOGRAPH - 0x98CE: 0x4F69, //CJK UNIFIED IDEOGRAPH - 0x98CF: 0x4F70, //CJK UNIFIED IDEOGRAPH - 0x98D0: 0x4F91, //CJK UNIFIED IDEOGRAPH - 0x98D1: 0x4F6F, //CJK UNIFIED IDEOGRAPH - 0x98D2: 0x4F86, //CJK UNIFIED IDEOGRAPH - 0x98D3: 0x4F96, //CJK UNIFIED IDEOGRAPH - 0x98D4: 0x5118, //CJK UNIFIED IDEOGRAPH - 0x98D5: 0x4FD4, //CJK UNIFIED IDEOGRAPH - 0x98D6: 0x4FDF, //CJK UNIFIED IDEOGRAPH - 0x98D7: 0x4FCE, //CJK UNIFIED IDEOGRAPH - 0x98D8: 0x4FD8, //CJK UNIFIED IDEOGRAPH - 0x98D9: 0x4FDB, //CJK UNIFIED IDEOGRAPH - 0x98DA: 0x4FD1, //CJK UNIFIED IDEOGRAPH - 0x98DB: 0x4FDA, //CJK UNIFIED IDEOGRAPH - 0x98DC: 0x4FD0, //CJK UNIFIED IDEOGRAPH - 0x98DD: 0x4FE4, //CJK UNIFIED IDEOGRAPH - 0x98DE: 0x4FE5, //CJK UNIFIED IDEOGRAPH - 0x98DF: 0x501A, //CJK UNIFIED IDEOGRAPH - 0x98E0: 0x5028, //CJK UNIFIED IDEOGRAPH - 0x98E1: 0x5014, //CJK UNIFIED IDEOGRAPH - 0x98E2: 0x502A, //CJK UNIFIED IDEOGRAPH - 0x98E3: 0x5025, //CJK UNIFIED IDEOGRAPH - 0x98E4: 0x5005, //CJK UNIFIED IDEOGRAPH - 0x98E5: 0x4F1C, //CJK UNIFIED IDEOGRAPH - 0x98E6: 0x4FF6, //CJK UNIFIED IDEOGRAPH - 0x98E7: 0x5021, //CJK UNIFIED IDEOGRAPH - 0x98E8: 0x5029, //CJK UNIFIED IDEOGRAPH - 0x98E9: 0x502C, //CJK UNIFIED IDEOGRAPH - 0x98EA: 0x4FFE, //CJK UNIFIED IDEOGRAPH - 0x98EB: 0x4FEF, //CJK UNIFIED IDEOGRAPH - 0x98EC: 0x5011, //CJK UNIFIED IDEOGRAPH - 0x98ED: 0x5006, //CJK UNIFIED IDEOGRAPH - 0x98EE: 0x5043, //CJK UNIFIED IDEOGRAPH - 0x98EF: 0x5047, //CJK UNIFIED IDEOGRAPH - 0x98F0: 0x6703, //CJK UNIFIED IDEOGRAPH - 0x98F1: 0x5055, //CJK UNIFIED IDEOGRAPH - 0x98F2: 0x5050, //CJK UNIFIED IDEOGRAPH - 0x98F3: 0x5048, //CJK UNIFIED IDEOGRAPH - 0x98F4: 0x505A, //CJK UNIFIED IDEOGRAPH - 0x98F5: 0x5056, //CJK UNIFIED IDEOGRAPH - 0x98F6: 0x506C, //CJK UNIFIED IDEOGRAPH - 0x98F7: 0x5078, //CJK UNIFIED IDEOGRAPH - 0x98F8: 0x5080, //CJK UNIFIED IDEOGRAPH - 0x98F9: 0x509A, //CJK UNIFIED IDEOGRAPH - 0x98FA: 0x5085, //CJK UNIFIED IDEOGRAPH - 0x98FB: 0x50B4, //CJK UNIFIED IDEOGRAPH - 0x98FC: 0x50B2, //CJK UNIFIED IDEOGRAPH - 0x9940: 0x50C9, //CJK UNIFIED IDEOGRAPH - 0x9941: 0x50CA, //CJK UNIFIED IDEOGRAPH - 0x9942: 0x50B3, //CJK UNIFIED IDEOGRAPH - 0x9943: 0x50C2, //CJK UNIFIED IDEOGRAPH - 0x9944: 0x50D6, //CJK UNIFIED IDEOGRAPH - 0x9945: 0x50DE, //CJK UNIFIED IDEOGRAPH - 0x9946: 0x50E5, //CJK UNIFIED IDEOGRAPH - 0x9947: 0x50ED, //CJK UNIFIED IDEOGRAPH - 0x9948: 0x50E3, //CJK UNIFIED IDEOGRAPH - 0x9949: 0x50EE, //CJK UNIFIED IDEOGRAPH - 0x994A: 0x50F9, //CJK UNIFIED IDEOGRAPH - 0x994B: 0x50F5, //CJK UNIFIED IDEOGRAPH - 0x994C: 0x5109, //CJK UNIFIED IDEOGRAPH - 0x994D: 0x5101, //CJK UNIFIED IDEOGRAPH - 0x994E: 0x5102, //CJK UNIFIED IDEOGRAPH - 0x994F: 0x5116, //CJK UNIFIED IDEOGRAPH - 0x9950: 0x5115, //CJK UNIFIED IDEOGRAPH - 0x9951: 0x5114, //CJK UNIFIED IDEOGRAPH - 0x9952: 0x511A, //CJK UNIFIED IDEOGRAPH - 0x9953: 0x5121, //CJK UNIFIED IDEOGRAPH - 0x9954: 0x513A, //CJK UNIFIED IDEOGRAPH - 0x9955: 0x5137, //CJK UNIFIED IDEOGRAPH - 0x9956: 0x513C, //CJK UNIFIED IDEOGRAPH - 0x9957: 0x513B, //CJK UNIFIED IDEOGRAPH - 0x9958: 0x513F, //CJK UNIFIED IDEOGRAPH - 0x9959: 0x5140, //CJK UNIFIED IDEOGRAPH - 0x995A: 0x5152, //CJK UNIFIED IDEOGRAPH - 0x995B: 0x514C, //CJK UNIFIED IDEOGRAPH - 0x995C: 0x5154, //CJK UNIFIED IDEOGRAPH - 0x995D: 0x5162, //CJK UNIFIED IDEOGRAPH - 0x995E: 0x7AF8, //CJK UNIFIED IDEOGRAPH - 0x995F: 0x5169, //CJK UNIFIED IDEOGRAPH - 0x9960: 0x516A, //CJK UNIFIED IDEOGRAPH - 0x9961: 0x516E, //CJK UNIFIED IDEOGRAPH - 0x9962: 0x5180, //CJK UNIFIED IDEOGRAPH - 0x9963: 0x5182, //CJK UNIFIED IDEOGRAPH - 0x9964: 0x56D8, //CJK UNIFIED IDEOGRAPH - 0x9965: 0x518C, //CJK UNIFIED IDEOGRAPH - 0x9966: 0x5189, //CJK UNIFIED IDEOGRAPH - 0x9967: 0x518F, //CJK UNIFIED IDEOGRAPH - 0x9968: 0x5191, //CJK UNIFIED IDEOGRAPH - 0x9969: 0x5193, //CJK UNIFIED IDEOGRAPH - 0x996A: 0x5195, //CJK UNIFIED IDEOGRAPH - 0x996B: 0x5196, //CJK UNIFIED IDEOGRAPH - 0x996C: 0x51A4, //CJK UNIFIED IDEOGRAPH - 0x996D: 0x51A6, //CJK UNIFIED IDEOGRAPH - 0x996E: 0x51A2, //CJK UNIFIED IDEOGRAPH - 0x996F: 0x51A9, //CJK UNIFIED IDEOGRAPH - 0x9970: 0x51AA, //CJK UNIFIED IDEOGRAPH - 0x9971: 0x51AB, //CJK UNIFIED IDEOGRAPH - 0x9972: 0x51B3, //CJK UNIFIED IDEOGRAPH - 0x9973: 0x51B1, //CJK UNIFIED IDEOGRAPH - 0x9974: 0x51B2, //CJK UNIFIED IDEOGRAPH - 0x9975: 0x51B0, //CJK UNIFIED IDEOGRAPH - 0x9976: 0x51B5, //CJK UNIFIED IDEOGRAPH - 0x9977: 0x51BD, //CJK UNIFIED IDEOGRAPH - 0x9978: 0x51C5, //CJK UNIFIED IDEOGRAPH - 0x9979: 0x51C9, //CJK UNIFIED IDEOGRAPH - 0x997A: 0x51DB, //CJK UNIFIED IDEOGRAPH - 0x997B: 0x51E0, //CJK UNIFIED IDEOGRAPH - 0x997C: 0x8655, //CJK UNIFIED IDEOGRAPH - 0x997D: 0x51E9, //CJK UNIFIED IDEOGRAPH - 0x997E: 0x51ED, //CJK UNIFIED IDEOGRAPH - 0x9980: 0x51F0, //CJK UNIFIED IDEOGRAPH - 0x9981: 0x51F5, //CJK UNIFIED IDEOGRAPH - 0x9982: 0x51FE, //CJK UNIFIED IDEOGRAPH - 0x9983: 0x5204, //CJK UNIFIED IDEOGRAPH - 0x9984: 0x520B, //CJK UNIFIED IDEOGRAPH - 0x9985: 0x5214, //CJK UNIFIED IDEOGRAPH - 0x9986: 0x520E, //CJK UNIFIED IDEOGRAPH - 0x9987: 0x5227, //CJK UNIFIED IDEOGRAPH - 0x9988: 0x522A, //CJK UNIFIED IDEOGRAPH - 0x9989: 0x522E, //CJK UNIFIED IDEOGRAPH - 0x998A: 0x5233, //CJK UNIFIED IDEOGRAPH - 0x998B: 0x5239, //CJK UNIFIED IDEOGRAPH - 0x998C: 0x524F, //CJK UNIFIED IDEOGRAPH - 0x998D: 0x5244, //CJK UNIFIED IDEOGRAPH - 0x998E: 0x524B, //CJK UNIFIED IDEOGRAPH - 0x998F: 0x524C, //CJK UNIFIED IDEOGRAPH - 0x9990: 0x525E, //CJK UNIFIED IDEOGRAPH - 0x9991: 0x5254, //CJK UNIFIED IDEOGRAPH - 0x9992: 0x526A, //CJK UNIFIED IDEOGRAPH - 0x9993: 0x5274, //CJK UNIFIED IDEOGRAPH - 0x9994: 0x5269, //CJK UNIFIED IDEOGRAPH - 0x9995: 0x5273, //CJK UNIFIED IDEOGRAPH - 0x9996: 0x527F, //CJK UNIFIED IDEOGRAPH - 0x9997: 0x527D, //CJK UNIFIED IDEOGRAPH - 0x9998: 0x528D, //CJK UNIFIED IDEOGRAPH - 0x9999: 0x5294, //CJK UNIFIED IDEOGRAPH - 0x999A: 0x5292, //CJK UNIFIED IDEOGRAPH - 0x999B: 0x5271, //CJK UNIFIED IDEOGRAPH - 0x999C: 0x5288, //CJK UNIFIED IDEOGRAPH - 0x999D: 0x5291, //CJK UNIFIED IDEOGRAPH - 0x999E: 0x8FA8, //CJK UNIFIED IDEOGRAPH - 0x999F: 0x8FA7, //CJK UNIFIED IDEOGRAPH - 0x99A0: 0x52AC, //CJK UNIFIED IDEOGRAPH - 0x99A1: 0x52AD, //CJK UNIFIED IDEOGRAPH - 0x99A2: 0x52BC, //CJK UNIFIED IDEOGRAPH - 0x99A3: 0x52B5, //CJK UNIFIED IDEOGRAPH - 0x99A4: 0x52C1, //CJK UNIFIED IDEOGRAPH - 0x99A5: 0x52CD, //CJK UNIFIED IDEOGRAPH - 0x99A6: 0x52D7, //CJK UNIFIED IDEOGRAPH - 0x99A7: 0x52DE, //CJK UNIFIED IDEOGRAPH - 0x99A8: 0x52E3, //CJK UNIFIED IDEOGRAPH - 0x99A9: 0x52E6, //CJK UNIFIED IDEOGRAPH - 0x99AA: 0x98ED, //CJK UNIFIED IDEOGRAPH - 0x99AB: 0x52E0, //CJK UNIFIED IDEOGRAPH - 0x99AC: 0x52F3, //CJK UNIFIED IDEOGRAPH - 0x99AD: 0x52F5, //CJK UNIFIED IDEOGRAPH - 0x99AE: 0x52F8, //CJK UNIFIED IDEOGRAPH - 0x99AF: 0x52F9, //CJK UNIFIED IDEOGRAPH - 0x99B0: 0x5306, //CJK UNIFIED IDEOGRAPH - 0x99B1: 0x5308, //CJK UNIFIED IDEOGRAPH - 0x99B2: 0x7538, //CJK UNIFIED IDEOGRAPH - 0x99B3: 0x530D, //CJK UNIFIED IDEOGRAPH - 0x99B4: 0x5310, //CJK UNIFIED IDEOGRAPH - 0x99B5: 0x530F, //CJK UNIFIED IDEOGRAPH - 0x99B6: 0x5315, //CJK UNIFIED IDEOGRAPH - 0x99B7: 0x531A, //CJK UNIFIED IDEOGRAPH - 0x99B8: 0x5323, //CJK UNIFIED IDEOGRAPH - 0x99B9: 0x532F, //CJK UNIFIED IDEOGRAPH - 0x99BA: 0x5331, //CJK UNIFIED IDEOGRAPH - 0x99BB: 0x5333, //CJK UNIFIED IDEOGRAPH - 0x99BC: 0x5338, //CJK UNIFIED IDEOGRAPH - 0x99BD: 0x5340, //CJK UNIFIED IDEOGRAPH - 0x99BE: 0x5346, //CJK UNIFIED IDEOGRAPH - 0x99BF: 0x5345, //CJK UNIFIED IDEOGRAPH - 0x99C0: 0x4E17, //CJK UNIFIED IDEOGRAPH - 0x99C1: 0x5349, //CJK UNIFIED IDEOGRAPH - 0x99C2: 0x534D, //CJK UNIFIED IDEOGRAPH - 0x99C3: 0x51D6, //CJK UNIFIED IDEOGRAPH - 0x99C4: 0x535E, //CJK UNIFIED IDEOGRAPH - 0x99C5: 0x5369, //CJK UNIFIED IDEOGRAPH - 0x99C6: 0x536E, //CJK UNIFIED IDEOGRAPH - 0x99C7: 0x5918, //CJK UNIFIED IDEOGRAPH - 0x99C8: 0x537B, //CJK UNIFIED IDEOGRAPH - 0x99C9: 0x5377, //CJK UNIFIED IDEOGRAPH - 0x99CA: 0x5382, //CJK UNIFIED IDEOGRAPH - 0x99CB: 0x5396, //CJK UNIFIED IDEOGRAPH - 0x99CC: 0x53A0, //CJK UNIFIED IDEOGRAPH - 0x99CD: 0x53A6, //CJK UNIFIED IDEOGRAPH - 0x99CE: 0x53A5, //CJK UNIFIED IDEOGRAPH - 0x99CF: 0x53AE, //CJK UNIFIED IDEOGRAPH - 0x99D0: 0x53B0, //CJK UNIFIED IDEOGRAPH - 0x99D1: 0x53B6, //CJK UNIFIED IDEOGRAPH - 0x99D2: 0x53C3, //CJK UNIFIED IDEOGRAPH - 0x99D3: 0x7C12, //CJK UNIFIED IDEOGRAPH - 0x99D4: 0x96D9, //CJK UNIFIED IDEOGRAPH - 0x99D5: 0x53DF, //CJK UNIFIED IDEOGRAPH - 0x99D6: 0x66FC, //CJK UNIFIED IDEOGRAPH - 0x99D7: 0x71EE, //CJK UNIFIED IDEOGRAPH - 0x99D8: 0x53EE, //CJK UNIFIED IDEOGRAPH - 0x99D9: 0x53E8, //CJK UNIFIED IDEOGRAPH - 0x99DA: 0x53ED, //CJK UNIFIED IDEOGRAPH - 0x99DB: 0x53FA, //CJK UNIFIED IDEOGRAPH - 0x99DC: 0x5401, //CJK UNIFIED IDEOGRAPH - 0x99DD: 0x543D, //CJK UNIFIED IDEOGRAPH - 0x99DE: 0x5440, //CJK UNIFIED IDEOGRAPH - 0x99DF: 0x542C, //CJK UNIFIED IDEOGRAPH - 0x99E0: 0x542D, //CJK UNIFIED IDEOGRAPH - 0x99E1: 0x543C, //CJK UNIFIED IDEOGRAPH - 0x99E2: 0x542E, //CJK UNIFIED IDEOGRAPH - 0x99E3: 0x5436, //CJK UNIFIED IDEOGRAPH - 0x99E4: 0x5429, //CJK UNIFIED IDEOGRAPH - 0x99E5: 0x541D, //CJK UNIFIED IDEOGRAPH - 0x99E6: 0x544E, //CJK UNIFIED IDEOGRAPH - 0x99E7: 0x548F, //CJK UNIFIED IDEOGRAPH - 0x99E8: 0x5475, //CJK UNIFIED IDEOGRAPH - 0x99E9: 0x548E, //CJK UNIFIED IDEOGRAPH - 0x99EA: 0x545F, //CJK UNIFIED IDEOGRAPH - 0x99EB: 0x5471, //CJK UNIFIED IDEOGRAPH - 0x99EC: 0x5477, //CJK UNIFIED IDEOGRAPH - 0x99ED: 0x5470, //CJK UNIFIED IDEOGRAPH - 0x99EE: 0x5492, //CJK UNIFIED IDEOGRAPH - 0x99EF: 0x547B, //CJK UNIFIED IDEOGRAPH - 0x99F0: 0x5480, //CJK UNIFIED IDEOGRAPH - 0x99F1: 0x5476, //CJK UNIFIED IDEOGRAPH - 0x99F2: 0x5484, //CJK UNIFIED IDEOGRAPH - 0x99F3: 0x5490, //CJK UNIFIED IDEOGRAPH - 0x99F4: 0x5486, //CJK UNIFIED IDEOGRAPH - 0x99F5: 0x54C7, //CJK UNIFIED IDEOGRAPH - 0x99F6: 0x54A2, //CJK UNIFIED IDEOGRAPH - 0x99F7: 0x54B8, //CJK UNIFIED IDEOGRAPH - 0x99F8: 0x54A5, //CJK UNIFIED IDEOGRAPH - 0x99F9: 0x54AC, //CJK UNIFIED IDEOGRAPH - 0x99FA: 0x54C4, //CJK UNIFIED IDEOGRAPH - 0x99FB: 0x54C8, //CJK UNIFIED IDEOGRAPH - 0x99FC: 0x54A8, //CJK UNIFIED IDEOGRAPH - 0x9A40: 0x54AB, //CJK UNIFIED IDEOGRAPH - 0x9A41: 0x54C2, //CJK UNIFIED IDEOGRAPH - 0x9A42: 0x54A4, //CJK UNIFIED IDEOGRAPH - 0x9A43: 0x54BE, //CJK UNIFIED IDEOGRAPH - 0x9A44: 0x54BC, //CJK UNIFIED IDEOGRAPH - 0x9A45: 0x54D8, //CJK UNIFIED IDEOGRAPH - 0x9A46: 0x54E5, //CJK UNIFIED IDEOGRAPH - 0x9A47: 0x54E6, //CJK UNIFIED IDEOGRAPH - 0x9A48: 0x550F, //CJK UNIFIED IDEOGRAPH - 0x9A49: 0x5514, //CJK UNIFIED IDEOGRAPH - 0x9A4A: 0x54FD, //CJK UNIFIED IDEOGRAPH - 0x9A4B: 0x54EE, //CJK UNIFIED IDEOGRAPH - 0x9A4C: 0x54ED, //CJK UNIFIED IDEOGRAPH - 0x9A4D: 0x54FA, //CJK UNIFIED IDEOGRAPH - 0x9A4E: 0x54E2, //CJK UNIFIED IDEOGRAPH - 0x9A4F: 0x5539, //CJK UNIFIED IDEOGRAPH - 0x9A50: 0x5540, //CJK UNIFIED IDEOGRAPH - 0x9A51: 0x5563, //CJK UNIFIED IDEOGRAPH - 0x9A52: 0x554C, //CJK UNIFIED IDEOGRAPH - 0x9A53: 0x552E, //CJK UNIFIED IDEOGRAPH - 0x9A54: 0x555C, //CJK UNIFIED IDEOGRAPH - 0x9A55: 0x5545, //CJK UNIFIED IDEOGRAPH - 0x9A56: 0x5556, //CJK UNIFIED IDEOGRAPH - 0x9A57: 0x5557, //CJK UNIFIED IDEOGRAPH - 0x9A58: 0x5538, //CJK UNIFIED IDEOGRAPH - 0x9A59: 0x5533, //CJK UNIFIED IDEOGRAPH - 0x9A5A: 0x555D, //CJK UNIFIED IDEOGRAPH - 0x9A5B: 0x5599, //CJK UNIFIED IDEOGRAPH - 0x9A5C: 0x5580, //CJK UNIFIED IDEOGRAPH - 0x9A5D: 0x54AF, //CJK UNIFIED IDEOGRAPH - 0x9A5E: 0x558A, //CJK UNIFIED IDEOGRAPH - 0x9A5F: 0x559F, //CJK UNIFIED IDEOGRAPH - 0x9A60: 0x557B, //CJK UNIFIED IDEOGRAPH - 0x9A61: 0x557E, //CJK UNIFIED IDEOGRAPH - 0x9A62: 0x5598, //CJK UNIFIED IDEOGRAPH - 0x9A63: 0x559E, //CJK UNIFIED IDEOGRAPH - 0x9A64: 0x55AE, //CJK UNIFIED IDEOGRAPH - 0x9A65: 0x557C, //CJK UNIFIED IDEOGRAPH - 0x9A66: 0x5583, //CJK UNIFIED IDEOGRAPH - 0x9A67: 0x55A9, //CJK UNIFIED IDEOGRAPH - 0x9A68: 0x5587, //CJK UNIFIED IDEOGRAPH - 0x9A69: 0x55A8, //CJK UNIFIED IDEOGRAPH - 0x9A6A: 0x55DA, //CJK UNIFIED IDEOGRAPH - 0x9A6B: 0x55C5, //CJK UNIFIED IDEOGRAPH - 0x9A6C: 0x55DF, //CJK UNIFIED IDEOGRAPH - 0x9A6D: 0x55C4, //CJK UNIFIED IDEOGRAPH - 0x9A6E: 0x55DC, //CJK UNIFIED IDEOGRAPH - 0x9A6F: 0x55E4, //CJK UNIFIED IDEOGRAPH - 0x9A70: 0x55D4, //CJK UNIFIED IDEOGRAPH - 0x9A71: 0x5614, //CJK UNIFIED IDEOGRAPH - 0x9A72: 0x55F7, //CJK UNIFIED IDEOGRAPH - 0x9A73: 0x5616, //CJK UNIFIED IDEOGRAPH - 0x9A74: 0x55FE, //CJK UNIFIED IDEOGRAPH - 0x9A75: 0x55FD, //CJK UNIFIED IDEOGRAPH - 0x9A76: 0x561B, //CJK UNIFIED IDEOGRAPH - 0x9A77: 0x55F9, //CJK UNIFIED IDEOGRAPH - 0x9A78: 0x564E, //CJK UNIFIED IDEOGRAPH - 0x9A79: 0x5650, //CJK UNIFIED IDEOGRAPH - 0x9A7A: 0x71DF, //CJK UNIFIED IDEOGRAPH - 0x9A7B: 0x5634, //CJK UNIFIED IDEOGRAPH - 0x9A7C: 0x5636, //CJK UNIFIED IDEOGRAPH - 0x9A7D: 0x5632, //CJK UNIFIED IDEOGRAPH - 0x9A7E: 0x5638, //CJK UNIFIED IDEOGRAPH - 0x9A80: 0x566B, //CJK UNIFIED IDEOGRAPH - 0x9A81: 0x5664, //CJK UNIFIED IDEOGRAPH - 0x9A82: 0x562F, //CJK UNIFIED IDEOGRAPH - 0x9A83: 0x566C, //CJK UNIFIED IDEOGRAPH - 0x9A84: 0x566A, //CJK UNIFIED IDEOGRAPH - 0x9A85: 0x5686, //CJK UNIFIED IDEOGRAPH - 0x9A86: 0x5680, //CJK UNIFIED IDEOGRAPH - 0x9A87: 0x568A, //CJK UNIFIED IDEOGRAPH - 0x9A88: 0x56A0, //CJK UNIFIED IDEOGRAPH - 0x9A89: 0x5694, //CJK UNIFIED IDEOGRAPH - 0x9A8A: 0x568F, //CJK UNIFIED IDEOGRAPH - 0x9A8B: 0x56A5, //CJK UNIFIED IDEOGRAPH - 0x9A8C: 0x56AE, //CJK UNIFIED IDEOGRAPH - 0x9A8D: 0x56B6, //CJK UNIFIED IDEOGRAPH - 0x9A8E: 0x56B4, //CJK UNIFIED IDEOGRAPH - 0x9A8F: 0x56C2, //CJK UNIFIED IDEOGRAPH - 0x9A90: 0x56BC, //CJK UNIFIED IDEOGRAPH - 0x9A91: 0x56C1, //CJK UNIFIED IDEOGRAPH - 0x9A92: 0x56C3, //CJK UNIFIED IDEOGRAPH - 0x9A93: 0x56C0, //CJK UNIFIED IDEOGRAPH - 0x9A94: 0x56C8, //CJK UNIFIED IDEOGRAPH - 0x9A95: 0x56CE, //CJK UNIFIED IDEOGRAPH - 0x9A96: 0x56D1, //CJK UNIFIED IDEOGRAPH - 0x9A97: 0x56D3, //CJK UNIFIED IDEOGRAPH - 0x9A98: 0x56D7, //CJK UNIFIED IDEOGRAPH - 0x9A99: 0x56EE, //CJK UNIFIED IDEOGRAPH - 0x9A9A: 0x56F9, //CJK UNIFIED IDEOGRAPH - 0x9A9B: 0x5700, //CJK UNIFIED IDEOGRAPH - 0x9A9C: 0x56FF, //CJK UNIFIED IDEOGRAPH - 0x9A9D: 0x5704, //CJK UNIFIED IDEOGRAPH - 0x9A9E: 0x5709, //CJK UNIFIED IDEOGRAPH - 0x9A9F: 0x5708, //CJK UNIFIED IDEOGRAPH - 0x9AA0: 0x570B, //CJK UNIFIED IDEOGRAPH - 0x9AA1: 0x570D, //CJK UNIFIED IDEOGRAPH - 0x9AA2: 0x5713, //CJK UNIFIED IDEOGRAPH - 0x9AA3: 0x5718, //CJK UNIFIED IDEOGRAPH - 0x9AA4: 0x5716, //CJK UNIFIED IDEOGRAPH - 0x9AA5: 0x55C7, //CJK UNIFIED IDEOGRAPH - 0x9AA6: 0x571C, //CJK UNIFIED IDEOGRAPH - 0x9AA7: 0x5726, //CJK UNIFIED IDEOGRAPH - 0x9AA8: 0x5737, //CJK UNIFIED IDEOGRAPH - 0x9AA9: 0x5738, //CJK UNIFIED IDEOGRAPH - 0x9AAA: 0x574E, //CJK UNIFIED IDEOGRAPH - 0x9AAB: 0x573B, //CJK UNIFIED IDEOGRAPH - 0x9AAC: 0x5740, //CJK UNIFIED IDEOGRAPH - 0x9AAD: 0x574F, //CJK UNIFIED IDEOGRAPH - 0x9AAE: 0x5769, //CJK UNIFIED IDEOGRAPH - 0x9AAF: 0x57C0, //CJK UNIFIED IDEOGRAPH - 0x9AB0: 0x5788, //CJK UNIFIED IDEOGRAPH - 0x9AB1: 0x5761, //CJK UNIFIED IDEOGRAPH - 0x9AB2: 0x577F, //CJK UNIFIED IDEOGRAPH - 0x9AB3: 0x5789, //CJK UNIFIED IDEOGRAPH - 0x9AB4: 0x5793, //CJK UNIFIED IDEOGRAPH - 0x9AB5: 0x57A0, //CJK UNIFIED IDEOGRAPH - 0x9AB6: 0x57B3, //CJK UNIFIED IDEOGRAPH - 0x9AB7: 0x57A4, //CJK UNIFIED IDEOGRAPH - 0x9AB8: 0x57AA, //CJK UNIFIED IDEOGRAPH - 0x9AB9: 0x57B0, //CJK UNIFIED IDEOGRAPH - 0x9ABA: 0x57C3, //CJK UNIFIED IDEOGRAPH - 0x9ABB: 0x57C6, //CJK UNIFIED IDEOGRAPH - 0x9ABC: 0x57D4, //CJK UNIFIED IDEOGRAPH - 0x9ABD: 0x57D2, //CJK UNIFIED IDEOGRAPH - 0x9ABE: 0x57D3, //CJK UNIFIED IDEOGRAPH - 0x9ABF: 0x580A, //CJK UNIFIED IDEOGRAPH - 0x9AC0: 0x57D6, //CJK UNIFIED IDEOGRAPH - 0x9AC1: 0x57E3, //CJK UNIFIED IDEOGRAPH - 0x9AC2: 0x580B, //CJK UNIFIED IDEOGRAPH - 0x9AC3: 0x5819, //CJK UNIFIED IDEOGRAPH - 0x9AC4: 0x581D, //CJK UNIFIED IDEOGRAPH - 0x9AC5: 0x5872, //CJK UNIFIED IDEOGRAPH - 0x9AC6: 0x5821, //CJK UNIFIED IDEOGRAPH - 0x9AC7: 0x5862, //CJK UNIFIED IDEOGRAPH - 0x9AC8: 0x584B, //CJK UNIFIED IDEOGRAPH - 0x9AC9: 0x5870, //CJK UNIFIED IDEOGRAPH - 0x9ACA: 0x6BC0, //CJK UNIFIED IDEOGRAPH - 0x9ACB: 0x5852, //CJK UNIFIED IDEOGRAPH - 0x9ACC: 0x583D, //CJK UNIFIED IDEOGRAPH - 0x9ACD: 0x5879, //CJK UNIFIED IDEOGRAPH - 0x9ACE: 0x5885, //CJK UNIFIED IDEOGRAPH - 0x9ACF: 0x58B9, //CJK UNIFIED IDEOGRAPH - 0x9AD0: 0x589F, //CJK UNIFIED IDEOGRAPH - 0x9AD1: 0x58AB, //CJK UNIFIED IDEOGRAPH - 0x9AD2: 0x58BA, //CJK UNIFIED IDEOGRAPH - 0x9AD3: 0x58DE, //CJK UNIFIED IDEOGRAPH - 0x9AD4: 0x58BB, //CJK UNIFIED IDEOGRAPH - 0x9AD5: 0x58B8, //CJK UNIFIED IDEOGRAPH - 0x9AD6: 0x58AE, //CJK UNIFIED IDEOGRAPH - 0x9AD7: 0x58C5, //CJK UNIFIED IDEOGRAPH - 0x9AD8: 0x58D3, //CJK UNIFIED IDEOGRAPH - 0x9AD9: 0x58D1, //CJK UNIFIED IDEOGRAPH - 0x9ADA: 0x58D7, //CJK UNIFIED IDEOGRAPH - 0x9ADB: 0x58D9, //CJK UNIFIED IDEOGRAPH - 0x9ADC: 0x58D8, //CJK UNIFIED IDEOGRAPH - 0x9ADD: 0x58E5, //CJK UNIFIED IDEOGRAPH - 0x9ADE: 0x58DC, //CJK UNIFIED IDEOGRAPH - 0x9ADF: 0x58E4, //CJK UNIFIED IDEOGRAPH - 0x9AE0: 0x58DF, //CJK UNIFIED IDEOGRAPH - 0x9AE1: 0x58EF, //CJK UNIFIED IDEOGRAPH - 0x9AE2: 0x58FA, //CJK UNIFIED IDEOGRAPH - 0x9AE3: 0x58F9, //CJK UNIFIED IDEOGRAPH - 0x9AE4: 0x58FB, //CJK UNIFIED IDEOGRAPH - 0x9AE5: 0x58FC, //CJK UNIFIED IDEOGRAPH - 0x9AE6: 0x58FD, //CJK UNIFIED IDEOGRAPH - 0x9AE7: 0x5902, //CJK UNIFIED IDEOGRAPH - 0x9AE8: 0x590A, //CJK UNIFIED IDEOGRAPH - 0x9AE9: 0x5910, //CJK UNIFIED IDEOGRAPH - 0x9AEA: 0x591B, //CJK UNIFIED IDEOGRAPH - 0x9AEB: 0x68A6, //CJK UNIFIED IDEOGRAPH - 0x9AEC: 0x5925, //CJK UNIFIED IDEOGRAPH - 0x9AED: 0x592C, //CJK UNIFIED IDEOGRAPH - 0x9AEE: 0x592D, //CJK UNIFIED IDEOGRAPH - 0x9AEF: 0x5932, //CJK UNIFIED IDEOGRAPH - 0x9AF0: 0x5938, //CJK UNIFIED IDEOGRAPH - 0x9AF1: 0x593E, //CJK UNIFIED IDEOGRAPH - 0x9AF2: 0x7AD2, //CJK UNIFIED IDEOGRAPH - 0x9AF3: 0x5955, //CJK UNIFIED IDEOGRAPH - 0x9AF4: 0x5950, //CJK UNIFIED IDEOGRAPH - 0x9AF5: 0x594E, //CJK UNIFIED IDEOGRAPH - 0x9AF6: 0x595A, //CJK UNIFIED IDEOGRAPH - 0x9AF7: 0x5958, //CJK UNIFIED IDEOGRAPH - 0x9AF8: 0x5962, //CJK UNIFIED IDEOGRAPH - 0x9AF9: 0x5960, //CJK UNIFIED IDEOGRAPH - 0x9AFA: 0x5967, //CJK UNIFIED IDEOGRAPH - 0x9AFB: 0x596C, //CJK UNIFIED IDEOGRAPH - 0x9AFC: 0x5969, //CJK UNIFIED IDEOGRAPH - 0x9B40: 0x5978, //CJK UNIFIED IDEOGRAPH - 0x9B41: 0x5981, //CJK UNIFIED IDEOGRAPH - 0x9B42: 0x599D, //CJK UNIFIED IDEOGRAPH - 0x9B43: 0x4F5E, //CJK UNIFIED IDEOGRAPH - 0x9B44: 0x4FAB, //CJK UNIFIED IDEOGRAPH - 0x9B45: 0x59A3, //CJK UNIFIED IDEOGRAPH - 0x9B46: 0x59B2, //CJK UNIFIED IDEOGRAPH - 0x9B47: 0x59C6, //CJK UNIFIED IDEOGRAPH - 0x9B48: 0x59E8, //CJK UNIFIED IDEOGRAPH - 0x9B49: 0x59DC, //CJK UNIFIED IDEOGRAPH - 0x9B4A: 0x598D, //CJK UNIFIED IDEOGRAPH - 0x9B4B: 0x59D9, //CJK UNIFIED IDEOGRAPH - 0x9B4C: 0x59DA, //CJK UNIFIED IDEOGRAPH - 0x9B4D: 0x5A25, //CJK UNIFIED IDEOGRAPH - 0x9B4E: 0x5A1F, //CJK UNIFIED IDEOGRAPH - 0x9B4F: 0x5A11, //CJK UNIFIED IDEOGRAPH - 0x9B50: 0x5A1C, //CJK UNIFIED IDEOGRAPH - 0x9B51: 0x5A09, //CJK UNIFIED IDEOGRAPH - 0x9B52: 0x5A1A, //CJK UNIFIED IDEOGRAPH - 0x9B53: 0x5A40, //CJK UNIFIED IDEOGRAPH - 0x9B54: 0x5A6C, //CJK UNIFIED IDEOGRAPH - 0x9B55: 0x5A49, //CJK UNIFIED IDEOGRAPH - 0x9B56: 0x5A35, //CJK UNIFIED IDEOGRAPH - 0x9B57: 0x5A36, //CJK UNIFIED IDEOGRAPH - 0x9B58: 0x5A62, //CJK UNIFIED IDEOGRAPH - 0x9B59: 0x5A6A, //CJK UNIFIED IDEOGRAPH - 0x9B5A: 0x5A9A, //CJK UNIFIED IDEOGRAPH - 0x9B5B: 0x5ABC, //CJK UNIFIED IDEOGRAPH - 0x9B5C: 0x5ABE, //CJK UNIFIED IDEOGRAPH - 0x9B5D: 0x5ACB, //CJK UNIFIED IDEOGRAPH - 0x9B5E: 0x5AC2, //CJK UNIFIED IDEOGRAPH - 0x9B5F: 0x5ABD, //CJK UNIFIED IDEOGRAPH - 0x9B60: 0x5AE3, //CJK UNIFIED IDEOGRAPH - 0x9B61: 0x5AD7, //CJK UNIFIED IDEOGRAPH - 0x9B62: 0x5AE6, //CJK UNIFIED IDEOGRAPH - 0x9B63: 0x5AE9, //CJK UNIFIED IDEOGRAPH - 0x9B64: 0x5AD6, //CJK UNIFIED IDEOGRAPH - 0x9B65: 0x5AFA, //CJK UNIFIED IDEOGRAPH - 0x9B66: 0x5AFB, //CJK UNIFIED IDEOGRAPH - 0x9B67: 0x5B0C, //CJK UNIFIED IDEOGRAPH - 0x9B68: 0x5B0B, //CJK UNIFIED IDEOGRAPH - 0x9B69: 0x5B16, //CJK UNIFIED IDEOGRAPH - 0x9B6A: 0x5B32, //CJK UNIFIED IDEOGRAPH - 0x9B6B: 0x5AD0, //CJK UNIFIED IDEOGRAPH - 0x9B6C: 0x5B2A, //CJK UNIFIED IDEOGRAPH - 0x9B6D: 0x5B36, //CJK UNIFIED IDEOGRAPH - 0x9B6E: 0x5B3E, //CJK UNIFIED IDEOGRAPH - 0x9B6F: 0x5B43, //CJK UNIFIED IDEOGRAPH - 0x9B70: 0x5B45, //CJK UNIFIED IDEOGRAPH - 0x9B71: 0x5B40, //CJK UNIFIED IDEOGRAPH - 0x9B72: 0x5B51, //CJK UNIFIED IDEOGRAPH - 0x9B73: 0x5B55, //CJK UNIFIED IDEOGRAPH - 0x9B74: 0x5B5A, //CJK UNIFIED IDEOGRAPH - 0x9B75: 0x5B5B, //CJK UNIFIED IDEOGRAPH - 0x9B76: 0x5B65, //CJK UNIFIED IDEOGRAPH - 0x9B77: 0x5B69, //CJK UNIFIED IDEOGRAPH - 0x9B78: 0x5B70, //CJK UNIFIED IDEOGRAPH - 0x9B79: 0x5B73, //CJK UNIFIED IDEOGRAPH - 0x9B7A: 0x5B75, //CJK UNIFIED IDEOGRAPH - 0x9B7B: 0x5B78, //CJK UNIFIED IDEOGRAPH - 0x9B7C: 0x6588, //CJK UNIFIED IDEOGRAPH - 0x9B7D: 0x5B7A, //CJK UNIFIED IDEOGRAPH - 0x9B7E: 0x5B80, //CJK UNIFIED IDEOGRAPH - 0x9B80: 0x5B83, //CJK UNIFIED IDEOGRAPH - 0x9B81: 0x5BA6, //CJK UNIFIED IDEOGRAPH - 0x9B82: 0x5BB8, //CJK UNIFIED IDEOGRAPH - 0x9B83: 0x5BC3, //CJK UNIFIED IDEOGRAPH - 0x9B84: 0x5BC7, //CJK UNIFIED IDEOGRAPH - 0x9B85: 0x5BC9, //CJK UNIFIED IDEOGRAPH - 0x9B86: 0x5BD4, //CJK UNIFIED IDEOGRAPH - 0x9B87: 0x5BD0, //CJK UNIFIED IDEOGRAPH - 0x9B88: 0x5BE4, //CJK UNIFIED IDEOGRAPH - 0x9B89: 0x5BE6, //CJK UNIFIED IDEOGRAPH - 0x9B8A: 0x5BE2, //CJK UNIFIED IDEOGRAPH - 0x9B8B: 0x5BDE, //CJK UNIFIED IDEOGRAPH - 0x9B8C: 0x5BE5, //CJK UNIFIED IDEOGRAPH - 0x9B8D: 0x5BEB, //CJK UNIFIED IDEOGRAPH - 0x9B8E: 0x5BF0, //CJK UNIFIED IDEOGRAPH - 0x9B8F: 0x5BF6, //CJK UNIFIED IDEOGRAPH - 0x9B90: 0x5BF3, //CJK UNIFIED IDEOGRAPH - 0x9B91: 0x5C05, //CJK UNIFIED IDEOGRAPH - 0x9B92: 0x5C07, //CJK UNIFIED IDEOGRAPH - 0x9B93: 0x5C08, //CJK UNIFIED IDEOGRAPH - 0x9B94: 0x5C0D, //CJK UNIFIED IDEOGRAPH - 0x9B95: 0x5C13, //CJK UNIFIED IDEOGRAPH - 0x9B96: 0x5C20, //CJK UNIFIED IDEOGRAPH - 0x9B97: 0x5C22, //CJK UNIFIED IDEOGRAPH - 0x9B98: 0x5C28, //CJK UNIFIED IDEOGRAPH - 0x9B99: 0x5C38, //CJK UNIFIED IDEOGRAPH - 0x9B9A: 0x5C39, //CJK UNIFIED IDEOGRAPH - 0x9B9B: 0x5C41, //CJK UNIFIED IDEOGRAPH - 0x9B9C: 0x5C46, //CJK UNIFIED IDEOGRAPH - 0x9B9D: 0x5C4E, //CJK UNIFIED IDEOGRAPH - 0x9B9E: 0x5C53, //CJK UNIFIED IDEOGRAPH - 0x9B9F: 0x5C50, //CJK UNIFIED IDEOGRAPH - 0x9BA0: 0x5C4F, //CJK UNIFIED IDEOGRAPH - 0x9BA1: 0x5B71, //CJK UNIFIED IDEOGRAPH - 0x9BA2: 0x5C6C, //CJK UNIFIED IDEOGRAPH - 0x9BA3: 0x5C6E, //CJK UNIFIED IDEOGRAPH - 0x9BA4: 0x4E62, //CJK UNIFIED IDEOGRAPH - 0x9BA5: 0x5C76, //CJK UNIFIED IDEOGRAPH - 0x9BA6: 0x5C79, //CJK UNIFIED IDEOGRAPH - 0x9BA7: 0x5C8C, //CJK UNIFIED IDEOGRAPH - 0x9BA8: 0x5C91, //CJK UNIFIED IDEOGRAPH - 0x9BA9: 0x5C94, //CJK UNIFIED IDEOGRAPH - 0x9BAA: 0x599B, //CJK UNIFIED IDEOGRAPH - 0x9BAB: 0x5CAB, //CJK UNIFIED IDEOGRAPH - 0x9BAC: 0x5CBB, //CJK UNIFIED IDEOGRAPH - 0x9BAD: 0x5CB6, //CJK UNIFIED IDEOGRAPH - 0x9BAE: 0x5CBC, //CJK UNIFIED IDEOGRAPH - 0x9BAF: 0x5CB7, //CJK UNIFIED IDEOGRAPH - 0x9BB0: 0x5CC5, //CJK UNIFIED IDEOGRAPH - 0x9BB1: 0x5CBE, //CJK UNIFIED IDEOGRAPH - 0x9BB2: 0x5CC7, //CJK UNIFIED IDEOGRAPH - 0x9BB3: 0x5CD9, //CJK UNIFIED IDEOGRAPH - 0x9BB4: 0x5CE9, //CJK UNIFIED IDEOGRAPH - 0x9BB5: 0x5CFD, //CJK UNIFIED IDEOGRAPH - 0x9BB6: 0x5CFA, //CJK UNIFIED IDEOGRAPH - 0x9BB7: 0x5CED, //CJK UNIFIED IDEOGRAPH - 0x9BB8: 0x5D8C, //CJK UNIFIED IDEOGRAPH - 0x9BB9: 0x5CEA, //CJK UNIFIED IDEOGRAPH - 0x9BBA: 0x5D0B, //CJK UNIFIED IDEOGRAPH - 0x9BBB: 0x5D15, //CJK UNIFIED IDEOGRAPH - 0x9BBC: 0x5D17, //CJK UNIFIED IDEOGRAPH - 0x9BBD: 0x5D5C, //CJK UNIFIED IDEOGRAPH - 0x9BBE: 0x5D1F, //CJK UNIFIED IDEOGRAPH - 0x9BBF: 0x5D1B, //CJK UNIFIED IDEOGRAPH - 0x9BC0: 0x5D11, //CJK UNIFIED IDEOGRAPH - 0x9BC1: 0x5D14, //CJK UNIFIED IDEOGRAPH - 0x9BC2: 0x5D22, //CJK UNIFIED IDEOGRAPH - 0x9BC3: 0x5D1A, //CJK UNIFIED IDEOGRAPH - 0x9BC4: 0x5D19, //CJK UNIFIED IDEOGRAPH - 0x9BC5: 0x5D18, //CJK UNIFIED IDEOGRAPH - 0x9BC6: 0x5D4C, //CJK UNIFIED IDEOGRAPH - 0x9BC7: 0x5D52, //CJK UNIFIED IDEOGRAPH - 0x9BC8: 0x5D4E, //CJK UNIFIED IDEOGRAPH - 0x9BC9: 0x5D4B, //CJK UNIFIED IDEOGRAPH - 0x9BCA: 0x5D6C, //CJK UNIFIED IDEOGRAPH - 0x9BCB: 0x5D73, //CJK UNIFIED IDEOGRAPH - 0x9BCC: 0x5D76, //CJK UNIFIED IDEOGRAPH - 0x9BCD: 0x5D87, //CJK UNIFIED IDEOGRAPH - 0x9BCE: 0x5D84, //CJK UNIFIED IDEOGRAPH - 0x9BCF: 0x5D82, //CJK UNIFIED IDEOGRAPH - 0x9BD0: 0x5DA2, //CJK UNIFIED IDEOGRAPH - 0x9BD1: 0x5D9D, //CJK UNIFIED IDEOGRAPH - 0x9BD2: 0x5DAC, //CJK UNIFIED IDEOGRAPH - 0x9BD3: 0x5DAE, //CJK UNIFIED IDEOGRAPH - 0x9BD4: 0x5DBD, //CJK UNIFIED IDEOGRAPH - 0x9BD5: 0x5D90, //CJK UNIFIED IDEOGRAPH - 0x9BD6: 0x5DB7, //CJK UNIFIED IDEOGRAPH - 0x9BD7: 0x5DBC, //CJK UNIFIED IDEOGRAPH - 0x9BD8: 0x5DC9, //CJK UNIFIED IDEOGRAPH - 0x9BD9: 0x5DCD, //CJK UNIFIED IDEOGRAPH - 0x9BDA: 0x5DD3, //CJK UNIFIED IDEOGRAPH - 0x9BDB: 0x5DD2, //CJK UNIFIED IDEOGRAPH - 0x9BDC: 0x5DD6, //CJK UNIFIED IDEOGRAPH - 0x9BDD: 0x5DDB, //CJK UNIFIED IDEOGRAPH - 0x9BDE: 0x5DEB, //CJK UNIFIED IDEOGRAPH - 0x9BDF: 0x5DF2, //CJK UNIFIED IDEOGRAPH - 0x9BE0: 0x5DF5, //CJK UNIFIED IDEOGRAPH - 0x9BE1: 0x5E0B, //CJK UNIFIED IDEOGRAPH - 0x9BE2: 0x5E1A, //CJK UNIFIED IDEOGRAPH - 0x9BE3: 0x5E19, //CJK UNIFIED IDEOGRAPH - 0x9BE4: 0x5E11, //CJK UNIFIED IDEOGRAPH - 0x9BE5: 0x5E1B, //CJK UNIFIED IDEOGRAPH - 0x9BE6: 0x5E36, //CJK UNIFIED IDEOGRAPH - 0x9BE7: 0x5E37, //CJK UNIFIED IDEOGRAPH - 0x9BE8: 0x5E44, //CJK UNIFIED IDEOGRAPH - 0x9BE9: 0x5E43, //CJK UNIFIED IDEOGRAPH - 0x9BEA: 0x5E40, //CJK UNIFIED IDEOGRAPH - 0x9BEB: 0x5E4E, //CJK UNIFIED IDEOGRAPH - 0x9BEC: 0x5E57, //CJK UNIFIED IDEOGRAPH - 0x9BED: 0x5E54, //CJK UNIFIED IDEOGRAPH - 0x9BEE: 0x5E5F, //CJK UNIFIED IDEOGRAPH - 0x9BEF: 0x5E62, //CJK UNIFIED IDEOGRAPH - 0x9BF0: 0x5E64, //CJK UNIFIED IDEOGRAPH - 0x9BF1: 0x5E47, //CJK UNIFIED IDEOGRAPH - 0x9BF2: 0x5E75, //CJK UNIFIED IDEOGRAPH - 0x9BF3: 0x5E76, //CJK UNIFIED IDEOGRAPH - 0x9BF4: 0x5E7A, //CJK UNIFIED IDEOGRAPH - 0x9BF5: 0x9EBC, //CJK UNIFIED IDEOGRAPH - 0x9BF6: 0x5E7F, //CJK UNIFIED IDEOGRAPH - 0x9BF7: 0x5EA0, //CJK UNIFIED IDEOGRAPH - 0x9BF8: 0x5EC1, //CJK UNIFIED IDEOGRAPH - 0x9BF9: 0x5EC2, //CJK UNIFIED IDEOGRAPH - 0x9BFA: 0x5EC8, //CJK UNIFIED IDEOGRAPH - 0x9BFB: 0x5ED0, //CJK UNIFIED IDEOGRAPH - 0x9BFC: 0x5ECF, //CJK UNIFIED IDEOGRAPH - 0x9C40: 0x5ED6, //CJK UNIFIED IDEOGRAPH - 0x9C41: 0x5EE3, //CJK UNIFIED IDEOGRAPH - 0x9C42: 0x5EDD, //CJK UNIFIED IDEOGRAPH - 0x9C43: 0x5EDA, //CJK UNIFIED IDEOGRAPH - 0x9C44: 0x5EDB, //CJK UNIFIED IDEOGRAPH - 0x9C45: 0x5EE2, //CJK UNIFIED IDEOGRAPH - 0x9C46: 0x5EE1, //CJK UNIFIED IDEOGRAPH - 0x9C47: 0x5EE8, //CJK UNIFIED IDEOGRAPH - 0x9C48: 0x5EE9, //CJK UNIFIED IDEOGRAPH - 0x9C49: 0x5EEC, //CJK UNIFIED IDEOGRAPH - 0x9C4A: 0x5EF1, //CJK UNIFIED IDEOGRAPH - 0x9C4B: 0x5EF3, //CJK UNIFIED IDEOGRAPH - 0x9C4C: 0x5EF0, //CJK UNIFIED IDEOGRAPH - 0x9C4D: 0x5EF4, //CJK UNIFIED IDEOGRAPH - 0x9C4E: 0x5EF8, //CJK UNIFIED IDEOGRAPH - 0x9C4F: 0x5EFE, //CJK UNIFIED IDEOGRAPH - 0x9C50: 0x5F03, //CJK UNIFIED IDEOGRAPH - 0x9C51: 0x5F09, //CJK UNIFIED IDEOGRAPH - 0x9C52: 0x5F5D, //CJK UNIFIED IDEOGRAPH - 0x9C53: 0x5F5C, //CJK UNIFIED IDEOGRAPH - 0x9C54: 0x5F0B, //CJK UNIFIED IDEOGRAPH - 0x9C55: 0x5F11, //CJK UNIFIED IDEOGRAPH - 0x9C56: 0x5F16, //CJK UNIFIED IDEOGRAPH - 0x9C57: 0x5F29, //CJK UNIFIED IDEOGRAPH - 0x9C58: 0x5F2D, //CJK UNIFIED IDEOGRAPH - 0x9C59: 0x5F38, //CJK UNIFIED IDEOGRAPH - 0x9C5A: 0x5F41, //CJK UNIFIED IDEOGRAPH - 0x9C5B: 0x5F48, //CJK UNIFIED IDEOGRAPH - 0x9C5C: 0x5F4C, //CJK UNIFIED IDEOGRAPH - 0x9C5D: 0x5F4E, //CJK UNIFIED IDEOGRAPH - 0x9C5E: 0x5F2F, //CJK UNIFIED IDEOGRAPH - 0x9C5F: 0x5F51, //CJK UNIFIED IDEOGRAPH - 0x9C60: 0x5F56, //CJK UNIFIED IDEOGRAPH - 0x9C61: 0x5F57, //CJK UNIFIED IDEOGRAPH - 0x9C62: 0x5F59, //CJK UNIFIED IDEOGRAPH - 0x9C63: 0x5F61, //CJK UNIFIED IDEOGRAPH - 0x9C64: 0x5F6D, //CJK UNIFIED IDEOGRAPH - 0x9C65: 0x5F73, //CJK UNIFIED IDEOGRAPH - 0x9C66: 0x5F77, //CJK UNIFIED IDEOGRAPH - 0x9C67: 0x5F83, //CJK UNIFIED IDEOGRAPH - 0x9C68: 0x5F82, //CJK UNIFIED IDEOGRAPH - 0x9C69: 0x5F7F, //CJK UNIFIED IDEOGRAPH - 0x9C6A: 0x5F8A, //CJK UNIFIED IDEOGRAPH - 0x9C6B: 0x5F88, //CJK UNIFIED IDEOGRAPH - 0x9C6C: 0x5F91, //CJK UNIFIED IDEOGRAPH - 0x9C6D: 0x5F87, //CJK UNIFIED IDEOGRAPH - 0x9C6E: 0x5F9E, //CJK UNIFIED IDEOGRAPH - 0x9C6F: 0x5F99, //CJK UNIFIED IDEOGRAPH - 0x9C70: 0x5F98, //CJK UNIFIED IDEOGRAPH - 0x9C71: 0x5FA0, //CJK UNIFIED IDEOGRAPH - 0x9C72: 0x5FA8, //CJK UNIFIED IDEOGRAPH - 0x9C73: 0x5FAD, //CJK UNIFIED IDEOGRAPH - 0x9C74: 0x5FBC, //CJK UNIFIED IDEOGRAPH - 0x9C75: 0x5FD6, //CJK UNIFIED IDEOGRAPH - 0x9C76: 0x5FFB, //CJK UNIFIED IDEOGRAPH - 0x9C77: 0x5FE4, //CJK UNIFIED IDEOGRAPH - 0x9C78: 0x5FF8, //CJK UNIFIED IDEOGRAPH - 0x9C79: 0x5FF1, //CJK UNIFIED IDEOGRAPH - 0x9C7A: 0x5FDD, //CJK UNIFIED IDEOGRAPH - 0x9C7B: 0x60B3, //CJK UNIFIED IDEOGRAPH - 0x9C7C: 0x5FFF, //CJK UNIFIED IDEOGRAPH - 0x9C7D: 0x6021, //CJK UNIFIED IDEOGRAPH - 0x9C7E: 0x6060, //CJK UNIFIED IDEOGRAPH - 0x9C80: 0x6019, //CJK UNIFIED IDEOGRAPH - 0x9C81: 0x6010, //CJK UNIFIED IDEOGRAPH - 0x9C82: 0x6029, //CJK UNIFIED IDEOGRAPH - 0x9C83: 0x600E, //CJK UNIFIED IDEOGRAPH - 0x9C84: 0x6031, //CJK UNIFIED IDEOGRAPH - 0x9C85: 0x601B, //CJK UNIFIED IDEOGRAPH - 0x9C86: 0x6015, //CJK UNIFIED IDEOGRAPH - 0x9C87: 0x602B, //CJK UNIFIED IDEOGRAPH - 0x9C88: 0x6026, //CJK UNIFIED IDEOGRAPH - 0x9C89: 0x600F, //CJK UNIFIED IDEOGRAPH - 0x9C8A: 0x603A, //CJK UNIFIED IDEOGRAPH - 0x9C8B: 0x605A, //CJK UNIFIED IDEOGRAPH - 0x9C8C: 0x6041, //CJK UNIFIED IDEOGRAPH - 0x9C8D: 0x606A, //CJK UNIFIED IDEOGRAPH - 0x9C8E: 0x6077, //CJK UNIFIED IDEOGRAPH - 0x9C8F: 0x605F, //CJK UNIFIED IDEOGRAPH - 0x9C90: 0x604A, //CJK UNIFIED IDEOGRAPH - 0x9C91: 0x6046, //CJK UNIFIED IDEOGRAPH - 0x9C92: 0x604D, //CJK UNIFIED IDEOGRAPH - 0x9C93: 0x6063, //CJK UNIFIED IDEOGRAPH - 0x9C94: 0x6043, //CJK UNIFIED IDEOGRAPH - 0x9C95: 0x6064, //CJK UNIFIED IDEOGRAPH - 0x9C96: 0x6042, //CJK UNIFIED IDEOGRAPH - 0x9C97: 0x606C, //CJK UNIFIED IDEOGRAPH - 0x9C98: 0x606B, //CJK UNIFIED IDEOGRAPH - 0x9C99: 0x6059, //CJK UNIFIED IDEOGRAPH - 0x9C9A: 0x6081, //CJK UNIFIED IDEOGRAPH - 0x9C9B: 0x608D, //CJK UNIFIED IDEOGRAPH - 0x9C9C: 0x60E7, //CJK UNIFIED IDEOGRAPH - 0x9C9D: 0x6083, //CJK UNIFIED IDEOGRAPH - 0x9C9E: 0x609A, //CJK UNIFIED IDEOGRAPH - 0x9C9F: 0x6084, //CJK UNIFIED IDEOGRAPH - 0x9CA0: 0x609B, //CJK UNIFIED IDEOGRAPH - 0x9CA1: 0x6096, //CJK UNIFIED IDEOGRAPH - 0x9CA2: 0x6097, //CJK UNIFIED IDEOGRAPH - 0x9CA3: 0x6092, //CJK UNIFIED IDEOGRAPH - 0x9CA4: 0x60A7, //CJK UNIFIED IDEOGRAPH - 0x9CA5: 0x608B, //CJK UNIFIED IDEOGRAPH - 0x9CA6: 0x60E1, //CJK UNIFIED IDEOGRAPH - 0x9CA7: 0x60B8, //CJK UNIFIED IDEOGRAPH - 0x9CA8: 0x60E0, //CJK UNIFIED IDEOGRAPH - 0x9CA9: 0x60D3, //CJK UNIFIED IDEOGRAPH - 0x9CAA: 0x60B4, //CJK UNIFIED IDEOGRAPH - 0x9CAB: 0x5FF0, //CJK UNIFIED IDEOGRAPH - 0x9CAC: 0x60BD, //CJK UNIFIED IDEOGRAPH - 0x9CAD: 0x60C6, //CJK UNIFIED IDEOGRAPH - 0x9CAE: 0x60B5, //CJK UNIFIED IDEOGRAPH - 0x9CAF: 0x60D8, //CJK UNIFIED IDEOGRAPH - 0x9CB0: 0x614D, //CJK UNIFIED IDEOGRAPH - 0x9CB1: 0x6115, //CJK UNIFIED IDEOGRAPH - 0x9CB2: 0x6106, //CJK UNIFIED IDEOGRAPH - 0x9CB3: 0x60F6, //CJK UNIFIED IDEOGRAPH - 0x9CB4: 0x60F7, //CJK UNIFIED IDEOGRAPH - 0x9CB5: 0x6100, //CJK UNIFIED IDEOGRAPH - 0x9CB6: 0x60F4, //CJK UNIFIED IDEOGRAPH - 0x9CB7: 0x60FA, //CJK UNIFIED IDEOGRAPH - 0x9CB8: 0x6103, //CJK UNIFIED IDEOGRAPH - 0x9CB9: 0x6121, //CJK UNIFIED IDEOGRAPH - 0x9CBA: 0x60FB, //CJK UNIFIED IDEOGRAPH - 0x9CBB: 0x60F1, //CJK UNIFIED IDEOGRAPH - 0x9CBC: 0x610D, //CJK UNIFIED IDEOGRAPH - 0x9CBD: 0x610E, //CJK UNIFIED IDEOGRAPH - 0x9CBE: 0x6147, //CJK UNIFIED IDEOGRAPH - 0x9CBF: 0x613E, //CJK UNIFIED IDEOGRAPH - 0x9CC0: 0x6128, //CJK UNIFIED IDEOGRAPH - 0x9CC1: 0x6127, //CJK UNIFIED IDEOGRAPH - 0x9CC2: 0x614A, //CJK UNIFIED IDEOGRAPH - 0x9CC3: 0x613F, //CJK UNIFIED IDEOGRAPH - 0x9CC4: 0x613C, //CJK UNIFIED IDEOGRAPH - 0x9CC5: 0x612C, //CJK UNIFIED IDEOGRAPH - 0x9CC6: 0x6134, //CJK UNIFIED IDEOGRAPH - 0x9CC7: 0x613D, //CJK UNIFIED IDEOGRAPH - 0x9CC8: 0x6142, //CJK UNIFIED IDEOGRAPH - 0x9CC9: 0x6144, //CJK UNIFIED IDEOGRAPH - 0x9CCA: 0x6173, //CJK UNIFIED IDEOGRAPH - 0x9CCB: 0x6177, //CJK UNIFIED IDEOGRAPH - 0x9CCC: 0x6158, //CJK UNIFIED IDEOGRAPH - 0x9CCD: 0x6159, //CJK UNIFIED IDEOGRAPH - 0x9CCE: 0x615A, //CJK UNIFIED IDEOGRAPH - 0x9CCF: 0x616B, //CJK UNIFIED IDEOGRAPH - 0x9CD0: 0x6174, //CJK UNIFIED IDEOGRAPH - 0x9CD1: 0x616F, //CJK UNIFIED IDEOGRAPH - 0x9CD2: 0x6165, //CJK UNIFIED IDEOGRAPH - 0x9CD3: 0x6171, //CJK UNIFIED IDEOGRAPH - 0x9CD4: 0x615F, //CJK UNIFIED IDEOGRAPH - 0x9CD5: 0x615D, //CJK UNIFIED IDEOGRAPH - 0x9CD6: 0x6153, //CJK UNIFIED IDEOGRAPH - 0x9CD7: 0x6175, //CJK UNIFIED IDEOGRAPH - 0x9CD8: 0x6199, //CJK UNIFIED IDEOGRAPH - 0x9CD9: 0x6196, //CJK UNIFIED IDEOGRAPH - 0x9CDA: 0x6187, //CJK UNIFIED IDEOGRAPH - 0x9CDB: 0x61AC, //CJK UNIFIED IDEOGRAPH - 0x9CDC: 0x6194, //CJK UNIFIED IDEOGRAPH - 0x9CDD: 0x619A, //CJK UNIFIED IDEOGRAPH - 0x9CDE: 0x618A, //CJK UNIFIED IDEOGRAPH - 0x9CDF: 0x6191, //CJK UNIFIED IDEOGRAPH - 0x9CE0: 0x61AB, //CJK UNIFIED IDEOGRAPH - 0x9CE1: 0x61AE, //CJK UNIFIED IDEOGRAPH - 0x9CE2: 0x61CC, //CJK UNIFIED IDEOGRAPH - 0x9CE3: 0x61CA, //CJK UNIFIED IDEOGRAPH - 0x9CE4: 0x61C9, //CJK UNIFIED IDEOGRAPH - 0x9CE5: 0x61F7, //CJK UNIFIED IDEOGRAPH - 0x9CE6: 0x61C8, //CJK UNIFIED IDEOGRAPH - 0x9CE7: 0x61C3, //CJK UNIFIED IDEOGRAPH - 0x9CE8: 0x61C6, //CJK UNIFIED IDEOGRAPH - 0x9CE9: 0x61BA, //CJK UNIFIED IDEOGRAPH - 0x9CEA: 0x61CB, //CJK UNIFIED IDEOGRAPH - 0x9CEB: 0x7F79, //CJK UNIFIED IDEOGRAPH - 0x9CEC: 0x61CD, //CJK UNIFIED IDEOGRAPH - 0x9CED: 0x61E6, //CJK UNIFIED IDEOGRAPH - 0x9CEE: 0x61E3, //CJK UNIFIED IDEOGRAPH - 0x9CEF: 0x61F6, //CJK UNIFIED IDEOGRAPH - 0x9CF0: 0x61FA, //CJK UNIFIED IDEOGRAPH - 0x9CF1: 0x61F4, //CJK UNIFIED IDEOGRAPH - 0x9CF2: 0x61FF, //CJK UNIFIED IDEOGRAPH - 0x9CF3: 0x61FD, //CJK UNIFIED IDEOGRAPH - 0x9CF4: 0x61FC, //CJK UNIFIED IDEOGRAPH - 0x9CF5: 0x61FE, //CJK UNIFIED IDEOGRAPH - 0x9CF6: 0x6200, //CJK UNIFIED IDEOGRAPH - 0x9CF7: 0x6208, //CJK UNIFIED IDEOGRAPH - 0x9CF8: 0x6209, //CJK UNIFIED IDEOGRAPH - 0x9CF9: 0x620D, //CJK UNIFIED IDEOGRAPH - 0x9CFA: 0x620C, //CJK UNIFIED IDEOGRAPH - 0x9CFB: 0x6214, //CJK UNIFIED IDEOGRAPH - 0x9CFC: 0x621B, //CJK UNIFIED IDEOGRAPH - 0x9D40: 0x621E, //CJK UNIFIED IDEOGRAPH - 0x9D41: 0x6221, //CJK UNIFIED IDEOGRAPH - 0x9D42: 0x622A, //CJK UNIFIED IDEOGRAPH - 0x9D43: 0x622E, //CJK UNIFIED IDEOGRAPH - 0x9D44: 0x6230, //CJK UNIFIED IDEOGRAPH - 0x9D45: 0x6232, //CJK UNIFIED IDEOGRAPH - 0x9D46: 0x6233, //CJK UNIFIED IDEOGRAPH - 0x9D47: 0x6241, //CJK UNIFIED IDEOGRAPH - 0x9D48: 0x624E, //CJK UNIFIED IDEOGRAPH - 0x9D49: 0x625E, //CJK UNIFIED IDEOGRAPH - 0x9D4A: 0x6263, //CJK UNIFIED IDEOGRAPH - 0x9D4B: 0x625B, //CJK UNIFIED IDEOGRAPH - 0x9D4C: 0x6260, //CJK UNIFIED IDEOGRAPH - 0x9D4D: 0x6268, //CJK UNIFIED IDEOGRAPH - 0x9D4E: 0x627C, //CJK UNIFIED IDEOGRAPH - 0x9D4F: 0x6282, //CJK UNIFIED IDEOGRAPH - 0x9D50: 0x6289, //CJK UNIFIED IDEOGRAPH - 0x9D51: 0x627E, //CJK UNIFIED IDEOGRAPH - 0x9D52: 0x6292, //CJK UNIFIED IDEOGRAPH - 0x9D53: 0x6293, //CJK UNIFIED IDEOGRAPH - 0x9D54: 0x6296, //CJK UNIFIED IDEOGRAPH - 0x9D55: 0x62D4, //CJK UNIFIED IDEOGRAPH - 0x9D56: 0x6283, //CJK UNIFIED IDEOGRAPH - 0x9D57: 0x6294, //CJK UNIFIED IDEOGRAPH - 0x9D58: 0x62D7, //CJK UNIFIED IDEOGRAPH - 0x9D59: 0x62D1, //CJK UNIFIED IDEOGRAPH - 0x9D5A: 0x62BB, //CJK UNIFIED IDEOGRAPH - 0x9D5B: 0x62CF, //CJK UNIFIED IDEOGRAPH - 0x9D5C: 0x62FF, //CJK UNIFIED IDEOGRAPH - 0x9D5D: 0x62C6, //CJK UNIFIED IDEOGRAPH - 0x9D5E: 0x64D4, //CJK UNIFIED IDEOGRAPH - 0x9D5F: 0x62C8, //CJK UNIFIED IDEOGRAPH - 0x9D60: 0x62DC, //CJK UNIFIED IDEOGRAPH - 0x9D61: 0x62CC, //CJK UNIFIED IDEOGRAPH - 0x9D62: 0x62CA, //CJK UNIFIED IDEOGRAPH - 0x9D63: 0x62C2, //CJK UNIFIED IDEOGRAPH - 0x9D64: 0x62C7, //CJK UNIFIED IDEOGRAPH - 0x9D65: 0x629B, //CJK UNIFIED IDEOGRAPH - 0x9D66: 0x62C9, //CJK UNIFIED IDEOGRAPH - 0x9D67: 0x630C, //CJK UNIFIED IDEOGRAPH - 0x9D68: 0x62EE, //CJK UNIFIED IDEOGRAPH - 0x9D69: 0x62F1, //CJK UNIFIED IDEOGRAPH - 0x9D6A: 0x6327, //CJK UNIFIED IDEOGRAPH - 0x9D6B: 0x6302, //CJK UNIFIED IDEOGRAPH - 0x9D6C: 0x6308, //CJK UNIFIED IDEOGRAPH - 0x9D6D: 0x62EF, //CJK UNIFIED IDEOGRAPH - 0x9D6E: 0x62F5, //CJK UNIFIED IDEOGRAPH - 0x9D6F: 0x6350, //CJK UNIFIED IDEOGRAPH - 0x9D70: 0x633E, //CJK UNIFIED IDEOGRAPH - 0x9D71: 0x634D, //CJK UNIFIED IDEOGRAPH - 0x9D72: 0x641C, //CJK UNIFIED IDEOGRAPH - 0x9D73: 0x634F, //CJK UNIFIED IDEOGRAPH - 0x9D74: 0x6396, //CJK UNIFIED IDEOGRAPH - 0x9D75: 0x638E, //CJK UNIFIED IDEOGRAPH - 0x9D76: 0x6380, //CJK UNIFIED IDEOGRAPH - 0x9D77: 0x63AB, //CJK UNIFIED IDEOGRAPH - 0x9D78: 0x6376, //CJK UNIFIED IDEOGRAPH - 0x9D79: 0x63A3, //CJK UNIFIED IDEOGRAPH - 0x9D7A: 0x638F, //CJK UNIFIED IDEOGRAPH - 0x9D7B: 0x6389, //CJK UNIFIED IDEOGRAPH - 0x9D7C: 0x639F, //CJK UNIFIED IDEOGRAPH - 0x9D7D: 0x63B5, //CJK UNIFIED IDEOGRAPH - 0x9D7E: 0x636B, //CJK UNIFIED IDEOGRAPH - 0x9D80: 0x6369, //CJK UNIFIED IDEOGRAPH - 0x9D81: 0x63BE, //CJK UNIFIED IDEOGRAPH - 0x9D82: 0x63E9, //CJK UNIFIED IDEOGRAPH - 0x9D83: 0x63C0, //CJK UNIFIED IDEOGRAPH - 0x9D84: 0x63C6, //CJK UNIFIED IDEOGRAPH - 0x9D85: 0x63E3, //CJK UNIFIED IDEOGRAPH - 0x9D86: 0x63C9, //CJK UNIFIED IDEOGRAPH - 0x9D87: 0x63D2, //CJK UNIFIED IDEOGRAPH - 0x9D88: 0x63F6, //CJK UNIFIED IDEOGRAPH - 0x9D89: 0x63C4, //CJK UNIFIED IDEOGRAPH - 0x9D8A: 0x6416, //CJK UNIFIED IDEOGRAPH - 0x9D8B: 0x6434, //CJK UNIFIED IDEOGRAPH - 0x9D8C: 0x6406, //CJK UNIFIED IDEOGRAPH - 0x9D8D: 0x6413, //CJK UNIFIED IDEOGRAPH - 0x9D8E: 0x6426, //CJK UNIFIED IDEOGRAPH - 0x9D8F: 0x6436, //CJK UNIFIED IDEOGRAPH - 0x9D90: 0x651D, //CJK UNIFIED IDEOGRAPH - 0x9D91: 0x6417, //CJK UNIFIED IDEOGRAPH - 0x9D92: 0x6428, //CJK UNIFIED IDEOGRAPH - 0x9D93: 0x640F, //CJK UNIFIED IDEOGRAPH - 0x9D94: 0x6467, //CJK UNIFIED IDEOGRAPH - 0x9D95: 0x646F, //CJK UNIFIED IDEOGRAPH - 0x9D96: 0x6476, //CJK UNIFIED IDEOGRAPH - 0x9D97: 0x644E, //CJK UNIFIED IDEOGRAPH - 0x9D98: 0x652A, //CJK UNIFIED IDEOGRAPH - 0x9D99: 0x6495, //CJK UNIFIED IDEOGRAPH - 0x9D9A: 0x6493, //CJK UNIFIED IDEOGRAPH - 0x9D9B: 0x64A5, //CJK UNIFIED IDEOGRAPH - 0x9D9C: 0x64A9, //CJK UNIFIED IDEOGRAPH - 0x9D9D: 0x6488, //CJK UNIFIED IDEOGRAPH - 0x9D9E: 0x64BC, //CJK UNIFIED IDEOGRAPH - 0x9D9F: 0x64DA, //CJK UNIFIED IDEOGRAPH - 0x9DA0: 0x64D2, //CJK UNIFIED IDEOGRAPH - 0x9DA1: 0x64C5, //CJK UNIFIED IDEOGRAPH - 0x9DA2: 0x64C7, //CJK UNIFIED IDEOGRAPH - 0x9DA3: 0x64BB, //CJK UNIFIED IDEOGRAPH - 0x9DA4: 0x64D8, //CJK UNIFIED IDEOGRAPH - 0x9DA5: 0x64C2, //CJK UNIFIED IDEOGRAPH - 0x9DA6: 0x64F1, //CJK UNIFIED IDEOGRAPH - 0x9DA7: 0x64E7, //CJK UNIFIED IDEOGRAPH - 0x9DA8: 0x8209, //CJK UNIFIED IDEOGRAPH - 0x9DA9: 0x64E0, //CJK UNIFIED IDEOGRAPH - 0x9DAA: 0x64E1, //CJK UNIFIED IDEOGRAPH - 0x9DAB: 0x62AC, //CJK UNIFIED IDEOGRAPH - 0x9DAC: 0x64E3, //CJK UNIFIED IDEOGRAPH - 0x9DAD: 0x64EF, //CJK UNIFIED IDEOGRAPH - 0x9DAE: 0x652C, //CJK UNIFIED IDEOGRAPH - 0x9DAF: 0x64F6, //CJK UNIFIED IDEOGRAPH - 0x9DB0: 0x64F4, //CJK UNIFIED IDEOGRAPH - 0x9DB1: 0x64F2, //CJK UNIFIED IDEOGRAPH - 0x9DB2: 0x64FA, //CJK UNIFIED IDEOGRAPH - 0x9DB3: 0x6500, //CJK UNIFIED IDEOGRAPH - 0x9DB4: 0x64FD, //CJK UNIFIED IDEOGRAPH - 0x9DB5: 0x6518, //CJK UNIFIED IDEOGRAPH - 0x9DB6: 0x651C, //CJK UNIFIED IDEOGRAPH - 0x9DB7: 0x6505, //CJK UNIFIED IDEOGRAPH - 0x9DB8: 0x6524, //CJK UNIFIED IDEOGRAPH - 0x9DB9: 0x6523, //CJK UNIFIED IDEOGRAPH - 0x9DBA: 0x652B, //CJK UNIFIED IDEOGRAPH - 0x9DBB: 0x6534, //CJK UNIFIED IDEOGRAPH - 0x9DBC: 0x6535, //CJK UNIFIED IDEOGRAPH - 0x9DBD: 0x6537, //CJK UNIFIED IDEOGRAPH - 0x9DBE: 0x6536, //CJK UNIFIED IDEOGRAPH - 0x9DBF: 0x6538, //CJK UNIFIED IDEOGRAPH - 0x9DC0: 0x754B, //CJK UNIFIED IDEOGRAPH - 0x9DC1: 0x6548, //CJK UNIFIED IDEOGRAPH - 0x9DC2: 0x6556, //CJK UNIFIED IDEOGRAPH - 0x9DC3: 0x6555, //CJK UNIFIED IDEOGRAPH - 0x9DC4: 0x654D, //CJK UNIFIED IDEOGRAPH - 0x9DC5: 0x6558, //CJK UNIFIED IDEOGRAPH - 0x9DC6: 0x655E, //CJK UNIFIED IDEOGRAPH - 0x9DC7: 0x655D, //CJK UNIFIED IDEOGRAPH - 0x9DC8: 0x6572, //CJK UNIFIED IDEOGRAPH - 0x9DC9: 0x6578, //CJK UNIFIED IDEOGRAPH - 0x9DCA: 0x6582, //CJK UNIFIED IDEOGRAPH - 0x9DCB: 0x6583, //CJK UNIFIED IDEOGRAPH - 0x9DCC: 0x8B8A, //CJK UNIFIED IDEOGRAPH - 0x9DCD: 0x659B, //CJK UNIFIED IDEOGRAPH - 0x9DCE: 0x659F, //CJK UNIFIED IDEOGRAPH - 0x9DCF: 0x65AB, //CJK UNIFIED IDEOGRAPH - 0x9DD0: 0x65B7, //CJK UNIFIED IDEOGRAPH - 0x9DD1: 0x65C3, //CJK UNIFIED IDEOGRAPH - 0x9DD2: 0x65C6, //CJK UNIFIED IDEOGRAPH - 0x9DD3: 0x65C1, //CJK UNIFIED IDEOGRAPH - 0x9DD4: 0x65C4, //CJK UNIFIED IDEOGRAPH - 0x9DD5: 0x65CC, //CJK UNIFIED IDEOGRAPH - 0x9DD6: 0x65D2, //CJK UNIFIED IDEOGRAPH - 0x9DD7: 0x65DB, //CJK UNIFIED IDEOGRAPH - 0x9DD8: 0x65D9, //CJK UNIFIED IDEOGRAPH - 0x9DD9: 0x65E0, //CJK UNIFIED IDEOGRAPH - 0x9DDA: 0x65E1, //CJK UNIFIED IDEOGRAPH - 0x9DDB: 0x65F1, //CJK UNIFIED IDEOGRAPH - 0x9DDC: 0x6772, //CJK UNIFIED IDEOGRAPH - 0x9DDD: 0x660A, //CJK UNIFIED IDEOGRAPH - 0x9DDE: 0x6603, //CJK UNIFIED IDEOGRAPH - 0x9DDF: 0x65FB, //CJK UNIFIED IDEOGRAPH - 0x9DE0: 0x6773, //CJK UNIFIED IDEOGRAPH - 0x9DE1: 0x6635, //CJK UNIFIED IDEOGRAPH - 0x9DE2: 0x6636, //CJK UNIFIED IDEOGRAPH - 0x9DE3: 0x6634, //CJK UNIFIED IDEOGRAPH - 0x9DE4: 0x661C, //CJK UNIFIED IDEOGRAPH - 0x9DE5: 0x664F, //CJK UNIFIED IDEOGRAPH - 0x9DE6: 0x6644, //CJK UNIFIED IDEOGRAPH - 0x9DE7: 0x6649, //CJK UNIFIED IDEOGRAPH - 0x9DE8: 0x6641, //CJK UNIFIED IDEOGRAPH - 0x9DE9: 0x665E, //CJK UNIFIED IDEOGRAPH - 0x9DEA: 0x665D, //CJK UNIFIED IDEOGRAPH - 0x9DEB: 0x6664, //CJK UNIFIED IDEOGRAPH - 0x9DEC: 0x6667, //CJK UNIFIED IDEOGRAPH - 0x9DED: 0x6668, //CJK UNIFIED IDEOGRAPH - 0x9DEE: 0x665F, //CJK UNIFIED IDEOGRAPH - 0x9DEF: 0x6662, //CJK UNIFIED IDEOGRAPH - 0x9DF0: 0x6670, //CJK UNIFIED IDEOGRAPH - 0x9DF1: 0x6683, //CJK UNIFIED IDEOGRAPH - 0x9DF2: 0x6688, //CJK UNIFIED IDEOGRAPH - 0x9DF3: 0x668E, //CJK UNIFIED IDEOGRAPH - 0x9DF4: 0x6689, //CJK UNIFIED IDEOGRAPH - 0x9DF5: 0x6684, //CJK UNIFIED IDEOGRAPH - 0x9DF6: 0x6698, //CJK UNIFIED IDEOGRAPH - 0x9DF7: 0x669D, //CJK UNIFIED IDEOGRAPH - 0x9DF8: 0x66C1, //CJK UNIFIED IDEOGRAPH - 0x9DF9: 0x66B9, //CJK UNIFIED IDEOGRAPH - 0x9DFA: 0x66C9, //CJK UNIFIED IDEOGRAPH - 0x9DFB: 0x66BE, //CJK UNIFIED IDEOGRAPH - 0x9DFC: 0x66BC, //CJK UNIFIED IDEOGRAPH - 0x9E40: 0x66C4, //CJK UNIFIED IDEOGRAPH - 0x9E41: 0x66B8, //CJK UNIFIED IDEOGRAPH - 0x9E42: 0x66D6, //CJK UNIFIED IDEOGRAPH - 0x9E43: 0x66DA, //CJK UNIFIED IDEOGRAPH - 0x9E44: 0x66E0, //CJK UNIFIED IDEOGRAPH - 0x9E45: 0x663F, //CJK UNIFIED IDEOGRAPH - 0x9E46: 0x66E6, //CJK UNIFIED IDEOGRAPH - 0x9E47: 0x66E9, //CJK UNIFIED IDEOGRAPH - 0x9E48: 0x66F0, //CJK UNIFIED IDEOGRAPH - 0x9E49: 0x66F5, //CJK UNIFIED IDEOGRAPH - 0x9E4A: 0x66F7, //CJK UNIFIED IDEOGRAPH - 0x9E4B: 0x670F, //CJK UNIFIED IDEOGRAPH - 0x9E4C: 0x6716, //CJK UNIFIED IDEOGRAPH - 0x9E4D: 0x671E, //CJK UNIFIED IDEOGRAPH - 0x9E4E: 0x6726, //CJK UNIFIED IDEOGRAPH - 0x9E4F: 0x6727, //CJK UNIFIED IDEOGRAPH - 0x9E50: 0x9738, //CJK UNIFIED IDEOGRAPH - 0x9E51: 0x672E, //CJK UNIFIED IDEOGRAPH - 0x9E52: 0x673F, //CJK UNIFIED IDEOGRAPH - 0x9E53: 0x6736, //CJK UNIFIED IDEOGRAPH - 0x9E54: 0x6741, //CJK UNIFIED IDEOGRAPH - 0x9E55: 0x6738, //CJK UNIFIED IDEOGRAPH - 0x9E56: 0x6737, //CJK UNIFIED IDEOGRAPH - 0x9E57: 0x6746, //CJK UNIFIED IDEOGRAPH - 0x9E58: 0x675E, //CJK UNIFIED IDEOGRAPH - 0x9E59: 0x6760, //CJK UNIFIED IDEOGRAPH - 0x9E5A: 0x6759, //CJK UNIFIED IDEOGRAPH - 0x9E5B: 0x6763, //CJK UNIFIED IDEOGRAPH - 0x9E5C: 0x6764, //CJK UNIFIED IDEOGRAPH - 0x9E5D: 0x6789, //CJK UNIFIED IDEOGRAPH - 0x9E5E: 0x6770, //CJK UNIFIED IDEOGRAPH - 0x9E5F: 0x67A9, //CJK UNIFIED IDEOGRAPH - 0x9E60: 0x677C, //CJK UNIFIED IDEOGRAPH - 0x9E61: 0x676A, //CJK UNIFIED IDEOGRAPH - 0x9E62: 0x678C, //CJK UNIFIED IDEOGRAPH - 0x9E63: 0x678B, //CJK UNIFIED IDEOGRAPH - 0x9E64: 0x67A6, //CJK UNIFIED IDEOGRAPH - 0x9E65: 0x67A1, //CJK UNIFIED IDEOGRAPH - 0x9E66: 0x6785, //CJK UNIFIED IDEOGRAPH - 0x9E67: 0x67B7, //CJK UNIFIED IDEOGRAPH - 0x9E68: 0x67EF, //CJK UNIFIED IDEOGRAPH - 0x9E69: 0x67B4, //CJK UNIFIED IDEOGRAPH - 0x9E6A: 0x67EC, //CJK UNIFIED IDEOGRAPH - 0x9E6B: 0x67B3, //CJK UNIFIED IDEOGRAPH - 0x9E6C: 0x67E9, //CJK UNIFIED IDEOGRAPH - 0x9E6D: 0x67B8, //CJK UNIFIED IDEOGRAPH - 0x9E6E: 0x67E4, //CJK UNIFIED IDEOGRAPH - 0x9E6F: 0x67DE, //CJK UNIFIED IDEOGRAPH - 0x9E70: 0x67DD, //CJK UNIFIED IDEOGRAPH - 0x9E71: 0x67E2, //CJK UNIFIED IDEOGRAPH - 0x9E72: 0x67EE, //CJK UNIFIED IDEOGRAPH - 0x9E73: 0x67B9, //CJK UNIFIED IDEOGRAPH - 0x9E74: 0x67CE, //CJK UNIFIED IDEOGRAPH - 0x9E75: 0x67C6, //CJK UNIFIED IDEOGRAPH - 0x9E76: 0x67E7, //CJK UNIFIED IDEOGRAPH - 0x9E77: 0x6A9C, //CJK UNIFIED IDEOGRAPH - 0x9E78: 0x681E, //CJK UNIFIED IDEOGRAPH - 0x9E79: 0x6846, //CJK UNIFIED IDEOGRAPH - 0x9E7A: 0x6829, //CJK UNIFIED IDEOGRAPH - 0x9E7B: 0x6840, //CJK UNIFIED IDEOGRAPH - 0x9E7C: 0x684D, //CJK UNIFIED IDEOGRAPH - 0x9E7D: 0x6832, //CJK UNIFIED IDEOGRAPH - 0x9E7E: 0x684E, //CJK UNIFIED IDEOGRAPH - 0x9E80: 0x68B3, //CJK UNIFIED IDEOGRAPH - 0x9E81: 0x682B, //CJK UNIFIED IDEOGRAPH - 0x9E82: 0x6859, //CJK UNIFIED IDEOGRAPH - 0x9E83: 0x6863, //CJK UNIFIED IDEOGRAPH - 0x9E84: 0x6877, //CJK UNIFIED IDEOGRAPH - 0x9E85: 0x687F, //CJK UNIFIED IDEOGRAPH - 0x9E86: 0x689F, //CJK UNIFIED IDEOGRAPH - 0x9E87: 0x688F, //CJK UNIFIED IDEOGRAPH - 0x9E88: 0x68AD, //CJK UNIFIED IDEOGRAPH - 0x9E89: 0x6894, //CJK UNIFIED IDEOGRAPH - 0x9E8A: 0x689D, //CJK UNIFIED IDEOGRAPH - 0x9E8B: 0x689B, //CJK UNIFIED IDEOGRAPH - 0x9E8C: 0x6883, //CJK UNIFIED IDEOGRAPH - 0x9E8D: 0x6AAE, //CJK UNIFIED IDEOGRAPH - 0x9E8E: 0x68B9, //CJK UNIFIED IDEOGRAPH - 0x9E8F: 0x6874, //CJK UNIFIED IDEOGRAPH - 0x9E90: 0x68B5, //CJK UNIFIED IDEOGRAPH - 0x9E91: 0x68A0, //CJK UNIFIED IDEOGRAPH - 0x9E92: 0x68BA, //CJK UNIFIED IDEOGRAPH - 0x9E93: 0x690F, //CJK UNIFIED IDEOGRAPH - 0x9E94: 0x688D, //CJK UNIFIED IDEOGRAPH - 0x9E95: 0x687E, //CJK UNIFIED IDEOGRAPH - 0x9E96: 0x6901, //CJK UNIFIED IDEOGRAPH - 0x9E97: 0x68CA, //CJK UNIFIED IDEOGRAPH - 0x9E98: 0x6908, //CJK UNIFIED IDEOGRAPH - 0x9E99: 0x68D8, //CJK UNIFIED IDEOGRAPH - 0x9E9A: 0x6922, //CJK UNIFIED IDEOGRAPH - 0x9E9B: 0x6926, //CJK UNIFIED IDEOGRAPH - 0x9E9C: 0x68E1, //CJK UNIFIED IDEOGRAPH - 0x9E9D: 0x690C, //CJK UNIFIED IDEOGRAPH - 0x9E9E: 0x68CD, //CJK UNIFIED IDEOGRAPH - 0x9E9F: 0x68D4, //CJK UNIFIED IDEOGRAPH - 0x9EA0: 0x68E7, //CJK UNIFIED IDEOGRAPH - 0x9EA1: 0x68D5, //CJK UNIFIED IDEOGRAPH - 0x9EA2: 0x6936, //CJK UNIFIED IDEOGRAPH - 0x9EA3: 0x6912, //CJK UNIFIED IDEOGRAPH - 0x9EA4: 0x6904, //CJK UNIFIED IDEOGRAPH - 0x9EA5: 0x68D7, //CJK UNIFIED IDEOGRAPH - 0x9EA6: 0x68E3, //CJK UNIFIED IDEOGRAPH - 0x9EA7: 0x6925, //CJK UNIFIED IDEOGRAPH - 0x9EA8: 0x68F9, //CJK UNIFIED IDEOGRAPH - 0x9EA9: 0x68E0, //CJK UNIFIED IDEOGRAPH - 0x9EAA: 0x68EF, //CJK UNIFIED IDEOGRAPH - 0x9EAB: 0x6928, //CJK UNIFIED IDEOGRAPH - 0x9EAC: 0x692A, //CJK UNIFIED IDEOGRAPH - 0x9EAD: 0x691A, //CJK UNIFIED IDEOGRAPH - 0x9EAE: 0x6923, //CJK UNIFIED IDEOGRAPH - 0x9EAF: 0x6921, //CJK UNIFIED IDEOGRAPH - 0x9EB0: 0x68C6, //CJK UNIFIED IDEOGRAPH - 0x9EB1: 0x6979, //CJK UNIFIED IDEOGRAPH - 0x9EB2: 0x6977, //CJK UNIFIED IDEOGRAPH - 0x9EB3: 0x695C, //CJK UNIFIED IDEOGRAPH - 0x9EB4: 0x6978, //CJK UNIFIED IDEOGRAPH - 0x9EB5: 0x696B, //CJK UNIFIED IDEOGRAPH - 0x9EB6: 0x6954, //CJK UNIFIED IDEOGRAPH - 0x9EB7: 0x697E, //CJK UNIFIED IDEOGRAPH - 0x9EB8: 0x696E, //CJK UNIFIED IDEOGRAPH - 0x9EB9: 0x6939, //CJK UNIFIED IDEOGRAPH - 0x9EBA: 0x6974, //CJK UNIFIED IDEOGRAPH - 0x9EBB: 0x693D, //CJK UNIFIED IDEOGRAPH - 0x9EBC: 0x6959, //CJK UNIFIED IDEOGRAPH - 0x9EBD: 0x6930, //CJK UNIFIED IDEOGRAPH - 0x9EBE: 0x6961, //CJK UNIFIED IDEOGRAPH - 0x9EBF: 0x695E, //CJK UNIFIED IDEOGRAPH - 0x9EC0: 0x695D, //CJK UNIFIED IDEOGRAPH - 0x9EC1: 0x6981, //CJK UNIFIED IDEOGRAPH - 0x9EC2: 0x696A, //CJK UNIFIED IDEOGRAPH - 0x9EC3: 0x69B2, //CJK UNIFIED IDEOGRAPH - 0x9EC4: 0x69AE, //CJK UNIFIED IDEOGRAPH - 0x9EC5: 0x69D0, //CJK UNIFIED IDEOGRAPH - 0x9EC6: 0x69BF, //CJK UNIFIED IDEOGRAPH - 0x9EC7: 0x69C1, //CJK UNIFIED IDEOGRAPH - 0x9EC8: 0x69D3, //CJK UNIFIED IDEOGRAPH - 0x9EC9: 0x69BE, //CJK UNIFIED IDEOGRAPH - 0x9ECA: 0x69CE, //CJK UNIFIED IDEOGRAPH - 0x9ECB: 0x5BE8, //CJK UNIFIED IDEOGRAPH - 0x9ECC: 0x69CA, //CJK UNIFIED IDEOGRAPH - 0x9ECD: 0x69DD, //CJK UNIFIED IDEOGRAPH - 0x9ECE: 0x69BB, //CJK UNIFIED IDEOGRAPH - 0x9ECF: 0x69C3, //CJK UNIFIED IDEOGRAPH - 0x9ED0: 0x69A7, //CJK UNIFIED IDEOGRAPH - 0x9ED1: 0x6A2E, //CJK UNIFIED IDEOGRAPH - 0x9ED2: 0x6991, //CJK UNIFIED IDEOGRAPH - 0x9ED3: 0x69A0, //CJK UNIFIED IDEOGRAPH - 0x9ED4: 0x699C, //CJK UNIFIED IDEOGRAPH - 0x9ED5: 0x6995, //CJK UNIFIED IDEOGRAPH - 0x9ED6: 0x69B4, //CJK UNIFIED IDEOGRAPH - 0x9ED7: 0x69DE, //CJK UNIFIED IDEOGRAPH - 0x9ED8: 0x69E8, //CJK UNIFIED IDEOGRAPH - 0x9ED9: 0x6A02, //CJK UNIFIED IDEOGRAPH - 0x9EDA: 0x6A1B, //CJK UNIFIED IDEOGRAPH - 0x9EDB: 0x69FF, //CJK UNIFIED IDEOGRAPH - 0x9EDC: 0x6B0A, //CJK UNIFIED IDEOGRAPH - 0x9EDD: 0x69F9, //CJK UNIFIED IDEOGRAPH - 0x9EDE: 0x69F2, //CJK UNIFIED IDEOGRAPH - 0x9EDF: 0x69E7, //CJK UNIFIED IDEOGRAPH - 0x9EE0: 0x6A05, //CJK UNIFIED IDEOGRAPH - 0x9EE1: 0x69B1, //CJK UNIFIED IDEOGRAPH - 0x9EE2: 0x6A1E, //CJK UNIFIED IDEOGRAPH - 0x9EE3: 0x69ED, //CJK UNIFIED IDEOGRAPH - 0x9EE4: 0x6A14, //CJK UNIFIED IDEOGRAPH - 0x9EE5: 0x69EB, //CJK UNIFIED IDEOGRAPH - 0x9EE6: 0x6A0A, //CJK UNIFIED IDEOGRAPH - 0x9EE7: 0x6A12, //CJK UNIFIED IDEOGRAPH - 0x9EE8: 0x6AC1, //CJK UNIFIED IDEOGRAPH - 0x9EE9: 0x6A23, //CJK UNIFIED IDEOGRAPH - 0x9EEA: 0x6A13, //CJK UNIFIED IDEOGRAPH - 0x9EEB: 0x6A44, //CJK UNIFIED IDEOGRAPH - 0x9EEC: 0x6A0C, //CJK UNIFIED IDEOGRAPH - 0x9EED: 0x6A72, //CJK UNIFIED IDEOGRAPH - 0x9EEE: 0x6A36, //CJK UNIFIED IDEOGRAPH - 0x9EEF: 0x6A78, //CJK UNIFIED IDEOGRAPH - 0x9EF0: 0x6A47, //CJK UNIFIED IDEOGRAPH - 0x9EF1: 0x6A62, //CJK UNIFIED IDEOGRAPH - 0x9EF2: 0x6A59, //CJK UNIFIED IDEOGRAPH - 0x9EF3: 0x6A66, //CJK UNIFIED IDEOGRAPH - 0x9EF4: 0x6A48, //CJK UNIFIED IDEOGRAPH - 0x9EF5: 0x6A38, //CJK UNIFIED IDEOGRAPH - 0x9EF6: 0x6A22, //CJK UNIFIED IDEOGRAPH - 0x9EF7: 0x6A90, //CJK UNIFIED IDEOGRAPH - 0x9EF8: 0x6A8D, //CJK UNIFIED IDEOGRAPH - 0x9EF9: 0x6AA0, //CJK UNIFIED IDEOGRAPH - 0x9EFA: 0x6A84, //CJK UNIFIED IDEOGRAPH - 0x9EFB: 0x6AA2, //CJK UNIFIED IDEOGRAPH - 0x9EFC: 0x6AA3, //CJK UNIFIED IDEOGRAPH - 0x9F40: 0x6A97, //CJK UNIFIED IDEOGRAPH - 0x9F41: 0x8617, //CJK UNIFIED IDEOGRAPH - 0x9F42: 0x6ABB, //CJK UNIFIED IDEOGRAPH - 0x9F43: 0x6AC3, //CJK UNIFIED IDEOGRAPH - 0x9F44: 0x6AC2, //CJK UNIFIED IDEOGRAPH - 0x9F45: 0x6AB8, //CJK UNIFIED IDEOGRAPH - 0x9F46: 0x6AB3, //CJK UNIFIED IDEOGRAPH - 0x9F47: 0x6AAC, //CJK UNIFIED IDEOGRAPH - 0x9F48: 0x6ADE, //CJK UNIFIED IDEOGRAPH - 0x9F49: 0x6AD1, //CJK UNIFIED IDEOGRAPH - 0x9F4A: 0x6ADF, //CJK UNIFIED IDEOGRAPH - 0x9F4B: 0x6AAA, //CJK UNIFIED IDEOGRAPH - 0x9F4C: 0x6ADA, //CJK UNIFIED IDEOGRAPH - 0x9F4D: 0x6AEA, //CJK UNIFIED IDEOGRAPH - 0x9F4E: 0x6AFB, //CJK UNIFIED IDEOGRAPH - 0x9F4F: 0x6B05, //CJK UNIFIED IDEOGRAPH - 0x9F50: 0x8616, //CJK UNIFIED IDEOGRAPH - 0x9F51: 0x6AFA, //CJK UNIFIED IDEOGRAPH - 0x9F52: 0x6B12, //CJK UNIFIED IDEOGRAPH - 0x9F53: 0x6B16, //CJK UNIFIED IDEOGRAPH - 0x9F54: 0x9B31, //CJK UNIFIED IDEOGRAPH - 0x9F55: 0x6B1F, //CJK UNIFIED IDEOGRAPH - 0x9F56: 0x6B38, //CJK UNIFIED IDEOGRAPH - 0x9F57: 0x6B37, //CJK UNIFIED IDEOGRAPH - 0x9F58: 0x76DC, //CJK UNIFIED IDEOGRAPH - 0x9F59: 0x6B39, //CJK UNIFIED IDEOGRAPH - 0x9F5A: 0x98EE, //CJK UNIFIED IDEOGRAPH - 0x9F5B: 0x6B47, //CJK UNIFIED IDEOGRAPH - 0x9F5C: 0x6B43, //CJK UNIFIED IDEOGRAPH - 0x9F5D: 0x6B49, //CJK UNIFIED IDEOGRAPH - 0x9F5E: 0x6B50, //CJK UNIFIED IDEOGRAPH - 0x9F5F: 0x6B59, //CJK UNIFIED IDEOGRAPH - 0x9F60: 0x6B54, //CJK UNIFIED IDEOGRAPH - 0x9F61: 0x6B5B, //CJK UNIFIED IDEOGRAPH - 0x9F62: 0x6B5F, //CJK UNIFIED IDEOGRAPH - 0x9F63: 0x6B61, //CJK UNIFIED IDEOGRAPH - 0x9F64: 0x6B78, //CJK UNIFIED IDEOGRAPH - 0x9F65: 0x6B79, //CJK UNIFIED IDEOGRAPH - 0x9F66: 0x6B7F, //CJK UNIFIED IDEOGRAPH - 0x9F67: 0x6B80, //CJK UNIFIED IDEOGRAPH - 0x9F68: 0x6B84, //CJK UNIFIED IDEOGRAPH - 0x9F69: 0x6B83, //CJK UNIFIED IDEOGRAPH - 0x9F6A: 0x6B8D, //CJK UNIFIED IDEOGRAPH - 0x9F6B: 0x6B98, //CJK UNIFIED IDEOGRAPH - 0x9F6C: 0x6B95, //CJK UNIFIED IDEOGRAPH - 0x9F6D: 0x6B9E, //CJK UNIFIED IDEOGRAPH - 0x9F6E: 0x6BA4, //CJK UNIFIED IDEOGRAPH - 0x9F6F: 0x6BAA, //CJK UNIFIED IDEOGRAPH - 0x9F70: 0x6BAB, //CJK UNIFIED IDEOGRAPH - 0x9F71: 0x6BAF, //CJK UNIFIED IDEOGRAPH - 0x9F72: 0x6BB2, //CJK UNIFIED IDEOGRAPH - 0x9F73: 0x6BB1, //CJK UNIFIED IDEOGRAPH - 0x9F74: 0x6BB3, //CJK UNIFIED IDEOGRAPH - 0x9F75: 0x6BB7, //CJK UNIFIED IDEOGRAPH - 0x9F76: 0x6BBC, //CJK UNIFIED IDEOGRAPH - 0x9F77: 0x6BC6, //CJK UNIFIED IDEOGRAPH - 0x9F78: 0x6BCB, //CJK UNIFIED IDEOGRAPH - 0x9F79: 0x6BD3, //CJK UNIFIED IDEOGRAPH - 0x9F7A: 0x6BDF, //CJK UNIFIED IDEOGRAPH - 0x9F7B: 0x6BEC, //CJK UNIFIED IDEOGRAPH - 0x9F7C: 0x6BEB, //CJK UNIFIED IDEOGRAPH - 0x9F7D: 0x6BF3, //CJK UNIFIED IDEOGRAPH - 0x9F7E: 0x6BEF, //CJK UNIFIED IDEOGRAPH - 0x9F80: 0x9EBE, //CJK UNIFIED IDEOGRAPH - 0x9F81: 0x6C08, //CJK UNIFIED IDEOGRAPH - 0x9F82: 0x6C13, //CJK UNIFIED IDEOGRAPH - 0x9F83: 0x6C14, //CJK UNIFIED IDEOGRAPH - 0x9F84: 0x6C1B, //CJK UNIFIED IDEOGRAPH - 0x9F85: 0x6C24, //CJK UNIFIED IDEOGRAPH - 0x9F86: 0x6C23, //CJK UNIFIED IDEOGRAPH - 0x9F87: 0x6C5E, //CJK UNIFIED IDEOGRAPH - 0x9F88: 0x6C55, //CJK UNIFIED IDEOGRAPH - 0x9F89: 0x6C62, //CJK UNIFIED IDEOGRAPH - 0x9F8A: 0x6C6A, //CJK UNIFIED IDEOGRAPH - 0x9F8B: 0x6C82, //CJK UNIFIED IDEOGRAPH - 0x9F8C: 0x6C8D, //CJK UNIFIED IDEOGRAPH - 0x9F8D: 0x6C9A, //CJK UNIFIED IDEOGRAPH - 0x9F8E: 0x6C81, //CJK UNIFIED IDEOGRAPH - 0x9F8F: 0x6C9B, //CJK UNIFIED IDEOGRAPH - 0x9F90: 0x6C7E, //CJK UNIFIED IDEOGRAPH - 0x9F91: 0x6C68, //CJK UNIFIED IDEOGRAPH - 0x9F92: 0x6C73, //CJK UNIFIED IDEOGRAPH - 0x9F93: 0x6C92, //CJK UNIFIED IDEOGRAPH - 0x9F94: 0x6C90, //CJK UNIFIED IDEOGRAPH - 0x9F95: 0x6CC4, //CJK UNIFIED IDEOGRAPH - 0x9F96: 0x6CF1, //CJK UNIFIED IDEOGRAPH - 0x9F97: 0x6CD3, //CJK UNIFIED IDEOGRAPH - 0x9F98: 0x6CBD, //CJK UNIFIED IDEOGRAPH - 0x9F99: 0x6CD7, //CJK UNIFIED IDEOGRAPH - 0x9F9A: 0x6CC5, //CJK UNIFIED IDEOGRAPH - 0x9F9B: 0x6CDD, //CJK UNIFIED IDEOGRAPH - 0x9F9C: 0x6CAE, //CJK UNIFIED IDEOGRAPH - 0x9F9D: 0x6CB1, //CJK UNIFIED IDEOGRAPH - 0x9F9E: 0x6CBE, //CJK UNIFIED IDEOGRAPH - 0x9F9F: 0x6CBA, //CJK UNIFIED IDEOGRAPH - 0x9FA0: 0x6CDB, //CJK UNIFIED IDEOGRAPH - 0x9FA1: 0x6CEF, //CJK UNIFIED IDEOGRAPH - 0x9FA2: 0x6CD9, //CJK UNIFIED IDEOGRAPH - 0x9FA3: 0x6CEA, //CJK UNIFIED IDEOGRAPH - 0x9FA4: 0x6D1F, //CJK UNIFIED IDEOGRAPH - 0x9FA5: 0x884D, //CJK UNIFIED IDEOGRAPH - 0x9FA6: 0x6D36, //CJK UNIFIED IDEOGRAPH - 0x9FA7: 0x6D2B, //CJK UNIFIED IDEOGRAPH - 0x9FA8: 0x6D3D, //CJK UNIFIED IDEOGRAPH - 0x9FA9: 0x6D38, //CJK UNIFIED IDEOGRAPH - 0x9FAA: 0x6D19, //CJK UNIFIED IDEOGRAPH - 0x9FAB: 0x6D35, //CJK UNIFIED IDEOGRAPH - 0x9FAC: 0x6D33, //CJK UNIFIED IDEOGRAPH - 0x9FAD: 0x6D12, //CJK UNIFIED IDEOGRAPH - 0x9FAE: 0x6D0C, //CJK UNIFIED IDEOGRAPH - 0x9FAF: 0x6D63, //CJK UNIFIED IDEOGRAPH - 0x9FB0: 0x6D93, //CJK UNIFIED IDEOGRAPH - 0x9FB1: 0x6D64, //CJK UNIFIED IDEOGRAPH - 0x9FB2: 0x6D5A, //CJK UNIFIED IDEOGRAPH - 0x9FB3: 0x6D79, //CJK UNIFIED IDEOGRAPH - 0x9FB4: 0x6D59, //CJK UNIFIED IDEOGRAPH - 0x9FB5: 0x6D8E, //CJK UNIFIED IDEOGRAPH - 0x9FB6: 0x6D95, //CJK UNIFIED IDEOGRAPH - 0x9FB7: 0x6FE4, //CJK UNIFIED IDEOGRAPH - 0x9FB8: 0x6D85, //CJK UNIFIED IDEOGRAPH - 0x9FB9: 0x6DF9, //CJK UNIFIED IDEOGRAPH - 0x9FBA: 0x6E15, //CJK UNIFIED IDEOGRAPH - 0x9FBB: 0x6E0A, //CJK UNIFIED IDEOGRAPH - 0x9FBC: 0x6DB5, //CJK UNIFIED IDEOGRAPH - 0x9FBD: 0x6DC7, //CJK UNIFIED IDEOGRAPH - 0x9FBE: 0x6DE6, //CJK UNIFIED IDEOGRAPH - 0x9FBF: 0x6DB8, //CJK UNIFIED IDEOGRAPH - 0x9FC0: 0x6DC6, //CJK UNIFIED IDEOGRAPH - 0x9FC1: 0x6DEC, //CJK UNIFIED IDEOGRAPH - 0x9FC2: 0x6DDE, //CJK UNIFIED IDEOGRAPH - 0x9FC3: 0x6DCC, //CJK UNIFIED IDEOGRAPH - 0x9FC4: 0x6DE8, //CJK UNIFIED IDEOGRAPH - 0x9FC5: 0x6DD2, //CJK UNIFIED IDEOGRAPH - 0x9FC6: 0x6DC5, //CJK UNIFIED IDEOGRAPH - 0x9FC7: 0x6DFA, //CJK UNIFIED IDEOGRAPH - 0x9FC8: 0x6DD9, //CJK UNIFIED IDEOGRAPH - 0x9FC9: 0x6DE4, //CJK UNIFIED IDEOGRAPH - 0x9FCA: 0x6DD5, //CJK UNIFIED IDEOGRAPH - 0x9FCB: 0x6DEA, //CJK UNIFIED IDEOGRAPH - 0x9FCC: 0x6DEE, //CJK UNIFIED IDEOGRAPH - 0x9FCD: 0x6E2D, //CJK UNIFIED IDEOGRAPH - 0x9FCE: 0x6E6E, //CJK UNIFIED IDEOGRAPH - 0x9FCF: 0x6E2E, //CJK UNIFIED IDEOGRAPH - 0x9FD0: 0x6E19, //CJK UNIFIED IDEOGRAPH - 0x9FD1: 0x6E72, //CJK UNIFIED IDEOGRAPH - 0x9FD2: 0x6E5F, //CJK UNIFIED IDEOGRAPH - 0x9FD3: 0x6E3E, //CJK UNIFIED IDEOGRAPH - 0x9FD4: 0x6E23, //CJK UNIFIED IDEOGRAPH - 0x9FD5: 0x6E6B, //CJK UNIFIED IDEOGRAPH - 0x9FD6: 0x6E2B, //CJK UNIFIED IDEOGRAPH - 0x9FD7: 0x6E76, //CJK UNIFIED IDEOGRAPH - 0x9FD8: 0x6E4D, //CJK UNIFIED IDEOGRAPH - 0x9FD9: 0x6E1F, //CJK UNIFIED IDEOGRAPH - 0x9FDA: 0x6E43, //CJK UNIFIED IDEOGRAPH - 0x9FDB: 0x6E3A, //CJK UNIFIED IDEOGRAPH - 0x9FDC: 0x6E4E, //CJK UNIFIED IDEOGRAPH - 0x9FDD: 0x6E24, //CJK UNIFIED IDEOGRAPH - 0x9FDE: 0x6EFF, //CJK UNIFIED IDEOGRAPH - 0x9FDF: 0x6E1D, //CJK UNIFIED IDEOGRAPH - 0x9FE0: 0x6E38, //CJK UNIFIED IDEOGRAPH - 0x9FE1: 0x6E82, //CJK UNIFIED IDEOGRAPH - 0x9FE2: 0x6EAA, //CJK UNIFIED IDEOGRAPH - 0x9FE3: 0x6E98, //CJK UNIFIED IDEOGRAPH - 0x9FE4: 0x6EC9, //CJK UNIFIED IDEOGRAPH - 0x9FE5: 0x6EB7, //CJK UNIFIED IDEOGRAPH - 0x9FE6: 0x6ED3, //CJK UNIFIED IDEOGRAPH - 0x9FE7: 0x6EBD, //CJK UNIFIED IDEOGRAPH - 0x9FE8: 0x6EAF, //CJK UNIFIED IDEOGRAPH - 0x9FE9: 0x6EC4, //CJK UNIFIED IDEOGRAPH - 0x9FEA: 0x6EB2, //CJK UNIFIED IDEOGRAPH - 0x9FEB: 0x6ED4, //CJK UNIFIED IDEOGRAPH - 0x9FEC: 0x6ED5, //CJK UNIFIED IDEOGRAPH - 0x9FED: 0x6E8F, //CJK UNIFIED IDEOGRAPH - 0x9FEE: 0x6EA5, //CJK UNIFIED IDEOGRAPH - 0x9FEF: 0x6EC2, //CJK UNIFIED IDEOGRAPH - 0x9FF0: 0x6E9F, //CJK UNIFIED IDEOGRAPH - 0x9FF1: 0x6F41, //CJK UNIFIED IDEOGRAPH - 0x9FF2: 0x6F11, //CJK UNIFIED IDEOGRAPH - 0x9FF3: 0x704C, //CJK UNIFIED IDEOGRAPH - 0x9FF4: 0x6EEC, //CJK UNIFIED IDEOGRAPH - 0x9FF5: 0x6EF8, //CJK UNIFIED IDEOGRAPH - 0x9FF6: 0x6EFE, //CJK UNIFIED IDEOGRAPH - 0x9FF7: 0x6F3F, //CJK UNIFIED IDEOGRAPH - 0x9FF8: 0x6EF2, //CJK UNIFIED IDEOGRAPH - 0x9FF9: 0x6F31, //CJK UNIFIED IDEOGRAPH - 0x9FFA: 0x6EEF, //CJK UNIFIED IDEOGRAPH - 0x9FFB: 0x6F32, //CJK UNIFIED IDEOGRAPH - 0x9FFC: 0x6ECC, //CJK UNIFIED IDEOGRAPH - 0xE040: 0x6F3E, //CJK UNIFIED IDEOGRAPH - 0xE041: 0x6F13, //CJK UNIFIED IDEOGRAPH - 0xE042: 0x6EF7, //CJK UNIFIED IDEOGRAPH - 0xE043: 0x6F86, //CJK UNIFIED IDEOGRAPH - 0xE044: 0x6F7A, //CJK UNIFIED IDEOGRAPH - 0xE045: 0x6F78, //CJK UNIFIED IDEOGRAPH - 0xE046: 0x6F81, //CJK UNIFIED IDEOGRAPH - 0xE047: 0x6F80, //CJK UNIFIED IDEOGRAPH - 0xE048: 0x6F6F, //CJK UNIFIED IDEOGRAPH - 0xE049: 0x6F5B, //CJK UNIFIED IDEOGRAPH - 0xE04A: 0x6FF3, //CJK UNIFIED IDEOGRAPH - 0xE04B: 0x6F6D, //CJK UNIFIED IDEOGRAPH - 0xE04C: 0x6F82, //CJK UNIFIED IDEOGRAPH - 0xE04D: 0x6F7C, //CJK UNIFIED IDEOGRAPH - 0xE04E: 0x6F58, //CJK UNIFIED IDEOGRAPH - 0xE04F: 0x6F8E, //CJK UNIFIED IDEOGRAPH - 0xE050: 0x6F91, //CJK UNIFIED IDEOGRAPH - 0xE051: 0x6FC2, //CJK UNIFIED IDEOGRAPH - 0xE052: 0x6F66, //CJK UNIFIED IDEOGRAPH - 0xE053: 0x6FB3, //CJK UNIFIED IDEOGRAPH - 0xE054: 0x6FA3, //CJK UNIFIED IDEOGRAPH - 0xE055: 0x6FA1, //CJK UNIFIED IDEOGRAPH - 0xE056: 0x6FA4, //CJK UNIFIED IDEOGRAPH - 0xE057: 0x6FB9, //CJK UNIFIED IDEOGRAPH - 0xE058: 0x6FC6, //CJK UNIFIED IDEOGRAPH - 0xE059: 0x6FAA, //CJK UNIFIED IDEOGRAPH - 0xE05A: 0x6FDF, //CJK UNIFIED IDEOGRAPH - 0xE05B: 0x6FD5, //CJK UNIFIED IDEOGRAPH - 0xE05C: 0x6FEC, //CJK UNIFIED IDEOGRAPH - 0xE05D: 0x6FD4, //CJK UNIFIED IDEOGRAPH - 0xE05E: 0x6FD8, //CJK UNIFIED IDEOGRAPH - 0xE05F: 0x6FF1, //CJK UNIFIED IDEOGRAPH - 0xE060: 0x6FEE, //CJK UNIFIED IDEOGRAPH - 0xE061: 0x6FDB, //CJK UNIFIED IDEOGRAPH - 0xE062: 0x7009, //CJK UNIFIED IDEOGRAPH - 0xE063: 0x700B, //CJK UNIFIED IDEOGRAPH - 0xE064: 0x6FFA, //CJK UNIFIED IDEOGRAPH - 0xE065: 0x7011, //CJK UNIFIED IDEOGRAPH - 0xE066: 0x7001, //CJK UNIFIED IDEOGRAPH - 0xE067: 0x700F, //CJK UNIFIED IDEOGRAPH - 0xE068: 0x6FFE, //CJK UNIFIED IDEOGRAPH - 0xE069: 0x701B, //CJK UNIFIED IDEOGRAPH - 0xE06A: 0x701A, //CJK UNIFIED IDEOGRAPH - 0xE06B: 0x6F74, //CJK UNIFIED IDEOGRAPH - 0xE06C: 0x701D, //CJK UNIFIED IDEOGRAPH - 0xE06D: 0x7018, //CJK UNIFIED IDEOGRAPH - 0xE06E: 0x701F, //CJK UNIFIED IDEOGRAPH - 0xE06F: 0x7030, //CJK UNIFIED IDEOGRAPH - 0xE070: 0x703E, //CJK UNIFIED IDEOGRAPH - 0xE071: 0x7032, //CJK UNIFIED IDEOGRAPH - 0xE072: 0x7051, //CJK UNIFIED IDEOGRAPH - 0xE073: 0x7063, //CJK UNIFIED IDEOGRAPH - 0xE074: 0x7099, //CJK UNIFIED IDEOGRAPH - 0xE075: 0x7092, //CJK UNIFIED IDEOGRAPH - 0xE076: 0x70AF, //CJK UNIFIED IDEOGRAPH - 0xE077: 0x70F1, //CJK UNIFIED IDEOGRAPH - 0xE078: 0x70AC, //CJK UNIFIED IDEOGRAPH - 0xE079: 0x70B8, //CJK UNIFIED IDEOGRAPH - 0xE07A: 0x70B3, //CJK UNIFIED IDEOGRAPH - 0xE07B: 0x70AE, //CJK UNIFIED IDEOGRAPH - 0xE07C: 0x70DF, //CJK UNIFIED IDEOGRAPH - 0xE07D: 0x70CB, //CJK UNIFIED IDEOGRAPH - 0xE07E: 0x70DD, //CJK UNIFIED IDEOGRAPH - 0xE080: 0x70D9, //CJK UNIFIED IDEOGRAPH - 0xE081: 0x7109, //CJK UNIFIED IDEOGRAPH - 0xE082: 0x70FD, //CJK UNIFIED IDEOGRAPH - 0xE083: 0x711C, //CJK UNIFIED IDEOGRAPH - 0xE084: 0x7119, //CJK UNIFIED IDEOGRAPH - 0xE085: 0x7165, //CJK UNIFIED IDEOGRAPH - 0xE086: 0x7155, //CJK UNIFIED IDEOGRAPH - 0xE087: 0x7188, //CJK UNIFIED IDEOGRAPH - 0xE088: 0x7166, //CJK UNIFIED IDEOGRAPH - 0xE089: 0x7162, //CJK UNIFIED IDEOGRAPH - 0xE08A: 0x714C, //CJK UNIFIED IDEOGRAPH - 0xE08B: 0x7156, //CJK UNIFIED IDEOGRAPH - 0xE08C: 0x716C, //CJK UNIFIED IDEOGRAPH - 0xE08D: 0x718F, //CJK UNIFIED IDEOGRAPH - 0xE08E: 0x71FB, //CJK UNIFIED IDEOGRAPH - 0xE08F: 0x7184, //CJK UNIFIED IDEOGRAPH - 0xE090: 0x7195, //CJK UNIFIED IDEOGRAPH - 0xE091: 0x71A8, //CJK UNIFIED IDEOGRAPH - 0xE092: 0x71AC, //CJK UNIFIED IDEOGRAPH - 0xE093: 0x71D7, //CJK UNIFIED IDEOGRAPH - 0xE094: 0x71B9, //CJK UNIFIED IDEOGRAPH - 0xE095: 0x71BE, //CJK UNIFIED IDEOGRAPH - 0xE096: 0x71D2, //CJK UNIFIED IDEOGRAPH - 0xE097: 0x71C9, //CJK UNIFIED IDEOGRAPH - 0xE098: 0x71D4, //CJK UNIFIED IDEOGRAPH - 0xE099: 0x71CE, //CJK UNIFIED IDEOGRAPH - 0xE09A: 0x71E0, //CJK UNIFIED IDEOGRAPH - 0xE09B: 0x71EC, //CJK UNIFIED IDEOGRAPH - 0xE09C: 0x71E7, //CJK UNIFIED IDEOGRAPH - 0xE09D: 0x71F5, //CJK UNIFIED IDEOGRAPH - 0xE09E: 0x71FC, //CJK UNIFIED IDEOGRAPH - 0xE09F: 0x71F9, //CJK UNIFIED IDEOGRAPH - 0xE0A0: 0x71FF, //CJK UNIFIED IDEOGRAPH - 0xE0A1: 0x720D, //CJK UNIFIED IDEOGRAPH - 0xE0A2: 0x7210, //CJK UNIFIED IDEOGRAPH - 0xE0A3: 0x721B, //CJK UNIFIED IDEOGRAPH - 0xE0A4: 0x7228, //CJK UNIFIED IDEOGRAPH - 0xE0A5: 0x722D, //CJK UNIFIED IDEOGRAPH - 0xE0A6: 0x722C, //CJK UNIFIED IDEOGRAPH - 0xE0A7: 0x7230, //CJK UNIFIED IDEOGRAPH - 0xE0A8: 0x7232, //CJK UNIFIED IDEOGRAPH - 0xE0A9: 0x723B, //CJK UNIFIED IDEOGRAPH - 0xE0AA: 0x723C, //CJK UNIFIED IDEOGRAPH - 0xE0AB: 0x723F, //CJK UNIFIED IDEOGRAPH - 0xE0AC: 0x7240, //CJK UNIFIED IDEOGRAPH - 0xE0AD: 0x7246, //CJK UNIFIED IDEOGRAPH - 0xE0AE: 0x724B, //CJK UNIFIED IDEOGRAPH - 0xE0AF: 0x7258, //CJK UNIFIED IDEOGRAPH - 0xE0B0: 0x7274, //CJK UNIFIED IDEOGRAPH - 0xE0B1: 0x727E, //CJK UNIFIED IDEOGRAPH - 0xE0B2: 0x7282, //CJK UNIFIED IDEOGRAPH - 0xE0B3: 0x7281, //CJK UNIFIED IDEOGRAPH - 0xE0B4: 0x7287, //CJK UNIFIED IDEOGRAPH - 0xE0B5: 0x7292, //CJK UNIFIED IDEOGRAPH - 0xE0B6: 0x7296, //CJK UNIFIED IDEOGRAPH - 0xE0B7: 0x72A2, //CJK UNIFIED IDEOGRAPH - 0xE0B8: 0x72A7, //CJK UNIFIED IDEOGRAPH - 0xE0B9: 0x72B9, //CJK UNIFIED IDEOGRAPH - 0xE0BA: 0x72B2, //CJK UNIFIED IDEOGRAPH - 0xE0BB: 0x72C3, //CJK UNIFIED IDEOGRAPH - 0xE0BC: 0x72C6, //CJK UNIFIED IDEOGRAPH - 0xE0BD: 0x72C4, //CJK UNIFIED IDEOGRAPH - 0xE0BE: 0x72CE, //CJK UNIFIED IDEOGRAPH - 0xE0BF: 0x72D2, //CJK UNIFIED IDEOGRAPH - 0xE0C0: 0x72E2, //CJK UNIFIED IDEOGRAPH - 0xE0C1: 0x72E0, //CJK UNIFIED IDEOGRAPH - 0xE0C2: 0x72E1, //CJK UNIFIED IDEOGRAPH - 0xE0C3: 0x72F9, //CJK UNIFIED IDEOGRAPH - 0xE0C4: 0x72F7, //CJK UNIFIED IDEOGRAPH - 0xE0C5: 0x500F, //CJK UNIFIED IDEOGRAPH - 0xE0C6: 0x7317, //CJK UNIFIED IDEOGRAPH - 0xE0C7: 0x730A, //CJK UNIFIED IDEOGRAPH - 0xE0C8: 0x731C, //CJK UNIFIED IDEOGRAPH - 0xE0C9: 0x7316, //CJK UNIFIED IDEOGRAPH - 0xE0CA: 0x731D, //CJK UNIFIED IDEOGRAPH - 0xE0CB: 0x7334, //CJK UNIFIED IDEOGRAPH - 0xE0CC: 0x732F, //CJK UNIFIED IDEOGRAPH - 0xE0CD: 0x7329, //CJK UNIFIED IDEOGRAPH - 0xE0CE: 0x7325, //CJK UNIFIED IDEOGRAPH - 0xE0CF: 0x733E, //CJK UNIFIED IDEOGRAPH - 0xE0D0: 0x734E, //CJK UNIFIED IDEOGRAPH - 0xE0D1: 0x734F, //CJK UNIFIED IDEOGRAPH - 0xE0D2: 0x9ED8, //CJK UNIFIED IDEOGRAPH - 0xE0D3: 0x7357, //CJK UNIFIED IDEOGRAPH - 0xE0D4: 0x736A, //CJK UNIFIED IDEOGRAPH - 0xE0D5: 0x7368, //CJK UNIFIED IDEOGRAPH - 0xE0D6: 0x7370, //CJK UNIFIED IDEOGRAPH - 0xE0D7: 0x7378, //CJK UNIFIED IDEOGRAPH - 0xE0D8: 0x7375, //CJK UNIFIED IDEOGRAPH - 0xE0D9: 0x737B, //CJK UNIFIED IDEOGRAPH - 0xE0DA: 0x737A, //CJK UNIFIED IDEOGRAPH - 0xE0DB: 0x73C8, //CJK UNIFIED IDEOGRAPH - 0xE0DC: 0x73B3, //CJK UNIFIED IDEOGRAPH - 0xE0DD: 0x73CE, //CJK UNIFIED IDEOGRAPH - 0xE0DE: 0x73BB, //CJK UNIFIED IDEOGRAPH - 0xE0DF: 0x73C0, //CJK UNIFIED IDEOGRAPH - 0xE0E0: 0x73E5, //CJK UNIFIED IDEOGRAPH - 0xE0E1: 0x73EE, //CJK UNIFIED IDEOGRAPH - 0xE0E2: 0x73DE, //CJK UNIFIED IDEOGRAPH - 0xE0E3: 0x74A2, //CJK UNIFIED IDEOGRAPH - 0xE0E4: 0x7405, //CJK UNIFIED IDEOGRAPH - 0xE0E5: 0x746F, //CJK UNIFIED IDEOGRAPH - 0xE0E6: 0x7425, //CJK UNIFIED IDEOGRAPH - 0xE0E7: 0x73F8, //CJK UNIFIED IDEOGRAPH - 0xE0E8: 0x7432, //CJK UNIFIED IDEOGRAPH - 0xE0E9: 0x743A, //CJK UNIFIED IDEOGRAPH - 0xE0EA: 0x7455, //CJK UNIFIED IDEOGRAPH - 0xE0EB: 0x743F, //CJK UNIFIED IDEOGRAPH - 0xE0EC: 0x745F, //CJK UNIFIED IDEOGRAPH - 0xE0ED: 0x7459, //CJK UNIFIED IDEOGRAPH - 0xE0EE: 0x7441, //CJK UNIFIED IDEOGRAPH - 0xE0EF: 0x745C, //CJK UNIFIED IDEOGRAPH - 0xE0F0: 0x7469, //CJK UNIFIED IDEOGRAPH - 0xE0F1: 0x7470, //CJK UNIFIED IDEOGRAPH - 0xE0F2: 0x7463, //CJK UNIFIED IDEOGRAPH - 0xE0F3: 0x746A, //CJK UNIFIED IDEOGRAPH - 0xE0F4: 0x7476, //CJK UNIFIED IDEOGRAPH - 0xE0F5: 0x747E, //CJK UNIFIED IDEOGRAPH - 0xE0F6: 0x748B, //CJK UNIFIED IDEOGRAPH - 0xE0F7: 0x749E, //CJK UNIFIED IDEOGRAPH - 0xE0F8: 0x74A7, //CJK UNIFIED IDEOGRAPH - 0xE0F9: 0x74CA, //CJK UNIFIED IDEOGRAPH - 0xE0FA: 0x74CF, //CJK UNIFIED IDEOGRAPH - 0xE0FB: 0x74D4, //CJK UNIFIED IDEOGRAPH - 0xE0FC: 0x73F1, //CJK UNIFIED IDEOGRAPH - 0xE140: 0x74E0, //CJK UNIFIED IDEOGRAPH - 0xE141: 0x74E3, //CJK UNIFIED IDEOGRAPH - 0xE142: 0x74E7, //CJK UNIFIED IDEOGRAPH - 0xE143: 0x74E9, //CJK UNIFIED IDEOGRAPH - 0xE144: 0x74EE, //CJK UNIFIED IDEOGRAPH - 0xE145: 0x74F2, //CJK UNIFIED IDEOGRAPH - 0xE146: 0x74F0, //CJK UNIFIED IDEOGRAPH - 0xE147: 0x74F1, //CJK UNIFIED IDEOGRAPH - 0xE148: 0x74F8, //CJK UNIFIED IDEOGRAPH - 0xE149: 0x74F7, //CJK UNIFIED IDEOGRAPH - 0xE14A: 0x7504, //CJK UNIFIED IDEOGRAPH - 0xE14B: 0x7503, //CJK UNIFIED IDEOGRAPH - 0xE14C: 0x7505, //CJK UNIFIED IDEOGRAPH - 0xE14D: 0x750C, //CJK UNIFIED IDEOGRAPH - 0xE14E: 0x750E, //CJK UNIFIED IDEOGRAPH - 0xE14F: 0x750D, //CJK UNIFIED IDEOGRAPH - 0xE150: 0x7515, //CJK UNIFIED IDEOGRAPH - 0xE151: 0x7513, //CJK UNIFIED IDEOGRAPH - 0xE152: 0x751E, //CJK UNIFIED IDEOGRAPH - 0xE153: 0x7526, //CJK UNIFIED IDEOGRAPH - 0xE154: 0x752C, //CJK UNIFIED IDEOGRAPH - 0xE155: 0x753C, //CJK UNIFIED IDEOGRAPH - 0xE156: 0x7544, //CJK UNIFIED IDEOGRAPH - 0xE157: 0x754D, //CJK UNIFIED IDEOGRAPH - 0xE158: 0x754A, //CJK UNIFIED IDEOGRAPH - 0xE159: 0x7549, //CJK UNIFIED IDEOGRAPH - 0xE15A: 0x755B, //CJK UNIFIED IDEOGRAPH - 0xE15B: 0x7546, //CJK UNIFIED IDEOGRAPH - 0xE15C: 0x755A, //CJK UNIFIED IDEOGRAPH - 0xE15D: 0x7569, //CJK UNIFIED IDEOGRAPH - 0xE15E: 0x7564, //CJK UNIFIED IDEOGRAPH - 0xE15F: 0x7567, //CJK UNIFIED IDEOGRAPH - 0xE160: 0x756B, //CJK UNIFIED IDEOGRAPH - 0xE161: 0x756D, //CJK UNIFIED IDEOGRAPH - 0xE162: 0x7578, //CJK UNIFIED IDEOGRAPH - 0xE163: 0x7576, //CJK UNIFIED IDEOGRAPH - 0xE164: 0x7586, //CJK UNIFIED IDEOGRAPH - 0xE165: 0x7587, //CJK UNIFIED IDEOGRAPH - 0xE166: 0x7574, //CJK UNIFIED IDEOGRAPH - 0xE167: 0x758A, //CJK UNIFIED IDEOGRAPH - 0xE168: 0x7589, //CJK UNIFIED IDEOGRAPH - 0xE169: 0x7582, //CJK UNIFIED IDEOGRAPH - 0xE16A: 0x7594, //CJK UNIFIED IDEOGRAPH - 0xE16B: 0x759A, //CJK UNIFIED IDEOGRAPH - 0xE16C: 0x759D, //CJK UNIFIED IDEOGRAPH - 0xE16D: 0x75A5, //CJK UNIFIED IDEOGRAPH - 0xE16E: 0x75A3, //CJK UNIFIED IDEOGRAPH - 0xE16F: 0x75C2, //CJK UNIFIED IDEOGRAPH - 0xE170: 0x75B3, //CJK UNIFIED IDEOGRAPH - 0xE171: 0x75C3, //CJK UNIFIED IDEOGRAPH - 0xE172: 0x75B5, //CJK UNIFIED IDEOGRAPH - 0xE173: 0x75BD, //CJK UNIFIED IDEOGRAPH - 0xE174: 0x75B8, //CJK UNIFIED IDEOGRAPH - 0xE175: 0x75BC, //CJK UNIFIED IDEOGRAPH - 0xE176: 0x75B1, //CJK UNIFIED IDEOGRAPH - 0xE177: 0x75CD, //CJK UNIFIED IDEOGRAPH - 0xE178: 0x75CA, //CJK UNIFIED IDEOGRAPH - 0xE179: 0x75D2, //CJK UNIFIED IDEOGRAPH - 0xE17A: 0x75D9, //CJK UNIFIED IDEOGRAPH - 0xE17B: 0x75E3, //CJK UNIFIED IDEOGRAPH - 0xE17C: 0x75DE, //CJK UNIFIED IDEOGRAPH - 0xE17D: 0x75FE, //CJK UNIFIED IDEOGRAPH - 0xE17E: 0x75FF, //CJK UNIFIED IDEOGRAPH - 0xE180: 0x75FC, //CJK UNIFIED IDEOGRAPH - 0xE181: 0x7601, //CJK UNIFIED IDEOGRAPH - 0xE182: 0x75F0, //CJK UNIFIED IDEOGRAPH - 0xE183: 0x75FA, //CJK UNIFIED IDEOGRAPH - 0xE184: 0x75F2, //CJK UNIFIED IDEOGRAPH - 0xE185: 0x75F3, //CJK UNIFIED IDEOGRAPH - 0xE186: 0x760B, //CJK UNIFIED IDEOGRAPH - 0xE187: 0x760D, //CJK UNIFIED IDEOGRAPH - 0xE188: 0x7609, //CJK UNIFIED IDEOGRAPH - 0xE189: 0x761F, //CJK UNIFIED IDEOGRAPH - 0xE18A: 0x7627, //CJK UNIFIED IDEOGRAPH - 0xE18B: 0x7620, //CJK UNIFIED IDEOGRAPH - 0xE18C: 0x7621, //CJK UNIFIED IDEOGRAPH - 0xE18D: 0x7622, //CJK UNIFIED IDEOGRAPH - 0xE18E: 0x7624, //CJK UNIFIED IDEOGRAPH - 0xE18F: 0x7634, //CJK UNIFIED IDEOGRAPH - 0xE190: 0x7630, //CJK UNIFIED IDEOGRAPH - 0xE191: 0x763B, //CJK UNIFIED IDEOGRAPH - 0xE192: 0x7647, //CJK UNIFIED IDEOGRAPH - 0xE193: 0x7648, //CJK UNIFIED IDEOGRAPH - 0xE194: 0x7646, //CJK UNIFIED IDEOGRAPH - 0xE195: 0x765C, //CJK UNIFIED IDEOGRAPH - 0xE196: 0x7658, //CJK UNIFIED IDEOGRAPH - 0xE197: 0x7661, //CJK UNIFIED IDEOGRAPH - 0xE198: 0x7662, //CJK UNIFIED IDEOGRAPH - 0xE199: 0x7668, //CJK UNIFIED IDEOGRAPH - 0xE19A: 0x7669, //CJK UNIFIED IDEOGRAPH - 0xE19B: 0x766A, //CJK UNIFIED IDEOGRAPH - 0xE19C: 0x7667, //CJK UNIFIED IDEOGRAPH - 0xE19D: 0x766C, //CJK UNIFIED IDEOGRAPH - 0xE19E: 0x7670, //CJK UNIFIED IDEOGRAPH - 0xE19F: 0x7672, //CJK UNIFIED IDEOGRAPH - 0xE1A0: 0x7676, //CJK UNIFIED IDEOGRAPH - 0xE1A1: 0x7678, //CJK UNIFIED IDEOGRAPH - 0xE1A2: 0x767C, //CJK UNIFIED IDEOGRAPH - 0xE1A3: 0x7680, //CJK UNIFIED IDEOGRAPH - 0xE1A4: 0x7683, //CJK UNIFIED IDEOGRAPH - 0xE1A5: 0x7688, //CJK UNIFIED IDEOGRAPH - 0xE1A6: 0x768B, //CJK UNIFIED IDEOGRAPH - 0xE1A7: 0x768E, //CJK UNIFIED IDEOGRAPH - 0xE1A8: 0x7696, //CJK UNIFIED IDEOGRAPH - 0xE1A9: 0x7693, //CJK UNIFIED IDEOGRAPH - 0xE1AA: 0x7699, //CJK UNIFIED IDEOGRAPH - 0xE1AB: 0x769A, //CJK UNIFIED IDEOGRAPH - 0xE1AC: 0x76B0, //CJK UNIFIED IDEOGRAPH - 0xE1AD: 0x76B4, //CJK UNIFIED IDEOGRAPH - 0xE1AE: 0x76B8, //CJK UNIFIED IDEOGRAPH - 0xE1AF: 0x76B9, //CJK UNIFIED IDEOGRAPH - 0xE1B0: 0x76BA, //CJK UNIFIED IDEOGRAPH - 0xE1B1: 0x76C2, //CJK UNIFIED IDEOGRAPH - 0xE1B2: 0x76CD, //CJK UNIFIED IDEOGRAPH - 0xE1B3: 0x76D6, //CJK UNIFIED IDEOGRAPH - 0xE1B4: 0x76D2, //CJK UNIFIED IDEOGRAPH - 0xE1B5: 0x76DE, //CJK UNIFIED IDEOGRAPH - 0xE1B6: 0x76E1, //CJK UNIFIED IDEOGRAPH - 0xE1B7: 0x76E5, //CJK UNIFIED IDEOGRAPH - 0xE1B8: 0x76E7, //CJK UNIFIED IDEOGRAPH - 0xE1B9: 0x76EA, //CJK UNIFIED IDEOGRAPH - 0xE1BA: 0x862F, //CJK UNIFIED IDEOGRAPH - 0xE1BB: 0x76FB, //CJK UNIFIED IDEOGRAPH - 0xE1BC: 0x7708, //CJK UNIFIED IDEOGRAPH - 0xE1BD: 0x7707, //CJK UNIFIED IDEOGRAPH - 0xE1BE: 0x7704, //CJK UNIFIED IDEOGRAPH - 0xE1BF: 0x7729, //CJK UNIFIED IDEOGRAPH - 0xE1C0: 0x7724, //CJK UNIFIED IDEOGRAPH - 0xE1C1: 0x771E, //CJK UNIFIED IDEOGRAPH - 0xE1C2: 0x7725, //CJK UNIFIED IDEOGRAPH - 0xE1C3: 0x7726, //CJK UNIFIED IDEOGRAPH - 0xE1C4: 0x771B, //CJK UNIFIED IDEOGRAPH - 0xE1C5: 0x7737, //CJK UNIFIED IDEOGRAPH - 0xE1C6: 0x7738, //CJK UNIFIED IDEOGRAPH - 0xE1C7: 0x7747, //CJK UNIFIED IDEOGRAPH - 0xE1C8: 0x775A, //CJK UNIFIED IDEOGRAPH - 0xE1C9: 0x7768, //CJK UNIFIED IDEOGRAPH - 0xE1CA: 0x776B, //CJK UNIFIED IDEOGRAPH - 0xE1CB: 0x775B, //CJK UNIFIED IDEOGRAPH - 0xE1CC: 0x7765, //CJK UNIFIED IDEOGRAPH - 0xE1CD: 0x777F, //CJK UNIFIED IDEOGRAPH - 0xE1CE: 0x777E, //CJK UNIFIED IDEOGRAPH - 0xE1CF: 0x7779, //CJK UNIFIED IDEOGRAPH - 0xE1D0: 0x778E, //CJK UNIFIED IDEOGRAPH - 0xE1D1: 0x778B, //CJK UNIFIED IDEOGRAPH - 0xE1D2: 0x7791, //CJK UNIFIED IDEOGRAPH - 0xE1D3: 0x77A0, //CJK UNIFIED IDEOGRAPH - 0xE1D4: 0x779E, //CJK UNIFIED IDEOGRAPH - 0xE1D5: 0x77B0, //CJK UNIFIED IDEOGRAPH - 0xE1D6: 0x77B6, //CJK UNIFIED IDEOGRAPH - 0xE1D7: 0x77B9, //CJK UNIFIED IDEOGRAPH - 0xE1D8: 0x77BF, //CJK UNIFIED IDEOGRAPH - 0xE1D9: 0x77BC, //CJK UNIFIED IDEOGRAPH - 0xE1DA: 0x77BD, //CJK UNIFIED IDEOGRAPH - 0xE1DB: 0x77BB, //CJK UNIFIED IDEOGRAPH - 0xE1DC: 0x77C7, //CJK UNIFIED IDEOGRAPH - 0xE1DD: 0x77CD, //CJK UNIFIED IDEOGRAPH - 0xE1DE: 0x77D7, //CJK UNIFIED IDEOGRAPH - 0xE1DF: 0x77DA, //CJK UNIFIED IDEOGRAPH - 0xE1E0: 0x77DC, //CJK UNIFIED IDEOGRAPH - 0xE1E1: 0x77E3, //CJK UNIFIED IDEOGRAPH - 0xE1E2: 0x77EE, //CJK UNIFIED IDEOGRAPH - 0xE1E3: 0x77FC, //CJK UNIFIED IDEOGRAPH - 0xE1E4: 0x780C, //CJK UNIFIED IDEOGRAPH - 0xE1E5: 0x7812, //CJK UNIFIED IDEOGRAPH - 0xE1E6: 0x7926, //CJK UNIFIED IDEOGRAPH - 0xE1E7: 0x7820, //CJK UNIFIED IDEOGRAPH - 0xE1E8: 0x792A, //CJK UNIFIED IDEOGRAPH - 0xE1E9: 0x7845, //CJK UNIFIED IDEOGRAPH - 0xE1EA: 0x788E, //CJK UNIFIED IDEOGRAPH - 0xE1EB: 0x7874, //CJK UNIFIED IDEOGRAPH - 0xE1EC: 0x7886, //CJK UNIFIED IDEOGRAPH - 0xE1ED: 0x787C, //CJK UNIFIED IDEOGRAPH - 0xE1EE: 0x789A, //CJK UNIFIED IDEOGRAPH - 0xE1EF: 0x788C, //CJK UNIFIED IDEOGRAPH - 0xE1F0: 0x78A3, //CJK UNIFIED IDEOGRAPH - 0xE1F1: 0x78B5, //CJK UNIFIED IDEOGRAPH - 0xE1F2: 0x78AA, //CJK UNIFIED IDEOGRAPH - 0xE1F3: 0x78AF, //CJK UNIFIED IDEOGRAPH - 0xE1F4: 0x78D1, //CJK UNIFIED IDEOGRAPH - 0xE1F5: 0x78C6, //CJK UNIFIED IDEOGRAPH - 0xE1F6: 0x78CB, //CJK UNIFIED IDEOGRAPH - 0xE1F7: 0x78D4, //CJK UNIFIED IDEOGRAPH - 0xE1F8: 0x78BE, //CJK UNIFIED IDEOGRAPH - 0xE1F9: 0x78BC, //CJK UNIFIED IDEOGRAPH - 0xE1FA: 0x78C5, //CJK UNIFIED IDEOGRAPH - 0xE1FB: 0x78CA, //CJK UNIFIED IDEOGRAPH - 0xE1FC: 0x78EC, //CJK UNIFIED IDEOGRAPH - 0xE240: 0x78E7, //CJK UNIFIED IDEOGRAPH - 0xE241: 0x78DA, //CJK UNIFIED IDEOGRAPH - 0xE242: 0x78FD, //CJK UNIFIED IDEOGRAPH - 0xE243: 0x78F4, //CJK UNIFIED IDEOGRAPH - 0xE244: 0x7907, //CJK UNIFIED IDEOGRAPH - 0xE245: 0x7912, //CJK UNIFIED IDEOGRAPH - 0xE246: 0x7911, //CJK UNIFIED IDEOGRAPH - 0xE247: 0x7919, //CJK UNIFIED IDEOGRAPH - 0xE248: 0x792C, //CJK UNIFIED IDEOGRAPH - 0xE249: 0x792B, //CJK UNIFIED IDEOGRAPH - 0xE24A: 0x7940, //CJK UNIFIED IDEOGRAPH - 0xE24B: 0x7960, //CJK UNIFIED IDEOGRAPH - 0xE24C: 0x7957, //CJK UNIFIED IDEOGRAPH - 0xE24D: 0x795F, //CJK UNIFIED IDEOGRAPH - 0xE24E: 0x795A, //CJK UNIFIED IDEOGRAPH - 0xE24F: 0x7955, //CJK UNIFIED IDEOGRAPH - 0xE250: 0x7953, //CJK UNIFIED IDEOGRAPH - 0xE251: 0x797A, //CJK UNIFIED IDEOGRAPH - 0xE252: 0x797F, //CJK UNIFIED IDEOGRAPH - 0xE253: 0x798A, //CJK UNIFIED IDEOGRAPH - 0xE254: 0x799D, //CJK UNIFIED IDEOGRAPH - 0xE255: 0x79A7, //CJK UNIFIED IDEOGRAPH - 0xE256: 0x9F4B, //CJK UNIFIED IDEOGRAPH - 0xE257: 0x79AA, //CJK UNIFIED IDEOGRAPH - 0xE258: 0x79AE, //CJK UNIFIED IDEOGRAPH - 0xE259: 0x79B3, //CJK UNIFIED IDEOGRAPH - 0xE25A: 0x79B9, //CJK UNIFIED IDEOGRAPH - 0xE25B: 0x79BA, //CJK UNIFIED IDEOGRAPH - 0xE25C: 0x79C9, //CJK UNIFIED IDEOGRAPH - 0xE25D: 0x79D5, //CJK UNIFIED IDEOGRAPH - 0xE25E: 0x79E7, //CJK UNIFIED IDEOGRAPH - 0xE25F: 0x79EC, //CJK UNIFIED IDEOGRAPH - 0xE260: 0x79E1, //CJK UNIFIED IDEOGRAPH - 0xE261: 0x79E3, //CJK UNIFIED IDEOGRAPH - 0xE262: 0x7A08, //CJK UNIFIED IDEOGRAPH - 0xE263: 0x7A0D, //CJK UNIFIED IDEOGRAPH - 0xE264: 0x7A18, //CJK UNIFIED IDEOGRAPH - 0xE265: 0x7A19, //CJK UNIFIED IDEOGRAPH - 0xE266: 0x7A20, //CJK UNIFIED IDEOGRAPH - 0xE267: 0x7A1F, //CJK UNIFIED IDEOGRAPH - 0xE268: 0x7980, //CJK UNIFIED IDEOGRAPH - 0xE269: 0x7A31, //CJK UNIFIED IDEOGRAPH - 0xE26A: 0x7A3B, //CJK UNIFIED IDEOGRAPH - 0xE26B: 0x7A3E, //CJK UNIFIED IDEOGRAPH - 0xE26C: 0x7A37, //CJK UNIFIED IDEOGRAPH - 0xE26D: 0x7A43, //CJK UNIFIED IDEOGRAPH - 0xE26E: 0x7A57, //CJK UNIFIED IDEOGRAPH - 0xE26F: 0x7A49, //CJK UNIFIED IDEOGRAPH - 0xE270: 0x7A61, //CJK UNIFIED IDEOGRAPH - 0xE271: 0x7A62, //CJK UNIFIED IDEOGRAPH - 0xE272: 0x7A69, //CJK UNIFIED IDEOGRAPH - 0xE273: 0x9F9D, //CJK UNIFIED IDEOGRAPH - 0xE274: 0x7A70, //CJK UNIFIED IDEOGRAPH - 0xE275: 0x7A79, //CJK UNIFIED IDEOGRAPH - 0xE276: 0x7A7D, //CJK UNIFIED IDEOGRAPH - 0xE277: 0x7A88, //CJK UNIFIED IDEOGRAPH - 0xE278: 0x7A97, //CJK UNIFIED IDEOGRAPH - 0xE279: 0x7A95, //CJK UNIFIED IDEOGRAPH - 0xE27A: 0x7A98, //CJK UNIFIED IDEOGRAPH - 0xE27B: 0x7A96, //CJK UNIFIED IDEOGRAPH - 0xE27C: 0x7AA9, //CJK UNIFIED IDEOGRAPH - 0xE27D: 0x7AC8, //CJK UNIFIED IDEOGRAPH - 0xE27E: 0x7AB0, //CJK UNIFIED IDEOGRAPH - 0xE280: 0x7AB6, //CJK UNIFIED IDEOGRAPH - 0xE281: 0x7AC5, //CJK UNIFIED IDEOGRAPH - 0xE282: 0x7AC4, //CJK UNIFIED IDEOGRAPH - 0xE283: 0x7ABF, //CJK UNIFIED IDEOGRAPH - 0xE284: 0x9083, //CJK UNIFIED IDEOGRAPH - 0xE285: 0x7AC7, //CJK UNIFIED IDEOGRAPH - 0xE286: 0x7ACA, //CJK UNIFIED IDEOGRAPH - 0xE287: 0x7ACD, //CJK UNIFIED IDEOGRAPH - 0xE288: 0x7ACF, //CJK UNIFIED IDEOGRAPH - 0xE289: 0x7AD5, //CJK UNIFIED IDEOGRAPH - 0xE28A: 0x7AD3, //CJK UNIFIED IDEOGRAPH - 0xE28B: 0x7AD9, //CJK UNIFIED IDEOGRAPH - 0xE28C: 0x7ADA, //CJK UNIFIED IDEOGRAPH - 0xE28D: 0x7ADD, //CJK UNIFIED IDEOGRAPH - 0xE28E: 0x7AE1, //CJK UNIFIED IDEOGRAPH - 0xE28F: 0x7AE2, //CJK UNIFIED IDEOGRAPH - 0xE290: 0x7AE6, //CJK UNIFIED IDEOGRAPH - 0xE291: 0x7AED, //CJK UNIFIED IDEOGRAPH - 0xE292: 0x7AF0, //CJK UNIFIED IDEOGRAPH - 0xE293: 0x7B02, //CJK UNIFIED IDEOGRAPH - 0xE294: 0x7B0F, //CJK UNIFIED IDEOGRAPH - 0xE295: 0x7B0A, //CJK UNIFIED IDEOGRAPH - 0xE296: 0x7B06, //CJK UNIFIED IDEOGRAPH - 0xE297: 0x7B33, //CJK UNIFIED IDEOGRAPH - 0xE298: 0x7B18, //CJK UNIFIED IDEOGRAPH - 0xE299: 0x7B19, //CJK UNIFIED IDEOGRAPH - 0xE29A: 0x7B1E, //CJK UNIFIED IDEOGRAPH - 0xE29B: 0x7B35, //CJK UNIFIED IDEOGRAPH - 0xE29C: 0x7B28, //CJK UNIFIED IDEOGRAPH - 0xE29D: 0x7B36, //CJK UNIFIED IDEOGRAPH - 0xE29E: 0x7B50, //CJK UNIFIED IDEOGRAPH - 0xE29F: 0x7B7A, //CJK UNIFIED IDEOGRAPH - 0xE2A0: 0x7B04, //CJK UNIFIED IDEOGRAPH - 0xE2A1: 0x7B4D, //CJK UNIFIED IDEOGRAPH - 0xE2A2: 0x7B0B, //CJK UNIFIED IDEOGRAPH - 0xE2A3: 0x7B4C, //CJK UNIFIED IDEOGRAPH - 0xE2A4: 0x7B45, //CJK UNIFIED IDEOGRAPH - 0xE2A5: 0x7B75, //CJK UNIFIED IDEOGRAPH - 0xE2A6: 0x7B65, //CJK UNIFIED IDEOGRAPH - 0xE2A7: 0x7B74, //CJK UNIFIED IDEOGRAPH - 0xE2A8: 0x7B67, //CJK UNIFIED IDEOGRAPH - 0xE2A9: 0x7B70, //CJK UNIFIED IDEOGRAPH - 0xE2AA: 0x7B71, //CJK UNIFIED IDEOGRAPH - 0xE2AB: 0x7B6C, //CJK UNIFIED IDEOGRAPH - 0xE2AC: 0x7B6E, //CJK UNIFIED IDEOGRAPH - 0xE2AD: 0x7B9D, //CJK UNIFIED IDEOGRAPH - 0xE2AE: 0x7B98, //CJK UNIFIED IDEOGRAPH - 0xE2AF: 0x7B9F, //CJK UNIFIED IDEOGRAPH - 0xE2B0: 0x7B8D, //CJK UNIFIED IDEOGRAPH - 0xE2B1: 0x7B9C, //CJK UNIFIED IDEOGRAPH - 0xE2B2: 0x7B9A, //CJK UNIFIED IDEOGRAPH - 0xE2B3: 0x7B8B, //CJK UNIFIED IDEOGRAPH - 0xE2B4: 0x7B92, //CJK UNIFIED IDEOGRAPH - 0xE2B5: 0x7B8F, //CJK UNIFIED IDEOGRAPH - 0xE2B6: 0x7B5D, //CJK UNIFIED IDEOGRAPH - 0xE2B7: 0x7B99, //CJK UNIFIED IDEOGRAPH - 0xE2B8: 0x7BCB, //CJK UNIFIED IDEOGRAPH - 0xE2B9: 0x7BC1, //CJK UNIFIED IDEOGRAPH - 0xE2BA: 0x7BCC, //CJK UNIFIED IDEOGRAPH - 0xE2BB: 0x7BCF, //CJK UNIFIED IDEOGRAPH - 0xE2BC: 0x7BB4, //CJK UNIFIED IDEOGRAPH - 0xE2BD: 0x7BC6, //CJK UNIFIED IDEOGRAPH - 0xE2BE: 0x7BDD, //CJK UNIFIED IDEOGRAPH - 0xE2BF: 0x7BE9, //CJK UNIFIED IDEOGRAPH - 0xE2C0: 0x7C11, //CJK UNIFIED IDEOGRAPH - 0xE2C1: 0x7C14, //CJK UNIFIED IDEOGRAPH - 0xE2C2: 0x7BE6, //CJK UNIFIED IDEOGRAPH - 0xE2C3: 0x7BE5, //CJK UNIFIED IDEOGRAPH - 0xE2C4: 0x7C60, //CJK UNIFIED IDEOGRAPH - 0xE2C5: 0x7C00, //CJK UNIFIED IDEOGRAPH - 0xE2C6: 0x7C07, //CJK UNIFIED IDEOGRAPH - 0xE2C7: 0x7C13, //CJK UNIFIED IDEOGRAPH - 0xE2C8: 0x7BF3, //CJK UNIFIED IDEOGRAPH - 0xE2C9: 0x7BF7, //CJK UNIFIED IDEOGRAPH - 0xE2CA: 0x7C17, //CJK UNIFIED IDEOGRAPH - 0xE2CB: 0x7C0D, //CJK UNIFIED IDEOGRAPH - 0xE2CC: 0x7BF6, //CJK UNIFIED IDEOGRAPH - 0xE2CD: 0x7C23, //CJK UNIFIED IDEOGRAPH - 0xE2CE: 0x7C27, //CJK UNIFIED IDEOGRAPH - 0xE2CF: 0x7C2A, //CJK UNIFIED IDEOGRAPH - 0xE2D0: 0x7C1F, //CJK UNIFIED IDEOGRAPH - 0xE2D1: 0x7C37, //CJK UNIFIED IDEOGRAPH - 0xE2D2: 0x7C2B, //CJK UNIFIED IDEOGRAPH - 0xE2D3: 0x7C3D, //CJK UNIFIED IDEOGRAPH - 0xE2D4: 0x7C4C, //CJK UNIFIED IDEOGRAPH - 0xE2D5: 0x7C43, //CJK UNIFIED IDEOGRAPH - 0xE2D6: 0x7C54, //CJK UNIFIED IDEOGRAPH - 0xE2D7: 0x7C4F, //CJK UNIFIED IDEOGRAPH - 0xE2D8: 0x7C40, //CJK UNIFIED IDEOGRAPH - 0xE2D9: 0x7C50, //CJK UNIFIED IDEOGRAPH - 0xE2DA: 0x7C58, //CJK UNIFIED IDEOGRAPH - 0xE2DB: 0x7C5F, //CJK UNIFIED IDEOGRAPH - 0xE2DC: 0x7C64, //CJK UNIFIED IDEOGRAPH - 0xE2DD: 0x7C56, //CJK UNIFIED IDEOGRAPH - 0xE2DE: 0x7C65, //CJK UNIFIED IDEOGRAPH - 0xE2DF: 0x7C6C, //CJK UNIFIED IDEOGRAPH - 0xE2E0: 0x7C75, //CJK UNIFIED IDEOGRAPH - 0xE2E1: 0x7C83, //CJK UNIFIED IDEOGRAPH - 0xE2E2: 0x7C90, //CJK UNIFIED IDEOGRAPH - 0xE2E3: 0x7CA4, //CJK UNIFIED IDEOGRAPH - 0xE2E4: 0x7CAD, //CJK UNIFIED IDEOGRAPH - 0xE2E5: 0x7CA2, //CJK UNIFIED IDEOGRAPH - 0xE2E6: 0x7CAB, //CJK UNIFIED IDEOGRAPH - 0xE2E7: 0x7CA1, //CJK UNIFIED IDEOGRAPH - 0xE2E8: 0x7CA8, //CJK UNIFIED IDEOGRAPH - 0xE2E9: 0x7CB3, //CJK UNIFIED IDEOGRAPH - 0xE2EA: 0x7CB2, //CJK UNIFIED IDEOGRAPH - 0xE2EB: 0x7CB1, //CJK UNIFIED IDEOGRAPH - 0xE2EC: 0x7CAE, //CJK UNIFIED IDEOGRAPH - 0xE2ED: 0x7CB9, //CJK UNIFIED IDEOGRAPH - 0xE2EE: 0x7CBD, //CJK UNIFIED IDEOGRAPH - 0xE2EF: 0x7CC0, //CJK UNIFIED IDEOGRAPH - 0xE2F0: 0x7CC5, //CJK UNIFIED IDEOGRAPH - 0xE2F1: 0x7CC2, //CJK UNIFIED IDEOGRAPH - 0xE2F2: 0x7CD8, //CJK UNIFIED IDEOGRAPH - 0xE2F3: 0x7CD2, //CJK UNIFIED IDEOGRAPH - 0xE2F4: 0x7CDC, //CJK UNIFIED IDEOGRAPH - 0xE2F5: 0x7CE2, //CJK UNIFIED IDEOGRAPH - 0xE2F6: 0x9B3B, //CJK UNIFIED IDEOGRAPH - 0xE2F7: 0x7CEF, //CJK UNIFIED IDEOGRAPH - 0xE2F8: 0x7CF2, //CJK UNIFIED IDEOGRAPH - 0xE2F9: 0x7CF4, //CJK UNIFIED IDEOGRAPH - 0xE2FA: 0x7CF6, //CJK UNIFIED IDEOGRAPH - 0xE2FB: 0x7CFA, //CJK UNIFIED IDEOGRAPH - 0xE2FC: 0x7D06, //CJK UNIFIED IDEOGRAPH - 0xE340: 0x7D02, //CJK UNIFIED IDEOGRAPH - 0xE341: 0x7D1C, //CJK UNIFIED IDEOGRAPH - 0xE342: 0x7D15, //CJK UNIFIED IDEOGRAPH - 0xE343: 0x7D0A, //CJK UNIFIED IDEOGRAPH - 0xE344: 0x7D45, //CJK UNIFIED IDEOGRAPH - 0xE345: 0x7D4B, //CJK UNIFIED IDEOGRAPH - 0xE346: 0x7D2E, //CJK UNIFIED IDEOGRAPH - 0xE347: 0x7D32, //CJK UNIFIED IDEOGRAPH - 0xE348: 0x7D3F, //CJK UNIFIED IDEOGRAPH - 0xE349: 0x7D35, //CJK UNIFIED IDEOGRAPH - 0xE34A: 0x7D46, //CJK UNIFIED IDEOGRAPH - 0xE34B: 0x7D73, //CJK UNIFIED IDEOGRAPH - 0xE34C: 0x7D56, //CJK UNIFIED IDEOGRAPH - 0xE34D: 0x7D4E, //CJK UNIFIED IDEOGRAPH - 0xE34E: 0x7D72, //CJK UNIFIED IDEOGRAPH - 0xE34F: 0x7D68, //CJK UNIFIED IDEOGRAPH - 0xE350: 0x7D6E, //CJK UNIFIED IDEOGRAPH - 0xE351: 0x7D4F, //CJK UNIFIED IDEOGRAPH - 0xE352: 0x7D63, //CJK UNIFIED IDEOGRAPH - 0xE353: 0x7D93, //CJK UNIFIED IDEOGRAPH - 0xE354: 0x7D89, //CJK UNIFIED IDEOGRAPH - 0xE355: 0x7D5B, //CJK UNIFIED IDEOGRAPH - 0xE356: 0x7D8F, //CJK UNIFIED IDEOGRAPH - 0xE357: 0x7D7D, //CJK UNIFIED IDEOGRAPH - 0xE358: 0x7D9B, //CJK UNIFIED IDEOGRAPH - 0xE359: 0x7DBA, //CJK UNIFIED IDEOGRAPH - 0xE35A: 0x7DAE, //CJK UNIFIED IDEOGRAPH - 0xE35B: 0x7DA3, //CJK UNIFIED IDEOGRAPH - 0xE35C: 0x7DB5, //CJK UNIFIED IDEOGRAPH - 0xE35D: 0x7DC7, //CJK UNIFIED IDEOGRAPH - 0xE35E: 0x7DBD, //CJK UNIFIED IDEOGRAPH - 0xE35F: 0x7DAB, //CJK UNIFIED IDEOGRAPH - 0xE360: 0x7E3D, //CJK UNIFIED IDEOGRAPH - 0xE361: 0x7DA2, //CJK UNIFIED IDEOGRAPH - 0xE362: 0x7DAF, //CJK UNIFIED IDEOGRAPH - 0xE363: 0x7DDC, //CJK UNIFIED IDEOGRAPH - 0xE364: 0x7DB8, //CJK UNIFIED IDEOGRAPH - 0xE365: 0x7D9F, //CJK UNIFIED IDEOGRAPH - 0xE366: 0x7DB0, //CJK UNIFIED IDEOGRAPH - 0xE367: 0x7DD8, //CJK UNIFIED IDEOGRAPH - 0xE368: 0x7DDD, //CJK UNIFIED IDEOGRAPH - 0xE369: 0x7DE4, //CJK UNIFIED IDEOGRAPH - 0xE36A: 0x7DDE, //CJK UNIFIED IDEOGRAPH - 0xE36B: 0x7DFB, //CJK UNIFIED IDEOGRAPH - 0xE36C: 0x7DF2, //CJK UNIFIED IDEOGRAPH - 0xE36D: 0x7DE1, //CJK UNIFIED IDEOGRAPH - 0xE36E: 0x7E05, //CJK UNIFIED IDEOGRAPH - 0xE36F: 0x7E0A, //CJK UNIFIED IDEOGRAPH - 0xE370: 0x7E23, //CJK UNIFIED IDEOGRAPH - 0xE371: 0x7E21, //CJK UNIFIED IDEOGRAPH - 0xE372: 0x7E12, //CJK UNIFIED IDEOGRAPH - 0xE373: 0x7E31, //CJK UNIFIED IDEOGRAPH - 0xE374: 0x7E1F, //CJK UNIFIED IDEOGRAPH - 0xE375: 0x7E09, //CJK UNIFIED IDEOGRAPH - 0xE376: 0x7E0B, //CJK UNIFIED IDEOGRAPH - 0xE377: 0x7E22, //CJK UNIFIED IDEOGRAPH - 0xE378: 0x7E46, //CJK UNIFIED IDEOGRAPH - 0xE379: 0x7E66, //CJK UNIFIED IDEOGRAPH - 0xE37A: 0x7E3B, //CJK UNIFIED IDEOGRAPH - 0xE37B: 0x7E35, //CJK UNIFIED IDEOGRAPH - 0xE37C: 0x7E39, //CJK UNIFIED IDEOGRAPH - 0xE37D: 0x7E43, //CJK UNIFIED IDEOGRAPH - 0xE37E: 0x7E37, //CJK UNIFIED IDEOGRAPH - 0xE380: 0x7E32, //CJK UNIFIED IDEOGRAPH - 0xE381: 0x7E3A, //CJK UNIFIED IDEOGRAPH - 0xE382: 0x7E67, //CJK UNIFIED IDEOGRAPH - 0xE383: 0x7E5D, //CJK UNIFIED IDEOGRAPH - 0xE384: 0x7E56, //CJK UNIFIED IDEOGRAPH - 0xE385: 0x7E5E, //CJK UNIFIED IDEOGRAPH - 0xE386: 0x7E59, //CJK UNIFIED IDEOGRAPH - 0xE387: 0x7E5A, //CJK UNIFIED IDEOGRAPH - 0xE388: 0x7E79, //CJK UNIFIED IDEOGRAPH - 0xE389: 0x7E6A, //CJK UNIFIED IDEOGRAPH - 0xE38A: 0x7E69, //CJK UNIFIED IDEOGRAPH - 0xE38B: 0x7E7C, //CJK UNIFIED IDEOGRAPH - 0xE38C: 0x7E7B, //CJK UNIFIED IDEOGRAPH - 0xE38D: 0x7E83, //CJK UNIFIED IDEOGRAPH - 0xE38E: 0x7DD5, //CJK UNIFIED IDEOGRAPH - 0xE38F: 0x7E7D, //CJK UNIFIED IDEOGRAPH - 0xE390: 0x8FAE, //CJK UNIFIED IDEOGRAPH - 0xE391: 0x7E7F, //CJK UNIFIED IDEOGRAPH - 0xE392: 0x7E88, //CJK UNIFIED IDEOGRAPH - 0xE393: 0x7E89, //CJK UNIFIED IDEOGRAPH - 0xE394: 0x7E8C, //CJK UNIFIED IDEOGRAPH - 0xE395: 0x7E92, //CJK UNIFIED IDEOGRAPH - 0xE396: 0x7E90, //CJK UNIFIED IDEOGRAPH - 0xE397: 0x7E93, //CJK UNIFIED IDEOGRAPH - 0xE398: 0x7E94, //CJK UNIFIED IDEOGRAPH - 0xE399: 0x7E96, //CJK UNIFIED IDEOGRAPH - 0xE39A: 0x7E8E, //CJK UNIFIED IDEOGRAPH - 0xE39B: 0x7E9B, //CJK UNIFIED IDEOGRAPH - 0xE39C: 0x7E9C, //CJK UNIFIED IDEOGRAPH - 0xE39D: 0x7F38, //CJK UNIFIED IDEOGRAPH - 0xE39E: 0x7F3A, //CJK UNIFIED IDEOGRAPH - 0xE39F: 0x7F45, //CJK UNIFIED IDEOGRAPH - 0xE3A0: 0x7F4C, //CJK UNIFIED IDEOGRAPH - 0xE3A1: 0x7F4D, //CJK UNIFIED IDEOGRAPH - 0xE3A2: 0x7F4E, //CJK UNIFIED IDEOGRAPH - 0xE3A3: 0x7F50, //CJK UNIFIED IDEOGRAPH - 0xE3A4: 0x7F51, //CJK UNIFIED IDEOGRAPH - 0xE3A5: 0x7F55, //CJK UNIFIED IDEOGRAPH - 0xE3A6: 0x7F54, //CJK UNIFIED IDEOGRAPH - 0xE3A7: 0x7F58, //CJK UNIFIED IDEOGRAPH - 0xE3A8: 0x7F5F, //CJK UNIFIED IDEOGRAPH - 0xE3A9: 0x7F60, //CJK UNIFIED IDEOGRAPH - 0xE3AA: 0x7F68, //CJK UNIFIED IDEOGRAPH - 0xE3AB: 0x7F69, //CJK UNIFIED IDEOGRAPH - 0xE3AC: 0x7F67, //CJK UNIFIED IDEOGRAPH - 0xE3AD: 0x7F78, //CJK UNIFIED IDEOGRAPH - 0xE3AE: 0x7F82, //CJK UNIFIED IDEOGRAPH - 0xE3AF: 0x7F86, //CJK UNIFIED IDEOGRAPH - 0xE3B0: 0x7F83, //CJK UNIFIED IDEOGRAPH - 0xE3B1: 0x7F88, //CJK UNIFIED IDEOGRAPH - 0xE3B2: 0x7F87, //CJK UNIFIED IDEOGRAPH - 0xE3B3: 0x7F8C, //CJK UNIFIED IDEOGRAPH - 0xE3B4: 0x7F94, //CJK UNIFIED IDEOGRAPH - 0xE3B5: 0x7F9E, //CJK UNIFIED IDEOGRAPH - 0xE3B6: 0x7F9D, //CJK UNIFIED IDEOGRAPH - 0xE3B7: 0x7F9A, //CJK UNIFIED IDEOGRAPH - 0xE3B8: 0x7FA3, //CJK UNIFIED IDEOGRAPH - 0xE3B9: 0x7FAF, //CJK UNIFIED IDEOGRAPH - 0xE3BA: 0x7FB2, //CJK UNIFIED IDEOGRAPH - 0xE3BB: 0x7FB9, //CJK UNIFIED IDEOGRAPH - 0xE3BC: 0x7FAE, //CJK UNIFIED IDEOGRAPH - 0xE3BD: 0x7FB6, //CJK UNIFIED IDEOGRAPH - 0xE3BE: 0x7FB8, //CJK UNIFIED IDEOGRAPH - 0xE3BF: 0x8B71, //CJK UNIFIED IDEOGRAPH - 0xE3C0: 0x7FC5, //CJK UNIFIED IDEOGRAPH - 0xE3C1: 0x7FC6, //CJK UNIFIED IDEOGRAPH - 0xE3C2: 0x7FCA, //CJK UNIFIED IDEOGRAPH - 0xE3C3: 0x7FD5, //CJK UNIFIED IDEOGRAPH - 0xE3C4: 0x7FD4, //CJK UNIFIED IDEOGRAPH - 0xE3C5: 0x7FE1, //CJK UNIFIED IDEOGRAPH - 0xE3C6: 0x7FE6, //CJK UNIFIED IDEOGRAPH - 0xE3C7: 0x7FE9, //CJK UNIFIED IDEOGRAPH - 0xE3C8: 0x7FF3, //CJK UNIFIED IDEOGRAPH - 0xE3C9: 0x7FF9, //CJK UNIFIED IDEOGRAPH - 0xE3CA: 0x98DC, //CJK UNIFIED IDEOGRAPH - 0xE3CB: 0x8006, //CJK UNIFIED IDEOGRAPH - 0xE3CC: 0x8004, //CJK UNIFIED IDEOGRAPH - 0xE3CD: 0x800B, //CJK UNIFIED IDEOGRAPH - 0xE3CE: 0x8012, //CJK UNIFIED IDEOGRAPH - 0xE3CF: 0x8018, //CJK UNIFIED IDEOGRAPH - 0xE3D0: 0x8019, //CJK UNIFIED IDEOGRAPH - 0xE3D1: 0x801C, //CJK UNIFIED IDEOGRAPH - 0xE3D2: 0x8021, //CJK UNIFIED IDEOGRAPH - 0xE3D3: 0x8028, //CJK UNIFIED IDEOGRAPH - 0xE3D4: 0x803F, //CJK UNIFIED IDEOGRAPH - 0xE3D5: 0x803B, //CJK UNIFIED IDEOGRAPH - 0xE3D6: 0x804A, //CJK UNIFIED IDEOGRAPH - 0xE3D7: 0x8046, //CJK UNIFIED IDEOGRAPH - 0xE3D8: 0x8052, //CJK UNIFIED IDEOGRAPH - 0xE3D9: 0x8058, //CJK UNIFIED IDEOGRAPH - 0xE3DA: 0x805A, //CJK UNIFIED IDEOGRAPH - 0xE3DB: 0x805F, //CJK UNIFIED IDEOGRAPH - 0xE3DC: 0x8062, //CJK UNIFIED IDEOGRAPH - 0xE3DD: 0x8068, //CJK UNIFIED IDEOGRAPH - 0xE3DE: 0x8073, //CJK UNIFIED IDEOGRAPH - 0xE3DF: 0x8072, //CJK UNIFIED IDEOGRAPH - 0xE3E0: 0x8070, //CJK UNIFIED IDEOGRAPH - 0xE3E1: 0x8076, //CJK UNIFIED IDEOGRAPH - 0xE3E2: 0x8079, //CJK UNIFIED IDEOGRAPH - 0xE3E3: 0x807D, //CJK UNIFIED IDEOGRAPH - 0xE3E4: 0x807F, //CJK UNIFIED IDEOGRAPH - 0xE3E5: 0x8084, //CJK UNIFIED IDEOGRAPH - 0xE3E6: 0x8086, //CJK UNIFIED IDEOGRAPH - 0xE3E7: 0x8085, //CJK UNIFIED IDEOGRAPH - 0xE3E8: 0x809B, //CJK UNIFIED IDEOGRAPH - 0xE3E9: 0x8093, //CJK UNIFIED IDEOGRAPH - 0xE3EA: 0x809A, //CJK UNIFIED IDEOGRAPH - 0xE3EB: 0x80AD, //CJK UNIFIED IDEOGRAPH - 0xE3EC: 0x5190, //CJK UNIFIED IDEOGRAPH - 0xE3ED: 0x80AC, //CJK UNIFIED IDEOGRAPH - 0xE3EE: 0x80DB, //CJK UNIFIED IDEOGRAPH - 0xE3EF: 0x80E5, //CJK UNIFIED IDEOGRAPH - 0xE3F0: 0x80D9, //CJK UNIFIED IDEOGRAPH - 0xE3F1: 0x80DD, //CJK UNIFIED IDEOGRAPH - 0xE3F2: 0x80C4, //CJK UNIFIED IDEOGRAPH - 0xE3F3: 0x80DA, //CJK UNIFIED IDEOGRAPH - 0xE3F4: 0x80D6, //CJK UNIFIED IDEOGRAPH - 0xE3F5: 0x8109, //CJK UNIFIED IDEOGRAPH - 0xE3F6: 0x80EF, //CJK UNIFIED IDEOGRAPH - 0xE3F7: 0x80F1, //CJK UNIFIED IDEOGRAPH - 0xE3F8: 0x811B, //CJK UNIFIED IDEOGRAPH - 0xE3F9: 0x8129, //CJK UNIFIED IDEOGRAPH - 0xE3FA: 0x8123, //CJK UNIFIED IDEOGRAPH - 0xE3FB: 0x812F, //CJK UNIFIED IDEOGRAPH - 0xE3FC: 0x814B, //CJK UNIFIED IDEOGRAPH - 0xE440: 0x968B, //CJK UNIFIED IDEOGRAPH - 0xE441: 0x8146, //CJK UNIFIED IDEOGRAPH - 0xE442: 0x813E, //CJK UNIFIED IDEOGRAPH - 0xE443: 0x8153, //CJK UNIFIED IDEOGRAPH - 0xE444: 0x8151, //CJK UNIFIED IDEOGRAPH - 0xE445: 0x80FC, //CJK UNIFIED IDEOGRAPH - 0xE446: 0x8171, //CJK UNIFIED IDEOGRAPH - 0xE447: 0x816E, //CJK UNIFIED IDEOGRAPH - 0xE448: 0x8165, //CJK UNIFIED IDEOGRAPH - 0xE449: 0x8166, //CJK UNIFIED IDEOGRAPH - 0xE44A: 0x8174, //CJK UNIFIED IDEOGRAPH - 0xE44B: 0x8183, //CJK UNIFIED IDEOGRAPH - 0xE44C: 0x8188, //CJK UNIFIED IDEOGRAPH - 0xE44D: 0x818A, //CJK UNIFIED IDEOGRAPH - 0xE44E: 0x8180, //CJK UNIFIED IDEOGRAPH - 0xE44F: 0x8182, //CJK UNIFIED IDEOGRAPH - 0xE450: 0x81A0, //CJK UNIFIED IDEOGRAPH - 0xE451: 0x8195, //CJK UNIFIED IDEOGRAPH - 0xE452: 0x81A4, //CJK UNIFIED IDEOGRAPH - 0xE453: 0x81A3, //CJK UNIFIED IDEOGRAPH - 0xE454: 0x815F, //CJK UNIFIED IDEOGRAPH - 0xE455: 0x8193, //CJK UNIFIED IDEOGRAPH - 0xE456: 0x81A9, //CJK UNIFIED IDEOGRAPH - 0xE457: 0x81B0, //CJK UNIFIED IDEOGRAPH - 0xE458: 0x81B5, //CJK UNIFIED IDEOGRAPH - 0xE459: 0x81BE, //CJK UNIFIED IDEOGRAPH - 0xE45A: 0x81B8, //CJK UNIFIED IDEOGRAPH - 0xE45B: 0x81BD, //CJK UNIFIED IDEOGRAPH - 0xE45C: 0x81C0, //CJK UNIFIED IDEOGRAPH - 0xE45D: 0x81C2, //CJK UNIFIED IDEOGRAPH - 0xE45E: 0x81BA, //CJK UNIFIED IDEOGRAPH - 0xE45F: 0x81C9, //CJK UNIFIED IDEOGRAPH - 0xE460: 0x81CD, //CJK UNIFIED IDEOGRAPH - 0xE461: 0x81D1, //CJK UNIFIED IDEOGRAPH - 0xE462: 0x81D9, //CJK UNIFIED IDEOGRAPH - 0xE463: 0x81D8, //CJK UNIFIED IDEOGRAPH - 0xE464: 0x81C8, //CJK UNIFIED IDEOGRAPH - 0xE465: 0x81DA, //CJK UNIFIED IDEOGRAPH - 0xE466: 0x81DF, //CJK UNIFIED IDEOGRAPH - 0xE467: 0x81E0, //CJK UNIFIED IDEOGRAPH - 0xE468: 0x81E7, //CJK UNIFIED IDEOGRAPH - 0xE469: 0x81FA, //CJK UNIFIED IDEOGRAPH - 0xE46A: 0x81FB, //CJK UNIFIED IDEOGRAPH - 0xE46B: 0x81FE, //CJK UNIFIED IDEOGRAPH - 0xE46C: 0x8201, //CJK UNIFIED IDEOGRAPH - 0xE46D: 0x8202, //CJK UNIFIED IDEOGRAPH - 0xE46E: 0x8205, //CJK UNIFIED IDEOGRAPH - 0xE46F: 0x8207, //CJK UNIFIED IDEOGRAPH - 0xE470: 0x820A, //CJK UNIFIED IDEOGRAPH - 0xE471: 0x820D, //CJK UNIFIED IDEOGRAPH - 0xE472: 0x8210, //CJK UNIFIED IDEOGRAPH - 0xE473: 0x8216, //CJK UNIFIED IDEOGRAPH - 0xE474: 0x8229, //CJK UNIFIED IDEOGRAPH - 0xE475: 0x822B, //CJK UNIFIED IDEOGRAPH - 0xE476: 0x8238, //CJK UNIFIED IDEOGRAPH - 0xE477: 0x8233, //CJK UNIFIED IDEOGRAPH - 0xE478: 0x8240, //CJK UNIFIED IDEOGRAPH - 0xE479: 0x8259, //CJK UNIFIED IDEOGRAPH - 0xE47A: 0x8258, //CJK UNIFIED IDEOGRAPH - 0xE47B: 0x825D, //CJK UNIFIED IDEOGRAPH - 0xE47C: 0x825A, //CJK UNIFIED IDEOGRAPH - 0xE47D: 0x825F, //CJK UNIFIED IDEOGRAPH - 0xE47E: 0x8264, //CJK UNIFIED IDEOGRAPH - 0xE480: 0x8262, //CJK UNIFIED IDEOGRAPH - 0xE481: 0x8268, //CJK UNIFIED IDEOGRAPH - 0xE482: 0x826A, //CJK UNIFIED IDEOGRAPH - 0xE483: 0x826B, //CJK UNIFIED IDEOGRAPH - 0xE484: 0x822E, //CJK UNIFIED IDEOGRAPH - 0xE485: 0x8271, //CJK UNIFIED IDEOGRAPH - 0xE486: 0x8277, //CJK UNIFIED IDEOGRAPH - 0xE487: 0x8278, //CJK UNIFIED IDEOGRAPH - 0xE488: 0x827E, //CJK UNIFIED IDEOGRAPH - 0xE489: 0x828D, //CJK UNIFIED IDEOGRAPH - 0xE48A: 0x8292, //CJK UNIFIED IDEOGRAPH - 0xE48B: 0x82AB, //CJK UNIFIED IDEOGRAPH - 0xE48C: 0x829F, //CJK UNIFIED IDEOGRAPH - 0xE48D: 0x82BB, //CJK UNIFIED IDEOGRAPH - 0xE48E: 0x82AC, //CJK UNIFIED IDEOGRAPH - 0xE48F: 0x82E1, //CJK UNIFIED IDEOGRAPH - 0xE490: 0x82E3, //CJK UNIFIED IDEOGRAPH - 0xE491: 0x82DF, //CJK UNIFIED IDEOGRAPH - 0xE492: 0x82D2, //CJK UNIFIED IDEOGRAPH - 0xE493: 0x82F4, //CJK UNIFIED IDEOGRAPH - 0xE494: 0x82F3, //CJK UNIFIED IDEOGRAPH - 0xE495: 0x82FA, //CJK UNIFIED IDEOGRAPH - 0xE496: 0x8393, //CJK UNIFIED IDEOGRAPH - 0xE497: 0x8303, //CJK UNIFIED IDEOGRAPH - 0xE498: 0x82FB, //CJK UNIFIED IDEOGRAPH - 0xE499: 0x82F9, //CJK UNIFIED IDEOGRAPH - 0xE49A: 0x82DE, //CJK UNIFIED IDEOGRAPH - 0xE49B: 0x8306, //CJK UNIFIED IDEOGRAPH - 0xE49C: 0x82DC, //CJK UNIFIED IDEOGRAPH - 0xE49D: 0x8309, //CJK UNIFIED IDEOGRAPH - 0xE49E: 0x82D9, //CJK UNIFIED IDEOGRAPH - 0xE49F: 0x8335, //CJK UNIFIED IDEOGRAPH - 0xE4A0: 0x8334, //CJK UNIFIED IDEOGRAPH - 0xE4A1: 0x8316, //CJK UNIFIED IDEOGRAPH - 0xE4A2: 0x8332, //CJK UNIFIED IDEOGRAPH - 0xE4A3: 0x8331, //CJK UNIFIED IDEOGRAPH - 0xE4A4: 0x8340, //CJK UNIFIED IDEOGRAPH - 0xE4A5: 0x8339, //CJK UNIFIED IDEOGRAPH - 0xE4A6: 0x8350, //CJK UNIFIED IDEOGRAPH - 0xE4A7: 0x8345, //CJK UNIFIED IDEOGRAPH - 0xE4A8: 0x832F, //CJK UNIFIED IDEOGRAPH - 0xE4A9: 0x832B, //CJK UNIFIED IDEOGRAPH - 0xE4AA: 0x8317, //CJK UNIFIED IDEOGRAPH - 0xE4AB: 0x8318, //CJK UNIFIED IDEOGRAPH - 0xE4AC: 0x8385, //CJK UNIFIED IDEOGRAPH - 0xE4AD: 0x839A, //CJK UNIFIED IDEOGRAPH - 0xE4AE: 0x83AA, //CJK UNIFIED IDEOGRAPH - 0xE4AF: 0x839F, //CJK UNIFIED IDEOGRAPH - 0xE4B0: 0x83A2, //CJK UNIFIED IDEOGRAPH - 0xE4B1: 0x8396, //CJK UNIFIED IDEOGRAPH - 0xE4B2: 0x8323, //CJK UNIFIED IDEOGRAPH - 0xE4B3: 0x838E, //CJK UNIFIED IDEOGRAPH - 0xE4B4: 0x8387, //CJK UNIFIED IDEOGRAPH - 0xE4B5: 0x838A, //CJK UNIFIED IDEOGRAPH - 0xE4B6: 0x837C, //CJK UNIFIED IDEOGRAPH - 0xE4B7: 0x83B5, //CJK UNIFIED IDEOGRAPH - 0xE4B8: 0x8373, //CJK UNIFIED IDEOGRAPH - 0xE4B9: 0x8375, //CJK UNIFIED IDEOGRAPH - 0xE4BA: 0x83A0, //CJK UNIFIED IDEOGRAPH - 0xE4BB: 0x8389, //CJK UNIFIED IDEOGRAPH - 0xE4BC: 0x83A8, //CJK UNIFIED IDEOGRAPH - 0xE4BD: 0x83F4, //CJK UNIFIED IDEOGRAPH - 0xE4BE: 0x8413, //CJK UNIFIED IDEOGRAPH - 0xE4BF: 0x83EB, //CJK UNIFIED IDEOGRAPH - 0xE4C0: 0x83CE, //CJK UNIFIED IDEOGRAPH - 0xE4C1: 0x83FD, //CJK UNIFIED IDEOGRAPH - 0xE4C2: 0x8403, //CJK UNIFIED IDEOGRAPH - 0xE4C3: 0x83D8, //CJK UNIFIED IDEOGRAPH - 0xE4C4: 0x840B, //CJK UNIFIED IDEOGRAPH - 0xE4C5: 0x83C1, //CJK UNIFIED IDEOGRAPH - 0xE4C6: 0x83F7, //CJK UNIFIED IDEOGRAPH - 0xE4C7: 0x8407, //CJK UNIFIED IDEOGRAPH - 0xE4C8: 0x83E0, //CJK UNIFIED IDEOGRAPH - 0xE4C9: 0x83F2, //CJK UNIFIED IDEOGRAPH - 0xE4CA: 0x840D, //CJK UNIFIED IDEOGRAPH - 0xE4CB: 0x8422, //CJK UNIFIED IDEOGRAPH - 0xE4CC: 0x8420, //CJK UNIFIED IDEOGRAPH - 0xE4CD: 0x83BD, //CJK UNIFIED IDEOGRAPH - 0xE4CE: 0x8438, //CJK UNIFIED IDEOGRAPH - 0xE4CF: 0x8506, //CJK UNIFIED IDEOGRAPH - 0xE4D0: 0x83FB, //CJK UNIFIED IDEOGRAPH - 0xE4D1: 0x846D, //CJK UNIFIED IDEOGRAPH - 0xE4D2: 0x842A, //CJK UNIFIED IDEOGRAPH - 0xE4D3: 0x843C, //CJK UNIFIED IDEOGRAPH - 0xE4D4: 0x855A, //CJK UNIFIED IDEOGRAPH - 0xE4D5: 0x8484, //CJK UNIFIED IDEOGRAPH - 0xE4D6: 0x8477, //CJK UNIFIED IDEOGRAPH - 0xE4D7: 0x846B, //CJK UNIFIED IDEOGRAPH - 0xE4D8: 0x84AD, //CJK UNIFIED IDEOGRAPH - 0xE4D9: 0x846E, //CJK UNIFIED IDEOGRAPH - 0xE4DA: 0x8482, //CJK UNIFIED IDEOGRAPH - 0xE4DB: 0x8469, //CJK UNIFIED IDEOGRAPH - 0xE4DC: 0x8446, //CJK UNIFIED IDEOGRAPH - 0xE4DD: 0x842C, //CJK UNIFIED IDEOGRAPH - 0xE4DE: 0x846F, //CJK UNIFIED IDEOGRAPH - 0xE4DF: 0x8479, //CJK UNIFIED IDEOGRAPH - 0xE4E0: 0x8435, //CJK UNIFIED IDEOGRAPH - 0xE4E1: 0x84CA, //CJK UNIFIED IDEOGRAPH - 0xE4E2: 0x8462, //CJK UNIFIED IDEOGRAPH - 0xE4E3: 0x84B9, //CJK UNIFIED IDEOGRAPH - 0xE4E4: 0x84BF, //CJK UNIFIED IDEOGRAPH - 0xE4E5: 0x849F, //CJK UNIFIED IDEOGRAPH - 0xE4E6: 0x84D9, //CJK UNIFIED IDEOGRAPH - 0xE4E7: 0x84CD, //CJK UNIFIED IDEOGRAPH - 0xE4E8: 0x84BB, //CJK UNIFIED IDEOGRAPH - 0xE4E9: 0x84DA, //CJK UNIFIED IDEOGRAPH - 0xE4EA: 0x84D0, //CJK UNIFIED IDEOGRAPH - 0xE4EB: 0x84C1, //CJK UNIFIED IDEOGRAPH - 0xE4EC: 0x84C6, //CJK UNIFIED IDEOGRAPH - 0xE4ED: 0x84D6, //CJK UNIFIED IDEOGRAPH - 0xE4EE: 0x84A1, //CJK UNIFIED IDEOGRAPH - 0xE4EF: 0x8521, //CJK UNIFIED IDEOGRAPH - 0xE4F0: 0x84FF, //CJK UNIFIED IDEOGRAPH - 0xE4F1: 0x84F4, //CJK UNIFIED IDEOGRAPH - 0xE4F2: 0x8517, //CJK UNIFIED IDEOGRAPH - 0xE4F3: 0x8518, //CJK UNIFIED IDEOGRAPH - 0xE4F4: 0x852C, //CJK UNIFIED IDEOGRAPH - 0xE4F5: 0x851F, //CJK UNIFIED IDEOGRAPH - 0xE4F6: 0x8515, //CJK UNIFIED IDEOGRAPH - 0xE4F7: 0x8514, //CJK UNIFIED IDEOGRAPH - 0xE4F8: 0x84FC, //CJK UNIFIED IDEOGRAPH - 0xE4F9: 0x8540, //CJK UNIFIED IDEOGRAPH - 0xE4FA: 0x8563, //CJK UNIFIED IDEOGRAPH - 0xE4FB: 0x8558, //CJK UNIFIED IDEOGRAPH - 0xE4FC: 0x8548, //CJK UNIFIED IDEOGRAPH - 0xE540: 0x8541, //CJK UNIFIED IDEOGRAPH - 0xE541: 0x8602, //CJK UNIFIED IDEOGRAPH - 0xE542: 0x854B, //CJK UNIFIED IDEOGRAPH - 0xE543: 0x8555, //CJK UNIFIED IDEOGRAPH - 0xE544: 0x8580, //CJK UNIFIED IDEOGRAPH - 0xE545: 0x85A4, //CJK UNIFIED IDEOGRAPH - 0xE546: 0x8588, //CJK UNIFIED IDEOGRAPH - 0xE547: 0x8591, //CJK UNIFIED IDEOGRAPH - 0xE548: 0x858A, //CJK UNIFIED IDEOGRAPH - 0xE549: 0x85A8, //CJK UNIFIED IDEOGRAPH - 0xE54A: 0x856D, //CJK UNIFIED IDEOGRAPH - 0xE54B: 0x8594, //CJK UNIFIED IDEOGRAPH - 0xE54C: 0x859B, //CJK UNIFIED IDEOGRAPH - 0xE54D: 0x85EA, //CJK UNIFIED IDEOGRAPH - 0xE54E: 0x8587, //CJK UNIFIED IDEOGRAPH - 0xE54F: 0x859C, //CJK UNIFIED IDEOGRAPH - 0xE550: 0x8577, //CJK UNIFIED IDEOGRAPH - 0xE551: 0x857E, //CJK UNIFIED IDEOGRAPH - 0xE552: 0x8590, //CJK UNIFIED IDEOGRAPH - 0xE553: 0x85C9, //CJK UNIFIED IDEOGRAPH - 0xE554: 0x85BA, //CJK UNIFIED IDEOGRAPH - 0xE555: 0x85CF, //CJK UNIFIED IDEOGRAPH - 0xE556: 0x85B9, //CJK UNIFIED IDEOGRAPH - 0xE557: 0x85D0, //CJK UNIFIED IDEOGRAPH - 0xE558: 0x85D5, //CJK UNIFIED IDEOGRAPH - 0xE559: 0x85DD, //CJK UNIFIED IDEOGRAPH - 0xE55A: 0x85E5, //CJK UNIFIED IDEOGRAPH - 0xE55B: 0x85DC, //CJK UNIFIED IDEOGRAPH - 0xE55C: 0x85F9, //CJK UNIFIED IDEOGRAPH - 0xE55D: 0x860A, //CJK UNIFIED IDEOGRAPH - 0xE55E: 0x8613, //CJK UNIFIED IDEOGRAPH - 0xE55F: 0x860B, //CJK UNIFIED IDEOGRAPH - 0xE560: 0x85FE, //CJK UNIFIED IDEOGRAPH - 0xE561: 0x85FA, //CJK UNIFIED IDEOGRAPH - 0xE562: 0x8606, //CJK UNIFIED IDEOGRAPH - 0xE563: 0x8622, //CJK UNIFIED IDEOGRAPH - 0xE564: 0x861A, //CJK UNIFIED IDEOGRAPH - 0xE565: 0x8630, //CJK UNIFIED IDEOGRAPH - 0xE566: 0x863F, //CJK UNIFIED IDEOGRAPH - 0xE567: 0x864D, //CJK UNIFIED IDEOGRAPH - 0xE568: 0x4E55, //CJK UNIFIED IDEOGRAPH - 0xE569: 0x8654, //CJK UNIFIED IDEOGRAPH - 0xE56A: 0x865F, //CJK UNIFIED IDEOGRAPH - 0xE56B: 0x8667, //CJK UNIFIED IDEOGRAPH - 0xE56C: 0x8671, //CJK UNIFIED IDEOGRAPH - 0xE56D: 0x8693, //CJK UNIFIED IDEOGRAPH - 0xE56E: 0x86A3, //CJK UNIFIED IDEOGRAPH - 0xE56F: 0x86A9, //CJK UNIFIED IDEOGRAPH - 0xE570: 0x86AA, //CJK UNIFIED IDEOGRAPH - 0xE571: 0x868B, //CJK UNIFIED IDEOGRAPH - 0xE572: 0x868C, //CJK UNIFIED IDEOGRAPH - 0xE573: 0x86B6, //CJK UNIFIED IDEOGRAPH - 0xE574: 0x86AF, //CJK UNIFIED IDEOGRAPH - 0xE575: 0x86C4, //CJK UNIFIED IDEOGRAPH - 0xE576: 0x86C6, //CJK UNIFIED IDEOGRAPH - 0xE577: 0x86B0, //CJK UNIFIED IDEOGRAPH - 0xE578: 0x86C9, //CJK UNIFIED IDEOGRAPH - 0xE579: 0x8823, //CJK UNIFIED IDEOGRAPH - 0xE57A: 0x86AB, //CJK UNIFIED IDEOGRAPH - 0xE57B: 0x86D4, //CJK UNIFIED IDEOGRAPH - 0xE57C: 0x86DE, //CJK UNIFIED IDEOGRAPH - 0xE57D: 0x86E9, //CJK UNIFIED IDEOGRAPH - 0xE57E: 0x86EC, //CJK UNIFIED IDEOGRAPH - 0xE580: 0x86DF, //CJK UNIFIED IDEOGRAPH - 0xE581: 0x86DB, //CJK UNIFIED IDEOGRAPH - 0xE582: 0x86EF, //CJK UNIFIED IDEOGRAPH - 0xE583: 0x8712, //CJK UNIFIED IDEOGRAPH - 0xE584: 0x8706, //CJK UNIFIED IDEOGRAPH - 0xE585: 0x8708, //CJK UNIFIED IDEOGRAPH - 0xE586: 0x8700, //CJK UNIFIED IDEOGRAPH - 0xE587: 0x8703, //CJK UNIFIED IDEOGRAPH - 0xE588: 0x86FB, //CJK UNIFIED IDEOGRAPH - 0xE589: 0x8711, //CJK UNIFIED IDEOGRAPH - 0xE58A: 0x8709, //CJK UNIFIED IDEOGRAPH - 0xE58B: 0x870D, //CJK UNIFIED IDEOGRAPH - 0xE58C: 0x86F9, //CJK UNIFIED IDEOGRAPH - 0xE58D: 0x870A, //CJK UNIFIED IDEOGRAPH - 0xE58E: 0x8734, //CJK UNIFIED IDEOGRAPH - 0xE58F: 0x873F, //CJK UNIFIED IDEOGRAPH - 0xE590: 0x8737, //CJK UNIFIED IDEOGRAPH - 0xE591: 0x873B, //CJK UNIFIED IDEOGRAPH - 0xE592: 0x8725, //CJK UNIFIED IDEOGRAPH - 0xE593: 0x8729, //CJK UNIFIED IDEOGRAPH - 0xE594: 0x871A, //CJK UNIFIED IDEOGRAPH - 0xE595: 0x8760, //CJK UNIFIED IDEOGRAPH - 0xE596: 0x875F, //CJK UNIFIED IDEOGRAPH - 0xE597: 0x8778, //CJK UNIFIED IDEOGRAPH - 0xE598: 0x874C, //CJK UNIFIED IDEOGRAPH - 0xE599: 0x874E, //CJK UNIFIED IDEOGRAPH - 0xE59A: 0x8774, //CJK UNIFIED IDEOGRAPH - 0xE59B: 0x8757, //CJK UNIFIED IDEOGRAPH - 0xE59C: 0x8768, //CJK UNIFIED IDEOGRAPH - 0xE59D: 0x876E, //CJK UNIFIED IDEOGRAPH - 0xE59E: 0x8759, //CJK UNIFIED IDEOGRAPH - 0xE59F: 0x8753, //CJK UNIFIED IDEOGRAPH - 0xE5A0: 0x8763, //CJK UNIFIED IDEOGRAPH - 0xE5A1: 0x876A, //CJK UNIFIED IDEOGRAPH - 0xE5A2: 0x8805, //CJK UNIFIED IDEOGRAPH - 0xE5A3: 0x87A2, //CJK UNIFIED IDEOGRAPH - 0xE5A4: 0x879F, //CJK UNIFIED IDEOGRAPH - 0xE5A5: 0x8782, //CJK UNIFIED IDEOGRAPH - 0xE5A6: 0x87AF, //CJK UNIFIED IDEOGRAPH - 0xE5A7: 0x87CB, //CJK UNIFIED IDEOGRAPH - 0xE5A8: 0x87BD, //CJK UNIFIED IDEOGRAPH - 0xE5A9: 0x87C0, //CJK UNIFIED IDEOGRAPH - 0xE5AA: 0x87D0, //CJK UNIFIED IDEOGRAPH - 0xE5AB: 0x96D6, //CJK UNIFIED IDEOGRAPH - 0xE5AC: 0x87AB, //CJK UNIFIED IDEOGRAPH - 0xE5AD: 0x87C4, //CJK UNIFIED IDEOGRAPH - 0xE5AE: 0x87B3, //CJK UNIFIED IDEOGRAPH - 0xE5AF: 0x87C7, //CJK UNIFIED IDEOGRAPH - 0xE5B0: 0x87C6, //CJK UNIFIED IDEOGRAPH - 0xE5B1: 0x87BB, //CJK UNIFIED IDEOGRAPH - 0xE5B2: 0x87EF, //CJK UNIFIED IDEOGRAPH - 0xE5B3: 0x87F2, //CJK UNIFIED IDEOGRAPH - 0xE5B4: 0x87E0, //CJK UNIFIED IDEOGRAPH - 0xE5B5: 0x880F, //CJK UNIFIED IDEOGRAPH - 0xE5B6: 0x880D, //CJK UNIFIED IDEOGRAPH - 0xE5B7: 0x87FE, //CJK UNIFIED IDEOGRAPH - 0xE5B8: 0x87F6, //CJK UNIFIED IDEOGRAPH - 0xE5B9: 0x87F7, //CJK UNIFIED IDEOGRAPH - 0xE5BA: 0x880E, //CJK UNIFIED IDEOGRAPH - 0xE5BB: 0x87D2, //CJK UNIFIED IDEOGRAPH - 0xE5BC: 0x8811, //CJK UNIFIED IDEOGRAPH - 0xE5BD: 0x8816, //CJK UNIFIED IDEOGRAPH - 0xE5BE: 0x8815, //CJK UNIFIED IDEOGRAPH - 0xE5BF: 0x8822, //CJK UNIFIED IDEOGRAPH - 0xE5C0: 0x8821, //CJK UNIFIED IDEOGRAPH - 0xE5C1: 0x8831, //CJK UNIFIED IDEOGRAPH - 0xE5C2: 0x8836, //CJK UNIFIED IDEOGRAPH - 0xE5C3: 0x8839, //CJK UNIFIED IDEOGRAPH - 0xE5C4: 0x8827, //CJK UNIFIED IDEOGRAPH - 0xE5C5: 0x883B, //CJK UNIFIED IDEOGRAPH - 0xE5C6: 0x8844, //CJK UNIFIED IDEOGRAPH - 0xE5C7: 0x8842, //CJK UNIFIED IDEOGRAPH - 0xE5C8: 0x8852, //CJK UNIFIED IDEOGRAPH - 0xE5C9: 0x8859, //CJK UNIFIED IDEOGRAPH - 0xE5CA: 0x885E, //CJK UNIFIED IDEOGRAPH - 0xE5CB: 0x8862, //CJK UNIFIED IDEOGRAPH - 0xE5CC: 0x886B, //CJK UNIFIED IDEOGRAPH - 0xE5CD: 0x8881, //CJK UNIFIED IDEOGRAPH - 0xE5CE: 0x887E, //CJK UNIFIED IDEOGRAPH - 0xE5CF: 0x889E, //CJK UNIFIED IDEOGRAPH - 0xE5D0: 0x8875, //CJK UNIFIED IDEOGRAPH - 0xE5D1: 0x887D, //CJK UNIFIED IDEOGRAPH - 0xE5D2: 0x88B5, //CJK UNIFIED IDEOGRAPH - 0xE5D3: 0x8872, //CJK UNIFIED IDEOGRAPH - 0xE5D4: 0x8882, //CJK UNIFIED IDEOGRAPH - 0xE5D5: 0x8897, //CJK UNIFIED IDEOGRAPH - 0xE5D6: 0x8892, //CJK UNIFIED IDEOGRAPH - 0xE5D7: 0x88AE, //CJK UNIFIED IDEOGRAPH - 0xE5D8: 0x8899, //CJK UNIFIED IDEOGRAPH - 0xE5D9: 0x88A2, //CJK UNIFIED IDEOGRAPH - 0xE5DA: 0x888D, //CJK UNIFIED IDEOGRAPH - 0xE5DB: 0x88A4, //CJK UNIFIED IDEOGRAPH - 0xE5DC: 0x88B0, //CJK UNIFIED IDEOGRAPH - 0xE5DD: 0x88BF, //CJK UNIFIED IDEOGRAPH - 0xE5DE: 0x88B1, //CJK UNIFIED IDEOGRAPH - 0xE5DF: 0x88C3, //CJK UNIFIED IDEOGRAPH - 0xE5E0: 0x88C4, //CJK UNIFIED IDEOGRAPH - 0xE5E1: 0x88D4, //CJK UNIFIED IDEOGRAPH - 0xE5E2: 0x88D8, //CJK UNIFIED IDEOGRAPH - 0xE5E3: 0x88D9, //CJK UNIFIED IDEOGRAPH - 0xE5E4: 0x88DD, //CJK UNIFIED IDEOGRAPH - 0xE5E5: 0x88F9, //CJK UNIFIED IDEOGRAPH - 0xE5E6: 0x8902, //CJK UNIFIED IDEOGRAPH - 0xE5E7: 0x88FC, //CJK UNIFIED IDEOGRAPH - 0xE5E8: 0x88F4, //CJK UNIFIED IDEOGRAPH - 0xE5E9: 0x88E8, //CJK UNIFIED IDEOGRAPH - 0xE5EA: 0x88F2, //CJK UNIFIED IDEOGRAPH - 0xE5EB: 0x8904, //CJK UNIFIED IDEOGRAPH - 0xE5EC: 0x890C, //CJK UNIFIED IDEOGRAPH - 0xE5ED: 0x890A, //CJK UNIFIED IDEOGRAPH - 0xE5EE: 0x8913, //CJK UNIFIED IDEOGRAPH - 0xE5EF: 0x8943, //CJK UNIFIED IDEOGRAPH - 0xE5F0: 0x891E, //CJK UNIFIED IDEOGRAPH - 0xE5F1: 0x8925, //CJK UNIFIED IDEOGRAPH - 0xE5F2: 0x892A, //CJK UNIFIED IDEOGRAPH - 0xE5F3: 0x892B, //CJK UNIFIED IDEOGRAPH - 0xE5F4: 0x8941, //CJK UNIFIED IDEOGRAPH - 0xE5F5: 0x8944, //CJK UNIFIED IDEOGRAPH - 0xE5F6: 0x893B, //CJK UNIFIED IDEOGRAPH - 0xE5F7: 0x8936, //CJK UNIFIED IDEOGRAPH - 0xE5F8: 0x8938, //CJK UNIFIED IDEOGRAPH - 0xE5F9: 0x894C, //CJK UNIFIED IDEOGRAPH - 0xE5FA: 0x891D, //CJK UNIFIED IDEOGRAPH - 0xE5FB: 0x8960, //CJK UNIFIED IDEOGRAPH - 0xE5FC: 0x895E, //CJK UNIFIED IDEOGRAPH - 0xE640: 0x8966, //CJK UNIFIED IDEOGRAPH - 0xE641: 0x8964, //CJK UNIFIED IDEOGRAPH - 0xE642: 0x896D, //CJK UNIFIED IDEOGRAPH - 0xE643: 0x896A, //CJK UNIFIED IDEOGRAPH - 0xE644: 0x896F, //CJK UNIFIED IDEOGRAPH - 0xE645: 0x8974, //CJK UNIFIED IDEOGRAPH - 0xE646: 0x8977, //CJK UNIFIED IDEOGRAPH - 0xE647: 0x897E, //CJK UNIFIED IDEOGRAPH - 0xE648: 0x8983, //CJK UNIFIED IDEOGRAPH - 0xE649: 0x8988, //CJK UNIFIED IDEOGRAPH - 0xE64A: 0x898A, //CJK UNIFIED IDEOGRAPH - 0xE64B: 0x8993, //CJK UNIFIED IDEOGRAPH - 0xE64C: 0x8998, //CJK UNIFIED IDEOGRAPH - 0xE64D: 0x89A1, //CJK UNIFIED IDEOGRAPH - 0xE64E: 0x89A9, //CJK UNIFIED IDEOGRAPH - 0xE64F: 0x89A6, //CJK UNIFIED IDEOGRAPH - 0xE650: 0x89AC, //CJK UNIFIED IDEOGRAPH - 0xE651: 0x89AF, //CJK UNIFIED IDEOGRAPH - 0xE652: 0x89B2, //CJK UNIFIED IDEOGRAPH - 0xE653: 0x89BA, //CJK UNIFIED IDEOGRAPH - 0xE654: 0x89BD, //CJK UNIFIED IDEOGRAPH - 0xE655: 0x89BF, //CJK UNIFIED IDEOGRAPH - 0xE656: 0x89C0, //CJK UNIFIED IDEOGRAPH - 0xE657: 0x89DA, //CJK UNIFIED IDEOGRAPH - 0xE658: 0x89DC, //CJK UNIFIED IDEOGRAPH - 0xE659: 0x89DD, //CJK UNIFIED IDEOGRAPH - 0xE65A: 0x89E7, //CJK UNIFIED IDEOGRAPH - 0xE65B: 0x89F4, //CJK UNIFIED IDEOGRAPH - 0xE65C: 0x89F8, //CJK UNIFIED IDEOGRAPH - 0xE65D: 0x8A03, //CJK UNIFIED IDEOGRAPH - 0xE65E: 0x8A16, //CJK UNIFIED IDEOGRAPH - 0xE65F: 0x8A10, //CJK UNIFIED IDEOGRAPH - 0xE660: 0x8A0C, //CJK UNIFIED IDEOGRAPH - 0xE661: 0x8A1B, //CJK UNIFIED IDEOGRAPH - 0xE662: 0x8A1D, //CJK UNIFIED IDEOGRAPH - 0xE663: 0x8A25, //CJK UNIFIED IDEOGRAPH - 0xE664: 0x8A36, //CJK UNIFIED IDEOGRAPH - 0xE665: 0x8A41, //CJK UNIFIED IDEOGRAPH - 0xE666: 0x8A5B, //CJK UNIFIED IDEOGRAPH - 0xE667: 0x8A52, //CJK UNIFIED IDEOGRAPH - 0xE668: 0x8A46, //CJK UNIFIED IDEOGRAPH - 0xE669: 0x8A48, //CJK UNIFIED IDEOGRAPH - 0xE66A: 0x8A7C, //CJK UNIFIED IDEOGRAPH - 0xE66B: 0x8A6D, //CJK UNIFIED IDEOGRAPH - 0xE66C: 0x8A6C, //CJK UNIFIED IDEOGRAPH - 0xE66D: 0x8A62, //CJK UNIFIED IDEOGRAPH - 0xE66E: 0x8A85, //CJK UNIFIED IDEOGRAPH - 0xE66F: 0x8A82, //CJK UNIFIED IDEOGRAPH - 0xE670: 0x8A84, //CJK UNIFIED IDEOGRAPH - 0xE671: 0x8AA8, //CJK UNIFIED IDEOGRAPH - 0xE672: 0x8AA1, //CJK UNIFIED IDEOGRAPH - 0xE673: 0x8A91, //CJK UNIFIED IDEOGRAPH - 0xE674: 0x8AA5, //CJK UNIFIED IDEOGRAPH - 0xE675: 0x8AA6, //CJK UNIFIED IDEOGRAPH - 0xE676: 0x8A9A, //CJK UNIFIED IDEOGRAPH - 0xE677: 0x8AA3, //CJK UNIFIED IDEOGRAPH - 0xE678: 0x8AC4, //CJK UNIFIED IDEOGRAPH - 0xE679: 0x8ACD, //CJK UNIFIED IDEOGRAPH - 0xE67A: 0x8AC2, //CJK UNIFIED IDEOGRAPH - 0xE67B: 0x8ADA, //CJK UNIFIED IDEOGRAPH - 0xE67C: 0x8AEB, //CJK UNIFIED IDEOGRAPH - 0xE67D: 0x8AF3, //CJK UNIFIED IDEOGRAPH - 0xE67E: 0x8AE7, //CJK UNIFIED IDEOGRAPH - 0xE680: 0x8AE4, //CJK UNIFIED IDEOGRAPH - 0xE681: 0x8AF1, //CJK UNIFIED IDEOGRAPH - 0xE682: 0x8B14, //CJK UNIFIED IDEOGRAPH - 0xE683: 0x8AE0, //CJK UNIFIED IDEOGRAPH - 0xE684: 0x8AE2, //CJK UNIFIED IDEOGRAPH - 0xE685: 0x8AF7, //CJK UNIFIED IDEOGRAPH - 0xE686: 0x8ADE, //CJK UNIFIED IDEOGRAPH - 0xE687: 0x8ADB, //CJK UNIFIED IDEOGRAPH - 0xE688: 0x8B0C, //CJK UNIFIED IDEOGRAPH - 0xE689: 0x8B07, //CJK UNIFIED IDEOGRAPH - 0xE68A: 0x8B1A, //CJK UNIFIED IDEOGRAPH - 0xE68B: 0x8AE1, //CJK UNIFIED IDEOGRAPH - 0xE68C: 0x8B16, //CJK UNIFIED IDEOGRAPH - 0xE68D: 0x8B10, //CJK UNIFIED IDEOGRAPH - 0xE68E: 0x8B17, //CJK UNIFIED IDEOGRAPH - 0xE68F: 0x8B20, //CJK UNIFIED IDEOGRAPH - 0xE690: 0x8B33, //CJK UNIFIED IDEOGRAPH - 0xE691: 0x97AB, //CJK UNIFIED IDEOGRAPH - 0xE692: 0x8B26, //CJK UNIFIED IDEOGRAPH - 0xE693: 0x8B2B, //CJK UNIFIED IDEOGRAPH - 0xE694: 0x8B3E, //CJK UNIFIED IDEOGRAPH - 0xE695: 0x8B28, //CJK UNIFIED IDEOGRAPH - 0xE696: 0x8B41, //CJK UNIFIED IDEOGRAPH - 0xE697: 0x8B4C, //CJK UNIFIED IDEOGRAPH - 0xE698: 0x8B4F, //CJK UNIFIED IDEOGRAPH - 0xE699: 0x8B4E, //CJK UNIFIED IDEOGRAPH - 0xE69A: 0x8B49, //CJK UNIFIED IDEOGRAPH - 0xE69B: 0x8B56, //CJK UNIFIED IDEOGRAPH - 0xE69C: 0x8B5B, //CJK UNIFIED IDEOGRAPH - 0xE69D: 0x8B5A, //CJK UNIFIED IDEOGRAPH - 0xE69E: 0x8B6B, //CJK UNIFIED IDEOGRAPH - 0xE69F: 0x8B5F, //CJK UNIFIED IDEOGRAPH - 0xE6A0: 0x8B6C, //CJK UNIFIED IDEOGRAPH - 0xE6A1: 0x8B6F, //CJK UNIFIED IDEOGRAPH - 0xE6A2: 0x8B74, //CJK UNIFIED IDEOGRAPH - 0xE6A3: 0x8B7D, //CJK UNIFIED IDEOGRAPH - 0xE6A4: 0x8B80, //CJK UNIFIED IDEOGRAPH - 0xE6A5: 0x8B8C, //CJK UNIFIED IDEOGRAPH - 0xE6A6: 0x8B8E, //CJK UNIFIED IDEOGRAPH - 0xE6A7: 0x8B92, //CJK UNIFIED IDEOGRAPH - 0xE6A8: 0x8B93, //CJK UNIFIED IDEOGRAPH - 0xE6A9: 0x8B96, //CJK UNIFIED IDEOGRAPH - 0xE6AA: 0x8B99, //CJK UNIFIED IDEOGRAPH - 0xE6AB: 0x8B9A, //CJK UNIFIED IDEOGRAPH - 0xE6AC: 0x8C3A, //CJK UNIFIED IDEOGRAPH - 0xE6AD: 0x8C41, //CJK UNIFIED IDEOGRAPH - 0xE6AE: 0x8C3F, //CJK UNIFIED IDEOGRAPH - 0xE6AF: 0x8C48, //CJK UNIFIED IDEOGRAPH - 0xE6B0: 0x8C4C, //CJK UNIFIED IDEOGRAPH - 0xE6B1: 0x8C4E, //CJK UNIFIED IDEOGRAPH - 0xE6B2: 0x8C50, //CJK UNIFIED IDEOGRAPH - 0xE6B3: 0x8C55, //CJK UNIFIED IDEOGRAPH - 0xE6B4: 0x8C62, //CJK UNIFIED IDEOGRAPH - 0xE6B5: 0x8C6C, //CJK UNIFIED IDEOGRAPH - 0xE6B6: 0x8C78, //CJK UNIFIED IDEOGRAPH - 0xE6B7: 0x8C7A, //CJK UNIFIED IDEOGRAPH - 0xE6B8: 0x8C82, //CJK UNIFIED IDEOGRAPH - 0xE6B9: 0x8C89, //CJK UNIFIED IDEOGRAPH - 0xE6BA: 0x8C85, //CJK UNIFIED IDEOGRAPH - 0xE6BB: 0x8C8A, //CJK UNIFIED IDEOGRAPH - 0xE6BC: 0x8C8D, //CJK UNIFIED IDEOGRAPH - 0xE6BD: 0x8C8E, //CJK UNIFIED IDEOGRAPH - 0xE6BE: 0x8C94, //CJK UNIFIED IDEOGRAPH - 0xE6BF: 0x8C7C, //CJK UNIFIED IDEOGRAPH - 0xE6C0: 0x8C98, //CJK UNIFIED IDEOGRAPH - 0xE6C1: 0x621D, //CJK UNIFIED IDEOGRAPH - 0xE6C2: 0x8CAD, //CJK UNIFIED IDEOGRAPH - 0xE6C3: 0x8CAA, //CJK UNIFIED IDEOGRAPH - 0xE6C4: 0x8CBD, //CJK UNIFIED IDEOGRAPH - 0xE6C5: 0x8CB2, //CJK UNIFIED IDEOGRAPH - 0xE6C6: 0x8CB3, //CJK UNIFIED IDEOGRAPH - 0xE6C7: 0x8CAE, //CJK UNIFIED IDEOGRAPH - 0xE6C8: 0x8CB6, //CJK UNIFIED IDEOGRAPH - 0xE6C9: 0x8CC8, //CJK UNIFIED IDEOGRAPH - 0xE6CA: 0x8CC1, //CJK UNIFIED IDEOGRAPH - 0xE6CB: 0x8CE4, //CJK UNIFIED IDEOGRAPH - 0xE6CC: 0x8CE3, //CJK UNIFIED IDEOGRAPH - 0xE6CD: 0x8CDA, //CJK UNIFIED IDEOGRAPH - 0xE6CE: 0x8CFD, //CJK UNIFIED IDEOGRAPH - 0xE6CF: 0x8CFA, //CJK UNIFIED IDEOGRAPH - 0xE6D0: 0x8CFB, //CJK UNIFIED IDEOGRAPH - 0xE6D1: 0x8D04, //CJK UNIFIED IDEOGRAPH - 0xE6D2: 0x8D05, //CJK UNIFIED IDEOGRAPH - 0xE6D3: 0x8D0A, //CJK UNIFIED IDEOGRAPH - 0xE6D4: 0x8D07, //CJK UNIFIED IDEOGRAPH - 0xE6D5: 0x8D0F, //CJK UNIFIED IDEOGRAPH - 0xE6D6: 0x8D0D, //CJK UNIFIED IDEOGRAPH - 0xE6D7: 0x8D10, //CJK UNIFIED IDEOGRAPH - 0xE6D8: 0x9F4E, //CJK UNIFIED IDEOGRAPH - 0xE6D9: 0x8D13, //CJK UNIFIED IDEOGRAPH - 0xE6DA: 0x8CCD, //CJK UNIFIED IDEOGRAPH - 0xE6DB: 0x8D14, //CJK UNIFIED IDEOGRAPH - 0xE6DC: 0x8D16, //CJK UNIFIED IDEOGRAPH - 0xE6DD: 0x8D67, //CJK UNIFIED IDEOGRAPH - 0xE6DE: 0x8D6D, //CJK UNIFIED IDEOGRAPH - 0xE6DF: 0x8D71, //CJK UNIFIED IDEOGRAPH - 0xE6E0: 0x8D73, //CJK UNIFIED IDEOGRAPH - 0xE6E1: 0x8D81, //CJK UNIFIED IDEOGRAPH - 0xE6E2: 0x8D99, //CJK UNIFIED IDEOGRAPH - 0xE6E3: 0x8DC2, //CJK UNIFIED IDEOGRAPH - 0xE6E4: 0x8DBE, //CJK UNIFIED IDEOGRAPH - 0xE6E5: 0x8DBA, //CJK UNIFIED IDEOGRAPH - 0xE6E6: 0x8DCF, //CJK UNIFIED IDEOGRAPH - 0xE6E7: 0x8DDA, //CJK UNIFIED IDEOGRAPH - 0xE6E8: 0x8DD6, //CJK UNIFIED IDEOGRAPH - 0xE6E9: 0x8DCC, //CJK UNIFIED IDEOGRAPH - 0xE6EA: 0x8DDB, //CJK UNIFIED IDEOGRAPH - 0xE6EB: 0x8DCB, //CJK UNIFIED IDEOGRAPH - 0xE6EC: 0x8DEA, //CJK UNIFIED IDEOGRAPH - 0xE6ED: 0x8DEB, //CJK UNIFIED IDEOGRAPH - 0xE6EE: 0x8DDF, //CJK UNIFIED IDEOGRAPH - 0xE6EF: 0x8DE3, //CJK UNIFIED IDEOGRAPH - 0xE6F0: 0x8DFC, //CJK UNIFIED IDEOGRAPH - 0xE6F1: 0x8E08, //CJK UNIFIED IDEOGRAPH - 0xE6F2: 0x8E09, //CJK UNIFIED IDEOGRAPH - 0xE6F3: 0x8DFF, //CJK UNIFIED IDEOGRAPH - 0xE6F4: 0x8E1D, //CJK UNIFIED IDEOGRAPH - 0xE6F5: 0x8E1E, //CJK UNIFIED IDEOGRAPH - 0xE6F6: 0x8E10, //CJK UNIFIED IDEOGRAPH - 0xE6F7: 0x8E1F, //CJK UNIFIED IDEOGRAPH - 0xE6F8: 0x8E42, //CJK UNIFIED IDEOGRAPH - 0xE6F9: 0x8E35, //CJK UNIFIED IDEOGRAPH - 0xE6FA: 0x8E30, //CJK UNIFIED IDEOGRAPH - 0xE6FB: 0x8E34, //CJK UNIFIED IDEOGRAPH - 0xE6FC: 0x8E4A, //CJK UNIFIED IDEOGRAPH - 0xE740: 0x8E47, //CJK UNIFIED IDEOGRAPH - 0xE741: 0x8E49, //CJK UNIFIED IDEOGRAPH - 0xE742: 0x8E4C, //CJK UNIFIED IDEOGRAPH - 0xE743: 0x8E50, //CJK UNIFIED IDEOGRAPH - 0xE744: 0x8E48, //CJK UNIFIED IDEOGRAPH - 0xE745: 0x8E59, //CJK UNIFIED IDEOGRAPH - 0xE746: 0x8E64, //CJK UNIFIED IDEOGRAPH - 0xE747: 0x8E60, //CJK UNIFIED IDEOGRAPH - 0xE748: 0x8E2A, //CJK UNIFIED IDEOGRAPH - 0xE749: 0x8E63, //CJK UNIFIED IDEOGRAPH - 0xE74A: 0x8E55, //CJK UNIFIED IDEOGRAPH - 0xE74B: 0x8E76, //CJK UNIFIED IDEOGRAPH - 0xE74C: 0x8E72, //CJK UNIFIED IDEOGRAPH - 0xE74D: 0x8E7C, //CJK UNIFIED IDEOGRAPH - 0xE74E: 0x8E81, //CJK UNIFIED IDEOGRAPH - 0xE74F: 0x8E87, //CJK UNIFIED IDEOGRAPH - 0xE750: 0x8E85, //CJK UNIFIED IDEOGRAPH - 0xE751: 0x8E84, //CJK UNIFIED IDEOGRAPH - 0xE752: 0x8E8B, //CJK UNIFIED IDEOGRAPH - 0xE753: 0x8E8A, //CJK UNIFIED IDEOGRAPH - 0xE754: 0x8E93, //CJK UNIFIED IDEOGRAPH - 0xE755: 0x8E91, //CJK UNIFIED IDEOGRAPH - 0xE756: 0x8E94, //CJK UNIFIED IDEOGRAPH - 0xE757: 0x8E99, //CJK UNIFIED IDEOGRAPH - 0xE758: 0x8EAA, //CJK UNIFIED IDEOGRAPH - 0xE759: 0x8EA1, //CJK UNIFIED IDEOGRAPH - 0xE75A: 0x8EAC, //CJK UNIFIED IDEOGRAPH - 0xE75B: 0x8EB0, //CJK UNIFIED IDEOGRAPH - 0xE75C: 0x8EC6, //CJK UNIFIED IDEOGRAPH - 0xE75D: 0x8EB1, //CJK UNIFIED IDEOGRAPH - 0xE75E: 0x8EBE, //CJK UNIFIED IDEOGRAPH - 0xE75F: 0x8EC5, //CJK UNIFIED IDEOGRAPH - 0xE760: 0x8EC8, //CJK UNIFIED IDEOGRAPH - 0xE761: 0x8ECB, //CJK UNIFIED IDEOGRAPH - 0xE762: 0x8EDB, //CJK UNIFIED IDEOGRAPH - 0xE763: 0x8EE3, //CJK UNIFIED IDEOGRAPH - 0xE764: 0x8EFC, //CJK UNIFIED IDEOGRAPH - 0xE765: 0x8EFB, //CJK UNIFIED IDEOGRAPH - 0xE766: 0x8EEB, //CJK UNIFIED IDEOGRAPH - 0xE767: 0x8EFE, //CJK UNIFIED IDEOGRAPH - 0xE768: 0x8F0A, //CJK UNIFIED IDEOGRAPH - 0xE769: 0x8F05, //CJK UNIFIED IDEOGRAPH - 0xE76A: 0x8F15, //CJK UNIFIED IDEOGRAPH - 0xE76B: 0x8F12, //CJK UNIFIED IDEOGRAPH - 0xE76C: 0x8F19, //CJK UNIFIED IDEOGRAPH - 0xE76D: 0x8F13, //CJK UNIFIED IDEOGRAPH - 0xE76E: 0x8F1C, //CJK UNIFIED IDEOGRAPH - 0xE76F: 0x8F1F, //CJK UNIFIED IDEOGRAPH - 0xE770: 0x8F1B, //CJK UNIFIED IDEOGRAPH - 0xE771: 0x8F0C, //CJK UNIFIED IDEOGRAPH - 0xE772: 0x8F26, //CJK UNIFIED IDEOGRAPH - 0xE773: 0x8F33, //CJK UNIFIED IDEOGRAPH - 0xE774: 0x8F3B, //CJK UNIFIED IDEOGRAPH - 0xE775: 0x8F39, //CJK UNIFIED IDEOGRAPH - 0xE776: 0x8F45, //CJK UNIFIED IDEOGRAPH - 0xE777: 0x8F42, //CJK UNIFIED IDEOGRAPH - 0xE778: 0x8F3E, //CJK UNIFIED IDEOGRAPH - 0xE779: 0x8F4C, //CJK UNIFIED IDEOGRAPH - 0xE77A: 0x8F49, //CJK UNIFIED IDEOGRAPH - 0xE77B: 0x8F46, //CJK UNIFIED IDEOGRAPH - 0xE77C: 0x8F4E, //CJK UNIFIED IDEOGRAPH - 0xE77D: 0x8F57, //CJK UNIFIED IDEOGRAPH - 0xE77E: 0x8F5C, //CJK UNIFIED IDEOGRAPH - 0xE780: 0x8F62, //CJK UNIFIED IDEOGRAPH - 0xE781: 0x8F63, //CJK UNIFIED IDEOGRAPH - 0xE782: 0x8F64, //CJK UNIFIED IDEOGRAPH - 0xE783: 0x8F9C, //CJK UNIFIED IDEOGRAPH - 0xE784: 0x8F9F, //CJK UNIFIED IDEOGRAPH - 0xE785: 0x8FA3, //CJK UNIFIED IDEOGRAPH - 0xE786: 0x8FAD, //CJK UNIFIED IDEOGRAPH - 0xE787: 0x8FAF, //CJK UNIFIED IDEOGRAPH - 0xE788: 0x8FB7, //CJK UNIFIED IDEOGRAPH - 0xE789: 0x8FDA, //CJK UNIFIED IDEOGRAPH - 0xE78A: 0x8FE5, //CJK UNIFIED IDEOGRAPH - 0xE78B: 0x8FE2, //CJK UNIFIED IDEOGRAPH - 0xE78C: 0x8FEA, //CJK UNIFIED IDEOGRAPH - 0xE78D: 0x8FEF, //CJK UNIFIED IDEOGRAPH - 0xE78E: 0x9087, //CJK UNIFIED IDEOGRAPH - 0xE78F: 0x8FF4, //CJK UNIFIED IDEOGRAPH - 0xE790: 0x9005, //CJK UNIFIED IDEOGRAPH - 0xE791: 0x8FF9, //CJK UNIFIED IDEOGRAPH - 0xE792: 0x8FFA, //CJK UNIFIED IDEOGRAPH - 0xE793: 0x9011, //CJK UNIFIED IDEOGRAPH - 0xE794: 0x9015, //CJK UNIFIED IDEOGRAPH - 0xE795: 0x9021, //CJK UNIFIED IDEOGRAPH - 0xE796: 0x900D, //CJK UNIFIED IDEOGRAPH - 0xE797: 0x901E, //CJK UNIFIED IDEOGRAPH - 0xE798: 0x9016, //CJK UNIFIED IDEOGRAPH - 0xE799: 0x900B, //CJK UNIFIED IDEOGRAPH - 0xE79A: 0x9027, //CJK UNIFIED IDEOGRAPH - 0xE79B: 0x9036, //CJK UNIFIED IDEOGRAPH - 0xE79C: 0x9035, //CJK UNIFIED IDEOGRAPH - 0xE79D: 0x9039, //CJK UNIFIED IDEOGRAPH - 0xE79E: 0x8FF8, //CJK UNIFIED IDEOGRAPH - 0xE79F: 0x904F, //CJK UNIFIED IDEOGRAPH - 0xE7A0: 0x9050, //CJK UNIFIED IDEOGRAPH - 0xE7A1: 0x9051, //CJK UNIFIED IDEOGRAPH - 0xE7A2: 0x9052, //CJK UNIFIED IDEOGRAPH - 0xE7A3: 0x900E, //CJK UNIFIED IDEOGRAPH - 0xE7A4: 0x9049, //CJK UNIFIED IDEOGRAPH - 0xE7A5: 0x903E, //CJK UNIFIED IDEOGRAPH - 0xE7A6: 0x9056, //CJK UNIFIED IDEOGRAPH - 0xE7A7: 0x9058, //CJK UNIFIED IDEOGRAPH - 0xE7A8: 0x905E, //CJK UNIFIED IDEOGRAPH - 0xE7A9: 0x9068, //CJK UNIFIED IDEOGRAPH - 0xE7AA: 0x906F, //CJK UNIFIED IDEOGRAPH - 0xE7AB: 0x9076, //CJK UNIFIED IDEOGRAPH - 0xE7AC: 0x96A8, //CJK UNIFIED IDEOGRAPH - 0xE7AD: 0x9072, //CJK UNIFIED IDEOGRAPH - 0xE7AE: 0x9082, //CJK UNIFIED IDEOGRAPH - 0xE7AF: 0x907D, //CJK UNIFIED IDEOGRAPH - 0xE7B0: 0x9081, //CJK UNIFIED IDEOGRAPH - 0xE7B1: 0x9080, //CJK UNIFIED IDEOGRAPH - 0xE7B2: 0x908A, //CJK UNIFIED IDEOGRAPH - 0xE7B3: 0x9089, //CJK UNIFIED IDEOGRAPH - 0xE7B4: 0x908F, //CJK UNIFIED IDEOGRAPH - 0xE7B5: 0x90A8, //CJK UNIFIED IDEOGRAPH - 0xE7B6: 0x90AF, //CJK UNIFIED IDEOGRAPH - 0xE7B7: 0x90B1, //CJK UNIFIED IDEOGRAPH - 0xE7B8: 0x90B5, //CJK UNIFIED IDEOGRAPH - 0xE7B9: 0x90E2, //CJK UNIFIED IDEOGRAPH - 0xE7BA: 0x90E4, //CJK UNIFIED IDEOGRAPH - 0xE7BB: 0x6248, //CJK UNIFIED IDEOGRAPH - 0xE7BC: 0x90DB, //CJK UNIFIED IDEOGRAPH - 0xE7BD: 0x9102, //CJK UNIFIED IDEOGRAPH - 0xE7BE: 0x9112, //CJK UNIFIED IDEOGRAPH - 0xE7BF: 0x9119, //CJK UNIFIED IDEOGRAPH - 0xE7C0: 0x9132, //CJK UNIFIED IDEOGRAPH - 0xE7C1: 0x9130, //CJK UNIFIED IDEOGRAPH - 0xE7C2: 0x914A, //CJK UNIFIED IDEOGRAPH - 0xE7C3: 0x9156, //CJK UNIFIED IDEOGRAPH - 0xE7C4: 0x9158, //CJK UNIFIED IDEOGRAPH - 0xE7C5: 0x9163, //CJK UNIFIED IDEOGRAPH - 0xE7C6: 0x9165, //CJK UNIFIED IDEOGRAPH - 0xE7C7: 0x9169, //CJK UNIFIED IDEOGRAPH - 0xE7C8: 0x9173, //CJK UNIFIED IDEOGRAPH - 0xE7C9: 0x9172, //CJK UNIFIED IDEOGRAPH - 0xE7CA: 0x918B, //CJK UNIFIED IDEOGRAPH - 0xE7CB: 0x9189, //CJK UNIFIED IDEOGRAPH - 0xE7CC: 0x9182, //CJK UNIFIED IDEOGRAPH - 0xE7CD: 0x91A2, //CJK UNIFIED IDEOGRAPH - 0xE7CE: 0x91AB, //CJK UNIFIED IDEOGRAPH - 0xE7CF: 0x91AF, //CJK UNIFIED IDEOGRAPH - 0xE7D0: 0x91AA, //CJK UNIFIED IDEOGRAPH - 0xE7D1: 0x91B5, //CJK UNIFIED IDEOGRAPH - 0xE7D2: 0x91B4, //CJK UNIFIED IDEOGRAPH - 0xE7D3: 0x91BA, //CJK UNIFIED IDEOGRAPH - 0xE7D4: 0x91C0, //CJK UNIFIED IDEOGRAPH - 0xE7D5: 0x91C1, //CJK UNIFIED IDEOGRAPH - 0xE7D6: 0x91C9, //CJK UNIFIED IDEOGRAPH - 0xE7D7: 0x91CB, //CJK UNIFIED IDEOGRAPH - 0xE7D8: 0x91D0, //CJK UNIFIED IDEOGRAPH - 0xE7D9: 0x91D6, //CJK UNIFIED IDEOGRAPH - 0xE7DA: 0x91DF, //CJK UNIFIED IDEOGRAPH - 0xE7DB: 0x91E1, //CJK UNIFIED IDEOGRAPH - 0xE7DC: 0x91DB, //CJK UNIFIED IDEOGRAPH - 0xE7DD: 0x91FC, //CJK UNIFIED IDEOGRAPH - 0xE7DE: 0x91F5, //CJK UNIFIED IDEOGRAPH - 0xE7DF: 0x91F6, //CJK UNIFIED IDEOGRAPH - 0xE7E0: 0x921E, //CJK UNIFIED IDEOGRAPH - 0xE7E1: 0x91FF, //CJK UNIFIED IDEOGRAPH - 0xE7E2: 0x9214, //CJK UNIFIED IDEOGRAPH - 0xE7E3: 0x922C, //CJK UNIFIED IDEOGRAPH - 0xE7E4: 0x9215, //CJK UNIFIED IDEOGRAPH - 0xE7E5: 0x9211, //CJK UNIFIED IDEOGRAPH - 0xE7E6: 0x925E, //CJK UNIFIED IDEOGRAPH - 0xE7E7: 0x9257, //CJK UNIFIED IDEOGRAPH - 0xE7E8: 0x9245, //CJK UNIFIED IDEOGRAPH - 0xE7E9: 0x9249, //CJK UNIFIED IDEOGRAPH - 0xE7EA: 0x9264, //CJK UNIFIED IDEOGRAPH - 0xE7EB: 0x9248, //CJK UNIFIED IDEOGRAPH - 0xE7EC: 0x9295, //CJK UNIFIED IDEOGRAPH - 0xE7ED: 0x923F, //CJK UNIFIED IDEOGRAPH - 0xE7EE: 0x924B, //CJK UNIFIED IDEOGRAPH - 0xE7EF: 0x9250, //CJK UNIFIED IDEOGRAPH - 0xE7F0: 0x929C, //CJK UNIFIED IDEOGRAPH - 0xE7F1: 0x9296, //CJK UNIFIED IDEOGRAPH - 0xE7F2: 0x9293, //CJK UNIFIED IDEOGRAPH - 0xE7F3: 0x929B, //CJK UNIFIED IDEOGRAPH - 0xE7F4: 0x925A, //CJK UNIFIED IDEOGRAPH - 0xE7F5: 0x92CF, //CJK UNIFIED IDEOGRAPH - 0xE7F6: 0x92B9, //CJK UNIFIED IDEOGRAPH - 0xE7F7: 0x92B7, //CJK UNIFIED IDEOGRAPH - 0xE7F8: 0x92E9, //CJK UNIFIED IDEOGRAPH - 0xE7F9: 0x930F, //CJK UNIFIED IDEOGRAPH - 0xE7FA: 0x92FA, //CJK UNIFIED IDEOGRAPH - 0xE7FB: 0x9344, //CJK UNIFIED IDEOGRAPH - 0xE7FC: 0x932E, //CJK UNIFIED IDEOGRAPH - 0xE840: 0x9319, //CJK UNIFIED IDEOGRAPH - 0xE841: 0x9322, //CJK UNIFIED IDEOGRAPH - 0xE842: 0x931A, //CJK UNIFIED IDEOGRAPH - 0xE843: 0x9323, //CJK UNIFIED IDEOGRAPH - 0xE844: 0x933A, //CJK UNIFIED IDEOGRAPH - 0xE845: 0x9335, //CJK UNIFIED IDEOGRAPH - 0xE846: 0x933B, //CJK UNIFIED IDEOGRAPH - 0xE847: 0x935C, //CJK UNIFIED IDEOGRAPH - 0xE848: 0x9360, //CJK UNIFIED IDEOGRAPH - 0xE849: 0x937C, //CJK UNIFIED IDEOGRAPH - 0xE84A: 0x936E, //CJK UNIFIED IDEOGRAPH - 0xE84B: 0x9356, //CJK UNIFIED IDEOGRAPH - 0xE84C: 0x93B0, //CJK UNIFIED IDEOGRAPH - 0xE84D: 0x93AC, //CJK UNIFIED IDEOGRAPH - 0xE84E: 0x93AD, //CJK UNIFIED IDEOGRAPH - 0xE84F: 0x9394, //CJK UNIFIED IDEOGRAPH - 0xE850: 0x93B9, //CJK UNIFIED IDEOGRAPH - 0xE851: 0x93D6, //CJK UNIFIED IDEOGRAPH - 0xE852: 0x93D7, //CJK UNIFIED IDEOGRAPH - 0xE853: 0x93E8, //CJK UNIFIED IDEOGRAPH - 0xE854: 0x93E5, //CJK UNIFIED IDEOGRAPH - 0xE855: 0x93D8, //CJK UNIFIED IDEOGRAPH - 0xE856: 0x93C3, //CJK UNIFIED IDEOGRAPH - 0xE857: 0x93DD, //CJK UNIFIED IDEOGRAPH - 0xE858: 0x93D0, //CJK UNIFIED IDEOGRAPH - 0xE859: 0x93C8, //CJK UNIFIED IDEOGRAPH - 0xE85A: 0x93E4, //CJK UNIFIED IDEOGRAPH - 0xE85B: 0x941A, //CJK UNIFIED IDEOGRAPH - 0xE85C: 0x9414, //CJK UNIFIED IDEOGRAPH - 0xE85D: 0x9413, //CJK UNIFIED IDEOGRAPH - 0xE85E: 0x9403, //CJK UNIFIED IDEOGRAPH - 0xE85F: 0x9407, //CJK UNIFIED IDEOGRAPH - 0xE860: 0x9410, //CJK UNIFIED IDEOGRAPH - 0xE861: 0x9436, //CJK UNIFIED IDEOGRAPH - 0xE862: 0x942B, //CJK UNIFIED IDEOGRAPH - 0xE863: 0x9435, //CJK UNIFIED IDEOGRAPH - 0xE864: 0x9421, //CJK UNIFIED IDEOGRAPH - 0xE865: 0x943A, //CJK UNIFIED IDEOGRAPH - 0xE866: 0x9441, //CJK UNIFIED IDEOGRAPH - 0xE867: 0x9452, //CJK UNIFIED IDEOGRAPH - 0xE868: 0x9444, //CJK UNIFIED IDEOGRAPH - 0xE869: 0x945B, //CJK UNIFIED IDEOGRAPH - 0xE86A: 0x9460, //CJK UNIFIED IDEOGRAPH - 0xE86B: 0x9462, //CJK UNIFIED IDEOGRAPH - 0xE86C: 0x945E, //CJK UNIFIED IDEOGRAPH - 0xE86D: 0x946A, //CJK UNIFIED IDEOGRAPH - 0xE86E: 0x9229, //CJK UNIFIED IDEOGRAPH - 0xE86F: 0x9470, //CJK UNIFIED IDEOGRAPH - 0xE870: 0x9475, //CJK UNIFIED IDEOGRAPH - 0xE871: 0x9477, //CJK UNIFIED IDEOGRAPH - 0xE872: 0x947D, //CJK UNIFIED IDEOGRAPH - 0xE873: 0x945A, //CJK UNIFIED IDEOGRAPH - 0xE874: 0x947C, //CJK UNIFIED IDEOGRAPH - 0xE875: 0x947E, //CJK UNIFIED IDEOGRAPH - 0xE876: 0x9481, //CJK UNIFIED IDEOGRAPH - 0xE877: 0x947F, //CJK UNIFIED IDEOGRAPH - 0xE878: 0x9582, //CJK UNIFIED IDEOGRAPH - 0xE879: 0x9587, //CJK UNIFIED IDEOGRAPH - 0xE87A: 0x958A, //CJK UNIFIED IDEOGRAPH - 0xE87B: 0x9594, //CJK UNIFIED IDEOGRAPH - 0xE87C: 0x9596, //CJK UNIFIED IDEOGRAPH - 0xE87D: 0x9598, //CJK UNIFIED IDEOGRAPH - 0xE87E: 0x9599, //CJK UNIFIED IDEOGRAPH - 0xE880: 0x95A0, //CJK UNIFIED IDEOGRAPH - 0xE881: 0x95A8, //CJK UNIFIED IDEOGRAPH - 0xE882: 0x95A7, //CJK UNIFIED IDEOGRAPH - 0xE883: 0x95AD, //CJK UNIFIED IDEOGRAPH - 0xE884: 0x95BC, //CJK UNIFIED IDEOGRAPH - 0xE885: 0x95BB, //CJK UNIFIED IDEOGRAPH - 0xE886: 0x95B9, //CJK UNIFIED IDEOGRAPH - 0xE887: 0x95BE, //CJK UNIFIED IDEOGRAPH - 0xE888: 0x95CA, //CJK UNIFIED IDEOGRAPH - 0xE889: 0x6FF6, //CJK UNIFIED IDEOGRAPH - 0xE88A: 0x95C3, //CJK UNIFIED IDEOGRAPH - 0xE88B: 0x95CD, //CJK UNIFIED IDEOGRAPH - 0xE88C: 0x95CC, //CJK UNIFIED IDEOGRAPH - 0xE88D: 0x95D5, //CJK UNIFIED IDEOGRAPH - 0xE88E: 0x95D4, //CJK UNIFIED IDEOGRAPH - 0xE88F: 0x95D6, //CJK UNIFIED IDEOGRAPH - 0xE890: 0x95DC, //CJK UNIFIED IDEOGRAPH - 0xE891: 0x95E1, //CJK UNIFIED IDEOGRAPH - 0xE892: 0x95E5, //CJK UNIFIED IDEOGRAPH - 0xE893: 0x95E2, //CJK UNIFIED IDEOGRAPH - 0xE894: 0x9621, //CJK UNIFIED IDEOGRAPH - 0xE895: 0x9628, //CJK UNIFIED IDEOGRAPH - 0xE896: 0x962E, //CJK UNIFIED IDEOGRAPH - 0xE897: 0x962F, //CJK UNIFIED IDEOGRAPH - 0xE898: 0x9642, //CJK UNIFIED IDEOGRAPH - 0xE899: 0x964C, //CJK UNIFIED IDEOGRAPH - 0xE89A: 0x964F, //CJK UNIFIED IDEOGRAPH - 0xE89B: 0x964B, //CJK UNIFIED IDEOGRAPH - 0xE89C: 0x9677, //CJK UNIFIED IDEOGRAPH - 0xE89D: 0x965C, //CJK UNIFIED IDEOGRAPH - 0xE89E: 0x965E, //CJK UNIFIED IDEOGRAPH - 0xE89F: 0x965D, //CJK UNIFIED IDEOGRAPH - 0xE8A0: 0x965F, //CJK UNIFIED IDEOGRAPH - 0xE8A1: 0x9666, //CJK UNIFIED IDEOGRAPH - 0xE8A2: 0x9672, //CJK UNIFIED IDEOGRAPH - 0xE8A3: 0x966C, //CJK UNIFIED IDEOGRAPH - 0xE8A4: 0x968D, //CJK UNIFIED IDEOGRAPH - 0xE8A5: 0x9698, //CJK UNIFIED IDEOGRAPH - 0xE8A6: 0x9695, //CJK UNIFIED IDEOGRAPH - 0xE8A7: 0x9697, //CJK UNIFIED IDEOGRAPH - 0xE8A8: 0x96AA, //CJK UNIFIED IDEOGRAPH - 0xE8A9: 0x96A7, //CJK UNIFIED IDEOGRAPH - 0xE8AA: 0x96B1, //CJK UNIFIED IDEOGRAPH - 0xE8AB: 0x96B2, //CJK UNIFIED IDEOGRAPH - 0xE8AC: 0x96B0, //CJK UNIFIED IDEOGRAPH - 0xE8AD: 0x96B4, //CJK UNIFIED IDEOGRAPH - 0xE8AE: 0x96B6, //CJK UNIFIED IDEOGRAPH - 0xE8AF: 0x96B8, //CJK UNIFIED IDEOGRAPH - 0xE8B0: 0x96B9, //CJK UNIFIED IDEOGRAPH - 0xE8B1: 0x96CE, //CJK UNIFIED IDEOGRAPH - 0xE8B2: 0x96CB, //CJK UNIFIED IDEOGRAPH - 0xE8B3: 0x96C9, //CJK UNIFIED IDEOGRAPH - 0xE8B4: 0x96CD, //CJK UNIFIED IDEOGRAPH - 0xE8B5: 0x894D, //CJK UNIFIED IDEOGRAPH - 0xE8B6: 0x96DC, //CJK UNIFIED IDEOGRAPH - 0xE8B7: 0x970D, //CJK UNIFIED IDEOGRAPH - 0xE8B8: 0x96D5, //CJK UNIFIED IDEOGRAPH - 0xE8B9: 0x96F9, //CJK UNIFIED IDEOGRAPH - 0xE8BA: 0x9704, //CJK UNIFIED IDEOGRAPH - 0xE8BB: 0x9706, //CJK UNIFIED IDEOGRAPH - 0xE8BC: 0x9708, //CJK UNIFIED IDEOGRAPH - 0xE8BD: 0x9713, //CJK UNIFIED IDEOGRAPH - 0xE8BE: 0x970E, //CJK UNIFIED IDEOGRAPH - 0xE8BF: 0x9711, //CJK UNIFIED IDEOGRAPH - 0xE8C0: 0x970F, //CJK UNIFIED IDEOGRAPH - 0xE8C1: 0x9716, //CJK UNIFIED IDEOGRAPH - 0xE8C2: 0x9719, //CJK UNIFIED IDEOGRAPH - 0xE8C3: 0x9724, //CJK UNIFIED IDEOGRAPH - 0xE8C4: 0x972A, //CJK UNIFIED IDEOGRAPH - 0xE8C5: 0x9730, //CJK UNIFIED IDEOGRAPH - 0xE8C6: 0x9739, //CJK UNIFIED IDEOGRAPH - 0xE8C7: 0x973D, //CJK UNIFIED IDEOGRAPH - 0xE8C8: 0x973E, //CJK UNIFIED IDEOGRAPH - 0xE8C9: 0x9744, //CJK UNIFIED IDEOGRAPH - 0xE8CA: 0x9746, //CJK UNIFIED IDEOGRAPH - 0xE8CB: 0x9748, //CJK UNIFIED IDEOGRAPH - 0xE8CC: 0x9742, //CJK UNIFIED IDEOGRAPH - 0xE8CD: 0x9749, //CJK UNIFIED IDEOGRAPH - 0xE8CE: 0x975C, //CJK UNIFIED IDEOGRAPH - 0xE8CF: 0x9760, //CJK UNIFIED IDEOGRAPH - 0xE8D0: 0x9764, //CJK UNIFIED IDEOGRAPH - 0xE8D1: 0x9766, //CJK UNIFIED IDEOGRAPH - 0xE8D2: 0x9768, //CJK UNIFIED IDEOGRAPH - 0xE8D3: 0x52D2, //CJK UNIFIED IDEOGRAPH - 0xE8D4: 0x976B, //CJK UNIFIED IDEOGRAPH - 0xE8D5: 0x9771, //CJK UNIFIED IDEOGRAPH - 0xE8D6: 0x9779, //CJK UNIFIED IDEOGRAPH - 0xE8D7: 0x9785, //CJK UNIFIED IDEOGRAPH - 0xE8D8: 0x977C, //CJK UNIFIED IDEOGRAPH - 0xE8D9: 0x9781, //CJK UNIFIED IDEOGRAPH - 0xE8DA: 0x977A, //CJK UNIFIED IDEOGRAPH - 0xE8DB: 0x9786, //CJK UNIFIED IDEOGRAPH - 0xE8DC: 0x978B, //CJK UNIFIED IDEOGRAPH - 0xE8DD: 0x978F, //CJK UNIFIED IDEOGRAPH - 0xE8DE: 0x9790, //CJK UNIFIED IDEOGRAPH - 0xE8DF: 0x979C, //CJK UNIFIED IDEOGRAPH - 0xE8E0: 0x97A8, //CJK UNIFIED IDEOGRAPH - 0xE8E1: 0x97A6, //CJK UNIFIED IDEOGRAPH - 0xE8E2: 0x97A3, //CJK UNIFIED IDEOGRAPH - 0xE8E3: 0x97B3, //CJK UNIFIED IDEOGRAPH - 0xE8E4: 0x97B4, //CJK UNIFIED IDEOGRAPH - 0xE8E5: 0x97C3, //CJK UNIFIED IDEOGRAPH - 0xE8E6: 0x97C6, //CJK UNIFIED IDEOGRAPH - 0xE8E7: 0x97C8, //CJK UNIFIED IDEOGRAPH - 0xE8E8: 0x97CB, //CJK UNIFIED IDEOGRAPH - 0xE8E9: 0x97DC, //CJK UNIFIED IDEOGRAPH - 0xE8EA: 0x97ED, //CJK UNIFIED IDEOGRAPH - 0xE8EB: 0x9F4F, //CJK UNIFIED IDEOGRAPH - 0xE8EC: 0x97F2, //CJK UNIFIED IDEOGRAPH - 0xE8ED: 0x7ADF, //CJK UNIFIED IDEOGRAPH - 0xE8EE: 0x97F6, //CJK UNIFIED IDEOGRAPH - 0xE8EF: 0x97F5, //CJK UNIFIED IDEOGRAPH - 0xE8F0: 0x980F, //CJK UNIFIED IDEOGRAPH - 0xE8F1: 0x980C, //CJK UNIFIED IDEOGRAPH - 0xE8F2: 0x9838, //CJK UNIFIED IDEOGRAPH - 0xE8F3: 0x9824, //CJK UNIFIED IDEOGRAPH - 0xE8F4: 0x9821, //CJK UNIFIED IDEOGRAPH - 0xE8F5: 0x9837, //CJK UNIFIED IDEOGRAPH - 0xE8F6: 0x983D, //CJK UNIFIED IDEOGRAPH - 0xE8F7: 0x9846, //CJK UNIFIED IDEOGRAPH - 0xE8F8: 0x984F, //CJK UNIFIED IDEOGRAPH - 0xE8F9: 0x984B, //CJK UNIFIED IDEOGRAPH - 0xE8FA: 0x986B, //CJK UNIFIED IDEOGRAPH - 0xE8FB: 0x986F, //CJK UNIFIED IDEOGRAPH - 0xE8FC: 0x9870, //CJK UNIFIED IDEOGRAPH - 0xE940: 0x9871, //CJK UNIFIED IDEOGRAPH - 0xE941: 0x9874, //CJK UNIFIED IDEOGRAPH - 0xE942: 0x9873, //CJK UNIFIED IDEOGRAPH - 0xE943: 0x98AA, //CJK UNIFIED IDEOGRAPH - 0xE944: 0x98AF, //CJK UNIFIED IDEOGRAPH - 0xE945: 0x98B1, //CJK UNIFIED IDEOGRAPH - 0xE946: 0x98B6, //CJK UNIFIED IDEOGRAPH - 0xE947: 0x98C4, //CJK UNIFIED IDEOGRAPH - 0xE948: 0x98C3, //CJK UNIFIED IDEOGRAPH - 0xE949: 0x98C6, //CJK UNIFIED IDEOGRAPH - 0xE94A: 0x98E9, //CJK UNIFIED IDEOGRAPH - 0xE94B: 0x98EB, //CJK UNIFIED IDEOGRAPH - 0xE94C: 0x9903, //CJK UNIFIED IDEOGRAPH - 0xE94D: 0x9909, //CJK UNIFIED IDEOGRAPH - 0xE94E: 0x9912, //CJK UNIFIED IDEOGRAPH - 0xE94F: 0x9914, //CJK UNIFIED IDEOGRAPH - 0xE950: 0x9918, //CJK UNIFIED IDEOGRAPH - 0xE951: 0x9921, //CJK UNIFIED IDEOGRAPH - 0xE952: 0x991D, //CJK UNIFIED IDEOGRAPH - 0xE953: 0x991E, //CJK UNIFIED IDEOGRAPH - 0xE954: 0x9924, //CJK UNIFIED IDEOGRAPH - 0xE955: 0x9920, //CJK UNIFIED IDEOGRAPH - 0xE956: 0x992C, //CJK UNIFIED IDEOGRAPH - 0xE957: 0x992E, //CJK UNIFIED IDEOGRAPH - 0xE958: 0x993D, //CJK UNIFIED IDEOGRAPH - 0xE959: 0x993E, //CJK UNIFIED IDEOGRAPH - 0xE95A: 0x9942, //CJK UNIFIED IDEOGRAPH - 0xE95B: 0x9949, //CJK UNIFIED IDEOGRAPH - 0xE95C: 0x9945, //CJK UNIFIED IDEOGRAPH - 0xE95D: 0x9950, //CJK UNIFIED IDEOGRAPH - 0xE95E: 0x994B, //CJK UNIFIED IDEOGRAPH - 0xE95F: 0x9951, //CJK UNIFIED IDEOGRAPH - 0xE960: 0x9952, //CJK UNIFIED IDEOGRAPH - 0xE961: 0x994C, //CJK UNIFIED IDEOGRAPH - 0xE962: 0x9955, //CJK UNIFIED IDEOGRAPH - 0xE963: 0x9997, //CJK UNIFIED IDEOGRAPH - 0xE964: 0x9998, //CJK UNIFIED IDEOGRAPH - 0xE965: 0x99A5, //CJK UNIFIED IDEOGRAPH - 0xE966: 0x99AD, //CJK UNIFIED IDEOGRAPH - 0xE967: 0x99AE, //CJK UNIFIED IDEOGRAPH - 0xE968: 0x99BC, //CJK UNIFIED IDEOGRAPH - 0xE969: 0x99DF, //CJK UNIFIED IDEOGRAPH - 0xE96A: 0x99DB, //CJK UNIFIED IDEOGRAPH - 0xE96B: 0x99DD, //CJK UNIFIED IDEOGRAPH - 0xE96C: 0x99D8, //CJK UNIFIED IDEOGRAPH - 0xE96D: 0x99D1, //CJK UNIFIED IDEOGRAPH - 0xE96E: 0x99ED, //CJK UNIFIED IDEOGRAPH - 0xE96F: 0x99EE, //CJK UNIFIED IDEOGRAPH - 0xE970: 0x99F1, //CJK UNIFIED IDEOGRAPH - 0xE971: 0x99F2, //CJK UNIFIED IDEOGRAPH - 0xE972: 0x99FB, //CJK UNIFIED IDEOGRAPH - 0xE973: 0x99F8, //CJK UNIFIED IDEOGRAPH - 0xE974: 0x9A01, //CJK UNIFIED IDEOGRAPH - 0xE975: 0x9A0F, //CJK UNIFIED IDEOGRAPH - 0xE976: 0x9A05, //CJK UNIFIED IDEOGRAPH - 0xE977: 0x99E2, //CJK UNIFIED IDEOGRAPH - 0xE978: 0x9A19, //CJK UNIFIED IDEOGRAPH - 0xE979: 0x9A2B, //CJK UNIFIED IDEOGRAPH - 0xE97A: 0x9A37, //CJK UNIFIED IDEOGRAPH - 0xE97B: 0x9A45, //CJK UNIFIED IDEOGRAPH - 0xE97C: 0x9A42, //CJK UNIFIED IDEOGRAPH - 0xE97D: 0x9A40, //CJK UNIFIED IDEOGRAPH - 0xE97E: 0x9A43, //CJK UNIFIED IDEOGRAPH - 0xE980: 0x9A3E, //CJK UNIFIED IDEOGRAPH - 0xE981: 0x9A55, //CJK UNIFIED IDEOGRAPH - 0xE982: 0x9A4D, //CJK UNIFIED IDEOGRAPH - 0xE983: 0x9A5B, //CJK UNIFIED IDEOGRAPH - 0xE984: 0x9A57, //CJK UNIFIED IDEOGRAPH - 0xE985: 0x9A5F, //CJK UNIFIED IDEOGRAPH - 0xE986: 0x9A62, //CJK UNIFIED IDEOGRAPH - 0xE987: 0x9A65, //CJK UNIFIED IDEOGRAPH - 0xE988: 0x9A64, //CJK UNIFIED IDEOGRAPH - 0xE989: 0x9A69, //CJK UNIFIED IDEOGRAPH - 0xE98A: 0x9A6B, //CJK UNIFIED IDEOGRAPH - 0xE98B: 0x9A6A, //CJK UNIFIED IDEOGRAPH - 0xE98C: 0x9AAD, //CJK UNIFIED IDEOGRAPH - 0xE98D: 0x9AB0, //CJK UNIFIED IDEOGRAPH - 0xE98E: 0x9ABC, //CJK UNIFIED IDEOGRAPH - 0xE98F: 0x9AC0, //CJK UNIFIED IDEOGRAPH - 0xE990: 0x9ACF, //CJK UNIFIED IDEOGRAPH - 0xE991: 0x9AD1, //CJK UNIFIED IDEOGRAPH - 0xE992: 0x9AD3, //CJK UNIFIED IDEOGRAPH - 0xE993: 0x9AD4, //CJK UNIFIED IDEOGRAPH - 0xE994: 0x9ADE, //CJK UNIFIED IDEOGRAPH - 0xE995: 0x9ADF, //CJK UNIFIED IDEOGRAPH - 0xE996: 0x9AE2, //CJK UNIFIED IDEOGRAPH - 0xE997: 0x9AE3, //CJK UNIFIED IDEOGRAPH - 0xE998: 0x9AE6, //CJK UNIFIED IDEOGRAPH - 0xE999: 0x9AEF, //CJK UNIFIED IDEOGRAPH - 0xE99A: 0x9AEB, //CJK UNIFIED IDEOGRAPH - 0xE99B: 0x9AEE, //CJK UNIFIED IDEOGRAPH - 0xE99C: 0x9AF4, //CJK UNIFIED IDEOGRAPH - 0xE99D: 0x9AF1, //CJK UNIFIED IDEOGRAPH - 0xE99E: 0x9AF7, //CJK UNIFIED IDEOGRAPH - 0xE99F: 0x9AFB, //CJK UNIFIED IDEOGRAPH - 0xE9A0: 0x9B06, //CJK UNIFIED IDEOGRAPH - 0xE9A1: 0x9B18, //CJK UNIFIED IDEOGRAPH - 0xE9A2: 0x9B1A, //CJK UNIFIED IDEOGRAPH - 0xE9A3: 0x9B1F, //CJK UNIFIED IDEOGRAPH - 0xE9A4: 0x9B22, //CJK UNIFIED IDEOGRAPH - 0xE9A5: 0x9B23, //CJK UNIFIED IDEOGRAPH - 0xE9A6: 0x9B25, //CJK UNIFIED IDEOGRAPH - 0xE9A7: 0x9B27, //CJK UNIFIED IDEOGRAPH - 0xE9A8: 0x9B28, //CJK UNIFIED IDEOGRAPH - 0xE9A9: 0x9B29, //CJK UNIFIED IDEOGRAPH - 0xE9AA: 0x9B2A, //CJK UNIFIED IDEOGRAPH - 0xE9AB: 0x9B2E, //CJK UNIFIED IDEOGRAPH - 0xE9AC: 0x9B2F, //CJK UNIFIED IDEOGRAPH - 0xE9AD: 0x9B32, //CJK UNIFIED IDEOGRAPH - 0xE9AE: 0x9B44, //CJK UNIFIED IDEOGRAPH - 0xE9AF: 0x9B43, //CJK UNIFIED IDEOGRAPH - 0xE9B0: 0x9B4F, //CJK UNIFIED IDEOGRAPH - 0xE9B1: 0x9B4D, //CJK UNIFIED IDEOGRAPH - 0xE9B2: 0x9B4E, //CJK UNIFIED IDEOGRAPH - 0xE9B3: 0x9B51, //CJK UNIFIED IDEOGRAPH - 0xE9B4: 0x9B58, //CJK UNIFIED IDEOGRAPH - 0xE9B5: 0x9B74, //CJK UNIFIED IDEOGRAPH - 0xE9B6: 0x9B93, //CJK UNIFIED IDEOGRAPH - 0xE9B7: 0x9B83, //CJK UNIFIED IDEOGRAPH - 0xE9B8: 0x9B91, //CJK UNIFIED IDEOGRAPH - 0xE9B9: 0x9B96, //CJK UNIFIED IDEOGRAPH - 0xE9BA: 0x9B97, //CJK UNIFIED IDEOGRAPH - 0xE9BB: 0x9B9F, //CJK UNIFIED IDEOGRAPH - 0xE9BC: 0x9BA0, //CJK UNIFIED IDEOGRAPH - 0xE9BD: 0x9BA8, //CJK UNIFIED IDEOGRAPH - 0xE9BE: 0x9BB4, //CJK UNIFIED IDEOGRAPH - 0xE9BF: 0x9BC0, //CJK UNIFIED IDEOGRAPH - 0xE9C0: 0x9BCA, //CJK UNIFIED IDEOGRAPH - 0xE9C1: 0x9BB9, //CJK UNIFIED IDEOGRAPH - 0xE9C2: 0x9BC6, //CJK UNIFIED IDEOGRAPH - 0xE9C3: 0x9BCF, //CJK UNIFIED IDEOGRAPH - 0xE9C4: 0x9BD1, //CJK UNIFIED IDEOGRAPH - 0xE9C5: 0x9BD2, //CJK UNIFIED IDEOGRAPH - 0xE9C6: 0x9BE3, //CJK UNIFIED IDEOGRAPH - 0xE9C7: 0x9BE2, //CJK UNIFIED IDEOGRAPH - 0xE9C8: 0x9BE4, //CJK UNIFIED IDEOGRAPH - 0xE9C9: 0x9BD4, //CJK UNIFIED IDEOGRAPH - 0xE9CA: 0x9BE1, //CJK UNIFIED IDEOGRAPH - 0xE9CB: 0x9C3A, //CJK UNIFIED IDEOGRAPH - 0xE9CC: 0x9BF2, //CJK UNIFIED IDEOGRAPH - 0xE9CD: 0x9BF1, //CJK UNIFIED IDEOGRAPH - 0xE9CE: 0x9BF0, //CJK UNIFIED IDEOGRAPH - 0xE9CF: 0x9C15, //CJK UNIFIED IDEOGRAPH - 0xE9D0: 0x9C14, //CJK UNIFIED IDEOGRAPH - 0xE9D1: 0x9C09, //CJK UNIFIED IDEOGRAPH - 0xE9D2: 0x9C13, //CJK UNIFIED IDEOGRAPH - 0xE9D3: 0x9C0C, //CJK UNIFIED IDEOGRAPH - 0xE9D4: 0x9C06, //CJK UNIFIED IDEOGRAPH - 0xE9D5: 0x9C08, //CJK UNIFIED IDEOGRAPH - 0xE9D6: 0x9C12, //CJK UNIFIED IDEOGRAPH - 0xE9D7: 0x9C0A, //CJK UNIFIED IDEOGRAPH - 0xE9D8: 0x9C04, //CJK UNIFIED IDEOGRAPH - 0xE9D9: 0x9C2E, //CJK UNIFIED IDEOGRAPH - 0xE9DA: 0x9C1B, //CJK UNIFIED IDEOGRAPH - 0xE9DB: 0x9C25, //CJK UNIFIED IDEOGRAPH - 0xE9DC: 0x9C24, //CJK UNIFIED IDEOGRAPH - 0xE9DD: 0x9C21, //CJK UNIFIED IDEOGRAPH - 0xE9DE: 0x9C30, //CJK UNIFIED IDEOGRAPH - 0xE9DF: 0x9C47, //CJK UNIFIED IDEOGRAPH - 0xE9E0: 0x9C32, //CJK UNIFIED IDEOGRAPH - 0xE9E1: 0x9C46, //CJK UNIFIED IDEOGRAPH - 0xE9E2: 0x9C3E, //CJK UNIFIED IDEOGRAPH - 0xE9E3: 0x9C5A, //CJK UNIFIED IDEOGRAPH - 0xE9E4: 0x9C60, //CJK UNIFIED IDEOGRAPH - 0xE9E5: 0x9C67, //CJK UNIFIED IDEOGRAPH - 0xE9E6: 0x9C76, //CJK UNIFIED IDEOGRAPH - 0xE9E7: 0x9C78, //CJK UNIFIED IDEOGRAPH - 0xE9E8: 0x9CE7, //CJK UNIFIED IDEOGRAPH - 0xE9E9: 0x9CEC, //CJK UNIFIED IDEOGRAPH - 0xE9EA: 0x9CF0, //CJK UNIFIED IDEOGRAPH - 0xE9EB: 0x9D09, //CJK UNIFIED IDEOGRAPH - 0xE9EC: 0x9D08, //CJK UNIFIED IDEOGRAPH - 0xE9ED: 0x9CEB, //CJK UNIFIED IDEOGRAPH - 0xE9EE: 0x9D03, //CJK UNIFIED IDEOGRAPH - 0xE9EF: 0x9D06, //CJK UNIFIED IDEOGRAPH - 0xE9F0: 0x9D2A, //CJK UNIFIED IDEOGRAPH - 0xE9F1: 0x9D26, //CJK UNIFIED IDEOGRAPH - 0xE9F2: 0x9DAF, //CJK UNIFIED IDEOGRAPH - 0xE9F3: 0x9D23, //CJK UNIFIED IDEOGRAPH - 0xE9F4: 0x9D1F, //CJK UNIFIED IDEOGRAPH - 0xE9F5: 0x9D44, //CJK UNIFIED IDEOGRAPH - 0xE9F6: 0x9D15, //CJK UNIFIED IDEOGRAPH - 0xE9F7: 0x9D12, //CJK UNIFIED IDEOGRAPH - 0xE9F8: 0x9D41, //CJK UNIFIED IDEOGRAPH - 0xE9F9: 0x9D3F, //CJK UNIFIED IDEOGRAPH - 0xE9FA: 0x9D3E, //CJK UNIFIED IDEOGRAPH - 0xE9FB: 0x9D46, //CJK UNIFIED IDEOGRAPH - 0xE9FC: 0x9D48, //CJK UNIFIED IDEOGRAPH - 0xEA40: 0x9D5D, //CJK UNIFIED IDEOGRAPH - 0xEA41: 0x9D5E, //CJK UNIFIED IDEOGRAPH - 0xEA42: 0x9D64, //CJK UNIFIED IDEOGRAPH - 0xEA43: 0x9D51, //CJK UNIFIED IDEOGRAPH - 0xEA44: 0x9D50, //CJK UNIFIED IDEOGRAPH - 0xEA45: 0x9D59, //CJK UNIFIED IDEOGRAPH - 0xEA46: 0x9D72, //CJK UNIFIED IDEOGRAPH - 0xEA47: 0x9D89, //CJK UNIFIED IDEOGRAPH - 0xEA48: 0x9D87, //CJK UNIFIED IDEOGRAPH - 0xEA49: 0x9DAB, //CJK UNIFIED IDEOGRAPH - 0xEA4A: 0x9D6F, //CJK UNIFIED IDEOGRAPH - 0xEA4B: 0x9D7A, //CJK UNIFIED IDEOGRAPH - 0xEA4C: 0x9D9A, //CJK UNIFIED IDEOGRAPH - 0xEA4D: 0x9DA4, //CJK UNIFIED IDEOGRAPH - 0xEA4E: 0x9DA9, //CJK UNIFIED IDEOGRAPH - 0xEA4F: 0x9DB2, //CJK UNIFIED IDEOGRAPH - 0xEA50: 0x9DC4, //CJK UNIFIED IDEOGRAPH - 0xEA51: 0x9DC1, //CJK UNIFIED IDEOGRAPH - 0xEA52: 0x9DBB, //CJK UNIFIED IDEOGRAPH - 0xEA53: 0x9DB8, //CJK UNIFIED IDEOGRAPH - 0xEA54: 0x9DBA, //CJK UNIFIED IDEOGRAPH - 0xEA55: 0x9DC6, //CJK UNIFIED IDEOGRAPH - 0xEA56: 0x9DCF, //CJK UNIFIED IDEOGRAPH - 0xEA57: 0x9DC2, //CJK UNIFIED IDEOGRAPH - 0xEA58: 0x9DD9, //CJK UNIFIED IDEOGRAPH - 0xEA59: 0x9DD3, //CJK UNIFIED IDEOGRAPH - 0xEA5A: 0x9DF8, //CJK UNIFIED IDEOGRAPH - 0xEA5B: 0x9DE6, //CJK UNIFIED IDEOGRAPH - 0xEA5C: 0x9DED, //CJK UNIFIED IDEOGRAPH - 0xEA5D: 0x9DEF, //CJK UNIFIED IDEOGRAPH - 0xEA5E: 0x9DFD, //CJK UNIFIED IDEOGRAPH - 0xEA5F: 0x9E1A, //CJK UNIFIED IDEOGRAPH - 0xEA60: 0x9E1B, //CJK UNIFIED IDEOGRAPH - 0xEA61: 0x9E1E, //CJK UNIFIED IDEOGRAPH - 0xEA62: 0x9E75, //CJK UNIFIED IDEOGRAPH - 0xEA63: 0x9E79, //CJK UNIFIED IDEOGRAPH - 0xEA64: 0x9E7D, //CJK UNIFIED IDEOGRAPH - 0xEA65: 0x9E81, //CJK UNIFIED IDEOGRAPH - 0xEA66: 0x9E88, //CJK UNIFIED IDEOGRAPH - 0xEA67: 0x9E8B, //CJK UNIFIED IDEOGRAPH - 0xEA68: 0x9E8C, //CJK UNIFIED IDEOGRAPH - 0xEA69: 0x9E92, //CJK UNIFIED IDEOGRAPH - 0xEA6A: 0x9E95, //CJK UNIFIED IDEOGRAPH - 0xEA6B: 0x9E91, //CJK UNIFIED IDEOGRAPH - 0xEA6C: 0x9E9D, //CJK UNIFIED IDEOGRAPH - 0xEA6D: 0x9EA5, //CJK UNIFIED IDEOGRAPH - 0xEA6E: 0x9EA9, //CJK UNIFIED IDEOGRAPH - 0xEA6F: 0x9EB8, //CJK UNIFIED IDEOGRAPH - 0xEA70: 0x9EAA, //CJK UNIFIED IDEOGRAPH - 0xEA71: 0x9EAD, //CJK UNIFIED IDEOGRAPH - 0xEA72: 0x9761, //CJK UNIFIED IDEOGRAPH - 0xEA73: 0x9ECC, //CJK UNIFIED IDEOGRAPH - 0xEA74: 0x9ECE, //CJK UNIFIED IDEOGRAPH - 0xEA75: 0x9ECF, //CJK UNIFIED IDEOGRAPH - 0xEA76: 0x9ED0, //CJK UNIFIED IDEOGRAPH - 0xEA77: 0x9ED4, //CJK UNIFIED IDEOGRAPH - 0xEA78: 0x9EDC, //CJK UNIFIED IDEOGRAPH - 0xEA79: 0x9EDE, //CJK UNIFIED IDEOGRAPH - 0xEA7A: 0x9EDD, //CJK UNIFIED IDEOGRAPH - 0xEA7B: 0x9EE0, //CJK UNIFIED IDEOGRAPH - 0xEA7C: 0x9EE5, //CJK UNIFIED IDEOGRAPH - 0xEA7D: 0x9EE8, //CJK UNIFIED IDEOGRAPH - 0xEA7E: 0x9EEF, //CJK UNIFIED IDEOGRAPH - 0xEA80: 0x9EF4, //CJK UNIFIED IDEOGRAPH - 0xEA81: 0x9EF6, //CJK UNIFIED IDEOGRAPH - 0xEA82: 0x9EF7, //CJK UNIFIED IDEOGRAPH - 0xEA83: 0x9EF9, //CJK UNIFIED IDEOGRAPH - 0xEA84: 0x9EFB, //CJK UNIFIED IDEOGRAPH - 0xEA85: 0x9EFC, //CJK UNIFIED IDEOGRAPH - 0xEA86: 0x9EFD, //CJK UNIFIED IDEOGRAPH - 0xEA87: 0x9F07, //CJK UNIFIED IDEOGRAPH - 0xEA88: 0x9F08, //CJK UNIFIED IDEOGRAPH - 0xEA89: 0x76B7, //CJK UNIFIED IDEOGRAPH - 0xEA8A: 0x9F15, //CJK UNIFIED IDEOGRAPH - 0xEA8B: 0x9F21, //CJK UNIFIED IDEOGRAPH - 0xEA8C: 0x9F2C, //CJK UNIFIED IDEOGRAPH - 0xEA8D: 0x9F3E, //CJK UNIFIED IDEOGRAPH - 0xEA8E: 0x9F4A, //CJK UNIFIED IDEOGRAPH - 0xEA8F: 0x9F52, //CJK UNIFIED IDEOGRAPH - 0xEA90: 0x9F54, //CJK UNIFIED IDEOGRAPH - 0xEA91: 0x9F63, //CJK UNIFIED IDEOGRAPH - 0xEA92: 0x9F5F, //CJK UNIFIED IDEOGRAPH - 0xEA93: 0x9F60, //CJK UNIFIED IDEOGRAPH - 0xEA94: 0x9F61, //CJK UNIFIED IDEOGRAPH - 0xEA95: 0x9F66, //CJK UNIFIED IDEOGRAPH - 0xEA96: 0x9F67, //CJK UNIFIED IDEOGRAPH - 0xEA97: 0x9F6C, //CJK UNIFIED IDEOGRAPH - 0xEA98: 0x9F6A, //CJK UNIFIED IDEOGRAPH - 0xEA99: 0x9F77, //CJK UNIFIED IDEOGRAPH - 0xEA9A: 0x9F72, //CJK UNIFIED IDEOGRAPH - 0xEA9B: 0x9F76, //CJK UNIFIED IDEOGRAPH - 0xEA9C: 0x9F95, //CJK UNIFIED IDEOGRAPH - 0xEA9D: 0x9F9C, //CJK UNIFIED IDEOGRAPH - 0xEA9E: 0x9FA0, //CJK UNIFIED IDEOGRAPH - 0xEA9F: 0x582F, //CJK UNIFIED IDEOGRAPH - 0xEAA0: 0x69C7, //CJK UNIFIED IDEOGRAPH - 0xEAA1: 0x9059, //CJK UNIFIED IDEOGRAPH - 0xEAA2: 0x7464, //CJK UNIFIED IDEOGRAPH - 0xEAA3: 0x51DC, //CJK UNIFIED IDEOGRAPH - 0xEAA4: 0x7199, //CJK UNIFIED IDEOGRAPH - 0xED40: 0x7E8A, //CJK UNIFIED IDEOGRAPH - 0xED41: 0x891C, //CJK UNIFIED IDEOGRAPH - 0xED42: 0x9348, //CJK UNIFIED IDEOGRAPH - 0xED43: 0x9288, //CJK UNIFIED IDEOGRAPH - 0xED44: 0x84DC, //CJK UNIFIED IDEOGRAPH - 0xED45: 0x4FC9, //CJK UNIFIED IDEOGRAPH - 0xED46: 0x70BB, //CJK UNIFIED IDEOGRAPH - 0xED47: 0x6631, //CJK UNIFIED IDEOGRAPH - 0xED48: 0x68C8, //CJK UNIFIED IDEOGRAPH - 0xED49: 0x92F9, //CJK UNIFIED IDEOGRAPH - 0xED4A: 0x66FB, //CJK UNIFIED IDEOGRAPH - 0xED4B: 0x5F45, //CJK UNIFIED IDEOGRAPH - 0xED4C: 0x4E28, //CJK UNIFIED IDEOGRAPH - 0xED4D: 0x4EE1, //CJK UNIFIED IDEOGRAPH - 0xED4E: 0x4EFC, //CJK UNIFIED IDEOGRAPH - 0xED4F: 0x4F00, //CJK UNIFIED IDEOGRAPH - 0xED50: 0x4F03, //CJK UNIFIED IDEOGRAPH - 0xED51: 0x4F39, //CJK UNIFIED IDEOGRAPH - 0xED52: 0x4F56, //CJK UNIFIED IDEOGRAPH - 0xED53: 0x4F92, //CJK UNIFIED IDEOGRAPH - 0xED54: 0x4F8A, //CJK UNIFIED IDEOGRAPH - 0xED55: 0x4F9A, //CJK UNIFIED IDEOGRAPH - 0xED56: 0x4F94, //CJK UNIFIED IDEOGRAPH - 0xED57: 0x4FCD, //CJK UNIFIED IDEOGRAPH - 0xED58: 0x5040, //CJK UNIFIED IDEOGRAPH - 0xED59: 0x5022, //CJK UNIFIED IDEOGRAPH - 0xED5A: 0x4FFF, //CJK UNIFIED IDEOGRAPH - 0xED5B: 0x501E, //CJK UNIFIED IDEOGRAPH - 0xED5C: 0x5046, //CJK UNIFIED IDEOGRAPH - 0xED5D: 0x5070, //CJK UNIFIED IDEOGRAPH - 0xED5E: 0x5042, //CJK UNIFIED IDEOGRAPH - 0xED5F: 0x5094, //CJK UNIFIED IDEOGRAPH - 0xED60: 0x50F4, //CJK UNIFIED IDEOGRAPH - 0xED61: 0x50D8, //CJK UNIFIED IDEOGRAPH - 0xED62: 0x514A, //CJK UNIFIED IDEOGRAPH - 0xED63: 0x5164, //CJK UNIFIED IDEOGRAPH - 0xED64: 0x519D, //CJK UNIFIED IDEOGRAPH - 0xED65: 0x51BE, //CJK UNIFIED IDEOGRAPH - 0xED66: 0x51EC, //CJK UNIFIED IDEOGRAPH - 0xED67: 0x5215, //CJK UNIFIED IDEOGRAPH - 0xED68: 0x529C, //CJK UNIFIED IDEOGRAPH - 0xED69: 0x52A6, //CJK UNIFIED IDEOGRAPH - 0xED6A: 0x52C0, //CJK UNIFIED IDEOGRAPH - 0xED6B: 0x52DB, //CJK UNIFIED IDEOGRAPH - 0xED6C: 0x5300, //CJK UNIFIED IDEOGRAPH - 0xED6D: 0x5307, //CJK UNIFIED IDEOGRAPH - 0xED6E: 0x5324, //CJK UNIFIED IDEOGRAPH - 0xED6F: 0x5372, //CJK UNIFIED IDEOGRAPH - 0xED70: 0x5393, //CJK UNIFIED IDEOGRAPH - 0xED71: 0x53B2, //CJK UNIFIED IDEOGRAPH - 0xED72: 0x53DD, //CJK UNIFIED IDEOGRAPH - 0xED73: 0xFA0E, //CJK COMPATIBILITY IDEOGRAPH - 0xED74: 0x549C, //CJK UNIFIED IDEOGRAPH - 0xED75: 0x548A, //CJK UNIFIED IDEOGRAPH - 0xED76: 0x54A9, //CJK UNIFIED IDEOGRAPH - 0xED77: 0x54FF, //CJK UNIFIED IDEOGRAPH - 0xED78: 0x5586, //CJK UNIFIED IDEOGRAPH - 0xED79: 0x5759, //CJK UNIFIED IDEOGRAPH - 0xED7A: 0x5765, //CJK UNIFIED IDEOGRAPH - 0xED7B: 0x57AC, //CJK UNIFIED IDEOGRAPH - 0xED7C: 0x57C8, //CJK UNIFIED IDEOGRAPH - 0xED7D: 0x57C7, //CJK UNIFIED IDEOGRAPH - 0xED7E: 0xFA0F, //CJK COMPATIBILITY IDEOGRAPH - 0xED80: 0xFA10, //CJK COMPATIBILITY IDEOGRAPH - 0xED81: 0x589E, //CJK UNIFIED IDEOGRAPH - 0xED82: 0x58B2, //CJK UNIFIED IDEOGRAPH - 0xED83: 0x590B, //CJK UNIFIED IDEOGRAPH - 0xED84: 0x5953, //CJK UNIFIED IDEOGRAPH - 0xED85: 0x595B, //CJK UNIFIED IDEOGRAPH - 0xED86: 0x595D, //CJK UNIFIED IDEOGRAPH - 0xED87: 0x5963, //CJK UNIFIED IDEOGRAPH - 0xED88: 0x59A4, //CJK UNIFIED IDEOGRAPH - 0xED89: 0x59BA, //CJK UNIFIED IDEOGRAPH - 0xED8A: 0x5B56, //CJK UNIFIED IDEOGRAPH - 0xED8B: 0x5BC0, //CJK UNIFIED IDEOGRAPH - 0xED8C: 0x752F, //CJK UNIFIED IDEOGRAPH - 0xED8D: 0x5BD8, //CJK UNIFIED IDEOGRAPH - 0xED8E: 0x5BEC, //CJK UNIFIED IDEOGRAPH - 0xED8F: 0x5C1E, //CJK UNIFIED IDEOGRAPH - 0xED90: 0x5CA6, //CJK UNIFIED IDEOGRAPH - 0xED91: 0x5CBA, //CJK UNIFIED IDEOGRAPH - 0xED92: 0x5CF5, //CJK UNIFIED IDEOGRAPH - 0xED93: 0x5D27, //CJK UNIFIED IDEOGRAPH - 0xED94: 0x5D53, //CJK UNIFIED IDEOGRAPH - 0xED95: 0xFA11, //CJK COMPATIBILITY IDEOGRAPH - 0xED96: 0x5D42, //CJK UNIFIED IDEOGRAPH - 0xED97: 0x5D6D, //CJK UNIFIED IDEOGRAPH - 0xED98: 0x5DB8, //CJK UNIFIED IDEOGRAPH - 0xED99: 0x5DB9, //CJK UNIFIED IDEOGRAPH - 0xED9A: 0x5DD0, //CJK UNIFIED IDEOGRAPH - 0xED9B: 0x5F21, //CJK UNIFIED IDEOGRAPH - 0xED9C: 0x5F34, //CJK UNIFIED IDEOGRAPH - 0xED9D: 0x5F67, //CJK UNIFIED IDEOGRAPH - 0xED9E: 0x5FB7, //CJK UNIFIED IDEOGRAPH - 0xED9F: 0x5FDE, //CJK UNIFIED IDEOGRAPH - 0xEDA0: 0x605D, //CJK UNIFIED IDEOGRAPH - 0xEDA1: 0x6085, //CJK UNIFIED IDEOGRAPH - 0xEDA2: 0x608A, //CJK UNIFIED IDEOGRAPH - 0xEDA3: 0x60DE, //CJK UNIFIED IDEOGRAPH - 0xEDA4: 0x60D5, //CJK UNIFIED IDEOGRAPH - 0xEDA5: 0x6120, //CJK UNIFIED IDEOGRAPH - 0xEDA6: 0x60F2, //CJK UNIFIED IDEOGRAPH - 0xEDA7: 0x6111, //CJK UNIFIED IDEOGRAPH - 0xEDA8: 0x6137, //CJK UNIFIED IDEOGRAPH - 0xEDA9: 0x6130, //CJK UNIFIED IDEOGRAPH - 0xEDAA: 0x6198, //CJK UNIFIED IDEOGRAPH - 0xEDAB: 0x6213, //CJK UNIFIED IDEOGRAPH - 0xEDAC: 0x62A6, //CJK UNIFIED IDEOGRAPH - 0xEDAD: 0x63F5, //CJK UNIFIED IDEOGRAPH - 0xEDAE: 0x6460, //CJK UNIFIED IDEOGRAPH - 0xEDAF: 0x649D, //CJK UNIFIED IDEOGRAPH - 0xEDB0: 0x64CE, //CJK UNIFIED IDEOGRAPH - 0xEDB1: 0x654E, //CJK UNIFIED IDEOGRAPH - 0xEDB2: 0x6600, //CJK UNIFIED IDEOGRAPH - 0xEDB3: 0x6615, //CJK UNIFIED IDEOGRAPH - 0xEDB4: 0x663B, //CJK UNIFIED IDEOGRAPH - 0xEDB5: 0x6609, //CJK UNIFIED IDEOGRAPH - 0xEDB6: 0x662E, //CJK UNIFIED IDEOGRAPH - 0xEDB7: 0x661E, //CJK UNIFIED IDEOGRAPH - 0xEDB8: 0x6624, //CJK UNIFIED IDEOGRAPH - 0xEDB9: 0x6665, //CJK UNIFIED IDEOGRAPH - 0xEDBA: 0x6657, //CJK UNIFIED IDEOGRAPH - 0xEDBB: 0x6659, //CJK UNIFIED IDEOGRAPH - 0xEDBC: 0xFA12, //CJK COMPATIBILITY IDEOGRAPH - 0xEDBD: 0x6673, //CJK UNIFIED IDEOGRAPH - 0xEDBE: 0x6699, //CJK UNIFIED IDEOGRAPH - 0xEDBF: 0x66A0, //CJK UNIFIED IDEOGRAPH - 0xEDC0: 0x66B2, //CJK UNIFIED IDEOGRAPH - 0xEDC1: 0x66BF, //CJK UNIFIED IDEOGRAPH - 0xEDC2: 0x66FA, //CJK UNIFIED IDEOGRAPH - 0xEDC3: 0x670E, //CJK UNIFIED IDEOGRAPH - 0xEDC4: 0xF929, //CJK COMPATIBILITY IDEOGRAPH - 0xEDC5: 0x6766, //CJK UNIFIED IDEOGRAPH - 0xEDC6: 0x67BB, //CJK UNIFIED IDEOGRAPH - 0xEDC7: 0x6852, //CJK UNIFIED IDEOGRAPH - 0xEDC8: 0x67C0, //CJK UNIFIED IDEOGRAPH - 0xEDC9: 0x6801, //CJK UNIFIED IDEOGRAPH - 0xEDCA: 0x6844, //CJK UNIFIED IDEOGRAPH - 0xEDCB: 0x68CF, //CJK UNIFIED IDEOGRAPH - 0xEDCC: 0xFA13, //CJK COMPATIBILITY IDEOGRAPH - 0xEDCD: 0x6968, //CJK UNIFIED IDEOGRAPH - 0xEDCE: 0xFA14, //CJK COMPATIBILITY IDEOGRAPH - 0xEDCF: 0x6998, //CJK UNIFIED IDEOGRAPH - 0xEDD0: 0x69E2, //CJK UNIFIED IDEOGRAPH - 0xEDD1: 0x6A30, //CJK UNIFIED IDEOGRAPH - 0xEDD2: 0x6A6B, //CJK UNIFIED IDEOGRAPH - 0xEDD3: 0x6A46, //CJK UNIFIED IDEOGRAPH - 0xEDD4: 0x6A73, //CJK UNIFIED IDEOGRAPH - 0xEDD5: 0x6A7E, //CJK UNIFIED IDEOGRAPH - 0xEDD6: 0x6AE2, //CJK UNIFIED IDEOGRAPH - 0xEDD7: 0x6AE4, //CJK UNIFIED IDEOGRAPH - 0xEDD8: 0x6BD6, //CJK UNIFIED IDEOGRAPH - 0xEDD9: 0x6C3F, //CJK UNIFIED IDEOGRAPH - 0xEDDA: 0x6C5C, //CJK UNIFIED IDEOGRAPH - 0xEDDB: 0x6C86, //CJK UNIFIED IDEOGRAPH - 0xEDDC: 0x6C6F, //CJK UNIFIED IDEOGRAPH - 0xEDDD: 0x6CDA, //CJK UNIFIED IDEOGRAPH - 0xEDDE: 0x6D04, //CJK UNIFIED IDEOGRAPH - 0xEDDF: 0x6D87, //CJK UNIFIED IDEOGRAPH - 0xEDE0: 0x6D6F, //CJK UNIFIED IDEOGRAPH - 0xEDE1: 0x6D96, //CJK UNIFIED IDEOGRAPH - 0xEDE2: 0x6DAC, //CJK UNIFIED IDEOGRAPH - 0xEDE3: 0x6DCF, //CJK UNIFIED IDEOGRAPH - 0xEDE4: 0x6DF8, //CJK UNIFIED IDEOGRAPH - 0xEDE5: 0x6DF2, //CJK UNIFIED IDEOGRAPH - 0xEDE6: 0x6DFC, //CJK UNIFIED IDEOGRAPH - 0xEDE7: 0x6E39, //CJK UNIFIED IDEOGRAPH - 0xEDE8: 0x6E5C, //CJK UNIFIED IDEOGRAPH - 0xEDE9: 0x6E27, //CJK UNIFIED IDEOGRAPH - 0xEDEA: 0x6E3C, //CJK UNIFIED IDEOGRAPH - 0xEDEB: 0x6EBF, //CJK UNIFIED IDEOGRAPH - 0xEDEC: 0x6F88, //CJK UNIFIED IDEOGRAPH - 0xEDED: 0x6FB5, //CJK UNIFIED IDEOGRAPH - 0xEDEE: 0x6FF5, //CJK UNIFIED IDEOGRAPH - 0xEDEF: 0x7005, //CJK UNIFIED IDEOGRAPH - 0xEDF0: 0x7007, //CJK UNIFIED IDEOGRAPH - 0xEDF1: 0x7028, //CJK UNIFIED IDEOGRAPH - 0xEDF2: 0x7085, //CJK UNIFIED IDEOGRAPH - 0xEDF3: 0x70AB, //CJK UNIFIED IDEOGRAPH - 0xEDF4: 0x710F, //CJK UNIFIED IDEOGRAPH - 0xEDF5: 0x7104, //CJK UNIFIED IDEOGRAPH - 0xEDF6: 0x715C, //CJK UNIFIED IDEOGRAPH - 0xEDF7: 0x7146, //CJK UNIFIED IDEOGRAPH - 0xEDF8: 0x7147, //CJK UNIFIED IDEOGRAPH - 0xEDF9: 0xFA15, //CJK COMPATIBILITY IDEOGRAPH - 0xEDFA: 0x71C1, //CJK UNIFIED IDEOGRAPH - 0xEDFB: 0x71FE, //CJK UNIFIED IDEOGRAPH - 0xEDFC: 0x72B1, //CJK UNIFIED IDEOGRAPH - 0xEE40: 0x72BE, //CJK UNIFIED IDEOGRAPH - 0xEE41: 0x7324, //CJK UNIFIED IDEOGRAPH - 0xEE42: 0xFA16, //CJK COMPATIBILITY IDEOGRAPH - 0xEE43: 0x7377, //CJK UNIFIED IDEOGRAPH - 0xEE44: 0x73BD, //CJK UNIFIED IDEOGRAPH - 0xEE45: 0x73C9, //CJK UNIFIED IDEOGRAPH - 0xEE46: 0x73D6, //CJK UNIFIED IDEOGRAPH - 0xEE47: 0x73E3, //CJK UNIFIED IDEOGRAPH - 0xEE48: 0x73D2, //CJK UNIFIED IDEOGRAPH - 0xEE49: 0x7407, //CJK UNIFIED IDEOGRAPH - 0xEE4A: 0x73F5, //CJK UNIFIED IDEOGRAPH - 0xEE4B: 0x7426, //CJK UNIFIED IDEOGRAPH - 0xEE4C: 0x742A, //CJK UNIFIED IDEOGRAPH - 0xEE4D: 0x7429, //CJK UNIFIED IDEOGRAPH - 0xEE4E: 0x742E, //CJK UNIFIED IDEOGRAPH - 0xEE4F: 0x7462, //CJK UNIFIED IDEOGRAPH - 0xEE50: 0x7489, //CJK UNIFIED IDEOGRAPH - 0xEE51: 0x749F, //CJK UNIFIED IDEOGRAPH - 0xEE52: 0x7501, //CJK UNIFIED IDEOGRAPH - 0xEE53: 0x756F, //CJK UNIFIED IDEOGRAPH - 0xEE54: 0x7682, //CJK UNIFIED IDEOGRAPH - 0xEE55: 0x769C, //CJK UNIFIED IDEOGRAPH - 0xEE56: 0x769E, //CJK UNIFIED IDEOGRAPH - 0xEE57: 0x769B, //CJK UNIFIED IDEOGRAPH - 0xEE58: 0x76A6, //CJK UNIFIED IDEOGRAPH - 0xEE59: 0xFA17, //CJK COMPATIBILITY IDEOGRAPH - 0xEE5A: 0x7746, //CJK UNIFIED IDEOGRAPH - 0xEE5B: 0x52AF, //CJK UNIFIED IDEOGRAPH - 0xEE5C: 0x7821, //CJK UNIFIED IDEOGRAPH - 0xEE5D: 0x784E, //CJK UNIFIED IDEOGRAPH - 0xEE5E: 0x7864, //CJK UNIFIED IDEOGRAPH - 0xEE5F: 0x787A, //CJK UNIFIED IDEOGRAPH - 0xEE60: 0x7930, //CJK UNIFIED IDEOGRAPH - 0xEE61: 0xFA18, //CJK COMPATIBILITY IDEOGRAPH - 0xEE62: 0xFA19, //CJK COMPATIBILITY IDEOGRAPH - 0xEE63: 0xFA1A, //CJK COMPATIBILITY IDEOGRAPH - 0xEE64: 0x7994, //CJK UNIFIED IDEOGRAPH - 0xEE65: 0xFA1B, //CJK COMPATIBILITY IDEOGRAPH - 0xEE66: 0x799B, //CJK UNIFIED IDEOGRAPH - 0xEE67: 0x7AD1, //CJK UNIFIED IDEOGRAPH - 0xEE68: 0x7AE7, //CJK UNIFIED IDEOGRAPH - 0xEE69: 0xFA1C, //CJK COMPATIBILITY IDEOGRAPH - 0xEE6A: 0x7AEB, //CJK UNIFIED IDEOGRAPH - 0xEE6B: 0x7B9E, //CJK UNIFIED IDEOGRAPH - 0xEE6C: 0xFA1D, //CJK COMPATIBILITY IDEOGRAPH - 0xEE6D: 0x7D48, //CJK UNIFIED IDEOGRAPH - 0xEE6E: 0x7D5C, //CJK UNIFIED IDEOGRAPH - 0xEE6F: 0x7DB7, //CJK UNIFIED IDEOGRAPH - 0xEE70: 0x7DA0, //CJK UNIFIED IDEOGRAPH - 0xEE71: 0x7DD6, //CJK UNIFIED IDEOGRAPH - 0xEE72: 0x7E52, //CJK UNIFIED IDEOGRAPH - 0xEE73: 0x7F47, //CJK UNIFIED IDEOGRAPH - 0xEE74: 0x7FA1, //CJK UNIFIED IDEOGRAPH - 0xEE75: 0xFA1E, //CJK COMPATIBILITY IDEOGRAPH - 0xEE76: 0x8301, //CJK UNIFIED IDEOGRAPH - 0xEE77: 0x8362, //CJK UNIFIED IDEOGRAPH - 0xEE78: 0x837F, //CJK UNIFIED IDEOGRAPH - 0xEE79: 0x83C7, //CJK UNIFIED IDEOGRAPH - 0xEE7A: 0x83F6, //CJK UNIFIED IDEOGRAPH - 0xEE7B: 0x8448, //CJK UNIFIED IDEOGRAPH - 0xEE7C: 0x84B4, //CJK UNIFIED IDEOGRAPH - 0xEE7D: 0x8553, //CJK UNIFIED IDEOGRAPH - 0xEE7E: 0x8559, //CJK UNIFIED IDEOGRAPH - 0xEE80: 0x856B, //CJK UNIFIED IDEOGRAPH - 0xEE81: 0xFA1F, //CJK COMPATIBILITY IDEOGRAPH - 0xEE82: 0x85B0, //CJK UNIFIED IDEOGRAPH - 0xEE83: 0xFA20, //CJK COMPATIBILITY IDEOGRAPH - 0xEE84: 0xFA21, //CJK COMPATIBILITY IDEOGRAPH - 0xEE85: 0x8807, //CJK UNIFIED IDEOGRAPH - 0xEE86: 0x88F5, //CJK UNIFIED IDEOGRAPH - 0xEE87: 0x8A12, //CJK UNIFIED IDEOGRAPH - 0xEE88: 0x8A37, //CJK UNIFIED IDEOGRAPH - 0xEE89: 0x8A79, //CJK UNIFIED IDEOGRAPH - 0xEE8A: 0x8AA7, //CJK UNIFIED IDEOGRAPH - 0xEE8B: 0x8ABE, //CJK UNIFIED IDEOGRAPH - 0xEE8C: 0x8ADF, //CJK UNIFIED IDEOGRAPH - 0xEE8D: 0xFA22, //CJK COMPATIBILITY IDEOGRAPH - 0xEE8E: 0x8AF6, //CJK UNIFIED IDEOGRAPH - 0xEE8F: 0x8B53, //CJK UNIFIED IDEOGRAPH - 0xEE90: 0x8B7F, //CJK UNIFIED IDEOGRAPH - 0xEE91: 0x8CF0, //CJK UNIFIED IDEOGRAPH - 0xEE92: 0x8CF4, //CJK UNIFIED IDEOGRAPH - 0xEE93: 0x8D12, //CJK UNIFIED IDEOGRAPH - 0xEE94: 0x8D76, //CJK UNIFIED IDEOGRAPH - 0xEE95: 0xFA23, //CJK COMPATIBILITY IDEOGRAPH - 0xEE96: 0x8ECF, //CJK UNIFIED IDEOGRAPH - 0xEE97: 0xFA24, //CJK COMPATIBILITY IDEOGRAPH - 0xEE98: 0xFA25, //CJK COMPATIBILITY IDEOGRAPH - 0xEE99: 0x9067, //CJK UNIFIED IDEOGRAPH - 0xEE9A: 0x90DE, //CJK UNIFIED IDEOGRAPH - 0xEE9B: 0xFA26, //CJK COMPATIBILITY IDEOGRAPH - 0xEE9C: 0x9115, //CJK UNIFIED IDEOGRAPH - 0xEE9D: 0x9127, //CJK UNIFIED IDEOGRAPH - 0xEE9E: 0x91DA, //CJK UNIFIED IDEOGRAPH - 0xEE9F: 0x91D7, //CJK UNIFIED IDEOGRAPH - 0xEEA0: 0x91DE, //CJK UNIFIED IDEOGRAPH - 0xEEA1: 0x91ED, //CJK UNIFIED IDEOGRAPH - 0xEEA2: 0x91EE, //CJK UNIFIED IDEOGRAPH - 0xEEA3: 0x91E4, //CJK UNIFIED IDEOGRAPH - 0xEEA4: 0x91E5, //CJK UNIFIED IDEOGRAPH - 0xEEA5: 0x9206, //CJK UNIFIED IDEOGRAPH - 0xEEA6: 0x9210, //CJK UNIFIED IDEOGRAPH - 0xEEA7: 0x920A, //CJK UNIFIED IDEOGRAPH - 0xEEA8: 0x923A, //CJK UNIFIED IDEOGRAPH - 0xEEA9: 0x9240, //CJK UNIFIED IDEOGRAPH - 0xEEAA: 0x923C, //CJK UNIFIED IDEOGRAPH - 0xEEAB: 0x924E, //CJK UNIFIED IDEOGRAPH - 0xEEAC: 0x9259, //CJK UNIFIED IDEOGRAPH - 0xEEAD: 0x9251, //CJK UNIFIED IDEOGRAPH - 0xEEAE: 0x9239, //CJK UNIFIED IDEOGRAPH - 0xEEAF: 0x9267, //CJK UNIFIED IDEOGRAPH - 0xEEB0: 0x92A7, //CJK UNIFIED IDEOGRAPH - 0xEEB1: 0x9277, //CJK UNIFIED IDEOGRAPH - 0xEEB2: 0x9278, //CJK UNIFIED IDEOGRAPH - 0xEEB3: 0x92E7, //CJK UNIFIED IDEOGRAPH - 0xEEB4: 0x92D7, //CJK UNIFIED IDEOGRAPH - 0xEEB5: 0x92D9, //CJK UNIFIED IDEOGRAPH - 0xEEB6: 0x92D0, //CJK UNIFIED IDEOGRAPH - 0xEEB7: 0xFA27, //CJK COMPATIBILITY IDEOGRAPH - 0xEEB8: 0x92D5, //CJK UNIFIED IDEOGRAPH - 0xEEB9: 0x92E0, //CJK UNIFIED IDEOGRAPH - 0xEEBA: 0x92D3, //CJK UNIFIED IDEOGRAPH - 0xEEBB: 0x9325, //CJK UNIFIED IDEOGRAPH - 0xEEBC: 0x9321, //CJK UNIFIED IDEOGRAPH - 0xEEBD: 0x92FB, //CJK UNIFIED IDEOGRAPH - 0xEEBE: 0xFA28, //CJK COMPATIBILITY IDEOGRAPH - 0xEEBF: 0x931E, //CJK UNIFIED IDEOGRAPH - 0xEEC0: 0x92FF, //CJK UNIFIED IDEOGRAPH - 0xEEC1: 0x931D, //CJK UNIFIED IDEOGRAPH - 0xEEC2: 0x9302, //CJK UNIFIED IDEOGRAPH - 0xEEC3: 0x9370, //CJK UNIFIED IDEOGRAPH - 0xEEC4: 0x9357, //CJK UNIFIED IDEOGRAPH - 0xEEC5: 0x93A4, //CJK UNIFIED IDEOGRAPH - 0xEEC6: 0x93C6, //CJK UNIFIED IDEOGRAPH - 0xEEC7: 0x93DE, //CJK UNIFIED IDEOGRAPH - 0xEEC8: 0x93F8, //CJK UNIFIED IDEOGRAPH - 0xEEC9: 0x9431, //CJK UNIFIED IDEOGRAPH - 0xEECA: 0x9445, //CJK UNIFIED IDEOGRAPH - 0xEECB: 0x9448, //CJK UNIFIED IDEOGRAPH - 0xEECC: 0x9592, //CJK UNIFIED IDEOGRAPH - 0xEECD: 0xF9DC, //CJK COMPATIBILITY IDEOGRAPH - 0xEECE: 0xFA29, //CJK COMPATIBILITY IDEOGRAPH - 0xEECF: 0x969D, //CJK UNIFIED IDEOGRAPH - 0xEED0: 0x96AF, //CJK UNIFIED IDEOGRAPH - 0xEED1: 0x9733, //CJK UNIFIED IDEOGRAPH - 0xEED2: 0x973B, //CJK UNIFIED IDEOGRAPH - 0xEED3: 0x9743, //CJK UNIFIED IDEOGRAPH - 0xEED4: 0x974D, //CJK UNIFIED IDEOGRAPH - 0xEED5: 0x974F, //CJK UNIFIED IDEOGRAPH - 0xEED6: 0x9751, //CJK UNIFIED IDEOGRAPH - 0xEED7: 0x9755, //CJK UNIFIED IDEOGRAPH - 0xEED8: 0x9857, //CJK UNIFIED IDEOGRAPH - 0xEED9: 0x9865, //CJK UNIFIED IDEOGRAPH - 0xEEDA: 0xFA2A, //CJK COMPATIBILITY IDEOGRAPH - 0xEEDB: 0xFA2B, //CJK COMPATIBILITY IDEOGRAPH - 0xEEDC: 0x9927, //CJK UNIFIED IDEOGRAPH - 0xEEDD: 0xFA2C, //CJK COMPATIBILITY IDEOGRAPH - 0xEEDE: 0x999E, //CJK UNIFIED IDEOGRAPH - 0xEEDF: 0x9A4E, //CJK UNIFIED IDEOGRAPH - 0xEEE0: 0x9AD9, //CJK UNIFIED IDEOGRAPH - 0xEEE1: 0x9ADC, //CJK UNIFIED IDEOGRAPH - 0xEEE2: 0x9B75, //CJK UNIFIED IDEOGRAPH - 0xEEE3: 0x9B72, //CJK UNIFIED IDEOGRAPH - 0xEEE4: 0x9B8F, //CJK UNIFIED IDEOGRAPH - 0xEEE5: 0x9BB1, //CJK UNIFIED IDEOGRAPH - 0xEEE6: 0x9BBB, //CJK UNIFIED IDEOGRAPH - 0xEEE7: 0x9C00, //CJK UNIFIED IDEOGRAPH - 0xEEE8: 0x9D70, //CJK UNIFIED IDEOGRAPH - 0xEEE9: 0x9D6B, //CJK UNIFIED IDEOGRAPH - 0xEEEA: 0xFA2D, //CJK COMPATIBILITY IDEOGRAPH - 0xEEEB: 0x9E19, //CJK UNIFIED IDEOGRAPH - 0xEEEC: 0x9ED1, //CJK UNIFIED IDEOGRAPH - 0xEEEF: 0x2170, //SMALL ROMAN NUMERAL ONE - 0xEEF0: 0x2171, //SMALL ROMAN NUMERAL TWO - 0xEEF1: 0x2172, //SMALL ROMAN NUMERAL THREE - 0xEEF2: 0x2173, //SMALL ROMAN NUMERAL FOUR - 0xEEF3: 0x2174, //SMALL ROMAN NUMERAL FIVE - 0xEEF4: 0x2175, //SMALL ROMAN NUMERAL SIX - 0xEEF5: 0x2176, //SMALL ROMAN NUMERAL SEVEN - 0xEEF6: 0x2177, //SMALL ROMAN NUMERAL EIGHT - 0xEEF7: 0x2178, //SMALL ROMAN NUMERAL NINE - 0xEEF8: 0x2179, //SMALL ROMAN NUMERAL TEN - 0xEEF9: 0xFFE2, //FULLWIDTH NOT SIGN - 0xEEFA: 0xFFE4, //FULLWIDTH BROKEN BAR - 0xEEFB: 0xFF07, //FULLWIDTH APOSTROPHE - 0xEEFC: 0xFF02, //FULLWIDTH QUOTATION MARK - 0xFA40: 0x2170, //SMALL ROMAN NUMERAL ONE - 0xFA41: 0x2171, //SMALL ROMAN NUMERAL TWO - 0xFA42: 0x2172, //SMALL ROMAN NUMERAL THREE - 0xFA43: 0x2173, //SMALL ROMAN NUMERAL FOUR - 0xFA44: 0x2174, //SMALL ROMAN NUMERAL FIVE - 0xFA45: 0x2175, //SMALL ROMAN NUMERAL SIX - 0xFA46: 0x2176, //SMALL ROMAN NUMERAL SEVEN - 0xFA47: 0x2177, //SMALL ROMAN NUMERAL EIGHT - 0xFA48: 0x2178, //SMALL ROMAN NUMERAL NINE - 0xFA49: 0x2179, //SMALL ROMAN NUMERAL TEN - 0xFA4A: 0x2160, //ROMAN NUMERAL ONE - 0xFA4B: 0x2161, //ROMAN NUMERAL TWO - 0xFA4C: 0x2162, //ROMAN NUMERAL THREE - 0xFA4D: 0x2163, //ROMAN NUMERAL FOUR - 0xFA4E: 0x2164, //ROMAN NUMERAL FIVE - 0xFA4F: 0x2165, //ROMAN NUMERAL SIX - 0xFA50: 0x2166, //ROMAN NUMERAL SEVEN - 0xFA51: 0x2167, //ROMAN NUMERAL EIGHT - 0xFA52: 0x2168, //ROMAN NUMERAL NINE - 0xFA53: 0x2169, //ROMAN NUMERAL TEN - 0xFA54: 0xFFE2, //FULLWIDTH NOT SIGN - 0xFA55: 0xFFE4, //FULLWIDTH BROKEN BAR - 0xFA56: 0xFF07, //FULLWIDTH APOSTROPHE - 0xFA57: 0xFF02, //FULLWIDTH QUOTATION MARK - 0xFA58: 0x3231, //PARENTHESIZED IDEOGRAPH STOCK - 0xFA59: 0x2116, //NUMERO SIGN - 0xFA5A: 0x2121, //TELEPHONE SIGN - 0xFA5B: 0x2235, //BECAUSE - 0xFA5C: 0x7E8A, //CJK UNIFIED IDEOGRAPH - 0xFA5D: 0x891C, //CJK UNIFIED IDEOGRAPH - 0xFA5E: 0x9348, //CJK UNIFIED IDEOGRAPH - 0xFA5F: 0x9288, //CJK UNIFIED IDEOGRAPH - 0xFA60: 0x84DC, //CJK UNIFIED IDEOGRAPH - 0xFA61: 0x4FC9, //CJK UNIFIED IDEOGRAPH - 0xFA62: 0x70BB, //CJK UNIFIED IDEOGRAPH - 0xFA63: 0x6631, //CJK UNIFIED IDEOGRAPH - 0xFA64: 0x68C8, //CJK UNIFIED IDEOGRAPH - 0xFA65: 0x92F9, //CJK UNIFIED IDEOGRAPH - 0xFA66: 0x66FB, //CJK UNIFIED IDEOGRAPH - 0xFA67: 0x5F45, //CJK UNIFIED IDEOGRAPH - 0xFA68: 0x4E28, //CJK UNIFIED IDEOGRAPH - 0xFA69: 0x4EE1, //CJK UNIFIED IDEOGRAPH - 0xFA6A: 0x4EFC, //CJK UNIFIED IDEOGRAPH - 0xFA6B: 0x4F00, //CJK UNIFIED IDEOGRAPH - 0xFA6C: 0x4F03, //CJK UNIFIED IDEOGRAPH - 0xFA6D: 0x4F39, //CJK UNIFIED IDEOGRAPH - 0xFA6E: 0x4F56, //CJK UNIFIED IDEOGRAPH - 0xFA6F: 0x4F92, //CJK UNIFIED IDEOGRAPH - 0xFA70: 0x4F8A, //CJK UNIFIED IDEOGRAPH - 0xFA71: 0x4F9A, //CJK UNIFIED IDEOGRAPH - 0xFA72: 0x4F94, //CJK UNIFIED IDEOGRAPH - 0xFA73: 0x4FCD, //CJK UNIFIED IDEOGRAPH - 0xFA74: 0x5040, //CJK UNIFIED IDEOGRAPH - 0xFA75: 0x5022, //CJK UNIFIED IDEOGRAPH - 0xFA76: 0x4FFF, //CJK UNIFIED IDEOGRAPH - 0xFA77: 0x501E, //CJK UNIFIED IDEOGRAPH - 0xFA78: 0x5046, //CJK UNIFIED IDEOGRAPH - 0xFA79: 0x5070, //CJK UNIFIED IDEOGRAPH - 0xFA7A: 0x5042, //CJK UNIFIED IDEOGRAPH - 0xFA7B: 0x5094, //CJK UNIFIED IDEOGRAPH - 0xFA7C: 0x50F4, //CJK UNIFIED IDEOGRAPH - 0xFA7D: 0x50D8, //CJK UNIFIED IDEOGRAPH - 0xFA7E: 0x514A, //CJK UNIFIED IDEOGRAPH - 0xFA80: 0x5164, //CJK UNIFIED IDEOGRAPH - 0xFA81: 0x519D, //CJK UNIFIED IDEOGRAPH - 0xFA82: 0x51BE, //CJK UNIFIED IDEOGRAPH - 0xFA83: 0x51EC, //CJK UNIFIED IDEOGRAPH - 0xFA84: 0x5215, //CJK UNIFIED IDEOGRAPH - 0xFA85: 0x529C, //CJK UNIFIED IDEOGRAPH - 0xFA86: 0x52A6, //CJK UNIFIED IDEOGRAPH - 0xFA87: 0x52C0, //CJK UNIFIED IDEOGRAPH - 0xFA88: 0x52DB, //CJK UNIFIED IDEOGRAPH - 0xFA89: 0x5300, //CJK UNIFIED IDEOGRAPH - 0xFA8A: 0x5307, //CJK UNIFIED IDEOGRAPH - 0xFA8B: 0x5324, //CJK UNIFIED IDEOGRAPH - 0xFA8C: 0x5372, //CJK UNIFIED IDEOGRAPH - 0xFA8D: 0x5393, //CJK UNIFIED IDEOGRAPH - 0xFA8E: 0x53B2, //CJK UNIFIED IDEOGRAPH - 0xFA8F: 0x53DD, //CJK UNIFIED IDEOGRAPH - 0xFA90: 0xFA0E, //CJK COMPATIBILITY IDEOGRAPH - 0xFA91: 0x549C, //CJK UNIFIED IDEOGRAPH - 0xFA92: 0x548A, //CJK UNIFIED IDEOGRAPH - 0xFA93: 0x54A9, //CJK UNIFIED IDEOGRAPH - 0xFA94: 0x54FF, //CJK UNIFIED IDEOGRAPH - 0xFA95: 0x5586, //CJK UNIFIED IDEOGRAPH - 0xFA96: 0x5759, //CJK UNIFIED IDEOGRAPH - 0xFA97: 0x5765, //CJK UNIFIED IDEOGRAPH - 0xFA98: 0x57AC, //CJK UNIFIED IDEOGRAPH - 0xFA99: 0x57C8, //CJK UNIFIED IDEOGRAPH - 0xFA9A: 0x57C7, //CJK UNIFIED IDEOGRAPH - 0xFA9B: 0xFA0F, //CJK COMPATIBILITY IDEOGRAPH - 0xFA9C: 0xFA10, //CJK COMPATIBILITY IDEOGRAPH - 0xFA9D: 0x589E, //CJK UNIFIED IDEOGRAPH - 0xFA9E: 0x58B2, //CJK UNIFIED IDEOGRAPH - 0xFA9F: 0x590B, //CJK UNIFIED IDEOGRAPH - 0xFAA0: 0x5953, //CJK UNIFIED IDEOGRAPH - 0xFAA1: 0x595B, //CJK UNIFIED IDEOGRAPH - 0xFAA2: 0x595D, //CJK UNIFIED IDEOGRAPH - 0xFAA3: 0x5963, //CJK UNIFIED IDEOGRAPH - 0xFAA4: 0x59A4, //CJK UNIFIED IDEOGRAPH - 0xFAA5: 0x59BA, //CJK UNIFIED IDEOGRAPH - 0xFAA6: 0x5B56, //CJK UNIFIED IDEOGRAPH - 0xFAA7: 0x5BC0, //CJK UNIFIED IDEOGRAPH - 0xFAA8: 0x752F, //CJK UNIFIED IDEOGRAPH - 0xFAA9: 0x5BD8, //CJK UNIFIED IDEOGRAPH - 0xFAAA: 0x5BEC, //CJK UNIFIED IDEOGRAPH - 0xFAAB: 0x5C1E, //CJK UNIFIED IDEOGRAPH - 0xFAAC: 0x5CA6, //CJK UNIFIED IDEOGRAPH - 0xFAAD: 0x5CBA, //CJK UNIFIED IDEOGRAPH - 0xFAAE: 0x5CF5, //CJK UNIFIED IDEOGRAPH - 0xFAAF: 0x5D27, //CJK UNIFIED IDEOGRAPH - 0xFAB0: 0x5D53, //CJK UNIFIED IDEOGRAPH - 0xFAB1: 0xFA11, //CJK COMPATIBILITY IDEOGRAPH - 0xFAB2: 0x5D42, //CJK UNIFIED IDEOGRAPH - 0xFAB3: 0x5D6D, //CJK UNIFIED IDEOGRAPH - 0xFAB4: 0x5DB8, //CJK UNIFIED IDEOGRAPH - 0xFAB5: 0x5DB9, //CJK UNIFIED IDEOGRAPH - 0xFAB6: 0x5DD0, //CJK UNIFIED IDEOGRAPH - 0xFAB7: 0x5F21, //CJK UNIFIED IDEOGRAPH - 0xFAB8: 0x5F34, //CJK UNIFIED IDEOGRAPH - 0xFAB9: 0x5F67, //CJK UNIFIED IDEOGRAPH - 0xFABA: 0x5FB7, //CJK UNIFIED IDEOGRAPH - 0xFABB: 0x5FDE, //CJK UNIFIED IDEOGRAPH - 0xFABC: 0x605D, //CJK UNIFIED IDEOGRAPH - 0xFABD: 0x6085, //CJK UNIFIED IDEOGRAPH - 0xFABE: 0x608A, //CJK UNIFIED IDEOGRAPH - 0xFABF: 0x60DE, //CJK UNIFIED IDEOGRAPH - 0xFAC0: 0x60D5, //CJK UNIFIED IDEOGRAPH - 0xFAC1: 0x6120, //CJK UNIFIED IDEOGRAPH - 0xFAC2: 0x60F2, //CJK UNIFIED IDEOGRAPH - 0xFAC3: 0x6111, //CJK UNIFIED IDEOGRAPH - 0xFAC4: 0x6137, //CJK UNIFIED IDEOGRAPH - 0xFAC5: 0x6130, //CJK UNIFIED IDEOGRAPH - 0xFAC6: 0x6198, //CJK UNIFIED IDEOGRAPH - 0xFAC7: 0x6213, //CJK UNIFIED IDEOGRAPH - 0xFAC8: 0x62A6, //CJK UNIFIED IDEOGRAPH - 0xFAC9: 0x63F5, //CJK UNIFIED IDEOGRAPH - 0xFACA: 0x6460, //CJK UNIFIED IDEOGRAPH - 0xFACB: 0x649D, //CJK UNIFIED IDEOGRAPH - 0xFACC: 0x64CE, //CJK UNIFIED IDEOGRAPH - 0xFACD: 0x654E, //CJK UNIFIED IDEOGRAPH - 0xFACE: 0x6600, //CJK UNIFIED IDEOGRAPH - 0xFACF: 0x6615, //CJK UNIFIED IDEOGRAPH - 0xFAD0: 0x663B, //CJK UNIFIED IDEOGRAPH - 0xFAD1: 0x6609, //CJK UNIFIED IDEOGRAPH - 0xFAD2: 0x662E, //CJK UNIFIED IDEOGRAPH - 0xFAD3: 0x661E, //CJK UNIFIED IDEOGRAPH - 0xFAD4: 0x6624, //CJK UNIFIED IDEOGRAPH - 0xFAD5: 0x6665, //CJK UNIFIED IDEOGRAPH - 0xFAD6: 0x6657, //CJK UNIFIED IDEOGRAPH - 0xFAD7: 0x6659, //CJK UNIFIED IDEOGRAPH - 0xFAD8: 0xFA12, //CJK COMPATIBILITY IDEOGRAPH - 0xFAD9: 0x6673, //CJK UNIFIED IDEOGRAPH - 0xFADA: 0x6699, //CJK UNIFIED IDEOGRAPH - 0xFADB: 0x66A0, //CJK UNIFIED IDEOGRAPH - 0xFADC: 0x66B2, //CJK UNIFIED IDEOGRAPH - 0xFADD: 0x66BF, //CJK UNIFIED IDEOGRAPH - 0xFADE: 0x66FA, //CJK UNIFIED IDEOGRAPH - 0xFADF: 0x670E, //CJK UNIFIED IDEOGRAPH - 0xFAE0: 0xF929, //CJK COMPATIBILITY IDEOGRAPH - 0xFAE1: 0x6766, //CJK UNIFIED IDEOGRAPH - 0xFAE2: 0x67BB, //CJK UNIFIED IDEOGRAPH - 0xFAE3: 0x6852, //CJK UNIFIED IDEOGRAPH - 0xFAE4: 0x67C0, //CJK UNIFIED IDEOGRAPH - 0xFAE5: 0x6801, //CJK UNIFIED IDEOGRAPH - 0xFAE6: 0x6844, //CJK UNIFIED IDEOGRAPH - 0xFAE7: 0x68CF, //CJK UNIFIED IDEOGRAPH - 0xFAE8: 0xFA13, //CJK COMPATIBILITY IDEOGRAPH - 0xFAE9: 0x6968, //CJK UNIFIED IDEOGRAPH - 0xFAEA: 0xFA14, //CJK COMPATIBILITY IDEOGRAPH - 0xFAEB: 0x6998, //CJK UNIFIED IDEOGRAPH - 0xFAEC: 0x69E2, //CJK UNIFIED IDEOGRAPH - 0xFAED: 0x6A30, //CJK UNIFIED IDEOGRAPH - 0xFAEE: 0x6A6B, //CJK UNIFIED IDEOGRAPH - 0xFAEF: 0x6A46, //CJK UNIFIED IDEOGRAPH - 0xFAF0: 0x6A73, //CJK UNIFIED IDEOGRAPH - 0xFAF1: 0x6A7E, //CJK UNIFIED IDEOGRAPH - 0xFAF2: 0x6AE2, //CJK UNIFIED IDEOGRAPH - 0xFAF3: 0x6AE4, //CJK UNIFIED IDEOGRAPH - 0xFAF4: 0x6BD6, //CJK UNIFIED IDEOGRAPH - 0xFAF5: 0x6C3F, //CJK UNIFIED IDEOGRAPH - 0xFAF6: 0x6C5C, //CJK UNIFIED IDEOGRAPH - 0xFAF7: 0x6C86, //CJK UNIFIED IDEOGRAPH - 0xFAF8: 0x6C6F, //CJK UNIFIED IDEOGRAPH - 0xFAF9: 0x6CDA, //CJK UNIFIED IDEOGRAPH - 0xFAFA: 0x6D04, //CJK UNIFIED IDEOGRAPH - 0xFAFB: 0x6D87, //CJK UNIFIED IDEOGRAPH - 0xFAFC: 0x6D6F, //CJK UNIFIED IDEOGRAPH - 0xFB40: 0x6D96, //CJK UNIFIED IDEOGRAPH - 0xFB41: 0x6DAC, //CJK UNIFIED IDEOGRAPH - 0xFB42: 0x6DCF, //CJK UNIFIED IDEOGRAPH - 0xFB43: 0x6DF8, //CJK UNIFIED IDEOGRAPH - 0xFB44: 0x6DF2, //CJK UNIFIED IDEOGRAPH - 0xFB45: 0x6DFC, //CJK UNIFIED IDEOGRAPH - 0xFB46: 0x6E39, //CJK UNIFIED IDEOGRAPH - 0xFB47: 0x6E5C, //CJK UNIFIED IDEOGRAPH - 0xFB48: 0x6E27, //CJK UNIFIED IDEOGRAPH - 0xFB49: 0x6E3C, //CJK UNIFIED IDEOGRAPH - 0xFB4A: 0x6EBF, //CJK UNIFIED IDEOGRAPH - 0xFB4B: 0x6F88, //CJK UNIFIED IDEOGRAPH - 0xFB4C: 0x6FB5, //CJK UNIFIED IDEOGRAPH - 0xFB4D: 0x6FF5, //CJK UNIFIED IDEOGRAPH - 0xFB4E: 0x7005, //CJK UNIFIED IDEOGRAPH - 0xFB4F: 0x7007, //CJK UNIFIED IDEOGRAPH - 0xFB50: 0x7028, //CJK UNIFIED IDEOGRAPH - 0xFB51: 0x7085, //CJK UNIFIED IDEOGRAPH - 0xFB52: 0x70AB, //CJK UNIFIED IDEOGRAPH - 0xFB53: 0x710F, //CJK UNIFIED IDEOGRAPH - 0xFB54: 0x7104, //CJK UNIFIED IDEOGRAPH - 0xFB55: 0x715C, //CJK UNIFIED IDEOGRAPH - 0xFB56: 0x7146, //CJK UNIFIED IDEOGRAPH - 0xFB57: 0x7147, //CJK UNIFIED IDEOGRAPH - 0xFB58: 0xFA15, //CJK COMPATIBILITY IDEOGRAPH - 0xFB59: 0x71C1, //CJK UNIFIED IDEOGRAPH - 0xFB5A: 0x71FE, //CJK UNIFIED IDEOGRAPH - 0xFB5B: 0x72B1, //CJK UNIFIED IDEOGRAPH - 0xFB5C: 0x72BE, //CJK UNIFIED IDEOGRAPH - 0xFB5D: 0x7324, //CJK UNIFIED IDEOGRAPH - 0xFB5E: 0xFA16, //CJK COMPATIBILITY IDEOGRAPH - 0xFB5F: 0x7377, //CJK UNIFIED IDEOGRAPH - 0xFB60: 0x73BD, //CJK UNIFIED IDEOGRAPH - 0xFB61: 0x73C9, //CJK UNIFIED IDEOGRAPH - 0xFB62: 0x73D6, //CJK UNIFIED IDEOGRAPH - 0xFB63: 0x73E3, //CJK UNIFIED IDEOGRAPH - 0xFB64: 0x73D2, //CJK UNIFIED IDEOGRAPH - 0xFB65: 0x7407, //CJK UNIFIED IDEOGRAPH - 0xFB66: 0x73F5, //CJK UNIFIED IDEOGRAPH - 0xFB67: 0x7426, //CJK UNIFIED IDEOGRAPH - 0xFB68: 0x742A, //CJK UNIFIED IDEOGRAPH - 0xFB69: 0x7429, //CJK UNIFIED IDEOGRAPH - 0xFB6A: 0x742E, //CJK UNIFIED IDEOGRAPH - 0xFB6B: 0x7462, //CJK UNIFIED IDEOGRAPH - 0xFB6C: 0x7489, //CJK UNIFIED IDEOGRAPH - 0xFB6D: 0x749F, //CJK UNIFIED IDEOGRAPH - 0xFB6E: 0x7501, //CJK UNIFIED IDEOGRAPH - 0xFB6F: 0x756F, //CJK UNIFIED IDEOGRAPH - 0xFB70: 0x7682, //CJK UNIFIED IDEOGRAPH - 0xFB71: 0x769C, //CJK UNIFIED IDEOGRAPH - 0xFB72: 0x769E, //CJK UNIFIED IDEOGRAPH - 0xFB73: 0x769B, //CJK UNIFIED IDEOGRAPH - 0xFB74: 0x76A6, //CJK UNIFIED IDEOGRAPH - 0xFB75: 0xFA17, //CJK COMPATIBILITY IDEOGRAPH - 0xFB76: 0x7746, //CJK UNIFIED IDEOGRAPH - 0xFB77: 0x52AF, //CJK UNIFIED IDEOGRAPH - 0xFB78: 0x7821, //CJK UNIFIED IDEOGRAPH - 0xFB79: 0x784E, //CJK UNIFIED IDEOGRAPH - 0xFB7A: 0x7864, //CJK UNIFIED IDEOGRAPH - 0xFB7B: 0x787A, //CJK UNIFIED IDEOGRAPH - 0xFB7C: 0x7930, //CJK UNIFIED IDEOGRAPH - 0xFB7D: 0xFA18, //CJK COMPATIBILITY IDEOGRAPH - 0xFB7E: 0xFA19, //CJK COMPATIBILITY IDEOGRAPH - 0xFB80: 0xFA1A, //CJK COMPATIBILITY IDEOGRAPH - 0xFB81: 0x7994, //CJK UNIFIED IDEOGRAPH - 0xFB82: 0xFA1B, //CJK COMPATIBILITY IDEOGRAPH - 0xFB83: 0x799B, //CJK UNIFIED IDEOGRAPH - 0xFB84: 0x7AD1, //CJK UNIFIED IDEOGRAPH - 0xFB85: 0x7AE7, //CJK UNIFIED IDEOGRAPH - 0xFB86: 0xFA1C, //CJK COMPATIBILITY IDEOGRAPH - 0xFB87: 0x7AEB, //CJK UNIFIED IDEOGRAPH - 0xFB88: 0x7B9E, //CJK UNIFIED IDEOGRAPH - 0xFB89: 0xFA1D, //CJK COMPATIBILITY IDEOGRAPH - 0xFB8A: 0x7D48, //CJK UNIFIED IDEOGRAPH - 0xFB8B: 0x7D5C, //CJK UNIFIED IDEOGRAPH - 0xFB8C: 0x7DB7, //CJK UNIFIED IDEOGRAPH - 0xFB8D: 0x7DA0, //CJK UNIFIED IDEOGRAPH - 0xFB8E: 0x7DD6, //CJK UNIFIED IDEOGRAPH - 0xFB8F: 0x7E52, //CJK UNIFIED IDEOGRAPH - 0xFB90: 0x7F47, //CJK UNIFIED IDEOGRAPH - 0xFB91: 0x7FA1, //CJK UNIFIED IDEOGRAPH - 0xFB92: 0xFA1E, //CJK COMPATIBILITY IDEOGRAPH - 0xFB93: 0x8301, //CJK UNIFIED IDEOGRAPH - 0xFB94: 0x8362, //CJK UNIFIED IDEOGRAPH - 0xFB95: 0x837F, //CJK UNIFIED IDEOGRAPH - 0xFB96: 0x83C7, //CJK UNIFIED IDEOGRAPH - 0xFB97: 0x83F6, //CJK UNIFIED IDEOGRAPH - 0xFB98: 0x8448, //CJK UNIFIED IDEOGRAPH - 0xFB99: 0x84B4, //CJK UNIFIED IDEOGRAPH - 0xFB9A: 0x8553, //CJK UNIFIED IDEOGRAPH - 0xFB9B: 0x8559, //CJK UNIFIED IDEOGRAPH - 0xFB9C: 0x856B, //CJK UNIFIED IDEOGRAPH - 0xFB9D: 0xFA1F, //CJK COMPATIBILITY IDEOGRAPH - 0xFB9E: 0x85B0, //CJK UNIFIED IDEOGRAPH - 0xFB9F: 0xFA20, //CJK COMPATIBILITY IDEOGRAPH - 0xFBA0: 0xFA21, //CJK COMPATIBILITY IDEOGRAPH - 0xFBA1: 0x8807, //CJK UNIFIED IDEOGRAPH - 0xFBA2: 0x88F5, //CJK UNIFIED IDEOGRAPH - 0xFBA3: 0x8A12, //CJK UNIFIED IDEOGRAPH - 0xFBA4: 0x8A37, //CJK UNIFIED IDEOGRAPH - 0xFBA5: 0x8A79, //CJK UNIFIED IDEOGRAPH - 0xFBA6: 0x8AA7, //CJK UNIFIED IDEOGRAPH - 0xFBA7: 0x8ABE, //CJK UNIFIED IDEOGRAPH - 0xFBA8: 0x8ADF, //CJK UNIFIED IDEOGRAPH - 0xFBA9: 0xFA22, //CJK COMPATIBILITY IDEOGRAPH - 0xFBAA: 0x8AF6, //CJK UNIFIED IDEOGRAPH - 0xFBAB: 0x8B53, //CJK UNIFIED IDEOGRAPH - 0xFBAC: 0x8B7F, //CJK UNIFIED IDEOGRAPH - 0xFBAD: 0x8CF0, //CJK UNIFIED IDEOGRAPH - 0xFBAE: 0x8CF4, //CJK UNIFIED IDEOGRAPH - 0xFBAF: 0x8D12, //CJK UNIFIED IDEOGRAPH - 0xFBB0: 0x8D76, //CJK UNIFIED IDEOGRAPH - 0xFBB1: 0xFA23, //CJK COMPATIBILITY IDEOGRAPH - 0xFBB2: 0x8ECF, //CJK UNIFIED IDEOGRAPH - 0xFBB3: 0xFA24, //CJK COMPATIBILITY IDEOGRAPH - 0xFBB4: 0xFA25, //CJK COMPATIBILITY IDEOGRAPH - 0xFBB5: 0x9067, //CJK UNIFIED IDEOGRAPH - 0xFBB6: 0x90DE, //CJK UNIFIED IDEOGRAPH - 0xFBB7: 0xFA26, //CJK COMPATIBILITY IDEOGRAPH - 0xFBB8: 0x9115, //CJK UNIFIED IDEOGRAPH - 0xFBB9: 0x9127, //CJK UNIFIED IDEOGRAPH - 0xFBBA: 0x91DA, //CJK UNIFIED IDEOGRAPH - 0xFBBB: 0x91D7, //CJK UNIFIED IDEOGRAPH - 0xFBBC: 0x91DE, //CJK UNIFIED IDEOGRAPH - 0xFBBD: 0x91ED, //CJK UNIFIED IDEOGRAPH - 0xFBBE: 0x91EE, //CJK UNIFIED IDEOGRAPH - 0xFBBF: 0x91E4, //CJK UNIFIED IDEOGRAPH - 0xFBC0: 0x91E5, //CJK UNIFIED IDEOGRAPH - 0xFBC1: 0x9206, //CJK UNIFIED IDEOGRAPH - 0xFBC2: 0x9210, //CJK UNIFIED IDEOGRAPH - 0xFBC3: 0x920A, //CJK UNIFIED IDEOGRAPH - 0xFBC4: 0x923A, //CJK UNIFIED IDEOGRAPH - 0xFBC5: 0x9240, //CJK UNIFIED IDEOGRAPH - 0xFBC6: 0x923C, //CJK UNIFIED IDEOGRAPH - 0xFBC7: 0x924E, //CJK UNIFIED IDEOGRAPH - 0xFBC8: 0x9259, //CJK UNIFIED IDEOGRAPH - 0xFBC9: 0x9251, //CJK UNIFIED IDEOGRAPH - 0xFBCA: 0x9239, //CJK UNIFIED IDEOGRAPH - 0xFBCB: 0x9267, //CJK UNIFIED IDEOGRAPH - 0xFBCC: 0x92A7, //CJK UNIFIED IDEOGRAPH - 0xFBCD: 0x9277, //CJK UNIFIED IDEOGRAPH - 0xFBCE: 0x9278, //CJK UNIFIED IDEOGRAPH - 0xFBCF: 0x92E7, //CJK UNIFIED IDEOGRAPH - 0xFBD0: 0x92D7, //CJK UNIFIED IDEOGRAPH - 0xFBD1: 0x92D9, //CJK UNIFIED IDEOGRAPH - 0xFBD2: 0x92D0, //CJK UNIFIED IDEOGRAPH - 0xFBD3: 0xFA27, //CJK COMPATIBILITY IDEOGRAPH - 0xFBD4: 0x92D5, //CJK UNIFIED IDEOGRAPH - 0xFBD5: 0x92E0, //CJK UNIFIED IDEOGRAPH - 0xFBD6: 0x92D3, //CJK UNIFIED IDEOGRAPH - 0xFBD7: 0x9325, //CJK UNIFIED IDEOGRAPH - 0xFBD8: 0x9321, //CJK UNIFIED IDEOGRAPH - 0xFBD9: 0x92FB, //CJK UNIFIED IDEOGRAPH - 0xFBDA: 0xFA28, //CJK COMPATIBILITY IDEOGRAPH - 0xFBDB: 0x931E, //CJK UNIFIED IDEOGRAPH - 0xFBDC: 0x92FF, //CJK UNIFIED IDEOGRAPH - 0xFBDD: 0x931D, //CJK UNIFIED IDEOGRAPH - 0xFBDE: 0x9302, //CJK UNIFIED IDEOGRAPH - 0xFBDF: 0x9370, //CJK UNIFIED IDEOGRAPH - 0xFBE0: 0x9357, //CJK UNIFIED IDEOGRAPH - 0xFBE1: 0x93A4, //CJK UNIFIED IDEOGRAPH - 0xFBE2: 0x93C6, //CJK UNIFIED IDEOGRAPH - 0xFBE3: 0x93DE, //CJK UNIFIED IDEOGRAPH - 0xFBE4: 0x93F8, //CJK UNIFIED IDEOGRAPH - 0xFBE5: 0x9431, //CJK UNIFIED IDEOGRAPH - 0xFBE6: 0x9445, //CJK UNIFIED IDEOGRAPH - 0xFBE7: 0x9448, //CJK UNIFIED IDEOGRAPH - 0xFBE8: 0x9592, //CJK UNIFIED IDEOGRAPH - 0xFBE9: 0xF9DC, //CJK COMPATIBILITY IDEOGRAPH - 0xFBEA: 0xFA29, //CJK COMPATIBILITY IDEOGRAPH - 0xFBEB: 0x969D, //CJK UNIFIED IDEOGRAPH - 0xFBEC: 0x96AF, //CJK UNIFIED IDEOGRAPH - 0xFBED: 0x9733, //CJK UNIFIED IDEOGRAPH - 0xFBEE: 0x973B, //CJK UNIFIED IDEOGRAPH - 0xFBEF: 0x9743, //CJK UNIFIED IDEOGRAPH - 0xFBF0: 0x974D, //CJK UNIFIED IDEOGRAPH - 0xFBF1: 0x974F, //CJK UNIFIED IDEOGRAPH - 0xFBF2: 0x9751, //CJK UNIFIED IDEOGRAPH - 0xFBF3: 0x9755, //CJK UNIFIED IDEOGRAPH - 0xFBF4: 0x9857, //CJK UNIFIED IDEOGRAPH - 0xFBF5: 0x9865, //CJK UNIFIED IDEOGRAPH - 0xFBF6: 0xFA2A, //CJK COMPATIBILITY IDEOGRAPH - 0xFBF7: 0xFA2B, //CJK COMPATIBILITY IDEOGRAPH - 0xFBF8: 0x9927, //CJK UNIFIED IDEOGRAPH - 0xFBF9: 0xFA2C, //CJK COMPATIBILITY IDEOGRAPH - 0xFBFA: 0x999E, //CJK UNIFIED IDEOGRAPH - 0xFBFB: 0x9A4E, //CJK UNIFIED IDEOGRAPH - 0xFBFC: 0x9AD9, //CJK UNIFIED IDEOGRAPH - 0xFC40: 0x9ADC, //CJK UNIFIED IDEOGRAPH - 0xFC41: 0x9B75, //CJK UNIFIED IDEOGRAPH - 0xFC42: 0x9B72, //CJK UNIFIED IDEOGRAPH - 0xFC43: 0x9B8F, //CJK UNIFIED IDEOGRAPH - 0xFC44: 0x9BB1, //CJK UNIFIED IDEOGRAPH - 0xFC45: 0x9BBB, //CJK UNIFIED IDEOGRAPH - 0xFC46: 0x9C00, //CJK UNIFIED IDEOGRAPH - 0xFC47: 0x9D70, //CJK UNIFIED IDEOGRAPH - 0xFC48: 0x9D6B, //CJK UNIFIED IDEOGRAPH - 0xFC49: 0xFA2D, //CJK COMPATIBILITY IDEOGRAPH - 0xFC4A: 0x9E19, //CJK UNIFIED IDEOGRAPH - 0xFC4B: 0x9ED1, //CJK UNIFIED IDEOGRAPH - }, -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/cp936.go b/vendor/github.com/denisenkom/go-mssqldb/cp936.go deleted file mode 100644 index fca5da76d..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/cp936.go +++ /dev/null @@ -1,22055 +0,0 @@ -package mssql - -var cp936 *charsetMap = &charsetMap{ - sb: [256]rune{ - 0x0000, //NULL - 0x0001, //START OF HEADING - 0x0002, //START OF TEXT - 0x0003, //END OF TEXT - 0x0004, //END OF TRANSMISSION - 0x0005, //ENQUIRY - 0x0006, //ACKNOWLEDGE - 0x0007, //BELL - 0x0008, //BACKSPACE - 0x0009, //HORIZONTAL TABULATION - 0x000A, //LINE FEED - 0x000B, //VERTICAL TABULATION - 0x000C, //FORM FEED - 0x000D, //CARRIAGE RETURN - 0x000E, //SHIFT OUT - 0x000F, //SHIFT IN - 0x0010, //DATA LINK ESCAPE - 0x0011, //DEVICE CONTROL ONE - 0x0012, //DEVICE CONTROL TWO - 0x0013, //DEVICE CONTROL THREE - 0x0014, //DEVICE CONTROL FOUR - 0x0015, //NEGATIVE ACKNOWLEDGE - 0x0016, //SYNCHRONOUS IDLE - 0x0017, //END OF TRANSMISSION BLOCK - 0x0018, //CANCEL - 0x0019, //END OF MEDIUM - 0x001A, //SUBSTITUTE - 0x001B, //ESCAPE - 0x001C, //FILE SEPARATOR - 0x001D, //GROUP SEPARATOR - 0x001E, //RECORD SEPARATOR - 0x001F, //UNIT SEPARATOR - 0x0020, //SPACE - 0x0021, //EXCLAMATION MARK - 0x0022, //QUOTATION MARK - 0x0023, //NUMBER SIGN - 0x0024, //DOLLAR SIGN - 0x0025, //PERCENT SIGN - 0x0026, //AMPERSAND - 0x0027, //APOSTROPHE - 0x0028, //LEFT PARENTHESIS - 0x0029, //RIGHT PARENTHESIS - 0x002A, //ASTERISK - 0x002B, //PLUS SIGN - 0x002C, //COMMA - 0x002D, //HYPHEN-MINUS - 0x002E, //FULL STOP - 0x002F, //SOLIDUS - 0x0030, //DIGIT ZERO - 0x0031, //DIGIT ONE - 0x0032, //DIGIT TWO - 0x0033, //DIGIT THREE - 0x0034, //DIGIT FOUR - 0x0035, //DIGIT FIVE - 0x0036, //DIGIT SIX - 0x0037, //DIGIT SEVEN - 0x0038, //DIGIT EIGHT - 0x0039, //DIGIT NINE - 0x003A, //COLON - 0x003B, //SEMICOLON - 0x003C, //LESS-THAN SIGN - 0x003D, //EQUALS SIGN - 0x003E, //GREATER-THAN SIGN - 0x003F, //QUESTION MARK - 0x0040, //COMMERCIAL AT - 0x0041, //LATIN CAPITAL LETTER A - 0x0042, //LATIN CAPITAL LETTER B - 0x0043, //LATIN CAPITAL LETTER C - 0x0044, //LATIN CAPITAL LETTER D - 0x0045, //LATIN CAPITAL LETTER E - 0x0046, //LATIN CAPITAL LETTER F - 0x0047, //LATIN CAPITAL LETTER G - 0x0048, //LATIN CAPITAL LETTER H - 0x0049, //LATIN CAPITAL LETTER I - 0x004A, //LATIN CAPITAL LETTER J - 0x004B, //LATIN CAPITAL LETTER K - 0x004C, //LATIN CAPITAL LETTER L - 0x004D, //LATIN CAPITAL LETTER M - 0x004E, //LATIN CAPITAL LETTER N - 0x004F, //LATIN CAPITAL LETTER O - 0x0050, //LATIN CAPITAL LETTER P - 0x0051, //LATIN CAPITAL LETTER Q - 0x0052, //LATIN CAPITAL LETTER R - 0x0053, //LATIN CAPITAL LETTER S - 0x0054, //LATIN CAPITAL LETTER T - 0x0055, //LATIN CAPITAL LETTER U - 0x0056, //LATIN CAPITAL LETTER V - 0x0057, //LATIN CAPITAL LETTER W - 0x0058, //LATIN CAPITAL LETTER X - 0x0059, //LATIN CAPITAL LETTER Y - 0x005A, //LATIN CAPITAL LETTER Z - 0x005B, //LEFT SQUARE BRACKET - 0x005C, //REVERSE SOLIDUS - 0x005D, //RIGHT SQUARE BRACKET - 0x005E, //CIRCUMFLEX ACCENT - 0x005F, //LOW LINE - 0x0060, //GRAVE ACCENT - 0x0061, //LATIN SMALL LETTER A - 0x0062, //LATIN SMALL LETTER B - 0x0063, //LATIN SMALL LETTER C - 0x0064, //LATIN SMALL LETTER D - 0x0065, //LATIN SMALL LETTER E - 0x0066, //LATIN SMALL LETTER F - 0x0067, //LATIN SMALL LETTER G - 0x0068, //LATIN SMALL LETTER H - 0x0069, //LATIN SMALL LETTER I - 0x006A, //LATIN SMALL LETTER J - 0x006B, //LATIN SMALL LETTER K - 0x006C, //LATIN SMALL LETTER L - 0x006D, //LATIN SMALL LETTER M - 0x006E, //LATIN SMALL LETTER N - 0x006F, //LATIN SMALL LETTER O - 0x0070, //LATIN SMALL LETTER P - 0x0071, //LATIN SMALL LETTER Q - 0x0072, //LATIN SMALL LETTER R - 0x0073, //LATIN SMALL LETTER S - 0x0074, //LATIN SMALL LETTER T - 0x0075, //LATIN SMALL LETTER U - 0x0076, //LATIN SMALL LETTER V - 0x0077, //LATIN SMALL LETTER W - 0x0078, //LATIN SMALL LETTER X - 0x0079, //LATIN SMALL LETTER Y - 0x007A, //LATIN SMALL LETTER Z - 0x007B, //LEFT CURLY BRACKET - 0x007C, //VERTICAL LINE - 0x007D, //RIGHT CURLY BRACKET - 0x007E, //TILDE - 0x007F, //DELETE - 0x20AC, //EURO SIGN - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - 0xFFFD, //UNDEFINED - }, - db: map[int]rune{ - 0x8140: 0x4E02, //CJK UNIFIED IDEOGRAPH - 0x8141: 0x4E04, //CJK UNIFIED IDEOGRAPH - 0x8142: 0x4E05, //CJK UNIFIED IDEOGRAPH - 0x8143: 0x4E06, //CJK UNIFIED IDEOGRAPH - 0x8144: 0x4E0F, //CJK UNIFIED IDEOGRAPH - 0x8145: 0x4E12, //CJK UNIFIED IDEOGRAPH - 0x8146: 0x4E17, //CJK UNIFIED IDEOGRAPH - 0x8147: 0x4E1F, //CJK UNIFIED IDEOGRAPH - 0x8148: 0x4E20, //CJK UNIFIED IDEOGRAPH - 0x8149: 0x4E21, //CJK UNIFIED IDEOGRAPH - 0x814A: 0x4E23, //CJK UNIFIED IDEOGRAPH - 0x814B: 0x4E26, //CJK UNIFIED IDEOGRAPH - 0x814C: 0x4E29, //CJK UNIFIED IDEOGRAPH - 0x814D: 0x4E2E, //CJK UNIFIED IDEOGRAPH - 0x814E: 0x4E2F, //CJK UNIFIED IDEOGRAPH - 0x814F: 0x4E31, //CJK UNIFIED IDEOGRAPH - 0x8150: 0x4E33, //CJK UNIFIED IDEOGRAPH - 0x8151: 0x4E35, //CJK UNIFIED IDEOGRAPH - 0x8152: 0x4E37, //CJK UNIFIED IDEOGRAPH - 0x8153: 0x4E3C, //CJK UNIFIED IDEOGRAPH - 0x8154: 0x4E40, //CJK UNIFIED IDEOGRAPH - 0x8155: 0x4E41, //CJK UNIFIED IDEOGRAPH - 0x8156: 0x4E42, //CJK UNIFIED IDEOGRAPH - 0x8157: 0x4E44, //CJK UNIFIED IDEOGRAPH - 0x8158: 0x4E46, //CJK UNIFIED IDEOGRAPH - 0x8159: 0x4E4A, //CJK UNIFIED IDEOGRAPH - 0x815A: 0x4E51, //CJK UNIFIED IDEOGRAPH - 0x815B: 0x4E55, //CJK UNIFIED IDEOGRAPH - 0x815C: 0x4E57, //CJK UNIFIED IDEOGRAPH - 0x815D: 0x4E5A, //CJK UNIFIED IDEOGRAPH - 0x815E: 0x4E5B, //CJK UNIFIED IDEOGRAPH - 0x815F: 0x4E62, //CJK UNIFIED IDEOGRAPH - 0x8160: 0x4E63, //CJK UNIFIED IDEOGRAPH - 0x8161: 0x4E64, //CJK UNIFIED IDEOGRAPH - 0x8162: 0x4E65, //CJK UNIFIED IDEOGRAPH - 0x8163: 0x4E67, //CJK UNIFIED IDEOGRAPH - 0x8164: 0x4E68, //CJK UNIFIED IDEOGRAPH - 0x8165: 0x4E6A, //CJK UNIFIED IDEOGRAPH - 0x8166: 0x4E6B, //CJK UNIFIED IDEOGRAPH - 0x8167: 0x4E6C, //CJK UNIFIED IDEOGRAPH - 0x8168: 0x4E6D, //CJK UNIFIED IDEOGRAPH - 0x8169: 0x4E6E, //CJK UNIFIED IDEOGRAPH - 0x816A: 0x4E6F, //CJK UNIFIED IDEOGRAPH - 0x816B: 0x4E72, //CJK UNIFIED IDEOGRAPH - 0x816C: 0x4E74, //CJK UNIFIED IDEOGRAPH - 0x816D: 0x4E75, //CJK UNIFIED IDEOGRAPH - 0x816E: 0x4E76, //CJK UNIFIED IDEOGRAPH - 0x816F: 0x4E77, //CJK UNIFIED IDEOGRAPH - 0x8170: 0x4E78, //CJK UNIFIED IDEOGRAPH - 0x8171: 0x4E79, //CJK UNIFIED IDEOGRAPH - 0x8172: 0x4E7A, //CJK UNIFIED IDEOGRAPH - 0x8173: 0x4E7B, //CJK UNIFIED IDEOGRAPH - 0x8174: 0x4E7C, //CJK UNIFIED IDEOGRAPH - 0x8175: 0x4E7D, //CJK UNIFIED IDEOGRAPH - 0x8176: 0x4E7F, //CJK UNIFIED IDEOGRAPH - 0x8177: 0x4E80, //CJK UNIFIED IDEOGRAPH - 0x8178: 0x4E81, //CJK UNIFIED IDEOGRAPH - 0x8179: 0x4E82, //CJK UNIFIED IDEOGRAPH - 0x817A: 0x4E83, //CJK UNIFIED IDEOGRAPH - 0x817B: 0x4E84, //CJK UNIFIED IDEOGRAPH - 0x817C: 0x4E85, //CJK UNIFIED IDEOGRAPH - 0x817D: 0x4E87, //CJK UNIFIED IDEOGRAPH - 0x817E: 0x4E8A, //CJK UNIFIED IDEOGRAPH - 0x8180: 0x4E90, //CJK UNIFIED IDEOGRAPH - 0x8181: 0x4E96, //CJK UNIFIED IDEOGRAPH - 0x8182: 0x4E97, //CJK UNIFIED IDEOGRAPH - 0x8183: 0x4E99, //CJK UNIFIED IDEOGRAPH - 0x8184: 0x4E9C, //CJK UNIFIED IDEOGRAPH - 0x8185: 0x4E9D, //CJK UNIFIED IDEOGRAPH - 0x8186: 0x4E9E, //CJK UNIFIED IDEOGRAPH - 0x8187: 0x4EA3, //CJK UNIFIED IDEOGRAPH - 0x8188: 0x4EAA, //CJK UNIFIED IDEOGRAPH - 0x8189: 0x4EAF, //CJK UNIFIED IDEOGRAPH - 0x818A: 0x4EB0, //CJK UNIFIED IDEOGRAPH - 0x818B: 0x4EB1, //CJK UNIFIED IDEOGRAPH - 0x818C: 0x4EB4, //CJK UNIFIED IDEOGRAPH - 0x818D: 0x4EB6, //CJK UNIFIED IDEOGRAPH - 0x818E: 0x4EB7, //CJK UNIFIED IDEOGRAPH - 0x818F: 0x4EB8, //CJK UNIFIED IDEOGRAPH - 0x8190: 0x4EB9, //CJK UNIFIED IDEOGRAPH - 0x8191: 0x4EBC, //CJK UNIFIED IDEOGRAPH - 0x8192: 0x4EBD, //CJK UNIFIED IDEOGRAPH - 0x8193: 0x4EBE, //CJK UNIFIED IDEOGRAPH - 0x8194: 0x4EC8, //CJK UNIFIED IDEOGRAPH - 0x8195: 0x4ECC, //CJK UNIFIED IDEOGRAPH - 0x8196: 0x4ECF, //CJK UNIFIED IDEOGRAPH - 0x8197: 0x4ED0, //CJK UNIFIED IDEOGRAPH - 0x8198: 0x4ED2, //CJK UNIFIED IDEOGRAPH - 0x8199: 0x4EDA, //CJK UNIFIED IDEOGRAPH - 0x819A: 0x4EDB, //CJK UNIFIED IDEOGRAPH - 0x819B: 0x4EDC, //CJK UNIFIED IDEOGRAPH - 0x819C: 0x4EE0, //CJK UNIFIED IDEOGRAPH - 0x819D: 0x4EE2, //CJK UNIFIED IDEOGRAPH - 0x819E: 0x4EE6, //CJK UNIFIED IDEOGRAPH - 0x819F: 0x4EE7, //CJK UNIFIED IDEOGRAPH - 0x81A0: 0x4EE9, //CJK UNIFIED IDEOGRAPH - 0x81A1: 0x4EED, //CJK UNIFIED IDEOGRAPH - 0x81A2: 0x4EEE, //CJK UNIFIED IDEOGRAPH - 0x81A3: 0x4EEF, //CJK UNIFIED IDEOGRAPH - 0x81A4: 0x4EF1, //CJK UNIFIED IDEOGRAPH - 0x81A5: 0x4EF4, //CJK UNIFIED IDEOGRAPH - 0x81A6: 0x4EF8, //CJK UNIFIED IDEOGRAPH - 0x81A7: 0x4EF9, //CJK UNIFIED IDEOGRAPH - 0x81A8: 0x4EFA, //CJK UNIFIED IDEOGRAPH - 0x81A9: 0x4EFC, //CJK UNIFIED IDEOGRAPH - 0x81AA: 0x4EFE, //CJK UNIFIED IDEOGRAPH - 0x81AB: 0x4F00, //CJK UNIFIED IDEOGRAPH - 0x81AC: 0x4F02, //CJK UNIFIED IDEOGRAPH - 0x81AD: 0x4F03, //CJK UNIFIED IDEOGRAPH - 0x81AE: 0x4F04, //CJK UNIFIED IDEOGRAPH - 0x81AF: 0x4F05, //CJK UNIFIED IDEOGRAPH - 0x81B0: 0x4F06, //CJK UNIFIED IDEOGRAPH - 0x81B1: 0x4F07, //CJK UNIFIED IDEOGRAPH - 0x81B2: 0x4F08, //CJK UNIFIED IDEOGRAPH - 0x81B3: 0x4F0B, //CJK UNIFIED IDEOGRAPH - 0x81B4: 0x4F0C, //CJK UNIFIED IDEOGRAPH - 0x81B5: 0x4F12, //CJK UNIFIED IDEOGRAPH - 0x81B6: 0x4F13, //CJK UNIFIED IDEOGRAPH - 0x81B7: 0x4F14, //CJK UNIFIED IDEOGRAPH - 0x81B8: 0x4F15, //CJK UNIFIED IDEOGRAPH - 0x81B9: 0x4F16, //CJK UNIFIED IDEOGRAPH - 0x81BA: 0x4F1C, //CJK UNIFIED IDEOGRAPH - 0x81BB: 0x4F1D, //CJK UNIFIED IDEOGRAPH - 0x81BC: 0x4F21, //CJK UNIFIED IDEOGRAPH - 0x81BD: 0x4F23, //CJK UNIFIED IDEOGRAPH - 0x81BE: 0x4F28, //CJK UNIFIED IDEOGRAPH - 0x81BF: 0x4F29, //CJK UNIFIED IDEOGRAPH - 0x81C0: 0x4F2C, //CJK UNIFIED IDEOGRAPH - 0x81C1: 0x4F2D, //CJK UNIFIED IDEOGRAPH - 0x81C2: 0x4F2E, //CJK UNIFIED IDEOGRAPH - 0x81C3: 0x4F31, //CJK UNIFIED IDEOGRAPH - 0x81C4: 0x4F33, //CJK UNIFIED IDEOGRAPH - 0x81C5: 0x4F35, //CJK UNIFIED IDEOGRAPH - 0x81C6: 0x4F37, //CJK UNIFIED IDEOGRAPH - 0x81C7: 0x4F39, //CJK UNIFIED IDEOGRAPH - 0x81C8: 0x4F3B, //CJK UNIFIED IDEOGRAPH - 0x81C9: 0x4F3E, //CJK UNIFIED IDEOGRAPH - 0x81CA: 0x4F3F, //CJK UNIFIED IDEOGRAPH - 0x81CB: 0x4F40, //CJK UNIFIED IDEOGRAPH - 0x81CC: 0x4F41, //CJK UNIFIED IDEOGRAPH - 0x81CD: 0x4F42, //CJK UNIFIED IDEOGRAPH - 0x81CE: 0x4F44, //CJK UNIFIED IDEOGRAPH - 0x81CF: 0x4F45, //CJK UNIFIED IDEOGRAPH - 0x81D0: 0x4F47, //CJK UNIFIED IDEOGRAPH - 0x81D1: 0x4F48, //CJK UNIFIED IDEOGRAPH - 0x81D2: 0x4F49, //CJK UNIFIED IDEOGRAPH - 0x81D3: 0x4F4A, //CJK UNIFIED IDEOGRAPH - 0x81D4: 0x4F4B, //CJK UNIFIED IDEOGRAPH - 0x81D5: 0x4F4C, //CJK UNIFIED IDEOGRAPH - 0x81D6: 0x4F52, //CJK UNIFIED IDEOGRAPH - 0x81D7: 0x4F54, //CJK UNIFIED IDEOGRAPH - 0x81D8: 0x4F56, //CJK UNIFIED IDEOGRAPH - 0x81D9: 0x4F61, //CJK UNIFIED IDEOGRAPH - 0x81DA: 0x4F62, //CJK UNIFIED IDEOGRAPH - 0x81DB: 0x4F66, //CJK UNIFIED IDEOGRAPH - 0x81DC: 0x4F68, //CJK UNIFIED IDEOGRAPH - 0x81DD: 0x4F6A, //CJK UNIFIED IDEOGRAPH - 0x81DE: 0x4F6B, //CJK UNIFIED IDEOGRAPH - 0x81DF: 0x4F6D, //CJK UNIFIED IDEOGRAPH - 0x81E0: 0x4F6E, //CJK UNIFIED IDEOGRAPH - 0x81E1: 0x4F71, //CJK UNIFIED IDEOGRAPH - 0x81E2: 0x4F72, //CJK UNIFIED IDEOGRAPH - 0x81E3: 0x4F75, //CJK UNIFIED IDEOGRAPH - 0x81E4: 0x4F77, //CJK UNIFIED IDEOGRAPH - 0x81E5: 0x4F78, //CJK UNIFIED IDEOGRAPH - 0x81E6: 0x4F79, //CJK UNIFIED IDEOGRAPH - 0x81E7: 0x4F7A, //CJK UNIFIED IDEOGRAPH - 0x81E8: 0x4F7D, //CJK UNIFIED IDEOGRAPH - 0x81E9: 0x4F80, //CJK UNIFIED IDEOGRAPH - 0x81EA: 0x4F81, //CJK UNIFIED IDEOGRAPH - 0x81EB: 0x4F82, //CJK UNIFIED IDEOGRAPH - 0x81EC: 0x4F85, //CJK UNIFIED IDEOGRAPH - 0x81ED: 0x4F86, //CJK UNIFIED IDEOGRAPH - 0x81EE: 0x4F87, //CJK UNIFIED IDEOGRAPH - 0x81EF: 0x4F8A, //CJK UNIFIED IDEOGRAPH - 0x81F0: 0x4F8C, //CJK UNIFIED IDEOGRAPH - 0x81F1: 0x4F8E, //CJK UNIFIED IDEOGRAPH - 0x81F2: 0x4F90, //CJK UNIFIED IDEOGRAPH - 0x81F3: 0x4F92, //CJK UNIFIED IDEOGRAPH - 0x81F4: 0x4F93, //CJK UNIFIED IDEOGRAPH - 0x81F5: 0x4F95, //CJK UNIFIED IDEOGRAPH - 0x81F6: 0x4F96, //CJK UNIFIED IDEOGRAPH - 0x81F7: 0x4F98, //CJK UNIFIED IDEOGRAPH - 0x81F8: 0x4F99, //CJK UNIFIED IDEOGRAPH - 0x81F9: 0x4F9A, //CJK UNIFIED IDEOGRAPH - 0x81FA: 0x4F9C, //CJK UNIFIED IDEOGRAPH - 0x81FB: 0x4F9E, //CJK UNIFIED IDEOGRAPH - 0x81FC: 0x4F9F, //CJK UNIFIED IDEOGRAPH - 0x81FD: 0x4FA1, //CJK UNIFIED IDEOGRAPH - 0x81FE: 0x4FA2, //CJK UNIFIED IDEOGRAPH - 0x8240: 0x4FA4, //CJK UNIFIED IDEOGRAPH - 0x8241: 0x4FAB, //CJK UNIFIED IDEOGRAPH - 0x8242: 0x4FAD, //CJK UNIFIED IDEOGRAPH - 0x8243: 0x4FB0, //CJK UNIFIED IDEOGRAPH - 0x8244: 0x4FB1, //CJK UNIFIED IDEOGRAPH - 0x8245: 0x4FB2, //CJK UNIFIED IDEOGRAPH - 0x8246: 0x4FB3, //CJK UNIFIED IDEOGRAPH - 0x8247: 0x4FB4, //CJK UNIFIED IDEOGRAPH - 0x8248: 0x4FB6, //CJK UNIFIED IDEOGRAPH - 0x8249: 0x4FB7, //CJK UNIFIED IDEOGRAPH - 0x824A: 0x4FB8, //CJK UNIFIED IDEOGRAPH - 0x824B: 0x4FB9, //CJK UNIFIED IDEOGRAPH - 0x824C: 0x4FBA, //CJK UNIFIED IDEOGRAPH - 0x824D: 0x4FBB, //CJK UNIFIED IDEOGRAPH - 0x824E: 0x4FBC, //CJK UNIFIED IDEOGRAPH - 0x824F: 0x4FBD, //CJK UNIFIED IDEOGRAPH - 0x8250: 0x4FBE, //CJK UNIFIED IDEOGRAPH - 0x8251: 0x4FC0, //CJK UNIFIED IDEOGRAPH - 0x8252: 0x4FC1, //CJK UNIFIED IDEOGRAPH - 0x8253: 0x4FC2, //CJK UNIFIED IDEOGRAPH - 0x8254: 0x4FC6, //CJK UNIFIED IDEOGRAPH - 0x8255: 0x4FC7, //CJK UNIFIED IDEOGRAPH - 0x8256: 0x4FC8, //CJK UNIFIED IDEOGRAPH - 0x8257: 0x4FC9, //CJK UNIFIED IDEOGRAPH - 0x8258: 0x4FCB, //CJK UNIFIED IDEOGRAPH - 0x8259: 0x4FCC, //CJK UNIFIED IDEOGRAPH - 0x825A: 0x4FCD, //CJK UNIFIED IDEOGRAPH - 0x825B: 0x4FD2, //CJK UNIFIED IDEOGRAPH - 0x825C: 0x4FD3, //CJK UNIFIED IDEOGRAPH - 0x825D: 0x4FD4, //CJK UNIFIED IDEOGRAPH - 0x825E: 0x4FD5, //CJK UNIFIED IDEOGRAPH - 0x825F: 0x4FD6, //CJK UNIFIED IDEOGRAPH - 0x8260: 0x4FD9, //CJK UNIFIED IDEOGRAPH - 0x8261: 0x4FDB, //CJK UNIFIED IDEOGRAPH - 0x8262: 0x4FE0, //CJK UNIFIED IDEOGRAPH - 0x8263: 0x4FE2, //CJK UNIFIED IDEOGRAPH - 0x8264: 0x4FE4, //CJK UNIFIED IDEOGRAPH - 0x8265: 0x4FE5, //CJK UNIFIED IDEOGRAPH - 0x8266: 0x4FE7, //CJK UNIFIED IDEOGRAPH - 0x8267: 0x4FEB, //CJK UNIFIED IDEOGRAPH - 0x8268: 0x4FEC, //CJK UNIFIED IDEOGRAPH - 0x8269: 0x4FF0, //CJK UNIFIED IDEOGRAPH - 0x826A: 0x4FF2, //CJK UNIFIED IDEOGRAPH - 0x826B: 0x4FF4, //CJK UNIFIED IDEOGRAPH - 0x826C: 0x4FF5, //CJK UNIFIED IDEOGRAPH - 0x826D: 0x4FF6, //CJK UNIFIED IDEOGRAPH - 0x826E: 0x4FF7, //CJK UNIFIED IDEOGRAPH - 0x826F: 0x4FF9, //CJK UNIFIED IDEOGRAPH - 0x8270: 0x4FFB, //CJK UNIFIED IDEOGRAPH - 0x8271: 0x4FFC, //CJK UNIFIED IDEOGRAPH - 0x8272: 0x4FFD, //CJK UNIFIED IDEOGRAPH - 0x8273: 0x4FFF, //CJK UNIFIED IDEOGRAPH - 0x8274: 0x5000, //CJK UNIFIED IDEOGRAPH - 0x8275: 0x5001, //CJK UNIFIED IDEOGRAPH - 0x8276: 0x5002, //CJK UNIFIED IDEOGRAPH - 0x8277: 0x5003, //CJK UNIFIED IDEOGRAPH - 0x8278: 0x5004, //CJK UNIFIED IDEOGRAPH - 0x8279: 0x5005, //CJK UNIFIED IDEOGRAPH - 0x827A: 0x5006, //CJK UNIFIED IDEOGRAPH - 0x827B: 0x5007, //CJK UNIFIED IDEOGRAPH - 0x827C: 0x5008, //CJK UNIFIED IDEOGRAPH - 0x827D: 0x5009, //CJK UNIFIED IDEOGRAPH - 0x827E: 0x500A, //CJK UNIFIED IDEOGRAPH - 0x8280: 0x500B, //CJK UNIFIED IDEOGRAPH - 0x8281: 0x500E, //CJK UNIFIED IDEOGRAPH - 0x8282: 0x5010, //CJK UNIFIED IDEOGRAPH - 0x8283: 0x5011, //CJK UNIFIED IDEOGRAPH - 0x8284: 0x5013, //CJK UNIFIED IDEOGRAPH - 0x8285: 0x5015, //CJK UNIFIED IDEOGRAPH - 0x8286: 0x5016, //CJK UNIFIED IDEOGRAPH - 0x8287: 0x5017, //CJK UNIFIED IDEOGRAPH - 0x8288: 0x501B, //CJK UNIFIED IDEOGRAPH - 0x8289: 0x501D, //CJK UNIFIED IDEOGRAPH - 0x828A: 0x501E, //CJK UNIFIED IDEOGRAPH - 0x828B: 0x5020, //CJK UNIFIED IDEOGRAPH - 0x828C: 0x5022, //CJK UNIFIED IDEOGRAPH - 0x828D: 0x5023, //CJK UNIFIED IDEOGRAPH - 0x828E: 0x5024, //CJK UNIFIED IDEOGRAPH - 0x828F: 0x5027, //CJK UNIFIED IDEOGRAPH - 0x8290: 0x502B, //CJK UNIFIED IDEOGRAPH - 0x8291: 0x502F, //CJK UNIFIED IDEOGRAPH - 0x8292: 0x5030, //CJK UNIFIED IDEOGRAPH - 0x8293: 0x5031, //CJK UNIFIED IDEOGRAPH - 0x8294: 0x5032, //CJK UNIFIED IDEOGRAPH - 0x8295: 0x5033, //CJK UNIFIED IDEOGRAPH - 0x8296: 0x5034, //CJK UNIFIED IDEOGRAPH - 0x8297: 0x5035, //CJK UNIFIED IDEOGRAPH - 0x8298: 0x5036, //CJK UNIFIED IDEOGRAPH - 0x8299: 0x5037, //CJK UNIFIED IDEOGRAPH - 0x829A: 0x5038, //CJK UNIFIED IDEOGRAPH - 0x829B: 0x5039, //CJK UNIFIED IDEOGRAPH - 0x829C: 0x503B, //CJK UNIFIED IDEOGRAPH - 0x829D: 0x503D, //CJK UNIFIED IDEOGRAPH - 0x829E: 0x503F, //CJK UNIFIED IDEOGRAPH - 0x829F: 0x5040, //CJK UNIFIED IDEOGRAPH - 0x82A0: 0x5041, //CJK UNIFIED IDEOGRAPH - 0x82A1: 0x5042, //CJK UNIFIED IDEOGRAPH - 0x82A2: 0x5044, //CJK UNIFIED IDEOGRAPH - 0x82A3: 0x5045, //CJK UNIFIED IDEOGRAPH - 0x82A4: 0x5046, //CJK UNIFIED IDEOGRAPH - 0x82A5: 0x5049, //CJK UNIFIED IDEOGRAPH - 0x82A6: 0x504A, //CJK UNIFIED IDEOGRAPH - 0x82A7: 0x504B, //CJK UNIFIED IDEOGRAPH - 0x82A8: 0x504D, //CJK UNIFIED IDEOGRAPH - 0x82A9: 0x5050, //CJK UNIFIED IDEOGRAPH - 0x82AA: 0x5051, //CJK UNIFIED IDEOGRAPH - 0x82AB: 0x5052, //CJK UNIFIED IDEOGRAPH - 0x82AC: 0x5053, //CJK UNIFIED IDEOGRAPH - 0x82AD: 0x5054, //CJK UNIFIED IDEOGRAPH - 0x82AE: 0x5056, //CJK UNIFIED IDEOGRAPH - 0x82AF: 0x5057, //CJK UNIFIED IDEOGRAPH - 0x82B0: 0x5058, //CJK UNIFIED IDEOGRAPH - 0x82B1: 0x5059, //CJK UNIFIED IDEOGRAPH - 0x82B2: 0x505B, //CJK UNIFIED IDEOGRAPH - 0x82B3: 0x505D, //CJK UNIFIED IDEOGRAPH - 0x82B4: 0x505E, //CJK UNIFIED IDEOGRAPH - 0x82B5: 0x505F, //CJK UNIFIED IDEOGRAPH - 0x82B6: 0x5060, //CJK UNIFIED IDEOGRAPH - 0x82B7: 0x5061, //CJK UNIFIED IDEOGRAPH - 0x82B8: 0x5062, //CJK UNIFIED IDEOGRAPH - 0x82B9: 0x5063, //CJK UNIFIED IDEOGRAPH - 0x82BA: 0x5064, //CJK UNIFIED IDEOGRAPH - 0x82BB: 0x5066, //CJK UNIFIED IDEOGRAPH - 0x82BC: 0x5067, //CJK UNIFIED IDEOGRAPH - 0x82BD: 0x5068, //CJK UNIFIED IDEOGRAPH - 0x82BE: 0x5069, //CJK UNIFIED IDEOGRAPH - 0x82BF: 0x506A, //CJK UNIFIED IDEOGRAPH - 0x82C0: 0x506B, //CJK UNIFIED IDEOGRAPH - 0x82C1: 0x506D, //CJK UNIFIED IDEOGRAPH - 0x82C2: 0x506E, //CJK UNIFIED IDEOGRAPH - 0x82C3: 0x506F, //CJK UNIFIED IDEOGRAPH - 0x82C4: 0x5070, //CJK UNIFIED IDEOGRAPH - 0x82C5: 0x5071, //CJK UNIFIED IDEOGRAPH - 0x82C6: 0x5072, //CJK UNIFIED IDEOGRAPH - 0x82C7: 0x5073, //CJK UNIFIED IDEOGRAPH - 0x82C8: 0x5074, //CJK UNIFIED IDEOGRAPH - 0x82C9: 0x5075, //CJK UNIFIED IDEOGRAPH - 0x82CA: 0x5078, //CJK UNIFIED IDEOGRAPH - 0x82CB: 0x5079, //CJK UNIFIED IDEOGRAPH - 0x82CC: 0x507A, //CJK UNIFIED IDEOGRAPH - 0x82CD: 0x507C, //CJK UNIFIED IDEOGRAPH - 0x82CE: 0x507D, //CJK UNIFIED IDEOGRAPH - 0x82CF: 0x5081, //CJK UNIFIED IDEOGRAPH - 0x82D0: 0x5082, //CJK UNIFIED IDEOGRAPH - 0x82D1: 0x5083, //CJK UNIFIED IDEOGRAPH - 0x82D2: 0x5084, //CJK UNIFIED IDEOGRAPH - 0x82D3: 0x5086, //CJK UNIFIED IDEOGRAPH - 0x82D4: 0x5087, //CJK UNIFIED IDEOGRAPH - 0x82D5: 0x5089, //CJK UNIFIED IDEOGRAPH - 0x82D6: 0x508A, //CJK UNIFIED IDEOGRAPH - 0x82D7: 0x508B, //CJK UNIFIED IDEOGRAPH - 0x82D8: 0x508C, //CJK UNIFIED IDEOGRAPH - 0x82D9: 0x508E, //CJK UNIFIED IDEOGRAPH - 0x82DA: 0x508F, //CJK UNIFIED IDEOGRAPH - 0x82DB: 0x5090, //CJK UNIFIED IDEOGRAPH - 0x82DC: 0x5091, //CJK UNIFIED IDEOGRAPH - 0x82DD: 0x5092, //CJK UNIFIED IDEOGRAPH - 0x82DE: 0x5093, //CJK UNIFIED IDEOGRAPH - 0x82DF: 0x5094, //CJK UNIFIED IDEOGRAPH - 0x82E0: 0x5095, //CJK UNIFIED IDEOGRAPH - 0x82E1: 0x5096, //CJK UNIFIED IDEOGRAPH - 0x82E2: 0x5097, //CJK UNIFIED IDEOGRAPH - 0x82E3: 0x5098, //CJK UNIFIED IDEOGRAPH - 0x82E4: 0x5099, //CJK UNIFIED IDEOGRAPH - 0x82E5: 0x509A, //CJK UNIFIED IDEOGRAPH - 0x82E6: 0x509B, //CJK UNIFIED IDEOGRAPH - 0x82E7: 0x509C, //CJK UNIFIED IDEOGRAPH - 0x82E8: 0x509D, //CJK UNIFIED IDEOGRAPH - 0x82E9: 0x509E, //CJK UNIFIED IDEOGRAPH - 0x82EA: 0x509F, //CJK UNIFIED IDEOGRAPH - 0x82EB: 0x50A0, //CJK UNIFIED IDEOGRAPH - 0x82EC: 0x50A1, //CJK UNIFIED IDEOGRAPH - 0x82ED: 0x50A2, //CJK UNIFIED IDEOGRAPH - 0x82EE: 0x50A4, //CJK UNIFIED IDEOGRAPH - 0x82EF: 0x50A6, //CJK UNIFIED IDEOGRAPH - 0x82F0: 0x50AA, //CJK UNIFIED IDEOGRAPH - 0x82F1: 0x50AB, //CJK UNIFIED IDEOGRAPH - 0x82F2: 0x50AD, //CJK UNIFIED IDEOGRAPH - 0x82F3: 0x50AE, //CJK UNIFIED IDEOGRAPH - 0x82F4: 0x50AF, //CJK UNIFIED IDEOGRAPH - 0x82F5: 0x50B0, //CJK UNIFIED IDEOGRAPH - 0x82F6: 0x50B1, //CJK UNIFIED IDEOGRAPH - 0x82F7: 0x50B3, //CJK UNIFIED IDEOGRAPH - 0x82F8: 0x50B4, //CJK UNIFIED IDEOGRAPH - 0x82F9: 0x50B5, //CJK UNIFIED IDEOGRAPH - 0x82FA: 0x50B6, //CJK UNIFIED IDEOGRAPH - 0x82FB: 0x50B7, //CJK UNIFIED IDEOGRAPH - 0x82FC: 0x50B8, //CJK UNIFIED IDEOGRAPH - 0x82FD: 0x50B9, //CJK UNIFIED IDEOGRAPH - 0x82FE: 0x50BC, //CJK UNIFIED IDEOGRAPH - 0x8340: 0x50BD, //CJK UNIFIED IDEOGRAPH - 0x8341: 0x50BE, //CJK UNIFIED IDEOGRAPH - 0x8342: 0x50BF, //CJK UNIFIED IDEOGRAPH - 0x8343: 0x50C0, //CJK UNIFIED IDEOGRAPH - 0x8344: 0x50C1, //CJK UNIFIED IDEOGRAPH - 0x8345: 0x50C2, //CJK UNIFIED IDEOGRAPH - 0x8346: 0x50C3, //CJK UNIFIED IDEOGRAPH - 0x8347: 0x50C4, //CJK UNIFIED IDEOGRAPH - 0x8348: 0x50C5, //CJK UNIFIED IDEOGRAPH - 0x8349: 0x50C6, //CJK UNIFIED IDEOGRAPH - 0x834A: 0x50C7, //CJK UNIFIED IDEOGRAPH - 0x834B: 0x50C8, //CJK UNIFIED IDEOGRAPH - 0x834C: 0x50C9, //CJK UNIFIED IDEOGRAPH - 0x834D: 0x50CA, //CJK UNIFIED IDEOGRAPH - 0x834E: 0x50CB, //CJK UNIFIED IDEOGRAPH - 0x834F: 0x50CC, //CJK UNIFIED IDEOGRAPH - 0x8350: 0x50CD, //CJK UNIFIED IDEOGRAPH - 0x8351: 0x50CE, //CJK UNIFIED IDEOGRAPH - 0x8352: 0x50D0, //CJK UNIFIED IDEOGRAPH - 0x8353: 0x50D1, //CJK UNIFIED IDEOGRAPH - 0x8354: 0x50D2, //CJK UNIFIED IDEOGRAPH - 0x8355: 0x50D3, //CJK UNIFIED IDEOGRAPH - 0x8356: 0x50D4, //CJK UNIFIED IDEOGRAPH - 0x8357: 0x50D5, //CJK UNIFIED IDEOGRAPH - 0x8358: 0x50D7, //CJK UNIFIED IDEOGRAPH - 0x8359: 0x50D8, //CJK UNIFIED IDEOGRAPH - 0x835A: 0x50D9, //CJK UNIFIED IDEOGRAPH - 0x835B: 0x50DB, //CJK UNIFIED IDEOGRAPH - 0x835C: 0x50DC, //CJK UNIFIED IDEOGRAPH - 0x835D: 0x50DD, //CJK UNIFIED IDEOGRAPH - 0x835E: 0x50DE, //CJK UNIFIED IDEOGRAPH - 0x835F: 0x50DF, //CJK UNIFIED IDEOGRAPH - 0x8360: 0x50E0, //CJK UNIFIED IDEOGRAPH - 0x8361: 0x50E1, //CJK UNIFIED IDEOGRAPH - 0x8362: 0x50E2, //CJK UNIFIED IDEOGRAPH - 0x8363: 0x50E3, //CJK UNIFIED IDEOGRAPH - 0x8364: 0x50E4, //CJK UNIFIED IDEOGRAPH - 0x8365: 0x50E5, //CJK UNIFIED IDEOGRAPH - 0x8366: 0x50E8, //CJK UNIFIED IDEOGRAPH - 0x8367: 0x50E9, //CJK UNIFIED IDEOGRAPH - 0x8368: 0x50EA, //CJK UNIFIED IDEOGRAPH - 0x8369: 0x50EB, //CJK UNIFIED IDEOGRAPH - 0x836A: 0x50EF, //CJK UNIFIED IDEOGRAPH - 0x836B: 0x50F0, //CJK UNIFIED IDEOGRAPH - 0x836C: 0x50F1, //CJK UNIFIED IDEOGRAPH - 0x836D: 0x50F2, //CJK UNIFIED IDEOGRAPH - 0x836E: 0x50F4, //CJK UNIFIED IDEOGRAPH - 0x836F: 0x50F6, //CJK UNIFIED IDEOGRAPH - 0x8370: 0x50F7, //CJK UNIFIED IDEOGRAPH - 0x8371: 0x50F8, //CJK UNIFIED IDEOGRAPH - 0x8372: 0x50F9, //CJK UNIFIED IDEOGRAPH - 0x8373: 0x50FA, //CJK UNIFIED IDEOGRAPH - 0x8374: 0x50FC, //CJK UNIFIED IDEOGRAPH - 0x8375: 0x50FD, //CJK UNIFIED IDEOGRAPH - 0x8376: 0x50FE, //CJK UNIFIED IDEOGRAPH - 0x8377: 0x50FF, //CJK UNIFIED IDEOGRAPH - 0x8378: 0x5100, //CJK UNIFIED IDEOGRAPH - 0x8379: 0x5101, //CJK UNIFIED IDEOGRAPH - 0x837A: 0x5102, //CJK UNIFIED IDEOGRAPH - 0x837B: 0x5103, //CJK UNIFIED IDEOGRAPH - 0x837C: 0x5104, //CJK UNIFIED IDEOGRAPH - 0x837D: 0x5105, //CJK UNIFIED IDEOGRAPH - 0x837E: 0x5108, //CJK UNIFIED IDEOGRAPH - 0x8380: 0x5109, //CJK UNIFIED IDEOGRAPH - 0x8381: 0x510A, //CJK UNIFIED IDEOGRAPH - 0x8382: 0x510C, //CJK UNIFIED IDEOGRAPH - 0x8383: 0x510D, //CJK UNIFIED IDEOGRAPH - 0x8384: 0x510E, //CJK UNIFIED IDEOGRAPH - 0x8385: 0x510F, //CJK UNIFIED IDEOGRAPH - 0x8386: 0x5110, //CJK UNIFIED IDEOGRAPH - 0x8387: 0x5111, //CJK UNIFIED IDEOGRAPH - 0x8388: 0x5113, //CJK UNIFIED IDEOGRAPH - 0x8389: 0x5114, //CJK UNIFIED IDEOGRAPH - 0x838A: 0x5115, //CJK UNIFIED IDEOGRAPH - 0x838B: 0x5116, //CJK UNIFIED IDEOGRAPH - 0x838C: 0x5117, //CJK UNIFIED IDEOGRAPH - 0x838D: 0x5118, //CJK UNIFIED IDEOGRAPH - 0x838E: 0x5119, //CJK UNIFIED IDEOGRAPH - 0x838F: 0x511A, //CJK UNIFIED IDEOGRAPH - 0x8390: 0x511B, //CJK UNIFIED IDEOGRAPH - 0x8391: 0x511C, //CJK UNIFIED IDEOGRAPH - 0x8392: 0x511D, //CJK UNIFIED IDEOGRAPH - 0x8393: 0x511E, //CJK UNIFIED IDEOGRAPH - 0x8394: 0x511F, //CJK UNIFIED IDEOGRAPH - 0x8395: 0x5120, //CJK UNIFIED IDEOGRAPH - 0x8396: 0x5122, //CJK UNIFIED IDEOGRAPH - 0x8397: 0x5123, //CJK UNIFIED IDEOGRAPH - 0x8398: 0x5124, //CJK UNIFIED IDEOGRAPH - 0x8399: 0x5125, //CJK UNIFIED IDEOGRAPH - 0x839A: 0x5126, //CJK UNIFIED IDEOGRAPH - 0x839B: 0x5127, //CJK UNIFIED IDEOGRAPH - 0x839C: 0x5128, //CJK UNIFIED IDEOGRAPH - 0x839D: 0x5129, //CJK UNIFIED IDEOGRAPH - 0x839E: 0x512A, //CJK UNIFIED IDEOGRAPH - 0x839F: 0x512B, //CJK UNIFIED IDEOGRAPH - 0x83A0: 0x512C, //CJK UNIFIED IDEOGRAPH - 0x83A1: 0x512D, //CJK UNIFIED IDEOGRAPH - 0x83A2: 0x512E, //CJK UNIFIED IDEOGRAPH - 0x83A3: 0x512F, //CJK UNIFIED IDEOGRAPH - 0x83A4: 0x5130, //CJK UNIFIED IDEOGRAPH - 0x83A5: 0x5131, //CJK UNIFIED IDEOGRAPH - 0x83A6: 0x5132, //CJK UNIFIED IDEOGRAPH - 0x83A7: 0x5133, //CJK UNIFIED IDEOGRAPH - 0x83A8: 0x5134, //CJK UNIFIED IDEOGRAPH - 0x83A9: 0x5135, //CJK UNIFIED IDEOGRAPH - 0x83AA: 0x5136, //CJK UNIFIED IDEOGRAPH - 0x83AB: 0x5137, //CJK UNIFIED IDEOGRAPH - 0x83AC: 0x5138, //CJK UNIFIED IDEOGRAPH - 0x83AD: 0x5139, //CJK UNIFIED IDEOGRAPH - 0x83AE: 0x513A, //CJK UNIFIED IDEOGRAPH - 0x83AF: 0x513B, //CJK UNIFIED IDEOGRAPH - 0x83B0: 0x513C, //CJK UNIFIED IDEOGRAPH - 0x83B1: 0x513D, //CJK UNIFIED IDEOGRAPH - 0x83B2: 0x513E, //CJK UNIFIED IDEOGRAPH - 0x83B3: 0x5142, //CJK UNIFIED IDEOGRAPH - 0x83B4: 0x5147, //CJK UNIFIED IDEOGRAPH - 0x83B5: 0x514A, //CJK UNIFIED IDEOGRAPH - 0x83B6: 0x514C, //CJK UNIFIED IDEOGRAPH - 0x83B7: 0x514E, //CJK UNIFIED IDEOGRAPH - 0x83B8: 0x514F, //CJK UNIFIED IDEOGRAPH - 0x83B9: 0x5150, //CJK UNIFIED IDEOGRAPH - 0x83BA: 0x5152, //CJK UNIFIED IDEOGRAPH - 0x83BB: 0x5153, //CJK UNIFIED IDEOGRAPH - 0x83BC: 0x5157, //CJK UNIFIED IDEOGRAPH - 0x83BD: 0x5158, //CJK UNIFIED IDEOGRAPH - 0x83BE: 0x5159, //CJK UNIFIED IDEOGRAPH - 0x83BF: 0x515B, //CJK UNIFIED IDEOGRAPH - 0x83C0: 0x515D, //CJK UNIFIED IDEOGRAPH - 0x83C1: 0x515E, //CJK UNIFIED IDEOGRAPH - 0x83C2: 0x515F, //CJK UNIFIED IDEOGRAPH - 0x83C3: 0x5160, //CJK UNIFIED IDEOGRAPH - 0x83C4: 0x5161, //CJK UNIFIED IDEOGRAPH - 0x83C5: 0x5163, //CJK UNIFIED IDEOGRAPH - 0x83C6: 0x5164, //CJK UNIFIED IDEOGRAPH - 0x83C7: 0x5166, //CJK UNIFIED IDEOGRAPH - 0x83C8: 0x5167, //CJK UNIFIED IDEOGRAPH - 0x83C9: 0x5169, //CJK UNIFIED IDEOGRAPH - 0x83CA: 0x516A, //CJK UNIFIED IDEOGRAPH - 0x83CB: 0x516F, //CJK UNIFIED IDEOGRAPH - 0x83CC: 0x5172, //CJK UNIFIED IDEOGRAPH - 0x83CD: 0x517A, //CJK UNIFIED IDEOGRAPH - 0x83CE: 0x517E, //CJK UNIFIED IDEOGRAPH - 0x83CF: 0x517F, //CJK UNIFIED IDEOGRAPH - 0x83D0: 0x5183, //CJK UNIFIED IDEOGRAPH - 0x83D1: 0x5184, //CJK UNIFIED IDEOGRAPH - 0x83D2: 0x5186, //CJK UNIFIED IDEOGRAPH - 0x83D3: 0x5187, //CJK UNIFIED IDEOGRAPH - 0x83D4: 0x518A, //CJK UNIFIED IDEOGRAPH - 0x83D5: 0x518B, //CJK UNIFIED IDEOGRAPH - 0x83D6: 0x518E, //CJK UNIFIED IDEOGRAPH - 0x83D7: 0x518F, //CJK UNIFIED IDEOGRAPH - 0x83D8: 0x5190, //CJK UNIFIED IDEOGRAPH - 0x83D9: 0x5191, //CJK UNIFIED IDEOGRAPH - 0x83DA: 0x5193, //CJK UNIFIED IDEOGRAPH - 0x83DB: 0x5194, //CJK UNIFIED IDEOGRAPH - 0x83DC: 0x5198, //CJK UNIFIED IDEOGRAPH - 0x83DD: 0x519A, //CJK UNIFIED IDEOGRAPH - 0x83DE: 0x519D, //CJK UNIFIED IDEOGRAPH - 0x83DF: 0x519E, //CJK UNIFIED IDEOGRAPH - 0x83E0: 0x519F, //CJK UNIFIED IDEOGRAPH - 0x83E1: 0x51A1, //CJK UNIFIED IDEOGRAPH - 0x83E2: 0x51A3, //CJK UNIFIED IDEOGRAPH - 0x83E3: 0x51A6, //CJK UNIFIED IDEOGRAPH - 0x83E4: 0x51A7, //CJK UNIFIED IDEOGRAPH - 0x83E5: 0x51A8, //CJK UNIFIED IDEOGRAPH - 0x83E6: 0x51A9, //CJK UNIFIED IDEOGRAPH - 0x83E7: 0x51AA, //CJK UNIFIED IDEOGRAPH - 0x83E8: 0x51AD, //CJK UNIFIED IDEOGRAPH - 0x83E9: 0x51AE, //CJK UNIFIED IDEOGRAPH - 0x83EA: 0x51B4, //CJK UNIFIED IDEOGRAPH - 0x83EB: 0x51B8, //CJK UNIFIED IDEOGRAPH - 0x83EC: 0x51B9, //CJK UNIFIED IDEOGRAPH - 0x83ED: 0x51BA, //CJK UNIFIED IDEOGRAPH - 0x83EE: 0x51BE, //CJK UNIFIED IDEOGRAPH - 0x83EF: 0x51BF, //CJK UNIFIED IDEOGRAPH - 0x83F0: 0x51C1, //CJK UNIFIED IDEOGRAPH - 0x83F1: 0x51C2, //CJK UNIFIED IDEOGRAPH - 0x83F2: 0x51C3, //CJK UNIFIED IDEOGRAPH - 0x83F3: 0x51C5, //CJK UNIFIED IDEOGRAPH - 0x83F4: 0x51C8, //CJK UNIFIED IDEOGRAPH - 0x83F5: 0x51CA, //CJK UNIFIED IDEOGRAPH - 0x83F6: 0x51CD, //CJK UNIFIED IDEOGRAPH - 0x83F7: 0x51CE, //CJK UNIFIED IDEOGRAPH - 0x83F8: 0x51D0, //CJK UNIFIED IDEOGRAPH - 0x83F9: 0x51D2, //CJK UNIFIED IDEOGRAPH - 0x83FA: 0x51D3, //CJK UNIFIED IDEOGRAPH - 0x83FB: 0x51D4, //CJK UNIFIED IDEOGRAPH - 0x83FC: 0x51D5, //CJK UNIFIED IDEOGRAPH - 0x83FD: 0x51D6, //CJK UNIFIED IDEOGRAPH - 0x83FE: 0x51D7, //CJK UNIFIED IDEOGRAPH - 0x8440: 0x51D8, //CJK UNIFIED IDEOGRAPH - 0x8441: 0x51D9, //CJK UNIFIED IDEOGRAPH - 0x8442: 0x51DA, //CJK UNIFIED IDEOGRAPH - 0x8443: 0x51DC, //CJK UNIFIED IDEOGRAPH - 0x8444: 0x51DE, //CJK UNIFIED IDEOGRAPH - 0x8445: 0x51DF, //CJK UNIFIED IDEOGRAPH - 0x8446: 0x51E2, //CJK UNIFIED IDEOGRAPH - 0x8447: 0x51E3, //CJK UNIFIED IDEOGRAPH - 0x8448: 0x51E5, //CJK UNIFIED IDEOGRAPH - 0x8449: 0x51E6, //CJK UNIFIED IDEOGRAPH - 0x844A: 0x51E7, //CJK UNIFIED IDEOGRAPH - 0x844B: 0x51E8, //CJK UNIFIED IDEOGRAPH - 0x844C: 0x51E9, //CJK UNIFIED IDEOGRAPH - 0x844D: 0x51EA, //CJK UNIFIED IDEOGRAPH - 0x844E: 0x51EC, //CJK UNIFIED IDEOGRAPH - 0x844F: 0x51EE, //CJK UNIFIED IDEOGRAPH - 0x8450: 0x51F1, //CJK UNIFIED IDEOGRAPH - 0x8451: 0x51F2, //CJK UNIFIED IDEOGRAPH - 0x8452: 0x51F4, //CJK UNIFIED IDEOGRAPH - 0x8453: 0x51F7, //CJK UNIFIED IDEOGRAPH - 0x8454: 0x51FE, //CJK UNIFIED IDEOGRAPH - 0x8455: 0x5204, //CJK UNIFIED IDEOGRAPH - 0x8456: 0x5205, //CJK UNIFIED IDEOGRAPH - 0x8457: 0x5209, //CJK UNIFIED IDEOGRAPH - 0x8458: 0x520B, //CJK UNIFIED IDEOGRAPH - 0x8459: 0x520C, //CJK UNIFIED IDEOGRAPH - 0x845A: 0x520F, //CJK UNIFIED IDEOGRAPH - 0x845B: 0x5210, //CJK UNIFIED IDEOGRAPH - 0x845C: 0x5213, //CJK UNIFIED IDEOGRAPH - 0x845D: 0x5214, //CJK UNIFIED IDEOGRAPH - 0x845E: 0x5215, //CJK UNIFIED IDEOGRAPH - 0x845F: 0x521C, //CJK UNIFIED IDEOGRAPH - 0x8460: 0x521E, //CJK UNIFIED IDEOGRAPH - 0x8461: 0x521F, //CJK UNIFIED IDEOGRAPH - 0x8462: 0x5221, //CJK UNIFIED IDEOGRAPH - 0x8463: 0x5222, //CJK UNIFIED IDEOGRAPH - 0x8464: 0x5223, //CJK UNIFIED IDEOGRAPH - 0x8465: 0x5225, //CJK UNIFIED IDEOGRAPH - 0x8466: 0x5226, //CJK UNIFIED IDEOGRAPH - 0x8467: 0x5227, //CJK UNIFIED IDEOGRAPH - 0x8468: 0x522A, //CJK UNIFIED IDEOGRAPH - 0x8469: 0x522C, //CJK UNIFIED IDEOGRAPH - 0x846A: 0x522F, //CJK UNIFIED IDEOGRAPH - 0x846B: 0x5231, //CJK UNIFIED IDEOGRAPH - 0x846C: 0x5232, //CJK UNIFIED IDEOGRAPH - 0x846D: 0x5234, //CJK UNIFIED IDEOGRAPH - 0x846E: 0x5235, //CJK UNIFIED IDEOGRAPH - 0x846F: 0x523C, //CJK UNIFIED IDEOGRAPH - 0x8470: 0x523E, //CJK UNIFIED IDEOGRAPH - 0x8471: 0x5244, //CJK UNIFIED IDEOGRAPH - 0x8472: 0x5245, //CJK UNIFIED IDEOGRAPH - 0x8473: 0x5246, //CJK UNIFIED IDEOGRAPH - 0x8474: 0x5247, //CJK UNIFIED IDEOGRAPH - 0x8475: 0x5248, //CJK UNIFIED IDEOGRAPH - 0x8476: 0x5249, //CJK UNIFIED IDEOGRAPH - 0x8477: 0x524B, //CJK UNIFIED IDEOGRAPH - 0x8478: 0x524E, //CJK UNIFIED IDEOGRAPH - 0x8479: 0x524F, //CJK UNIFIED IDEOGRAPH - 0x847A: 0x5252, //CJK UNIFIED IDEOGRAPH - 0x847B: 0x5253, //CJK UNIFIED IDEOGRAPH - 0x847C: 0x5255, //CJK UNIFIED IDEOGRAPH - 0x847D: 0x5257, //CJK UNIFIED IDEOGRAPH - 0x847E: 0x5258, //CJK UNIFIED IDEOGRAPH - 0x8480: 0x5259, //CJK UNIFIED IDEOGRAPH - 0x8481: 0x525A, //CJK UNIFIED IDEOGRAPH - 0x8482: 0x525B, //CJK UNIFIED IDEOGRAPH - 0x8483: 0x525D, //CJK UNIFIED IDEOGRAPH - 0x8484: 0x525F, //CJK UNIFIED IDEOGRAPH - 0x8485: 0x5260, //CJK UNIFIED IDEOGRAPH - 0x8486: 0x5262, //CJK UNIFIED IDEOGRAPH - 0x8487: 0x5263, //CJK UNIFIED IDEOGRAPH - 0x8488: 0x5264, //CJK UNIFIED IDEOGRAPH - 0x8489: 0x5266, //CJK UNIFIED IDEOGRAPH - 0x848A: 0x5268, //CJK UNIFIED IDEOGRAPH - 0x848B: 0x526B, //CJK UNIFIED IDEOGRAPH - 0x848C: 0x526C, //CJK UNIFIED IDEOGRAPH - 0x848D: 0x526D, //CJK UNIFIED IDEOGRAPH - 0x848E: 0x526E, //CJK UNIFIED IDEOGRAPH - 0x848F: 0x5270, //CJK UNIFIED IDEOGRAPH - 0x8490: 0x5271, //CJK UNIFIED IDEOGRAPH - 0x8491: 0x5273, //CJK UNIFIED IDEOGRAPH - 0x8492: 0x5274, //CJK UNIFIED IDEOGRAPH - 0x8493: 0x5275, //CJK UNIFIED IDEOGRAPH - 0x8494: 0x5276, //CJK UNIFIED IDEOGRAPH - 0x8495: 0x5277, //CJK UNIFIED IDEOGRAPH - 0x8496: 0x5278, //CJK UNIFIED IDEOGRAPH - 0x8497: 0x5279, //CJK UNIFIED IDEOGRAPH - 0x8498: 0x527A, //CJK UNIFIED IDEOGRAPH - 0x8499: 0x527B, //CJK UNIFIED IDEOGRAPH - 0x849A: 0x527C, //CJK UNIFIED IDEOGRAPH - 0x849B: 0x527E, //CJK UNIFIED IDEOGRAPH - 0x849C: 0x5280, //CJK UNIFIED IDEOGRAPH - 0x849D: 0x5283, //CJK UNIFIED IDEOGRAPH - 0x849E: 0x5284, //CJK UNIFIED IDEOGRAPH - 0x849F: 0x5285, //CJK UNIFIED IDEOGRAPH - 0x84A0: 0x5286, //CJK UNIFIED IDEOGRAPH - 0x84A1: 0x5287, //CJK UNIFIED IDEOGRAPH - 0x84A2: 0x5289, //CJK UNIFIED IDEOGRAPH - 0x84A3: 0x528A, //CJK UNIFIED IDEOGRAPH - 0x84A4: 0x528B, //CJK UNIFIED IDEOGRAPH - 0x84A5: 0x528C, //CJK UNIFIED IDEOGRAPH - 0x84A6: 0x528D, //CJK UNIFIED IDEOGRAPH - 0x84A7: 0x528E, //CJK UNIFIED IDEOGRAPH - 0x84A8: 0x528F, //CJK UNIFIED IDEOGRAPH - 0x84A9: 0x5291, //CJK UNIFIED IDEOGRAPH - 0x84AA: 0x5292, //CJK UNIFIED IDEOGRAPH - 0x84AB: 0x5294, //CJK UNIFIED IDEOGRAPH - 0x84AC: 0x5295, //CJK UNIFIED IDEOGRAPH - 0x84AD: 0x5296, //CJK UNIFIED IDEOGRAPH - 0x84AE: 0x5297, //CJK UNIFIED IDEOGRAPH - 0x84AF: 0x5298, //CJK UNIFIED IDEOGRAPH - 0x84B0: 0x5299, //CJK UNIFIED IDEOGRAPH - 0x84B1: 0x529A, //CJK UNIFIED IDEOGRAPH - 0x84B2: 0x529C, //CJK UNIFIED IDEOGRAPH - 0x84B3: 0x52A4, //CJK UNIFIED IDEOGRAPH - 0x84B4: 0x52A5, //CJK UNIFIED IDEOGRAPH - 0x84B5: 0x52A6, //CJK UNIFIED IDEOGRAPH - 0x84B6: 0x52A7, //CJK UNIFIED IDEOGRAPH - 0x84B7: 0x52AE, //CJK UNIFIED IDEOGRAPH - 0x84B8: 0x52AF, //CJK UNIFIED IDEOGRAPH - 0x84B9: 0x52B0, //CJK UNIFIED IDEOGRAPH - 0x84BA: 0x52B4, //CJK UNIFIED IDEOGRAPH - 0x84BB: 0x52B5, //CJK UNIFIED IDEOGRAPH - 0x84BC: 0x52B6, //CJK UNIFIED IDEOGRAPH - 0x84BD: 0x52B7, //CJK UNIFIED IDEOGRAPH - 0x84BE: 0x52B8, //CJK UNIFIED IDEOGRAPH - 0x84BF: 0x52B9, //CJK UNIFIED IDEOGRAPH - 0x84C0: 0x52BA, //CJK UNIFIED IDEOGRAPH - 0x84C1: 0x52BB, //CJK UNIFIED IDEOGRAPH - 0x84C2: 0x52BC, //CJK UNIFIED IDEOGRAPH - 0x84C3: 0x52BD, //CJK UNIFIED IDEOGRAPH - 0x84C4: 0x52C0, //CJK UNIFIED IDEOGRAPH - 0x84C5: 0x52C1, //CJK UNIFIED IDEOGRAPH - 0x84C6: 0x52C2, //CJK UNIFIED IDEOGRAPH - 0x84C7: 0x52C4, //CJK UNIFIED IDEOGRAPH - 0x84C8: 0x52C5, //CJK UNIFIED IDEOGRAPH - 0x84C9: 0x52C6, //CJK UNIFIED IDEOGRAPH - 0x84CA: 0x52C8, //CJK UNIFIED IDEOGRAPH - 0x84CB: 0x52CA, //CJK UNIFIED IDEOGRAPH - 0x84CC: 0x52CC, //CJK UNIFIED IDEOGRAPH - 0x84CD: 0x52CD, //CJK UNIFIED IDEOGRAPH - 0x84CE: 0x52CE, //CJK UNIFIED IDEOGRAPH - 0x84CF: 0x52CF, //CJK UNIFIED IDEOGRAPH - 0x84D0: 0x52D1, //CJK UNIFIED IDEOGRAPH - 0x84D1: 0x52D3, //CJK UNIFIED IDEOGRAPH - 0x84D2: 0x52D4, //CJK UNIFIED IDEOGRAPH - 0x84D3: 0x52D5, //CJK UNIFIED IDEOGRAPH - 0x84D4: 0x52D7, //CJK UNIFIED IDEOGRAPH - 0x84D5: 0x52D9, //CJK UNIFIED IDEOGRAPH - 0x84D6: 0x52DA, //CJK UNIFIED IDEOGRAPH - 0x84D7: 0x52DB, //CJK UNIFIED IDEOGRAPH - 0x84D8: 0x52DC, //CJK UNIFIED IDEOGRAPH - 0x84D9: 0x52DD, //CJK UNIFIED IDEOGRAPH - 0x84DA: 0x52DE, //CJK UNIFIED IDEOGRAPH - 0x84DB: 0x52E0, //CJK UNIFIED IDEOGRAPH - 0x84DC: 0x52E1, //CJK UNIFIED IDEOGRAPH - 0x84DD: 0x52E2, //CJK UNIFIED IDEOGRAPH - 0x84DE: 0x52E3, //CJK UNIFIED IDEOGRAPH - 0x84DF: 0x52E5, //CJK UNIFIED IDEOGRAPH - 0x84E0: 0x52E6, //CJK UNIFIED IDEOGRAPH - 0x84E1: 0x52E7, //CJK UNIFIED IDEOGRAPH - 0x84E2: 0x52E8, //CJK UNIFIED IDEOGRAPH - 0x84E3: 0x52E9, //CJK UNIFIED IDEOGRAPH - 0x84E4: 0x52EA, //CJK UNIFIED IDEOGRAPH - 0x84E5: 0x52EB, //CJK UNIFIED IDEOGRAPH - 0x84E6: 0x52EC, //CJK UNIFIED IDEOGRAPH - 0x84E7: 0x52ED, //CJK UNIFIED IDEOGRAPH - 0x84E8: 0x52EE, //CJK UNIFIED IDEOGRAPH - 0x84E9: 0x52EF, //CJK UNIFIED IDEOGRAPH - 0x84EA: 0x52F1, //CJK UNIFIED IDEOGRAPH - 0x84EB: 0x52F2, //CJK UNIFIED IDEOGRAPH - 0x84EC: 0x52F3, //CJK UNIFIED IDEOGRAPH - 0x84ED: 0x52F4, //CJK UNIFIED IDEOGRAPH - 0x84EE: 0x52F5, //CJK UNIFIED IDEOGRAPH - 0x84EF: 0x52F6, //CJK UNIFIED IDEOGRAPH - 0x84F0: 0x52F7, //CJK UNIFIED IDEOGRAPH - 0x84F1: 0x52F8, //CJK UNIFIED IDEOGRAPH - 0x84F2: 0x52FB, //CJK UNIFIED IDEOGRAPH - 0x84F3: 0x52FC, //CJK UNIFIED IDEOGRAPH - 0x84F4: 0x52FD, //CJK UNIFIED IDEOGRAPH - 0x84F5: 0x5301, //CJK UNIFIED IDEOGRAPH - 0x84F6: 0x5302, //CJK UNIFIED IDEOGRAPH - 0x84F7: 0x5303, //CJK UNIFIED IDEOGRAPH - 0x84F8: 0x5304, //CJK UNIFIED IDEOGRAPH - 0x84F9: 0x5307, //CJK UNIFIED IDEOGRAPH - 0x84FA: 0x5309, //CJK UNIFIED IDEOGRAPH - 0x84FB: 0x530A, //CJK UNIFIED IDEOGRAPH - 0x84FC: 0x530B, //CJK UNIFIED IDEOGRAPH - 0x84FD: 0x530C, //CJK UNIFIED IDEOGRAPH - 0x84FE: 0x530E, //CJK UNIFIED IDEOGRAPH - 0x8540: 0x5311, //CJK UNIFIED IDEOGRAPH - 0x8541: 0x5312, //CJK UNIFIED IDEOGRAPH - 0x8542: 0x5313, //CJK UNIFIED IDEOGRAPH - 0x8543: 0x5314, //CJK UNIFIED IDEOGRAPH - 0x8544: 0x5318, //CJK UNIFIED IDEOGRAPH - 0x8545: 0x531B, //CJK UNIFIED IDEOGRAPH - 0x8546: 0x531C, //CJK UNIFIED IDEOGRAPH - 0x8547: 0x531E, //CJK UNIFIED IDEOGRAPH - 0x8548: 0x531F, //CJK UNIFIED IDEOGRAPH - 0x8549: 0x5322, //CJK UNIFIED IDEOGRAPH - 0x854A: 0x5324, //CJK UNIFIED IDEOGRAPH - 0x854B: 0x5325, //CJK UNIFIED IDEOGRAPH - 0x854C: 0x5327, //CJK UNIFIED IDEOGRAPH - 0x854D: 0x5328, //CJK UNIFIED IDEOGRAPH - 0x854E: 0x5329, //CJK UNIFIED IDEOGRAPH - 0x854F: 0x532B, //CJK UNIFIED IDEOGRAPH - 0x8550: 0x532C, //CJK UNIFIED IDEOGRAPH - 0x8551: 0x532D, //CJK UNIFIED IDEOGRAPH - 0x8552: 0x532F, //CJK UNIFIED IDEOGRAPH - 0x8553: 0x5330, //CJK UNIFIED IDEOGRAPH - 0x8554: 0x5331, //CJK UNIFIED IDEOGRAPH - 0x8555: 0x5332, //CJK UNIFIED IDEOGRAPH - 0x8556: 0x5333, //CJK UNIFIED IDEOGRAPH - 0x8557: 0x5334, //CJK UNIFIED IDEOGRAPH - 0x8558: 0x5335, //CJK UNIFIED IDEOGRAPH - 0x8559: 0x5336, //CJK UNIFIED IDEOGRAPH - 0x855A: 0x5337, //CJK UNIFIED IDEOGRAPH - 0x855B: 0x5338, //CJK UNIFIED IDEOGRAPH - 0x855C: 0x533C, //CJK UNIFIED IDEOGRAPH - 0x855D: 0x533D, //CJK UNIFIED IDEOGRAPH - 0x855E: 0x5340, //CJK UNIFIED IDEOGRAPH - 0x855F: 0x5342, //CJK UNIFIED IDEOGRAPH - 0x8560: 0x5344, //CJK UNIFIED IDEOGRAPH - 0x8561: 0x5346, //CJK UNIFIED IDEOGRAPH - 0x8562: 0x534B, //CJK UNIFIED IDEOGRAPH - 0x8563: 0x534C, //CJK UNIFIED IDEOGRAPH - 0x8564: 0x534D, //CJK UNIFIED IDEOGRAPH - 0x8565: 0x5350, //CJK UNIFIED IDEOGRAPH - 0x8566: 0x5354, //CJK UNIFIED IDEOGRAPH - 0x8567: 0x5358, //CJK UNIFIED IDEOGRAPH - 0x8568: 0x5359, //CJK UNIFIED IDEOGRAPH - 0x8569: 0x535B, //CJK UNIFIED IDEOGRAPH - 0x856A: 0x535D, //CJK UNIFIED IDEOGRAPH - 0x856B: 0x5365, //CJK UNIFIED IDEOGRAPH - 0x856C: 0x5368, //CJK UNIFIED IDEOGRAPH - 0x856D: 0x536A, //CJK UNIFIED IDEOGRAPH - 0x856E: 0x536C, //CJK UNIFIED IDEOGRAPH - 0x856F: 0x536D, //CJK UNIFIED IDEOGRAPH - 0x8570: 0x5372, //CJK UNIFIED IDEOGRAPH - 0x8571: 0x5376, //CJK UNIFIED IDEOGRAPH - 0x8572: 0x5379, //CJK UNIFIED IDEOGRAPH - 0x8573: 0x537B, //CJK UNIFIED IDEOGRAPH - 0x8574: 0x537C, //CJK UNIFIED IDEOGRAPH - 0x8575: 0x537D, //CJK UNIFIED IDEOGRAPH - 0x8576: 0x537E, //CJK UNIFIED IDEOGRAPH - 0x8577: 0x5380, //CJK UNIFIED IDEOGRAPH - 0x8578: 0x5381, //CJK UNIFIED IDEOGRAPH - 0x8579: 0x5383, //CJK UNIFIED IDEOGRAPH - 0x857A: 0x5387, //CJK UNIFIED IDEOGRAPH - 0x857B: 0x5388, //CJK UNIFIED IDEOGRAPH - 0x857C: 0x538A, //CJK UNIFIED IDEOGRAPH - 0x857D: 0x538E, //CJK UNIFIED IDEOGRAPH - 0x857E: 0x538F, //CJK UNIFIED IDEOGRAPH - 0x8580: 0x5390, //CJK UNIFIED IDEOGRAPH - 0x8581: 0x5391, //CJK UNIFIED IDEOGRAPH - 0x8582: 0x5392, //CJK UNIFIED IDEOGRAPH - 0x8583: 0x5393, //CJK UNIFIED IDEOGRAPH - 0x8584: 0x5394, //CJK UNIFIED IDEOGRAPH - 0x8585: 0x5396, //CJK UNIFIED IDEOGRAPH - 0x8586: 0x5397, //CJK UNIFIED IDEOGRAPH - 0x8587: 0x5399, //CJK UNIFIED IDEOGRAPH - 0x8588: 0x539B, //CJK UNIFIED IDEOGRAPH - 0x8589: 0x539C, //CJK UNIFIED IDEOGRAPH - 0x858A: 0x539E, //CJK UNIFIED IDEOGRAPH - 0x858B: 0x53A0, //CJK UNIFIED IDEOGRAPH - 0x858C: 0x53A1, //CJK UNIFIED IDEOGRAPH - 0x858D: 0x53A4, //CJK UNIFIED IDEOGRAPH - 0x858E: 0x53A7, //CJK UNIFIED IDEOGRAPH - 0x858F: 0x53AA, //CJK UNIFIED IDEOGRAPH - 0x8590: 0x53AB, //CJK UNIFIED IDEOGRAPH - 0x8591: 0x53AC, //CJK UNIFIED IDEOGRAPH - 0x8592: 0x53AD, //CJK UNIFIED IDEOGRAPH - 0x8593: 0x53AF, //CJK UNIFIED IDEOGRAPH - 0x8594: 0x53B0, //CJK UNIFIED IDEOGRAPH - 0x8595: 0x53B1, //CJK UNIFIED IDEOGRAPH - 0x8596: 0x53B2, //CJK UNIFIED IDEOGRAPH - 0x8597: 0x53B3, //CJK UNIFIED IDEOGRAPH - 0x8598: 0x53B4, //CJK UNIFIED IDEOGRAPH - 0x8599: 0x53B5, //CJK UNIFIED IDEOGRAPH - 0x859A: 0x53B7, //CJK UNIFIED IDEOGRAPH - 0x859B: 0x53B8, //CJK UNIFIED IDEOGRAPH - 0x859C: 0x53B9, //CJK UNIFIED IDEOGRAPH - 0x859D: 0x53BA, //CJK UNIFIED IDEOGRAPH - 0x859E: 0x53BC, //CJK UNIFIED IDEOGRAPH - 0x859F: 0x53BD, //CJK UNIFIED IDEOGRAPH - 0x85A0: 0x53BE, //CJK UNIFIED IDEOGRAPH - 0x85A1: 0x53C0, //CJK UNIFIED IDEOGRAPH - 0x85A2: 0x53C3, //CJK UNIFIED IDEOGRAPH - 0x85A3: 0x53C4, //CJK UNIFIED IDEOGRAPH - 0x85A4: 0x53C5, //CJK UNIFIED IDEOGRAPH - 0x85A5: 0x53C6, //CJK UNIFIED IDEOGRAPH - 0x85A6: 0x53C7, //CJK UNIFIED IDEOGRAPH - 0x85A7: 0x53CE, //CJK UNIFIED IDEOGRAPH - 0x85A8: 0x53CF, //CJK UNIFIED IDEOGRAPH - 0x85A9: 0x53D0, //CJK UNIFIED IDEOGRAPH - 0x85AA: 0x53D2, //CJK UNIFIED IDEOGRAPH - 0x85AB: 0x53D3, //CJK UNIFIED IDEOGRAPH - 0x85AC: 0x53D5, //CJK UNIFIED IDEOGRAPH - 0x85AD: 0x53DA, //CJK UNIFIED IDEOGRAPH - 0x85AE: 0x53DC, //CJK UNIFIED IDEOGRAPH - 0x85AF: 0x53DD, //CJK UNIFIED IDEOGRAPH - 0x85B0: 0x53DE, //CJK UNIFIED IDEOGRAPH - 0x85B1: 0x53E1, //CJK UNIFIED IDEOGRAPH - 0x85B2: 0x53E2, //CJK UNIFIED IDEOGRAPH - 0x85B3: 0x53E7, //CJK UNIFIED IDEOGRAPH - 0x85B4: 0x53F4, //CJK UNIFIED IDEOGRAPH - 0x85B5: 0x53FA, //CJK UNIFIED IDEOGRAPH - 0x85B6: 0x53FE, //CJK UNIFIED IDEOGRAPH - 0x85B7: 0x53FF, //CJK UNIFIED IDEOGRAPH - 0x85B8: 0x5400, //CJK UNIFIED IDEOGRAPH - 0x85B9: 0x5402, //CJK UNIFIED IDEOGRAPH - 0x85BA: 0x5405, //CJK UNIFIED IDEOGRAPH - 0x85BB: 0x5407, //CJK UNIFIED IDEOGRAPH - 0x85BC: 0x540B, //CJK UNIFIED IDEOGRAPH - 0x85BD: 0x5414, //CJK UNIFIED IDEOGRAPH - 0x85BE: 0x5418, //CJK UNIFIED IDEOGRAPH - 0x85BF: 0x5419, //CJK UNIFIED IDEOGRAPH - 0x85C0: 0x541A, //CJK UNIFIED IDEOGRAPH - 0x85C1: 0x541C, //CJK UNIFIED IDEOGRAPH - 0x85C2: 0x5422, //CJK UNIFIED IDEOGRAPH - 0x85C3: 0x5424, //CJK UNIFIED IDEOGRAPH - 0x85C4: 0x5425, //CJK UNIFIED IDEOGRAPH - 0x85C5: 0x542A, //CJK UNIFIED IDEOGRAPH - 0x85C6: 0x5430, //CJK UNIFIED IDEOGRAPH - 0x85C7: 0x5433, //CJK UNIFIED IDEOGRAPH - 0x85C8: 0x5436, //CJK UNIFIED IDEOGRAPH - 0x85C9: 0x5437, //CJK UNIFIED IDEOGRAPH - 0x85CA: 0x543A, //CJK UNIFIED IDEOGRAPH - 0x85CB: 0x543D, //CJK UNIFIED IDEOGRAPH - 0x85CC: 0x543F, //CJK UNIFIED IDEOGRAPH - 0x85CD: 0x5441, //CJK UNIFIED IDEOGRAPH - 0x85CE: 0x5442, //CJK UNIFIED IDEOGRAPH - 0x85CF: 0x5444, //CJK UNIFIED IDEOGRAPH - 0x85D0: 0x5445, //CJK UNIFIED IDEOGRAPH - 0x85D1: 0x5447, //CJK UNIFIED IDEOGRAPH - 0x85D2: 0x5449, //CJK UNIFIED IDEOGRAPH - 0x85D3: 0x544C, //CJK UNIFIED IDEOGRAPH - 0x85D4: 0x544D, //CJK UNIFIED IDEOGRAPH - 0x85D5: 0x544E, //CJK UNIFIED IDEOGRAPH - 0x85D6: 0x544F, //CJK UNIFIED IDEOGRAPH - 0x85D7: 0x5451, //CJK UNIFIED IDEOGRAPH - 0x85D8: 0x545A, //CJK UNIFIED IDEOGRAPH - 0x85D9: 0x545D, //CJK UNIFIED IDEOGRAPH - 0x85DA: 0x545E, //CJK UNIFIED IDEOGRAPH - 0x85DB: 0x545F, //CJK UNIFIED IDEOGRAPH - 0x85DC: 0x5460, //CJK UNIFIED IDEOGRAPH - 0x85DD: 0x5461, //CJK UNIFIED IDEOGRAPH - 0x85DE: 0x5463, //CJK UNIFIED IDEOGRAPH - 0x85DF: 0x5465, //CJK UNIFIED IDEOGRAPH - 0x85E0: 0x5467, //CJK UNIFIED IDEOGRAPH - 0x85E1: 0x5469, //CJK UNIFIED IDEOGRAPH - 0x85E2: 0x546A, //CJK UNIFIED IDEOGRAPH - 0x85E3: 0x546B, //CJK UNIFIED IDEOGRAPH - 0x85E4: 0x546C, //CJK UNIFIED IDEOGRAPH - 0x85E5: 0x546D, //CJK UNIFIED IDEOGRAPH - 0x85E6: 0x546E, //CJK UNIFIED IDEOGRAPH - 0x85E7: 0x546F, //CJK UNIFIED IDEOGRAPH - 0x85E8: 0x5470, //CJK UNIFIED IDEOGRAPH - 0x85E9: 0x5474, //CJK UNIFIED IDEOGRAPH - 0x85EA: 0x5479, //CJK UNIFIED IDEOGRAPH - 0x85EB: 0x547A, //CJK UNIFIED IDEOGRAPH - 0x85EC: 0x547E, //CJK UNIFIED IDEOGRAPH - 0x85ED: 0x547F, //CJK UNIFIED IDEOGRAPH - 0x85EE: 0x5481, //CJK UNIFIED IDEOGRAPH - 0x85EF: 0x5483, //CJK UNIFIED IDEOGRAPH - 0x85F0: 0x5485, //CJK UNIFIED IDEOGRAPH - 0x85F1: 0x5487, //CJK UNIFIED IDEOGRAPH - 0x85F2: 0x5488, //CJK UNIFIED IDEOGRAPH - 0x85F3: 0x5489, //CJK UNIFIED IDEOGRAPH - 0x85F4: 0x548A, //CJK UNIFIED IDEOGRAPH - 0x85F5: 0x548D, //CJK UNIFIED IDEOGRAPH - 0x85F6: 0x5491, //CJK UNIFIED IDEOGRAPH - 0x85F7: 0x5493, //CJK UNIFIED IDEOGRAPH - 0x85F8: 0x5497, //CJK UNIFIED IDEOGRAPH - 0x85F9: 0x5498, //CJK UNIFIED IDEOGRAPH - 0x85FA: 0x549C, //CJK UNIFIED IDEOGRAPH - 0x85FB: 0x549E, //CJK UNIFIED IDEOGRAPH - 0x85FC: 0x549F, //CJK UNIFIED IDEOGRAPH - 0x85FD: 0x54A0, //CJK UNIFIED IDEOGRAPH - 0x85FE: 0x54A1, //CJK UNIFIED IDEOGRAPH - 0x8640: 0x54A2, //CJK UNIFIED IDEOGRAPH - 0x8641: 0x54A5, //CJK UNIFIED IDEOGRAPH - 0x8642: 0x54AE, //CJK UNIFIED IDEOGRAPH - 0x8643: 0x54B0, //CJK UNIFIED IDEOGRAPH - 0x8644: 0x54B2, //CJK UNIFIED IDEOGRAPH - 0x8645: 0x54B5, //CJK UNIFIED IDEOGRAPH - 0x8646: 0x54B6, //CJK UNIFIED IDEOGRAPH - 0x8647: 0x54B7, //CJK UNIFIED IDEOGRAPH - 0x8648: 0x54B9, //CJK UNIFIED IDEOGRAPH - 0x8649: 0x54BA, //CJK UNIFIED IDEOGRAPH - 0x864A: 0x54BC, //CJK UNIFIED IDEOGRAPH - 0x864B: 0x54BE, //CJK UNIFIED IDEOGRAPH - 0x864C: 0x54C3, //CJK UNIFIED IDEOGRAPH - 0x864D: 0x54C5, //CJK UNIFIED IDEOGRAPH - 0x864E: 0x54CA, //CJK UNIFIED IDEOGRAPH - 0x864F: 0x54CB, //CJK UNIFIED IDEOGRAPH - 0x8650: 0x54D6, //CJK UNIFIED IDEOGRAPH - 0x8651: 0x54D8, //CJK UNIFIED IDEOGRAPH - 0x8652: 0x54DB, //CJK UNIFIED IDEOGRAPH - 0x8653: 0x54E0, //CJK UNIFIED IDEOGRAPH - 0x8654: 0x54E1, //CJK UNIFIED IDEOGRAPH - 0x8655: 0x54E2, //CJK UNIFIED IDEOGRAPH - 0x8656: 0x54E3, //CJK UNIFIED IDEOGRAPH - 0x8657: 0x54E4, //CJK UNIFIED IDEOGRAPH - 0x8658: 0x54EB, //CJK UNIFIED IDEOGRAPH - 0x8659: 0x54EC, //CJK UNIFIED IDEOGRAPH - 0x865A: 0x54EF, //CJK UNIFIED IDEOGRAPH - 0x865B: 0x54F0, //CJK UNIFIED IDEOGRAPH - 0x865C: 0x54F1, //CJK UNIFIED IDEOGRAPH - 0x865D: 0x54F4, //CJK UNIFIED IDEOGRAPH - 0x865E: 0x54F5, //CJK UNIFIED IDEOGRAPH - 0x865F: 0x54F6, //CJK UNIFIED IDEOGRAPH - 0x8660: 0x54F7, //CJK UNIFIED IDEOGRAPH - 0x8661: 0x54F8, //CJK UNIFIED IDEOGRAPH - 0x8662: 0x54F9, //CJK UNIFIED IDEOGRAPH - 0x8663: 0x54FB, //CJK UNIFIED IDEOGRAPH - 0x8664: 0x54FE, //CJK UNIFIED IDEOGRAPH - 0x8665: 0x5500, //CJK UNIFIED IDEOGRAPH - 0x8666: 0x5502, //CJK UNIFIED IDEOGRAPH - 0x8667: 0x5503, //CJK UNIFIED IDEOGRAPH - 0x8668: 0x5504, //CJK UNIFIED IDEOGRAPH - 0x8669: 0x5505, //CJK UNIFIED IDEOGRAPH - 0x866A: 0x5508, //CJK UNIFIED IDEOGRAPH - 0x866B: 0x550A, //CJK UNIFIED IDEOGRAPH - 0x866C: 0x550B, //CJK UNIFIED IDEOGRAPH - 0x866D: 0x550C, //CJK UNIFIED IDEOGRAPH - 0x866E: 0x550D, //CJK UNIFIED IDEOGRAPH - 0x866F: 0x550E, //CJK UNIFIED IDEOGRAPH - 0x8670: 0x5512, //CJK UNIFIED IDEOGRAPH - 0x8671: 0x5513, //CJK UNIFIED IDEOGRAPH - 0x8672: 0x5515, //CJK UNIFIED IDEOGRAPH - 0x8673: 0x5516, //CJK UNIFIED IDEOGRAPH - 0x8674: 0x5517, //CJK UNIFIED IDEOGRAPH - 0x8675: 0x5518, //CJK UNIFIED IDEOGRAPH - 0x8676: 0x5519, //CJK UNIFIED IDEOGRAPH - 0x8677: 0x551A, //CJK UNIFIED IDEOGRAPH - 0x8678: 0x551C, //CJK UNIFIED IDEOGRAPH - 0x8679: 0x551D, //CJK UNIFIED IDEOGRAPH - 0x867A: 0x551E, //CJK UNIFIED IDEOGRAPH - 0x867B: 0x551F, //CJK UNIFIED IDEOGRAPH - 0x867C: 0x5521, //CJK UNIFIED IDEOGRAPH - 0x867D: 0x5525, //CJK UNIFIED IDEOGRAPH - 0x867E: 0x5526, //CJK UNIFIED IDEOGRAPH - 0x8680: 0x5528, //CJK UNIFIED IDEOGRAPH - 0x8681: 0x5529, //CJK UNIFIED IDEOGRAPH - 0x8682: 0x552B, //CJK UNIFIED IDEOGRAPH - 0x8683: 0x552D, //CJK UNIFIED IDEOGRAPH - 0x8684: 0x5532, //CJK UNIFIED IDEOGRAPH - 0x8685: 0x5534, //CJK UNIFIED IDEOGRAPH - 0x8686: 0x5535, //CJK UNIFIED IDEOGRAPH - 0x8687: 0x5536, //CJK UNIFIED IDEOGRAPH - 0x8688: 0x5538, //CJK UNIFIED IDEOGRAPH - 0x8689: 0x5539, //CJK UNIFIED IDEOGRAPH - 0x868A: 0x553A, //CJK UNIFIED IDEOGRAPH - 0x868B: 0x553B, //CJK UNIFIED IDEOGRAPH - 0x868C: 0x553D, //CJK UNIFIED IDEOGRAPH - 0x868D: 0x5540, //CJK UNIFIED IDEOGRAPH - 0x868E: 0x5542, //CJK UNIFIED IDEOGRAPH - 0x868F: 0x5545, //CJK UNIFIED IDEOGRAPH - 0x8690: 0x5547, //CJK UNIFIED IDEOGRAPH - 0x8691: 0x5548, //CJK UNIFIED IDEOGRAPH - 0x8692: 0x554B, //CJK UNIFIED IDEOGRAPH - 0x8693: 0x554C, //CJK UNIFIED IDEOGRAPH - 0x8694: 0x554D, //CJK UNIFIED IDEOGRAPH - 0x8695: 0x554E, //CJK UNIFIED IDEOGRAPH - 0x8696: 0x554F, //CJK UNIFIED IDEOGRAPH - 0x8697: 0x5551, //CJK UNIFIED IDEOGRAPH - 0x8698: 0x5552, //CJK UNIFIED IDEOGRAPH - 0x8699: 0x5553, //CJK UNIFIED IDEOGRAPH - 0x869A: 0x5554, //CJK UNIFIED IDEOGRAPH - 0x869B: 0x5557, //CJK UNIFIED IDEOGRAPH - 0x869C: 0x5558, //CJK UNIFIED IDEOGRAPH - 0x869D: 0x5559, //CJK UNIFIED IDEOGRAPH - 0x869E: 0x555A, //CJK UNIFIED IDEOGRAPH - 0x869F: 0x555B, //CJK UNIFIED IDEOGRAPH - 0x86A0: 0x555D, //CJK UNIFIED IDEOGRAPH - 0x86A1: 0x555E, //CJK UNIFIED IDEOGRAPH - 0x86A2: 0x555F, //CJK UNIFIED IDEOGRAPH - 0x86A3: 0x5560, //CJK UNIFIED IDEOGRAPH - 0x86A4: 0x5562, //CJK UNIFIED IDEOGRAPH - 0x86A5: 0x5563, //CJK UNIFIED IDEOGRAPH - 0x86A6: 0x5568, //CJK UNIFIED IDEOGRAPH - 0x86A7: 0x5569, //CJK UNIFIED IDEOGRAPH - 0x86A8: 0x556B, //CJK UNIFIED IDEOGRAPH - 0x86A9: 0x556F, //CJK UNIFIED IDEOGRAPH - 0x86AA: 0x5570, //CJK UNIFIED IDEOGRAPH - 0x86AB: 0x5571, //CJK UNIFIED IDEOGRAPH - 0x86AC: 0x5572, //CJK UNIFIED IDEOGRAPH - 0x86AD: 0x5573, //CJK UNIFIED IDEOGRAPH - 0x86AE: 0x5574, //CJK UNIFIED IDEOGRAPH - 0x86AF: 0x5579, //CJK UNIFIED IDEOGRAPH - 0x86B0: 0x557A, //CJK UNIFIED IDEOGRAPH - 0x86B1: 0x557D, //CJK UNIFIED IDEOGRAPH - 0x86B2: 0x557F, //CJK UNIFIED IDEOGRAPH - 0x86B3: 0x5585, //CJK UNIFIED IDEOGRAPH - 0x86B4: 0x5586, //CJK UNIFIED IDEOGRAPH - 0x86B5: 0x558C, //CJK UNIFIED IDEOGRAPH - 0x86B6: 0x558D, //CJK UNIFIED IDEOGRAPH - 0x86B7: 0x558E, //CJK UNIFIED IDEOGRAPH - 0x86B8: 0x5590, //CJK UNIFIED IDEOGRAPH - 0x86B9: 0x5592, //CJK UNIFIED IDEOGRAPH - 0x86BA: 0x5593, //CJK UNIFIED IDEOGRAPH - 0x86BB: 0x5595, //CJK UNIFIED IDEOGRAPH - 0x86BC: 0x5596, //CJK UNIFIED IDEOGRAPH - 0x86BD: 0x5597, //CJK UNIFIED IDEOGRAPH - 0x86BE: 0x559A, //CJK UNIFIED IDEOGRAPH - 0x86BF: 0x559B, //CJK UNIFIED IDEOGRAPH - 0x86C0: 0x559E, //CJK UNIFIED IDEOGRAPH - 0x86C1: 0x55A0, //CJK UNIFIED IDEOGRAPH - 0x86C2: 0x55A1, //CJK UNIFIED IDEOGRAPH - 0x86C3: 0x55A2, //CJK UNIFIED IDEOGRAPH - 0x86C4: 0x55A3, //CJK UNIFIED IDEOGRAPH - 0x86C5: 0x55A4, //CJK UNIFIED IDEOGRAPH - 0x86C6: 0x55A5, //CJK UNIFIED IDEOGRAPH - 0x86C7: 0x55A6, //CJK UNIFIED IDEOGRAPH - 0x86C8: 0x55A8, //CJK UNIFIED IDEOGRAPH - 0x86C9: 0x55A9, //CJK UNIFIED IDEOGRAPH - 0x86CA: 0x55AA, //CJK UNIFIED IDEOGRAPH - 0x86CB: 0x55AB, //CJK UNIFIED IDEOGRAPH - 0x86CC: 0x55AC, //CJK UNIFIED IDEOGRAPH - 0x86CD: 0x55AD, //CJK UNIFIED IDEOGRAPH - 0x86CE: 0x55AE, //CJK UNIFIED IDEOGRAPH - 0x86CF: 0x55AF, //CJK UNIFIED IDEOGRAPH - 0x86D0: 0x55B0, //CJK UNIFIED IDEOGRAPH - 0x86D1: 0x55B2, //CJK UNIFIED IDEOGRAPH - 0x86D2: 0x55B4, //CJK UNIFIED IDEOGRAPH - 0x86D3: 0x55B6, //CJK UNIFIED IDEOGRAPH - 0x86D4: 0x55B8, //CJK UNIFIED IDEOGRAPH - 0x86D5: 0x55BA, //CJK UNIFIED IDEOGRAPH - 0x86D6: 0x55BC, //CJK UNIFIED IDEOGRAPH - 0x86D7: 0x55BF, //CJK UNIFIED IDEOGRAPH - 0x86D8: 0x55C0, //CJK UNIFIED IDEOGRAPH - 0x86D9: 0x55C1, //CJK UNIFIED IDEOGRAPH - 0x86DA: 0x55C2, //CJK UNIFIED IDEOGRAPH - 0x86DB: 0x55C3, //CJK UNIFIED IDEOGRAPH - 0x86DC: 0x55C6, //CJK UNIFIED IDEOGRAPH - 0x86DD: 0x55C7, //CJK UNIFIED IDEOGRAPH - 0x86DE: 0x55C8, //CJK UNIFIED IDEOGRAPH - 0x86DF: 0x55CA, //CJK UNIFIED IDEOGRAPH - 0x86E0: 0x55CB, //CJK UNIFIED IDEOGRAPH - 0x86E1: 0x55CE, //CJK UNIFIED IDEOGRAPH - 0x86E2: 0x55CF, //CJK UNIFIED IDEOGRAPH - 0x86E3: 0x55D0, //CJK UNIFIED IDEOGRAPH - 0x86E4: 0x55D5, //CJK UNIFIED IDEOGRAPH - 0x86E5: 0x55D7, //CJK UNIFIED IDEOGRAPH - 0x86E6: 0x55D8, //CJK UNIFIED IDEOGRAPH - 0x86E7: 0x55D9, //CJK UNIFIED IDEOGRAPH - 0x86E8: 0x55DA, //CJK UNIFIED IDEOGRAPH - 0x86E9: 0x55DB, //CJK UNIFIED IDEOGRAPH - 0x86EA: 0x55DE, //CJK UNIFIED IDEOGRAPH - 0x86EB: 0x55E0, //CJK UNIFIED IDEOGRAPH - 0x86EC: 0x55E2, //CJK UNIFIED IDEOGRAPH - 0x86ED: 0x55E7, //CJK UNIFIED IDEOGRAPH - 0x86EE: 0x55E9, //CJK UNIFIED IDEOGRAPH - 0x86EF: 0x55ED, //CJK UNIFIED IDEOGRAPH - 0x86F0: 0x55EE, //CJK UNIFIED IDEOGRAPH - 0x86F1: 0x55F0, //CJK UNIFIED IDEOGRAPH - 0x86F2: 0x55F1, //CJK UNIFIED IDEOGRAPH - 0x86F3: 0x55F4, //CJK UNIFIED IDEOGRAPH - 0x86F4: 0x55F6, //CJK UNIFIED IDEOGRAPH - 0x86F5: 0x55F8, //CJK UNIFIED IDEOGRAPH - 0x86F6: 0x55F9, //CJK UNIFIED IDEOGRAPH - 0x86F7: 0x55FA, //CJK UNIFIED IDEOGRAPH - 0x86F8: 0x55FB, //CJK UNIFIED IDEOGRAPH - 0x86F9: 0x55FC, //CJK UNIFIED IDEOGRAPH - 0x86FA: 0x55FF, //CJK UNIFIED IDEOGRAPH - 0x86FB: 0x5602, //CJK UNIFIED IDEOGRAPH - 0x86FC: 0x5603, //CJK UNIFIED IDEOGRAPH - 0x86FD: 0x5604, //CJK UNIFIED IDEOGRAPH - 0x86FE: 0x5605, //CJK UNIFIED IDEOGRAPH - 0x8740: 0x5606, //CJK UNIFIED IDEOGRAPH - 0x8741: 0x5607, //CJK UNIFIED IDEOGRAPH - 0x8742: 0x560A, //CJK UNIFIED IDEOGRAPH - 0x8743: 0x560B, //CJK UNIFIED IDEOGRAPH - 0x8744: 0x560D, //CJK UNIFIED IDEOGRAPH - 0x8745: 0x5610, //CJK UNIFIED IDEOGRAPH - 0x8746: 0x5611, //CJK UNIFIED IDEOGRAPH - 0x8747: 0x5612, //CJK UNIFIED IDEOGRAPH - 0x8748: 0x5613, //CJK UNIFIED IDEOGRAPH - 0x8749: 0x5614, //CJK UNIFIED IDEOGRAPH - 0x874A: 0x5615, //CJK UNIFIED IDEOGRAPH - 0x874B: 0x5616, //CJK UNIFIED IDEOGRAPH - 0x874C: 0x5617, //CJK UNIFIED IDEOGRAPH - 0x874D: 0x5619, //CJK UNIFIED IDEOGRAPH - 0x874E: 0x561A, //CJK UNIFIED IDEOGRAPH - 0x874F: 0x561C, //CJK UNIFIED IDEOGRAPH - 0x8750: 0x561D, //CJK UNIFIED IDEOGRAPH - 0x8751: 0x5620, //CJK UNIFIED IDEOGRAPH - 0x8752: 0x5621, //CJK UNIFIED IDEOGRAPH - 0x8753: 0x5622, //CJK UNIFIED IDEOGRAPH - 0x8754: 0x5625, //CJK UNIFIED IDEOGRAPH - 0x8755: 0x5626, //CJK UNIFIED IDEOGRAPH - 0x8756: 0x5628, //CJK UNIFIED IDEOGRAPH - 0x8757: 0x5629, //CJK UNIFIED IDEOGRAPH - 0x8758: 0x562A, //CJK UNIFIED IDEOGRAPH - 0x8759: 0x562B, //CJK UNIFIED IDEOGRAPH - 0x875A: 0x562E, //CJK UNIFIED IDEOGRAPH - 0x875B: 0x562F, //CJK UNIFIED IDEOGRAPH - 0x875C: 0x5630, //CJK UNIFIED IDEOGRAPH - 0x875D: 0x5633, //CJK UNIFIED IDEOGRAPH - 0x875E: 0x5635, //CJK UNIFIED IDEOGRAPH - 0x875F: 0x5637, //CJK UNIFIED IDEOGRAPH - 0x8760: 0x5638, //CJK UNIFIED IDEOGRAPH - 0x8761: 0x563A, //CJK UNIFIED IDEOGRAPH - 0x8762: 0x563C, //CJK UNIFIED IDEOGRAPH - 0x8763: 0x563D, //CJK UNIFIED IDEOGRAPH - 0x8764: 0x563E, //CJK UNIFIED IDEOGRAPH - 0x8765: 0x5640, //CJK UNIFIED IDEOGRAPH - 0x8766: 0x5641, //CJK UNIFIED IDEOGRAPH - 0x8767: 0x5642, //CJK UNIFIED IDEOGRAPH - 0x8768: 0x5643, //CJK UNIFIED IDEOGRAPH - 0x8769: 0x5644, //CJK UNIFIED IDEOGRAPH - 0x876A: 0x5645, //CJK UNIFIED IDEOGRAPH - 0x876B: 0x5646, //CJK UNIFIED IDEOGRAPH - 0x876C: 0x5647, //CJK UNIFIED IDEOGRAPH - 0x876D: 0x5648, //CJK UNIFIED IDEOGRAPH - 0x876E: 0x5649, //CJK UNIFIED IDEOGRAPH - 0x876F: 0x564A, //CJK UNIFIED IDEOGRAPH - 0x8770: 0x564B, //CJK UNIFIED IDEOGRAPH - 0x8771: 0x564F, //CJK UNIFIED IDEOGRAPH - 0x8772: 0x5650, //CJK UNIFIED IDEOGRAPH - 0x8773: 0x5651, //CJK UNIFIED IDEOGRAPH - 0x8774: 0x5652, //CJK UNIFIED IDEOGRAPH - 0x8775: 0x5653, //CJK UNIFIED IDEOGRAPH - 0x8776: 0x5655, //CJK UNIFIED IDEOGRAPH - 0x8777: 0x5656, //CJK UNIFIED IDEOGRAPH - 0x8778: 0x565A, //CJK UNIFIED IDEOGRAPH - 0x8779: 0x565B, //CJK UNIFIED IDEOGRAPH - 0x877A: 0x565D, //CJK UNIFIED IDEOGRAPH - 0x877B: 0x565E, //CJK UNIFIED IDEOGRAPH - 0x877C: 0x565F, //CJK UNIFIED IDEOGRAPH - 0x877D: 0x5660, //CJK UNIFIED IDEOGRAPH - 0x877E: 0x5661, //CJK UNIFIED IDEOGRAPH - 0x8780: 0x5663, //CJK UNIFIED IDEOGRAPH - 0x8781: 0x5665, //CJK UNIFIED IDEOGRAPH - 0x8782: 0x5666, //CJK UNIFIED IDEOGRAPH - 0x8783: 0x5667, //CJK UNIFIED IDEOGRAPH - 0x8784: 0x566D, //CJK UNIFIED IDEOGRAPH - 0x8785: 0x566E, //CJK UNIFIED IDEOGRAPH - 0x8786: 0x566F, //CJK UNIFIED IDEOGRAPH - 0x8787: 0x5670, //CJK UNIFIED IDEOGRAPH - 0x8788: 0x5672, //CJK UNIFIED IDEOGRAPH - 0x8789: 0x5673, //CJK UNIFIED IDEOGRAPH - 0x878A: 0x5674, //CJK UNIFIED IDEOGRAPH - 0x878B: 0x5675, //CJK UNIFIED IDEOGRAPH - 0x878C: 0x5677, //CJK UNIFIED IDEOGRAPH - 0x878D: 0x5678, //CJK UNIFIED IDEOGRAPH - 0x878E: 0x5679, //CJK UNIFIED IDEOGRAPH - 0x878F: 0x567A, //CJK UNIFIED IDEOGRAPH - 0x8790: 0x567D, //CJK UNIFIED IDEOGRAPH - 0x8791: 0x567E, //CJK UNIFIED IDEOGRAPH - 0x8792: 0x567F, //CJK UNIFIED IDEOGRAPH - 0x8793: 0x5680, //CJK UNIFIED IDEOGRAPH - 0x8794: 0x5681, //CJK UNIFIED IDEOGRAPH - 0x8795: 0x5682, //CJK UNIFIED IDEOGRAPH - 0x8796: 0x5683, //CJK UNIFIED IDEOGRAPH - 0x8797: 0x5684, //CJK UNIFIED IDEOGRAPH - 0x8798: 0x5687, //CJK UNIFIED IDEOGRAPH - 0x8799: 0x5688, //CJK UNIFIED IDEOGRAPH - 0x879A: 0x5689, //CJK UNIFIED IDEOGRAPH - 0x879B: 0x568A, //CJK UNIFIED IDEOGRAPH - 0x879C: 0x568B, //CJK UNIFIED IDEOGRAPH - 0x879D: 0x568C, //CJK UNIFIED IDEOGRAPH - 0x879E: 0x568D, //CJK UNIFIED IDEOGRAPH - 0x879F: 0x5690, //CJK UNIFIED IDEOGRAPH - 0x87A0: 0x5691, //CJK UNIFIED IDEOGRAPH - 0x87A1: 0x5692, //CJK UNIFIED IDEOGRAPH - 0x87A2: 0x5694, //CJK UNIFIED IDEOGRAPH - 0x87A3: 0x5695, //CJK UNIFIED IDEOGRAPH - 0x87A4: 0x5696, //CJK UNIFIED IDEOGRAPH - 0x87A5: 0x5697, //CJK UNIFIED IDEOGRAPH - 0x87A6: 0x5698, //CJK UNIFIED IDEOGRAPH - 0x87A7: 0x5699, //CJK UNIFIED IDEOGRAPH - 0x87A8: 0x569A, //CJK UNIFIED IDEOGRAPH - 0x87A9: 0x569B, //CJK UNIFIED IDEOGRAPH - 0x87AA: 0x569C, //CJK UNIFIED IDEOGRAPH - 0x87AB: 0x569D, //CJK UNIFIED IDEOGRAPH - 0x87AC: 0x569E, //CJK UNIFIED IDEOGRAPH - 0x87AD: 0x569F, //CJK UNIFIED IDEOGRAPH - 0x87AE: 0x56A0, //CJK UNIFIED IDEOGRAPH - 0x87AF: 0x56A1, //CJK UNIFIED IDEOGRAPH - 0x87B0: 0x56A2, //CJK UNIFIED IDEOGRAPH - 0x87B1: 0x56A4, //CJK UNIFIED IDEOGRAPH - 0x87B2: 0x56A5, //CJK UNIFIED IDEOGRAPH - 0x87B3: 0x56A6, //CJK UNIFIED IDEOGRAPH - 0x87B4: 0x56A7, //CJK UNIFIED IDEOGRAPH - 0x87B5: 0x56A8, //CJK UNIFIED IDEOGRAPH - 0x87B6: 0x56A9, //CJK UNIFIED IDEOGRAPH - 0x87B7: 0x56AA, //CJK UNIFIED IDEOGRAPH - 0x87B8: 0x56AB, //CJK UNIFIED IDEOGRAPH - 0x87B9: 0x56AC, //CJK UNIFIED IDEOGRAPH - 0x87BA: 0x56AD, //CJK UNIFIED IDEOGRAPH - 0x87BB: 0x56AE, //CJK UNIFIED IDEOGRAPH - 0x87BC: 0x56B0, //CJK UNIFIED IDEOGRAPH - 0x87BD: 0x56B1, //CJK UNIFIED IDEOGRAPH - 0x87BE: 0x56B2, //CJK UNIFIED IDEOGRAPH - 0x87BF: 0x56B3, //CJK UNIFIED IDEOGRAPH - 0x87C0: 0x56B4, //CJK UNIFIED IDEOGRAPH - 0x87C1: 0x56B5, //CJK UNIFIED IDEOGRAPH - 0x87C2: 0x56B6, //CJK UNIFIED IDEOGRAPH - 0x87C3: 0x56B8, //CJK UNIFIED IDEOGRAPH - 0x87C4: 0x56B9, //CJK UNIFIED IDEOGRAPH - 0x87C5: 0x56BA, //CJK UNIFIED IDEOGRAPH - 0x87C6: 0x56BB, //CJK UNIFIED IDEOGRAPH - 0x87C7: 0x56BD, //CJK UNIFIED IDEOGRAPH - 0x87C8: 0x56BE, //CJK UNIFIED IDEOGRAPH - 0x87C9: 0x56BF, //CJK UNIFIED IDEOGRAPH - 0x87CA: 0x56C0, //CJK UNIFIED IDEOGRAPH - 0x87CB: 0x56C1, //CJK UNIFIED IDEOGRAPH - 0x87CC: 0x56C2, //CJK UNIFIED IDEOGRAPH - 0x87CD: 0x56C3, //CJK UNIFIED IDEOGRAPH - 0x87CE: 0x56C4, //CJK UNIFIED IDEOGRAPH - 0x87CF: 0x56C5, //CJK UNIFIED IDEOGRAPH - 0x87D0: 0x56C6, //CJK UNIFIED IDEOGRAPH - 0x87D1: 0x56C7, //CJK UNIFIED IDEOGRAPH - 0x87D2: 0x56C8, //CJK UNIFIED IDEOGRAPH - 0x87D3: 0x56C9, //CJK UNIFIED IDEOGRAPH - 0x87D4: 0x56CB, //CJK UNIFIED IDEOGRAPH - 0x87D5: 0x56CC, //CJK UNIFIED IDEOGRAPH - 0x87D6: 0x56CD, //CJK UNIFIED IDEOGRAPH - 0x87D7: 0x56CE, //CJK UNIFIED IDEOGRAPH - 0x87D8: 0x56CF, //CJK UNIFIED IDEOGRAPH - 0x87D9: 0x56D0, //CJK UNIFIED IDEOGRAPH - 0x87DA: 0x56D1, //CJK UNIFIED IDEOGRAPH - 0x87DB: 0x56D2, //CJK UNIFIED IDEOGRAPH - 0x87DC: 0x56D3, //CJK UNIFIED IDEOGRAPH - 0x87DD: 0x56D5, //CJK UNIFIED IDEOGRAPH - 0x87DE: 0x56D6, //CJK UNIFIED IDEOGRAPH - 0x87DF: 0x56D8, //CJK UNIFIED IDEOGRAPH - 0x87E0: 0x56D9, //CJK UNIFIED IDEOGRAPH - 0x87E1: 0x56DC, //CJK UNIFIED IDEOGRAPH - 0x87E2: 0x56E3, //CJK UNIFIED IDEOGRAPH - 0x87E3: 0x56E5, //CJK UNIFIED IDEOGRAPH - 0x87E4: 0x56E6, //CJK UNIFIED IDEOGRAPH - 0x87E5: 0x56E7, //CJK UNIFIED IDEOGRAPH - 0x87E6: 0x56E8, //CJK UNIFIED IDEOGRAPH - 0x87E7: 0x56E9, //CJK UNIFIED IDEOGRAPH - 0x87E8: 0x56EA, //CJK UNIFIED IDEOGRAPH - 0x87E9: 0x56EC, //CJK UNIFIED IDEOGRAPH - 0x87EA: 0x56EE, //CJK UNIFIED IDEOGRAPH - 0x87EB: 0x56EF, //CJK UNIFIED IDEOGRAPH - 0x87EC: 0x56F2, //CJK UNIFIED IDEOGRAPH - 0x87ED: 0x56F3, //CJK UNIFIED IDEOGRAPH - 0x87EE: 0x56F6, //CJK UNIFIED IDEOGRAPH - 0x87EF: 0x56F7, //CJK UNIFIED IDEOGRAPH - 0x87F0: 0x56F8, //CJK UNIFIED IDEOGRAPH - 0x87F1: 0x56FB, //CJK UNIFIED IDEOGRAPH - 0x87F2: 0x56FC, //CJK UNIFIED IDEOGRAPH - 0x87F3: 0x5700, //CJK UNIFIED IDEOGRAPH - 0x87F4: 0x5701, //CJK UNIFIED IDEOGRAPH - 0x87F5: 0x5702, //CJK UNIFIED IDEOGRAPH - 0x87F6: 0x5705, //CJK UNIFIED IDEOGRAPH - 0x87F7: 0x5707, //CJK UNIFIED IDEOGRAPH - 0x87F8: 0x570B, //CJK UNIFIED IDEOGRAPH - 0x87F9: 0x570C, //CJK UNIFIED IDEOGRAPH - 0x87FA: 0x570D, //CJK UNIFIED IDEOGRAPH - 0x87FB: 0x570E, //CJK UNIFIED IDEOGRAPH - 0x87FC: 0x570F, //CJK UNIFIED IDEOGRAPH - 0x87FD: 0x5710, //CJK UNIFIED IDEOGRAPH - 0x87FE: 0x5711, //CJK UNIFIED IDEOGRAPH - 0x8840: 0x5712, //CJK UNIFIED IDEOGRAPH - 0x8841: 0x5713, //CJK UNIFIED IDEOGRAPH - 0x8842: 0x5714, //CJK UNIFIED IDEOGRAPH - 0x8843: 0x5715, //CJK UNIFIED IDEOGRAPH - 0x8844: 0x5716, //CJK UNIFIED IDEOGRAPH - 0x8845: 0x5717, //CJK UNIFIED IDEOGRAPH - 0x8846: 0x5718, //CJK UNIFIED IDEOGRAPH - 0x8847: 0x5719, //CJK UNIFIED IDEOGRAPH - 0x8848: 0x571A, //CJK UNIFIED IDEOGRAPH - 0x8849: 0x571B, //CJK UNIFIED IDEOGRAPH - 0x884A: 0x571D, //CJK UNIFIED IDEOGRAPH - 0x884B: 0x571E, //CJK UNIFIED IDEOGRAPH - 0x884C: 0x5720, //CJK UNIFIED IDEOGRAPH - 0x884D: 0x5721, //CJK UNIFIED IDEOGRAPH - 0x884E: 0x5722, //CJK UNIFIED IDEOGRAPH - 0x884F: 0x5724, //CJK UNIFIED IDEOGRAPH - 0x8850: 0x5725, //CJK UNIFIED IDEOGRAPH - 0x8851: 0x5726, //CJK UNIFIED IDEOGRAPH - 0x8852: 0x5727, //CJK UNIFIED IDEOGRAPH - 0x8853: 0x572B, //CJK UNIFIED IDEOGRAPH - 0x8854: 0x5731, //CJK UNIFIED IDEOGRAPH - 0x8855: 0x5732, //CJK UNIFIED IDEOGRAPH - 0x8856: 0x5734, //CJK UNIFIED IDEOGRAPH - 0x8857: 0x5735, //CJK UNIFIED IDEOGRAPH - 0x8858: 0x5736, //CJK UNIFIED IDEOGRAPH - 0x8859: 0x5737, //CJK UNIFIED IDEOGRAPH - 0x885A: 0x5738, //CJK UNIFIED IDEOGRAPH - 0x885B: 0x573C, //CJK UNIFIED IDEOGRAPH - 0x885C: 0x573D, //CJK UNIFIED IDEOGRAPH - 0x885D: 0x573F, //CJK UNIFIED IDEOGRAPH - 0x885E: 0x5741, //CJK UNIFIED IDEOGRAPH - 0x885F: 0x5743, //CJK UNIFIED IDEOGRAPH - 0x8860: 0x5744, //CJK UNIFIED IDEOGRAPH - 0x8861: 0x5745, //CJK UNIFIED IDEOGRAPH - 0x8862: 0x5746, //CJK UNIFIED IDEOGRAPH - 0x8863: 0x5748, //CJK UNIFIED IDEOGRAPH - 0x8864: 0x5749, //CJK UNIFIED IDEOGRAPH - 0x8865: 0x574B, //CJK UNIFIED IDEOGRAPH - 0x8866: 0x5752, //CJK UNIFIED IDEOGRAPH - 0x8867: 0x5753, //CJK UNIFIED IDEOGRAPH - 0x8868: 0x5754, //CJK UNIFIED IDEOGRAPH - 0x8869: 0x5755, //CJK UNIFIED IDEOGRAPH - 0x886A: 0x5756, //CJK UNIFIED IDEOGRAPH - 0x886B: 0x5758, //CJK UNIFIED IDEOGRAPH - 0x886C: 0x5759, //CJK UNIFIED IDEOGRAPH - 0x886D: 0x5762, //CJK UNIFIED IDEOGRAPH - 0x886E: 0x5763, //CJK UNIFIED IDEOGRAPH - 0x886F: 0x5765, //CJK UNIFIED IDEOGRAPH - 0x8870: 0x5767, //CJK UNIFIED IDEOGRAPH - 0x8871: 0x576C, //CJK UNIFIED IDEOGRAPH - 0x8872: 0x576E, //CJK UNIFIED IDEOGRAPH - 0x8873: 0x5770, //CJK UNIFIED IDEOGRAPH - 0x8874: 0x5771, //CJK UNIFIED IDEOGRAPH - 0x8875: 0x5772, //CJK UNIFIED IDEOGRAPH - 0x8876: 0x5774, //CJK UNIFIED IDEOGRAPH - 0x8877: 0x5775, //CJK UNIFIED IDEOGRAPH - 0x8878: 0x5778, //CJK UNIFIED IDEOGRAPH - 0x8879: 0x5779, //CJK UNIFIED IDEOGRAPH - 0x887A: 0x577A, //CJK UNIFIED IDEOGRAPH - 0x887B: 0x577D, //CJK UNIFIED IDEOGRAPH - 0x887C: 0x577E, //CJK UNIFIED IDEOGRAPH - 0x887D: 0x577F, //CJK UNIFIED IDEOGRAPH - 0x887E: 0x5780, //CJK UNIFIED IDEOGRAPH - 0x8880: 0x5781, //CJK UNIFIED IDEOGRAPH - 0x8881: 0x5787, //CJK UNIFIED IDEOGRAPH - 0x8882: 0x5788, //CJK UNIFIED IDEOGRAPH - 0x8883: 0x5789, //CJK UNIFIED IDEOGRAPH - 0x8884: 0x578A, //CJK UNIFIED IDEOGRAPH - 0x8885: 0x578D, //CJK UNIFIED IDEOGRAPH - 0x8886: 0x578E, //CJK UNIFIED IDEOGRAPH - 0x8887: 0x578F, //CJK UNIFIED IDEOGRAPH - 0x8888: 0x5790, //CJK UNIFIED IDEOGRAPH - 0x8889: 0x5791, //CJK UNIFIED IDEOGRAPH - 0x888A: 0x5794, //CJK UNIFIED IDEOGRAPH - 0x888B: 0x5795, //CJK UNIFIED IDEOGRAPH - 0x888C: 0x5796, //CJK UNIFIED IDEOGRAPH - 0x888D: 0x5797, //CJK UNIFIED IDEOGRAPH - 0x888E: 0x5798, //CJK UNIFIED IDEOGRAPH - 0x888F: 0x5799, //CJK UNIFIED IDEOGRAPH - 0x8890: 0x579A, //CJK UNIFIED IDEOGRAPH - 0x8891: 0x579C, //CJK UNIFIED IDEOGRAPH - 0x8892: 0x579D, //CJK UNIFIED IDEOGRAPH - 0x8893: 0x579E, //CJK UNIFIED IDEOGRAPH - 0x8894: 0x579F, //CJK UNIFIED IDEOGRAPH - 0x8895: 0x57A5, //CJK UNIFIED IDEOGRAPH - 0x8896: 0x57A8, //CJK UNIFIED IDEOGRAPH - 0x8897: 0x57AA, //CJK UNIFIED IDEOGRAPH - 0x8898: 0x57AC, //CJK UNIFIED IDEOGRAPH - 0x8899: 0x57AF, //CJK UNIFIED IDEOGRAPH - 0x889A: 0x57B0, //CJK UNIFIED IDEOGRAPH - 0x889B: 0x57B1, //CJK UNIFIED IDEOGRAPH - 0x889C: 0x57B3, //CJK UNIFIED IDEOGRAPH - 0x889D: 0x57B5, //CJK UNIFIED IDEOGRAPH - 0x889E: 0x57B6, //CJK UNIFIED IDEOGRAPH - 0x889F: 0x57B7, //CJK UNIFIED IDEOGRAPH - 0x88A0: 0x57B9, //CJK UNIFIED IDEOGRAPH - 0x88A1: 0x57BA, //CJK UNIFIED IDEOGRAPH - 0x88A2: 0x57BB, //CJK UNIFIED IDEOGRAPH - 0x88A3: 0x57BC, //CJK UNIFIED IDEOGRAPH - 0x88A4: 0x57BD, //CJK UNIFIED IDEOGRAPH - 0x88A5: 0x57BE, //CJK UNIFIED IDEOGRAPH - 0x88A6: 0x57BF, //CJK UNIFIED IDEOGRAPH - 0x88A7: 0x57C0, //CJK UNIFIED IDEOGRAPH - 0x88A8: 0x57C1, //CJK UNIFIED IDEOGRAPH - 0x88A9: 0x57C4, //CJK UNIFIED IDEOGRAPH - 0x88AA: 0x57C5, //CJK UNIFIED IDEOGRAPH - 0x88AB: 0x57C6, //CJK UNIFIED IDEOGRAPH - 0x88AC: 0x57C7, //CJK UNIFIED IDEOGRAPH - 0x88AD: 0x57C8, //CJK UNIFIED IDEOGRAPH - 0x88AE: 0x57C9, //CJK UNIFIED IDEOGRAPH - 0x88AF: 0x57CA, //CJK UNIFIED IDEOGRAPH - 0x88B0: 0x57CC, //CJK UNIFIED IDEOGRAPH - 0x88B1: 0x57CD, //CJK UNIFIED IDEOGRAPH - 0x88B2: 0x57D0, //CJK UNIFIED IDEOGRAPH - 0x88B3: 0x57D1, //CJK UNIFIED IDEOGRAPH - 0x88B4: 0x57D3, //CJK UNIFIED IDEOGRAPH - 0x88B5: 0x57D6, //CJK UNIFIED IDEOGRAPH - 0x88B6: 0x57D7, //CJK UNIFIED IDEOGRAPH - 0x88B7: 0x57DB, //CJK UNIFIED IDEOGRAPH - 0x88B8: 0x57DC, //CJK UNIFIED IDEOGRAPH - 0x88B9: 0x57DE, //CJK UNIFIED IDEOGRAPH - 0x88BA: 0x57E1, //CJK UNIFIED IDEOGRAPH - 0x88BB: 0x57E2, //CJK UNIFIED IDEOGRAPH - 0x88BC: 0x57E3, //CJK UNIFIED IDEOGRAPH - 0x88BD: 0x57E5, //CJK UNIFIED IDEOGRAPH - 0x88BE: 0x57E6, //CJK UNIFIED IDEOGRAPH - 0x88BF: 0x57E7, //CJK UNIFIED IDEOGRAPH - 0x88C0: 0x57E8, //CJK UNIFIED IDEOGRAPH - 0x88C1: 0x57E9, //CJK UNIFIED IDEOGRAPH - 0x88C2: 0x57EA, //CJK UNIFIED IDEOGRAPH - 0x88C3: 0x57EB, //CJK UNIFIED IDEOGRAPH - 0x88C4: 0x57EC, //CJK UNIFIED IDEOGRAPH - 0x88C5: 0x57EE, //CJK UNIFIED IDEOGRAPH - 0x88C6: 0x57F0, //CJK UNIFIED IDEOGRAPH - 0x88C7: 0x57F1, //CJK UNIFIED IDEOGRAPH - 0x88C8: 0x57F2, //CJK UNIFIED IDEOGRAPH - 0x88C9: 0x57F3, //CJK UNIFIED IDEOGRAPH - 0x88CA: 0x57F5, //CJK UNIFIED IDEOGRAPH - 0x88CB: 0x57F6, //CJK UNIFIED IDEOGRAPH - 0x88CC: 0x57F7, //CJK UNIFIED IDEOGRAPH - 0x88CD: 0x57FB, //CJK UNIFIED IDEOGRAPH - 0x88CE: 0x57FC, //CJK UNIFIED IDEOGRAPH - 0x88CF: 0x57FE, //CJK UNIFIED IDEOGRAPH - 0x88D0: 0x57FF, //CJK UNIFIED IDEOGRAPH - 0x88D1: 0x5801, //CJK UNIFIED IDEOGRAPH - 0x88D2: 0x5803, //CJK UNIFIED IDEOGRAPH - 0x88D3: 0x5804, //CJK UNIFIED IDEOGRAPH - 0x88D4: 0x5805, //CJK UNIFIED IDEOGRAPH - 0x88D5: 0x5808, //CJK UNIFIED IDEOGRAPH - 0x88D6: 0x5809, //CJK UNIFIED IDEOGRAPH - 0x88D7: 0x580A, //CJK UNIFIED IDEOGRAPH - 0x88D8: 0x580C, //CJK UNIFIED IDEOGRAPH - 0x88D9: 0x580E, //CJK UNIFIED IDEOGRAPH - 0x88DA: 0x580F, //CJK UNIFIED IDEOGRAPH - 0x88DB: 0x5810, //CJK UNIFIED IDEOGRAPH - 0x88DC: 0x5812, //CJK UNIFIED IDEOGRAPH - 0x88DD: 0x5813, //CJK UNIFIED IDEOGRAPH - 0x88DE: 0x5814, //CJK UNIFIED IDEOGRAPH - 0x88DF: 0x5816, //CJK UNIFIED IDEOGRAPH - 0x88E0: 0x5817, //CJK UNIFIED IDEOGRAPH - 0x88E1: 0x5818, //CJK UNIFIED IDEOGRAPH - 0x88E2: 0x581A, //CJK UNIFIED IDEOGRAPH - 0x88E3: 0x581B, //CJK UNIFIED IDEOGRAPH - 0x88E4: 0x581C, //CJK UNIFIED IDEOGRAPH - 0x88E5: 0x581D, //CJK UNIFIED IDEOGRAPH - 0x88E6: 0x581F, //CJK UNIFIED IDEOGRAPH - 0x88E7: 0x5822, //CJK UNIFIED IDEOGRAPH - 0x88E8: 0x5823, //CJK UNIFIED IDEOGRAPH - 0x88E9: 0x5825, //CJK UNIFIED IDEOGRAPH - 0x88EA: 0x5826, //CJK UNIFIED IDEOGRAPH - 0x88EB: 0x5827, //CJK UNIFIED IDEOGRAPH - 0x88EC: 0x5828, //CJK UNIFIED IDEOGRAPH - 0x88ED: 0x5829, //CJK UNIFIED IDEOGRAPH - 0x88EE: 0x582B, //CJK UNIFIED IDEOGRAPH - 0x88EF: 0x582C, //CJK UNIFIED IDEOGRAPH - 0x88F0: 0x582D, //CJK UNIFIED IDEOGRAPH - 0x88F1: 0x582E, //CJK UNIFIED IDEOGRAPH - 0x88F2: 0x582F, //CJK UNIFIED IDEOGRAPH - 0x88F3: 0x5831, //CJK UNIFIED IDEOGRAPH - 0x88F4: 0x5832, //CJK UNIFIED IDEOGRAPH - 0x88F5: 0x5833, //CJK UNIFIED IDEOGRAPH - 0x88F6: 0x5834, //CJK UNIFIED IDEOGRAPH - 0x88F7: 0x5836, //CJK UNIFIED IDEOGRAPH - 0x88F8: 0x5837, //CJK UNIFIED IDEOGRAPH - 0x88F9: 0x5838, //CJK UNIFIED IDEOGRAPH - 0x88FA: 0x5839, //CJK UNIFIED IDEOGRAPH - 0x88FB: 0x583A, //CJK UNIFIED IDEOGRAPH - 0x88FC: 0x583B, //CJK UNIFIED IDEOGRAPH - 0x88FD: 0x583C, //CJK UNIFIED IDEOGRAPH - 0x88FE: 0x583D, //CJK UNIFIED IDEOGRAPH - 0x8940: 0x583E, //CJK UNIFIED IDEOGRAPH - 0x8941: 0x583F, //CJK UNIFIED IDEOGRAPH - 0x8942: 0x5840, //CJK UNIFIED IDEOGRAPH - 0x8943: 0x5841, //CJK UNIFIED IDEOGRAPH - 0x8944: 0x5842, //CJK UNIFIED IDEOGRAPH - 0x8945: 0x5843, //CJK UNIFIED IDEOGRAPH - 0x8946: 0x5845, //CJK UNIFIED IDEOGRAPH - 0x8947: 0x5846, //CJK UNIFIED IDEOGRAPH - 0x8948: 0x5847, //CJK UNIFIED IDEOGRAPH - 0x8949: 0x5848, //CJK UNIFIED IDEOGRAPH - 0x894A: 0x5849, //CJK UNIFIED IDEOGRAPH - 0x894B: 0x584A, //CJK UNIFIED IDEOGRAPH - 0x894C: 0x584B, //CJK UNIFIED IDEOGRAPH - 0x894D: 0x584E, //CJK UNIFIED IDEOGRAPH - 0x894E: 0x584F, //CJK UNIFIED IDEOGRAPH - 0x894F: 0x5850, //CJK UNIFIED IDEOGRAPH - 0x8950: 0x5852, //CJK UNIFIED IDEOGRAPH - 0x8951: 0x5853, //CJK UNIFIED IDEOGRAPH - 0x8952: 0x5855, //CJK UNIFIED IDEOGRAPH - 0x8953: 0x5856, //CJK UNIFIED IDEOGRAPH - 0x8954: 0x5857, //CJK UNIFIED IDEOGRAPH - 0x8955: 0x5859, //CJK UNIFIED IDEOGRAPH - 0x8956: 0x585A, //CJK UNIFIED IDEOGRAPH - 0x8957: 0x585B, //CJK UNIFIED IDEOGRAPH - 0x8958: 0x585C, //CJK UNIFIED IDEOGRAPH - 0x8959: 0x585D, //CJK UNIFIED IDEOGRAPH - 0x895A: 0x585F, //CJK UNIFIED IDEOGRAPH - 0x895B: 0x5860, //CJK UNIFIED IDEOGRAPH - 0x895C: 0x5861, //CJK UNIFIED IDEOGRAPH - 0x895D: 0x5862, //CJK UNIFIED IDEOGRAPH - 0x895E: 0x5863, //CJK UNIFIED IDEOGRAPH - 0x895F: 0x5864, //CJK UNIFIED IDEOGRAPH - 0x8960: 0x5866, //CJK UNIFIED IDEOGRAPH - 0x8961: 0x5867, //CJK UNIFIED IDEOGRAPH - 0x8962: 0x5868, //CJK UNIFIED IDEOGRAPH - 0x8963: 0x5869, //CJK UNIFIED IDEOGRAPH - 0x8964: 0x586A, //CJK UNIFIED IDEOGRAPH - 0x8965: 0x586D, //CJK UNIFIED IDEOGRAPH - 0x8966: 0x586E, //CJK UNIFIED IDEOGRAPH - 0x8967: 0x586F, //CJK UNIFIED IDEOGRAPH - 0x8968: 0x5870, //CJK UNIFIED IDEOGRAPH - 0x8969: 0x5871, //CJK UNIFIED IDEOGRAPH - 0x896A: 0x5872, //CJK UNIFIED IDEOGRAPH - 0x896B: 0x5873, //CJK UNIFIED IDEOGRAPH - 0x896C: 0x5874, //CJK UNIFIED IDEOGRAPH - 0x896D: 0x5875, //CJK UNIFIED IDEOGRAPH - 0x896E: 0x5876, //CJK UNIFIED IDEOGRAPH - 0x896F: 0x5877, //CJK UNIFIED IDEOGRAPH - 0x8970: 0x5878, //CJK UNIFIED IDEOGRAPH - 0x8971: 0x5879, //CJK UNIFIED IDEOGRAPH - 0x8972: 0x587A, //CJK UNIFIED IDEOGRAPH - 0x8973: 0x587B, //CJK UNIFIED IDEOGRAPH - 0x8974: 0x587C, //CJK UNIFIED IDEOGRAPH - 0x8975: 0x587D, //CJK UNIFIED IDEOGRAPH - 0x8976: 0x587F, //CJK UNIFIED IDEOGRAPH - 0x8977: 0x5882, //CJK UNIFIED IDEOGRAPH - 0x8978: 0x5884, //CJK UNIFIED IDEOGRAPH - 0x8979: 0x5886, //CJK UNIFIED IDEOGRAPH - 0x897A: 0x5887, //CJK UNIFIED IDEOGRAPH - 0x897B: 0x5888, //CJK UNIFIED IDEOGRAPH - 0x897C: 0x588A, //CJK UNIFIED IDEOGRAPH - 0x897D: 0x588B, //CJK UNIFIED IDEOGRAPH - 0x897E: 0x588C, //CJK UNIFIED IDEOGRAPH - 0x8980: 0x588D, //CJK UNIFIED IDEOGRAPH - 0x8981: 0x588E, //CJK UNIFIED IDEOGRAPH - 0x8982: 0x588F, //CJK UNIFIED IDEOGRAPH - 0x8983: 0x5890, //CJK UNIFIED IDEOGRAPH - 0x8984: 0x5891, //CJK UNIFIED IDEOGRAPH - 0x8985: 0x5894, //CJK UNIFIED IDEOGRAPH - 0x8986: 0x5895, //CJK UNIFIED IDEOGRAPH - 0x8987: 0x5896, //CJK UNIFIED IDEOGRAPH - 0x8988: 0x5897, //CJK UNIFIED IDEOGRAPH - 0x8989: 0x5898, //CJK UNIFIED IDEOGRAPH - 0x898A: 0x589B, //CJK UNIFIED IDEOGRAPH - 0x898B: 0x589C, //CJK UNIFIED IDEOGRAPH - 0x898C: 0x589D, //CJK UNIFIED IDEOGRAPH - 0x898D: 0x58A0, //CJK UNIFIED IDEOGRAPH - 0x898E: 0x58A1, //CJK UNIFIED IDEOGRAPH - 0x898F: 0x58A2, //CJK UNIFIED IDEOGRAPH - 0x8990: 0x58A3, //CJK UNIFIED IDEOGRAPH - 0x8991: 0x58A4, //CJK UNIFIED IDEOGRAPH - 0x8992: 0x58A5, //CJK UNIFIED IDEOGRAPH - 0x8993: 0x58A6, //CJK UNIFIED IDEOGRAPH - 0x8994: 0x58A7, //CJK UNIFIED IDEOGRAPH - 0x8995: 0x58AA, //CJK UNIFIED IDEOGRAPH - 0x8996: 0x58AB, //CJK UNIFIED IDEOGRAPH - 0x8997: 0x58AC, //CJK UNIFIED IDEOGRAPH - 0x8998: 0x58AD, //CJK UNIFIED IDEOGRAPH - 0x8999: 0x58AE, //CJK UNIFIED IDEOGRAPH - 0x899A: 0x58AF, //CJK UNIFIED IDEOGRAPH - 0x899B: 0x58B0, //CJK UNIFIED IDEOGRAPH - 0x899C: 0x58B1, //CJK UNIFIED IDEOGRAPH - 0x899D: 0x58B2, //CJK UNIFIED IDEOGRAPH - 0x899E: 0x58B3, //CJK UNIFIED IDEOGRAPH - 0x899F: 0x58B4, //CJK UNIFIED IDEOGRAPH - 0x89A0: 0x58B5, //CJK UNIFIED IDEOGRAPH - 0x89A1: 0x58B6, //CJK UNIFIED IDEOGRAPH - 0x89A2: 0x58B7, //CJK UNIFIED IDEOGRAPH - 0x89A3: 0x58B8, //CJK UNIFIED IDEOGRAPH - 0x89A4: 0x58B9, //CJK UNIFIED IDEOGRAPH - 0x89A5: 0x58BA, //CJK UNIFIED IDEOGRAPH - 0x89A6: 0x58BB, //CJK UNIFIED IDEOGRAPH - 0x89A7: 0x58BD, //CJK UNIFIED IDEOGRAPH - 0x89A8: 0x58BE, //CJK UNIFIED IDEOGRAPH - 0x89A9: 0x58BF, //CJK UNIFIED IDEOGRAPH - 0x89AA: 0x58C0, //CJK UNIFIED IDEOGRAPH - 0x89AB: 0x58C2, //CJK UNIFIED IDEOGRAPH - 0x89AC: 0x58C3, //CJK UNIFIED IDEOGRAPH - 0x89AD: 0x58C4, //CJK UNIFIED IDEOGRAPH - 0x89AE: 0x58C6, //CJK UNIFIED IDEOGRAPH - 0x89AF: 0x58C7, //CJK UNIFIED IDEOGRAPH - 0x89B0: 0x58C8, //CJK UNIFIED IDEOGRAPH - 0x89B1: 0x58C9, //CJK UNIFIED IDEOGRAPH - 0x89B2: 0x58CA, //CJK UNIFIED IDEOGRAPH - 0x89B3: 0x58CB, //CJK UNIFIED IDEOGRAPH - 0x89B4: 0x58CC, //CJK UNIFIED IDEOGRAPH - 0x89B5: 0x58CD, //CJK UNIFIED IDEOGRAPH - 0x89B6: 0x58CE, //CJK UNIFIED IDEOGRAPH - 0x89B7: 0x58CF, //CJK UNIFIED IDEOGRAPH - 0x89B8: 0x58D0, //CJK UNIFIED IDEOGRAPH - 0x89B9: 0x58D2, //CJK UNIFIED IDEOGRAPH - 0x89BA: 0x58D3, //CJK UNIFIED IDEOGRAPH - 0x89BB: 0x58D4, //CJK UNIFIED IDEOGRAPH - 0x89BC: 0x58D6, //CJK UNIFIED IDEOGRAPH - 0x89BD: 0x58D7, //CJK UNIFIED IDEOGRAPH - 0x89BE: 0x58D8, //CJK UNIFIED IDEOGRAPH - 0x89BF: 0x58D9, //CJK UNIFIED IDEOGRAPH - 0x89C0: 0x58DA, //CJK UNIFIED IDEOGRAPH - 0x89C1: 0x58DB, //CJK UNIFIED IDEOGRAPH - 0x89C2: 0x58DC, //CJK UNIFIED IDEOGRAPH - 0x89C3: 0x58DD, //CJK UNIFIED IDEOGRAPH - 0x89C4: 0x58DE, //CJK UNIFIED IDEOGRAPH - 0x89C5: 0x58DF, //CJK UNIFIED IDEOGRAPH - 0x89C6: 0x58E0, //CJK UNIFIED IDEOGRAPH - 0x89C7: 0x58E1, //CJK UNIFIED IDEOGRAPH - 0x89C8: 0x58E2, //CJK UNIFIED IDEOGRAPH - 0x89C9: 0x58E3, //CJK UNIFIED IDEOGRAPH - 0x89CA: 0x58E5, //CJK UNIFIED IDEOGRAPH - 0x89CB: 0x58E6, //CJK UNIFIED IDEOGRAPH - 0x89CC: 0x58E7, //CJK UNIFIED IDEOGRAPH - 0x89CD: 0x58E8, //CJK UNIFIED IDEOGRAPH - 0x89CE: 0x58E9, //CJK UNIFIED IDEOGRAPH - 0x89CF: 0x58EA, //CJK UNIFIED IDEOGRAPH - 0x89D0: 0x58ED, //CJK UNIFIED IDEOGRAPH - 0x89D1: 0x58EF, //CJK UNIFIED IDEOGRAPH - 0x89D2: 0x58F1, //CJK UNIFIED IDEOGRAPH - 0x89D3: 0x58F2, //CJK UNIFIED IDEOGRAPH - 0x89D4: 0x58F4, //CJK UNIFIED IDEOGRAPH - 0x89D5: 0x58F5, //CJK UNIFIED IDEOGRAPH - 0x89D6: 0x58F7, //CJK UNIFIED IDEOGRAPH - 0x89D7: 0x58F8, //CJK UNIFIED IDEOGRAPH - 0x89D8: 0x58FA, //CJK UNIFIED IDEOGRAPH - 0x89D9: 0x58FB, //CJK UNIFIED IDEOGRAPH - 0x89DA: 0x58FC, //CJK UNIFIED IDEOGRAPH - 0x89DB: 0x58FD, //CJK UNIFIED IDEOGRAPH - 0x89DC: 0x58FE, //CJK UNIFIED IDEOGRAPH - 0x89DD: 0x58FF, //CJK UNIFIED IDEOGRAPH - 0x89DE: 0x5900, //CJK UNIFIED IDEOGRAPH - 0x89DF: 0x5901, //CJK UNIFIED IDEOGRAPH - 0x89E0: 0x5903, //CJK UNIFIED IDEOGRAPH - 0x89E1: 0x5905, //CJK UNIFIED IDEOGRAPH - 0x89E2: 0x5906, //CJK UNIFIED IDEOGRAPH - 0x89E3: 0x5908, //CJK UNIFIED IDEOGRAPH - 0x89E4: 0x5909, //CJK UNIFIED IDEOGRAPH - 0x89E5: 0x590A, //CJK UNIFIED IDEOGRAPH - 0x89E6: 0x590B, //CJK UNIFIED IDEOGRAPH - 0x89E7: 0x590C, //CJK UNIFIED IDEOGRAPH - 0x89E8: 0x590E, //CJK UNIFIED IDEOGRAPH - 0x89E9: 0x5910, //CJK UNIFIED IDEOGRAPH - 0x89EA: 0x5911, //CJK UNIFIED IDEOGRAPH - 0x89EB: 0x5912, //CJK UNIFIED IDEOGRAPH - 0x89EC: 0x5913, //CJK UNIFIED IDEOGRAPH - 0x89ED: 0x5917, //CJK UNIFIED IDEOGRAPH - 0x89EE: 0x5918, //CJK UNIFIED IDEOGRAPH - 0x89EF: 0x591B, //CJK UNIFIED IDEOGRAPH - 0x89F0: 0x591D, //CJK UNIFIED IDEOGRAPH - 0x89F1: 0x591E, //CJK UNIFIED IDEOGRAPH - 0x89F2: 0x5920, //CJK UNIFIED IDEOGRAPH - 0x89F3: 0x5921, //CJK UNIFIED IDEOGRAPH - 0x89F4: 0x5922, //CJK UNIFIED IDEOGRAPH - 0x89F5: 0x5923, //CJK UNIFIED IDEOGRAPH - 0x89F6: 0x5926, //CJK UNIFIED IDEOGRAPH - 0x89F7: 0x5928, //CJK UNIFIED IDEOGRAPH - 0x89F8: 0x592C, //CJK UNIFIED IDEOGRAPH - 0x89F9: 0x5930, //CJK UNIFIED IDEOGRAPH - 0x89FA: 0x5932, //CJK UNIFIED IDEOGRAPH - 0x89FB: 0x5933, //CJK UNIFIED IDEOGRAPH - 0x89FC: 0x5935, //CJK UNIFIED IDEOGRAPH - 0x89FD: 0x5936, //CJK UNIFIED IDEOGRAPH - 0x89FE: 0x593B, //CJK UNIFIED IDEOGRAPH - 0x8A40: 0x593D, //CJK UNIFIED IDEOGRAPH - 0x8A41: 0x593E, //CJK UNIFIED IDEOGRAPH - 0x8A42: 0x593F, //CJK UNIFIED IDEOGRAPH - 0x8A43: 0x5940, //CJK UNIFIED IDEOGRAPH - 0x8A44: 0x5943, //CJK UNIFIED IDEOGRAPH - 0x8A45: 0x5945, //CJK UNIFIED IDEOGRAPH - 0x8A46: 0x5946, //CJK UNIFIED IDEOGRAPH - 0x8A47: 0x594A, //CJK UNIFIED IDEOGRAPH - 0x8A48: 0x594C, //CJK UNIFIED IDEOGRAPH - 0x8A49: 0x594D, //CJK UNIFIED IDEOGRAPH - 0x8A4A: 0x5950, //CJK UNIFIED IDEOGRAPH - 0x8A4B: 0x5952, //CJK UNIFIED IDEOGRAPH - 0x8A4C: 0x5953, //CJK UNIFIED IDEOGRAPH - 0x8A4D: 0x5959, //CJK UNIFIED IDEOGRAPH - 0x8A4E: 0x595B, //CJK UNIFIED IDEOGRAPH - 0x8A4F: 0x595C, //CJK UNIFIED IDEOGRAPH - 0x8A50: 0x595D, //CJK UNIFIED IDEOGRAPH - 0x8A51: 0x595E, //CJK UNIFIED IDEOGRAPH - 0x8A52: 0x595F, //CJK UNIFIED IDEOGRAPH - 0x8A53: 0x5961, //CJK UNIFIED IDEOGRAPH - 0x8A54: 0x5963, //CJK UNIFIED IDEOGRAPH - 0x8A55: 0x5964, //CJK UNIFIED IDEOGRAPH - 0x8A56: 0x5966, //CJK UNIFIED IDEOGRAPH - 0x8A57: 0x5967, //CJK UNIFIED IDEOGRAPH - 0x8A58: 0x5968, //CJK UNIFIED IDEOGRAPH - 0x8A59: 0x5969, //CJK UNIFIED IDEOGRAPH - 0x8A5A: 0x596A, //CJK UNIFIED IDEOGRAPH - 0x8A5B: 0x596B, //CJK UNIFIED IDEOGRAPH - 0x8A5C: 0x596C, //CJK UNIFIED IDEOGRAPH - 0x8A5D: 0x596D, //CJK UNIFIED IDEOGRAPH - 0x8A5E: 0x596E, //CJK UNIFIED IDEOGRAPH - 0x8A5F: 0x596F, //CJK UNIFIED IDEOGRAPH - 0x8A60: 0x5970, //CJK UNIFIED IDEOGRAPH - 0x8A61: 0x5971, //CJK UNIFIED IDEOGRAPH - 0x8A62: 0x5972, //CJK UNIFIED IDEOGRAPH - 0x8A63: 0x5975, //CJK UNIFIED IDEOGRAPH - 0x8A64: 0x5977, //CJK UNIFIED IDEOGRAPH - 0x8A65: 0x597A, //CJK UNIFIED IDEOGRAPH - 0x8A66: 0x597B, //CJK UNIFIED IDEOGRAPH - 0x8A67: 0x597C, //CJK UNIFIED IDEOGRAPH - 0x8A68: 0x597E, //CJK UNIFIED IDEOGRAPH - 0x8A69: 0x597F, //CJK UNIFIED IDEOGRAPH - 0x8A6A: 0x5980, //CJK UNIFIED IDEOGRAPH - 0x8A6B: 0x5985, //CJK UNIFIED IDEOGRAPH - 0x8A6C: 0x5989, //CJK UNIFIED IDEOGRAPH - 0x8A6D: 0x598B, //CJK UNIFIED IDEOGRAPH - 0x8A6E: 0x598C, //CJK UNIFIED IDEOGRAPH - 0x8A6F: 0x598E, //CJK UNIFIED IDEOGRAPH - 0x8A70: 0x598F, //CJK UNIFIED IDEOGRAPH - 0x8A71: 0x5990, //CJK UNIFIED IDEOGRAPH - 0x8A72: 0x5991, //CJK UNIFIED IDEOGRAPH - 0x8A73: 0x5994, //CJK UNIFIED IDEOGRAPH - 0x8A74: 0x5995, //CJK UNIFIED IDEOGRAPH - 0x8A75: 0x5998, //CJK UNIFIED IDEOGRAPH - 0x8A76: 0x599A, //CJK UNIFIED IDEOGRAPH - 0x8A77: 0x599B, //CJK UNIFIED IDEOGRAPH - 0x8A78: 0x599C, //CJK UNIFIED IDEOGRAPH - 0x8A79: 0x599D, //CJK UNIFIED IDEOGRAPH - 0x8A7A: 0x599F, //CJK UNIFIED IDEOGRAPH - 0x8A7B: 0x59A0, //CJK UNIFIED IDEOGRAPH - 0x8A7C: 0x59A1, //CJK UNIFIED IDEOGRAPH - 0x8A7D: 0x59A2, //CJK UNIFIED IDEOGRAPH - 0x8A7E: 0x59A6, //CJK UNIFIED IDEOGRAPH - 0x8A80: 0x59A7, //CJK UNIFIED IDEOGRAPH - 0x8A81: 0x59AC, //CJK UNIFIED IDEOGRAPH - 0x8A82: 0x59AD, //CJK UNIFIED IDEOGRAPH - 0x8A83: 0x59B0, //CJK UNIFIED IDEOGRAPH - 0x8A84: 0x59B1, //CJK UNIFIED IDEOGRAPH - 0x8A85: 0x59B3, //CJK UNIFIED IDEOGRAPH - 0x8A86: 0x59B4, //CJK UNIFIED IDEOGRAPH - 0x8A87: 0x59B5, //CJK UNIFIED IDEOGRAPH - 0x8A88: 0x59B6, //CJK UNIFIED IDEOGRAPH - 0x8A89: 0x59B7, //CJK UNIFIED IDEOGRAPH - 0x8A8A: 0x59B8, //CJK UNIFIED IDEOGRAPH - 0x8A8B: 0x59BA, //CJK UNIFIED IDEOGRAPH - 0x8A8C: 0x59BC, //CJK UNIFIED IDEOGRAPH - 0x8A8D: 0x59BD, //CJK UNIFIED IDEOGRAPH - 0x8A8E: 0x59BF, //CJK UNIFIED IDEOGRAPH - 0x8A8F: 0x59C0, //CJK UNIFIED IDEOGRAPH - 0x8A90: 0x59C1, //CJK UNIFIED IDEOGRAPH - 0x8A91: 0x59C2, //CJK UNIFIED IDEOGRAPH - 0x8A92: 0x59C3, //CJK UNIFIED IDEOGRAPH - 0x8A93: 0x59C4, //CJK UNIFIED IDEOGRAPH - 0x8A94: 0x59C5, //CJK UNIFIED IDEOGRAPH - 0x8A95: 0x59C7, //CJK UNIFIED IDEOGRAPH - 0x8A96: 0x59C8, //CJK UNIFIED IDEOGRAPH - 0x8A97: 0x59C9, //CJK UNIFIED IDEOGRAPH - 0x8A98: 0x59CC, //CJK UNIFIED IDEOGRAPH - 0x8A99: 0x59CD, //CJK UNIFIED IDEOGRAPH - 0x8A9A: 0x59CE, //CJK UNIFIED IDEOGRAPH - 0x8A9B: 0x59CF, //CJK UNIFIED IDEOGRAPH - 0x8A9C: 0x59D5, //CJK UNIFIED IDEOGRAPH - 0x8A9D: 0x59D6, //CJK UNIFIED IDEOGRAPH - 0x8A9E: 0x59D9, //CJK UNIFIED IDEOGRAPH - 0x8A9F: 0x59DB, //CJK UNIFIED IDEOGRAPH - 0x8AA0: 0x59DE, //CJK UNIFIED IDEOGRAPH - 0x8AA1: 0x59DF, //CJK UNIFIED IDEOGRAPH - 0x8AA2: 0x59E0, //CJK UNIFIED IDEOGRAPH - 0x8AA3: 0x59E1, //CJK UNIFIED IDEOGRAPH - 0x8AA4: 0x59E2, //CJK UNIFIED IDEOGRAPH - 0x8AA5: 0x59E4, //CJK UNIFIED IDEOGRAPH - 0x8AA6: 0x59E6, //CJK UNIFIED IDEOGRAPH - 0x8AA7: 0x59E7, //CJK UNIFIED IDEOGRAPH - 0x8AA8: 0x59E9, //CJK UNIFIED IDEOGRAPH - 0x8AA9: 0x59EA, //CJK UNIFIED IDEOGRAPH - 0x8AAA: 0x59EB, //CJK UNIFIED IDEOGRAPH - 0x8AAB: 0x59ED, //CJK UNIFIED IDEOGRAPH - 0x8AAC: 0x59EE, //CJK UNIFIED IDEOGRAPH - 0x8AAD: 0x59EF, //CJK UNIFIED IDEOGRAPH - 0x8AAE: 0x59F0, //CJK UNIFIED IDEOGRAPH - 0x8AAF: 0x59F1, //CJK UNIFIED IDEOGRAPH - 0x8AB0: 0x59F2, //CJK UNIFIED IDEOGRAPH - 0x8AB1: 0x59F3, //CJK UNIFIED IDEOGRAPH - 0x8AB2: 0x59F4, //CJK UNIFIED IDEOGRAPH - 0x8AB3: 0x59F5, //CJK UNIFIED IDEOGRAPH - 0x8AB4: 0x59F6, //CJK UNIFIED IDEOGRAPH - 0x8AB5: 0x59F7, //CJK UNIFIED IDEOGRAPH - 0x8AB6: 0x59F8, //CJK UNIFIED IDEOGRAPH - 0x8AB7: 0x59FA, //CJK UNIFIED IDEOGRAPH - 0x8AB8: 0x59FC, //CJK UNIFIED IDEOGRAPH - 0x8AB9: 0x59FD, //CJK UNIFIED IDEOGRAPH - 0x8ABA: 0x59FE, //CJK UNIFIED IDEOGRAPH - 0x8ABB: 0x5A00, //CJK UNIFIED IDEOGRAPH - 0x8ABC: 0x5A02, //CJK UNIFIED IDEOGRAPH - 0x8ABD: 0x5A0A, //CJK UNIFIED IDEOGRAPH - 0x8ABE: 0x5A0B, //CJK UNIFIED IDEOGRAPH - 0x8ABF: 0x5A0D, //CJK UNIFIED IDEOGRAPH - 0x8AC0: 0x5A0E, //CJK UNIFIED IDEOGRAPH - 0x8AC1: 0x5A0F, //CJK UNIFIED IDEOGRAPH - 0x8AC2: 0x5A10, //CJK UNIFIED IDEOGRAPH - 0x8AC3: 0x5A12, //CJK UNIFIED IDEOGRAPH - 0x8AC4: 0x5A14, //CJK UNIFIED IDEOGRAPH - 0x8AC5: 0x5A15, //CJK UNIFIED IDEOGRAPH - 0x8AC6: 0x5A16, //CJK UNIFIED IDEOGRAPH - 0x8AC7: 0x5A17, //CJK UNIFIED IDEOGRAPH - 0x8AC8: 0x5A19, //CJK UNIFIED IDEOGRAPH - 0x8AC9: 0x5A1A, //CJK UNIFIED IDEOGRAPH - 0x8ACA: 0x5A1B, //CJK UNIFIED IDEOGRAPH - 0x8ACB: 0x5A1D, //CJK UNIFIED IDEOGRAPH - 0x8ACC: 0x5A1E, //CJK UNIFIED IDEOGRAPH - 0x8ACD: 0x5A21, //CJK UNIFIED IDEOGRAPH - 0x8ACE: 0x5A22, //CJK UNIFIED IDEOGRAPH - 0x8ACF: 0x5A24, //CJK UNIFIED IDEOGRAPH - 0x8AD0: 0x5A26, //CJK UNIFIED IDEOGRAPH - 0x8AD1: 0x5A27, //CJK UNIFIED IDEOGRAPH - 0x8AD2: 0x5A28, //CJK UNIFIED IDEOGRAPH - 0x8AD3: 0x5A2A, //CJK UNIFIED IDEOGRAPH - 0x8AD4: 0x5A2B, //CJK UNIFIED IDEOGRAPH - 0x8AD5: 0x5A2C, //CJK UNIFIED IDEOGRAPH - 0x8AD6: 0x5A2D, //CJK UNIFIED IDEOGRAPH - 0x8AD7: 0x5A2E, //CJK UNIFIED IDEOGRAPH - 0x8AD8: 0x5A2F, //CJK UNIFIED IDEOGRAPH - 0x8AD9: 0x5A30, //CJK UNIFIED IDEOGRAPH - 0x8ADA: 0x5A33, //CJK UNIFIED IDEOGRAPH - 0x8ADB: 0x5A35, //CJK UNIFIED IDEOGRAPH - 0x8ADC: 0x5A37, //CJK UNIFIED IDEOGRAPH - 0x8ADD: 0x5A38, //CJK UNIFIED IDEOGRAPH - 0x8ADE: 0x5A39, //CJK UNIFIED IDEOGRAPH - 0x8ADF: 0x5A3A, //CJK UNIFIED IDEOGRAPH - 0x8AE0: 0x5A3B, //CJK UNIFIED IDEOGRAPH - 0x8AE1: 0x5A3D, //CJK UNIFIED IDEOGRAPH - 0x8AE2: 0x5A3E, //CJK UNIFIED IDEOGRAPH - 0x8AE3: 0x5A3F, //CJK UNIFIED IDEOGRAPH - 0x8AE4: 0x5A41, //CJK UNIFIED IDEOGRAPH - 0x8AE5: 0x5A42, //CJK UNIFIED IDEOGRAPH - 0x8AE6: 0x5A43, //CJK UNIFIED IDEOGRAPH - 0x8AE7: 0x5A44, //CJK UNIFIED IDEOGRAPH - 0x8AE8: 0x5A45, //CJK UNIFIED IDEOGRAPH - 0x8AE9: 0x5A47, //CJK UNIFIED IDEOGRAPH - 0x8AEA: 0x5A48, //CJK UNIFIED IDEOGRAPH - 0x8AEB: 0x5A4B, //CJK UNIFIED IDEOGRAPH - 0x8AEC: 0x5A4C, //CJK UNIFIED IDEOGRAPH - 0x8AED: 0x5A4D, //CJK UNIFIED IDEOGRAPH - 0x8AEE: 0x5A4E, //CJK UNIFIED IDEOGRAPH - 0x8AEF: 0x5A4F, //CJK UNIFIED IDEOGRAPH - 0x8AF0: 0x5A50, //CJK UNIFIED IDEOGRAPH - 0x8AF1: 0x5A51, //CJK UNIFIED IDEOGRAPH - 0x8AF2: 0x5A52, //CJK UNIFIED IDEOGRAPH - 0x8AF3: 0x5A53, //CJK UNIFIED IDEOGRAPH - 0x8AF4: 0x5A54, //CJK UNIFIED IDEOGRAPH - 0x8AF5: 0x5A56, //CJK UNIFIED IDEOGRAPH - 0x8AF6: 0x5A57, //CJK UNIFIED IDEOGRAPH - 0x8AF7: 0x5A58, //CJK UNIFIED IDEOGRAPH - 0x8AF8: 0x5A59, //CJK UNIFIED IDEOGRAPH - 0x8AF9: 0x5A5B, //CJK UNIFIED IDEOGRAPH - 0x8AFA: 0x5A5C, //CJK UNIFIED IDEOGRAPH - 0x8AFB: 0x5A5D, //CJK UNIFIED IDEOGRAPH - 0x8AFC: 0x5A5E, //CJK UNIFIED IDEOGRAPH - 0x8AFD: 0x5A5F, //CJK UNIFIED IDEOGRAPH - 0x8AFE: 0x5A60, //CJK UNIFIED IDEOGRAPH - 0x8B40: 0x5A61, //CJK UNIFIED IDEOGRAPH - 0x8B41: 0x5A63, //CJK UNIFIED IDEOGRAPH - 0x8B42: 0x5A64, //CJK UNIFIED IDEOGRAPH - 0x8B43: 0x5A65, //CJK UNIFIED IDEOGRAPH - 0x8B44: 0x5A66, //CJK UNIFIED IDEOGRAPH - 0x8B45: 0x5A68, //CJK UNIFIED IDEOGRAPH - 0x8B46: 0x5A69, //CJK UNIFIED IDEOGRAPH - 0x8B47: 0x5A6B, //CJK UNIFIED IDEOGRAPH - 0x8B48: 0x5A6C, //CJK UNIFIED IDEOGRAPH - 0x8B49: 0x5A6D, //CJK UNIFIED IDEOGRAPH - 0x8B4A: 0x5A6E, //CJK UNIFIED IDEOGRAPH - 0x8B4B: 0x5A6F, //CJK UNIFIED IDEOGRAPH - 0x8B4C: 0x5A70, //CJK UNIFIED IDEOGRAPH - 0x8B4D: 0x5A71, //CJK UNIFIED IDEOGRAPH - 0x8B4E: 0x5A72, //CJK UNIFIED IDEOGRAPH - 0x8B4F: 0x5A73, //CJK UNIFIED IDEOGRAPH - 0x8B50: 0x5A78, //CJK UNIFIED IDEOGRAPH - 0x8B51: 0x5A79, //CJK UNIFIED IDEOGRAPH - 0x8B52: 0x5A7B, //CJK UNIFIED IDEOGRAPH - 0x8B53: 0x5A7C, //CJK UNIFIED IDEOGRAPH - 0x8B54: 0x5A7D, //CJK UNIFIED IDEOGRAPH - 0x8B55: 0x5A7E, //CJK UNIFIED IDEOGRAPH - 0x8B56: 0x5A80, //CJK UNIFIED IDEOGRAPH - 0x8B57: 0x5A81, //CJK UNIFIED IDEOGRAPH - 0x8B58: 0x5A82, //CJK UNIFIED IDEOGRAPH - 0x8B59: 0x5A83, //CJK UNIFIED IDEOGRAPH - 0x8B5A: 0x5A84, //CJK UNIFIED IDEOGRAPH - 0x8B5B: 0x5A85, //CJK UNIFIED IDEOGRAPH - 0x8B5C: 0x5A86, //CJK UNIFIED IDEOGRAPH - 0x8B5D: 0x5A87, //CJK UNIFIED IDEOGRAPH - 0x8B5E: 0x5A88, //CJK UNIFIED IDEOGRAPH - 0x8B5F: 0x5A89, //CJK UNIFIED IDEOGRAPH - 0x8B60: 0x5A8A, //CJK UNIFIED IDEOGRAPH - 0x8B61: 0x5A8B, //CJK UNIFIED IDEOGRAPH - 0x8B62: 0x5A8C, //CJK UNIFIED IDEOGRAPH - 0x8B63: 0x5A8D, //CJK UNIFIED IDEOGRAPH - 0x8B64: 0x5A8E, //CJK UNIFIED IDEOGRAPH - 0x8B65: 0x5A8F, //CJK UNIFIED IDEOGRAPH - 0x8B66: 0x5A90, //CJK UNIFIED IDEOGRAPH - 0x8B67: 0x5A91, //CJK UNIFIED IDEOGRAPH - 0x8B68: 0x5A93, //CJK UNIFIED IDEOGRAPH - 0x8B69: 0x5A94, //CJK UNIFIED IDEOGRAPH - 0x8B6A: 0x5A95, //CJK UNIFIED IDEOGRAPH - 0x8B6B: 0x5A96, //CJK UNIFIED IDEOGRAPH - 0x8B6C: 0x5A97, //CJK UNIFIED IDEOGRAPH - 0x8B6D: 0x5A98, //CJK UNIFIED IDEOGRAPH - 0x8B6E: 0x5A99, //CJK UNIFIED IDEOGRAPH - 0x8B6F: 0x5A9C, //CJK UNIFIED IDEOGRAPH - 0x8B70: 0x5A9D, //CJK UNIFIED IDEOGRAPH - 0x8B71: 0x5A9E, //CJK UNIFIED IDEOGRAPH - 0x8B72: 0x5A9F, //CJK UNIFIED IDEOGRAPH - 0x8B73: 0x5AA0, //CJK UNIFIED IDEOGRAPH - 0x8B74: 0x5AA1, //CJK UNIFIED IDEOGRAPH - 0x8B75: 0x5AA2, //CJK UNIFIED IDEOGRAPH - 0x8B76: 0x5AA3, //CJK UNIFIED IDEOGRAPH - 0x8B77: 0x5AA4, //CJK UNIFIED IDEOGRAPH - 0x8B78: 0x5AA5, //CJK UNIFIED IDEOGRAPH - 0x8B79: 0x5AA6, //CJK UNIFIED IDEOGRAPH - 0x8B7A: 0x5AA7, //CJK UNIFIED IDEOGRAPH - 0x8B7B: 0x5AA8, //CJK UNIFIED IDEOGRAPH - 0x8B7C: 0x5AA9, //CJK UNIFIED IDEOGRAPH - 0x8B7D: 0x5AAB, //CJK UNIFIED IDEOGRAPH - 0x8B7E: 0x5AAC, //CJK UNIFIED IDEOGRAPH - 0x8B80: 0x5AAD, //CJK UNIFIED IDEOGRAPH - 0x8B81: 0x5AAE, //CJK UNIFIED IDEOGRAPH - 0x8B82: 0x5AAF, //CJK UNIFIED IDEOGRAPH - 0x8B83: 0x5AB0, //CJK UNIFIED IDEOGRAPH - 0x8B84: 0x5AB1, //CJK UNIFIED IDEOGRAPH - 0x8B85: 0x5AB4, //CJK UNIFIED IDEOGRAPH - 0x8B86: 0x5AB6, //CJK UNIFIED IDEOGRAPH - 0x8B87: 0x5AB7, //CJK UNIFIED IDEOGRAPH - 0x8B88: 0x5AB9, //CJK UNIFIED IDEOGRAPH - 0x8B89: 0x5ABA, //CJK UNIFIED IDEOGRAPH - 0x8B8A: 0x5ABB, //CJK UNIFIED IDEOGRAPH - 0x8B8B: 0x5ABC, //CJK UNIFIED IDEOGRAPH - 0x8B8C: 0x5ABD, //CJK UNIFIED IDEOGRAPH - 0x8B8D: 0x5ABF, //CJK UNIFIED IDEOGRAPH - 0x8B8E: 0x5AC0, //CJK UNIFIED IDEOGRAPH - 0x8B8F: 0x5AC3, //CJK UNIFIED IDEOGRAPH - 0x8B90: 0x5AC4, //CJK UNIFIED IDEOGRAPH - 0x8B91: 0x5AC5, //CJK UNIFIED IDEOGRAPH - 0x8B92: 0x5AC6, //CJK UNIFIED IDEOGRAPH - 0x8B93: 0x5AC7, //CJK UNIFIED IDEOGRAPH - 0x8B94: 0x5AC8, //CJK UNIFIED IDEOGRAPH - 0x8B95: 0x5ACA, //CJK UNIFIED IDEOGRAPH - 0x8B96: 0x5ACB, //CJK UNIFIED IDEOGRAPH - 0x8B97: 0x5ACD, //CJK UNIFIED IDEOGRAPH - 0x8B98: 0x5ACE, //CJK UNIFIED IDEOGRAPH - 0x8B99: 0x5ACF, //CJK UNIFIED IDEOGRAPH - 0x8B9A: 0x5AD0, //CJK UNIFIED IDEOGRAPH - 0x8B9B: 0x5AD1, //CJK UNIFIED IDEOGRAPH - 0x8B9C: 0x5AD3, //CJK UNIFIED IDEOGRAPH - 0x8B9D: 0x5AD5, //CJK UNIFIED IDEOGRAPH - 0x8B9E: 0x5AD7, //CJK UNIFIED IDEOGRAPH - 0x8B9F: 0x5AD9, //CJK UNIFIED IDEOGRAPH - 0x8BA0: 0x5ADA, //CJK UNIFIED IDEOGRAPH - 0x8BA1: 0x5ADB, //CJK UNIFIED IDEOGRAPH - 0x8BA2: 0x5ADD, //CJK UNIFIED IDEOGRAPH - 0x8BA3: 0x5ADE, //CJK UNIFIED IDEOGRAPH - 0x8BA4: 0x5ADF, //CJK UNIFIED IDEOGRAPH - 0x8BA5: 0x5AE2, //CJK UNIFIED IDEOGRAPH - 0x8BA6: 0x5AE4, //CJK UNIFIED IDEOGRAPH - 0x8BA7: 0x5AE5, //CJK UNIFIED IDEOGRAPH - 0x8BA8: 0x5AE7, //CJK UNIFIED IDEOGRAPH - 0x8BA9: 0x5AE8, //CJK UNIFIED IDEOGRAPH - 0x8BAA: 0x5AEA, //CJK UNIFIED IDEOGRAPH - 0x8BAB: 0x5AEC, //CJK UNIFIED IDEOGRAPH - 0x8BAC: 0x5AED, //CJK UNIFIED IDEOGRAPH - 0x8BAD: 0x5AEE, //CJK UNIFIED IDEOGRAPH - 0x8BAE: 0x5AEF, //CJK UNIFIED IDEOGRAPH - 0x8BAF: 0x5AF0, //CJK UNIFIED IDEOGRAPH - 0x8BB0: 0x5AF2, //CJK UNIFIED IDEOGRAPH - 0x8BB1: 0x5AF3, //CJK UNIFIED IDEOGRAPH - 0x8BB2: 0x5AF4, //CJK UNIFIED IDEOGRAPH - 0x8BB3: 0x5AF5, //CJK UNIFIED IDEOGRAPH - 0x8BB4: 0x5AF6, //CJK UNIFIED IDEOGRAPH - 0x8BB5: 0x5AF7, //CJK UNIFIED IDEOGRAPH - 0x8BB6: 0x5AF8, //CJK UNIFIED IDEOGRAPH - 0x8BB7: 0x5AF9, //CJK UNIFIED IDEOGRAPH - 0x8BB8: 0x5AFA, //CJK UNIFIED IDEOGRAPH - 0x8BB9: 0x5AFB, //CJK UNIFIED IDEOGRAPH - 0x8BBA: 0x5AFC, //CJK UNIFIED IDEOGRAPH - 0x8BBB: 0x5AFD, //CJK UNIFIED IDEOGRAPH - 0x8BBC: 0x5AFE, //CJK UNIFIED IDEOGRAPH - 0x8BBD: 0x5AFF, //CJK UNIFIED IDEOGRAPH - 0x8BBE: 0x5B00, //CJK UNIFIED IDEOGRAPH - 0x8BBF: 0x5B01, //CJK UNIFIED IDEOGRAPH - 0x8BC0: 0x5B02, //CJK UNIFIED IDEOGRAPH - 0x8BC1: 0x5B03, //CJK UNIFIED IDEOGRAPH - 0x8BC2: 0x5B04, //CJK UNIFIED IDEOGRAPH - 0x8BC3: 0x5B05, //CJK UNIFIED IDEOGRAPH - 0x8BC4: 0x5B06, //CJK UNIFIED IDEOGRAPH - 0x8BC5: 0x5B07, //CJK UNIFIED IDEOGRAPH - 0x8BC6: 0x5B08, //CJK UNIFIED IDEOGRAPH - 0x8BC7: 0x5B0A, //CJK UNIFIED IDEOGRAPH - 0x8BC8: 0x5B0B, //CJK UNIFIED IDEOGRAPH - 0x8BC9: 0x5B0C, //CJK UNIFIED IDEOGRAPH - 0x8BCA: 0x5B0D, //CJK UNIFIED IDEOGRAPH - 0x8BCB: 0x5B0E, //CJK UNIFIED IDEOGRAPH - 0x8BCC: 0x5B0F, //CJK UNIFIED IDEOGRAPH - 0x8BCD: 0x5B10, //CJK UNIFIED IDEOGRAPH - 0x8BCE: 0x5B11, //CJK UNIFIED IDEOGRAPH - 0x8BCF: 0x5B12, //CJK UNIFIED IDEOGRAPH - 0x8BD0: 0x5B13, //CJK UNIFIED IDEOGRAPH - 0x8BD1: 0x5B14, //CJK UNIFIED IDEOGRAPH - 0x8BD2: 0x5B15, //CJK UNIFIED IDEOGRAPH - 0x8BD3: 0x5B18, //CJK UNIFIED IDEOGRAPH - 0x8BD4: 0x5B19, //CJK UNIFIED IDEOGRAPH - 0x8BD5: 0x5B1A, //CJK UNIFIED IDEOGRAPH - 0x8BD6: 0x5B1B, //CJK UNIFIED IDEOGRAPH - 0x8BD7: 0x5B1C, //CJK UNIFIED IDEOGRAPH - 0x8BD8: 0x5B1D, //CJK UNIFIED IDEOGRAPH - 0x8BD9: 0x5B1E, //CJK UNIFIED IDEOGRAPH - 0x8BDA: 0x5B1F, //CJK UNIFIED IDEOGRAPH - 0x8BDB: 0x5B20, //CJK UNIFIED IDEOGRAPH - 0x8BDC: 0x5B21, //CJK UNIFIED IDEOGRAPH - 0x8BDD: 0x5B22, //CJK UNIFIED IDEOGRAPH - 0x8BDE: 0x5B23, //CJK UNIFIED IDEOGRAPH - 0x8BDF: 0x5B24, //CJK UNIFIED IDEOGRAPH - 0x8BE0: 0x5B25, //CJK UNIFIED IDEOGRAPH - 0x8BE1: 0x5B26, //CJK UNIFIED IDEOGRAPH - 0x8BE2: 0x5B27, //CJK UNIFIED IDEOGRAPH - 0x8BE3: 0x5B28, //CJK UNIFIED IDEOGRAPH - 0x8BE4: 0x5B29, //CJK UNIFIED IDEOGRAPH - 0x8BE5: 0x5B2A, //CJK UNIFIED IDEOGRAPH - 0x8BE6: 0x5B2B, //CJK UNIFIED IDEOGRAPH - 0x8BE7: 0x5B2C, //CJK UNIFIED IDEOGRAPH - 0x8BE8: 0x5B2D, //CJK UNIFIED IDEOGRAPH - 0x8BE9: 0x5B2E, //CJK UNIFIED IDEOGRAPH - 0x8BEA: 0x5B2F, //CJK UNIFIED IDEOGRAPH - 0x8BEB: 0x5B30, //CJK UNIFIED IDEOGRAPH - 0x8BEC: 0x5B31, //CJK UNIFIED IDEOGRAPH - 0x8BED: 0x5B33, //CJK UNIFIED IDEOGRAPH - 0x8BEE: 0x5B35, //CJK UNIFIED IDEOGRAPH - 0x8BEF: 0x5B36, //CJK UNIFIED IDEOGRAPH - 0x8BF0: 0x5B38, //CJK UNIFIED IDEOGRAPH - 0x8BF1: 0x5B39, //CJK UNIFIED IDEOGRAPH - 0x8BF2: 0x5B3A, //CJK UNIFIED IDEOGRAPH - 0x8BF3: 0x5B3B, //CJK UNIFIED IDEOGRAPH - 0x8BF4: 0x5B3C, //CJK UNIFIED IDEOGRAPH - 0x8BF5: 0x5B3D, //CJK UNIFIED IDEOGRAPH - 0x8BF6: 0x5B3E, //CJK UNIFIED IDEOGRAPH - 0x8BF7: 0x5B3F, //CJK UNIFIED IDEOGRAPH - 0x8BF8: 0x5B41, //CJK UNIFIED IDEOGRAPH - 0x8BF9: 0x5B42, //CJK UNIFIED IDEOGRAPH - 0x8BFA: 0x5B43, //CJK UNIFIED IDEOGRAPH - 0x8BFB: 0x5B44, //CJK UNIFIED IDEOGRAPH - 0x8BFC: 0x5B45, //CJK UNIFIED IDEOGRAPH - 0x8BFD: 0x5B46, //CJK UNIFIED IDEOGRAPH - 0x8BFE: 0x5B47, //CJK UNIFIED IDEOGRAPH - 0x8C40: 0x5B48, //CJK UNIFIED IDEOGRAPH - 0x8C41: 0x5B49, //CJK UNIFIED IDEOGRAPH - 0x8C42: 0x5B4A, //CJK UNIFIED IDEOGRAPH - 0x8C43: 0x5B4B, //CJK UNIFIED IDEOGRAPH - 0x8C44: 0x5B4C, //CJK UNIFIED IDEOGRAPH - 0x8C45: 0x5B4D, //CJK UNIFIED IDEOGRAPH - 0x8C46: 0x5B4E, //CJK UNIFIED IDEOGRAPH - 0x8C47: 0x5B4F, //CJK UNIFIED IDEOGRAPH - 0x8C48: 0x5B52, //CJK UNIFIED IDEOGRAPH - 0x8C49: 0x5B56, //CJK UNIFIED IDEOGRAPH - 0x8C4A: 0x5B5E, //CJK UNIFIED IDEOGRAPH - 0x8C4B: 0x5B60, //CJK UNIFIED IDEOGRAPH - 0x8C4C: 0x5B61, //CJK UNIFIED IDEOGRAPH - 0x8C4D: 0x5B67, //CJK UNIFIED IDEOGRAPH - 0x8C4E: 0x5B68, //CJK UNIFIED IDEOGRAPH - 0x8C4F: 0x5B6B, //CJK UNIFIED IDEOGRAPH - 0x8C50: 0x5B6D, //CJK UNIFIED IDEOGRAPH - 0x8C51: 0x5B6E, //CJK UNIFIED IDEOGRAPH - 0x8C52: 0x5B6F, //CJK UNIFIED IDEOGRAPH - 0x8C53: 0x5B72, //CJK UNIFIED IDEOGRAPH - 0x8C54: 0x5B74, //CJK UNIFIED IDEOGRAPH - 0x8C55: 0x5B76, //CJK UNIFIED IDEOGRAPH - 0x8C56: 0x5B77, //CJK UNIFIED IDEOGRAPH - 0x8C57: 0x5B78, //CJK UNIFIED IDEOGRAPH - 0x8C58: 0x5B79, //CJK UNIFIED IDEOGRAPH - 0x8C59: 0x5B7B, //CJK UNIFIED IDEOGRAPH - 0x8C5A: 0x5B7C, //CJK UNIFIED IDEOGRAPH - 0x8C5B: 0x5B7E, //CJK UNIFIED IDEOGRAPH - 0x8C5C: 0x5B7F, //CJK UNIFIED IDEOGRAPH - 0x8C5D: 0x5B82, //CJK UNIFIED IDEOGRAPH - 0x8C5E: 0x5B86, //CJK UNIFIED IDEOGRAPH - 0x8C5F: 0x5B8A, //CJK UNIFIED IDEOGRAPH - 0x8C60: 0x5B8D, //CJK UNIFIED IDEOGRAPH - 0x8C61: 0x5B8E, //CJK UNIFIED IDEOGRAPH - 0x8C62: 0x5B90, //CJK UNIFIED IDEOGRAPH - 0x8C63: 0x5B91, //CJK UNIFIED IDEOGRAPH - 0x8C64: 0x5B92, //CJK UNIFIED IDEOGRAPH - 0x8C65: 0x5B94, //CJK UNIFIED IDEOGRAPH - 0x8C66: 0x5B96, //CJK UNIFIED IDEOGRAPH - 0x8C67: 0x5B9F, //CJK UNIFIED IDEOGRAPH - 0x8C68: 0x5BA7, //CJK UNIFIED IDEOGRAPH - 0x8C69: 0x5BA8, //CJK UNIFIED IDEOGRAPH - 0x8C6A: 0x5BA9, //CJK UNIFIED IDEOGRAPH - 0x8C6B: 0x5BAC, //CJK UNIFIED IDEOGRAPH - 0x8C6C: 0x5BAD, //CJK UNIFIED IDEOGRAPH - 0x8C6D: 0x5BAE, //CJK UNIFIED IDEOGRAPH - 0x8C6E: 0x5BAF, //CJK UNIFIED IDEOGRAPH - 0x8C6F: 0x5BB1, //CJK UNIFIED IDEOGRAPH - 0x8C70: 0x5BB2, //CJK UNIFIED IDEOGRAPH - 0x8C71: 0x5BB7, //CJK UNIFIED IDEOGRAPH - 0x8C72: 0x5BBA, //CJK UNIFIED IDEOGRAPH - 0x8C73: 0x5BBB, //CJK UNIFIED IDEOGRAPH - 0x8C74: 0x5BBC, //CJK UNIFIED IDEOGRAPH - 0x8C75: 0x5BC0, //CJK UNIFIED IDEOGRAPH - 0x8C76: 0x5BC1, //CJK UNIFIED IDEOGRAPH - 0x8C77: 0x5BC3, //CJK UNIFIED IDEOGRAPH - 0x8C78: 0x5BC8, //CJK UNIFIED IDEOGRAPH - 0x8C79: 0x5BC9, //CJK UNIFIED IDEOGRAPH - 0x8C7A: 0x5BCA, //CJK UNIFIED IDEOGRAPH - 0x8C7B: 0x5BCB, //CJK UNIFIED IDEOGRAPH - 0x8C7C: 0x5BCD, //CJK UNIFIED IDEOGRAPH - 0x8C7D: 0x5BCE, //CJK UNIFIED IDEOGRAPH - 0x8C7E: 0x5BCF, //CJK UNIFIED IDEOGRAPH - 0x8C80: 0x5BD1, //CJK UNIFIED IDEOGRAPH - 0x8C81: 0x5BD4, //CJK UNIFIED IDEOGRAPH - 0x8C82: 0x5BD5, //CJK UNIFIED IDEOGRAPH - 0x8C83: 0x5BD6, //CJK UNIFIED IDEOGRAPH - 0x8C84: 0x5BD7, //CJK UNIFIED IDEOGRAPH - 0x8C85: 0x5BD8, //CJK UNIFIED IDEOGRAPH - 0x8C86: 0x5BD9, //CJK UNIFIED IDEOGRAPH - 0x8C87: 0x5BDA, //CJK UNIFIED IDEOGRAPH - 0x8C88: 0x5BDB, //CJK UNIFIED IDEOGRAPH - 0x8C89: 0x5BDC, //CJK UNIFIED IDEOGRAPH - 0x8C8A: 0x5BE0, //CJK UNIFIED IDEOGRAPH - 0x8C8B: 0x5BE2, //CJK UNIFIED IDEOGRAPH - 0x8C8C: 0x5BE3, //CJK UNIFIED IDEOGRAPH - 0x8C8D: 0x5BE6, //CJK UNIFIED IDEOGRAPH - 0x8C8E: 0x5BE7, //CJK UNIFIED IDEOGRAPH - 0x8C8F: 0x5BE9, //CJK UNIFIED IDEOGRAPH - 0x8C90: 0x5BEA, //CJK UNIFIED IDEOGRAPH - 0x8C91: 0x5BEB, //CJK UNIFIED IDEOGRAPH - 0x8C92: 0x5BEC, //CJK UNIFIED IDEOGRAPH - 0x8C93: 0x5BED, //CJK UNIFIED IDEOGRAPH - 0x8C94: 0x5BEF, //CJK UNIFIED IDEOGRAPH - 0x8C95: 0x5BF1, //CJK UNIFIED IDEOGRAPH - 0x8C96: 0x5BF2, //CJK UNIFIED IDEOGRAPH - 0x8C97: 0x5BF3, //CJK UNIFIED IDEOGRAPH - 0x8C98: 0x5BF4, //CJK UNIFIED IDEOGRAPH - 0x8C99: 0x5BF5, //CJK UNIFIED IDEOGRAPH - 0x8C9A: 0x5BF6, //CJK UNIFIED IDEOGRAPH - 0x8C9B: 0x5BF7, //CJK UNIFIED IDEOGRAPH - 0x8C9C: 0x5BFD, //CJK UNIFIED IDEOGRAPH - 0x8C9D: 0x5BFE, //CJK UNIFIED IDEOGRAPH - 0x8C9E: 0x5C00, //CJK UNIFIED IDEOGRAPH - 0x8C9F: 0x5C02, //CJK UNIFIED IDEOGRAPH - 0x8CA0: 0x5C03, //CJK UNIFIED IDEOGRAPH - 0x8CA1: 0x5C05, //CJK UNIFIED IDEOGRAPH - 0x8CA2: 0x5C07, //CJK UNIFIED IDEOGRAPH - 0x8CA3: 0x5C08, //CJK UNIFIED IDEOGRAPH - 0x8CA4: 0x5C0B, //CJK UNIFIED IDEOGRAPH - 0x8CA5: 0x5C0C, //CJK UNIFIED IDEOGRAPH - 0x8CA6: 0x5C0D, //CJK UNIFIED IDEOGRAPH - 0x8CA7: 0x5C0E, //CJK UNIFIED IDEOGRAPH - 0x8CA8: 0x5C10, //CJK UNIFIED IDEOGRAPH - 0x8CA9: 0x5C12, //CJK UNIFIED IDEOGRAPH - 0x8CAA: 0x5C13, //CJK UNIFIED IDEOGRAPH - 0x8CAB: 0x5C17, //CJK UNIFIED IDEOGRAPH - 0x8CAC: 0x5C19, //CJK UNIFIED IDEOGRAPH - 0x8CAD: 0x5C1B, //CJK UNIFIED IDEOGRAPH - 0x8CAE: 0x5C1E, //CJK UNIFIED IDEOGRAPH - 0x8CAF: 0x5C1F, //CJK UNIFIED IDEOGRAPH - 0x8CB0: 0x5C20, //CJK UNIFIED IDEOGRAPH - 0x8CB1: 0x5C21, //CJK UNIFIED IDEOGRAPH - 0x8CB2: 0x5C23, //CJK UNIFIED IDEOGRAPH - 0x8CB3: 0x5C26, //CJK UNIFIED IDEOGRAPH - 0x8CB4: 0x5C28, //CJK UNIFIED IDEOGRAPH - 0x8CB5: 0x5C29, //CJK UNIFIED IDEOGRAPH - 0x8CB6: 0x5C2A, //CJK UNIFIED IDEOGRAPH - 0x8CB7: 0x5C2B, //CJK UNIFIED IDEOGRAPH - 0x8CB8: 0x5C2D, //CJK UNIFIED IDEOGRAPH - 0x8CB9: 0x5C2E, //CJK UNIFIED IDEOGRAPH - 0x8CBA: 0x5C2F, //CJK UNIFIED IDEOGRAPH - 0x8CBB: 0x5C30, //CJK UNIFIED IDEOGRAPH - 0x8CBC: 0x5C32, //CJK UNIFIED IDEOGRAPH - 0x8CBD: 0x5C33, //CJK UNIFIED IDEOGRAPH - 0x8CBE: 0x5C35, //CJK UNIFIED IDEOGRAPH - 0x8CBF: 0x5C36, //CJK UNIFIED IDEOGRAPH - 0x8CC0: 0x5C37, //CJK UNIFIED IDEOGRAPH - 0x8CC1: 0x5C43, //CJK UNIFIED IDEOGRAPH - 0x8CC2: 0x5C44, //CJK UNIFIED IDEOGRAPH - 0x8CC3: 0x5C46, //CJK UNIFIED IDEOGRAPH - 0x8CC4: 0x5C47, //CJK UNIFIED IDEOGRAPH - 0x8CC5: 0x5C4C, //CJK UNIFIED IDEOGRAPH - 0x8CC6: 0x5C4D, //CJK UNIFIED IDEOGRAPH - 0x8CC7: 0x5C52, //CJK UNIFIED IDEOGRAPH - 0x8CC8: 0x5C53, //CJK UNIFIED IDEOGRAPH - 0x8CC9: 0x5C54, //CJK UNIFIED IDEOGRAPH - 0x8CCA: 0x5C56, //CJK UNIFIED IDEOGRAPH - 0x8CCB: 0x5C57, //CJK UNIFIED IDEOGRAPH - 0x8CCC: 0x5C58, //CJK UNIFIED IDEOGRAPH - 0x8CCD: 0x5C5A, //CJK UNIFIED IDEOGRAPH - 0x8CCE: 0x5C5B, //CJK UNIFIED IDEOGRAPH - 0x8CCF: 0x5C5C, //CJK UNIFIED IDEOGRAPH - 0x8CD0: 0x5C5D, //CJK UNIFIED IDEOGRAPH - 0x8CD1: 0x5C5F, //CJK UNIFIED IDEOGRAPH - 0x8CD2: 0x5C62, //CJK UNIFIED IDEOGRAPH - 0x8CD3: 0x5C64, //CJK UNIFIED IDEOGRAPH - 0x8CD4: 0x5C67, //CJK UNIFIED IDEOGRAPH - 0x8CD5: 0x5C68, //CJK UNIFIED IDEOGRAPH - 0x8CD6: 0x5C69, //CJK UNIFIED IDEOGRAPH - 0x8CD7: 0x5C6A, //CJK UNIFIED IDEOGRAPH - 0x8CD8: 0x5C6B, //CJK UNIFIED IDEOGRAPH - 0x8CD9: 0x5C6C, //CJK UNIFIED IDEOGRAPH - 0x8CDA: 0x5C6D, //CJK UNIFIED IDEOGRAPH - 0x8CDB: 0x5C70, //CJK UNIFIED IDEOGRAPH - 0x8CDC: 0x5C72, //CJK UNIFIED IDEOGRAPH - 0x8CDD: 0x5C73, //CJK UNIFIED IDEOGRAPH - 0x8CDE: 0x5C74, //CJK UNIFIED IDEOGRAPH - 0x8CDF: 0x5C75, //CJK UNIFIED IDEOGRAPH - 0x8CE0: 0x5C76, //CJK UNIFIED IDEOGRAPH - 0x8CE1: 0x5C77, //CJK UNIFIED IDEOGRAPH - 0x8CE2: 0x5C78, //CJK UNIFIED IDEOGRAPH - 0x8CE3: 0x5C7B, //CJK UNIFIED IDEOGRAPH - 0x8CE4: 0x5C7C, //CJK UNIFIED IDEOGRAPH - 0x8CE5: 0x5C7D, //CJK UNIFIED IDEOGRAPH - 0x8CE6: 0x5C7E, //CJK UNIFIED IDEOGRAPH - 0x8CE7: 0x5C80, //CJK UNIFIED IDEOGRAPH - 0x8CE8: 0x5C83, //CJK UNIFIED IDEOGRAPH - 0x8CE9: 0x5C84, //CJK UNIFIED IDEOGRAPH - 0x8CEA: 0x5C85, //CJK UNIFIED IDEOGRAPH - 0x8CEB: 0x5C86, //CJK UNIFIED IDEOGRAPH - 0x8CEC: 0x5C87, //CJK UNIFIED IDEOGRAPH - 0x8CED: 0x5C89, //CJK UNIFIED IDEOGRAPH - 0x8CEE: 0x5C8A, //CJK UNIFIED IDEOGRAPH - 0x8CEF: 0x5C8B, //CJK UNIFIED IDEOGRAPH - 0x8CF0: 0x5C8E, //CJK UNIFIED IDEOGRAPH - 0x8CF1: 0x5C8F, //CJK UNIFIED IDEOGRAPH - 0x8CF2: 0x5C92, //CJK UNIFIED IDEOGRAPH - 0x8CF3: 0x5C93, //CJK UNIFIED IDEOGRAPH - 0x8CF4: 0x5C95, //CJK UNIFIED IDEOGRAPH - 0x8CF5: 0x5C9D, //CJK UNIFIED IDEOGRAPH - 0x8CF6: 0x5C9E, //CJK UNIFIED IDEOGRAPH - 0x8CF7: 0x5C9F, //CJK UNIFIED IDEOGRAPH - 0x8CF8: 0x5CA0, //CJK UNIFIED IDEOGRAPH - 0x8CF9: 0x5CA1, //CJK UNIFIED IDEOGRAPH - 0x8CFA: 0x5CA4, //CJK UNIFIED IDEOGRAPH - 0x8CFB: 0x5CA5, //CJK UNIFIED IDEOGRAPH - 0x8CFC: 0x5CA6, //CJK UNIFIED IDEOGRAPH - 0x8CFD: 0x5CA7, //CJK UNIFIED IDEOGRAPH - 0x8CFE: 0x5CA8, //CJK UNIFIED IDEOGRAPH - 0x8D40: 0x5CAA, //CJK UNIFIED IDEOGRAPH - 0x8D41: 0x5CAE, //CJK UNIFIED IDEOGRAPH - 0x8D42: 0x5CAF, //CJK UNIFIED IDEOGRAPH - 0x8D43: 0x5CB0, //CJK UNIFIED IDEOGRAPH - 0x8D44: 0x5CB2, //CJK UNIFIED IDEOGRAPH - 0x8D45: 0x5CB4, //CJK UNIFIED IDEOGRAPH - 0x8D46: 0x5CB6, //CJK UNIFIED IDEOGRAPH - 0x8D47: 0x5CB9, //CJK UNIFIED IDEOGRAPH - 0x8D48: 0x5CBA, //CJK UNIFIED IDEOGRAPH - 0x8D49: 0x5CBB, //CJK UNIFIED IDEOGRAPH - 0x8D4A: 0x5CBC, //CJK UNIFIED IDEOGRAPH - 0x8D4B: 0x5CBE, //CJK UNIFIED IDEOGRAPH - 0x8D4C: 0x5CC0, //CJK UNIFIED IDEOGRAPH - 0x8D4D: 0x5CC2, //CJK UNIFIED IDEOGRAPH - 0x8D4E: 0x5CC3, //CJK UNIFIED IDEOGRAPH - 0x8D4F: 0x5CC5, //CJK UNIFIED IDEOGRAPH - 0x8D50: 0x5CC6, //CJK UNIFIED IDEOGRAPH - 0x8D51: 0x5CC7, //CJK UNIFIED IDEOGRAPH - 0x8D52: 0x5CC8, //CJK UNIFIED IDEOGRAPH - 0x8D53: 0x5CC9, //CJK UNIFIED IDEOGRAPH - 0x8D54: 0x5CCA, //CJK UNIFIED IDEOGRAPH - 0x8D55: 0x5CCC, //CJK UNIFIED IDEOGRAPH - 0x8D56: 0x5CCD, //CJK UNIFIED IDEOGRAPH - 0x8D57: 0x5CCE, //CJK UNIFIED IDEOGRAPH - 0x8D58: 0x5CCF, //CJK UNIFIED IDEOGRAPH - 0x8D59: 0x5CD0, //CJK UNIFIED IDEOGRAPH - 0x8D5A: 0x5CD1, //CJK UNIFIED IDEOGRAPH - 0x8D5B: 0x5CD3, //CJK UNIFIED IDEOGRAPH - 0x8D5C: 0x5CD4, //CJK UNIFIED IDEOGRAPH - 0x8D5D: 0x5CD5, //CJK UNIFIED IDEOGRAPH - 0x8D5E: 0x5CD6, //CJK UNIFIED IDEOGRAPH - 0x8D5F: 0x5CD7, //CJK UNIFIED IDEOGRAPH - 0x8D60: 0x5CD8, //CJK UNIFIED IDEOGRAPH - 0x8D61: 0x5CDA, //CJK UNIFIED IDEOGRAPH - 0x8D62: 0x5CDB, //CJK UNIFIED IDEOGRAPH - 0x8D63: 0x5CDC, //CJK UNIFIED IDEOGRAPH - 0x8D64: 0x5CDD, //CJK UNIFIED IDEOGRAPH - 0x8D65: 0x5CDE, //CJK UNIFIED IDEOGRAPH - 0x8D66: 0x5CDF, //CJK UNIFIED IDEOGRAPH - 0x8D67: 0x5CE0, //CJK UNIFIED IDEOGRAPH - 0x8D68: 0x5CE2, //CJK UNIFIED IDEOGRAPH - 0x8D69: 0x5CE3, //CJK UNIFIED IDEOGRAPH - 0x8D6A: 0x5CE7, //CJK UNIFIED IDEOGRAPH - 0x8D6B: 0x5CE9, //CJK UNIFIED IDEOGRAPH - 0x8D6C: 0x5CEB, //CJK UNIFIED IDEOGRAPH - 0x8D6D: 0x5CEC, //CJK UNIFIED IDEOGRAPH - 0x8D6E: 0x5CEE, //CJK UNIFIED IDEOGRAPH - 0x8D6F: 0x5CEF, //CJK UNIFIED IDEOGRAPH - 0x8D70: 0x5CF1, //CJK UNIFIED IDEOGRAPH - 0x8D71: 0x5CF2, //CJK UNIFIED IDEOGRAPH - 0x8D72: 0x5CF3, //CJK UNIFIED IDEOGRAPH - 0x8D73: 0x5CF4, //CJK UNIFIED IDEOGRAPH - 0x8D74: 0x5CF5, //CJK UNIFIED IDEOGRAPH - 0x8D75: 0x5CF6, //CJK UNIFIED IDEOGRAPH - 0x8D76: 0x5CF7, //CJK UNIFIED IDEOGRAPH - 0x8D77: 0x5CF8, //CJK UNIFIED IDEOGRAPH - 0x8D78: 0x5CF9, //CJK UNIFIED IDEOGRAPH - 0x8D79: 0x5CFA, //CJK UNIFIED IDEOGRAPH - 0x8D7A: 0x5CFC, //CJK UNIFIED IDEOGRAPH - 0x8D7B: 0x5CFD, //CJK UNIFIED IDEOGRAPH - 0x8D7C: 0x5CFE, //CJK UNIFIED IDEOGRAPH - 0x8D7D: 0x5CFF, //CJK UNIFIED IDEOGRAPH - 0x8D7E: 0x5D00, //CJK UNIFIED IDEOGRAPH - 0x8D80: 0x5D01, //CJK UNIFIED IDEOGRAPH - 0x8D81: 0x5D04, //CJK UNIFIED IDEOGRAPH - 0x8D82: 0x5D05, //CJK UNIFIED IDEOGRAPH - 0x8D83: 0x5D08, //CJK UNIFIED IDEOGRAPH - 0x8D84: 0x5D09, //CJK UNIFIED IDEOGRAPH - 0x8D85: 0x5D0A, //CJK UNIFIED IDEOGRAPH - 0x8D86: 0x5D0B, //CJK UNIFIED IDEOGRAPH - 0x8D87: 0x5D0C, //CJK UNIFIED IDEOGRAPH - 0x8D88: 0x5D0D, //CJK UNIFIED IDEOGRAPH - 0x8D89: 0x5D0F, //CJK UNIFIED IDEOGRAPH - 0x8D8A: 0x5D10, //CJK UNIFIED IDEOGRAPH - 0x8D8B: 0x5D11, //CJK UNIFIED IDEOGRAPH - 0x8D8C: 0x5D12, //CJK UNIFIED IDEOGRAPH - 0x8D8D: 0x5D13, //CJK UNIFIED IDEOGRAPH - 0x8D8E: 0x5D15, //CJK UNIFIED IDEOGRAPH - 0x8D8F: 0x5D17, //CJK UNIFIED IDEOGRAPH - 0x8D90: 0x5D18, //CJK UNIFIED IDEOGRAPH - 0x8D91: 0x5D19, //CJK UNIFIED IDEOGRAPH - 0x8D92: 0x5D1A, //CJK UNIFIED IDEOGRAPH - 0x8D93: 0x5D1C, //CJK UNIFIED IDEOGRAPH - 0x8D94: 0x5D1D, //CJK UNIFIED IDEOGRAPH - 0x8D95: 0x5D1F, //CJK UNIFIED IDEOGRAPH - 0x8D96: 0x5D20, //CJK UNIFIED IDEOGRAPH - 0x8D97: 0x5D21, //CJK UNIFIED IDEOGRAPH - 0x8D98: 0x5D22, //CJK UNIFIED IDEOGRAPH - 0x8D99: 0x5D23, //CJK UNIFIED IDEOGRAPH - 0x8D9A: 0x5D25, //CJK UNIFIED IDEOGRAPH - 0x8D9B: 0x5D28, //CJK UNIFIED IDEOGRAPH - 0x8D9C: 0x5D2A, //CJK UNIFIED IDEOGRAPH - 0x8D9D: 0x5D2B, //CJK UNIFIED IDEOGRAPH - 0x8D9E: 0x5D2C, //CJK UNIFIED IDEOGRAPH - 0x8D9F: 0x5D2F, //CJK UNIFIED IDEOGRAPH - 0x8DA0: 0x5D30, //CJK UNIFIED IDEOGRAPH - 0x8DA1: 0x5D31, //CJK UNIFIED IDEOGRAPH - 0x8DA2: 0x5D32, //CJK UNIFIED IDEOGRAPH - 0x8DA3: 0x5D33, //CJK UNIFIED IDEOGRAPH - 0x8DA4: 0x5D35, //CJK UNIFIED IDEOGRAPH - 0x8DA5: 0x5D36, //CJK UNIFIED IDEOGRAPH - 0x8DA6: 0x5D37, //CJK UNIFIED IDEOGRAPH - 0x8DA7: 0x5D38, //CJK UNIFIED IDEOGRAPH - 0x8DA8: 0x5D39, //CJK UNIFIED IDEOGRAPH - 0x8DA9: 0x5D3A, //CJK UNIFIED IDEOGRAPH - 0x8DAA: 0x5D3B, //CJK UNIFIED IDEOGRAPH - 0x8DAB: 0x5D3C, //CJK UNIFIED IDEOGRAPH - 0x8DAC: 0x5D3F, //CJK UNIFIED IDEOGRAPH - 0x8DAD: 0x5D40, //CJK UNIFIED IDEOGRAPH - 0x8DAE: 0x5D41, //CJK UNIFIED IDEOGRAPH - 0x8DAF: 0x5D42, //CJK UNIFIED IDEOGRAPH - 0x8DB0: 0x5D43, //CJK UNIFIED IDEOGRAPH - 0x8DB1: 0x5D44, //CJK UNIFIED IDEOGRAPH - 0x8DB2: 0x5D45, //CJK UNIFIED IDEOGRAPH - 0x8DB3: 0x5D46, //CJK UNIFIED IDEOGRAPH - 0x8DB4: 0x5D48, //CJK UNIFIED IDEOGRAPH - 0x8DB5: 0x5D49, //CJK UNIFIED IDEOGRAPH - 0x8DB6: 0x5D4D, //CJK UNIFIED IDEOGRAPH - 0x8DB7: 0x5D4E, //CJK UNIFIED IDEOGRAPH - 0x8DB8: 0x5D4F, //CJK UNIFIED IDEOGRAPH - 0x8DB9: 0x5D50, //CJK UNIFIED IDEOGRAPH - 0x8DBA: 0x5D51, //CJK UNIFIED IDEOGRAPH - 0x8DBB: 0x5D52, //CJK UNIFIED IDEOGRAPH - 0x8DBC: 0x5D53, //CJK UNIFIED IDEOGRAPH - 0x8DBD: 0x5D54, //CJK UNIFIED IDEOGRAPH - 0x8DBE: 0x5D55, //CJK UNIFIED IDEOGRAPH - 0x8DBF: 0x5D56, //CJK UNIFIED IDEOGRAPH - 0x8DC0: 0x5D57, //CJK UNIFIED IDEOGRAPH - 0x8DC1: 0x5D59, //CJK UNIFIED IDEOGRAPH - 0x8DC2: 0x5D5A, //CJK UNIFIED IDEOGRAPH - 0x8DC3: 0x5D5C, //CJK UNIFIED IDEOGRAPH - 0x8DC4: 0x5D5E, //CJK UNIFIED IDEOGRAPH - 0x8DC5: 0x5D5F, //CJK UNIFIED IDEOGRAPH - 0x8DC6: 0x5D60, //CJK UNIFIED IDEOGRAPH - 0x8DC7: 0x5D61, //CJK UNIFIED IDEOGRAPH - 0x8DC8: 0x5D62, //CJK UNIFIED IDEOGRAPH - 0x8DC9: 0x5D63, //CJK UNIFIED IDEOGRAPH - 0x8DCA: 0x5D64, //CJK UNIFIED IDEOGRAPH - 0x8DCB: 0x5D65, //CJK UNIFIED IDEOGRAPH - 0x8DCC: 0x5D66, //CJK UNIFIED IDEOGRAPH - 0x8DCD: 0x5D67, //CJK UNIFIED IDEOGRAPH - 0x8DCE: 0x5D68, //CJK UNIFIED IDEOGRAPH - 0x8DCF: 0x5D6A, //CJK UNIFIED IDEOGRAPH - 0x8DD0: 0x5D6D, //CJK UNIFIED IDEOGRAPH - 0x8DD1: 0x5D6E, //CJK UNIFIED IDEOGRAPH - 0x8DD2: 0x5D70, //CJK UNIFIED IDEOGRAPH - 0x8DD3: 0x5D71, //CJK UNIFIED IDEOGRAPH - 0x8DD4: 0x5D72, //CJK UNIFIED IDEOGRAPH - 0x8DD5: 0x5D73, //CJK UNIFIED IDEOGRAPH - 0x8DD6: 0x5D75, //CJK UNIFIED IDEOGRAPH - 0x8DD7: 0x5D76, //CJK UNIFIED IDEOGRAPH - 0x8DD8: 0x5D77, //CJK UNIFIED IDEOGRAPH - 0x8DD9: 0x5D78, //CJK UNIFIED IDEOGRAPH - 0x8DDA: 0x5D79, //CJK UNIFIED IDEOGRAPH - 0x8DDB: 0x5D7A, //CJK UNIFIED IDEOGRAPH - 0x8DDC: 0x5D7B, //CJK UNIFIED IDEOGRAPH - 0x8DDD: 0x5D7C, //CJK UNIFIED IDEOGRAPH - 0x8DDE: 0x5D7D, //CJK UNIFIED IDEOGRAPH - 0x8DDF: 0x5D7E, //CJK UNIFIED IDEOGRAPH - 0x8DE0: 0x5D7F, //CJK UNIFIED IDEOGRAPH - 0x8DE1: 0x5D80, //CJK UNIFIED IDEOGRAPH - 0x8DE2: 0x5D81, //CJK UNIFIED IDEOGRAPH - 0x8DE3: 0x5D83, //CJK UNIFIED IDEOGRAPH - 0x8DE4: 0x5D84, //CJK UNIFIED IDEOGRAPH - 0x8DE5: 0x5D85, //CJK UNIFIED IDEOGRAPH - 0x8DE6: 0x5D86, //CJK UNIFIED IDEOGRAPH - 0x8DE7: 0x5D87, //CJK UNIFIED IDEOGRAPH - 0x8DE8: 0x5D88, //CJK UNIFIED IDEOGRAPH - 0x8DE9: 0x5D89, //CJK UNIFIED IDEOGRAPH - 0x8DEA: 0x5D8A, //CJK UNIFIED IDEOGRAPH - 0x8DEB: 0x5D8B, //CJK UNIFIED IDEOGRAPH - 0x8DEC: 0x5D8C, //CJK UNIFIED IDEOGRAPH - 0x8DED: 0x5D8D, //CJK UNIFIED IDEOGRAPH - 0x8DEE: 0x5D8E, //CJK UNIFIED IDEOGRAPH - 0x8DEF: 0x5D8F, //CJK UNIFIED IDEOGRAPH - 0x8DF0: 0x5D90, //CJK UNIFIED IDEOGRAPH - 0x8DF1: 0x5D91, //CJK UNIFIED IDEOGRAPH - 0x8DF2: 0x5D92, //CJK UNIFIED IDEOGRAPH - 0x8DF3: 0x5D93, //CJK UNIFIED IDEOGRAPH - 0x8DF4: 0x5D94, //CJK UNIFIED IDEOGRAPH - 0x8DF5: 0x5D95, //CJK UNIFIED IDEOGRAPH - 0x8DF6: 0x5D96, //CJK UNIFIED IDEOGRAPH - 0x8DF7: 0x5D97, //CJK UNIFIED IDEOGRAPH - 0x8DF8: 0x5D98, //CJK UNIFIED IDEOGRAPH - 0x8DF9: 0x5D9A, //CJK UNIFIED IDEOGRAPH - 0x8DFA: 0x5D9B, //CJK UNIFIED IDEOGRAPH - 0x8DFB: 0x5D9C, //CJK UNIFIED IDEOGRAPH - 0x8DFC: 0x5D9E, //CJK UNIFIED IDEOGRAPH - 0x8DFD: 0x5D9F, //CJK UNIFIED IDEOGRAPH - 0x8DFE: 0x5DA0, //CJK UNIFIED IDEOGRAPH - 0x8E40: 0x5DA1, //CJK UNIFIED IDEOGRAPH - 0x8E41: 0x5DA2, //CJK UNIFIED IDEOGRAPH - 0x8E42: 0x5DA3, //CJK UNIFIED IDEOGRAPH - 0x8E43: 0x5DA4, //CJK UNIFIED IDEOGRAPH - 0x8E44: 0x5DA5, //CJK UNIFIED IDEOGRAPH - 0x8E45: 0x5DA6, //CJK UNIFIED IDEOGRAPH - 0x8E46: 0x5DA7, //CJK UNIFIED IDEOGRAPH - 0x8E47: 0x5DA8, //CJK UNIFIED IDEOGRAPH - 0x8E48: 0x5DA9, //CJK UNIFIED IDEOGRAPH - 0x8E49: 0x5DAA, //CJK UNIFIED IDEOGRAPH - 0x8E4A: 0x5DAB, //CJK UNIFIED IDEOGRAPH - 0x8E4B: 0x5DAC, //CJK UNIFIED IDEOGRAPH - 0x8E4C: 0x5DAD, //CJK UNIFIED IDEOGRAPH - 0x8E4D: 0x5DAE, //CJK UNIFIED IDEOGRAPH - 0x8E4E: 0x5DAF, //CJK UNIFIED IDEOGRAPH - 0x8E4F: 0x5DB0, //CJK UNIFIED IDEOGRAPH - 0x8E50: 0x5DB1, //CJK UNIFIED IDEOGRAPH - 0x8E51: 0x5DB2, //CJK UNIFIED IDEOGRAPH - 0x8E52: 0x5DB3, //CJK UNIFIED IDEOGRAPH - 0x8E53: 0x5DB4, //CJK UNIFIED IDEOGRAPH - 0x8E54: 0x5DB5, //CJK UNIFIED IDEOGRAPH - 0x8E55: 0x5DB6, //CJK UNIFIED IDEOGRAPH - 0x8E56: 0x5DB8, //CJK UNIFIED IDEOGRAPH - 0x8E57: 0x5DB9, //CJK UNIFIED IDEOGRAPH - 0x8E58: 0x5DBA, //CJK UNIFIED IDEOGRAPH - 0x8E59: 0x5DBB, //CJK UNIFIED IDEOGRAPH - 0x8E5A: 0x5DBC, //CJK UNIFIED IDEOGRAPH - 0x8E5B: 0x5DBD, //CJK UNIFIED IDEOGRAPH - 0x8E5C: 0x5DBE, //CJK UNIFIED IDEOGRAPH - 0x8E5D: 0x5DBF, //CJK UNIFIED IDEOGRAPH - 0x8E5E: 0x5DC0, //CJK UNIFIED IDEOGRAPH - 0x8E5F: 0x5DC1, //CJK UNIFIED IDEOGRAPH - 0x8E60: 0x5DC2, //CJK UNIFIED IDEOGRAPH - 0x8E61: 0x5DC3, //CJK UNIFIED IDEOGRAPH - 0x8E62: 0x5DC4, //CJK UNIFIED IDEOGRAPH - 0x8E63: 0x5DC6, //CJK UNIFIED IDEOGRAPH - 0x8E64: 0x5DC7, //CJK UNIFIED IDEOGRAPH - 0x8E65: 0x5DC8, //CJK UNIFIED IDEOGRAPH - 0x8E66: 0x5DC9, //CJK UNIFIED IDEOGRAPH - 0x8E67: 0x5DCA, //CJK UNIFIED IDEOGRAPH - 0x8E68: 0x5DCB, //CJK UNIFIED IDEOGRAPH - 0x8E69: 0x5DCC, //CJK UNIFIED IDEOGRAPH - 0x8E6A: 0x5DCE, //CJK UNIFIED IDEOGRAPH - 0x8E6B: 0x5DCF, //CJK UNIFIED IDEOGRAPH - 0x8E6C: 0x5DD0, //CJK UNIFIED IDEOGRAPH - 0x8E6D: 0x5DD1, //CJK UNIFIED IDEOGRAPH - 0x8E6E: 0x5DD2, //CJK UNIFIED IDEOGRAPH - 0x8E6F: 0x5DD3, //CJK UNIFIED IDEOGRAPH - 0x8E70: 0x5DD4, //CJK UNIFIED IDEOGRAPH - 0x8E71: 0x5DD5, //CJK UNIFIED IDEOGRAPH - 0x8E72: 0x5DD6, //CJK UNIFIED IDEOGRAPH - 0x8E73: 0x5DD7, //CJK UNIFIED IDEOGRAPH - 0x8E74: 0x5DD8, //CJK UNIFIED IDEOGRAPH - 0x8E75: 0x5DD9, //CJK UNIFIED IDEOGRAPH - 0x8E76: 0x5DDA, //CJK UNIFIED IDEOGRAPH - 0x8E77: 0x5DDC, //CJK UNIFIED IDEOGRAPH - 0x8E78: 0x5DDF, //CJK UNIFIED IDEOGRAPH - 0x8E79: 0x5DE0, //CJK UNIFIED IDEOGRAPH - 0x8E7A: 0x5DE3, //CJK UNIFIED IDEOGRAPH - 0x8E7B: 0x5DE4, //CJK UNIFIED IDEOGRAPH - 0x8E7C: 0x5DEA, //CJK UNIFIED IDEOGRAPH - 0x8E7D: 0x5DEC, //CJK UNIFIED IDEOGRAPH - 0x8E7E: 0x5DED, //CJK UNIFIED IDEOGRAPH - 0x8E80: 0x5DF0, //CJK UNIFIED IDEOGRAPH - 0x8E81: 0x5DF5, //CJK UNIFIED IDEOGRAPH - 0x8E82: 0x5DF6, //CJK UNIFIED IDEOGRAPH - 0x8E83: 0x5DF8, //CJK UNIFIED IDEOGRAPH - 0x8E84: 0x5DF9, //CJK UNIFIED IDEOGRAPH - 0x8E85: 0x5DFA, //CJK UNIFIED IDEOGRAPH - 0x8E86: 0x5DFB, //CJK UNIFIED IDEOGRAPH - 0x8E87: 0x5DFC, //CJK UNIFIED IDEOGRAPH - 0x8E88: 0x5DFF, //CJK UNIFIED IDEOGRAPH - 0x8E89: 0x5E00, //CJK UNIFIED IDEOGRAPH - 0x8E8A: 0x5E04, //CJK UNIFIED IDEOGRAPH - 0x8E8B: 0x5E07, //CJK UNIFIED IDEOGRAPH - 0x8E8C: 0x5E09, //CJK UNIFIED IDEOGRAPH - 0x8E8D: 0x5E0A, //CJK UNIFIED IDEOGRAPH - 0x8E8E: 0x5E0B, //CJK UNIFIED IDEOGRAPH - 0x8E8F: 0x5E0D, //CJK UNIFIED IDEOGRAPH - 0x8E90: 0x5E0E, //CJK UNIFIED IDEOGRAPH - 0x8E91: 0x5E12, //CJK UNIFIED IDEOGRAPH - 0x8E92: 0x5E13, //CJK UNIFIED IDEOGRAPH - 0x8E93: 0x5E17, //CJK UNIFIED IDEOGRAPH - 0x8E94: 0x5E1E, //CJK UNIFIED IDEOGRAPH - 0x8E95: 0x5E1F, //CJK UNIFIED IDEOGRAPH - 0x8E96: 0x5E20, //CJK UNIFIED IDEOGRAPH - 0x8E97: 0x5E21, //CJK UNIFIED IDEOGRAPH - 0x8E98: 0x5E22, //CJK UNIFIED IDEOGRAPH - 0x8E99: 0x5E23, //CJK UNIFIED IDEOGRAPH - 0x8E9A: 0x5E24, //CJK UNIFIED IDEOGRAPH - 0x8E9B: 0x5E25, //CJK UNIFIED IDEOGRAPH - 0x8E9C: 0x5E28, //CJK UNIFIED IDEOGRAPH - 0x8E9D: 0x5E29, //CJK UNIFIED IDEOGRAPH - 0x8E9E: 0x5E2A, //CJK UNIFIED IDEOGRAPH - 0x8E9F: 0x5E2B, //CJK UNIFIED IDEOGRAPH - 0x8EA0: 0x5E2C, //CJK UNIFIED IDEOGRAPH - 0x8EA1: 0x5E2F, //CJK UNIFIED IDEOGRAPH - 0x8EA2: 0x5E30, //CJK UNIFIED IDEOGRAPH - 0x8EA3: 0x5E32, //CJK UNIFIED IDEOGRAPH - 0x8EA4: 0x5E33, //CJK UNIFIED IDEOGRAPH - 0x8EA5: 0x5E34, //CJK UNIFIED IDEOGRAPH - 0x8EA6: 0x5E35, //CJK UNIFIED IDEOGRAPH - 0x8EA7: 0x5E36, //CJK UNIFIED IDEOGRAPH - 0x8EA8: 0x5E39, //CJK UNIFIED IDEOGRAPH - 0x8EA9: 0x5E3A, //CJK UNIFIED IDEOGRAPH - 0x8EAA: 0x5E3E, //CJK UNIFIED IDEOGRAPH - 0x8EAB: 0x5E3F, //CJK UNIFIED IDEOGRAPH - 0x8EAC: 0x5E40, //CJK UNIFIED IDEOGRAPH - 0x8EAD: 0x5E41, //CJK UNIFIED IDEOGRAPH - 0x8EAE: 0x5E43, //CJK UNIFIED IDEOGRAPH - 0x8EAF: 0x5E46, //CJK UNIFIED IDEOGRAPH - 0x8EB0: 0x5E47, //CJK UNIFIED IDEOGRAPH - 0x8EB1: 0x5E48, //CJK UNIFIED IDEOGRAPH - 0x8EB2: 0x5E49, //CJK UNIFIED IDEOGRAPH - 0x8EB3: 0x5E4A, //CJK UNIFIED IDEOGRAPH - 0x8EB4: 0x5E4B, //CJK UNIFIED IDEOGRAPH - 0x8EB5: 0x5E4D, //CJK UNIFIED IDEOGRAPH - 0x8EB6: 0x5E4E, //CJK UNIFIED IDEOGRAPH - 0x8EB7: 0x5E4F, //CJK UNIFIED IDEOGRAPH - 0x8EB8: 0x5E50, //CJK UNIFIED IDEOGRAPH - 0x8EB9: 0x5E51, //CJK UNIFIED IDEOGRAPH - 0x8EBA: 0x5E52, //CJK UNIFIED IDEOGRAPH - 0x8EBB: 0x5E53, //CJK UNIFIED IDEOGRAPH - 0x8EBC: 0x5E56, //CJK UNIFIED IDEOGRAPH - 0x8EBD: 0x5E57, //CJK UNIFIED IDEOGRAPH - 0x8EBE: 0x5E58, //CJK UNIFIED IDEOGRAPH - 0x8EBF: 0x5E59, //CJK UNIFIED IDEOGRAPH - 0x8EC0: 0x5E5A, //CJK UNIFIED IDEOGRAPH - 0x8EC1: 0x5E5C, //CJK UNIFIED IDEOGRAPH - 0x8EC2: 0x5E5D, //CJK UNIFIED IDEOGRAPH - 0x8EC3: 0x5E5F, //CJK UNIFIED IDEOGRAPH - 0x8EC4: 0x5E60, //CJK UNIFIED IDEOGRAPH - 0x8EC5: 0x5E63, //CJK UNIFIED IDEOGRAPH - 0x8EC6: 0x5E64, //CJK UNIFIED IDEOGRAPH - 0x8EC7: 0x5E65, //CJK UNIFIED IDEOGRAPH - 0x8EC8: 0x5E66, //CJK UNIFIED IDEOGRAPH - 0x8EC9: 0x5E67, //CJK UNIFIED IDEOGRAPH - 0x8ECA: 0x5E68, //CJK UNIFIED IDEOGRAPH - 0x8ECB: 0x5E69, //CJK UNIFIED IDEOGRAPH - 0x8ECC: 0x5E6A, //CJK UNIFIED IDEOGRAPH - 0x8ECD: 0x5E6B, //CJK UNIFIED IDEOGRAPH - 0x8ECE: 0x5E6C, //CJK UNIFIED IDEOGRAPH - 0x8ECF: 0x5E6D, //CJK UNIFIED IDEOGRAPH - 0x8ED0: 0x5E6E, //CJK UNIFIED IDEOGRAPH - 0x8ED1: 0x5E6F, //CJK UNIFIED IDEOGRAPH - 0x8ED2: 0x5E70, //CJK UNIFIED IDEOGRAPH - 0x8ED3: 0x5E71, //CJK UNIFIED IDEOGRAPH - 0x8ED4: 0x5E75, //CJK UNIFIED IDEOGRAPH - 0x8ED5: 0x5E77, //CJK UNIFIED IDEOGRAPH - 0x8ED6: 0x5E79, //CJK UNIFIED IDEOGRAPH - 0x8ED7: 0x5E7E, //CJK UNIFIED IDEOGRAPH - 0x8ED8: 0x5E81, //CJK UNIFIED IDEOGRAPH - 0x8ED9: 0x5E82, //CJK UNIFIED IDEOGRAPH - 0x8EDA: 0x5E83, //CJK UNIFIED IDEOGRAPH - 0x8EDB: 0x5E85, //CJK UNIFIED IDEOGRAPH - 0x8EDC: 0x5E88, //CJK UNIFIED IDEOGRAPH - 0x8EDD: 0x5E89, //CJK UNIFIED IDEOGRAPH - 0x8EDE: 0x5E8C, //CJK UNIFIED IDEOGRAPH - 0x8EDF: 0x5E8D, //CJK UNIFIED IDEOGRAPH - 0x8EE0: 0x5E8E, //CJK UNIFIED IDEOGRAPH - 0x8EE1: 0x5E92, //CJK UNIFIED IDEOGRAPH - 0x8EE2: 0x5E98, //CJK UNIFIED IDEOGRAPH - 0x8EE3: 0x5E9B, //CJK UNIFIED IDEOGRAPH - 0x8EE4: 0x5E9D, //CJK UNIFIED IDEOGRAPH - 0x8EE5: 0x5EA1, //CJK UNIFIED IDEOGRAPH - 0x8EE6: 0x5EA2, //CJK UNIFIED IDEOGRAPH - 0x8EE7: 0x5EA3, //CJK UNIFIED IDEOGRAPH - 0x8EE8: 0x5EA4, //CJK UNIFIED IDEOGRAPH - 0x8EE9: 0x5EA8, //CJK UNIFIED IDEOGRAPH - 0x8EEA: 0x5EA9, //CJK UNIFIED IDEOGRAPH - 0x8EEB: 0x5EAA, //CJK UNIFIED IDEOGRAPH - 0x8EEC: 0x5EAB, //CJK UNIFIED IDEOGRAPH - 0x8EED: 0x5EAC, //CJK UNIFIED IDEOGRAPH - 0x8EEE: 0x5EAE, //CJK UNIFIED IDEOGRAPH - 0x8EEF: 0x5EAF, //CJK UNIFIED IDEOGRAPH - 0x8EF0: 0x5EB0, //CJK UNIFIED IDEOGRAPH - 0x8EF1: 0x5EB1, //CJK UNIFIED IDEOGRAPH - 0x8EF2: 0x5EB2, //CJK UNIFIED IDEOGRAPH - 0x8EF3: 0x5EB4, //CJK UNIFIED IDEOGRAPH - 0x8EF4: 0x5EBA, //CJK UNIFIED IDEOGRAPH - 0x8EF5: 0x5EBB, //CJK UNIFIED IDEOGRAPH - 0x8EF6: 0x5EBC, //CJK UNIFIED IDEOGRAPH - 0x8EF7: 0x5EBD, //CJK UNIFIED IDEOGRAPH - 0x8EF8: 0x5EBF, //CJK UNIFIED IDEOGRAPH - 0x8EF9: 0x5EC0, //CJK UNIFIED IDEOGRAPH - 0x8EFA: 0x5EC1, //CJK UNIFIED IDEOGRAPH - 0x8EFB: 0x5EC2, //CJK UNIFIED IDEOGRAPH - 0x8EFC: 0x5EC3, //CJK UNIFIED IDEOGRAPH - 0x8EFD: 0x5EC4, //CJK UNIFIED IDEOGRAPH - 0x8EFE: 0x5EC5, //CJK UNIFIED IDEOGRAPH - 0x8F40: 0x5EC6, //CJK UNIFIED IDEOGRAPH - 0x8F41: 0x5EC7, //CJK UNIFIED IDEOGRAPH - 0x8F42: 0x5EC8, //CJK UNIFIED IDEOGRAPH - 0x8F43: 0x5ECB, //CJK UNIFIED IDEOGRAPH - 0x8F44: 0x5ECC, //CJK UNIFIED IDEOGRAPH - 0x8F45: 0x5ECD, //CJK UNIFIED IDEOGRAPH - 0x8F46: 0x5ECE, //CJK UNIFIED IDEOGRAPH - 0x8F47: 0x5ECF, //CJK UNIFIED IDEOGRAPH - 0x8F48: 0x5ED0, //CJK UNIFIED IDEOGRAPH - 0x8F49: 0x5ED4, //CJK UNIFIED IDEOGRAPH - 0x8F4A: 0x5ED5, //CJK UNIFIED IDEOGRAPH - 0x8F4B: 0x5ED7, //CJK UNIFIED IDEOGRAPH - 0x8F4C: 0x5ED8, //CJK UNIFIED IDEOGRAPH - 0x8F4D: 0x5ED9, //CJK UNIFIED IDEOGRAPH - 0x8F4E: 0x5EDA, //CJK UNIFIED IDEOGRAPH - 0x8F4F: 0x5EDC, //CJK UNIFIED IDEOGRAPH - 0x8F50: 0x5EDD, //CJK UNIFIED IDEOGRAPH - 0x8F51: 0x5EDE, //CJK UNIFIED IDEOGRAPH - 0x8F52: 0x5EDF, //CJK UNIFIED IDEOGRAPH - 0x8F53: 0x5EE0, //CJK UNIFIED IDEOGRAPH - 0x8F54: 0x5EE1, //CJK UNIFIED IDEOGRAPH - 0x8F55: 0x5EE2, //CJK UNIFIED IDEOGRAPH - 0x8F56: 0x5EE3, //CJK UNIFIED IDEOGRAPH - 0x8F57: 0x5EE4, //CJK UNIFIED IDEOGRAPH - 0x8F58: 0x5EE5, //CJK UNIFIED IDEOGRAPH - 0x8F59: 0x5EE6, //CJK UNIFIED IDEOGRAPH - 0x8F5A: 0x5EE7, //CJK UNIFIED IDEOGRAPH - 0x8F5B: 0x5EE9, //CJK UNIFIED IDEOGRAPH - 0x8F5C: 0x5EEB, //CJK UNIFIED IDEOGRAPH - 0x8F5D: 0x5EEC, //CJK UNIFIED IDEOGRAPH - 0x8F5E: 0x5EED, //CJK UNIFIED IDEOGRAPH - 0x8F5F: 0x5EEE, //CJK UNIFIED IDEOGRAPH - 0x8F60: 0x5EEF, //CJK UNIFIED IDEOGRAPH - 0x8F61: 0x5EF0, //CJK UNIFIED IDEOGRAPH - 0x8F62: 0x5EF1, //CJK UNIFIED IDEOGRAPH - 0x8F63: 0x5EF2, //CJK UNIFIED IDEOGRAPH - 0x8F64: 0x5EF3, //CJK UNIFIED IDEOGRAPH - 0x8F65: 0x5EF5, //CJK UNIFIED IDEOGRAPH - 0x8F66: 0x5EF8, //CJK UNIFIED IDEOGRAPH - 0x8F67: 0x5EF9, //CJK UNIFIED IDEOGRAPH - 0x8F68: 0x5EFB, //CJK UNIFIED IDEOGRAPH - 0x8F69: 0x5EFC, //CJK UNIFIED IDEOGRAPH - 0x8F6A: 0x5EFD, //CJK UNIFIED IDEOGRAPH - 0x8F6B: 0x5F05, //CJK UNIFIED IDEOGRAPH - 0x8F6C: 0x5F06, //CJK UNIFIED IDEOGRAPH - 0x8F6D: 0x5F07, //CJK UNIFIED IDEOGRAPH - 0x8F6E: 0x5F09, //CJK UNIFIED IDEOGRAPH - 0x8F6F: 0x5F0C, //CJK UNIFIED IDEOGRAPH - 0x8F70: 0x5F0D, //CJK UNIFIED IDEOGRAPH - 0x8F71: 0x5F0E, //CJK UNIFIED IDEOGRAPH - 0x8F72: 0x5F10, //CJK UNIFIED IDEOGRAPH - 0x8F73: 0x5F12, //CJK UNIFIED IDEOGRAPH - 0x8F74: 0x5F14, //CJK UNIFIED IDEOGRAPH - 0x8F75: 0x5F16, //CJK UNIFIED IDEOGRAPH - 0x8F76: 0x5F19, //CJK UNIFIED IDEOGRAPH - 0x8F77: 0x5F1A, //CJK UNIFIED IDEOGRAPH - 0x8F78: 0x5F1C, //CJK UNIFIED IDEOGRAPH - 0x8F79: 0x5F1D, //CJK UNIFIED IDEOGRAPH - 0x8F7A: 0x5F1E, //CJK UNIFIED IDEOGRAPH - 0x8F7B: 0x5F21, //CJK UNIFIED IDEOGRAPH - 0x8F7C: 0x5F22, //CJK UNIFIED IDEOGRAPH - 0x8F7D: 0x5F23, //CJK UNIFIED IDEOGRAPH - 0x8F7E: 0x5F24, //CJK UNIFIED IDEOGRAPH - 0x8F80: 0x5F28, //CJK UNIFIED IDEOGRAPH - 0x8F81: 0x5F2B, //CJK UNIFIED IDEOGRAPH - 0x8F82: 0x5F2C, //CJK UNIFIED IDEOGRAPH - 0x8F83: 0x5F2E, //CJK UNIFIED IDEOGRAPH - 0x8F84: 0x5F30, //CJK UNIFIED IDEOGRAPH - 0x8F85: 0x5F32, //CJK UNIFIED IDEOGRAPH - 0x8F86: 0x5F33, //CJK UNIFIED IDEOGRAPH - 0x8F87: 0x5F34, //CJK UNIFIED IDEOGRAPH - 0x8F88: 0x5F35, //CJK UNIFIED IDEOGRAPH - 0x8F89: 0x5F36, //CJK UNIFIED IDEOGRAPH - 0x8F8A: 0x5F37, //CJK UNIFIED IDEOGRAPH - 0x8F8B: 0x5F38, //CJK UNIFIED IDEOGRAPH - 0x8F8C: 0x5F3B, //CJK UNIFIED IDEOGRAPH - 0x8F8D: 0x5F3D, //CJK UNIFIED IDEOGRAPH - 0x8F8E: 0x5F3E, //CJK UNIFIED IDEOGRAPH - 0x8F8F: 0x5F3F, //CJK UNIFIED IDEOGRAPH - 0x8F90: 0x5F41, //CJK UNIFIED IDEOGRAPH - 0x8F91: 0x5F42, //CJK UNIFIED IDEOGRAPH - 0x8F92: 0x5F43, //CJK UNIFIED IDEOGRAPH - 0x8F93: 0x5F44, //CJK UNIFIED IDEOGRAPH - 0x8F94: 0x5F45, //CJK UNIFIED IDEOGRAPH - 0x8F95: 0x5F46, //CJK UNIFIED IDEOGRAPH - 0x8F96: 0x5F47, //CJK UNIFIED IDEOGRAPH - 0x8F97: 0x5F48, //CJK UNIFIED IDEOGRAPH - 0x8F98: 0x5F49, //CJK UNIFIED IDEOGRAPH - 0x8F99: 0x5F4A, //CJK UNIFIED IDEOGRAPH - 0x8F9A: 0x5F4B, //CJK UNIFIED IDEOGRAPH - 0x8F9B: 0x5F4C, //CJK UNIFIED IDEOGRAPH - 0x8F9C: 0x5F4D, //CJK UNIFIED IDEOGRAPH - 0x8F9D: 0x5F4E, //CJK UNIFIED IDEOGRAPH - 0x8F9E: 0x5F4F, //CJK UNIFIED IDEOGRAPH - 0x8F9F: 0x5F51, //CJK UNIFIED IDEOGRAPH - 0x8FA0: 0x5F54, //CJK UNIFIED IDEOGRAPH - 0x8FA1: 0x5F59, //CJK UNIFIED IDEOGRAPH - 0x8FA2: 0x5F5A, //CJK UNIFIED IDEOGRAPH - 0x8FA3: 0x5F5B, //CJK UNIFIED IDEOGRAPH - 0x8FA4: 0x5F5C, //CJK UNIFIED IDEOGRAPH - 0x8FA5: 0x5F5E, //CJK UNIFIED IDEOGRAPH - 0x8FA6: 0x5F5F, //CJK UNIFIED IDEOGRAPH - 0x8FA7: 0x5F60, //CJK UNIFIED IDEOGRAPH - 0x8FA8: 0x5F63, //CJK UNIFIED IDEOGRAPH - 0x8FA9: 0x5F65, //CJK UNIFIED IDEOGRAPH - 0x8FAA: 0x5F67, //CJK UNIFIED IDEOGRAPH - 0x8FAB: 0x5F68, //CJK UNIFIED IDEOGRAPH - 0x8FAC: 0x5F6B, //CJK UNIFIED IDEOGRAPH - 0x8FAD: 0x5F6E, //CJK UNIFIED IDEOGRAPH - 0x8FAE: 0x5F6F, //CJK UNIFIED IDEOGRAPH - 0x8FAF: 0x5F72, //CJK UNIFIED IDEOGRAPH - 0x8FB0: 0x5F74, //CJK UNIFIED IDEOGRAPH - 0x8FB1: 0x5F75, //CJK UNIFIED IDEOGRAPH - 0x8FB2: 0x5F76, //CJK UNIFIED IDEOGRAPH - 0x8FB3: 0x5F78, //CJK UNIFIED IDEOGRAPH - 0x8FB4: 0x5F7A, //CJK UNIFIED IDEOGRAPH - 0x8FB5: 0x5F7D, //CJK UNIFIED IDEOGRAPH - 0x8FB6: 0x5F7E, //CJK UNIFIED IDEOGRAPH - 0x8FB7: 0x5F7F, //CJK UNIFIED IDEOGRAPH - 0x8FB8: 0x5F83, //CJK UNIFIED IDEOGRAPH - 0x8FB9: 0x5F86, //CJK UNIFIED IDEOGRAPH - 0x8FBA: 0x5F8D, //CJK UNIFIED IDEOGRAPH - 0x8FBB: 0x5F8E, //CJK UNIFIED IDEOGRAPH - 0x8FBC: 0x5F8F, //CJK UNIFIED IDEOGRAPH - 0x8FBD: 0x5F91, //CJK UNIFIED IDEOGRAPH - 0x8FBE: 0x5F93, //CJK UNIFIED IDEOGRAPH - 0x8FBF: 0x5F94, //CJK UNIFIED IDEOGRAPH - 0x8FC0: 0x5F96, //CJK UNIFIED IDEOGRAPH - 0x8FC1: 0x5F9A, //CJK UNIFIED IDEOGRAPH - 0x8FC2: 0x5F9B, //CJK UNIFIED IDEOGRAPH - 0x8FC3: 0x5F9D, //CJK UNIFIED IDEOGRAPH - 0x8FC4: 0x5F9E, //CJK UNIFIED IDEOGRAPH - 0x8FC5: 0x5F9F, //CJK UNIFIED IDEOGRAPH - 0x8FC6: 0x5FA0, //CJK UNIFIED IDEOGRAPH - 0x8FC7: 0x5FA2, //CJK UNIFIED IDEOGRAPH - 0x8FC8: 0x5FA3, //CJK UNIFIED IDEOGRAPH - 0x8FC9: 0x5FA4, //CJK UNIFIED IDEOGRAPH - 0x8FCA: 0x5FA5, //CJK UNIFIED IDEOGRAPH - 0x8FCB: 0x5FA6, //CJK UNIFIED IDEOGRAPH - 0x8FCC: 0x5FA7, //CJK UNIFIED IDEOGRAPH - 0x8FCD: 0x5FA9, //CJK UNIFIED IDEOGRAPH - 0x8FCE: 0x5FAB, //CJK UNIFIED IDEOGRAPH - 0x8FCF: 0x5FAC, //CJK UNIFIED IDEOGRAPH - 0x8FD0: 0x5FAF, //CJK UNIFIED IDEOGRAPH - 0x8FD1: 0x5FB0, //CJK UNIFIED IDEOGRAPH - 0x8FD2: 0x5FB1, //CJK UNIFIED IDEOGRAPH - 0x8FD3: 0x5FB2, //CJK UNIFIED IDEOGRAPH - 0x8FD4: 0x5FB3, //CJK UNIFIED IDEOGRAPH - 0x8FD5: 0x5FB4, //CJK UNIFIED IDEOGRAPH - 0x8FD6: 0x5FB6, //CJK UNIFIED IDEOGRAPH - 0x8FD7: 0x5FB8, //CJK UNIFIED IDEOGRAPH - 0x8FD8: 0x5FB9, //CJK UNIFIED IDEOGRAPH - 0x8FD9: 0x5FBA, //CJK UNIFIED IDEOGRAPH - 0x8FDA: 0x5FBB, //CJK UNIFIED IDEOGRAPH - 0x8FDB: 0x5FBE, //CJK UNIFIED IDEOGRAPH - 0x8FDC: 0x5FBF, //CJK UNIFIED IDEOGRAPH - 0x8FDD: 0x5FC0, //CJK UNIFIED IDEOGRAPH - 0x8FDE: 0x5FC1, //CJK UNIFIED IDEOGRAPH - 0x8FDF: 0x5FC2, //CJK UNIFIED IDEOGRAPH - 0x8FE0: 0x5FC7, //CJK UNIFIED IDEOGRAPH - 0x8FE1: 0x5FC8, //CJK UNIFIED IDEOGRAPH - 0x8FE2: 0x5FCA, //CJK UNIFIED IDEOGRAPH - 0x8FE3: 0x5FCB, //CJK UNIFIED IDEOGRAPH - 0x8FE4: 0x5FCE, //CJK UNIFIED IDEOGRAPH - 0x8FE5: 0x5FD3, //CJK UNIFIED IDEOGRAPH - 0x8FE6: 0x5FD4, //CJK UNIFIED IDEOGRAPH - 0x8FE7: 0x5FD5, //CJK UNIFIED IDEOGRAPH - 0x8FE8: 0x5FDA, //CJK UNIFIED IDEOGRAPH - 0x8FE9: 0x5FDB, //CJK UNIFIED IDEOGRAPH - 0x8FEA: 0x5FDC, //CJK UNIFIED IDEOGRAPH - 0x8FEB: 0x5FDE, //CJK UNIFIED IDEOGRAPH - 0x8FEC: 0x5FDF, //CJK UNIFIED IDEOGRAPH - 0x8FED: 0x5FE2, //CJK UNIFIED IDEOGRAPH - 0x8FEE: 0x5FE3, //CJK UNIFIED IDEOGRAPH - 0x8FEF: 0x5FE5, //CJK UNIFIED IDEOGRAPH - 0x8FF0: 0x5FE6, //CJK UNIFIED IDEOGRAPH - 0x8FF1: 0x5FE8, //CJK UNIFIED IDEOGRAPH - 0x8FF2: 0x5FE9, //CJK UNIFIED IDEOGRAPH - 0x8FF3: 0x5FEC, //CJK UNIFIED IDEOGRAPH - 0x8FF4: 0x5FEF, //CJK UNIFIED IDEOGRAPH - 0x8FF5: 0x5FF0, //CJK UNIFIED IDEOGRAPH - 0x8FF6: 0x5FF2, //CJK UNIFIED IDEOGRAPH - 0x8FF7: 0x5FF3, //CJK UNIFIED IDEOGRAPH - 0x8FF8: 0x5FF4, //CJK UNIFIED IDEOGRAPH - 0x8FF9: 0x5FF6, //CJK UNIFIED IDEOGRAPH - 0x8FFA: 0x5FF7, //CJK UNIFIED IDEOGRAPH - 0x8FFB: 0x5FF9, //CJK UNIFIED IDEOGRAPH - 0x8FFC: 0x5FFA, //CJK UNIFIED IDEOGRAPH - 0x8FFD: 0x5FFC, //CJK UNIFIED IDEOGRAPH - 0x8FFE: 0x6007, //CJK UNIFIED IDEOGRAPH - 0x9040: 0x6008, //CJK UNIFIED IDEOGRAPH - 0x9041: 0x6009, //CJK UNIFIED IDEOGRAPH - 0x9042: 0x600B, //CJK UNIFIED IDEOGRAPH - 0x9043: 0x600C, //CJK UNIFIED IDEOGRAPH - 0x9044: 0x6010, //CJK UNIFIED IDEOGRAPH - 0x9045: 0x6011, //CJK UNIFIED IDEOGRAPH - 0x9046: 0x6013, //CJK UNIFIED IDEOGRAPH - 0x9047: 0x6017, //CJK UNIFIED IDEOGRAPH - 0x9048: 0x6018, //CJK UNIFIED IDEOGRAPH - 0x9049: 0x601A, //CJK UNIFIED IDEOGRAPH - 0x904A: 0x601E, //CJK UNIFIED IDEOGRAPH - 0x904B: 0x601F, //CJK UNIFIED IDEOGRAPH - 0x904C: 0x6022, //CJK UNIFIED IDEOGRAPH - 0x904D: 0x6023, //CJK UNIFIED IDEOGRAPH - 0x904E: 0x6024, //CJK UNIFIED IDEOGRAPH - 0x904F: 0x602C, //CJK UNIFIED IDEOGRAPH - 0x9050: 0x602D, //CJK UNIFIED IDEOGRAPH - 0x9051: 0x602E, //CJK UNIFIED IDEOGRAPH - 0x9052: 0x6030, //CJK UNIFIED IDEOGRAPH - 0x9053: 0x6031, //CJK UNIFIED IDEOGRAPH - 0x9054: 0x6032, //CJK UNIFIED IDEOGRAPH - 0x9055: 0x6033, //CJK UNIFIED IDEOGRAPH - 0x9056: 0x6034, //CJK UNIFIED IDEOGRAPH - 0x9057: 0x6036, //CJK UNIFIED IDEOGRAPH - 0x9058: 0x6037, //CJK UNIFIED IDEOGRAPH - 0x9059: 0x6038, //CJK UNIFIED IDEOGRAPH - 0x905A: 0x6039, //CJK UNIFIED IDEOGRAPH - 0x905B: 0x603A, //CJK UNIFIED IDEOGRAPH - 0x905C: 0x603D, //CJK UNIFIED IDEOGRAPH - 0x905D: 0x603E, //CJK UNIFIED IDEOGRAPH - 0x905E: 0x6040, //CJK UNIFIED IDEOGRAPH - 0x905F: 0x6044, //CJK UNIFIED IDEOGRAPH - 0x9060: 0x6045, //CJK UNIFIED IDEOGRAPH - 0x9061: 0x6046, //CJK UNIFIED IDEOGRAPH - 0x9062: 0x6047, //CJK UNIFIED IDEOGRAPH - 0x9063: 0x6048, //CJK UNIFIED IDEOGRAPH - 0x9064: 0x6049, //CJK UNIFIED IDEOGRAPH - 0x9065: 0x604A, //CJK UNIFIED IDEOGRAPH - 0x9066: 0x604C, //CJK UNIFIED IDEOGRAPH - 0x9067: 0x604E, //CJK UNIFIED IDEOGRAPH - 0x9068: 0x604F, //CJK UNIFIED IDEOGRAPH - 0x9069: 0x6051, //CJK UNIFIED IDEOGRAPH - 0x906A: 0x6053, //CJK UNIFIED IDEOGRAPH - 0x906B: 0x6054, //CJK UNIFIED IDEOGRAPH - 0x906C: 0x6056, //CJK UNIFIED IDEOGRAPH - 0x906D: 0x6057, //CJK UNIFIED IDEOGRAPH - 0x906E: 0x6058, //CJK UNIFIED IDEOGRAPH - 0x906F: 0x605B, //CJK UNIFIED IDEOGRAPH - 0x9070: 0x605C, //CJK UNIFIED IDEOGRAPH - 0x9071: 0x605E, //CJK UNIFIED IDEOGRAPH - 0x9072: 0x605F, //CJK UNIFIED IDEOGRAPH - 0x9073: 0x6060, //CJK UNIFIED IDEOGRAPH - 0x9074: 0x6061, //CJK UNIFIED IDEOGRAPH - 0x9075: 0x6065, //CJK UNIFIED IDEOGRAPH - 0x9076: 0x6066, //CJK UNIFIED IDEOGRAPH - 0x9077: 0x606E, //CJK UNIFIED IDEOGRAPH - 0x9078: 0x6071, //CJK UNIFIED IDEOGRAPH - 0x9079: 0x6072, //CJK UNIFIED IDEOGRAPH - 0x907A: 0x6074, //CJK UNIFIED IDEOGRAPH - 0x907B: 0x6075, //CJK UNIFIED IDEOGRAPH - 0x907C: 0x6077, //CJK UNIFIED IDEOGRAPH - 0x907D: 0x607E, //CJK UNIFIED IDEOGRAPH - 0x907E: 0x6080, //CJK UNIFIED IDEOGRAPH - 0x9080: 0x6081, //CJK UNIFIED IDEOGRAPH - 0x9081: 0x6082, //CJK UNIFIED IDEOGRAPH - 0x9082: 0x6085, //CJK UNIFIED IDEOGRAPH - 0x9083: 0x6086, //CJK UNIFIED IDEOGRAPH - 0x9084: 0x6087, //CJK UNIFIED IDEOGRAPH - 0x9085: 0x6088, //CJK UNIFIED IDEOGRAPH - 0x9086: 0x608A, //CJK UNIFIED IDEOGRAPH - 0x9087: 0x608B, //CJK UNIFIED IDEOGRAPH - 0x9088: 0x608E, //CJK UNIFIED IDEOGRAPH - 0x9089: 0x608F, //CJK UNIFIED IDEOGRAPH - 0x908A: 0x6090, //CJK UNIFIED IDEOGRAPH - 0x908B: 0x6091, //CJK UNIFIED IDEOGRAPH - 0x908C: 0x6093, //CJK UNIFIED IDEOGRAPH - 0x908D: 0x6095, //CJK UNIFIED IDEOGRAPH - 0x908E: 0x6097, //CJK UNIFIED IDEOGRAPH - 0x908F: 0x6098, //CJK UNIFIED IDEOGRAPH - 0x9090: 0x6099, //CJK UNIFIED IDEOGRAPH - 0x9091: 0x609C, //CJK UNIFIED IDEOGRAPH - 0x9092: 0x609E, //CJK UNIFIED IDEOGRAPH - 0x9093: 0x60A1, //CJK UNIFIED IDEOGRAPH - 0x9094: 0x60A2, //CJK UNIFIED IDEOGRAPH - 0x9095: 0x60A4, //CJK UNIFIED IDEOGRAPH - 0x9096: 0x60A5, //CJK UNIFIED IDEOGRAPH - 0x9097: 0x60A7, //CJK UNIFIED IDEOGRAPH - 0x9098: 0x60A9, //CJK UNIFIED IDEOGRAPH - 0x9099: 0x60AA, //CJK UNIFIED IDEOGRAPH - 0x909A: 0x60AE, //CJK UNIFIED IDEOGRAPH - 0x909B: 0x60B0, //CJK UNIFIED IDEOGRAPH - 0x909C: 0x60B3, //CJK UNIFIED IDEOGRAPH - 0x909D: 0x60B5, //CJK UNIFIED IDEOGRAPH - 0x909E: 0x60B6, //CJK UNIFIED IDEOGRAPH - 0x909F: 0x60B7, //CJK UNIFIED IDEOGRAPH - 0x90A0: 0x60B9, //CJK UNIFIED IDEOGRAPH - 0x90A1: 0x60BA, //CJK UNIFIED IDEOGRAPH - 0x90A2: 0x60BD, //CJK UNIFIED IDEOGRAPH - 0x90A3: 0x60BE, //CJK UNIFIED IDEOGRAPH - 0x90A4: 0x60BF, //CJK UNIFIED IDEOGRAPH - 0x90A5: 0x60C0, //CJK UNIFIED IDEOGRAPH - 0x90A6: 0x60C1, //CJK UNIFIED IDEOGRAPH - 0x90A7: 0x60C2, //CJK UNIFIED IDEOGRAPH - 0x90A8: 0x60C3, //CJK UNIFIED IDEOGRAPH - 0x90A9: 0x60C4, //CJK UNIFIED IDEOGRAPH - 0x90AA: 0x60C7, //CJK UNIFIED IDEOGRAPH - 0x90AB: 0x60C8, //CJK UNIFIED IDEOGRAPH - 0x90AC: 0x60C9, //CJK UNIFIED IDEOGRAPH - 0x90AD: 0x60CC, //CJK UNIFIED IDEOGRAPH - 0x90AE: 0x60CD, //CJK UNIFIED IDEOGRAPH - 0x90AF: 0x60CE, //CJK UNIFIED IDEOGRAPH - 0x90B0: 0x60CF, //CJK UNIFIED IDEOGRAPH - 0x90B1: 0x60D0, //CJK UNIFIED IDEOGRAPH - 0x90B2: 0x60D2, //CJK UNIFIED IDEOGRAPH - 0x90B3: 0x60D3, //CJK UNIFIED IDEOGRAPH - 0x90B4: 0x60D4, //CJK UNIFIED IDEOGRAPH - 0x90B5: 0x60D6, //CJK UNIFIED IDEOGRAPH - 0x90B6: 0x60D7, //CJK UNIFIED IDEOGRAPH - 0x90B7: 0x60D9, //CJK UNIFIED IDEOGRAPH - 0x90B8: 0x60DB, //CJK UNIFIED IDEOGRAPH - 0x90B9: 0x60DE, //CJK UNIFIED IDEOGRAPH - 0x90BA: 0x60E1, //CJK UNIFIED IDEOGRAPH - 0x90BB: 0x60E2, //CJK UNIFIED IDEOGRAPH - 0x90BC: 0x60E3, //CJK UNIFIED IDEOGRAPH - 0x90BD: 0x60E4, //CJK UNIFIED IDEOGRAPH - 0x90BE: 0x60E5, //CJK UNIFIED IDEOGRAPH - 0x90BF: 0x60EA, //CJK UNIFIED IDEOGRAPH - 0x90C0: 0x60F1, //CJK UNIFIED IDEOGRAPH - 0x90C1: 0x60F2, //CJK UNIFIED IDEOGRAPH - 0x90C2: 0x60F5, //CJK UNIFIED IDEOGRAPH - 0x90C3: 0x60F7, //CJK UNIFIED IDEOGRAPH - 0x90C4: 0x60F8, //CJK UNIFIED IDEOGRAPH - 0x90C5: 0x60FB, //CJK UNIFIED IDEOGRAPH - 0x90C6: 0x60FC, //CJK UNIFIED IDEOGRAPH - 0x90C7: 0x60FD, //CJK UNIFIED IDEOGRAPH - 0x90C8: 0x60FE, //CJK UNIFIED IDEOGRAPH - 0x90C9: 0x60FF, //CJK UNIFIED IDEOGRAPH - 0x90CA: 0x6102, //CJK UNIFIED IDEOGRAPH - 0x90CB: 0x6103, //CJK UNIFIED IDEOGRAPH - 0x90CC: 0x6104, //CJK UNIFIED IDEOGRAPH - 0x90CD: 0x6105, //CJK UNIFIED IDEOGRAPH - 0x90CE: 0x6107, //CJK UNIFIED IDEOGRAPH - 0x90CF: 0x610A, //CJK UNIFIED IDEOGRAPH - 0x90D0: 0x610B, //CJK UNIFIED IDEOGRAPH - 0x90D1: 0x610C, //CJK UNIFIED IDEOGRAPH - 0x90D2: 0x6110, //CJK UNIFIED IDEOGRAPH - 0x90D3: 0x6111, //CJK UNIFIED IDEOGRAPH - 0x90D4: 0x6112, //CJK UNIFIED IDEOGRAPH - 0x90D5: 0x6113, //CJK UNIFIED IDEOGRAPH - 0x90D6: 0x6114, //CJK UNIFIED IDEOGRAPH - 0x90D7: 0x6116, //CJK UNIFIED IDEOGRAPH - 0x90D8: 0x6117, //CJK UNIFIED IDEOGRAPH - 0x90D9: 0x6118, //CJK UNIFIED IDEOGRAPH - 0x90DA: 0x6119, //CJK UNIFIED IDEOGRAPH - 0x90DB: 0x611B, //CJK UNIFIED IDEOGRAPH - 0x90DC: 0x611C, //CJK UNIFIED IDEOGRAPH - 0x90DD: 0x611D, //CJK UNIFIED IDEOGRAPH - 0x90DE: 0x611E, //CJK UNIFIED IDEOGRAPH - 0x90DF: 0x6121, //CJK UNIFIED IDEOGRAPH - 0x90E0: 0x6122, //CJK UNIFIED IDEOGRAPH - 0x90E1: 0x6125, //CJK UNIFIED IDEOGRAPH - 0x90E2: 0x6128, //CJK UNIFIED IDEOGRAPH - 0x90E3: 0x6129, //CJK UNIFIED IDEOGRAPH - 0x90E4: 0x612A, //CJK UNIFIED IDEOGRAPH - 0x90E5: 0x612C, //CJK UNIFIED IDEOGRAPH - 0x90E6: 0x612D, //CJK UNIFIED IDEOGRAPH - 0x90E7: 0x612E, //CJK UNIFIED IDEOGRAPH - 0x90E8: 0x612F, //CJK UNIFIED IDEOGRAPH - 0x90E9: 0x6130, //CJK UNIFIED IDEOGRAPH - 0x90EA: 0x6131, //CJK UNIFIED IDEOGRAPH - 0x90EB: 0x6132, //CJK UNIFIED IDEOGRAPH - 0x90EC: 0x6133, //CJK UNIFIED IDEOGRAPH - 0x90ED: 0x6134, //CJK UNIFIED IDEOGRAPH - 0x90EE: 0x6135, //CJK UNIFIED IDEOGRAPH - 0x90EF: 0x6136, //CJK UNIFIED IDEOGRAPH - 0x90F0: 0x6137, //CJK UNIFIED IDEOGRAPH - 0x90F1: 0x6138, //CJK UNIFIED IDEOGRAPH - 0x90F2: 0x6139, //CJK UNIFIED IDEOGRAPH - 0x90F3: 0x613A, //CJK UNIFIED IDEOGRAPH - 0x90F4: 0x613B, //CJK UNIFIED IDEOGRAPH - 0x90F5: 0x613C, //CJK UNIFIED IDEOGRAPH - 0x90F6: 0x613D, //CJK UNIFIED IDEOGRAPH - 0x90F7: 0x613E, //CJK UNIFIED IDEOGRAPH - 0x90F8: 0x6140, //CJK UNIFIED IDEOGRAPH - 0x90F9: 0x6141, //CJK UNIFIED IDEOGRAPH - 0x90FA: 0x6142, //CJK UNIFIED IDEOGRAPH - 0x90FB: 0x6143, //CJK UNIFIED IDEOGRAPH - 0x90FC: 0x6144, //CJK UNIFIED IDEOGRAPH - 0x90FD: 0x6145, //CJK UNIFIED IDEOGRAPH - 0x90FE: 0x6146, //CJK UNIFIED IDEOGRAPH - 0x9140: 0x6147, //CJK UNIFIED IDEOGRAPH - 0x9141: 0x6149, //CJK UNIFIED IDEOGRAPH - 0x9142: 0x614B, //CJK UNIFIED IDEOGRAPH - 0x9143: 0x614D, //CJK UNIFIED IDEOGRAPH - 0x9144: 0x614F, //CJK UNIFIED IDEOGRAPH - 0x9145: 0x6150, //CJK UNIFIED IDEOGRAPH - 0x9146: 0x6152, //CJK UNIFIED IDEOGRAPH - 0x9147: 0x6153, //CJK UNIFIED IDEOGRAPH - 0x9148: 0x6154, //CJK UNIFIED IDEOGRAPH - 0x9149: 0x6156, //CJK UNIFIED IDEOGRAPH - 0x914A: 0x6157, //CJK UNIFIED IDEOGRAPH - 0x914B: 0x6158, //CJK UNIFIED IDEOGRAPH - 0x914C: 0x6159, //CJK UNIFIED IDEOGRAPH - 0x914D: 0x615A, //CJK UNIFIED IDEOGRAPH - 0x914E: 0x615B, //CJK UNIFIED IDEOGRAPH - 0x914F: 0x615C, //CJK UNIFIED IDEOGRAPH - 0x9150: 0x615E, //CJK UNIFIED IDEOGRAPH - 0x9151: 0x615F, //CJK UNIFIED IDEOGRAPH - 0x9152: 0x6160, //CJK UNIFIED IDEOGRAPH - 0x9153: 0x6161, //CJK UNIFIED IDEOGRAPH - 0x9154: 0x6163, //CJK UNIFIED IDEOGRAPH - 0x9155: 0x6164, //CJK UNIFIED IDEOGRAPH - 0x9156: 0x6165, //CJK UNIFIED IDEOGRAPH - 0x9157: 0x6166, //CJK UNIFIED IDEOGRAPH - 0x9158: 0x6169, //CJK UNIFIED IDEOGRAPH - 0x9159: 0x616A, //CJK UNIFIED IDEOGRAPH - 0x915A: 0x616B, //CJK UNIFIED IDEOGRAPH - 0x915B: 0x616C, //CJK UNIFIED IDEOGRAPH - 0x915C: 0x616D, //CJK UNIFIED IDEOGRAPH - 0x915D: 0x616E, //CJK UNIFIED IDEOGRAPH - 0x915E: 0x616F, //CJK UNIFIED IDEOGRAPH - 0x915F: 0x6171, //CJK UNIFIED IDEOGRAPH - 0x9160: 0x6172, //CJK UNIFIED IDEOGRAPH - 0x9161: 0x6173, //CJK UNIFIED IDEOGRAPH - 0x9162: 0x6174, //CJK UNIFIED IDEOGRAPH - 0x9163: 0x6176, //CJK UNIFIED IDEOGRAPH - 0x9164: 0x6178, //CJK UNIFIED IDEOGRAPH - 0x9165: 0x6179, //CJK UNIFIED IDEOGRAPH - 0x9166: 0x617A, //CJK UNIFIED IDEOGRAPH - 0x9167: 0x617B, //CJK UNIFIED IDEOGRAPH - 0x9168: 0x617C, //CJK UNIFIED IDEOGRAPH - 0x9169: 0x617D, //CJK UNIFIED IDEOGRAPH - 0x916A: 0x617E, //CJK UNIFIED IDEOGRAPH - 0x916B: 0x617F, //CJK UNIFIED IDEOGRAPH - 0x916C: 0x6180, //CJK UNIFIED IDEOGRAPH - 0x916D: 0x6181, //CJK UNIFIED IDEOGRAPH - 0x916E: 0x6182, //CJK UNIFIED IDEOGRAPH - 0x916F: 0x6183, //CJK UNIFIED IDEOGRAPH - 0x9170: 0x6184, //CJK UNIFIED IDEOGRAPH - 0x9171: 0x6185, //CJK UNIFIED IDEOGRAPH - 0x9172: 0x6186, //CJK UNIFIED IDEOGRAPH - 0x9173: 0x6187, //CJK UNIFIED IDEOGRAPH - 0x9174: 0x6188, //CJK UNIFIED IDEOGRAPH - 0x9175: 0x6189, //CJK UNIFIED IDEOGRAPH - 0x9176: 0x618A, //CJK UNIFIED IDEOGRAPH - 0x9177: 0x618C, //CJK UNIFIED IDEOGRAPH - 0x9178: 0x618D, //CJK UNIFIED IDEOGRAPH - 0x9179: 0x618F, //CJK UNIFIED IDEOGRAPH - 0x917A: 0x6190, //CJK UNIFIED IDEOGRAPH - 0x917B: 0x6191, //CJK UNIFIED IDEOGRAPH - 0x917C: 0x6192, //CJK UNIFIED IDEOGRAPH - 0x917D: 0x6193, //CJK UNIFIED IDEOGRAPH - 0x917E: 0x6195, //CJK UNIFIED IDEOGRAPH - 0x9180: 0x6196, //CJK UNIFIED IDEOGRAPH - 0x9181: 0x6197, //CJK UNIFIED IDEOGRAPH - 0x9182: 0x6198, //CJK UNIFIED IDEOGRAPH - 0x9183: 0x6199, //CJK UNIFIED IDEOGRAPH - 0x9184: 0x619A, //CJK UNIFIED IDEOGRAPH - 0x9185: 0x619B, //CJK UNIFIED IDEOGRAPH - 0x9186: 0x619C, //CJK UNIFIED IDEOGRAPH - 0x9187: 0x619E, //CJK UNIFIED IDEOGRAPH - 0x9188: 0x619F, //CJK UNIFIED IDEOGRAPH - 0x9189: 0x61A0, //CJK UNIFIED IDEOGRAPH - 0x918A: 0x61A1, //CJK UNIFIED IDEOGRAPH - 0x918B: 0x61A2, //CJK UNIFIED IDEOGRAPH - 0x918C: 0x61A3, //CJK UNIFIED IDEOGRAPH - 0x918D: 0x61A4, //CJK UNIFIED IDEOGRAPH - 0x918E: 0x61A5, //CJK UNIFIED IDEOGRAPH - 0x918F: 0x61A6, //CJK UNIFIED IDEOGRAPH - 0x9190: 0x61AA, //CJK UNIFIED IDEOGRAPH - 0x9191: 0x61AB, //CJK UNIFIED IDEOGRAPH - 0x9192: 0x61AD, //CJK UNIFIED IDEOGRAPH - 0x9193: 0x61AE, //CJK UNIFIED IDEOGRAPH - 0x9194: 0x61AF, //CJK UNIFIED IDEOGRAPH - 0x9195: 0x61B0, //CJK UNIFIED IDEOGRAPH - 0x9196: 0x61B1, //CJK UNIFIED IDEOGRAPH - 0x9197: 0x61B2, //CJK UNIFIED IDEOGRAPH - 0x9198: 0x61B3, //CJK UNIFIED IDEOGRAPH - 0x9199: 0x61B4, //CJK UNIFIED IDEOGRAPH - 0x919A: 0x61B5, //CJK UNIFIED IDEOGRAPH - 0x919B: 0x61B6, //CJK UNIFIED IDEOGRAPH - 0x919C: 0x61B8, //CJK UNIFIED IDEOGRAPH - 0x919D: 0x61B9, //CJK UNIFIED IDEOGRAPH - 0x919E: 0x61BA, //CJK UNIFIED IDEOGRAPH - 0x919F: 0x61BB, //CJK UNIFIED IDEOGRAPH - 0x91A0: 0x61BC, //CJK UNIFIED IDEOGRAPH - 0x91A1: 0x61BD, //CJK UNIFIED IDEOGRAPH - 0x91A2: 0x61BF, //CJK UNIFIED IDEOGRAPH - 0x91A3: 0x61C0, //CJK UNIFIED IDEOGRAPH - 0x91A4: 0x61C1, //CJK UNIFIED IDEOGRAPH - 0x91A5: 0x61C3, //CJK UNIFIED IDEOGRAPH - 0x91A6: 0x61C4, //CJK UNIFIED IDEOGRAPH - 0x91A7: 0x61C5, //CJK UNIFIED IDEOGRAPH - 0x91A8: 0x61C6, //CJK UNIFIED IDEOGRAPH - 0x91A9: 0x61C7, //CJK UNIFIED IDEOGRAPH - 0x91AA: 0x61C9, //CJK UNIFIED IDEOGRAPH - 0x91AB: 0x61CC, //CJK UNIFIED IDEOGRAPH - 0x91AC: 0x61CD, //CJK UNIFIED IDEOGRAPH - 0x91AD: 0x61CE, //CJK UNIFIED IDEOGRAPH - 0x91AE: 0x61CF, //CJK UNIFIED IDEOGRAPH - 0x91AF: 0x61D0, //CJK UNIFIED IDEOGRAPH - 0x91B0: 0x61D3, //CJK UNIFIED IDEOGRAPH - 0x91B1: 0x61D5, //CJK UNIFIED IDEOGRAPH - 0x91B2: 0x61D6, //CJK UNIFIED IDEOGRAPH - 0x91B3: 0x61D7, //CJK UNIFIED IDEOGRAPH - 0x91B4: 0x61D8, //CJK UNIFIED IDEOGRAPH - 0x91B5: 0x61D9, //CJK UNIFIED IDEOGRAPH - 0x91B6: 0x61DA, //CJK UNIFIED IDEOGRAPH - 0x91B7: 0x61DB, //CJK UNIFIED IDEOGRAPH - 0x91B8: 0x61DC, //CJK UNIFIED IDEOGRAPH - 0x91B9: 0x61DD, //CJK UNIFIED IDEOGRAPH - 0x91BA: 0x61DE, //CJK UNIFIED IDEOGRAPH - 0x91BB: 0x61DF, //CJK UNIFIED IDEOGRAPH - 0x91BC: 0x61E0, //CJK UNIFIED IDEOGRAPH - 0x91BD: 0x61E1, //CJK UNIFIED IDEOGRAPH - 0x91BE: 0x61E2, //CJK UNIFIED IDEOGRAPH - 0x91BF: 0x61E3, //CJK UNIFIED IDEOGRAPH - 0x91C0: 0x61E4, //CJK UNIFIED IDEOGRAPH - 0x91C1: 0x61E5, //CJK UNIFIED IDEOGRAPH - 0x91C2: 0x61E7, //CJK UNIFIED IDEOGRAPH - 0x91C3: 0x61E8, //CJK UNIFIED IDEOGRAPH - 0x91C4: 0x61E9, //CJK UNIFIED IDEOGRAPH - 0x91C5: 0x61EA, //CJK UNIFIED IDEOGRAPH - 0x91C6: 0x61EB, //CJK UNIFIED IDEOGRAPH - 0x91C7: 0x61EC, //CJK UNIFIED IDEOGRAPH - 0x91C8: 0x61ED, //CJK UNIFIED IDEOGRAPH - 0x91C9: 0x61EE, //CJK UNIFIED IDEOGRAPH - 0x91CA: 0x61EF, //CJK UNIFIED IDEOGRAPH - 0x91CB: 0x61F0, //CJK UNIFIED IDEOGRAPH - 0x91CC: 0x61F1, //CJK UNIFIED IDEOGRAPH - 0x91CD: 0x61F2, //CJK UNIFIED IDEOGRAPH - 0x91CE: 0x61F3, //CJK UNIFIED IDEOGRAPH - 0x91CF: 0x61F4, //CJK UNIFIED IDEOGRAPH - 0x91D0: 0x61F6, //CJK UNIFIED IDEOGRAPH - 0x91D1: 0x61F7, //CJK UNIFIED IDEOGRAPH - 0x91D2: 0x61F8, //CJK UNIFIED IDEOGRAPH - 0x91D3: 0x61F9, //CJK UNIFIED IDEOGRAPH - 0x91D4: 0x61FA, //CJK UNIFIED IDEOGRAPH - 0x91D5: 0x61FB, //CJK UNIFIED IDEOGRAPH - 0x91D6: 0x61FC, //CJK UNIFIED IDEOGRAPH - 0x91D7: 0x61FD, //CJK UNIFIED IDEOGRAPH - 0x91D8: 0x61FE, //CJK UNIFIED IDEOGRAPH - 0x91D9: 0x6200, //CJK UNIFIED IDEOGRAPH - 0x91DA: 0x6201, //CJK UNIFIED IDEOGRAPH - 0x91DB: 0x6202, //CJK UNIFIED IDEOGRAPH - 0x91DC: 0x6203, //CJK UNIFIED IDEOGRAPH - 0x91DD: 0x6204, //CJK UNIFIED IDEOGRAPH - 0x91DE: 0x6205, //CJK UNIFIED IDEOGRAPH - 0x91DF: 0x6207, //CJK UNIFIED IDEOGRAPH - 0x91E0: 0x6209, //CJK UNIFIED IDEOGRAPH - 0x91E1: 0x6213, //CJK UNIFIED IDEOGRAPH - 0x91E2: 0x6214, //CJK UNIFIED IDEOGRAPH - 0x91E3: 0x6219, //CJK UNIFIED IDEOGRAPH - 0x91E4: 0x621C, //CJK UNIFIED IDEOGRAPH - 0x91E5: 0x621D, //CJK UNIFIED IDEOGRAPH - 0x91E6: 0x621E, //CJK UNIFIED IDEOGRAPH - 0x91E7: 0x6220, //CJK UNIFIED IDEOGRAPH - 0x91E8: 0x6223, //CJK UNIFIED IDEOGRAPH - 0x91E9: 0x6226, //CJK UNIFIED IDEOGRAPH - 0x91EA: 0x6227, //CJK UNIFIED IDEOGRAPH - 0x91EB: 0x6228, //CJK UNIFIED IDEOGRAPH - 0x91EC: 0x6229, //CJK UNIFIED IDEOGRAPH - 0x91ED: 0x622B, //CJK UNIFIED IDEOGRAPH - 0x91EE: 0x622D, //CJK UNIFIED IDEOGRAPH - 0x91EF: 0x622F, //CJK UNIFIED IDEOGRAPH - 0x91F0: 0x6230, //CJK UNIFIED IDEOGRAPH - 0x91F1: 0x6231, //CJK UNIFIED IDEOGRAPH - 0x91F2: 0x6232, //CJK UNIFIED IDEOGRAPH - 0x91F3: 0x6235, //CJK UNIFIED IDEOGRAPH - 0x91F4: 0x6236, //CJK UNIFIED IDEOGRAPH - 0x91F5: 0x6238, //CJK UNIFIED IDEOGRAPH - 0x91F6: 0x6239, //CJK UNIFIED IDEOGRAPH - 0x91F7: 0x623A, //CJK UNIFIED IDEOGRAPH - 0x91F8: 0x623B, //CJK UNIFIED IDEOGRAPH - 0x91F9: 0x623C, //CJK UNIFIED IDEOGRAPH - 0x91FA: 0x6242, //CJK UNIFIED IDEOGRAPH - 0x91FB: 0x6244, //CJK UNIFIED IDEOGRAPH - 0x91FC: 0x6245, //CJK UNIFIED IDEOGRAPH - 0x91FD: 0x6246, //CJK UNIFIED IDEOGRAPH - 0x91FE: 0x624A, //CJK UNIFIED IDEOGRAPH - 0x9240: 0x624F, //CJK UNIFIED IDEOGRAPH - 0x9241: 0x6250, //CJK UNIFIED IDEOGRAPH - 0x9242: 0x6255, //CJK UNIFIED IDEOGRAPH - 0x9243: 0x6256, //CJK UNIFIED IDEOGRAPH - 0x9244: 0x6257, //CJK UNIFIED IDEOGRAPH - 0x9245: 0x6259, //CJK UNIFIED IDEOGRAPH - 0x9246: 0x625A, //CJK UNIFIED IDEOGRAPH - 0x9247: 0x625C, //CJK UNIFIED IDEOGRAPH - 0x9248: 0x625D, //CJK UNIFIED IDEOGRAPH - 0x9249: 0x625E, //CJK UNIFIED IDEOGRAPH - 0x924A: 0x625F, //CJK UNIFIED IDEOGRAPH - 0x924B: 0x6260, //CJK UNIFIED IDEOGRAPH - 0x924C: 0x6261, //CJK UNIFIED IDEOGRAPH - 0x924D: 0x6262, //CJK UNIFIED IDEOGRAPH - 0x924E: 0x6264, //CJK UNIFIED IDEOGRAPH - 0x924F: 0x6265, //CJK UNIFIED IDEOGRAPH - 0x9250: 0x6268, //CJK UNIFIED IDEOGRAPH - 0x9251: 0x6271, //CJK UNIFIED IDEOGRAPH - 0x9252: 0x6272, //CJK UNIFIED IDEOGRAPH - 0x9253: 0x6274, //CJK UNIFIED IDEOGRAPH - 0x9254: 0x6275, //CJK UNIFIED IDEOGRAPH - 0x9255: 0x6277, //CJK UNIFIED IDEOGRAPH - 0x9256: 0x6278, //CJK UNIFIED IDEOGRAPH - 0x9257: 0x627A, //CJK UNIFIED IDEOGRAPH - 0x9258: 0x627B, //CJK UNIFIED IDEOGRAPH - 0x9259: 0x627D, //CJK UNIFIED IDEOGRAPH - 0x925A: 0x6281, //CJK UNIFIED IDEOGRAPH - 0x925B: 0x6282, //CJK UNIFIED IDEOGRAPH - 0x925C: 0x6283, //CJK UNIFIED IDEOGRAPH - 0x925D: 0x6285, //CJK UNIFIED IDEOGRAPH - 0x925E: 0x6286, //CJK UNIFIED IDEOGRAPH - 0x925F: 0x6287, //CJK UNIFIED IDEOGRAPH - 0x9260: 0x6288, //CJK UNIFIED IDEOGRAPH - 0x9261: 0x628B, //CJK UNIFIED IDEOGRAPH - 0x9262: 0x628C, //CJK UNIFIED IDEOGRAPH - 0x9263: 0x628D, //CJK UNIFIED IDEOGRAPH - 0x9264: 0x628E, //CJK UNIFIED IDEOGRAPH - 0x9265: 0x628F, //CJK UNIFIED IDEOGRAPH - 0x9266: 0x6290, //CJK UNIFIED IDEOGRAPH - 0x9267: 0x6294, //CJK UNIFIED IDEOGRAPH - 0x9268: 0x6299, //CJK UNIFIED IDEOGRAPH - 0x9269: 0x629C, //CJK UNIFIED IDEOGRAPH - 0x926A: 0x629D, //CJK UNIFIED IDEOGRAPH - 0x926B: 0x629E, //CJK UNIFIED IDEOGRAPH - 0x926C: 0x62A3, //CJK UNIFIED IDEOGRAPH - 0x926D: 0x62A6, //CJK UNIFIED IDEOGRAPH - 0x926E: 0x62A7, //CJK UNIFIED IDEOGRAPH - 0x926F: 0x62A9, //CJK UNIFIED IDEOGRAPH - 0x9270: 0x62AA, //CJK UNIFIED IDEOGRAPH - 0x9271: 0x62AD, //CJK UNIFIED IDEOGRAPH - 0x9272: 0x62AE, //CJK UNIFIED IDEOGRAPH - 0x9273: 0x62AF, //CJK UNIFIED IDEOGRAPH - 0x9274: 0x62B0, //CJK UNIFIED IDEOGRAPH - 0x9275: 0x62B2, //CJK UNIFIED IDEOGRAPH - 0x9276: 0x62B3, //CJK UNIFIED IDEOGRAPH - 0x9277: 0x62B4, //CJK UNIFIED IDEOGRAPH - 0x9278: 0x62B6, //CJK UNIFIED IDEOGRAPH - 0x9279: 0x62B7, //CJK UNIFIED IDEOGRAPH - 0x927A: 0x62B8, //CJK UNIFIED IDEOGRAPH - 0x927B: 0x62BA, //CJK UNIFIED IDEOGRAPH - 0x927C: 0x62BE, //CJK UNIFIED IDEOGRAPH - 0x927D: 0x62C0, //CJK UNIFIED IDEOGRAPH - 0x927E: 0x62C1, //CJK UNIFIED IDEOGRAPH - 0x9280: 0x62C3, //CJK UNIFIED IDEOGRAPH - 0x9281: 0x62CB, //CJK UNIFIED IDEOGRAPH - 0x9282: 0x62CF, //CJK UNIFIED IDEOGRAPH - 0x9283: 0x62D1, //CJK UNIFIED IDEOGRAPH - 0x9284: 0x62D5, //CJK UNIFIED IDEOGRAPH - 0x9285: 0x62DD, //CJK UNIFIED IDEOGRAPH - 0x9286: 0x62DE, //CJK UNIFIED IDEOGRAPH - 0x9287: 0x62E0, //CJK UNIFIED IDEOGRAPH - 0x9288: 0x62E1, //CJK UNIFIED IDEOGRAPH - 0x9289: 0x62E4, //CJK UNIFIED IDEOGRAPH - 0x928A: 0x62EA, //CJK UNIFIED IDEOGRAPH - 0x928B: 0x62EB, //CJK UNIFIED IDEOGRAPH - 0x928C: 0x62F0, //CJK UNIFIED IDEOGRAPH - 0x928D: 0x62F2, //CJK UNIFIED IDEOGRAPH - 0x928E: 0x62F5, //CJK UNIFIED IDEOGRAPH - 0x928F: 0x62F8, //CJK UNIFIED IDEOGRAPH - 0x9290: 0x62F9, //CJK UNIFIED IDEOGRAPH - 0x9291: 0x62FA, //CJK UNIFIED IDEOGRAPH - 0x9292: 0x62FB, //CJK UNIFIED IDEOGRAPH - 0x9293: 0x6300, //CJK UNIFIED IDEOGRAPH - 0x9294: 0x6303, //CJK UNIFIED IDEOGRAPH - 0x9295: 0x6304, //CJK UNIFIED IDEOGRAPH - 0x9296: 0x6305, //CJK UNIFIED IDEOGRAPH - 0x9297: 0x6306, //CJK UNIFIED IDEOGRAPH - 0x9298: 0x630A, //CJK UNIFIED IDEOGRAPH - 0x9299: 0x630B, //CJK UNIFIED IDEOGRAPH - 0x929A: 0x630C, //CJK UNIFIED IDEOGRAPH - 0x929B: 0x630D, //CJK UNIFIED IDEOGRAPH - 0x929C: 0x630F, //CJK UNIFIED IDEOGRAPH - 0x929D: 0x6310, //CJK UNIFIED IDEOGRAPH - 0x929E: 0x6312, //CJK UNIFIED IDEOGRAPH - 0x929F: 0x6313, //CJK UNIFIED IDEOGRAPH - 0x92A0: 0x6314, //CJK UNIFIED IDEOGRAPH - 0x92A1: 0x6315, //CJK UNIFIED IDEOGRAPH - 0x92A2: 0x6317, //CJK UNIFIED IDEOGRAPH - 0x92A3: 0x6318, //CJK UNIFIED IDEOGRAPH - 0x92A4: 0x6319, //CJK UNIFIED IDEOGRAPH - 0x92A5: 0x631C, //CJK UNIFIED IDEOGRAPH - 0x92A6: 0x6326, //CJK UNIFIED IDEOGRAPH - 0x92A7: 0x6327, //CJK UNIFIED IDEOGRAPH - 0x92A8: 0x6329, //CJK UNIFIED IDEOGRAPH - 0x92A9: 0x632C, //CJK UNIFIED IDEOGRAPH - 0x92AA: 0x632D, //CJK UNIFIED IDEOGRAPH - 0x92AB: 0x632E, //CJK UNIFIED IDEOGRAPH - 0x92AC: 0x6330, //CJK UNIFIED IDEOGRAPH - 0x92AD: 0x6331, //CJK UNIFIED IDEOGRAPH - 0x92AE: 0x6333, //CJK UNIFIED IDEOGRAPH - 0x92AF: 0x6334, //CJK UNIFIED IDEOGRAPH - 0x92B0: 0x6335, //CJK UNIFIED IDEOGRAPH - 0x92B1: 0x6336, //CJK UNIFIED IDEOGRAPH - 0x92B2: 0x6337, //CJK UNIFIED IDEOGRAPH - 0x92B3: 0x6338, //CJK UNIFIED IDEOGRAPH - 0x92B4: 0x633B, //CJK UNIFIED IDEOGRAPH - 0x92B5: 0x633C, //CJK UNIFIED IDEOGRAPH - 0x92B6: 0x633E, //CJK UNIFIED IDEOGRAPH - 0x92B7: 0x633F, //CJK UNIFIED IDEOGRAPH - 0x92B8: 0x6340, //CJK UNIFIED IDEOGRAPH - 0x92B9: 0x6341, //CJK UNIFIED IDEOGRAPH - 0x92BA: 0x6344, //CJK UNIFIED IDEOGRAPH - 0x92BB: 0x6347, //CJK UNIFIED IDEOGRAPH - 0x92BC: 0x6348, //CJK UNIFIED IDEOGRAPH - 0x92BD: 0x634A, //CJK UNIFIED IDEOGRAPH - 0x92BE: 0x6351, //CJK UNIFIED IDEOGRAPH - 0x92BF: 0x6352, //CJK UNIFIED IDEOGRAPH - 0x92C0: 0x6353, //CJK UNIFIED IDEOGRAPH - 0x92C1: 0x6354, //CJK UNIFIED IDEOGRAPH - 0x92C2: 0x6356, //CJK UNIFIED IDEOGRAPH - 0x92C3: 0x6357, //CJK UNIFIED IDEOGRAPH - 0x92C4: 0x6358, //CJK UNIFIED IDEOGRAPH - 0x92C5: 0x6359, //CJK UNIFIED IDEOGRAPH - 0x92C6: 0x635A, //CJK UNIFIED IDEOGRAPH - 0x92C7: 0x635B, //CJK UNIFIED IDEOGRAPH - 0x92C8: 0x635C, //CJK UNIFIED IDEOGRAPH - 0x92C9: 0x635D, //CJK UNIFIED IDEOGRAPH - 0x92CA: 0x6360, //CJK UNIFIED IDEOGRAPH - 0x92CB: 0x6364, //CJK UNIFIED IDEOGRAPH - 0x92CC: 0x6365, //CJK UNIFIED IDEOGRAPH - 0x92CD: 0x6366, //CJK UNIFIED IDEOGRAPH - 0x92CE: 0x6368, //CJK UNIFIED IDEOGRAPH - 0x92CF: 0x636A, //CJK UNIFIED IDEOGRAPH - 0x92D0: 0x636B, //CJK UNIFIED IDEOGRAPH - 0x92D1: 0x636C, //CJK UNIFIED IDEOGRAPH - 0x92D2: 0x636F, //CJK UNIFIED IDEOGRAPH - 0x92D3: 0x6370, //CJK UNIFIED IDEOGRAPH - 0x92D4: 0x6372, //CJK UNIFIED IDEOGRAPH - 0x92D5: 0x6373, //CJK UNIFIED IDEOGRAPH - 0x92D6: 0x6374, //CJK UNIFIED IDEOGRAPH - 0x92D7: 0x6375, //CJK UNIFIED IDEOGRAPH - 0x92D8: 0x6378, //CJK UNIFIED IDEOGRAPH - 0x92D9: 0x6379, //CJK UNIFIED IDEOGRAPH - 0x92DA: 0x637C, //CJK UNIFIED IDEOGRAPH - 0x92DB: 0x637D, //CJK UNIFIED IDEOGRAPH - 0x92DC: 0x637E, //CJK UNIFIED IDEOGRAPH - 0x92DD: 0x637F, //CJK UNIFIED IDEOGRAPH - 0x92DE: 0x6381, //CJK UNIFIED IDEOGRAPH - 0x92DF: 0x6383, //CJK UNIFIED IDEOGRAPH - 0x92E0: 0x6384, //CJK UNIFIED IDEOGRAPH - 0x92E1: 0x6385, //CJK UNIFIED IDEOGRAPH - 0x92E2: 0x6386, //CJK UNIFIED IDEOGRAPH - 0x92E3: 0x638B, //CJK UNIFIED IDEOGRAPH - 0x92E4: 0x638D, //CJK UNIFIED IDEOGRAPH - 0x92E5: 0x6391, //CJK UNIFIED IDEOGRAPH - 0x92E6: 0x6393, //CJK UNIFIED IDEOGRAPH - 0x92E7: 0x6394, //CJK UNIFIED IDEOGRAPH - 0x92E8: 0x6395, //CJK UNIFIED IDEOGRAPH - 0x92E9: 0x6397, //CJK UNIFIED IDEOGRAPH - 0x92EA: 0x6399, //CJK UNIFIED IDEOGRAPH - 0x92EB: 0x639A, //CJK UNIFIED IDEOGRAPH - 0x92EC: 0x639B, //CJK UNIFIED IDEOGRAPH - 0x92ED: 0x639C, //CJK UNIFIED IDEOGRAPH - 0x92EE: 0x639D, //CJK UNIFIED IDEOGRAPH - 0x92EF: 0x639E, //CJK UNIFIED IDEOGRAPH - 0x92F0: 0x639F, //CJK UNIFIED IDEOGRAPH - 0x92F1: 0x63A1, //CJK UNIFIED IDEOGRAPH - 0x92F2: 0x63A4, //CJK UNIFIED IDEOGRAPH - 0x92F3: 0x63A6, //CJK UNIFIED IDEOGRAPH - 0x92F4: 0x63AB, //CJK UNIFIED IDEOGRAPH - 0x92F5: 0x63AF, //CJK UNIFIED IDEOGRAPH - 0x92F6: 0x63B1, //CJK UNIFIED IDEOGRAPH - 0x92F7: 0x63B2, //CJK UNIFIED IDEOGRAPH - 0x92F8: 0x63B5, //CJK UNIFIED IDEOGRAPH - 0x92F9: 0x63B6, //CJK UNIFIED IDEOGRAPH - 0x92FA: 0x63B9, //CJK UNIFIED IDEOGRAPH - 0x92FB: 0x63BB, //CJK UNIFIED IDEOGRAPH - 0x92FC: 0x63BD, //CJK UNIFIED IDEOGRAPH - 0x92FD: 0x63BF, //CJK UNIFIED IDEOGRAPH - 0x92FE: 0x63C0, //CJK UNIFIED IDEOGRAPH - 0x9340: 0x63C1, //CJK UNIFIED IDEOGRAPH - 0x9341: 0x63C2, //CJK UNIFIED IDEOGRAPH - 0x9342: 0x63C3, //CJK UNIFIED IDEOGRAPH - 0x9343: 0x63C5, //CJK UNIFIED IDEOGRAPH - 0x9344: 0x63C7, //CJK UNIFIED IDEOGRAPH - 0x9345: 0x63C8, //CJK UNIFIED IDEOGRAPH - 0x9346: 0x63CA, //CJK UNIFIED IDEOGRAPH - 0x9347: 0x63CB, //CJK UNIFIED IDEOGRAPH - 0x9348: 0x63CC, //CJK UNIFIED IDEOGRAPH - 0x9349: 0x63D1, //CJK UNIFIED IDEOGRAPH - 0x934A: 0x63D3, //CJK UNIFIED IDEOGRAPH - 0x934B: 0x63D4, //CJK UNIFIED IDEOGRAPH - 0x934C: 0x63D5, //CJK UNIFIED IDEOGRAPH - 0x934D: 0x63D7, //CJK UNIFIED IDEOGRAPH - 0x934E: 0x63D8, //CJK UNIFIED IDEOGRAPH - 0x934F: 0x63D9, //CJK UNIFIED IDEOGRAPH - 0x9350: 0x63DA, //CJK UNIFIED IDEOGRAPH - 0x9351: 0x63DB, //CJK UNIFIED IDEOGRAPH - 0x9352: 0x63DC, //CJK UNIFIED IDEOGRAPH - 0x9353: 0x63DD, //CJK UNIFIED IDEOGRAPH - 0x9354: 0x63DF, //CJK UNIFIED IDEOGRAPH - 0x9355: 0x63E2, //CJK UNIFIED IDEOGRAPH - 0x9356: 0x63E4, //CJK UNIFIED IDEOGRAPH - 0x9357: 0x63E5, //CJK UNIFIED IDEOGRAPH - 0x9358: 0x63E6, //CJK UNIFIED IDEOGRAPH - 0x9359: 0x63E7, //CJK UNIFIED IDEOGRAPH - 0x935A: 0x63E8, //CJK UNIFIED IDEOGRAPH - 0x935B: 0x63EB, //CJK UNIFIED IDEOGRAPH - 0x935C: 0x63EC, //CJK UNIFIED IDEOGRAPH - 0x935D: 0x63EE, //CJK UNIFIED IDEOGRAPH - 0x935E: 0x63EF, //CJK UNIFIED IDEOGRAPH - 0x935F: 0x63F0, //CJK UNIFIED IDEOGRAPH - 0x9360: 0x63F1, //CJK UNIFIED IDEOGRAPH - 0x9361: 0x63F3, //CJK UNIFIED IDEOGRAPH - 0x9362: 0x63F5, //CJK UNIFIED IDEOGRAPH - 0x9363: 0x63F7, //CJK UNIFIED IDEOGRAPH - 0x9364: 0x63F9, //CJK UNIFIED IDEOGRAPH - 0x9365: 0x63FA, //CJK UNIFIED IDEOGRAPH - 0x9366: 0x63FB, //CJK UNIFIED IDEOGRAPH - 0x9367: 0x63FC, //CJK UNIFIED IDEOGRAPH - 0x9368: 0x63FE, //CJK UNIFIED IDEOGRAPH - 0x9369: 0x6403, //CJK UNIFIED IDEOGRAPH - 0x936A: 0x6404, //CJK UNIFIED IDEOGRAPH - 0x936B: 0x6406, //CJK UNIFIED IDEOGRAPH - 0x936C: 0x6407, //CJK UNIFIED IDEOGRAPH - 0x936D: 0x6408, //CJK UNIFIED IDEOGRAPH - 0x936E: 0x6409, //CJK UNIFIED IDEOGRAPH - 0x936F: 0x640A, //CJK UNIFIED IDEOGRAPH - 0x9370: 0x640D, //CJK UNIFIED IDEOGRAPH - 0x9371: 0x640E, //CJK UNIFIED IDEOGRAPH - 0x9372: 0x6411, //CJK UNIFIED IDEOGRAPH - 0x9373: 0x6412, //CJK UNIFIED IDEOGRAPH - 0x9374: 0x6415, //CJK UNIFIED IDEOGRAPH - 0x9375: 0x6416, //CJK UNIFIED IDEOGRAPH - 0x9376: 0x6417, //CJK UNIFIED IDEOGRAPH - 0x9377: 0x6418, //CJK UNIFIED IDEOGRAPH - 0x9378: 0x6419, //CJK UNIFIED IDEOGRAPH - 0x9379: 0x641A, //CJK UNIFIED IDEOGRAPH - 0x937A: 0x641D, //CJK UNIFIED IDEOGRAPH - 0x937B: 0x641F, //CJK UNIFIED IDEOGRAPH - 0x937C: 0x6422, //CJK UNIFIED IDEOGRAPH - 0x937D: 0x6423, //CJK UNIFIED IDEOGRAPH - 0x937E: 0x6424, //CJK UNIFIED IDEOGRAPH - 0x9380: 0x6425, //CJK UNIFIED IDEOGRAPH - 0x9381: 0x6427, //CJK UNIFIED IDEOGRAPH - 0x9382: 0x6428, //CJK UNIFIED IDEOGRAPH - 0x9383: 0x6429, //CJK UNIFIED IDEOGRAPH - 0x9384: 0x642B, //CJK UNIFIED IDEOGRAPH - 0x9385: 0x642E, //CJK UNIFIED IDEOGRAPH - 0x9386: 0x642F, //CJK UNIFIED IDEOGRAPH - 0x9387: 0x6430, //CJK UNIFIED IDEOGRAPH - 0x9388: 0x6431, //CJK UNIFIED IDEOGRAPH - 0x9389: 0x6432, //CJK UNIFIED IDEOGRAPH - 0x938A: 0x6433, //CJK UNIFIED IDEOGRAPH - 0x938B: 0x6435, //CJK UNIFIED IDEOGRAPH - 0x938C: 0x6436, //CJK UNIFIED IDEOGRAPH - 0x938D: 0x6437, //CJK UNIFIED IDEOGRAPH - 0x938E: 0x6438, //CJK UNIFIED IDEOGRAPH - 0x938F: 0x6439, //CJK UNIFIED IDEOGRAPH - 0x9390: 0x643B, //CJK UNIFIED IDEOGRAPH - 0x9391: 0x643C, //CJK UNIFIED IDEOGRAPH - 0x9392: 0x643E, //CJK UNIFIED IDEOGRAPH - 0x9393: 0x6440, //CJK UNIFIED IDEOGRAPH - 0x9394: 0x6442, //CJK UNIFIED IDEOGRAPH - 0x9395: 0x6443, //CJK UNIFIED IDEOGRAPH - 0x9396: 0x6449, //CJK UNIFIED IDEOGRAPH - 0x9397: 0x644B, //CJK UNIFIED IDEOGRAPH - 0x9398: 0x644C, //CJK UNIFIED IDEOGRAPH - 0x9399: 0x644D, //CJK UNIFIED IDEOGRAPH - 0x939A: 0x644E, //CJK UNIFIED IDEOGRAPH - 0x939B: 0x644F, //CJK UNIFIED IDEOGRAPH - 0x939C: 0x6450, //CJK UNIFIED IDEOGRAPH - 0x939D: 0x6451, //CJK UNIFIED IDEOGRAPH - 0x939E: 0x6453, //CJK UNIFIED IDEOGRAPH - 0x939F: 0x6455, //CJK UNIFIED IDEOGRAPH - 0x93A0: 0x6456, //CJK UNIFIED IDEOGRAPH - 0x93A1: 0x6457, //CJK UNIFIED IDEOGRAPH - 0x93A2: 0x6459, //CJK UNIFIED IDEOGRAPH - 0x93A3: 0x645A, //CJK UNIFIED IDEOGRAPH - 0x93A4: 0x645B, //CJK UNIFIED IDEOGRAPH - 0x93A5: 0x645C, //CJK UNIFIED IDEOGRAPH - 0x93A6: 0x645D, //CJK UNIFIED IDEOGRAPH - 0x93A7: 0x645F, //CJK UNIFIED IDEOGRAPH - 0x93A8: 0x6460, //CJK UNIFIED IDEOGRAPH - 0x93A9: 0x6461, //CJK UNIFIED IDEOGRAPH - 0x93AA: 0x6462, //CJK UNIFIED IDEOGRAPH - 0x93AB: 0x6463, //CJK UNIFIED IDEOGRAPH - 0x93AC: 0x6464, //CJK UNIFIED IDEOGRAPH - 0x93AD: 0x6465, //CJK UNIFIED IDEOGRAPH - 0x93AE: 0x6466, //CJK UNIFIED IDEOGRAPH - 0x93AF: 0x6468, //CJK UNIFIED IDEOGRAPH - 0x93B0: 0x646A, //CJK UNIFIED IDEOGRAPH - 0x93B1: 0x646B, //CJK UNIFIED IDEOGRAPH - 0x93B2: 0x646C, //CJK UNIFIED IDEOGRAPH - 0x93B3: 0x646E, //CJK UNIFIED IDEOGRAPH - 0x93B4: 0x646F, //CJK UNIFIED IDEOGRAPH - 0x93B5: 0x6470, //CJK UNIFIED IDEOGRAPH - 0x93B6: 0x6471, //CJK UNIFIED IDEOGRAPH - 0x93B7: 0x6472, //CJK UNIFIED IDEOGRAPH - 0x93B8: 0x6473, //CJK UNIFIED IDEOGRAPH - 0x93B9: 0x6474, //CJK UNIFIED IDEOGRAPH - 0x93BA: 0x6475, //CJK UNIFIED IDEOGRAPH - 0x93BB: 0x6476, //CJK UNIFIED IDEOGRAPH - 0x93BC: 0x6477, //CJK UNIFIED IDEOGRAPH - 0x93BD: 0x647B, //CJK UNIFIED IDEOGRAPH - 0x93BE: 0x647C, //CJK UNIFIED IDEOGRAPH - 0x93BF: 0x647D, //CJK UNIFIED IDEOGRAPH - 0x93C0: 0x647E, //CJK UNIFIED IDEOGRAPH - 0x93C1: 0x647F, //CJK UNIFIED IDEOGRAPH - 0x93C2: 0x6480, //CJK UNIFIED IDEOGRAPH - 0x93C3: 0x6481, //CJK UNIFIED IDEOGRAPH - 0x93C4: 0x6483, //CJK UNIFIED IDEOGRAPH - 0x93C5: 0x6486, //CJK UNIFIED IDEOGRAPH - 0x93C6: 0x6488, //CJK UNIFIED IDEOGRAPH - 0x93C7: 0x6489, //CJK UNIFIED IDEOGRAPH - 0x93C8: 0x648A, //CJK UNIFIED IDEOGRAPH - 0x93C9: 0x648B, //CJK UNIFIED IDEOGRAPH - 0x93CA: 0x648C, //CJK UNIFIED IDEOGRAPH - 0x93CB: 0x648D, //CJK UNIFIED IDEOGRAPH - 0x93CC: 0x648E, //CJK UNIFIED IDEOGRAPH - 0x93CD: 0x648F, //CJK UNIFIED IDEOGRAPH - 0x93CE: 0x6490, //CJK UNIFIED IDEOGRAPH - 0x93CF: 0x6493, //CJK UNIFIED IDEOGRAPH - 0x93D0: 0x6494, //CJK UNIFIED IDEOGRAPH - 0x93D1: 0x6497, //CJK UNIFIED IDEOGRAPH - 0x93D2: 0x6498, //CJK UNIFIED IDEOGRAPH - 0x93D3: 0x649A, //CJK UNIFIED IDEOGRAPH - 0x93D4: 0x649B, //CJK UNIFIED IDEOGRAPH - 0x93D5: 0x649C, //CJK UNIFIED IDEOGRAPH - 0x93D6: 0x649D, //CJK UNIFIED IDEOGRAPH - 0x93D7: 0x649F, //CJK UNIFIED IDEOGRAPH - 0x93D8: 0x64A0, //CJK UNIFIED IDEOGRAPH - 0x93D9: 0x64A1, //CJK UNIFIED IDEOGRAPH - 0x93DA: 0x64A2, //CJK UNIFIED IDEOGRAPH - 0x93DB: 0x64A3, //CJK UNIFIED IDEOGRAPH - 0x93DC: 0x64A5, //CJK UNIFIED IDEOGRAPH - 0x93DD: 0x64A6, //CJK UNIFIED IDEOGRAPH - 0x93DE: 0x64A7, //CJK UNIFIED IDEOGRAPH - 0x93DF: 0x64A8, //CJK UNIFIED IDEOGRAPH - 0x93E0: 0x64AA, //CJK UNIFIED IDEOGRAPH - 0x93E1: 0x64AB, //CJK UNIFIED IDEOGRAPH - 0x93E2: 0x64AF, //CJK UNIFIED IDEOGRAPH - 0x93E3: 0x64B1, //CJK UNIFIED IDEOGRAPH - 0x93E4: 0x64B2, //CJK UNIFIED IDEOGRAPH - 0x93E5: 0x64B3, //CJK UNIFIED IDEOGRAPH - 0x93E6: 0x64B4, //CJK UNIFIED IDEOGRAPH - 0x93E7: 0x64B6, //CJK UNIFIED IDEOGRAPH - 0x93E8: 0x64B9, //CJK UNIFIED IDEOGRAPH - 0x93E9: 0x64BB, //CJK UNIFIED IDEOGRAPH - 0x93EA: 0x64BD, //CJK UNIFIED IDEOGRAPH - 0x93EB: 0x64BE, //CJK UNIFIED IDEOGRAPH - 0x93EC: 0x64BF, //CJK UNIFIED IDEOGRAPH - 0x93ED: 0x64C1, //CJK UNIFIED IDEOGRAPH - 0x93EE: 0x64C3, //CJK UNIFIED IDEOGRAPH - 0x93EF: 0x64C4, //CJK UNIFIED IDEOGRAPH - 0x93F0: 0x64C6, //CJK UNIFIED IDEOGRAPH - 0x93F1: 0x64C7, //CJK UNIFIED IDEOGRAPH - 0x93F2: 0x64C8, //CJK UNIFIED IDEOGRAPH - 0x93F3: 0x64C9, //CJK UNIFIED IDEOGRAPH - 0x93F4: 0x64CA, //CJK UNIFIED IDEOGRAPH - 0x93F5: 0x64CB, //CJK UNIFIED IDEOGRAPH - 0x93F6: 0x64CC, //CJK UNIFIED IDEOGRAPH - 0x93F7: 0x64CF, //CJK UNIFIED IDEOGRAPH - 0x93F8: 0x64D1, //CJK UNIFIED IDEOGRAPH - 0x93F9: 0x64D3, //CJK UNIFIED IDEOGRAPH - 0x93FA: 0x64D4, //CJK UNIFIED IDEOGRAPH - 0x93FB: 0x64D5, //CJK UNIFIED IDEOGRAPH - 0x93FC: 0x64D6, //CJK UNIFIED IDEOGRAPH - 0x93FD: 0x64D9, //CJK UNIFIED IDEOGRAPH - 0x93FE: 0x64DA, //CJK UNIFIED IDEOGRAPH - 0x9440: 0x64DB, //CJK UNIFIED IDEOGRAPH - 0x9441: 0x64DC, //CJK UNIFIED IDEOGRAPH - 0x9442: 0x64DD, //CJK UNIFIED IDEOGRAPH - 0x9443: 0x64DF, //CJK UNIFIED IDEOGRAPH - 0x9444: 0x64E0, //CJK UNIFIED IDEOGRAPH - 0x9445: 0x64E1, //CJK UNIFIED IDEOGRAPH - 0x9446: 0x64E3, //CJK UNIFIED IDEOGRAPH - 0x9447: 0x64E5, //CJK UNIFIED IDEOGRAPH - 0x9448: 0x64E7, //CJK UNIFIED IDEOGRAPH - 0x9449: 0x64E8, //CJK UNIFIED IDEOGRAPH - 0x944A: 0x64E9, //CJK UNIFIED IDEOGRAPH - 0x944B: 0x64EA, //CJK UNIFIED IDEOGRAPH - 0x944C: 0x64EB, //CJK UNIFIED IDEOGRAPH - 0x944D: 0x64EC, //CJK UNIFIED IDEOGRAPH - 0x944E: 0x64ED, //CJK UNIFIED IDEOGRAPH - 0x944F: 0x64EE, //CJK UNIFIED IDEOGRAPH - 0x9450: 0x64EF, //CJK UNIFIED IDEOGRAPH - 0x9451: 0x64F0, //CJK UNIFIED IDEOGRAPH - 0x9452: 0x64F1, //CJK UNIFIED IDEOGRAPH - 0x9453: 0x64F2, //CJK UNIFIED IDEOGRAPH - 0x9454: 0x64F3, //CJK UNIFIED IDEOGRAPH - 0x9455: 0x64F4, //CJK UNIFIED IDEOGRAPH - 0x9456: 0x64F5, //CJK UNIFIED IDEOGRAPH - 0x9457: 0x64F6, //CJK UNIFIED IDEOGRAPH - 0x9458: 0x64F7, //CJK UNIFIED IDEOGRAPH - 0x9459: 0x64F8, //CJK UNIFIED IDEOGRAPH - 0x945A: 0x64F9, //CJK UNIFIED IDEOGRAPH - 0x945B: 0x64FA, //CJK UNIFIED IDEOGRAPH - 0x945C: 0x64FB, //CJK UNIFIED IDEOGRAPH - 0x945D: 0x64FC, //CJK UNIFIED IDEOGRAPH - 0x945E: 0x64FD, //CJK UNIFIED IDEOGRAPH - 0x945F: 0x64FE, //CJK UNIFIED IDEOGRAPH - 0x9460: 0x64FF, //CJK UNIFIED IDEOGRAPH - 0x9461: 0x6501, //CJK UNIFIED IDEOGRAPH - 0x9462: 0x6502, //CJK UNIFIED IDEOGRAPH - 0x9463: 0x6503, //CJK UNIFIED IDEOGRAPH - 0x9464: 0x6504, //CJK UNIFIED IDEOGRAPH - 0x9465: 0x6505, //CJK UNIFIED IDEOGRAPH - 0x9466: 0x6506, //CJK UNIFIED IDEOGRAPH - 0x9467: 0x6507, //CJK UNIFIED IDEOGRAPH - 0x9468: 0x6508, //CJK UNIFIED IDEOGRAPH - 0x9469: 0x650A, //CJK UNIFIED IDEOGRAPH - 0x946A: 0x650B, //CJK UNIFIED IDEOGRAPH - 0x946B: 0x650C, //CJK UNIFIED IDEOGRAPH - 0x946C: 0x650D, //CJK UNIFIED IDEOGRAPH - 0x946D: 0x650E, //CJK UNIFIED IDEOGRAPH - 0x946E: 0x650F, //CJK UNIFIED IDEOGRAPH - 0x946F: 0x6510, //CJK UNIFIED IDEOGRAPH - 0x9470: 0x6511, //CJK UNIFIED IDEOGRAPH - 0x9471: 0x6513, //CJK UNIFIED IDEOGRAPH - 0x9472: 0x6514, //CJK UNIFIED IDEOGRAPH - 0x9473: 0x6515, //CJK UNIFIED IDEOGRAPH - 0x9474: 0x6516, //CJK UNIFIED IDEOGRAPH - 0x9475: 0x6517, //CJK UNIFIED IDEOGRAPH - 0x9476: 0x6519, //CJK UNIFIED IDEOGRAPH - 0x9477: 0x651A, //CJK UNIFIED IDEOGRAPH - 0x9478: 0x651B, //CJK UNIFIED IDEOGRAPH - 0x9479: 0x651C, //CJK UNIFIED IDEOGRAPH - 0x947A: 0x651D, //CJK UNIFIED IDEOGRAPH - 0x947B: 0x651E, //CJK UNIFIED IDEOGRAPH - 0x947C: 0x651F, //CJK UNIFIED IDEOGRAPH - 0x947D: 0x6520, //CJK UNIFIED IDEOGRAPH - 0x947E: 0x6521, //CJK UNIFIED IDEOGRAPH - 0x9480: 0x6522, //CJK UNIFIED IDEOGRAPH - 0x9481: 0x6523, //CJK UNIFIED IDEOGRAPH - 0x9482: 0x6524, //CJK UNIFIED IDEOGRAPH - 0x9483: 0x6526, //CJK UNIFIED IDEOGRAPH - 0x9484: 0x6527, //CJK UNIFIED IDEOGRAPH - 0x9485: 0x6528, //CJK UNIFIED IDEOGRAPH - 0x9486: 0x6529, //CJK UNIFIED IDEOGRAPH - 0x9487: 0x652A, //CJK UNIFIED IDEOGRAPH - 0x9488: 0x652C, //CJK UNIFIED IDEOGRAPH - 0x9489: 0x652D, //CJK UNIFIED IDEOGRAPH - 0x948A: 0x6530, //CJK UNIFIED IDEOGRAPH - 0x948B: 0x6531, //CJK UNIFIED IDEOGRAPH - 0x948C: 0x6532, //CJK UNIFIED IDEOGRAPH - 0x948D: 0x6533, //CJK UNIFIED IDEOGRAPH - 0x948E: 0x6537, //CJK UNIFIED IDEOGRAPH - 0x948F: 0x653A, //CJK UNIFIED IDEOGRAPH - 0x9490: 0x653C, //CJK UNIFIED IDEOGRAPH - 0x9491: 0x653D, //CJK UNIFIED IDEOGRAPH - 0x9492: 0x6540, //CJK UNIFIED IDEOGRAPH - 0x9493: 0x6541, //CJK UNIFIED IDEOGRAPH - 0x9494: 0x6542, //CJK UNIFIED IDEOGRAPH - 0x9495: 0x6543, //CJK UNIFIED IDEOGRAPH - 0x9496: 0x6544, //CJK UNIFIED IDEOGRAPH - 0x9497: 0x6546, //CJK UNIFIED IDEOGRAPH - 0x9498: 0x6547, //CJK UNIFIED IDEOGRAPH - 0x9499: 0x654A, //CJK UNIFIED IDEOGRAPH - 0x949A: 0x654B, //CJK UNIFIED IDEOGRAPH - 0x949B: 0x654D, //CJK UNIFIED IDEOGRAPH - 0x949C: 0x654E, //CJK UNIFIED IDEOGRAPH - 0x949D: 0x6550, //CJK UNIFIED IDEOGRAPH - 0x949E: 0x6552, //CJK UNIFIED IDEOGRAPH - 0x949F: 0x6553, //CJK UNIFIED IDEOGRAPH - 0x94A0: 0x6554, //CJK UNIFIED IDEOGRAPH - 0x94A1: 0x6557, //CJK UNIFIED IDEOGRAPH - 0x94A2: 0x6558, //CJK UNIFIED IDEOGRAPH - 0x94A3: 0x655A, //CJK UNIFIED IDEOGRAPH - 0x94A4: 0x655C, //CJK UNIFIED IDEOGRAPH - 0x94A5: 0x655F, //CJK UNIFIED IDEOGRAPH - 0x94A6: 0x6560, //CJK UNIFIED IDEOGRAPH - 0x94A7: 0x6561, //CJK UNIFIED IDEOGRAPH - 0x94A8: 0x6564, //CJK UNIFIED IDEOGRAPH - 0x94A9: 0x6565, //CJK UNIFIED IDEOGRAPH - 0x94AA: 0x6567, //CJK UNIFIED IDEOGRAPH - 0x94AB: 0x6568, //CJK UNIFIED IDEOGRAPH - 0x94AC: 0x6569, //CJK UNIFIED IDEOGRAPH - 0x94AD: 0x656A, //CJK UNIFIED IDEOGRAPH - 0x94AE: 0x656D, //CJK UNIFIED IDEOGRAPH - 0x94AF: 0x656E, //CJK UNIFIED IDEOGRAPH - 0x94B0: 0x656F, //CJK UNIFIED IDEOGRAPH - 0x94B1: 0x6571, //CJK UNIFIED IDEOGRAPH - 0x94B2: 0x6573, //CJK UNIFIED IDEOGRAPH - 0x94B3: 0x6575, //CJK UNIFIED IDEOGRAPH - 0x94B4: 0x6576, //CJK UNIFIED IDEOGRAPH - 0x94B5: 0x6578, //CJK UNIFIED IDEOGRAPH - 0x94B6: 0x6579, //CJK UNIFIED IDEOGRAPH - 0x94B7: 0x657A, //CJK UNIFIED IDEOGRAPH - 0x94B8: 0x657B, //CJK UNIFIED IDEOGRAPH - 0x94B9: 0x657C, //CJK UNIFIED IDEOGRAPH - 0x94BA: 0x657D, //CJK UNIFIED IDEOGRAPH - 0x94BB: 0x657E, //CJK UNIFIED IDEOGRAPH - 0x94BC: 0x657F, //CJK UNIFIED IDEOGRAPH - 0x94BD: 0x6580, //CJK UNIFIED IDEOGRAPH - 0x94BE: 0x6581, //CJK UNIFIED IDEOGRAPH - 0x94BF: 0x6582, //CJK UNIFIED IDEOGRAPH - 0x94C0: 0x6583, //CJK UNIFIED IDEOGRAPH - 0x94C1: 0x6584, //CJK UNIFIED IDEOGRAPH - 0x94C2: 0x6585, //CJK UNIFIED IDEOGRAPH - 0x94C3: 0x6586, //CJK UNIFIED IDEOGRAPH - 0x94C4: 0x6588, //CJK UNIFIED IDEOGRAPH - 0x94C5: 0x6589, //CJK UNIFIED IDEOGRAPH - 0x94C6: 0x658A, //CJK UNIFIED IDEOGRAPH - 0x94C7: 0x658D, //CJK UNIFIED IDEOGRAPH - 0x94C8: 0x658E, //CJK UNIFIED IDEOGRAPH - 0x94C9: 0x658F, //CJK UNIFIED IDEOGRAPH - 0x94CA: 0x6592, //CJK UNIFIED IDEOGRAPH - 0x94CB: 0x6594, //CJK UNIFIED IDEOGRAPH - 0x94CC: 0x6595, //CJK UNIFIED IDEOGRAPH - 0x94CD: 0x6596, //CJK UNIFIED IDEOGRAPH - 0x94CE: 0x6598, //CJK UNIFIED IDEOGRAPH - 0x94CF: 0x659A, //CJK UNIFIED IDEOGRAPH - 0x94D0: 0x659D, //CJK UNIFIED IDEOGRAPH - 0x94D1: 0x659E, //CJK UNIFIED IDEOGRAPH - 0x94D2: 0x65A0, //CJK UNIFIED IDEOGRAPH - 0x94D3: 0x65A2, //CJK UNIFIED IDEOGRAPH - 0x94D4: 0x65A3, //CJK UNIFIED IDEOGRAPH - 0x94D5: 0x65A6, //CJK UNIFIED IDEOGRAPH - 0x94D6: 0x65A8, //CJK UNIFIED IDEOGRAPH - 0x94D7: 0x65AA, //CJK UNIFIED IDEOGRAPH - 0x94D8: 0x65AC, //CJK UNIFIED IDEOGRAPH - 0x94D9: 0x65AE, //CJK UNIFIED IDEOGRAPH - 0x94DA: 0x65B1, //CJK UNIFIED IDEOGRAPH - 0x94DB: 0x65B2, //CJK UNIFIED IDEOGRAPH - 0x94DC: 0x65B3, //CJK UNIFIED IDEOGRAPH - 0x94DD: 0x65B4, //CJK UNIFIED IDEOGRAPH - 0x94DE: 0x65B5, //CJK UNIFIED IDEOGRAPH - 0x94DF: 0x65B6, //CJK UNIFIED IDEOGRAPH - 0x94E0: 0x65B7, //CJK UNIFIED IDEOGRAPH - 0x94E1: 0x65B8, //CJK UNIFIED IDEOGRAPH - 0x94E2: 0x65BA, //CJK UNIFIED IDEOGRAPH - 0x94E3: 0x65BB, //CJK UNIFIED IDEOGRAPH - 0x94E4: 0x65BE, //CJK UNIFIED IDEOGRAPH - 0x94E5: 0x65BF, //CJK UNIFIED IDEOGRAPH - 0x94E6: 0x65C0, //CJK UNIFIED IDEOGRAPH - 0x94E7: 0x65C2, //CJK UNIFIED IDEOGRAPH - 0x94E8: 0x65C7, //CJK UNIFIED IDEOGRAPH - 0x94E9: 0x65C8, //CJK UNIFIED IDEOGRAPH - 0x94EA: 0x65C9, //CJK UNIFIED IDEOGRAPH - 0x94EB: 0x65CA, //CJK UNIFIED IDEOGRAPH - 0x94EC: 0x65CD, //CJK UNIFIED IDEOGRAPH - 0x94ED: 0x65D0, //CJK UNIFIED IDEOGRAPH - 0x94EE: 0x65D1, //CJK UNIFIED IDEOGRAPH - 0x94EF: 0x65D3, //CJK UNIFIED IDEOGRAPH - 0x94F0: 0x65D4, //CJK UNIFIED IDEOGRAPH - 0x94F1: 0x65D5, //CJK UNIFIED IDEOGRAPH - 0x94F2: 0x65D8, //CJK UNIFIED IDEOGRAPH - 0x94F3: 0x65D9, //CJK UNIFIED IDEOGRAPH - 0x94F4: 0x65DA, //CJK UNIFIED IDEOGRAPH - 0x94F5: 0x65DB, //CJK UNIFIED IDEOGRAPH - 0x94F6: 0x65DC, //CJK UNIFIED IDEOGRAPH - 0x94F7: 0x65DD, //CJK UNIFIED IDEOGRAPH - 0x94F8: 0x65DE, //CJK UNIFIED IDEOGRAPH - 0x94F9: 0x65DF, //CJK UNIFIED IDEOGRAPH - 0x94FA: 0x65E1, //CJK UNIFIED IDEOGRAPH - 0x94FB: 0x65E3, //CJK UNIFIED IDEOGRAPH - 0x94FC: 0x65E4, //CJK UNIFIED IDEOGRAPH - 0x94FD: 0x65EA, //CJK UNIFIED IDEOGRAPH - 0x94FE: 0x65EB, //CJK UNIFIED IDEOGRAPH - 0x9540: 0x65F2, //CJK UNIFIED IDEOGRAPH - 0x9541: 0x65F3, //CJK UNIFIED IDEOGRAPH - 0x9542: 0x65F4, //CJK UNIFIED IDEOGRAPH - 0x9543: 0x65F5, //CJK UNIFIED IDEOGRAPH - 0x9544: 0x65F8, //CJK UNIFIED IDEOGRAPH - 0x9545: 0x65F9, //CJK UNIFIED IDEOGRAPH - 0x9546: 0x65FB, //CJK UNIFIED IDEOGRAPH - 0x9547: 0x65FC, //CJK UNIFIED IDEOGRAPH - 0x9548: 0x65FD, //CJK UNIFIED IDEOGRAPH - 0x9549: 0x65FE, //CJK UNIFIED IDEOGRAPH - 0x954A: 0x65FF, //CJK UNIFIED IDEOGRAPH - 0x954B: 0x6601, //CJK UNIFIED IDEOGRAPH - 0x954C: 0x6604, //CJK UNIFIED IDEOGRAPH - 0x954D: 0x6605, //CJK UNIFIED IDEOGRAPH - 0x954E: 0x6607, //CJK UNIFIED IDEOGRAPH - 0x954F: 0x6608, //CJK UNIFIED IDEOGRAPH - 0x9550: 0x6609, //CJK UNIFIED IDEOGRAPH - 0x9551: 0x660B, //CJK UNIFIED IDEOGRAPH - 0x9552: 0x660D, //CJK UNIFIED IDEOGRAPH - 0x9553: 0x6610, //CJK UNIFIED IDEOGRAPH - 0x9554: 0x6611, //CJK UNIFIED IDEOGRAPH - 0x9555: 0x6612, //CJK UNIFIED IDEOGRAPH - 0x9556: 0x6616, //CJK UNIFIED IDEOGRAPH - 0x9557: 0x6617, //CJK UNIFIED IDEOGRAPH - 0x9558: 0x6618, //CJK UNIFIED IDEOGRAPH - 0x9559: 0x661A, //CJK UNIFIED IDEOGRAPH - 0x955A: 0x661B, //CJK UNIFIED IDEOGRAPH - 0x955B: 0x661C, //CJK UNIFIED IDEOGRAPH - 0x955C: 0x661E, //CJK UNIFIED IDEOGRAPH - 0x955D: 0x6621, //CJK UNIFIED IDEOGRAPH - 0x955E: 0x6622, //CJK UNIFIED IDEOGRAPH - 0x955F: 0x6623, //CJK UNIFIED IDEOGRAPH - 0x9560: 0x6624, //CJK UNIFIED IDEOGRAPH - 0x9561: 0x6626, //CJK UNIFIED IDEOGRAPH - 0x9562: 0x6629, //CJK UNIFIED IDEOGRAPH - 0x9563: 0x662A, //CJK UNIFIED IDEOGRAPH - 0x9564: 0x662B, //CJK UNIFIED IDEOGRAPH - 0x9565: 0x662C, //CJK UNIFIED IDEOGRAPH - 0x9566: 0x662E, //CJK UNIFIED IDEOGRAPH - 0x9567: 0x6630, //CJK UNIFIED IDEOGRAPH - 0x9568: 0x6632, //CJK UNIFIED IDEOGRAPH - 0x9569: 0x6633, //CJK UNIFIED IDEOGRAPH - 0x956A: 0x6637, //CJK UNIFIED IDEOGRAPH - 0x956B: 0x6638, //CJK UNIFIED IDEOGRAPH - 0x956C: 0x6639, //CJK UNIFIED IDEOGRAPH - 0x956D: 0x663A, //CJK UNIFIED IDEOGRAPH - 0x956E: 0x663B, //CJK UNIFIED IDEOGRAPH - 0x956F: 0x663D, //CJK UNIFIED IDEOGRAPH - 0x9570: 0x663F, //CJK UNIFIED IDEOGRAPH - 0x9571: 0x6640, //CJK UNIFIED IDEOGRAPH - 0x9572: 0x6642, //CJK UNIFIED IDEOGRAPH - 0x9573: 0x6644, //CJK UNIFIED IDEOGRAPH - 0x9574: 0x6645, //CJK UNIFIED IDEOGRAPH - 0x9575: 0x6646, //CJK UNIFIED IDEOGRAPH - 0x9576: 0x6647, //CJK UNIFIED IDEOGRAPH - 0x9577: 0x6648, //CJK UNIFIED IDEOGRAPH - 0x9578: 0x6649, //CJK UNIFIED IDEOGRAPH - 0x9579: 0x664A, //CJK UNIFIED IDEOGRAPH - 0x957A: 0x664D, //CJK UNIFIED IDEOGRAPH - 0x957B: 0x664E, //CJK UNIFIED IDEOGRAPH - 0x957C: 0x6650, //CJK UNIFIED IDEOGRAPH - 0x957D: 0x6651, //CJK UNIFIED IDEOGRAPH - 0x957E: 0x6658, //CJK UNIFIED IDEOGRAPH - 0x9580: 0x6659, //CJK UNIFIED IDEOGRAPH - 0x9581: 0x665B, //CJK UNIFIED IDEOGRAPH - 0x9582: 0x665C, //CJK UNIFIED IDEOGRAPH - 0x9583: 0x665D, //CJK UNIFIED IDEOGRAPH - 0x9584: 0x665E, //CJK UNIFIED IDEOGRAPH - 0x9585: 0x6660, //CJK UNIFIED IDEOGRAPH - 0x9586: 0x6662, //CJK UNIFIED IDEOGRAPH - 0x9587: 0x6663, //CJK UNIFIED IDEOGRAPH - 0x9588: 0x6665, //CJK UNIFIED IDEOGRAPH - 0x9589: 0x6667, //CJK UNIFIED IDEOGRAPH - 0x958A: 0x6669, //CJK UNIFIED IDEOGRAPH - 0x958B: 0x666A, //CJK UNIFIED IDEOGRAPH - 0x958C: 0x666B, //CJK UNIFIED IDEOGRAPH - 0x958D: 0x666C, //CJK UNIFIED IDEOGRAPH - 0x958E: 0x666D, //CJK UNIFIED IDEOGRAPH - 0x958F: 0x6671, //CJK UNIFIED IDEOGRAPH - 0x9590: 0x6672, //CJK UNIFIED IDEOGRAPH - 0x9591: 0x6673, //CJK UNIFIED IDEOGRAPH - 0x9592: 0x6675, //CJK UNIFIED IDEOGRAPH - 0x9593: 0x6678, //CJK UNIFIED IDEOGRAPH - 0x9594: 0x6679, //CJK UNIFIED IDEOGRAPH - 0x9595: 0x667B, //CJK UNIFIED IDEOGRAPH - 0x9596: 0x667C, //CJK UNIFIED IDEOGRAPH - 0x9597: 0x667D, //CJK UNIFIED IDEOGRAPH - 0x9598: 0x667F, //CJK UNIFIED IDEOGRAPH - 0x9599: 0x6680, //CJK UNIFIED IDEOGRAPH - 0x959A: 0x6681, //CJK UNIFIED IDEOGRAPH - 0x959B: 0x6683, //CJK UNIFIED IDEOGRAPH - 0x959C: 0x6685, //CJK UNIFIED IDEOGRAPH - 0x959D: 0x6686, //CJK UNIFIED IDEOGRAPH - 0x959E: 0x6688, //CJK UNIFIED IDEOGRAPH - 0x959F: 0x6689, //CJK UNIFIED IDEOGRAPH - 0x95A0: 0x668A, //CJK UNIFIED IDEOGRAPH - 0x95A1: 0x668B, //CJK UNIFIED IDEOGRAPH - 0x95A2: 0x668D, //CJK UNIFIED IDEOGRAPH - 0x95A3: 0x668E, //CJK UNIFIED IDEOGRAPH - 0x95A4: 0x668F, //CJK UNIFIED IDEOGRAPH - 0x95A5: 0x6690, //CJK UNIFIED IDEOGRAPH - 0x95A6: 0x6692, //CJK UNIFIED IDEOGRAPH - 0x95A7: 0x6693, //CJK UNIFIED IDEOGRAPH - 0x95A8: 0x6694, //CJK UNIFIED IDEOGRAPH - 0x95A9: 0x6695, //CJK UNIFIED IDEOGRAPH - 0x95AA: 0x6698, //CJK UNIFIED IDEOGRAPH - 0x95AB: 0x6699, //CJK UNIFIED IDEOGRAPH - 0x95AC: 0x669A, //CJK UNIFIED IDEOGRAPH - 0x95AD: 0x669B, //CJK UNIFIED IDEOGRAPH - 0x95AE: 0x669C, //CJK UNIFIED IDEOGRAPH - 0x95AF: 0x669E, //CJK UNIFIED IDEOGRAPH - 0x95B0: 0x669F, //CJK UNIFIED IDEOGRAPH - 0x95B1: 0x66A0, //CJK UNIFIED IDEOGRAPH - 0x95B2: 0x66A1, //CJK UNIFIED IDEOGRAPH - 0x95B3: 0x66A2, //CJK UNIFIED IDEOGRAPH - 0x95B4: 0x66A3, //CJK UNIFIED IDEOGRAPH - 0x95B5: 0x66A4, //CJK UNIFIED IDEOGRAPH - 0x95B6: 0x66A5, //CJK UNIFIED IDEOGRAPH - 0x95B7: 0x66A6, //CJK UNIFIED IDEOGRAPH - 0x95B8: 0x66A9, //CJK UNIFIED IDEOGRAPH - 0x95B9: 0x66AA, //CJK UNIFIED IDEOGRAPH - 0x95BA: 0x66AB, //CJK UNIFIED IDEOGRAPH - 0x95BB: 0x66AC, //CJK UNIFIED IDEOGRAPH - 0x95BC: 0x66AD, //CJK UNIFIED IDEOGRAPH - 0x95BD: 0x66AF, //CJK UNIFIED IDEOGRAPH - 0x95BE: 0x66B0, //CJK UNIFIED IDEOGRAPH - 0x95BF: 0x66B1, //CJK UNIFIED IDEOGRAPH - 0x95C0: 0x66B2, //CJK UNIFIED IDEOGRAPH - 0x95C1: 0x66B3, //CJK UNIFIED IDEOGRAPH - 0x95C2: 0x66B5, //CJK UNIFIED IDEOGRAPH - 0x95C3: 0x66B6, //CJK UNIFIED IDEOGRAPH - 0x95C4: 0x66B7, //CJK UNIFIED IDEOGRAPH - 0x95C5: 0x66B8, //CJK UNIFIED IDEOGRAPH - 0x95C6: 0x66BA, //CJK UNIFIED IDEOGRAPH - 0x95C7: 0x66BB, //CJK UNIFIED IDEOGRAPH - 0x95C8: 0x66BC, //CJK UNIFIED IDEOGRAPH - 0x95C9: 0x66BD, //CJK UNIFIED IDEOGRAPH - 0x95CA: 0x66BF, //CJK UNIFIED IDEOGRAPH - 0x95CB: 0x66C0, //CJK UNIFIED IDEOGRAPH - 0x95CC: 0x66C1, //CJK UNIFIED IDEOGRAPH - 0x95CD: 0x66C2, //CJK UNIFIED IDEOGRAPH - 0x95CE: 0x66C3, //CJK UNIFIED IDEOGRAPH - 0x95CF: 0x66C4, //CJK UNIFIED IDEOGRAPH - 0x95D0: 0x66C5, //CJK UNIFIED IDEOGRAPH - 0x95D1: 0x66C6, //CJK UNIFIED IDEOGRAPH - 0x95D2: 0x66C7, //CJK UNIFIED IDEOGRAPH - 0x95D3: 0x66C8, //CJK UNIFIED IDEOGRAPH - 0x95D4: 0x66C9, //CJK UNIFIED IDEOGRAPH - 0x95D5: 0x66CA, //CJK UNIFIED IDEOGRAPH - 0x95D6: 0x66CB, //CJK UNIFIED IDEOGRAPH - 0x95D7: 0x66CC, //CJK UNIFIED IDEOGRAPH - 0x95D8: 0x66CD, //CJK UNIFIED IDEOGRAPH - 0x95D9: 0x66CE, //CJK UNIFIED IDEOGRAPH - 0x95DA: 0x66CF, //CJK UNIFIED IDEOGRAPH - 0x95DB: 0x66D0, //CJK UNIFIED IDEOGRAPH - 0x95DC: 0x66D1, //CJK UNIFIED IDEOGRAPH - 0x95DD: 0x66D2, //CJK UNIFIED IDEOGRAPH - 0x95DE: 0x66D3, //CJK UNIFIED IDEOGRAPH - 0x95DF: 0x66D4, //CJK UNIFIED IDEOGRAPH - 0x95E0: 0x66D5, //CJK UNIFIED IDEOGRAPH - 0x95E1: 0x66D6, //CJK UNIFIED IDEOGRAPH - 0x95E2: 0x66D7, //CJK UNIFIED IDEOGRAPH - 0x95E3: 0x66D8, //CJK UNIFIED IDEOGRAPH - 0x95E4: 0x66DA, //CJK UNIFIED IDEOGRAPH - 0x95E5: 0x66DE, //CJK UNIFIED IDEOGRAPH - 0x95E6: 0x66DF, //CJK UNIFIED IDEOGRAPH - 0x95E7: 0x66E0, //CJK UNIFIED IDEOGRAPH - 0x95E8: 0x66E1, //CJK UNIFIED IDEOGRAPH - 0x95E9: 0x66E2, //CJK UNIFIED IDEOGRAPH - 0x95EA: 0x66E3, //CJK UNIFIED IDEOGRAPH - 0x95EB: 0x66E4, //CJK UNIFIED IDEOGRAPH - 0x95EC: 0x66E5, //CJK UNIFIED IDEOGRAPH - 0x95ED: 0x66E7, //CJK UNIFIED IDEOGRAPH - 0x95EE: 0x66E8, //CJK UNIFIED IDEOGRAPH - 0x95EF: 0x66EA, //CJK UNIFIED IDEOGRAPH - 0x95F0: 0x66EB, //CJK UNIFIED IDEOGRAPH - 0x95F1: 0x66EC, //CJK UNIFIED IDEOGRAPH - 0x95F2: 0x66ED, //CJK UNIFIED IDEOGRAPH - 0x95F3: 0x66EE, //CJK UNIFIED IDEOGRAPH - 0x95F4: 0x66EF, //CJK UNIFIED IDEOGRAPH - 0x95F5: 0x66F1, //CJK UNIFIED IDEOGRAPH - 0x95F6: 0x66F5, //CJK UNIFIED IDEOGRAPH - 0x95F7: 0x66F6, //CJK UNIFIED IDEOGRAPH - 0x95F8: 0x66F8, //CJK UNIFIED IDEOGRAPH - 0x95F9: 0x66FA, //CJK UNIFIED IDEOGRAPH - 0x95FA: 0x66FB, //CJK UNIFIED IDEOGRAPH - 0x95FB: 0x66FD, //CJK UNIFIED IDEOGRAPH - 0x95FC: 0x6701, //CJK UNIFIED IDEOGRAPH - 0x95FD: 0x6702, //CJK UNIFIED IDEOGRAPH - 0x95FE: 0x6703, //CJK UNIFIED IDEOGRAPH - 0x9640: 0x6704, //CJK UNIFIED IDEOGRAPH - 0x9641: 0x6705, //CJK UNIFIED IDEOGRAPH - 0x9642: 0x6706, //CJK UNIFIED IDEOGRAPH - 0x9643: 0x6707, //CJK UNIFIED IDEOGRAPH - 0x9644: 0x670C, //CJK UNIFIED IDEOGRAPH - 0x9645: 0x670E, //CJK UNIFIED IDEOGRAPH - 0x9646: 0x670F, //CJK UNIFIED IDEOGRAPH - 0x9647: 0x6711, //CJK UNIFIED IDEOGRAPH - 0x9648: 0x6712, //CJK UNIFIED IDEOGRAPH - 0x9649: 0x6713, //CJK UNIFIED IDEOGRAPH - 0x964A: 0x6716, //CJK UNIFIED IDEOGRAPH - 0x964B: 0x6718, //CJK UNIFIED IDEOGRAPH - 0x964C: 0x6719, //CJK UNIFIED IDEOGRAPH - 0x964D: 0x671A, //CJK UNIFIED IDEOGRAPH - 0x964E: 0x671C, //CJK UNIFIED IDEOGRAPH - 0x964F: 0x671E, //CJK UNIFIED IDEOGRAPH - 0x9650: 0x6720, //CJK UNIFIED IDEOGRAPH - 0x9651: 0x6721, //CJK UNIFIED IDEOGRAPH - 0x9652: 0x6722, //CJK UNIFIED IDEOGRAPH - 0x9653: 0x6723, //CJK UNIFIED IDEOGRAPH - 0x9654: 0x6724, //CJK UNIFIED IDEOGRAPH - 0x9655: 0x6725, //CJK UNIFIED IDEOGRAPH - 0x9656: 0x6727, //CJK UNIFIED IDEOGRAPH - 0x9657: 0x6729, //CJK UNIFIED IDEOGRAPH - 0x9658: 0x672E, //CJK UNIFIED IDEOGRAPH - 0x9659: 0x6730, //CJK UNIFIED IDEOGRAPH - 0x965A: 0x6732, //CJK UNIFIED IDEOGRAPH - 0x965B: 0x6733, //CJK UNIFIED IDEOGRAPH - 0x965C: 0x6736, //CJK UNIFIED IDEOGRAPH - 0x965D: 0x6737, //CJK UNIFIED IDEOGRAPH - 0x965E: 0x6738, //CJK UNIFIED IDEOGRAPH - 0x965F: 0x6739, //CJK UNIFIED IDEOGRAPH - 0x9660: 0x673B, //CJK UNIFIED IDEOGRAPH - 0x9661: 0x673C, //CJK UNIFIED IDEOGRAPH - 0x9662: 0x673E, //CJK UNIFIED IDEOGRAPH - 0x9663: 0x673F, //CJK UNIFIED IDEOGRAPH - 0x9664: 0x6741, //CJK UNIFIED IDEOGRAPH - 0x9665: 0x6744, //CJK UNIFIED IDEOGRAPH - 0x9666: 0x6745, //CJK UNIFIED IDEOGRAPH - 0x9667: 0x6747, //CJK UNIFIED IDEOGRAPH - 0x9668: 0x674A, //CJK UNIFIED IDEOGRAPH - 0x9669: 0x674B, //CJK UNIFIED IDEOGRAPH - 0x966A: 0x674D, //CJK UNIFIED IDEOGRAPH - 0x966B: 0x6752, //CJK UNIFIED IDEOGRAPH - 0x966C: 0x6754, //CJK UNIFIED IDEOGRAPH - 0x966D: 0x6755, //CJK UNIFIED IDEOGRAPH - 0x966E: 0x6757, //CJK UNIFIED IDEOGRAPH - 0x966F: 0x6758, //CJK UNIFIED IDEOGRAPH - 0x9670: 0x6759, //CJK UNIFIED IDEOGRAPH - 0x9671: 0x675A, //CJK UNIFIED IDEOGRAPH - 0x9672: 0x675B, //CJK UNIFIED IDEOGRAPH - 0x9673: 0x675D, //CJK UNIFIED IDEOGRAPH - 0x9674: 0x6762, //CJK UNIFIED IDEOGRAPH - 0x9675: 0x6763, //CJK UNIFIED IDEOGRAPH - 0x9676: 0x6764, //CJK UNIFIED IDEOGRAPH - 0x9677: 0x6766, //CJK UNIFIED IDEOGRAPH - 0x9678: 0x6767, //CJK UNIFIED IDEOGRAPH - 0x9679: 0x676B, //CJK UNIFIED IDEOGRAPH - 0x967A: 0x676C, //CJK UNIFIED IDEOGRAPH - 0x967B: 0x676E, //CJK UNIFIED IDEOGRAPH - 0x967C: 0x6771, //CJK UNIFIED IDEOGRAPH - 0x967D: 0x6774, //CJK UNIFIED IDEOGRAPH - 0x967E: 0x6776, //CJK UNIFIED IDEOGRAPH - 0x9680: 0x6778, //CJK UNIFIED IDEOGRAPH - 0x9681: 0x6779, //CJK UNIFIED IDEOGRAPH - 0x9682: 0x677A, //CJK UNIFIED IDEOGRAPH - 0x9683: 0x677B, //CJK UNIFIED IDEOGRAPH - 0x9684: 0x677D, //CJK UNIFIED IDEOGRAPH - 0x9685: 0x6780, //CJK UNIFIED IDEOGRAPH - 0x9686: 0x6782, //CJK UNIFIED IDEOGRAPH - 0x9687: 0x6783, //CJK UNIFIED IDEOGRAPH - 0x9688: 0x6785, //CJK UNIFIED IDEOGRAPH - 0x9689: 0x6786, //CJK UNIFIED IDEOGRAPH - 0x968A: 0x6788, //CJK UNIFIED IDEOGRAPH - 0x968B: 0x678A, //CJK UNIFIED IDEOGRAPH - 0x968C: 0x678C, //CJK UNIFIED IDEOGRAPH - 0x968D: 0x678D, //CJK UNIFIED IDEOGRAPH - 0x968E: 0x678E, //CJK UNIFIED IDEOGRAPH - 0x968F: 0x678F, //CJK UNIFIED IDEOGRAPH - 0x9690: 0x6791, //CJK UNIFIED IDEOGRAPH - 0x9691: 0x6792, //CJK UNIFIED IDEOGRAPH - 0x9692: 0x6793, //CJK UNIFIED IDEOGRAPH - 0x9693: 0x6794, //CJK UNIFIED IDEOGRAPH - 0x9694: 0x6796, //CJK UNIFIED IDEOGRAPH - 0x9695: 0x6799, //CJK UNIFIED IDEOGRAPH - 0x9696: 0x679B, //CJK UNIFIED IDEOGRAPH - 0x9697: 0x679F, //CJK UNIFIED IDEOGRAPH - 0x9698: 0x67A0, //CJK UNIFIED IDEOGRAPH - 0x9699: 0x67A1, //CJK UNIFIED IDEOGRAPH - 0x969A: 0x67A4, //CJK UNIFIED IDEOGRAPH - 0x969B: 0x67A6, //CJK UNIFIED IDEOGRAPH - 0x969C: 0x67A9, //CJK UNIFIED IDEOGRAPH - 0x969D: 0x67AC, //CJK UNIFIED IDEOGRAPH - 0x969E: 0x67AE, //CJK UNIFIED IDEOGRAPH - 0x969F: 0x67B1, //CJK UNIFIED IDEOGRAPH - 0x96A0: 0x67B2, //CJK UNIFIED IDEOGRAPH - 0x96A1: 0x67B4, //CJK UNIFIED IDEOGRAPH - 0x96A2: 0x67B9, //CJK UNIFIED IDEOGRAPH - 0x96A3: 0x67BA, //CJK UNIFIED IDEOGRAPH - 0x96A4: 0x67BB, //CJK UNIFIED IDEOGRAPH - 0x96A5: 0x67BC, //CJK UNIFIED IDEOGRAPH - 0x96A6: 0x67BD, //CJK UNIFIED IDEOGRAPH - 0x96A7: 0x67BE, //CJK UNIFIED IDEOGRAPH - 0x96A8: 0x67BF, //CJK UNIFIED IDEOGRAPH - 0x96A9: 0x67C0, //CJK UNIFIED IDEOGRAPH - 0x96AA: 0x67C2, //CJK UNIFIED IDEOGRAPH - 0x96AB: 0x67C5, //CJK UNIFIED IDEOGRAPH - 0x96AC: 0x67C6, //CJK UNIFIED IDEOGRAPH - 0x96AD: 0x67C7, //CJK UNIFIED IDEOGRAPH - 0x96AE: 0x67C8, //CJK UNIFIED IDEOGRAPH - 0x96AF: 0x67C9, //CJK UNIFIED IDEOGRAPH - 0x96B0: 0x67CA, //CJK UNIFIED IDEOGRAPH - 0x96B1: 0x67CB, //CJK UNIFIED IDEOGRAPH - 0x96B2: 0x67CC, //CJK UNIFIED IDEOGRAPH - 0x96B3: 0x67CD, //CJK UNIFIED IDEOGRAPH - 0x96B4: 0x67CE, //CJK UNIFIED IDEOGRAPH - 0x96B5: 0x67D5, //CJK UNIFIED IDEOGRAPH - 0x96B6: 0x67D6, //CJK UNIFIED IDEOGRAPH - 0x96B7: 0x67D7, //CJK UNIFIED IDEOGRAPH - 0x96B8: 0x67DB, //CJK UNIFIED IDEOGRAPH - 0x96B9: 0x67DF, //CJK UNIFIED IDEOGRAPH - 0x96BA: 0x67E1, //CJK UNIFIED IDEOGRAPH - 0x96BB: 0x67E3, //CJK UNIFIED IDEOGRAPH - 0x96BC: 0x67E4, //CJK UNIFIED IDEOGRAPH - 0x96BD: 0x67E6, //CJK UNIFIED IDEOGRAPH - 0x96BE: 0x67E7, //CJK UNIFIED IDEOGRAPH - 0x96BF: 0x67E8, //CJK UNIFIED IDEOGRAPH - 0x96C0: 0x67EA, //CJK UNIFIED IDEOGRAPH - 0x96C1: 0x67EB, //CJK UNIFIED IDEOGRAPH - 0x96C2: 0x67ED, //CJK UNIFIED IDEOGRAPH - 0x96C3: 0x67EE, //CJK UNIFIED IDEOGRAPH - 0x96C4: 0x67F2, //CJK UNIFIED IDEOGRAPH - 0x96C5: 0x67F5, //CJK UNIFIED IDEOGRAPH - 0x96C6: 0x67F6, //CJK UNIFIED IDEOGRAPH - 0x96C7: 0x67F7, //CJK UNIFIED IDEOGRAPH - 0x96C8: 0x67F8, //CJK UNIFIED IDEOGRAPH - 0x96C9: 0x67F9, //CJK UNIFIED IDEOGRAPH - 0x96CA: 0x67FA, //CJK UNIFIED IDEOGRAPH - 0x96CB: 0x67FB, //CJK UNIFIED IDEOGRAPH - 0x96CC: 0x67FC, //CJK UNIFIED IDEOGRAPH - 0x96CD: 0x67FE, //CJK UNIFIED IDEOGRAPH - 0x96CE: 0x6801, //CJK UNIFIED IDEOGRAPH - 0x96CF: 0x6802, //CJK UNIFIED IDEOGRAPH - 0x96D0: 0x6803, //CJK UNIFIED IDEOGRAPH - 0x96D1: 0x6804, //CJK UNIFIED IDEOGRAPH - 0x96D2: 0x6806, //CJK UNIFIED IDEOGRAPH - 0x96D3: 0x680D, //CJK UNIFIED IDEOGRAPH - 0x96D4: 0x6810, //CJK UNIFIED IDEOGRAPH - 0x96D5: 0x6812, //CJK UNIFIED IDEOGRAPH - 0x96D6: 0x6814, //CJK UNIFIED IDEOGRAPH - 0x96D7: 0x6815, //CJK UNIFIED IDEOGRAPH - 0x96D8: 0x6818, //CJK UNIFIED IDEOGRAPH - 0x96D9: 0x6819, //CJK UNIFIED IDEOGRAPH - 0x96DA: 0x681A, //CJK UNIFIED IDEOGRAPH - 0x96DB: 0x681B, //CJK UNIFIED IDEOGRAPH - 0x96DC: 0x681C, //CJK UNIFIED IDEOGRAPH - 0x96DD: 0x681E, //CJK UNIFIED IDEOGRAPH - 0x96DE: 0x681F, //CJK UNIFIED IDEOGRAPH - 0x96DF: 0x6820, //CJK UNIFIED IDEOGRAPH - 0x96E0: 0x6822, //CJK UNIFIED IDEOGRAPH - 0x96E1: 0x6823, //CJK UNIFIED IDEOGRAPH - 0x96E2: 0x6824, //CJK UNIFIED IDEOGRAPH - 0x96E3: 0x6825, //CJK UNIFIED IDEOGRAPH - 0x96E4: 0x6826, //CJK UNIFIED IDEOGRAPH - 0x96E5: 0x6827, //CJK UNIFIED IDEOGRAPH - 0x96E6: 0x6828, //CJK UNIFIED IDEOGRAPH - 0x96E7: 0x682B, //CJK UNIFIED IDEOGRAPH - 0x96E8: 0x682C, //CJK UNIFIED IDEOGRAPH - 0x96E9: 0x682D, //CJK UNIFIED IDEOGRAPH - 0x96EA: 0x682E, //CJK UNIFIED IDEOGRAPH - 0x96EB: 0x682F, //CJK UNIFIED IDEOGRAPH - 0x96EC: 0x6830, //CJK UNIFIED IDEOGRAPH - 0x96ED: 0x6831, //CJK UNIFIED IDEOGRAPH - 0x96EE: 0x6834, //CJK UNIFIED IDEOGRAPH - 0x96EF: 0x6835, //CJK UNIFIED IDEOGRAPH - 0x96F0: 0x6836, //CJK UNIFIED IDEOGRAPH - 0x96F1: 0x683A, //CJK UNIFIED IDEOGRAPH - 0x96F2: 0x683B, //CJK UNIFIED IDEOGRAPH - 0x96F3: 0x683F, //CJK UNIFIED IDEOGRAPH - 0x96F4: 0x6847, //CJK UNIFIED IDEOGRAPH - 0x96F5: 0x684B, //CJK UNIFIED IDEOGRAPH - 0x96F6: 0x684D, //CJK UNIFIED IDEOGRAPH - 0x96F7: 0x684F, //CJK UNIFIED IDEOGRAPH - 0x96F8: 0x6852, //CJK UNIFIED IDEOGRAPH - 0x96F9: 0x6856, //CJK UNIFIED IDEOGRAPH - 0x96FA: 0x6857, //CJK UNIFIED IDEOGRAPH - 0x96FB: 0x6858, //CJK UNIFIED IDEOGRAPH - 0x96FC: 0x6859, //CJK UNIFIED IDEOGRAPH - 0x96FD: 0x685A, //CJK UNIFIED IDEOGRAPH - 0x96FE: 0x685B, //CJK UNIFIED IDEOGRAPH - 0x9740: 0x685C, //CJK UNIFIED IDEOGRAPH - 0x9741: 0x685D, //CJK UNIFIED IDEOGRAPH - 0x9742: 0x685E, //CJK UNIFIED IDEOGRAPH - 0x9743: 0x685F, //CJK UNIFIED IDEOGRAPH - 0x9744: 0x686A, //CJK UNIFIED IDEOGRAPH - 0x9745: 0x686C, //CJK UNIFIED IDEOGRAPH - 0x9746: 0x686D, //CJK UNIFIED IDEOGRAPH - 0x9747: 0x686E, //CJK UNIFIED IDEOGRAPH - 0x9748: 0x686F, //CJK UNIFIED IDEOGRAPH - 0x9749: 0x6870, //CJK UNIFIED IDEOGRAPH - 0x974A: 0x6871, //CJK UNIFIED IDEOGRAPH - 0x974B: 0x6872, //CJK UNIFIED IDEOGRAPH - 0x974C: 0x6873, //CJK UNIFIED IDEOGRAPH - 0x974D: 0x6875, //CJK UNIFIED IDEOGRAPH - 0x974E: 0x6878, //CJK UNIFIED IDEOGRAPH - 0x974F: 0x6879, //CJK UNIFIED IDEOGRAPH - 0x9750: 0x687A, //CJK UNIFIED IDEOGRAPH - 0x9751: 0x687B, //CJK UNIFIED IDEOGRAPH - 0x9752: 0x687C, //CJK UNIFIED IDEOGRAPH - 0x9753: 0x687D, //CJK UNIFIED IDEOGRAPH - 0x9754: 0x687E, //CJK UNIFIED IDEOGRAPH - 0x9755: 0x687F, //CJK UNIFIED IDEOGRAPH - 0x9756: 0x6880, //CJK UNIFIED IDEOGRAPH - 0x9757: 0x6882, //CJK UNIFIED IDEOGRAPH - 0x9758: 0x6884, //CJK UNIFIED IDEOGRAPH - 0x9759: 0x6887, //CJK UNIFIED IDEOGRAPH - 0x975A: 0x6888, //CJK UNIFIED IDEOGRAPH - 0x975B: 0x6889, //CJK UNIFIED IDEOGRAPH - 0x975C: 0x688A, //CJK UNIFIED IDEOGRAPH - 0x975D: 0x688B, //CJK UNIFIED IDEOGRAPH - 0x975E: 0x688C, //CJK UNIFIED IDEOGRAPH - 0x975F: 0x688D, //CJK UNIFIED IDEOGRAPH - 0x9760: 0x688E, //CJK UNIFIED IDEOGRAPH - 0x9761: 0x6890, //CJK UNIFIED IDEOGRAPH - 0x9762: 0x6891, //CJK UNIFIED IDEOGRAPH - 0x9763: 0x6892, //CJK UNIFIED IDEOGRAPH - 0x9764: 0x6894, //CJK UNIFIED IDEOGRAPH - 0x9765: 0x6895, //CJK UNIFIED IDEOGRAPH - 0x9766: 0x6896, //CJK UNIFIED IDEOGRAPH - 0x9767: 0x6898, //CJK UNIFIED IDEOGRAPH - 0x9768: 0x6899, //CJK UNIFIED IDEOGRAPH - 0x9769: 0x689A, //CJK UNIFIED IDEOGRAPH - 0x976A: 0x689B, //CJK UNIFIED IDEOGRAPH - 0x976B: 0x689C, //CJK UNIFIED IDEOGRAPH - 0x976C: 0x689D, //CJK UNIFIED IDEOGRAPH - 0x976D: 0x689E, //CJK UNIFIED IDEOGRAPH - 0x976E: 0x689F, //CJK UNIFIED IDEOGRAPH - 0x976F: 0x68A0, //CJK UNIFIED IDEOGRAPH - 0x9770: 0x68A1, //CJK UNIFIED IDEOGRAPH - 0x9771: 0x68A3, //CJK UNIFIED IDEOGRAPH - 0x9772: 0x68A4, //CJK UNIFIED IDEOGRAPH - 0x9773: 0x68A5, //CJK UNIFIED IDEOGRAPH - 0x9774: 0x68A9, //CJK UNIFIED IDEOGRAPH - 0x9775: 0x68AA, //CJK UNIFIED IDEOGRAPH - 0x9776: 0x68AB, //CJK UNIFIED IDEOGRAPH - 0x9777: 0x68AC, //CJK UNIFIED IDEOGRAPH - 0x9778: 0x68AE, //CJK UNIFIED IDEOGRAPH - 0x9779: 0x68B1, //CJK UNIFIED IDEOGRAPH - 0x977A: 0x68B2, //CJK UNIFIED IDEOGRAPH - 0x977B: 0x68B4, //CJK UNIFIED IDEOGRAPH - 0x977C: 0x68B6, //CJK UNIFIED IDEOGRAPH - 0x977D: 0x68B7, //CJK UNIFIED IDEOGRAPH - 0x977E: 0x68B8, //CJK UNIFIED IDEOGRAPH - 0x9780: 0x68B9, //CJK UNIFIED IDEOGRAPH - 0x9781: 0x68BA, //CJK UNIFIED IDEOGRAPH - 0x9782: 0x68BB, //CJK UNIFIED IDEOGRAPH - 0x9783: 0x68BC, //CJK UNIFIED IDEOGRAPH - 0x9784: 0x68BD, //CJK UNIFIED IDEOGRAPH - 0x9785: 0x68BE, //CJK UNIFIED IDEOGRAPH - 0x9786: 0x68BF, //CJK UNIFIED IDEOGRAPH - 0x9787: 0x68C1, //CJK UNIFIED IDEOGRAPH - 0x9788: 0x68C3, //CJK UNIFIED IDEOGRAPH - 0x9789: 0x68C4, //CJK UNIFIED IDEOGRAPH - 0x978A: 0x68C5, //CJK UNIFIED IDEOGRAPH - 0x978B: 0x68C6, //CJK UNIFIED IDEOGRAPH - 0x978C: 0x68C7, //CJK UNIFIED IDEOGRAPH - 0x978D: 0x68C8, //CJK UNIFIED IDEOGRAPH - 0x978E: 0x68CA, //CJK UNIFIED IDEOGRAPH - 0x978F: 0x68CC, //CJK UNIFIED IDEOGRAPH - 0x9790: 0x68CE, //CJK UNIFIED IDEOGRAPH - 0x9791: 0x68CF, //CJK UNIFIED IDEOGRAPH - 0x9792: 0x68D0, //CJK UNIFIED IDEOGRAPH - 0x9793: 0x68D1, //CJK UNIFIED IDEOGRAPH - 0x9794: 0x68D3, //CJK UNIFIED IDEOGRAPH - 0x9795: 0x68D4, //CJK UNIFIED IDEOGRAPH - 0x9796: 0x68D6, //CJK UNIFIED IDEOGRAPH - 0x9797: 0x68D7, //CJK UNIFIED IDEOGRAPH - 0x9798: 0x68D9, //CJK UNIFIED IDEOGRAPH - 0x9799: 0x68DB, //CJK UNIFIED IDEOGRAPH - 0x979A: 0x68DC, //CJK UNIFIED IDEOGRAPH - 0x979B: 0x68DD, //CJK UNIFIED IDEOGRAPH - 0x979C: 0x68DE, //CJK UNIFIED IDEOGRAPH - 0x979D: 0x68DF, //CJK UNIFIED IDEOGRAPH - 0x979E: 0x68E1, //CJK UNIFIED IDEOGRAPH - 0x979F: 0x68E2, //CJK UNIFIED IDEOGRAPH - 0x97A0: 0x68E4, //CJK UNIFIED IDEOGRAPH - 0x97A1: 0x68E5, //CJK UNIFIED IDEOGRAPH - 0x97A2: 0x68E6, //CJK UNIFIED IDEOGRAPH - 0x97A3: 0x68E7, //CJK UNIFIED IDEOGRAPH - 0x97A4: 0x68E8, //CJK UNIFIED IDEOGRAPH - 0x97A5: 0x68E9, //CJK UNIFIED IDEOGRAPH - 0x97A6: 0x68EA, //CJK UNIFIED IDEOGRAPH - 0x97A7: 0x68EB, //CJK UNIFIED IDEOGRAPH - 0x97A8: 0x68EC, //CJK UNIFIED IDEOGRAPH - 0x97A9: 0x68ED, //CJK UNIFIED IDEOGRAPH - 0x97AA: 0x68EF, //CJK UNIFIED IDEOGRAPH - 0x97AB: 0x68F2, //CJK UNIFIED IDEOGRAPH - 0x97AC: 0x68F3, //CJK UNIFIED IDEOGRAPH - 0x97AD: 0x68F4, //CJK UNIFIED IDEOGRAPH - 0x97AE: 0x68F6, //CJK UNIFIED IDEOGRAPH - 0x97AF: 0x68F7, //CJK UNIFIED IDEOGRAPH - 0x97B0: 0x68F8, //CJK UNIFIED IDEOGRAPH - 0x97B1: 0x68FB, //CJK UNIFIED IDEOGRAPH - 0x97B2: 0x68FD, //CJK UNIFIED IDEOGRAPH - 0x97B3: 0x68FE, //CJK UNIFIED IDEOGRAPH - 0x97B4: 0x68FF, //CJK UNIFIED IDEOGRAPH - 0x97B5: 0x6900, //CJK UNIFIED IDEOGRAPH - 0x97B6: 0x6902, //CJK UNIFIED IDEOGRAPH - 0x97B7: 0x6903, //CJK UNIFIED IDEOGRAPH - 0x97B8: 0x6904, //CJK UNIFIED IDEOGRAPH - 0x97B9: 0x6906, //CJK UNIFIED IDEOGRAPH - 0x97BA: 0x6907, //CJK UNIFIED IDEOGRAPH - 0x97BB: 0x6908, //CJK UNIFIED IDEOGRAPH - 0x97BC: 0x6909, //CJK UNIFIED IDEOGRAPH - 0x97BD: 0x690A, //CJK UNIFIED IDEOGRAPH - 0x97BE: 0x690C, //CJK UNIFIED IDEOGRAPH - 0x97BF: 0x690F, //CJK UNIFIED IDEOGRAPH - 0x97C0: 0x6911, //CJK UNIFIED IDEOGRAPH - 0x97C1: 0x6913, //CJK UNIFIED IDEOGRAPH - 0x97C2: 0x6914, //CJK UNIFIED IDEOGRAPH - 0x97C3: 0x6915, //CJK UNIFIED IDEOGRAPH - 0x97C4: 0x6916, //CJK UNIFIED IDEOGRAPH - 0x97C5: 0x6917, //CJK UNIFIED IDEOGRAPH - 0x97C6: 0x6918, //CJK UNIFIED IDEOGRAPH - 0x97C7: 0x6919, //CJK UNIFIED IDEOGRAPH - 0x97C8: 0x691A, //CJK UNIFIED IDEOGRAPH - 0x97C9: 0x691B, //CJK UNIFIED IDEOGRAPH - 0x97CA: 0x691C, //CJK UNIFIED IDEOGRAPH - 0x97CB: 0x691D, //CJK UNIFIED IDEOGRAPH - 0x97CC: 0x691E, //CJK UNIFIED IDEOGRAPH - 0x97CD: 0x6921, //CJK UNIFIED IDEOGRAPH - 0x97CE: 0x6922, //CJK UNIFIED IDEOGRAPH - 0x97CF: 0x6923, //CJK UNIFIED IDEOGRAPH - 0x97D0: 0x6925, //CJK UNIFIED IDEOGRAPH - 0x97D1: 0x6926, //CJK UNIFIED IDEOGRAPH - 0x97D2: 0x6927, //CJK UNIFIED IDEOGRAPH - 0x97D3: 0x6928, //CJK UNIFIED IDEOGRAPH - 0x97D4: 0x6929, //CJK UNIFIED IDEOGRAPH - 0x97D5: 0x692A, //CJK UNIFIED IDEOGRAPH - 0x97D6: 0x692B, //CJK UNIFIED IDEOGRAPH - 0x97D7: 0x692C, //CJK UNIFIED IDEOGRAPH - 0x97D8: 0x692E, //CJK UNIFIED IDEOGRAPH - 0x97D9: 0x692F, //CJK UNIFIED IDEOGRAPH - 0x97DA: 0x6931, //CJK UNIFIED IDEOGRAPH - 0x97DB: 0x6932, //CJK UNIFIED IDEOGRAPH - 0x97DC: 0x6933, //CJK UNIFIED IDEOGRAPH - 0x97DD: 0x6935, //CJK UNIFIED IDEOGRAPH - 0x97DE: 0x6936, //CJK UNIFIED IDEOGRAPH - 0x97DF: 0x6937, //CJK UNIFIED IDEOGRAPH - 0x97E0: 0x6938, //CJK UNIFIED IDEOGRAPH - 0x97E1: 0x693A, //CJK UNIFIED IDEOGRAPH - 0x97E2: 0x693B, //CJK UNIFIED IDEOGRAPH - 0x97E3: 0x693C, //CJK UNIFIED IDEOGRAPH - 0x97E4: 0x693E, //CJK UNIFIED IDEOGRAPH - 0x97E5: 0x6940, //CJK UNIFIED IDEOGRAPH - 0x97E6: 0x6941, //CJK UNIFIED IDEOGRAPH - 0x97E7: 0x6943, //CJK UNIFIED IDEOGRAPH - 0x97E8: 0x6944, //CJK UNIFIED IDEOGRAPH - 0x97E9: 0x6945, //CJK UNIFIED IDEOGRAPH - 0x97EA: 0x6946, //CJK UNIFIED IDEOGRAPH - 0x97EB: 0x6947, //CJK UNIFIED IDEOGRAPH - 0x97EC: 0x6948, //CJK UNIFIED IDEOGRAPH - 0x97ED: 0x6949, //CJK UNIFIED IDEOGRAPH - 0x97EE: 0x694A, //CJK UNIFIED IDEOGRAPH - 0x97EF: 0x694B, //CJK UNIFIED IDEOGRAPH - 0x97F0: 0x694C, //CJK UNIFIED IDEOGRAPH - 0x97F1: 0x694D, //CJK UNIFIED IDEOGRAPH - 0x97F2: 0x694E, //CJK UNIFIED IDEOGRAPH - 0x97F3: 0x694F, //CJK UNIFIED IDEOGRAPH - 0x97F4: 0x6950, //CJK UNIFIED IDEOGRAPH - 0x97F5: 0x6951, //CJK UNIFIED IDEOGRAPH - 0x97F6: 0x6952, //CJK UNIFIED IDEOGRAPH - 0x97F7: 0x6953, //CJK UNIFIED IDEOGRAPH - 0x97F8: 0x6955, //CJK UNIFIED IDEOGRAPH - 0x97F9: 0x6956, //CJK UNIFIED IDEOGRAPH - 0x97FA: 0x6958, //CJK UNIFIED IDEOGRAPH - 0x97FB: 0x6959, //CJK UNIFIED IDEOGRAPH - 0x97FC: 0x695B, //CJK UNIFIED IDEOGRAPH - 0x97FD: 0x695C, //CJK UNIFIED IDEOGRAPH - 0x97FE: 0x695F, //CJK UNIFIED IDEOGRAPH - 0x9840: 0x6961, //CJK UNIFIED IDEOGRAPH - 0x9841: 0x6962, //CJK UNIFIED IDEOGRAPH - 0x9842: 0x6964, //CJK UNIFIED IDEOGRAPH - 0x9843: 0x6965, //CJK UNIFIED IDEOGRAPH - 0x9844: 0x6967, //CJK UNIFIED IDEOGRAPH - 0x9845: 0x6968, //CJK UNIFIED IDEOGRAPH - 0x9846: 0x6969, //CJK UNIFIED IDEOGRAPH - 0x9847: 0x696A, //CJK UNIFIED IDEOGRAPH - 0x9848: 0x696C, //CJK UNIFIED IDEOGRAPH - 0x9849: 0x696D, //CJK UNIFIED IDEOGRAPH - 0x984A: 0x696F, //CJK UNIFIED IDEOGRAPH - 0x984B: 0x6970, //CJK UNIFIED IDEOGRAPH - 0x984C: 0x6972, //CJK UNIFIED IDEOGRAPH - 0x984D: 0x6973, //CJK UNIFIED IDEOGRAPH - 0x984E: 0x6974, //CJK UNIFIED IDEOGRAPH - 0x984F: 0x6975, //CJK UNIFIED IDEOGRAPH - 0x9850: 0x6976, //CJK UNIFIED IDEOGRAPH - 0x9851: 0x697A, //CJK UNIFIED IDEOGRAPH - 0x9852: 0x697B, //CJK UNIFIED IDEOGRAPH - 0x9853: 0x697D, //CJK UNIFIED IDEOGRAPH - 0x9854: 0x697E, //CJK UNIFIED IDEOGRAPH - 0x9855: 0x697F, //CJK UNIFIED IDEOGRAPH - 0x9856: 0x6981, //CJK UNIFIED IDEOGRAPH - 0x9857: 0x6983, //CJK UNIFIED IDEOGRAPH - 0x9858: 0x6985, //CJK UNIFIED IDEOGRAPH - 0x9859: 0x698A, //CJK UNIFIED IDEOGRAPH - 0x985A: 0x698B, //CJK UNIFIED IDEOGRAPH - 0x985B: 0x698C, //CJK UNIFIED IDEOGRAPH - 0x985C: 0x698E, //CJK UNIFIED IDEOGRAPH - 0x985D: 0x698F, //CJK UNIFIED IDEOGRAPH - 0x985E: 0x6990, //CJK UNIFIED IDEOGRAPH - 0x985F: 0x6991, //CJK UNIFIED IDEOGRAPH - 0x9860: 0x6992, //CJK UNIFIED IDEOGRAPH - 0x9861: 0x6993, //CJK UNIFIED IDEOGRAPH - 0x9862: 0x6996, //CJK UNIFIED IDEOGRAPH - 0x9863: 0x6997, //CJK UNIFIED IDEOGRAPH - 0x9864: 0x6999, //CJK UNIFIED IDEOGRAPH - 0x9865: 0x699A, //CJK UNIFIED IDEOGRAPH - 0x9866: 0x699D, //CJK UNIFIED IDEOGRAPH - 0x9867: 0x699E, //CJK UNIFIED IDEOGRAPH - 0x9868: 0x699F, //CJK UNIFIED IDEOGRAPH - 0x9869: 0x69A0, //CJK UNIFIED IDEOGRAPH - 0x986A: 0x69A1, //CJK UNIFIED IDEOGRAPH - 0x986B: 0x69A2, //CJK UNIFIED IDEOGRAPH - 0x986C: 0x69A3, //CJK UNIFIED IDEOGRAPH - 0x986D: 0x69A4, //CJK UNIFIED IDEOGRAPH - 0x986E: 0x69A5, //CJK UNIFIED IDEOGRAPH - 0x986F: 0x69A6, //CJK UNIFIED IDEOGRAPH - 0x9870: 0x69A9, //CJK UNIFIED IDEOGRAPH - 0x9871: 0x69AA, //CJK UNIFIED IDEOGRAPH - 0x9872: 0x69AC, //CJK UNIFIED IDEOGRAPH - 0x9873: 0x69AE, //CJK UNIFIED IDEOGRAPH - 0x9874: 0x69AF, //CJK UNIFIED IDEOGRAPH - 0x9875: 0x69B0, //CJK UNIFIED IDEOGRAPH - 0x9876: 0x69B2, //CJK UNIFIED IDEOGRAPH - 0x9877: 0x69B3, //CJK UNIFIED IDEOGRAPH - 0x9878: 0x69B5, //CJK UNIFIED IDEOGRAPH - 0x9879: 0x69B6, //CJK UNIFIED IDEOGRAPH - 0x987A: 0x69B8, //CJK UNIFIED IDEOGRAPH - 0x987B: 0x69B9, //CJK UNIFIED IDEOGRAPH - 0x987C: 0x69BA, //CJK UNIFIED IDEOGRAPH - 0x987D: 0x69BC, //CJK UNIFIED IDEOGRAPH - 0x987E: 0x69BD, //CJK UNIFIED IDEOGRAPH - 0x9880: 0x69BE, //CJK UNIFIED IDEOGRAPH - 0x9881: 0x69BF, //CJK UNIFIED IDEOGRAPH - 0x9882: 0x69C0, //CJK UNIFIED IDEOGRAPH - 0x9883: 0x69C2, //CJK UNIFIED IDEOGRAPH - 0x9884: 0x69C3, //CJK UNIFIED IDEOGRAPH - 0x9885: 0x69C4, //CJK UNIFIED IDEOGRAPH - 0x9886: 0x69C5, //CJK UNIFIED IDEOGRAPH - 0x9887: 0x69C6, //CJK UNIFIED IDEOGRAPH - 0x9888: 0x69C7, //CJK UNIFIED IDEOGRAPH - 0x9889: 0x69C8, //CJK UNIFIED IDEOGRAPH - 0x988A: 0x69C9, //CJK UNIFIED IDEOGRAPH - 0x988B: 0x69CB, //CJK UNIFIED IDEOGRAPH - 0x988C: 0x69CD, //CJK UNIFIED IDEOGRAPH - 0x988D: 0x69CF, //CJK UNIFIED IDEOGRAPH - 0x988E: 0x69D1, //CJK UNIFIED IDEOGRAPH - 0x988F: 0x69D2, //CJK UNIFIED IDEOGRAPH - 0x9890: 0x69D3, //CJK UNIFIED IDEOGRAPH - 0x9891: 0x69D5, //CJK UNIFIED IDEOGRAPH - 0x9892: 0x69D6, //CJK UNIFIED IDEOGRAPH - 0x9893: 0x69D7, //CJK UNIFIED IDEOGRAPH - 0x9894: 0x69D8, //CJK UNIFIED IDEOGRAPH - 0x9895: 0x69D9, //CJK UNIFIED IDEOGRAPH - 0x9896: 0x69DA, //CJK UNIFIED IDEOGRAPH - 0x9897: 0x69DC, //CJK UNIFIED IDEOGRAPH - 0x9898: 0x69DD, //CJK UNIFIED IDEOGRAPH - 0x9899: 0x69DE, //CJK UNIFIED IDEOGRAPH - 0x989A: 0x69E1, //CJK UNIFIED IDEOGRAPH - 0x989B: 0x69E2, //CJK UNIFIED IDEOGRAPH - 0x989C: 0x69E3, //CJK UNIFIED IDEOGRAPH - 0x989D: 0x69E4, //CJK UNIFIED IDEOGRAPH - 0x989E: 0x69E5, //CJK UNIFIED IDEOGRAPH - 0x989F: 0x69E6, //CJK UNIFIED IDEOGRAPH - 0x98A0: 0x69E7, //CJK UNIFIED IDEOGRAPH - 0x98A1: 0x69E8, //CJK UNIFIED IDEOGRAPH - 0x98A2: 0x69E9, //CJK UNIFIED IDEOGRAPH - 0x98A3: 0x69EA, //CJK UNIFIED IDEOGRAPH - 0x98A4: 0x69EB, //CJK UNIFIED IDEOGRAPH - 0x98A5: 0x69EC, //CJK UNIFIED IDEOGRAPH - 0x98A6: 0x69EE, //CJK UNIFIED IDEOGRAPH - 0x98A7: 0x69EF, //CJK UNIFIED IDEOGRAPH - 0x98A8: 0x69F0, //CJK UNIFIED IDEOGRAPH - 0x98A9: 0x69F1, //CJK UNIFIED IDEOGRAPH - 0x98AA: 0x69F3, //CJK UNIFIED IDEOGRAPH - 0x98AB: 0x69F4, //CJK UNIFIED IDEOGRAPH - 0x98AC: 0x69F5, //CJK UNIFIED IDEOGRAPH - 0x98AD: 0x69F6, //CJK UNIFIED IDEOGRAPH - 0x98AE: 0x69F7, //CJK UNIFIED IDEOGRAPH - 0x98AF: 0x69F8, //CJK UNIFIED IDEOGRAPH - 0x98B0: 0x69F9, //CJK UNIFIED IDEOGRAPH - 0x98B1: 0x69FA, //CJK UNIFIED IDEOGRAPH - 0x98B2: 0x69FB, //CJK UNIFIED IDEOGRAPH - 0x98B3: 0x69FC, //CJK UNIFIED IDEOGRAPH - 0x98B4: 0x69FE, //CJK UNIFIED IDEOGRAPH - 0x98B5: 0x6A00, //CJK UNIFIED IDEOGRAPH - 0x98B6: 0x6A01, //CJK UNIFIED IDEOGRAPH - 0x98B7: 0x6A02, //CJK UNIFIED IDEOGRAPH - 0x98B8: 0x6A03, //CJK UNIFIED IDEOGRAPH - 0x98B9: 0x6A04, //CJK UNIFIED IDEOGRAPH - 0x98BA: 0x6A05, //CJK UNIFIED IDEOGRAPH - 0x98BB: 0x6A06, //CJK UNIFIED IDEOGRAPH - 0x98BC: 0x6A07, //CJK UNIFIED IDEOGRAPH - 0x98BD: 0x6A08, //CJK UNIFIED IDEOGRAPH - 0x98BE: 0x6A09, //CJK UNIFIED IDEOGRAPH - 0x98BF: 0x6A0B, //CJK UNIFIED IDEOGRAPH - 0x98C0: 0x6A0C, //CJK UNIFIED IDEOGRAPH - 0x98C1: 0x6A0D, //CJK UNIFIED IDEOGRAPH - 0x98C2: 0x6A0E, //CJK UNIFIED IDEOGRAPH - 0x98C3: 0x6A0F, //CJK UNIFIED IDEOGRAPH - 0x98C4: 0x6A10, //CJK UNIFIED IDEOGRAPH - 0x98C5: 0x6A11, //CJK UNIFIED IDEOGRAPH - 0x98C6: 0x6A12, //CJK UNIFIED IDEOGRAPH - 0x98C7: 0x6A13, //CJK UNIFIED IDEOGRAPH - 0x98C8: 0x6A14, //CJK UNIFIED IDEOGRAPH - 0x98C9: 0x6A15, //CJK UNIFIED IDEOGRAPH - 0x98CA: 0x6A16, //CJK UNIFIED IDEOGRAPH - 0x98CB: 0x6A19, //CJK UNIFIED IDEOGRAPH - 0x98CC: 0x6A1A, //CJK UNIFIED IDEOGRAPH - 0x98CD: 0x6A1B, //CJK UNIFIED IDEOGRAPH - 0x98CE: 0x6A1C, //CJK UNIFIED IDEOGRAPH - 0x98CF: 0x6A1D, //CJK UNIFIED IDEOGRAPH - 0x98D0: 0x6A1E, //CJK UNIFIED IDEOGRAPH - 0x98D1: 0x6A20, //CJK UNIFIED IDEOGRAPH - 0x98D2: 0x6A22, //CJK UNIFIED IDEOGRAPH - 0x98D3: 0x6A23, //CJK UNIFIED IDEOGRAPH - 0x98D4: 0x6A24, //CJK UNIFIED IDEOGRAPH - 0x98D5: 0x6A25, //CJK UNIFIED IDEOGRAPH - 0x98D6: 0x6A26, //CJK UNIFIED IDEOGRAPH - 0x98D7: 0x6A27, //CJK UNIFIED IDEOGRAPH - 0x98D8: 0x6A29, //CJK UNIFIED IDEOGRAPH - 0x98D9: 0x6A2B, //CJK UNIFIED IDEOGRAPH - 0x98DA: 0x6A2C, //CJK UNIFIED IDEOGRAPH - 0x98DB: 0x6A2D, //CJK UNIFIED IDEOGRAPH - 0x98DC: 0x6A2E, //CJK UNIFIED IDEOGRAPH - 0x98DD: 0x6A30, //CJK UNIFIED IDEOGRAPH - 0x98DE: 0x6A32, //CJK UNIFIED IDEOGRAPH - 0x98DF: 0x6A33, //CJK UNIFIED IDEOGRAPH - 0x98E0: 0x6A34, //CJK UNIFIED IDEOGRAPH - 0x98E1: 0x6A36, //CJK UNIFIED IDEOGRAPH - 0x98E2: 0x6A37, //CJK UNIFIED IDEOGRAPH - 0x98E3: 0x6A38, //CJK UNIFIED IDEOGRAPH - 0x98E4: 0x6A39, //CJK UNIFIED IDEOGRAPH - 0x98E5: 0x6A3A, //CJK UNIFIED IDEOGRAPH - 0x98E6: 0x6A3B, //CJK UNIFIED IDEOGRAPH - 0x98E7: 0x6A3C, //CJK UNIFIED IDEOGRAPH - 0x98E8: 0x6A3F, //CJK UNIFIED IDEOGRAPH - 0x98E9: 0x6A40, //CJK UNIFIED IDEOGRAPH - 0x98EA: 0x6A41, //CJK UNIFIED IDEOGRAPH - 0x98EB: 0x6A42, //CJK UNIFIED IDEOGRAPH - 0x98EC: 0x6A43, //CJK UNIFIED IDEOGRAPH - 0x98ED: 0x6A45, //CJK UNIFIED IDEOGRAPH - 0x98EE: 0x6A46, //CJK UNIFIED IDEOGRAPH - 0x98EF: 0x6A48, //CJK UNIFIED IDEOGRAPH - 0x98F0: 0x6A49, //CJK UNIFIED IDEOGRAPH - 0x98F1: 0x6A4A, //CJK UNIFIED IDEOGRAPH - 0x98F2: 0x6A4B, //CJK UNIFIED IDEOGRAPH - 0x98F3: 0x6A4C, //CJK UNIFIED IDEOGRAPH - 0x98F4: 0x6A4D, //CJK UNIFIED IDEOGRAPH - 0x98F5: 0x6A4E, //CJK UNIFIED IDEOGRAPH - 0x98F6: 0x6A4F, //CJK UNIFIED IDEOGRAPH - 0x98F7: 0x6A51, //CJK UNIFIED IDEOGRAPH - 0x98F8: 0x6A52, //CJK UNIFIED IDEOGRAPH - 0x98F9: 0x6A53, //CJK UNIFIED IDEOGRAPH - 0x98FA: 0x6A54, //CJK UNIFIED IDEOGRAPH - 0x98FB: 0x6A55, //CJK UNIFIED IDEOGRAPH - 0x98FC: 0x6A56, //CJK UNIFIED IDEOGRAPH - 0x98FD: 0x6A57, //CJK UNIFIED IDEOGRAPH - 0x98FE: 0x6A5A, //CJK UNIFIED IDEOGRAPH - 0x9940: 0x6A5C, //CJK UNIFIED IDEOGRAPH - 0x9941: 0x6A5D, //CJK UNIFIED IDEOGRAPH - 0x9942: 0x6A5E, //CJK UNIFIED IDEOGRAPH - 0x9943: 0x6A5F, //CJK UNIFIED IDEOGRAPH - 0x9944: 0x6A60, //CJK UNIFIED IDEOGRAPH - 0x9945: 0x6A62, //CJK UNIFIED IDEOGRAPH - 0x9946: 0x6A63, //CJK UNIFIED IDEOGRAPH - 0x9947: 0x6A64, //CJK UNIFIED IDEOGRAPH - 0x9948: 0x6A66, //CJK UNIFIED IDEOGRAPH - 0x9949: 0x6A67, //CJK UNIFIED IDEOGRAPH - 0x994A: 0x6A68, //CJK UNIFIED IDEOGRAPH - 0x994B: 0x6A69, //CJK UNIFIED IDEOGRAPH - 0x994C: 0x6A6A, //CJK UNIFIED IDEOGRAPH - 0x994D: 0x6A6B, //CJK UNIFIED IDEOGRAPH - 0x994E: 0x6A6C, //CJK UNIFIED IDEOGRAPH - 0x994F: 0x6A6D, //CJK UNIFIED IDEOGRAPH - 0x9950: 0x6A6E, //CJK UNIFIED IDEOGRAPH - 0x9951: 0x6A6F, //CJK UNIFIED IDEOGRAPH - 0x9952: 0x6A70, //CJK UNIFIED IDEOGRAPH - 0x9953: 0x6A72, //CJK UNIFIED IDEOGRAPH - 0x9954: 0x6A73, //CJK UNIFIED IDEOGRAPH - 0x9955: 0x6A74, //CJK UNIFIED IDEOGRAPH - 0x9956: 0x6A75, //CJK UNIFIED IDEOGRAPH - 0x9957: 0x6A76, //CJK UNIFIED IDEOGRAPH - 0x9958: 0x6A77, //CJK UNIFIED IDEOGRAPH - 0x9959: 0x6A78, //CJK UNIFIED IDEOGRAPH - 0x995A: 0x6A7A, //CJK UNIFIED IDEOGRAPH - 0x995B: 0x6A7B, //CJK UNIFIED IDEOGRAPH - 0x995C: 0x6A7D, //CJK UNIFIED IDEOGRAPH - 0x995D: 0x6A7E, //CJK UNIFIED IDEOGRAPH - 0x995E: 0x6A7F, //CJK UNIFIED IDEOGRAPH - 0x995F: 0x6A81, //CJK UNIFIED IDEOGRAPH - 0x9960: 0x6A82, //CJK UNIFIED IDEOGRAPH - 0x9961: 0x6A83, //CJK UNIFIED IDEOGRAPH - 0x9962: 0x6A85, //CJK UNIFIED IDEOGRAPH - 0x9963: 0x6A86, //CJK UNIFIED IDEOGRAPH - 0x9964: 0x6A87, //CJK UNIFIED IDEOGRAPH - 0x9965: 0x6A88, //CJK UNIFIED IDEOGRAPH - 0x9966: 0x6A89, //CJK UNIFIED IDEOGRAPH - 0x9967: 0x6A8A, //CJK UNIFIED IDEOGRAPH - 0x9968: 0x6A8B, //CJK UNIFIED IDEOGRAPH - 0x9969: 0x6A8C, //CJK UNIFIED IDEOGRAPH - 0x996A: 0x6A8D, //CJK UNIFIED IDEOGRAPH - 0x996B: 0x6A8F, //CJK UNIFIED IDEOGRAPH - 0x996C: 0x6A92, //CJK UNIFIED IDEOGRAPH - 0x996D: 0x6A93, //CJK UNIFIED IDEOGRAPH - 0x996E: 0x6A94, //CJK UNIFIED IDEOGRAPH - 0x996F: 0x6A95, //CJK UNIFIED IDEOGRAPH - 0x9970: 0x6A96, //CJK UNIFIED IDEOGRAPH - 0x9971: 0x6A98, //CJK UNIFIED IDEOGRAPH - 0x9972: 0x6A99, //CJK UNIFIED IDEOGRAPH - 0x9973: 0x6A9A, //CJK UNIFIED IDEOGRAPH - 0x9974: 0x6A9B, //CJK UNIFIED IDEOGRAPH - 0x9975: 0x6A9C, //CJK UNIFIED IDEOGRAPH - 0x9976: 0x6A9D, //CJK UNIFIED IDEOGRAPH - 0x9977: 0x6A9E, //CJK UNIFIED IDEOGRAPH - 0x9978: 0x6A9F, //CJK UNIFIED IDEOGRAPH - 0x9979: 0x6AA1, //CJK UNIFIED IDEOGRAPH - 0x997A: 0x6AA2, //CJK UNIFIED IDEOGRAPH - 0x997B: 0x6AA3, //CJK UNIFIED IDEOGRAPH - 0x997C: 0x6AA4, //CJK UNIFIED IDEOGRAPH - 0x997D: 0x6AA5, //CJK UNIFIED IDEOGRAPH - 0x997E: 0x6AA6, //CJK UNIFIED IDEOGRAPH - 0x9980: 0x6AA7, //CJK UNIFIED IDEOGRAPH - 0x9981: 0x6AA8, //CJK UNIFIED IDEOGRAPH - 0x9982: 0x6AAA, //CJK UNIFIED IDEOGRAPH - 0x9983: 0x6AAD, //CJK UNIFIED IDEOGRAPH - 0x9984: 0x6AAE, //CJK UNIFIED IDEOGRAPH - 0x9985: 0x6AAF, //CJK UNIFIED IDEOGRAPH - 0x9986: 0x6AB0, //CJK UNIFIED IDEOGRAPH - 0x9987: 0x6AB1, //CJK UNIFIED IDEOGRAPH - 0x9988: 0x6AB2, //CJK UNIFIED IDEOGRAPH - 0x9989: 0x6AB3, //CJK UNIFIED IDEOGRAPH - 0x998A: 0x6AB4, //CJK UNIFIED IDEOGRAPH - 0x998B: 0x6AB5, //CJK UNIFIED IDEOGRAPH - 0x998C: 0x6AB6, //CJK UNIFIED IDEOGRAPH - 0x998D: 0x6AB7, //CJK UNIFIED IDEOGRAPH - 0x998E: 0x6AB8, //CJK UNIFIED IDEOGRAPH - 0x998F: 0x6AB9, //CJK UNIFIED IDEOGRAPH - 0x9990: 0x6ABA, //CJK UNIFIED IDEOGRAPH - 0x9991: 0x6ABB, //CJK UNIFIED IDEOGRAPH - 0x9992: 0x6ABC, //CJK UNIFIED IDEOGRAPH - 0x9993: 0x6ABD, //CJK UNIFIED IDEOGRAPH - 0x9994: 0x6ABE, //CJK UNIFIED IDEOGRAPH - 0x9995: 0x6ABF, //CJK UNIFIED IDEOGRAPH - 0x9996: 0x6AC0, //CJK UNIFIED IDEOGRAPH - 0x9997: 0x6AC1, //CJK UNIFIED IDEOGRAPH - 0x9998: 0x6AC2, //CJK UNIFIED IDEOGRAPH - 0x9999: 0x6AC3, //CJK UNIFIED IDEOGRAPH - 0x999A: 0x6AC4, //CJK UNIFIED IDEOGRAPH - 0x999B: 0x6AC5, //CJK UNIFIED IDEOGRAPH - 0x999C: 0x6AC6, //CJK UNIFIED IDEOGRAPH - 0x999D: 0x6AC7, //CJK UNIFIED IDEOGRAPH - 0x999E: 0x6AC8, //CJK UNIFIED IDEOGRAPH - 0x999F: 0x6AC9, //CJK UNIFIED IDEOGRAPH - 0x99A0: 0x6ACA, //CJK UNIFIED IDEOGRAPH - 0x99A1: 0x6ACB, //CJK UNIFIED IDEOGRAPH - 0x99A2: 0x6ACC, //CJK UNIFIED IDEOGRAPH - 0x99A3: 0x6ACD, //CJK UNIFIED IDEOGRAPH - 0x99A4: 0x6ACE, //CJK UNIFIED IDEOGRAPH - 0x99A5: 0x6ACF, //CJK UNIFIED IDEOGRAPH - 0x99A6: 0x6AD0, //CJK UNIFIED IDEOGRAPH - 0x99A7: 0x6AD1, //CJK UNIFIED IDEOGRAPH - 0x99A8: 0x6AD2, //CJK UNIFIED IDEOGRAPH - 0x99A9: 0x6AD3, //CJK UNIFIED IDEOGRAPH - 0x99AA: 0x6AD4, //CJK UNIFIED IDEOGRAPH - 0x99AB: 0x6AD5, //CJK UNIFIED IDEOGRAPH - 0x99AC: 0x6AD6, //CJK UNIFIED IDEOGRAPH - 0x99AD: 0x6AD7, //CJK UNIFIED IDEOGRAPH - 0x99AE: 0x6AD8, //CJK UNIFIED IDEOGRAPH - 0x99AF: 0x6AD9, //CJK UNIFIED IDEOGRAPH - 0x99B0: 0x6ADA, //CJK UNIFIED IDEOGRAPH - 0x99B1: 0x6ADB, //CJK UNIFIED IDEOGRAPH - 0x99B2: 0x6ADC, //CJK UNIFIED IDEOGRAPH - 0x99B3: 0x6ADD, //CJK UNIFIED IDEOGRAPH - 0x99B4: 0x6ADE, //CJK UNIFIED IDEOGRAPH - 0x99B5: 0x6ADF, //CJK UNIFIED IDEOGRAPH - 0x99B6: 0x6AE0, //CJK UNIFIED IDEOGRAPH - 0x99B7: 0x6AE1, //CJK UNIFIED IDEOGRAPH - 0x99B8: 0x6AE2, //CJK UNIFIED IDEOGRAPH - 0x99B9: 0x6AE3, //CJK UNIFIED IDEOGRAPH - 0x99BA: 0x6AE4, //CJK UNIFIED IDEOGRAPH - 0x99BB: 0x6AE5, //CJK UNIFIED IDEOGRAPH - 0x99BC: 0x6AE6, //CJK UNIFIED IDEOGRAPH - 0x99BD: 0x6AE7, //CJK UNIFIED IDEOGRAPH - 0x99BE: 0x6AE8, //CJK UNIFIED IDEOGRAPH - 0x99BF: 0x6AE9, //CJK UNIFIED IDEOGRAPH - 0x99C0: 0x6AEA, //CJK UNIFIED IDEOGRAPH - 0x99C1: 0x6AEB, //CJK UNIFIED IDEOGRAPH - 0x99C2: 0x6AEC, //CJK UNIFIED IDEOGRAPH - 0x99C3: 0x6AED, //CJK UNIFIED IDEOGRAPH - 0x99C4: 0x6AEE, //CJK UNIFIED IDEOGRAPH - 0x99C5: 0x6AEF, //CJK UNIFIED IDEOGRAPH - 0x99C6: 0x6AF0, //CJK UNIFIED IDEOGRAPH - 0x99C7: 0x6AF1, //CJK UNIFIED IDEOGRAPH - 0x99C8: 0x6AF2, //CJK UNIFIED IDEOGRAPH - 0x99C9: 0x6AF3, //CJK UNIFIED IDEOGRAPH - 0x99CA: 0x6AF4, //CJK UNIFIED IDEOGRAPH - 0x99CB: 0x6AF5, //CJK UNIFIED IDEOGRAPH - 0x99CC: 0x6AF6, //CJK UNIFIED IDEOGRAPH - 0x99CD: 0x6AF7, //CJK UNIFIED IDEOGRAPH - 0x99CE: 0x6AF8, //CJK UNIFIED IDEOGRAPH - 0x99CF: 0x6AF9, //CJK UNIFIED IDEOGRAPH - 0x99D0: 0x6AFA, //CJK UNIFIED IDEOGRAPH - 0x99D1: 0x6AFB, //CJK UNIFIED IDEOGRAPH - 0x99D2: 0x6AFC, //CJK UNIFIED IDEOGRAPH - 0x99D3: 0x6AFD, //CJK UNIFIED IDEOGRAPH - 0x99D4: 0x6AFE, //CJK UNIFIED IDEOGRAPH - 0x99D5: 0x6AFF, //CJK UNIFIED IDEOGRAPH - 0x99D6: 0x6B00, //CJK UNIFIED IDEOGRAPH - 0x99D7: 0x6B01, //CJK UNIFIED IDEOGRAPH - 0x99D8: 0x6B02, //CJK UNIFIED IDEOGRAPH - 0x99D9: 0x6B03, //CJK UNIFIED IDEOGRAPH - 0x99DA: 0x6B04, //CJK UNIFIED IDEOGRAPH - 0x99DB: 0x6B05, //CJK UNIFIED IDEOGRAPH - 0x99DC: 0x6B06, //CJK UNIFIED IDEOGRAPH - 0x99DD: 0x6B07, //CJK UNIFIED IDEOGRAPH - 0x99DE: 0x6B08, //CJK UNIFIED IDEOGRAPH - 0x99DF: 0x6B09, //CJK UNIFIED IDEOGRAPH - 0x99E0: 0x6B0A, //CJK UNIFIED IDEOGRAPH - 0x99E1: 0x6B0B, //CJK UNIFIED IDEOGRAPH - 0x99E2: 0x6B0C, //CJK UNIFIED IDEOGRAPH - 0x99E3: 0x6B0D, //CJK UNIFIED IDEOGRAPH - 0x99E4: 0x6B0E, //CJK UNIFIED IDEOGRAPH - 0x99E5: 0x6B0F, //CJK UNIFIED IDEOGRAPH - 0x99E6: 0x6B10, //CJK UNIFIED IDEOGRAPH - 0x99E7: 0x6B11, //CJK UNIFIED IDEOGRAPH - 0x99E8: 0x6B12, //CJK UNIFIED IDEOGRAPH - 0x99E9: 0x6B13, //CJK UNIFIED IDEOGRAPH - 0x99EA: 0x6B14, //CJK UNIFIED IDEOGRAPH - 0x99EB: 0x6B15, //CJK UNIFIED IDEOGRAPH - 0x99EC: 0x6B16, //CJK UNIFIED IDEOGRAPH - 0x99ED: 0x6B17, //CJK UNIFIED IDEOGRAPH - 0x99EE: 0x6B18, //CJK UNIFIED IDEOGRAPH - 0x99EF: 0x6B19, //CJK UNIFIED IDEOGRAPH - 0x99F0: 0x6B1A, //CJK UNIFIED IDEOGRAPH - 0x99F1: 0x6B1B, //CJK UNIFIED IDEOGRAPH - 0x99F2: 0x6B1C, //CJK UNIFIED IDEOGRAPH - 0x99F3: 0x6B1D, //CJK UNIFIED IDEOGRAPH - 0x99F4: 0x6B1E, //CJK UNIFIED IDEOGRAPH - 0x99F5: 0x6B1F, //CJK UNIFIED IDEOGRAPH - 0x99F6: 0x6B25, //CJK UNIFIED IDEOGRAPH - 0x99F7: 0x6B26, //CJK UNIFIED IDEOGRAPH - 0x99F8: 0x6B28, //CJK UNIFIED IDEOGRAPH - 0x99F9: 0x6B29, //CJK UNIFIED IDEOGRAPH - 0x99FA: 0x6B2A, //CJK UNIFIED IDEOGRAPH - 0x99FB: 0x6B2B, //CJK UNIFIED IDEOGRAPH - 0x99FC: 0x6B2C, //CJK UNIFIED IDEOGRAPH - 0x99FD: 0x6B2D, //CJK UNIFIED IDEOGRAPH - 0x99FE: 0x6B2E, //CJK UNIFIED IDEOGRAPH - 0x9A40: 0x6B2F, //CJK UNIFIED IDEOGRAPH - 0x9A41: 0x6B30, //CJK UNIFIED IDEOGRAPH - 0x9A42: 0x6B31, //CJK UNIFIED IDEOGRAPH - 0x9A43: 0x6B33, //CJK UNIFIED IDEOGRAPH - 0x9A44: 0x6B34, //CJK UNIFIED IDEOGRAPH - 0x9A45: 0x6B35, //CJK UNIFIED IDEOGRAPH - 0x9A46: 0x6B36, //CJK UNIFIED IDEOGRAPH - 0x9A47: 0x6B38, //CJK UNIFIED IDEOGRAPH - 0x9A48: 0x6B3B, //CJK UNIFIED IDEOGRAPH - 0x9A49: 0x6B3C, //CJK UNIFIED IDEOGRAPH - 0x9A4A: 0x6B3D, //CJK UNIFIED IDEOGRAPH - 0x9A4B: 0x6B3F, //CJK UNIFIED IDEOGRAPH - 0x9A4C: 0x6B40, //CJK UNIFIED IDEOGRAPH - 0x9A4D: 0x6B41, //CJK UNIFIED IDEOGRAPH - 0x9A4E: 0x6B42, //CJK UNIFIED IDEOGRAPH - 0x9A4F: 0x6B44, //CJK UNIFIED IDEOGRAPH - 0x9A50: 0x6B45, //CJK UNIFIED IDEOGRAPH - 0x9A51: 0x6B48, //CJK UNIFIED IDEOGRAPH - 0x9A52: 0x6B4A, //CJK UNIFIED IDEOGRAPH - 0x9A53: 0x6B4B, //CJK UNIFIED IDEOGRAPH - 0x9A54: 0x6B4D, //CJK UNIFIED IDEOGRAPH - 0x9A55: 0x6B4E, //CJK UNIFIED IDEOGRAPH - 0x9A56: 0x6B4F, //CJK UNIFIED IDEOGRAPH - 0x9A57: 0x6B50, //CJK UNIFIED IDEOGRAPH - 0x9A58: 0x6B51, //CJK UNIFIED IDEOGRAPH - 0x9A59: 0x6B52, //CJK UNIFIED IDEOGRAPH - 0x9A5A: 0x6B53, //CJK UNIFIED IDEOGRAPH - 0x9A5B: 0x6B54, //CJK UNIFIED IDEOGRAPH - 0x9A5C: 0x6B55, //CJK UNIFIED IDEOGRAPH - 0x9A5D: 0x6B56, //CJK UNIFIED IDEOGRAPH - 0x9A5E: 0x6B57, //CJK UNIFIED IDEOGRAPH - 0x9A5F: 0x6B58, //CJK UNIFIED IDEOGRAPH - 0x9A60: 0x6B5A, //CJK UNIFIED IDEOGRAPH - 0x9A61: 0x6B5B, //CJK UNIFIED IDEOGRAPH - 0x9A62: 0x6B5C, //CJK UNIFIED IDEOGRAPH - 0x9A63: 0x6B5D, //CJK UNIFIED IDEOGRAPH - 0x9A64: 0x6B5E, //CJK UNIFIED IDEOGRAPH - 0x9A65: 0x6B5F, //CJK UNIFIED IDEOGRAPH - 0x9A66: 0x6B60, //CJK UNIFIED IDEOGRAPH - 0x9A67: 0x6B61, //CJK UNIFIED IDEOGRAPH - 0x9A68: 0x6B68, //CJK UNIFIED IDEOGRAPH - 0x9A69: 0x6B69, //CJK UNIFIED IDEOGRAPH - 0x9A6A: 0x6B6B, //CJK UNIFIED IDEOGRAPH - 0x9A6B: 0x6B6C, //CJK UNIFIED IDEOGRAPH - 0x9A6C: 0x6B6D, //CJK UNIFIED IDEOGRAPH - 0x9A6D: 0x6B6E, //CJK UNIFIED IDEOGRAPH - 0x9A6E: 0x6B6F, //CJK UNIFIED IDEOGRAPH - 0x9A6F: 0x6B70, //CJK UNIFIED IDEOGRAPH - 0x9A70: 0x6B71, //CJK UNIFIED IDEOGRAPH - 0x9A71: 0x6B72, //CJK UNIFIED IDEOGRAPH - 0x9A72: 0x6B73, //CJK UNIFIED IDEOGRAPH - 0x9A73: 0x6B74, //CJK UNIFIED IDEOGRAPH - 0x9A74: 0x6B75, //CJK UNIFIED IDEOGRAPH - 0x9A75: 0x6B76, //CJK UNIFIED IDEOGRAPH - 0x9A76: 0x6B77, //CJK UNIFIED IDEOGRAPH - 0x9A77: 0x6B78, //CJK UNIFIED IDEOGRAPH - 0x9A78: 0x6B7A, //CJK UNIFIED IDEOGRAPH - 0x9A79: 0x6B7D, //CJK UNIFIED IDEOGRAPH - 0x9A7A: 0x6B7E, //CJK UNIFIED IDEOGRAPH - 0x9A7B: 0x6B7F, //CJK UNIFIED IDEOGRAPH - 0x9A7C: 0x6B80, //CJK UNIFIED IDEOGRAPH - 0x9A7D: 0x6B85, //CJK UNIFIED IDEOGRAPH - 0x9A7E: 0x6B88, //CJK UNIFIED IDEOGRAPH - 0x9A80: 0x6B8C, //CJK UNIFIED IDEOGRAPH - 0x9A81: 0x6B8E, //CJK UNIFIED IDEOGRAPH - 0x9A82: 0x6B8F, //CJK UNIFIED IDEOGRAPH - 0x9A83: 0x6B90, //CJK UNIFIED IDEOGRAPH - 0x9A84: 0x6B91, //CJK UNIFIED IDEOGRAPH - 0x9A85: 0x6B94, //CJK UNIFIED IDEOGRAPH - 0x9A86: 0x6B95, //CJK UNIFIED IDEOGRAPH - 0x9A87: 0x6B97, //CJK UNIFIED IDEOGRAPH - 0x9A88: 0x6B98, //CJK UNIFIED IDEOGRAPH - 0x9A89: 0x6B99, //CJK UNIFIED IDEOGRAPH - 0x9A8A: 0x6B9C, //CJK UNIFIED IDEOGRAPH - 0x9A8B: 0x6B9D, //CJK UNIFIED IDEOGRAPH - 0x9A8C: 0x6B9E, //CJK UNIFIED IDEOGRAPH - 0x9A8D: 0x6B9F, //CJK UNIFIED IDEOGRAPH - 0x9A8E: 0x6BA0, //CJK UNIFIED IDEOGRAPH - 0x9A8F: 0x6BA2, //CJK UNIFIED IDEOGRAPH - 0x9A90: 0x6BA3, //CJK UNIFIED IDEOGRAPH - 0x9A91: 0x6BA4, //CJK UNIFIED IDEOGRAPH - 0x9A92: 0x6BA5, //CJK UNIFIED IDEOGRAPH - 0x9A93: 0x6BA6, //CJK UNIFIED IDEOGRAPH - 0x9A94: 0x6BA7, //CJK UNIFIED IDEOGRAPH - 0x9A95: 0x6BA8, //CJK UNIFIED IDEOGRAPH - 0x9A96: 0x6BA9, //CJK UNIFIED IDEOGRAPH - 0x9A97: 0x6BAB, //CJK UNIFIED IDEOGRAPH - 0x9A98: 0x6BAC, //CJK UNIFIED IDEOGRAPH - 0x9A99: 0x6BAD, //CJK UNIFIED IDEOGRAPH - 0x9A9A: 0x6BAE, //CJK UNIFIED IDEOGRAPH - 0x9A9B: 0x6BAF, //CJK UNIFIED IDEOGRAPH - 0x9A9C: 0x6BB0, //CJK UNIFIED IDEOGRAPH - 0x9A9D: 0x6BB1, //CJK UNIFIED IDEOGRAPH - 0x9A9E: 0x6BB2, //CJK UNIFIED IDEOGRAPH - 0x9A9F: 0x6BB6, //CJK UNIFIED IDEOGRAPH - 0x9AA0: 0x6BB8, //CJK UNIFIED IDEOGRAPH - 0x9AA1: 0x6BB9, //CJK UNIFIED IDEOGRAPH - 0x9AA2: 0x6BBA, //CJK UNIFIED IDEOGRAPH - 0x9AA3: 0x6BBB, //CJK UNIFIED IDEOGRAPH - 0x9AA4: 0x6BBC, //CJK UNIFIED IDEOGRAPH - 0x9AA5: 0x6BBD, //CJK UNIFIED IDEOGRAPH - 0x9AA6: 0x6BBE, //CJK UNIFIED IDEOGRAPH - 0x9AA7: 0x6BC0, //CJK UNIFIED IDEOGRAPH - 0x9AA8: 0x6BC3, //CJK UNIFIED IDEOGRAPH - 0x9AA9: 0x6BC4, //CJK UNIFIED IDEOGRAPH - 0x9AAA: 0x6BC6, //CJK UNIFIED IDEOGRAPH - 0x9AAB: 0x6BC7, //CJK UNIFIED IDEOGRAPH - 0x9AAC: 0x6BC8, //CJK UNIFIED IDEOGRAPH - 0x9AAD: 0x6BC9, //CJK UNIFIED IDEOGRAPH - 0x9AAE: 0x6BCA, //CJK UNIFIED IDEOGRAPH - 0x9AAF: 0x6BCC, //CJK UNIFIED IDEOGRAPH - 0x9AB0: 0x6BCE, //CJK UNIFIED IDEOGRAPH - 0x9AB1: 0x6BD0, //CJK UNIFIED IDEOGRAPH - 0x9AB2: 0x6BD1, //CJK UNIFIED IDEOGRAPH - 0x9AB3: 0x6BD8, //CJK UNIFIED IDEOGRAPH - 0x9AB4: 0x6BDA, //CJK UNIFIED IDEOGRAPH - 0x9AB5: 0x6BDC, //CJK UNIFIED IDEOGRAPH - 0x9AB6: 0x6BDD, //CJK UNIFIED IDEOGRAPH - 0x9AB7: 0x6BDE, //CJK UNIFIED IDEOGRAPH - 0x9AB8: 0x6BDF, //CJK UNIFIED IDEOGRAPH - 0x9AB9: 0x6BE0, //CJK UNIFIED IDEOGRAPH - 0x9ABA: 0x6BE2, //CJK UNIFIED IDEOGRAPH - 0x9ABB: 0x6BE3, //CJK UNIFIED IDEOGRAPH - 0x9ABC: 0x6BE4, //CJK UNIFIED IDEOGRAPH - 0x9ABD: 0x6BE5, //CJK UNIFIED IDEOGRAPH - 0x9ABE: 0x6BE6, //CJK UNIFIED IDEOGRAPH - 0x9ABF: 0x6BE7, //CJK UNIFIED IDEOGRAPH - 0x9AC0: 0x6BE8, //CJK UNIFIED IDEOGRAPH - 0x9AC1: 0x6BE9, //CJK UNIFIED IDEOGRAPH - 0x9AC2: 0x6BEC, //CJK UNIFIED IDEOGRAPH - 0x9AC3: 0x6BED, //CJK UNIFIED IDEOGRAPH - 0x9AC4: 0x6BEE, //CJK UNIFIED IDEOGRAPH - 0x9AC5: 0x6BF0, //CJK UNIFIED IDEOGRAPH - 0x9AC6: 0x6BF1, //CJK UNIFIED IDEOGRAPH - 0x9AC7: 0x6BF2, //CJK UNIFIED IDEOGRAPH - 0x9AC8: 0x6BF4, //CJK UNIFIED IDEOGRAPH - 0x9AC9: 0x6BF6, //CJK UNIFIED IDEOGRAPH - 0x9ACA: 0x6BF7, //CJK UNIFIED IDEOGRAPH - 0x9ACB: 0x6BF8, //CJK UNIFIED IDEOGRAPH - 0x9ACC: 0x6BFA, //CJK UNIFIED IDEOGRAPH - 0x9ACD: 0x6BFB, //CJK UNIFIED IDEOGRAPH - 0x9ACE: 0x6BFC, //CJK UNIFIED IDEOGRAPH - 0x9ACF: 0x6BFE, //CJK UNIFIED IDEOGRAPH - 0x9AD0: 0x6BFF, //CJK UNIFIED IDEOGRAPH - 0x9AD1: 0x6C00, //CJK UNIFIED IDEOGRAPH - 0x9AD2: 0x6C01, //CJK UNIFIED IDEOGRAPH - 0x9AD3: 0x6C02, //CJK UNIFIED IDEOGRAPH - 0x9AD4: 0x6C03, //CJK UNIFIED IDEOGRAPH - 0x9AD5: 0x6C04, //CJK UNIFIED IDEOGRAPH - 0x9AD6: 0x6C08, //CJK UNIFIED IDEOGRAPH - 0x9AD7: 0x6C09, //CJK UNIFIED IDEOGRAPH - 0x9AD8: 0x6C0A, //CJK UNIFIED IDEOGRAPH - 0x9AD9: 0x6C0B, //CJK UNIFIED IDEOGRAPH - 0x9ADA: 0x6C0C, //CJK UNIFIED IDEOGRAPH - 0x9ADB: 0x6C0E, //CJK UNIFIED IDEOGRAPH - 0x9ADC: 0x6C12, //CJK UNIFIED IDEOGRAPH - 0x9ADD: 0x6C17, //CJK UNIFIED IDEOGRAPH - 0x9ADE: 0x6C1C, //CJK UNIFIED IDEOGRAPH - 0x9ADF: 0x6C1D, //CJK UNIFIED IDEOGRAPH - 0x9AE0: 0x6C1E, //CJK UNIFIED IDEOGRAPH - 0x9AE1: 0x6C20, //CJK UNIFIED IDEOGRAPH - 0x9AE2: 0x6C23, //CJK UNIFIED IDEOGRAPH - 0x9AE3: 0x6C25, //CJK UNIFIED IDEOGRAPH - 0x9AE4: 0x6C2B, //CJK UNIFIED IDEOGRAPH - 0x9AE5: 0x6C2C, //CJK UNIFIED IDEOGRAPH - 0x9AE6: 0x6C2D, //CJK UNIFIED IDEOGRAPH - 0x9AE7: 0x6C31, //CJK UNIFIED IDEOGRAPH - 0x9AE8: 0x6C33, //CJK UNIFIED IDEOGRAPH - 0x9AE9: 0x6C36, //CJK UNIFIED IDEOGRAPH - 0x9AEA: 0x6C37, //CJK UNIFIED IDEOGRAPH - 0x9AEB: 0x6C39, //CJK UNIFIED IDEOGRAPH - 0x9AEC: 0x6C3A, //CJK UNIFIED IDEOGRAPH - 0x9AED: 0x6C3B, //CJK UNIFIED IDEOGRAPH - 0x9AEE: 0x6C3C, //CJK UNIFIED IDEOGRAPH - 0x9AEF: 0x6C3E, //CJK UNIFIED IDEOGRAPH - 0x9AF0: 0x6C3F, //CJK UNIFIED IDEOGRAPH - 0x9AF1: 0x6C43, //CJK UNIFIED IDEOGRAPH - 0x9AF2: 0x6C44, //CJK UNIFIED IDEOGRAPH - 0x9AF3: 0x6C45, //CJK UNIFIED IDEOGRAPH - 0x9AF4: 0x6C48, //CJK UNIFIED IDEOGRAPH - 0x9AF5: 0x6C4B, //CJK UNIFIED IDEOGRAPH - 0x9AF6: 0x6C4C, //CJK UNIFIED IDEOGRAPH - 0x9AF7: 0x6C4D, //CJK UNIFIED IDEOGRAPH - 0x9AF8: 0x6C4E, //CJK UNIFIED IDEOGRAPH - 0x9AF9: 0x6C4F, //CJK UNIFIED IDEOGRAPH - 0x9AFA: 0x6C51, //CJK UNIFIED IDEOGRAPH - 0x9AFB: 0x6C52, //CJK UNIFIED IDEOGRAPH - 0x9AFC: 0x6C53, //CJK UNIFIED IDEOGRAPH - 0x9AFD: 0x6C56, //CJK UNIFIED IDEOGRAPH - 0x9AFE: 0x6C58, //CJK UNIFIED IDEOGRAPH - 0x9B40: 0x6C59, //CJK UNIFIED IDEOGRAPH - 0x9B41: 0x6C5A, //CJK UNIFIED IDEOGRAPH - 0x9B42: 0x6C62, //CJK UNIFIED IDEOGRAPH - 0x9B43: 0x6C63, //CJK UNIFIED IDEOGRAPH - 0x9B44: 0x6C65, //CJK UNIFIED IDEOGRAPH - 0x9B45: 0x6C66, //CJK UNIFIED IDEOGRAPH - 0x9B46: 0x6C67, //CJK UNIFIED IDEOGRAPH - 0x9B47: 0x6C6B, //CJK UNIFIED IDEOGRAPH - 0x9B48: 0x6C6C, //CJK UNIFIED IDEOGRAPH - 0x9B49: 0x6C6D, //CJK UNIFIED IDEOGRAPH - 0x9B4A: 0x6C6E, //CJK UNIFIED IDEOGRAPH - 0x9B4B: 0x6C6F, //CJK UNIFIED IDEOGRAPH - 0x9B4C: 0x6C71, //CJK UNIFIED IDEOGRAPH - 0x9B4D: 0x6C73, //CJK UNIFIED IDEOGRAPH - 0x9B4E: 0x6C75, //CJK UNIFIED IDEOGRAPH - 0x9B4F: 0x6C77, //CJK UNIFIED IDEOGRAPH - 0x9B50: 0x6C78, //CJK UNIFIED IDEOGRAPH - 0x9B51: 0x6C7A, //CJK UNIFIED IDEOGRAPH - 0x9B52: 0x6C7B, //CJK UNIFIED IDEOGRAPH - 0x9B53: 0x6C7C, //CJK UNIFIED IDEOGRAPH - 0x9B54: 0x6C7F, //CJK UNIFIED IDEOGRAPH - 0x9B55: 0x6C80, //CJK UNIFIED IDEOGRAPH - 0x9B56: 0x6C84, //CJK UNIFIED IDEOGRAPH - 0x9B57: 0x6C87, //CJK UNIFIED IDEOGRAPH - 0x9B58: 0x6C8A, //CJK UNIFIED IDEOGRAPH - 0x9B59: 0x6C8B, //CJK UNIFIED IDEOGRAPH - 0x9B5A: 0x6C8D, //CJK UNIFIED IDEOGRAPH - 0x9B5B: 0x6C8E, //CJK UNIFIED IDEOGRAPH - 0x9B5C: 0x6C91, //CJK UNIFIED IDEOGRAPH - 0x9B5D: 0x6C92, //CJK UNIFIED IDEOGRAPH - 0x9B5E: 0x6C95, //CJK UNIFIED IDEOGRAPH - 0x9B5F: 0x6C96, //CJK UNIFIED IDEOGRAPH - 0x9B60: 0x6C97, //CJK UNIFIED IDEOGRAPH - 0x9B61: 0x6C98, //CJK UNIFIED IDEOGRAPH - 0x9B62: 0x6C9A, //CJK UNIFIED IDEOGRAPH - 0x9B63: 0x6C9C, //CJK UNIFIED IDEOGRAPH - 0x9B64: 0x6C9D, //CJK UNIFIED IDEOGRAPH - 0x9B65: 0x6C9E, //CJK UNIFIED IDEOGRAPH - 0x9B66: 0x6CA0, //CJK UNIFIED IDEOGRAPH - 0x9B67: 0x6CA2, //CJK UNIFIED IDEOGRAPH - 0x9B68: 0x6CA8, //CJK UNIFIED IDEOGRAPH - 0x9B69: 0x6CAC, //CJK UNIFIED IDEOGRAPH - 0x9B6A: 0x6CAF, //CJK UNIFIED IDEOGRAPH - 0x9B6B: 0x6CB0, //CJK UNIFIED IDEOGRAPH - 0x9B6C: 0x6CB4, //CJK UNIFIED IDEOGRAPH - 0x9B6D: 0x6CB5, //CJK UNIFIED IDEOGRAPH - 0x9B6E: 0x6CB6, //CJK UNIFIED IDEOGRAPH - 0x9B6F: 0x6CB7, //CJK UNIFIED IDEOGRAPH - 0x9B70: 0x6CBA, //CJK UNIFIED IDEOGRAPH - 0x9B71: 0x6CC0, //CJK UNIFIED IDEOGRAPH - 0x9B72: 0x6CC1, //CJK UNIFIED IDEOGRAPH - 0x9B73: 0x6CC2, //CJK UNIFIED IDEOGRAPH - 0x9B74: 0x6CC3, //CJK UNIFIED IDEOGRAPH - 0x9B75: 0x6CC6, //CJK UNIFIED IDEOGRAPH - 0x9B76: 0x6CC7, //CJK UNIFIED IDEOGRAPH - 0x9B77: 0x6CC8, //CJK UNIFIED IDEOGRAPH - 0x9B78: 0x6CCB, //CJK UNIFIED IDEOGRAPH - 0x9B79: 0x6CCD, //CJK UNIFIED IDEOGRAPH - 0x9B7A: 0x6CCE, //CJK UNIFIED IDEOGRAPH - 0x9B7B: 0x6CCF, //CJK UNIFIED IDEOGRAPH - 0x9B7C: 0x6CD1, //CJK UNIFIED IDEOGRAPH - 0x9B7D: 0x6CD2, //CJK UNIFIED IDEOGRAPH - 0x9B7E: 0x6CD8, //CJK UNIFIED IDEOGRAPH - 0x9B80: 0x6CD9, //CJK UNIFIED IDEOGRAPH - 0x9B81: 0x6CDA, //CJK UNIFIED IDEOGRAPH - 0x9B82: 0x6CDC, //CJK UNIFIED IDEOGRAPH - 0x9B83: 0x6CDD, //CJK UNIFIED IDEOGRAPH - 0x9B84: 0x6CDF, //CJK UNIFIED IDEOGRAPH - 0x9B85: 0x6CE4, //CJK UNIFIED IDEOGRAPH - 0x9B86: 0x6CE6, //CJK UNIFIED IDEOGRAPH - 0x9B87: 0x6CE7, //CJK UNIFIED IDEOGRAPH - 0x9B88: 0x6CE9, //CJK UNIFIED IDEOGRAPH - 0x9B89: 0x6CEC, //CJK UNIFIED IDEOGRAPH - 0x9B8A: 0x6CED, //CJK UNIFIED IDEOGRAPH - 0x9B8B: 0x6CF2, //CJK UNIFIED IDEOGRAPH - 0x9B8C: 0x6CF4, //CJK UNIFIED IDEOGRAPH - 0x9B8D: 0x6CF9, //CJK UNIFIED IDEOGRAPH - 0x9B8E: 0x6CFF, //CJK UNIFIED IDEOGRAPH - 0x9B8F: 0x6D00, //CJK UNIFIED IDEOGRAPH - 0x9B90: 0x6D02, //CJK UNIFIED IDEOGRAPH - 0x9B91: 0x6D03, //CJK UNIFIED IDEOGRAPH - 0x9B92: 0x6D05, //CJK UNIFIED IDEOGRAPH - 0x9B93: 0x6D06, //CJK UNIFIED IDEOGRAPH - 0x9B94: 0x6D08, //CJK UNIFIED IDEOGRAPH - 0x9B95: 0x6D09, //CJK UNIFIED IDEOGRAPH - 0x9B96: 0x6D0A, //CJK UNIFIED IDEOGRAPH - 0x9B97: 0x6D0D, //CJK UNIFIED IDEOGRAPH - 0x9B98: 0x6D0F, //CJK UNIFIED IDEOGRAPH - 0x9B99: 0x6D10, //CJK UNIFIED IDEOGRAPH - 0x9B9A: 0x6D11, //CJK UNIFIED IDEOGRAPH - 0x9B9B: 0x6D13, //CJK UNIFIED IDEOGRAPH - 0x9B9C: 0x6D14, //CJK UNIFIED IDEOGRAPH - 0x9B9D: 0x6D15, //CJK UNIFIED IDEOGRAPH - 0x9B9E: 0x6D16, //CJK UNIFIED IDEOGRAPH - 0x9B9F: 0x6D18, //CJK UNIFIED IDEOGRAPH - 0x9BA0: 0x6D1C, //CJK UNIFIED IDEOGRAPH - 0x9BA1: 0x6D1D, //CJK UNIFIED IDEOGRAPH - 0x9BA2: 0x6D1F, //CJK UNIFIED IDEOGRAPH - 0x9BA3: 0x6D20, //CJK UNIFIED IDEOGRAPH - 0x9BA4: 0x6D21, //CJK UNIFIED IDEOGRAPH - 0x9BA5: 0x6D22, //CJK UNIFIED IDEOGRAPH - 0x9BA6: 0x6D23, //CJK UNIFIED IDEOGRAPH - 0x9BA7: 0x6D24, //CJK UNIFIED IDEOGRAPH - 0x9BA8: 0x6D26, //CJK UNIFIED IDEOGRAPH - 0x9BA9: 0x6D28, //CJK UNIFIED IDEOGRAPH - 0x9BAA: 0x6D29, //CJK UNIFIED IDEOGRAPH - 0x9BAB: 0x6D2C, //CJK UNIFIED IDEOGRAPH - 0x9BAC: 0x6D2D, //CJK UNIFIED IDEOGRAPH - 0x9BAD: 0x6D2F, //CJK UNIFIED IDEOGRAPH - 0x9BAE: 0x6D30, //CJK UNIFIED IDEOGRAPH - 0x9BAF: 0x6D34, //CJK UNIFIED IDEOGRAPH - 0x9BB0: 0x6D36, //CJK UNIFIED IDEOGRAPH - 0x9BB1: 0x6D37, //CJK UNIFIED IDEOGRAPH - 0x9BB2: 0x6D38, //CJK UNIFIED IDEOGRAPH - 0x9BB3: 0x6D3A, //CJK UNIFIED IDEOGRAPH - 0x9BB4: 0x6D3F, //CJK UNIFIED IDEOGRAPH - 0x9BB5: 0x6D40, //CJK UNIFIED IDEOGRAPH - 0x9BB6: 0x6D42, //CJK UNIFIED IDEOGRAPH - 0x9BB7: 0x6D44, //CJK UNIFIED IDEOGRAPH - 0x9BB8: 0x6D49, //CJK UNIFIED IDEOGRAPH - 0x9BB9: 0x6D4C, //CJK UNIFIED IDEOGRAPH - 0x9BBA: 0x6D50, //CJK UNIFIED IDEOGRAPH - 0x9BBB: 0x6D55, //CJK UNIFIED IDEOGRAPH - 0x9BBC: 0x6D56, //CJK UNIFIED IDEOGRAPH - 0x9BBD: 0x6D57, //CJK UNIFIED IDEOGRAPH - 0x9BBE: 0x6D58, //CJK UNIFIED IDEOGRAPH - 0x9BBF: 0x6D5B, //CJK UNIFIED IDEOGRAPH - 0x9BC0: 0x6D5D, //CJK UNIFIED IDEOGRAPH - 0x9BC1: 0x6D5F, //CJK UNIFIED IDEOGRAPH - 0x9BC2: 0x6D61, //CJK UNIFIED IDEOGRAPH - 0x9BC3: 0x6D62, //CJK UNIFIED IDEOGRAPH - 0x9BC4: 0x6D64, //CJK UNIFIED IDEOGRAPH - 0x9BC5: 0x6D65, //CJK UNIFIED IDEOGRAPH - 0x9BC6: 0x6D67, //CJK UNIFIED IDEOGRAPH - 0x9BC7: 0x6D68, //CJK UNIFIED IDEOGRAPH - 0x9BC8: 0x6D6B, //CJK UNIFIED IDEOGRAPH - 0x9BC9: 0x6D6C, //CJK UNIFIED IDEOGRAPH - 0x9BCA: 0x6D6D, //CJK UNIFIED IDEOGRAPH - 0x9BCB: 0x6D70, //CJK UNIFIED IDEOGRAPH - 0x9BCC: 0x6D71, //CJK UNIFIED IDEOGRAPH - 0x9BCD: 0x6D72, //CJK UNIFIED IDEOGRAPH - 0x9BCE: 0x6D73, //CJK UNIFIED IDEOGRAPH - 0x9BCF: 0x6D75, //CJK UNIFIED IDEOGRAPH - 0x9BD0: 0x6D76, //CJK UNIFIED IDEOGRAPH - 0x9BD1: 0x6D79, //CJK UNIFIED IDEOGRAPH - 0x9BD2: 0x6D7A, //CJK UNIFIED IDEOGRAPH - 0x9BD3: 0x6D7B, //CJK UNIFIED IDEOGRAPH - 0x9BD4: 0x6D7D, //CJK UNIFIED IDEOGRAPH - 0x9BD5: 0x6D7E, //CJK UNIFIED IDEOGRAPH - 0x9BD6: 0x6D7F, //CJK UNIFIED IDEOGRAPH - 0x9BD7: 0x6D80, //CJK UNIFIED IDEOGRAPH - 0x9BD8: 0x6D81, //CJK UNIFIED IDEOGRAPH - 0x9BD9: 0x6D83, //CJK UNIFIED IDEOGRAPH - 0x9BDA: 0x6D84, //CJK UNIFIED IDEOGRAPH - 0x9BDB: 0x6D86, //CJK UNIFIED IDEOGRAPH - 0x9BDC: 0x6D87, //CJK UNIFIED IDEOGRAPH - 0x9BDD: 0x6D8A, //CJK UNIFIED IDEOGRAPH - 0x9BDE: 0x6D8B, //CJK UNIFIED IDEOGRAPH - 0x9BDF: 0x6D8D, //CJK UNIFIED IDEOGRAPH - 0x9BE0: 0x6D8F, //CJK UNIFIED IDEOGRAPH - 0x9BE1: 0x6D90, //CJK UNIFIED IDEOGRAPH - 0x9BE2: 0x6D92, //CJK UNIFIED IDEOGRAPH - 0x9BE3: 0x6D96, //CJK UNIFIED IDEOGRAPH - 0x9BE4: 0x6D97, //CJK UNIFIED IDEOGRAPH - 0x9BE5: 0x6D98, //CJK UNIFIED IDEOGRAPH - 0x9BE6: 0x6D99, //CJK UNIFIED IDEOGRAPH - 0x9BE7: 0x6D9A, //CJK UNIFIED IDEOGRAPH - 0x9BE8: 0x6D9C, //CJK UNIFIED IDEOGRAPH - 0x9BE9: 0x6DA2, //CJK UNIFIED IDEOGRAPH - 0x9BEA: 0x6DA5, //CJK UNIFIED IDEOGRAPH - 0x9BEB: 0x6DAC, //CJK UNIFIED IDEOGRAPH - 0x9BEC: 0x6DAD, //CJK UNIFIED IDEOGRAPH - 0x9BED: 0x6DB0, //CJK UNIFIED IDEOGRAPH - 0x9BEE: 0x6DB1, //CJK UNIFIED IDEOGRAPH - 0x9BEF: 0x6DB3, //CJK UNIFIED IDEOGRAPH - 0x9BF0: 0x6DB4, //CJK UNIFIED IDEOGRAPH - 0x9BF1: 0x6DB6, //CJK UNIFIED IDEOGRAPH - 0x9BF2: 0x6DB7, //CJK UNIFIED IDEOGRAPH - 0x9BF3: 0x6DB9, //CJK UNIFIED IDEOGRAPH - 0x9BF4: 0x6DBA, //CJK UNIFIED IDEOGRAPH - 0x9BF5: 0x6DBB, //CJK UNIFIED IDEOGRAPH - 0x9BF6: 0x6DBC, //CJK UNIFIED IDEOGRAPH - 0x9BF7: 0x6DBD, //CJK UNIFIED IDEOGRAPH - 0x9BF8: 0x6DBE, //CJK UNIFIED IDEOGRAPH - 0x9BF9: 0x6DC1, //CJK UNIFIED IDEOGRAPH - 0x9BFA: 0x6DC2, //CJK UNIFIED IDEOGRAPH - 0x9BFB: 0x6DC3, //CJK UNIFIED IDEOGRAPH - 0x9BFC: 0x6DC8, //CJK UNIFIED IDEOGRAPH - 0x9BFD: 0x6DC9, //CJK UNIFIED IDEOGRAPH - 0x9BFE: 0x6DCA, //CJK UNIFIED IDEOGRAPH - 0x9C40: 0x6DCD, //CJK UNIFIED IDEOGRAPH - 0x9C41: 0x6DCE, //CJK UNIFIED IDEOGRAPH - 0x9C42: 0x6DCF, //CJK UNIFIED IDEOGRAPH - 0x9C43: 0x6DD0, //CJK UNIFIED IDEOGRAPH - 0x9C44: 0x6DD2, //CJK UNIFIED IDEOGRAPH - 0x9C45: 0x6DD3, //CJK UNIFIED IDEOGRAPH - 0x9C46: 0x6DD4, //CJK UNIFIED IDEOGRAPH - 0x9C47: 0x6DD5, //CJK UNIFIED IDEOGRAPH - 0x9C48: 0x6DD7, //CJK UNIFIED IDEOGRAPH - 0x9C49: 0x6DDA, //CJK UNIFIED IDEOGRAPH - 0x9C4A: 0x6DDB, //CJK UNIFIED IDEOGRAPH - 0x9C4B: 0x6DDC, //CJK UNIFIED IDEOGRAPH - 0x9C4C: 0x6DDF, //CJK UNIFIED IDEOGRAPH - 0x9C4D: 0x6DE2, //CJK UNIFIED IDEOGRAPH - 0x9C4E: 0x6DE3, //CJK UNIFIED IDEOGRAPH - 0x9C4F: 0x6DE5, //CJK UNIFIED IDEOGRAPH - 0x9C50: 0x6DE7, //CJK UNIFIED IDEOGRAPH - 0x9C51: 0x6DE8, //CJK UNIFIED IDEOGRAPH - 0x9C52: 0x6DE9, //CJK UNIFIED IDEOGRAPH - 0x9C53: 0x6DEA, //CJK UNIFIED IDEOGRAPH - 0x9C54: 0x6DED, //CJK UNIFIED IDEOGRAPH - 0x9C55: 0x6DEF, //CJK UNIFIED IDEOGRAPH - 0x9C56: 0x6DF0, //CJK UNIFIED IDEOGRAPH - 0x9C57: 0x6DF2, //CJK UNIFIED IDEOGRAPH - 0x9C58: 0x6DF4, //CJK UNIFIED IDEOGRAPH - 0x9C59: 0x6DF5, //CJK UNIFIED IDEOGRAPH - 0x9C5A: 0x6DF6, //CJK UNIFIED IDEOGRAPH - 0x9C5B: 0x6DF8, //CJK UNIFIED IDEOGRAPH - 0x9C5C: 0x6DFA, //CJK UNIFIED IDEOGRAPH - 0x9C5D: 0x6DFD, //CJK UNIFIED IDEOGRAPH - 0x9C5E: 0x6DFE, //CJK UNIFIED IDEOGRAPH - 0x9C5F: 0x6DFF, //CJK UNIFIED IDEOGRAPH - 0x9C60: 0x6E00, //CJK UNIFIED IDEOGRAPH - 0x9C61: 0x6E01, //CJK UNIFIED IDEOGRAPH - 0x9C62: 0x6E02, //CJK UNIFIED IDEOGRAPH - 0x9C63: 0x6E03, //CJK UNIFIED IDEOGRAPH - 0x9C64: 0x6E04, //CJK UNIFIED IDEOGRAPH - 0x9C65: 0x6E06, //CJK UNIFIED IDEOGRAPH - 0x9C66: 0x6E07, //CJK UNIFIED IDEOGRAPH - 0x9C67: 0x6E08, //CJK UNIFIED IDEOGRAPH - 0x9C68: 0x6E09, //CJK UNIFIED IDEOGRAPH - 0x9C69: 0x6E0B, //CJK UNIFIED IDEOGRAPH - 0x9C6A: 0x6E0F, //CJK UNIFIED IDEOGRAPH - 0x9C6B: 0x6E12, //CJK UNIFIED IDEOGRAPH - 0x9C6C: 0x6E13, //CJK UNIFIED IDEOGRAPH - 0x9C6D: 0x6E15, //CJK UNIFIED IDEOGRAPH - 0x9C6E: 0x6E18, //CJK UNIFIED IDEOGRAPH - 0x9C6F: 0x6E19, //CJK UNIFIED IDEOGRAPH - 0x9C70: 0x6E1B, //CJK UNIFIED IDEOGRAPH - 0x9C71: 0x6E1C, //CJK UNIFIED IDEOGRAPH - 0x9C72: 0x6E1E, //CJK UNIFIED IDEOGRAPH - 0x9C73: 0x6E1F, //CJK UNIFIED IDEOGRAPH - 0x9C74: 0x6E22, //CJK UNIFIED IDEOGRAPH - 0x9C75: 0x6E26, //CJK UNIFIED IDEOGRAPH - 0x9C76: 0x6E27, //CJK UNIFIED IDEOGRAPH - 0x9C77: 0x6E28, //CJK UNIFIED IDEOGRAPH - 0x9C78: 0x6E2A, //CJK UNIFIED IDEOGRAPH - 0x9C79: 0x6E2C, //CJK UNIFIED IDEOGRAPH - 0x9C7A: 0x6E2E, //CJK UNIFIED IDEOGRAPH - 0x9C7B: 0x6E30, //CJK UNIFIED IDEOGRAPH - 0x9C7C: 0x6E31, //CJK UNIFIED IDEOGRAPH - 0x9C7D: 0x6E33, //CJK UNIFIED IDEOGRAPH - 0x9C7E: 0x6E35, //CJK UNIFIED IDEOGRAPH - 0x9C80: 0x6E36, //CJK UNIFIED IDEOGRAPH - 0x9C81: 0x6E37, //CJK UNIFIED IDEOGRAPH - 0x9C82: 0x6E39, //CJK UNIFIED IDEOGRAPH - 0x9C83: 0x6E3B, //CJK UNIFIED IDEOGRAPH - 0x9C84: 0x6E3C, //CJK UNIFIED IDEOGRAPH - 0x9C85: 0x6E3D, //CJK UNIFIED IDEOGRAPH - 0x9C86: 0x6E3E, //CJK UNIFIED IDEOGRAPH - 0x9C87: 0x6E3F, //CJK UNIFIED IDEOGRAPH - 0x9C88: 0x6E40, //CJK UNIFIED IDEOGRAPH - 0x9C89: 0x6E41, //CJK UNIFIED IDEOGRAPH - 0x9C8A: 0x6E42, //CJK UNIFIED IDEOGRAPH - 0x9C8B: 0x6E45, //CJK UNIFIED IDEOGRAPH - 0x9C8C: 0x6E46, //CJK UNIFIED IDEOGRAPH - 0x9C8D: 0x6E47, //CJK UNIFIED IDEOGRAPH - 0x9C8E: 0x6E48, //CJK UNIFIED IDEOGRAPH - 0x9C8F: 0x6E49, //CJK UNIFIED IDEOGRAPH - 0x9C90: 0x6E4A, //CJK UNIFIED IDEOGRAPH - 0x9C91: 0x6E4B, //CJK UNIFIED IDEOGRAPH - 0x9C92: 0x6E4C, //CJK UNIFIED IDEOGRAPH - 0x9C93: 0x6E4F, //CJK UNIFIED IDEOGRAPH - 0x9C94: 0x6E50, //CJK UNIFIED IDEOGRAPH - 0x9C95: 0x6E51, //CJK UNIFIED IDEOGRAPH - 0x9C96: 0x6E52, //CJK UNIFIED IDEOGRAPH - 0x9C97: 0x6E55, //CJK UNIFIED IDEOGRAPH - 0x9C98: 0x6E57, //CJK UNIFIED IDEOGRAPH - 0x9C99: 0x6E59, //CJK UNIFIED IDEOGRAPH - 0x9C9A: 0x6E5A, //CJK UNIFIED IDEOGRAPH - 0x9C9B: 0x6E5C, //CJK UNIFIED IDEOGRAPH - 0x9C9C: 0x6E5D, //CJK UNIFIED IDEOGRAPH - 0x9C9D: 0x6E5E, //CJK UNIFIED IDEOGRAPH - 0x9C9E: 0x6E60, //CJK UNIFIED IDEOGRAPH - 0x9C9F: 0x6E61, //CJK UNIFIED IDEOGRAPH - 0x9CA0: 0x6E62, //CJK UNIFIED IDEOGRAPH - 0x9CA1: 0x6E63, //CJK UNIFIED IDEOGRAPH - 0x9CA2: 0x6E64, //CJK UNIFIED IDEOGRAPH - 0x9CA3: 0x6E65, //CJK UNIFIED IDEOGRAPH - 0x9CA4: 0x6E66, //CJK UNIFIED IDEOGRAPH - 0x9CA5: 0x6E67, //CJK UNIFIED IDEOGRAPH - 0x9CA6: 0x6E68, //CJK UNIFIED IDEOGRAPH - 0x9CA7: 0x6E69, //CJK UNIFIED IDEOGRAPH - 0x9CA8: 0x6E6A, //CJK UNIFIED IDEOGRAPH - 0x9CA9: 0x6E6C, //CJK UNIFIED IDEOGRAPH - 0x9CAA: 0x6E6D, //CJK UNIFIED IDEOGRAPH - 0x9CAB: 0x6E6F, //CJK UNIFIED IDEOGRAPH - 0x9CAC: 0x6E70, //CJK UNIFIED IDEOGRAPH - 0x9CAD: 0x6E71, //CJK UNIFIED IDEOGRAPH - 0x9CAE: 0x6E72, //CJK UNIFIED IDEOGRAPH - 0x9CAF: 0x6E73, //CJK UNIFIED IDEOGRAPH - 0x9CB0: 0x6E74, //CJK UNIFIED IDEOGRAPH - 0x9CB1: 0x6E75, //CJK UNIFIED IDEOGRAPH - 0x9CB2: 0x6E76, //CJK UNIFIED IDEOGRAPH - 0x9CB3: 0x6E77, //CJK UNIFIED IDEOGRAPH - 0x9CB4: 0x6E78, //CJK UNIFIED IDEOGRAPH - 0x9CB5: 0x6E79, //CJK UNIFIED IDEOGRAPH - 0x9CB6: 0x6E7A, //CJK UNIFIED IDEOGRAPH - 0x9CB7: 0x6E7B, //CJK UNIFIED IDEOGRAPH - 0x9CB8: 0x6E7C, //CJK UNIFIED IDEOGRAPH - 0x9CB9: 0x6E7D, //CJK UNIFIED IDEOGRAPH - 0x9CBA: 0x6E80, //CJK UNIFIED IDEOGRAPH - 0x9CBB: 0x6E81, //CJK UNIFIED IDEOGRAPH - 0x9CBC: 0x6E82, //CJK UNIFIED IDEOGRAPH - 0x9CBD: 0x6E84, //CJK UNIFIED IDEOGRAPH - 0x9CBE: 0x6E87, //CJK UNIFIED IDEOGRAPH - 0x9CBF: 0x6E88, //CJK UNIFIED IDEOGRAPH - 0x9CC0: 0x6E8A, //CJK UNIFIED IDEOGRAPH - 0x9CC1: 0x6E8B, //CJK UNIFIED IDEOGRAPH - 0x9CC2: 0x6E8C, //CJK UNIFIED IDEOGRAPH - 0x9CC3: 0x6E8D, //CJK UNIFIED IDEOGRAPH - 0x9CC4: 0x6E8E, //CJK UNIFIED IDEOGRAPH - 0x9CC5: 0x6E91, //CJK UNIFIED IDEOGRAPH - 0x9CC6: 0x6E92, //CJK UNIFIED IDEOGRAPH - 0x9CC7: 0x6E93, //CJK UNIFIED IDEOGRAPH - 0x9CC8: 0x6E94, //CJK UNIFIED IDEOGRAPH - 0x9CC9: 0x6E95, //CJK UNIFIED IDEOGRAPH - 0x9CCA: 0x6E96, //CJK UNIFIED IDEOGRAPH - 0x9CCB: 0x6E97, //CJK UNIFIED IDEOGRAPH - 0x9CCC: 0x6E99, //CJK UNIFIED IDEOGRAPH - 0x9CCD: 0x6E9A, //CJK UNIFIED IDEOGRAPH - 0x9CCE: 0x6E9B, //CJK UNIFIED IDEOGRAPH - 0x9CCF: 0x6E9D, //CJK UNIFIED IDEOGRAPH - 0x9CD0: 0x6E9E, //CJK UNIFIED IDEOGRAPH - 0x9CD1: 0x6EA0, //CJK UNIFIED IDEOGRAPH - 0x9CD2: 0x6EA1, //CJK UNIFIED IDEOGRAPH - 0x9CD3: 0x6EA3, //CJK UNIFIED IDEOGRAPH - 0x9CD4: 0x6EA4, //CJK UNIFIED IDEOGRAPH - 0x9CD5: 0x6EA6, //CJK UNIFIED IDEOGRAPH - 0x9CD6: 0x6EA8, //CJK UNIFIED IDEOGRAPH - 0x9CD7: 0x6EA9, //CJK UNIFIED IDEOGRAPH - 0x9CD8: 0x6EAB, //CJK UNIFIED IDEOGRAPH - 0x9CD9: 0x6EAC, //CJK UNIFIED IDEOGRAPH - 0x9CDA: 0x6EAD, //CJK UNIFIED IDEOGRAPH - 0x9CDB: 0x6EAE, //CJK UNIFIED IDEOGRAPH - 0x9CDC: 0x6EB0, //CJK UNIFIED IDEOGRAPH - 0x9CDD: 0x6EB3, //CJK UNIFIED IDEOGRAPH - 0x9CDE: 0x6EB5, //CJK UNIFIED IDEOGRAPH - 0x9CDF: 0x6EB8, //CJK UNIFIED IDEOGRAPH - 0x9CE0: 0x6EB9, //CJK UNIFIED IDEOGRAPH - 0x9CE1: 0x6EBC, //CJK UNIFIED IDEOGRAPH - 0x9CE2: 0x6EBE, //CJK UNIFIED IDEOGRAPH - 0x9CE3: 0x6EBF, //CJK UNIFIED IDEOGRAPH - 0x9CE4: 0x6EC0, //CJK UNIFIED IDEOGRAPH - 0x9CE5: 0x6EC3, //CJK UNIFIED IDEOGRAPH - 0x9CE6: 0x6EC4, //CJK UNIFIED IDEOGRAPH - 0x9CE7: 0x6EC5, //CJK UNIFIED IDEOGRAPH - 0x9CE8: 0x6EC6, //CJK UNIFIED IDEOGRAPH - 0x9CE9: 0x6EC8, //CJK UNIFIED IDEOGRAPH - 0x9CEA: 0x6EC9, //CJK UNIFIED IDEOGRAPH - 0x9CEB: 0x6ECA, //CJK UNIFIED IDEOGRAPH - 0x9CEC: 0x6ECC, //CJK UNIFIED IDEOGRAPH - 0x9CED: 0x6ECD, //CJK UNIFIED IDEOGRAPH - 0x9CEE: 0x6ECE, //CJK UNIFIED IDEOGRAPH - 0x9CEF: 0x6ED0, //CJK UNIFIED IDEOGRAPH - 0x9CF0: 0x6ED2, //CJK UNIFIED IDEOGRAPH - 0x9CF1: 0x6ED6, //CJK UNIFIED IDEOGRAPH - 0x9CF2: 0x6ED8, //CJK UNIFIED IDEOGRAPH - 0x9CF3: 0x6ED9, //CJK UNIFIED IDEOGRAPH - 0x9CF4: 0x6EDB, //CJK UNIFIED IDEOGRAPH - 0x9CF5: 0x6EDC, //CJK UNIFIED IDEOGRAPH - 0x9CF6: 0x6EDD, //CJK UNIFIED IDEOGRAPH - 0x9CF7: 0x6EE3, //CJK UNIFIED IDEOGRAPH - 0x9CF8: 0x6EE7, //CJK UNIFIED IDEOGRAPH - 0x9CF9: 0x6EEA, //CJK UNIFIED IDEOGRAPH - 0x9CFA: 0x6EEB, //CJK UNIFIED IDEOGRAPH - 0x9CFB: 0x6EEC, //CJK UNIFIED IDEOGRAPH - 0x9CFC: 0x6EED, //CJK UNIFIED IDEOGRAPH - 0x9CFD: 0x6EEE, //CJK UNIFIED IDEOGRAPH - 0x9CFE: 0x6EEF, //CJK UNIFIED IDEOGRAPH - 0x9D40: 0x6EF0, //CJK UNIFIED IDEOGRAPH - 0x9D41: 0x6EF1, //CJK UNIFIED IDEOGRAPH - 0x9D42: 0x6EF2, //CJK UNIFIED IDEOGRAPH - 0x9D43: 0x6EF3, //CJK UNIFIED IDEOGRAPH - 0x9D44: 0x6EF5, //CJK UNIFIED IDEOGRAPH - 0x9D45: 0x6EF6, //CJK UNIFIED IDEOGRAPH - 0x9D46: 0x6EF7, //CJK UNIFIED IDEOGRAPH - 0x9D47: 0x6EF8, //CJK UNIFIED IDEOGRAPH - 0x9D48: 0x6EFA, //CJK UNIFIED IDEOGRAPH - 0x9D49: 0x6EFB, //CJK UNIFIED IDEOGRAPH - 0x9D4A: 0x6EFC, //CJK UNIFIED IDEOGRAPH - 0x9D4B: 0x6EFD, //CJK UNIFIED IDEOGRAPH - 0x9D4C: 0x6EFE, //CJK UNIFIED IDEOGRAPH - 0x9D4D: 0x6EFF, //CJK UNIFIED IDEOGRAPH - 0x9D4E: 0x6F00, //CJK UNIFIED IDEOGRAPH - 0x9D4F: 0x6F01, //CJK UNIFIED IDEOGRAPH - 0x9D50: 0x6F03, //CJK UNIFIED IDEOGRAPH - 0x9D51: 0x6F04, //CJK UNIFIED IDEOGRAPH - 0x9D52: 0x6F05, //CJK UNIFIED IDEOGRAPH - 0x9D53: 0x6F07, //CJK UNIFIED IDEOGRAPH - 0x9D54: 0x6F08, //CJK UNIFIED IDEOGRAPH - 0x9D55: 0x6F0A, //CJK UNIFIED IDEOGRAPH - 0x9D56: 0x6F0B, //CJK UNIFIED IDEOGRAPH - 0x9D57: 0x6F0C, //CJK UNIFIED IDEOGRAPH - 0x9D58: 0x6F0D, //CJK UNIFIED IDEOGRAPH - 0x9D59: 0x6F0E, //CJK UNIFIED IDEOGRAPH - 0x9D5A: 0x6F10, //CJK UNIFIED IDEOGRAPH - 0x9D5B: 0x6F11, //CJK UNIFIED IDEOGRAPH - 0x9D5C: 0x6F12, //CJK UNIFIED IDEOGRAPH - 0x9D5D: 0x6F16, //CJK UNIFIED IDEOGRAPH - 0x9D5E: 0x6F17, //CJK UNIFIED IDEOGRAPH - 0x9D5F: 0x6F18, //CJK UNIFIED IDEOGRAPH - 0x9D60: 0x6F19, //CJK UNIFIED IDEOGRAPH - 0x9D61: 0x6F1A, //CJK UNIFIED IDEOGRAPH - 0x9D62: 0x6F1B, //CJK UNIFIED IDEOGRAPH - 0x9D63: 0x6F1C, //CJK UNIFIED IDEOGRAPH - 0x9D64: 0x6F1D, //CJK UNIFIED IDEOGRAPH - 0x9D65: 0x6F1E, //CJK UNIFIED IDEOGRAPH - 0x9D66: 0x6F1F, //CJK UNIFIED IDEOGRAPH - 0x9D67: 0x6F21, //CJK UNIFIED IDEOGRAPH - 0x9D68: 0x6F22, //CJK UNIFIED IDEOGRAPH - 0x9D69: 0x6F23, //CJK UNIFIED IDEOGRAPH - 0x9D6A: 0x6F25, //CJK UNIFIED IDEOGRAPH - 0x9D6B: 0x6F26, //CJK UNIFIED IDEOGRAPH - 0x9D6C: 0x6F27, //CJK UNIFIED IDEOGRAPH - 0x9D6D: 0x6F28, //CJK UNIFIED IDEOGRAPH - 0x9D6E: 0x6F2C, //CJK UNIFIED IDEOGRAPH - 0x9D6F: 0x6F2E, //CJK UNIFIED IDEOGRAPH - 0x9D70: 0x6F30, //CJK UNIFIED IDEOGRAPH - 0x9D71: 0x6F32, //CJK UNIFIED IDEOGRAPH - 0x9D72: 0x6F34, //CJK UNIFIED IDEOGRAPH - 0x9D73: 0x6F35, //CJK UNIFIED IDEOGRAPH - 0x9D74: 0x6F37, //CJK UNIFIED IDEOGRAPH - 0x9D75: 0x6F38, //CJK UNIFIED IDEOGRAPH - 0x9D76: 0x6F39, //CJK UNIFIED IDEOGRAPH - 0x9D77: 0x6F3A, //CJK UNIFIED IDEOGRAPH - 0x9D78: 0x6F3B, //CJK UNIFIED IDEOGRAPH - 0x9D79: 0x6F3C, //CJK UNIFIED IDEOGRAPH - 0x9D7A: 0x6F3D, //CJK UNIFIED IDEOGRAPH - 0x9D7B: 0x6F3F, //CJK UNIFIED IDEOGRAPH - 0x9D7C: 0x6F40, //CJK UNIFIED IDEOGRAPH - 0x9D7D: 0x6F41, //CJK UNIFIED IDEOGRAPH - 0x9D7E: 0x6F42, //CJK UNIFIED IDEOGRAPH - 0x9D80: 0x6F43, //CJK UNIFIED IDEOGRAPH - 0x9D81: 0x6F44, //CJK UNIFIED IDEOGRAPH - 0x9D82: 0x6F45, //CJK UNIFIED IDEOGRAPH - 0x9D83: 0x6F48, //CJK UNIFIED IDEOGRAPH - 0x9D84: 0x6F49, //CJK UNIFIED IDEOGRAPH - 0x9D85: 0x6F4A, //CJK UNIFIED IDEOGRAPH - 0x9D86: 0x6F4C, //CJK UNIFIED IDEOGRAPH - 0x9D87: 0x6F4E, //CJK UNIFIED IDEOGRAPH - 0x9D88: 0x6F4F, //CJK UNIFIED IDEOGRAPH - 0x9D89: 0x6F50, //CJK UNIFIED IDEOGRAPH - 0x9D8A: 0x6F51, //CJK UNIFIED IDEOGRAPH - 0x9D8B: 0x6F52, //CJK UNIFIED IDEOGRAPH - 0x9D8C: 0x6F53, //CJK UNIFIED IDEOGRAPH - 0x9D8D: 0x6F54, //CJK UNIFIED IDEOGRAPH - 0x9D8E: 0x6F55, //CJK UNIFIED IDEOGRAPH - 0x9D8F: 0x6F56, //CJK UNIFIED IDEOGRAPH - 0x9D90: 0x6F57, //CJK UNIFIED IDEOGRAPH - 0x9D91: 0x6F59, //CJK UNIFIED IDEOGRAPH - 0x9D92: 0x6F5A, //CJK UNIFIED IDEOGRAPH - 0x9D93: 0x6F5B, //CJK UNIFIED IDEOGRAPH - 0x9D94: 0x6F5D, //CJK UNIFIED IDEOGRAPH - 0x9D95: 0x6F5F, //CJK UNIFIED IDEOGRAPH - 0x9D96: 0x6F60, //CJK UNIFIED IDEOGRAPH - 0x9D97: 0x6F61, //CJK UNIFIED IDEOGRAPH - 0x9D98: 0x6F63, //CJK UNIFIED IDEOGRAPH - 0x9D99: 0x6F64, //CJK UNIFIED IDEOGRAPH - 0x9D9A: 0x6F65, //CJK UNIFIED IDEOGRAPH - 0x9D9B: 0x6F67, //CJK UNIFIED IDEOGRAPH - 0x9D9C: 0x6F68, //CJK UNIFIED IDEOGRAPH - 0x9D9D: 0x6F69, //CJK UNIFIED IDEOGRAPH - 0x9D9E: 0x6F6A, //CJK UNIFIED IDEOGRAPH - 0x9D9F: 0x6F6B, //CJK UNIFIED IDEOGRAPH - 0x9DA0: 0x6F6C, //CJK UNIFIED IDEOGRAPH - 0x9DA1: 0x6F6F, //CJK UNIFIED IDEOGRAPH - 0x9DA2: 0x6F70, //CJK UNIFIED IDEOGRAPH - 0x9DA3: 0x6F71, //CJK UNIFIED IDEOGRAPH - 0x9DA4: 0x6F73, //CJK UNIFIED IDEOGRAPH - 0x9DA5: 0x6F75, //CJK UNIFIED IDEOGRAPH - 0x9DA6: 0x6F76, //CJK UNIFIED IDEOGRAPH - 0x9DA7: 0x6F77, //CJK UNIFIED IDEOGRAPH - 0x9DA8: 0x6F79, //CJK UNIFIED IDEOGRAPH - 0x9DA9: 0x6F7B, //CJK UNIFIED IDEOGRAPH - 0x9DAA: 0x6F7D, //CJK UNIFIED IDEOGRAPH - 0x9DAB: 0x6F7E, //CJK UNIFIED IDEOGRAPH - 0x9DAC: 0x6F7F, //CJK UNIFIED IDEOGRAPH - 0x9DAD: 0x6F80, //CJK UNIFIED IDEOGRAPH - 0x9DAE: 0x6F81, //CJK UNIFIED IDEOGRAPH - 0x9DAF: 0x6F82, //CJK UNIFIED IDEOGRAPH - 0x9DB0: 0x6F83, //CJK UNIFIED IDEOGRAPH - 0x9DB1: 0x6F85, //CJK UNIFIED IDEOGRAPH - 0x9DB2: 0x6F86, //CJK UNIFIED IDEOGRAPH - 0x9DB3: 0x6F87, //CJK UNIFIED IDEOGRAPH - 0x9DB4: 0x6F8A, //CJK UNIFIED IDEOGRAPH - 0x9DB5: 0x6F8B, //CJK UNIFIED IDEOGRAPH - 0x9DB6: 0x6F8F, //CJK UNIFIED IDEOGRAPH - 0x9DB7: 0x6F90, //CJK UNIFIED IDEOGRAPH - 0x9DB8: 0x6F91, //CJK UNIFIED IDEOGRAPH - 0x9DB9: 0x6F92, //CJK UNIFIED IDEOGRAPH - 0x9DBA: 0x6F93, //CJK UNIFIED IDEOGRAPH - 0x9DBB: 0x6F94, //CJK UNIFIED IDEOGRAPH - 0x9DBC: 0x6F95, //CJK UNIFIED IDEOGRAPH - 0x9DBD: 0x6F96, //CJK UNIFIED IDEOGRAPH - 0x9DBE: 0x6F97, //CJK UNIFIED IDEOGRAPH - 0x9DBF: 0x6F98, //CJK UNIFIED IDEOGRAPH - 0x9DC0: 0x6F99, //CJK UNIFIED IDEOGRAPH - 0x9DC1: 0x6F9A, //CJK UNIFIED IDEOGRAPH - 0x9DC2: 0x6F9B, //CJK UNIFIED IDEOGRAPH - 0x9DC3: 0x6F9D, //CJK UNIFIED IDEOGRAPH - 0x9DC4: 0x6F9E, //CJK UNIFIED IDEOGRAPH - 0x9DC5: 0x6F9F, //CJK UNIFIED IDEOGRAPH - 0x9DC6: 0x6FA0, //CJK UNIFIED IDEOGRAPH - 0x9DC7: 0x6FA2, //CJK UNIFIED IDEOGRAPH - 0x9DC8: 0x6FA3, //CJK UNIFIED IDEOGRAPH - 0x9DC9: 0x6FA4, //CJK UNIFIED IDEOGRAPH - 0x9DCA: 0x6FA5, //CJK UNIFIED IDEOGRAPH - 0x9DCB: 0x6FA6, //CJK UNIFIED IDEOGRAPH - 0x9DCC: 0x6FA8, //CJK UNIFIED IDEOGRAPH - 0x9DCD: 0x6FA9, //CJK UNIFIED IDEOGRAPH - 0x9DCE: 0x6FAA, //CJK UNIFIED IDEOGRAPH - 0x9DCF: 0x6FAB, //CJK UNIFIED IDEOGRAPH - 0x9DD0: 0x6FAC, //CJK UNIFIED IDEOGRAPH - 0x9DD1: 0x6FAD, //CJK UNIFIED IDEOGRAPH - 0x9DD2: 0x6FAE, //CJK UNIFIED IDEOGRAPH - 0x9DD3: 0x6FAF, //CJK UNIFIED IDEOGRAPH - 0x9DD4: 0x6FB0, //CJK UNIFIED IDEOGRAPH - 0x9DD5: 0x6FB1, //CJK UNIFIED IDEOGRAPH - 0x9DD6: 0x6FB2, //CJK UNIFIED IDEOGRAPH - 0x9DD7: 0x6FB4, //CJK UNIFIED IDEOGRAPH - 0x9DD8: 0x6FB5, //CJK UNIFIED IDEOGRAPH - 0x9DD9: 0x6FB7, //CJK UNIFIED IDEOGRAPH - 0x9DDA: 0x6FB8, //CJK UNIFIED IDEOGRAPH - 0x9DDB: 0x6FBA, //CJK UNIFIED IDEOGRAPH - 0x9DDC: 0x6FBB, //CJK UNIFIED IDEOGRAPH - 0x9DDD: 0x6FBC, //CJK UNIFIED IDEOGRAPH - 0x9DDE: 0x6FBD, //CJK UNIFIED IDEOGRAPH - 0x9DDF: 0x6FBE, //CJK UNIFIED IDEOGRAPH - 0x9DE0: 0x6FBF, //CJK UNIFIED IDEOGRAPH - 0x9DE1: 0x6FC1, //CJK UNIFIED IDEOGRAPH - 0x9DE2: 0x6FC3, //CJK UNIFIED IDEOGRAPH - 0x9DE3: 0x6FC4, //CJK UNIFIED IDEOGRAPH - 0x9DE4: 0x6FC5, //CJK UNIFIED IDEOGRAPH - 0x9DE5: 0x6FC6, //CJK UNIFIED IDEOGRAPH - 0x9DE6: 0x6FC7, //CJK UNIFIED IDEOGRAPH - 0x9DE7: 0x6FC8, //CJK UNIFIED IDEOGRAPH - 0x9DE8: 0x6FCA, //CJK UNIFIED IDEOGRAPH - 0x9DE9: 0x6FCB, //CJK UNIFIED IDEOGRAPH - 0x9DEA: 0x6FCC, //CJK UNIFIED IDEOGRAPH - 0x9DEB: 0x6FCD, //CJK UNIFIED IDEOGRAPH - 0x9DEC: 0x6FCE, //CJK UNIFIED IDEOGRAPH - 0x9DED: 0x6FCF, //CJK UNIFIED IDEOGRAPH - 0x9DEE: 0x6FD0, //CJK UNIFIED IDEOGRAPH - 0x9DEF: 0x6FD3, //CJK UNIFIED IDEOGRAPH - 0x9DF0: 0x6FD4, //CJK UNIFIED IDEOGRAPH - 0x9DF1: 0x6FD5, //CJK UNIFIED IDEOGRAPH - 0x9DF2: 0x6FD6, //CJK UNIFIED IDEOGRAPH - 0x9DF3: 0x6FD7, //CJK UNIFIED IDEOGRAPH - 0x9DF4: 0x6FD8, //CJK UNIFIED IDEOGRAPH - 0x9DF5: 0x6FD9, //CJK UNIFIED IDEOGRAPH - 0x9DF6: 0x6FDA, //CJK UNIFIED IDEOGRAPH - 0x9DF7: 0x6FDB, //CJK UNIFIED IDEOGRAPH - 0x9DF8: 0x6FDC, //CJK UNIFIED IDEOGRAPH - 0x9DF9: 0x6FDD, //CJK UNIFIED IDEOGRAPH - 0x9DFA: 0x6FDF, //CJK UNIFIED IDEOGRAPH - 0x9DFB: 0x6FE2, //CJK UNIFIED IDEOGRAPH - 0x9DFC: 0x6FE3, //CJK UNIFIED IDEOGRAPH - 0x9DFD: 0x6FE4, //CJK UNIFIED IDEOGRAPH - 0x9DFE: 0x6FE5, //CJK UNIFIED IDEOGRAPH - 0x9E40: 0x6FE6, //CJK UNIFIED IDEOGRAPH - 0x9E41: 0x6FE7, //CJK UNIFIED IDEOGRAPH - 0x9E42: 0x6FE8, //CJK UNIFIED IDEOGRAPH - 0x9E43: 0x6FE9, //CJK UNIFIED IDEOGRAPH - 0x9E44: 0x6FEA, //CJK UNIFIED IDEOGRAPH - 0x9E45: 0x6FEB, //CJK UNIFIED IDEOGRAPH - 0x9E46: 0x6FEC, //CJK UNIFIED IDEOGRAPH - 0x9E47: 0x6FED, //CJK UNIFIED IDEOGRAPH - 0x9E48: 0x6FF0, //CJK UNIFIED IDEOGRAPH - 0x9E49: 0x6FF1, //CJK UNIFIED IDEOGRAPH - 0x9E4A: 0x6FF2, //CJK UNIFIED IDEOGRAPH - 0x9E4B: 0x6FF3, //CJK UNIFIED IDEOGRAPH - 0x9E4C: 0x6FF4, //CJK UNIFIED IDEOGRAPH - 0x9E4D: 0x6FF5, //CJK UNIFIED IDEOGRAPH - 0x9E4E: 0x6FF6, //CJK UNIFIED IDEOGRAPH - 0x9E4F: 0x6FF7, //CJK UNIFIED IDEOGRAPH - 0x9E50: 0x6FF8, //CJK UNIFIED IDEOGRAPH - 0x9E51: 0x6FF9, //CJK UNIFIED IDEOGRAPH - 0x9E52: 0x6FFA, //CJK UNIFIED IDEOGRAPH - 0x9E53: 0x6FFB, //CJK UNIFIED IDEOGRAPH - 0x9E54: 0x6FFC, //CJK UNIFIED IDEOGRAPH - 0x9E55: 0x6FFD, //CJK UNIFIED IDEOGRAPH - 0x9E56: 0x6FFE, //CJK UNIFIED IDEOGRAPH - 0x9E57: 0x6FFF, //CJK UNIFIED IDEOGRAPH - 0x9E58: 0x7000, //CJK UNIFIED IDEOGRAPH - 0x9E59: 0x7001, //CJK UNIFIED IDEOGRAPH - 0x9E5A: 0x7002, //CJK UNIFIED IDEOGRAPH - 0x9E5B: 0x7003, //CJK UNIFIED IDEOGRAPH - 0x9E5C: 0x7004, //CJK UNIFIED IDEOGRAPH - 0x9E5D: 0x7005, //CJK UNIFIED IDEOGRAPH - 0x9E5E: 0x7006, //CJK UNIFIED IDEOGRAPH - 0x9E5F: 0x7007, //CJK UNIFIED IDEOGRAPH - 0x9E60: 0x7008, //CJK UNIFIED IDEOGRAPH - 0x9E61: 0x7009, //CJK UNIFIED IDEOGRAPH - 0x9E62: 0x700A, //CJK UNIFIED IDEOGRAPH - 0x9E63: 0x700B, //CJK UNIFIED IDEOGRAPH - 0x9E64: 0x700C, //CJK UNIFIED IDEOGRAPH - 0x9E65: 0x700D, //CJK UNIFIED IDEOGRAPH - 0x9E66: 0x700E, //CJK UNIFIED IDEOGRAPH - 0x9E67: 0x700F, //CJK UNIFIED IDEOGRAPH - 0x9E68: 0x7010, //CJK UNIFIED IDEOGRAPH - 0x9E69: 0x7012, //CJK UNIFIED IDEOGRAPH - 0x9E6A: 0x7013, //CJK UNIFIED IDEOGRAPH - 0x9E6B: 0x7014, //CJK UNIFIED IDEOGRAPH - 0x9E6C: 0x7015, //CJK UNIFIED IDEOGRAPH - 0x9E6D: 0x7016, //CJK UNIFIED IDEOGRAPH - 0x9E6E: 0x7017, //CJK UNIFIED IDEOGRAPH - 0x9E6F: 0x7018, //CJK UNIFIED IDEOGRAPH - 0x9E70: 0x7019, //CJK UNIFIED IDEOGRAPH - 0x9E71: 0x701C, //CJK UNIFIED IDEOGRAPH - 0x9E72: 0x701D, //CJK UNIFIED IDEOGRAPH - 0x9E73: 0x701E, //CJK UNIFIED IDEOGRAPH - 0x9E74: 0x701F, //CJK UNIFIED IDEOGRAPH - 0x9E75: 0x7020, //CJK UNIFIED IDEOGRAPH - 0x9E76: 0x7021, //CJK UNIFIED IDEOGRAPH - 0x9E77: 0x7022, //CJK UNIFIED IDEOGRAPH - 0x9E78: 0x7024, //CJK UNIFIED IDEOGRAPH - 0x9E79: 0x7025, //CJK UNIFIED IDEOGRAPH - 0x9E7A: 0x7026, //CJK UNIFIED IDEOGRAPH - 0x9E7B: 0x7027, //CJK UNIFIED IDEOGRAPH - 0x9E7C: 0x7028, //CJK UNIFIED IDEOGRAPH - 0x9E7D: 0x7029, //CJK UNIFIED IDEOGRAPH - 0x9E7E: 0x702A, //CJK UNIFIED IDEOGRAPH - 0x9E80: 0x702B, //CJK UNIFIED IDEOGRAPH - 0x9E81: 0x702C, //CJK UNIFIED IDEOGRAPH - 0x9E82: 0x702D, //CJK UNIFIED IDEOGRAPH - 0x9E83: 0x702E, //CJK UNIFIED IDEOGRAPH - 0x9E84: 0x702F, //CJK UNIFIED IDEOGRAPH - 0x9E85: 0x7030, //CJK UNIFIED IDEOGRAPH - 0x9E86: 0x7031, //CJK UNIFIED IDEOGRAPH - 0x9E87: 0x7032, //CJK UNIFIED IDEOGRAPH - 0x9E88: 0x7033, //CJK UNIFIED IDEOGRAPH - 0x9E89: 0x7034, //CJK UNIFIED IDEOGRAPH - 0x9E8A: 0x7036, //CJK UNIFIED IDEOGRAPH - 0x9E8B: 0x7037, //CJK UNIFIED IDEOGRAPH - 0x9E8C: 0x7038, //CJK UNIFIED IDEOGRAPH - 0x9E8D: 0x703A, //CJK UNIFIED IDEOGRAPH - 0x9E8E: 0x703B, //CJK UNIFIED IDEOGRAPH - 0x9E8F: 0x703C, //CJK UNIFIED IDEOGRAPH - 0x9E90: 0x703D, //CJK UNIFIED IDEOGRAPH - 0x9E91: 0x703E, //CJK UNIFIED IDEOGRAPH - 0x9E92: 0x703F, //CJK UNIFIED IDEOGRAPH - 0x9E93: 0x7040, //CJK UNIFIED IDEOGRAPH - 0x9E94: 0x7041, //CJK UNIFIED IDEOGRAPH - 0x9E95: 0x7042, //CJK UNIFIED IDEOGRAPH - 0x9E96: 0x7043, //CJK UNIFIED IDEOGRAPH - 0x9E97: 0x7044, //CJK UNIFIED IDEOGRAPH - 0x9E98: 0x7045, //CJK UNIFIED IDEOGRAPH - 0x9E99: 0x7046, //CJK UNIFIED IDEOGRAPH - 0x9E9A: 0x7047, //CJK UNIFIED IDEOGRAPH - 0x9E9B: 0x7048, //CJK UNIFIED IDEOGRAPH - 0x9E9C: 0x7049, //CJK UNIFIED IDEOGRAPH - 0x9E9D: 0x704A, //CJK UNIFIED IDEOGRAPH - 0x9E9E: 0x704B, //CJK UNIFIED IDEOGRAPH - 0x9E9F: 0x704D, //CJK UNIFIED IDEOGRAPH - 0x9EA0: 0x704E, //CJK UNIFIED IDEOGRAPH - 0x9EA1: 0x7050, //CJK UNIFIED IDEOGRAPH - 0x9EA2: 0x7051, //CJK UNIFIED IDEOGRAPH - 0x9EA3: 0x7052, //CJK UNIFIED IDEOGRAPH - 0x9EA4: 0x7053, //CJK UNIFIED IDEOGRAPH - 0x9EA5: 0x7054, //CJK UNIFIED IDEOGRAPH - 0x9EA6: 0x7055, //CJK UNIFIED IDEOGRAPH - 0x9EA7: 0x7056, //CJK UNIFIED IDEOGRAPH - 0x9EA8: 0x7057, //CJK UNIFIED IDEOGRAPH - 0x9EA9: 0x7058, //CJK UNIFIED IDEOGRAPH - 0x9EAA: 0x7059, //CJK UNIFIED IDEOGRAPH - 0x9EAB: 0x705A, //CJK UNIFIED IDEOGRAPH - 0x9EAC: 0x705B, //CJK UNIFIED IDEOGRAPH - 0x9EAD: 0x705C, //CJK UNIFIED IDEOGRAPH - 0x9EAE: 0x705D, //CJK UNIFIED IDEOGRAPH - 0x9EAF: 0x705F, //CJK UNIFIED IDEOGRAPH - 0x9EB0: 0x7060, //CJK UNIFIED IDEOGRAPH - 0x9EB1: 0x7061, //CJK UNIFIED IDEOGRAPH - 0x9EB2: 0x7062, //CJK UNIFIED IDEOGRAPH - 0x9EB3: 0x7063, //CJK UNIFIED IDEOGRAPH - 0x9EB4: 0x7064, //CJK UNIFIED IDEOGRAPH - 0x9EB5: 0x7065, //CJK UNIFIED IDEOGRAPH - 0x9EB6: 0x7066, //CJK UNIFIED IDEOGRAPH - 0x9EB7: 0x7067, //CJK UNIFIED IDEOGRAPH - 0x9EB8: 0x7068, //CJK UNIFIED IDEOGRAPH - 0x9EB9: 0x7069, //CJK UNIFIED IDEOGRAPH - 0x9EBA: 0x706A, //CJK UNIFIED IDEOGRAPH - 0x9EBB: 0x706E, //CJK UNIFIED IDEOGRAPH - 0x9EBC: 0x7071, //CJK UNIFIED IDEOGRAPH - 0x9EBD: 0x7072, //CJK UNIFIED IDEOGRAPH - 0x9EBE: 0x7073, //CJK UNIFIED IDEOGRAPH - 0x9EBF: 0x7074, //CJK UNIFIED IDEOGRAPH - 0x9EC0: 0x7077, //CJK UNIFIED IDEOGRAPH - 0x9EC1: 0x7079, //CJK UNIFIED IDEOGRAPH - 0x9EC2: 0x707A, //CJK UNIFIED IDEOGRAPH - 0x9EC3: 0x707B, //CJK UNIFIED IDEOGRAPH - 0x9EC4: 0x707D, //CJK UNIFIED IDEOGRAPH - 0x9EC5: 0x7081, //CJK UNIFIED IDEOGRAPH - 0x9EC6: 0x7082, //CJK UNIFIED IDEOGRAPH - 0x9EC7: 0x7083, //CJK UNIFIED IDEOGRAPH - 0x9EC8: 0x7084, //CJK UNIFIED IDEOGRAPH - 0x9EC9: 0x7086, //CJK UNIFIED IDEOGRAPH - 0x9ECA: 0x7087, //CJK UNIFIED IDEOGRAPH - 0x9ECB: 0x7088, //CJK UNIFIED IDEOGRAPH - 0x9ECC: 0x708B, //CJK UNIFIED IDEOGRAPH - 0x9ECD: 0x708C, //CJK UNIFIED IDEOGRAPH - 0x9ECE: 0x708D, //CJK UNIFIED IDEOGRAPH - 0x9ECF: 0x708F, //CJK UNIFIED IDEOGRAPH - 0x9ED0: 0x7090, //CJK UNIFIED IDEOGRAPH - 0x9ED1: 0x7091, //CJK UNIFIED IDEOGRAPH - 0x9ED2: 0x7093, //CJK UNIFIED IDEOGRAPH - 0x9ED3: 0x7097, //CJK UNIFIED IDEOGRAPH - 0x9ED4: 0x7098, //CJK UNIFIED IDEOGRAPH - 0x9ED5: 0x709A, //CJK UNIFIED IDEOGRAPH - 0x9ED6: 0x709B, //CJK UNIFIED IDEOGRAPH - 0x9ED7: 0x709E, //CJK UNIFIED IDEOGRAPH - 0x9ED8: 0x709F, //CJK UNIFIED IDEOGRAPH - 0x9ED9: 0x70A0, //CJK UNIFIED IDEOGRAPH - 0x9EDA: 0x70A1, //CJK UNIFIED IDEOGRAPH - 0x9EDB: 0x70A2, //CJK UNIFIED IDEOGRAPH - 0x9EDC: 0x70A3, //CJK UNIFIED IDEOGRAPH - 0x9EDD: 0x70A4, //CJK UNIFIED IDEOGRAPH - 0x9EDE: 0x70A5, //CJK UNIFIED IDEOGRAPH - 0x9EDF: 0x70A6, //CJK UNIFIED IDEOGRAPH - 0x9EE0: 0x70A7, //CJK UNIFIED IDEOGRAPH - 0x9EE1: 0x70A8, //CJK UNIFIED IDEOGRAPH - 0x9EE2: 0x70A9, //CJK UNIFIED IDEOGRAPH - 0x9EE3: 0x70AA, //CJK UNIFIED IDEOGRAPH - 0x9EE4: 0x70B0, //CJK UNIFIED IDEOGRAPH - 0x9EE5: 0x70B2, //CJK UNIFIED IDEOGRAPH - 0x9EE6: 0x70B4, //CJK UNIFIED IDEOGRAPH - 0x9EE7: 0x70B5, //CJK UNIFIED IDEOGRAPH - 0x9EE8: 0x70B6, //CJK UNIFIED IDEOGRAPH - 0x9EE9: 0x70BA, //CJK UNIFIED IDEOGRAPH - 0x9EEA: 0x70BE, //CJK UNIFIED IDEOGRAPH - 0x9EEB: 0x70BF, //CJK UNIFIED IDEOGRAPH - 0x9EEC: 0x70C4, //CJK UNIFIED IDEOGRAPH - 0x9EED: 0x70C5, //CJK UNIFIED IDEOGRAPH - 0x9EEE: 0x70C6, //CJK UNIFIED IDEOGRAPH - 0x9EEF: 0x70C7, //CJK UNIFIED IDEOGRAPH - 0x9EF0: 0x70C9, //CJK UNIFIED IDEOGRAPH - 0x9EF1: 0x70CB, //CJK UNIFIED IDEOGRAPH - 0x9EF2: 0x70CC, //CJK UNIFIED IDEOGRAPH - 0x9EF3: 0x70CD, //CJK UNIFIED IDEOGRAPH - 0x9EF4: 0x70CE, //CJK UNIFIED IDEOGRAPH - 0x9EF5: 0x70CF, //CJK UNIFIED IDEOGRAPH - 0x9EF6: 0x70D0, //CJK UNIFIED IDEOGRAPH - 0x9EF7: 0x70D1, //CJK UNIFIED IDEOGRAPH - 0x9EF8: 0x70D2, //CJK UNIFIED IDEOGRAPH - 0x9EF9: 0x70D3, //CJK UNIFIED IDEOGRAPH - 0x9EFA: 0x70D4, //CJK UNIFIED IDEOGRAPH - 0x9EFB: 0x70D5, //CJK UNIFIED IDEOGRAPH - 0x9EFC: 0x70D6, //CJK UNIFIED IDEOGRAPH - 0x9EFD: 0x70D7, //CJK UNIFIED IDEOGRAPH - 0x9EFE: 0x70DA, //CJK UNIFIED IDEOGRAPH - 0x9F40: 0x70DC, //CJK UNIFIED IDEOGRAPH - 0x9F41: 0x70DD, //CJK UNIFIED IDEOGRAPH - 0x9F42: 0x70DE, //CJK UNIFIED IDEOGRAPH - 0x9F43: 0x70E0, //CJK UNIFIED IDEOGRAPH - 0x9F44: 0x70E1, //CJK UNIFIED IDEOGRAPH - 0x9F45: 0x70E2, //CJK UNIFIED IDEOGRAPH - 0x9F46: 0x70E3, //CJK UNIFIED IDEOGRAPH - 0x9F47: 0x70E5, //CJK UNIFIED IDEOGRAPH - 0x9F48: 0x70EA, //CJK UNIFIED IDEOGRAPH - 0x9F49: 0x70EE, //CJK UNIFIED IDEOGRAPH - 0x9F4A: 0x70F0, //CJK UNIFIED IDEOGRAPH - 0x9F4B: 0x70F1, //CJK UNIFIED IDEOGRAPH - 0x9F4C: 0x70F2, //CJK UNIFIED IDEOGRAPH - 0x9F4D: 0x70F3, //CJK UNIFIED IDEOGRAPH - 0x9F4E: 0x70F4, //CJK UNIFIED IDEOGRAPH - 0x9F4F: 0x70F5, //CJK UNIFIED IDEOGRAPH - 0x9F50: 0x70F6, //CJK UNIFIED IDEOGRAPH - 0x9F51: 0x70F8, //CJK UNIFIED IDEOGRAPH - 0x9F52: 0x70FA, //CJK UNIFIED IDEOGRAPH - 0x9F53: 0x70FB, //CJK UNIFIED IDEOGRAPH - 0x9F54: 0x70FC, //CJK UNIFIED IDEOGRAPH - 0x9F55: 0x70FE, //CJK UNIFIED IDEOGRAPH - 0x9F56: 0x70FF, //CJK UNIFIED IDEOGRAPH - 0x9F57: 0x7100, //CJK UNIFIED IDEOGRAPH - 0x9F58: 0x7101, //CJK UNIFIED IDEOGRAPH - 0x9F59: 0x7102, //CJK UNIFIED IDEOGRAPH - 0x9F5A: 0x7103, //CJK UNIFIED IDEOGRAPH - 0x9F5B: 0x7104, //CJK UNIFIED IDEOGRAPH - 0x9F5C: 0x7105, //CJK UNIFIED IDEOGRAPH - 0x9F5D: 0x7106, //CJK UNIFIED IDEOGRAPH - 0x9F5E: 0x7107, //CJK UNIFIED IDEOGRAPH - 0x9F5F: 0x7108, //CJK UNIFIED IDEOGRAPH - 0x9F60: 0x710B, //CJK UNIFIED IDEOGRAPH - 0x9F61: 0x710C, //CJK UNIFIED IDEOGRAPH - 0x9F62: 0x710D, //CJK UNIFIED IDEOGRAPH - 0x9F63: 0x710E, //CJK UNIFIED IDEOGRAPH - 0x9F64: 0x710F, //CJK UNIFIED IDEOGRAPH - 0x9F65: 0x7111, //CJK UNIFIED IDEOGRAPH - 0x9F66: 0x7112, //CJK UNIFIED IDEOGRAPH - 0x9F67: 0x7114, //CJK UNIFIED IDEOGRAPH - 0x9F68: 0x7117, //CJK UNIFIED IDEOGRAPH - 0x9F69: 0x711B, //CJK UNIFIED IDEOGRAPH - 0x9F6A: 0x711C, //CJK UNIFIED IDEOGRAPH - 0x9F6B: 0x711D, //CJK UNIFIED IDEOGRAPH - 0x9F6C: 0x711E, //CJK UNIFIED IDEOGRAPH - 0x9F6D: 0x711F, //CJK UNIFIED IDEOGRAPH - 0x9F6E: 0x7120, //CJK UNIFIED IDEOGRAPH - 0x9F6F: 0x7121, //CJK UNIFIED IDEOGRAPH - 0x9F70: 0x7122, //CJK UNIFIED IDEOGRAPH - 0x9F71: 0x7123, //CJK UNIFIED IDEOGRAPH - 0x9F72: 0x7124, //CJK UNIFIED IDEOGRAPH - 0x9F73: 0x7125, //CJK UNIFIED IDEOGRAPH - 0x9F74: 0x7127, //CJK UNIFIED IDEOGRAPH - 0x9F75: 0x7128, //CJK UNIFIED IDEOGRAPH - 0x9F76: 0x7129, //CJK UNIFIED IDEOGRAPH - 0x9F77: 0x712A, //CJK UNIFIED IDEOGRAPH - 0x9F78: 0x712B, //CJK UNIFIED IDEOGRAPH - 0x9F79: 0x712C, //CJK UNIFIED IDEOGRAPH - 0x9F7A: 0x712D, //CJK UNIFIED IDEOGRAPH - 0x9F7B: 0x712E, //CJK UNIFIED IDEOGRAPH - 0x9F7C: 0x7132, //CJK UNIFIED IDEOGRAPH - 0x9F7D: 0x7133, //CJK UNIFIED IDEOGRAPH - 0x9F7E: 0x7134, //CJK UNIFIED IDEOGRAPH - 0x9F80: 0x7135, //CJK UNIFIED IDEOGRAPH - 0x9F81: 0x7137, //CJK UNIFIED IDEOGRAPH - 0x9F82: 0x7138, //CJK UNIFIED IDEOGRAPH - 0x9F83: 0x7139, //CJK UNIFIED IDEOGRAPH - 0x9F84: 0x713A, //CJK UNIFIED IDEOGRAPH - 0x9F85: 0x713B, //CJK UNIFIED IDEOGRAPH - 0x9F86: 0x713C, //CJK UNIFIED IDEOGRAPH - 0x9F87: 0x713D, //CJK UNIFIED IDEOGRAPH - 0x9F88: 0x713E, //CJK UNIFIED IDEOGRAPH - 0x9F89: 0x713F, //CJK UNIFIED IDEOGRAPH - 0x9F8A: 0x7140, //CJK UNIFIED IDEOGRAPH - 0x9F8B: 0x7141, //CJK UNIFIED IDEOGRAPH - 0x9F8C: 0x7142, //CJK UNIFIED IDEOGRAPH - 0x9F8D: 0x7143, //CJK UNIFIED IDEOGRAPH - 0x9F8E: 0x7144, //CJK UNIFIED IDEOGRAPH - 0x9F8F: 0x7146, //CJK UNIFIED IDEOGRAPH - 0x9F90: 0x7147, //CJK UNIFIED IDEOGRAPH - 0x9F91: 0x7148, //CJK UNIFIED IDEOGRAPH - 0x9F92: 0x7149, //CJK UNIFIED IDEOGRAPH - 0x9F93: 0x714B, //CJK UNIFIED IDEOGRAPH - 0x9F94: 0x714D, //CJK UNIFIED IDEOGRAPH - 0x9F95: 0x714F, //CJK UNIFIED IDEOGRAPH - 0x9F96: 0x7150, //CJK UNIFIED IDEOGRAPH - 0x9F97: 0x7151, //CJK UNIFIED IDEOGRAPH - 0x9F98: 0x7152, //CJK UNIFIED IDEOGRAPH - 0x9F99: 0x7153, //CJK UNIFIED IDEOGRAPH - 0x9F9A: 0x7154, //CJK UNIFIED IDEOGRAPH - 0x9F9B: 0x7155, //CJK UNIFIED IDEOGRAPH - 0x9F9C: 0x7156, //CJK UNIFIED IDEOGRAPH - 0x9F9D: 0x7157, //CJK UNIFIED IDEOGRAPH - 0x9F9E: 0x7158, //CJK UNIFIED IDEOGRAPH - 0x9F9F: 0x7159, //CJK UNIFIED IDEOGRAPH - 0x9FA0: 0x715A, //CJK UNIFIED IDEOGRAPH - 0x9FA1: 0x715B, //CJK UNIFIED IDEOGRAPH - 0x9FA2: 0x715D, //CJK UNIFIED IDEOGRAPH - 0x9FA3: 0x715F, //CJK UNIFIED IDEOGRAPH - 0x9FA4: 0x7160, //CJK UNIFIED IDEOGRAPH - 0x9FA5: 0x7161, //CJK UNIFIED IDEOGRAPH - 0x9FA6: 0x7162, //CJK UNIFIED IDEOGRAPH - 0x9FA7: 0x7163, //CJK UNIFIED IDEOGRAPH - 0x9FA8: 0x7165, //CJK UNIFIED IDEOGRAPH - 0x9FA9: 0x7169, //CJK UNIFIED IDEOGRAPH - 0x9FAA: 0x716A, //CJK UNIFIED IDEOGRAPH - 0x9FAB: 0x716B, //CJK UNIFIED IDEOGRAPH - 0x9FAC: 0x716C, //CJK UNIFIED IDEOGRAPH - 0x9FAD: 0x716D, //CJK UNIFIED IDEOGRAPH - 0x9FAE: 0x716F, //CJK UNIFIED IDEOGRAPH - 0x9FAF: 0x7170, //CJK UNIFIED IDEOGRAPH - 0x9FB0: 0x7171, //CJK UNIFIED IDEOGRAPH - 0x9FB1: 0x7174, //CJK UNIFIED IDEOGRAPH - 0x9FB2: 0x7175, //CJK UNIFIED IDEOGRAPH - 0x9FB3: 0x7176, //CJK UNIFIED IDEOGRAPH - 0x9FB4: 0x7177, //CJK UNIFIED IDEOGRAPH - 0x9FB5: 0x7179, //CJK UNIFIED IDEOGRAPH - 0x9FB6: 0x717B, //CJK UNIFIED IDEOGRAPH - 0x9FB7: 0x717C, //CJK UNIFIED IDEOGRAPH - 0x9FB8: 0x717E, //CJK UNIFIED IDEOGRAPH - 0x9FB9: 0x717F, //CJK UNIFIED IDEOGRAPH - 0x9FBA: 0x7180, //CJK UNIFIED IDEOGRAPH - 0x9FBB: 0x7181, //CJK UNIFIED IDEOGRAPH - 0x9FBC: 0x7182, //CJK UNIFIED IDEOGRAPH - 0x9FBD: 0x7183, //CJK UNIFIED IDEOGRAPH - 0x9FBE: 0x7185, //CJK UNIFIED IDEOGRAPH - 0x9FBF: 0x7186, //CJK UNIFIED IDEOGRAPH - 0x9FC0: 0x7187, //CJK UNIFIED IDEOGRAPH - 0x9FC1: 0x7188, //CJK UNIFIED IDEOGRAPH - 0x9FC2: 0x7189, //CJK UNIFIED IDEOGRAPH - 0x9FC3: 0x718B, //CJK UNIFIED IDEOGRAPH - 0x9FC4: 0x718C, //CJK UNIFIED IDEOGRAPH - 0x9FC5: 0x718D, //CJK UNIFIED IDEOGRAPH - 0x9FC6: 0x718E, //CJK UNIFIED IDEOGRAPH - 0x9FC7: 0x7190, //CJK UNIFIED IDEOGRAPH - 0x9FC8: 0x7191, //CJK UNIFIED IDEOGRAPH - 0x9FC9: 0x7192, //CJK UNIFIED IDEOGRAPH - 0x9FCA: 0x7193, //CJK UNIFIED IDEOGRAPH - 0x9FCB: 0x7195, //CJK UNIFIED IDEOGRAPH - 0x9FCC: 0x7196, //CJK UNIFIED IDEOGRAPH - 0x9FCD: 0x7197, //CJK UNIFIED IDEOGRAPH - 0x9FCE: 0x719A, //CJK UNIFIED IDEOGRAPH - 0x9FCF: 0x719B, //CJK UNIFIED IDEOGRAPH - 0x9FD0: 0x719C, //CJK UNIFIED IDEOGRAPH - 0x9FD1: 0x719D, //CJK UNIFIED IDEOGRAPH - 0x9FD2: 0x719E, //CJK UNIFIED IDEOGRAPH - 0x9FD3: 0x71A1, //CJK UNIFIED IDEOGRAPH - 0x9FD4: 0x71A2, //CJK UNIFIED IDEOGRAPH - 0x9FD5: 0x71A3, //CJK UNIFIED IDEOGRAPH - 0x9FD6: 0x71A4, //CJK UNIFIED IDEOGRAPH - 0x9FD7: 0x71A5, //CJK UNIFIED IDEOGRAPH - 0x9FD8: 0x71A6, //CJK UNIFIED IDEOGRAPH - 0x9FD9: 0x71A7, //CJK UNIFIED IDEOGRAPH - 0x9FDA: 0x71A9, //CJK UNIFIED IDEOGRAPH - 0x9FDB: 0x71AA, //CJK UNIFIED IDEOGRAPH - 0x9FDC: 0x71AB, //CJK UNIFIED IDEOGRAPH - 0x9FDD: 0x71AD, //CJK UNIFIED IDEOGRAPH - 0x9FDE: 0x71AE, //CJK UNIFIED IDEOGRAPH - 0x9FDF: 0x71AF, //CJK UNIFIED IDEOGRAPH - 0x9FE0: 0x71B0, //CJK UNIFIED IDEOGRAPH - 0x9FE1: 0x71B1, //CJK UNIFIED IDEOGRAPH - 0x9FE2: 0x71B2, //CJK UNIFIED IDEOGRAPH - 0x9FE3: 0x71B4, //CJK UNIFIED IDEOGRAPH - 0x9FE4: 0x71B6, //CJK UNIFIED IDEOGRAPH - 0x9FE5: 0x71B7, //CJK UNIFIED IDEOGRAPH - 0x9FE6: 0x71B8, //CJK UNIFIED IDEOGRAPH - 0x9FE7: 0x71BA, //CJK UNIFIED IDEOGRAPH - 0x9FE8: 0x71BB, //CJK UNIFIED IDEOGRAPH - 0x9FE9: 0x71BC, //CJK UNIFIED IDEOGRAPH - 0x9FEA: 0x71BD, //CJK UNIFIED IDEOGRAPH - 0x9FEB: 0x71BE, //CJK UNIFIED IDEOGRAPH - 0x9FEC: 0x71BF, //CJK UNIFIED IDEOGRAPH - 0x9FED: 0x71C0, //CJK UNIFIED IDEOGRAPH - 0x9FEE: 0x71C1, //CJK UNIFIED IDEOGRAPH - 0x9FEF: 0x71C2, //CJK UNIFIED IDEOGRAPH - 0x9FF0: 0x71C4, //CJK UNIFIED IDEOGRAPH - 0x9FF1: 0x71C5, //CJK UNIFIED IDEOGRAPH - 0x9FF2: 0x71C6, //CJK UNIFIED IDEOGRAPH - 0x9FF3: 0x71C7, //CJK UNIFIED IDEOGRAPH - 0x9FF4: 0x71C8, //CJK UNIFIED IDEOGRAPH - 0x9FF5: 0x71C9, //CJK UNIFIED IDEOGRAPH - 0x9FF6: 0x71CA, //CJK UNIFIED IDEOGRAPH - 0x9FF7: 0x71CB, //CJK UNIFIED IDEOGRAPH - 0x9FF8: 0x71CC, //CJK UNIFIED IDEOGRAPH - 0x9FF9: 0x71CD, //CJK UNIFIED IDEOGRAPH - 0x9FFA: 0x71CF, //CJK UNIFIED IDEOGRAPH - 0x9FFB: 0x71D0, //CJK UNIFIED IDEOGRAPH - 0x9FFC: 0x71D1, //CJK UNIFIED IDEOGRAPH - 0x9FFD: 0x71D2, //CJK UNIFIED IDEOGRAPH - 0x9FFE: 0x71D3, //CJK UNIFIED IDEOGRAPH - 0xA040: 0x71D6, //CJK UNIFIED IDEOGRAPH - 0xA041: 0x71D7, //CJK UNIFIED IDEOGRAPH - 0xA042: 0x71D8, //CJK UNIFIED IDEOGRAPH - 0xA043: 0x71D9, //CJK UNIFIED IDEOGRAPH - 0xA044: 0x71DA, //CJK UNIFIED IDEOGRAPH - 0xA045: 0x71DB, //CJK UNIFIED IDEOGRAPH - 0xA046: 0x71DC, //CJK UNIFIED IDEOGRAPH - 0xA047: 0x71DD, //CJK UNIFIED IDEOGRAPH - 0xA048: 0x71DE, //CJK UNIFIED IDEOGRAPH - 0xA049: 0x71DF, //CJK UNIFIED IDEOGRAPH - 0xA04A: 0x71E1, //CJK UNIFIED IDEOGRAPH - 0xA04B: 0x71E2, //CJK UNIFIED IDEOGRAPH - 0xA04C: 0x71E3, //CJK UNIFIED IDEOGRAPH - 0xA04D: 0x71E4, //CJK UNIFIED IDEOGRAPH - 0xA04E: 0x71E6, //CJK UNIFIED IDEOGRAPH - 0xA04F: 0x71E8, //CJK UNIFIED IDEOGRAPH - 0xA050: 0x71E9, //CJK UNIFIED IDEOGRAPH - 0xA051: 0x71EA, //CJK UNIFIED IDEOGRAPH - 0xA052: 0x71EB, //CJK UNIFIED IDEOGRAPH - 0xA053: 0x71EC, //CJK UNIFIED IDEOGRAPH - 0xA054: 0x71ED, //CJK UNIFIED IDEOGRAPH - 0xA055: 0x71EF, //CJK UNIFIED IDEOGRAPH - 0xA056: 0x71F0, //CJK UNIFIED IDEOGRAPH - 0xA057: 0x71F1, //CJK UNIFIED IDEOGRAPH - 0xA058: 0x71F2, //CJK UNIFIED IDEOGRAPH - 0xA059: 0x71F3, //CJK UNIFIED IDEOGRAPH - 0xA05A: 0x71F4, //CJK UNIFIED IDEOGRAPH - 0xA05B: 0x71F5, //CJK UNIFIED IDEOGRAPH - 0xA05C: 0x71F6, //CJK UNIFIED IDEOGRAPH - 0xA05D: 0x71F7, //CJK UNIFIED IDEOGRAPH - 0xA05E: 0x71F8, //CJK UNIFIED IDEOGRAPH - 0xA05F: 0x71FA, //CJK UNIFIED IDEOGRAPH - 0xA060: 0x71FB, //CJK UNIFIED IDEOGRAPH - 0xA061: 0x71FC, //CJK UNIFIED IDEOGRAPH - 0xA062: 0x71FD, //CJK UNIFIED IDEOGRAPH - 0xA063: 0x71FE, //CJK UNIFIED IDEOGRAPH - 0xA064: 0x71FF, //CJK UNIFIED IDEOGRAPH - 0xA065: 0x7200, //CJK UNIFIED IDEOGRAPH - 0xA066: 0x7201, //CJK UNIFIED IDEOGRAPH - 0xA067: 0x7202, //CJK UNIFIED IDEOGRAPH - 0xA068: 0x7203, //CJK UNIFIED IDEOGRAPH - 0xA069: 0x7204, //CJK UNIFIED IDEOGRAPH - 0xA06A: 0x7205, //CJK UNIFIED IDEOGRAPH - 0xA06B: 0x7207, //CJK UNIFIED IDEOGRAPH - 0xA06C: 0x7208, //CJK UNIFIED IDEOGRAPH - 0xA06D: 0x7209, //CJK UNIFIED IDEOGRAPH - 0xA06E: 0x720A, //CJK UNIFIED IDEOGRAPH - 0xA06F: 0x720B, //CJK UNIFIED IDEOGRAPH - 0xA070: 0x720C, //CJK UNIFIED IDEOGRAPH - 0xA071: 0x720D, //CJK UNIFIED IDEOGRAPH - 0xA072: 0x720E, //CJK UNIFIED IDEOGRAPH - 0xA073: 0x720F, //CJK UNIFIED IDEOGRAPH - 0xA074: 0x7210, //CJK UNIFIED IDEOGRAPH - 0xA075: 0x7211, //CJK UNIFIED IDEOGRAPH - 0xA076: 0x7212, //CJK UNIFIED IDEOGRAPH - 0xA077: 0x7213, //CJK UNIFIED IDEOGRAPH - 0xA078: 0x7214, //CJK UNIFIED IDEOGRAPH - 0xA079: 0x7215, //CJK UNIFIED IDEOGRAPH - 0xA07A: 0x7216, //CJK UNIFIED IDEOGRAPH - 0xA07B: 0x7217, //CJK UNIFIED IDEOGRAPH - 0xA07C: 0x7218, //CJK UNIFIED IDEOGRAPH - 0xA07D: 0x7219, //CJK UNIFIED IDEOGRAPH - 0xA07E: 0x721A, //CJK UNIFIED IDEOGRAPH - 0xA080: 0x721B, //CJK UNIFIED IDEOGRAPH - 0xA081: 0x721C, //CJK UNIFIED IDEOGRAPH - 0xA082: 0x721E, //CJK UNIFIED IDEOGRAPH - 0xA083: 0x721F, //CJK UNIFIED IDEOGRAPH - 0xA084: 0x7220, //CJK UNIFIED IDEOGRAPH - 0xA085: 0x7221, //CJK UNIFIED IDEOGRAPH - 0xA086: 0x7222, //CJK UNIFIED IDEOGRAPH - 0xA087: 0x7223, //CJK UNIFIED IDEOGRAPH - 0xA088: 0x7224, //CJK UNIFIED IDEOGRAPH - 0xA089: 0x7225, //CJK UNIFIED IDEOGRAPH - 0xA08A: 0x7226, //CJK UNIFIED IDEOGRAPH - 0xA08B: 0x7227, //CJK UNIFIED IDEOGRAPH - 0xA08C: 0x7229, //CJK UNIFIED IDEOGRAPH - 0xA08D: 0x722B, //CJK UNIFIED IDEOGRAPH - 0xA08E: 0x722D, //CJK UNIFIED IDEOGRAPH - 0xA08F: 0x722E, //CJK UNIFIED IDEOGRAPH - 0xA090: 0x722F, //CJK UNIFIED IDEOGRAPH - 0xA091: 0x7232, //CJK UNIFIED IDEOGRAPH - 0xA092: 0x7233, //CJK UNIFIED IDEOGRAPH - 0xA093: 0x7234, //CJK UNIFIED IDEOGRAPH - 0xA094: 0x723A, //CJK UNIFIED IDEOGRAPH - 0xA095: 0x723C, //CJK UNIFIED IDEOGRAPH - 0xA096: 0x723E, //CJK UNIFIED IDEOGRAPH - 0xA097: 0x7240, //CJK UNIFIED IDEOGRAPH - 0xA098: 0x7241, //CJK UNIFIED IDEOGRAPH - 0xA099: 0x7242, //CJK UNIFIED IDEOGRAPH - 0xA09A: 0x7243, //CJK UNIFIED IDEOGRAPH - 0xA09B: 0x7244, //CJK UNIFIED IDEOGRAPH - 0xA09C: 0x7245, //CJK UNIFIED IDEOGRAPH - 0xA09D: 0x7246, //CJK UNIFIED IDEOGRAPH - 0xA09E: 0x7249, //CJK UNIFIED IDEOGRAPH - 0xA09F: 0x724A, //CJK UNIFIED IDEOGRAPH - 0xA0A0: 0x724B, //CJK UNIFIED IDEOGRAPH - 0xA0A1: 0x724E, //CJK UNIFIED IDEOGRAPH - 0xA0A2: 0x724F, //CJK UNIFIED IDEOGRAPH - 0xA0A3: 0x7250, //CJK UNIFIED IDEOGRAPH - 0xA0A4: 0x7251, //CJK UNIFIED IDEOGRAPH - 0xA0A5: 0x7253, //CJK UNIFIED IDEOGRAPH - 0xA0A6: 0x7254, //CJK UNIFIED IDEOGRAPH - 0xA0A7: 0x7255, //CJK UNIFIED IDEOGRAPH - 0xA0A8: 0x7257, //CJK UNIFIED IDEOGRAPH - 0xA0A9: 0x7258, //CJK UNIFIED IDEOGRAPH - 0xA0AA: 0x725A, //CJK UNIFIED IDEOGRAPH - 0xA0AB: 0x725C, //CJK UNIFIED IDEOGRAPH - 0xA0AC: 0x725E, //CJK UNIFIED IDEOGRAPH - 0xA0AD: 0x7260, //CJK UNIFIED IDEOGRAPH - 0xA0AE: 0x7263, //CJK UNIFIED IDEOGRAPH - 0xA0AF: 0x7264, //CJK UNIFIED IDEOGRAPH - 0xA0B0: 0x7265, //CJK UNIFIED IDEOGRAPH - 0xA0B1: 0x7268, //CJK UNIFIED IDEOGRAPH - 0xA0B2: 0x726A, //CJK UNIFIED IDEOGRAPH - 0xA0B3: 0x726B, //CJK UNIFIED IDEOGRAPH - 0xA0B4: 0x726C, //CJK UNIFIED IDEOGRAPH - 0xA0B5: 0x726D, //CJK UNIFIED IDEOGRAPH - 0xA0B6: 0x7270, //CJK UNIFIED IDEOGRAPH - 0xA0B7: 0x7271, //CJK UNIFIED IDEOGRAPH - 0xA0B8: 0x7273, //CJK UNIFIED IDEOGRAPH - 0xA0B9: 0x7274, //CJK UNIFIED IDEOGRAPH - 0xA0BA: 0x7276, //CJK UNIFIED IDEOGRAPH - 0xA0BB: 0x7277, //CJK UNIFIED IDEOGRAPH - 0xA0BC: 0x7278, //CJK UNIFIED IDEOGRAPH - 0xA0BD: 0x727B, //CJK UNIFIED IDEOGRAPH - 0xA0BE: 0x727C, //CJK UNIFIED IDEOGRAPH - 0xA0BF: 0x727D, //CJK UNIFIED IDEOGRAPH - 0xA0C0: 0x7282, //CJK UNIFIED IDEOGRAPH - 0xA0C1: 0x7283, //CJK UNIFIED IDEOGRAPH - 0xA0C2: 0x7285, //CJK UNIFIED IDEOGRAPH - 0xA0C3: 0x7286, //CJK UNIFIED IDEOGRAPH - 0xA0C4: 0x7287, //CJK UNIFIED IDEOGRAPH - 0xA0C5: 0x7288, //CJK UNIFIED IDEOGRAPH - 0xA0C6: 0x7289, //CJK UNIFIED IDEOGRAPH - 0xA0C7: 0x728C, //CJK UNIFIED IDEOGRAPH - 0xA0C8: 0x728E, //CJK UNIFIED IDEOGRAPH - 0xA0C9: 0x7290, //CJK UNIFIED IDEOGRAPH - 0xA0CA: 0x7291, //CJK UNIFIED IDEOGRAPH - 0xA0CB: 0x7293, //CJK UNIFIED IDEOGRAPH - 0xA0CC: 0x7294, //CJK UNIFIED IDEOGRAPH - 0xA0CD: 0x7295, //CJK UNIFIED IDEOGRAPH - 0xA0CE: 0x7296, //CJK UNIFIED IDEOGRAPH - 0xA0CF: 0x7297, //CJK UNIFIED IDEOGRAPH - 0xA0D0: 0x7298, //CJK UNIFIED IDEOGRAPH - 0xA0D1: 0x7299, //CJK UNIFIED IDEOGRAPH - 0xA0D2: 0x729A, //CJK UNIFIED IDEOGRAPH - 0xA0D3: 0x729B, //CJK UNIFIED IDEOGRAPH - 0xA0D4: 0x729C, //CJK UNIFIED IDEOGRAPH - 0xA0D5: 0x729D, //CJK UNIFIED IDEOGRAPH - 0xA0D6: 0x729E, //CJK UNIFIED IDEOGRAPH - 0xA0D7: 0x72A0, //CJK UNIFIED IDEOGRAPH - 0xA0D8: 0x72A1, //CJK UNIFIED IDEOGRAPH - 0xA0D9: 0x72A2, //CJK UNIFIED IDEOGRAPH - 0xA0DA: 0x72A3, //CJK UNIFIED IDEOGRAPH - 0xA0DB: 0x72A4, //CJK UNIFIED IDEOGRAPH - 0xA0DC: 0x72A5, //CJK UNIFIED IDEOGRAPH - 0xA0DD: 0x72A6, //CJK UNIFIED IDEOGRAPH - 0xA0DE: 0x72A7, //CJK UNIFIED IDEOGRAPH - 0xA0DF: 0x72A8, //CJK UNIFIED IDEOGRAPH - 0xA0E0: 0x72A9, //CJK UNIFIED IDEOGRAPH - 0xA0E1: 0x72AA, //CJK UNIFIED IDEOGRAPH - 0xA0E2: 0x72AB, //CJK UNIFIED IDEOGRAPH - 0xA0E3: 0x72AE, //CJK UNIFIED IDEOGRAPH - 0xA0E4: 0x72B1, //CJK UNIFIED IDEOGRAPH - 0xA0E5: 0x72B2, //CJK UNIFIED IDEOGRAPH - 0xA0E6: 0x72B3, //CJK UNIFIED IDEOGRAPH - 0xA0E7: 0x72B5, //CJK UNIFIED IDEOGRAPH - 0xA0E8: 0x72BA, //CJK UNIFIED IDEOGRAPH - 0xA0E9: 0x72BB, //CJK UNIFIED IDEOGRAPH - 0xA0EA: 0x72BC, //CJK UNIFIED IDEOGRAPH - 0xA0EB: 0x72BD, //CJK UNIFIED IDEOGRAPH - 0xA0EC: 0x72BE, //CJK UNIFIED IDEOGRAPH - 0xA0ED: 0x72BF, //CJK UNIFIED IDEOGRAPH - 0xA0EE: 0x72C0, //CJK UNIFIED IDEOGRAPH - 0xA0EF: 0x72C5, //CJK UNIFIED IDEOGRAPH - 0xA0F0: 0x72C6, //CJK UNIFIED IDEOGRAPH - 0xA0F1: 0x72C7, //CJK UNIFIED IDEOGRAPH - 0xA0F2: 0x72C9, //CJK UNIFIED IDEOGRAPH - 0xA0F3: 0x72CA, //CJK UNIFIED IDEOGRAPH - 0xA0F4: 0x72CB, //CJK UNIFIED IDEOGRAPH - 0xA0F5: 0x72CC, //CJK UNIFIED IDEOGRAPH - 0xA0F6: 0x72CF, //CJK UNIFIED IDEOGRAPH - 0xA0F7: 0x72D1, //CJK UNIFIED IDEOGRAPH - 0xA0F8: 0x72D3, //CJK UNIFIED IDEOGRAPH - 0xA0F9: 0x72D4, //CJK UNIFIED IDEOGRAPH - 0xA0FA: 0x72D5, //CJK UNIFIED IDEOGRAPH - 0xA0FB: 0x72D6, //CJK UNIFIED IDEOGRAPH - 0xA0FC: 0x72D8, //CJK UNIFIED IDEOGRAPH - 0xA0FD: 0x72DA, //CJK UNIFIED IDEOGRAPH - 0xA0FE: 0x72DB, //CJK UNIFIED IDEOGRAPH - 0xA1A1: 0x3000, //IDEOGRAPHIC SPACE - 0xA1A2: 0x3001, //IDEOGRAPHIC COMMA - 0xA1A3: 0x3002, //IDEOGRAPHIC FULL STOP - 0xA1A4: 0x00B7, //MIDDLE DOT - 0xA1A5: 0x02C9, //MODIFIER LETTER MACRON - 0xA1A6: 0x02C7, //CARON - 0xA1A7: 0x00A8, //DIAERESIS - 0xA1A8: 0x3003, //DITTO MARK - 0xA1A9: 0x3005, //IDEOGRAPHIC ITERATION MARK - 0xA1AA: 0x2014, //EM DASH - 0xA1AB: 0xFF5E, //FULLWIDTH TILDE - 0xA1AC: 0x2016, //DOUBLE VERTICAL LINE - 0xA1AD: 0x2026, //HORIZONTAL ELLIPSIS - 0xA1AE: 0x2018, //LEFT SINGLE QUOTATION MARK - 0xA1AF: 0x2019, //RIGHT SINGLE QUOTATION MARK - 0xA1B0: 0x201C, //LEFT DOUBLE QUOTATION MARK - 0xA1B1: 0x201D, //RIGHT DOUBLE QUOTATION MARK - 0xA1B2: 0x3014, //LEFT TORTOISE SHELL BRACKET - 0xA1B3: 0x3015, //RIGHT TORTOISE SHELL BRACKET - 0xA1B4: 0x3008, //LEFT ANGLE BRACKET - 0xA1B5: 0x3009, //RIGHT ANGLE BRACKET - 0xA1B6: 0x300A, //LEFT DOUBLE ANGLE BRACKET - 0xA1B7: 0x300B, //RIGHT DOUBLE ANGLE BRACKET - 0xA1B8: 0x300C, //LEFT CORNER BRACKET - 0xA1B9: 0x300D, //RIGHT CORNER BRACKET - 0xA1BA: 0x300E, //LEFT WHITE CORNER BRACKET - 0xA1BB: 0x300F, //RIGHT WHITE CORNER BRACKET - 0xA1BC: 0x3016, //LEFT WHITE LENTICULAR BRACKET - 0xA1BD: 0x3017, //RIGHT WHITE LENTICULAR BRACKET - 0xA1BE: 0x3010, //LEFT BLACK LENTICULAR BRACKET - 0xA1BF: 0x3011, //RIGHT BLACK LENTICULAR BRACKET - 0xA1C0: 0x00B1, //PLUS-MINUS SIGN - 0xA1C1: 0x00D7, //MULTIPLICATION SIGN - 0xA1C2: 0x00F7, //DIVISION SIGN - 0xA1C3: 0x2236, //RATIO - 0xA1C4: 0x2227, //LOGICAL AND - 0xA1C5: 0x2228, //LOGICAL OR - 0xA1C6: 0x2211, //N-ARY SUMMATION - 0xA1C7: 0x220F, //N-ARY PRODUCT - 0xA1C8: 0x222A, //UNION - 0xA1C9: 0x2229, //INTERSECTION - 0xA1CA: 0x2208, //ELEMENT OF - 0xA1CB: 0x2237, //PROPORTION - 0xA1CC: 0x221A, //SQUARE ROOT - 0xA1CD: 0x22A5, //UP TACK - 0xA1CE: 0x2225, //PARALLEL TO - 0xA1CF: 0x2220, //ANGLE - 0xA1D0: 0x2312, //ARC - 0xA1D1: 0x2299, //CIRCLED DOT OPERATOR - 0xA1D2: 0x222B, //INTEGRAL - 0xA1D3: 0x222E, //CONTOUR INTEGRAL - 0xA1D4: 0x2261, //IDENTICAL TO - 0xA1D5: 0x224C, //ALL EQUAL TO - 0xA1D6: 0x2248, //ALMOST EQUAL TO - 0xA1D7: 0x223D, //REVERSED TILDE - 0xA1D8: 0x221D, //PROPORTIONAL TO - 0xA1D9: 0x2260, //NOT EQUAL TO - 0xA1DA: 0x226E, //NOT LESS-THAN - 0xA1DB: 0x226F, //NOT GREATER-THAN - 0xA1DC: 0x2264, //LESS-THAN OR EQUAL TO - 0xA1DD: 0x2265, //GREATER-THAN OR EQUAL TO - 0xA1DE: 0x221E, //INFINITY - 0xA1DF: 0x2235, //BECAUSE - 0xA1E0: 0x2234, //THEREFORE - 0xA1E1: 0x2642, //MALE SIGN - 0xA1E2: 0x2640, //FEMALE SIGN - 0xA1E3: 0x00B0, //DEGREE SIGN - 0xA1E4: 0x2032, //PRIME - 0xA1E5: 0x2033, //DOUBLE PRIME - 0xA1E6: 0x2103, //DEGREE CELSIUS - 0xA1E7: 0xFF04, //FULLWIDTH DOLLAR SIGN - 0xA1E8: 0x00A4, //CURRENCY SIGN - 0xA1E9: 0xFFE0, //FULLWIDTH CENT SIGN - 0xA1EA: 0xFFE1, //FULLWIDTH POUND SIGN - 0xA1EB: 0x2030, //PER MILLE SIGN - 0xA1EC: 0x00A7, //SECTION SIGN - 0xA1ED: 0x2116, //NUMERO SIGN - 0xA1EE: 0x2606, //WHITE STAR - 0xA1EF: 0x2605, //BLACK STAR - 0xA1F0: 0x25CB, //WHITE CIRCLE - 0xA1F1: 0x25CF, //BLACK CIRCLE - 0xA1F2: 0x25CE, //BULLSEYE - 0xA1F3: 0x25C7, //WHITE DIAMOND - 0xA1F4: 0x25C6, //BLACK DIAMOND - 0xA1F5: 0x25A1, //WHITE SQUARE - 0xA1F6: 0x25A0, //BLACK SQUARE - 0xA1F7: 0x25B3, //WHITE UP-POINTING TRIANGLE - 0xA1F8: 0x25B2, //BLACK UP-POINTING TRIANGLE - 0xA1F9: 0x203B, //REFERENCE MARK - 0xA1FA: 0x2192, //RIGHTWARDS ARROW - 0xA1FB: 0x2190, //LEFTWARDS ARROW - 0xA1FC: 0x2191, //UPWARDS ARROW - 0xA1FD: 0x2193, //DOWNWARDS ARROW - 0xA1FE: 0x3013, //GETA MARK - 0xA2A1: 0x2170, //SMALL ROMAN NUMERAL ONE - 0xA2A2: 0x2171, //SMALL ROMAN NUMERAL TWO - 0xA2A3: 0x2172, //SMALL ROMAN NUMERAL THREE - 0xA2A4: 0x2173, //SMALL ROMAN NUMERAL FOUR - 0xA2A5: 0x2174, //SMALL ROMAN NUMERAL FIVE - 0xA2A6: 0x2175, //SMALL ROMAN NUMERAL SIX - 0xA2A7: 0x2176, //SMALL ROMAN NUMERAL SEVEN - 0xA2A8: 0x2177, //SMALL ROMAN NUMERAL EIGHT - 0xA2A9: 0x2178, //SMALL ROMAN NUMERAL NINE - 0xA2AA: 0x2179, //SMALL ROMAN NUMERAL TEN - 0xA2B1: 0x2488, //DIGIT ONE FULL STOP - 0xA2B2: 0x2489, //DIGIT TWO FULL STOP - 0xA2B3: 0x248A, //DIGIT THREE FULL STOP - 0xA2B4: 0x248B, //DIGIT FOUR FULL STOP - 0xA2B5: 0x248C, //DIGIT FIVE FULL STOP - 0xA2B6: 0x248D, //DIGIT SIX FULL STOP - 0xA2B7: 0x248E, //DIGIT SEVEN FULL STOP - 0xA2B8: 0x248F, //DIGIT EIGHT FULL STOP - 0xA2B9: 0x2490, //DIGIT NINE FULL STOP - 0xA2BA: 0x2491, //NUMBER TEN FULL STOP - 0xA2BB: 0x2492, //NUMBER ELEVEN FULL STOP - 0xA2BC: 0x2493, //NUMBER TWELVE FULL STOP - 0xA2BD: 0x2494, //NUMBER THIRTEEN FULL STOP - 0xA2BE: 0x2495, //NUMBER FOURTEEN FULL STOP - 0xA2BF: 0x2496, //NUMBER FIFTEEN FULL STOP - 0xA2C0: 0x2497, //NUMBER SIXTEEN FULL STOP - 0xA2C1: 0x2498, //NUMBER SEVENTEEN FULL STOP - 0xA2C2: 0x2499, //NUMBER EIGHTEEN FULL STOP - 0xA2C3: 0x249A, //NUMBER NINETEEN FULL STOP - 0xA2C4: 0x249B, //NUMBER TWENTY FULL STOP - 0xA2C5: 0x2474, //PARENTHESIZED DIGIT ONE - 0xA2C6: 0x2475, //PARENTHESIZED DIGIT TWO - 0xA2C7: 0x2476, //PARENTHESIZED DIGIT THREE - 0xA2C8: 0x2477, //PARENTHESIZED DIGIT FOUR - 0xA2C9: 0x2478, //PARENTHESIZED DIGIT FIVE - 0xA2CA: 0x2479, //PARENTHESIZED DIGIT SIX - 0xA2CB: 0x247A, //PARENTHESIZED DIGIT SEVEN - 0xA2CC: 0x247B, //PARENTHESIZED DIGIT EIGHT - 0xA2CD: 0x247C, //PARENTHESIZED DIGIT NINE - 0xA2CE: 0x247D, //PARENTHESIZED NUMBER TEN - 0xA2CF: 0x247E, //PARENTHESIZED NUMBER ELEVEN - 0xA2D0: 0x247F, //PARENTHESIZED NUMBER TWELVE - 0xA2D1: 0x2480, //PARENTHESIZED NUMBER THIRTEEN - 0xA2D2: 0x2481, //PARENTHESIZED NUMBER FOURTEEN - 0xA2D3: 0x2482, //PARENTHESIZED NUMBER FIFTEEN - 0xA2D4: 0x2483, //PARENTHESIZED NUMBER SIXTEEN - 0xA2D5: 0x2484, //PARENTHESIZED NUMBER SEVENTEEN - 0xA2D6: 0x2485, //PARENTHESIZED NUMBER EIGHTEEN - 0xA2D7: 0x2486, //PARENTHESIZED NUMBER NINETEEN - 0xA2D8: 0x2487, //PARENTHESIZED NUMBER TWENTY - 0xA2D9: 0x2460, //CIRCLED DIGIT ONE - 0xA2DA: 0x2461, //CIRCLED DIGIT TWO - 0xA2DB: 0x2462, //CIRCLED DIGIT THREE - 0xA2DC: 0x2463, //CIRCLED DIGIT FOUR - 0xA2DD: 0x2464, //CIRCLED DIGIT FIVE - 0xA2DE: 0x2465, //CIRCLED DIGIT SIX - 0xA2DF: 0x2466, //CIRCLED DIGIT SEVEN - 0xA2E0: 0x2467, //CIRCLED DIGIT EIGHT - 0xA2E1: 0x2468, //CIRCLED DIGIT NINE - 0xA2E2: 0x2469, //CIRCLED NUMBER TEN - 0xA2E5: 0x3220, //PARENTHESIZED IDEOGRAPH ONE - 0xA2E6: 0x3221, //PARENTHESIZED IDEOGRAPH TWO - 0xA2E7: 0x3222, //PARENTHESIZED IDEOGRAPH THREE - 0xA2E8: 0x3223, //PARENTHESIZED IDEOGRAPH FOUR - 0xA2E9: 0x3224, //PARENTHESIZED IDEOGRAPH FIVE - 0xA2EA: 0x3225, //PARENTHESIZED IDEOGRAPH SIX - 0xA2EB: 0x3226, //PARENTHESIZED IDEOGRAPH SEVEN - 0xA2EC: 0x3227, //PARENTHESIZED IDEOGRAPH EIGHT - 0xA2ED: 0x3228, //PARENTHESIZED IDEOGRAPH NINE - 0xA2EE: 0x3229, //PARENTHESIZED IDEOGRAPH TEN - 0xA2F1: 0x2160, //ROMAN NUMERAL ONE - 0xA2F2: 0x2161, //ROMAN NUMERAL TWO - 0xA2F3: 0x2162, //ROMAN NUMERAL THREE - 0xA2F4: 0x2163, //ROMAN NUMERAL FOUR - 0xA2F5: 0x2164, //ROMAN NUMERAL FIVE - 0xA2F6: 0x2165, //ROMAN NUMERAL SIX - 0xA2F7: 0x2166, //ROMAN NUMERAL SEVEN - 0xA2F8: 0x2167, //ROMAN NUMERAL EIGHT - 0xA2F9: 0x2168, //ROMAN NUMERAL NINE - 0xA2FA: 0x2169, //ROMAN NUMERAL TEN - 0xA2FB: 0x216A, //ROMAN NUMERAL ELEVEN - 0xA2FC: 0x216B, //ROMAN NUMERAL TWELVE - 0xA3A1: 0xFF01, //FULLWIDTH EXCLAMATION MARK - 0xA3A2: 0xFF02, //FULLWIDTH QUOTATION MARK - 0xA3A3: 0xFF03, //FULLWIDTH NUMBER SIGN - 0xA3A4: 0xFFE5, //FULLWIDTH YEN SIGN - 0xA3A5: 0xFF05, //FULLWIDTH PERCENT SIGN - 0xA3A6: 0xFF06, //FULLWIDTH AMPERSAND - 0xA3A7: 0xFF07, //FULLWIDTH APOSTROPHE - 0xA3A8: 0xFF08, //FULLWIDTH LEFT PARENTHESIS - 0xA3A9: 0xFF09, //FULLWIDTH RIGHT PARENTHESIS - 0xA3AA: 0xFF0A, //FULLWIDTH ASTERISK - 0xA3AB: 0xFF0B, //FULLWIDTH PLUS SIGN - 0xA3AC: 0xFF0C, //FULLWIDTH COMMA - 0xA3AD: 0xFF0D, //FULLWIDTH HYPHEN-MINUS - 0xA3AE: 0xFF0E, //FULLWIDTH FULL STOP - 0xA3AF: 0xFF0F, //FULLWIDTH SOLIDUS - 0xA3B0: 0xFF10, //FULLWIDTH DIGIT ZERO - 0xA3B1: 0xFF11, //FULLWIDTH DIGIT ONE - 0xA3B2: 0xFF12, //FULLWIDTH DIGIT TWO - 0xA3B3: 0xFF13, //FULLWIDTH DIGIT THREE - 0xA3B4: 0xFF14, //FULLWIDTH DIGIT FOUR - 0xA3B5: 0xFF15, //FULLWIDTH DIGIT FIVE - 0xA3B6: 0xFF16, //FULLWIDTH DIGIT SIX - 0xA3B7: 0xFF17, //FULLWIDTH DIGIT SEVEN - 0xA3B8: 0xFF18, //FULLWIDTH DIGIT EIGHT - 0xA3B9: 0xFF19, //FULLWIDTH DIGIT NINE - 0xA3BA: 0xFF1A, //FULLWIDTH COLON - 0xA3BB: 0xFF1B, //FULLWIDTH SEMICOLON - 0xA3BC: 0xFF1C, //FULLWIDTH LESS-THAN SIGN - 0xA3BD: 0xFF1D, //FULLWIDTH EQUALS SIGN - 0xA3BE: 0xFF1E, //FULLWIDTH GREATER-THAN SIGN - 0xA3BF: 0xFF1F, //FULLWIDTH QUESTION MARK - 0xA3C0: 0xFF20, //FULLWIDTH COMMERCIAL AT - 0xA3C1: 0xFF21, //FULLWIDTH LATIN CAPITAL LETTER A - 0xA3C2: 0xFF22, //FULLWIDTH LATIN CAPITAL LETTER B - 0xA3C3: 0xFF23, //FULLWIDTH LATIN CAPITAL LETTER C - 0xA3C4: 0xFF24, //FULLWIDTH LATIN CAPITAL LETTER D - 0xA3C5: 0xFF25, //FULLWIDTH LATIN CAPITAL LETTER E - 0xA3C6: 0xFF26, //FULLWIDTH LATIN CAPITAL LETTER F - 0xA3C7: 0xFF27, //FULLWIDTH LATIN CAPITAL LETTER G - 0xA3C8: 0xFF28, //FULLWIDTH LATIN CAPITAL LETTER H - 0xA3C9: 0xFF29, //FULLWIDTH LATIN CAPITAL LETTER I - 0xA3CA: 0xFF2A, //FULLWIDTH LATIN CAPITAL LETTER J - 0xA3CB: 0xFF2B, //FULLWIDTH LATIN CAPITAL LETTER K - 0xA3CC: 0xFF2C, //FULLWIDTH LATIN CAPITAL LETTER L - 0xA3CD: 0xFF2D, //FULLWIDTH LATIN CAPITAL LETTER M - 0xA3CE: 0xFF2E, //FULLWIDTH LATIN CAPITAL LETTER N - 0xA3CF: 0xFF2F, //FULLWIDTH LATIN CAPITAL LETTER O - 0xA3D0: 0xFF30, //FULLWIDTH LATIN CAPITAL LETTER P - 0xA3D1: 0xFF31, //FULLWIDTH LATIN CAPITAL LETTER Q - 0xA3D2: 0xFF32, //FULLWIDTH LATIN CAPITAL LETTER R - 0xA3D3: 0xFF33, //FULLWIDTH LATIN CAPITAL LETTER S - 0xA3D4: 0xFF34, //FULLWIDTH LATIN CAPITAL LETTER T - 0xA3D5: 0xFF35, //FULLWIDTH LATIN CAPITAL LETTER U - 0xA3D6: 0xFF36, //FULLWIDTH LATIN CAPITAL LETTER V - 0xA3D7: 0xFF37, //FULLWIDTH LATIN CAPITAL LETTER W - 0xA3D8: 0xFF38, //FULLWIDTH LATIN CAPITAL LETTER X - 0xA3D9: 0xFF39, //FULLWIDTH LATIN CAPITAL LETTER Y - 0xA3DA: 0xFF3A, //FULLWIDTH LATIN CAPITAL LETTER Z - 0xA3DB: 0xFF3B, //FULLWIDTH LEFT SQUARE BRACKET - 0xA3DC: 0xFF3C, //FULLWIDTH REVERSE SOLIDUS - 0xA3DD: 0xFF3D, //FULLWIDTH RIGHT SQUARE BRACKET - 0xA3DE: 0xFF3E, //FULLWIDTH CIRCUMFLEX ACCENT - 0xA3DF: 0xFF3F, //FULLWIDTH LOW LINE - 0xA3E0: 0xFF40, //FULLWIDTH GRAVE ACCENT - 0xA3E1: 0xFF41, //FULLWIDTH LATIN SMALL LETTER A - 0xA3E2: 0xFF42, //FULLWIDTH LATIN SMALL LETTER B - 0xA3E3: 0xFF43, //FULLWIDTH LATIN SMALL LETTER C - 0xA3E4: 0xFF44, //FULLWIDTH LATIN SMALL LETTER D - 0xA3E5: 0xFF45, //FULLWIDTH LATIN SMALL LETTER E - 0xA3E6: 0xFF46, //FULLWIDTH LATIN SMALL LETTER F - 0xA3E7: 0xFF47, //FULLWIDTH LATIN SMALL LETTER G - 0xA3E8: 0xFF48, //FULLWIDTH LATIN SMALL LETTER H - 0xA3E9: 0xFF49, //FULLWIDTH LATIN SMALL LETTER I - 0xA3EA: 0xFF4A, //FULLWIDTH LATIN SMALL LETTER J - 0xA3EB: 0xFF4B, //FULLWIDTH LATIN SMALL LETTER K - 0xA3EC: 0xFF4C, //FULLWIDTH LATIN SMALL LETTER L - 0xA3ED: 0xFF4D, //FULLWIDTH LATIN SMALL LETTER M - 0xA3EE: 0xFF4E, //FULLWIDTH LATIN SMALL LETTER N - 0xA3EF: 0xFF4F, //FULLWIDTH LATIN SMALL LETTER O - 0xA3F0: 0xFF50, //FULLWIDTH LATIN SMALL LETTER P - 0xA3F1: 0xFF51, //FULLWIDTH LATIN SMALL LETTER Q - 0xA3F2: 0xFF52, //FULLWIDTH LATIN SMALL LETTER R - 0xA3F3: 0xFF53, //FULLWIDTH LATIN SMALL LETTER S - 0xA3F4: 0xFF54, //FULLWIDTH LATIN SMALL LETTER T - 0xA3F5: 0xFF55, //FULLWIDTH LATIN SMALL LETTER U - 0xA3F6: 0xFF56, //FULLWIDTH LATIN SMALL LETTER V - 0xA3F7: 0xFF57, //FULLWIDTH LATIN SMALL LETTER W - 0xA3F8: 0xFF58, //FULLWIDTH LATIN SMALL LETTER X - 0xA3F9: 0xFF59, //FULLWIDTH LATIN SMALL LETTER Y - 0xA3FA: 0xFF5A, //FULLWIDTH LATIN SMALL LETTER Z - 0xA3FB: 0xFF5B, //FULLWIDTH LEFT CURLY BRACKET - 0xA3FC: 0xFF5C, //FULLWIDTH VERTICAL LINE - 0xA3FD: 0xFF5D, //FULLWIDTH RIGHT CURLY BRACKET - 0xA3FE: 0xFFE3, //FULLWIDTH MACRON - 0xA4A1: 0x3041, //HIRAGANA LETTER SMALL A - 0xA4A2: 0x3042, //HIRAGANA LETTER A - 0xA4A3: 0x3043, //HIRAGANA LETTER SMALL I - 0xA4A4: 0x3044, //HIRAGANA LETTER I - 0xA4A5: 0x3045, //HIRAGANA LETTER SMALL U - 0xA4A6: 0x3046, //HIRAGANA LETTER U - 0xA4A7: 0x3047, //HIRAGANA LETTER SMALL E - 0xA4A8: 0x3048, //HIRAGANA LETTER E - 0xA4A9: 0x3049, //HIRAGANA LETTER SMALL O - 0xA4AA: 0x304A, //HIRAGANA LETTER O - 0xA4AB: 0x304B, //HIRAGANA LETTER KA - 0xA4AC: 0x304C, //HIRAGANA LETTER GA - 0xA4AD: 0x304D, //HIRAGANA LETTER KI - 0xA4AE: 0x304E, //HIRAGANA LETTER GI - 0xA4AF: 0x304F, //HIRAGANA LETTER KU - 0xA4B0: 0x3050, //HIRAGANA LETTER GU - 0xA4B1: 0x3051, //HIRAGANA LETTER KE - 0xA4B2: 0x3052, //HIRAGANA LETTER GE - 0xA4B3: 0x3053, //HIRAGANA LETTER KO - 0xA4B4: 0x3054, //HIRAGANA LETTER GO - 0xA4B5: 0x3055, //HIRAGANA LETTER SA - 0xA4B6: 0x3056, //HIRAGANA LETTER ZA - 0xA4B7: 0x3057, //HIRAGANA LETTER SI - 0xA4B8: 0x3058, //HIRAGANA LETTER ZI - 0xA4B9: 0x3059, //HIRAGANA LETTER SU - 0xA4BA: 0x305A, //HIRAGANA LETTER ZU - 0xA4BB: 0x305B, //HIRAGANA LETTER SE - 0xA4BC: 0x305C, //HIRAGANA LETTER ZE - 0xA4BD: 0x305D, //HIRAGANA LETTER SO - 0xA4BE: 0x305E, //HIRAGANA LETTER ZO - 0xA4BF: 0x305F, //HIRAGANA LETTER TA - 0xA4C0: 0x3060, //HIRAGANA LETTER DA - 0xA4C1: 0x3061, //HIRAGANA LETTER TI - 0xA4C2: 0x3062, //HIRAGANA LETTER DI - 0xA4C3: 0x3063, //HIRAGANA LETTER SMALL TU - 0xA4C4: 0x3064, //HIRAGANA LETTER TU - 0xA4C5: 0x3065, //HIRAGANA LETTER DU - 0xA4C6: 0x3066, //HIRAGANA LETTER TE - 0xA4C7: 0x3067, //HIRAGANA LETTER DE - 0xA4C8: 0x3068, //HIRAGANA LETTER TO - 0xA4C9: 0x3069, //HIRAGANA LETTER DO - 0xA4CA: 0x306A, //HIRAGANA LETTER NA - 0xA4CB: 0x306B, //HIRAGANA LETTER NI - 0xA4CC: 0x306C, //HIRAGANA LETTER NU - 0xA4CD: 0x306D, //HIRAGANA LETTER NE - 0xA4CE: 0x306E, //HIRAGANA LETTER NO - 0xA4CF: 0x306F, //HIRAGANA LETTER HA - 0xA4D0: 0x3070, //HIRAGANA LETTER BA - 0xA4D1: 0x3071, //HIRAGANA LETTER PA - 0xA4D2: 0x3072, //HIRAGANA LETTER HI - 0xA4D3: 0x3073, //HIRAGANA LETTER BI - 0xA4D4: 0x3074, //HIRAGANA LETTER PI - 0xA4D5: 0x3075, //HIRAGANA LETTER HU - 0xA4D6: 0x3076, //HIRAGANA LETTER BU - 0xA4D7: 0x3077, //HIRAGANA LETTER PU - 0xA4D8: 0x3078, //HIRAGANA LETTER HE - 0xA4D9: 0x3079, //HIRAGANA LETTER BE - 0xA4DA: 0x307A, //HIRAGANA LETTER PE - 0xA4DB: 0x307B, //HIRAGANA LETTER HO - 0xA4DC: 0x307C, //HIRAGANA LETTER BO - 0xA4DD: 0x307D, //HIRAGANA LETTER PO - 0xA4DE: 0x307E, //HIRAGANA LETTER MA - 0xA4DF: 0x307F, //HIRAGANA LETTER MI - 0xA4E0: 0x3080, //HIRAGANA LETTER MU - 0xA4E1: 0x3081, //HIRAGANA LETTER ME - 0xA4E2: 0x3082, //HIRAGANA LETTER MO - 0xA4E3: 0x3083, //HIRAGANA LETTER SMALL YA - 0xA4E4: 0x3084, //HIRAGANA LETTER YA - 0xA4E5: 0x3085, //HIRAGANA LETTER SMALL YU - 0xA4E6: 0x3086, //HIRAGANA LETTER YU - 0xA4E7: 0x3087, //HIRAGANA LETTER SMALL YO - 0xA4E8: 0x3088, //HIRAGANA LETTER YO - 0xA4E9: 0x3089, //HIRAGANA LETTER RA - 0xA4EA: 0x308A, //HIRAGANA LETTER RI - 0xA4EB: 0x308B, //HIRAGANA LETTER RU - 0xA4EC: 0x308C, //HIRAGANA LETTER RE - 0xA4ED: 0x308D, //HIRAGANA LETTER RO - 0xA4EE: 0x308E, //HIRAGANA LETTER SMALL WA - 0xA4EF: 0x308F, //HIRAGANA LETTER WA - 0xA4F0: 0x3090, //HIRAGANA LETTER WI - 0xA4F1: 0x3091, //HIRAGANA LETTER WE - 0xA4F2: 0x3092, //HIRAGANA LETTER WO - 0xA4F3: 0x3093, //HIRAGANA LETTER N - 0xA5A1: 0x30A1, //KATAKANA LETTER SMALL A - 0xA5A2: 0x30A2, //KATAKANA LETTER A - 0xA5A3: 0x30A3, //KATAKANA LETTER SMALL I - 0xA5A4: 0x30A4, //KATAKANA LETTER I - 0xA5A5: 0x30A5, //KATAKANA LETTER SMALL U - 0xA5A6: 0x30A6, //KATAKANA LETTER U - 0xA5A7: 0x30A7, //KATAKANA LETTER SMALL E - 0xA5A8: 0x30A8, //KATAKANA LETTER E - 0xA5A9: 0x30A9, //KATAKANA LETTER SMALL O - 0xA5AA: 0x30AA, //KATAKANA LETTER O - 0xA5AB: 0x30AB, //KATAKANA LETTER KA - 0xA5AC: 0x30AC, //KATAKANA LETTER GA - 0xA5AD: 0x30AD, //KATAKANA LETTER KI - 0xA5AE: 0x30AE, //KATAKANA LETTER GI - 0xA5AF: 0x30AF, //KATAKANA LETTER KU - 0xA5B0: 0x30B0, //KATAKANA LETTER GU - 0xA5B1: 0x30B1, //KATAKANA LETTER KE - 0xA5B2: 0x30B2, //KATAKANA LETTER GE - 0xA5B3: 0x30B3, //KATAKANA LETTER KO - 0xA5B4: 0x30B4, //KATAKANA LETTER GO - 0xA5B5: 0x30B5, //KATAKANA LETTER SA - 0xA5B6: 0x30B6, //KATAKANA LETTER ZA - 0xA5B7: 0x30B7, //KATAKANA LETTER SI - 0xA5B8: 0x30B8, //KATAKANA LETTER ZI - 0xA5B9: 0x30B9, //KATAKANA LETTER SU - 0xA5BA: 0x30BA, //KATAKANA LETTER ZU - 0xA5BB: 0x30BB, //KATAKANA LETTER SE - 0xA5BC: 0x30BC, //KATAKANA LETTER ZE - 0xA5BD: 0x30BD, //KATAKANA LETTER SO - 0xA5BE: 0x30BE, //KATAKANA LETTER ZO - 0xA5BF: 0x30BF, //KATAKANA LETTER TA - 0xA5C0: 0x30C0, //KATAKANA LETTER DA - 0xA5C1: 0x30C1, //KATAKANA LETTER TI - 0xA5C2: 0x30C2, //KATAKANA LETTER DI - 0xA5C3: 0x30C3, //KATAKANA LETTER SMALL TU - 0xA5C4: 0x30C4, //KATAKANA LETTER TU - 0xA5C5: 0x30C5, //KATAKANA LETTER DU - 0xA5C6: 0x30C6, //KATAKANA LETTER TE - 0xA5C7: 0x30C7, //KATAKANA LETTER DE - 0xA5C8: 0x30C8, //KATAKANA LETTER TO - 0xA5C9: 0x30C9, //KATAKANA LETTER DO - 0xA5CA: 0x30CA, //KATAKANA LETTER NA - 0xA5CB: 0x30CB, //KATAKANA LETTER NI - 0xA5CC: 0x30CC, //KATAKANA LETTER NU - 0xA5CD: 0x30CD, //KATAKANA LETTER NE - 0xA5CE: 0x30CE, //KATAKANA LETTER NO - 0xA5CF: 0x30CF, //KATAKANA LETTER HA - 0xA5D0: 0x30D0, //KATAKANA LETTER BA - 0xA5D1: 0x30D1, //KATAKANA LETTER PA - 0xA5D2: 0x30D2, //KATAKANA LETTER HI - 0xA5D3: 0x30D3, //KATAKANA LETTER BI - 0xA5D4: 0x30D4, //KATAKANA LETTER PI - 0xA5D5: 0x30D5, //KATAKANA LETTER HU - 0xA5D6: 0x30D6, //KATAKANA LETTER BU - 0xA5D7: 0x30D7, //KATAKANA LETTER PU - 0xA5D8: 0x30D8, //KATAKANA LETTER HE - 0xA5D9: 0x30D9, //KATAKANA LETTER BE - 0xA5DA: 0x30DA, //KATAKANA LETTER PE - 0xA5DB: 0x30DB, //KATAKANA LETTER HO - 0xA5DC: 0x30DC, //KATAKANA LETTER BO - 0xA5DD: 0x30DD, //KATAKANA LETTER PO - 0xA5DE: 0x30DE, //KATAKANA LETTER MA - 0xA5DF: 0x30DF, //KATAKANA LETTER MI - 0xA5E0: 0x30E0, //KATAKANA LETTER MU - 0xA5E1: 0x30E1, //KATAKANA LETTER ME - 0xA5E2: 0x30E2, //KATAKANA LETTER MO - 0xA5E3: 0x30E3, //KATAKANA LETTER SMALL YA - 0xA5E4: 0x30E4, //KATAKANA LETTER YA - 0xA5E5: 0x30E5, //KATAKANA LETTER SMALL YU - 0xA5E6: 0x30E6, //KATAKANA LETTER YU - 0xA5E7: 0x30E7, //KATAKANA LETTER SMALL YO - 0xA5E8: 0x30E8, //KATAKANA LETTER YO - 0xA5E9: 0x30E9, //KATAKANA LETTER RA - 0xA5EA: 0x30EA, //KATAKANA LETTER RI - 0xA5EB: 0x30EB, //KATAKANA LETTER RU - 0xA5EC: 0x30EC, //KATAKANA LETTER RE - 0xA5ED: 0x30ED, //KATAKANA LETTER RO - 0xA5EE: 0x30EE, //KATAKANA LETTER SMALL WA - 0xA5EF: 0x30EF, //KATAKANA LETTER WA - 0xA5F0: 0x30F0, //KATAKANA LETTER WI - 0xA5F1: 0x30F1, //KATAKANA LETTER WE - 0xA5F2: 0x30F2, //KATAKANA LETTER WO - 0xA5F3: 0x30F3, //KATAKANA LETTER N - 0xA5F4: 0x30F4, //KATAKANA LETTER VU - 0xA5F5: 0x30F5, //KATAKANA LETTER SMALL KA - 0xA5F6: 0x30F6, //KATAKANA LETTER SMALL KE - 0xA6A1: 0x0391, //GREEK CAPITAL LETTER ALPHA - 0xA6A2: 0x0392, //GREEK CAPITAL LETTER BETA - 0xA6A3: 0x0393, //GREEK CAPITAL LETTER GAMMA - 0xA6A4: 0x0394, //GREEK CAPITAL LETTER DELTA - 0xA6A5: 0x0395, //GREEK CAPITAL LETTER EPSILON - 0xA6A6: 0x0396, //GREEK CAPITAL LETTER ZETA - 0xA6A7: 0x0397, //GREEK CAPITAL LETTER ETA - 0xA6A8: 0x0398, //GREEK CAPITAL LETTER THETA - 0xA6A9: 0x0399, //GREEK CAPITAL LETTER IOTA - 0xA6AA: 0x039A, //GREEK CAPITAL LETTER KAPPA - 0xA6AB: 0x039B, //GREEK CAPITAL LETTER LAMDA - 0xA6AC: 0x039C, //GREEK CAPITAL LETTER MU - 0xA6AD: 0x039D, //GREEK CAPITAL LETTER NU - 0xA6AE: 0x039E, //GREEK CAPITAL LETTER XI - 0xA6AF: 0x039F, //GREEK CAPITAL LETTER OMICRON - 0xA6B0: 0x03A0, //GREEK CAPITAL LETTER PI - 0xA6B1: 0x03A1, //GREEK CAPITAL LETTER RHO - 0xA6B2: 0x03A3, //GREEK CAPITAL LETTER SIGMA - 0xA6B3: 0x03A4, //GREEK CAPITAL LETTER TAU - 0xA6B4: 0x03A5, //GREEK CAPITAL LETTER UPSILON - 0xA6B5: 0x03A6, //GREEK CAPITAL LETTER PHI - 0xA6B6: 0x03A7, //GREEK CAPITAL LETTER CHI - 0xA6B7: 0x03A8, //GREEK CAPITAL LETTER PSI - 0xA6B8: 0x03A9, //GREEK CAPITAL LETTER OMEGA - 0xA6C1: 0x03B1, //GREEK SMALL LETTER ALPHA - 0xA6C2: 0x03B2, //GREEK SMALL LETTER BETA - 0xA6C3: 0x03B3, //GREEK SMALL LETTER GAMMA - 0xA6C4: 0x03B4, //GREEK SMALL LETTER DELTA - 0xA6C5: 0x03B5, //GREEK SMALL LETTER EPSILON - 0xA6C6: 0x03B6, //GREEK SMALL LETTER ZETA - 0xA6C7: 0x03B7, //GREEK SMALL LETTER ETA - 0xA6C8: 0x03B8, //GREEK SMALL LETTER THETA - 0xA6C9: 0x03B9, //GREEK SMALL LETTER IOTA - 0xA6CA: 0x03BA, //GREEK SMALL LETTER KAPPA - 0xA6CB: 0x03BB, //GREEK SMALL LETTER LAMDA - 0xA6CC: 0x03BC, //GREEK SMALL LETTER MU - 0xA6CD: 0x03BD, //GREEK SMALL LETTER NU - 0xA6CE: 0x03BE, //GREEK SMALL LETTER XI - 0xA6CF: 0x03BF, //GREEK SMALL LETTER OMICRON - 0xA6D0: 0x03C0, //GREEK SMALL LETTER PI - 0xA6D1: 0x03C1, //GREEK SMALL LETTER RHO - 0xA6D2: 0x03C3, //GREEK SMALL LETTER SIGMA - 0xA6D3: 0x03C4, //GREEK SMALL LETTER TAU - 0xA6D4: 0x03C5, //GREEK SMALL LETTER UPSILON - 0xA6D5: 0x03C6, //GREEK SMALL LETTER PHI - 0xA6D6: 0x03C7, //GREEK SMALL LETTER CHI - 0xA6D7: 0x03C8, //GREEK SMALL LETTER PSI - 0xA6D8: 0x03C9, //GREEK SMALL LETTER OMEGA - 0xA6E0: 0xFE35, //PRESENTATION FORM FOR VERTICAL LEFT PARENTHESIS - 0xA6E1: 0xFE36, //PRESENTATION FORM FOR VERTICAL RIGHT PARENTHESIS - 0xA6E2: 0xFE39, //PRESENTATION FORM FOR VERTICAL LEFT TORTOISE SHELL BRACKET - 0xA6E3: 0xFE3A, //PRESENTATION FORM FOR VERTICAL RIGHT TORTOISE SHELL BRACKET - 0xA6E4: 0xFE3F, //PRESENTATION FORM FOR VERTICAL LEFT ANGLE BRACKET - 0xA6E5: 0xFE40, //PRESENTATION FORM FOR VERTICAL RIGHT ANGLE BRACKET - 0xA6E6: 0xFE3D, //PRESENTATION FORM FOR VERTICAL LEFT DOUBLE ANGLE BRACKET - 0xA6E7: 0xFE3E, //PRESENTATION FORM FOR VERTICAL RIGHT DOUBLE ANGLE BRACKET - 0xA6E8: 0xFE41, //PRESENTATION FORM FOR VERTICAL LEFT CORNER BRACKET - 0xA6E9: 0xFE42, //PRESENTATION FORM FOR VERTICAL RIGHT CORNER BRACKET - 0xA6EA: 0xFE43, //PRESENTATION FORM FOR VERTICAL LEFT WHITE CORNER BRACKET - 0xA6EB: 0xFE44, //PRESENTATION FORM FOR VERTICAL RIGHT WHITE CORNER BRACKET - 0xA6EE: 0xFE3B, //PRESENTATION FORM FOR VERTICAL LEFT BLACK LENTICULAR BRACKET - 0xA6EF: 0xFE3C, //PRESENTATION FORM FOR VERTICAL RIGHT BLACK LENTICULAR BRACKET - 0xA6F0: 0xFE37, //PRESENTATION FORM FOR VERTICAL LEFT CURLY BRACKET - 0xA6F1: 0xFE38, //PRESENTATION FORM FOR VERTICAL RIGHT CURLY BRACKET - 0xA6F2: 0xFE31, //PRESENTATION FORM FOR VERTICAL EM DASH - 0xA6F4: 0xFE33, //PRESENTATION FORM FOR VERTICAL LOW LINE - 0xA6F5: 0xFE34, //PRESENTATION FORM FOR VERTICAL WAVY LOW LINE - 0xA7A1: 0x0410, //CYRILLIC CAPITAL LETTER A - 0xA7A2: 0x0411, //CYRILLIC CAPITAL LETTER BE - 0xA7A3: 0x0412, //CYRILLIC CAPITAL LETTER VE - 0xA7A4: 0x0413, //CYRILLIC CAPITAL LETTER GHE - 0xA7A5: 0x0414, //CYRILLIC CAPITAL LETTER DE - 0xA7A6: 0x0415, //CYRILLIC CAPITAL LETTER IE - 0xA7A7: 0x0401, //CYRILLIC CAPITAL LETTER IO - 0xA7A8: 0x0416, //CYRILLIC CAPITAL LETTER ZHE - 0xA7A9: 0x0417, //CYRILLIC CAPITAL LETTER ZE - 0xA7AA: 0x0418, //CYRILLIC CAPITAL LETTER I - 0xA7AB: 0x0419, //CYRILLIC CAPITAL LETTER SHORT I - 0xA7AC: 0x041A, //CYRILLIC CAPITAL LETTER KA - 0xA7AD: 0x041B, //CYRILLIC CAPITAL LETTER EL - 0xA7AE: 0x041C, //CYRILLIC CAPITAL LETTER EM - 0xA7AF: 0x041D, //CYRILLIC CAPITAL LETTER EN - 0xA7B0: 0x041E, //CYRILLIC CAPITAL LETTER O - 0xA7B1: 0x041F, //CYRILLIC CAPITAL LETTER PE - 0xA7B2: 0x0420, //CYRILLIC CAPITAL LETTER ER - 0xA7B3: 0x0421, //CYRILLIC CAPITAL LETTER ES - 0xA7B4: 0x0422, //CYRILLIC CAPITAL LETTER TE - 0xA7B5: 0x0423, //CYRILLIC CAPITAL LETTER U - 0xA7B6: 0x0424, //CYRILLIC CAPITAL LETTER EF - 0xA7B7: 0x0425, //CYRILLIC CAPITAL LETTER HA - 0xA7B8: 0x0426, //CYRILLIC CAPITAL LETTER TSE - 0xA7B9: 0x0427, //CYRILLIC CAPITAL LETTER CHE - 0xA7BA: 0x0428, //CYRILLIC CAPITAL LETTER SHA - 0xA7BB: 0x0429, //CYRILLIC CAPITAL LETTER SHCHA - 0xA7BC: 0x042A, //CYRILLIC CAPITAL LETTER HARD SIGN - 0xA7BD: 0x042B, //CYRILLIC CAPITAL LETTER YERU - 0xA7BE: 0x042C, //CYRILLIC CAPITAL LETTER SOFT SIGN - 0xA7BF: 0x042D, //CYRILLIC CAPITAL LETTER E - 0xA7C0: 0x042E, //CYRILLIC CAPITAL LETTER YU - 0xA7C1: 0x042F, //CYRILLIC CAPITAL LETTER YA - 0xA7D1: 0x0430, //CYRILLIC SMALL LETTER A - 0xA7D2: 0x0431, //CYRILLIC SMALL LETTER BE - 0xA7D3: 0x0432, //CYRILLIC SMALL LETTER VE - 0xA7D4: 0x0433, //CYRILLIC SMALL LETTER GHE - 0xA7D5: 0x0434, //CYRILLIC SMALL LETTER DE - 0xA7D6: 0x0435, //CYRILLIC SMALL LETTER IE - 0xA7D7: 0x0451, //CYRILLIC SMALL LETTER IO - 0xA7D8: 0x0436, //CYRILLIC SMALL LETTER ZHE - 0xA7D9: 0x0437, //CYRILLIC SMALL LETTER ZE - 0xA7DA: 0x0438, //CYRILLIC SMALL LETTER I - 0xA7DB: 0x0439, //CYRILLIC SMALL LETTER SHORT I - 0xA7DC: 0x043A, //CYRILLIC SMALL LETTER KA - 0xA7DD: 0x043B, //CYRILLIC SMALL LETTER EL - 0xA7DE: 0x043C, //CYRILLIC SMALL LETTER EM - 0xA7DF: 0x043D, //CYRILLIC SMALL LETTER EN - 0xA7E0: 0x043E, //CYRILLIC SMALL LETTER O - 0xA7E1: 0x043F, //CYRILLIC SMALL LETTER PE - 0xA7E2: 0x0440, //CYRILLIC SMALL LETTER ER - 0xA7E3: 0x0441, //CYRILLIC SMALL LETTER ES - 0xA7E4: 0x0442, //CYRILLIC SMALL LETTER TE - 0xA7E5: 0x0443, //CYRILLIC SMALL LETTER U - 0xA7E6: 0x0444, //CYRILLIC SMALL LETTER EF - 0xA7E7: 0x0445, //CYRILLIC SMALL LETTER HA - 0xA7E8: 0x0446, //CYRILLIC SMALL LETTER TSE - 0xA7E9: 0x0447, //CYRILLIC SMALL LETTER CHE - 0xA7EA: 0x0448, //CYRILLIC SMALL LETTER SHA - 0xA7EB: 0x0449, //CYRILLIC SMALL LETTER SHCHA - 0xA7EC: 0x044A, //CYRILLIC SMALL LETTER HARD SIGN - 0xA7ED: 0x044B, //CYRILLIC SMALL LETTER YERU - 0xA7EE: 0x044C, //CYRILLIC SMALL LETTER SOFT SIGN - 0xA7EF: 0x044D, //CYRILLIC SMALL LETTER E - 0xA7F0: 0x044E, //CYRILLIC SMALL LETTER YU - 0xA7F1: 0x044F, //CYRILLIC SMALL LETTER YA - 0xA840: 0x02CA, //MODIFIER LETTER ACUTE ACCENT - 0xA841: 0x02CB, //MODIFIER LETTER GRAVE ACCENT - 0xA842: 0x02D9, //DOT ABOVE - 0xA843: 0x2013, //EN DASH - 0xA844: 0x2015, //HORIZONTAL BAR - 0xA845: 0x2025, //TWO DOT LEADER - 0xA846: 0x2035, //REVERSED PRIME - 0xA847: 0x2105, //CARE OF - 0xA848: 0x2109, //DEGREE FAHRENHEIT - 0xA849: 0x2196, //NORTH WEST ARROW - 0xA84A: 0x2197, //NORTH EAST ARROW - 0xA84B: 0x2198, //SOUTH EAST ARROW - 0xA84C: 0x2199, //SOUTH WEST ARROW - 0xA84D: 0x2215, //DIVISION SLASH - 0xA84E: 0x221F, //RIGHT ANGLE - 0xA84F: 0x2223, //DIVIDES - 0xA850: 0x2252, //APPROXIMATELY EQUAL TO OR THE IMAGE OF - 0xA851: 0x2266, //LESS-THAN OVER EQUAL TO - 0xA852: 0x2267, //GREATER-THAN OVER EQUAL TO - 0xA853: 0x22BF, //RIGHT TRIANGLE - 0xA854: 0x2550, //BOX DRAWINGS DOUBLE HORIZONTAL - 0xA855: 0x2551, //BOX DRAWINGS DOUBLE VERTICAL - 0xA856: 0x2552, //BOX DRAWINGS DOWN SINGLE AND RIGHT DOUBLE - 0xA857: 0x2553, //BOX DRAWINGS DOWN DOUBLE AND RIGHT SINGLE - 0xA858: 0x2554, //BOX DRAWINGS DOUBLE DOWN AND RIGHT - 0xA859: 0x2555, //BOX DRAWINGS DOWN SINGLE AND LEFT DOUBLE - 0xA85A: 0x2556, //BOX DRAWINGS DOWN DOUBLE AND LEFT SINGLE - 0xA85B: 0x2557, //BOX DRAWINGS DOUBLE DOWN AND LEFT - 0xA85C: 0x2558, //BOX DRAWINGS UP SINGLE AND RIGHT DOUBLE - 0xA85D: 0x2559, //BOX DRAWINGS UP DOUBLE AND RIGHT SINGLE - 0xA85E: 0x255A, //BOX DRAWINGS DOUBLE UP AND RIGHT - 0xA85F: 0x255B, //BOX DRAWINGS UP SINGLE AND LEFT DOUBLE - 0xA860: 0x255C, //BOX DRAWINGS UP DOUBLE AND LEFT SINGLE - 0xA861: 0x255D, //BOX DRAWINGS DOUBLE UP AND LEFT - 0xA862: 0x255E, //BOX DRAWINGS VERTICAL SINGLE AND RIGHT DOUBLE - 0xA863: 0x255F, //BOX DRAWINGS VERTICAL DOUBLE AND RIGHT SINGLE - 0xA864: 0x2560, //BOX DRAWINGS DOUBLE VERTICAL AND RIGHT - 0xA865: 0x2561, //BOX DRAWINGS VERTICAL SINGLE AND LEFT DOUBLE - 0xA866: 0x2562, //BOX DRAWINGS VERTICAL DOUBLE AND LEFT SINGLE - 0xA867: 0x2563, //BOX DRAWINGS DOUBLE VERTICAL AND LEFT - 0xA868: 0x2564, //BOX DRAWINGS DOWN SINGLE AND HORIZONTAL DOUBLE - 0xA869: 0x2565, //BOX DRAWINGS DOWN DOUBLE AND HORIZONTAL SINGLE - 0xA86A: 0x2566, //BOX DRAWINGS DOUBLE DOWN AND HORIZONTAL - 0xA86B: 0x2567, //BOX DRAWINGS UP SINGLE AND HORIZONTAL DOUBLE - 0xA86C: 0x2568, //BOX DRAWINGS UP DOUBLE AND HORIZONTAL SINGLE - 0xA86D: 0x2569, //BOX DRAWINGS DOUBLE UP AND HORIZONTAL - 0xA86E: 0x256A, //BOX DRAWINGS VERTICAL SINGLE AND HORIZONTAL DOUBLE - 0xA86F: 0x256B, //BOX DRAWINGS VERTICAL DOUBLE AND HORIZONTAL SINGLE - 0xA870: 0x256C, //BOX DRAWINGS DOUBLE VERTICAL AND HORIZONTAL - 0xA871: 0x256D, //BOX DRAWINGS LIGHT ARC DOWN AND RIGHT - 0xA872: 0x256E, //BOX DRAWINGS LIGHT ARC DOWN AND LEFT - 0xA873: 0x256F, //BOX DRAWINGS LIGHT ARC UP AND LEFT - 0xA874: 0x2570, //BOX DRAWINGS LIGHT ARC UP AND RIGHT - 0xA875: 0x2571, //BOX DRAWINGS LIGHT DIAGONAL UPPER RIGHT TO LOWER LEFT - 0xA876: 0x2572, //BOX DRAWINGS LIGHT DIAGONAL UPPER LEFT TO LOWER RIGHT - 0xA877: 0x2573, //BOX DRAWINGS LIGHT DIAGONAL CROSS - 0xA878: 0x2581, //LOWER ONE EIGHTH BLOCK - 0xA879: 0x2582, //LOWER ONE QUARTER BLOCK - 0xA87A: 0x2583, //LOWER THREE EIGHTHS BLOCK - 0xA87B: 0x2584, //LOWER HALF BLOCK - 0xA87C: 0x2585, //LOWER FIVE EIGHTHS BLOCK - 0xA87D: 0x2586, //LOWER THREE QUARTERS BLOCK - 0xA87E: 0x2587, //LOWER SEVEN EIGHTHS BLOCK - 0xA880: 0x2588, //FULL BLOCK - 0xA881: 0x2589, //LEFT SEVEN EIGHTHS BLOCK - 0xA882: 0x258A, //LEFT THREE QUARTERS BLOCK - 0xA883: 0x258B, //LEFT FIVE EIGHTHS BLOCK - 0xA884: 0x258C, //LEFT HALF BLOCK - 0xA885: 0x258D, //LEFT THREE EIGHTHS BLOCK - 0xA886: 0x258E, //LEFT ONE QUARTER BLOCK - 0xA887: 0x258F, //LEFT ONE EIGHTH BLOCK - 0xA888: 0x2593, //DARK SHADE - 0xA889: 0x2594, //UPPER ONE EIGHTH BLOCK - 0xA88A: 0x2595, //RIGHT ONE EIGHTH BLOCK - 0xA88B: 0x25BC, //BLACK DOWN-POINTING TRIANGLE - 0xA88C: 0x25BD, //WHITE DOWN-POINTING TRIANGLE - 0xA88D: 0x25E2, //BLACK LOWER RIGHT TRIANGLE - 0xA88E: 0x25E3, //BLACK LOWER LEFT TRIANGLE - 0xA88F: 0x25E4, //BLACK UPPER LEFT TRIANGLE - 0xA890: 0x25E5, //BLACK UPPER RIGHT TRIANGLE - 0xA891: 0x2609, //SUN - 0xA892: 0x2295, //CIRCLED PLUS - 0xA893: 0x3012, //POSTAL MARK - 0xA894: 0x301D, //REVERSED DOUBLE PRIME QUOTATION MARK - 0xA895: 0x301E, //DOUBLE PRIME QUOTATION MARK - 0xA8A1: 0x0101, //LATIN SMALL LETTER A WITH MACRON - 0xA8A2: 0x00E1, //LATIN SMALL LETTER A WITH ACUTE - 0xA8A3: 0x01CE, //LATIN SMALL LETTER A WITH CARON - 0xA8A4: 0x00E0, //LATIN SMALL LETTER A WITH GRAVE - 0xA8A5: 0x0113, //LATIN SMALL LETTER E WITH MACRON - 0xA8A6: 0x00E9, //LATIN SMALL LETTER E WITH ACUTE - 0xA8A7: 0x011B, //LATIN SMALL LETTER E WITH CARON - 0xA8A8: 0x00E8, //LATIN SMALL LETTER E WITH GRAVE - 0xA8A9: 0x012B, //LATIN SMALL LETTER I WITH MACRON - 0xA8AA: 0x00ED, //LATIN SMALL LETTER I WITH ACUTE - 0xA8AB: 0x01D0, //LATIN SMALL LETTER I WITH CARON - 0xA8AC: 0x00EC, //LATIN SMALL LETTER I WITH GRAVE - 0xA8AD: 0x014D, //LATIN SMALL LETTER O WITH MACRON - 0xA8AE: 0x00F3, //LATIN SMALL LETTER O WITH ACUTE - 0xA8AF: 0x01D2, //LATIN SMALL LETTER O WITH CARON - 0xA8B0: 0x00F2, //LATIN SMALL LETTER O WITH GRAVE - 0xA8B1: 0x016B, //LATIN SMALL LETTER U WITH MACRON - 0xA8B2: 0x00FA, //LATIN SMALL LETTER U WITH ACUTE - 0xA8B3: 0x01D4, //LATIN SMALL LETTER U WITH CARON - 0xA8B4: 0x00F9, //LATIN SMALL LETTER U WITH GRAVE - 0xA8B5: 0x01D6, //LATIN SMALL LETTER U WITH DIAERESIS AND MACRON - 0xA8B6: 0x01D8, //LATIN SMALL LETTER U WITH DIAERESIS AND ACUTE - 0xA8B7: 0x01DA, //LATIN SMALL LETTER U WITH DIAERESIS AND CARON - 0xA8B8: 0x01DC, //LATIN SMALL LETTER U WITH DIAERESIS AND GRAVE - 0xA8B9: 0x00FC, //LATIN SMALL LETTER U WITH DIAERESIS - 0xA8BA: 0x00EA, //LATIN SMALL LETTER E WITH CIRCUMFLEX - 0xA8BB: 0x0251, //LATIN SMALL LETTER ALPHA - 0xA8BD: 0x0144, //LATIN SMALL LETTER N WITH ACUTE - 0xA8BE: 0x0148, //LATIN SMALL LETTER N WITH CARON - 0xA8C0: 0x0261, //LATIN SMALL LETTER SCRIPT G - 0xA8C5: 0x3105, //BOPOMOFO LETTER B - 0xA8C6: 0x3106, //BOPOMOFO LETTER P - 0xA8C7: 0x3107, //BOPOMOFO LETTER M - 0xA8C8: 0x3108, //BOPOMOFO LETTER F - 0xA8C9: 0x3109, //BOPOMOFO LETTER D - 0xA8CA: 0x310A, //BOPOMOFO LETTER T - 0xA8CB: 0x310B, //BOPOMOFO LETTER N - 0xA8CC: 0x310C, //BOPOMOFO LETTER L - 0xA8CD: 0x310D, //BOPOMOFO LETTER G - 0xA8CE: 0x310E, //BOPOMOFO LETTER K - 0xA8CF: 0x310F, //BOPOMOFO LETTER H - 0xA8D0: 0x3110, //BOPOMOFO LETTER J - 0xA8D1: 0x3111, //BOPOMOFO LETTER Q - 0xA8D2: 0x3112, //BOPOMOFO LETTER X - 0xA8D3: 0x3113, //BOPOMOFO LETTER ZH - 0xA8D4: 0x3114, //BOPOMOFO LETTER CH - 0xA8D5: 0x3115, //BOPOMOFO LETTER SH - 0xA8D6: 0x3116, //BOPOMOFO LETTER R - 0xA8D7: 0x3117, //BOPOMOFO LETTER Z - 0xA8D8: 0x3118, //BOPOMOFO LETTER C - 0xA8D9: 0x3119, //BOPOMOFO LETTER S - 0xA8DA: 0x311A, //BOPOMOFO LETTER A - 0xA8DB: 0x311B, //BOPOMOFO LETTER O - 0xA8DC: 0x311C, //BOPOMOFO LETTER E - 0xA8DD: 0x311D, //BOPOMOFO LETTER EH - 0xA8DE: 0x311E, //BOPOMOFO LETTER AI - 0xA8DF: 0x311F, //BOPOMOFO LETTER EI - 0xA8E0: 0x3120, //BOPOMOFO LETTER AU - 0xA8E1: 0x3121, //BOPOMOFO LETTER OU - 0xA8E2: 0x3122, //BOPOMOFO LETTER AN - 0xA8E3: 0x3123, //BOPOMOFO LETTER EN - 0xA8E4: 0x3124, //BOPOMOFO LETTER ANG - 0xA8E5: 0x3125, //BOPOMOFO LETTER ENG - 0xA8E6: 0x3126, //BOPOMOFO LETTER ER - 0xA8E7: 0x3127, //BOPOMOFO LETTER I - 0xA8E8: 0x3128, //BOPOMOFO LETTER U - 0xA8E9: 0x3129, //BOPOMOFO LETTER IU - 0xA940: 0x3021, //HANGZHOU NUMERAL ONE - 0xA941: 0x3022, //HANGZHOU NUMERAL TWO - 0xA942: 0x3023, //HANGZHOU NUMERAL THREE - 0xA943: 0x3024, //HANGZHOU NUMERAL FOUR - 0xA944: 0x3025, //HANGZHOU NUMERAL FIVE - 0xA945: 0x3026, //HANGZHOU NUMERAL SIX - 0xA946: 0x3027, //HANGZHOU NUMERAL SEVEN - 0xA947: 0x3028, //HANGZHOU NUMERAL EIGHT - 0xA948: 0x3029, //HANGZHOU NUMERAL NINE - 0xA949: 0x32A3, //CIRCLED IDEOGRAPH CORRECT - 0xA94A: 0x338E, //SQUARE MG - 0xA94B: 0x338F, //SQUARE KG - 0xA94C: 0x339C, //SQUARE MM - 0xA94D: 0x339D, //SQUARE CM - 0xA94E: 0x339E, //SQUARE KM - 0xA94F: 0x33A1, //SQUARE M SQUARED - 0xA950: 0x33C4, //SQUARE CC - 0xA951: 0x33CE, //SQUARE KM CAPITAL - 0xA952: 0x33D1, //SQUARE LN - 0xA953: 0x33D2, //SQUARE LOG - 0xA954: 0x33D5, //SQUARE MIL - 0xA955: 0xFE30, //PRESENTATION FORM FOR VERTICAL TWO DOT LEADER - 0xA956: 0xFFE2, //FULLWIDTH NOT SIGN - 0xA957: 0xFFE4, //FULLWIDTH BROKEN BAR - 0xA959: 0x2121, //TELEPHONE SIGN - 0xA95A: 0x3231, //PARENTHESIZED IDEOGRAPH STOCK - 0xA95C: 0x2010, //HYPHEN - 0xA960: 0x30FC, //KATAKANA-HIRAGANA PROLONGED SOUND MARK - 0xA961: 0x309B, //KATAKANA-HIRAGANA VOICED SOUND MARK - 0xA962: 0x309C, //KATAKANA-HIRAGANA SEMI-VOICED SOUND MARK - 0xA963: 0x30FD, //KATAKANA ITERATION MARK - 0xA964: 0x30FE, //KATAKANA VOICED ITERATION MARK - 0xA965: 0x3006, //IDEOGRAPHIC CLOSING MARK - 0xA966: 0x309D, //HIRAGANA ITERATION MARK - 0xA967: 0x309E, //HIRAGANA VOICED ITERATION MARK - 0xA968: 0xFE49, //DASHED OVERLINE - 0xA969: 0xFE4A, //CENTRELINE OVERLINE - 0xA96A: 0xFE4B, //WAVY OVERLINE - 0xA96B: 0xFE4C, //DOUBLE WAVY OVERLINE - 0xA96C: 0xFE4D, //DASHED LOW LINE - 0xA96D: 0xFE4E, //CENTRELINE LOW LINE - 0xA96E: 0xFE4F, //WAVY LOW LINE - 0xA96F: 0xFE50, //SMALL COMMA - 0xA970: 0xFE51, //SMALL IDEOGRAPHIC COMMA - 0xA971: 0xFE52, //SMALL FULL STOP - 0xA972: 0xFE54, //SMALL SEMICOLON - 0xA973: 0xFE55, //SMALL COLON - 0xA974: 0xFE56, //SMALL QUESTION MARK - 0xA975: 0xFE57, //SMALL EXCLAMATION MARK - 0xA976: 0xFE59, //SMALL LEFT PARENTHESIS - 0xA977: 0xFE5A, //SMALL RIGHT PARENTHESIS - 0xA978: 0xFE5B, //SMALL LEFT CURLY BRACKET - 0xA979: 0xFE5C, //SMALL RIGHT CURLY BRACKET - 0xA97A: 0xFE5D, //SMALL LEFT TORTOISE SHELL BRACKET - 0xA97B: 0xFE5E, //SMALL RIGHT TORTOISE SHELL BRACKET - 0xA97C: 0xFE5F, //SMALL NUMBER SIGN - 0xA97D: 0xFE60, //SMALL AMPERSAND - 0xA97E: 0xFE61, //SMALL ASTERISK - 0xA980: 0xFE62, //SMALL PLUS SIGN - 0xA981: 0xFE63, //SMALL HYPHEN-MINUS - 0xA982: 0xFE64, //SMALL LESS-THAN SIGN - 0xA983: 0xFE65, //SMALL GREATER-THAN SIGN - 0xA984: 0xFE66, //SMALL EQUALS SIGN - 0xA985: 0xFE68, //SMALL REVERSE SOLIDUS - 0xA986: 0xFE69, //SMALL DOLLAR SIGN - 0xA987: 0xFE6A, //SMALL PERCENT SIGN - 0xA988: 0xFE6B, //SMALL COMMERCIAL AT - 0xA996: 0x3007, //IDEOGRAPHIC NUMBER ZERO - 0xA9A4: 0x2500, //BOX DRAWINGS LIGHT HORIZONTAL - 0xA9A5: 0x2501, //BOX DRAWINGS HEAVY HORIZONTAL - 0xA9A6: 0x2502, //BOX DRAWINGS LIGHT VERTICAL - 0xA9A7: 0x2503, //BOX DRAWINGS HEAVY VERTICAL - 0xA9A8: 0x2504, //BOX DRAWINGS LIGHT TRIPLE DASH HORIZONTAL - 0xA9A9: 0x2505, //BOX DRAWINGS HEAVY TRIPLE DASH HORIZONTAL - 0xA9AA: 0x2506, //BOX DRAWINGS LIGHT TRIPLE DASH VERTICAL - 0xA9AB: 0x2507, //BOX DRAWINGS HEAVY TRIPLE DASH VERTICAL - 0xA9AC: 0x2508, //BOX DRAWINGS LIGHT QUADRUPLE DASH HORIZONTAL - 0xA9AD: 0x2509, //BOX DRAWINGS HEAVY QUADRUPLE DASH HORIZONTAL - 0xA9AE: 0x250A, //BOX DRAWINGS LIGHT QUADRUPLE DASH VERTICAL - 0xA9AF: 0x250B, //BOX DRAWINGS HEAVY QUADRUPLE DASH VERTICAL - 0xA9B0: 0x250C, //BOX DRAWINGS LIGHT DOWN AND RIGHT - 0xA9B1: 0x250D, //BOX DRAWINGS DOWN LIGHT AND RIGHT HEAVY - 0xA9B2: 0x250E, //BOX DRAWINGS DOWN HEAVY AND RIGHT LIGHT - 0xA9B3: 0x250F, //BOX DRAWINGS HEAVY DOWN AND RIGHT - 0xA9B4: 0x2510, //BOX DRAWINGS LIGHT DOWN AND LEFT - 0xA9B5: 0x2511, //BOX DRAWINGS DOWN LIGHT AND LEFT HEAVY - 0xA9B6: 0x2512, //BOX DRAWINGS DOWN HEAVY AND LEFT LIGHT - 0xA9B7: 0x2513, //BOX DRAWINGS HEAVY DOWN AND LEFT - 0xA9B8: 0x2514, //BOX DRAWINGS LIGHT UP AND RIGHT - 0xA9B9: 0x2515, //BOX DRAWINGS UP LIGHT AND RIGHT HEAVY - 0xA9BA: 0x2516, //BOX DRAWINGS UP HEAVY AND RIGHT LIGHT - 0xA9BB: 0x2517, //BOX DRAWINGS HEAVY UP AND RIGHT - 0xA9BC: 0x2518, //BOX DRAWINGS LIGHT UP AND LEFT - 0xA9BD: 0x2519, //BOX DRAWINGS UP LIGHT AND LEFT HEAVY - 0xA9BE: 0x251A, //BOX DRAWINGS UP HEAVY AND LEFT LIGHT - 0xA9BF: 0x251B, //BOX DRAWINGS HEAVY UP AND LEFT - 0xA9C0: 0x251C, //BOX DRAWINGS LIGHT VERTICAL AND RIGHT - 0xA9C1: 0x251D, //BOX DRAWINGS VERTICAL LIGHT AND RIGHT HEAVY - 0xA9C2: 0x251E, //BOX DRAWINGS UP HEAVY AND RIGHT DOWN LIGHT - 0xA9C3: 0x251F, //BOX DRAWINGS DOWN HEAVY AND RIGHT UP LIGHT - 0xA9C4: 0x2520, //BOX DRAWINGS VERTICAL HEAVY AND RIGHT LIGHT - 0xA9C5: 0x2521, //BOX DRAWINGS DOWN LIGHT AND RIGHT UP HEAVY - 0xA9C6: 0x2522, //BOX DRAWINGS UP LIGHT AND RIGHT DOWN HEAVY - 0xA9C7: 0x2523, //BOX DRAWINGS HEAVY VERTICAL AND RIGHT - 0xA9C8: 0x2524, //BOX DRAWINGS LIGHT VERTICAL AND LEFT - 0xA9C9: 0x2525, //BOX DRAWINGS VERTICAL LIGHT AND LEFT HEAVY - 0xA9CA: 0x2526, //BOX DRAWINGS UP HEAVY AND LEFT DOWN LIGHT - 0xA9CB: 0x2527, //BOX DRAWINGS DOWN HEAVY AND LEFT UP LIGHT - 0xA9CC: 0x2528, //BOX DRAWINGS VERTICAL HEAVY AND LEFT LIGHT - 0xA9CD: 0x2529, //BOX DRAWINGS DOWN LIGHT AND LEFT UP HEAVY - 0xA9CE: 0x252A, //BOX DRAWINGS UP LIGHT AND LEFT DOWN HEAVY - 0xA9CF: 0x252B, //BOX DRAWINGS HEAVY VERTICAL AND LEFT - 0xA9D0: 0x252C, //BOX DRAWINGS LIGHT DOWN AND HORIZONTAL - 0xA9D1: 0x252D, //BOX DRAWINGS LEFT HEAVY AND RIGHT DOWN LIGHT - 0xA9D2: 0x252E, //BOX DRAWINGS RIGHT HEAVY AND LEFT DOWN LIGHT - 0xA9D3: 0x252F, //BOX DRAWINGS DOWN LIGHT AND HORIZONTAL HEAVY - 0xA9D4: 0x2530, //BOX DRAWINGS DOWN HEAVY AND HORIZONTAL LIGHT - 0xA9D5: 0x2531, //BOX DRAWINGS RIGHT LIGHT AND LEFT DOWN HEAVY - 0xA9D6: 0x2532, //BOX DRAWINGS LEFT LIGHT AND RIGHT DOWN HEAVY - 0xA9D7: 0x2533, //BOX DRAWINGS HEAVY DOWN AND HORIZONTAL - 0xA9D8: 0x2534, //BOX DRAWINGS LIGHT UP AND HORIZONTAL - 0xA9D9: 0x2535, //BOX DRAWINGS LEFT HEAVY AND RIGHT UP LIGHT - 0xA9DA: 0x2536, //BOX DRAWINGS RIGHT HEAVY AND LEFT UP LIGHT - 0xA9DB: 0x2537, //BOX DRAWINGS UP LIGHT AND HORIZONTAL HEAVY - 0xA9DC: 0x2538, //BOX DRAWINGS UP HEAVY AND HORIZONTAL LIGHT - 0xA9DD: 0x2539, //BOX DRAWINGS RIGHT LIGHT AND LEFT UP HEAVY - 0xA9DE: 0x253A, //BOX DRAWINGS LEFT LIGHT AND RIGHT UP HEAVY - 0xA9DF: 0x253B, //BOX DRAWINGS HEAVY UP AND HORIZONTAL - 0xA9E0: 0x253C, //BOX DRAWINGS LIGHT VERTICAL AND HORIZONTAL - 0xA9E1: 0x253D, //BOX DRAWINGS LEFT HEAVY AND RIGHT VERTICAL LIGHT - 0xA9E2: 0x253E, //BOX DRAWINGS RIGHT HEAVY AND LEFT VERTICAL LIGHT - 0xA9E3: 0x253F, //BOX DRAWINGS VERTICAL LIGHT AND HORIZONTAL HEAVY - 0xA9E4: 0x2540, //BOX DRAWINGS UP HEAVY AND DOWN HORIZONTAL LIGHT - 0xA9E5: 0x2541, //BOX DRAWINGS DOWN HEAVY AND UP HORIZONTAL LIGHT - 0xA9E6: 0x2542, //BOX DRAWINGS VERTICAL HEAVY AND HORIZONTAL LIGHT - 0xA9E7: 0x2543, //BOX DRAWINGS LEFT UP HEAVY AND RIGHT DOWN LIGHT - 0xA9E8: 0x2544, //BOX DRAWINGS RIGHT UP HEAVY AND LEFT DOWN LIGHT - 0xA9E9: 0x2545, //BOX DRAWINGS LEFT DOWN HEAVY AND RIGHT UP LIGHT - 0xA9EA: 0x2546, //BOX DRAWINGS RIGHT DOWN HEAVY AND LEFT UP LIGHT - 0xA9EB: 0x2547, //BOX DRAWINGS DOWN LIGHT AND UP HORIZONTAL HEAVY - 0xA9EC: 0x2548, //BOX DRAWINGS UP LIGHT AND DOWN HORIZONTAL HEAVY - 0xA9ED: 0x2549, //BOX DRAWINGS RIGHT LIGHT AND LEFT VERTICAL HEAVY - 0xA9EE: 0x254A, //BOX DRAWINGS LEFT LIGHT AND RIGHT VERTICAL HEAVY - 0xA9EF: 0x254B, //BOX DRAWINGS HEAVY VERTICAL AND HORIZONTAL - 0xAA40: 0x72DC, //CJK UNIFIED IDEOGRAPH - 0xAA41: 0x72DD, //CJK UNIFIED IDEOGRAPH - 0xAA42: 0x72DF, //CJK UNIFIED IDEOGRAPH - 0xAA43: 0x72E2, //CJK UNIFIED IDEOGRAPH - 0xAA44: 0x72E3, //CJK UNIFIED IDEOGRAPH - 0xAA45: 0x72E4, //CJK UNIFIED IDEOGRAPH - 0xAA46: 0x72E5, //CJK UNIFIED IDEOGRAPH - 0xAA47: 0x72E6, //CJK UNIFIED IDEOGRAPH - 0xAA48: 0x72E7, //CJK UNIFIED IDEOGRAPH - 0xAA49: 0x72EA, //CJK UNIFIED IDEOGRAPH - 0xAA4A: 0x72EB, //CJK UNIFIED IDEOGRAPH - 0xAA4B: 0x72F5, //CJK UNIFIED IDEOGRAPH - 0xAA4C: 0x72F6, //CJK UNIFIED IDEOGRAPH - 0xAA4D: 0x72F9, //CJK UNIFIED IDEOGRAPH - 0xAA4E: 0x72FD, //CJK UNIFIED IDEOGRAPH - 0xAA4F: 0x72FE, //CJK UNIFIED IDEOGRAPH - 0xAA50: 0x72FF, //CJK UNIFIED IDEOGRAPH - 0xAA51: 0x7300, //CJK UNIFIED IDEOGRAPH - 0xAA52: 0x7302, //CJK UNIFIED IDEOGRAPH - 0xAA53: 0x7304, //CJK UNIFIED IDEOGRAPH - 0xAA54: 0x7305, //CJK UNIFIED IDEOGRAPH - 0xAA55: 0x7306, //CJK UNIFIED IDEOGRAPH - 0xAA56: 0x7307, //CJK UNIFIED IDEOGRAPH - 0xAA57: 0x7308, //CJK UNIFIED IDEOGRAPH - 0xAA58: 0x7309, //CJK UNIFIED IDEOGRAPH - 0xAA59: 0x730B, //CJK UNIFIED IDEOGRAPH - 0xAA5A: 0x730C, //CJK UNIFIED IDEOGRAPH - 0xAA5B: 0x730D, //CJK UNIFIED IDEOGRAPH - 0xAA5C: 0x730F, //CJK UNIFIED IDEOGRAPH - 0xAA5D: 0x7310, //CJK UNIFIED IDEOGRAPH - 0xAA5E: 0x7311, //CJK UNIFIED IDEOGRAPH - 0xAA5F: 0x7312, //CJK UNIFIED IDEOGRAPH - 0xAA60: 0x7314, //CJK UNIFIED IDEOGRAPH - 0xAA61: 0x7318, //CJK UNIFIED IDEOGRAPH - 0xAA62: 0x7319, //CJK UNIFIED IDEOGRAPH - 0xAA63: 0x731A, //CJK UNIFIED IDEOGRAPH - 0xAA64: 0x731F, //CJK UNIFIED IDEOGRAPH - 0xAA65: 0x7320, //CJK UNIFIED IDEOGRAPH - 0xAA66: 0x7323, //CJK UNIFIED IDEOGRAPH - 0xAA67: 0x7324, //CJK UNIFIED IDEOGRAPH - 0xAA68: 0x7326, //CJK UNIFIED IDEOGRAPH - 0xAA69: 0x7327, //CJK UNIFIED IDEOGRAPH - 0xAA6A: 0x7328, //CJK UNIFIED IDEOGRAPH - 0xAA6B: 0x732D, //CJK UNIFIED IDEOGRAPH - 0xAA6C: 0x732F, //CJK UNIFIED IDEOGRAPH - 0xAA6D: 0x7330, //CJK UNIFIED IDEOGRAPH - 0xAA6E: 0x7332, //CJK UNIFIED IDEOGRAPH - 0xAA6F: 0x7333, //CJK UNIFIED IDEOGRAPH - 0xAA70: 0x7335, //CJK UNIFIED IDEOGRAPH - 0xAA71: 0x7336, //CJK UNIFIED IDEOGRAPH - 0xAA72: 0x733A, //CJK UNIFIED IDEOGRAPH - 0xAA73: 0x733B, //CJK UNIFIED IDEOGRAPH - 0xAA74: 0x733C, //CJK UNIFIED IDEOGRAPH - 0xAA75: 0x733D, //CJK UNIFIED IDEOGRAPH - 0xAA76: 0x7340, //CJK UNIFIED IDEOGRAPH - 0xAA77: 0x7341, //CJK UNIFIED IDEOGRAPH - 0xAA78: 0x7342, //CJK UNIFIED IDEOGRAPH - 0xAA79: 0x7343, //CJK UNIFIED IDEOGRAPH - 0xAA7A: 0x7344, //CJK UNIFIED IDEOGRAPH - 0xAA7B: 0x7345, //CJK UNIFIED IDEOGRAPH - 0xAA7C: 0x7346, //CJK UNIFIED IDEOGRAPH - 0xAA7D: 0x7347, //CJK UNIFIED IDEOGRAPH - 0xAA7E: 0x7348, //CJK UNIFIED IDEOGRAPH - 0xAA80: 0x7349, //CJK UNIFIED IDEOGRAPH - 0xAA81: 0x734A, //CJK UNIFIED IDEOGRAPH - 0xAA82: 0x734B, //CJK UNIFIED IDEOGRAPH - 0xAA83: 0x734C, //CJK UNIFIED IDEOGRAPH - 0xAA84: 0x734E, //CJK UNIFIED IDEOGRAPH - 0xAA85: 0x734F, //CJK UNIFIED IDEOGRAPH - 0xAA86: 0x7351, //CJK UNIFIED IDEOGRAPH - 0xAA87: 0x7353, //CJK UNIFIED IDEOGRAPH - 0xAA88: 0x7354, //CJK UNIFIED IDEOGRAPH - 0xAA89: 0x7355, //CJK UNIFIED IDEOGRAPH - 0xAA8A: 0x7356, //CJK UNIFIED IDEOGRAPH - 0xAA8B: 0x7358, //CJK UNIFIED IDEOGRAPH - 0xAA8C: 0x7359, //CJK UNIFIED IDEOGRAPH - 0xAA8D: 0x735A, //CJK UNIFIED IDEOGRAPH - 0xAA8E: 0x735B, //CJK UNIFIED IDEOGRAPH - 0xAA8F: 0x735C, //CJK UNIFIED IDEOGRAPH - 0xAA90: 0x735D, //CJK UNIFIED IDEOGRAPH - 0xAA91: 0x735E, //CJK UNIFIED IDEOGRAPH - 0xAA92: 0x735F, //CJK UNIFIED IDEOGRAPH - 0xAA93: 0x7361, //CJK UNIFIED IDEOGRAPH - 0xAA94: 0x7362, //CJK UNIFIED IDEOGRAPH - 0xAA95: 0x7363, //CJK UNIFIED IDEOGRAPH - 0xAA96: 0x7364, //CJK UNIFIED IDEOGRAPH - 0xAA97: 0x7365, //CJK UNIFIED IDEOGRAPH - 0xAA98: 0x7366, //CJK UNIFIED IDEOGRAPH - 0xAA99: 0x7367, //CJK UNIFIED IDEOGRAPH - 0xAA9A: 0x7368, //CJK UNIFIED IDEOGRAPH - 0xAA9B: 0x7369, //CJK UNIFIED IDEOGRAPH - 0xAA9C: 0x736A, //CJK UNIFIED IDEOGRAPH - 0xAA9D: 0x736B, //CJK UNIFIED IDEOGRAPH - 0xAA9E: 0x736E, //CJK UNIFIED IDEOGRAPH - 0xAA9F: 0x7370, //CJK UNIFIED IDEOGRAPH - 0xAAA0: 0x7371, //CJK UNIFIED IDEOGRAPH - 0xAB40: 0x7372, //CJK UNIFIED IDEOGRAPH - 0xAB41: 0x7373, //CJK UNIFIED IDEOGRAPH - 0xAB42: 0x7374, //CJK UNIFIED IDEOGRAPH - 0xAB43: 0x7375, //CJK UNIFIED IDEOGRAPH - 0xAB44: 0x7376, //CJK UNIFIED IDEOGRAPH - 0xAB45: 0x7377, //CJK UNIFIED IDEOGRAPH - 0xAB46: 0x7378, //CJK UNIFIED IDEOGRAPH - 0xAB47: 0x7379, //CJK UNIFIED IDEOGRAPH - 0xAB48: 0x737A, //CJK UNIFIED IDEOGRAPH - 0xAB49: 0x737B, //CJK UNIFIED IDEOGRAPH - 0xAB4A: 0x737C, //CJK UNIFIED IDEOGRAPH - 0xAB4B: 0x737D, //CJK UNIFIED IDEOGRAPH - 0xAB4C: 0x737F, //CJK UNIFIED IDEOGRAPH - 0xAB4D: 0x7380, //CJK UNIFIED IDEOGRAPH - 0xAB4E: 0x7381, //CJK UNIFIED IDEOGRAPH - 0xAB4F: 0x7382, //CJK UNIFIED IDEOGRAPH - 0xAB50: 0x7383, //CJK UNIFIED IDEOGRAPH - 0xAB51: 0x7385, //CJK UNIFIED IDEOGRAPH - 0xAB52: 0x7386, //CJK UNIFIED IDEOGRAPH - 0xAB53: 0x7388, //CJK UNIFIED IDEOGRAPH - 0xAB54: 0x738A, //CJK UNIFIED IDEOGRAPH - 0xAB55: 0x738C, //CJK UNIFIED IDEOGRAPH - 0xAB56: 0x738D, //CJK UNIFIED IDEOGRAPH - 0xAB57: 0x738F, //CJK UNIFIED IDEOGRAPH - 0xAB58: 0x7390, //CJK UNIFIED IDEOGRAPH - 0xAB59: 0x7392, //CJK UNIFIED IDEOGRAPH - 0xAB5A: 0x7393, //CJK UNIFIED IDEOGRAPH - 0xAB5B: 0x7394, //CJK UNIFIED IDEOGRAPH - 0xAB5C: 0x7395, //CJK UNIFIED IDEOGRAPH - 0xAB5D: 0x7397, //CJK UNIFIED IDEOGRAPH - 0xAB5E: 0x7398, //CJK UNIFIED IDEOGRAPH - 0xAB5F: 0x7399, //CJK UNIFIED IDEOGRAPH - 0xAB60: 0x739A, //CJK UNIFIED IDEOGRAPH - 0xAB61: 0x739C, //CJK UNIFIED IDEOGRAPH - 0xAB62: 0x739D, //CJK UNIFIED IDEOGRAPH - 0xAB63: 0x739E, //CJK UNIFIED IDEOGRAPH - 0xAB64: 0x73A0, //CJK UNIFIED IDEOGRAPH - 0xAB65: 0x73A1, //CJK UNIFIED IDEOGRAPH - 0xAB66: 0x73A3, //CJK UNIFIED IDEOGRAPH - 0xAB67: 0x73A4, //CJK UNIFIED IDEOGRAPH - 0xAB68: 0x73A5, //CJK UNIFIED IDEOGRAPH - 0xAB69: 0x73A6, //CJK UNIFIED IDEOGRAPH - 0xAB6A: 0x73A7, //CJK UNIFIED IDEOGRAPH - 0xAB6B: 0x73A8, //CJK UNIFIED IDEOGRAPH - 0xAB6C: 0x73AA, //CJK UNIFIED IDEOGRAPH - 0xAB6D: 0x73AC, //CJK UNIFIED IDEOGRAPH - 0xAB6E: 0x73AD, //CJK UNIFIED IDEOGRAPH - 0xAB6F: 0x73B1, //CJK UNIFIED IDEOGRAPH - 0xAB70: 0x73B4, //CJK UNIFIED IDEOGRAPH - 0xAB71: 0x73B5, //CJK UNIFIED IDEOGRAPH - 0xAB72: 0x73B6, //CJK UNIFIED IDEOGRAPH - 0xAB73: 0x73B8, //CJK UNIFIED IDEOGRAPH - 0xAB74: 0x73B9, //CJK UNIFIED IDEOGRAPH - 0xAB75: 0x73BC, //CJK UNIFIED IDEOGRAPH - 0xAB76: 0x73BD, //CJK UNIFIED IDEOGRAPH - 0xAB77: 0x73BE, //CJK UNIFIED IDEOGRAPH - 0xAB78: 0x73BF, //CJK UNIFIED IDEOGRAPH - 0xAB79: 0x73C1, //CJK UNIFIED IDEOGRAPH - 0xAB7A: 0x73C3, //CJK UNIFIED IDEOGRAPH - 0xAB7B: 0x73C4, //CJK UNIFIED IDEOGRAPH - 0xAB7C: 0x73C5, //CJK UNIFIED IDEOGRAPH - 0xAB7D: 0x73C6, //CJK UNIFIED IDEOGRAPH - 0xAB7E: 0x73C7, //CJK UNIFIED IDEOGRAPH - 0xAB80: 0x73CB, //CJK UNIFIED IDEOGRAPH - 0xAB81: 0x73CC, //CJK UNIFIED IDEOGRAPH - 0xAB82: 0x73CE, //CJK UNIFIED IDEOGRAPH - 0xAB83: 0x73D2, //CJK UNIFIED IDEOGRAPH - 0xAB84: 0x73D3, //CJK UNIFIED IDEOGRAPH - 0xAB85: 0x73D4, //CJK UNIFIED IDEOGRAPH - 0xAB86: 0x73D5, //CJK UNIFIED IDEOGRAPH - 0xAB87: 0x73D6, //CJK UNIFIED IDEOGRAPH - 0xAB88: 0x73D7, //CJK UNIFIED IDEOGRAPH - 0xAB89: 0x73D8, //CJK UNIFIED IDEOGRAPH - 0xAB8A: 0x73DA, //CJK UNIFIED IDEOGRAPH - 0xAB8B: 0x73DB, //CJK UNIFIED IDEOGRAPH - 0xAB8C: 0x73DC, //CJK UNIFIED IDEOGRAPH - 0xAB8D: 0x73DD, //CJK UNIFIED IDEOGRAPH - 0xAB8E: 0x73DF, //CJK UNIFIED IDEOGRAPH - 0xAB8F: 0x73E1, //CJK UNIFIED IDEOGRAPH - 0xAB90: 0x73E2, //CJK UNIFIED IDEOGRAPH - 0xAB91: 0x73E3, //CJK UNIFIED IDEOGRAPH - 0xAB92: 0x73E4, //CJK UNIFIED IDEOGRAPH - 0xAB93: 0x73E6, //CJK UNIFIED IDEOGRAPH - 0xAB94: 0x73E8, //CJK UNIFIED IDEOGRAPH - 0xAB95: 0x73EA, //CJK UNIFIED IDEOGRAPH - 0xAB96: 0x73EB, //CJK UNIFIED IDEOGRAPH - 0xAB97: 0x73EC, //CJK UNIFIED IDEOGRAPH - 0xAB98: 0x73EE, //CJK UNIFIED IDEOGRAPH - 0xAB99: 0x73EF, //CJK UNIFIED IDEOGRAPH - 0xAB9A: 0x73F0, //CJK UNIFIED IDEOGRAPH - 0xAB9B: 0x73F1, //CJK UNIFIED IDEOGRAPH - 0xAB9C: 0x73F3, //CJK UNIFIED IDEOGRAPH - 0xAB9D: 0x73F4, //CJK UNIFIED IDEOGRAPH - 0xAB9E: 0x73F5, //CJK UNIFIED IDEOGRAPH - 0xAB9F: 0x73F6, //CJK UNIFIED IDEOGRAPH - 0xABA0: 0x73F7, //CJK UNIFIED IDEOGRAPH - 0xAC40: 0x73F8, //CJK UNIFIED IDEOGRAPH - 0xAC41: 0x73F9, //CJK UNIFIED IDEOGRAPH - 0xAC42: 0x73FA, //CJK UNIFIED IDEOGRAPH - 0xAC43: 0x73FB, //CJK UNIFIED IDEOGRAPH - 0xAC44: 0x73FC, //CJK UNIFIED IDEOGRAPH - 0xAC45: 0x73FD, //CJK UNIFIED IDEOGRAPH - 0xAC46: 0x73FE, //CJK UNIFIED IDEOGRAPH - 0xAC47: 0x73FF, //CJK UNIFIED IDEOGRAPH - 0xAC48: 0x7400, //CJK UNIFIED IDEOGRAPH - 0xAC49: 0x7401, //CJK UNIFIED IDEOGRAPH - 0xAC4A: 0x7402, //CJK UNIFIED IDEOGRAPH - 0xAC4B: 0x7404, //CJK UNIFIED IDEOGRAPH - 0xAC4C: 0x7407, //CJK UNIFIED IDEOGRAPH - 0xAC4D: 0x7408, //CJK UNIFIED IDEOGRAPH - 0xAC4E: 0x740B, //CJK UNIFIED IDEOGRAPH - 0xAC4F: 0x740C, //CJK UNIFIED IDEOGRAPH - 0xAC50: 0x740D, //CJK UNIFIED IDEOGRAPH - 0xAC51: 0x740E, //CJK UNIFIED IDEOGRAPH - 0xAC52: 0x7411, //CJK UNIFIED IDEOGRAPH - 0xAC53: 0x7412, //CJK UNIFIED IDEOGRAPH - 0xAC54: 0x7413, //CJK UNIFIED IDEOGRAPH - 0xAC55: 0x7414, //CJK UNIFIED IDEOGRAPH - 0xAC56: 0x7415, //CJK UNIFIED IDEOGRAPH - 0xAC57: 0x7416, //CJK UNIFIED IDEOGRAPH - 0xAC58: 0x7417, //CJK UNIFIED IDEOGRAPH - 0xAC59: 0x7418, //CJK UNIFIED IDEOGRAPH - 0xAC5A: 0x7419, //CJK UNIFIED IDEOGRAPH - 0xAC5B: 0x741C, //CJK UNIFIED IDEOGRAPH - 0xAC5C: 0x741D, //CJK UNIFIED IDEOGRAPH - 0xAC5D: 0x741E, //CJK UNIFIED IDEOGRAPH - 0xAC5E: 0x741F, //CJK UNIFIED IDEOGRAPH - 0xAC5F: 0x7420, //CJK UNIFIED IDEOGRAPH - 0xAC60: 0x7421, //CJK UNIFIED IDEOGRAPH - 0xAC61: 0x7423, //CJK UNIFIED IDEOGRAPH - 0xAC62: 0x7424, //CJK UNIFIED IDEOGRAPH - 0xAC63: 0x7427, //CJK UNIFIED IDEOGRAPH - 0xAC64: 0x7429, //CJK UNIFIED IDEOGRAPH - 0xAC65: 0x742B, //CJK UNIFIED IDEOGRAPH - 0xAC66: 0x742D, //CJK UNIFIED IDEOGRAPH - 0xAC67: 0x742F, //CJK UNIFIED IDEOGRAPH - 0xAC68: 0x7431, //CJK UNIFIED IDEOGRAPH - 0xAC69: 0x7432, //CJK UNIFIED IDEOGRAPH - 0xAC6A: 0x7437, //CJK UNIFIED IDEOGRAPH - 0xAC6B: 0x7438, //CJK UNIFIED IDEOGRAPH - 0xAC6C: 0x7439, //CJK UNIFIED IDEOGRAPH - 0xAC6D: 0x743A, //CJK UNIFIED IDEOGRAPH - 0xAC6E: 0x743B, //CJK UNIFIED IDEOGRAPH - 0xAC6F: 0x743D, //CJK UNIFIED IDEOGRAPH - 0xAC70: 0x743E, //CJK UNIFIED IDEOGRAPH - 0xAC71: 0x743F, //CJK UNIFIED IDEOGRAPH - 0xAC72: 0x7440, //CJK UNIFIED IDEOGRAPH - 0xAC73: 0x7442, //CJK UNIFIED IDEOGRAPH - 0xAC74: 0x7443, //CJK UNIFIED IDEOGRAPH - 0xAC75: 0x7444, //CJK UNIFIED IDEOGRAPH - 0xAC76: 0x7445, //CJK UNIFIED IDEOGRAPH - 0xAC77: 0x7446, //CJK UNIFIED IDEOGRAPH - 0xAC78: 0x7447, //CJK UNIFIED IDEOGRAPH - 0xAC79: 0x7448, //CJK UNIFIED IDEOGRAPH - 0xAC7A: 0x7449, //CJK UNIFIED IDEOGRAPH - 0xAC7B: 0x744A, //CJK UNIFIED IDEOGRAPH - 0xAC7C: 0x744B, //CJK UNIFIED IDEOGRAPH - 0xAC7D: 0x744C, //CJK UNIFIED IDEOGRAPH - 0xAC7E: 0x744D, //CJK UNIFIED IDEOGRAPH - 0xAC80: 0x744E, //CJK UNIFIED IDEOGRAPH - 0xAC81: 0x744F, //CJK UNIFIED IDEOGRAPH - 0xAC82: 0x7450, //CJK UNIFIED IDEOGRAPH - 0xAC83: 0x7451, //CJK UNIFIED IDEOGRAPH - 0xAC84: 0x7452, //CJK UNIFIED IDEOGRAPH - 0xAC85: 0x7453, //CJK UNIFIED IDEOGRAPH - 0xAC86: 0x7454, //CJK UNIFIED IDEOGRAPH - 0xAC87: 0x7456, //CJK UNIFIED IDEOGRAPH - 0xAC88: 0x7458, //CJK UNIFIED IDEOGRAPH - 0xAC89: 0x745D, //CJK UNIFIED IDEOGRAPH - 0xAC8A: 0x7460, //CJK UNIFIED IDEOGRAPH - 0xAC8B: 0x7461, //CJK UNIFIED IDEOGRAPH - 0xAC8C: 0x7462, //CJK UNIFIED IDEOGRAPH - 0xAC8D: 0x7463, //CJK UNIFIED IDEOGRAPH - 0xAC8E: 0x7464, //CJK UNIFIED IDEOGRAPH - 0xAC8F: 0x7465, //CJK UNIFIED IDEOGRAPH - 0xAC90: 0x7466, //CJK UNIFIED IDEOGRAPH - 0xAC91: 0x7467, //CJK UNIFIED IDEOGRAPH - 0xAC92: 0x7468, //CJK UNIFIED IDEOGRAPH - 0xAC93: 0x7469, //CJK UNIFIED IDEOGRAPH - 0xAC94: 0x746A, //CJK UNIFIED IDEOGRAPH - 0xAC95: 0x746B, //CJK UNIFIED IDEOGRAPH - 0xAC96: 0x746C, //CJK UNIFIED IDEOGRAPH - 0xAC97: 0x746E, //CJK UNIFIED IDEOGRAPH - 0xAC98: 0x746F, //CJK UNIFIED IDEOGRAPH - 0xAC99: 0x7471, //CJK UNIFIED IDEOGRAPH - 0xAC9A: 0x7472, //CJK UNIFIED IDEOGRAPH - 0xAC9B: 0x7473, //CJK UNIFIED IDEOGRAPH - 0xAC9C: 0x7474, //CJK UNIFIED IDEOGRAPH - 0xAC9D: 0x7475, //CJK UNIFIED IDEOGRAPH - 0xAC9E: 0x7478, //CJK UNIFIED IDEOGRAPH - 0xAC9F: 0x7479, //CJK UNIFIED IDEOGRAPH - 0xACA0: 0x747A, //CJK UNIFIED IDEOGRAPH - 0xAD40: 0x747B, //CJK UNIFIED IDEOGRAPH - 0xAD41: 0x747C, //CJK UNIFIED IDEOGRAPH - 0xAD42: 0x747D, //CJK UNIFIED IDEOGRAPH - 0xAD43: 0x747F, //CJK UNIFIED IDEOGRAPH - 0xAD44: 0x7482, //CJK UNIFIED IDEOGRAPH - 0xAD45: 0x7484, //CJK UNIFIED IDEOGRAPH - 0xAD46: 0x7485, //CJK UNIFIED IDEOGRAPH - 0xAD47: 0x7486, //CJK UNIFIED IDEOGRAPH - 0xAD48: 0x7488, //CJK UNIFIED IDEOGRAPH - 0xAD49: 0x7489, //CJK UNIFIED IDEOGRAPH - 0xAD4A: 0x748A, //CJK UNIFIED IDEOGRAPH - 0xAD4B: 0x748C, //CJK UNIFIED IDEOGRAPH - 0xAD4C: 0x748D, //CJK UNIFIED IDEOGRAPH - 0xAD4D: 0x748F, //CJK UNIFIED IDEOGRAPH - 0xAD4E: 0x7491, //CJK UNIFIED IDEOGRAPH - 0xAD4F: 0x7492, //CJK UNIFIED IDEOGRAPH - 0xAD50: 0x7493, //CJK UNIFIED IDEOGRAPH - 0xAD51: 0x7494, //CJK UNIFIED IDEOGRAPH - 0xAD52: 0x7495, //CJK UNIFIED IDEOGRAPH - 0xAD53: 0x7496, //CJK UNIFIED IDEOGRAPH - 0xAD54: 0x7497, //CJK UNIFIED IDEOGRAPH - 0xAD55: 0x7498, //CJK UNIFIED IDEOGRAPH - 0xAD56: 0x7499, //CJK UNIFIED IDEOGRAPH - 0xAD57: 0x749A, //CJK UNIFIED IDEOGRAPH - 0xAD58: 0x749B, //CJK UNIFIED IDEOGRAPH - 0xAD59: 0x749D, //CJK UNIFIED IDEOGRAPH - 0xAD5A: 0x749F, //CJK UNIFIED IDEOGRAPH - 0xAD5B: 0x74A0, //CJK UNIFIED IDEOGRAPH - 0xAD5C: 0x74A1, //CJK UNIFIED IDEOGRAPH - 0xAD5D: 0x74A2, //CJK UNIFIED IDEOGRAPH - 0xAD5E: 0x74A3, //CJK UNIFIED IDEOGRAPH - 0xAD5F: 0x74A4, //CJK UNIFIED IDEOGRAPH - 0xAD60: 0x74A5, //CJK UNIFIED IDEOGRAPH - 0xAD61: 0x74A6, //CJK UNIFIED IDEOGRAPH - 0xAD62: 0x74AA, //CJK UNIFIED IDEOGRAPH - 0xAD63: 0x74AB, //CJK UNIFIED IDEOGRAPH - 0xAD64: 0x74AC, //CJK UNIFIED IDEOGRAPH - 0xAD65: 0x74AD, //CJK UNIFIED IDEOGRAPH - 0xAD66: 0x74AE, //CJK UNIFIED IDEOGRAPH - 0xAD67: 0x74AF, //CJK UNIFIED IDEOGRAPH - 0xAD68: 0x74B0, //CJK UNIFIED IDEOGRAPH - 0xAD69: 0x74B1, //CJK UNIFIED IDEOGRAPH - 0xAD6A: 0x74B2, //CJK UNIFIED IDEOGRAPH - 0xAD6B: 0x74B3, //CJK UNIFIED IDEOGRAPH - 0xAD6C: 0x74B4, //CJK UNIFIED IDEOGRAPH - 0xAD6D: 0x74B5, //CJK UNIFIED IDEOGRAPH - 0xAD6E: 0x74B6, //CJK UNIFIED IDEOGRAPH - 0xAD6F: 0x74B7, //CJK UNIFIED IDEOGRAPH - 0xAD70: 0x74B8, //CJK UNIFIED IDEOGRAPH - 0xAD71: 0x74B9, //CJK UNIFIED IDEOGRAPH - 0xAD72: 0x74BB, //CJK UNIFIED IDEOGRAPH - 0xAD73: 0x74BC, //CJK UNIFIED IDEOGRAPH - 0xAD74: 0x74BD, //CJK UNIFIED IDEOGRAPH - 0xAD75: 0x74BE, //CJK UNIFIED IDEOGRAPH - 0xAD76: 0x74BF, //CJK UNIFIED IDEOGRAPH - 0xAD77: 0x74C0, //CJK UNIFIED IDEOGRAPH - 0xAD78: 0x74C1, //CJK UNIFIED IDEOGRAPH - 0xAD79: 0x74C2, //CJK UNIFIED IDEOGRAPH - 0xAD7A: 0x74C3, //CJK UNIFIED IDEOGRAPH - 0xAD7B: 0x74C4, //CJK UNIFIED IDEOGRAPH - 0xAD7C: 0x74C5, //CJK UNIFIED IDEOGRAPH - 0xAD7D: 0x74C6, //CJK UNIFIED IDEOGRAPH - 0xAD7E: 0x74C7, //CJK UNIFIED IDEOGRAPH - 0xAD80: 0x74C8, //CJK UNIFIED IDEOGRAPH - 0xAD81: 0x74C9, //CJK UNIFIED IDEOGRAPH - 0xAD82: 0x74CA, //CJK UNIFIED IDEOGRAPH - 0xAD83: 0x74CB, //CJK UNIFIED IDEOGRAPH - 0xAD84: 0x74CC, //CJK UNIFIED IDEOGRAPH - 0xAD85: 0x74CD, //CJK UNIFIED IDEOGRAPH - 0xAD86: 0x74CE, //CJK UNIFIED IDEOGRAPH - 0xAD87: 0x74CF, //CJK UNIFIED IDEOGRAPH - 0xAD88: 0x74D0, //CJK UNIFIED IDEOGRAPH - 0xAD89: 0x74D1, //CJK UNIFIED IDEOGRAPH - 0xAD8A: 0x74D3, //CJK UNIFIED IDEOGRAPH - 0xAD8B: 0x74D4, //CJK UNIFIED IDEOGRAPH - 0xAD8C: 0x74D5, //CJK UNIFIED IDEOGRAPH - 0xAD8D: 0x74D6, //CJK UNIFIED IDEOGRAPH - 0xAD8E: 0x74D7, //CJK UNIFIED IDEOGRAPH - 0xAD8F: 0x74D8, //CJK UNIFIED IDEOGRAPH - 0xAD90: 0x74D9, //CJK UNIFIED IDEOGRAPH - 0xAD91: 0x74DA, //CJK UNIFIED IDEOGRAPH - 0xAD92: 0x74DB, //CJK UNIFIED IDEOGRAPH - 0xAD93: 0x74DD, //CJK UNIFIED IDEOGRAPH - 0xAD94: 0x74DF, //CJK UNIFIED IDEOGRAPH - 0xAD95: 0x74E1, //CJK UNIFIED IDEOGRAPH - 0xAD96: 0x74E5, //CJK UNIFIED IDEOGRAPH - 0xAD97: 0x74E7, //CJK UNIFIED IDEOGRAPH - 0xAD98: 0x74E8, //CJK UNIFIED IDEOGRAPH - 0xAD99: 0x74E9, //CJK UNIFIED IDEOGRAPH - 0xAD9A: 0x74EA, //CJK UNIFIED IDEOGRAPH - 0xAD9B: 0x74EB, //CJK UNIFIED IDEOGRAPH - 0xAD9C: 0x74EC, //CJK UNIFIED IDEOGRAPH - 0xAD9D: 0x74ED, //CJK UNIFIED IDEOGRAPH - 0xAD9E: 0x74F0, //CJK UNIFIED IDEOGRAPH - 0xAD9F: 0x74F1, //CJK UNIFIED IDEOGRAPH - 0xADA0: 0x74F2, //CJK UNIFIED IDEOGRAPH - 0xAE40: 0x74F3, //CJK UNIFIED IDEOGRAPH - 0xAE41: 0x74F5, //CJK UNIFIED IDEOGRAPH - 0xAE42: 0x74F8, //CJK UNIFIED IDEOGRAPH - 0xAE43: 0x74F9, //CJK UNIFIED IDEOGRAPH - 0xAE44: 0x74FA, //CJK UNIFIED IDEOGRAPH - 0xAE45: 0x74FB, //CJK UNIFIED IDEOGRAPH - 0xAE46: 0x74FC, //CJK UNIFIED IDEOGRAPH - 0xAE47: 0x74FD, //CJK UNIFIED IDEOGRAPH - 0xAE48: 0x74FE, //CJK UNIFIED IDEOGRAPH - 0xAE49: 0x7500, //CJK UNIFIED IDEOGRAPH - 0xAE4A: 0x7501, //CJK UNIFIED IDEOGRAPH - 0xAE4B: 0x7502, //CJK UNIFIED IDEOGRAPH - 0xAE4C: 0x7503, //CJK UNIFIED IDEOGRAPH - 0xAE4D: 0x7505, //CJK UNIFIED IDEOGRAPH - 0xAE4E: 0x7506, //CJK UNIFIED IDEOGRAPH - 0xAE4F: 0x7507, //CJK UNIFIED IDEOGRAPH - 0xAE50: 0x7508, //CJK UNIFIED IDEOGRAPH - 0xAE51: 0x7509, //CJK UNIFIED IDEOGRAPH - 0xAE52: 0x750A, //CJK UNIFIED IDEOGRAPH - 0xAE53: 0x750B, //CJK UNIFIED IDEOGRAPH - 0xAE54: 0x750C, //CJK UNIFIED IDEOGRAPH - 0xAE55: 0x750E, //CJK UNIFIED IDEOGRAPH - 0xAE56: 0x7510, //CJK UNIFIED IDEOGRAPH - 0xAE57: 0x7512, //CJK UNIFIED IDEOGRAPH - 0xAE58: 0x7514, //CJK UNIFIED IDEOGRAPH - 0xAE59: 0x7515, //CJK UNIFIED IDEOGRAPH - 0xAE5A: 0x7516, //CJK UNIFIED IDEOGRAPH - 0xAE5B: 0x7517, //CJK UNIFIED IDEOGRAPH - 0xAE5C: 0x751B, //CJK UNIFIED IDEOGRAPH - 0xAE5D: 0x751D, //CJK UNIFIED IDEOGRAPH - 0xAE5E: 0x751E, //CJK UNIFIED IDEOGRAPH - 0xAE5F: 0x7520, //CJK UNIFIED IDEOGRAPH - 0xAE60: 0x7521, //CJK UNIFIED IDEOGRAPH - 0xAE61: 0x7522, //CJK UNIFIED IDEOGRAPH - 0xAE62: 0x7523, //CJK UNIFIED IDEOGRAPH - 0xAE63: 0x7524, //CJK UNIFIED IDEOGRAPH - 0xAE64: 0x7526, //CJK UNIFIED IDEOGRAPH - 0xAE65: 0x7527, //CJK UNIFIED IDEOGRAPH - 0xAE66: 0x752A, //CJK UNIFIED IDEOGRAPH - 0xAE67: 0x752E, //CJK UNIFIED IDEOGRAPH - 0xAE68: 0x7534, //CJK UNIFIED IDEOGRAPH - 0xAE69: 0x7536, //CJK UNIFIED IDEOGRAPH - 0xAE6A: 0x7539, //CJK UNIFIED IDEOGRAPH - 0xAE6B: 0x753C, //CJK UNIFIED IDEOGRAPH - 0xAE6C: 0x753D, //CJK UNIFIED IDEOGRAPH - 0xAE6D: 0x753F, //CJK UNIFIED IDEOGRAPH - 0xAE6E: 0x7541, //CJK UNIFIED IDEOGRAPH - 0xAE6F: 0x7542, //CJK UNIFIED IDEOGRAPH - 0xAE70: 0x7543, //CJK UNIFIED IDEOGRAPH - 0xAE71: 0x7544, //CJK UNIFIED IDEOGRAPH - 0xAE72: 0x7546, //CJK UNIFIED IDEOGRAPH - 0xAE73: 0x7547, //CJK UNIFIED IDEOGRAPH - 0xAE74: 0x7549, //CJK UNIFIED IDEOGRAPH - 0xAE75: 0x754A, //CJK UNIFIED IDEOGRAPH - 0xAE76: 0x754D, //CJK UNIFIED IDEOGRAPH - 0xAE77: 0x7550, //CJK UNIFIED IDEOGRAPH - 0xAE78: 0x7551, //CJK UNIFIED IDEOGRAPH - 0xAE79: 0x7552, //CJK UNIFIED IDEOGRAPH - 0xAE7A: 0x7553, //CJK UNIFIED IDEOGRAPH - 0xAE7B: 0x7555, //CJK UNIFIED IDEOGRAPH - 0xAE7C: 0x7556, //CJK UNIFIED IDEOGRAPH - 0xAE7D: 0x7557, //CJK UNIFIED IDEOGRAPH - 0xAE7E: 0x7558, //CJK UNIFIED IDEOGRAPH - 0xAE80: 0x755D, //CJK UNIFIED IDEOGRAPH - 0xAE81: 0x755E, //CJK UNIFIED IDEOGRAPH - 0xAE82: 0x755F, //CJK UNIFIED IDEOGRAPH - 0xAE83: 0x7560, //CJK UNIFIED IDEOGRAPH - 0xAE84: 0x7561, //CJK UNIFIED IDEOGRAPH - 0xAE85: 0x7562, //CJK UNIFIED IDEOGRAPH - 0xAE86: 0x7563, //CJK UNIFIED IDEOGRAPH - 0xAE87: 0x7564, //CJK UNIFIED IDEOGRAPH - 0xAE88: 0x7567, //CJK UNIFIED IDEOGRAPH - 0xAE89: 0x7568, //CJK UNIFIED IDEOGRAPH - 0xAE8A: 0x7569, //CJK UNIFIED IDEOGRAPH - 0xAE8B: 0x756B, //CJK UNIFIED IDEOGRAPH - 0xAE8C: 0x756C, //CJK UNIFIED IDEOGRAPH - 0xAE8D: 0x756D, //CJK UNIFIED IDEOGRAPH - 0xAE8E: 0x756E, //CJK UNIFIED IDEOGRAPH - 0xAE8F: 0x756F, //CJK UNIFIED IDEOGRAPH - 0xAE90: 0x7570, //CJK UNIFIED IDEOGRAPH - 0xAE91: 0x7571, //CJK UNIFIED IDEOGRAPH - 0xAE92: 0x7573, //CJK UNIFIED IDEOGRAPH - 0xAE93: 0x7575, //CJK UNIFIED IDEOGRAPH - 0xAE94: 0x7576, //CJK UNIFIED IDEOGRAPH - 0xAE95: 0x7577, //CJK UNIFIED IDEOGRAPH - 0xAE96: 0x757A, //CJK UNIFIED IDEOGRAPH - 0xAE97: 0x757B, //CJK UNIFIED IDEOGRAPH - 0xAE98: 0x757C, //CJK UNIFIED IDEOGRAPH - 0xAE99: 0x757D, //CJK UNIFIED IDEOGRAPH - 0xAE9A: 0x757E, //CJK UNIFIED IDEOGRAPH - 0xAE9B: 0x7580, //CJK UNIFIED IDEOGRAPH - 0xAE9C: 0x7581, //CJK UNIFIED IDEOGRAPH - 0xAE9D: 0x7582, //CJK UNIFIED IDEOGRAPH - 0xAE9E: 0x7584, //CJK UNIFIED IDEOGRAPH - 0xAE9F: 0x7585, //CJK UNIFIED IDEOGRAPH - 0xAEA0: 0x7587, //CJK UNIFIED IDEOGRAPH - 0xAF40: 0x7588, //CJK UNIFIED IDEOGRAPH - 0xAF41: 0x7589, //CJK UNIFIED IDEOGRAPH - 0xAF42: 0x758A, //CJK UNIFIED IDEOGRAPH - 0xAF43: 0x758C, //CJK UNIFIED IDEOGRAPH - 0xAF44: 0x758D, //CJK UNIFIED IDEOGRAPH - 0xAF45: 0x758E, //CJK UNIFIED IDEOGRAPH - 0xAF46: 0x7590, //CJK UNIFIED IDEOGRAPH - 0xAF47: 0x7593, //CJK UNIFIED IDEOGRAPH - 0xAF48: 0x7595, //CJK UNIFIED IDEOGRAPH - 0xAF49: 0x7598, //CJK UNIFIED IDEOGRAPH - 0xAF4A: 0x759B, //CJK UNIFIED IDEOGRAPH - 0xAF4B: 0x759C, //CJK UNIFIED IDEOGRAPH - 0xAF4C: 0x759E, //CJK UNIFIED IDEOGRAPH - 0xAF4D: 0x75A2, //CJK UNIFIED IDEOGRAPH - 0xAF4E: 0x75A6, //CJK UNIFIED IDEOGRAPH - 0xAF4F: 0x75A7, //CJK UNIFIED IDEOGRAPH - 0xAF50: 0x75A8, //CJK UNIFIED IDEOGRAPH - 0xAF51: 0x75A9, //CJK UNIFIED IDEOGRAPH - 0xAF52: 0x75AA, //CJK UNIFIED IDEOGRAPH - 0xAF53: 0x75AD, //CJK UNIFIED IDEOGRAPH - 0xAF54: 0x75B6, //CJK UNIFIED IDEOGRAPH - 0xAF55: 0x75B7, //CJK UNIFIED IDEOGRAPH - 0xAF56: 0x75BA, //CJK UNIFIED IDEOGRAPH - 0xAF57: 0x75BB, //CJK UNIFIED IDEOGRAPH - 0xAF58: 0x75BF, //CJK UNIFIED IDEOGRAPH - 0xAF59: 0x75C0, //CJK UNIFIED IDEOGRAPH - 0xAF5A: 0x75C1, //CJK UNIFIED IDEOGRAPH - 0xAF5B: 0x75C6, //CJK UNIFIED IDEOGRAPH - 0xAF5C: 0x75CB, //CJK UNIFIED IDEOGRAPH - 0xAF5D: 0x75CC, //CJK UNIFIED IDEOGRAPH - 0xAF5E: 0x75CE, //CJK UNIFIED IDEOGRAPH - 0xAF5F: 0x75CF, //CJK UNIFIED IDEOGRAPH - 0xAF60: 0x75D0, //CJK UNIFIED IDEOGRAPH - 0xAF61: 0x75D1, //CJK UNIFIED IDEOGRAPH - 0xAF62: 0x75D3, //CJK UNIFIED IDEOGRAPH - 0xAF63: 0x75D7, //CJK UNIFIED IDEOGRAPH - 0xAF64: 0x75D9, //CJK UNIFIED IDEOGRAPH - 0xAF65: 0x75DA, //CJK UNIFIED IDEOGRAPH - 0xAF66: 0x75DC, //CJK UNIFIED IDEOGRAPH - 0xAF67: 0x75DD, //CJK UNIFIED IDEOGRAPH - 0xAF68: 0x75DF, //CJK UNIFIED IDEOGRAPH - 0xAF69: 0x75E0, //CJK UNIFIED IDEOGRAPH - 0xAF6A: 0x75E1, //CJK UNIFIED IDEOGRAPH - 0xAF6B: 0x75E5, //CJK UNIFIED IDEOGRAPH - 0xAF6C: 0x75E9, //CJK UNIFIED IDEOGRAPH - 0xAF6D: 0x75EC, //CJK UNIFIED IDEOGRAPH - 0xAF6E: 0x75ED, //CJK UNIFIED IDEOGRAPH - 0xAF6F: 0x75EE, //CJK UNIFIED IDEOGRAPH - 0xAF70: 0x75EF, //CJK UNIFIED IDEOGRAPH - 0xAF71: 0x75F2, //CJK UNIFIED IDEOGRAPH - 0xAF72: 0x75F3, //CJK UNIFIED IDEOGRAPH - 0xAF73: 0x75F5, //CJK UNIFIED IDEOGRAPH - 0xAF74: 0x75F6, //CJK UNIFIED IDEOGRAPH - 0xAF75: 0x75F7, //CJK UNIFIED IDEOGRAPH - 0xAF76: 0x75F8, //CJK UNIFIED IDEOGRAPH - 0xAF77: 0x75FA, //CJK UNIFIED IDEOGRAPH - 0xAF78: 0x75FB, //CJK UNIFIED IDEOGRAPH - 0xAF79: 0x75FD, //CJK UNIFIED IDEOGRAPH - 0xAF7A: 0x75FE, //CJK UNIFIED IDEOGRAPH - 0xAF7B: 0x7602, //CJK UNIFIED IDEOGRAPH - 0xAF7C: 0x7604, //CJK UNIFIED IDEOGRAPH - 0xAF7D: 0x7606, //CJK UNIFIED IDEOGRAPH - 0xAF7E: 0x7607, //CJK UNIFIED IDEOGRAPH - 0xAF80: 0x7608, //CJK UNIFIED IDEOGRAPH - 0xAF81: 0x7609, //CJK UNIFIED IDEOGRAPH - 0xAF82: 0x760B, //CJK UNIFIED IDEOGRAPH - 0xAF83: 0x760D, //CJK UNIFIED IDEOGRAPH - 0xAF84: 0x760E, //CJK UNIFIED IDEOGRAPH - 0xAF85: 0x760F, //CJK UNIFIED IDEOGRAPH - 0xAF86: 0x7611, //CJK UNIFIED IDEOGRAPH - 0xAF87: 0x7612, //CJK UNIFIED IDEOGRAPH - 0xAF88: 0x7613, //CJK UNIFIED IDEOGRAPH - 0xAF89: 0x7614, //CJK UNIFIED IDEOGRAPH - 0xAF8A: 0x7616, //CJK UNIFIED IDEOGRAPH - 0xAF8B: 0x761A, //CJK UNIFIED IDEOGRAPH - 0xAF8C: 0x761C, //CJK UNIFIED IDEOGRAPH - 0xAF8D: 0x761D, //CJK UNIFIED IDEOGRAPH - 0xAF8E: 0x761E, //CJK UNIFIED IDEOGRAPH - 0xAF8F: 0x7621, //CJK UNIFIED IDEOGRAPH - 0xAF90: 0x7623, //CJK UNIFIED IDEOGRAPH - 0xAF91: 0x7627, //CJK UNIFIED IDEOGRAPH - 0xAF92: 0x7628, //CJK UNIFIED IDEOGRAPH - 0xAF93: 0x762C, //CJK UNIFIED IDEOGRAPH - 0xAF94: 0x762E, //CJK UNIFIED IDEOGRAPH - 0xAF95: 0x762F, //CJK UNIFIED IDEOGRAPH - 0xAF96: 0x7631, //CJK UNIFIED IDEOGRAPH - 0xAF97: 0x7632, //CJK UNIFIED IDEOGRAPH - 0xAF98: 0x7636, //CJK UNIFIED IDEOGRAPH - 0xAF99: 0x7637, //CJK UNIFIED IDEOGRAPH - 0xAF9A: 0x7639, //CJK UNIFIED IDEOGRAPH - 0xAF9B: 0x763A, //CJK UNIFIED IDEOGRAPH - 0xAF9C: 0x763B, //CJK UNIFIED IDEOGRAPH - 0xAF9D: 0x763D, //CJK UNIFIED IDEOGRAPH - 0xAF9E: 0x7641, //CJK UNIFIED IDEOGRAPH - 0xAF9F: 0x7642, //CJK UNIFIED IDEOGRAPH - 0xAFA0: 0x7644, //CJK UNIFIED IDEOGRAPH - 0xB040: 0x7645, //CJK UNIFIED IDEOGRAPH - 0xB041: 0x7646, //CJK UNIFIED IDEOGRAPH - 0xB042: 0x7647, //CJK UNIFIED IDEOGRAPH - 0xB043: 0x7648, //CJK UNIFIED IDEOGRAPH - 0xB044: 0x7649, //CJK UNIFIED IDEOGRAPH - 0xB045: 0x764A, //CJK UNIFIED IDEOGRAPH - 0xB046: 0x764B, //CJK UNIFIED IDEOGRAPH - 0xB047: 0x764E, //CJK UNIFIED IDEOGRAPH - 0xB048: 0x764F, //CJK UNIFIED IDEOGRAPH - 0xB049: 0x7650, //CJK UNIFIED IDEOGRAPH - 0xB04A: 0x7651, //CJK UNIFIED IDEOGRAPH - 0xB04B: 0x7652, //CJK UNIFIED IDEOGRAPH - 0xB04C: 0x7653, //CJK UNIFIED IDEOGRAPH - 0xB04D: 0x7655, //CJK UNIFIED IDEOGRAPH - 0xB04E: 0x7657, //CJK UNIFIED IDEOGRAPH - 0xB04F: 0x7658, //CJK UNIFIED IDEOGRAPH - 0xB050: 0x7659, //CJK UNIFIED IDEOGRAPH - 0xB051: 0x765A, //CJK UNIFIED IDEOGRAPH - 0xB052: 0x765B, //CJK UNIFIED IDEOGRAPH - 0xB053: 0x765D, //CJK UNIFIED IDEOGRAPH - 0xB054: 0x765F, //CJK UNIFIED IDEOGRAPH - 0xB055: 0x7660, //CJK UNIFIED IDEOGRAPH - 0xB056: 0x7661, //CJK UNIFIED IDEOGRAPH - 0xB057: 0x7662, //CJK UNIFIED IDEOGRAPH - 0xB058: 0x7664, //CJK UNIFIED IDEOGRAPH - 0xB059: 0x7665, //CJK UNIFIED IDEOGRAPH - 0xB05A: 0x7666, //CJK UNIFIED IDEOGRAPH - 0xB05B: 0x7667, //CJK UNIFIED IDEOGRAPH - 0xB05C: 0x7668, //CJK UNIFIED IDEOGRAPH - 0xB05D: 0x7669, //CJK UNIFIED IDEOGRAPH - 0xB05E: 0x766A, //CJK UNIFIED IDEOGRAPH - 0xB05F: 0x766C, //CJK UNIFIED IDEOGRAPH - 0xB060: 0x766D, //CJK UNIFIED IDEOGRAPH - 0xB061: 0x766E, //CJK UNIFIED IDEOGRAPH - 0xB062: 0x7670, //CJK UNIFIED IDEOGRAPH - 0xB063: 0x7671, //CJK UNIFIED IDEOGRAPH - 0xB064: 0x7672, //CJK UNIFIED IDEOGRAPH - 0xB065: 0x7673, //CJK UNIFIED IDEOGRAPH - 0xB066: 0x7674, //CJK UNIFIED IDEOGRAPH - 0xB067: 0x7675, //CJK UNIFIED IDEOGRAPH - 0xB068: 0x7676, //CJK UNIFIED IDEOGRAPH - 0xB069: 0x7677, //CJK UNIFIED IDEOGRAPH - 0xB06A: 0x7679, //CJK UNIFIED IDEOGRAPH - 0xB06B: 0x767A, //CJK UNIFIED IDEOGRAPH - 0xB06C: 0x767C, //CJK UNIFIED IDEOGRAPH - 0xB06D: 0x767F, //CJK UNIFIED IDEOGRAPH - 0xB06E: 0x7680, //CJK UNIFIED IDEOGRAPH - 0xB06F: 0x7681, //CJK UNIFIED IDEOGRAPH - 0xB070: 0x7683, //CJK UNIFIED IDEOGRAPH - 0xB071: 0x7685, //CJK UNIFIED IDEOGRAPH - 0xB072: 0x7689, //CJK UNIFIED IDEOGRAPH - 0xB073: 0x768A, //CJK UNIFIED IDEOGRAPH - 0xB074: 0x768C, //CJK UNIFIED IDEOGRAPH - 0xB075: 0x768D, //CJK UNIFIED IDEOGRAPH - 0xB076: 0x768F, //CJK UNIFIED IDEOGRAPH - 0xB077: 0x7690, //CJK UNIFIED IDEOGRAPH - 0xB078: 0x7692, //CJK UNIFIED IDEOGRAPH - 0xB079: 0x7694, //CJK UNIFIED IDEOGRAPH - 0xB07A: 0x7695, //CJK UNIFIED IDEOGRAPH - 0xB07B: 0x7697, //CJK UNIFIED IDEOGRAPH - 0xB07C: 0x7698, //CJK UNIFIED IDEOGRAPH - 0xB07D: 0x769A, //CJK UNIFIED IDEOGRAPH - 0xB07E: 0x769B, //CJK UNIFIED IDEOGRAPH - 0xB080: 0x769C, //CJK UNIFIED IDEOGRAPH - 0xB081: 0x769D, //CJK UNIFIED IDEOGRAPH - 0xB082: 0x769E, //CJK UNIFIED IDEOGRAPH - 0xB083: 0x769F, //CJK UNIFIED IDEOGRAPH - 0xB084: 0x76A0, //CJK UNIFIED IDEOGRAPH - 0xB085: 0x76A1, //CJK UNIFIED IDEOGRAPH - 0xB086: 0x76A2, //CJK UNIFIED IDEOGRAPH - 0xB087: 0x76A3, //CJK UNIFIED IDEOGRAPH - 0xB088: 0x76A5, //CJK UNIFIED IDEOGRAPH - 0xB089: 0x76A6, //CJK UNIFIED IDEOGRAPH - 0xB08A: 0x76A7, //CJK UNIFIED IDEOGRAPH - 0xB08B: 0x76A8, //CJK UNIFIED IDEOGRAPH - 0xB08C: 0x76A9, //CJK UNIFIED IDEOGRAPH - 0xB08D: 0x76AA, //CJK UNIFIED IDEOGRAPH - 0xB08E: 0x76AB, //CJK UNIFIED IDEOGRAPH - 0xB08F: 0x76AC, //CJK UNIFIED IDEOGRAPH - 0xB090: 0x76AD, //CJK UNIFIED IDEOGRAPH - 0xB091: 0x76AF, //CJK UNIFIED IDEOGRAPH - 0xB092: 0x76B0, //CJK UNIFIED IDEOGRAPH - 0xB093: 0x76B3, //CJK UNIFIED IDEOGRAPH - 0xB094: 0x76B5, //CJK UNIFIED IDEOGRAPH - 0xB095: 0x76B6, //CJK UNIFIED IDEOGRAPH - 0xB096: 0x76B7, //CJK UNIFIED IDEOGRAPH - 0xB097: 0x76B8, //CJK UNIFIED IDEOGRAPH - 0xB098: 0x76B9, //CJK UNIFIED IDEOGRAPH - 0xB099: 0x76BA, //CJK UNIFIED IDEOGRAPH - 0xB09A: 0x76BB, //CJK UNIFIED IDEOGRAPH - 0xB09B: 0x76BC, //CJK UNIFIED IDEOGRAPH - 0xB09C: 0x76BD, //CJK UNIFIED IDEOGRAPH - 0xB09D: 0x76BE, //CJK UNIFIED IDEOGRAPH - 0xB09E: 0x76C0, //CJK UNIFIED IDEOGRAPH - 0xB09F: 0x76C1, //CJK UNIFIED IDEOGRAPH - 0xB0A0: 0x76C3, //CJK UNIFIED IDEOGRAPH - 0xB0A1: 0x554A, //CJK UNIFIED IDEOGRAPH - 0xB0A2: 0x963F, //CJK UNIFIED IDEOGRAPH - 0xB0A3: 0x57C3, //CJK UNIFIED IDEOGRAPH - 0xB0A4: 0x6328, //CJK UNIFIED IDEOGRAPH - 0xB0A5: 0x54CE, //CJK UNIFIED IDEOGRAPH - 0xB0A6: 0x5509, //CJK UNIFIED IDEOGRAPH - 0xB0A7: 0x54C0, //CJK UNIFIED IDEOGRAPH - 0xB0A8: 0x7691, //CJK UNIFIED IDEOGRAPH - 0xB0A9: 0x764C, //CJK UNIFIED IDEOGRAPH - 0xB0AA: 0x853C, //CJK UNIFIED IDEOGRAPH - 0xB0AB: 0x77EE, //CJK UNIFIED IDEOGRAPH - 0xB0AC: 0x827E, //CJK UNIFIED IDEOGRAPH - 0xB0AD: 0x788D, //CJK UNIFIED IDEOGRAPH - 0xB0AE: 0x7231, //CJK UNIFIED IDEOGRAPH - 0xB0AF: 0x9698, //CJK UNIFIED IDEOGRAPH - 0xB0B0: 0x978D, //CJK UNIFIED IDEOGRAPH - 0xB0B1: 0x6C28, //CJK UNIFIED IDEOGRAPH - 0xB0B2: 0x5B89, //CJK UNIFIED IDEOGRAPH - 0xB0B3: 0x4FFA, //CJK UNIFIED IDEOGRAPH - 0xB0B4: 0x6309, //CJK UNIFIED IDEOGRAPH - 0xB0B5: 0x6697, //CJK UNIFIED IDEOGRAPH - 0xB0B6: 0x5CB8, //CJK UNIFIED IDEOGRAPH - 0xB0B7: 0x80FA, //CJK UNIFIED IDEOGRAPH - 0xB0B8: 0x6848, //CJK UNIFIED IDEOGRAPH - 0xB0B9: 0x80AE, //CJK UNIFIED IDEOGRAPH - 0xB0BA: 0x6602, //CJK UNIFIED IDEOGRAPH - 0xB0BB: 0x76CE, //CJK UNIFIED IDEOGRAPH - 0xB0BC: 0x51F9, //CJK UNIFIED IDEOGRAPH - 0xB0BD: 0x6556, //CJK UNIFIED IDEOGRAPH - 0xB0BE: 0x71AC, //CJK UNIFIED IDEOGRAPH - 0xB0BF: 0x7FF1, //CJK UNIFIED IDEOGRAPH - 0xB0C0: 0x8884, //CJK UNIFIED IDEOGRAPH - 0xB0C1: 0x50B2, //CJK UNIFIED IDEOGRAPH - 0xB0C2: 0x5965, //CJK UNIFIED IDEOGRAPH - 0xB0C3: 0x61CA, //CJK UNIFIED IDEOGRAPH - 0xB0C4: 0x6FB3, //CJK UNIFIED IDEOGRAPH - 0xB0C5: 0x82AD, //CJK UNIFIED IDEOGRAPH - 0xB0C6: 0x634C, //CJK UNIFIED IDEOGRAPH - 0xB0C7: 0x6252, //CJK UNIFIED IDEOGRAPH - 0xB0C8: 0x53ED, //CJK UNIFIED IDEOGRAPH - 0xB0C9: 0x5427, //CJK UNIFIED IDEOGRAPH - 0xB0CA: 0x7B06, //CJK UNIFIED IDEOGRAPH - 0xB0CB: 0x516B, //CJK UNIFIED IDEOGRAPH - 0xB0CC: 0x75A4, //CJK UNIFIED IDEOGRAPH - 0xB0CD: 0x5DF4, //CJK UNIFIED IDEOGRAPH - 0xB0CE: 0x62D4, //CJK UNIFIED IDEOGRAPH - 0xB0CF: 0x8DCB, //CJK UNIFIED IDEOGRAPH - 0xB0D0: 0x9776, //CJK UNIFIED IDEOGRAPH - 0xB0D1: 0x628A, //CJK UNIFIED IDEOGRAPH - 0xB0D2: 0x8019, //CJK UNIFIED IDEOGRAPH - 0xB0D3: 0x575D, //CJK UNIFIED IDEOGRAPH - 0xB0D4: 0x9738, //CJK UNIFIED IDEOGRAPH - 0xB0D5: 0x7F62, //CJK UNIFIED IDEOGRAPH - 0xB0D6: 0x7238, //CJK UNIFIED IDEOGRAPH - 0xB0D7: 0x767D, //CJK UNIFIED IDEOGRAPH - 0xB0D8: 0x67CF, //CJK UNIFIED IDEOGRAPH - 0xB0D9: 0x767E, //CJK UNIFIED IDEOGRAPH - 0xB0DA: 0x6446, //CJK UNIFIED IDEOGRAPH - 0xB0DB: 0x4F70, //CJK UNIFIED IDEOGRAPH - 0xB0DC: 0x8D25, //CJK UNIFIED IDEOGRAPH - 0xB0DD: 0x62DC, //CJK UNIFIED IDEOGRAPH - 0xB0DE: 0x7A17, //CJK UNIFIED IDEOGRAPH - 0xB0DF: 0x6591, //CJK UNIFIED IDEOGRAPH - 0xB0E0: 0x73ED, //CJK UNIFIED IDEOGRAPH - 0xB0E1: 0x642C, //CJK UNIFIED IDEOGRAPH - 0xB0E2: 0x6273, //CJK UNIFIED IDEOGRAPH - 0xB0E3: 0x822C, //CJK UNIFIED IDEOGRAPH - 0xB0E4: 0x9881, //CJK UNIFIED IDEOGRAPH - 0xB0E5: 0x677F, //CJK UNIFIED IDEOGRAPH - 0xB0E6: 0x7248, //CJK UNIFIED IDEOGRAPH - 0xB0E7: 0x626E, //CJK UNIFIED IDEOGRAPH - 0xB0E8: 0x62CC, //CJK UNIFIED IDEOGRAPH - 0xB0E9: 0x4F34, //CJK UNIFIED IDEOGRAPH - 0xB0EA: 0x74E3, //CJK UNIFIED IDEOGRAPH - 0xB0EB: 0x534A, //CJK UNIFIED IDEOGRAPH - 0xB0EC: 0x529E, //CJK UNIFIED IDEOGRAPH - 0xB0ED: 0x7ECA, //CJK UNIFIED IDEOGRAPH - 0xB0EE: 0x90A6, //CJK UNIFIED IDEOGRAPH - 0xB0EF: 0x5E2E, //CJK UNIFIED IDEOGRAPH - 0xB0F0: 0x6886, //CJK UNIFIED IDEOGRAPH - 0xB0F1: 0x699C, //CJK UNIFIED IDEOGRAPH - 0xB0F2: 0x8180, //CJK UNIFIED IDEOGRAPH - 0xB0F3: 0x7ED1, //CJK UNIFIED IDEOGRAPH - 0xB0F4: 0x68D2, //CJK UNIFIED IDEOGRAPH - 0xB0F5: 0x78C5, //CJK UNIFIED IDEOGRAPH - 0xB0F6: 0x868C, //CJK UNIFIED IDEOGRAPH - 0xB0F7: 0x9551, //CJK UNIFIED IDEOGRAPH - 0xB0F8: 0x508D, //CJK UNIFIED IDEOGRAPH - 0xB0F9: 0x8C24, //CJK UNIFIED IDEOGRAPH - 0xB0FA: 0x82DE, //CJK UNIFIED IDEOGRAPH - 0xB0FB: 0x80DE, //CJK UNIFIED IDEOGRAPH - 0xB0FC: 0x5305, //CJK UNIFIED IDEOGRAPH - 0xB0FD: 0x8912, //CJK UNIFIED IDEOGRAPH - 0xB0FE: 0x5265, //CJK UNIFIED IDEOGRAPH - 0xB140: 0x76C4, //CJK UNIFIED IDEOGRAPH - 0xB141: 0x76C7, //CJK UNIFIED IDEOGRAPH - 0xB142: 0x76C9, //CJK UNIFIED IDEOGRAPH - 0xB143: 0x76CB, //CJK UNIFIED IDEOGRAPH - 0xB144: 0x76CC, //CJK UNIFIED IDEOGRAPH - 0xB145: 0x76D3, //CJK UNIFIED IDEOGRAPH - 0xB146: 0x76D5, //CJK UNIFIED IDEOGRAPH - 0xB147: 0x76D9, //CJK UNIFIED IDEOGRAPH - 0xB148: 0x76DA, //CJK UNIFIED IDEOGRAPH - 0xB149: 0x76DC, //CJK UNIFIED IDEOGRAPH - 0xB14A: 0x76DD, //CJK UNIFIED IDEOGRAPH - 0xB14B: 0x76DE, //CJK UNIFIED IDEOGRAPH - 0xB14C: 0x76E0, //CJK UNIFIED IDEOGRAPH - 0xB14D: 0x76E1, //CJK UNIFIED IDEOGRAPH - 0xB14E: 0x76E2, //CJK UNIFIED IDEOGRAPH - 0xB14F: 0x76E3, //CJK UNIFIED IDEOGRAPH - 0xB150: 0x76E4, //CJK UNIFIED IDEOGRAPH - 0xB151: 0x76E6, //CJK UNIFIED IDEOGRAPH - 0xB152: 0x76E7, //CJK UNIFIED IDEOGRAPH - 0xB153: 0x76E8, //CJK UNIFIED IDEOGRAPH - 0xB154: 0x76E9, //CJK UNIFIED IDEOGRAPH - 0xB155: 0x76EA, //CJK UNIFIED IDEOGRAPH - 0xB156: 0x76EB, //CJK UNIFIED IDEOGRAPH - 0xB157: 0x76EC, //CJK UNIFIED IDEOGRAPH - 0xB158: 0x76ED, //CJK UNIFIED IDEOGRAPH - 0xB159: 0x76F0, //CJK UNIFIED IDEOGRAPH - 0xB15A: 0x76F3, //CJK UNIFIED IDEOGRAPH - 0xB15B: 0x76F5, //CJK UNIFIED IDEOGRAPH - 0xB15C: 0x76F6, //CJK UNIFIED IDEOGRAPH - 0xB15D: 0x76F7, //CJK UNIFIED IDEOGRAPH - 0xB15E: 0x76FA, //CJK UNIFIED IDEOGRAPH - 0xB15F: 0x76FB, //CJK UNIFIED IDEOGRAPH - 0xB160: 0x76FD, //CJK UNIFIED IDEOGRAPH - 0xB161: 0x76FF, //CJK UNIFIED IDEOGRAPH - 0xB162: 0x7700, //CJK UNIFIED IDEOGRAPH - 0xB163: 0x7702, //CJK UNIFIED IDEOGRAPH - 0xB164: 0x7703, //CJK UNIFIED IDEOGRAPH - 0xB165: 0x7705, //CJK UNIFIED IDEOGRAPH - 0xB166: 0x7706, //CJK UNIFIED IDEOGRAPH - 0xB167: 0x770A, //CJK UNIFIED IDEOGRAPH - 0xB168: 0x770C, //CJK UNIFIED IDEOGRAPH - 0xB169: 0x770E, //CJK UNIFIED IDEOGRAPH - 0xB16A: 0x770F, //CJK UNIFIED IDEOGRAPH - 0xB16B: 0x7710, //CJK UNIFIED IDEOGRAPH - 0xB16C: 0x7711, //CJK UNIFIED IDEOGRAPH - 0xB16D: 0x7712, //CJK UNIFIED IDEOGRAPH - 0xB16E: 0x7713, //CJK UNIFIED IDEOGRAPH - 0xB16F: 0x7714, //CJK UNIFIED IDEOGRAPH - 0xB170: 0x7715, //CJK UNIFIED IDEOGRAPH - 0xB171: 0x7716, //CJK UNIFIED IDEOGRAPH - 0xB172: 0x7717, //CJK UNIFIED IDEOGRAPH - 0xB173: 0x7718, //CJK UNIFIED IDEOGRAPH - 0xB174: 0x771B, //CJK UNIFIED IDEOGRAPH - 0xB175: 0x771C, //CJK UNIFIED IDEOGRAPH - 0xB176: 0x771D, //CJK UNIFIED IDEOGRAPH - 0xB177: 0x771E, //CJK UNIFIED IDEOGRAPH - 0xB178: 0x7721, //CJK UNIFIED IDEOGRAPH - 0xB179: 0x7723, //CJK UNIFIED IDEOGRAPH - 0xB17A: 0x7724, //CJK UNIFIED IDEOGRAPH - 0xB17B: 0x7725, //CJK UNIFIED IDEOGRAPH - 0xB17C: 0x7727, //CJK UNIFIED IDEOGRAPH - 0xB17D: 0x772A, //CJK UNIFIED IDEOGRAPH - 0xB17E: 0x772B, //CJK UNIFIED IDEOGRAPH - 0xB180: 0x772C, //CJK UNIFIED IDEOGRAPH - 0xB181: 0x772E, //CJK UNIFIED IDEOGRAPH - 0xB182: 0x7730, //CJK UNIFIED IDEOGRAPH - 0xB183: 0x7731, //CJK UNIFIED IDEOGRAPH - 0xB184: 0x7732, //CJK UNIFIED IDEOGRAPH - 0xB185: 0x7733, //CJK UNIFIED IDEOGRAPH - 0xB186: 0x7734, //CJK UNIFIED IDEOGRAPH - 0xB187: 0x7739, //CJK UNIFIED IDEOGRAPH - 0xB188: 0x773B, //CJK UNIFIED IDEOGRAPH - 0xB189: 0x773D, //CJK UNIFIED IDEOGRAPH - 0xB18A: 0x773E, //CJK UNIFIED IDEOGRAPH - 0xB18B: 0x773F, //CJK UNIFIED IDEOGRAPH - 0xB18C: 0x7742, //CJK UNIFIED IDEOGRAPH - 0xB18D: 0x7744, //CJK UNIFIED IDEOGRAPH - 0xB18E: 0x7745, //CJK UNIFIED IDEOGRAPH - 0xB18F: 0x7746, //CJK UNIFIED IDEOGRAPH - 0xB190: 0x7748, //CJK UNIFIED IDEOGRAPH - 0xB191: 0x7749, //CJK UNIFIED IDEOGRAPH - 0xB192: 0x774A, //CJK UNIFIED IDEOGRAPH - 0xB193: 0x774B, //CJK UNIFIED IDEOGRAPH - 0xB194: 0x774C, //CJK UNIFIED IDEOGRAPH - 0xB195: 0x774D, //CJK UNIFIED IDEOGRAPH - 0xB196: 0x774E, //CJK UNIFIED IDEOGRAPH - 0xB197: 0x774F, //CJK UNIFIED IDEOGRAPH - 0xB198: 0x7752, //CJK UNIFIED IDEOGRAPH - 0xB199: 0x7753, //CJK UNIFIED IDEOGRAPH - 0xB19A: 0x7754, //CJK UNIFIED IDEOGRAPH - 0xB19B: 0x7755, //CJK UNIFIED IDEOGRAPH - 0xB19C: 0x7756, //CJK UNIFIED IDEOGRAPH - 0xB19D: 0x7757, //CJK UNIFIED IDEOGRAPH - 0xB19E: 0x7758, //CJK UNIFIED IDEOGRAPH - 0xB19F: 0x7759, //CJK UNIFIED IDEOGRAPH - 0xB1A0: 0x775C, //CJK UNIFIED IDEOGRAPH - 0xB1A1: 0x8584, //CJK UNIFIED IDEOGRAPH - 0xB1A2: 0x96F9, //CJK UNIFIED IDEOGRAPH - 0xB1A3: 0x4FDD, //CJK UNIFIED IDEOGRAPH - 0xB1A4: 0x5821, //CJK UNIFIED IDEOGRAPH - 0xB1A5: 0x9971, //CJK UNIFIED IDEOGRAPH - 0xB1A6: 0x5B9D, //CJK UNIFIED IDEOGRAPH - 0xB1A7: 0x62B1, //CJK UNIFIED IDEOGRAPH - 0xB1A8: 0x62A5, //CJK UNIFIED IDEOGRAPH - 0xB1A9: 0x66B4, //CJK UNIFIED IDEOGRAPH - 0xB1AA: 0x8C79, //CJK UNIFIED IDEOGRAPH - 0xB1AB: 0x9C8D, //CJK UNIFIED IDEOGRAPH - 0xB1AC: 0x7206, //CJK UNIFIED IDEOGRAPH - 0xB1AD: 0x676F, //CJK UNIFIED IDEOGRAPH - 0xB1AE: 0x7891, //CJK UNIFIED IDEOGRAPH - 0xB1AF: 0x60B2, //CJK UNIFIED IDEOGRAPH - 0xB1B0: 0x5351, //CJK UNIFIED IDEOGRAPH - 0xB1B1: 0x5317, //CJK UNIFIED IDEOGRAPH - 0xB1B2: 0x8F88, //CJK UNIFIED IDEOGRAPH - 0xB1B3: 0x80CC, //CJK UNIFIED IDEOGRAPH - 0xB1B4: 0x8D1D, //CJK UNIFIED IDEOGRAPH - 0xB1B5: 0x94A1, //CJK UNIFIED IDEOGRAPH - 0xB1B6: 0x500D, //CJK UNIFIED IDEOGRAPH - 0xB1B7: 0x72C8, //CJK UNIFIED IDEOGRAPH - 0xB1B8: 0x5907, //CJK UNIFIED IDEOGRAPH - 0xB1B9: 0x60EB, //CJK UNIFIED IDEOGRAPH - 0xB1BA: 0x7119, //CJK UNIFIED IDEOGRAPH - 0xB1BB: 0x88AB, //CJK UNIFIED IDEOGRAPH - 0xB1BC: 0x5954, //CJK UNIFIED IDEOGRAPH - 0xB1BD: 0x82EF, //CJK UNIFIED IDEOGRAPH - 0xB1BE: 0x672C, //CJK UNIFIED IDEOGRAPH - 0xB1BF: 0x7B28, //CJK UNIFIED IDEOGRAPH - 0xB1C0: 0x5D29, //CJK UNIFIED IDEOGRAPH - 0xB1C1: 0x7EF7, //CJK UNIFIED IDEOGRAPH - 0xB1C2: 0x752D, //CJK UNIFIED IDEOGRAPH - 0xB1C3: 0x6CF5, //CJK UNIFIED IDEOGRAPH - 0xB1C4: 0x8E66, //CJK UNIFIED IDEOGRAPH - 0xB1C5: 0x8FF8, //CJK UNIFIED IDEOGRAPH - 0xB1C6: 0x903C, //CJK UNIFIED IDEOGRAPH - 0xB1C7: 0x9F3B, //CJK UNIFIED IDEOGRAPH - 0xB1C8: 0x6BD4, //CJK UNIFIED IDEOGRAPH - 0xB1C9: 0x9119, //CJK UNIFIED IDEOGRAPH - 0xB1CA: 0x7B14, //CJK UNIFIED IDEOGRAPH - 0xB1CB: 0x5F7C, //CJK UNIFIED IDEOGRAPH - 0xB1CC: 0x78A7, //CJK UNIFIED IDEOGRAPH - 0xB1CD: 0x84D6, //CJK UNIFIED IDEOGRAPH - 0xB1CE: 0x853D, //CJK UNIFIED IDEOGRAPH - 0xB1CF: 0x6BD5, //CJK UNIFIED IDEOGRAPH - 0xB1D0: 0x6BD9, //CJK UNIFIED IDEOGRAPH - 0xB1D1: 0x6BD6, //CJK UNIFIED IDEOGRAPH - 0xB1D2: 0x5E01, //CJK UNIFIED IDEOGRAPH - 0xB1D3: 0x5E87, //CJK UNIFIED IDEOGRAPH - 0xB1D4: 0x75F9, //CJK UNIFIED IDEOGRAPH - 0xB1D5: 0x95ED, //CJK UNIFIED IDEOGRAPH - 0xB1D6: 0x655D, //CJK UNIFIED IDEOGRAPH - 0xB1D7: 0x5F0A, //CJK UNIFIED IDEOGRAPH - 0xB1D8: 0x5FC5, //CJK UNIFIED IDEOGRAPH - 0xB1D9: 0x8F9F, //CJK UNIFIED IDEOGRAPH - 0xB1DA: 0x58C1, //CJK UNIFIED IDEOGRAPH - 0xB1DB: 0x81C2, //CJK UNIFIED IDEOGRAPH - 0xB1DC: 0x907F, //CJK UNIFIED IDEOGRAPH - 0xB1DD: 0x965B, //CJK UNIFIED IDEOGRAPH - 0xB1DE: 0x97AD, //CJK UNIFIED IDEOGRAPH - 0xB1DF: 0x8FB9, //CJK UNIFIED IDEOGRAPH - 0xB1E0: 0x7F16, //CJK UNIFIED IDEOGRAPH - 0xB1E1: 0x8D2C, //CJK UNIFIED IDEOGRAPH - 0xB1E2: 0x6241, //CJK UNIFIED IDEOGRAPH - 0xB1E3: 0x4FBF, //CJK UNIFIED IDEOGRAPH - 0xB1E4: 0x53D8, //CJK UNIFIED IDEOGRAPH - 0xB1E5: 0x535E, //CJK UNIFIED IDEOGRAPH - 0xB1E6: 0x8FA8, //CJK UNIFIED IDEOGRAPH - 0xB1E7: 0x8FA9, //CJK UNIFIED IDEOGRAPH - 0xB1E8: 0x8FAB, //CJK UNIFIED IDEOGRAPH - 0xB1E9: 0x904D, //CJK UNIFIED IDEOGRAPH - 0xB1EA: 0x6807, //CJK UNIFIED IDEOGRAPH - 0xB1EB: 0x5F6A, //CJK UNIFIED IDEOGRAPH - 0xB1EC: 0x8198, //CJK UNIFIED IDEOGRAPH - 0xB1ED: 0x8868, //CJK UNIFIED IDEOGRAPH - 0xB1EE: 0x9CD6, //CJK UNIFIED IDEOGRAPH - 0xB1EF: 0x618B, //CJK UNIFIED IDEOGRAPH - 0xB1F0: 0x522B, //CJK UNIFIED IDEOGRAPH - 0xB1F1: 0x762A, //CJK UNIFIED IDEOGRAPH - 0xB1F2: 0x5F6C, //CJK UNIFIED IDEOGRAPH - 0xB1F3: 0x658C, //CJK UNIFIED IDEOGRAPH - 0xB1F4: 0x6FD2, //CJK UNIFIED IDEOGRAPH - 0xB1F5: 0x6EE8, //CJK UNIFIED IDEOGRAPH - 0xB1F6: 0x5BBE, //CJK UNIFIED IDEOGRAPH - 0xB1F7: 0x6448, //CJK UNIFIED IDEOGRAPH - 0xB1F8: 0x5175, //CJK UNIFIED IDEOGRAPH - 0xB1F9: 0x51B0, //CJK UNIFIED IDEOGRAPH - 0xB1FA: 0x67C4, //CJK UNIFIED IDEOGRAPH - 0xB1FB: 0x4E19, //CJK UNIFIED IDEOGRAPH - 0xB1FC: 0x79C9, //CJK UNIFIED IDEOGRAPH - 0xB1FD: 0x997C, //CJK UNIFIED IDEOGRAPH - 0xB1FE: 0x70B3, //CJK UNIFIED IDEOGRAPH - 0xB240: 0x775D, //CJK UNIFIED IDEOGRAPH - 0xB241: 0x775E, //CJK UNIFIED IDEOGRAPH - 0xB242: 0x775F, //CJK UNIFIED IDEOGRAPH - 0xB243: 0x7760, //CJK UNIFIED IDEOGRAPH - 0xB244: 0x7764, //CJK UNIFIED IDEOGRAPH - 0xB245: 0x7767, //CJK UNIFIED IDEOGRAPH - 0xB246: 0x7769, //CJK UNIFIED IDEOGRAPH - 0xB247: 0x776A, //CJK UNIFIED IDEOGRAPH - 0xB248: 0x776D, //CJK UNIFIED IDEOGRAPH - 0xB249: 0x776E, //CJK UNIFIED IDEOGRAPH - 0xB24A: 0x776F, //CJK UNIFIED IDEOGRAPH - 0xB24B: 0x7770, //CJK UNIFIED IDEOGRAPH - 0xB24C: 0x7771, //CJK UNIFIED IDEOGRAPH - 0xB24D: 0x7772, //CJK UNIFIED IDEOGRAPH - 0xB24E: 0x7773, //CJK UNIFIED IDEOGRAPH - 0xB24F: 0x7774, //CJK UNIFIED IDEOGRAPH - 0xB250: 0x7775, //CJK UNIFIED IDEOGRAPH - 0xB251: 0x7776, //CJK UNIFIED IDEOGRAPH - 0xB252: 0x7777, //CJK UNIFIED IDEOGRAPH - 0xB253: 0x7778, //CJK UNIFIED IDEOGRAPH - 0xB254: 0x777A, //CJK UNIFIED IDEOGRAPH - 0xB255: 0x777B, //CJK UNIFIED IDEOGRAPH - 0xB256: 0x777C, //CJK UNIFIED IDEOGRAPH - 0xB257: 0x7781, //CJK UNIFIED IDEOGRAPH - 0xB258: 0x7782, //CJK UNIFIED IDEOGRAPH - 0xB259: 0x7783, //CJK UNIFIED IDEOGRAPH - 0xB25A: 0x7786, //CJK UNIFIED IDEOGRAPH - 0xB25B: 0x7787, //CJK UNIFIED IDEOGRAPH - 0xB25C: 0x7788, //CJK UNIFIED IDEOGRAPH - 0xB25D: 0x7789, //CJK UNIFIED IDEOGRAPH - 0xB25E: 0x778A, //CJK UNIFIED IDEOGRAPH - 0xB25F: 0x778B, //CJK UNIFIED IDEOGRAPH - 0xB260: 0x778F, //CJK UNIFIED IDEOGRAPH - 0xB261: 0x7790, //CJK UNIFIED IDEOGRAPH - 0xB262: 0x7793, //CJK UNIFIED IDEOGRAPH - 0xB263: 0x7794, //CJK UNIFIED IDEOGRAPH - 0xB264: 0x7795, //CJK UNIFIED IDEOGRAPH - 0xB265: 0x7796, //CJK UNIFIED IDEOGRAPH - 0xB266: 0x7797, //CJK UNIFIED IDEOGRAPH - 0xB267: 0x7798, //CJK UNIFIED IDEOGRAPH - 0xB268: 0x7799, //CJK UNIFIED IDEOGRAPH - 0xB269: 0x779A, //CJK UNIFIED IDEOGRAPH - 0xB26A: 0x779B, //CJK UNIFIED IDEOGRAPH - 0xB26B: 0x779C, //CJK UNIFIED IDEOGRAPH - 0xB26C: 0x779D, //CJK UNIFIED IDEOGRAPH - 0xB26D: 0x779E, //CJK UNIFIED IDEOGRAPH - 0xB26E: 0x77A1, //CJK UNIFIED IDEOGRAPH - 0xB26F: 0x77A3, //CJK UNIFIED IDEOGRAPH - 0xB270: 0x77A4, //CJK UNIFIED IDEOGRAPH - 0xB271: 0x77A6, //CJK UNIFIED IDEOGRAPH - 0xB272: 0x77A8, //CJK UNIFIED IDEOGRAPH - 0xB273: 0x77AB, //CJK UNIFIED IDEOGRAPH - 0xB274: 0x77AD, //CJK UNIFIED IDEOGRAPH - 0xB275: 0x77AE, //CJK UNIFIED IDEOGRAPH - 0xB276: 0x77AF, //CJK UNIFIED IDEOGRAPH - 0xB277: 0x77B1, //CJK UNIFIED IDEOGRAPH - 0xB278: 0x77B2, //CJK UNIFIED IDEOGRAPH - 0xB279: 0x77B4, //CJK UNIFIED IDEOGRAPH - 0xB27A: 0x77B6, //CJK UNIFIED IDEOGRAPH - 0xB27B: 0x77B7, //CJK UNIFIED IDEOGRAPH - 0xB27C: 0x77B8, //CJK UNIFIED IDEOGRAPH - 0xB27D: 0x77B9, //CJK UNIFIED IDEOGRAPH - 0xB27E: 0x77BA, //CJK UNIFIED IDEOGRAPH - 0xB280: 0x77BC, //CJK UNIFIED IDEOGRAPH - 0xB281: 0x77BE, //CJK UNIFIED IDEOGRAPH - 0xB282: 0x77C0, //CJK UNIFIED IDEOGRAPH - 0xB283: 0x77C1, //CJK UNIFIED IDEOGRAPH - 0xB284: 0x77C2, //CJK UNIFIED IDEOGRAPH - 0xB285: 0x77C3, //CJK UNIFIED IDEOGRAPH - 0xB286: 0x77C4, //CJK UNIFIED IDEOGRAPH - 0xB287: 0x77C5, //CJK UNIFIED IDEOGRAPH - 0xB288: 0x77C6, //CJK UNIFIED IDEOGRAPH - 0xB289: 0x77C7, //CJK UNIFIED IDEOGRAPH - 0xB28A: 0x77C8, //CJK UNIFIED IDEOGRAPH - 0xB28B: 0x77C9, //CJK UNIFIED IDEOGRAPH - 0xB28C: 0x77CA, //CJK UNIFIED IDEOGRAPH - 0xB28D: 0x77CB, //CJK UNIFIED IDEOGRAPH - 0xB28E: 0x77CC, //CJK UNIFIED IDEOGRAPH - 0xB28F: 0x77CE, //CJK UNIFIED IDEOGRAPH - 0xB290: 0x77CF, //CJK UNIFIED IDEOGRAPH - 0xB291: 0x77D0, //CJK UNIFIED IDEOGRAPH - 0xB292: 0x77D1, //CJK UNIFIED IDEOGRAPH - 0xB293: 0x77D2, //CJK UNIFIED IDEOGRAPH - 0xB294: 0x77D3, //CJK UNIFIED IDEOGRAPH - 0xB295: 0x77D4, //CJK UNIFIED IDEOGRAPH - 0xB296: 0x77D5, //CJK UNIFIED IDEOGRAPH - 0xB297: 0x77D6, //CJK UNIFIED IDEOGRAPH - 0xB298: 0x77D8, //CJK UNIFIED IDEOGRAPH - 0xB299: 0x77D9, //CJK UNIFIED IDEOGRAPH - 0xB29A: 0x77DA, //CJK UNIFIED IDEOGRAPH - 0xB29B: 0x77DD, //CJK UNIFIED IDEOGRAPH - 0xB29C: 0x77DE, //CJK UNIFIED IDEOGRAPH - 0xB29D: 0x77DF, //CJK UNIFIED IDEOGRAPH - 0xB29E: 0x77E0, //CJK UNIFIED IDEOGRAPH - 0xB29F: 0x77E1, //CJK UNIFIED IDEOGRAPH - 0xB2A0: 0x77E4, //CJK UNIFIED IDEOGRAPH - 0xB2A1: 0x75C5, //CJK UNIFIED IDEOGRAPH - 0xB2A2: 0x5E76, //CJK UNIFIED IDEOGRAPH - 0xB2A3: 0x73BB, //CJK UNIFIED IDEOGRAPH - 0xB2A4: 0x83E0, //CJK UNIFIED IDEOGRAPH - 0xB2A5: 0x64AD, //CJK UNIFIED IDEOGRAPH - 0xB2A6: 0x62E8, //CJK UNIFIED IDEOGRAPH - 0xB2A7: 0x94B5, //CJK UNIFIED IDEOGRAPH - 0xB2A8: 0x6CE2, //CJK UNIFIED IDEOGRAPH - 0xB2A9: 0x535A, //CJK UNIFIED IDEOGRAPH - 0xB2AA: 0x52C3, //CJK UNIFIED IDEOGRAPH - 0xB2AB: 0x640F, //CJK UNIFIED IDEOGRAPH - 0xB2AC: 0x94C2, //CJK UNIFIED IDEOGRAPH - 0xB2AD: 0x7B94, //CJK UNIFIED IDEOGRAPH - 0xB2AE: 0x4F2F, //CJK UNIFIED IDEOGRAPH - 0xB2AF: 0x5E1B, //CJK UNIFIED IDEOGRAPH - 0xB2B0: 0x8236, //CJK UNIFIED IDEOGRAPH - 0xB2B1: 0x8116, //CJK UNIFIED IDEOGRAPH - 0xB2B2: 0x818A, //CJK UNIFIED IDEOGRAPH - 0xB2B3: 0x6E24, //CJK UNIFIED IDEOGRAPH - 0xB2B4: 0x6CCA, //CJK UNIFIED IDEOGRAPH - 0xB2B5: 0x9A73, //CJK UNIFIED IDEOGRAPH - 0xB2B6: 0x6355, //CJK UNIFIED IDEOGRAPH - 0xB2B7: 0x535C, //CJK UNIFIED IDEOGRAPH - 0xB2B8: 0x54FA, //CJK UNIFIED IDEOGRAPH - 0xB2B9: 0x8865, //CJK UNIFIED IDEOGRAPH - 0xB2BA: 0x57E0, //CJK UNIFIED IDEOGRAPH - 0xB2BB: 0x4E0D, //CJK UNIFIED IDEOGRAPH - 0xB2BC: 0x5E03, //CJK UNIFIED IDEOGRAPH - 0xB2BD: 0x6B65, //CJK UNIFIED IDEOGRAPH - 0xB2BE: 0x7C3F, //CJK UNIFIED IDEOGRAPH - 0xB2BF: 0x90E8, //CJK UNIFIED IDEOGRAPH - 0xB2C0: 0x6016, //CJK UNIFIED IDEOGRAPH - 0xB2C1: 0x64E6, //CJK UNIFIED IDEOGRAPH - 0xB2C2: 0x731C, //CJK UNIFIED IDEOGRAPH - 0xB2C3: 0x88C1, //CJK UNIFIED IDEOGRAPH - 0xB2C4: 0x6750, //CJK UNIFIED IDEOGRAPH - 0xB2C5: 0x624D, //CJK UNIFIED IDEOGRAPH - 0xB2C6: 0x8D22, //CJK UNIFIED IDEOGRAPH - 0xB2C7: 0x776C, //CJK UNIFIED IDEOGRAPH - 0xB2C8: 0x8E29, //CJK UNIFIED IDEOGRAPH - 0xB2C9: 0x91C7, //CJK UNIFIED IDEOGRAPH - 0xB2CA: 0x5F69, //CJK UNIFIED IDEOGRAPH - 0xB2CB: 0x83DC, //CJK UNIFIED IDEOGRAPH - 0xB2CC: 0x8521, //CJK UNIFIED IDEOGRAPH - 0xB2CD: 0x9910, //CJK UNIFIED IDEOGRAPH - 0xB2CE: 0x53C2, //CJK UNIFIED IDEOGRAPH - 0xB2CF: 0x8695, //CJK UNIFIED IDEOGRAPH - 0xB2D0: 0x6B8B, //CJK UNIFIED IDEOGRAPH - 0xB2D1: 0x60ED, //CJK UNIFIED IDEOGRAPH - 0xB2D2: 0x60E8, //CJK UNIFIED IDEOGRAPH - 0xB2D3: 0x707F, //CJK UNIFIED IDEOGRAPH - 0xB2D4: 0x82CD, //CJK UNIFIED IDEOGRAPH - 0xB2D5: 0x8231, //CJK UNIFIED IDEOGRAPH - 0xB2D6: 0x4ED3, //CJK UNIFIED IDEOGRAPH - 0xB2D7: 0x6CA7, //CJK UNIFIED IDEOGRAPH - 0xB2D8: 0x85CF, //CJK UNIFIED IDEOGRAPH - 0xB2D9: 0x64CD, //CJK UNIFIED IDEOGRAPH - 0xB2DA: 0x7CD9, //CJK UNIFIED IDEOGRAPH - 0xB2DB: 0x69FD, //CJK UNIFIED IDEOGRAPH - 0xB2DC: 0x66F9, //CJK UNIFIED IDEOGRAPH - 0xB2DD: 0x8349, //CJK UNIFIED IDEOGRAPH - 0xB2DE: 0x5395, //CJK UNIFIED IDEOGRAPH - 0xB2DF: 0x7B56, //CJK UNIFIED IDEOGRAPH - 0xB2E0: 0x4FA7, //CJK UNIFIED IDEOGRAPH - 0xB2E1: 0x518C, //CJK UNIFIED IDEOGRAPH - 0xB2E2: 0x6D4B, //CJK UNIFIED IDEOGRAPH - 0xB2E3: 0x5C42, //CJK UNIFIED IDEOGRAPH - 0xB2E4: 0x8E6D, //CJK UNIFIED IDEOGRAPH - 0xB2E5: 0x63D2, //CJK UNIFIED IDEOGRAPH - 0xB2E6: 0x53C9, //CJK UNIFIED IDEOGRAPH - 0xB2E7: 0x832C, //CJK UNIFIED IDEOGRAPH - 0xB2E8: 0x8336, //CJK UNIFIED IDEOGRAPH - 0xB2E9: 0x67E5, //CJK UNIFIED IDEOGRAPH - 0xB2EA: 0x78B4, //CJK UNIFIED IDEOGRAPH - 0xB2EB: 0x643D, //CJK UNIFIED IDEOGRAPH - 0xB2EC: 0x5BDF, //CJK UNIFIED IDEOGRAPH - 0xB2ED: 0x5C94, //CJK UNIFIED IDEOGRAPH - 0xB2EE: 0x5DEE, //CJK UNIFIED IDEOGRAPH - 0xB2EF: 0x8BE7, //CJK UNIFIED IDEOGRAPH - 0xB2F0: 0x62C6, //CJK UNIFIED IDEOGRAPH - 0xB2F1: 0x67F4, //CJK UNIFIED IDEOGRAPH - 0xB2F2: 0x8C7A, //CJK UNIFIED IDEOGRAPH - 0xB2F3: 0x6400, //CJK UNIFIED IDEOGRAPH - 0xB2F4: 0x63BA, //CJK UNIFIED IDEOGRAPH - 0xB2F5: 0x8749, //CJK UNIFIED IDEOGRAPH - 0xB2F6: 0x998B, //CJK UNIFIED IDEOGRAPH - 0xB2F7: 0x8C17, //CJK UNIFIED IDEOGRAPH - 0xB2F8: 0x7F20, //CJK UNIFIED IDEOGRAPH - 0xB2F9: 0x94F2, //CJK UNIFIED IDEOGRAPH - 0xB2FA: 0x4EA7, //CJK UNIFIED IDEOGRAPH - 0xB2FB: 0x9610, //CJK UNIFIED IDEOGRAPH - 0xB2FC: 0x98A4, //CJK UNIFIED IDEOGRAPH - 0xB2FD: 0x660C, //CJK UNIFIED IDEOGRAPH - 0xB2FE: 0x7316, //CJK UNIFIED IDEOGRAPH - 0xB340: 0x77E6, //CJK UNIFIED IDEOGRAPH - 0xB341: 0x77E8, //CJK UNIFIED IDEOGRAPH - 0xB342: 0x77EA, //CJK UNIFIED IDEOGRAPH - 0xB343: 0x77EF, //CJK UNIFIED IDEOGRAPH - 0xB344: 0x77F0, //CJK UNIFIED IDEOGRAPH - 0xB345: 0x77F1, //CJK UNIFIED IDEOGRAPH - 0xB346: 0x77F2, //CJK UNIFIED IDEOGRAPH - 0xB347: 0x77F4, //CJK UNIFIED IDEOGRAPH - 0xB348: 0x77F5, //CJK UNIFIED IDEOGRAPH - 0xB349: 0x77F7, //CJK UNIFIED IDEOGRAPH - 0xB34A: 0x77F9, //CJK UNIFIED IDEOGRAPH - 0xB34B: 0x77FA, //CJK UNIFIED IDEOGRAPH - 0xB34C: 0x77FB, //CJK UNIFIED IDEOGRAPH - 0xB34D: 0x77FC, //CJK UNIFIED IDEOGRAPH - 0xB34E: 0x7803, //CJK UNIFIED IDEOGRAPH - 0xB34F: 0x7804, //CJK UNIFIED IDEOGRAPH - 0xB350: 0x7805, //CJK UNIFIED IDEOGRAPH - 0xB351: 0x7806, //CJK UNIFIED IDEOGRAPH - 0xB352: 0x7807, //CJK UNIFIED IDEOGRAPH - 0xB353: 0x7808, //CJK UNIFIED IDEOGRAPH - 0xB354: 0x780A, //CJK UNIFIED IDEOGRAPH - 0xB355: 0x780B, //CJK UNIFIED IDEOGRAPH - 0xB356: 0x780E, //CJK UNIFIED IDEOGRAPH - 0xB357: 0x780F, //CJK UNIFIED IDEOGRAPH - 0xB358: 0x7810, //CJK UNIFIED IDEOGRAPH - 0xB359: 0x7813, //CJK UNIFIED IDEOGRAPH - 0xB35A: 0x7815, //CJK UNIFIED IDEOGRAPH - 0xB35B: 0x7819, //CJK UNIFIED IDEOGRAPH - 0xB35C: 0x781B, //CJK UNIFIED IDEOGRAPH - 0xB35D: 0x781E, //CJK UNIFIED IDEOGRAPH - 0xB35E: 0x7820, //CJK UNIFIED IDEOGRAPH - 0xB35F: 0x7821, //CJK UNIFIED IDEOGRAPH - 0xB360: 0x7822, //CJK UNIFIED IDEOGRAPH - 0xB361: 0x7824, //CJK UNIFIED IDEOGRAPH - 0xB362: 0x7828, //CJK UNIFIED IDEOGRAPH - 0xB363: 0x782A, //CJK UNIFIED IDEOGRAPH - 0xB364: 0x782B, //CJK UNIFIED IDEOGRAPH - 0xB365: 0x782E, //CJK UNIFIED IDEOGRAPH - 0xB366: 0x782F, //CJK UNIFIED IDEOGRAPH - 0xB367: 0x7831, //CJK UNIFIED IDEOGRAPH - 0xB368: 0x7832, //CJK UNIFIED IDEOGRAPH - 0xB369: 0x7833, //CJK UNIFIED IDEOGRAPH - 0xB36A: 0x7835, //CJK UNIFIED IDEOGRAPH - 0xB36B: 0x7836, //CJK UNIFIED IDEOGRAPH - 0xB36C: 0x783D, //CJK UNIFIED IDEOGRAPH - 0xB36D: 0x783F, //CJK UNIFIED IDEOGRAPH - 0xB36E: 0x7841, //CJK UNIFIED IDEOGRAPH - 0xB36F: 0x7842, //CJK UNIFIED IDEOGRAPH - 0xB370: 0x7843, //CJK UNIFIED IDEOGRAPH - 0xB371: 0x7844, //CJK UNIFIED IDEOGRAPH - 0xB372: 0x7846, //CJK UNIFIED IDEOGRAPH - 0xB373: 0x7848, //CJK UNIFIED IDEOGRAPH - 0xB374: 0x7849, //CJK UNIFIED IDEOGRAPH - 0xB375: 0x784A, //CJK UNIFIED IDEOGRAPH - 0xB376: 0x784B, //CJK UNIFIED IDEOGRAPH - 0xB377: 0x784D, //CJK UNIFIED IDEOGRAPH - 0xB378: 0x784F, //CJK UNIFIED IDEOGRAPH - 0xB379: 0x7851, //CJK UNIFIED IDEOGRAPH - 0xB37A: 0x7853, //CJK UNIFIED IDEOGRAPH - 0xB37B: 0x7854, //CJK UNIFIED IDEOGRAPH - 0xB37C: 0x7858, //CJK UNIFIED IDEOGRAPH - 0xB37D: 0x7859, //CJK UNIFIED IDEOGRAPH - 0xB37E: 0x785A, //CJK UNIFIED IDEOGRAPH - 0xB380: 0x785B, //CJK UNIFIED IDEOGRAPH - 0xB381: 0x785C, //CJK UNIFIED IDEOGRAPH - 0xB382: 0x785E, //CJK UNIFIED IDEOGRAPH - 0xB383: 0x785F, //CJK UNIFIED IDEOGRAPH - 0xB384: 0x7860, //CJK UNIFIED IDEOGRAPH - 0xB385: 0x7861, //CJK UNIFIED IDEOGRAPH - 0xB386: 0x7862, //CJK UNIFIED IDEOGRAPH - 0xB387: 0x7863, //CJK UNIFIED IDEOGRAPH - 0xB388: 0x7864, //CJK UNIFIED IDEOGRAPH - 0xB389: 0x7865, //CJK UNIFIED IDEOGRAPH - 0xB38A: 0x7866, //CJK UNIFIED IDEOGRAPH - 0xB38B: 0x7867, //CJK UNIFIED IDEOGRAPH - 0xB38C: 0x7868, //CJK UNIFIED IDEOGRAPH - 0xB38D: 0x7869, //CJK UNIFIED IDEOGRAPH - 0xB38E: 0x786F, //CJK UNIFIED IDEOGRAPH - 0xB38F: 0x7870, //CJK UNIFIED IDEOGRAPH - 0xB390: 0x7871, //CJK UNIFIED IDEOGRAPH - 0xB391: 0x7872, //CJK UNIFIED IDEOGRAPH - 0xB392: 0x7873, //CJK UNIFIED IDEOGRAPH - 0xB393: 0x7874, //CJK UNIFIED IDEOGRAPH - 0xB394: 0x7875, //CJK UNIFIED IDEOGRAPH - 0xB395: 0x7876, //CJK UNIFIED IDEOGRAPH - 0xB396: 0x7878, //CJK UNIFIED IDEOGRAPH - 0xB397: 0x7879, //CJK UNIFIED IDEOGRAPH - 0xB398: 0x787A, //CJK UNIFIED IDEOGRAPH - 0xB399: 0x787B, //CJK UNIFIED IDEOGRAPH - 0xB39A: 0x787D, //CJK UNIFIED IDEOGRAPH - 0xB39B: 0x787E, //CJK UNIFIED IDEOGRAPH - 0xB39C: 0x787F, //CJK UNIFIED IDEOGRAPH - 0xB39D: 0x7880, //CJK UNIFIED IDEOGRAPH - 0xB39E: 0x7881, //CJK UNIFIED IDEOGRAPH - 0xB39F: 0x7882, //CJK UNIFIED IDEOGRAPH - 0xB3A0: 0x7883, //CJK UNIFIED IDEOGRAPH - 0xB3A1: 0x573A, //CJK UNIFIED IDEOGRAPH - 0xB3A2: 0x5C1D, //CJK UNIFIED IDEOGRAPH - 0xB3A3: 0x5E38, //CJK UNIFIED IDEOGRAPH - 0xB3A4: 0x957F, //CJK UNIFIED IDEOGRAPH - 0xB3A5: 0x507F, //CJK UNIFIED IDEOGRAPH - 0xB3A6: 0x80A0, //CJK UNIFIED IDEOGRAPH - 0xB3A7: 0x5382, //CJK UNIFIED IDEOGRAPH - 0xB3A8: 0x655E, //CJK UNIFIED IDEOGRAPH - 0xB3A9: 0x7545, //CJK UNIFIED IDEOGRAPH - 0xB3AA: 0x5531, //CJK UNIFIED IDEOGRAPH - 0xB3AB: 0x5021, //CJK UNIFIED IDEOGRAPH - 0xB3AC: 0x8D85, //CJK UNIFIED IDEOGRAPH - 0xB3AD: 0x6284, //CJK UNIFIED IDEOGRAPH - 0xB3AE: 0x949E, //CJK UNIFIED IDEOGRAPH - 0xB3AF: 0x671D, //CJK UNIFIED IDEOGRAPH - 0xB3B0: 0x5632, //CJK UNIFIED IDEOGRAPH - 0xB3B1: 0x6F6E, //CJK UNIFIED IDEOGRAPH - 0xB3B2: 0x5DE2, //CJK UNIFIED IDEOGRAPH - 0xB3B3: 0x5435, //CJK UNIFIED IDEOGRAPH - 0xB3B4: 0x7092, //CJK UNIFIED IDEOGRAPH - 0xB3B5: 0x8F66, //CJK UNIFIED IDEOGRAPH - 0xB3B6: 0x626F, //CJK UNIFIED IDEOGRAPH - 0xB3B7: 0x64A4, //CJK UNIFIED IDEOGRAPH - 0xB3B8: 0x63A3, //CJK UNIFIED IDEOGRAPH - 0xB3B9: 0x5F7B, //CJK UNIFIED IDEOGRAPH - 0xB3BA: 0x6F88, //CJK UNIFIED IDEOGRAPH - 0xB3BB: 0x90F4, //CJK UNIFIED IDEOGRAPH - 0xB3BC: 0x81E3, //CJK UNIFIED IDEOGRAPH - 0xB3BD: 0x8FB0, //CJK UNIFIED IDEOGRAPH - 0xB3BE: 0x5C18, //CJK UNIFIED IDEOGRAPH - 0xB3BF: 0x6668, //CJK UNIFIED IDEOGRAPH - 0xB3C0: 0x5FF1, //CJK UNIFIED IDEOGRAPH - 0xB3C1: 0x6C89, //CJK UNIFIED IDEOGRAPH - 0xB3C2: 0x9648, //CJK UNIFIED IDEOGRAPH - 0xB3C3: 0x8D81, //CJK UNIFIED IDEOGRAPH - 0xB3C4: 0x886C, //CJK UNIFIED IDEOGRAPH - 0xB3C5: 0x6491, //CJK UNIFIED IDEOGRAPH - 0xB3C6: 0x79F0, //CJK UNIFIED IDEOGRAPH - 0xB3C7: 0x57CE, //CJK UNIFIED IDEOGRAPH - 0xB3C8: 0x6A59, //CJK UNIFIED IDEOGRAPH - 0xB3C9: 0x6210, //CJK UNIFIED IDEOGRAPH - 0xB3CA: 0x5448, //CJK UNIFIED IDEOGRAPH - 0xB3CB: 0x4E58, //CJK UNIFIED IDEOGRAPH - 0xB3CC: 0x7A0B, //CJK UNIFIED IDEOGRAPH - 0xB3CD: 0x60E9, //CJK UNIFIED IDEOGRAPH - 0xB3CE: 0x6F84, //CJK UNIFIED IDEOGRAPH - 0xB3CF: 0x8BDA, //CJK UNIFIED IDEOGRAPH - 0xB3D0: 0x627F, //CJK UNIFIED IDEOGRAPH - 0xB3D1: 0x901E, //CJK UNIFIED IDEOGRAPH - 0xB3D2: 0x9A8B, //CJK UNIFIED IDEOGRAPH - 0xB3D3: 0x79E4, //CJK UNIFIED IDEOGRAPH - 0xB3D4: 0x5403, //CJK UNIFIED IDEOGRAPH - 0xB3D5: 0x75F4, //CJK UNIFIED IDEOGRAPH - 0xB3D6: 0x6301, //CJK UNIFIED IDEOGRAPH - 0xB3D7: 0x5319, //CJK UNIFIED IDEOGRAPH - 0xB3D8: 0x6C60, //CJK UNIFIED IDEOGRAPH - 0xB3D9: 0x8FDF, //CJK UNIFIED IDEOGRAPH - 0xB3DA: 0x5F1B, //CJK UNIFIED IDEOGRAPH - 0xB3DB: 0x9A70, //CJK UNIFIED IDEOGRAPH - 0xB3DC: 0x803B, //CJK UNIFIED IDEOGRAPH - 0xB3DD: 0x9F7F, //CJK UNIFIED IDEOGRAPH - 0xB3DE: 0x4F88, //CJK UNIFIED IDEOGRAPH - 0xB3DF: 0x5C3A, //CJK UNIFIED IDEOGRAPH - 0xB3E0: 0x8D64, //CJK UNIFIED IDEOGRAPH - 0xB3E1: 0x7FC5, //CJK UNIFIED IDEOGRAPH - 0xB3E2: 0x65A5, //CJK UNIFIED IDEOGRAPH - 0xB3E3: 0x70BD, //CJK UNIFIED IDEOGRAPH - 0xB3E4: 0x5145, //CJK UNIFIED IDEOGRAPH - 0xB3E5: 0x51B2, //CJK UNIFIED IDEOGRAPH - 0xB3E6: 0x866B, //CJK UNIFIED IDEOGRAPH - 0xB3E7: 0x5D07, //CJK UNIFIED IDEOGRAPH - 0xB3E8: 0x5BA0, //CJK UNIFIED IDEOGRAPH - 0xB3E9: 0x62BD, //CJK UNIFIED IDEOGRAPH - 0xB3EA: 0x916C, //CJK UNIFIED IDEOGRAPH - 0xB3EB: 0x7574, //CJK UNIFIED IDEOGRAPH - 0xB3EC: 0x8E0C, //CJK UNIFIED IDEOGRAPH - 0xB3ED: 0x7A20, //CJK UNIFIED IDEOGRAPH - 0xB3EE: 0x6101, //CJK UNIFIED IDEOGRAPH - 0xB3EF: 0x7B79, //CJK UNIFIED IDEOGRAPH - 0xB3F0: 0x4EC7, //CJK UNIFIED IDEOGRAPH - 0xB3F1: 0x7EF8, //CJK UNIFIED IDEOGRAPH - 0xB3F2: 0x7785, //CJK UNIFIED IDEOGRAPH - 0xB3F3: 0x4E11, //CJK UNIFIED IDEOGRAPH - 0xB3F4: 0x81ED, //CJK UNIFIED IDEOGRAPH - 0xB3F5: 0x521D, //CJK UNIFIED IDEOGRAPH - 0xB3F6: 0x51FA, //CJK UNIFIED IDEOGRAPH - 0xB3F7: 0x6A71, //CJK UNIFIED IDEOGRAPH - 0xB3F8: 0x53A8, //CJK UNIFIED IDEOGRAPH - 0xB3F9: 0x8E87, //CJK UNIFIED IDEOGRAPH - 0xB3FA: 0x9504, //CJK UNIFIED IDEOGRAPH - 0xB3FB: 0x96CF, //CJK UNIFIED IDEOGRAPH - 0xB3FC: 0x6EC1, //CJK UNIFIED IDEOGRAPH - 0xB3FD: 0x9664, //CJK UNIFIED IDEOGRAPH - 0xB3FE: 0x695A, //CJK UNIFIED IDEOGRAPH - 0xB440: 0x7884, //CJK UNIFIED IDEOGRAPH - 0xB441: 0x7885, //CJK UNIFIED IDEOGRAPH - 0xB442: 0x7886, //CJK UNIFIED IDEOGRAPH - 0xB443: 0x7888, //CJK UNIFIED IDEOGRAPH - 0xB444: 0x788A, //CJK UNIFIED IDEOGRAPH - 0xB445: 0x788B, //CJK UNIFIED IDEOGRAPH - 0xB446: 0x788F, //CJK UNIFIED IDEOGRAPH - 0xB447: 0x7890, //CJK UNIFIED IDEOGRAPH - 0xB448: 0x7892, //CJK UNIFIED IDEOGRAPH - 0xB449: 0x7894, //CJK UNIFIED IDEOGRAPH - 0xB44A: 0x7895, //CJK UNIFIED IDEOGRAPH - 0xB44B: 0x7896, //CJK UNIFIED IDEOGRAPH - 0xB44C: 0x7899, //CJK UNIFIED IDEOGRAPH - 0xB44D: 0x789D, //CJK UNIFIED IDEOGRAPH - 0xB44E: 0x789E, //CJK UNIFIED IDEOGRAPH - 0xB44F: 0x78A0, //CJK UNIFIED IDEOGRAPH - 0xB450: 0x78A2, //CJK UNIFIED IDEOGRAPH - 0xB451: 0x78A4, //CJK UNIFIED IDEOGRAPH - 0xB452: 0x78A6, //CJK UNIFIED IDEOGRAPH - 0xB453: 0x78A8, //CJK UNIFIED IDEOGRAPH - 0xB454: 0x78A9, //CJK UNIFIED IDEOGRAPH - 0xB455: 0x78AA, //CJK UNIFIED IDEOGRAPH - 0xB456: 0x78AB, //CJK UNIFIED IDEOGRAPH - 0xB457: 0x78AC, //CJK UNIFIED IDEOGRAPH - 0xB458: 0x78AD, //CJK UNIFIED IDEOGRAPH - 0xB459: 0x78AE, //CJK UNIFIED IDEOGRAPH - 0xB45A: 0x78AF, //CJK UNIFIED IDEOGRAPH - 0xB45B: 0x78B5, //CJK UNIFIED IDEOGRAPH - 0xB45C: 0x78B6, //CJK UNIFIED IDEOGRAPH - 0xB45D: 0x78B7, //CJK UNIFIED IDEOGRAPH - 0xB45E: 0x78B8, //CJK UNIFIED IDEOGRAPH - 0xB45F: 0x78BA, //CJK UNIFIED IDEOGRAPH - 0xB460: 0x78BB, //CJK UNIFIED IDEOGRAPH - 0xB461: 0x78BC, //CJK UNIFIED IDEOGRAPH - 0xB462: 0x78BD, //CJK UNIFIED IDEOGRAPH - 0xB463: 0x78BF, //CJK UNIFIED IDEOGRAPH - 0xB464: 0x78C0, //CJK UNIFIED IDEOGRAPH - 0xB465: 0x78C2, //CJK UNIFIED IDEOGRAPH - 0xB466: 0x78C3, //CJK UNIFIED IDEOGRAPH - 0xB467: 0x78C4, //CJK UNIFIED IDEOGRAPH - 0xB468: 0x78C6, //CJK UNIFIED IDEOGRAPH - 0xB469: 0x78C7, //CJK UNIFIED IDEOGRAPH - 0xB46A: 0x78C8, //CJK UNIFIED IDEOGRAPH - 0xB46B: 0x78CC, //CJK UNIFIED IDEOGRAPH - 0xB46C: 0x78CD, //CJK UNIFIED IDEOGRAPH - 0xB46D: 0x78CE, //CJK UNIFIED IDEOGRAPH - 0xB46E: 0x78CF, //CJK UNIFIED IDEOGRAPH - 0xB46F: 0x78D1, //CJK UNIFIED IDEOGRAPH - 0xB470: 0x78D2, //CJK UNIFIED IDEOGRAPH - 0xB471: 0x78D3, //CJK UNIFIED IDEOGRAPH - 0xB472: 0x78D6, //CJK UNIFIED IDEOGRAPH - 0xB473: 0x78D7, //CJK UNIFIED IDEOGRAPH - 0xB474: 0x78D8, //CJK UNIFIED IDEOGRAPH - 0xB475: 0x78DA, //CJK UNIFIED IDEOGRAPH - 0xB476: 0x78DB, //CJK UNIFIED IDEOGRAPH - 0xB477: 0x78DC, //CJK UNIFIED IDEOGRAPH - 0xB478: 0x78DD, //CJK UNIFIED IDEOGRAPH - 0xB479: 0x78DE, //CJK UNIFIED IDEOGRAPH - 0xB47A: 0x78DF, //CJK UNIFIED IDEOGRAPH - 0xB47B: 0x78E0, //CJK UNIFIED IDEOGRAPH - 0xB47C: 0x78E1, //CJK UNIFIED IDEOGRAPH - 0xB47D: 0x78E2, //CJK UNIFIED IDEOGRAPH - 0xB47E: 0x78E3, //CJK UNIFIED IDEOGRAPH - 0xB480: 0x78E4, //CJK UNIFIED IDEOGRAPH - 0xB481: 0x78E5, //CJK UNIFIED IDEOGRAPH - 0xB482: 0x78E6, //CJK UNIFIED IDEOGRAPH - 0xB483: 0x78E7, //CJK UNIFIED IDEOGRAPH - 0xB484: 0x78E9, //CJK UNIFIED IDEOGRAPH - 0xB485: 0x78EA, //CJK UNIFIED IDEOGRAPH - 0xB486: 0x78EB, //CJK UNIFIED IDEOGRAPH - 0xB487: 0x78ED, //CJK UNIFIED IDEOGRAPH - 0xB488: 0x78EE, //CJK UNIFIED IDEOGRAPH - 0xB489: 0x78EF, //CJK UNIFIED IDEOGRAPH - 0xB48A: 0x78F0, //CJK UNIFIED IDEOGRAPH - 0xB48B: 0x78F1, //CJK UNIFIED IDEOGRAPH - 0xB48C: 0x78F3, //CJK UNIFIED IDEOGRAPH - 0xB48D: 0x78F5, //CJK UNIFIED IDEOGRAPH - 0xB48E: 0x78F6, //CJK UNIFIED IDEOGRAPH - 0xB48F: 0x78F8, //CJK UNIFIED IDEOGRAPH - 0xB490: 0x78F9, //CJK UNIFIED IDEOGRAPH - 0xB491: 0x78FB, //CJK UNIFIED IDEOGRAPH - 0xB492: 0x78FC, //CJK UNIFIED IDEOGRAPH - 0xB493: 0x78FD, //CJK UNIFIED IDEOGRAPH - 0xB494: 0x78FE, //CJK UNIFIED IDEOGRAPH - 0xB495: 0x78FF, //CJK UNIFIED IDEOGRAPH - 0xB496: 0x7900, //CJK UNIFIED IDEOGRAPH - 0xB497: 0x7902, //CJK UNIFIED IDEOGRAPH - 0xB498: 0x7903, //CJK UNIFIED IDEOGRAPH - 0xB499: 0x7904, //CJK UNIFIED IDEOGRAPH - 0xB49A: 0x7906, //CJK UNIFIED IDEOGRAPH - 0xB49B: 0x7907, //CJK UNIFIED IDEOGRAPH - 0xB49C: 0x7908, //CJK UNIFIED IDEOGRAPH - 0xB49D: 0x7909, //CJK UNIFIED IDEOGRAPH - 0xB49E: 0x790A, //CJK UNIFIED IDEOGRAPH - 0xB49F: 0x790B, //CJK UNIFIED IDEOGRAPH - 0xB4A0: 0x790C, //CJK UNIFIED IDEOGRAPH - 0xB4A1: 0x7840, //CJK UNIFIED IDEOGRAPH - 0xB4A2: 0x50A8, //CJK UNIFIED IDEOGRAPH - 0xB4A3: 0x77D7, //CJK UNIFIED IDEOGRAPH - 0xB4A4: 0x6410, //CJK UNIFIED IDEOGRAPH - 0xB4A5: 0x89E6, //CJK UNIFIED IDEOGRAPH - 0xB4A6: 0x5904, //CJK UNIFIED IDEOGRAPH - 0xB4A7: 0x63E3, //CJK UNIFIED IDEOGRAPH - 0xB4A8: 0x5DDD, //CJK UNIFIED IDEOGRAPH - 0xB4A9: 0x7A7F, //CJK UNIFIED IDEOGRAPH - 0xB4AA: 0x693D, //CJK UNIFIED IDEOGRAPH - 0xB4AB: 0x4F20, //CJK UNIFIED IDEOGRAPH - 0xB4AC: 0x8239, //CJK UNIFIED IDEOGRAPH - 0xB4AD: 0x5598, //CJK UNIFIED IDEOGRAPH - 0xB4AE: 0x4E32, //CJK UNIFIED IDEOGRAPH - 0xB4AF: 0x75AE, //CJK UNIFIED IDEOGRAPH - 0xB4B0: 0x7A97, //CJK UNIFIED IDEOGRAPH - 0xB4B1: 0x5E62, //CJK UNIFIED IDEOGRAPH - 0xB4B2: 0x5E8A, //CJK UNIFIED IDEOGRAPH - 0xB4B3: 0x95EF, //CJK UNIFIED IDEOGRAPH - 0xB4B4: 0x521B, //CJK UNIFIED IDEOGRAPH - 0xB4B5: 0x5439, //CJK UNIFIED IDEOGRAPH - 0xB4B6: 0x708A, //CJK UNIFIED IDEOGRAPH - 0xB4B7: 0x6376, //CJK UNIFIED IDEOGRAPH - 0xB4B8: 0x9524, //CJK UNIFIED IDEOGRAPH - 0xB4B9: 0x5782, //CJK UNIFIED IDEOGRAPH - 0xB4BA: 0x6625, //CJK UNIFIED IDEOGRAPH - 0xB4BB: 0x693F, //CJK UNIFIED IDEOGRAPH - 0xB4BC: 0x9187, //CJK UNIFIED IDEOGRAPH - 0xB4BD: 0x5507, //CJK UNIFIED IDEOGRAPH - 0xB4BE: 0x6DF3, //CJK UNIFIED IDEOGRAPH - 0xB4BF: 0x7EAF, //CJK UNIFIED IDEOGRAPH - 0xB4C0: 0x8822, //CJK UNIFIED IDEOGRAPH - 0xB4C1: 0x6233, //CJK UNIFIED IDEOGRAPH - 0xB4C2: 0x7EF0, //CJK UNIFIED IDEOGRAPH - 0xB4C3: 0x75B5, //CJK UNIFIED IDEOGRAPH - 0xB4C4: 0x8328, //CJK UNIFIED IDEOGRAPH - 0xB4C5: 0x78C1, //CJK UNIFIED IDEOGRAPH - 0xB4C6: 0x96CC, //CJK UNIFIED IDEOGRAPH - 0xB4C7: 0x8F9E, //CJK UNIFIED IDEOGRAPH - 0xB4C8: 0x6148, //CJK UNIFIED IDEOGRAPH - 0xB4C9: 0x74F7, //CJK UNIFIED IDEOGRAPH - 0xB4CA: 0x8BCD, //CJK UNIFIED IDEOGRAPH - 0xB4CB: 0x6B64, //CJK UNIFIED IDEOGRAPH - 0xB4CC: 0x523A, //CJK UNIFIED IDEOGRAPH - 0xB4CD: 0x8D50, //CJK UNIFIED IDEOGRAPH - 0xB4CE: 0x6B21, //CJK UNIFIED IDEOGRAPH - 0xB4CF: 0x806A, //CJK UNIFIED IDEOGRAPH - 0xB4D0: 0x8471, //CJK UNIFIED IDEOGRAPH - 0xB4D1: 0x56F1, //CJK UNIFIED IDEOGRAPH - 0xB4D2: 0x5306, //CJK UNIFIED IDEOGRAPH - 0xB4D3: 0x4ECE, //CJK UNIFIED IDEOGRAPH - 0xB4D4: 0x4E1B, //CJK UNIFIED IDEOGRAPH - 0xB4D5: 0x51D1, //CJK UNIFIED IDEOGRAPH - 0xB4D6: 0x7C97, //CJK UNIFIED IDEOGRAPH - 0xB4D7: 0x918B, //CJK UNIFIED IDEOGRAPH - 0xB4D8: 0x7C07, //CJK UNIFIED IDEOGRAPH - 0xB4D9: 0x4FC3, //CJK UNIFIED IDEOGRAPH - 0xB4DA: 0x8E7F, //CJK UNIFIED IDEOGRAPH - 0xB4DB: 0x7BE1, //CJK UNIFIED IDEOGRAPH - 0xB4DC: 0x7A9C, //CJK UNIFIED IDEOGRAPH - 0xB4DD: 0x6467, //CJK UNIFIED IDEOGRAPH - 0xB4DE: 0x5D14, //CJK UNIFIED IDEOGRAPH - 0xB4DF: 0x50AC, //CJK UNIFIED IDEOGRAPH - 0xB4E0: 0x8106, //CJK UNIFIED IDEOGRAPH - 0xB4E1: 0x7601, //CJK UNIFIED IDEOGRAPH - 0xB4E2: 0x7CB9, //CJK UNIFIED IDEOGRAPH - 0xB4E3: 0x6DEC, //CJK UNIFIED IDEOGRAPH - 0xB4E4: 0x7FE0, //CJK UNIFIED IDEOGRAPH - 0xB4E5: 0x6751, //CJK UNIFIED IDEOGRAPH - 0xB4E6: 0x5B58, //CJK UNIFIED IDEOGRAPH - 0xB4E7: 0x5BF8, //CJK UNIFIED IDEOGRAPH - 0xB4E8: 0x78CB, //CJK UNIFIED IDEOGRAPH - 0xB4E9: 0x64AE, //CJK UNIFIED IDEOGRAPH - 0xB4EA: 0x6413, //CJK UNIFIED IDEOGRAPH - 0xB4EB: 0x63AA, //CJK UNIFIED IDEOGRAPH - 0xB4EC: 0x632B, //CJK UNIFIED IDEOGRAPH - 0xB4ED: 0x9519, //CJK UNIFIED IDEOGRAPH - 0xB4EE: 0x642D, //CJK UNIFIED IDEOGRAPH - 0xB4EF: 0x8FBE, //CJK UNIFIED IDEOGRAPH - 0xB4F0: 0x7B54, //CJK UNIFIED IDEOGRAPH - 0xB4F1: 0x7629, //CJK UNIFIED IDEOGRAPH - 0xB4F2: 0x6253, //CJK UNIFIED IDEOGRAPH - 0xB4F3: 0x5927, //CJK UNIFIED IDEOGRAPH - 0xB4F4: 0x5446, //CJK UNIFIED IDEOGRAPH - 0xB4F5: 0x6B79, //CJK UNIFIED IDEOGRAPH - 0xB4F6: 0x50A3, //CJK UNIFIED IDEOGRAPH - 0xB4F7: 0x6234, //CJK UNIFIED IDEOGRAPH - 0xB4F8: 0x5E26, //CJK UNIFIED IDEOGRAPH - 0xB4F9: 0x6B86, //CJK UNIFIED IDEOGRAPH - 0xB4FA: 0x4EE3, //CJK UNIFIED IDEOGRAPH - 0xB4FB: 0x8D37, //CJK UNIFIED IDEOGRAPH - 0xB4FC: 0x888B, //CJK UNIFIED IDEOGRAPH - 0xB4FD: 0x5F85, //CJK UNIFIED IDEOGRAPH - 0xB4FE: 0x902E, //CJK UNIFIED IDEOGRAPH - 0xB540: 0x790D, //CJK UNIFIED IDEOGRAPH - 0xB541: 0x790E, //CJK UNIFIED IDEOGRAPH - 0xB542: 0x790F, //CJK UNIFIED IDEOGRAPH - 0xB543: 0x7910, //CJK UNIFIED IDEOGRAPH - 0xB544: 0x7911, //CJK UNIFIED IDEOGRAPH - 0xB545: 0x7912, //CJK UNIFIED IDEOGRAPH - 0xB546: 0x7914, //CJK UNIFIED IDEOGRAPH - 0xB547: 0x7915, //CJK UNIFIED IDEOGRAPH - 0xB548: 0x7916, //CJK UNIFIED IDEOGRAPH - 0xB549: 0x7917, //CJK UNIFIED IDEOGRAPH - 0xB54A: 0x7918, //CJK UNIFIED IDEOGRAPH - 0xB54B: 0x7919, //CJK UNIFIED IDEOGRAPH - 0xB54C: 0x791A, //CJK UNIFIED IDEOGRAPH - 0xB54D: 0x791B, //CJK UNIFIED IDEOGRAPH - 0xB54E: 0x791C, //CJK UNIFIED IDEOGRAPH - 0xB54F: 0x791D, //CJK UNIFIED IDEOGRAPH - 0xB550: 0x791F, //CJK UNIFIED IDEOGRAPH - 0xB551: 0x7920, //CJK UNIFIED IDEOGRAPH - 0xB552: 0x7921, //CJK UNIFIED IDEOGRAPH - 0xB553: 0x7922, //CJK UNIFIED IDEOGRAPH - 0xB554: 0x7923, //CJK UNIFIED IDEOGRAPH - 0xB555: 0x7925, //CJK UNIFIED IDEOGRAPH - 0xB556: 0x7926, //CJK UNIFIED IDEOGRAPH - 0xB557: 0x7927, //CJK UNIFIED IDEOGRAPH - 0xB558: 0x7928, //CJK UNIFIED IDEOGRAPH - 0xB559: 0x7929, //CJK UNIFIED IDEOGRAPH - 0xB55A: 0x792A, //CJK UNIFIED IDEOGRAPH - 0xB55B: 0x792B, //CJK UNIFIED IDEOGRAPH - 0xB55C: 0x792C, //CJK UNIFIED IDEOGRAPH - 0xB55D: 0x792D, //CJK UNIFIED IDEOGRAPH - 0xB55E: 0x792E, //CJK UNIFIED IDEOGRAPH - 0xB55F: 0x792F, //CJK UNIFIED IDEOGRAPH - 0xB560: 0x7930, //CJK UNIFIED IDEOGRAPH - 0xB561: 0x7931, //CJK UNIFIED IDEOGRAPH - 0xB562: 0x7932, //CJK UNIFIED IDEOGRAPH - 0xB563: 0x7933, //CJK UNIFIED IDEOGRAPH - 0xB564: 0x7935, //CJK UNIFIED IDEOGRAPH - 0xB565: 0x7936, //CJK UNIFIED IDEOGRAPH - 0xB566: 0x7937, //CJK UNIFIED IDEOGRAPH - 0xB567: 0x7938, //CJK UNIFIED IDEOGRAPH - 0xB568: 0x7939, //CJK UNIFIED IDEOGRAPH - 0xB569: 0x793D, //CJK UNIFIED IDEOGRAPH - 0xB56A: 0x793F, //CJK UNIFIED IDEOGRAPH - 0xB56B: 0x7942, //CJK UNIFIED IDEOGRAPH - 0xB56C: 0x7943, //CJK UNIFIED IDEOGRAPH - 0xB56D: 0x7944, //CJK UNIFIED IDEOGRAPH - 0xB56E: 0x7945, //CJK UNIFIED IDEOGRAPH - 0xB56F: 0x7947, //CJK UNIFIED IDEOGRAPH - 0xB570: 0x794A, //CJK UNIFIED IDEOGRAPH - 0xB571: 0x794B, //CJK UNIFIED IDEOGRAPH - 0xB572: 0x794C, //CJK UNIFIED IDEOGRAPH - 0xB573: 0x794D, //CJK UNIFIED IDEOGRAPH - 0xB574: 0x794E, //CJK UNIFIED IDEOGRAPH - 0xB575: 0x794F, //CJK UNIFIED IDEOGRAPH - 0xB576: 0x7950, //CJK UNIFIED IDEOGRAPH - 0xB577: 0x7951, //CJK UNIFIED IDEOGRAPH - 0xB578: 0x7952, //CJK UNIFIED IDEOGRAPH - 0xB579: 0x7954, //CJK UNIFIED IDEOGRAPH - 0xB57A: 0x7955, //CJK UNIFIED IDEOGRAPH - 0xB57B: 0x7958, //CJK UNIFIED IDEOGRAPH - 0xB57C: 0x7959, //CJK UNIFIED IDEOGRAPH - 0xB57D: 0x7961, //CJK UNIFIED IDEOGRAPH - 0xB57E: 0x7963, //CJK UNIFIED IDEOGRAPH - 0xB580: 0x7964, //CJK UNIFIED IDEOGRAPH - 0xB581: 0x7966, //CJK UNIFIED IDEOGRAPH - 0xB582: 0x7969, //CJK UNIFIED IDEOGRAPH - 0xB583: 0x796A, //CJK UNIFIED IDEOGRAPH - 0xB584: 0x796B, //CJK UNIFIED IDEOGRAPH - 0xB585: 0x796C, //CJK UNIFIED IDEOGRAPH - 0xB586: 0x796E, //CJK UNIFIED IDEOGRAPH - 0xB587: 0x7970, //CJK UNIFIED IDEOGRAPH - 0xB588: 0x7971, //CJK UNIFIED IDEOGRAPH - 0xB589: 0x7972, //CJK UNIFIED IDEOGRAPH - 0xB58A: 0x7973, //CJK UNIFIED IDEOGRAPH - 0xB58B: 0x7974, //CJK UNIFIED IDEOGRAPH - 0xB58C: 0x7975, //CJK UNIFIED IDEOGRAPH - 0xB58D: 0x7976, //CJK UNIFIED IDEOGRAPH - 0xB58E: 0x7979, //CJK UNIFIED IDEOGRAPH - 0xB58F: 0x797B, //CJK UNIFIED IDEOGRAPH - 0xB590: 0x797C, //CJK UNIFIED IDEOGRAPH - 0xB591: 0x797D, //CJK UNIFIED IDEOGRAPH - 0xB592: 0x797E, //CJK UNIFIED IDEOGRAPH - 0xB593: 0x797F, //CJK UNIFIED IDEOGRAPH - 0xB594: 0x7982, //CJK UNIFIED IDEOGRAPH - 0xB595: 0x7983, //CJK UNIFIED IDEOGRAPH - 0xB596: 0x7986, //CJK UNIFIED IDEOGRAPH - 0xB597: 0x7987, //CJK UNIFIED IDEOGRAPH - 0xB598: 0x7988, //CJK UNIFIED IDEOGRAPH - 0xB599: 0x7989, //CJK UNIFIED IDEOGRAPH - 0xB59A: 0x798B, //CJK UNIFIED IDEOGRAPH - 0xB59B: 0x798C, //CJK UNIFIED IDEOGRAPH - 0xB59C: 0x798D, //CJK UNIFIED IDEOGRAPH - 0xB59D: 0x798E, //CJK UNIFIED IDEOGRAPH - 0xB59E: 0x7990, //CJK UNIFIED IDEOGRAPH - 0xB59F: 0x7991, //CJK UNIFIED IDEOGRAPH - 0xB5A0: 0x7992, //CJK UNIFIED IDEOGRAPH - 0xB5A1: 0x6020, //CJK UNIFIED IDEOGRAPH - 0xB5A2: 0x803D, //CJK UNIFIED IDEOGRAPH - 0xB5A3: 0x62C5, //CJK UNIFIED IDEOGRAPH - 0xB5A4: 0x4E39, //CJK UNIFIED IDEOGRAPH - 0xB5A5: 0x5355, //CJK UNIFIED IDEOGRAPH - 0xB5A6: 0x90F8, //CJK UNIFIED IDEOGRAPH - 0xB5A7: 0x63B8, //CJK UNIFIED IDEOGRAPH - 0xB5A8: 0x80C6, //CJK UNIFIED IDEOGRAPH - 0xB5A9: 0x65E6, //CJK UNIFIED IDEOGRAPH - 0xB5AA: 0x6C2E, //CJK UNIFIED IDEOGRAPH - 0xB5AB: 0x4F46, //CJK UNIFIED IDEOGRAPH - 0xB5AC: 0x60EE, //CJK UNIFIED IDEOGRAPH - 0xB5AD: 0x6DE1, //CJK UNIFIED IDEOGRAPH - 0xB5AE: 0x8BDE, //CJK UNIFIED IDEOGRAPH - 0xB5AF: 0x5F39, //CJK UNIFIED IDEOGRAPH - 0xB5B0: 0x86CB, //CJK UNIFIED IDEOGRAPH - 0xB5B1: 0x5F53, //CJK UNIFIED IDEOGRAPH - 0xB5B2: 0x6321, //CJK UNIFIED IDEOGRAPH - 0xB5B3: 0x515A, //CJK UNIFIED IDEOGRAPH - 0xB5B4: 0x8361, //CJK UNIFIED IDEOGRAPH - 0xB5B5: 0x6863, //CJK UNIFIED IDEOGRAPH - 0xB5B6: 0x5200, //CJK UNIFIED IDEOGRAPH - 0xB5B7: 0x6363, //CJK UNIFIED IDEOGRAPH - 0xB5B8: 0x8E48, //CJK UNIFIED IDEOGRAPH - 0xB5B9: 0x5012, //CJK UNIFIED IDEOGRAPH - 0xB5BA: 0x5C9B, //CJK UNIFIED IDEOGRAPH - 0xB5BB: 0x7977, //CJK UNIFIED IDEOGRAPH - 0xB5BC: 0x5BFC, //CJK UNIFIED IDEOGRAPH - 0xB5BD: 0x5230, //CJK UNIFIED IDEOGRAPH - 0xB5BE: 0x7A3B, //CJK UNIFIED IDEOGRAPH - 0xB5BF: 0x60BC, //CJK UNIFIED IDEOGRAPH - 0xB5C0: 0x9053, //CJK UNIFIED IDEOGRAPH - 0xB5C1: 0x76D7, //CJK UNIFIED IDEOGRAPH - 0xB5C2: 0x5FB7, //CJK UNIFIED IDEOGRAPH - 0xB5C3: 0x5F97, //CJK UNIFIED IDEOGRAPH - 0xB5C4: 0x7684, //CJK UNIFIED IDEOGRAPH - 0xB5C5: 0x8E6C, //CJK UNIFIED IDEOGRAPH - 0xB5C6: 0x706F, //CJK UNIFIED IDEOGRAPH - 0xB5C7: 0x767B, //CJK UNIFIED IDEOGRAPH - 0xB5C8: 0x7B49, //CJK UNIFIED IDEOGRAPH - 0xB5C9: 0x77AA, //CJK UNIFIED IDEOGRAPH - 0xB5CA: 0x51F3, //CJK UNIFIED IDEOGRAPH - 0xB5CB: 0x9093, //CJK UNIFIED IDEOGRAPH - 0xB5CC: 0x5824, //CJK UNIFIED IDEOGRAPH - 0xB5CD: 0x4F4E, //CJK UNIFIED IDEOGRAPH - 0xB5CE: 0x6EF4, //CJK UNIFIED IDEOGRAPH - 0xB5CF: 0x8FEA, //CJK UNIFIED IDEOGRAPH - 0xB5D0: 0x654C, //CJK UNIFIED IDEOGRAPH - 0xB5D1: 0x7B1B, //CJK UNIFIED IDEOGRAPH - 0xB5D2: 0x72C4, //CJK UNIFIED IDEOGRAPH - 0xB5D3: 0x6DA4, //CJK UNIFIED IDEOGRAPH - 0xB5D4: 0x7FDF, //CJK UNIFIED IDEOGRAPH - 0xB5D5: 0x5AE1, //CJK UNIFIED IDEOGRAPH - 0xB5D6: 0x62B5, //CJK UNIFIED IDEOGRAPH - 0xB5D7: 0x5E95, //CJK UNIFIED IDEOGRAPH - 0xB5D8: 0x5730, //CJK UNIFIED IDEOGRAPH - 0xB5D9: 0x8482, //CJK UNIFIED IDEOGRAPH - 0xB5DA: 0x7B2C, //CJK UNIFIED IDEOGRAPH - 0xB5DB: 0x5E1D, //CJK UNIFIED IDEOGRAPH - 0xB5DC: 0x5F1F, //CJK UNIFIED IDEOGRAPH - 0xB5DD: 0x9012, //CJK UNIFIED IDEOGRAPH - 0xB5DE: 0x7F14, //CJK UNIFIED IDEOGRAPH - 0xB5DF: 0x98A0, //CJK UNIFIED IDEOGRAPH - 0xB5E0: 0x6382, //CJK UNIFIED IDEOGRAPH - 0xB5E1: 0x6EC7, //CJK UNIFIED IDEOGRAPH - 0xB5E2: 0x7898, //CJK UNIFIED IDEOGRAPH - 0xB5E3: 0x70B9, //CJK UNIFIED IDEOGRAPH - 0xB5E4: 0x5178, //CJK UNIFIED IDEOGRAPH - 0xB5E5: 0x975B, //CJK UNIFIED IDEOGRAPH - 0xB5E6: 0x57AB, //CJK UNIFIED IDEOGRAPH - 0xB5E7: 0x7535, //CJK UNIFIED IDEOGRAPH - 0xB5E8: 0x4F43, //CJK UNIFIED IDEOGRAPH - 0xB5E9: 0x7538, //CJK UNIFIED IDEOGRAPH - 0xB5EA: 0x5E97, //CJK UNIFIED IDEOGRAPH - 0xB5EB: 0x60E6, //CJK UNIFIED IDEOGRAPH - 0xB5EC: 0x5960, //CJK UNIFIED IDEOGRAPH - 0xB5ED: 0x6DC0, //CJK UNIFIED IDEOGRAPH - 0xB5EE: 0x6BBF, //CJK UNIFIED IDEOGRAPH - 0xB5EF: 0x7889, //CJK UNIFIED IDEOGRAPH - 0xB5F0: 0x53FC, //CJK UNIFIED IDEOGRAPH - 0xB5F1: 0x96D5, //CJK UNIFIED IDEOGRAPH - 0xB5F2: 0x51CB, //CJK UNIFIED IDEOGRAPH - 0xB5F3: 0x5201, //CJK UNIFIED IDEOGRAPH - 0xB5F4: 0x6389, //CJK UNIFIED IDEOGRAPH - 0xB5F5: 0x540A, //CJK UNIFIED IDEOGRAPH - 0xB5F6: 0x9493, //CJK UNIFIED IDEOGRAPH - 0xB5F7: 0x8C03, //CJK UNIFIED IDEOGRAPH - 0xB5F8: 0x8DCC, //CJK UNIFIED IDEOGRAPH - 0xB5F9: 0x7239, //CJK UNIFIED IDEOGRAPH - 0xB5FA: 0x789F, //CJK UNIFIED IDEOGRAPH - 0xB5FB: 0x8776, //CJK UNIFIED IDEOGRAPH - 0xB5FC: 0x8FED, //CJK UNIFIED IDEOGRAPH - 0xB5FD: 0x8C0D, //CJK UNIFIED IDEOGRAPH - 0xB5FE: 0x53E0, //CJK UNIFIED IDEOGRAPH - 0xB640: 0x7993, //CJK UNIFIED IDEOGRAPH - 0xB641: 0x7994, //CJK UNIFIED IDEOGRAPH - 0xB642: 0x7995, //CJK UNIFIED IDEOGRAPH - 0xB643: 0x7996, //CJK UNIFIED IDEOGRAPH - 0xB644: 0x7997, //CJK UNIFIED IDEOGRAPH - 0xB645: 0x7998, //CJK UNIFIED IDEOGRAPH - 0xB646: 0x7999, //CJK UNIFIED IDEOGRAPH - 0xB647: 0x799B, //CJK UNIFIED IDEOGRAPH - 0xB648: 0x799C, //CJK UNIFIED IDEOGRAPH - 0xB649: 0x799D, //CJK UNIFIED IDEOGRAPH - 0xB64A: 0x799E, //CJK UNIFIED IDEOGRAPH - 0xB64B: 0x799F, //CJK UNIFIED IDEOGRAPH - 0xB64C: 0x79A0, //CJK UNIFIED IDEOGRAPH - 0xB64D: 0x79A1, //CJK UNIFIED IDEOGRAPH - 0xB64E: 0x79A2, //CJK UNIFIED IDEOGRAPH - 0xB64F: 0x79A3, //CJK UNIFIED IDEOGRAPH - 0xB650: 0x79A4, //CJK UNIFIED IDEOGRAPH - 0xB651: 0x79A5, //CJK UNIFIED IDEOGRAPH - 0xB652: 0x79A6, //CJK UNIFIED IDEOGRAPH - 0xB653: 0x79A8, //CJK UNIFIED IDEOGRAPH - 0xB654: 0x79A9, //CJK UNIFIED IDEOGRAPH - 0xB655: 0x79AA, //CJK UNIFIED IDEOGRAPH - 0xB656: 0x79AB, //CJK UNIFIED IDEOGRAPH - 0xB657: 0x79AC, //CJK UNIFIED IDEOGRAPH - 0xB658: 0x79AD, //CJK UNIFIED IDEOGRAPH - 0xB659: 0x79AE, //CJK UNIFIED IDEOGRAPH - 0xB65A: 0x79AF, //CJK UNIFIED IDEOGRAPH - 0xB65B: 0x79B0, //CJK UNIFIED IDEOGRAPH - 0xB65C: 0x79B1, //CJK UNIFIED IDEOGRAPH - 0xB65D: 0x79B2, //CJK UNIFIED IDEOGRAPH - 0xB65E: 0x79B4, //CJK UNIFIED IDEOGRAPH - 0xB65F: 0x79B5, //CJK UNIFIED IDEOGRAPH - 0xB660: 0x79B6, //CJK UNIFIED IDEOGRAPH - 0xB661: 0x79B7, //CJK UNIFIED IDEOGRAPH - 0xB662: 0x79B8, //CJK UNIFIED IDEOGRAPH - 0xB663: 0x79BC, //CJK UNIFIED IDEOGRAPH - 0xB664: 0x79BF, //CJK UNIFIED IDEOGRAPH - 0xB665: 0x79C2, //CJK UNIFIED IDEOGRAPH - 0xB666: 0x79C4, //CJK UNIFIED IDEOGRAPH - 0xB667: 0x79C5, //CJK UNIFIED IDEOGRAPH - 0xB668: 0x79C7, //CJK UNIFIED IDEOGRAPH - 0xB669: 0x79C8, //CJK UNIFIED IDEOGRAPH - 0xB66A: 0x79CA, //CJK UNIFIED IDEOGRAPH - 0xB66B: 0x79CC, //CJK UNIFIED IDEOGRAPH - 0xB66C: 0x79CE, //CJK UNIFIED IDEOGRAPH - 0xB66D: 0x79CF, //CJK UNIFIED IDEOGRAPH - 0xB66E: 0x79D0, //CJK UNIFIED IDEOGRAPH - 0xB66F: 0x79D3, //CJK UNIFIED IDEOGRAPH - 0xB670: 0x79D4, //CJK UNIFIED IDEOGRAPH - 0xB671: 0x79D6, //CJK UNIFIED IDEOGRAPH - 0xB672: 0x79D7, //CJK UNIFIED IDEOGRAPH - 0xB673: 0x79D9, //CJK UNIFIED IDEOGRAPH - 0xB674: 0x79DA, //CJK UNIFIED IDEOGRAPH - 0xB675: 0x79DB, //CJK UNIFIED IDEOGRAPH - 0xB676: 0x79DC, //CJK UNIFIED IDEOGRAPH - 0xB677: 0x79DD, //CJK UNIFIED IDEOGRAPH - 0xB678: 0x79DE, //CJK UNIFIED IDEOGRAPH - 0xB679: 0x79E0, //CJK UNIFIED IDEOGRAPH - 0xB67A: 0x79E1, //CJK UNIFIED IDEOGRAPH - 0xB67B: 0x79E2, //CJK UNIFIED IDEOGRAPH - 0xB67C: 0x79E5, //CJK UNIFIED IDEOGRAPH - 0xB67D: 0x79E8, //CJK UNIFIED IDEOGRAPH - 0xB67E: 0x79EA, //CJK UNIFIED IDEOGRAPH - 0xB680: 0x79EC, //CJK UNIFIED IDEOGRAPH - 0xB681: 0x79EE, //CJK UNIFIED IDEOGRAPH - 0xB682: 0x79F1, //CJK UNIFIED IDEOGRAPH - 0xB683: 0x79F2, //CJK UNIFIED IDEOGRAPH - 0xB684: 0x79F3, //CJK UNIFIED IDEOGRAPH - 0xB685: 0x79F4, //CJK UNIFIED IDEOGRAPH - 0xB686: 0x79F5, //CJK UNIFIED IDEOGRAPH - 0xB687: 0x79F6, //CJK UNIFIED IDEOGRAPH - 0xB688: 0x79F7, //CJK UNIFIED IDEOGRAPH - 0xB689: 0x79F9, //CJK UNIFIED IDEOGRAPH - 0xB68A: 0x79FA, //CJK UNIFIED IDEOGRAPH - 0xB68B: 0x79FC, //CJK UNIFIED IDEOGRAPH - 0xB68C: 0x79FE, //CJK UNIFIED IDEOGRAPH - 0xB68D: 0x79FF, //CJK UNIFIED IDEOGRAPH - 0xB68E: 0x7A01, //CJK UNIFIED IDEOGRAPH - 0xB68F: 0x7A04, //CJK UNIFIED IDEOGRAPH - 0xB690: 0x7A05, //CJK UNIFIED IDEOGRAPH - 0xB691: 0x7A07, //CJK UNIFIED IDEOGRAPH - 0xB692: 0x7A08, //CJK UNIFIED IDEOGRAPH - 0xB693: 0x7A09, //CJK UNIFIED IDEOGRAPH - 0xB694: 0x7A0A, //CJK UNIFIED IDEOGRAPH - 0xB695: 0x7A0C, //CJK UNIFIED IDEOGRAPH - 0xB696: 0x7A0F, //CJK UNIFIED IDEOGRAPH - 0xB697: 0x7A10, //CJK UNIFIED IDEOGRAPH - 0xB698: 0x7A11, //CJK UNIFIED IDEOGRAPH - 0xB699: 0x7A12, //CJK UNIFIED IDEOGRAPH - 0xB69A: 0x7A13, //CJK UNIFIED IDEOGRAPH - 0xB69B: 0x7A15, //CJK UNIFIED IDEOGRAPH - 0xB69C: 0x7A16, //CJK UNIFIED IDEOGRAPH - 0xB69D: 0x7A18, //CJK UNIFIED IDEOGRAPH - 0xB69E: 0x7A19, //CJK UNIFIED IDEOGRAPH - 0xB69F: 0x7A1B, //CJK UNIFIED IDEOGRAPH - 0xB6A0: 0x7A1C, //CJK UNIFIED IDEOGRAPH - 0xB6A1: 0x4E01, //CJK UNIFIED IDEOGRAPH - 0xB6A2: 0x76EF, //CJK UNIFIED IDEOGRAPH - 0xB6A3: 0x53EE, //CJK UNIFIED IDEOGRAPH - 0xB6A4: 0x9489, //CJK UNIFIED IDEOGRAPH - 0xB6A5: 0x9876, //CJK UNIFIED IDEOGRAPH - 0xB6A6: 0x9F0E, //CJK UNIFIED IDEOGRAPH - 0xB6A7: 0x952D, //CJK UNIFIED IDEOGRAPH - 0xB6A8: 0x5B9A, //CJK UNIFIED IDEOGRAPH - 0xB6A9: 0x8BA2, //CJK UNIFIED IDEOGRAPH - 0xB6AA: 0x4E22, //CJK UNIFIED IDEOGRAPH - 0xB6AB: 0x4E1C, //CJK UNIFIED IDEOGRAPH - 0xB6AC: 0x51AC, //CJK UNIFIED IDEOGRAPH - 0xB6AD: 0x8463, //CJK UNIFIED IDEOGRAPH - 0xB6AE: 0x61C2, //CJK UNIFIED IDEOGRAPH - 0xB6AF: 0x52A8, //CJK UNIFIED IDEOGRAPH - 0xB6B0: 0x680B, //CJK UNIFIED IDEOGRAPH - 0xB6B1: 0x4F97, //CJK UNIFIED IDEOGRAPH - 0xB6B2: 0x606B, //CJK UNIFIED IDEOGRAPH - 0xB6B3: 0x51BB, //CJK UNIFIED IDEOGRAPH - 0xB6B4: 0x6D1E, //CJK UNIFIED IDEOGRAPH - 0xB6B5: 0x515C, //CJK UNIFIED IDEOGRAPH - 0xB6B6: 0x6296, //CJK UNIFIED IDEOGRAPH - 0xB6B7: 0x6597, //CJK UNIFIED IDEOGRAPH - 0xB6B8: 0x9661, //CJK UNIFIED IDEOGRAPH - 0xB6B9: 0x8C46, //CJK UNIFIED IDEOGRAPH - 0xB6BA: 0x9017, //CJK UNIFIED IDEOGRAPH - 0xB6BB: 0x75D8, //CJK UNIFIED IDEOGRAPH - 0xB6BC: 0x90FD, //CJK UNIFIED IDEOGRAPH - 0xB6BD: 0x7763, //CJK UNIFIED IDEOGRAPH - 0xB6BE: 0x6BD2, //CJK UNIFIED IDEOGRAPH - 0xB6BF: 0x728A, //CJK UNIFIED IDEOGRAPH - 0xB6C0: 0x72EC, //CJK UNIFIED IDEOGRAPH - 0xB6C1: 0x8BFB, //CJK UNIFIED IDEOGRAPH - 0xB6C2: 0x5835, //CJK UNIFIED IDEOGRAPH - 0xB6C3: 0x7779, //CJK UNIFIED IDEOGRAPH - 0xB6C4: 0x8D4C, //CJK UNIFIED IDEOGRAPH - 0xB6C5: 0x675C, //CJK UNIFIED IDEOGRAPH - 0xB6C6: 0x9540, //CJK UNIFIED IDEOGRAPH - 0xB6C7: 0x809A, //CJK UNIFIED IDEOGRAPH - 0xB6C8: 0x5EA6, //CJK UNIFIED IDEOGRAPH - 0xB6C9: 0x6E21, //CJK UNIFIED IDEOGRAPH - 0xB6CA: 0x5992, //CJK UNIFIED IDEOGRAPH - 0xB6CB: 0x7AEF, //CJK UNIFIED IDEOGRAPH - 0xB6CC: 0x77ED, //CJK UNIFIED IDEOGRAPH - 0xB6CD: 0x953B, //CJK UNIFIED IDEOGRAPH - 0xB6CE: 0x6BB5, //CJK UNIFIED IDEOGRAPH - 0xB6CF: 0x65AD, //CJK UNIFIED IDEOGRAPH - 0xB6D0: 0x7F0E, //CJK UNIFIED IDEOGRAPH - 0xB6D1: 0x5806, //CJK UNIFIED IDEOGRAPH - 0xB6D2: 0x5151, //CJK UNIFIED IDEOGRAPH - 0xB6D3: 0x961F, //CJK UNIFIED IDEOGRAPH - 0xB6D4: 0x5BF9, //CJK UNIFIED IDEOGRAPH - 0xB6D5: 0x58A9, //CJK UNIFIED IDEOGRAPH - 0xB6D6: 0x5428, //CJK UNIFIED IDEOGRAPH - 0xB6D7: 0x8E72, //CJK UNIFIED IDEOGRAPH - 0xB6D8: 0x6566, //CJK UNIFIED IDEOGRAPH - 0xB6D9: 0x987F, //CJK UNIFIED IDEOGRAPH - 0xB6DA: 0x56E4, //CJK UNIFIED IDEOGRAPH - 0xB6DB: 0x949D, //CJK UNIFIED IDEOGRAPH - 0xB6DC: 0x76FE, //CJK UNIFIED IDEOGRAPH - 0xB6DD: 0x9041, //CJK UNIFIED IDEOGRAPH - 0xB6DE: 0x6387, //CJK UNIFIED IDEOGRAPH - 0xB6DF: 0x54C6, //CJK UNIFIED IDEOGRAPH - 0xB6E0: 0x591A, //CJK UNIFIED IDEOGRAPH - 0xB6E1: 0x593A, //CJK UNIFIED IDEOGRAPH - 0xB6E2: 0x579B, //CJK UNIFIED IDEOGRAPH - 0xB6E3: 0x8EB2, //CJK UNIFIED IDEOGRAPH - 0xB6E4: 0x6735, //CJK UNIFIED IDEOGRAPH - 0xB6E5: 0x8DFA, //CJK UNIFIED IDEOGRAPH - 0xB6E6: 0x8235, //CJK UNIFIED IDEOGRAPH - 0xB6E7: 0x5241, //CJK UNIFIED IDEOGRAPH - 0xB6E8: 0x60F0, //CJK UNIFIED IDEOGRAPH - 0xB6E9: 0x5815, //CJK UNIFIED IDEOGRAPH - 0xB6EA: 0x86FE, //CJK UNIFIED IDEOGRAPH - 0xB6EB: 0x5CE8, //CJK UNIFIED IDEOGRAPH - 0xB6EC: 0x9E45, //CJK UNIFIED IDEOGRAPH - 0xB6ED: 0x4FC4, //CJK UNIFIED IDEOGRAPH - 0xB6EE: 0x989D, //CJK UNIFIED IDEOGRAPH - 0xB6EF: 0x8BB9, //CJK UNIFIED IDEOGRAPH - 0xB6F0: 0x5A25, //CJK UNIFIED IDEOGRAPH - 0xB6F1: 0x6076, //CJK UNIFIED IDEOGRAPH - 0xB6F2: 0x5384, //CJK UNIFIED IDEOGRAPH - 0xB6F3: 0x627C, //CJK UNIFIED IDEOGRAPH - 0xB6F4: 0x904F, //CJK UNIFIED IDEOGRAPH - 0xB6F5: 0x9102, //CJK UNIFIED IDEOGRAPH - 0xB6F6: 0x997F, //CJK UNIFIED IDEOGRAPH - 0xB6F7: 0x6069, //CJK UNIFIED IDEOGRAPH - 0xB6F8: 0x800C, //CJK UNIFIED IDEOGRAPH - 0xB6F9: 0x513F, //CJK UNIFIED IDEOGRAPH - 0xB6FA: 0x8033, //CJK UNIFIED IDEOGRAPH - 0xB6FB: 0x5C14, //CJK UNIFIED IDEOGRAPH - 0xB6FC: 0x9975, //CJK UNIFIED IDEOGRAPH - 0xB6FD: 0x6D31, //CJK UNIFIED IDEOGRAPH - 0xB6FE: 0x4E8C, //CJK UNIFIED IDEOGRAPH - 0xB740: 0x7A1D, //CJK UNIFIED IDEOGRAPH - 0xB741: 0x7A1F, //CJK UNIFIED IDEOGRAPH - 0xB742: 0x7A21, //CJK UNIFIED IDEOGRAPH - 0xB743: 0x7A22, //CJK UNIFIED IDEOGRAPH - 0xB744: 0x7A24, //CJK UNIFIED IDEOGRAPH - 0xB745: 0x7A25, //CJK UNIFIED IDEOGRAPH - 0xB746: 0x7A26, //CJK UNIFIED IDEOGRAPH - 0xB747: 0x7A27, //CJK UNIFIED IDEOGRAPH - 0xB748: 0x7A28, //CJK UNIFIED IDEOGRAPH - 0xB749: 0x7A29, //CJK UNIFIED IDEOGRAPH - 0xB74A: 0x7A2A, //CJK UNIFIED IDEOGRAPH - 0xB74B: 0x7A2B, //CJK UNIFIED IDEOGRAPH - 0xB74C: 0x7A2C, //CJK UNIFIED IDEOGRAPH - 0xB74D: 0x7A2D, //CJK UNIFIED IDEOGRAPH - 0xB74E: 0x7A2E, //CJK UNIFIED IDEOGRAPH - 0xB74F: 0x7A2F, //CJK UNIFIED IDEOGRAPH - 0xB750: 0x7A30, //CJK UNIFIED IDEOGRAPH - 0xB751: 0x7A31, //CJK UNIFIED IDEOGRAPH - 0xB752: 0x7A32, //CJK UNIFIED IDEOGRAPH - 0xB753: 0x7A34, //CJK UNIFIED IDEOGRAPH - 0xB754: 0x7A35, //CJK UNIFIED IDEOGRAPH - 0xB755: 0x7A36, //CJK UNIFIED IDEOGRAPH - 0xB756: 0x7A38, //CJK UNIFIED IDEOGRAPH - 0xB757: 0x7A3A, //CJK UNIFIED IDEOGRAPH - 0xB758: 0x7A3E, //CJK UNIFIED IDEOGRAPH - 0xB759: 0x7A40, //CJK UNIFIED IDEOGRAPH - 0xB75A: 0x7A41, //CJK UNIFIED IDEOGRAPH - 0xB75B: 0x7A42, //CJK UNIFIED IDEOGRAPH - 0xB75C: 0x7A43, //CJK UNIFIED IDEOGRAPH - 0xB75D: 0x7A44, //CJK UNIFIED IDEOGRAPH - 0xB75E: 0x7A45, //CJK UNIFIED IDEOGRAPH - 0xB75F: 0x7A47, //CJK UNIFIED IDEOGRAPH - 0xB760: 0x7A48, //CJK UNIFIED IDEOGRAPH - 0xB761: 0x7A49, //CJK UNIFIED IDEOGRAPH - 0xB762: 0x7A4A, //CJK UNIFIED IDEOGRAPH - 0xB763: 0x7A4B, //CJK UNIFIED IDEOGRAPH - 0xB764: 0x7A4C, //CJK UNIFIED IDEOGRAPH - 0xB765: 0x7A4D, //CJK UNIFIED IDEOGRAPH - 0xB766: 0x7A4E, //CJK UNIFIED IDEOGRAPH - 0xB767: 0x7A4F, //CJK UNIFIED IDEOGRAPH - 0xB768: 0x7A50, //CJK UNIFIED IDEOGRAPH - 0xB769: 0x7A52, //CJK UNIFIED IDEOGRAPH - 0xB76A: 0x7A53, //CJK UNIFIED IDEOGRAPH - 0xB76B: 0x7A54, //CJK UNIFIED IDEOGRAPH - 0xB76C: 0x7A55, //CJK UNIFIED IDEOGRAPH - 0xB76D: 0x7A56, //CJK UNIFIED IDEOGRAPH - 0xB76E: 0x7A58, //CJK UNIFIED IDEOGRAPH - 0xB76F: 0x7A59, //CJK UNIFIED IDEOGRAPH - 0xB770: 0x7A5A, //CJK UNIFIED IDEOGRAPH - 0xB771: 0x7A5B, //CJK UNIFIED IDEOGRAPH - 0xB772: 0x7A5C, //CJK UNIFIED IDEOGRAPH - 0xB773: 0x7A5D, //CJK UNIFIED IDEOGRAPH - 0xB774: 0x7A5E, //CJK UNIFIED IDEOGRAPH - 0xB775: 0x7A5F, //CJK UNIFIED IDEOGRAPH - 0xB776: 0x7A60, //CJK UNIFIED IDEOGRAPH - 0xB777: 0x7A61, //CJK UNIFIED IDEOGRAPH - 0xB778: 0x7A62, //CJK UNIFIED IDEOGRAPH - 0xB779: 0x7A63, //CJK UNIFIED IDEOGRAPH - 0xB77A: 0x7A64, //CJK UNIFIED IDEOGRAPH - 0xB77B: 0x7A65, //CJK UNIFIED IDEOGRAPH - 0xB77C: 0x7A66, //CJK UNIFIED IDEOGRAPH - 0xB77D: 0x7A67, //CJK UNIFIED IDEOGRAPH - 0xB77E: 0x7A68, //CJK UNIFIED IDEOGRAPH - 0xB780: 0x7A69, //CJK UNIFIED IDEOGRAPH - 0xB781: 0x7A6A, //CJK UNIFIED IDEOGRAPH - 0xB782: 0x7A6B, //CJK UNIFIED IDEOGRAPH - 0xB783: 0x7A6C, //CJK UNIFIED IDEOGRAPH - 0xB784: 0x7A6D, //CJK UNIFIED IDEOGRAPH - 0xB785: 0x7A6E, //CJK UNIFIED IDEOGRAPH - 0xB786: 0x7A6F, //CJK UNIFIED IDEOGRAPH - 0xB787: 0x7A71, //CJK UNIFIED IDEOGRAPH - 0xB788: 0x7A72, //CJK UNIFIED IDEOGRAPH - 0xB789: 0x7A73, //CJK UNIFIED IDEOGRAPH - 0xB78A: 0x7A75, //CJK UNIFIED IDEOGRAPH - 0xB78B: 0x7A7B, //CJK UNIFIED IDEOGRAPH - 0xB78C: 0x7A7C, //CJK UNIFIED IDEOGRAPH - 0xB78D: 0x7A7D, //CJK UNIFIED IDEOGRAPH - 0xB78E: 0x7A7E, //CJK UNIFIED IDEOGRAPH - 0xB78F: 0x7A82, //CJK UNIFIED IDEOGRAPH - 0xB790: 0x7A85, //CJK UNIFIED IDEOGRAPH - 0xB791: 0x7A87, //CJK UNIFIED IDEOGRAPH - 0xB792: 0x7A89, //CJK UNIFIED IDEOGRAPH - 0xB793: 0x7A8A, //CJK UNIFIED IDEOGRAPH - 0xB794: 0x7A8B, //CJK UNIFIED IDEOGRAPH - 0xB795: 0x7A8C, //CJK UNIFIED IDEOGRAPH - 0xB796: 0x7A8E, //CJK UNIFIED IDEOGRAPH - 0xB797: 0x7A8F, //CJK UNIFIED IDEOGRAPH - 0xB798: 0x7A90, //CJK UNIFIED IDEOGRAPH - 0xB799: 0x7A93, //CJK UNIFIED IDEOGRAPH - 0xB79A: 0x7A94, //CJK UNIFIED IDEOGRAPH - 0xB79B: 0x7A99, //CJK UNIFIED IDEOGRAPH - 0xB79C: 0x7A9A, //CJK UNIFIED IDEOGRAPH - 0xB79D: 0x7A9B, //CJK UNIFIED IDEOGRAPH - 0xB79E: 0x7A9E, //CJK UNIFIED IDEOGRAPH - 0xB79F: 0x7AA1, //CJK UNIFIED IDEOGRAPH - 0xB7A0: 0x7AA2, //CJK UNIFIED IDEOGRAPH - 0xB7A1: 0x8D30, //CJK UNIFIED IDEOGRAPH - 0xB7A2: 0x53D1, //CJK UNIFIED IDEOGRAPH - 0xB7A3: 0x7F5A, //CJK UNIFIED IDEOGRAPH - 0xB7A4: 0x7B4F, //CJK UNIFIED IDEOGRAPH - 0xB7A5: 0x4F10, //CJK UNIFIED IDEOGRAPH - 0xB7A6: 0x4E4F, //CJK UNIFIED IDEOGRAPH - 0xB7A7: 0x9600, //CJK UNIFIED IDEOGRAPH - 0xB7A8: 0x6CD5, //CJK UNIFIED IDEOGRAPH - 0xB7A9: 0x73D0, //CJK UNIFIED IDEOGRAPH - 0xB7AA: 0x85E9, //CJK UNIFIED IDEOGRAPH - 0xB7AB: 0x5E06, //CJK UNIFIED IDEOGRAPH - 0xB7AC: 0x756A, //CJK UNIFIED IDEOGRAPH - 0xB7AD: 0x7FFB, //CJK UNIFIED IDEOGRAPH - 0xB7AE: 0x6A0A, //CJK UNIFIED IDEOGRAPH - 0xB7AF: 0x77FE, //CJK UNIFIED IDEOGRAPH - 0xB7B0: 0x9492, //CJK UNIFIED IDEOGRAPH - 0xB7B1: 0x7E41, //CJK UNIFIED IDEOGRAPH - 0xB7B2: 0x51E1, //CJK UNIFIED IDEOGRAPH - 0xB7B3: 0x70E6, //CJK UNIFIED IDEOGRAPH - 0xB7B4: 0x53CD, //CJK UNIFIED IDEOGRAPH - 0xB7B5: 0x8FD4, //CJK UNIFIED IDEOGRAPH - 0xB7B6: 0x8303, //CJK UNIFIED IDEOGRAPH - 0xB7B7: 0x8D29, //CJK UNIFIED IDEOGRAPH - 0xB7B8: 0x72AF, //CJK UNIFIED IDEOGRAPH - 0xB7B9: 0x996D, //CJK UNIFIED IDEOGRAPH - 0xB7BA: 0x6CDB, //CJK UNIFIED IDEOGRAPH - 0xB7BB: 0x574A, //CJK UNIFIED IDEOGRAPH - 0xB7BC: 0x82B3, //CJK UNIFIED IDEOGRAPH - 0xB7BD: 0x65B9, //CJK UNIFIED IDEOGRAPH - 0xB7BE: 0x80AA, //CJK UNIFIED IDEOGRAPH - 0xB7BF: 0x623F, //CJK UNIFIED IDEOGRAPH - 0xB7C0: 0x9632, //CJK UNIFIED IDEOGRAPH - 0xB7C1: 0x59A8, //CJK UNIFIED IDEOGRAPH - 0xB7C2: 0x4EFF, //CJK UNIFIED IDEOGRAPH - 0xB7C3: 0x8BBF, //CJK UNIFIED IDEOGRAPH - 0xB7C4: 0x7EBA, //CJK UNIFIED IDEOGRAPH - 0xB7C5: 0x653E, //CJK UNIFIED IDEOGRAPH - 0xB7C6: 0x83F2, //CJK UNIFIED IDEOGRAPH - 0xB7C7: 0x975E, //CJK UNIFIED IDEOGRAPH - 0xB7C8: 0x5561, //CJK UNIFIED IDEOGRAPH - 0xB7C9: 0x98DE, //CJK UNIFIED IDEOGRAPH - 0xB7CA: 0x80A5, //CJK UNIFIED IDEOGRAPH - 0xB7CB: 0x532A, //CJK UNIFIED IDEOGRAPH - 0xB7CC: 0x8BFD, //CJK UNIFIED IDEOGRAPH - 0xB7CD: 0x5420, //CJK UNIFIED IDEOGRAPH - 0xB7CE: 0x80BA, //CJK UNIFIED IDEOGRAPH - 0xB7CF: 0x5E9F, //CJK UNIFIED IDEOGRAPH - 0xB7D0: 0x6CB8, //CJK UNIFIED IDEOGRAPH - 0xB7D1: 0x8D39, //CJK UNIFIED IDEOGRAPH - 0xB7D2: 0x82AC, //CJK UNIFIED IDEOGRAPH - 0xB7D3: 0x915A, //CJK UNIFIED IDEOGRAPH - 0xB7D4: 0x5429, //CJK UNIFIED IDEOGRAPH - 0xB7D5: 0x6C1B, //CJK UNIFIED IDEOGRAPH - 0xB7D6: 0x5206, //CJK UNIFIED IDEOGRAPH - 0xB7D7: 0x7EB7, //CJK UNIFIED IDEOGRAPH - 0xB7D8: 0x575F, //CJK UNIFIED IDEOGRAPH - 0xB7D9: 0x711A, //CJK UNIFIED IDEOGRAPH - 0xB7DA: 0x6C7E, //CJK UNIFIED IDEOGRAPH - 0xB7DB: 0x7C89, //CJK UNIFIED IDEOGRAPH - 0xB7DC: 0x594B, //CJK UNIFIED IDEOGRAPH - 0xB7DD: 0x4EFD, //CJK UNIFIED IDEOGRAPH - 0xB7DE: 0x5FFF, //CJK UNIFIED IDEOGRAPH - 0xB7DF: 0x6124, //CJK UNIFIED IDEOGRAPH - 0xB7E0: 0x7CAA, //CJK UNIFIED IDEOGRAPH - 0xB7E1: 0x4E30, //CJK UNIFIED IDEOGRAPH - 0xB7E2: 0x5C01, //CJK UNIFIED IDEOGRAPH - 0xB7E3: 0x67AB, //CJK UNIFIED IDEOGRAPH - 0xB7E4: 0x8702, //CJK UNIFIED IDEOGRAPH - 0xB7E5: 0x5CF0, //CJK UNIFIED IDEOGRAPH - 0xB7E6: 0x950B, //CJK UNIFIED IDEOGRAPH - 0xB7E7: 0x98CE, //CJK UNIFIED IDEOGRAPH - 0xB7E8: 0x75AF, //CJK UNIFIED IDEOGRAPH - 0xB7E9: 0x70FD, //CJK UNIFIED IDEOGRAPH - 0xB7EA: 0x9022, //CJK UNIFIED IDEOGRAPH - 0xB7EB: 0x51AF, //CJK UNIFIED IDEOGRAPH - 0xB7EC: 0x7F1D, //CJK UNIFIED IDEOGRAPH - 0xB7ED: 0x8BBD, //CJK UNIFIED IDEOGRAPH - 0xB7EE: 0x5949, //CJK UNIFIED IDEOGRAPH - 0xB7EF: 0x51E4, //CJK UNIFIED IDEOGRAPH - 0xB7F0: 0x4F5B, //CJK UNIFIED IDEOGRAPH - 0xB7F1: 0x5426, //CJK UNIFIED IDEOGRAPH - 0xB7F2: 0x592B, //CJK UNIFIED IDEOGRAPH - 0xB7F3: 0x6577, //CJK UNIFIED IDEOGRAPH - 0xB7F4: 0x80A4, //CJK UNIFIED IDEOGRAPH - 0xB7F5: 0x5B75, //CJK UNIFIED IDEOGRAPH - 0xB7F6: 0x6276, //CJK UNIFIED IDEOGRAPH - 0xB7F7: 0x62C2, //CJK UNIFIED IDEOGRAPH - 0xB7F8: 0x8F90, //CJK UNIFIED IDEOGRAPH - 0xB7F9: 0x5E45, //CJK UNIFIED IDEOGRAPH - 0xB7FA: 0x6C1F, //CJK UNIFIED IDEOGRAPH - 0xB7FB: 0x7B26, //CJK UNIFIED IDEOGRAPH - 0xB7FC: 0x4F0F, //CJK UNIFIED IDEOGRAPH - 0xB7FD: 0x4FD8, //CJK UNIFIED IDEOGRAPH - 0xB7FE: 0x670D, //CJK UNIFIED IDEOGRAPH - 0xB840: 0x7AA3, //CJK UNIFIED IDEOGRAPH - 0xB841: 0x7AA4, //CJK UNIFIED IDEOGRAPH - 0xB842: 0x7AA7, //CJK UNIFIED IDEOGRAPH - 0xB843: 0x7AA9, //CJK UNIFIED IDEOGRAPH - 0xB844: 0x7AAA, //CJK UNIFIED IDEOGRAPH - 0xB845: 0x7AAB, //CJK UNIFIED IDEOGRAPH - 0xB846: 0x7AAE, //CJK UNIFIED IDEOGRAPH - 0xB847: 0x7AAF, //CJK UNIFIED IDEOGRAPH - 0xB848: 0x7AB0, //CJK UNIFIED IDEOGRAPH - 0xB849: 0x7AB1, //CJK UNIFIED IDEOGRAPH - 0xB84A: 0x7AB2, //CJK UNIFIED IDEOGRAPH - 0xB84B: 0x7AB4, //CJK UNIFIED IDEOGRAPH - 0xB84C: 0x7AB5, //CJK UNIFIED IDEOGRAPH - 0xB84D: 0x7AB6, //CJK UNIFIED IDEOGRAPH - 0xB84E: 0x7AB7, //CJK UNIFIED IDEOGRAPH - 0xB84F: 0x7AB8, //CJK UNIFIED IDEOGRAPH - 0xB850: 0x7AB9, //CJK UNIFIED IDEOGRAPH - 0xB851: 0x7ABA, //CJK UNIFIED IDEOGRAPH - 0xB852: 0x7ABB, //CJK UNIFIED IDEOGRAPH - 0xB853: 0x7ABC, //CJK UNIFIED IDEOGRAPH - 0xB854: 0x7ABD, //CJK UNIFIED IDEOGRAPH - 0xB855: 0x7ABE, //CJK UNIFIED IDEOGRAPH - 0xB856: 0x7AC0, //CJK UNIFIED IDEOGRAPH - 0xB857: 0x7AC1, //CJK UNIFIED IDEOGRAPH - 0xB858: 0x7AC2, //CJK UNIFIED IDEOGRAPH - 0xB859: 0x7AC3, //CJK UNIFIED IDEOGRAPH - 0xB85A: 0x7AC4, //CJK UNIFIED IDEOGRAPH - 0xB85B: 0x7AC5, //CJK UNIFIED IDEOGRAPH - 0xB85C: 0x7AC6, //CJK UNIFIED IDEOGRAPH - 0xB85D: 0x7AC7, //CJK UNIFIED IDEOGRAPH - 0xB85E: 0x7AC8, //CJK UNIFIED IDEOGRAPH - 0xB85F: 0x7AC9, //CJK UNIFIED IDEOGRAPH - 0xB860: 0x7ACA, //CJK UNIFIED IDEOGRAPH - 0xB861: 0x7ACC, //CJK UNIFIED IDEOGRAPH - 0xB862: 0x7ACD, //CJK UNIFIED IDEOGRAPH - 0xB863: 0x7ACE, //CJK UNIFIED IDEOGRAPH - 0xB864: 0x7ACF, //CJK UNIFIED IDEOGRAPH - 0xB865: 0x7AD0, //CJK UNIFIED IDEOGRAPH - 0xB866: 0x7AD1, //CJK UNIFIED IDEOGRAPH - 0xB867: 0x7AD2, //CJK UNIFIED IDEOGRAPH - 0xB868: 0x7AD3, //CJK UNIFIED IDEOGRAPH - 0xB869: 0x7AD4, //CJK UNIFIED IDEOGRAPH - 0xB86A: 0x7AD5, //CJK UNIFIED IDEOGRAPH - 0xB86B: 0x7AD7, //CJK UNIFIED IDEOGRAPH - 0xB86C: 0x7AD8, //CJK UNIFIED IDEOGRAPH - 0xB86D: 0x7ADA, //CJK UNIFIED IDEOGRAPH - 0xB86E: 0x7ADB, //CJK UNIFIED IDEOGRAPH - 0xB86F: 0x7ADC, //CJK UNIFIED IDEOGRAPH - 0xB870: 0x7ADD, //CJK UNIFIED IDEOGRAPH - 0xB871: 0x7AE1, //CJK UNIFIED IDEOGRAPH - 0xB872: 0x7AE2, //CJK UNIFIED IDEOGRAPH - 0xB873: 0x7AE4, //CJK UNIFIED IDEOGRAPH - 0xB874: 0x7AE7, //CJK UNIFIED IDEOGRAPH - 0xB875: 0x7AE8, //CJK UNIFIED IDEOGRAPH - 0xB876: 0x7AE9, //CJK UNIFIED IDEOGRAPH - 0xB877: 0x7AEA, //CJK UNIFIED IDEOGRAPH - 0xB878: 0x7AEB, //CJK UNIFIED IDEOGRAPH - 0xB879: 0x7AEC, //CJK UNIFIED IDEOGRAPH - 0xB87A: 0x7AEE, //CJK UNIFIED IDEOGRAPH - 0xB87B: 0x7AF0, //CJK UNIFIED IDEOGRAPH - 0xB87C: 0x7AF1, //CJK UNIFIED IDEOGRAPH - 0xB87D: 0x7AF2, //CJK UNIFIED IDEOGRAPH - 0xB87E: 0x7AF3, //CJK UNIFIED IDEOGRAPH - 0xB880: 0x7AF4, //CJK UNIFIED IDEOGRAPH - 0xB881: 0x7AF5, //CJK UNIFIED IDEOGRAPH - 0xB882: 0x7AF6, //CJK UNIFIED IDEOGRAPH - 0xB883: 0x7AF7, //CJK UNIFIED IDEOGRAPH - 0xB884: 0x7AF8, //CJK UNIFIED IDEOGRAPH - 0xB885: 0x7AFB, //CJK UNIFIED IDEOGRAPH - 0xB886: 0x7AFC, //CJK UNIFIED IDEOGRAPH - 0xB887: 0x7AFE, //CJK UNIFIED IDEOGRAPH - 0xB888: 0x7B00, //CJK UNIFIED IDEOGRAPH - 0xB889: 0x7B01, //CJK UNIFIED IDEOGRAPH - 0xB88A: 0x7B02, //CJK UNIFIED IDEOGRAPH - 0xB88B: 0x7B05, //CJK UNIFIED IDEOGRAPH - 0xB88C: 0x7B07, //CJK UNIFIED IDEOGRAPH - 0xB88D: 0x7B09, //CJK UNIFIED IDEOGRAPH - 0xB88E: 0x7B0C, //CJK UNIFIED IDEOGRAPH - 0xB88F: 0x7B0D, //CJK UNIFIED IDEOGRAPH - 0xB890: 0x7B0E, //CJK UNIFIED IDEOGRAPH - 0xB891: 0x7B10, //CJK UNIFIED IDEOGRAPH - 0xB892: 0x7B12, //CJK UNIFIED IDEOGRAPH - 0xB893: 0x7B13, //CJK UNIFIED IDEOGRAPH - 0xB894: 0x7B16, //CJK UNIFIED IDEOGRAPH - 0xB895: 0x7B17, //CJK UNIFIED IDEOGRAPH - 0xB896: 0x7B18, //CJK UNIFIED IDEOGRAPH - 0xB897: 0x7B1A, //CJK UNIFIED IDEOGRAPH - 0xB898: 0x7B1C, //CJK UNIFIED IDEOGRAPH - 0xB899: 0x7B1D, //CJK UNIFIED IDEOGRAPH - 0xB89A: 0x7B1F, //CJK UNIFIED IDEOGRAPH - 0xB89B: 0x7B21, //CJK UNIFIED IDEOGRAPH - 0xB89C: 0x7B22, //CJK UNIFIED IDEOGRAPH - 0xB89D: 0x7B23, //CJK UNIFIED IDEOGRAPH - 0xB89E: 0x7B27, //CJK UNIFIED IDEOGRAPH - 0xB89F: 0x7B29, //CJK UNIFIED IDEOGRAPH - 0xB8A0: 0x7B2D, //CJK UNIFIED IDEOGRAPH - 0xB8A1: 0x6D6E, //CJK UNIFIED IDEOGRAPH - 0xB8A2: 0x6DAA, //CJK UNIFIED IDEOGRAPH - 0xB8A3: 0x798F, //CJK UNIFIED IDEOGRAPH - 0xB8A4: 0x88B1, //CJK UNIFIED IDEOGRAPH - 0xB8A5: 0x5F17, //CJK UNIFIED IDEOGRAPH - 0xB8A6: 0x752B, //CJK UNIFIED IDEOGRAPH - 0xB8A7: 0x629A, //CJK UNIFIED IDEOGRAPH - 0xB8A8: 0x8F85, //CJK UNIFIED IDEOGRAPH - 0xB8A9: 0x4FEF, //CJK UNIFIED IDEOGRAPH - 0xB8AA: 0x91DC, //CJK UNIFIED IDEOGRAPH - 0xB8AB: 0x65A7, //CJK UNIFIED IDEOGRAPH - 0xB8AC: 0x812F, //CJK UNIFIED IDEOGRAPH - 0xB8AD: 0x8151, //CJK UNIFIED IDEOGRAPH - 0xB8AE: 0x5E9C, //CJK UNIFIED IDEOGRAPH - 0xB8AF: 0x8150, //CJK UNIFIED IDEOGRAPH - 0xB8B0: 0x8D74, //CJK UNIFIED IDEOGRAPH - 0xB8B1: 0x526F, //CJK UNIFIED IDEOGRAPH - 0xB8B2: 0x8986, //CJK UNIFIED IDEOGRAPH - 0xB8B3: 0x8D4B, //CJK UNIFIED IDEOGRAPH - 0xB8B4: 0x590D, //CJK UNIFIED IDEOGRAPH - 0xB8B5: 0x5085, //CJK UNIFIED IDEOGRAPH - 0xB8B6: 0x4ED8, //CJK UNIFIED IDEOGRAPH - 0xB8B7: 0x961C, //CJK UNIFIED IDEOGRAPH - 0xB8B8: 0x7236, //CJK UNIFIED IDEOGRAPH - 0xB8B9: 0x8179, //CJK UNIFIED IDEOGRAPH - 0xB8BA: 0x8D1F, //CJK UNIFIED IDEOGRAPH - 0xB8BB: 0x5BCC, //CJK UNIFIED IDEOGRAPH - 0xB8BC: 0x8BA3, //CJK UNIFIED IDEOGRAPH - 0xB8BD: 0x9644, //CJK UNIFIED IDEOGRAPH - 0xB8BE: 0x5987, //CJK UNIFIED IDEOGRAPH - 0xB8BF: 0x7F1A, //CJK UNIFIED IDEOGRAPH - 0xB8C0: 0x5490, //CJK UNIFIED IDEOGRAPH - 0xB8C1: 0x5676, //CJK UNIFIED IDEOGRAPH - 0xB8C2: 0x560E, //CJK UNIFIED IDEOGRAPH - 0xB8C3: 0x8BE5, //CJK UNIFIED IDEOGRAPH - 0xB8C4: 0x6539, //CJK UNIFIED IDEOGRAPH - 0xB8C5: 0x6982, //CJK UNIFIED IDEOGRAPH - 0xB8C6: 0x9499, //CJK UNIFIED IDEOGRAPH - 0xB8C7: 0x76D6, //CJK UNIFIED IDEOGRAPH - 0xB8C8: 0x6E89, //CJK UNIFIED IDEOGRAPH - 0xB8C9: 0x5E72, //CJK UNIFIED IDEOGRAPH - 0xB8CA: 0x7518, //CJK UNIFIED IDEOGRAPH - 0xB8CB: 0x6746, //CJK UNIFIED IDEOGRAPH - 0xB8CC: 0x67D1, //CJK UNIFIED IDEOGRAPH - 0xB8CD: 0x7AFF, //CJK UNIFIED IDEOGRAPH - 0xB8CE: 0x809D, //CJK UNIFIED IDEOGRAPH - 0xB8CF: 0x8D76, //CJK UNIFIED IDEOGRAPH - 0xB8D0: 0x611F, //CJK UNIFIED IDEOGRAPH - 0xB8D1: 0x79C6, //CJK UNIFIED IDEOGRAPH - 0xB8D2: 0x6562, //CJK UNIFIED IDEOGRAPH - 0xB8D3: 0x8D63, //CJK UNIFIED IDEOGRAPH - 0xB8D4: 0x5188, //CJK UNIFIED IDEOGRAPH - 0xB8D5: 0x521A, //CJK UNIFIED IDEOGRAPH - 0xB8D6: 0x94A2, //CJK UNIFIED IDEOGRAPH - 0xB8D7: 0x7F38, //CJK UNIFIED IDEOGRAPH - 0xB8D8: 0x809B, //CJK UNIFIED IDEOGRAPH - 0xB8D9: 0x7EB2, //CJK UNIFIED IDEOGRAPH - 0xB8DA: 0x5C97, //CJK UNIFIED IDEOGRAPH - 0xB8DB: 0x6E2F, //CJK UNIFIED IDEOGRAPH - 0xB8DC: 0x6760, //CJK UNIFIED IDEOGRAPH - 0xB8DD: 0x7BD9, //CJK UNIFIED IDEOGRAPH - 0xB8DE: 0x768B, //CJK UNIFIED IDEOGRAPH - 0xB8DF: 0x9AD8, //CJK UNIFIED IDEOGRAPH - 0xB8E0: 0x818F, //CJK UNIFIED IDEOGRAPH - 0xB8E1: 0x7F94, //CJK UNIFIED IDEOGRAPH - 0xB8E2: 0x7CD5, //CJK UNIFIED IDEOGRAPH - 0xB8E3: 0x641E, //CJK UNIFIED IDEOGRAPH - 0xB8E4: 0x9550, //CJK UNIFIED IDEOGRAPH - 0xB8E5: 0x7A3F, //CJK UNIFIED IDEOGRAPH - 0xB8E6: 0x544A, //CJK UNIFIED IDEOGRAPH - 0xB8E7: 0x54E5, //CJK UNIFIED IDEOGRAPH - 0xB8E8: 0x6B4C, //CJK UNIFIED IDEOGRAPH - 0xB8E9: 0x6401, //CJK UNIFIED IDEOGRAPH - 0xB8EA: 0x6208, //CJK UNIFIED IDEOGRAPH - 0xB8EB: 0x9E3D, //CJK UNIFIED IDEOGRAPH - 0xB8EC: 0x80F3, //CJK UNIFIED IDEOGRAPH - 0xB8ED: 0x7599, //CJK UNIFIED IDEOGRAPH - 0xB8EE: 0x5272, //CJK UNIFIED IDEOGRAPH - 0xB8EF: 0x9769, //CJK UNIFIED IDEOGRAPH - 0xB8F0: 0x845B, //CJK UNIFIED IDEOGRAPH - 0xB8F1: 0x683C, //CJK UNIFIED IDEOGRAPH - 0xB8F2: 0x86E4, //CJK UNIFIED IDEOGRAPH - 0xB8F3: 0x9601, //CJK UNIFIED IDEOGRAPH - 0xB8F4: 0x9694, //CJK UNIFIED IDEOGRAPH - 0xB8F5: 0x94EC, //CJK UNIFIED IDEOGRAPH - 0xB8F6: 0x4E2A, //CJK UNIFIED IDEOGRAPH - 0xB8F7: 0x5404, //CJK UNIFIED IDEOGRAPH - 0xB8F8: 0x7ED9, //CJK UNIFIED IDEOGRAPH - 0xB8F9: 0x6839, //CJK UNIFIED IDEOGRAPH - 0xB8FA: 0x8DDF, //CJK UNIFIED IDEOGRAPH - 0xB8FB: 0x8015, //CJK UNIFIED IDEOGRAPH - 0xB8FC: 0x66F4, //CJK UNIFIED IDEOGRAPH - 0xB8FD: 0x5E9A, //CJK UNIFIED IDEOGRAPH - 0xB8FE: 0x7FB9, //CJK UNIFIED IDEOGRAPH - 0xB940: 0x7B2F, //CJK UNIFIED IDEOGRAPH - 0xB941: 0x7B30, //CJK UNIFIED IDEOGRAPH - 0xB942: 0x7B32, //CJK UNIFIED IDEOGRAPH - 0xB943: 0x7B34, //CJK UNIFIED IDEOGRAPH - 0xB944: 0x7B35, //CJK UNIFIED IDEOGRAPH - 0xB945: 0x7B36, //CJK UNIFIED IDEOGRAPH - 0xB946: 0x7B37, //CJK UNIFIED IDEOGRAPH - 0xB947: 0x7B39, //CJK UNIFIED IDEOGRAPH - 0xB948: 0x7B3B, //CJK UNIFIED IDEOGRAPH - 0xB949: 0x7B3D, //CJK UNIFIED IDEOGRAPH - 0xB94A: 0x7B3F, //CJK UNIFIED IDEOGRAPH - 0xB94B: 0x7B40, //CJK UNIFIED IDEOGRAPH - 0xB94C: 0x7B41, //CJK UNIFIED IDEOGRAPH - 0xB94D: 0x7B42, //CJK UNIFIED IDEOGRAPH - 0xB94E: 0x7B43, //CJK UNIFIED IDEOGRAPH - 0xB94F: 0x7B44, //CJK UNIFIED IDEOGRAPH - 0xB950: 0x7B46, //CJK UNIFIED IDEOGRAPH - 0xB951: 0x7B48, //CJK UNIFIED IDEOGRAPH - 0xB952: 0x7B4A, //CJK UNIFIED IDEOGRAPH - 0xB953: 0x7B4D, //CJK UNIFIED IDEOGRAPH - 0xB954: 0x7B4E, //CJK UNIFIED IDEOGRAPH - 0xB955: 0x7B53, //CJK UNIFIED IDEOGRAPH - 0xB956: 0x7B55, //CJK UNIFIED IDEOGRAPH - 0xB957: 0x7B57, //CJK UNIFIED IDEOGRAPH - 0xB958: 0x7B59, //CJK UNIFIED IDEOGRAPH - 0xB959: 0x7B5C, //CJK UNIFIED IDEOGRAPH - 0xB95A: 0x7B5E, //CJK UNIFIED IDEOGRAPH - 0xB95B: 0x7B5F, //CJK UNIFIED IDEOGRAPH - 0xB95C: 0x7B61, //CJK UNIFIED IDEOGRAPH - 0xB95D: 0x7B63, //CJK UNIFIED IDEOGRAPH - 0xB95E: 0x7B64, //CJK UNIFIED IDEOGRAPH - 0xB95F: 0x7B65, //CJK UNIFIED IDEOGRAPH - 0xB960: 0x7B66, //CJK UNIFIED IDEOGRAPH - 0xB961: 0x7B67, //CJK UNIFIED IDEOGRAPH - 0xB962: 0x7B68, //CJK UNIFIED IDEOGRAPH - 0xB963: 0x7B69, //CJK UNIFIED IDEOGRAPH - 0xB964: 0x7B6A, //CJK UNIFIED IDEOGRAPH - 0xB965: 0x7B6B, //CJK UNIFIED IDEOGRAPH - 0xB966: 0x7B6C, //CJK UNIFIED IDEOGRAPH - 0xB967: 0x7B6D, //CJK UNIFIED IDEOGRAPH - 0xB968: 0x7B6F, //CJK UNIFIED IDEOGRAPH - 0xB969: 0x7B70, //CJK UNIFIED IDEOGRAPH - 0xB96A: 0x7B73, //CJK UNIFIED IDEOGRAPH - 0xB96B: 0x7B74, //CJK UNIFIED IDEOGRAPH - 0xB96C: 0x7B76, //CJK UNIFIED IDEOGRAPH - 0xB96D: 0x7B78, //CJK UNIFIED IDEOGRAPH - 0xB96E: 0x7B7A, //CJK UNIFIED IDEOGRAPH - 0xB96F: 0x7B7C, //CJK UNIFIED IDEOGRAPH - 0xB970: 0x7B7D, //CJK UNIFIED IDEOGRAPH - 0xB971: 0x7B7F, //CJK UNIFIED IDEOGRAPH - 0xB972: 0x7B81, //CJK UNIFIED IDEOGRAPH - 0xB973: 0x7B82, //CJK UNIFIED IDEOGRAPH - 0xB974: 0x7B83, //CJK UNIFIED IDEOGRAPH - 0xB975: 0x7B84, //CJK UNIFIED IDEOGRAPH - 0xB976: 0x7B86, //CJK UNIFIED IDEOGRAPH - 0xB977: 0x7B87, //CJK UNIFIED IDEOGRAPH - 0xB978: 0x7B88, //CJK UNIFIED IDEOGRAPH - 0xB979: 0x7B89, //CJK UNIFIED IDEOGRAPH - 0xB97A: 0x7B8A, //CJK UNIFIED IDEOGRAPH - 0xB97B: 0x7B8B, //CJK UNIFIED IDEOGRAPH - 0xB97C: 0x7B8C, //CJK UNIFIED IDEOGRAPH - 0xB97D: 0x7B8E, //CJK UNIFIED IDEOGRAPH - 0xB97E: 0x7B8F, //CJK UNIFIED IDEOGRAPH - 0xB980: 0x7B91, //CJK UNIFIED IDEOGRAPH - 0xB981: 0x7B92, //CJK UNIFIED IDEOGRAPH - 0xB982: 0x7B93, //CJK UNIFIED IDEOGRAPH - 0xB983: 0x7B96, //CJK UNIFIED IDEOGRAPH - 0xB984: 0x7B98, //CJK UNIFIED IDEOGRAPH - 0xB985: 0x7B99, //CJK UNIFIED IDEOGRAPH - 0xB986: 0x7B9A, //CJK UNIFIED IDEOGRAPH - 0xB987: 0x7B9B, //CJK UNIFIED IDEOGRAPH - 0xB988: 0x7B9E, //CJK UNIFIED IDEOGRAPH - 0xB989: 0x7B9F, //CJK UNIFIED IDEOGRAPH - 0xB98A: 0x7BA0, //CJK UNIFIED IDEOGRAPH - 0xB98B: 0x7BA3, //CJK UNIFIED IDEOGRAPH - 0xB98C: 0x7BA4, //CJK UNIFIED IDEOGRAPH - 0xB98D: 0x7BA5, //CJK UNIFIED IDEOGRAPH - 0xB98E: 0x7BAE, //CJK UNIFIED IDEOGRAPH - 0xB98F: 0x7BAF, //CJK UNIFIED IDEOGRAPH - 0xB990: 0x7BB0, //CJK UNIFIED IDEOGRAPH - 0xB991: 0x7BB2, //CJK UNIFIED IDEOGRAPH - 0xB992: 0x7BB3, //CJK UNIFIED IDEOGRAPH - 0xB993: 0x7BB5, //CJK UNIFIED IDEOGRAPH - 0xB994: 0x7BB6, //CJK UNIFIED IDEOGRAPH - 0xB995: 0x7BB7, //CJK UNIFIED IDEOGRAPH - 0xB996: 0x7BB9, //CJK UNIFIED IDEOGRAPH - 0xB997: 0x7BBA, //CJK UNIFIED IDEOGRAPH - 0xB998: 0x7BBB, //CJK UNIFIED IDEOGRAPH - 0xB999: 0x7BBC, //CJK UNIFIED IDEOGRAPH - 0xB99A: 0x7BBD, //CJK UNIFIED IDEOGRAPH - 0xB99B: 0x7BBE, //CJK UNIFIED IDEOGRAPH - 0xB99C: 0x7BBF, //CJK UNIFIED IDEOGRAPH - 0xB99D: 0x7BC0, //CJK UNIFIED IDEOGRAPH - 0xB99E: 0x7BC2, //CJK UNIFIED IDEOGRAPH - 0xB99F: 0x7BC3, //CJK UNIFIED IDEOGRAPH - 0xB9A0: 0x7BC4, //CJK UNIFIED IDEOGRAPH - 0xB9A1: 0x57C2, //CJK UNIFIED IDEOGRAPH - 0xB9A2: 0x803F, //CJK UNIFIED IDEOGRAPH - 0xB9A3: 0x6897, //CJK UNIFIED IDEOGRAPH - 0xB9A4: 0x5DE5, //CJK UNIFIED IDEOGRAPH - 0xB9A5: 0x653B, //CJK UNIFIED IDEOGRAPH - 0xB9A6: 0x529F, //CJK UNIFIED IDEOGRAPH - 0xB9A7: 0x606D, //CJK UNIFIED IDEOGRAPH - 0xB9A8: 0x9F9A, //CJK UNIFIED IDEOGRAPH - 0xB9A9: 0x4F9B, //CJK UNIFIED IDEOGRAPH - 0xB9AA: 0x8EAC, //CJK UNIFIED IDEOGRAPH - 0xB9AB: 0x516C, //CJK UNIFIED IDEOGRAPH - 0xB9AC: 0x5BAB, //CJK UNIFIED IDEOGRAPH - 0xB9AD: 0x5F13, //CJK UNIFIED IDEOGRAPH - 0xB9AE: 0x5DE9, //CJK UNIFIED IDEOGRAPH - 0xB9AF: 0x6C5E, //CJK UNIFIED IDEOGRAPH - 0xB9B0: 0x62F1, //CJK UNIFIED IDEOGRAPH - 0xB9B1: 0x8D21, //CJK UNIFIED IDEOGRAPH - 0xB9B2: 0x5171, //CJK UNIFIED IDEOGRAPH - 0xB9B3: 0x94A9, //CJK UNIFIED IDEOGRAPH - 0xB9B4: 0x52FE, //CJK UNIFIED IDEOGRAPH - 0xB9B5: 0x6C9F, //CJK UNIFIED IDEOGRAPH - 0xB9B6: 0x82DF, //CJK UNIFIED IDEOGRAPH - 0xB9B7: 0x72D7, //CJK UNIFIED IDEOGRAPH - 0xB9B8: 0x57A2, //CJK UNIFIED IDEOGRAPH - 0xB9B9: 0x6784, //CJK UNIFIED IDEOGRAPH - 0xB9BA: 0x8D2D, //CJK UNIFIED IDEOGRAPH - 0xB9BB: 0x591F, //CJK UNIFIED IDEOGRAPH - 0xB9BC: 0x8F9C, //CJK UNIFIED IDEOGRAPH - 0xB9BD: 0x83C7, //CJK UNIFIED IDEOGRAPH - 0xB9BE: 0x5495, //CJK UNIFIED IDEOGRAPH - 0xB9BF: 0x7B8D, //CJK UNIFIED IDEOGRAPH - 0xB9C0: 0x4F30, //CJK UNIFIED IDEOGRAPH - 0xB9C1: 0x6CBD, //CJK UNIFIED IDEOGRAPH - 0xB9C2: 0x5B64, //CJK UNIFIED IDEOGRAPH - 0xB9C3: 0x59D1, //CJK UNIFIED IDEOGRAPH - 0xB9C4: 0x9F13, //CJK UNIFIED IDEOGRAPH - 0xB9C5: 0x53E4, //CJK UNIFIED IDEOGRAPH - 0xB9C6: 0x86CA, //CJK UNIFIED IDEOGRAPH - 0xB9C7: 0x9AA8, //CJK UNIFIED IDEOGRAPH - 0xB9C8: 0x8C37, //CJK UNIFIED IDEOGRAPH - 0xB9C9: 0x80A1, //CJK UNIFIED IDEOGRAPH - 0xB9CA: 0x6545, //CJK UNIFIED IDEOGRAPH - 0xB9CB: 0x987E, //CJK UNIFIED IDEOGRAPH - 0xB9CC: 0x56FA, //CJK UNIFIED IDEOGRAPH - 0xB9CD: 0x96C7, //CJK UNIFIED IDEOGRAPH - 0xB9CE: 0x522E, //CJK UNIFIED IDEOGRAPH - 0xB9CF: 0x74DC, //CJK UNIFIED IDEOGRAPH - 0xB9D0: 0x5250, //CJK UNIFIED IDEOGRAPH - 0xB9D1: 0x5BE1, //CJK UNIFIED IDEOGRAPH - 0xB9D2: 0x6302, //CJK UNIFIED IDEOGRAPH - 0xB9D3: 0x8902, //CJK UNIFIED IDEOGRAPH - 0xB9D4: 0x4E56, //CJK UNIFIED IDEOGRAPH - 0xB9D5: 0x62D0, //CJK UNIFIED IDEOGRAPH - 0xB9D6: 0x602A, //CJK UNIFIED IDEOGRAPH - 0xB9D7: 0x68FA, //CJK UNIFIED IDEOGRAPH - 0xB9D8: 0x5173, //CJK UNIFIED IDEOGRAPH - 0xB9D9: 0x5B98, //CJK UNIFIED IDEOGRAPH - 0xB9DA: 0x51A0, //CJK UNIFIED IDEOGRAPH - 0xB9DB: 0x89C2, //CJK UNIFIED IDEOGRAPH - 0xB9DC: 0x7BA1, //CJK UNIFIED IDEOGRAPH - 0xB9DD: 0x9986, //CJK UNIFIED IDEOGRAPH - 0xB9DE: 0x7F50, //CJK UNIFIED IDEOGRAPH - 0xB9DF: 0x60EF, //CJK UNIFIED IDEOGRAPH - 0xB9E0: 0x704C, //CJK UNIFIED IDEOGRAPH - 0xB9E1: 0x8D2F, //CJK UNIFIED IDEOGRAPH - 0xB9E2: 0x5149, //CJK UNIFIED IDEOGRAPH - 0xB9E3: 0x5E7F, //CJK UNIFIED IDEOGRAPH - 0xB9E4: 0x901B, //CJK UNIFIED IDEOGRAPH - 0xB9E5: 0x7470, //CJK UNIFIED IDEOGRAPH - 0xB9E6: 0x89C4, //CJK UNIFIED IDEOGRAPH - 0xB9E7: 0x572D, //CJK UNIFIED IDEOGRAPH - 0xB9E8: 0x7845, //CJK UNIFIED IDEOGRAPH - 0xB9E9: 0x5F52, //CJK UNIFIED IDEOGRAPH - 0xB9EA: 0x9F9F, //CJK UNIFIED IDEOGRAPH - 0xB9EB: 0x95FA, //CJK UNIFIED IDEOGRAPH - 0xB9EC: 0x8F68, //CJK UNIFIED IDEOGRAPH - 0xB9ED: 0x9B3C, //CJK UNIFIED IDEOGRAPH - 0xB9EE: 0x8BE1, //CJK UNIFIED IDEOGRAPH - 0xB9EF: 0x7678, //CJK UNIFIED IDEOGRAPH - 0xB9F0: 0x6842, //CJK UNIFIED IDEOGRAPH - 0xB9F1: 0x67DC, //CJK UNIFIED IDEOGRAPH - 0xB9F2: 0x8DEA, //CJK UNIFIED IDEOGRAPH - 0xB9F3: 0x8D35, //CJK UNIFIED IDEOGRAPH - 0xB9F4: 0x523D, //CJK UNIFIED IDEOGRAPH - 0xB9F5: 0x8F8A, //CJK UNIFIED IDEOGRAPH - 0xB9F6: 0x6EDA, //CJK UNIFIED IDEOGRAPH - 0xB9F7: 0x68CD, //CJK UNIFIED IDEOGRAPH - 0xB9F8: 0x9505, //CJK UNIFIED IDEOGRAPH - 0xB9F9: 0x90ED, //CJK UNIFIED IDEOGRAPH - 0xB9FA: 0x56FD, //CJK UNIFIED IDEOGRAPH - 0xB9FB: 0x679C, //CJK UNIFIED IDEOGRAPH - 0xB9FC: 0x88F9, //CJK UNIFIED IDEOGRAPH - 0xB9FD: 0x8FC7, //CJK UNIFIED IDEOGRAPH - 0xB9FE: 0x54C8, //CJK UNIFIED IDEOGRAPH - 0xBA40: 0x7BC5, //CJK UNIFIED IDEOGRAPH - 0xBA41: 0x7BC8, //CJK UNIFIED IDEOGRAPH - 0xBA42: 0x7BC9, //CJK UNIFIED IDEOGRAPH - 0xBA43: 0x7BCA, //CJK UNIFIED IDEOGRAPH - 0xBA44: 0x7BCB, //CJK UNIFIED IDEOGRAPH - 0xBA45: 0x7BCD, //CJK UNIFIED IDEOGRAPH - 0xBA46: 0x7BCE, //CJK UNIFIED IDEOGRAPH - 0xBA47: 0x7BCF, //CJK UNIFIED IDEOGRAPH - 0xBA48: 0x7BD0, //CJK UNIFIED IDEOGRAPH - 0xBA49: 0x7BD2, //CJK UNIFIED IDEOGRAPH - 0xBA4A: 0x7BD4, //CJK UNIFIED IDEOGRAPH - 0xBA4B: 0x7BD5, //CJK UNIFIED IDEOGRAPH - 0xBA4C: 0x7BD6, //CJK UNIFIED IDEOGRAPH - 0xBA4D: 0x7BD7, //CJK UNIFIED IDEOGRAPH - 0xBA4E: 0x7BD8, //CJK UNIFIED IDEOGRAPH - 0xBA4F: 0x7BDB, //CJK UNIFIED IDEOGRAPH - 0xBA50: 0x7BDC, //CJK UNIFIED IDEOGRAPH - 0xBA51: 0x7BDE, //CJK UNIFIED IDEOGRAPH - 0xBA52: 0x7BDF, //CJK UNIFIED IDEOGRAPH - 0xBA53: 0x7BE0, //CJK UNIFIED IDEOGRAPH - 0xBA54: 0x7BE2, //CJK UNIFIED IDEOGRAPH - 0xBA55: 0x7BE3, //CJK UNIFIED IDEOGRAPH - 0xBA56: 0x7BE4, //CJK UNIFIED IDEOGRAPH - 0xBA57: 0x7BE7, //CJK UNIFIED IDEOGRAPH - 0xBA58: 0x7BE8, //CJK UNIFIED IDEOGRAPH - 0xBA59: 0x7BE9, //CJK UNIFIED IDEOGRAPH - 0xBA5A: 0x7BEB, //CJK UNIFIED IDEOGRAPH - 0xBA5B: 0x7BEC, //CJK UNIFIED IDEOGRAPH - 0xBA5C: 0x7BED, //CJK UNIFIED IDEOGRAPH - 0xBA5D: 0x7BEF, //CJK UNIFIED IDEOGRAPH - 0xBA5E: 0x7BF0, //CJK UNIFIED IDEOGRAPH - 0xBA5F: 0x7BF2, //CJK UNIFIED IDEOGRAPH - 0xBA60: 0x7BF3, //CJK UNIFIED IDEOGRAPH - 0xBA61: 0x7BF4, //CJK UNIFIED IDEOGRAPH - 0xBA62: 0x7BF5, //CJK UNIFIED IDEOGRAPH - 0xBA63: 0x7BF6, //CJK UNIFIED IDEOGRAPH - 0xBA64: 0x7BF8, //CJK UNIFIED IDEOGRAPH - 0xBA65: 0x7BF9, //CJK UNIFIED IDEOGRAPH - 0xBA66: 0x7BFA, //CJK UNIFIED IDEOGRAPH - 0xBA67: 0x7BFB, //CJK UNIFIED IDEOGRAPH - 0xBA68: 0x7BFD, //CJK UNIFIED IDEOGRAPH - 0xBA69: 0x7BFF, //CJK UNIFIED IDEOGRAPH - 0xBA6A: 0x7C00, //CJK UNIFIED IDEOGRAPH - 0xBA6B: 0x7C01, //CJK UNIFIED IDEOGRAPH - 0xBA6C: 0x7C02, //CJK UNIFIED IDEOGRAPH - 0xBA6D: 0x7C03, //CJK UNIFIED IDEOGRAPH - 0xBA6E: 0x7C04, //CJK UNIFIED IDEOGRAPH - 0xBA6F: 0x7C05, //CJK UNIFIED IDEOGRAPH - 0xBA70: 0x7C06, //CJK UNIFIED IDEOGRAPH - 0xBA71: 0x7C08, //CJK UNIFIED IDEOGRAPH - 0xBA72: 0x7C09, //CJK UNIFIED IDEOGRAPH - 0xBA73: 0x7C0A, //CJK UNIFIED IDEOGRAPH - 0xBA74: 0x7C0D, //CJK UNIFIED IDEOGRAPH - 0xBA75: 0x7C0E, //CJK UNIFIED IDEOGRAPH - 0xBA76: 0x7C10, //CJK UNIFIED IDEOGRAPH - 0xBA77: 0x7C11, //CJK UNIFIED IDEOGRAPH - 0xBA78: 0x7C12, //CJK UNIFIED IDEOGRAPH - 0xBA79: 0x7C13, //CJK UNIFIED IDEOGRAPH - 0xBA7A: 0x7C14, //CJK UNIFIED IDEOGRAPH - 0xBA7B: 0x7C15, //CJK UNIFIED IDEOGRAPH - 0xBA7C: 0x7C17, //CJK UNIFIED IDEOGRAPH - 0xBA7D: 0x7C18, //CJK UNIFIED IDEOGRAPH - 0xBA7E: 0x7C19, //CJK UNIFIED IDEOGRAPH - 0xBA80: 0x7C1A, //CJK UNIFIED IDEOGRAPH - 0xBA81: 0x7C1B, //CJK UNIFIED IDEOGRAPH - 0xBA82: 0x7C1C, //CJK UNIFIED IDEOGRAPH - 0xBA83: 0x7C1D, //CJK UNIFIED IDEOGRAPH - 0xBA84: 0x7C1E, //CJK UNIFIED IDEOGRAPH - 0xBA85: 0x7C20, //CJK UNIFIED IDEOGRAPH - 0xBA86: 0x7C21, //CJK UNIFIED IDEOGRAPH - 0xBA87: 0x7C22, //CJK UNIFIED IDEOGRAPH - 0xBA88: 0x7C23, //CJK UNIFIED IDEOGRAPH - 0xBA89: 0x7C24, //CJK UNIFIED IDEOGRAPH - 0xBA8A: 0x7C25, //CJK UNIFIED IDEOGRAPH - 0xBA8B: 0x7C28, //CJK UNIFIED IDEOGRAPH - 0xBA8C: 0x7C29, //CJK UNIFIED IDEOGRAPH - 0xBA8D: 0x7C2B, //CJK UNIFIED IDEOGRAPH - 0xBA8E: 0x7C2C, //CJK UNIFIED IDEOGRAPH - 0xBA8F: 0x7C2D, //CJK UNIFIED IDEOGRAPH - 0xBA90: 0x7C2E, //CJK UNIFIED IDEOGRAPH - 0xBA91: 0x7C2F, //CJK UNIFIED IDEOGRAPH - 0xBA92: 0x7C30, //CJK UNIFIED IDEOGRAPH - 0xBA93: 0x7C31, //CJK UNIFIED IDEOGRAPH - 0xBA94: 0x7C32, //CJK UNIFIED IDEOGRAPH - 0xBA95: 0x7C33, //CJK UNIFIED IDEOGRAPH - 0xBA96: 0x7C34, //CJK UNIFIED IDEOGRAPH - 0xBA97: 0x7C35, //CJK UNIFIED IDEOGRAPH - 0xBA98: 0x7C36, //CJK UNIFIED IDEOGRAPH - 0xBA99: 0x7C37, //CJK UNIFIED IDEOGRAPH - 0xBA9A: 0x7C39, //CJK UNIFIED IDEOGRAPH - 0xBA9B: 0x7C3A, //CJK UNIFIED IDEOGRAPH - 0xBA9C: 0x7C3B, //CJK UNIFIED IDEOGRAPH - 0xBA9D: 0x7C3C, //CJK UNIFIED IDEOGRAPH - 0xBA9E: 0x7C3D, //CJK UNIFIED IDEOGRAPH - 0xBA9F: 0x7C3E, //CJK UNIFIED IDEOGRAPH - 0xBAA0: 0x7C42, //CJK UNIFIED IDEOGRAPH - 0xBAA1: 0x9AB8, //CJK UNIFIED IDEOGRAPH - 0xBAA2: 0x5B69, //CJK UNIFIED IDEOGRAPH - 0xBAA3: 0x6D77, //CJK UNIFIED IDEOGRAPH - 0xBAA4: 0x6C26, //CJK UNIFIED IDEOGRAPH - 0xBAA5: 0x4EA5, //CJK UNIFIED IDEOGRAPH - 0xBAA6: 0x5BB3, //CJK UNIFIED IDEOGRAPH - 0xBAA7: 0x9A87, //CJK UNIFIED IDEOGRAPH - 0xBAA8: 0x9163, //CJK UNIFIED IDEOGRAPH - 0xBAA9: 0x61A8, //CJK UNIFIED IDEOGRAPH - 0xBAAA: 0x90AF, //CJK UNIFIED IDEOGRAPH - 0xBAAB: 0x97E9, //CJK UNIFIED IDEOGRAPH - 0xBAAC: 0x542B, //CJK UNIFIED IDEOGRAPH - 0xBAAD: 0x6DB5, //CJK UNIFIED IDEOGRAPH - 0xBAAE: 0x5BD2, //CJK UNIFIED IDEOGRAPH - 0xBAAF: 0x51FD, //CJK UNIFIED IDEOGRAPH - 0xBAB0: 0x558A, //CJK UNIFIED IDEOGRAPH - 0xBAB1: 0x7F55, //CJK UNIFIED IDEOGRAPH - 0xBAB2: 0x7FF0, //CJK UNIFIED IDEOGRAPH - 0xBAB3: 0x64BC, //CJK UNIFIED IDEOGRAPH - 0xBAB4: 0x634D, //CJK UNIFIED IDEOGRAPH - 0xBAB5: 0x65F1, //CJK UNIFIED IDEOGRAPH - 0xBAB6: 0x61BE, //CJK UNIFIED IDEOGRAPH - 0xBAB7: 0x608D, //CJK UNIFIED IDEOGRAPH - 0xBAB8: 0x710A, //CJK UNIFIED IDEOGRAPH - 0xBAB9: 0x6C57, //CJK UNIFIED IDEOGRAPH - 0xBABA: 0x6C49, //CJK UNIFIED IDEOGRAPH - 0xBABB: 0x592F, //CJK UNIFIED IDEOGRAPH - 0xBABC: 0x676D, //CJK UNIFIED IDEOGRAPH - 0xBABD: 0x822A, //CJK UNIFIED IDEOGRAPH - 0xBABE: 0x58D5, //CJK UNIFIED IDEOGRAPH - 0xBABF: 0x568E, //CJK UNIFIED IDEOGRAPH - 0xBAC0: 0x8C6A, //CJK UNIFIED IDEOGRAPH - 0xBAC1: 0x6BEB, //CJK UNIFIED IDEOGRAPH - 0xBAC2: 0x90DD, //CJK UNIFIED IDEOGRAPH - 0xBAC3: 0x597D, //CJK UNIFIED IDEOGRAPH - 0xBAC4: 0x8017, //CJK UNIFIED IDEOGRAPH - 0xBAC5: 0x53F7, //CJK UNIFIED IDEOGRAPH - 0xBAC6: 0x6D69, //CJK UNIFIED IDEOGRAPH - 0xBAC7: 0x5475, //CJK UNIFIED IDEOGRAPH - 0xBAC8: 0x559D, //CJK UNIFIED IDEOGRAPH - 0xBAC9: 0x8377, //CJK UNIFIED IDEOGRAPH - 0xBACA: 0x83CF, //CJK UNIFIED IDEOGRAPH - 0xBACB: 0x6838, //CJK UNIFIED IDEOGRAPH - 0xBACC: 0x79BE, //CJK UNIFIED IDEOGRAPH - 0xBACD: 0x548C, //CJK UNIFIED IDEOGRAPH - 0xBACE: 0x4F55, //CJK UNIFIED IDEOGRAPH - 0xBACF: 0x5408, //CJK UNIFIED IDEOGRAPH - 0xBAD0: 0x76D2, //CJK UNIFIED IDEOGRAPH - 0xBAD1: 0x8C89, //CJK UNIFIED IDEOGRAPH - 0xBAD2: 0x9602, //CJK UNIFIED IDEOGRAPH - 0xBAD3: 0x6CB3, //CJK UNIFIED IDEOGRAPH - 0xBAD4: 0x6DB8, //CJK UNIFIED IDEOGRAPH - 0xBAD5: 0x8D6B, //CJK UNIFIED IDEOGRAPH - 0xBAD6: 0x8910, //CJK UNIFIED IDEOGRAPH - 0xBAD7: 0x9E64, //CJK UNIFIED IDEOGRAPH - 0xBAD8: 0x8D3A, //CJK UNIFIED IDEOGRAPH - 0xBAD9: 0x563F, //CJK UNIFIED IDEOGRAPH - 0xBADA: 0x9ED1, //CJK UNIFIED IDEOGRAPH - 0xBADB: 0x75D5, //CJK UNIFIED IDEOGRAPH - 0xBADC: 0x5F88, //CJK UNIFIED IDEOGRAPH - 0xBADD: 0x72E0, //CJK UNIFIED IDEOGRAPH - 0xBADE: 0x6068, //CJK UNIFIED IDEOGRAPH - 0xBADF: 0x54FC, //CJK UNIFIED IDEOGRAPH - 0xBAE0: 0x4EA8, //CJK UNIFIED IDEOGRAPH - 0xBAE1: 0x6A2A, //CJK UNIFIED IDEOGRAPH - 0xBAE2: 0x8861, //CJK UNIFIED IDEOGRAPH - 0xBAE3: 0x6052, //CJK UNIFIED IDEOGRAPH - 0xBAE4: 0x8F70, //CJK UNIFIED IDEOGRAPH - 0xBAE5: 0x54C4, //CJK UNIFIED IDEOGRAPH - 0xBAE6: 0x70D8, //CJK UNIFIED IDEOGRAPH - 0xBAE7: 0x8679, //CJK UNIFIED IDEOGRAPH - 0xBAE8: 0x9E3F, //CJK UNIFIED IDEOGRAPH - 0xBAE9: 0x6D2A, //CJK UNIFIED IDEOGRAPH - 0xBAEA: 0x5B8F, //CJK UNIFIED IDEOGRAPH - 0xBAEB: 0x5F18, //CJK UNIFIED IDEOGRAPH - 0xBAEC: 0x7EA2, //CJK UNIFIED IDEOGRAPH - 0xBAED: 0x5589, //CJK UNIFIED IDEOGRAPH - 0xBAEE: 0x4FAF, //CJK UNIFIED IDEOGRAPH - 0xBAEF: 0x7334, //CJK UNIFIED IDEOGRAPH - 0xBAF0: 0x543C, //CJK UNIFIED IDEOGRAPH - 0xBAF1: 0x539A, //CJK UNIFIED IDEOGRAPH - 0xBAF2: 0x5019, //CJK UNIFIED IDEOGRAPH - 0xBAF3: 0x540E, //CJK UNIFIED IDEOGRAPH - 0xBAF4: 0x547C, //CJK UNIFIED IDEOGRAPH - 0xBAF5: 0x4E4E, //CJK UNIFIED IDEOGRAPH - 0xBAF6: 0x5FFD, //CJK UNIFIED IDEOGRAPH - 0xBAF7: 0x745A, //CJK UNIFIED IDEOGRAPH - 0xBAF8: 0x58F6, //CJK UNIFIED IDEOGRAPH - 0xBAF9: 0x846B, //CJK UNIFIED IDEOGRAPH - 0xBAFA: 0x80E1, //CJK UNIFIED IDEOGRAPH - 0xBAFB: 0x8774, //CJK UNIFIED IDEOGRAPH - 0xBAFC: 0x72D0, //CJK UNIFIED IDEOGRAPH - 0xBAFD: 0x7CCA, //CJK UNIFIED IDEOGRAPH - 0xBAFE: 0x6E56, //CJK UNIFIED IDEOGRAPH - 0xBB40: 0x7C43, //CJK UNIFIED IDEOGRAPH - 0xBB41: 0x7C44, //CJK UNIFIED IDEOGRAPH - 0xBB42: 0x7C45, //CJK UNIFIED IDEOGRAPH - 0xBB43: 0x7C46, //CJK UNIFIED IDEOGRAPH - 0xBB44: 0x7C47, //CJK UNIFIED IDEOGRAPH - 0xBB45: 0x7C48, //CJK UNIFIED IDEOGRAPH - 0xBB46: 0x7C49, //CJK UNIFIED IDEOGRAPH - 0xBB47: 0x7C4A, //CJK UNIFIED IDEOGRAPH - 0xBB48: 0x7C4B, //CJK UNIFIED IDEOGRAPH - 0xBB49: 0x7C4C, //CJK UNIFIED IDEOGRAPH - 0xBB4A: 0x7C4E, //CJK UNIFIED IDEOGRAPH - 0xBB4B: 0x7C4F, //CJK UNIFIED IDEOGRAPH - 0xBB4C: 0x7C50, //CJK UNIFIED IDEOGRAPH - 0xBB4D: 0x7C51, //CJK UNIFIED IDEOGRAPH - 0xBB4E: 0x7C52, //CJK UNIFIED IDEOGRAPH - 0xBB4F: 0x7C53, //CJK UNIFIED IDEOGRAPH - 0xBB50: 0x7C54, //CJK UNIFIED IDEOGRAPH - 0xBB51: 0x7C55, //CJK UNIFIED IDEOGRAPH - 0xBB52: 0x7C56, //CJK UNIFIED IDEOGRAPH - 0xBB53: 0x7C57, //CJK UNIFIED IDEOGRAPH - 0xBB54: 0x7C58, //CJK UNIFIED IDEOGRAPH - 0xBB55: 0x7C59, //CJK UNIFIED IDEOGRAPH - 0xBB56: 0x7C5A, //CJK UNIFIED IDEOGRAPH - 0xBB57: 0x7C5B, //CJK UNIFIED IDEOGRAPH - 0xBB58: 0x7C5C, //CJK UNIFIED IDEOGRAPH - 0xBB59: 0x7C5D, //CJK UNIFIED IDEOGRAPH - 0xBB5A: 0x7C5E, //CJK UNIFIED IDEOGRAPH - 0xBB5B: 0x7C5F, //CJK UNIFIED IDEOGRAPH - 0xBB5C: 0x7C60, //CJK UNIFIED IDEOGRAPH - 0xBB5D: 0x7C61, //CJK UNIFIED IDEOGRAPH - 0xBB5E: 0x7C62, //CJK UNIFIED IDEOGRAPH - 0xBB5F: 0x7C63, //CJK UNIFIED IDEOGRAPH - 0xBB60: 0x7C64, //CJK UNIFIED IDEOGRAPH - 0xBB61: 0x7C65, //CJK UNIFIED IDEOGRAPH - 0xBB62: 0x7C66, //CJK UNIFIED IDEOGRAPH - 0xBB63: 0x7C67, //CJK UNIFIED IDEOGRAPH - 0xBB64: 0x7C68, //CJK UNIFIED IDEOGRAPH - 0xBB65: 0x7C69, //CJK UNIFIED IDEOGRAPH - 0xBB66: 0x7C6A, //CJK UNIFIED IDEOGRAPH - 0xBB67: 0x7C6B, //CJK UNIFIED IDEOGRAPH - 0xBB68: 0x7C6C, //CJK UNIFIED IDEOGRAPH - 0xBB69: 0x7C6D, //CJK UNIFIED IDEOGRAPH - 0xBB6A: 0x7C6E, //CJK UNIFIED IDEOGRAPH - 0xBB6B: 0x7C6F, //CJK UNIFIED IDEOGRAPH - 0xBB6C: 0x7C70, //CJK UNIFIED IDEOGRAPH - 0xBB6D: 0x7C71, //CJK UNIFIED IDEOGRAPH - 0xBB6E: 0x7C72, //CJK UNIFIED IDEOGRAPH - 0xBB6F: 0x7C75, //CJK UNIFIED IDEOGRAPH - 0xBB70: 0x7C76, //CJK UNIFIED IDEOGRAPH - 0xBB71: 0x7C77, //CJK UNIFIED IDEOGRAPH - 0xBB72: 0x7C78, //CJK UNIFIED IDEOGRAPH - 0xBB73: 0x7C79, //CJK UNIFIED IDEOGRAPH - 0xBB74: 0x7C7A, //CJK UNIFIED IDEOGRAPH - 0xBB75: 0x7C7E, //CJK UNIFIED IDEOGRAPH - 0xBB76: 0x7C7F, //CJK UNIFIED IDEOGRAPH - 0xBB77: 0x7C80, //CJK UNIFIED IDEOGRAPH - 0xBB78: 0x7C81, //CJK UNIFIED IDEOGRAPH - 0xBB79: 0x7C82, //CJK UNIFIED IDEOGRAPH - 0xBB7A: 0x7C83, //CJK UNIFIED IDEOGRAPH - 0xBB7B: 0x7C84, //CJK UNIFIED IDEOGRAPH - 0xBB7C: 0x7C85, //CJK UNIFIED IDEOGRAPH - 0xBB7D: 0x7C86, //CJK UNIFIED IDEOGRAPH - 0xBB7E: 0x7C87, //CJK UNIFIED IDEOGRAPH - 0xBB80: 0x7C88, //CJK UNIFIED IDEOGRAPH - 0xBB81: 0x7C8A, //CJK UNIFIED IDEOGRAPH - 0xBB82: 0x7C8B, //CJK UNIFIED IDEOGRAPH - 0xBB83: 0x7C8C, //CJK UNIFIED IDEOGRAPH - 0xBB84: 0x7C8D, //CJK UNIFIED IDEOGRAPH - 0xBB85: 0x7C8E, //CJK UNIFIED IDEOGRAPH - 0xBB86: 0x7C8F, //CJK UNIFIED IDEOGRAPH - 0xBB87: 0x7C90, //CJK UNIFIED IDEOGRAPH - 0xBB88: 0x7C93, //CJK UNIFIED IDEOGRAPH - 0xBB89: 0x7C94, //CJK UNIFIED IDEOGRAPH - 0xBB8A: 0x7C96, //CJK UNIFIED IDEOGRAPH - 0xBB8B: 0x7C99, //CJK UNIFIED IDEOGRAPH - 0xBB8C: 0x7C9A, //CJK UNIFIED IDEOGRAPH - 0xBB8D: 0x7C9B, //CJK UNIFIED IDEOGRAPH - 0xBB8E: 0x7CA0, //CJK UNIFIED IDEOGRAPH - 0xBB8F: 0x7CA1, //CJK UNIFIED IDEOGRAPH - 0xBB90: 0x7CA3, //CJK UNIFIED IDEOGRAPH - 0xBB91: 0x7CA6, //CJK UNIFIED IDEOGRAPH - 0xBB92: 0x7CA7, //CJK UNIFIED IDEOGRAPH - 0xBB93: 0x7CA8, //CJK UNIFIED IDEOGRAPH - 0xBB94: 0x7CA9, //CJK UNIFIED IDEOGRAPH - 0xBB95: 0x7CAB, //CJK UNIFIED IDEOGRAPH - 0xBB96: 0x7CAC, //CJK UNIFIED IDEOGRAPH - 0xBB97: 0x7CAD, //CJK UNIFIED IDEOGRAPH - 0xBB98: 0x7CAF, //CJK UNIFIED IDEOGRAPH - 0xBB99: 0x7CB0, //CJK UNIFIED IDEOGRAPH - 0xBB9A: 0x7CB4, //CJK UNIFIED IDEOGRAPH - 0xBB9B: 0x7CB5, //CJK UNIFIED IDEOGRAPH - 0xBB9C: 0x7CB6, //CJK UNIFIED IDEOGRAPH - 0xBB9D: 0x7CB7, //CJK UNIFIED IDEOGRAPH - 0xBB9E: 0x7CB8, //CJK UNIFIED IDEOGRAPH - 0xBB9F: 0x7CBA, //CJK UNIFIED IDEOGRAPH - 0xBBA0: 0x7CBB, //CJK UNIFIED IDEOGRAPH - 0xBBA1: 0x5F27, //CJK UNIFIED IDEOGRAPH - 0xBBA2: 0x864E, //CJK UNIFIED IDEOGRAPH - 0xBBA3: 0x552C, //CJK UNIFIED IDEOGRAPH - 0xBBA4: 0x62A4, //CJK UNIFIED IDEOGRAPH - 0xBBA5: 0x4E92, //CJK UNIFIED IDEOGRAPH - 0xBBA6: 0x6CAA, //CJK UNIFIED IDEOGRAPH - 0xBBA7: 0x6237, //CJK UNIFIED IDEOGRAPH - 0xBBA8: 0x82B1, //CJK UNIFIED IDEOGRAPH - 0xBBA9: 0x54D7, //CJK UNIFIED IDEOGRAPH - 0xBBAA: 0x534E, //CJK UNIFIED IDEOGRAPH - 0xBBAB: 0x733E, //CJK UNIFIED IDEOGRAPH - 0xBBAC: 0x6ED1, //CJK UNIFIED IDEOGRAPH - 0xBBAD: 0x753B, //CJK UNIFIED IDEOGRAPH - 0xBBAE: 0x5212, //CJK UNIFIED IDEOGRAPH - 0xBBAF: 0x5316, //CJK UNIFIED IDEOGRAPH - 0xBBB0: 0x8BDD, //CJK UNIFIED IDEOGRAPH - 0xBBB1: 0x69D0, //CJK UNIFIED IDEOGRAPH - 0xBBB2: 0x5F8A, //CJK UNIFIED IDEOGRAPH - 0xBBB3: 0x6000, //CJK UNIFIED IDEOGRAPH - 0xBBB4: 0x6DEE, //CJK UNIFIED IDEOGRAPH - 0xBBB5: 0x574F, //CJK UNIFIED IDEOGRAPH - 0xBBB6: 0x6B22, //CJK UNIFIED IDEOGRAPH - 0xBBB7: 0x73AF, //CJK UNIFIED IDEOGRAPH - 0xBBB8: 0x6853, //CJK UNIFIED IDEOGRAPH - 0xBBB9: 0x8FD8, //CJK UNIFIED IDEOGRAPH - 0xBBBA: 0x7F13, //CJK UNIFIED IDEOGRAPH - 0xBBBB: 0x6362, //CJK UNIFIED IDEOGRAPH - 0xBBBC: 0x60A3, //CJK UNIFIED IDEOGRAPH - 0xBBBD: 0x5524, //CJK UNIFIED IDEOGRAPH - 0xBBBE: 0x75EA, //CJK UNIFIED IDEOGRAPH - 0xBBBF: 0x8C62, //CJK UNIFIED IDEOGRAPH - 0xBBC0: 0x7115, //CJK UNIFIED IDEOGRAPH - 0xBBC1: 0x6DA3, //CJK UNIFIED IDEOGRAPH - 0xBBC2: 0x5BA6, //CJK UNIFIED IDEOGRAPH - 0xBBC3: 0x5E7B, //CJK UNIFIED IDEOGRAPH - 0xBBC4: 0x8352, //CJK UNIFIED IDEOGRAPH - 0xBBC5: 0x614C, //CJK UNIFIED IDEOGRAPH - 0xBBC6: 0x9EC4, //CJK UNIFIED IDEOGRAPH - 0xBBC7: 0x78FA, //CJK UNIFIED IDEOGRAPH - 0xBBC8: 0x8757, //CJK UNIFIED IDEOGRAPH - 0xBBC9: 0x7C27, //CJK UNIFIED IDEOGRAPH - 0xBBCA: 0x7687, //CJK UNIFIED IDEOGRAPH - 0xBBCB: 0x51F0, //CJK UNIFIED IDEOGRAPH - 0xBBCC: 0x60F6, //CJK UNIFIED IDEOGRAPH - 0xBBCD: 0x714C, //CJK UNIFIED IDEOGRAPH - 0xBBCE: 0x6643, //CJK UNIFIED IDEOGRAPH - 0xBBCF: 0x5E4C, //CJK UNIFIED IDEOGRAPH - 0xBBD0: 0x604D, //CJK UNIFIED IDEOGRAPH - 0xBBD1: 0x8C0E, //CJK UNIFIED IDEOGRAPH - 0xBBD2: 0x7070, //CJK UNIFIED IDEOGRAPH - 0xBBD3: 0x6325, //CJK UNIFIED IDEOGRAPH - 0xBBD4: 0x8F89, //CJK UNIFIED IDEOGRAPH - 0xBBD5: 0x5FBD, //CJK UNIFIED IDEOGRAPH - 0xBBD6: 0x6062, //CJK UNIFIED IDEOGRAPH - 0xBBD7: 0x86D4, //CJK UNIFIED IDEOGRAPH - 0xBBD8: 0x56DE, //CJK UNIFIED IDEOGRAPH - 0xBBD9: 0x6BC1, //CJK UNIFIED IDEOGRAPH - 0xBBDA: 0x6094, //CJK UNIFIED IDEOGRAPH - 0xBBDB: 0x6167, //CJK UNIFIED IDEOGRAPH - 0xBBDC: 0x5349, //CJK UNIFIED IDEOGRAPH - 0xBBDD: 0x60E0, //CJK UNIFIED IDEOGRAPH - 0xBBDE: 0x6666, //CJK UNIFIED IDEOGRAPH - 0xBBDF: 0x8D3F, //CJK UNIFIED IDEOGRAPH - 0xBBE0: 0x79FD, //CJK UNIFIED IDEOGRAPH - 0xBBE1: 0x4F1A, //CJK UNIFIED IDEOGRAPH - 0xBBE2: 0x70E9, //CJK UNIFIED IDEOGRAPH - 0xBBE3: 0x6C47, //CJK UNIFIED IDEOGRAPH - 0xBBE4: 0x8BB3, //CJK UNIFIED IDEOGRAPH - 0xBBE5: 0x8BF2, //CJK UNIFIED IDEOGRAPH - 0xBBE6: 0x7ED8, //CJK UNIFIED IDEOGRAPH - 0xBBE7: 0x8364, //CJK UNIFIED IDEOGRAPH - 0xBBE8: 0x660F, //CJK UNIFIED IDEOGRAPH - 0xBBE9: 0x5A5A, //CJK UNIFIED IDEOGRAPH - 0xBBEA: 0x9B42, //CJK UNIFIED IDEOGRAPH - 0xBBEB: 0x6D51, //CJK UNIFIED IDEOGRAPH - 0xBBEC: 0x6DF7, //CJK UNIFIED IDEOGRAPH - 0xBBED: 0x8C41, //CJK UNIFIED IDEOGRAPH - 0xBBEE: 0x6D3B, //CJK UNIFIED IDEOGRAPH - 0xBBEF: 0x4F19, //CJK UNIFIED IDEOGRAPH - 0xBBF0: 0x706B, //CJK UNIFIED IDEOGRAPH - 0xBBF1: 0x83B7, //CJK UNIFIED IDEOGRAPH - 0xBBF2: 0x6216, //CJK UNIFIED IDEOGRAPH - 0xBBF3: 0x60D1, //CJK UNIFIED IDEOGRAPH - 0xBBF4: 0x970D, //CJK UNIFIED IDEOGRAPH - 0xBBF5: 0x8D27, //CJK UNIFIED IDEOGRAPH - 0xBBF6: 0x7978, //CJK UNIFIED IDEOGRAPH - 0xBBF7: 0x51FB, //CJK UNIFIED IDEOGRAPH - 0xBBF8: 0x573E, //CJK UNIFIED IDEOGRAPH - 0xBBF9: 0x57FA, //CJK UNIFIED IDEOGRAPH - 0xBBFA: 0x673A, //CJK UNIFIED IDEOGRAPH - 0xBBFB: 0x7578, //CJK UNIFIED IDEOGRAPH - 0xBBFC: 0x7A3D, //CJK UNIFIED IDEOGRAPH - 0xBBFD: 0x79EF, //CJK UNIFIED IDEOGRAPH - 0xBBFE: 0x7B95, //CJK UNIFIED IDEOGRAPH - 0xBC40: 0x7CBF, //CJK UNIFIED IDEOGRAPH - 0xBC41: 0x7CC0, //CJK UNIFIED IDEOGRAPH - 0xBC42: 0x7CC2, //CJK UNIFIED IDEOGRAPH - 0xBC43: 0x7CC3, //CJK UNIFIED IDEOGRAPH - 0xBC44: 0x7CC4, //CJK UNIFIED IDEOGRAPH - 0xBC45: 0x7CC6, //CJK UNIFIED IDEOGRAPH - 0xBC46: 0x7CC9, //CJK UNIFIED IDEOGRAPH - 0xBC47: 0x7CCB, //CJK UNIFIED IDEOGRAPH - 0xBC48: 0x7CCE, //CJK UNIFIED IDEOGRAPH - 0xBC49: 0x7CCF, //CJK UNIFIED IDEOGRAPH - 0xBC4A: 0x7CD0, //CJK UNIFIED IDEOGRAPH - 0xBC4B: 0x7CD1, //CJK UNIFIED IDEOGRAPH - 0xBC4C: 0x7CD2, //CJK UNIFIED IDEOGRAPH - 0xBC4D: 0x7CD3, //CJK UNIFIED IDEOGRAPH - 0xBC4E: 0x7CD4, //CJK UNIFIED IDEOGRAPH - 0xBC4F: 0x7CD8, //CJK UNIFIED IDEOGRAPH - 0xBC50: 0x7CDA, //CJK UNIFIED IDEOGRAPH - 0xBC51: 0x7CDB, //CJK UNIFIED IDEOGRAPH - 0xBC52: 0x7CDD, //CJK UNIFIED IDEOGRAPH - 0xBC53: 0x7CDE, //CJK UNIFIED IDEOGRAPH - 0xBC54: 0x7CE1, //CJK UNIFIED IDEOGRAPH - 0xBC55: 0x7CE2, //CJK UNIFIED IDEOGRAPH - 0xBC56: 0x7CE3, //CJK UNIFIED IDEOGRAPH - 0xBC57: 0x7CE4, //CJK UNIFIED IDEOGRAPH - 0xBC58: 0x7CE5, //CJK UNIFIED IDEOGRAPH - 0xBC59: 0x7CE6, //CJK UNIFIED IDEOGRAPH - 0xBC5A: 0x7CE7, //CJK UNIFIED IDEOGRAPH - 0xBC5B: 0x7CE9, //CJK UNIFIED IDEOGRAPH - 0xBC5C: 0x7CEA, //CJK UNIFIED IDEOGRAPH - 0xBC5D: 0x7CEB, //CJK UNIFIED IDEOGRAPH - 0xBC5E: 0x7CEC, //CJK UNIFIED IDEOGRAPH - 0xBC5F: 0x7CED, //CJK UNIFIED IDEOGRAPH - 0xBC60: 0x7CEE, //CJK UNIFIED IDEOGRAPH - 0xBC61: 0x7CF0, //CJK UNIFIED IDEOGRAPH - 0xBC62: 0x7CF1, //CJK UNIFIED IDEOGRAPH - 0xBC63: 0x7CF2, //CJK UNIFIED IDEOGRAPH - 0xBC64: 0x7CF3, //CJK UNIFIED IDEOGRAPH - 0xBC65: 0x7CF4, //CJK UNIFIED IDEOGRAPH - 0xBC66: 0x7CF5, //CJK UNIFIED IDEOGRAPH - 0xBC67: 0x7CF6, //CJK UNIFIED IDEOGRAPH - 0xBC68: 0x7CF7, //CJK UNIFIED IDEOGRAPH - 0xBC69: 0x7CF9, //CJK UNIFIED IDEOGRAPH - 0xBC6A: 0x7CFA, //CJK UNIFIED IDEOGRAPH - 0xBC6B: 0x7CFC, //CJK UNIFIED IDEOGRAPH - 0xBC6C: 0x7CFD, //CJK UNIFIED IDEOGRAPH - 0xBC6D: 0x7CFE, //CJK UNIFIED IDEOGRAPH - 0xBC6E: 0x7CFF, //CJK UNIFIED IDEOGRAPH - 0xBC6F: 0x7D00, //CJK UNIFIED IDEOGRAPH - 0xBC70: 0x7D01, //CJK UNIFIED IDEOGRAPH - 0xBC71: 0x7D02, //CJK UNIFIED IDEOGRAPH - 0xBC72: 0x7D03, //CJK UNIFIED IDEOGRAPH - 0xBC73: 0x7D04, //CJK UNIFIED IDEOGRAPH - 0xBC74: 0x7D05, //CJK UNIFIED IDEOGRAPH - 0xBC75: 0x7D06, //CJK UNIFIED IDEOGRAPH - 0xBC76: 0x7D07, //CJK UNIFIED IDEOGRAPH - 0xBC77: 0x7D08, //CJK UNIFIED IDEOGRAPH - 0xBC78: 0x7D09, //CJK UNIFIED IDEOGRAPH - 0xBC79: 0x7D0B, //CJK UNIFIED IDEOGRAPH - 0xBC7A: 0x7D0C, //CJK UNIFIED IDEOGRAPH - 0xBC7B: 0x7D0D, //CJK UNIFIED IDEOGRAPH - 0xBC7C: 0x7D0E, //CJK UNIFIED IDEOGRAPH - 0xBC7D: 0x7D0F, //CJK UNIFIED IDEOGRAPH - 0xBC7E: 0x7D10, //CJK UNIFIED IDEOGRAPH - 0xBC80: 0x7D11, //CJK UNIFIED IDEOGRAPH - 0xBC81: 0x7D12, //CJK UNIFIED IDEOGRAPH - 0xBC82: 0x7D13, //CJK UNIFIED IDEOGRAPH - 0xBC83: 0x7D14, //CJK UNIFIED IDEOGRAPH - 0xBC84: 0x7D15, //CJK UNIFIED IDEOGRAPH - 0xBC85: 0x7D16, //CJK UNIFIED IDEOGRAPH - 0xBC86: 0x7D17, //CJK UNIFIED IDEOGRAPH - 0xBC87: 0x7D18, //CJK UNIFIED IDEOGRAPH - 0xBC88: 0x7D19, //CJK UNIFIED IDEOGRAPH - 0xBC89: 0x7D1A, //CJK UNIFIED IDEOGRAPH - 0xBC8A: 0x7D1B, //CJK UNIFIED IDEOGRAPH - 0xBC8B: 0x7D1C, //CJK UNIFIED IDEOGRAPH - 0xBC8C: 0x7D1D, //CJK UNIFIED IDEOGRAPH - 0xBC8D: 0x7D1E, //CJK UNIFIED IDEOGRAPH - 0xBC8E: 0x7D1F, //CJK UNIFIED IDEOGRAPH - 0xBC8F: 0x7D21, //CJK UNIFIED IDEOGRAPH - 0xBC90: 0x7D23, //CJK UNIFIED IDEOGRAPH - 0xBC91: 0x7D24, //CJK UNIFIED IDEOGRAPH - 0xBC92: 0x7D25, //CJK UNIFIED IDEOGRAPH - 0xBC93: 0x7D26, //CJK UNIFIED IDEOGRAPH - 0xBC94: 0x7D28, //CJK UNIFIED IDEOGRAPH - 0xBC95: 0x7D29, //CJK UNIFIED IDEOGRAPH - 0xBC96: 0x7D2A, //CJK UNIFIED IDEOGRAPH - 0xBC97: 0x7D2C, //CJK UNIFIED IDEOGRAPH - 0xBC98: 0x7D2D, //CJK UNIFIED IDEOGRAPH - 0xBC99: 0x7D2E, //CJK UNIFIED IDEOGRAPH - 0xBC9A: 0x7D30, //CJK UNIFIED IDEOGRAPH - 0xBC9B: 0x7D31, //CJK UNIFIED IDEOGRAPH - 0xBC9C: 0x7D32, //CJK UNIFIED IDEOGRAPH - 0xBC9D: 0x7D33, //CJK UNIFIED IDEOGRAPH - 0xBC9E: 0x7D34, //CJK UNIFIED IDEOGRAPH - 0xBC9F: 0x7D35, //CJK UNIFIED IDEOGRAPH - 0xBCA0: 0x7D36, //CJK UNIFIED IDEOGRAPH - 0xBCA1: 0x808C, //CJK UNIFIED IDEOGRAPH - 0xBCA2: 0x9965, //CJK UNIFIED IDEOGRAPH - 0xBCA3: 0x8FF9, //CJK UNIFIED IDEOGRAPH - 0xBCA4: 0x6FC0, //CJK UNIFIED IDEOGRAPH - 0xBCA5: 0x8BA5, //CJK UNIFIED IDEOGRAPH - 0xBCA6: 0x9E21, //CJK UNIFIED IDEOGRAPH - 0xBCA7: 0x59EC, //CJK UNIFIED IDEOGRAPH - 0xBCA8: 0x7EE9, //CJK UNIFIED IDEOGRAPH - 0xBCA9: 0x7F09, //CJK UNIFIED IDEOGRAPH - 0xBCAA: 0x5409, //CJK UNIFIED IDEOGRAPH - 0xBCAB: 0x6781, //CJK UNIFIED IDEOGRAPH - 0xBCAC: 0x68D8, //CJK UNIFIED IDEOGRAPH - 0xBCAD: 0x8F91, //CJK UNIFIED IDEOGRAPH - 0xBCAE: 0x7C4D, //CJK UNIFIED IDEOGRAPH - 0xBCAF: 0x96C6, //CJK UNIFIED IDEOGRAPH - 0xBCB0: 0x53CA, //CJK UNIFIED IDEOGRAPH - 0xBCB1: 0x6025, //CJK UNIFIED IDEOGRAPH - 0xBCB2: 0x75BE, //CJK UNIFIED IDEOGRAPH - 0xBCB3: 0x6C72, //CJK UNIFIED IDEOGRAPH - 0xBCB4: 0x5373, //CJK UNIFIED IDEOGRAPH - 0xBCB5: 0x5AC9, //CJK UNIFIED IDEOGRAPH - 0xBCB6: 0x7EA7, //CJK UNIFIED IDEOGRAPH - 0xBCB7: 0x6324, //CJK UNIFIED IDEOGRAPH - 0xBCB8: 0x51E0, //CJK UNIFIED IDEOGRAPH - 0xBCB9: 0x810A, //CJK UNIFIED IDEOGRAPH - 0xBCBA: 0x5DF1, //CJK UNIFIED IDEOGRAPH - 0xBCBB: 0x84DF, //CJK UNIFIED IDEOGRAPH - 0xBCBC: 0x6280, //CJK UNIFIED IDEOGRAPH - 0xBCBD: 0x5180, //CJK UNIFIED IDEOGRAPH - 0xBCBE: 0x5B63, //CJK UNIFIED IDEOGRAPH - 0xBCBF: 0x4F0E, //CJK UNIFIED IDEOGRAPH - 0xBCC0: 0x796D, //CJK UNIFIED IDEOGRAPH - 0xBCC1: 0x5242, //CJK UNIFIED IDEOGRAPH - 0xBCC2: 0x60B8, //CJK UNIFIED IDEOGRAPH - 0xBCC3: 0x6D4E, //CJK UNIFIED IDEOGRAPH - 0xBCC4: 0x5BC4, //CJK UNIFIED IDEOGRAPH - 0xBCC5: 0x5BC2, //CJK UNIFIED IDEOGRAPH - 0xBCC6: 0x8BA1, //CJK UNIFIED IDEOGRAPH - 0xBCC7: 0x8BB0, //CJK UNIFIED IDEOGRAPH - 0xBCC8: 0x65E2, //CJK UNIFIED IDEOGRAPH - 0xBCC9: 0x5FCC, //CJK UNIFIED IDEOGRAPH - 0xBCCA: 0x9645, //CJK UNIFIED IDEOGRAPH - 0xBCCB: 0x5993, //CJK UNIFIED IDEOGRAPH - 0xBCCC: 0x7EE7, //CJK UNIFIED IDEOGRAPH - 0xBCCD: 0x7EAA, //CJK UNIFIED IDEOGRAPH - 0xBCCE: 0x5609, //CJK UNIFIED IDEOGRAPH - 0xBCCF: 0x67B7, //CJK UNIFIED IDEOGRAPH - 0xBCD0: 0x5939, //CJK UNIFIED IDEOGRAPH - 0xBCD1: 0x4F73, //CJK UNIFIED IDEOGRAPH - 0xBCD2: 0x5BB6, //CJK UNIFIED IDEOGRAPH - 0xBCD3: 0x52A0, //CJK UNIFIED IDEOGRAPH - 0xBCD4: 0x835A, //CJK UNIFIED IDEOGRAPH - 0xBCD5: 0x988A, //CJK UNIFIED IDEOGRAPH - 0xBCD6: 0x8D3E, //CJK UNIFIED IDEOGRAPH - 0xBCD7: 0x7532, //CJK UNIFIED IDEOGRAPH - 0xBCD8: 0x94BE, //CJK UNIFIED IDEOGRAPH - 0xBCD9: 0x5047, //CJK UNIFIED IDEOGRAPH - 0xBCDA: 0x7A3C, //CJK UNIFIED IDEOGRAPH - 0xBCDB: 0x4EF7, //CJK UNIFIED IDEOGRAPH - 0xBCDC: 0x67B6, //CJK UNIFIED IDEOGRAPH - 0xBCDD: 0x9A7E, //CJK UNIFIED IDEOGRAPH - 0xBCDE: 0x5AC1, //CJK UNIFIED IDEOGRAPH - 0xBCDF: 0x6B7C, //CJK UNIFIED IDEOGRAPH - 0xBCE0: 0x76D1, //CJK UNIFIED IDEOGRAPH - 0xBCE1: 0x575A, //CJK UNIFIED IDEOGRAPH - 0xBCE2: 0x5C16, //CJK UNIFIED IDEOGRAPH - 0xBCE3: 0x7B3A, //CJK UNIFIED IDEOGRAPH - 0xBCE4: 0x95F4, //CJK UNIFIED IDEOGRAPH - 0xBCE5: 0x714E, //CJK UNIFIED IDEOGRAPH - 0xBCE6: 0x517C, //CJK UNIFIED IDEOGRAPH - 0xBCE7: 0x80A9, //CJK UNIFIED IDEOGRAPH - 0xBCE8: 0x8270, //CJK UNIFIED IDEOGRAPH - 0xBCE9: 0x5978, //CJK UNIFIED IDEOGRAPH - 0xBCEA: 0x7F04, //CJK UNIFIED IDEOGRAPH - 0xBCEB: 0x8327, //CJK UNIFIED IDEOGRAPH - 0xBCEC: 0x68C0, //CJK UNIFIED IDEOGRAPH - 0xBCED: 0x67EC, //CJK UNIFIED IDEOGRAPH - 0xBCEE: 0x78B1, //CJK UNIFIED IDEOGRAPH - 0xBCEF: 0x7877, //CJK UNIFIED IDEOGRAPH - 0xBCF0: 0x62E3, //CJK UNIFIED IDEOGRAPH - 0xBCF1: 0x6361, //CJK UNIFIED IDEOGRAPH - 0xBCF2: 0x7B80, //CJK UNIFIED IDEOGRAPH - 0xBCF3: 0x4FED, //CJK UNIFIED IDEOGRAPH - 0xBCF4: 0x526A, //CJK UNIFIED IDEOGRAPH - 0xBCF5: 0x51CF, //CJK UNIFIED IDEOGRAPH - 0xBCF6: 0x8350, //CJK UNIFIED IDEOGRAPH - 0xBCF7: 0x69DB, //CJK UNIFIED IDEOGRAPH - 0xBCF8: 0x9274, //CJK UNIFIED IDEOGRAPH - 0xBCF9: 0x8DF5, //CJK UNIFIED IDEOGRAPH - 0xBCFA: 0x8D31, //CJK UNIFIED IDEOGRAPH - 0xBCFB: 0x89C1, //CJK UNIFIED IDEOGRAPH - 0xBCFC: 0x952E, //CJK UNIFIED IDEOGRAPH - 0xBCFD: 0x7BAD, //CJK UNIFIED IDEOGRAPH - 0xBCFE: 0x4EF6, //CJK UNIFIED IDEOGRAPH - 0xBD40: 0x7D37, //CJK UNIFIED IDEOGRAPH - 0xBD41: 0x7D38, //CJK UNIFIED IDEOGRAPH - 0xBD42: 0x7D39, //CJK UNIFIED IDEOGRAPH - 0xBD43: 0x7D3A, //CJK UNIFIED IDEOGRAPH - 0xBD44: 0x7D3B, //CJK UNIFIED IDEOGRAPH - 0xBD45: 0x7D3C, //CJK UNIFIED IDEOGRAPH - 0xBD46: 0x7D3D, //CJK UNIFIED IDEOGRAPH - 0xBD47: 0x7D3E, //CJK UNIFIED IDEOGRAPH - 0xBD48: 0x7D3F, //CJK UNIFIED IDEOGRAPH - 0xBD49: 0x7D40, //CJK UNIFIED IDEOGRAPH - 0xBD4A: 0x7D41, //CJK UNIFIED IDEOGRAPH - 0xBD4B: 0x7D42, //CJK UNIFIED IDEOGRAPH - 0xBD4C: 0x7D43, //CJK UNIFIED IDEOGRAPH - 0xBD4D: 0x7D44, //CJK UNIFIED IDEOGRAPH - 0xBD4E: 0x7D45, //CJK UNIFIED IDEOGRAPH - 0xBD4F: 0x7D46, //CJK UNIFIED IDEOGRAPH - 0xBD50: 0x7D47, //CJK UNIFIED IDEOGRAPH - 0xBD51: 0x7D48, //CJK UNIFIED IDEOGRAPH - 0xBD52: 0x7D49, //CJK UNIFIED IDEOGRAPH - 0xBD53: 0x7D4A, //CJK UNIFIED IDEOGRAPH - 0xBD54: 0x7D4B, //CJK UNIFIED IDEOGRAPH - 0xBD55: 0x7D4C, //CJK UNIFIED IDEOGRAPH - 0xBD56: 0x7D4D, //CJK UNIFIED IDEOGRAPH - 0xBD57: 0x7D4E, //CJK UNIFIED IDEOGRAPH - 0xBD58: 0x7D4F, //CJK UNIFIED IDEOGRAPH - 0xBD59: 0x7D50, //CJK UNIFIED IDEOGRAPH - 0xBD5A: 0x7D51, //CJK UNIFIED IDEOGRAPH - 0xBD5B: 0x7D52, //CJK UNIFIED IDEOGRAPH - 0xBD5C: 0x7D53, //CJK UNIFIED IDEOGRAPH - 0xBD5D: 0x7D54, //CJK UNIFIED IDEOGRAPH - 0xBD5E: 0x7D55, //CJK UNIFIED IDEOGRAPH - 0xBD5F: 0x7D56, //CJK UNIFIED IDEOGRAPH - 0xBD60: 0x7D57, //CJK UNIFIED IDEOGRAPH - 0xBD61: 0x7D58, //CJK UNIFIED IDEOGRAPH - 0xBD62: 0x7D59, //CJK UNIFIED IDEOGRAPH - 0xBD63: 0x7D5A, //CJK UNIFIED IDEOGRAPH - 0xBD64: 0x7D5B, //CJK UNIFIED IDEOGRAPH - 0xBD65: 0x7D5C, //CJK UNIFIED IDEOGRAPH - 0xBD66: 0x7D5D, //CJK UNIFIED IDEOGRAPH - 0xBD67: 0x7D5E, //CJK UNIFIED IDEOGRAPH - 0xBD68: 0x7D5F, //CJK UNIFIED IDEOGRAPH - 0xBD69: 0x7D60, //CJK UNIFIED IDEOGRAPH - 0xBD6A: 0x7D61, //CJK UNIFIED IDEOGRAPH - 0xBD6B: 0x7D62, //CJK UNIFIED IDEOGRAPH - 0xBD6C: 0x7D63, //CJK UNIFIED IDEOGRAPH - 0xBD6D: 0x7D64, //CJK UNIFIED IDEOGRAPH - 0xBD6E: 0x7D65, //CJK UNIFIED IDEOGRAPH - 0xBD6F: 0x7D66, //CJK UNIFIED IDEOGRAPH - 0xBD70: 0x7D67, //CJK UNIFIED IDEOGRAPH - 0xBD71: 0x7D68, //CJK UNIFIED IDEOGRAPH - 0xBD72: 0x7D69, //CJK UNIFIED IDEOGRAPH - 0xBD73: 0x7D6A, //CJK UNIFIED IDEOGRAPH - 0xBD74: 0x7D6B, //CJK UNIFIED IDEOGRAPH - 0xBD75: 0x7D6C, //CJK UNIFIED IDEOGRAPH - 0xBD76: 0x7D6D, //CJK UNIFIED IDEOGRAPH - 0xBD77: 0x7D6F, //CJK UNIFIED IDEOGRAPH - 0xBD78: 0x7D70, //CJK UNIFIED IDEOGRAPH - 0xBD79: 0x7D71, //CJK UNIFIED IDEOGRAPH - 0xBD7A: 0x7D72, //CJK UNIFIED IDEOGRAPH - 0xBD7B: 0x7D73, //CJK UNIFIED IDEOGRAPH - 0xBD7C: 0x7D74, //CJK UNIFIED IDEOGRAPH - 0xBD7D: 0x7D75, //CJK UNIFIED IDEOGRAPH - 0xBD7E: 0x7D76, //CJK UNIFIED IDEOGRAPH - 0xBD80: 0x7D78, //CJK UNIFIED IDEOGRAPH - 0xBD81: 0x7D79, //CJK UNIFIED IDEOGRAPH - 0xBD82: 0x7D7A, //CJK UNIFIED IDEOGRAPH - 0xBD83: 0x7D7B, //CJK UNIFIED IDEOGRAPH - 0xBD84: 0x7D7C, //CJK UNIFIED IDEOGRAPH - 0xBD85: 0x7D7D, //CJK UNIFIED IDEOGRAPH - 0xBD86: 0x7D7E, //CJK UNIFIED IDEOGRAPH - 0xBD87: 0x7D7F, //CJK UNIFIED IDEOGRAPH - 0xBD88: 0x7D80, //CJK UNIFIED IDEOGRAPH - 0xBD89: 0x7D81, //CJK UNIFIED IDEOGRAPH - 0xBD8A: 0x7D82, //CJK UNIFIED IDEOGRAPH - 0xBD8B: 0x7D83, //CJK UNIFIED IDEOGRAPH - 0xBD8C: 0x7D84, //CJK UNIFIED IDEOGRAPH - 0xBD8D: 0x7D85, //CJK UNIFIED IDEOGRAPH - 0xBD8E: 0x7D86, //CJK UNIFIED IDEOGRAPH - 0xBD8F: 0x7D87, //CJK UNIFIED IDEOGRAPH - 0xBD90: 0x7D88, //CJK UNIFIED IDEOGRAPH - 0xBD91: 0x7D89, //CJK UNIFIED IDEOGRAPH - 0xBD92: 0x7D8A, //CJK UNIFIED IDEOGRAPH - 0xBD93: 0x7D8B, //CJK UNIFIED IDEOGRAPH - 0xBD94: 0x7D8C, //CJK UNIFIED IDEOGRAPH - 0xBD95: 0x7D8D, //CJK UNIFIED IDEOGRAPH - 0xBD96: 0x7D8E, //CJK UNIFIED IDEOGRAPH - 0xBD97: 0x7D8F, //CJK UNIFIED IDEOGRAPH - 0xBD98: 0x7D90, //CJK UNIFIED IDEOGRAPH - 0xBD99: 0x7D91, //CJK UNIFIED IDEOGRAPH - 0xBD9A: 0x7D92, //CJK UNIFIED IDEOGRAPH - 0xBD9B: 0x7D93, //CJK UNIFIED IDEOGRAPH - 0xBD9C: 0x7D94, //CJK UNIFIED IDEOGRAPH - 0xBD9D: 0x7D95, //CJK UNIFIED IDEOGRAPH - 0xBD9E: 0x7D96, //CJK UNIFIED IDEOGRAPH - 0xBD9F: 0x7D97, //CJK UNIFIED IDEOGRAPH - 0xBDA0: 0x7D98, //CJK UNIFIED IDEOGRAPH - 0xBDA1: 0x5065, //CJK UNIFIED IDEOGRAPH - 0xBDA2: 0x8230, //CJK UNIFIED IDEOGRAPH - 0xBDA3: 0x5251, //CJK UNIFIED IDEOGRAPH - 0xBDA4: 0x996F, //CJK UNIFIED IDEOGRAPH - 0xBDA5: 0x6E10, //CJK UNIFIED IDEOGRAPH - 0xBDA6: 0x6E85, //CJK UNIFIED IDEOGRAPH - 0xBDA7: 0x6DA7, //CJK UNIFIED IDEOGRAPH - 0xBDA8: 0x5EFA, //CJK UNIFIED IDEOGRAPH - 0xBDA9: 0x50F5, //CJK UNIFIED IDEOGRAPH - 0xBDAA: 0x59DC, //CJK UNIFIED IDEOGRAPH - 0xBDAB: 0x5C06, //CJK UNIFIED IDEOGRAPH - 0xBDAC: 0x6D46, //CJK UNIFIED IDEOGRAPH - 0xBDAD: 0x6C5F, //CJK UNIFIED IDEOGRAPH - 0xBDAE: 0x7586, //CJK UNIFIED IDEOGRAPH - 0xBDAF: 0x848B, //CJK UNIFIED IDEOGRAPH - 0xBDB0: 0x6868, //CJK UNIFIED IDEOGRAPH - 0xBDB1: 0x5956, //CJK UNIFIED IDEOGRAPH - 0xBDB2: 0x8BB2, //CJK UNIFIED IDEOGRAPH - 0xBDB3: 0x5320, //CJK UNIFIED IDEOGRAPH - 0xBDB4: 0x9171, //CJK UNIFIED IDEOGRAPH - 0xBDB5: 0x964D, //CJK UNIFIED IDEOGRAPH - 0xBDB6: 0x8549, //CJK UNIFIED IDEOGRAPH - 0xBDB7: 0x6912, //CJK UNIFIED IDEOGRAPH - 0xBDB8: 0x7901, //CJK UNIFIED IDEOGRAPH - 0xBDB9: 0x7126, //CJK UNIFIED IDEOGRAPH - 0xBDBA: 0x80F6, //CJK UNIFIED IDEOGRAPH - 0xBDBB: 0x4EA4, //CJK UNIFIED IDEOGRAPH - 0xBDBC: 0x90CA, //CJK UNIFIED IDEOGRAPH - 0xBDBD: 0x6D47, //CJK UNIFIED IDEOGRAPH - 0xBDBE: 0x9A84, //CJK UNIFIED IDEOGRAPH - 0xBDBF: 0x5A07, //CJK UNIFIED IDEOGRAPH - 0xBDC0: 0x56BC, //CJK UNIFIED IDEOGRAPH - 0xBDC1: 0x6405, //CJK UNIFIED IDEOGRAPH - 0xBDC2: 0x94F0, //CJK UNIFIED IDEOGRAPH - 0xBDC3: 0x77EB, //CJK UNIFIED IDEOGRAPH - 0xBDC4: 0x4FA5, //CJK UNIFIED IDEOGRAPH - 0xBDC5: 0x811A, //CJK UNIFIED IDEOGRAPH - 0xBDC6: 0x72E1, //CJK UNIFIED IDEOGRAPH - 0xBDC7: 0x89D2, //CJK UNIFIED IDEOGRAPH - 0xBDC8: 0x997A, //CJK UNIFIED IDEOGRAPH - 0xBDC9: 0x7F34, //CJK UNIFIED IDEOGRAPH - 0xBDCA: 0x7EDE, //CJK UNIFIED IDEOGRAPH - 0xBDCB: 0x527F, //CJK UNIFIED IDEOGRAPH - 0xBDCC: 0x6559, //CJK UNIFIED IDEOGRAPH - 0xBDCD: 0x9175, //CJK UNIFIED IDEOGRAPH - 0xBDCE: 0x8F7F, //CJK UNIFIED IDEOGRAPH - 0xBDCF: 0x8F83, //CJK UNIFIED IDEOGRAPH - 0xBDD0: 0x53EB, //CJK UNIFIED IDEOGRAPH - 0xBDD1: 0x7A96, //CJK UNIFIED IDEOGRAPH - 0xBDD2: 0x63ED, //CJK UNIFIED IDEOGRAPH - 0xBDD3: 0x63A5, //CJK UNIFIED IDEOGRAPH - 0xBDD4: 0x7686, //CJK UNIFIED IDEOGRAPH - 0xBDD5: 0x79F8, //CJK UNIFIED IDEOGRAPH - 0xBDD6: 0x8857, //CJK UNIFIED IDEOGRAPH - 0xBDD7: 0x9636, //CJK UNIFIED IDEOGRAPH - 0xBDD8: 0x622A, //CJK UNIFIED IDEOGRAPH - 0xBDD9: 0x52AB, //CJK UNIFIED IDEOGRAPH - 0xBDDA: 0x8282, //CJK UNIFIED IDEOGRAPH - 0xBDDB: 0x6854, //CJK UNIFIED IDEOGRAPH - 0xBDDC: 0x6770, //CJK UNIFIED IDEOGRAPH - 0xBDDD: 0x6377, //CJK UNIFIED IDEOGRAPH - 0xBDDE: 0x776B, //CJK UNIFIED IDEOGRAPH - 0xBDDF: 0x7AED, //CJK UNIFIED IDEOGRAPH - 0xBDE0: 0x6D01, //CJK UNIFIED IDEOGRAPH - 0xBDE1: 0x7ED3, //CJK UNIFIED IDEOGRAPH - 0xBDE2: 0x89E3, //CJK UNIFIED IDEOGRAPH - 0xBDE3: 0x59D0, //CJK UNIFIED IDEOGRAPH - 0xBDE4: 0x6212, //CJK UNIFIED IDEOGRAPH - 0xBDE5: 0x85C9, //CJK UNIFIED IDEOGRAPH - 0xBDE6: 0x82A5, //CJK UNIFIED IDEOGRAPH - 0xBDE7: 0x754C, //CJK UNIFIED IDEOGRAPH - 0xBDE8: 0x501F, //CJK UNIFIED IDEOGRAPH - 0xBDE9: 0x4ECB, //CJK UNIFIED IDEOGRAPH - 0xBDEA: 0x75A5, //CJK UNIFIED IDEOGRAPH - 0xBDEB: 0x8BEB, //CJK UNIFIED IDEOGRAPH - 0xBDEC: 0x5C4A, //CJK UNIFIED IDEOGRAPH - 0xBDED: 0x5DFE, //CJK UNIFIED IDEOGRAPH - 0xBDEE: 0x7B4B, //CJK UNIFIED IDEOGRAPH - 0xBDEF: 0x65A4, //CJK UNIFIED IDEOGRAPH - 0xBDF0: 0x91D1, //CJK UNIFIED IDEOGRAPH - 0xBDF1: 0x4ECA, //CJK UNIFIED IDEOGRAPH - 0xBDF2: 0x6D25, //CJK UNIFIED IDEOGRAPH - 0xBDF3: 0x895F, //CJK UNIFIED IDEOGRAPH - 0xBDF4: 0x7D27, //CJK UNIFIED IDEOGRAPH - 0xBDF5: 0x9526, //CJK UNIFIED IDEOGRAPH - 0xBDF6: 0x4EC5, //CJK UNIFIED IDEOGRAPH - 0xBDF7: 0x8C28, //CJK UNIFIED IDEOGRAPH - 0xBDF8: 0x8FDB, //CJK UNIFIED IDEOGRAPH - 0xBDF9: 0x9773, //CJK UNIFIED IDEOGRAPH - 0xBDFA: 0x664B, //CJK UNIFIED IDEOGRAPH - 0xBDFB: 0x7981, //CJK UNIFIED IDEOGRAPH - 0xBDFC: 0x8FD1, //CJK UNIFIED IDEOGRAPH - 0xBDFD: 0x70EC, //CJK UNIFIED IDEOGRAPH - 0xBDFE: 0x6D78, //CJK UNIFIED IDEOGRAPH - 0xBE40: 0x7D99, //CJK UNIFIED IDEOGRAPH - 0xBE41: 0x7D9A, //CJK UNIFIED IDEOGRAPH - 0xBE42: 0x7D9B, //CJK UNIFIED IDEOGRAPH - 0xBE43: 0x7D9C, //CJK UNIFIED IDEOGRAPH - 0xBE44: 0x7D9D, //CJK UNIFIED IDEOGRAPH - 0xBE45: 0x7D9E, //CJK UNIFIED IDEOGRAPH - 0xBE46: 0x7D9F, //CJK UNIFIED IDEOGRAPH - 0xBE47: 0x7DA0, //CJK UNIFIED IDEOGRAPH - 0xBE48: 0x7DA1, //CJK UNIFIED IDEOGRAPH - 0xBE49: 0x7DA2, //CJK UNIFIED IDEOGRAPH - 0xBE4A: 0x7DA3, //CJK UNIFIED IDEOGRAPH - 0xBE4B: 0x7DA4, //CJK UNIFIED IDEOGRAPH - 0xBE4C: 0x7DA5, //CJK UNIFIED IDEOGRAPH - 0xBE4D: 0x7DA7, //CJK UNIFIED IDEOGRAPH - 0xBE4E: 0x7DA8, //CJK UNIFIED IDEOGRAPH - 0xBE4F: 0x7DA9, //CJK UNIFIED IDEOGRAPH - 0xBE50: 0x7DAA, //CJK UNIFIED IDEOGRAPH - 0xBE51: 0x7DAB, //CJK UNIFIED IDEOGRAPH - 0xBE52: 0x7DAC, //CJK UNIFIED IDEOGRAPH - 0xBE53: 0x7DAD, //CJK UNIFIED IDEOGRAPH - 0xBE54: 0x7DAF, //CJK UNIFIED IDEOGRAPH - 0xBE55: 0x7DB0, //CJK UNIFIED IDEOGRAPH - 0xBE56: 0x7DB1, //CJK UNIFIED IDEOGRAPH - 0xBE57: 0x7DB2, //CJK UNIFIED IDEOGRAPH - 0xBE58: 0x7DB3, //CJK UNIFIED IDEOGRAPH - 0xBE59: 0x7DB4, //CJK UNIFIED IDEOGRAPH - 0xBE5A: 0x7DB5, //CJK UNIFIED IDEOGRAPH - 0xBE5B: 0x7DB6, //CJK UNIFIED IDEOGRAPH - 0xBE5C: 0x7DB7, //CJK UNIFIED IDEOGRAPH - 0xBE5D: 0x7DB8, //CJK UNIFIED IDEOGRAPH - 0xBE5E: 0x7DB9, //CJK UNIFIED IDEOGRAPH - 0xBE5F: 0x7DBA, //CJK UNIFIED IDEOGRAPH - 0xBE60: 0x7DBB, //CJK UNIFIED IDEOGRAPH - 0xBE61: 0x7DBC, //CJK UNIFIED IDEOGRAPH - 0xBE62: 0x7DBD, //CJK UNIFIED IDEOGRAPH - 0xBE63: 0x7DBE, //CJK UNIFIED IDEOGRAPH - 0xBE64: 0x7DBF, //CJK UNIFIED IDEOGRAPH - 0xBE65: 0x7DC0, //CJK UNIFIED IDEOGRAPH - 0xBE66: 0x7DC1, //CJK UNIFIED IDEOGRAPH - 0xBE67: 0x7DC2, //CJK UNIFIED IDEOGRAPH - 0xBE68: 0x7DC3, //CJK UNIFIED IDEOGRAPH - 0xBE69: 0x7DC4, //CJK UNIFIED IDEOGRAPH - 0xBE6A: 0x7DC5, //CJK UNIFIED IDEOGRAPH - 0xBE6B: 0x7DC6, //CJK UNIFIED IDEOGRAPH - 0xBE6C: 0x7DC7, //CJK UNIFIED IDEOGRAPH - 0xBE6D: 0x7DC8, //CJK UNIFIED IDEOGRAPH - 0xBE6E: 0x7DC9, //CJK UNIFIED IDEOGRAPH - 0xBE6F: 0x7DCA, //CJK UNIFIED IDEOGRAPH - 0xBE70: 0x7DCB, //CJK UNIFIED IDEOGRAPH - 0xBE71: 0x7DCC, //CJK UNIFIED IDEOGRAPH - 0xBE72: 0x7DCD, //CJK UNIFIED IDEOGRAPH - 0xBE73: 0x7DCE, //CJK UNIFIED IDEOGRAPH - 0xBE74: 0x7DCF, //CJK UNIFIED IDEOGRAPH - 0xBE75: 0x7DD0, //CJK UNIFIED IDEOGRAPH - 0xBE76: 0x7DD1, //CJK UNIFIED IDEOGRAPH - 0xBE77: 0x7DD2, //CJK UNIFIED IDEOGRAPH - 0xBE78: 0x7DD3, //CJK UNIFIED IDEOGRAPH - 0xBE79: 0x7DD4, //CJK UNIFIED IDEOGRAPH - 0xBE7A: 0x7DD5, //CJK UNIFIED IDEOGRAPH - 0xBE7B: 0x7DD6, //CJK UNIFIED IDEOGRAPH - 0xBE7C: 0x7DD7, //CJK UNIFIED IDEOGRAPH - 0xBE7D: 0x7DD8, //CJK UNIFIED IDEOGRAPH - 0xBE7E: 0x7DD9, //CJK UNIFIED IDEOGRAPH - 0xBE80: 0x7DDA, //CJK UNIFIED IDEOGRAPH - 0xBE81: 0x7DDB, //CJK UNIFIED IDEOGRAPH - 0xBE82: 0x7DDC, //CJK UNIFIED IDEOGRAPH - 0xBE83: 0x7DDD, //CJK UNIFIED IDEOGRAPH - 0xBE84: 0x7DDE, //CJK UNIFIED IDEOGRAPH - 0xBE85: 0x7DDF, //CJK UNIFIED IDEOGRAPH - 0xBE86: 0x7DE0, //CJK UNIFIED IDEOGRAPH - 0xBE87: 0x7DE1, //CJK UNIFIED IDEOGRAPH - 0xBE88: 0x7DE2, //CJK UNIFIED IDEOGRAPH - 0xBE89: 0x7DE3, //CJK UNIFIED IDEOGRAPH - 0xBE8A: 0x7DE4, //CJK UNIFIED IDEOGRAPH - 0xBE8B: 0x7DE5, //CJK UNIFIED IDEOGRAPH - 0xBE8C: 0x7DE6, //CJK UNIFIED IDEOGRAPH - 0xBE8D: 0x7DE7, //CJK UNIFIED IDEOGRAPH - 0xBE8E: 0x7DE8, //CJK UNIFIED IDEOGRAPH - 0xBE8F: 0x7DE9, //CJK UNIFIED IDEOGRAPH - 0xBE90: 0x7DEA, //CJK UNIFIED IDEOGRAPH - 0xBE91: 0x7DEB, //CJK UNIFIED IDEOGRAPH - 0xBE92: 0x7DEC, //CJK UNIFIED IDEOGRAPH - 0xBE93: 0x7DED, //CJK UNIFIED IDEOGRAPH - 0xBE94: 0x7DEE, //CJK UNIFIED IDEOGRAPH - 0xBE95: 0x7DEF, //CJK UNIFIED IDEOGRAPH - 0xBE96: 0x7DF0, //CJK UNIFIED IDEOGRAPH - 0xBE97: 0x7DF1, //CJK UNIFIED IDEOGRAPH - 0xBE98: 0x7DF2, //CJK UNIFIED IDEOGRAPH - 0xBE99: 0x7DF3, //CJK UNIFIED IDEOGRAPH - 0xBE9A: 0x7DF4, //CJK UNIFIED IDEOGRAPH - 0xBE9B: 0x7DF5, //CJK UNIFIED IDEOGRAPH - 0xBE9C: 0x7DF6, //CJK UNIFIED IDEOGRAPH - 0xBE9D: 0x7DF7, //CJK UNIFIED IDEOGRAPH - 0xBE9E: 0x7DF8, //CJK UNIFIED IDEOGRAPH - 0xBE9F: 0x7DF9, //CJK UNIFIED IDEOGRAPH - 0xBEA0: 0x7DFA, //CJK UNIFIED IDEOGRAPH - 0xBEA1: 0x5C3D, //CJK UNIFIED IDEOGRAPH - 0xBEA2: 0x52B2, //CJK UNIFIED IDEOGRAPH - 0xBEA3: 0x8346, //CJK UNIFIED IDEOGRAPH - 0xBEA4: 0x5162, //CJK UNIFIED IDEOGRAPH - 0xBEA5: 0x830E, //CJK UNIFIED IDEOGRAPH - 0xBEA6: 0x775B, //CJK UNIFIED IDEOGRAPH - 0xBEA7: 0x6676, //CJK UNIFIED IDEOGRAPH - 0xBEA8: 0x9CB8, //CJK UNIFIED IDEOGRAPH - 0xBEA9: 0x4EAC, //CJK UNIFIED IDEOGRAPH - 0xBEAA: 0x60CA, //CJK UNIFIED IDEOGRAPH - 0xBEAB: 0x7CBE, //CJK UNIFIED IDEOGRAPH - 0xBEAC: 0x7CB3, //CJK UNIFIED IDEOGRAPH - 0xBEAD: 0x7ECF, //CJK UNIFIED IDEOGRAPH - 0xBEAE: 0x4E95, //CJK UNIFIED IDEOGRAPH - 0xBEAF: 0x8B66, //CJK UNIFIED IDEOGRAPH - 0xBEB0: 0x666F, //CJK UNIFIED IDEOGRAPH - 0xBEB1: 0x9888, //CJK UNIFIED IDEOGRAPH - 0xBEB2: 0x9759, //CJK UNIFIED IDEOGRAPH - 0xBEB3: 0x5883, //CJK UNIFIED IDEOGRAPH - 0xBEB4: 0x656C, //CJK UNIFIED IDEOGRAPH - 0xBEB5: 0x955C, //CJK UNIFIED IDEOGRAPH - 0xBEB6: 0x5F84, //CJK UNIFIED IDEOGRAPH - 0xBEB7: 0x75C9, //CJK UNIFIED IDEOGRAPH - 0xBEB8: 0x9756, //CJK UNIFIED IDEOGRAPH - 0xBEB9: 0x7ADF, //CJK UNIFIED IDEOGRAPH - 0xBEBA: 0x7ADE, //CJK UNIFIED IDEOGRAPH - 0xBEBB: 0x51C0, //CJK UNIFIED IDEOGRAPH - 0xBEBC: 0x70AF, //CJK UNIFIED IDEOGRAPH - 0xBEBD: 0x7A98, //CJK UNIFIED IDEOGRAPH - 0xBEBE: 0x63EA, //CJK UNIFIED IDEOGRAPH - 0xBEBF: 0x7A76, //CJK UNIFIED IDEOGRAPH - 0xBEC0: 0x7EA0, //CJK UNIFIED IDEOGRAPH - 0xBEC1: 0x7396, //CJK UNIFIED IDEOGRAPH - 0xBEC2: 0x97ED, //CJK UNIFIED IDEOGRAPH - 0xBEC3: 0x4E45, //CJK UNIFIED IDEOGRAPH - 0xBEC4: 0x7078, //CJK UNIFIED IDEOGRAPH - 0xBEC5: 0x4E5D, //CJK UNIFIED IDEOGRAPH - 0xBEC6: 0x9152, //CJK UNIFIED IDEOGRAPH - 0xBEC7: 0x53A9, //CJK UNIFIED IDEOGRAPH - 0xBEC8: 0x6551, //CJK UNIFIED IDEOGRAPH - 0xBEC9: 0x65E7, //CJK UNIFIED IDEOGRAPH - 0xBECA: 0x81FC, //CJK UNIFIED IDEOGRAPH - 0xBECB: 0x8205, //CJK UNIFIED IDEOGRAPH - 0xBECC: 0x548E, //CJK UNIFIED IDEOGRAPH - 0xBECD: 0x5C31, //CJK UNIFIED IDEOGRAPH - 0xBECE: 0x759A, //CJK UNIFIED IDEOGRAPH - 0xBECF: 0x97A0, //CJK UNIFIED IDEOGRAPH - 0xBED0: 0x62D8, //CJK UNIFIED IDEOGRAPH - 0xBED1: 0x72D9, //CJK UNIFIED IDEOGRAPH - 0xBED2: 0x75BD, //CJK UNIFIED IDEOGRAPH - 0xBED3: 0x5C45, //CJK UNIFIED IDEOGRAPH - 0xBED4: 0x9A79, //CJK UNIFIED IDEOGRAPH - 0xBED5: 0x83CA, //CJK UNIFIED IDEOGRAPH - 0xBED6: 0x5C40, //CJK UNIFIED IDEOGRAPH - 0xBED7: 0x5480, //CJK UNIFIED IDEOGRAPH - 0xBED8: 0x77E9, //CJK UNIFIED IDEOGRAPH - 0xBED9: 0x4E3E, //CJK UNIFIED IDEOGRAPH - 0xBEDA: 0x6CAE, //CJK UNIFIED IDEOGRAPH - 0xBEDB: 0x805A, //CJK UNIFIED IDEOGRAPH - 0xBEDC: 0x62D2, //CJK UNIFIED IDEOGRAPH - 0xBEDD: 0x636E, //CJK UNIFIED IDEOGRAPH - 0xBEDE: 0x5DE8, //CJK UNIFIED IDEOGRAPH - 0xBEDF: 0x5177, //CJK UNIFIED IDEOGRAPH - 0xBEE0: 0x8DDD, //CJK UNIFIED IDEOGRAPH - 0xBEE1: 0x8E1E, //CJK UNIFIED IDEOGRAPH - 0xBEE2: 0x952F, //CJK UNIFIED IDEOGRAPH - 0xBEE3: 0x4FF1, //CJK UNIFIED IDEOGRAPH - 0xBEE4: 0x53E5, //CJK UNIFIED IDEOGRAPH - 0xBEE5: 0x60E7, //CJK UNIFIED IDEOGRAPH - 0xBEE6: 0x70AC, //CJK UNIFIED IDEOGRAPH - 0xBEE7: 0x5267, //CJK UNIFIED IDEOGRAPH - 0xBEE8: 0x6350, //CJK UNIFIED IDEOGRAPH - 0xBEE9: 0x9E43, //CJK UNIFIED IDEOGRAPH - 0xBEEA: 0x5A1F, //CJK UNIFIED IDEOGRAPH - 0xBEEB: 0x5026, //CJK UNIFIED IDEOGRAPH - 0xBEEC: 0x7737, //CJK UNIFIED IDEOGRAPH - 0xBEED: 0x5377, //CJK UNIFIED IDEOGRAPH - 0xBEEE: 0x7EE2, //CJK UNIFIED IDEOGRAPH - 0xBEEF: 0x6485, //CJK UNIFIED IDEOGRAPH - 0xBEF0: 0x652B, //CJK UNIFIED IDEOGRAPH - 0xBEF1: 0x6289, //CJK UNIFIED IDEOGRAPH - 0xBEF2: 0x6398, //CJK UNIFIED IDEOGRAPH - 0xBEF3: 0x5014, //CJK UNIFIED IDEOGRAPH - 0xBEF4: 0x7235, //CJK UNIFIED IDEOGRAPH - 0xBEF5: 0x89C9, //CJK UNIFIED IDEOGRAPH - 0xBEF6: 0x51B3, //CJK UNIFIED IDEOGRAPH - 0xBEF7: 0x8BC0, //CJK UNIFIED IDEOGRAPH - 0xBEF8: 0x7EDD, //CJK UNIFIED IDEOGRAPH - 0xBEF9: 0x5747, //CJK UNIFIED IDEOGRAPH - 0xBEFA: 0x83CC, //CJK UNIFIED IDEOGRAPH - 0xBEFB: 0x94A7, //CJK UNIFIED IDEOGRAPH - 0xBEFC: 0x519B, //CJK UNIFIED IDEOGRAPH - 0xBEFD: 0x541B, //CJK UNIFIED IDEOGRAPH - 0xBEFE: 0x5CFB, //CJK UNIFIED IDEOGRAPH - 0xBF40: 0x7DFB, //CJK UNIFIED IDEOGRAPH - 0xBF41: 0x7DFC, //CJK UNIFIED IDEOGRAPH - 0xBF42: 0x7DFD, //CJK UNIFIED IDEOGRAPH - 0xBF43: 0x7DFE, //CJK UNIFIED IDEOGRAPH - 0xBF44: 0x7DFF, //CJK UNIFIED IDEOGRAPH - 0xBF45: 0x7E00, //CJK UNIFIED IDEOGRAPH - 0xBF46: 0x7E01, //CJK UNIFIED IDEOGRAPH - 0xBF47: 0x7E02, //CJK UNIFIED IDEOGRAPH - 0xBF48: 0x7E03, //CJK UNIFIED IDEOGRAPH - 0xBF49: 0x7E04, //CJK UNIFIED IDEOGRAPH - 0xBF4A: 0x7E05, //CJK UNIFIED IDEOGRAPH - 0xBF4B: 0x7E06, //CJK UNIFIED IDEOGRAPH - 0xBF4C: 0x7E07, //CJK UNIFIED IDEOGRAPH - 0xBF4D: 0x7E08, //CJK UNIFIED IDEOGRAPH - 0xBF4E: 0x7E09, //CJK UNIFIED IDEOGRAPH - 0xBF4F: 0x7E0A, //CJK UNIFIED IDEOGRAPH - 0xBF50: 0x7E0B, //CJK UNIFIED IDEOGRAPH - 0xBF51: 0x7E0C, //CJK UNIFIED IDEOGRAPH - 0xBF52: 0x7E0D, //CJK UNIFIED IDEOGRAPH - 0xBF53: 0x7E0E, //CJK UNIFIED IDEOGRAPH - 0xBF54: 0x7E0F, //CJK UNIFIED IDEOGRAPH - 0xBF55: 0x7E10, //CJK UNIFIED IDEOGRAPH - 0xBF56: 0x7E11, //CJK UNIFIED IDEOGRAPH - 0xBF57: 0x7E12, //CJK UNIFIED IDEOGRAPH - 0xBF58: 0x7E13, //CJK UNIFIED IDEOGRAPH - 0xBF59: 0x7E14, //CJK UNIFIED IDEOGRAPH - 0xBF5A: 0x7E15, //CJK UNIFIED IDEOGRAPH - 0xBF5B: 0x7E16, //CJK UNIFIED IDEOGRAPH - 0xBF5C: 0x7E17, //CJK UNIFIED IDEOGRAPH - 0xBF5D: 0x7E18, //CJK UNIFIED IDEOGRAPH - 0xBF5E: 0x7E19, //CJK UNIFIED IDEOGRAPH - 0xBF5F: 0x7E1A, //CJK UNIFIED IDEOGRAPH - 0xBF60: 0x7E1B, //CJK UNIFIED IDEOGRAPH - 0xBF61: 0x7E1C, //CJK UNIFIED IDEOGRAPH - 0xBF62: 0x7E1D, //CJK UNIFIED IDEOGRAPH - 0xBF63: 0x7E1E, //CJK UNIFIED IDEOGRAPH - 0xBF64: 0x7E1F, //CJK UNIFIED IDEOGRAPH - 0xBF65: 0x7E20, //CJK UNIFIED IDEOGRAPH - 0xBF66: 0x7E21, //CJK UNIFIED IDEOGRAPH - 0xBF67: 0x7E22, //CJK UNIFIED IDEOGRAPH - 0xBF68: 0x7E23, //CJK UNIFIED IDEOGRAPH - 0xBF69: 0x7E24, //CJK UNIFIED IDEOGRAPH - 0xBF6A: 0x7E25, //CJK UNIFIED IDEOGRAPH - 0xBF6B: 0x7E26, //CJK UNIFIED IDEOGRAPH - 0xBF6C: 0x7E27, //CJK UNIFIED IDEOGRAPH - 0xBF6D: 0x7E28, //CJK UNIFIED IDEOGRAPH - 0xBF6E: 0x7E29, //CJK UNIFIED IDEOGRAPH - 0xBF6F: 0x7E2A, //CJK UNIFIED IDEOGRAPH - 0xBF70: 0x7E2B, //CJK UNIFIED IDEOGRAPH - 0xBF71: 0x7E2C, //CJK UNIFIED IDEOGRAPH - 0xBF72: 0x7E2D, //CJK UNIFIED IDEOGRAPH - 0xBF73: 0x7E2E, //CJK UNIFIED IDEOGRAPH - 0xBF74: 0x7E2F, //CJK UNIFIED IDEOGRAPH - 0xBF75: 0x7E30, //CJK UNIFIED IDEOGRAPH - 0xBF76: 0x7E31, //CJK UNIFIED IDEOGRAPH - 0xBF77: 0x7E32, //CJK UNIFIED IDEOGRAPH - 0xBF78: 0x7E33, //CJK UNIFIED IDEOGRAPH - 0xBF79: 0x7E34, //CJK UNIFIED IDEOGRAPH - 0xBF7A: 0x7E35, //CJK UNIFIED IDEOGRAPH - 0xBF7B: 0x7E36, //CJK UNIFIED IDEOGRAPH - 0xBF7C: 0x7E37, //CJK UNIFIED IDEOGRAPH - 0xBF7D: 0x7E38, //CJK UNIFIED IDEOGRAPH - 0xBF7E: 0x7E39, //CJK UNIFIED IDEOGRAPH - 0xBF80: 0x7E3A, //CJK UNIFIED IDEOGRAPH - 0xBF81: 0x7E3C, //CJK UNIFIED IDEOGRAPH - 0xBF82: 0x7E3D, //CJK UNIFIED IDEOGRAPH - 0xBF83: 0x7E3E, //CJK UNIFIED IDEOGRAPH - 0xBF84: 0x7E3F, //CJK UNIFIED IDEOGRAPH - 0xBF85: 0x7E40, //CJK UNIFIED IDEOGRAPH - 0xBF86: 0x7E42, //CJK UNIFIED IDEOGRAPH - 0xBF87: 0x7E43, //CJK UNIFIED IDEOGRAPH - 0xBF88: 0x7E44, //CJK UNIFIED IDEOGRAPH - 0xBF89: 0x7E45, //CJK UNIFIED IDEOGRAPH - 0xBF8A: 0x7E46, //CJK UNIFIED IDEOGRAPH - 0xBF8B: 0x7E48, //CJK UNIFIED IDEOGRAPH - 0xBF8C: 0x7E49, //CJK UNIFIED IDEOGRAPH - 0xBF8D: 0x7E4A, //CJK UNIFIED IDEOGRAPH - 0xBF8E: 0x7E4B, //CJK UNIFIED IDEOGRAPH - 0xBF8F: 0x7E4C, //CJK UNIFIED IDEOGRAPH - 0xBF90: 0x7E4D, //CJK UNIFIED IDEOGRAPH - 0xBF91: 0x7E4E, //CJK UNIFIED IDEOGRAPH - 0xBF92: 0x7E4F, //CJK UNIFIED IDEOGRAPH - 0xBF93: 0x7E50, //CJK UNIFIED IDEOGRAPH - 0xBF94: 0x7E51, //CJK UNIFIED IDEOGRAPH - 0xBF95: 0x7E52, //CJK UNIFIED IDEOGRAPH - 0xBF96: 0x7E53, //CJK UNIFIED IDEOGRAPH - 0xBF97: 0x7E54, //CJK UNIFIED IDEOGRAPH - 0xBF98: 0x7E55, //CJK UNIFIED IDEOGRAPH - 0xBF99: 0x7E56, //CJK UNIFIED IDEOGRAPH - 0xBF9A: 0x7E57, //CJK UNIFIED IDEOGRAPH - 0xBF9B: 0x7E58, //CJK UNIFIED IDEOGRAPH - 0xBF9C: 0x7E59, //CJK UNIFIED IDEOGRAPH - 0xBF9D: 0x7E5A, //CJK UNIFIED IDEOGRAPH - 0xBF9E: 0x7E5B, //CJK UNIFIED IDEOGRAPH - 0xBF9F: 0x7E5C, //CJK UNIFIED IDEOGRAPH - 0xBFA0: 0x7E5D, //CJK UNIFIED IDEOGRAPH - 0xBFA1: 0x4FCA, //CJK UNIFIED IDEOGRAPH - 0xBFA2: 0x7AE3, //CJK UNIFIED IDEOGRAPH - 0xBFA3: 0x6D5A, //CJK UNIFIED IDEOGRAPH - 0xBFA4: 0x90E1, //CJK UNIFIED IDEOGRAPH - 0xBFA5: 0x9A8F, //CJK UNIFIED IDEOGRAPH - 0xBFA6: 0x5580, //CJK UNIFIED IDEOGRAPH - 0xBFA7: 0x5496, //CJK UNIFIED IDEOGRAPH - 0xBFA8: 0x5361, //CJK UNIFIED IDEOGRAPH - 0xBFA9: 0x54AF, //CJK UNIFIED IDEOGRAPH - 0xBFAA: 0x5F00, //CJK UNIFIED IDEOGRAPH - 0xBFAB: 0x63E9, //CJK UNIFIED IDEOGRAPH - 0xBFAC: 0x6977, //CJK UNIFIED IDEOGRAPH - 0xBFAD: 0x51EF, //CJK UNIFIED IDEOGRAPH - 0xBFAE: 0x6168, //CJK UNIFIED IDEOGRAPH - 0xBFAF: 0x520A, //CJK UNIFIED IDEOGRAPH - 0xBFB0: 0x582A, //CJK UNIFIED IDEOGRAPH - 0xBFB1: 0x52D8, //CJK UNIFIED IDEOGRAPH - 0xBFB2: 0x574E, //CJK UNIFIED IDEOGRAPH - 0xBFB3: 0x780D, //CJK UNIFIED IDEOGRAPH - 0xBFB4: 0x770B, //CJK UNIFIED IDEOGRAPH - 0xBFB5: 0x5EB7, //CJK UNIFIED IDEOGRAPH - 0xBFB6: 0x6177, //CJK UNIFIED IDEOGRAPH - 0xBFB7: 0x7CE0, //CJK UNIFIED IDEOGRAPH - 0xBFB8: 0x625B, //CJK UNIFIED IDEOGRAPH - 0xBFB9: 0x6297, //CJK UNIFIED IDEOGRAPH - 0xBFBA: 0x4EA2, //CJK UNIFIED IDEOGRAPH - 0xBFBB: 0x7095, //CJK UNIFIED IDEOGRAPH - 0xBFBC: 0x8003, //CJK UNIFIED IDEOGRAPH - 0xBFBD: 0x62F7, //CJK UNIFIED IDEOGRAPH - 0xBFBE: 0x70E4, //CJK UNIFIED IDEOGRAPH - 0xBFBF: 0x9760, //CJK UNIFIED IDEOGRAPH - 0xBFC0: 0x5777, //CJK UNIFIED IDEOGRAPH - 0xBFC1: 0x82DB, //CJK UNIFIED IDEOGRAPH - 0xBFC2: 0x67EF, //CJK UNIFIED IDEOGRAPH - 0xBFC3: 0x68F5, //CJK UNIFIED IDEOGRAPH - 0xBFC4: 0x78D5, //CJK UNIFIED IDEOGRAPH - 0xBFC5: 0x9897, //CJK UNIFIED IDEOGRAPH - 0xBFC6: 0x79D1, //CJK UNIFIED IDEOGRAPH - 0xBFC7: 0x58F3, //CJK UNIFIED IDEOGRAPH - 0xBFC8: 0x54B3, //CJK UNIFIED IDEOGRAPH - 0xBFC9: 0x53EF, //CJK UNIFIED IDEOGRAPH - 0xBFCA: 0x6E34, //CJK UNIFIED IDEOGRAPH - 0xBFCB: 0x514B, //CJK UNIFIED IDEOGRAPH - 0xBFCC: 0x523B, //CJK UNIFIED IDEOGRAPH - 0xBFCD: 0x5BA2, //CJK UNIFIED IDEOGRAPH - 0xBFCE: 0x8BFE, //CJK UNIFIED IDEOGRAPH - 0xBFCF: 0x80AF, //CJK UNIFIED IDEOGRAPH - 0xBFD0: 0x5543, //CJK UNIFIED IDEOGRAPH - 0xBFD1: 0x57A6, //CJK UNIFIED IDEOGRAPH - 0xBFD2: 0x6073, //CJK UNIFIED IDEOGRAPH - 0xBFD3: 0x5751, //CJK UNIFIED IDEOGRAPH - 0xBFD4: 0x542D, //CJK UNIFIED IDEOGRAPH - 0xBFD5: 0x7A7A, //CJK UNIFIED IDEOGRAPH - 0xBFD6: 0x6050, //CJK UNIFIED IDEOGRAPH - 0xBFD7: 0x5B54, //CJK UNIFIED IDEOGRAPH - 0xBFD8: 0x63A7, //CJK UNIFIED IDEOGRAPH - 0xBFD9: 0x62A0, //CJK UNIFIED IDEOGRAPH - 0xBFDA: 0x53E3, //CJK UNIFIED IDEOGRAPH - 0xBFDB: 0x6263, //CJK UNIFIED IDEOGRAPH - 0xBFDC: 0x5BC7, //CJK UNIFIED IDEOGRAPH - 0xBFDD: 0x67AF, //CJK UNIFIED IDEOGRAPH - 0xBFDE: 0x54ED, //CJK UNIFIED IDEOGRAPH - 0xBFDF: 0x7A9F, //CJK UNIFIED IDEOGRAPH - 0xBFE0: 0x82E6, //CJK UNIFIED IDEOGRAPH - 0xBFE1: 0x9177, //CJK UNIFIED IDEOGRAPH - 0xBFE2: 0x5E93, //CJK UNIFIED IDEOGRAPH - 0xBFE3: 0x88E4, //CJK UNIFIED IDEOGRAPH - 0xBFE4: 0x5938, //CJK UNIFIED IDEOGRAPH - 0xBFE5: 0x57AE, //CJK UNIFIED IDEOGRAPH - 0xBFE6: 0x630E, //CJK UNIFIED IDEOGRAPH - 0xBFE7: 0x8DE8, //CJK UNIFIED IDEOGRAPH - 0xBFE8: 0x80EF, //CJK UNIFIED IDEOGRAPH - 0xBFE9: 0x5757, //CJK UNIFIED IDEOGRAPH - 0xBFEA: 0x7B77, //CJK UNIFIED IDEOGRAPH - 0xBFEB: 0x4FA9, //CJK UNIFIED IDEOGRAPH - 0xBFEC: 0x5FEB, //CJK UNIFIED IDEOGRAPH - 0xBFED: 0x5BBD, //CJK UNIFIED IDEOGRAPH - 0xBFEE: 0x6B3E, //CJK UNIFIED IDEOGRAPH - 0xBFEF: 0x5321, //CJK UNIFIED IDEOGRAPH - 0xBFF0: 0x7B50, //CJK UNIFIED IDEOGRAPH - 0xBFF1: 0x72C2, //CJK UNIFIED IDEOGRAPH - 0xBFF2: 0x6846, //CJK UNIFIED IDEOGRAPH - 0xBFF3: 0x77FF, //CJK UNIFIED IDEOGRAPH - 0xBFF4: 0x7736, //CJK UNIFIED IDEOGRAPH - 0xBFF5: 0x65F7, //CJK UNIFIED IDEOGRAPH - 0xBFF6: 0x51B5, //CJK UNIFIED IDEOGRAPH - 0xBFF7: 0x4E8F, //CJK UNIFIED IDEOGRAPH - 0xBFF8: 0x76D4, //CJK UNIFIED IDEOGRAPH - 0xBFF9: 0x5CBF, //CJK UNIFIED IDEOGRAPH - 0xBFFA: 0x7AA5, //CJK UNIFIED IDEOGRAPH - 0xBFFB: 0x8475, //CJK UNIFIED IDEOGRAPH - 0xBFFC: 0x594E, //CJK UNIFIED IDEOGRAPH - 0xBFFD: 0x9B41, //CJK UNIFIED IDEOGRAPH - 0xBFFE: 0x5080, //CJK UNIFIED IDEOGRAPH - 0xC040: 0x7E5E, //CJK UNIFIED IDEOGRAPH - 0xC041: 0x7E5F, //CJK UNIFIED IDEOGRAPH - 0xC042: 0x7E60, //CJK UNIFIED IDEOGRAPH - 0xC043: 0x7E61, //CJK UNIFIED IDEOGRAPH - 0xC044: 0x7E62, //CJK UNIFIED IDEOGRAPH - 0xC045: 0x7E63, //CJK UNIFIED IDEOGRAPH - 0xC046: 0x7E64, //CJK UNIFIED IDEOGRAPH - 0xC047: 0x7E65, //CJK UNIFIED IDEOGRAPH - 0xC048: 0x7E66, //CJK UNIFIED IDEOGRAPH - 0xC049: 0x7E67, //CJK UNIFIED IDEOGRAPH - 0xC04A: 0x7E68, //CJK UNIFIED IDEOGRAPH - 0xC04B: 0x7E69, //CJK UNIFIED IDEOGRAPH - 0xC04C: 0x7E6A, //CJK UNIFIED IDEOGRAPH - 0xC04D: 0x7E6B, //CJK UNIFIED IDEOGRAPH - 0xC04E: 0x7E6C, //CJK UNIFIED IDEOGRAPH - 0xC04F: 0x7E6D, //CJK UNIFIED IDEOGRAPH - 0xC050: 0x7E6E, //CJK UNIFIED IDEOGRAPH - 0xC051: 0x7E6F, //CJK UNIFIED IDEOGRAPH - 0xC052: 0x7E70, //CJK UNIFIED IDEOGRAPH - 0xC053: 0x7E71, //CJK UNIFIED IDEOGRAPH - 0xC054: 0x7E72, //CJK UNIFIED IDEOGRAPH - 0xC055: 0x7E73, //CJK UNIFIED IDEOGRAPH - 0xC056: 0x7E74, //CJK UNIFIED IDEOGRAPH - 0xC057: 0x7E75, //CJK UNIFIED IDEOGRAPH - 0xC058: 0x7E76, //CJK UNIFIED IDEOGRAPH - 0xC059: 0x7E77, //CJK UNIFIED IDEOGRAPH - 0xC05A: 0x7E78, //CJK UNIFIED IDEOGRAPH - 0xC05B: 0x7E79, //CJK UNIFIED IDEOGRAPH - 0xC05C: 0x7E7A, //CJK UNIFIED IDEOGRAPH - 0xC05D: 0x7E7B, //CJK UNIFIED IDEOGRAPH - 0xC05E: 0x7E7C, //CJK UNIFIED IDEOGRAPH - 0xC05F: 0x7E7D, //CJK UNIFIED IDEOGRAPH - 0xC060: 0x7E7E, //CJK UNIFIED IDEOGRAPH - 0xC061: 0x7E7F, //CJK UNIFIED IDEOGRAPH - 0xC062: 0x7E80, //CJK UNIFIED IDEOGRAPH - 0xC063: 0x7E81, //CJK UNIFIED IDEOGRAPH - 0xC064: 0x7E83, //CJK UNIFIED IDEOGRAPH - 0xC065: 0x7E84, //CJK UNIFIED IDEOGRAPH - 0xC066: 0x7E85, //CJK UNIFIED IDEOGRAPH - 0xC067: 0x7E86, //CJK UNIFIED IDEOGRAPH - 0xC068: 0x7E87, //CJK UNIFIED IDEOGRAPH - 0xC069: 0x7E88, //CJK UNIFIED IDEOGRAPH - 0xC06A: 0x7E89, //CJK UNIFIED IDEOGRAPH - 0xC06B: 0x7E8A, //CJK UNIFIED IDEOGRAPH - 0xC06C: 0x7E8B, //CJK UNIFIED IDEOGRAPH - 0xC06D: 0x7E8C, //CJK UNIFIED IDEOGRAPH - 0xC06E: 0x7E8D, //CJK UNIFIED IDEOGRAPH - 0xC06F: 0x7E8E, //CJK UNIFIED IDEOGRAPH - 0xC070: 0x7E8F, //CJK UNIFIED IDEOGRAPH - 0xC071: 0x7E90, //CJK UNIFIED IDEOGRAPH - 0xC072: 0x7E91, //CJK UNIFIED IDEOGRAPH - 0xC073: 0x7E92, //CJK UNIFIED IDEOGRAPH - 0xC074: 0x7E93, //CJK UNIFIED IDEOGRAPH - 0xC075: 0x7E94, //CJK UNIFIED IDEOGRAPH - 0xC076: 0x7E95, //CJK UNIFIED IDEOGRAPH - 0xC077: 0x7E96, //CJK UNIFIED IDEOGRAPH - 0xC078: 0x7E97, //CJK UNIFIED IDEOGRAPH - 0xC079: 0x7E98, //CJK UNIFIED IDEOGRAPH - 0xC07A: 0x7E99, //CJK UNIFIED IDEOGRAPH - 0xC07B: 0x7E9A, //CJK UNIFIED IDEOGRAPH - 0xC07C: 0x7E9C, //CJK UNIFIED IDEOGRAPH - 0xC07D: 0x7E9D, //CJK UNIFIED IDEOGRAPH - 0xC07E: 0x7E9E, //CJK UNIFIED IDEOGRAPH - 0xC080: 0x7EAE, //CJK UNIFIED IDEOGRAPH - 0xC081: 0x7EB4, //CJK UNIFIED IDEOGRAPH - 0xC082: 0x7EBB, //CJK UNIFIED IDEOGRAPH - 0xC083: 0x7EBC, //CJK UNIFIED IDEOGRAPH - 0xC084: 0x7ED6, //CJK UNIFIED IDEOGRAPH - 0xC085: 0x7EE4, //CJK UNIFIED IDEOGRAPH - 0xC086: 0x7EEC, //CJK UNIFIED IDEOGRAPH - 0xC087: 0x7EF9, //CJK UNIFIED IDEOGRAPH - 0xC088: 0x7F0A, //CJK UNIFIED IDEOGRAPH - 0xC089: 0x7F10, //CJK UNIFIED IDEOGRAPH - 0xC08A: 0x7F1E, //CJK UNIFIED IDEOGRAPH - 0xC08B: 0x7F37, //CJK UNIFIED IDEOGRAPH - 0xC08C: 0x7F39, //CJK UNIFIED IDEOGRAPH - 0xC08D: 0x7F3B, //CJK UNIFIED IDEOGRAPH - 0xC08E: 0x7F3C, //CJK UNIFIED IDEOGRAPH - 0xC08F: 0x7F3D, //CJK UNIFIED IDEOGRAPH - 0xC090: 0x7F3E, //CJK UNIFIED IDEOGRAPH - 0xC091: 0x7F3F, //CJK UNIFIED IDEOGRAPH - 0xC092: 0x7F40, //CJK UNIFIED IDEOGRAPH - 0xC093: 0x7F41, //CJK UNIFIED IDEOGRAPH - 0xC094: 0x7F43, //CJK UNIFIED IDEOGRAPH - 0xC095: 0x7F46, //CJK UNIFIED IDEOGRAPH - 0xC096: 0x7F47, //CJK UNIFIED IDEOGRAPH - 0xC097: 0x7F48, //CJK UNIFIED IDEOGRAPH - 0xC098: 0x7F49, //CJK UNIFIED IDEOGRAPH - 0xC099: 0x7F4A, //CJK UNIFIED IDEOGRAPH - 0xC09A: 0x7F4B, //CJK UNIFIED IDEOGRAPH - 0xC09B: 0x7F4C, //CJK UNIFIED IDEOGRAPH - 0xC09C: 0x7F4D, //CJK UNIFIED IDEOGRAPH - 0xC09D: 0x7F4E, //CJK UNIFIED IDEOGRAPH - 0xC09E: 0x7F4F, //CJK UNIFIED IDEOGRAPH - 0xC09F: 0x7F52, //CJK UNIFIED IDEOGRAPH - 0xC0A0: 0x7F53, //CJK UNIFIED IDEOGRAPH - 0xC0A1: 0x9988, //CJK UNIFIED IDEOGRAPH - 0xC0A2: 0x6127, //CJK UNIFIED IDEOGRAPH - 0xC0A3: 0x6E83, //CJK UNIFIED IDEOGRAPH - 0xC0A4: 0x5764, //CJK UNIFIED IDEOGRAPH - 0xC0A5: 0x6606, //CJK UNIFIED IDEOGRAPH - 0xC0A6: 0x6346, //CJK UNIFIED IDEOGRAPH - 0xC0A7: 0x56F0, //CJK UNIFIED IDEOGRAPH - 0xC0A8: 0x62EC, //CJK UNIFIED IDEOGRAPH - 0xC0A9: 0x6269, //CJK UNIFIED IDEOGRAPH - 0xC0AA: 0x5ED3, //CJK UNIFIED IDEOGRAPH - 0xC0AB: 0x9614, //CJK UNIFIED IDEOGRAPH - 0xC0AC: 0x5783, //CJK UNIFIED IDEOGRAPH - 0xC0AD: 0x62C9, //CJK UNIFIED IDEOGRAPH - 0xC0AE: 0x5587, //CJK UNIFIED IDEOGRAPH - 0xC0AF: 0x8721, //CJK UNIFIED IDEOGRAPH - 0xC0B0: 0x814A, //CJK UNIFIED IDEOGRAPH - 0xC0B1: 0x8FA3, //CJK UNIFIED IDEOGRAPH - 0xC0B2: 0x5566, //CJK UNIFIED IDEOGRAPH - 0xC0B3: 0x83B1, //CJK UNIFIED IDEOGRAPH - 0xC0B4: 0x6765, //CJK UNIFIED IDEOGRAPH - 0xC0B5: 0x8D56, //CJK UNIFIED IDEOGRAPH - 0xC0B6: 0x84DD, //CJK UNIFIED IDEOGRAPH - 0xC0B7: 0x5A6A, //CJK UNIFIED IDEOGRAPH - 0xC0B8: 0x680F, //CJK UNIFIED IDEOGRAPH - 0xC0B9: 0x62E6, //CJK UNIFIED IDEOGRAPH - 0xC0BA: 0x7BEE, //CJK UNIFIED IDEOGRAPH - 0xC0BB: 0x9611, //CJK UNIFIED IDEOGRAPH - 0xC0BC: 0x5170, //CJK UNIFIED IDEOGRAPH - 0xC0BD: 0x6F9C, //CJK UNIFIED IDEOGRAPH - 0xC0BE: 0x8C30, //CJK UNIFIED IDEOGRAPH - 0xC0BF: 0x63FD, //CJK UNIFIED IDEOGRAPH - 0xC0C0: 0x89C8, //CJK UNIFIED IDEOGRAPH - 0xC0C1: 0x61D2, //CJK UNIFIED IDEOGRAPH - 0xC0C2: 0x7F06, //CJK UNIFIED IDEOGRAPH - 0xC0C3: 0x70C2, //CJK UNIFIED IDEOGRAPH - 0xC0C4: 0x6EE5, //CJK UNIFIED IDEOGRAPH - 0xC0C5: 0x7405, //CJK UNIFIED IDEOGRAPH - 0xC0C6: 0x6994, //CJK UNIFIED IDEOGRAPH - 0xC0C7: 0x72FC, //CJK UNIFIED IDEOGRAPH - 0xC0C8: 0x5ECA, //CJK UNIFIED IDEOGRAPH - 0xC0C9: 0x90CE, //CJK UNIFIED IDEOGRAPH - 0xC0CA: 0x6717, //CJK UNIFIED IDEOGRAPH - 0xC0CB: 0x6D6A, //CJK UNIFIED IDEOGRAPH - 0xC0CC: 0x635E, //CJK UNIFIED IDEOGRAPH - 0xC0CD: 0x52B3, //CJK UNIFIED IDEOGRAPH - 0xC0CE: 0x7262, //CJK UNIFIED IDEOGRAPH - 0xC0CF: 0x8001, //CJK UNIFIED IDEOGRAPH - 0xC0D0: 0x4F6C, //CJK UNIFIED IDEOGRAPH - 0xC0D1: 0x59E5, //CJK UNIFIED IDEOGRAPH - 0xC0D2: 0x916A, //CJK UNIFIED IDEOGRAPH - 0xC0D3: 0x70D9, //CJK UNIFIED IDEOGRAPH - 0xC0D4: 0x6D9D, //CJK UNIFIED IDEOGRAPH - 0xC0D5: 0x52D2, //CJK UNIFIED IDEOGRAPH - 0xC0D6: 0x4E50, //CJK UNIFIED IDEOGRAPH - 0xC0D7: 0x96F7, //CJK UNIFIED IDEOGRAPH - 0xC0D8: 0x956D, //CJK UNIFIED IDEOGRAPH - 0xC0D9: 0x857E, //CJK UNIFIED IDEOGRAPH - 0xC0DA: 0x78CA, //CJK UNIFIED IDEOGRAPH - 0xC0DB: 0x7D2F, //CJK UNIFIED IDEOGRAPH - 0xC0DC: 0x5121, //CJK UNIFIED IDEOGRAPH - 0xC0DD: 0x5792, //CJK UNIFIED IDEOGRAPH - 0xC0DE: 0x64C2, //CJK UNIFIED IDEOGRAPH - 0xC0DF: 0x808B, //CJK UNIFIED IDEOGRAPH - 0xC0E0: 0x7C7B, //CJK UNIFIED IDEOGRAPH - 0xC0E1: 0x6CEA, //CJK UNIFIED IDEOGRAPH - 0xC0E2: 0x68F1, //CJK UNIFIED IDEOGRAPH - 0xC0E3: 0x695E, //CJK UNIFIED IDEOGRAPH - 0xC0E4: 0x51B7, //CJK UNIFIED IDEOGRAPH - 0xC0E5: 0x5398, //CJK UNIFIED IDEOGRAPH - 0xC0E6: 0x68A8, //CJK UNIFIED IDEOGRAPH - 0xC0E7: 0x7281, //CJK UNIFIED IDEOGRAPH - 0xC0E8: 0x9ECE, //CJK UNIFIED IDEOGRAPH - 0xC0E9: 0x7BF1, //CJK UNIFIED IDEOGRAPH - 0xC0EA: 0x72F8, //CJK UNIFIED IDEOGRAPH - 0xC0EB: 0x79BB, //CJK UNIFIED IDEOGRAPH - 0xC0EC: 0x6F13, //CJK UNIFIED IDEOGRAPH - 0xC0ED: 0x7406, //CJK UNIFIED IDEOGRAPH - 0xC0EE: 0x674E, //CJK UNIFIED IDEOGRAPH - 0xC0EF: 0x91CC, //CJK UNIFIED IDEOGRAPH - 0xC0F0: 0x9CA4, //CJK UNIFIED IDEOGRAPH - 0xC0F1: 0x793C, //CJK UNIFIED IDEOGRAPH - 0xC0F2: 0x8389, //CJK UNIFIED IDEOGRAPH - 0xC0F3: 0x8354, //CJK UNIFIED IDEOGRAPH - 0xC0F4: 0x540F, //CJK UNIFIED IDEOGRAPH - 0xC0F5: 0x6817, //CJK UNIFIED IDEOGRAPH - 0xC0F6: 0x4E3D, //CJK UNIFIED IDEOGRAPH - 0xC0F7: 0x5389, //CJK UNIFIED IDEOGRAPH - 0xC0F8: 0x52B1, //CJK UNIFIED IDEOGRAPH - 0xC0F9: 0x783E, //CJK UNIFIED IDEOGRAPH - 0xC0FA: 0x5386, //CJK UNIFIED IDEOGRAPH - 0xC0FB: 0x5229, //CJK UNIFIED IDEOGRAPH - 0xC0FC: 0x5088, //CJK UNIFIED IDEOGRAPH - 0xC0FD: 0x4F8B, //CJK UNIFIED IDEOGRAPH - 0xC0FE: 0x4FD0, //CJK UNIFIED IDEOGRAPH - 0xC140: 0x7F56, //CJK UNIFIED IDEOGRAPH - 0xC141: 0x7F59, //CJK UNIFIED IDEOGRAPH - 0xC142: 0x7F5B, //CJK UNIFIED IDEOGRAPH - 0xC143: 0x7F5C, //CJK UNIFIED IDEOGRAPH - 0xC144: 0x7F5D, //CJK UNIFIED IDEOGRAPH - 0xC145: 0x7F5E, //CJK UNIFIED IDEOGRAPH - 0xC146: 0x7F60, //CJK UNIFIED IDEOGRAPH - 0xC147: 0x7F63, //CJK UNIFIED IDEOGRAPH - 0xC148: 0x7F64, //CJK UNIFIED IDEOGRAPH - 0xC149: 0x7F65, //CJK UNIFIED IDEOGRAPH - 0xC14A: 0x7F66, //CJK UNIFIED IDEOGRAPH - 0xC14B: 0x7F67, //CJK UNIFIED IDEOGRAPH - 0xC14C: 0x7F6B, //CJK UNIFIED IDEOGRAPH - 0xC14D: 0x7F6C, //CJK UNIFIED IDEOGRAPH - 0xC14E: 0x7F6D, //CJK UNIFIED IDEOGRAPH - 0xC14F: 0x7F6F, //CJK UNIFIED IDEOGRAPH - 0xC150: 0x7F70, //CJK UNIFIED IDEOGRAPH - 0xC151: 0x7F73, //CJK UNIFIED IDEOGRAPH - 0xC152: 0x7F75, //CJK UNIFIED IDEOGRAPH - 0xC153: 0x7F76, //CJK UNIFIED IDEOGRAPH - 0xC154: 0x7F77, //CJK UNIFIED IDEOGRAPH - 0xC155: 0x7F78, //CJK UNIFIED IDEOGRAPH - 0xC156: 0x7F7A, //CJK UNIFIED IDEOGRAPH - 0xC157: 0x7F7B, //CJK UNIFIED IDEOGRAPH - 0xC158: 0x7F7C, //CJK UNIFIED IDEOGRAPH - 0xC159: 0x7F7D, //CJK UNIFIED IDEOGRAPH - 0xC15A: 0x7F7F, //CJK UNIFIED IDEOGRAPH - 0xC15B: 0x7F80, //CJK UNIFIED IDEOGRAPH - 0xC15C: 0x7F82, //CJK UNIFIED IDEOGRAPH - 0xC15D: 0x7F83, //CJK UNIFIED IDEOGRAPH - 0xC15E: 0x7F84, //CJK UNIFIED IDEOGRAPH - 0xC15F: 0x7F85, //CJK UNIFIED IDEOGRAPH - 0xC160: 0x7F86, //CJK UNIFIED IDEOGRAPH - 0xC161: 0x7F87, //CJK UNIFIED IDEOGRAPH - 0xC162: 0x7F88, //CJK UNIFIED IDEOGRAPH - 0xC163: 0x7F89, //CJK UNIFIED IDEOGRAPH - 0xC164: 0x7F8B, //CJK UNIFIED IDEOGRAPH - 0xC165: 0x7F8D, //CJK UNIFIED IDEOGRAPH - 0xC166: 0x7F8F, //CJK UNIFIED IDEOGRAPH - 0xC167: 0x7F90, //CJK UNIFIED IDEOGRAPH - 0xC168: 0x7F91, //CJK UNIFIED IDEOGRAPH - 0xC169: 0x7F92, //CJK UNIFIED IDEOGRAPH - 0xC16A: 0x7F93, //CJK UNIFIED IDEOGRAPH - 0xC16B: 0x7F95, //CJK UNIFIED IDEOGRAPH - 0xC16C: 0x7F96, //CJK UNIFIED IDEOGRAPH - 0xC16D: 0x7F97, //CJK UNIFIED IDEOGRAPH - 0xC16E: 0x7F98, //CJK UNIFIED IDEOGRAPH - 0xC16F: 0x7F99, //CJK UNIFIED IDEOGRAPH - 0xC170: 0x7F9B, //CJK UNIFIED IDEOGRAPH - 0xC171: 0x7F9C, //CJK UNIFIED IDEOGRAPH - 0xC172: 0x7FA0, //CJK UNIFIED IDEOGRAPH - 0xC173: 0x7FA2, //CJK UNIFIED IDEOGRAPH - 0xC174: 0x7FA3, //CJK UNIFIED IDEOGRAPH - 0xC175: 0x7FA5, //CJK UNIFIED IDEOGRAPH - 0xC176: 0x7FA6, //CJK UNIFIED IDEOGRAPH - 0xC177: 0x7FA8, //CJK UNIFIED IDEOGRAPH - 0xC178: 0x7FA9, //CJK UNIFIED IDEOGRAPH - 0xC179: 0x7FAA, //CJK UNIFIED IDEOGRAPH - 0xC17A: 0x7FAB, //CJK UNIFIED IDEOGRAPH - 0xC17B: 0x7FAC, //CJK UNIFIED IDEOGRAPH - 0xC17C: 0x7FAD, //CJK UNIFIED IDEOGRAPH - 0xC17D: 0x7FAE, //CJK UNIFIED IDEOGRAPH - 0xC17E: 0x7FB1, //CJK UNIFIED IDEOGRAPH - 0xC180: 0x7FB3, //CJK UNIFIED IDEOGRAPH - 0xC181: 0x7FB4, //CJK UNIFIED IDEOGRAPH - 0xC182: 0x7FB5, //CJK UNIFIED IDEOGRAPH - 0xC183: 0x7FB6, //CJK UNIFIED IDEOGRAPH - 0xC184: 0x7FB7, //CJK UNIFIED IDEOGRAPH - 0xC185: 0x7FBA, //CJK UNIFIED IDEOGRAPH - 0xC186: 0x7FBB, //CJK UNIFIED IDEOGRAPH - 0xC187: 0x7FBE, //CJK UNIFIED IDEOGRAPH - 0xC188: 0x7FC0, //CJK UNIFIED IDEOGRAPH - 0xC189: 0x7FC2, //CJK UNIFIED IDEOGRAPH - 0xC18A: 0x7FC3, //CJK UNIFIED IDEOGRAPH - 0xC18B: 0x7FC4, //CJK UNIFIED IDEOGRAPH - 0xC18C: 0x7FC6, //CJK UNIFIED IDEOGRAPH - 0xC18D: 0x7FC7, //CJK UNIFIED IDEOGRAPH - 0xC18E: 0x7FC8, //CJK UNIFIED IDEOGRAPH - 0xC18F: 0x7FC9, //CJK UNIFIED IDEOGRAPH - 0xC190: 0x7FCB, //CJK UNIFIED IDEOGRAPH - 0xC191: 0x7FCD, //CJK UNIFIED IDEOGRAPH - 0xC192: 0x7FCF, //CJK UNIFIED IDEOGRAPH - 0xC193: 0x7FD0, //CJK UNIFIED IDEOGRAPH - 0xC194: 0x7FD1, //CJK UNIFIED IDEOGRAPH - 0xC195: 0x7FD2, //CJK UNIFIED IDEOGRAPH - 0xC196: 0x7FD3, //CJK UNIFIED IDEOGRAPH - 0xC197: 0x7FD6, //CJK UNIFIED IDEOGRAPH - 0xC198: 0x7FD7, //CJK UNIFIED IDEOGRAPH - 0xC199: 0x7FD9, //CJK UNIFIED IDEOGRAPH - 0xC19A: 0x7FDA, //CJK UNIFIED IDEOGRAPH - 0xC19B: 0x7FDB, //CJK UNIFIED IDEOGRAPH - 0xC19C: 0x7FDC, //CJK UNIFIED IDEOGRAPH - 0xC19D: 0x7FDD, //CJK UNIFIED IDEOGRAPH - 0xC19E: 0x7FDE, //CJK UNIFIED IDEOGRAPH - 0xC19F: 0x7FE2, //CJK UNIFIED IDEOGRAPH - 0xC1A0: 0x7FE3, //CJK UNIFIED IDEOGRAPH - 0xC1A1: 0x75E2, //CJK UNIFIED IDEOGRAPH - 0xC1A2: 0x7ACB, //CJK UNIFIED IDEOGRAPH - 0xC1A3: 0x7C92, //CJK UNIFIED IDEOGRAPH - 0xC1A4: 0x6CA5, //CJK UNIFIED IDEOGRAPH - 0xC1A5: 0x96B6, //CJK UNIFIED IDEOGRAPH - 0xC1A6: 0x529B, //CJK UNIFIED IDEOGRAPH - 0xC1A7: 0x7483, //CJK UNIFIED IDEOGRAPH - 0xC1A8: 0x54E9, //CJK UNIFIED IDEOGRAPH - 0xC1A9: 0x4FE9, //CJK UNIFIED IDEOGRAPH - 0xC1AA: 0x8054, //CJK UNIFIED IDEOGRAPH - 0xC1AB: 0x83B2, //CJK UNIFIED IDEOGRAPH - 0xC1AC: 0x8FDE, //CJK UNIFIED IDEOGRAPH - 0xC1AD: 0x9570, //CJK UNIFIED IDEOGRAPH - 0xC1AE: 0x5EC9, //CJK UNIFIED IDEOGRAPH - 0xC1AF: 0x601C, //CJK UNIFIED IDEOGRAPH - 0xC1B0: 0x6D9F, //CJK UNIFIED IDEOGRAPH - 0xC1B1: 0x5E18, //CJK UNIFIED IDEOGRAPH - 0xC1B2: 0x655B, //CJK UNIFIED IDEOGRAPH - 0xC1B3: 0x8138, //CJK UNIFIED IDEOGRAPH - 0xC1B4: 0x94FE, //CJK UNIFIED IDEOGRAPH - 0xC1B5: 0x604B, //CJK UNIFIED IDEOGRAPH - 0xC1B6: 0x70BC, //CJK UNIFIED IDEOGRAPH - 0xC1B7: 0x7EC3, //CJK UNIFIED IDEOGRAPH - 0xC1B8: 0x7CAE, //CJK UNIFIED IDEOGRAPH - 0xC1B9: 0x51C9, //CJK UNIFIED IDEOGRAPH - 0xC1BA: 0x6881, //CJK UNIFIED IDEOGRAPH - 0xC1BB: 0x7CB1, //CJK UNIFIED IDEOGRAPH - 0xC1BC: 0x826F, //CJK UNIFIED IDEOGRAPH - 0xC1BD: 0x4E24, //CJK UNIFIED IDEOGRAPH - 0xC1BE: 0x8F86, //CJK UNIFIED IDEOGRAPH - 0xC1BF: 0x91CF, //CJK UNIFIED IDEOGRAPH - 0xC1C0: 0x667E, //CJK UNIFIED IDEOGRAPH - 0xC1C1: 0x4EAE, //CJK UNIFIED IDEOGRAPH - 0xC1C2: 0x8C05, //CJK UNIFIED IDEOGRAPH - 0xC1C3: 0x64A9, //CJK UNIFIED IDEOGRAPH - 0xC1C4: 0x804A, //CJK UNIFIED IDEOGRAPH - 0xC1C5: 0x50DA, //CJK UNIFIED IDEOGRAPH - 0xC1C6: 0x7597, //CJK UNIFIED IDEOGRAPH - 0xC1C7: 0x71CE, //CJK UNIFIED IDEOGRAPH - 0xC1C8: 0x5BE5, //CJK UNIFIED IDEOGRAPH - 0xC1C9: 0x8FBD, //CJK UNIFIED IDEOGRAPH - 0xC1CA: 0x6F66, //CJK UNIFIED IDEOGRAPH - 0xC1CB: 0x4E86, //CJK UNIFIED IDEOGRAPH - 0xC1CC: 0x6482, //CJK UNIFIED IDEOGRAPH - 0xC1CD: 0x9563, //CJK UNIFIED IDEOGRAPH - 0xC1CE: 0x5ED6, //CJK UNIFIED IDEOGRAPH - 0xC1CF: 0x6599, //CJK UNIFIED IDEOGRAPH - 0xC1D0: 0x5217, //CJK UNIFIED IDEOGRAPH - 0xC1D1: 0x88C2, //CJK UNIFIED IDEOGRAPH - 0xC1D2: 0x70C8, //CJK UNIFIED IDEOGRAPH - 0xC1D3: 0x52A3, //CJK UNIFIED IDEOGRAPH - 0xC1D4: 0x730E, //CJK UNIFIED IDEOGRAPH - 0xC1D5: 0x7433, //CJK UNIFIED IDEOGRAPH - 0xC1D6: 0x6797, //CJK UNIFIED IDEOGRAPH - 0xC1D7: 0x78F7, //CJK UNIFIED IDEOGRAPH - 0xC1D8: 0x9716, //CJK UNIFIED IDEOGRAPH - 0xC1D9: 0x4E34, //CJK UNIFIED IDEOGRAPH - 0xC1DA: 0x90BB, //CJK UNIFIED IDEOGRAPH - 0xC1DB: 0x9CDE, //CJK UNIFIED IDEOGRAPH - 0xC1DC: 0x6DCB, //CJK UNIFIED IDEOGRAPH - 0xC1DD: 0x51DB, //CJK UNIFIED IDEOGRAPH - 0xC1DE: 0x8D41, //CJK UNIFIED IDEOGRAPH - 0xC1DF: 0x541D, //CJK UNIFIED IDEOGRAPH - 0xC1E0: 0x62CE, //CJK UNIFIED IDEOGRAPH - 0xC1E1: 0x73B2, //CJK UNIFIED IDEOGRAPH - 0xC1E2: 0x83F1, //CJK UNIFIED IDEOGRAPH - 0xC1E3: 0x96F6, //CJK UNIFIED IDEOGRAPH - 0xC1E4: 0x9F84, //CJK UNIFIED IDEOGRAPH - 0xC1E5: 0x94C3, //CJK UNIFIED IDEOGRAPH - 0xC1E6: 0x4F36, //CJK UNIFIED IDEOGRAPH - 0xC1E7: 0x7F9A, //CJK UNIFIED IDEOGRAPH - 0xC1E8: 0x51CC, //CJK UNIFIED IDEOGRAPH - 0xC1E9: 0x7075, //CJK UNIFIED IDEOGRAPH - 0xC1EA: 0x9675, //CJK UNIFIED IDEOGRAPH - 0xC1EB: 0x5CAD, //CJK UNIFIED IDEOGRAPH - 0xC1EC: 0x9886, //CJK UNIFIED IDEOGRAPH - 0xC1ED: 0x53E6, //CJK UNIFIED IDEOGRAPH - 0xC1EE: 0x4EE4, //CJK UNIFIED IDEOGRAPH - 0xC1EF: 0x6E9C, //CJK UNIFIED IDEOGRAPH - 0xC1F0: 0x7409, //CJK UNIFIED IDEOGRAPH - 0xC1F1: 0x69B4, //CJK UNIFIED IDEOGRAPH - 0xC1F2: 0x786B, //CJK UNIFIED IDEOGRAPH - 0xC1F3: 0x998F, //CJK UNIFIED IDEOGRAPH - 0xC1F4: 0x7559, //CJK UNIFIED IDEOGRAPH - 0xC1F5: 0x5218, //CJK UNIFIED IDEOGRAPH - 0xC1F6: 0x7624, //CJK UNIFIED IDEOGRAPH - 0xC1F7: 0x6D41, //CJK UNIFIED IDEOGRAPH - 0xC1F8: 0x67F3, //CJK UNIFIED IDEOGRAPH - 0xC1F9: 0x516D, //CJK UNIFIED IDEOGRAPH - 0xC1FA: 0x9F99, //CJK UNIFIED IDEOGRAPH - 0xC1FB: 0x804B, //CJK UNIFIED IDEOGRAPH - 0xC1FC: 0x5499, //CJK UNIFIED IDEOGRAPH - 0xC1FD: 0x7B3C, //CJK UNIFIED IDEOGRAPH - 0xC1FE: 0x7ABF, //CJK UNIFIED IDEOGRAPH - 0xC240: 0x7FE4, //CJK UNIFIED IDEOGRAPH - 0xC241: 0x7FE7, //CJK UNIFIED IDEOGRAPH - 0xC242: 0x7FE8, //CJK UNIFIED IDEOGRAPH - 0xC243: 0x7FEA, //CJK UNIFIED IDEOGRAPH - 0xC244: 0x7FEB, //CJK UNIFIED IDEOGRAPH - 0xC245: 0x7FEC, //CJK UNIFIED IDEOGRAPH - 0xC246: 0x7FED, //CJK UNIFIED IDEOGRAPH - 0xC247: 0x7FEF, //CJK UNIFIED IDEOGRAPH - 0xC248: 0x7FF2, //CJK UNIFIED IDEOGRAPH - 0xC249: 0x7FF4, //CJK UNIFIED IDEOGRAPH - 0xC24A: 0x7FF5, //CJK UNIFIED IDEOGRAPH - 0xC24B: 0x7FF6, //CJK UNIFIED IDEOGRAPH - 0xC24C: 0x7FF7, //CJK UNIFIED IDEOGRAPH - 0xC24D: 0x7FF8, //CJK UNIFIED IDEOGRAPH - 0xC24E: 0x7FF9, //CJK UNIFIED IDEOGRAPH - 0xC24F: 0x7FFA, //CJK UNIFIED IDEOGRAPH - 0xC250: 0x7FFD, //CJK UNIFIED IDEOGRAPH - 0xC251: 0x7FFE, //CJK UNIFIED IDEOGRAPH - 0xC252: 0x7FFF, //CJK UNIFIED IDEOGRAPH - 0xC253: 0x8002, //CJK UNIFIED IDEOGRAPH - 0xC254: 0x8007, //CJK UNIFIED IDEOGRAPH - 0xC255: 0x8008, //CJK UNIFIED IDEOGRAPH - 0xC256: 0x8009, //CJK UNIFIED IDEOGRAPH - 0xC257: 0x800A, //CJK UNIFIED IDEOGRAPH - 0xC258: 0x800E, //CJK UNIFIED IDEOGRAPH - 0xC259: 0x800F, //CJK UNIFIED IDEOGRAPH - 0xC25A: 0x8011, //CJK UNIFIED IDEOGRAPH - 0xC25B: 0x8013, //CJK UNIFIED IDEOGRAPH - 0xC25C: 0x801A, //CJK UNIFIED IDEOGRAPH - 0xC25D: 0x801B, //CJK UNIFIED IDEOGRAPH - 0xC25E: 0x801D, //CJK UNIFIED IDEOGRAPH - 0xC25F: 0x801E, //CJK UNIFIED IDEOGRAPH - 0xC260: 0x801F, //CJK UNIFIED IDEOGRAPH - 0xC261: 0x8021, //CJK UNIFIED IDEOGRAPH - 0xC262: 0x8023, //CJK UNIFIED IDEOGRAPH - 0xC263: 0x8024, //CJK UNIFIED IDEOGRAPH - 0xC264: 0x802B, //CJK UNIFIED IDEOGRAPH - 0xC265: 0x802C, //CJK UNIFIED IDEOGRAPH - 0xC266: 0x802D, //CJK UNIFIED IDEOGRAPH - 0xC267: 0x802E, //CJK UNIFIED IDEOGRAPH - 0xC268: 0x802F, //CJK UNIFIED IDEOGRAPH - 0xC269: 0x8030, //CJK UNIFIED IDEOGRAPH - 0xC26A: 0x8032, //CJK UNIFIED IDEOGRAPH - 0xC26B: 0x8034, //CJK UNIFIED IDEOGRAPH - 0xC26C: 0x8039, //CJK UNIFIED IDEOGRAPH - 0xC26D: 0x803A, //CJK UNIFIED IDEOGRAPH - 0xC26E: 0x803C, //CJK UNIFIED IDEOGRAPH - 0xC26F: 0x803E, //CJK UNIFIED IDEOGRAPH - 0xC270: 0x8040, //CJK UNIFIED IDEOGRAPH - 0xC271: 0x8041, //CJK UNIFIED IDEOGRAPH - 0xC272: 0x8044, //CJK UNIFIED IDEOGRAPH - 0xC273: 0x8045, //CJK UNIFIED IDEOGRAPH - 0xC274: 0x8047, //CJK UNIFIED IDEOGRAPH - 0xC275: 0x8048, //CJK UNIFIED IDEOGRAPH - 0xC276: 0x8049, //CJK UNIFIED IDEOGRAPH - 0xC277: 0x804E, //CJK UNIFIED IDEOGRAPH - 0xC278: 0x804F, //CJK UNIFIED IDEOGRAPH - 0xC279: 0x8050, //CJK UNIFIED IDEOGRAPH - 0xC27A: 0x8051, //CJK UNIFIED IDEOGRAPH - 0xC27B: 0x8053, //CJK UNIFIED IDEOGRAPH - 0xC27C: 0x8055, //CJK UNIFIED IDEOGRAPH - 0xC27D: 0x8056, //CJK UNIFIED IDEOGRAPH - 0xC27E: 0x8057, //CJK UNIFIED IDEOGRAPH - 0xC280: 0x8059, //CJK UNIFIED IDEOGRAPH - 0xC281: 0x805B, //CJK UNIFIED IDEOGRAPH - 0xC282: 0x805C, //CJK UNIFIED IDEOGRAPH - 0xC283: 0x805D, //CJK UNIFIED IDEOGRAPH - 0xC284: 0x805E, //CJK UNIFIED IDEOGRAPH - 0xC285: 0x805F, //CJK UNIFIED IDEOGRAPH - 0xC286: 0x8060, //CJK UNIFIED IDEOGRAPH - 0xC287: 0x8061, //CJK UNIFIED IDEOGRAPH - 0xC288: 0x8062, //CJK UNIFIED IDEOGRAPH - 0xC289: 0x8063, //CJK UNIFIED IDEOGRAPH - 0xC28A: 0x8064, //CJK UNIFIED IDEOGRAPH - 0xC28B: 0x8065, //CJK UNIFIED IDEOGRAPH - 0xC28C: 0x8066, //CJK UNIFIED IDEOGRAPH - 0xC28D: 0x8067, //CJK UNIFIED IDEOGRAPH - 0xC28E: 0x8068, //CJK UNIFIED IDEOGRAPH - 0xC28F: 0x806B, //CJK UNIFIED IDEOGRAPH - 0xC290: 0x806C, //CJK UNIFIED IDEOGRAPH - 0xC291: 0x806D, //CJK UNIFIED IDEOGRAPH - 0xC292: 0x806E, //CJK UNIFIED IDEOGRAPH - 0xC293: 0x806F, //CJK UNIFIED IDEOGRAPH - 0xC294: 0x8070, //CJK UNIFIED IDEOGRAPH - 0xC295: 0x8072, //CJK UNIFIED IDEOGRAPH - 0xC296: 0x8073, //CJK UNIFIED IDEOGRAPH - 0xC297: 0x8074, //CJK UNIFIED IDEOGRAPH - 0xC298: 0x8075, //CJK UNIFIED IDEOGRAPH - 0xC299: 0x8076, //CJK UNIFIED IDEOGRAPH - 0xC29A: 0x8077, //CJK UNIFIED IDEOGRAPH - 0xC29B: 0x8078, //CJK UNIFIED IDEOGRAPH - 0xC29C: 0x8079, //CJK UNIFIED IDEOGRAPH - 0xC29D: 0x807A, //CJK UNIFIED IDEOGRAPH - 0xC29E: 0x807B, //CJK UNIFIED IDEOGRAPH - 0xC29F: 0x807C, //CJK UNIFIED IDEOGRAPH - 0xC2A0: 0x807D, //CJK UNIFIED IDEOGRAPH - 0xC2A1: 0x9686, //CJK UNIFIED IDEOGRAPH - 0xC2A2: 0x5784, //CJK UNIFIED IDEOGRAPH - 0xC2A3: 0x62E2, //CJK UNIFIED IDEOGRAPH - 0xC2A4: 0x9647, //CJK UNIFIED IDEOGRAPH - 0xC2A5: 0x697C, //CJK UNIFIED IDEOGRAPH - 0xC2A6: 0x5A04, //CJK UNIFIED IDEOGRAPH - 0xC2A7: 0x6402, //CJK UNIFIED IDEOGRAPH - 0xC2A8: 0x7BD3, //CJK UNIFIED IDEOGRAPH - 0xC2A9: 0x6F0F, //CJK UNIFIED IDEOGRAPH - 0xC2AA: 0x964B, //CJK UNIFIED IDEOGRAPH - 0xC2AB: 0x82A6, //CJK UNIFIED IDEOGRAPH - 0xC2AC: 0x5362, //CJK UNIFIED IDEOGRAPH - 0xC2AD: 0x9885, //CJK UNIFIED IDEOGRAPH - 0xC2AE: 0x5E90, //CJK UNIFIED IDEOGRAPH - 0xC2AF: 0x7089, //CJK UNIFIED IDEOGRAPH - 0xC2B0: 0x63B3, //CJK UNIFIED IDEOGRAPH - 0xC2B1: 0x5364, //CJK UNIFIED IDEOGRAPH - 0xC2B2: 0x864F, //CJK UNIFIED IDEOGRAPH - 0xC2B3: 0x9C81, //CJK UNIFIED IDEOGRAPH - 0xC2B4: 0x9E93, //CJK UNIFIED IDEOGRAPH - 0xC2B5: 0x788C, //CJK UNIFIED IDEOGRAPH - 0xC2B6: 0x9732, //CJK UNIFIED IDEOGRAPH - 0xC2B7: 0x8DEF, //CJK UNIFIED IDEOGRAPH - 0xC2B8: 0x8D42, //CJK UNIFIED IDEOGRAPH - 0xC2B9: 0x9E7F, //CJK UNIFIED IDEOGRAPH - 0xC2BA: 0x6F5E, //CJK UNIFIED IDEOGRAPH - 0xC2BB: 0x7984, //CJK UNIFIED IDEOGRAPH - 0xC2BC: 0x5F55, //CJK UNIFIED IDEOGRAPH - 0xC2BD: 0x9646, //CJK UNIFIED IDEOGRAPH - 0xC2BE: 0x622E, //CJK UNIFIED IDEOGRAPH - 0xC2BF: 0x9A74, //CJK UNIFIED IDEOGRAPH - 0xC2C0: 0x5415, //CJK UNIFIED IDEOGRAPH - 0xC2C1: 0x94DD, //CJK UNIFIED IDEOGRAPH - 0xC2C2: 0x4FA3, //CJK UNIFIED IDEOGRAPH - 0xC2C3: 0x65C5, //CJK UNIFIED IDEOGRAPH - 0xC2C4: 0x5C65, //CJK UNIFIED IDEOGRAPH - 0xC2C5: 0x5C61, //CJK UNIFIED IDEOGRAPH - 0xC2C6: 0x7F15, //CJK UNIFIED IDEOGRAPH - 0xC2C7: 0x8651, //CJK UNIFIED IDEOGRAPH - 0xC2C8: 0x6C2F, //CJK UNIFIED IDEOGRAPH - 0xC2C9: 0x5F8B, //CJK UNIFIED IDEOGRAPH - 0xC2CA: 0x7387, //CJK UNIFIED IDEOGRAPH - 0xC2CB: 0x6EE4, //CJK UNIFIED IDEOGRAPH - 0xC2CC: 0x7EFF, //CJK UNIFIED IDEOGRAPH - 0xC2CD: 0x5CE6, //CJK UNIFIED IDEOGRAPH - 0xC2CE: 0x631B, //CJK UNIFIED IDEOGRAPH - 0xC2CF: 0x5B6A, //CJK UNIFIED IDEOGRAPH - 0xC2D0: 0x6EE6, //CJK UNIFIED IDEOGRAPH - 0xC2D1: 0x5375, //CJK UNIFIED IDEOGRAPH - 0xC2D2: 0x4E71, //CJK UNIFIED IDEOGRAPH - 0xC2D3: 0x63A0, //CJK UNIFIED IDEOGRAPH - 0xC2D4: 0x7565, //CJK UNIFIED IDEOGRAPH - 0xC2D5: 0x62A1, //CJK UNIFIED IDEOGRAPH - 0xC2D6: 0x8F6E, //CJK UNIFIED IDEOGRAPH - 0xC2D7: 0x4F26, //CJK UNIFIED IDEOGRAPH - 0xC2D8: 0x4ED1, //CJK UNIFIED IDEOGRAPH - 0xC2D9: 0x6CA6, //CJK UNIFIED IDEOGRAPH - 0xC2DA: 0x7EB6, //CJK UNIFIED IDEOGRAPH - 0xC2DB: 0x8BBA, //CJK UNIFIED IDEOGRAPH - 0xC2DC: 0x841D, //CJK UNIFIED IDEOGRAPH - 0xC2DD: 0x87BA, //CJK UNIFIED IDEOGRAPH - 0xC2DE: 0x7F57, //CJK UNIFIED IDEOGRAPH - 0xC2DF: 0x903B, //CJK UNIFIED IDEOGRAPH - 0xC2E0: 0x9523, //CJK UNIFIED IDEOGRAPH - 0xC2E1: 0x7BA9, //CJK UNIFIED IDEOGRAPH - 0xC2E2: 0x9AA1, //CJK UNIFIED IDEOGRAPH - 0xC2E3: 0x88F8, //CJK UNIFIED IDEOGRAPH - 0xC2E4: 0x843D, //CJK UNIFIED IDEOGRAPH - 0xC2E5: 0x6D1B, //CJK UNIFIED IDEOGRAPH - 0xC2E6: 0x9A86, //CJK UNIFIED IDEOGRAPH - 0xC2E7: 0x7EDC, //CJK UNIFIED IDEOGRAPH - 0xC2E8: 0x5988, //CJK UNIFIED IDEOGRAPH - 0xC2E9: 0x9EBB, //CJK UNIFIED IDEOGRAPH - 0xC2EA: 0x739B, //CJK UNIFIED IDEOGRAPH - 0xC2EB: 0x7801, //CJK UNIFIED IDEOGRAPH - 0xC2EC: 0x8682, //CJK UNIFIED IDEOGRAPH - 0xC2ED: 0x9A6C, //CJK UNIFIED IDEOGRAPH - 0xC2EE: 0x9A82, //CJK UNIFIED IDEOGRAPH - 0xC2EF: 0x561B, //CJK UNIFIED IDEOGRAPH - 0xC2F0: 0x5417, //CJK UNIFIED IDEOGRAPH - 0xC2F1: 0x57CB, //CJK UNIFIED IDEOGRAPH - 0xC2F2: 0x4E70, //CJK UNIFIED IDEOGRAPH - 0xC2F3: 0x9EA6, //CJK UNIFIED IDEOGRAPH - 0xC2F4: 0x5356, //CJK UNIFIED IDEOGRAPH - 0xC2F5: 0x8FC8, //CJK UNIFIED IDEOGRAPH - 0xC2F6: 0x8109, //CJK UNIFIED IDEOGRAPH - 0xC2F7: 0x7792, //CJK UNIFIED IDEOGRAPH - 0xC2F8: 0x9992, //CJK UNIFIED IDEOGRAPH - 0xC2F9: 0x86EE, //CJK UNIFIED IDEOGRAPH - 0xC2FA: 0x6EE1, //CJK UNIFIED IDEOGRAPH - 0xC2FB: 0x8513, //CJK UNIFIED IDEOGRAPH - 0xC2FC: 0x66FC, //CJK UNIFIED IDEOGRAPH - 0xC2FD: 0x6162, //CJK UNIFIED IDEOGRAPH - 0xC2FE: 0x6F2B, //CJK UNIFIED IDEOGRAPH - 0xC340: 0x807E, //CJK UNIFIED IDEOGRAPH - 0xC341: 0x8081, //CJK UNIFIED IDEOGRAPH - 0xC342: 0x8082, //CJK UNIFIED IDEOGRAPH - 0xC343: 0x8085, //CJK UNIFIED IDEOGRAPH - 0xC344: 0x8088, //CJK UNIFIED IDEOGRAPH - 0xC345: 0x808A, //CJK UNIFIED IDEOGRAPH - 0xC346: 0x808D, //CJK UNIFIED IDEOGRAPH - 0xC347: 0x808E, //CJK UNIFIED IDEOGRAPH - 0xC348: 0x808F, //CJK UNIFIED IDEOGRAPH - 0xC349: 0x8090, //CJK UNIFIED IDEOGRAPH - 0xC34A: 0x8091, //CJK UNIFIED IDEOGRAPH - 0xC34B: 0x8092, //CJK UNIFIED IDEOGRAPH - 0xC34C: 0x8094, //CJK UNIFIED IDEOGRAPH - 0xC34D: 0x8095, //CJK UNIFIED IDEOGRAPH - 0xC34E: 0x8097, //CJK UNIFIED IDEOGRAPH - 0xC34F: 0x8099, //CJK UNIFIED IDEOGRAPH - 0xC350: 0x809E, //CJK UNIFIED IDEOGRAPH - 0xC351: 0x80A3, //CJK UNIFIED IDEOGRAPH - 0xC352: 0x80A6, //CJK UNIFIED IDEOGRAPH - 0xC353: 0x80A7, //CJK UNIFIED IDEOGRAPH - 0xC354: 0x80A8, //CJK UNIFIED IDEOGRAPH - 0xC355: 0x80AC, //CJK UNIFIED IDEOGRAPH - 0xC356: 0x80B0, //CJK UNIFIED IDEOGRAPH - 0xC357: 0x80B3, //CJK UNIFIED IDEOGRAPH - 0xC358: 0x80B5, //CJK UNIFIED IDEOGRAPH - 0xC359: 0x80B6, //CJK UNIFIED IDEOGRAPH - 0xC35A: 0x80B8, //CJK UNIFIED IDEOGRAPH - 0xC35B: 0x80B9, //CJK UNIFIED IDEOGRAPH - 0xC35C: 0x80BB, //CJK UNIFIED IDEOGRAPH - 0xC35D: 0x80C5, //CJK UNIFIED IDEOGRAPH - 0xC35E: 0x80C7, //CJK UNIFIED IDEOGRAPH - 0xC35F: 0x80C8, //CJK UNIFIED IDEOGRAPH - 0xC360: 0x80C9, //CJK UNIFIED IDEOGRAPH - 0xC361: 0x80CA, //CJK UNIFIED IDEOGRAPH - 0xC362: 0x80CB, //CJK UNIFIED IDEOGRAPH - 0xC363: 0x80CF, //CJK UNIFIED IDEOGRAPH - 0xC364: 0x80D0, //CJK UNIFIED IDEOGRAPH - 0xC365: 0x80D1, //CJK UNIFIED IDEOGRAPH - 0xC366: 0x80D2, //CJK UNIFIED IDEOGRAPH - 0xC367: 0x80D3, //CJK UNIFIED IDEOGRAPH - 0xC368: 0x80D4, //CJK UNIFIED IDEOGRAPH - 0xC369: 0x80D5, //CJK UNIFIED IDEOGRAPH - 0xC36A: 0x80D8, //CJK UNIFIED IDEOGRAPH - 0xC36B: 0x80DF, //CJK UNIFIED IDEOGRAPH - 0xC36C: 0x80E0, //CJK UNIFIED IDEOGRAPH - 0xC36D: 0x80E2, //CJK UNIFIED IDEOGRAPH - 0xC36E: 0x80E3, //CJK UNIFIED IDEOGRAPH - 0xC36F: 0x80E6, //CJK UNIFIED IDEOGRAPH - 0xC370: 0x80EE, //CJK UNIFIED IDEOGRAPH - 0xC371: 0x80F5, //CJK UNIFIED IDEOGRAPH - 0xC372: 0x80F7, //CJK UNIFIED IDEOGRAPH - 0xC373: 0x80F9, //CJK UNIFIED IDEOGRAPH - 0xC374: 0x80FB, //CJK UNIFIED IDEOGRAPH - 0xC375: 0x80FE, //CJK UNIFIED IDEOGRAPH - 0xC376: 0x80FF, //CJK UNIFIED IDEOGRAPH - 0xC377: 0x8100, //CJK UNIFIED IDEOGRAPH - 0xC378: 0x8101, //CJK UNIFIED IDEOGRAPH - 0xC379: 0x8103, //CJK UNIFIED IDEOGRAPH - 0xC37A: 0x8104, //CJK UNIFIED IDEOGRAPH - 0xC37B: 0x8105, //CJK UNIFIED IDEOGRAPH - 0xC37C: 0x8107, //CJK UNIFIED IDEOGRAPH - 0xC37D: 0x8108, //CJK UNIFIED IDEOGRAPH - 0xC37E: 0x810B, //CJK UNIFIED IDEOGRAPH - 0xC380: 0x810C, //CJK UNIFIED IDEOGRAPH - 0xC381: 0x8115, //CJK UNIFIED IDEOGRAPH - 0xC382: 0x8117, //CJK UNIFIED IDEOGRAPH - 0xC383: 0x8119, //CJK UNIFIED IDEOGRAPH - 0xC384: 0x811B, //CJK UNIFIED IDEOGRAPH - 0xC385: 0x811C, //CJK UNIFIED IDEOGRAPH - 0xC386: 0x811D, //CJK UNIFIED IDEOGRAPH - 0xC387: 0x811F, //CJK UNIFIED IDEOGRAPH - 0xC388: 0x8120, //CJK UNIFIED IDEOGRAPH - 0xC389: 0x8121, //CJK UNIFIED IDEOGRAPH - 0xC38A: 0x8122, //CJK UNIFIED IDEOGRAPH - 0xC38B: 0x8123, //CJK UNIFIED IDEOGRAPH - 0xC38C: 0x8124, //CJK UNIFIED IDEOGRAPH - 0xC38D: 0x8125, //CJK UNIFIED IDEOGRAPH - 0xC38E: 0x8126, //CJK UNIFIED IDEOGRAPH - 0xC38F: 0x8127, //CJK UNIFIED IDEOGRAPH - 0xC390: 0x8128, //CJK UNIFIED IDEOGRAPH - 0xC391: 0x8129, //CJK UNIFIED IDEOGRAPH - 0xC392: 0x812A, //CJK UNIFIED IDEOGRAPH - 0xC393: 0x812B, //CJK UNIFIED IDEOGRAPH - 0xC394: 0x812D, //CJK UNIFIED IDEOGRAPH - 0xC395: 0x812E, //CJK UNIFIED IDEOGRAPH - 0xC396: 0x8130, //CJK UNIFIED IDEOGRAPH - 0xC397: 0x8133, //CJK UNIFIED IDEOGRAPH - 0xC398: 0x8134, //CJK UNIFIED IDEOGRAPH - 0xC399: 0x8135, //CJK UNIFIED IDEOGRAPH - 0xC39A: 0x8137, //CJK UNIFIED IDEOGRAPH - 0xC39B: 0x8139, //CJK UNIFIED IDEOGRAPH - 0xC39C: 0x813A, //CJK UNIFIED IDEOGRAPH - 0xC39D: 0x813B, //CJK UNIFIED IDEOGRAPH - 0xC39E: 0x813C, //CJK UNIFIED IDEOGRAPH - 0xC39F: 0x813D, //CJK UNIFIED IDEOGRAPH - 0xC3A0: 0x813F, //CJK UNIFIED IDEOGRAPH - 0xC3A1: 0x8C29, //CJK UNIFIED IDEOGRAPH - 0xC3A2: 0x8292, //CJK UNIFIED IDEOGRAPH - 0xC3A3: 0x832B, //CJK UNIFIED IDEOGRAPH - 0xC3A4: 0x76F2, //CJK UNIFIED IDEOGRAPH - 0xC3A5: 0x6C13, //CJK UNIFIED IDEOGRAPH - 0xC3A6: 0x5FD9, //CJK UNIFIED IDEOGRAPH - 0xC3A7: 0x83BD, //CJK UNIFIED IDEOGRAPH - 0xC3A8: 0x732B, //CJK UNIFIED IDEOGRAPH - 0xC3A9: 0x8305, //CJK UNIFIED IDEOGRAPH - 0xC3AA: 0x951A, //CJK UNIFIED IDEOGRAPH - 0xC3AB: 0x6BDB, //CJK UNIFIED IDEOGRAPH - 0xC3AC: 0x77DB, //CJK UNIFIED IDEOGRAPH - 0xC3AD: 0x94C6, //CJK UNIFIED IDEOGRAPH - 0xC3AE: 0x536F, //CJK UNIFIED IDEOGRAPH - 0xC3AF: 0x8302, //CJK UNIFIED IDEOGRAPH - 0xC3B0: 0x5192, //CJK UNIFIED IDEOGRAPH - 0xC3B1: 0x5E3D, //CJK UNIFIED IDEOGRAPH - 0xC3B2: 0x8C8C, //CJK UNIFIED IDEOGRAPH - 0xC3B3: 0x8D38, //CJK UNIFIED IDEOGRAPH - 0xC3B4: 0x4E48, //CJK UNIFIED IDEOGRAPH - 0xC3B5: 0x73AB, //CJK UNIFIED IDEOGRAPH - 0xC3B6: 0x679A, //CJK UNIFIED IDEOGRAPH - 0xC3B7: 0x6885, //CJK UNIFIED IDEOGRAPH - 0xC3B8: 0x9176, //CJK UNIFIED IDEOGRAPH - 0xC3B9: 0x9709, //CJK UNIFIED IDEOGRAPH - 0xC3BA: 0x7164, //CJK UNIFIED IDEOGRAPH - 0xC3BB: 0x6CA1, //CJK UNIFIED IDEOGRAPH - 0xC3BC: 0x7709, //CJK UNIFIED IDEOGRAPH - 0xC3BD: 0x5A92, //CJK UNIFIED IDEOGRAPH - 0xC3BE: 0x9541, //CJK UNIFIED IDEOGRAPH - 0xC3BF: 0x6BCF, //CJK UNIFIED IDEOGRAPH - 0xC3C0: 0x7F8E, //CJK UNIFIED IDEOGRAPH - 0xC3C1: 0x6627, //CJK UNIFIED IDEOGRAPH - 0xC3C2: 0x5BD0, //CJK UNIFIED IDEOGRAPH - 0xC3C3: 0x59B9, //CJK UNIFIED IDEOGRAPH - 0xC3C4: 0x5A9A, //CJK UNIFIED IDEOGRAPH - 0xC3C5: 0x95E8, //CJK UNIFIED IDEOGRAPH - 0xC3C6: 0x95F7, //CJK UNIFIED IDEOGRAPH - 0xC3C7: 0x4EEC, //CJK UNIFIED IDEOGRAPH - 0xC3C8: 0x840C, //CJK UNIFIED IDEOGRAPH - 0xC3C9: 0x8499, //CJK UNIFIED IDEOGRAPH - 0xC3CA: 0x6AAC, //CJK UNIFIED IDEOGRAPH - 0xC3CB: 0x76DF, //CJK UNIFIED IDEOGRAPH - 0xC3CC: 0x9530, //CJK UNIFIED IDEOGRAPH - 0xC3CD: 0x731B, //CJK UNIFIED IDEOGRAPH - 0xC3CE: 0x68A6, //CJK UNIFIED IDEOGRAPH - 0xC3CF: 0x5B5F, //CJK UNIFIED IDEOGRAPH - 0xC3D0: 0x772F, //CJK UNIFIED IDEOGRAPH - 0xC3D1: 0x919A, //CJK UNIFIED IDEOGRAPH - 0xC3D2: 0x9761, //CJK UNIFIED IDEOGRAPH - 0xC3D3: 0x7CDC, //CJK UNIFIED IDEOGRAPH - 0xC3D4: 0x8FF7, //CJK UNIFIED IDEOGRAPH - 0xC3D5: 0x8C1C, //CJK UNIFIED IDEOGRAPH - 0xC3D6: 0x5F25, //CJK UNIFIED IDEOGRAPH - 0xC3D7: 0x7C73, //CJK UNIFIED IDEOGRAPH - 0xC3D8: 0x79D8, //CJK UNIFIED IDEOGRAPH - 0xC3D9: 0x89C5, //CJK UNIFIED IDEOGRAPH - 0xC3DA: 0x6CCC, //CJK UNIFIED IDEOGRAPH - 0xC3DB: 0x871C, //CJK UNIFIED IDEOGRAPH - 0xC3DC: 0x5BC6, //CJK UNIFIED IDEOGRAPH - 0xC3DD: 0x5E42, //CJK UNIFIED IDEOGRAPH - 0xC3DE: 0x68C9, //CJK UNIFIED IDEOGRAPH - 0xC3DF: 0x7720, //CJK UNIFIED IDEOGRAPH - 0xC3E0: 0x7EF5, //CJK UNIFIED IDEOGRAPH - 0xC3E1: 0x5195, //CJK UNIFIED IDEOGRAPH - 0xC3E2: 0x514D, //CJK UNIFIED IDEOGRAPH - 0xC3E3: 0x52C9, //CJK UNIFIED IDEOGRAPH - 0xC3E4: 0x5A29, //CJK UNIFIED IDEOGRAPH - 0xC3E5: 0x7F05, //CJK UNIFIED IDEOGRAPH - 0xC3E6: 0x9762, //CJK UNIFIED IDEOGRAPH - 0xC3E7: 0x82D7, //CJK UNIFIED IDEOGRAPH - 0xC3E8: 0x63CF, //CJK UNIFIED IDEOGRAPH - 0xC3E9: 0x7784, //CJK UNIFIED IDEOGRAPH - 0xC3EA: 0x85D0, //CJK UNIFIED IDEOGRAPH - 0xC3EB: 0x79D2, //CJK UNIFIED IDEOGRAPH - 0xC3EC: 0x6E3A, //CJK UNIFIED IDEOGRAPH - 0xC3ED: 0x5E99, //CJK UNIFIED IDEOGRAPH - 0xC3EE: 0x5999, //CJK UNIFIED IDEOGRAPH - 0xC3EF: 0x8511, //CJK UNIFIED IDEOGRAPH - 0xC3F0: 0x706D, //CJK UNIFIED IDEOGRAPH - 0xC3F1: 0x6C11, //CJK UNIFIED IDEOGRAPH - 0xC3F2: 0x62BF, //CJK UNIFIED IDEOGRAPH - 0xC3F3: 0x76BF, //CJK UNIFIED IDEOGRAPH - 0xC3F4: 0x654F, //CJK UNIFIED IDEOGRAPH - 0xC3F5: 0x60AF, //CJK UNIFIED IDEOGRAPH - 0xC3F6: 0x95FD, //CJK UNIFIED IDEOGRAPH - 0xC3F7: 0x660E, //CJK UNIFIED IDEOGRAPH - 0xC3F8: 0x879F, //CJK UNIFIED IDEOGRAPH - 0xC3F9: 0x9E23, //CJK UNIFIED IDEOGRAPH - 0xC3FA: 0x94ED, //CJK UNIFIED IDEOGRAPH - 0xC3FB: 0x540D, //CJK UNIFIED IDEOGRAPH - 0xC3FC: 0x547D, //CJK UNIFIED IDEOGRAPH - 0xC3FD: 0x8C2C, //CJK UNIFIED IDEOGRAPH - 0xC3FE: 0x6478, //CJK UNIFIED IDEOGRAPH - 0xC440: 0x8140, //CJK UNIFIED IDEOGRAPH - 0xC441: 0x8141, //CJK UNIFIED IDEOGRAPH - 0xC442: 0x8142, //CJK UNIFIED IDEOGRAPH - 0xC443: 0x8143, //CJK UNIFIED IDEOGRAPH - 0xC444: 0x8144, //CJK UNIFIED IDEOGRAPH - 0xC445: 0x8145, //CJK UNIFIED IDEOGRAPH - 0xC446: 0x8147, //CJK UNIFIED IDEOGRAPH - 0xC447: 0x8149, //CJK UNIFIED IDEOGRAPH - 0xC448: 0x814D, //CJK UNIFIED IDEOGRAPH - 0xC449: 0x814E, //CJK UNIFIED IDEOGRAPH - 0xC44A: 0x814F, //CJK UNIFIED IDEOGRAPH - 0xC44B: 0x8152, //CJK UNIFIED IDEOGRAPH - 0xC44C: 0x8156, //CJK UNIFIED IDEOGRAPH - 0xC44D: 0x8157, //CJK UNIFIED IDEOGRAPH - 0xC44E: 0x8158, //CJK UNIFIED IDEOGRAPH - 0xC44F: 0x815B, //CJK UNIFIED IDEOGRAPH - 0xC450: 0x815C, //CJK UNIFIED IDEOGRAPH - 0xC451: 0x815D, //CJK UNIFIED IDEOGRAPH - 0xC452: 0x815E, //CJK UNIFIED IDEOGRAPH - 0xC453: 0x815F, //CJK UNIFIED IDEOGRAPH - 0xC454: 0x8161, //CJK UNIFIED IDEOGRAPH - 0xC455: 0x8162, //CJK UNIFIED IDEOGRAPH - 0xC456: 0x8163, //CJK UNIFIED IDEOGRAPH - 0xC457: 0x8164, //CJK UNIFIED IDEOGRAPH - 0xC458: 0x8166, //CJK UNIFIED IDEOGRAPH - 0xC459: 0x8168, //CJK UNIFIED IDEOGRAPH - 0xC45A: 0x816A, //CJK UNIFIED IDEOGRAPH - 0xC45B: 0x816B, //CJK UNIFIED IDEOGRAPH - 0xC45C: 0x816C, //CJK UNIFIED IDEOGRAPH - 0xC45D: 0x816F, //CJK UNIFIED IDEOGRAPH - 0xC45E: 0x8172, //CJK UNIFIED IDEOGRAPH - 0xC45F: 0x8173, //CJK UNIFIED IDEOGRAPH - 0xC460: 0x8175, //CJK UNIFIED IDEOGRAPH - 0xC461: 0x8176, //CJK UNIFIED IDEOGRAPH - 0xC462: 0x8177, //CJK UNIFIED IDEOGRAPH - 0xC463: 0x8178, //CJK UNIFIED IDEOGRAPH - 0xC464: 0x8181, //CJK UNIFIED IDEOGRAPH - 0xC465: 0x8183, //CJK UNIFIED IDEOGRAPH - 0xC466: 0x8184, //CJK UNIFIED IDEOGRAPH - 0xC467: 0x8185, //CJK UNIFIED IDEOGRAPH - 0xC468: 0x8186, //CJK UNIFIED IDEOGRAPH - 0xC469: 0x8187, //CJK UNIFIED IDEOGRAPH - 0xC46A: 0x8189, //CJK UNIFIED IDEOGRAPH - 0xC46B: 0x818B, //CJK UNIFIED IDEOGRAPH - 0xC46C: 0x818C, //CJK UNIFIED IDEOGRAPH - 0xC46D: 0x818D, //CJK UNIFIED IDEOGRAPH - 0xC46E: 0x818E, //CJK UNIFIED IDEOGRAPH - 0xC46F: 0x8190, //CJK UNIFIED IDEOGRAPH - 0xC470: 0x8192, //CJK UNIFIED IDEOGRAPH - 0xC471: 0x8193, //CJK UNIFIED IDEOGRAPH - 0xC472: 0x8194, //CJK UNIFIED IDEOGRAPH - 0xC473: 0x8195, //CJK UNIFIED IDEOGRAPH - 0xC474: 0x8196, //CJK UNIFIED IDEOGRAPH - 0xC475: 0x8197, //CJK UNIFIED IDEOGRAPH - 0xC476: 0x8199, //CJK UNIFIED IDEOGRAPH - 0xC477: 0x819A, //CJK UNIFIED IDEOGRAPH - 0xC478: 0x819E, //CJK UNIFIED IDEOGRAPH - 0xC479: 0x819F, //CJK UNIFIED IDEOGRAPH - 0xC47A: 0x81A0, //CJK UNIFIED IDEOGRAPH - 0xC47B: 0x81A1, //CJK UNIFIED IDEOGRAPH - 0xC47C: 0x81A2, //CJK UNIFIED IDEOGRAPH - 0xC47D: 0x81A4, //CJK UNIFIED IDEOGRAPH - 0xC47E: 0x81A5, //CJK UNIFIED IDEOGRAPH - 0xC480: 0x81A7, //CJK UNIFIED IDEOGRAPH - 0xC481: 0x81A9, //CJK UNIFIED IDEOGRAPH - 0xC482: 0x81AB, //CJK UNIFIED IDEOGRAPH - 0xC483: 0x81AC, //CJK UNIFIED IDEOGRAPH - 0xC484: 0x81AD, //CJK UNIFIED IDEOGRAPH - 0xC485: 0x81AE, //CJK UNIFIED IDEOGRAPH - 0xC486: 0x81AF, //CJK UNIFIED IDEOGRAPH - 0xC487: 0x81B0, //CJK UNIFIED IDEOGRAPH - 0xC488: 0x81B1, //CJK UNIFIED IDEOGRAPH - 0xC489: 0x81B2, //CJK UNIFIED IDEOGRAPH - 0xC48A: 0x81B4, //CJK UNIFIED IDEOGRAPH - 0xC48B: 0x81B5, //CJK UNIFIED IDEOGRAPH - 0xC48C: 0x81B6, //CJK UNIFIED IDEOGRAPH - 0xC48D: 0x81B7, //CJK UNIFIED IDEOGRAPH - 0xC48E: 0x81B8, //CJK UNIFIED IDEOGRAPH - 0xC48F: 0x81B9, //CJK UNIFIED IDEOGRAPH - 0xC490: 0x81BC, //CJK UNIFIED IDEOGRAPH - 0xC491: 0x81BD, //CJK UNIFIED IDEOGRAPH - 0xC492: 0x81BE, //CJK UNIFIED IDEOGRAPH - 0xC493: 0x81BF, //CJK UNIFIED IDEOGRAPH - 0xC494: 0x81C4, //CJK UNIFIED IDEOGRAPH - 0xC495: 0x81C5, //CJK UNIFIED IDEOGRAPH - 0xC496: 0x81C7, //CJK UNIFIED IDEOGRAPH - 0xC497: 0x81C8, //CJK UNIFIED IDEOGRAPH - 0xC498: 0x81C9, //CJK UNIFIED IDEOGRAPH - 0xC499: 0x81CB, //CJK UNIFIED IDEOGRAPH - 0xC49A: 0x81CD, //CJK UNIFIED IDEOGRAPH - 0xC49B: 0x81CE, //CJK UNIFIED IDEOGRAPH - 0xC49C: 0x81CF, //CJK UNIFIED IDEOGRAPH - 0xC49D: 0x81D0, //CJK UNIFIED IDEOGRAPH - 0xC49E: 0x81D1, //CJK UNIFIED IDEOGRAPH - 0xC49F: 0x81D2, //CJK UNIFIED IDEOGRAPH - 0xC4A0: 0x81D3, //CJK UNIFIED IDEOGRAPH - 0xC4A1: 0x6479, //CJK UNIFIED IDEOGRAPH - 0xC4A2: 0x8611, //CJK UNIFIED IDEOGRAPH - 0xC4A3: 0x6A21, //CJK UNIFIED IDEOGRAPH - 0xC4A4: 0x819C, //CJK UNIFIED IDEOGRAPH - 0xC4A5: 0x78E8, //CJK UNIFIED IDEOGRAPH - 0xC4A6: 0x6469, //CJK UNIFIED IDEOGRAPH - 0xC4A7: 0x9B54, //CJK UNIFIED IDEOGRAPH - 0xC4A8: 0x62B9, //CJK UNIFIED IDEOGRAPH - 0xC4A9: 0x672B, //CJK UNIFIED IDEOGRAPH - 0xC4AA: 0x83AB, //CJK UNIFIED IDEOGRAPH - 0xC4AB: 0x58A8, //CJK UNIFIED IDEOGRAPH - 0xC4AC: 0x9ED8, //CJK UNIFIED IDEOGRAPH - 0xC4AD: 0x6CAB, //CJK UNIFIED IDEOGRAPH - 0xC4AE: 0x6F20, //CJK UNIFIED IDEOGRAPH - 0xC4AF: 0x5BDE, //CJK UNIFIED IDEOGRAPH - 0xC4B0: 0x964C, //CJK UNIFIED IDEOGRAPH - 0xC4B1: 0x8C0B, //CJK UNIFIED IDEOGRAPH - 0xC4B2: 0x725F, //CJK UNIFIED IDEOGRAPH - 0xC4B3: 0x67D0, //CJK UNIFIED IDEOGRAPH - 0xC4B4: 0x62C7, //CJK UNIFIED IDEOGRAPH - 0xC4B5: 0x7261, //CJK UNIFIED IDEOGRAPH - 0xC4B6: 0x4EA9, //CJK UNIFIED IDEOGRAPH - 0xC4B7: 0x59C6, //CJK UNIFIED IDEOGRAPH - 0xC4B8: 0x6BCD, //CJK UNIFIED IDEOGRAPH - 0xC4B9: 0x5893, //CJK UNIFIED IDEOGRAPH - 0xC4BA: 0x66AE, //CJK UNIFIED IDEOGRAPH - 0xC4BB: 0x5E55, //CJK UNIFIED IDEOGRAPH - 0xC4BC: 0x52DF, //CJK UNIFIED IDEOGRAPH - 0xC4BD: 0x6155, //CJK UNIFIED IDEOGRAPH - 0xC4BE: 0x6728, //CJK UNIFIED IDEOGRAPH - 0xC4BF: 0x76EE, //CJK UNIFIED IDEOGRAPH - 0xC4C0: 0x7766, //CJK UNIFIED IDEOGRAPH - 0xC4C1: 0x7267, //CJK UNIFIED IDEOGRAPH - 0xC4C2: 0x7A46, //CJK UNIFIED IDEOGRAPH - 0xC4C3: 0x62FF, //CJK UNIFIED IDEOGRAPH - 0xC4C4: 0x54EA, //CJK UNIFIED IDEOGRAPH - 0xC4C5: 0x5450, //CJK UNIFIED IDEOGRAPH - 0xC4C6: 0x94A0, //CJK UNIFIED IDEOGRAPH - 0xC4C7: 0x90A3, //CJK UNIFIED IDEOGRAPH - 0xC4C8: 0x5A1C, //CJK UNIFIED IDEOGRAPH - 0xC4C9: 0x7EB3, //CJK UNIFIED IDEOGRAPH - 0xC4CA: 0x6C16, //CJK UNIFIED IDEOGRAPH - 0xC4CB: 0x4E43, //CJK UNIFIED IDEOGRAPH - 0xC4CC: 0x5976, //CJK UNIFIED IDEOGRAPH - 0xC4CD: 0x8010, //CJK UNIFIED IDEOGRAPH - 0xC4CE: 0x5948, //CJK UNIFIED IDEOGRAPH - 0xC4CF: 0x5357, //CJK UNIFIED IDEOGRAPH - 0xC4D0: 0x7537, //CJK UNIFIED IDEOGRAPH - 0xC4D1: 0x96BE, //CJK UNIFIED IDEOGRAPH - 0xC4D2: 0x56CA, //CJK UNIFIED IDEOGRAPH - 0xC4D3: 0x6320, //CJK UNIFIED IDEOGRAPH - 0xC4D4: 0x8111, //CJK UNIFIED IDEOGRAPH - 0xC4D5: 0x607C, //CJK UNIFIED IDEOGRAPH - 0xC4D6: 0x95F9, //CJK UNIFIED IDEOGRAPH - 0xC4D7: 0x6DD6, //CJK UNIFIED IDEOGRAPH - 0xC4D8: 0x5462, //CJK UNIFIED IDEOGRAPH - 0xC4D9: 0x9981, //CJK UNIFIED IDEOGRAPH - 0xC4DA: 0x5185, //CJK UNIFIED IDEOGRAPH - 0xC4DB: 0x5AE9, //CJK UNIFIED IDEOGRAPH - 0xC4DC: 0x80FD, //CJK UNIFIED IDEOGRAPH - 0xC4DD: 0x59AE, //CJK UNIFIED IDEOGRAPH - 0xC4DE: 0x9713, //CJK UNIFIED IDEOGRAPH - 0xC4DF: 0x502A, //CJK UNIFIED IDEOGRAPH - 0xC4E0: 0x6CE5, //CJK UNIFIED IDEOGRAPH - 0xC4E1: 0x5C3C, //CJK UNIFIED IDEOGRAPH - 0xC4E2: 0x62DF, //CJK UNIFIED IDEOGRAPH - 0xC4E3: 0x4F60, //CJK UNIFIED IDEOGRAPH - 0xC4E4: 0x533F, //CJK UNIFIED IDEOGRAPH - 0xC4E5: 0x817B, //CJK UNIFIED IDEOGRAPH - 0xC4E6: 0x9006, //CJK UNIFIED IDEOGRAPH - 0xC4E7: 0x6EBA, //CJK UNIFIED IDEOGRAPH - 0xC4E8: 0x852B, //CJK UNIFIED IDEOGRAPH - 0xC4E9: 0x62C8, //CJK UNIFIED IDEOGRAPH - 0xC4EA: 0x5E74, //CJK UNIFIED IDEOGRAPH - 0xC4EB: 0x78BE, //CJK UNIFIED IDEOGRAPH - 0xC4EC: 0x64B5, //CJK UNIFIED IDEOGRAPH - 0xC4ED: 0x637B, //CJK UNIFIED IDEOGRAPH - 0xC4EE: 0x5FF5, //CJK UNIFIED IDEOGRAPH - 0xC4EF: 0x5A18, //CJK UNIFIED IDEOGRAPH - 0xC4F0: 0x917F, //CJK UNIFIED IDEOGRAPH - 0xC4F1: 0x9E1F, //CJK UNIFIED IDEOGRAPH - 0xC4F2: 0x5C3F, //CJK UNIFIED IDEOGRAPH - 0xC4F3: 0x634F, //CJK UNIFIED IDEOGRAPH - 0xC4F4: 0x8042, //CJK UNIFIED IDEOGRAPH - 0xC4F5: 0x5B7D, //CJK UNIFIED IDEOGRAPH - 0xC4F6: 0x556E, //CJK UNIFIED IDEOGRAPH - 0xC4F7: 0x954A, //CJK UNIFIED IDEOGRAPH - 0xC4F8: 0x954D, //CJK UNIFIED IDEOGRAPH - 0xC4F9: 0x6D85, //CJK UNIFIED IDEOGRAPH - 0xC4FA: 0x60A8, //CJK UNIFIED IDEOGRAPH - 0xC4FB: 0x67E0, //CJK UNIFIED IDEOGRAPH - 0xC4FC: 0x72DE, //CJK UNIFIED IDEOGRAPH - 0xC4FD: 0x51DD, //CJK UNIFIED IDEOGRAPH - 0xC4FE: 0x5B81, //CJK UNIFIED IDEOGRAPH - 0xC540: 0x81D4, //CJK UNIFIED IDEOGRAPH - 0xC541: 0x81D5, //CJK UNIFIED IDEOGRAPH - 0xC542: 0x81D6, //CJK UNIFIED IDEOGRAPH - 0xC543: 0x81D7, //CJK UNIFIED IDEOGRAPH - 0xC544: 0x81D8, //CJK UNIFIED IDEOGRAPH - 0xC545: 0x81D9, //CJK UNIFIED IDEOGRAPH - 0xC546: 0x81DA, //CJK UNIFIED IDEOGRAPH - 0xC547: 0x81DB, //CJK UNIFIED IDEOGRAPH - 0xC548: 0x81DC, //CJK UNIFIED IDEOGRAPH - 0xC549: 0x81DD, //CJK UNIFIED IDEOGRAPH - 0xC54A: 0x81DE, //CJK UNIFIED IDEOGRAPH - 0xC54B: 0x81DF, //CJK UNIFIED IDEOGRAPH - 0xC54C: 0x81E0, //CJK UNIFIED IDEOGRAPH - 0xC54D: 0x81E1, //CJK UNIFIED IDEOGRAPH - 0xC54E: 0x81E2, //CJK UNIFIED IDEOGRAPH - 0xC54F: 0x81E4, //CJK UNIFIED IDEOGRAPH - 0xC550: 0x81E5, //CJK UNIFIED IDEOGRAPH - 0xC551: 0x81E6, //CJK UNIFIED IDEOGRAPH - 0xC552: 0x81E8, //CJK UNIFIED IDEOGRAPH - 0xC553: 0x81E9, //CJK UNIFIED IDEOGRAPH - 0xC554: 0x81EB, //CJK UNIFIED IDEOGRAPH - 0xC555: 0x81EE, //CJK UNIFIED IDEOGRAPH - 0xC556: 0x81EF, //CJK UNIFIED IDEOGRAPH - 0xC557: 0x81F0, //CJK UNIFIED IDEOGRAPH - 0xC558: 0x81F1, //CJK UNIFIED IDEOGRAPH - 0xC559: 0x81F2, //CJK UNIFIED IDEOGRAPH - 0xC55A: 0x81F5, //CJK UNIFIED IDEOGRAPH - 0xC55B: 0x81F6, //CJK UNIFIED IDEOGRAPH - 0xC55C: 0x81F7, //CJK UNIFIED IDEOGRAPH - 0xC55D: 0x81F8, //CJK UNIFIED IDEOGRAPH - 0xC55E: 0x81F9, //CJK UNIFIED IDEOGRAPH - 0xC55F: 0x81FA, //CJK UNIFIED IDEOGRAPH - 0xC560: 0x81FD, //CJK UNIFIED IDEOGRAPH - 0xC561: 0x81FF, //CJK UNIFIED IDEOGRAPH - 0xC562: 0x8203, //CJK UNIFIED IDEOGRAPH - 0xC563: 0x8207, //CJK UNIFIED IDEOGRAPH - 0xC564: 0x8208, //CJK UNIFIED IDEOGRAPH - 0xC565: 0x8209, //CJK UNIFIED IDEOGRAPH - 0xC566: 0x820A, //CJK UNIFIED IDEOGRAPH - 0xC567: 0x820B, //CJK UNIFIED IDEOGRAPH - 0xC568: 0x820E, //CJK UNIFIED IDEOGRAPH - 0xC569: 0x820F, //CJK UNIFIED IDEOGRAPH - 0xC56A: 0x8211, //CJK UNIFIED IDEOGRAPH - 0xC56B: 0x8213, //CJK UNIFIED IDEOGRAPH - 0xC56C: 0x8215, //CJK UNIFIED IDEOGRAPH - 0xC56D: 0x8216, //CJK UNIFIED IDEOGRAPH - 0xC56E: 0x8217, //CJK UNIFIED IDEOGRAPH - 0xC56F: 0x8218, //CJK UNIFIED IDEOGRAPH - 0xC570: 0x8219, //CJK UNIFIED IDEOGRAPH - 0xC571: 0x821A, //CJK UNIFIED IDEOGRAPH - 0xC572: 0x821D, //CJK UNIFIED IDEOGRAPH - 0xC573: 0x8220, //CJK UNIFIED IDEOGRAPH - 0xC574: 0x8224, //CJK UNIFIED IDEOGRAPH - 0xC575: 0x8225, //CJK UNIFIED IDEOGRAPH - 0xC576: 0x8226, //CJK UNIFIED IDEOGRAPH - 0xC577: 0x8227, //CJK UNIFIED IDEOGRAPH - 0xC578: 0x8229, //CJK UNIFIED IDEOGRAPH - 0xC579: 0x822E, //CJK UNIFIED IDEOGRAPH - 0xC57A: 0x8232, //CJK UNIFIED IDEOGRAPH - 0xC57B: 0x823A, //CJK UNIFIED IDEOGRAPH - 0xC57C: 0x823C, //CJK UNIFIED IDEOGRAPH - 0xC57D: 0x823D, //CJK UNIFIED IDEOGRAPH - 0xC57E: 0x823F, //CJK UNIFIED IDEOGRAPH - 0xC580: 0x8240, //CJK UNIFIED IDEOGRAPH - 0xC581: 0x8241, //CJK UNIFIED IDEOGRAPH - 0xC582: 0x8242, //CJK UNIFIED IDEOGRAPH - 0xC583: 0x8243, //CJK UNIFIED IDEOGRAPH - 0xC584: 0x8245, //CJK UNIFIED IDEOGRAPH - 0xC585: 0x8246, //CJK UNIFIED IDEOGRAPH - 0xC586: 0x8248, //CJK UNIFIED IDEOGRAPH - 0xC587: 0x824A, //CJK UNIFIED IDEOGRAPH - 0xC588: 0x824C, //CJK UNIFIED IDEOGRAPH - 0xC589: 0x824D, //CJK UNIFIED IDEOGRAPH - 0xC58A: 0x824E, //CJK UNIFIED IDEOGRAPH - 0xC58B: 0x8250, //CJK UNIFIED IDEOGRAPH - 0xC58C: 0x8251, //CJK UNIFIED IDEOGRAPH - 0xC58D: 0x8252, //CJK UNIFIED IDEOGRAPH - 0xC58E: 0x8253, //CJK UNIFIED IDEOGRAPH - 0xC58F: 0x8254, //CJK UNIFIED IDEOGRAPH - 0xC590: 0x8255, //CJK UNIFIED IDEOGRAPH - 0xC591: 0x8256, //CJK UNIFIED IDEOGRAPH - 0xC592: 0x8257, //CJK UNIFIED IDEOGRAPH - 0xC593: 0x8259, //CJK UNIFIED IDEOGRAPH - 0xC594: 0x825B, //CJK UNIFIED IDEOGRAPH - 0xC595: 0x825C, //CJK UNIFIED IDEOGRAPH - 0xC596: 0x825D, //CJK UNIFIED IDEOGRAPH - 0xC597: 0x825E, //CJK UNIFIED IDEOGRAPH - 0xC598: 0x8260, //CJK UNIFIED IDEOGRAPH - 0xC599: 0x8261, //CJK UNIFIED IDEOGRAPH - 0xC59A: 0x8262, //CJK UNIFIED IDEOGRAPH - 0xC59B: 0x8263, //CJK UNIFIED IDEOGRAPH - 0xC59C: 0x8264, //CJK UNIFIED IDEOGRAPH - 0xC59D: 0x8265, //CJK UNIFIED IDEOGRAPH - 0xC59E: 0x8266, //CJK UNIFIED IDEOGRAPH - 0xC59F: 0x8267, //CJK UNIFIED IDEOGRAPH - 0xC5A0: 0x8269, //CJK UNIFIED IDEOGRAPH - 0xC5A1: 0x62E7, //CJK UNIFIED IDEOGRAPH - 0xC5A2: 0x6CDE, //CJK UNIFIED IDEOGRAPH - 0xC5A3: 0x725B, //CJK UNIFIED IDEOGRAPH - 0xC5A4: 0x626D, //CJK UNIFIED IDEOGRAPH - 0xC5A5: 0x94AE, //CJK UNIFIED IDEOGRAPH - 0xC5A6: 0x7EBD, //CJK UNIFIED IDEOGRAPH - 0xC5A7: 0x8113, //CJK UNIFIED IDEOGRAPH - 0xC5A8: 0x6D53, //CJK UNIFIED IDEOGRAPH - 0xC5A9: 0x519C, //CJK UNIFIED IDEOGRAPH - 0xC5AA: 0x5F04, //CJK UNIFIED IDEOGRAPH - 0xC5AB: 0x5974, //CJK UNIFIED IDEOGRAPH - 0xC5AC: 0x52AA, //CJK UNIFIED IDEOGRAPH - 0xC5AD: 0x6012, //CJK UNIFIED IDEOGRAPH - 0xC5AE: 0x5973, //CJK UNIFIED IDEOGRAPH - 0xC5AF: 0x6696, //CJK UNIFIED IDEOGRAPH - 0xC5B0: 0x8650, //CJK UNIFIED IDEOGRAPH - 0xC5B1: 0x759F, //CJK UNIFIED IDEOGRAPH - 0xC5B2: 0x632A, //CJK UNIFIED IDEOGRAPH - 0xC5B3: 0x61E6, //CJK UNIFIED IDEOGRAPH - 0xC5B4: 0x7CEF, //CJK UNIFIED IDEOGRAPH - 0xC5B5: 0x8BFA, //CJK UNIFIED IDEOGRAPH - 0xC5B6: 0x54E6, //CJK UNIFIED IDEOGRAPH - 0xC5B7: 0x6B27, //CJK UNIFIED IDEOGRAPH - 0xC5B8: 0x9E25, //CJK UNIFIED IDEOGRAPH - 0xC5B9: 0x6BB4, //CJK UNIFIED IDEOGRAPH - 0xC5BA: 0x85D5, //CJK UNIFIED IDEOGRAPH - 0xC5BB: 0x5455, //CJK UNIFIED IDEOGRAPH - 0xC5BC: 0x5076, //CJK UNIFIED IDEOGRAPH - 0xC5BD: 0x6CA4, //CJK UNIFIED IDEOGRAPH - 0xC5BE: 0x556A, //CJK UNIFIED IDEOGRAPH - 0xC5BF: 0x8DB4, //CJK UNIFIED IDEOGRAPH - 0xC5C0: 0x722C, //CJK UNIFIED IDEOGRAPH - 0xC5C1: 0x5E15, //CJK UNIFIED IDEOGRAPH - 0xC5C2: 0x6015, //CJK UNIFIED IDEOGRAPH - 0xC5C3: 0x7436, //CJK UNIFIED IDEOGRAPH - 0xC5C4: 0x62CD, //CJK UNIFIED IDEOGRAPH - 0xC5C5: 0x6392, //CJK UNIFIED IDEOGRAPH - 0xC5C6: 0x724C, //CJK UNIFIED IDEOGRAPH - 0xC5C7: 0x5F98, //CJK UNIFIED IDEOGRAPH - 0xC5C8: 0x6E43, //CJK UNIFIED IDEOGRAPH - 0xC5C9: 0x6D3E, //CJK UNIFIED IDEOGRAPH - 0xC5CA: 0x6500, //CJK UNIFIED IDEOGRAPH - 0xC5CB: 0x6F58, //CJK UNIFIED IDEOGRAPH - 0xC5CC: 0x76D8, //CJK UNIFIED IDEOGRAPH - 0xC5CD: 0x78D0, //CJK UNIFIED IDEOGRAPH - 0xC5CE: 0x76FC, //CJK UNIFIED IDEOGRAPH - 0xC5CF: 0x7554, //CJK UNIFIED IDEOGRAPH - 0xC5D0: 0x5224, //CJK UNIFIED IDEOGRAPH - 0xC5D1: 0x53DB, //CJK UNIFIED IDEOGRAPH - 0xC5D2: 0x4E53, //CJK UNIFIED IDEOGRAPH - 0xC5D3: 0x5E9E, //CJK UNIFIED IDEOGRAPH - 0xC5D4: 0x65C1, //CJK UNIFIED IDEOGRAPH - 0xC5D5: 0x802A, //CJK UNIFIED IDEOGRAPH - 0xC5D6: 0x80D6, //CJK UNIFIED IDEOGRAPH - 0xC5D7: 0x629B, //CJK UNIFIED IDEOGRAPH - 0xC5D8: 0x5486, //CJK UNIFIED IDEOGRAPH - 0xC5D9: 0x5228, //CJK UNIFIED IDEOGRAPH - 0xC5DA: 0x70AE, //CJK UNIFIED IDEOGRAPH - 0xC5DB: 0x888D, //CJK UNIFIED IDEOGRAPH - 0xC5DC: 0x8DD1, //CJK UNIFIED IDEOGRAPH - 0xC5DD: 0x6CE1, //CJK UNIFIED IDEOGRAPH - 0xC5DE: 0x5478, //CJK UNIFIED IDEOGRAPH - 0xC5DF: 0x80DA, //CJK UNIFIED IDEOGRAPH - 0xC5E0: 0x57F9, //CJK UNIFIED IDEOGRAPH - 0xC5E1: 0x88F4, //CJK UNIFIED IDEOGRAPH - 0xC5E2: 0x8D54, //CJK UNIFIED IDEOGRAPH - 0xC5E3: 0x966A, //CJK UNIFIED IDEOGRAPH - 0xC5E4: 0x914D, //CJK UNIFIED IDEOGRAPH - 0xC5E5: 0x4F69, //CJK UNIFIED IDEOGRAPH - 0xC5E6: 0x6C9B, //CJK UNIFIED IDEOGRAPH - 0xC5E7: 0x55B7, //CJK UNIFIED IDEOGRAPH - 0xC5E8: 0x76C6, //CJK UNIFIED IDEOGRAPH - 0xC5E9: 0x7830, //CJK UNIFIED IDEOGRAPH - 0xC5EA: 0x62A8, //CJK UNIFIED IDEOGRAPH - 0xC5EB: 0x70F9, //CJK UNIFIED IDEOGRAPH - 0xC5EC: 0x6F8E, //CJK UNIFIED IDEOGRAPH - 0xC5ED: 0x5F6D, //CJK UNIFIED IDEOGRAPH - 0xC5EE: 0x84EC, //CJK UNIFIED IDEOGRAPH - 0xC5EF: 0x68DA, //CJK UNIFIED IDEOGRAPH - 0xC5F0: 0x787C, //CJK UNIFIED IDEOGRAPH - 0xC5F1: 0x7BF7, //CJK UNIFIED IDEOGRAPH - 0xC5F2: 0x81A8, //CJK UNIFIED IDEOGRAPH - 0xC5F3: 0x670B, //CJK UNIFIED IDEOGRAPH - 0xC5F4: 0x9E4F, //CJK UNIFIED IDEOGRAPH - 0xC5F5: 0x6367, //CJK UNIFIED IDEOGRAPH - 0xC5F6: 0x78B0, //CJK UNIFIED IDEOGRAPH - 0xC5F7: 0x576F, //CJK UNIFIED IDEOGRAPH - 0xC5F8: 0x7812, //CJK UNIFIED IDEOGRAPH - 0xC5F9: 0x9739, //CJK UNIFIED IDEOGRAPH - 0xC5FA: 0x6279, //CJK UNIFIED IDEOGRAPH - 0xC5FB: 0x62AB, //CJK UNIFIED IDEOGRAPH - 0xC5FC: 0x5288, //CJK UNIFIED IDEOGRAPH - 0xC5FD: 0x7435, //CJK UNIFIED IDEOGRAPH - 0xC5FE: 0x6BD7, //CJK UNIFIED IDEOGRAPH - 0xC640: 0x826A, //CJK UNIFIED IDEOGRAPH - 0xC641: 0x826B, //CJK UNIFIED IDEOGRAPH - 0xC642: 0x826C, //CJK UNIFIED IDEOGRAPH - 0xC643: 0x826D, //CJK UNIFIED IDEOGRAPH - 0xC644: 0x8271, //CJK UNIFIED IDEOGRAPH - 0xC645: 0x8275, //CJK UNIFIED IDEOGRAPH - 0xC646: 0x8276, //CJK UNIFIED IDEOGRAPH - 0xC647: 0x8277, //CJK UNIFIED IDEOGRAPH - 0xC648: 0x8278, //CJK UNIFIED IDEOGRAPH - 0xC649: 0x827B, //CJK UNIFIED IDEOGRAPH - 0xC64A: 0x827C, //CJK UNIFIED IDEOGRAPH - 0xC64B: 0x8280, //CJK UNIFIED IDEOGRAPH - 0xC64C: 0x8281, //CJK UNIFIED IDEOGRAPH - 0xC64D: 0x8283, //CJK UNIFIED IDEOGRAPH - 0xC64E: 0x8285, //CJK UNIFIED IDEOGRAPH - 0xC64F: 0x8286, //CJK UNIFIED IDEOGRAPH - 0xC650: 0x8287, //CJK UNIFIED IDEOGRAPH - 0xC651: 0x8289, //CJK UNIFIED IDEOGRAPH - 0xC652: 0x828C, //CJK UNIFIED IDEOGRAPH - 0xC653: 0x8290, //CJK UNIFIED IDEOGRAPH - 0xC654: 0x8293, //CJK UNIFIED IDEOGRAPH - 0xC655: 0x8294, //CJK UNIFIED IDEOGRAPH - 0xC656: 0x8295, //CJK UNIFIED IDEOGRAPH - 0xC657: 0x8296, //CJK UNIFIED IDEOGRAPH - 0xC658: 0x829A, //CJK UNIFIED IDEOGRAPH - 0xC659: 0x829B, //CJK UNIFIED IDEOGRAPH - 0xC65A: 0x829E, //CJK UNIFIED IDEOGRAPH - 0xC65B: 0x82A0, //CJK UNIFIED IDEOGRAPH - 0xC65C: 0x82A2, //CJK UNIFIED IDEOGRAPH - 0xC65D: 0x82A3, //CJK UNIFIED IDEOGRAPH - 0xC65E: 0x82A7, //CJK UNIFIED IDEOGRAPH - 0xC65F: 0x82B2, //CJK UNIFIED IDEOGRAPH - 0xC660: 0x82B5, //CJK UNIFIED IDEOGRAPH - 0xC661: 0x82B6, //CJK UNIFIED IDEOGRAPH - 0xC662: 0x82BA, //CJK UNIFIED IDEOGRAPH - 0xC663: 0x82BB, //CJK UNIFIED IDEOGRAPH - 0xC664: 0x82BC, //CJK UNIFIED IDEOGRAPH - 0xC665: 0x82BF, //CJK UNIFIED IDEOGRAPH - 0xC666: 0x82C0, //CJK UNIFIED IDEOGRAPH - 0xC667: 0x82C2, //CJK UNIFIED IDEOGRAPH - 0xC668: 0x82C3, //CJK UNIFIED IDEOGRAPH - 0xC669: 0x82C5, //CJK UNIFIED IDEOGRAPH - 0xC66A: 0x82C6, //CJK UNIFIED IDEOGRAPH - 0xC66B: 0x82C9, //CJK UNIFIED IDEOGRAPH - 0xC66C: 0x82D0, //CJK UNIFIED IDEOGRAPH - 0xC66D: 0x82D6, //CJK UNIFIED IDEOGRAPH - 0xC66E: 0x82D9, //CJK UNIFIED IDEOGRAPH - 0xC66F: 0x82DA, //CJK UNIFIED IDEOGRAPH - 0xC670: 0x82DD, //CJK UNIFIED IDEOGRAPH - 0xC671: 0x82E2, //CJK UNIFIED IDEOGRAPH - 0xC672: 0x82E7, //CJK UNIFIED IDEOGRAPH - 0xC673: 0x82E8, //CJK UNIFIED IDEOGRAPH - 0xC674: 0x82E9, //CJK UNIFIED IDEOGRAPH - 0xC675: 0x82EA, //CJK UNIFIED IDEOGRAPH - 0xC676: 0x82EC, //CJK UNIFIED IDEOGRAPH - 0xC677: 0x82ED, //CJK UNIFIED IDEOGRAPH - 0xC678: 0x82EE, //CJK UNIFIED IDEOGRAPH - 0xC679: 0x82F0, //CJK UNIFIED IDEOGRAPH - 0xC67A: 0x82F2, //CJK UNIFIED IDEOGRAPH - 0xC67B: 0x82F3, //CJK UNIFIED IDEOGRAPH - 0xC67C: 0x82F5, //CJK UNIFIED IDEOGRAPH - 0xC67D: 0x82F6, //CJK UNIFIED IDEOGRAPH - 0xC67E: 0x82F8, //CJK UNIFIED IDEOGRAPH - 0xC680: 0x82FA, //CJK UNIFIED IDEOGRAPH - 0xC681: 0x82FC, //CJK UNIFIED IDEOGRAPH - 0xC682: 0x82FD, //CJK UNIFIED IDEOGRAPH - 0xC683: 0x82FE, //CJK UNIFIED IDEOGRAPH - 0xC684: 0x82FF, //CJK UNIFIED IDEOGRAPH - 0xC685: 0x8300, //CJK UNIFIED IDEOGRAPH - 0xC686: 0x830A, //CJK UNIFIED IDEOGRAPH - 0xC687: 0x830B, //CJK UNIFIED IDEOGRAPH - 0xC688: 0x830D, //CJK UNIFIED IDEOGRAPH - 0xC689: 0x8310, //CJK UNIFIED IDEOGRAPH - 0xC68A: 0x8312, //CJK UNIFIED IDEOGRAPH - 0xC68B: 0x8313, //CJK UNIFIED IDEOGRAPH - 0xC68C: 0x8316, //CJK UNIFIED IDEOGRAPH - 0xC68D: 0x8318, //CJK UNIFIED IDEOGRAPH - 0xC68E: 0x8319, //CJK UNIFIED IDEOGRAPH - 0xC68F: 0x831D, //CJK UNIFIED IDEOGRAPH - 0xC690: 0x831E, //CJK UNIFIED IDEOGRAPH - 0xC691: 0x831F, //CJK UNIFIED IDEOGRAPH - 0xC692: 0x8320, //CJK UNIFIED IDEOGRAPH - 0xC693: 0x8321, //CJK UNIFIED IDEOGRAPH - 0xC694: 0x8322, //CJK UNIFIED IDEOGRAPH - 0xC695: 0x8323, //CJK UNIFIED IDEOGRAPH - 0xC696: 0x8324, //CJK UNIFIED IDEOGRAPH - 0xC697: 0x8325, //CJK UNIFIED IDEOGRAPH - 0xC698: 0x8326, //CJK UNIFIED IDEOGRAPH - 0xC699: 0x8329, //CJK UNIFIED IDEOGRAPH - 0xC69A: 0x832A, //CJK UNIFIED IDEOGRAPH - 0xC69B: 0x832E, //CJK UNIFIED IDEOGRAPH - 0xC69C: 0x8330, //CJK UNIFIED IDEOGRAPH - 0xC69D: 0x8332, //CJK UNIFIED IDEOGRAPH - 0xC69E: 0x8337, //CJK UNIFIED IDEOGRAPH - 0xC69F: 0x833B, //CJK UNIFIED IDEOGRAPH - 0xC6A0: 0x833D, //CJK UNIFIED IDEOGRAPH - 0xC6A1: 0x5564, //CJK UNIFIED IDEOGRAPH - 0xC6A2: 0x813E, //CJK UNIFIED IDEOGRAPH - 0xC6A3: 0x75B2, //CJK UNIFIED IDEOGRAPH - 0xC6A4: 0x76AE, //CJK UNIFIED IDEOGRAPH - 0xC6A5: 0x5339, //CJK UNIFIED IDEOGRAPH - 0xC6A6: 0x75DE, //CJK UNIFIED IDEOGRAPH - 0xC6A7: 0x50FB, //CJK UNIFIED IDEOGRAPH - 0xC6A8: 0x5C41, //CJK UNIFIED IDEOGRAPH - 0xC6A9: 0x8B6C, //CJK UNIFIED IDEOGRAPH - 0xC6AA: 0x7BC7, //CJK UNIFIED IDEOGRAPH - 0xC6AB: 0x504F, //CJK UNIFIED IDEOGRAPH - 0xC6AC: 0x7247, //CJK UNIFIED IDEOGRAPH - 0xC6AD: 0x9A97, //CJK UNIFIED IDEOGRAPH - 0xC6AE: 0x98D8, //CJK UNIFIED IDEOGRAPH - 0xC6AF: 0x6F02, //CJK UNIFIED IDEOGRAPH - 0xC6B0: 0x74E2, //CJK UNIFIED IDEOGRAPH - 0xC6B1: 0x7968, //CJK UNIFIED IDEOGRAPH - 0xC6B2: 0x6487, //CJK UNIFIED IDEOGRAPH - 0xC6B3: 0x77A5, //CJK UNIFIED IDEOGRAPH - 0xC6B4: 0x62FC, //CJK UNIFIED IDEOGRAPH - 0xC6B5: 0x9891, //CJK UNIFIED IDEOGRAPH - 0xC6B6: 0x8D2B, //CJK UNIFIED IDEOGRAPH - 0xC6B7: 0x54C1, //CJK UNIFIED IDEOGRAPH - 0xC6B8: 0x8058, //CJK UNIFIED IDEOGRAPH - 0xC6B9: 0x4E52, //CJK UNIFIED IDEOGRAPH - 0xC6BA: 0x576A, //CJK UNIFIED IDEOGRAPH - 0xC6BB: 0x82F9, //CJK UNIFIED IDEOGRAPH - 0xC6BC: 0x840D, //CJK UNIFIED IDEOGRAPH - 0xC6BD: 0x5E73, //CJK UNIFIED IDEOGRAPH - 0xC6BE: 0x51ED, //CJK UNIFIED IDEOGRAPH - 0xC6BF: 0x74F6, //CJK UNIFIED IDEOGRAPH - 0xC6C0: 0x8BC4, //CJK UNIFIED IDEOGRAPH - 0xC6C1: 0x5C4F, //CJK UNIFIED IDEOGRAPH - 0xC6C2: 0x5761, //CJK UNIFIED IDEOGRAPH - 0xC6C3: 0x6CFC, //CJK UNIFIED IDEOGRAPH - 0xC6C4: 0x9887, //CJK UNIFIED IDEOGRAPH - 0xC6C5: 0x5A46, //CJK UNIFIED IDEOGRAPH - 0xC6C6: 0x7834, //CJK UNIFIED IDEOGRAPH - 0xC6C7: 0x9B44, //CJK UNIFIED IDEOGRAPH - 0xC6C8: 0x8FEB, //CJK UNIFIED IDEOGRAPH - 0xC6C9: 0x7C95, //CJK UNIFIED IDEOGRAPH - 0xC6CA: 0x5256, //CJK UNIFIED IDEOGRAPH - 0xC6CB: 0x6251, //CJK UNIFIED IDEOGRAPH - 0xC6CC: 0x94FA, //CJK UNIFIED IDEOGRAPH - 0xC6CD: 0x4EC6, //CJK UNIFIED IDEOGRAPH - 0xC6CE: 0x8386, //CJK UNIFIED IDEOGRAPH - 0xC6CF: 0x8461, //CJK UNIFIED IDEOGRAPH - 0xC6D0: 0x83E9, //CJK UNIFIED IDEOGRAPH - 0xC6D1: 0x84B2, //CJK UNIFIED IDEOGRAPH - 0xC6D2: 0x57D4, //CJK UNIFIED IDEOGRAPH - 0xC6D3: 0x6734, //CJK UNIFIED IDEOGRAPH - 0xC6D4: 0x5703, //CJK UNIFIED IDEOGRAPH - 0xC6D5: 0x666E, //CJK UNIFIED IDEOGRAPH - 0xC6D6: 0x6D66, //CJK UNIFIED IDEOGRAPH - 0xC6D7: 0x8C31, //CJK UNIFIED IDEOGRAPH - 0xC6D8: 0x66DD, //CJK UNIFIED IDEOGRAPH - 0xC6D9: 0x7011, //CJK UNIFIED IDEOGRAPH - 0xC6DA: 0x671F, //CJK UNIFIED IDEOGRAPH - 0xC6DB: 0x6B3A, //CJK UNIFIED IDEOGRAPH - 0xC6DC: 0x6816, //CJK UNIFIED IDEOGRAPH - 0xC6DD: 0x621A, //CJK UNIFIED IDEOGRAPH - 0xC6DE: 0x59BB, //CJK UNIFIED IDEOGRAPH - 0xC6DF: 0x4E03, //CJK UNIFIED IDEOGRAPH - 0xC6E0: 0x51C4, //CJK UNIFIED IDEOGRAPH - 0xC6E1: 0x6F06, //CJK UNIFIED IDEOGRAPH - 0xC6E2: 0x67D2, //CJK UNIFIED IDEOGRAPH - 0xC6E3: 0x6C8F, //CJK UNIFIED IDEOGRAPH - 0xC6E4: 0x5176, //CJK UNIFIED IDEOGRAPH - 0xC6E5: 0x68CB, //CJK UNIFIED IDEOGRAPH - 0xC6E6: 0x5947, //CJK UNIFIED IDEOGRAPH - 0xC6E7: 0x6B67, //CJK UNIFIED IDEOGRAPH - 0xC6E8: 0x7566, //CJK UNIFIED IDEOGRAPH - 0xC6E9: 0x5D0E, //CJK UNIFIED IDEOGRAPH - 0xC6EA: 0x8110, //CJK UNIFIED IDEOGRAPH - 0xC6EB: 0x9F50, //CJK UNIFIED IDEOGRAPH - 0xC6EC: 0x65D7, //CJK UNIFIED IDEOGRAPH - 0xC6ED: 0x7948, //CJK UNIFIED IDEOGRAPH - 0xC6EE: 0x7941, //CJK UNIFIED IDEOGRAPH - 0xC6EF: 0x9A91, //CJK UNIFIED IDEOGRAPH - 0xC6F0: 0x8D77, //CJK UNIFIED IDEOGRAPH - 0xC6F1: 0x5C82, //CJK UNIFIED IDEOGRAPH - 0xC6F2: 0x4E5E, //CJK UNIFIED IDEOGRAPH - 0xC6F3: 0x4F01, //CJK UNIFIED IDEOGRAPH - 0xC6F4: 0x542F, //CJK UNIFIED IDEOGRAPH - 0xC6F5: 0x5951, //CJK UNIFIED IDEOGRAPH - 0xC6F6: 0x780C, //CJK UNIFIED IDEOGRAPH - 0xC6F7: 0x5668, //CJK UNIFIED IDEOGRAPH - 0xC6F8: 0x6C14, //CJK UNIFIED IDEOGRAPH - 0xC6F9: 0x8FC4, //CJK UNIFIED IDEOGRAPH - 0xC6FA: 0x5F03, //CJK UNIFIED IDEOGRAPH - 0xC6FB: 0x6C7D, //CJK UNIFIED IDEOGRAPH - 0xC6FC: 0x6CE3, //CJK UNIFIED IDEOGRAPH - 0xC6FD: 0x8BAB, //CJK UNIFIED IDEOGRAPH - 0xC6FE: 0x6390, //CJK UNIFIED IDEOGRAPH - 0xC740: 0x833E, //CJK UNIFIED IDEOGRAPH - 0xC741: 0x833F, //CJK UNIFIED IDEOGRAPH - 0xC742: 0x8341, //CJK UNIFIED IDEOGRAPH - 0xC743: 0x8342, //CJK UNIFIED IDEOGRAPH - 0xC744: 0x8344, //CJK UNIFIED IDEOGRAPH - 0xC745: 0x8345, //CJK UNIFIED IDEOGRAPH - 0xC746: 0x8348, //CJK UNIFIED IDEOGRAPH - 0xC747: 0x834A, //CJK UNIFIED IDEOGRAPH - 0xC748: 0x834B, //CJK UNIFIED IDEOGRAPH - 0xC749: 0x834C, //CJK UNIFIED IDEOGRAPH - 0xC74A: 0x834D, //CJK UNIFIED IDEOGRAPH - 0xC74B: 0x834E, //CJK UNIFIED IDEOGRAPH - 0xC74C: 0x8353, //CJK UNIFIED IDEOGRAPH - 0xC74D: 0x8355, //CJK UNIFIED IDEOGRAPH - 0xC74E: 0x8356, //CJK UNIFIED IDEOGRAPH - 0xC74F: 0x8357, //CJK UNIFIED IDEOGRAPH - 0xC750: 0x8358, //CJK UNIFIED IDEOGRAPH - 0xC751: 0x8359, //CJK UNIFIED IDEOGRAPH - 0xC752: 0x835D, //CJK UNIFIED IDEOGRAPH - 0xC753: 0x8362, //CJK UNIFIED IDEOGRAPH - 0xC754: 0x8370, //CJK UNIFIED IDEOGRAPH - 0xC755: 0x8371, //CJK UNIFIED IDEOGRAPH - 0xC756: 0x8372, //CJK UNIFIED IDEOGRAPH - 0xC757: 0x8373, //CJK UNIFIED IDEOGRAPH - 0xC758: 0x8374, //CJK UNIFIED IDEOGRAPH - 0xC759: 0x8375, //CJK UNIFIED IDEOGRAPH - 0xC75A: 0x8376, //CJK UNIFIED IDEOGRAPH - 0xC75B: 0x8379, //CJK UNIFIED IDEOGRAPH - 0xC75C: 0x837A, //CJK UNIFIED IDEOGRAPH - 0xC75D: 0x837E, //CJK UNIFIED IDEOGRAPH - 0xC75E: 0x837F, //CJK UNIFIED IDEOGRAPH - 0xC75F: 0x8380, //CJK UNIFIED IDEOGRAPH - 0xC760: 0x8381, //CJK UNIFIED IDEOGRAPH - 0xC761: 0x8382, //CJK UNIFIED IDEOGRAPH - 0xC762: 0x8383, //CJK UNIFIED IDEOGRAPH - 0xC763: 0x8384, //CJK UNIFIED IDEOGRAPH - 0xC764: 0x8387, //CJK UNIFIED IDEOGRAPH - 0xC765: 0x8388, //CJK UNIFIED IDEOGRAPH - 0xC766: 0x838A, //CJK UNIFIED IDEOGRAPH - 0xC767: 0x838B, //CJK UNIFIED IDEOGRAPH - 0xC768: 0x838C, //CJK UNIFIED IDEOGRAPH - 0xC769: 0x838D, //CJK UNIFIED IDEOGRAPH - 0xC76A: 0x838F, //CJK UNIFIED IDEOGRAPH - 0xC76B: 0x8390, //CJK UNIFIED IDEOGRAPH - 0xC76C: 0x8391, //CJK UNIFIED IDEOGRAPH - 0xC76D: 0x8394, //CJK UNIFIED IDEOGRAPH - 0xC76E: 0x8395, //CJK UNIFIED IDEOGRAPH - 0xC76F: 0x8396, //CJK UNIFIED IDEOGRAPH - 0xC770: 0x8397, //CJK UNIFIED IDEOGRAPH - 0xC771: 0x8399, //CJK UNIFIED IDEOGRAPH - 0xC772: 0x839A, //CJK UNIFIED IDEOGRAPH - 0xC773: 0x839D, //CJK UNIFIED IDEOGRAPH - 0xC774: 0x839F, //CJK UNIFIED IDEOGRAPH - 0xC775: 0x83A1, //CJK UNIFIED IDEOGRAPH - 0xC776: 0x83A2, //CJK UNIFIED IDEOGRAPH - 0xC777: 0x83A3, //CJK UNIFIED IDEOGRAPH - 0xC778: 0x83A4, //CJK UNIFIED IDEOGRAPH - 0xC779: 0x83A5, //CJK UNIFIED IDEOGRAPH - 0xC77A: 0x83A6, //CJK UNIFIED IDEOGRAPH - 0xC77B: 0x83A7, //CJK UNIFIED IDEOGRAPH - 0xC77C: 0x83AC, //CJK UNIFIED IDEOGRAPH - 0xC77D: 0x83AD, //CJK UNIFIED IDEOGRAPH - 0xC77E: 0x83AE, //CJK UNIFIED IDEOGRAPH - 0xC780: 0x83AF, //CJK UNIFIED IDEOGRAPH - 0xC781: 0x83B5, //CJK UNIFIED IDEOGRAPH - 0xC782: 0x83BB, //CJK UNIFIED IDEOGRAPH - 0xC783: 0x83BE, //CJK UNIFIED IDEOGRAPH - 0xC784: 0x83BF, //CJK UNIFIED IDEOGRAPH - 0xC785: 0x83C2, //CJK UNIFIED IDEOGRAPH - 0xC786: 0x83C3, //CJK UNIFIED IDEOGRAPH - 0xC787: 0x83C4, //CJK UNIFIED IDEOGRAPH - 0xC788: 0x83C6, //CJK UNIFIED IDEOGRAPH - 0xC789: 0x83C8, //CJK UNIFIED IDEOGRAPH - 0xC78A: 0x83C9, //CJK UNIFIED IDEOGRAPH - 0xC78B: 0x83CB, //CJK UNIFIED IDEOGRAPH - 0xC78C: 0x83CD, //CJK UNIFIED IDEOGRAPH - 0xC78D: 0x83CE, //CJK UNIFIED IDEOGRAPH - 0xC78E: 0x83D0, //CJK UNIFIED IDEOGRAPH - 0xC78F: 0x83D1, //CJK UNIFIED IDEOGRAPH - 0xC790: 0x83D2, //CJK UNIFIED IDEOGRAPH - 0xC791: 0x83D3, //CJK UNIFIED IDEOGRAPH - 0xC792: 0x83D5, //CJK UNIFIED IDEOGRAPH - 0xC793: 0x83D7, //CJK UNIFIED IDEOGRAPH - 0xC794: 0x83D9, //CJK UNIFIED IDEOGRAPH - 0xC795: 0x83DA, //CJK UNIFIED IDEOGRAPH - 0xC796: 0x83DB, //CJK UNIFIED IDEOGRAPH - 0xC797: 0x83DE, //CJK UNIFIED IDEOGRAPH - 0xC798: 0x83E2, //CJK UNIFIED IDEOGRAPH - 0xC799: 0x83E3, //CJK UNIFIED IDEOGRAPH - 0xC79A: 0x83E4, //CJK UNIFIED IDEOGRAPH - 0xC79B: 0x83E6, //CJK UNIFIED IDEOGRAPH - 0xC79C: 0x83E7, //CJK UNIFIED IDEOGRAPH - 0xC79D: 0x83E8, //CJK UNIFIED IDEOGRAPH - 0xC79E: 0x83EB, //CJK UNIFIED IDEOGRAPH - 0xC79F: 0x83EC, //CJK UNIFIED IDEOGRAPH - 0xC7A0: 0x83ED, //CJK UNIFIED IDEOGRAPH - 0xC7A1: 0x6070, //CJK UNIFIED IDEOGRAPH - 0xC7A2: 0x6D3D, //CJK UNIFIED IDEOGRAPH - 0xC7A3: 0x7275, //CJK UNIFIED IDEOGRAPH - 0xC7A4: 0x6266, //CJK UNIFIED IDEOGRAPH - 0xC7A5: 0x948E, //CJK UNIFIED IDEOGRAPH - 0xC7A6: 0x94C5, //CJK UNIFIED IDEOGRAPH - 0xC7A7: 0x5343, //CJK UNIFIED IDEOGRAPH - 0xC7A8: 0x8FC1, //CJK UNIFIED IDEOGRAPH - 0xC7A9: 0x7B7E, //CJK UNIFIED IDEOGRAPH - 0xC7AA: 0x4EDF, //CJK UNIFIED IDEOGRAPH - 0xC7AB: 0x8C26, //CJK UNIFIED IDEOGRAPH - 0xC7AC: 0x4E7E, //CJK UNIFIED IDEOGRAPH - 0xC7AD: 0x9ED4, //CJK UNIFIED IDEOGRAPH - 0xC7AE: 0x94B1, //CJK UNIFIED IDEOGRAPH - 0xC7AF: 0x94B3, //CJK UNIFIED IDEOGRAPH - 0xC7B0: 0x524D, //CJK UNIFIED IDEOGRAPH - 0xC7B1: 0x6F5C, //CJK UNIFIED IDEOGRAPH - 0xC7B2: 0x9063, //CJK UNIFIED IDEOGRAPH - 0xC7B3: 0x6D45, //CJK UNIFIED IDEOGRAPH - 0xC7B4: 0x8C34, //CJK UNIFIED IDEOGRAPH - 0xC7B5: 0x5811, //CJK UNIFIED IDEOGRAPH - 0xC7B6: 0x5D4C, //CJK UNIFIED IDEOGRAPH - 0xC7B7: 0x6B20, //CJK UNIFIED IDEOGRAPH - 0xC7B8: 0x6B49, //CJK UNIFIED IDEOGRAPH - 0xC7B9: 0x67AA, //CJK UNIFIED IDEOGRAPH - 0xC7BA: 0x545B, //CJK UNIFIED IDEOGRAPH - 0xC7BB: 0x8154, //CJK UNIFIED IDEOGRAPH - 0xC7BC: 0x7F8C, //CJK UNIFIED IDEOGRAPH - 0xC7BD: 0x5899, //CJK UNIFIED IDEOGRAPH - 0xC7BE: 0x8537, //CJK UNIFIED IDEOGRAPH - 0xC7BF: 0x5F3A, //CJK UNIFIED IDEOGRAPH - 0xC7C0: 0x62A2, //CJK UNIFIED IDEOGRAPH - 0xC7C1: 0x6A47, //CJK UNIFIED IDEOGRAPH - 0xC7C2: 0x9539, //CJK UNIFIED IDEOGRAPH - 0xC7C3: 0x6572, //CJK UNIFIED IDEOGRAPH - 0xC7C4: 0x6084, //CJK UNIFIED IDEOGRAPH - 0xC7C5: 0x6865, //CJK UNIFIED IDEOGRAPH - 0xC7C6: 0x77A7, //CJK UNIFIED IDEOGRAPH - 0xC7C7: 0x4E54, //CJK UNIFIED IDEOGRAPH - 0xC7C8: 0x4FA8, //CJK UNIFIED IDEOGRAPH - 0xC7C9: 0x5DE7, //CJK UNIFIED IDEOGRAPH - 0xC7CA: 0x9798, //CJK UNIFIED IDEOGRAPH - 0xC7CB: 0x64AC, //CJK UNIFIED IDEOGRAPH - 0xC7CC: 0x7FD8, //CJK UNIFIED IDEOGRAPH - 0xC7CD: 0x5CED, //CJK UNIFIED IDEOGRAPH - 0xC7CE: 0x4FCF, //CJK UNIFIED IDEOGRAPH - 0xC7CF: 0x7A8D, //CJK UNIFIED IDEOGRAPH - 0xC7D0: 0x5207, //CJK UNIFIED IDEOGRAPH - 0xC7D1: 0x8304, //CJK UNIFIED IDEOGRAPH - 0xC7D2: 0x4E14, //CJK UNIFIED IDEOGRAPH - 0xC7D3: 0x602F, //CJK UNIFIED IDEOGRAPH - 0xC7D4: 0x7A83, //CJK UNIFIED IDEOGRAPH - 0xC7D5: 0x94A6, //CJK UNIFIED IDEOGRAPH - 0xC7D6: 0x4FB5, //CJK UNIFIED IDEOGRAPH - 0xC7D7: 0x4EB2, //CJK UNIFIED IDEOGRAPH - 0xC7D8: 0x79E6, //CJK UNIFIED IDEOGRAPH - 0xC7D9: 0x7434, //CJK UNIFIED IDEOGRAPH - 0xC7DA: 0x52E4, //CJK UNIFIED IDEOGRAPH - 0xC7DB: 0x82B9, //CJK UNIFIED IDEOGRAPH - 0xC7DC: 0x64D2, //CJK UNIFIED IDEOGRAPH - 0xC7DD: 0x79BD, //CJK UNIFIED IDEOGRAPH - 0xC7DE: 0x5BDD, //CJK UNIFIED IDEOGRAPH - 0xC7DF: 0x6C81, //CJK UNIFIED IDEOGRAPH - 0xC7E0: 0x9752, //CJK UNIFIED IDEOGRAPH - 0xC7E1: 0x8F7B, //CJK UNIFIED IDEOGRAPH - 0xC7E2: 0x6C22, //CJK UNIFIED IDEOGRAPH - 0xC7E3: 0x503E, //CJK UNIFIED IDEOGRAPH - 0xC7E4: 0x537F, //CJK UNIFIED IDEOGRAPH - 0xC7E5: 0x6E05, //CJK UNIFIED IDEOGRAPH - 0xC7E6: 0x64CE, //CJK UNIFIED IDEOGRAPH - 0xC7E7: 0x6674, //CJK UNIFIED IDEOGRAPH - 0xC7E8: 0x6C30, //CJK UNIFIED IDEOGRAPH - 0xC7E9: 0x60C5, //CJK UNIFIED IDEOGRAPH - 0xC7EA: 0x9877, //CJK UNIFIED IDEOGRAPH - 0xC7EB: 0x8BF7, //CJK UNIFIED IDEOGRAPH - 0xC7EC: 0x5E86, //CJK UNIFIED IDEOGRAPH - 0xC7ED: 0x743C, //CJK UNIFIED IDEOGRAPH - 0xC7EE: 0x7A77, //CJK UNIFIED IDEOGRAPH - 0xC7EF: 0x79CB, //CJK UNIFIED IDEOGRAPH - 0xC7F0: 0x4E18, //CJK UNIFIED IDEOGRAPH - 0xC7F1: 0x90B1, //CJK UNIFIED IDEOGRAPH - 0xC7F2: 0x7403, //CJK UNIFIED IDEOGRAPH - 0xC7F3: 0x6C42, //CJK UNIFIED IDEOGRAPH - 0xC7F4: 0x56DA, //CJK UNIFIED IDEOGRAPH - 0xC7F5: 0x914B, //CJK UNIFIED IDEOGRAPH - 0xC7F6: 0x6CC5, //CJK UNIFIED IDEOGRAPH - 0xC7F7: 0x8D8B, //CJK UNIFIED IDEOGRAPH - 0xC7F8: 0x533A, //CJK UNIFIED IDEOGRAPH - 0xC7F9: 0x86C6, //CJK UNIFIED IDEOGRAPH - 0xC7FA: 0x66F2, //CJK UNIFIED IDEOGRAPH - 0xC7FB: 0x8EAF, //CJK UNIFIED IDEOGRAPH - 0xC7FC: 0x5C48, //CJK UNIFIED IDEOGRAPH - 0xC7FD: 0x9A71, //CJK UNIFIED IDEOGRAPH - 0xC7FE: 0x6E20, //CJK UNIFIED IDEOGRAPH - 0xC840: 0x83EE, //CJK UNIFIED IDEOGRAPH - 0xC841: 0x83EF, //CJK UNIFIED IDEOGRAPH - 0xC842: 0x83F3, //CJK UNIFIED IDEOGRAPH - 0xC843: 0x83F4, //CJK UNIFIED IDEOGRAPH - 0xC844: 0x83F5, //CJK UNIFIED IDEOGRAPH - 0xC845: 0x83F6, //CJK UNIFIED IDEOGRAPH - 0xC846: 0x83F7, //CJK UNIFIED IDEOGRAPH - 0xC847: 0x83FA, //CJK UNIFIED IDEOGRAPH - 0xC848: 0x83FB, //CJK UNIFIED IDEOGRAPH - 0xC849: 0x83FC, //CJK UNIFIED IDEOGRAPH - 0xC84A: 0x83FE, //CJK UNIFIED IDEOGRAPH - 0xC84B: 0x83FF, //CJK UNIFIED IDEOGRAPH - 0xC84C: 0x8400, //CJK UNIFIED IDEOGRAPH - 0xC84D: 0x8402, //CJK UNIFIED IDEOGRAPH - 0xC84E: 0x8405, //CJK UNIFIED IDEOGRAPH - 0xC84F: 0x8407, //CJK UNIFIED IDEOGRAPH - 0xC850: 0x8408, //CJK UNIFIED IDEOGRAPH - 0xC851: 0x8409, //CJK UNIFIED IDEOGRAPH - 0xC852: 0x840A, //CJK UNIFIED IDEOGRAPH - 0xC853: 0x8410, //CJK UNIFIED IDEOGRAPH - 0xC854: 0x8412, //CJK UNIFIED IDEOGRAPH - 0xC855: 0x8413, //CJK UNIFIED IDEOGRAPH - 0xC856: 0x8414, //CJK UNIFIED IDEOGRAPH - 0xC857: 0x8415, //CJK UNIFIED IDEOGRAPH - 0xC858: 0x8416, //CJK UNIFIED IDEOGRAPH - 0xC859: 0x8417, //CJK UNIFIED IDEOGRAPH - 0xC85A: 0x8419, //CJK UNIFIED IDEOGRAPH - 0xC85B: 0x841A, //CJK UNIFIED IDEOGRAPH - 0xC85C: 0x841B, //CJK UNIFIED IDEOGRAPH - 0xC85D: 0x841E, //CJK UNIFIED IDEOGRAPH - 0xC85E: 0x841F, //CJK UNIFIED IDEOGRAPH - 0xC85F: 0x8420, //CJK UNIFIED IDEOGRAPH - 0xC860: 0x8421, //CJK UNIFIED IDEOGRAPH - 0xC861: 0x8422, //CJK UNIFIED IDEOGRAPH - 0xC862: 0x8423, //CJK UNIFIED IDEOGRAPH - 0xC863: 0x8429, //CJK UNIFIED IDEOGRAPH - 0xC864: 0x842A, //CJK UNIFIED IDEOGRAPH - 0xC865: 0x842B, //CJK UNIFIED IDEOGRAPH - 0xC866: 0x842C, //CJK UNIFIED IDEOGRAPH - 0xC867: 0x842D, //CJK UNIFIED IDEOGRAPH - 0xC868: 0x842E, //CJK UNIFIED IDEOGRAPH - 0xC869: 0x842F, //CJK UNIFIED IDEOGRAPH - 0xC86A: 0x8430, //CJK UNIFIED IDEOGRAPH - 0xC86B: 0x8432, //CJK UNIFIED IDEOGRAPH - 0xC86C: 0x8433, //CJK UNIFIED IDEOGRAPH - 0xC86D: 0x8434, //CJK UNIFIED IDEOGRAPH - 0xC86E: 0x8435, //CJK UNIFIED IDEOGRAPH - 0xC86F: 0x8436, //CJK UNIFIED IDEOGRAPH - 0xC870: 0x8437, //CJK UNIFIED IDEOGRAPH - 0xC871: 0x8439, //CJK UNIFIED IDEOGRAPH - 0xC872: 0x843A, //CJK UNIFIED IDEOGRAPH - 0xC873: 0x843B, //CJK UNIFIED IDEOGRAPH - 0xC874: 0x843E, //CJK UNIFIED IDEOGRAPH - 0xC875: 0x843F, //CJK UNIFIED IDEOGRAPH - 0xC876: 0x8440, //CJK UNIFIED IDEOGRAPH - 0xC877: 0x8441, //CJK UNIFIED IDEOGRAPH - 0xC878: 0x8442, //CJK UNIFIED IDEOGRAPH - 0xC879: 0x8443, //CJK UNIFIED IDEOGRAPH - 0xC87A: 0x8444, //CJK UNIFIED IDEOGRAPH - 0xC87B: 0x8445, //CJK UNIFIED IDEOGRAPH - 0xC87C: 0x8447, //CJK UNIFIED IDEOGRAPH - 0xC87D: 0x8448, //CJK UNIFIED IDEOGRAPH - 0xC87E: 0x8449, //CJK UNIFIED IDEOGRAPH - 0xC880: 0x844A, //CJK UNIFIED IDEOGRAPH - 0xC881: 0x844B, //CJK UNIFIED IDEOGRAPH - 0xC882: 0x844C, //CJK UNIFIED IDEOGRAPH - 0xC883: 0x844D, //CJK UNIFIED IDEOGRAPH - 0xC884: 0x844E, //CJK UNIFIED IDEOGRAPH - 0xC885: 0x844F, //CJK UNIFIED IDEOGRAPH - 0xC886: 0x8450, //CJK UNIFIED IDEOGRAPH - 0xC887: 0x8452, //CJK UNIFIED IDEOGRAPH - 0xC888: 0x8453, //CJK UNIFIED IDEOGRAPH - 0xC889: 0x8454, //CJK UNIFIED IDEOGRAPH - 0xC88A: 0x8455, //CJK UNIFIED IDEOGRAPH - 0xC88B: 0x8456, //CJK UNIFIED IDEOGRAPH - 0xC88C: 0x8458, //CJK UNIFIED IDEOGRAPH - 0xC88D: 0x845D, //CJK UNIFIED IDEOGRAPH - 0xC88E: 0x845E, //CJK UNIFIED IDEOGRAPH - 0xC88F: 0x845F, //CJK UNIFIED IDEOGRAPH - 0xC890: 0x8460, //CJK UNIFIED IDEOGRAPH - 0xC891: 0x8462, //CJK UNIFIED IDEOGRAPH - 0xC892: 0x8464, //CJK UNIFIED IDEOGRAPH - 0xC893: 0x8465, //CJK UNIFIED IDEOGRAPH - 0xC894: 0x8466, //CJK UNIFIED IDEOGRAPH - 0xC895: 0x8467, //CJK UNIFIED IDEOGRAPH - 0xC896: 0x8468, //CJK UNIFIED IDEOGRAPH - 0xC897: 0x846A, //CJK UNIFIED IDEOGRAPH - 0xC898: 0x846E, //CJK UNIFIED IDEOGRAPH - 0xC899: 0x846F, //CJK UNIFIED IDEOGRAPH - 0xC89A: 0x8470, //CJK UNIFIED IDEOGRAPH - 0xC89B: 0x8472, //CJK UNIFIED IDEOGRAPH - 0xC89C: 0x8474, //CJK UNIFIED IDEOGRAPH - 0xC89D: 0x8477, //CJK UNIFIED IDEOGRAPH - 0xC89E: 0x8479, //CJK UNIFIED IDEOGRAPH - 0xC89F: 0x847B, //CJK UNIFIED IDEOGRAPH - 0xC8A0: 0x847C, //CJK UNIFIED IDEOGRAPH - 0xC8A1: 0x53D6, //CJK UNIFIED IDEOGRAPH - 0xC8A2: 0x5A36, //CJK UNIFIED IDEOGRAPH - 0xC8A3: 0x9F8B, //CJK UNIFIED IDEOGRAPH - 0xC8A4: 0x8DA3, //CJK UNIFIED IDEOGRAPH - 0xC8A5: 0x53BB, //CJK UNIFIED IDEOGRAPH - 0xC8A6: 0x5708, //CJK UNIFIED IDEOGRAPH - 0xC8A7: 0x98A7, //CJK UNIFIED IDEOGRAPH - 0xC8A8: 0x6743, //CJK UNIFIED IDEOGRAPH - 0xC8A9: 0x919B, //CJK UNIFIED IDEOGRAPH - 0xC8AA: 0x6CC9, //CJK UNIFIED IDEOGRAPH - 0xC8AB: 0x5168, //CJK UNIFIED IDEOGRAPH - 0xC8AC: 0x75CA, //CJK UNIFIED IDEOGRAPH - 0xC8AD: 0x62F3, //CJK UNIFIED IDEOGRAPH - 0xC8AE: 0x72AC, //CJK UNIFIED IDEOGRAPH - 0xC8AF: 0x5238, //CJK UNIFIED IDEOGRAPH - 0xC8B0: 0x529D, //CJK UNIFIED IDEOGRAPH - 0xC8B1: 0x7F3A, //CJK UNIFIED IDEOGRAPH - 0xC8B2: 0x7094, //CJK UNIFIED IDEOGRAPH - 0xC8B3: 0x7638, //CJK UNIFIED IDEOGRAPH - 0xC8B4: 0x5374, //CJK UNIFIED IDEOGRAPH - 0xC8B5: 0x9E4A, //CJK UNIFIED IDEOGRAPH - 0xC8B6: 0x69B7, //CJK UNIFIED IDEOGRAPH - 0xC8B7: 0x786E, //CJK UNIFIED IDEOGRAPH - 0xC8B8: 0x96C0, //CJK UNIFIED IDEOGRAPH - 0xC8B9: 0x88D9, //CJK UNIFIED IDEOGRAPH - 0xC8BA: 0x7FA4, //CJK UNIFIED IDEOGRAPH - 0xC8BB: 0x7136, //CJK UNIFIED IDEOGRAPH - 0xC8BC: 0x71C3, //CJK UNIFIED IDEOGRAPH - 0xC8BD: 0x5189, //CJK UNIFIED IDEOGRAPH - 0xC8BE: 0x67D3, //CJK UNIFIED IDEOGRAPH - 0xC8BF: 0x74E4, //CJK UNIFIED IDEOGRAPH - 0xC8C0: 0x58E4, //CJK UNIFIED IDEOGRAPH - 0xC8C1: 0x6518, //CJK UNIFIED IDEOGRAPH - 0xC8C2: 0x56B7, //CJK UNIFIED IDEOGRAPH - 0xC8C3: 0x8BA9, //CJK UNIFIED IDEOGRAPH - 0xC8C4: 0x9976, //CJK UNIFIED IDEOGRAPH - 0xC8C5: 0x6270, //CJK UNIFIED IDEOGRAPH - 0xC8C6: 0x7ED5, //CJK UNIFIED IDEOGRAPH - 0xC8C7: 0x60F9, //CJK UNIFIED IDEOGRAPH - 0xC8C8: 0x70ED, //CJK UNIFIED IDEOGRAPH - 0xC8C9: 0x58EC, //CJK UNIFIED IDEOGRAPH - 0xC8CA: 0x4EC1, //CJK UNIFIED IDEOGRAPH - 0xC8CB: 0x4EBA, //CJK UNIFIED IDEOGRAPH - 0xC8CC: 0x5FCD, //CJK UNIFIED IDEOGRAPH - 0xC8CD: 0x97E7, //CJK UNIFIED IDEOGRAPH - 0xC8CE: 0x4EFB, //CJK UNIFIED IDEOGRAPH - 0xC8CF: 0x8BA4, //CJK UNIFIED IDEOGRAPH - 0xC8D0: 0x5203, //CJK UNIFIED IDEOGRAPH - 0xC8D1: 0x598A, //CJK UNIFIED IDEOGRAPH - 0xC8D2: 0x7EAB, //CJK UNIFIED IDEOGRAPH - 0xC8D3: 0x6254, //CJK UNIFIED IDEOGRAPH - 0xC8D4: 0x4ECD, //CJK UNIFIED IDEOGRAPH - 0xC8D5: 0x65E5, //CJK UNIFIED IDEOGRAPH - 0xC8D6: 0x620E, //CJK UNIFIED IDEOGRAPH - 0xC8D7: 0x8338, //CJK UNIFIED IDEOGRAPH - 0xC8D8: 0x84C9, //CJK UNIFIED IDEOGRAPH - 0xC8D9: 0x8363, //CJK UNIFIED IDEOGRAPH - 0xC8DA: 0x878D, //CJK UNIFIED IDEOGRAPH - 0xC8DB: 0x7194, //CJK UNIFIED IDEOGRAPH - 0xC8DC: 0x6EB6, //CJK UNIFIED IDEOGRAPH - 0xC8DD: 0x5BB9, //CJK UNIFIED IDEOGRAPH - 0xC8DE: 0x7ED2, //CJK UNIFIED IDEOGRAPH - 0xC8DF: 0x5197, //CJK UNIFIED IDEOGRAPH - 0xC8E0: 0x63C9, //CJK UNIFIED IDEOGRAPH - 0xC8E1: 0x67D4, //CJK UNIFIED IDEOGRAPH - 0xC8E2: 0x8089, //CJK UNIFIED IDEOGRAPH - 0xC8E3: 0x8339, //CJK UNIFIED IDEOGRAPH - 0xC8E4: 0x8815, //CJK UNIFIED IDEOGRAPH - 0xC8E5: 0x5112, //CJK UNIFIED IDEOGRAPH - 0xC8E6: 0x5B7A, //CJK UNIFIED IDEOGRAPH - 0xC8E7: 0x5982, //CJK UNIFIED IDEOGRAPH - 0xC8E8: 0x8FB1, //CJK UNIFIED IDEOGRAPH - 0xC8E9: 0x4E73, //CJK UNIFIED IDEOGRAPH - 0xC8EA: 0x6C5D, //CJK UNIFIED IDEOGRAPH - 0xC8EB: 0x5165, //CJK UNIFIED IDEOGRAPH - 0xC8EC: 0x8925, //CJK UNIFIED IDEOGRAPH - 0xC8ED: 0x8F6F, //CJK UNIFIED IDEOGRAPH - 0xC8EE: 0x962E, //CJK UNIFIED IDEOGRAPH - 0xC8EF: 0x854A, //CJK UNIFIED IDEOGRAPH - 0xC8F0: 0x745E, //CJK UNIFIED IDEOGRAPH - 0xC8F1: 0x9510, //CJK UNIFIED IDEOGRAPH - 0xC8F2: 0x95F0, //CJK UNIFIED IDEOGRAPH - 0xC8F3: 0x6DA6, //CJK UNIFIED IDEOGRAPH - 0xC8F4: 0x82E5, //CJK UNIFIED IDEOGRAPH - 0xC8F5: 0x5F31, //CJK UNIFIED IDEOGRAPH - 0xC8F6: 0x6492, //CJK UNIFIED IDEOGRAPH - 0xC8F7: 0x6D12, //CJK UNIFIED IDEOGRAPH - 0xC8F8: 0x8428, //CJK UNIFIED IDEOGRAPH - 0xC8F9: 0x816E, //CJK UNIFIED IDEOGRAPH - 0xC8FA: 0x9CC3, //CJK UNIFIED IDEOGRAPH - 0xC8FB: 0x585E, //CJK UNIFIED IDEOGRAPH - 0xC8FC: 0x8D5B, //CJK UNIFIED IDEOGRAPH - 0xC8FD: 0x4E09, //CJK UNIFIED IDEOGRAPH - 0xC8FE: 0x53C1, //CJK UNIFIED IDEOGRAPH - 0xC940: 0x847D, //CJK UNIFIED IDEOGRAPH - 0xC941: 0x847E, //CJK UNIFIED IDEOGRAPH - 0xC942: 0x847F, //CJK UNIFIED IDEOGRAPH - 0xC943: 0x8480, //CJK UNIFIED IDEOGRAPH - 0xC944: 0x8481, //CJK UNIFIED IDEOGRAPH - 0xC945: 0x8483, //CJK UNIFIED IDEOGRAPH - 0xC946: 0x8484, //CJK UNIFIED IDEOGRAPH - 0xC947: 0x8485, //CJK UNIFIED IDEOGRAPH - 0xC948: 0x8486, //CJK UNIFIED IDEOGRAPH - 0xC949: 0x848A, //CJK UNIFIED IDEOGRAPH - 0xC94A: 0x848D, //CJK UNIFIED IDEOGRAPH - 0xC94B: 0x848F, //CJK UNIFIED IDEOGRAPH - 0xC94C: 0x8490, //CJK UNIFIED IDEOGRAPH - 0xC94D: 0x8491, //CJK UNIFIED IDEOGRAPH - 0xC94E: 0x8492, //CJK UNIFIED IDEOGRAPH - 0xC94F: 0x8493, //CJK UNIFIED IDEOGRAPH - 0xC950: 0x8494, //CJK UNIFIED IDEOGRAPH - 0xC951: 0x8495, //CJK UNIFIED IDEOGRAPH - 0xC952: 0x8496, //CJK UNIFIED IDEOGRAPH - 0xC953: 0x8498, //CJK UNIFIED IDEOGRAPH - 0xC954: 0x849A, //CJK UNIFIED IDEOGRAPH - 0xC955: 0x849B, //CJK UNIFIED IDEOGRAPH - 0xC956: 0x849D, //CJK UNIFIED IDEOGRAPH - 0xC957: 0x849E, //CJK UNIFIED IDEOGRAPH - 0xC958: 0x849F, //CJK UNIFIED IDEOGRAPH - 0xC959: 0x84A0, //CJK UNIFIED IDEOGRAPH - 0xC95A: 0x84A2, //CJK UNIFIED IDEOGRAPH - 0xC95B: 0x84A3, //CJK UNIFIED IDEOGRAPH - 0xC95C: 0x84A4, //CJK UNIFIED IDEOGRAPH - 0xC95D: 0x84A5, //CJK UNIFIED IDEOGRAPH - 0xC95E: 0x84A6, //CJK UNIFIED IDEOGRAPH - 0xC95F: 0x84A7, //CJK UNIFIED IDEOGRAPH - 0xC960: 0x84A8, //CJK UNIFIED IDEOGRAPH - 0xC961: 0x84A9, //CJK UNIFIED IDEOGRAPH - 0xC962: 0x84AA, //CJK UNIFIED IDEOGRAPH - 0xC963: 0x84AB, //CJK UNIFIED IDEOGRAPH - 0xC964: 0x84AC, //CJK UNIFIED IDEOGRAPH - 0xC965: 0x84AD, //CJK UNIFIED IDEOGRAPH - 0xC966: 0x84AE, //CJK UNIFIED IDEOGRAPH - 0xC967: 0x84B0, //CJK UNIFIED IDEOGRAPH - 0xC968: 0x84B1, //CJK UNIFIED IDEOGRAPH - 0xC969: 0x84B3, //CJK UNIFIED IDEOGRAPH - 0xC96A: 0x84B5, //CJK UNIFIED IDEOGRAPH - 0xC96B: 0x84B6, //CJK UNIFIED IDEOGRAPH - 0xC96C: 0x84B7, //CJK UNIFIED IDEOGRAPH - 0xC96D: 0x84BB, //CJK UNIFIED IDEOGRAPH - 0xC96E: 0x84BC, //CJK UNIFIED IDEOGRAPH - 0xC96F: 0x84BE, //CJK UNIFIED IDEOGRAPH - 0xC970: 0x84C0, //CJK UNIFIED IDEOGRAPH - 0xC971: 0x84C2, //CJK UNIFIED IDEOGRAPH - 0xC972: 0x84C3, //CJK UNIFIED IDEOGRAPH - 0xC973: 0x84C5, //CJK UNIFIED IDEOGRAPH - 0xC974: 0x84C6, //CJK UNIFIED IDEOGRAPH - 0xC975: 0x84C7, //CJK UNIFIED IDEOGRAPH - 0xC976: 0x84C8, //CJK UNIFIED IDEOGRAPH - 0xC977: 0x84CB, //CJK UNIFIED IDEOGRAPH - 0xC978: 0x84CC, //CJK UNIFIED IDEOGRAPH - 0xC979: 0x84CE, //CJK UNIFIED IDEOGRAPH - 0xC97A: 0x84CF, //CJK UNIFIED IDEOGRAPH - 0xC97B: 0x84D2, //CJK UNIFIED IDEOGRAPH - 0xC97C: 0x84D4, //CJK UNIFIED IDEOGRAPH - 0xC97D: 0x84D5, //CJK UNIFIED IDEOGRAPH - 0xC97E: 0x84D7, //CJK UNIFIED IDEOGRAPH - 0xC980: 0x84D8, //CJK UNIFIED IDEOGRAPH - 0xC981: 0x84D9, //CJK UNIFIED IDEOGRAPH - 0xC982: 0x84DA, //CJK UNIFIED IDEOGRAPH - 0xC983: 0x84DB, //CJK UNIFIED IDEOGRAPH - 0xC984: 0x84DC, //CJK UNIFIED IDEOGRAPH - 0xC985: 0x84DE, //CJK UNIFIED IDEOGRAPH - 0xC986: 0x84E1, //CJK UNIFIED IDEOGRAPH - 0xC987: 0x84E2, //CJK UNIFIED IDEOGRAPH - 0xC988: 0x84E4, //CJK UNIFIED IDEOGRAPH - 0xC989: 0x84E7, //CJK UNIFIED IDEOGRAPH - 0xC98A: 0x84E8, //CJK UNIFIED IDEOGRAPH - 0xC98B: 0x84E9, //CJK UNIFIED IDEOGRAPH - 0xC98C: 0x84EA, //CJK UNIFIED IDEOGRAPH - 0xC98D: 0x84EB, //CJK UNIFIED IDEOGRAPH - 0xC98E: 0x84ED, //CJK UNIFIED IDEOGRAPH - 0xC98F: 0x84EE, //CJK UNIFIED IDEOGRAPH - 0xC990: 0x84EF, //CJK UNIFIED IDEOGRAPH - 0xC991: 0x84F1, //CJK UNIFIED IDEOGRAPH - 0xC992: 0x84F2, //CJK UNIFIED IDEOGRAPH - 0xC993: 0x84F3, //CJK UNIFIED IDEOGRAPH - 0xC994: 0x84F4, //CJK UNIFIED IDEOGRAPH - 0xC995: 0x84F5, //CJK UNIFIED IDEOGRAPH - 0xC996: 0x84F6, //CJK UNIFIED IDEOGRAPH - 0xC997: 0x84F7, //CJK UNIFIED IDEOGRAPH - 0xC998: 0x84F8, //CJK UNIFIED IDEOGRAPH - 0xC999: 0x84F9, //CJK UNIFIED IDEOGRAPH - 0xC99A: 0x84FA, //CJK UNIFIED IDEOGRAPH - 0xC99B: 0x84FB, //CJK UNIFIED IDEOGRAPH - 0xC99C: 0x84FD, //CJK UNIFIED IDEOGRAPH - 0xC99D: 0x84FE, //CJK UNIFIED IDEOGRAPH - 0xC99E: 0x8500, //CJK UNIFIED IDEOGRAPH - 0xC99F: 0x8501, //CJK UNIFIED IDEOGRAPH - 0xC9A0: 0x8502, //CJK UNIFIED IDEOGRAPH - 0xC9A1: 0x4F1E, //CJK UNIFIED IDEOGRAPH - 0xC9A2: 0x6563, //CJK UNIFIED IDEOGRAPH - 0xC9A3: 0x6851, //CJK UNIFIED IDEOGRAPH - 0xC9A4: 0x55D3, //CJK UNIFIED IDEOGRAPH - 0xC9A5: 0x4E27, //CJK UNIFIED IDEOGRAPH - 0xC9A6: 0x6414, //CJK UNIFIED IDEOGRAPH - 0xC9A7: 0x9A9A, //CJK UNIFIED IDEOGRAPH - 0xC9A8: 0x626B, //CJK UNIFIED IDEOGRAPH - 0xC9A9: 0x5AC2, //CJK UNIFIED IDEOGRAPH - 0xC9AA: 0x745F, //CJK UNIFIED IDEOGRAPH - 0xC9AB: 0x8272, //CJK UNIFIED IDEOGRAPH - 0xC9AC: 0x6DA9, //CJK UNIFIED IDEOGRAPH - 0xC9AD: 0x68EE, //CJK UNIFIED IDEOGRAPH - 0xC9AE: 0x50E7, //CJK UNIFIED IDEOGRAPH - 0xC9AF: 0x838E, //CJK UNIFIED IDEOGRAPH - 0xC9B0: 0x7802, //CJK UNIFIED IDEOGRAPH - 0xC9B1: 0x6740, //CJK UNIFIED IDEOGRAPH - 0xC9B2: 0x5239, //CJK UNIFIED IDEOGRAPH - 0xC9B3: 0x6C99, //CJK UNIFIED IDEOGRAPH - 0xC9B4: 0x7EB1, //CJK UNIFIED IDEOGRAPH - 0xC9B5: 0x50BB, //CJK UNIFIED IDEOGRAPH - 0xC9B6: 0x5565, //CJK UNIFIED IDEOGRAPH - 0xC9B7: 0x715E, //CJK UNIFIED IDEOGRAPH - 0xC9B8: 0x7B5B, //CJK UNIFIED IDEOGRAPH - 0xC9B9: 0x6652, //CJK UNIFIED IDEOGRAPH - 0xC9BA: 0x73CA, //CJK UNIFIED IDEOGRAPH - 0xC9BB: 0x82EB, //CJK UNIFIED IDEOGRAPH - 0xC9BC: 0x6749, //CJK UNIFIED IDEOGRAPH - 0xC9BD: 0x5C71, //CJK UNIFIED IDEOGRAPH - 0xC9BE: 0x5220, //CJK UNIFIED IDEOGRAPH - 0xC9BF: 0x717D, //CJK UNIFIED IDEOGRAPH - 0xC9C0: 0x886B, //CJK UNIFIED IDEOGRAPH - 0xC9C1: 0x95EA, //CJK UNIFIED IDEOGRAPH - 0xC9C2: 0x9655, //CJK UNIFIED IDEOGRAPH - 0xC9C3: 0x64C5, //CJK UNIFIED IDEOGRAPH - 0xC9C4: 0x8D61, //CJK UNIFIED IDEOGRAPH - 0xC9C5: 0x81B3, //CJK UNIFIED IDEOGRAPH - 0xC9C6: 0x5584, //CJK UNIFIED IDEOGRAPH - 0xC9C7: 0x6C55, //CJK UNIFIED IDEOGRAPH - 0xC9C8: 0x6247, //CJK UNIFIED IDEOGRAPH - 0xC9C9: 0x7F2E, //CJK UNIFIED IDEOGRAPH - 0xC9CA: 0x5892, //CJK UNIFIED IDEOGRAPH - 0xC9CB: 0x4F24, //CJK UNIFIED IDEOGRAPH - 0xC9CC: 0x5546, //CJK UNIFIED IDEOGRAPH - 0xC9CD: 0x8D4F, //CJK UNIFIED IDEOGRAPH - 0xC9CE: 0x664C, //CJK UNIFIED IDEOGRAPH - 0xC9CF: 0x4E0A, //CJK UNIFIED IDEOGRAPH - 0xC9D0: 0x5C1A, //CJK UNIFIED IDEOGRAPH - 0xC9D1: 0x88F3, //CJK UNIFIED IDEOGRAPH - 0xC9D2: 0x68A2, //CJK UNIFIED IDEOGRAPH - 0xC9D3: 0x634E, //CJK UNIFIED IDEOGRAPH - 0xC9D4: 0x7A0D, //CJK UNIFIED IDEOGRAPH - 0xC9D5: 0x70E7, //CJK UNIFIED IDEOGRAPH - 0xC9D6: 0x828D, //CJK UNIFIED IDEOGRAPH - 0xC9D7: 0x52FA, //CJK UNIFIED IDEOGRAPH - 0xC9D8: 0x97F6, //CJK UNIFIED IDEOGRAPH - 0xC9D9: 0x5C11, //CJK UNIFIED IDEOGRAPH - 0xC9DA: 0x54E8, //CJK UNIFIED IDEOGRAPH - 0xC9DB: 0x90B5, //CJK UNIFIED IDEOGRAPH - 0xC9DC: 0x7ECD, //CJK UNIFIED IDEOGRAPH - 0xC9DD: 0x5962, //CJK UNIFIED IDEOGRAPH - 0xC9DE: 0x8D4A, //CJK UNIFIED IDEOGRAPH - 0xC9DF: 0x86C7, //CJK UNIFIED IDEOGRAPH - 0xC9E0: 0x820C, //CJK UNIFIED IDEOGRAPH - 0xC9E1: 0x820D, //CJK UNIFIED IDEOGRAPH - 0xC9E2: 0x8D66, //CJK UNIFIED IDEOGRAPH - 0xC9E3: 0x6444, //CJK UNIFIED IDEOGRAPH - 0xC9E4: 0x5C04, //CJK UNIFIED IDEOGRAPH - 0xC9E5: 0x6151, //CJK UNIFIED IDEOGRAPH - 0xC9E6: 0x6D89, //CJK UNIFIED IDEOGRAPH - 0xC9E7: 0x793E, //CJK UNIFIED IDEOGRAPH - 0xC9E8: 0x8BBE, //CJK UNIFIED IDEOGRAPH - 0xC9E9: 0x7837, //CJK UNIFIED IDEOGRAPH - 0xC9EA: 0x7533, //CJK UNIFIED IDEOGRAPH - 0xC9EB: 0x547B, //CJK UNIFIED IDEOGRAPH - 0xC9EC: 0x4F38, //CJK UNIFIED IDEOGRAPH - 0xC9ED: 0x8EAB, //CJK UNIFIED IDEOGRAPH - 0xC9EE: 0x6DF1, //CJK UNIFIED IDEOGRAPH - 0xC9EF: 0x5A20, //CJK UNIFIED IDEOGRAPH - 0xC9F0: 0x7EC5, //CJK UNIFIED IDEOGRAPH - 0xC9F1: 0x795E, //CJK UNIFIED IDEOGRAPH - 0xC9F2: 0x6C88, //CJK UNIFIED IDEOGRAPH - 0xC9F3: 0x5BA1, //CJK UNIFIED IDEOGRAPH - 0xC9F4: 0x5A76, //CJK UNIFIED IDEOGRAPH - 0xC9F5: 0x751A, //CJK UNIFIED IDEOGRAPH - 0xC9F6: 0x80BE, //CJK UNIFIED IDEOGRAPH - 0xC9F7: 0x614E, //CJK UNIFIED IDEOGRAPH - 0xC9F8: 0x6E17, //CJK UNIFIED IDEOGRAPH - 0xC9F9: 0x58F0, //CJK UNIFIED IDEOGRAPH - 0xC9FA: 0x751F, //CJK UNIFIED IDEOGRAPH - 0xC9FB: 0x7525, //CJK UNIFIED IDEOGRAPH - 0xC9FC: 0x7272, //CJK UNIFIED IDEOGRAPH - 0xC9FD: 0x5347, //CJK UNIFIED IDEOGRAPH - 0xC9FE: 0x7EF3, //CJK UNIFIED IDEOGRAPH - 0xCA40: 0x8503, //CJK UNIFIED IDEOGRAPH - 0xCA41: 0x8504, //CJK UNIFIED IDEOGRAPH - 0xCA42: 0x8505, //CJK UNIFIED IDEOGRAPH - 0xCA43: 0x8506, //CJK UNIFIED IDEOGRAPH - 0xCA44: 0x8507, //CJK UNIFIED IDEOGRAPH - 0xCA45: 0x8508, //CJK UNIFIED IDEOGRAPH - 0xCA46: 0x8509, //CJK UNIFIED IDEOGRAPH - 0xCA47: 0x850A, //CJK UNIFIED IDEOGRAPH - 0xCA48: 0x850B, //CJK UNIFIED IDEOGRAPH - 0xCA49: 0x850D, //CJK UNIFIED IDEOGRAPH - 0xCA4A: 0x850E, //CJK UNIFIED IDEOGRAPH - 0xCA4B: 0x850F, //CJK UNIFIED IDEOGRAPH - 0xCA4C: 0x8510, //CJK UNIFIED IDEOGRAPH - 0xCA4D: 0x8512, //CJK UNIFIED IDEOGRAPH - 0xCA4E: 0x8514, //CJK UNIFIED IDEOGRAPH - 0xCA4F: 0x8515, //CJK UNIFIED IDEOGRAPH - 0xCA50: 0x8516, //CJK UNIFIED IDEOGRAPH - 0xCA51: 0x8518, //CJK UNIFIED IDEOGRAPH - 0xCA52: 0x8519, //CJK UNIFIED IDEOGRAPH - 0xCA53: 0x851B, //CJK UNIFIED IDEOGRAPH - 0xCA54: 0x851C, //CJK UNIFIED IDEOGRAPH - 0xCA55: 0x851D, //CJK UNIFIED IDEOGRAPH - 0xCA56: 0x851E, //CJK UNIFIED IDEOGRAPH - 0xCA57: 0x8520, //CJK UNIFIED IDEOGRAPH - 0xCA58: 0x8522, //CJK UNIFIED IDEOGRAPH - 0xCA59: 0x8523, //CJK UNIFIED IDEOGRAPH - 0xCA5A: 0x8524, //CJK UNIFIED IDEOGRAPH - 0xCA5B: 0x8525, //CJK UNIFIED IDEOGRAPH - 0xCA5C: 0x8526, //CJK UNIFIED IDEOGRAPH - 0xCA5D: 0x8527, //CJK UNIFIED IDEOGRAPH - 0xCA5E: 0x8528, //CJK UNIFIED IDEOGRAPH - 0xCA5F: 0x8529, //CJK UNIFIED IDEOGRAPH - 0xCA60: 0x852A, //CJK UNIFIED IDEOGRAPH - 0xCA61: 0x852D, //CJK UNIFIED IDEOGRAPH - 0xCA62: 0x852E, //CJK UNIFIED IDEOGRAPH - 0xCA63: 0x852F, //CJK UNIFIED IDEOGRAPH - 0xCA64: 0x8530, //CJK UNIFIED IDEOGRAPH - 0xCA65: 0x8531, //CJK UNIFIED IDEOGRAPH - 0xCA66: 0x8532, //CJK UNIFIED IDEOGRAPH - 0xCA67: 0x8533, //CJK UNIFIED IDEOGRAPH - 0xCA68: 0x8534, //CJK UNIFIED IDEOGRAPH - 0xCA69: 0x8535, //CJK UNIFIED IDEOGRAPH - 0xCA6A: 0x8536, //CJK UNIFIED IDEOGRAPH - 0xCA6B: 0x853E, //CJK UNIFIED IDEOGRAPH - 0xCA6C: 0x853F, //CJK UNIFIED IDEOGRAPH - 0xCA6D: 0x8540, //CJK UNIFIED IDEOGRAPH - 0xCA6E: 0x8541, //CJK UNIFIED IDEOGRAPH - 0xCA6F: 0x8542, //CJK UNIFIED IDEOGRAPH - 0xCA70: 0x8544, //CJK UNIFIED IDEOGRAPH - 0xCA71: 0x8545, //CJK UNIFIED IDEOGRAPH - 0xCA72: 0x8546, //CJK UNIFIED IDEOGRAPH - 0xCA73: 0x8547, //CJK UNIFIED IDEOGRAPH - 0xCA74: 0x854B, //CJK UNIFIED IDEOGRAPH - 0xCA75: 0x854C, //CJK UNIFIED IDEOGRAPH - 0xCA76: 0x854D, //CJK UNIFIED IDEOGRAPH - 0xCA77: 0x854E, //CJK UNIFIED IDEOGRAPH - 0xCA78: 0x854F, //CJK UNIFIED IDEOGRAPH - 0xCA79: 0x8550, //CJK UNIFIED IDEOGRAPH - 0xCA7A: 0x8551, //CJK UNIFIED IDEOGRAPH - 0xCA7B: 0x8552, //CJK UNIFIED IDEOGRAPH - 0xCA7C: 0x8553, //CJK UNIFIED IDEOGRAPH - 0xCA7D: 0x8554, //CJK UNIFIED IDEOGRAPH - 0xCA7E: 0x8555, //CJK UNIFIED IDEOGRAPH - 0xCA80: 0x8557, //CJK UNIFIED IDEOGRAPH - 0xCA81: 0x8558, //CJK UNIFIED IDEOGRAPH - 0xCA82: 0x855A, //CJK UNIFIED IDEOGRAPH - 0xCA83: 0x855B, //CJK UNIFIED IDEOGRAPH - 0xCA84: 0x855C, //CJK UNIFIED IDEOGRAPH - 0xCA85: 0x855D, //CJK UNIFIED IDEOGRAPH - 0xCA86: 0x855F, //CJK UNIFIED IDEOGRAPH - 0xCA87: 0x8560, //CJK UNIFIED IDEOGRAPH - 0xCA88: 0x8561, //CJK UNIFIED IDEOGRAPH - 0xCA89: 0x8562, //CJK UNIFIED IDEOGRAPH - 0xCA8A: 0x8563, //CJK UNIFIED IDEOGRAPH - 0xCA8B: 0x8565, //CJK UNIFIED IDEOGRAPH - 0xCA8C: 0x8566, //CJK UNIFIED IDEOGRAPH - 0xCA8D: 0x8567, //CJK UNIFIED IDEOGRAPH - 0xCA8E: 0x8569, //CJK UNIFIED IDEOGRAPH - 0xCA8F: 0x856A, //CJK UNIFIED IDEOGRAPH - 0xCA90: 0x856B, //CJK UNIFIED IDEOGRAPH - 0xCA91: 0x856C, //CJK UNIFIED IDEOGRAPH - 0xCA92: 0x856D, //CJK UNIFIED IDEOGRAPH - 0xCA93: 0x856E, //CJK UNIFIED IDEOGRAPH - 0xCA94: 0x856F, //CJK UNIFIED IDEOGRAPH - 0xCA95: 0x8570, //CJK UNIFIED IDEOGRAPH - 0xCA96: 0x8571, //CJK UNIFIED IDEOGRAPH - 0xCA97: 0x8573, //CJK UNIFIED IDEOGRAPH - 0xCA98: 0x8575, //CJK UNIFIED IDEOGRAPH - 0xCA99: 0x8576, //CJK UNIFIED IDEOGRAPH - 0xCA9A: 0x8577, //CJK UNIFIED IDEOGRAPH - 0xCA9B: 0x8578, //CJK UNIFIED IDEOGRAPH - 0xCA9C: 0x857C, //CJK UNIFIED IDEOGRAPH - 0xCA9D: 0x857D, //CJK UNIFIED IDEOGRAPH - 0xCA9E: 0x857F, //CJK UNIFIED IDEOGRAPH - 0xCA9F: 0x8580, //CJK UNIFIED IDEOGRAPH - 0xCAA0: 0x8581, //CJK UNIFIED IDEOGRAPH - 0xCAA1: 0x7701, //CJK UNIFIED IDEOGRAPH - 0xCAA2: 0x76DB, //CJK UNIFIED IDEOGRAPH - 0xCAA3: 0x5269, //CJK UNIFIED IDEOGRAPH - 0xCAA4: 0x80DC, //CJK UNIFIED IDEOGRAPH - 0xCAA5: 0x5723, //CJK UNIFIED IDEOGRAPH - 0xCAA6: 0x5E08, //CJK UNIFIED IDEOGRAPH - 0xCAA7: 0x5931, //CJK UNIFIED IDEOGRAPH - 0xCAA8: 0x72EE, //CJK UNIFIED IDEOGRAPH - 0xCAA9: 0x65BD, //CJK UNIFIED IDEOGRAPH - 0xCAAA: 0x6E7F, //CJK UNIFIED IDEOGRAPH - 0xCAAB: 0x8BD7, //CJK UNIFIED IDEOGRAPH - 0xCAAC: 0x5C38, //CJK UNIFIED IDEOGRAPH - 0xCAAD: 0x8671, //CJK UNIFIED IDEOGRAPH - 0xCAAE: 0x5341, //CJK UNIFIED IDEOGRAPH - 0xCAAF: 0x77F3, //CJK UNIFIED IDEOGRAPH - 0xCAB0: 0x62FE, //CJK UNIFIED IDEOGRAPH - 0xCAB1: 0x65F6, //CJK UNIFIED IDEOGRAPH - 0xCAB2: 0x4EC0, //CJK UNIFIED IDEOGRAPH - 0xCAB3: 0x98DF, //CJK UNIFIED IDEOGRAPH - 0xCAB4: 0x8680, //CJK UNIFIED IDEOGRAPH - 0xCAB5: 0x5B9E, //CJK UNIFIED IDEOGRAPH - 0xCAB6: 0x8BC6, //CJK UNIFIED IDEOGRAPH - 0xCAB7: 0x53F2, //CJK UNIFIED IDEOGRAPH - 0xCAB8: 0x77E2, //CJK UNIFIED IDEOGRAPH - 0xCAB9: 0x4F7F, //CJK UNIFIED IDEOGRAPH - 0xCABA: 0x5C4E, //CJK UNIFIED IDEOGRAPH - 0xCABB: 0x9A76, //CJK UNIFIED IDEOGRAPH - 0xCABC: 0x59CB, //CJK UNIFIED IDEOGRAPH - 0xCABD: 0x5F0F, //CJK UNIFIED IDEOGRAPH - 0xCABE: 0x793A, //CJK UNIFIED IDEOGRAPH - 0xCABF: 0x58EB, //CJK UNIFIED IDEOGRAPH - 0xCAC0: 0x4E16, //CJK UNIFIED IDEOGRAPH - 0xCAC1: 0x67FF, //CJK UNIFIED IDEOGRAPH - 0xCAC2: 0x4E8B, //CJK UNIFIED IDEOGRAPH - 0xCAC3: 0x62ED, //CJK UNIFIED IDEOGRAPH - 0xCAC4: 0x8A93, //CJK UNIFIED IDEOGRAPH - 0xCAC5: 0x901D, //CJK UNIFIED IDEOGRAPH - 0xCAC6: 0x52BF, //CJK UNIFIED IDEOGRAPH - 0xCAC7: 0x662F, //CJK UNIFIED IDEOGRAPH - 0xCAC8: 0x55DC, //CJK UNIFIED IDEOGRAPH - 0xCAC9: 0x566C, //CJK UNIFIED IDEOGRAPH - 0xCACA: 0x9002, //CJK UNIFIED IDEOGRAPH - 0xCACB: 0x4ED5, //CJK UNIFIED IDEOGRAPH - 0xCACC: 0x4F8D, //CJK UNIFIED IDEOGRAPH - 0xCACD: 0x91CA, //CJK UNIFIED IDEOGRAPH - 0xCACE: 0x9970, //CJK UNIFIED IDEOGRAPH - 0xCACF: 0x6C0F, //CJK UNIFIED IDEOGRAPH - 0xCAD0: 0x5E02, //CJK UNIFIED IDEOGRAPH - 0xCAD1: 0x6043, //CJK UNIFIED IDEOGRAPH - 0xCAD2: 0x5BA4, //CJK UNIFIED IDEOGRAPH - 0xCAD3: 0x89C6, //CJK UNIFIED IDEOGRAPH - 0xCAD4: 0x8BD5, //CJK UNIFIED IDEOGRAPH - 0xCAD5: 0x6536, //CJK UNIFIED IDEOGRAPH - 0xCAD6: 0x624B, //CJK UNIFIED IDEOGRAPH - 0xCAD7: 0x9996, //CJK UNIFIED IDEOGRAPH - 0xCAD8: 0x5B88, //CJK UNIFIED IDEOGRAPH - 0xCAD9: 0x5BFF, //CJK UNIFIED IDEOGRAPH - 0xCADA: 0x6388, //CJK UNIFIED IDEOGRAPH - 0xCADB: 0x552E, //CJK UNIFIED IDEOGRAPH - 0xCADC: 0x53D7, //CJK UNIFIED IDEOGRAPH - 0xCADD: 0x7626, //CJK UNIFIED IDEOGRAPH - 0xCADE: 0x517D, //CJK UNIFIED IDEOGRAPH - 0xCADF: 0x852C, //CJK UNIFIED IDEOGRAPH - 0xCAE0: 0x67A2, //CJK UNIFIED IDEOGRAPH - 0xCAE1: 0x68B3, //CJK UNIFIED IDEOGRAPH - 0xCAE2: 0x6B8A, //CJK UNIFIED IDEOGRAPH - 0xCAE3: 0x6292, //CJK UNIFIED IDEOGRAPH - 0xCAE4: 0x8F93, //CJK UNIFIED IDEOGRAPH - 0xCAE5: 0x53D4, //CJK UNIFIED IDEOGRAPH - 0xCAE6: 0x8212, //CJK UNIFIED IDEOGRAPH - 0xCAE7: 0x6DD1, //CJK UNIFIED IDEOGRAPH - 0xCAE8: 0x758F, //CJK UNIFIED IDEOGRAPH - 0xCAE9: 0x4E66, //CJK UNIFIED IDEOGRAPH - 0xCAEA: 0x8D4E, //CJK UNIFIED IDEOGRAPH - 0xCAEB: 0x5B70, //CJK UNIFIED IDEOGRAPH - 0xCAEC: 0x719F, //CJK UNIFIED IDEOGRAPH - 0xCAED: 0x85AF, //CJK UNIFIED IDEOGRAPH - 0xCAEE: 0x6691, //CJK UNIFIED IDEOGRAPH - 0xCAEF: 0x66D9, //CJK UNIFIED IDEOGRAPH - 0xCAF0: 0x7F72, //CJK UNIFIED IDEOGRAPH - 0xCAF1: 0x8700, //CJK UNIFIED IDEOGRAPH - 0xCAF2: 0x9ECD, //CJK UNIFIED IDEOGRAPH - 0xCAF3: 0x9F20, //CJK UNIFIED IDEOGRAPH - 0xCAF4: 0x5C5E, //CJK UNIFIED IDEOGRAPH - 0xCAF5: 0x672F, //CJK UNIFIED IDEOGRAPH - 0xCAF6: 0x8FF0, //CJK UNIFIED IDEOGRAPH - 0xCAF7: 0x6811, //CJK UNIFIED IDEOGRAPH - 0xCAF8: 0x675F, //CJK UNIFIED IDEOGRAPH - 0xCAF9: 0x620D, //CJK UNIFIED IDEOGRAPH - 0xCAFA: 0x7AD6, //CJK UNIFIED IDEOGRAPH - 0xCAFB: 0x5885, //CJK UNIFIED IDEOGRAPH - 0xCAFC: 0x5EB6, //CJK UNIFIED IDEOGRAPH - 0xCAFD: 0x6570, //CJK UNIFIED IDEOGRAPH - 0xCAFE: 0x6F31, //CJK UNIFIED IDEOGRAPH - 0xCB40: 0x8582, //CJK UNIFIED IDEOGRAPH - 0xCB41: 0x8583, //CJK UNIFIED IDEOGRAPH - 0xCB42: 0x8586, //CJK UNIFIED IDEOGRAPH - 0xCB43: 0x8588, //CJK UNIFIED IDEOGRAPH - 0xCB44: 0x8589, //CJK UNIFIED IDEOGRAPH - 0xCB45: 0x858A, //CJK UNIFIED IDEOGRAPH - 0xCB46: 0x858B, //CJK UNIFIED IDEOGRAPH - 0xCB47: 0x858C, //CJK UNIFIED IDEOGRAPH - 0xCB48: 0x858D, //CJK UNIFIED IDEOGRAPH - 0xCB49: 0x858E, //CJK UNIFIED IDEOGRAPH - 0xCB4A: 0x8590, //CJK UNIFIED IDEOGRAPH - 0xCB4B: 0x8591, //CJK UNIFIED IDEOGRAPH - 0xCB4C: 0x8592, //CJK UNIFIED IDEOGRAPH - 0xCB4D: 0x8593, //CJK UNIFIED IDEOGRAPH - 0xCB4E: 0x8594, //CJK UNIFIED IDEOGRAPH - 0xCB4F: 0x8595, //CJK UNIFIED IDEOGRAPH - 0xCB50: 0x8596, //CJK UNIFIED IDEOGRAPH - 0xCB51: 0x8597, //CJK UNIFIED IDEOGRAPH - 0xCB52: 0x8598, //CJK UNIFIED IDEOGRAPH - 0xCB53: 0x8599, //CJK UNIFIED IDEOGRAPH - 0xCB54: 0x859A, //CJK UNIFIED IDEOGRAPH - 0xCB55: 0x859D, //CJK UNIFIED IDEOGRAPH - 0xCB56: 0x859E, //CJK UNIFIED IDEOGRAPH - 0xCB57: 0x859F, //CJK UNIFIED IDEOGRAPH - 0xCB58: 0x85A0, //CJK UNIFIED IDEOGRAPH - 0xCB59: 0x85A1, //CJK UNIFIED IDEOGRAPH - 0xCB5A: 0x85A2, //CJK UNIFIED IDEOGRAPH - 0xCB5B: 0x85A3, //CJK UNIFIED IDEOGRAPH - 0xCB5C: 0x85A5, //CJK UNIFIED IDEOGRAPH - 0xCB5D: 0x85A6, //CJK UNIFIED IDEOGRAPH - 0xCB5E: 0x85A7, //CJK UNIFIED IDEOGRAPH - 0xCB5F: 0x85A9, //CJK UNIFIED IDEOGRAPH - 0xCB60: 0x85AB, //CJK UNIFIED IDEOGRAPH - 0xCB61: 0x85AC, //CJK UNIFIED IDEOGRAPH - 0xCB62: 0x85AD, //CJK UNIFIED IDEOGRAPH - 0xCB63: 0x85B1, //CJK UNIFIED IDEOGRAPH - 0xCB64: 0x85B2, //CJK UNIFIED IDEOGRAPH - 0xCB65: 0x85B3, //CJK UNIFIED IDEOGRAPH - 0xCB66: 0x85B4, //CJK UNIFIED IDEOGRAPH - 0xCB67: 0x85B5, //CJK UNIFIED IDEOGRAPH - 0xCB68: 0x85B6, //CJK UNIFIED IDEOGRAPH - 0xCB69: 0x85B8, //CJK UNIFIED IDEOGRAPH - 0xCB6A: 0x85BA, //CJK UNIFIED IDEOGRAPH - 0xCB6B: 0x85BB, //CJK UNIFIED IDEOGRAPH - 0xCB6C: 0x85BC, //CJK UNIFIED IDEOGRAPH - 0xCB6D: 0x85BD, //CJK UNIFIED IDEOGRAPH - 0xCB6E: 0x85BE, //CJK UNIFIED IDEOGRAPH - 0xCB6F: 0x85BF, //CJK UNIFIED IDEOGRAPH - 0xCB70: 0x85C0, //CJK UNIFIED IDEOGRAPH - 0xCB71: 0x85C2, //CJK UNIFIED IDEOGRAPH - 0xCB72: 0x85C3, //CJK UNIFIED IDEOGRAPH - 0xCB73: 0x85C4, //CJK UNIFIED IDEOGRAPH - 0xCB74: 0x85C5, //CJK UNIFIED IDEOGRAPH - 0xCB75: 0x85C6, //CJK UNIFIED IDEOGRAPH - 0xCB76: 0x85C7, //CJK UNIFIED IDEOGRAPH - 0xCB77: 0x85C8, //CJK UNIFIED IDEOGRAPH - 0xCB78: 0x85CA, //CJK UNIFIED IDEOGRAPH - 0xCB79: 0x85CB, //CJK UNIFIED IDEOGRAPH - 0xCB7A: 0x85CC, //CJK UNIFIED IDEOGRAPH - 0xCB7B: 0x85CD, //CJK UNIFIED IDEOGRAPH - 0xCB7C: 0x85CE, //CJK UNIFIED IDEOGRAPH - 0xCB7D: 0x85D1, //CJK UNIFIED IDEOGRAPH - 0xCB7E: 0x85D2, //CJK UNIFIED IDEOGRAPH - 0xCB80: 0x85D4, //CJK UNIFIED IDEOGRAPH - 0xCB81: 0x85D6, //CJK UNIFIED IDEOGRAPH - 0xCB82: 0x85D7, //CJK UNIFIED IDEOGRAPH - 0xCB83: 0x85D8, //CJK UNIFIED IDEOGRAPH - 0xCB84: 0x85D9, //CJK UNIFIED IDEOGRAPH - 0xCB85: 0x85DA, //CJK UNIFIED IDEOGRAPH - 0xCB86: 0x85DB, //CJK UNIFIED IDEOGRAPH - 0xCB87: 0x85DD, //CJK UNIFIED IDEOGRAPH - 0xCB88: 0x85DE, //CJK UNIFIED IDEOGRAPH - 0xCB89: 0x85DF, //CJK UNIFIED IDEOGRAPH - 0xCB8A: 0x85E0, //CJK UNIFIED IDEOGRAPH - 0xCB8B: 0x85E1, //CJK UNIFIED IDEOGRAPH - 0xCB8C: 0x85E2, //CJK UNIFIED IDEOGRAPH - 0xCB8D: 0x85E3, //CJK UNIFIED IDEOGRAPH - 0xCB8E: 0x85E5, //CJK UNIFIED IDEOGRAPH - 0xCB8F: 0x85E6, //CJK UNIFIED IDEOGRAPH - 0xCB90: 0x85E7, //CJK UNIFIED IDEOGRAPH - 0xCB91: 0x85E8, //CJK UNIFIED IDEOGRAPH - 0xCB92: 0x85EA, //CJK UNIFIED IDEOGRAPH - 0xCB93: 0x85EB, //CJK UNIFIED IDEOGRAPH - 0xCB94: 0x85EC, //CJK UNIFIED IDEOGRAPH - 0xCB95: 0x85ED, //CJK UNIFIED IDEOGRAPH - 0xCB96: 0x85EE, //CJK UNIFIED IDEOGRAPH - 0xCB97: 0x85EF, //CJK UNIFIED IDEOGRAPH - 0xCB98: 0x85F0, //CJK UNIFIED IDEOGRAPH - 0xCB99: 0x85F1, //CJK UNIFIED IDEOGRAPH - 0xCB9A: 0x85F2, //CJK UNIFIED IDEOGRAPH - 0xCB9B: 0x85F3, //CJK UNIFIED IDEOGRAPH - 0xCB9C: 0x85F4, //CJK UNIFIED IDEOGRAPH - 0xCB9D: 0x85F5, //CJK UNIFIED IDEOGRAPH - 0xCB9E: 0x85F6, //CJK UNIFIED IDEOGRAPH - 0xCB9F: 0x85F7, //CJK UNIFIED IDEOGRAPH - 0xCBA0: 0x85F8, //CJK UNIFIED IDEOGRAPH - 0xCBA1: 0x6055, //CJK UNIFIED IDEOGRAPH - 0xCBA2: 0x5237, //CJK UNIFIED IDEOGRAPH - 0xCBA3: 0x800D, //CJK UNIFIED IDEOGRAPH - 0xCBA4: 0x6454, //CJK UNIFIED IDEOGRAPH - 0xCBA5: 0x8870, //CJK UNIFIED IDEOGRAPH - 0xCBA6: 0x7529, //CJK UNIFIED IDEOGRAPH - 0xCBA7: 0x5E05, //CJK UNIFIED IDEOGRAPH - 0xCBA8: 0x6813, //CJK UNIFIED IDEOGRAPH - 0xCBA9: 0x62F4, //CJK UNIFIED IDEOGRAPH - 0xCBAA: 0x971C, //CJK UNIFIED IDEOGRAPH - 0xCBAB: 0x53CC, //CJK UNIFIED IDEOGRAPH - 0xCBAC: 0x723D, //CJK UNIFIED IDEOGRAPH - 0xCBAD: 0x8C01, //CJK UNIFIED IDEOGRAPH - 0xCBAE: 0x6C34, //CJK UNIFIED IDEOGRAPH - 0xCBAF: 0x7761, //CJK UNIFIED IDEOGRAPH - 0xCBB0: 0x7A0E, //CJK UNIFIED IDEOGRAPH - 0xCBB1: 0x542E, //CJK UNIFIED IDEOGRAPH - 0xCBB2: 0x77AC, //CJK UNIFIED IDEOGRAPH - 0xCBB3: 0x987A, //CJK UNIFIED IDEOGRAPH - 0xCBB4: 0x821C, //CJK UNIFIED IDEOGRAPH - 0xCBB5: 0x8BF4, //CJK UNIFIED IDEOGRAPH - 0xCBB6: 0x7855, //CJK UNIFIED IDEOGRAPH - 0xCBB7: 0x6714, //CJK UNIFIED IDEOGRAPH - 0xCBB8: 0x70C1, //CJK UNIFIED IDEOGRAPH - 0xCBB9: 0x65AF, //CJK UNIFIED IDEOGRAPH - 0xCBBA: 0x6495, //CJK UNIFIED IDEOGRAPH - 0xCBBB: 0x5636, //CJK UNIFIED IDEOGRAPH - 0xCBBC: 0x601D, //CJK UNIFIED IDEOGRAPH - 0xCBBD: 0x79C1, //CJK UNIFIED IDEOGRAPH - 0xCBBE: 0x53F8, //CJK UNIFIED IDEOGRAPH - 0xCBBF: 0x4E1D, //CJK UNIFIED IDEOGRAPH - 0xCBC0: 0x6B7B, //CJK UNIFIED IDEOGRAPH - 0xCBC1: 0x8086, //CJK UNIFIED IDEOGRAPH - 0xCBC2: 0x5BFA, //CJK UNIFIED IDEOGRAPH - 0xCBC3: 0x55E3, //CJK UNIFIED IDEOGRAPH - 0xCBC4: 0x56DB, //CJK UNIFIED IDEOGRAPH - 0xCBC5: 0x4F3A, //CJK UNIFIED IDEOGRAPH - 0xCBC6: 0x4F3C, //CJK UNIFIED IDEOGRAPH - 0xCBC7: 0x9972, //CJK UNIFIED IDEOGRAPH - 0xCBC8: 0x5DF3, //CJK UNIFIED IDEOGRAPH - 0xCBC9: 0x677E, //CJK UNIFIED IDEOGRAPH - 0xCBCA: 0x8038, //CJK UNIFIED IDEOGRAPH - 0xCBCB: 0x6002, //CJK UNIFIED IDEOGRAPH - 0xCBCC: 0x9882, //CJK UNIFIED IDEOGRAPH - 0xCBCD: 0x9001, //CJK UNIFIED IDEOGRAPH - 0xCBCE: 0x5B8B, //CJK UNIFIED IDEOGRAPH - 0xCBCF: 0x8BBC, //CJK UNIFIED IDEOGRAPH - 0xCBD0: 0x8BF5, //CJK UNIFIED IDEOGRAPH - 0xCBD1: 0x641C, //CJK UNIFIED IDEOGRAPH - 0xCBD2: 0x8258, //CJK UNIFIED IDEOGRAPH - 0xCBD3: 0x64DE, //CJK UNIFIED IDEOGRAPH - 0xCBD4: 0x55FD, //CJK UNIFIED IDEOGRAPH - 0xCBD5: 0x82CF, //CJK UNIFIED IDEOGRAPH - 0xCBD6: 0x9165, //CJK UNIFIED IDEOGRAPH - 0xCBD7: 0x4FD7, //CJK UNIFIED IDEOGRAPH - 0xCBD8: 0x7D20, //CJK UNIFIED IDEOGRAPH - 0xCBD9: 0x901F, //CJK UNIFIED IDEOGRAPH - 0xCBDA: 0x7C9F, //CJK UNIFIED IDEOGRAPH - 0xCBDB: 0x50F3, //CJK UNIFIED IDEOGRAPH - 0xCBDC: 0x5851, //CJK UNIFIED IDEOGRAPH - 0xCBDD: 0x6EAF, //CJK UNIFIED IDEOGRAPH - 0xCBDE: 0x5BBF, //CJK UNIFIED IDEOGRAPH - 0xCBDF: 0x8BC9, //CJK UNIFIED IDEOGRAPH - 0xCBE0: 0x8083, //CJK UNIFIED IDEOGRAPH - 0xCBE1: 0x9178, //CJK UNIFIED IDEOGRAPH - 0xCBE2: 0x849C, //CJK UNIFIED IDEOGRAPH - 0xCBE3: 0x7B97, //CJK UNIFIED IDEOGRAPH - 0xCBE4: 0x867D, //CJK UNIFIED IDEOGRAPH - 0xCBE5: 0x968B, //CJK UNIFIED IDEOGRAPH - 0xCBE6: 0x968F, //CJK UNIFIED IDEOGRAPH - 0xCBE7: 0x7EE5, //CJK UNIFIED IDEOGRAPH - 0xCBE8: 0x9AD3, //CJK UNIFIED IDEOGRAPH - 0xCBE9: 0x788E, //CJK UNIFIED IDEOGRAPH - 0xCBEA: 0x5C81, //CJK UNIFIED IDEOGRAPH - 0xCBEB: 0x7A57, //CJK UNIFIED IDEOGRAPH - 0xCBEC: 0x9042, //CJK UNIFIED IDEOGRAPH - 0xCBED: 0x96A7, //CJK UNIFIED IDEOGRAPH - 0xCBEE: 0x795F, //CJK UNIFIED IDEOGRAPH - 0xCBEF: 0x5B59, //CJK UNIFIED IDEOGRAPH - 0xCBF0: 0x635F, //CJK UNIFIED IDEOGRAPH - 0xCBF1: 0x7B0B, //CJK UNIFIED IDEOGRAPH - 0xCBF2: 0x84D1, //CJK UNIFIED IDEOGRAPH - 0xCBF3: 0x68AD, //CJK UNIFIED IDEOGRAPH - 0xCBF4: 0x5506, //CJK UNIFIED IDEOGRAPH - 0xCBF5: 0x7F29, //CJK UNIFIED IDEOGRAPH - 0xCBF6: 0x7410, //CJK UNIFIED IDEOGRAPH - 0xCBF7: 0x7D22, //CJK UNIFIED IDEOGRAPH - 0xCBF8: 0x9501, //CJK UNIFIED IDEOGRAPH - 0xCBF9: 0x6240, //CJK UNIFIED IDEOGRAPH - 0xCBFA: 0x584C, //CJK UNIFIED IDEOGRAPH - 0xCBFB: 0x4ED6, //CJK UNIFIED IDEOGRAPH - 0xCBFC: 0x5B83, //CJK UNIFIED IDEOGRAPH - 0xCBFD: 0x5979, //CJK UNIFIED IDEOGRAPH - 0xCBFE: 0x5854, //CJK UNIFIED IDEOGRAPH - 0xCC40: 0x85F9, //CJK UNIFIED IDEOGRAPH - 0xCC41: 0x85FA, //CJK UNIFIED IDEOGRAPH - 0xCC42: 0x85FC, //CJK UNIFIED IDEOGRAPH - 0xCC43: 0x85FD, //CJK UNIFIED IDEOGRAPH - 0xCC44: 0x85FE, //CJK UNIFIED IDEOGRAPH - 0xCC45: 0x8600, //CJK UNIFIED IDEOGRAPH - 0xCC46: 0x8601, //CJK UNIFIED IDEOGRAPH - 0xCC47: 0x8602, //CJK UNIFIED IDEOGRAPH - 0xCC48: 0x8603, //CJK UNIFIED IDEOGRAPH - 0xCC49: 0x8604, //CJK UNIFIED IDEOGRAPH - 0xCC4A: 0x8606, //CJK UNIFIED IDEOGRAPH - 0xCC4B: 0x8607, //CJK UNIFIED IDEOGRAPH - 0xCC4C: 0x8608, //CJK UNIFIED IDEOGRAPH - 0xCC4D: 0x8609, //CJK UNIFIED IDEOGRAPH - 0xCC4E: 0x860A, //CJK UNIFIED IDEOGRAPH - 0xCC4F: 0x860B, //CJK UNIFIED IDEOGRAPH - 0xCC50: 0x860C, //CJK UNIFIED IDEOGRAPH - 0xCC51: 0x860D, //CJK UNIFIED IDEOGRAPH - 0xCC52: 0x860E, //CJK UNIFIED IDEOGRAPH - 0xCC53: 0x860F, //CJK UNIFIED IDEOGRAPH - 0xCC54: 0x8610, //CJK UNIFIED IDEOGRAPH - 0xCC55: 0x8612, //CJK UNIFIED IDEOGRAPH - 0xCC56: 0x8613, //CJK UNIFIED IDEOGRAPH - 0xCC57: 0x8614, //CJK UNIFIED IDEOGRAPH - 0xCC58: 0x8615, //CJK UNIFIED IDEOGRAPH - 0xCC59: 0x8617, //CJK UNIFIED IDEOGRAPH - 0xCC5A: 0x8618, //CJK UNIFIED IDEOGRAPH - 0xCC5B: 0x8619, //CJK UNIFIED IDEOGRAPH - 0xCC5C: 0x861A, //CJK UNIFIED IDEOGRAPH - 0xCC5D: 0x861B, //CJK UNIFIED IDEOGRAPH - 0xCC5E: 0x861C, //CJK UNIFIED IDEOGRAPH - 0xCC5F: 0x861D, //CJK UNIFIED IDEOGRAPH - 0xCC60: 0x861E, //CJK UNIFIED IDEOGRAPH - 0xCC61: 0x861F, //CJK UNIFIED IDEOGRAPH - 0xCC62: 0x8620, //CJK UNIFIED IDEOGRAPH - 0xCC63: 0x8621, //CJK UNIFIED IDEOGRAPH - 0xCC64: 0x8622, //CJK UNIFIED IDEOGRAPH - 0xCC65: 0x8623, //CJK UNIFIED IDEOGRAPH - 0xCC66: 0x8624, //CJK UNIFIED IDEOGRAPH - 0xCC67: 0x8625, //CJK UNIFIED IDEOGRAPH - 0xCC68: 0x8626, //CJK UNIFIED IDEOGRAPH - 0xCC69: 0x8628, //CJK UNIFIED IDEOGRAPH - 0xCC6A: 0x862A, //CJK UNIFIED IDEOGRAPH - 0xCC6B: 0x862B, //CJK UNIFIED IDEOGRAPH - 0xCC6C: 0x862C, //CJK UNIFIED IDEOGRAPH - 0xCC6D: 0x862D, //CJK UNIFIED IDEOGRAPH - 0xCC6E: 0x862E, //CJK UNIFIED IDEOGRAPH - 0xCC6F: 0x862F, //CJK UNIFIED IDEOGRAPH - 0xCC70: 0x8630, //CJK UNIFIED IDEOGRAPH - 0xCC71: 0x8631, //CJK UNIFIED IDEOGRAPH - 0xCC72: 0x8632, //CJK UNIFIED IDEOGRAPH - 0xCC73: 0x8633, //CJK UNIFIED IDEOGRAPH - 0xCC74: 0x8634, //CJK UNIFIED IDEOGRAPH - 0xCC75: 0x8635, //CJK UNIFIED IDEOGRAPH - 0xCC76: 0x8636, //CJK UNIFIED IDEOGRAPH - 0xCC77: 0x8637, //CJK UNIFIED IDEOGRAPH - 0xCC78: 0x8639, //CJK UNIFIED IDEOGRAPH - 0xCC79: 0x863A, //CJK UNIFIED IDEOGRAPH - 0xCC7A: 0x863B, //CJK UNIFIED IDEOGRAPH - 0xCC7B: 0x863D, //CJK UNIFIED IDEOGRAPH - 0xCC7C: 0x863E, //CJK UNIFIED IDEOGRAPH - 0xCC7D: 0x863F, //CJK UNIFIED IDEOGRAPH - 0xCC7E: 0x8640, //CJK UNIFIED IDEOGRAPH - 0xCC80: 0x8641, //CJK UNIFIED IDEOGRAPH - 0xCC81: 0x8642, //CJK UNIFIED IDEOGRAPH - 0xCC82: 0x8643, //CJK UNIFIED IDEOGRAPH - 0xCC83: 0x8644, //CJK UNIFIED IDEOGRAPH - 0xCC84: 0x8645, //CJK UNIFIED IDEOGRAPH - 0xCC85: 0x8646, //CJK UNIFIED IDEOGRAPH - 0xCC86: 0x8647, //CJK UNIFIED IDEOGRAPH - 0xCC87: 0x8648, //CJK UNIFIED IDEOGRAPH - 0xCC88: 0x8649, //CJK UNIFIED IDEOGRAPH - 0xCC89: 0x864A, //CJK UNIFIED IDEOGRAPH - 0xCC8A: 0x864B, //CJK UNIFIED IDEOGRAPH - 0xCC8B: 0x864C, //CJK UNIFIED IDEOGRAPH - 0xCC8C: 0x8652, //CJK UNIFIED IDEOGRAPH - 0xCC8D: 0x8653, //CJK UNIFIED IDEOGRAPH - 0xCC8E: 0x8655, //CJK UNIFIED IDEOGRAPH - 0xCC8F: 0x8656, //CJK UNIFIED IDEOGRAPH - 0xCC90: 0x8657, //CJK UNIFIED IDEOGRAPH - 0xCC91: 0x8658, //CJK UNIFIED IDEOGRAPH - 0xCC92: 0x8659, //CJK UNIFIED IDEOGRAPH - 0xCC93: 0x865B, //CJK UNIFIED IDEOGRAPH - 0xCC94: 0x865C, //CJK UNIFIED IDEOGRAPH - 0xCC95: 0x865D, //CJK UNIFIED IDEOGRAPH - 0xCC96: 0x865F, //CJK UNIFIED IDEOGRAPH - 0xCC97: 0x8660, //CJK UNIFIED IDEOGRAPH - 0xCC98: 0x8661, //CJK UNIFIED IDEOGRAPH - 0xCC99: 0x8663, //CJK UNIFIED IDEOGRAPH - 0xCC9A: 0x8664, //CJK UNIFIED IDEOGRAPH - 0xCC9B: 0x8665, //CJK UNIFIED IDEOGRAPH - 0xCC9C: 0x8666, //CJK UNIFIED IDEOGRAPH - 0xCC9D: 0x8667, //CJK UNIFIED IDEOGRAPH - 0xCC9E: 0x8668, //CJK UNIFIED IDEOGRAPH - 0xCC9F: 0x8669, //CJK UNIFIED IDEOGRAPH - 0xCCA0: 0x866A, //CJK UNIFIED IDEOGRAPH - 0xCCA1: 0x736D, //CJK UNIFIED IDEOGRAPH - 0xCCA2: 0x631E, //CJK UNIFIED IDEOGRAPH - 0xCCA3: 0x8E4B, //CJK UNIFIED IDEOGRAPH - 0xCCA4: 0x8E0F, //CJK UNIFIED IDEOGRAPH - 0xCCA5: 0x80CE, //CJK UNIFIED IDEOGRAPH - 0xCCA6: 0x82D4, //CJK UNIFIED IDEOGRAPH - 0xCCA7: 0x62AC, //CJK UNIFIED IDEOGRAPH - 0xCCA8: 0x53F0, //CJK UNIFIED IDEOGRAPH - 0xCCA9: 0x6CF0, //CJK UNIFIED IDEOGRAPH - 0xCCAA: 0x915E, //CJK UNIFIED IDEOGRAPH - 0xCCAB: 0x592A, //CJK UNIFIED IDEOGRAPH - 0xCCAC: 0x6001, //CJK UNIFIED IDEOGRAPH - 0xCCAD: 0x6C70, //CJK UNIFIED IDEOGRAPH - 0xCCAE: 0x574D, //CJK UNIFIED IDEOGRAPH - 0xCCAF: 0x644A, //CJK UNIFIED IDEOGRAPH - 0xCCB0: 0x8D2A, //CJK UNIFIED IDEOGRAPH - 0xCCB1: 0x762B, //CJK UNIFIED IDEOGRAPH - 0xCCB2: 0x6EE9, //CJK UNIFIED IDEOGRAPH - 0xCCB3: 0x575B, //CJK UNIFIED IDEOGRAPH - 0xCCB4: 0x6A80, //CJK UNIFIED IDEOGRAPH - 0xCCB5: 0x75F0, //CJK UNIFIED IDEOGRAPH - 0xCCB6: 0x6F6D, //CJK UNIFIED IDEOGRAPH - 0xCCB7: 0x8C2D, //CJK UNIFIED IDEOGRAPH - 0xCCB8: 0x8C08, //CJK UNIFIED IDEOGRAPH - 0xCCB9: 0x5766, //CJK UNIFIED IDEOGRAPH - 0xCCBA: 0x6BEF, //CJK UNIFIED IDEOGRAPH - 0xCCBB: 0x8892, //CJK UNIFIED IDEOGRAPH - 0xCCBC: 0x78B3, //CJK UNIFIED IDEOGRAPH - 0xCCBD: 0x63A2, //CJK UNIFIED IDEOGRAPH - 0xCCBE: 0x53F9, //CJK UNIFIED IDEOGRAPH - 0xCCBF: 0x70AD, //CJK UNIFIED IDEOGRAPH - 0xCCC0: 0x6C64, //CJK UNIFIED IDEOGRAPH - 0xCCC1: 0x5858, //CJK UNIFIED IDEOGRAPH - 0xCCC2: 0x642A, //CJK UNIFIED IDEOGRAPH - 0xCCC3: 0x5802, //CJK UNIFIED IDEOGRAPH - 0xCCC4: 0x68E0, //CJK UNIFIED IDEOGRAPH - 0xCCC5: 0x819B, //CJK UNIFIED IDEOGRAPH - 0xCCC6: 0x5510, //CJK UNIFIED IDEOGRAPH - 0xCCC7: 0x7CD6, //CJK UNIFIED IDEOGRAPH - 0xCCC8: 0x5018, //CJK UNIFIED IDEOGRAPH - 0xCCC9: 0x8EBA, //CJK UNIFIED IDEOGRAPH - 0xCCCA: 0x6DCC, //CJK UNIFIED IDEOGRAPH - 0xCCCB: 0x8D9F, //CJK UNIFIED IDEOGRAPH - 0xCCCC: 0x70EB, //CJK UNIFIED IDEOGRAPH - 0xCCCD: 0x638F, //CJK UNIFIED IDEOGRAPH - 0xCCCE: 0x6D9B, //CJK UNIFIED IDEOGRAPH - 0xCCCF: 0x6ED4, //CJK UNIFIED IDEOGRAPH - 0xCCD0: 0x7EE6, //CJK UNIFIED IDEOGRAPH - 0xCCD1: 0x8404, //CJK UNIFIED IDEOGRAPH - 0xCCD2: 0x6843, //CJK UNIFIED IDEOGRAPH - 0xCCD3: 0x9003, //CJK UNIFIED IDEOGRAPH - 0xCCD4: 0x6DD8, //CJK UNIFIED IDEOGRAPH - 0xCCD5: 0x9676, //CJK UNIFIED IDEOGRAPH - 0xCCD6: 0x8BA8, //CJK UNIFIED IDEOGRAPH - 0xCCD7: 0x5957, //CJK UNIFIED IDEOGRAPH - 0xCCD8: 0x7279, //CJK UNIFIED IDEOGRAPH - 0xCCD9: 0x85E4, //CJK UNIFIED IDEOGRAPH - 0xCCDA: 0x817E, //CJK UNIFIED IDEOGRAPH - 0xCCDB: 0x75BC, //CJK UNIFIED IDEOGRAPH - 0xCCDC: 0x8A8A, //CJK UNIFIED IDEOGRAPH - 0xCCDD: 0x68AF, //CJK UNIFIED IDEOGRAPH - 0xCCDE: 0x5254, //CJK UNIFIED IDEOGRAPH - 0xCCDF: 0x8E22, //CJK UNIFIED IDEOGRAPH - 0xCCE0: 0x9511, //CJK UNIFIED IDEOGRAPH - 0xCCE1: 0x63D0, //CJK UNIFIED IDEOGRAPH - 0xCCE2: 0x9898, //CJK UNIFIED IDEOGRAPH - 0xCCE3: 0x8E44, //CJK UNIFIED IDEOGRAPH - 0xCCE4: 0x557C, //CJK UNIFIED IDEOGRAPH - 0xCCE5: 0x4F53, //CJK UNIFIED IDEOGRAPH - 0xCCE6: 0x66FF, //CJK UNIFIED IDEOGRAPH - 0xCCE7: 0x568F, //CJK UNIFIED IDEOGRAPH - 0xCCE8: 0x60D5, //CJK UNIFIED IDEOGRAPH - 0xCCE9: 0x6D95, //CJK UNIFIED IDEOGRAPH - 0xCCEA: 0x5243, //CJK UNIFIED IDEOGRAPH - 0xCCEB: 0x5C49, //CJK UNIFIED IDEOGRAPH - 0xCCEC: 0x5929, //CJK UNIFIED IDEOGRAPH - 0xCCED: 0x6DFB, //CJK UNIFIED IDEOGRAPH - 0xCCEE: 0x586B, //CJK UNIFIED IDEOGRAPH - 0xCCEF: 0x7530, //CJK UNIFIED IDEOGRAPH - 0xCCF0: 0x751C, //CJK UNIFIED IDEOGRAPH - 0xCCF1: 0x606C, //CJK UNIFIED IDEOGRAPH - 0xCCF2: 0x8214, //CJK UNIFIED IDEOGRAPH - 0xCCF3: 0x8146, //CJK UNIFIED IDEOGRAPH - 0xCCF4: 0x6311, //CJK UNIFIED IDEOGRAPH - 0xCCF5: 0x6761, //CJK UNIFIED IDEOGRAPH - 0xCCF6: 0x8FE2, //CJK UNIFIED IDEOGRAPH - 0xCCF7: 0x773A, //CJK UNIFIED IDEOGRAPH - 0xCCF8: 0x8DF3, //CJK UNIFIED IDEOGRAPH - 0xCCF9: 0x8D34, //CJK UNIFIED IDEOGRAPH - 0xCCFA: 0x94C1, //CJK UNIFIED IDEOGRAPH - 0xCCFB: 0x5E16, //CJK UNIFIED IDEOGRAPH - 0xCCFC: 0x5385, //CJK UNIFIED IDEOGRAPH - 0xCCFD: 0x542C, //CJK UNIFIED IDEOGRAPH - 0xCCFE: 0x70C3, //CJK UNIFIED IDEOGRAPH - 0xCD40: 0x866D, //CJK UNIFIED IDEOGRAPH - 0xCD41: 0x866F, //CJK UNIFIED IDEOGRAPH - 0xCD42: 0x8670, //CJK UNIFIED IDEOGRAPH - 0xCD43: 0x8672, //CJK UNIFIED IDEOGRAPH - 0xCD44: 0x8673, //CJK UNIFIED IDEOGRAPH - 0xCD45: 0x8674, //CJK UNIFIED IDEOGRAPH - 0xCD46: 0x8675, //CJK UNIFIED IDEOGRAPH - 0xCD47: 0x8676, //CJK UNIFIED IDEOGRAPH - 0xCD48: 0x8677, //CJK UNIFIED IDEOGRAPH - 0xCD49: 0x8678, //CJK UNIFIED IDEOGRAPH - 0xCD4A: 0x8683, //CJK UNIFIED IDEOGRAPH - 0xCD4B: 0x8684, //CJK UNIFIED IDEOGRAPH - 0xCD4C: 0x8685, //CJK UNIFIED IDEOGRAPH - 0xCD4D: 0x8686, //CJK UNIFIED IDEOGRAPH - 0xCD4E: 0x8687, //CJK UNIFIED IDEOGRAPH - 0xCD4F: 0x8688, //CJK UNIFIED IDEOGRAPH - 0xCD50: 0x8689, //CJK UNIFIED IDEOGRAPH - 0xCD51: 0x868E, //CJK UNIFIED IDEOGRAPH - 0xCD52: 0x868F, //CJK UNIFIED IDEOGRAPH - 0xCD53: 0x8690, //CJK UNIFIED IDEOGRAPH - 0xCD54: 0x8691, //CJK UNIFIED IDEOGRAPH - 0xCD55: 0x8692, //CJK UNIFIED IDEOGRAPH - 0xCD56: 0x8694, //CJK UNIFIED IDEOGRAPH - 0xCD57: 0x8696, //CJK UNIFIED IDEOGRAPH - 0xCD58: 0x8697, //CJK UNIFIED IDEOGRAPH - 0xCD59: 0x8698, //CJK UNIFIED IDEOGRAPH - 0xCD5A: 0x8699, //CJK UNIFIED IDEOGRAPH - 0xCD5B: 0x869A, //CJK UNIFIED IDEOGRAPH - 0xCD5C: 0x869B, //CJK UNIFIED IDEOGRAPH - 0xCD5D: 0x869E, //CJK UNIFIED IDEOGRAPH - 0xCD5E: 0x869F, //CJK UNIFIED IDEOGRAPH - 0xCD5F: 0x86A0, //CJK UNIFIED IDEOGRAPH - 0xCD60: 0x86A1, //CJK UNIFIED IDEOGRAPH - 0xCD61: 0x86A2, //CJK UNIFIED IDEOGRAPH - 0xCD62: 0x86A5, //CJK UNIFIED IDEOGRAPH - 0xCD63: 0x86A6, //CJK UNIFIED IDEOGRAPH - 0xCD64: 0x86AB, //CJK UNIFIED IDEOGRAPH - 0xCD65: 0x86AD, //CJK UNIFIED IDEOGRAPH - 0xCD66: 0x86AE, //CJK UNIFIED IDEOGRAPH - 0xCD67: 0x86B2, //CJK UNIFIED IDEOGRAPH - 0xCD68: 0x86B3, //CJK UNIFIED IDEOGRAPH - 0xCD69: 0x86B7, //CJK UNIFIED IDEOGRAPH - 0xCD6A: 0x86B8, //CJK UNIFIED IDEOGRAPH - 0xCD6B: 0x86B9, //CJK UNIFIED IDEOGRAPH - 0xCD6C: 0x86BB, //CJK UNIFIED IDEOGRAPH - 0xCD6D: 0x86BC, //CJK UNIFIED IDEOGRAPH - 0xCD6E: 0x86BD, //CJK UNIFIED IDEOGRAPH - 0xCD6F: 0x86BE, //CJK UNIFIED IDEOGRAPH - 0xCD70: 0x86BF, //CJK UNIFIED IDEOGRAPH - 0xCD71: 0x86C1, //CJK UNIFIED IDEOGRAPH - 0xCD72: 0x86C2, //CJK UNIFIED IDEOGRAPH - 0xCD73: 0x86C3, //CJK UNIFIED IDEOGRAPH - 0xCD74: 0x86C5, //CJK UNIFIED IDEOGRAPH - 0xCD75: 0x86C8, //CJK UNIFIED IDEOGRAPH - 0xCD76: 0x86CC, //CJK UNIFIED IDEOGRAPH - 0xCD77: 0x86CD, //CJK UNIFIED IDEOGRAPH - 0xCD78: 0x86D2, //CJK UNIFIED IDEOGRAPH - 0xCD79: 0x86D3, //CJK UNIFIED IDEOGRAPH - 0xCD7A: 0x86D5, //CJK UNIFIED IDEOGRAPH - 0xCD7B: 0x86D6, //CJK UNIFIED IDEOGRAPH - 0xCD7C: 0x86D7, //CJK UNIFIED IDEOGRAPH - 0xCD7D: 0x86DA, //CJK UNIFIED IDEOGRAPH - 0xCD7E: 0x86DC, //CJK UNIFIED IDEOGRAPH - 0xCD80: 0x86DD, //CJK UNIFIED IDEOGRAPH - 0xCD81: 0x86E0, //CJK UNIFIED IDEOGRAPH - 0xCD82: 0x86E1, //CJK UNIFIED IDEOGRAPH - 0xCD83: 0x86E2, //CJK UNIFIED IDEOGRAPH - 0xCD84: 0x86E3, //CJK UNIFIED IDEOGRAPH - 0xCD85: 0x86E5, //CJK UNIFIED IDEOGRAPH - 0xCD86: 0x86E6, //CJK UNIFIED IDEOGRAPH - 0xCD87: 0x86E7, //CJK UNIFIED IDEOGRAPH - 0xCD88: 0x86E8, //CJK UNIFIED IDEOGRAPH - 0xCD89: 0x86EA, //CJK UNIFIED IDEOGRAPH - 0xCD8A: 0x86EB, //CJK UNIFIED IDEOGRAPH - 0xCD8B: 0x86EC, //CJK UNIFIED IDEOGRAPH - 0xCD8C: 0x86EF, //CJK UNIFIED IDEOGRAPH - 0xCD8D: 0x86F5, //CJK UNIFIED IDEOGRAPH - 0xCD8E: 0x86F6, //CJK UNIFIED IDEOGRAPH - 0xCD8F: 0x86F7, //CJK UNIFIED IDEOGRAPH - 0xCD90: 0x86FA, //CJK UNIFIED IDEOGRAPH - 0xCD91: 0x86FB, //CJK UNIFIED IDEOGRAPH - 0xCD92: 0x86FC, //CJK UNIFIED IDEOGRAPH - 0xCD93: 0x86FD, //CJK UNIFIED IDEOGRAPH - 0xCD94: 0x86FF, //CJK UNIFIED IDEOGRAPH - 0xCD95: 0x8701, //CJK UNIFIED IDEOGRAPH - 0xCD96: 0x8704, //CJK UNIFIED IDEOGRAPH - 0xCD97: 0x8705, //CJK UNIFIED IDEOGRAPH - 0xCD98: 0x8706, //CJK UNIFIED IDEOGRAPH - 0xCD99: 0x870B, //CJK UNIFIED IDEOGRAPH - 0xCD9A: 0x870C, //CJK UNIFIED IDEOGRAPH - 0xCD9B: 0x870E, //CJK UNIFIED IDEOGRAPH - 0xCD9C: 0x870F, //CJK UNIFIED IDEOGRAPH - 0xCD9D: 0x8710, //CJK UNIFIED IDEOGRAPH - 0xCD9E: 0x8711, //CJK UNIFIED IDEOGRAPH - 0xCD9F: 0x8714, //CJK UNIFIED IDEOGRAPH - 0xCDA0: 0x8716, //CJK UNIFIED IDEOGRAPH - 0xCDA1: 0x6C40, //CJK UNIFIED IDEOGRAPH - 0xCDA2: 0x5EF7, //CJK UNIFIED IDEOGRAPH - 0xCDA3: 0x505C, //CJK UNIFIED IDEOGRAPH - 0xCDA4: 0x4EAD, //CJK UNIFIED IDEOGRAPH - 0xCDA5: 0x5EAD, //CJK UNIFIED IDEOGRAPH - 0xCDA6: 0x633A, //CJK UNIFIED IDEOGRAPH - 0xCDA7: 0x8247, //CJK UNIFIED IDEOGRAPH - 0xCDA8: 0x901A, //CJK UNIFIED IDEOGRAPH - 0xCDA9: 0x6850, //CJK UNIFIED IDEOGRAPH - 0xCDAA: 0x916E, //CJK UNIFIED IDEOGRAPH - 0xCDAB: 0x77B3, //CJK UNIFIED IDEOGRAPH - 0xCDAC: 0x540C, //CJK UNIFIED IDEOGRAPH - 0xCDAD: 0x94DC, //CJK UNIFIED IDEOGRAPH - 0xCDAE: 0x5F64, //CJK UNIFIED IDEOGRAPH - 0xCDAF: 0x7AE5, //CJK UNIFIED IDEOGRAPH - 0xCDB0: 0x6876, //CJK UNIFIED IDEOGRAPH - 0xCDB1: 0x6345, //CJK UNIFIED IDEOGRAPH - 0xCDB2: 0x7B52, //CJK UNIFIED IDEOGRAPH - 0xCDB3: 0x7EDF, //CJK UNIFIED IDEOGRAPH - 0xCDB4: 0x75DB, //CJK UNIFIED IDEOGRAPH - 0xCDB5: 0x5077, //CJK UNIFIED IDEOGRAPH - 0xCDB6: 0x6295, //CJK UNIFIED IDEOGRAPH - 0xCDB7: 0x5934, //CJK UNIFIED IDEOGRAPH - 0xCDB8: 0x900F, //CJK UNIFIED IDEOGRAPH - 0xCDB9: 0x51F8, //CJK UNIFIED IDEOGRAPH - 0xCDBA: 0x79C3, //CJK UNIFIED IDEOGRAPH - 0xCDBB: 0x7A81, //CJK UNIFIED IDEOGRAPH - 0xCDBC: 0x56FE, //CJK UNIFIED IDEOGRAPH - 0xCDBD: 0x5F92, //CJK UNIFIED IDEOGRAPH - 0xCDBE: 0x9014, //CJK UNIFIED IDEOGRAPH - 0xCDBF: 0x6D82, //CJK UNIFIED IDEOGRAPH - 0xCDC0: 0x5C60, //CJK UNIFIED IDEOGRAPH - 0xCDC1: 0x571F, //CJK UNIFIED IDEOGRAPH - 0xCDC2: 0x5410, //CJK UNIFIED IDEOGRAPH - 0xCDC3: 0x5154, //CJK UNIFIED IDEOGRAPH - 0xCDC4: 0x6E4D, //CJK UNIFIED IDEOGRAPH - 0xCDC5: 0x56E2, //CJK UNIFIED IDEOGRAPH - 0xCDC6: 0x63A8, //CJK UNIFIED IDEOGRAPH - 0xCDC7: 0x9893, //CJK UNIFIED IDEOGRAPH - 0xCDC8: 0x817F, //CJK UNIFIED IDEOGRAPH - 0xCDC9: 0x8715, //CJK UNIFIED IDEOGRAPH - 0xCDCA: 0x892A, //CJK UNIFIED IDEOGRAPH - 0xCDCB: 0x9000, //CJK UNIFIED IDEOGRAPH - 0xCDCC: 0x541E, //CJK UNIFIED IDEOGRAPH - 0xCDCD: 0x5C6F, //CJK UNIFIED IDEOGRAPH - 0xCDCE: 0x81C0, //CJK UNIFIED IDEOGRAPH - 0xCDCF: 0x62D6, //CJK UNIFIED IDEOGRAPH - 0xCDD0: 0x6258, //CJK UNIFIED IDEOGRAPH - 0xCDD1: 0x8131, //CJK UNIFIED IDEOGRAPH - 0xCDD2: 0x9E35, //CJK UNIFIED IDEOGRAPH - 0xCDD3: 0x9640, //CJK UNIFIED IDEOGRAPH - 0xCDD4: 0x9A6E, //CJK UNIFIED IDEOGRAPH - 0xCDD5: 0x9A7C, //CJK UNIFIED IDEOGRAPH - 0xCDD6: 0x692D, //CJK UNIFIED IDEOGRAPH - 0xCDD7: 0x59A5, //CJK UNIFIED IDEOGRAPH - 0xCDD8: 0x62D3, //CJK UNIFIED IDEOGRAPH - 0xCDD9: 0x553E, //CJK UNIFIED IDEOGRAPH - 0xCDDA: 0x6316, //CJK UNIFIED IDEOGRAPH - 0xCDDB: 0x54C7, //CJK UNIFIED IDEOGRAPH - 0xCDDC: 0x86D9, //CJK UNIFIED IDEOGRAPH - 0xCDDD: 0x6D3C, //CJK UNIFIED IDEOGRAPH - 0xCDDE: 0x5A03, //CJK UNIFIED IDEOGRAPH - 0xCDDF: 0x74E6, //CJK UNIFIED IDEOGRAPH - 0xCDE0: 0x889C, //CJK UNIFIED IDEOGRAPH - 0xCDE1: 0x6B6A, //CJK UNIFIED IDEOGRAPH - 0xCDE2: 0x5916, //CJK UNIFIED IDEOGRAPH - 0xCDE3: 0x8C4C, //CJK UNIFIED IDEOGRAPH - 0xCDE4: 0x5F2F, //CJK UNIFIED IDEOGRAPH - 0xCDE5: 0x6E7E, //CJK UNIFIED IDEOGRAPH - 0xCDE6: 0x73A9, //CJK UNIFIED IDEOGRAPH - 0xCDE7: 0x987D, //CJK UNIFIED IDEOGRAPH - 0xCDE8: 0x4E38, //CJK UNIFIED IDEOGRAPH - 0xCDE9: 0x70F7, //CJK UNIFIED IDEOGRAPH - 0xCDEA: 0x5B8C, //CJK UNIFIED IDEOGRAPH - 0xCDEB: 0x7897, //CJK UNIFIED IDEOGRAPH - 0xCDEC: 0x633D, //CJK UNIFIED IDEOGRAPH - 0xCDED: 0x665A, //CJK UNIFIED IDEOGRAPH - 0xCDEE: 0x7696, //CJK UNIFIED IDEOGRAPH - 0xCDEF: 0x60CB, //CJK UNIFIED IDEOGRAPH - 0xCDF0: 0x5B9B, //CJK UNIFIED IDEOGRAPH - 0xCDF1: 0x5A49, //CJK UNIFIED IDEOGRAPH - 0xCDF2: 0x4E07, //CJK UNIFIED IDEOGRAPH - 0xCDF3: 0x8155, //CJK UNIFIED IDEOGRAPH - 0xCDF4: 0x6C6A, //CJK UNIFIED IDEOGRAPH - 0xCDF5: 0x738B, //CJK UNIFIED IDEOGRAPH - 0xCDF6: 0x4EA1, //CJK UNIFIED IDEOGRAPH - 0xCDF7: 0x6789, //CJK UNIFIED IDEOGRAPH - 0xCDF8: 0x7F51, //CJK UNIFIED IDEOGRAPH - 0xCDF9: 0x5F80, //CJK UNIFIED IDEOGRAPH - 0xCDFA: 0x65FA, //CJK UNIFIED IDEOGRAPH - 0xCDFB: 0x671B, //CJK UNIFIED IDEOGRAPH - 0xCDFC: 0x5FD8, //CJK UNIFIED IDEOGRAPH - 0xCDFD: 0x5984, //CJK UNIFIED IDEOGRAPH - 0xCDFE: 0x5A01, //CJK UNIFIED IDEOGRAPH - 0xCE40: 0x8719, //CJK UNIFIED IDEOGRAPH - 0xCE41: 0x871B, //CJK UNIFIED IDEOGRAPH - 0xCE42: 0x871D, //CJK UNIFIED IDEOGRAPH - 0xCE43: 0x871F, //CJK UNIFIED IDEOGRAPH - 0xCE44: 0x8720, //CJK UNIFIED IDEOGRAPH - 0xCE45: 0x8724, //CJK UNIFIED IDEOGRAPH - 0xCE46: 0x8726, //CJK UNIFIED IDEOGRAPH - 0xCE47: 0x8727, //CJK UNIFIED IDEOGRAPH - 0xCE48: 0x8728, //CJK UNIFIED IDEOGRAPH - 0xCE49: 0x872A, //CJK UNIFIED IDEOGRAPH - 0xCE4A: 0x872B, //CJK UNIFIED IDEOGRAPH - 0xCE4B: 0x872C, //CJK UNIFIED IDEOGRAPH - 0xCE4C: 0x872D, //CJK UNIFIED IDEOGRAPH - 0xCE4D: 0x872F, //CJK UNIFIED IDEOGRAPH - 0xCE4E: 0x8730, //CJK UNIFIED IDEOGRAPH - 0xCE4F: 0x8732, //CJK UNIFIED IDEOGRAPH - 0xCE50: 0x8733, //CJK UNIFIED IDEOGRAPH - 0xCE51: 0x8735, //CJK UNIFIED IDEOGRAPH - 0xCE52: 0x8736, //CJK UNIFIED IDEOGRAPH - 0xCE53: 0x8738, //CJK UNIFIED IDEOGRAPH - 0xCE54: 0x8739, //CJK UNIFIED IDEOGRAPH - 0xCE55: 0x873A, //CJK UNIFIED IDEOGRAPH - 0xCE56: 0x873C, //CJK UNIFIED IDEOGRAPH - 0xCE57: 0x873D, //CJK UNIFIED IDEOGRAPH - 0xCE58: 0x8740, //CJK UNIFIED IDEOGRAPH - 0xCE59: 0x8741, //CJK UNIFIED IDEOGRAPH - 0xCE5A: 0x8742, //CJK UNIFIED IDEOGRAPH - 0xCE5B: 0x8743, //CJK UNIFIED IDEOGRAPH - 0xCE5C: 0x8744, //CJK UNIFIED IDEOGRAPH - 0xCE5D: 0x8745, //CJK UNIFIED IDEOGRAPH - 0xCE5E: 0x8746, //CJK UNIFIED IDEOGRAPH - 0xCE5F: 0x874A, //CJK UNIFIED IDEOGRAPH - 0xCE60: 0x874B, //CJK UNIFIED IDEOGRAPH - 0xCE61: 0x874D, //CJK UNIFIED IDEOGRAPH - 0xCE62: 0x874F, //CJK UNIFIED IDEOGRAPH - 0xCE63: 0x8750, //CJK UNIFIED IDEOGRAPH - 0xCE64: 0x8751, //CJK UNIFIED IDEOGRAPH - 0xCE65: 0x8752, //CJK UNIFIED IDEOGRAPH - 0xCE66: 0x8754, //CJK UNIFIED IDEOGRAPH - 0xCE67: 0x8755, //CJK UNIFIED IDEOGRAPH - 0xCE68: 0x8756, //CJK UNIFIED IDEOGRAPH - 0xCE69: 0x8758, //CJK UNIFIED IDEOGRAPH - 0xCE6A: 0x875A, //CJK UNIFIED IDEOGRAPH - 0xCE6B: 0x875B, //CJK UNIFIED IDEOGRAPH - 0xCE6C: 0x875C, //CJK UNIFIED IDEOGRAPH - 0xCE6D: 0x875D, //CJK UNIFIED IDEOGRAPH - 0xCE6E: 0x875E, //CJK UNIFIED IDEOGRAPH - 0xCE6F: 0x875F, //CJK UNIFIED IDEOGRAPH - 0xCE70: 0x8761, //CJK UNIFIED IDEOGRAPH - 0xCE71: 0x8762, //CJK UNIFIED IDEOGRAPH - 0xCE72: 0x8766, //CJK UNIFIED IDEOGRAPH - 0xCE73: 0x8767, //CJK UNIFIED IDEOGRAPH - 0xCE74: 0x8768, //CJK UNIFIED IDEOGRAPH - 0xCE75: 0x8769, //CJK UNIFIED IDEOGRAPH - 0xCE76: 0x876A, //CJK UNIFIED IDEOGRAPH - 0xCE77: 0x876B, //CJK UNIFIED IDEOGRAPH - 0xCE78: 0x876C, //CJK UNIFIED IDEOGRAPH - 0xCE79: 0x876D, //CJK UNIFIED IDEOGRAPH - 0xCE7A: 0x876F, //CJK UNIFIED IDEOGRAPH - 0xCE7B: 0x8771, //CJK UNIFIED IDEOGRAPH - 0xCE7C: 0x8772, //CJK UNIFIED IDEOGRAPH - 0xCE7D: 0x8773, //CJK UNIFIED IDEOGRAPH - 0xCE7E: 0x8775, //CJK UNIFIED IDEOGRAPH - 0xCE80: 0x8777, //CJK UNIFIED IDEOGRAPH - 0xCE81: 0x8778, //CJK UNIFIED IDEOGRAPH - 0xCE82: 0x8779, //CJK UNIFIED IDEOGRAPH - 0xCE83: 0x877A, //CJK UNIFIED IDEOGRAPH - 0xCE84: 0x877F, //CJK UNIFIED IDEOGRAPH - 0xCE85: 0x8780, //CJK UNIFIED IDEOGRAPH - 0xCE86: 0x8781, //CJK UNIFIED IDEOGRAPH - 0xCE87: 0x8784, //CJK UNIFIED IDEOGRAPH - 0xCE88: 0x8786, //CJK UNIFIED IDEOGRAPH - 0xCE89: 0x8787, //CJK UNIFIED IDEOGRAPH - 0xCE8A: 0x8789, //CJK UNIFIED IDEOGRAPH - 0xCE8B: 0x878A, //CJK UNIFIED IDEOGRAPH - 0xCE8C: 0x878C, //CJK UNIFIED IDEOGRAPH - 0xCE8D: 0x878E, //CJK UNIFIED IDEOGRAPH - 0xCE8E: 0x878F, //CJK UNIFIED IDEOGRAPH - 0xCE8F: 0x8790, //CJK UNIFIED IDEOGRAPH - 0xCE90: 0x8791, //CJK UNIFIED IDEOGRAPH - 0xCE91: 0x8792, //CJK UNIFIED IDEOGRAPH - 0xCE92: 0x8794, //CJK UNIFIED IDEOGRAPH - 0xCE93: 0x8795, //CJK UNIFIED IDEOGRAPH - 0xCE94: 0x8796, //CJK UNIFIED IDEOGRAPH - 0xCE95: 0x8798, //CJK UNIFIED IDEOGRAPH - 0xCE96: 0x8799, //CJK UNIFIED IDEOGRAPH - 0xCE97: 0x879A, //CJK UNIFIED IDEOGRAPH - 0xCE98: 0x879B, //CJK UNIFIED IDEOGRAPH - 0xCE99: 0x879C, //CJK UNIFIED IDEOGRAPH - 0xCE9A: 0x879D, //CJK UNIFIED IDEOGRAPH - 0xCE9B: 0x879E, //CJK UNIFIED IDEOGRAPH - 0xCE9C: 0x87A0, //CJK UNIFIED IDEOGRAPH - 0xCE9D: 0x87A1, //CJK UNIFIED IDEOGRAPH - 0xCE9E: 0x87A2, //CJK UNIFIED IDEOGRAPH - 0xCE9F: 0x87A3, //CJK UNIFIED IDEOGRAPH - 0xCEA0: 0x87A4, //CJK UNIFIED IDEOGRAPH - 0xCEA1: 0x5DCD, //CJK UNIFIED IDEOGRAPH - 0xCEA2: 0x5FAE, //CJK UNIFIED IDEOGRAPH - 0xCEA3: 0x5371, //CJK UNIFIED IDEOGRAPH - 0xCEA4: 0x97E6, //CJK UNIFIED IDEOGRAPH - 0xCEA5: 0x8FDD, //CJK UNIFIED IDEOGRAPH - 0xCEA6: 0x6845, //CJK UNIFIED IDEOGRAPH - 0xCEA7: 0x56F4, //CJK UNIFIED IDEOGRAPH - 0xCEA8: 0x552F, //CJK UNIFIED IDEOGRAPH - 0xCEA9: 0x60DF, //CJK UNIFIED IDEOGRAPH - 0xCEAA: 0x4E3A, //CJK UNIFIED IDEOGRAPH - 0xCEAB: 0x6F4D, //CJK UNIFIED IDEOGRAPH - 0xCEAC: 0x7EF4, //CJK UNIFIED IDEOGRAPH - 0xCEAD: 0x82C7, //CJK UNIFIED IDEOGRAPH - 0xCEAE: 0x840E, //CJK UNIFIED IDEOGRAPH - 0xCEAF: 0x59D4, //CJK UNIFIED IDEOGRAPH - 0xCEB0: 0x4F1F, //CJK UNIFIED IDEOGRAPH - 0xCEB1: 0x4F2A, //CJK UNIFIED IDEOGRAPH - 0xCEB2: 0x5C3E, //CJK UNIFIED IDEOGRAPH - 0xCEB3: 0x7EAC, //CJK UNIFIED IDEOGRAPH - 0xCEB4: 0x672A, //CJK UNIFIED IDEOGRAPH - 0xCEB5: 0x851A, //CJK UNIFIED IDEOGRAPH - 0xCEB6: 0x5473, //CJK UNIFIED IDEOGRAPH - 0xCEB7: 0x754F, //CJK UNIFIED IDEOGRAPH - 0xCEB8: 0x80C3, //CJK UNIFIED IDEOGRAPH - 0xCEB9: 0x5582, //CJK UNIFIED IDEOGRAPH - 0xCEBA: 0x9B4F, //CJK UNIFIED IDEOGRAPH - 0xCEBB: 0x4F4D, //CJK UNIFIED IDEOGRAPH - 0xCEBC: 0x6E2D, //CJK UNIFIED IDEOGRAPH - 0xCEBD: 0x8C13, //CJK UNIFIED IDEOGRAPH - 0xCEBE: 0x5C09, //CJK UNIFIED IDEOGRAPH - 0xCEBF: 0x6170, //CJK UNIFIED IDEOGRAPH - 0xCEC0: 0x536B, //CJK UNIFIED IDEOGRAPH - 0xCEC1: 0x761F, //CJK UNIFIED IDEOGRAPH - 0xCEC2: 0x6E29, //CJK UNIFIED IDEOGRAPH - 0xCEC3: 0x868A, //CJK UNIFIED IDEOGRAPH - 0xCEC4: 0x6587, //CJK UNIFIED IDEOGRAPH - 0xCEC5: 0x95FB, //CJK UNIFIED IDEOGRAPH - 0xCEC6: 0x7EB9, //CJK UNIFIED IDEOGRAPH - 0xCEC7: 0x543B, //CJK UNIFIED IDEOGRAPH - 0xCEC8: 0x7A33, //CJK UNIFIED IDEOGRAPH - 0xCEC9: 0x7D0A, //CJK UNIFIED IDEOGRAPH - 0xCECA: 0x95EE, //CJK UNIFIED IDEOGRAPH - 0xCECB: 0x55E1, //CJK UNIFIED IDEOGRAPH - 0xCECC: 0x7FC1, //CJK UNIFIED IDEOGRAPH - 0xCECD: 0x74EE, //CJK UNIFIED IDEOGRAPH - 0xCECE: 0x631D, //CJK UNIFIED IDEOGRAPH - 0xCECF: 0x8717, //CJK UNIFIED IDEOGRAPH - 0xCED0: 0x6DA1, //CJK UNIFIED IDEOGRAPH - 0xCED1: 0x7A9D, //CJK UNIFIED IDEOGRAPH - 0xCED2: 0x6211, //CJK UNIFIED IDEOGRAPH - 0xCED3: 0x65A1, //CJK UNIFIED IDEOGRAPH - 0xCED4: 0x5367, //CJK UNIFIED IDEOGRAPH - 0xCED5: 0x63E1, //CJK UNIFIED IDEOGRAPH - 0xCED6: 0x6C83, //CJK UNIFIED IDEOGRAPH - 0xCED7: 0x5DEB, //CJK UNIFIED IDEOGRAPH - 0xCED8: 0x545C, //CJK UNIFIED IDEOGRAPH - 0xCED9: 0x94A8, //CJK UNIFIED IDEOGRAPH - 0xCEDA: 0x4E4C, //CJK UNIFIED IDEOGRAPH - 0xCEDB: 0x6C61, //CJK UNIFIED IDEOGRAPH - 0xCEDC: 0x8BEC, //CJK UNIFIED IDEOGRAPH - 0xCEDD: 0x5C4B, //CJK UNIFIED IDEOGRAPH - 0xCEDE: 0x65E0, //CJK UNIFIED IDEOGRAPH - 0xCEDF: 0x829C, //CJK UNIFIED IDEOGRAPH - 0xCEE0: 0x68A7, //CJK UNIFIED IDEOGRAPH - 0xCEE1: 0x543E, //CJK UNIFIED IDEOGRAPH - 0xCEE2: 0x5434, //CJK UNIFIED IDEOGRAPH - 0xCEE3: 0x6BCB, //CJK UNIFIED IDEOGRAPH - 0xCEE4: 0x6B66, //CJK UNIFIED IDEOGRAPH - 0xCEE5: 0x4E94, //CJK UNIFIED IDEOGRAPH - 0xCEE6: 0x6342, //CJK UNIFIED IDEOGRAPH - 0xCEE7: 0x5348, //CJK UNIFIED IDEOGRAPH - 0xCEE8: 0x821E, //CJK UNIFIED IDEOGRAPH - 0xCEE9: 0x4F0D, //CJK UNIFIED IDEOGRAPH - 0xCEEA: 0x4FAE, //CJK UNIFIED IDEOGRAPH - 0xCEEB: 0x575E, //CJK UNIFIED IDEOGRAPH - 0xCEEC: 0x620A, //CJK UNIFIED IDEOGRAPH - 0xCEED: 0x96FE, //CJK UNIFIED IDEOGRAPH - 0xCEEE: 0x6664, //CJK UNIFIED IDEOGRAPH - 0xCEEF: 0x7269, //CJK UNIFIED IDEOGRAPH - 0xCEF0: 0x52FF, //CJK UNIFIED IDEOGRAPH - 0xCEF1: 0x52A1, //CJK UNIFIED IDEOGRAPH - 0xCEF2: 0x609F, //CJK UNIFIED IDEOGRAPH - 0xCEF3: 0x8BEF, //CJK UNIFIED IDEOGRAPH - 0xCEF4: 0x6614, //CJK UNIFIED IDEOGRAPH - 0xCEF5: 0x7199, //CJK UNIFIED IDEOGRAPH - 0xCEF6: 0x6790, //CJK UNIFIED IDEOGRAPH - 0xCEF7: 0x897F, //CJK UNIFIED IDEOGRAPH - 0xCEF8: 0x7852, //CJK UNIFIED IDEOGRAPH - 0xCEF9: 0x77FD, //CJK UNIFIED IDEOGRAPH - 0xCEFA: 0x6670, //CJK UNIFIED IDEOGRAPH - 0xCEFB: 0x563B, //CJK UNIFIED IDEOGRAPH - 0xCEFC: 0x5438, //CJK UNIFIED IDEOGRAPH - 0xCEFD: 0x9521, //CJK UNIFIED IDEOGRAPH - 0xCEFE: 0x727A, //CJK UNIFIED IDEOGRAPH - 0xCF40: 0x87A5, //CJK UNIFIED IDEOGRAPH - 0xCF41: 0x87A6, //CJK UNIFIED IDEOGRAPH - 0xCF42: 0x87A7, //CJK UNIFIED IDEOGRAPH - 0xCF43: 0x87A9, //CJK UNIFIED IDEOGRAPH - 0xCF44: 0x87AA, //CJK UNIFIED IDEOGRAPH - 0xCF45: 0x87AE, //CJK UNIFIED IDEOGRAPH - 0xCF46: 0x87B0, //CJK UNIFIED IDEOGRAPH - 0xCF47: 0x87B1, //CJK UNIFIED IDEOGRAPH - 0xCF48: 0x87B2, //CJK UNIFIED IDEOGRAPH - 0xCF49: 0x87B4, //CJK UNIFIED IDEOGRAPH - 0xCF4A: 0x87B6, //CJK UNIFIED IDEOGRAPH - 0xCF4B: 0x87B7, //CJK UNIFIED IDEOGRAPH - 0xCF4C: 0x87B8, //CJK UNIFIED IDEOGRAPH - 0xCF4D: 0x87B9, //CJK UNIFIED IDEOGRAPH - 0xCF4E: 0x87BB, //CJK UNIFIED IDEOGRAPH - 0xCF4F: 0x87BC, //CJK UNIFIED IDEOGRAPH - 0xCF50: 0x87BE, //CJK UNIFIED IDEOGRAPH - 0xCF51: 0x87BF, //CJK UNIFIED IDEOGRAPH - 0xCF52: 0x87C1, //CJK UNIFIED IDEOGRAPH - 0xCF53: 0x87C2, //CJK UNIFIED IDEOGRAPH - 0xCF54: 0x87C3, //CJK UNIFIED IDEOGRAPH - 0xCF55: 0x87C4, //CJK UNIFIED IDEOGRAPH - 0xCF56: 0x87C5, //CJK UNIFIED IDEOGRAPH - 0xCF57: 0x87C7, //CJK UNIFIED IDEOGRAPH - 0xCF58: 0x87C8, //CJK UNIFIED IDEOGRAPH - 0xCF59: 0x87C9, //CJK UNIFIED IDEOGRAPH - 0xCF5A: 0x87CC, //CJK UNIFIED IDEOGRAPH - 0xCF5B: 0x87CD, //CJK UNIFIED IDEOGRAPH - 0xCF5C: 0x87CE, //CJK UNIFIED IDEOGRAPH - 0xCF5D: 0x87CF, //CJK UNIFIED IDEOGRAPH - 0xCF5E: 0x87D0, //CJK UNIFIED IDEOGRAPH - 0xCF5F: 0x87D4, //CJK UNIFIED IDEOGRAPH - 0xCF60: 0x87D5, //CJK UNIFIED IDEOGRAPH - 0xCF61: 0x87D6, //CJK UNIFIED IDEOGRAPH - 0xCF62: 0x87D7, //CJK UNIFIED IDEOGRAPH - 0xCF63: 0x87D8, //CJK UNIFIED IDEOGRAPH - 0xCF64: 0x87D9, //CJK UNIFIED IDEOGRAPH - 0xCF65: 0x87DA, //CJK UNIFIED IDEOGRAPH - 0xCF66: 0x87DC, //CJK UNIFIED IDEOGRAPH - 0xCF67: 0x87DD, //CJK UNIFIED IDEOGRAPH - 0xCF68: 0x87DE, //CJK UNIFIED IDEOGRAPH - 0xCF69: 0x87DF, //CJK UNIFIED IDEOGRAPH - 0xCF6A: 0x87E1, //CJK UNIFIED IDEOGRAPH - 0xCF6B: 0x87E2, //CJK UNIFIED IDEOGRAPH - 0xCF6C: 0x87E3, //CJK UNIFIED IDEOGRAPH - 0xCF6D: 0x87E4, //CJK UNIFIED IDEOGRAPH - 0xCF6E: 0x87E6, //CJK UNIFIED IDEOGRAPH - 0xCF6F: 0x87E7, //CJK UNIFIED IDEOGRAPH - 0xCF70: 0x87E8, //CJK UNIFIED IDEOGRAPH - 0xCF71: 0x87E9, //CJK UNIFIED IDEOGRAPH - 0xCF72: 0x87EB, //CJK UNIFIED IDEOGRAPH - 0xCF73: 0x87EC, //CJK UNIFIED IDEOGRAPH - 0xCF74: 0x87ED, //CJK UNIFIED IDEOGRAPH - 0xCF75: 0x87EF, //CJK UNIFIED IDEOGRAPH - 0xCF76: 0x87F0, //CJK UNIFIED IDEOGRAPH - 0xCF77: 0x87F1, //CJK UNIFIED IDEOGRAPH - 0xCF78: 0x87F2, //CJK UNIFIED IDEOGRAPH - 0xCF79: 0x87F3, //CJK UNIFIED IDEOGRAPH - 0xCF7A: 0x87F4, //CJK UNIFIED IDEOGRAPH - 0xCF7B: 0x87F5, //CJK UNIFIED IDEOGRAPH - 0xCF7C: 0x87F6, //CJK UNIFIED IDEOGRAPH - 0xCF7D: 0x87F7, //CJK UNIFIED IDEOGRAPH - 0xCF7E: 0x87F8, //CJK UNIFIED IDEOGRAPH - 0xCF80: 0x87FA, //CJK UNIFIED IDEOGRAPH - 0xCF81: 0x87FB, //CJK UNIFIED IDEOGRAPH - 0xCF82: 0x87FC, //CJK UNIFIED IDEOGRAPH - 0xCF83: 0x87FD, //CJK UNIFIED IDEOGRAPH - 0xCF84: 0x87FF, //CJK UNIFIED IDEOGRAPH - 0xCF85: 0x8800, //CJK UNIFIED IDEOGRAPH - 0xCF86: 0x8801, //CJK UNIFIED IDEOGRAPH - 0xCF87: 0x8802, //CJK UNIFIED IDEOGRAPH - 0xCF88: 0x8804, //CJK UNIFIED IDEOGRAPH - 0xCF89: 0x8805, //CJK UNIFIED IDEOGRAPH - 0xCF8A: 0x8806, //CJK UNIFIED IDEOGRAPH - 0xCF8B: 0x8807, //CJK UNIFIED IDEOGRAPH - 0xCF8C: 0x8808, //CJK UNIFIED IDEOGRAPH - 0xCF8D: 0x8809, //CJK UNIFIED IDEOGRAPH - 0xCF8E: 0x880B, //CJK UNIFIED IDEOGRAPH - 0xCF8F: 0x880C, //CJK UNIFIED IDEOGRAPH - 0xCF90: 0x880D, //CJK UNIFIED IDEOGRAPH - 0xCF91: 0x880E, //CJK UNIFIED IDEOGRAPH - 0xCF92: 0x880F, //CJK UNIFIED IDEOGRAPH - 0xCF93: 0x8810, //CJK UNIFIED IDEOGRAPH - 0xCF94: 0x8811, //CJK UNIFIED IDEOGRAPH - 0xCF95: 0x8812, //CJK UNIFIED IDEOGRAPH - 0xCF96: 0x8814, //CJK UNIFIED IDEOGRAPH - 0xCF97: 0x8817, //CJK UNIFIED IDEOGRAPH - 0xCF98: 0x8818, //CJK UNIFIED IDEOGRAPH - 0xCF99: 0x8819, //CJK UNIFIED IDEOGRAPH - 0xCF9A: 0x881A, //CJK UNIFIED IDEOGRAPH - 0xCF9B: 0x881C, //CJK UNIFIED IDEOGRAPH - 0xCF9C: 0x881D, //CJK UNIFIED IDEOGRAPH - 0xCF9D: 0x881E, //CJK UNIFIED IDEOGRAPH - 0xCF9E: 0x881F, //CJK UNIFIED IDEOGRAPH - 0xCF9F: 0x8820, //CJK UNIFIED IDEOGRAPH - 0xCFA0: 0x8823, //CJK UNIFIED IDEOGRAPH - 0xCFA1: 0x7A00, //CJK UNIFIED IDEOGRAPH - 0xCFA2: 0x606F, //CJK UNIFIED IDEOGRAPH - 0xCFA3: 0x5E0C, //CJK UNIFIED IDEOGRAPH - 0xCFA4: 0x6089, //CJK UNIFIED IDEOGRAPH - 0xCFA5: 0x819D, //CJK UNIFIED IDEOGRAPH - 0xCFA6: 0x5915, //CJK UNIFIED IDEOGRAPH - 0xCFA7: 0x60DC, //CJK UNIFIED IDEOGRAPH - 0xCFA8: 0x7184, //CJK UNIFIED IDEOGRAPH - 0xCFA9: 0x70EF, //CJK UNIFIED IDEOGRAPH - 0xCFAA: 0x6EAA, //CJK UNIFIED IDEOGRAPH - 0xCFAB: 0x6C50, //CJK UNIFIED IDEOGRAPH - 0xCFAC: 0x7280, //CJK UNIFIED IDEOGRAPH - 0xCFAD: 0x6A84, //CJK UNIFIED IDEOGRAPH - 0xCFAE: 0x88AD, //CJK UNIFIED IDEOGRAPH - 0xCFAF: 0x5E2D, //CJK UNIFIED IDEOGRAPH - 0xCFB0: 0x4E60, //CJK UNIFIED IDEOGRAPH - 0xCFB1: 0x5AB3, //CJK UNIFIED IDEOGRAPH - 0xCFB2: 0x559C, //CJK UNIFIED IDEOGRAPH - 0xCFB3: 0x94E3, //CJK UNIFIED IDEOGRAPH - 0xCFB4: 0x6D17, //CJK UNIFIED IDEOGRAPH - 0xCFB5: 0x7CFB, //CJK UNIFIED IDEOGRAPH - 0xCFB6: 0x9699, //CJK UNIFIED IDEOGRAPH - 0xCFB7: 0x620F, //CJK UNIFIED IDEOGRAPH - 0xCFB8: 0x7EC6, //CJK UNIFIED IDEOGRAPH - 0xCFB9: 0x778E, //CJK UNIFIED IDEOGRAPH - 0xCFBA: 0x867E, //CJK UNIFIED IDEOGRAPH - 0xCFBB: 0x5323, //CJK UNIFIED IDEOGRAPH - 0xCFBC: 0x971E, //CJK UNIFIED IDEOGRAPH - 0xCFBD: 0x8F96, //CJK UNIFIED IDEOGRAPH - 0xCFBE: 0x6687, //CJK UNIFIED IDEOGRAPH - 0xCFBF: 0x5CE1, //CJK UNIFIED IDEOGRAPH - 0xCFC0: 0x4FA0, //CJK UNIFIED IDEOGRAPH - 0xCFC1: 0x72ED, //CJK UNIFIED IDEOGRAPH - 0xCFC2: 0x4E0B, //CJK UNIFIED IDEOGRAPH - 0xCFC3: 0x53A6, //CJK UNIFIED IDEOGRAPH - 0xCFC4: 0x590F, //CJK UNIFIED IDEOGRAPH - 0xCFC5: 0x5413, //CJK UNIFIED IDEOGRAPH - 0xCFC6: 0x6380, //CJK UNIFIED IDEOGRAPH - 0xCFC7: 0x9528, //CJK UNIFIED IDEOGRAPH - 0xCFC8: 0x5148, //CJK UNIFIED IDEOGRAPH - 0xCFC9: 0x4ED9, //CJK UNIFIED IDEOGRAPH - 0xCFCA: 0x9C9C, //CJK UNIFIED IDEOGRAPH - 0xCFCB: 0x7EA4, //CJK UNIFIED IDEOGRAPH - 0xCFCC: 0x54B8, //CJK UNIFIED IDEOGRAPH - 0xCFCD: 0x8D24, //CJK UNIFIED IDEOGRAPH - 0xCFCE: 0x8854, //CJK UNIFIED IDEOGRAPH - 0xCFCF: 0x8237, //CJK UNIFIED IDEOGRAPH - 0xCFD0: 0x95F2, //CJK UNIFIED IDEOGRAPH - 0xCFD1: 0x6D8E, //CJK UNIFIED IDEOGRAPH - 0xCFD2: 0x5F26, //CJK UNIFIED IDEOGRAPH - 0xCFD3: 0x5ACC, //CJK UNIFIED IDEOGRAPH - 0xCFD4: 0x663E, //CJK UNIFIED IDEOGRAPH - 0xCFD5: 0x9669, //CJK UNIFIED IDEOGRAPH - 0xCFD6: 0x73B0, //CJK UNIFIED IDEOGRAPH - 0xCFD7: 0x732E, //CJK UNIFIED IDEOGRAPH - 0xCFD8: 0x53BF, //CJK UNIFIED IDEOGRAPH - 0xCFD9: 0x817A, //CJK UNIFIED IDEOGRAPH - 0xCFDA: 0x9985, //CJK UNIFIED IDEOGRAPH - 0xCFDB: 0x7FA1, //CJK UNIFIED IDEOGRAPH - 0xCFDC: 0x5BAA, //CJK UNIFIED IDEOGRAPH - 0xCFDD: 0x9677, //CJK UNIFIED IDEOGRAPH - 0xCFDE: 0x9650, //CJK UNIFIED IDEOGRAPH - 0xCFDF: 0x7EBF, //CJK UNIFIED IDEOGRAPH - 0xCFE0: 0x76F8, //CJK UNIFIED IDEOGRAPH - 0xCFE1: 0x53A2, //CJK UNIFIED IDEOGRAPH - 0xCFE2: 0x9576, //CJK UNIFIED IDEOGRAPH - 0xCFE3: 0x9999, //CJK UNIFIED IDEOGRAPH - 0xCFE4: 0x7BB1, //CJK UNIFIED IDEOGRAPH - 0xCFE5: 0x8944, //CJK UNIFIED IDEOGRAPH - 0xCFE6: 0x6E58, //CJK UNIFIED IDEOGRAPH - 0xCFE7: 0x4E61, //CJK UNIFIED IDEOGRAPH - 0xCFE8: 0x7FD4, //CJK UNIFIED IDEOGRAPH - 0xCFE9: 0x7965, //CJK UNIFIED IDEOGRAPH - 0xCFEA: 0x8BE6, //CJK UNIFIED IDEOGRAPH - 0xCFEB: 0x60F3, //CJK UNIFIED IDEOGRAPH - 0xCFEC: 0x54CD, //CJK UNIFIED IDEOGRAPH - 0xCFED: 0x4EAB, //CJK UNIFIED IDEOGRAPH - 0xCFEE: 0x9879, //CJK UNIFIED IDEOGRAPH - 0xCFEF: 0x5DF7, //CJK UNIFIED IDEOGRAPH - 0xCFF0: 0x6A61, //CJK UNIFIED IDEOGRAPH - 0xCFF1: 0x50CF, //CJK UNIFIED IDEOGRAPH - 0xCFF2: 0x5411, //CJK UNIFIED IDEOGRAPH - 0xCFF3: 0x8C61, //CJK UNIFIED IDEOGRAPH - 0xCFF4: 0x8427, //CJK UNIFIED IDEOGRAPH - 0xCFF5: 0x785D, //CJK UNIFIED IDEOGRAPH - 0xCFF6: 0x9704, //CJK UNIFIED IDEOGRAPH - 0xCFF7: 0x524A, //CJK UNIFIED IDEOGRAPH - 0xCFF8: 0x54EE, //CJK UNIFIED IDEOGRAPH - 0xCFF9: 0x56A3, //CJK UNIFIED IDEOGRAPH - 0xCFFA: 0x9500, //CJK UNIFIED IDEOGRAPH - 0xCFFB: 0x6D88, //CJK UNIFIED IDEOGRAPH - 0xCFFC: 0x5BB5, //CJK UNIFIED IDEOGRAPH - 0xCFFD: 0x6DC6, //CJK UNIFIED IDEOGRAPH - 0xCFFE: 0x6653, //CJK UNIFIED IDEOGRAPH - 0xD040: 0x8824, //CJK UNIFIED IDEOGRAPH - 0xD041: 0x8825, //CJK UNIFIED IDEOGRAPH - 0xD042: 0x8826, //CJK UNIFIED IDEOGRAPH - 0xD043: 0x8827, //CJK UNIFIED IDEOGRAPH - 0xD044: 0x8828, //CJK UNIFIED IDEOGRAPH - 0xD045: 0x8829, //CJK UNIFIED IDEOGRAPH - 0xD046: 0x882A, //CJK UNIFIED IDEOGRAPH - 0xD047: 0x882B, //CJK UNIFIED IDEOGRAPH - 0xD048: 0x882C, //CJK UNIFIED IDEOGRAPH - 0xD049: 0x882D, //CJK UNIFIED IDEOGRAPH - 0xD04A: 0x882E, //CJK UNIFIED IDEOGRAPH - 0xD04B: 0x882F, //CJK UNIFIED IDEOGRAPH - 0xD04C: 0x8830, //CJK UNIFIED IDEOGRAPH - 0xD04D: 0x8831, //CJK UNIFIED IDEOGRAPH - 0xD04E: 0x8833, //CJK UNIFIED IDEOGRAPH - 0xD04F: 0x8834, //CJK UNIFIED IDEOGRAPH - 0xD050: 0x8835, //CJK UNIFIED IDEOGRAPH - 0xD051: 0x8836, //CJK UNIFIED IDEOGRAPH - 0xD052: 0x8837, //CJK UNIFIED IDEOGRAPH - 0xD053: 0x8838, //CJK UNIFIED IDEOGRAPH - 0xD054: 0x883A, //CJK UNIFIED IDEOGRAPH - 0xD055: 0x883B, //CJK UNIFIED IDEOGRAPH - 0xD056: 0x883D, //CJK UNIFIED IDEOGRAPH - 0xD057: 0x883E, //CJK UNIFIED IDEOGRAPH - 0xD058: 0x883F, //CJK UNIFIED IDEOGRAPH - 0xD059: 0x8841, //CJK UNIFIED IDEOGRAPH - 0xD05A: 0x8842, //CJK UNIFIED IDEOGRAPH - 0xD05B: 0x8843, //CJK UNIFIED IDEOGRAPH - 0xD05C: 0x8846, //CJK UNIFIED IDEOGRAPH - 0xD05D: 0x8847, //CJK UNIFIED IDEOGRAPH - 0xD05E: 0x8848, //CJK UNIFIED IDEOGRAPH - 0xD05F: 0x8849, //CJK UNIFIED IDEOGRAPH - 0xD060: 0x884A, //CJK UNIFIED IDEOGRAPH - 0xD061: 0x884B, //CJK UNIFIED IDEOGRAPH - 0xD062: 0x884E, //CJK UNIFIED IDEOGRAPH - 0xD063: 0x884F, //CJK UNIFIED IDEOGRAPH - 0xD064: 0x8850, //CJK UNIFIED IDEOGRAPH - 0xD065: 0x8851, //CJK UNIFIED IDEOGRAPH - 0xD066: 0x8852, //CJK UNIFIED IDEOGRAPH - 0xD067: 0x8853, //CJK UNIFIED IDEOGRAPH - 0xD068: 0x8855, //CJK UNIFIED IDEOGRAPH - 0xD069: 0x8856, //CJK UNIFIED IDEOGRAPH - 0xD06A: 0x8858, //CJK UNIFIED IDEOGRAPH - 0xD06B: 0x885A, //CJK UNIFIED IDEOGRAPH - 0xD06C: 0x885B, //CJK UNIFIED IDEOGRAPH - 0xD06D: 0x885C, //CJK UNIFIED IDEOGRAPH - 0xD06E: 0x885D, //CJK UNIFIED IDEOGRAPH - 0xD06F: 0x885E, //CJK UNIFIED IDEOGRAPH - 0xD070: 0x885F, //CJK UNIFIED IDEOGRAPH - 0xD071: 0x8860, //CJK UNIFIED IDEOGRAPH - 0xD072: 0x8866, //CJK UNIFIED IDEOGRAPH - 0xD073: 0x8867, //CJK UNIFIED IDEOGRAPH - 0xD074: 0x886A, //CJK UNIFIED IDEOGRAPH - 0xD075: 0x886D, //CJK UNIFIED IDEOGRAPH - 0xD076: 0x886F, //CJK UNIFIED IDEOGRAPH - 0xD077: 0x8871, //CJK UNIFIED IDEOGRAPH - 0xD078: 0x8873, //CJK UNIFIED IDEOGRAPH - 0xD079: 0x8874, //CJK UNIFIED IDEOGRAPH - 0xD07A: 0x8875, //CJK UNIFIED IDEOGRAPH - 0xD07B: 0x8876, //CJK UNIFIED IDEOGRAPH - 0xD07C: 0x8878, //CJK UNIFIED IDEOGRAPH - 0xD07D: 0x8879, //CJK UNIFIED IDEOGRAPH - 0xD07E: 0x887A, //CJK UNIFIED IDEOGRAPH - 0xD080: 0x887B, //CJK UNIFIED IDEOGRAPH - 0xD081: 0x887C, //CJK UNIFIED IDEOGRAPH - 0xD082: 0x8880, //CJK UNIFIED IDEOGRAPH - 0xD083: 0x8883, //CJK UNIFIED IDEOGRAPH - 0xD084: 0x8886, //CJK UNIFIED IDEOGRAPH - 0xD085: 0x8887, //CJK UNIFIED IDEOGRAPH - 0xD086: 0x8889, //CJK UNIFIED IDEOGRAPH - 0xD087: 0x888A, //CJK UNIFIED IDEOGRAPH - 0xD088: 0x888C, //CJK UNIFIED IDEOGRAPH - 0xD089: 0x888E, //CJK UNIFIED IDEOGRAPH - 0xD08A: 0x888F, //CJK UNIFIED IDEOGRAPH - 0xD08B: 0x8890, //CJK UNIFIED IDEOGRAPH - 0xD08C: 0x8891, //CJK UNIFIED IDEOGRAPH - 0xD08D: 0x8893, //CJK UNIFIED IDEOGRAPH - 0xD08E: 0x8894, //CJK UNIFIED IDEOGRAPH - 0xD08F: 0x8895, //CJK UNIFIED IDEOGRAPH - 0xD090: 0x8897, //CJK UNIFIED IDEOGRAPH - 0xD091: 0x8898, //CJK UNIFIED IDEOGRAPH - 0xD092: 0x8899, //CJK UNIFIED IDEOGRAPH - 0xD093: 0x889A, //CJK UNIFIED IDEOGRAPH - 0xD094: 0x889B, //CJK UNIFIED IDEOGRAPH - 0xD095: 0x889D, //CJK UNIFIED IDEOGRAPH - 0xD096: 0x889E, //CJK UNIFIED IDEOGRAPH - 0xD097: 0x889F, //CJK UNIFIED IDEOGRAPH - 0xD098: 0x88A0, //CJK UNIFIED IDEOGRAPH - 0xD099: 0x88A1, //CJK UNIFIED IDEOGRAPH - 0xD09A: 0x88A3, //CJK UNIFIED IDEOGRAPH - 0xD09B: 0x88A5, //CJK UNIFIED IDEOGRAPH - 0xD09C: 0x88A6, //CJK UNIFIED IDEOGRAPH - 0xD09D: 0x88A7, //CJK UNIFIED IDEOGRAPH - 0xD09E: 0x88A8, //CJK UNIFIED IDEOGRAPH - 0xD09F: 0x88A9, //CJK UNIFIED IDEOGRAPH - 0xD0A0: 0x88AA, //CJK UNIFIED IDEOGRAPH - 0xD0A1: 0x5C0F, //CJK UNIFIED IDEOGRAPH - 0xD0A2: 0x5B5D, //CJK UNIFIED IDEOGRAPH - 0xD0A3: 0x6821, //CJK UNIFIED IDEOGRAPH - 0xD0A4: 0x8096, //CJK UNIFIED IDEOGRAPH - 0xD0A5: 0x5578, //CJK UNIFIED IDEOGRAPH - 0xD0A6: 0x7B11, //CJK UNIFIED IDEOGRAPH - 0xD0A7: 0x6548, //CJK UNIFIED IDEOGRAPH - 0xD0A8: 0x6954, //CJK UNIFIED IDEOGRAPH - 0xD0A9: 0x4E9B, //CJK UNIFIED IDEOGRAPH - 0xD0AA: 0x6B47, //CJK UNIFIED IDEOGRAPH - 0xD0AB: 0x874E, //CJK UNIFIED IDEOGRAPH - 0xD0AC: 0x978B, //CJK UNIFIED IDEOGRAPH - 0xD0AD: 0x534F, //CJK UNIFIED IDEOGRAPH - 0xD0AE: 0x631F, //CJK UNIFIED IDEOGRAPH - 0xD0AF: 0x643A, //CJK UNIFIED IDEOGRAPH - 0xD0B0: 0x90AA, //CJK UNIFIED IDEOGRAPH - 0xD0B1: 0x659C, //CJK UNIFIED IDEOGRAPH - 0xD0B2: 0x80C1, //CJK UNIFIED IDEOGRAPH - 0xD0B3: 0x8C10, //CJK UNIFIED IDEOGRAPH - 0xD0B4: 0x5199, //CJK UNIFIED IDEOGRAPH - 0xD0B5: 0x68B0, //CJK UNIFIED IDEOGRAPH - 0xD0B6: 0x5378, //CJK UNIFIED IDEOGRAPH - 0xD0B7: 0x87F9, //CJK UNIFIED IDEOGRAPH - 0xD0B8: 0x61C8, //CJK UNIFIED IDEOGRAPH - 0xD0B9: 0x6CC4, //CJK UNIFIED IDEOGRAPH - 0xD0BA: 0x6CFB, //CJK UNIFIED IDEOGRAPH - 0xD0BB: 0x8C22, //CJK UNIFIED IDEOGRAPH - 0xD0BC: 0x5C51, //CJK UNIFIED IDEOGRAPH - 0xD0BD: 0x85AA, //CJK UNIFIED IDEOGRAPH - 0xD0BE: 0x82AF, //CJK UNIFIED IDEOGRAPH - 0xD0BF: 0x950C, //CJK UNIFIED IDEOGRAPH - 0xD0C0: 0x6B23, //CJK UNIFIED IDEOGRAPH - 0xD0C1: 0x8F9B, //CJK UNIFIED IDEOGRAPH - 0xD0C2: 0x65B0, //CJK UNIFIED IDEOGRAPH - 0xD0C3: 0x5FFB, //CJK UNIFIED IDEOGRAPH - 0xD0C4: 0x5FC3, //CJK UNIFIED IDEOGRAPH - 0xD0C5: 0x4FE1, //CJK UNIFIED IDEOGRAPH - 0xD0C6: 0x8845, //CJK UNIFIED IDEOGRAPH - 0xD0C7: 0x661F, //CJK UNIFIED IDEOGRAPH - 0xD0C8: 0x8165, //CJK UNIFIED IDEOGRAPH - 0xD0C9: 0x7329, //CJK UNIFIED IDEOGRAPH - 0xD0CA: 0x60FA, //CJK UNIFIED IDEOGRAPH - 0xD0CB: 0x5174, //CJK UNIFIED IDEOGRAPH - 0xD0CC: 0x5211, //CJK UNIFIED IDEOGRAPH - 0xD0CD: 0x578B, //CJK UNIFIED IDEOGRAPH - 0xD0CE: 0x5F62, //CJK UNIFIED IDEOGRAPH - 0xD0CF: 0x90A2, //CJK UNIFIED IDEOGRAPH - 0xD0D0: 0x884C, //CJK UNIFIED IDEOGRAPH - 0xD0D1: 0x9192, //CJK UNIFIED IDEOGRAPH - 0xD0D2: 0x5E78, //CJK UNIFIED IDEOGRAPH - 0xD0D3: 0x674F, //CJK UNIFIED IDEOGRAPH - 0xD0D4: 0x6027, //CJK UNIFIED IDEOGRAPH - 0xD0D5: 0x59D3, //CJK UNIFIED IDEOGRAPH - 0xD0D6: 0x5144, //CJK UNIFIED IDEOGRAPH - 0xD0D7: 0x51F6, //CJK UNIFIED IDEOGRAPH - 0xD0D8: 0x80F8, //CJK UNIFIED IDEOGRAPH - 0xD0D9: 0x5308, //CJK UNIFIED IDEOGRAPH - 0xD0DA: 0x6C79, //CJK UNIFIED IDEOGRAPH - 0xD0DB: 0x96C4, //CJK UNIFIED IDEOGRAPH - 0xD0DC: 0x718A, //CJK UNIFIED IDEOGRAPH - 0xD0DD: 0x4F11, //CJK UNIFIED IDEOGRAPH - 0xD0DE: 0x4FEE, //CJK UNIFIED IDEOGRAPH - 0xD0DF: 0x7F9E, //CJK UNIFIED IDEOGRAPH - 0xD0E0: 0x673D, //CJK UNIFIED IDEOGRAPH - 0xD0E1: 0x55C5, //CJK UNIFIED IDEOGRAPH - 0xD0E2: 0x9508, //CJK UNIFIED IDEOGRAPH - 0xD0E3: 0x79C0, //CJK UNIFIED IDEOGRAPH - 0xD0E4: 0x8896, //CJK UNIFIED IDEOGRAPH - 0xD0E5: 0x7EE3, //CJK UNIFIED IDEOGRAPH - 0xD0E6: 0x589F, //CJK UNIFIED IDEOGRAPH - 0xD0E7: 0x620C, //CJK UNIFIED IDEOGRAPH - 0xD0E8: 0x9700, //CJK UNIFIED IDEOGRAPH - 0xD0E9: 0x865A, //CJK UNIFIED IDEOGRAPH - 0xD0EA: 0x5618, //CJK UNIFIED IDEOGRAPH - 0xD0EB: 0x987B, //CJK UNIFIED IDEOGRAPH - 0xD0EC: 0x5F90, //CJK UNIFIED IDEOGRAPH - 0xD0ED: 0x8BB8, //CJK UNIFIED IDEOGRAPH - 0xD0EE: 0x84C4, //CJK UNIFIED IDEOGRAPH - 0xD0EF: 0x9157, //CJK UNIFIED IDEOGRAPH - 0xD0F0: 0x53D9, //CJK UNIFIED IDEOGRAPH - 0xD0F1: 0x65ED, //CJK UNIFIED IDEOGRAPH - 0xD0F2: 0x5E8F, //CJK UNIFIED IDEOGRAPH - 0xD0F3: 0x755C, //CJK UNIFIED IDEOGRAPH - 0xD0F4: 0x6064, //CJK UNIFIED IDEOGRAPH - 0xD0F5: 0x7D6E, //CJK UNIFIED IDEOGRAPH - 0xD0F6: 0x5A7F, //CJK UNIFIED IDEOGRAPH - 0xD0F7: 0x7EEA, //CJK UNIFIED IDEOGRAPH - 0xD0F8: 0x7EED, //CJK UNIFIED IDEOGRAPH - 0xD0F9: 0x8F69, //CJK UNIFIED IDEOGRAPH - 0xD0FA: 0x55A7, //CJK UNIFIED IDEOGRAPH - 0xD0FB: 0x5BA3, //CJK UNIFIED IDEOGRAPH - 0xD0FC: 0x60AC, //CJK UNIFIED IDEOGRAPH - 0xD0FD: 0x65CB, //CJK UNIFIED IDEOGRAPH - 0xD0FE: 0x7384, //CJK UNIFIED IDEOGRAPH - 0xD140: 0x88AC, //CJK UNIFIED IDEOGRAPH - 0xD141: 0x88AE, //CJK UNIFIED IDEOGRAPH - 0xD142: 0x88AF, //CJK UNIFIED IDEOGRAPH - 0xD143: 0x88B0, //CJK UNIFIED IDEOGRAPH - 0xD144: 0x88B2, //CJK UNIFIED IDEOGRAPH - 0xD145: 0x88B3, //CJK UNIFIED IDEOGRAPH - 0xD146: 0x88B4, //CJK UNIFIED IDEOGRAPH - 0xD147: 0x88B5, //CJK UNIFIED IDEOGRAPH - 0xD148: 0x88B6, //CJK UNIFIED IDEOGRAPH - 0xD149: 0x88B8, //CJK UNIFIED IDEOGRAPH - 0xD14A: 0x88B9, //CJK UNIFIED IDEOGRAPH - 0xD14B: 0x88BA, //CJK UNIFIED IDEOGRAPH - 0xD14C: 0x88BB, //CJK UNIFIED IDEOGRAPH - 0xD14D: 0x88BD, //CJK UNIFIED IDEOGRAPH - 0xD14E: 0x88BE, //CJK UNIFIED IDEOGRAPH - 0xD14F: 0x88BF, //CJK UNIFIED IDEOGRAPH - 0xD150: 0x88C0, //CJK UNIFIED IDEOGRAPH - 0xD151: 0x88C3, //CJK UNIFIED IDEOGRAPH - 0xD152: 0x88C4, //CJK UNIFIED IDEOGRAPH - 0xD153: 0x88C7, //CJK UNIFIED IDEOGRAPH - 0xD154: 0x88C8, //CJK UNIFIED IDEOGRAPH - 0xD155: 0x88CA, //CJK UNIFIED IDEOGRAPH - 0xD156: 0x88CB, //CJK UNIFIED IDEOGRAPH - 0xD157: 0x88CC, //CJK UNIFIED IDEOGRAPH - 0xD158: 0x88CD, //CJK UNIFIED IDEOGRAPH - 0xD159: 0x88CF, //CJK UNIFIED IDEOGRAPH - 0xD15A: 0x88D0, //CJK UNIFIED IDEOGRAPH - 0xD15B: 0x88D1, //CJK UNIFIED IDEOGRAPH - 0xD15C: 0x88D3, //CJK UNIFIED IDEOGRAPH - 0xD15D: 0x88D6, //CJK UNIFIED IDEOGRAPH - 0xD15E: 0x88D7, //CJK UNIFIED IDEOGRAPH - 0xD15F: 0x88DA, //CJK UNIFIED IDEOGRAPH - 0xD160: 0x88DB, //CJK UNIFIED IDEOGRAPH - 0xD161: 0x88DC, //CJK UNIFIED IDEOGRAPH - 0xD162: 0x88DD, //CJK UNIFIED IDEOGRAPH - 0xD163: 0x88DE, //CJK UNIFIED IDEOGRAPH - 0xD164: 0x88E0, //CJK UNIFIED IDEOGRAPH - 0xD165: 0x88E1, //CJK UNIFIED IDEOGRAPH - 0xD166: 0x88E6, //CJK UNIFIED IDEOGRAPH - 0xD167: 0x88E7, //CJK UNIFIED IDEOGRAPH - 0xD168: 0x88E9, //CJK UNIFIED IDEOGRAPH - 0xD169: 0x88EA, //CJK UNIFIED IDEOGRAPH - 0xD16A: 0x88EB, //CJK UNIFIED IDEOGRAPH - 0xD16B: 0x88EC, //CJK UNIFIED IDEOGRAPH - 0xD16C: 0x88ED, //CJK UNIFIED IDEOGRAPH - 0xD16D: 0x88EE, //CJK UNIFIED IDEOGRAPH - 0xD16E: 0x88EF, //CJK UNIFIED IDEOGRAPH - 0xD16F: 0x88F2, //CJK UNIFIED IDEOGRAPH - 0xD170: 0x88F5, //CJK UNIFIED IDEOGRAPH - 0xD171: 0x88F6, //CJK UNIFIED IDEOGRAPH - 0xD172: 0x88F7, //CJK UNIFIED IDEOGRAPH - 0xD173: 0x88FA, //CJK UNIFIED IDEOGRAPH - 0xD174: 0x88FB, //CJK UNIFIED IDEOGRAPH - 0xD175: 0x88FD, //CJK UNIFIED IDEOGRAPH - 0xD176: 0x88FF, //CJK UNIFIED IDEOGRAPH - 0xD177: 0x8900, //CJK UNIFIED IDEOGRAPH - 0xD178: 0x8901, //CJK UNIFIED IDEOGRAPH - 0xD179: 0x8903, //CJK UNIFIED IDEOGRAPH - 0xD17A: 0x8904, //CJK UNIFIED IDEOGRAPH - 0xD17B: 0x8905, //CJK UNIFIED IDEOGRAPH - 0xD17C: 0x8906, //CJK UNIFIED IDEOGRAPH - 0xD17D: 0x8907, //CJK UNIFIED IDEOGRAPH - 0xD17E: 0x8908, //CJK UNIFIED IDEOGRAPH - 0xD180: 0x8909, //CJK UNIFIED IDEOGRAPH - 0xD181: 0x890B, //CJK UNIFIED IDEOGRAPH - 0xD182: 0x890C, //CJK UNIFIED IDEOGRAPH - 0xD183: 0x890D, //CJK UNIFIED IDEOGRAPH - 0xD184: 0x890E, //CJK UNIFIED IDEOGRAPH - 0xD185: 0x890F, //CJK UNIFIED IDEOGRAPH - 0xD186: 0x8911, //CJK UNIFIED IDEOGRAPH - 0xD187: 0x8914, //CJK UNIFIED IDEOGRAPH - 0xD188: 0x8915, //CJK UNIFIED IDEOGRAPH - 0xD189: 0x8916, //CJK UNIFIED IDEOGRAPH - 0xD18A: 0x8917, //CJK UNIFIED IDEOGRAPH - 0xD18B: 0x8918, //CJK UNIFIED IDEOGRAPH - 0xD18C: 0x891C, //CJK UNIFIED IDEOGRAPH - 0xD18D: 0x891D, //CJK UNIFIED IDEOGRAPH - 0xD18E: 0x891E, //CJK UNIFIED IDEOGRAPH - 0xD18F: 0x891F, //CJK UNIFIED IDEOGRAPH - 0xD190: 0x8920, //CJK UNIFIED IDEOGRAPH - 0xD191: 0x8922, //CJK UNIFIED IDEOGRAPH - 0xD192: 0x8923, //CJK UNIFIED IDEOGRAPH - 0xD193: 0x8924, //CJK UNIFIED IDEOGRAPH - 0xD194: 0x8926, //CJK UNIFIED IDEOGRAPH - 0xD195: 0x8927, //CJK UNIFIED IDEOGRAPH - 0xD196: 0x8928, //CJK UNIFIED IDEOGRAPH - 0xD197: 0x8929, //CJK UNIFIED IDEOGRAPH - 0xD198: 0x892C, //CJK UNIFIED IDEOGRAPH - 0xD199: 0x892D, //CJK UNIFIED IDEOGRAPH - 0xD19A: 0x892E, //CJK UNIFIED IDEOGRAPH - 0xD19B: 0x892F, //CJK UNIFIED IDEOGRAPH - 0xD19C: 0x8931, //CJK UNIFIED IDEOGRAPH - 0xD19D: 0x8932, //CJK UNIFIED IDEOGRAPH - 0xD19E: 0x8933, //CJK UNIFIED IDEOGRAPH - 0xD19F: 0x8935, //CJK UNIFIED IDEOGRAPH - 0xD1A0: 0x8937, //CJK UNIFIED IDEOGRAPH - 0xD1A1: 0x9009, //CJK UNIFIED IDEOGRAPH - 0xD1A2: 0x7663, //CJK UNIFIED IDEOGRAPH - 0xD1A3: 0x7729, //CJK UNIFIED IDEOGRAPH - 0xD1A4: 0x7EDA, //CJK UNIFIED IDEOGRAPH - 0xD1A5: 0x9774, //CJK UNIFIED IDEOGRAPH - 0xD1A6: 0x859B, //CJK UNIFIED IDEOGRAPH - 0xD1A7: 0x5B66, //CJK UNIFIED IDEOGRAPH - 0xD1A8: 0x7A74, //CJK UNIFIED IDEOGRAPH - 0xD1A9: 0x96EA, //CJK UNIFIED IDEOGRAPH - 0xD1AA: 0x8840, //CJK UNIFIED IDEOGRAPH - 0xD1AB: 0x52CB, //CJK UNIFIED IDEOGRAPH - 0xD1AC: 0x718F, //CJK UNIFIED IDEOGRAPH - 0xD1AD: 0x5FAA, //CJK UNIFIED IDEOGRAPH - 0xD1AE: 0x65EC, //CJK UNIFIED IDEOGRAPH - 0xD1AF: 0x8BE2, //CJK UNIFIED IDEOGRAPH - 0xD1B0: 0x5BFB, //CJK UNIFIED IDEOGRAPH - 0xD1B1: 0x9A6F, //CJK UNIFIED IDEOGRAPH - 0xD1B2: 0x5DE1, //CJK UNIFIED IDEOGRAPH - 0xD1B3: 0x6B89, //CJK UNIFIED IDEOGRAPH - 0xD1B4: 0x6C5B, //CJK UNIFIED IDEOGRAPH - 0xD1B5: 0x8BAD, //CJK UNIFIED IDEOGRAPH - 0xD1B6: 0x8BAF, //CJK UNIFIED IDEOGRAPH - 0xD1B7: 0x900A, //CJK UNIFIED IDEOGRAPH - 0xD1B8: 0x8FC5, //CJK UNIFIED IDEOGRAPH - 0xD1B9: 0x538B, //CJK UNIFIED IDEOGRAPH - 0xD1BA: 0x62BC, //CJK UNIFIED IDEOGRAPH - 0xD1BB: 0x9E26, //CJK UNIFIED IDEOGRAPH - 0xD1BC: 0x9E2D, //CJK UNIFIED IDEOGRAPH - 0xD1BD: 0x5440, //CJK UNIFIED IDEOGRAPH - 0xD1BE: 0x4E2B, //CJK UNIFIED IDEOGRAPH - 0xD1BF: 0x82BD, //CJK UNIFIED IDEOGRAPH - 0xD1C0: 0x7259, //CJK UNIFIED IDEOGRAPH - 0xD1C1: 0x869C, //CJK UNIFIED IDEOGRAPH - 0xD1C2: 0x5D16, //CJK UNIFIED IDEOGRAPH - 0xD1C3: 0x8859, //CJK UNIFIED IDEOGRAPH - 0xD1C4: 0x6DAF, //CJK UNIFIED IDEOGRAPH - 0xD1C5: 0x96C5, //CJK UNIFIED IDEOGRAPH - 0xD1C6: 0x54D1, //CJK UNIFIED IDEOGRAPH - 0xD1C7: 0x4E9A, //CJK UNIFIED IDEOGRAPH - 0xD1C8: 0x8BB6, //CJK UNIFIED IDEOGRAPH - 0xD1C9: 0x7109, //CJK UNIFIED IDEOGRAPH - 0xD1CA: 0x54BD, //CJK UNIFIED IDEOGRAPH - 0xD1CB: 0x9609, //CJK UNIFIED IDEOGRAPH - 0xD1CC: 0x70DF, //CJK UNIFIED IDEOGRAPH - 0xD1CD: 0x6DF9, //CJK UNIFIED IDEOGRAPH - 0xD1CE: 0x76D0, //CJK UNIFIED IDEOGRAPH - 0xD1CF: 0x4E25, //CJK UNIFIED IDEOGRAPH - 0xD1D0: 0x7814, //CJK UNIFIED IDEOGRAPH - 0xD1D1: 0x8712, //CJK UNIFIED IDEOGRAPH - 0xD1D2: 0x5CA9, //CJK UNIFIED IDEOGRAPH - 0xD1D3: 0x5EF6, //CJK UNIFIED IDEOGRAPH - 0xD1D4: 0x8A00, //CJK UNIFIED IDEOGRAPH - 0xD1D5: 0x989C, //CJK UNIFIED IDEOGRAPH - 0xD1D6: 0x960E, //CJK UNIFIED IDEOGRAPH - 0xD1D7: 0x708E, //CJK UNIFIED IDEOGRAPH - 0xD1D8: 0x6CBF, //CJK UNIFIED IDEOGRAPH - 0xD1D9: 0x5944, //CJK UNIFIED IDEOGRAPH - 0xD1DA: 0x63A9, //CJK UNIFIED IDEOGRAPH - 0xD1DB: 0x773C, //CJK UNIFIED IDEOGRAPH - 0xD1DC: 0x884D, //CJK UNIFIED IDEOGRAPH - 0xD1DD: 0x6F14, //CJK UNIFIED IDEOGRAPH - 0xD1DE: 0x8273, //CJK UNIFIED IDEOGRAPH - 0xD1DF: 0x5830, //CJK UNIFIED IDEOGRAPH - 0xD1E0: 0x71D5, //CJK UNIFIED IDEOGRAPH - 0xD1E1: 0x538C, //CJK UNIFIED IDEOGRAPH - 0xD1E2: 0x781A, //CJK UNIFIED IDEOGRAPH - 0xD1E3: 0x96C1, //CJK UNIFIED IDEOGRAPH - 0xD1E4: 0x5501, //CJK UNIFIED IDEOGRAPH - 0xD1E5: 0x5F66, //CJK UNIFIED IDEOGRAPH - 0xD1E6: 0x7130, //CJK UNIFIED IDEOGRAPH - 0xD1E7: 0x5BB4, //CJK UNIFIED IDEOGRAPH - 0xD1E8: 0x8C1A, //CJK UNIFIED IDEOGRAPH - 0xD1E9: 0x9A8C, //CJK UNIFIED IDEOGRAPH - 0xD1EA: 0x6B83, //CJK UNIFIED IDEOGRAPH - 0xD1EB: 0x592E, //CJK UNIFIED IDEOGRAPH - 0xD1EC: 0x9E2F, //CJK UNIFIED IDEOGRAPH - 0xD1ED: 0x79E7, //CJK UNIFIED IDEOGRAPH - 0xD1EE: 0x6768, //CJK UNIFIED IDEOGRAPH - 0xD1EF: 0x626C, //CJK UNIFIED IDEOGRAPH - 0xD1F0: 0x4F6F, //CJK UNIFIED IDEOGRAPH - 0xD1F1: 0x75A1, //CJK UNIFIED IDEOGRAPH - 0xD1F2: 0x7F8A, //CJK UNIFIED IDEOGRAPH - 0xD1F3: 0x6D0B, //CJK UNIFIED IDEOGRAPH - 0xD1F4: 0x9633, //CJK UNIFIED IDEOGRAPH - 0xD1F5: 0x6C27, //CJK UNIFIED IDEOGRAPH - 0xD1F6: 0x4EF0, //CJK UNIFIED IDEOGRAPH - 0xD1F7: 0x75D2, //CJK UNIFIED IDEOGRAPH - 0xD1F8: 0x517B, //CJK UNIFIED IDEOGRAPH - 0xD1F9: 0x6837, //CJK UNIFIED IDEOGRAPH - 0xD1FA: 0x6F3E, //CJK UNIFIED IDEOGRAPH - 0xD1FB: 0x9080, //CJK UNIFIED IDEOGRAPH - 0xD1FC: 0x8170, //CJK UNIFIED IDEOGRAPH - 0xD1FD: 0x5996, //CJK UNIFIED IDEOGRAPH - 0xD1FE: 0x7476, //CJK UNIFIED IDEOGRAPH - 0xD240: 0x8938, //CJK UNIFIED IDEOGRAPH - 0xD241: 0x8939, //CJK UNIFIED IDEOGRAPH - 0xD242: 0x893A, //CJK UNIFIED IDEOGRAPH - 0xD243: 0x893B, //CJK UNIFIED IDEOGRAPH - 0xD244: 0x893C, //CJK UNIFIED IDEOGRAPH - 0xD245: 0x893D, //CJK UNIFIED IDEOGRAPH - 0xD246: 0x893E, //CJK UNIFIED IDEOGRAPH - 0xD247: 0x893F, //CJK UNIFIED IDEOGRAPH - 0xD248: 0x8940, //CJK UNIFIED IDEOGRAPH - 0xD249: 0x8942, //CJK UNIFIED IDEOGRAPH - 0xD24A: 0x8943, //CJK UNIFIED IDEOGRAPH - 0xD24B: 0x8945, //CJK UNIFIED IDEOGRAPH - 0xD24C: 0x8946, //CJK UNIFIED IDEOGRAPH - 0xD24D: 0x8947, //CJK UNIFIED IDEOGRAPH - 0xD24E: 0x8948, //CJK UNIFIED IDEOGRAPH - 0xD24F: 0x8949, //CJK UNIFIED IDEOGRAPH - 0xD250: 0x894A, //CJK UNIFIED IDEOGRAPH - 0xD251: 0x894B, //CJK UNIFIED IDEOGRAPH - 0xD252: 0x894C, //CJK UNIFIED IDEOGRAPH - 0xD253: 0x894D, //CJK UNIFIED IDEOGRAPH - 0xD254: 0x894E, //CJK UNIFIED IDEOGRAPH - 0xD255: 0x894F, //CJK UNIFIED IDEOGRAPH - 0xD256: 0x8950, //CJK UNIFIED IDEOGRAPH - 0xD257: 0x8951, //CJK UNIFIED IDEOGRAPH - 0xD258: 0x8952, //CJK UNIFIED IDEOGRAPH - 0xD259: 0x8953, //CJK UNIFIED IDEOGRAPH - 0xD25A: 0x8954, //CJK UNIFIED IDEOGRAPH - 0xD25B: 0x8955, //CJK UNIFIED IDEOGRAPH - 0xD25C: 0x8956, //CJK UNIFIED IDEOGRAPH - 0xD25D: 0x8957, //CJK UNIFIED IDEOGRAPH - 0xD25E: 0x8958, //CJK UNIFIED IDEOGRAPH - 0xD25F: 0x8959, //CJK UNIFIED IDEOGRAPH - 0xD260: 0x895A, //CJK UNIFIED IDEOGRAPH - 0xD261: 0x895B, //CJK UNIFIED IDEOGRAPH - 0xD262: 0x895C, //CJK UNIFIED IDEOGRAPH - 0xD263: 0x895D, //CJK UNIFIED IDEOGRAPH - 0xD264: 0x8960, //CJK UNIFIED IDEOGRAPH - 0xD265: 0x8961, //CJK UNIFIED IDEOGRAPH - 0xD266: 0x8962, //CJK UNIFIED IDEOGRAPH - 0xD267: 0x8963, //CJK UNIFIED IDEOGRAPH - 0xD268: 0x8964, //CJK UNIFIED IDEOGRAPH - 0xD269: 0x8965, //CJK UNIFIED IDEOGRAPH - 0xD26A: 0x8967, //CJK UNIFIED IDEOGRAPH - 0xD26B: 0x8968, //CJK UNIFIED IDEOGRAPH - 0xD26C: 0x8969, //CJK UNIFIED IDEOGRAPH - 0xD26D: 0x896A, //CJK UNIFIED IDEOGRAPH - 0xD26E: 0x896B, //CJK UNIFIED IDEOGRAPH - 0xD26F: 0x896C, //CJK UNIFIED IDEOGRAPH - 0xD270: 0x896D, //CJK UNIFIED IDEOGRAPH - 0xD271: 0x896E, //CJK UNIFIED IDEOGRAPH - 0xD272: 0x896F, //CJK UNIFIED IDEOGRAPH - 0xD273: 0x8970, //CJK UNIFIED IDEOGRAPH - 0xD274: 0x8971, //CJK UNIFIED IDEOGRAPH - 0xD275: 0x8972, //CJK UNIFIED IDEOGRAPH - 0xD276: 0x8973, //CJK UNIFIED IDEOGRAPH - 0xD277: 0x8974, //CJK UNIFIED IDEOGRAPH - 0xD278: 0x8975, //CJK UNIFIED IDEOGRAPH - 0xD279: 0x8976, //CJK UNIFIED IDEOGRAPH - 0xD27A: 0x8977, //CJK UNIFIED IDEOGRAPH - 0xD27B: 0x8978, //CJK UNIFIED IDEOGRAPH - 0xD27C: 0x8979, //CJK UNIFIED IDEOGRAPH - 0xD27D: 0x897A, //CJK UNIFIED IDEOGRAPH - 0xD27E: 0x897C, //CJK UNIFIED IDEOGRAPH - 0xD280: 0x897D, //CJK UNIFIED IDEOGRAPH - 0xD281: 0x897E, //CJK UNIFIED IDEOGRAPH - 0xD282: 0x8980, //CJK UNIFIED IDEOGRAPH - 0xD283: 0x8982, //CJK UNIFIED IDEOGRAPH - 0xD284: 0x8984, //CJK UNIFIED IDEOGRAPH - 0xD285: 0x8985, //CJK UNIFIED IDEOGRAPH - 0xD286: 0x8987, //CJK UNIFIED IDEOGRAPH - 0xD287: 0x8988, //CJK UNIFIED IDEOGRAPH - 0xD288: 0x8989, //CJK UNIFIED IDEOGRAPH - 0xD289: 0x898A, //CJK UNIFIED IDEOGRAPH - 0xD28A: 0x898B, //CJK UNIFIED IDEOGRAPH - 0xD28B: 0x898C, //CJK UNIFIED IDEOGRAPH - 0xD28C: 0x898D, //CJK UNIFIED IDEOGRAPH - 0xD28D: 0x898E, //CJK UNIFIED IDEOGRAPH - 0xD28E: 0x898F, //CJK UNIFIED IDEOGRAPH - 0xD28F: 0x8990, //CJK UNIFIED IDEOGRAPH - 0xD290: 0x8991, //CJK UNIFIED IDEOGRAPH - 0xD291: 0x8992, //CJK UNIFIED IDEOGRAPH - 0xD292: 0x8993, //CJK UNIFIED IDEOGRAPH - 0xD293: 0x8994, //CJK UNIFIED IDEOGRAPH - 0xD294: 0x8995, //CJK UNIFIED IDEOGRAPH - 0xD295: 0x8996, //CJK UNIFIED IDEOGRAPH - 0xD296: 0x8997, //CJK UNIFIED IDEOGRAPH - 0xD297: 0x8998, //CJK UNIFIED IDEOGRAPH - 0xD298: 0x8999, //CJK UNIFIED IDEOGRAPH - 0xD299: 0x899A, //CJK UNIFIED IDEOGRAPH - 0xD29A: 0x899B, //CJK UNIFIED IDEOGRAPH - 0xD29B: 0x899C, //CJK UNIFIED IDEOGRAPH - 0xD29C: 0x899D, //CJK UNIFIED IDEOGRAPH - 0xD29D: 0x899E, //CJK UNIFIED IDEOGRAPH - 0xD29E: 0x899F, //CJK UNIFIED IDEOGRAPH - 0xD29F: 0x89A0, //CJK UNIFIED IDEOGRAPH - 0xD2A0: 0x89A1, //CJK UNIFIED IDEOGRAPH - 0xD2A1: 0x6447, //CJK UNIFIED IDEOGRAPH - 0xD2A2: 0x5C27, //CJK UNIFIED IDEOGRAPH - 0xD2A3: 0x9065, //CJK UNIFIED IDEOGRAPH - 0xD2A4: 0x7A91, //CJK UNIFIED IDEOGRAPH - 0xD2A5: 0x8C23, //CJK UNIFIED IDEOGRAPH - 0xD2A6: 0x59DA, //CJK UNIFIED IDEOGRAPH - 0xD2A7: 0x54AC, //CJK UNIFIED IDEOGRAPH - 0xD2A8: 0x8200, //CJK UNIFIED IDEOGRAPH - 0xD2A9: 0x836F, //CJK UNIFIED IDEOGRAPH - 0xD2AA: 0x8981, //CJK UNIFIED IDEOGRAPH - 0xD2AB: 0x8000, //CJK UNIFIED IDEOGRAPH - 0xD2AC: 0x6930, //CJK UNIFIED IDEOGRAPH - 0xD2AD: 0x564E, //CJK UNIFIED IDEOGRAPH - 0xD2AE: 0x8036, //CJK UNIFIED IDEOGRAPH - 0xD2AF: 0x7237, //CJK UNIFIED IDEOGRAPH - 0xD2B0: 0x91CE, //CJK UNIFIED IDEOGRAPH - 0xD2B1: 0x51B6, //CJK UNIFIED IDEOGRAPH - 0xD2B2: 0x4E5F, //CJK UNIFIED IDEOGRAPH - 0xD2B3: 0x9875, //CJK UNIFIED IDEOGRAPH - 0xD2B4: 0x6396, //CJK UNIFIED IDEOGRAPH - 0xD2B5: 0x4E1A, //CJK UNIFIED IDEOGRAPH - 0xD2B6: 0x53F6, //CJK UNIFIED IDEOGRAPH - 0xD2B7: 0x66F3, //CJK UNIFIED IDEOGRAPH - 0xD2B8: 0x814B, //CJK UNIFIED IDEOGRAPH - 0xD2B9: 0x591C, //CJK UNIFIED IDEOGRAPH - 0xD2BA: 0x6DB2, //CJK UNIFIED IDEOGRAPH - 0xD2BB: 0x4E00, //CJK UNIFIED IDEOGRAPH - 0xD2BC: 0x58F9, //CJK UNIFIED IDEOGRAPH - 0xD2BD: 0x533B, //CJK UNIFIED IDEOGRAPH - 0xD2BE: 0x63D6, //CJK UNIFIED IDEOGRAPH - 0xD2BF: 0x94F1, //CJK UNIFIED IDEOGRAPH - 0xD2C0: 0x4F9D, //CJK UNIFIED IDEOGRAPH - 0xD2C1: 0x4F0A, //CJK UNIFIED IDEOGRAPH - 0xD2C2: 0x8863, //CJK UNIFIED IDEOGRAPH - 0xD2C3: 0x9890, //CJK UNIFIED IDEOGRAPH - 0xD2C4: 0x5937, //CJK UNIFIED IDEOGRAPH - 0xD2C5: 0x9057, //CJK UNIFIED IDEOGRAPH - 0xD2C6: 0x79FB, //CJK UNIFIED IDEOGRAPH - 0xD2C7: 0x4EEA, //CJK UNIFIED IDEOGRAPH - 0xD2C8: 0x80F0, //CJK UNIFIED IDEOGRAPH - 0xD2C9: 0x7591, //CJK UNIFIED IDEOGRAPH - 0xD2CA: 0x6C82, //CJK UNIFIED IDEOGRAPH - 0xD2CB: 0x5B9C, //CJK UNIFIED IDEOGRAPH - 0xD2CC: 0x59E8, //CJK UNIFIED IDEOGRAPH - 0xD2CD: 0x5F5D, //CJK UNIFIED IDEOGRAPH - 0xD2CE: 0x6905, //CJK UNIFIED IDEOGRAPH - 0xD2CF: 0x8681, //CJK UNIFIED IDEOGRAPH - 0xD2D0: 0x501A, //CJK UNIFIED IDEOGRAPH - 0xD2D1: 0x5DF2, //CJK UNIFIED IDEOGRAPH - 0xD2D2: 0x4E59, //CJK UNIFIED IDEOGRAPH - 0xD2D3: 0x77E3, //CJK UNIFIED IDEOGRAPH - 0xD2D4: 0x4EE5, //CJK UNIFIED IDEOGRAPH - 0xD2D5: 0x827A, //CJK UNIFIED IDEOGRAPH - 0xD2D6: 0x6291, //CJK UNIFIED IDEOGRAPH - 0xD2D7: 0x6613, //CJK UNIFIED IDEOGRAPH - 0xD2D8: 0x9091, //CJK UNIFIED IDEOGRAPH - 0xD2D9: 0x5C79, //CJK UNIFIED IDEOGRAPH - 0xD2DA: 0x4EBF, //CJK UNIFIED IDEOGRAPH - 0xD2DB: 0x5F79, //CJK UNIFIED IDEOGRAPH - 0xD2DC: 0x81C6, //CJK UNIFIED IDEOGRAPH - 0xD2DD: 0x9038, //CJK UNIFIED IDEOGRAPH - 0xD2DE: 0x8084, //CJK UNIFIED IDEOGRAPH - 0xD2DF: 0x75AB, //CJK UNIFIED IDEOGRAPH - 0xD2E0: 0x4EA6, //CJK UNIFIED IDEOGRAPH - 0xD2E1: 0x88D4, //CJK UNIFIED IDEOGRAPH - 0xD2E2: 0x610F, //CJK UNIFIED IDEOGRAPH - 0xD2E3: 0x6BC5, //CJK UNIFIED IDEOGRAPH - 0xD2E4: 0x5FC6, //CJK UNIFIED IDEOGRAPH - 0xD2E5: 0x4E49, //CJK UNIFIED IDEOGRAPH - 0xD2E6: 0x76CA, //CJK UNIFIED IDEOGRAPH - 0xD2E7: 0x6EA2, //CJK UNIFIED IDEOGRAPH - 0xD2E8: 0x8BE3, //CJK UNIFIED IDEOGRAPH - 0xD2E9: 0x8BAE, //CJK UNIFIED IDEOGRAPH - 0xD2EA: 0x8C0A, //CJK UNIFIED IDEOGRAPH - 0xD2EB: 0x8BD1, //CJK UNIFIED IDEOGRAPH - 0xD2EC: 0x5F02, //CJK UNIFIED IDEOGRAPH - 0xD2ED: 0x7FFC, //CJK UNIFIED IDEOGRAPH - 0xD2EE: 0x7FCC, //CJK UNIFIED IDEOGRAPH - 0xD2EF: 0x7ECE, //CJK UNIFIED IDEOGRAPH - 0xD2F0: 0x8335, //CJK UNIFIED IDEOGRAPH - 0xD2F1: 0x836B, //CJK UNIFIED IDEOGRAPH - 0xD2F2: 0x56E0, //CJK UNIFIED IDEOGRAPH - 0xD2F3: 0x6BB7, //CJK UNIFIED IDEOGRAPH - 0xD2F4: 0x97F3, //CJK UNIFIED IDEOGRAPH - 0xD2F5: 0x9634, //CJK UNIFIED IDEOGRAPH - 0xD2F6: 0x59FB, //CJK UNIFIED IDEOGRAPH - 0xD2F7: 0x541F, //CJK UNIFIED IDEOGRAPH - 0xD2F8: 0x94F6, //CJK UNIFIED IDEOGRAPH - 0xD2F9: 0x6DEB, //CJK UNIFIED IDEOGRAPH - 0xD2FA: 0x5BC5, //CJK UNIFIED IDEOGRAPH - 0xD2FB: 0x996E, //CJK UNIFIED IDEOGRAPH - 0xD2FC: 0x5C39, //CJK UNIFIED IDEOGRAPH - 0xD2FD: 0x5F15, //CJK UNIFIED IDEOGRAPH - 0xD2FE: 0x9690, //CJK UNIFIED IDEOGRAPH - 0xD340: 0x89A2, //CJK UNIFIED IDEOGRAPH - 0xD341: 0x89A3, //CJK UNIFIED IDEOGRAPH - 0xD342: 0x89A4, //CJK UNIFIED IDEOGRAPH - 0xD343: 0x89A5, //CJK UNIFIED IDEOGRAPH - 0xD344: 0x89A6, //CJK UNIFIED IDEOGRAPH - 0xD345: 0x89A7, //CJK UNIFIED IDEOGRAPH - 0xD346: 0x89A8, //CJK UNIFIED IDEOGRAPH - 0xD347: 0x89A9, //CJK UNIFIED IDEOGRAPH - 0xD348: 0x89AA, //CJK UNIFIED IDEOGRAPH - 0xD349: 0x89AB, //CJK UNIFIED IDEOGRAPH - 0xD34A: 0x89AC, //CJK UNIFIED IDEOGRAPH - 0xD34B: 0x89AD, //CJK UNIFIED IDEOGRAPH - 0xD34C: 0x89AE, //CJK UNIFIED IDEOGRAPH - 0xD34D: 0x89AF, //CJK UNIFIED IDEOGRAPH - 0xD34E: 0x89B0, //CJK UNIFIED IDEOGRAPH - 0xD34F: 0x89B1, //CJK UNIFIED IDEOGRAPH - 0xD350: 0x89B2, //CJK UNIFIED IDEOGRAPH - 0xD351: 0x89B3, //CJK UNIFIED IDEOGRAPH - 0xD352: 0x89B4, //CJK UNIFIED IDEOGRAPH - 0xD353: 0x89B5, //CJK UNIFIED IDEOGRAPH - 0xD354: 0x89B6, //CJK UNIFIED IDEOGRAPH - 0xD355: 0x89B7, //CJK UNIFIED IDEOGRAPH - 0xD356: 0x89B8, //CJK UNIFIED IDEOGRAPH - 0xD357: 0x89B9, //CJK UNIFIED IDEOGRAPH - 0xD358: 0x89BA, //CJK UNIFIED IDEOGRAPH - 0xD359: 0x89BB, //CJK UNIFIED IDEOGRAPH - 0xD35A: 0x89BC, //CJK UNIFIED IDEOGRAPH - 0xD35B: 0x89BD, //CJK UNIFIED IDEOGRAPH - 0xD35C: 0x89BE, //CJK UNIFIED IDEOGRAPH - 0xD35D: 0x89BF, //CJK UNIFIED IDEOGRAPH - 0xD35E: 0x89C0, //CJK UNIFIED IDEOGRAPH - 0xD35F: 0x89C3, //CJK UNIFIED IDEOGRAPH - 0xD360: 0x89CD, //CJK UNIFIED IDEOGRAPH - 0xD361: 0x89D3, //CJK UNIFIED IDEOGRAPH - 0xD362: 0x89D4, //CJK UNIFIED IDEOGRAPH - 0xD363: 0x89D5, //CJK UNIFIED IDEOGRAPH - 0xD364: 0x89D7, //CJK UNIFIED IDEOGRAPH - 0xD365: 0x89D8, //CJK UNIFIED IDEOGRAPH - 0xD366: 0x89D9, //CJK UNIFIED IDEOGRAPH - 0xD367: 0x89DB, //CJK UNIFIED IDEOGRAPH - 0xD368: 0x89DD, //CJK UNIFIED IDEOGRAPH - 0xD369: 0x89DF, //CJK UNIFIED IDEOGRAPH - 0xD36A: 0x89E0, //CJK UNIFIED IDEOGRAPH - 0xD36B: 0x89E1, //CJK UNIFIED IDEOGRAPH - 0xD36C: 0x89E2, //CJK UNIFIED IDEOGRAPH - 0xD36D: 0x89E4, //CJK UNIFIED IDEOGRAPH - 0xD36E: 0x89E7, //CJK UNIFIED IDEOGRAPH - 0xD36F: 0x89E8, //CJK UNIFIED IDEOGRAPH - 0xD370: 0x89E9, //CJK UNIFIED IDEOGRAPH - 0xD371: 0x89EA, //CJK UNIFIED IDEOGRAPH - 0xD372: 0x89EC, //CJK UNIFIED IDEOGRAPH - 0xD373: 0x89ED, //CJK UNIFIED IDEOGRAPH - 0xD374: 0x89EE, //CJK UNIFIED IDEOGRAPH - 0xD375: 0x89F0, //CJK UNIFIED IDEOGRAPH - 0xD376: 0x89F1, //CJK UNIFIED IDEOGRAPH - 0xD377: 0x89F2, //CJK UNIFIED IDEOGRAPH - 0xD378: 0x89F4, //CJK UNIFIED IDEOGRAPH - 0xD379: 0x89F5, //CJK UNIFIED IDEOGRAPH - 0xD37A: 0x89F6, //CJK UNIFIED IDEOGRAPH - 0xD37B: 0x89F7, //CJK UNIFIED IDEOGRAPH - 0xD37C: 0x89F8, //CJK UNIFIED IDEOGRAPH - 0xD37D: 0x89F9, //CJK UNIFIED IDEOGRAPH - 0xD37E: 0x89FA, //CJK UNIFIED IDEOGRAPH - 0xD380: 0x89FB, //CJK UNIFIED IDEOGRAPH - 0xD381: 0x89FC, //CJK UNIFIED IDEOGRAPH - 0xD382: 0x89FD, //CJK UNIFIED IDEOGRAPH - 0xD383: 0x89FE, //CJK UNIFIED IDEOGRAPH - 0xD384: 0x89FF, //CJK UNIFIED IDEOGRAPH - 0xD385: 0x8A01, //CJK UNIFIED IDEOGRAPH - 0xD386: 0x8A02, //CJK UNIFIED IDEOGRAPH - 0xD387: 0x8A03, //CJK UNIFIED IDEOGRAPH - 0xD388: 0x8A04, //CJK UNIFIED IDEOGRAPH - 0xD389: 0x8A05, //CJK UNIFIED IDEOGRAPH - 0xD38A: 0x8A06, //CJK UNIFIED IDEOGRAPH - 0xD38B: 0x8A08, //CJK UNIFIED IDEOGRAPH - 0xD38C: 0x8A09, //CJK UNIFIED IDEOGRAPH - 0xD38D: 0x8A0A, //CJK UNIFIED IDEOGRAPH - 0xD38E: 0x8A0B, //CJK UNIFIED IDEOGRAPH - 0xD38F: 0x8A0C, //CJK UNIFIED IDEOGRAPH - 0xD390: 0x8A0D, //CJK UNIFIED IDEOGRAPH - 0xD391: 0x8A0E, //CJK UNIFIED IDEOGRAPH - 0xD392: 0x8A0F, //CJK UNIFIED IDEOGRAPH - 0xD393: 0x8A10, //CJK UNIFIED IDEOGRAPH - 0xD394: 0x8A11, //CJK UNIFIED IDEOGRAPH - 0xD395: 0x8A12, //CJK UNIFIED IDEOGRAPH - 0xD396: 0x8A13, //CJK UNIFIED IDEOGRAPH - 0xD397: 0x8A14, //CJK UNIFIED IDEOGRAPH - 0xD398: 0x8A15, //CJK UNIFIED IDEOGRAPH - 0xD399: 0x8A16, //CJK UNIFIED IDEOGRAPH - 0xD39A: 0x8A17, //CJK UNIFIED IDEOGRAPH - 0xD39B: 0x8A18, //CJK UNIFIED IDEOGRAPH - 0xD39C: 0x8A19, //CJK UNIFIED IDEOGRAPH - 0xD39D: 0x8A1A, //CJK UNIFIED IDEOGRAPH - 0xD39E: 0x8A1B, //CJK UNIFIED IDEOGRAPH - 0xD39F: 0x8A1C, //CJK UNIFIED IDEOGRAPH - 0xD3A0: 0x8A1D, //CJK UNIFIED IDEOGRAPH - 0xD3A1: 0x5370, //CJK UNIFIED IDEOGRAPH - 0xD3A2: 0x82F1, //CJK UNIFIED IDEOGRAPH - 0xD3A3: 0x6A31, //CJK UNIFIED IDEOGRAPH - 0xD3A4: 0x5A74, //CJK UNIFIED IDEOGRAPH - 0xD3A5: 0x9E70, //CJK UNIFIED IDEOGRAPH - 0xD3A6: 0x5E94, //CJK UNIFIED IDEOGRAPH - 0xD3A7: 0x7F28, //CJK UNIFIED IDEOGRAPH - 0xD3A8: 0x83B9, //CJK UNIFIED IDEOGRAPH - 0xD3A9: 0x8424, //CJK UNIFIED IDEOGRAPH - 0xD3AA: 0x8425, //CJK UNIFIED IDEOGRAPH - 0xD3AB: 0x8367, //CJK UNIFIED IDEOGRAPH - 0xD3AC: 0x8747, //CJK UNIFIED IDEOGRAPH - 0xD3AD: 0x8FCE, //CJK UNIFIED IDEOGRAPH - 0xD3AE: 0x8D62, //CJK UNIFIED IDEOGRAPH - 0xD3AF: 0x76C8, //CJK UNIFIED IDEOGRAPH - 0xD3B0: 0x5F71, //CJK UNIFIED IDEOGRAPH - 0xD3B1: 0x9896, //CJK UNIFIED IDEOGRAPH - 0xD3B2: 0x786C, //CJK UNIFIED IDEOGRAPH - 0xD3B3: 0x6620, //CJK UNIFIED IDEOGRAPH - 0xD3B4: 0x54DF, //CJK UNIFIED IDEOGRAPH - 0xD3B5: 0x62E5, //CJK UNIFIED IDEOGRAPH - 0xD3B6: 0x4F63, //CJK UNIFIED IDEOGRAPH - 0xD3B7: 0x81C3, //CJK UNIFIED IDEOGRAPH - 0xD3B8: 0x75C8, //CJK UNIFIED IDEOGRAPH - 0xD3B9: 0x5EB8, //CJK UNIFIED IDEOGRAPH - 0xD3BA: 0x96CD, //CJK UNIFIED IDEOGRAPH - 0xD3BB: 0x8E0A, //CJK UNIFIED IDEOGRAPH - 0xD3BC: 0x86F9, //CJK UNIFIED IDEOGRAPH - 0xD3BD: 0x548F, //CJK UNIFIED IDEOGRAPH - 0xD3BE: 0x6CF3, //CJK UNIFIED IDEOGRAPH - 0xD3BF: 0x6D8C, //CJK UNIFIED IDEOGRAPH - 0xD3C0: 0x6C38, //CJK UNIFIED IDEOGRAPH - 0xD3C1: 0x607F, //CJK UNIFIED IDEOGRAPH - 0xD3C2: 0x52C7, //CJK UNIFIED IDEOGRAPH - 0xD3C3: 0x7528, //CJK UNIFIED IDEOGRAPH - 0xD3C4: 0x5E7D, //CJK UNIFIED IDEOGRAPH - 0xD3C5: 0x4F18, //CJK UNIFIED IDEOGRAPH - 0xD3C6: 0x60A0, //CJK UNIFIED IDEOGRAPH - 0xD3C7: 0x5FE7, //CJK UNIFIED IDEOGRAPH - 0xD3C8: 0x5C24, //CJK UNIFIED IDEOGRAPH - 0xD3C9: 0x7531, //CJK UNIFIED IDEOGRAPH - 0xD3CA: 0x90AE, //CJK UNIFIED IDEOGRAPH - 0xD3CB: 0x94C0, //CJK UNIFIED IDEOGRAPH - 0xD3CC: 0x72B9, //CJK UNIFIED IDEOGRAPH - 0xD3CD: 0x6CB9, //CJK UNIFIED IDEOGRAPH - 0xD3CE: 0x6E38, //CJK UNIFIED IDEOGRAPH - 0xD3CF: 0x9149, //CJK UNIFIED IDEOGRAPH - 0xD3D0: 0x6709, //CJK UNIFIED IDEOGRAPH - 0xD3D1: 0x53CB, //CJK UNIFIED IDEOGRAPH - 0xD3D2: 0x53F3, //CJK UNIFIED IDEOGRAPH - 0xD3D3: 0x4F51, //CJK UNIFIED IDEOGRAPH - 0xD3D4: 0x91C9, //CJK UNIFIED IDEOGRAPH - 0xD3D5: 0x8BF1, //CJK UNIFIED IDEOGRAPH - 0xD3D6: 0x53C8, //CJK UNIFIED IDEOGRAPH - 0xD3D7: 0x5E7C, //CJK UNIFIED IDEOGRAPH - 0xD3D8: 0x8FC2, //CJK UNIFIED IDEOGRAPH - 0xD3D9: 0x6DE4, //CJK UNIFIED IDEOGRAPH - 0xD3DA: 0x4E8E, //CJK UNIFIED IDEOGRAPH - 0xD3DB: 0x76C2, //CJK UNIFIED IDEOGRAPH - 0xD3DC: 0x6986, //CJK UNIFIED IDEOGRAPH - 0xD3DD: 0x865E, //CJK UNIFIED IDEOGRAPH - 0xD3DE: 0x611A, //CJK UNIFIED IDEOGRAPH - 0xD3DF: 0x8206, //CJK UNIFIED IDEOGRAPH - 0xD3E0: 0x4F59, //CJK UNIFIED IDEOGRAPH - 0xD3E1: 0x4FDE, //CJK UNIFIED IDEOGRAPH - 0xD3E2: 0x903E, //CJK UNIFIED IDEOGRAPH - 0xD3E3: 0x9C7C, //CJK UNIFIED IDEOGRAPH - 0xD3E4: 0x6109, //CJK UNIFIED IDEOGRAPH - 0xD3E5: 0x6E1D, //CJK UNIFIED IDEOGRAPH - 0xD3E6: 0x6E14, //CJK UNIFIED IDEOGRAPH - 0xD3E7: 0x9685, //CJK UNIFIED IDEOGRAPH - 0xD3E8: 0x4E88, //CJK UNIFIED IDEOGRAPH - 0xD3E9: 0x5A31, //CJK UNIFIED IDEOGRAPH - 0xD3EA: 0x96E8, //CJK UNIFIED IDEOGRAPH - 0xD3EB: 0x4E0E, //CJK UNIFIED IDEOGRAPH - 0xD3EC: 0x5C7F, //CJK UNIFIED IDEOGRAPH - 0xD3ED: 0x79B9, //CJK UNIFIED IDEOGRAPH - 0xD3EE: 0x5B87, //CJK UNIFIED IDEOGRAPH - 0xD3EF: 0x8BED, //CJK UNIFIED IDEOGRAPH - 0xD3F0: 0x7FBD, //CJK UNIFIED IDEOGRAPH - 0xD3F1: 0x7389, //CJK UNIFIED IDEOGRAPH - 0xD3F2: 0x57DF, //CJK UNIFIED IDEOGRAPH - 0xD3F3: 0x828B, //CJK UNIFIED IDEOGRAPH - 0xD3F4: 0x90C1, //CJK UNIFIED IDEOGRAPH - 0xD3F5: 0x5401, //CJK UNIFIED IDEOGRAPH - 0xD3F6: 0x9047, //CJK UNIFIED IDEOGRAPH - 0xD3F7: 0x55BB, //CJK UNIFIED IDEOGRAPH - 0xD3F8: 0x5CEA, //CJK UNIFIED IDEOGRAPH - 0xD3F9: 0x5FA1, //CJK UNIFIED IDEOGRAPH - 0xD3FA: 0x6108, //CJK UNIFIED IDEOGRAPH - 0xD3FB: 0x6B32, //CJK UNIFIED IDEOGRAPH - 0xD3FC: 0x72F1, //CJK UNIFIED IDEOGRAPH - 0xD3FD: 0x80B2, //CJK UNIFIED IDEOGRAPH - 0xD3FE: 0x8A89, //CJK UNIFIED IDEOGRAPH - 0xD440: 0x8A1E, //CJK UNIFIED IDEOGRAPH - 0xD441: 0x8A1F, //CJK UNIFIED IDEOGRAPH - 0xD442: 0x8A20, //CJK UNIFIED IDEOGRAPH - 0xD443: 0x8A21, //CJK UNIFIED IDEOGRAPH - 0xD444: 0x8A22, //CJK UNIFIED IDEOGRAPH - 0xD445: 0x8A23, //CJK UNIFIED IDEOGRAPH - 0xD446: 0x8A24, //CJK UNIFIED IDEOGRAPH - 0xD447: 0x8A25, //CJK UNIFIED IDEOGRAPH - 0xD448: 0x8A26, //CJK UNIFIED IDEOGRAPH - 0xD449: 0x8A27, //CJK UNIFIED IDEOGRAPH - 0xD44A: 0x8A28, //CJK UNIFIED IDEOGRAPH - 0xD44B: 0x8A29, //CJK UNIFIED IDEOGRAPH - 0xD44C: 0x8A2A, //CJK UNIFIED IDEOGRAPH - 0xD44D: 0x8A2B, //CJK UNIFIED IDEOGRAPH - 0xD44E: 0x8A2C, //CJK UNIFIED IDEOGRAPH - 0xD44F: 0x8A2D, //CJK UNIFIED IDEOGRAPH - 0xD450: 0x8A2E, //CJK UNIFIED IDEOGRAPH - 0xD451: 0x8A2F, //CJK UNIFIED IDEOGRAPH - 0xD452: 0x8A30, //CJK UNIFIED IDEOGRAPH - 0xD453: 0x8A31, //CJK UNIFIED IDEOGRAPH - 0xD454: 0x8A32, //CJK UNIFIED IDEOGRAPH - 0xD455: 0x8A33, //CJK UNIFIED IDEOGRAPH - 0xD456: 0x8A34, //CJK UNIFIED IDEOGRAPH - 0xD457: 0x8A35, //CJK UNIFIED IDEOGRAPH - 0xD458: 0x8A36, //CJK UNIFIED IDEOGRAPH - 0xD459: 0x8A37, //CJK UNIFIED IDEOGRAPH - 0xD45A: 0x8A38, //CJK UNIFIED IDEOGRAPH - 0xD45B: 0x8A39, //CJK UNIFIED IDEOGRAPH - 0xD45C: 0x8A3A, //CJK UNIFIED IDEOGRAPH - 0xD45D: 0x8A3B, //CJK UNIFIED IDEOGRAPH - 0xD45E: 0x8A3C, //CJK UNIFIED IDEOGRAPH - 0xD45F: 0x8A3D, //CJK UNIFIED IDEOGRAPH - 0xD460: 0x8A3F, //CJK UNIFIED IDEOGRAPH - 0xD461: 0x8A40, //CJK UNIFIED IDEOGRAPH - 0xD462: 0x8A41, //CJK UNIFIED IDEOGRAPH - 0xD463: 0x8A42, //CJK UNIFIED IDEOGRAPH - 0xD464: 0x8A43, //CJK UNIFIED IDEOGRAPH - 0xD465: 0x8A44, //CJK UNIFIED IDEOGRAPH - 0xD466: 0x8A45, //CJK UNIFIED IDEOGRAPH - 0xD467: 0x8A46, //CJK UNIFIED IDEOGRAPH - 0xD468: 0x8A47, //CJK UNIFIED IDEOGRAPH - 0xD469: 0x8A49, //CJK UNIFIED IDEOGRAPH - 0xD46A: 0x8A4A, //CJK UNIFIED IDEOGRAPH - 0xD46B: 0x8A4B, //CJK UNIFIED IDEOGRAPH - 0xD46C: 0x8A4C, //CJK UNIFIED IDEOGRAPH - 0xD46D: 0x8A4D, //CJK UNIFIED IDEOGRAPH - 0xD46E: 0x8A4E, //CJK UNIFIED IDEOGRAPH - 0xD46F: 0x8A4F, //CJK UNIFIED IDEOGRAPH - 0xD470: 0x8A50, //CJK UNIFIED IDEOGRAPH - 0xD471: 0x8A51, //CJK UNIFIED IDEOGRAPH - 0xD472: 0x8A52, //CJK UNIFIED IDEOGRAPH - 0xD473: 0x8A53, //CJK UNIFIED IDEOGRAPH - 0xD474: 0x8A54, //CJK UNIFIED IDEOGRAPH - 0xD475: 0x8A55, //CJK UNIFIED IDEOGRAPH - 0xD476: 0x8A56, //CJK UNIFIED IDEOGRAPH - 0xD477: 0x8A57, //CJK UNIFIED IDEOGRAPH - 0xD478: 0x8A58, //CJK UNIFIED IDEOGRAPH - 0xD479: 0x8A59, //CJK UNIFIED IDEOGRAPH - 0xD47A: 0x8A5A, //CJK UNIFIED IDEOGRAPH - 0xD47B: 0x8A5B, //CJK UNIFIED IDEOGRAPH - 0xD47C: 0x8A5C, //CJK UNIFIED IDEOGRAPH - 0xD47D: 0x8A5D, //CJK UNIFIED IDEOGRAPH - 0xD47E: 0x8A5E, //CJK UNIFIED IDEOGRAPH - 0xD480: 0x8A5F, //CJK UNIFIED IDEOGRAPH - 0xD481: 0x8A60, //CJK UNIFIED IDEOGRAPH - 0xD482: 0x8A61, //CJK UNIFIED IDEOGRAPH - 0xD483: 0x8A62, //CJK UNIFIED IDEOGRAPH - 0xD484: 0x8A63, //CJK UNIFIED IDEOGRAPH - 0xD485: 0x8A64, //CJK UNIFIED IDEOGRAPH - 0xD486: 0x8A65, //CJK UNIFIED IDEOGRAPH - 0xD487: 0x8A66, //CJK UNIFIED IDEOGRAPH - 0xD488: 0x8A67, //CJK UNIFIED IDEOGRAPH - 0xD489: 0x8A68, //CJK UNIFIED IDEOGRAPH - 0xD48A: 0x8A69, //CJK UNIFIED IDEOGRAPH - 0xD48B: 0x8A6A, //CJK UNIFIED IDEOGRAPH - 0xD48C: 0x8A6B, //CJK UNIFIED IDEOGRAPH - 0xD48D: 0x8A6C, //CJK UNIFIED IDEOGRAPH - 0xD48E: 0x8A6D, //CJK UNIFIED IDEOGRAPH - 0xD48F: 0x8A6E, //CJK UNIFIED IDEOGRAPH - 0xD490: 0x8A6F, //CJK UNIFIED IDEOGRAPH - 0xD491: 0x8A70, //CJK UNIFIED IDEOGRAPH - 0xD492: 0x8A71, //CJK UNIFIED IDEOGRAPH - 0xD493: 0x8A72, //CJK UNIFIED IDEOGRAPH - 0xD494: 0x8A73, //CJK UNIFIED IDEOGRAPH - 0xD495: 0x8A74, //CJK UNIFIED IDEOGRAPH - 0xD496: 0x8A75, //CJK UNIFIED IDEOGRAPH - 0xD497: 0x8A76, //CJK UNIFIED IDEOGRAPH - 0xD498: 0x8A77, //CJK UNIFIED IDEOGRAPH - 0xD499: 0x8A78, //CJK UNIFIED IDEOGRAPH - 0xD49A: 0x8A7A, //CJK UNIFIED IDEOGRAPH - 0xD49B: 0x8A7B, //CJK UNIFIED IDEOGRAPH - 0xD49C: 0x8A7C, //CJK UNIFIED IDEOGRAPH - 0xD49D: 0x8A7D, //CJK UNIFIED IDEOGRAPH - 0xD49E: 0x8A7E, //CJK UNIFIED IDEOGRAPH - 0xD49F: 0x8A7F, //CJK UNIFIED IDEOGRAPH - 0xD4A0: 0x8A80, //CJK UNIFIED IDEOGRAPH - 0xD4A1: 0x6D74, //CJK UNIFIED IDEOGRAPH - 0xD4A2: 0x5BD3, //CJK UNIFIED IDEOGRAPH - 0xD4A3: 0x88D5, //CJK UNIFIED IDEOGRAPH - 0xD4A4: 0x9884, //CJK UNIFIED IDEOGRAPH - 0xD4A5: 0x8C6B, //CJK UNIFIED IDEOGRAPH - 0xD4A6: 0x9A6D, //CJK UNIFIED IDEOGRAPH - 0xD4A7: 0x9E33, //CJK UNIFIED IDEOGRAPH - 0xD4A8: 0x6E0A, //CJK UNIFIED IDEOGRAPH - 0xD4A9: 0x51A4, //CJK UNIFIED IDEOGRAPH - 0xD4AA: 0x5143, //CJK UNIFIED IDEOGRAPH - 0xD4AB: 0x57A3, //CJK UNIFIED IDEOGRAPH - 0xD4AC: 0x8881, //CJK UNIFIED IDEOGRAPH - 0xD4AD: 0x539F, //CJK UNIFIED IDEOGRAPH - 0xD4AE: 0x63F4, //CJK UNIFIED IDEOGRAPH - 0xD4AF: 0x8F95, //CJK UNIFIED IDEOGRAPH - 0xD4B0: 0x56ED, //CJK UNIFIED IDEOGRAPH - 0xD4B1: 0x5458, //CJK UNIFIED IDEOGRAPH - 0xD4B2: 0x5706, //CJK UNIFIED IDEOGRAPH - 0xD4B3: 0x733F, //CJK UNIFIED IDEOGRAPH - 0xD4B4: 0x6E90, //CJK UNIFIED IDEOGRAPH - 0xD4B5: 0x7F18, //CJK UNIFIED IDEOGRAPH - 0xD4B6: 0x8FDC, //CJK UNIFIED IDEOGRAPH - 0xD4B7: 0x82D1, //CJK UNIFIED IDEOGRAPH - 0xD4B8: 0x613F, //CJK UNIFIED IDEOGRAPH - 0xD4B9: 0x6028, //CJK UNIFIED IDEOGRAPH - 0xD4BA: 0x9662, //CJK UNIFIED IDEOGRAPH - 0xD4BB: 0x66F0, //CJK UNIFIED IDEOGRAPH - 0xD4BC: 0x7EA6, //CJK UNIFIED IDEOGRAPH - 0xD4BD: 0x8D8A, //CJK UNIFIED IDEOGRAPH - 0xD4BE: 0x8DC3, //CJK UNIFIED IDEOGRAPH - 0xD4BF: 0x94A5, //CJK UNIFIED IDEOGRAPH - 0xD4C0: 0x5CB3, //CJK UNIFIED IDEOGRAPH - 0xD4C1: 0x7CA4, //CJK UNIFIED IDEOGRAPH - 0xD4C2: 0x6708, //CJK UNIFIED IDEOGRAPH - 0xD4C3: 0x60A6, //CJK UNIFIED IDEOGRAPH - 0xD4C4: 0x9605, //CJK UNIFIED IDEOGRAPH - 0xD4C5: 0x8018, //CJK UNIFIED IDEOGRAPH - 0xD4C6: 0x4E91, //CJK UNIFIED IDEOGRAPH - 0xD4C7: 0x90E7, //CJK UNIFIED IDEOGRAPH - 0xD4C8: 0x5300, //CJK UNIFIED IDEOGRAPH - 0xD4C9: 0x9668, //CJK UNIFIED IDEOGRAPH - 0xD4CA: 0x5141, //CJK UNIFIED IDEOGRAPH - 0xD4CB: 0x8FD0, //CJK UNIFIED IDEOGRAPH - 0xD4CC: 0x8574, //CJK UNIFIED IDEOGRAPH - 0xD4CD: 0x915D, //CJK UNIFIED IDEOGRAPH - 0xD4CE: 0x6655, //CJK UNIFIED IDEOGRAPH - 0xD4CF: 0x97F5, //CJK UNIFIED IDEOGRAPH - 0xD4D0: 0x5B55, //CJK UNIFIED IDEOGRAPH - 0xD4D1: 0x531D, //CJK UNIFIED IDEOGRAPH - 0xD4D2: 0x7838, //CJK UNIFIED IDEOGRAPH - 0xD4D3: 0x6742, //CJK UNIFIED IDEOGRAPH - 0xD4D4: 0x683D, //CJK UNIFIED IDEOGRAPH - 0xD4D5: 0x54C9, //CJK UNIFIED IDEOGRAPH - 0xD4D6: 0x707E, //CJK UNIFIED IDEOGRAPH - 0xD4D7: 0x5BB0, //CJK UNIFIED IDEOGRAPH - 0xD4D8: 0x8F7D, //CJK UNIFIED IDEOGRAPH - 0xD4D9: 0x518D, //CJK UNIFIED IDEOGRAPH - 0xD4DA: 0x5728, //CJK UNIFIED IDEOGRAPH - 0xD4DB: 0x54B1, //CJK UNIFIED IDEOGRAPH - 0xD4DC: 0x6512, //CJK UNIFIED IDEOGRAPH - 0xD4DD: 0x6682, //CJK UNIFIED IDEOGRAPH - 0xD4DE: 0x8D5E, //CJK UNIFIED IDEOGRAPH - 0xD4DF: 0x8D43, //CJK UNIFIED IDEOGRAPH - 0xD4E0: 0x810F, //CJK UNIFIED IDEOGRAPH - 0xD4E1: 0x846C, //CJK UNIFIED IDEOGRAPH - 0xD4E2: 0x906D, //CJK UNIFIED IDEOGRAPH - 0xD4E3: 0x7CDF, //CJK UNIFIED IDEOGRAPH - 0xD4E4: 0x51FF, //CJK UNIFIED IDEOGRAPH - 0xD4E5: 0x85FB, //CJK UNIFIED IDEOGRAPH - 0xD4E6: 0x67A3, //CJK UNIFIED IDEOGRAPH - 0xD4E7: 0x65E9, //CJK UNIFIED IDEOGRAPH - 0xD4E8: 0x6FA1, //CJK UNIFIED IDEOGRAPH - 0xD4E9: 0x86A4, //CJK UNIFIED IDEOGRAPH - 0xD4EA: 0x8E81, //CJK UNIFIED IDEOGRAPH - 0xD4EB: 0x566A, //CJK UNIFIED IDEOGRAPH - 0xD4EC: 0x9020, //CJK UNIFIED IDEOGRAPH - 0xD4ED: 0x7682, //CJK UNIFIED IDEOGRAPH - 0xD4EE: 0x7076, //CJK UNIFIED IDEOGRAPH - 0xD4EF: 0x71E5, //CJK UNIFIED IDEOGRAPH - 0xD4F0: 0x8D23, //CJK UNIFIED IDEOGRAPH - 0xD4F1: 0x62E9, //CJK UNIFIED IDEOGRAPH - 0xD4F2: 0x5219, //CJK UNIFIED IDEOGRAPH - 0xD4F3: 0x6CFD, //CJK UNIFIED IDEOGRAPH - 0xD4F4: 0x8D3C, //CJK UNIFIED IDEOGRAPH - 0xD4F5: 0x600E, //CJK UNIFIED IDEOGRAPH - 0xD4F6: 0x589E, //CJK UNIFIED IDEOGRAPH - 0xD4F7: 0x618E, //CJK UNIFIED IDEOGRAPH - 0xD4F8: 0x66FE, //CJK UNIFIED IDEOGRAPH - 0xD4F9: 0x8D60, //CJK UNIFIED IDEOGRAPH - 0xD4FA: 0x624E, //CJK UNIFIED IDEOGRAPH - 0xD4FB: 0x55B3, //CJK UNIFIED IDEOGRAPH - 0xD4FC: 0x6E23, //CJK UNIFIED IDEOGRAPH - 0xD4FD: 0x672D, //CJK UNIFIED IDEOGRAPH - 0xD4FE: 0x8F67, //CJK UNIFIED IDEOGRAPH - 0xD540: 0x8A81, //CJK UNIFIED IDEOGRAPH - 0xD541: 0x8A82, //CJK UNIFIED IDEOGRAPH - 0xD542: 0x8A83, //CJK UNIFIED IDEOGRAPH - 0xD543: 0x8A84, //CJK UNIFIED IDEOGRAPH - 0xD544: 0x8A85, //CJK UNIFIED IDEOGRAPH - 0xD545: 0x8A86, //CJK UNIFIED IDEOGRAPH - 0xD546: 0x8A87, //CJK UNIFIED IDEOGRAPH - 0xD547: 0x8A88, //CJK UNIFIED IDEOGRAPH - 0xD548: 0x8A8B, //CJK UNIFIED IDEOGRAPH - 0xD549: 0x8A8C, //CJK UNIFIED IDEOGRAPH - 0xD54A: 0x8A8D, //CJK UNIFIED IDEOGRAPH - 0xD54B: 0x8A8E, //CJK UNIFIED IDEOGRAPH - 0xD54C: 0x8A8F, //CJK UNIFIED IDEOGRAPH - 0xD54D: 0x8A90, //CJK UNIFIED IDEOGRAPH - 0xD54E: 0x8A91, //CJK UNIFIED IDEOGRAPH - 0xD54F: 0x8A92, //CJK UNIFIED IDEOGRAPH - 0xD550: 0x8A94, //CJK UNIFIED IDEOGRAPH - 0xD551: 0x8A95, //CJK UNIFIED IDEOGRAPH - 0xD552: 0x8A96, //CJK UNIFIED IDEOGRAPH - 0xD553: 0x8A97, //CJK UNIFIED IDEOGRAPH - 0xD554: 0x8A98, //CJK UNIFIED IDEOGRAPH - 0xD555: 0x8A99, //CJK UNIFIED IDEOGRAPH - 0xD556: 0x8A9A, //CJK UNIFIED IDEOGRAPH - 0xD557: 0x8A9B, //CJK UNIFIED IDEOGRAPH - 0xD558: 0x8A9C, //CJK UNIFIED IDEOGRAPH - 0xD559: 0x8A9D, //CJK UNIFIED IDEOGRAPH - 0xD55A: 0x8A9E, //CJK UNIFIED IDEOGRAPH - 0xD55B: 0x8A9F, //CJK UNIFIED IDEOGRAPH - 0xD55C: 0x8AA0, //CJK UNIFIED IDEOGRAPH - 0xD55D: 0x8AA1, //CJK UNIFIED IDEOGRAPH - 0xD55E: 0x8AA2, //CJK UNIFIED IDEOGRAPH - 0xD55F: 0x8AA3, //CJK UNIFIED IDEOGRAPH - 0xD560: 0x8AA4, //CJK UNIFIED IDEOGRAPH - 0xD561: 0x8AA5, //CJK UNIFIED IDEOGRAPH - 0xD562: 0x8AA6, //CJK UNIFIED IDEOGRAPH - 0xD563: 0x8AA7, //CJK UNIFIED IDEOGRAPH - 0xD564: 0x8AA8, //CJK UNIFIED IDEOGRAPH - 0xD565: 0x8AA9, //CJK UNIFIED IDEOGRAPH - 0xD566: 0x8AAA, //CJK UNIFIED IDEOGRAPH - 0xD567: 0x8AAB, //CJK UNIFIED IDEOGRAPH - 0xD568: 0x8AAC, //CJK UNIFIED IDEOGRAPH - 0xD569: 0x8AAD, //CJK UNIFIED IDEOGRAPH - 0xD56A: 0x8AAE, //CJK UNIFIED IDEOGRAPH - 0xD56B: 0x8AAF, //CJK UNIFIED IDEOGRAPH - 0xD56C: 0x8AB0, //CJK UNIFIED IDEOGRAPH - 0xD56D: 0x8AB1, //CJK UNIFIED IDEOGRAPH - 0xD56E: 0x8AB2, //CJK UNIFIED IDEOGRAPH - 0xD56F: 0x8AB3, //CJK UNIFIED IDEOGRAPH - 0xD570: 0x8AB4, //CJK UNIFIED IDEOGRAPH - 0xD571: 0x8AB5, //CJK UNIFIED IDEOGRAPH - 0xD572: 0x8AB6, //CJK UNIFIED IDEOGRAPH - 0xD573: 0x8AB7, //CJK UNIFIED IDEOGRAPH - 0xD574: 0x8AB8, //CJK UNIFIED IDEOGRAPH - 0xD575: 0x8AB9, //CJK UNIFIED IDEOGRAPH - 0xD576: 0x8ABA, //CJK UNIFIED IDEOGRAPH - 0xD577: 0x8ABB, //CJK UNIFIED IDEOGRAPH - 0xD578: 0x8ABC, //CJK UNIFIED IDEOGRAPH - 0xD579: 0x8ABD, //CJK UNIFIED IDEOGRAPH - 0xD57A: 0x8ABE, //CJK UNIFIED IDEOGRAPH - 0xD57B: 0x8ABF, //CJK UNIFIED IDEOGRAPH - 0xD57C: 0x8AC0, //CJK UNIFIED IDEOGRAPH - 0xD57D: 0x8AC1, //CJK UNIFIED IDEOGRAPH - 0xD57E: 0x8AC2, //CJK UNIFIED IDEOGRAPH - 0xD580: 0x8AC3, //CJK UNIFIED IDEOGRAPH - 0xD581: 0x8AC4, //CJK UNIFIED IDEOGRAPH - 0xD582: 0x8AC5, //CJK UNIFIED IDEOGRAPH - 0xD583: 0x8AC6, //CJK UNIFIED IDEOGRAPH - 0xD584: 0x8AC7, //CJK UNIFIED IDEOGRAPH - 0xD585: 0x8AC8, //CJK UNIFIED IDEOGRAPH - 0xD586: 0x8AC9, //CJK UNIFIED IDEOGRAPH - 0xD587: 0x8ACA, //CJK UNIFIED IDEOGRAPH - 0xD588: 0x8ACB, //CJK UNIFIED IDEOGRAPH - 0xD589: 0x8ACC, //CJK UNIFIED IDEOGRAPH - 0xD58A: 0x8ACD, //CJK UNIFIED IDEOGRAPH - 0xD58B: 0x8ACE, //CJK UNIFIED IDEOGRAPH - 0xD58C: 0x8ACF, //CJK UNIFIED IDEOGRAPH - 0xD58D: 0x8AD0, //CJK UNIFIED IDEOGRAPH - 0xD58E: 0x8AD1, //CJK UNIFIED IDEOGRAPH - 0xD58F: 0x8AD2, //CJK UNIFIED IDEOGRAPH - 0xD590: 0x8AD3, //CJK UNIFIED IDEOGRAPH - 0xD591: 0x8AD4, //CJK UNIFIED IDEOGRAPH - 0xD592: 0x8AD5, //CJK UNIFIED IDEOGRAPH - 0xD593: 0x8AD6, //CJK UNIFIED IDEOGRAPH - 0xD594: 0x8AD7, //CJK UNIFIED IDEOGRAPH - 0xD595: 0x8AD8, //CJK UNIFIED IDEOGRAPH - 0xD596: 0x8AD9, //CJK UNIFIED IDEOGRAPH - 0xD597: 0x8ADA, //CJK UNIFIED IDEOGRAPH - 0xD598: 0x8ADB, //CJK UNIFIED IDEOGRAPH - 0xD599: 0x8ADC, //CJK UNIFIED IDEOGRAPH - 0xD59A: 0x8ADD, //CJK UNIFIED IDEOGRAPH - 0xD59B: 0x8ADE, //CJK UNIFIED IDEOGRAPH - 0xD59C: 0x8ADF, //CJK UNIFIED IDEOGRAPH - 0xD59D: 0x8AE0, //CJK UNIFIED IDEOGRAPH - 0xD59E: 0x8AE1, //CJK UNIFIED IDEOGRAPH - 0xD59F: 0x8AE2, //CJK UNIFIED IDEOGRAPH - 0xD5A0: 0x8AE3, //CJK UNIFIED IDEOGRAPH - 0xD5A1: 0x94E1, //CJK UNIFIED IDEOGRAPH - 0xD5A2: 0x95F8, //CJK UNIFIED IDEOGRAPH - 0xD5A3: 0x7728, //CJK UNIFIED IDEOGRAPH - 0xD5A4: 0x6805, //CJK UNIFIED IDEOGRAPH - 0xD5A5: 0x69A8, //CJK UNIFIED IDEOGRAPH - 0xD5A6: 0x548B, //CJK UNIFIED IDEOGRAPH - 0xD5A7: 0x4E4D, //CJK UNIFIED IDEOGRAPH - 0xD5A8: 0x70B8, //CJK UNIFIED IDEOGRAPH - 0xD5A9: 0x8BC8, //CJK UNIFIED IDEOGRAPH - 0xD5AA: 0x6458, //CJK UNIFIED IDEOGRAPH - 0xD5AB: 0x658B, //CJK UNIFIED IDEOGRAPH - 0xD5AC: 0x5B85, //CJK UNIFIED IDEOGRAPH - 0xD5AD: 0x7A84, //CJK UNIFIED IDEOGRAPH - 0xD5AE: 0x503A, //CJK UNIFIED IDEOGRAPH - 0xD5AF: 0x5BE8, //CJK UNIFIED IDEOGRAPH - 0xD5B0: 0x77BB, //CJK UNIFIED IDEOGRAPH - 0xD5B1: 0x6BE1, //CJK UNIFIED IDEOGRAPH - 0xD5B2: 0x8A79, //CJK UNIFIED IDEOGRAPH - 0xD5B3: 0x7C98, //CJK UNIFIED IDEOGRAPH - 0xD5B4: 0x6CBE, //CJK UNIFIED IDEOGRAPH - 0xD5B5: 0x76CF, //CJK UNIFIED IDEOGRAPH - 0xD5B6: 0x65A9, //CJK UNIFIED IDEOGRAPH - 0xD5B7: 0x8F97, //CJK UNIFIED IDEOGRAPH - 0xD5B8: 0x5D2D, //CJK UNIFIED IDEOGRAPH - 0xD5B9: 0x5C55, //CJK UNIFIED IDEOGRAPH - 0xD5BA: 0x8638, //CJK UNIFIED IDEOGRAPH - 0xD5BB: 0x6808, //CJK UNIFIED IDEOGRAPH - 0xD5BC: 0x5360, //CJK UNIFIED IDEOGRAPH - 0xD5BD: 0x6218, //CJK UNIFIED IDEOGRAPH - 0xD5BE: 0x7AD9, //CJK UNIFIED IDEOGRAPH - 0xD5BF: 0x6E5B, //CJK UNIFIED IDEOGRAPH - 0xD5C0: 0x7EFD, //CJK UNIFIED IDEOGRAPH - 0xD5C1: 0x6A1F, //CJK UNIFIED IDEOGRAPH - 0xD5C2: 0x7AE0, //CJK UNIFIED IDEOGRAPH - 0xD5C3: 0x5F70, //CJK UNIFIED IDEOGRAPH - 0xD5C4: 0x6F33, //CJK UNIFIED IDEOGRAPH - 0xD5C5: 0x5F20, //CJK UNIFIED IDEOGRAPH - 0xD5C6: 0x638C, //CJK UNIFIED IDEOGRAPH - 0xD5C7: 0x6DA8, //CJK UNIFIED IDEOGRAPH - 0xD5C8: 0x6756, //CJK UNIFIED IDEOGRAPH - 0xD5C9: 0x4E08, //CJK UNIFIED IDEOGRAPH - 0xD5CA: 0x5E10, //CJK UNIFIED IDEOGRAPH - 0xD5CB: 0x8D26, //CJK UNIFIED IDEOGRAPH - 0xD5CC: 0x4ED7, //CJK UNIFIED IDEOGRAPH - 0xD5CD: 0x80C0, //CJK UNIFIED IDEOGRAPH - 0xD5CE: 0x7634, //CJK UNIFIED IDEOGRAPH - 0xD5CF: 0x969C, //CJK UNIFIED IDEOGRAPH - 0xD5D0: 0x62DB, //CJK UNIFIED IDEOGRAPH - 0xD5D1: 0x662D, //CJK UNIFIED IDEOGRAPH - 0xD5D2: 0x627E, //CJK UNIFIED IDEOGRAPH - 0xD5D3: 0x6CBC, //CJK UNIFIED IDEOGRAPH - 0xD5D4: 0x8D75, //CJK UNIFIED IDEOGRAPH - 0xD5D5: 0x7167, //CJK UNIFIED IDEOGRAPH - 0xD5D6: 0x7F69, //CJK UNIFIED IDEOGRAPH - 0xD5D7: 0x5146, //CJK UNIFIED IDEOGRAPH - 0xD5D8: 0x8087, //CJK UNIFIED IDEOGRAPH - 0xD5D9: 0x53EC, //CJK UNIFIED IDEOGRAPH - 0xD5DA: 0x906E, //CJK UNIFIED IDEOGRAPH - 0xD5DB: 0x6298, //CJK UNIFIED IDEOGRAPH - 0xD5DC: 0x54F2, //CJK UNIFIED IDEOGRAPH - 0xD5DD: 0x86F0, //CJK UNIFIED IDEOGRAPH - 0xD5DE: 0x8F99, //CJK UNIFIED IDEOGRAPH - 0xD5DF: 0x8005, //CJK UNIFIED IDEOGRAPH - 0xD5E0: 0x9517, //CJK UNIFIED IDEOGRAPH - 0xD5E1: 0x8517, //CJK UNIFIED IDEOGRAPH - 0xD5E2: 0x8FD9, //CJK UNIFIED IDEOGRAPH - 0xD5E3: 0x6D59, //CJK UNIFIED IDEOGRAPH - 0xD5E4: 0x73CD, //CJK UNIFIED IDEOGRAPH - 0xD5E5: 0x659F, //CJK UNIFIED IDEOGRAPH - 0xD5E6: 0x771F, //CJK UNIFIED IDEOGRAPH - 0xD5E7: 0x7504, //CJK UNIFIED IDEOGRAPH - 0xD5E8: 0x7827, //CJK UNIFIED IDEOGRAPH - 0xD5E9: 0x81FB, //CJK UNIFIED IDEOGRAPH - 0xD5EA: 0x8D1E, //CJK UNIFIED IDEOGRAPH - 0xD5EB: 0x9488, //CJK UNIFIED IDEOGRAPH - 0xD5EC: 0x4FA6, //CJK UNIFIED IDEOGRAPH - 0xD5ED: 0x6795, //CJK UNIFIED IDEOGRAPH - 0xD5EE: 0x75B9, //CJK UNIFIED IDEOGRAPH - 0xD5EF: 0x8BCA, //CJK UNIFIED IDEOGRAPH - 0xD5F0: 0x9707, //CJK UNIFIED IDEOGRAPH - 0xD5F1: 0x632F, //CJK UNIFIED IDEOGRAPH - 0xD5F2: 0x9547, //CJK UNIFIED IDEOGRAPH - 0xD5F3: 0x9635, //CJK UNIFIED IDEOGRAPH - 0xD5F4: 0x84B8, //CJK UNIFIED IDEOGRAPH - 0xD5F5: 0x6323, //CJK UNIFIED IDEOGRAPH - 0xD5F6: 0x7741, //CJK UNIFIED IDEOGRAPH - 0xD5F7: 0x5F81, //CJK UNIFIED IDEOGRAPH - 0xD5F8: 0x72F0, //CJK UNIFIED IDEOGRAPH - 0xD5F9: 0x4E89, //CJK UNIFIED IDEOGRAPH - 0xD5FA: 0x6014, //CJK UNIFIED IDEOGRAPH - 0xD5FB: 0x6574, //CJK UNIFIED IDEOGRAPH - 0xD5FC: 0x62EF, //CJK UNIFIED IDEOGRAPH - 0xD5FD: 0x6B63, //CJK UNIFIED IDEOGRAPH - 0xD5FE: 0x653F, //CJK UNIFIED IDEOGRAPH - 0xD640: 0x8AE4, //CJK UNIFIED IDEOGRAPH - 0xD641: 0x8AE5, //CJK UNIFIED IDEOGRAPH - 0xD642: 0x8AE6, //CJK UNIFIED IDEOGRAPH - 0xD643: 0x8AE7, //CJK UNIFIED IDEOGRAPH - 0xD644: 0x8AE8, //CJK UNIFIED IDEOGRAPH - 0xD645: 0x8AE9, //CJK UNIFIED IDEOGRAPH - 0xD646: 0x8AEA, //CJK UNIFIED IDEOGRAPH - 0xD647: 0x8AEB, //CJK UNIFIED IDEOGRAPH - 0xD648: 0x8AEC, //CJK UNIFIED IDEOGRAPH - 0xD649: 0x8AED, //CJK UNIFIED IDEOGRAPH - 0xD64A: 0x8AEE, //CJK UNIFIED IDEOGRAPH - 0xD64B: 0x8AEF, //CJK UNIFIED IDEOGRAPH - 0xD64C: 0x8AF0, //CJK UNIFIED IDEOGRAPH - 0xD64D: 0x8AF1, //CJK UNIFIED IDEOGRAPH - 0xD64E: 0x8AF2, //CJK UNIFIED IDEOGRAPH - 0xD64F: 0x8AF3, //CJK UNIFIED IDEOGRAPH - 0xD650: 0x8AF4, //CJK UNIFIED IDEOGRAPH - 0xD651: 0x8AF5, //CJK UNIFIED IDEOGRAPH - 0xD652: 0x8AF6, //CJK UNIFIED IDEOGRAPH - 0xD653: 0x8AF7, //CJK UNIFIED IDEOGRAPH - 0xD654: 0x8AF8, //CJK UNIFIED IDEOGRAPH - 0xD655: 0x8AF9, //CJK UNIFIED IDEOGRAPH - 0xD656: 0x8AFA, //CJK UNIFIED IDEOGRAPH - 0xD657: 0x8AFB, //CJK UNIFIED IDEOGRAPH - 0xD658: 0x8AFC, //CJK UNIFIED IDEOGRAPH - 0xD659: 0x8AFD, //CJK UNIFIED IDEOGRAPH - 0xD65A: 0x8AFE, //CJK UNIFIED IDEOGRAPH - 0xD65B: 0x8AFF, //CJK UNIFIED IDEOGRAPH - 0xD65C: 0x8B00, //CJK UNIFIED IDEOGRAPH - 0xD65D: 0x8B01, //CJK UNIFIED IDEOGRAPH - 0xD65E: 0x8B02, //CJK UNIFIED IDEOGRAPH - 0xD65F: 0x8B03, //CJK UNIFIED IDEOGRAPH - 0xD660: 0x8B04, //CJK UNIFIED IDEOGRAPH - 0xD661: 0x8B05, //CJK UNIFIED IDEOGRAPH - 0xD662: 0x8B06, //CJK UNIFIED IDEOGRAPH - 0xD663: 0x8B08, //CJK UNIFIED IDEOGRAPH - 0xD664: 0x8B09, //CJK UNIFIED IDEOGRAPH - 0xD665: 0x8B0A, //CJK UNIFIED IDEOGRAPH - 0xD666: 0x8B0B, //CJK UNIFIED IDEOGRAPH - 0xD667: 0x8B0C, //CJK UNIFIED IDEOGRAPH - 0xD668: 0x8B0D, //CJK UNIFIED IDEOGRAPH - 0xD669: 0x8B0E, //CJK UNIFIED IDEOGRAPH - 0xD66A: 0x8B0F, //CJK UNIFIED IDEOGRAPH - 0xD66B: 0x8B10, //CJK UNIFIED IDEOGRAPH - 0xD66C: 0x8B11, //CJK UNIFIED IDEOGRAPH - 0xD66D: 0x8B12, //CJK UNIFIED IDEOGRAPH - 0xD66E: 0x8B13, //CJK UNIFIED IDEOGRAPH - 0xD66F: 0x8B14, //CJK UNIFIED IDEOGRAPH - 0xD670: 0x8B15, //CJK UNIFIED IDEOGRAPH - 0xD671: 0x8B16, //CJK UNIFIED IDEOGRAPH - 0xD672: 0x8B17, //CJK UNIFIED IDEOGRAPH - 0xD673: 0x8B18, //CJK UNIFIED IDEOGRAPH - 0xD674: 0x8B19, //CJK UNIFIED IDEOGRAPH - 0xD675: 0x8B1A, //CJK UNIFIED IDEOGRAPH - 0xD676: 0x8B1B, //CJK UNIFIED IDEOGRAPH - 0xD677: 0x8B1C, //CJK UNIFIED IDEOGRAPH - 0xD678: 0x8B1D, //CJK UNIFIED IDEOGRAPH - 0xD679: 0x8B1E, //CJK UNIFIED IDEOGRAPH - 0xD67A: 0x8B1F, //CJK UNIFIED IDEOGRAPH - 0xD67B: 0x8B20, //CJK UNIFIED IDEOGRAPH - 0xD67C: 0x8B21, //CJK UNIFIED IDEOGRAPH - 0xD67D: 0x8B22, //CJK UNIFIED IDEOGRAPH - 0xD67E: 0x8B23, //CJK UNIFIED IDEOGRAPH - 0xD680: 0x8B24, //CJK UNIFIED IDEOGRAPH - 0xD681: 0x8B25, //CJK UNIFIED IDEOGRAPH - 0xD682: 0x8B27, //CJK UNIFIED IDEOGRAPH - 0xD683: 0x8B28, //CJK UNIFIED IDEOGRAPH - 0xD684: 0x8B29, //CJK UNIFIED IDEOGRAPH - 0xD685: 0x8B2A, //CJK UNIFIED IDEOGRAPH - 0xD686: 0x8B2B, //CJK UNIFIED IDEOGRAPH - 0xD687: 0x8B2C, //CJK UNIFIED IDEOGRAPH - 0xD688: 0x8B2D, //CJK UNIFIED IDEOGRAPH - 0xD689: 0x8B2E, //CJK UNIFIED IDEOGRAPH - 0xD68A: 0x8B2F, //CJK UNIFIED IDEOGRAPH - 0xD68B: 0x8B30, //CJK UNIFIED IDEOGRAPH - 0xD68C: 0x8B31, //CJK UNIFIED IDEOGRAPH - 0xD68D: 0x8B32, //CJK UNIFIED IDEOGRAPH - 0xD68E: 0x8B33, //CJK UNIFIED IDEOGRAPH - 0xD68F: 0x8B34, //CJK UNIFIED IDEOGRAPH - 0xD690: 0x8B35, //CJK UNIFIED IDEOGRAPH - 0xD691: 0x8B36, //CJK UNIFIED IDEOGRAPH - 0xD692: 0x8B37, //CJK UNIFIED IDEOGRAPH - 0xD693: 0x8B38, //CJK UNIFIED IDEOGRAPH - 0xD694: 0x8B39, //CJK UNIFIED IDEOGRAPH - 0xD695: 0x8B3A, //CJK UNIFIED IDEOGRAPH - 0xD696: 0x8B3B, //CJK UNIFIED IDEOGRAPH - 0xD697: 0x8B3C, //CJK UNIFIED IDEOGRAPH - 0xD698: 0x8B3D, //CJK UNIFIED IDEOGRAPH - 0xD699: 0x8B3E, //CJK UNIFIED IDEOGRAPH - 0xD69A: 0x8B3F, //CJK UNIFIED IDEOGRAPH - 0xD69B: 0x8B40, //CJK UNIFIED IDEOGRAPH - 0xD69C: 0x8B41, //CJK UNIFIED IDEOGRAPH - 0xD69D: 0x8B42, //CJK UNIFIED IDEOGRAPH - 0xD69E: 0x8B43, //CJK UNIFIED IDEOGRAPH - 0xD69F: 0x8B44, //CJK UNIFIED IDEOGRAPH - 0xD6A0: 0x8B45, //CJK UNIFIED IDEOGRAPH - 0xD6A1: 0x5E27, //CJK UNIFIED IDEOGRAPH - 0xD6A2: 0x75C7, //CJK UNIFIED IDEOGRAPH - 0xD6A3: 0x90D1, //CJK UNIFIED IDEOGRAPH - 0xD6A4: 0x8BC1, //CJK UNIFIED IDEOGRAPH - 0xD6A5: 0x829D, //CJK UNIFIED IDEOGRAPH - 0xD6A6: 0x679D, //CJK UNIFIED IDEOGRAPH - 0xD6A7: 0x652F, //CJK UNIFIED IDEOGRAPH - 0xD6A8: 0x5431, //CJK UNIFIED IDEOGRAPH - 0xD6A9: 0x8718, //CJK UNIFIED IDEOGRAPH - 0xD6AA: 0x77E5, //CJK UNIFIED IDEOGRAPH - 0xD6AB: 0x80A2, //CJK UNIFIED IDEOGRAPH - 0xD6AC: 0x8102, //CJK UNIFIED IDEOGRAPH - 0xD6AD: 0x6C41, //CJK UNIFIED IDEOGRAPH - 0xD6AE: 0x4E4B, //CJK UNIFIED IDEOGRAPH - 0xD6AF: 0x7EC7, //CJK UNIFIED IDEOGRAPH - 0xD6B0: 0x804C, //CJK UNIFIED IDEOGRAPH - 0xD6B1: 0x76F4, //CJK UNIFIED IDEOGRAPH - 0xD6B2: 0x690D, //CJK UNIFIED IDEOGRAPH - 0xD6B3: 0x6B96, //CJK UNIFIED IDEOGRAPH - 0xD6B4: 0x6267, //CJK UNIFIED IDEOGRAPH - 0xD6B5: 0x503C, //CJK UNIFIED IDEOGRAPH - 0xD6B6: 0x4F84, //CJK UNIFIED IDEOGRAPH - 0xD6B7: 0x5740, //CJK UNIFIED IDEOGRAPH - 0xD6B8: 0x6307, //CJK UNIFIED IDEOGRAPH - 0xD6B9: 0x6B62, //CJK UNIFIED IDEOGRAPH - 0xD6BA: 0x8DBE, //CJK UNIFIED IDEOGRAPH - 0xD6BB: 0x53EA, //CJK UNIFIED IDEOGRAPH - 0xD6BC: 0x65E8, //CJK UNIFIED IDEOGRAPH - 0xD6BD: 0x7EB8, //CJK UNIFIED IDEOGRAPH - 0xD6BE: 0x5FD7, //CJK UNIFIED IDEOGRAPH - 0xD6BF: 0x631A, //CJK UNIFIED IDEOGRAPH - 0xD6C0: 0x63B7, //CJK UNIFIED IDEOGRAPH - 0xD6C1: 0x81F3, //CJK UNIFIED IDEOGRAPH - 0xD6C2: 0x81F4, //CJK UNIFIED IDEOGRAPH - 0xD6C3: 0x7F6E, //CJK UNIFIED IDEOGRAPH - 0xD6C4: 0x5E1C, //CJK UNIFIED IDEOGRAPH - 0xD6C5: 0x5CD9, //CJK UNIFIED IDEOGRAPH - 0xD6C6: 0x5236, //CJK UNIFIED IDEOGRAPH - 0xD6C7: 0x667A, //CJK UNIFIED IDEOGRAPH - 0xD6C8: 0x79E9, //CJK UNIFIED IDEOGRAPH - 0xD6C9: 0x7A1A, //CJK UNIFIED IDEOGRAPH - 0xD6CA: 0x8D28, //CJK UNIFIED IDEOGRAPH - 0xD6CB: 0x7099, //CJK UNIFIED IDEOGRAPH - 0xD6CC: 0x75D4, //CJK UNIFIED IDEOGRAPH - 0xD6CD: 0x6EDE, //CJK UNIFIED IDEOGRAPH - 0xD6CE: 0x6CBB, //CJK UNIFIED IDEOGRAPH - 0xD6CF: 0x7A92, //CJK UNIFIED IDEOGRAPH - 0xD6D0: 0x4E2D, //CJK UNIFIED IDEOGRAPH - 0xD6D1: 0x76C5, //CJK UNIFIED IDEOGRAPH - 0xD6D2: 0x5FE0, //CJK UNIFIED IDEOGRAPH - 0xD6D3: 0x949F, //CJK UNIFIED IDEOGRAPH - 0xD6D4: 0x8877, //CJK UNIFIED IDEOGRAPH - 0xD6D5: 0x7EC8, //CJK UNIFIED IDEOGRAPH - 0xD6D6: 0x79CD, //CJK UNIFIED IDEOGRAPH - 0xD6D7: 0x80BF, //CJK UNIFIED IDEOGRAPH - 0xD6D8: 0x91CD, //CJK UNIFIED IDEOGRAPH - 0xD6D9: 0x4EF2, //CJK UNIFIED IDEOGRAPH - 0xD6DA: 0x4F17, //CJK UNIFIED IDEOGRAPH - 0xD6DB: 0x821F, //CJK UNIFIED IDEOGRAPH - 0xD6DC: 0x5468, //CJK UNIFIED IDEOGRAPH - 0xD6DD: 0x5DDE, //CJK UNIFIED IDEOGRAPH - 0xD6DE: 0x6D32, //CJK UNIFIED IDEOGRAPH - 0xD6DF: 0x8BCC, //CJK UNIFIED IDEOGRAPH - 0xD6E0: 0x7CA5, //CJK UNIFIED IDEOGRAPH - 0xD6E1: 0x8F74, //CJK UNIFIED IDEOGRAPH - 0xD6E2: 0x8098, //CJK UNIFIED IDEOGRAPH - 0xD6E3: 0x5E1A, //CJK UNIFIED IDEOGRAPH - 0xD6E4: 0x5492, //CJK UNIFIED IDEOGRAPH - 0xD6E5: 0x76B1, //CJK UNIFIED IDEOGRAPH - 0xD6E6: 0x5B99, //CJK UNIFIED IDEOGRAPH - 0xD6E7: 0x663C, //CJK UNIFIED IDEOGRAPH - 0xD6E8: 0x9AA4, //CJK UNIFIED IDEOGRAPH - 0xD6E9: 0x73E0, //CJK UNIFIED IDEOGRAPH - 0xD6EA: 0x682A, //CJK UNIFIED IDEOGRAPH - 0xD6EB: 0x86DB, //CJK UNIFIED IDEOGRAPH - 0xD6EC: 0x6731, //CJK UNIFIED IDEOGRAPH - 0xD6ED: 0x732A, //CJK UNIFIED IDEOGRAPH - 0xD6EE: 0x8BF8, //CJK UNIFIED IDEOGRAPH - 0xD6EF: 0x8BDB, //CJK UNIFIED IDEOGRAPH - 0xD6F0: 0x9010, //CJK UNIFIED IDEOGRAPH - 0xD6F1: 0x7AF9, //CJK UNIFIED IDEOGRAPH - 0xD6F2: 0x70DB, //CJK UNIFIED IDEOGRAPH - 0xD6F3: 0x716E, //CJK UNIFIED IDEOGRAPH - 0xD6F4: 0x62C4, //CJK UNIFIED IDEOGRAPH - 0xD6F5: 0x77A9, //CJK UNIFIED IDEOGRAPH - 0xD6F6: 0x5631, //CJK UNIFIED IDEOGRAPH - 0xD6F7: 0x4E3B, //CJK UNIFIED IDEOGRAPH - 0xD6F8: 0x8457, //CJK UNIFIED IDEOGRAPH - 0xD6F9: 0x67F1, //CJK UNIFIED IDEOGRAPH - 0xD6FA: 0x52A9, //CJK UNIFIED IDEOGRAPH - 0xD6FB: 0x86C0, //CJK UNIFIED IDEOGRAPH - 0xD6FC: 0x8D2E, //CJK UNIFIED IDEOGRAPH - 0xD6FD: 0x94F8, //CJK UNIFIED IDEOGRAPH - 0xD6FE: 0x7B51, //CJK UNIFIED IDEOGRAPH - 0xD740: 0x8B46, //CJK UNIFIED IDEOGRAPH - 0xD741: 0x8B47, //CJK UNIFIED IDEOGRAPH - 0xD742: 0x8B48, //CJK UNIFIED IDEOGRAPH - 0xD743: 0x8B49, //CJK UNIFIED IDEOGRAPH - 0xD744: 0x8B4A, //CJK UNIFIED IDEOGRAPH - 0xD745: 0x8B4B, //CJK UNIFIED IDEOGRAPH - 0xD746: 0x8B4C, //CJK UNIFIED IDEOGRAPH - 0xD747: 0x8B4D, //CJK UNIFIED IDEOGRAPH - 0xD748: 0x8B4E, //CJK UNIFIED IDEOGRAPH - 0xD749: 0x8B4F, //CJK UNIFIED IDEOGRAPH - 0xD74A: 0x8B50, //CJK UNIFIED IDEOGRAPH - 0xD74B: 0x8B51, //CJK UNIFIED IDEOGRAPH - 0xD74C: 0x8B52, //CJK UNIFIED IDEOGRAPH - 0xD74D: 0x8B53, //CJK UNIFIED IDEOGRAPH - 0xD74E: 0x8B54, //CJK UNIFIED IDEOGRAPH - 0xD74F: 0x8B55, //CJK UNIFIED IDEOGRAPH - 0xD750: 0x8B56, //CJK UNIFIED IDEOGRAPH - 0xD751: 0x8B57, //CJK UNIFIED IDEOGRAPH - 0xD752: 0x8B58, //CJK UNIFIED IDEOGRAPH - 0xD753: 0x8B59, //CJK UNIFIED IDEOGRAPH - 0xD754: 0x8B5A, //CJK UNIFIED IDEOGRAPH - 0xD755: 0x8B5B, //CJK UNIFIED IDEOGRAPH - 0xD756: 0x8B5C, //CJK UNIFIED IDEOGRAPH - 0xD757: 0x8B5D, //CJK UNIFIED IDEOGRAPH - 0xD758: 0x8B5E, //CJK UNIFIED IDEOGRAPH - 0xD759: 0x8B5F, //CJK UNIFIED IDEOGRAPH - 0xD75A: 0x8B60, //CJK UNIFIED IDEOGRAPH - 0xD75B: 0x8B61, //CJK UNIFIED IDEOGRAPH - 0xD75C: 0x8B62, //CJK UNIFIED IDEOGRAPH - 0xD75D: 0x8B63, //CJK UNIFIED IDEOGRAPH - 0xD75E: 0x8B64, //CJK UNIFIED IDEOGRAPH - 0xD75F: 0x8B65, //CJK UNIFIED IDEOGRAPH - 0xD760: 0x8B67, //CJK UNIFIED IDEOGRAPH - 0xD761: 0x8B68, //CJK UNIFIED IDEOGRAPH - 0xD762: 0x8B69, //CJK UNIFIED IDEOGRAPH - 0xD763: 0x8B6A, //CJK UNIFIED IDEOGRAPH - 0xD764: 0x8B6B, //CJK UNIFIED IDEOGRAPH - 0xD765: 0x8B6D, //CJK UNIFIED IDEOGRAPH - 0xD766: 0x8B6E, //CJK UNIFIED IDEOGRAPH - 0xD767: 0x8B6F, //CJK UNIFIED IDEOGRAPH - 0xD768: 0x8B70, //CJK UNIFIED IDEOGRAPH - 0xD769: 0x8B71, //CJK UNIFIED IDEOGRAPH - 0xD76A: 0x8B72, //CJK UNIFIED IDEOGRAPH - 0xD76B: 0x8B73, //CJK UNIFIED IDEOGRAPH - 0xD76C: 0x8B74, //CJK UNIFIED IDEOGRAPH - 0xD76D: 0x8B75, //CJK UNIFIED IDEOGRAPH - 0xD76E: 0x8B76, //CJK UNIFIED IDEOGRAPH - 0xD76F: 0x8B77, //CJK UNIFIED IDEOGRAPH - 0xD770: 0x8B78, //CJK UNIFIED IDEOGRAPH - 0xD771: 0x8B79, //CJK UNIFIED IDEOGRAPH - 0xD772: 0x8B7A, //CJK UNIFIED IDEOGRAPH - 0xD773: 0x8B7B, //CJK UNIFIED IDEOGRAPH - 0xD774: 0x8B7C, //CJK UNIFIED IDEOGRAPH - 0xD775: 0x8B7D, //CJK UNIFIED IDEOGRAPH - 0xD776: 0x8B7E, //CJK UNIFIED IDEOGRAPH - 0xD777: 0x8B7F, //CJK UNIFIED IDEOGRAPH - 0xD778: 0x8B80, //CJK UNIFIED IDEOGRAPH - 0xD779: 0x8B81, //CJK UNIFIED IDEOGRAPH - 0xD77A: 0x8B82, //CJK UNIFIED IDEOGRAPH - 0xD77B: 0x8B83, //CJK UNIFIED IDEOGRAPH - 0xD77C: 0x8B84, //CJK UNIFIED IDEOGRAPH - 0xD77D: 0x8B85, //CJK UNIFIED IDEOGRAPH - 0xD77E: 0x8B86, //CJK UNIFIED IDEOGRAPH - 0xD780: 0x8B87, //CJK UNIFIED IDEOGRAPH - 0xD781: 0x8B88, //CJK UNIFIED IDEOGRAPH - 0xD782: 0x8B89, //CJK UNIFIED IDEOGRAPH - 0xD783: 0x8B8A, //CJK UNIFIED IDEOGRAPH - 0xD784: 0x8B8B, //CJK UNIFIED IDEOGRAPH - 0xD785: 0x8B8C, //CJK UNIFIED IDEOGRAPH - 0xD786: 0x8B8D, //CJK UNIFIED IDEOGRAPH - 0xD787: 0x8B8E, //CJK UNIFIED IDEOGRAPH - 0xD788: 0x8B8F, //CJK UNIFIED IDEOGRAPH - 0xD789: 0x8B90, //CJK UNIFIED IDEOGRAPH - 0xD78A: 0x8B91, //CJK UNIFIED IDEOGRAPH - 0xD78B: 0x8B92, //CJK UNIFIED IDEOGRAPH - 0xD78C: 0x8B93, //CJK UNIFIED IDEOGRAPH - 0xD78D: 0x8B94, //CJK UNIFIED IDEOGRAPH - 0xD78E: 0x8B95, //CJK UNIFIED IDEOGRAPH - 0xD78F: 0x8B96, //CJK UNIFIED IDEOGRAPH - 0xD790: 0x8B97, //CJK UNIFIED IDEOGRAPH - 0xD791: 0x8B98, //CJK UNIFIED IDEOGRAPH - 0xD792: 0x8B99, //CJK UNIFIED IDEOGRAPH - 0xD793: 0x8B9A, //CJK UNIFIED IDEOGRAPH - 0xD794: 0x8B9B, //CJK UNIFIED IDEOGRAPH - 0xD795: 0x8B9C, //CJK UNIFIED IDEOGRAPH - 0xD796: 0x8B9D, //CJK UNIFIED IDEOGRAPH - 0xD797: 0x8B9E, //CJK UNIFIED IDEOGRAPH - 0xD798: 0x8B9F, //CJK UNIFIED IDEOGRAPH - 0xD799: 0x8BAC, //CJK UNIFIED IDEOGRAPH - 0xD79A: 0x8BB1, //CJK UNIFIED IDEOGRAPH - 0xD79B: 0x8BBB, //CJK UNIFIED IDEOGRAPH - 0xD79C: 0x8BC7, //CJK UNIFIED IDEOGRAPH - 0xD79D: 0x8BD0, //CJK UNIFIED IDEOGRAPH - 0xD79E: 0x8BEA, //CJK UNIFIED IDEOGRAPH - 0xD79F: 0x8C09, //CJK UNIFIED IDEOGRAPH - 0xD7A0: 0x8C1E, //CJK UNIFIED IDEOGRAPH - 0xD7A1: 0x4F4F, //CJK UNIFIED IDEOGRAPH - 0xD7A2: 0x6CE8, //CJK UNIFIED IDEOGRAPH - 0xD7A3: 0x795D, //CJK UNIFIED IDEOGRAPH - 0xD7A4: 0x9A7B, //CJK UNIFIED IDEOGRAPH - 0xD7A5: 0x6293, //CJK UNIFIED IDEOGRAPH - 0xD7A6: 0x722A, //CJK UNIFIED IDEOGRAPH - 0xD7A7: 0x62FD, //CJK UNIFIED IDEOGRAPH - 0xD7A8: 0x4E13, //CJK UNIFIED IDEOGRAPH - 0xD7A9: 0x7816, //CJK UNIFIED IDEOGRAPH - 0xD7AA: 0x8F6C, //CJK UNIFIED IDEOGRAPH - 0xD7AB: 0x64B0, //CJK UNIFIED IDEOGRAPH - 0xD7AC: 0x8D5A, //CJK UNIFIED IDEOGRAPH - 0xD7AD: 0x7BC6, //CJK UNIFIED IDEOGRAPH - 0xD7AE: 0x6869, //CJK UNIFIED IDEOGRAPH - 0xD7AF: 0x5E84, //CJK UNIFIED IDEOGRAPH - 0xD7B0: 0x88C5, //CJK UNIFIED IDEOGRAPH - 0xD7B1: 0x5986, //CJK UNIFIED IDEOGRAPH - 0xD7B2: 0x649E, //CJK UNIFIED IDEOGRAPH - 0xD7B3: 0x58EE, //CJK UNIFIED IDEOGRAPH - 0xD7B4: 0x72B6, //CJK UNIFIED IDEOGRAPH - 0xD7B5: 0x690E, //CJK UNIFIED IDEOGRAPH - 0xD7B6: 0x9525, //CJK UNIFIED IDEOGRAPH - 0xD7B7: 0x8FFD, //CJK UNIFIED IDEOGRAPH - 0xD7B8: 0x8D58, //CJK UNIFIED IDEOGRAPH - 0xD7B9: 0x5760, //CJK UNIFIED IDEOGRAPH - 0xD7BA: 0x7F00, //CJK UNIFIED IDEOGRAPH - 0xD7BB: 0x8C06, //CJK UNIFIED IDEOGRAPH - 0xD7BC: 0x51C6, //CJK UNIFIED IDEOGRAPH - 0xD7BD: 0x6349, //CJK UNIFIED IDEOGRAPH - 0xD7BE: 0x62D9, //CJK UNIFIED IDEOGRAPH - 0xD7BF: 0x5353, //CJK UNIFIED IDEOGRAPH - 0xD7C0: 0x684C, //CJK UNIFIED IDEOGRAPH - 0xD7C1: 0x7422, //CJK UNIFIED IDEOGRAPH - 0xD7C2: 0x8301, //CJK UNIFIED IDEOGRAPH - 0xD7C3: 0x914C, //CJK UNIFIED IDEOGRAPH - 0xD7C4: 0x5544, //CJK UNIFIED IDEOGRAPH - 0xD7C5: 0x7740, //CJK UNIFIED IDEOGRAPH - 0xD7C6: 0x707C, //CJK UNIFIED IDEOGRAPH - 0xD7C7: 0x6D4A, //CJK UNIFIED IDEOGRAPH - 0xD7C8: 0x5179, //CJK UNIFIED IDEOGRAPH - 0xD7C9: 0x54A8, //CJK UNIFIED IDEOGRAPH - 0xD7CA: 0x8D44, //CJK UNIFIED IDEOGRAPH - 0xD7CB: 0x59FF, //CJK UNIFIED IDEOGRAPH - 0xD7CC: 0x6ECB, //CJK UNIFIED IDEOGRAPH - 0xD7CD: 0x6DC4, //CJK UNIFIED IDEOGRAPH - 0xD7CE: 0x5B5C, //CJK UNIFIED IDEOGRAPH - 0xD7CF: 0x7D2B, //CJK UNIFIED IDEOGRAPH - 0xD7D0: 0x4ED4, //CJK UNIFIED IDEOGRAPH - 0xD7D1: 0x7C7D, //CJK UNIFIED IDEOGRAPH - 0xD7D2: 0x6ED3, //CJK UNIFIED IDEOGRAPH - 0xD7D3: 0x5B50, //CJK UNIFIED IDEOGRAPH - 0xD7D4: 0x81EA, //CJK UNIFIED IDEOGRAPH - 0xD7D5: 0x6E0D, //CJK UNIFIED IDEOGRAPH - 0xD7D6: 0x5B57, //CJK UNIFIED IDEOGRAPH - 0xD7D7: 0x9B03, //CJK UNIFIED IDEOGRAPH - 0xD7D8: 0x68D5, //CJK UNIFIED IDEOGRAPH - 0xD7D9: 0x8E2A, //CJK UNIFIED IDEOGRAPH - 0xD7DA: 0x5B97, //CJK UNIFIED IDEOGRAPH - 0xD7DB: 0x7EFC, //CJK UNIFIED IDEOGRAPH - 0xD7DC: 0x603B, //CJK UNIFIED IDEOGRAPH - 0xD7DD: 0x7EB5, //CJK UNIFIED IDEOGRAPH - 0xD7DE: 0x90B9, //CJK UNIFIED IDEOGRAPH - 0xD7DF: 0x8D70, //CJK UNIFIED IDEOGRAPH - 0xD7E0: 0x594F, //CJK UNIFIED IDEOGRAPH - 0xD7E1: 0x63CD, //CJK UNIFIED IDEOGRAPH - 0xD7E2: 0x79DF, //CJK UNIFIED IDEOGRAPH - 0xD7E3: 0x8DB3, //CJK UNIFIED IDEOGRAPH - 0xD7E4: 0x5352, //CJK UNIFIED IDEOGRAPH - 0xD7E5: 0x65CF, //CJK UNIFIED IDEOGRAPH - 0xD7E6: 0x7956, //CJK UNIFIED IDEOGRAPH - 0xD7E7: 0x8BC5, //CJK UNIFIED IDEOGRAPH - 0xD7E8: 0x963B, //CJK UNIFIED IDEOGRAPH - 0xD7E9: 0x7EC4, //CJK UNIFIED IDEOGRAPH - 0xD7EA: 0x94BB, //CJK UNIFIED IDEOGRAPH - 0xD7EB: 0x7E82, //CJK UNIFIED IDEOGRAPH - 0xD7EC: 0x5634, //CJK UNIFIED IDEOGRAPH - 0xD7ED: 0x9189, //CJK UNIFIED IDEOGRAPH - 0xD7EE: 0x6700, //CJK UNIFIED IDEOGRAPH - 0xD7EF: 0x7F6A, //CJK UNIFIED IDEOGRAPH - 0xD7F0: 0x5C0A, //CJK UNIFIED IDEOGRAPH - 0xD7F1: 0x9075, //CJK UNIFIED IDEOGRAPH - 0xD7F2: 0x6628, //CJK UNIFIED IDEOGRAPH - 0xD7F3: 0x5DE6, //CJK UNIFIED IDEOGRAPH - 0xD7F4: 0x4F50, //CJK UNIFIED IDEOGRAPH - 0xD7F5: 0x67DE, //CJK UNIFIED IDEOGRAPH - 0xD7F6: 0x505A, //CJK UNIFIED IDEOGRAPH - 0xD7F7: 0x4F5C, //CJK UNIFIED IDEOGRAPH - 0xD7F8: 0x5750, //CJK UNIFIED IDEOGRAPH - 0xD7F9: 0x5EA7, //CJK UNIFIED IDEOGRAPH - 0xD840: 0x8C38, //CJK UNIFIED IDEOGRAPH - 0xD841: 0x8C39, //CJK UNIFIED IDEOGRAPH - 0xD842: 0x8C3A, //CJK UNIFIED IDEOGRAPH - 0xD843: 0x8C3B, //CJK UNIFIED IDEOGRAPH - 0xD844: 0x8C3C, //CJK UNIFIED IDEOGRAPH - 0xD845: 0x8C3D, //CJK UNIFIED IDEOGRAPH - 0xD846: 0x8C3E, //CJK UNIFIED IDEOGRAPH - 0xD847: 0x8C3F, //CJK UNIFIED IDEOGRAPH - 0xD848: 0x8C40, //CJK UNIFIED IDEOGRAPH - 0xD849: 0x8C42, //CJK UNIFIED IDEOGRAPH - 0xD84A: 0x8C43, //CJK UNIFIED IDEOGRAPH - 0xD84B: 0x8C44, //CJK UNIFIED IDEOGRAPH - 0xD84C: 0x8C45, //CJK UNIFIED IDEOGRAPH - 0xD84D: 0x8C48, //CJK UNIFIED IDEOGRAPH - 0xD84E: 0x8C4A, //CJK UNIFIED IDEOGRAPH - 0xD84F: 0x8C4B, //CJK UNIFIED IDEOGRAPH - 0xD850: 0x8C4D, //CJK UNIFIED IDEOGRAPH - 0xD851: 0x8C4E, //CJK UNIFIED IDEOGRAPH - 0xD852: 0x8C4F, //CJK UNIFIED IDEOGRAPH - 0xD853: 0x8C50, //CJK UNIFIED IDEOGRAPH - 0xD854: 0x8C51, //CJK UNIFIED IDEOGRAPH - 0xD855: 0x8C52, //CJK UNIFIED IDEOGRAPH - 0xD856: 0x8C53, //CJK UNIFIED IDEOGRAPH - 0xD857: 0x8C54, //CJK UNIFIED IDEOGRAPH - 0xD858: 0x8C56, //CJK UNIFIED IDEOGRAPH - 0xD859: 0x8C57, //CJK UNIFIED IDEOGRAPH - 0xD85A: 0x8C58, //CJK UNIFIED IDEOGRAPH - 0xD85B: 0x8C59, //CJK UNIFIED IDEOGRAPH - 0xD85C: 0x8C5B, //CJK UNIFIED IDEOGRAPH - 0xD85D: 0x8C5C, //CJK UNIFIED IDEOGRAPH - 0xD85E: 0x8C5D, //CJK UNIFIED IDEOGRAPH - 0xD85F: 0x8C5E, //CJK UNIFIED IDEOGRAPH - 0xD860: 0x8C5F, //CJK UNIFIED IDEOGRAPH - 0xD861: 0x8C60, //CJK UNIFIED IDEOGRAPH - 0xD862: 0x8C63, //CJK UNIFIED IDEOGRAPH - 0xD863: 0x8C64, //CJK UNIFIED IDEOGRAPH - 0xD864: 0x8C65, //CJK UNIFIED IDEOGRAPH - 0xD865: 0x8C66, //CJK UNIFIED IDEOGRAPH - 0xD866: 0x8C67, //CJK UNIFIED IDEOGRAPH - 0xD867: 0x8C68, //CJK UNIFIED IDEOGRAPH - 0xD868: 0x8C69, //CJK UNIFIED IDEOGRAPH - 0xD869: 0x8C6C, //CJK UNIFIED IDEOGRAPH - 0xD86A: 0x8C6D, //CJK UNIFIED IDEOGRAPH - 0xD86B: 0x8C6E, //CJK UNIFIED IDEOGRAPH - 0xD86C: 0x8C6F, //CJK UNIFIED IDEOGRAPH - 0xD86D: 0x8C70, //CJK UNIFIED IDEOGRAPH - 0xD86E: 0x8C71, //CJK UNIFIED IDEOGRAPH - 0xD86F: 0x8C72, //CJK UNIFIED IDEOGRAPH - 0xD870: 0x8C74, //CJK UNIFIED IDEOGRAPH - 0xD871: 0x8C75, //CJK UNIFIED IDEOGRAPH - 0xD872: 0x8C76, //CJK UNIFIED IDEOGRAPH - 0xD873: 0x8C77, //CJK UNIFIED IDEOGRAPH - 0xD874: 0x8C7B, //CJK UNIFIED IDEOGRAPH - 0xD875: 0x8C7C, //CJK UNIFIED IDEOGRAPH - 0xD876: 0x8C7D, //CJK UNIFIED IDEOGRAPH - 0xD877: 0x8C7E, //CJK UNIFIED IDEOGRAPH - 0xD878: 0x8C7F, //CJK UNIFIED IDEOGRAPH - 0xD879: 0x8C80, //CJK UNIFIED IDEOGRAPH - 0xD87A: 0x8C81, //CJK UNIFIED IDEOGRAPH - 0xD87B: 0x8C83, //CJK UNIFIED IDEOGRAPH - 0xD87C: 0x8C84, //CJK UNIFIED IDEOGRAPH - 0xD87D: 0x8C86, //CJK UNIFIED IDEOGRAPH - 0xD87E: 0x8C87, //CJK UNIFIED IDEOGRAPH - 0xD880: 0x8C88, //CJK UNIFIED IDEOGRAPH - 0xD881: 0x8C8B, //CJK UNIFIED IDEOGRAPH - 0xD882: 0x8C8D, //CJK UNIFIED IDEOGRAPH - 0xD883: 0x8C8E, //CJK UNIFIED IDEOGRAPH - 0xD884: 0x8C8F, //CJK UNIFIED IDEOGRAPH - 0xD885: 0x8C90, //CJK UNIFIED IDEOGRAPH - 0xD886: 0x8C91, //CJK UNIFIED IDEOGRAPH - 0xD887: 0x8C92, //CJK UNIFIED IDEOGRAPH - 0xD888: 0x8C93, //CJK UNIFIED IDEOGRAPH - 0xD889: 0x8C95, //CJK UNIFIED IDEOGRAPH - 0xD88A: 0x8C96, //CJK UNIFIED IDEOGRAPH - 0xD88B: 0x8C97, //CJK UNIFIED IDEOGRAPH - 0xD88C: 0x8C99, //CJK UNIFIED IDEOGRAPH - 0xD88D: 0x8C9A, //CJK UNIFIED IDEOGRAPH - 0xD88E: 0x8C9B, //CJK UNIFIED IDEOGRAPH - 0xD88F: 0x8C9C, //CJK UNIFIED IDEOGRAPH - 0xD890: 0x8C9D, //CJK UNIFIED IDEOGRAPH - 0xD891: 0x8C9E, //CJK UNIFIED IDEOGRAPH - 0xD892: 0x8C9F, //CJK UNIFIED IDEOGRAPH - 0xD893: 0x8CA0, //CJK UNIFIED IDEOGRAPH - 0xD894: 0x8CA1, //CJK UNIFIED IDEOGRAPH - 0xD895: 0x8CA2, //CJK UNIFIED IDEOGRAPH - 0xD896: 0x8CA3, //CJK UNIFIED IDEOGRAPH - 0xD897: 0x8CA4, //CJK UNIFIED IDEOGRAPH - 0xD898: 0x8CA5, //CJK UNIFIED IDEOGRAPH - 0xD899: 0x8CA6, //CJK UNIFIED IDEOGRAPH - 0xD89A: 0x8CA7, //CJK UNIFIED IDEOGRAPH - 0xD89B: 0x8CA8, //CJK UNIFIED IDEOGRAPH - 0xD89C: 0x8CA9, //CJK UNIFIED IDEOGRAPH - 0xD89D: 0x8CAA, //CJK UNIFIED IDEOGRAPH - 0xD89E: 0x8CAB, //CJK UNIFIED IDEOGRAPH - 0xD89F: 0x8CAC, //CJK UNIFIED IDEOGRAPH - 0xD8A0: 0x8CAD, //CJK UNIFIED IDEOGRAPH - 0xD8A1: 0x4E8D, //CJK UNIFIED IDEOGRAPH - 0xD8A2: 0x4E0C, //CJK UNIFIED IDEOGRAPH - 0xD8A3: 0x5140, //CJK UNIFIED IDEOGRAPH - 0xD8A4: 0x4E10, //CJK UNIFIED IDEOGRAPH - 0xD8A5: 0x5EFF, //CJK UNIFIED IDEOGRAPH - 0xD8A6: 0x5345, //CJK UNIFIED IDEOGRAPH - 0xD8A7: 0x4E15, //CJK UNIFIED IDEOGRAPH - 0xD8A8: 0x4E98, //CJK UNIFIED IDEOGRAPH - 0xD8A9: 0x4E1E, //CJK UNIFIED IDEOGRAPH - 0xD8AA: 0x9B32, //CJK UNIFIED IDEOGRAPH - 0xD8AB: 0x5B6C, //CJK UNIFIED IDEOGRAPH - 0xD8AC: 0x5669, //CJK UNIFIED IDEOGRAPH - 0xD8AD: 0x4E28, //CJK UNIFIED IDEOGRAPH - 0xD8AE: 0x79BA, //CJK UNIFIED IDEOGRAPH - 0xD8AF: 0x4E3F, //CJK UNIFIED IDEOGRAPH - 0xD8B0: 0x5315, //CJK UNIFIED IDEOGRAPH - 0xD8B1: 0x4E47, //CJK UNIFIED IDEOGRAPH - 0xD8B2: 0x592D, //CJK UNIFIED IDEOGRAPH - 0xD8B3: 0x723B, //CJK UNIFIED IDEOGRAPH - 0xD8B4: 0x536E, //CJK UNIFIED IDEOGRAPH - 0xD8B5: 0x6C10, //CJK UNIFIED IDEOGRAPH - 0xD8B6: 0x56DF, //CJK UNIFIED IDEOGRAPH - 0xD8B7: 0x80E4, //CJK UNIFIED IDEOGRAPH - 0xD8B8: 0x9997, //CJK UNIFIED IDEOGRAPH - 0xD8B9: 0x6BD3, //CJK UNIFIED IDEOGRAPH - 0xD8BA: 0x777E, //CJK UNIFIED IDEOGRAPH - 0xD8BB: 0x9F17, //CJK UNIFIED IDEOGRAPH - 0xD8BC: 0x4E36, //CJK UNIFIED IDEOGRAPH - 0xD8BD: 0x4E9F, //CJK UNIFIED IDEOGRAPH - 0xD8BE: 0x9F10, //CJK UNIFIED IDEOGRAPH - 0xD8BF: 0x4E5C, //CJK UNIFIED IDEOGRAPH - 0xD8C0: 0x4E69, //CJK UNIFIED IDEOGRAPH - 0xD8C1: 0x4E93, //CJK UNIFIED IDEOGRAPH - 0xD8C2: 0x8288, //CJK UNIFIED IDEOGRAPH - 0xD8C3: 0x5B5B, //CJK UNIFIED IDEOGRAPH - 0xD8C4: 0x556C, //CJK UNIFIED IDEOGRAPH - 0xD8C5: 0x560F, //CJK UNIFIED IDEOGRAPH - 0xD8C6: 0x4EC4, //CJK UNIFIED IDEOGRAPH - 0xD8C7: 0x538D, //CJK UNIFIED IDEOGRAPH - 0xD8C8: 0x539D, //CJK UNIFIED IDEOGRAPH - 0xD8C9: 0x53A3, //CJK UNIFIED IDEOGRAPH - 0xD8CA: 0x53A5, //CJK UNIFIED IDEOGRAPH - 0xD8CB: 0x53AE, //CJK UNIFIED IDEOGRAPH - 0xD8CC: 0x9765, //CJK UNIFIED IDEOGRAPH - 0xD8CD: 0x8D5D, //CJK UNIFIED IDEOGRAPH - 0xD8CE: 0x531A, //CJK UNIFIED IDEOGRAPH - 0xD8CF: 0x53F5, //CJK UNIFIED IDEOGRAPH - 0xD8D0: 0x5326, //CJK UNIFIED IDEOGRAPH - 0xD8D1: 0x532E, //CJK UNIFIED IDEOGRAPH - 0xD8D2: 0x533E, //CJK UNIFIED IDEOGRAPH - 0xD8D3: 0x8D5C, //CJK UNIFIED IDEOGRAPH - 0xD8D4: 0x5366, //CJK UNIFIED IDEOGRAPH - 0xD8D5: 0x5363, //CJK UNIFIED IDEOGRAPH - 0xD8D6: 0x5202, //CJK UNIFIED IDEOGRAPH - 0xD8D7: 0x5208, //CJK UNIFIED IDEOGRAPH - 0xD8D8: 0x520E, //CJK UNIFIED IDEOGRAPH - 0xD8D9: 0x522D, //CJK UNIFIED IDEOGRAPH - 0xD8DA: 0x5233, //CJK UNIFIED IDEOGRAPH - 0xD8DB: 0x523F, //CJK UNIFIED IDEOGRAPH - 0xD8DC: 0x5240, //CJK UNIFIED IDEOGRAPH - 0xD8DD: 0x524C, //CJK UNIFIED IDEOGRAPH - 0xD8DE: 0x525E, //CJK UNIFIED IDEOGRAPH - 0xD8DF: 0x5261, //CJK UNIFIED IDEOGRAPH - 0xD8E0: 0x525C, //CJK UNIFIED IDEOGRAPH - 0xD8E1: 0x84AF, //CJK UNIFIED IDEOGRAPH - 0xD8E2: 0x527D, //CJK UNIFIED IDEOGRAPH - 0xD8E3: 0x5282, //CJK UNIFIED IDEOGRAPH - 0xD8E4: 0x5281, //CJK UNIFIED IDEOGRAPH - 0xD8E5: 0x5290, //CJK UNIFIED IDEOGRAPH - 0xD8E6: 0x5293, //CJK UNIFIED IDEOGRAPH - 0xD8E7: 0x5182, //CJK UNIFIED IDEOGRAPH - 0xD8E8: 0x7F54, //CJK UNIFIED IDEOGRAPH - 0xD8E9: 0x4EBB, //CJK UNIFIED IDEOGRAPH - 0xD8EA: 0x4EC3, //CJK UNIFIED IDEOGRAPH - 0xD8EB: 0x4EC9, //CJK UNIFIED IDEOGRAPH - 0xD8EC: 0x4EC2, //CJK UNIFIED IDEOGRAPH - 0xD8ED: 0x4EE8, //CJK UNIFIED IDEOGRAPH - 0xD8EE: 0x4EE1, //CJK UNIFIED IDEOGRAPH - 0xD8EF: 0x4EEB, //CJK UNIFIED IDEOGRAPH - 0xD8F0: 0x4EDE, //CJK UNIFIED IDEOGRAPH - 0xD8F1: 0x4F1B, //CJK UNIFIED IDEOGRAPH - 0xD8F2: 0x4EF3, //CJK UNIFIED IDEOGRAPH - 0xD8F3: 0x4F22, //CJK UNIFIED IDEOGRAPH - 0xD8F4: 0x4F64, //CJK UNIFIED IDEOGRAPH - 0xD8F5: 0x4EF5, //CJK UNIFIED IDEOGRAPH - 0xD8F6: 0x4F25, //CJK UNIFIED IDEOGRAPH - 0xD8F7: 0x4F27, //CJK UNIFIED IDEOGRAPH - 0xD8F8: 0x4F09, //CJK UNIFIED IDEOGRAPH - 0xD8F9: 0x4F2B, //CJK UNIFIED IDEOGRAPH - 0xD8FA: 0x4F5E, //CJK UNIFIED IDEOGRAPH - 0xD8FB: 0x4F67, //CJK UNIFIED IDEOGRAPH - 0xD8FC: 0x6538, //CJK UNIFIED IDEOGRAPH - 0xD8FD: 0x4F5A, //CJK UNIFIED IDEOGRAPH - 0xD8FE: 0x4F5D, //CJK UNIFIED IDEOGRAPH - 0xD940: 0x8CAE, //CJK UNIFIED IDEOGRAPH - 0xD941: 0x8CAF, //CJK UNIFIED IDEOGRAPH - 0xD942: 0x8CB0, //CJK UNIFIED IDEOGRAPH - 0xD943: 0x8CB1, //CJK UNIFIED IDEOGRAPH - 0xD944: 0x8CB2, //CJK UNIFIED IDEOGRAPH - 0xD945: 0x8CB3, //CJK UNIFIED IDEOGRAPH - 0xD946: 0x8CB4, //CJK UNIFIED IDEOGRAPH - 0xD947: 0x8CB5, //CJK UNIFIED IDEOGRAPH - 0xD948: 0x8CB6, //CJK UNIFIED IDEOGRAPH - 0xD949: 0x8CB7, //CJK UNIFIED IDEOGRAPH - 0xD94A: 0x8CB8, //CJK UNIFIED IDEOGRAPH - 0xD94B: 0x8CB9, //CJK UNIFIED IDEOGRAPH - 0xD94C: 0x8CBA, //CJK UNIFIED IDEOGRAPH - 0xD94D: 0x8CBB, //CJK UNIFIED IDEOGRAPH - 0xD94E: 0x8CBC, //CJK UNIFIED IDEOGRAPH - 0xD94F: 0x8CBD, //CJK UNIFIED IDEOGRAPH - 0xD950: 0x8CBE, //CJK UNIFIED IDEOGRAPH - 0xD951: 0x8CBF, //CJK UNIFIED IDEOGRAPH - 0xD952: 0x8CC0, //CJK UNIFIED IDEOGRAPH - 0xD953: 0x8CC1, //CJK UNIFIED IDEOGRAPH - 0xD954: 0x8CC2, //CJK UNIFIED IDEOGRAPH - 0xD955: 0x8CC3, //CJK UNIFIED IDEOGRAPH - 0xD956: 0x8CC4, //CJK UNIFIED IDEOGRAPH - 0xD957: 0x8CC5, //CJK UNIFIED IDEOGRAPH - 0xD958: 0x8CC6, //CJK UNIFIED IDEOGRAPH - 0xD959: 0x8CC7, //CJK UNIFIED IDEOGRAPH - 0xD95A: 0x8CC8, //CJK UNIFIED IDEOGRAPH - 0xD95B: 0x8CC9, //CJK UNIFIED IDEOGRAPH - 0xD95C: 0x8CCA, //CJK UNIFIED IDEOGRAPH - 0xD95D: 0x8CCB, //CJK UNIFIED IDEOGRAPH - 0xD95E: 0x8CCC, //CJK UNIFIED IDEOGRAPH - 0xD95F: 0x8CCD, //CJK UNIFIED IDEOGRAPH - 0xD960: 0x8CCE, //CJK UNIFIED IDEOGRAPH - 0xD961: 0x8CCF, //CJK UNIFIED IDEOGRAPH - 0xD962: 0x8CD0, //CJK UNIFIED IDEOGRAPH - 0xD963: 0x8CD1, //CJK UNIFIED IDEOGRAPH - 0xD964: 0x8CD2, //CJK UNIFIED IDEOGRAPH - 0xD965: 0x8CD3, //CJK UNIFIED IDEOGRAPH - 0xD966: 0x8CD4, //CJK UNIFIED IDEOGRAPH - 0xD967: 0x8CD5, //CJK UNIFIED IDEOGRAPH - 0xD968: 0x8CD6, //CJK UNIFIED IDEOGRAPH - 0xD969: 0x8CD7, //CJK UNIFIED IDEOGRAPH - 0xD96A: 0x8CD8, //CJK UNIFIED IDEOGRAPH - 0xD96B: 0x8CD9, //CJK UNIFIED IDEOGRAPH - 0xD96C: 0x8CDA, //CJK UNIFIED IDEOGRAPH - 0xD96D: 0x8CDB, //CJK UNIFIED IDEOGRAPH - 0xD96E: 0x8CDC, //CJK UNIFIED IDEOGRAPH - 0xD96F: 0x8CDD, //CJK UNIFIED IDEOGRAPH - 0xD970: 0x8CDE, //CJK UNIFIED IDEOGRAPH - 0xD971: 0x8CDF, //CJK UNIFIED IDEOGRAPH - 0xD972: 0x8CE0, //CJK UNIFIED IDEOGRAPH - 0xD973: 0x8CE1, //CJK UNIFIED IDEOGRAPH - 0xD974: 0x8CE2, //CJK UNIFIED IDEOGRAPH - 0xD975: 0x8CE3, //CJK UNIFIED IDEOGRAPH - 0xD976: 0x8CE4, //CJK UNIFIED IDEOGRAPH - 0xD977: 0x8CE5, //CJK UNIFIED IDEOGRAPH - 0xD978: 0x8CE6, //CJK UNIFIED IDEOGRAPH - 0xD979: 0x8CE7, //CJK UNIFIED IDEOGRAPH - 0xD97A: 0x8CE8, //CJK UNIFIED IDEOGRAPH - 0xD97B: 0x8CE9, //CJK UNIFIED IDEOGRAPH - 0xD97C: 0x8CEA, //CJK UNIFIED IDEOGRAPH - 0xD97D: 0x8CEB, //CJK UNIFIED IDEOGRAPH - 0xD97E: 0x8CEC, //CJK UNIFIED IDEOGRAPH - 0xD980: 0x8CED, //CJK UNIFIED IDEOGRAPH - 0xD981: 0x8CEE, //CJK UNIFIED IDEOGRAPH - 0xD982: 0x8CEF, //CJK UNIFIED IDEOGRAPH - 0xD983: 0x8CF0, //CJK UNIFIED IDEOGRAPH - 0xD984: 0x8CF1, //CJK UNIFIED IDEOGRAPH - 0xD985: 0x8CF2, //CJK UNIFIED IDEOGRAPH - 0xD986: 0x8CF3, //CJK UNIFIED IDEOGRAPH - 0xD987: 0x8CF4, //CJK UNIFIED IDEOGRAPH - 0xD988: 0x8CF5, //CJK UNIFIED IDEOGRAPH - 0xD989: 0x8CF6, //CJK UNIFIED IDEOGRAPH - 0xD98A: 0x8CF7, //CJK UNIFIED IDEOGRAPH - 0xD98B: 0x8CF8, //CJK UNIFIED IDEOGRAPH - 0xD98C: 0x8CF9, //CJK UNIFIED IDEOGRAPH - 0xD98D: 0x8CFA, //CJK UNIFIED IDEOGRAPH - 0xD98E: 0x8CFB, //CJK UNIFIED IDEOGRAPH - 0xD98F: 0x8CFC, //CJK UNIFIED IDEOGRAPH - 0xD990: 0x8CFD, //CJK UNIFIED IDEOGRAPH - 0xD991: 0x8CFE, //CJK UNIFIED IDEOGRAPH - 0xD992: 0x8CFF, //CJK UNIFIED IDEOGRAPH - 0xD993: 0x8D00, //CJK UNIFIED IDEOGRAPH - 0xD994: 0x8D01, //CJK UNIFIED IDEOGRAPH - 0xD995: 0x8D02, //CJK UNIFIED IDEOGRAPH - 0xD996: 0x8D03, //CJK UNIFIED IDEOGRAPH - 0xD997: 0x8D04, //CJK UNIFIED IDEOGRAPH - 0xD998: 0x8D05, //CJK UNIFIED IDEOGRAPH - 0xD999: 0x8D06, //CJK UNIFIED IDEOGRAPH - 0xD99A: 0x8D07, //CJK UNIFIED IDEOGRAPH - 0xD99B: 0x8D08, //CJK UNIFIED IDEOGRAPH - 0xD99C: 0x8D09, //CJK UNIFIED IDEOGRAPH - 0xD99D: 0x8D0A, //CJK UNIFIED IDEOGRAPH - 0xD99E: 0x8D0B, //CJK UNIFIED IDEOGRAPH - 0xD99F: 0x8D0C, //CJK UNIFIED IDEOGRAPH - 0xD9A0: 0x8D0D, //CJK UNIFIED IDEOGRAPH - 0xD9A1: 0x4F5F, //CJK UNIFIED IDEOGRAPH - 0xD9A2: 0x4F57, //CJK UNIFIED IDEOGRAPH - 0xD9A3: 0x4F32, //CJK UNIFIED IDEOGRAPH - 0xD9A4: 0x4F3D, //CJK UNIFIED IDEOGRAPH - 0xD9A5: 0x4F76, //CJK UNIFIED IDEOGRAPH - 0xD9A6: 0x4F74, //CJK UNIFIED IDEOGRAPH - 0xD9A7: 0x4F91, //CJK UNIFIED IDEOGRAPH - 0xD9A8: 0x4F89, //CJK UNIFIED IDEOGRAPH - 0xD9A9: 0x4F83, //CJK UNIFIED IDEOGRAPH - 0xD9AA: 0x4F8F, //CJK UNIFIED IDEOGRAPH - 0xD9AB: 0x4F7E, //CJK UNIFIED IDEOGRAPH - 0xD9AC: 0x4F7B, //CJK UNIFIED IDEOGRAPH - 0xD9AD: 0x4FAA, //CJK UNIFIED IDEOGRAPH - 0xD9AE: 0x4F7C, //CJK UNIFIED IDEOGRAPH - 0xD9AF: 0x4FAC, //CJK UNIFIED IDEOGRAPH - 0xD9B0: 0x4F94, //CJK UNIFIED IDEOGRAPH - 0xD9B1: 0x4FE6, //CJK UNIFIED IDEOGRAPH - 0xD9B2: 0x4FE8, //CJK UNIFIED IDEOGRAPH - 0xD9B3: 0x4FEA, //CJK UNIFIED IDEOGRAPH - 0xD9B4: 0x4FC5, //CJK UNIFIED IDEOGRAPH - 0xD9B5: 0x4FDA, //CJK UNIFIED IDEOGRAPH - 0xD9B6: 0x4FE3, //CJK UNIFIED IDEOGRAPH - 0xD9B7: 0x4FDC, //CJK UNIFIED IDEOGRAPH - 0xD9B8: 0x4FD1, //CJK UNIFIED IDEOGRAPH - 0xD9B9: 0x4FDF, //CJK UNIFIED IDEOGRAPH - 0xD9BA: 0x4FF8, //CJK UNIFIED IDEOGRAPH - 0xD9BB: 0x5029, //CJK UNIFIED IDEOGRAPH - 0xD9BC: 0x504C, //CJK UNIFIED IDEOGRAPH - 0xD9BD: 0x4FF3, //CJK UNIFIED IDEOGRAPH - 0xD9BE: 0x502C, //CJK UNIFIED IDEOGRAPH - 0xD9BF: 0x500F, //CJK UNIFIED IDEOGRAPH - 0xD9C0: 0x502E, //CJK UNIFIED IDEOGRAPH - 0xD9C1: 0x502D, //CJK UNIFIED IDEOGRAPH - 0xD9C2: 0x4FFE, //CJK UNIFIED IDEOGRAPH - 0xD9C3: 0x501C, //CJK UNIFIED IDEOGRAPH - 0xD9C4: 0x500C, //CJK UNIFIED IDEOGRAPH - 0xD9C5: 0x5025, //CJK UNIFIED IDEOGRAPH - 0xD9C6: 0x5028, //CJK UNIFIED IDEOGRAPH - 0xD9C7: 0x507E, //CJK UNIFIED IDEOGRAPH - 0xD9C8: 0x5043, //CJK UNIFIED IDEOGRAPH - 0xD9C9: 0x5055, //CJK UNIFIED IDEOGRAPH - 0xD9CA: 0x5048, //CJK UNIFIED IDEOGRAPH - 0xD9CB: 0x504E, //CJK UNIFIED IDEOGRAPH - 0xD9CC: 0x506C, //CJK UNIFIED IDEOGRAPH - 0xD9CD: 0x507B, //CJK UNIFIED IDEOGRAPH - 0xD9CE: 0x50A5, //CJK UNIFIED IDEOGRAPH - 0xD9CF: 0x50A7, //CJK UNIFIED IDEOGRAPH - 0xD9D0: 0x50A9, //CJK UNIFIED IDEOGRAPH - 0xD9D1: 0x50BA, //CJK UNIFIED IDEOGRAPH - 0xD9D2: 0x50D6, //CJK UNIFIED IDEOGRAPH - 0xD9D3: 0x5106, //CJK UNIFIED IDEOGRAPH - 0xD9D4: 0x50ED, //CJK UNIFIED IDEOGRAPH - 0xD9D5: 0x50EC, //CJK UNIFIED IDEOGRAPH - 0xD9D6: 0x50E6, //CJK UNIFIED IDEOGRAPH - 0xD9D7: 0x50EE, //CJK UNIFIED IDEOGRAPH - 0xD9D8: 0x5107, //CJK UNIFIED IDEOGRAPH - 0xD9D9: 0x510B, //CJK UNIFIED IDEOGRAPH - 0xD9DA: 0x4EDD, //CJK UNIFIED IDEOGRAPH - 0xD9DB: 0x6C3D, //CJK UNIFIED IDEOGRAPH - 0xD9DC: 0x4F58, //CJK UNIFIED IDEOGRAPH - 0xD9DD: 0x4F65, //CJK UNIFIED IDEOGRAPH - 0xD9DE: 0x4FCE, //CJK UNIFIED IDEOGRAPH - 0xD9DF: 0x9FA0, //CJK UNIFIED IDEOGRAPH - 0xD9E0: 0x6C46, //CJK UNIFIED IDEOGRAPH - 0xD9E1: 0x7C74, //CJK UNIFIED IDEOGRAPH - 0xD9E2: 0x516E, //CJK UNIFIED IDEOGRAPH - 0xD9E3: 0x5DFD, //CJK UNIFIED IDEOGRAPH - 0xD9E4: 0x9EC9, //CJK UNIFIED IDEOGRAPH - 0xD9E5: 0x9998, //CJK UNIFIED IDEOGRAPH - 0xD9E6: 0x5181, //CJK UNIFIED IDEOGRAPH - 0xD9E7: 0x5914, //CJK UNIFIED IDEOGRAPH - 0xD9E8: 0x52F9, //CJK UNIFIED IDEOGRAPH - 0xD9E9: 0x530D, //CJK UNIFIED IDEOGRAPH - 0xD9EA: 0x8A07, //CJK UNIFIED IDEOGRAPH - 0xD9EB: 0x5310, //CJK UNIFIED IDEOGRAPH - 0xD9EC: 0x51EB, //CJK UNIFIED IDEOGRAPH - 0xD9ED: 0x5919, //CJK UNIFIED IDEOGRAPH - 0xD9EE: 0x5155, //CJK UNIFIED IDEOGRAPH - 0xD9EF: 0x4EA0, //CJK UNIFIED IDEOGRAPH - 0xD9F0: 0x5156, //CJK UNIFIED IDEOGRAPH - 0xD9F1: 0x4EB3, //CJK UNIFIED IDEOGRAPH - 0xD9F2: 0x886E, //CJK UNIFIED IDEOGRAPH - 0xD9F3: 0x88A4, //CJK UNIFIED IDEOGRAPH - 0xD9F4: 0x4EB5, //CJK UNIFIED IDEOGRAPH - 0xD9F5: 0x8114, //CJK UNIFIED IDEOGRAPH - 0xD9F6: 0x88D2, //CJK UNIFIED IDEOGRAPH - 0xD9F7: 0x7980, //CJK UNIFIED IDEOGRAPH - 0xD9F8: 0x5B34, //CJK UNIFIED IDEOGRAPH - 0xD9F9: 0x8803, //CJK UNIFIED IDEOGRAPH - 0xD9FA: 0x7FB8, //CJK UNIFIED IDEOGRAPH - 0xD9FB: 0x51AB, //CJK UNIFIED IDEOGRAPH - 0xD9FC: 0x51B1, //CJK UNIFIED IDEOGRAPH - 0xD9FD: 0x51BD, //CJK UNIFIED IDEOGRAPH - 0xD9FE: 0x51BC, //CJK UNIFIED IDEOGRAPH - 0xDA40: 0x8D0E, //CJK UNIFIED IDEOGRAPH - 0xDA41: 0x8D0F, //CJK UNIFIED IDEOGRAPH - 0xDA42: 0x8D10, //CJK UNIFIED IDEOGRAPH - 0xDA43: 0x8D11, //CJK UNIFIED IDEOGRAPH - 0xDA44: 0x8D12, //CJK UNIFIED IDEOGRAPH - 0xDA45: 0x8D13, //CJK UNIFIED IDEOGRAPH - 0xDA46: 0x8D14, //CJK UNIFIED IDEOGRAPH - 0xDA47: 0x8D15, //CJK UNIFIED IDEOGRAPH - 0xDA48: 0x8D16, //CJK UNIFIED IDEOGRAPH - 0xDA49: 0x8D17, //CJK UNIFIED IDEOGRAPH - 0xDA4A: 0x8D18, //CJK UNIFIED IDEOGRAPH - 0xDA4B: 0x8D19, //CJK UNIFIED IDEOGRAPH - 0xDA4C: 0x8D1A, //CJK UNIFIED IDEOGRAPH - 0xDA4D: 0x8D1B, //CJK UNIFIED IDEOGRAPH - 0xDA4E: 0x8D1C, //CJK UNIFIED IDEOGRAPH - 0xDA4F: 0x8D20, //CJK UNIFIED IDEOGRAPH - 0xDA50: 0x8D51, //CJK UNIFIED IDEOGRAPH - 0xDA51: 0x8D52, //CJK UNIFIED IDEOGRAPH - 0xDA52: 0x8D57, //CJK UNIFIED IDEOGRAPH - 0xDA53: 0x8D5F, //CJK UNIFIED IDEOGRAPH - 0xDA54: 0x8D65, //CJK UNIFIED IDEOGRAPH - 0xDA55: 0x8D68, //CJK UNIFIED IDEOGRAPH - 0xDA56: 0x8D69, //CJK UNIFIED IDEOGRAPH - 0xDA57: 0x8D6A, //CJK UNIFIED IDEOGRAPH - 0xDA58: 0x8D6C, //CJK UNIFIED IDEOGRAPH - 0xDA59: 0x8D6E, //CJK UNIFIED IDEOGRAPH - 0xDA5A: 0x8D6F, //CJK UNIFIED IDEOGRAPH - 0xDA5B: 0x8D71, //CJK UNIFIED IDEOGRAPH - 0xDA5C: 0x8D72, //CJK UNIFIED IDEOGRAPH - 0xDA5D: 0x8D78, //CJK UNIFIED IDEOGRAPH - 0xDA5E: 0x8D79, //CJK UNIFIED IDEOGRAPH - 0xDA5F: 0x8D7A, //CJK UNIFIED IDEOGRAPH - 0xDA60: 0x8D7B, //CJK UNIFIED IDEOGRAPH - 0xDA61: 0x8D7C, //CJK UNIFIED IDEOGRAPH - 0xDA62: 0x8D7D, //CJK UNIFIED IDEOGRAPH - 0xDA63: 0x8D7E, //CJK UNIFIED IDEOGRAPH - 0xDA64: 0x8D7F, //CJK UNIFIED IDEOGRAPH - 0xDA65: 0x8D80, //CJK UNIFIED IDEOGRAPH - 0xDA66: 0x8D82, //CJK UNIFIED IDEOGRAPH - 0xDA67: 0x8D83, //CJK UNIFIED IDEOGRAPH - 0xDA68: 0x8D86, //CJK UNIFIED IDEOGRAPH - 0xDA69: 0x8D87, //CJK UNIFIED IDEOGRAPH - 0xDA6A: 0x8D88, //CJK UNIFIED IDEOGRAPH - 0xDA6B: 0x8D89, //CJK UNIFIED IDEOGRAPH - 0xDA6C: 0x8D8C, //CJK UNIFIED IDEOGRAPH - 0xDA6D: 0x8D8D, //CJK UNIFIED IDEOGRAPH - 0xDA6E: 0x8D8E, //CJK UNIFIED IDEOGRAPH - 0xDA6F: 0x8D8F, //CJK UNIFIED IDEOGRAPH - 0xDA70: 0x8D90, //CJK UNIFIED IDEOGRAPH - 0xDA71: 0x8D92, //CJK UNIFIED IDEOGRAPH - 0xDA72: 0x8D93, //CJK UNIFIED IDEOGRAPH - 0xDA73: 0x8D95, //CJK UNIFIED IDEOGRAPH - 0xDA74: 0x8D96, //CJK UNIFIED IDEOGRAPH - 0xDA75: 0x8D97, //CJK UNIFIED IDEOGRAPH - 0xDA76: 0x8D98, //CJK UNIFIED IDEOGRAPH - 0xDA77: 0x8D99, //CJK UNIFIED IDEOGRAPH - 0xDA78: 0x8D9A, //CJK UNIFIED IDEOGRAPH - 0xDA79: 0x8D9B, //CJK UNIFIED IDEOGRAPH - 0xDA7A: 0x8D9C, //CJK UNIFIED IDEOGRAPH - 0xDA7B: 0x8D9D, //CJK UNIFIED IDEOGRAPH - 0xDA7C: 0x8D9E, //CJK UNIFIED IDEOGRAPH - 0xDA7D: 0x8DA0, //CJK UNIFIED IDEOGRAPH - 0xDA7E: 0x8DA1, //CJK UNIFIED IDEOGRAPH - 0xDA80: 0x8DA2, //CJK UNIFIED IDEOGRAPH - 0xDA81: 0x8DA4, //CJK UNIFIED IDEOGRAPH - 0xDA82: 0x8DA5, //CJK UNIFIED IDEOGRAPH - 0xDA83: 0x8DA6, //CJK UNIFIED IDEOGRAPH - 0xDA84: 0x8DA7, //CJK UNIFIED IDEOGRAPH - 0xDA85: 0x8DA8, //CJK UNIFIED IDEOGRAPH - 0xDA86: 0x8DA9, //CJK UNIFIED IDEOGRAPH - 0xDA87: 0x8DAA, //CJK UNIFIED IDEOGRAPH - 0xDA88: 0x8DAB, //CJK UNIFIED IDEOGRAPH - 0xDA89: 0x8DAC, //CJK UNIFIED IDEOGRAPH - 0xDA8A: 0x8DAD, //CJK UNIFIED IDEOGRAPH - 0xDA8B: 0x8DAE, //CJK UNIFIED IDEOGRAPH - 0xDA8C: 0x8DAF, //CJK UNIFIED IDEOGRAPH - 0xDA8D: 0x8DB0, //CJK UNIFIED IDEOGRAPH - 0xDA8E: 0x8DB2, //CJK UNIFIED IDEOGRAPH - 0xDA8F: 0x8DB6, //CJK UNIFIED IDEOGRAPH - 0xDA90: 0x8DB7, //CJK UNIFIED IDEOGRAPH - 0xDA91: 0x8DB9, //CJK UNIFIED IDEOGRAPH - 0xDA92: 0x8DBB, //CJK UNIFIED IDEOGRAPH - 0xDA93: 0x8DBD, //CJK UNIFIED IDEOGRAPH - 0xDA94: 0x8DC0, //CJK UNIFIED IDEOGRAPH - 0xDA95: 0x8DC1, //CJK UNIFIED IDEOGRAPH - 0xDA96: 0x8DC2, //CJK UNIFIED IDEOGRAPH - 0xDA97: 0x8DC5, //CJK UNIFIED IDEOGRAPH - 0xDA98: 0x8DC7, //CJK UNIFIED IDEOGRAPH - 0xDA99: 0x8DC8, //CJK UNIFIED IDEOGRAPH - 0xDA9A: 0x8DC9, //CJK UNIFIED IDEOGRAPH - 0xDA9B: 0x8DCA, //CJK UNIFIED IDEOGRAPH - 0xDA9C: 0x8DCD, //CJK UNIFIED IDEOGRAPH - 0xDA9D: 0x8DD0, //CJK UNIFIED IDEOGRAPH - 0xDA9E: 0x8DD2, //CJK UNIFIED IDEOGRAPH - 0xDA9F: 0x8DD3, //CJK UNIFIED IDEOGRAPH - 0xDAA0: 0x8DD4, //CJK UNIFIED IDEOGRAPH - 0xDAA1: 0x51C7, //CJK UNIFIED IDEOGRAPH - 0xDAA2: 0x5196, //CJK UNIFIED IDEOGRAPH - 0xDAA3: 0x51A2, //CJK UNIFIED IDEOGRAPH - 0xDAA4: 0x51A5, //CJK UNIFIED IDEOGRAPH - 0xDAA5: 0x8BA0, //CJK UNIFIED IDEOGRAPH - 0xDAA6: 0x8BA6, //CJK UNIFIED IDEOGRAPH - 0xDAA7: 0x8BA7, //CJK UNIFIED IDEOGRAPH - 0xDAA8: 0x8BAA, //CJK UNIFIED IDEOGRAPH - 0xDAA9: 0x8BB4, //CJK UNIFIED IDEOGRAPH - 0xDAAA: 0x8BB5, //CJK UNIFIED IDEOGRAPH - 0xDAAB: 0x8BB7, //CJK UNIFIED IDEOGRAPH - 0xDAAC: 0x8BC2, //CJK UNIFIED IDEOGRAPH - 0xDAAD: 0x8BC3, //CJK UNIFIED IDEOGRAPH - 0xDAAE: 0x8BCB, //CJK UNIFIED IDEOGRAPH - 0xDAAF: 0x8BCF, //CJK UNIFIED IDEOGRAPH - 0xDAB0: 0x8BCE, //CJK UNIFIED IDEOGRAPH - 0xDAB1: 0x8BD2, //CJK UNIFIED IDEOGRAPH - 0xDAB2: 0x8BD3, //CJK UNIFIED IDEOGRAPH - 0xDAB3: 0x8BD4, //CJK UNIFIED IDEOGRAPH - 0xDAB4: 0x8BD6, //CJK UNIFIED IDEOGRAPH - 0xDAB5: 0x8BD8, //CJK UNIFIED IDEOGRAPH - 0xDAB6: 0x8BD9, //CJK UNIFIED IDEOGRAPH - 0xDAB7: 0x8BDC, //CJK UNIFIED IDEOGRAPH - 0xDAB8: 0x8BDF, //CJK UNIFIED IDEOGRAPH - 0xDAB9: 0x8BE0, //CJK UNIFIED IDEOGRAPH - 0xDABA: 0x8BE4, //CJK UNIFIED IDEOGRAPH - 0xDABB: 0x8BE8, //CJK UNIFIED IDEOGRAPH - 0xDABC: 0x8BE9, //CJK UNIFIED IDEOGRAPH - 0xDABD: 0x8BEE, //CJK UNIFIED IDEOGRAPH - 0xDABE: 0x8BF0, //CJK UNIFIED IDEOGRAPH - 0xDABF: 0x8BF3, //CJK UNIFIED IDEOGRAPH - 0xDAC0: 0x8BF6, //CJK UNIFIED IDEOGRAPH - 0xDAC1: 0x8BF9, //CJK UNIFIED IDEOGRAPH - 0xDAC2: 0x8BFC, //CJK UNIFIED IDEOGRAPH - 0xDAC3: 0x8BFF, //CJK UNIFIED IDEOGRAPH - 0xDAC4: 0x8C00, //CJK UNIFIED IDEOGRAPH - 0xDAC5: 0x8C02, //CJK UNIFIED IDEOGRAPH - 0xDAC6: 0x8C04, //CJK UNIFIED IDEOGRAPH - 0xDAC7: 0x8C07, //CJK UNIFIED IDEOGRAPH - 0xDAC8: 0x8C0C, //CJK UNIFIED IDEOGRAPH - 0xDAC9: 0x8C0F, //CJK UNIFIED IDEOGRAPH - 0xDACA: 0x8C11, //CJK UNIFIED IDEOGRAPH - 0xDACB: 0x8C12, //CJK UNIFIED IDEOGRAPH - 0xDACC: 0x8C14, //CJK UNIFIED IDEOGRAPH - 0xDACD: 0x8C15, //CJK UNIFIED IDEOGRAPH - 0xDACE: 0x8C16, //CJK UNIFIED IDEOGRAPH - 0xDACF: 0x8C19, //CJK UNIFIED IDEOGRAPH - 0xDAD0: 0x8C1B, //CJK UNIFIED IDEOGRAPH - 0xDAD1: 0x8C18, //CJK UNIFIED IDEOGRAPH - 0xDAD2: 0x8C1D, //CJK UNIFIED IDEOGRAPH - 0xDAD3: 0x8C1F, //CJK UNIFIED IDEOGRAPH - 0xDAD4: 0x8C20, //CJK UNIFIED IDEOGRAPH - 0xDAD5: 0x8C21, //CJK UNIFIED IDEOGRAPH - 0xDAD6: 0x8C25, //CJK UNIFIED IDEOGRAPH - 0xDAD7: 0x8C27, //CJK UNIFIED IDEOGRAPH - 0xDAD8: 0x8C2A, //CJK UNIFIED IDEOGRAPH - 0xDAD9: 0x8C2B, //CJK UNIFIED IDEOGRAPH - 0xDADA: 0x8C2E, //CJK UNIFIED IDEOGRAPH - 0xDADB: 0x8C2F, //CJK UNIFIED IDEOGRAPH - 0xDADC: 0x8C32, //CJK UNIFIED IDEOGRAPH - 0xDADD: 0x8C33, //CJK UNIFIED IDEOGRAPH - 0xDADE: 0x8C35, //CJK UNIFIED IDEOGRAPH - 0xDADF: 0x8C36, //CJK UNIFIED IDEOGRAPH - 0xDAE0: 0x5369, //CJK UNIFIED IDEOGRAPH - 0xDAE1: 0x537A, //CJK UNIFIED IDEOGRAPH - 0xDAE2: 0x961D, //CJK UNIFIED IDEOGRAPH - 0xDAE3: 0x9622, //CJK UNIFIED IDEOGRAPH - 0xDAE4: 0x9621, //CJK UNIFIED IDEOGRAPH - 0xDAE5: 0x9631, //CJK UNIFIED IDEOGRAPH - 0xDAE6: 0x962A, //CJK UNIFIED IDEOGRAPH - 0xDAE7: 0x963D, //CJK UNIFIED IDEOGRAPH - 0xDAE8: 0x963C, //CJK UNIFIED IDEOGRAPH - 0xDAE9: 0x9642, //CJK UNIFIED IDEOGRAPH - 0xDAEA: 0x9649, //CJK UNIFIED IDEOGRAPH - 0xDAEB: 0x9654, //CJK UNIFIED IDEOGRAPH - 0xDAEC: 0x965F, //CJK UNIFIED IDEOGRAPH - 0xDAED: 0x9667, //CJK UNIFIED IDEOGRAPH - 0xDAEE: 0x966C, //CJK UNIFIED IDEOGRAPH - 0xDAEF: 0x9672, //CJK UNIFIED IDEOGRAPH - 0xDAF0: 0x9674, //CJK UNIFIED IDEOGRAPH - 0xDAF1: 0x9688, //CJK UNIFIED IDEOGRAPH - 0xDAF2: 0x968D, //CJK UNIFIED IDEOGRAPH - 0xDAF3: 0x9697, //CJK UNIFIED IDEOGRAPH - 0xDAF4: 0x96B0, //CJK UNIFIED IDEOGRAPH - 0xDAF5: 0x9097, //CJK UNIFIED IDEOGRAPH - 0xDAF6: 0x909B, //CJK UNIFIED IDEOGRAPH - 0xDAF7: 0x909D, //CJK UNIFIED IDEOGRAPH - 0xDAF8: 0x9099, //CJK UNIFIED IDEOGRAPH - 0xDAF9: 0x90AC, //CJK UNIFIED IDEOGRAPH - 0xDAFA: 0x90A1, //CJK UNIFIED IDEOGRAPH - 0xDAFB: 0x90B4, //CJK UNIFIED IDEOGRAPH - 0xDAFC: 0x90B3, //CJK UNIFIED IDEOGRAPH - 0xDAFD: 0x90B6, //CJK UNIFIED IDEOGRAPH - 0xDAFE: 0x90BA, //CJK UNIFIED IDEOGRAPH - 0xDB40: 0x8DD5, //CJK UNIFIED IDEOGRAPH - 0xDB41: 0x8DD8, //CJK UNIFIED IDEOGRAPH - 0xDB42: 0x8DD9, //CJK UNIFIED IDEOGRAPH - 0xDB43: 0x8DDC, //CJK UNIFIED IDEOGRAPH - 0xDB44: 0x8DE0, //CJK UNIFIED IDEOGRAPH - 0xDB45: 0x8DE1, //CJK UNIFIED IDEOGRAPH - 0xDB46: 0x8DE2, //CJK UNIFIED IDEOGRAPH - 0xDB47: 0x8DE5, //CJK UNIFIED IDEOGRAPH - 0xDB48: 0x8DE6, //CJK UNIFIED IDEOGRAPH - 0xDB49: 0x8DE7, //CJK UNIFIED IDEOGRAPH - 0xDB4A: 0x8DE9, //CJK UNIFIED IDEOGRAPH - 0xDB4B: 0x8DED, //CJK UNIFIED IDEOGRAPH - 0xDB4C: 0x8DEE, //CJK UNIFIED IDEOGRAPH - 0xDB4D: 0x8DF0, //CJK UNIFIED IDEOGRAPH - 0xDB4E: 0x8DF1, //CJK UNIFIED IDEOGRAPH - 0xDB4F: 0x8DF2, //CJK UNIFIED IDEOGRAPH - 0xDB50: 0x8DF4, //CJK UNIFIED IDEOGRAPH - 0xDB51: 0x8DF6, //CJK UNIFIED IDEOGRAPH - 0xDB52: 0x8DFC, //CJK UNIFIED IDEOGRAPH - 0xDB53: 0x8DFE, //CJK UNIFIED IDEOGRAPH - 0xDB54: 0x8DFF, //CJK UNIFIED IDEOGRAPH - 0xDB55: 0x8E00, //CJK UNIFIED IDEOGRAPH - 0xDB56: 0x8E01, //CJK UNIFIED IDEOGRAPH - 0xDB57: 0x8E02, //CJK UNIFIED IDEOGRAPH - 0xDB58: 0x8E03, //CJK UNIFIED IDEOGRAPH - 0xDB59: 0x8E04, //CJK UNIFIED IDEOGRAPH - 0xDB5A: 0x8E06, //CJK UNIFIED IDEOGRAPH - 0xDB5B: 0x8E07, //CJK UNIFIED IDEOGRAPH - 0xDB5C: 0x8E08, //CJK UNIFIED IDEOGRAPH - 0xDB5D: 0x8E0B, //CJK UNIFIED IDEOGRAPH - 0xDB5E: 0x8E0D, //CJK UNIFIED IDEOGRAPH - 0xDB5F: 0x8E0E, //CJK UNIFIED IDEOGRAPH - 0xDB60: 0x8E10, //CJK UNIFIED IDEOGRAPH - 0xDB61: 0x8E11, //CJK UNIFIED IDEOGRAPH - 0xDB62: 0x8E12, //CJK UNIFIED IDEOGRAPH - 0xDB63: 0x8E13, //CJK UNIFIED IDEOGRAPH - 0xDB64: 0x8E15, //CJK UNIFIED IDEOGRAPH - 0xDB65: 0x8E16, //CJK UNIFIED IDEOGRAPH - 0xDB66: 0x8E17, //CJK UNIFIED IDEOGRAPH - 0xDB67: 0x8E18, //CJK UNIFIED IDEOGRAPH - 0xDB68: 0x8E19, //CJK UNIFIED IDEOGRAPH - 0xDB69: 0x8E1A, //CJK UNIFIED IDEOGRAPH - 0xDB6A: 0x8E1B, //CJK UNIFIED IDEOGRAPH - 0xDB6B: 0x8E1C, //CJK UNIFIED IDEOGRAPH - 0xDB6C: 0x8E20, //CJK UNIFIED IDEOGRAPH - 0xDB6D: 0x8E21, //CJK UNIFIED IDEOGRAPH - 0xDB6E: 0x8E24, //CJK UNIFIED IDEOGRAPH - 0xDB6F: 0x8E25, //CJK UNIFIED IDEOGRAPH - 0xDB70: 0x8E26, //CJK UNIFIED IDEOGRAPH - 0xDB71: 0x8E27, //CJK UNIFIED IDEOGRAPH - 0xDB72: 0x8E28, //CJK UNIFIED IDEOGRAPH - 0xDB73: 0x8E2B, //CJK UNIFIED IDEOGRAPH - 0xDB74: 0x8E2D, //CJK UNIFIED IDEOGRAPH - 0xDB75: 0x8E30, //CJK UNIFIED IDEOGRAPH - 0xDB76: 0x8E32, //CJK UNIFIED IDEOGRAPH - 0xDB77: 0x8E33, //CJK UNIFIED IDEOGRAPH - 0xDB78: 0x8E34, //CJK UNIFIED IDEOGRAPH - 0xDB79: 0x8E36, //CJK UNIFIED IDEOGRAPH - 0xDB7A: 0x8E37, //CJK UNIFIED IDEOGRAPH - 0xDB7B: 0x8E38, //CJK UNIFIED IDEOGRAPH - 0xDB7C: 0x8E3B, //CJK UNIFIED IDEOGRAPH - 0xDB7D: 0x8E3C, //CJK UNIFIED IDEOGRAPH - 0xDB7E: 0x8E3E, //CJK UNIFIED IDEOGRAPH - 0xDB80: 0x8E3F, //CJK UNIFIED IDEOGRAPH - 0xDB81: 0x8E43, //CJK UNIFIED IDEOGRAPH - 0xDB82: 0x8E45, //CJK UNIFIED IDEOGRAPH - 0xDB83: 0x8E46, //CJK UNIFIED IDEOGRAPH - 0xDB84: 0x8E4C, //CJK UNIFIED IDEOGRAPH - 0xDB85: 0x8E4D, //CJK UNIFIED IDEOGRAPH - 0xDB86: 0x8E4E, //CJK UNIFIED IDEOGRAPH - 0xDB87: 0x8E4F, //CJK UNIFIED IDEOGRAPH - 0xDB88: 0x8E50, //CJK UNIFIED IDEOGRAPH - 0xDB89: 0x8E53, //CJK UNIFIED IDEOGRAPH - 0xDB8A: 0x8E54, //CJK UNIFIED IDEOGRAPH - 0xDB8B: 0x8E55, //CJK UNIFIED IDEOGRAPH - 0xDB8C: 0x8E56, //CJK UNIFIED IDEOGRAPH - 0xDB8D: 0x8E57, //CJK UNIFIED IDEOGRAPH - 0xDB8E: 0x8E58, //CJK UNIFIED IDEOGRAPH - 0xDB8F: 0x8E5A, //CJK UNIFIED IDEOGRAPH - 0xDB90: 0x8E5B, //CJK UNIFIED IDEOGRAPH - 0xDB91: 0x8E5C, //CJK UNIFIED IDEOGRAPH - 0xDB92: 0x8E5D, //CJK UNIFIED IDEOGRAPH - 0xDB93: 0x8E5E, //CJK UNIFIED IDEOGRAPH - 0xDB94: 0x8E5F, //CJK UNIFIED IDEOGRAPH - 0xDB95: 0x8E60, //CJK UNIFIED IDEOGRAPH - 0xDB96: 0x8E61, //CJK UNIFIED IDEOGRAPH - 0xDB97: 0x8E62, //CJK UNIFIED IDEOGRAPH - 0xDB98: 0x8E63, //CJK UNIFIED IDEOGRAPH - 0xDB99: 0x8E64, //CJK UNIFIED IDEOGRAPH - 0xDB9A: 0x8E65, //CJK UNIFIED IDEOGRAPH - 0xDB9B: 0x8E67, //CJK UNIFIED IDEOGRAPH - 0xDB9C: 0x8E68, //CJK UNIFIED IDEOGRAPH - 0xDB9D: 0x8E6A, //CJK UNIFIED IDEOGRAPH - 0xDB9E: 0x8E6B, //CJK UNIFIED IDEOGRAPH - 0xDB9F: 0x8E6E, //CJK UNIFIED IDEOGRAPH - 0xDBA0: 0x8E71, //CJK UNIFIED IDEOGRAPH - 0xDBA1: 0x90B8, //CJK UNIFIED IDEOGRAPH - 0xDBA2: 0x90B0, //CJK UNIFIED IDEOGRAPH - 0xDBA3: 0x90CF, //CJK UNIFIED IDEOGRAPH - 0xDBA4: 0x90C5, //CJK UNIFIED IDEOGRAPH - 0xDBA5: 0x90BE, //CJK UNIFIED IDEOGRAPH - 0xDBA6: 0x90D0, //CJK UNIFIED IDEOGRAPH - 0xDBA7: 0x90C4, //CJK UNIFIED IDEOGRAPH - 0xDBA8: 0x90C7, //CJK UNIFIED IDEOGRAPH - 0xDBA9: 0x90D3, //CJK UNIFIED IDEOGRAPH - 0xDBAA: 0x90E6, //CJK UNIFIED IDEOGRAPH - 0xDBAB: 0x90E2, //CJK UNIFIED IDEOGRAPH - 0xDBAC: 0x90DC, //CJK UNIFIED IDEOGRAPH - 0xDBAD: 0x90D7, //CJK UNIFIED IDEOGRAPH - 0xDBAE: 0x90DB, //CJK UNIFIED IDEOGRAPH - 0xDBAF: 0x90EB, //CJK UNIFIED IDEOGRAPH - 0xDBB0: 0x90EF, //CJK UNIFIED IDEOGRAPH - 0xDBB1: 0x90FE, //CJK UNIFIED IDEOGRAPH - 0xDBB2: 0x9104, //CJK UNIFIED IDEOGRAPH - 0xDBB3: 0x9122, //CJK UNIFIED IDEOGRAPH - 0xDBB4: 0x911E, //CJK UNIFIED IDEOGRAPH - 0xDBB5: 0x9123, //CJK UNIFIED IDEOGRAPH - 0xDBB6: 0x9131, //CJK UNIFIED IDEOGRAPH - 0xDBB7: 0x912F, //CJK UNIFIED IDEOGRAPH - 0xDBB8: 0x9139, //CJK UNIFIED IDEOGRAPH - 0xDBB9: 0x9143, //CJK UNIFIED IDEOGRAPH - 0xDBBA: 0x9146, //CJK UNIFIED IDEOGRAPH - 0xDBBB: 0x520D, //CJK UNIFIED IDEOGRAPH - 0xDBBC: 0x5942, //CJK UNIFIED IDEOGRAPH - 0xDBBD: 0x52A2, //CJK UNIFIED IDEOGRAPH - 0xDBBE: 0x52AC, //CJK UNIFIED IDEOGRAPH - 0xDBBF: 0x52AD, //CJK UNIFIED IDEOGRAPH - 0xDBC0: 0x52BE, //CJK UNIFIED IDEOGRAPH - 0xDBC1: 0x54FF, //CJK UNIFIED IDEOGRAPH - 0xDBC2: 0x52D0, //CJK UNIFIED IDEOGRAPH - 0xDBC3: 0x52D6, //CJK UNIFIED IDEOGRAPH - 0xDBC4: 0x52F0, //CJK UNIFIED IDEOGRAPH - 0xDBC5: 0x53DF, //CJK UNIFIED IDEOGRAPH - 0xDBC6: 0x71EE, //CJK UNIFIED IDEOGRAPH - 0xDBC7: 0x77CD, //CJK UNIFIED IDEOGRAPH - 0xDBC8: 0x5EF4, //CJK UNIFIED IDEOGRAPH - 0xDBC9: 0x51F5, //CJK UNIFIED IDEOGRAPH - 0xDBCA: 0x51FC, //CJK UNIFIED IDEOGRAPH - 0xDBCB: 0x9B2F, //CJK UNIFIED IDEOGRAPH - 0xDBCC: 0x53B6, //CJK UNIFIED IDEOGRAPH - 0xDBCD: 0x5F01, //CJK UNIFIED IDEOGRAPH - 0xDBCE: 0x755A, //CJK UNIFIED IDEOGRAPH - 0xDBCF: 0x5DEF, //CJK UNIFIED IDEOGRAPH - 0xDBD0: 0x574C, //CJK UNIFIED IDEOGRAPH - 0xDBD1: 0x57A9, //CJK UNIFIED IDEOGRAPH - 0xDBD2: 0x57A1, //CJK UNIFIED IDEOGRAPH - 0xDBD3: 0x587E, //CJK UNIFIED IDEOGRAPH - 0xDBD4: 0x58BC, //CJK UNIFIED IDEOGRAPH - 0xDBD5: 0x58C5, //CJK UNIFIED IDEOGRAPH - 0xDBD6: 0x58D1, //CJK UNIFIED IDEOGRAPH - 0xDBD7: 0x5729, //CJK UNIFIED IDEOGRAPH - 0xDBD8: 0x572C, //CJK UNIFIED IDEOGRAPH - 0xDBD9: 0x572A, //CJK UNIFIED IDEOGRAPH - 0xDBDA: 0x5733, //CJK UNIFIED IDEOGRAPH - 0xDBDB: 0x5739, //CJK UNIFIED IDEOGRAPH - 0xDBDC: 0x572E, //CJK UNIFIED IDEOGRAPH - 0xDBDD: 0x572F, //CJK UNIFIED IDEOGRAPH - 0xDBDE: 0x575C, //CJK UNIFIED IDEOGRAPH - 0xDBDF: 0x573B, //CJK UNIFIED IDEOGRAPH - 0xDBE0: 0x5742, //CJK UNIFIED IDEOGRAPH - 0xDBE1: 0x5769, //CJK UNIFIED IDEOGRAPH - 0xDBE2: 0x5785, //CJK UNIFIED IDEOGRAPH - 0xDBE3: 0x576B, //CJK UNIFIED IDEOGRAPH - 0xDBE4: 0x5786, //CJK UNIFIED IDEOGRAPH - 0xDBE5: 0x577C, //CJK UNIFIED IDEOGRAPH - 0xDBE6: 0x577B, //CJK UNIFIED IDEOGRAPH - 0xDBE7: 0x5768, //CJK UNIFIED IDEOGRAPH - 0xDBE8: 0x576D, //CJK UNIFIED IDEOGRAPH - 0xDBE9: 0x5776, //CJK UNIFIED IDEOGRAPH - 0xDBEA: 0x5773, //CJK UNIFIED IDEOGRAPH - 0xDBEB: 0x57AD, //CJK UNIFIED IDEOGRAPH - 0xDBEC: 0x57A4, //CJK UNIFIED IDEOGRAPH - 0xDBED: 0x578C, //CJK UNIFIED IDEOGRAPH - 0xDBEE: 0x57B2, //CJK UNIFIED IDEOGRAPH - 0xDBEF: 0x57CF, //CJK UNIFIED IDEOGRAPH - 0xDBF0: 0x57A7, //CJK UNIFIED IDEOGRAPH - 0xDBF1: 0x57B4, //CJK UNIFIED IDEOGRAPH - 0xDBF2: 0x5793, //CJK UNIFIED IDEOGRAPH - 0xDBF3: 0x57A0, //CJK UNIFIED IDEOGRAPH - 0xDBF4: 0x57D5, //CJK UNIFIED IDEOGRAPH - 0xDBF5: 0x57D8, //CJK UNIFIED IDEOGRAPH - 0xDBF6: 0x57DA, //CJK UNIFIED IDEOGRAPH - 0xDBF7: 0x57D9, //CJK UNIFIED IDEOGRAPH - 0xDBF8: 0x57D2, //CJK UNIFIED IDEOGRAPH - 0xDBF9: 0x57B8, //CJK UNIFIED IDEOGRAPH - 0xDBFA: 0x57F4, //CJK UNIFIED IDEOGRAPH - 0xDBFB: 0x57EF, //CJK UNIFIED IDEOGRAPH - 0xDBFC: 0x57F8, //CJK UNIFIED IDEOGRAPH - 0xDBFD: 0x57E4, //CJK UNIFIED IDEOGRAPH - 0xDBFE: 0x57DD, //CJK UNIFIED IDEOGRAPH - 0xDC40: 0x8E73, //CJK UNIFIED IDEOGRAPH - 0xDC41: 0x8E75, //CJK UNIFIED IDEOGRAPH - 0xDC42: 0x8E77, //CJK UNIFIED IDEOGRAPH - 0xDC43: 0x8E78, //CJK UNIFIED IDEOGRAPH - 0xDC44: 0x8E79, //CJK UNIFIED IDEOGRAPH - 0xDC45: 0x8E7A, //CJK UNIFIED IDEOGRAPH - 0xDC46: 0x8E7B, //CJK UNIFIED IDEOGRAPH - 0xDC47: 0x8E7D, //CJK UNIFIED IDEOGRAPH - 0xDC48: 0x8E7E, //CJK UNIFIED IDEOGRAPH - 0xDC49: 0x8E80, //CJK UNIFIED IDEOGRAPH - 0xDC4A: 0x8E82, //CJK UNIFIED IDEOGRAPH - 0xDC4B: 0x8E83, //CJK UNIFIED IDEOGRAPH - 0xDC4C: 0x8E84, //CJK UNIFIED IDEOGRAPH - 0xDC4D: 0x8E86, //CJK UNIFIED IDEOGRAPH - 0xDC4E: 0x8E88, //CJK UNIFIED IDEOGRAPH - 0xDC4F: 0x8E89, //CJK UNIFIED IDEOGRAPH - 0xDC50: 0x8E8A, //CJK UNIFIED IDEOGRAPH - 0xDC51: 0x8E8B, //CJK UNIFIED IDEOGRAPH - 0xDC52: 0x8E8C, //CJK UNIFIED IDEOGRAPH - 0xDC53: 0x8E8D, //CJK UNIFIED IDEOGRAPH - 0xDC54: 0x8E8E, //CJK UNIFIED IDEOGRAPH - 0xDC55: 0x8E91, //CJK UNIFIED IDEOGRAPH - 0xDC56: 0x8E92, //CJK UNIFIED IDEOGRAPH - 0xDC57: 0x8E93, //CJK UNIFIED IDEOGRAPH - 0xDC58: 0x8E95, //CJK UNIFIED IDEOGRAPH - 0xDC59: 0x8E96, //CJK UNIFIED IDEOGRAPH - 0xDC5A: 0x8E97, //CJK UNIFIED IDEOGRAPH - 0xDC5B: 0x8E98, //CJK UNIFIED IDEOGRAPH - 0xDC5C: 0x8E99, //CJK UNIFIED IDEOGRAPH - 0xDC5D: 0x8E9A, //CJK UNIFIED IDEOGRAPH - 0xDC5E: 0x8E9B, //CJK UNIFIED IDEOGRAPH - 0xDC5F: 0x8E9D, //CJK UNIFIED IDEOGRAPH - 0xDC60: 0x8E9F, //CJK UNIFIED IDEOGRAPH - 0xDC61: 0x8EA0, //CJK UNIFIED IDEOGRAPH - 0xDC62: 0x8EA1, //CJK UNIFIED IDEOGRAPH - 0xDC63: 0x8EA2, //CJK UNIFIED IDEOGRAPH - 0xDC64: 0x8EA3, //CJK UNIFIED IDEOGRAPH - 0xDC65: 0x8EA4, //CJK UNIFIED IDEOGRAPH - 0xDC66: 0x8EA5, //CJK UNIFIED IDEOGRAPH - 0xDC67: 0x8EA6, //CJK UNIFIED IDEOGRAPH - 0xDC68: 0x8EA7, //CJK UNIFIED IDEOGRAPH - 0xDC69: 0x8EA8, //CJK UNIFIED IDEOGRAPH - 0xDC6A: 0x8EA9, //CJK UNIFIED IDEOGRAPH - 0xDC6B: 0x8EAA, //CJK UNIFIED IDEOGRAPH - 0xDC6C: 0x8EAD, //CJK UNIFIED IDEOGRAPH - 0xDC6D: 0x8EAE, //CJK UNIFIED IDEOGRAPH - 0xDC6E: 0x8EB0, //CJK UNIFIED IDEOGRAPH - 0xDC6F: 0x8EB1, //CJK UNIFIED IDEOGRAPH - 0xDC70: 0x8EB3, //CJK UNIFIED IDEOGRAPH - 0xDC71: 0x8EB4, //CJK UNIFIED IDEOGRAPH - 0xDC72: 0x8EB5, //CJK UNIFIED IDEOGRAPH - 0xDC73: 0x8EB6, //CJK UNIFIED IDEOGRAPH - 0xDC74: 0x8EB7, //CJK UNIFIED IDEOGRAPH - 0xDC75: 0x8EB8, //CJK UNIFIED IDEOGRAPH - 0xDC76: 0x8EB9, //CJK UNIFIED IDEOGRAPH - 0xDC77: 0x8EBB, //CJK UNIFIED IDEOGRAPH - 0xDC78: 0x8EBC, //CJK UNIFIED IDEOGRAPH - 0xDC79: 0x8EBD, //CJK UNIFIED IDEOGRAPH - 0xDC7A: 0x8EBE, //CJK UNIFIED IDEOGRAPH - 0xDC7B: 0x8EBF, //CJK UNIFIED IDEOGRAPH - 0xDC7C: 0x8EC0, //CJK UNIFIED IDEOGRAPH - 0xDC7D: 0x8EC1, //CJK UNIFIED IDEOGRAPH - 0xDC7E: 0x8EC2, //CJK UNIFIED IDEOGRAPH - 0xDC80: 0x8EC3, //CJK UNIFIED IDEOGRAPH - 0xDC81: 0x8EC4, //CJK UNIFIED IDEOGRAPH - 0xDC82: 0x8EC5, //CJK UNIFIED IDEOGRAPH - 0xDC83: 0x8EC6, //CJK UNIFIED IDEOGRAPH - 0xDC84: 0x8EC7, //CJK UNIFIED IDEOGRAPH - 0xDC85: 0x8EC8, //CJK UNIFIED IDEOGRAPH - 0xDC86: 0x8EC9, //CJK UNIFIED IDEOGRAPH - 0xDC87: 0x8ECA, //CJK UNIFIED IDEOGRAPH - 0xDC88: 0x8ECB, //CJK UNIFIED IDEOGRAPH - 0xDC89: 0x8ECC, //CJK UNIFIED IDEOGRAPH - 0xDC8A: 0x8ECD, //CJK UNIFIED IDEOGRAPH - 0xDC8B: 0x8ECF, //CJK UNIFIED IDEOGRAPH - 0xDC8C: 0x8ED0, //CJK UNIFIED IDEOGRAPH - 0xDC8D: 0x8ED1, //CJK UNIFIED IDEOGRAPH - 0xDC8E: 0x8ED2, //CJK UNIFIED IDEOGRAPH - 0xDC8F: 0x8ED3, //CJK UNIFIED IDEOGRAPH - 0xDC90: 0x8ED4, //CJK UNIFIED IDEOGRAPH - 0xDC91: 0x8ED5, //CJK UNIFIED IDEOGRAPH - 0xDC92: 0x8ED6, //CJK UNIFIED IDEOGRAPH - 0xDC93: 0x8ED7, //CJK UNIFIED IDEOGRAPH - 0xDC94: 0x8ED8, //CJK UNIFIED IDEOGRAPH - 0xDC95: 0x8ED9, //CJK UNIFIED IDEOGRAPH - 0xDC96: 0x8EDA, //CJK UNIFIED IDEOGRAPH - 0xDC97: 0x8EDB, //CJK UNIFIED IDEOGRAPH - 0xDC98: 0x8EDC, //CJK UNIFIED IDEOGRAPH - 0xDC99: 0x8EDD, //CJK UNIFIED IDEOGRAPH - 0xDC9A: 0x8EDE, //CJK UNIFIED IDEOGRAPH - 0xDC9B: 0x8EDF, //CJK UNIFIED IDEOGRAPH - 0xDC9C: 0x8EE0, //CJK UNIFIED IDEOGRAPH - 0xDC9D: 0x8EE1, //CJK UNIFIED IDEOGRAPH - 0xDC9E: 0x8EE2, //CJK UNIFIED IDEOGRAPH - 0xDC9F: 0x8EE3, //CJK UNIFIED IDEOGRAPH - 0xDCA0: 0x8EE4, //CJK UNIFIED IDEOGRAPH - 0xDCA1: 0x580B, //CJK UNIFIED IDEOGRAPH - 0xDCA2: 0x580D, //CJK UNIFIED IDEOGRAPH - 0xDCA3: 0x57FD, //CJK UNIFIED IDEOGRAPH - 0xDCA4: 0x57ED, //CJK UNIFIED IDEOGRAPH - 0xDCA5: 0x5800, //CJK UNIFIED IDEOGRAPH - 0xDCA6: 0x581E, //CJK UNIFIED IDEOGRAPH - 0xDCA7: 0x5819, //CJK UNIFIED IDEOGRAPH - 0xDCA8: 0x5844, //CJK UNIFIED IDEOGRAPH - 0xDCA9: 0x5820, //CJK UNIFIED IDEOGRAPH - 0xDCAA: 0x5865, //CJK UNIFIED IDEOGRAPH - 0xDCAB: 0x586C, //CJK UNIFIED IDEOGRAPH - 0xDCAC: 0x5881, //CJK UNIFIED IDEOGRAPH - 0xDCAD: 0x5889, //CJK UNIFIED IDEOGRAPH - 0xDCAE: 0x589A, //CJK UNIFIED IDEOGRAPH - 0xDCAF: 0x5880, //CJK UNIFIED IDEOGRAPH - 0xDCB0: 0x99A8, //CJK UNIFIED IDEOGRAPH - 0xDCB1: 0x9F19, //CJK UNIFIED IDEOGRAPH - 0xDCB2: 0x61FF, //CJK UNIFIED IDEOGRAPH - 0xDCB3: 0x8279, //CJK UNIFIED IDEOGRAPH - 0xDCB4: 0x827D, //CJK UNIFIED IDEOGRAPH - 0xDCB5: 0x827F, //CJK UNIFIED IDEOGRAPH - 0xDCB6: 0x828F, //CJK UNIFIED IDEOGRAPH - 0xDCB7: 0x828A, //CJK UNIFIED IDEOGRAPH - 0xDCB8: 0x82A8, //CJK UNIFIED IDEOGRAPH - 0xDCB9: 0x8284, //CJK UNIFIED IDEOGRAPH - 0xDCBA: 0x828E, //CJK UNIFIED IDEOGRAPH - 0xDCBB: 0x8291, //CJK UNIFIED IDEOGRAPH - 0xDCBC: 0x8297, //CJK UNIFIED IDEOGRAPH - 0xDCBD: 0x8299, //CJK UNIFIED IDEOGRAPH - 0xDCBE: 0x82AB, //CJK UNIFIED IDEOGRAPH - 0xDCBF: 0x82B8, //CJK UNIFIED IDEOGRAPH - 0xDCC0: 0x82BE, //CJK UNIFIED IDEOGRAPH - 0xDCC1: 0x82B0, //CJK UNIFIED IDEOGRAPH - 0xDCC2: 0x82C8, //CJK UNIFIED IDEOGRAPH - 0xDCC3: 0x82CA, //CJK UNIFIED IDEOGRAPH - 0xDCC4: 0x82E3, //CJK UNIFIED IDEOGRAPH - 0xDCC5: 0x8298, //CJK UNIFIED IDEOGRAPH - 0xDCC6: 0x82B7, //CJK UNIFIED IDEOGRAPH - 0xDCC7: 0x82AE, //CJK UNIFIED IDEOGRAPH - 0xDCC8: 0x82CB, //CJK UNIFIED IDEOGRAPH - 0xDCC9: 0x82CC, //CJK UNIFIED IDEOGRAPH - 0xDCCA: 0x82C1, //CJK UNIFIED IDEOGRAPH - 0xDCCB: 0x82A9, //CJK UNIFIED IDEOGRAPH - 0xDCCC: 0x82B4, //CJK UNIFIED IDEOGRAPH - 0xDCCD: 0x82A1, //CJK UNIFIED IDEOGRAPH - 0xDCCE: 0x82AA, //CJK UNIFIED IDEOGRAPH - 0xDCCF: 0x829F, //CJK UNIFIED IDEOGRAPH - 0xDCD0: 0x82C4, //CJK UNIFIED IDEOGRAPH - 0xDCD1: 0x82CE, //CJK UNIFIED IDEOGRAPH - 0xDCD2: 0x82A4, //CJK UNIFIED IDEOGRAPH - 0xDCD3: 0x82E1, //CJK UNIFIED IDEOGRAPH - 0xDCD4: 0x8309, //CJK UNIFIED IDEOGRAPH - 0xDCD5: 0x82F7, //CJK UNIFIED IDEOGRAPH - 0xDCD6: 0x82E4, //CJK UNIFIED IDEOGRAPH - 0xDCD7: 0x830F, //CJK UNIFIED IDEOGRAPH - 0xDCD8: 0x8307, //CJK UNIFIED IDEOGRAPH - 0xDCD9: 0x82DC, //CJK UNIFIED IDEOGRAPH - 0xDCDA: 0x82F4, //CJK UNIFIED IDEOGRAPH - 0xDCDB: 0x82D2, //CJK UNIFIED IDEOGRAPH - 0xDCDC: 0x82D8, //CJK UNIFIED IDEOGRAPH - 0xDCDD: 0x830C, //CJK UNIFIED IDEOGRAPH - 0xDCDE: 0x82FB, //CJK UNIFIED IDEOGRAPH - 0xDCDF: 0x82D3, //CJK UNIFIED IDEOGRAPH - 0xDCE0: 0x8311, //CJK UNIFIED IDEOGRAPH - 0xDCE1: 0x831A, //CJK UNIFIED IDEOGRAPH - 0xDCE2: 0x8306, //CJK UNIFIED IDEOGRAPH - 0xDCE3: 0x8314, //CJK UNIFIED IDEOGRAPH - 0xDCE4: 0x8315, //CJK UNIFIED IDEOGRAPH - 0xDCE5: 0x82E0, //CJK UNIFIED IDEOGRAPH - 0xDCE6: 0x82D5, //CJK UNIFIED IDEOGRAPH - 0xDCE7: 0x831C, //CJK UNIFIED IDEOGRAPH - 0xDCE8: 0x8351, //CJK UNIFIED IDEOGRAPH - 0xDCE9: 0x835B, //CJK UNIFIED IDEOGRAPH - 0xDCEA: 0x835C, //CJK UNIFIED IDEOGRAPH - 0xDCEB: 0x8308, //CJK UNIFIED IDEOGRAPH - 0xDCEC: 0x8392, //CJK UNIFIED IDEOGRAPH - 0xDCED: 0x833C, //CJK UNIFIED IDEOGRAPH - 0xDCEE: 0x8334, //CJK UNIFIED IDEOGRAPH - 0xDCEF: 0x8331, //CJK UNIFIED IDEOGRAPH - 0xDCF0: 0x839B, //CJK UNIFIED IDEOGRAPH - 0xDCF1: 0x835E, //CJK UNIFIED IDEOGRAPH - 0xDCF2: 0x832F, //CJK UNIFIED IDEOGRAPH - 0xDCF3: 0x834F, //CJK UNIFIED IDEOGRAPH - 0xDCF4: 0x8347, //CJK UNIFIED IDEOGRAPH - 0xDCF5: 0x8343, //CJK UNIFIED IDEOGRAPH - 0xDCF6: 0x835F, //CJK UNIFIED IDEOGRAPH - 0xDCF7: 0x8340, //CJK UNIFIED IDEOGRAPH - 0xDCF8: 0x8317, //CJK UNIFIED IDEOGRAPH - 0xDCF9: 0x8360, //CJK UNIFIED IDEOGRAPH - 0xDCFA: 0x832D, //CJK UNIFIED IDEOGRAPH - 0xDCFB: 0x833A, //CJK UNIFIED IDEOGRAPH - 0xDCFC: 0x8333, //CJK UNIFIED IDEOGRAPH - 0xDCFD: 0x8366, //CJK UNIFIED IDEOGRAPH - 0xDCFE: 0x8365, //CJK UNIFIED IDEOGRAPH - 0xDD40: 0x8EE5, //CJK UNIFIED IDEOGRAPH - 0xDD41: 0x8EE6, //CJK UNIFIED IDEOGRAPH - 0xDD42: 0x8EE7, //CJK UNIFIED IDEOGRAPH - 0xDD43: 0x8EE8, //CJK UNIFIED IDEOGRAPH - 0xDD44: 0x8EE9, //CJK UNIFIED IDEOGRAPH - 0xDD45: 0x8EEA, //CJK UNIFIED IDEOGRAPH - 0xDD46: 0x8EEB, //CJK UNIFIED IDEOGRAPH - 0xDD47: 0x8EEC, //CJK UNIFIED IDEOGRAPH - 0xDD48: 0x8EED, //CJK UNIFIED IDEOGRAPH - 0xDD49: 0x8EEE, //CJK UNIFIED IDEOGRAPH - 0xDD4A: 0x8EEF, //CJK UNIFIED IDEOGRAPH - 0xDD4B: 0x8EF0, //CJK UNIFIED IDEOGRAPH - 0xDD4C: 0x8EF1, //CJK UNIFIED IDEOGRAPH - 0xDD4D: 0x8EF2, //CJK UNIFIED IDEOGRAPH - 0xDD4E: 0x8EF3, //CJK UNIFIED IDEOGRAPH - 0xDD4F: 0x8EF4, //CJK UNIFIED IDEOGRAPH - 0xDD50: 0x8EF5, //CJK UNIFIED IDEOGRAPH - 0xDD51: 0x8EF6, //CJK UNIFIED IDEOGRAPH - 0xDD52: 0x8EF7, //CJK UNIFIED IDEOGRAPH - 0xDD53: 0x8EF8, //CJK UNIFIED IDEOGRAPH - 0xDD54: 0x8EF9, //CJK UNIFIED IDEOGRAPH - 0xDD55: 0x8EFA, //CJK UNIFIED IDEOGRAPH - 0xDD56: 0x8EFB, //CJK UNIFIED IDEOGRAPH - 0xDD57: 0x8EFC, //CJK UNIFIED IDEOGRAPH - 0xDD58: 0x8EFD, //CJK UNIFIED IDEOGRAPH - 0xDD59: 0x8EFE, //CJK UNIFIED IDEOGRAPH - 0xDD5A: 0x8EFF, //CJK UNIFIED IDEOGRAPH - 0xDD5B: 0x8F00, //CJK UNIFIED IDEOGRAPH - 0xDD5C: 0x8F01, //CJK UNIFIED IDEOGRAPH - 0xDD5D: 0x8F02, //CJK UNIFIED IDEOGRAPH - 0xDD5E: 0x8F03, //CJK UNIFIED IDEOGRAPH - 0xDD5F: 0x8F04, //CJK UNIFIED IDEOGRAPH - 0xDD60: 0x8F05, //CJK UNIFIED IDEOGRAPH - 0xDD61: 0x8F06, //CJK UNIFIED IDEOGRAPH - 0xDD62: 0x8F07, //CJK UNIFIED IDEOGRAPH - 0xDD63: 0x8F08, //CJK UNIFIED IDEOGRAPH - 0xDD64: 0x8F09, //CJK UNIFIED IDEOGRAPH - 0xDD65: 0x8F0A, //CJK UNIFIED IDEOGRAPH - 0xDD66: 0x8F0B, //CJK UNIFIED IDEOGRAPH - 0xDD67: 0x8F0C, //CJK UNIFIED IDEOGRAPH - 0xDD68: 0x8F0D, //CJK UNIFIED IDEOGRAPH - 0xDD69: 0x8F0E, //CJK UNIFIED IDEOGRAPH - 0xDD6A: 0x8F0F, //CJK UNIFIED IDEOGRAPH - 0xDD6B: 0x8F10, //CJK UNIFIED IDEOGRAPH - 0xDD6C: 0x8F11, //CJK UNIFIED IDEOGRAPH - 0xDD6D: 0x8F12, //CJK UNIFIED IDEOGRAPH - 0xDD6E: 0x8F13, //CJK UNIFIED IDEOGRAPH - 0xDD6F: 0x8F14, //CJK UNIFIED IDEOGRAPH - 0xDD70: 0x8F15, //CJK UNIFIED IDEOGRAPH - 0xDD71: 0x8F16, //CJK UNIFIED IDEOGRAPH - 0xDD72: 0x8F17, //CJK UNIFIED IDEOGRAPH - 0xDD73: 0x8F18, //CJK UNIFIED IDEOGRAPH - 0xDD74: 0x8F19, //CJK UNIFIED IDEOGRAPH - 0xDD75: 0x8F1A, //CJK UNIFIED IDEOGRAPH - 0xDD76: 0x8F1B, //CJK UNIFIED IDEOGRAPH - 0xDD77: 0x8F1C, //CJK UNIFIED IDEOGRAPH - 0xDD78: 0x8F1D, //CJK UNIFIED IDEOGRAPH - 0xDD79: 0x8F1E, //CJK UNIFIED IDEOGRAPH - 0xDD7A: 0x8F1F, //CJK UNIFIED IDEOGRAPH - 0xDD7B: 0x8F20, //CJK UNIFIED IDEOGRAPH - 0xDD7C: 0x8F21, //CJK UNIFIED IDEOGRAPH - 0xDD7D: 0x8F22, //CJK UNIFIED IDEOGRAPH - 0xDD7E: 0x8F23, //CJK UNIFIED IDEOGRAPH - 0xDD80: 0x8F24, //CJK UNIFIED IDEOGRAPH - 0xDD81: 0x8F25, //CJK UNIFIED IDEOGRAPH - 0xDD82: 0x8F26, //CJK UNIFIED IDEOGRAPH - 0xDD83: 0x8F27, //CJK UNIFIED IDEOGRAPH - 0xDD84: 0x8F28, //CJK UNIFIED IDEOGRAPH - 0xDD85: 0x8F29, //CJK UNIFIED IDEOGRAPH - 0xDD86: 0x8F2A, //CJK UNIFIED IDEOGRAPH - 0xDD87: 0x8F2B, //CJK UNIFIED IDEOGRAPH - 0xDD88: 0x8F2C, //CJK UNIFIED IDEOGRAPH - 0xDD89: 0x8F2D, //CJK UNIFIED IDEOGRAPH - 0xDD8A: 0x8F2E, //CJK UNIFIED IDEOGRAPH - 0xDD8B: 0x8F2F, //CJK UNIFIED IDEOGRAPH - 0xDD8C: 0x8F30, //CJK UNIFIED IDEOGRAPH - 0xDD8D: 0x8F31, //CJK UNIFIED IDEOGRAPH - 0xDD8E: 0x8F32, //CJK UNIFIED IDEOGRAPH - 0xDD8F: 0x8F33, //CJK UNIFIED IDEOGRAPH - 0xDD90: 0x8F34, //CJK UNIFIED IDEOGRAPH - 0xDD91: 0x8F35, //CJK UNIFIED IDEOGRAPH - 0xDD92: 0x8F36, //CJK UNIFIED IDEOGRAPH - 0xDD93: 0x8F37, //CJK UNIFIED IDEOGRAPH - 0xDD94: 0x8F38, //CJK UNIFIED IDEOGRAPH - 0xDD95: 0x8F39, //CJK UNIFIED IDEOGRAPH - 0xDD96: 0x8F3A, //CJK UNIFIED IDEOGRAPH - 0xDD97: 0x8F3B, //CJK UNIFIED IDEOGRAPH - 0xDD98: 0x8F3C, //CJK UNIFIED IDEOGRAPH - 0xDD99: 0x8F3D, //CJK UNIFIED IDEOGRAPH - 0xDD9A: 0x8F3E, //CJK UNIFIED IDEOGRAPH - 0xDD9B: 0x8F3F, //CJK UNIFIED IDEOGRAPH - 0xDD9C: 0x8F40, //CJK UNIFIED IDEOGRAPH - 0xDD9D: 0x8F41, //CJK UNIFIED IDEOGRAPH - 0xDD9E: 0x8F42, //CJK UNIFIED IDEOGRAPH - 0xDD9F: 0x8F43, //CJK UNIFIED IDEOGRAPH - 0xDDA0: 0x8F44, //CJK UNIFIED IDEOGRAPH - 0xDDA1: 0x8368, //CJK UNIFIED IDEOGRAPH - 0xDDA2: 0x831B, //CJK UNIFIED IDEOGRAPH - 0xDDA3: 0x8369, //CJK UNIFIED IDEOGRAPH - 0xDDA4: 0x836C, //CJK UNIFIED IDEOGRAPH - 0xDDA5: 0x836A, //CJK UNIFIED IDEOGRAPH - 0xDDA6: 0x836D, //CJK UNIFIED IDEOGRAPH - 0xDDA7: 0x836E, //CJK UNIFIED IDEOGRAPH - 0xDDA8: 0x83B0, //CJK UNIFIED IDEOGRAPH - 0xDDA9: 0x8378, //CJK UNIFIED IDEOGRAPH - 0xDDAA: 0x83B3, //CJK UNIFIED IDEOGRAPH - 0xDDAB: 0x83B4, //CJK UNIFIED IDEOGRAPH - 0xDDAC: 0x83A0, //CJK UNIFIED IDEOGRAPH - 0xDDAD: 0x83AA, //CJK UNIFIED IDEOGRAPH - 0xDDAE: 0x8393, //CJK UNIFIED IDEOGRAPH - 0xDDAF: 0x839C, //CJK UNIFIED IDEOGRAPH - 0xDDB0: 0x8385, //CJK UNIFIED IDEOGRAPH - 0xDDB1: 0x837C, //CJK UNIFIED IDEOGRAPH - 0xDDB2: 0x83B6, //CJK UNIFIED IDEOGRAPH - 0xDDB3: 0x83A9, //CJK UNIFIED IDEOGRAPH - 0xDDB4: 0x837D, //CJK UNIFIED IDEOGRAPH - 0xDDB5: 0x83B8, //CJK UNIFIED IDEOGRAPH - 0xDDB6: 0x837B, //CJK UNIFIED IDEOGRAPH - 0xDDB7: 0x8398, //CJK UNIFIED IDEOGRAPH - 0xDDB8: 0x839E, //CJK UNIFIED IDEOGRAPH - 0xDDB9: 0x83A8, //CJK UNIFIED IDEOGRAPH - 0xDDBA: 0x83BA, //CJK UNIFIED IDEOGRAPH - 0xDDBB: 0x83BC, //CJK UNIFIED IDEOGRAPH - 0xDDBC: 0x83C1, //CJK UNIFIED IDEOGRAPH - 0xDDBD: 0x8401, //CJK UNIFIED IDEOGRAPH - 0xDDBE: 0x83E5, //CJK UNIFIED IDEOGRAPH - 0xDDBF: 0x83D8, //CJK UNIFIED IDEOGRAPH - 0xDDC0: 0x5807, //CJK UNIFIED IDEOGRAPH - 0xDDC1: 0x8418, //CJK UNIFIED IDEOGRAPH - 0xDDC2: 0x840B, //CJK UNIFIED IDEOGRAPH - 0xDDC3: 0x83DD, //CJK UNIFIED IDEOGRAPH - 0xDDC4: 0x83FD, //CJK UNIFIED IDEOGRAPH - 0xDDC5: 0x83D6, //CJK UNIFIED IDEOGRAPH - 0xDDC6: 0x841C, //CJK UNIFIED IDEOGRAPH - 0xDDC7: 0x8438, //CJK UNIFIED IDEOGRAPH - 0xDDC8: 0x8411, //CJK UNIFIED IDEOGRAPH - 0xDDC9: 0x8406, //CJK UNIFIED IDEOGRAPH - 0xDDCA: 0x83D4, //CJK UNIFIED IDEOGRAPH - 0xDDCB: 0x83DF, //CJK UNIFIED IDEOGRAPH - 0xDDCC: 0x840F, //CJK UNIFIED IDEOGRAPH - 0xDDCD: 0x8403, //CJK UNIFIED IDEOGRAPH - 0xDDCE: 0x83F8, //CJK UNIFIED IDEOGRAPH - 0xDDCF: 0x83F9, //CJK UNIFIED IDEOGRAPH - 0xDDD0: 0x83EA, //CJK UNIFIED IDEOGRAPH - 0xDDD1: 0x83C5, //CJK UNIFIED IDEOGRAPH - 0xDDD2: 0x83C0, //CJK UNIFIED IDEOGRAPH - 0xDDD3: 0x8426, //CJK UNIFIED IDEOGRAPH - 0xDDD4: 0x83F0, //CJK UNIFIED IDEOGRAPH - 0xDDD5: 0x83E1, //CJK UNIFIED IDEOGRAPH - 0xDDD6: 0x845C, //CJK UNIFIED IDEOGRAPH - 0xDDD7: 0x8451, //CJK UNIFIED IDEOGRAPH - 0xDDD8: 0x845A, //CJK UNIFIED IDEOGRAPH - 0xDDD9: 0x8459, //CJK UNIFIED IDEOGRAPH - 0xDDDA: 0x8473, //CJK UNIFIED IDEOGRAPH - 0xDDDB: 0x8487, //CJK UNIFIED IDEOGRAPH - 0xDDDC: 0x8488, //CJK UNIFIED IDEOGRAPH - 0xDDDD: 0x847A, //CJK UNIFIED IDEOGRAPH - 0xDDDE: 0x8489, //CJK UNIFIED IDEOGRAPH - 0xDDDF: 0x8478, //CJK UNIFIED IDEOGRAPH - 0xDDE0: 0x843C, //CJK UNIFIED IDEOGRAPH - 0xDDE1: 0x8446, //CJK UNIFIED IDEOGRAPH - 0xDDE2: 0x8469, //CJK UNIFIED IDEOGRAPH - 0xDDE3: 0x8476, //CJK UNIFIED IDEOGRAPH - 0xDDE4: 0x848C, //CJK UNIFIED IDEOGRAPH - 0xDDE5: 0x848E, //CJK UNIFIED IDEOGRAPH - 0xDDE6: 0x8431, //CJK UNIFIED IDEOGRAPH - 0xDDE7: 0x846D, //CJK UNIFIED IDEOGRAPH - 0xDDE8: 0x84C1, //CJK UNIFIED IDEOGRAPH - 0xDDE9: 0x84CD, //CJK UNIFIED IDEOGRAPH - 0xDDEA: 0x84D0, //CJK UNIFIED IDEOGRAPH - 0xDDEB: 0x84E6, //CJK UNIFIED IDEOGRAPH - 0xDDEC: 0x84BD, //CJK UNIFIED IDEOGRAPH - 0xDDED: 0x84D3, //CJK UNIFIED IDEOGRAPH - 0xDDEE: 0x84CA, //CJK UNIFIED IDEOGRAPH - 0xDDEF: 0x84BF, //CJK UNIFIED IDEOGRAPH - 0xDDF0: 0x84BA, //CJK UNIFIED IDEOGRAPH - 0xDDF1: 0x84E0, //CJK UNIFIED IDEOGRAPH - 0xDDF2: 0x84A1, //CJK UNIFIED IDEOGRAPH - 0xDDF3: 0x84B9, //CJK UNIFIED IDEOGRAPH - 0xDDF4: 0x84B4, //CJK UNIFIED IDEOGRAPH - 0xDDF5: 0x8497, //CJK UNIFIED IDEOGRAPH - 0xDDF6: 0x84E5, //CJK UNIFIED IDEOGRAPH - 0xDDF7: 0x84E3, //CJK UNIFIED IDEOGRAPH - 0xDDF8: 0x850C, //CJK UNIFIED IDEOGRAPH - 0xDDF9: 0x750D, //CJK UNIFIED IDEOGRAPH - 0xDDFA: 0x8538, //CJK UNIFIED IDEOGRAPH - 0xDDFB: 0x84F0, //CJK UNIFIED IDEOGRAPH - 0xDDFC: 0x8539, //CJK UNIFIED IDEOGRAPH - 0xDDFD: 0x851F, //CJK UNIFIED IDEOGRAPH - 0xDDFE: 0x853A, //CJK UNIFIED IDEOGRAPH - 0xDE40: 0x8F45, //CJK UNIFIED IDEOGRAPH - 0xDE41: 0x8F46, //CJK UNIFIED IDEOGRAPH - 0xDE42: 0x8F47, //CJK UNIFIED IDEOGRAPH - 0xDE43: 0x8F48, //CJK UNIFIED IDEOGRAPH - 0xDE44: 0x8F49, //CJK UNIFIED IDEOGRAPH - 0xDE45: 0x8F4A, //CJK UNIFIED IDEOGRAPH - 0xDE46: 0x8F4B, //CJK UNIFIED IDEOGRAPH - 0xDE47: 0x8F4C, //CJK UNIFIED IDEOGRAPH - 0xDE48: 0x8F4D, //CJK UNIFIED IDEOGRAPH - 0xDE49: 0x8F4E, //CJK UNIFIED IDEOGRAPH - 0xDE4A: 0x8F4F, //CJK UNIFIED IDEOGRAPH - 0xDE4B: 0x8F50, //CJK UNIFIED IDEOGRAPH - 0xDE4C: 0x8F51, //CJK UNIFIED IDEOGRAPH - 0xDE4D: 0x8F52, //CJK UNIFIED IDEOGRAPH - 0xDE4E: 0x8F53, //CJK UNIFIED IDEOGRAPH - 0xDE4F: 0x8F54, //CJK UNIFIED IDEOGRAPH - 0xDE50: 0x8F55, //CJK UNIFIED IDEOGRAPH - 0xDE51: 0x8F56, //CJK UNIFIED IDEOGRAPH - 0xDE52: 0x8F57, //CJK UNIFIED IDEOGRAPH - 0xDE53: 0x8F58, //CJK UNIFIED IDEOGRAPH - 0xDE54: 0x8F59, //CJK UNIFIED IDEOGRAPH - 0xDE55: 0x8F5A, //CJK UNIFIED IDEOGRAPH - 0xDE56: 0x8F5B, //CJK UNIFIED IDEOGRAPH - 0xDE57: 0x8F5C, //CJK UNIFIED IDEOGRAPH - 0xDE58: 0x8F5D, //CJK UNIFIED IDEOGRAPH - 0xDE59: 0x8F5E, //CJK UNIFIED IDEOGRAPH - 0xDE5A: 0x8F5F, //CJK UNIFIED IDEOGRAPH - 0xDE5B: 0x8F60, //CJK UNIFIED IDEOGRAPH - 0xDE5C: 0x8F61, //CJK UNIFIED IDEOGRAPH - 0xDE5D: 0x8F62, //CJK UNIFIED IDEOGRAPH - 0xDE5E: 0x8F63, //CJK UNIFIED IDEOGRAPH - 0xDE5F: 0x8F64, //CJK UNIFIED IDEOGRAPH - 0xDE60: 0x8F65, //CJK UNIFIED IDEOGRAPH - 0xDE61: 0x8F6A, //CJK UNIFIED IDEOGRAPH - 0xDE62: 0x8F80, //CJK UNIFIED IDEOGRAPH - 0xDE63: 0x8F8C, //CJK UNIFIED IDEOGRAPH - 0xDE64: 0x8F92, //CJK UNIFIED IDEOGRAPH - 0xDE65: 0x8F9D, //CJK UNIFIED IDEOGRAPH - 0xDE66: 0x8FA0, //CJK UNIFIED IDEOGRAPH - 0xDE67: 0x8FA1, //CJK UNIFIED IDEOGRAPH - 0xDE68: 0x8FA2, //CJK UNIFIED IDEOGRAPH - 0xDE69: 0x8FA4, //CJK UNIFIED IDEOGRAPH - 0xDE6A: 0x8FA5, //CJK UNIFIED IDEOGRAPH - 0xDE6B: 0x8FA6, //CJK UNIFIED IDEOGRAPH - 0xDE6C: 0x8FA7, //CJK UNIFIED IDEOGRAPH - 0xDE6D: 0x8FAA, //CJK UNIFIED IDEOGRAPH - 0xDE6E: 0x8FAC, //CJK UNIFIED IDEOGRAPH - 0xDE6F: 0x8FAD, //CJK UNIFIED IDEOGRAPH - 0xDE70: 0x8FAE, //CJK UNIFIED IDEOGRAPH - 0xDE71: 0x8FAF, //CJK UNIFIED IDEOGRAPH - 0xDE72: 0x8FB2, //CJK UNIFIED IDEOGRAPH - 0xDE73: 0x8FB3, //CJK UNIFIED IDEOGRAPH - 0xDE74: 0x8FB4, //CJK UNIFIED IDEOGRAPH - 0xDE75: 0x8FB5, //CJK UNIFIED IDEOGRAPH - 0xDE76: 0x8FB7, //CJK UNIFIED IDEOGRAPH - 0xDE77: 0x8FB8, //CJK UNIFIED IDEOGRAPH - 0xDE78: 0x8FBA, //CJK UNIFIED IDEOGRAPH - 0xDE79: 0x8FBB, //CJK UNIFIED IDEOGRAPH - 0xDE7A: 0x8FBC, //CJK UNIFIED IDEOGRAPH - 0xDE7B: 0x8FBF, //CJK UNIFIED IDEOGRAPH - 0xDE7C: 0x8FC0, //CJK UNIFIED IDEOGRAPH - 0xDE7D: 0x8FC3, //CJK UNIFIED IDEOGRAPH - 0xDE7E: 0x8FC6, //CJK UNIFIED IDEOGRAPH - 0xDE80: 0x8FC9, //CJK UNIFIED IDEOGRAPH - 0xDE81: 0x8FCA, //CJK UNIFIED IDEOGRAPH - 0xDE82: 0x8FCB, //CJK UNIFIED IDEOGRAPH - 0xDE83: 0x8FCC, //CJK UNIFIED IDEOGRAPH - 0xDE84: 0x8FCD, //CJK UNIFIED IDEOGRAPH - 0xDE85: 0x8FCF, //CJK UNIFIED IDEOGRAPH - 0xDE86: 0x8FD2, //CJK UNIFIED IDEOGRAPH - 0xDE87: 0x8FD6, //CJK UNIFIED IDEOGRAPH - 0xDE88: 0x8FD7, //CJK UNIFIED IDEOGRAPH - 0xDE89: 0x8FDA, //CJK UNIFIED IDEOGRAPH - 0xDE8A: 0x8FE0, //CJK UNIFIED IDEOGRAPH - 0xDE8B: 0x8FE1, //CJK UNIFIED IDEOGRAPH - 0xDE8C: 0x8FE3, //CJK UNIFIED IDEOGRAPH - 0xDE8D: 0x8FE7, //CJK UNIFIED IDEOGRAPH - 0xDE8E: 0x8FEC, //CJK UNIFIED IDEOGRAPH - 0xDE8F: 0x8FEF, //CJK UNIFIED IDEOGRAPH - 0xDE90: 0x8FF1, //CJK UNIFIED IDEOGRAPH - 0xDE91: 0x8FF2, //CJK UNIFIED IDEOGRAPH - 0xDE92: 0x8FF4, //CJK UNIFIED IDEOGRAPH - 0xDE93: 0x8FF5, //CJK UNIFIED IDEOGRAPH - 0xDE94: 0x8FF6, //CJK UNIFIED IDEOGRAPH - 0xDE95: 0x8FFA, //CJK UNIFIED IDEOGRAPH - 0xDE96: 0x8FFB, //CJK UNIFIED IDEOGRAPH - 0xDE97: 0x8FFC, //CJK UNIFIED IDEOGRAPH - 0xDE98: 0x8FFE, //CJK UNIFIED IDEOGRAPH - 0xDE99: 0x8FFF, //CJK UNIFIED IDEOGRAPH - 0xDE9A: 0x9007, //CJK UNIFIED IDEOGRAPH - 0xDE9B: 0x9008, //CJK UNIFIED IDEOGRAPH - 0xDE9C: 0x900C, //CJK UNIFIED IDEOGRAPH - 0xDE9D: 0x900E, //CJK UNIFIED IDEOGRAPH - 0xDE9E: 0x9013, //CJK UNIFIED IDEOGRAPH - 0xDE9F: 0x9015, //CJK UNIFIED IDEOGRAPH - 0xDEA0: 0x9018, //CJK UNIFIED IDEOGRAPH - 0xDEA1: 0x8556, //CJK UNIFIED IDEOGRAPH - 0xDEA2: 0x853B, //CJK UNIFIED IDEOGRAPH - 0xDEA3: 0x84FF, //CJK UNIFIED IDEOGRAPH - 0xDEA4: 0x84FC, //CJK UNIFIED IDEOGRAPH - 0xDEA5: 0x8559, //CJK UNIFIED IDEOGRAPH - 0xDEA6: 0x8548, //CJK UNIFIED IDEOGRAPH - 0xDEA7: 0x8568, //CJK UNIFIED IDEOGRAPH - 0xDEA8: 0x8564, //CJK UNIFIED IDEOGRAPH - 0xDEA9: 0x855E, //CJK UNIFIED IDEOGRAPH - 0xDEAA: 0x857A, //CJK UNIFIED IDEOGRAPH - 0xDEAB: 0x77A2, //CJK UNIFIED IDEOGRAPH - 0xDEAC: 0x8543, //CJK UNIFIED IDEOGRAPH - 0xDEAD: 0x8572, //CJK UNIFIED IDEOGRAPH - 0xDEAE: 0x857B, //CJK UNIFIED IDEOGRAPH - 0xDEAF: 0x85A4, //CJK UNIFIED IDEOGRAPH - 0xDEB0: 0x85A8, //CJK UNIFIED IDEOGRAPH - 0xDEB1: 0x8587, //CJK UNIFIED IDEOGRAPH - 0xDEB2: 0x858F, //CJK UNIFIED IDEOGRAPH - 0xDEB3: 0x8579, //CJK UNIFIED IDEOGRAPH - 0xDEB4: 0x85AE, //CJK UNIFIED IDEOGRAPH - 0xDEB5: 0x859C, //CJK UNIFIED IDEOGRAPH - 0xDEB6: 0x8585, //CJK UNIFIED IDEOGRAPH - 0xDEB7: 0x85B9, //CJK UNIFIED IDEOGRAPH - 0xDEB8: 0x85B7, //CJK UNIFIED IDEOGRAPH - 0xDEB9: 0x85B0, //CJK UNIFIED IDEOGRAPH - 0xDEBA: 0x85D3, //CJK UNIFIED IDEOGRAPH - 0xDEBB: 0x85C1, //CJK UNIFIED IDEOGRAPH - 0xDEBC: 0x85DC, //CJK UNIFIED IDEOGRAPH - 0xDEBD: 0x85FF, //CJK UNIFIED IDEOGRAPH - 0xDEBE: 0x8627, //CJK UNIFIED IDEOGRAPH - 0xDEBF: 0x8605, //CJK UNIFIED IDEOGRAPH - 0xDEC0: 0x8629, //CJK UNIFIED IDEOGRAPH - 0xDEC1: 0x8616, //CJK UNIFIED IDEOGRAPH - 0xDEC2: 0x863C, //CJK UNIFIED IDEOGRAPH - 0xDEC3: 0x5EFE, //CJK UNIFIED IDEOGRAPH - 0xDEC4: 0x5F08, //CJK UNIFIED IDEOGRAPH - 0xDEC5: 0x593C, //CJK UNIFIED IDEOGRAPH - 0xDEC6: 0x5941, //CJK UNIFIED IDEOGRAPH - 0xDEC7: 0x8037, //CJK UNIFIED IDEOGRAPH - 0xDEC8: 0x5955, //CJK UNIFIED IDEOGRAPH - 0xDEC9: 0x595A, //CJK UNIFIED IDEOGRAPH - 0xDECA: 0x5958, //CJK UNIFIED IDEOGRAPH - 0xDECB: 0x530F, //CJK UNIFIED IDEOGRAPH - 0xDECC: 0x5C22, //CJK UNIFIED IDEOGRAPH - 0xDECD: 0x5C25, //CJK UNIFIED IDEOGRAPH - 0xDECE: 0x5C2C, //CJK UNIFIED IDEOGRAPH - 0xDECF: 0x5C34, //CJK UNIFIED IDEOGRAPH - 0xDED0: 0x624C, //CJK UNIFIED IDEOGRAPH - 0xDED1: 0x626A, //CJK UNIFIED IDEOGRAPH - 0xDED2: 0x629F, //CJK UNIFIED IDEOGRAPH - 0xDED3: 0x62BB, //CJK UNIFIED IDEOGRAPH - 0xDED4: 0x62CA, //CJK UNIFIED IDEOGRAPH - 0xDED5: 0x62DA, //CJK UNIFIED IDEOGRAPH - 0xDED6: 0x62D7, //CJK UNIFIED IDEOGRAPH - 0xDED7: 0x62EE, //CJK UNIFIED IDEOGRAPH - 0xDED8: 0x6322, //CJK UNIFIED IDEOGRAPH - 0xDED9: 0x62F6, //CJK UNIFIED IDEOGRAPH - 0xDEDA: 0x6339, //CJK UNIFIED IDEOGRAPH - 0xDEDB: 0x634B, //CJK UNIFIED IDEOGRAPH - 0xDEDC: 0x6343, //CJK UNIFIED IDEOGRAPH - 0xDEDD: 0x63AD, //CJK UNIFIED IDEOGRAPH - 0xDEDE: 0x63F6, //CJK UNIFIED IDEOGRAPH - 0xDEDF: 0x6371, //CJK UNIFIED IDEOGRAPH - 0xDEE0: 0x637A, //CJK UNIFIED IDEOGRAPH - 0xDEE1: 0x638E, //CJK UNIFIED IDEOGRAPH - 0xDEE2: 0x63B4, //CJK UNIFIED IDEOGRAPH - 0xDEE3: 0x636D, //CJK UNIFIED IDEOGRAPH - 0xDEE4: 0x63AC, //CJK UNIFIED IDEOGRAPH - 0xDEE5: 0x638A, //CJK UNIFIED IDEOGRAPH - 0xDEE6: 0x6369, //CJK UNIFIED IDEOGRAPH - 0xDEE7: 0x63AE, //CJK UNIFIED IDEOGRAPH - 0xDEE8: 0x63BC, //CJK UNIFIED IDEOGRAPH - 0xDEE9: 0x63F2, //CJK UNIFIED IDEOGRAPH - 0xDEEA: 0x63F8, //CJK UNIFIED IDEOGRAPH - 0xDEEB: 0x63E0, //CJK UNIFIED IDEOGRAPH - 0xDEEC: 0x63FF, //CJK UNIFIED IDEOGRAPH - 0xDEED: 0x63C4, //CJK UNIFIED IDEOGRAPH - 0xDEEE: 0x63DE, //CJK UNIFIED IDEOGRAPH - 0xDEEF: 0x63CE, //CJK UNIFIED IDEOGRAPH - 0xDEF0: 0x6452, //CJK UNIFIED IDEOGRAPH - 0xDEF1: 0x63C6, //CJK UNIFIED IDEOGRAPH - 0xDEF2: 0x63BE, //CJK UNIFIED IDEOGRAPH - 0xDEF3: 0x6445, //CJK UNIFIED IDEOGRAPH - 0xDEF4: 0x6441, //CJK UNIFIED IDEOGRAPH - 0xDEF5: 0x640B, //CJK UNIFIED IDEOGRAPH - 0xDEF6: 0x641B, //CJK UNIFIED IDEOGRAPH - 0xDEF7: 0x6420, //CJK UNIFIED IDEOGRAPH - 0xDEF8: 0x640C, //CJK UNIFIED IDEOGRAPH - 0xDEF9: 0x6426, //CJK UNIFIED IDEOGRAPH - 0xDEFA: 0x6421, //CJK UNIFIED IDEOGRAPH - 0xDEFB: 0x645E, //CJK UNIFIED IDEOGRAPH - 0xDEFC: 0x6484, //CJK UNIFIED IDEOGRAPH - 0xDEFD: 0x646D, //CJK UNIFIED IDEOGRAPH - 0xDEFE: 0x6496, //CJK UNIFIED IDEOGRAPH - 0xDF40: 0x9019, //CJK UNIFIED IDEOGRAPH - 0xDF41: 0x901C, //CJK UNIFIED IDEOGRAPH - 0xDF42: 0x9023, //CJK UNIFIED IDEOGRAPH - 0xDF43: 0x9024, //CJK UNIFIED IDEOGRAPH - 0xDF44: 0x9025, //CJK UNIFIED IDEOGRAPH - 0xDF45: 0x9027, //CJK UNIFIED IDEOGRAPH - 0xDF46: 0x9028, //CJK UNIFIED IDEOGRAPH - 0xDF47: 0x9029, //CJK UNIFIED IDEOGRAPH - 0xDF48: 0x902A, //CJK UNIFIED IDEOGRAPH - 0xDF49: 0x902B, //CJK UNIFIED IDEOGRAPH - 0xDF4A: 0x902C, //CJK UNIFIED IDEOGRAPH - 0xDF4B: 0x9030, //CJK UNIFIED IDEOGRAPH - 0xDF4C: 0x9031, //CJK UNIFIED IDEOGRAPH - 0xDF4D: 0x9032, //CJK UNIFIED IDEOGRAPH - 0xDF4E: 0x9033, //CJK UNIFIED IDEOGRAPH - 0xDF4F: 0x9034, //CJK UNIFIED IDEOGRAPH - 0xDF50: 0x9037, //CJK UNIFIED IDEOGRAPH - 0xDF51: 0x9039, //CJK UNIFIED IDEOGRAPH - 0xDF52: 0x903A, //CJK UNIFIED IDEOGRAPH - 0xDF53: 0x903D, //CJK UNIFIED IDEOGRAPH - 0xDF54: 0x903F, //CJK UNIFIED IDEOGRAPH - 0xDF55: 0x9040, //CJK UNIFIED IDEOGRAPH - 0xDF56: 0x9043, //CJK UNIFIED IDEOGRAPH - 0xDF57: 0x9045, //CJK UNIFIED IDEOGRAPH - 0xDF58: 0x9046, //CJK UNIFIED IDEOGRAPH - 0xDF59: 0x9048, //CJK UNIFIED IDEOGRAPH - 0xDF5A: 0x9049, //CJK UNIFIED IDEOGRAPH - 0xDF5B: 0x904A, //CJK UNIFIED IDEOGRAPH - 0xDF5C: 0x904B, //CJK UNIFIED IDEOGRAPH - 0xDF5D: 0x904C, //CJK UNIFIED IDEOGRAPH - 0xDF5E: 0x904E, //CJK UNIFIED IDEOGRAPH - 0xDF5F: 0x9054, //CJK UNIFIED IDEOGRAPH - 0xDF60: 0x9055, //CJK UNIFIED IDEOGRAPH - 0xDF61: 0x9056, //CJK UNIFIED IDEOGRAPH - 0xDF62: 0x9059, //CJK UNIFIED IDEOGRAPH - 0xDF63: 0x905A, //CJK UNIFIED IDEOGRAPH - 0xDF64: 0x905C, //CJK UNIFIED IDEOGRAPH - 0xDF65: 0x905D, //CJK UNIFIED IDEOGRAPH - 0xDF66: 0x905E, //CJK UNIFIED IDEOGRAPH - 0xDF67: 0x905F, //CJK UNIFIED IDEOGRAPH - 0xDF68: 0x9060, //CJK UNIFIED IDEOGRAPH - 0xDF69: 0x9061, //CJK UNIFIED IDEOGRAPH - 0xDF6A: 0x9064, //CJK UNIFIED IDEOGRAPH - 0xDF6B: 0x9066, //CJK UNIFIED IDEOGRAPH - 0xDF6C: 0x9067, //CJK UNIFIED IDEOGRAPH - 0xDF6D: 0x9069, //CJK UNIFIED IDEOGRAPH - 0xDF6E: 0x906A, //CJK UNIFIED IDEOGRAPH - 0xDF6F: 0x906B, //CJK UNIFIED IDEOGRAPH - 0xDF70: 0x906C, //CJK UNIFIED IDEOGRAPH - 0xDF71: 0x906F, //CJK UNIFIED IDEOGRAPH - 0xDF72: 0x9070, //CJK UNIFIED IDEOGRAPH - 0xDF73: 0x9071, //CJK UNIFIED IDEOGRAPH - 0xDF74: 0x9072, //CJK UNIFIED IDEOGRAPH - 0xDF75: 0x9073, //CJK UNIFIED IDEOGRAPH - 0xDF76: 0x9076, //CJK UNIFIED IDEOGRAPH - 0xDF77: 0x9077, //CJK UNIFIED IDEOGRAPH - 0xDF78: 0x9078, //CJK UNIFIED IDEOGRAPH - 0xDF79: 0x9079, //CJK UNIFIED IDEOGRAPH - 0xDF7A: 0x907A, //CJK UNIFIED IDEOGRAPH - 0xDF7B: 0x907B, //CJK UNIFIED IDEOGRAPH - 0xDF7C: 0x907C, //CJK UNIFIED IDEOGRAPH - 0xDF7D: 0x907E, //CJK UNIFIED IDEOGRAPH - 0xDF7E: 0x9081, //CJK UNIFIED IDEOGRAPH - 0xDF80: 0x9084, //CJK UNIFIED IDEOGRAPH - 0xDF81: 0x9085, //CJK UNIFIED IDEOGRAPH - 0xDF82: 0x9086, //CJK UNIFIED IDEOGRAPH - 0xDF83: 0x9087, //CJK UNIFIED IDEOGRAPH - 0xDF84: 0x9089, //CJK UNIFIED IDEOGRAPH - 0xDF85: 0x908A, //CJK UNIFIED IDEOGRAPH - 0xDF86: 0x908C, //CJK UNIFIED IDEOGRAPH - 0xDF87: 0x908D, //CJK UNIFIED IDEOGRAPH - 0xDF88: 0x908E, //CJK UNIFIED IDEOGRAPH - 0xDF89: 0x908F, //CJK UNIFIED IDEOGRAPH - 0xDF8A: 0x9090, //CJK UNIFIED IDEOGRAPH - 0xDF8B: 0x9092, //CJK UNIFIED IDEOGRAPH - 0xDF8C: 0x9094, //CJK UNIFIED IDEOGRAPH - 0xDF8D: 0x9096, //CJK UNIFIED IDEOGRAPH - 0xDF8E: 0x9098, //CJK UNIFIED IDEOGRAPH - 0xDF8F: 0x909A, //CJK UNIFIED IDEOGRAPH - 0xDF90: 0x909C, //CJK UNIFIED IDEOGRAPH - 0xDF91: 0x909E, //CJK UNIFIED IDEOGRAPH - 0xDF92: 0x909F, //CJK UNIFIED IDEOGRAPH - 0xDF93: 0x90A0, //CJK UNIFIED IDEOGRAPH - 0xDF94: 0x90A4, //CJK UNIFIED IDEOGRAPH - 0xDF95: 0x90A5, //CJK UNIFIED IDEOGRAPH - 0xDF96: 0x90A7, //CJK UNIFIED IDEOGRAPH - 0xDF97: 0x90A8, //CJK UNIFIED IDEOGRAPH - 0xDF98: 0x90A9, //CJK UNIFIED IDEOGRAPH - 0xDF99: 0x90AB, //CJK UNIFIED IDEOGRAPH - 0xDF9A: 0x90AD, //CJK UNIFIED IDEOGRAPH - 0xDF9B: 0x90B2, //CJK UNIFIED IDEOGRAPH - 0xDF9C: 0x90B7, //CJK UNIFIED IDEOGRAPH - 0xDF9D: 0x90BC, //CJK UNIFIED IDEOGRAPH - 0xDF9E: 0x90BD, //CJK UNIFIED IDEOGRAPH - 0xDF9F: 0x90BF, //CJK UNIFIED IDEOGRAPH - 0xDFA0: 0x90C0, //CJK UNIFIED IDEOGRAPH - 0xDFA1: 0x647A, //CJK UNIFIED IDEOGRAPH - 0xDFA2: 0x64B7, //CJK UNIFIED IDEOGRAPH - 0xDFA3: 0x64B8, //CJK UNIFIED IDEOGRAPH - 0xDFA4: 0x6499, //CJK UNIFIED IDEOGRAPH - 0xDFA5: 0x64BA, //CJK UNIFIED IDEOGRAPH - 0xDFA6: 0x64C0, //CJK UNIFIED IDEOGRAPH - 0xDFA7: 0x64D0, //CJK UNIFIED IDEOGRAPH - 0xDFA8: 0x64D7, //CJK UNIFIED IDEOGRAPH - 0xDFA9: 0x64E4, //CJK UNIFIED IDEOGRAPH - 0xDFAA: 0x64E2, //CJK UNIFIED IDEOGRAPH - 0xDFAB: 0x6509, //CJK UNIFIED IDEOGRAPH - 0xDFAC: 0x6525, //CJK UNIFIED IDEOGRAPH - 0xDFAD: 0x652E, //CJK UNIFIED IDEOGRAPH - 0xDFAE: 0x5F0B, //CJK UNIFIED IDEOGRAPH - 0xDFAF: 0x5FD2, //CJK UNIFIED IDEOGRAPH - 0xDFB0: 0x7519, //CJK UNIFIED IDEOGRAPH - 0xDFB1: 0x5F11, //CJK UNIFIED IDEOGRAPH - 0xDFB2: 0x535F, //CJK UNIFIED IDEOGRAPH - 0xDFB3: 0x53F1, //CJK UNIFIED IDEOGRAPH - 0xDFB4: 0x53FD, //CJK UNIFIED IDEOGRAPH - 0xDFB5: 0x53E9, //CJK UNIFIED IDEOGRAPH - 0xDFB6: 0x53E8, //CJK UNIFIED IDEOGRAPH - 0xDFB7: 0x53FB, //CJK UNIFIED IDEOGRAPH - 0xDFB8: 0x5412, //CJK UNIFIED IDEOGRAPH - 0xDFB9: 0x5416, //CJK UNIFIED IDEOGRAPH - 0xDFBA: 0x5406, //CJK UNIFIED IDEOGRAPH - 0xDFBB: 0x544B, //CJK UNIFIED IDEOGRAPH - 0xDFBC: 0x5452, //CJK UNIFIED IDEOGRAPH - 0xDFBD: 0x5453, //CJK UNIFIED IDEOGRAPH - 0xDFBE: 0x5454, //CJK UNIFIED IDEOGRAPH - 0xDFBF: 0x5456, //CJK UNIFIED IDEOGRAPH - 0xDFC0: 0x5443, //CJK UNIFIED IDEOGRAPH - 0xDFC1: 0x5421, //CJK UNIFIED IDEOGRAPH - 0xDFC2: 0x5457, //CJK UNIFIED IDEOGRAPH - 0xDFC3: 0x5459, //CJK UNIFIED IDEOGRAPH - 0xDFC4: 0x5423, //CJK UNIFIED IDEOGRAPH - 0xDFC5: 0x5432, //CJK UNIFIED IDEOGRAPH - 0xDFC6: 0x5482, //CJK UNIFIED IDEOGRAPH - 0xDFC7: 0x5494, //CJK UNIFIED IDEOGRAPH - 0xDFC8: 0x5477, //CJK UNIFIED IDEOGRAPH - 0xDFC9: 0x5471, //CJK UNIFIED IDEOGRAPH - 0xDFCA: 0x5464, //CJK UNIFIED IDEOGRAPH - 0xDFCB: 0x549A, //CJK UNIFIED IDEOGRAPH - 0xDFCC: 0x549B, //CJK UNIFIED IDEOGRAPH - 0xDFCD: 0x5484, //CJK UNIFIED IDEOGRAPH - 0xDFCE: 0x5476, //CJK UNIFIED IDEOGRAPH - 0xDFCF: 0x5466, //CJK UNIFIED IDEOGRAPH - 0xDFD0: 0x549D, //CJK UNIFIED IDEOGRAPH - 0xDFD1: 0x54D0, //CJK UNIFIED IDEOGRAPH - 0xDFD2: 0x54AD, //CJK UNIFIED IDEOGRAPH - 0xDFD3: 0x54C2, //CJK UNIFIED IDEOGRAPH - 0xDFD4: 0x54B4, //CJK UNIFIED IDEOGRAPH - 0xDFD5: 0x54D2, //CJK UNIFIED IDEOGRAPH - 0xDFD6: 0x54A7, //CJK UNIFIED IDEOGRAPH - 0xDFD7: 0x54A6, //CJK UNIFIED IDEOGRAPH - 0xDFD8: 0x54D3, //CJK UNIFIED IDEOGRAPH - 0xDFD9: 0x54D4, //CJK UNIFIED IDEOGRAPH - 0xDFDA: 0x5472, //CJK UNIFIED IDEOGRAPH - 0xDFDB: 0x54A3, //CJK UNIFIED IDEOGRAPH - 0xDFDC: 0x54D5, //CJK UNIFIED IDEOGRAPH - 0xDFDD: 0x54BB, //CJK UNIFIED IDEOGRAPH - 0xDFDE: 0x54BF, //CJK UNIFIED IDEOGRAPH - 0xDFDF: 0x54CC, //CJK UNIFIED IDEOGRAPH - 0xDFE0: 0x54D9, //CJK UNIFIED IDEOGRAPH - 0xDFE1: 0x54DA, //CJK UNIFIED IDEOGRAPH - 0xDFE2: 0x54DC, //CJK UNIFIED IDEOGRAPH - 0xDFE3: 0x54A9, //CJK UNIFIED IDEOGRAPH - 0xDFE4: 0x54AA, //CJK UNIFIED IDEOGRAPH - 0xDFE5: 0x54A4, //CJK UNIFIED IDEOGRAPH - 0xDFE6: 0x54DD, //CJK UNIFIED IDEOGRAPH - 0xDFE7: 0x54CF, //CJK UNIFIED IDEOGRAPH - 0xDFE8: 0x54DE, //CJK UNIFIED IDEOGRAPH - 0xDFE9: 0x551B, //CJK UNIFIED IDEOGRAPH - 0xDFEA: 0x54E7, //CJK UNIFIED IDEOGRAPH - 0xDFEB: 0x5520, //CJK UNIFIED IDEOGRAPH - 0xDFEC: 0x54FD, //CJK UNIFIED IDEOGRAPH - 0xDFED: 0x5514, //CJK UNIFIED IDEOGRAPH - 0xDFEE: 0x54F3, //CJK UNIFIED IDEOGRAPH - 0xDFEF: 0x5522, //CJK UNIFIED IDEOGRAPH - 0xDFF0: 0x5523, //CJK UNIFIED IDEOGRAPH - 0xDFF1: 0x550F, //CJK UNIFIED IDEOGRAPH - 0xDFF2: 0x5511, //CJK UNIFIED IDEOGRAPH - 0xDFF3: 0x5527, //CJK UNIFIED IDEOGRAPH - 0xDFF4: 0x552A, //CJK UNIFIED IDEOGRAPH - 0xDFF5: 0x5567, //CJK UNIFIED IDEOGRAPH - 0xDFF6: 0x558F, //CJK UNIFIED IDEOGRAPH - 0xDFF7: 0x55B5, //CJK UNIFIED IDEOGRAPH - 0xDFF8: 0x5549, //CJK UNIFIED IDEOGRAPH - 0xDFF9: 0x556D, //CJK UNIFIED IDEOGRAPH - 0xDFFA: 0x5541, //CJK UNIFIED IDEOGRAPH - 0xDFFB: 0x5555, //CJK UNIFIED IDEOGRAPH - 0xDFFC: 0x553F, //CJK UNIFIED IDEOGRAPH - 0xDFFD: 0x5550, //CJK UNIFIED IDEOGRAPH - 0xDFFE: 0x553C, //CJK UNIFIED IDEOGRAPH - 0xE040: 0x90C2, //CJK UNIFIED IDEOGRAPH - 0xE041: 0x90C3, //CJK UNIFIED IDEOGRAPH - 0xE042: 0x90C6, //CJK UNIFIED IDEOGRAPH - 0xE043: 0x90C8, //CJK UNIFIED IDEOGRAPH - 0xE044: 0x90C9, //CJK UNIFIED IDEOGRAPH - 0xE045: 0x90CB, //CJK UNIFIED IDEOGRAPH - 0xE046: 0x90CC, //CJK UNIFIED IDEOGRAPH - 0xE047: 0x90CD, //CJK UNIFIED IDEOGRAPH - 0xE048: 0x90D2, //CJK UNIFIED IDEOGRAPH - 0xE049: 0x90D4, //CJK UNIFIED IDEOGRAPH - 0xE04A: 0x90D5, //CJK UNIFIED IDEOGRAPH - 0xE04B: 0x90D6, //CJK UNIFIED IDEOGRAPH - 0xE04C: 0x90D8, //CJK UNIFIED IDEOGRAPH - 0xE04D: 0x90D9, //CJK UNIFIED IDEOGRAPH - 0xE04E: 0x90DA, //CJK UNIFIED IDEOGRAPH - 0xE04F: 0x90DE, //CJK UNIFIED IDEOGRAPH - 0xE050: 0x90DF, //CJK UNIFIED IDEOGRAPH - 0xE051: 0x90E0, //CJK UNIFIED IDEOGRAPH - 0xE052: 0x90E3, //CJK UNIFIED IDEOGRAPH - 0xE053: 0x90E4, //CJK UNIFIED IDEOGRAPH - 0xE054: 0x90E5, //CJK UNIFIED IDEOGRAPH - 0xE055: 0x90E9, //CJK UNIFIED IDEOGRAPH - 0xE056: 0x90EA, //CJK UNIFIED IDEOGRAPH - 0xE057: 0x90EC, //CJK UNIFIED IDEOGRAPH - 0xE058: 0x90EE, //CJK UNIFIED IDEOGRAPH - 0xE059: 0x90F0, //CJK UNIFIED IDEOGRAPH - 0xE05A: 0x90F1, //CJK UNIFIED IDEOGRAPH - 0xE05B: 0x90F2, //CJK UNIFIED IDEOGRAPH - 0xE05C: 0x90F3, //CJK UNIFIED IDEOGRAPH - 0xE05D: 0x90F5, //CJK UNIFIED IDEOGRAPH - 0xE05E: 0x90F6, //CJK UNIFIED IDEOGRAPH - 0xE05F: 0x90F7, //CJK UNIFIED IDEOGRAPH - 0xE060: 0x90F9, //CJK UNIFIED IDEOGRAPH - 0xE061: 0x90FA, //CJK UNIFIED IDEOGRAPH - 0xE062: 0x90FB, //CJK UNIFIED IDEOGRAPH - 0xE063: 0x90FC, //CJK UNIFIED IDEOGRAPH - 0xE064: 0x90FF, //CJK UNIFIED IDEOGRAPH - 0xE065: 0x9100, //CJK UNIFIED IDEOGRAPH - 0xE066: 0x9101, //CJK UNIFIED IDEOGRAPH - 0xE067: 0x9103, //CJK UNIFIED IDEOGRAPH - 0xE068: 0x9105, //CJK UNIFIED IDEOGRAPH - 0xE069: 0x9106, //CJK UNIFIED IDEOGRAPH - 0xE06A: 0x9107, //CJK UNIFIED IDEOGRAPH - 0xE06B: 0x9108, //CJK UNIFIED IDEOGRAPH - 0xE06C: 0x9109, //CJK UNIFIED IDEOGRAPH - 0xE06D: 0x910A, //CJK UNIFIED IDEOGRAPH - 0xE06E: 0x910B, //CJK UNIFIED IDEOGRAPH - 0xE06F: 0x910C, //CJK UNIFIED IDEOGRAPH - 0xE070: 0x910D, //CJK UNIFIED IDEOGRAPH - 0xE071: 0x910E, //CJK UNIFIED IDEOGRAPH - 0xE072: 0x910F, //CJK UNIFIED IDEOGRAPH - 0xE073: 0x9110, //CJK UNIFIED IDEOGRAPH - 0xE074: 0x9111, //CJK UNIFIED IDEOGRAPH - 0xE075: 0x9112, //CJK UNIFIED IDEOGRAPH - 0xE076: 0x9113, //CJK UNIFIED IDEOGRAPH - 0xE077: 0x9114, //CJK UNIFIED IDEOGRAPH - 0xE078: 0x9115, //CJK UNIFIED IDEOGRAPH - 0xE079: 0x9116, //CJK UNIFIED IDEOGRAPH - 0xE07A: 0x9117, //CJK UNIFIED IDEOGRAPH - 0xE07B: 0x9118, //CJK UNIFIED IDEOGRAPH - 0xE07C: 0x911A, //CJK UNIFIED IDEOGRAPH - 0xE07D: 0x911B, //CJK UNIFIED IDEOGRAPH - 0xE07E: 0x911C, //CJK UNIFIED IDEOGRAPH - 0xE080: 0x911D, //CJK UNIFIED IDEOGRAPH - 0xE081: 0x911F, //CJK UNIFIED IDEOGRAPH - 0xE082: 0x9120, //CJK UNIFIED IDEOGRAPH - 0xE083: 0x9121, //CJK UNIFIED IDEOGRAPH - 0xE084: 0x9124, //CJK UNIFIED IDEOGRAPH - 0xE085: 0x9125, //CJK UNIFIED IDEOGRAPH - 0xE086: 0x9126, //CJK UNIFIED IDEOGRAPH - 0xE087: 0x9127, //CJK UNIFIED IDEOGRAPH - 0xE088: 0x9128, //CJK UNIFIED IDEOGRAPH - 0xE089: 0x9129, //CJK UNIFIED IDEOGRAPH - 0xE08A: 0x912A, //CJK UNIFIED IDEOGRAPH - 0xE08B: 0x912B, //CJK UNIFIED IDEOGRAPH - 0xE08C: 0x912C, //CJK UNIFIED IDEOGRAPH - 0xE08D: 0x912D, //CJK UNIFIED IDEOGRAPH - 0xE08E: 0x912E, //CJK UNIFIED IDEOGRAPH - 0xE08F: 0x9130, //CJK UNIFIED IDEOGRAPH - 0xE090: 0x9132, //CJK UNIFIED IDEOGRAPH - 0xE091: 0x9133, //CJK UNIFIED IDEOGRAPH - 0xE092: 0x9134, //CJK UNIFIED IDEOGRAPH - 0xE093: 0x9135, //CJK UNIFIED IDEOGRAPH - 0xE094: 0x9136, //CJK UNIFIED IDEOGRAPH - 0xE095: 0x9137, //CJK UNIFIED IDEOGRAPH - 0xE096: 0x9138, //CJK UNIFIED IDEOGRAPH - 0xE097: 0x913A, //CJK UNIFIED IDEOGRAPH - 0xE098: 0x913B, //CJK UNIFIED IDEOGRAPH - 0xE099: 0x913C, //CJK UNIFIED IDEOGRAPH - 0xE09A: 0x913D, //CJK UNIFIED IDEOGRAPH - 0xE09B: 0x913E, //CJK UNIFIED IDEOGRAPH - 0xE09C: 0x913F, //CJK UNIFIED IDEOGRAPH - 0xE09D: 0x9140, //CJK UNIFIED IDEOGRAPH - 0xE09E: 0x9141, //CJK UNIFIED IDEOGRAPH - 0xE09F: 0x9142, //CJK UNIFIED IDEOGRAPH - 0xE0A0: 0x9144, //CJK UNIFIED IDEOGRAPH - 0xE0A1: 0x5537, //CJK UNIFIED IDEOGRAPH - 0xE0A2: 0x5556, //CJK UNIFIED IDEOGRAPH - 0xE0A3: 0x5575, //CJK UNIFIED IDEOGRAPH - 0xE0A4: 0x5576, //CJK UNIFIED IDEOGRAPH - 0xE0A5: 0x5577, //CJK UNIFIED IDEOGRAPH - 0xE0A6: 0x5533, //CJK UNIFIED IDEOGRAPH - 0xE0A7: 0x5530, //CJK UNIFIED IDEOGRAPH - 0xE0A8: 0x555C, //CJK UNIFIED IDEOGRAPH - 0xE0A9: 0x558B, //CJK UNIFIED IDEOGRAPH - 0xE0AA: 0x55D2, //CJK UNIFIED IDEOGRAPH - 0xE0AB: 0x5583, //CJK UNIFIED IDEOGRAPH - 0xE0AC: 0x55B1, //CJK UNIFIED IDEOGRAPH - 0xE0AD: 0x55B9, //CJK UNIFIED IDEOGRAPH - 0xE0AE: 0x5588, //CJK UNIFIED IDEOGRAPH - 0xE0AF: 0x5581, //CJK UNIFIED IDEOGRAPH - 0xE0B0: 0x559F, //CJK UNIFIED IDEOGRAPH - 0xE0B1: 0x557E, //CJK UNIFIED IDEOGRAPH - 0xE0B2: 0x55D6, //CJK UNIFIED IDEOGRAPH - 0xE0B3: 0x5591, //CJK UNIFIED IDEOGRAPH - 0xE0B4: 0x557B, //CJK UNIFIED IDEOGRAPH - 0xE0B5: 0x55DF, //CJK UNIFIED IDEOGRAPH - 0xE0B6: 0x55BD, //CJK UNIFIED IDEOGRAPH - 0xE0B7: 0x55BE, //CJK UNIFIED IDEOGRAPH - 0xE0B8: 0x5594, //CJK UNIFIED IDEOGRAPH - 0xE0B9: 0x5599, //CJK UNIFIED IDEOGRAPH - 0xE0BA: 0x55EA, //CJK UNIFIED IDEOGRAPH - 0xE0BB: 0x55F7, //CJK UNIFIED IDEOGRAPH - 0xE0BC: 0x55C9, //CJK UNIFIED IDEOGRAPH - 0xE0BD: 0x561F, //CJK UNIFIED IDEOGRAPH - 0xE0BE: 0x55D1, //CJK UNIFIED IDEOGRAPH - 0xE0BF: 0x55EB, //CJK UNIFIED IDEOGRAPH - 0xE0C0: 0x55EC, //CJK UNIFIED IDEOGRAPH - 0xE0C1: 0x55D4, //CJK UNIFIED IDEOGRAPH - 0xE0C2: 0x55E6, //CJK UNIFIED IDEOGRAPH - 0xE0C3: 0x55DD, //CJK UNIFIED IDEOGRAPH - 0xE0C4: 0x55C4, //CJK UNIFIED IDEOGRAPH - 0xE0C5: 0x55EF, //CJK UNIFIED IDEOGRAPH - 0xE0C6: 0x55E5, //CJK UNIFIED IDEOGRAPH - 0xE0C7: 0x55F2, //CJK UNIFIED IDEOGRAPH - 0xE0C8: 0x55F3, //CJK UNIFIED IDEOGRAPH - 0xE0C9: 0x55CC, //CJK UNIFIED IDEOGRAPH - 0xE0CA: 0x55CD, //CJK UNIFIED IDEOGRAPH - 0xE0CB: 0x55E8, //CJK UNIFIED IDEOGRAPH - 0xE0CC: 0x55F5, //CJK UNIFIED IDEOGRAPH - 0xE0CD: 0x55E4, //CJK UNIFIED IDEOGRAPH - 0xE0CE: 0x8F94, //CJK UNIFIED IDEOGRAPH - 0xE0CF: 0x561E, //CJK UNIFIED IDEOGRAPH - 0xE0D0: 0x5608, //CJK UNIFIED IDEOGRAPH - 0xE0D1: 0x560C, //CJK UNIFIED IDEOGRAPH - 0xE0D2: 0x5601, //CJK UNIFIED IDEOGRAPH - 0xE0D3: 0x5624, //CJK UNIFIED IDEOGRAPH - 0xE0D4: 0x5623, //CJK UNIFIED IDEOGRAPH - 0xE0D5: 0x55FE, //CJK UNIFIED IDEOGRAPH - 0xE0D6: 0x5600, //CJK UNIFIED IDEOGRAPH - 0xE0D7: 0x5627, //CJK UNIFIED IDEOGRAPH - 0xE0D8: 0x562D, //CJK UNIFIED IDEOGRAPH - 0xE0D9: 0x5658, //CJK UNIFIED IDEOGRAPH - 0xE0DA: 0x5639, //CJK UNIFIED IDEOGRAPH - 0xE0DB: 0x5657, //CJK UNIFIED IDEOGRAPH - 0xE0DC: 0x562C, //CJK UNIFIED IDEOGRAPH - 0xE0DD: 0x564D, //CJK UNIFIED IDEOGRAPH - 0xE0DE: 0x5662, //CJK UNIFIED IDEOGRAPH - 0xE0DF: 0x5659, //CJK UNIFIED IDEOGRAPH - 0xE0E0: 0x565C, //CJK UNIFIED IDEOGRAPH - 0xE0E1: 0x564C, //CJK UNIFIED IDEOGRAPH - 0xE0E2: 0x5654, //CJK UNIFIED IDEOGRAPH - 0xE0E3: 0x5686, //CJK UNIFIED IDEOGRAPH - 0xE0E4: 0x5664, //CJK UNIFIED IDEOGRAPH - 0xE0E5: 0x5671, //CJK UNIFIED IDEOGRAPH - 0xE0E6: 0x566B, //CJK UNIFIED IDEOGRAPH - 0xE0E7: 0x567B, //CJK UNIFIED IDEOGRAPH - 0xE0E8: 0x567C, //CJK UNIFIED IDEOGRAPH - 0xE0E9: 0x5685, //CJK UNIFIED IDEOGRAPH - 0xE0EA: 0x5693, //CJK UNIFIED IDEOGRAPH - 0xE0EB: 0x56AF, //CJK UNIFIED IDEOGRAPH - 0xE0EC: 0x56D4, //CJK UNIFIED IDEOGRAPH - 0xE0ED: 0x56D7, //CJK UNIFIED IDEOGRAPH - 0xE0EE: 0x56DD, //CJK UNIFIED IDEOGRAPH - 0xE0EF: 0x56E1, //CJK UNIFIED IDEOGRAPH - 0xE0F0: 0x56F5, //CJK UNIFIED IDEOGRAPH - 0xE0F1: 0x56EB, //CJK UNIFIED IDEOGRAPH - 0xE0F2: 0x56F9, //CJK UNIFIED IDEOGRAPH - 0xE0F3: 0x56FF, //CJK UNIFIED IDEOGRAPH - 0xE0F4: 0x5704, //CJK UNIFIED IDEOGRAPH - 0xE0F5: 0x570A, //CJK UNIFIED IDEOGRAPH - 0xE0F6: 0x5709, //CJK UNIFIED IDEOGRAPH - 0xE0F7: 0x571C, //CJK UNIFIED IDEOGRAPH - 0xE0F8: 0x5E0F, //CJK UNIFIED IDEOGRAPH - 0xE0F9: 0x5E19, //CJK UNIFIED IDEOGRAPH - 0xE0FA: 0x5E14, //CJK UNIFIED IDEOGRAPH - 0xE0FB: 0x5E11, //CJK UNIFIED IDEOGRAPH - 0xE0FC: 0x5E31, //CJK UNIFIED IDEOGRAPH - 0xE0FD: 0x5E3B, //CJK UNIFIED IDEOGRAPH - 0xE0FE: 0x5E3C, //CJK UNIFIED IDEOGRAPH - 0xE140: 0x9145, //CJK UNIFIED IDEOGRAPH - 0xE141: 0x9147, //CJK UNIFIED IDEOGRAPH - 0xE142: 0x9148, //CJK UNIFIED IDEOGRAPH - 0xE143: 0x9151, //CJK UNIFIED IDEOGRAPH - 0xE144: 0x9153, //CJK UNIFIED IDEOGRAPH - 0xE145: 0x9154, //CJK UNIFIED IDEOGRAPH - 0xE146: 0x9155, //CJK UNIFIED IDEOGRAPH - 0xE147: 0x9156, //CJK UNIFIED IDEOGRAPH - 0xE148: 0x9158, //CJK UNIFIED IDEOGRAPH - 0xE149: 0x9159, //CJK UNIFIED IDEOGRAPH - 0xE14A: 0x915B, //CJK UNIFIED IDEOGRAPH - 0xE14B: 0x915C, //CJK UNIFIED IDEOGRAPH - 0xE14C: 0x915F, //CJK UNIFIED IDEOGRAPH - 0xE14D: 0x9160, //CJK UNIFIED IDEOGRAPH - 0xE14E: 0x9166, //CJK UNIFIED IDEOGRAPH - 0xE14F: 0x9167, //CJK UNIFIED IDEOGRAPH - 0xE150: 0x9168, //CJK UNIFIED IDEOGRAPH - 0xE151: 0x916B, //CJK UNIFIED IDEOGRAPH - 0xE152: 0x916D, //CJK UNIFIED IDEOGRAPH - 0xE153: 0x9173, //CJK UNIFIED IDEOGRAPH - 0xE154: 0x917A, //CJK UNIFIED IDEOGRAPH - 0xE155: 0x917B, //CJK UNIFIED IDEOGRAPH - 0xE156: 0x917C, //CJK UNIFIED IDEOGRAPH - 0xE157: 0x9180, //CJK UNIFIED IDEOGRAPH - 0xE158: 0x9181, //CJK UNIFIED IDEOGRAPH - 0xE159: 0x9182, //CJK UNIFIED IDEOGRAPH - 0xE15A: 0x9183, //CJK UNIFIED IDEOGRAPH - 0xE15B: 0x9184, //CJK UNIFIED IDEOGRAPH - 0xE15C: 0x9186, //CJK UNIFIED IDEOGRAPH - 0xE15D: 0x9188, //CJK UNIFIED IDEOGRAPH - 0xE15E: 0x918A, //CJK UNIFIED IDEOGRAPH - 0xE15F: 0x918E, //CJK UNIFIED IDEOGRAPH - 0xE160: 0x918F, //CJK UNIFIED IDEOGRAPH - 0xE161: 0x9193, //CJK UNIFIED IDEOGRAPH - 0xE162: 0x9194, //CJK UNIFIED IDEOGRAPH - 0xE163: 0x9195, //CJK UNIFIED IDEOGRAPH - 0xE164: 0x9196, //CJK UNIFIED IDEOGRAPH - 0xE165: 0x9197, //CJK UNIFIED IDEOGRAPH - 0xE166: 0x9198, //CJK UNIFIED IDEOGRAPH - 0xE167: 0x9199, //CJK UNIFIED IDEOGRAPH - 0xE168: 0x919C, //CJK UNIFIED IDEOGRAPH - 0xE169: 0x919D, //CJK UNIFIED IDEOGRAPH - 0xE16A: 0x919E, //CJK UNIFIED IDEOGRAPH - 0xE16B: 0x919F, //CJK UNIFIED IDEOGRAPH - 0xE16C: 0x91A0, //CJK UNIFIED IDEOGRAPH - 0xE16D: 0x91A1, //CJK UNIFIED IDEOGRAPH - 0xE16E: 0x91A4, //CJK UNIFIED IDEOGRAPH - 0xE16F: 0x91A5, //CJK UNIFIED IDEOGRAPH - 0xE170: 0x91A6, //CJK UNIFIED IDEOGRAPH - 0xE171: 0x91A7, //CJK UNIFIED IDEOGRAPH - 0xE172: 0x91A8, //CJK UNIFIED IDEOGRAPH - 0xE173: 0x91A9, //CJK UNIFIED IDEOGRAPH - 0xE174: 0x91AB, //CJK UNIFIED IDEOGRAPH - 0xE175: 0x91AC, //CJK UNIFIED IDEOGRAPH - 0xE176: 0x91B0, //CJK UNIFIED IDEOGRAPH - 0xE177: 0x91B1, //CJK UNIFIED IDEOGRAPH - 0xE178: 0x91B2, //CJK UNIFIED IDEOGRAPH - 0xE179: 0x91B3, //CJK UNIFIED IDEOGRAPH - 0xE17A: 0x91B6, //CJK UNIFIED IDEOGRAPH - 0xE17B: 0x91B7, //CJK UNIFIED IDEOGRAPH - 0xE17C: 0x91B8, //CJK UNIFIED IDEOGRAPH - 0xE17D: 0x91B9, //CJK UNIFIED IDEOGRAPH - 0xE17E: 0x91BB, //CJK UNIFIED IDEOGRAPH - 0xE180: 0x91BC, //CJK UNIFIED IDEOGRAPH - 0xE181: 0x91BD, //CJK UNIFIED IDEOGRAPH - 0xE182: 0x91BE, //CJK UNIFIED IDEOGRAPH - 0xE183: 0x91BF, //CJK UNIFIED IDEOGRAPH - 0xE184: 0x91C0, //CJK UNIFIED IDEOGRAPH - 0xE185: 0x91C1, //CJK UNIFIED IDEOGRAPH - 0xE186: 0x91C2, //CJK UNIFIED IDEOGRAPH - 0xE187: 0x91C3, //CJK UNIFIED IDEOGRAPH - 0xE188: 0x91C4, //CJK UNIFIED IDEOGRAPH - 0xE189: 0x91C5, //CJK UNIFIED IDEOGRAPH - 0xE18A: 0x91C6, //CJK UNIFIED IDEOGRAPH - 0xE18B: 0x91C8, //CJK UNIFIED IDEOGRAPH - 0xE18C: 0x91CB, //CJK UNIFIED IDEOGRAPH - 0xE18D: 0x91D0, //CJK UNIFIED IDEOGRAPH - 0xE18E: 0x91D2, //CJK UNIFIED IDEOGRAPH - 0xE18F: 0x91D3, //CJK UNIFIED IDEOGRAPH - 0xE190: 0x91D4, //CJK UNIFIED IDEOGRAPH - 0xE191: 0x91D5, //CJK UNIFIED IDEOGRAPH - 0xE192: 0x91D6, //CJK UNIFIED IDEOGRAPH - 0xE193: 0x91D7, //CJK UNIFIED IDEOGRAPH - 0xE194: 0x91D8, //CJK UNIFIED IDEOGRAPH - 0xE195: 0x91D9, //CJK UNIFIED IDEOGRAPH - 0xE196: 0x91DA, //CJK UNIFIED IDEOGRAPH - 0xE197: 0x91DB, //CJK UNIFIED IDEOGRAPH - 0xE198: 0x91DD, //CJK UNIFIED IDEOGRAPH - 0xE199: 0x91DE, //CJK UNIFIED IDEOGRAPH - 0xE19A: 0x91DF, //CJK UNIFIED IDEOGRAPH - 0xE19B: 0x91E0, //CJK UNIFIED IDEOGRAPH - 0xE19C: 0x91E1, //CJK UNIFIED IDEOGRAPH - 0xE19D: 0x91E2, //CJK UNIFIED IDEOGRAPH - 0xE19E: 0x91E3, //CJK UNIFIED IDEOGRAPH - 0xE19F: 0x91E4, //CJK UNIFIED IDEOGRAPH - 0xE1A0: 0x91E5, //CJK UNIFIED IDEOGRAPH - 0xE1A1: 0x5E37, //CJK UNIFIED IDEOGRAPH - 0xE1A2: 0x5E44, //CJK UNIFIED IDEOGRAPH - 0xE1A3: 0x5E54, //CJK UNIFIED IDEOGRAPH - 0xE1A4: 0x5E5B, //CJK UNIFIED IDEOGRAPH - 0xE1A5: 0x5E5E, //CJK UNIFIED IDEOGRAPH - 0xE1A6: 0x5E61, //CJK UNIFIED IDEOGRAPH - 0xE1A7: 0x5C8C, //CJK UNIFIED IDEOGRAPH - 0xE1A8: 0x5C7A, //CJK UNIFIED IDEOGRAPH - 0xE1A9: 0x5C8D, //CJK UNIFIED IDEOGRAPH - 0xE1AA: 0x5C90, //CJK UNIFIED IDEOGRAPH - 0xE1AB: 0x5C96, //CJK UNIFIED IDEOGRAPH - 0xE1AC: 0x5C88, //CJK UNIFIED IDEOGRAPH - 0xE1AD: 0x5C98, //CJK UNIFIED IDEOGRAPH - 0xE1AE: 0x5C99, //CJK UNIFIED IDEOGRAPH - 0xE1AF: 0x5C91, //CJK UNIFIED IDEOGRAPH - 0xE1B0: 0x5C9A, //CJK UNIFIED IDEOGRAPH - 0xE1B1: 0x5C9C, //CJK UNIFIED IDEOGRAPH - 0xE1B2: 0x5CB5, //CJK UNIFIED IDEOGRAPH - 0xE1B3: 0x5CA2, //CJK UNIFIED IDEOGRAPH - 0xE1B4: 0x5CBD, //CJK UNIFIED IDEOGRAPH - 0xE1B5: 0x5CAC, //CJK UNIFIED IDEOGRAPH - 0xE1B6: 0x5CAB, //CJK UNIFIED IDEOGRAPH - 0xE1B7: 0x5CB1, //CJK UNIFIED IDEOGRAPH - 0xE1B8: 0x5CA3, //CJK UNIFIED IDEOGRAPH - 0xE1B9: 0x5CC1, //CJK UNIFIED IDEOGRAPH - 0xE1BA: 0x5CB7, //CJK UNIFIED IDEOGRAPH - 0xE1BB: 0x5CC4, //CJK UNIFIED IDEOGRAPH - 0xE1BC: 0x5CD2, //CJK UNIFIED IDEOGRAPH - 0xE1BD: 0x5CE4, //CJK UNIFIED IDEOGRAPH - 0xE1BE: 0x5CCB, //CJK UNIFIED IDEOGRAPH - 0xE1BF: 0x5CE5, //CJK UNIFIED IDEOGRAPH - 0xE1C0: 0x5D02, //CJK UNIFIED IDEOGRAPH - 0xE1C1: 0x5D03, //CJK UNIFIED IDEOGRAPH - 0xE1C2: 0x5D27, //CJK UNIFIED IDEOGRAPH - 0xE1C3: 0x5D26, //CJK UNIFIED IDEOGRAPH - 0xE1C4: 0x5D2E, //CJK UNIFIED IDEOGRAPH - 0xE1C5: 0x5D24, //CJK UNIFIED IDEOGRAPH - 0xE1C6: 0x5D1E, //CJK UNIFIED IDEOGRAPH - 0xE1C7: 0x5D06, //CJK UNIFIED IDEOGRAPH - 0xE1C8: 0x5D1B, //CJK UNIFIED IDEOGRAPH - 0xE1C9: 0x5D58, //CJK UNIFIED IDEOGRAPH - 0xE1CA: 0x5D3E, //CJK UNIFIED IDEOGRAPH - 0xE1CB: 0x5D34, //CJK UNIFIED IDEOGRAPH - 0xE1CC: 0x5D3D, //CJK UNIFIED IDEOGRAPH - 0xE1CD: 0x5D6C, //CJK UNIFIED IDEOGRAPH - 0xE1CE: 0x5D5B, //CJK UNIFIED IDEOGRAPH - 0xE1CF: 0x5D6F, //CJK UNIFIED IDEOGRAPH - 0xE1D0: 0x5D5D, //CJK UNIFIED IDEOGRAPH - 0xE1D1: 0x5D6B, //CJK UNIFIED IDEOGRAPH - 0xE1D2: 0x5D4B, //CJK UNIFIED IDEOGRAPH - 0xE1D3: 0x5D4A, //CJK UNIFIED IDEOGRAPH - 0xE1D4: 0x5D69, //CJK UNIFIED IDEOGRAPH - 0xE1D5: 0x5D74, //CJK UNIFIED IDEOGRAPH - 0xE1D6: 0x5D82, //CJK UNIFIED IDEOGRAPH - 0xE1D7: 0x5D99, //CJK UNIFIED IDEOGRAPH - 0xE1D8: 0x5D9D, //CJK UNIFIED IDEOGRAPH - 0xE1D9: 0x8C73, //CJK UNIFIED IDEOGRAPH - 0xE1DA: 0x5DB7, //CJK UNIFIED IDEOGRAPH - 0xE1DB: 0x5DC5, //CJK UNIFIED IDEOGRAPH - 0xE1DC: 0x5F73, //CJK UNIFIED IDEOGRAPH - 0xE1DD: 0x5F77, //CJK UNIFIED IDEOGRAPH - 0xE1DE: 0x5F82, //CJK UNIFIED IDEOGRAPH - 0xE1DF: 0x5F87, //CJK UNIFIED IDEOGRAPH - 0xE1E0: 0x5F89, //CJK UNIFIED IDEOGRAPH - 0xE1E1: 0x5F8C, //CJK UNIFIED IDEOGRAPH - 0xE1E2: 0x5F95, //CJK UNIFIED IDEOGRAPH - 0xE1E3: 0x5F99, //CJK UNIFIED IDEOGRAPH - 0xE1E4: 0x5F9C, //CJK UNIFIED IDEOGRAPH - 0xE1E5: 0x5FA8, //CJK UNIFIED IDEOGRAPH - 0xE1E6: 0x5FAD, //CJK UNIFIED IDEOGRAPH - 0xE1E7: 0x5FB5, //CJK UNIFIED IDEOGRAPH - 0xE1E8: 0x5FBC, //CJK UNIFIED IDEOGRAPH - 0xE1E9: 0x8862, //CJK UNIFIED IDEOGRAPH - 0xE1EA: 0x5F61, //CJK UNIFIED IDEOGRAPH - 0xE1EB: 0x72AD, //CJK UNIFIED IDEOGRAPH - 0xE1EC: 0x72B0, //CJK UNIFIED IDEOGRAPH - 0xE1ED: 0x72B4, //CJK UNIFIED IDEOGRAPH - 0xE1EE: 0x72B7, //CJK UNIFIED IDEOGRAPH - 0xE1EF: 0x72B8, //CJK UNIFIED IDEOGRAPH - 0xE1F0: 0x72C3, //CJK UNIFIED IDEOGRAPH - 0xE1F1: 0x72C1, //CJK UNIFIED IDEOGRAPH - 0xE1F2: 0x72CE, //CJK UNIFIED IDEOGRAPH - 0xE1F3: 0x72CD, //CJK UNIFIED IDEOGRAPH - 0xE1F4: 0x72D2, //CJK UNIFIED IDEOGRAPH - 0xE1F5: 0x72E8, //CJK UNIFIED IDEOGRAPH - 0xE1F6: 0x72EF, //CJK UNIFIED IDEOGRAPH - 0xE1F7: 0x72E9, //CJK UNIFIED IDEOGRAPH - 0xE1F8: 0x72F2, //CJK UNIFIED IDEOGRAPH - 0xE1F9: 0x72F4, //CJK UNIFIED IDEOGRAPH - 0xE1FA: 0x72F7, //CJK UNIFIED IDEOGRAPH - 0xE1FB: 0x7301, //CJK UNIFIED IDEOGRAPH - 0xE1FC: 0x72F3, //CJK UNIFIED IDEOGRAPH - 0xE1FD: 0x7303, //CJK UNIFIED IDEOGRAPH - 0xE1FE: 0x72FA, //CJK UNIFIED IDEOGRAPH - 0xE240: 0x91E6, //CJK UNIFIED IDEOGRAPH - 0xE241: 0x91E7, //CJK UNIFIED IDEOGRAPH - 0xE242: 0x91E8, //CJK UNIFIED IDEOGRAPH - 0xE243: 0x91E9, //CJK UNIFIED IDEOGRAPH - 0xE244: 0x91EA, //CJK UNIFIED IDEOGRAPH - 0xE245: 0x91EB, //CJK UNIFIED IDEOGRAPH - 0xE246: 0x91EC, //CJK UNIFIED IDEOGRAPH - 0xE247: 0x91ED, //CJK UNIFIED IDEOGRAPH - 0xE248: 0x91EE, //CJK UNIFIED IDEOGRAPH - 0xE249: 0x91EF, //CJK UNIFIED IDEOGRAPH - 0xE24A: 0x91F0, //CJK UNIFIED IDEOGRAPH - 0xE24B: 0x91F1, //CJK UNIFIED IDEOGRAPH - 0xE24C: 0x91F2, //CJK UNIFIED IDEOGRAPH - 0xE24D: 0x91F3, //CJK UNIFIED IDEOGRAPH - 0xE24E: 0x91F4, //CJK UNIFIED IDEOGRAPH - 0xE24F: 0x91F5, //CJK UNIFIED IDEOGRAPH - 0xE250: 0x91F6, //CJK UNIFIED IDEOGRAPH - 0xE251: 0x91F7, //CJK UNIFIED IDEOGRAPH - 0xE252: 0x91F8, //CJK UNIFIED IDEOGRAPH - 0xE253: 0x91F9, //CJK UNIFIED IDEOGRAPH - 0xE254: 0x91FA, //CJK UNIFIED IDEOGRAPH - 0xE255: 0x91FB, //CJK UNIFIED IDEOGRAPH - 0xE256: 0x91FC, //CJK UNIFIED IDEOGRAPH - 0xE257: 0x91FD, //CJK UNIFIED IDEOGRAPH - 0xE258: 0x91FE, //CJK UNIFIED IDEOGRAPH - 0xE259: 0x91FF, //CJK UNIFIED IDEOGRAPH - 0xE25A: 0x9200, //CJK UNIFIED IDEOGRAPH - 0xE25B: 0x9201, //CJK UNIFIED IDEOGRAPH - 0xE25C: 0x9202, //CJK UNIFIED IDEOGRAPH - 0xE25D: 0x9203, //CJK UNIFIED IDEOGRAPH - 0xE25E: 0x9204, //CJK UNIFIED IDEOGRAPH - 0xE25F: 0x9205, //CJK UNIFIED IDEOGRAPH - 0xE260: 0x9206, //CJK UNIFIED IDEOGRAPH - 0xE261: 0x9207, //CJK UNIFIED IDEOGRAPH - 0xE262: 0x9208, //CJK UNIFIED IDEOGRAPH - 0xE263: 0x9209, //CJK UNIFIED IDEOGRAPH - 0xE264: 0x920A, //CJK UNIFIED IDEOGRAPH - 0xE265: 0x920B, //CJK UNIFIED IDEOGRAPH - 0xE266: 0x920C, //CJK UNIFIED IDEOGRAPH - 0xE267: 0x920D, //CJK UNIFIED IDEOGRAPH - 0xE268: 0x920E, //CJK UNIFIED IDEOGRAPH - 0xE269: 0x920F, //CJK UNIFIED IDEOGRAPH - 0xE26A: 0x9210, //CJK UNIFIED IDEOGRAPH - 0xE26B: 0x9211, //CJK UNIFIED IDEOGRAPH - 0xE26C: 0x9212, //CJK UNIFIED IDEOGRAPH - 0xE26D: 0x9213, //CJK UNIFIED IDEOGRAPH - 0xE26E: 0x9214, //CJK UNIFIED IDEOGRAPH - 0xE26F: 0x9215, //CJK UNIFIED IDEOGRAPH - 0xE270: 0x9216, //CJK UNIFIED IDEOGRAPH - 0xE271: 0x9217, //CJK UNIFIED IDEOGRAPH - 0xE272: 0x9218, //CJK UNIFIED IDEOGRAPH - 0xE273: 0x9219, //CJK UNIFIED IDEOGRAPH - 0xE274: 0x921A, //CJK UNIFIED IDEOGRAPH - 0xE275: 0x921B, //CJK UNIFIED IDEOGRAPH - 0xE276: 0x921C, //CJK UNIFIED IDEOGRAPH - 0xE277: 0x921D, //CJK UNIFIED IDEOGRAPH - 0xE278: 0x921E, //CJK UNIFIED IDEOGRAPH - 0xE279: 0x921F, //CJK UNIFIED IDEOGRAPH - 0xE27A: 0x9220, //CJK UNIFIED IDEOGRAPH - 0xE27B: 0x9221, //CJK UNIFIED IDEOGRAPH - 0xE27C: 0x9222, //CJK UNIFIED IDEOGRAPH - 0xE27D: 0x9223, //CJK UNIFIED IDEOGRAPH - 0xE27E: 0x9224, //CJK UNIFIED IDEOGRAPH - 0xE280: 0x9225, //CJK UNIFIED IDEOGRAPH - 0xE281: 0x9226, //CJK UNIFIED IDEOGRAPH - 0xE282: 0x9227, //CJK UNIFIED IDEOGRAPH - 0xE283: 0x9228, //CJK UNIFIED IDEOGRAPH - 0xE284: 0x9229, //CJK UNIFIED IDEOGRAPH - 0xE285: 0x922A, //CJK UNIFIED IDEOGRAPH - 0xE286: 0x922B, //CJK UNIFIED IDEOGRAPH - 0xE287: 0x922C, //CJK UNIFIED IDEOGRAPH - 0xE288: 0x922D, //CJK UNIFIED IDEOGRAPH - 0xE289: 0x922E, //CJK UNIFIED IDEOGRAPH - 0xE28A: 0x922F, //CJK UNIFIED IDEOGRAPH - 0xE28B: 0x9230, //CJK UNIFIED IDEOGRAPH - 0xE28C: 0x9231, //CJK UNIFIED IDEOGRAPH - 0xE28D: 0x9232, //CJK UNIFIED IDEOGRAPH - 0xE28E: 0x9233, //CJK UNIFIED IDEOGRAPH - 0xE28F: 0x9234, //CJK UNIFIED IDEOGRAPH - 0xE290: 0x9235, //CJK UNIFIED IDEOGRAPH - 0xE291: 0x9236, //CJK UNIFIED IDEOGRAPH - 0xE292: 0x9237, //CJK UNIFIED IDEOGRAPH - 0xE293: 0x9238, //CJK UNIFIED IDEOGRAPH - 0xE294: 0x9239, //CJK UNIFIED IDEOGRAPH - 0xE295: 0x923A, //CJK UNIFIED IDEOGRAPH - 0xE296: 0x923B, //CJK UNIFIED IDEOGRAPH - 0xE297: 0x923C, //CJK UNIFIED IDEOGRAPH - 0xE298: 0x923D, //CJK UNIFIED IDEOGRAPH - 0xE299: 0x923E, //CJK UNIFIED IDEOGRAPH - 0xE29A: 0x923F, //CJK UNIFIED IDEOGRAPH - 0xE29B: 0x9240, //CJK UNIFIED IDEOGRAPH - 0xE29C: 0x9241, //CJK UNIFIED IDEOGRAPH - 0xE29D: 0x9242, //CJK UNIFIED IDEOGRAPH - 0xE29E: 0x9243, //CJK UNIFIED IDEOGRAPH - 0xE29F: 0x9244, //CJK UNIFIED IDEOGRAPH - 0xE2A0: 0x9245, //CJK UNIFIED IDEOGRAPH - 0xE2A1: 0x72FB, //CJK UNIFIED IDEOGRAPH - 0xE2A2: 0x7317, //CJK UNIFIED IDEOGRAPH - 0xE2A3: 0x7313, //CJK UNIFIED IDEOGRAPH - 0xE2A4: 0x7321, //CJK UNIFIED IDEOGRAPH - 0xE2A5: 0x730A, //CJK UNIFIED IDEOGRAPH - 0xE2A6: 0x731E, //CJK UNIFIED IDEOGRAPH - 0xE2A7: 0x731D, //CJK UNIFIED IDEOGRAPH - 0xE2A8: 0x7315, //CJK UNIFIED IDEOGRAPH - 0xE2A9: 0x7322, //CJK UNIFIED IDEOGRAPH - 0xE2AA: 0x7339, //CJK UNIFIED IDEOGRAPH - 0xE2AB: 0x7325, //CJK UNIFIED IDEOGRAPH - 0xE2AC: 0x732C, //CJK UNIFIED IDEOGRAPH - 0xE2AD: 0x7338, //CJK UNIFIED IDEOGRAPH - 0xE2AE: 0x7331, //CJK UNIFIED IDEOGRAPH - 0xE2AF: 0x7350, //CJK UNIFIED IDEOGRAPH - 0xE2B0: 0x734D, //CJK UNIFIED IDEOGRAPH - 0xE2B1: 0x7357, //CJK UNIFIED IDEOGRAPH - 0xE2B2: 0x7360, //CJK UNIFIED IDEOGRAPH - 0xE2B3: 0x736C, //CJK UNIFIED IDEOGRAPH - 0xE2B4: 0x736F, //CJK UNIFIED IDEOGRAPH - 0xE2B5: 0x737E, //CJK UNIFIED IDEOGRAPH - 0xE2B6: 0x821B, //CJK UNIFIED IDEOGRAPH - 0xE2B7: 0x5925, //CJK UNIFIED IDEOGRAPH - 0xE2B8: 0x98E7, //CJK UNIFIED IDEOGRAPH - 0xE2B9: 0x5924, //CJK UNIFIED IDEOGRAPH - 0xE2BA: 0x5902, //CJK UNIFIED IDEOGRAPH - 0xE2BB: 0x9963, //CJK UNIFIED IDEOGRAPH - 0xE2BC: 0x9967, //CJK UNIFIED IDEOGRAPH - 0xE2BD: 0x9968, //CJK UNIFIED IDEOGRAPH - 0xE2BE: 0x9969, //CJK UNIFIED IDEOGRAPH - 0xE2BF: 0x996A, //CJK UNIFIED IDEOGRAPH - 0xE2C0: 0x996B, //CJK UNIFIED IDEOGRAPH - 0xE2C1: 0x996C, //CJK UNIFIED IDEOGRAPH - 0xE2C2: 0x9974, //CJK UNIFIED IDEOGRAPH - 0xE2C3: 0x9977, //CJK UNIFIED IDEOGRAPH - 0xE2C4: 0x997D, //CJK UNIFIED IDEOGRAPH - 0xE2C5: 0x9980, //CJK UNIFIED IDEOGRAPH - 0xE2C6: 0x9984, //CJK UNIFIED IDEOGRAPH - 0xE2C7: 0x9987, //CJK UNIFIED IDEOGRAPH - 0xE2C8: 0x998A, //CJK UNIFIED IDEOGRAPH - 0xE2C9: 0x998D, //CJK UNIFIED IDEOGRAPH - 0xE2CA: 0x9990, //CJK UNIFIED IDEOGRAPH - 0xE2CB: 0x9991, //CJK UNIFIED IDEOGRAPH - 0xE2CC: 0x9993, //CJK UNIFIED IDEOGRAPH - 0xE2CD: 0x9994, //CJK UNIFIED IDEOGRAPH - 0xE2CE: 0x9995, //CJK UNIFIED IDEOGRAPH - 0xE2CF: 0x5E80, //CJK UNIFIED IDEOGRAPH - 0xE2D0: 0x5E91, //CJK UNIFIED IDEOGRAPH - 0xE2D1: 0x5E8B, //CJK UNIFIED IDEOGRAPH - 0xE2D2: 0x5E96, //CJK UNIFIED IDEOGRAPH - 0xE2D3: 0x5EA5, //CJK UNIFIED IDEOGRAPH - 0xE2D4: 0x5EA0, //CJK UNIFIED IDEOGRAPH - 0xE2D5: 0x5EB9, //CJK UNIFIED IDEOGRAPH - 0xE2D6: 0x5EB5, //CJK UNIFIED IDEOGRAPH - 0xE2D7: 0x5EBE, //CJK UNIFIED IDEOGRAPH - 0xE2D8: 0x5EB3, //CJK UNIFIED IDEOGRAPH - 0xE2D9: 0x8D53, //CJK UNIFIED IDEOGRAPH - 0xE2DA: 0x5ED2, //CJK UNIFIED IDEOGRAPH - 0xE2DB: 0x5ED1, //CJK UNIFIED IDEOGRAPH - 0xE2DC: 0x5EDB, //CJK UNIFIED IDEOGRAPH - 0xE2DD: 0x5EE8, //CJK UNIFIED IDEOGRAPH - 0xE2DE: 0x5EEA, //CJK UNIFIED IDEOGRAPH - 0xE2DF: 0x81BA, //CJK UNIFIED IDEOGRAPH - 0xE2E0: 0x5FC4, //CJK UNIFIED IDEOGRAPH - 0xE2E1: 0x5FC9, //CJK UNIFIED IDEOGRAPH - 0xE2E2: 0x5FD6, //CJK UNIFIED IDEOGRAPH - 0xE2E3: 0x5FCF, //CJK UNIFIED IDEOGRAPH - 0xE2E4: 0x6003, //CJK UNIFIED IDEOGRAPH - 0xE2E5: 0x5FEE, //CJK UNIFIED IDEOGRAPH - 0xE2E6: 0x6004, //CJK UNIFIED IDEOGRAPH - 0xE2E7: 0x5FE1, //CJK UNIFIED IDEOGRAPH - 0xE2E8: 0x5FE4, //CJK UNIFIED IDEOGRAPH - 0xE2E9: 0x5FFE, //CJK UNIFIED IDEOGRAPH - 0xE2EA: 0x6005, //CJK UNIFIED IDEOGRAPH - 0xE2EB: 0x6006, //CJK UNIFIED IDEOGRAPH - 0xE2EC: 0x5FEA, //CJK UNIFIED IDEOGRAPH - 0xE2ED: 0x5FED, //CJK UNIFIED IDEOGRAPH - 0xE2EE: 0x5FF8, //CJK UNIFIED IDEOGRAPH - 0xE2EF: 0x6019, //CJK UNIFIED IDEOGRAPH - 0xE2F0: 0x6035, //CJK UNIFIED IDEOGRAPH - 0xE2F1: 0x6026, //CJK UNIFIED IDEOGRAPH - 0xE2F2: 0x601B, //CJK UNIFIED IDEOGRAPH - 0xE2F3: 0x600F, //CJK UNIFIED IDEOGRAPH - 0xE2F4: 0x600D, //CJK UNIFIED IDEOGRAPH - 0xE2F5: 0x6029, //CJK UNIFIED IDEOGRAPH - 0xE2F6: 0x602B, //CJK UNIFIED IDEOGRAPH - 0xE2F7: 0x600A, //CJK UNIFIED IDEOGRAPH - 0xE2F8: 0x603F, //CJK UNIFIED IDEOGRAPH - 0xE2F9: 0x6021, //CJK UNIFIED IDEOGRAPH - 0xE2FA: 0x6078, //CJK UNIFIED IDEOGRAPH - 0xE2FB: 0x6079, //CJK UNIFIED IDEOGRAPH - 0xE2FC: 0x607B, //CJK UNIFIED IDEOGRAPH - 0xE2FD: 0x607A, //CJK UNIFIED IDEOGRAPH - 0xE2FE: 0x6042, //CJK UNIFIED IDEOGRAPH - 0xE340: 0x9246, //CJK UNIFIED IDEOGRAPH - 0xE341: 0x9247, //CJK UNIFIED IDEOGRAPH - 0xE342: 0x9248, //CJK UNIFIED IDEOGRAPH - 0xE343: 0x9249, //CJK UNIFIED IDEOGRAPH - 0xE344: 0x924A, //CJK UNIFIED IDEOGRAPH - 0xE345: 0x924B, //CJK UNIFIED IDEOGRAPH - 0xE346: 0x924C, //CJK UNIFIED IDEOGRAPH - 0xE347: 0x924D, //CJK UNIFIED IDEOGRAPH - 0xE348: 0x924E, //CJK UNIFIED IDEOGRAPH - 0xE349: 0x924F, //CJK UNIFIED IDEOGRAPH - 0xE34A: 0x9250, //CJK UNIFIED IDEOGRAPH - 0xE34B: 0x9251, //CJK UNIFIED IDEOGRAPH - 0xE34C: 0x9252, //CJK UNIFIED IDEOGRAPH - 0xE34D: 0x9253, //CJK UNIFIED IDEOGRAPH - 0xE34E: 0x9254, //CJK UNIFIED IDEOGRAPH - 0xE34F: 0x9255, //CJK UNIFIED IDEOGRAPH - 0xE350: 0x9256, //CJK UNIFIED IDEOGRAPH - 0xE351: 0x9257, //CJK UNIFIED IDEOGRAPH - 0xE352: 0x9258, //CJK UNIFIED IDEOGRAPH - 0xE353: 0x9259, //CJK UNIFIED IDEOGRAPH - 0xE354: 0x925A, //CJK UNIFIED IDEOGRAPH - 0xE355: 0x925B, //CJK UNIFIED IDEOGRAPH - 0xE356: 0x925C, //CJK UNIFIED IDEOGRAPH - 0xE357: 0x925D, //CJK UNIFIED IDEOGRAPH - 0xE358: 0x925E, //CJK UNIFIED IDEOGRAPH - 0xE359: 0x925F, //CJK UNIFIED IDEOGRAPH - 0xE35A: 0x9260, //CJK UNIFIED IDEOGRAPH - 0xE35B: 0x9261, //CJK UNIFIED IDEOGRAPH - 0xE35C: 0x9262, //CJK UNIFIED IDEOGRAPH - 0xE35D: 0x9263, //CJK UNIFIED IDEOGRAPH - 0xE35E: 0x9264, //CJK UNIFIED IDEOGRAPH - 0xE35F: 0x9265, //CJK UNIFIED IDEOGRAPH - 0xE360: 0x9266, //CJK UNIFIED IDEOGRAPH - 0xE361: 0x9267, //CJK UNIFIED IDEOGRAPH - 0xE362: 0x9268, //CJK UNIFIED IDEOGRAPH - 0xE363: 0x9269, //CJK UNIFIED IDEOGRAPH - 0xE364: 0x926A, //CJK UNIFIED IDEOGRAPH - 0xE365: 0x926B, //CJK UNIFIED IDEOGRAPH - 0xE366: 0x926C, //CJK UNIFIED IDEOGRAPH - 0xE367: 0x926D, //CJK UNIFIED IDEOGRAPH - 0xE368: 0x926E, //CJK UNIFIED IDEOGRAPH - 0xE369: 0x926F, //CJK UNIFIED IDEOGRAPH - 0xE36A: 0x9270, //CJK UNIFIED IDEOGRAPH - 0xE36B: 0x9271, //CJK UNIFIED IDEOGRAPH - 0xE36C: 0x9272, //CJK UNIFIED IDEOGRAPH - 0xE36D: 0x9273, //CJK UNIFIED IDEOGRAPH - 0xE36E: 0x9275, //CJK UNIFIED IDEOGRAPH - 0xE36F: 0x9276, //CJK UNIFIED IDEOGRAPH - 0xE370: 0x9277, //CJK UNIFIED IDEOGRAPH - 0xE371: 0x9278, //CJK UNIFIED IDEOGRAPH - 0xE372: 0x9279, //CJK UNIFIED IDEOGRAPH - 0xE373: 0x927A, //CJK UNIFIED IDEOGRAPH - 0xE374: 0x927B, //CJK UNIFIED IDEOGRAPH - 0xE375: 0x927C, //CJK UNIFIED IDEOGRAPH - 0xE376: 0x927D, //CJK UNIFIED IDEOGRAPH - 0xE377: 0x927E, //CJK UNIFIED IDEOGRAPH - 0xE378: 0x927F, //CJK UNIFIED IDEOGRAPH - 0xE379: 0x9280, //CJK UNIFIED IDEOGRAPH - 0xE37A: 0x9281, //CJK UNIFIED IDEOGRAPH - 0xE37B: 0x9282, //CJK UNIFIED IDEOGRAPH - 0xE37C: 0x9283, //CJK UNIFIED IDEOGRAPH - 0xE37D: 0x9284, //CJK UNIFIED IDEOGRAPH - 0xE37E: 0x9285, //CJK UNIFIED IDEOGRAPH - 0xE380: 0x9286, //CJK UNIFIED IDEOGRAPH - 0xE381: 0x9287, //CJK UNIFIED IDEOGRAPH - 0xE382: 0x9288, //CJK UNIFIED IDEOGRAPH - 0xE383: 0x9289, //CJK UNIFIED IDEOGRAPH - 0xE384: 0x928A, //CJK UNIFIED IDEOGRAPH - 0xE385: 0x928B, //CJK UNIFIED IDEOGRAPH - 0xE386: 0x928C, //CJK UNIFIED IDEOGRAPH - 0xE387: 0x928D, //CJK UNIFIED IDEOGRAPH - 0xE388: 0x928F, //CJK UNIFIED IDEOGRAPH - 0xE389: 0x9290, //CJK UNIFIED IDEOGRAPH - 0xE38A: 0x9291, //CJK UNIFIED IDEOGRAPH - 0xE38B: 0x9292, //CJK UNIFIED IDEOGRAPH - 0xE38C: 0x9293, //CJK UNIFIED IDEOGRAPH - 0xE38D: 0x9294, //CJK UNIFIED IDEOGRAPH - 0xE38E: 0x9295, //CJK UNIFIED IDEOGRAPH - 0xE38F: 0x9296, //CJK UNIFIED IDEOGRAPH - 0xE390: 0x9297, //CJK UNIFIED IDEOGRAPH - 0xE391: 0x9298, //CJK UNIFIED IDEOGRAPH - 0xE392: 0x9299, //CJK UNIFIED IDEOGRAPH - 0xE393: 0x929A, //CJK UNIFIED IDEOGRAPH - 0xE394: 0x929B, //CJK UNIFIED IDEOGRAPH - 0xE395: 0x929C, //CJK UNIFIED IDEOGRAPH - 0xE396: 0x929D, //CJK UNIFIED IDEOGRAPH - 0xE397: 0x929E, //CJK UNIFIED IDEOGRAPH - 0xE398: 0x929F, //CJK UNIFIED IDEOGRAPH - 0xE399: 0x92A0, //CJK UNIFIED IDEOGRAPH - 0xE39A: 0x92A1, //CJK UNIFIED IDEOGRAPH - 0xE39B: 0x92A2, //CJK UNIFIED IDEOGRAPH - 0xE39C: 0x92A3, //CJK UNIFIED IDEOGRAPH - 0xE39D: 0x92A4, //CJK UNIFIED IDEOGRAPH - 0xE39E: 0x92A5, //CJK UNIFIED IDEOGRAPH - 0xE39F: 0x92A6, //CJK UNIFIED IDEOGRAPH - 0xE3A0: 0x92A7, //CJK UNIFIED IDEOGRAPH - 0xE3A1: 0x606A, //CJK UNIFIED IDEOGRAPH - 0xE3A2: 0x607D, //CJK UNIFIED IDEOGRAPH - 0xE3A3: 0x6096, //CJK UNIFIED IDEOGRAPH - 0xE3A4: 0x609A, //CJK UNIFIED IDEOGRAPH - 0xE3A5: 0x60AD, //CJK UNIFIED IDEOGRAPH - 0xE3A6: 0x609D, //CJK UNIFIED IDEOGRAPH - 0xE3A7: 0x6083, //CJK UNIFIED IDEOGRAPH - 0xE3A8: 0x6092, //CJK UNIFIED IDEOGRAPH - 0xE3A9: 0x608C, //CJK UNIFIED IDEOGRAPH - 0xE3AA: 0x609B, //CJK UNIFIED IDEOGRAPH - 0xE3AB: 0x60EC, //CJK UNIFIED IDEOGRAPH - 0xE3AC: 0x60BB, //CJK UNIFIED IDEOGRAPH - 0xE3AD: 0x60B1, //CJK UNIFIED IDEOGRAPH - 0xE3AE: 0x60DD, //CJK UNIFIED IDEOGRAPH - 0xE3AF: 0x60D8, //CJK UNIFIED IDEOGRAPH - 0xE3B0: 0x60C6, //CJK UNIFIED IDEOGRAPH - 0xE3B1: 0x60DA, //CJK UNIFIED IDEOGRAPH - 0xE3B2: 0x60B4, //CJK UNIFIED IDEOGRAPH - 0xE3B3: 0x6120, //CJK UNIFIED IDEOGRAPH - 0xE3B4: 0x6126, //CJK UNIFIED IDEOGRAPH - 0xE3B5: 0x6115, //CJK UNIFIED IDEOGRAPH - 0xE3B6: 0x6123, //CJK UNIFIED IDEOGRAPH - 0xE3B7: 0x60F4, //CJK UNIFIED IDEOGRAPH - 0xE3B8: 0x6100, //CJK UNIFIED IDEOGRAPH - 0xE3B9: 0x610E, //CJK UNIFIED IDEOGRAPH - 0xE3BA: 0x612B, //CJK UNIFIED IDEOGRAPH - 0xE3BB: 0x614A, //CJK UNIFIED IDEOGRAPH - 0xE3BC: 0x6175, //CJK UNIFIED IDEOGRAPH - 0xE3BD: 0x61AC, //CJK UNIFIED IDEOGRAPH - 0xE3BE: 0x6194, //CJK UNIFIED IDEOGRAPH - 0xE3BF: 0x61A7, //CJK UNIFIED IDEOGRAPH - 0xE3C0: 0x61B7, //CJK UNIFIED IDEOGRAPH - 0xE3C1: 0x61D4, //CJK UNIFIED IDEOGRAPH - 0xE3C2: 0x61F5, //CJK UNIFIED IDEOGRAPH - 0xE3C3: 0x5FDD, //CJK UNIFIED IDEOGRAPH - 0xE3C4: 0x96B3, //CJK UNIFIED IDEOGRAPH - 0xE3C5: 0x95E9, //CJK UNIFIED IDEOGRAPH - 0xE3C6: 0x95EB, //CJK UNIFIED IDEOGRAPH - 0xE3C7: 0x95F1, //CJK UNIFIED IDEOGRAPH - 0xE3C8: 0x95F3, //CJK UNIFIED IDEOGRAPH - 0xE3C9: 0x95F5, //CJK UNIFIED IDEOGRAPH - 0xE3CA: 0x95F6, //CJK UNIFIED IDEOGRAPH - 0xE3CB: 0x95FC, //CJK UNIFIED IDEOGRAPH - 0xE3CC: 0x95FE, //CJK UNIFIED IDEOGRAPH - 0xE3CD: 0x9603, //CJK UNIFIED IDEOGRAPH - 0xE3CE: 0x9604, //CJK UNIFIED IDEOGRAPH - 0xE3CF: 0x9606, //CJK UNIFIED IDEOGRAPH - 0xE3D0: 0x9608, //CJK UNIFIED IDEOGRAPH - 0xE3D1: 0x960A, //CJK UNIFIED IDEOGRAPH - 0xE3D2: 0x960B, //CJK UNIFIED IDEOGRAPH - 0xE3D3: 0x960C, //CJK UNIFIED IDEOGRAPH - 0xE3D4: 0x960D, //CJK UNIFIED IDEOGRAPH - 0xE3D5: 0x960F, //CJK UNIFIED IDEOGRAPH - 0xE3D6: 0x9612, //CJK UNIFIED IDEOGRAPH - 0xE3D7: 0x9615, //CJK UNIFIED IDEOGRAPH - 0xE3D8: 0x9616, //CJK UNIFIED IDEOGRAPH - 0xE3D9: 0x9617, //CJK UNIFIED IDEOGRAPH - 0xE3DA: 0x9619, //CJK UNIFIED IDEOGRAPH - 0xE3DB: 0x961A, //CJK UNIFIED IDEOGRAPH - 0xE3DC: 0x4E2C, //CJK UNIFIED IDEOGRAPH - 0xE3DD: 0x723F, //CJK UNIFIED IDEOGRAPH - 0xE3DE: 0x6215, //CJK UNIFIED IDEOGRAPH - 0xE3DF: 0x6C35, //CJK UNIFIED IDEOGRAPH - 0xE3E0: 0x6C54, //CJK UNIFIED IDEOGRAPH - 0xE3E1: 0x6C5C, //CJK UNIFIED IDEOGRAPH - 0xE3E2: 0x6C4A, //CJK UNIFIED IDEOGRAPH - 0xE3E3: 0x6CA3, //CJK UNIFIED IDEOGRAPH - 0xE3E4: 0x6C85, //CJK UNIFIED IDEOGRAPH - 0xE3E5: 0x6C90, //CJK UNIFIED IDEOGRAPH - 0xE3E6: 0x6C94, //CJK UNIFIED IDEOGRAPH - 0xE3E7: 0x6C8C, //CJK UNIFIED IDEOGRAPH - 0xE3E8: 0x6C68, //CJK UNIFIED IDEOGRAPH - 0xE3E9: 0x6C69, //CJK UNIFIED IDEOGRAPH - 0xE3EA: 0x6C74, //CJK UNIFIED IDEOGRAPH - 0xE3EB: 0x6C76, //CJK UNIFIED IDEOGRAPH - 0xE3EC: 0x6C86, //CJK UNIFIED IDEOGRAPH - 0xE3ED: 0x6CA9, //CJK UNIFIED IDEOGRAPH - 0xE3EE: 0x6CD0, //CJK UNIFIED IDEOGRAPH - 0xE3EF: 0x6CD4, //CJK UNIFIED IDEOGRAPH - 0xE3F0: 0x6CAD, //CJK UNIFIED IDEOGRAPH - 0xE3F1: 0x6CF7, //CJK UNIFIED IDEOGRAPH - 0xE3F2: 0x6CF8, //CJK UNIFIED IDEOGRAPH - 0xE3F3: 0x6CF1, //CJK UNIFIED IDEOGRAPH - 0xE3F4: 0x6CD7, //CJK UNIFIED IDEOGRAPH - 0xE3F5: 0x6CB2, //CJK UNIFIED IDEOGRAPH - 0xE3F6: 0x6CE0, //CJK UNIFIED IDEOGRAPH - 0xE3F7: 0x6CD6, //CJK UNIFIED IDEOGRAPH - 0xE3F8: 0x6CFA, //CJK UNIFIED IDEOGRAPH - 0xE3F9: 0x6CEB, //CJK UNIFIED IDEOGRAPH - 0xE3FA: 0x6CEE, //CJK UNIFIED IDEOGRAPH - 0xE3FB: 0x6CB1, //CJK UNIFIED IDEOGRAPH - 0xE3FC: 0x6CD3, //CJK UNIFIED IDEOGRAPH - 0xE3FD: 0x6CEF, //CJK UNIFIED IDEOGRAPH - 0xE3FE: 0x6CFE, //CJK UNIFIED IDEOGRAPH - 0xE440: 0x92A8, //CJK UNIFIED IDEOGRAPH - 0xE441: 0x92A9, //CJK UNIFIED IDEOGRAPH - 0xE442: 0x92AA, //CJK UNIFIED IDEOGRAPH - 0xE443: 0x92AB, //CJK UNIFIED IDEOGRAPH - 0xE444: 0x92AC, //CJK UNIFIED IDEOGRAPH - 0xE445: 0x92AD, //CJK UNIFIED IDEOGRAPH - 0xE446: 0x92AF, //CJK UNIFIED IDEOGRAPH - 0xE447: 0x92B0, //CJK UNIFIED IDEOGRAPH - 0xE448: 0x92B1, //CJK UNIFIED IDEOGRAPH - 0xE449: 0x92B2, //CJK UNIFIED IDEOGRAPH - 0xE44A: 0x92B3, //CJK UNIFIED IDEOGRAPH - 0xE44B: 0x92B4, //CJK UNIFIED IDEOGRAPH - 0xE44C: 0x92B5, //CJK UNIFIED IDEOGRAPH - 0xE44D: 0x92B6, //CJK UNIFIED IDEOGRAPH - 0xE44E: 0x92B7, //CJK UNIFIED IDEOGRAPH - 0xE44F: 0x92B8, //CJK UNIFIED IDEOGRAPH - 0xE450: 0x92B9, //CJK UNIFIED IDEOGRAPH - 0xE451: 0x92BA, //CJK UNIFIED IDEOGRAPH - 0xE452: 0x92BB, //CJK UNIFIED IDEOGRAPH - 0xE453: 0x92BC, //CJK UNIFIED IDEOGRAPH - 0xE454: 0x92BD, //CJK UNIFIED IDEOGRAPH - 0xE455: 0x92BE, //CJK UNIFIED IDEOGRAPH - 0xE456: 0x92BF, //CJK UNIFIED IDEOGRAPH - 0xE457: 0x92C0, //CJK UNIFIED IDEOGRAPH - 0xE458: 0x92C1, //CJK UNIFIED IDEOGRAPH - 0xE459: 0x92C2, //CJK UNIFIED IDEOGRAPH - 0xE45A: 0x92C3, //CJK UNIFIED IDEOGRAPH - 0xE45B: 0x92C4, //CJK UNIFIED IDEOGRAPH - 0xE45C: 0x92C5, //CJK UNIFIED IDEOGRAPH - 0xE45D: 0x92C6, //CJK UNIFIED IDEOGRAPH - 0xE45E: 0x92C7, //CJK UNIFIED IDEOGRAPH - 0xE45F: 0x92C9, //CJK UNIFIED IDEOGRAPH - 0xE460: 0x92CA, //CJK UNIFIED IDEOGRAPH - 0xE461: 0x92CB, //CJK UNIFIED IDEOGRAPH - 0xE462: 0x92CC, //CJK UNIFIED IDEOGRAPH - 0xE463: 0x92CD, //CJK UNIFIED IDEOGRAPH - 0xE464: 0x92CE, //CJK UNIFIED IDEOGRAPH - 0xE465: 0x92CF, //CJK UNIFIED IDEOGRAPH - 0xE466: 0x92D0, //CJK UNIFIED IDEOGRAPH - 0xE467: 0x92D1, //CJK UNIFIED IDEOGRAPH - 0xE468: 0x92D2, //CJK UNIFIED IDEOGRAPH - 0xE469: 0x92D3, //CJK UNIFIED IDEOGRAPH - 0xE46A: 0x92D4, //CJK UNIFIED IDEOGRAPH - 0xE46B: 0x92D5, //CJK UNIFIED IDEOGRAPH - 0xE46C: 0x92D6, //CJK UNIFIED IDEOGRAPH - 0xE46D: 0x92D7, //CJK UNIFIED IDEOGRAPH - 0xE46E: 0x92D8, //CJK UNIFIED IDEOGRAPH - 0xE46F: 0x92D9, //CJK UNIFIED IDEOGRAPH - 0xE470: 0x92DA, //CJK UNIFIED IDEOGRAPH - 0xE471: 0x92DB, //CJK UNIFIED IDEOGRAPH - 0xE472: 0x92DC, //CJK UNIFIED IDEOGRAPH - 0xE473: 0x92DD, //CJK UNIFIED IDEOGRAPH - 0xE474: 0x92DE, //CJK UNIFIED IDEOGRAPH - 0xE475: 0x92DF, //CJK UNIFIED IDEOGRAPH - 0xE476: 0x92E0, //CJK UNIFIED IDEOGRAPH - 0xE477: 0x92E1, //CJK UNIFIED IDEOGRAPH - 0xE478: 0x92E2, //CJK UNIFIED IDEOGRAPH - 0xE479: 0x92E3, //CJK UNIFIED IDEOGRAPH - 0xE47A: 0x92E4, //CJK UNIFIED IDEOGRAPH - 0xE47B: 0x92E5, //CJK UNIFIED IDEOGRAPH - 0xE47C: 0x92E6, //CJK UNIFIED IDEOGRAPH - 0xE47D: 0x92E7, //CJK UNIFIED IDEOGRAPH - 0xE47E: 0x92E8, //CJK UNIFIED IDEOGRAPH - 0xE480: 0x92E9, //CJK UNIFIED IDEOGRAPH - 0xE481: 0x92EA, //CJK UNIFIED IDEOGRAPH - 0xE482: 0x92EB, //CJK UNIFIED IDEOGRAPH - 0xE483: 0x92EC, //CJK UNIFIED IDEOGRAPH - 0xE484: 0x92ED, //CJK UNIFIED IDEOGRAPH - 0xE485: 0x92EE, //CJK UNIFIED IDEOGRAPH - 0xE486: 0x92EF, //CJK UNIFIED IDEOGRAPH - 0xE487: 0x92F0, //CJK UNIFIED IDEOGRAPH - 0xE488: 0x92F1, //CJK UNIFIED IDEOGRAPH - 0xE489: 0x92F2, //CJK UNIFIED IDEOGRAPH - 0xE48A: 0x92F3, //CJK UNIFIED IDEOGRAPH - 0xE48B: 0x92F4, //CJK UNIFIED IDEOGRAPH - 0xE48C: 0x92F5, //CJK UNIFIED IDEOGRAPH - 0xE48D: 0x92F6, //CJK UNIFIED IDEOGRAPH - 0xE48E: 0x92F7, //CJK UNIFIED IDEOGRAPH - 0xE48F: 0x92F8, //CJK UNIFIED IDEOGRAPH - 0xE490: 0x92F9, //CJK UNIFIED IDEOGRAPH - 0xE491: 0x92FA, //CJK UNIFIED IDEOGRAPH - 0xE492: 0x92FB, //CJK UNIFIED IDEOGRAPH - 0xE493: 0x92FC, //CJK UNIFIED IDEOGRAPH - 0xE494: 0x92FD, //CJK UNIFIED IDEOGRAPH - 0xE495: 0x92FE, //CJK UNIFIED IDEOGRAPH - 0xE496: 0x92FF, //CJK UNIFIED IDEOGRAPH - 0xE497: 0x9300, //CJK UNIFIED IDEOGRAPH - 0xE498: 0x9301, //CJK UNIFIED IDEOGRAPH - 0xE499: 0x9302, //CJK UNIFIED IDEOGRAPH - 0xE49A: 0x9303, //CJK UNIFIED IDEOGRAPH - 0xE49B: 0x9304, //CJK UNIFIED IDEOGRAPH - 0xE49C: 0x9305, //CJK UNIFIED IDEOGRAPH - 0xE49D: 0x9306, //CJK UNIFIED IDEOGRAPH - 0xE49E: 0x9307, //CJK UNIFIED IDEOGRAPH - 0xE49F: 0x9308, //CJK UNIFIED IDEOGRAPH - 0xE4A0: 0x9309, //CJK UNIFIED IDEOGRAPH - 0xE4A1: 0x6D39, //CJK UNIFIED IDEOGRAPH - 0xE4A2: 0x6D27, //CJK UNIFIED IDEOGRAPH - 0xE4A3: 0x6D0C, //CJK UNIFIED IDEOGRAPH - 0xE4A4: 0x6D43, //CJK UNIFIED IDEOGRAPH - 0xE4A5: 0x6D48, //CJK UNIFIED IDEOGRAPH - 0xE4A6: 0x6D07, //CJK UNIFIED IDEOGRAPH - 0xE4A7: 0x6D04, //CJK UNIFIED IDEOGRAPH - 0xE4A8: 0x6D19, //CJK UNIFIED IDEOGRAPH - 0xE4A9: 0x6D0E, //CJK UNIFIED IDEOGRAPH - 0xE4AA: 0x6D2B, //CJK UNIFIED IDEOGRAPH - 0xE4AB: 0x6D4D, //CJK UNIFIED IDEOGRAPH - 0xE4AC: 0x6D2E, //CJK UNIFIED IDEOGRAPH - 0xE4AD: 0x6D35, //CJK UNIFIED IDEOGRAPH - 0xE4AE: 0x6D1A, //CJK UNIFIED IDEOGRAPH - 0xE4AF: 0x6D4F, //CJK UNIFIED IDEOGRAPH - 0xE4B0: 0x6D52, //CJK UNIFIED IDEOGRAPH - 0xE4B1: 0x6D54, //CJK UNIFIED IDEOGRAPH - 0xE4B2: 0x6D33, //CJK UNIFIED IDEOGRAPH - 0xE4B3: 0x6D91, //CJK UNIFIED IDEOGRAPH - 0xE4B4: 0x6D6F, //CJK UNIFIED IDEOGRAPH - 0xE4B5: 0x6D9E, //CJK UNIFIED IDEOGRAPH - 0xE4B6: 0x6DA0, //CJK UNIFIED IDEOGRAPH - 0xE4B7: 0x6D5E, //CJK UNIFIED IDEOGRAPH - 0xE4B8: 0x6D93, //CJK UNIFIED IDEOGRAPH - 0xE4B9: 0x6D94, //CJK UNIFIED IDEOGRAPH - 0xE4BA: 0x6D5C, //CJK UNIFIED IDEOGRAPH - 0xE4BB: 0x6D60, //CJK UNIFIED IDEOGRAPH - 0xE4BC: 0x6D7C, //CJK UNIFIED IDEOGRAPH - 0xE4BD: 0x6D63, //CJK UNIFIED IDEOGRAPH - 0xE4BE: 0x6E1A, //CJK UNIFIED IDEOGRAPH - 0xE4BF: 0x6DC7, //CJK UNIFIED IDEOGRAPH - 0xE4C0: 0x6DC5, //CJK UNIFIED IDEOGRAPH - 0xE4C1: 0x6DDE, //CJK UNIFIED IDEOGRAPH - 0xE4C2: 0x6E0E, //CJK UNIFIED IDEOGRAPH - 0xE4C3: 0x6DBF, //CJK UNIFIED IDEOGRAPH - 0xE4C4: 0x6DE0, //CJK UNIFIED IDEOGRAPH - 0xE4C5: 0x6E11, //CJK UNIFIED IDEOGRAPH - 0xE4C6: 0x6DE6, //CJK UNIFIED IDEOGRAPH - 0xE4C7: 0x6DDD, //CJK UNIFIED IDEOGRAPH - 0xE4C8: 0x6DD9, //CJK UNIFIED IDEOGRAPH - 0xE4C9: 0x6E16, //CJK UNIFIED IDEOGRAPH - 0xE4CA: 0x6DAB, //CJK UNIFIED IDEOGRAPH - 0xE4CB: 0x6E0C, //CJK UNIFIED IDEOGRAPH - 0xE4CC: 0x6DAE, //CJK UNIFIED IDEOGRAPH - 0xE4CD: 0x6E2B, //CJK UNIFIED IDEOGRAPH - 0xE4CE: 0x6E6E, //CJK UNIFIED IDEOGRAPH - 0xE4CF: 0x6E4E, //CJK UNIFIED IDEOGRAPH - 0xE4D0: 0x6E6B, //CJK UNIFIED IDEOGRAPH - 0xE4D1: 0x6EB2, //CJK UNIFIED IDEOGRAPH - 0xE4D2: 0x6E5F, //CJK UNIFIED IDEOGRAPH - 0xE4D3: 0x6E86, //CJK UNIFIED IDEOGRAPH - 0xE4D4: 0x6E53, //CJK UNIFIED IDEOGRAPH - 0xE4D5: 0x6E54, //CJK UNIFIED IDEOGRAPH - 0xE4D6: 0x6E32, //CJK UNIFIED IDEOGRAPH - 0xE4D7: 0x6E25, //CJK UNIFIED IDEOGRAPH - 0xE4D8: 0x6E44, //CJK UNIFIED IDEOGRAPH - 0xE4D9: 0x6EDF, //CJK UNIFIED IDEOGRAPH - 0xE4DA: 0x6EB1, //CJK UNIFIED IDEOGRAPH - 0xE4DB: 0x6E98, //CJK UNIFIED IDEOGRAPH - 0xE4DC: 0x6EE0, //CJK UNIFIED IDEOGRAPH - 0xE4DD: 0x6F2D, //CJK UNIFIED IDEOGRAPH - 0xE4DE: 0x6EE2, //CJK UNIFIED IDEOGRAPH - 0xE4DF: 0x6EA5, //CJK UNIFIED IDEOGRAPH - 0xE4E0: 0x6EA7, //CJK UNIFIED IDEOGRAPH - 0xE4E1: 0x6EBD, //CJK UNIFIED IDEOGRAPH - 0xE4E2: 0x6EBB, //CJK UNIFIED IDEOGRAPH - 0xE4E3: 0x6EB7, //CJK UNIFIED IDEOGRAPH - 0xE4E4: 0x6ED7, //CJK UNIFIED IDEOGRAPH - 0xE4E5: 0x6EB4, //CJK UNIFIED IDEOGRAPH - 0xE4E6: 0x6ECF, //CJK UNIFIED IDEOGRAPH - 0xE4E7: 0x6E8F, //CJK UNIFIED IDEOGRAPH - 0xE4E8: 0x6EC2, //CJK UNIFIED IDEOGRAPH - 0xE4E9: 0x6E9F, //CJK UNIFIED IDEOGRAPH - 0xE4EA: 0x6F62, //CJK UNIFIED IDEOGRAPH - 0xE4EB: 0x6F46, //CJK UNIFIED IDEOGRAPH - 0xE4EC: 0x6F47, //CJK UNIFIED IDEOGRAPH - 0xE4ED: 0x6F24, //CJK UNIFIED IDEOGRAPH - 0xE4EE: 0x6F15, //CJK UNIFIED IDEOGRAPH - 0xE4EF: 0x6EF9, //CJK UNIFIED IDEOGRAPH - 0xE4F0: 0x6F2F, //CJK UNIFIED IDEOGRAPH - 0xE4F1: 0x6F36, //CJK UNIFIED IDEOGRAPH - 0xE4F2: 0x6F4B, //CJK UNIFIED IDEOGRAPH - 0xE4F3: 0x6F74, //CJK UNIFIED IDEOGRAPH - 0xE4F4: 0x6F2A, //CJK UNIFIED IDEOGRAPH - 0xE4F5: 0x6F09, //CJK UNIFIED IDEOGRAPH - 0xE4F6: 0x6F29, //CJK UNIFIED IDEOGRAPH - 0xE4F7: 0x6F89, //CJK UNIFIED IDEOGRAPH - 0xE4F8: 0x6F8D, //CJK UNIFIED IDEOGRAPH - 0xE4F9: 0x6F8C, //CJK UNIFIED IDEOGRAPH - 0xE4FA: 0x6F78, //CJK UNIFIED IDEOGRAPH - 0xE4FB: 0x6F72, //CJK UNIFIED IDEOGRAPH - 0xE4FC: 0x6F7C, //CJK UNIFIED IDEOGRAPH - 0xE4FD: 0x6F7A, //CJK UNIFIED IDEOGRAPH - 0xE4FE: 0x6FD1, //CJK UNIFIED IDEOGRAPH - 0xE540: 0x930A, //CJK UNIFIED IDEOGRAPH - 0xE541: 0x930B, //CJK UNIFIED IDEOGRAPH - 0xE542: 0x930C, //CJK UNIFIED IDEOGRAPH - 0xE543: 0x930D, //CJK UNIFIED IDEOGRAPH - 0xE544: 0x930E, //CJK UNIFIED IDEOGRAPH - 0xE545: 0x930F, //CJK UNIFIED IDEOGRAPH - 0xE546: 0x9310, //CJK UNIFIED IDEOGRAPH - 0xE547: 0x9311, //CJK UNIFIED IDEOGRAPH - 0xE548: 0x9312, //CJK UNIFIED IDEOGRAPH - 0xE549: 0x9313, //CJK UNIFIED IDEOGRAPH - 0xE54A: 0x9314, //CJK UNIFIED IDEOGRAPH - 0xE54B: 0x9315, //CJK UNIFIED IDEOGRAPH - 0xE54C: 0x9316, //CJK UNIFIED IDEOGRAPH - 0xE54D: 0x9317, //CJK UNIFIED IDEOGRAPH - 0xE54E: 0x9318, //CJK UNIFIED IDEOGRAPH - 0xE54F: 0x9319, //CJK UNIFIED IDEOGRAPH - 0xE550: 0x931A, //CJK UNIFIED IDEOGRAPH - 0xE551: 0x931B, //CJK UNIFIED IDEOGRAPH - 0xE552: 0x931C, //CJK UNIFIED IDEOGRAPH - 0xE553: 0x931D, //CJK UNIFIED IDEOGRAPH - 0xE554: 0x931E, //CJK UNIFIED IDEOGRAPH - 0xE555: 0x931F, //CJK UNIFIED IDEOGRAPH - 0xE556: 0x9320, //CJK UNIFIED IDEOGRAPH - 0xE557: 0x9321, //CJK UNIFIED IDEOGRAPH - 0xE558: 0x9322, //CJK UNIFIED IDEOGRAPH - 0xE559: 0x9323, //CJK UNIFIED IDEOGRAPH - 0xE55A: 0x9324, //CJK UNIFIED IDEOGRAPH - 0xE55B: 0x9325, //CJK UNIFIED IDEOGRAPH - 0xE55C: 0x9326, //CJK UNIFIED IDEOGRAPH - 0xE55D: 0x9327, //CJK UNIFIED IDEOGRAPH - 0xE55E: 0x9328, //CJK UNIFIED IDEOGRAPH - 0xE55F: 0x9329, //CJK UNIFIED IDEOGRAPH - 0xE560: 0x932A, //CJK UNIFIED IDEOGRAPH - 0xE561: 0x932B, //CJK UNIFIED IDEOGRAPH - 0xE562: 0x932C, //CJK UNIFIED IDEOGRAPH - 0xE563: 0x932D, //CJK UNIFIED IDEOGRAPH - 0xE564: 0x932E, //CJK UNIFIED IDEOGRAPH - 0xE565: 0x932F, //CJK UNIFIED IDEOGRAPH - 0xE566: 0x9330, //CJK UNIFIED IDEOGRAPH - 0xE567: 0x9331, //CJK UNIFIED IDEOGRAPH - 0xE568: 0x9332, //CJK UNIFIED IDEOGRAPH - 0xE569: 0x9333, //CJK UNIFIED IDEOGRAPH - 0xE56A: 0x9334, //CJK UNIFIED IDEOGRAPH - 0xE56B: 0x9335, //CJK UNIFIED IDEOGRAPH - 0xE56C: 0x9336, //CJK UNIFIED IDEOGRAPH - 0xE56D: 0x9337, //CJK UNIFIED IDEOGRAPH - 0xE56E: 0x9338, //CJK UNIFIED IDEOGRAPH - 0xE56F: 0x9339, //CJK UNIFIED IDEOGRAPH - 0xE570: 0x933A, //CJK UNIFIED IDEOGRAPH - 0xE571: 0x933B, //CJK UNIFIED IDEOGRAPH - 0xE572: 0x933C, //CJK UNIFIED IDEOGRAPH - 0xE573: 0x933D, //CJK UNIFIED IDEOGRAPH - 0xE574: 0x933F, //CJK UNIFIED IDEOGRAPH - 0xE575: 0x9340, //CJK UNIFIED IDEOGRAPH - 0xE576: 0x9341, //CJK UNIFIED IDEOGRAPH - 0xE577: 0x9342, //CJK UNIFIED IDEOGRAPH - 0xE578: 0x9343, //CJK UNIFIED IDEOGRAPH - 0xE579: 0x9344, //CJK UNIFIED IDEOGRAPH - 0xE57A: 0x9345, //CJK UNIFIED IDEOGRAPH - 0xE57B: 0x9346, //CJK UNIFIED IDEOGRAPH - 0xE57C: 0x9347, //CJK UNIFIED IDEOGRAPH - 0xE57D: 0x9348, //CJK UNIFIED IDEOGRAPH - 0xE57E: 0x9349, //CJK UNIFIED IDEOGRAPH - 0xE580: 0x934A, //CJK UNIFIED IDEOGRAPH - 0xE581: 0x934B, //CJK UNIFIED IDEOGRAPH - 0xE582: 0x934C, //CJK UNIFIED IDEOGRAPH - 0xE583: 0x934D, //CJK UNIFIED IDEOGRAPH - 0xE584: 0x934E, //CJK UNIFIED IDEOGRAPH - 0xE585: 0x934F, //CJK UNIFIED IDEOGRAPH - 0xE586: 0x9350, //CJK UNIFIED IDEOGRAPH - 0xE587: 0x9351, //CJK UNIFIED IDEOGRAPH - 0xE588: 0x9352, //CJK UNIFIED IDEOGRAPH - 0xE589: 0x9353, //CJK UNIFIED IDEOGRAPH - 0xE58A: 0x9354, //CJK UNIFIED IDEOGRAPH - 0xE58B: 0x9355, //CJK UNIFIED IDEOGRAPH - 0xE58C: 0x9356, //CJK UNIFIED IDEOGRAPH - 0xE58D: 0x9357, //CJK UNIFIED IDEOGRAPH - 0xE58E: 0x9358, //CJK UNIFIED IDEOGRAPH - 0xE58F: 0x9359, //CJK UNIFIED IDEOGRAPH - 0xE590: 0x935A, //CJK UNIFIED IDEOGRAPH - 0xE591: 0x935B, //CJK UNIFIED IDEOGRAPH - 0xE592: 0x935C, //CJK UNIFIED IDEOGRAPH - 0xE593: 0x935D, //CJK UNIFIED IDEOGRAPH - 0xE594: 0x935E, //CJK UNIFIED IDEOGRAPH - 0xE595: 0x935F, //CJK UNIFIED IDEOGRAPH - 0xE596: 0x9360, //CJK UNIFIED IDEOGRAPH - 0xE597: 0x9361, //CJK UNIFIED IDEOGRAPH - 0xE598: 0x9362, //CJK UNIFIED IDEOGRAPH - 0xE599: 0x9363, //CJK UNIFIED IDEOGRAPH - 0xE59A: 0x9364, //CJK UNIFIED IDEOGRAPH - 0xE59B: 0x9365, //CJK UNIFIED IDEOGRAPH - 0xE59C: 0x9366, //CJK UNIFIED IDEOGRAPH - 0xE59D: 0x9367, //CJK UNIFIED IDEOGRAPH - 0xE59E: 0x9368, //CJK UNIFIED IDEOGRAPH - 0xE59F: 0x9369, //CJK UNIFIED IDEOGRAPH - 0xE5A0: 0x936B, //CJK UNIFIED IDEOGRAPH - 0xE5A1: 0x6FC9, //CJK UNIFIED IDEOGRAPH - 0xE5A2: 0x6FA7, //CJK UNIFIED IDEOGRAPH - 0xE5A3: 0x6FB9, //CJK UNIFIED IDEOGRAPH - 0xE5A4: 0x6FB6, //CJK UNIFIED IDEOGRAPH - 0xE5A5: 0x6FC2, //CJK UNIFIED IDEOGRAPH - 0xE5A6: 0x6FE1, //CJK UNIFIED IDEOGRAPH - 0xE5A7: 0x6FEE, //CJK UNIFIED IDEOGRAPH - 0xE5A8: 0x6FDE, //CJK UNIFIED IDEOGRAPH - 0xE5A9: 0x6FE0, //CJK UNIFIED IDEOGRAPH - 0xE5AA: 0x6FEF, //CJK UNIFIED IDEOGRAPH - 0xE5AB: 0x701A, //CJK UNIFIED IDEOGRAPH - 0xE5AC: 0x7023, //CJK UNIFIED IDEOGRAPH - 0xE5AD: 0x701B, //CJK UNIFIED IDEOGRAPH - 0xE5AE: 0x7039, //CJK UNIFIED IDEOGRAPH - 0xE5AF: 0x7035, //CJK UNIFIED IDEOGRAPH - 0xE5B0: 0x704F, //CJK UNIFIED IDEOGRAPH - 0xE5B1: 0x705E, //CJK UNIFIED IDEOGRAPH - 0xE5B2: 0x5B80, //CJK UNIFIED IDEOGRAPH - 0xE5B3: 0x5B84, //CJK UNIFIED IDEOGRAPH - 0xE5B4: 0x5B95, //CJK UNIFIED IDEOGRAPH - 0xE5B5: 0x5B93, //CJK UNIFIED IDEOGRAPH - 0xE5B6: 0x5BA5, //CJK UNIFIED IDEOGRAPH - 0xE5B7: 0x5BB8, //CJK UNIFIED IDEOGRAPH - 0xE5B8: 0x752F, //CJK UNIFIED IDEOGRAPH - 0xE5B9: 0x9A9E, //CJK UNIFIED IDEOGRAPH - 0xE5BA: 0x6434, //CJK UNIFIED IDEOGRAPH - 0xE5BB: 0x5BE4, //CJK UNIFIED IDEOGRAPH - 0xE5BC: 0x5BEE, //CJK UNIFIED IDEOGRAPH - 0xE5BD: 0x8930, //CJK UNIFIED IDEOGRAPH - 0xE5BE: 0x5BF0, //CJK UNIFIED IDEOGRAPH - 0xE5BF: 0x8E47, //CJK UNIFIED IDEOGRAPH - 0xE5C0: 0x8B07, //CJK UNIFIED IDEOGRAPH - 0xE5C1: 0x8FB6, //CJK UNIFIED IDEOGRAPH - 0xE5C2: 0x8FD3, //CJK UNIFIED IDEOGRAPH - 0xE5C3: 0x8FD5, //CJK UNIFIED IDEOGRAPH - 0xE5C4: 0x8FE5, //CJK UNIFIED IDEOGRAPH - 0xE5C5: 0x8FEE, //CJK UNIFIED IDEOGRAPH - 0xE5C6: 0x8FE4, //CJK UNIFIED IDEOGRAPH - 0xE5C7: 0x8FE9, //CJK UNIFIED IDEOGRAPH - 0xE5C8: 0x8FE6, //CJK UNIFIED IDEOGRAPH - 0xE5C9: 0x8FF3, //CJK UNIFIED IDEOGRAPH - 0xE5CA: 0x8FE8, //CJK UNIFIED IDEOGRAPH - 0xE5CB: 0x9005, //CJK UNIFIED IDEOGRAPH - 0xE5CC: 0x9004, //CJK UNIFIED IDEOGRAPH - 0xE5CD: 0x900B, //CJK UNIFIED IDEOGRAPH - 0xE5CE: 0x9026, //CJK UNIFIED IDEOGRAPH - 0xE5CF: 0x9011, //CJK UNIFIED IDEOGRAPH - 0xE5D0: 0x900D, //CJK UNIFIED IDEOGRAPH - 0xE5D1: 0x9016, //CJK UNIFIED IDEOGRAPH - 0xE5D2: 0x9021, //CJK UNIFIED IDEOGRAPH - 0xE5D3: 0x9035, //CJK UNIFIED IDEOGRAPH - 0xE5D4: 0x9036, //CJK UNIFIED IDEOGRAPH - 0xE5D5: 0x902D, //CJK UNIFIED IDEOGRAPH - 0xE5D6: 0x902F, //CJK UNIFIED IDEOGRAPH - 0xE5D7: 0x9044, //CJK UNIFIED IDEOGRAPH - 0xE5D8: 0x9051, //CJK UNIFIED IDEOGRAPH - 0xE5D9: 0x9052, //CJK UNIFIED IDEOGRAPH - 0xE5DA: 0x9050, //CJK UNIFIED IDEOGRAPH - 0xE5DB: 0x9068, //CJK UNIFIED IDEOGRAPH - 0xE5DC: 0x9058, //CJK UNIFIED IDEOGRAPH - 0xE5DD: 0x9062, //CJK UNIFIED IDEOGRAPH - 0xE5DE: 0x905B, //CJK UNIFIED IDEOGRAPH - 0xE5DF: 0x66B9, //CJK UNIFIED IDEOGRAPH - 0xE5E0: 0x9074, //CJK UNIFIED IDEOGRAPH - 0xE5E1: 0x907D, //CJK UNIFIED IDEOGRAPH - 0xE5E2: 0x9082, //CJK UNIFIED IDEOGRAPH - 0xE5E3: 0x9088, //CJK UNIFIED IDEOGRAPH - 0xE5E4: 0x9083, //CJK UNIFIED IDEOGRAPH - 0xE5E5: 0x908B, //CJK UNIFIED IDEOGRAPH - 0xE5E6: 0x5F50, //CJK UNIFIED IDEOGRAPH - 0xE5E7: 0x5F57, //CJK UNIFIED IDEOGRAPH - 0xE5E8: 0x5F56, //CJK UNIFIED IDEOGRAPH - 0xE5E9: 0x5F58, //CJK UNIFIED IDEOGRAPH - 0xE5EA: 0x5C3B, //CJK UNIFIED IDEOGRAPH - 0xE5EB: 0x54AB, //CJK UNIFIED IDEOGRAPH - 0xE5EC: 0x5C50, //CJK UNIFIED IDEOGRAPH - 0xE5ED: 0x5C59, //CJK UNIFIED IDEOGRAPH - 0xE5EE: 0x5B71, //CJK UNIFIED IDEOGRAPH - 0xE5EF: 0x5C63, //CJK UNIFIED IDEOGRAPH - 0xE5F0: 0x5C66, //CJK UNIFIED IDEOGRAPH - 0xE5F1: 0x7FBC, //CJK UNIFIED IDEOGRAPH - 0xE5F2: 0x5F2A, //CJK UNIFIED IDEOGRAPH - 0xE5F3: 0x5F29, //CJK UNIFIED IDEOGRAPH - 0xE5F4: 0x5F2D, //CJK UNIFIED IDEOGRAPH - 0xE5F5: 0x8274, //CJK UNIFIED IDEOGRAPH - 0xE5F6: 0x5F3C, //CJK UNIFIED IDEOGRAPH - 0xE5F7: 0x9B3B, //CJK UNIFIED IDEOGRAPH - 0xE5F8: 0x5C6E, //CJK UNIFIED IDEOGRAPH - 0xE5F9: 0x5981, //CJK UNIFIED IDEOGRAPH - 0xE5FA: 0x5983, //CJK UNIFIED IDEOGRAPH - 0xE5FB: 0x598D, //CJK UNIFIED IDEOGRAPH - 0xE5FC: 0x59A9, //CJK UNIFIED IDEOGRAPH - 0xE5FD: 0x59AA, //CJK UNIFIED IDEOGRAPH - 0xE5FE: 0x59A3, //CJK UNIFIED IDEOGRAPH - 0xE640: 0x936C, //CJK UNIFIED IDEOGRAPH - 0xE641: 0x936D, //CJK UNIFIED IDEOGRAPH - 0xE642: 0x936E, //CJK UNIFIED IDEOGRAPH - 0xE643: 0x936F, //CJK UNIFIED IDEOGRAPH - 0xE644: 0x9370, //CJK UNIFIED IDEOGRAPH - 0xE645: 0x9371, //CJK UNIFIED IDEOGRAPH - 0xE646: 0x9372, //CJK UNIFIED IDEOGRAPH - 0xE647: 0x9373, //CJK UNIFIED IDEOGRAPH - 0xE648: 0x9374, //CJK UNIFIED IDEOGRAPH - 0xE649: 0x9375, //CJK UNIFIED IDEOGRAPH - 0xE64A: 0x9376, //CJK UNIFIED IDEOGRAPH - 0xE64B: 0x9377, //CJK UNIFIED IDEOGRAPH - 0xE64C: 0x9378, //CJK UNIFIED IDEOGRAPH - 0xE64D: 0x9379, //CJK UNIFIED IDEOGRAPH - 0xE64E: 0x937A, //CJK UNIFIED IDEOGRAPH - 0xE64F: 0x937B, //CJK UNIFIED IDEOGRAPH - 0xE650: 0x937C, //CJK UNIFIED IDEOGRAPH - 0xE651: 0x937D, //CJK UNIFIED IDEOGRAPH - 0xE652: 0x937E, //CJK UNIFIED IDEOGRAPH - 0xE653: 0x937F, //CJK UNIFIED IDEOGRAPH - 0xE654: 0x9380, //CJK UNIFIED IDEOGRAPH - 0xE655: 0x9381, //CJK UNIFIED IDEOGRAPH - 0xE656: 0x9382, //CJK UNIFIED IDEOGRAPH - 0xE657: 0x9383, //CJK UNIFIED IDEOGRAPH - 0xE658: 0x9384, //CJK UNIFIED IDEOGRAPH - 0xE659: 0x9385, //CJK UNIFIED IDEOGRAPH - 0xE65A: 0x9386, //CJK UNIFIED IDEOGRAPH - 0xE65B: 0x9387, //CJK UNIFIED IDEOGRAPH - 0xE65C: 0x9388, //CJK UNIFIED IDEOGRAPH - 0xE65D: 0x9389, //CJK UNIFIED IDEOGRAPH - 0xE65E: 0x938A, //CJK UNIFIED IDEOGRAPH - 0xE65F: 0x938B, //CJK UNIFIED IDEOGRAPH - 0xE660: 0x938C, //CJK UNIFIED IDEOGRAPH - 0xE661: 0x938D, //CJK UNIFIED IDEOGRAPH - 0xE662: 0x938E, //CJK UNIFIED IDEOGRAPH - 0xE663: 0x9390, //CJK UNIFIED IDEOGRAPH - 0xE664: 0x9391, //CJK UNIFIED IDEOGRAPH - 0xE665: 0x9392, //CJK UNIFIED IDEOGRAPH - 0xE666: 0x9393, //CJK UNIFIED IDEOGRAPH - 0xE667: 0x9394, //CJK UNIFIED IDEOGRAPH - 0xE668: 0x9395, //CJK UNIFIED IDEOGRAPH - 0xE669: 0x9396, //CJK UNIFIED IDEOGRAPH - 0xE66A: 0x9397, //CJK UNIFIED IDEOGRAPH - 0xE66B: 0x9398, //CJK UNIFIED IDEOGRAPH - 0xE66C: 0x9399, //CJK UNIFIED IDEOGRAPH - 0xE66D: 0x939A, //CJK UNIFIED IDEOGRAPH - 0xE66E: 0x939B, //CJK UNIFIED IDEOGRAPH - 0xE66F: 0x939C, //CJK UNIFIED IDEOGRAPH - 0xE670: 0x939D, //CJK UNIFIED IDEOGRAPH - 0xE671: 0x939E, //CJK UNIFIED IDEOGRAPH - 0xE672: 0x939F, //CJK UNIFIED IDEOGRAPH - 0xE673: 0x93A0, //CJK UNIFIED IDEOGRAPH - 0xE674: 0x93A1, //CJK UNIFIED IDEOGRAPH - 0xE675: 0x93A2, //CJK UNIFIED IDEOGRAPH - 0xE676: 0x93A3, //CJK UNIFIED IDEOGRAPH - 0xE677: 0x93A4, //CJK UNIFIED IDEOGRAPH - 0xE678: 0x93A5, //CJK UNIFIED IDEOGRAPH - 0xE679: 0x93A6, //CJK UNIFIED IDEOGRAPH - 0xE67A: 0x93A7, //CJK UNIFIED IDEOGRAPH - 0xE67B: 0x93A8, //CJK UNIFIED IDEOGRAPH - 0xE67C: 0x93A9, //CJK UNIFIED IDEOGRAPH - 0xE67D: 0x93AA, //CJK UNIFIED IDEOGRAPH - 0xE67E: 0x93AB, //CJK UNIFIED IDEOGRAPH - 0xE680: 0x93AC, //CJK UNIFIED IDEOGRAPH - 0xE681: 0x93AD, //CJK UNIFIED IDEOGRAPH - 0xE682: 0x93AE, //CJK UNIFIED IDEOGRAPH - 0xE683: 0x93AF, //CJK UNIFIED IDEOGRAPH - 0xE684: 0x93B0, //CJK UNIFIED IDEOGRAPH - 0xE685: 0x93B1, //CJK UNIFIED IDEOGRAPH - 0xE686: 0x93B2, //CJK UNIFIED IDEOGRAPH - 0xE687: 0x93B3, //CJK UNIFIED IDEOGRAPH - 0xE688: 0x93B4, //CJK UNIFIED IDEOGRAPH - 0xE689: 0x93B5, //CJK UNIFIED IDEOGRAPH - 0xE68A: 0x93B6, //CJK UNIFIED IDEOGRAPH - 0xE68B: 0x93B7, //CJK UNIFIED IDEOGRAPH - 0xE68C: 0x93B8, //CJK UNIFIED IDEOGRAPH - 0xE68D: 0x93B9, //CJK UNIFIED IDEOGRAPH - 0xE68E: 0x93BA, //CJK UNIFIED IDEOGRAPH - 0xE68F: 0x93BB, //CJK UNIFIED IDEOGRAPH - 0xE690: 0x93BC, //CJK UNIFIED IDEOGRAPH - 0xE691: 0x93BD, //CJK UNIFIED IDEOGRAPH - 0xE692: 0x93BE, //CJK UNIFIED IDEOGRAPH - 0xE693: 0x93BF, //CJK UNIFIED IDEOGRAPH - 0xE694: 0x93C0, //CJK UNIFIED IDEOGRAPH - 0xE695: 0x93C1, //CJK UNIFIED IDEOGRAPH - 0xE696: 0x93C2, //CJK UNIFIED IDEOGRAPH - 0xE697: 0x93C3, //CJK UNIFIED IDEOGRAPH - 0xE698: 0x93C4, //CJK UNIFIED IDEOGRAPH - 0xE699: 0x93C5, //CJK UNIFIED IDEOGRAPH - 0xE69A: 0x93C6, //CJK UNIFIED IDEOGRAPH - 0xE69B: 0x93C7, //CJK UNIFIED IDEOGRAPH - 0xE69C: 0x93C8, //CJK UNIFIED IDEOGRAPH - 0xE69D: 0x93C9, //CJK UNIFIED IDEOGRAPH - 0xE69E: 0x93CB, //CJK UNIFIED IDEOGRAPH - 0xE69F: 0x93CC, //CJK UNIFIED IDEOGRAPH - 0xE6A0: 0x93CD, //CJK UNIFIED IDEOGRAPH - 0xE6A1: 0x5997, //CJK UNIFIED IDEOGRAPH - 0xE6A2: 0x59CA, //CJK UNIFIED IDEOGRAPH - 0xE6A3: 0x59AB, //CJK UNIFIED IDEOGRAPH - 0xE6A4: 0x599E, //CJK UNIFIED IDEOGRAPH - 0xE6A5: 0x59A4, //CJK UNIFIED IDEOGRAPH - 0xE6A6: 0x59D2, //CJK UNIFIED IDEOGRAPH - 0xE6A7: 0x59B2, //CJK UNIFIED IDEOGRAPH - 0xE6A8: 0x59AF, //CJK UNIFIED IDEOGRAPH - 0xE6A9: 0x59D7, //CJK UNIFIED IDEOGRAPH - 0xE6AA: 0x59BE, //CJK UNIFIED IDEOGRAPH - 0xE6AB: 0x5A05, //CJK UNIFIED IDEOGRAPH - 0xE6AC: 0x5A06, //CJK UNIFIED IDEOGRAPH - 0xE6AD: 0x59DD, //CJK UNIFIED IDEOGRAPH - 0xE6AE: 0x5A08, //CJK UNIFIED IDEOGRAPH - 0xE6AF: 0x59E3, //CJK UNIFIED IDEOGRAPH - 0xE6B0: 0x59D8, //CJK UNIFIED IDEOGRAPH - 0xE6B1: 0x59F9, //CJK UNIFIED IDEOGRAPH - 0xE6B2: 0x5A0C, //CJK UNIFIED IDEOGRAPH - 0xE6B3: 0x5A09, //CJK UNIFIED IDEOGRAPH - 0xE6B4: 0x5A32, //CJK UNIFIED IDEOGRAPH - 0xE6B5: 0x5A34, //CJK UNIFIED IDEOGRAPH - 0xE6B6: 0x5A11, //CJK UNIFIED IDEOGRAPH - 0xE6B7: 0x5A23, //CJK UNIFIED IDEOGRAPH - 0xE6B8: 0x5A13, //CJK UNIFIED IDEOGRAPH - 0xE6B9: 0x5A40, //CJK UNIFIED IDEOGRAPH - 0xE6BA: 0x5A67, //CJK UNIFIED IDEOGRAPH - 0xE6BB: 0x5A4A, //CJK UNIFIED IDEOGRAPH - 0xE6BC: 0x5A55, //CJK UNIFIED IDEOGRAPH - 0xE6BD: 0x5A3C, //CJK UNIFIED IDEOGRAPH - 0xE6BE: 0x5A62, //CJK UNIFIED IDEOGRAPH - 0xE6BF: 0x5A75, //CJK UNIFIED IDEOGRAPH - 0xE6C0: 0x80EC, //CJK UNIFIED IDEOGRAPH - 0xE6C1: 0x5AAA, //CJK UNIFIED IDEOGRAPH - 0xE6C2: 0x5A9B, //CJK UNIFIED IDEOGRAPH - 0xE6C3: 0x5A77, //CJK UNIFIED IDEOGRAPH - 0xE6C4: 0x5A7A, //CJK UNIFIED IDEOGRAPH - 0xE6C5: 0x5ABE, //CJK UNIFIED IDEOGRAPH - 0xE6C6: 0x5AEB, //CJK UNIFIED IDEOGRAPH - 0xE6C7: 0x5AB2, //CJK UNIFIED IDEOGRAPH - 0xE6C8: 0x5AD2, //CJK UNIFIED IDEOGRAPH - 0xE6C9: 0x5AD4, //CJK UNIFIED IDEOGRAPH - 0xE6CA: 0x5AB8, //CJK UNIFIED IDEOGRAPH - 0xE6CB: 0x5AE0, //CJK UNIFIED IDEOGRAPH - 0xE6CC: 0x5AE3, //CJK UNIFIED IDEOGRAPH - 0xE6CD: 0x5AF1, //CJK UNIFIED IDEOGRAPH - 0xE6CE: 0x5AD6, //CJK UNIFIED IDEOGRAPH - 0xE6CF: 0x5AE6, //CJK UNIFIED IDEOGRAPH - 0xE6D0: 0x5AD8, //CJK UNIFIED IDEOGRAPH - 0xE6D1: 0x5ADC, //CJK UNIFIED IDEOGRAPH - 0xE6D2: 0x5B09, //CJK UNIFIED IDEOGRAPH - 0xE6D3: 0x5B17, //CJK UNIFIED IDEOGRAPH - 0xE6D4: 0x5B16, //CJK UNIFIED IDEOGRAPH - 0xE6D5: 0x5B32, //CJK UNIFIED IDEOGRAPH - 0xE6D6: 0x5B37, //CJK UNIFIED IDEOGRAPH - 0xE6D7: 0x5B40, //CJK UNIFIED IDEOGRAPH - 0xE6D8: 0x5C15, //CJK UNIFIED IDEOGRAPH - 0xE6D9: 0x5C1C, //CJK UNIFIED IDEOGRAPH - 0xE6DA: 0x5B5A, //CJK UNIFIED IDEOGRAPH - 0xE6DB: 0x5B65, //CJK UNIFIED IDEOGRAPH - 0xE6DC: 0x5B73, //CJK UNIFIED IDEOGRAPH - 0xE6DD: 0x5B51, //CJK UNIFIED IDEOGRAPH - 0xE6DE: 0x5B53, //CJK UNIFIED IDEOGRAPH - 0xE6DF: 0x5B62, //CJK UNIFIED IDEOGRAPH - 0xE6E0: 0x9A75, //CJK UNIFIED IDEOGRAPH - 0xE6E1: 0x9A77, //CJK UNIFIED IDEOGRAPH - 0xE6E2: 0x9A78, //CJK UNIFIED IDEOGRAPH - 0xE6E3: 0x9A7A, //CJK UNIFIED IDEOGRAPH - 0xE6E4: 0x9A7F, //CJK UNIFIED IDEOGRAPH - 0xE6E5: 0x9A7D, //CJK UNIFIED IDEOGRAPH - 0xE6E6: 0x9A80, //CJK UNIFIED IDEOGRAPH - 0xE6E7: 0x9A81, //CJK UNIFIED IDEOGRAPH - 0xE6E8: 0x9A85, //CJK UNIFIED IDEOGRAPH - 0xE6E9: 0x9A88, //CJK UNIFIED IDEOGRAPH - 0xE6EA: 0x9A8A, //CJK UNIFIED IDEOGRAPH - 0xE6EB: 0x9A90, //CJK UNIFIED IDEOGRAPH - 0xE6EC: 0x9A92, //CJK UNIFIED IDEOGRAPH - 0xE6ED: 0x9A93, //CJK UNIFIED IDEOGRAPH - 0xE6EE: 0x9A96, //CJK UNIFIED IDEOGRAPH - 0xE6EF: 0x9A98, //CJK UNIFIED IDEOGRAPH - 0xE6F0: 0x9A9B, //CJK UNIFIED IDEOGRAPH - 0xE6F1: 0x9A9C, //CJK UNIFIED IDEOGRAPH - 0xE6F2: 0x9A9D, //CJK UNIFIED IDEOGRAPH - 0xE6F3: 0x9A9F, //CJK UNIFIED IDEOGRAPH - 0xE6F4: 0x9AA0, //CJK UNIFIED IDEOGRAPH - 0xE6F5: 0x9AA2, //CJK UNIFIED IDEOGRAPH - 0xE6F6: 0x9AA3, //CJK UNIFIED IDEOGRAPH - 0xE6F7: 0x9AA5, //CJK UNIFIED IDEOGRAPH - 0xE6F8: 0x9AA7, //CJK UNIFIED IDEOGRAPH - 0xE6F9: 0x7E9F, //CJK UNIFIED IDEOGRAPH - 0xE6FA: 0x7EA1, //CJK UNIFIED IDEOGRAPH - 0xE6FB: 0x7EA3, //CJK UNIFIED IDEOGRAPH - 0xE6FC: 0x7EA5, //CJK UNIFIED IDEOGRAPH - 0xE6FD: 0x7EA8, //CJK UNIFIED IDEOGRAPH - 0xE6FE: 0x7EA9, //CJK UNIFIED IDEOGRAPH - 0xE740: 0x93CE, //CJK UNIFIED IDEOGRAPH - 0xE741: 0x93CF, //CJK UNIFIED IDEOGRAPH - 0xE742: 0x93D0, //CJK UNIFIED IDEOGRAPH - 0xE743: 0x93D1, //CJK UNIFIED IDEOGRAPH - 0xE744: 0x93D2, //CJK UNIFIED IDEOGRAPH - 0xE745: 0x93D3, //CJK UNIFIED IDEOGRAPH - 0xE746: 0x93D4, //CJK UNIFIED IDEOGRAPH - 0xE747: 0x93D5, //CJK UNIFIED IDEOGRAPH - 0xE748: 0x93D7, //CJK UNIFIED IDEOGRAPH - 0xE749: 0x93D8, //CJK UNIFIED IDEOGRAPH - 0xE74A: 0x93D9, //CJK UNIFIED IDEOGRAPH - 0xE74B: 0x93DA, //CJK UNIFIED IDEOGRAPH - 0xE74C: 0x93DB, //CJK UNIFIED IDEOGRAPH - 0xE74D: 0x93DC, //CJK UNIFIED IDEOGRAPH - 0xE74E: 0x93DD, //CJK UNIFIED IDEOGRAPH - 0xE74F: 0x93DE, //CJK UNIFIED IDEOGRAPH - 0xE750: 0x93DF, //CJK UNIFIED IDEOGRAPH - 0xE751: 0x93E0, //CJK UNIFIED IDEOGRAPH - 0xE752: 0x93E1, //CJK UNIFIED IDEOGRAPH - 0xE753: 0x93E2, //CJK UNIFIED IDEOGRAPH - 0xE754: 0x93E3, //CJK UNIFIED IDEOGRAPH - 0xE755: 0x93E4, //CJK UNIFIED IDEOGRAPH - 0xE756: 0x93E5, //CJK UNIFIED IDEOGRAPH - 0xE757: 0x93E6, //CJK UNIFIED IDEOGRAPH - 0xE758: 0x93E7, //CJK UNIFIED IDEOGRAPH - 0xE759: 0x93E8, //CJK UNIFIED IDEOGRAPH - 0xE75A: 0x93E9, //CJK UNIFIED IDEOGRAPH - 0xE75B: 0x93EA, //CJK UNIFIED IDEOGRAPH - 0xE75C: 0x93EB, //CJK UNIFIED IDEOGRAPH - 0xE75D: 0x93EC, //CJK UNIFIED IDEOGRAPH - 0xE75E: 0x93ED, //CJK UNIFIED IDEOGRAPH - 0xE75F: 0x93EE, //CJK UNIFIED IDEOGRAPH - 0xE760: 0x93EF, //CJK UNIFIED IDEOGRAPH - 0xE761: 0x93F0, //CJK UNIFIED IDEOGRAPH - 0xE762: 0x93F1, //CJK UNIFIED IDEOGRAPH - 0xE763: 0x93F2, //CJK UNIFIED IDEOGRAPH - 0xE764: 0x93F3, //CJK UNIFIED IDEOGRAPH - 0xE765: 0x93F4, //CJK UNIFIED IDEOGRAPH - 0xE766: 0x93F5, //CJK UNIFIED IDEOGRAPH - 0xE767: 0x93F6, //CJK UNIFIED IDEOGRAPH - 0xE768: 0x93F7, //CJK UNIFIED IDEOGRAPH - 0xE769: 0x93F8, //CJK UNIFIED IDEOGRAPH - 0xE76A: 0x93F9, //CJK UNIFIED IDEOGRAPH - 0xE76B: 0x93FA, //CJK UNIFIED IDEOGRAPH - 0xE76C: 0x93FB, //CJK UNIFIED IDEOGRAPH - 0xE76D: 0x93FC, //CJK UNIFIED IDEOGRAPH - 0xE76E: 0x93FD, //CJK UNIFIED IDEOGRAPH - 0xE76F: 0x93FE, //CJK UNIFIED IDEOGRAPH - 0xE770: 0x93FF, //CJK UNIFIED IDEOGRAPH - 0xE771: 0x9400, //CJK UNIFIED IDEOGRAPH - 0xE772: 0x9401, //CJK UNIFIED IDEOGRAPH - 0xE773: 0x9402, //CJK UNIFIED IDEOGRAPH - 0xE774: 0x9403, //CJK UNIFIED IDEOGRAPH - 0xE775: 0x9404, //CJK UNIFIED IDEOGRAPH - 0xE776: 0x9405, //CJK UNIFIED IDEOGRAPH - 0xE777: 0x9406, //CJK UNIFIED IDEOGRAPH - 0xE778: 0x9407, //CJK UNIFIED IDEOGRAPH - 0xE779: 0x9408, //CJK UNIFIED IDEOGRAPH - 0xE77A: 0x9409, //CJK UNIFIED IDEOGRAPH - 0xE77B: 0x940A, //CJK UNIFIED IDEOGRAPH - 0xE77C: 0x940B, //CJK UNIFIED IDEOGRAPH - 0xE77D: 0x940C, //CJK UNIFIED IDEOGRAPH - 0xE77E: 0x940D, //CJK UNIFIED IDEOGRAPH - 0xE780: 0x940E, //CJK UNIFIED IDEOGRAPH - 0xE781: 0x940F, //CJK UNIFIED IDEOGRAPH - 0xE782: 0x9410, //CJK UNIFIED IDEOGRAPH - 0xE783: 0x9411, //CJK UNIFIED IDEOGRAPH - 0xE784: 0x9412, //CJK UNIFIED IDEOGRAPH - 0xE785: 0x9413, //CJK UNIFIED IDEOGRAPH - 0xE786: 0x9414, //CJK UNIFIED IDEOGRAPH - 0xE787: 0x9415, //CJK UNIFIED IDEOGRAPH - 0xE788: 0x9416, //CJK UNIFIED IDEOGRAPH - 0xE789: 0x9417, //CJK UNIFIED IDEOGRAPH - 0xE78A: 0x9418, //CJK UNIFIED IDEOGRAPH - 0xE78B: 0x9419, //CJK UNIFIED IDEOGRAPH - 0xE78C: 0x941A, //CJK UNIFIED IDEOGRAPH - 0xE78D: 0x941B, //CJK UNIFIED IDEOGRAPH - 0xE78E: 0x941C, //CJK UNIFIED IDEOGRAPH - 0xE78F: 0x941D, //CJK UNIFIED IDEOGRAPH - 0xE790: 0x941E, //CJK UNIFIED IDEOGRAPH - 0xE791: 0x941F, //CJK UNIFIED IDEOGRAPH - 0xE792: 0x9420, //CJK UNIFIED IDEOGRAPH - 0xE793: 0x9421, //CJK UNIFIED IDEOGRAPH - 0xE794: 0x9422, //CJK UNIFIED IDEOGRAPH - 0xE795: 0x9423, //CJK UNIFIED IDEOGRAPH - 0xE796: 0x9424, //CJK UNIFIED IDEOGRAPH - 0xE797: 0x9425, //CJK UNIFIED IDEOGRAPH - 0xE798: 0x9426, //CJK UNIFIED IDEOGRAPH - 0xE799: 0x9427, //CJK UNIFIED IDEOGRAPH - 0xE79A: 0x9428, //CJK UNIFIED IDEOGRAPH - 0xE79B: 0x9429, //CJK UNIFIED IDEOGRAPH - 0xE79C: 0x942A, //CJK UNIFIED IDEOGRAPH - 0xE79D: 0x942B, //CJK UNIFIED IDEOGRAPH - 0xE79E: 0x942C, //CJK UNIFIED IDEOGRAPH - 0xE79F: 0x942D, //CJK UNIFIED IDEOGRAPH - 0xE7A0: 0x942E, //CJK UNIFIED IDEOGRAPH - 0xE7A1: 0x7EAD, //CJK UNIFIED IDEOGRAPH - 0xE7A2: 0x7EB0, //CJK UNIFIED IDEOGRAPH - 0xE7A3: 0x7EBE, //CJK UNIFIED IDEOGRAPH - 0xE7A4: 0x7EC0, //CJK UNIFIED IDEOGRAPH - 0xE7A5: 0x7EC1, //CJK UNIFIED IDEOGRAPH - 0xE7A6: 0x7EC2, //CJK UNIFIED IDEOGRAPH - 0xE7A7: 0x7EC9, //CJK UNIFIED IDEOGRAPH - 0xE7A8: 0x7ECB, //CJK UNIFIED IDEOGRAPH - 0xE7A9: 0x7ECC, //CJK UNIFIED IDEOGRAPH - 0xE7AA: 0x7ED0, //CJK UNIFIED IDEOGRAPH - 0xE7AB: 0x7ED4, //CJK UNIFIED IDEOGRAPH - 0xE7AC: 0x7ED7, //CJK UNIFIED IDEOGRAPH - 0xE7AD: 0x7EDB, //CJK UNIFIED IDEOGRAPH - 0xE7AE: 0x7EE0, //CJK UNIFIED IDEOGRAPH - 0xE7AF: 0x7EE1, //CJK UNIFIED IDEOGRAPH - 0xE7B0: 0x7EE8, //CJK UNIFIED IDEOGRAPH - 0xE7B1: 0x7EEB, //CJK UNIFIED IDEOGRAPH - 0xE7B2: 0x7EEE, //CJK UNIFIED IDEOGRAPH - 0xE7B3: 0x7EEF, //CJK UNIFIED IDEOGRAPH - 0xE7B4: 0x7EF1, //CJK UNIFIED IDEOGRAPH - 0xE7B5: 0x7EF2, //CJK UNIFIED IDEOGRAPH - 0xE7B6: 0x7F0D, //CJK UNIFIED IDEOGRAPH - 0xE7B7: 0x7EF6, //CJK UNIFIED IDEOGRAPH - 0xE7B8: 0x7EFA, //CJK UNIFIED IDEOGRAPH - 0xE7B9: 0x7EFB, //CJK UNIFIED IDEOGRAPH - 0xE7BA: 0x7EFE, //CJK UNIFIED IDEOGRAPH - 0xE7BB: 0x7F01, //CJK UNIFIED IDEOGRAPH - 0xE7BC: 0x7F02, //CJK UNIFIED IDEOGRAPH - 0xE7BD: 0x7F03, //CJK UNIFIED IDEOGRAPH - 0xE7BE: 0x7F07, //CJK UNIFIED IDEOGRAPH - 0xE7BF: 0x7F08, //CJK UNIFIED IDEOGRAPH - 0xE7C0: 0x7F0B, //CJK UNIFIED IDEOGRAPH - 0xE7C1: 0x7F0C, //CJK UNIFIED IDEOGRAPH - 0xE7C2: 0x7F0F, //CJK UNIFIED IDEOGRAPH - 0xE7C3: 0x7F11, //CJK UNIFIED IDEOGRAPH - 0xE7C4: 0x7F12, //CJK UNIFIED IDEOGRAPH - 0xE7C5: 0x7F17, //CJK UNIFIED IDEOGRAPH - 0xE7C6: 0x7F19, //CJK UNIFIED IDEOGRAPH - 0xE7C7: 0x7F1C, //CJK UNIFIED IDEOGRAPH - 0xE7C8: 0x7F1B, //CJK UNIFIED IDEOGRAPH - 0xE7C9: 0x7F1F, //CJK UNIFIED IDEOGRAPH - 0xE7CA: 0x7F21, //CJK UNIFIED IDEOGRAPH - 0xE7CB: 0x7F22, //CJK UNIFIED IDEOGRAPH - 0xE7CC: 0x7F23, //CJK UNIFIED IDEOGRAPH - 0xE7CD: 0x7F24, //CJK UNIFIED IDEOGRAPH - 0xE7CE: 0x7F25, //CJK UNIFIED IDEOGRAPH - 0xE7CF: 0x7F26, //CJK UNIFIED IDEOGRAPH - 0xE7D0: 0x7F27, //CJK UNIFIED IDEOGRAPH - 0xE7D1: 0x7F2A, //CJK UNIFIED IDEOGRAPH - 0xE7D2: 0x7F2B, //CJK UNIFIED IDEOGRAPH - 0xE7D3: 0x7F2C, //CJK UNIFIED IDEOGRAPH - 0xE7D4: 0x7F2D, //CJK UNIFIED IDEOGRAPH - 0xE7D5: 0x7F2F, //CJK UNIFIED IDEOGRAPH - 0xE7D6: 0x7F30, //CJK UNIFIED IDEOGRAPH - 0xE7D7: 0x7F31, //CJK UNIFIED IDEOGRAPH - 0xE7D8: 0x7F32, //CJK UNIFIED IDEOGRAPH - 0xE7D9: 0x7F33, //CJK UNIFIED IDEOGRAPH - 0xE7DA: 0x7F35, //CJK UNIFIED IDEOGRAPH - 0xE7DB: 0x5E7A, //CJK UNIFIED IDEOGRAPH - 0xE7DC: 0x757F, //CJK UNIFIED IDEOGRAPH - 0xE7DD: 0x5DDB, //CJK UNIFIED IDEOGRAPH - 0xE7DE: 0x753E, //CJK UNIFIED IDEOGRAPH - 0xE7DF: 0x9095, //CJK UNIFIED IDEOGRAPH - 0xE7E0: 0x738E, //CJK UNIFIED IDEOGRAPH - 0xE7E1: 0x7391, //CJK UNIFIED IDEOGRAPH - 0xE7E2: 0x73AE, //CJK UNIFIED IDEOGRAPH - 0xE7E3: 0x73A2, //CJK UNIFIED IDEOGRAPH - 0xE7E4: 0x739F, //CJK UNIFIED IDEOGRAPH - 0xE7E5: 0x73CF, //CJK UNIFIED IDEOGRAPH - 0xE7E6: 0x73C2, //CJK UNIFIED IDEOGRAPH - 0xE7E7: 0x73D1, //CJK UNIFIED IDEOGRAPH - 0xE7E8: 0x73B7, //CJK UNIFIED IDEOGRAPH - 0xE7E9: 0x73B3, //CJK UNIFIED IDEOGRAPH - 0xE7EA: 0x73C0, //CJK UNIFIED IDEOGRAPH - 0xE7EB: 0x73C9, //CJK UNIFIED IDEOGRAPH - 0xE7EC: 0x73C8, //CJK UNIFIED IDEOGRAPH - 0xE7ED: 0x73E5, //CJK UNIFIED IDEOGRAPH - 0xE7EE: 0x73D9, //CJK UNIFIED IDEOGRAPH - 0xE7EF: 0x987C, //CJK UNIFIED IDEOGRAPH - 0xE7F0: 0x740A, //CJK UNIFIED IDEOGRAPH - 0xE7F1: 0x73E9, //CJK UNIFIED IDEOGRAPH - 0xE7F2: 0x73E7, //CJK UNIFIED IDEOGRAPH - 0xE7F3: 0x73DE, //CJK UNIFIED IDEOGRAPH - 0xE7F4: 0x73BA, //CJK UNIFIED IDEOGRAPH - 0xE7F5: 0x73F2, //CJK UNIFIED IDEOGRAPH - 0xE7F6: 0x740F, //CJK UNIFIED IDEOGRAPH - 0xE7F7: 0x742A, //CJK UNIFIED IDEOGRAPH - 0xE7F8: 0x745B, //CJK UNIFIED IDEOGRAPH - 0xE7F9: 0x7426, //CJK UNIFIED IDEOGRAPH - 0xE7FA: 0x7425, //CJK UNIFIED IDEOGRAPH - 0xE7FB: 0x7428, //CJK UNIFIED IDEOGRAPH - 0xE7FC: 0x7430, //CJK UNIFIED IDEOGRAPH - 0xE7FD: 0x742E, //CJK UNIFIED IDEOGRAPH - 0xE7FE: 0x742C, //CJK UNIFIED IDEOGRAPH - 0xE840: 0x942F, //CJK UNIFIED IDEOGRAPH - 0xE841: 0x9430, //CJK UNIFIED IDEOGRAPH - 0xE842: 0x9431, //CJK UNIFIED IDEOGRAPH - 0xE843: 0x9432, //CJK UNIFIED IDEOGRAPH - 0xE844: 0x9433, //CJK UNIFIED IDEOGRAPH - 0xE845: 0x9434, //CJK UNIFIED IDEOGRAPH - 0xE846: 0x9435, //CJK UNIFIED IDEOGRAPH - 0xE847: 0x9436, //CJK UNIFIED IDEOGRAPH - 0xE848: 0x9437, //CJK UNIFIED IDEOGRAPH - 0xE849: 0x9438, //CJK UNIFIED IDEOGRAPH - 0xE84A: 0x9439, //CJK UNIFIED IDEOGRAPH - 0xE84B: 0x943A, //CJK UNIFIED IDEOGRAPH - 0xE84C: 0x943B, //CJK UNIFIED IDEOGRAPH - 0xE84D: 0x943C, //CJK UNIFIED IDEOGRAPH - 0xE84E: 0x943D, //CJK UNIFIED IDEOGRAPH - 0xE84F: 0x943F, //CJK UNIFIED IDEOGRAPH - 0xE850: 0x9440, //CJK UNIFIED IDEOGRAPH - 0xE851: 0x9441, //CJK UNIFIED IDEOGRAPH - 0xE852: 0x9442, //CJK UNIFIED IDEOGRAPH - 0xE853: 0x9443, //CJK UNIFIED IDEOGRAPH - 0xE854: 0x9444, //CJK UNIFIED IDEOGRAPH - 0xE855: 0x9445, //CJK UNIFIED IDEOGRAPH - 0xE856: 0x9446, //CJK UNIFIED IDEOGRAPH - 0xE857: 0x9447, //CJK UNIFIED IDEOGRAPH - 0xE858: 0x9448, //CJK UNIFIED IDEOGRAPH - 0xE859: 0x9449, //CJK UNIFIED IDEOGRAPH - 0xE85A: 0x944A, //CJK UNIFIED IDEOGRAPH - 0xE85B: 0x944B, //CJK UNIFIED IDEOGRAPH - 0xE85C: 0x944C, //CJK UNIFIED IDEOGRAPH - 0xE85D: 0x944D, //CJK UNIFIED IDEOGRAPH - 0xE85E: 0x944E, //CJK UNIFIED IDEOGRAPH - 0xE85F: 0x944F, //CJK UNIFIED IDEOGRAPH - 0xE860: 0x9450, //CJK UNIFIED IDEOGRAPH - 0xE861: 0x9451, //CJK UNIFIED IDEOGRAPH - 0xE862: 0x9452, //CJK UNIFIED IDEOGRAPH - 0xE863: 0x9453, //CJK UNIFIED IDEOGRAPH - 0xE864: 0x9454, //CJK UNIFIED IDEOGRAPH - 0xE865: 0x9455, //CJK UNIFIED IDEOGRAPH - 0xE866: 0x9456, //CJK UNIFIED IDEOGRAPH - 0xE867: 0x9457, //CJK UNIFIED IDEOGRAPH - 0xE868: 0x9458, //CJK UNIFIED IDEOGRAPH - 0xE869: 0x9459, //CJK UNIFIED IDEOGRAPH - 0xE86A: 0x945A, //CJK UNIFIED IDEOGRAPH - 0xE86B: 0x945B, //CJK UNIFIED IDEOGRAPH - 0xE86C: 0x945C, //CJK UNIFIED IDEOGRAPH - 0xE86D: 0x945D, //CJK UNIFIED IDEOGRAPH - 0xE86E: 0x945E, //CJK UNIFIED IDEOGRAPH - 0xE86F: 0x945F, //CJK UNIFIED IDEOGRAPH - 0xE870: 0x9460, //CJK UNIFIED IDEOGRAPH - 0xE871: 0x9461, //CJK UNIFIED IDEOGRAPH - 0xE872: 0x9462, //CJK UNIFIED IDEOGRAPH - 0xE873: 0x9463, //CJK UNIFIED IDEOGRAPH - 0xE874: 0x9464, //CJK UNIFIED IDEOGRAPH - 0xE875: 0x9465, //CJK UNIFIED IDEOGRAPH - 0xE876: 0x9466, //CJK UNIFIED IDEOGRAPH - 0xE877: 0x9467, //CJK UNIFIED IDEOGRAPH - 0xE878: 0x9468, //CJK UNIFIED IDEOGRAPH - 0xE879: 0x9469, //CJK UNIFIED IDEOGRAPH - 0xE87A: 0x946A, //CJK UNIFIED IDEOGRAPH - 0xE87B: 0x946C, //CJK UNIFIED IDEOGRAPH - 0xE87C: 0x946D, //CJK UNIFIED IDEOGRAPH - 0xE87D: 0x946E, //CJK UNIFIED IDEOGRAPH - 0xE87E: 0x946F, //CJK UNIFIED IDEOGRAPH - 0xE880: 0x9470, //CJK UNIFIED IDEOGRAPH - 0xE881: 0x9471, //CJK UNIFIED IDEOGRAPH - 0xE882: 0x9472, //CJK UNIFIED IDEOGRAPH - 0xE883: 0x9473, //CJK UNIFIED IDEOGRAPH - 0xE884: 0x9474, //CJK UNIFIED IDEOGRAPH - 0xE885: 0x9475, //CJK UNIFIED IDEOGRAPH - 0xE886: 0x9476, //CJK UNIFIED IDEOGRAPH - 0xE887: 0x9477, //CJK UNIFIED IDEOGRAPH - 0xE888: 0x9478, //CJK UNIFIED IDEOGRAPH - 0xE889: 0x9479, //CJK UNIFIED IDEOGRAPH - 0xE88A: 0x947A, //CJK UNIFIED IDEOGRAPH - 0xE88B: 0x947B, //CJK UNIFIED IDEOGRAPH - 0xE88C: 0x947C, //CJK UNIFIED IDEOGRAPH - 0xE88D: 0x947D, //CJK UNIFIED IDEOGRAPH - 0xE88E: 0x947E, //CJK UNIFIED IDEOGRAPH - 0xE88F: 0x947F, //CJK UNIFIED IDEOGRAPH - 0xE890: 0x9480, //CJK UNIFIED IDEOGRAPH - 0xE891: 0x9481, //CJK UNIFIED IDEOGRAPH - 0xE892: 0x9482, //CJK UNIFIED IDEOGRAPH - 0xE893: 0x9483, //CJK UNIFIED IDEOGRAPH - 0xE894: 0x9484, //CJK UNIFIED IDEOGRAPH - 0xE895: 0x9491, //CJK UNIFIED IDEOGRAPH - 0xE896: 0x9496, //CJK UNIFIED IDEOGRAPH - 0xE897: 0x9498, //CJK UNIFIED IDEOGRAPH - 0xE898: 0x94C7, //CJK UNIFIED IDEOGRAPH - 0xE899: 0x94CF, //CJK UNIFIED IDEOGRAPH - 0xE89A: 0x94D3, //CJK UNIFIED IDEOGRAPH - 0xE89B: 0x94D4, //CJK UNIFIED IDEOGRAPH - 0xE89C: 0x94DA, //CJK UNIFIED IDEOGRAPH - 0xE89D: 0x94E6, //CJK UNIFIED IDEOGRAPH - 0xE89E: 0x94FB, //CJK UNIFIED IDEOGRAPH - 0xE89F: 0x951C, //CJK UNIFIED IDEOGRAPH - 0xE8A0: 0x9520, //CJK UNIFIED IDEOGRAPH - 0xE8A1: 0x741B, //CJK UNIFIED IDEOGRAPH - 0xE8A2: 0x741A, //CJK UNIFIED IDEOGRAPH - 0xE8A3: 0x7441, //CJK UNIFIED IDEOGRAPH - 0xE8A4: 0x745C, //CJK UNIFIED IDEOGRAPH - 0xE8A5: 0x7457, //CJK UNIFIED IDEOGRAPH - 0xE8A6: 0x7455, //CJK UNIFIED IDEOGRAPH - 0xE8A7: 0x7459, //CJK UNIFIED IDEOGRAPH - 0xE8A8: 0x7477, //CJK UNIFIED IDEOGRAPH - 0xE8A9: 0x746D, //CJK UNIFIED IDEOGRAPH - 0xE8AA: 0x747E, //CJK UNIFIED IDEOGRAPH - 0xE8AB: 0x749C, //CJK UNIFIED IDEOGRAPH - 0xE8AC: 0x748E, //CJK UNIFIED IDEOGRAPH - 0xE8AD: 0x7480, //CJK UNIFIED IDEOGRAPH - 0xE8AE: 0x7481, //CJK UNIFIED IDEOGRAPH - 0xE8AF: 0x7487, //CJK UNIFIED IDEOGRAPH - 0xE8B0: 0x748B, //CJK UNIFIED IDEOGRAPH - 0xE8B1: 0x749E, //CJK UNIFIED IDEOGRAPH - 0xE8B2: 0x74A8, //CJK UNIFIED IDEOGRAPH - 0xE8B3: 0x74A9, //CJK UNIFIED IDEOGRAPH - 0xE8B4: 0x7490, //CJK UNIFIED IDEOGRAPH - 0xE8B5: 0x74A7, //CJK UNIFIED IDEOGRAPH - 0xE8B6: 0x74D2, //CJK UNIFIED IDEOGRAPH - 0xE8B7: 0x74BA, //CJK UNIFIED IDEOGRAPH - 0xE8B8: 0x97EA, //CJK UNIFIED IDEOGRAPH - 0xE8B9: 0x97EB, //CJK UNIFIED IDEOGRAPH - 0xE8BA: 0x97EC, //CJK UNIFIED IDEOGRAPH - 0xE8BB: 0x674C, //CJK UNIFIED IDEOGRAPH - 0xE8BC: 0x6753, //CJK UNIFIED IDEOGRAPH - 0xE8BD: 0x675E, //CJK UNIFIED IDEOGRAPH - 0xE8BE: 0x6748, //CJK UNIFIED IDEOGRAPH - 0xE8BF: 0x6769, //CJK UNIFIED IDEOGRAPH - 0xE8C0: 0x67A5, //CJK UNIFIED IDEOGRAPH - 0xE8C1: 0x6787, //CJK UNIFIED IDEOGRAPH - 0xE8C2: 0x676A, //CJK UNIFIED IDEOGRAPH - 0xE8C3: 0x6773, //CJK UNIFIED IDEOGRAPH - 0xE8C4: 0x6798, //CJK UNIFIED IDEOGRAPH - 0xE8C5: 0x67A7, //CJK UNIFIED IDEOGRAPH - 0xE8C6: 0x6775, //CJK UNIFIED IDEOGRAPH - 0xE8C7: 0x67A8, //CJK UNIFIED IDEOGRAPH - 0xE8C8: 0x679E, //CJK UNIFIED IDEOGRAPH - 0xE8C9: 0x67AD, //CJK UNIFIED IDEOGRAPH - 0xE8CA: 0x678B, //CJK UNIFIED IDEOGRAPH - 0xE8CB: 0x6777, //CJK UNIFIED IDEOGRAPH - 0xE8CC: 0x677C, //CJK UNIFIED IDEOGRAPH - 0xE8CD: 0x67F0, //CJK UNIFIED IDEOGRAPH - 0xE8CE: 0x6809, //CJK UNIFIED IDEOGRAPH - 0xE8CF: 0x67D8, //CJK UNIFIED IDEOGRAPH - 0xE8D0: 0x680A, //CJK UNIFIED IDEOGRAPH - 0xE8D1: 0x67E9, //CJK UNIFIED IDEOGRAPH - 0xE8D2: 0x67B0, //CJK UNIFIED IDEOGRAPH - 0xE8D3: 0x680C, //CJK UNIFIED IDEOGRAPH - 0xE8D4: 0x67D9, //CJK UNIFIED IDEOGRAPH - 0xE8D5: 0x67B5, //CJK UNIFIED IDEOGRAPH - 0xE8D6: 0x67DA, //CJK UNIFIED IDEOGRAPH - 0xE8D7: 0x67B3, //CJK UNIFIED IDEOGRAPH - 0xE8D8: 0x67DD, //CJK UNIFIED IDEOGRAPH - 0xE8D9: 0x6800, //CJK UNIFIED IDEOGRAPH - 0xE8DA: 0x67C3, //CJK UNIFIED IDEOGRAPH - 0xE8DB: 0x67B8, //CJK UNIFIED IDEOGRAPH - 0xE8DC: 0x67E2, //CJK UNIFIED IDEOGRAPH - 0xE8DD: 0x680E, //CJK UNIFIED IDEOGRAPH - 0xE8DE: 0x67C1, //CJK UNIFIED IDEOGRAPH - 0xE8DF: 0x67FD, //CJK UNIFIED IDEOGRAPH - 0xE8E0: 0x6832, //CJK UNIFIED IDEOGRAPH - 0xE8E1: 0x6833, //CJK UNIFIED IDEOGRAPH - 0xE8E2: 0x6860, //CJK UNIFIED IDEOGRAPH - 0xE8E3: 0x6861, //CJK UNIFIED IDEOGRAPH - 0xE8E4: 0x684E, //CJK UNIFIED IDEOGRAPH - 0xE8E5: 0x6862, //CJK UNIFIED IDEOGRAPH - 0xE8E6: 0x6844, //CJK UNIFIED IDEOGRAPH - 0xE8E7: 0x6864, //CJK UNIFIED IDEOGRAPH - 0xE8E8: 0x6883, //CJK UNIFIED IDEOGRAPH - 0xE8E9: 0x681D, //CJK UNIFIED IDEOGRAPH - 0xE8EA: 0x6855, //CJK UNIFIED IDEOGRAPH - 0xE8EB: 0x6866, //CJK UNIFIED IDEOGRAPH - 0xE8EC: 0x6841, //CJK UNIFIED IDEOGRAPH - 0xE8ED: 0x6867, //CJK UNIFIED IDEOGRAPH - 0xE8EE: 0x6840, //CJK UNIFIED IDEOGRAPH - 0xE8EF: 0x683E, //CJK UNIFIED IDEOGRAPH - 0xE8F0: 0x684A, //CJK UNIFIED IDEOGRAPH - 0xE8F1: 0x6849, //CJK UNIFIED IDEOGRAPH - 0xE8F2: 0x6829, //CJK UNIFIED IDEOGRAPH - 0xE8F3: 0x68B5, //CJK UNIFIED IDEOGRAPH - 0xE8F4: 0x688F, //CJK UNIFIED IDEOGRAPH - 0xE8F5: 0x6874, //CJK UNIFIED IDEOGRAPH - 0xE8F6: 0x6877, //CJK UNIFIED IDEOGRAPH - 0xE8F7: 0x6893, //CJK UNIFIED IDEOGRAPH - 0xE8F8: 0x686B, //CJK UNIFIED IDEOGRAPH - 0xE8F9: 0x68C2, //CJK UNIFIED IDEOGRAPH - 0xE8FA: 0x696E, //CJK UNIFIED IDEOGRAPH - 0xE8FB: 0x68FC, //CJK UNIFIED IDEOGRAPH - 0xE8FC: 0x691F, //CJK UNIFIED IDEOGRAPH - 0xE8FD: 0x6920, //CJK UNIFIED IDEOGRAPH - 0xE8FE: 0x68F9, //CJK UNIFIED IDEOGRAPH - 0xE940: 0x9527, //CJK UNIFIED IDEOGRAPH - 0xE941: 0x9533, //CJK UNIFIED IDEOGRAPH - 0xE942: 0x953D, //CJK UNIFIED IDEOGRAPH - 0xE943: 0x9543, //CJK UNIFIED IDEOGRAPH - 0xE944: 0x9548, //CJK UNIFIED IDEOGRAPH - 0xE945: 0x954B, //CJK UNIFIED IDEOGRAPH - 0xE946: 0x9555, //CJK UNIFIED IDEOGRAPH - 0xE947: 0x955A, //CJK UNIFIED IDEOGRAPH - 0xE948: 0x9560, //CJK UNIFIED IDEOGRAPH - 0xE949: 0x956E, //CJK UNIFIED IDEOGRAPH - 0xE94A: 0x9574, //CJK UNIFIED IDEOGRAPH - 0xE94B: 0x9575, //CJK UNIFIED IDEOGRAPH - 0xE94C: 0x9577, //CJK UNIFIED IDEOGRAPH - 0xE94D: 0x9578, //CJK UNIFIED IDEOGRAPH - 0xE94E: 0x9579, //CJK UNIFIED IDEOGRAPH - 0xE94F: 0x957A, //CJK UNIFIED IDEOGRAPH - 0xE950: 0x957B, //CJK UNIFIED IDEOGRAPH - 0xE951: 0x957C, //CJK UNIFIED IDEOGRAPH - 0xE952: 0x957D, //CJK UNIFIED IDEOGRAPH - 0xE953: 0x957E, //CJK UNIFIED IDEOGRAPH - 0xE954: 0x9580, //CJK UNIFIED IDEOGRAPH - 0xE955: 0x9581, //CJK UNIFIED IDEOGRAPH - 0xE956: 0x9582, //CJK UNIFIED IDEOGRAPH - 0xE957: 0x9583, //CJK UNIFIED IDEOGRAPH - 0xE958: 0x9584, //CJK UNIFIED IDEOGRAPH - 0xE959: 0x9585, //CJK UNIFIED IDEOGRAPH - 0xE95A: 0x9586, //CJK UNIFIED IDEOGRAPH - 0xE95B: 0x9587, //CJK UNIFIED IDEOGRAPH - 0xE95C: 0x9588, //CJK UNIFIED IDEOGRAPH - 0xE95D: 0x9589, //CJK UNIFIED IDEOGRAPH - 0xE95E: 0x958A, //CJK UNIFIED IDEOGRAPH - 0xE95F: 0x958B, //CJK UNIFIED IDEOGRAPH - 0xE960: 0x958C, //CJK UNIFIED IDEOGRAPH - 0xE961: 0x958D, //CJK UNIFIED IDEOGRAPH - 0xE962: 0x958E, //CJK UNIFIED IDEOGRAPH - 0xE963: 0x958F, //CJK UNIFIED IDEOGRAPH - 0xE964: 0x9590, //CJK UNIFIED IDEOGRAPH - 0xE965: 0x9591, //CJK UNIFIED IDEOGRAPH - 0xE966: 0x9592, //CJK UNIFIED IDEOGRAPH - 0xE967: 0x9593, //CJK UNIFIED IDEOGRAPH - 0xE968: 0x9594, //CJK UNIFIED IDEOGRAPH - 0xE969: 0x9595, //CJK UNIFIED IDEOGRAPH - 0xE96A: 0x9596, //CJK UNIFIED IDEOGRAPH - 0xE96B: 0x9597, //CJK UNIFIED IDEOGRAPH - 0xE96C: 0x9598, //CJK UNIFIED IDEOGRAPH - 0xE96D: 0x9599, //CJK UNIFIED IDEOGRAPH - 0xE96E: 0x959A, //CJK UNIFIED IDEOGRAPH - 0xE96F: 0x959B, //CJK UNIFIED IDEOGRAPH - 0xE970: 0x959C, //CJK UNIFIED IDEOGRAPH - 0xE971: 0x959D, //CJK UNIFIED IDEOGRAPH - 0xE972: 0x959E, //CJK UNIFIED IDEOGRAPH - 0xE973: 0x959F, //CJK UNIFIED IDEOGRAPH - 0xE974: 0x95A0, //CJK UNIFIED IDEOGRAPH - 0xE975: 0x95A1, //CJK UNIFIED IDEOGRAPH - 0xE976: 0x95A2, //CJK UNIFIED IDEOGRAPH - 0xE977: 0x95A3, //CJK UNIFIED IDEOGRAPH - 0xE978: 0x95A4, //CJK UNIFIED IDEOGRAPH - 0xE979: 0x95A5, //CJK UNIFIED IDEOGRAPH - 0xE97A: 0x95A6, //CJK UNIFIED IDEOGRAPH - 0xE97B: 0x95A7, //CJK UNIFIED IDEOGRAPH - 0xE97C: 0x95A8, //CJK UNIFIED IDEOGRAPH - 0xE97D: 0x95A9, //CJK UNIFIED IDEOGRAPH - 0xE97E: 0x95AA, //CJK UNIFIED IDEOGRAPH - 0xE980: 0x95AB, //CJK UNIFIED IDEOGRAPH - 0xE981: 0x95AC, //CJK UNIFIED IDEOGRAPH - 0xE982: 0x95AD, //CJK UNIFIED IDEOGRAPH - 0xE983: 0x95AE, //CJK UNIFIED IDEOGRAPH - 0xE984: 0x95AF, //CJK UNIFIED IDEOGRAPH - 0xE985: 0x95B0, //CJK UNIFIED IDEOGRAPH - 0xE986: 0x95B1, //CJK UNIFIED IDEOGRAPH - 0xE987: 0x95B2, //CJK UNIFIED IDEOGRAPH - 0xE988: 0x95B3, //CJK UNIFIED IDEOGRAPH - 0xE989: 0x95B4, //CJK UNIFIED IDEOGRAPH - 0xE98A: 0x95B5, //CJK UNIFIED IDEOGRAPH - 0xE98B: 0x95B6, //CJK UNIFIED IDEOGRAPH - 0xE98C: 0x95B7, //CJK UNIFIED IDEOGRAPH - 0xE98D: 0x95B8, //CJK UNIFIED IDEOGRAPH - 0xE98E: 0x95B9, //CJK UNIFIED IDEOGRAPH - 0xE98F: 0x95BA, //CJK UNIFIED IDEOGRAPH - 0xE990: 0x95BB, //CJK UNIFIED IDEOGRAPH - 0xE991: 0x95BC, //CJK UNIFIED IDEOGRAPH - 0xE992: 0x95BD, //CJK UNIFIED IDEOGRAPH - 0xE993: 0x95BE, //CJK UNIFIED IDEOGRAPH - 0xE994: 0x95BF, //CJK UNIFIED IDEOGRAPH - 0xE995: 0x95C0, //CJK UNIFIED IDEOGRAPH - 0xE996: 0x95C1, //CJK UNIFIED IDEOGRAPH - 0xE997: 0x95C2, //CJK UNIFIED IDEOGRAPH - 0xE998: 0x95C3, //CJK UNIFIED IDEOGRAPH - 0xE999: 0x95C4, //CJK UNIFIED IDEOGRAPH - 0xE99A: 0x95C5, //CJK UNIFIED IDEOGRAPH - 0xE99B: 0x95C6, //CJK UNIFIED IDEOGRAPH - 0xE99C: 0x95C7, //CJK UNIFIED IDEOGRAPH - 0xE99D: 0x95C8, //CJK UNIFIED IDEOGRAPH - 0xE99E: 0x95C9, //CJK UNIFIED IDEOGRAPH - 0xE99F: 0x95CA, //CJK UNIFIED IDEOGRAPH - 0xE9A0: 0x95CB, //CJK UNIFIED IDEOGRAPH - 0xE9A1: 0x6924, //CJK UNIFIED IDEOGRAPH - 0xE9A2: 0x68F0, //CJK UNIFIED IDEOGRAPH - 0xE9A3: 0x690B, //CJK UNIFIED IDEOGRAPH - 0xE9A4: 0x6901, //CJK UNIFIED IDEOGRAPH - 0xE9A5: 0x6957, //CJK UNIFIED IDEOGRAPH - 0xE9A6: 0x68E3, //CJK UNIFIED IDEOGRAPH - 0xE9A7: 0x6910, //CJK UNIFIED IDEOGRAPH - 0xE9A8: 0x6971, //CJK UNIFIED IDEOGRAPH - 0xE9A9: 0x6939, //CJK UNIFIED IDEOGRAPH - 0xE9AA: 0x6960, //CJK UNIFIED IDEOGRAPH - 0xE9AB: 0x6942, //CJK UNIFIED IDEOGRAPH - 0xE9AC: 0x695D, //CJK UNIFIED IDEOGRAPH - 0xE9AD: 0x6984, //CJK UNIFIED IDEOGRAPH - 0xE9AE: 0x696B, //CJK UNIFIED IDEOGRAPH - 0xE9AF: 0x6980, //CJK UNIFIED IDEOGRAPH - 0xE9B0: 0x6998, //CJK UNIFIED IDEOGRAPH - 0xE9B1: 0x6978, //CJK UNIFIED IDEOGRAPH - 0xE9B2: 0x6934, //CJK UNIFIED IDEOGRAPH - 0xE9B3: 0x69CC, //CJK UNIFIED IDEOGRAPH - 0xE9B4: 0x6987, //CJK UNIFIED IDEOGRAPH - 0xE9B5: 0x6988, //CJK UNIFIED IDEOGRAPH - 0xE9B6: 0x69CE, //CJK UNIFIED IDEOGRAPH - 0xE9B7: 0x6989, //CJK UNIFIED IDEOGRAPH - 0xE9B8: 0x6966, //CJK UNIFIED IDEOGRAPH - 0xE9B9: 0x6963, //CJK UNIFIED IDEOGRAPH - 0xE9BA: 0x6979, //CJK UNIFIED IDEOGRAPH - 0xE9BB: 0x699B, //CJK UNIFIED IDEOGRAPH - 0xE9BC: 0x69A7, //CJK UNIFIED IDEOGRAPH - 0xE9BD: 0x69BB, //CJK UNIFIED IDEOGRAPH - 0xE9BE: 0x69AB, //CJK UNIFIED IDEOGRAPH - 0xE9BF: 0x69AD, //CJK UNIFIED IDEOGRAPH - 0xE9C0: 0x69D4, //CJK UNIFIED IDEOGRAPH - 0xE9C1: 0x69B1, //CJK UNIFIED IDEOGRAPH - 0xE9C2: 0x69C1, //CJK UNIFIED IDEOGRAPH - 0xE9C3: 0x69CA, //CJK UNIFIED IDEOGRAPH - 0xE9C4: 0x69DF, //CJK UNIFIED IDEOGRAPH - 0xE9C5: 0x6995, //CJK UNIFIED IDEOGRAPH - 0xE9C6: 0x69E0, //CJK UNIFIED IDEOGRAPH - 0xE9C7: 0x698D, //CJK UNIFIED IDEOGRAPH - 0xE9C8: 0x69FF, //CJK UNIFIED IDEOGRAPH - 0xE9C9: 0x6A2F, //CJK UNIFIED IDEOGRAPH - 0xE9CA: 0x69ED, //CJK UNIFIED IDEOGRAPH - 0xE9CB: 0x6A17, //CJK UNIFIED IDEOGRAPH - 0xE9CC: 0x6A18, //CJK UNIFIED IDEOGRAPH - 0xE9CD: 0x6A65, //CJK UNIFIED IDEOGRAPH - 0xE9CE: 0x69F2, //CJK UNIFIED IDEOGRAPH - 0xE9CF: 0x6A44, //CJK UNIFIED IDEOGRAPH - 0xE9D0: 0x6A3E, //CJK UNIFIED IDEOGRAPH - 0xE9D1: 0x6AA0, //CJK UNIFIED IDEOGRAPH - 0xE9D2: 0x6A50, //CJK UNIFIED IDEOGRAPH - 0xE9D3: 0x6A5B, //CJK UNIFIED IDEOGRAPH - 0xE9D4: 0x6A35, //CJK UNIFIED IDEOGRAPH - 0xE9D5: 0x6A8E, //CJK UNIFIED IDEOGRAPH - 0xE9D6: 0x6A79, //CJK UNIFIED IDEOGRAPH - 0xE9D7: 0x6A3D, //CJK UNIFIED IDEOGRAPH - 0xE9D8: 0x6A28, //CJK UNIFIED IDEOGRAPH - 0xE9D9: 0x6A58, //CJK UNIFIED IDEOGRAPH - 0xE9DA: 0x6A7C, //CJK UNIFIED IDEOGRAPH - 0xE9DB: 0x6A91, //CJK UNIFIED IDEOGRAPH - 0xE9DC: 0x6A90, //CJK UNIFIED IDEOGRAPH - 0xE9DD: 0x6AA9, //CJK UNIFIED IDEOGRAPH - 0xE9DE: 0x6A97, //CJK UNIFIED IDEOGRAPH - 0xE9DF: 0x6AAB, //CJK UNIFIED IDEOGRAPH - 0xE9E0: 0x7337, //CJK UNIFIED IDEOGRAPH - 0xE9E1: 0x7352, //CJK UNIFIED IDEOGRAPH - 0xE9E2: 0x6B81, //CJK UNIFIED IDEOGRAPH - 0xE9E3: 0x6B82, //CJK UNIFIED IDEOGRAPH - 0xE9E4: 0x6B87, //CJK UNIFIED IDEOGRAPH - 0xE9E5: 0x6B84, //CJK UNIFIED IDEOGRAPH - 0xE9E6: 0x6B92, //CJK UNIFIED IDEOGRAPH - 0xE9E7: 0x6B93, //CJK UNIFIED IDEOGRAPH - 0xE9E8: 0x6B8D, //CJK UNIFIED IDEOGRAPH - 0xE9E9: 0x6B9A, //CJK UNIFIED IDEOGRAPH - 0xE9EA: 0x6B9B, //CJK UNIFIED IDEOGRAPH - 0xE9EB: 0x6BA1, //CJK UNIFIED IDEOGRAPH - 0xE9EC: 0x6BAA, //CJK UNIFIED IDEOGRAPH - 0xE9ED: 0x8F6B, //CJK UNIFIED IDEOGRAPH - 0xE9EE: 0x8F6D, //CJK UNIFIED IDEOGRAPH - 0xE9EF: 0x8F71, //CJK UNIFIED IDEOGRAPH - 0xE9F0: 0x8F72, //CJK UNIFIED IDEOGRAPH - 0xE9F1: 0x8F73, //CJK UNIFIED IDEOGRAPH - 0xE9F2: 0x8F75, //CJK UNIFIED IDEOGRAPH - 0xE9F3: 0x8F76, //CJK UNIFIED IDEOGRAPH - 0xE9F4: 0x8F78, //CJK UNIFIED IDEOGRAPH - 0xE9F5: 0x8F77, //CJK UNIFIED IDEOGRAPH - 0xE9F6: 0x8F79, //CJK UNIFIED IDEOGRAPH - 0xE9F7: 0x8F7A, //CJK UNIFIED IDEOGRAPH - 0xE9F8: 0x8F7C, //CJK UNIFIED IDEOGRAPH - 0xE9F9: 0x8F7E, //CJK UNIFIED IDEOGRAPH - 0xE9FA: 0x8F81, //CJK UNIFIED IDEOGRAPH - 0xE9FB: 0x8F82, //CJK UNIFIED IDEOGRAPH - 0xE9FC: 0x8F84, //CJK UNIFIED IDEOGRAPH - 0xE9FD: 0x8F87, //CJK UNIFIED IDEOGRAPH - 0xE9FE: 0x8F8B, //CJK UNIFIED IDEOGRAPH - 0xEA40: 0x95CC, //CJK UNIFIED IDEOGRAPH - 0xEA41: 0x95CD, //CJK UNIFIED IDEOGRAPH - 0xEA42: 0x95CE, //CJK UNIFIED IDEOGRAPH - 0xEA43: 0x95CF, //CJK UNIFIED IDEOGRAPH - 0xEA44: 0x95D0, //CJK UNIFIED IDEOGRAPH - 0xEA45: 0x95D1, //CJK UNIFIED IDEOGRAPH - 0xEA46: 0x95D2, //CJK UNIFIED IDEOGRAPH - 0xEA47: 0x95D3, //CJK UNIFIED IDEOGRAPH - 0xEA48: 0x95D4, //CJK UNIFIED IDEOGRAPH - 0xEA49: 0x95D5, //CJK UNIFIED IDEOGRAPH - 0xEA4A: 0x95D6, //CJK UNIFIED IDEOGRAPH - 0xEA4B: 0x95D7, //CJK UNIFIED IDEOGRAPH - 0xEA4C: 0x95D8, //CJK UNIFIED IDEOGRAPH - 0xEA4D: 0x95D9, //CJK UNIFIED IDEOGRAPH - 0xEA4E: 0x95DA, //CJK UNIFIED IDEOGRAPH - 0xEA4F: 0x95DB, //CJK UNIFIED IDEOGRAPH - 0xEA50: 0x95DC, //CJK UNIFIED IDEOGRAPH - 0xEA51: 0x95DD, //CJK UNIFIED IDEOGRAPH - 0xEA52: 0x95DE, //CJK UNIFIED IDEOGRAPH - 0xEA53: 0x95DF, //CJK UNIFIED IDEOGRAPH - 0xEA54: 0x95E0, //CJK UNIFIED IDEOGRAPH - 0xEA55: 0x95E1, //CJK UNIFIED IDEOGRAPH - 0xEA56: 0x95E2, //CJK UNIFIED IDEOGRAPH - 0xEA57: 0x95E3, //CJK UNIFIED IDEOGRAPH - 0xEA58: 0x95E4, //CJK UNIFIED IDEOGRAPH - 0xEA59: 0x95E5, //CJK UNIFIED IDEOGRAPH - 0xEA5A: 0x95E6, //CJK UNIFIED IDEOGRAPH - 0xEA5B: 0x95E7, //CJK UNIFIED IDEOGRAPH - 0xEA5C: 0x95EC, //CJK UNIFIED IDEOGRAPH - 0xEA5D: 0x95FF, //CJK UNIFIED IDEOGRAPH - 0xEA5E: 0x9607, //CJK UNIFIED IDEOGRAPH - 0xEA5F: 0x9613, //CJK UNIFIED IDEOGRAPH - 0xEA60: 0x9618, //CJK UNIFIED IDEOGRAPH - 0xEA61: 0x961B, //CJK UNIFIED IDEOGRAPH - 0xEA62: 0x961E, //CJK UNIFIED IDEOGRAPH - 0xEA63: 0x9620, //CJK UNIFIED IDEOGRAPH - 0xEA64: 0x9623, //CJK UNIFIED IDEOGRAPH - 0xEA65: 0x9624, //CJK UNIFIED IDEOGRAPH - 0xEA66: 0x9625, //CJK UNIFIED IDEOGRAPH - 0xEA67: 0x9626, //CJK UNIFIED IDEOGRAPH - 0xEA68: 0x9627, //CJK UNIFIED IDEOGRAPH - 0xEA69: 0x9628, //CJK UNIFIED IDEOGRAPH - 0xEA6A: 0x9629, //CJK UNIFIED IDEOGRAPH - 0xEA6B: 0x962B, //CJK UNIFIED IDEOGRAPH - 0xEA6C: 0x962C, //CJK UNIFIED IDEOGRAPH - 0xEA6D: 0x962D, //CJK UNIFIED IDEOGRAPH - 0xEA6E: 0x962F, //CJK UNIFIED IDEOGRAPH - 0xEA6F: 0x9630, //CJK UNIFIED IDEOGRAPH - 0xEA70: 0x9637, //CJK UNIFIED IDEOGRAPH - 0xEA71: 0x9638, //CJK UNIFIED IDEOGRAPH - 0xEA72: 0x9639, //CJK UNIFIED IDEOGRAPH - 0xEA73: 0x963A, //CJK UNIFIED IDEOGRAPH - 0xEA74: 0x963E, //CJK UNIFIED IDEOGRAPH - 0xEA75: 0x9641, //CJK UNIFIED IDEOGRAPH - 0xEA76: 0x9643, //CJK UNIFIED IDEOGRAPH - 0xEA77: 0x964A, //CJK UNIFIED IDEOGRAPH - 0xEA78: 0x964E, //CJK UNIFIED IDEOGRAPH - 0xEA79: 0x964F, //CJK UNIFIED IDEOGRAPH - 0xEA7A: 0x9651, //CJK UNIFIED IDEOGRAPH - 0xEA7B: 0x9652, //CJK UNIFIED IDEOGRAPH - 0xEA7C: 0x9653, //CJK UNIFIED IDEOGRAPH - 0xEA7D: 0x9656, //CJK UNIFIED IDEOGRAPH - 0xEA7E: 0x9657, //CJK UNIFIED IDEOGRAPH - 0xEA80: 0x9658, //CJK UNIFIED IDEOGRAPH - 0xEA81: 0x9659, //CJK UNIFIED IDEOGRAPH - 0xEA82: 0x965A, //CJK UNIFIED IDEOGRAPH - 0xEA83: 0x965C, //CJK UNIFIED IDEOGRAPH - 0xEA84: 0x965D, //CJK UNIFIED IDEOGRAPH - 0xEA85: 0x965E, //CJK UNIFIED IDEOGRAPH - 0xEA86: 0x9660, //CJK UNIFIED IDEOGRAPH - 0xEA87: 0x9663, //CJK UNIFIED IDEOGRAPH - 0xEA88: 0x9665, //CJK UNIFIED IDEOGRAPH - 0xEA89: 0x9666, //CJK UNIFIED IDEOGRAPH - 0xEA8A: 0x966B, //CJK UNIFIED IDEOGRAPH - 0xEA8B: 0x966D, //CJK UNIFIED IDEOGRAPH - 0xEA8C: 0x966E, //CJK UNIFIED IDEOGRAPH - 0xEA8D: 0x966F, //CJK UNIFIED IDEOGRAPH - 0xEA8E: 0x9670, //CJK UNIFIED IDEOGRAPH - 0xEA8F: 0x9671, //CJK UNIFIED IDEOGRAPH - 0xEA90: 0x9673, //CJK UNIFIED IDEOGRAPH - 0xEA91: 0x9678, //CJK UNIFIED IDEOGRAPH - 0xEA92: 0x9679, //CJK UNIFIED IDEOGRAPH - 0xEA93: 0x967A, //CJK UNIFIED IDEOGRAPH - 0xEA94: 0x967B, //CJK UNIFIED IDEOGRAPH - 0xEA95: 0x967C, //CJK UNIFIED IDEOGRAPH - 0xEA96: 0x967D, //CJK UNIFIED IDEOGRAPH - 0xEA97: 0x967E, //CJK UNIFIED IDEOGRAPH - 0xEA98: 0x967F, //CJK UNIFIED IDEOGRAPH - 0xEA99: 0x9680, //CJK UNIFIED IDEOGRAPH - 0xEA9A: 0x9681, //CJK UNIFIED IDEOGRAPH - 0xEA9B: 0x9682, //CJK UNIFIED IDEOGRAPH - 0xEA9C: 0x9683, //CJK UNIFIED IDEOGRAPH - 0xEA9D: 0x9684, //CJK UNIFIED IDEOGRAPH - 0xEA9E: 0x9687, //CJK UNIFIED IDEOGRAPH - 0xEA9F: 0x9689, //CJK UNIFIED IDEOGRAPH - 0xEAA0: 0x968A, //CJK UNIFIED IDEOGRAPH - 0xEAA1: 0x8F8D, //CJK UNIFIED IDEOGRAPH - 0xEAA2: 0x8F8E, //CJK UNIFIED IDEOGRAPH - 0xEAA3: 0x8F8F, //CJK UNIFIED IDEOGRAPH - 0xEAA4: 0x8F98, //CJK UNIFIED IDEOGRAPH - 0xEAA5: 0x8F9A, //CJK UNIFIED IDEOGRAPH - 0xEAA6: 0x8ECE, //CJK UNIFIED IDEOGRAPH - 0xEAA7: 0x620B, //CJK UNIFIED IDEOGRAPH - 0xEAA8: 0x6217, //CJK UNIFIED IDEOGRAPH - 0xEAA9: 0x621B, //CJK UNIFIED IDEOGRAPH - 0xEAAA: 0x621F, //CJK UNIFIED IDEOGRAPH - 0xEAAB: 0x6222, //CJK UNIFIED IDEOGRAPH - 0xEAAC: 0x6221, //CJK UNIFIED IDEOGRAPH - 0xEAAD: 0x6225, //CJK UNIFIED IDEOGRAPH - 0xEAAE: 0x6224, //CJK UNIFIED IDEOGRAPH - 0xEAAF: 0x622C, //CJK UNIFIED IDEOGRAPH - 0xEAB0: 0x81E7, //CJK UNIFIED IDEOGRAPH - 0xEAB1: 0x74EF, //CJK UNIFIED IDEOGRAPH - 0xEAB2: 0x74F4, //CJK UNIFIED IDEOGRAPH - 0xEAB3: 0x74FF, //CJK UNIFIED IDEOGRAPH - 0xEAB4: 0x750F, //CJK UNIFIED IDEOGRAPH - 0xEAB5: 0x7511, //CJK UNIFIED IDEOGRAPH - 0xEAB6: 0x7513, //CJK UNIFIED IDEOGRAPH - 0xEAB7: 0x6534, //CJK UNIFIED IDEOGRAPH - 0xEAB8: 0x65EE, //CJK UNIFIED IDEOGRAPH - 0xEAB9: 0x65EF, //CJK UNIFIED IDEOGRAPH - 0xEABA: 0x65F0, //CJK UNIFIED IDEOGRAPH - 0xEABB: 0x660A, //CJK UNIFIED IDEOGRAPH - 0xEABC: 0x6619, //CJK UNIFIED IDEOGRAPH - 0xEABD: 0x6772, //CJK UNIFIED IDEOGRAPH - 0xEABE: 0x6603, //CJK UNIFIED IDEOGRAPH - 0xEABF: 0x6615, //CJK UNIFIED IDEOGRAPH - 0xEAC0: 0x6600, //CJK UNIFIED IDEOGRAPH - 0xEAC1: 0x7085, //CJK UNIFIED IDEOGRAPH - 0xEAC2: 0x66F7, //CJK UNIFIED IDEOGRAPH - 0xEAC3: 0x661D, //CJK UNIFIED IDEOGRAPH - 0xEAC4: 0x6634, //CJK UNIFIED IDEOGRAPH - 0xEAC5: 0x6631, //CJK UNIFIED IDEOGRAPH - 0xEAC6: 0x6636, //CJK UNIFIED IDEOGRAPH - 0xEAC7: 0x6635, //CJK UNIFIED IDEOGRAPH - 0xEAC8: 0x8006, //CJK UNIFIED IDEOGRAPH - 0xEAC9: 0x665F, //CJK UNIFIED IDEOGRAPH - 0xEACA: 0x6654, //CJK UNIFIED IDEOGRAPH - 0xEACB: 0x6641, //CJK UNIFIED IDEOGRAPH - 0xEACC: 0x664F, //CJK UNIFIED IDEOGRAPH - 0xEACD: 0x6656, //CJK UNIFIED IDEOGRAPH - 0xEACE: 0x6661, //CJK UNIFIED IDEOGRAPH - 0xEACF: 0x6657, //CJK UNIFIED IDEOGRAPH - 0xEAD0: 0x6677, //CJK UNIFIED IDEOGRAPH - 0xEAD1: 0x6684, //CJK UNIFIED IDEOGRAPH - 0xEAD2: 0x668C, //CJK UNIFIED IDEOGRAPH - 0xEAD3: 0x66A7, //CJK UNIFIED IDEOGRAPH - 0xEAD4: 0x669D, //CJK UNIFIED IDEOGRAPH - 0xEAD5: 0x66BE, //CJK UNIFIED IDEOGRAPH - 0xEAD6: 0x66DB, //CJK UNIFIED IDEOGRAPH - 0xEAD7: 0x66DC, //CJK UNIFIED IDEOGRAPH - 0xEAD8: 0x66E6, //CJK UNIFIED IDEOGRAPH - 0xEAD9: 0x66E9, //CJK UNIFIED IDEOGRAPH - 0xEADA: 0x8D32, //CJK UNIFIED IDEOGRAPH - 0xEADB: 0x8D33, //CJK UNIFIED IDEOGRAPH - 0xEADC: 0x8D36, //CJK UNIFIED IDEOGRAPH - 0xEADD: 0x8D3B, //CJK UNIFIED IDEOGRAPH - 0xEADE: 0x8D3D, //CJK UNIFIED IDEOGRAPH - 0xEADF: 0x8D40, //CJK UNIFIED IDEOGRAPH - 0xEAE0: 0x8D45, //CJK UNIFIED IDEOGRAPH - 0xEAE1: 0x8D46, //CJK UNIFIED IDEOGRAPH - 0xEAE2: 0x8D48, //CJK UNIFIED IDEOGRAPH - 0xEAE3: 0x8D49, //CJK UNIFIED IDEOGRAPH - 0xEAE4: 0x8D47, //CJK UNIFIED IDEOGRAPH - 0xEAE5: 0x8D4D, //CJK UNIFIED IDEOGRAPH - 0xEAE6: 0x8D55, //CJK UNIFIED IDEOGRAPH - 0xEAE7: 0x8D59, //CJK UNIFIED IDEOGRAPH - 0xEAE8: 0x89C7, //CJK UNIFIED IDEOGRAPH - 0xEAE9: 0x89CA, //CJK UNIFIED IDEOGRAPH - 0xEAEA: 0x89CB, //CJK UNIFIED IDEOGRAPH - 0xEAEB: 0x89CC, //CJK UNIFIED IDEOGRAPH - 0xEAEC: 0x89CE, //CJK UNIFIED IDEOGRAPH - 0xEAED: 0x89CF, //CJK UNIFIED IDEOGRAPH - 0xEAEE: 0x89D0, //CJK UNIFIED IDEOGRAPH - 0xEAEF: 0x89D1, //CJK UNIFIED IDEOGRAPH - 0xEAF0: 0x726E, //CJK UNIFIED IDEOGRAPH - 0xEAF1: 0x729F, //CJK UNIFIED IDEOGRAPH - 0xEAF2: 0x725D, //CJK UNIFIED IDEOGRAPH - 0xEAF3: 0x7266, //CJK UNIFIED IDEOGRAPH - 0xEAF4: 0x726F, //CJK UNIFIED IDEOGRAPH - 0xEAF5: 0x727E, //CJK UNIFIED IDEOGRAPH - 0xEAF6: 0x727F, //CJK UNIFIED IDEOGRAPH - 0xEAF7: 0x7284, //CJK UNIFIED IDEOGRAPH - 0xEAF8: 0x728B, //CJK UNIFIED IDEOGRAPH - 0xEAF9: 0x728D, //CJK UNIFIED IDEOGRAPH - 0xEAFA: 0x728F, //CJK UNIFIED IDEOGRAPH - 0xEAFB: 0x7292, //CJK UNIFIED IDEOGRAPH - 0xEAFC: 0x6308, //CJK UNIFIED IDEOGRAPH - 0xEAFD: 0x6332, //CJK UNIFIED IDEOGRAPH - 0xEAFE: 0x63B0, //CJK UNIFIED IDEOGRAPH - 0xEB40: 0x968C, //CJK UNIFIED IDEOGRAPH - 0xEB41: 0x968E, //CJK UNIFIED IDEOGRAPH - 0xEB42: 0x9691, //CJK UNIFIED IDEOGRAPH - 0xEB43: 0x9692, //CJK UNIFIED IDEOGRAPH - 0xEB44: 0x9693, //CJK UNIFIED IDEOGRAPH - 0xEB45: 0x9695, //CJK UNIFIED IDEOGRAPH - 0xEB46: 0x9696, //CJK UNIFIED IDEOGRAPH - 0xEB47: 0x969A, //CJK UNIFIED IDEOGRAPH - 0xEB48: 0x969B, //CJK UNIFIED IDEOGRAPH - 0xEB49: 0x969D, //CJK UNIFIED IDEOGRAPH - 0xEB4A: 0x969E, //CJK UNIFIED IDEOGRAPH - 0xEB4B: 0x969F, //CJK UNIFIED IDEOGRAPH - 0xEB4C: 0x96A0, //CJK UNIFIED IDEOGRAPH - 0xEB4D: 0x96A1, //CJK UNIFIED IDEOGRAPH - 0xEB4E: 0x96A2, //CJK UNIFIED IDEOGRAPH - 0xEB4F: 0x96A3, //CJK UNIFIED IDEOGRAPH - 0xEB50: 0x96A4, //CJK UNIFIED IDEOGRAPH - 0xEB51: 0x96A5, //CJK UNIFIED IDEOGRAPH - 0xEB52: 0x96A6, //CJK UNIFIED IDEOGRAPH - 0xEB53: 0x96A8, //CJK UNIFIED IDEOGRAPH - 0xEB54: 0x96A9, //CJK UNIFIED IDEOGRAPH - 0xEB55: 0x96AA, //CJK UNIFIED IDEOGRAPH - 0xEB56: 0x96AB, //CJK UNIFIED IDEOGRAPH - 0xEB57: 0x96AC, //CJK UNIFIED IDEOGRAPH - 0xEB58: 0x96AD, //CJK UNIFIED IDEOGRAPH - 0xEB59: 0x96AE, //CJK UNIFIED IDEOGRAPH - 0xEB5A: 0x96AF, //CJK UNIFIED IDEOGRAPH - 0xEB5B: 0x96B1, //CJK UNIFIED IDEOGRAPH - 0xEB5C: 0x96B2, //CJK UNIFIED IDEOGRAPH - 0xEB5D: 0x96B4, //CJK UNIFIED IDEOGRAPH - 0xEB5E: 0x96B5, //CJK UNIFIED IDEOGRAPH - 0xEB5F: 0x96B7, //CJK UNIFIED IDEOGRAPH - 0xEB60: 0x96B8, //CJK UNIFIED IDEOGRAPH - 0xEB61: 0x96BA, //CJK UNIFIED IDEOGRAPH - 0xEB62: 0x96BB, //CJK UNIFIED IDEOGRAPH - 0xEB63: 0x96BF, //CJK UNIFIED IDEOGRAPH - 0xEB64: 0x96C2, //CJK UNIFIED IDEOGRAPH - 0xEB65: 0x96C3, //CJK UNIFIED IDEOGRAPH - 0xEB66: 0x96C8, //CJK UNIFIED IDEOGRAPH - 0xEB67: 0x96CA, //CJK UNIFIED IDEOGRAPH - 0xEB68: 0x96CB, //CJK UNIFIED IDEOGRAPH - 0xEB69: 0x96D0, //CJK UNIFIED IDEOGRAPH - 0xEB6A: 0x96D1, //CJK UNIFIED IDEOGRAPH - 0xEB6B: 0x96D3, //CJK UNIFIED IDEOGRAPH - 0xEB6C: 0x96D4, //CJK UNIFIED IDEOGRAPH - 0xEB6D: 0x96D6, //CJK UNIFIED IDEOGRAPH - 0xEB6E: 0x96D7, //CJK UNIFIED IDEOGRAPH - 0xEB6F: 0x96D8, //CJK UNIFIED IDEOGRAPH - 0xEB70: 0x96D9, //CJK UNIFIED IDEOGRAPH - 0xEB71: 0x96DA, //CJK UNIFIED IDEOGRAPH - 0xEB72: 0x96DB, //CJK UNIFIED IDEOGRAPH - 0xEB73: 0x96DC, //CJK UNIFIED IDEOGRAPH - 0xEB74: 0x96DD, //CJK UNIFIED IDEOGRAPH - 0xEB75: 0x96DE, //CJK UNIFIED IDEOGRAPH - 0xEB76: 0x96DF, //CJK UNIFIED IDEOGRAPH - 0xEB77: 0x96E1, //CJK UNIFIED IDEOGRAPH - 0xEB78: 0x96E2, //CJK UNIFIED IDEOGRAPH - 0xEB79: 0x96E3, //CJK UNIFIED IDEOGRAPH - 0xEB7A: 0x96E4, //CJK UNIFIED IDEOGRAPH - 0xEB7B: 0x96E5, //CJK UNIFIED IDEOGRAPH - 0xEB7C: 0x96E6, //CJK UNIFIED IDEOGRAPH - 0xEB7D: 0x96E7, //CJK UNIFIED IDEOGRAPH - 0xEB7E: 0x96EB, //CJK UNIFIED IDEOGRAPH - 0xEB80: 0x96EC, //CJK UNIFIED IDEOGRAPH - 0xEB81: 0x96ED, //CJK UNIFIED IDEOGRAPH - 0xEB82: 0x96EE, //CJK UNIFIED IDEOGRAPH - 0xEB83: 0x96F0, //CJK UNIFIED IDEOGRAPH - 0xEB84: 0x96F1, //CJK UNIFIED IDEOGRAPH - 0xEB85: 0x96F2, //CJK UNIFIED IDEOGRAPH - 0xEB86: 0x96F4, //CJK UNIFIED IDEOGRAPH - 0xEB87: 0x96F5, //CJK UNIFIED IDEOGRAPH - 0xEB88: 0x96F8, //CJK UNIFIED IDEOGRAPH - 0xEB89: 0x96FA, //CJK UNIFIED IDEOGRAPH - 0xEB8A: 0x96FB, //CJK UNIFIED IDEOGRAPH - 0xEB8B: 0x96FC, //CJK UNIFIED IDEOGRAPH - 0xEB8C: 0x96FD, //CJK UNIFIED IDEOGRAPH - 0xEB8D: 0x96FF, //CJK UNIFIED IDEOGRAPH - 0xEB8E: 0x9702, //CJK UNIFIED IDEOGRAPH - 0xEB8F: 0x9703, //CJK UNIFIED IDEOGRAPH - 0xEB90: 0x9705, //CJK UNIFIED IDEOGRAPH - 0xEB91: 0x970A, //CJK UNIFIED IDEOGRAPH - 0xEB92: 0x970B, //CJK UNIFIED IDEOGRAPH - 0xEB93: 0x970C, //CJK UNIFIED IDEOGRAPH - 0xEB94: 0x9710, //CJK UNIFIED IDEOGRAPH - 0xEB95: 0x9711, //CJK UNIFIED IDEOGRAPH - 0xEB96: 0x9712, //CJK UNIFIED IDEOGRAPH - 0xEB97: 0x9714, //CJK UNIFIED IDEOGRAPH - 0xEB98: 0x9715, //CJK UNIFIED IDEOGRAPH - 0xEB99: 0x9717, //CJK UNIFIED IDEOGRAPH - 0xEB9A: 0x9718, //CJK UNIFIED IDEOGRAPH - 0xEB9B: 0x9719, //CJK UNIFIED IDEOGRAPH - 0xEB9C: 0x971A, //CJK UNIFIED IDEOGRAPH - 0xEB9D: 0x971B, //CJK UNIFIED IDEOGRAPH - 0xEB9E: 0x971D, //CJK UNIFIED IDEOGRAPH - 0xEB9F: 0x971F, //CJK UNIFIED IDEOGRAPH - 0xEBA0: 0x9720, //CJK UNIFIED IDEOGRAPH - 0xEBA1: 0x643F, //CJK UNIFIED IDEOGRAPH - 0xEBA2: 0x64D8, //CJK UNIFIED IDEOGRAPH - 0xEBA3: 0x8004, //CJK UNIFIED IDEOGRAPH - 0xEBA4: 0x6BEA, //CJK UNIFIED IDEOGRAPH - 0xEBA5: 0x6BF3, //CJK UNIFIED IDEOGRAPH - 0xEBA6: 0x6BFD, //CJK UNIFIED IDEOGRAPH - 0xEBA7: 0x6BF5, //CJK UNIFIED IDEOGRAPH - 0xEBA8: 0x6BF9, //CJK UNIFIED IDEOGRAPH - 0xEBA9: 0x6C05, //CJK UNIFIED IDEOGRAPH - 0xEBAA: 0x6C07, //CJK UNIFIED IDEOGRAPH - 0xEBAB: 0x6C06, //CJK UNIFIED IDEOGRAPH - 0xEBAC: 0x6C0D, //CJK UNIFIED IDEOGRAPH - 0xEBAD: 0x6C15, //CJK UNIFIED IDEOGRAPH - 0xEBAE: 0x6C18, //CJK UNIFIED IDEOGRAPH - 0xEBAF: 0x6C19, //CJK UNIFIED IDEOGRAPH - 0xEBB0: 0x6C1A, //CJK UNIFIED IDEOGRAPH - 0xEBB1: 0x6C21, //CJK UNIFIED IDEOGRAPH - 0xEBB2: 0x6C29, //CJK UNIFIED IDEOGRAPH - 0xEBB3: 0x6C24, //CJK UNIFIED IDEOGRAPH - 0xEBB4: 0x6C2A, //CJK UNIFIED IDEOGRAPH - 0xEBB5: 0x6C32, //CJK UNIFIED IDEOGRAPH - 0xEBB6: 0x6535, //CJK UNIFIED IDEOGRAPH - 0xEBB7: 0x6555, //CJK UNIFIED IDEOGRAPH - 0xEBB8: 0x656B, //CJK UNIFIED IDEOGRAPH - 0xEBB9: 0x724D, //CJK UNIFIED IDEOGRAPH - 0xEBBA: 0x7252, //CJK UNIFIED IDEOGRAPH - 0xEBBB: 0x7256, //CJK UNIFIED IDEOGRAPH - 0xEBBC: 0x7230, //CJK UNIFIED IDEOGRAPH - 0xEBBD: 0x8662, //CJK UNIFIED IDEOGRAPH - 0xEBBE: 0x5216, //CJK UNIFIED IDEOGRAPH - 0xEBBF: 0x809F, //CJK UNIFIED IDEOGRAPH - 0xEBC0: 0x809C, //CJK UNIFIED IDEOGRAPH - 0xEBC1: 0x8093, //CJK UNIFIED IDEOGRAPH - 0xEBC2: 0x80BC, //CJK UNIFIED IDEOGRAPH - 0xEBC3: 0x670A, //CJK UNIFIED IDEOGRAPH - 0xEBC4: 0x80BD, //CJK UNIFIED IDEOGRAPH - 0xEBC5: 0x80B1, //CJK UNIFIED IDEOGRAPH - 0xEBC6: 0x80AB, //CJK UNIFIED IDEOGRAPH - 0xEBC7: 0x80AD, //CJK UNIFIED IDEOGRAPH - 0xEBC8: 0x80B4, //CJK UNIFIED IDEOGRAPH - 0xEBC9: 0x80B7, //CJK UNIFIED IDEOGRAPH - 0xEBCA: 0x80E7, //CJK UNIFIED IDEOGRAPH - 0xEBCB: 0x80E8, //CJK UNIFIED IDEOGRAPH - 0xEBCC: 0x80E9, //CJK UNIFIED IDEOGRAPH - 0xEBCD: 0x80EA, //CJK UNIFIED IDEOGRAPH - 0xEBCE: 0x80DB, //CJK UNIFIED IDEOGRAPH - 0xEBCF: 0x80C2, //CJK UNIFIED IDEOGRAPH - 0xEBD0: 0x80C4, //CJK UNIFIED IDEOGRAPH - 0xEBD1: 0x80D9, //CJK UNIFIED IDEOGRAPH - 0xEBD2: 0x80CD, //CJK UNIFIED IDEOGRAPH - 0xEBD3: 0x80D7, //CJK UNIFIED IDEOGRAPH - 0xEBD4: 0x6710, //CJK UNIFIED IDEOGRAPH - 0xEBD5: 0x80DD, //CJK UNIFIED IDEOGRAPH - 0xEBD6: 0x80EB, //CJK UNIFIED IDEOGRAPH - 0xEBD7: 0x80F1, //CJK UNIFIED IDEOGRAPH - 0xEBD8: 0x80F4, //CJK UNIFIED IDEOGRAPH - 0xEBD9: 0x80ED, //CJK UNIFIED IDEOGRAPH - 0xEBDA: 0x810D, //CJK UNIFIED IDEOGRAPH - 0xEBDB: 0x810E, //CJK UNIFIED IDEOGRAPH - 0xEBDC: 0x80F2, //CJK UNIFIED IDEOGRAPH - 0xEBDD: 0x80FC, //CJK UNIFIED IDEOGRAPH - 0xEBDE: 0x6715, //CJK UNIFIED IDEOGRAPH - 0xEBDF: 0x8112, //CJK UNIFIED IDEOGRAPH - 0xEBE0: 0x8C5A, //CJK UNIFIED IDEOGRAPH - 0xEBE1: 0x8136, //CJK UNIFIED IDEOGRAPH - 0xEBE2: 0x811E, //CJK UNIFIED IDEOGRAPH - 0xEBE3: 0x812C, //CJK UNIFIED IDEOGRAPH - 0xEBE4: 0x8118, //CJK UNIFIED IDEOGRAPH - 0xEBE5: 0x8132, //CJK UNIFIED IDEOGRAPH - 0xEBE6: 0x8148, //CJK UNIFIED IDEOGRAPH - 0xEBE7: 0x814C, //CJK UNIFIED IDEOGRAPH - 0xEBE8: 0x8153, //CJK UNIFIED IDEOGRAPH - 0xEBE9: 0x8174, //CJK UNIFIED IDEOGRAPH - 0xEBEA: 0x8159, //CJK UNIFIED IDEOGRAPH - 0xEBEB: 0x815A, //CJK UNIFIED IDEOGRAPH - 0xEBEC: 0x8171, //CJK UNIFIED IDEOGRAPH - 0xEBED: 0x8160, //CJK UNIFIED IDEOGRAPH - 0xEBEE: 0x8169, //CJK UNIFIED IDEOGRAPH - 0xEBEF: 0x817C, //CJK UNIFIED IDEOGRAPH - 0xEBF0: 0x817D, //CJK UNIFIED IDEOGRAPH - 0xEBF1: 0x816D, //CJK UNIFIED IDEOGRAPH - 0xEBF2: 0x8167, //CJK UNIFIED IDEOGRAPH - 0xEBF3: 0x584D, //CJK UNIFIED IDEOGRAPH - 0xEBF4: 0x5AB5, //CJK UNIFIED IDEOGRAPH - 0xEBF5: 0x8188, //CJK UNIFIED IDEOGRAPH - 0xEBF6: 0x8182, //CJK UNIFIED IDEOGRAPH - 0xEBF7: 0x8191, //CJK UNIFIED IDEOGRAPH - 0xEBF8: 0x6ED5, //CJK UNIFIED IDEOGRAPH - 0xEBF9: 0x81A3, //CJK UNIFIED IDEOGRAPH - 0xEBFA: 0x81AA, //CJK UNIFIED IDEOGRAPH - 0xEBFB: 0x81CC, //CJK UNIFIED IDEOGRAPH - 0xEBFC: 0x6726, //CJK UNIFIED IDEOGRAPH - 0xEBFD: 0x81CA, //CJK UNIFIED IDEOGRAPH - 0xEBFE: 0x81BB, //CJK UNIFIED IDEOGRAPH - 0xEC40: 0x9721, //CJK UNIFIED IDEOGRAPH - 0xEC41: 0x9722, //CJK UNIFIED IDEOGRAPH - 0xEC42: 0x9723, //CJK UNIFIED IDEOGRAPH - 0xEC43: 0x9724, //CJK UNIFIED IDEOGRAPH - 0xEC44: 0x9725, //CJK UNIFIED IDEOGRAPH - 0xEC45: 0x9726, //CJK UNIFIED IDEOGRAPH - 0xEC46: 0x9727, //CJK UNIFIED IDEOGRAPH - 0xEC47: 0x9728, //CJK UNIFIED IDEOGRAPH - 0xEC48: 0x9729, //CJK UNIFIED IDEOGRAPH - 0xEC49: 0x972B, //CJK UNIFIED IDEOGRAPH - 0xEC4A: 0x972C, //CJK UNIFIED IDEOGRAPH - 0xEC4B: 0x972E, //CJK UNIFIED IDEOGRAPH - 0xEC4C: 0x972F, //CJK UNIFIED IDEOGRAPH - 0xEC4D: 0x9731, //CJK UNIFIED IDEOGRAPH - 0xEC4E: 0x9733, //CJK UNIFIED IDEOGRAPH - 0xEC4F: 0x9734, //CJK UNIFIED IDEOGRAPH - 0xEC50: 0x9735, //CJK UNIFIED IDEOGRAPH - 0xEC51: 0x9736, //CJK UNIFIED IDEOGRAPH - 0xEC52: 0x9737, //CJK UNIFIED IDEOGRAPH - 0xEC53: 0x973A, //CJK UNIFIED IDEOGRAPH - 0xEC54: 0x973B, //CJK UNIFIED IDEOGRAPH - 0xEC55: 0x973C, //CJK UNIFIED IDEOGRAPH - 0xEC56: 0x973D, //CJK UNIFIED IDEOGRAPH - 0xEC57: 0x973F, //CJK UNIFIED IDEOGRAPH - 0xEC58: 0x9740, //CJK UNIFIED IDEOGRAPH - 0xEC59: 0x9741, //CJK UNIFIED IDEOGRAPH - 0xEC5A: 0x9742, //CJK UNIFIED IDEOGRAPH - 0xEC5B: 0x9743, //CJK UNIFIED IDEOGRAPH - 0xEC5C: 0x9744, //CJK UNIFIED IDEOGRAPH - 0xEC5D: 0x9745, //CJK UNIFIED IDEOGRAPH - 0xEC5E: 0x9746, //CJK UNIFIED IDEOGRAPH - 0xEC5F: 0x9747, //CJK UNIFIED IDEOGRAPH - 0xEC60: 0x9748, //CJK UNIFIED IDEOGRAPH - 0xEC61: 0x9749, //CJK UNIFIED IDEOGRAPH - 0xEC62: 0x974A, //CJK UNIFIED IDEOGRAPH - 0xEC63: 0x974B, //CJK UNIFIED IDEOGRAPH - 0xEC64: 0x974C, //CJK UNIFIED IDEOGRAPH - 0xEC65: 0x974D, //CJK UNIFIED IDEOGRAPH - 0xEC66: 0x974E, //CJK UNIFIED IDEOGRAPH - 0xEC67: 0x974F, //CJK UNIFIED IDEOGRAPH - 0xEC68: 0x9750, //CJK UNIFIED IDEOGRAPH - 0xEC69: 0x9751, //CJK UNIFIED IDEOGRAPH - 0xEC6A: 0x9754, //CJK UNIFIED IDEOGRAPH - 0xEC6B: 0x9755, //CJK UNIFIED IDEOGRAPH - 0xEC6C: 0x9757, //CJK UNIFIED IDEOGRAPH - 0xEC6D: 0x9758, //CJK UNIFIED IDEOGRAPH - 0xEC6E: 0x975A, //CJK UNIFIED IDEOGRAPH - 0xEC6F: 0x975C, //CJK UNIFIED IDEOGRAPH - 0xEC70: 0x975D, //CJK UNIFIED IDEOGRAPH - 0xEC71: 0x975F, //CJK UNIFIED IDEOGRAPH - 0xEC72: 0x9763, //CJK UNIFIED IDEOGRAPH - 0xEC73: 0x9764, //CJK UNIFIED IDEOGRAPH - 0xEC74: 0x9766, //CJK UNIFIED IDEOGRAPH - 0xEC75: 0x9767, //CJK UNIFIED IDEOGRAPH - 0xEC76: 0x9768, //CJK UNIFIED IDEOGRAPH - 0xEC77: 0x976A, //CJK UNIFIED IDEOGRAPH - 0xEC78: 0x976B, //CJK UNIFIED IDEOGRAPH - 0xEC79: 0x976C, //CJK UNIFIED IDEOGRAPH - 0xEC7A: 0x976D, //CJK UNIFIED IDEOGRAPH - 0xEC7B: 0x976E, //CJK UNIFIED IDEOGRAPH - 0xEC7C: 0x976F, //CJK UNIFIED IDEOGRAPH - 0xEC7D: 0x9770, //CJK UNIFIED IDEOGRAPH - 0xEC7E: 0x9771, //CJK UNIFIED IDEOGRAPH - 0xEC80: 0x9772, //CJK UNIFIED IDEOGRAPH - 0xEC81: 0x9775, //CJK UNIFIED IDEOGRAPH - 0xEC82: 0x9777, //CJK UNIFIED IDEOGRAPH - 0xEC83: 0x9778, //CJK UNIFIED IDEOGRAPH - 0xEC84: 0x9779, //CJK UNIFIED IDEOGRAPH - 0xEC85: 0x977A, //CJK UNIFIED IDEOGRAPH - 0xEC86: 0x977B, //CJK UNIFIED IDEOGRAPH - 0xEC87: 0x977D, //CJK UNIFIED IDEOGRAPH - 0xEC88: 0x977E, //CJK UNIFIED IDEOGRAPH - 0xEC89: 0x977F, //CJK UNIFIED IDEOGRAPH - 0xEC8A: 0x9780, //CJK UNIFIED IDEOGRAPH - 0xEC8B: 0x9781, //CJK UNIFIED IDEOGRAPH - 0xEC8C: 0x9782, //CJK UNIFIED IDEOGRAPH - 0xEC8D: 0x9783, //CJK UNIFIED IDEOGRAPH - 0xEC8E: 0x9784, //CJK UNIFIED IDEOGRAPH - 0xEC8F: 0x9786, //CJK UNIFIED IDEOGRAPH - 0xEC90: 0x9787, //CJK UNIFIED IDEOGRAPH - 0xEC91: 0x9788, //CJK UNIFIED IDEOGRAPH - 0xEC92: 0x9789, //CJK UNIFIED IDEOGRAPH - 0xEC93: 0x978A, //CJK UNIFIED IDEOGRAPH - 0xEC94: 0x978C, //CJK UNIFIED IDEOGRAPH - 0xEC95: 0x978E, //CJK UNIFIED IDEOGRAPH - 0xEC96: 0x978F, //CJK UNIFIED IDEOGRAPH - 0xEC97: 0x9790, //CJK UNIFIED IDEOGRAPH - 0xEC98: 0x9793, //CJK UNIFIED IDEOGRAPH - 0xEC99: 0x9795, //CJK UNIFIED IDEOGRAPH - 0xEC9A: 0x9796, //CJK UNIFIED IDEOGRAPH - 0xEC9B: 0x9797, //CJK UNIFIED IDEOGRAPH - 0xEC9C: 0x9799, //CJK UNIFIED IDEOGRAPH - 0xEC9D: 0x979A, //CJK UNIFIED IDEOGRAPH - 0xEC9E: 0x979B, //CJK UNIFIED IDEOGRAPH - 0xEC9F: 0x979C, //CJK UNIFIED IDEOGRAPH - 0xECA0: 0x979D, //CJK UNIFIED IDEOGRAPH - 0xECA1: 0x81C1, //CJK UNIFIED IDEOGRAPH - 0xECA2: 0x81A6, //CJK UNIFIED IDEOGRAPH - 0xECA3: 0x6B24, //CJK UNIFIED IDEOGRAPH - 0xECA4: 0x6B37, //CJK UNIFIED IDEOGRAPH - 0xECA5: 0x6B39, //CJK UNIFIED IDEOGRAPH - 0xECA6: 0x6B43, //CJK UNIFIED IDEOGRAPH - 0xECA7: 0x6B46, //CJK UNIFIED IDEOGRAPH - 0xECA8: 0x6B59, //CJK UNIFIED IDEOGRAPH - 0xECA9: 0x98D1, //CJK UNIFIED IDEOGRAPH - 0xECAA: 0x98D2, //CJK UNIFIED IDEOGRAPH - 0xECAB: 0x98D3, //CJK UNIFIED IDEOGRAPH - 0xECAC: 0x98D5, //CJK UNIFIED IDEOGRAPH - 0xECAD: 0x98D9, //CJK UNIFIED IDEOGRAPH - 0xECAE: 0x98DA, //CJK UNIFIED IDEOGRAPH - 0xECAF: 0x6BB3, //CJK UNIFIED IDEOGRAPH - 0xECB0: 0x5F40, //CJK UNIFIED IDEOGRAPH - 0xECB1: 0x6BC2, //CJK UNIFIED IDEOGRAPH - 0xECB2: 0x89F3, //CJK UNIFIED IDEOGRAPH - 0xECB3: 0x6590, //CJK UNIFIED IDEOGRAPH - 0xECB4: 0x9F51, //CJK UNIFIED IDEOGRAPH - 0xECB5: 0x6593, //CJK UNIFIED IDEOGRAPH - 0xECB6: 0x65BC, //CJK UNIFIED IDEOGRAPH - 0xECB7: 0x65C6, //CJK UNIFIED IDEOGRAPH - 0xECB8: 0x65C4, //CJK UNIFIED IDEOGRAPH - 0xECB9: 0x65C3, //CJK UNIFIED IDEOGRAPH - 0xECBA: 0x65CC, //CJK UNIFIED IDEOGRAPH - 0xECBB: 0x65CE, //CJK UNIFIED IDEOGRAPH - 0xECBC: 0x65D2, //CJK UNIFIED IDEOGRAPH - 0xECBD: 0x65D6, //CJK UNIFIED IDEOGRAPH - 0xECBE: 0x7080, //CJK UNIFIED IDEOGRAPH - 0xECBF: 0x709C, //CJK UNIFIED IDEOGRAPH - 0xECC0: 0x7096, //CJK UNIFIED IDEOGRAPH - 0xECC1: 0x709D, //CJK UNIFIED IDEOGRAPH - 0xECC2: 0x70BB, //CJK UNIFIED IDEOGRAPH - 0xECC3: 0x70C0, //CJK UNIFIED IDEOGRAPH - 0xECC4: 0x70B7, //CJK UNIFIED IDEOGRAPH - 0xECC5: 0x70AB, //CJK UNIFIED IDEOGRAPH - 0xECC6: 0x70B1, //CJK UNIFIED IDEOGRAPH - 0xECC7: 0x70E8, //CJK UNIFIED IDEOGRAPH - 0xECC8: 0x70CA, //CJK UNIFIED IDEOGRAPH - 0xECC9: 0x7110, //CJK UNIFIED IDEOGRAPH - 0xECCA: 0x7113, //CJK UNIFIED IDEOGRAPH - 0xECCB: 0x7116, //CJK UNIFIED IDEOGRAPH - 0xECCC: 0x712F, //CJK UNIFIED IDEOGRAPH - 0xECCD: 0x7131, //CJK UNIFIED IDEOGRAPH - 0xECCE: 0x7173, //CJK UNIFIED IDEOGRAPH - 0xECCF: 0x715C, //CJK UNIFIED IDEOGRAPH - 0xECD0: 0x7168, //CJK UNIFIED IDEOGRAPH - 0xECD1: 0x7145, //CJK UNIFIED IDEOGRAPH - 0xECD2: 0x7172, //CJK UNIFIED IDEOGRAPH - 0xECD3: 0x714A, //CJK UNIFIED IDEOGRAPH - 0xECD4: 0x7178, //CJK UNIFIED IDEOGRAPH - 0xECD5: 0x717A, //CJK UNIFIED IDEOGRAPH - 0xECD6: 0x7198, //CJK UNIFIED IDEOGRAPH - 0xECD7: 0x71B3, //CJK UNIFIED IDEOGRAPH - 0xECD8: 0x71B5, //CJK UNIFIED IDEOGRAPH - 0xECD9: 0x71A8, //CJK UNIFIED IDEOGRAPH - 0xECDA: 0x71A0, //CJK UNIFIED IDEOGRAPH - 0xECDB: 0x71E0, //CJK UNIFIED IDEOGRAPH - 0xECDC: 0x71D4, //CJK UNIFIED IDEOGRAPH - 0xECDD: 0x71E7, //CJK UNIFIED IDEOGRAPH - 0xECDE: 0x71F9, //CJK UNIFIED IDEOGRAPH - 0xECDF: 0x721D, //CJK UNIFIED IDEOGRAPH - 0xECE0: 0x7228, //CJK UNIFIED IDEOGRAPH - 0xECE1: 0x706C, //CJK UNIFIED IDEOGRAPH - 0xECE2: 0x7118, //CJK UNIFIED IDEOGRAPH - 0xECE3: 0x7166, //CJK UNIFIED IDEOGRAPH - 0xECE4: 0x71B9, //CJK UNIFIED IDEOGRAPH - 0xECE5: 0x623E, //CJK UNIFIED IDEOGRAPH - 0xECE6: 0x623D, //CJK UNIFIED IDEOGRAPH - 0xECE7: 0x6243, //CJK UNIFIED IDEOGRAPH - 0xECE8: 0x6248, //CJK UNIFIED IDEOGRAPH - 0xECE9: 0x6249, //CJK UNIFIED IDEOGRAPH - 0xECEA: 0x793B, //CJK UNIFIED IDEOGRAPH - 0xECEB: 0x7940, //CJK UNIFIED IDEOGRAPH - 0xECEC: 0x7946, //CJK UNIFIED IDEOGRAPH - 0xECED: 0x7949, //CJK UNIFIED IDEOGRAPH - 0xECEE: 0x795B, //CJK UNIFIED IDEOGRAPH - 0xECEF: 0x795C, //CJK UNIFIED IDEOGRAPH - 0xECF0: 0x7953, //CJK UNIFIED IDEOGRAPH - 0xECF1: 0x795A, //CJK UNIFIED IDEOGRAPH - 0xECF2: 0x7962, //CJK UNIFIED IDEOGRAPH - 0xECF3: 0x7957, //CJK UNIFIED IDEOGRAPH - 0xECF4: 0x7960, //CJK UNIFIED IDEOGRAPH - 0xECF5: 0x796F, //CJK UNIFIED IDEOGRAPH - 0xECF6: 0x7967, //CJK UNIFIED IDEOGRAPH - 0xECF7: 0x797A, //CJK UNIFIED IDEOGRAPH - 0xECF8: 0x7985, //CJK UNIFIED IDEOGRAPH - 0xECF9: 0x798A, //CJK UNIFIED IDEOGRAPH - 0xECFA: 0x799A, //CJK UNIFIED IDEOGRAPH - 0xECFB: 0x79A7, //CJK UNIFIED IDEOGRAPH - 0xECFC: 0x79B3, //CJK UNIFIED IDEOGRAPH - 0xECFD: 0x5FD1, //CJK UNIFIED IDEOGRAPH - 0xECFE: 0x5FD0, //CJK UNIFIED IDEOGRAPH - 0xED40: 0x979E, //CJK UNIFIED IDEOGRAPH - 0xED41: 0x979F, //CJK UNIFIED IDEOGRAPH - 0xED42: 0x97A1, //CJK UNIFIED IDEOGRAPH - 0xED43: 0x97A2, //CJK UNIFIED IDEOGRAPH - 0xED44: 0x97A4, //CJK UNIFIED IDEOGRAPH - 0xED45: 0x97A5, //CJK UNIFIED IDEOGRAPH - 0xED46: 0x97A6, //CJK UNIFIED IDEOGRAPH - 0xED47: 0x97A7, //CJK UNIFIED IDEOGRAPH - 0xED48: 0x97A8, //CJK UNIFIED IDEOGRAPH - 0xED49: 0x97A9, //CJK UNIFIED IDEOGRAPH - 0xED4A: 0x97AA, //CJK UNIFIED IDEOGRAPH - 0xED4B: 0x97AC, //CJK UNIFIED IDEOGRAPH - 0xED4C: 0x97AE, //CJK UNIFIED IDEOGRAPH - 0xED4D: 0x97B0, //CJK UNIFIED IDEOGRAPH - 0xED4E: 0x97B1, //CJK UNIFIED IDEOGRAPH - 0xED4F: 0x97B3, //CJK UNIFIED IDEOGRAPH - 0xED50: 0x97B5, //CJK UNIFIED IDEOGRAPH - 0xED51: 0x97B6, //CJK UNIFIED IDEOGRAPH - 0xED52: 0x97B7, //CJK UNIFIED IDEOGRAPH - 0xED53: 0x97B8, //CJK UNIFIED IDEOGRAPH - 0xED54: 0x97B9, //CJK UNIFIED IDEOGRAPH - 0xED55: 0x97BA, //CJK UNIFIED IDEOGRAPH - 0xED56: 0x97BB, //CJK UNIFIED IDEOGRAPH - 0xED57: 0x97BC, //CJK UNIFIED IDEOGRAPH - 0xED58: 0x97BD, //CJK UNIFIED IDEOGRAPH - 0xED59: 0x97BE, //CJK UNIFIED IDEOGRAPH - 0xED5A: 0x97BF, //CJK UNIFIED IDEOGRAPH - 0xED5B: 0x97C0, //CJK UNIFIED IDEOGRAPH - 0xED5C: 0x97C1, //CJK UNIFIED IDEOGRAPH - 0xED5D: 0x97C2, //CJK UNIFIED IDEOGRAPH - 0xED5E: 0x97C3, //CJK UNIFIED IDEOGRAPH - 0xED5F: 0x97C4, //CJK UNIFIED IDEOGRAPH - 0xED60: 0x97C5, //CJK UNIFIED IDEOGRAPH - 0xED61: 0x97C6, //CJK UNIFIED IDEOGRAPH - 0xED62: 0x97C7, //CJK UNIFIED IDEOGRAPH - 0xED63: 0x97C8, //CJK UNIFIED IDEOGRAPH - 0xED64: 0x97C9, //CJK UNIFIED IDEOGRAPH - 0xED65: 0x97CA, //CJK UNIFIED IDEOGRAPH - 0xED66: 0x97CB, //CJK UNIFIED IDEOGRAPH - 0xED67: 0x97CC, //CJK UNIFIED IDEOGRAPH - 0xED68: 0x97CD, //CJK UNIFIED IDEOGRAPH - 0xED69: 0x97CE, //CJK UNIFIED IDEOGRAPH - 0xED6A: 0x97CF, //CJK UNIFIED IDEOGRAPH - 0xED6B: 0x97D0, //CJK UNIFIED IDEOGRAPH - 0xED6C: 0x97D1, //CJK UNIFIED IDEOGRAPH - 0xED6D: 0x97D2, //CJK UNIFIED IDEOGRAPH - 0xED6E: 0x97D3, //CJK UNIFIED IDEOGRAPH - 0xED6F: 0x97D4, //CJK UNIFIED IDEOGRAPH - 0xED70: 0x97D5, //CJK UNIFIED IDEOGRAPH - 0xED71: 0x97D6, //CJK UNIFIED IDEOGRAPH - 0xED72: 0x97D7, //CJK UNIFIED IDEOGRAPH - 0xED73: 0x97D8, //CJK UNIFIED IDEOGRAPH - 0xED74: 0x97D9, //CJK UNIFIED IDEOGRAPH - 0xED75: 0x97DA, //CJK UNIFIED IDEOGRAPH - 0xED76: 0x97DB, //CJK UNIFIED IDEOGRAPH - 0xED77: 0x97DC, //CJK UNIFIED IDEOGRAPH - 0xED78: 0x97DD, //CJK UNIFIED IDEOGRAPH - 0xED79: 0x97DE, //CJK UNIFIED IDEOGRAPH - 0xED7A: 0x97DF, //CJK UNIFIED IDEOGRAPH - 0xED7B: 0x97E0, //CJK UNIFIED IDEOGRAPH - 0xED7C: 0x97E1, //CJK UNIFIED IDEOGRAPH - 0xED7D: 0x97E2, //CJK UNIFIED IDEOGRAPH - 0xED7E: 0x97E3, //CJK UNIFIED IDEOGRAPH - 0xED80: 0x97E4, //CJK UNIFIED IDEOGRAPH - 0xED81: 0x97E5, //CJK UNIFIED IDEOGRAPH - 0xED82: 0x97E8, //CJK UNIFIED IDEOGRAPH - 0xED83: 0x97EE, //CJK UNIFIED IDEOGRAPH - 0xED84: 0x97EF, //CJK UNIFIED IDEOGRAPH - 0xED85: 0x97F0, //CJK UNIFIED IDEOGRAPH - 0xED86: 0x97F1, //CJK UNIFIED IDEOGRAPH - 0xED87: 0x97F2, //CJK UNIFIED IDEOGRAPH - 0xED88: 0x97F4, //CJK UNIFIED IDEOGRAPH - 0xED89: 0x97F7, //CJK UNIFIED IDEOGRAPH - 0xED8A: 0x97F8, //CJK UNIFIED IDEOGRAPH - 0xED8B: 0x97F9, //CJK UNIFIED IDEOGRAPH - 0xED8C: 0x97FA, //CJK UNIFIED IDEOGRAPH - 0xED8D: 0x97FB, //CJK UNIFIED IDEOGRAPH - 0xED8E: 0x97FC, //CJK UNIFIED IDEOGRAPH - 0xED8F: 0x97FD, //CJK UNIFIED IDEOGRAPH - 0xED90: 0x97FE, //CJK UNIFIED IDEOGRAPH - 0xED91: 0x97FF, //CJK UNIFIED IDEOGRAPH - 0xED92: 0x9800, //CJK UNIFIED IDEOGRAPH - 0xED93: 0x9801, //CJK UNIFIED IDEOGRAPH - 0xED94: 0x9802, //CJK UNIFIED IDEOGRAPH - 0xED95: 0x9803, //CJK UNIFIED IDEOGRAPH - 0xED96: 0x9804, //CJK UNIFIED IDEOGRAPH - 0xED97: 0x9805, //CJK UNIFIED IDEOGRAPH - 0xED98: 0x9806, //CJK UNIFIED IDEOGRAPH - 0xED99: 0x9807, //CJK UNIFIED IDEOGRAPH - 0xED9A: 0x9808, //CJK UNIFIED IDEOGRAPH - 0xED9B: 0x9809, //CJK UNIFIED IDEOGRAPH - 0xED9C: 0x980A, //CJK UNIFIED IDEOGRAPH - 0xED9D: 0x980B, //CJK UNIFIED IDEOGRAPH - 0xED9E: 0x980C, //CJK UNIFIED IDEOGRAPH - 0xED9F: 0x980D, //CJK UNIFIED IDEOGRAPH - 0xEDA0: 0x980E, //CJK UNIFIED IDEOGRAPH - 0xEDA1: 0x603C, //CJK UNIFIED IDEOGRAPH - 0xEDA2: 0x605D, //CJK UNIFIED IDEOGRAPH - 0xEDA3: 0x605A, //CJK UNIFIED IDEOGRAPH - 0xEDA4: 0x6067, //CJK UNIFIED IDEOGRAPH - 0xEDA5: 0x6041, //CJK UNIFIED IDEOGRAPH - 0xEDA6: 0x6059, //CJK UNIFIED IDEOGRAPH - 0xEDA7: 0x6063, //CJK UNIFIED IDEOGRAPH - 0xEDA8: 0x60AB, //CJK UNIFIED IDEOGRAPH - 0xEDA9: 0x6106, //CJK UNIFIED IDEOGRAPH - 0xEDAA: 0x610D, //CJK UNIFIED IDEOGRAPH - 0xEDAB: 0x615D, //CJK UNIFIED IDEOGRAPH - 0xEDAC: 0x61A9, //CJK UNIFIED IDEOGRAPH - 0xEDAD: 0x619D, //CJK UNIFIED IDEOGRAPH - 0xEDAE: 0x61CB, //CJK UNIFIED IDEOGRAPH - 0xEDAF: 0x61D1, //CJK UNIFIED IDEOGRAPH - 0xEDB0: 0x6206, //CJK UNIFIED IDEOGRAPH - 0xEDB1: 0x8080, //CJK UNIFIED IDEOGRAPH - 0xEDB2: 0x807F, //CJK UNIFIED IDEOGRAPH - 0xEDB3: 0x6C93, //CJK UNIFIED IDEOGRAPH - 0xEDB4: 0x6CF6, //CJK UNIFIED IDEOGRAPH - 0xEDB5: 0x6DFC, //CJK UNIFIED IDEOGRAPH - 0xEDB6: 0x77F6, //CJK UNIFIED IDEOGRAPH - 0xEDB7: 0x77F8, //CJK UNIFIED IDEOGRAPH - 0xEDB8: 0x7800, //CJK UNIFIED IDEOGRAPH - 0xEDB9: 0x7809, //CJK UNIFIED IDEOGRAPH - 0xEDBA: 0x7817, //CJK UNIFIED IDEOGRAPH - 0xEDBB: 0x7818, //CJK UNIFIED IDEOGRAPH - 0xEDBC: 0x7811, //CJK UNIFIED IDEOGRAPH - 0xEDBD: 0x65AB, //CJK UNIFIED IDEOGRAPH - 0xEDBE: 0x782D, //CJK UNIFIED IDEOGRAPH - 0xEDBF: 0x781C, //CJK UNIFIED IDEOGRAPH - 0xEDC0: 0x781D, //CJK UNIFIED IDEOGRAPH - 0xEDC1: 0x7839, //CJK UNIFIED IDEOGRAPH - 0xEDC2: 0x783A, //CJK UNIFIED IDEOGRAPH - 0xEDC3: 0x783B, //CJK UNIFIED IDEOGRAPH - 0xEDC4: 0x781F, //CJK UNIFIED IDEOGRAPH - 0xEDC5: 0x783C, //CJK UNIFIED IDEOGRAPH - 0xEDC6: 0x7825, //CJK UNIFIED IDEOGRAPH - 0xEDC7: 0x782C, //CJK UNIFIED IDEOGRAPH - 0xEDC8: 0x7823, //CJK UNIFIED IDEOGRAPH - 0xEDC9: 0x7829, //CJK UNIFIED IDEOGRAPH - 0xEDCA: 0x784E, //CJK UNIFIED IDEOGRAPH - 0xEDCB: 0x786D, //CJK UNIFIED IDEOGRAPH - 0xEDCC: 0x7856, //CJK UNIFIED IDEOGRAPH - 0xEDCD: 0x7857, //CJK UNIFIED IDEOGRAPH - 0xEDCE: 0x7826, //CJK UNIFIED IDEOGRAPH - 0xEDCF: 0x7850, //CJK UNIFIED IDEOGRAPH - 0xEDD0: 0x7847, //CJK UNIFIED IDEOGRAPH - 0xEDD1: 0x784C, //CJK UNIFIED IDEOGRAPH - 0xEDD2: 0x786A, //CJK UNIFIED IDEOGRAPH - 0xEDD3: 0x789B, //CJK UNIFIED IDEOGRAPH - 0xEDD4: 0x7893, //CJK UNIFIED IDEOGRAPH - 0xEDD5: 0x789A, //CJK UNIFIED IDEOGRAPH - 0xEDD6: 0x7887, //CJK UNIFIED IDEOGRAPH - 0xEDD7: 0x789C, //CJK UNIFIED IDEOGRAPH - 0xEDD8: 0x78A1, //CJK UNIFIED IDEOGRAPH - 0xEDD9: 0x78A3, //CJK UNIFIED IDEOGRAPH - 0xEDDA: 0x78B2, //CJK UNIFIED IDEOGRAPH - 0xEDDB: 0x78B9, //CJK UNIFIED IDEOGRAPH - 0xEDDC: 0x78A5, //CJK UNIFIED IDEOGRAPH - 0xEDDD: 0x78D4, //CJK UNIFIED IDEOGRAPH - 0xEDDE: 0x78D9, //CJK UNIFIED IDEOGRAPH - 0xEDDF: 0x78C9, //CJK UNIFIED IDEOGRAPH - 0xEDE0: 0x78EC, //CJK UNIFIED IDEOGRAPH - 0xEDE1: 0x78F2, //CJK UNIFIED IDEOGRAPH - 0xEDE2: 0x7905, //CJK UNIFIED IDEOGRAPH - 0xEDE3: 0x78F4, //CJK UNIFIED IDEOGRAPH - 0xEDE4: 0x7913, //CJK UNIFIED IDEOGRAPH - 0xEDE5: 0x7924, //CJK UNIFIED IDEOGRAPH - 0xEDE6: 0x791E, //CJK UNIFIED IDEOGRAPH - 0xEDE7: 0x7934, //CJK UNIFIED IDEOGRAPH - 0xEDE8: 0x9F9B, //CJK UNIFIED IDEOGRAPH - 0xEDE9: 0x9EF9, //CJK UNIFIED IDEOGRAPH - 0xEDEA: 0x9EFB, //CJK UNIFIED IDEOGRAPH - 0xEDEB: 0x9EFC, //CJK UNIFIED IDEOGRAPH - 0xEDEC: 0x76F1, //CJK UNIFIED IDEOGRAPH - 0xEDED: 0x7704, //CJK UNIFIED IDEOGRAPH - 0xEDEE: 0x770D, //CJK UNIFIED IDEOGRAPH - 0xEDEF: 0x76F9, //CJK UNIFIED IDEOGRAPH - 0xEDF0: 0x7707, //CJK UNIFIED IDEOGRAPH - 0xEDF1: 0x7708, //CJK UNIFIED IDEOGRAPH - 0xEDF2: 0x771A, //CJK UNIFIED IDEOGRAPH - 0xEDF3: 0x7722, //CJK UNIFIED IDEOGRAPH - 0xEDF4: 0x7719, //CJK UNIFIED IDEOGRAPH - 0xEDF5: 0x772D, //CJK UNIFIED IDEOGRAPH - 0xEDF6: 0x7726, //CJK UNIFIED IDEOGRAPH - 0xEDF7: 0x7735, //CJK UNIFIED IDEOGRAPH - 0xEDF8: 0x7738, //CJK UNIFIED IDEOGRAPH - 0xEDF9: 0x7750, //CJK UNIFIED IDEOGRAPH - 0xEDFA: 0x7751, //CJK UNIFIED IDEOGRAPH - 0xEDFB: 0x7747, //CJK UNIFIED IDEOGRAPH - 0xEDFC: 0x7743, //CJK UNIFIED IDEOGRAPH - 0xEDFD: 0x775A, //CJK UNIFIED IDEOGRAPH - 0xEDFE: 0x7768, //CJK UNIFIED IDEOGRAPH - 0xEE40: 0x980F, //CJK UNIFIED IDEOGRAPH - 0xEE41: 0x9810, //CJK UNIFIED IDEOGRAPH - 0xEE42: 0x9811, //CJK UNIFIED IDEOGRAPH - 0xEE43: 0x9812, //CJK UNIFIED IDEOGRAPH - 0xEE44: 0x9813, //CJK UNIFIED IDEOGRAPH - 0xEE45: 0x9814, //CJK UNIFIED IDEOGRAPH - 0xEE46: 0x9815, //CJK UNIFIED IDEOGRAPH - 0xEE47: 0x9816, //CJK UNIFIED IDEOGRAPH - 0xEE48: 0x9817, //CJK UNIFIED IDEOGRAPH - 0xEE49: 0x9818, //CJK UNIFIED IDEOGRAPH - 0xEE4A: 0x9819, //CJK UNIFIED IDEOGRAPH - 0xEE4B: 0x981A, //CJK UNIFIED IDEOGRAPH - 0xEE4C: 0x981B, //CJK UNIFIED IDEOGRAPH - 0xEE4D: 0x981C, //CJK UNIFIED IDEOGRAPH - 0xEE4E: 0x981D, //CJK UNIFIED IDEOGRAPH - 0xEE4F: 0x981E, //CJK UNIFIED IDEOGRAPH - 0xEE50: 0x981F, //CJK UNIFIED IDEOGRAPH - 0xEE51: 0x9820, //CJK UNIFIED IDEOGRAPH - 0xEE52: 0x9821, //CJK UNIFIED IDEOGRAPH - 0xEE53: 0x9822, //CJK UNIFIED IDEOGRAPH - 0xEE54: 0x9823, //CJK UNIFIED IDEOGRAPH - 0xEE55: 0x9824, //CJK UNIFIED IDEOGRAPH - 0xEE56: 0x9825, //CJK UNIFIED IDEOGRAPH - 0xEE57: 0x9826, //CJK UNIFIED IDEOGRAPH - 0xEE58: 0x9827, //CJK UNIFIED IDEOGRAPH - 0xEE59: 0x9828, //CJK UNIFIED IDEOGRAPH - 0xEE5A: 0x9829, //CJK UNIFIED IDEOGRAPH - 0xEE5B: 0x982A, //CJK UNIFIED IDEOGRAPH - 0xEE5C: 0x982B, //CJK UNIFIED IDEOGRAPH - 0xEE5D: 0x982C, //CJK UNIFIED IDEOGRAPH - 0xEE5E: 0x982D, //CJK UNIFIED IDEOGRAPH - 0xEE5F: 0x982E, //CJK UNIFIED IDEOGRAPH - 0xEE60: 0x982F, //CJK UNIFIED IDEOGRAPH - 0xEE61: 0x9830, //CJK UNIFIED IDEOGRAPH - 0xEE62: 0x9831, //CJK UNIFIED IDEOGRAPH - 0xEE63: 0x9832, //CJK UNIFIED IDEOGRAPH - 0xEE64: 0x9833, //CJK UNIFIED IDEOGRAPH - 0xEE65: 0x9834, //CJK UNIFIED IDEOGRAPH - 0xEE66: 0x9835, //CJK UNIFIED IDEOGRAPH - 0xEE67: 0x9836, //CJK UNIFIED IDEOGRAPH - 0xEE68: 0x9837, //CJK UNIFIED IDEOGRAPH - 0xEE69: 0x9838, //CJK UNIFIED IDEOGRAPH - 0xEE6A: 0x9839, //CJK UNIFIED IDEOGRAPH - 0xEE6B: 0x983A, //CJK UNIFIED IDEOGRAPH - 0xEE6C: 0x983B, //CJK UNIFIED IDEOGRAPH - 0xEE6D: 0x983C, //CJK UNIFIED IDEOGRAPH - 0xEE6E: 0x983D, //CJK UNIFIED IDEOGRAPH - 0xEE6F: 0x983E, //CJK UNIFIED IDEOGRAPH - 0xEE70: 0x983F, //CJK UNIFIED IDEOGRAPH - 0xEE71: 0x9840, //CJK UNIFIED IDEOGRAPH - 0xEE72: 0x9841, //CJK UNIFIED IDEOGRAPH - 0xEE73: 0x9842, //CJK UNIFIED IDEOGRAPH - 0xEE74: 0x9843, //CJK UNIFIED IDEOGRAPH - 0xEE75: 0x9844, //CJK UNIFIED IDEOGRAPH - 0xEE76: 0x9845, //CJK UNIFIED IDEOGRAPH - 0xEE77: 0x9846, //CJK UNIFIED IDEOGRAPH - 0xEE78: 0x9847, //CJK UNIFIED IDEOGRAPH - 0xEE79: 0x9848, //CJK UNIFIED IDEOGRAPH - 0xEE7A: 0x9849, //CJK UNIFIED IDEOGRAPH - 0xEE7B: 0x984A, //CJK UNIFIED IDEOGRAPH - 0xEE7C: 0x984B, //CJK UNIFIED IDEOGRAPH - 0xEE7D: 0x984C, //CJK UNIFIED IDEOGRAPH - 0xEE7E: 0x984D, //CJK UNIFIED IDEOGRAPH - 0xEE80: 0x984E, //CJK UNIFIED IDEOGRAPH - 0xEE81: 0x984F, //CJK UNIFIED IDEOGRAPH - 0xEE82: 0x9850, //CJK UNIFIED IDEOGRAPH - 0xEE83: 0x9851, //CJK UNIFIED IDEOGRAPH - 0xEE84: 0x9852, //CJK UNIFIED IDEOGRAPH - 0xEE85: 0x9853, //CJK UNIFIED IDEOGRAPH - 0xEE86: 0x9854, //CJK UNIFIED IDEOGRAPH - 0xEE87: 0x9855, //CJK UNIFIED IDEOGRAPH - 0xEE88: 0x9856, //CJK UNIFIED IDEOGRAPH - 0xEE89: 0x9857, //CJK UNIFIED IDEOGRAPH - 0xEE8A: 0x9858, //CJK UNIFIED IDEOGRAPH - 0xEE8B: 0x9859, //CJK UNIFIED IDEOGRAPH - 0xEE8C: 0x985A, //CJK UNIFIED IDEOGRAPH - 0xEE8D: 0x985B, //CJK UNIFIED IDEOGRAPH - 0xEE8E: 0x985C, //CJK UNIFIED IDEOGRAPH - 0xEE8F: 0x985D, //CJK UNIFIED IDEOGRAPH - 0xEE90: 0x985E, //CJK UNIFIED IDEOGRAPH - 0xEE91: 0x985F, //CJK UNIFIED IDEOGRAPH - 0xEE92: 0x9860, //CJK UNIFIED IDEOGRAPH - 0xEE93: 0x9861, //CJK UNIFIED IDEOGRAPH - 0xEE94: 0x9862, //CJK UNIFIED IDEOGRAPH - 0xEE95: 0x9863, //CJK UNIFIED IDEOGRAPH - 0xEE96: 0x9864, //CJK UNIFIED IDEOGRAPH - 0xEE97: 0x9865, //CJK UNIFIED IDEOGRAPH - 0xEE98: 0x9866, //CJK UNIFIED IDEOGRAPH - 0xEE99: 0x9867, //CJK UNIFIED IDEOGRAPH - 0xEE9A: 0x9868, //CJK UNIFIED IDEOGRAPH - 0xEE9B: 0x9869, //CJK UNIFIED IDEOGRAPH - 0xEE9C: 0x986A, //CJK UNIFIED IDEOGRAPH - 0xEE9D: 0x986B, //CJK UNIFIED IDEOGRAPH - 0xEE9E: 0x986C, //CJK UNIFIED IDEOGRAPH - 0xEE9F: 0x986D, //CJK UNIFIED IDEOGRAPH - 0xEEA0: 0x986E, //CJK UNIFIED IDEOGRAPH - 0xEEA1: 0x7762, //CJK UNIFIED IDEOGRAPH - 0xEEA2: 0x7765, //CJK UNIFIED IDEOGRAPH - 0xEEA3: 0x777F, //CJK UNIFIED IDEOGRAPH - 0xEEA4: 0x778D, //CJK UNIFIED IDEOGRAPH - 0xEEA5: 0x777D, //CJK UNIFIED IDEOGRAPH - 0xEEA6: 0x7780, //CJK UNIFIED IDEOGRAPH - 0xEEA7: 0x778C, //CJK UNIFIED IDEOGRAPH - 0xEEA8: 0x7791, //CJK UNIFIED IDEOGRAPH - 0xEEA9: 0x779F, //CJK UNIFIED IDEOGRAPH - 0xEEAA: 0x77A0, //CJK UNIFIED IDEOGRAPH - 0xEEAB: 0x77B0, //CJK UNIFIED IDEOGRAPH - 0xEEAC: 0x77B5, //CJK UNIFIED IDEOGRAPH - 0xEEAD: 0x77BD, //CJK UNIFIED IDEOGRAPH - 0xEEAE: 0x753A, //CJK UNIFIED IDEOGRAPH - 0xEEAF: 0x7540, //CJK UNIFIED IDEOGRAPH - 0xEEB0: 0x754E, //CJK UNIFIED IDEOGRAPH - 0xEEB1: 0x754B, //CJK UNIFIED IDEOGRAPH - 0xEEB2: 0x7548, //CJK UNIFIED IDEOGRAPH - 0xEEB3: 0x755B, //CJK UNIFIED IDEOGRAPH - 0xEEB4: 0x7572, //CJK UNIFIED IDEOGRAPH - 0xEEB5: 0x7579, //CJK UNIFIED IDEOGRAPH - 0xEEB6: 0x7583, //CJK UNIFIED IDEOGRAPH - 0xEEB7: 0x7F58, //CJK UNIFIED IDEOGRAPH - 0xEEB8: 0x7F61, //CJK UNIFIED IDEOGRAPH - 0xEEB9: 0x7F5F, //CJK UNIFIED IDEOGRAPH - 0xEEBA: 0x8A48, //CJK UNIFIED IDEOGRAPH - 0xEEBB: 0x7F68, //CJK UNIFIED IDEOGRAPH - 0xEEBC: 0x7F74, //CJK UNIFIED IDEOGRAPH - 0xEEBD: 0x7F71, //CJK UNIFIED IDEOGRAPH - 0xEEBE: 0x7F79, //CJK UNIFIED IDEOGRAPH - 0xEEBF: 0x7F81, //CJK UNIFIED IDEOGRAPH - 0xEEC0: 0x7F7E, //CJK UNIFIED IDEOGRAPH - 0xEEC1: 0x76CD, //CJK UNIFIED IDEOGRAPH - 0xEEC2: 0x76E5, //CJK UNIFIED IDEOGRAPH - 0xEEC3: 0x8832, //CJK UNIFIED IDEOGRAPH - 0xEEC4: 0x9485, //CJK UNIFIED IDEOGRAPH - 0xEEC5: 0x9486, //CJK UNIFIED IDEOGRAPH - 0xEEC6: 0x9487, //CJK UNIFIED IDEOGRAPH - 0xEEC7: 0x948B, //CJK UNIFIED IDEOGRAPH - 0xEEC8: 0x948A, //CJK UNIFIED IDEOGRAPH - 0xEEC9: 0x948C, //CJK UNIFIED IDEOGRAPH - 0xEECA: 0x948D, //CJK UNIFIED IDEOGRAPH - 0xEECB: 0x948F, //CJK UNIFIED IDEOGRAPH - 0xEECC: 0x9490, //CJK UNIFIED IDEOGRAPH - 0xEECD: 0x9494, //CJK UNIFIED IDEOGRAPH - 0xEECE: 0x9497, //CJK UNIFIED IDEOGRAPH - 0xEECF: 0x9495, //CJK UNIFIED IDEOGRAPH - 0xEED0: 0x949A, //CJK UNIFIED IDEOGRAPH - 0xEED1: 0x949B, //CJK UNIFIED IDEOGRAPH - 0xEED2: 0x949C, //CJK UNIFIED IDEOGRAPH - 0xEED3: 0x94A3, //CJK UNIFIED IDEOGRAPH - 0xEED4: 0x94A4, //CJK UNIFIED IDEOGRAPH - 0xEED5: 0x94AB, //CJK UNIFIED IDEOGRAPH - 0xEED6: 0x94AA, //CJK UNIFIED IDEOGRAPH - 0xEED7: 0x94AD, //CJK UNIFIED IDEOGRAPH - 0xEED8: 0x94AC, //CJK UNIFIED IDEOGRAPH - 0xEED9: 0x94AF, //CJK UNIFIED IDEOGRAPH - 0xEEDA: 0x94B0, //CJK UNIFIED IDEOGRAPH - 0xEEDB: 0x94B2, //CJK UNIFIED IDEOGRAPH - 0xEEDC: 0x94B4, //CJK UNIFIED IDEOGRAPH - 0xEEDD: 0x94B6, //CJK UNIFIED IDEOGRAPH - 0xEEDE: 0x94B7, //CJK UNIFIED IDEOGRAPH - 0xEEDF: 0x94B8, //CJK UNIFIED IDEOGRAPH - 0xEEE0: 0x94B9, //CJK UNIFIED IDEOGRAPH - 0xEEE1: 0x94BA, //CJK UNIFIED IDEOGRAPH - 0xEEE2: 0x94BC, //CJK UNIFIED IDEOGRAPH - 0xEEE3: 0x94BD, //CJK UNIFIED IDEOGRAPH - 0xEEE4: 0x94BF, //CJK UNIFIED IDEOGRAPH - 0xEEE5: 0x94C4, //CJK UNIFIED IDEOGRAPH - 0xEEE6: 0x94C8, //CJK UNIFIED IDEOGRAPH - 0xEEE7: 0x94C9, //CJK UNIFIED IDEOGRAPH - 0xEEE8: 0x94CA, //CJK UNIFIED IDEOGRAPH - 0xEEE9: 0x94CB, //CJK UNIFIED IDEOGRAPH - 0xEEEA: 0x94CC, //CJK UNIFIED IDEOGRAPH - 0xEEEB: 0x94CD, //CJK UNIFIED IDEOGRAPH - 0xEEEC: 0x94CE, //CJK UNIFIED IDEOGRAPH - 0xEEED: 0x94D0, //CJK UNIFIED IDEOGRAPH - 0xEEEE: 0x94D1, //CJK UNIFIED IDEOGRAPH - 0xEEEF: 0x94D2, //CJK UNIFIED IDEOGRAPH - 0xEEF0: 0x94D5, //CJK UNIFIED IDEOGRAPH - 0xEEF1: 0x94D6, //CJK UNIFIED IDEOGRAPH - 0xEEF2: 0x94D7, //CJK UNIFIED IDEOGRAPH - 0xEEF3: 0x94D9, //CJK UNIFIED IDEOGRAPH - 0xEEF4: 0x94D8, //CJK UNIFIED IDEOGRAPH - 0xEEF5: 0x94DB, //CJK UNIFIED IDEOGRAPH - 0xEEF6: 0x94DE, //CJK UNIFIED IDEOGRAPH - 0xEEF7: 0x94DF, //CJK UNIFIED IDEOGRAPH - 0xEEF8: 0x94E0, //CJK UNIFIED IDEOGRAPH - 0xEEF9: 0x94E2, //CJK UNIFIED IDEOGRAPH - 0xEEFA: 0x94E4, //CJK UNIFIED IDEOGRAPH - 0xEEFB: 0x94E5, //CJK UNIFIED IDEOGRAPH - 0xEEFC: 0x94E7, //CJK UNIFIED IDEOGRAPH - 0xEEFD: 0x94E8, //CJK UNIFIED IDEOGRAPH - 0xEEFE: 0x94EA, //CJK UNIFIED IDEOGRAPH - 0xEF40: 0x986F, //CJK UNIFIED IDEOGRAPH - 0xEF41: 0x9870, //CJK UNIFIED IDEOGRAPH - 0xEF42: 0x9871, //CJK UNIFIED IDEOGRAPH - 0xEF43: 0x9872, //CJK UNIFIED IDEOGRAPH - 0xEF44: 0x9873, //CJK UNIFIED IDEOGRAPH - 0xEF45: 0x9874, //CJK UNIFIED IDEOGRAPH - 0xEF46: 0x988B, //CJK UNIFIED IDEOGRAPH - 0xEF47: 0x988E, //CJK UNIFIED IDEOGRAPH - 0xEF48: 0x9892, //CJK UNIFIED IDEOGRAPH - 0xEF49: 0x9895, //CJK UNIFIED IDEOGRAPH - 0xEF4A: 0x9899, //CJK UNIFIED IDEOGRAPH - 0xEF4B: 0x98A3, //CJK UNIFIED IDEOGRAPH - 0xEF4C: 0x98A8, //CJK UNIFIED IDEOGRAPH - 0xEF4D: 0x98A9, //CJK UNIFIED IDEOGRAPH - 0xEF4E: 0x98AA, //CJK UNIFIED IDEOGRAPH - 0xEF4F: 0x98AB, //CJK UNIFIED IDEOGRAPH - 0xEF50: 0x98AC, //CJK UNIFIED IDEOGRAPH - 0xEF51: 0x98AD, //CJK UNIFIED IDEOGRAPH - 0xEF52: 0x98AE, //CJK UNIFIED IDEOGRAPH - 0xEF53: 0x98AF, //CJK UNIFIED IDEOGRAPH - 0xEF54: 0x98B0, //CJK UNIFIED IDEOGRAPH - 0xEF55: 0x98B1, //CJK UNIFIED IDEOGRAPH - 0xEF56: 0x98B2, //CJK UNIFIED IDEOGRAPH - 0xEF57: 0x98B3, //CJK UNIFIED IDEOGRAPH - 0xEF58: 0x98B4, //CJK UNIFIED IDEOGRAPH - 0xEF59: 0x98B5, //CJK UNIFIED IDEOGRAPH - 0xEF5A: 0x98B6, //CJK UNIFIED IDEOGRAPH - 0xEF5B: 0x98B7, //CJK UNIFIED IDEOGRAPH - 0xEF5C: 0x98B8, //CJK UNIFIED IDEOGRAPH - 0xEF5D: 0x98B9, //CJK UNIFIED IDEOGRAPH - 0xEF5E: 0x98BA, //CJK UNIFIED IDEOGRAPH - 0xEF5F: 0x98BB, //CJK UNIFIED IDEOGRAPH - 0xEF60: 0x98BC, //CJK UNIFIED IDEOGRAPH - 0xEF61: 0x98BD, //CJK UNIFIED IDEOGRAPH - 0xEF62: 0x98BE, //CJK UNIFIED IDEOGRAPH - 0xEF63: 0x98BF, //CJK UNIFIED IDEOGRAPH - 0xEF64: 0x98C0, //CJK UNIFIED IDEOGRAPH - 0xEF65: 0x98C1, //CJK UNIFIED IDEOGRAPH - 0xEF66: 0x98C2, //CJK UNIFIED IDEOGRAPH - 0xEF67: 0x98C3, //CJK UNIFIED IDEOGRAPH - 0xEF68: 0x98C4, //CJK UNIFIED IDEOGRAPH - 0xEF69: 0x98C5, //CJK UNIFIED IDEOGRAPH - 0xEF6A: 0x98C6, //CJK UNIFIED IDEOGRAPH - 0xEF6B: 0x98C7, //CJK UNIFIED IDEOGRAPH - 0xEF6C: 0x98C8, //CJK UNIFIED IDEOGRAPH - 0xEF6D: 0x98C9, //CJK UNIFIED IDEOGRAPH - 0xEF6E: 0x98CA, //CJK UNIFIED IDEOGRAPH - 0xEF6F: 0x98CB, //CJK UNIFIED IDEOGRAPH - 0xEF70: 0x98CC, //CJK UNIFIED IDEOGRAPH - 0xEF71: 0x98CD, //CJK UNIFIED IDEOGRAPH - 0xEF72: 0x98CF, //CJK UNIFIED IDEOGRAPH - 0xEF73: 0x98D0, //CJK UNIFIED IDEOGRAPH - 0xEF74: 0x98D4, //CJK UNIFIED IDEOGRAPH - 0xEF75: 0x98D6, //CJK UNIFIED IDEOGRAPH - 0xEF76: 0x98D7, //CJK UNIFIED IDEOGRAPH - 0xEF77: 0x98DB, //CJK UNIFIED IDEOGRAPH - 0xEF78: 0x98DC, //CJK UNIFIED IDEOGRAPH - 0xEF79: 0x98DD, //CJK UNIFIED IDEOGRAPH - 0xEF7A: 0x98E0, //CJK UNIFIED IDEOGRAPH - 0xEF7B: 0x98E1, //CJK UNIFIED IDEOGRAPH - 0xEF7C: 0x98E2, //CJK UNIFIED IDEOGRAPH - 0xEF7D: 0x98E3, //CJK UNIFIED IDEOGRAPH - 0xEF7E: 0x98E4, //CJK UNIFIED IDEOGRAPH - 0xEF80: 0x98E5, //CJK UNIFIED IDEOGRAPH - 0xEF81: 0x98E6, //CJK UNIFIED IDEOGRAPH - 0xEF82: 0x98E9, //CJK UNIFIED IDEOGRAPH - 0xEF83: 0x98EA, //CJK UNIFIED IDEOGRAPH - 0xEF84: 0x98EB, //CJK UNIFIED IDEOGRAPH - 0xEF85: 0x98EC, //CJK UNIFIED IDEOGRAPH - 0xEF86: 0x98ED, //CJK UNIFIED IDEOGRAPH - 0xEF87: 0x98EE, //CJK UNIFIED IDEOGRAPH - 0xEF88: 0x98EF, //CJK UNIFIED IDEOGRAPH - 0xEF89: 0x98F0, //CJK UNIFIED IDEOGRAPH - 0xEF8A: 0x98F1, //CJK UNIFIED IDEOGRAPH - 0xEF8B: 0x98F2, //CJK UNIFIED IDEOGRAPH - 0xEF8C: 0x98F3, //CJK UNIFIED IDEOGRAPH - 0xEF8D: 0x98F4, //CJK UNIFIED IDEOGRAPH - 0xEF8E: 0x98F5, //CJK UNIFIED IDEOGRAPH - 0xEF8F: 0x98F6, //CJK UNIFIED IDEOGRAPH - 0xEF90: 0x98F7, //CJK UNIFIED IDEOGRAPH - 0xEF91: 0x98F8, //CJK UNIFIED IDEOGRAPH - 0xEF92: 0x98F9, //CJK UNIFIED IDEOGRAPH - 0xEF93: 0x98FA, //CJK UNIFIED IDEOGRAPH - 0xEF94: 0x98FB, //CJK UNIFIED IDEOGRAPH - 0xEF95: 0x98FC, //CJK UNIFIED IDEOGRAPH - 0xEF96: 0x98FD, //CJK UNIFIED IDEOGRAPH - 0xEF97: 0x98FE, //CJK UNIFIED IDEOGRAPH - 0xEF98: 0x98FF, //CJK UNIFIED IDEOGRAPH - 0xEF99: 0x9900, //CJK UNIFIED IDEOGRAPH - 0xEF9A: 0x9901, //CJK UNIFIED IDEOGRAPH - 0xEF9B: 0x9902, //CJK UNIFIED IDEOGRAPH - 0xEF9C: 0x9903, //CJK UNIFIED IDEOGRAPH - 0xEF9D: 0x9904, //CJK UNIFIED IDEOGRAPH - 0xEF9E: 0x9905, //CJK UNIFIED IDEOGRAPH - 0xEF9F: 0x9906, //CJK UNIFIED IDEOGRAPH - 0xEFA0: 0x9907, //CJK UNIFIED IDEOGRAPH - 0xEFA1: 0x94E9, //CJK UNIFIED IDEOGRAPH - 0xEFA2: 0x94EB, //CJK UNIFIED IDEOGRAPH - 0xEFA3: 0x94EE, //CJK UNIFIED IDEOGRAPH - 0xEFA4: 0x94EF, //CJK UNIFIED IDEOGRAPH - 0xEFA5: 0x94F3, //CJK UNIFIED IDEOGRAPH - 0xEFA6: 0x94F4, //CJK UNIFIED IDEOGRAPH - 0xEFA7: 0x94F5, //CJK UNIFIED IDEOGRAPH - 0xEFA8: 0x94F7, //CJK UNIFIED IDEOGRAPH - 0xEFA9: 0x94F9, //CJK UNIFIED IDEOGRAPH - 0xEFAA: 0x94FC, //CJK UNIFIED IDEOGRAPH - 0xEFAB: 0x94FD, //CJK UNIFIED IDEOGRAPH - 0xEFAC: 0x94FF, //CJK UNIFIED IDEOGRAPH - 0xEFAD: 0x9503, //CJK UNIFIED IDEOGRAPH - 0xEFAE: 0x9502, //CJK UNIFIED IDEOGRAPH - 0xEFAF: 0x9506, //CJK UNIFIED IDEOGRAPH - 0xEFB0: 0x9507, //CJK UNIFIED IDEOGRAPH - 0xEFB1: 0x9509, //CJK UNIFIED IDEOGRAPH - 0xEFB2: 0x950A, //CJK UNIFIED IDEOGRAPH - 0xEFB3: 0x950D, //CJK UNIFIED IDEOGRAPH - 0xEFB4: 0x950E, //CJK UNIFIED IDEOGRAPH - 0xEFB5: 0x950F, //CJK UNIFIED IDEOGRAPH - 0xEFB6: 0x9512, //CJK UNIFIED IDEOGRAPH - 0xEFB7: 0x9513, //CJK UNIFIED IDEOGRAPH - 0xEFB8: 0x9514, //CJK UNIFIED IDEOGRAPH - 0xEFB9: 0x9515, //CJK UNIFIED IDEOGRAPH - 0xEFBA: 0x9516, //CJK UNIFIED IDEOGRAPH - 0xEFBB: 0x9518, //CJK UNIFIED IDEOGRAPH - 0xEFBC: 0x951B, //CJK UNIFIED IDEOGRAPH - 0xEFBD: 0x951D, //CJK UNIFIED IDEOGRAPH - 0xEFBE: 0x951E, //CJK UNIFIED IDEOGRAPH - 0xEFBF: 0x951F, //CJK UNIFIED IDEOGRAPH - 0xEFC0: 0x9522, //CJK UNIFIED IDEOGRAPH - 0xEFC1: 0x952A, //CJK UNIFIED IDEOGRAPH - 0xEFC2: 0x952B, //CJK UNIFIED IDEOGRAPH - 0xEFC3: 0x9529, //CJK UNIFIED IDEOGRAPH - 0xEFC4: 0x952C, //CJK UNIFIED IDEOGRAPH - 0xEFC5: 0x9531, //CJK UNIFIED IDEOGRAPH - 0xEFC6: 0x9532, //CJK UNIFIED IDEOGRAPH - 0xEFC7: 0x9534, //CJK UNIFIED IDEOGRAPH - 0xEFC8: 0x9536, //CJK UNIFIED IDEOGRAPH - 0xEFC9: 0x9537, //CJK UNIFIED IDEOGRAPH - 0xEFCA: 0x9538, //CJK UNIFIED IDEOGRAPH - 0xEFCB: 0x953C, //CJK UNIFIED IDEOGRAPH - 0xEFCC: 0x953E, //CJK UNIFIED IDEOGRAPH - 0xEFCD: 0x953F, //CJK UNIFIED IDEOGRAPH - 0xEFCE: 0x9542, //CJK UNIFIED IDEOGRAPH - 0xEFCF: 0x9535, //CJK UNIFIED IDEOGRAPH - 0xEFD0: 0x9544, //CJK UNIFIED IDEOGRAPH - 0xEFD1: 0x9545, //CJK UNIFIED IDEOGRAPH - 0xEFD2: 0x9546, //CJK UNIFIED IDEOGRAPH - 0xEFD3: 0x9549, //CJK UNIFIED IDEOGRAPH - 0xEFD4: 0x954C, //CJK UNIFIED IDEOGRAPH - 0xEFD5: 0x954E, //CJK UNIFIED IDEOGRAPH - 0xEFD6: 0x954F, //CJK UNIFIED IDEOGRAPH - 0xEFD7: 0x9552, //CJK UNIFIED IDEOGRAPH - 0xEFD8: 0x9553, //CJK UNIFIED IDEOGRAPH - 0xEFD9: 0x9554, //CJK UNIFIED IDEOGRAPH - 0xEFDA: 0x9556, //CJK UNIFIED IDEOGRAPH - 0xEFDB: 0x9557, //CJK UNIFIED IDEOGRAPH - 0xEFDC: 0x9558, //CJK UNIFIED IDEOGRAPH - 0xEFDD: 0x9559, //CJK UNIFIED IDEOGRAPH - 0xEFDE: 0x955B, //CJK UNIFIED IDEOGRAPH - 0xEFDF: 0x955E, //CJK UNIFIED IDEOGRAPH - 0xEFE0: 0x955F, //CJK UNIFIED IDEOGRAPH - 0xEFE1: 0x955D, //CJK UNIFIED IDEOGRAPH - 0xEFE2: 0x9561, //CJK UNIFIED IDEOGRAPH - 0xEFE3: 0x9562, //CJK UNIFIED IDEOGRAPH - 0xEFE4: 0x9564, //CJK UNIFIED IDEOGRAPH - 0xEFE5: 0x9565, //CJK UNIFIED IDEOGRAPH - 0xEFE6: 0x9566, //CJK UNIFIED IDEOGRAPH - 0xEFE7: 0x9567, //CJK UNIFIED IDEOGRAPH - 0xEFE8: 0x9568, //CJK UNIFIED IDEOGRAPH - 0xEFE9: 0x9569, //CJK UNIFIED IDEOGRAPH - 0xEFEA: 0x956A, //CJK UNIFIED IDEOGRAPH - 0xEFEB: 0x956B, //CJK UNIFIED IDEOGRAPH - 0xEFEC: 0x956C, //CJK UNIFIED IDEOGRAPH - 0xEFED: 0x956F, //CJK UNIFIED IDEOGRAPH - 0xEFEE: 0x9571, //CJK UNIFIED IDEOGRAPH - 0xEFEF: 0x9572, //CJK UNIFIED IDEOGRAPH - 0xEFF0: 0x9573, //CJK UNIFIED IDEOGRAPH - 0xEFF1: 0x953A, //CJK UNIFIED IDEOGRAPH - 0xEFF2: 0x77E7, //CJK UNIFIED IDEOGRAPH - 0xEFF3: 0x77EC, //CJK UNIFIED IDEOGRAPH - 0xEFF4: 0x96C9, //CJK UNIFIED IDEOGRAPH - 0xEFF5: 0x79D5, //CJK UNIFIED IDEOGRAPH - 0xEFF6: 0x79ED, //CJK UNIFIED IDEOGRAPH - 0xEFF7: 0x79E3, //CJK UNIFIED IDEOGRAPH - 0xEFF8: 0x79EB, //CJK UNIFIED IDEOGRAPH - 0xEFF9: 0x7A06, //CJK UNIFIED IDEOGRAPH - 0xEFFA: 0x5D47, //CJK UNIFIED IDEOGRAPH - 0xEFFB: 0x7A03, //CJK UNIFIED IDEOGRAPH - 0xEFFC: 0x7A02, //CJK UNIFIED IDEOGRAPH - 0xEFFD: 0x7A1E, //CJK UNIFIED IDEOGRAPH - 0xEFFE: 0x7A14, //CJK UNIFIED IDEOGRAPH - 0xF040: 0x9908, //CJK UNIFIED IDEOGRAPH - 0xF041: 0x9909, //CJK UNIFIED IDEOGRAPH - 0xF042: 0x990A, //CJK UNIFIED IDEOGRAPH - 0xF043: 0x990B, //CJK UNIFIED IDEOGRAPH - 0xF044: 0x990C, //CJK UNIFIED IDEOGRAPH - 0xF045: 0x990E, //CJK UNIFIED IDEOGRAPH - 0xF046: 0x990F, //CJK UNIFIED IDEOGRAPH - 0xF047: 0x9911, //CJK UNIFIED IDEOGRAPH - 0xF048: 0x9912, //CJK UNIFIED IDEOGRAPH - 0xF049: 0x9913, //CJK UNIFIED IDEOGRAPH - 0xF04A: 0x9914, //CJK UNIFIED IDEOGRAPH - 0xF04B: 0x9915, //CJK UNIFIED IDEOGRAPH - 0xF04C: 0x9916, //CJK UNIFIED IDEOGRAPH - 0xF04D: 0x9917, //CJK UNIFIED IDEOGRAPH - 0xF04E: 0x9918, //CJK UNIFIED IDEOGRAPH - 0xF04F: 0x9919, //CJK UNIFIED IDEOGRAPH - 0xF050: 0x991A, //CJK UNIFIED IDEOGRAPH - 0xF051: 0x991B, //CJK UNIFIED IDEOGRAPH - 0xF052: 0x991C, //CJK UNIFIED IDEOGRAPH - 0xF053: 0x991D, //CJK UNIFIED IDEOGRAPH - 0xF054: 0x991E, //CJK UNIFIED IDEOGRAPH - 0xF055: 0x991F, //CJK UNIFIED IDEOGRAPH - 0xF056: 0x9920, //CJK UNIFIED IDEOGRAPH - 0xF057: 0x9921, //CJK UNIFIED IDEOGRAPH - 0xF058: 0x9922, //CJK UNIFIED IDEOGRAPH - 0xF059: 0x9923, //CJK UNIFIED IDEOGRAPH - 0xF05A: 0x9924, //CJK UNIFIED IDEOGRAPH - 0xF05B: 0x9925, //CJK UNIFIED IDEOGRAPH - 0xF05C: 0x9926, //CJK UNIFIED IDEOGRAPH - 0xF05D: 0x9927, //CJK UNIFIED IDEOGRAPH - 0xF05E: 0x9928, //CJK UNIFIED IDEOGRAPH - 0xF05F: 0x9929, //CJK UNIFIED IDEOGRAPH - 0xF060: 0x992A, //CJK UNIFIED IDEOGRAPH - 0xF061: 0x992B, //CJK UNIFIED IDEOGRAPH - 0xF062: 0x992C, //CJK UNIFIED IDEOGRAPH - 0xF063: 0x992D, //CJK UNIFIED IDEOGRAPH - 0xF064: 0x992F, //CJK UNIFIED IDEOGRAPH - 0xF065: 0x9930, //CJK UNIFIED IDEOGRAPH - 0xF066: 0x9931, //CJK UNIFIED IDEOGRAPH - 0xF067: 0x9932, //CJK UNIFIED IDEOGRAPH - 0xF068: 0x9933, //CJK UNIFIED IDEOGRAPH - 0xF069: 0x9934, //CJK UNIFIED IDEOGRAPH - 0xF06A: 0x9935, //CJK UNIFIED IDEOGRAPH - 0xF06B: 0x9936, //CJK UNIFIED IDEOGRAPH - 0xF06C: 0x9937, //CJK UNIFIED IDEOGRAPH - 0xF06D: 0x9938, //CJK UNIFIED IDEOGRAPH - 0xF06E: 0x9939, //CJK UNIFIED IDEOGRAPH - 0xF06F: 0x993A, //CJK UNIFIED IDEOGRAPH - 0xF070: 0x993B, //CJK UNIFIED IDEOGRAPH - 0xF071: 0x993C, //CJK UNIFIED IDEOGRAPH - 0xF072: 0x993D, //CJK UNIFIED IDEOGRAPH - 0xF073: 0x993E, //CJK UNIFIED IDEOGRAPH - 0xF074: 0x993F, //CJK UNIFIED IDEOGRAPH - 0xF075: 0x9940, //CJK UNIFIED IDEOGRAPH - 0xF076: 0x9941, //CJK UNIFIED IDEOGRAPH - 0xF077: 0x9942, //CJK UNIFIED IDEOGRAPH - 0xF078: 0x9943, //CJK UNIFIED IDEOGRAPH - 0xF079: 0x9944, //CJK UNIFIED IDEOGRAPH - 0xF07A: 0x9945, //CJK UNIFIED IDEOGRAPH - 0xF07B: 0x9946, //CJK UNIFIED IDEOGRAPH - 0xF07C: 0x9947, //CJK UNIFIED IDEOGRAPH - 0xF07D: 0x9948, //CJK UNIFIED IDEOGRAPH - 0xF07E: 0x9949, //CJK UNIFIED IDEOGRAPH - 0xF080: 0x994A, //CJK UNIFIED IDEOGRAPH - 0xF081: 0x994B, //CJK UNIFIED IDEOGRAPH - 0xF082: 0x994C, //CJK UNIFIED IDEOGRAPH - 0xF083: 0x994D, //CJK UNIFIED IDEOGRAPH - 0xF084: 0x994E, //CJK UNIFIED IDEOGRAPH - 0xF085: 0x994F, //CJK UNIFIED IDEOGRAPH - 0xF086: 0x9950, //CJK UNIFIED IDEOGRAPH - 0xF087: 0x9951, //CJK UNIFIED IDEOGRAPH - 0xF088: 0x9952, //CJK UNIFIED IDEOGRAPH - 0xF089: 0x9953, //CJK UNIFIED IDEOGRAPH - 0xF08A: 0x9956, //CJK UNIFIED IDEOGRAPH - 0xF08B: 0x9957, //CJK UNIFIED IDEOGRAPH - 0xF08C: 0x9958, //CJK UNIFIED IDEOGRAPH - 0xF08D: 0x9959, //CJK UNIFIED IDEOGRAPH - 0xF08E: 0x995A, //CJK UNIFIED IDEOGRAPH - 0xF08F: 0x995B, //CJK UNIFIED IDEOGRAPH - 0xF090: 0x995C, //CJK UNIFIED IDEOGRAPH - 0xF091: 0x995D, //CJK UNIFIED IDEOGRAPH - 0xF092: 0x995E, //CJK UNIFIED IDEOGRAPH - 0xF093: 0x995F, //CJK UNIFIED IDEOGRAPH - 0xF094: 0x9960, //CJK UNIFIED IDEOGRAPH - 0xF095: 0x9961, //CJK UNIFIED IDEOGRAPH - 0xF096: 0x9962, //CJK UNIFIED IDEOGRAPH - 0xF097: 0x9964, //CJK UNIFIED IDEOGRAPH - 0xF098: 0x9966, //CJK UNIFIED IDEOGRAPH - 0xF099: 0x9973, //CJK UNIFIED IDEOGRAPH - 0xF09A: 0x9978, //CJK UNIFIED IDEOGRAPH - 0xF09B: 0x9979, //CJK UNIFIED IDEOGRAPH - 0xF09C: 0x997B, //CJK UNIFIED IDEOGRAPH - 0xF09D: 0x997E, //CJK UNIFIED IDEOGRAPH - 0xF09E: 0x9982, //CJK UNIFIED IDEOGRAPH - 0xF09F: 0x9983, //CJK UNIFIED IDEOGRAPH - 0xF0A0: 0x9989, //CJK UNIFIED IDEOGRAPH - 0xF0A1: 0x7A39, //CJK UNIFIED IDEOGRAPH - 0xF0A2: 0x7A37, //CJK UNIFIED IDEOGRAPH - 0xF0A3: 0x7A51, //CJK UNIFIED IDEOGRAPH - 0xF0A4: 0x9ECF, //CJK UNIFIED IDEOGRAPH - 0xF0A5: 0x99A5, //CJK UNIFIED IDEOGRAPH - 0xF0A6: 0x7A70, //CJK UNIFIED IDEOGRAPH - 0xF0A7: 0x7688, //CJK UNIFIED IDEOGRAPH - 0xF0A8: 0x768E, //CJK UNIFIED IDEOGRAPH - 0xF0A9: 0x7693, //CJK UNIFIED IDEOGRAPH - 0xF0AA: 0x7699, //CJK UNIFIED IDEOGRAPH - 0xF0AB: 0x76A4, //CJK UNIFIED IDEOGRAPH - 0xF0AC: 0x74DE, //CJK UNIFIED IDEOGRAPH - 0xF0AD: 0x74E0, //CJK UNIFIED IDEOGRAPH - 0xF0AE: 0x752C, //CJK UNIFIED IDEOGRAPH - 0xF0AF: 0x9E20, //CJK UNIFIED IDEOGRAPH - 0xF0B0: 0x9E22, //CJK UNIFIED IDEOGRAPH - 0xF0B1: 0x9E28, //CJK UNIFIED IDEOGRAPH - 0xF0B2: 0x9E29, //CJK UNIFIED IDEOGRAPH - 0xF0B3: 0x9E2A, //CJK UNIFIED IDEOGRAPH - 0xF0B4: 0x9E2B, //CJK UNIFIED IDEOGRAPH - 0xF0B5: 0x9E2C, //CJK UNIFIED IDEOGRAPH - 0xF0B6: 0x9E32, //CJK UNIFIED IDEOGRAPH - 0xF0B7: 0x9E31, //CJK UNIFIED IDEOGRAPH - 0xF0B8: 0x9E36, //CJK UNIFIED IDEOGRAPH - 0xF0B9: 0x9E38, //CJK UNIFIED IDEOGRAPH - 0xF0BA: 0x9E37, //CJK UNIFIED IDEOGRAPH - 0xF0BB: 0x9E39, //CJK UNIFIED IDEOGRAPH - 0xF0BC: 0x9E3A, //CJK UNIFIED IDEOGRAPH - 0xF0BD: 0x9E3E, //CJK UNIFIED IDEOGRAPH - 0xF0BE: 0x9E41, //CJK UNIFIED IDEOGRAPH - 0xF0BF: 0x9E42, //CJK UNIFIED IDEOGRAPH - 0xF0C0: 0x9E44, //CJK UNIFIED IDEOGRAPH - 0xF0C1: 0x9E46, //CJK UNIFIED IDEOGRAPH - 0xF0C2: 0x9E47, //CJK UNIFIED IDEOGRAPH - 0xF0C3: 0x9E48, //CJK UNIFIED IDEOGRAPH - 0xF0C4: 0x9E49, //CJK UNIFIED IDEOGRAPH - 0xF0C5: 0x9E4B, //CJK UNIFIED IDEOGRAPH - 0xF0C6: 0x9E4C, //CJK UNIFIED IDEOGRAPH - 0xF0C7: 0x9E4E, //CJK UNIFIED IDEOGRAPH - 0xF0C8: 0x9E51, //CJK UNIFIED IDEOGRAPH - 0xF0C9: 0x9E55, //CJK UNIFIED IDEOGRAPH - 0xF0CA: 0x9E57, //CJK UNIFIED IDEOGRAPH - 0xF0CB: 0x9E5A, //CJK UNIFIED IDEOGRAPH - 0xF0CC: 0x9E5B, //CJK UNIFIED IDEOGRAPH - 0xF0CD: 0x9E5C, //CJK UNIFIED IDEOGRAPH - 0xF0CE: 0x9E5E, //CJK UNIFIED IDEOGRAPH - 0xF0CF: 0x9E63, //CJK UNIFIED IDEOGRAPH - 0xF0D0: 0x9E66, //CJK UNIFIED IDEOGRAPH - 0xF0D1: 0x9E67, //CJK UNIFIED IDEOGRAPH - 0xF0D2: 0x9E68, //CJK UNIFIED IDEOGRAPH - 0xF0D3: 0x9E69, //CJK UNIFIED IDEOGRAPH - 0xF0D4: 0x9E6A, //CJK UNIFIED IDEOGRAPH - 0xF0D5: 0x9E6B, //CJK UNIFIED IDEOGRAPH - 0xF0D6: 0x9E6C, //CJK UNIFIED IDEOGRAPH - 0xF0D7: 0x9E71, //CJK UNIFIED IDEOGRAPH - 0xF0D8: 0x9E6D, //CJK UNIFIED IDEOGRAPH - 0xF0D9: 0x9E73, //CJK UNIFIED IDEOGRAPH - 0xF0DA: 0x7592, //CJK UNIFIED IDEOGRAPH - 0xF0DB: 0x7594, //CJK UNIFIED IDEOGRAPH - 0xF0DC: 0x7596, //CJK UNIFIED IDEOGRAPH - 0xF0DD: 0x75A0, //CJK UNIFIED IDEOGRAPH - 0xF0DE: 0x759D, //CJK UNIFIED IDEOGRAPH - 0xF0DF: 0x75AC, //CJK UNIFIED IDEOGRAPH - 0xF0E0: 0x75A3, //CJK UNIFIED IDEOGRAPH - 0xF0E1: 0x75B3, //CJK UNIFIED IDEOGRAPH - 0xF0E2: 0x75B4, //CJK UNIFIED IDEOGRAPH - 0xF0E3: 0x75B8, //CJK UNIFIED IDEOGRAPH - 0xF0E4: 0x75C4, //CJK UNIFIED IDEOGRAPH - 0xF0E5: 0x75B1, //CJK UNIFIED IDEOGRAPH - 0xF0E6: 0x75B0, //CJK UNIFIED IDEOGRAPH - 0xF0E7: 0x75C3, //CJK UNIFIED IDEOGRAPH - 0xF0E8: 0x75C2, //CJK UNIFIED IDEOGRAPH - 0xF0E9: 0x75D6, //CJK UNIFIED IDEOGRAPH - 0xF0EA: 0x75CD, //CJK UNIFIED IDEOGRAPH - 0xF0EB: 0x75E3, //CJK UNIFIED IDEOGRAPH - 0xF0EC: 0x75E8, //CJK UNIFIED IDEOGRAPH - 0xF0ED: 0x75E6, //CJK UNIFIED IDEOGRAPH - 0xF0EE: 0x75E4, //CJK UNIFIED IDEOGRAPH - 0xF0EF: 0x75EB, //CJK UNIFIED IDEOGRAPH - 0xF0F0: 0x75E7, //CJK UNIFIED IDEOGRAPH - 0xF0F1: 0x7603, //CJK UNIFIED IDEOGRAPH - 0xF0F2: 0x75F1, //CJK UNIFIED IDEOGRAPH - 0xF0F3: 0x75FC, //CJK UNIFIED IDEOGRAPH - 0xF0F4: 0x75FF, //CJK UNIFIED IDEOGRAPH - 0xF0F5: 0x7610, //CJK UNIFIED IDEOGRAPH - 0xF0F6: 0x7600, //CJK UNIFIED IDEOGRAPH - 0xF0F7: 0x7605, //CJK UNIFIED IDEOGRAPH - 0xF0F8: 0x760C, //CJK UNIFIED IDEOGRAPH - 0xF0F9: 0x7617, //CJK UNIFIED IDEOGRAPH - 0xF0FA: 0x760A, //CJK UNIFIED IDEOGRAPH - 0xF0FB: 0x7625, //CJK UNIFIED IDEOGRAPH - 0xF0FC: 0x7618, //CJK UNIFIED IDEOGRAPH - 0xF0FD: 0x7615, //CJK UNIFIED IDEOGRAPH - 0xF0FE: 0x7619, //CJK UNIFIED IDEOGRAPH - 0xF140: 0x998C, //CJK UNIFIED IDEOGRAPH - 0xF141: 0x998E, //CJK UNIFIED IDEOGRAPH - 0xF142: 0x999A, //CJK UNIFIED IDEOGRAPH - 0xF143: 0x999B, //CJK UNIFIED IDEOGRAPH - 0xF144: 0x999C, //CJK UNIFIED IDEOGRAPH - 0xF145: 0x999D, //CJK UNIFIED IDEOGRAPH - 0xF146: 0x999E, //CJK UNIFIED IDEOGRAPH - 0xF147: 0x999F, //CJK UNIFIED IDEOGRAPH - 0xF148: 0x99A0, //CJK UNIFIED IDEOGRAPH - 0xF149: 0x99A1, //CJK UNIFIED IDEOGRAPH - 0xF14A: 0x99A2, //CJK UNIFIED IDEOGRAPH - 0xF14B: 0x99A3, //CJK UNIFIED IDEOGRAPH - 0xF14C: 0x99A4, //CJK UNIFIED IDEOGRAPH - 0xF14D: 0x99A6, //CJK UNIFIED IDEOGRAPH - 0xF14E: 0x99A7, //CJK UNIFIED IDEOGRAPH - 0xF14F: 0x99A9, //CJK UNIFIED IDEOGRAPH - 0xF150: 0x99AA, //CJK UNIFIED IDEOGRAPH - 0xF151: 0x99AB, //CJK UNIFIED IDEOGRAPH - 0xF152: 0x99AC, //CJK UNIFIED IDEOGRAPH - 0xF153: 0x99AD, //CJK UNIFIED IDEOGRAPH - 0xF154: 0x99AE, //CJK UNIFIED IDEOGRAPH - 0xF155: 0x99AF, //CJK UNIFIED IDEOGRAPH - 0xF156: 0x99B0, //CJK UNIFIED IDEOGRAPH - 0xF157: 0x99B1, //CJK UNIFIED IDEOGRAPH - 0xF158: 0x99B2, //CJK UNIFIED IDEOGRAPH - 0xF159: 0x99B3, //CJK UNIFIED IDEOGRAPH - 0xF15A: 0x99B4, //CJK UNIFIED IDEOGRAPH - 0xF15B: 0x99B5, //CJK UNIFIED IDEOGRAPH - 0xF15C: 0x99B6, //CJK UNIFIED IDEOGRAPH - 0xF15D: 0x99B7, //CJK UNIFIED IDEOGRAPH - 0xF15E: 0x99B8, //CJK UNIFIED IDEOGRAPH - 0xF15F: 0x99B9, //CJK UNIFIED IDEOGRAPH - 0xF160: 0x99BA, //CJK UNIFIED IDEOGRAPH - 0xF161: 0x99BB, //CJK UNIFIED IDEOGRAPH - 0xF162: 0x99BC, //CJK UNIFIED IDEOGRAPH - 0xF163: 0x99BD, //CJK UNIFIED IDEOGRAPH - 0xF164: 0x99BE, //CJK UNIFIED IDEOGRAPH - 0xF165: 0x99BF, //CJK UNIFIED IDEOGRAPH - 0xF166: 0x99C0, //CJK UNIFIED IDEOGRAPH - 0xF167: 0x99C1, //CJK UNIFIED IDEOGRAPH - 0xF168: 0x99C2, //CJK UNIFIED IDEOGRAPH - 0xF169: 0x99C3, //CJK UNIFIED IDEOGRAPH - 0xF16A: 0x99C4, //CJK UNIFIED IDEOGRAPH - 0xF16B: 0x99C5, //CJK UNIFIED IDEOGRAPH - 0xF16C: 0x99C6, //CJK UNIFIED IDEOGRAPH - 0xF16D: 0x99C7, //CJK UNIFIED IDEOGRAPH - 0xF16E: 0x99C8, //CJK UNIFIED IDEOGRAPH - 0xF16F: 0x99C9, //CJK UNIFIED IDEOGRAPH - 0xF170: 0x99CA, //CJK UNIFIED IDEOGRAPH - 0xF171: 0x99CB, //CJK UNIFIED IDEOGRAPH - 0xF172: 0x99CC, //CJK UNIFIED IDEOGRAPH - 0xF173: 0x99CD, //CJK UNIFIED IDEOGRAPH - 0xF174: 0x99CE, //CJK UNIFIED IDEOGRAPH - 0xF175: 0x99CF, //CJK UNIFIED IDEOGRAPH - 0xF176: 0x99D0, //CJK UNIFIED IDEOGRAPH - 0xF177: 0x99D1, //CJK UNIFIED IDEOGRAPH - 0xF178: 0x99D2, //CJK UNIFIED IDEOGRAPH - 0xF179: 0x99D3, //CJK UNIFIED IDEOGRAPH - 0xF17A: 0x99D4, //CJK UNIFIED IDEOGRAPH - 0xF17B: 0x99D5, //CJK UNIFIED IDEOGRAPH - 0xF17C: 0x99D6, //CJK UNIFIED IDEOGRAPH - 0xF17D: 0x99D7, //CJK UNIFIED IDEOGRAPH - 0xF17E: 0x99D8, //CJK UNIFIED IDEOGRAPH - 0xF180: 0x99D9, //CJK UNIFIED IDEOGRAPH - 0xF181: 0x99DA, //CJK UNIFIED IDEOGRAPH - 0xF182: 0x99DB, //CJK UNIFIED IDEOGRAPH - 0xF183: 0x99DC, //CJK UNIFIED IDEOGRAPH - 0xF184: 0x99DD, //CJK UNIFIED IDEOGRAPH - 0xF185: 0x99DE, //CJK UNIFIED IDEOGRAPH - 0xF186: 0x99DF, //CJK UNIFIED IDEOGRAPH - 0xF187: 0x99E0, //CJK UNIFIED IDEOGRAPH - 0xF188: 0x99E1, //CJK UNIFIED IDEOGRAPH - 0xF189: 0x99E2, //CJK UNIFIED IDEOGRAPH - 0xF18A: 0x99E3, //CJK UNIFIED IDEOGRAPH - 0xF18B: 0x99E4, //CJK UNIFIED IDEOGRAPH - 0xF18C: 0x99E5, //CJK UNIFIED IDEOGRAPH - 0xF18D: 0x99E6, //CJK UNIFIED IDEOGRAPH - 0xF18E: 0x99E7, //CJK UNIFIED IDEOGRAPH - 0xF18F: 0x99E8, //CJK UNIFIED IDEOGRAPH - 0xF190: 0x99E9, //CJK UNIFIED IDEOGRAPH - 0xF191: 0x99EA, //CJK UNIFIED IDEOGRAPH - 0xF192: 0x99EB, //CJK UNIFIED IDEOGRAPH - 0xF193: 0x99EC, //CJK UNIFIED IDEOGRAPH - 0xF194: 0x99ED, //CJK UNIFIED IDEOGRAPH - 0xF195: 0x99EE, //CJK UNIFIED IDEOGRAPH - 0xF196: 0x99EF, //CJK UNIFIED IDEOGRAPH - 0xF197: 0x99F0, //CJK UNIFIED IDEOGRAPH - 0xF198: 0x99F1, //CJK UNIFIED IDEOGRAPH - 0xF199: 0x99F2, //CJK UNIFIED IDEOGRAPH - 0xF19A: 0x99F3, //CJK UNIFIED IDEOGRAPH - 0xF19B: 0x99F4, //CJK UNIFIED IDEOGRAPH - 0xF19C: 0x99F5, //CJK UNIFIED IDEOGRAPH - 0xF19D: 0x99F6, //CJK UNIFIED IDEOGRAPH - 0xF19E: 0x99F7, //CJK UNIFIED IDEOGRAPH - 0xF19F: 0x99F8, //CJK UNIFIED IDEOGRAPH - 0xF1A0: 0x99F9, //CJK UNIFIED IDEOGRAPH - 0xF1A1: 0x761B, //CJK UNIFIED IDEOGRAPH - 0xF1A2: 0x763C, //CJK UNIFIED IDEOGRAPH - 0xF1A3: 0x7622, //CJK UNIFIED IDEOGRAPH - 0xF1A4: 0x7620, //CJK UNIFIED IDEOGRAPH - 0xF1A5: 0x7640, //CJK UNIFIED IDEOGRAPH - 0xF1A6: 0x762D, //CJK UNIFIED IDEOGRAPH - 0xF1A7: 0x7630, //CJK UNIFIED IDEOGRAPH - 0xF1A8: 0x763F, //CJK UNIFIED IDEOGRAPH - 0xF1A9: 0x7635, //CJK UNIFIED IDEOGRAPH - 0xF1AA: 0x7643, //CJK UNIFIED IDEOGRAPH - 0xF1AB: 0x763E, //CJK UNIFIED IDEOGRAPH - 0xF1AC: 0x7633, //CJK UNIFIED IDEOGRAPH - 0xF1AD: 0x764D, //CJK UNIFIED IDEOGRAPH - 0xF1AE: 0x765E, //CJK UNIFIED IDEOGRAPH - 0xF1AF: 0x7654, //CJK UNIFIED IDEOGRAPH - 0xF1B0: 0x765C, //CJK UNIFIED IDEOGRAPH - 0xF1B1: 0x7656, //CJK UNIFIED IDEOGRAPH - 0xF1B2: 0x766B, //CJK UNIFIED IDEOGRAPH - 0xF1B3: 0x766F, //CJK UNIFIED IDEOGRAPH - 0xF1B4: 0x7FCA, //CJK UNIFIED IDEOGRAPH - 0xF1B5: 0x7AE6, //CJK UNIFIED IDEOGRAPH - 0xF1B6: 0x7A78, //CJK UNIFIED IDEOGRAPH - 0xF1B7: 0x7A79, //CJK UNIFIED IDEOGRAPH - 0xF1B8: 0x7A80, //CJK UNIFIED IDEOGRAPH - 0xF1B9: 0x7A86, //CJK UNIFIED IDEOGRAPH - 0xF1BA: 0x7A88, //CJK UNIFIED IDEOGRAPH - 0xF1BB: 0x7A95, //CJK UNIFIED IDEOGRAPH - 0xF1BC: 0x7AA6, //CJK UNIFIED IDEOGRAPH - 0xF1BD: 0x7AA0, //CJK UNIFIED IDEOGRAPH - 0xF1BE: 0x7AAC, //CJK UNIFIED IDEOGRAPH - 0xF1BF: 0x7AA8, //CJK UNIFIED IDEOGRAPH - 0xF1C0: 0x7AAD, //CJK UNIFIED IDEOGRAPH - 0xF1C1: 0x7AB3, //CJK UNIFIED IDEOGRAPH - 0xF1C2: 0x8864, //CJK UNIFIED IDEOGRAPH - 0xF1C3: 0x8869, //CJK UNIFIED IDEOGRAPH - 0xF1C4: 0x8872, //CJK UNIFIED IDEOGRAPH - 0xF1C5: 0x887D, //CJK UNIFIED IDEOGRAPH - 0xF1C6: 0x887F, //CJK UNIFIED IDEOGRAPH - 0xF1C7: 0x8882, //CJK UNIFIED IDEOGRAPH - 0xF1C8: 0x88A2, //CJK UNIFIED IDEOGRAPH - 0xF1C9: 0x88C6, //CJK UNIFIED IDEOGRAPH - 0xF1CA: 0x88B7, //CJK UNIFIED IDEOGRAPH - 0xF1CB: 0x88BC, //CJK UNIFIED IDEOGRAPH - 0xF1CC: 0x88C9, //CJK UNIFIED IDEOGRAPH - 0xF1CD: 0x88E2, //CJK UNIFIED IDEOGRAPH - 0xF1CE: 0x88CE, //CJK UNIFIED IDEOGRAPH - 0xF1CF: 0x88E3, //CJK UNIFIED IDEOGRAPH - 0xF1D0: 0x88E5, //CJK UNIFIED IDEOGRAPH - 0xF1D1: 0x88F1, //CJK UNIFIED IDEOGRAPH - 0xF1D2: 0x891A, //CJK UNIFIED IDEOGRAPH - 0xF1D3: 0x88FC, //CJK UNIFIED IDEOGRAPH - 0xF1D4: 0x88E8, //CJK UNIFIED IDEOGRAPH - 0xF1D5: 0x88FE, //CJK UNIFIED IDEOGRAPH - 0xF1D6: 0x88F0, //CJK UNIFIED IDEOGRAPH - 0xF1D7: 0x8921, //CJK UNIFIED IDEOGRAPH - 0xF1D8: 0x8919, //CJK UNIFIED IDEOGRAPH - 0xF1D9: 0x8913, //CJK UNIFIED IDEOGRAPH - 0xF1DA: 0x891B, //CJK UNIFIED IDEOGRAPH - 0xF1DB: 0x890A, //CJK UNIFIED IDEOGRAPH - 0xF1DC: 0x8934, //CJK UNIFIED IDEOGRAPH - 0xF1DD: 0x892B, //CJK UNIFIED IDEOGRAPH - 0xF1DE: 0x8936, //CJK UNIFIED IDEOGRAPH - 0xF1DF: 0x8941, //CJK UNIFIED IDEOGRAPH - 0xF1E0: 0x8966, //CJK UNIFIED IDEOGRAPH - 0xF1E1: 0x897B, //CJK UNIFIED IDEOGRAPH - 0xF1E2: 0x758B, //CJK UNIFIED IDEOGRAPH - 0xF1E3: 0x80E5, //CJK UNIFIED IDEOGRAPH - 0xF1E4: 0x76B2, //CJK UNIFIED IDEOGRAPH - 0xF1E5: 0x76B4, //CJK UNIFIED IDEOGRAPH - 0xF1E6: 0x77DC, //CJK UNIFIED IDEOGRAPH - 0xF1E7: 0x8012, //CJK UNIFIED IDEOGRAPH - 0xF1E8: 0x8014, //CJK UNIFIED IDEOGRAPH - 0xF1E9: 0x8016, //CJK UNIFIED IDEOGRAPH - 0xF1EA: 0x801C, //CJK UNIFIED IDEOGRAPH - 0xF1EB: 0x8020, //CJK UNIFIED IDEOGRAPH - 0xF1EC: 0x8022, //CJK UNIFIED IDEOGRAPH - 0xF1ED: 0x8025, //CJK UNIFIED IDEOGRAPH - 0xF1EE: 0x8026, //CJK UNIFIED IDEOGRAPH - 0xF1EF: 0x8027, //CJK UNIFIED IDEOGRAPH - 0xF1F0: 0x8029, //CJK UNIFIED IDEOGRAPH - 0xF1F1: 0x8028, //CJK UNIFIED IDEOGRAPH - 0xF1F2: 0x8031, //CJK UNIFIED IDEOGRAPH - 0xF1F3: 0x800B, //CJK UNIFIED IDEOGRAPH - 0xF1F4: 0x8035, //CJK UNIFIED IDEOGRAPH - 0xF1F5: 0x8043, //CJK UNIFIED IDEOGRAPH - 0xF1F6: 0x8046, //CJK UNIFIED IDEOGRAPH - 0xF1F7: 0x804D, //CJK UNIFIED IDEOGRAPH - 0xF1F8: 0x8052, //CJK UNIFIED IDEOGRAPH - 0xF1F9: 0x8069, //CJK UNIFIED IDEOGRAPH - 0xF1FA: 0x8071, //CJK UNIFIED IDEOGRAPH - 0xF1FB: 0x8983, //CJK UNIFIED IDEOGRAPH - 0xF1FC: 0x9878, //CJK UNIFIED IDEOGRAPH - 0xF1FD: 0x9880, //CJK UNIFIED IDEOGRAPH - 0xF1FE: 0x9883, //CJK UNIFIED IDEOGRAPH - 0xF240: 0x99FA, //CJK UNIFIED IDEOGRAPH - 0xF241: 0x99FB, //CJK UNIFIED IDEOGRAPH - 0xF242: 0x99FC, //CJK UNIFIED IDEOGRAPH - 0xF243: 0x99FD, //CJK UNIFIED IDEOGRAPH - 0xF244: 0x99FE, //CJK UNIFIED IDEOGRAPH - 0xF245: 0x99FF, //CJK UNIFIED IDEOGRAPH - 0xF246: 0x9A00, //CJK UNIFIED IDEOGRAPH - 0xF247: 0x9A01, //CJK UNIFIED IDEOGRAPH - 0xF248: 0x9A02, //CJK UNIFIED IDEOGRAPH - 0xF249: 0x9A03, //CJK UNIFIED IDEOGRAPH - 0xF24A: 0x9A04, //CJK UNIFIED IDEOGRAPH - 0xF24B: 0x9A05, //CJK UNIFIED IDEOGRAPH - 0xF24C: 0x9A06, //CJK UNIFIED IDEOGRAPH - 0xF24D: 0x9A07, //CJK UNIFIED IDEOGRAPH - 0xF24E: 0x9A08, //CJK UNIFIED IDEOGRAPH - 0xF24F: 0x9A09, //CJK UNIFIED IDEOGRAPH - 0xF250: 0x9A0A, //CJK UNIFIED IDEOGRAPH - 0xF251: 0x9A0B, //CJK UNIFIED IDEOGRAPH - 0xF252: 0x9A0C, //CJK UNIFIED IDEOGRAPH - 0xF253: 0x9A0D, //CJK UNIFIED IDEOGRAPH - 0xF254: 0x9A0E, //CJK UNIFIED IDEOGRAPH - 0xF255: 0x9A0F, //CJK UNIFIED IDEOGRAPH - 0xF256: 0x9A10, //CJK UNIFIED IDEOGRAPH - 0xF257: 0x9A11, //CJK UNIFIED IDEOGRAPH - 0xF258: 0x9A12, //CJK UNIFIED IDEOGRAPH - 0xF259: 0x9A13, //CJK UNIFIED IDEOGRAPH - 0xF25A: 0x9A14, //CJK UNIFIED IDEOGRAPH - 0xF25B: 0x9A15, //CJK UNIFIED IDEOGRAPH - 0xF25C: 0x9A16, //CJK UNIFIED IDEOGRAPH - 0xF25D: 0x9A17, //CJK UNIFIED IDEOGRAPH - 0xF25E: 0x9A18, //CJK UNIFIED IDEOGRAPH - 0xF25F: 0x9A19, //CJK UNIFIED IDEOGRAPH - 0xF260: 0x9A1A, //CJK UNIFIED IDEOGRAPH - 0xF261: 0x9A1B, //CJK UNIFIED IDEOGRAPH - 0xF262: 0x9A1C, //CJK UNIFIED IDEOGRAPH - 0xF263: 0x9A1D, //CJK UNIFIED IDEOGRAPH - 0xF264: 0x9A1E, //CJK UNIFIED IDEOGRAPH - 0xF265: 0x9A1F, //CJK UNIFIED IDEOGRAPH - 0xF266: 0x9A20, //CJK UNIFIED IDEOGRAPH - 0xF267: 0x9A21, //CJK UNIFIED IDEOGRAPH - 0xF268: 0x9A22, //CJK UNIFIED IDEOGRAPH - 0xF269: 0x9A23, //CJK UNIFIED IDEOGRAPH - 0xF26A: 0x9A24, //CJK UNIFIED IDEOGRAPH - 0xF26B: 0x9A25, //CJK UNIFIED IDEOGRAPH - 0xF26C: 0x9A26, //CJK UNIFIED IDEOGRAPH - 0xF26D: 0x9A27, //CJK UNIFIED IDEOGRAPH - 0xF26E: 0x9A28, //CJK UNIFIED IDEOGRAPH - 0xF26F: 0x9A29, //CJK UNIFIED IDEOGRAPH - 0xF270: 0x9A2A, //CJK UNIFIED IDEOGRAPH - 0xF271: 0x9A2B, //CJK UNIFIED IDEOGRAPH - 0xF272: 0x9A2C, //CJK UNIFIED IDEOGRAPH - 0xF273: 0x9A2D, //CJK UNIFIED IDEOGRAPH - 0xF274: 0x9A2E, //CJK UNIFIED IDEOGRAPH - 0xF275: 0x9A2F, //CJK UNIFIED IDEOGRAPH - 0xF276: 0x9A30, //CJK UNIFIED IDEOGRAPH - 0xF277: 0x9A31, //CJK UNIFIED IDEOGRAPH - 0xF278: 0x9A32, //CJK UNIFIED IDEOGRAPH - 0xF279: 0x9A33, //CJK UNIFIED IDEOGRAPH - 0xF27A: 0x9A34, //CJK UNIFIED IDEOGRAPH - 0xF27B: 0x9A35, //CJK UNIFIED IDEOGRAPH - 0xF27C: 0x9A36, //CJK UNIFIED IDEOGRAPH - 0xF27D: 0x9A37, //CJK UNIFIED IDEOGRAPH - 0xF27E: 0x9A38, //CJK UNIFIED IDEOGRAPH - 0xF280: 0x9A39, //CJK UNIFIED IDEOGRAPH - 0xF281: 0x9A3A, //CJK UNIFIED IDEOGRAPH - 0xF282: 0x9A3B, //CJK UNIFIED IDEOGRAPH - 0xF283: 0x9A3C, //CJK UNIFIED IDEOGRAPH - 0xF284: 0x9A3D, //CJK UNIFIED IDEOGRAPH - 0xF285: 0x9A3E, //CJK UNIFIED IDEOGRAPH - 0xF286: 0x9A3F, //CJK UNIFIED IDEOGRAPH - 0xF287: 0x9A40, //CJK UNIFIED IDEOGRAPH - 0xF288: 0x9A41, //CJK UNIFIED IDEOGRAPH - 0xF289: 0x9A42, //CJK UNIFIED IDEOGRAPH - 0xF28A: 0x9A43, //CJK UNIFIED IDEOGRAPH - 0xF28B: 0x9A44, //CJK UNIFIED IDEOGRAPH - 0xF28C: 0x9A45, //CJK UNIFIED IDEOGRAPH - 0xF28D: 0x9A46, //CJK UNIFIED IDEOGRAPH - 0xF28E: 0x9A47, //CJK UNIFIED IDEOGRAPH - 0xF28F: 0x9A48, //CJK UNIFIED IDEOGRAPH - 0xF290: 0x9A49, //CJK UNIFIED IDEOGRAPH - 0xF291: 0x9A4A, //CJK UNIFIED IDEOGRAPH - 0xF292: 0x9A4B, //CJK UNIFIED IDEOGRAPH - 0xF293: 0x9A4C, //CJK UNIFIED IDEOGRAPH - 0xF294: 0x9A4D, //CJK UNIFIED IDEOGRAPH - 0xF295: 0x9A4E, //CJK UNIFIED IDEOGRAPH - 0xF296: 0x9A4F, //CJK UNIFIED IDEOGRAPH - 0xF297: 0x9A50, //CJK UNIFIED IDEOGRAPH - 0xF298: 0x9A51, //CJK UNIFIED IDEOGRAPH - 0xF299: 0x9A52, //CJK UNIFIED IDEOGRAPH - 0xF29A: 0x9A53, //CJK UNIFIED IDEOGRAPH - 0xF29B: 0x9A54, //CJK UNIFIED IDEOGRAPH - 0xF29C: 0x9A55, //CJK UNIFIED IDEOGRAPH - 0xF29D: 0x9A56, //CJK UNIFIED IDEOGRAPH - 0xF29E: 0x9A57, //CJK UNIFIED IDEOGRAPH - 0xF29F: 0x9A58, //CJK UNIFIED IDEOGRAPH - 0xF2A0: 0x9A59, //CJK UNIFIED IDEOGRAPH - 0xF2A1: 0x9889, //CJK UNIFIED IDEOGRAPH - 0xF2A2: 0x988C, //CJK UNIFIED IDEOGRAPH - 0xF2A3: 0x988D, //CJK UNIFIED IDEOGRAPH - 0xF2A4: 0x988F, //CJK UNIFIED IDEOGRAPH - 0xF2A5: 0x9894, //CJK UNIFIED IDEOGRAPH - 0xF2A6: 0x989A, //CJK UNIFIED IDEOGRAPH - 0xF2A7: 0x989B, //CJK UNIFIED IDEOGRAPH - 0xF2A8: 0x989E, //CJK UNIFIED IDEOGRAPH - 0xF2A9: 0x989F, //CJK UNIFIED IDEOGRAPH - 0xF2AA: 0x98A1, //CJK UNIFIED IDEOGRAPH - 0xF2AB: 0x98A2, //CJK UNIFIED IDEOGRAPH - 0xF2AC: 0x98A5, //CJK UNIFIED IDEOGRAPH - 0xF2AD: 0x98A6, //CJK UNIFIED IDEOGRAPH - 0xF2AE: 0x864D, //CJK UNIFIED IDEOGRAPH - 0xF2AF: 0x8654, //CJK UNIFIED IDEOGRAPH - 0xF2B0: 0x866C, //CJK UNIFIED IDEOGRAPH - 0xF2B1: 0x866E, //CJK UNIFIED IDEOGRAPH - 0xF2B2: 0x867F, //CJK UNIFIED IDEOGRAPH - 0xF2B3: 0x867A, //CJK UNIFIED IDEOGRAPH - 0xF2B4: 0x867C, //CJK UNIFIED IDEOGRAPH - 0xF2B5: 0x867B, //CJK UNIFIED IDEOGRAPH - 0xF2B6: 0x86A8, //CJK UNIFIED IDEOGRAPH - 0xF2B7: 0x868D, //CJK UNIFIED IDEOGRAPH - 0xF2B8: 0x868B, //CJK UNIFIED IDEOGRAPH - 0xF2B9: 0x86AC, //CJK UNIFIED IDEOGRAPH - 0xF2BA: 0x869D, //CJK UNIFIED IDEOGRAPH - 0xF2BB: 0x86A7, //CJK UNIFIED IDEOGRAPH - 0xF2BC: 0x86A3, //CJK UNIFIED IDEOGRAPH - 0xF2BD: 0x86AA, //CJK UNIFIED IDEOGRAPH - 0xF2BE: 0x8693, //CJK UNIFIED IDEOGRAPH - 0xF2BF: 0x86A9, //CJK UNIFIED IDEOGRAPH - 0xF2C0: 0x86B6, //CJK UNIFIED IDEOGRAPH - 0xF2C1: 0x86C4, //CJK UNIFIED IDEOGRAPH - 0xF2C2: 0x86B5, //CJK UNIFIED IDEOGRAPH - 0xF2C3: 0x86CE, //CJK UNIFIED IDEOGRAPH - 0xF2C4: 0x86B0, //CJK UNIFIED IDEOGRAPH - 0xF2C5: 0x86BA, //CJK UNIFIED IDEOGRAPH - 0xF2C6: 0x86B1, //CJK UNIFIED IDEOGRAPH - 0xF2C7: 0x86AF, //CJK UNIFIED IDEOGRAPH - 0xF2C8: 0x86C9, //CJK UNIFIED IDEOGRAPH - 0xF2C9: 0x86CF, //CJK UNIFIED IDEOGRAPH - 0xF2CA: 0x86B4, //CJK UNIFIED IDEOGRAPH - 0xF2CB: 0x86E9, //CJK UNIFIED IDEOGRAPH - 0xF2CC: 0x86F1, //CJK UNIFIED IDEOGRAPH - 0xF2CD: 0x86F2, //CJK UNIFIED IDEOGRAPH - 0xF2CE: 0x86ED, //CJK UNIFIED IDEOGRAPH - 0xF2CF: 0x86F3, //CJK UNIFIED IDEOGRAPH - 0xF2D0: 0x86D0, //CJK UNIFIED IDEOGRAPH - 0xF2D1: 0x8713, //CJK UNIFIED IDEOGRAPH - 0xF2D2: 0x86DE, //CJK UNIFIED IDEOGRAPH - 0xF2D3: 0x86F4, //CJK UNIFIED IDEOGRAPH - 0xF2D4: 0x86DF, //CJK UNIFIED IDEOGRAPH - 0xF2D5: 0x86D8, //CJK UNIFIED IDEOGRAPH - 0xF2D6: 0x86D1, //CJK UNIFIED IDEOGRAPH - 0xF2D7: 0x8703, //CJK UNIFIED IDEOGRAPH - 0xF2D8: 0x8707, //CJK UNIFIED IDEOGRAPH - 0xF2D9: 0x86F8, //CJK UNIFIED IDEOGRAPH - 0xF2DA: 0x8708, //CJK UNIFIED IDEOGRAPH - 0xF2DB: 0x870A, //CJK UNIFIED IDEOGRAPH - 0xF2DC: 0x870D, //CJK UNIFIED IDEOGRAPH - 0xF2DD: 0x8709, //CJK UNIFIED IDEOGRAPH - 0xF2DE: 0x8723, //CJK UNIFIED IDEOGRAPH - 0xF2DF: 0x873B, //CJK UNIFIED IDEOGRAPH - 0xF2E0: 0x871E, //CJK UNIFIED IDEOGRAPH - 0xF2E1: 0x8725, //CJK UNIFIED IDEOGRAPH - 0xF2E2: 0x872E, //CJK UNIFIED IDEOGRAPH - 0xF2E3: 0x871A, //CJK UNIFIED IDEOGRAPH - 0xF2E4: 0x873E, //CJK UNIFIED IDEOGRAPH - 0xF2E5: 0x8748, //CJK UNIFIED IDEOGRAPH - 0xF2E6: 0x8734, //CJK UNIFIED IDEOGRAPH - 0xF2E7: 0x8731, //CJK UNIFIED IDEOGRAPH - 0xF2E8: 0x8729, //CJK UNIFIED IDEOGRAPH - 0xF2E9: 0x8737, //CJK UNIFIED IDEOGRAPH - 0xF2EA: 0x873F, //CJK UNIFIED IDEOGRAPH - 0xF2EB: 0x8782, //CJK UNIFIED IDEOGRAPH - 0xF2EC: 0x8722, //CJK UNIFIED IDEOGRAPH - 0xF2ED: 0x877D, //CJK UNIFIED IDEOGRAPH - 0xF2EE: 0x877E, //CJK UNIFIED IDEOGRAPH - 0xF2EF: 0x877B, //CJK UNIFIED IDEOGRAPH - 0xF2F0: 0x8760, //CJK UNIFIED IDEOGRAPH - 0xF2F1: 0x8770, //CJK UNIFIED IDEOGRAPH - 0xF2F2: 0x874C, //CJK UNIFIED IDEOGRAPH - 0xF2F3: 0x876E, //CJK UNIFIED IDEOGRAPH - 0xF2F4: 0x878B, //CJK UNIFIED IDEOGRAPH - 0xF2F5: 0x8753, //CJK UNIFIED IDEOGRAPH - 0xF2F6: 0x8763, //CJK UNIFIED IDEOGRAPH - 0xF2F7: 0x877C, //CJK UNIFIED IDEOGRAPH - 0xF2F8: 0x8764, //CJK UNIFIED IDEOGRAPH - 0xF2F9: 0x8759, //CJK UNIFIED IDEOGRAPH - 0xF2FA: 0x8765, //CJK UNIFIED IDEOGRAPH - 0xF2FB: 0x8793, //CJK UNIFIED IDEOGRAPH - 0xF2FC: 0x87AF, //CJK UNIFIED IDEOGRAPH - 0xF2FD: 0x87A8, //CJK UNIFIED IDEOGRAPH - 0xF2FE: 0x87D2, //CJK UNIFIED IDEOGRAPH - 0xF340: 0x9A5A, //CJK UNIFIED IDEOGRAPH - 0xF341: 0x9A5B, //CJK UNIFIED IDEOGRAPH - 0xF342: 0x9A5C, //CJK UNIFIED IDEOGRAPH - 0xF343: 0x9A5D, //CJK UNIFIED IDEOGRAPH - 0xF344: 0x9A5E, //CJK UNIFIED IDEOGRAPH - 0xF345: 0x9A5F, //CJK UNIFIED IDEOGRAPH - 0xF346: 0x9A60, //CJK UNIFIED IDEOGRAPH - 0xF347: 0x9A61, //CJK UNIFIED IDEOGRAPH - 0xF348: 0x9A62, //CJK UNIFIED IDEOGRAPH - 0xF349: 0x9A63, //CJK UNIFIED IDEOGRAPH - 0xF34A: 0x9A64, //CJK UNIFIED IDEOGRAPH - 0xF34B: 0x9A65, //CJK UNIFIED IDEOGRAPH - 0xF34C: 0x9A66, //CJK UNIFIED IDEOGRAPH - 0xF34D: 0x9A67, //CJK UNIFIED IDEOGRAPH - 0xF34E: 0x9A68, //CJK UNIFIED IDEOGRAPH - 0xF34F: 0x9A69, //CJK UNIFIED IDEOGRAPH - 0xF350: 0x9A6A, //CJK UNIFIED IDEOGRAPH - 0xF351: 0x9A6B, //CJK UNIFIED IDEOGRAPH - 0xF352: 0x9A72, //CJK UNIFIED IDEOGRAPH - 0xF353: 0x9A83, //CJK UNIFIED IDEOGRAPH - 0xF354: 0x9A89, //CJK UNIFIED IDEOGRAPH - 0xF355: 0x9A8D, //CJK UNIFIED IDEOGRAPH - 0xF356: 0x9A8E, //CJK UNIFIED IDEOGRAPH - 0xF357: 0x9A94, //CJK UNIFIED IDEOGRAPH - 0xF358: 0x9A95, //CJK UNIFIED IDEOGRAPH - 0xF359: 0x9A99, //CJK UNIFIED IDEOGRAPH - 0xF35A: 0x9AA6, //CJK UNIFIED IDEOGRAPH - 0xF35B: 0x9AA9, //CJK UNIFIED IDEOGRAPH - 0xF35C: 0x9AAA, //CJK UNIFIED IDEOGRAPH - 0xF35D: 0x9AAB, //CJK UNIFIED IDEOGRAPH - 0xF35E: 0x9AAC, //CJK UNIFIED IDEOGRAPH - 0xF35F: 0x9AAD, //CJK UNIFIED IDEOGRAPH - 0xF360: 0x9AAE, //CJK UNIFIED IDEOGRAPH - 0xF361: 0x9AAF, //CJK UNIFIED IDEOGRAPH - 0xF362: 0x9AB2, //CJK UNIFIED IDEOGRAPH - 0xF363: 0x9AB3, //CJK UNIFIED IDEOGRAPH - 0xF364: 0x9AB4, //CJK UNIFIED IDEOGRAPH - 0xF365: 0x9AB5, //CJK UNIFIED IDEOGRAPH - 0xF366: 0x9AB9, //CJK UNIFIED IDEOGRAPH - 0xF367: 0x9ABB, //CJK UNIFIED IDEOGRAPH - 0xF368: 0x9ABD, //CJK UNIFIED IDEOGRAPH - 0xF369: 0x9ABE, //CJK UNIFIED IDEOGRAPH - 0xF36A: 0x9ABF, //CJK UNIFIED IDEOGRAPH - 0xF36B: 0x9AC3, //CJK UNIFIED IDEOGRAPH - 0xF36C: 0x9AC4, //CJK UNIFIED IDEOGRAPH - 0xF36D: 0x9AC6, //CJK UNIFIED IDEOGRAPH - 0xF36E: 0x9AC7, //CJK UNIFIED IDEOGRAPH - 0xF36F: 0x9AC8, //CJK UNIFIED IDEOGRAPH - 0xF370: 0x9AC9, //CJK UNIFIED IDEOGRAPH - 0xF371: 0x9ACA, //CJK UNIFIED IDEOGRAPH - 0xF372: 0x9ACD, //CJK UNIFIED IDEOGRAPH - 0xF373: 0x9ACE, //CJK UNIFIED IDEOGRAPH - 0xF374: 0x9ACF, //CJK UNIFIED IDEOGRAPH - 0xF375: 0x9AD0, //CJK UNIFIED IDEOGRAPH - 0xF376: 0x9AD2, //CJK UNIFIED IDEOGRAPH - 0xF377: 0x9AD4, //CJK UNIFIED IDEOGRAPH - 0xF378: 0x9AD5, //CJK UNIFIED IDEOGRAPH - 0xF379: 0x9AD6, //CJK UNIFIED IDEOGRAPH - 0xF37A: 0x9AD7, //CJK UNIFIED IDEOGRAPH - 0xF37B: 0x9AD9, //CJK UNIFIED IDEOGRAPH - 0xF37C: 0x9ADA, //CJK UNIFIED IDEOGRAPH - 0xF37D: 0x9ADB, //CJK UNIFIED IDEOGRAPH - 0xF37E: 0x9ADC, //CJK UNIFIED IDEOGRAPH - 0xF380: 0x9ADD, //CJK UNIFIED IDEOGRAPH - 0xF381: 0x9ADE, //CJK UNIFIED IDEOGRAPH - 0xF382: 0x9AE0, //CJK UNIFIED IDEOGRAPH - 0xF383: 0x9AE2, //CJK UNIFIED IDEOGRAPH - 0xF384: 0x9AE3, //CJK UNIFIED IDEOGRAPH - 0xF385: 0x9AE4, //CJK UNIFIED IDEOGRAPH - 0xF386: 0x9AE5, //CJK UNIFIED IDEOGRAPH - 0xF387: 0x9AE7, //CJK UNIFIED IDEOGRAPH - 0xF388: 0x9AE8, //CJK UNIFIED IDEOGRAPH - 0xF389: 0x9AE9, //CJK UNIFIED IDEOGRAPH - 0xF38A: 0x9AEA, //CJK UNIFIED IDEOGRAPH - 0xF38B: 0x9AEC, //CJK UNIFIED IDEOGRAPH - 0xF38C: 0x9AEE, //CJK UNIFIED IDEOGRAPH - 0xF38D: 0x9AF0, //CJK UNIFIED IDEOGRAPH - 0xF38E: 0x9AF1, //CJK UNIFIED IDEOGRAPH - 0xF38F: 0x9AF2, //CJK UNIFIED IDEOGRAPH - 0xF390: 0x9AF3, //CJK UNIFIED IDEOGRAPH - 0xF391: 0x9AF4, //CJK UNIFIED IDEOGRAPH - 0xF392: 0x9AF5, //CJK UNIFIED IDEOGRAPH - 0xF393: 0x9AF6, //CJK UNIFIED IDEOGRAPH - 0xF394: 0x9AF7, //CJK UNIFIED IDEOGRAPH - 0xF395: 0x9AF8, //CJK UNIFIED IDEOGRAPH - 0xF396: 0x9AFA, //CJK UNIFIED IDEOGRAPH - 0xF397: 0x9AFC, //CJK UNIFIED IDEOGRAPH - 0xF398: 0x9AFD, //CJK UNIFIED IDEOGRAPH - 0xF399: 0x9AFE, //CJK UNIFIED IDEOGRAPH - 0xF39A: 0x9AFF, //CJK UNIFIED IDEOGRAPH - 0xF39B: 0x9B00, //CJK UNIFIED IDEOGRAPH - 0xF39C: 0x9B01, //CJK UNIFIED IDEOGRAPH - 0xF39D: 0x9B02, //CJK UNIFIED IDEOGRAPH - 0xF39E: 0x9B04, //CJK UNIFIED IDEOGRAPH - 0xF39F: 0x9B05, //CJK UNIFIED IDEOGRAPH - 0xF3A0: 0x9B06, //CJK UNIFIED IDEOGRAPH - 0xF3A1: 0x87C6, //CJK UNIFIED IDEOGRAPH - 0xF3A2: 0x8788, //CJK UNIFIED IDEOGRAPH - 0xF3A3: 0x8785, //CJK UNIFIED IDEOGRAPH - 0xF3A4: 0x87AD, //CJK UNIFIED IDEOGRAPH - 0xF3A5: 0x8797, //CJK UNIFIED IDEOGRAPH - 0xF3A6: 0x8783, //CJK UNIFIED IDEOGRAPH - 0xF3A7: 0x87AB, //CJK UNIFIED IDEOGRAPH - 0xF3A8: 0x87E5, //CJK UNIFIED IDEOGRAPH - 0xF3A9: 0x87AC, //CJK UNIFIED IDEOGRAPH - 0xF3AA: 0x87B5, //CJK UNIFIED IDEOGRAPH - 0xF3AB: 0x87B3, //CJK UNIFIED IDEOGRAPH - 0xF3AC: 0x87CB, //CJK UNIFIED IDEOGRAPH - 0xF3AD: 0x87D3, //CJK UNIFIED IDEOGRAPH - 0xF3AE: 0x87BD, //CJK UNIFIED IDEOGRAPH - 0xF3AF: 0x87D1, //CJK UNIFIED IDEOGRAPH - 0xF3B0: 0x87C0, //CJK UNIFIED IDEOGRAPH - 0xF3B1: 0x87CA, //CJK UNIFIED IDEOGRAPH - 0xF3B2: 0x87DB, //CJK UNIFIED IDEOGRAPH - 0xF3B3: 0x87EA, //CJK UNIFIED IDEOGRAPH - 0xF3B4: 0x87E0, //CJK UNIFIED IDEOGRAPH - 0xF3B5: 0x87EE, //CJK UNIFIED IDEOGRAPH - 0xF3B6: 0x8816, //CJK UNIFIED IDEOGRAPH - 0xF3B7: 0x8813, //CJK UNIFIED IDEOGRAPH - 0xF3B8: 0x87FE, //CJK UNIFIED IDEOGRAPH - 0xF3B9: 0x880A, //CJK UNIFIED IDEOGRAPH - 0xF3BA: 0x881B, //CJK UNIFIED IDEOGRAPH - 0xF3BB: 0x8821, //CJK UNIFIED IDEOGRAPH - 0xF3BC: 0x8839, //CJK UNIFIED IDEOGRAPH - 0xF3BD: 0x883C, //CJK UNIFIED IDEOGRAPH - 0xF3BE: 0x7F36, //CJK UNIFIED IDEOGRAPH - 0xF3BF: 0x7F42, //CJK UNIFIED IDEOGRAPH - 0xF3C0: 0x7F44, //CJK UNIFIED IDEOGRAPH - 0xF3C1: 0x7F45, //CJK UNIFIED IDEOGRAPH - 0xF3C2: 0x8210, //CJK UNIFIED IDEOGRAPH - 0xF3C3: 0x7AFA, //CJK UNIFIED IDEOGRAPH - 0xF3C4: 0x7AFD, //CJK UNIFIED IDEOGRAPH - 0xF3C5: 0x7B08, //CJK UNIFIED IDEOGRAPH - 0xF3C6: 0x7B03, //CJK UNIFIED IDEOGRAPH - 0xF3C7: 0x7B04, //CJK UNIFIED IDEOGRAPH - 0xF3C8: 0x7B15, //CJK UNIFIED IDEOGRAPH - 0xF3C9: 0x7B0A, //CJK UNIFIED IDEOGRAPH - 0xF3CA: 0x7B2B, //CJK UNIFIED IDEOGRAPH - 0xF3CB: 0x7B0F, //CJK UNIFIED IDEOGRAPH - 0xF3CC: 0x7B47, //CJK UNIFIED IDEOGRAPH - 0xF3CD: 0x7B38, //CJK UNIFIED IDEOGRAPH - 0xF3CE: 0x7B2A, //CJK UNIFIED IDEOGRAPH - 0xF3CF: 0x7B19, //CJK UNIFIED IDEOGRAPH - 0xF3D0: 0x7B2E, //CJK UNIFIED IDEOGRAPH - 0xF3D1: 0x7B31, //CJK UNIFIED IDEOGRAPH - 0xF3D2: 0x7B20, //CJK UNIFIED IDEOGRAPH - 0xF3D3: 0x7B25, //CJK UNIFIED IDEOGRAPH - 0xF3D4: 0x7B24, //CJK UNIFIED IDEOGRAPH - 0xF3D5: 0x7B33, //CJK UNIFIED IDEOGRAPH - 0xF3D6: 0x7B3E, //CJK UNIFIED IDEOGRAPH - 0xF3D7: 0x7B1E, //CJK UNIFIED IDEOGRAPH - 0xF3D8: 0x7B58, //CJK UNIFIED IDEOGRAPH - 0xF3D9: 0x7B5A, //CJK UNIFIED IDEOGRAPH - 0xF3DA: 0x7B45, //CJK UNIFIED IDEOGRAPH - 0xF3DB: 0x7B75, //CJK UNIFIED IDEOGRAPH - 0xF3DC: 0x7B4C, //CJK UNIFIED IDEOGRAPH - 0xF3DD: 0x7B5D, //CJK UNIFIED IDEOGRAPH - 0xF3DE: 0x7B60, //CJK UNIFIED IDEOGRAPH - 0xF3DF: 0x7B6E, //CJK UNIFIED IDEOGRAPH - 0xF3E0: 0x7B7B, //CJK UNIFIED IDEOGRAPH - 0xF3E1: 0x7B62, //CJK UNIFIED IDEOGRAPH - 0xF3E2: 0x7B72, //CJK UNIFIED IDEOGRAPH - 0xF3E3: 0x7B71, //CJK UNIFIED IDEOGRAPH - 0xF3E4: 0x7B90, //CJK UNIFIED IDEOGRAPH - 0xF3E5: 0x7BA6, //CJK UNIFIED IDEOGRAPH - 0xF3E6: 0x7BA7, //CJK UNIFIED IDEOGRAPH - 0xF3E7: 0x7BB8, //CJK UNIFIED IDEOGRAPH - 0xF3E8: 0x7BAC, //CJK UNIFIED IDEOGRAPH - 0xF3E9: 0x7B9D, //CJK UNIFIED IDEOGRAPH - 0xF3EA: 0x7BA8, //CJK UNIFIED IDEOGRAPH - 0xF3EB: 0x7B85, //CJK UNIFIED IDEOGRAPH - 0xF3EC: 0x7BAA, //CJK UNIFIED IDEOGRAPH - 0xF3ED: 0x7B9C, //CJK UNIFIED IDEOGRAPH - 0xF3EE: 0x7BA2, //CJK UNIFIED IDEOGRAPH - 0xF3EF: 0x7BAB, //CJK UNIFIED IDEOGRAPH - 0xF3F0: 0x7BB4, //CJK UNIFIED IDEOGRAPH - 0xF3F1: 0x7BD1, //CJK UNIFIED IDEOGRAPH - 0xF3F2: 0x7BC1, //CJK UNIFIED IDEOGRAPH - 0xF3F3: 0x7BCC, //CJK UNIFIED IDEOGRAPH - 0xF3F4: 0x7BDD, //CJK UNIFIED IDEOGRAPH - 0xF3F5: 0x7BDA, //CJK UNIFIED IDEOGRAPH - 0xF3F6: 0x7BE5, //CJK UNIFIED IDEOGRAPH - 0xF3F7: 0x7BE6, //CJK UNIFIED IDEOGRAPH - 0xF3F8: 0x7BEA, //CJK UNIFIED IDEOGRAPH - 0xF3F9: 0x7C0C, //CJK UNIFIED IDEOGRAPH - 0xF3FA: 0x7BFE, //CJK UNIFIED IDEOGRAPH - 0xF3FB: 0x7BFC, //CJK UNIFIED IDEOGRAPH - 0xF3FC: 0x7C0F, //CJK UNIFIED IDEOGRAPH - 0xF3FD: 0x7C16, //CJK UNIFIED IDEOGRAPH - 0xF3FE: 0x7C0B, //CJK UNIFIED IDEOGRAPH - 0xF440: 0x9B07, //CJK UNIFIED IDEOGRAPH - 0xF441: 0x9B09, //CJK UNIFIED IDEOGRAPH - 0xF442: 0x9B0A, //CJK UNIFIED IDEOGRAPH - 0xF443: 0x9B0B, //CJK UNIFIED IDEOGRAPH - 0xF444: 0x9B0C, //CJK UNIFIED IDEOGRAPH - 0xF445: 0x9B0D, //CJK UNIFIED IDEOGRAPH - 0xF446: 0x9B0E, //CJK UNIFIED IDEOGRAPH - 0xF447: 0x9B10, //CJK UNIFIED IDEOGRAPH - 0xF448: 0x9B11, //CJK UNIFIED IDEOGRAPH - 0xF449: 0x9B12, //CJK UNIFIED IDEOGRAPH - 0xF44A: 0x9B14, //CJK UNIFIED IDEOGRAPH - 0xF44B: 0x9B15, //CJK UNIFIED IDEOGRAPH - 0xF44C: 0x9B16, //CJK UNIFIED IDEOGRAPH - 0xF44D: 0x9B17, //CJK UNIFIED IDEOGRAPH - 0xF44E: 0x9B18, //CJK UNIFIED IDEOGRAPH - 0xF44F: 0x9B19, //CJK UNIFIED IDEOGRAPH - 0xF450: 0x9B1A, //CJK UNIFIED IDEOGRAPH - 0xF451: 0x9B1B, //CJK UNIFIED IDEOGRAPH - 0xF452: 0x9B1C, //CJK UNIFIED IDEOGRAPH - 0xF453: 0x9B1D, //CJK UNIFIED IDEOGRAPH - 0xF454: 0x9B1E, //CJK UNIFIED IDEOGRAPH - 0xF455: 0x9B20, //CJK UNIFIED IDEOGRAPH - 0xF456: 0x9B21, //CJK UNIFIED IDEOGRAPH - 0xF457: 0x9B22, //CJK UNIFIED IDEOGRAPH - 0xF458: 0x9B24, //CJK UNIFIED IDEOGRAPH - 0xF459: 0x9B25, //CJK UNIFIED IDEOGRAPH - 0xF45A: 0x9B26, //CJK UNIFIED IDEOGRAPH - 0xF45B: 0x9B27, //CJK UNIFIED IDEOGRAPH - 0xF45C: 0x9B28, //CJK UNIFIED IDEOGRAPH - 0xF45D: 0x9B29, //CJK UNIFIED IDEOGRAPH - 0xF45E: 0x9B2A, //CJK UNIFIED IDEOGRAPH - 0xF45F: 0x9B2B, //CJK UNIFIED IDEOGRAPH - 0xF460: 0x9B2C, //CJK UNIFIED IDEOGRAPH - 0xF461: 0x9B2D, //CJK UNIFIED IDEOGRAPH - 0xF462: 0x9B2E, //CJK UNIFIED IDEOGRAPH - 0xF463: 0x9B30, //CJK UNIFIED IDEOGRAPH - 0xF464: 0x9B31, //CJK UNIFIED IDEOGRAPH - 0xF465: 0x9B33, //CJK UNIFIED IDEOGRAPH - 0xF466: 0x9B34, //CJK UNIFIED IDEOGRAPH - 0xF467: 0x9B35, //CJK UNIFIED IDEOGRAPH - 0xF468: 0x9B36, //CJK UNIFIED IDEOGRAPH - 0xF469: 0x9B37, //CJK UNIFIED IDEOGRAPH - 0xF46A: 0x9B38, //CJK UNIFIED IDEOGRAPH - 0xF46B: 0x9B39, //CJK UNIFIED IDEOGRAPH - 0xF46C: 0x9B3A, //CJK UNIFIED IDEOGRAPH - 0xF46D: 0x9B3D, //CJK UNIFIED IDEOGRAPH - 0xF46E: 0x9B3E, //CJK UNIFIED IDEOGRAPH - 0xF46F: 0x9B3F, //CJK UNIFIED IDEOGRAPH - 0xF470: 0x9B40, //CJK UNIFIED IDEOGRAPH - 0xF471: 0x9B46, //CJK UNIFIED IDEOGRAPH - 0xF472: 0x9B4A, //CJK UNIFIED IDEOGRAPH - 0xF473: 0x9B4B, //CJK UNIFIED IDEOGRAPH - 0xF474: 0x9B4C, //CJK UNIFIED IDEOGRAPH - 0xF475: 0x9B4E, //CJK UNIFIED IDEOGRAPH - 0xF476: 0x9B50, //CJK UNIFIED IDEOGRAPH - 0xF477: 0x9B52, //CJK UNIFIED IDEOGRAPH - 0xF478: 0x9B53, //CJK UNIFIED IDEOGRAPH - 0xF479: 0x9B55, //CJK UNIFIED IDEOGRAPH - 0xF47A: 0x9B56, //CJK UNIFIED IDEOGRAPH - 0xF47B: 0x9B57, //CJK UNIFIED IDEOGRAPH - 0xF47C: 0x9B58, //CJK UNIFIED IDEOGRAPH - 0xF47D: 0x9B59, //CJK UNIFIED IDEOGRAPH - 0xF47E: 0x9B5A, //CJK UNIFIED IDEOGRAPH - 0xF480: 0x9B5B, //CJK UNIFIED IDEOGRAPH - 0xF481: 0x9B5C, //CJK UNIFIED IDEOGRAPH - 0xF482: 0x9B5D, //CJK UNIFIED IDEOGRAPH - 0xF483: 0x9B5E, //CJK UNIFIED IDEOGRAPH - 0xF484: 0x9B5F, //CJK UNIFIED IDEOGRAPH - 0xF485: 0x9B60, //CJK UNIFIED IDEOGRAPH - 0xF486: 0x9B61, //CJK UNIFIED IDEOGRAPH - 0xF487: 0x9B62, //CJK UNIFIED IDEOGRAPH - 0xF488: 0x9B63, //CJK UNIFIED IDEOGRAPH - 0xF489: 0x9B64, //CJK UNIFIED IDEOGRAPH - 0xF48A: 0x9B65, //CJK UNIFIED IDEOGRAPH - 0xF48B: 0x9B66, //CJK UNIFIED IDEOGRAPH - 0xF48C: 0x9B67, //CJK UNIFIED IDEOGRAPH - 0xF48D: 0x9B68, //CJK UNIFIED IDEOGRAPH - 0xF48E: 0x9B69, //CJK UNIFIED IDEOGRAPH - 0xF48F: 0x9B6A, //CJK UNIFIED IDEOGRAPH - 0xF490: 0x9B6B, //CJK UNIFIED IDEOGRAPH - 0xF491: 0x9B6C, //CJK UNIFIED IDEOGRAPH - 0xF492: 0x9B6D, //CJK UNIFIED IDEOGRAPH - 0xF493: 0x9B6E, //CJK UNIFIED IDEOGRAPH - 0xF494: 0x9B6F, //CJK UNIFIED IDEOGRAPH - 0xF495: 0x9B70, //CJK UNIFIED IDEOGRAPH - 0xF496: 0x9B71, //CJK UNIFIED IDEOGRAPH - 0xF497: 0x9B72, //CJK UNIFIED IDEOGRAPH - 0xF498: 0x9B73, //CJK UNIFIED IDEOGRAPH - 0xF499: 0x9B74, //CJK UNIFIED IDEOGRAPH - 0xF49A: 0x9B75, //CJK UNIFIED IDEOGRAPH - 0xF49B: 0x9B76, //CJK UNIFIED IDEOGRAPH - 0xF49C: 0x9B77, //CJK UNIFIED IDEOGRAPH - 0xF49D: 0x9B78, //CJK UNIFIED IDEOGRAPH - 0xF49E: 0x9B79, //CJK UNIFIED IDEOGRAPH - 0xF49F: 0x9B7A, //CJK UNIFIED IDEOGRAPH - 0xF4A0: 0x9B7B, //CJK UNIFIED IDEOGRAPH - 0xF4A1: 0x7C1F, //CJK UNIFIED IDEOGRAPH - 0xF4A2: 0x7C2A, //CJK UNIFIED IDEOGRAPH - 0xF4A3: 0x7C26, //CJK UNIFIED IDEOGRAPH - 0xF4A4: 0x7C38, //CJK UNIFIED IDEOGRAPH - 0xF4A5: 0x7C41, //CJK UNIFIED IDEOGRAPH - 0xF4A6: 0x7C40, //CJK UNIFIED IDEOGRAPH - 0xF4A7: 0x81FE, //CJK UNIFIED IDEOGRAPH - 0xF4A8: 0x8201, //CJK UNIFIED IDEOGRAPH - 0xF4A9: 0x8202, //CJK UNIFIED IDEOGRAPH - 0xF4AA: 0x8204, //CJK UNIFIED IDEOGRAPH - 0xF4AB: 0x81EC, //CJK UNIFIED IDEOGRAPH - 0xF4AC: 0x8844, //CJK UNIFIED IDEOGRAPH - 0xF4AD: 0x8221, //CJK UNIFIED IDEOGRAPH - 0xF4AE: 0x8222, //CJK UNIFIED IDEOGRAPH - 0xF4AF: 0x8223, //CJK UNIFIED IDEOGRAPH - 0xF4B0: 0x822D, //CJK UNIFIED IDEOGRAPH - 0xF4B1: 0x822F, //CJK UNIFIED IDEOGRAPH - 0xF4B2: 0x8228, //CJK UNIFIED IDEOGRAPH - 0xF4B3: 0x822B, //CJK UNIFIED IDEOGRAPH - 0xF4B4: 0x8238, //CJK UNIFIED IDEOGRAPH - 0xF4B5: 0x823B, //CJK UNIFIED IDEOGRAPH - 0xF4B6: 0x8233, //CJK UNIFIED IDEOGRAPH - 0xF4B7: 0x8234, //CJK UNIFIED IDEOGRAPH - 0xF4B8: 0x823E, //CJK UNIFIED IDEOGRAPH - 0xF4B9: 0x8244, //CJK UNIFIED IDEOGRAPH - 0xF4BA: 0x8249, //CJK UNIFIED IDEOGRAPH - 0xF4BB: 0x824B, //CJK UNIFIED IDEOGRAPH - 0xF4BC: 0x824F, //CJK UNIFIED IDEOGRAPH - 0xF4BD: 0x825A, //CJK UNIFIED IDEOGRAPH - 0xF4BE: 0x825F, //CJK UNIFIED IDEOGRAPH - 0xF4BF: 0x8268, //CJK UNIFIED IDEOGRAPH - 0xF4C0: 0x887E, //CJK UNIFIED IDEOGRAPH - 0xF4C1: 0x8885, //CJK UNIFIED IDEOGRAPH - 0xF4C2: 0x8888, //CJK UNIFIED IDEOGRAPH - 0xF4C3: 0x88D8, //CJK UNIFIED IDEOGRAPH - 0xF4C4: 0x88DF, //CJK UNIFIED IDEOGRAPH - 0xF4C5: 0x895E, //CJK UNIFIED IDEOGRAPH - 0xF4C6: 0x7F9D, //CJK UNIFIED IDEOGRAPH - 0xF4C7: 0x7F9F, //CJK UNIFIED IDEOGRAPH - 0xF4C8: 0x7FA7, //CJK UNIFIED IDEOGRAPH - 0xF4C9: 0x7FAF, //CJK UNIFIED IDEOGRAPH - 0xF4CA: 0x7FB0, //CJK UNIFIED IDEOGRAPH - 0xF4CB: 0x7FB2, //CJK UNIFIED IDEOGRAPH - 0xF4CC: 0x7C7C, //CJK UNIFIED IDEOGRAPH - 0xF4CD: 0x6549, //CJK UNIFIED IDEOGRAPH - 0xF4CE: 0x7C91, //CJK UNIFIED IDEOGRAPH - 0xF4CF: 0x7C9D, //CJK UNIFIED IDEOGRAPH - 0xF4D0: 0x7C9C, //CJK UNIFIED IDEOGRAPH - 0xF4D1: 0x7C9E, //CJK UNIFIED IDEOGRAPH - 0xF4D2: 0x7CA2, //CJK UNIFIED IDEOGRAPH - 0xF4D3: 0x7CB2, //CJK UNIFIED IDEOGRAPH - 0xF4D4: 0x7CBC, //CJK UNIFIED IDEOGRAPH - 0xF4D5: 0x7CBD, //CJK UNIFIED IDEOGRAPH - 0xF4D6: 0x7CC1, //CJK UNIFIED IDEOGRAPH - 0xF4D7: 0x7CC7, //CJK UNIFIED IDEOGRAPH - 0xF4D8: 0x7CCC, //CJK UNIFIED IDEOGRAPH - 0xF4D9: 0x7CCD, //CJK UNIFIED IDEOGRAPH - 0xF4DA: 0x7CC8, //CJK UNIFIED IDEOGRAPH - 0xF4DB: 0x7CC5, //CJK UNIFIED IDEOGRAPH - 0xF4DC: 0x7CD7, //CJK UNIFIED IDEOGRAPH - 0xF4DD: 0x7CE8, //CJK UNIFIED IDEOGRAPH - 0xF4DE: 0x826E, //CJK UNIFIED IDEOGRAPH - 0xF4DF: 0x66A8, //CJK UNIFIED IDEOGRAPH - 0xF4E0: 0x7FBF, //CJK UNIFIED IDEOGRAPH - 0xF4E1: 0x7FCE, //CJK UNIFIED IDEOGRAPH - 0xF4E2: 0x7FD5, //CJK UNIFIED IDEOGRAPH - 0xF4E3: 0x7FE5, //CJK UNIFIED IDEOGRAPH - 0xF4E4: 0x7FE1, //CJK UNIFIED IDEOGRAPH - 0xF4E5: 0x7FE6, //CJK UNIFIED IDEOGRAPH - 0xF4E6: 0x7FE9, //CJK UNIFIED IDEOGRAPH - 0xF4E7: 0x7FEE, //CJK UNIFIED IDEOGRAPH - 0xF4E8: 0x7FF3, //CJK UNIFIED IDEOGRAPH - 0xF4E9: 0x7CF8, //CJK UNIFIED IDEOGRAPH - 0xF4EA: 0x7D77, //CJK UNIFIED IDEOGRAPH - 0xF4EB: 0x7DA6, //CJK UNIFIED IDEOGRAPH - 0xF4EC: 0x7DAE, //CJK UNIFIED IDEOGRAPH - 0xF4ED: 0x7E47, //CJK UNIFIED IDEOGRAPH - 0xF4EE: 0x7E9B, //CJK UNIFIED IDEOGRAPH - 0xF4EF: 0x9EB8, //CJK UNIFIED IDEOGRAPH - 0xF4F0: 0x9EB4, //CJK UNIFIED IDEOGRAPH - 0xF4F1: 0x8D73, //CJK UNIFIED IDEOGRAPH - 0xF4F2: 0x8D84, //CJK UNIFIED IDEOGRAPH - 0xF4F3: 0x8D94, //CJK UNIFIED IDEOGRAPH - 0xF4F4: 0x8D91, //CJK UNIFIED IDEOGRAPH - 0xF4F5: 0x8DB1, //CJK UNIFIED IDEOGRAPH - 0xF4F6: 0x8D67, //CJK UNIFIED IDEOGRAPH - 0xF4F7: 0x8D6D, //CJK UNIFIED IDEOGRAPH - 0xF4F8: 0x8C47, //CJK UNIFIED IDEOGRAPH - 0xF4F9: 0x8C49, //CJK UNIFIED IDEOGRAPH - 0xF4FA: 0x914A, //CJK UNIFIED IDEOGRAPH - 0xF4FB: 0x9150, //CJK UNIFIED IDEOGRAPH - 0xF4FC: 0x914E, //CJK UNIFIED IDEOGRAPH - 0xF4FD: 0x914F, //CJK UNIFIED IDEOGRAPH - 0xF4FE: 0x9164, //CJK UNIFIED IDEOGRAPH - 0xF540: 0x9B7C, //CJK UNIFIED IDEOGRAPH - 0xF541: 0x9B7D, //CJK UNIFIED IDEOGRAPH - 0xF542: 0x9B7E, //CJK UNIFIED IDEOGRAPH - 0xF543: 0x9B7F, //CJK UNIFIED IDEOGRAPH - 0xF544: 0x9B80, //CJK UNIFIED IDEOGRAPH - 0xF545: 0x9B81, //CJK UNIFIED IDEOGRAPH - 0xF546: 0x9B82, //CJK UNIFIED IDEOGRAPH - 0xF547: 0x9B83, //CJK UNIFIED IDEOGRAPH - 0xF548: 0x9B84, //CJK UNIFIED IDEOGRAPH - 0xF549: 0x9B85, //CJK UNIFIED IDEOGRAPH - 0xF54A: 0x9B86, //CJK UNIFIED IDEOGRAPH - 0xF54B: 0x9B87, //CJK UNIFIED IDEOGRAPH - 0xF54C: 0x9B88, //CJK UNIFIED IDEOGRAPH - 0xF54D: 0x9B89, //CJK UNIFIED IDEOGRAPH - 0xF54E: 0x9B8A, //CJK UNIFIED IDEOGRAPH - 0xF54F: 0x9B8B, //CJK UNIFIED IDEOGRAPH - 0xF550: 0x9B8C, //CJK UNIFIED IDEOGRAPH - 0xF551: 0x9B8D, //CJK UNIFIED IDEOGRAPH - 0xF552: 0x9B8E, //CJK UNIFIED IDEOGRAPH - 0xF553: 0x9B8F, //CJK UNIFIED IDEOGRAPH - 0xF554: 0x9B90, //CJK UNIFIED IDEOGRAPH - 0xF555: 0x9B91, //CJK UNIFIED IDEOGRAPH - 0xF556: 0x9B92, //CJK UNIFIED IDEOGRAPH - 0xF557: 0x9B93, //CJK UNIFIED IDEOGRAPH - 0xF558: 0x9B94, //CJK UNIFIED IDEOGRAPH - 0xF559: 0x9B95, //CJK UNIFIED IDEOGRAPH - 0xF55A: 0x9B96, //CJK UNIFIED IDEOGRAPH - 0xF55B: 0x9B97, //CJK UNIFIED IDEOGRAPH - 0xF55C: 0x9B98, //CJK UNIFIED IDEOGRAPH - 0xF55D: 0x9B99, //CJK UNIFIED IDEOGRAPH - 0xF55E: 0x9B9A, //CJK UNIFIED IDEOGRAPH - 0xF55F: 0x9B9B, //CJK UNIFIED IDEOGRAPH - 0xF560: 0x9B9C, //CJK UNIFIED IDEOGRAPH - 0xF561: 0x9B9D, //CJK UNIFIED IDEOGRAPH - 0xF562: 0x9B9E, //CJK UNIFIED IDEOGRAPH - 0xF563: 0x9B9F, //CJK UNIFIED IDEOGRAPH - 0xF564: 0x9BA0, //CJK UNIFIED IDEOGRAPH - 0xF565: 0x9BA1, //CJK UNIFIED IDEOGRAPH - 0xF566: 0x9BA2, //CJK UNIFIED IDEOGRAPH - 0xF567: 0x9BA3, //CJK UNIFIED IDEOGRAPH - 0xF568: 0x9BA4, //CJK UNIFIED IDEOGRAPH - 0xF569: 0x9BA5, //CJK UNIFIED IDEOGRAPH - 0xF56A: 0x9BA6, //CJK UNIFIED IDEOGRAPH - 0xF56B: 0x9BA7, //CJK UNIFIED IDEOGRAPH - 0xF56C: 0x9BA8, //CJK UNIFIED IDEOGRAPH - 0xF56D: 0x9BA9, //CJK UNIFIED IDEOGRAPH - 0xF56E: 0x9BAA, //CJK UNIFIED IDEOGRAPH - 0xF56F: 0x9BAB, //CJK UNIFIED IDEOGRAPH - 0xF570: 0x9BAC, //CJK UNIFIED IDEOGRAPH - 0xF571: 0x9BAD, //CJK UNIFIED IDEOGRAPH - 0xF572: 0x9BAE, //CJK UNIFIED IDEOGRAPH - 0xF573: 0x9BAF, //CJK UNIFIED IDEOGRAPH - 0xF574: 0x9BB0, //CJK UNIFIED IDEOGRAPH - 0xF575: 0x9BB1, //CJK UNIFIED IDEOGRAPH - 0xF576: 0x9BB2, //CJK UNIFIED IDEOGRAPH - 0xF577: 0x9BB3, //CJK UNIFIED IDEOGRAPH - 0xF578: 0x9BB4, //CJK UNIFIED IDEOGRAPH - 0xF579: 0x9BB5, //CJK UNIFIED IDEOGRAPH - 0xF57A: 0x9BB6, //CJK UNIFIED IDEOGRAPH - 0xF57B: 0x9BB7, //CJK UNIFIED IDEOGRAPH - 0xF57C: 0x9BB8, //CJK UNIFIED IDEOGRAPH - 0xF57D: 0x9BB9, //CJK UNIFIED IDEOGRAPH - 0xF57E: 0x9BBA, //CJK UNIFIED IDEOGRAPH - 0xF580: 0x9BBB, //CJK UNIFIED IDEOGRAPH - 0xF581: 0x9BBC, //CJK UNIFIED IDEOGRAPH - 0xF582: 0x9BBD, //CJK UNIFIED IDEOGRAPH - 0xF583: 0x9BBE, //CJK UNIFIED IDEOGRAPH - 0xF584: 0x9BBF, //CJK UNIFIED IDEOGRAPH - 0xF585: 0x9BC0, //CJK UNIFIED IDEOGRAPH - 0xF586: 0x9BC1, //CJK UNIFIED IDEOGRAPH - 0xF587: 0x9BC2, //CJK UNIFIED IDEOGRAPH - 0xF588: 0x9BC3, //CJK UNIFIED IDEOGRAPH - 0xF589: 0x9BC4, //CJK UNIFIED IDEOGRAPH - 0xF58A: 0x9BC5, //CJK UNIFIED IDEOGRAPH - 0xF58B: 0x9BC6, //CJK UNIFIED IDEOGRAPH - 0xF58C: 0x9BC7, //CJK UNIFIED IDEOGRAPH - 0xF58D: 0x9BC8, //CJK UNIFIED IDEOGRAPH - 0xF58E: 0x9BC9, //CJK UNIFIED IDEOGRAPH - 0xF58F: 0x9BCA, //CJK UNIFIED IDEOGRAPH - 0xF590: 0x9BCB, //CJK UNIFIED IDEOGRAPH - 0xF591: 0x9BCC, //CJK UNIFIED IDEOGRAPH - 0xF592: 0x9BCD, //CJK UNIFIED IDEOGRAPH - 0xF593: 0x9BCE, //CJK UNIFIED IDEOGRAPH - 0xF594: 0x9BCF, //CJK UNIFIED IDEOGRAPH - 0xF595: 0x9BD0, //CJK UNIFIED IDEOGRAPH - 0xF596: 0x9BD1, //CJK UNIFIED IDEOGRAPH - 0xF597: 0x9BD2, //CJK UNIFIED IDEOGRAPH - 0xF598: 0x9BD3, //CJK UNIFIED IDEOGRAPH - 0xF599: 0x9BD4, //CJK UNIFIED IDEOGRAPH - 0xF59A: 0x9BD5, //CJK UNIFIED IDEOGRAPH - 0xF59B: 0x9BD6, //CJK UNIFIED IDEOGRAPH - 0xF59C: 0x9BD7, //CJK UNIFIED IDEOGRAPH - 0xF59D: 0x9BD8, //CJK UNIFIED IDEOGRAPH - 0xF59E: 0x9BD9, //CJK UNIFIED IDEOGRAPH - 0xF59F: 0x9BDA, //CJK UNIFIED IDEOGRAPH - 0xF5A0: 0x9BDB, //CJK UNIFIED IDEOGRAPH - 0xF5A1: 0x9162, //CJK UNIFIED IDEOGRAPH - 0xF5A2: 0x9161, //CJK UNIFIED IDEOGRAPH - 0xF5A3: 0x9170, //CJK UNIFIED IDEOGRAPH - 0xF5A4: 0x9169, //CJK UNIFIED IDEOGRAPH - 0xF5A5: 0x916F, //CJK UNIFIED IDEOGRAPH - 0xF5A6: 0x917D, //CJK UNIFIED IDEOGRAPH - 0xF5A7: 0x917E, //CJK UNIFIED IDEOGRAPH - 0xF5A8: 0x9172, //CJK UNIFIED IDEOGRAPH - 0xF5A9: 0x9174, //CJK UNIFIED IDEOGRAPH - 0xF5AA: 0x9179, //CJK UNIFIED IDEOGRAPH - 0xF5AB: 0x918C, //CJK UNIFIED IDEOGRAPH - 0xF5AC: 0x9185, //CJK UNIFIED IDEOGRAPH - 0xF5AD: 0x9190, //CJK UNIFIED IDEOGRAPH - 0xF5AE: 0x918D, //CJK UNIFIED IDEOGRAPH - 0xF5AF: 0x9191, //CJK UNIFIED IDEOGRAPH - 0xF5B0: 0x91A2, //CJK UNIFIED IDEOGRAPH - 0xF5B1: 0x91A3, //CJK UNIFIED IDEOGRAPH - 0xF5B2: 0x91AA, //CJK UNIFIED IDEOGRAPH - 0xF5B3: 0x91AD, //CJK UNIFIED IDEOGRAPH - 0xF5B4: 0x91AE, //CJK UNIFIED IDEOGRAPH - 0xF5B5: 0x91AF, //CJK UNIFIED IDEOGRAPH - 0xF5B6: 0x91B5, //CJK UNIFIED IDEOGRAPH - 0xF5B7: 0x91B4, //CJK UNIFIED IDEOGRAPH - 0xF5B8: 0x91BA, //CJK UNIFIED IDEOGRAPH - 0xF5B9: 0x8C55, //CJK UNIFIED IDEOGRAPH - 0xF5BA: 0x9E7E, //CJK UNIFIED IDEOGRAPH - 0xF5BB: 0x8DB8, //CJK UNIFIED IDEOGRAPH - 0xF5BC: 0x8DEB, //CJK UNIFIED IDEOGRAPH - 0xF5BD: 0x8E05, //CJK UNIFIED IDEOGRAPH - 0xF5BE: 0x8E59, //CJK UNIFIED IDEOGRAPH - 0xF5BF: 0x8E69, //CJK UNIFIED IDEOGRAPH - 0xF5C0: 0x8DB5, //CJK UNIFIED IDEOGRAPH - 0xF5C1: 0x8DBF, //CJK UNIFIED IDEOGRAPH - 0xF5C2: 0x8DBC, //CJK UNIFIED IDEOGRAPH - 0xF5C3: 0x8DBA, //CJK UNIFIED IDEOGRAPH - 0xF5C4: 0x8DC4, //CJK UNIFIED IDEOGRAPH - 0xF5C5: 0x8DD6, //CJK UNIFIED IDEOGRAPH - 0xF5C6: 0x8DD7, //CJK UNIFIED IDEOGRAPH - 0xF5C7: 0x8DDA, //CJK UNIFIED IDEOGRAPH - 0xF5C8: 0x8DDE, //CJK UNIFIED IDEOGRAPH - 0xF5C9: 0x8DCE, //CJK UNIFIED IDEOGRAPH - 0xF5CA: 0x8DCF, //CJK UNIFIED IDEOGRAPH - 0xF5CB: 0x8DDB, //CJK UNIFIED IDEOGRAPH - 0xF5CC: 0x8DC6, //CJK UNIFIED IDEOGRAPH - 0xF5CD: 0x8DEC, //CJK UNIFIED IDEOGRAPH - 0xF5CE: 0x8DF7, //CJK UNIFIED IDEOGRAPH - 0xF5CF: 0x8DF8, //CJK UNIFIED IDEOGRAPH - 0xF5D0: 0x8DE3, //CJK UNIFIED IDEOGRAPH - 0xF5D1: 0x8DF9, //CJK UNIFIED IDEOGRAPH - 0xF5D2: 0x8DFB, //CJK UNIFIED IDEOGRAPH - 0xF5D3: 0x8DE4, //CJK UNIFIED IDEOGRAPH - 0xF5D4: 0x8E09, //CJK UNIFIED IDEOGRAPH - 0xF5D5: 0x8DFD, //CJK UNIFIED IDEOGRAPH - 0xF5D6: 0x8E14, //CJK UNIFIED IDEOGRAPH - 0xF5D7: 0x8E1D, //CJK UNIFIED IDEOGRAPH - 0xF5D8: 0x8E1F, //CJK UNIFIED IDEOGRAPH - 0xF5D9: 0x8E2C, //CJK UNIFIED IDEOGRAPH - 0xF5DA: 0x8E2E, //CJK UNIFIED IDEOGRAPH - 0xF5DB: 0x8E23, //CJK UNIFIED IDEOGRAPH - 0xF5DC: 0x8E2F, //CJK UNIFIED IDEOGRAPH - 0xF5DD: 0x8E3A, //CJK UNIFIED IDEOGRAPH - 0xF5DE: 0x8E40, //CJK UNIFIED IDEOGRAPH - 0xF5DF: 0x8E39, //CJK UNIFIED IDEOGRAPH - 0xF5E0: 0x8E35, //CJK UNIFIED IDEOGRAPH - 0xF5E1: 0x8E3D, //CJK UNIFIED IDEOGRAPH - 0xF5E2: 0x8E31, //CJK UNIFIED IDEOGRAPH - 0xF5E3: 0x8E49, //CJK UNIFIED IDEOGRAPH - 0xF5E4: 0x8E41, //CJK UNIFIED IDEOGRAPH - 0xF5E5: 0x8E42, //CJK UNIFIED IDEOGRAPH - 0xF5E6: 0x8E51, //CJK UNIFIED IDEOGRAPH - 0xF5E7: 0x8E52, //CJK UNIFIED IDEOGRAPH - 0xF5E8: 0x8E4A, //CJK UNIFIED IDEOGRAPH - 0xF5E9: 0x8E70, //CJK UNIFIED IDEOGRAPH - 0xF5EA: 0x8E76, //CJK UNIFIED IDEOGRAPH - 0xF5EB: 0x8E7C, //CJK UNIFIED IDEOGRAPH - 0xF5EC: 0x8E6F, //CJK UNIFIED IDEOGRAPH - 0xF5ED: 0x8E74, //CJK UNIFIED IDEOGRAPH - 0xF5EE: 0x8E85, //CJK UNIFIED IDEOGRAPH - 0xF5EF: 0x8E8F, //CJK UNIFIED IDEOGRAPH - 0xF5F0: 0x8E94, //CJK UNIFIED IDEOGRAPH - 0xF5F1: 0x8E90, //CJK UNIFIED IDEOGRAPH - 0xF5F2: 0x8E9C, //CJK UNIFIED IDEOGRAPH - 0xF5F3: 0x8E9E, //CJK UNIFIED IDEOGRAPH - 0xF5F4: 0x8C78, //CJK UNIFIED IDEOGRAPH - 0xF5F5: 0x8C82, //CJK UNIFIED IDEOGRAPH - 0xF5F6: 0x8C8A, //CJK UNIFIED IDEOGRAPH - 0xF5F7: 0x8C85, //CJK UNIFIED IDEOGRAPH - 0xF5F8: 0x8C98, //CJK UNIFIED IDEOGRAPH - 0xF5F9: 0x8C94, //CJK UNIFIED IDEOGRAPH - 0xF5FA: 0x659B, //CJK UNIFIED IDEOGRAPH - 0xF5FB: 0x89D6, //CJK UNIFIED IDEOGRAPH - 0xF5FC: 0x89DE, //CJK UNIFIED IDEOGRAPH - 0xF5FD: 0x89DA, //CJK UNIFIED IDEOGRAPH - 0xF5FE: 0x89DC, //CJK UNIFIED IDEOGRAPH - 0xF640: 0x9BDC, //CJK UNIFIED IDEOGRAPH - 0xF641: 0x9BDD, //CJK UNIFIED IDEOGRAPH - 0xF642: 0x9BDE, //CJK UNIFIED IDEOGRAPH - 0xF643: 0x9BDF, //CJK UNIFIED IDEOGRAPH - 0xF644: 0x9BE0, //CJK UNIFIED IDEOGRAPH - 0xF645: 0x9BE1, //CJK UNIFIED IDEOGRAPH - 0xF646: 0x9BE2, //CJK UNIFIED IDEOGRAPH - 0xF647: 0x9BE3, //CJK UNIFIED IDEOGRAPH - 0xF648: 0x9BE4, //CJK UNIFIED IDEOGRAPH - 0xF649: 0x9BE5, //CJK UNIFIED IDEOGRAPH - 0xF64A: 0x9BE6, //CJK UNIFIED IDEOGRAPH - 0xF64B: 0x9BE7, //CJK UNIFIED IDEOGRAPH - 0xF64C: 0x9BE8, //CJK UNIFIED IDEOGRAPH - 0xF64D: 0x9BE9, //CJK UNIFIED IDEOGRAPH - 0xF64E: 0x9BEA, //CJK UNIFIED IDEOGRAPH - 0xF64F: 0x9BEB, //CJK UNIFIED IDEOGRAPH - 0xF650: 0x9BEC, //CJK UNIFIED IDEOGRAPH - 0xF651: 0x9BED, //CJK UNIFIED IDEOGRAPH - 0xF652: 0x9BEE, //CJK UNIFIED IDEOGRAPH - 0xF653: 0x9BEF, //CJK UNIFIED IDEOGRAPH - 0xF654: 0x9BF0, //CJK UNIFIED IDEOGRAPH - 0xF655: 0x9BF1, //CJK UNIFIED IDEOGRAPH - 0xF656: 0x9BF2, //CJK UNIFIED IDEOGRAPH - 0xF657: 0x9BF3, //CJK UNIFIED IDEOGRAPH - 0xF658: 0x9BF4, //CJK UNIFIED IDEOGRAPH - 0xF659: 0x9BF5, //CJK UNIFIED IDEOGRAPH - 0xF65A: 0x9BF6, //CJK UNIFIED IDEOGRAPH - 0xF65B: 0x9BF7, //CJK UNIFIED IDEOGRAPH - 0xF65C: 0x9BF8, //CJK UNIFIED IDEOGRAPH - 0xF65D: 0x9BF9, //CJK UNIFIED IDEOGRAPH - 0xF65E: 0x9BFA, //CJK UNIFIED IDEOGRAPH - 0xF65F: 0x9BFB, //CJK UNIFIED IDEOGRAPH - 0xF660: 0x9BFC, //CJK UNIFIED IDEOGRAPH - 0xF661: 0x9BFD, //CJK UNIFIED IDEOGRAPH - 0xF662: 0x9BFE, //CJK UNIFIED IDEOGRAPH - 0xF663: 0x9BFF, //CJK UNIFIED IDEOGRAPH - 0xF664: 0x9C00, //CJK UNIFIED IDEOGRAPH - 0xF665: 0x9C01, //CJK UNIFIED IDEOGRAPH - 0xF666: 0x9C02, //CJK UNIFIED IDEOGRAPH - 0xF667: 0x9C03, //CJK UNIFIED IDEOGRAPH - 0xF668: 0x9C04, //CJK UNIFIED IDEOGRAPH - 0xF669: 0x9C05, //CJK UNIFIED IDEOGRAPH - 0xF66A: 0x9C06, //CJK UNIFIED IDEOGRAPH - 0xF66B: 0x9C07, //CJK UNIFIED IDEOGRAPH - 0xF66C: 0x9C08, //CJK UNIFIED IDEOGRAPH - 0xF66D: 0x9C09, //CJK UNIFIED IDEOGRAPH - 0xF66E: 0x9C0A, //CJK UNIFIED IDEOGRAPH - 0xF66F: 0x9C0B, //CJK UNIFIED IDEOGRAPH - 0xF670: 0x9C0C, //CJK UNIFIED IDEOGRAPH - 0xF671: 0x9C0D, //CJK UNIFIED IDEOGRAPH - 0xF672: 0x9C0E, //CJK UNIFIED IDEOGRAPH - 0xF673: 0x9C0F, //CJK UNIFIED IDEOGRAPH - 0xF674: 0x9C10, //CJK UNIFIED IDEOGRAPH - 0xF675: 0x9C11, //CJK UNIFIED IDEOGRAPH - 0xF676: 0x9C12, //CJK UNIFIED IDEOGRAPH - 0xF677: 0x9C13, //CJK UNIFIED IDEOGRAPH - 0xF678: 0x9C14, //CJK UNIFIED IDEOGRAPH - 0xF679: 0x9C15, //CJK UNIFIED IDEOGRAPH - 0xF67A: 0x9C16, //CJK UNIFIED IDEOGRAPH - 0xF67B: 0x9C17, //CJK UNIFIED IDEOGRAPH - 0xF67C: 0x9C18, //CJK UNIFIED IDEOGRAPH - 0xF67D: 0x9C19, //CJK UNIFIED IDEOGRAPH - 0xF67E: 0x9C1A, //CJK UNIFIED IDEOGRAPH - 0xF680: 0x9C1B, //CJK UNIFIED IDEOGRAPH - 0xF681: 0x9C1C, //CJK UNIFIED IDEOGRAPH - 0xF682: 0x9C1D, //CJK UNIFIED IDEOGRAPH - 0xF683: 0x9C1E, //CJK UNIFIED IDEOGRAPH - 0xF684: 0x9C1F, //CJK UNIFIED IDEOGRAPH - 0xF685: 0x9C20, //CJK UNIFIED IDEOGRAPH - 0xF686: 0x9C21, //CJK UNIFIED IDEOGRAPH - 0xF687: 0x9C22, //CJK UNIFIED IDEOGRAPH - 0xF688: 0x9C23, //CJK UNIFIED IDEOGRAPH - 0xF689: 0x9C24, //CJK UNIFIED IDEOGRAPH - 0xF68A: 0x9C25, //CJK UNIFIED IDEOGRAPH - 0xF68B: 0x9C26, //CJK UNIFIED IDEOGRAPH - 0xF68C: 0x9C27, //CJK UNIFIED IDEOGRAPH - 0xF68D: 0x9C28, //CJK UNIFIED IDEOGRAPH - 0xF68E: 0x9C29, //CJK UNIFIED IDEOGRAPH - 0xF68F: 0x9C2A, //CJK UNIFIED IDEOGRAPH - 0xF690: 0x9C2B, //CJK UNIFIED IDEOGRAPH - 0xF691: 0x9C2C, //CJK UNIFIED IDEOGRAPH - 0xF692: 0x9C2D, //CJK UNIFIED IDEOGRAPH - 0xF693: 0x9C2E, //CJK UNIFIED IDEOGRAPH - 0xF694: 0x9C2F, //CJK UNIFIED IDEOGRAPH - 0xF695: 0x9C30, //CJK UNIFIED IDEOGRAPH - 0xF696: 0x9C31, //CJK UNIFIED IDEOGRAPH - 0xF697: 0x9C32, //CJK UNIFIED IDEOGRAPH - 0xF698: 0x9C33, //CJK UNIFIED IDEOGRAPH - 0xF699: 0x9C34, //CJK UNIFIED IDEOGRAPH - 0xF69A: 0x9C35, //CJK UNIFIED IDEOGRAPH - 0xF69B: 0x9C36, //CJK UNIFIED IDEOGRAPH - 0xF69C: 0x9C37, //CJK UNIFIED IDEOGRAPH - 0xF69D: 0x9C38, //CJK UNIFIED IDEOGRAPH - 0xF69E: 0x9C39, //CJK UNIFIED IDEOGRAPH - 0xF69F: 0x9C3A, //CJK UNIFIED IDEOGRAPH - 0xF6A0: 0x9C3B, //CJK UNIFIED IDEOGRAPH - 0xF6A1: 0x89E5, //CJK UNIFIED IDEOGRAPH - 0xF6A2: 0x89EB, //CJK UNIFIED IDEOGRAPH - 0xF6A3: 0x89EF, //CJK UNIFIED IDEOGRAPH - 0xF6A4: 0x8A3E, //CJK UNIFIED IDEOGRAPH - 0xF6A5: 0x8B26, //CJK UNIFIED IDEOGRAPH - 0xF6A6: 0x9753, //CJK UNIFIED IDEOGRAPH - 0xF6A7: 0x96E9, //CJK UNIFIED IDEOGRAPH - 0xF6A8: 0x96F3, //CJK UNIFIED IDEOGRAPH - 0xF6A9: 0x96EF, //CJK UNIFIED IDEOGRAPH - 0xF6AA: 0x9706, //CJK UNIFIED IDEOGRAPH - 0xF6AB: 0x9701, //CJK UNIFIED IDEOGRAPH - 0xF6AC: 0x9708, //CJK UNIFIED IDEOGRAPH - 0xF6AD: 0x970F, //CJK UNIFIED IDEOGRAPH - 0xF6AE: 0x970E, //CJK UNIFIED IDEOGRAPH - 0xF6AF: 0x972A, //CJK UNIFIED IDEOGRAPH - 0xF6B0: 0x972D, //CJK UNIFIED IDEOGRAPH - 0xF6B1: 0x9730, //CJK UNIFIED IDEOGRAPH - 0xF6B2: 0x973E, //CJK UNIFIED IDEOGRAPH - 0xF6B3: 0x9F80, //CJK UNIFIED IDEOGRAPH - 0xF6B4: 0x9F83, //CJK UNIFIED IDEOGRAPH - 0xF6B5: 0x9F85, //CJK UNIFIED IDEOGRAPH - 0xF6B6: 0x9F86, //CJK UNIFIED IDEOGRAPH - 0xF6B7: 0x9F87, //CJK UNIFIED IDEOGRAPH - 0xF6B8: 0x9F88, //CJK UNIFIED IDEOGRAPH - 0xF6B9: 0x9F89, //CJK UNIFIED IDEOGRAPH - 0xF6BA: 0x9F8A, //CJK UNIFIED IDEOGRAPH - 0xF6BB: 0x9F8C, //CJK UNIFIED IDEOGRAPH - 0xF6BC: 0x9EFE, //CJK UNIFIED IDEOGRAPH - 0xF6BD: 0x9F0B, //CJK UNIFIED IDEOGRAPH - 0xF6BE: 0x9F0D, //CJK UNIFIED IDEOGRAPH - 0xF6BF: 0x96B9, //CJK UNIFIED IDEOGRAPH - 0xF6C0: 0x96BC, //CJK UNIFIED IDEOGRAPH - 0xF6C1: 0x96BD, //CJK UNIFIED IDEOGRAPH - 0xF6C2: 0x96CE, //CJK UNIFIED IDEOGRAPH - 0xF6C3: 0x96D2, //CJK UNIFIED IDEOGRAPH - 0xF6C4: 0x77BF, //CJK UNIFIED IDEOGRAPH - 0xF6C5: 0x96E0, //CJK UNIFIED IDEOGRAPH - 0xF6C6: 0x928E, //CJK UNIFIED IDEOGRAPH - 0xF6C7: 0x92AE, //CJK UNIFIED IDEOGRAPH - 0xF6C8: 0x92C8, //CJK UNIFIED IDEOGRAPH - 0xF6C9: 0x933E, //CJK UNIFIED IDEOGRAPH - 0xF6CA: 0x936A, //CJK UNIFIED IDEOGRAPH - 0xF6CB: 0x93CA, //CJK UNIFIED IDEOGRAPH - 0xF6CC: 0x938F, //CJK UNIFIED IDEOGRAPH - 0xF6CD: 0x943E, //CJK UNIFIED IDEOGRAPH - 0xF6CE: 0x946B, //CJK UNIFIED IDEOGRAPH - 0xF6CF: 0x9C7F, //CJK UNIFIED IDEOGRAPH - 0xF6D0: 0x9C82, //CJK UNIFIED IDEOGRAPH - 0xF6D1: 0x9C85, //CJK UNIFIED IDEOGRAPH - 0xF6D2: 0x9C86, //CJK UNIFIED IDEOGRAPH - 0xF6D3: 0x9C87, //CJK UNIFIED IDEOGRAPH - 0xF6D4: 0x9C88, //CJK UNIFIED IDEOGRAPH - 0xF6D5: 0x7A23, //CJK UNIFIED IDEOGRAPH - 0xF6D6: 0x9C8B, //CJK UNIFIED IDEOGRAPH - 0xF6D7: 0x9C8E, //CJK UNIFIED IDEOGRAPH - 0xF6D8: 0x9C90, //CJK UNIFIED IDEOGRAPH - 0xF6D9: 0x9C91, //CJK UNIFIED IDEOGRAPH - 0xF6DA: 0x9C92, //CJK UNIFIED IDEOGRAPH - 0xF6DB: 0x9C94, //CJK UNIFIED IDEOGRAPH - 0xF6DC: 0x9C95, //CJK UNIFIED IDEOGRAPH - 0xF6DD: 0x9C9A, //CJK UNIFIED IDEOGRAPH - 0xF6DE: 0x9C9B, //CJK UNIFIED IDEOGRAPH - 0xF6DF: 0x9C9E, //CJK UNIFIED IDEOGRAPH - 0xF6E0: 0x9C9F, //CJK UNIFIED IDEOGRAPH - 0xF6E1: 0x9CA0, //CJK UNIFIED IDEOGRAPH - 0xF6E2: 0x9CA1, //CJK UNIFIED IDEOGRAPH - 0xF6E3: 0x9CA2, //CJK UNIFIED IDEOGRAPH - 0xF6E4: 0x9CA3, //CJK UNIFIED IDEOGRAPH - 0xF6E5: 0x9CA5, //CJK UNIFIED IDEOGRAPH - 0xF6E6: 0x9CA6, //CJK UNIFIED IDEOGRAPH - 0xF6E7: 0x9CA7, //CJK UNIFIED IDEOGRAPH - 0xF6E8: 0x9CA8, //CJK UNIFIED IDEOGRAPH - 0xF6E9: 0x9CA9, //CJK UNIFIED IDEOGRAPH - 0xF6EA: 0x9CAB, //CJK UNIFIED IDEOGRAPH - 0xF6EB: 0x9CAD, //CJK UNIFIED IDEOGRAPH - 0xF6EC: 0x9CAE, //CJK UNIFIED IDEOGRAPH - 0xF6ED: 0x9CB0, //CJK UNIFIED IDEOGRAPH - 0xF6EE: 0x9CB1, //CJK UNIFIED IDEOGRAPH - 0xF6EF: 0x9CB2, //CJK UNIFIED IDEOGRAPH - 0xF6F0: 0x9CB3, //CJK UNIFIED IDEOGRAPH - 0xF6F1: 0x9CB4, //CJK UNIFIED IDEOGRAPH - 0xF6F2: 0x9CB5, //CJK UNIFIED IDEOGRAPH - 0xF6F3: 0x9CB6, //CJK UNIFIED IDEOGRAPH - 0xF6F4: 0x9CB7, //CJK UNIFIED IDEOGRAPH - 0xF6F5: 0x9CBA, //CJK UNIFIED IDEOGRAPH - 0xF6F6: 0x9CBB, //CJK UNIFIED IDEOGRAPH - 0xF6F7: 0x9CBC, //CJK UNIFIED IDEOGRAPH - 0xF6F8: 0x9CBD, //CJK UNIFIED IDEOGRAPH - 0xF6F9: 0x9CC4, //CJK UNIFIED IDEOGRAPH - 0xF6FA: 0x9CC5, //CJK UNIFIED IDEOGRAPH - 0xF6FB: 0x9CC6, //CJK UNIFIED IDEOGRAPH - 0xF6FC: 0x9CC7, //CJK UNIFIED IDEOGRAPH - 0xF6FD: 0x9CCA, //CJK UNIFIED IDEOGRAPH - 0xF6FE: 0x9CCB, //CJK UNIFIED IDEOGRAPH - 0xF740: 0x9C3C, //CJK UNIFIED IDEOGRAPH - 0xF741: 0x9C3D, //CJK UNIFIED IDEOGRAPH - 0xF742: 0x9C3E, //CJK UNIFIED IDEOGRAPH - 0xF743: 0x9C3F, //CJK UNIFIED IDEOGRAPH - 0xF744: 0x9C40, //CJK UNIFIED IDEOGRAPH - 0xF745: 0x9C41, //CJK UNIFIED IDEOGRAPH - 0xF746: 0x9C42, //CJK UNIFIED IDEOGRAPH - 0xF747: 0x9C43, //CJK UNIFIED IDEOGRAPH - 0xF748: 0x9C44, //CJK UNIFIED IDEOGRAPH - 0xF749: 0x9C45, //CJK UNIFIED IDEOGRAPH - 0xF74A: 0x9C46, //CJK UNIFIED IDEOGRAPH - 0xF74B: 0x9C47, //CJK UNIFIED IDEOGRAPH - 0xF74C: 0x9C48, //CJK UNIFIED IDEOGRAPH - 0xF74D: 0x9C49, //CJK UNIFIED IDEOGRAPH - 0xF74E: 0x9C4A, //CJK UNIFIED IDEOGRAPH - 0xF74F: 0x9C4B, //CJK UNIFIED IDEOGRAPH - 0xF750: 0x9C4C, //CJK UNIFIED IDEOGRAPH - 0xF751: 0x9C4D, //CJK UNIFIED IDEOGRAPH - 0xF752: 0x9C4E, //CJK UNIFIED IDEOGRAPH - 0xF753: 0x9C4F, //CJK UNIFIED IDEOGRAPH - 0xF754: 0x9C50, //CJK UNIFIED IDEOGRAPH - 0xF755: 0x9C51, //CJK UNIFIED IDEOGRAPH - 0xF756: 0x9C52, //CJK UNIFIED IDEOGRAPH - 0xF757: 0x9C53, //CJK UNIFIED IDEOGRAPH - 0xF758: 0x9C54, //CJK UNIFIED IDEOGRAPH - 0xF759: 0x9C55, //CJK UNIFIED IDEOGRAPH - 0xF75A: 0x9C56, //CJK UNIFIED IDEOGRAPH - 0xF75B: 0x9C57, //CJK UNIFIED IDEOGRAPH - 0xF75C: 0x9C58, //CJK UNIFIED IDEOGRAPH - 0xF75D: 0x9C59, //CJK UNIFIED IDEOGRAPH - 0xF75E: 0x9C5A, //CJK UNIFIED IDEOGRAPH - 0xF75F: 0x9C5B, //CJK UNIFIED IDEOGRAPH - 0xF760: 0x9C5C, //CJK UNIFIED IDEOGRAPH - 0xF761: 0x9C5D, //CJK UNIFIED IDEOGRAPH - 0xF762: 0x9C5E, //CJK UNIFIED IDEOGRAPH - 0xF763: 0x9C5F, //CJK UNIFIED IDEOGRAPH - 0xF764: 0x9C60, //CJK UNIFIED IDEOGRAPH - 0xF765: 0x9C61, //CJK UNIFIED IDEOGRAPH - 0xF766: 0x9C62, //CJK UNIFIED IDEOGRAPH - 0xF767: 0x9C63, //CJK UNIFIED IDEOGRAPH - 0xF768: 0x9C64, //CJK UNIFIED IDEOGRAPH - 0xF769: 0x9C65, //CJK UNIFIED IDEOGRAPH - 0xF76A: 0x9C66, //CJK UNIFIED IDEOGRAPH - 0xF76B: 0x9C67, //CJK UNIFIED IDEOGRAPH - 0xF76C: 0x9C68, //CJK UNIFIED IDEOGRAPH - 0xF76D: 0x9C69, //CJK UNIFIED IDEOGRAPH - 0xF76E: 0x9C6A, //CJK UNIFIED IDEOGRAPH - 0xF76F: 0x9C6B, //CJK UNIFIED IDEOGRAPH - 0xF770: 0x9C6C, //CJK UNIFIED IDEOGRAPH - 0xF771: 0x9C6D, //CJK UNIFIED IDEOGRAPH - 0xF772: 0x9C6E, //CJK UNIFIED IDEOGRAPH - 0xF773: 0x9C6F, //CJK UNIFIED IDEOGRAPH - 0xF774: 0x9C70, //CJK UNIFIED IDEOGRAPH - 0xF775: 0x9C71, //CJK UNIFIED IDEOGRAPH - 0xF776: 0x9C72, //CJK UNIFIED IDEOGRAPH - 0xF777: 0x9C73, //CJK UNIFIED IDEOGRAPH - 0xF778: 0x9C74, //CJK UNIFIED IDEOGRAPH - 0xF779: 0x9C75, //CJK UNIFIED IDEOGRAPH - 0xF77A: 0x9C76, //CJK UNIFIED IDEOGRAPH - 0xF77B: 0x9C77, //CJK UNIFIED IDEOGRAPH - 0xF77C: 0x9C78, //CJK UNIFIED IDEOGRAPH - 0xF77D: 0x9C79, //CJK UNIFIED IDEOGRAPH - 0xF77E: 0x9C7A, //CJK UNIFIED IDEOGRAPH - 0xF780: 0x9C7B, //CJK UNIFIED IDEOGRAPH - 0xF781: 0x9C7D, //CJK UNIFIED IDEOGRAPH - 0xF782: 0x9C7E, //CJK UNIFIED IDEOGRAPH - 0xF783: 0x9C80, //CJK UNIFIED IDEOGRAPH - 0xF784: 0x9C83, //CJK UNIFIED IDEOGRAPH - 0xF785: 0x9C84, //CJK UNIFIED IDEOGRAPH - 0xF786: 0x9C89, //CJK UNIFIED IDEOGRAPH - 0xF787: 0x9C8A, //CJK UNIFIED IDEOGRAPH - 0xF788: 0x9C8C, //CJK UNIFIED IDEOGRAPH - 0xF789: 0x9C8F, //CJK UNIFIED IDEOGRAPH - 0xF78A: 0x9C93, //CJK UNIFIED IDEOGRAPH - 0xF78B: 0x9C96, //CJK UNIFIED IDEOGRAPH - 0xF78C: 0x9C97, //CJK UNIFIED IDEOGRAPH - 0xF78D: 0x9C98, //CJK UNIFIED IDEOGRAPH - 0xF78E: 0x9C99, //CJK UNIFIED IDEOGRAPH - 0xF78F: 0x9C9D, //CJK UNIFIED IDEOGRAPH - 0xF790: 0x9CAA, //CJK UNIFIED IDEOGRAPH - 0xF791: 0x9CAC, //CJK UNIFIED IDEOGRAPH - 0xF792: 0x9CAF, //CJK UNIFIED IDEOGRAPH - 0xF793: 0x9CB9, //CJK UNIFIED IDEOGRAPH - 0xF794: 0x9CBE, //CJK UNIFIED IDEOGRAPH - 0xF795: 0x9CBF, //CJK UNIFIED IDEOGRAPH - 0xF796: 0x9CC0, //CJK UNIFIED IDEOGRAPH - 0xF797: 0x9CC1, //CJK UNIFIED IDEOGRAPH - 0xF798: 0x9CC2, //CJK UNIFIED IDEOGRAPH - 0xF799: 0x9CC8, //CJK UNIFIED IDEOGRAPH - 0xF79A: 0x9CC9, //CJK UNIFIED IDEOGRAPH - 0xF79B: 0x9CD1, //CJK UNIFIED IDEOGRAPH - 0xF79C: 0x9CD2, //CJK UNIFIED IDEOGRAPH - 0xF79D: 0x9CDA, //CJK UNIFIED IDEOGRAPH - 0xF79E: 0x9CDB, //CJK UNIFIED IDEOGRAPH - 0xF79F: 0x9CE0, //CJK UNIFIED IDEOGRAPH - 0xF7A0: 0x9CE1, //CJK UNIFIED IDEOGRAPH - 0xF7A1: 0x9CCC, //CJK UNIFIED IDEOGRAPH - 0xF7A2: 0x9CCD, //CJK UNIFIED IDEOGRAPH - 0xF7A3: 0x9CCE, //CJK UNIFIED IDEOGRAPH - 0xF7A4: 0x9CCF, //CJK UNIFIED IDEOGRAPH - 0xF7A5: 0x9CD0, //CJK UNIFIED IDEOGRAPH - 0xF7A6: 0x9CD3, //CJK UNIFIED IDEOGRAPH - 0xF7A7: 0x9CD4, //CJK UNIFIED IDEOGRAPH - 0xF7A8: 0x9CD5, //CJK UNIFIED IDEOGRAPH - 0xF7A9: 0x9CD7, //CJK UNIFIED IDEOGRAPH - 0xF7AA: 0x9CD8, //CJK UNIFIED IDEOGRAPH - 0xF7AB: 0x9CD9, //CJK UNIFIED IDEOGRAPH - 0xF7AC: 0x9CDC, //CJK UNIFIED IDEOGRAPH - 0xF7AD: 0x9CDD, //CJK UNIFIED IDEOGRAPH - 0xF7AE: 0x9CDF, //CJK UNIFIED IDEOGRAPH - 0xF7AF: 0x9CE2, //CJK UNIFIED IDEOGRAPH - 0xF7B0: 0x977C, //CJK UNIFIED IDEOGRAPH - 0xF7B1: 0x9785, //CJK UNIFIED IDEOGRAPH - 0xF7B2: 0x9791, //CJK UNIFIED IDEOGRAPH - 0xF7B3: 0x9792, //CJK UNIFIED IDEOGRAPH - 0xF7B4: 0x9794, //CJK UNIFIED IDEOGRAPH - 0xF7B5: 0x97AF, //CJK UNIFIED IDEOGRAPH - 0xF7B6: 0x97AB, //CJK UNIFIED IDEOGRAPH - 0xF7B7: 0x97A3, //CJK UNIFIED IDEOGRAPH - 0xF7B8: 0x97B2, //CJK UNIFIED IDEOGRAPH - 0xF7B9: 0x97B4, //CJK UNIFIED IDEOGRAPH - 0xF7BA: 0x9AB1, //CJK UNIFIED IDEOGRAPH - 0xF7BB: 0x9AB0, //CJK UNIFIED IDEOGRAPH - 0xF7BC: 0x9AB7, //CJK UNIFIED IDEOGRAPH - 0xF7BD: 0x9E58, //CJK UNIFIED IDEOGRAPH - 0xF7BE: 0x9AB6, //CJK UNIFIED IDEOGRAPH - 0xF7BF: 0x9ABA, //CJK UNIFIED IDEOGRAPH - 0xF7C0: 0x9ABC, //CJK UNIFIED IDEOGRAPH - 0xF7C1: 0x9AC1, //CJK UNIFIED IDEOGRAPH - 0xF7C2: 0x9AC0, //CJK UNIFIED IDEOGRAPH - 0xF7C3: 0x9AC5, //CJK UNIFIED IDEOGRAPH - 0xF7C4: 0x9AC2, //CJK UNIFIED IDEOGRAPH - 0xF7C5: 0x9ACB, //CJK UNIFIED IDEOGRAPH - 0xF7C6: 0x9ACC, //CJK UNIFIED IDEOGRAPH - 0xF7C7: 0x9AD1, //CJK UNIFIED IDEOGRAPH - 0xF7C8: 0x9B45, //CJK UNIFIED IDEOGRAPH - 0xF7C9: 0x9B43, //CJK UNIFIED IDEOGRAPH - 0xF7CA: 0x9B47, //CJK UNIFIED IDEOGRAPH - 0xF7CB: 0x9B49, //CJK UNIFIED IDEOGRAPH - 0xF7CC: 0x9B48, //CJK UNIFIED IDEOGRAPH - 0xF7CD: 0x9B4D, //CJK UNIFIED IDEOGRAPH - 0xF7CE: 0x9B51, //CJK UNIFIED IDEOGRAPH - 0xF7CF: 0x98E8, //CJK UNIFIED IDEOGRAPH - 0xF7D0: 0x990D, //CJK UNIFIED IDEOGRAPH - 0xF7D1: 0x992E, //CJK UNIFIED IDEOGRAPH - 0xF7D2: 0x9955, //CJK UNIFIED IDEOGRAPH - 0xF7D3: 0x9954, //CJK UNIFIED IDEOGRAPH - 0xF7D4: 0x9ADF, //CJK UNIFIED IDEOGRAPH - 0xF7D5: 0x9AE1, //CJK UNIFIED IDEOGRAPH - 0xF7D6: 0x9AE6, //CJK UNIFIED IDEOGRAPH - 0xF7D7: 0x9AEF, //CJK UNIFIED IDEOGRAPH - 0xF7D8: 0x9AEB, //CJK UNIFIED IDEOGRAPH - 0xF7D9: 0x9AFB, //CJK UNIFIED IDEOGRAPH - 0xF7DA: 0x9AED, //CJK UNIFIED IDEOGRAPH - 0xF7DB: 0x9AF9, //CJK UNIFIED IDEOGRAPH - 0xF7DC: 0x9B08, //CJK UNIFIED IDEOGRAPH - 0xF7DD: 0x9B0F, //CJK UNIFIED IDEOGRAPH - 0xF7DE: 0x9B13, //CJK UNIFIED IDEOGRAPH - 0xF7DF: 0x9B1F, //CJK UNIFIED IDEOGRAPH - 0xF7E0: 0x9B23, //CJK UNIFIED IDEOGRAPH - 0xF7E1: 0x9EBD, //CJK UNIFIED IDEOGRAPH - 0xF7E2: 0x9EBE, //CJK UNIFIED IDEOGRAPH - 0xF7E3: 0x7E3B, //CJK UNIFIED IDEOGRAPH - 0xF7E4: 0x9E82, //CJK UNIFIED IDEOGRAPH - 0xF7E5: 0x9E87, //CJK UNIFIED IDEOGRAPH - 0xF7E6: 0x9E88, //CJK UNIFIED IDEOGRAPH - 0xF7E7: 0x9E8B, //CJK UNIFIED IDEOGRAPH - 0xF7E8: 0x9E92, //CJK UNIFIED IDEOGRAPH - 0xF7E9: 0x93D6, //CJK UNIFIED IDEOGRAPH - 0xF7EA: 0x9E9D, //CJK UNIFIED IDEOGRAPH - 0xF7EB: 0x9E9F, //CJK UNIFIED IDEOGRAPH - 0xF7EC: 0x9EDB, //CJK UNIFIED IDEOGRAPH - 0xF7ED: 0x9EDC, //CJK UNIFIED IDEOGRAPH - 0xF7EE: 0x9EDD, //CJK UNIFIED IDEOGRAPH - 0xF7EF: 0x9EE0, //CJK UNIFIED IDEOGRAPH - 0xF7F0: 0x9EDF, //CJK UNIFIED IDEOGRAPH - 0xF7F1: 0x9EE2, //CJK UNIFIED IDEOGRAPH - 0xF7F2: 0x9EE9, //CJK UNIFIED IDEOGRAPH - 0xF7F3: 0x9EE7, //CJK UNIFIED IDEOGRAPH - 0xF7F4: 0x9EE5, //CJK UNIFIED IDEOGRAPH - 0xF7F5: 0x9EEA, //CJK UNIFIED IDEOGRAPH - 0xF7F6: 0x9EEF, //CJK UNIFIED IDEOGRAPH - 0xF7F7: 0x9F22, //CJK UNIFIED IDEOGRAPH - 0xF7F8: 0x9F2C, //CJK UNIFIED IDEOGRAPH - 0xF7F9: 0x9F2F, //CJK UNIFIED IDEOGRAPH - 0xF7FA: 0x9F39, //CJK UNIFIED IDEOGRAPH - 0xF7FB: 0x9F37, //CJK UNIFIED IDEOGRAPH - 0xF7FC: 0x9F3D, //CJK UNIFIED IDEOGRAPH - 0xF7FD: 0x9F3E, //CJK UNIFIED IDEOGRAPH - 0xF7FE: 0x9F44, //CJK UNIFIED IDEOGRAPH - 0xF840: 0x9CE3, //CJK UNIFIED IDEOGRAPH - 0xF841: 0x9CE4, //CJK UNIFIED IDEOGRAPH - 0xF842: 0x9CE5, //CJK UNIFIED IDEOGRAPH - 0xF843: 0x9CE6, //CJK UNIFIED IDEOGRAPH - 0xF844: 0x9CE7, //CJK UNIFIED IDEOGRAPH - 0xF845: 0x9CE8, //CJK UNIFIED IDEOGRAPH - 0xF846: 0x9CE9, //CJK UNIFIED IDEOGRAPH - 0xF847: 0x9CEA, //CJK UNIFIED IDEOGRAPH - 0xF848: 0x9CEB, //CJK UNIFIED IDEOGRAPH - 0xF849: 0x9CEC, //CJK UNIFIED IDEOGRAPH - 0xF84A: 0x9CED, //CJK UNIFIED IDEOGRAPH - 0xF84B: 0x9CEE, //CJK UNIFIED IDEOGRAPH - 0xF84C: 0x9CEF, //CJK UNIFIED IDEOGRAPH - 0xF84D: 0x9CF0, //CJK UNIFIED IDEOGRAPH - 0xF84E: 0x9CF1, //CJK UNIFIED IDEOGRAPH - 0xF84F: 0x9CF2, //CJK UNIFIED IDEOGRAPH - 0xF850: 0x9CF3, //CJK UNIFIED IDEOGRAPH - 0xF851: 0x9CF4, //CJK UNIFIED IDEOGRAPH - 0xF852: 0x9CF5, //CJK UNIFIED IDEOGRAPH - 0xF853: 0x9CF6, //CJK UNIFIED IDEOGRAPH - 0xF854: 0x9CF7, //CJK UNIFIED IDEOGRAPH - 0xF855: 0x9CF8, //CJK UNIFIED IDEOGRAPH - 0xF856: 0x9CF9, //CJK UNIFIED IDEOGRAPH - 0xF857: 0x9CFA, //CJK UNIFIED IDEOGRAPH - 0xF858: 0x9CFB, //CJK UNIFIED IDEOGRAPH - 0xF859: 0x9CFC, //CJK UNIFIED IDEOGRAPH - 0xF85A: 0x9CFD, //CJK UNIFIED IDEOGRAPH - 0xF85B: 0x9CFE, //CJK UNIFIED IDEOGRAPH - 0xF85C: 0x9CFF, //CJK UNIFIED IDEOGRAPH - 0xF85D: 0x9D00, //CJK UNIFIED IDEOGRAPH - 0xF85E: 0x9D01, //CJK UNIFIED IDEOGRAPH - 0xF85F: 0x9D02, //CJK UNIFIED IDEOGRAPH - 0xF860: 0x9D03, //CJK UNIFIED IDEOGRAPH - 0xF861: 0x9D04, //CJK UNIFIED IDEOGRAPH - 0xF862: 0x9D05, //CJK UNIFIED IDEOGRAPH - 0xF863: 0x9D06, //CJK UNIFIED IDEOGRAPH - 0xF864: 0x9D07, //CJK UNIFIED IDEOGRAPH - 0xF865: 0x9D08, //CJK UNIFIED IDEOGRAPH - 0xF866: 0x9D09, //CJK UNIFIED IDEOGRAPH - 0xF867: 0x9D0A, //CJK UNIFIED IDEOGRAPH - 0xF868: 0x9D0B, //CJK UNIFIED IDEOGRAPH - 0xF869: 0x9D0C, //CJK UNIFIED IDEOGRAPH - 0xF86A: 0x9D0D, //CJK UNIFIED IDEOGRAPH - 0xF86B: 0x9D0E, //CJK UNIFIED IDEOGRAPH - 0xF86C: 0x9D0F, //CJK UNIFIED IDEOGRAPH - 0xF86D: 0x9D10, //CJK UNIFIED IDEOGRAPH - 0xF86E: 0x9D11, //CJK UNIFIED IDEOGRAPH - 0xF86F: 0x9D12, //CJK UNIFIED IDEOGRAPH - 0xF870: 0x9D13, //CJK UNIFIED IDEOGRAPH - 0xF871: 0x9D14, //CJK UNIFIED IDEOGRAPH - 0xF872: 0x9D15, //CJK UNIFIED IDEOGRAPH - 0xF873: 0x9D16, //CJK UNIFIED IDEOGRAPH - 0xF874: 0x9D17, //CJK UNIFIED IDEOGRAPH - 0xF875: 0x9D18, //CJK UNIFIED IDEOGRAPH - 0xF876: 0x9D19, //CJK UNIFIED IDEOGRAPH - 0xF877: 0x9D1A, //CJK UNIFIED IDEOGRAPH - 0xF878: 0x9D1B, //CJK UNIFIED IDEOGRAPH - 0xF879: 0x9D1C, //CJK UNIFIED IDEOGRAPH - 0xF87A: 0x9D1D, //CJK UNIFIED IDEOGRAPH - 0xF87B: 0x9D1E, //CJK UNIFIED IDEOGRAPH - 0xF87C: 0x9D1F, //CJK UNIFIED IDEOGRAPH - 0xF87D: 0x9D20, //CJK UNIFIED IDEOGRAPH - 0xF87E: 0x9D21, //CJK UNIFIED IDEOGRAPH - 0xF880: 0x9D22, //CJK UNIFIED IDEOGRAPH - 0xF881: 0x9D23, //CJK UNIFIED IDEOGRAPH - 0xF882: 0x9D24, //CJK UNIFIED IDEOGRAPH - 0xF883: 0x9D25, //CJK UNIFIED IDEOGRAPH - 0xF884: 0x9D26, //CJK UNIFIED IDEOGRAPH - 0xF885: 0x9D27, //CJK UNIFIED IDEOGRAPH - 0xF886: 0x9D28, //CJK UNIFIED IDEOGRAPH - 0xF887: 0x9D29, //CJK UNIFIED IDEOGRAPH - 0xF888: 0x9D2A, //CJK UNIFIED IDEOGRAPH - 0xF889: 0x9D2B, //CJK UNIFIED IDEOGRAPH - 0xF88A: 0x9D2C, //CJK UNIFIED IDEOGRAPH - 0xF88B: 0x9D2D, //CJK UNIFIED IDEOGRAPH - 0xF88C: 0x9D2E, //CJK UNIFIED IDEOGRAPH - 0xF88D: 0x9D2F, //CJK UNIFIED IDEOGRAPH - 0xF88E: 0x9D30, //CJK UNIFIED IDEOGRAPH - 0xF88F: 0x9D31, //CJK UNIFIED IDEOGRAPH - 0xF890: 0x9D32, //CJK UNIFIED IDEOGRAPH - 0xF891: 0x9D33, //CJK UNIFIED IDEOGRAPH - 0xF892: 0x9D34, //CJK UNIFIED IDEOGRAPH - 0xF893: 0x9D35, //CJK UNIFIED IDEOGRAPH - 0xF894: 0x9D36, //CJK UNIFIED IDEOGRAPH - 0xF895: 0x9D37, //CJK UNIFIED IDEOGRAPH - 0xF896: 0x9D38, //CJK UNIFIED IDEOGRAPH - 0xF897: 0x9D39, //CJK UNIFIED IDEOGRAPH - 0xF898: 0x9D3A, //CJK UNIFIED IDEOGRAPH - 0xF899: 0x9D3B, //CJK UNIFIED IDEOGRAPH - 0xF89A: 0x9D3C, //CJK UNIFIED IDEOGRAPH - 0xF89B: 0x9D3D, //CJK UNIFIED IDEOGRAPH - 0xF89C: 0x9D3E, //CJK UNIFIED IDEOGRAPH - 0xF89D: 0x9D3F, //CJK UNIFIED IDEOGRAPH - 0xF89E: 0x9D40, //CJK UNIFIED IDEOGRAPH - 0xF89F: 0x9D41, //CJK UNIFIED IDEOGRAPH - 0xF8A0: 0x9D42, //CJK UNIFIED IDEOGRAPH - 0xF940: 0x9D43, //CJK UNIFIED IDEOGRAPH - 0xF941: 0x9D44, //CJK UNIFIED IDEOGRAPH - 0xF942: 0x9D45, //CJK UNIFIED IDEOGRAPH - 0xF943: 0x9D46, //CJK UNIFIED IDEOGRAPH - 0xF944: 0x9D47, //CJK UNIFIED IDEOGRAPH - 0xF945: 0x9D48, //CJK UNIFIED IDEOGRAPH - 0xF946: 0x9D49, //CJK UNIFIED IDEOGRAPH - 0xF947: 0x9D4A, //CJK UNIFIED IDEOGRAPH - 0xF948: 0x9D4B, //CJK UNIFIED IDEOGRAPH - 0xF949: 0x9D4C, //CJK UNIFIED IDEOGRAPH - 0xF94A: 0x9D4D, //CJK UNIFIED IDEOGRAPH - 0xF94B: 0x9D4E, //CJK UNIFIED IDEOGRAPH - 0xF94C: 0x9D4F, //CJK UNIFIED IDEOGRAPH - 0xF94D: 0x9D50, //CJK UNIFIED IDEOGRAPH - 0xF94E: 0x9D51, //CJK UNIFIED IDEOGRAPH - 0xF94F: 0x9D52, //CJK UNIFIED IDEOGRAPH - 0xF950: 0x9D53, //CJK UNIFIED IDEOGRAPH - 0xF951: 0x9D54, //CJK UNIFIED IDEOGRAPH - 0xF952: 0x9D55, //CJK UNIFIED IDEOGRAPH - 0xF953: 0x9D56, //CJK UNIFIED IDEOGRAPH - 0xF954: 0x9D57, //CJK UNIFIED IDEOGRAPH - 0xF955: 0x9D58, //CJK UNIFIED IDEOGRAPH - 0xF956: 0x9D59, //CJK UNIFIED IDEOGRAPH - 0xF957: 0x9D5A, //CJK UNIFIED IDEOGRAPH - 0xF958: 0x9D5B, //CJK UNIFIED IDEOGRAPH - 0xF959: 0x9D5C, //CJK UNIFIED IDEOGRAPH - 0xF95A: 0x9D5D, //CJK UNIFIED IDEOGRAPH - 0xF95B: 0x9D5E, //CJK UNIFIED IDEOGRAPH - 0xF95C: 0x9D5F, //CJK UNIFIED IDEOGRAPH - 0xF95D: 0x9D60, //CJK UNIFIED IDEOGRAPH - 0xF95E: 0x9D61, //CJK UNIFIED IDEOGRAPH - 0xF95F: 0x9D62, //CJK UNIFIED IDEOGRAPH - 0xF960: 0x9D63, //CJK UNIFIED IDEOGRAPH - 0xF961: 0x9D64, //CJK UNIFIED IDEOGRAPH - 0xF962: 0x9D65, //CJK UNIFIED IDEOGRAPH - 0xF963: 0x9D66, //CJK UNIFIED IDEOGRAPH - 0xF964: 0x9D67, //CJK UNIFIED IDEOGRAPH - 0xF965: 0x9D68, //CJK UNIFIED IDEOGRAPH - 0xF966: 0x9D69, //CJK UNIFIED IDEOGRAPH - 0xF967: 0x9D6A, //CJK UNIFIED IDEOGRAPH - 0xF968: 0x9D6B, //CJK UNIFIED IDEOGRAPH - 0xF969: 0x9D6C, //CJK UNIFIED IDEOGRAPH - 0xF96A: 0x9D6D, //CJK UNIFIED IDEOGRAPH - 0xF96B: 0x9D6E, //CJK UNIFIED IDEOGRAPH - 0xF96C: 0x9D6F, //CJK UNIFIED IDEOGRAPH - 0xF96D: 0x9D70, //CJK UNIFIED IDEOGRAPH - 0xF96E: 0x9D71, //CJK UNIFIED IDEOGRAPH - 0xF96F: 0x9D72, //CJK UNIFIED IDEOGRAPH - 0xF970: 0x9D73, //CJK UNIFIED IDEOGRAPH - 0xF971: 0x9D74, //CJK UNIFIED IDEOGRAPH - 0xF972: 0x9D75, //CJK UNIFIED IDEOGRAPH - 0xF973: 0x9D76, //CJK UNIFIED IDEOGRAPH - 0xF974: 0x9D77, //CJK UNIFIED IDEOGRAPH - 0xF975: 0x9D78, //CJK UNIFIED IDEOGRAPH - 0xF976: 0x9D79, //CJK UNIFIED IDEOGRAPH - 0xF977: 0x9D7A, //CJK UNIFIED IDEOGRAPH - 0xF978: 0x9D7B, //CJK UNIFIED IDEOGRAPH - 0xF979: 0x9D7C, //CJK UNIFIED IDEOGRAPH - 0xF97A: 0x9D7D, //CJK UNIFIED IDEOGRAPH - 0xF97B: 0x9D7E, //CJK UNIFIED IDEOGRAPH - 0xF97C: 0x9D7F, //CJK UNIFIED IDEOGRAPH - 0xF97D: 0x9D80, //CJK UNIFIED IDEOGRAPH - 0xF97E: 0x9D81, //CJK UNIFIED IDEOGRAPH - 0xF980: 0x9D82, //CJK UNIFIED IDEOGRAPH - 0xF981: 0x9D83, //CJK UNIFIED IDEOGRAPH - 0xF982: 0x9D84, //CJK UNIFIED IDEOGRAPH - 0xF983: 0x9D85, //CJK UNIFIED IDEOGRAPH - 0xF984: 0x9D86, //CJK UNIFIED IDEOGRAPH - 0xF985: 0x9D87, //CJK UNIFIED IDEOGRAPH - 0xF986: 0x9D88, //CJK UNIFIED IDEOGRAPH - 0xF987: 0x9D89, //CJK UNIFIED IDEOGRAPH - 0xF988: 0x9D8A, //CJK UNIFIED IDEOGRAPH - 0xF989: 0x9D8B, //CJK UNIFIED IDEOGRAPH - 0xF98A: 0x9D8C, //CJK UNIFIED IDEOGRAPH - 0xF98B: 0x9D8D, //CJK UNIFIED IDEOGRAPH - 0xF98C: 0x9D8E, //CJK UNIFIED IDEOGRAPH - 0xF98D: 0x9D8F, //CJK UNIFIED IDEOGRAPH - 0xF98E: 0x9D90, //CJK UNIFIED IDEOGRAPH - 0xF98F: 0x9D91, //CJK UNIFIED IDEOGRAPH - 0xF990: 0x9D92, //CJK UNIFIED IDEOGRAPH - 0xF991: 0x9D93, //CJK UNIFIED IDEOGRAPH - 0xF992: 0x9D94, //CJK UNIFIED IDEOGRAPH - 0xF993: 0x9D95, //CJK UNIFIED IDEOGRAPH - 0xF994: 0x9D96, //CJK UNIFIED IDEOGRAPH - 0xF995: 0x9D97, //CJK UNIFIED IDEOGRAPH - 0xF996: 0x9D98, //CJK UNIFIED IDEOGRAPH - 0xF997: 0x9D99, //CJK UNIFIED IDEOGRAPH - 0xF998: 0x9D9A, //CJK UNIFIED IDEOGRAPH - 0xF999: 0x9D9B, //CJK UNIFIED IDEOGRAPH - 0xF99A: 0x9D9C, //CJK UNIFIED IDEOGRAPH - 0xF99B: 0x9D9D, //CJK UNIFIED IDEOGRAPH - 0xF99C: 0x9D9E, //CJK UNIFIED IDEOGRAPH - 0xF99D: 0x9D9F, //CJK UNIFIED IDEOGRAPH - 0xF99E: 0x9DA0, //CJK UNIFIED IDEOGRAPH - 0xF99F: 0x9DA1, //CJK UNIFIED IDEOGRAPH - 0xF9A0: 0x9DA2, //CJK UNIFIED IDEOGRAPH - 0xFA40: 0x9DA3, //CJK UNIFIED IDEOGRAPH - 0xFA41: 0x9DA4, //CJK UNIFIED IDEOGRAPH - 0xFA42: 0x9DA5, //CJK UNIFIED IDEOGRAPH - 0xFA43: 0x9DA6, //CJK UNIFIED IDEOGRAPH - 0xFA44: 0x9DA7, //CJK UNIFIED IDEOGRAPH - 0xFA45: 0x9DA8, //CJK UNIFIED IDEOGRAPH - 0xFA46: 0x9DA9, //CJK UNIFIED IDEOGRAPH - 0xFA47: 0x9DAA, //CJK UNIFIED IDEOGRAPH - 0xFA48: 0x9DAB, //CJK UNIFIED IDEOGRAPH - 0xFA49: 0x9DAC, //CJK UNIFIED IDEOGRAPH - 0xFA4A: 0x9DAD, //CJK UNIFIED IDEOGRAPH - 0xFA4B: 0x9DAE, //CJK UNIFIED IDEOGRAPH - 0xFA4C: 0x9DAF, //CJK UNIFIED IDEOGRAPH - 0xFA4D: 0x9DB0, //CJK UNIFIED IDEOGRAPH - 0xFA4E: 0x9DB1, //CJK UNIFIED IDEOGRAPH - 0xFA4F: 0x9DB2, //CJK UNIFIED IDEOGRAPH - 0xFA50: 0x9DB3, //CJK UNIFIED IDEOGRAPH - 0xFA51: 0x9DB4, //CJK UNIFIED IDEOGRAPH - 0xFA52: 0x9DB5, //CJK UNIFIED IDEOGRAPH - 0xFA53: 0x9DB6, //CJK UNIFIED IDEOGRAPH - 0xFA54: 0x9DB7, //CJK UNIFIED IDEOGRAPH - 0xFA55: 0x9DB8, //CJK UNIFIED IDEOGRAPH - 0xFA56: 0x9DB9, //CJK UNIFIED IDEOGRAPH - 0xFA57: 0x9DBA, //CJK UNIFIED IDEOGRAPH - 0xFA58: 0x9DBB, //CJK UNIFIED IDEOGRAPH - 0xFA59: 0x9DBC, //CJK UNIFIED IDEOGRAPH - 0xFA5A: 0x9DBD, //CJK UNIFIED IDEOGRAPH - 0xFA5B: 0x9DBE, //CJK UNIFIED IDEOGRAPH - 0xFA5C: 0x9DBF, //CJK UNIFIED IDEOGRAPH - 0xFA5D: 0x9DC0, //CJK UNIFIED IDEOGRAPH - 0xFA5E: 0x9DC1, //CJK UNIFIED IDEOGRAPH - 0xFA5F: 0x9DC2, //CJK UNIFIED IDEOGRAPH - 0xFA60: 0x9DC3, //CJK UNIFIED IDEOGRAPH - 0xFA61: 0x9DC4, //CJK UNIFIED IDEOGRAPH - 0xFA62: 0x9DC5, //CJK UNIFIED IDEOGRAPH - 0xFA63: 0x9DC6, //CJK UNIFIED IDEOGRAPH - 0xFA64: 0x9DC7, //CJK UNIFIED IDEOGRAPH - 0xFA65: 0x9DC8, //CJK UNIFIED IDEOGRAPH - 0xFA66: 0x9DC9, //CJK UNIFIED IDEOGRAPH - 0xFA67: 0x9DCA, //CJK UNIFIED IDEOGRAPH - 0xFA68: 0x9DCB, //CJK UNIFIED IDEOGRAPH - 0xFA69: 0x9DCC, //CJK UNIFIED IDEOGRAPH - 0xFA6A: 0x9DCD, //CJK UNIFIED IDEOGRAPH - 0xFA6B: 0x9DCE, //CJK UNIFIED IDEOGRAPH - 0xFA6C: 0x9DCF, //CJK UNIFIED IDEOGRAPH - 0xFA6D: 0x9DD0, //CJK UNIFIED IDEOGRAPH - 0xFA6E: 0x9DD1, //CJK UNIFIED IDEOGRAPH - 0xFA6F: 0x9DD2, //CJK UNIFIED IDEOGRAPH - 0xFA70: 0x9DD3, //CJK UNIFIED IDEOGRAPH - 0xFA71: 0x9DD4, //CJK UNIFIED IDEOGRAPH - 0xFA72: 0x9DD5, //CJK UNIFIED IDEOGRAPH - 0xFA73: 0x9DD6, //CJK UNIFIED IDEOGRAPH - 0xFA74: 0x9DD7, //CJK UNIFIED IDEOGRAPH - 0xFA75: 0x9DD8, //CJK UNIFIED IDEOGRAPH - 0xFA76: 0x9DD9, //CJK UNIFIED IDEOGRAPH - 0xFA77: 0x9DDA, //CJK UNIFIED IDEOGRAPH - 0xFA78: 0x9DDB, //CJK UNIFIED IDEOGRAPH - 0xFA79: 0x9DDC, //CJK UNIFIED IDEOGRAPH - 0xFA7A: 0x9DDD, //CJK UNIFIED IDEOGRAPH - 0xFA7B: 0x9DDE, //CJK UNIFIED IDEOGRAPH - 0xFA7C: 0x9DDF, //CJK UNIFIED IDEOGRAPH - 0xFA7D: 0x9DE0, //CJK UNIFIED IDEOGRAPH - 0xFA7E: 0x9DE1, //CJK UNIFIED IDEOGRAPH - 0xFA80: 0x9DE2, //CJK UNIFIED IDEOGRAPH - 0xFA81: 0x9DE3, //CJK UNIFIED IDEOGRAPH - 0xFA82: 0x9DE4, //CJK UNIFIED IDEOGRAPH - 0xFA83: 0x9DE5, //CJK UNIFIED IDEOGRAPH - 0xFA84: 0x9DE6, //CJK UNIFIED IDEOGRAPH - 0xFA85: 0x9DE7, //CJK UNIFIED IDEOGRAPH - 0xFA86: 0x9DE8, //CJK UNIFIED IDEOGRAPH - 0xFA87: 0x9DE9, //CJK UNIFIED IDEOGRAPH - 0xFA88: 0x9DEA, //CJK UNIFIED IDEOGRAPH - 0xFA89: 0x9DEB, //CJK UNIFIED IDEOGRAPH - 0xFA8A: 0x9DEC, //CJK UNIFIED IDEOGRAPH - 0xFA8B: 0x9DED, //CJK UNIFIED IDEOGRAPH - 0xFA8C: 0x9DEE, //CJK UNIFIED IDEOGRAPH - 0xFA8D: 0x9DEF, //CJK UNIFIED IDEOGRAPH - 0xFA8E: 0x9DF0, //CJK UNIFIED IDEOGRAPH - 0xFA8F: 0x9DF1, //CJK UNIFIED IDEOGRAPH - 0xFA90: 0x9DF2, //CJK UNIFIED IDEOGRAPH - 0xFA91: 0x9DF3, //CJK UNIFIED IDEOGRAPH - 0xFA92: 0x9DF4, //CJK UNIFIED IDEOGRAPH - 0xFA93: 0x9DF5, //CJK UNIFIED IDEOGRAPH - 0xFA94: 0x9DF6, //CJK UNIFIED IDEOGRAPH - 0xFA95: 0x9DF7, //CJK UNIFIED IDEOGRAPH - 0xFA96: 0x9DF8, //CJK UNIFIED IDEOGRAPH - 0xFA97: 0x9DF9, //CJK UNIFIED IDEOGRAPH - 0xFA98: 0x9DFA, //CJK UNIFIED IDEOGRAPH - 0xFA99: 0x9DFB, //CJK UNIFIED IDEOGRAPH - 0xFA9A: 0x9DFC, //CJK UNIFIED IDEOGRAPH - 0xFA9B: 0x9DFD, //CJK UNIFIED IDEOGRAPH - 0xFA9C: 0x9DFE, //CJK UNIFIED IDEOGRAPH - 0xFA9D: 0x9DFF, //CJK UNIFIED IDEOGRAPH - 0xFA9E: 0x9E00, //CJK UNIFIED IDEOGRAPH - 0xFA9F: 0x9E01, //CJK UNIFIED IDEOGRAPH - 0xFAA0: 0x9E02, //CJK UNIFIED IDEOGRAPH - 0xFB40: 0x9E03, //CJK UNIFIED IDEOGRAPH - 0xFB41: 0x9E04, //CJK UNIFIED IDEOGRAPH - 0xFB42: 0x9E05, //CJK UNIFIED IDEOGRAPH - 0xFB43: 0x9E06, //CJK UNIFIED IDEOGRAPH - 0xFB44: 0x9E07, //CJK UNIFIED IDEOGRAPH - 0xFB45: 0x9E08, //CJK UNIFIED IDEOGRAPH - 0xFB46: 0x9E09, //CJK UNIFIED IDEOGRAPH - 0xFB47: 0x9E0A, //CJK UNIFIED IDEOGRAPH - 0xFB48: 0x9E0B, //CJK UNIFIED IDEOGRAPH - 0xFB49: 0x9E0C, //CJK UNIFIED IDEOGRAPH - 0xFB4A: 0x9E0D, //CJK UNIFIED IDEOGRAPH - 0xFB4B: 0x9E0E, //CJK UNIFIED IDEOGRAPH - 0xFB4C: 0x9E0F, //CJK UNIFIED IDEOGRAPH - 0xFB4D: 0x9E10, //CJK UNIFIED IDEOGRAPH - 0xFB4E: 0x9E11, //CJK UNIFIED IDEOGRAPH - 0xFB4F: 0x9E12, //CJK UNIFIED IDEOGRAPH - 0xFB50: 0x9E13, //CJK UNIFIED IDEOGRAPH - 0xFB51: 0x9E14, //CJK UNIFIED IDEOGRAPH - 0xFB52: 0x9E15, //CJK UNIFIED IDEOGRAPH - 0xFB53: 0x9E16, //CJK UNIFIED IDEOGRAPH - 0xFB54: 0x9E17, //CJK UNIFIED IDEOGRAPH - 0xFB55: 0x9E18, //CJK UNIFIED IDEOGRAPH - 0xFB56: 0x9E19, //CJK UNIFIED IDEOGRAPH - 0xFB57: 0x9E1A, //CJK UNIFIED IDEOGRAPH - 0xFB58: 0x9E1B, //CJK UNIFIED IDEOGRAPH - 0xFB59: 0x9E1C, //CJK UNIFIED IDEOGRAPH - 0xFB5A: 0x9E1D, //CJK UNIFIED IDEOGRAPH - 0xFB5B: 0x9E1E, //CJK UNIFIED IDEOGRAPH - 0xFB5C: 0x9E24, //CJK UNIFIED IDEOGRAPH - 0xFB5D: 0x9E27, //CJK UNIFIED IDEOGRAPH - 0xFB5E: 0x9E2E, //CJK UNIFIED IDEOGRAPH - 0xFB5F: 0x9E30, //CJK UNIFIED IDEOGRAPH - 0xFB60: 0x9E34, //CJK UNIFIED IDEOGRAPH - 0xFB61: 0x9E3B, //CJK UNIFIED IDEOGRAPH - 0xFB62: 0x9E3C, //CJK UNIFIED IDEOGRAPH - 0xFB63: 0x9E40, //CJK UNIFIED IDEOGRAPH - 0xFB64: 0x9E4D, //CJK UNIFIED IDEOGRAPH - 0xFB65: 0x9E50, //CJK UNIFIED IDEOGRAPH - 0xFB66: 0x9E52, //CJK UNIFIED IDEOGRAPH - 0xFB67: 0x9E53, //CJK UNIFIED IDEOGRAPH - 0xFB68: 0x9E54, //CJK UNIFIED IDEOGRAPH - 0xFB69: 0x9E56, //CJK UNIFIED IDEOGRAPH - 0xFB6A: 0x9E59, //CJK UNIFIED IDEOGRAPH - 0xFB6B: 0x9E5D, //CJK UNIFIED IDEOGRAPH - 0xFB6C: 0x9E5F, //CJK UNIFIED IDEOGRAPH - 0xFB6D: 0x9E60, //CJK UNIFIED IDEOGRAPH - 0xFB6E: 0x9E61, //CJK UNIFIED IDEOGRAPH - 0xFB6F: 0x9E62, //CJK UNIFIED IDEOGRAPH - 0xFB70: 0x9E65, //CJK UNIFIED IDEOGRAPH - 0xFB71: 0x9E6E, //CJK UNIFIED IDEOGRAPH - 0xFB72: 0x9E6F, //CJK UNIFIED IDEOGRAPH - 0xFB73: 0x9E72, //CJK UNIFIED IDEOGRAPH - 0xFB74: 0x9E74, //CJK UNIFIED IDEOGRAPH - 0xFB75: 0x9E75, //CJK UNIFIED IDEOGRAPH - 0xFB76: 0x9E76, //CJK UNIFIED IDEOGRAPH - 0xFB77: 0x9E77, //CJK UNIFIED IDEOGRAPH - 0xFB78: 0x9E78, //CJK UNIFIED IDEOGRAPH - 0xFB79: 0x9E79, //CJK UNIFIED IDEOGRAPH - 0xFB7A: 0x9E7A, //CJK UNIFIED IDEOGRAPH - 0xFB7B: 0x9E7B, //CJK UNIFIED IDEOGRAPH - 0xFB7C: 0x9E7C, //CJK UNIFIED IDEOGRAPH - 0xFB7D: 0x9E7D, //CJK UNIFIED IDEOGRAPH - 0xFB7E: 0x9E80, //CJK UNIFIED IDEOGRAPH - 0xFB80: 0x9E81, //CJK UNIFIED IDEOGRAPH - 0xFB81: 0x9E83, //CJK UNIFIED IDEOGRAPH - 0xFB82: 0x9E84, //CJK UNIFIED IDEOGRAPH - 0xFB83: 0x9E85, //CJK UNIFIED IDEOGRAPH - 0xFB84: 0x9E86, //CJK UNIFIED IDEOGRAPH - 0xFB85: 0x9E89, //CJK UNIFIED IDEOGRAPH - 0xFB86: 0x9E8A, //CJK UNIFIED IDEOGRAPH - 0xFB87: 0x9E8C, //CJK UNIFIED IDEOGRAPH - 0xFB88: 0x9E8D, //CJK UNIFIED IDEOGRAPH - 0xFB89: 0x9E8E, //CJK UNIFIED IDEOGRAPH - 0xFB8A: 0x9E8F, //CJK UNIFIED IDEOGRAPH - 0xFB8B: 0x9E90, //CJK UNIFIED IDEOGRAPH - 0xFB8C: 0x9E91, //CJK UNIFIED IDEOGRAPH - 0xFB8D: 0x9E94, //CJK UNIFIED IDEOGRAPH - 0xFB8E: 0x9E95, //CJK UNIFIED IDEOGRAPH - 0xFB8F: 0x9E96, //CJK UNIFIED IDEOGRAPH - 0xFB90: 0x9E97, //CJK UNIFIED IDEOGRAPH - 0xFB91: 0x9E98, //CJK UNIFIED IDEOGRAPH - 0xFB92: 0x9E99, //CJK UNIFIED IDEOGRAPH - 0xFB93: 0x9E9A, //CJK UNIFIED IDEOGRAPH - 0xFB94: 0x9E9B, //CJK UNIFIED IDEOGRAPH - 0xFB95: 0x9E9C, //CJK UNIFIED IDEOGRAPH - 0xFB96: 0x9E9E, //CJK UNIFIED IDEOGRAPH - 0xFB97: 0x9EA0, //CJK UNIFIED IDEOGRAPH - 0xFB98: 0x9EA1, //CJK UNIFIED IDEOGRAPH - 0xFB99: 0x9EA2, //CJK UNIFIED IDEOGRAPH - 0xFB9A: 0x9EA3, //CJK UNIFIED IDEOGRAPH - 0xFB9B: 0x9EA4, //CJK UNIFIED IDEOGRAPH - 0xFB9C: 0x9EA5, //CJK UNIFIED IDEOGRAPH - 0xFB9D: 0x9EA7, //CJK UNIFIED IDEOGRAPH - 0xFB9E: 0x9EA8, //CJK UNIFIED IDEOGRAPH - 0xFB9F: 0x9EA9, //CJK UNIFIED IDEOGRAPH - 0xFBA0: 0x9EAA, //CJK UNIFIED IDEOGRAPH - 0xFC40: 0x9EAB, //CJK UNIFIED IDEOGRAPH - 0xFC41: 0x9EAC, //CJK UNIFIED IDEOGRAPH - 0xFC42: 0x9EAD, //CJK UNIFIED IDEOGRAPH - 0xFC43: 0x9EAE, //CJK UNIFIED IDEOGRAPH - 0xFC44: 0x9EAF, //CJK UNIFIED IDEOGRAPH - 0xFC45: 0x9EB0, //CJK UNIFIED IDEOGRAPH - 0xFC46: 0x9EB1, //CJK UNIFIED IDEOGRAPH - 0xFC47: 0x9EB2, //CJK UNIFIED IDEOGRAPH - 0xFC48: 0x9EB3, //CJK UNIFIED IDEOGRAPH - 0xFC49: 0x9EB5, //CJK UNIFIED IDEOGRAPH - 0xFC4A: 0x9EB6, //CJK UNIFIED IDEOGRAPH - 0xFC4B: 0x9EB7, //CJK UNIFIED IDEOGRAPH - 0xFC4C: 0x9EB9, //CJK UNIFIED IDEOGRAPH - 0xFC4D: 0x9EBA, //CJK UNIFIED IDEOGRAPH - 0xFC4E: 0x9EBC, //CJK UNIFIED IDEOGRAPH - 0xFC4F: 0x9EBF, //CJK UNIFIED IDEOGRAPH - 0xFC50: 0x9EC0, //CJK UNIFIED IDEOGRAPH - 0xFC51: 0x9EC1, //CJK UNIFIED IDEOGRAPH - 0xFC52: 0x9EC2, //CJK UNIFIED IDEOGRAPH - 0xFC53: 0x9EC3, //CJK UNIFIED IDEOGRAPH - 0xFC54: 0x9EC5, //CJK UNIFIED IDEOGRAPH - 0xFC55: 0x9EC6, //CJK UNIFIED IDEOGRAPH - 0xFC56: 0x9EC7, //CJK UNIFIED IDEOGRAPH - 0xFC57: 0x9EC8, //CJK UNIFIED IDEOGRAPH - 0xFC58: 0x9ECA, //CJK UNIFIED IDEOGRAPH - 0xFC59: 0x9ECB, //CJK UNIFIED IDEOGRAPH - 0xFC5A: 0x9ECC, //CJK UNIFIED IDEOGRAPH - 0xFC5B: 0x9ED0, //CJK UNIFIED IDEOGRAPH - 0xFC5C: 0x9ED2, //CJK UNIFIED IDEOGRAPH - 0xFC5D: 0x9ED3, //CJK UNIFIED IDEOGRAPH - 0xFC5E: 0x9ED5, //CJK UNIFIED IDEOGRAPH - 0xFC5F: 0x9ED6, //CJK UNIFIED IDEOGRAPH - 0xFC60: 0x9ED7, //CJK UNIFIED IDEOGRAPH - 0xFC61: 0x9ED9, //CJK UNIFIED IDEOGRAPH - 0xFC62: 0x9EDA, //CJK UNIFIED IDEOGRAPH - 0xFC63: 0x9EDE, //CJK UNIFIED IDEOGRAPH - 0xFC64: 0x9EE1, //CJK UNIFIED IDEOGRAPH - 0xFC65: 0x9EE3, //CJK UNIFIED IDEOGRAPH - 0xFC66: 0x9EE4, //CJK UNIFIED IDEOGRAPH - 0xFC67: 0x9EE6, //CJK UNIFIED IDEOGRAPH - 0xFC68: 0x9EE8, //CJK UNIFIED IDEOGRAPH - 0xFC69: 0x9EEB, //CJK UNIFIED IDEOGRAPH - 0xFC6A: 0x9EEC, //CJK UNIFIED IDEOGRAPH - 0xFC6B: 0x9EED, //CJK UNIFIED IDEOGRAPH - 0xFC6C: 0x9EEE, //CJK UNIFIED IDEOGRAPH - 0xFC6D: 0x9EF0, //CJK UNIFIED IDEOGRAPH - 0xFC6E: 0x9EF1, //CJK UNIFIED IDEOGRAPH - 0xFC6F: 0x9EF2, //CJK UNIFIED IDEOGRAPH - 0xFC70: 0x9EF3, //CJK UNIFIED IDEOGRAPH - 0xFC71: 0x9EF4, //CJK UNIFIED IDEOGRAPH - 0xFC72: 0x9EF5, //CJK UNIFIED IDEOGRAPH - 0xFC73: 0x9EF6, //CJK UNIFIED IDEOGRAPH - 0xFC74: 0x9EF7, //CJK UNIFIED IDEOGRAPH - 0xFC75: 0x9EF8, //CJK UNIFIED IDEOGRAPH - 0xFC76: 0x9EFA, //CJK UNIFIED IDEOGRAPH - 0xFC77: 0x9EFD, //CJK UNIFIED IDEOGRAPH - 0xFC78: 0x9EFF, //CJK UNIFIED IDEOGRAPH - 0xFC79: 0x9F00, //CJK UNIFIED IDEOGRAPH - 0xFC7A: 0x9F01, //CJK UNIFIED IDEOGRAPH - 0xFC7B: 0x9F02, //CJK UNIFIED IDEOGRAPH - 0xFC7C: 0x9F03, //CJK UNIFIED IDEOGRAPH - 0xFC7D: 0x9F04, //CJK UNIFIED IDEOGRAPH - 0xFC7E: 0x9F05, //CJK UNIFIED IDEOGRAPH - 0xFC80: 0x9F06, //CJK UNIFIED IDEOGRAPH - 0xFC81: 0x9F07, //CJK UNIFIED IDEOGRAPH - 0xFC82: 0x9F08, //CJK UNIFIED IDEOGRAPH - 0xFC83: 0x9F09, //CJK UNIFIED IDEOGRAPH - 0xFC84: 0x9F0A, //CJK UNIFIED IDEOGRAPH - 0xFC85: 0x9F0C, //CJK UNIFIED IDEOGRAPH - 0xFC86: 0x9F0F, //CJK UNIFIED IDEOGRAPH - 0xFC87: 0x9F11, //CJK UNIFIED IDEOGRAPH - 0xFC88: 0x9F12, //CJK UNIFIED IDEOGRAPH - 0xFC89: 0x9F14, //CJK UNIFIED IDEOGRAPH - 0xFC8A: 0x9F15, //CJK UNIFIED IDEOGRAPH - 0xFC8B: 0x9F16, //CJK UNIFIED IDEOGRAPH - 0xFC8C: 0x9F18, //CJK UNIFIED IDEOGRAPH - 0xFC8D: 0x9F1A, //CJK UNIFIED IDEOGRAPH - 0xFC8E: 0x9F1B, //CJK UNIFIED IDEOGRAPH - 0xFC8F: 0x9F1C, //CJK UNIFIED IDEOGRAPH - 0xFC90: 0x9F1D, //CJK UNIFIED IDEOGRAPH - 0xFC91: 0x9F1E, //CJK UNIFIED IDEOGRAPH - 0xFC92: 0x9F1F, //CJK UNIFIED IDEOGRAPH - 0xFC93: 0x9F21, //CJK UNIFIED IDEOGRAPH - 0xFC94: 0x9F23, //CJK UNIFIED IDEOGRAPH - 0xFC95: 0x9F24, //CJK UNIFIED IDEOGRAPH - 0xFC96: 0x9F25, //CJK UNIFIED IDEOGRAPH - 0xFC97: 0x9F26, //CJK UNIFIED IDEOGRAPH - 0xFC98: 0x9F27, //CJK UNIFIED IDEOGRAPH - 0xFC99: 0x9F28, //CJK UNIFIED IDEOGRAPH - 0xFC9A: 0x9F29, //CJK UNIFIED IDEOGRAPH - 0xFC9B: 0x9F2A, //CJK UNIFIED IDEOGRAPH - 0xFC9C: 0x9F2B, //CJK UNIFIED IDEOGRAPH - 0xFC9D: 0x9F2D, //CJK UNIFIED IDEOGRAPH - 0xFC9E: 0x9F2E, //CJK UNIFIED IDEOGRAPH - 0xFC9F: 0x9F30, //CJK UNIFIED IDEOGRAPH - 0xFCA0: 0x9F31, //CJK UNIFIED IDEOGRAPH - 0xFD40: 0x9F32, //CJK UNIFIED IDEOGRAPH - 0xFD41: 0x9F33, //CJK UNIFIED IDEOGRAPH - 0xFD42: 0x9F34, //CJK UNIFIED IDEOGRAPH - 0xFD43: 0x9F35, //CJK UNIFIED IDEOGRAPH - 0xFD44: 0x9F36, //CJK UNIFIED IDEOGRAPH - 0xFD45: 0x9F38, //CJK UNIFIED IDEOGRAPH - 0xFD46: 0x9F3A, //CJK UNIFIED IDEOGRAPH - 0xFD47: 0x9F3C, //CJK UNIFIED IDEOGRAPH - 0xFD48: 0x9F3F, //CJK UNIFIED IDEOGRAPH - 0xFD49: 0x9F40, //CJK UNIFIED IDEOGRAPH - 0xFD4A: 0x9F41, //CJK UNIFIED IDEOGRAPH - 0xFD4B: 0x9F42, //CJK UNIFIED IDEOGRAPH - 0xFD4C: 0x9F43, //CJK UNIFIED IDEOGRAPH - 0xFD4D: 0x9F45, //CJK UNIFIED IDEOGRAPH - 0xFD4E: 0x9F46, //CJK UNIFIED IDEOGRAPH - 0xFD4F: 0x9F47, //CJK UNIFIED IDEOGRAPH - 0xFD50: 0x9F48, //CJK UNIFIED IDEOGRAPH - 0xFD51: 0x9F49, //CJK UNIFIED IDEOGRAPH - 0xFD52: 0x9F4A, //CJK UNIFIED IDEOGRAPH - 0xFD53: 0x9F4B, //CJK UNIFIED IDEOGRAPH - 0xFD54: 0x9F4C, //CJK UNIFIED IDEOGRAPH - 0xFD55: 0x9F4D, //CJK UNIFIED IDEOGRAPH - 0xFD56: 0x9F4E, //CJK UNIFIED IDEOGRAPH - 0xFD57: 0x9F4F, //CJK UNIFIED IDEOGRAPH - 0xFD58: 0x9F52, //CJK UNIFIED IDEOGRAPH - 0xFD59: 0x9F53, //CJK UNIFIED IDEOGRAPH - 0xFD5A: 0x9F54, //CJK UNIFIED IDEOGRAPH - 0xFD5B: 0x9F55, //CJK UNIFIED IDEOGRAPH - 0xFD5C: 0x9F56, //CJK UNIFIED IDEOGRAPH - 0xFD5D: 0x9F57, //CJK UNIFIED IDEOGRAPH - 0xFD5E: 0x9F58, //CJK UNIFIED IDEOGRAPH - 0xFD5F: 0x9F59, //CJK UNIFIED IDEOGRAPH - 0xFD60: 0x9F5A, //CJK UNIFIED IDEOGRAPH - 0xFD61: 0x9F5B, //CJK UNIFIED IDEOGRAPH - 0xFD62: 0x9F5C, //CJK UNIFIED IDEOGRAPH - 0xFD63: 0x9F5D, //CJK UNIFIED IDEOGRAPH - 0xFD64: 0x9F5E, //CJK UNIFIED IDEOGRAPH - 0xFD65: 0x9F5F, //CJK UNIFIED IDEOGRAPH - 0xFD66: 0x9F60, //CJK UNIFIED IDEOGRAPH - 0xFD67: 0x9F61, //CJK UNIFIED IDEOGRAPH - 0xFD68: 0x9F62, //CJK UNIFIED IDEOGRAPH - 0xFD69: 0x9F63, //CJK UNIFIED IDEOGRAPH - 0xFD6A: 0x9F64, //CJK UNIFIED IDEOGRAPH - 0xFD6B: 0x9F65, //CJK UNIFIED IDEOGRAPH - 0xFD6C: 0x9F66, //CJK UNIFIED IDEOGRAPH - 0xFD6D: 0x9F67, //CJK UNIFIED IDEOGRAPH - 0xFD6E: 0x9F68, //CJK UNIFIED IDEOGRAPH - 0xFD6F: 0x9F69, //CJK UNIFIED IDEOGRAPH - 0xFD70: 0x9F6A, //CJK UNIFIED IDEOGRAPH - 0xFD71: 0x9F6B, //CJK UNIFIED IDEOGRAPH - 0xFD72: 0x9F6C, //CJK UNIFIED IDEOGRAPH - 0xFD73: 0x9F6D, //CJK UNIFIED IDEOGRAPH - 0xFD74: 0x9F6E, //CJK UNIFIED IDEOGRAPH - 0xFD75: 0x9F6F, //CJK UNIFIED IDEOGRAPH - 0xFD76: 0x9F70, //CJK UNIFIED IDEOGRAPH - 0xFD77: 0x9F71, //CJK UNIFIED IDEOGRAPH - 0xFD78: 0x9F72, //CJK UNIFIED IDEOGRAPH - 0xFD79: 0x9F73, //CJK UNIFIED IDEOGRAPH - 0xFD7A: 0x9F74, //CJK UNIFIED IDEOGRAPH - 0xFD7B: 0x9F75, //CJK UNIFIED IDEOGRAPH - 0xFD7C: 0x9F76, //CJK UNIFIED IDEOGRAPH - 0xFD7D: 0x9F77, //CJK UNIFIED IDEOGRAPH - 0xFD7E: 0x9F78, //CJK UNIFIED IDEOGRAPH - 0xFD80: 0x9F79, //CJK UNIFIED IDEOGRAPH - 0xFD81: 0x9F7A, //CJK UNIFIED IDEOGRAPH - 0xFD82: 0x9F7B, //CJK UNIFIED IDEOGRAPH - 0xFD83: 0x9F7C, //CJK UNIFIED IDEOGRAPH - 0xFD84: 0x9F7D, //CJK UNIFIED IDEOGRAPH - 0xFD85: 0x9F7E, //CJK UNIFIED IDEOGRAPH - 0xFD86: 0x9F81, //CJK UNIFIED IDEOGRAPH - 0xFD87: 0x9F82, //CJK UNIFIED IDEOGRAPH - 0xFD88: 0x9F8D, //CJK UNIFIED IDEOGRAPH - 0xFD89: 0x9F8E, //CJK UNIFIED IDEOGRAPH - 0xFD8A: 0x9F8F, //CJK UNIFIED IDEOGRAPH - 0xFD8B: 0x9F90, //CJK UNIFIED IDEOGRAPH - 0xFD8C: 0x9F91, //CJK UNIFIED IDEOGRAPH - 0xFD8D: 0x9F92, //CJK UNIFIED IDEOGRAPH - 0xFD8E: 0x9F93, //CJK UNIFIED IDEOGRAPH - 0xFD8F: 0x9F94, //CJK UNIFIED IDEOGRAPH - 0xFD90: 0x9F95, //CJK UNIFIED IDEOGRAPH - 0xFD91: 0x9F96, //CJK UNIFIED IDEOGRAPH - 0xFD92: 0x9F97, //CJK UNIFIED IDEOGRAPH - 0xFD93: 0x9F98, //CJK UNIFIED IDEOGRAPH - 0xFD94: 0x9F9C, //CJK UNIFIED IDEOGRAPH - 0xFD95: 0x9F9D, //CJK UNIFIED IDEOGRAPH - 0xFD96: 0x9F9E, //CJK UNIFIED IDEOGRAPH - 0xFD97: 0x9FA1, //CJK UNIFIED IDEOGRAPH - 0xFD98: 0x9FA2, //CJK UNIFIED IDEOGRAPH - 0xFD99: 0x9FA3, //CJK UNIFIED IDEOGRAPH - 0xFD9A: 0x9FA4, //CJK UNIFIED IDEOGRAPH - 0xFD9B: 0x9FA5, //CJK UNIFIED IDEOGRAPH - 0xFD9C: 0xF92C, //CJK COMPATIBILITY IDEOGRAPH - 0xFD9D: 0xF979, //CJK COMPATIBILITY IDEOGRAPH - 0xFD9E: 0xF995, //CJK COMPATIBILITY IDEOGRAPH - 0xFD9F: 0xF9E7, //CJK COMPATIBILITY IDEOGRAPH - 0xFDA0: 0xF9F1, //CJK COMPATIBILITY IDEOGRAPH - 0xFE40: 0xFA0C, //CJK COMPATIBILITY IDEOGRAPH - 0xFE41: 0xFA0D, //CJK COMPATIBILITY IDEOGRAPH - 0xFE42: 0xFA0E, //CJK COMPATIBILITY IDEOGRAPH - 0xFE43: 0xFA0F, //CJK COMPATIBILITY IDEOGRAPH - 0xFE44: 0xFA11, //CJK COMPATIBILITY IDEOGRAPH - 0xFE45: 0xFA13, //CJK COMPATIBILITY IDEOGRAPH - 0xFE46: 0xFA14, //CJK COMPATIBILITY IDEOGRAPH - 0xFE47: 0xFA18, //CJK COMPATIBILITY IDEOGRAPH - 0xFE48: 0xFA1F, //CJK COMPATIBILITY IDEOGRAPH - 0xFE49: 0xFA20, //CJK COMPATIBILITY IDEOGRAPH - 0xFE4A: 0xFA21, //CJK COMPATIBILITY IDEOGRAPH - 0xFE4B: 0xFA23, //CJK COMPATIBILITY IDEOGRAPH - 0xFE4C: 0xFA24, //CJK COMPATIBILITY IDEOGRAPH - 0xFE4D: 0xFA27, //CJK COMPATIBILITY IDEOGRAPH - 0xFE4E: 0xFA28, //CJK COMPATIBILITY IDEOGRAPH - 0xFE4F: 0xFA29, //CJK COMPATIBILITY IDEOGRAPH - }, -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/cp949.go b/vendor/github.com/denisenkom/go-mssqldb/cp949.go deleted file mode 100644 index cddfcbc85..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/cp949.go +++ /dev/null @@ -1,17312 +0,0 @@ -package mssql - -var cp949 *charsetMap = &charsetMap{ - sb: [256]rune{ - 0x0000, //NULL - 0x0001, //START OF HEADING - 0x0002, //START OF TEXT - 0x0003, //END OF TEXT - 0x0004, //END OF TRANSMISSION - 0x0005, //ENQUIRY - 0x0006, //ACKNOWLEDGE - 0x0007, //BELL - 0x0008, //BACKSPACE - 0x0009, //HORIZONTAL TABULATION - 0x000A, //LINE FEED - 0x000B, //VERTICAL TABULATION - 0x000C, //FORM FEED - 0x000D, //CARRIAGE RETURN - 0x000E, //SHIFT OUT - 0x000F, //SHIFT IN - 0x0010, //DATA LINK ESCAPE - 0x0011, //DEVICE CONTROL ONE - 0x0012, //DEVICE CONTROL TWO - 0x0013, //DEVICE CONTROL THREE - 0x0014, //DEVICE CONTROL FOUR - 0x0015, //NEGATIVE ACKNOWLEDGE - 0x0016, //SYNCHRONOUS IDLE - 0x0017, //END OF TRANSMISSION BLOCK - 0x0018, //CANCEL - 0x0019, //END OF MEDIUM - 0x001A, //SUBSTITUTE - 0x001B, //ESCAPE - 0x001C, //FILE SEPARATOR - 0x001D, //GROUP SEPARATOR - 0x001E, //RECORD SEPARATOR - 0x001F, //UNIT SEPARATOR - 0x0020, //SPACE - 0x0021, //EXCLAMATION MARK - 0x0022, //QUOTATION MARK - 0x0023, //NUMBER SIGN - 0x0024, //DOLLAR SIGN - 0x0025, //PERCENT SIGN - 0x0026, //AMPERSAND - 0x0027, //APOSTROPHE - 0x0028, //LEFT PARENTHESIS - 0x0029, //RIGHT PARENTHESIS - 0x002A, //ASTERISK - 0x002B, //PLUS SIGN - 0x002C, //COMMA - 0x002D, //HYPHEN-MINUS - 0x002E, //FULL STOP - 0x002F, //SOLIDUS - 0x0030, //DIGIT ZERO - 0x0031, //DIGIT ONE - 0x0032, //DIGIT TWO - 0x0033, //DIGIT THREE - 0x0034, //DIGIT FOUR - 0x0035, //DIGIT FIVE - 0x0036, //DIGIT SIX - 0x0037, //DIGIT SEVEN - 0x0038, //DIGIT EIGHT - 0x0039, //DIGIT NINE - 0x003A, //COLON - 0x003B, //SEMICOLON - 0x003C, //LESS-THAN SIGN - 0x003D, //EQUALS SIGN - 0x003E, //GREATER-THAN SIGN - 0x003F, //QUESTION MARK - 0x0040, //COMMERCIAL AT - 0x0041, //LATIN CAPITAL LETTER A - 0x0042, //LATIN CAPITAL LETTER B - 0x0043, //LATIN CAPITAL LETTER C - 0x0044, //LATIN CAPITAL LETTER D - 0x0045, //LATIN CAPITAL LETTER E - 0x0046, //LATIN CAPITAL LETTER F - 0x0047, //LATIN CAPITAL LETTER G - 0x0048, //LATIN CAPITAL LETTER H - 0x0049, //LATIN CAPITAL LETTER I - 0x004A, //LATIN CAPITAL LETTER J - 0x004B, //LATIN CAPITAL LETTER K - 0x004C, //LATIN CAPITAL LETTER L - 0x004D, //LATIN CAPITAL LETTER M - 0x004E, //LATIN CAPITAL LETTER N - 0x004F, //LATIN CAPITAL LETTER O - 0x0050, //LATIN CAPITAL LETTER P - 0x0051, //LATIN CAPITAL LETTER Q - 0x0052, //LATIN CAPITAL LETTER R - 0x0053, //LATIN CAPITAL LETTER S - 0x0054, //LATIN CAPITAL LETTER T - 0x0055, //LATIN CAPITAL LETTER U - 0x0056, //LATIN CAPITAL LETTER V - 0x0057, //LATIN CAPITAL LETTER W - 0x0058, //LATIN CAPITAL LETTER X - 0x0059, //LATIN CAPITAL LETTER Y - 0x005A, //LATIN CAPITAL LETTER Z - 0x005B, //LEFT SQUARE BRACKET - 0x005C, //REVERSE SOLIDUS - 0x005D, //RIGHT SQUARE BRACKET - 0x005E, //CIRCUMFLEX ACCENT - 0x005F, //LOW LINE - 0x0060, //GRAVE ACCENT - 0x0061, //LATIN SMALL LETTER A - 0x0062, //LATIN SMALL LETTER B - 0x0063, //LATIN SMALL LETTER C - 0x0064, //LATIN SMALL LETTER D - 0x0065, //LATIN SMALL LETTER E - 0x0066, //LATIN SMALL LETTER F - 0x0067, //LATIN SMALL LETTER G - 0x0068, //LATIN SMALL LETTER H - 0x0069, //LATIN SMALL LETTER I - 0x006A, //LATIN SMALL LETTER J - 0x006B, //LATIN SMALL LETTER K - 0x006C, //LATIN SMALL LETTER L - 0x006D, //LATIN SMALL LETTER M - 0x006E, //LATIN SMALL LETTER N - 0x006F, //LATIN SMALL LETTER O - 0x0070, //LATIN SMALL LETTER P - 0x0071, //LATIN SMALL LETTER Q - 0x0072, //LATIN SMALL LETTER R - 0x0073, //LATIN SMALL LETTER S - 0x0074, //LATIN SMALL LETTER T - 0x0075, //LATIN SMALL LETTER U - 0x0076, //LATIN SMALL LETTER V - 0x0077, //LATIN SMALL LETTER W - 0x0078, //LATIN SMALL LETTER X - 0x0079, //LATIN SMALL LETTER Y - 0x007A, //LATIN SMALL LETTER Z - 0x007B, //LEFT CURLY BRACKET - 0x007C, //VERTICAL LINE - 0x007D, //RIGHT CURLY BRACKET - 0x007E, //TILDE - 0x007F, //DELETE - 0xFFFD, //UNDEFINED - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - 0xFFFD, //UNDEFINED - }, - db: map[int]rune{ - 0x8141: 0xAC02, //HANGUL SYLLABLE KIYEOK A SSANGKIYEOK - 0x8142: 0xAC03, //HANGUL SYLLABLE KIYEOK A KIYEOKSIOS - 0x8143: 0xAC05, //HANGUL SYLLABLE KIYEOK A NIEUNCIEUC - 0x8144: 0xAC06, //HANGUL SYLLABLE KIYEOK A NIEUNHIEUH - 0x8145: 0xAC0B, //HANGUL SYLLABLE KIYEOK A RIEULPIEUP - 0x8146: 0xAC0C, //HANGUL SYLLABLE KIYEOK A RIEULSIOS - 0x8147: 0xAC0D, //HANGUL SYLLABLE KIYEOK A RIEULTHIEUTH - 0x8148: 0xAC0E, //HANGUL SYLLABLE KIYEOK A RIEULPHIEUPH - 0x8149: 0xAC0F, //HANGUL SYLLABLE KIYEOK A RIEULHIEUH - 0x814A: 0xAC18, //HANGUL SYLLABLE KIYEOK A KHIEUKH - 0x814B: 0xAC1E, //HANGUL SYLLABLE KIYEOK AE SSANGKIYEOK - 0x814C: 0xAC1F, //HANGUL SYLLABLE KIYEOK AE KIYEOKSIOS - 0x814D: 0xAC21, //HANGUL SYLLABLE KIYEOK AE NIEUNCIEUC - 0x814E: 0xAC22, //HANGUL SYLLABLE KIYEOK AE NIEUNHIEUH - 0x814F: 0xAC23, //HANGUL SYLLABLE KIYEOK AE TIKEUT - 0x8150: 0xAC25, //HANGUL SYLLABLE KIYEOK AE RIEULKIYEOK - 0x8151: 0xAC26, //HANGUL SYLLABLE KIYEOK AE RIEULMIEUM - 0x8152: 0xAC27, //HANGUL SYLLABLE KIYEOK AE RIEULPIEUP - 0x8153: 0xAC28, //HANGUL SYLLABLE KIYEOK AE RIEULSIOS - 0x8154: 0xAC29, //HANGUL SYLLABLE KIYEOK AE RIEULTHIEUTH - 0x8155: 0xAC2A, //HANGUL SYLLABLE KIYEOK AE RIEULPHIEUPH - 0x8156: 0xAC2B, //HANGUL SYLLABLE KIYEOK AE RIEULHIEUH - 0x8157: 0xAC2E, //HANGUL SYLLABLE KIYEOK AE PIEUPSIOS - 0x8158: 0xAC32, //HANGUL SYLLABLE KIYEOK AE CIEUC - 0x8159: 0xAC33, //HANGUL SYLLABLE KIYEOK AE CHIEUCH - 0x815A: 0xAC34, //HANGUL SYLLABLE KIYEOK AE KHIEUKH - 0x8161: 0xAC35, //HANGUL SYLLABLE KIYEOK AE THIEUTH - 0x8162: 0xAC36, //HANGUL SYLLABLE KIYEOK AE PHIEUPH - 0x8163: 0xAC37, //HANGUL SYLLABLE KIYEOK AE HIEUH - 0x8164: 0xAC3A, //HANGUL SYLLABLE KIYEOK YA SSANGKIYEOK - 0x8165: 0xAC3B, //HANGUL SYLLABLE KIYEOK YA KIYEOKSIOS - 0x8166: 0xAC3D, //HANGUL SYLLABLE KIYEOK YA NIEUNCIEUC - 0x8167: 0xAC3E, //HANGUL SYLLABLE KIYEOK YA NIEUNHIEUH - 0x8168: 0xAC3F, //HANGUL SYLLABLE KIYEOK YA TIKEUT - 0x8169: 0xAC41, //HANGUL SYLLABLE KIYEOK YA RIEULKIYEOK - 0x816A: 0xAC42, //HANGUL SYLLABLE KIYEOK YA RIEULMIEUM - 0x816B: 0xAC43, //HANGUL SYLLABLE KIYEOK YA RIEULPIEUP - 0x816C: 0xAC44, //HANGUL SYLLABLE KIYEOK YA RIEULSIOS - 0x816D: 0xAC45, //HANGUL SYLLABLE KIYEOK YA RIEULTHIEUTH - 0x816E: 0xAC46, //HANGUL SYLLABLE KIYEOK YA RIEULPHIEUPH - 0x816F: 0xAC47, //HANGUL SYLLABLE KIYEOK YA RIEULHIEUH - 0x8170: 0xAC48, //HANGUL SYLLABLE KIYEOK YA MIEUM - 0x8171: 0xAC49, //HANGUL SYLLABLE KIYEOK YA PIEUP - 0x8172: 0xAC4A, //HANGUL SYLLABLE KIYEOK YA PIEUPSIOS - 0x8173: 0xAC4C, //HANGUL SYLLABLE KIYEOK YA SSANGSIOS - 0x8174: 0xAC4E, //HANGUL SYLLABLE KIYEOK YA CIEUC - 0x8175: 0xAC4F, //HANGUL SYLLABLE KIYEOK YA CHIEUCH - 0x8176: 0xAC50, //HANGUL SYLLABLE KIYEOK YA KHIEUKH - 0x8177: 0xAC51, //HANGUL SYLLABLE KIYEOK YA THIEUTH - 0x8178: 0xAC52, //HANGUL SYLLABLE KIYEOK YA PHIEUPH - 0x8179: 0xAC53, //HANGUL SYLLABLE KIYEOK YA HIEUH - 0x817A: 0xAC55, //HANGUL SYLLABLE KIYEOK YAE KIYEOK - 0x8181: 0xAC56, //HANGUL SYLLABLE KIYEOK YAE SSANGKIYEOK - 0x8182: 0xAC57, //HANGUL SYLLABLE KIYEOK YAE KIYEOKSIOS - 0x8183: 0xAC59, //HANGUL SYLLABLE KIYEOK YAE NIEUNCIEUC - 0x8184: 0xAC5A, //HANGUL SYLLABLE KIYEOK YAE NIEUNHIEUH - 0x8185: 0xAC5B, //HANGUL SYLLABLE KIYEOK YAE TIKEUT - 0x8186: 0xAC5D, //HANGUL SYLLABLE KIYEOK YAE RIEULKIYEOK - 0x8187: 0xAC5E, //HANGUL SYLLABLE KIYEOK YAE RIEULMIEUM - 0x8188: 0xAC5F, //HANGUL SYLLABLE KIYEOK YAE RIEULPIEUP - 0x8189: 0xAC60, //HANGUL SYLLABLE KIYEOK YAE RIEULSIOS - 0x818A: 0xAC61, //HANGUL SYLLABLE KIYEOK YAE RIEULTHIEUTH - 0x818B: 0xAC62, //HANGUL SYLLABLE KIYEOK YAE RIEULPHIEUPH - 0x818C: 0xAC63, //HANGUL SYLLABLE KIYEOK YAE RIEULHIEUH - 0x818D: 0xAC64, //HANGUL SYLLABLE KIYEOK YAE MIEUM - 0x818E: 0xAC65, //HANGUL SYLLABLE KIYEOK YAE PIEUP - 0x818F: 0xAC66, //HANGUL SYLLABLE KIYEOK YAE PIEUPSIOS - 0x8190: 0xAC67, //HANGUL SYLLABLE KIYEOK YAE SIOS - 0x8191: 0xAC68, //HANGUL SYLLABLE KIYEOK YAE SSANGSIOS - 0x8192: 0xAC69, //HANGUL SYLLABLE KIYEOK YAE IEUNG - 0x8193: 0xAC6A, //HANGUL SYLLABLE KIYEOK YAE CIEUC - 0x8194: 0xAC6B, //HANGUL SYLLABLE KIYEOK YAE CHIEUCH - 0x8195: 0xAC6C, //HANGUL SYLLABLE KIYEOK YAE KHIEUKH - 0x8196: 0xAC6D, //HANGUL SYLLABLE KIYEOK YAE THIEUTH - 0x8197: 0xAC6E, //HANGUL SYLLABLE KIYEOK YAE PHIEUPH - 0x8198: 0xAC6F, //HANGUL SYLLABLE KIYEOK YAE HIEUH - 0x8199: 0xAC72, //HANGUL SYLLABLE KIYEOK EO SSANGKIYEOK - 0x819A: 0xAC73, //HANGUL SYLLABLE KIYEOK EO KIYEOKSIOS - 0x819B: 0xAC75, //HANGUL SYLLABLE KIYEOK EO NIEUNCIEUC - 0x819C: 0xAC76, //HANGUL SYLLABLE KIYEOK EO NIEUNHIEUH - 0x819D: 0xAC79, //HANGUL SYLLABLE KIYEOK EO RIEULKIYEOK - 0x819E: 0xAC7B, //HANGUL SYLLABLE KIYEOK EO RIEULPIEUP - 0x819F: 0xAC7C, //HANGUL SYLLABLE KIYEOK EO RIEULSIOS - 0x81A0: 0xAC7D, //HANGUL SYLLABLE KIYEOK EO RIEULTHIEUTH - 0x81A1: 0xAC7E, //HANGUL SYLLABLE KIYEOK EO RIEULPHIEUPH - 0x81A2: 0xAC7F, //HANGUL SYLLABLE KIYEOK EO RIEULHIEUH - 0x81A3: 0xAC82, //HANGUL SYLLABLE KIYEOK EO PIEUPSIOS - 0x81A4: 0xAC87, //HANGUL SYLLABLE KIYEOK EO CHIEUCH - 0x81A5: 0xAC88, //HANGUL SYLLABLE KIYEOK EO KHIEUKH - 0x81A6: 0xAC8D, //HANGUL SYLLABLE KIYEOK E KIYEOK - 0x81A7: 0xAC8E, //HANGUL SYLLABLE KIYEOK E SSANGKIYEOK - 0x81A8: 0xAC8F, //HANGUL SYLLABLE KIYEOK E KIYEOKSIOS - 0x81A9: 0xAC91, //HANGUL SYLLABLE KIYEOK E NIEUNCIEUC - 0x81AA: 0xAC92, //HANGUL SYLLABLE KIYEOK E NIEUNHIEUH - 0x81AB: 0xAC93, //HANGUL SYLLABLE KIYEOK E TIKEUT - 0x81AC: 0xAC95, //HANGUL SYLLABLE KIYEOK E RIEULKIYEOK - 0x81AD: 0xAC96, //HANGUL SYLLABLE KIYEOK E RIEULMIEUM - 0x81AE: 0xAC97, //HANGUL SYLLABLE KIYEOK E RIEULPIEUP - 0x81AF: 0xAC98, //HANGUL SYLLABLE KIYEOK E RIEULSIOS - 0x81B0: 0xAC99, //HANGUL SYLLABLE KIYEOK E RIEULTHIEUTH - 0x81B1: 0xAC9A, //HANGUL SYLLABLE KIYEOK E RIEULPHIEUPH - 0x81B2: 0xAC9B, //HANGUL SYLLABLE KIYEOK E RIEULHIEUH - 0x81B3: 0xAC9E, //HANGUL SYLLABLE KIYEOK E PIEUPSIOS - 0x81B4: 0xACA2, //HANGUL SYLLABLE KIYEOK E CIEUC - 0x81B5: 0xACA3, //HANGUL SYLLABLE KIYEOK E CHIEUCH - 0x81B6: 0xACA4, //HANGUL SYLLABLE KIYEOK E KHIEUKH - 0x81B7: 0xACA5, //HANGUL SYLLABLE KIYEOK E THIEUTH - 0x81B8: 0xACA6, //HANGUL SYLLABLE KIYEOK E PHIEUPH - 0x81B9: 0xACA7, //HANGUL SYLLABLE KIYEOK E HIEUH - 0x81BA: 0xACAB, //HANGUL SYLLABLE KIYEOK YEO KIYEOKSIOS - 0x81BB: 0xACAD, //HANGUL SYLLABLE KIYEOK YEO NIEUNCIEUC - 0x81BC: 0xACAE, //HANGUL SYLLABLE KIYEOK YEO NIEUNHIEUH - 0x81BD: 0xACB1, //HANGUL SYLLABLE KIYEOK YEO RIEULKIYEOK - 0x81BE: 0xACB2, //HANGUL SYLLABLE KIYEOK YEO RIEULMIEUM - 0x81BF: 0xACB3, //HANGUL SYLLABLE KIYEOK YEO RIEULPIEUP - 0x81C0: 0xACB4, //HANGUL SYLLABLE KIYEOK YEO RIEULSIOS - 0x81C1: 0xACB5, //HANGUL SYLLABLE KIYEOK YEO RIEULTHIEUTH - 0x81C2: 0xACB6, //HANGUL SYLLABLE KIYEOK YEO RIEULPHIEUPH - 0x81C3: 0xACB7, //HANGUL SYLLABLE KIYEOK YEO RIEULHIEUH - 0x81C4: 0xACBA, //HANGUL SYLLABLE KIYEOK YEO PIEUPSIOS - 0x81C5: 0xACBE, //HANGUL SYLLABLE KIYEOK YEO CIEUC - 0x81C6: 0xACBF, //HANGUL SYLLABLE KIYEOK YEO CHIEUCH - 0x81C7: 0xACC0, //HANGUL SYLLABLE KIYEOK YEO KHIEUKH - 0x81C8: 0xACC2, //HANGUL SYLLABLE KIYEOK YEO PHIEUPH - 0x81C9: 0xACC3, //HANGUL SYLLABLE KIYEOK YEO HIEUH - 0x81CA: 0xACC5, //HANGUL SYLLABLE KIYEOK YE KIYEOK - 0x81CB: 0xACC6, //HANGUL SYLLABLE KIYEOK YE SSANGKIYEOK - 0x81CC: 0xACC7, //HANGUL SYLLABLE KIYEOK YE KIYEOKSIOS - 0x81CD: 0xACC9, //HANGUL SYLLABLE KIYEOK YE NIEUNCIEUC - 0x81CE: 0xACCA, //HANGUL SYLLABLE KIYEOK YE NIEUNHIEUH - 0x81CF: 0xACCB, //HANGUL SYLLABLE KIYEOK YE TIKEUT - 0x81D0: 0xACCD, //HANGUL SYLLABLE KIYEOK YE RIEULKIYEOK - 0x81D1: 0xACCE, //HANGUL SYLLABLE KIYEOK YE RIEULMIEUM - 0x81D2: 0xACCF, //HANGUL SYLLABLE KIYEOK YE RIEULPIEUP - 0x81D3: 0xACD0, //HANGUL SYLLABLE KIYEOK YE RIEULSIOS - 0x81D4: 0xACD1, //HANGUL SYLLABLE KIYEOK YE RIEULTHIEUTH - 0x81D5: 0xACD2, //HANGUL SYLLABLE KIYEOK YE RIEULPHIEUPH - 0x81D6: 0xACD3, //HANGUL SYLLABLE KIYEOK YE RIEULHIEUH - 0x81D7: 0xACD4, //HANGUL SYLLABLE KIYEOK YE MIEUM - 0x81D8: 0xACD6, //HANGUL SYLLABLE KIYEOK YE PIEUPSIOS - 0x81D9: 0xACD8, //HANGUL SYLLABLE KIYEOK YE SSANGSIOS - 0x81DA: 0xACD9, //HANGUL SYLLABLE KIYEOK YE IEUNG - 0x81DB: 0xACDA, //HANGUL SYLLABLE KIYEOK YE CIEUC - 0x81DC: 0xACDB, //HANGUL SYLLABLE KIYEOK YE CHIEUCH - 0x81DD: 0xACDC, //HANGUL SYLLABLE KIYEOK YE KHIEUKH - 0x81DE: 0xACDD, //HANGUL SYLLABLE KIYEOK YE THIEUTH - 0x81DF: 0xACDE, //HANGUL SYLLABLE KIYEOK YE PHIEUPH - 0x81E0: 0xACDF, //HANGUL SYLLABLE KIYEOK YE HIEUH - 0x81E1: 0xACE2, //HANGUL SYLLABLE KIYEOK O SSANGKIYEOK - 0x81E2: 0xACE3, //HANGUL SYLLABLE KIYEOK O KIYEOKSIOS - 0x81E3: 0xACE5, //HANGUL SYLLABLE KIYEOK O NIEUNCIEUC - 0x81E4: 0xACE6, //HANGUL SYLLABLE KIYEOK O NIEUNHIEUH - 0x81E5: 0xACE9, //HANGUL SYLLABLE KIYEOK O RIEULKIYEOK - 0x81E6: 0xACEB, //HANGUL SYLLABLE KIYEOK O RIEULPIEUP - 0x81E7: 0xACED, //HANGUL SYLLABLE KIYEOK O RIEULTHIEUTH - 0x81E8: 0xACEE, //HANGUL SYLLABLE KIYEOK O RIEULPHIEUPH - 0x81E9: 0xACF2, //HANGUL SYLLABLE KIYEOK O PIEUPSIOS - 0x81EA: 0xACF4, //HANGUL SYLLABLE KIYEOK O SSANGSIOS - 0x81EB: 0xACF7, //HANGUL SYLLABLE KIYEOK O CHIEUCH - 0x81EC: 0xACF8, //HANGUL SYLLABLE KIYEOK O KHIEUKH - 0x81ED: 0xACF9, //HANGUL SYLLABLE KIYEOK O THIEUTH - 0x81EE: 0xACFA, //HANGUL SYLLABLE KIYEOK O PHIEUPH - 0x81EF: 0xACFB, //HANGUL SYLLABLE KIYEOK O HIEUH - 0x81F0: 0xACFE, //HANGUL SYLLABLE KIYEOK WA SSANGKIYEOK - 0x81F1: 0xACFF, //HANGUL SYLLABLE KIYEOK WA KIYEOKSIOS - 0x81F2: 0xAD01, //HANGUL SYLLABLE KIYEOK WA NIEUNCIEUC - 0x81F3: 0xAD02, //HANGUL SYLLABLE KIYEOK WA NIEUNHIEUH - 0x81F4: 0xAD03, //HANGUL SYLLABLE KIYEOK WA TIKEUT - 0x81F5: 0xAD05, //HANGUL SYLLABLE KIYEOK WA RIEULKIYEOK - 0x81F6: 0xAD07, //HANGUL SYLLABLE KIYEOK WA RIEULPIEUP - 0x81F7: 0xAD08, //HANGUL SYLLABLE KIYEOK WA RIEULSIOS - 0x81F8: 0xAD09, //HANGUL SYLLABLE KIYEOK WA RIEULTHIEUTH - 0x81F9: 0xAD0A, //HANGUL SYLLABLE KIYEOK WA RIEULPHIEUPH - 0x81FA: 0xAD0B, //HANGUL SYLLABLE KIYEOK WA RIEULHIEUH - 0x81FB: 0xAD0E, //HANGUL SYLLABLE KIYEOK WA PIEUPSIOS - 0x81FC: 0xAD10, //HANGUL SYLLABLE KIYEOK WA SSANGSIOS - 0x81FD: 0xAD12, //HANGUL SYLLABLE KIYEOK WA CIEUC - 0x81FE: 0xAD13, //HANGUL SYLLABLE KIYEOK WA CHIEUCH - 0x8241: 0xAD14, //HANGUL SYLLABLE KIYEOK WA KHIEUKH - 0x8242: 0xAD15, //HANGUL SYLLABLE KIYEOK WA THIEUTH - 0x8243: 0xAD16, //HANGUL SYLLABLE KIYEOK WA PHIEUPH - 0x8244: 0xAD17, //HANGUL SYLLABLE KIYEOK WA HIEUH - 0x8245: 0xAD19, //HANGUL SYLLABLE KIYEOK WAE KIYEOK - 0x8246: 0xAD1A, //HANGUL SYLLABLE KIYEOK WAE SSANGKIYEOK - 0x8247: 0xAD1B, //HANGUL SYLLABLE KIYEOK WAE KIYEOKSIOS - 0x8248: 0xAD1D, //HANGUL SYLLABLE KIYEOK WAE NIEUNCIEUC - 0x8249: 0xAD1E, //HANGUL SYLLABLE KIYEOK WAE NIEUNHIEUH - 0x824A: 0xAD1F, //HANGUL SYLLABLE KIYEOK WAE TIKEUT - 0x824B: 0xAD21, //HANGUL SYLLABLE KIYEOK WAE RIEULKIYEOK - 0x824C: 0xAD22, //HANGUL SYLLABLE KIYEOK WAE RIEULMIEUM - 0x824D: 0xAD23, //HANGUL SYLLABLE KIYEOK WAE RIEULPIEUP - 0x824E: 0xAD24, //HANGUL SYLLABLE KIYEOK WAE RIEULSIOS - 0x824F: 0xAD25, //HANGUL SYLLABLE KIYEOK WAE RIEULTHIEUTH - 0x8250: 0xAD26, //HANGUL SYLLABLE KIYEOK WAE RIEULPHIEUPH - 0x8251: 0xAD27, //HANGUL SYLLABLE KIYEOK WAE RIEULHIEUH - 0x8252: 0xAD28, //HANGUL SYLLABLE KIYEOK WAE MIEUM - 0x8253: 0xAD2A, //HANGUL SYLLABLE KIYEOK WAE PIEUPSIOS - 0x8254: 0xAD2B, //HANGUL SYLLABLE KIYEOK WAE SIOS - 0x8255: 0xAD2E, //HANGUL SYLLABLE KIYEOK WAE CIEUC - 0x8256: 0xAD2F, //HANGUL SYLLABLE KIYEOK WAE CHIEUCH - 0x8257: 0xAD30, //HANGUL SYLLABLE KIYEOK WAE KHIEUKH - 0x8258: 0xAD31, //HANGUL SYLLABLE KIYEOK WAE THIEUTH - 0x8259: 0xAD32, //HANGUL SYLLABLE KIYEOK WAE PHIEUPH - 0x825A: 0xAD33, //HANGUL SYLLABLE KIYEOK WAE HIEUH - 0x8261: 0xAD36, //HANGUL SYLLABLE KIYEOK OE SSANGKIYEOK - 0x8262: 0xAD37, //HANGUL SYLLABLE KIYEOK OE KIYEOKSIOS - 0x8263: 0xAD39, //HANGUL SYLLABLE KIYEOK OE NIEUNCIEUC - 0x8264: 0xAD3A, //HANGUL SYLLABLE KIYEOK OE NIEUNHIEUH - 0x8265: 0xAD3B, //HANGUL SYLLABLE KIYEOK OE TIKEUT - 0x8266: 0xAD3D, //HANGUL SYLLABLE KIYEOK OE RIEULKIYEOK - 0x8267: 0xAD3E, //HANGUL SYLLABLE KIYEOK OE RIEULMIEUM - 0x8268: 0xAD3F, //HANGUL SYLLABLE KIYEOK OE RIEULPIEUP - 0x8269: 0xAD40, //HANGUL SYLLABLE KIYEOK OE RIEULSIOS - 0x826A: 0xAD41, //HANGUL SYLLABLE KIYEOK OE RIEULTHIEUTH - 0x826B: 0xAD42, //HANGUL SYLLABLE KIYEOK OE RIEULPHIEUPH - 0x826C: 0xAD43, //HANGUL SYLLABLE KIYEOK OE RIEULHIEUH - 0x826D: 0xAD46, //HANGUL SYLLABLE KIYEOK OE PIEUPSIOS - 0x826E: 0xAD48, //HANGUL SYLLABLE KIYEOK OE SSANGSIOS - 0x826F: 0xAD4A, //HANGUL SYLLABLE KIYEOK OE CIEUC - 0x8270: 0xAD4B, //HANGUL SYLLABLE KIYEOK OE CHIEUCH - 0x8271: 0xAD4C, //HANGUL SYLLABLE KIYEOK OE KHIEUKH - 0x8272: 0xAD4D, //HANGUL SYLLABLE KIYEOK OE THIEUTH - 0x8273: 0xAD4E, //HANGUL SYLLABLE KIYEOK OE PHIEUPH - 0x8274: 0xAD4F, //HANGUL SYLLABLE KIYEOK OE HIEUH - 0x8275: 0xAD51, //HANGUL SYLLABLE KIYEOK YO KIYEOK - 0x8276: 0xAD52, //HANGUL SYLLABLE KIYEOK YO SSANGKIYEOK - 0x8277: 0xAD53, //HANGUL SYLLABLE KIYEOK YO KIYEOKSIOS - 0x8278: 0xAD55, //HANGUL SYLLABLE KIYEOK YO NIEUNCIEUC - 0x8279: 0xAD56, //HANGUL SYLLABLE KIYEOK YO NIEUNHIEUH - 0x827A: 0xAD57, //HANGUL SYLLABLE KIYEOK YO TIKEUT - 0x8281: 0xAD59, //HANGUL SYLLABLE KIYEOK YO RIEULKIYEOK - 0x8282: 0xAD5A, //HANGUL SYLLABLE KIYEOK YO RIEULMIEUM - 0x8283: 0xAD5B, //HANGUL SYLLABLE KIYEOK YO RIEULPIEUP - 0x8284: 0xAD5C, //HANGUL SYLLABLE KIYEOK YO RIEULSIOS - 0x8285: 0xAD5D, //HANGUL SYLLABLE KIYEOK YO RIEULTHIEUTH - 0x8286: 0xAD5E, //HANGUL SYLLABLE KIYEOK YO RIEULPHIEUPH - 0x8287: 0xAD5F, //HANGUL SYLLABLE KIYEOK YO RIEULHIEUH - 0x8288: 0xAD60, //HANGUL SYLLABLE KIYEOK YO MIEUM - 0x8289: 0xAD62, //HANGUL SYLLABLE KIYEOK YO PIEUPSIOS - 0x828A: 0xAD64, //HANGUL SYLLABLE KIYEOK YO SSANGSIOS - 0x828B: 0xAD65, //HANGUL SYLLABLE KIYEOK YO IEUNG - 0x828C: 0xAD66, //HANGUL SYLLABLE KIYEOK YO CIEUC - 0x828D: 0xAD67, //HANGUL SYLLABLE KIYEOK YO CHIEUCH - 0x828E: 0xAD68, //HANGUL SYLLABLE KIYEOK YO KHIEUKH - 0x828F: 0xAD69, //HANGUL SYLLABLE KIYEOK YO THIEUTH - 0x8290: 0xAD6A, //HANGUL SYLLABLE KIYEOK YO PHIEUPH - 0x8291: 0xAD6B, //HANGUL SYLLABLE KIYEOK YO HIEUH - 0x8292: 0xAD6E, //HANGUL SYLLABLE KIYEOK U SSANGKIYEOK - 0x8293: 0xAD6F, //HANGUL SYLLABLE KIYEOK U KIYEOKSIOS - 0x8294: 0xAD71, //HANGUL SYLLABLE KIYEOK U NIEUNCIEUC - 0x8295: 0xAD72, //HANGUL SYLLABLE KIYEOK U NIEUNHIEUH - 0x8296: 0xAD77, //HANGUL SYLLABLE KIYEOK U RIEULPIEUP - 0x8297: 0xAD78, //HANGUL SYLLABLE KIYEOK U RIEULSIOS - 0x8298: 0xAD79, //HANGUL SYLLABLE KIYEOK U RIEULTHIEUTH - 0x8299: 0xAD7A, //HANGUL SYLLABLE KIYEOK U RIEULPHIEUPH - 0x829A: 0xAD7E, //HANGUL SYLLABLE KIYEOK U PIEUPSIOS - 0x829B: 0xAD80, //HANGUL SYLLABLE KIYEOK U SSANGSIOS - 0x829C: 0xAD83, //HANGUL SYLLABLE KIYEOK U CHIEUCH - 0x829D: 0xAD84, //HANGUL SYLLABLE KIYEOK U KHIEUKH - 0x829E: 0xAD85, //HANGUL SYLLABLE KIYEOK U THIEUTH - 0x829F: 0xAD86, //HANGUL SYLLABLE KIYEOK U PHIEUPH - 0x82A0: 0xAD87, //HANGUL SYLLABLE KIYEOK U HIEUH - 0x82A1: 0xAD8A, //HANGUL SYLLABLE KIYEOK WEO SSANGKIYEOK - 0x82A2: 0xAD8B, //HANGUL SYLLABLE KIYEOK WEO KIYEOKSIOS - 0x82A3: 0xAD8D, //HANGUL SYLLABLE KIYEOK WEO NIEUNCIEUC - 0x82A4: 0xAD8E, //HANGUL SYLLABLE KIYEOK WEO NIEUNHIEUH - 0x82A5: 0xAD8F, //HANGUL SYLLABLE KIYEOK WEO TIKEUT - 0x82A6: 0xAD91, //HANGUL SYLLABLE KIYEOK WEO RIEULKIYEOK - 0x82A7: 0xAD92, //HANGUL SYLLABLE KIYEOK WEO RIEULMIEUM - 0x82A8: 0xAD93, //HANGUL SYLLABLE KIYEOK WEO RIEULPIEUP - 0x82A9: 0xAD94, //HANGUL SYLLABLE KIYEOK WEO RIEULSIOS - 0x82AA: 0xAD95, //HANGUL SYLLABLE KIYEOK WEO RIEULTHIEUTH - 0x82AB: 0xAD96, //HANGUL SYLLABLE KIYEOK WEO RIEULPHIEUPH - 0x82AC: 0xAD97, //HANGUL SYLLABLE KIYEOK WEO RIEULHIEUH - 0x82AD: 0xAD98, //HANGUL SYLLABLE KIYEOK WEO MIEUM - 0x82AE: 0xAD99, //HANGUL SYLLABLE KIYEOK WEO PIEUP - 0x82AF: 0xAD9A, //HANGUL SYLLABLE KIYEOK WEO PIEUPSIOS - 0x82B0: 0xAD9B, //HANGUL SYLLABLE KIYEOK WEO SIOS - 0x82B1: 0xAD9E, //HANGUL SYLLABLE KIYEOK WEO CIEUC - 0x82B2: 0xAD9F, //HANGUL SYLLABLE KIYEOK WEO CHIEUCH - 0x82B3: 0xADA0, //HANGUL SYLLABLE KIYEOK WEO KHIEUKH - 0x82B4: 0xADA1, //HANGUL SYLLABLE KIYEOK WEO THIEUTH - 0x82B5: 0xADA2, //HANGUL SYLLABLE KIYEOK WEO PHIEUPH - 0x82B6: 0xADA3, //HANGUL SYLLABLE KIYEOK WEO HIEUH - 0x82B7: 0xADA5, //HANGUL SYLLABLE KIYEOK WE KIYEOK - 0x82B8: 0xADA6, //HANGUL SYLLABLE KIYEOK WE SSANGKIYEOK - 0x82B9: 0xADA7, //HANGUL SYLLABLE KIYEOK WE KIYEOKSIOS - 0x82BA: 0xADA8, //HANGUL SYLLABLE KIYEOK WE NIEUN - 0x82BB: 0xADA9, //HANGUL SYLLABLE KIYEOK WE NIEUNCIEUC - 0x82BC: 0xADAA, //HANGUL SYLLABLE KIYEOK WE NIEUNHIEUH - 0x82BD: 0xADAB, //HANGUL SYLLABLE KIYEOK WE TIKEUT - 0x82BE: 0xADAC, //HANGUL SYLLABLE KIYEOK WE RIEUL - 0x82BF: 0xADAD, //HANGUL SYLLABLE KIYEOK WE RIEULKIYEOK - 0x82C0: 0xADAE, //HANGUL SYLLABLE KIYEOK WE RIEULMIEUM - 0x82C1: 0xADAF, //HANGUL SYLLABLE KIYEOK WE RIEULPIEUP - 0x82C2: 0xADB0, //HANGUL SYLLABLE KIYEOK WE RIEULSIOS - 0x82C3: 0xADB1, //HANGUL SYLLABLE KIYEOK WE RIEULTHIEUTH - 0x82C4: 0xADB2, //HANGUL SYLLABLE KIYEOK WE RIEULPHIEUPH - 0x82C5: 0xADB3, //HANGUL SYLLABLE KIYEOK WE RIEULHIEUH - 0x82C6: 0xADB4, //HANGUL SYLLABLE KIYEOK WE MIEUM - 0x82C7: 0xADB5, //HANGUL SYLLABLE KIYEOK WE PIEUP - 0x82C8: 0xADB6, //HANGUL SYLLABLE KIYEOK WE PIEUPSIOS - 0x82C9: 0xADB8, //HANGUL SYLLABLE KIYEOK WE SSANGSIOS - 0x82CA: 0xADB9, //HANGUL SYLLABLE KIYEOK WE IEUNG - 0x82CB: 0xADBA, //HANGUL SYLLABLE KIYEOK WE CIEUC - 0x82CC: 0xADBB, //HANGUL SYLLABLE KIYEOK WE CHIEUCH - 0x82CD: 0xADBC, //HANGUL SYLLABLE KIYEOK WE KHIEUKH - 0x82CE: 0xADBD, //HANGUL SYLLABLE KIYEOK WE THIEUTH - 0x82CF: 0xADBE, //HANGUL SYLLABLE KIYEOK WE PHIEUPH - 0x82D0: 0xADBF, //HANGUL SYLLABLE KIYEOK WE HIEUH - 0x82D1: 0xADC2, //HANGUL SYLLABLE KIYEOK WI SSANGKIYEOK - 0x82D2: 0xADC3, //HANGUL SYLLABLE KIYEOK WI KIYEOKSIOS - 0x82D3: 0xADC5, //HANGUL SYLLABLE KIYEOK WI NIEUNCIEUC - 0x82D4: 0xADC6, //HANGUL SYLLABLE KIYEOK WI NIEUNHIEUH - 0x82D5: 0xADC7, //HANGUL SYLLABLE KIYEOK WI TIKEUT - 0x82D6: 0xADC9, //HANGUL SYLLABLE KIYEOK WI RIEULKIYEOK - 0x82D7: 0xADCA, //HANGUL SYLLABLE KIYEOK WI RIEULMIEUM - 0x82D8: 0xADCB, //HANGUL SYLLABLE KIYEOK WI RIEULPIEUP - 0x82D9: 0xADCC, //HANGUL SYLLABLE KIYEOK WI RIEULSIOS - 0x82DA: 0xADCD, //HANGUL SYLLABLE KIYEOK WI RIEULTHIEUTH - 0x82DB: 0xADCE, //HANGUL SYLLABLE KIYEOK WI RIEULPHIEUPH - 0x82DC: 0xADCF, //HANGUL SYLLABLE KIYEOK WI RIEULHIEUH - 0x82DD: 0xADD2, //HANGUL SYLLABLE KIYEOK WI PIEUPSIOS - 0x82DE: 0xADD4, //HANGUL SYLLABLE KIYEOK WI SSANGSIOS - 0x82DF: 0xADD5, //HANGUL SYLLABLE KIYEOK WI IEUNG - 0x82E0: 0xADD6, //HANGUL SYLLABLE KIYEOK WI CIEUC - 0x82E1: 0xADD7, //HANGUL SYLLABLE KIYEOK WI CHIEUCH - 0x82E2: 0xADD8, //HANGUL SYLLABLE KIYEOK WI KHIEUKH - 0x82E3: 0xADD9, //HANGUL SYLLABLE KIYEOK WI THIEUTH - 0x82E4: 0xADDA, //HANGUL SYLLABLE KIYEOK WI PHIEUPH - 0x82E5: 0xADDB, //HANGUL SYLLABLE KIYEOK WI HIEUH - 0x82E6: 0xADDD, //HANGUL SYLLABLE KIYEOK YU KIYEOK - 0x82E7: 0xADDE, //HANGUL SYLLABLE KIYEOK YU SSANGKIYEOK - 0x82E8: 0xADDF, //HANGUL SYLLABLE KIYEOK YU KIYEOKSIOS - 0x82E9: 0xADE1, //HANGUL SYLLABLE KIYEOK YU NIEUNCIEUC - 0x82EA: 0xADE2, //HANGUL SYLLABLE KIYEOK YU NIEUNHIEUH - 0x82EB: 0xADE3, //HANGUL SYLLABLE KIYEOK YU TIKEUT - 0x82EC: 0xADE5, //HANGUL SYLLABLE KIYEOK YU RIEULKIYEOK - 0x82ED: 0xADE6, //HANGUL SYLLABLE KIYEOK YU RIEULMIEUM - 0x82EE: 0xADE7, //HANGUL SYLLABLE KIYEOK YU RIEULPIEUP - 0x82EF: 0xADE8, //HANGUL SYLLABLE KIYEOK YU RIEULSIOS - 0x82F0: 0xADE9, //HANGUL SYLLABLE KIYEOK YU RIEULTHIEUTH - 0x82F1: 0xADEA, //HANGUL SYLLABLE KIYEOK YU RIEULPHIEUPH - 0x82F2: 0xADEB, //HANGUL SYLLABLE KIYEOK YU RIEULHIEUH - 0x82F3: 0xADEC, //HANGUL SYLLABLE KIYEOK YU MIEUM - 0x82F4: 0xADED, //HANGUL SYLLABLE KIYEOK YU PIEUP - 0x82F5: 0xADEE, //HANGUL SYLLABLE KIYEOK YU PIEUPSIOS - 0x82F6: 0xADEF, //HANGUL SYLLABLE KIYEOK YU SIOS - 0x82F7: 0xADF0, //HANGUL SYLLABLE KIYEOK YU SSANGSIOS - 0x82F8: 0xADF1, //HANGUL SYLLABLE KIYEOK YU IEUNG - 0x82F9: 0xADF2, //HANGUL SYLLABLE KIYEOK YU CIEUC - 0x82FA: 0xADF3, //HANGUL SYLLABLE KIYEOK YU CHIEUCH - 0x82FB: 0xADF4, //HANGUL SYLLABLE KIYEOK YU KHIEUKH - 0x82FC: 0xADF5, //HANGUL SYLLABLE KIYEOK YU THIEUTH - 0x82FD: 0xADF6, //HANGUL SYLLABLE KIYEOK YU PHIEUPH - 0x82FE: 0xADF7, //HANGUL SYLLABLE KIYEOK YU HIEUH - 0x8341: 0xADFA, //HANGUL SYLLABLE KIYEOK EU SSANGKIYEOK - 0x8342: 0xADFB, //HANGUL SYLLABLE KIYEOK EU KIYEOKSIOS - 0x8343: 0xADFD, //HANGUL SYLLABLE KIYEOK EU NIEUNCIEUC - 0x8344: 0xADFE, //HANGUL SYLLABLE KIYEOK EU NIEUNHIEUH - 0x8345: 0xAE02, //HANGUL SYLLABLE KIYEOK EU RIEULMIEUM - 0x8346: 0xAE03, //HANGUL SYLLABLE KIYEOK EU RIEULPIEUP - 0x8347: 0xAE04, //HANGUL SYLLABLE KIYEOK EU RIEULSIOS - 0x8348: 0xAE05, //HANGUL SYLLABLE KIYEOK EU RIEULTHIEUTH - 0x8349: 0xAE06, //HANGUL SYLLABLE KIYEOK EU RIEULPHIEUPH - 0x834A: 0xAE07, //HANGUL SYLLABLE KIYEOK EU RIEULHIEUH - 0x834B: 0xAE0A, //HANGUL SYLLABLE KIYEOK EU PIEUPSIOS - 0x834C: 0xAE0C, //HANGUL SYLLABLE KIYEOK EU SSANGSIOS - 0x834D: 0xAE0E, //HANGUL SYLLABLE KIYEOK EU CIEUC - 0x834E: 0xAE0F, //HANGUL SYLLABLE KIYEOK EU CHIEUCH - 0x834F: 0xAE10, //HANGUL SYLLABLE KIYEOK EU KHIEUKH - 0x8350: 0xAE11, //HANGUL SYLLABLE KIYEOK EU THIEUTH - 0x8351: 0xAE12, //HANGUL SYLLABLE KIYEOK EU PHIEUPH - 0x8352: 0xAE13, //HANGUL SYLLABLE KIYEOK EU HIEUH - 0x8353: 0xAE15, //HANGUL SYLLABLE KIYEOK YI KIYEOK - 0x8354: 0xAE16, //HANGUL SYLLABLE KIYEOK YI SSANGKIYEOK - 0x8355: 0xAE17, //HANGUL SYLLABLE KIYEOK YI KIYEOKSIOS - 0x8356: 0xAE18, //HANGUL SYLLABLE KIYEOK YI NIEUN - 0x8357: 0xAE19, //HANGUL SYLLABLE KIYEOK YI NIEUNCIEUC - 0x8358: 0xAE1A, //HANGUL SYLLABLE KIYEOK YI NIEUNHIEUH - 0x8359: 0xAE1B, //HANGUL SYLLABLE KIYEOK YI TIKEUT - 0x835A: 0xAE1C, //HANGUL SYLLABLE KIYEOK YI RIEUL - 0x8361: 0xAE1D, //HANGUL SYLLABLE KIYEOK YI RIEULKIYEOK - 0x8362: 0xAE1E, //HANGUL SYLLABLE KIYEOK YI RIEULMIEUM - 0x8363: 0xAE1F, //HANGUL SYLLABLE KIYEOK YI RIEULPIEUP - 0x8364: 0xAE20, //HANGUL SYLLABLE KIYEOK YI RIEULSIOS - 0x8365: 0xAE21, //HANGUL SYLLABLE KIYEOK YI RIEULTHIEUTH - 0x8366: 0xAE22, //HANGUL SYLLABLE KIYEOK YI RIEULPHIEUPH - 0x8367: 0xAE23, //HANGUL SYLLABLE KIYEOK YI RIEULHIEUH - 0x8368: 0xAE24, //HANGUL SYLLABLE KIYEOK YI MIEUM - 0x8369: 0xAE25, //HANGUL SYLLABLE KIYEOK YI PIEUP - 0x836A: 0xAE26, //HANGUL SYLLABLE KIYEOK YI PIEUPSIOS - 0x836B: 0xAE27, //HANGUL SYLLABLE KIYEOK YI SIOS - 0x836C: 0xAE28, //HANGUL SYLLABLE KIYEOK YI SSANGSIOS - 0x836D: 0xAE29, //HANGUL SYLLABLE KIYEOK YI IEUNG - 0x836E: 0xAE2A, //HANGUL SYLLABLE KIYEOK YI CIEUC - 0x836F: 0xAE2B, //HANGUL SYLLABLE KIYEOK YI CHIEUCH - 0x8370: 0xAE2C, //HANGUL SYLLABLE KIYEOK YI KHIEUKH - 0x8371: 0xAE2D, //HANGUL SYLLABLE KIYEOK YI THIEUTH - 0x8372: 0xAE2E, //HANGUL SYLLABLE KIYEOK YI PHIEUPH - 0x8373: 0xAE2F, //HANGUL SYLLABLE KIYEOK YI HIEUH - 0x8374: 0xAE32, //HANGUL SYLLABLE KIYEOK I SSANGKIYEOK - 0x8375: 0xAE33, //HANGUL SYLLABLE KIYEOK I KIYEOKSIOS - 0x8376: 0xAE35, //HANGUL SYLLABLE KIYEOK I NIEUNCIEUC - 0x8377: 0xAE36, //HANGUL SYLLABLE KIYEOK I NIEUNHIEUH - 0x8378: 0xAE39, //HANGUL SYLLABLE KIYEOK I RIEULKIYEOK - 0x8379: 0xAE3B, //HANGUL SYLLABLE KIYEOK I RIEULPIEUP - 0x837A: 0xAE3C, //HANGUL SYLLABLE KIYEOK I RIEULSIOS - 0x8381: 0xAE3D, //HANGUL SYLLABLE KIYEOK I RIEULTHIEUTH - 0x8382: 0xAE3E, //HANGUL SYLLABLE KIYEOK I RIEULPHIEUPH - 0x8383: 0xAE3F, //HANGUL SYLLABLE KIYEOK I RIEULHIEUH - 0x8384: 0xAE42, //HANGUL SYLLABLE KIYEOK I PIEUPSIOS - 0x8385: 0xAE44, //HANGUL SYLLABLE KIYEOK I SSANGSIOS - 0x8386: 0xAE47, //HANGUL SYLLABLE KIYEOK I CHIEUCH - 0x8387: 0xAE48, //HANGUL SYLLABLE KIYEOK I KHIEUKH - 0x8388: 0xAE49, //HANGUL SYLLABLE KIYEOK I THIEUTH - 0x8389: 0xAE4B, //HANGUL SYLLABLE KIYEOK I HIEUH - 0x838A: 0xAE4F, //HANGUL SYLLABLE SSANGKIYEOK A KIYEOKSIOS - 0x838B: 0xAE51, //HANGUL SYLLABLE SSANGKIYEOK A NIEUNCIEUC - 0x838C: 0xAE52, //HANGUL SYLLABLE SSANGKIYEOK A NIEUNHIEUH - 0x838D: 0xAE53, //HANGUL SYLLABLE SSANGKIYEOK A TIKEUT - 0x838E: 0xAE55, //HANGUL SYLLABLE SSANGKIYEOK A RIEULKIYEOK - 0x838F: 0xAE57, //HANGUL SYLLABLE SSANGKIYEOK A RIEULPIEUP - 0x8390: 0xAE58, //HANGUL SYLLABLE SSANGKIYEOK A RIEULSIOS - 0x8391: 0xAE59, //HANGUL SYLLABLE SSANGKIYEOK A RIEULTHIEUTH - 0x8392: 0xAE5A, //HANGUL SYLLABLE SSANGKIYEOK A RIEULPHIEUPH - 0x8393: 0xAE5B, //HANGUL SYLLABLE SSANGKIYEOK A RIEULHIEUH - 0x8394: 0xAE5E, //HANGUL SYLLABLE SSANGKIYEOK A PIEUPSIOS - 0x8395: 0xAE62, //HANGUL SYLLABLE SSANGKIYEOK A CIEUC - 0x8396: 0xAE63, //HANGUL SYLLABLE SSANGKIYEOK A CHIEUCH - 0x8397: 0xAE64, //HANGUL SYLLABLE SSANGKIYEOK A KHIEUKH - 0x8398: 0xAE66, //HANGUL SYLLABLE SSANGKIYEOK A PHIEUPH - 0x8399: 0xAE67, //HANGUL SYLLABLE SSANGKIYEOK A HIEUH - 0x839A: 0xAE6A, //HANGUL SYLLABLE SSANGKIYEOK AE SSANGKIYEOK - 0x839B: 0xAE6B, //HANGUL SYLLABLE SSANGKIYEOK AE KIYEOKSIOS - 0x839C: 0xAE6D, //HANGUL SYLLABLE SSANGKIYEOK AE NIEUNCIEUC - 0x839D: 0xAE6E, //HANGUL SYLLABLE SSANGKIYEOK AE NIEUNHIEUH - 0x839E: 0xAE6F, //HANGUL SYLLABLE SSANGKIYEOK AE TIKEUT - 0x839F: 0xAE71, //HANGUL SYLLABLE SSANGKIYEOK AE RIEULKIYEOK - 0x83A0: 0xAE72, //HANGUL SYLLABLE SSANGKIYEOK AE RIEULMIEUM - 0x83A1: 0xAE73, //HANGUL SYLLABLE SSANGKIYEOK AE RIEULPIEUP - 0x83A2: 0xAE74, //HANGUL SYLLABLE SSANGKIYEOK AE RIEULSIOS - 0x83A3: 0xAE75, //HANGUL SYLLABLE SSANGKIYEOK AE RIEULTHIEUTH - 0x83A4: 0xAE76, //HANGUL SYLLABLE SSANGKIYEOK AE RIEULPHIEUPH - 0x83A5: 0xAE77, //HANGUL SYLLABLE SSANGKIYEOK AE RIEULHIEUH - 0x83A6: 0xAE7A, //HANGUL SYLLABLE SSANGKIYEOK AE PIEUPSIOS - 0x83A7: 0xAE7E, //HANGUL SYLLABLE SSANGKIYEOK AE CIEUC - 0x83A8: 0xAE7F, //HANGUL SYLLABLE SSANGKIYEOK AE CHIEUCH - 0x83A9: 0xAE80, //HANGUL SYLLABLE SSANGKIYEOK AE KHIEUKH - 0x83AA: 0xAE81, //HANGUL SYLLABLE SSANGKIYEOK AE THIEUTH - 0x83AB: 0xAE82, //HANGUL SYLLABLE SSANGKIYEOK AE PHIEUPH - 0x83AC: 0xAE83, //HANGUL SYLLABLE SSANGKIYEOK AE HIEUH - 0x83AD: 0xAE86, //HANGUL SYLLABLE SSANGKIYEOK YA SSANGKIYEOK - 0x83AE: 0xAE87, //HANGUL SYLLABLE SSANGKIYEOK YA KIYEOKSIOS - 0x83AF: 0xAE88, //HANGUL SYLLABLE SSANGKIYEOK YA NIEUN - 0x83B0: 0xAE89, //HANGUL SYLLABLE SSANGKIYEOK YA NIEUNCIEUC - 0x83B1: 0xAE8A, //HANGUL SYLLABLE SSANGKIYEOK YA NIEUNHIEUH - 0x83B2: 0xAE8B, //HANGUL SYLLABLE SSANGKIYEOK YA TIKEUT - 0x83B3: 0xAE8D, //HANGUL SYLLABLE SSANGKIYEOK YA RIEULKIYEOK - 0x83B4: 0xAE8E, //HANGUL SYLLABLE SSANGKIYEOK YA RIEULMIEUM - 0x83B5: 0xAE8F, //HANGUL SYLLABLE SSANGKIYEOK YA RIEULPIEUP - 0x83B6: 0xAE90, //HANGUL SYLLABLE SSANGKIYEOK YA RIEULSIOS - 0x83B7: 0xAE91, //HANGUL SYLLABLE SSANGKIYEOK YA RIEULTHIEUTH - 0x83B8: 0xAE92, //HANGUL SYLLABLE SSANGKIYEOK YA RIEULPHIEUPH - 0x83B9: 0xAE93, //HANGUL SYLLABLE SSANGKIYEOK YA RIEULHIEUH - 0x83BA: 0xAE94, //HANGUL SYLLABLE SSANGKIYEOK YA MIEUM - 0x83BB: 0xAE95, //HANGUL SYLLABLE SSANGKIYEOK YA PIEUP - 0x83BC: 0xAE96, //HANGUL SYLLABLE SSANGKIYEOK YA PIEUPSIOS - 0x83BD: 0xAE97, //HANGUL SYLLABLE SSANGKIYEOK YA SIOS - 0x83BE: 0xAE98, //HANGUL SYLLABLE SSANGKIYEOK YA SSANGSIOS - 0x83BF: 0xAE99, //HANGUL SYLLABLE SSANGKIYEOK YA IEUNG - 0x83C0: 0xAE9A, //HANGUL SYLLABLE SSANGKIYEOK YA CIEUC - 0x83C1: 0xAE9B, //HANGUL SYLLABLE SSANGKIYEOK YA CHIEUCH - 0x83C2: 0xAE9C, //HANGUL SYLLABLE SSANGKIYEOK YA KHIEUKH - 0x83C3: 0xAE9D, //HANGUL SYLLABLE SSANGKIYEOK YA THIEUTH - 0x83C4: 0xAE9E, //HANGUL SYLLABLE SSANGKIYEOK YA PHIEUPH - 0x83C5: 0xAE9F, //HANGUL SYLLABLE SSANGKIYEOK YA HIEUH - 0x83C6: 0xAEA0, //HANGUL SYLLABLE SSANGKIYEOK YAE - 0x83C7: 0xAEA1, //HANGUL SYLLABLE SSANGKIYEOK YAE KIYEOK - 0x83C8: 0xAEA2, //HANGUL SYLLABLE SSANGKIYEOK YAE SSANGKIYEOK - 0x83C9: 0xAEA3, //HANGUL SYLLABLE SSANGKIYEOK YAE KIYEOKSIOS - 0x83CA: 0xAEA4, //HANGUL SYLLABLE SSANGKIYEOK YAE NIEUN - 0x83CB: 0xAEA5, //HANGUL SYLLABLE SSANGKIYEOK YAE NIEUNCIEUC - 0x83CC: 0xAEA6, //HANGUL SYLLABLE SSANGKIYEOK YAE NIEUNHIEUH - 0x83CD: 0xAEA7, //HANGUL SYLLABLE SSANGKIYEOK YAE TIKEUT - 0x83CE: 0xAEA8, //HANGUL SYLLABLE SSANGKIYEOK YAE RIEUL - 0x83CF: 0xAEA9, //HANGUL SYLLABLE SSANGKIYEOK YAE RIEULKIYEOK - 0x83D0: 0xAEAA, //HANGUL SYLLABLE SSANGKIYEOK YAE RIEULMIEUM - 0x83D1: 0xAEAB, //HANGUL SYLLABLE SSANGKIYEOK YAE RIEULPIEUP - 0x83D2: 0xAEAC, //HANGUL SYLLABLE SSANGKIYEOK YAE RIEULSIOS - 0x83D3: 0xAEAD, //HANGUL SYLLABLE SSANGKIYEOK YAE RIEULTHIEUTH - 0x83D4: 0xAEAE, //HANGUL SYLLABLE SSANGKIYEOK YAE RIEULPHIEUPH - 0x83D5: 0xAEAF, //HANGUL SYLLABLE SSANGKIYEOK YAE RIEULHIEUH - 0x83D6: 0xAEB0, //HANGUL SYLLABLE SSANGKIYEOK YAE MIEUM - 0x83D7: 0xAEB1, //HANGUL SYLLABLE SSANGKIYEOK YAE PIEUP - 0x83D8: 0xAEB2, //HANGUL SYLLABLE SSANGKIYEOK YAE PIEUPSIOS - 0x83D9: 0xAEB3, //HANGUL SYLLABLE SSANGKIYEOK YAE SIOS - 0x83DA: 0xAEB4, //HANGUL SYLLABLE SSANGKIYEOK YAE SSANGSIOS - 0x83DB: 0xAEB5, //HANGUL SYLLABLE SSANGKIYEOK YAE IEUNG - 0x83DC: 0xAEB6, //HANGUL SYLLABLE SSANGKIYEOK YAE CIEUC - 0x83DD: 0xAEB7, //HANGUL SYLLABLE SSANGKIYEOK YAE CHIEUCH - 0x83DE: 0xAEB8, //HANGUL SYLLABLE SSANGKIYEOK YAE KHIEUKH - 0x83DF: 0xAEB9, //HANGUL SYLLABLE SSANGKIYEOK YAE THIEUTH - 0x83E0: 0xAEBA, //HANGUL SYLLABLE SSANGKIYEOK YAE PHIEUPH - 0x83E1: 0xAEBB, //HANGUL SYLLABLE SSANGKIYEOK YAE HIEUH - 0x83E2: 0xAEBF, //HANGUL SYLLABLE SSANGKIYEOK EO KIYEOKSIOS - 0x83E3: 0xAEC1, //HANGUL SYLLABLE SSANGKIYEOK EO NIEUNCIEUC - 0x83E4: 0xAEC2, //HANGUL SYLLABLE SSANGKIYEOK EO NIEUNHIEUH - 0x83E5: 0xAEC3, //HANGUL SYLLABLE SSANGKIYEOK EO TIKEUT - 0x83E6: 0xAEC5, //HANGUL SYLLABLE SSANGKIYEOK EO RIEULKIYEOK - 0x83E7: 0xAEC6, //HANGUL SYLLABLE SSANGKIYEOK EO RIEULMIEUM - 0x83E8: 0xAEC7, //HANGUL SYLLABLE SSANGKIYEOK EO RIEULPIEUP - 0x83E9: 0xAEC8, //HANGUL SYLLABLE SSANGKIYEOK EO RIEULSIOS - 0x83EA: 0xAEC9, //HANGUL SYLLABLE SSANGKIYEOK EO RIEULTHIEUTH - 0x83EB: 0xAECA, //HANGUL SYLLABLE SSANGKIYEOK EO RIEULPHIEUPH - 0x83EC: 0xAECB, //HANGUL SYLLABLE SSANGKIYEOK EO RIEULHIEUH - 0x83ED: 0xAECE, //HANGUL SYLLABLE SSANGKIYEOK EO PIEUPSIOS - 0x83EE: 0xAED2, //HANGUL SYLLABLE SSANGKIYEOK EO CIEUC - 0x83EF: 0xAED3, //HANGUL SYLLABLE SSANGKIYEOK EO CHIEUCH - 0x83F0: 0xAED4, //HANGUL SYLLABLE SSANGKIYEOK EO KHIEUKH - 0x83F1: 0xAED5, //HANGUL SYLLABLE SSANGKIYEOK EO THIEUTH - 0x83F2: 0xAED6, //HANGUL SYLLABLE SSANGKIYEOK EO PHIEUPH - 0x83F3: 0xAED7, //HANGUL SYLLABLE SSANGKIYEOK EO HIEUH - 0x83F4: 0xAEDA, //HANGUL SYLLABLE SSANGKIYEOK E SSANGKIYEOK - 0x83F5: 0xAEDB, //HANGUL SYLLABLE SSANGKIYEOK E KIYEOKSIOS - 0x83F6: 0xAEDD, //HANGUL SYLLABLE SSANGKIYEOK E NIEUNCIEUC - 0x83F7: 0xAEDE, //HANGUL SYLLABLE SSANGKIYEOK E NIEUNHIEUH - 0x83F8: 0xAEDF, //HANGUL SYLLABLE SSANGKIYEOK E TIKEUT - 0x83F9: 0xAEE0, //HANGUL SYLLABLE SSANGKIYEOK E RIEUL - 0x83FA: 0xAEE1, //HANGUL SYLLABLE SSANGKIYEOK E RIEULKIYEOK - 0x83FB: 0xAEE2, //HANGUL SYLLABLE SSANGKIYEOK E RIEULMIEUM - 0x83FC: 0xAEE3, //HANGUL SYLLABLE SSANGKIYEOK E RIEULPIEUP - 0x83FD: 0xAEE4, //HANGUL SYLLABLE SSANGKIYEOK E RIEULSIOS - 0x83FE: 0xAEE5, //HANGUL SYLLABLE SSANGKIYEOK E RIEULTHIEUTH - 0x8441: 0xAEE6, //HANGUL SYLLABLE SSANGKIYEOK E RIEULPHIEUPH - 0x8442: 0xAEE7, //HANGUL SYLLABLE SSANGKIYEOK E RIEULHIEUH - 0x8443: 0xAEE9, //HANGUL SYLLABLE SSANGKIYEOK E PIEUP - 0x8444: 0xAEEA, //HANGUL SYLLABLE SSANGKIYEOK E PIEUPSIOS - 0x8445: 0xAEEC, //HANGUL SYLLABLE SSANGKIYEOK E SSANGSIOS - 0x8446: 0xAEEE, //HANGUL SYLLABLE SSANGKIYEOK E CIEUC - 0x8447: 0xAEEF, //HANGUL SYLLABLE SSANGKIYEOK E CHIEUCH - 0x8448: 0xAEF0, //HANGUL SYLLABLE SSANGKIYEOK E KHIEUKH - 0x8449: 0xAEF1, //HANGUL SYLLABLE SSANGKIYEOK E THIEUTH - 0x844A: 0xAEF2, //HANGUL SYLLABLE SSANGKIYEOK E PHIEUPH - 0x844B: 0xAEF3, //HANGUL SYLLABLE SSANGKIYEOK E HIEUH - 0x844C: 0xAEF5, //HANGUL SYLLABLE SSANGKIYEOK YEO KIYEOK - 0x844D: 0xAEF6, //HANGUL SYLLABLE SSANGKIYEOK YEO SSANGKIYEOK - 0x844E: 0xAEF7, //HANGUL SYLLABLE SSANGKIYEOK YEO KIYEOKSIOS - 0x844F: 0xAEF9, //HANGUL SYLLABLE SSANGKIYEOK YEO NIEUNCIEUC - 0x8450: 0xAEFA, //HANGUL SYLLABLE SSANGKIYEOK YEO NIEUNHIEUH - 0x8451: 0xAEFB, //HANGUL SYLLABLE SSANGKIYEOK YEO TIKEUT - 0x8452: 0xAEFD, //HANGUL SYLLABLE SSANGKIYEOK YEO RIEULKIYEOK - 0x8453: 0xAEFE, //HANGUL SYLLABLE SSANGKIYEOK YEO RIEULMIEUM - 0x8454: 0xAEFF, //HANGUL SYLLABLE SSANGKIYEOK YEO RIEULPIEUP - 0x8455: 0xAF00, //HANGUL SYLLABLE SSANGKIYEOK YEO RIEULSIOS - 0x8456: 0xAF01, //HANGUL SYLLABLE SSANGKIYEOK YEO RIEULTHIEUTH - 0x8457: 0xAF02, //HANGUL SYLLABLE SSANGKIYEOK YEO RIEULPHIEUPH - 0x8458: 0xAF03, //HANGUL SYLLABLE SSANGKIYEOK YEO RIEULHIEUH - 0x8459: 0xAF04, //HANGUL SYLLABLE SSANGKIYEOK YEO MIEUM - 0x845A: 0xAF05, //HANGUL SYLLABLE SSANGKIYEOK YEO PIEUP - 0x8461: 0xAF06, //HANGUL SYLLABLE SSANGKIYEOK YEO PIEUPSIOS - 0x8462: 0xAF09, //HANGUL SYLLABLE SSANGKIYEOK YEO IEUNG - 0x8463: 0xAF0A, //HANGUL SYLLABLE SSANGKIYEOK YEO CIEUC - 0x8464: 0xAF0B, //HANGUL SYLLABLE SSANGKIYEOK YEO CHIEUCH - 0x8465: 0xAF0C, //HANGUL SYLLABLE SSANGKIYEOK YEO KHIEUKH - 0x8466: 0xAF0E, //HANGUL SYLLABLE SSANGKIYEOK YEO PHIEUPH - 0x8467: 0xAF0F, //HANGUL SYLLABLE SSANGKIYEOK YEO HIEUH - 0x8468: 0xAF11, //HANGUL SYLLABLE SSANGKIYEOK YE KIYEOK - 0x8469: 0xAF12, //HANGUL SYLLABLE SSANGKIYEOK YE SSANGKIYEOK - 0x846A: 0xAF13, //HANGUL SYLLABLE SSANGKIYEOK YE KIYEOKSIOS - 0x846B: 0xAF14, //HANGUL SYLLABLE SSANGKIYEOK YE NIEUN - 0x846C: 0xAF15, //HANGUL SYLLABLE SSANGKIYEOK YE NIEUNCIEUC - 0x846D: 0xAF16, //HANGUL SYLLABLE SSANGKIYEOK YE NIEUNHIEUH - 0x846E: 0xAF17, //HANGUL SYLLABLE SSANGKIYEOK YE TIKEUT - 0x846F: 0xAF18, //HANGUL SYLLABLE SSANGKIYEOK YE RIEUL - 0x8470: 0xAF19, //HANGUL SYLLABLE SSANGKIYEOK YE RIEULKIYEOK - 0x8471: 0xAF1A, //HANGUL SYLLABLE SSANGKIYEOK YE RIEULMIEUM - 0x8472: 0xAF1B, //HANGUL SYLLABLE SSANGKIYEOK YE RIEULPIEUP - 0x8473: 0xAF1C, //HANGUL SYLLABLE SSANGKIYEOK YE RIEULSIOS - 0x8474: 0xAF1D, //HANGUL SYLLABLE SSANGKIYEOK YE RIEULTHIEUTH - 0x8475: 0xAF1E, //HANGUL SYLLABLE SSANGKIYEOK YE RIEULPHIEUPH - 0x8476: 0xAF1F, //HANGUL SYLLABLE SSANGKIYEOK YE RIEULHIEUH - 0x8477: 0xAF20, //HANGUL SYLLABLE SSANGKIYEOK YE MIEUM - 0x8478: 0xAF21, //HANGUL SYLLABLE SSANGKIYEOK YE PIEUP - 0x8479: 0xAF22, //HANGUL SYLLABLE SSANGKIYEOK YE PIEUPSIOS - 0x847A: 0xAF23, //HANGUL SYLLABLE SSANGKIYEOK YE SIOS - 0x8481: 0xAF24, //HANGUL SYLLABLE SSANGKIYEOK YE SSANGSIOS - 0x8482: 0xAF25, //HANGUL SYLLABLE SSANGKIYEOK YE IEUNG - 0x8483: 0xAF26, //HANGUL SYLLABLE SSANGKIYEOK YE CIEUC - 0x8484: 0xAF27, //HANGUL SYLLABLE SSANGKIYEOK YE CHIEUCH - 0x8485: 0xAF28, //HANGUL SYLLABLE SSANGKIYEOK YE KHIEUKH - 0x8486: 0xAF29, //HANGUL SYLLABLE SSANGKIYEOK YE THIEUTH - 0x8487: 0xAF2A, //HANGUL SYLLABLE SSANGKIYEOK YE PHIEUPH - 0x8488: 0xAF2B, //HANGUL SYLLABLE SSANGKIYEOK YE HIEUH - 0x8489: 0xAF2E, //HANGUL SYLLABLE SSANGKIYEOK O SSANGKIYEOK - 0x848A: 0xAF2F, //HANGUL SYLLABLE SSANGKIYEOK O KIYEOKSIOS - 0x848B: 0xAF31, //HANGUL SYLLABLE SSANGKIYEOK O NIEUNCIEUC - 0x848C: 0xAF33, //HANGUL SYLLABLE SSANGKIYEOK O TIKEUT - 0x848D: 0xAF35, //HANGUL SYLLABLE SSANGKIYEOK O RIEULKIYEOK - 0x848E: 0xAF36, //HANGUL SYLLABLE SSANGKIYEOK O RIEULMIEUM - 0x848F: 0xAF37, //HANGUL SYLLABLE SSANGKIYEOK O RIEULPIEUP - 0x8490: 0xAF38, //HANGUL SYLLABLE SSANGKIYEOK O RIEULSIOS - 0x8491: 0xAF39, //HANGUL SYLLABLE SSANGKIYEOK O RIEULTHIEUTH - 0x8492: 0xAF3A, //HANGUL SYLLABLE SSANGKIYEOK O RIEULPHIEUPH - 0x8493: 0xAF3B, //HANGUL SYLLABLE SSANGKIYEOK O RIEULHIEUH - 0x8494: 0xAF3E, //HANGUL SYLLABLE SSANGKIYEOK O PIEUPSIOS - 0x8495: 0xAF40, //HANGUL SYLLABLE SSANGKIYEOK O SSANGSIOS - 0x8496: 0xAF44, //HANGUL SYLLABLE SSANGKIYEOK O KHIEUKH - 0x8497: 0xAF45, //HANGUL SYLLABLE SSANGKIYEOK O THIEUTH - 0x8498: 0xAF46, //HANGUL SYLLABLE SSANGKIYEOK O PHIEUPH - 0x8499: 0xAF47, //HANGUL SYLLABLE SSANGKIYEOK O HIEUH - 0x849A: 0xAF4A, //HANGUL SYLLABLE SSANGKIYEOK WA SSANGKIYEOK - 0x849B: 0xAF4B, //HANGUL SYLLABLE SSANGKIYEOK WA KIYEOKSIOS - 0x849C: 0xAF4C, //HANGUL SYLLABLE SSANGKIYEOK WA NIEUN - 0x849D: 0xAF4D, //HANGUL SYLLABLE SSANGKIYEOK WA NIEUNCIEUC - 0x849E: 0xAF4E, //HANGUL SYLLABLE SSANGKIYEOK WA NIEUNHIEUH - 0x849F: 0xAF4F, //HANGUL SYLLABLE SSANGKIYEOK WA TIKEUT - 0x84A0: 0xAF51, //HANGUL SYLLABLE SSANGKIYEOK WA RIEULKIYEOK - 0x84A1: 0xAF52, //HANGUL SYLLABLE SSANGKIYEOK WA RIEULMIEUM - 0x84A2: 0xAF53, //HANGUL SYLLABLE SSANGKIYEOK WA RIEULPIEUP - 0x84A3: 0xAF54, //HANGUL SYLLABLE SSANGKIYEOK WA RIEULSIOS - 0x84A4: 0xAF55, //HANGUL SYLLABLE SSANGKIYEOK WA RIEULTHIEUTH - 0x84A5: 0xAF56, //HANGUL SYLLABLE SSANGKIYEOK WA RIEULPHIEUPH - 0x84A6: 0xAF57, //HANGUL SYLLABLE SSANGKIYEOK WA RIEULHIEUH - 0x84A7: 0xAF58, //HANGUL SYLLABLE SSANGKIYEOK WA MIEUM - 0x84A8: 0xAF59, //HANGUL SYLLABLE SSANGKIYEOK WA PIEUP - 0x84A9: 0xAF5A, //HANGUL SYLLABLE SSANGKIYEOK WA PIEUPSIOS - 0x84AA: 0xAF5B, //HANGUL SYLLABLE SSANGKIYEOK WA SIOS - 0x84AB: 0xAF5E, //HANGUL SYLLABLE SSANGKIYEOK WA CIEUC - 0x84AC: 0xAF5F, //HANGUL SYLLABLE SSANGKIYEOK WA CHIEUCH - 0x84AD: 0xAF60, //HANGUL SYLLABLE SSANGKIYEOK WA KHIEUKH - 0x84AE: 0xAF61, //HANGUL SYLLABLE SSANGKIYEOK WA THIEUTH - 0x84AF: 0xAF62, //HANGUL SYLLABLE SSANGKIYEOK WA PHIEUPH - 0x84B0: 0xAF63, //HANGUL SYLLABLE SSANGKIYEOK WA HIEUH - 0x84B1: 0xAF66, //HANGUL SYLLABLE SSANGKIYEOK WAE SSANGKIYEOK - 0x84B2: 0xAF67, //HANGUL SYLLABLE SSANGKIYEOK WAE KIYEOKSIOS - 0x84B3: 0xAF68, //HANGUL SYLLABLE SSANGKIYEOK WAE NIEUN - 0x84B4: 0xAF69, //HANGUL SYLLABLE SSANGKIYEOK WAE NIEUNCIEUC - 0x84B5: 0xAF6A, //HANGUL SYLLABLE SSANGKIYEOK WAE NIEUNHIEUH - 0x84B6: 0xAF6B, //HANGUL SYLLABLE SSANGKIYEOK WAE TIKEUT - 0x84B7: 0xAF6C, //HANGUL SYLLABLE SSANGKIYEOK WAE RIEUL - 0x84B8: 0xAF6D, //HANGUL SYLLABLE SSANGKIYEOK WAE RIEULKIYEOK - 0x84B9: 0xAF6E, //HANGUL SYLLABLE SSANGKIYEOK WAE RIEULMIEUM - 0x84BA: 0xAF6F, //HANGUL SYLLABLE SSANGKIYEOK WAE RIEULPIEUP - 0x84BB: 0xAF70, //HANGUL SYLLABLE SSANGKIYEOK WAE RIEULSIOS - 0x84BC: 0xAF71, //HANGUL SYLLABLE SSANGKIYEOK WAE RIEULTHIEUTH - 0x84BD: 0xAF72, //HANGUL SYLLABLE SSANGKIYEOK WAE RIEULPHIEUPH - 0x84BE: 0xAF73, //HANGUL SYLLABLE SSANGKIYEOK WAE RIEULHIEUH - 0x84BF: 0xAF74, //HANGUL SYLLABLE SSANGKIYEOK WAE MIEUM - 0x84C0: 0xAF75, //HANGUL SYLLABLE SSANGKIYEOK WAE PIEUP - 0x84C1: 0xAF76, //HANGUL SYLLABLE SSANGKIYEOK WAE PIEUPSIOS - 0x84C2: 0xAF77, //HANGUL SYLLABLE SSANGKIYEOK WAE SIOS - 0x84C3: 0xAF78, //HANGUL SYLLABLE SSANGKIYEOK WAE SSANGSIOS - 0x84C4: 0xAF7A, //HANGUL SYLLABLE SSANGKIYEOK WAE CIEUC - 0x84C5: 0xAF7B, //HANGUL SYLLABLE SSANGKIYEOK WAE CHIEUCH - 0x84C6: 0xAF7C, //HANGUL SYLLABLE SSANGKIYEOK WAE KHIEUKH - 0x84C7: 0xAF7D, //HANGUL SYLLABLE SSANGKIYEOK WAE THIEUTH - 0x84C8: 0xAF7E, //HANGUL SYLLABLE SSANGKIYEOK WAE PHIEUPH - 0x84C9: 0xAF7F, //HANGUL SYLLABLE SSANGKIYEOK WAE HIEUH - 0x84CA: 0xAF81, //HANGUL SYLLABLE SSANGKIYEOK OE KIYEOK - 0x84CB: 0xAF82, //HANGUL SYLLABLE SSANGKIYEOK OE SSANGKIYEOK - 0x84CC: 0xAF83, //HANGUL SYLLABLE SSANGKIYEOK OE KIYEOKSIOS - 0x84CD: 0xAF85, //HANGUL SYLLABLE SSANGKIYEOK OE NIEUNCIEUC - 0x84CE: 0xAF86, //HANGUL SYLLABLE SSANGKIYEOK OE NIEUNHIEUH - 0x84CF: 0xAF87, //HANGUL SYLLABLE SSANGKIYEOK OE TIKEUT - 0x84D0: 0xAF89, //HANGUL SYLLABLE SSANGKIYEOK OE RIEULKIYEOK - 0x84D1: 0xAF8A, //HANGUL SYLLABLE SSANGKIYEOK OE RIEULMIEUM - 0x84D2: 0xAF8B, //HANGUL SYLLABLE SSANGKIYEOK OE RIEULPIEUP - 0x84D3: 0xAF8C, //HANGUL SYLLABLE SSANGKIYEOK OE RIEULSIOS - 0x84D4: 0xAF8D, //HANGUL SYLLABLE SSANGKIYEOK OE RIEULTHIEUTH - 0x84D5: 0xAF8E, //HANGUL SYLLABLE SSANGKIYEOK OE RIEULPHIEUPH - 0x84D6: 0xAF8F, //HANGUL SYLLABLE SSANGKIYEOK OE RIEULHIEUH - 0x84D7: 0xAF92, //HANGUL SYLLABLE SSANGKIYEOK OE PIEUPSIOS - 0x84D8: 0xAF93, //HANGUL SYLLABLE SSANGKIYEOK OE SIOS - 0x84D9: 0xAF94, //HANGUL SYLLABLE SSANGKIYEOK OE SSANGSIOS - 0x84DA: 0xAF96, //HANGUL SYLLABLE SSANGKIYEOK OE CIEUC - 0x84DB: 0xAF97, //HANGUL SYLLABLE SSANGKIYEOK OE CHIEUCH - 0x84DC: 0xAF98, //HANGUL SYLLABLE SSANGKIYEOK OE KHIEUKH - 0x84DD: 0xAF99, //HANGUL SYLLABLE SSANGKIYEOK OE THIEUTH - 0x84DE: 0xAF9A, //HANGUL SYLLABLE SSANGKIYEOK OE PHIEUPH - 0x84DF: 0xAF9B, //HANGUL SYLLABLE SSANGKIYEOK OE HIEUH - 0x84E0: 0xAF9D, //HANGUL SYLLABLE SSANGKIYEOK YO KIYEOK - 0x84E1: 0xAF9E, //HANGUL SYLLABLE SSANGKIYEOK YO SSANGKIYEOK - 0x84E2: 0xAF9F, //HANGUL SYLLABLE SSANGKIYEOK YO KIYEOKSIOS - 0x84E3: 0xAFA0, //HANGUL SYLLABLE SSANGKIYEOK YO NIEUN - 0x84E4: 0xAFA1, //HANGUL SYLLABLE SSANGKIYEOK YO NIEUNCIEUC - 0x84E5: 0xAFA2, //HANGUL SYLLABLE SSANGKIYEOK YO NIEUNHIEUH - 0x84E6: 0xAFA3, //HANGUL SYLLABLE SSANGKIYEOK YO TIKEUT - 0x84E7: 0xAFA4, //HANGUL SYLLABLE SSANGKIYEOK YO RIEUL - 0x84E8: 0xAFA5, //HANGUL SYLLABLE SSANGKIYEOK YO RIEULKIYEOK - 0x84E9: 0xAFA6, //HANGUL SYLLABLE SSANGKIYEOK YO RIEULMIEUM - 0x84EA: 0xAFA7, //HANGUL SYLLABLE SSANGKIYEOK YO RIEULPIEUP - 0x84EB: 0xAFA8, //HANGUL SYLLABLE SSANGKIYEOK YO RIEULSIOS - 0x84EC: 0xAFA9, //HANGUL SYLLABLE SSANGKIYEOK YO RIEULTHIEUTH - 0x84ED: 0xAFAA, //HANGUL SYLLABLE SSANGKIYEOK YO RIEULPHIEUPH - 0x84EE: 0xAFAB, //HANGUL SYLLABLE SSANGKIYEOK YO RIEULHIEUH - 0x84EF: 0xAFAC, //HANGUL SYLLABLE SSANGKIYEOK YO MIEUM - 0x84F0: 0xAFAD, //HANGUL SYLLABLE SSANGKIYEOK YO PIEUP - 0x84F1: 0xAFAE, //HANGUL SYLLABLE SSANGKIYEOK YO PIEUPSIOS - 0x84F2: 0xAFAF, //HANGUL SYLLABLE SSANGKIYEOK YO SIOS - 0x84F3: 0xAFB0, //HANGUL SYLLABLE SSANGKIYEOK YO SSANGSIOS - 0x84F4: 0xAFB1, //HANGUL SYLLABLE SSANGKIYEOK YO IEUNG - 0x84F5: 0xAFB2, //HANGUL SYLLABLE SSANGKIYEOK YO CIEUC - 0x84F6: 0xAFB3, //HANGUL SYLLABLE SSANGKIYEOK YO CHIEUCH - 0x84F7: 0xAFB4, //HANGUL SYLLABLE SSANGKIYEOK YO KHIEUKH - 0x84F8: 0xAFB5, //HANGUL SYLLABLE SSANGKIYEOK YO THIEUTH - 0x84F9: 0xAFB6, //HANGUL SYLLABLE SSANGKIYEOK YO PHIEUPH - 0x84FA: 0xAFB7, //HANGUL SYLLABLE SSANGKIYEOK YO HIEUH - 0x84FB: 0xAFBA, //HANGUL SYLLABLE SSANGKIYEOK U SSANGKIYEOK - 0x84FC: 0xAFBB, //HANGUL SYLLABLE SSANGKIYEOK U KIYEOKSIOS - 0x84FD: 0xAFBD, //HANGUL SYLLABLE SSANGKIYEOK U NIEUNCIEUC - 0x84FE: 0xAFBE, //HANGUL SYLLABLE SSANGKIYEOK U NIEUNHIEUH - 0x8541: 0xAFBF, //HANGUL SYLLABLE SSANGKIYEOK U TIKEUT - 0x8542: 0xAFC1, //HANGUL SYLLABLE SSANGKIYEOK U RIEULKIYEOK - 0x8543: 0xAFC2, //HANGUL SYLLABLE SSANGKIYEOK U RIEULMIEUM - 0x8544: 0xAFC3, //HANGUL SYLLABLE SSANGKIYEOK U RIEULPIEUP - 0x8545: 0xAFC4, //HANGUL SYLLABLE SSANGKIYEOK U RIEULSIOS - 0x8546: 0xAFC5, //HANGUL SYLLABLE SSANGKIYEOK U RIEULTHIEUTH - 0x8547: 0xAFC6, //HANGUL SYLLABLE SSANGKIYEOK U RIEULPHIEUPH - 0x8548: 0xAFCA, //HANGUL SYLLABLE SSANGKIYEOK U PIEUPSIOS - 0x8549: 0xAFCC, //HANGUL SYLLABLE SSANGKIYEOK U SSANGSIOS - 0x854A: 0xAFCF, //HANGUL SYLLABLE SSANGKIYEOK U CHIEUCH - 0x854B: 0xAFD0, //HANGUL SYLLABLE SSANGKIYEOK U KHIEUKH - 0x854C: 0xAFD1, //HANGUL SYLLABLE SSANGKIYEOK U THIEUTH - 0x854D: 0xAFD2, //HANGUL SYLLABLE SSANGKIYEOK U PHIEUPH - 0x854E: 0xAFD3, //HANGUL SYLLABLE SSANGKIYEOK U HIEUH - 0x854F: 0xAFD5, //HANGUL SYLLABLE SSANGKIYEOK WEO KIYEOK - 0x8550: 0xAFD6, //HANGUL SYLLABLE SSANGKIYEOK WEO SSANGKIYEOK - 0x8551: 0xAFD7, //HANGUL SYLLABLE SSANGKIYEOK WEO KIYEOKSIOS - 0x8552: 0xAFD8, //HANGUL SYLLABLE SSANGKIYEOK WEO NIEUN - 0x8553: 0xAFD9, //HANGUL SYLLABLE SSANGKIYEOK WEO NIEUNCIEUC - 0x8554: 0xAFDA, //HANGUL SYLLABLE SSANGKIYEOK WEO NIEUNHIEUH - 0x8555: 0xAFDB, //HANGUL SYLLABLE SSANGKIYEOK WEO TIKEUT - 0x8556: 0xAFDD, //HANGUL SYLLABLE SSANGKIYEOK WEO RIEULKIYEOK - 0x8557: 0xAFDE, //HANGUL SYLLABLE SSANGKIYEOK WEO RIEULMIEUM - 0x8558: 0xAFDF, //HANGUL SYLLABLE SSANGKIYEOK WEO RIEULPIEUP - 0x8559: 0xAFE0, //HANGUL SYLLABLE SSANGKIYEOK WEO RIEULSIOS - 0x855A: 0xAFE1, //HANGUL SYLLABLE SSANGKIYEOK WEO RIEULTHIEUTH - 0x8561: 0xAFE2, //HANGUL SYLLABLE SSANGKIYEOK WEO RIEULPHIEUPH - 0x8562: 0xAFE3, //HANGUL SYLLABLE SSANGKIYEOK WEO RIEULHIEUH - 0x8563: 0xAFE4, //HANGUL SYLLABLE SSANGKIYEOK WEO MIEUM - 0x8564: 0xAFE5, //HANGUL SYLLABLE SSANGKIYEOK WEO PIEUP - 0x8565: 0xAFE6, //HANGUL SYLLABLE SSANGKIYEOK WEO PIEUPSIOS - 0x8566: 0xAFE7, //HANGUL SYLLABLE SSANGKIYEOK WEO SIOS - 0x8567: 0xAFEA, //HANGUL SYLLABLE SSANGKIYEOK WEO CIEUC - 0x8568: 0xAFEB, //HANGUL SYLLABLE SSANGKIYEOK WEO CHIEUCH - 0x8569: 0xAFEC, //HANGUL SYLLABLE SSANGKIYEOK WEO KHIEUKH - 0x856A: 0xAFED, //HANGUL SYLLABLE SSANGKIYEOK WEO THIEUTH - 0x856B: 0xAFEE, //HANGUL SYLLABLE SSANGKIYEOK WEO PHIEUPH - 0x856C: 0xAFEF, //HANGUL SYLLABLE SSANGKIYEOK WEO HIEUH - 0x856D: 0xAFF2, //HANGUL SYLLABLE SSANGKIYEOK WE SSANGKIYEOK - 0x856E: 0xAFF3, //HANGUL SYLLABLE SSANGKIYEOK WE KIYEOKSIOS - 0x856F: 0xAFF5, //HANGUL SYLLABLE SSANGKIYEOK WE NIEUNCIEUC - 0x8570: 0xAFF6, //HANGUL SYLLABLE SSANGKIYEOK WE NIEUNHIEUH - 0x8571: 0xAFF7, //HANGUL SYLLABLE SSANGKIYEOK WE TIKEUT - 0x8572: 0xAFF9, //HANGUL SYLLABLE SSANGKIYEOK WE RIEULKIYEOK - 0x8573: 0xAFFA, //HANGUL SYLLABLE SSANGKIYEOK WE RIEULMIEUM - 0x8574: 0xAFFB, //HANGUL SYLLABLE SSANGKIYEOK WE RIEULPIEUP - 0x8575: 0xAFFC, //HANGUL SYLLABLE SSANGKIYEOK WE RIEULSIOS - 0x8576: 0xAFFD, //HANGUL SYLLABLE SSANGKIYEOK WE RIEULTHIEUTH - 0x8577: 0xAFFE, //HANGUL SYLLABLE SSANGKIYEOK WE RIEULPHIEUPH - 0x8578: 0xAFFF, //HANGUL SYLLABLE SSANGKIYEOK WE RIEULHIEUH - 0x8579: 0xB002, //HANGUL SYLLABLE SSANGKIYEOK WE PIEUPSIOS - 0x857A: 0xB003, //HANGUL SYLLABLE SSANGKIYEOK WE SIOS - 0x8581: 0xB005, //HANGUL SYLLABLE SSANGKIYEOK WE IEUNG - 0x8582: 0xB006, //HANGUL SYLLABLE SSANGKIYEOK WE CIEUC - 0x8583: 0xB007, //HANGUL SYLLABLE SSANGKIYEOK WE CHIEUCH - 0x8584: 0xB008, //HANGUL SYLLABLE SSANGKIYEOK WE KHIEUKH - 0x8585: 0xB009, //HANGUL SYLLABLE SSANGKIYEOK WE THIEUTH - 0x8586: 0xB00A, //HANGUL SYLLABLE SSANGKIYEOK WE PHIEUPH - 0x8587: 0xB00B, //HANGUL SYLLABLE SSANGKIYEOK WE HIEUH - 0x8588: 0xB00D, //HANGUL SYLLABLE SSANGKIYEOK WI KIYEOK - 0x8589: 0xB00E, //HANGUL SYLLABLE SSANGKIYEOK WI SSANGKIYEOK - 0x858A: 0xB00F, //HANGUL SYLLABLE SSANGKIYEOK WI KIYEOKSIOS - 0x858B: 0xB011, //HANGUL SYLLABLE SSANGKIYEOK WI NIEUNCIEUC - 0x858C: 0xB012, //HANGUL SYLLABLE SSANGKIYEOK WI NIEUNHIEUH - 0x858D: 0xB013, //HANGUL SYLLABLE SSANGKIYEOK WI TIKEUT - 0x858E: 0xB015, //HANGUL SYLLABLE SSANGKIYEOK WI RIEULKIYEOK - 0x858F: 0xB016, //HANGUL SYLLABLE SSANGKIYEOK WI RIEULMIEUM - 0x8590: 0xB017, //HANGUL SYLLABLE SSANGKIYEOK WI RIEULPIEUP - 0x8591: 0xB018, //HANGUL SYLLABLE SSANGKIYEOK WI RIEULSIOS - 0x8592: 0xB019, //HANGUL SYLLABLE SSANGKIYEOK WI RIEULTHIEUTH - 0x8593: 0xB01A, //HANGUL SYLLABLE SSANGKIYEOK WI RIEULPHIEUPH - 0x8594: 0xB01B, //HANGUL SYLLABLE SSANGKIYEOK WI RIEULHIEUH - 0x8595: 0xB01E, //HANGUL SYLLABLE SSANGKIYEOK WI PIEUPSIOS - 0x8596: 0xB01F, //HANGUL SYLLABLE SSANGKIYEOK WI SIOS - 0x8597: 0xB020, //HANGUL SYLLABLE SSANGKIYEOK WI SSANGSIOS - 0x8598: 0xB021, //HANGUL SYLLABLE SSANGKIYEOK WI IEUNG - 0x8599: 0xB022, //HANGUL SYLLABLE SSANGKIYEOK WI CIEUC - 0x859A: 0xB023, //HANGUL SYLLABLE SSANGKIYEOK WI CHIEUCH - 0x859B: 0xB024, //HANGUL SYLLABLE SSANGKIYEOK WI KHIEUKH - 0x859C: 0xB025, //HANGUL SYLLABLE SSANGKIYEOK WI THIEUTH - 0x859D: 0xB026, //HANGUL SYLLABLE SSANGKIYEOK WI PHIEUPH - 0x859E: 0xB027, //HANGUL SYLLABLE SSANGKIYEOK WI HIEUH - 0x859F: 0xB029, //HANGUL SYLLABLE SSANGKIYEOK YU KIYEOK - 0x85A0: 0xB02A, //HANGUL SYLLABLE SSANGKIYEOK YU SSANGKIYEOK - 0x85A1: 0xB02B, //HANGUL SYLLABLE SSANGKIYEOK YU KIYEOKSIOS - 0x85A2: 0xB02C, //HANGUL SYLLABLE SSANGKIYEOK YU NIEUN - 0x85A3: 0xB02D, //HANGUL SYLLABLE SSANGKIYEOK YU NIEUNCIEUC - 0x85A4: 0xB02E, //HANGUL SYLLABLE SSANGKIYEOK YU NIEUNHIEUH - 0x85A5: 0xB02F, //HANGUL SYLLABLE SSANGKIYEOK YU TIKEUT - 0x85A6: 0xB030, //HANGUL SYLLABLE SSANGKIYEOK YU RIEUL - 0x85A7: 0xB031, //HANGUL SYLLABLE SSANGKIYEOK YU RIEULKIYEOK - 0x85A8: 0xB032, //HANGUL SYLLABLE SSANGKIYEOK YU RIEULMIEUM - 0x85A9: 0xB033, //HANGUL SYLLABLE SSANGKIYEOK YU RIEULPIEUP - 0x85AA: 0xB034, //HANGUL SYLLABLE SSANGKIYEOK YU RIEULSIOS - 0x85AB: 0xB035, //HANGUL SYLLABLE SSANGKIYEOK YU RIEULTHIEUTH - 0x85AC: 0xB036, //HANGUL SYLLABLE SSANGKIYEOK YU RIEULPHIEUPH - 0x85AD: 0xB037, //HANGUL SYLLABLE SSANGKIYEOK YU RIEULHIEUH - 0x85AE: 0xB038, //HANGUL SYLLABLE SSANGKIYEOK YU MIEUM - 0x85AF: 0xB039, //HANGUL SYLLABLE SSANGKIYEOK YU PIEUP - 0x85B0: 0xB03A, //HANGUL SYLLABLE SSANGKIYEOK YU PIEUPSIOS - 0x85B1: 0xB03B, //HANGUL SYLLABLE SSANGKIYEOK YU SIOS - 0x85B2: 0xB03C, //HANGUL SYLLABLE SSANGKIYEOK YU SSANGSIOS - 0x85B3: 0xB03D, //HANGUL SYLLABLE SSANGKIYEOK YU IEUNG - 0x85B4: 0xB03E, //HANGUL SYLLABLE SSANGKIYEOK YU CIEUC - 0x85B5: 0xB03F, //HANGUL SYLLABLE SSANGKIYEOK YU CHIEUCH - 0x85B6: 0xB040, //HANGUL SYLLABLE SSANGKIYEOK YU KHIEUKH - 0x85B7: 0xB041, //HANGUL SYLLABLE SSANGKIYEOK YU THIEUTH - 0x85B8: 0xB042, //HANGUL SYLLABLE SSANGKIYEOK YU PHIEUPH - 0x85B9: 0xB043, //HANGUL SYLLABLE SSANGKIYEOK YU HIEUH - 0x85BA: 0xB046, //HANGUL SYLLABLE SSANGKIYEOK EU SSANGKIYEOK - 0x85BB: 0xB047, //HANGUL SYLLABLE SSANGKIYEOK EU KIYEOKSIOS - 0x85BC: 0xB049, //HANGUL SYLLABLE SSANGKIYEOK EU NIEUNCIEUC - 0x85BD: 0xB04B, //HANGUL SYLLABLE SSANGKIYEOK EU TIKEUT - 0x85BE: 0xB04D, //HANGUL SYLLABLE SSANGKIYEOK EU RIEULKIYEOK - 0x85BF: 0xB04F, //HANGUL SYLLABLE SSANGKIYEOK EU RIEULPIEUP - 0x85C0: 0xB050, //HANGUL SYLLABLE SSANGKIYEOK EU RIEULSIOS - 0x85C1: 0xB051, //HANGUL SYLLABLE SSANGKIYEOK EU RIEULTHIEUTH - 0x85C2: 0xB052, //HANGUL SYLLABLE SSANGKIYEOK EU RIEULPHIEUPH - 0x85C3: 0xB056, //HANGUL SYLLABLE SSANGKIYEOK EU PIEUPSIOS - 0x85C4: 0xB058, //HANGUL SYLLABLE SSANGKIYEOK EU SSANGSIOS - 0x85C5: 0xB05A, //HANGUL SYLLABLE SSANGKIYEOK EU CIEUC - 0x85C6: 0xB05B, //HANGUL SYLLABLE SSANGKIYEOK EU CHIEUCH - 0x85C7: 0xB05C, //HANGUL SYLLABLE SSANGKIYEOK EU KHIEUKH - 0x85C8: 0xB05E, //HANGUL SYLLABLE SSANGKIYEOK EU PHIEUPH - 0x85C9: 0xB05F, //HANGUL SYLLABLE SSANGKIYEOK EU HIEUH - 0x85CA: 0xB060, //HANGUL SYLLABLE SSANGKIYEOK YI - 0x85CB: 0xB061, //HANGUL SYLLABLE SSANGKIYEOK YI KIYEOK - 0x85CC: 0xB062, //HANGUL SYLLABLE SSANGKIYEOK YI SSANGKIYEOK - 0x85CD: 0xB063, //HANGUL SYLLABLE SSANGKIYEOK YI KIYEOKSIOS - 0x85CE: 0xB064, //HANGUL SYLLABLE SSANGKIYEOK YI NIEUN - 0x85CF: 0xB065, //HANGUL SYLLABLE SSANGKIYEOK YI NIEUNCIEUC - 0x85D0: 0xB066, //HANGUL SYLLABLE SSANGKIYEOK YI NIEUNHIEUH - 0x85D1: 0xB067, //HANGUL SYLLABLE SSANGKIYEOK YI TIKEUT - 0x85D2: 0xB068, //HANGUL SYLLABLE SSANGKIYEOK YI RIEUL - 0x85D3: 0xB069, //HANGUL SYLLABLE SSANGKIYEOK YI RIEULKIYEOK - 0x85D4: 0xB06A, //HANGUL SYLLABLE SSANGKIYEOK YI RIEULMIEUM - 0x85D5: 0xB06B, //HANGUL SYLLABLE SSANGKIYEOK YI RIEULPIEUP - 0x85D6: 0xB06C, //HANGUL SYLLABLE SSANGKIYEOK YI RIEULSIOS - 0x85D7: 0xB06D, //HANGUL SYLLABLE SSANGKIYEOK YI RIEULTHIEUTH - 0x85D8: 0xB06E, //HANGUL SYLLABLE SSANGKIYEOK YI RIEULPHIEUPH - 0x85D9: 0xB06F, //HANGUL SYLLABLE SSANGKIYEOK YI RIEULHIEUH - 0x85DA: 0xB070, //HANGUL SYLLABLE SSANGKIYEOK YI MIEUM - 0x85DB: 0xB071, //HANGUL SYLLABLE SSANGKIYEOK YI PIEUP - 0x85DC: 0xB072, //HANGUL SYLLABLE SSANGKIYEOK YI PIEUPSIOS - 0x85DD: 0xB073, //HANGUL SYLLABLE SSANGKIYEOK YI SIOS - 0x85DE: 0xB074, //HANGUL SYLLABLE SSANGKIYEOK YI SSANGSIOS - 0x85DF: 0xB075, //HANGUL SYLLABLE SSANGKIYEOK YI IEUNG - 0x85E0: 0xB076, //HANGUL SYLLABLE SSANGKIYEOK YI CIEUC - 0x85E1: 0xB077, //HANGUL SYLLABLE SSANGKIYEOK YI CHIEUCH - 0x85E2: 0xB078, //HANGUL SYLLABLE SSANGKIYEOK YI KHIEUKH - 0x85E3: 0xB079, //HANGUL SYLLABLE SSANGKIYEOK YI THIEUTH - 0x85E4: 0xB07A, //HANGUL SYLLABLE SSANGKIYEOK YI PHIEUPH - 0x85E5: 0xB07B, //HANGUL SYLLABLE SSANGKIYEOK YI HIEUH - 0x85E6: 0xB07E, //HANGUL SYLLABLE SSANGKIYEOK I SSANGKIYEOK - 0x85E7: 0xB07F, //HANGUL SYLLABLE SSANGKIYEOK I KIYEOKSIOS - 0x85E8: 0xB081, //HANGUL SYLLABLE SSANGKIYEOK I NIEUNCIEUC - 0x85E9: 0xB082, //HANGUL SYLLABLE SSANGKIYEOK I NIEUNHIEUH - 0x85EA: 0xB083, //HANGUL SYLLABLE SSANGKIYEOK I TIKEUT - 0x85EB: 0xB085, //HANGUL SYLLABLE SSANGKIYEOK I RIEULKIYEOK - 0x85EC: 0xB086, //HANGUL SYLLABLE SSANGKIYEOK I RIEULMIEUM - 0x85ED: 0xB087, //HANGUL SYLLABLE SSANGKIYEOK I RIEULPIEUP - 0x85EE: 0xB088, //HANGUL SYLLABLE SSANGKIYEOK I RIEULSIOS - 0x85EF: 0xB089, //HANGUL SYLLABLE SSANGKIYEOK I RIEULTHIEUTH - 0x85F0: 0xB08A, //HANGUL SYLLABLE SSANGKIYEOK I RIEULPHIEUPH - 0x85F1: 0xB08B, //HANGUL SYLLABLE SSANGKIYEOK I RIEULHIEUH - 0x85F2: 0xB08E, //HANGUL SYLLABLE SSANGKIYEOK I PIEUPSIOS - 0x85F3: 0xB090, //HANGUL SYLLABLE SSANGKIYEOK I SSANGSIOS - 0x85F4: 0xB092, //HANGUL SYLLABLE SSANGKIYEOK I CIEUC - 0x85F5: 0xB093, //HANGUL SYLLABLE SSANGKIYEOK I CHIEUCH - 0x85F6: 0xB094, //HANGUL SYLLABLE SSANGKIYEOK I KHIEUKH - 0x85F7: 0xB095, //HANGUL SYLLABLE SSANGKIYEOK I THIEUTH - 0x85F8: 0xB096, //HANGUL SYLLABLE SSANGKIYEOK I PHIEUPH - 0x85F9: 0xB097, //HANGUL SYLLABLE SSANGKIYEOK I HIEUH - 0x85FA: 0xB09B, //HANGUL SYLLABLE NIEUN A KIYEOKSIOS - 0x85FB: 0xB09D, //HANGUL SYLLABLE NIEUN A NIEUNCIEUC - 0x85FC: 0xB09E, //HANGUL SYLLABLE NIEUN A NIEUNHIEUH - 0x85FD: 0xB0A3, //HANGUL SYLLABLE NIEUN A RIEULPIEUP - 0x85FE: 0xB0A4, //HANGUL SYLLABLE NIEUN A RIEULSIOS - 0x8641: 0xB0A5, //HANGUL SYLLABLE NIEUN A RIEULTHIEUTH - 0x8642: 0xB0A6, //HANGUL SYLLABLE NIEUN A RIEULPHIEUPH - 0x8643: 0xB0A7, //HANGUL SYLLABLE NIEUN A RIEULHIEUH - 0x8644: 0xB0AA, //HANGUL SYLLABLE NIEUN A PIEUPSIOS - 0x8645: 0xB0B0, //HANGUL SYLLABLE NIEUN A KHIEUKH - 0x8646: 0xB0B2, //HANGUL SYLLABLE NIEUN A PHIEUPH - 0x8647: 0xB0B6, //HANGUL SYLLABLE NIEUN AE SSANGKIYEOK - 0x8648: 0xB0B7, //HANGUL SYLLABLE NIEUN AE KIYEOKSIOS - 0x8649: 0xB0B9, //HANGUL SYLLABLE NIEUN AE NIEUNCIEUC - 0x864A: 0xB0BA, //HANGUL SYLLABLE NIEUN AE NIEUNHIEUH - 0x864B: 0xB0BB, //HANGUL SYLLABLE NIEUN AE TIKEUT - 0x864C: 0xB0BD, //HANGUL SYLLABLE NIEUN AE RIEULKIYEOK - 0x864D: 0xB0BE, //HANGUL SYLLABLE NIEUN AE RIEULMIEUM - 0x864E: 0xB0BF, //HANGUL SYLLABLE NIEUN AE RIEULPIEUP - 0x864F: 0xB0C0, //HANGUL SYLLABLE NIEUN AE RIEULSIOS - 0x8650: 0xB0C1, //HANGUL SYLLABLE NIEUN AE RIEULTHIEUTH - 0x8651: 0xB0C2, //HANGUL SYLLABLE NIEUN AE RIEULPHIEUPH - 0x8652: 0xB0C3, //HANGUL SYLLABLE NIEUN AE RIEULHIEUH - 0x8653: 0xB0C6, //HANGUL SYLLABLE NIEUN AE PIEUPSIOS - 0x8654: 0xB0CA, //HANGUL SYLLABLE NIEUN AE CIEUC - 0x8655: 0xB0CB, //HANGUL SYLLABLE NIEUN AE CHIEUCH - 0x8656: 0xB0CC, //HANGUL SYLLABLE NIEUN AE KHIEUKH - 0x8657: 0xB0CD, //HANGUL SYLLABLE NIEUN AE THIEUTH - 0x8658: 0xB0CE, //HANGUL SYLLABLE NIEUN AE PHIEUPH - 0x8659: 0xB0CF, //HANGUL SYLLABLE NIEUN AE HIEUH - 0x865A: 0xB0D2, //HANGUL SYLLABLE NIEUN YA SSANGKIYEOK - 0x8661: 0xB0D3, //HANGUL SYLLABLE NIEUN YA KIYEOKSIOS - 0x8662: 0xB0D5, //HANGUL SYLLABLE NIEUN YA NIEUNCIEUC - 0x8663: 0xB0D6, //HANGUL SYLLABLE NIEUN YA NIEUNHIEUH - 0x8664: 0xB0D7, //HANGUL SYLLABLE NIEUN YA TIKEUT - 0x8665: 0xB0D9, //HANGUL SYLLABLE NIEUN YA RIEULKIYEOK - 0x8666: 0xB0DA, //HANGUL SYLLABLE NIEUN YA RIEULMIEUM - 0x8667: 0xB0DB, //HANGUL SYLLABLE NIEUN YA RIEULPIEUP - 0x8668: 0xB0DC, //HANGUL SYLLABLE NIEUN YA RIEULSIOS - 0x8669: 0xB0DD, //HANGUL SYLLABLE NIEUN YA RIEULTHIEUTH - 0x866A: 0xB0DE, //HANGUL SYLLABLE NIEUN YA RIEULPHIEUPH - 0x866B: 0xB0DF, //HANGUL SYLLABLE NIEUN YA RIEULHIEUH - 0x866C: 0xB0E1, //HANGUL SYLLABLE NIEUN YA PIEUP - 0x866D: 0xB0E2, //HANGUL SYLLABLE NIEUN YA PIEUPSIOS - 0x866E: 0xB0E3, //HANGUL SYLLABLE NIEUN YA SIOS - 0x866F: 0xB0E4, //HANGUL SYLLABLE NIEUN YA SSANGSIOS - 0x8670: 0xB0E6, //HANGUL SYLLABLE NIEUN YA CIEUC - 0x8671: 0xB0E7, //HANGUL SYLLABLE NIEUN YA CHIEUCH - 0x8672: 0xB0E8, //HANGUL SYLLABLE NIEUN YA KHIEUKH - 0x8673: 0xB0E9, //HANGUL SYLLABLE NIEUN YA THIEUTH - 0x8674: 0xB0EA, //HANGUL SYLLABLE NIEUN YA PHIEUPH - 0x8675: 0xB0EB, //HANGUL SYLLABLE NIEUN YA HIEUH - 0x8676: 0xB0EC, //HANGUL SYLLABLE NIEUN YAE - 0x8677: 0xB0ED, //HANGUL SYLLABLE NIEUN YAE KIYEOK - 0x8678: 0xB0EE, //HANGUL SYLLABLE NIEUN YAE SSANGKIYEOK - 0x8679: 0xB0EF, //HANGUL SYLLABLE NIEUN YAE KIYEOKSIOS - 0x867A: 0xB0F0, //HANGUL SYLLABLE NIEUN YAE NIEUN - 0x8681: 0xB0F1, //HANGUL SYLLABLE NIEUN YAE NIEUNCIEUC - 0x8682: 0xB0F2, //HANGUL SYLLABLE NIEUN YAE NIEUNHIEUH - 0x8683: 0xB0F3, //HANGUL SYLLABLE NIEUN YAE TIKEUT - 0x8684: 0xB0F4, //HANGUL SYLLABLE NIEUN YAE RIEUL - 0x8685: 0xB0F5, //HANGUL SYLLABLE NIEUN YAE RIEULKIYEOK - 0x8686: 0xB0F6, //HANGUL SYLLABLE NIEUN YAE RIEULMIEUM - 0x8687: 0xB0F7, //HANGUL SYLLABLE NIEUN YAE RIEULPIEUP - 0x8688: 0xB0F8, //HANGUL SYLLABLE NIEUN YAE RIEULSIOS - 0x8689: 0xB0F9, //HANGUL SYLLABLE NIEUN YAE RIEULTHIEUTH - 0x868A: 0xB0FA, //HANGUL SYLLABLE NIEUN YAE RIEULPHIEUPH - 0x868B: 0xB0FB, //HANGUL SYLLABLE NIEUN YAE RIEULHIEUH - 0x868C: 0xB0FC, //HANGUL SYLLABLE NIEUN YAE MIEUM - 0x868D: 0xB0FD, //HANGUL SYLLABLE NIEUN YAE PIEUP - 0x868E: 0xB0FE, //HANGUL SYLLABLE NIEUN YAE PIEUPSIOS - 0x868F: 0xB0FF, //HANGUL SYLLABLE NIEUN YAE SIOS - 0x8690: 0xB100, //HANGUL SYLLABLE NIEUN YAE SSANGSIOS - 0x8691: 0xB101, //HANGUL SYLLABLE NIEUN YAE IEUNG - 0x8692: 0xB102, //HANGUL SYLLABLE NIEUN YAE CIEUC - 0x8693: 0xB103, //HANGUL SYLLABLE NIEUN YAE CHIEUCH - 0x8694: 0xB104, //HANGUL SYLLABLE NIEUN YAE KHIEUKH - 0x8695: 0xB105, //HANGUL SYLLABLE NIEUN YAE THIEUTH - 0x8696: 0xB106, //HANGUL SYLLABLE NIEUN YAE PHIEUPH - 0x8697: 0xB107, //HANGUL SYLLABLE NIEUN YAE HIEUH - 0x8698: 0xB10A, //HANGUL SYLLABLE NIEUN EO SSANGKIYEOK - 0x8699: 0xB10D, //HANGUL SYLLABLE NIEUN EO NIEUNCIEUC - 0x869A: 0xB10E, //HANGUL SYLLABLE NIEUN EO NIEUNHIEUH - 0x869B: 0xB10F, //HANGUL SYLLABLE NIEUN EO TIKEUT - 0x869C: 0xB111, //HANGUL SYLLABLE NIEUN EO RIEULKIYEOK - 0x869D: 0xB114, //HANGUL SYLLABLE NIEUN EO RIEULSIOS - 0x869E: 0xB115, //HANGUL SYLLABLE NIEUN EO RIEULTHIEUTH - 0x869F: 0xB116, //HANGUL SYLLABLE NIEUN EO RIEULPHIEUPH - 0x86A0: 0xB117, //HANGUL SYLLABLE NIEUN EO RIEULHIEUH - 0x86A1: 0xB11A, //HANGUL SYLLABLE NIEUN EO PIEUPSIOS - 0x86A2: 0xB11E, //HANGUL SYLLABLE NIEUN EO CIEUC - 0x86A3: 0xB11F, //HANGUL SYLLABLE NIEUN EO CHIEUCH - 0x86A4: 0xB120, //HANGUL SYLLABLE NIEUN EO KHIEUKH - 0x86A5: 0xB121, //HANGUL SYLLABLE NIEUN EO THIEUTH - 0x86A6: 0xB122, //HANGUL SYLLABLE NIEUN EO PHIEUPH - 0x86A7: 0xB126, //HANGUL SYLLABLE NIEUN E SSANGKIYEOK - 0x86A8: 0xB127, //HANGUL SYLLABLE NIEUN E KIYEOKSIOS - 0x86A9: 0xB129, //HANGUL SYLLABLE NIEUN E NIEUNCIEUC - 0x86AA: 0xB12A, //HANGUL SYLLABLE NIEUN E NIEUNHIEUH - 0x86AB: 0xB12B, //HANGUL SYLLABLE NIEUN E TIKEUT - 0x86AC: 0xB12D, //HANGUL SYLLABLE NIEUN E RIEULKIYEOK - 0x86AD: 0xB12E, //HANGUL SYLLABLE NIEUN E RIEULMIEUM - 0x86AE: 0xB12F, //HANGUL SYLLABLE NIEUN E RIEULPIEUP - 0x86AF: 0xB130, //HANGUL SYLLABLE NIEUN E RIEULSIOS - 0x86B0: 0xB131, //HANGUL SYLLABLE NIEUN E RIEULTHIEUTH - 0x86B1: 0xB132, //HANGUL SYLLABLE NIEUN E RIEULPHIEUPH - 0x86B2: 0xB133, //HANGUL SYLLABLE NIEUN E RIEULHIEUH - 0x86B3: 0xB136, //HANGUL SYLLABLE NIEUN E PIEUPSIOS - 0x86B4: 0xB13A, //HANGUL SYLLABLE NIEUN E CIEUC - 0x86B5: 0xB13B, //HANGUL SYLLABLE NIEUN E CHIEUCH - 0x86B6: 0xB13C, //HANGUL SYLLABLE NIEUN E KHIEUKH - 0x86B7: 0xB13D, //HANGUL SYLLABLE NIEUN E THIEUTH - 0x86B8: 0xB13E, //HANGUL SYLLABLE NIEUN E PHIEUPH - 0x86B9: 0xB13F, //HANGUL SYLLABLE NIEUN E HIEUH - 0x86BA: 0xB142, //HANGUL SYLLABLE NIEUN YEO SSANGKIYEOK - 0x86BB: 0xB143, //HANGUL SYLLABLE NIEUN YEO KIYEOKSIOS - 0x86BC: 0xB145, //HANGUL SYLLABLE NIEUN YEO NIEUNCIEUC - 0x86BD: 0xB146, //HANGUL SYLLABLE NIEUN YEO NIEUNHIEUH - 0x86BE: 0xB147, //HANGUL SYLLABLE NIEUN YEO TIKEUT - 0x86BF: 0xB149, //HANGUL SYLLABLE NIEUN YEO RIEULKIYEOK - 0x86C0: 0xB14A, //HANGUL SYLLABLE NIEUN YEO RIEULMIEUM - 0x86C1: 0xB14B, //HANGUL SYLLABLE NIEUN YEO RIEULPIEUP - 0x86C2: 0xB14C, //HANGUL SYLLABLE NIEUN YEO RIEULSIOS - 0x86C3: 0xB14D, //HANGUL SYLLABLE NIEUN YEO RIEULTHIEUTH - 0x86C4: 0xB14E, //HANGUL SYLLABLE NIEUN YEO RIEULPHIEUPH - 0x86C5: 0xB14F, //HANGUL SYLLABLE NIEUN YEO RIEULHIEUH - 0x86C6: 0xB152, //HANGUL SYLLABLE NIEUN YEO PIEUPSIOS - 0x86C7: 0xB153, //HANGUL SYLLABLE NIEUN YEO SIOS - 0x86C8: 0xB156, //HANGUL SYLLABLE NIEUN YEO CIEUC - 0x86C9: 0xB157, //HANGUL SYLLABLE NIEUN YEO CHIEUCH - 0x86CA: 0xB159, //HANGUL SYLLABLE NIEUN YEO THIEUTH - 0x86CB: 0xB15A, //HANGUL SYLLABLE NIEUN YEO PHIEUPH - 0x86CC: 0xB15B, //HANGUL SYLLABLE NIEUN YEO HIEUH - 0x86CD: 0xB15D, //HANGUL SYLLABLE NIEUN YE KIYEOK - 0x86CE: 0xB15E, //HANGUL SYLLABLE NIEUN YE SSANGKIYEOK - 0x86CF: 0xB15F, //HANGUL SYLLABLE NIEUN YE KIYEOKSIOS - 0x86D0: 0xB161, //HANGUL SYLLABLE NIEUN YE NIEUNCIEUC - 0x86D1: 0xB162, //HANGUL SYLLABLE NIEUN YE NIEUNHIEUH - 0x86D2: 0xB163, //HANGUL SYLLABLE NIEUN YE TIKEUT - 0x86D3: 0xB164, //HANGUL SYLLABLE NIEUN YE RIEUL - 0x86D4: 0xB165, //HANGUL SYLLABLE NIEUN YE RIEULKIYEOK - 0x86D5: 0xB166, //HANGUL SYLLABLE NIEUN YE RIEULMIEUM - 0x86D6: 0xB167, //HANGUL SYLLABLE NIEUN YE RIEULPIEUP - 0x86D7: 0xB168, //HANGUL SYLLABLE NIEUN YE RIEULSIOS - 0x86D8: 0xB169, //HANGUL SYLLABLE NIEUN YE RIEULTHIEUTH - 0x86D9: 0xB16A, //HANGUL SYLLABLE NIEUN YE RIEULPHIEUPH - 0x86DA: 0xB16B, //HANGUL SYLLABLE NIEUN YE RIEULHIEUH - 0x86DB: 0xB16C, //HANGUL SYLLABLE NIEUN YE MIEUM - 0x86DC: 0xB16D, //HANGUL SYLLABLE NIEUN YE PIEUP - 0x86DD: 0xB16E, //HANGUL SYLLABLE NIEUN YE PIEUPSIOS - 0x86DE: 0xB16F, //HANGUL SYLLABLE NIEUN YE SIOS - 0x86DF: 0xB170, //HANGUL SYLLABLE NIEUN YE SSANGSIOS - 0x86E0: 0xB171, //HANGUL SYLLABLE NIEUN YE IEUNG - 0x86E1: 0xB172, //HANGUL SYLLABLE NIEUN YE CIEUC - 0x86E2: 0xB173, //HANGUL SYLLABLE NIEUN YE CHIEUCH - 0x86E3: 0xB174, //HANGUL SYLLABLE NIEUN YE KHIEUKH - 0x86E4: 0xB175, //HANGUL SYLLABLE NIEUN YE THIEUTH - 0x86E5: 0xB176, //HANGUL SYLLABLE NIEUN YE PHIEUPH - 0x86E6: 0xB177, //HANGUL SYLLABLE NIEUN YE HIEUH - 0x86E7: 0xB17A, //HANGUL SYLLABLE NIEUN O SSANGKIYEOK - 0x86E8: 0xB17B, //HANGUL SYLLABLE NIEUN O KIYEOKSIOS - 0x86E9: 0xB17D, //HANGUL SYLLABLE NIEUN O NIEUNCIEUC - 0x86EA: 0xB17E, //HANGUL SYLLABLE NIEUN O NIEUNHIEUH - 0x86EB: 0xB17F, //HANGUL SYLLABLE NIEUN O TIKEUT - 0x86EC: 0xB181, //HANGUL SYLLABLE NIEUN O RIEULKIYEOK - 0x86ED: 0xB183, //HANGUL SYLLABLE NIEUN O RIEULPIEUP - 0x86EE: 0xB184, //HANGUL SYLLABLE NIEUN O RIEULSIOS - 0x86EF: 0xB185, //HANGUL SYLLABLE NIEUN O RIEULTHIEUTH - 0x86F0: 0xB186, //HANGUL SYLLABLE NIEUN O RIEULPHIEUPH - 0x86F1: 0xB187, //HANGUL SYLLABLE NIEUN O RIEULHIEUH - 0x86F2: 0xB18A, //HANGUL SYLLABLE NIEUN O PIEUPSIOS - 0x86F3: 0xB18C, //HANGUL SYLLABLE NIEUN O SSANGSIOS - 0x86F4: 0xB18E, //HANGUL SYLLABLE NIEUN O CIEUC - 0x86F5: 0xB18F, //HANGUL SYLLABLE NIEUN O CHIEUCH - 0x86F6: 0xB190, //HANGUL SYLLABLE NIEUN O KHIEUKH - 0x86F7: 0xB191, //HANGUL SYLLABLE NIEUN O THIEUTH - 0x86F8: 0xB195, //HANGUL SYLLABLE NIEUN WA KIYEOK - 0x86F9: 0xB196, //HANGUL SYLLABLE NIEUN WA SSANGKIYEOK - 0x86FA: 0xB197, //HANGUL SYLLABLE NIEUN WA KIYEOKSIOS - 0x86FB: 0xB199, //HANGUL SYLLABLE NIEUN WA NIEUNCIEUC - 0x86FC: 0xB19A, //HANGUL SYLLABLE NIEUN WA NIEUNHIEUH - 0x86FD: 0xB19B, //HANGUL SYLLABLE NIEUN WA TIKEUT - 0x86FE: 0xB19D, //HANGUL SYLLABLE NIEUN WA RIEULKIYEOK - 0x8741: 0xB19E, //HANGUL SYLLABLE NIEUN WA RIEULMIEUM - 0x8742: 0xB19F, //HANGUL SYLLABLE NIEUN WA RIEULPIEUP - 0x8743: 0xB1A0, //HANGUL SYLLABLE NIEUN WA RIEULSIOS - 0x8744: 0xB1A1, //HANGUL SYLLABLE NIEUN WA RIEULTHIEUTH - 0x8745: 0xB1A2, //HANGUL SYLLABLE NIEUN WA RIEULPHIEUPH - 0x8746: 0xB1A3, //HANGUL SYLLABLE NIEUN WA RIEULHIEUH - 0x8747: 0xB1A4, //HANGUL SYLLABLE NIEUN WA MIEUM - 0x8748: 0xB1A5, //HANGUL SYLLABLE NIEUN WA PIEUP - 0x8749: 0xB1A6, //HANGUL SYLLABLE NIEUN WA PIEUPSIOS - 0x874A: 0xB1A7, //HANGUL SYLLABLE NIEUN WA SIOS - 0x874B: 0xB1A9, //HANGUL SYLLABLE NIEUN WA IEUNG - 0x874C: 0xB1AA, //HANGUL SYLLABLE NIEUN WA CIEUC - 0x874D: 0xB1AB, //HANGUL SYLLABLE NIEUN WA CHIEUCH - 0x874E: 0xB1AC, //HANGUL SYLLABLE NIEUN WA KHIEUKH - 0x874F: 0xB1AD, //HANGUL SYLLABLE NIEUN WA THIEUTH - 0x8750: 0xB1AE, //HANGUL SYLLABLE NIEUN WA PHIEUPH - 0x8751: 0xB1AF, //HANGUL SYLLABLE NIEUN WA HIEUH - 0x8752: 0xB1B0, //HANGUL SYLLABLE NIEUN WAE - 0x8753: 0xB1B1, //HANGUL SYLLABLE NIEUN WAE KIYEOK - 0x8754: 0xB1B2, //HANGUL SYLLABLE NIEUN WAE SSANGKIYEOK - 0x8755: 0xB1B3, //HANGUL SYLLABLE NIEUN WAE KIYEOKSIOS - 0x8756: 0xB1B4, //HANGUL SYLLABLE NIEUN WAE NIEUN - 0x8757: 0xB1B5, //HANGUL SYLLABLE NIEUN WAE NIEUNCIEUC - 0x8758: 0xB1B6, //HANGUL SYLLABLE NIEUN WAE NIEUNHIEUH - 0x8759: 0xB1B7, //HANGUL SYLLABLE NIEUN WAE TIKEUT - 0x875A: 0xB1B8, //HANGUL SYLLABLE NIEUN WAE RIEUL - 0x8761: 0xB1B9, //HANGUL SYLLABLE NIEUN WAE RIEULKIYEOK - 0x8762: 0xB1BA, //HANGUL SYLLABLE NIEUN WAE RIEULMIEUM - 0x8763: 0xB1BB, //HANGUL SYLLABLE NIEUN WAE RIEULPIEUP - 0x8764: 0xB1BC, //HANGUL SYLLABLE NIEUN WAE RIEULSIOS - 0x8765: 0xB1BD, //HANGUL SYLLABLE NIEUN WAE RIEULTHIEUTH - 0x8766: 0xB1BE, //HANGUL SYLLABLE NIEUN WAE RIEULPHIEUPH - 0x8767: 0xB1BF, //HANGUL SYLLABLE NIEUN WAE RIEULHIEUH - 0x8768: 0xB1C0, //HANGUL SYLLABLE NIEUN WAE MIEUM - 0x8769: 0xB1C1, //HANGUL SYLLABLE NIEUN WAE PIEUP - 0x876A: 0xB1C2, //HANGUL SYLLABLE NIEUN WAE PIEUPSIOS - 0x876B: 0xB1C3, //HANGUL SYLLABLE NIEUN WAE SIOS - 0x876C: 0xB1C4, //HANGUL SYLLABLE NIEUN WAE SSANGSIOS - 0x876D: 0xB1C5, //HANGUL SYLLABLE NIEUN WAE IEUNG - 0x876E: 0xB1C6, //HANGUL SYLLABLE NIEUN WAE CIEUC - 0x876F: 0xB1C7, //HANGUL SYLLABLE NIEUN WAE CHIEUCH - 0x8770: 0xB1C8, //HANGUL SYLLABLE NIEUN WAE KHIEUKH - 0x8771: 0xB1C9, //HANGUL SYLLABLE NIEUN WAE THIEUTH - 0x8772: 0xB1CA, //HANGUL SYLLABLE NIEUN WAE PHIEUPH - 0x8773: 0xB1CB, //HANGUL SYLLABLE NIEUN WAE HIEUH - 0x8774: 0xB1CD, //HANGUL SYLLABLE NIEUN OE KIYEOK - 0x8775: 0xB1CE, //HANGUL SYLLABLE NIEUN OE SSANGKIYEOK - 0x8776: 0xB1CF, //HANGUL SYLLABLE NIEUN OE KIYEOKSIOS - 0x8777: 0xB1D1, //HANGUL SYLLABLE NIEUN OE NIEUNCIEUC - 0x8778: 0xB1D2, //HANGUL SYLLABLE NIEUN OE NIEUNHIEUH - 0x8779: 0xB1D3, //HANGUL SYLLABLE NIEUN OE TIKEUT - 0x877A: 0xB1D5, //HANGUL SYLLABLE NIEUN OE RIEULKIYEOK - 0x8781: 0xB1D6, //HANGUL SYLLABLE NIEUN OE RIEULMIEUM - 0x8782: 0xB1D7, //HANGUL SYLLABLE NIEUN OE RIEULPIEUP - 0x8783: 0xB1D8, //HANGUL SYLLABLE NIEUN OE RIEULSIOS - 0x8784: 0xB1D9, //HANGUL SYLLABLE NIEUN OE RIEULTHIEUTH - 0x8785: 0xB1DA, //HANGUL SYLLABLE NIEUN OE RIEULPHIEUPH - 0x8786: 0xB1DB, //HANGUL SYLLABLE NIEUN OE RIEULHIEUH - 0x8787: 0xB1DE, //HANGUL SYLLABLE NIEUN OE PIEUPSIOS - 0x8788: 0xB1E0, //HANGUL SYLLABLE NIEUN OE SSANGSIOS - 0x8789: 0xB1E1, //HANGUL SYLLABLE NIEUN OE IEUNG - 0x878A: 0xB1E2, //HANGUL SYLLABLE NIEUN OE CIEUC - 0x878B: 0xB1E3, //HANGUL SYLLABLE NIEUN OE CHIEUCH - 0x878C: 0xB1E4, //HANGUL SYLLABLE NIEUN OE KHIEUKH - 0x878D: 0xB1E5, //HANGUL SYLLABLE NIEUN OE THIEUTH - 0x878E: 0xB1E6, //HANGUL SYLLABLE NIEUN OE PHIEUPH - 0x878F: 0xB1E7, //HANGUL SYLLABLE NIEUN OE HIEUH - 0x8790: 0xB1EA, //HANGUL SYLLABLE NIEUN YO SSANGKIYEOK - 0x8791: 0xB1EB, //HANGUL SYLLABLE NIEUN YO KIYEOKSIOS - 0x8792: 0xB1ED, //HANGUL SYLLABLE NIEUN YO NIEUNCIEUC - 0x8793: 0xB1EE, //HANGUL SYLLABLE NIEUN YO NIEUNHIEUH - 0x8794: 0xB1EF, //HANGUL SYLLABLE NIEUN YO TIKEUT - 0x8795: 0xB1F1, //HANGUL SYLLABLE NIEUN YO RIEULKIYEOK - 0x8796: 0xB1F2, //HANGUL SYLLABLE NIEUN YO RIEULMIEUM - 0x8797: 0xB1F3, //HANGUL SYLLABLE NIEUN YO RIEULPIEUP - 0x8798: 0xB1F4, //HANGUL SYLLABLE NIEUN YO RIEULSIOS - 0x8799: 0xB1F5, //HANGUL SYLLABLE NIEUN YO RIEULTHIEUTH - 0x879A: 0xB1F6, //HANGUL SYLLABLE NIEUN YO RIEULPHIEUPH - 0x879B: 0xB1F7, //HANGUL SYLLABLE NIEUN YO RIEULHIEUH - 0x879C: 0xB1F8, //HANGUL SYLLABLE NIEUN YO MIEUM - 0x879D: 0xB1FA, //HANGUL SYLLABLE NIEUN YO PIEUPSIOS - 0x879E: 0xB1FC, //HANGUL SYLLABLE NIEUN YO SSANGSIOS - 0x879F: 0xB1FE, //HANGUL SYLLABLE NIEUN YO CIEUC - 0x87A0: 0xB1FF, //HANGUL SYLLABLE NIEUN YO CHIEUCH - 0x87A1: 0xB200, //HANGUL SYLLABLE NIEUN YO KHIEUKH - 0x87A2: 0xB201, //HANGUL SYLLABLE NIEUN YO THIEUTH - 0x87A3: 0xB202, //HANGUL SYLLABLE NIEUN YO PHIEUPH - 0x87A4: 0xB203, //HANGUL SYLLABLE NIEUN YO HIEUH - 0x87A5: 0xB206, //HANGUL SYLLABLE NIEUN U SSANGKIYEOK - 0x87A6: 0xB207, //HANGUL SYLLABLE NIEUN U KIYEOKSIOS - 0x87A7: 0xB209, //HANGUL SYLLABLE NIEUN U NIEUNCIEUC - 0x87A8: 0xB20A, //HANGUL SYLLABLE NIEUN U NIEUNHIEUH - 0x87A9: 0xB20D, //HANGUL SYLLABLE NIEUN U RIEULKIYEOK - 0x87AA: 0xB20E, //HANGUL SYLLABLE NIEUN U RIEULMIEUM - 0x87AB: 0xB20F, //HANGUL SYLLABLE NIEUN U RIEULPIEUP - 0x87AC: 0xB210, //HANGUL SYLLABLE NIEUN U RIEULSIOS - 0x87AD: 0xB211, //HANGUL SYLLABLE NIEUN U RIEULTHIEUTH - 0x87AE: 0xB212, //HANGUL SYLLABLE NIEUN U RIEULPHIEUPH - 0x87AF: 0xB213, //HANGUL SYLLABLE NIEUN U RIEULHIEUH - 0x87B0: 0xB216, //HANGUL SYLLABLE NIEUN U PIEUPSIOS - 0x87B1: 0xB218, //HANGUL SYLLABLE NIEUN U SSANGSIOS - 0x87B2: 0xB21A, //HANGUL SYLLABLE NIEUN U CIEUC - 0x87B3: 0xB21B, //HANGUL SYLLABLE NIEUN U CHIEUCH - 0x87B4: 0xB21C, //HANGUL SYLLABLE NIEUN U KHIEUKH - 0x87B5: 0xB21D, //HANGUL SYLLABLE NIEUN U THIEUTH - 0x87B6: 0xB21E, //HANGUL SYLLABLE NIEUN U PHIEUPH - 0x87B7: 0xB21F, //HANGUL SYLLABLE NIEUN U HIEUH - 0x87B8: 0xB221, //HANGUL SYLLABLE NIEUN WEO KIYEOK - 0x87B9: 0xB222, //HANGUL SYLLABLE NIEUN WEO SSANGKIYEOK - 0x87BA: 0xB223, //HANGUL SYLLABLE NIEUN WEO KIYEOKSIOS - 0x87BB: 0xB224, //HANGUL SYLLABLE NIEUN WEO NIEUN - 0x87BC: 0xB225, //HANGUL SYLLABLE NIEUN WEO NIEUNCIEUC - 0x87BD: 0xB226, //HANGUL SYLLABLE NIEUN WEO NIEUNHIEUH - 0x87BE: 0xB227, //HANGUL SYLLABLE NIEUN WEO TIKEUT - 0x87BF: 0xB228, //HANGUL SYLLABLE NIEUN WEO RIEUL - 0x87C0: 0xB229, //HANGUL SYLLABLE NIEUN WEO RIEULKIYEOK - 0x87C1: 0xB22A, //HANGUL SYLLABLE NIEUN WEO RIEULMIEUM - 0x87C2: 0xB22B, //HANGUL SYLLABLE NIEUN WEO RIEULPIEUP - 0x87C3: 0xB22C, //HANGUL SYLLABLE NIEUN WEO RIEULSIOS - 0x87C4: 0xB22D, //HANGUL SYLLABLE NIEUN WEO RIEULTHIEUTH - 0x87C5: 0xB22E, //HANGUL SYLLABLE NIEUN WEO RIEULPHIEUPH - 0x87C6: 0xB22F, //HANGUL SYLLABLE NIEUN WEO RIEULHIEUH - 0x87C7: 0xB230, //HANGUL SYLLABLE NIEUN WEO MIEUM - 0x87C8: 0xB231, //HANGUL SYLLABLE NIEUN WEO PIEUP - 0x87C9: 0xB232, //HANGUL SYLLABLE NIEUN WEO PIEUPSIOS - 0x87CA: 0xB233, //HANGUL SYLLABLE NIEUN WEO SIOS - 0x87CB: 0xB235, //HANGUL SYLLABLE NIEUN WEO IEUNG - 0x87CC: 0xB236, //HANGUL SYLLABLE NIEUN WEO CIEUC - 0x87CD: 0xB237, //HANGUL SYLLABLE NIEUN WEO CHIEUCH - 0x87CE: 0xB238, //HANGUL SYLLABLE NIEUN WEO KHIEUKH - 0x87CF: 0xB239, //HANGUL SYLLABLE NIEUN WEO THIEUTH - 0x87D0: 0xB23A, //HANGUL SYLLABLE NIEUN WEO PHIEUPH - 0x87D1: 0xB23B, //HANGUL SYLLABLE NIEUN WEO HIEUH - 0x87D2: 0xB23D, //HANGUL SYLLABLE NIEUN WE KIYEOK - 0x87D3: 0xB23E, //HANGUL SYLLABLE NIEUN WE SSANGKIYEOK - 0x87D4: 0xB23F, //HANGUL SYLLABLE NIEUN WE KIYEOKSIOS - 0x87D5: 0xB240, //HANGUL SYLLABLE NIEUN WE NIEUN - 0x87D6: 0xB241, //HANGUL SYLLABLE NIEUN WE NIEUNCIEUC - 0x87D7: 0xB242, //HANGUL SYLLABLE NIEUN WE NIEUNHIEUH - 0x87D8: 0xB243, //HANGUL SYLLABLE NIEUN WE TIKEUT - 0x87D9: 0xB244, //HANGUL SYLLABLE NIEUN WE RIEUL - 0x87DA: 0xB245, //HANGUL SYLLABLE NIEUN WE RIEULKIYEOK - 0x87DB: 0xB246, //HANGUL SYLLABLE NIEUN WE RIEULMIEUM - 0x87DC: 0xB247, //HANGUL SYLLABLE NIEUN WE RIEULPIEUP - 0x87DD: 0xB248, //HANGUL SYLLABLE NIEUN WE RIEULSIOS - 0x87DE: 0xB249, //HANGUL SYLLABLE NIEUN WE RIEULTHIEUTH - 0x87DF: 0xB24A, //HANGUL SYLLABLE NIEUN WE RIEULPHIEUPH - 0x87E0: 0xB24B, //HANGUL SYLLABLE NIEUN WE RIEULHIEUH - 0x87E1: 0xB24C, //HANGUL SYLLABLE NIEUN WE MIEUM - 0x87E2: 0xB24D, //HANGUL SYLLABLE NIEUN WE PIEUP - 0x87E3: 0xB24E, //HANGUL SYLLABLE NIEUN WE PIEUPSIOS - 0x87E4: 0xB24F, //HANGUL SYLLABLE NIEUN WE SIOS - 0x87E5: 0xB250, //HANGUL SYLLABLE NIEUN WE SSANGSIOS - 0x87E6: 0xB251, //HANGUL SYLLABLE NIEUN WE IEUNG - 0x87E7: 0xB252, //HANGUL SYLLABLE NIEUN WE CIEUC - 0x87E8: 0xB253, //HANGUL SYLLABLE NIEUN WE CHIEUCH - 0x87E9: 0xB254, //HANGUL SYLLABLE NIEUN WE KHIEUKH - 0x87EA: 0xB255, //HANGUL SYLLABLE NIEUN WE THIEUTH - 0x87EB: 0xB256, //HANGUL SYLLABLE NIEUN WE PHIEUPH - 0x87EC: 0xB257, //HANGUL SYLLABLE NIEUN WE HIEUH - 0x87ED: 0xB259, //HANGUL SYLLABLE NIEUN WI KIYEOK - 0x87EE: 0xB25A, //HANGUL SYLLABLE NIEUN WI SSANGKIYEOK - 0x87EF: 0xB25B, //HANGUL SYLLABLE NIEUN WI KIYEOKSIOS - 0x87F0: 0xB25D, //HANGUL SYLLABLE NIEUN WI NIEUNCIEUC - 0x87F1: 0xB25E, //HANGUL SYLLABLE NIEUN WI NIEUNHIEUH - 0x87F2: 0xB25F, //HANGUL SYLLABLE NIEUN WI TIKEUT - 0x87F3: 0xB261, //HANGUL SYLLABLE NIEUN WI RIEULKIYEOK - 0x87F4: 0xB262, //HANGUL SYLLABLE NIEUN WI RIEULMIEUM - 0x87F5: 0xB263, //HANGUL SYLLABLE NIEUN WI RIEULPIEUP - 0x87F6: 0xB264, //HANGUL SYLLABLE NIEUN WI RIEULSIOS - 0x87F7: 0xB265, //HANGUL SYLLABLE NIEUN WI RIEULTHIEUTH - 0x87F8: 0xB266, //HANGUL SYLLABLE NIEUN WI RIEULPHIEUPH - 0x87F9: 0xB267, //HANGUL SYLLABLE NIEUN WI RIEULHIEUH - 0x87FA: 0xB26A, //HANGUL SYLLABLE NIEUN WI PIEUPSIOS - 0x87FB: 0xB26B, //HANGUL SYLLABLE NIEUN WI SIOS - 0x87FC: 0xB26C, //HANGUL SYLLABLE NIEUN WI SSANGSIOS - 0x87FD: 0xB26D, //HANGUL SYLLABLE NIEUN WI IEUNG - 0x87FE: 0xB26E, //HANGUL SYLLABLE NIEUN WI CIEUC - 0x8841: 0xB26F, //HANGUL SYLLABLE NIEUN WI CHIEUCH - 0x8842: 0xB270, //HANGUL SYLLABLE NIEUN WI KHIEUKH - 0x8843: 0xB271, //HANGUL SYLLABLE NIEUN WI THIEUTH - 0x8844: 0xB272, //HANGUL SYLLABLE NIEUN WI PHIEUPH - 0x8845: 0xB273, //HANGUL SYLLABLE NIEUN WI HIEUH - 0x8846: 0xB276, //HANGUL SYLLABLE NIEUN YU SSANGKIYEOK - 0x8847: 0xB277, //HANGUL SYLLABLE NIEUN YU KIYEOKSIOS - 0x8848: 0xB278, //HANGUL SYLLABLE NIEUN YU NIEUN - 0x8849: 0xB279, //HANGUL SYLLABLE NIEUN YU NIEUNCIEUC - 0x884A: 0xB27A, //HANGUL SYLLABLE NIEUN YU NIEUNHIEUH - 0x884B: 0xB27B, //HANGUL SYLLABLE NIEUN YU TIKEUT - 0x884C: 0xB27D, //HANGUL SYLLABLE NIEUN YU RIEULKIYEOK - 0x884D: 0xB27E, //HANGUL SYLLABLE NIEUN YU RIEULMIEUM - 0x884E: 0xB27F, //HANGUL SYLLABLE NIEUN YU RIEULPIEUP - 0x884F: 0xB280, //HANGUL SYLLABLE NIEUN YU RIEULSIOS - 0x8850: 0xB281, //HANGUL SYLLABLE NIEUN YU RIEULTHIEUTH - 0x8851: 0xB282, //HANGUL SYLLABLE NIEUN YU RIEULPHIEUPH - 0x8852: 0xB283, //HANGUL SYLLABLE NIEUN YU RIEULHIEUH - 0x8853: 0xB286, //HANGUL SYLLABLE NIEUN YU PIEUPSIOS - 0x8854: 0xB287, //HANGUL SYLLABLE NIEUN YU SIOS - 0x8855: 0xB288, //HANGUL SYLLABLE NIEUN YU SSANGSIOS - 0x8856: 0xB28A, //HANGUL SYLLABLE NIEUN YU CIEUC - 0x8857: 0xB28B, //HANGUL SYLLABLE NIEUN YU CHIEUCH - 0x8858: 0xB28C, //HANGUL SYLLABLE NIEUN YU KHIEUKH - 0x8859: 0xB28D, //HANGUL SYLLABLE NIEUN YU THIEUTH - 0x885A: 0xB28E, //HANGUL SYLLABLE NIEUN YU PHIEUPH - 0x8861: 0xB28F, //HANGUL SYLLABLE NIEUN YU HIEUH - 0x8862: 0xB292, //HANGUL SYLLABLE NIEUN EU SSANGKIYEOK - 0x8863: 0xB293, //HANGUL SYLLABLE NIEUN EU KIYEOKSIOS - 0x8864: 0xB295, //HANGUL SYLLABLE NIEUN EU NIEUNCIEUC - 0x8865: 0xB296, //HANGUL SYLLABLE NIEUN EU NIEUNHIEUH - 0x8866: 0xB297, //HANGUL SYLLABLE NIEUN EU TIKEUT - 0x8867: 0xB29B, //HANGUL SYLLABLE NIEUN EU RIEULPIEUP - 0x8868: 0xB29C, //HANGUL SYLLABLE NIEUN EU RIEULSIOS - 0x8869: 0xB29D, //HANGUL SYLLABLE NIEUN EU RIEULTHIEUTH - 0x886A: 0xB29E, //HANGUL SYLLABLE NIEUN EU RIEULPHIEUPH - 0x886B: 0xB29F, //HANGUL SYLLABLE NIEUN EU RIEULHIEUH - 0x886C: 0xB2A2, //HANGUL SYLLABLE NIEUN EU PIEUPSIOS - 0x886D: 0xB2A4, //HANGUL SYLLABLE NIEUN EU SSANGSIOS - 0x886E: 0xB2A7, //HANGUL SYLLABLE NIEUN EU CHIEUCH - 0x886F: 0xB2A8, //HANGUL SYLLABLE NIEUN EU KHIEUKH - 0x8870: 0xB2A9, //HANGUL SYLLABLE NIEUN EU THIEUTH - 0x8871: 0xB2AB, //HANGUL SYLLABLE NIEUN EU HIEUH - 0x8872: 0xB2AD, //HANGUL SYLLABLE NIEUN YI KIYEOK - 0x8873: 0xB2AE, //HANGUL SYLLABLE NIEUN YI SSANGKIYEOK - 0x8874: 0xB2AF, //HANGUL SYLLABLE NIEUN YI KIYEOKSIOS - 0x8875: 0xB2B1, //HANGUL SYLLABLE NIEUN YI NIEUNCIEUC - 0x8876: 0xB2B2, //HANGUL SYLLABLE NIEUN YI NIEUNHIEUH - 0x8877: 0xB2B3, //HANGUL SYLLABLE NIEUN YI TIKEUT - 0x8878: 0xB2B5, //HANGUL SYLLABLE NIEUN YI RIEULKIYEOK - 0x8879: 0xB2B6, //HANGUL SYLLABLE NIEUN YI RIEULMIEUM - 0x887A: 0xB2B7, //HANGUL SYLLABLE NIEUN YI RIEULPIEUP - 0x8881: 0xB2B8, //HANGUL SYLLABLE NIEUN YI RIEULSIOS - 0x8882: 0xB2B9, //HANGUL SYLLABLE NIEUN YI RIEULTHIEUTH - 0x8883: 0xB2BA, //HANGUL SYLLABLE NIEUN YI RIEULPHIEUPH - 0x8884: 0xB2BB, //HANGUL SYLLABLE NIEUN YI RIEULHIEUH - 0x8885: 0xB2BC, //HANGUL SYLLABLE NIEUN YI MIEUM - 0x8886: 0xB2BD, //HANGUL SYLLABLE NIEUN YI PIEUP - 0x8887: 0xB2BE, //HANGUL SYLLABLE NIEUN YI PIEUPSIOS - 0x8888: 0xB2BF, //HANGUL SYLLABLE NIEUN YI SIOS - 0x8889: 0xB2C0, //HANGUL SYLLABLE NIEUN YI SSANGSIOS - 0x888A: 0xB2C1, //HANGUL SYLLABLE NIEUN YI IEUNG - 0x888B: 0xB2C2, //HANGUL SYLLABLE NIEUN YI CIEUC - 0x888C: 0xB2C3, //HANGUL SYLLABLE NIEUN YI CHIEUCH - 0x888D: 0xB2C4, //HANGUL SYLLABLE NIEUN YI KHIEUKH - 0x888E: 0xB2C5, //HANGUL SYLLABLE NIEUN YI THIEUTH - 0x888F: 0xB2C6, //HANGUL SYLLABLE NIEUN YI PHIEUPH - 0x8890: 0xB2C7, //HANGUL SYLLABLE NIEUN YI HIEUH - 0x8891: 0xB2CA, //HANGUL SYLLABLE NIEUN I SSANGKIYEOK - 0x8892: 0xB2CB, //HANGUL SYLLABLE NIEUN I KIYEOKSIOS - 0x8893: 0xB2CD, //HANGUL SYLLABLE NIEUN I NIEUNCIEUC - 0x8894: 0xB2CE, //HANGUL SYLLABLE NIEUN I NIEUNHIEUH - 0x8895: 0xB2CF, //HANGUL SYLLABLE NIEUN I TIKEUT - 0x8896: 0xB2D1, //HANGUL SYLLABLE NIEUN I RIEULKIYEOK - 0x8897: 0xB2D3, //HANGUL SYLLABLE NIEUN I RIEULPIEUP - 0x8898: 0xB2D4, //HANGUL SYLLABLE NIEUN I RIEULSIOS - 0x8899: 0xB2D5, //HANGUL SYLLABLE NIEUN I RIEULTHIEUTH - 0x889A: 0xB2D6, //HANGUL SYLLABLE NIEUN I RIEULPHIEUPH - 0x889B: 0xB2D7, //HANGUL SYLLABLE NIEUN I RIEULHIEUH - 0x889C: 0xB2DA, //HANGUL SYLLABLE NIEUN I PIEUPSIOS - 0x889D: 0xB2DC, //HANGUL SYLLABLE NIEUN I SSANGSIOS - 0x889E: 0xB2DE, //HANGUL SYLLABLE NIEUN I CIEUC - 0x889F: 0xB2DF, //HANGUL SYLLABLE NIEUN I CHIEUCH - 0x88A0: 0xB2E0, //HANGUL SYLLABLE NIEUN I KHIEUKH - 0x88A1: 0xB2E1, //HANGUL SYLLABLE NIEUN I THIEUTH - 0x88A2: 0xB2E3, //HANGUL SYLLABLE NIEUN I HIEUH - 0x88A3: 0xB2E7, //HANGUL SYLLABLE TIKEUT A KIYEOKSIOS - 0x88A4: 0xB2E9, //HANGUL SYLLABLE TIKEUT A NIEUNCIEUC - 0x88A5: 0xB2EA, //HANGUL SYLLABLE TIKEUT A NIEUNHIEUH - 0x88A6: 0xB2F0, //HANGUL SYLLABLE TIKEUT A RIEULSIOS - 0x88A7: 0xB2F1, //HANGUL SYLLABLE TIKEUT A RIEULTHIEUTH - 0x88A8: 0xB2F2, //HANGUL SYLLABLE TIKEUT A RIEULPHIEUPH - 0x88A9: 0xB2F6, //HANGUL SYLLABLE TIKEUT A PIEUPSIOS - 0x88AA: 0xB2FC, //HANGUL SYLLABLE TIKEUT A KHIEUKH - 0x88AB: 0xB2FD, //HANGUL SYLLABLE TIKEUT A THIEUTH - 0x88AC: 0xB2FE, //HANGUL SYLLABLE TIKEUT A PHIEUPH - 0x88AD: 0xB302, //HANGUL SYLLABLE TIKEUT AE SSANGKIYEOK - 0x88AE: 0xB303, //HANGUL SYLLABLE TIKEUT AE KIYEOKSIOS - 0x88AF: 0xB305, //HANGUL SYLLABLE TIKEUT AE NIEUNCIEUC - 0x88B0: 0xB306, //HANGUL SYLLABLE TIKEUT AE NIEUNHIEUH - 0x88B1: 0xB307, //HANGUL SYLLABLE TIKEUT AE TIKEUT - 0x88B2: 0xB309, //HANGUL SYLLABLE TIKEUT AE RIEULKIYEOK - 0x88B3: 0xB30A, //HANGUL SYLLABLE TIKEUT AE RIEULMIEUM - 0x88B4: 0xB30B, //HANGUL SYLLABLE TIKEUT AE RIEULPIEUP - 0x88B5: 0xB30C, //HANGUL SYLLABLE TIKEUT AE RIEULSIOS - 0x88B6: 0xB30D, //HANGUL SYLLABLE TIKEUT AE RIEULTHIEUTH - 0x88B7: 0xB30E, //HANGUL SYLLABLE TIKEUT AE RIEULPHIEUPH - 0x88B8: 0xB30F, //HANGUL SYLLABLE TIKEUT AE RIEULHIEUH - 0x88B9: 0xB312, //HANGUL SYLLABLE TIKEUT AE PIEUPSIOS - 0x88BA: 0xB316, //HANGUL SYLLABLE TIKEUT AE CIEUC - 0x88BB: 0xB317, //HANGUL SYLLABLE TIKEUT AE CHIEUCH - 0x88BC: 0xB318, //HANGUL SYLLABLE TIKEUT AE KHIEUKH - 0x88BD: 0xB319, //HANGUL SYLLABLE TIKEUT AE THIEUTH - 0x88BE: 0xB31A, //HANGUL SYLLABLE TIKEUT AE PHIEUPH - 0x88BF: 0xB31B, //HANGUL SYLLABLE TIKEUT AE HIEUH - 0x88C0: 0xB31D, //HANGUL SYLLABLE TIKEUT YA KIYEOK - 0x88C1: 0xB31E, //HANGUL SYLLABLE TIKEUT YA SSANGKIYEOK - 0x88C2: 0xB31F, //HANGUL SYLLABLE TIKEUT YA KIYEOKSIOS - 0x88C3: 0xB320, //HANGUL SYLLABLE TIKEUT YA NIEUN - 0x88C4: 0xB321, //HANGUL SYLLABLE TIKEUT YA NIEUNCIEUC - 0x88C5: 0xB322, //HANGUL SYLLABLE TIKEUT YA NIEUNHIEUH - 0x88C6: 0xB323, //HANGUL SYLLABLE TIKEUT YA TIKEUT - 0x88C7: 0xB324, //HANGUL SYLLABLE TIKEUT YA RIEUL - 0x88C8: 0xB325, //HANGUL SYLLABLE TIKEUT YA RIEULKIYEOK - 0x88C9: 0xB326, //HANGUL SYLLABLE TIKEUT YA RIEULMIEUM - 0x88CA: 0xB327, //HANGUL SYLLABLE TIKEUT YA RIEULPIEUP - 0x88CB: 0xB328, //HANGUL SYLLABLE TIKEUT YA RIEULSIOS - 0x88CC: 0xB329, //HANGUL SYLLABLE TIKEUT YA RIEULTHIEUTH - 0x88CD: 0xB32A, //HANGUL SYLLABLE TIKEUT YA RIEULPHIEUPH - 0x88CE: 0xB32B, //HANGUL SYLLABLE TIKEUT YA RIEULHIEUH - 0x88CF: 0xB32C, //HANGUL SYLLABLE TIKEUT YA MIEUM - 0x88D0: 0xB32D, //HANGUL SYLLABLE TIKEUT YA PIEUP - 0x88D1: 0xB32E, //HANGUL SYLLABLE TIKEUT YA PIEUPSIOS - 0x88D2: 0xB32F, //HANGUL SYLLABLE TIKEUT YA SIOS - 0x88D3: 0xB330, //HANGUL SYLLABLE TIKEUT YA SSANGSIOS - 0x88D4: 0xB331, //HANGUL SYLLABLE TIKEUT YA IEUNG - 0x88D5: 0xB332, //HANGUL SYLLABLE TIKEUT YA CIEUC - 0x88D6: 0xB333, //HANGUL SYLLABLE TIKEUT YA CHIEUCH - 0x88D7: 0xB334, //HANGUL SYLLABLE TIKEUT YA KHIEUKH - 0x88D8: 0xB335, //HANGUL SYLLABLE TIKEUT YA THIEUTH - 0x88D9: 0xB336, //HANGUL SYLLABLE TIKEUT YA PHIEUPH - 0x88DA: 0xB337, //HANGUL SYLLABLE TIKEUT YA HIEUH - 0x88DB: 0xB338, //HANGUL SYLLABLE TIKEUT YAE - 0x88DC: 0xB339, //HANGUL SYLLABLE TIKEUT YAE KIYEOK - 0x88DD: 0xB33A, //HANGUL SYLLABLE TIKEUT YAE SSANGKIYEOK - 0x88DE: 0xB33B, //HANGUL SYLLABLE TIKEUT YAE KIYEOKSIOS - 0x88DF: 0xB33C, //HANGUL SYLLABLE TIKEUT YAE NIEUN - 0x88E0: 0xB33D, //HANGUL SYLLABLE TIKEUT YAE NIEUNCIEUC - 0x88E1: 0xB33E, //HANGUL SYLLABLE TIKEUT YAE NIEUNHIEUH - 0x88E2: 0xB33F, //HANGUL SYLLABLE TIKEUT YAE TIKEUT - 0x88E3: 0xB340, //HANGUL SYLLABLE TIKEUT YAE RIEUL - 0x88E4: 0xB341, //HANGUL SYLLABLE TIKEUT YAE RIEULKIYEOK - 0x88E5: 0xB342, //HANGUL SYLLABLE TIKEUT YAE RIEULMIEUM - 0x88E6: 0xB343, //HANGUL SYLLABLE TIKEUT YAE RIEULPIEUP - 0x88E7: 0xB344, //HANGUL SYLLABLE TIKEUT YAE RIEULSIOS - 0x88E8: 0xB345, //HANGUL SYLLABLE TIKEUT YAE RIEULTHIEUTH - 0x88E9: 0xB346, //HANGUL SYLLABLE TIKEUT YAE RIEULPHIEUPH - 0x88EA: 0xB347, //HANGUL SYLLABLE TIKEUT YAE RIEULHIEUH - 0x88EB: 0xB348, //HANGUL SYLLABLE TIKEUT YAE MIEUM - 0x88EC: 0xB349, //HANGUL SYLLABLE TIKEUT YAE PIEUP - 0x88ED: 0xB34A, //HANGUL SYLLABLE TIKEUT YAE PIEUPSIOS - 0x88EE: 0xB34B, //HANGUL SYLLABLE TIKEUT YAE SIOS - 0x88EF: 0xB34C, //HANGUL SYLLABLE TIKEUT YAE SSANGSIOS - 0x88F0: 0xB34D, //HANGUL SYLLABLE TIKEUT YAE IEUNG - 0x88F1: 0xB34E, //HANGUL SYLLABLE TIKEUT YAE CIEUC - 0x88F2: 0xB34F, //HANGUL SYLLABLE TIKEUT YAE CHIEUCH - 0x88F3: 0xB350, //HANGUL SYLLABLE TIKEUT YAE KHIEUKH - 0x88F4: 0xB351, //HANGUL SYLLABLE TIKEUT YAE THIEUTH - 0x88F5: 0xB352, //HANGUL SYLLABLE TIKEUT YAE PHIEUPH - 0x88F6: 0xB353, //HANGUL SYLLABLE TIKEUT YAE HIEUH - 0x88F7: 0xB357, //HANGUL SYLLABLE TIKEUT EO KIYEOKSIOS - 0x88F8: 0xB359, //HANGUL SYLLABLE TIKEUT EO NIEUNCIEUC - 0x88F9: 0xB35A, //HANGUL SYLLABLE TIKEUT EO NIEUNHIEUH - 0x88FA: 0xB35D, //HANGUL SYLLABLE TIKEUT EO RIEULKIYEOK - 0x88FB: 0xB360, //HANGUL SYLLABLE TIKEUT EO RIEULSIOS - 0x88FC: 0xB361, //HANGUL SYLLABLE TIKEUT EO RIEULTHIEUTH - 0x88FD: 0xB362, //HANGUL SYLLABLE TIKEUT EO RIEULPHIEUPH - 0x88FE: 0xB363, //HANGUL SYLLABLE TIKEUT EO RIEULHIEUH - 0x8941: 0xB366, //HANGUL SYLLABLE TIKEUT EO PIEUPSIOS - 0x8942: 0xB368, //HANGUL SYLLABLE TIKEUT EO SSANGSIOS - 0x8943: 0xB36A, //HANGUL SYLLABLE TIKEUT EO CIEUC - 0x8944: 0xB36C, //HANGUL SYLLABLE TIKEUT EO KHIEUKH - 0x8945: 0xB36D, //HANGUL SYLLABLE TIKEUT EO THIEUTH - 0x8946: 0xB36F, //HANGUL SYLLABLE TIKEUT EO HIEUH - 0x8947: 0xB372, //HANGUL SYLLABLE TIKEUT E SSANGKIYEOK - 0x8948: 0xB373, //HANGUL SYLLABLE TIKEUT E KIYEOKSIOS - 0x8949: 0xB375, //HANGUL SYLLABLE TIKEUT E NIEUNCIEUC - 0x894A: 0xB376, //HANGUL SYLLABLE TIKEUT E NIEUNHIEUH - 0x894B: 0xB377, //HANGUL SYLLABLE TIKEUT E TIKEUT - 0x894C: 0xB379, //HANGUL SYLLABLE TIKEUT E RIEULKIYEOK - 0x894D: 0xB37A, //HANGUL SYLLABLE TIKEUT E RIEULMIEUM - 0x894E: 0xB37B, //HANGUL SYLLABLE TIKEUT E RIEULPIEUP - 0x894F: 0xB37C, //HANGUL SYLLABLE TIKEUT E RIEULSIOS - 0x8950: 0xB37D, //HANGUL SYLLABLE TIKEUT E RIEULTHIEUTH - 0x8951: 0xB37E, //HANGUL SYLLABLE TIKEUT E RIEULPHIEUPH - 0x8952: 0xB37F, //HANGUL SYLLABLE TIKEUT E RIEULHIEUH - 0x8953: 0xB382, //HANGUL SYLLABLE TIKEUT E PIEUPSIOS - 0x8954: 0xB386, //HANGUL SYLLABLE TIKEUT E CIEUC - 0x8955: 0xB387, //HANGUL SYLLABLE TIKEUT E CHIEUCH - 0x8956: 0xB388, //HANGUL SYLLABLE TIKEUT E KHIEUKH - 0x8957: 0xB389, //HANGUL SYLLABLE TIKEUT E THIEUTH - 0x8958: 0xB38A, //HANGUL SYLLABLE TIKEUT E PHIEUPH - 0x8959: 0xB38B, //HANGUL SYLLABLE TIKEUT E HIEUH - 0x895A: 0xB38D, //HANGUL SYLLABLE TIKEUT YEO KIYEOK - 0x8961: 0xB38E, //HANGUL SYLLABLE TIKEUT YEO SSANGKIYEOK - 0x8962: 0xB38F, //HANGUL SYLLABLE TIKEUT YEO KIYEOKSIOS - 0x8963: 0xB391, //HANGUL SYLLABLE TIKEUT YEO NIEUNCIEUC - 0x8964: 0xB392, //HANGUL SYLLABLE TIKEUT YEO NIEUNHIEUH - 0x8965: 0xB393, //HANGUL SYLLABLE TIKEUT YEO TIKEUT - 0x8966: 0xB395, //HANGUL SYLLABLE TIKEUT YEO RIEULKIYEOK - 0x8967: 0xB396, //HANGUL SYLLABLE TIKEUT YEO RIEULMIEUM - 0x8968: 0xB397, //HANGUL SYLLABLE TIKEUT YEO RIEULPIEUP - 0x8969: 0xB398, //HANGUL SYLLABLE TIKEUT YEO RIEULSIOS - 0x896A: 0xB399, //HANGUL SYLLABLE TIKEUT YEO RIEULTHIEUTH - 0x896B: 0xB39A, //HANGUL SYLLABLE TIKEUT YEO RIEULPHIEUPH - 0x896C: 0xB39B, //HANGUL SYLLABLE TIKEUT YEO RIEULHIEUH - 0x896D: 0xB39C, //HANGUL SYLLABLE TIKEUT YEO MIEUM - 0x896E: 0xB39D, //HANGUL SYLLABLE TIKEUT YEO PIEUP - 0x896F: 0xB39E, //HANGUL SYLLABLE TIKEUT YEO PIEUPSIOS - 0x8970: 0xB39F, //HANGUL SYLLABLE TIKEUT YEO SIOS - 0x8971: 0xB3A2, //HANGUL SYLLABLE TIKEUT YEO CIEUC - 0x8972: 0xB3A3, //HANGUL SYLLABLE TIKEUT YEO CHIEUCH - 0x8973: 0xB3A4, //HANGUL SYLLABLE TIKEUT YEO KHIEUKH - 0x8974: 0xB3A5, //HANGUL SYLLABLE TIKEUT YEO THIEUTH - 0x8975: 0xB3A6, //HANGUL SYLLABLE TIKEUT YEO PHIEUPH - 0x8976: 0xB3A7, //HANGUL SYLLABLE TIKEUT YEO HIEUH - 0x8977: 0xB3A9, //HANGUL SYLLABLE TIKEUT YE KIYEOK - 0x8978: 0xB3AA, //HANGUL SYLLABLE TIKEUT YE SSANGKIYEOK - 0x8979: 0xB3AB, //HANGUL SYLLABLE TIKEUT YE KIYEOKSIOS - 0x897A: 0xB3AD, //HANGUL SYLLABLE TIKEUT YE NIEUNCIEUC - 0x8981: 0xB3AE, //HANGUL SYLLABLE TIKEUT YE NIEUNHIEUH - 0x8982: 0xB3AF, //HANGUL SYLLABLE TIKEUT YE TIKEUT - 0x8983: 0xB3B0, //HANGUL SYLLABLE TIKEUT YE RIEUL - 0x8984: 0xB3B1, //HANGUL SYLLABLE TIKEUT YE RIEULKIYEOK - 0x8985: 0xB3B2, //HANGUL SYLLABLE TIKEUT YE RIEULMIEUM - 0x8986: 0xB3B3, //HANGUL SYLLABLE TIKEUT YE RIEULPIEUP - 0x8987: 0xB3B4, //HANGUL SYLLABLE TIKEUT YE RIEULSIOS - 0x8988: 0xB3B5, //HANGUL SYLLABLE TIKEUT YE RIEULTHIEUTH - 0x8989: 0xB3B6, //HANGUL SYLLABLE TIKEUT YE RIEULPHIEUPH - 0x898A: 0xB3B7, //HANGUL SYLLABLE TIKEUT YE RIEULHIEUH - 0x898B: 0xB3B8, //HANGUL SYLLABLE TIKEUT YE MIEUM - 0x898C: 0xB3B9, //HANGUL SYLLABLE TIKEUT YE PIEUP - 0x898D: 0xB3BA, //HANGUL SYLLABLE TIKEUT YE PIEUPSIOS - 0x898E: 0xB3BB, //HANGUL SYLLABLE TIKEUT YE SIOS - 0x898F: 0xB3BC, //HANGUL SYLLABLE TIKEUT YE SSANGSIOS - 0x8990: 0xB3BD, //HANGUL SYLLABLE TIKEUT YE IEUNG - 0x8991: 0xB3BE, //HANGUL SYLLABLE TIKEUT YE CIEUC - 0x8992: 0xB3BF, //HANGUL SYLLABLE TIKEUT YE CHIEUCH - 0x8993: 0xB3C0, //HANGUL SYLLABLE TIKEUT YE KHIEUKH - 0x8994: 0xB3C1, //HANGUL SYLLABLE TIKEUT YE THIEUTH - 0x8995: 0xB3C2, //HANGUL SYLLABLE TIKEUT YE PHIEUPH - 0x8996: 0xB3C3, //HANGUL SYLLABLE TIKEUT YE HIEUH - 0x8997: 0xB3C6, //HANGUL SYLLABLE TIKEUT O SSANGKIYEOK - 0x8998: 0xB3C7, //HANGUL SYLLABLE TIKEUT O KIYEOKSIOS - 0x8999: 0xB3C9, //HANGUL SYLLABLE TIKEUT O NIEUNCIEUC - 0x899A: 0xB3CA, //HANGUL SYLLABLE TIKEUT O NIEUNHIEUH - 0x899B: 0xB3CD, //HANGUL SYLLABLE TIKEUT O RIEULKIYEOK - 0x899C: 0xB3CF, //HANGUL SYLLABLE TIKEUT O RIEULPIEUP - 0x899D: 0xB3D1, //HANGUL SYLLABLE TIKEUT O RIEULTHIEUTH - 0x899E: 0xB3D2, //HANGUL SYLLABLE TIKEUT O RIEULPHIEUPH - 0x899F: 0xB3D3, //HANGUL SYLLABLE TIKEUT O RIEULHIEUH - 0x89A0: 0xB3D6, //HANGUL SYLLABLE TIKEUT O PIEUPSIOS - 0x89A1: 0xB3D8, //HANGUL SYLLABLE TIKEUT O SSANGSIOS - 0x89A2: 0xB3DA, //HANGUL SYLLABLE TIKEUT O CIEUC - 0x89A3: 0xB3DC, //HANGUL SYLLABLE TIKEUT O KHIEUKH - 0x89A4: 0xB3DE, //HANGUL SYLLABLE TIKEUT O PHIEUPH - 0x89A5: 0xB3DF, //HANGUL SYLLABLE TIKEUT O HIEUH - 0x89A6: 0xB3E1, //HANGUL SYLLABLE TIKEUT WA KIYEOK - 0x89A7: 0xB3E2, //HANGUL SYLLABLE TIKEUT WA SSANGKIYEOK - 0x89A8: 0xB3E3, //HANGUL SYLLABLE TIKEUT WA KIYEOKSIOS - 0x89A9: 0xB3E5, //HANGUL SYLLABLE TIKEUT WA NIEUNCIEUC - 0x89AA: 0xB3E6, //HANGUL SYLLABLE TIKEUT WA NIEUNHIEUH - 0x89AB: 0xB3E7, //HANGUL SYLLABLE TIKEUT WA TIKEUT - 0x89AC: 0xB3E9, //HANGUL SYLLABLE TIKEUT WA RIEULKIYEOK - 0x89AD: 0xB3EA, //HANGUL SYLLABLE TIKEUT WA RIEULMIEUM - 0x89AE: 0xB3EB, //HANGUL SYLLABLE TIKEUT WA RIEULPIEUP - 0x89AF: 0xB3EC, //HANGUL SYLLABLE TIKEUT WA RIEULSIOS - 0x89B0: 0xB3ED, //HANGUL SYLLABLE TIKEUT WA RIEULTHIEUTH - 0x89B1: 0xB3EE, //HANGUL SYLLABLE TIKEUT WA RIEULPHIEUPH - 0x89B2: 0xB3EF, //HANGUL SYLLABLE TIKEUT WA RIEULHIEUH - 0x89B3: 0xB3F0, //HANGUL SYLLABLE TIKEUT WA MIEUM - 0x89B4: 0xB3F1, //HANGUL SYLLABLE TIKEUT WA PIEUP - 0x89B5: 0xB3F2, //HANGUL SYLLABLE TIKEUT WA PIEUPSIOS - 0x89B6: 0xB3F3, //HANGUL SYLLABLE TIKEUT WA SIOS - 0x89B7: 0xB3F4, //HANGUL SYLLABLE TIKEUT WA SSANGSIOS - 0x89B8: 0xB3F5, //HANGUL SYLLABLE TIKEUT WA IEUNG - 0x89B9: 0xB3F6, //HANGUL SYLLABLE TIKEUT WA CIEUC - 0x89BA: 0xB3F7, //HANGUL SYLLABLE TIKEUT WA CHIEUCH - 0x89BB: 0xB3F8, //HANGUL SYLLABLE TIKEUT WA KHIEUKH - 0x89BC: 0xB3F9, //HANGUL SYLLABLE TIKEUT WA THIEUTH - 0x89BD: 0xB3FA, //HANGUL SYLLABLE TIKEUT WA PHIEUPH - 0x89BE: 0xB3FB, //HANGUL SYLLABLE TIKEUT WA HIEUH - 0x89BF: 0xB3FD, //HANGUL SYLLABLE TIKEUT WAE KIYEOK - 0x89C0: 0xB3FE, //HANGUL SYLLABLE TIKEUT WAE SSANGKIYEOK - 0x89C1: 0xB3FF, //HANGUL SYLLABLE TIKEUT WAE KIYEOKSIOS - 0x89C2: 0xB400, //HANGUL SYLLABLE TIKEUT WAE NIEUN - 0x89C3: 0xB401, //HANGUL SYLLABLE TIKEUT WAE NIEUNCIEUC - 0x89C4: 0xB402, //HANGUL SYLLABLE TIKEUT WAE NIEUNHIEUH - 0x89C5: 0xB403, //HANGUL SYLLABLE TIKEUT WAE TIKEUT - 0x89C6: 0xB404, //HANGUL SYLLABLE TIKEUT WAE RIEUL - 0x89C7: 0xB405, //HANGUL SYLLABLE TIKEUT WAE RIEULKIYEOK - 0x89C8: 0xB406, //HANGUL SYLLABLE TIKEUT WAE RIEULMIEUM - 0x89C9: 0xB407, //HANGUL SYLLABLE TIKEUT WAE RIEULPIEUP - 0x89CA: 0xB408, //HANGUL SYLLABLE TIKEUT WAE RIEULSIOS - 0x89CB: 0xB409, //HANGUL SYLLABLE TIKEUT WAE RIEULTHIEUTH - 0x89CC: 0xB40A, //HANGUL SYLLABLE TIKEUT WAE RIEULPHIEUPH - 0x89CD: 0xB40B, //HANGUL SYLLABLE TIKEUT WAE RIEULHIEUH - 0x89CE: 0xB40C, //HANGUL SYLLABLE TIKEUT WAE MIEUM - 0x89CF: 0xB40D, //HANGUL SYLLABLE TIKEUT WAE PIEUP - 0x89D0: 0xB40E, //HANGUL SYLLABLE TIKEUT WAE PIEUPSIOS - 0x89D1: 0xB40F, //HANGUL SYLLABLE TIKEUT WAE SIOS - 0x89D2: 0xB411, //HANGUL SYLLABLE TIKEUT WAE IEUNG - 0x89D3: 0xB412, //HANGUL SYLLABLE TIKEUT WAE CIEUC - 0x89D4: 0xB413, //HANGUL SYLLABLE TIKEUT WAE CHIEUCH - 0x89D5: 0xB414, //HANGUL SYLLABLE TIKEUT WAE KHIEUKH - 0x89D6: 0xB415, //HANGUL SYLLABLE TIKEUT WAE THIEUTH - 0x89D7: 0xB416, //HANGUL SYLLABLE TIKEUT WAE PHIEUPH - 0x89D8: 0xB417, //HANGUL SYLLABLE TIKEUT WAE HIEUH - 0x89D9: 0xB419, //HANGUL SYLLABLE TIKEUT OE KIYEOK - 0x89DA: 0xB41A, //HANGUL SYLLABLE TIKEUT OE SSANGKIYEOK - 0x89DB: 0xB41B, //HANGUL SYLLABLE TIKEUT OE KIYEOKSIOS - 0x89DC: 0xB41D, //HANGUL SYLLABLE TIKEUT OE NIEUNCIEUC - 0x89DD: 0xB41E, //HANGUL SYLLABLE TIKEUT OE NIEUNHIEUH - 0x89DE: 0xB41F, //HANGUL SYLLABLE TIKEUT OE TIKEUT - 0x89DF: 0xB421, //HANGUL SYLLABLE TIKEUT OE RIEULKIYEOK - 0x89E0: 0xB422, //HANGUL SYLLABLE TIKEUT OE RIEULMIEUM - 0x89E1: 0xB423, //HANGUL SYLLABLE TIKEUT OE RIEULPIEUP - 0x89E2: 0xB424, //HANGUL SYLLABLE TIKEUT OE RIEULSIOS - 0x89E3: 0xB425, //HANGUL SYLLABLE TIKEUT OE RIEULTHIEUTH - 0x89E4: 0xB426, //HANGUL SYLLABLE TIKEUT OE RIEULPHIEUPH - 0x89E5: 0xB427, //HANGUL SYLLABLE TIKEUT OE RIEULHIEUH - 0x89E6: 0xB42A, //HANGUL SYLLABLE TIKEUT OE PIEUPSIOS - 0x89E7: 0xB42C, //HANGUL SYLLABLE TIKEUT OE SSANGSIOS - 0x89E8: 0xB42D, //HANGUL SYLLABLE TIKEUT OE IEUNG - 0x89E9: 0xB42E, //HANGUL SYLLABLE TIKEUT OE CIEUC - 0x89EA: 0xB42F, //HANGUL SYLLABLE TIKEUT OE CHIEUCH - 0x89EB: 0xB430, //HANGUL SYLLABLE TIKEUT OE KHIEUKH - 0x89EC: 0xB431, //HANGUL SYLLABLE TIKEUT OE THIEUTH - 0x89ED: 0xB432, //HANGUL SYLLABLE TIKEUT OE PHIEUPH - 0x89EE: 0xB433, //HANGUL SYLLABLE TIKEUT OE HIEUH - 0x89EF: 0xB435, //HANGUL SYLLABLE TIKEUT YO KIYEOK - 0x89F0: 0xB436, //HANGUL SYLLABLE TIKEUT YO SSANGKIYEOK - 0x89F1: 0xB437, //HANGUL SYLLABLE TIKEUT YO KIYEOKSIOS - 0x89F2: 0xB438, //HANGUL SYLLABLE TIKEUT YO NIEUN - 0x89F3: 0xB439, //HANGUL SYLLABLE TIKEUT YO NIEUNCIEUC - 0x89F4: 0xB43A, //HANGUL SYLLABLE TIKEUT YO NIEUNHIEUH - 0x89F5: 0xB43B, //HANGUL SYLLABLE TIKEUT YO TIKEUT - 0x89F6: 0xB43C, //HANGUL SYLLABLE TIKEUT YO RIEUL - 0x89F7: 0xB43D, //HANGUL SYLLABLE TIKEUT YO RIEULKIYEOK - 0x89F8: 0xB43E, //HANGUL SYLLABLE TIKEUT YO RIEULMIEUM - 0x89F9: 0xB43F, //HANGUL SYLLABLE TIKEUT YO RIEULPIEUP - 0x89FA: 0xB440, //HANGUL SYLLABLE TIKEUT YO RIEULSIOS - 0x89FB: 0xB441, //HANGUL SYLLABLE TIKEUT YO RIEULTHIEUTH - 0x89FC: 0xB442, //HANGUL SYLLABLE TIKEUT YO RIEULPHIEUPH - 0x89FD: 0xB443, //HANGUL SYLLABLE TIKEUT YO RIEULHIEUH - 0x89FE: 0xB444, //HANGUL SYLLABLE TIKEUT YO MIEUM - 0x8A41: 0xB445, //HANGUL SYLLABLE TIKEUT YO PIEUP - 0x8A42: 0xB446, //HANGUL SYLLABLE TIKEUT YO PIEUPSIOS - 0x8A43: 0xB447, //HANGUL SYLLABLE TIKEUT YO SIOS - 0x8A44: 0xB448, //HANGUL SYLLABLE TIKEUT YO SSANGSIOS - 0x8A45: 0xB449, //HANGUL SYLLABLE TIKEUT YO IEUNG - 0x8A46: 0xB44A, //HANGUL SYLLABLE TIKEUT YO CIEUC - 0x8A47: 0xB44B, //HANGUL SYLLABLE TIKEUT YO CHIEUCH - 0x8A48: 0xB44C, //HANGUL SYLLABLE TIKEUT YO KHIEUKH - 0x8A49: 0xB44D, //HANGUL SYLLABLE TIKEUT YO THIEUTH - 0x8A4A: 0xB44E, //HANGUL SYLLABLE TIKEUT YO PHIEUPH - 0x8A4B: 0xB44F, //HANGUL SYLLABLE TIKEUT YO HIEUH - 0x8A4C: 0xB452, //HANGUL SYLLABLE TIKEUT U SSANGKIYEOK - 0x8A4D: 0xB453, //HANGUL SYLLABLE TIKEUT U KIYEOKSIOS - 0x8A4E: 0xB455, //HANGUL SYLLABLE TIKEUT U NIEUNCIEUC - 0x8A4F: 0xB456, //HANGUL SYLLABLE TIKEUT U NIEUNHIEUH - 0x8A50: 0xB457, //HANGUL SYLLABLE TIKEUT U TIKEUT - 0x8A51: 0xB459, //HANGUL SYLLABLE TIKEUT U RIEULKIYEOK - 0x8A52: 0xB45A, //HANGUL SYLLABLE TIKEUT U RIEULMIEUM - 0x8A53: 0xB45B, //HANGUL SYLLABLE TIKEUT U RIEULPIEUP - 0x8A54: 0xB45C, //HANGUL SYLLABLE TIKEUT U RIEULSIOS - 0x8A55: 0xB45D, //HANGUL SYLLABLE TIKEUT U RIEULTHIEUTH - 0x8A56: 0xB45E, //HANGUL SYLLABLE TIKEUT U RIEULPHIEUPH - 0x8A57: 0xB45F, //HANGUL SYLLABLE TIKEUT U RIEULHIEUH - 0x8A58: 0xB462, //HANGUL SYLLABLE TIKEUT U PIEUPSIOS - 0x8A59: 0xB464, //HANGUL SYLLABLE TIKEUT U SSANGSIOS - 0x8A5A: 0xB466, //HANGUL SYLLABLE TIKEUT U CIEUC - 0x8A61: 0xB467, //HANGUL SYLLABLE TIKEUT U CHIEUCH - 0x8A62: 0xB468, //HANGUL SYLLABLE TIKEUT U KHIEUKH - 0x8A63: 0xB469, //HANGUL SYLLABLE TIKEUT U THIEUTH - 0x8A64: 0xB46A, //HANGUL SYLLABLE TIKEUT U PHIEUPH - 0x8A65: 0xB46B, //HANGUL SYLLABLE TIKEUT U HIEUH - 0x8A66: 0xB46D, //HANGUL SYLLABLE TIKEUT WEO KIYEOK - 0x8A67: 0xB46E, //HANGUL SYLLABLE TIKEUT WEO SSANGKIYEOK - 0x8A68: 0xB46F, //HANGUL SYLLABLE TIKEUT WEO KIYEOKSIOS - 0x8A69: 0xB470, //HANGUL SYLLABLE TIKEUT WEO NIEUN - 0x8A6A: 0xB471, //HANGUL SYLLABLE TIKEUT WEO NIEUNCIEUC - 0x8A6B: 0xB472, //HANGUL SYLLABLE TIKEUT WEO NIEUNHIEUH - 0x8A6C: 0xB473, //HANGUL SYLLABLE TIKEUT WEO TIKEUT - 0x8A6D: 0xB474, //HANGUL SYLLABLE TIKEUT WEO RIEUL - 0x8A6E: 0xB475, //HANGUL SYLLABLE TIKEUT WEO RIEULKIYEOK - 0x8A6F: 0xB476, //HANGUL SYLLABLE TIKEUT WEO RIEULMIEUM - 0x8A70: 0xB477, //HANGUL SYLLABLE TIKEUT WEO RIEULPIEUP - 0x8A71: 0xB478, //HANGUL SYLLABLE TIKEUT WEO RIEULSIOS - 0x8A72: 0xB479, //HANGUL SYLLABLE TIKEUT WEO RIEULTHIEUTH - 0x8A73: 0xB47A, //HANGUL SYLLABLE TIKEUT WEO RIEULPHIEUPH - 0x8A74: 0xB47B, //HANGUL SYLLABLE TIKEUT WEO RIEULHIEUH - 0x8A75: 0xB47C, //HANGUL SYLLABLE TIKEUT WEO MIEUM - 0x8A76: 0xB47D, //HANGUL SYLLABLE TIKEUT WEO PIEUP - 0x8A77: 0xB47E, //HANGUL SYLLABLE TIKEUT WEO PIEUPSIOS - 0x8A78: 0xB47F, //HANGUL SYLLABLE TIKEUT WEO SIOS - 0x8A79: 0xB481, //HANGUL SYLLABLE TIKEUT WEO IEUNG - 0x8A7A: 0xB482, //HANGUL SYLLABLE TIKEUT WEO CIEUC - 0x8A81: 0xB483, //HANGUL SYLLABLE TIKEUT WEO CHIEUCH - 0x8A82: 0xB484, //HANGUL SYLLABLE TIKEUT WEO KHIEUKH - 0x8A83: 0xB485, //HANGUL SYLLABLE TIKEUT WEO THIEUTH - 0x8A84: 0xB486, //HANGUL SYLLABLE TIKEUT WEO PHIEUPH - 0x8A85: 0xB487, //HANGUL SYLLABLE TIKEUT WEO HIEUH - 0x8A86: 0xB489, //HANGUL SYLLABLE TIKEUT WE KIYEOK - 0x8A87: 0xB48A, //HANGUL SYLLABLE TIKEUT WE SSANGKIYEOK - 0x8A88: 0xB48B, //HANGUL SYLLABLE TIKEUT WE KIYEOKSIOS - 0x8A89: 0xB48C, //HANGUL SYLLABLE TIKEUT WE NIEUN - 0x8A8A: 0xB48D, //HANGUL SYLLABLE TIKEUT WE NIEUNCIEUC - 0x8A8B: 0xB48E, //HANGUL SYLLABLE TIKEUT WE NIEUNHIEUH - 0x8A8C: 0xB48F, //HANGUL SYLLABLE TIKEUT WE TIKEUT - 0x8A8D: 0xB490, //HANGUL SYLLABLE TIKEUT WE RIEUL - 0x8A8E: 0xB491, //HANGUL SYLLABLE TIKEUT WE RIEULKIYEOK - 0x8A8F: 0xB492, //HANGUL SYLLABLE TIKEUT WE RIEULMIEUM - 0x8A90: 0xB493, //HANGUL SYLLABLE TIKEUT WE RIEULPIEUP - 0x8A91: 0xB494, //HANGUL SYLLABLE TIKEUT WE RIEULSIOS - 0x8A92: 0xB495, //HANGUL SYLLABLE TIKEUT WE RIEULTHIEUTH - 0x8A93: 0xB496, //HANGUL SYLLABLE TIKEUT WE RIEULPHIEUPH - 0x8A94: 0xB497, //HANGUL SYLLABLE TIKEUT WE RIEULHIEUH - 0x8A95: 0xB498, //HANGUL SYLLABLE TIKEUT WE MIEUM - 0x8A96: 0xB499, //HANGUL SYLLABLE TIKEUT WE PIEUP - 0x8A97: 0xB49A, //HANGUL SYLLABLE TIKEUT WE PIEUPSIOS - 0x8A98: 0xB49B, //HANGUL SYLLABLE TIKEUT WE SIOS - 0x8A99: 0xB49C, //HANGUL SYLLABLE TIKEUT WE SSANGSIOS - 0x8A9A: 0xB49E, //HANGUL SYLLABLE TIKEUT WE CIEUC - 0x8A9B: 0xB49F, //HANGUL SYLLABLE TIKEUT WE CHIEUCH - 0x8A9C: 0xB4A0, //HANGUL SYLLABLE TIKEUT WE KHIEUKH - 0x8A9D: 0xB4A1, //HANGUL SYLLABLE TIKEUT WE THIEUTH - 0x8A9E: 0xB4A2, //HANGUL SYLLABLE TIKEUT WE PHIEUPH - 0x8A9F: 0xB4A3, //HANGUL SYLLABLE TIKEUT WE HIEUH - 0x8AA0: 0xB4A5, //HANGUL SYLLABLE TIKEUT WI KIYEOK - 0x8AA1: 0xB4A6, //HANGUL SYLLABLE TIKEUT WI SSANGKIYEOK - 0x8AA2: 0xB4A7, //HANGUL SYLLABLE TIKEUT WI KIYEOKSIOS - 0x8AA3: 0xB4A9, //HANGUL SYLLABLE TIKEUT WI NIEUNCIEUC - 0x8AA4: 0xB4AA, //HANGUL SYLLABLE TIKEUT WI NIEUNHIEUH - 0x8AA5: 0xB4AB, //HANGUL SYLLABLE TIKEUT WI TIKEUT - 0x8AA6: 0xB4AD, //HANGUL SYLLABLE TIKEUT WI RIEULKIYEOK - 0x8AA7: 0xB4AE, //HANGUL SYLLABLE TIKEUT WI RIEULMIEUM - 0x8AA8: 0xB4AF, //HANGUL SYLLABLE TIKEUT WI RIEULPIEUP - 0x8AA9: 0xB4B0, //HANGUL SYLLABLE TIKEUT WI RIEULSIOS - 0x8AAA: 0xB4B1, //HANGUL SYLLABLE TIKEUT WI RIEULTHIEUTH - 0x8AAB: 0xB4B2, //HANGUL SYLLABLE TIKEUT WI RIEULPHIEUPH - 0x8AAC: 0xB4B3, //HANGUL SYLLABLE TIKEUT WI RIEULHIEUH - 0x8AAD: 0xB4B4, //HANGUL SYLLABLE TIKEUT WI MIEUM - 0x8AAE: 0xB4B6, //HANGUL SYLLABLE TIKEUT WI PIEUPSIOS - 0x8AAF: 0xB4B8, //HANGUL SYLLABLE TIKEUT WI SSANGSIOS - 0x8AB0: 0xB4BA, //HANGUL SYLLABLE TIKEUT WI CIEUC - 0x8AB1: 0xB4BB, //HANGUL SYLLABLE TIKEUT WI CHIEUCH - 0x8AB2: 0xB4BC, //HANGUL SYLLABLE TIKEUT WI KHIEUKH - 0x8AB3: 0xB4BD, //HANGUL SYLLABLE TIKEUT WI THIEUTH - 0x8AB4: 0xB4BE, //HANGUL SYLLABLE TIKEUT WI PHIEUPH - 0x8AB5: 0xB4BF, //HANGUL SYLLABLE TIKEUT WI HIEUH - 0x8AB6: 0xB4C1, //HANGUL SYLLABLE TIKEUT YU KIYEOK - 0x8AB7: 0xB4C2, //HANGUL SYLLABLE TIKEUT YU SSANGKIYEOK - 0x8AB8: 0xB4C3, //HANGUL SYLLABLE TIKEUT YU KIYEOKSIOS - 0x8AB9: 0xB4C5, //HANGUL SYLLABLE TIKEUT YU NIEUNCIEUC - 0x8ABA: 0xB4C6, //HANGUL SYLLABLE TIKEUT YU NIEUNHIEUH - 0x8ABB: 0xB4C7, //HANGUL SYLLABLE TIKEUT YU TIKEUT - 0x8ABC: 0xB4C9, //HANGUL SYLLABLE TIKEUT YU RIEULKIYEOK - 0x8ABD: 0xB4CA, //HANGUL SYLLABLE TIKEUT YU RIEULMIEUM - 0x8ABE: 0xB4CB, //HANGUL SYLLABLE TIKEUT YU RIEULPIEUP - 0x8ABF: 0xB4CC, //HANGUL SYLLABLE TIKEUT YU RIEULSIOS - 0x8AC0: 0xB4CD, //HANGUL SYLLABLE TIKEUT YU RIEULTHIEUTH - 0x8AC1: 0xB4CE, //HANGUL SYLLABLE TIKEUT YU RIEULPHIEUPH - 0x8AC2: 0xB4CF, //HANGUL SYLLABLE TIKEUT YU RIEULHIEUH - 0x8AC3: 0xB4D1, //HANGUL SYLLABLE TIKEUT YU PIEUP - 0x8AC4: 0xB4D2, //HANGUL SYLLABLE TIKEUT YU PIEUPSIOS - 0x8AC5: 0xB4D3, //HANGUL SYLLABLE TIKEUT YU SIOS - 0x8AC6: 0xB4D4, //HANGUL SYLLABLE TIKEUT YU SSANGSIOS - 0x8AC7: 0xB4D6, //HANGUL SYLLABLE TIKEUT YU CIEUC - 0x8AC8: 0xB4D7, //HANGUL SYLLABLE TIKEUT YU CHIEUCH - 0x8AC9: 0xB4D8, //HANGUL SYLLABLE TIKEUT YU KHIEUKH - 0x8ACA: 0xB4D9, //HANGUL SYLLABLE TIKEUT YU THIEUTH - 0x8ACB: 0xB4DA, //HANGUL SYLLABLE TIKEUT YU PHIEUPH - 0x8ACC: 0xB4DB, //HANGUL SYLLABLE TIKEUT YU HIEUH - 0x8ACD: 0xB4DE, //HANGUL SYLLABLE TIKEUT EU SSANGKIYEOK - 0x8ACE: 0xB4DF, //HANGUL SYLLABLE TIKEUT EU KIYEOKSIOS - 0x8ACF: 0xB4E1, //HANGUL SYLLABLE TIKEUT EU NIEUNCIEUC - 0x8AD0: 0xB4E2, //HANGUL SYLLABLE TIKEUT EU NIEUNHIEUH - 0x8AD1: 0xB4E5, //HANGUL SYLLABLE TIKEUT EU RIEULKIYEOK - 0x8AD2: 0xB4E7, //HANGUL SYLLABLE TIKEUT EU RIEULPIEUP - 0x8AD3: 0xB4E8, //HANGUL SYLLABLE TIKEUT EU RIEULSIOS - 0x8AD4: 0xB4E9, //HANGUL SYLLABLE TIKEUT EU RIEULTHIEUTH - 0x8AD5: 0xB4EA, //HANGUL SYLLABLE TIKEUT EU RIEULPHIEUPH - 0x8AD6: 0xB4EB, //HANGUL SYLLABLE TIKEUT EU RIEULHIEUH - 0x8AD7: 0xB4EE, //HANGUL SYLLABLE TIKEUT EU PIEUPSIOS - 0x8AD8: 0xB4F0, //HANGUL SYLLABLE TIKEUT EU SSANGSIOS - 0x8AD9: 0xB4F2, //HANGUL SYLLABLE TIKEUT EU CIEUC - 0x8ADA: 0xB4F3, //HANGUL SYLLABLE TIKEUT EU CHIEUCH - 0x8ADB: 0xB4F4, //HANGUL SYLLABLE TIKEUT EU KHIEUKH - 0x8ADC: 0xB4F5, //HANGUL SYLLABLE TIKEUT EU THIEUTH - 0x8ADD: 0xB4F6, //HANGUL SYLLABLE TIKEUT EU PHIEUPH - 0x8ADE: 0xB4F7, //HANGUL SYLLABLE TIKEUT EU HIEUH - 0x8ADF: 0xB4F9, //HANGUL SYLLABLE TIKEUT YI KIYEOK - 0x8AE0: 0xB4FA, //HANGUL SYLLABLE TIKEUT YI SSANGKIYEOK - 0x8AE1: 0xB4FB, //HANGUL SYLLABLE TIKEUT YI KIYEOKSIOS - 0x8AE2: 0xB4FC, //HANGUL SYLLABLE TIKEUT YI NIEUN - 0x8AE3: 0xB4FD, //HANGUL SYLLABLE TIKEUT YI NIEUNCIEUC - 0x8AE4: 0xB4FE, //HANGUL SYLLABLE TIKEUT YI NIEUNHIEUH - 0x8AE5: 0xB4FF, //HANGUL SYLLABLE TIKEUT YI TIKEUT - 0x8AE6: 0xB500, //HANGUL SYLLABLE TIKEUT YI RIEUL - 0x8AE7: 0xB501, //HANGUL SYLLABLE TIKEUT YI RIEULKIYEOK - 0x8AE8: 0xB502, //HANGUL SYLLABLE TIKEUT YI RIEULMIEUM - 0x8AE9: 0xB503, //HANGUL SYLLABLE TIKEUT YI RIEULPIEUP - 0x8AEA: 0xB504, //HANGUL SYLLABLE TIKEUT YI RIEULSIOS - 0x8AEB: 0xB505, //HANGUL SYLLABLE TIKEUT YI RIEULTHIEUTH - 0x8AEC: 0xB506, //HANGUL SYLLABLE TIKEUT YI RIEULPHIEUPH - 0x8AED: 0xB507, //HANGUL SYLLABLE TIKEUT YI RIEULHIEUH - 0x8AEE: 0xB508, //HANGUL SYLLABLE TIKEUT YI MIEUM - 0x8AEF: 0xB509, //HANGUL SYLLABLE TIKEUT YI PIEUP - 0x8AF0: 0xB50A, //HANGUL SYLLABLE TIKEUT YI PIEUPSIOS - 0x8AF1: 0xB50B, //HANGUL SYLLABLE TIKEUT YI SIOS - 0x8AF2: 0xB50C, //HANGUL SYLLABLE TIKEUT YI SSANGSIOS - 0x8AF3: 0xB50D, //HANGUL SYLLABLE TIKEUT YI IEUNG - 0x8AF4: 0xB50E, //HANGUL SYLLABLE TIKEUT YI CIEUC - 0x8AF5: 0xB50F, //HANGUL SYLLABLE TIKEUT YI CHIEUCH - 0x8AF6: 0xB510, //HANGUL SYLLABLE TIKEUT YI KHIEUKH - 0x8AF7: 0xB511, //HANGUL SYLLABLE TIKEUT YI THIEUTH - 0x8AF8: 0xB512, //HANGUL SYLLABLE TIKEUT YI PHIEUPH - 0x8AF9: 0xB513, //HANGUL SYLLABLE TIKEUT YI HIEUH - 0x8AFA: 0xB516, //HANGUL SYLLABLE TIKEUT I SSANGKIYEOK - 0x8AFB: 0xB517, //HANGUL SYLLABLE TIKEUT I KIYEOKSIOS - 0x8AFC: 0xB519, //HANGUL SYLLABLE TIKEUT I NIEUNCIEUC - 0x8AFD: 0xB51A, //HANGUL SYLLABLE TIKEUT I NIEUNHIEUH - 0x8AFE: 0xB51D, //HANGUL SYLLABLE TIKEUT I RIEULKIYEOK - 0x8B41: 0xB51E, //HANGUL SYLLABLE TIKEUT I RIEULMIEUM - 0x8B42: 0xB51F, //HANGUL SYLLABLE TIKEUT I RIEULPIEUP - 0x8B43: 0xB520, //HANGUL SYLLABLE TIKEUT I RIEULSIOS - 0x8B44: 0xB521, //HANGUL SYLLABLE TIKEUT I RIEULTHIEUTH - 0x8B45: 0xB522, //HANGUL SYLLABLE TIKEUT I RIEULPHIEUPH - 0x8B46: 0xB523, //HANGUL SYLLABLE TIKEUT I RIEULHIEUH - 0x8B47: 0xB526, //HANGUL SYLLABLE TIKEUT I PIEUPSIOS - 0x8B48: 0xB52B, //HANGUL SYLLABLE TIKEUT I CHIEUCH - 0x8B49: 0xB52C, //HANGUL SYLLABLE TIKEUT I KHIEUKH - 0x8B4A: 0xB52D, //HANGUL SYLLABLE TIKEUT I THIEUTH - 0x8B4B: 0xB52E, //HANGUL SYLLABLE TIKEUT I PHIEUPH - 0x8B4C: 0xB52F, //HANGUL SYLLABLE TIKEUT I HIEUH - 0x8B4D: 0xB532, //HANGUL SYLLABLE SSANGTIKEUT A SSANGKIYEOK - 0x8B4E: 0xB533, //HANGUL SYLLABLE SSANGTIKEUT A KIYEOKSIOS - 0x8B4F: 0xB535, //HANGUL SYLLABLE SSANGTIKEUT A NIEUNCIEUC - 0x8B50: 0xB536, //HANGUL SYLLABLE SSANGTIKEUT A NIEUNHIEUH - 0x8B51: 0xB537, //HANGUL SYLLABLE SSANGTIKEUT A TIKEUT - 0x8B52: 0xB539, //HANGUL SYLLABLE SSANGTIKEUT A RIEULKIYEOK - 0x8B53: 0xB53A, //HANGUL SYLLABLE SSANGTIKEUT A RIEULMIEUM - 0x8B54: 0xB53B, //HANGUL SYLLABLE SSANGTIKEUT A RIEULPIEUP - 0x8B55: 0xB53C, //HANGUL SYLLABLE SSANGTIKEUT A RIEULSIOS - 0x8B56: 0xB53D, //HANGUL SYLLABLE SSANGTIKEUT A RIEULTHIEUTH - 0x8B57: 0xB53E, //HANGUL SYLLABLE SSANGTIKEUT A RIEULPHIEUPH - 0x8B58: 0xB53F, //HANGUL SYLLABLE SSANGTIKEUT A RIEULHIEUH - 0x8B59: 0xB542, //HANGUL SYLLABLE SSANGTIKEUT A PIEUPSIOS - 0x8B5A: 0xB546, //HANGUL SYLLABLE SSANGTIKEUT A CIEUC - 0x8B61: 0xB547, //HANGUL SYLLABLE SSANGTIKEUT A CHIEUCH - 0x8B62: 0xB548, //HANGUL SYLLABLE SSANGTIKEUT A KHIEUKH - 0x8B63: 0xB549, //HANGUL SYLLABLE SSANGTIKEUT A THIEUTH - 0x8B64: 0xB54A, //HANGUL SYLLABLE SSANGTIKEUT A PHIEUPH - 0x8B65: 0xB54E, //HANGUL SYLLABLE SSANGTIKEUT AE SSANGKIYEOK - 0x8B66: 0xB54F, //HANGUL SYLLABLE SSANGTIKEUT AE KIYEOKSIOS - 0x8B67: 0xB551, //HANGUL SYLLABLE SSANGTIKEUT AE NIEUNCIEUC - 0x8B68: 0xB552, //HANGUL SYLLABLE SSANGTIKEUT AE NIEUNHIEUH - 0x8B69: 0xB553, //HANGUL SYLLABLE SSANGTIKEUT AE TIKEUT - 0x8B6A: 0xB555, //HANGUL SYLLABLE SSANGTIKEUT AE RIEULKIYEOK - 0x8B6B: 0xB556, //HANGUL SYLLABLE SSANGTIKEUT AE RIEULMIEUM - 0x8B6C: 0xB557, //HANGUL SYLLABLE SSANGTIKEUT AE RIEULPIEUP - 0x8B6D: 0xB558, //HANGUL SYLLABLE SSANGTIKEUT AE RIEULSIOS - 0x8B6E: 0xB559, //HANGUL SYLLABLE SSANGTIKEUT AE RIEULTHIEUTH - 0x8B6F: 0xB55A, //HANGUL SYLLABLE SSANGTIKEUT AE RIEULPHIEUPH - 0x8B70: 0xB55B, //HANGUL SYLLABLE SSANGTIKEUT AE RIEULHIEUH - 0x8B71: 0xB55E, //HANGUL SYLLABLE SSANGTIKEUT AE PIEUPSIOS - 0x8B72: 0xB562, //HANGUL SYLLABLE SSANGTIKEUT AE CIEUC - 0x8B73: 0xB563, //HANGUL SYLLABLE SSANGTIKEUT AE CHIEUCH - 0x8B74: 0xB564, //HANGUL SYLLABLE SSANGTIKEUT AE KHIEUKH - 0x8B75: 0xB565, //HANGUL SYLLABLE SSANGTIKEUT AE THIEUTH - 0x8B76: 0xB566, //HANGUL SYLLABLE SSANGTIKEUT AE PHIEUPH - 0x8B77: 0xB567, //HANGUL SYLLABLE SSANGTIKEUT AE HIEUH - 0x8B78: 0xB568, //HANGUL SYLLABLE SSANGTIKEUT YA - 0x8B79: 0xB569, //HANGUL SYLLABLE SSANGTIKEUT YA KIYEOK - 0x8B7A: 0xB56A, //HANGUL SYLLABLE SSANGTIKEUT YA SSANGKIYEOK - 0x8B81: 0xB56B, //HANGUL SYLLABLE SSANGTIKEUT YA KIYEOKSIOS - 0x8B82: 0xB56C, //HANGUL SYLLABLE SSANGTIKEUT YA NIEUN - 0x8B83: 0xB56D, //HANGUL SYLLABLE SSANGTIKEUT YA NIEUNCIEUC - 0x8B84: 0xB56E, //HANGUL SYLLABLE SSANGTIKEUT YA NIEUNHIEUH - 0x8B85: 0xB56F, //HANGUL SYLLABLE SSANGTIKEUT YA TIKEUT - 0x8B86: 0xB570, //HANGUL SYLLABLE SSANGTIKEUT YA RIEUL - 0x8B87: 0xB571, //HANGUL SYLLABLE SSANGTIKEUT YA RIEULKIYEOK - 0x8B88: 0xB572, //HANGUL SYLLABLE SSANGTIKEUT YA RIEULMIEUM - 0x8B89: 0xB573, //HANGUL SYLLABLE SSANGTIKEUT YA RIEULPIEUP - 0x8B8A: 0xB574, //HANGUL SYLLABLE SSANGTIKEUT YA RIEULSIOS - 0x8B8B: 0xB575, //HANGUL SYLLABLE SSANGTIKEUT YA RIEULTHIEUTH - 0x8B8C: 0xB576, //HANGUL SYLLABLE SSANGTIKEUT YA RIEULPHIEUPH - 0x8B8D: 0xB577, //HANGUL SYLLABLE SSANGTIKEUT YA RIEULHIEUH - 0x8B8E: 0xB578, //HANGUL SYLLABLE SSANGTIKEUT YA MIEUM - 0x8B8F: 0xB579, //HANGUL SYLLABLE SSANGTIKEUT YA PIEUP - 0x8B90: 0xB57A, //HANGUL SYLLABLE SSANGTIKEUT YA PIEUPSIOS - 0x8B91: 0xB57B, //HANGUL SYLLABLE SSANGTIKEUT YA SIOS - 0x8B92: 0xB57C, //HANGUL SYLLABLE SSANGTIKEUT YA SSANGSIOS - 0x8B93: 0xB57D, //HANGUL SYLLABLE SSANGTIKEUT YA IEUNG - 0x8B94: 0xB57E, //HANGUL SYLLABLE SSANGTIKEUT YA CIEUC - 0x8B95: 0xB57F, //HANGUL SYLLABLE SSANGTIKEUT YA CHIEUCH - 0x8B96: 0xB580, //HANGUL SYLLABLE SSANGTIKEUT YA KHIEUKH - 0x8B97: 0xB581, //HANGUL SYLLABLE SSANGTIKEUT YA THIEUTH - 0x8B98: 0xB582, //HANGUL SYLLABLE SSANGTIKEUT YA PHIEUPH - 0x8B99: 0xB583, //HANGUL SYLLABLE SSANGTIKEUT YA HIEUH - 0x8B9A: 0xB584, //HANGUL SYLLABLE SSANGTIKEUT YAE - 0x8B9B: 0xB585, //HANGUL SYLLABLE SSANGTIKEUT YAE KIYEOK - 0x8B9C: 0xB586, //HANGUL SYLLABLE SSANGTIKEUT YAE SSANGKIYEOK - 0x8B9D: 0xB587, //HANGUL SYLLABLE SSANGTIKEUT YAE KIYEOKSIOS - 0x8B9E: 0xB588, //HANGUL SYLLABLE SSANGTIKEUT YAE NIEUN - 0x8B9F: 0xB589, //HANGUL SYLLABLE SSANGTIKEUT YAE NIEUNCIEUC - 0x8BA0: 0xB58A, //HANGUL SYLLABLE SSANGTIKEUT YAE NIEUNHIEUH - 0x8BA1: 0xB58B, //HANGUL SYLLABLE SSANGTIKEUT YAE TIKEUT - 0x8BA2: 0xB58C, //HANGUL SYLLABLE SSANGTIKEUT YAE RIEUL - 0x8BA3: 0xB58D, //HANGUL SYLLABLE SSANGTIKEUT YAE RIEULKIYEOK - 0x8BA4: 0xB58E, //HANGUL SYLLABLE SSANGTIKEUT YAE RIEULMIEUM - 0x8BA5: 0xB58F, //HANGUL SYLLABLE SSANGTIKEUT YAE RIEULPIEUP - 0x8BA6: 0xB590, //HANGUL SYLLABLE SSANGTIKEUT YAE RIEULSIOS - 0x8BA7: 0xB591, //HANGUL SYLLABLE SSANGTIKEUT YAE RIEULTHIEUTH - 0x8BA8: 0xB592, //HANGUL SYLLABLE SSANGTIKEUT YAE RIEULPHIEUPH - 0x8BA9: 0xB593, //HANGUL SYLLABLE SSANGTIKEUT YAE RIEULHIEUH - 0x8BAA: 0xB594, //HANGUL SYLLABLE SSANGTIKEUT YAE MIEUM - 0x8BAB: 0xB595, //HANGUL SYLLABLE SSANGTIKEUT YAE PIEUP - 0x8BAC: 0xB596, //HANGUL SYLLABLE SSANGTIKEUT YAE PIEUPSIOS - 0x8BAD: 0xB597, //HANGUL SYLLABLE SSANGTIKEUT YAE SIOS - 0x8BAE: 0xB598, //HANGUL SYLLABLE SSANGTIKEUT YAE SSANGSIOS - 0x8BAF: 0xB599, //HANGUL SYLLABLE SSANGTIKEUT YAE IEUNG - 0x8BB0: 0xB59A, //HANGUL SYLLABLE SSANGTIKEUT YAE CIEUC - 0x8BB1: 0xB59B, //HANGUL SYLLABLE SSANGTIKEUT YAE CHIEUCH - 0x8BB2: 0xB59C, //HANGUL SYLLABLE SSANGTIKEUT YAE KHIEUKH - 0x8BB3: 0xB59D, //HANGUL SYLLABLE SSANGTIKEUT YAE THIEUTH - 0x8BB4: 0xB59E, //HANGUL SYLLABLE SSANGTIKEUT YAE PHIEUPH - 0x8BB5: 0xB59F, //HANGUL SYLLABLE SSANGTIKEUT YAE HIEUH - 0x8BB6: 0xB5A2, //HANGUL SYLLABLE SSANGTIKEUT EO SSANGKIYEOK - 0x8BB7: 0xB5A3, //HANGUL SYLLABLE SSANGTIKEUT EO KIYEOKSIOS - 0x8BB8: 0xB5A5, //HANGUL SYLLABLE SSANGTIKEUT EO NIEUNCIEUC - 0x8BB9: 0xB5A6, //HANGUL SYLLABLE SSANGTIKEUT EO NIEUNHIEUH - 0x8BBA: 0xB5A7, //HANGUL SYLLABLE SSANGTIKEUT EO TIKEUT - 0x8BBB: 0xB5A9, //HANGUL SYLLABLE SSANGTIKEUT EO RIEULKIYEOK - 0x8BBC: 0xB5AC, //HANGUL SYLLABLE SSANGTIKEUT EO RIEULSIOS - 0x8BBD: 0xB5AD, //HANGUL SYLLABLE SSANGTIKEUT EO RIEULTHIEUTH - 0x8BBE: 0xB5AE, //HANGUL SYLLABLE SSANGTIKEUT EO RIEULPHIEUPH - 0x8BBF: 0xB5AF, //HANGUL SYLLABLE SSANGTIKEUT EO RIEULHIEUH - 0x8BC0: 0xB5B2, //HANGUL SYLLABLE SSANGTIKEUT EO PIEUPSIOS - 0x8BC1: 0xB5B6, //HANGUL SYLLABLE SSANGTIKEUT EO CIEUC - 0x8BC2: 0xB5B7, //HANGUL SYLLABLE SSANGTIKEUT EO CHIEUCH - 0x8BC3: 0xB5B8, //HANGUL SYLLABLE SSANGTIKEUT EO KHIEUKH - 0x8BC4: 0xB5B9, //HANGUL SYLLABLE SSANGTIKEUT EO THIEUTH - 0x8BC5: 0xB5BA, //HANGUL SYLLABLE SSANGTIKEUT EO PHIEUPH - 0x8BC6: 0xB5BE, //HANGUL SYLLABLE SSANGTIKEUT E SSANGKIYEOK - 0x8BC7: 0xB5BF, //HANGUL SYLLABLE SSANGTIKEUT E KIYEOKSIOS - 0x8BC8: 0xB5C1, //HANGUL SYLLABLE SSANGTIKEUT E NIEUNCIEUC - 0x8BC9: 0xB5C2, //HANGUL SYLLABLE SSANGTIKEUT E NIEUNHIEUH - 0x8BCA: 0xB5C3, //HANGUL SYLLABLE SSANGTIKEUT E TIKEUT - 0x8BCB: 0xB5C5, //HANGUL SYLLABLE SSANGTIKEUT E RIEULKIYEOK - 0x8BCC: 0xB5C6, //HANGUL SYLLABLE SSANGTIKEUT E RIEULMIEUM - 0x8BCD: 0xB5C7, //HANGUL SYLLABLE SSANGTIKEUT E RIEULPIEUP - 0x8BCE: 0xB5C8, //HANGUL SYLLABLE SSANGTIKEUT E RIEULSIOS - 0x8BCF: 0xB5C9, //HANGUL SYLLABLE SSANGTIKEUT E RIEULTHIEUTH - 0x8BD0: 0xB5CA, //HANGUL SYLLABLE SSANGTIKEUT E RIEULPHIEUPH - 0x8BD1: 0xB5CB, //HANGUL SYLLABLE SSANGTIKEUT E RIEULHIEUH - 0x8BD2: 0xB5CE, //HANGUL SYLLABLE SSANGTIKEUT E PIEUPSIOS - 0x8BD3: 0xB5D2, //HANGUL SYLLABLE SSANGTIKEUT E CIEUC - 0x8BD4: 0xB5D3, //HANGUL SYLLABLE SSANGTIKEUT E CHIEUCH - 0x8BD5: 0xB5D4, //HANGUL SYLLABLE SSANGTIKEUT E KHIEUKH - 0x8BD6: 0xB5D5, //HANGUL SYLLABLE SSANGTIKEUT E THIEUTH - 0x8BD7: 0xB5D6, //HANGUL SYLLABLE SSANGTIKEUT E PHIEUPH - 0x8BD8: 0xB5D7, //HANGUL SYLLABLE SSANGTIKEUT E HIEUH - 0x8BD9: 0xB5D9, //HANGUL SYLLABLE SSANGTIKEUT YEO KIYEOK - 0x8BDA: 0xB5DA, //HANGUL SYLLABLE SSANGTIKEUT YEO SSANGKIYEOK - 0x8BDB: 0xB5DB, //HANGUL SYLLABLE SSANGTIKEUT YEO KIYEOKSIOS - 0x8BDC: 0xB5DC, //HANGUL SYLLABLE SSANGTIKEUT YEO NIEUN - 0x8BDD: 0xB5DD, //HANGUL SYLLABLE SSANGTIKEUT YEO NIEUNCIEUC - 0x8BDE: 0xB5DE, //HANGUL SYLLABLE SSANGTIKEUT YEO NIEUNHIEUH - 0x8BDF: 0xB5DF, //HANGUL SYLLABLE SSANGTIKEUT YEO TIKEUT - 0x8BE0: 0xB5E0, //HANGUL SYLLABLE SSANGTIKEUT YEO RIEUL - 0x8BE1: 0xB5E1, //HANGUL SYLLABLE SSANGTIKEUT YEO RIEULKIYEOK - 0x8BE2: 0xB5E2, //HANGUL SYLLABLE SSANGTIKEUT YEO RIEULMIEUM - 0x8BE3: 0xB5E3, //HANGUL SYLLABLE SSANGTIKEUT YEO RIEULPIEUP - 0x8BE4: 0xB5E4, //HANGUL SYLLABLE SSANGTIKEUT YEO RIEULSIOS - 0x8BE5: 0xB5E5, //HANGUL SYLLABLE SSANGTIKEUT YEO RIEULTHIEUTH - 0x8BE6: 0xB5E6, //HANGUL SYLLABLE SSANGTIKEUT YEO RIEULPHIEUPH - 0x8BE7: 0xB5E7, //HANGUL SYLLABLE SSANGTIKEUT YEO RIEULHIEUH - 0x8BE8: 0xB5E8, //HANGUL SYLLABLE SSANGTIKEUT YEO MIEUM - 0x8BE9: 0xB5E9, //HANGUL SYLLABLE SSANGTIKEUT YEO PIEUP - 0x8BEA: 0xB5EA, //HANGUL SYLLABLE SSANGTIKEUT YEO PIEUPSIOS - 0x8BEB: 0xB5EB, //HANGUL SYLLABLE SSANGTIKEUT YEO SIOS - 0x8BEC: 0xB5ED, //HANGUL SYLLABLE SSANGTIKEUT YEO IEUNG - 0x8BED: 0xB5EE, //HANGUL SYLLABLE SSANGTIKEUT YEO CIEUC - 0x8BEE: 0xB5EF, //HANGUL SYLLABLE SSANGTIKEUT YEO CHIEUCH - 0x8BEF: 0xB5F0, //HANGUL SYLLABLE SSANGTIKEUT YEO KHIEUKH - 0x8BF0: 0xB5F1, //HANGUL SYLLABLE SSANGTIKEUT YEO THIEUTH - 0x8BF1: 0xB5F2, //HANGUL SYLLABLE SSANGTIKEUT YEO PHIEUPH - 0x8BF2: 0xB5F3, //HANGUL SYLLABLE SSANGTIKEUT YEO HIEUH - 0x8BF3: 0xB5F4, //HANGUL SYLLABLE SSANGTIKEUT YE - 0x8BF4: 0xB5F5, //HANGUL SYLLABLE SSANGTIKEUT YE KIYEOK - 0x8BF5: 0xB5F6, //HANGUL SYLLABLE SSANGTIKEUT YE SSANGKIYEOK - 0x8BF6: 0xB5F7, //HANGUL SYLLABLE SSANGTIKEUT YE KIYEOKSIOS - 0x8BF7: 0xB5F8, //HANGUL SYLLABLE SSANGTIKEUT YE NIEUN - 0x8BF8: 0xB5F9, //HANGUL SYLLABLE SSANGTIKEUT YE NIEUNCIEUC - 0x8BF9: 0xB5FA, //HANGUL SYLLABLE SSANGTIKEUT YE NIEUNHIEUH - 0x8BFA: 0xB5FB, //HANGUL SYLLABLE SSANGTIKEUT YE TIKEUT - 0x8BFB: 0xB5FC, //HANGUL SYLLABLE SSANGTIKEUT YE RIEUL - 0x8BFC: 0xB5FD, //HANGUL SYLLABLE SSANGTIKEUT YE RIEULKIYEOK - 0x8BFD: 0xB5FE, //HANGUL SYLLABLE SSANGTIKEUT YE RIEULMIEUM - 0x8BFE: 0xB5FF, //HANGUL SYLLABLE SSANGTIKEUT YE RIEULPIEUP - 0x8C41: 0xB600, //HANGUL SYLLABLE SSANGTIKEUT YE RIEULSIOS - 0x8C42: 0xB601, //HANGUL SYLLABLE SSANGTIKEUT YE RIEULTHIEUTH - 0x8C43: 0xB602, //HANGUL SYLLABLE SSANGTIKEUT YE RIEULPHIEUPH - 0x8C44: 0xB603, //HANGUL SYLLABLE SSANGTIKEUT YE RIEULHIEUH - 0x8C45: 0xB604, //HANGUL SYLLABLE SSANGTIKEUT YE MIEUM - 0x8C46: 0xB605, //HANGUL SYLLABLE SSANGTIKEUT YE PIEUP - 0x8C47: 0xB606, //HANGUL SYLLABLE SSANGTIKEUT YE PIEUPSIOS - 0x8C48: 0xB607, //HANGUL SYLLABLE SSANGTIKEUT YE SIOS - 0x8C49: 0xB608, //HANGUL SYLLABLE SSANGTIKEUT YE SSANGSIOS - 0x8C4A: 0xB609, //HANGUL SYLLABLE SSANGTIKEUT YE IEUNG - 0x8C4B: 0xB60A, //HANGUL SYLLABLE SSANGTIKEUT YE CIEUC - 0x8C4C: 0xB60B, //HANGUL SYLLABLE SSANGTIKEUT YE CHIEUCH - 0x8C4D: 0xB60C, //HANGUL SYLLABLE SSANGTIKEUT YE KHIEUKH - 0x8C4E: 0xB60D, //HANGUL SYLLABLE SSANGTIKEUT YE THIEUTH - 0x8C4F: 0xB60E, //HANGUL SYLLABLE SSANGTIKEUT YE PHIEUPH - 0x8C50: 0xB60F, //HANGUL SYLLABLE SSANGTIKEUT YE HIEUH - 0x8C51: 0xB612, //HANGUL SYLLABLE SSANGTIKEUT O SSANGKIYEOK - 0x8C52: 0xB613, //HANGUL SYLLABLE SSANGTIKEUT O KIYEOKSIOS - 0x8C53: 0xB615, //HANGUL SYLLABLE SSANGTIKEUT O NIEUNCIEUC - 0x8C54: 0xB616, //HANGUL SYLLABLE SSANGTIKEUT O NIEUNHIEUH - 0x8C55: 0xB617, //HANGUL SYLLABLE SSANGTIKEUT O TIKEUT - 0x8C56: 0xB619, //HANGUL SYLLABLE SSANGTIKEUT O RIEULKIYEOK - 0x8C57: 0xB61A, //HANGUL SYLLABLE SSANGTIKEUT O RIEULMIEUM - 0x8C58: 0xB61B, //HANGUL SYLLABLE SSANGTIKEUT O RIEULPIEUP - 0x8C59: 0xB61C, //HANGUL SYLLABLE SSANGTIKEUT O RIEULSIOS - 0x8C5A: 0xB61D, //HANGUL SYLLABLE SSANGTIKEUT O RIEULTHIEUTH - 0x8C61: 0xB61E, //HANGUL SYLLABLE SSANGTIKEUT O RIEULPHIEUPH - 0x8C62: 0xB61F, //HANGUL SYLLABLE SSANGTIKEUT O RIEULHIEUH - 0x8C63: 0xB620, //HANGUL SYLLABLE SSANGTIKEUT O MIEUM - 0x8C64: 0xB621, //HANGUL SYLLABLE SSANGTIKEUT O PIEUP - 0x8C65: 0xB622, //HANGUL SYLLABLE SSANGTIKEUT O PIEUPSIOS - 0x8C66: 0xB623, //HANGUL SYLLABLE SSANGTIKEUT O SIOS - 0x8C67: 0xB624, //HANGUL SYLLABLE SSANGTIKEUT O SSANGSIOS - 0x8C68: 0xB626, //HANGUL SYLLABLE SSANGTIKEUT O CIEUC - 0x8C69: 0xB627, //HANGUL SYLLABLE SSANGTIKEUT O CHIEUCH - 0x8C6A: 0xB628, //HANGUL SYLLABLE SSANGTIKEUT O KHIEUKH - 0x8C6B: 0xB629, //HANGUL SYLLABLE SSANGTIKEUT O THIEUTH - 0x8C6C: 0xB62A, //HANGUL SYLLABLE SSANGTIKEUT O PHIEUPH - 0x8C6D: 0xB62B, //HANGUL SYLLABLE SSANGTIKEUT O HIEUH - 0x8C6E: 0xB62D, //HANGUL SYLLABLE SSANGTIKEUT WA KIYEOK - 0x8C6F: 0xB62E, //HANGUL SYLLABLE SSANGTIKEUT WA SSANGKIYEOK - 0x8C70: 0xB62F, //HANGUL SYLLABLE SSANGTIKEUT WA KIYEOKSIOS - 0x8C71: 0xB630, //HANGUL SYLLABLE SSANGTIKEUT WA NIEUN - 0x8C72: 0xB631, //HANGUL SYLLABLE SSANGTIKEUT WA NIEUNCIEUC - 0x8C73: 0xB632, //HANGUL SYLLABLE SSANGTIKEUT WA NIEUNHIEUH - 0x8C74: 0xB633, //HANGUL SYLLABLE SSANGTIKEUT WA TIKEUT - 0x8C75: 0xB635, //HANGUL SYLLABLE SSANGTIKEUT WA RIEULKIYEOK - 0x8C76: 0xB636, //HANGUL SYLLABLE SSANGTIKEUT WA RIEULMIEUM - 0x8C77: 0xB637, //HANGUL SYLLABLE SSANGTIKEUT WA RIEULPIEUP - 0x8C78: 0xB638, //HANGUL SYLLABLE SSANGTIKEUT WA RIEULSIOS - 0x8C79: 0xB639, //HANGUL SYLLABLE SSANGTIKEUT WA RIEULTHIEUTH - 0x8C7A: 0xB63A, //HANGUL SYLLABLE SSANGTIKEUT WA RIEULPHIEUPH - 0x8C81: 0xB63B, //HANGUL SYLLABLE SSANGTIKEUT WA RIEULHIEUH - 0x8C82: 0xB63C, //HANGUL SYLLABLE SSANGTIKEUT WA MIEUM - 0x8C83: 0xB63D, //HANGUL SYLLABLE SSANGTIKEUT WA PIEUP - 0x8C84: 0xB63E, //HANGUL SYLLABLE SSANGTIKEUT WA PIEUPSIOS - 0x8C85: 0xB63F, //HANGUL SYLLABLE SSANGTIKEUT WA SIOS - 0x8C86: 0xB640, //HANGUL SYLLABLE SSANGTIKEUT WA SSANGSIOS - 0x8C87: 0xB641, //HANGUL SYLLABLE SSANGTIKEUT WA IEUNG - 0x8C88: 0xB642, //HANGUL SYLLABLE SSANGTIKEUT WA CIEUC - 0x8C89: 0xB643, //HANGUL SYLLABLE SSANGTIKEUT WA CHIEUCH - 0x8C8A: 0xB644, //HANGUL SYLLABLE SSANGTIKEUT WA KHIEUKH - 0x8C8B: 0xB645, //HANGUL SYLLABLE SSANGTIKEUT WA THIEUTH - 0x8C8C: 0xB646, //HANGUL SYLLABLE SSANGTIKEUT WA PHIEUPH - 0x8C8D: 0xB647, //HANGUL SYLLABLE SSANGTIKEUT WA HIEUH - 0x8C8E: 0xB649, //HANGUL SYLLABLE SSANGTIKEUT WAE KIYEOK - 0x8C8F: 0xB64A, //HANGUL SYLLABLE SSANGTIKEUT WAE SSANGKIYEOK - 0x8C90: 0xB64B, //HANGUL SYLLABLE SSANGTIKEUT WAE KIYEOKSIOS - 0x8C91: 0xB64C, //HANGUL SYLLABLE SSANGTIKEUT WAE NIEUN - 0x8C92: 0xB64D, //HANGUL SYLLABLE SSANGTIKEUT WAE NIEUNCIEUC - 0x8C93: 0xB64E, //HANGUL SYLLABLE SSANGTIKEUT WAE NIEUNHIEUH - 0x8C94: 0xB64F, //HANGUL SYLLABLE SSANGTIKEUT WAE TIKEUT - 0x8C95: 0xB650, //HANGUL SYLLABLE SSANGTIKEUT WAE RIEUL - 0x8C96: 0xB651, //HANGUL SYLLABLE SSANGTIKEUT WAE RIEULKIYEOK - 0x8C97: 0xB652, //HANGUL SYLLABLE SSANGTIKEUT WAE RIEULMIEUM - 0x8C98: 0xB653, //HANGUL SYLLABLE SSANGTIKEUT WAE RIEULPIEUP - 0x8C99: 0xB654, //HANGUL SYLLABLE SSANGTIKEUT WAE RIEULSIOS - 0x8C9A: 0xB655, //HANGUL SYLLABLE SSANGTIKEUT WAE RIEULTHIEUTH - 0x8C9B: 0xB656, //HANGUL SYLLABLE SSANGTIKEUT WAE RIEULPHIEUPH - 0x8C9C: 0xB657, //HANGUL SYLLABLE SSANGTIKEUT WAE RIEULHIEUH - 0x8C9D: 0xB658, //HANGUL SYLLABLE SSANGTIKEUT WAE MIEUM - 0x8C9E: 0xB659, //HANGUL SYLLABLE SSANGTIKEUT WAE PIEUP - 0x8C9F: 0xB65A, //HANGUL SYLLABLE SSANGTIKEUT WAE PIEUPSIOS - 0x8CA0: 0xB65B, //HANGUL SYLLABLE SSANGTIKEUT WAE SIOS - 0x8CA1: 0xB65C, //HANGUL SYLLABLE SSANGTIKEUT WAE SSANGSIOS - 0x8CA2: 0xB65D, //HANGUL SYLLABLE SSANGTIKEUT WAE IEUNG - 0x8CA3: 0xB65E, //HANGUL SYLLABLE SSANGTIKEUT WAE CIEUC - 0x8CA4: 0xB65F, //HANGUL SYLLABLE SSANGTIKEUT WAE CHIEUCH - 0x8CA5: 0xB660, //HANGUL SYLLABLE SSANGTIKEUT WAE KHIEUKH - 0x8CA6: 0xB661, //HANGUL SYLLABLE SSANGTIKEUT WAE THIEUTH - 0x8CA7: 0xB662, //HANGUL SYLLABLE SSANGTIKEUT WAE PHIEUPH - 0x8CA8: 0xB663, //HANGUL SYLLABLE SSANGTIKEUT WAE HIEUH - 0x8CA9: 0xB665, //HANGUL SYLLABLE SSANGTIKEUT OE KIYEOK - 0x8CAA: 0xB666, //HANGUL SYLLABLE SSANGTIKEUT OE SSANGKIYEOK - 0x8CAB: 0xB667, //HANGUL SYLLABLE SSANGTIKEUT OE KIYEOKSIOS - 0x8CAC: 0xB669, //HANGUL SYLLABLE SSANGTIKEUT OE NIEUNCIEUC - 0x8CAD: 0xB66A, //HANGUL SYLLABLE SSANGTIKEUT OE NIEUNHIEUH - 0x8CAE: 0xB66B, //HANGUL SYLLABLE SSANGTIKEUT OE TIKEUT - 0x8CAF: 0xB66C, //HANGUL SYLLABLE SSANGTIKEUT OE RIEUL - 0x8CB0: 0xB66D, //HANGUL SYLLABLE SSANGTIKEUT OE RIEULKIYEOK - 0x8CB1: 0xB66E, //HANGUL SYLLABLE SSANGTIKEUT OE RIEULMIEUM - 0x8CB2: 0xB66F, //HANGUL SYLLABLE SSANGTIKEUT OE RIEULPIEUP - 0x8CB3: 0xB670, //HANGUL SYLLABLE SSANGTIKEUT OE RIEULSIOS - 0x8CB4: 0xB671, //HANGUL SYLLABLE SSANGTIKEUT OE RIEULTHIEUTH - 0x8CB5: 0xB672, //HANGUL SYLLABLE SSANGTIKEUT OE RIEULPHIEUPH - 0x8CB6: 0xB673, //HANGUL SYLLABLE SSANGTIKEUT OE RIEULHIEUH - 0x8CB7: 0xB674, //HANGUL SYLLABLE SSANGTIKEUT OE MIEUM - 0x8CB8: 0xB675, //HANGUL SYLLABLE SSANGTIKEUT OE PIEUP - 0x8CB9: 0xB676, //HANGUL SYLLABLE SSANGTIKEUT OE PIEUPSIOS - 0x8CBA: 0xB677, //HANGUL SYLLABLE SSANGTIKEUT OE SIOS - 0x8CBB: 0xB678, //HANGUL SYLLABLE SSANGTIKEUT OE SSANGSIOS - 0x8CBC: 0xB679, //HANGUL SYLLABLE SSANGTIKEUT OE IEUNG - 0x8CBD: 0xB67A, //HANGUL SYLLABLE SSANGTIKEUT OE CIEUC - 0x8CBE: 0xB67B, //HANGUL SYLLABLE SSANGTIKEUT OE CHIEUCH - 0x8CBF: 0xB67C, //HANGUL SYLLABLE SSANGTIKEUT OE KHIEUKH - 0x8CC0: 0xB67D, //HANGUL SYLLABLE SSANGTIKEUT OE THIEUTH - 0x8CC1: 0xB67E, //HANGUL SYLLABLE SSANGTIKEUT OE PHIEUPH - 0x8CC2: 0xB67F, //HANGUL SYLLABLE SSANGTIKEUT OE HIEUH - 0x8CC3: 0xB680, //HANGUL SYLLABLE SSANGTIKEUT YO - 0x8CC4: 0xB681, //HANGUL SYLLABLE SSANGTIKEUT YO KIYEOK - 0x8CC5: 0xB682, //HANGUL SYLLABLE SSANGTIKEUT YO SSANGKIYEOK - 0x8CC6: 0xB683, //HANGUL SYLLABLE SSANGTIKEUT YO KIYEOKSIOS - 0x8CC7: 0xB684, //HANGUL SYLLABLE SSANGTIKEUT YO NIEUN - 0x8CC8: 0xB685, //HANGUL SYLLABLE SSANGTIKEUT YO NIEUNCIEUC - 0x8CC9: 0xB686, //HANGUL SYLLABLE SSANGTIKEUT YO NIEUNHIEUH - 0x8CCA: 0xB687, //HANGUL SYLLABLE SSANGTIKEUT YO TIKEUT - 0x8CCB: 0xB688, //HANGUL SYLLABLE SSANGTIKEUT YO RIEUL - 0x8CCC: 0xB689, //HANGUL SYLLABLE SSANGTIKEUT YO RIEULKIYEOK - 0x8CCD: 0xB68A, //HANGUL SYLLABLE SSANGTIKEUT YO RIEULMIEUM - 0x8CCE: 0xB68B, //HANGUL SYLLABLE SSANGTIKEUT YO RIEULPIEUP - 0x8CCF: 0xB68C, //HANGUL SYLLABLE SSANGTIKEUT YO RIEULSIOS - 0x8CD0: 0xB68D, //HANGUL SYLLABLE SSANGTIKEUT YO RIEULTHIEUTH - 0x8CD1: 0xB68E, //HANGUL SYLLABLE SSANGTIKEUT YO RIEULPHIEUPH - 0x8CD2: 0xB68F, //HANGUL SYLLABLE SSANGTIKEUT YO RIEULHIEUH - 0x8CD3: 0xB690, //HANGUL SYLLABLE SSANGTIKEUT YO MIEUM - 0x8CD4: 0xB691, //HANGUL SYLLABLE SSANGTIKEUT YO PIEUP - 0x8CD5: 0xB692, //HANGUL SYLLABLE SSANGTIKEUT YO PIEUPSIOS - 0x8CD6: 0xB693, //HANGUL SYLLABLE SSANGTIKEUT YO SIOS - 0x8CD7: 0xB694, //HANGUL SYLLABLE SSANGTIKEUT YO SSANGSIOS - 0x8CD8: 0xB695, //HANGUL SYLLABLE SSANGTIKEUT YO IEUNG - 0x8CD9: 0xB696, //HANGUL SYLLABLE SSANGTIKEUT YO CIEUC - 0x8CDA: 0xB697, //HANGUL SYLLABLE SSANGTIKEUT YO CHIEUCH - 0x8CDB: 0xB698, //HANGUL SYLLABLE SSANGTIKEUT YO KHIEUKH - 0x8CDC: 0xB699, //HANGUL SYLLABLE SSANGTIKEUT YO THIEUTH - 0x8CDD: 0xB69A, //HANGUL SYLLABLE SSANGTIKEUT YO PHIEUPH - 0x8CDE: 0xB69B, //HANGUL SYLLABLE SSANGTIKEUT YO HIEUH - 0x8CDF: 0xB69E, //HANGUL SYLLABLE SSANGTIKEUT U SSANGKIYEOK - 0x8CE0: 0xB69F, //HANGUL SYLLABLE SSANGTIKEUT U KIYEOKSIOS - 0x8CE1: 0xB6A1, //HANGUL SYLLABLE SSANGTIKEUT U NIEUNCIEUC - 0x8CE2: 0xB6A2, //HANGUL SYLLABLE SSANGTIKEUT U NIEUNHIEUH - 0x8CE3: 0xB6A3, //HANGUL SYLLABLE SSANGTIKEUT U TIKEUT - 0x8CE4: 0xB6A5, //HANGUL SYLLABLE SSANGTIKEUT U RIEULKIYEOK - 0x8CE5: 0xB6A6, //HANGUL SYLLABLE SSANGTIKEUT U RIEULMIEUM - 0x8CE6: 0xB6A7, //HANGUL SYLLABLE SSANGTIKEUT U RIEULPIEUP - 0x8CE7: 0xB6A8, //HANGUL SYLLABLE SSANGTIKEUT U RIEULSIOS - 0x8CE8: 0xB6A9, //HANGUL SYLLABLE SSANGTIKEUT U RIEULTHIEUTH - 0x8CE9: 0xB6AA, //HANGUL SYLLABLE SSANGTIKEUT U RIEULPHIEUPH - 0x8CEA: 0xB6AD, //HANGUL SYLLABLE SSANGTIKEUT U PIEUP - 0x8CEB: 0xB6AE, //HANGUL SYLLABLE SSANGTIKEUT U PIEUPSIOS - 0x8CEC: 0xB6AF, //HANGUL SYLLABLE SSANGTIKEUT U SIOS - 0x8CED: 0xB6B0, //HANGUL SYLLABLE SSANGTIKEUT U SSANGSIOS - 0x8CEE: 0xB6B2, //HANGUL SYLLABLE SSANGTIKEUT U CIEUC - 0x8CEF: 0xB6B3, //HANGUL SYLLABLE SSANGTIKEUT U CHIEUCH - 0x8CF0: 0xB6B4, //HANGUL SYLLABLE SSANGTIKEUT U KHIEUKH - 0x8CF1: 0xB6B5, //HANGUL SYLLABLE SSANGTIKEUT U THIEUTH - 0x8CF2: 0xB6B6, //HANGUL SYLLABLE SSANGTIKEUT U PHIEUPH - 0x8CF3: 0xB6B7, //HANGUL SYLLABLE SSANGTIKEUT U HIEUH - 0x8CF4: 0xB6B8, //HANGUL SYLLABLE SSANGTIKEUT WEO - 0x8CF5: 0xB6B9, //HANGUL SYLLABLE SSANGTIKEUT WEO KIYEOK - 0x8CF6: 0xB6BA, //HANGUL SYLLABLE SSANGTIKEUT WEO SSANGKIYEOK - 0x8CF7: 0xB6BB, //HANGUL SYLLABLE SSANGTIKEUT WEO KIYEOKSIOS - 0x8CF8: 0xB6BC, //HANGUL SYLLABLE SSANGTIKEUT WEO NIEUN - 0x8CF9: 0xB6BD, //HANGUL SYLLABLE SSANGTIKEUT WEO NIEUNCIEUC - 0x8CFA: 0xB6BE, //HANGUL SYLLABLE SSANGTIKEUT WEO NIEUNHIEUH - 0x8CFB: 0xB6BF, //HANGUL SYLLABLE SSANGTIKEUT WEO TIKEUT - 0x8CFC: 0xB6C0, //HANGUL SYLLABLE SSANGTIKEUT WEO RIEUL - 0x8CFD: 0xB6C1, //HANGUL SYLLABLE SSANGTIKEUT WEO RIEULKIYEOK - 0x8CFE: 0xB6C2, //HANGUL SYLLABLE SSANGTIKEUT WEO RIEULMIEUM - 0x8D41: 0xB6C3, //HANGUL SYLLABLE SSANGTIKEUT WEO RIEULPIEUP - 0x8D42: 0xB6C4, //HANGUL SYLLABLE SSANGTIKEUT WEO RIEULSIOS - 0x8D43: 0xB6C5, //HANGUL SYLLABLE SSANGTIKEUT WEO RIEULTHIEUTH - 0x8D44: 0xB6C6, //HANGUL SYLLABLE SSANGTIKEUT WEO RIEULPHIEUPH - 0x8D45: 0xB6C7, //HANGUL SYLLABLE SSANGTIKEUT WEO RIEULHIEUH - 0x8D46: 0xB6C8, //HANGUL SYLLABLE SSANGTIKEUT WEO MIEUM - 0x8D47: 0xB6C9, //HANGUL SYLLABLE SSANGTIKEUT WEO PIEUP - 0x8D48: 0xB6CA, //HANGUL SYLLABLE SSANGTIKEUT WEO PIEUPSIOS - 0x8D49: 0xB6CB, //HANGUL SYLLABLE SSANGTIKEUT WEO SIOS - 0x8D4A: 0xB6CC, //HANGUL SYLLABLE SSANGTIKEUT WEO SSANGSIOS - 0x8D4B: 0xB6CD, //HANGUL SYLLABLE SSANGTIKEUT WEO IEUNG - 0x8D4C: 0xB6CE, //HANGUL SYLLABLE SSANGTIKEUT WEO CIEUC - 0x8D4D: 0xB6CF, //HANGUL SYLLABLE SSANGTIKEUT WEO CHIEUCH - 0x8D4E: 0xB6D0, //HANGUL SYLLABLE SSANGTIKEUT WEO KHIEUKH - 0x8D4F: 0xB6D1, //HANGUL SYLLABLE SSANGTIKEUT WEO THIEUTH - 0x8D50: 0xB6D2, //HANGUL SYLLABLE SSANGTIKEUT WEO PHIEUPH - 0x8D51: 0xB6D3, //HANGUL SYLLABLE SSANGTIKEUT WEO HIEUH - 0x8D52: 0xB6D5, //HANGUL SYLLABLE SSANGTIKEUT WE KIYEOK - 0x8D53: 0xB6D6, //HANGUL SYLLABLE SSANGTIKEUT WE SSANGKIYEOK - 0x8D54: 0xB6D7, //HANGUL SYLLABLE SSANGTIKEUT WE KIYEOKSIOS - 0x8D55: 0xB6D8, //HANGUL SYLLABLE SSANGTIKEUT WE NIEUN - 0x8D56: 0xB6D9, //HANGUL SYLLABLE SSANGTIKEUT WE NIEUNCIEUC - 0x8D57: 0xB6DA, //HANGUL SYLLABLE SSANGTIKEUT WE NIEUNHIEUH - 0x8D58: 0xB6DB, //HANGUL SYLLABLE SSANGTIKEUT WE TIKEUT - 0x8D59: 0xB6DC, //HANGUL SYLLABLE SSANGTIKEUT WE RIEUL - 0x8D5A: 0xB6DD, //HANGUL SYLLABLE SSANGTIKEUT WE RIEULKIYEOK - 0x8D61: 0xB6DE, //HANGUL SYLLABLE SSANGTIKEUT WE RIEULMIEUM - 0x8D62: 0xB6DF, //HANGUL SYLLABLE SSANGTIKEUT WE RIEULPIEUP - 0x8D63: 0xB6E0, //HANGUL SYLLABLE SSANGTIKEUT WE RIEULSIOS - 0x8D64: 0xB6E1, //HANGUL SYLLABLE SSANGTIKEUT WE RIEULTHIEUTH - 0x8D65: 0xB6E2, //HANGUL SYLLABLE SSANGTIKEUT WE RIEULPHIEUPH - 0x8D66: 0xB6E3, //HANGUL SYLLABLE SSANGTIKEUT WE RIEULHIEUH - 0x8D67: 0xB6E4, //HANGUL SYLLABLE SSANGTIKEUT WE MIEUM - 0x8D68: 0xB6E5, //HANGUL SYLLABLE SSANGTIKEUT WE PIEUP - 0x8D69: 0xB6E6, //HANGUL SYLLABLE SSANGTIKEUT WE PIEUPSIOS - 0x8D6A: 0xB6E7, //HANGUL SYLLABLE SSANGTIKEUT WE SIOS - 0x8D6B: 0xB6E8, //HANGUL SYLLABLE SSANGTIKEUT WE SSANGSIOS - 0x8D6C: 0xB6E9, //HANGUL SYLLABLE SSANGTIKEUT WE IEUNG - 0x8D6D: 0xB6EA, //HANGUL SYLLABLE SSANGTIKEUT WE CIEUC - 0x8D6E: 0xB6EB, //HANGUL SYLLABLE SSANGTIKEUT WE CHIEUCH - 0x8D6F: 0xB6EC, //HANGUL SYLLABLE SSANGTIKEUT WE KHIEUKH - 0x8D70: 0xB6ED, //HANGUL SYLLABLE SSANGTIKEUT WE THIEUTH - 0x8D71: 0xB6EE, //HANGUL SYLLABLE SSANGTIKEUT WE PHIEUPH - 0x8D72: 0xB6EF, //HANGUL SYLLABLE SSANGTIKEUT WE HIEUH - 0x8D73: 0xB6F1, //HANGUL SYLLABLE SSANGTIKEUT WI KIYEOK - 0x8D74: 0xB6F2, //HANGUL SYLLABLE SSANGTIKEUT WI SSANGKIYEOK - 0x8D75: 0xB6F3, //HANGUL SYLLABLE SSANGTIKEUT WI KIYEOKSIOS - 0x8D76: 0xB6F5, //HANGUL SYLLABLE SSANGTIKEUT WI NIEUNCIEUC - 0x8D77: 0xB6F6, //HANGUL SYLLABLE SSANGTIKEUT WI NIEUNHIEUH - 0x8D78: 0xB6F7, //HANGUL SYLLABLE SSANGTIKEUT WI TIKEUT - 0x8D79: 0xB6F9, //HANGUL SYLLABLE SSANGTIKEUT WI RIEULKIYEOK - 0x8D7A: 0xB6FA, //HANGUL SYLLABLE SSANGTIKEUT WI RIEULMIEUM - 0x8D81: 0xB6FB, //HANGUL SYLLABLE SSANGTIKEUT WI RIEULPIEUP - 0x8D82: 0xB6FC, //HANGUL SYLLABLE SSANGTIKEUT WI RIEULSIOS - 0x8D83: 0xB6FD, //HANGUL SYLLABLE SSANGTIKEUT WI RIEULTHIEUTH - 0x8D84: 0xB6FE, //HANGUL SYLLABLE SSANGTIKEUT WI RIEULPHIEUPH - 0x8D85: 0xB6FF, //HANGUL SYLLABLE SSANGTIKEUT WI RIEULHIEUH - 0x8D86: 0xB702, //HANGUL SYLLABLE SSANGTIKEUT WI PIEUPSIOS - 0x8D87: 0xB703, //HANGUL SYLLABLE SSANGTIKEUT WI SIOS - 0x8D88: 0xB704, //HANGUL SYLLABLE SSANGTIKEUT WI SSANGSIOS - 0x8D89: 0xB706, //HANGUL SYLLABLE SSANGTIKEUT WI CIEUC - 0x8D8A: 0xB707, //HANGUL SYLLABLE SSANGTIKEUT WI CHIEUCH - 0x8D8B: 0xB708, //HANGUL SYLLABLE SSANGTIKEUT WI KHIEUKH - 0x8D8C: 0xB709, //HANGUL SYLLABLE SSANGTIKEUT WI THIEUTH - 0x8D8D: 0xB70A, //HANGUL SYLLABLE SSANGTIKEUT WI PHIEUPH - 0x8D8E: 0xB70B, //HANGUL SYLLABLE SSANGTIKEUT WI HIEUH - 0x8D8F: 0xB70C, //HANGUL SYLLABLE SSANGTIKEUT YU - 0x8D90: 0xB70D, //HANGUL SYLLABLE SSANGTIKEUT YU KIYEOK - 0x8D91: 0xB70E, //HANGUL SYLLABLE SSANGTIKEUT YU SSANGKIYEOK - 0x8D92: 0xB70F, //HANGUL SYLLABLE SSANGTIKEUT YU KIYEOKSIOS - 0x8D93: 0xB710, //HANGUL SYLLABLE SSANGTIKEUT YU NIEUN - 0x8D94: 0xB711, //HANGUL SYLLABLE SSANGTIKEUT YU NIEUNCIEUC - 0x8D95: 0xB712, //HANGUL SYLLABLE SSANGTIKEUT YU NIEUNHIEUH - 0x8D96: 0xB713, //HANGUL SYLLABLE SSANGTIKEUT YU TIKEUT - 0x8D97: 0xB714, //HANGUL SYLLABLE SSANGTIKEUT YU RIEUL - 0x8D98: 0xB715, //HANGUL SYLLABLE SSANGTIKEUT YU RIEULKIYEOK - 0x8D99: 0xB716, //HANGUL SYLLABLE SSANGTIKEUT YU RIEULMIEUM - 0x8D9A: 0xB717, //HANGUL SYLLABLE SSANGTIKEUT YU RIEULPIEUP - 0x8D9B: 0xB718, //HANGUL SYLLABLE SSANGTIKEUT YU RIEULSIOS - 0x8D9C: 0xB719, //HANGUL SYLLABLE SSANGTIKEUT YU RIEULTHIEUTH - 0x8D9D: 0xB71A, //HANGUL SYLLABLE SSANGTIKEUT YU RIEULPHIEUPH - 0x8D9E: 0xB71B, //HANGUL SYLLABLE SSANGTIKEUT YU RIEULHIEUH - 0x8D9F: 0xB71C, //HANGUL SYLLABLE SSANGTIKEUT YU MIEUM - 0x8DA0: 0xB71D, //HANGUL SYLLABLE SSANGTIKEUT YU PIEUP - 0x8DA1: 0xB71E, //HANGUL SYLLABLE SSANGTIKEUT YU PIEUPSIOS - 0x8DA2: 0xB71F, //HANGUL SYLLABLE SSANGTIKEUT YU SIOS - 0x8DA3: 0xB720, //HANGUL SYLLABLE SSANGTIKEUT YU SSANGSIOS - 0x8DA4: 0xB721, //HANGUL SYLLABLE SSANGTIKEUT YU IEUNG - 0x8DA5: 0xB722, //HANGUL SYLLABLE SSANGTIKEUT YU CIEUC - 0x8DA6: 0xB723, //HANGUL SYLLABLE SSANGTIKEUT YU CHIEUCH - 0x8DA7: 0xB724, //HANGUL SYLLABLE SSANGTIKEUT YU KHIEUKH - 0x8DA8: 0xB725, //HANGUL SYLLABLE SSANGTIKEUT YU THIEUTH - 0x8DA9: 0xB726, //HANGUL SYLLABLE SSANGTIKEUT YU PHIEUPH - 0x8DAA: 0xB727, //HANGUL SYLLABLE SSANGTIKEUT YU HIEUH - 0x8DAB: 0xB72A, //HANGUL SYLLABLE SSANGTIKEUT EU SSANGKIYEOK - 0x8DAC: 0xB72B, //HANGUL SYLLABLE SSANGTIKEUT EU KIYEOKSIOS - 0x8DAD: 0xB72D, //HANGUL SYLLABLE SSANGTIKEUT EU NIEUNCIEUC - 0x8DAE: 0xB72E, //HANGUL SYLLABLE SSANGTIKEUT EU NIEUNHIEUH - 0x8DAF: 0xB731, //HANGUL SYLLABLE SSANGTIKEUT EU RIEULKIYEOK - 0x8DB0: 0xB732, //HANGUL SYLLABLE SSANGTIKEUT EU RIEULMIEUM - 0x8DB1: 0xB733, //HANGUL SYLLABLE SSANGTIKEUT EU RIEULPIEUP - 0x8DB2: 0xB734, //HANGUL SYLLABLE SSANGTIKEUT EU RIEULSIOS - 0x8DB3: 0xB735, //HANGUL SYLLABLE SSANGTIKEUT EU RIEULTHIEUTH - 0x8DB4: 0xB736, //HANGUL SYLLABLE SSANGTIKEUT EU RIEULPHIEUPH - 0x8DB5: 0xB737, //HANGUL SYLLABLE SSANGTIKEUT EU RIEULHIEUH - 0x8DB6: 0xB73A, //HANGUL SYLLABLE SSANGTIKEUT EU PIEUPSIOS - 0x8DB7: 0xB73C, //HANGUL SYLLABLE SSANGTIKEUT EU SSANGSIOS - 0x8DB8: 0xB73D, //HANGUL SYLLABLE SSANGTIKEUT EU IEUNG - 0x8DB9: 0xB73E, //HANGUL SYLLABLE SSANGTIKEUT EU CIEUC - 0x8DBA: 0xB73F, //HANGUL SYLLABLE SSANGTIKEUT EU CHIEUCH - 0x8DBB: 0xB740, //HANGUL SYLLABLE SSANGTIKEUT EU KHIEUKH - 0x8DBC: 0xB741, //HANGUL SYLLABLE SSANGTIKEUT EU THIEUTH - 0x8DBD: 0xB742, //HANGUL SYLLABLE SSANGTIKEUT EU PHIEUPH - 0x8DBE: 0xB743, //HANGUL SYLLABLE SSANGTIKEUT EU HIEUH - 0x8DBF: 0xB745, //HANGUL SYLLABLE SSANGTIKEUT YI KIYEOK - 0x8DC0: 0xB746, //HANGUL SYLLABLE SSANGTIKEUT YI SSANGKIYEOK - 0x8DC1: 0xB747, //HANGUL SYLLABLE SSANGTIKEUT YI KIYEOKSIOS - 0x8DC2: 0xB749, //HANGUL SYLLABLE SSANGTIKEUT YI NIEUNCIEUC - 0x8DC3: 0xB74A, //HANGUL SYLLABLE SSANGTIKEUT YI NIEUNHIEUH - 0x8DC4: 0xB74B, //HANGUL SYLLABLE SSANGTIKEUT YI TIKEUT - 0x8DC5: 0xB74D, //HANGUL SYLLABLE SSANGTIKEUT YI RIEULKIYEOK - 0x8DC6: 0xB74E, //HANGUL SYLLABLE SSANGTIKEUT YI RIEULMIEUM - 0x8DC7: 0xB74F, //HANGUL SYLLABLE SSANGTIKEUT YI RIEULPIEUP - 0x8DC8: 0xB750, //HANGUL SYLLABLE SSANGTIKEUT YI RIEULSIOS - 0x8DC9: 0xB751, //HANGUL SYLLABLE SSANGTIKEUT YI RIEULTHIEUTH - 0x8DCA: 0xB752, //HANGUL SYLLABLE SSANGTIKEUT YI RIEULPHIEUPH - 0x8DCB: 0xB753, //HANGUL SYLLABLE SSANGTIKEUT YI RIEULHIEUH - 0x8DCC: 0xB756, //HANGUL SYLLABLE SSANGTIKEUT YI PIEUPSIOS - 0x8DCD: 0xB757, //HANGUL SYLLABLE SSANGTIKEUT YI SIOS - 0x8DCE: 0xB758, //HANGUL SYLLABLE SSANGTIKEUT YI SSANGSIOS - 0x8DCF: 0xB759, //HANGUL SYLLABLE SSANGTIKEUT YI IEUNG - 0x8DD0: 0xB75A, //HANGUL SYLLABLE SSANGTIKEUT YI CIEUC - 0x8DD1: 0xB75B, //HANGUL SYLLABLE SSANGTIKEUT YI CHIEUCH - 0x8DD2: 0xB75C, //HANGUL SYLLABLE SSANGTIKEUT YI KHIEUKH - 0x8DD3: 0xB75D, //HANGUL SYLLABLE SSANGTIKEUT YI THIEUTH - 0x8DD4: 0xB75E, //HANGUL SYLLABLE SSANGTIKEUT YI PHIEUPH - 0x8DD5: 0xB75F, //HANGUL SYLLABLE SSANGTIKEUT YI HIEUH - 0x8DD6: 0xB761, //HANGUL SYLLABLE SSANGTIKEUT I KIYEOK - 0x8DD7: 0xB762, //HANGUL SYLLABLE SSANGTIKEUT I SSANGKIYEOK - 0x8DD8: 0xB763, //HANGUL SYLLABLE SSANGTIKEUT I KIYEOKSIOS - 0x8DD9: 0xB765, //HANGUL SYLLABLE SSANGTIKEUT I NIEUNCIEUC - 0x8DDA: 0xB766, //HANGUL SYLLABLE SSANGTIKEUT I NIEUNHIEUH - 0x8DDB: 0xB767, //HANGUL SYLLABLE SSANGTIKEUT I TIKEUT - 0x8DDC: 0xB769, //HANGUL SYLLABLE SSANGTIKEUT I RIEULKIYEOK - 0x8DDD: 0xB76A, //HANGUL SYLLABLE SSANGTIKEUT I RIEULMIEUM - 0x8DDE: 0xB76B, //HANGUL SYLLABLE SSANGTIKEUT I RIEULPIEUP - 0x8DDF: 0xB76C, //HANGUL SYLLABLE SSANGTIKEUT I RIEULSIOS - 0x8DE0: 0xB76D, //HANGUL SYLLABLE SSANGTIKEUT I RIEULTHIEUTH - 0x8DE1: 0xB76E, //HANGUL SYLLABLE SSANGTIKEUT I RIEULPHIEUPH - 0x8DE2: 0xB76F, //HANGUL SYLLABLE SSANGTIKEUT I RIEULHIEUH - 0x8DE3: 0xB772, //HANGUL SYLLABLE SSANGTIKEUT I PIEUPSIOS - 0x8DE4: 0xB774, //HANGUL SYLLABLE SSANGTIKEUT I SSANGSIOS - 0x8DE5: 0xB776, //HANGUL SYLLABLE SSANGTIKEUT I CIEUC - 0x8DE6: 0xB777, //HANGUL SYLLABLE SSANGTIKEUT I CHIEUCH - 0x8DE7: 0xB778, //HANGUL SYLLABLE SSANGTIKEUT I KHIEUKH - 0x8DE8: 0xB779, //HANGUL SYLLABLE SSANGTIKEUT I THIEUTH - 0x8DE9: 0xB77A, //HANGUL SYLLABLE SSANGTIKEUT I PHIEUPH - 0x8DEA: 0xB77B, //HANGUL SYLLABLE SSANGTIKEUT I HIEUH - 0x8DEB: 0xB77E, //HANGUL SYLLABLE RIEUL A SSANGKIYEOK - 0x8DEC: 0xB77F, //HANGUL SYLLABLE RIEUL A KIYEOKSIOS - 0x8DED: 0xB781, //HANGUL SYLLABLE RIEUL A NIEUNCIEUC - 0x8DEE: 0xB782, //HANGUL SYLLABLE RIEUL A NIEUNHIEUH - 0x8DEF: 0xB783, //HANGUL SYLLABLE RIEUL A TIKEUT - 0x8DF0: 0xB785, //HANGUL SYLLABLE RIEUL A RIEULKIYEOK - 0x8DF1: 0xB786, //HANGUL SYLLABLE RIEUL A RIEULMIEUM - 0x8DF2: 0xB787, //HANGUL SYLLABLE RIEUL A RIEULPIEUP - 0x8DF3: 0xB788, //HANGUL SYLLABLE RIEUL A RIEULSIOS - 0x8DF4: 0xB789, //HANGUL SYLLABLE RIEUL A RIEULTHIEUTH - 0x8DF5: 0xB78A, //HANGUL SYLLABLE RIEUL A RIEULPHIEUPH - 0x8DF6: 0xB78B, //HANGUL SYLLABLE RIEUL A RIEULHIEUH - 0x8DF7: 0xB78E, //HANGUL SYLLABLE RIEUL A PIEUPSIOS - 0x8DF8: 0xB793, //HANGUL SYLLABLE RIEUL A CHIEUCH - 0x8DF9: 0xB794, //HANGUL SYLLABLE RIEUL A KHIEUKH - 0x8DFA: 0xB795, //HANGUL SYLLABLE RIEUL A THIEUTH - 0x8DFB: 0xB79A, //HANGUL SYLLABLE RIEUL AE SSANGKIYEOK - 0x8DFC: 0xB79B, //HANGUL SYLLABLE RIEUL AE KIYEOKSIOS - 0x8DFD: 0xB79D, //HANGUL SYLLABLE RIEUL AE NIEUNCIEUC - 0x8DFE: 0xB79E, //HANGUL SYLLABLE RIEUL AE NIEUNHIEUH - 0x8E41: 0xB79F, //HANGUL SYLLABLE RIEUL AE TIKEUT - 0x8E42: 0xB7A1, //HANGUL SYLLABLE RIEUL AE RIEULKIYEOK - 0x8E43: 0xB7A2, //HANGUL SYLLABLE RIEUL AE RIEULMIEUM - 0x8E44: 0xB7A3, //HANGUL SYLLABLE RIEUL AE RIEULPIEUP - 0x8E45: 0xB7A4, //HANGUL SYLLABLE RIEUL AE RIEULSIOS - 0x8E46: 0xB7A5, //HANGUL SYLLABLE RIEUL AE RIEULTHIEUTH - 0x8E47: 0xB7A6, //HANGUL SYLLABLE RIEUL AE RIEULPHIEUPH - 0x8E48: 0xB7A7, //HANGUL SYLLABLE RIEUL AE RIEULHIEUH - 0x8E49: 0xB7AA, //HANGUL SYLLABLE RIEUL AE PIEUPSIOS - 0x8E4A: 0xB7AE, //HANGUL SYLLABLE RIEUL AE CIEUC - 0x8E4B: 0xB7AF, //HANGUL SYLLABLE RIEUL AE CHIEUCH - 0x8E4C: 0xB7B0, //HANGUL SYLLABLE RIEUL AE KHIEUKH - 0x8E4D: 0xB7B1, //HANGUL SYLLABLE RIEUL AE THIEUTH - 0x8E4E: 0xB7B2, //HANGUL SYLLABLE RIEUL AE PHIEUPH - 0x8E4F: 0xB7B3, //HANGUL SYLLABLE RIEUL AE HIEUH - 0x8E50: 0xB7B6, //HANGUL SYLLABLE RIEUL YA SSANGKIYEOK - 0x8E51: 0xB7B7, //HANGUL SYLLABLE RIEUL YA KIYEOKSIOS - 0x8E52: 0xB7B9, //HANGUL SYLLABLE RIEUL YA NIEUNCIEUC - 0x8E53: 0xB7BA, //HANGUL SYLLABLE RIEUL YA NIEUNHIEUH - 0x8E54: 0xB7BB, //HANGUL SYLLABLE RIEUL YA TIKEUT - 0x8E55: 0xB7BC, //HANGUL SYLLABLE RIEUL YA RIEUL - 0x8E56: 0xB7BD, //HANGUL SYLLABLE RIEUL YA RIEULKIYEOK - 0x8E57: 0xB7BE, //HANGUL SYLLABLE RIEUL YA RIEULMIEUM - 0x8E58: 0xB7BF, //HANGUL SYLLABLE RIEUL YA RIEULPIEUP - 0x8E59: 0xB7C0, //HANGUL SYLLABLE RIEUL YA RIEULSIOS - 0x8E5A: 0xB7C1, //HANGUL SYLLABLE RIEUL YA RIEULTHIEUTH - 0x8E61: 0xB7C2, //HANGUL SYLLABLE RIEUL YA RIEULPHIEUPH - 0x8E62: 0xB7C3, //HANGUL SYLLABLE RIEUL YA RIEULHIEUH - 0x8E63: 0xB7C4, //HANGUL SYLLABLE RIEUL YA MIEUM - 0x8E64: 0xB7C5, //HANGUL SYLLABLE RIEUL YA PIEUP - 0x8E65: 0xB7C6, //HANGUL SYLLABLE RIEUL YA PIEUPSIOS - 0x8E66: 0xB7C8, //HANGUL SYLLABLE RIEUL YA SSANGSIOS - 0x8E67: 0xB7CA, //HANGUL SYLLABLE RIEUL YA CIEUC - 0x8E68: 0xB7CB, //HANGUL SYLLABLE RIEUL YA CHIEUCH - 0x8E69: 0xB7CC, //HANGUL SYLLABLE RIEUL YA KHIEUKH - 0x8E6A: 0xB7CD, //HANGUL SYLLABLE RIEUL YA THIEUTH - 0x8E6B: 0xB7CE, //HANGUL SYLLABLE RIEUL YA PHIEUPH - 0x8E6C: 0xB7CF, //HANGUL SYLLABLE RIEUL YA HIEUH - 0x8E6D: 0xB7D0, //HANGUL SYLLABLE RIEUL YAE - 0x8E6E: 0xB7D1, //HANGUL SYLLABLE RIEUL YAE KIYEOK - 0x8E6F: 0xB7D2, //HANGUL SYLLABLE RIEUL YAE SSANGKIYEOK - 0x8E70: 0xB7D3, //HANGUL SYLLABLE RIEUL YAE KIYEOKSIOS - 0x8E71: 0xB7D4, //HANGUL SYLLABLE RIEUL YAE NIEUN - 0x8E72: 0xB7D5, //HANGUL SYLLABLE RIEUL YAE NIEUNCIEUC - 0x8E73: 0xB7D6, //HANGUL SYLLABLE RIEUL YAE NIEUNHIEUH - 0x8E74: 0xB7D7, //HANGUL SYLLABLE RIEUL YAE TIKEUT - 0x8E75: 0xB7D8, //HANGUL SYLLABLE RIEUL YAE RIEUL - 0x8E76: 0xB7D9, //HANGUL SYLLABLE RIEUL YAE RIEULKIYEOK - 0x8E77: 0xB7DA, //HANGUL SYLLABLE RIEUL YAE RIEULMIEUM - 0x8E78: 0xB7DB, //HANGUL SYLLABLE RIEUL YAE RIEULPIEUP - 0x8E79: 0xB7DC, //HANGUL SYLLABLE RIEUL YAE RIEULSIOS - 0x8E7A: 0xB7DD, //HANGUL SYLLABLE RIEUL YAE RIEULTHIEUTH - 0x8E81: 0xB7DE, //HANGUL SYLLABLE RIEUL YAE RIEULPHIEUPH - 0x8E82: 0xB7DF, //HANGUL SYLLABLE RIEUL YAE RIEULHIEUH - 0x8E83: 0xB7E0, //HANGUL SYLLABLE RIEUL YAE MIEUM - 0x8E84: 0xB7E1, //HANGUL SYLLABLE RIEUL YAE PIEUP - 0x8E85: 0xB7E2, //HANGUL SYLLABLE RIEUL YAE PIEUPSIOS - 0x8E86: 0xB7E3, //HANGUL SYLLABLE RIEUL YAE SIOS - 0x8E87: 0xB7E4, //HANGUL SYLLABLE RIEUL YAE SSANGSIOS - 0x8E88: 0xB7E5, //HANGUL SYLLABLE RIEUL YAE IEUNG - 0x8E89: 0xB7E6, //HANGUL SYLLABLE RIEUL YAE CIEUC - 0x8E8A: 0xB7E7, //HANGUL SYLLABLE RIEUL YAE CHIEUCH - 0x8E8B: 0xB7E8, //HANGUL SYLLABLE RIEUL YAE KHIEUKH - 0x8E8C: 0xB7E9, //HANGUL SYLLABLE RIEUL YAE THIEUTH - 0x8E8D: 0xB7EA, //HANGUL SYLLABLE RIEUL YAE PHIEUPH - 0x8E8E: 0xB7EB, //HANGUL SYLLABLE RIEUL YAE HIEUH - 0x8E8F: 0xB7EE, //HANGUL SYLLABLE RIEUL EO SSANGKIYEOK - 0x8E90: 0xB7EF, //HANGUL SYLLABLE RIEUL EO KIYEOKSIOS - 0x8E91: 0xB7F1, //HANGUL SYLLABLE RIEUL EO NIEUNCIEUC - 0x8E92: 0xB7F2, //HANGUL SYLLABLE RIEUL EO NIEUNHIEUH - 0x8E93: 0xB7F3, //HANGUL SYLLABLE RIEUL EO TIKEUT - 0x8E94: 0xB7F5, //HANGUL SYLLABLE RIEUL EO RIEULKIYEOK - 0x8E95: 0xB7F6, //HANGUL SYLLABLE RIEUL EO RIEULMIEUM - 0x8E96: 0xB7F7, //HANGUL SYLLABLE RIEUL EO RIEULPIEUP - 0x8E97: 0xB7F8, //HANGUL SYLLABLE RIEUL EO RIEULSIOS - 0x8E98: 0xB7F9, //HANGUL SYLLABLE RIEUL EO RIEULTHIEUTH - 0x8E99: 0xB7FA, //HANGUL SYLLABLE RIEUL EO RIEULPHIEUPH - 0x8E9A: 0xB7FB, //HANGUL SYLLABLE RIEUL EO RIEULHIEUH - 0x8E9B: 0xB7FE, //HANGUL SYLLABLE RIEUL EO PIEUPSIOS - 0x8E9C: 0xB802, //HANGUL SYLLABLE RIEUL EO CIEUC - 0x8E9D: 0xB803, //HANGUL SYLLABLE RIEUL EO CHIEUCH - 0x8E9E: 0xB804, //HANGUL SYLLABLE RIEUL EO KHIEUKH - 0x8E9F: 0xB805, //HANGUL SYLLABLE RIEUL EO THIEUTH - 0x8EA0: 0xB806, //HANGUL SYLLABLE RIEUL EO PHIEUPH - 0x8EA1: 0xB80A, //HANGUL SYLLABLE RIEUL E SSANGKIYEOK - 0x8EA2: 0xB80B, //HANGUL SYLLABLE RIEUL E KIYEOKSIOS - 0x8EA3: 0xB80D, //HANGUL SYLLABLE RIEUL E NIEUNCIEUC - 0x8EA4: 0xB80E, //HANGUL SYLLABLE RIEUL E NIEUNHIEUH - 0x8EA5: 0xB80F, //HANGUL SYLLABLE RIEUL E TIKEUT - 0x8EA6: 0xB811, //HANGUL SYLLABLE RIEUL E RIEULKIYEOK - 0x8EA7: 0xB812, //HANGUL SYLLABLE RIEUL E RIEULMIEUM - 0x8EA8: 0xB813, //HANGUL SYLLABLE RIEUL E RIEULPIEUP - 0x8EA9: 0xB814, //HANGUL SYLLABLE RIEUL E RIEULSIOS - 0x8EAA: 0xB815, //HANGUL SYLLABLE RIEUL E RIEULTHIEUTH - 0x8EAB: 0xB816, //HANGUL SYLLABLE RIEUL E RIEULPHIEUPH - 0x8EAC: 0xB817, //HANGUL SYLLABLE RIEUL E RIEULHIEUH - 0x8EAD: 0xB81A, //HANGUL SYLLABLE RIEUL E PIEUPSIOS - 0x8EAE: 0xB81C, //HANGUL SYLLABLE RIEUL E SSANGSIOS - 0x8EAF: 0xB81E, //HANGUL SYLLABLE RIEUL E CIEUC - 0x8EB0: 0xB81F, //HANGUL SYLLABLE RIEUL E CHIEUCH - 0x8EB1: 0xB820, //HANGUL SYLLABLE RIEUL E KHIEUKH - 0x8EB2: 0xB821, //HANGUL SYLLABLE RIEUL E THIEUTH - 0x8EB3: 0xB822, //HANGUL SYLLABLE RIEUL E PHIEUPH - 0x8EB4: 0xB823, //HANGUL SYLLABLE RIEUL E HIEUH - 0x8EB5: 0xB826, //HANGUL SYLLABLE RIEUL YEO SSANGKIYEOK - 0x8EB6: 0xB827, //HANGUL SYLLABLE RIEUL YEO KIYEOKSIOS - 0x8EB7: 0xB829, //HANGUL SYLLABLE RIEUL YEO NIEUNCIEUC - 0x8EB8: 0xB82A, //HANGUL SYLLABLE RIEUL YEO NIEUNHIEUH - 0x8EB9: 0xB82B, //HANGUL SYLLABLE RIEUL YEO TIKEUT - 0x8EBA: 0xB82D, //HANGUL SYLLABLE RIEUL YEO RIEULKIYEOK - 0x8EBB: 0xB82E, //HANGUL SYLLABLE RIEUL YEO RIEULMIEUM - 0x8EBC: 0xB82F, //HANGUL SYLLABLE RIEUL YEO RIEULPIEUP - 0x8EBD: 0xB830, //HANGUL SYLLABLE RIEUL YEO RIEULSIOS - 0x8EBE: 0xB831, //HANGUL SYLLABLE RIEUL YEO RIEULTHIEUTH - 0x8EBF: 0xB832, //HANGUL SYLLABLE RIEUL YEO RIEULPHIEUPH - 0x8EC0: 0xB833, //HANGUL SYLLABLE RIEUL YEO RIEULHIEUH - 0x8EC1: 0xB836, //HANGUL SYLLABLE RIEUL YEO PIEUPSIOS - 0x8EC2: 0xB83A, //HANGUL SYLLABLE RIEUL YEO CIEUC - 0x8EC3: 0xB83B, //HANGUL SYLLABLE RIEUL YEO CHIEUCH - 0x8EC4: 0xB83C, //HANGUL SYLLABLE RIEUL YEO KHIEUKH - 0x8EC5: 0xB83D, //HANGUL SYLLABLE RIEUL YEO THIEUTH - 0x8EC6: 0xB83E, //HANGUL SYLLABLE RIEUL YEO PHIEUPH - 0x8EC7: 0xB83F, //HANGUL SYLLABLE RIEUL YEO HIEUH - 0x8EC8: 0xB841, //HANGUL SYLLABLE RIEUL YE KIYEOK - 0x8EC9: 0xB842, //HANGUL SYLLABLE RIEUL YE SSANGKIYEOK - 0x8ECA: 0xB843, //HANGUL SYLLABLE RIEUL YE KIYEOKSIOS - 0x8ECB: 0xB845, //HANGUL SYLLABLE RIEUL YE NIEUNCIEUC - 0x8ECC: 0xB846, //HANGUL SYLLABLE RIEUL YE NIEUNHIEUH - 0x8ECD: 0xB847, //HANGUL SYLLABLE RIEUL YE TIKEUT - 0x8ECE: 0xB848, //HANGUL SYLLABLE RIEUL YE RIEUL - 0x8ECF: 0xB849, //HANGUL SYLLABLE RIEUL YE RIEULKIYEOK - 0x8ED0: 0xB84A, //HANGUL SYLLABLE RIEUL YE RIEULMIEUM - 0x8ED1: 0xB84B, //HANGUL SYLLABLE RIEUL YE RIEULPIEUP - 0x8ED2: 0xB84C, //HANGUL SYLLABLE RIEUL YE RIEULSIOS - 0x8ED3: 0xB84D, //HANGUL SYLLABLE RIEUL YE RIEULTHIEUTH - 0x8ED4: 0xB84E, //HANGUL SYLLABLE RIEUL YE RIEULPHIEUPH - 0x8ED5: 0xB84F, //HANGUL SYLLABLE RIEUL YE RIEULHIEUH - 0x8ED6: 0xB850, //HANGUL SYLLABLE RIEUL YE MIEUM - 0x8ED7: 0xB852, //HANGUL SYLLABLE RIEUL YE PIEUPSIOS - 0x8ED8: 0xB854, //HANGUL SYLLABLE RIEUL YE SSANGSIOS - 0x8ED9: 0xB855, //HANGUL SYLLABLE RIEUL YE IEUNG - 0x8EDA: 0xB856, //HANGUL SYLLABLE RIEUL YE CIEUC - 0x8EDB: 0xB857, //HANGUL SYLLABLE RIEUL YE CHIEUCH - 0x8EDC: 0xB858, //HANGUL SYLLABLE RIEUL YE KHIEUKH - 0x8EDD: 0xB859, //HANGUL SYLLABLE RIEUL YE THIEUTH - 0x8EDE: 0xB85A, //HANGUL SYLLABLE RIEUL YE PHIEUPH - 0x8EDF: 0xB85B, //HANGUL SYLLABLE RIEUL YE HIEUH - 0x8EE0: 0xB85E, //HANGUL SYLLABLE RIEUL O SSANGKIYEOK - 0x8EE1: 0xB85F, //HANGUL SYLLABLE RIEUL O KIYEOKSIOS - 0x8EE2: 0xB861, //HANGUL SYLLABLE RIEUL O NIEUNCIEUC - 0x8EE3: 0xB862, //HANGUL SYLLABLE RIEUL O NIEUNHIEUH - 0x8EE4: 0xB863, //HANGUL SYLLABLE RIEUL O TIKEUT - 0x8EE5: 0xB865, //HANGUL SYLLABLE RIEUL O RIEULKIYEOK - 0x8EE6: 0xB866, //HANGUL SYLLABLE RIEUL O RIEULMIEUM - 0x8EE7: 0xB867, //HANGUL SYLLABLE RIEUL O RIEULPIEUP - 0x8EE8: 0xB868, //HANGUL SYLLABLE RIEUL O RIEULSIOS - 0x8EE9: 0xB869, //HANGUL SYLLABLE RIEUL O RIEULTHIEUTH - 0x8EEA: 0xB86A, //HANGUL SYLLABLE RIEUL O RIEULPHIEUPH - 0x8EEB: 0xB86B, //HANGUL SYLLABLE RIEUL O RIEULHIEUH - 0x8EEC: 0xB86E, //HANGUL SYLLABLE RIEUL O PIEUPSIOS - 0x8EED: 0xB870, //HANGUL SYLLABLE RIEUL O SSANGSIOS - 0x8EEE: 0xB872, //HANGUL SYLLABLE RIEUL O CIEUC - 0x8EEF: 0xB873, //HANGUL SYLLABLE RIEUL O CHIEUCH - 0x8EF0: 0xB874, //HANGUL SYLLABLE RIEUL O KHIEUKH - 0x8EF1: 0xB875, //HANGUL SYLLABLE RIEUL O THIEUTH - 0x8EF2: 0xB876, //HANGUL SYLLABLE RIEUL O PHIEUPH - 0x8EF3: 0xB877, //HANGUL SYLLABLE RIEUL O HIEUH - 0x8EF4: 0xB879, //HANGUL SYLLABLE RIEUL WA KIYEOK - 0x8EF5: 0xB87A, //HANGUL SYLLABLE RIEUL WA SSANGKIYEOK - 0x8EF6: 0xB87B, //HANGUL SYLLABLE RIEUL WA KIYEOKSIOS - 0x8EF7: 0xB87D, //HANGUL SYLLABLE RIEUL WA NIEUNCIEUC - 0x8EF8: 0xB87E, //HANGUL SYLLABLE RIEUL WA NIEUNHIEUH - 0x8EF9: 0xB87F, //HANGUL SYLLABLE RIEUL WA TIKEUT - 0x8EFA: 0xB880, //HANGUL SYLLABLE RIEUL WA RIEUL - 0x8EFB: 0xB881, //HANGUL SYLLABLE RIEUL WA RIEULKIYEOK - 0x8EFC: 0xB882, //HANGUL SYLLABLE RIEUL WA RIEULMIEUM - 0x8EFD: 0xB883, //HANGUL SYLLABLE RIEUL WA RIEULPIEUP - 0x8EFE: 0xB884, //HANGUL SYLLABLE RIEUL WA RIEULSIOS - 0x8F41: 0xB885, //HANGUL SYLLABLE RIEUL WA RIEULTHIEUTH - 0x8F42: 0xB886, //HANGUL SYLLABLE RIEUL WA RIEULPHIEUPH - 0x8F43: 0xB887, //HANGUL SYLLABLE RIEUL WA RIEULHIEUH - 0x8F44: 0xB888, //HANGUL SYLLABLE RIEUL WA MIEUM - 0x8F45: 0xB889, //HANGUL SYLLABLE RIEUL WA PIEUP - 0x8F46: 0xB88A, //HANGUL SYLLABLE RIEUL WA PIEUPSIOS - 0x8F47: 0xB88B, //HANGUL SYLLABLE RIEUL WA SIOS - 0x8F48: 0xB88C, //HANGUL SYLLABLE RIEUL WA SSANGSIOS - 0x8F49: 0xB88E, //HANGUL SYLLABLE RIEUL WA CIEUC - 0x8F4A: 0xB88F, //HANGUL SYLLABLE RIEUL WA CHIEUCH - 0x8F4B: 0xB890, //HANGUL SYLLABLE RIEUL WA KHIEUKH - 0x8F4C: 0xB891, //HANGUL SYLLABLE RIEUL WA THIEUTH - 0x8F4D: 0xB892, //HANGUL SYLLABLE RIEUL WA PHIEUPH - 0x8F4E: 0xB893, //HANGUL SYLLABLE RIEUL WA HIEUH - 0x8F4F: 0xB894, //HANGUL SYLLABLE RIEUL WAE - 0x8F50: 0xB895, //HANGUL SYLLABLE RIEUL WAE KIYEOK - 0x8F51: 0xB896, //HANGUL SYLLABLE RIEUL WAE SSANGKIYEOK - 0x8F52: 0xB897, //HANGUL SYLLABLE RIEUL WAE KIYEOKSIOS - 0x8F53: 0xB898, //HANGUL SYLLABLE RIEUL WAE NIEUN - 0x8F54: 0xB899, //HANGUL SYLLABLE RIEUL WAE NIEUNCIEUC - 0x8F55: 0xB89A, //HANGUL SYLLABLE RIEUL WAE NIEUNHIEUH - 0x8F56: 0xB89B, //HANGUL SYLLABLE RIEUL WAE TIKEUT - 0x8F57: 0xB89C, //HANGUL SYLLABLE RIEUL WAE RIEUL - 0x8F58: 0xB89D, //HANGUL SYLLABLE RIEUL WAE RIEULKIYEOK - 0x8F59: 0xB89E, //HANGUL SYLLABLE RIEUL WAE RIEULMIEUM - 0x8F5A: 0xB89F, //HANGUL SYLLABLE RIEUL WAE RIEULPIEUP - 0x8F61: 0xB8A0, //HANGUL SYLLABLE RIEUL WAE RIEULSIOS - 0x8F62: 0xB8A1, //HANGUL SYLLABLE RIEUL WAE RIEULTHIEUTH - 0x8F63: 0xB8A2, //HANGUL SYLLABLE RIEUL WAE RIEULPHIEUPH - 0x8F64: 0xB8A3, //HANGUL SYLLABLE RIEUL WAE RIEULHIEUH - 0x8F65: 0xB8A4, //HANGUL SYLLABLE RIEUL WAE MIEUM - 0x8F66: 0xB8A5, //HANGUL SYLLABLE RIEUL WAE PIEUP - 0x8F67: 0xB8A6, //HANGUL SYLLABLE RIEUL WAE PIEUPSIOS - 0x8F68: 0xB8A7, //HANGUL SYLLABLE RIEUL WAE SIOS - 0x8F69: 0xB8A9, //HANGUL SYLLABLE RIEUL WAE IEUNG - 0x8F6A: 0xB8AA, //HANGUL SYLLABLE RIEUL WAE CIEUC - 0x8F6B: 0xB8AB, //HANGUL SYLLABLE RIEUL WAE CHIEUCH - 0x8F6C: 0xB8AC, //HANGUL SYLLABLE RIEUL WAE KHIEUKH - 0x8F6D: 0xB8AD, //HANGUL SYLLABLE RIEUL WAE THIEUTH - 0x8F6E: 0xB8AE, //HANGUL SYLLABLE RIEUL WAE PHIEUPH - 0x8F6F: 0xB8AF, //HANGUL SYLLABLE RIEUL WAE HIEUH - 0x8F70: 0xB8B1, //HANGUL SYLLABLE RIEUL OE KIYEOK - 0x8F71: 0xB8B2, //HANGUL SYLLABLE RIEUL OE SSANGKIYEOK - 0x8F72: 0xB8B3, //HANGUL SYLLABLE RIEUL OE KIYEOKSIOS - 0x8F73: 0xB8B5, //HANGUL SYLLABLE RIEUL OE NIEUNCIEUC - 0x8F74: 0xB8B6, //HANGUL SYLLABLE RIEUL OE NIEUNHIEUH - 0x8F75: 0xB8B7, //HANGUL SYLLABLE RIEUL OE TIKEUT - 0x8F76: 0xB8B9, //HANGUL SYLLABLE RIEUL OE RIEULKIYEOK - 0x8F77: 0xB8BA, //HANGUL SYLLABLE RIEUL OE RIEULMIEUM - 0x8F78: 0xB8BB, //HANGUL SYLLABLE RIEUL OE RIEULPIEUP - 0x8F79: 0xB8BC, //HANGUL SYLLABLE RIEUL OE RIEULSIOS - 0x8F7A: 0xB8BD, //HANGUL SYLLABLE RIEUL OE RIEULTHIEUTH - 0x8F81: 0xB8BE, //HANGUL SYLLABLE RIEUL OE RIEULPHIEUPH - 0x8F82: 0xB8BF, //HANGUL SYLLABLE RIEUL OE RIEULHIEUH - 0x8F83: 0xB8C2, //HANGUL SYLLABLE RIEUL OE PIEUPSIOS - 0x8F84: 0xB8C4, //HANGUL SYLLABLE RIEUL OE SSANGSIOS - 0x8F85: 0xB8C6, //HANGUL SYLLABLE RIEUL OE CIEUC - 0x8F86: 0xB8C7, //HANGUL SYLLABLE RIEUL OE CHIEUCH - 0x8F87: 0xB8C8, //HANGUL SYLLABLE RIEUL OE KHIEUKH - 0x8F88: 0xB8C9, //HANGUL SYLLABLE RIEUL OE THIEUTH - 0x8F89: 0xB8CA, //HANGUL SYLLABLE RIEUL OE PHIEUPH - 0x8F8A: 0xB8CB, //HANGUL SYLLABLE RIEUL OE HIEUH - 0x8F8B: 0xB8CD, //HANGUL SYLLABLE RIEUL YO KIYEOK - 0x8F8C: 0xB8CE, //HANGUL SYLLABLE RIEUL YO SSANGKIYEOK - 0x8F8D: 0xB8CF, //HANGUL SYLLABLE RIEUL YO KIYEOKSIOS - 0x8F8E: 0xB8D1, //HANGUL SYLLABLE RIEUL YO NIEUNCIEUC - 0x8F8F: 0xB8D2, //HANGUL SYLLABLE RIEUL YO NIEUNHIEUH - 0x8F90: 0xB8D3, //HANGUL SYLLABLE RIEUL YO TIKEUT - 0x8F91: 0xB8D5, //HANGUL SYLLABLE RIEUL YO RIEULKIYEOK - 0x8F92: 0xB8D6, //HANGUL SYLLABLE RIEUL YO RIEULMIEUM - 0x8F93: 0xB8D7, //HANGUL SYLLABLE RIEUL YO RIEULPIEUP - 0x8F94: 0xB8D8, //HANGUL SYLLABLE RIEUL YO RIEULSIOS - 0x8F95: 0xB8D9, //HANGUL SYLLABLE RIEUL YO RIEULTHIEUTH - 0x8F96: 0xB8DA, //HANGUL SYLLABLE RIEUL YO RIEULPHIEUPH - 0x8F97: 0xB8DB, //HANGUL SYLLABLE RIEUL YO RIEULHIEUH - 0x8F98: 0xB8DC, //HANGUL SYLLABLE RIEUL YO MIEUM - 0x8F99: 0xB8DE, //HANGUL SYLLABLE RIEUL YO PIEUPSIOS - 0x8F9A: 0xB8E0, //HANGUL SYLLABLE RIEUL YO SSANGSIOS - 0x8F9B: 0xB8E2, //HANGUL SYLLABLE RIEUL YO CIEUC - 0x8F9C: 0xB8E3, //HANGUL SYLLABLE RIEUL YO CHIEUCH - 0x8F9D: 0xB8E4, //HANGUL SYLLABLE RIEUL YO KHIEUKH - 0x8F9E: 0xB8E5, //HANGUL SYLLABLE RIEUL YO THIEUTH - 0x8F9F: 0xB8E6, //HANGUL SYLLABLE RIEUL YO PHIEUPH - 0x8FA0: 0xB8E7, //HANGUL SYLLABLE RIEUL YO HIEUH - 0x8FA1: 0xB8EA, //HANGUL SYLLABLE RIEUL U SSANGKIYEOK - 0x8FA2: 0xB8EB, //HANGUL SYLLABLE RIEUL U KIYEOKSIOS - 0x8FA3: 0xB8ED, //HANGUL SYLLABLE RIEUL U NIEUNCIEUC - 0x8FA4: 0xB8EE, //HANGUL SYLLABLE RIEUL U NIEUNHIEUH - 0x8FA5: 0xB8EF, //HANGUL SYLLABLE RIEUL U TIKEUT - 0x8FA6: 0xB8F1, //HANGUL SYLLABLE RIEUL U RIEULKIYEOK - 0x8FA7: 0xB8F2, //HANGUL SYLLABLE RIEUL U RIEULMIEUM - 0x8FA8: 0xB8F3, //HANGUL SYLLABLE RIEUL U RIEULPIEUP - 0x8FA9: 0xB8F4, //HANGUL SYLLABLE RIEUL U RIEULSIOS - 0x8FAA: 0xB8F5, //HANGUL SYLLABLE RIEUL U RIEULTHIEUTH - 0x8FAB: 0xB8F6, //HANGUL SYLLABLE RIEUL U RIEULPHIEUPH - 0x8FAC: 0xB8F7, //HANGUL SYLLABLE RIEUL U RIEULHIEUH - 0x8FAD: 0xB8FA, //HANGUL SYLLABLE RIEUL U PIEUPSIOS - 0x8FAE: 0xB8FC, //HANGUL SYLLABLE RIEUL U SSANGSIOS - 0x8FAF: 0xB8FE, //HANGUL SYLLABLE RIEUL U CIEUC - 0x8FB0: 0xB8FF, //HANGUL SYLLABLE RIEUL U CHIEUCH - 0x8FB1: 0xB900, //HANGUL SYLLABLE RIEUL U KHIEUKH - 0x8FB2: 0xB901, //HANGUL SYLLABLE RIEUL U THIEUTH - 0x8FB3: 0xB902, //HANGUL SYLLABLE RIEUL U PHIEUPH - 0x8FB4: 0xB903, //HANGUL SYLLABLE RIEUL U HIEUH - 0x8FB5: 0xB905, //HANGUL SYLLABLE RIEUL WEO KIYEOK - 0x8FB6: 0xB906, //HANGUL SYLLABLE RIEUL WEO SSANGKIYEOK - 0x8FB7: 0xB907, //HANGUL SYLLABLE RIEUL WEO KIYEOKSIOS - 0x8FB8: 0xB908, //HANGUL SYLLABLE RIEUL WEO NIEUN - 0x8FB9: 0xB909, //HANGUL SYLLABLE RIEUL WEO NIEUNCIEUC - 0x8FBA: 0xB90A, //HANGUL SYLLABLE RIEUL WEO NIEUNHIEUH - 0x8FBB: 0xB90B, //HANGUL SYLLABLE RIEUL WEO TIKEUT - 0x8FBC: 0xB90C, //HANGUL SYLLABLE RIEUL WEO RIEUL - 0x8FBD: 0xB90D, //HANGUL SYLLABLE RIEUL WEO RIEULKIYEOK - 0x8FBE: 0xB90E, //HANGUL SYLLABLE RIEUL WEO RIEULMIEUM - 0x8FBF: 0xB90F, //HANGUL SYLLABLE RIEUL WEO RIEULPIEUP - 0x8FC0: 0xB910, //HANGUL SYLLABLE RIEUL WEO RIEULSIOS - 0x8FC1: 0xB911, //HANGUL SYLLABLE RIEUL WEO RIEULTHIEUTH - 0x8FC2: 0xB912, //HANGUL SYLLABLE RIEUL WEO RIEULPHIEUPH - 0x8FC3: 0xB913, //HANGUL SYLLABLE RIEUL WEO RIEULHIEUH - 0x8FC4: 0xB914, //HANGUL SYLLABLE RIEUL WEO MIEUM - 0x8FC5: 0xB915, //HANGUL SYLLABLE RIEUL WEO PIEUP - 0x8FC6: 0xB916, //HANGUL SYLLABLE RIEUL WEO PIEUPSIOS - 0x8FC7: 0xB917, //HANGUL SYLLABLE RIEUL WEO SIOS - 0x8FC8: 0xB919, //HANGUL SYLLABLE RIEUL WEO IEUNG - 0x8FC9: 0xB91A, //HANGUL SYLLABLE RIEUL WEO CIEUC - 0x8FCA: 0xB91B, //HANGUL SYLLABLE RIEUL WEO CHIEUCH - 0x8FCB: 0xB91C, //HANGUL SYLLABLE RIEUL WEO KHIEUKH - 0x8FCC: 0xB91D, //HANGUL SYLLABLE RIEUL WEO THIEUTH - 0x8FCD: 0xB91E, //HANGUL SYLLABLE RIEUL WEO PHIEUPH - 0x8FCE: 0xB91F, //HANGUL SYLLABLE RIEUL WEO HIEUH - 0x8FCF: 0xB921, //HANGUL SYLLABLE RIEUL WE KIYEOK - 0x8FD0: 0xB922, //HANGUL SYLLABLE RIEUL WE SSANGKIYEOK - 0x8FD1: 0xB923, //HANGUL SYLLABLE RIEUL WE KIYEOKSIOS - 0x8FD2: 0xB924, //HANGUL SYLLABLE RIEUL WE NIEUN - 0x8FD3: 0xB925, //HANGUL SYLLABLE RIEUL WE NIEUNCIEUC - 0x8FD4: 0xB926, //HANGUL SYLLABLE RIEUL WE NIEUNHIEUH - 0x8FD5: 0xB927, //HANGUL SYLLABLE RIEUL WE TIKEUT - 0x8FD6: 0xB928, //HANGUL SYLLABLE RIEUL WE RIEUL - 0x8FD7: 0xB929, //HANGUL SYLLABLE RIEUL WE RIEULKIYEOK - 0x8FD8: 0xB92A, //HANGUL SYLLABLE RIEUL WE RIEULMIEUM - 0x8FD9: 0xB92B, //HANGUL SYLLABLE RIEUL WE RIEULPIEUP - 0x8FDA: 0xB92C, //HANGUL SYLLABLE RIEUL WE RIEULSIOS - 0x8FDB: 0xB92D, //HANGUL SYLLABLE RIEUL WE RIEULTHIEUTH - 0x8FDC: 0xB92E, //HANGUL SYLLABLE RIEUL WE RIEULPHIEUPH - 0x8FDD: 0xB92F, //HANGUL SYLLABLE RIEUL WE RIEULHIEUH - 0x8FDE: 0xB930, //HANGUL SYLLABLE RIEUL WE MIEUM - 0x8FDF: 0xB931, //HANGUL SYLLABLE RIEUL WE PIEUP - 0x8FE0: 0xB932, //HANGUL SYLLABLE RIEUL WE PIEUPSIOS - 0x8FE1: 0xB933, //HANGUL SYLLABLE RIEUL WE SIOS - 0x8FE2: 0xB934, //HANGUL SYLLABLE RIEUL WE SSANGSIOS - 0x8FE3: 0xB935, //HANGUL SYLLABLE RIEUL WE IEUNG - 0x8FE4: 0xB936, //HANGUL SYLLABLE RIEUL WE CIEUC - 0x8FE5: 0xB937, //HANGUL SYLLABLE RIEUL WE CHIEUCH - 0x8FE6: 0xB938, //HANGUL SYLLABLE RIEUL WE KHIEUKH - 0x8FE7: 0xB939, //HANGUL SYLLABLE RIEUL WE THIEUTH - 0x8FE8: 0xB93A, //HANGUL SYLLABLE RIEUL WE PHIEUPH - 0x8FE9: 0xB93B, //HANGUL SYLLABLE RIEUL WE HIEUH - 0x8FEA: 0xB93E, //HANGUL SYLLABLE RIEUL WI SSANGKIYEOK - 0x8FEB: 0xB93F, //HANGUL SYLLABLE RIEUL WI KIYEOKSIOS - 0x8FEC: 0xB941, //HANGUL SYLLABLE RIEUL WI NIEUNCIEUC - 0x8FED: 0xB942, //HANGUL SYLLABLE RIEUL WI NIEUNHIEUH - 0x8FEE: 0xB943, //HANGUL SYLLABLE RIEUL WI TIKEUT - 0x8FEF: 0xB945, //HANGUL SYLLABLE RIEUL WI RIEULKIYEOK - 0x8FF0: 0xB946, //HANGUL SYLLABLE RIEUL WI RIEULMIEUM - 0x8FF1: 0xB947, //HANGUL SYLLABLE RIEUL WI RIEULPIEUP - 0x8FF2: 0xB948, //HANGUL SYLLABLE RIEUL WI RIEULSIOS - 0x8FF3: 0xB949, //HANGUL SYLLABLE RIEUL WI RIEULTHIEUTH - 0x8FF4: 0xB94A, //HANGUL SYLLABLE RIEUL WI RIEULPHIEUPH - 0x8FF5: 0xB94B, //HANGUL SYLLABLE RIEUL WI RIEULHIEUH - 0x8FF6: 0xB94D, //HANGUL SYLLABLE RIEUL WI PIEUP - 0x8FF7: 0xB94E, //HANGUL SYLLABLE RIEUL WI PIEUPSIOS - 0x8FF8: 0xB950, //HANGUL SYLLABLE RIEUL WI SSANGSIOS - 0x8FF9: 0xB952, //HANGUL SYLLABLE RIEUL WI CIEUC - 0x8FFA: 0xB953, //HANGUL SYLLABLE RIEUL WI CHIEUCH - 0x8FFB: 0xB954, //HANGUL SYLLABLE RIEUL WI KHIEUKH - 0x8FFC: 0xB955, //HANGUL SYLLABLE RIEUL WI THIEUTH - 0x8FFD: 0xB956, //HANGUL SYLLABLE RIEUL WI PHIEUPH - 0x8FFE: 0xB957, //HANGUL SYLLABLE RIEUL WI HIEUH - 0x9041: 0xB95A, //HANGUL SYLLABLE RIEUL YU SSANGKIYEOK - 0x9042: 0xB95B, //HANGUL SYLLABLE RIEUL YU KIYEOKSIOS - 0x9043: 0xB95D, //HANGUL SYLLABLE RIEUL YU NIEUNCIEUC - 0x9044: 0xB95E, //HANGUL SYLLABLE RIEUL YU NIEUNHIEUH - 0x9045: 0xB95F, //HANGUL SYLLABLE RIEUL YU TIKEUT - 0x9046: 0xB961, //HANGUL SYLLABLE RIEUL YU RIEULKIYEOK - 0x9047: 0xB962, //HANGUL SYLLABLE RIEUL YU RIEULMIEUM - 0x9048: 0xB963, //HANGUL SYLLABLE RIEUL YU RIEULPIEUP - 0x9049: 0xB964, //HANGUL SYLLABLE RIEUL YU RIEULSIOS - 0x904A: 0xB965, //HANGUL SYLLABLE RIEUL YU RIEULTHIEUTH - 0x904B: 0xB966, //HANGUL SYLLABLE RIEUL YU RIEULPHIEUPH - 0x904C: 0xB967, //HANGUL SYLLABLE RIEUL YU RIEULHIEUH - 0x904D: 0xB96A, //HANGUL SYLLABLE RIEUL YU PIEUPSIOS - 0x904E: 0xB96C, //HANGUL SYLLABLE RIEUL YU SSANGSIOS - 0x904F: 0xB96E, //HANGUL SYLLABLE RIEUL YU CIEUC - 0x9050: 0xB96F, //HANGUL SYLLABLE RIEUL YU CHIEUCH - 0x9051: 0xB970, //HANGUL SYLLABLE RIEUL YU KHIEUKH - 0x9052: 0xB971, //HANGUL SYLLABLE RIEUL YU THIEUTH - 0x9053: 0xB972, //HANGUL SYLLABLE RIEUL YU PHIEUPH - 0x9054: 0xB973, //HANGUL SYLLABLE RIEUL YU HIEUH - 0x9055: 0xB976, //HANGUL SYLLABLE RIEUL EU SSANGKIYEOK - 0x9056: 0xB977, //HANGUL SYLLABLE RIEUL EU KIYEOKSIOS - 0x9057: 0xB979, //HANGUL SYLLABLE RIEUL EU NIEUNCIEUC - 0x9058: 0xB97A, //HANGUL SYLLABLE RIEUL EU NIEUNHIEUH - 0x9059: 0xB97B, //HANGUL SYLLABLE RIEUL EU TIKEUT - 0x905A: 0xB97D, //HANGUL SYLLABLE RIEUL EU RIEULKIYEOK - 0x9061: 0xB97E, //HANGUL SYLLABLE RIEUL EU RIEULMIEUM - 0x9062: 0xB97F, //HANGUL SYLLABLE RIEUL EU RIEULPIEUP - 0x9063: 0xB980, //HANGUL SYLLABLE RIEUL EU RIEULSIOS - 0x9064: 0xB981, //HANGUL SYLLABLE RIEUL EU RIEULTHIEUTH - 0x9065: 0xB982, //HANGUL SYLLABLE RIEUL EU RIEULPHIEUPH - 0x9066: 0xB983, //HANGUL SYLLABLE RIEUL EU RIEULHIEUH - 0x9067: 0xB986, //HANGUL SYLLABLE RIEUL EU PIEUPSIOS - 0x9068: 0xB988, //HANGUL SYLLABLE RIEUL EU SSANGSIOS - 0x9069: 0xB98B, //HANGUL SYLLABLE RIEUL EU CHIEUCH - 0x906A: 0xB98C, //HANGUL SYLLABLE RIEUL EU KHIEUKH - 0x906B: 0xB98F, //HANGUL SYLLABLE RIEUL EU HIEUH - 0x906C: 0xB990, //HANGUL SYLLABLE RIEUL YI - 0x906D: 0xB991, //HANGUL SYLLABLE RIEUL YI KIYEOK - 0x906E: 0xB992, //HANGUL SYLLABLE RIEUL YI SSANGKIYEOK - 0x906F: 0xB993, //HANGUL SYLLABLE RIEUL YI KIYEOKSIOS - 0x9070: 0xB994, //HANGUL SYLLABLE RIEUL YI NIEUN - 0x9071: 0xB995, //HANGUL SYLLABLE RIEUL YI NIEUNCIEUC - 0x9072: 0xB996, //HANGUL SYLLABLE RIEUL YI NIEUNHIEUH - 0x9073: 0xB997, //HANGUL SYLLABLE RIEUL YI TIKEUT - 0x9074: 0xB998, //HANGUL SYLLABLE RIEUL YI RIEUL - 0x9075: 0xB999, //HANGUL SYLLABLE RIEUL YI RIEULKIYEOK - 0x9076: 0xB99A, //HANGUL SYLLABLE RIEUL YI RIEULMIEUM - 0x9077: 0xB99B, //HANGUL SYLLABLE RIEUL YI RIEULPIEUP - 0x9078: 0xB99C, //HANGUL SYLLABLE RIEUL YI RIEULSIOS - 0x9079: 0xB99D, //HANGUL SYLLABLE RIEUL YI RIEULTHIEUTH - 0x907A: 0xB99E, //HANGUL SYLLABLE RIEUL YI RIEULPHIEUPH - 0x9081: 0xB99F, //HANGUL SYLLABLE RIEUL YI RIEULHIEUH - 0x9082: 0xB9A0, //HANGUL SYLLABLE RIEUL YI MIEUM - 0x9083: 0xB9A1, //HANGUL SYLLABLE RIEUL YI PIEUP - 0x9084: 0xB9A2, //HANGUL SYLLABLE RIEUL YI PIEUPSIOS - 0x9085: 0xB9A3, //HANGUL SYLLABLE RIEUL YI SIOS - 0x9086: 0xB9A4, //HANGUL SYLLABLE RIEUL YI SSANGSIOS - 0x9087: 0xB9A5, //HANGUL SYLLABLE RIEUL YI IEUNG - 0x9088: 0xB9A6, //HANGUL SYLLABLE RIEUL YI CIEUC - 0x9089: 0xB9A7, //HANGUL SYLLABLE RIEUL YI CHIEUCH - 0x908A: 0xB9A8, //HANGUL SYLLABLE RIEUL YI KHIEUKH - 0x908B: 0xB9A9, //HANGUL SYLLABLE RIEUL YI THIEUTH - 0x908C: 0xB9AA, //HANGUL SYLLABLE RIEUL YI PHIEUPH - 0x908D: 0xB9AB, //HANGUL SYLLABLE RIEUL YI HIEUH - 0x908E: 0xB9AE, //HANGUL SYLLABLE RIEUL I SSANGKIYEOK - 0x908F: 0xB9AF, //HANGUL SYLLABLE RIEUL I KIYEOKSIOS - 0x9090: 0xB9B1, //HANGUL SYLLABLE RIEUL I NIEUNCIEUC - 0x9091: 0xB9B2, //HANGUL SYLLABLE RIEUL I NIEUNHIEUH - 0x9092: 0xB9B3, //HANGUL SYLLABLE RIEUL I TIKEUT - 0x9093: 0xB9B5, //HANGUL SYLLABLE RIEUL I RIEULKIYEOK - 0x9094: 0xB9B6, //HANGUL SYLLABLE RIEUL I RIEULMIEUM - 0x9095: 0xB9B7, //HANGUL SYLLABLE RIEUL I RIEULPIEUP - 0x9096: 0xB9B8, //HANGUL SYLLABLE RIEUL I RIEULSIOS - 0x9097: 0xB9B9, //HANGUL SYLLABLE RIEUL I RIEULTHIEUTH - 0x9098: 0xB9BA, //HANGUL SYLLABLE RIEUL I RIEULPHIEUPH - 0x9099: 0xB9BB, //HANGUL SYLLABLE RIEUL I RIEULHIEUH - 0x909A: 0xB9BE, //HANGUL SYLLABLE RIEUL I PIEUPSIOS - 0x909B: 0xB9C0, //HANGUL SYLLABLE RIEUL I SSANGSIOS - 0x909C: 0xB9C2, //HANGUL SYLLABLE RIEUL I CIEUC - 0x909D: 0xB9C3, //HANGUL SYLLABLE RIEUL I CHIEUCH - 0x909E: 0xB9C4, //HANGUL SYLLABLE RIEUL I KHIEUKH - 0x909F: 0xB9C5, //HANGUL SYLLABLE RIEUL I THIEUTH - 0x90A0: 0xB9C6, //HANGUL SYLLABLE RIEUL I PHIEUPH - 0x90A1: 0xB9C7, //HANGUL SYLLABLE RIEUL I HIEUH - 0x90A2: 0xB9CA, //HANGUL SYLLABLE MIEUM A SSANGKIYEOK - 0x90A3: 0xB9CB, //HANGUL SYLLABLE MIEUM A KIYEOKSIOS - 0x90A4: 0xB9CD, //HANGUL SYLLABLE MIEUM A NIEUNCIEUC - 0x90A5: 0xB9D3, //HANGUL SYLLABLE MIEUM A RIEULPIEUP - 0x90A6: 0xB9D4, //HANGUL SYLLABLE MIEUM A RIEULSIOS - 0x90A7: 0xB9D5, //HANGUL SYLLABLE MIEUM A RIEULTHIEUTH - 0x90A8: 0xB9D6, //HANGUL SYLLABLE MIEUM A RIEULPHIEUPH - 0x90A9: 0xB9D7, //HANGUL SYLLABLE MIEUM A RIEULHIEUH - 0x90AA: 0xB9DA, //HANGUL SYLLABLE MIEUM A PIEUPSIOS - 0x90AB: 0xB9DC, //HANGUL SYLLABLE MIEUM A SSANGSIOS - 0x90AC: 0xB9DF, //HANGUL SYLLABLE MIEUM A CHIEUCH - 0x90AD: 0xB9E0, //HANGUL SYLLABLE MIEUM A KHIEUKH - 0x90AE: 0xB9E2, //HANGUL SYLLABLE MIEUM A PHIEUPH - 0x90AF: 0xB9E6, //HANGUL SYLLABLE MIEUM AE SSANGKIYEOK - 0x90B0: 0xB9E7, //HANGUL SYLLABLE MIEUM AE KIYEOKSIOS - 0x90B1: 0xB9E9, //HANGUL SYLLABLE MIEUM AE NIEUNCIEUC - 0x90B2: 0xB9EA, //HANGUL SYLLABLE MIEUM AE NIEUNHIEUH - 0x90B3: 0xB9EB, //HANGUL SYLLABLE MIEUM AE TIKEUT - 0x90B4: 0xB9ED, //HANGUL SYLLABLE MIEUM AE RIEULKIYEOK - 0x90B5: 0xB9EE, //HANGUL SYLLABLE MIEUM AE RIEULMIEUM - 0x90B6: 0xB9EF, //HANGUL SYLLABLE MIEUM AE RIEULPIEUP - 0x90B7: 0xB9F0, //HANGUL SYLLABLE MIEUM AE RIEULSIOS - 0x90B8: 0xB9F1, //HANGUL SYLLABLE MIEUM AE RIEULTHIEUTH - 0x90B9: 0xB9F2, //HANGUL SYLLABLE MIEUM AE RIEULPHIEUPH - 0x90BA: 0xB9F3, //HANGUL SYLLABLE MIEUM AE RIEULHIEUH - 0x90BB: 0xB9F6, //HANGUL SYLLABLE MIEUM AE PIEUPSIOS - 0x90BC: 0xB9FB, //HANGUL SYLLABLE MIEUM AE CHIEUCH - 0x90BD: 0xB9FC, //HANGUL SYLLABLE MIEUM AE KHIEUKH - 0x90BE: 0xB9FD, //HANGUL SYLLABLE MIEUM AE THIEUTH - 0x90BF: 0xB9FE, //HANGUL SYLLABLE MIEUM AE PHIEUPH - 0x90C0: 0xB9FF, //HANGUL SYLLABLE MIEUM AE HIEUH - 0x90C1: 0xBA02, //HANGUL SYLLABLE MIEUM YA SSANGKIYEOK - 0x90C2: 0xBA03, //HANGUL SYLLABLE MIEUM YA KIYEOKSIOS - 0x90C3: 0xBA04, //HANGUL SYLLABLE MIEUM YA NIEUN - 0x90C4: 0xBA05, //HANGUL SYLLABLE MIEUM YA NIEUNCIEUC - 0x90C5: 0xBA06, //HANGUL SYLLABLE MIEUM YA NIEUNHIEUH - 0x90C6: 0xBA07, //HANGUL SYLLABLE MIEUM YA TIKEUT - 0x90C7: 0xBA09, //HANGUL SYLLABLE MIEUM YA RIEULKIYEOK - 0x90C8: 0xBA0A, //HANGUL SYLLABLE MIEUM YA RIEULMIEUM - 0x90C9: 0xBA0B, //HANGUL SYLLABLE MIEUM YA RIEULPIEUP - 0x90CA: 0xBA0C, //HANGUL SYLLABLE MIEUM YA RIEULSIOS - 0x90CB: 0xBA0D, //HANGUL SYLLABLE MIEUM YA RIEULTHIEUTH - 0x90CC: 0xBA0E, //HANGUL SYLLABLE MIEUM YA RIEULPHIEUPH - 0x90CD: 0xBA0F, //HANGUL SYLLABLE MIEUM YA RIEULHIEUH - 0x90CE: 0xBA10, //HANGUL SYLLABLE MIEUM YA MIEUM - 0x90CF: 0xBA11, //HANGUL SYLLABLE MIEUM YA PIEUP - 0x90D0: 0xBA12, //HANGUL SYLLABLE MIEUM YA PIEUPSIOS - 0x90D1: 0xBA13, //HANGUL SYLLABLE MIEUM YA SIOS - 0x90D2: 0xBA14, //HANGUL SYLLABLE MIEUM YA SSANGSIOS - 0x90D3: 0xBA16, //HANGUL SYLLABLE MIEUM YA CIEUC - 0x90D4: 0xBA17, //HANGUL SYLLABLE MIEUM YA CHIEUCH - 0x90D5: 0xBA18, //HANGUL SYLLABLE MIEUM YA KHIEUKH - 0x90D6: 0xBA19, //HANGUL SYLLABLE MIEUM YA THIEUTH - 0x90D7: 0xBA1A, //HANGUL SYLLABLE MIEUM YA PHIEUPH - 0x90D8: 0xBA1B, //HANGUL SYLLABLE MIEUM YA HIEUH - 0x90D9: 0xBA1C, //HANGUL SYLLABLE MIEUM YAE - 0x90DA: 0xBA1D, //HANGUL SYLLABLE MIEUM YAE KIYEOK - 0x90DB: 0xBA1E, //HANGUL SYLLABLE MIEUM YAE SSANGKIYEOK - 0x90DC: 0xBA1F, //HANGUL SYLLABLE MIEUM YAE KIYEOKSIOS - 0x90DD: 0xBA20, //HANGUL SYLLABLE MIEUM YAE NIEUN - 0x90DE: 0xBA21, //HANGUL SYLLABLE MIEUM YAE NIEUNCIEUC - 0x90DF: 0xBA22, //HANGUL SYLLABLE MIEUM YAE NIEUNHIEUH - 0x90E0: 0xBA23, //HANGUL SYLLABLE MIEUM YAE TIKEUT - 0x90E1: 0xBA24, //HANGUL SYLLABLE MIEUM YAE RIEUL - 0x90E2: 0xBA25, //HANGUL SYLLABLE MIEUM YAE RIEULKIYEOK - 0x90E3: 0xBA26, //HANGUL SYLLABLE MIEUM YAE RIEULMIEUM - 0x90E4: 0xBA27, //HANGUL SYLLABLE MIEUM YAE RIEULPIEUP - 0x90E5: 0xBA28, //HANGUL SYLLABLE MIEUM YAE RIEULSIOS - 0x90E6: 0xBA29, //HANGUL SYLLABLE MIEUM YAE RIEULTHIEUTH - 0x90E7: 0xBA2A, //HANGUL SYLLABLE MIEUM YAE RIEULPHIEUPH - 0x90E8: 0xBA2B, //HANGUL SYLLABLE MIEUM YAE RIEULHIEUH - 0x90E9: 0xBA2C, //HANGUL SYLLABLE MIEUM YAE MIEUM - 0x90EA: 0xBA2D, //HANGUL SYLLABLE MIEUM YAE PIEUP - 0x90EB: 0xBA2E, //HANGUL SYLLABLE MIEUM YAE PIEUPSIOS - 0x90EC: 0xBA2F, //HANGUL SYLLABLE MIEUM YAE SIOS - 0x90ED: 0xBA30, //HANGUL SYLLABLE MIEUM YAE SSANGSIOS - 0x90EE: 0xBA31, //HANGUL SYLLABLE MIEUM YAE IEUNG - 0x90EF: 0xBA32, //HANGUL SYLLABLE MIEUM YAE CIEUC - 0x90F0: 0xBA33, //HANGUL SYLLABLE MIEUM YAE CHIEUCH - 0x90F1: 0xBA34, //HANGUL SYLLABLE MIEUM YAE KHIEUKH - 0x90F2: 0xBA35, //HANGUL SYLLABLE MIEUM YAE THIEUTH - 0x90F3: 0xBA36, //HANGUL SYLLABLE MIEUM YAE PHIEUPH - 0x90F4: 0xBA37, //HANGUL SYLLABLE MIEUM YAE HIEUH - 0x90F5: 0xBA3A, //HANGUL SYLLABLE MIEUM EO SSANGKIYEOK - 0x90F6: 0xBA3B, //HANGUL SYLLABLE MIEUM EO KIYEOKSIOS - 0x90F7: 0xBA3D, //HANGUL SYLLABLE MIEUM EO NIEUNCIEUC - 0x90F8: 0xBA3E, //HANGUL SYLLABLE MIEUM EO NIEUNHIEUH - 0x90F9: 0xBA3F, //HANGUL SYLLABLE MIEUM EO TIKEUT - 0x90FA: 0xBA41, //HANGUL SYLLABLE MIEUM EO RIEULKIYEOK - 0x90FB: 0xBA43, //HANGUL SYLLABLE MIEUM EO RIEULPIEUP - 0x90FC: 0xBA44, //HANGUL SYLLABLE MIEUM EO RIEULSIOS - 0x90FD: 0xBA45, //HANGUL SYLLABLE MIEUM EO RIEULTHIEUTH - 0x90FE: 0xBA46, //HANGUL SYLLABLE MIEUM EO RIEULPHIEUPH - 0x9141: 0xBA47, //HANGUL SYLLABLE MIEUM EO RIEULHIEUH - 0x9142: 0xBA4A, //HANGUL SYLLABLE MIEUM EO PIEUPSIOS - 0x9143: 0xBA4C, //HANGUL SYLLABLE MIEUM EO SSANGSIOS - 0x9144: 0xBA4F, //HANGUL SYLLABLE MIEUM EO CHIEUCH - 0x9145: 0xBA50, //HANGUL SYLLABLE MIEUM EO KHIEUKH - 0x9146: 0xBA51, //HANGUL SYLLABLE MIEUM EO THIEUTH - 0x9147: 0xBA52, //HANGUL SYLLABLE MIEUM EO PHIEUPH - 0x9148: 0xBA56, //HANGUL SYLLABLE MIEUM E SSANGKIYEOK - 0x9149: 0xBA57, //HANGUL SYLLABLE MIEUM E KIYEOKSIOS - 0x914A: 0xBA59, //HANGUL SYLLABLE MIEUM E NIEUNCIEUC - 0x914B: 0xBA5A, //HANGUL SYLLABLE MIEUM E NIEUNHIEUH - 0x914C: 0xBA5B, //HANGUL SYLLABLE MIEUM E TIKEUT - 0x914D: 0xBA5D, //HANGUL SYLLABLE MIEUM E RIEULKIYEOK - 0x914E: 0xBA5E, //HANGUL SYLLABLE MIEUM E RIEULMIEUM - 0x914F: 0xBA5F, //HANGUL SYLLABLE MIEUM E RIEULPIEUP - 0x9150: 0xBA60, //HANGUL SYLLABLE MIEUM E RIEULSIOS - 0x9151: 0xBA61, //HANGUL SYLLABLE MIEUM E RIEULTHIEUTH - 0x9152: 0xBA62, //HANGUL SYLLABLE MIEUM E RIEULPHIEUPH - 0x9153: 0xBA63, //HANGUL SYLLABLE MIEUM E RIEULHIEUH - 0x9154: 0xBA66, //HANGUL SYLLABLE MIEUM E PIEUPSIOS - 0x9155: 0xBA6A, //HANGUL SYLLABLE MIEUM E CIEUC - 0x9156: 0xBA6B, //HANGUL SYLLABLE MIEUM E CHIEUCH - 0x9157: 0xBA6C, //HANGUL SYLLABLE MIEUM E KHIEUKH - 0x9158: 0xBA6D, //HANGUL SYLLABLE MIEUM E THIEUTH - 0x9159: 0xBA6E, //HANGUL SYLLABLE MIEUM E PHIEUPH - 0x915A: 0xBA6F, //HANGUL SYLLABLE MIEUM E HIEUH - 0x9161: 0xBA72, //HANGUL SYLLABLE MIEUM YEO SSANGKIYEOK - 0x9162: 0xBA73, //HANGUL SYLLABLE MIEUM YEO KIYEOKSIOS - 0x9163: 0xBA75, //HANGUL SYLLABLE MIEUM YEO NIEUNCIEUC - 0x9164: 0xBA76, //HANGUL SYLLABLE MIEUM YEO NIEUNHIEUH - 0x9165: 0xBA77, //HANGUL SYLLABLE MIEUM YEO TIKEUT - 0x9166: 0xBA79, //HANGUL SYLLABLE MIEUM YEO RIEULKIYEOK - 0x9167: 0xBA7A, //HANGUL SYLLABLE MIEUM YEO RIEULMIEUM - 0x9168: 0xBA7B, //HANGUL SYLLABLE MIEUM YEO RIEULPIEUP - 0x9169: 0xBA7C, //HANGUL SYLLABLE MIEUM YEO RIEULSIOS - 0x916A: 0xBA7D, //HANGUL SYLLABLE MIEUM YEO RIEULTHIEUTH - 0x916B: 0xBA7E, //HANGUL SYLLABLE MIEUM YEO RIEULPHIEUPH - 0x916C: 0xBA7F, //HANGUL SYLLABLE MIEUM YEO RIEULHIEUH - 0x916D: 0xBA80, //HANGUL SYLLABLE MIEUM YEO MIEUM - 0x916E: 0xBA81, //HANGUL SYLLABLE MIEUM YEO PIEUP - 0x916F: 0xBA82, //HANGUL SYLLABLE MIEUM YEO PIEUPSIOS - 0x9170: 0xBA86, //HANGUL SYLLABLE MIEUM YEO CIEUC - 0x9171: 0xBA88, //HANGUL SYLLABLE MIEUM YEO KHIEUKH - 0x9172: 0xBA89, //HANGUL SYLLABLE MIEUM YEO THIEUTH - 0x9173: 0xBA8A, //HANGUL SYLLABLE MIEUM YEO PHIEUPH - 0x9174: 0xBA8B, //HANGUL SYLLABLE MIEUM YEO HIEUH - 0x9175: 0xBA8D, //HANGUL SYLLABLE MIEUM YE KIYEOK - 0x9176: 0xBA8E, //HANGUL SYLLABLE MIEUM YE SSANGKIYEOK - 0x9177: 0xBA8F, //HANGUL SYLLABLE MIEUM YE KIYEOKSIOS - 0x9178: 0xBA90, //HANGUL SYLLABLE MIEUM YE NIEUN - 0x9179: 0xBA91, //HANGUL SYLLABLE MIEUM YE NIEUNCIEUC - 0x917A: 0xBA92, //HANGUL SYLLABLE MIEUM YE NIEUNHIEUH - 0x9181: 0xBA93, //HANGUL SYLLABLE MIEUM YE TIKEUT - 0x9182: 0xBA94, //HANGUL SYLLABLE MIEUM YE RIEUL - 0x9183: 0xBA95, //HANGUL SYLLABLE MIEUM YE RIEULKIYEOK - 0x9184: 0xBA96, //HANGUL SYLLABLE MIEUM YE RIEULMIEUM - 0x9185: 0xBA97, //HANGUL SYLLABLE MIEUM YE RIEULPIEUP - 0x9186: 0xBA98, //HANGUL SYLLABLE MIEUM YE RIEULSIOS - 0x9187: 0xBA99, //HANGUL SYLLABLE MIEUM YE RIEULTHIEUTH - 0x9188: 0xBA9A, //HANGUL SYLLABLE MIEUM YE RIEULPHIEUPH - 0x9189: 0xBA9B, //HANGUL SYLLABLE MIEUM YE RIEULHIEUH - 0x918A: 0xBA9C, //HANGUL SYLLABLE MIEUM YE MIEUM - 0x918B: 0xBA9D, //HANGUL SYLLABLE MIEUM YE PIEUP - 0x918C: 0xBA9E, //HANGUL SYLLABLE MIEUM YE PIEUPSIOS - 0x918D: 0xBA9F, //HANGUL SYLLABLE MIEUM YE SIOS - 0x918E: 0xBAA0, //HANGUL SYLLABLE MIEUM YE SSANGSIOS - 0x918F: 0xBAA1, //HANGUL SYLLABLE MIEUM YE IEUNG - 0x9190: 0xBAA2, //HANGUL SYLLABLE MIEUM YE CIEUC - 0x9191: 0xBAA3, //HANGUL SYLLABLE MIEUM YE CHIEUCH - 0x9192: 0xBAA4, //HANGUL SYLLABLE MIEUM YE KHIEUKH - 0x9193: 0xBAA5, //HANGUL SYLLABLE MIEUM YE THIEUTH - 0x9194: 0xBAA6, //HANGUL SYLLABLE MIEUM YE PHIEUPH - 0x9195: 0xBAA7, //HANGUL SYLLABLE MIEUM YE HIEUH - 0x9196: 0xBAAA, //HANGUL SYLLABLE MIEUM O SSANGKIYEOK - 0x9197: 0xBAAD, //HANGUL SYLLABLE MIEUM O NIEUNCIEUC - 0x9198: 0xBAAE, //HANGUL SYLLABLE MIEUM O NIEUNHIEUH - 0x9199: 0xBAAF, //HANGUL SYLLABLE MIEUM O TIKEUT - 0x919A: 0xBAB1, //HANGUL SYLLABLE MIEUM O RIEULKIYEOK - 0x919B: 0xBAB3, //HANGUL SYLLABLE MIEUM O RIEULPIEUP - 0x919C: 0xBAB4, //HANGUL SYLLABLE MIEUM O RIEULSIOS - 0x919D: 0xBAB5, //HANGUL SYLLABLE MIEUM O RIEULTHIEUTH - 0x919E: 0xBAB6, //HANGUL SYLLABLE MIEUM O RIEULPHIEUPH - 0x919F: 0xBAB7, //HANGUL SYLLABLE MIEUM O RIEULHIEUH - 0x91A0: 0xBABA, //HANGUL SYLLABLE MIEUM O PIEUPSIOS - 0x91A1: 0xBABC, //HANGUL SYLLABLE MIEUM O SSANGSIOS - 0x91A2: 0xBABE, //HANGUL SYLLABLE MIEUM O CIEUC - 0x91A3: 0xBABF, //HANGUL SYLLABLE MIEUM O CHIEUCH - 0x91A4: 0xBAC0, //HANGUL SYLLABLE MIEUM O KHIEUKH - 0x91A5: 0xBAC1, //HANGUL SYLLABLE MIEUM O THIEUTH - 0x91A6: 0xBAC2, //HANGUL SYLLABLE MIEUM O PHIEUPH - 0x91A7: 0xBAC3, //HANGUL SYLLABLE MIEUM O HIEUH - 0x91A8: 0xBAC5, //HANGUL SYLLABLE MIEUM WA KIYEOK - 0x91A9: 0xBAC6, //HANGUL SYLLABLE MIEUM WA SSANGKIYEOK - 0x91AA: 0xBAC7, //HANGUL SYLLABLE MIEUM WA KIYEOKSIOS - 0x91AB: 0xBAC9, //HANGUL SYLLABLE MIEUM WA NIEUNCIEUC - 0x91AC: 0xBACA, //HANGUL SYLLABLE MIEUM WA NIEUNHIEUH - 0x91AD: 0xBACB, //HANGUL SYLLABLE MIEUM WA TIKEUT - 0x91AE: 0xBACC, //HANGUL SYLLABLE MIEUM WA RIEUL - 0x91AF: 0xBACD, //HANGUL SYLLABLE MIEUM WA RIEULKIYEOK - 0x91B0: 0xBACE, //HANGUL SYLLABLE MIEUM WA RIEULMIEUM - 0x91B1: 0xBACF, //HANGUL SYLLABLE MIEUM WA RIEULPIEUP - 0x91B2: 0xBAD0, //HANGUL SYLLABLE MIEUM WA RIEULSIOS - 0x91B3: 0xBAD1, //HANGUL SYLLABLE MIEUM WA RIEULTHIEUTH - 0x91B4: 0xBAD2, //HANGUL SYLLABLE MIEUM WA RIEULPHIEUPH - 0x91B5: 0xBAD3, //HANGUL SYLLABLE MIEUM WA RIEULHIEUH - 0x91B6: 0xBAD4, //HANGUL SYLLABLE MIEUM WA MIEUM - 0x91B7: 0xBAD5, //HANGUL SYLLABLE MIEUM WA PIEUP - 0x91B8: 0xBAD6, //HANGUL SYLLABLE MIEUM WA PIEUPSIOS - 0x91B9: 0xBAD7, //HANGUL SYLLABLE MIEUM WA SIOS - 0x91BA: 0xBADA, //HANGUL SYLLABLE MIEUM WA CIEUC - 0x91BB: 0xBADB, //HANGUL SYLLABLE MIEUM WA CHIEUCH - 0x91BC: 0xBADC, //HANGUL SYLLABLE MIEUM WA KHIEUKH - 0x91BD: 0xBADD, //HANGUL SYLLABLE MIEUM WA THIEUTH - 0x91BE: 0xBADE, //HANGUL SYLLABLE MIEUM WA PHIEUPH - 0x91BF: 0xBADF, //HANGUL SYLLABLE MIEUM WA HIEUH - 0x91C0: 0xBAE0, //HANGUL SYLLABLE MIEUM WAE - 0x91C1: 0xBAE1, //HANGUL SYLLABLE MIEUM WAE KIYEOK - 0x91C2: 0xBAE2, //HANGUL SYLLABLE MIEUM WAE SSANGKIYEOK - 0x91C3: 0xBAE3, //HANGUL SYLLABLE MIEUM WAE KIYEOKSIOS - 0x91C4: 0xBAE4, //HANGUL SYLLABLE MIEUM WAE NIEUN - 0x91C5: 0xBAE5, //HANGUL SYLLABLE MIEUM WAE NIEUNCIEUC - 0x91C6: 0xBAE6, //HANGUL SYLLABLE MIEUM WAE NIEUNHIEUH - 0x91C7: 0xBAE7, //HANGUL SYLLABLE MIEUM WAE TIKEUT - 0x91C8: 0xBAE8, //HANGUL SYLLABLE MIEUM WAE RIEUL - 0x91C9: 0xBAE9, //HANGUL SYLLABLE MIEUM WAE RIEULKIYEOK - 0x91CA: 0xBAEA, //HANGUL SYLLABLE MIEUM WAE RIEULMIEUM - 0x91CB: 0xBAEB, //HANGUL SYLLABLE MIEUM WAE RIEULPIEUP - 0x91CC: 0xBAEC, //HANGUL SYLLABLE MIEUM WAE RIEULSIOS - 0x91CD: 0xBAED, //HANGUL SYLLABLE MIEUM WAE RIEULTHIEUTH - 0x91CE: 0xBAEE, //HANGUL SYLLABLE MIEUM WAE RIEULPHIEUPH - 0x91CF: 0xBAEF, //HANGUL SYLLABLE MIEUM WAE RIEULHIEUH - 0x91D0: 0xBAF0, //HANGUL SYLLABLE MIEUM WAE MIEUM - 0x91D1: 0xBAF1, //HANGUL SYLLABLE MIEUM WAE PIEUP - 0x91D2: 0xBAF2, //HANGUL SYLLABLE MIEUM WAE PIEUPSIOS - 0x91D3: 0xBAF3, //HANGUL SYLLABLE MIEUM WAE SIOS - 0x91D4: 0xBAF4, //HANGUL SYLLABLE MIEUM WAE SSANGSIOS - 0x91D5: 0xBAF5, //HANGUL SYLLABLE MIEUM WAE IEUNG - 0x91D6: 0xBAF6, //HANGUL SYLLABLE MIEUM WAE CIEUC - 0x91D7: 0xBAF7, //HANGUL SYLLABLE MIEUM WAE CHIEUCH - 0x91D8: 0xBAF8, //HANGUL SYLLABLE MIEUM WAE KHIEUKH - 0x91D9: 0xBAF9, //HANGUL SYLLABLE MIEUM WAE THIEUTH - 0x91DA: 0xBAFA, //HANGUL SYLLABLE MIEUM WAE PHIEUPH - 0x91DB: 0xBAFB, //HANGUL SYLLABLE MIEUM WAE HIEUH - 0x91DC: 0xBAFD, //HANGUL SYLLABLE MIEUM OE KIYEOK - 0x91DD: 0xBAFE, //HANGUL SYLLABLE MIEUM OE SSANGKIYEOK - 0x91DE: 0xBAFF, //HANGUL SYLLABLE MIEUM OE KIYEOKSIOS - 0x91DF: 0xBB01, //HANGUL SYLLABLE MIEUM OE NIEUNCIEUC - 0x91E0: 0xBB02, //HANGUL SYLLABLE MIEUM OE NIEUNHIEUH - 0x91E1: 0xBB03, //HANGUL SYLLABLE MIEUM OE TIKEUT - 0x91E2: 0xBB05, //HANGUL SYLLABLE MIEUM OE RIEULKIYEOK - 0x91E3: 0xBB06, //HANGUL SYLLABLE MIEUM OE RIEULMIEUM - 0x91E4: 0xBB07, //HANGUL SYLLABLE MIEUM OE RIEULPIEUP - 0x91E5: 0xBB08, //HANGUL SYLLABLE MIEUM OE RIEULSIOS - 0x91E6: 0xBB09, //HANGUL SYLLABLE MIEUM OE RIEULTHIEUTH - 0x91E7: 0xBB0A, //HANGUL SYLLABLE MIEUM OE RIEULPHIEUPH - 0x91E8: 0xBB0B, //HANGUL SYLLABLE MIEUM OE RIEULHIEUH - 0x91E9: 0xBB0C, //HANGUL SYLLABLE MIEUM OE MIEUM - 0x91EA: 0xBB0E, //HANGUL SYLLABLE MIEUM OE PIEUPSIOS - 0x91EB: 0xBB10, //HANGUL SYLLABLE MIEUM OE SSANGSIOS - 0x91EC: 0xBB12, //HANGUL SYLLABLE MIEUM OE CIEUC - 0x91ED: 0xBB13, //HANGUL SYLLABLE MIEUM OE CHIEUCH - 0x91EE: 0xBB14, //HANGUL SYLLABLE MIEUM OE KHIEUKH - 0x91EF: 0xBB15, //HANGUL SYLLABLE MIEUM OE THIEUTH - 0x91F0: 0xBB16, //HANGUL SYLLABLE MIEUM OE PHIEUPH - 0x91F1: 0xBB17, //HANGUL SYLLABLE MIEUM OE HIEUH - 0x91F2: 0xBB19, //HANGUL SYLLABLE MIEUM YO KIYEOK - 0x91F3: 0xBB1A, //HANGUL SYLLABLE MIEUM YO SSANGKIYEOK - 0x91F4: 0xBB1B, //HANGUL SYLLABLE MIEUM YO KIYEOKSIOS - 0x91F5: 0xBB1D, //HANGUL SYLLABLE MIEUM YO NIEUNCIEUC - 0x91F6: 0xBB1E, //HANGUL SYLLABLE MIEUM YO NIEUNHIEUH - 0x91F7: 0xBB1F, //HANGUL SYLLABLE MIEUM YO TIKEUT - 0x91F8: 0xBB21, //HANGUL SYLLABLE MIEUM YO RIEULKIYEOK - 0x91F9: 0xBB22, //HANGUL SYLLABLE MIEUM YO RIEULMIEUM - 0x91FA: 0xBB23, //HANGUL SYLLABLE MIEUM YO RIEULPIEUP - 0x91FB: 0xBB24, //HANGUL SYLLABLE MIEUM YO RIEULSIOS - 0x91FC: 0xBB25, //HANGUL SYLLABLE MIEUM YO RIEULTHIEUTH - 0x91FD: 0xBB26, //HANGUL SYLLABLE MIEUM YO RIEULPHIEUPH - 0x91FE: 0xBB27, //HANGUL SYLLABLE MIEUM YO RIEULHIEUH - 0x9241: 0xBB28, //HANGUL SYLLABLE MIEUM YO MIEUM - 0x9242: 0xBB2A, //HANGUL SYLLABLE MIEUM YO PIEUPSIOS - 0x9243: 0xBB2C, //HANGUL SYLLABLE MIEUM YO SSANGSIOS - 0x9244: 0xBB2D, //HANGUL SYLLABLE MIEUM YO IEUNG - 0x9245: 0xBB2E, //HANGUL SYLLABLE MIEUM YO CIEUC - 0x9246: 0xBB2F, //HANGUL SYLLABLE MIEUM YO CHIEUCH - 0x9247: 0xBB30, //HANGUL SYLLABLE MIEUM YO KHIEUKH - 0x9248: 0xBB31, //HANGUL SYLLABLE MIEUM YO THIEUTH - 0x9249: 0xBB32, //HANGUL SYLLABLE MIEUM YO PHIEUPH - 0x924A: 0xBB33, //HANGUL SYLLABLE MIEUM YO HIEUH - 0x924B: 0xBB37, //HANGUL SYLLABLE MIEUM U KIYEOKSIOS - 0x924C: 0xBB39, //HANGUL SYLLABLE MIEUM U NIEUNCIEUC - 0x924D: 0xBB3A, //HANGUL SYLLABLE MIEUM U NIEUNHIEUH - 0x924E: 0xBB3F, //HANGUL SYLLABLE MIEUM U RIEULPIEUP - 0x924F: 0xBB40, //HANGUL SYLLABLE MIEUM U RIEULSIOS - 0x9250: 0xBB41, //HANGUL SYLLABLE MIEUM U RIEULTHIEUTH - 0x9251: 0xBB42, //HANGUL SYLLABLE MIEUM U RIEULPHIEUPH - 0x9252: 0xBB43, //HANGUL SYLLABLE MIEUM U RIEULHIEUH - 0x9253: 0xBB46, //HANGUL SYLLABLE MIEUM U PIEUPSIOS - 0x9254: 0xBB48, //HANGUL SYLLABLE MIEUM U SSANGSIOS - 0x9255: 0xBB4A, //HANGUL SYLLABLE MIEUM U CIEUC - 0x9256: 0xBB4B, //HANGUL SYLLABLE MIEUM U CHIEUCH - 0x9257: 0xBB4C, //HANGUL SYLLABLE MIEUM U KHIEUKH - 0x9258: 0xBB4E, //HANGUL SYLLABLE MIEUM U PHIEUPH - 0x9259: 0xBB51, //HANGUL SYLLABLE MIEUM WEO KIYEOK - 0x925A: 0xBB52, //HANGUL SYLLABLE MIEUM WEO SSANGKIYEOK - 0x9261: 0xBB53, //HANGUL SYLLABLE MIEUM WEO KIYEOKSIOS - 0x9262: 0xBB55, //HANGUL SYLLABLE MIEUM WEO NIEUNCIEUC - 0x9263: 0xBB56, //HANGUL SYLLABLE MIEUM WEO NIEUNHIEUH - 0x9264: 0xBB57, //HANGUL SYLLABLE MIEUM WEO TIKEUT - 0x9265: 0xBB59, //HANGUL SYLLABLE MIEUM WEO RIEULKIYEOK - 0x9266: 0xBB5A, //HANGUL SYLLABLE MIEUM WEO RIEULMIEUM - 0x9267: 0xBB5B, //HANGUL SYLLABLE MIEUM WEO RIEULPIEUP - 0x9268: 0xBB5C, //HANGUL SYLLABLE MIEUM WEO RIEULSIOS - 0x9269: 0xBB5D, //HANGUL SYLLABLE MIEUM WEO RIEULTHIEUTH - 0x926A: 0xBB5E, //HANGUL SYLLABLE MIEUM WEO RIEULPHIEUPH - 0x926B: 0xBB5F, //HANGUL SYLLABLE MIEUM WEO RIEULHIEUH - 0x926C: 0xBB60, //HANGUL SYLLABLE MIEUM WEO MIEUM - 0x926D: 0xBB62, //HANGUL SYLLABLE MIEUM WEO PIEUPSIOS - 0x926E: 0xBB64, //HANGUL SYLLABLE MIEUM WEO SSANGSIOS - 0x926F: 0xBB65, //HANGUL SYLLABLE MIEUM WEO IEUNG - 0x9270: 0xBB66, //HANGUL SYLLABLE MIEUM WEO CIEUC - 0x9271: 0xBB67, //HANGUL SYLLABLE MIEUM WEO CHIEUCH - 0x9272: 0xBB68, //HANGUL SYLLABLE MIEUM WEO KHIEUKH - 0x9273: 0xBB69, //HANGUL SYLLABLE MIEUM WEO THIEUTH - 0x9274: 0xBB6A, //HANGUL SYLLABLE MIEUM WEO PHIEUPH - 0x9275: 0xBB6B, //HANGUL SYLLABLE MIEUM WEO HIEUH - 0x9276: 0xBB6D, //HANGUL SYLLABLE MIEUM WE KIYEOK - 0x9277: 0xBB6E, //HANGUL SYLLABLE MIEUM WE SSANGKIYEOK - 0x9278: 0xBB6F, //HANGUL SYLLABLE MIEUM WE KIYEOKSIOS - 0x9279: 0xBB70, //HANGUL SYLLABLE MIEUM WE NIEUN - 0x927A: 0xBB71, //HANGUL SYLLABLE MIEUM WE NIEUNCIEUC - 0x9281: 0xBB72, //HANGUL SYLLABLE MIEUM WE NIEUNHIEUH - 0x9282: 0xBB73, //HANGUL SYLLABLE MIEUM WE TIKEUT - 0x9283: 0xBB74, //HANGUL SYLLABLE MIEUM WE RIEUL - 0x9284: 0xBB75, //HANGUL SYLLABLE MIEUM WE RIEULKIYEOK - 0x9285: 0xBB76, //HANGUL SYLLABLE MIEUM WE RIEULMIEUM - 0x9286: 0xBB77, //HANGUL SYLLABLE MIEUM WE RIEULPIEUP - 0x9287: 0xBB78, //HANGUL SYLLABLE MIEUM WE RIEULSIOS - 0x9288: 0xBB79, //HANGUL SYLLABLE MIEUM WE RIEULTHIEUTH - 0x9289: 0xBB7A, //HANGUL SYLLABLE MIEUM WE RIEULPHIEUPH - 0x928A: 0xBB7B, //HANGUL SYLLABLE MIEUM WE RIEULHIEUH - 0x928B: 0xBB7C, //HANGUL SYLLABLE MIEUM WE MIEUM - 0x928C: 0xBB7D, //HANGUL SYLLABLE MIEUM WE PIEUP - 0x928D: 0xBB7E, //HANGUL SYLLABLE MIEUM WE PIEUPSIOS - 0x928E: 0xBB7F, //HANGUL SYLLABLE MIEUM WE SIOS - 0x928F: 0xBB80, //HANGUL SYLLABLE MIEUM WE SSANGSIOS - 0x9290: 0xBB81, //HANGUL SYLLABLE MIEUM WE IEUNG - 0x9291: 0xBB82, //HANGUL SYLLABLE MIEUM WE CIEUC - 0x9292: 0xBB83, //HANGUL SYLLABLE MIEUM WE CHIEUCH - 0x9293: 0xBB84, //HANGUL SYLLABLE MIEUM WE KHIEUKH - 0x9294: 0xBB85, //HANGUL SYLLABLE MIEUM WE THIEUTH - 0x9295: 0xBB86, //HANGUL SYLLABLE MIEUM WE PHIEUPH - 0x9296: 0xBB87, //HANGUL SYLLABLE MIEUM WE HIEUH - 0x9297: 0xBB89, //HANGUL SYLLABLE MIEUM WI KIYEOK - 0x9298: 0xBB8A, //HANGUL SYLLABLE MIEUM WI SSANGKIYEOK - 0x9299: 0xBB8B, //HANGUL SYLLABLE MIEUM WI KIYEOKSIOS - 0x929A: 0xBB8D, //HANGUL SYLLABLE MIEUM WI NIEUNCIEUC - 0x929B: 0xBB8E, //HANGUL SYLLABLE MIEUM WI NIEUNHIEUH - 0x929C: 0xBB8F, //HANGUL SYLLABLE MIEUM WI TIKEUT - 0x929D: 0xBB91, //HANGUL SYLLABLE MIEUM WI RIEULKIYEOK - 0x929E: 0xBB92, //HANGUL SYLLABLE MIEUM WI RIEULMIEUM - 0x929F: 0xBB93, //HANGUL SYLLABLE MIEUM WI RIEULPIEUP - 0x92A0: 0xBB94, //HANGUL SYLLABLE MIEUM WI RIEULSIOS - 0x92A1: 0xBB95, //HANGUL SYLLABLE MIEUM WI RIEULTHIEUTH - 0x92A2: 0xBB96, //HANGUL SYLLABLE MIEUM WI RIEULPHIEUPH - 0x92A3: 0xBB97, //HANGUL SYLLABLE MIEUM WI RIEULHIEUH - 0x92A4: 0xBB98, //HANGUL SYLLABLE MIEUM WI MIEUM - 0x92A5: 0xBB99, //HANGUL SYLLABLE MIEUM WI PIEUP - 0x92A6: 0xBB9A, //HANGUL SYLLABLE MIEUM WI PIEUPSIOS - 0x92A7: 0xBB9B, //HANGUL SYLLABLE MIEUM WI SIOS - 0x92A8: 0xBB9C, //HANGUL SYLLABLE MIEUM WI SSANGSIOS - 0x92A9: 0xBB9D, //HANGUL SYLLABLE MIEUM WI IEUNG - 0x92AA: 0xBB9E, //HANGUL SYLLABLE MIEUM WI CIEUC - 0x92AB: 0xBB9F, //HANGUL SYLLABLE MIEUM WI CHIEUCH - 0x92AC: 0xBBA0, //HANGUL SYLLABLE MIEUM WI KHIEUKH - 0x92AD: 0xBBA1, //HANGUL SYLLABLE MIEUM WI THIEUTH - 0x92AE: 0xBBA2, //HANGUL SYLLABLE MIEUM WI PHIEUPH - 0x92AF: 0xBBA3, //HANGUL SYLLABLE MIEUM WI HIEUH - 0x92B0: 0xBBA5, //HANGUL SYLLABLE MIEUM YU KIYEOK - 0x92B1: 0xBBA6, //HANGUL SYLLABLE MIEUM YU SSANGKIYEOK - 0x92B2: 0xBBA7, //HANGUL SYLLABLE MIEUM YU KIYEOKSIOS - 0x92B3: 0xBBA9, //HANGUL SYLLABLE MIEUM YU NIEUNCIEUC - 0x92B4: 0xBBAA, //HANGUL SYLLABLE MIEUM YU NIEUNHIEUH - 0x92B5: 0xBBAB, //HANGUL SYLLABLE MIEUM YU TIKEUT - 0x92B6: 0xBBAD, //HANGUL SYLLABLE MIEUM YU RIEULKIYEOK - 0x92B7: 0xBBAE, //HANGUL SYLLABLE MIEUM YU RIEULMIEUM - 0x92B8: 0xBBAF, //HANGUL SYLLABLE MIEUM YU RIEULPIEUP - 0x92B9: 0xBBB0, //HANGUL SYLLABLE MIEUM YU RIEULSIOS - 0x92BA: 0xBBB1, //HANGUL SYLLABLE MIEUM YU RIEULTHIEUTH - 0x92BB: 0xBBB2, //HANGUL SYLLABLE MIEUM YU RIEULPHIEUPH - 0x92BC: 0xBBB3, //HANGUL SYLLABLE MIEUM YU RIEULHIEUH - 0x92BD: 0xBBB5, //HANGUL SYLLABLE MIEUM YU PIEUP - 0x92BE: 0xBBB6, //HANGUL SYLLABLE MIEUM YU PIEUPSIOS - 0x92BF: 0xBBB8, //HANGUL SYLLABLE MIEUM YU SSANGSIOS - 0x92C0: 0xBBB9, //HANGUL SYLLABLE MIEUM YU IEUNG - 0x92C1: 0xBBBA, //HANGUL SYLLABLE MIEUM YU CIEUC - 0x92C2: 0xBBBB, //HANGUL SYLLABLE MIEUM YU CHIEUCH - 0x92C3: 0xBBBC, //HANGUL SYLLABLE MIEUM YU KHIEUKH - 0x92C4: 0xBBBD, //HANGUL SYLLABLE MIEUM YU THIEUTH - 0x92C5: 0xBBBE, //HANGUL SYLLABLE MIEUM YU PHIEUPH - 0x92C6: 0xBBBF, //HANGUL SYLLABLE MIEUM YU HIEUH - 0x92C7: 0xBBC1, //HANGUL SYLLABLE MIEUM EU KIYEOK - 0x92C8: 0xBBC2, //HANGUL SYLLABLE MIEUM EU SSANGKIYEOK - 0x92C9: 0xBBC3, //HANGUL SYLLABLE MIEUM EU KIYEOKSIOS - 0x92CA: 0xBBC5, //HANGUL SYLLABLE MIEUM EU NIEUNCIEUC - 0x92CB: 0xBBC6, //HANGUL SYLLABLE MIEUM EU NIEUNHIEUH - 0x92CC: 0xBBC7, //HANGUL SYLLABLE MIEUM EU TIKEUT - 0x92CD: 0xBBC9, //HANGUL SYLLABLE MIEUM EU RIEULKIYEOK - 0x92CE: 0xBBCA, //HANGUL SYLLABLE MIEUM EU RIEULMIEUM - 0x92CF: 0xBBCB, //HANGUL SYLLABLE MIEUM EU RIEULPIEUP - 0x92D0: 0xBBCC, //HANGUL SYLLABLE MIEUM EU RIEULSIOS - 0x92D1: 0xBBCD, //HANGUL SYLLABLE MIEUM EU RIEULTHIEUTH - 0x92D2: 0xBBCE, //HANGUL SYLLABLE MIEUM EU RIEULPHIEUPH - 0x92D3: 0xBBCF, //HANGUL SYLLABLE MIEUM EU RIEULHIEUH - 0x92D4: 0xBBD1, //HANGUL SYLLABLE MIEUM EU PIEUP - 0x92D5: 0xBBD2, //HANGUL SYLLABLE MIEUM EU PIEUPSIOS - 0x92D6: 0xBBD4, //HANGUL SYLLABLE MIEUM EU SSANGSIOS - 0x92D7: 0xBBD5, //HANGUL SYLLABLE MIEUM EU IEUNG - 0x92D8: 0xBBD6, //HANGUL SYLLABLE MIEUM EU CIEUC - 0x92D9: 0xBBD7, //HANGUL SYLLABLE MIEUM EU CHIEUCH - 0x92DA: 0xBBD8, //HANGUL SYLLABLE MIEUM EU KHIEUKH - 0x92DB: 0xBBD9, //HANGUL SYLLABLE MIEUM EU THIEUTH - 0x92DC: 0xBBDA, //HANGUL SYLLABLE MIEUM EU PHIEUPH - 0x92DD: 0xBBDB, //HANGUL SYLLABLE MIEUM EU HIEUH - 0x92DE: 0xBBDC, //HANGUL SYLLABLE MIEUM YI - 0x92DF: 0xBBDD, //HANGUL SYLLABLE MIEUM YI KIYEOK - 0x92E0: 0xBBDE, //HANGUL SYLLABLE MIEUM YI SSANGKIYEOK - 0x92E1: 0xBBDF, //HANGUL SYLLABLE MIEUM YI KIYEOKSIOS - 0x92E2: 0xBBE0, //HANGUL SYLLABLE MIEUM YI NIEUN - 0x92E3: 0xBBE1, //HANGUL SYLLABLE MIEUM YI NIEUNCIEUC - 0x92E4: 0xBBE2, //HANGUL SYLLABLE MIEUM YI NIEUNHIEUH - 0x92E5: 0xBBE3, //HANGUL SYLLABLE MIEUM YI TIKEUT - 0x92E6: 0xBBE4, //HANGUL SYLLABLE MIEUM YI RIEUL - 0x92E7: 0xBBE5, //HANGUL SYLLABLE MIEUM YI RIEULKIYEOK - 0x92E8: 0xBBE6, //HANGUL SYLLABLE MIEUM YI RIEULMIEUM - 0x92E9: 0xBBE7, //HANGUL SYLLABLE MIEUM YI RIEULPIEUP - 0x92EA: 0xBBE8, //HANGUL SYLLABLE MIEUM YI RIEULSIOS - 0x92EB: 0xBBE9, //HANGUL SYLLABLE MIEUM YI RIEULTHIEUTH - 0x92EC: 0xBBEA, //HANGUL SYLLABLE MIEUM YI RIEULPHIEUPH - 0x92ED: 0xBBEB, //HANGUL SYLLABLE MIEUM YI RIEULHIEUH - 0x92EE: 0xBBEC, //HANGUL SYLLABLE MIEUM YI MIEUM - 0x92EF: 0xBBED, //HANGUL SYLLABLE MIEUM YI PIEUP - 0x92F0: 0xBBEE, //HANGUL SYLLABLE MIEUM YI PIEUPSIOS - 0x92F1: 0xBBEF, //HANGUL SYLLABLE MIEUM YI SIOS - 0x92F2: 0xBBF0, //HANGUL SYLLABLE MIEUM YI SSANGSIOS - 0x92F3: 0xBBF1, //HANGUL SYLLABLE MIEUM YI IEUNG - 0x92F4: 0xBBF2, //HANGUL SYLLABLE MIEUM YI CIEUC - 0x92F5: 0xBBF3, //HANGUL SYLLABLE MIEUM YI CHIEUCH - 0x92F6: 0xBBF4, //HANGUL SYLLABLE MIEUM YI KHIEUKH - 0x92F7: 0xBBF5, //HANGUL SYLLABLE MIEUM YI THIEUTH - 0x92F8: 0xBBF6, //HANGUL SYLLABLE MIEUM YI PHIEUPH - 0x92F9: 0xBBF7, //HANGUL SYLLABLE MIEUM YI HIEUH - 0x92FA: 0xBBFA, //HANGUL SYLLABLE MIEUM I SSANGKIYEOK - 0x92FB: 0xBBFB, //HANGUL SYLLABLE MIEUM I KIYEOKSIOS - 0x92FC: 0xBBFD, //HANGUL SYLLABLE MIEUM I NIEUNCIEUC - 0x92FD: 0xBBFE, //HANGUL SYLLABLE MIEUM I NIEUNHIEUH - 0x92FE: 0xBC01, //HANGUL SYLLABLE MIEUM I RIEULKIYEOK - 0x9341: 0xBC03, //HANGUL SYLLABLE MIEUM I RIEULPIEUP - 0x9342: 0xBC04, //HANGUL SYLLABLE MIEUM I RIEULSIOS - 0x9343: 0xBC05, //HANGUL SYLLABLE MIEUM I RIEULTHIEUTH - 0x9344: 0xBC06, //HANGUL SYLLABLE MIEUM I RIEULPHIEUPH - 0x9345: 0xBC07, //HANGUL SYLLABLE MIEUM I RIEULHIEUH - 0x9346: 0xBC0A, //HANGUL SYLLABLE MIEUM I PIEUPSIOS - 0x9347: 0xBC0E, //HANGUL SYLLABLE MIEUM I CIEUC - 0x9348: 0xBC10, //HANGUL SYLLABLE MIEUM I KHIEUKH - 0x9349: 0xBC12, //HANGUL SYLLABLE MIEUM I PHIEUPH - 0x934A: 0xBC13, //HANGUL SYLLABLE MIEUM I HIEUH - 0x934B: 0xBC19, //HANGUL SYLLABLE PIEUP A NIEUNCIEUC - 0x934C: 0xBC1A, //HANGUL SYLLABLE PIEUP A NIEUNHIEUH - 0x934D: 0xBC20, //HANGUL SYLLABLE PIEUP A RIEULSIOS - 0x934E: 0xBC21, //HANGUL SYLLABLE PIEUP A RIEULTHIEUTH - 0x934F: 0xBC22, //HANGUL SYLLABLE PIEUP A RIEULPHIEUPH - 0x9350: 0xBC23, //HANGUL SYLLABLE PIEUP A RIEULHIEUH - 0x9351: 0xBC26, //HANGUL SYLLABLE PIEUP A PIEUPSIOS - 0x9352: 0xBC28, //HANGUL SYLLABLE PIEUP A SSANGSIOS - 0x9353: 0xBC2A, //HANGUL SYLLABLE PIEUP A CIEUC - 0x9354: 0xBC2B, //HANGUL SYLLABLE PIEUP A CHIEUCH - 0x9355: 0xBC2C, //HANGUL SYLLABLE PIEUP A KHIEUKH - 0x9356: 0xBC2E, //HANGUL SYLLABLE PIEUP A PHIEUPH - 0x9357: 0xBC2F, //HANGUL SYLLABLE PIEUP A HIEUH - 0x9358: 0xBC32, //HANGUL SYLLABLE PIEUP AE SSANGKIYEOK - 0x9359: 0xBC33, //HANGUL SYLLABLE PIEUP AE KIYEOKSIOS - 0x935A: 0xBC35, //HANGUL SYLLABLE PIEUP AE NIEUNCIEUC - 0x9361: 0xBC36, //HANGUL SYLLABLE PIEUP AE NIEUNHIEUH - 0x9362: 0xBC37, //HANGUL SYLLABLE PIEUP AE TIKEUT - 0x9363: 0xBC39, //HANGUL SYLLABLE PIEUP AE RIEULKIYEOK - 0x9364: 0xBC3A, //HANGUL SYLLABLE PIEUP AE RIEULMIEUM - 0x9365: 0xBC3B, //HANGUL SYLLABLE PIEUP AE RIEULPIEUP - 0x9366: 0xBC3C, //HANGUL SYLLABLE PIEUP AE RIEULSIOS - 0x9367: 0xBC3D, //HANGUL SYLLABLE PIEUP AE RIEULTHIEUTH - 0x9368: 0xBC3E, //HANGUL SYLLABLE PIEUP AE RIEULPHIEUPH - 0x9369: 0xBC3F, //HANGUL SYLLABLE PIEUP AE RIEULHIEUH - 0x936A: 0xBC42, //HANGUL SYLLABLE PIEUP AE PIEUPSIOS - 0x936B: 0xBC46, //HANGUL SYLLABLE PIEUP AE CIEUC - 0x936C: 0xBC47, //HANGUL SYLLABLE PIEUP AE CHIEUCH - 0x936D: 0xBC48, //HANGUL SYLLABLE PIEUP AE KHIEUKH - 0x936E: 0xBC4A, //HANGUL SYLLABLE PIEUP AE PHIEUPH - 0x936F: 0xBC4B, //HANGUL SYLLABLE PIEUP AE HIEUH - 0x9370: 0xBC4E, //HANGUL SYLLABLE PIEUP YA SSANGKIYEOK - 0x9371: 0xBC4F, //HANGUL SYLLABLE PIEUP YA KIYEOKSIOS - 0x9372: 0xBC51, //HANGUL SYLLABLE PIEUP YA NIEUNCIEUC - 0x9373: 0xBC52, //HANGUL SYLLABLE PIEUP YA NIEUNHIEUH - 0x9374: 0xBC53, //HANGUL SYLLABLE PIEUP YA TIKEUT - 0x9375: 0xBC54, //HANGUL SYLLABLE PIEUP YA RIEUL - 0x9376: 0xBC55, //HANGUL SYLLABLE PIEUP YA RIEULKIYEOK - 0x9377: 0xBC56, //HANGUL SYLLABLE PIEUP YA RIEULMIEUM - 0x9378: 0xBC57, //HANGUL SYLLABLE PIEUP YA RIEULPIEUP - 0x9379: 0xBC58, //HANGUL SYLLABLE PIEUP YA RIEULSIOS - 0x937A: 0xBC59, //HANGUL SYLLABLE PIEUP YA RIEULTHIEUTH - 0x9381: 0xBC5A, //HANGUL SYLLABLE PIEUP YA RIEULPHIEUPH - 0x9382: 0xBC5B, //HANGUL SYLLABLE PIEUP YA RIEULHIEUH - 0x9383: 0xBC5C, //HANGUL SYLLABLE PIEUP YA MIEUM - 0x9384: 0xBC5E, //HANGUL SYLLABLE PIEUP YA PIEUPSIOS - 0x9385: 0xBC5F, //HANGUL SYLLABLE PIEUP YA SIOS - 0x9386: 0xBC60, //HANGUL SYLLABLE PIEUP YA SSANGSIOS - 0x9387: 0xBC61, //HANGUL SYLLABLE PIEUP YA IEUNG - 0x9388: 0xBC62, //HANGUL SYLLABLE PIEUP YA CIEUC - 0x9389: 0xBC63, //HANGUL SYLLABLE PIEUP YA CHIEUCH - 0x938A: 0xBC64, //HANGUL SYLLABLE PIEUP YA KHIEUKH - 0x938B: 0xBC65, //HANGUL SYLLABLE PIEUP YA THIEUTH - 0x938C: 0xBC66, //HANGUL SYLLABLE PIEUP YA PHIEUPH - 0x938D: 0xBC67, //HANGUL SYLLABLE PIEUP YA HIEUH - 0x938E: 0xBC68, //HANGUL SYLLABLE PIEUP YAE - 0x938F: 0xBC69, //HANGUL SYLLABLE PIEUP YAE KIYEOK - 0x9390: 0xBC6A, //HANGUL SYLLABLE PIEUP YAE SSANGKIYEOK - 0x9391: 0xBC6B, //HANGUL SYLLABLE PIEUP YAE KIYEOKSIOS - 0x9392: 0xBC6C, //HANGUL SYLLABLE PIEUP YAE NIEUN - 0x9393: 0xBC6D, //HANGUL SYLLABLE PIEUP YAE NIEUNCIEUC - 0x9394: 0xBC6E, //HANGUL SYLLABLE PIEUP YAE NIEUNHIEUH - 0x9395: 0xBC6F, //HANGUL SYLLABLE PIEUP YAE TIKEUT - 0x9396: 0xBC70, //HANGUL SYLLABLE PIEUP YAE RIEUL - 0x9397: 0xBC71, //HANGUL SYLLABLE PIEUP YAE RIEULKIYEOK - 0x9398: 0xBC72, //HANGUL SYLLABLE PIEUP YAE RIEULMIEUM - 0x9399: 0xBC73, //HANGUL SYLLABLE PIEUP YAE RIEULPIEUP - 0x939A: 0xBC74, //HANGUL SYLLABLE PIEUP YAE RIEULSIOS - 0x939B: 0xBC75, //HANGUL SYLLABLE PIEUP YAE RIEULTHIEUTH - 0x939C: 0xBC76, //HANGUL SYLLABLE PIEUP YAE RIEULPHIEUPH - 0x939D: 0xBC77, //HANGUL SYLLABLE PIEUP YAE RIEULHIEUH - 0x939E: 0xBC78, //HANGUL SYLLABLE PIEUP YAE MIEUM - 0x939F: 0xBC79, //HANGUL SYLLABLE PIEUP YAE PIEUP - 0x93A0: 0xBC7A, //HANGUL SYLLABLE PIEUP YAE PIEUPSIOS - 0x93A1: 0xBC7B, //HANGUL SYLLABLE PIEUP YAE SIOS - 0x93A2: 0xBC7C, //HANGUL SYLLABLE PIEUP YAE SSANGSIOS - 0x93A3: 0xBC7D, //HANGUL SYLLABLE PIEUP YAE IEUNG - 0x93A4: 0xBC7E, //HANGUL SYLLABLE PIEUP YAE CIEUC - 0x93A5: 0xBC7F, //HANGUL SYLLABLE PIEUP YAE CHIEUCH - 0x93A6: 0xBC80, //HANGUL SYLLABLE PIEUP YAE KHIEUKH - 0x93A7: 0xBC81, //HANGUL SYLLABLE PIEUP YAE THIEUTH - 0x93A8: 0xBC82, //HANGUL SYLLABLE PIEUP YAE PHIEUPH - 0x93A9: 0xBC83, //HANGUL SYLLABLE PIEUP YAE HIEUH - 0x93AA: 0xBC86, //HANGUL SYLLABLE PIEUP EO SSANGKIYEOK - 0x93AB: 0xBC87, //HANGUL SYLLABLE PIEUP EO KIYEOKSIOS - 0x93AC: 0xBC89, //HANGUL SYLLABLE PIEUP EO NIEUNCIEUC - 0x93AD: 0xBC8A, //HANGUL SYLLABLE PIEUP EO NIEUNHIEUH - 0x93AE: 0xBC8D, //HANGUL SYLLABLE PIEUP EO RIEULKIYEOK - 0x93AF: 0xBC8F, //HANGUL SYLLABLE PIEUP EO RIEULPIEUP - 0x93B0: 0xBC90, //HANGUL SYLLABLE PIEUP EO RIEULSIOS - 0x93B1: 0xBC91, //HANGUL SYLLABLE PIEUP EO RIEULTHIEUTH - 0x93B2: 0xBC92, //HANGUL SYLLABLE PIEUP EO RIEULPHIEUPH - 0x93B3: 0xBC93, //HANGUL SYLLABLE PIEUP EO RIEULHIEUH - 0x93B4: 0xBC96, //HANGUL SYLLABLE PIEUP EO PIEUPSIOS - 0x93B5: 0xBC98, //HANGUL SYLLABLE PIEUP EO SSANGSIOS - 0x93B6: 0xBC9B, //HANGUL SYLLABLE PIEUP EO CHIEUCH - 0x93B7: 0xBC9C, //HANGUL SYLLABLE PIEUP EO KHIEUKH - 0x93B8: 0xBC9D, //HANGUL SYLLABLE PIEUP EO THIEUTH - 0x93B9: 0xBC9E, //HANGUL SYLLABLE PIEUP EO PHIEUPH - 0x93BA: 0xBC9F, //HANGUL SYLLABLE PIEUP EO HIEUH - 0x93BB: 0xBCA2, //HANGUL SYLLABLE PIEUP E SSANGKIYEOK - 0x93BC: 0xBCA3, //HANGUL SYLLABLE PIEUP E KIYEOKSIOS - 0x93BD: 0xBCA5, //HANGUL SYLLABLE PIEUP E NIEUNCIEUC - 0x93BE: 0xBCA6, //HANGUL SYLLABLE PIEUP E NIEUNHIEUH - 0x93BF: 0xBCA9, //HANGUL SYLLABLE PIEUP E RIEULKIYEOK - 0x93C0: 0xBCAA, //HANGUL SYLLABLE PIEUP E RIEULMIEUM - 0x93C1: 0xBCAB, //HANGUL SYLLABLE PIEUP E RIEULPIEUP - 0x93C2: 0xBCAC, //HANGUL SYLLABLE PIEUP E RIEULSIOS - 0x93C3: 0xBCAD, //HANGUL SYLLABLE PIEUP E RIEULTHIEUTH - 0x93C4: 0xBCAE, //HANGUL SYLLABLE PIEUP E RIEULPHIEUPH - 0x93C5: 0xBCAF, //HANGUL SYLLABLE PIEUP E RIEULHIEUH - 0x93C6: 0xBCB2, //HANGUL SYLLABLE PIEUP E PIEUPSIOS - 0x93C7: 0xBCB6, //HANGUL SYLLABLE PIEUP E CIEUC - 0x93C8: 0xBCB7, //HANGUL SYLLABLE PIEUP E CHIEUCH - 0x93C9: 0xBCB8, //HANGUL SYLLABLE PIEUP E KHIEUKH - 0x93CA: 0xBCB9, //HANGUL SYLLABLE PIEUP E THIEUTH - 0x93CB: 0xBCBA, //HANGUL SYLLABLE PIEUP E PHIEUPH - 0x93CC: 0xBCBB, //HANGUL SYLLABLE PIEUP E HIEUH - 0x93CD: 0xBCBE, //HANGUL SYLLABLE PIEUP YEO SSANGKIYEOK - 0x93CE: 0xBCBF, //HANGUL SYLLABLE PIEUP YEO KIYEOKSIOS - 0x93CF: 0xBCC1, //HANGUL SYLLABLE PIEUP YEO NIEUNCIEUC - 0x93D0: 0xBCC2, //HANGUL SYLLABLE PIEUP YEO NIEUNHIEUH - 0x93D1: 0xBCC3, //HANGUL SYLLABLE PIEUP YEO TIKEUT - 0x93D2: 0xBCC5, //HANGUL SYLLABLE PIEUP YEO RIEULKIYEOK - 0x93D3: 0xBCC6, //HANGUL SYLLABLE PIEUP YEO RIEULMIEUM - 0x93D4: 0xBCC7, //HANGUL SYLLABLE PIEUP YEO RIEULPIEUP - 0x93D5: 0xBCC8, //HANGUL SYLLABLE PIEUP YEO RIEULSIOS - 0x93D6: 0xBCC9, //HANGUL SYLLABLE PIEUP YEO RIEULTHIEUTH - 0x93D7: 0xBCCA, //HANGUL SYLLABLE PIEUP YEO RIEULPHIEUPH - 0x93D8: 0xBCCB, //HANGUL SYLLABLE PIEUP YEO RIEULHIEUH - 0x93D9: 0xBCCC, //HANGUL SYLLABLE PIEUP YEO MIEUM - 0x93DA: 0xBCCE, //HANGUL SYLLABLE PIEUP YEO PIEUPSIOS - 0x93DB: 0xBCD2, //HANGUL SYLLABLE PIEUP YEO CIEUC - 0x93DC: 0xBCD3, //HANGUL SYLLABLE PIEUP YEO CHIEUCH - 0x93DD: 0xBCD4, //HANGUL SYLLABLE PIEUP YEO KHIEUKH - 0x93DE: 0xBCD6, //HANGUL SYLLABLE PIEUP YEO PHIEUPH - 0x93DF: 0xBCD7, //HANGUL SYLLABLE PIEUP YEO HIEUH - 0x93E0: 0xBCD9, //HANGUL SYLLABLE PIEUP YE KIYEOK - 0x93E1: 0xBCDA, //HANGUL SYLLABLE PIEUP YE SSANGKIYEOK - 0x93E2: 0xBCDB, //HANGUL SYLLABLE PIEUP YE KIYEOKSIOS - 0x93E3: 0xBCDD, //HANGUL SYLLABLE PIEUP YE NIEUNCIEUC - 0x93E4: 0xBCDE, //HANGUL SYLLABLE PIEUP YE NIEUNHIEUH - 0x93E5: 0xBCDF, //HANGUL SYLLABLE PIEUP YE TIKEUT - 0x93E6: 0xBCE0, //HANGUL SYLLABLE PIEUP YE RIEUL - 0x93E7: 0xBCE1, //HANGUL SYLLABLE PIEUP YE RIEULKIYEOK - 0x93E8: 0xBCE2, //HANGUL SYLLABLE PIEUP YE RIEULMIEUM - 0x93E9: 0xBCE3, //HANGUL SYLLABLE PIEUP YE RIEULPIEUP - 0x93EA: 0xBCE4, //HANGUL SYLLABLE PIEUP YE RIEULSIOS - 0x93EB: 0xBCE5, //HANGUL SYLLABLE PIEUP YE RIEULTHIEUTH - 0x93EC: 0xBCE6, //HANGUL SYLLABLE PIEUP YE RIEULPHIEUPH - 0x93ED: 0xBCE7, //HANGUL SYLLABLE PIEUP YE RIEULHIEUH - 0x93EE: 0xBCE8, //HANGUL SYLLABLE PIEUP YE MIEUM - 0x93EF: 0xBCE9, //HANGUL SYLLABLE PIEUP YE PIEUP - 0x93F0: 0xBCEA, //HANGUL SYLLABLE PIEUP YE PIEUPSIOS - 0x93F1: 0xBCEB, //HANGUL SYLLABLE PIEUP YE SIOS - 0x93F2: 0xBCEC, //HANGUL SYLLABLE PIEUP YE SSANGSIOS - 0x93F3: 0xBCED, //HANGUL SYLLABLE PIEUP YE IEUNG - 0x93F4: 0xBCEE, //HANGUL SYLLABLE PIEUP YE CIEUC - 0x93F5: 0xBCEF, //HANGUL SYLLABLE PIEUP YE CHIEUCH - 0x93F6: 0xBCF0, //HANGUL SYLLABLE PIEUP YE KHIEUKH - 0x93F7: 0xBCF1, //HANGUL SYLLABLE PIEUP YE THIEUTH - 0x93F8: 0xBCF2, //HANGUL SYLLABLE PIEUP YE PHIEUPH - 0x93F9: 0xBCF3, //HANGUL SYLLABLE PIEUP YE HIEUH - 0x93FA: 0xBCF7, //HANGUL SYLLABLE PIEUP O KIYEOKSIOS - 0x93FB: 0xBCF9, //HANGUL SYLLABLE PIEUP O NIEUNCIEUC - 0x93FC: 0xBCFA, //HANGUL SYLLABLE PIEUP O NIEUNHIEUH - 0x93FD: 0xBCFB, //HANGUL SYLLABLE PIEUP O TIKEUT - 0x93FE: 0xBCFD, //HANGUL SYLLABLE PIEUP O RIEULKIYEOK - 0x9441: 0xBCFE, //HANGUL SYLLABLE PIEUP O RIEULMIEUM - 0x9442: 0xBCFF, //HANGUL SYLLABLE PIEUP O RIEULPIEUP - 0x9443: 0xBD00, //HANGUL SYLLABLE PIEUP O RIEULSIOS - 0x9444: 0xBD01, //HANGUL SYLLABLE PIEUP O RIEULTHIEUTH - 0x9445: 0xBD02, //HANGUL SYLLABLE PIEUP O RIEULPHIEUPH - 0x9446: 0xBD03, //HANGUL SYLLABLE PIEUP O RIEULHIEUH - 0x9447: 0xBD06, //HANGUL SYLLABLE PIEUP O PIEUPSIOS - 0x9448: 0xBD08, //HANGUL SYLLABLE PIEUP O SSANGSIOS - 0x9449: 0xBD0A, //HANGUL SYLLABLE PIEUP O CIEUC - 0x944A: 0xBD0B, //HANGUL SYLLABLE PIEUP O CHIEUCH - 0x944B: 0xBD0C, //HANGUL SYLLABLE PIEUP O KHIEUKH - 0x944C: 0xBD0D, //HANGUL SYLLABLE PIEUP O THIEUTH - 0x944D: 0xBD0E, //HANGUL SYLLABLE PIEUP O PHIEUPH - 0x944E: 0xBD0F, //HANGUL SYLLABLE PIEUP O HIEUH - 0x944F: 0xBD11, //HANGUL SYLLABLE PIEUP WA KIYEOK - 0x9450: 0xBD12, //HANGUL SYLLABLE PIEUP WA SSANGKIYEOK - 0x9451: 0xBD13, //HANGUL SYLLABLE PIEUP WA KIYEOKSIOS - 0x9452: 0xBD15, //HANGUL SYLLABLE PIEUP WA NIEUNCIEUC - 0x9453: 0xBD16, //HANGUL SYLLABLE PIEUP WA NIEUNHIEUH - 0x9454: 0xBD17, //HANGUL SYLLABLE PIEUP WA TIKEUT - 0x9455: 0xBD18, //HANGUL SYLLABLE PIEUP WA RIEUL - 0x9456: 0xBD19, //HANGUL SYLLABLE PIEUP WA RIEULKIYEOK - 0x9457: 0xBD1A, //HANGUL SYLLABLE PIEUP WA RIEULMIEUM - 0x9458: 0xBD1B, //HANGUL SYLLABLE PIEUP WA RIEULPIEUP - 0x9459: 0xBD1C, //HANGUL SYLLABLE PIEUP WA RIEULSIOS - 0x945A: 0xBD1D, //HANGUL SYLLABLE PIEUP WA RIEULTHIEUTH - 0x9461: 0xBD1E, //HANGUL SYLLABLE PIEUP WA RIEULPHIEUPH - 0x9462: 0xBD1F, //HANGUL SYLLABLE PIEUP WA RIEULHIEUH - 0x9463: 0xBD20, //HANGUL SYLLABLE PIEUP WA MIEUM - 0x9464: 0xBD21, //HANGUL SYLLABLE PIEUP WA PIEUP - 0x9465: 0xBD22, //HANGUL SYLLABLE PIEUP WA PIEUPSIOS - 0x9466: 0xBD23, //HANGUL SYLLABLE PIEUP WA SIOS - 0x9467: 0xBD25, //HANGUL SYLLABLE PIEUP WA IEUNG - 0x9468: 0xBD26, //HANGUL SYLLABLE PIEUP WA CIEUC - 0x9469: 0xBD27, //HANGUL SYLLABLE PIEUP WA CHIEUCH - 0x946A: 0xBD28, //HANGUL SYLLABLE PIEUP WA KHIEUKH - 0x946B: 0xBD29, //HANGUL SYLLABLE PIEUP WA THIEUTH - 0x946C: 0xBD2A, //HANGUL SYLLABLE PIEUP WA PHIEUPH - 0x946D: 0xBD2B, //HANGUL SYLLABLE PIEUP WA HIEUH - 0x946E: 0xBD2D, //HANGUL SYLLABLE PIEUP WAE KIYEOK - 0x946F: 0xBD2E, //HANGUL SYLLABLE PIEUP WAE SSANGKIYEOK - 0x9470: 0xBD2F, //HANGUL SYLLABLE PIEUP WAE KIYEOKSIOS - 0x9471: 0xBD30, //HANGUL SYLLABLE PIEUP WAE NIEUN - 0x9472: 0xBD31, //HANGUL SYLLABLE PIEUP WAE NIEUNCIEUC - 0x9473: 0xBD32, //HANGUL SYLLABLE PIEUP WAE NIEUNHIEUH - 0x9474: 0xBD33, //HANGUL SYLLABLE PIEUP WAE TIKEUT - 0x9475: 0xBD34, //HANGUL SYLLABLE PIEUP WAE RIEUL - 0x9476: 0xBD35, //HANGUL SYLLABLE PIEUP WAE RIEULKIYEOK - 0x9477: 0xBD36, //HANGUL SYLLABLE PIEUP WAE RIEULMIEUM - 0x9478: 0xBD37, //HANGUL SYLLABLE PIEUP WAE RIEULPIEUP - 0x9479: 0xBD38, //HANGUL SYLLABLE PIEUP WAE RIEULSIOS - 0x947A: 0xBD39, //HANGUL SYLLABLE PIEUP WAE RIEULTHIEUTH - 0x9481: 0xBD3A, //HANGUL SYLLABLE PIEUP WAE RIEULPHIEUPH - 0x9482: 0xBD3B, //HANGUL SYLLABLE PIEUP WAE RIEULHIEUH - 0x9483: 0xBD3C, //HANGUL SYLLABLE PIEUP WAE MIEUM - 0x9484: 0xBD3D, //HANGUL SYLLABLE PIEUP WAE PIEUP - 0x9485: 0xBD3E, //HANGUL SYLLABLE PIEUP WAE PIEUPSIOS - 0x9486: 0xBD3F, //HANGUL SYLLABLE PIEUP WAE SIOS - 0x9487: 0xBD41, //HANGUL SYLLABLE PIEUP WAE IEUNG - 0x9488: 0xBD42, //HANGUL SYLLABLE PIEUP WAE CIEUC - 0x9489: 0xBD43, //HANGUL SYLLABLE PIEUP WAE CHIEUCH - 0x948A: 0xBD44, //HANGUL SYLLABLE PIEUP WAE KHIEUKH - 0x948B: 0xBD45, //HANGUL SYLLABLE PIEUP WAE THIEUTH - 0x948C: 0xBD46, //HANGUL SYLLABLE PIEUP WAE PHIEUPH - 0x948D: 0xBD47, //HANGUL SYLLABLE PIEUP WAE HIEUH - 0x948E: 0xBD4A, //HANGUL SYLLABLE PIEUP OE SSANGKIYEOK - 0x948F: 0xBD4B, //HANGUL SYLLABLE PIEUP OE KIYEOKSIOS - 0x9490: 0xBD4D, //HANGUL SYLLABLE PIEUP OE NIEUNCIEUC - 0x9491: 0xBD4E, //HANGUL SYLLABLE PIEUP OE NIEUNHIEUH - 0x9492: 0xBD4F, //HANGUL SYLLABLE PIEUP OE TIKEUT - 0x9493: 0xBD51, //HANGUL SYLLABLE PIEUP OE RIEULKIYEOK - 0x9494: 0xBD52, //HANGUL SYLLABLE PIEUP OE RIEULMIEUM - 0x9495: 0xBD53, //HANGUL SYLLABLE PIEUP OE RIEULPIEUP - 0x9496: 0xBD54, //HANGUL SYLLABLE PIEUP OE RIEULSIOS - 0x9497: 0xBD55, //HANGUL SYLLABLE PIEUP OE RIEULTHIEUTH - 0x9498: 0xBD56, //HANGUL SYLLABLE PIEUP OE RIEULPHIEUPH - 0x9499: 0xBD57, //HANGUL SYLLABLE PIEUP OE RIEULHIEUH - 0x949A: 0xBD5A, //HANGUL SYLLABLE PIEUP OE PIEUPSIOS - 0x949B: 0xBD5B, //HANGUL SYLLABLE PIEUP OE SIOS - 0x949C: 0xBD5C, //HANGUL SYLLABLE PIEUP OE SSANGSIOS - 0x949D: 0xBD5D, //HANGUL SYLLABLE PIEUP OE IEUNG - 0x949E: 0xBD5E, //HANGUL SYLLABLE PIEUP OE CIEUC - 0x949F: 0xBD5F, //HANGUL SYLLABLE PIEUP OE CHIEUCH - 0x94A0: 0xBD60, //HANGUL SYLLABLE PIEUP OE KHIEUKH - 0x94A1: 0xBD61, //HANGUL SYLLABLE PIEUP OE THIEUTH - 0x94A2: 0xBD62, //HANGUL SYLLABLE PIEUP OE PHIEUPH - 0x94A3: 0xBD63, //HANGUL SYLLABLE PIEUP OE HIEUH - 0x94A4: 0xBD65, //HANGUL SYLLABLE PIEUP YO KIYEOK - 0x94A5: 0xBD66, //HANGUL SYLLABLE PIEUP YO SSANGKIYEOK - 0x94A6: 0xBD67, //HANGUL SYLLABLE PIEUP YO KIYEOKSIOS - 0x94A7: 0xBD69, //HANGUL SYLLABLE PIEUP YO NIEUNCIEUC - 0x94A8: 0xBD6A, //HANGUL SYLLABLE PIEUP YO NIEUNHIEUH - 0x94A9: 0xBD6B, //HANGUL SYLLABLE PIEUP YO TIKEUT - 0x94AA: 0xBD6C, //HANGUL SYLLABLE PIEUP YO RIEUL - 0x94AB: 0xBD6D, //HANGUL SYLLABLE PIEUP YO RIEULKIYEOK - 0x94AC: 0xBD6E, //HANGUL SYLLABLE PIEUP YO RIEULMIEUM - 0x94AD: 0xBD6F, //HANGUL SYLLABLE PIEUP YO RIEULPIEUP - 0x94AE: 0xBD70, //HANGUL SYLLABLE PIEUP YO RIEULSIOS - 0x94AF: 0xBD71, //HANGUL SYLLABLE PIEUP YO RIEULTHIEUTH - 0x94B0: 0xBD72, //HANGUL SYLLABLE PIEUP YO RIEULPHIEUPH - 0x94B1: 0xBD73, //HANGUL SYLLABLE PIEUP YO RIEULHIEUH - 0x94B2: 0xBD74, //HANGUL SYLLABLE PIEUP YO MIEUM - 0x94B3: 0xBD75, //HANGUL SYLLABLE PIEUP YO PIEUP - 0x94B4: 0xBD76, //HANGUL SYLLABLE PIEUP YO PIEUPSIOS - 0x94B5: 0xBD77, //HANGUL SYLLABLE PIEUP YO SIOS - 0x94B6: 0xBD78, //HANGUL SYLLABLE PIEUP YO SSANGSIOS - 0x94B7: 0xBD79, //HANGUL SYLLABLE PIEUP YO IEUNG - 0x94B8: 0xBD7A, //HANGUL SYLLABLE PIEUP YO CIEUC - 0x94B9: 0xBD7B, //HANGUL SYLLABLE PIEUP YO CHIEUCH - 0x94BA: 0xBD7C, //HANGUL SYLLABLE PIEUP YO KHIEUKH - 0x94BB: 0xBD7D, //HANGUL SYLLABLE PIEUP YO THIEUTH - 0x94BC: 0xBD7E, //HANGUL SYLLABLE PIEUP YO PHIEUPH - 0x94BD: 0xBD7F, //HANGUL SYLLABLE PIEUP YO HIEUH - 0x94BE: 0xBD82, //HANGUL SYLLABLE PIEUP U SSANGKIYEOK - 0x94BF: 0xBD83, //HANGUL SYLLABLE PIEUP U KIYEOKSIOS - 0x94C0: 0xBD85, //HANGUL SYLLABLE PIEUP U NIEUNCIEUC - 0x94C1: 0xBD86, //HANGUL SYLLABLE PIEUP U NIEUNHIEUH - 0x94C2: 0xBD8B, //HANGUL SYLLABLE PIEUP U RIEULPIEUP - 0x94C3: 0xBD8C, //HANGUL SYLLABLE PIEUP U RIEULSIOS - 0x94C4: 0xBD8D, //HANGUL SYLLABLE PIEUP U RIEULTHIEUTH - 0x94C5: 0xBD8E, //HANGUL SYLLABLE PIEUP U RIEULPHIEUPH - 0x94C6: 0xBD8F, //HANGUL SYLLABLE PIEUP U RIEULHIEUH - 0x94C7: 0xBD92, //HANGUL SYLLABLE PIEUP U PIEUPSIOS - 0x94C8: 0xBD94, //HANGUL SYLLABLE PIEUP U SSANGSIOS - 0x94C9: 0xBD96, //HANGUL SYLLABLE PIEUP U CIEUC - 0x94CA: 0xBD97, //HANGUL SYLLABLE PIEUP U CHIEUCH - 0x94CB: 0xBD98, //HANGUL SYLLABLE PIEUP U KHIEUKH - 0x94CC: 0xBD9B, //HANGUL SYLLABLE PIEUP U HIEUH - 0x94CD: 0xBD9D, //HANGUL SYLLABLE PIEUP WEO KIYEOK - 0x94CE: 0xBD9E, //HANGUL SYLLABLE PIEUP WEO SSANGKIYEOK - 0x94CF: 0xBD9F, //HANGUL SYLLABLE PIEUP WEO KIYEOKSIOS - 0x94D0: 0xBDA0, //HANGUL SYLLABLE PIEUP WEO NIEUN - 0x94D1: 0xBDA1, //HANGUL SYLLABLE PIEUP WEO NIEUNCIEUC - 0x94D2: 0xBDA2, //HANGUL SYLLABLE PIEUP WEO NIEUNHIEUH - 0x94D3: 0xBDA3, //HANGUL SYLLABLE PIEUP WEO TIKEUT - 0x94D4: 0xBDA5, //HANGUL SYLLABLE PIEUP WEO RIEULKIYEOK - 0x94D5: 0xBDA6, //HANGUL SYLLABLE PIEUP WEO RIEULMIEUM - 0x94D6: 0xBDA7, //HANGUL SYLLABLE PIEUP WEO RIEULPIEUP - 0x94D7: 0xBDA8, //HANGUL SYLLABLE PIEUP WEO RIEULSIOS - 0x94D8: 0xBDA9, //HANGUL SYLLABLE PIEUP WEO RIEULTHIEUTH - 0x94D9: 0xBDAA, //HANGUL SYLLABLE PIEUP WEO RIEULPHIEUPH - 0x94DA: 0xBDAB, //HANGUL SYLLABLE PIEUP WEO RIEULHIEUH - 0x94DB: 0xBDAC, //HANGUL SYLLABLE PIEUP WEO MIEUM - 0x94DC: 0xBDAD, //HANGUL SYLLABLE PIEUP WEO PIEUP - 0x94DD: 0xBDAE, //HANGUL SYLLABLE PIEUP WEO PIEUPSIOS - 0x94DE: 0xBDAF, //HANGUL SYLLABLE PIEUP WEO SIOS - 0x94DF: 0xBDB1, //HANGUL SYLLABLE PIEUP WEO IEUNG - 0x94E0: 0xBDB2, //HANGUL SYLLABLE PIEUP WEO CIEUC - 0x94E1: 0xBDB3, //HANGUL SYLLABLE PIEUP WEO CHIEUCH - 0x94E2: 0xBDB4, //HANGUL SYLLABLE PIEUP WEO KHIEUKH - 0x94E3: 0xBDB5, //HANGUL SYLLABLE PIEUP WEO THIEUTH - 0x94E4: 0xBDB6, //HANGUL SYLLABLE PIEUP WEO PHIEUPH - 0x94E5: 0xBDB7, //HANGUL SYLLABLE PIEUP WEO HIEUH - 0x94E6: 0xBDB9, //HANGUL SYLLABLE PIEUP WE KIYEOK - 0x94E7: 0xBDBA, //HANGUL SYLLABLE PIEUP WE SSANGKIYEOK - 0x94E8: 0xBDBB, //HANGUL SYLLABLE PIEUP WE KIYEOKSIOS - 0x94E9: 0xBDBC, //HANGUL SYLLABLE PIEUP WE NIEUN - 0x94EA: 0xBDBD, //HANGUL SYLLABLE PIEUP WE NIEUNCIEUC - 0x94EB: 0xBDBE, //HANGUL SYLLABLE PIEUP WE NIEUNHIEUH - 0x94EC: 0xBDBF, //HANGUL SYLLABLE PIEUP WE TIKEUT - 0x94ED: 0xBDC0, //HANGUL SYLLABLE PIEUP WE RIEUL - 0x94EE: 0xBDC1, //HANGUL SYLLABLE PIEUP WE RIEULKIYEOK - 0x94EF: 0xBDC2, //HANGUL SYLLABLE PIEUP WE RIEULMIEUM - 0x94F0: 0xBDC3, //HANGUL SYLLABLE PIEUP WE RIEULPIEUP - 0x94F1: 0xBDC4, //HANGUL SYLLABLE PIEUP WE RIEULSIOS - 0x94F2: 0xBDC5, //HANGUL SYLLABLE PIEUP WE RIEULTHIEUTH - 0x94F3: 0xBDC6, //HANGUL SYLLABLE PIEUP WE RIEULPHIEUPH - 0x94F4: 0xBDC7, //HANGUL SYLLABLE PIEUP WE RIEULHIEUH - 0x94F5: 0xBDC8, //HANGUL SYLLABLE PIEUP WE MIEUM - 0x94F6: 0xBDC9, //HANGUL SYLLABLE PIEUP WE PIEUP - 0x94F7: 0xBDCA, //HANGUL SYLLABLE PIEUP WE PIEUPSIOS - 0x94F8: 0xBDCB, //HANGUL SYLLABLE PIEUP WE SIOS - 0x94F9: 0xBDCC, //HANGUL SYLLABLE PIEUP WE SSANGSIOS - 0x94FA: 0xBDCD, //HANGUL SYLLABLE PIEUP WE IEUNG - 0x94FB: 0xBDCE, //HANGUL SYLLABLE PIEUP WE CIEUC - 0x94FC: 0xBDCF, //HANGUL SYLLABLE PIEUP WE CHIEUCH - 0x94FD: 0xBDD0, //HANGUL SYLLABLE PIEUP WE KHIEUKH - 0x94FE: 0xBDD1, //HANGUL SYLLABLE PIEUP WE THIEUTH - 0x9541: 0xBDD2, //HANGUL SYLLABLE PIEUP WE PHIEUPH - 0x9542: 0xBDD3, //HANGUL SYLLABLE PIEUP WE HIEUH - 0x9543: 0xBDD6, //HANGUL SYLLABLE PIEUP WI SSANGKIYEOK - 0x9544: 0xBDD7, //HANGUL SYLLABLE PIEUP WI KIYEOKSIOS - 0x9545: 0xBDD9, //HANGUL SYLLABLE PIEUP WI NIEUNCIEUC - 0x9546: 0xBDDA, //HANGUL SYLLABLE PIEUP WI NIEUNHIEUH - 0x9547: 0xBDDB, //HANGUL SYLLABLE PIEUP WI TIKEUT - 0x9548: 0xBDDD, //HANGUL SYLLABLE PIEUP WI RIEULKIYEOK - 0x9549: 0xBDDE, //HANGUL SYLLABLE PIEUP WI RIEULMIEUM - 0x954A: 0xBDDF, //HANGUL SYLLABLE PIEUP WI RIEULPIEUP - 0x954B: 0xBDE0, //HANGUL SYLLABLE PIEUP WI RIEULSIOS - 0x954C: 0xBDE1, //HANGUL SYLLABLE PIEUP WI RIEULTHIEUTH - 0x954D: 0xBDE2, //HANGUL SYLLABLE PIEUP WI RIEULPHIEUPH - 0x954E: 0xBDE3, //HANGUL SYLLABLE PIEUP WI RIEULHIEUH - 0x954F: 0xBDE4, //HANGUL SYLLABLE PIEUP WI MIEUM - 0x9550: 0xBDE5, //HANGUL SYLLABLE PIEUP WI PIEUP - 0x9551: 0xBDE6, //HANGUL SYLLABLE PIEUP WI PIEUPSIOS - 0x9552: 0xBDE7, //HANGUL SYLLABLE PIEUP WI SIOS - 0x9553: 0xBDE8, //HANGUL SYLLABLE PIEUP WI SSANGSIOS - 0x9554: 0xBDEA, //HANGUL SYLLABLE PIEUP WI CIEUC - 0x9555: 0xBDEB, //HANGUL SYLLABLE PIEUP WI CHIEUCH - 0x9556: 0xBDEC, //HANGUL SYLLABLE PIEUP WI KHIEUKH - 0x9557: 0xBDED, //HANGUL SYLLABLE PIEUP WI THIEUTH - 0x9558: 0xBDEE, //HANGUL SYLLABLE PIEUP WI PHIEUPH - 0x9559: 0xBDEF, //HANGUL SYLLABLE PIEUP WI HIEUH - 0x955A: 0xBDF1, //HANGUL SYLLABLE PIEUP YU KIYEOK - 0x9561: 0xBDF2, //HANGUL SYLLABLE PIEUP YU SSANGKIYEOK - 0x9562: 0xBDF3, //HANGUL SYLLABLE PIEUP YU KIYEOKSIOS - 0x9563: 0xBDF5, //HANGUL SYLLABLE PIEUP YU NIEUNCIEUC - 0x9564: 0xBDF6, //HANGUL SYLLABLE PIEUP YU NIEUNHIEUH - 0x9565: 0xBDF7, //HANGUL SYLLABLE PIEUP YU TIKEUT - 0x9566: 0xBDF9, //HANGUL SYLLABLE PIEUP YU RIEULKIYEOK - 0x9567: 0xBDFA, //HANGUL SYLLABLE PIEUP YU RIEULMIEUM - 0x9568: 0xBDFB, //HANGUL SYLLABLE PIEUP YU RIEULPIEUP - 0x9569: 0xBDFC, //HANGUL SYLLABLE PIEUP YU RIEULSIOS - 0x956A: 0xBDFD, //HANGUL SYLLABLE PIEUP YU RIEULTHIEUTH - 0x956B: 0xBDFE, //HANGUL SYLLABLE PIEUP YU RIEULPHIEUPH - 0x956C: 0xBDFF, //HANGUL SYLLABLE PIEUP YU RIEULHIEUH - 0x956D: 0xBE01, //HANGUL SYLLABLE PIEUP YU PIEUP - 0x956E: 0xBE02, //HANGUL SYLLABLE PIEUP YU PIEUPSIOS - 0x956F: 0xBE04, //HANGUL SYLLABLE PIEUP YU SSANGSIOS - 0x9570: 0xBE06, //HANGUL SYLLABLE PIEUP YU CIEUC - 0x9571: 0xBE07, //HANGUL SYLLABLE PIEUP YU CHIEUCH - 0x9572: 0xBE08, //HANGUL SYLLABLE PIEUP YU KHIEUKH - 0x9573: 0xBE09, //HANGUL SYLLABLE PIEUP YU THIEUTH - 0x9574: 0xBE0A, //HANGUL SYLLABLE PIEUP YU PHIEUPH - 0x9575: 0xBE0B, //HANGUL SYLLABLE PIEUP YU HIEUH - 0x9576: 0xBE0E, //HANGUL SYLLABLE PIEUP EU SSANGKIYEOK - 0x9577: 0xBE0F, //HANGUL SYLLABLE PIEUP EU KIYEOKSIOS - 0x9578: 0xBE11, //HANGUL SYLLABLE PIEUP EU NIEUNCIEUC - 0x9579: 0xBE12, //HANGUL SYLLABLE PIEUP EU NIEUNHIEUH - 0x957A: 0xBE13, //HANGUL SYLLABLE PIEUP EU TIKEUT - 0x9581: 0xBE15, //HANGUL SYLLABLE PIEUP EU RIEULKIYEOK - 0x9582: 0xBE16, //HANGUL SYLLABLE PIEUP EU RIEULMIEUM - 0x9583: 0xBE17, //HANGUL SYLLABLE PIEUP EU RIEULPIEUP - 0x9584: 0xBE18, //HANGUL SYLLABLE PIEUP EU RIEULSIOS - 0x9585: 0xBE19, //HANGUL SYLLABLE PIEUP EU RIEULTHIEUTH - 0x9586: 0xBE1A, //HANGUL SYLLABLE PIEUP EU RIEULPHIEUPH - 0x9587: 0xBE1B, //HANGUL SYLLABLE PIEUP EU RIEULHIEUH - 0x9588: 0xBE1E, //HANGUL SYLLABLE PIEUP EU PIEUPSIOS - 0x9589: 0xBE20, //HANGUL SYLLABLE PIEUP EU SSANGSIOS - 0x958A: 0xBE21, //HANGUL SYLLABLE PIEUP EU IEUNG - 0x958B: 0xBE22, //HANGUL SYLLABLE PIEUP EU CIEUC - 0x958C: 0xBE23, //HANGUL SYLLABLE PIEUP EU CHIEUCH - 0x958D: 0xBE24, //HANGUL SYLLABLE PIEUP EU KHIEUKH - 0x958E: 0xBE25, //HANGUL SYLLABLE PIEUP EU THIEUTH - 0x958F: 0xBE26, //HANGUL SYLLABLE PIEUP EU PHIEUPH - 0x9590: 0xBE27, //HANGUL SYLLABLE PIEUP EU HIEUH - 0x9591: 0xBE28, //HANGUL SYLLABLE PIEUP YI - 0x9592: 0xBE29, //HANGUL SYLLABLE PIEUP YI KIYEOK - 0x9593: 0xBE2A, //HANGUL SYLLABLE PIEUP YI SSANGKIYEOK - 0x9594: 0xBE2B, //HANGUL SYLLABLE PIEUP YI KIYEOKSIOS - 0x9595: 0xBE2C, //HANGUL SYLLABLE PIEUP YI NIEUN - 0x9596: 0xBE2D, //HANGUL SYLLABLE PIEUP YI NIEUNCIEUC - 0x9597: 0xBE2E, //HANGUL SYLLABLE PIEUP YI NIEUNHIEUH - 0x9598: 0xBE2F, //HANGUL SYLLABLE PIEUP YI TIKEUT - 0x9599: 0xBE30, //HANGUL SYLLABLE PIEUP YI RIEUL - 0x959A: 0xBE31, //HANGUL SYLLABLE PIEUP YI RIEULKIYEOK - 0x959B: 0xBE32, //HANGUL SYLLABLE PIEUP YI RIEULMIEUM - 0x959C: 0xBE33, //HANGUL SYLLABLE PIEUP YI RIEULPIEUP - 0x959D: 0xBE34, //HANGUL SYLLABLE PIEUP YI RIEULSIOS - 0x959E: 0xBE35, //HANGUL SYLLABLE PIEUP YI RIEULTHIEUTH - 0x959F: 0xBE36, //HANGUL SYLLABLE PIEUP YI RIEULPHIEUPH - 0x95A0: 0xBE37, //HANGUL SYLLABLE PIEUP YI RIEULHIEUH - 0x95A1: 0xBE38, //HANGUL SYLLABLE PIEUP YI MIEUM - 0x95A2: 0xBE39, //HANGUL SYLLABLE PIEUP YI PIEUP - 0x95A3: 0xBE3A, //HANGUL SYLLABLE PIEUP YI PIEUPSIOS - 0x95A4: 0xBE3B, //HANGUL SYLLABLE PIEUP YI SIOS - 0x95A5: 0xBE3C, //HANGUL SYLLABLE PIEUP YI SSANGSIOS - 0x95A6: 0xBE3D, //HANGUL SYLLABLE PIEUP YI IEUNG - 0x95A7: 0xBE3E, //HANGUL SYLLABLE PIEUP YI CIEUC - 0x95A8: 0xBE3F, //HANGUL SYLLABLE PIEUP YI CHIEUCH - 0x95A9: 0xBE40, //HANGUL SYLLABLE PIEUP YI KHIEUKH - 0x95AA: 0xBE41, //HANGUL SYLLABLE PIEUP YI THIEUTH - 0x95AB: 0xBE42, //HANGUL SYLLABLE PIEUP YI PHIEUPH - 0x95AC: 0xBE43, //HANGUL SYLLABLE PIEUP YI HIEUH - 0x95AD: 0xBE46, //HANGUL SYLLABLE PIEUP I SSANGKIYEOK - 0x95AE: 0xBE47, //HANGUL SYLLABLE PIEUP I KIYEOKSIOS - 0x95AF: 0xBE49, //HANGUL SYLLABLE PIEUP I NIEUNCIEUC - 0x95B0: 0xBE4A, //HANGUL SYLLABLE PIEUP I NIEUNHIEUH - 0x95B1: 0xBE4B, //HANGUL SYLLABLE PIEUP I TIKEUT - 0x95B2: 0xBE4D, //HANGUL SYLLABLE PIEUP I RIEULKIYEOK - 0x95B3: 0xBE4F, //HANGUL SYLLABLE PIEUP I RIEULPIEUP - 0x95B4: 0xBE50, //HANGUL SYLLABLE PIEUP I RIEULSIOS - 0x95B5: 0xBE51, //HANGUL SYLLABLE PIEUP I RIEULTHIEUTH - 0x95B6: 0xBE52, //HANGUL SYLLABLE PIEUP I RIEULPHIEUPH - 0x95B7: 0xBE53, //HANGUL SYLLABLE PIEUP I RIEULHIEUH - 0x95B8: 0xBE56, //HANGUL SYLLABLE PIEUP I PIEUPSIOS - 0x95B9: 0xBE58, //HANGUL SYLLABLE PIEUP I SSANGSIOS - 0x95BA: 0xBE5C, //HANGUL SYLLABLE PIEUP I KHIEUKH - 0x95BB: 0xBE5D, //HANGUL SYLLABLE PIEUP I THIEUTH - 0x95BC: 0xBE5E, //HANGUL SYLLABLE PIEUP I PHIEUPH - 0x95BD: 0xBE5F, //HANGUL SYLLABLE PIEUP I HIEUH - 0x95BE: 0xBE62, //HANGUL SYLLABLE SSANGPIEUP A SSANGKIYEOK - 0x95BF: 0xBE63, //HANGUL SYLLABLE SSANGPIEUP A KIYEOKSIOS - 0x95C0: 0xBE65, //HANGUL SYLLABLE SSANGPIEUP A NIEUNCIEUC - 0x95C1: 0xBE66, //HANGUL SYLLABLE SSANGPIEUP A NIEUNHIEUH - 0x95C2: 0xBE67, //HANGUL SYLLABLE SSANGPIEUP A TIKEUT - 0x95C3: 0xBE69, //HANGUL SYLLABLE SSANGPIEUP A RIEULKIYEOK - 0x95C4: 0xBE6B, //HANGUL SYLLABLE SSANGPIEUP A RIEULPIEUP - 0x95C5: 0xBE6C, //HANGUL SYLLABLE SSANGPIEUP A RIEULSIOS - 0x95C6: 0xBE6D, //HANGUL SYLLABLE SSANGPIEUP A RIEULTHIEUTH - 0x95C7: 0xBE6E, //HANGUL SYLLABLE SSANGPIEUP A RIEULPHIEUPH - 0x95C8: 0xBE6F, //HANGUL SYLLABLE SSANGPIEUP A RIEULHIEUH - 0x95C9: 0xBE72, //HANGUL SYLLABLE SSANGPIEUP A PIEUPSIOS - 0x95CA: 0xBE76, //HANGUL SYLLABLE SSANGPIEUP A CIEUC - 0x95CB: 0xBE77, //HANGUL SYLLABLE SSANGPIEUP A CHIEUCH - 0x95CC: 0xBE78, //HANGUL SYLLABLE SSANGPIEUP A KHIEUKH - 0x95CD: 0xBE79, //HANGUL SYLLABLE SSANGPIEUP A THIEUTH - 0x95CE: 0xBE7A, //HANGUL SYLLABLE SSANGPIEUP A PHIEUPH - 0x95CF: 0xBE7E, //HANGUL SYLLABLE SSANGPIEUP AE SSANGKIYEOK - 0x95D0: 0xBE7F, //HANGUL SYLLABLE SSANGPIEUP AE KIYEOKSIOS - 0x95D1: 0xBE81, //HANGUL SYLLABLE SSANGPIEUP AE NIEUNCIEUC - 0x95D2: 0xBE82, //HANGUL SYLLABLE SSANGPIEUP AE NIEUNHIEUH - 0x95D3: 0xBE83, //HANGUL SYLLABLE SSANGPIEUP AE TIKEUT - 0x95D4: 0xBE85, //HANGUL SYLLABLE SSANGPIEUP AE RIEULKIYEOK - 0x95D5: 0xBE86, //HANGUL SYLLABLE SSANGPIEUP AE RIEULMIEUM - 0x95D6: 0xBE87, //HANGUL SYLLABLE SSANGPIEUP AE RIEULPIEUP - 0x95D7: 0xBE88, //HANGUL SYLLABLE SSANGPIEUP AE RIEULSIOS - 0x95D8: 0xBE89, //HANGUL SYLLABLE SSANGPIEUP AE RIEULTHIEUTH - 0x95D9: 0xBE8A, //HANGUL SYLLABLE SSANGPIEUP AE RIEULPHIEUPH - 0x95DA: 0xBE8B, //HANGUL SYLLABLE SSANGPIEUP AE RIEULHIEUH - 0x95DB: 0xBE8E, //HANGUL SYLLABLE SSANGPIEUP AE PIEUPSIOS - 0x95DC: 0xBE92, //HANGUL SYLLABLE SSANGPIEUP AE CIEUC - 0x95DD: 0xBE93, //HANGUL SYLLABLE SSANGPIEUP AE CHIEUCH - 0x95DE: 0xBE94, //HANGUL SYLLABLE SSANGPIEUP AE KHIEUKH - 0x95DF: 0xBE95, //HANGUL SYLLABLE SSANGPIEUP AE THIEUTH - 0x95E0: 0xBE96, //HANGUL SYLLABLE SSANGPIEUP AE PHIEUPH - 0x95E1: 0xBE97, //HANGUL SYLLABLE SSANGPIEUP AE HIEUH - 0x95E2: 0xBE9A, //HANGUL SYLLABLE SSANGPIEUP YA SSANGKIYEOK - 0x95E3: 0xBE9B, //HANGUL SYLLABLE SSANGPIEUP YA KIYEOKSIOS - 0x95E4: 0xBE9C, //HANGUL SYLLABLE SSANGPIEUP YA NIEUN - 0x95E5: 0xBE9D, //HANGUL SYLLABLE SSANGPIEUP YA NIEUNCIEUC - 0x95E6: 0xBE9E, //HANGUL SYLLABLE SSANGPIEUP YA NIEUNHIEUH - 0x95E7: 0xBE9F, //HANGUL SYLLABLE SSANGPIEUP YA TIKEUT - 0x95E8: 0xBEA0, //HANGUL SYLLABLE SSANGPIEUP YA RIEUL - 0x95E9: 0xBEA1, //HANGUL SYLLABLE SSANGPIEUP YA RIEULKIYEOK - 0x95EA: 0xBEA2, //HANGUL SYLLABLE SSANGPIEUP YA RIEULMIEUM - 0x95EB: 0xBEA3, //HANGUL SYLLABLE SSANGPIEUP YA RIEULPIEUP - 0x95EC: 0xBEA4, //HANGUL SYLLABLE SSANGPIEUP YA RIEULSIOS - 0x95ED: 0xBEA5, //HANGUL SYLLABLE SSANGPIEUP YA RIEULTHIEUTH - 0x95EE: 0xBEA6, //HANGUL SYLLABLE SSANGPIEUP YA RIEULPHIEUPH - 0x95EF: 0xBEA7, //HANGUL SYLLABLE SSANGPIEUP YA RIEULHIEUH - 0x95F0: 0xBEA9, //HANGUL SYLLABLE SSANGPIEUP YA PIEUP - 0x95F1: 0xBEAA, //HANGUL SYLLABLE SSANGPIEUP YA PIEUPSIOS - 0x95F2: 0xBEAB, //HANGUL SYLLABLE SSANGPIEUP YA SIOS - 0x95F3: 0xBEAC, //HANGUL SYLLABLE SSANGPIEUP YA SSANGSIOS - 0x95F4: 0xBEAD, //HANGUL SYLLABLE SSANGPIEUP YA IEUNG - 0x95F5: 0xBEAE, //HANGUL SYLLABLE SSANGPIEUP YA CIEUC - 0x95F6: 0xBEAF, //HANGUL SYLLABLE SSANGPIEUP YA CHIEUCH - 0x95F7: 0xBEB0, //HANGUL SYLLABLE SSANGPIEUP YA KHIEUKH - 0x95F8: 0xBEB1, //HANGUL SYLLABLE SSANGPIEUP YA THIEUTH - 0x95F9: 0xBEB2, //HANGUL SYLLABLE SSANGPIEUP YA PHIEUPH - 0x95FA: 0xBEB3, //HANGUL SYLLABLE SSANGPIEUP YA HIEUH - 0x95FB: 0xBEB4, //HANGUL SYLLABLE SSANGPIEUP YAE - 0x95FC: 0xBEB5, //HANGUL SYLLABLE SSANGPIEUP YAE KIYEOK - 0x95FD: 0xBEB6, //HANGUL SYLLABLE SSANGPIEUP YAE SSANGKIYEOK - 0x95FE: 0xBEB7, //HANGUL SYLLABLE SSANGPIEUP YAE KIYEOKSIOS - 0x9641: 0xBEB8, //HANGUL SYLLABLE SSANGPIEUP YAE NIEUN - 0x9642: 0xBEB9, //HANGUL SYLLABLE SSANGPIEUP YAE NIEUNCIEUC - 0x9643: 0xBEBA, //HANGUL SYLLABLE SSANGPIEUP YAE NIEUNHIEUH - 0x9644: 0xBEBB, //HANGUL SYLLABLE SSANGPIEUP YAE TIKEUT - 0x9645: 0xBEBC, //HANGUL SYLLABLE SSANGPIEUP YAE RIEUL - 0x9646: 0xBEBD, //HANGUL SYLLABLE SSANGPIEUP YAE RIEULKIYEOK - 0x9647: 0xBEBE, //HANGUL SYLLABLE SSANGPIEUP YAE RIEULMIEUM - 0x9648: 0xBEBF, //HANGUL SYLLABLE SSANGPIEUP YAE RIEULPIEUP - 0x9649: 0xBEC0, //HANGUL SYLLABLE SSANGPIEUP YAE RIEULSIOS - 0x964A: 0xBEC1, //HANGUL SYLLABLE SSANGPIEUP YAE RIEULTHIEUTH - 0x964B: 0xBEC2, //HANGUL SYLLABLE SSANGPIEUP YAE RIEULPHIEUPH - 0x964C: 0xBEC3, //HANGUL SYLLABLE SSANGPIEUP YAE RIEULHIEUH - 0x964D: 0xBEC4, //HANGUL SYLLABLE SSANGPIEUP YAE MIEUM - 0x964E: 0xBEC5, //HANGUL SYLLABLE SSANGPIEUP YAE PIEUP - 0x964F: 0xBEC6, //HANGUL SYLLABLE SSANGPIEUP YAE PIEUPSIOS - 0x9650: 0xBEC7, //HANGUL SYLLABLE SSANGPIEUP YAE SIOS - 0x9651: 0xBEC8, //HANGUL SYLLABLE SSANGPIEUP YAE SSANGSIOS - 0x9652: 0xBEC9, //HANGUL SYLLABLE SSANGPIEUP YAE IEUNG - 0x9653: 0xBECA, //HANGUL SYLLABLE SSANGPIEUP YAE CIEUC - 0x9654: 0xBECB, //HANGUL SYLLABLE SSANGPIEUP YAE CHIEUCH - 0x9655: 0xBECC, //HANGUL SYLLABLE SSANGPIEUP YAE KHIEUKH - 0x9656: 0xBECD, //HANGUL SYLLABLE SSANGPIEUP YAE THIEUTH - 0x9657: 0xBECE, //HANGUL SYLLABLE SSANGPIEUP YAE PHIEUPH - 0x9658: 0xBECF, //HANGUL SYLLABLE SSANGPIEUP YAE HIEUH - 0x9659: 0xBED2, //HANGUL SYLLABLE SSANGPIEUP EO SSANGKIYEOK - 0x965A: 0xBED3, //HANGUL SYLLABLE SSANGPIEUP EO KIYEOKSIOS - 0x9661: 0xBED5, //HANGUL SYLLABLE SSANGPIEUP EO NIEUNCIEUC - 0x9662: 0xBED6, //HANGUL SYLLABLE SSANGPIEUP EO NIEUNHIEUH - 0x9663: 0xBED9, //HANGUL SYLLABLE SSANGPIEUP EO RIEULKIYEOK - 0x9664: 0xBEDA, //HANGUL SYLLABLE SSANGPIEUP EO RIEULMIEUM - 0x9665: 0xBEDB, //HANGUL SYLLABLE SSANGPIEUP EO RIEULPIEUP - 0x9666: 0xBEDC, //HANGUL SYLLABLE SSANGPIEUP EO RIEULSIOS - 0x9667: 0xBEDD, //HANGUL SYLLABLE SSANGPIEUP EO RIEULTHIEUTH - 0x9668: 0xBEDE, //HANGUL SYLLABLE SSANGPIEUP EO RIEULPHIEUPH - 0x9669: 0xBEDF, //HANGUL SYLLABLE SSANGPIEUP EO RIEULHIEUH - 0x966A: 0xBEE1, //HANGUL SYLLABLE SSANGPIEUP EO PIEUP - 0x966B: 0xBEE2, //HANGUL SYLLABLE SSANGPIEUP EO PIEUPSIOS - 0x966C: 0xBEE6, //HANGUL SYLLABLE SSANGPIEUP EO CIEUC - 0x966D: 0xBEE7, //HANGUL SYLLABLE SSANGPIEUP EO CHIEUCH - 0x966E: 0xBEE8, //HANGUL SYLLABLE SSANGPIEUP EO KHIEUKH - 0x966F: 0xBEE9, //HANGUL SYLLABLE SSANGPIEUP EO THIEUTH - 0x9670: 0xBEEA, //HANGUL SYLLABLE SSANGPIEUP EO PHIEUPH - 0x9671: 0xBEEB, //HANGUL SYLLABLE SSANGPIEUP EO HIEUH - 0x9672: 0xBEED, //HANGUL SYLLABLE SSANGPIEUP E KIYEOK - 0x9673: 0xBEEE, //HANGUL SYLLABLE SSANGPIEUP E SSANGKIYEOK - 0x9674: 0xBEEF, //HANGUL SYLLABLE SSANGPIEUP E KIYEOKSIOS - 0x9675: 0xBEF0, //HANGUL SYLLABLE SSANGPIEUP E NIEUN - 0x9676: 0xBEF1, //HANGUL SYLLABLE SSANGPIEUP E NIEUNCIEUC - 0x9677: 0xBEF2, //HANGUL SYLLABLE SSANGPIEUP E NIEUNHIEUH - 0x9678: 0xBEF3, //HANGUL SYLLABLE SSANGPIEUP E TIKEUT - 0x9679: 0xBEF4, //HANGUL SYLLABLE SSANGPIEUP E RIEUL - 0x967A: 0xBEF5, //HANGUL SYLLABLE SSANGPIEUP E RIEULKIYEOK - 0x9681: 0xBEF6, //HANGUL SYLLABLE SSANGPIEUP E RIEULMIEUM - 0x9682: 0xBEF7, //HANGUL SYLLABLE SSANGPIEUP E RIEULPIEUP - 0x9683: 0xBEF8, //HANGUL SYLLABLE SSANGPIEUP E RIEULSIOS - 0x9684: 0xBEF9, //HANGUL SYLLABLE SSANGPIEUP E RIEULTHIEUTH - 0x9685: 0xBEFA, //HANGUL SYLLABLE SSANGPIEUP E RIEULPHIEUPH - 0x9686: 0xBEFB, //HANGUL SYLLABLE SSANGPIEUP E RIEULHIEUH - 0x9687: 0xBEFC, //HANGUL SYLLABLE SSANGPIEUP E MIEUM - 0x9688: 0xBEFD, //HANGUL SYLLABLE SSANGPIEUP E PIEUP - 0x9689: 0xBEFE, //HANGUL SYLLABLE SSANGPIEUP E PIEUPSIOS - 0x968A: 0xBEFF, //HANGUL SYLLABLE SSANGPIEUP E SIOS - 0x968B: 0xBF00, //HANGUL SYLLABLE SSANGPIEUP E SSANGSIOS - 0x968C: 0xBF02, //HANGUL SYLLABLE SSANGPIEUP E CIEUC - 0x968D: 0xBF03, //HANGUL SYLLABLE SSANGPIEUP E CHIEUCH - 0x968E: 0xBF04, //HANGUL SYLLABLE SSANGPIEUP E KHIEUKH - 0x968F: 0xBF05, //HANGUL SYLLABLE SSANGPIEUP E THIEUTH - 0x9690: 0xBF06, //HANGUL SYLLABLE SSANGPIEUP E PHIEUPH - 0x9691: 0xBF07, //HANGUL SYLLABLE SSANGPIEUP E HIEUH - 0x9692: 0xBF0A, //HANGUL SYLLABLE SSANGPIEUP YEO SSANGKIYEOK - 0x9693: 0xBF0B, //HANGUL SYLLABLE SSANGPIEUP YEO KIYEOKSIOS - 0x9694: 0xBF0C, //HANGUL SYLLABLE SSANGPIEUP YEO NIEUN - 0x9695: 0xBF0D, //HANGUL SYLLABLE SSANGPIEUP YEO NIEUNCIEUC - 0x9696: 0xBF0E, //HANGUL SYLLABLE SSANGPIEUP YEO NIEUNHIEUH - 0x9697: 0xBF0F, //HANGUL SYLLABLE SSANGPIEUP YEO TIKEUT - 0x9698: 0xBF10, //HANGUL SYLLABLE SSANGPIEUP YEO RIEUL - 0x9699: 0xBF11, //HANGUL SYLLABLE SSANGPIEUP YEO RIEULKIYEOK - 0x969A: 0xBF12, //HANGUL SYLLABLE SSANGPIEUP YEO RIEULMIEUM - 0x969B: 0xBF13, //HANGUL SYLLABLE SSANGPIEUP YEO RIEULPIEUP - 0x969C: 0xBF14, //HANGUL SYLLABLE SSANGPIEUP YEO RIEULSIOS - 0x969D: 0xBF15, //HANGUL SYLLABLE SSANGPIEUP YEO RIEULTHIEUTH - 0x969E: 0xBF16, //HANGUL SYLLABLE SSANGPIEUP YEO RIEULPHIEUPH - 0x969F: 0xBF17, //HANGUL SYLLABLE SSANGPIEUP YEO RIEULHIEUH - 0x96A0: 0xBF1A, //HANGUL SYLLABLE SSANGPIEUP YEO PIEUPSIOS - 0x96A1: 0xBF1E, //HANGUL SYLLABLE SSANGPIEUP YEO CIEUC - 0x96A2: 0xBF1F, //HANGUL SYLLABLE SSANGPIEUP YEO CHIEUCH - 0x96A3: 0xBF20, //HANGUL SYLLABLE SSANGPIEUP YEO KHIEUKH - 0x96A4: 0xBF21, //HANGUL SYLLABLE SSANGPIEUP YEO THIEUTH - 0x96A5: 0xBF22, //HANGUL SYLLABLE SSANGPIEUP YEO PHIEUPH - 0x96A6: 0xBF23, //HANGUL SYLLABLE SSANGPIEUP YEO HIEUH - 0x96A7: 0xBF24, //HANGUL SYLLABLE SSANGPIEUP YE - 0x96A8: 0xBF25, //HANGUL SYLLABLE SSANGPIEUP YE KIYEOK - 0x96A9: 0xBF26, //HANGUL SYLLABLE SSANGPIEUP YE SSANGKIYEOK - 0x96AA: 0xBF27, //HANGUL SYLLABLE SSANGPIEUP YE KIYEOKSIOS - 0x96AB: 0xBF28, //HANGUL SYLLABLE SSANGPIEUP YE NIEUN - 0x96AC: 0xBF29, //HANGUL SYLLABLE SSANGPIEUP YE NIEUNCIEUC - 0x96AD: 0xBF2A, //HANGUL SYLLABLE SSANGPIEUP YE NIEUNHIEUH - 0x96AE: 0xBF2B, //HANGUL SYLLABLE SSANGPIEUP YE TIKEUT - 0x96AF: 0xBF2C, //HANGUL SYLLABLE SSANGPIEUP YE RIEUL - 0x96B0: 0xBF2D, //HANGUL SYLLABLE SSANGPIEUP YE RIEULKIYEOK - 0x96B1: 0xBF2E, //HANGUL SYLLABLE SSANGPIEUP YE RIEULMIEUM - 0x96B2: 0xBF2F, //HANGUL SYLLABLE SSANGPIEUP YE RIEULPIEUP - 0x96B3: 0xBF30, //HANGUL SYLLABLE SSANGPIEUP YE RIEULSIOS - 0x96B4: 0xBF31, //HANGUL SYLLABLE SSANGPIEUP YE RIEULTHIEUTH - 0x96B5: 0xBF32, //HANGUL SYLLABLE SSANGPIEUP YE RIEULPHIEUPH - 0x96B6: 0xBF33, //HANGUL SYLLABLE SSANGPIEUP YE RIEULHIEUH - 0x96B7: 0xBF34, //HANGUL SYLLABLE SSANGPIEUP YE MIEUM - 0x96B8: 0xBF35, //HANGUL SYLLABLE SSANGPIEUP YE PIEUP - 0x96B9: 0xBF36, //HANGUL SYLLABLE SSANGPIEUP YE PIEUPSIOS - 0x96BA: 0xBF37, //HANGUL SYLLABLE SSANGPIEUP YE SIOS - 0x96BB: 0xBF38, //HANGUL SYLLABLE SSANGPIEUP YE SSANGSIOS - 0x96BC: 0xBF39, //HANGUL SYLLABLE SSANGPIEUP YE IEUNG - 0x96BD: 0xBF3A, //HANGUL SYLLABLE SSANGPIEUP YE CIEUC - 0x96BE: 0xBF3B, //HANGUL SYLLABLE SSANGPIEUP YE CHIEUCH - 0x96BF: 0xBF3C, //HANGUL SYLLABLE SSANGPIEUP YE KHIEUKH - 0x96C0: 0xBF3D, //HANGUL SYLLABLE SSANGPIEUP YE THIEUTH - 0x96C1: 0xBF3E, //HANGUL SYLLABLE SSANGPIEUP YE PHIEUPH - 0x96C2: 0xBF3F, //HANGUL SYLLABLE SSANGPIEUP YE HIEUH - 0x96C3: 0xBF42, //HANGUL SYLLABLE SSANGPIEUP O SSANGKIYEOK - 0x96C4: 0xBF43, //HANGUL SYLLABLE SSANGPIEUP O KIYEOKSIOS - 0x96C5: 0xBF45, //HANGUL SYLLABLE SSANGPIEUP O NIEUNCIEUC - 0x96C6: 0xBF46, //HANGUL SYLLABLE SSANGPIEUP O NIEUNHIEUH - 0x96C7: 0xBF47, //HANGUL SYLLABLE SSANGPIEUP O TIKEUT - 0x96C8: 0xBF49, //HANGUL SYLLABLE SSANGPIEUP O RIEULKIYEOK - 0x96C9: 0xBF4A, //HANGUL SYLLABLE SSANGPIEUP O RIEULMIEUM - 0x96CA: 0xBF4B, //HANGUL SYLLABLE SSANGPIEUP O RIEULPIEUP - 0x96CB: 0xBF4C, //HANGUL SYLLABLE SSANGPIEUP O RIEULSIOS - 0x96CC: 0xBF4D, //HANGUL SYLLABLE SSANGPIEUP O RIEULTHIEUTH - 0x96CD: 0xBF4E, //HANGUL SYLLABLE SSANGPIEUP O RIEULPHIEUPH - 0x96CE: 0xBF4F, //HANGUL SYLLABLE SSANGPIEUP O RIEULHIEUH - 0x96CF: 0xBF52, //HANGUL SYLLABLE SSANGPIEUP O PIEUPSIOS - 0x96D0: 0xBF53, //HANGUL SYLLABLE SSANGPIEUP O SIOS - 0x96D1: 0xBF54, //HANGUL SYLLABLE SSANGPIEUP O SSANGSIOS - 0x96D2: 0xBF56, //HANGUL SYLLABLE SSANGPIEUP O CIEUC - 0x96D3: 0xBF57, //HANGUL SYLLABLE SSANGPIEUP O CHIEUCH - 0x96D4: 0xBF58, //HANGUL SYLLABLE SSANGPIEUP O KHIEUKH - 0x96D5: 0xBF59, //HANGUL SYLLABLE SSANGPIEUP O THIEUTH - 0x96D6: 0xBF5A, //HANGUL SYLLABLE SSANGPIEUP O PHIEUPH - 0x96D7: 0xBF5B, //HANGUL SYLLABLE SSANGPIEUP O HIEUH - 0x96D8: 0xBF5C, //HANGUL SYLLABLE SSANGPIEUP WA - 0x96D9: 0xBF5D, //HANGUL SYLLABLE SSANGPIEUP WA KIYEOK - 0x96DA: 0xBF5E, //HANGUL SYLLABLE SSANGPIEUP WA SSANGKIYEOK - 0x96DB: 0xBF5F, //HANGUL SYLLABLE SSANGPIEUP WA KIYEOKSIOS - 0x96DC: 0xBF60, //HANGUL SYLLABLE SSANGPIEUP WA NIEUN - 0x96DD: 0xBF61, //HANGUL SYLLABLE SSANGPIEUP WA NIEUNCIEUC - 0x96DE: 0xBF62, //HANGUL SYLLABLE SSANGPIEUP WA NIEUNHIEUH - 0x96DF: 0xBF63, //HANGUL SYLLABLE SSANGPIEUP WA TIKEUT - 0x96E0: 0xBF64, //HANGUL SYLLABLE SSANGPIEUP WA RIEUL - 0x96E1: 0xBF65, //HANGUL SYLLABLE SSANGPIEUP WA RIEULKIYEOK - 0x96E2: 0xBF66, //HANGUL SYLLABLE SSANGPIEUP WA RIEULMIEUM - 0x96E3: 0xBF67, //HANGUL SYLLABLE SSANGPIEUP WA RIEULPIEUP - 0x96E4: 0xBF68, //HANGUL SYLLABLE SSANGPIEUP WA RIEULSIOS - 0x96E5: 0xBF69, //HANGUL SYLLABLE SSANGPIEUP WA RIEULTHIEUTH - 0x96E6: 0xBF6A, //HANGUL SYLLABLE SSANGPIEUP WA RIEULPHIEUPH - 0x96E7: 0xBF6B, //HANGUL SYLLABLE SSANGPIEUP WA RIEULHIEUH - 0x96E8: 0xBF6C, //HANGUL SYLLABLE SSANGPIEUP WA MIEUM - 0x96E9: 0xBF6D, //HANGUL SYLLABLE SSANGPIEUP WA PIEUP - 0x96EA: 0xBF6E, //HANGUL SYLLABLE SSANGPIEUP WA PIEUPSIOS - 0x96EB: 0xBF6F, //HANGUL SYLLABLE SSANGPIEUP WA SIOS - 0x96EC: 0xBF70, //HANGUL SYLLABLE SSANGPIEUP WA SSANGSIOS - 0x96ED: 0xBF71, //HANGUL SYLLABLE SSANGPIEUP WA IEUNG - 0x96EE: 0xBF72, //HANGUL SYLLABLE SSANGPIEUP WA CIEUC - 0x96EF: 0xBF73, //HANGUL SYLLABLE SSANGPIEUP WA CHIEUCH - 0x96F0: 0xBF74, //HANGUL SYLLABLE SSANGPIEUP WA KHIEUKH - 0x96F1: 0xBF75, //HANGUL SYLLABLE SSANGPIEUP WA THIEUTH - 0x96F2: 0xBF76, //HANGUL SYLLABLE SSANGPIEUP WA PHIEUPH - 0x96F3: 0xBF77, //HANGUL SYLLABLE SSANGPIEUP WA HIEUH - 0x96F4: 0xBF78, //HANGUL SYLLABLE SSANGPIEUP WAE - 0x96F5: 0xBF79, //HANGUL SYLLABLE SSANGPIEUP WAE KIYEOK - 0x96F6: 0xBF7A, //HANGUL SYLLABLE SSANGPIEUP WAE SSANGKIYEOK - 0x96F7: 0xBF7B, //HANGUL SYLLABLE SSANGPIEUP WAE KIYEOKSIOS - 0x96F8: 0xBF7C, //HANGUL SYLLABLE SSANGPIEUP WAE NIEUN - 0x96F9: 0xBF7D, //HANGUL SYLLABLE SSANGPIEUP WAE NIEUNCIEUC - 0x96FA: 0xBF7E, //HANGUL SYLLABLE SSANGPIEUP WAE NIEUNHIEUH - 0x96FB: 0xBF7F, //HANGUL SYLLABLE SSANGPIEUP WAE TIKEUT - 0x96FC: 0xBF80, //HANGUL SYLLABLE SSANGPIEUP WAE RIEUL - 0x96FD: 0xBF81, //HANGUL SYLLABLE SSANGPIEUP WAE RIEULKIYEOK - 0x96FE: 0xBF82, //HANGUL SYLLABLE SSANGPIEUP WAE RIEULMIEUM - 0x9741: 0xBF83, //HANGUL SYLLABLE SSANGPIEUP WAE RIEULPIEUP - 0x9742: 0xBF84, //HANGUL SYLLABLE SSANGPIEUP WAE RIEULSIOS - 0x9743: 0xBF85, //HANGUL SYLLABLE SSANGPIEUP WAE RIEULTHIEUTH - 0x9744: 0xBF86, //HANGUL SYLLABLE SSANGPIEUP WAE RIEULPHIEUPH - 0x9745: 0xBF87, //HANGUL SYLLABLE SSANGPIEUP WAE RIEULHIEUH - 0x9746: 0xBF88, //HANGUL SYLLABLE SSANGPIEUP WAE MIEUM - 0x9747: 0xBF89, //HANGUL SYLLABLE SSANGPIEUP WAE PIEUP - 0x9748: 0xBF8A, //HANGUL SYLLABLE SSANGPIEUP WAE PIEUPSIOS - 0x9749: 0xBF8B, //HANGUL SYLLABLE SSANGPIEUP WAE SIOS - 0x974A: 0xBF8C, //HANGUL SYLLABLE SSANGPIEUP WAE SSANGSIOS - 0x974B: 0xBF8D, //HANGUL SYLLABLE SSANGPIEUP WAE IEUNG - 0x974C: 0xBF8E, //HANGUL SYLLABLE SSANGPIEUP WAE CIEUC - 0x974D: 0xBF8F, //HANGUL SYLLABLE SSANGPIEUP WAE CHIEUCH - 0x974E: 0xBF90, //HANGUL SYLLABLE SSANGPIEUP WAE KHIEUKH - 0x974F: 0xBF91, //HANGUL SYLLABLE SSANGPIEUP WAE THIEUTH - 0x9750: 0xBF92, //HANGUL SYLLABLE SSANGPIEUP WAE PHIEUPH - 0x9751: 0xBF93, //HANGUL SYLLABLE SSANGPIEUP WAE HIEUH - 0x9752: 0xBF95, //HANGUL SYLLABLE SSANGPIEUP OE KIYEOK - 0x9753: 0xBF96, //HANGUL SYLLABLE SSANGPIEUP OE SSANGKIYEOK - 0x9754: 0xBF97, //HANGUL SYLLABLE SSANGPIEUP OE KIYEOKSIOS - 0x9755: 0xBF98, //HANGUL SYLLABLE SSANGPIEUP OE NIEUN - 0x9756: 0xBF99, //HANGUL SYLLABLE SSANGPIEUP OE NIEUNCIEUC - 0x9757: 0xBF9A, //HANGUL SYLLABLE SSANGPIEUP OE NIEUNHIEUH - 0x9758: 0xBF9B, //HANGUL SYLLABLE SSANGPIEUP OE TIKEUT - 0x9759: 0xBF9C, //HANGUL SYLLABLE SSANGPIEUP OE RIEUL - 0x975A: 0xBF9D, //HANGUL SYLLABLE SSANGPIEUP OE RIEULKIYEOK - 0x9761: 0xBF9E, //HANGUL SYLLABLE SSANGPIEUP OE RIEULMIEUM - 0x9762: 0xBF9F, //HANGUL SYLLABLE SSANGPIEUP OE RIEULPIEUP - 0x9763: 0xBFA0, //HANGUL SYLLABLE SSANGPIEUP OE RIEULSIOS - 0x9764: 0xBFA1, //HANGUL SYLLABLE SSANGPIEUP OE RIEULTHIEUTH - 0x9765: 0xBFA2, //HANGUL SYLLABLE SSANGPIEUP OE RIEULPHIEUPH - 0x9766: 0xBFA3, //HANGUL SYLLABLE SSANGPIEUP OE RIEULHIEUH - 0x9767: 0xBFA4, //HANGUL SYLLABLE SSANGPIEUP OE MIEUM - 0x9768: 0xBFA5, //HANGUL SYLLABLE SSANGPIEUP OE PIEUP - 0x9769: 0xBFA6, //HANGUL SYLLABLE SSANGPIEUP OE PIEUPSIOS - 0x976A: 0xBFA7, //HANGUL SYLLABLE SSANGPIEUP OE SIOS - 0x976B: 0xBFA8, //HANGUL SYLLABLE SSANGPIEUP OE SSANGSIOS - 0x976C: 0xBFA9, //HANGUL SYLLABLE SSANGPIEUP OE IEUNG - 0x976D: 0xBFAA, //HANGUL SYLLABLE SSANGPIEUP OE CIEUC - 0x976E: 0xBFAB, //HANGUL SYLLABLE SSANGPIEUP OE CHIEUCH - 0x976F: 0xBFAC, //HANGUL SYLLABLE SSANGPIEUP OE KHIEUKH - 0x9770: 0xBFAD, //HANGUL SYLLABLE SSANGPIEUP OE THIEUTH - 0x9771: 0xBFAE, //HANGUL SYLLABLE SSANGPIEUP OE PHIEUPH - 0x9772: 0xBFAF, //HANGUL SYLLABLE SSANGPIEUP OE HIEUH - 0x9773: 0xBFB1, //HANGUL SYLLABLE SSANGPIEUP YO KIYEOK - 0x9774: 0xBFB2, //HANGUL SYLLABLE SSANGPIEUP YO SSANGKIYEOK - 0x9775: 0xBFB3, //HANGUL SYLLABLE SSANGPIEUP YO KIYEOKSIOS - 0x9776: 0xBFB4, //HANGUL SYLLABLE SSANGPIEUP YO NIEUN - 0x9777: 0xBFB5, //HANGUL SYLLABLE SSANGPIEUP YO NIEUNCIEUC - 0x9778: 0xBFB6, //HANGUL SYLLABLE SSANGPIEUP YO NIEUNHIEUH - 0x9779: 0xBFB7, //HANGUL SYLLABLE SSANGPIEUP YO TIKEUT - 0x977A: 0xBFB8, //HANGUL SYLLABLE SSANGPIEUP YO RIEUL - 0x9781: 0xBFB9, //HANGUL SYLLABLE SSANGPIEUP YO RIEULKIYEOK - 0x9782: 0xBFBA, //HANGUL SYLLABLE SSANGPIEUP YO RIEULMIEUM - 0x9783: 0xBFBB, //HANGUL SYLLABLE SSANGPIEUP YO RIEULPIEUP - 0x9784: 0xBFBC, //HANGUL SYLLABLE SSANGPIEUP YO RIEULSIOS - 0x9785: 0xBFBD, //HANGUL SYLLABLE SSANGPIEUP YO RIEULTHIEUTH - 0x9786: 0xBFBE, //HANGUL SYLLABLE SSANGPIEUP YO RIEULPHIEUPH - 0x9787: 0xBFBF, //HANGUL SYLLABLE SSANGPIEUP YO RIEULHIEUH - 0x9788: 0xBFC0, //HANGUL SYLLABLE SSANGPIEUP YO MIEUM - 0x9789: 0xBFC1, //HANGUL SYLLABLE SSANGPIEUP YO PIEUP - 0x978A: 0xBFC2, //HANGUL SYLLABLE SSANGPIEUP YO PIEUPSIOS - 0x978B: 0xBFC3, //HANGUL SYLLABLE SSANGPIEUP YO SIOS - 0x978C: 0xBFC4, //HANGUL SYLLABLE SSANGPIEUP YO SSANGSIOS - 0x978D: 0xBFC6, //HANGUL SYLLABLE SSANGPIEUP YO CIEUC - 0x978E: 0xBFC7, //HANGUL SYLLABLE SSANGPIEUP YO CHIEUCH - 0x978F: 0xBFC8, //HANGUL SYLLABLE SSANGPIEUP YO KHIEUKH - 0x9790: 0xBFC9, //HANGUL SYLLABLE SSANGPIEUP YO THIEUTH - 0x9791: 0xBFCA, //HANGUL SYLLABLE SSANGPIEUP YO PHIEUPH - 0x9792: 0xBFCB, //HANGUL SYLLABLE SSANGPIEUP YO HIEUH - 0x9793: 0xBFCE, //HANGUL SYLLABLE SSANGPIEUP U SSANGKIYEOK - 0x9794: 0xBFCF, //HANGUL SYLLABLE SSANGPIEUP U KIYEOKSIOS - 0x9795: 0xBFD1, //HANGUL SYLLABLE SSANGPIEUP U NIEUNCIEUC - 0x9796: 0xBFD2, //HANGUL SYLLABLE SSANGPIEUP U NIEUNHIEUH - 0x9797: 0xBFD3, //HANGUL SYLLABLE SSANGPIEUP U TIKEUT - 0x9798: 0xBFD5, //HANGUL SYLLABLE SSANGPIEUP U RIEULKIYEOK - 0x9799: 0xBFD6, //HANGUL SYLLABLE SSANGPIEUP U RIEULMIEUM - 0x979A: 0xBFD7, //HANGUL SYLLABLE SSANGPIEUP U RIEULPIEUP - 0x979B: 0xBFD8, //HANGUL SYLLABLE SSANGPIEUP U RIEULSIOS - 0x979C: 0xBFD9, //HANGUL SYLLABLE SSANGPIEUP U RIEULTHIEUTH - 0x979D: 0xBFDA, //HANGUL SYLLABLE SSANGPIEUP U RIEULPHIEUPH - 0x979E: 0xBFDB, //HANGUL SYLLABLE SSANGPIEUP U RIEULHIEUH - 0x979F: 0xBFDD, //HANGUL SYLLABLE SSANGPIEUP U PIEUP - 0x97A0: 0xBFDE, //HANGUL SYLLABLE SSANGPIEUP U PIEUPSIOS - 0x97A1: 0xBFE0, //HANGUL SYLLABLE SSANGPIEUP U SSANGSIOS - 0x97A2: 0xBFE2, //HANGUL SYLLABLE SSANGPIEUP U CIEUC - 0x97A3: 0xBFE3, //HANGUL SYLLABLE SSANGPIEUP U CHIEUCH - 0x97A4: 0xBFE4, //HANGUL SYLLABLE SSANGPIEUP U KHIEUKH - 0x97A5: 0xBFE5, //HANGUL SYLLABLE SSANGPIEUP U THIEUTH - 0x97A6: 0xBFE6, //HANGUL SYLLABLE SSANGPIEUP U PHIEUPH - 0x97A7: 0xBFE7, //HANGUL SYLLABLE SSANGPIEUP U HIEUH - 0x97A8: 0xBFE8, //HANGUL SYLLABLE SSANGPIEUP WEO - 0x97A9: 0xBFE9, //HANGUL SYLLABLE SSANGPIEUP WEO KIYEOK - 0x97AA: 0xBFEA, //HANGUL SYLLABLE SSANGPIEUP WEO SSANGKIYEOK - 0x97AB: 0xBFEB, //HANGUL SYLLABLE SSANGPIEUP WEO KIYEOKSIOS - 0x97AC: 0xBFEC, //HANGUL SYLLABLE SSANGPIEUP WEO NIEUN - 0x97AD: 0xBFED, //HANGUL SYLLABLE SSANGPIEUP WEO NIEUNCIEUC - 0x97AE: 0xBFEE, //HANGUL SYLLABLE SSANGPIEUP WEO NIEUNHIEUH - 0x97AF: 0xBFEF, //HANGUL SYLLABLE SSANGPIEUP WEO TIKEUT - 0x97B0: 0xBFF0, //HANGUL SYLLABLE SSANGPIEUP WEO RIEUL - 0x97B1: 0xBFF1, //HANGUL SYLLABLE SSANGPIEUP WEO RIEULKIYEOK - 0x97B2: 0xBFF2, //HANGUL SYLLABLE SSANGPIEUP WEO RIEULMIEUM - 0x97B3: 0xBFF3, //HANGUL SYLLABLE SSANGPIEUP WEO RIEULPIEUP - 0x97B4: 0xBFF4, //HANGUL SYLLABLE SSANGPIEUP WEO RIEULSIOS - 0x97B5: 0xBFF5, //HANGUL SYLLABLE SSANGPIEUP WEO RIEULTHIEUTH - 0x97B6: 0xBFF6, //HANGUL SYLLABLE SSANGPIEUP WEO RIEULPHIEUPH - 0x97B7: 0xBFF7, //HANGUL SYLLABLE SSANGPIEUP WEO RIEULHIEUH - 0x97B8: 0xBFF8, //HANGUL SYLLABLE SSANGPIEUP WEO MIEUM - 0x97B9: 0xBFF9, //HANGUL SYLLABLE SSANGPIEUP WEO PIEUP - 0x97BA: 0xBFFA, //HANGUL SYLLABLE SSANGPIEUP WEO PIEUPSIOS - 0x97BB: 0xBFFB, //HANGUL SYLLABLE SSANGPIEUP WEO SIOS - 0x97BC: 0xBFFC, //HANGUL SYLLABLE SSANGPIEUP WEO SSANGSIOS - 0x97BD: 0xBFFD, //HANGUL SYLLABLE SSANGPIEUP WEO IEUNG - 0x97BE: 0xBFFE, //HANGUL SYLLABLE SSANGPIEUP WEO CIEUC - 0x97BF: 0xBFFF, //HANGUL SYLLABLE SSANGPIEUP WEO CHIEUCH - 0x97C0: 0xC000, //HANGUL SYLLABLE SSANGPIEUP WEO KHIEUKH - 0x97C1: 0xC001, //HANGUL SYLLABLE SSANGPIEUP WEO THIEUTH - 0x97C2: 0xC002, //HANGUL SYLLABLE SSANGPIEUP WEO PHIEUPH - 0x97C3: 0xC003, //HANGUL SYLLABLE SSANGPIEUP WEO HIEUH - 0x97C4: 0xC004, //HANGUL SYLLABLE SSANGPIEUP WE - 0x97C5: 0xC005, //HANGUL SYLLABLE SSANGPIEUP WE KIYEOK - 0x97C6: 0xC006, //HANGUL SYLLABLE SSANGPIEUP WE SSANGKIYEOK - 0x97C7: 0xC007, //HANGUL SYLLABLE SSANGPIEUP WE KIYEOKSIOS - 0x97C8: 0xC008, //HANGUL SYLLABLE SSANGPIEUP WE NIEUN - 0x97C9: 0xC009, //HANGUL SYLLABLE SSANGPIEUP WE NIEUNCIEUC - 0x97CA: 0xC00A, //HANGUL SYLLABLE SSANGPIEUP WE NIEUNHIEUH - 0x97CB: 0xC00B, //HANGUL SYLLABLE SSANGPIEUP WE TIKEUT - 0x97CC: 0xC00C, //HANGUL SYLLABLE SSANGPIEUP WE RIEUL - 0x97CD: 0xC00D, //HANGUL SYLLABLE SSANGPIEUP WE RIEULKIYEOK - 0x97CE: 0xC00E, //HANGUL SYLLABLE SSANGPIEUP WE RIEULMIEUM - 0x97CF: 0xC00F, //HANGUL SYLLABLE SSANGPIEUP WE RIEULPIEUP - 0x97D0: 0xC010, //HANGUL SYLLABLE SSANGPIEUP WE RIEULSIOS - 0x97D1: 0xC011, //HANGUL SYLLABLE SSANGPIEUP WE RIEULTHIEUTH - 0x97D2: 0xC012, //HANGUL SYLLABLE SSANGPIEUP WE RIEULPHIEUPH - 0x97D3: 0xC013, //HANGUL SYLLABLE SSANGPIEUP WE RIEULHIEUH - 0x97D4: 0xC014, //HANGUL SYLLABLE SSANGPIEUP WE MIEUM - 0x97D5: 0xC015, //HANGUL SYLLABLE SSANGPIEUP WE PIEUP - 0x97D6: 0xC016, //HANGUL SYLLABLE SSANGPIEUP WE PIEUPSIOS - 0x97D7: 0xC017, //HANGUL SYLLABLE SSANGPIEUP WE SIOS - 0x97D8: 0xC018, //HANGUL SYLLABLE SSANGPIEUP WE SSANGSIOS - 0x97D9: 0xC019, //HANGUL SYLLABLE SSANGPIEUP WE IEUNG - 0x97DA: 0xC01A, //HANGUL SYLLABLE SSANGPIEUP WE CIEUC - 0x97DB: 0xC01B, //HANGUL SYLLABLE SSANGPIEUP WE CHIEUCH - 0x97DC: 0xC01C, //HANGUL SYLLABLE SSANGPIEUP WE KHIEUKH - 0x97DD: 0xC01D, //HANGUL SYLLABLE SSANGPIEUP WE THIEUTH - 0x97DE: 0xC01E, //HANGUL SYLLABLE SSANGPIEUP WE PHIEUPH - 0x97DF: 0xC01F, //HANGUL SYLLABLE SSANGPIEUP WE HIEUH - 0x97E0: 0xC020, //HANGUL SYLLABLE SSANGPIEUP WI - 0x97E1: 0xC021, //HANGUL SYLLABLE SSANGPIEUP WI KIYEOK - 0x97E2: 0xC022, //HANGUL SYLLABLE SSANGPIEUP WI SSANGKIYEOK - 0x97E3: 0xC023, //HANGUL SYLLABLE SSANGPIEUP WI KIYEOKSIOS - 0x97E4: 0xC024, //HANGUL SYLLABLE SSANGPIEUP WI NIEUN - 0x97E5: 0xC025, //HANGUL SYLLABLE SSANGPIEUP WI NIEUNCIEUC - 0x97E6: 0xC026, //HANGUL SYLLABLE SSANGPIEUP WI NIEUNHIEUH - 0x97E7: 0xC027, //HANGUL SYLLABLE SSANGPIEUP WI TIKEUT - 0x97E8: 0xC028, //HANGUL SYLLABLE SSANGPIEUP WI RIEUL - 0x97E9: 0xC029, //HANGUL SYLLABLE SSANGPIEUP WI RIEULKIYEOK - 0x97EA: 0xC02A, //HANGUL SYLLABLE SSANGPIEUP WI RIEULMIEUM - 0x97EB: 0xC02B, //HANGUL SYLLABLE SSANGPIEUP WI RIEULPIEUP - 0x97EC: 0xC02C, //HANGUL SYLLABLE SSANGPIEUP WI RIEULSIOS - 0x97ED: 0xC02D, //HANGUL SYLLABLE SSANGPIEUP WI RIEULTHIEUTH - 0x97EE: 0xC02E, //HANGUL SYLLABLE SSANGPIEUP WI RIEULPHIEUPH - 0x97EF: 0xC02F, //HANGUL SYLLABLE SSANGPIEUP WI RIEULHIEUH - 0x97F0: 0xC030, //HANGUL SYLLABLE SSANGPIEUP WI MIEUM - 0x97F1: 0xC031, //HANGUL SYLLABLE SSANGPIEUP WI PIEUP - 0x97F2: 0xC032, //HANGUL SYLLABLE SSANGPIEUP WI PIEUPSIOS - 0x97F3: 0xC033, //HANGUL SYLLABLE SSANGPIEUP WI SIOS - 0x97F4: 0xC034, //HANGUL SYLLABLE SSANGPIEUP WI SSANGSIOS - 0x97F5: 0xC035, //HANGUL SYLLABLE SSANGPIEUP WI IEUNG - 0x97F6: 0xC036, //HANGUL SYLLABLE SSANGPIEUP WI CIEUC - 0x97F7: 0xC037, //HANGUL SYLLABLE SSANGPIEUP WI CHIEUCH - 0x97F8: 0xC038, //HANGUL SYLLABLE SSANGPIEUP WI KHIEUKH - 0x97F9: 0xC039, //HANGUL SYLLABLE SSANGPIEUP WI THIEUTH - 0x97FA: 0xC03A, //HANGUL SYLLABLE SSANGPIEUP WI PHIEUPH - 0x97FB: 0xC03B, //HANGUL SYLLABLE SSANGPIEUP WI HIEUH - 0x97FC: 0xC03D, //HANGUL SYLLABLE SSANGPIEUP YU KIYEOK - 0x97FD: 0xC03E, //HANGUL SYLLABLE SSANGPIEUP YU SSANGKIYEOK - 0x97FE: 0xC03F, //HANGUL SYLLABLE SSANGPIEUP YU KIYEOKSIOS - 0x9841: 0xC040, //HANGUL SYLLABLE SSANGPIEUP YU NIEUN - 0x9842: 0xC041, //HANGUL SYLLABLE SSANGPIEUP YU NIEUNCIEUC - 0x9843: 0xC042, //HANGUL SYLLABLE SSANGPIEUP YU NIEUNHIEUH - 0x9844: 0xC043, //HANGUL SYLLABLE SSANGPIEUP YU TIKEUT - 0x9845: 0xC044, //HANGUL SYLLABLE SSANGPIEUP YU RIEUL - 0x9846: 0xC045, //HANGUL SYLLABLE SSANGPIEUP YU RIEULKIYEOK - 0x9847: 0xC046, //HANGUL SYLLABLE SSANGPIEUP YU RIEULMIEUM - 0x9848: 0xC047, //HANGUL SYLLABLE SSANGPIEUP YU RIEULPIEUP - 0x9849: 0xC048, //HANGUL SYLLABLE SSANGPIEUP YU RIEULSIOS - 0x984A: 0xC049, //HANGUL SYLLABLE SSANGPIEUP YU RIEULTHIEUTH - 0x984B: 0xC04A, //HANGUL SYLLABLE SSANGPIEUP YU RIEULPHIEUPH - 0x984C: 0xC04B, //HANGUL SYLLABLE SSANGPIEUP YU RIEULHIEUH - 0x984D: 0xC04C, //HANGUL SYLLABLE SSANGPIEUP YU MIEUM - 0x984E: 0xC04D, //HANGUL SYLLABLE SSANGPIEUP YU PIEUP - 0x984F: 0xC04E, //HANGUL SYLLABLE SSANGPIEUP YU PIEUPSIOS - 0x9850: 0xC04F, //HANGUL SYLLABLE SSANGPIEUP YU SIOS - 0x9851: 0xC050, //HANGUL SYLLABLE SSANGPIEUP YU SSANGSIOS - 0x9852: 0xC052, //HANGUL SYLLABLE SSANGPIEUP YU CIEUC - 0x9853: 0xC053, //HANGUL SYLLABLE SSANGPIEUP YU CHIEUCH - 0x9854: 0xC054, //HANGUL SYLLABLE SSANGPIEUP YU KHIEUKH - 0x9855: 0xC055, //HANGUL SYLLABLE SSANGPIEUP YU THIEUTH - 0x9856: 0xC056, //HANGUL SYLLABLE SSANGPIEUP YU PHIEUPH - 0x9857: 0xC057, //HANGUL SYLLABLE SSANGPIEUP YU HIEUH - 0x9858: 0xC059, //HANGUL SYLLABLE SSANGPIEUP EU KIYEOK - 0x9859: 0xC05A, //HANGUL SYLLABLE SSANGPIEUP EU SSANGKIYEOK - 0x985A: 0xC05B, //HANGUL SYLLABLE SSANGPIEUP EU KIYEOKSIOS - 0x9861: 0xC05D, //HANGUL SYLLABLE SSANGPIEUP EU NIEUNCIEUC - 0x9862: 0xC05E, //HANGUL SYLLABLE SSANGPIEUP EU NIEUNHIEUH - 0x9863: 0xC05F, //HANGUL SYLLABLE SSANGPIEUP EU TIKEUT - 0x9864: 0xC061, //HANGUL SYLLABLE SSANGPIEUP EU RIEULKIYEOK - 0x9865: 0xC062, //HANGUL SYLLABLE SSANGPIEUP EU RIEULMIEUM - 0x9866: 0xC063, //HANGUL SYLLABLE SSANGPIEUP EU RIEULPIEUP - 0x9867: 0xC064, //HANGUL SYLLABLE SSANGPIEUP EU RIEULSIOS - 0x9868: 0xC065, //HANGUL SYLLABLE SSANGPIEUP EU RIEULTHIEUTH - 0x9869: 0xC066, //HANGUL SYLLABLE SSANGPIEUP EU RIEULPHIEUPH - 0x986A: 0xC067, //HANGUL SYLLABLE SSANGPIEUP EU RIEULHIEUH - 0x986B: 0xC06A, //HANGUL SYLLABLE SSANGPIEUP EU PIEUPSIOS - 0x986C: 0xC06B, //HANGUL SYLLABLE SSANGPIEUP EU SIOS - 0x986D: 0xC06C, //HANGUL SYLLABLE SSANGPIEUP EU SSANGSIOS - 0x986E: 0xC06D, //HANGUL SYLLABLE SSANGPIEUP EU IEUNG - 0x986F: 0xC06E, //HANGUL SYLLABLE SSANGPIEUP EU CIEUC - 0x9870: 0xC06F, //HANGUL SYLLABLE SSANGPIEUP EU CHIEUCH - 0x9871: 0xC070, //HANGUL SYLLABLE SSANGPIEUP EU KHIEUKH - 0x9872: 0xC071, //HANGUL SYLLABLE SSANGPIEUP EU THIEUTH - 0x9873: 0xC072, //HANGUL SYLLABLE SSANGPIEUP EU PHIEUPH - 0x9874: 0xC073, //HANGUL SYLLABLE SSANGPIEUP EU HIEUH - 0x9875: 0xC074, //HANGUL SYLLABLE SSANGPIEUP YI - 0x9876: 0xC075, //HANGUL SYLLABLE SSANGPIEUP YI KIYEOK - 0x9877: 0xC076, //HANGUL SYLLABLE SSANGPIEUP YI SSANGKIYEOK - 0x9878: 0xC077, //HANGUL SYLLABLE SSANGPIEUP YI KIYEOKSIOS - 0x9879: 0xC078, //HANGUL SYLLABLE SSANGPIEUP YI NIEUN - 0x987A: 0xC079, //HANGUL SYLLABLE SSANGPIEUP YI NIEUNCIEUC - 0x9881: 0xC07A, //HANGUL SYLLABLE SSANGPIEUP YI NIEUNHIEUH - 0x9882: 0xC07B, //HANGUL SYLLABLE SSANGPIEUP YI TIKEUT - 0x9883: 0xC07C, //HANGUL SYLLABLE SSANGPIEUP YI RIEUL - 0x9884: 0xC07D, //HANGUL SYLLABLE SSANGPIEUP YI RIEULKIYEOK - 0x9885: 0xC07E, //HANGUL SYLLABLE SSANGPIEUP YI RIEULMIEUM - 0x9886: 0xC07F, //HANGUL SYLLABLE SSANGPIEUP YI RIEULPIEUP - 0x9887: 0xC080, //HANGUL SYLLABLE SSANGPIEUP YI RIEULSIOS - 0x9888: 0xC081, //HANGUL SYLLABLE SSANGPIEUP YI RIEULTHIEUTH - 0x9889: 0xC082, //HANGUL SYLLABLE SSANGPIEUP YI RIEULPHIEUPH - 0x988A: 0xC083, //HANGUL SYLLABLE SSANGPIEUP YI RIEULHIEUH - 0x988B: 0xC084, //HANGUL SYLLABLE SSANGPIEUP YI MIEUM - 0x988C: 0xC085, //HANGUL SYLLABLE SSANGPIEUP YI PIEUP - 0x988D: 0xC086, //HANGUL SYLLABLE SSANGPIEUP YI PIEUPSIOS - 0x988E: 0xC087, //HANGUL SYLLABLE SSANGPIEUP YI SIOS - 0x988F: 0xC088, //HANGUL SYLLABLE SSANGPIEUP YI SSANGSIOS - 0x9890: 0xC089, //HANGUL SYLLABLE SSANGPIEUP YI IEUNG - 0x9891: 0xC08A, //HANGUL SYLLABLE SSANGPIEUP YI CIEUC - 0x9892: 0xC08B, //HANGUL SYLLABLE SSANGPIEUP YI CHIEUCH - 0x9893: 0xC08C, //HANGUL SYLLABLE SSANGPIEUP YI KHIEUKH - 0x9894: 0xC08D, //HANGUL SYLLABLE SSANGPIEUP YI THIEUTH - 0x9895: 0xC08E, //HANGUL SYLLABLE SSANGPIEUP YI PHIEUPH - 0x9896: 0xC08F, //HANGUL SYLLABLE SSANGPIEUP YI HIEUH - 0x9897: 0xC092, //HANGUL SYLLABLE SSANGPIEUP I SSANGKIYEOK - 0x9898: 0xC093, //HANGUL SYLLABLE SSANGPIEUP I KIYEOKSIOS - 0x9899: 0xC095, //HANGUL SYLLABLE SSANGPIEUP I NIEUNCIEUC - 0x989A: 0xC096, //HANGUL SYLLABLE SSANGPIEUP I NIEUNHIEUH - 0x989B: 0xC097, //HANGUL SYLLABLE SSANGPIEUP I TIKEUT - 0x989C: 0xC099, //HANGUL SYLLABLE SSANGPIEUP I RIEULKIYEOK - 0x989D: 0xC09A, //HANGUL SYLLABLE SSANGPIEUP I RIEULMIEUM - 0x989E: 0xC09B, //HANGUL SYLLABLE SSANGPIEUP I RIEULPIEUP - 0x989F: 0xC09C, //HANGUL SYLLABLE SSANGPIEUP I RIEULSIOS - 0x98A0: 0xC09D, //HANGUL SYLLABLE SSANGPIEUP I RIEULTHIEUTH - 0x98A1: 0xC09E, //HANGUL SYLLABLE SSANGPIEUP I RIEULPHIEUPH - 0x98A2: 0xC09F, //HANGUL SYLLABLE SSANGPIEUP I RIEULHIEUH - 0x98A3: 0xC0A2, //HANGUL SYLLABLE SSANGPIEUP I PIEUPSIOS - 0x98A4: 0xC0A4, //HANGUL SYLLABLE SSANGPIEUP I SSANGSIOS - 0x98A5: 0xC0A6, //HANGUL SYLLABLE SSANGPIEUP I CIEUC - 0x98A6: 0xC0A7, //HANGUL SYLLABLE SSANGPIEUP I CHIEUCH - 0x98A7: 0xC0A8, //HANGUL SYLLABLE SSANGPIEUP I KHIEUKH - 0x98A8: 0xC0A9, //HANGUL SYLLABLE SSANGPIEUP I THIEUTH - 0x98A9: 0xC0AA, //HANGUL SYLLABLE SSANGPIEUP I PHIEUPH - 0x98AA: 0xC0AB, //HANGUL SYLLABLE SSANGPIEUP I HIEUH - 0x98AB: 0xC0AE, //HANGUL SYLLABLE SIOS A SSANGKIYEOK - 0x98AC: 0xC0B1, //HANGUL SYLLABLE SIOS A NIEUNCIEUC - 0x98AD: 0xC0B2, //HANGUL SYLLABLE SIOS A NIEUNHIEUH - 0x98AE: 0xC0B7, //HANGUL SYLLABLE SIOS A RIEULPIEUP - 0x98AF: 0xC0B8, //HANGUL SYLLABLE SIOS A RIEULSIOS - 0x98B0: 0xC0B9, //HANGUL SYLLABLE SIOS A RIEULTHIEUTH - 0x98B1: 0xC0BA, //HANGUL SYLLABLE SIOS A RIEULPHIEUPH - 0x98B2: 0xC0BB, //HANGUL SYLLABLE SIOS A RIEULHIEUH - 0x98B3: 0xC0BE, //HANGUL SYLLABLE SIOS A PIEUPSIOS - 0x98B4: 0xC0C2, //HANGUL SYLLABLE SIOS A CIEUC - 0x98B5: 0xC0C3, //HANGUL SYLLABLE SIOS A CHIEUCH - 0x98B6: 0xC0C4, //HANGUL SYLLABLE SIOS A KHIEUKH - 0x98B7: 0xC0C6, //HANGUL SYLLABLE SIOS A PHIEUPH - 0x98B8: 0xC0C7, //HANGUL SYLLABLE SIOS A HIEUH - 0x98B9: 0xC0CA, //HANGUL SYLLABLE SIOS AE SSANGKIYEOK - 0x98BA: 0xC0CB, //HANGUL SYLLABLE SIOS AE KIYEOKSIOS - 0x98BB: 0xC0CD, //HANGUL SYLLABLE SIOS AE NIEUNCIEUC - 0x98BC: 0xC0CE, //HANGUL SYLLABLE SIOS AE NIEUNHIEUH - 0x98BD: 0xC0CF, //HANGUL SYLLABLE SIOS AE TIKEUT - 0x98BE: 0xC0D1, //HANGUL SYLLABLE SIOS AE RIEULKIYEOK - 0x98BF: 0xC0D2, //HANGUL SYLLABLE SIOS AE RIEULMIEUM - 0x98C0: 0xC0D3, //HANGUL SYLLABLE SIOS AE RIEULPIEUP - 0x98C1: 0xC0D4, //HANGUL SYLLABLE SIOS AE RIEULSIOS - 0x98C2: 0xC0D5, //HANGUL SYLLABLE SIOS AE RIEULTHIEUTH - 0x98C3: 0xC0D6, //HANGUL SYLLABLE SIOS AE RIEULPHIEUPH - 0x98C4: 0xC0D7, //HANGUL SYLLABLE SIOS AE RIEULHIEUH - 0x98C5: 0xC0DA, //HANGUL SYLLABLE SIOS AE PIEUPSIOS - 0x98C6: 0xC0DE, //HANGUL SYLLABLE SIOS AE CIEUC - 0x98C7: 0xC0DF, //HANGUL SYLLABLE SIOS AE CHIEUCH - 0x98C8: 0xC0E0, //HANGUL SYLLABLE SIOS AE KHIEUKH - 0x98C9: 0xC0E1, //HANGUL SYLLABLE SIOS AE THIEUTH - 0x98CA: 0xC0E2, //HANGUL SYLLABLE SIOS AE PHIEUPH - 0x98CB: 0xC0E3, //HANGUL SYLLABLE SIOS AE HIEUH - 0x98CC: 0xC0E6, //HANGUL SYLLABLE SIOS YA SSANGKIYEOK - 0x98CD: 0xC0E7, //HANGUL SYLLABLE SIOS YA KIYEOKSIOS - 0x98CE: 0xC0E9, //HANGUL SYLLABLE SIOS YA NIEUNCIEUC - 0x98CF: 0xC0EA, //HANGUL SYLLABLE SIOS YA NIEUNHIEUH - 0x98D0: 0xC0EB, //HANGUL SYLLABLE SIOS YA TIKEUT - 0x98D1: 0xC0ED, //HANGUL SYLLABLE SIOS YA RIEULKIYEOK - 0x98D2: 0xC0EE, //HANGUL SYLLABLE SIOS YA RIEULMIEUM - 0x98D3: 0xC0EF, //HANGUL SYLLABLE SIOS YA RIEULPIEUP - 0x98D4: 0xC0F0, //HANGUL SYLLABLE SIOS YA RIEULSIOS - 0x98D5: 0xC0F1, //HANGUL SYLLABLE SIOS YA RIEULTHIEUTH - 0x98D6: 0xC0F2, //HANGUL SYLLABLE SIOS YA RIEULPHIEUPH - 0x98D7: 0xC0F3, //HANGUL SYLLABLE SIOS YA RIEULHIEUH - 0x98D8: 0xC0F6, //HANGUL SYLLABLE SIOS YA PIEUPSIOS - 0x98D9: 0xC0F8, //HANGUL SYLLABLE SIOS YA SSANGSIOS - 0x98DA: 0xC0FA, //HANGUL SYLLABLE SIOS YA CIEUC - 0x98DB: 0xC0FB, //HANGUL SYLLABLE SIOS YA CHIEUCH - 0x98DC: 0xC0FC, //HANGUL SYLLABLE SIOS YA KHIEUKH - 0x98DD: 0xC0FD, //HANGUL SYLLABLE SIOS YA THIEUTH - 0x98DE: 0xC0FE, //HANGUL SYLLABLE SIOS YA PHIEUPH - 0x98DF: 0xC0FF, //HANGUL SYLLABLE SIOS YA HIEUH - 0x98E0: 0xC101, //HANGUL SYLLABLE SIOS YAE KIYEOK - 0x98E1: 0xC102, //HANGUL SYLLABLE SIOS YAE SSANGKIYEOK - 0x98E2: 0xC103, //HANGUL SYLLABLE SIOS YAE KIYEOKSIOS - 0x98E3: 0xC105, //HANGUL SYLLABLE SIOS YAE NIEUNCIEUC - 0x98E4: 0xC106, //HANGUL SYLLABLE SIOS YAE NIEUNHIEUH - 0x98E5: 0xC107, //HANGUL SYLLABLE SIOS YAE TIKEUT - 0x98E6: 0xC109, //HANGUL SYLLABLE SIOS YAE RIEULKIYEOK - 0x98E7: 0xC10A, //HANGUL SYLLABLE SIOS YAE RIEULMIEUM - 0x98E8: 0xC10B, //HANGUL SYLLABLE SIOS YAE RIEULPIEUP - 0x98E9: 0xC10C, //HANGUL SYLLABLE SIOS YAE RIEULSIOS - 0x98EA: 0xC10D, //HANGUL SYLLABLE SIOS YAE RIEULTHIEUTH - 0x98EB: 0xC10E, //HANGUL SYLLABLE SIOS YAE RIEULPHIEUPH - 0x98EC: 0xC10F, //HANGUL SYLLABLE SIOS YAE RIEULHIEUH - 0x98ED: 0xC111, //HANGUL SYLLABLE SIOS YAE PIEUP - 0x98EE: 0xC112, //HANGUL SYLLABLE SIOS YAE PIEUPSIOS - 0x98EF: 0xC113, //HANGUL SYLLABLE SIOS YAE SIOS - 0x98F0: 0xC114, //HANGUL SYLLABLE SIOS YAE SSANGSIOS - 0x98F1: 0xC116, //HANGUL SYLLABLE SIOS YAE CIEUC - 0x98F2: 0xC117, //HANGUL SYLLABLE SIOS YAE CHIEUCH - 0x98F3: 0xC118, //HANGUL SYLLABLE SIOS YAE KHIEUKH - 0x98F4: 0xC119, //HANGUL SYLLABLE SIOS YAE THIEUTH - 0x98F5: 0xC11A, //HANGUL SYLLABLE SIOS YAE PHIEUPH - 0x98F6: 0xC11B, //HANGUL SYLLABLE SIOS YAE HIEUH - 0x98F7: 0xC121, //HANGUL SYLLABLE SIOS EO NIEUNCIEUC - 0x98F8: 0xC122, //HANGUL SYLLABLE SIOS EO NIEUNHIEUH - 0x98F9: 0xC125, //HANGUL SYLLABLE SIOS EO RIEULKIYEOK - 0x98FA: 0xC128, //HANGUL SYLLABLE SIOS EO RIEULSIOS - 0x98FB: 0xC129, //HANGUL SYLLABLE SIOS EO RIEULTHIEUTH - 0x98FC: 0xC12A, //HANGUL SYLLABLE SIOS EO RIEULPHIEUPH - 0x98FD: 0xC12B, //HANGUL SYLLABLE SIOS EO RIEULHIEUH - 0x98FE: 0xC12E, //HANGUL SYLLABLE SIOS EO PIEUPSIOS - 0x9941: 0xC132, //HANGUL SYLLABLE SIOS EO CIEUC - 0x9942: 0xC133, //HANGUL SYLLABLE SIOS EO CHIEUCH - 0x9943: 0xC134, //HANGUL SYLLABLE SIOS EO KHIEUKH - 0x9944: 0xC135, //HANGUL SYLLABLE SIOS EO THIEUTH - 0x9945: 0xC137, //HANGUL SYLLABLE SIOS EO HIEUH - 0x9946: 0xC13A, //HANGUL SYLLABLE SIOS E SSANGKIYEOK - 0x9947: 0xC13B, //HANGUL SYLLABLE SIOS E KIYEOKSIOS - 0x9948: 0xC13D, //HANGUL SYLLABLE SIOS E NIEUNCIEUC - 0x9949: 0xC13E, //HANGUL SYLLABLE SIOS E NIEUNHIEUH - 0x994A: 0xC13F, //HANGUL SYLLABLE SIOS E TIKEUT - 0x994B: 0xC141, //HANGUL SYLLABLE SIOS E RIEULKIYEOK - 0x994C: 0xC142, //HANGUL SYLLABLE SIOS E RIEULMIEUM - 0x994D: 0xC143, //HANGUL SYLLABLE SIOS E RIEULPIEUP - 0x994E: 0xC144, //HANGUL SYLLABLE SIOS E RIEULSIOS - 0x994F: 0xC145, //HANGUL SYLLABLE SIOS E RIEULTHIEUTH - 0x9950: 0xC146, //HANGUL SYLLABLE SIOS E RIEULPHIEUPH - 0x9951: 0xC147, //HANGUL SYLLABLE SIOS E RIEULHIEUH - 0x9952: 0xC14A, //HANGUL SYLLABLE SIOS E PIEUPSIOS - 0x9953: 0xC14E, //HANGUL SYLLABLE SIOS E CIEUC - 0x9954: 0xC14F, //HANGUL SYLLABLE SIOS E CHIEUCH - 0x9955: 0xC150, //HANGUL SYLLABLE SIOS E KHIEUKH - 0x9956: 0xC151, //HANGUL SYLLABLE SIOS E THIEUTH - 0x9957: 0xC152, //HANGUL SYLLABLE SIOS E PHIEUPH - 0x9958: 0xC153, //HANGUL SYLLABLE SIOS E HIEUH - 0x9959: 0xC156, //HANGUL SYLLABLE SIOS YEO SSANGKIYEOK - 0x995A: 0xC157, //HANGUL SYLLABLE SIOS YEO KIYEOKSIOS - 0x9961: 0xC159, //HANGUL SYLLABLE SIOS YEO NIEUNCIEUC - 0x9962: 0xC15A, //HANGUL SYLLABLE SIOS YEO NIEUNHIEUH - 0x9963: 0xC15B, //HANGUL SYLLABLE SIOS YEO TIKEUT - 0x9964: 0xC15D, //HANGUL SYLLABLE SIOS YEO RIEULKIYEOK - 0x9965: 0xC15E, //HANGUL SYLLABLE SIOS YEO RIEULMIEUM - 0x9966: 0xC15F, //HANGUL SYLLABLE SIOS YEO RIEULPIEUP - 0x9967: 0xC160, //HANGUL SYLLABLE SIOS YEO RIEULSIOS - 0x9968: 0xC161, //HANGUL SYLLABLE SIOS YEO RIEULTHIEUTH - 0x9969: 0xC162, //HANGUL SYLLABLE SIOS YEO RIEULPHIEUPH - 0x996A: 0xC163, //HANGUL SYLLABLE SIOS YEO RIEULHIEUH - 0x996B: 0xC166, //HANGUL SYLLABLE SIOS YEO PIEUPSIOS - 0x996C: 0xC16A, //HANGUL SYLLABLE SIOS YEO CIEUC - 0x996D: 0xC16B, //HANGUL SYLLABLE SIOS YEO CHIEUCH - 0x996E: 0xC16C, //HANGUL SYLLABLE SIOS YEO KHIEUKH - 0x996F: 0xC16D, //HANGUL SYLLABLE SIOS YEO THIEUTH - 0x9970: 0xC16E, //HANGUL SYLLABLE SIOS YEO PHIEUPH - 0x9971: 0xC16F, //HANGUL SYLLABLE SIOS YEO HIEUH - 0x9972: 0xC171, //HANGUL SYLLABLE SIOS YE KIYEOK - 0x9973: 0xC172, //HANGUL SYLLABLE SIOS YE SSANGKIYEOK - 0x9974: 0xC173, //HANGUL SYLLABLE SIOS YE KIYEOKSIOS - 0x9975: 0xC175, //HANGUL SYLLABLE SIOS YE NIEUNCIEUC - 0x9976: 0xC176, //HANGUL SYLLABLE SIOS YE NIEUNHIEUH - 0x9977: 0xC177, //HANGUL SYLLABLE SIOS YE TIKEUT - 0x9978: 0xC179, //HANGUL SYLLABLE SIOS YE RIEULKIYEOK - 0x9979: 0xC17A, //HANGUL SYLLABLE SIOS YE RIEULMIEUM - 0x997A: 0xC17B, //HANGUL SYLLABLE SIOS YE RIEULPIEUP - 0x9981: 0xC17C, //HANGUL SYLLABLE SIOS YE RIEULSIOS - 0x9982: 0xC17D, //HANGUL SYLLABLE SIOS YE RIEULTHIEUTH - 0x9983: 0xC17E, //HANGUL SYLLABLE SIOS YE RIEULPHIEUPH - 0x9984: 0xC17F, //HANGUL SYLLABLE SIOS YE RIEULHIEUH - 0x9985: 0xC180, //HANGUL SYLLABLE SIOS YE MIEUM - 0x9986: 0xC181, //HANGUL SYLLABLE SIOS YE PIEUP - 0x9987: 0xC182, //HANGUL SYLLABLE SIOS YE PIEUPSIOS - 0x9988: 0xC183, //HANGUL SYLLABLE SIOS YE SIOS - 0x9989: 0xC184, //HANGUL SYLLABLE SIOS YE SSANGSIOS - 0x998A: 0xC186, //HANGUL SYLLABLE SIOS YE CIEUC - 0x998B: 0xC187, //HANGUL SYLLABLE SIOS YE CHIEUCH - 0x998C: 0xC188, //HANGUL SYLLABLE SIOS YE KHIEUKH - 0x998D: 0xC189, //HANGUL SYLLABLE SIOS YE THIEUTH - 0x998E: 0xC18A, //HANGUL SYLLABLE SIOS YE PHIEUPH - 0x998F: 0xC18B, //HANGUL SYLLABLE SIOS YE HIEUH - 0x9990: 0xC18F, //HANGUL SYLLABLE SIOS O KIYEOKSIOS - 0x9991: 0xC191, //HANGUL SYLLABLE SIOS O NIEUNCIEUC - 0x9992: 0xC192, //HANGUL SYLLABLE SIOS O NIEUNHIEUH - 0x9993: 0xC193, //HANGUL SYLLABLE SIOS O TIKEUT - 0x9994: 0xC195, //HANGUL SYLLABLE SIOS O RIEULKIYEOK - 0x9995: 0xC197, //HANGUL SYLLABLE SIOS O RIEULPIEUP - 0x9996: 0xC198, //HANGUL SYLLABLE SIOS O RIEULSIOS - 0x9997: 0xC199, //HANGUL SYLLABLE SIOS O RIEULTHIEUTH - 0x9998: 0xC19A, //HANGUL SYLLABLE SIOS O RIEULPHIEUPH - 0x9999: 0xC19B, //HANGUL SYLLABLE SIOS O RIEULHIEUH - 0x999A: 0xC19E, //HANGUL SYLLABLE SIOS O PIEUPSIOS - 0x999B: 0xC1A0, //HANGUL SYLLABLE SIOS O SSANGSIOS - 0x999C: 0xC1A2, //HANGUL SYLLABLE SIOS O CIEUC - 0x999D: 0xC1A3, //HANGUL SYLLABLE SIOS O CHIEUCH - 0x999E: 0xC1A4, //HANGUL SYLLABLE SIOS O KHIEUKH - 0x999F: 0xC1A6, //HANGUL SYLLABLE SIOS O PHIEUPH - 0x99A0: 0xC1A7, //HANGUL SYLLABLE SIOS O HIEUH - 0x99A1: 0xC1AA, //HANGUL SYLLABLE SIOS WA SSANGKIYEOK - 0x99A2: 0xC1AB, //HANGUL SYLLABLE SIOS WA KIYEOKSIOS - 0x99A3: 0xC1AD, //HANGUL SYLLABLE SIOS WA NIEUNCIEUC - 0x99A4: 0xC1AE, //HANGUL SYLLABLE SIOS WA NIEUNHIEUH - 0x99A5: 0xC1AF, //HANGUL SYLLABLE SIOS WA TIKEUT - 0x99A6: 0xC1B1, //HANGUL SYLLABLE SIOS WA RIEULKIYEOK - 0x99A7: 0xC1B2, //HANGUL SYLLABLE SIOS WA RIEULMIEUM - 0x99A8: 0xC1B3, //HANGUL SYLLABLE SIOS WA RIEULPIEUP - 0x99A9: 0xC1B4, //HANGUL SYLLABLE SIOS WA RIEULSIOS - 0x99AA: 0xC1B5, //HANGUL SYLLABLE SIOS WA RIEULTHIEUTH - 0x99AB: 0xC1B6, //HANGUL SYLLABLE SIOS WA RIEULPHIEUPH - 0x99AC: 0xC1B7, //HANGUL SYLLABLE SIOS WA RIEULHIEUH - 0x99AD: 0xC1B8, //HANGUL SYLLABLE SIOS WA MIEUM - 0x99AE: 0xC1B9, //HANGUL SYLLABLE SIOS WA PIEUP - 0x99AF: 0xC1BA, //HANGUL SYLLABLE SIOS WA PIEUPSIOS - 0x99B0: 0xC1BB, //HANGUL SYLLABLE SIOS WA SIOS - 0x99B1: 0xC1BC, //HANGUL SYLLABLE SIOS WA SSANGSIOS - 0x99B2: 0xC1BE, //HANGUL SYLLABLE SIOS WA CIEUC - 0x99B3: 0xC1BF, //HANGUL SYLLABLE SIOS WA CHIEUCH - 0x99B4: 0xC1C0, //HANGUL SYLLABLE SIOS WA KHIEUKH - 0x99B5: 0xC1C1, //HANGUL SYLLABLE SIOS WA THIEUTH - 0x99B6: 0xC1C2, //HANGUL SYLLABLE SIOS WA PHIEUPH - 0x99B7: 0xC1C3, //HANGUL SYLLABLE SIOS WA HIEUH - 0x99B8: 0xC1C5, //HANGUL SYLLABLE SIOS WAE KIYEOK - 0x99B9: 0xC1C6, //HANGUL SYLLABLE SIOS WAE SSANGKIYEOK - 0x99BA: 0xC1C7, //HANGUL SYLLABLE SIOS WAE KIYEOKSIOS - 0x99BB: 0xC1C9, //HANGUL SYLLABLE SIOS WAE NIEUNCIEUC - 0x99BC: 0xC1CA, //HANGUL SYLLABLE SIOS WAE NIEUNHIEUH - 0x99BD: 0xC1CB, //HANGUL SYLLABLE SIOS WAE TIKEUT - 0x99BE: 0xC1CD, //HANGUL SYLLABLE SIOS WAE RIEULKIYEOK - 0x99BF: 0xC1CE, //HANGUL SYLLABLE SIOS WAE RIEULMIEUM - 0x99C0: 0xC1CF, //HANGUL SYLLABLE SIOS WAE RIEULPIEUP - 0x99C1: 0xC1D0, //HANGUL SYLLABLE SIOS WAE RIEULSIOS - 0x99C2: 0xC1D1, //HANGUL SYLLABLE SIOS WAE RIEULTHIEUTH - 0x99C3: 0xC1D2, //HANGUL SYLLABLE SIOS WAE RIEULPHIEUPH - 0x99C4: 0xC1D3, //HANGUL SYLLABLE SIOS WAE RIEULHIEUH - 0x99C5: 0xC1D5, //HANGUL SYLLABLE SIOS WAE PIEUP - 0x99C6: 0xC1D6, //HANGUL SYLLABLE SIOS WAE PIEUPSIOS - 0x99C7: 0xC1D9, //HANGUL SYLLABLE SIOS WAE IEUNG - 0x99C8: 0xC1DA, //HANGUL SYLLABLE SIOS WAE CIEUC - 0x99C9: 0xC1DB, //HANGUL SYLLABLE SIOS WAE CHIEUCH - 0x99CA: 0xC1DC, //HANGUL SYLLABLE SIOS WAE KHIEUKH - 0x99CB: 0xC1DD, //HANGUL SYLLABLE SIOS WAE THIEUTH - 0x99CC: 0xC1DE, //HANGUL SYLLABLE SIOS WAE PHIEUPH - 0x99CD: 0xC1DF, //HANGUL SYLLABLE SIOS WAE HIEUH - 0x99CE: 0xC1E1, //HANGUL SYLLABLE SIOS OE KIYEOK - 0x99CF: 0xC1E2, //HANGUL SYLLABLE SIOS OE SSANGKIYEOK - 0x99D0: 0xC1E3, //HANGUL SYLLABLE SIOS OE KIYEOKSIOS - 0x99D1: 0xC1E5, //HANGUL SYLLABLE SIOS OE NIEUNCIEUC - 0x99D2: 0xC1E6, //HANGUL SYLLABLE SIOS OE NIEUNHIEUH - 0x99D3: 0xC1E7, //HANGUL SYLLABLE SIOS OE TIKEUT - 0x99D4: 0xC1E9, //HANGUL SYLLABLE SIOS OE RIEULKIYEOK - 0x99D5: 0xC1EA, //HANGUL SYLLABLE SIOS OE RIEULMIEUM - 0x99D6: 0xC1EB, //HANGUL SYLLABLE SIOS OE RIEULPIEUP - 0x99D7: 0xC1EC, //HANGUL SYLLABLE SIOS OE RIEULSIOS - 0x99D8: 0xC1ED, //HANGUL SYLLABLE SIOS OE RIEULTHIEUTH - 0x99D9: 0xC1EE, //HANGUL SYLLABLE SIOS OE RIEULPHIEUPH - 0x99DA: 0xC1EF, //HANGUL SYLLABLE SIOS OE RIEULHIEUH - 0x99DB: 0xC1F2, //HANGUL SYLLABLE SIOS OE PIEUPSIOS - 0x99DC: 0xC1F4, //HANGUL SYLLABLE SIOS OE SSANGSIOS - 0x99DD: 0xC1F5, //HANGUL SYLLABLE SIOS OE IEUNG - 0x99DE: 0xC1F6, //HANGUL SYLLABLE SIOS OE CIEUC - 0x99DF: 0xC1F7, //HANGUL SYLLABLE SIOS OE CHIEUCH - 0x99E0: 0xC1F8, //HANGUL SYLLABLE SIOS OE KHIEUKH - 0x99E1: 0xC1F9, //HANGUL SYLLABLE SIOS OE THIEUTH - 0x99E2: 0xC1FA, //HANGUL SYLLABLE SIOS OE PHIEUPH - 0x99E3: 0xC1FB, //HANGUL SYLLABLE SIOS OE HIEUH - 0x99E4: 0xC1FE, //HANGUL SYLLABLE SIOS YO SSANGKIYEOK - 0x99E5: 0xC1FF, //HANGUL SYLLABLE SIOS YO KIYEOKSIOS - 0x99E6: 0xC201, //HANGUL SYLLABLE SIOS YO NIEUNCIEUC - 0x99E7: 0xC202, //HANGUL SYLLABLE SIOS YO NIEUNHIEUH - 0x99E8: 0xC203, //HANGUL SYLLABLE SIOS YO TIKEUT - 0x99E9: 0xC205, //HANGUL SYLLABLE SIOS YO RIEULKIYEOK - 0x99EA: 0xC206, //HANGUL SYLLABLE SIOS YO RIEULMIEUM - 0x99EB: 0xC207, //HANGUL SYLLABLE SIOS YO RIEULPIEUP - 0x99EC: 0xC208, //HANGUL SYLLABLE SIOS YO RIEULSIOS - 0x99ED: 0xC209, //HANGUL SYLLABLE SIOS YO RIEULTHIEUTH - 0x99EE: 0xC20A, //HANGUL SYLLABLE SIOS YO RIEULPHIEUPH - 0x99EF: 0xC20B, //HANGUL SYLLABLE SIOS YO RIEULHIEUH - 0x99F0: 0xC20E, //HANGUL SYLLABLE SIOS YO PIEUPSIOS - 0x99F1: 0xC210, //HANGUL SYLLABLE SIOS YO SSANGSIOS - 0x99F2: 0xC212, //HANGUL SYLLABLE SIOS YO CIEUC - 0x99F3: 0xC213, //HANGUL SYLLABLE SIOS YO CHIEUCH - 0x99F4: 0xC214, //HANGUL SYLLABLE SIOS YO KHIEUKH - 0x99F5: 0xC215, //HANGUL SYLLABLE SIOS YO THIEUTH - 0x99F6: 0xC216, //HANGUL SYLLABLE SIOS YO PHIEUPH - 0x99F7: 0xC217, //HANGUL SYLLABLE SIOS YO HIEUH - 0x99F8: 0xC21A, //HANGUL SYLLABLE SIOS U SSANGKIYEOK - 0x99F9: 0xC21B, //HANGUL SYLLABLE SIOS U KIYEOKSIOS - 0x99FA: 0xC21D, //HANGUL SYLLABLE SIOS U NIEUNCIEUC - 0x99FB: 0xC21E, //HANGUL SYLLABLE SIOS U NIEUNHIEUH - 0x99FC: 0xC221, //HANGUL SYLLABLE SIOS U RIEULKIYEOK - 0x99FD: 0xC222, //HANGUL SYLLABLE SIOS U RIEULMIEUM - 0x99FE: 0xC223, //HANGUL SYLLABLE SIOS U RIEULPIEUP - 0x9A41: 0xC224, //HANGUL SYLLABLE SIOS U RIEULSIOS - 0x9A42: 0xC225, //HANGUL SYLLABLE SIOS U RIEULTHIEUTH - 0x9A43: 0xC226, //HANGUL SYLLABLE SIOS U RIEULPHIEUPH - 0x9A44: 0xC227, //HANGUL SYLLABLE SIOS U RIEULHIEUH - 0x9A45: 0xC22A, //HANGUL SYLLABLE SIOS U PIEUPSIOS - 0x9A46: 0xC22C, //HANGUL SYLLABLE SIOS U SSANGSIOS - 0x9A47: 0xC22E, //HANGUL SYLLABLE SIOS U CIEUC - 0x9A48: 0xC230, //HANGUL SYLLABLE SIOS U KHIEUKH - 0x9A49: 0xC233, //HANGUL SYLLABLE SIOS U HIEUH - 0x9A4A: 0xC235, //HANGUL SYLLABLE SIOS WEO KIYEOK - 0x9A4B: 0xC236, //HANGUL SYLLABLE SIOS WEO SSANGKIYEOK - 0x9A4C: 0xC237, //HANGUL SYLLABLE SIOS WEO KIYEOKSIOS - 0x9A4D: 0xC238, //HANGUL SYLLABLE SIOS WEO NIEUN - 0x9A4E: 0xC239, //HANGUL SYLLABLE SIOS WEO NIEUNCIEUC - 0x9A4F: 0xC23A, //HANGUL SYLLABLE SIOS WEO NIEUNHIEUH - 0x9A50: 0xC23B, //HANGUL SYLLABLE SIOS WEO TIKEUT - 0x9A51: 0xC23C, //HANGUL SYLLABLE SIOS WEO RIEUL - 0x9A52: 0xC23D, //HANGUL SYLLABLE SIOS WEO RIEULKIYEOK - 0x9A53: 0xC23E, //HANGUL SYLLABLE SIOS WEO RIEULMIEUM - 0x9A54: 0xC23F, //HANGUL SYLLABLE SIOS WEO RIEULPIEUP - 0x9A55: 0xC240, //HANGUL SYLLABLE SIOS WEO RIEULSIOS - 0x9A56: 0xC241, //HANGUL SYLLABLE SIOS WEO RIEULTHIEUTH - 0x9A57: 0xC242, //HANGUL SYLLABLE SIOS WEO RIEULPHIEUPH - 0x9A58: 0xC243, //HANGUL SYLLABLE SIOS WEO RIEULHIEUH - 0x9A59: 0xC244, //HANGUL SYLLABLE SIOS WEO MIEUM - 0x9A5A: 0xC245, //HANGUL SYLLABLE SIOS WEO PIEUP - 0x9A61: 0xC246, //HANGUL SYLLABLE SIOS WEO PIEUPSIOS - 0x9A62: 0xC247, //HANGUL SYLLABLE SIOS WEO SIOS - 0x9A63: 0xC249, //HANGUL SYLLABLE SIOS WEO IEUNG - 0x9A64: 0xC24A, //HANGUL SYLLABLE SIOS WEO CIEUC - 0x9A65: 0xC24B, //HANGUL SYLLABLE SIOS WEO CHIEUCH - 0x9A66: 0xC24C, //HANGUL SYLLABLE SIOS WEO KHIEUKH - 0x9A67: 0xC24D, //HANGUL SYLLABLE SIOS WEO THIEUTH - 0x9A68: 0xC24E, //HANGUL SYLLABLE SIOS WEO PHIEUPH - 0x9A69: 0xC24F, //HANGUL SYLLABLE SIOS WEO HIEUH - 0x9A6A: 0xC252, //HANGUL SYLLABLE SIOS WE SSANGKIYEOK - 0x9A6B: 0xC253, //HANGUL SYLLABLE SIOS WE KIYEOKSIOS - 0x9A6C: 0xC255, //HANGUL SYLLABLE SIOS WE NIEUNCIEUC - 0x9A6D: 0xC256, //HANGUL SYLLABLE SIOS WE NIEUNHIEUH - 0x9A6E: 0xC257, //HANGUL SYLLABLE SIOS WE TIKEUT - 0x9A6F: 0xC259, //HANGUL SYLLABLE SIOS WE RIEULKIYEOK - 0x9A70: 0xC25A, //HANGUL SYLLABLE SIOS WE RIEULMIEUM - 0x9A71: 0xC25B, //HANGUL SYLLABLE SIOS WE RIEULPIEUP - 0x9A72: 0xC25C, //HANGUL SYLLABLE SIOS WE RIEULSIOS - 0x9A73: 0xC25D, //HANGUL SYLLABLE SIOS WE RIEULTHIEUTH - 0x9A74: 0xC25E, //HANGUL SYLLABLE SIOS WE RIEULPHIEUPH - 0x9A75: 0xC25F, //HANGUL SYLLABLE SIOS WE RIEULHIEUH - 0x9A76: 0xC261, //HANGUL SYLLABLE SIOS WE PIEUP - 0x9A77: 0xC262, //HANGUL SYLLABLE SIOS WE PIEUPSIOS - 0x9A78: 0xC263, //HANGUL SYLLABLE SIOS WE SIOS - 0x9A79: 0xC264, //HANGUL SYLLABLE SIOS WE SSANGSIOS - 0x9A7A: 0xC266, //HANGUL SYLLABLE SIOS WE CIEUC - 0x9A81: 0xC267, //HANGUL SYLLABLE SIOS WE CHIEUCH - 0x9A82: 0xC268, //HANGUL SYLLABLE SIOS WE KHIEUKH - 0x9A83: 0xC269, //HANGUL SYLLABLE SIOS WE THIEUTH - 0x9A84: 0xC26A, //HANGUL SYLLABLE SIOS WE PHIEUPH - 0x9A85: 0xC26B, //HANGUL SYLLABLE SIOS WE HIEUH - 0x9A86: 0xC26E, //HANGUL SYLLABLE SIOS WI SSANGKIYEOK - 0x9A87: 0xC26F, //HANGUL SYLLABLE SIOS WI KIYEOKSIOS - 0x9A88: 0xC271, //HANGUL SYLLABLE SIOS WI NIEUNCIEUC - 0x9A89: 0xC272, //HANGUL SYLLABLE SIOS WI NIEUNHIEUH - 0x9A8A: 0xC273, //HANGUL SYLLABLE SIOS WI TIKEUT - 0x9A8B: 0xC275, //HANGUL SYLLABLE SIOS WI RIEULKIYEOK - 0x9A8C: 0xC276, //HANGUL SYLLABLE SIOS WI RIEULMIEUM - 0x9A8D: 0xC277, //HANGUL SYLLABLE SIOS WI RIEULPIEUP - 0x9A8E: 0xC278, //HANGUL SYLLABLE SIOS WI RIEULSIOS - 0x9A8F: 0xC279, //HANGUL SYLLABLE SIOS WI RIEULTHIEUTH - 0x9A90: 0xC27A, //HANGUL SYLLABLE SIOS WI RIEULPHIEUPH - 0x9A91: 0xC27B, //HANGUL SYLLABLE SIOS WI RIEULHIEUH - 0x9A92: 0xC27E, //HANGUL SYLLABLE SIOS WI PIEUPSIOS - 0x9A93: 0xC280, //HANGUL SYLLABLE SIOS WI SSANGSIOS - 0x9A94: 0xC282, //HANGUL SYLLABLE SIOS WI CIEUC - 0x9A95: 0xC283, //HANGUL SYLLABLE SIOS WI CHIEUCH - 0x9A96: 0xC284, //HANGUL SYLLABLE SIOS WI KHIEUKH - 0x9A97: 0xC285, //HANGUL SYLLABLE SIOS WI THIEUTH - 0x9A98: 0xC286, //HANGUL SYLLABLE SIOS WI PHIEUPH - 0x9A99: 0xC287, //HANGUL SYLLABLE SIOS WI HIEUH - 0x9A9A: 0xC28A, //HANGUL SYLLABLE SIOS YU SSANGKIYEOK - 0x9A9B: 0xC28B, //HANGUL SYLLABLE SIOS YU KIYEOKSIOS - 0x9A9C: 0xC28C, //HANGUL SYLLABLE SIOS YU NIEUN - 0x9A9D: 0xC28D, //HANGUL SYLLABLE SIOS YU NIEUNCIEUC - 0x9A9E: 0xC28E, //HANGUL SYLLABLE SIOS YU NIEUNHIEUH - 0x9A9F: 0xC28F, //HANGUL SYLLABLE SIOS YU TIKEUT - 0x9AA0: 0xC291, //HANGUL SYLLABLE SIOS YU RIEULKIYEOK - 0x9AA1: 0xC292, //HANGUL SYLLABLE SIOS YU RIEULMIEUM - 0x9AA2: 0xC293, //HANGUL SYLLABLE SIOS YU RIEULPIEUP - 0x9AA3: 0xC294, //HANGUL SYLLABLE SIOS YU RIEULSIOS - 0x9AA4: 0xC295, //HANGUL SYLLABLE SIOS YU RIEULTHIEUTH - 0x9AA5: 0xC296, //HANGUL SYLLABLE SIOS YU RIEULPHIEUPH - 0x9AA6: 0xC297, //HANGUL SYLLABLE SIOS YU RIEULHIEUH - 0x9AA7: 0xC299, //HANGUL SYLLABLE SIOS YU PIEUP - 0x9AA8: 0xC29A, //HANGUL SYLLABLE SIOS YU PIEUPSIOS - 0x9AA9: 0xC29C, //HANGUL SYLLABLE SIOS YU SSANGSIOS - 0x9AAA: 0xC29E, //HANGUL SYLLABLE SIOS YU CIEUC - 0x9AAB: 0xC29F, //HANGUL SYLLABLE SIOS YU CHIEUCH - 0x9AAC: 0xC2A0, //HANGUL SYLLABLE SIOS YU KHIEUKH - 0x9AAD: 0xC2A1, //HANGUL SYLLABLE SIOS YU THIEUTH - 0x9AAE: 0xC2A2, //HANGUL SYLLABLE SIOS YU PHIEUPH - 0x9AAF: 0xC2A3, //HANGUL SYLLABLE SIOS YU HIEUH - 0x9AB0: 0xC2A6, //HANGUL SYLLABLE SIOS EU SSANGKIYEOK - 0x9AB1: 0xC2A7, //HANGUL SYLLABLE SIOS EU KIYEOKSIOS - 0x9AB2: 0xC2A9, //HANGUL SYLLABLE SIOS EU NIEUNCIEUC - 0x9AB3: 0xC2AA, //HANGUL SYLLABLE SIOS EU NIEUNHIEUH - 0x9AB4: 0xC2AB, //HANGUL SYLLABLE SIOS EU TIKEUT - 0x9AB5: 0xC2AE, //HANGUL SYLLABLE SIOS EU RIEULMIEUM - 0x9AB6: 0xC2AF, //HANGUL SYLLABLE SIOS EU RIEULPIEUP - 0x9AB7: 0xC2B0, //HANGUL SYLLABLE SIOS EU RIEULSIOS - 0x9AB8: 0xC2B1, //HANGUL SYLLABLE SIOS EU RIEULTHIEUTH - 0x9AB9: 0xC2B2, //HANGUL SYLLABLE SIOS EU RIEULPHIEUPH - 0x9ABA: 0xC2B3, //HANGUL SYLLABLE SIOS EU RIEULHIEUH - 0x9ABB: 0xC2B6, //HANGUL SYLLABLE SIOS EU PIEUPSIOS - 0x9ABC: 0xC2B8, //HANGUL SYLLABLE SIOS EU SSANGSIOS - 0x9ABD: 0xC2BA, //HANGUL SYLLABLE SIOS EU CIEUC - 0x9ABE: 0xC2BB, //HANGUL SYLLABLE SIOS EU CHIEUCH - 0x9ABF: 0xC2BC, //HANGUL SYLLABLE SIOS EU KHIEUKH - 0x9AC0: 0xC2BD, //HANGUL SYLLABLE SIOS EU THIEUTH - 0x9AC1: 0xC2BE, //HANGUL SYLLABLE SIOS EU PHIEUPH - 0x9AC2: 0xC2BF, //HANGUL SYLLABLE SIOS EU HIEUH - 0x9AC3: 0xC2C0, //HANGUL SYLLABLE SIOS YI - 0x9AC4: 0xC2C1, //HANGUL SYLLABLE SIOS YI KIYEOK - 0x9AC5: 0xC2C2, //HANGUL SYLLABLE SIOS YI SSANGKIYEOK - 0x9AC6: 0xC2C3, //HANGUL SYLLABLE SIOS YI KIYEOKSIOS - 0x9AC7: 0xC2C4, //HANGUL SYLLABLE SIOS YI NIEUN - 0x9AC8: 0xC2C5, //HANGUL SYLLABLE SIOS YI NIEUNCIEUC - 0x9AC9: 0xC2C6, //HANGUL SYLLABLE SIOS YI NIEUNHIEUH - 0x9ACA: 0xC2C7, //HANGUL SYLLABLE SIOS YI TIKEUT - 0x9ACB: 0xC2C8, //HANGUL SYLLABLE SIOS YI RIEUL - 0x9ACC: 0xC2C9, //HANGUL SYLLABLE SIOS YI RIEULKIYEOK - 0x9ACD: 0xC2CA, //HANGUL SYLLABLE SIOS YI RIEULMIEUM - 0x9ACE: 0xC2CB, //HANGUL SYLLABLE SIOS YI RIEULPIEUP - 0x9ACF: 0xC2CC, //HANGUL SYLLABLE SIOS YI RIEULSIOS - 0x9AD0: 0xC2CD, //HANGUL SYLLABLE SIOS YI RIEULTHIEUTH - 0x9AD1: 0xC2CE, //HANGUL SYLLABLE SIOS YI RIEULPHIEUPH - 0x9AD2: 0xC2CF, //HANGUL SYLLABLE SIOS YI RIEULHIEUH - 0x9AD3: 0xC2D0, //HANGUL SYLLABLE SIOS YI MIEUM - 0x9AD4: 0xC2D1, //HANGUL SYLLABLE SIOS YI PIEUP - 0x9AD5: 0xC2D2, //HANGUL SYLLABLE SIOS YI PIEUPSIOS - 0x9AD6: 0xC2D3, //HANGUL SYLLABLE SIOS YI SIOS - 0x9AD7: 0xC2D4, //HANGUL SYLLABLE SIOS YI SSANGSIOS - 0x9AD8: 0xC2D5, //HANGUL SYLLABLE SIOS YI IEUNG - 0x9AD9: 0xC2D6, //HANGUL SYLLABLE SIOS YI CIEUC - 0x9ADA: 0xC2D7, //HANGUL SYLLABLE SIOS YI CHIEUCH - 0x9ADB: 0xC2D8, //HANGUL SYLLABLE SIOS YI KHIEUKH - 0x9ADC: 0xC2D9, //HANGUL SYLLABLE SIOS YI THIEUTH - 0x9ADD: 0xC2DA, //HANGUL SYLLABLE SIOS YI PHIEUPH - 0x9ADE: 0xC2DB, //HANGUL SYLLABLE SIOS YI HIEUH - 0x9ADF: 0xC2DE, //HANGUL SYLLABLE SIOS I SSANGKIYEOK - 0x9AE0: 0xC2DF, //HANGUL SYLLABLE SIOS I KIYEOKSIOS - 0x9AE1: 0xC2E1, //HANGUL SYLLABLE SIOS I NIEUNCIEUC - 0x9AE2: 0xC2E2, //HANGUL SYLLABLE SIOS I NIEUNHIEUH - 0x9AE3: 0xC2E5, //HANGUL SYLLABLE SIOS I RIEULKIYEOK - 0x9AE4: 0xC2E6, //HANGUL SYLLABLE SIOS I RIEULMIEUM - 0x9AE5: 0xC2E7, //HANGUL SYLLABLE SIOS I RIEULPIEUP - 0x9AE6: 0xC2E8, //HANGUL SYLLABLE SIOS I RIEULSIOS - 0x9AE7: 0xC2E9, //HANGUL SYLLABLE SIOS I RIEULTHIEUTH - 0x9AE8: 0xC2EA, //HANGUL SYLLABLE SIOS I RIEULPHIEUPH - 0x9AE9: 0xC2EE, //HANGUL SYLLABLE SIOS I PIEUPSIOS - 0x9AEA: 0xC2F0, //HANGUL SYLLABLE SIOS I SSANGSIOS - 0x9AEB: 0xC2F2, //HANGUL SYLLABLE SIOS I CIEUC - 0x9AEC: 0xC2F3, //HANGUL SYLLABLE SIOS I CHIEUCH - 0x9AED: 0xC2F4, //HANGUL SYLLABLE SIOS I KHIEUKH - 0x9AEE: 0xC2F5, //HANGUL SYLLABLE SIOS I THIEUTH - 0x9AEF: 0xC2F7, //HANGUL SYLLABLE SIOS I HIEUH - 0x9AF0: 0xC2FA, //HANGUL SYLLABLE SSANGSIOS A SSANGKIYEOK - 0x9AF1: 0xC2FD, //HANGUL SYLLABLE SSANGSIOS A NIEUNCIEUC - 0x9AF2: 0xC2FE, //HANGUL SYLLABLE SSANGSIOS A NIEUNHIEUH - 0x9AF3: 0xC2FF, //HANGUL SYLLABLE SSANGSIOS A TIKEUT - 0x9AF4: 0xC301, //HANGUL SYLLABLE SSANGSIOS A RIEULKIYEOK - 0x9AF5: 0xC302, //HANGUL SYLLABLE SSANGSIOS A RIEULMIEUM - 0x9AF6: 0xC303, //HANGUL SYLLABLE SSANGSIOS A RIEULPIEUP - 0x9AF7: 0xC304, //HANGUL SYLLABLE SSANGSIOS A RIEULSIOS - 0x9AF8: 0xC305, //HANGUL SYLLABLE SSANGSIOS A RIEULTHIEUTH - 0x9AF9: 0xC306, //HANGUL SYLLABLE SSANGSIOS A RIEULPHIEUPH - 0x9AFA: 0xC307, //HANGUL SYLLABLE SSANGSIOS A RIEULHIEUH - 0x9AFB: 0xC30A, //HANGUL SYLLABLE SSANGSIOS A PIEUPSIOS - 0x9AFC: 0xC30B, //HANGUL SYLLABLE SSANGSIOS A SIOS - 0x9AFD: 0xC30E, //HANGUL SYLLABLE SSANGSIOS A CIEUC - 0x9AFE: 0xC30F, //HANGUL SYLLABLE SSANGSIOS A CHIEUCH - 0x9B41: 0xC310, //HANGUL SYLLABLE SSANGSIOS A KHIEUKH - 0x9B42: 0xC311, //HANGUL SYLLABLE SSANGSIOS A THIEUTH - 0x9B43: 0xC312, //HANGUL SYLLABLE SSANGSIOS A PHIEUPH - 0x9B44: 0xC316, //HANGUL SYLLABLE SSANGSIOS AE SSANGKIYEOK - 0x9B45: 0xC317, //HANGUL SYLLABLE SSANGSIOS AE KIYEOKSIOS - 0x9B46: 0xC319, //HANGUL SYLLABLE SSANGSIOS AE NIEUNCIEUC - 0x9B47: 0xC31A, //HANGUL SYLLABLE SSANGSIOS AE NIEUNHIEUH - 0x9B48: 0xC31B, //HANGUL SYLLABLE SSANGSIOS AE TIKEUT - 0x9B49: 0xC31D, //HANGUL SYLLABLE SSANGSIOS AE RIEULKIYEOK - 0x9B4A: 0xC31E, //HANGUL SYLLABLE SSANGSIOS AE RIEULMIEUM - 0x9B4B: 0xC31F, //HANGUL SYLLABLE SSANGSIOS AE RIEULPIEUP - 0x9B4C: 0xC320, //HANGUL SYLLABLE SSANGSIOS AE RIEULSIOS - 0x9B4D: 0xC321, //HANGUL SYLLABLE SSANGSIOS AE RIEULTHIEUTH - 0x9B4E: 0xC322, //HANGUL SYLLABLE SSANGSIOS AE RIEULPHIEUPH - 0x9B4F: 0xC323, //HANGUL SYLLABLE SSANGSIOS AE RIEULHIEUH - 0x9B50: 0xC326, //HANGUL SYLLABLE SSANGSIOS AE PIEUPSIOS - 0x9B51: 0xC327, //HANGUL SYLLABLE SSANGSIOS AE SIOS - 0x9B52: 0xC32A, //HANGUL SYLLABLE SSANGSIOS AE CIEUC - 0x9B53: 0xC32B, //HANGUL SYLLABLE SSANGSIOS AE CHIEUCH - 0x9B54: 0xC32C, //HANGUL SYLLABLE SSANGSIOS AE KHIEUKH - 0x9B55: 0xC32D, //HANGUL SYLLABLE SSANGSIOS AE THIEUTH - 0x9B56: 0xC32E, //HANGUL SYLLABLE SSANGSIOS AE PHIEUPH - 0x9B57: 0xC32F, //HANGUL SYLLABLE SSANGSIOS AE HIEUH - 0x9B58: 0xC330, //HANGUL SYLLABLE SSANGSIOS YA - 0x9B59: 0xC331, //HANGUL SYLLABLE SSANGSIOS YA KIYEOK - 0x9B5A: 0xC332, //HANGUL SYLLABLE SSANGSIOS YA SSANGKIYEOK - 0x9B61: 0xC333, //HANGUL SYLLABLE SSANGSIOS YA KIYEOKSIOS - 0x9B62: 0xC334, //HANGUL SYLLABLE SSANGSIOS YA NIEUN - 0x9B63: 0xC335, //HANGUL SYLLABLE SSANGSIOS YA NIEUNCIEUC - 0x9B64: 0xC336, //HANGUL SYLLABLE SSANGSIOS YA NIEUNHIEUH - 0x9B65: 0xC337, //HANGUL SYLLABLE SSANGSIOS YA TIKEUT - 0x9B66: 0xC338, //HANGUL SYLLABLE SSANGSIOS YA RIEUL - 0x9B67: 0xC339, //HANGUL SYLLABLE SSANGSIOS YA RIEULKIYEOK - 0x9B68: 0xC33A, //HANGUL SYLLABLE SSANGSIOS YA RIEULMIEUM - 0x9B69: 0xC33B, //HANGUL SYLLABLE SSANGSIOS YA RIEULPIEUP - 0x9B6A: 0xC33C, //HANGUL SYLLABLE SSANGSIOS YA RIEULSIOS - 0x9B6B: 0xC33D, //HANGUL SYLLABLE SSANGSIOS YA RIEULTHIEUTH - 0x9B6C: 0xC33E, //HANGUL SYLLABLE SSANGSIOS YA RIEULPHIEUPH - 0x9B6D: 0xC33F, //HANGUL SYLLABLE SSANGSIOS YA RIEULHIEUH - 0x9B6E: 0xC340, //HANGUL SYLLABLE SSANGSIOS YA MIEUM - 0x9B6F: 0xC341, //HANGUL SYLLABLE SSANGSIOS YA PIEUP - 0x9B70: 0xC342, //HANGUL SYLLABLE SSANGSIOS YA PIEUPSIOS - 0x9B71: 0xC343, //HANGUL SYLLABLE SSANGSIOS YA SIOS - 0x9B72: 0xC344, //HANGUL SYLLABLE SSANGSIOS YA SSANGSIOS - 0x9B73: 0xC346, //HANGUL SYLLABLE SSANGSIOS YA CIEUC - 0x9B74: 0xC347, //HANGUL SYLLABLE SSANGSIOS YA CHIEUCH - 0x9B75: 0xC348, //HANGUL SYLLABLE SSANGSIOS YA KHIEUKH - 0x9B76: 0xC349, //HANGUL SYLLABLE SSANGSIOS YA THIEUTH - 0x9B77: 0xC34A, //HANGUL SYLLABLE SSANGSIOS YA PHIEUPH - 0x9B78: 0xC34B, //HANGUL SYLLABLE SSANGSIOS YA HIEUH - 0x9B79: 0xC34C, //HANGUL SYLLABLE SSANGSIOS YAE - 0x9B7A: 0xC34D, //HANGUL SYLLABLE SSANGSIOS YAE KIYEOK - 0x9B81: 0xC34E, //HANGUL SYLLABLE SSANGSIOS YAE SSANGKIYEOK - 0x9B82: 0xC34F, //HANGUL SYLLABLE SSANGSIOS YAE KIYEOKSIOS - 0x9B83: 0xC350, //HANGUL SYLLABLE SSANGSIOS YAE NIEUN - 0x9B84: 0xC351, //HANGUL SYLLABLE SSANGSIOS YAE NIEUNCIEUC - 0x9B85: 0xC352, //HANGUL SYLLABLE SSANGSIOS YAE NIEUNHIEUH - 0x9B86: 0xC353, //HANGUL SYLLABLE SSANGSIOS YAE TIKEUT - 0x9B87: 0xC354, //HANGUL SYLLABLE SSANGSIOS YAE RIEUL - 0x9B88: 0xC355, //HANGUL SYLLABLE SSANGSIOS YAE RIEULKIYEOK - 0x9B89: 0xC356, //HANGUL SYLLABLE SSANGSIOS YAE RIEULMIEUM - 0x9B8A: 0xC357, //HANGUL SYLLABLE SSANGSIOS YAE RIEULPIEUP - 0x9B8B: 0xC358, //HANGUL SYLLABLE SSANGSIOS YAE RIEULSIOS - 0x9B8C: 0xC359, //HANGUL SYLLABLE SSANGSIOS YAE RIEULTHIEUTH - 0x9B8D: 0xC35A, //HANGUL SYLLABLE SSANGSIOS YAE RIEULPHIEUPH - 0x9B8E: 0xC35B, //HANGUL SYLLABLE SSANGSIOS YAE RIEULHIEUH - 0x9B8F: 0xC35C, //HANGUL SYLLABLE SSANGSIOS YAE MIEUM - 0x9B90: 0xC35D, //HANGUL SYLLABLE SSANGSIOS YAE PIEUP - 0x9B91: 0xC35E, //HANGUL SYLLABLE SSANGSIOS YAE PIEUPSIOS - 0x9B92: 0xC35F, //HANGUL SYLLABLE SSANGSIOS YAE SIOS - 0x9B93: 0xC360, //HANGUL SYLLABLE SSANGSIOS YAE SSANGSIOS - 0x9B94: 0xC361, //HANGUL SYLLABLE SSANGSIOS YAE IEUNG - 0x9B95: 0xC362, //HANGUL SYLLABLE SSANGSIOS YAE CIEUC - 0x9B96: 0xC363, //HANGUL SYLLABLE SSANGSIOS YAE CHIEUCH - 0x9B97: 0xC364, //HANGUL SYLLABLE SSANGSIOS YAE KHIEUKH - 0x9B98: 0xC365, //HANGUL SYLLABLE SSANGSIOS YAE THIEUTH - 0x9B99: 0xC366, //HANGUL SYLLABLE SSANGSIOS YAE PHIEUPH - 0x9B9A: 0xC367, //HANGUL SYLLABLE SSANGSIOS YAE HIEUH - 0x9B9B: 0xC36A, //HANGUL SYLLABLE SSANGSIOS EO SSANGKIYEOK - 0x9B9C: 0xC36B, //HANGUL SYLLABLE SSANGSIOS EO KIYEOKSIOS - 0x9B9D: 0xC36D, //HANGUL SYLLABLE SSANGSIOS EO NIEUNCIEUC - 0x9B9E: 0xC36E, //HANGUL SYLLABLE SSANGSIOS EO NIEUNHIEUH - 0x9B9F: 0xC36F, //HANGUL SYLLABLE SSANGSIOS EO TIKEUT - 0x9BA0: 0xC371, //HANGUL SYLLABLE SSANGSIOS EO RIEULKIYEOK - 0x9BA1: 0xC373, //HANGUL SYLLABLE SSANGSIOS EO RIEULPIEUP - 0x9BA2: 0xC374, //HANGUL SYLLABLE SSANGSIOS EO RIEULSIOS - 0x9BA3: 0xC375, //HANGUL SYLLABLE SSANGSIOS EO RIEULTHIEUTH - 0x9BA4: 0xC376, //HANGUL SYLLABLE SSANGSIOS EO RIEULPHIEUPH - 0x9BA5: 0xC377, //HANGUL SYLLABLE SSANGSIOS EO RIEULHIEUH - 0x9BA6: 0xC37A, //HANGUL SYLLABLE SSANGSIOS EO PIEUPSIOS - 0x9BA7: 0xC37B, //HANGUL SYLLABLE SSANGSIOS EO SIOS - 0x9BA8: 0xC37E, //HANGUL SYLLABLE SSANGSIOS EO CIEUC - 0x9BA9: 0xC37F, //HANGUL SYLLABLE SSANGSIOS EO CHIEUCH - 0x9BAA: 0xC380, //HANGUL SYLLABLE SSANGSIOS EO KHIEUKH - 0x9BAB: 0xC381, //HANGUL SYLLABLE SSANGSIOS EO THIEUTH - 0x9BAC: 0xC382, //HANGUL SYLLABLE SSANGSIOS EO PHIEUPH - 0x9BAD: 0xC383, //HANGUL SYLLABLE SSANGSIOS EO HIEUH - 0x9BAE: 0xC385, //HANGUL SYLLABLE SSANGSIOS E KIYEOK - 0x9BAF: 0xC386, //HANGUL SYLLABLE SSANGSIOS E SSANGKIYEOK - 0x9BB0: 0xC387, //HANGUL SYLLABLE SSANGSIOS E KIYEOKSIOS - 0x9BB1: 0xC389, //HANGUL SYLLABLE SSANGSIOS E NIEUNCIEUC - 0x9BB2: 0xC38A, //HANGUL SYLLABLE SSANGSIOS E NIEUNHIEUH - 0x9BB3: 0xC38B, //HANGUL SYLLABLE SSANGSIOS E TIKEUT - 0x9BB4: 0xC38D, //HANGUL SYLLABLE SSANGSIOS E RIEULKIYEOK - 0x9BB5: 0xC38E, //HANGUL SYLLABLE SSANGSIOS E RIEULMIEUM - 0x9BB6: 0xC38F, //HANGUL SYLLABLE SSANGSIOS E RIEULPIEUP - 0x9BB7: 0xC390, //HANGUL SYLLABLE SSANGSIOS E RIEULSIOS - 0x9BB8: 0xC391, //HANGUL SYLLABLE SSANGSIOS E RIEULTHIEUTH - 0x9BB9: 0xC392, //HANGUL SYLLABLE SSANGSIOS E RIEULPHIEUPH - 0x9BBA: 0xC393, //HANGUL SYLLABLE SSANGSIOS E RIEULHIEUH - 0x9BBB: 0xC394, //HANGUL SYLLABLE SSANGSIOS E MIEUM - 0x9BBC: 0xC395, //HANGUL SYLLABLE SSANGSIOS E PIEUP - 0x9BBD: 0xC396, //HANGUL SYLLABLE SSANGSIOS E PIEUPSIOS - 0x9BBE: 0xC397, //HANGUL SYLLABLE SSANGSIOS E SIOS - 0x9BBF: 0xC398, //HANGUL SYLLABLE SSANGSIOS E SSANGSIOS - 0x9BC0: 0xC399, //HANGUL SYLLABLE SSANGSIOS E IEUNG - 0x9BC1: 0xC39A, //HANGUL SYLLABLE SSANGSIOS E CIEUC - 0x9BC2: 0xC39B, //HANGUL SYLLABLE SSANGSIOS E CHIEUCH - 0x9BC3: 0xC39C, //HANGUL SYLLABLE SSANGSIOS E KHIEUKH - 0x9BC4: 0xC39D, //HANGUL SYLLABLE SSANGSIOS E THIEUTH - 0x9BC5: 0xC39E, //HANGUL SYLLABLE SSANGSIOS E PHIEUPH - 0x9BC6: 0xC39F, //HANGUL SYLLABLE SSANGSIOS E HIEUH - 0x9BC7: 0xC3A0, //HANGUL SYLLABLE SSANGSIOS YEO - 0x9BC8: 0xC3A1, //HANGUL SYLLABLE SSANGSIOS YEO KIYEOK - 0x9BC9: 0xC3A2, //HANGUL SYLLABLE SSANGSIOS YEO SSANGKIYEOK - 0x9BCA: 0xC3A3, //HANGUL SYLLABLE SSANGSIOS YEO KIYEOKSIOS - 0x9BCB: 0xC3A4, //HANGUL SYLLABLE SSANGSIOS YEO NIEUN - 0x9BCC: 0xC3A5, //HANGUL SYLLABLE SSANGSIOS YEO NIEUNCIEUC - 0x9BCD: 0xC3A6, //HANGUL SYLLABLE SSANGSIOS YEO NIEUNHIEUH - 0x9BCE: 0xC3A7, //HANGUL SYLLABLE SSANGSIOS YEO TIKEUT - 0x9BCF: 0xC3A8, //HANGUL SYLLABLE SSANGSIOS YEO RIEUL - 0x9BD0: 0xC3A9, //HANGUL SYLLABLE SSANGSIOS YEO RIEULKIYEOK - 0x9BD1: 0xC3AA, //HANGUL SYLLABLE SSANGSIOS YEO RIEULMIEUM - 0x9BD2: 0xC3AB, //HANGUL SYLLABLE SSANGSIOS YEO RIEULPIEUP - 0x9BD3: 0xC3AC, //HANGUL SYLLABLE SSANGSIOS YEO RIEULSIOS - 0x9BD4: 0xC3AD, //HANGUL SYLLABLE SSANGSIOS YEO RIEULTHIEUTH - 0x9BD5: 0xC3AE, //HANGUL SYLLABLE SSANGSIOS YEO RIEULPHIEUPH - 0x9BD6: 0xC3AF, //HANGUL SYLLABLE SSANGSIOS YEO RIEULHIEUH - 0x9BD7: 0xC3B0, //HANGUL SYLLABLE SSANGSIOS YEO MIEUM - 0x9BD8: 0xC3B1, //HANGUL SYLLABLE SSANGSIOS YEO PIEUP - 0x9BD9: 0xC3B2, //HANGUL SYLLABLE SSANGSIOS YEO PIEUPSIOS - 0x9BDA: 0xC3B3, //HANGUL SYLLABLE SSANGSIOS YEO SIOS - 0x9BDB: 0xC3B4, //HANGUL SYLLABLE SSANGSIOS YEO SSANGSIOS - 0x9BDC: 0xC3B5, //HANGUL SYLLABLE SSANGSIOS YEO IEUNG - 0x9BDD: 0xC3B6, //HANGUL SYLLABLE SSANGSIOS YEO CIEUC - 0x9BDE: 0xC3B7, //HANGUL SYLLABLE SSANGSIOS YEO CHIEUCH - 0x9BDF: 0xC3B8, //HANGUL SYLLABLE SSANGSIOS YEO KHIEUKH - 0x9BE0: 0xC3B9, //HANGUL SYLLABLE SSANGSIOS YEO THIEUTH - 0x9BE1: 0xC3BA, //HANGUL SYLLABLE SSANGSIOS YEO PHIEUPH - 0x9BE2: 0xC3BB, //HANGUL SYLLABLE SSANGSIOS YEO HIEUH - 0x9BE3: 0xC3BC, //HANGUL SYLLABLE SSANGSIOS YE - 0x9BE4: 0xC3BD, //HANGUL SYLLABLE SSANGSIOS YE KIYEOK - 0x9BE5: 0xC3BE, //HANGUL SYLLABLE SSANGSIOS YE SSANGKIYEOK - 0x9BE6: 0xC3BF, //HANGUL SYLLABLE SSANGSIOS YE KIYEOKSIOS - 0x9BE7: 0xC3C1, //HANGUL SYLLABLE SSANGSIOS YE NIEUNCIEUC - 0x9BE8: 0xC3C2, //HANGUL SYLLABLE SSANGSIOS YE NIEUNHIEUH - 0x9BE9: 0xC3C3, //HANGUL SYLLABLE SSANGSIOS YE TIKEUT - 0x9BEA: 0xC3C4, //HANGUL SYLLABLE SSANGSIOS YE RIEUL - 0x9BEB: 0xC3C5, //HANGUL SYLLABLE SSANGSIOS YE RIEULKIYEOK - 0x9BEC: 0xC3C6, //HANGUL SYLLABLE SSANGSIOS YE RIEULMIEUM - 0x9BED: 0xC3C7, //HANGUL SYLLABLE SSANGSIOS YE RIEULPIEUP - 0x9BEE: 0xC3C8, //HANGUL SYLLABLE SSANGSIOS YE RIEULSIOS - 0x9BEF: 0xC3C9, //HANGUL SYLLABLE SSANGSIOS YE RIEULTHIEUTH - 0x9BF0: 0xC3CA, //HANGUL SYLLABLE SSANGSIOS YE RIEULPHIEUPH - 0x9BF1: 0xC3CB, //HANGUL SYLLABLE SSANGSIOS YE RIEULHIEUH - 0x9BF2: 0xC3CC, //HANGUL SYLLABLE SSANGSIOS YE MIEUM - 0x9BF3: 0xC3CD, //HANGUL SYLLABLE SSANGSIOS YE PIEUP - 0x9BF4: 0xC3CE, //HANGUL SYLLABLE SSANGSIOS YE PIEUPSIOS - 0x9BF5: 0xC3CF, //HANGUL SYLLABLE SSANGSIOS YE SIOS - 0x9BF6: 0xC3D0, //HANGUL SYLLABLE SSANGSIOS YE SSANGSIOS - 0x9BF7: 0xC3D1, //HANGUL SYLLABLE SSANGSIOS YE IEUNG - 0x9BF8: 0xC3D2, //HANGUL SYLLABLE SSANGSIOS YE CIEUC - 0x9BF9: 0xC3D3, //HANGUL SYLLABLE SSANGSIOS YE CHIEUCH - 0x9BFA: 0xC3D4, //HANGUL SYLLABLE SSANGSIOS YE KHIEUKH - 0x9BFB: 0xC3D5, //HANGUL SYLLABLE SSANGSIOS YE THIEUTH - 0x9BFC: 0xC3D6, //HANGUL SYLLABLE SSANGSIOS YE PHIEUPH - 0x9BFD: 0xC3D7, //HANGUL SYLLABLE SSANGSIOS YE HIEUH - 0x9BFE: 0xC3DA, //HANGUL SYLLABLE SSANGSIOS O SSANGKIYEOK - 0x9C41: 0xC3DB, //HANGUL SYLLABLE SSANGSIOS O KIYEOKSIOS - 0x9C42: 0xC3DD, //HANGUL SYLLABLE SSANGSIOS O NIEUNCIEUC - 0x9C43: 0xC3DE, //HANGUL SYLLABLE SSANGSIOS O NIEUNHIEUH - 0x9C44: 0xC3E1, //HANGUL SYLLABLE SSANGSIOS O RIEULKIYEOK - 0x9C45: 0xC3E3, //HANGUL SYLLABLE SSANGSIOS O RIEULPIEUP - 0x9C46: 0xC3E4, //HANGUL SYLLABLE SSANGSIOS O RIEULSIOS - 0x9C47: 0xC3E5, //HANGUL SYLLABLE SSANGSIOS O RIEULTHIEUTH - 0x9C48: 0xC3E6, //HANGUL SYLLABLE SSANGSIOS O RIEULPHIEUPH - 0x9C49: 0xC3E7, //HANGUL SYLLABLE SSANGSIOS O RIEULHIEUH - 0x9C4A: 0xC3EA, //HANGUL SYLLABLE SSANGSIOS O PIEUPSIOS - 0x9C4B: 0xC3EB, //HANGUL SYLLABLE SSANGSIOS O SIOS - 0x9C4C: 0xC3EC, //HANGUL SYLLABLE SSANGSIOS O SSANGSIOS - 0x9C4D: 0xC3EE, //HANGUL SYLLABLE SSANGSIOS O CIEUC - 0x9C4E: 0xC3EF, //HANGUL SYLLABLE SSANGSIOS O CHIEUCH - 0x9C4F: 0xC3F0, //HANGUL SYLLABLE SSANGSIOS O KHIEUKH - 0x9C50: 0xC3F1, //HANGUL SYLLABLE SSANGSIOS O THIEUTH - 0x9C51: 0xC3F2, //HANGUL SYLLABLE SSANGSIOS O PHIEUPH - 0x9C52: 0xC3F3, //HANGUL SYLLABLE SSANGSIOS O HIEUH - 0x9C53: 0xC3F6, //HANGUL SYLLABLE SSANGSIOS WA SSANGKIYEOK - 0x9C54: 0xC3F7, //HANGUL SYLLABLE SSANGSIOS WA KIYEOKSIOS - 0x9C55: 0xC3F9, //HANGUL SYLLABLE SSANGSIOS WA NIEUNCIEUC - 0x9C56: 0xC3FA, //HANGUL SYLLABLE SSANGSIOS WA NIEUNHIEUH - 0x9C57: 0xC3FB, //HANGUL SYLLABLE SSANGSIOS WA TIKEUT - 0x9C58: 0xC3FC, //HANGUL SYLLABLE SSANGSIOS WA RIEUL - 0x9C59: 0xC3FD, //HANGUL SYLLABLE SSANGSIOS WA RIEULKIYEOK - 0x9C5A: 0xC3FE, //HANGUL SYLLABLE SSANGSIOS WA RIEULMIEUM - 0x9C61: 0xC3FF, //HANGUL SYLLABLE SSANGSIOS WA RIEULPIEUP - 0x9C62: 0xC400, //HANGUL SYLLABLE SSANGSIOS WA RIEULSIOS - 0x9C63: 0xC401, //HANGUL SYLLABLE SSANGSIOS WA RIEULTHIEUTH - 0x9C64: 0xC402, //HANGUL SYLLABLE SSANGSIOS WA RIEULPHIEUPH - 0x9C65: 0xC403, //HANGUL SYLLABLE SSANGSIOS WA RIEULHIEUH - 0x9C66: 0xC404, //HANGUL SYLLABLE SSANGSIOS WA MIEUM - 0x9C67: 0xC405, //HANGUL SYLLABLE SSANGSIOS WA PIEUP - 0x9C68: 0xC406, //HANGUL SYLLABLE SSANGSIOS WA PIEUPSIOS - 0x9C69: 0xC407, //HANGUL SYLLABLE SSANGSIOS WA SIOS - 0x9C6A: 0xC409, //HANGUL SYLLABLE SSANGSIOS WA IEUNG - 0x9C6B: 0xC40A, //HANGUL SYLLABLE SSANGSIOS WA CIEUC - 0x9C6C: 0xC40B, //HANGUL SYLLABLE SSANGSIOS WA CHIEUCH - 0x9C6D: 0xC40C, //HANGUL SYLLABLE SSANGSIOS WA KHIEUKH - 0x9C6E: 0xC40D, //HANGUL SYLLABLE SSANGSIOS WA THIEUTH - 0x9C6F: 0xC40E, //HANGUL SYLLABLE SSANGSIOS WA PHIEUPH - 0x9C70: 0xC40F, //HANGUL SYLLABLE SSANGSIOS WA HIEUH - 0x9C71: 0xC411, //HANGUL SYLLABLE SSANGSIOS WAE KIYEOK - 0x9C72: 0xC412, //HANGUL SYLLABLE SSANGSIOS WAE SSANGKIYEOK - 0x9C73: 0xC413, //HANGUL SYLLABLE SSANGSIOS WAE KIYEOKSIOS - 0x9C74: 0xC414, //HANGUL SYLLABLE SSANGSIOS WAE NIEUN - 0x9C75: 0xC415, //HANGUL SYLLABLE SSANGSIOS WAE NIEUNCIEUC - 0x9C76: 0xC416, //HANGUL SYLLABLE SSANGSIOS WAE NIEUNHIEUH - 0x9C77: 0xC417, //HANGUL SYLLABLE SSANGSIOS WAE TIKEUT - 0x9C78: 0xC418, //HANGUL SYLLABLE SSANGSIOS WAE RIEUL - 0x9C79: 0xC419, //HANGUL SYLLABLE SSANGSIOS WAE RIEULKIYEOK - 0x9C7A: 0xC41A, //HANGUL SYLLABLE SSANGSIOS WAE RIEULMIEUM - 0x9C81: 0xC41B, //HANGUL SYLLABLE SSANGSIOS WAE RIEULPIEUP - 0x9C82: 0xC41C, //HANGUL SYLLABLE SSANGSIOS WAE RIEULSIOS - 0x9C83: 0xC41D, //HANGUL SYLLABLE SSANGSIOS WAE RIEULTHIEUTH - 0x9C84: 0xC41E, //HANGUL SYLLABLE SSANGSIOS WAE RIEULPHIEUPH - 0x9C85: 0xC41F, //HANGUL SYLLABLE SSANGSIOS WAE RIEULHIEUH - 0x9C86: 0xC420, //HANGUL SYLLABLE SSANGSIOS WAE MIEUM - 0x9C87: 0xC421, //HANGUL SYLLABLE SSANGSIOS WAE PIEUP - 0x9C88: 0xC422, //HANGUL SYLLABLE SSANGSIOS WAE PIEUPSIOS - 0x9C89: 0xC423, //HANGUL SYLLABLE SSANGSIOS WAE SIOS - 0x9C8A: 0xC425, //HANGUL SYLLABLE SSANGSIOS WAE IEUNG - 0x9C8B: 0xC426, //HANGUL SYLLABLE SSANGSIOS WAE CIEUC - 0x9C8C: 0xC427, //HANGUL SYLLABLE SSANGSIOS WAE CHIEUCH - 0x9C8D: 0xC428, //HANGUL SYLLABLE SSANGSIOS WAE KHIEUKH - 0x9C8E: 0xC429, //HANGUL SYLLABLE SSANGSIOS WAE THIEUTH - 0x9C8F: 0xC42A, //HANGUL SYLLABLE SSANGSIOS WAE PHIEUPH - 0x9C90: 0xC42B, //HANGUL SYLLABLE SSANGSIOS WAE HIEUH - 0x9C91: 0xC42D, //HANGUL SYLLABLE SSANGSIOS OE KIYEOK - 0x9C92: 0xC42E, //HANGUL SYLLABLE SSANGSIOS OE SSANGKIYEOK - 0x9C93: 0xC42F, //HANGUL SYLLABLE SSANGSIOS OE KIYEOKSIOS - 0x9C94: 0xC431, //HANGUL SYLLABLE SSANGSIOS OE NIEUNCIEUC - 0x9C95: 0xC432, //HANGUL SYLLABLE SSANGSIOS OE NIEUNHIEUH - 0x9C96: 0xC433, //HANGUL SYLLABLE SSANGSIOS OE TIKEUT - 0x9C97: 0xC435, //HANGUL SYLLABLE SSANGSIOS OE RIEULKIYEOK - 0x9C98: 0xC436, //HANGUL SYLLABLE SSANGSIOS OE RIEULMIEUM - 0x9C99: 0xC437, //HANGUL SYLLABLE SSANGSIOS OE RIEULPIEUP - 0x9C9A: 0xC438, //HANGUL SYLLABLE SSANGSIOS OE RIEULSIOS - 0x9C9B: 0xC439, //HANGUL SYLLABLE SSANGSIOS OE RIEULTHIEUTH - 0x9C9C: 0xC43A, //HANGUL SYLLABLE SSANGSIOS OE RIEULPHIEUPH - 0x9C9D: 0xC43B, //HANGUL SYLLABLE SSANGSIOS OE RIEULHIEUH - 0x9C9E: 0xC43E, //HANGUL SYLLABLE SSANGSIOS OE PIEUPSIOS - 0x9C9F: 0xC43F, //HANGUL SYLLABLE SSANGSIOS OE SIOS - 0x9CA0: 0xC440, //HANGUL SYLLABLE SSANGSIOS OE SSANGSIOS - 0x9CA1: 0xC441, //HANGUL SYLLABLE SSANGSIOS OE IEUNG - 0x9CA2: 0xC442, //HANGUL SYLLABLE SSANGSIOS OE CIEUC - 0x9CA3: 0xC443, //HANGUL SYLLABLE SSANGSIOS OE CHIEUCH - 0x9CA4: 0xC444, //HANGUL SYLLABLE SSANGSIOS OE KHIEUKH - 0x9CA5: 0xC445, //HANGUL SYLLABLE SSANGSIOS OE THIEUTH - 0x9CA6: 0xC446, //HANGUL SYLLABLE SSANGSIOS OE PHIEUPH - 0x9CA7: 0xC447, //HANGUL SYLLABLE SSANGSIOS OE HIEUH - 0x9CA8: 0xC449, //HANGUL SYLLABLE SSANGSIOS YO KIYEOK - 0x9CA9: 0xC44A, //HANGUL SYLLABLE SSANGSIOS YO SSANGKIYEOK - 0x9CAA: 0xC44B, //HANGUL SYLLABLE SSANGSIOS YO KIYEOKSIOS - 0x9CAB: 0xC44C, //HANGUL SYLLABLE SSANGSIOS YO NIEUN - 0x9CAC: 0xC44D, //HANGUL SYLLABLE SSANGSIOS YO NIEUNCIEUC - 0x9CAD: 0xC44E, //HANGUL SYLLABLE SSANGSIOS YO NIEUNHIEUH - 0x9CAE: 0xC44F, //HANGUL SYLLABLE SSANGSIOS YO TIKEUT - 0x9CAF: 0xC450, //HANGUL SYLLABLE SSANGSIOS YO RIEUL - 0x9CB0: 0xC451, //HANGUL SYLLABLE SSANGSIOS YO RIEULKIYEOK - 0x9CB1: 0xC452, //HANGUL SYLLABLE SSANGSIOS YO RIEULMIEUM - 0x9CB2: 0xC453, //HANGUL SYLLABLE SSANGSIOS YO RIEULPIEUP - 0x9CB3: 0xC454, //HANGUL SYLLABLE SSANGSIOS YO RIEULSIOS - 0x9CB4: 0xC455, //HANGUL SYLLABLE SSANGSIOS YO RIEULTHIEUTH - 0x9CB5: 0xC456, //HANGUL SYLLABLE SSANGSIOS YO RIEULPHIEUPH - 0x9CB6: 0xC457, //HANGUL SYLLABLE SSANGSIOS YO RIEULHIEUH - 0x9CB7: 0xC458, //HANGUL SYLLABLE SSANGSIOS YO MIEUM - 0x9CB8: 0xC459, //HANGUL SYLLABLE SSANGSIOS YO PIEUP - 0x9CB9: 0xC45A, //HANGUL SYLLABLE SSANGSIOS YO PIEUPSIOS - 0x9CBA: 0xC45B, //HANGUL SYLLABLE SSANGSIOS YO SIOS - 0x9CBB: 0xC45C, //HANGUL SYLLABLE SSANGSIOS YO SSANGSIOS - 0x9CBC: 0xC45D, //HANGUL SYLLABLE SSANGSIOS YO IEUNG - 0x9CBD: 0xC45E, //HANGUL SYLLABLE SSANGSIOS YO CIEUC - 0x9CBE: 0xC45F, //HANGUL SYLLABLE SSANGSIOS YO CHIEUCH - 0x9CBF: 0xC460, //HANGUL SYLLABLE SSANGSIOS YO KHIEUKH - 0x9CC0: 0xC461, //HANGUL SYLLABLE SSANGSIOS YO THIEUTH - 0x9CC1: 0xC462, //HANGUL SYLLABLE SSANGSIOS YO PHIEUPH - 0x9CC2: 0xC463, //HANGUL SYLLABLE SSANGSIOS YO HIEUH - 0x9CC3: 0xC466, //HANGUL SYLLABLE SSANGSIOS U SSANGKIYEOK - 0x9CC4: 0xC467, //HANGUL SYLLABLE SSANGSIOS U KIYEOKSIOS - 0x9CC5: 0xC469, //HANGUL SYLLABLE SSANGSIOS U NIEUNCIEUC - 0x9CC6: 0xC46A, //HANGUL SYLLABLE SSANGSIOS U NIEUNHIEUH - 0x9CC7: 0xC46B, //HANGUL SYLLABLE SSANGSIOS U TIKEUT - 0x9CC8: 0xC46D, //HANGUL SYLLABLE SSANGSIOS U RIEULKIYEOK - 0x9CC9: 0xC46E, //HANGUL SYLLABLE SSANGSIOS U RIEULMIEUM - 0x9CCA: 0xC46F, //HANGUL SYLLABLE SSANGSIOS U RIEULPIEUP - 0x9CCB: 0xC470, //HANGUL SYLLABLE SSANGSIOS U RIEULSIOS - 0x9CCC: 0xC471, //HANGUL SYLLABLE SSANGSIOS U RIEULTHIEUTH - 0x9CCD: 0xC472, //HANGUL SYLLABLE SSANGSIOS U RIEULPHIEUPH - 0x9CCE: 0xC473, //HANGUL SYLLABLE SSANGSIOS U RIEULHIEUH - 0x9CCF: 0xC476, //HANGUL SYLLABLE SSANGSIOS U PIEUPSIOS - 0x9CD0: 0xC477, //HANGUL SYLLABLE SSANGSIOS U SIOS - 0x9CD1: 0xC478, //HANGUL SYLLABLE SSANGSIOS U SSANGSIOS - 0x9CD2: 0xC47A, //HANGUL SYLLABLE SSANGSIOS U CIEUC - 0x9CD3: 0xC47B, //HANGUL SYLLABLE SSANGSIOS U CHIEUCH - 0x9CD4: 0xC47C, //HANGUL SYLLABLE SSANGSIOS U KHIEUKH - 0x9CD5: 0xC47D, //HANGUL SYLLABLE SSANGSIOS U THIEUTH - 0x9CD6: 0xC47E, //HANGUL SYLLABLE SSANGSIOS U PHIEUPH - 0x9CD7: 0xC47F, //HANGUL SYLLABLE SSANGSIOS U HIEUH - 0x9CD8: 0xC481, //HANGUL SYLLABLE SSANGSIOS WEO KIYEOK - 0x9CD9: 0xC482, //HANGUL SYLLABLE SSANGSIOS WEO SSANGKIYEOK - 0x9CDA: 0xC483, //HANGUL SYLLABLE SSANGSIOS WEO KIYEOKSIOS - 0x9CDB: 0xC484, //HANGUL SYLLABLE SSANGSIOS WEO NIEUN - 0x9CDC: 0xC485, //HANGUL SYLLABLE SSANGSIOS WEO NIEUNCIEUC - 0x9CDD: 0xC486, //HANGUL SYLLABLE SSANGSIOS WEO NIEUNHIEUH - 0x9CDE: 0xC487, //HANGUL SYLLABLE SSANGSIOS WEO TIKEUT - 0x9CDF: 0xC488, //HANGUL SYLLABLE SSANGSIOS WEO RIEUL - 0x9CE0: 0xC489, //HANGUL SYLLABLE SSANGSIOS WEO RIEULKIYEOK - 0x9CE1: 0xC48A, //HANGUL SYLLABLE SSANGSIOS WEO RIEULMIEUM - 0x9CE2: 0xC48B, //HANGUL SYLLABLE SSANGSIOS WEO RIEULPIEUP - 0x9CE3: 0xC48C, //HANGUL SYLLABLE SSANGSIOS WEO RIEULSIOS - 0x9CE4: 0xC48D, //HANGUL SYLLABLE SSANGSIOS WEO RIEULTHIEUTH - 0x9CE5: 0xC48E, //HANGUL SYLLABLE SSANGSIOS WEO RIEULPHIEUPH - 0x9CE6: 0xC48F, //HANGUL SYLLABLE SSANGSIOS WEO RIEULHIEUH - 0x9CE7: 0xC490, //HANGUL SYLLABLE SSANGSIOS WEO MIEUM - 0x9CE8: 0xC491, //HANGUL SYLLABLE SSANGSIOS WEO PIEUP - 0x9CE9: 0xC492, //HANGUL SYLLABLE SSANGSIOS WEO PIEUPSIOS - 0x9CEA: 0xC493, //HANGUL SYLLABLE SSANGSIOS WEO SIOS - 0x9CEB: 0xC495, //HANGUL SYLLABLE SSANGSIOS WEO IEUNG - 0x9CEC: 0xC496, //HANGUL SYLLABLE SSANGSIOS WEO CIEUC - 0x9CED: 0xC497, //HANGUL SYLLABLE SSANGSIOS WEO CHIEUCH - 0x9CEE: 0xC498, //HANGUL SYLLABLE SSANGSIOS WEO KHIEUKH - 0x9CEF: 0xC499, //HANGUL SYLLABLE SSANGSIOS WEO THIEUTH - 0x9CF0: 0xC49A, //HANGUL SYLLABLE SSANGSIOS WEO PHIEUPH - 0x9CF1: 0xC49B, //HANGUL SYLLABLE SSANGSIOS WEO HIEUH - 0x9CF2: 0xC49D, //HANGUL SYLLABLE SSANGSIOS WE KIYEOK - 0x9CF3: 0xC49E, //HANGUL SYLLABLE SSANGSIOS WE SSANGKIYEOK - 0x9CF4: 0xC49F, //HANGUL SYLLABLE SSANGSIOS WE KIYEOKSIOS - 0x9CF5: 0xC4A0, //HANGUL SYLLABLE SSANGSIOS WE NIEUN - 0x9CF6: 0xC4A1, //HANGUL SYLLABLE SSANGSIOS WE NIEUNCIEUC - 0x9CF7: 0xC4A2, //HANGUL SYLLABLE SSANGSIOS WE NIEUNHIEUH - 0x9CF8: 0xC4A3, //HANGUL SYLLABLE SSANGSIOS WE TIKEUT - 0x9CF9: 0xC4A4, //HANGUL SYLLABLE SSANGSIOS WE RIEUL - 0x9CFA: 0xC4A5, //HANGUL SYLLABLE SSANGSIOS WE RIEULKIYEOK - 0x9CFB: 0xC4A6, //HANGUL SYLLABLE SSANGSIOS WE RIEULMIEUM - 0x9CFC: 0xC4A7, //HANGUL SYLLABLE SSANGSIOS WE RIEULPIEUP - 0x9CFD: 0xC4A8, //HANGUL SYLLABLE SSANGSIOS WE RIEULSIOS - 0x9CFE: 0xC4A9, //HANGUL SYLLABLE SSANGSIOS WE RIEULTHIEUTH - 0x9D41: 0xC4AA, //HANGUL SYLLABLE SSANGSIOS WE RIEULPHIEUPH - 0x9D42: 0xC4AB, //HANGUL SYLLABLE SSANGSIOS WE RIEULHIEUH - 0x9D43: 0xC4AC, //HANGUL SYLLABLE SSANGSIOS WE MIEUM - 0x9D44: 0xC4AD, //HANGUL SYLLABLE SSANGSIOS WE PIEUP - 0x9D45: 0xC4AE, //HANGUL SYLLABLE SSANGSIOS WE PIEUPSIOS - 0x9D46: 0xC4AF, //HANGUL SYLLABLE SSANGSIOS WE SIOS - 0x9D47: 0xC4B0, //HANGUL SYLLABLE SSANGSIOS WE SSANGSIOS - 0x9D48: 0xC4B1, //HANGUL SYLLABLE SSANGSIOS WE IEUNG - 0x9D49: 0xC4B2, //HANGUL SYLLABLE SSANGSIOS WE CIEUC - 0x9D4A: 0xC4B3, //HANGUL SYLLABLE SSANGSIOS WE CHIEUCH - 0x9D4B: 0xC4B4, //HANGUL SYLLABLE SSANGSIOS WE KHIEUKH - 0x9D4C: 0xC4B5, //HANGUL SYLLABLE SSANGSIOS WE THIEUTH - 0x9D4D: 0xC4B6, //HANGUL SYLLABLE SSANGSIOS WE PHIEUPH - 0x9D4E: 0xC4B7, //HANGUL SYLLABLE SSANGSIOS WE HIEUH - 0x9D4F: 0xC4B9, //HANGUL SYLLABLE SSANGSIOS WI KIYEOK - 0x9D50: 0xC4BA, //HANGUL SYLLABLE SSANGSIOS WI SSANGKIYEOK - 0x9D51: 0xC4BB, //HANGUL SYLLABLE SSANGSIOS WI KIYEOKSIOS - 0x9D52: 0xC4BD, //HANGUL SYLLABLE SSANGSIOS WI NIEUNCIEUC - 0x9D53: 0xC4BE, //HANGUL SYLLABLE SSANGSIOS WI NIEUNHIEUH - 0x9D54: 0xC4BF, //HANGUL SYLLABLE SSANGSIOS WI TIKEUT - 0x9D55: 0xC4C0, //HANGUL SYLLABLE SSANGSIOS WI RIEUL - 0x9D56: 0xC4C1, //HANGUL SYLLABLE SSANGSIOS WI RIEULKIYEOK - 0x9D57: 0xC4C2, //HANGUL SYLLABLE SSANGSIOS WI RIEULMIEUM - 0x9D58: 0xC4C3, //HANGUL SYLLABLE SSANGSIOS WI RIEULPIEUP - 0x9D59: 0xC4C4, //HANGUL SYLLABLE SSANGSIOS WI RIEULSIOS - 0x9D5A: 0xC4C5, //HANGUL SYLLABLE SSANGSIOS WI RIEULTHIEUTH - 0x9D61: 0xC4C6, //HANGUL SYLLABLE SSANGSIOS WI RIEULPHIEUPH - 0x9D62: 0xC4C7, //HANGUL SYLLABLE SSANGSIOS WI RIEULHIEUH - 0x9D63: 0xC4C8, //HANGUL SYLLABLE SSANGSIOS WI MIEUM - 0x9D64: 0xC4C9, //HANGUL SYLLABLE SSANGSIOS WI PIEUP - 0x9D65: 0xC4CA, //HANGUL SYLLABLE SSANGSIOS WI PIEUPSIOS - 0x9D66: 0xC4CB, //HANGUL SYLLABLE SSANGSIOS WI SIOS - 0x9D67: 0xC4CC, //HANGUL SYLLABLE SSANGSIOS WI SSANGSIOS - 0x9D68: 0xC4CD, //HANGUL SYLLABLE SSANGSIOS WI IEUNG - 0x9D69: 0xC4CE, //HANGUL SYLLABLE SSANGSIOS WI CIEUC - 0x9D6A: 0xC4CF, //HANGUL SYLLABLE SSANGSIOS WI CHIEUCH - 0x9D6B: 0xC4D0, //HANGUL SYLLABLE SSANGSIOS WI KHIEUKH - 0x9D6C: 0xC4D1, //HANGUL SYLLABLE SSANGSIOS WI THIEUTH - 0x9D6D: 0xC4D2, //HANGUL SYLLABLE SSANGSIOS WI PHIEUPH - 0x9D6E: 0xC4D3, //HANGUL SYLLABLE SSANGSIOS WI HIEUH - 0x9D6F: 0xC4D4, //HANGUL SYLLABLE SSANGSIOS YU - 0x9D70: 0xC4D5, //HANGUL SYLLABLE SSANGSIOS YU KIYEOK - 0x9D71: 0xC4D6, //HANGUL SYLLABLE SSANGSIOS YU SSANGKIYEOK - 0x9D72: 0xC4D7, //HANGUL SYLLABLE SSANGSIOS YU KIYEOKSIOS - 0x9D73: 0xC4D8, //HANGUL SYLLABLE SSANGSIOS YU NIEUN - 0x9D74: 0xC4D9, //HANGUL SYLLABLE SSANGSIOS YU NIEUNCIEUC - 0x9D75: 0xC4DA, //HANGUL SYLLABLE SSANGSIOS YU NIEUNHIEUH - 0x9D76: 0xC4DB, //HANGUL SYLLABLE SSANGSIOS YU TIKEUT - 0x9D77: 0xC4DC, //HANGUL SYLLABLE SSANGSIOS YU RIEUL - 0x9D78: 0xC4DD, //HANGUL SYLLABLE SSANGSIOS YU RIEULKIYEOK - 0x9D79: 0xC4DE, //HANGUL SYLLABLE SSANGSIOS YU RIEULMIEUM - 0x9D7A: 0xC4DF, //HANGUL SYLLABLE SSANGSIOS YU RIEULPIEUP - 0x9D81: 0xC4E0, //HANGUL SYLLABLE SSANGSIOS YU RIEULSIOS - 0x9D82: 0xC4E1, //HANGUL SYLLABLE SSANGSIOS YU RIEULTHIEUTH - 0x9D83: 0xC4E2, //HANGUL SYLLABLE SSANGSIOS YU RIEULPHIEUPH - 0x9D84: 0xC4E3, //HANGUL SYLLABLE SSANGSIOS YU RIEULHIEUH - 0x9D85: 0xC4E4, //HANGUL SYLLABLE SSANGSIOS YU MIEUM - 0x9D86: 0xC4E5, //HANGUL SYLLABLE SSANGSIOS YU PIEUP - 0x9D87: 0xC4E6, //HANGUL SYLLABLE SSANGSIOS YU PIEUPSIOS - 0x9D88: 0xC4E7, //HANGUL SYLLABLE SSANGSIOS YU SIOS - 0x9D89: 0xC4E8, //HANGUL SYLLABLE SSANGSIOS YU SSANGSIOS - 0x9D8A: 0xC4EA, //HANGUL SYLLABLE SSANGSIOS YU CIEUC - 0x9D8B: 0xC4EB, //HANGUL SYLLABLE SSANGSIOS YU CHIEUCH - 0x9D8C: 0xC4EC, //HANGUL SYLLABLE SSANGSIOS YU KHIEUKH - 0x9D8D: 0xC4ED, //HANGUL SYLLABLE SSANGSIOS YU THIEUTH - 0x9D8E: 0xC4EE, //HANGUL SYLLABLE SSANGSIOS YU PHIEUPH - 0x9D8F: 0xC4EF, //HANGUL SYLLABLE SSANGSIOS YU HIEUH - 0x9D90: 0xC4F2, //HANGUL SYLLABLE SSANGSIOS EU SSANGKIYEOK - 0x9D91: 0xC4F3, //HANGUL SYLLABLE SSANGSIOS EU KIYEOKSIOS - 0x9D92: 0xC4F5, //HANGUL SYLLABLE SSANGSIOS EU NIEUNCIEUC - 0x9D93: 0xC4F6, //HANGUL SYLLABLE SSANGSIOS EU NIEUNHIEUH - 0x9D94: 0xC4F7, //HANGUL SYLLABLE SSANGSIOS EU TIKEUT - 0x9D95: 0xC4F9, //HANGUL SYLLABLE SSANGSIOS EU RIEULKIYEOK - 0x9D96: 0xC4FB, //HANGUL SYLLABLE SSANGSIOS EU RIEULPIEUP - 0x9D97: 0xC4FC, //HANGUL SYLLABLE SSANGSIOS EU RIEULSIOS - 0x9D98: 0xC4FD, //HANGUL SYLLABLE SSANGSIOS EU RIEULTHIEUTH - 0x9D99: 0xC4FE, //HANGUL SYLLABLE SSANGSIOS EU RIEULPHIEUPH - 0x9D9A: 0xC502, //HANGUL SYLLABLE SSANGSIOS EU PIEUPSIOS - 0x9D9B: 0xC503, //HANGUL SYLLABLE SSANGSIOS EU SIOS - 0x9D9C: 0xC504, //HANGUL SYLLABLE SSANGSIOS EU SSANGSIOS - 0x9D9D: 0xC505, //HANGUL SYLLABLE SSANGSIOS EU IEUNG - 0x9D9E: 0xC506, //HANGUL SYLLABLE SSANGSIOS EU CIEUC - 0x9D9F: 0xC507, //HANGUL SYLLABLE SSANGSIOS EU CHIEUCH - 0x9DA0: 0xC508, //HANGUL SYLLABLE SSANGSIOS EU KHIEUKH - 0x9DA1: 0xC509, //HANGUL SYLLABLE SSANGSIOS EU THIEUTH - 0x9DA2: 0xC50A, //HANGUL SYLLABLE SSANGSIOS EU PHIEUPH - 0x9DA3: 0xC50B, //HANGUL SYLLABLE SSANGSIOS EU HIEUH - 0x9DA4: 0xC50D, //HANGUL SYLLABLE SSANGSIOS YI KIYEOK - 0x9DA5: 0xC50E, //HANGUL SYLLABLE SSANGSIOS YI SSANGKIYEOK - 0x9DA6: 0xC50F, //HANGUL SYLLABLE SSANGSIOS YI KIYEOKSIOS - 0x9DA7: 0xC511, //HANGUL SYLLABLE SSANGSIOS YI NIEUNCIEUC - 0x9DA8: 0xC512, //HANGUL SYLLABLE SSANGSIOS YI NIEUNHIEUH - 0x9DA9: 0xC513, //HANGUL SYLLABLE SSANGSIOS YI TIKEUT - 0x9DAA: 0xC515, //HANGUL SYLLABLE SSANGSIOS YI RIEULKIYEOK - 0x9DAB: 0xC516, //HANGUL SYLLABLE SSANGSIOS YI RIEULMIEUM - 0x9DAC: 0xC517, //HANGUL SYLLABLE SSANGSIOS YI RIEULPIEUP - 0x9DAD: 0xC518, //HANGUL SYLLABLE SSANGSIOS YI RIEULSIOS - 0x9DAE: 0xC519, //HANGUL SYLLABLE SSANGSIOS YI RIEULTHIEUTH - 0x9DAF: 0xC51A, //HANGUL SYLLABLE SSANGSIOS YI RIEULPHIEUPH - 0x9DB0: 0xC51B, //HANGUL SYLLABLE SSANGSIOS YI RIEULHIEUH - 0x9DB1: 0xC51D, //HANGUL SYLLABLE SSANGSIOS YI PIEUP - 0x9DB2: 0xC51E, //HANGUL SYLLABLE SSANGSIOS YI PIEUPSIOS - 0x9DB3: 0xC51F, //HANGUL SYLLABLE SSANGSIOS YI SIOS - 0x9DB4: 0xC520, //HANGUL SYLLABLE SSANGSIOS YI SSANGSIOS - 0x9DB5: 0xC521, //HANGUL SYLLABLE SSANGSIOS YI IEUNG - 0x9DB6: 0xC522, //HANGUL SYLLABLE SSANGSIOS YI CIEUC - 0x9DB7: 0xC523, //HANGUL SYLLABLE SSANGSIOS YI CHIEUCH - 0x9DB8: 0xC524, //HANGUL SYLLABLE SSANGSIOS YI KHIEUKH - 0x9DB9: 0xC525, //HANGUL SYLLABLE SSANGSIOS YI THIEUTH - 0x9DBA: 0xC526, //HANGUL SYLLABLE SSANGSIOS YI PHIEUPH - 0x9DBB: 0xC527, //HANGUL SYLLABLE SSANGSIOS YI HIEUH - 0x9DBC: 0xC52A, //HANGUL SYLLABLE SSANGSIOS I SSANGKIYEOK - 0x9DBD: 0xC52B, //HANGUL SYLLABLE SSANGSIOS I KIYEOKSIOS - 0x9DBE: 0xC52D, //HANGUL SYLLABLE SSANGSIOS I NIEUNCIEUC - 0x9DBF: 0xC52E, //HANGUL SYLLABLE SSANGSIOS I NIEUNHIEUH - 0x9DC0: 0xC52F, //HANGUL SYLLABLE SSANGSIOS I TIKEUT - 0x9DC1: 0xC531, //HANGUL SYLLABLE SSANGSIOS I RIEULKIYEOK - 0x9DC2: 0xC532, //HANGUL SYLLABLE SSANGSIOS I RIEULMIEUM - 0x9DC3: 0xC533, //HANGUL SYLLABLE SSANGSIOS I RIEULPIEUP - 0x9DC4: 0xC534, //HANGUL SYLLABLE SSANGSIOS I RIEULSIOS - 0x9DC5: 0xC535, //HANGUL SYLLABLE SSANGSIOS I RIEULTHIEUTH - 0x9DC6: 0xC536, //HANGUL SYLLABLE SSANGSIOS I RIEULPHIEUPH - 0x9DC7: 0xC537, //HANGUL SYLLABLE SSANGSIOS I RIEULHIEUH - 0x9DC8: 0xC53A, //HANGUL SYLLABLE SSANGSIOS I PIEUPSIOS - 0x9DC9: 0xC53C, //HANGUL SYLLABLE SSANGSIOS I SSANGSIOS - 0x9DCA: 0xC53E, //HANGUL SYLLABLE SSANGSIOS I CIEUC - 0x9DCB: 0xC53F, //HANGUL SYLLABLE SSANGSIOS I CHIEUCH - 0x9DCC: 0xC540, //HANGUL SYLLABLE SSANGSIOS I KHIEUKH - 0x9DCD: 0xC541, //HANGUL SYLLABLE SSANGSIOS I THIEUTH - 0x9DCE: 0xC542, //HANGUL SYLLABLE SSANGSIOS I PHIEUPH - 0x9DCF: 0xC543, //HANGUL SYLLABLE SSANGSIOS I HIEUH - 0x9DD0: 0xC546, //HANGUL SYLLABLE IEUNG A SSANGKIYEOK - 0x9DD1: 0xC547, //HANGUL SYLLABLE IEUNG A KIYEOKSIOS - 0x9DD2: 0xC54B, //HANGUL SYLLABLE IEUNG A TIKEUT - 0x9DD3: 0xC54F, //HANGUL SYLLABLE IEUNG A RIEULPIEUP - 0x9DD4: 0xC550, //HANGUL SYLLABLE IEUNG A RIEULSIOS - 0x9DD5: 0xC551, //HANGUL SYLLABLE IEUNG A RIEULTHIEUTH - 0x9DD6: 0xC552, //HANGUL SYLLABLE IEUNG A RIEULPHIEUPH - 0x9DD7: 0xC556, //HANGUL SYLLABLE IEUNG A PIEUPSIOS - 0x9DD8: 0xC55A, //HANGUL SYLLABLE IEUNG A CIEUC - 0x9DD9: 0xC55B, //HANGUL SYLLABLE IEUNG A CHIEUCH - 0x9DDA: 0xC55C, //HANGUL SYLLABLE IEUNG A KHIEUKH - 0x9DDB: 0xC55F, //HANGUL SYLLABLE IEUNG A HIEUH - 0x9DDC: 0xC562, //HANGUL SYLLABLE IEUNG AE SSANGKIYEOK - 0x9DDD: 0xC563, //HANGUL SYLLABLE IEUNG AE KIYEOKSIOS - 0x9DDE: 0xC565, //HANGUL SYLLABLE IEUNG AE NIEUNCIEUC - 0x9DDF: 0xC566, //HANGUL SYLLABLE IEUNG AE NIEUNHIEUH - 0x9DE0: 0xC567, //HANGUL SYLLABLE IEUNG AE TIKEUT - 0x9DE1: 0xC569, //HANGUL SYLLABLE IEUNG AE RIEULKIYEOK - 0x9DE2: 0xC56A, //HANGUL SYLLABLE IEUNG AE RIEULMIEUM - 0x9DE3: 0xC56B, //HANGUL SYLLABLE IEUNG AE RIEULPIEUP - 0x9DE4: 0xC56C, //HANGUL SYLLABLE IEUNG AE RIEULSIOS - 0x9DE5: 0xC56D, //HANGUL SYLLABLE IEUNG AE RIEULTHIEUTH - 0x9DE6: 0xC56E, //HANGUL SYLLABLE IEUNG AE RIEULPHIEUPH - 0x9DE7: 0xC56F, //HANGUL SYLLABLE IEUNG AE RIEULHIEUH - 0x9DE8: 0xC572, //HANGUL SYLLABLE IEUNG AE PIEUPSIOS - 0x9DE9: 0xC576, //HANGUL SYLLABLE IEUNG AE CIEUC - 0x9DEA: 0xC577, //HANGUL SYLLABLE IEUNG AE CHIEUCH - 0x9DEB: 0xC578, //HANGUL SYLLABLE IEUNG AE KHIEUKH - 0x9DEC: 0xC579, //HANGUL SYLLABLE IEUNG AE THIEUTH - 0x9DED: 0xC57A, //HANGUL SYLLABLE IEUNG AE PHIEUPH - 0x9DEE: 0xC57B, //HANGUL SYLLABLE IEUNG AE HIEUH - 0x9DEF: 0xC57E, //HANGUL SYLLABLE IEUNG YA SSANGKIYEOK - 0x9DF0: 0xC57F, //HANGUL SYLLABLE IEUNG YA KIYEOKSIOS - 0x9DF1: 0xC581, //HANGUL SYLLABLE IEUNG YA NIEUNCIEUC - 0x9DF2: 0xC582, //HANGUL SYLLABLE IEUNG YA NIEUNHIEUH - 0x9DF3: 0xC583, //HANGUL SYLLABLE IEUNG YA TIKEUT - 0x9DF4: 0xC585, //HANGUL SYLLABLE IEUNG YA RIEULKIYEOK - 0x9DF5: 0xC586, //HANGUL SYLLABLE IEUNG YA RIEULMIEUM - 0x9DF6: 0xC588, //HANGUL SYLLABLE IEUNG YA RIEULSIOS - 0x9DF7: 0xC589, //HANGUL SYLLABLE IEUNG YA RIEULTHIEUTH - 0x9DF8: 0xC58A, //HANGUL SYLLABLE IEUNG YA RIEULPHIEUPH - 0x9DF9: 0xC58B, //HANGUL SYLLABLE IEUNG YA RIEULHIEUH - 0x9DFA: 0xC58E, //HANGUL SYLLABLE IEUNG YA PIEUPSIOS - 0x9DFB: 0xC590, //HANGUL SYLLABLE IEUNG YA SSANGSIOS - 0x9DFC: 0xC592, //HANGUL SYLLABLE IEUNG YA CIEUC - 0x9DFD: 0xC593, //HANGUL SYLLABLE IEUNG YA CHIEUCH - 0x9DFE: 0xC594, //HANGUL SYLLABLE IEUNG YA KHIEUKH - 0x9E41: 0xC596, //HANGUL SYLLABLE IEUNG YA PHIEUPH - 0x9E42: 0xC599, //HANGUL SYLLABLE IEUNG YAE KIYEOK - 0x9E43: 0xC59A, //HANGUL SYLLABLE IEUNG YAE SSANGKIYEOK - 0x9E44: 0xC59B, //HANGUL SYLLABLE IEUNG YAE KIYEOKSIOS - 0x9E45: 0xC59D, //HANGUL SYLLABLE IEUNG YAE NIEUNCIEUC - 0x9E46: 0xC59E, //HANGUL SYLLABLE IEUNG YAE NIEUNHIEUH - 0x9E47: 0xC59F, //HANGUL SYLLABLE IEUNG YAE TIKEUT - 0x9E48: 0xC5A1, //HANGUL SYLLABLE IEUNG YAE RIEULKIYEOK - 0x9E49: 0xC5A2, //HANGUL SYLLABLE IEUNG YAE RIEULMIEUM - 0x9E4A: 0xC5A3, //HANGUL SYLLABLE IEUNG YAE RIEULPIEUP - 0x9E4B: 0xC5A4, //HANGUL SYLLABLE IEUNG YAE RIEULSIOS - 0x9E4C: 0xC5A5, //HANGUL SYLLABLE IEUNG YAE RIEULTHIEUTH - 0x9E4D: 0xC5A6, //HANGUL SYLLABLE IEUNG YAE RIEULPHIEUPH - 0x9E4E: 0xC5A7, //HANGUL SYLLABLE IEUNG YAE RIEULHIEUH - 0x9E4F: 0xC5A8, //HANGUL SYLLABLE IEUNG YAE MIEUM - 0x9E50: 0xC5AA, //HANGUL SYLLABLE IEUNG YAE PIEUPSIOS - 0x9E51: 0xC5AB, //HANGUL SYLLABLE IEUNG YAE SIOS - 0x9E52: 0xC5AC, //HANGUL SYLLABLE IEUNG YAE SSANGSIOS - 0x9E53: 0xC5AD, //HANGUL SYLLABLE IEUNG YAE IEUNG - 0x9E54: 0xC5AE, //HANGUL SYLLABLE IEUNG YAE CIEUC - 0x9E55: 0xC5AF, //HANGUL SYLLABLE IEUNG YAE CHIEUCH - 0x9E56: 0xC5B0, //HANGUL SYLLABLE IEUNG YAE KHIEUKH - 0x9E57: 0xC5B1, //HANGUL SYLLABLE IEUNG YAE THIEUTH - 0x9E58: 0xC5B2, //HANGUL SYLLABLE IEUNG YAE PHIEUPH - 0x9E59: 0xC5B3, //HANGUL SYLLABLE IEUNG YAE HIEUH - 0x9E5A: 0xC5B6, //HANGUL SYLLABLE IEUNG EO SSANGKIYEOK - 0x9E61: 0xC5B7, //HANGUL SYLLABLE IEUNG EO KIYEOKSIOS - 0x9E62: 0xC5BA, //HANGUL SYLLABLE IEUNG EO NIEUNHIEUH - 0x9E63: 0xC5BF, //HANGUL SYLLABLE IEUNG EO RIEULPIEUP - 0x9E64: 0xC5C0, //HANGUL SYLLABLE IEUNG EO RIEULSIOS - 0x9E65: 0xC5C1, //HANGUL SYLLABLE IEUNG EO RIEULTHIEUTH - 0x9E66: 0xC5C2, //HANGUL SYLLABLE IEUNG EO RIEULPHIEUPH - 0x9E67: 0xC5C3, //HANGUL SYLLABLE IEUNG EO RIEULHIEUH - 0x9E68: 0xC5CB, //HANGUL SYLLABLE IEUNG EO CHIEUCH - 0x9E69: 0xC5CD, //HANGUL SYLLABLE IEUNG EO THIEUTH - 0x9E6A: 0xC5CF, //HANGUL SYLLABLE IEUNG EO HIEUH - 0x9E6B: 0xC5D2, //HANGUL SYLLABLE IEUNG E SSANGKIYEOK - 0x9E6C: 0xC5D3, //HANGUL SYLLABLE IEUNG E KIYEOKSIOS - 0x9E6D: 0xC5D5, //HANGUL SYLLABLE IEUNG E NIEUNCIEUC - 0x9E6E: 0xC5D6, //HANGUL SYLLABLE IEUNG E NIEUNHIEUH - 0x9E6F: 0xC5D7, //HANGUL SYLLABLE IEUNG E TIKEUT - 0x9E70: 0xC5D9, //HANGUL SYLLABLE IEUNG E RIEULKIYEOK - 0x9E71: 0xC5DA, //HANGUL SYLLABLE IEUNG E RIEULMIEUM - 0x9E72: 0xC5DB, //HANGUL SYLLABLE IEUNG E RIEULPIEUP - 0x9E73: 0xC5DC, //HANGUL SYLLABLE IEUNG E RIEULSIOS - 0x9E74: 0xC5DD, //HANGUL SYLLABLE IEUNG E RIEULTHIEUTH - 0x9E75: 0xC5DE, //HANGUL SYLLABLE IEUNG E RIEULPHIEUPH - 0x9E76: 0xC5DF, //HANGUL SYLLABLE IEUNG E RIEULHIEUH - 0x9E77: 0xC5E2, //HANGUL SYLLABLE IEUNG E PIEUPSIOS - 0x9E78: 0xC5E4, //HANGUL SYLLABLE IEUNG E SSANGSIOS - 0x9E79: 0xC5E6, //HANGUL SYLLABLE IEUNG E CIEUC - 0x9E7A: 0xC5E7, //HANGUL SYLLABLE IEUNG E CHIEUCH - 0x9E81: 0xC5E8, //HANGUL SYLLABLE IEUNG E KHIEUKH - 0x9E82: 0xC5E9, //HANGUL SYLLABLE IEUNG E THIEUTH - 0x9E83: 0xC5EA, //HANGUL SYLLABLE IEUNG E PHIEUPH - 0x9E84: 0xC5EB, //HANGUL SYLLABLE IEUNG E HIEUH - 0x9E85: 0xC5EF, //HANGUL SYLLABLE IEUNG YEO KIYEOKSIOS - 0x9E86: 0xC5F1, //HANGUL SYLLABLE IEUNG YEO NIEUNCIEUC - 0x9E87: 0xC5F2, //HANGUL SYLLABLE IEUNG YEO NIEUNHIEUH - 0x9E88: 0xC5F3, //HANGUL SYLLABLE IEUNG YEO TIKEUT - 0x9E89: 0xC5F5, //HANGUL SYLLABLE IEUNG YEO RIEULKIYEOK - 0x9E8A: 0xC5F8, //HANGUL SYLLABLE IEUNG YEO RIEULSIOS - 0x9E8B: 0xC5F9, //HANGUL SYLLABLE IEUNG YEO RIEULTHIEUTH - 0x9E8C: 0xC5FA, //HANGUL SYLLABLE IEUNG YEO RIEULPHIEUPH - 0x9E8D: 0xC5FB, //HANGUL SYLLABLE IEUNG YEO RIEULHIEUH - 0x9E8E: 0xC602, //HANGUL SYLLABLE IEUNG YEO CIEUC - 0x9E8F: 0xC603, //HANGUL SYLLABLE IEUNG YEO CHIEUCH - 0x9E90: 0xC604, //HANGUL SYLLABLE IEUNG YEO KHIEUKH - 0x9E91: 0xC609, //HANGUL SYLLABLE IEUNG YE KIYEOK - 0x9E92: 0xC60A, //HANGUL SYLLABLE IEUNG YE SSANGKIYEOK - 0x9E93: 0xC60B, //HANGUL SYLLABLE IEUNG YE KIYEOKSIOS - 0x9E94: 0xC60D, //HANGUL SYLLABLE IEUNG YE NIEUNCIEUC - 0x9E95: 0xC60E, //HANGUL SYLLABLE IEUNG YE NIEUNHIEUH - 0x9E96: 0xC60F, //HANGUL SYLLABLE IEUNG YE TIKEUT - 0x9E97: 0xC611, //HANGUL SYLLABLE IEUNG YE RIEULKIYEOK - 0x9E98: 0xC612, //HANGUL SYLLABLE IEUNG YE RIEULMIEUM - 0x9E99: 0xC613, //HANGUL SYLLABLE IEUNG YE RIEULPIEUP - 0x9E9A: 0xC614, //HANGUL SYLLABLE IEUNG YE RIEULSIOS - 0x9E9B: 0xC615, //HANGUL SYLLABLE IEUNG YE RIEULTHIEUTH - 0x9E9C: 0xC616, //HANGUL SYLLABLE IEUNG YE RIEULPHIEUPH - 0x9E9D: 0xC617, //HANGUL SYLLABLE IEUNG YE RIEULHIEUH - 0x9E9E: 0xC61A, //HANGUL SYLLABLE IEUNG YE PIEUPSIOS - 0x9E9F: 0xC61D, //HANGUL SYLLABLE IEUNG YE IEUNG - 0x9EA0: 0xC61E, //HANGUL SYLLABLE IEUNG YE CIEUC - 0x9EA1: 0xC61F, //HANGUL SYLLABLE IEUNG YE CHIEUCH - 0x9EA2: 0xC620, //HANGUL SYLLABLE IEUNG YE KHIEUKH - 0x9EA3: 0xC621, //HANGUL SYLLABLE IEUNG YE THIEUTH - 0x9EA4: 0xC622, //HANGUL SYLLABLE IEUNG YE PHIEUPH - 0x9EA5: 0xC623, //HANGUL SYLLABLE IEUNG YE HIEUH - 0x9EA6: 0xC626, //HANGUL SYLLABLE IEUNG O SSANGKIYEOK - 0x9EA7: 0xC627, //HANGUL SYLLABLE IEUNG O KIYEOKSIOS - 0x9EA8: 0xC629, //HANGUL SYLLABLE IEUNG O NIEUNCIEUC - 0x9EA9: 0xC62A, //HANGUL SYLLABLE IEUNG O NIEUNHIEUH - 0x9EAA: 0xC62B, //HANGUL SYLLABLE IEUNG O TIKEUT - 0x9EAB: 0xC62F, //HANGUL SYLLABLE IEUNG O RIEULPIEUP - 0x9EAC: 0xC631, //HANGUL SYLLABLE IEUNG O RIEULTHIEUTH - 0x9EAD: 0xC632, //HANGUL SYLLABLE IEUNG O RIEULPHIEUPH - 0x9EAE: 0xC636, //HANGUL SYLLABLE IEUNG O PIEUPSIOS - 0x9EAF: 0xC638, //HANGUL SYLLABLE IEUNG O SSANGSIOS - 0x9EB0: 0xC63A, //HANGUL SYLLABLE IEUNG O CIEUC - 0x9EB1: 0xC63C, //HANGUL SYLLABLE IEUNG O KHIEUKH - 0x9EB2: 0xC63D, //HANGUL SYLLABLE IEUNG O THIEUTH - 0x9EB3: 0xC63E, //HANGUL SYLLABLE IEUNG O PHIEUPH - 0x9EB4: 0xC63F, //HANGUL SYLLABLE IEUNG O HIEUH - 0x9EB5: 0xC642, //HANGUL SYLLABLE IEUNG WA SSANGKIYEOK - 0x9EB6: 0xC643, //HANGUL SYLLABLE IEUNG WA KIYEOKSIOS - 0x9EB7: 0xC645, //HANGUL SYLLABLE IEUNG WA NIEUNCIEUC - 0x9EB8: 0xC646, //HANGUL SYLLABLE IEUNG WA NIEUNHIEUH - 0x9EB9: 0xC647, //HANGUL SYLLABLE IEUNG WA TIKEUT - 0x9EBA: 0xC649, //HANGUL SYLLABLE IEUNG WA RIEULKIYEOK - 0x9EBB: 0xC64A, //HANGUL SYLLABLE IEUNG WA RIEULMIEUM - 0x9EBC: 0xC64B, //HANGUL SYLLABLE IEUNG WA RIEULPIEUP - 0x9EBD: 0xC64C, //HANGUL SYLLABLE IEUNG WA RIEULSIOS - 0x9EBE: 0xC64D, //HANGUL SYLLABLE IEUNG WA RIEULTHIEUTH - 0x9EBF: 0xC64E, //HANGUL SYLLABLE IEUNG WA RIEULPHIEUPH - 0x9EC0: 0xC64F, //HANGUL SYLLABLE IEUNG WA RIEULHIEUH - 0x9EC1: 0xC652, //HANGUL SYLLABLE IEUNG WA PIEUPSIOS - 0x9EC2: 0xC656, //HANGUL SYLLABLE IEUNG WA CIEUC - 0x9EC3: 0xC657, //HANGUL SYLLABLE IEUNG WA CHIEUCH - 0x9EC4: 0xC658, //HANGUL SYLLABLE IEUNG WA KHIEUKH - 0x9EC5: 0xC659, //HANGUL SYLLABLE IEUNG WA THIEUTH - 0x9EC6: 0xC65A, //HANGUL SYLLABLE IEUNG WA PHIEUPH - 0x9EC7: 0xC65B, //HANGUL SYLLABLE IEUNG WA HIEUH - 0x9EC8: 0xC65E, //HANGUL SYLLABLE IEUNG WAE SSANGKIYEOK - 0x9EC9: 0xC65F, //HANGUL SYLLABLE IEUNG WAE KIYEOKSIOS - 0x9ECA: 0xC661, //HANGUL SYLLABLE IEUNG WAE NIEUNCIEUC - 0x9ECB: 0xC662, //HANGUL SYLLABLE IEUNG WAE NIEUNHIEUH - 0x9ECC: 0xC663, //HANGUL SYLLABLE IEUNG WAE TIKEUT - 0x9ECD: 0xC664, //HANGUL SYLLABLE IEUNG WAE RIEUL - 0x9ECE: 0xC665, //HANGUL SYLLABLE IEUNG WAE RIEULKIYEOK - 0x9ECF: 0xC666, //HANGUL SYLLABLE IEUNG WAE RIEULMIEUM - 0x9ED0: 0xC667, //HANGUL SYLLABLE IEUNG WAE RIEULPIEUP - 0x9ED1: 0xC668, //HANGUL SYLLABLE IEUNG WAE RIEULSIOS - 0x9ED2: 0xC669, //HANGUL SYLLABLE IEUNG WAE RIEULTHIEUTH - 0x9ED3: 0xC66A, //HANGUL SYLLABLE IEUNG WAE RIEULPHIEUPH - 0x9ED4: 0xC66B, //HANGUL SYLLABLE IEUNG WAE RIEULHIEUH - 0x9ED5: 0xC66D, //HANGUL SYLLABLE IEUNG WAE PIEUP - 0x9ED6: 0xC66E, //HANGUL SYLLABLE IEUNG WAE PIEUPSIOS - 0x9ED7: 0xC670, //HANGUL SYLLABLE IEUNG WAE SSANGSIOS - 0x9ED8: 0xC672, //HANGUL SYLLABLE IEUNG WAE CIEUC - 0x9ED9: 0xC673, //HANGUL SYLLABLE IEUNG WAE CHIEUCH - 0x9EDA: 0xC674, //HANGUL SYLLABLE IEUNG WAE KHIEUKH - 0x9EDB: 0xC675, //HANGUL SYLLABLE IEUNG WAE THIEUTH - 0x9EDC: 0xC676, //HANGUL SYLLABLE IEUNG WAE PHIEUPH - 0x9EDD: 0xC677, //HANGUL SYLLABLE IEUNG WAE HIEUH - 0x9EDE: 0xC67A, //HANGUL SYLLABLE IEUNG OE SSANGKIYEOK - 0x9EDF: 0xC67B, //HANGUL SYLLABLE IEUNG OE KIYEOKSIOS - 0x9EE0: 0xC67D, //HANGUL SYLLABLE IEUNG OE NIEUNCIEUC - 0x9EE1: 0xC67E, //HANGUL SYLLABLE IEUNG OE NIEUNHIEUH - 0x9EE2: 0xC67F, //HANGUL SYLLABLE IEUNG OE TIKEUT - 0x9EE3: 0xC681, //HANGUL SYLLABLE IEUNG OE RIEULKIYEOK - 0x9EE4: 0xC682, //HANGUL SYLLABLE IEUNG OE RIEULMIEUM - 0x9EE5: 0xC683, //HANGUL SYLLABLE IEUNG OE RIEULPIEUP - 0x9EE6: 0xC684, //HANGUL SYLLABLE IEUNG OE RIEULSIOS - 0x9EE7: 0xC685, //HANGUL SYLLABLE IEUNG OE RIEULTHIEUTH - 0x9EE8: 0xC686, //HANGUL SYLLABLE IEUNG OE RIEULPHIEUPH - 0x9EE9: 0xC687, //HANGUL SYLLABLE IEUNG OE RIEULHIEUH - 0x9EEA: 0xC68A, //HANGUL SYLLABLE IEUNG OE PIEUPSIOS - 0x9EEB: 0xC68C, //HANGUL SYLLABLE IEUNG OE SSANGSIOS - 0x9EEC: 0xC68E, //HANGUL SYLLABLE IEUNG OE CIEUC - 0x9EED: 0xC68F, //HANGUL SYLLABLE IEUNG OE CHIEUCH - 0x9EEE: 0xC690, //HANGUL SYLLABLE IEUNG OE KHIEUKH - 0x9EEF: 0xC691, //HANGUL SYLLABLE IEUNG OE THIEUTH - 0x9EF0: 0xC692, //HANGUL SYLLABLE IEUNG OE PHIEUPH - 0x9EF1: 0xC693, //HANGUL SYLLABLE IEUNG OE HIEUH - 0x9EF2: 0xC696, //HANGUL SYLLABLE IEUNG YO SSANGKIYEOK - 0x9EF3: 0xC697, //HANGUL SYLLABLE IEUNG YO KIYEOKSIOS - 0x9EF4: 0xC699, //HANGUL SYLLABLE IEUNG YO NIEUNCIEUC - 0x9EF5: 0xC69A, //HANGUL SYLLABLE IEUNG YO NIEUNHIEUH - 0x9EF6: 0xC69B, //HANGUL SYLLABLE IEUNG YO TIKEUT - 0x9EF7: 0xC69D, //HANGUL SYLLABLE IEUNG YO RIEULKIYEOK - 0x9EF8: 0xC69E, //HANGUL SYLLABLE IEUNG YO RIEULMIEUM - 0x9EF9: 0xC69F, //HANGUL SYLLABLE IEUNG YO RIEULPIEUP - 0x9EFA: 0xC6A0, //HANGUL SYLLABLE IEUNG YO RIEULSIOS - 0x9EFB: 0xC6A1, //HANGUL SYLLABLE IEUNG YO RIEULTHIEUTH - 0x9EFC: 0xC6A2, //HANGUL SYLLABLE IEUNG YO RIEULPHIEUPH - 0x9EFD: 0xC6A3, //HANGUL SYLLABLE IEUNG YO RIEULHIEUH - 0x9EFE: 0xC6A6, //HANGUL SYLLABLE IEUNG YO PIEUPSIOS - 0x9F41: 0xC6A8, //HANGUL SYLLABLE IEUNG YO SSANGSIOS - 0x9F42: 0xC6AA, //HANGUL SYLLABLE IEUNG YO CIEUC - 0x9F43: 0xC6AB, //HANGUL SYLLABLE IEUNG YO CHIEUCH - 0x9F44: 0xC6AC, //HANGUL SYLLABLE IEUNG YO KHIEUKH - 0x9F45: 0xC6AD, //HANGUL SYLLABLE IEUNG YO THIEUTH - 0x9F46: 0xC6AE, //HANGUL SYLLABLE IEUNG YO PHIEUPH - 0x9F47: 0xC6AF, //HANGUL SYLLABLE IEUNG YO HIEUH - 0x9F48: 0xC6B2, //HANGUL SYLLABLE IEUNG U SSANGKIYEOK - 0x9F49: 0xC6B3, //HANGUL SYLLABLE IEUNG U KIYEOKSIOS - 0x9F4A: 0xC6B5, //HANGUL SYLLABLE IEUNG U NIEUNCIEUC - 0x9F4B: 0xC6B6, //HANGUL SYLLABLE IEUNG U NIEUNHIEUH - 0x9F4C: 0xC6B7, //HANGUL SYLLABLE IEUNG U TIKEUT - 0x9F4D: 0xC6BB, //HANGUL SYLLABLE IEUNG U RIEULPIEUP - 0x9F4E: 0xC6BC, //HANGUL SYLLABLE IEUNG U RIEULSIOS - 0x9F4F: 0xC6BD, //HANGUL SYLLABLE IEUNG U RIEULTHIEUTH - 0x9F50: 0xC6BE, //HANGUL SYLLABLE IEUNG U RIEULPHIEUPH - 0x9F51: 0xC6BF, //HANGUL SYLLABLE IEUNG U RIEULHIEUH - 0x9F52: 0xC6C2, //HANGUL SYLLABLE IEUNG U PIEUPSIOS - 0x9F53: 0xC6C4, //HANGUL SYLLABLE IEUNG U SSANGSIOS - 0x9F54: 0xC6C6, //HANGUL SYLLABLE IEUNG U CIEUC - 0x9F55: 0xC6C7, //HANGUL SYLLABLE IEUNG U CHIEUCH - 0x9F56: 0xC6C8, //HANGUL SYLLABLE IEUNG U KHIEUKH - 0x9F57: 0xC6C9, //HANGUL SYLLABLE IEUNG U THIEUTH - 0x9F58: 0xC6CA, //HANGUL SYLLABLE IEUNG U PHIEUPH - 0x9F59: 0xC6CB, //HANGUL SYLLABLE IEUNG U HIEUH - 0x9F5A: 0xC6CE, //HANGUL SYLLABLE IEUNG WEO SSANGKIYEOK - 0x9F61: 0xC6CF, //HANGUL SYLLABLE IEUNG WEO KIYEOKSIOS - 0x9F62: 0xC6D1, //HANGUL SYLLABLE IEUNG WEO NIEUNCIEUC - 0x9F63: 0xC6D2, //HANGUL SYLLABLE IEUNG WEO NIEUNHIEUH - 0x9F64: 0xC6D3, //HANGUL SYLLABLE IEUNG WEO TIKEUT - 0x9F65: 0xC6D5, //HANGUL SYLLABLE IEUNG WEO RIEULKIYEOK - 0x9F66: 0xC6D6, //HANGUL SYLLABLE IEUNG WEO RIEULMIEUM - 0x9F67: 0xC6D7, //HANGUL SYLLABLE IEUNG WEO RIEULPIEUP - 0x9F68: 0xC6D8, //HANGUL SYLLABLE IEUNG WEO RIEULSIOS - 0x9F69: 0xC6D9, //HANGUL SYLLABLE IEUNG WEO RIEULTHIEUTH - 0x9F6A: 0xC6DA, //HANGUL SYLLABLE IEUNG WEO RIEULPHIEUPH - 0x9F6B: 0xC6DB, //HANGUL SYLLABLE IEUNG WEO RIEULHIEUH - 0x9F6C: 0xC6DE, //HANGUL SYLLABLE IEUNG WEO PIEUPSIOS - 0x9F6D: 0xC6DF, //HANGUL SYLLABLE IEUNG WEO SIOS - 0x9F6E: 0xC6E2, //HANGUL SYLLABLE IEUNG WEO CIEUC - 0x9F6F: 0xC6E3, //HANGUL SYLLABLE IEUNG WEO CHIEUCH - 0x9F70: 0xC6E4, //HANGUL SYLLABLE IEUNG WEO KHIEUKH - 0x9F71: 0xC6E5, //HANGUL SYLLABLE IEUNG WEO THIEUTH - 0x9F72: 0xC6E6, //HANGUL SYLLABLE IEUNG WEO PHIEUPH - 0x9F73: 0xC6E7, //HANGUL SYLLABLE IEUNG WEO HIEUH - 0x9F74: 0xC6EA, //HANGUL SYLLABLE IEUNG WE SSANGKIYEOK - 0x9F75: 0xC6EB, //HANGUL SYLLABLE IEUNG WE KIYEOKSIOS - 0x9F76: 0xC6ED, //HANGUL SYLLABLE IEUNG WE NIEUNCIEUC - 0x9F77: 0xC6EE, //HANGUL SYLLABLE IEUNG WE NIEUNHIEUH - 0x9F78: 0xC6EF, //HANGUL SYLLABLE IEUNG WE TIKEUT - 0x9F79: 0xC6F1, //HANGUL SYLLABLE IEUNG WE RIEULKIYEOK - 0x9F7A: 0xC6F2, //HANGUL SYLLABLE IEUNG WE RIEULMIEUM - 0x9F81: 0xC6F3, //HANGUL SYLLABLE IEUNG WE RIEULPIEUP - 0x9F82: 0xC6F4, //HANGUL SYLLABLE IEUNG WE RIEULSIOS - 0x9F83: 0xC6F5, //HANGUL SYLLABLE IEUNG WE RIEULTHIEUTH - 0x9F84: 0xC6F6, //HANGUL SYLLABLE IEUNG WE RIEULPHIEUPH - 0x9F85: 0xC6F7, //HANGUL SYLLABLE IEUNG WE RIEULHIEUH - 0x9F86: 0xC6FA, //HANGUL SYLLABLE IEUNG WE PIEUPSIOS - 0x9F87: 0xC6FB, //HANGUL SYLLABLE IEUNG WE SIOS - 0x9F88: 0xC6FC, //HANGUL SYLLABLE IEUNG WE SSANGSIOS - 0x9F89: 0xC6FE, //HANGUL SYLLABLE IEUNG WE CIEUC - 0x9F8A: 0xC6FF, //HANGUL SYLLABLE IEUNG WE CHIEUCH - 0x9F8B: 0xC700, //HANGUL SYLLABLE IEUNG WE KHIEUKH - 0x9F8C: 0xC701, //HANGUL SYLLABLE IEUNG WE THIEUTH - 0x9F8D: 0xC702, //HANGUL SYLLABLE IEUNG WE PHIEUPH - 0x9F8E: 0xC703, //HANGUL SYLLABLE IEUNG WE HIEUH - 0x9F8F: 0xC706, //HANGUL SYLLABLE IEUNG WI SSANGKIYEOK - 0x9F90: 0xC707, //HANGUL SYLLABLE IEUNG WI KIYEOKSIOS - 0x9F91: 0xC709, //HANGUL SYLLABLE IEUNG WI NIEUNCIEUC - 0x9F92: 0xC70A, //HANGUL SYLLABLE IEUNG WI NIEUNHIEUH - 0x9F93: 0xC70B, //HANGUL SYLLABLE IEUNG WI TIKEUT - 0x9F94: 0xC70D, //HANGUL SYLLABLE IEUNG WI RIEULKIYEOK - 0x9F95: 0xC70E, //HANGUL SYLLABLE IEUNG WI RIEULMIEUM - 0x9F96: 0xC70F, //HANGUL SYLLABLE IEUNG WI RIEULPIEUP - 0x9F97: 0xC710, //HANGUL SYLLABLE IEUNG WI RIEULSIOS - 0x9F98: 0xC711, //HANGUL SYLLABLE IEUNG WI RIEULTHIEUTH - 0x9F99: 0xC712, //HANGUL SYLLABLE IEUNG WI RIEULPHIEUPH - 0x9F9A: 0xC713, //HANGUL SYLLABLE IEUNG WI RIEULHIEUH - 0x9F9B: 0xC716, //HANGUL SYLLABLE IEUNG WI PIEUPSIOS - 0x9F9C: 0xC718, //HANGUL SYLLABLE IEUNG WI SSANGSIOS - 0x9F9D: 0xC71A, //HANGUL SYLLABLE IEUNG WI CIEUC - 0x9F9E: 0xC71B, //HANGUL SYLLABLE IEUNG WI CHIEUCH - 0x9F9F: 0xC71C, //HANGUL SYLLABLE IEUNG WI KHIEUKH - 0x9FA0: 0xC71D, //HANGUL SYLLABLE IEUNG WI THIEUTH - 0x9FA1: 0xC71E, //HANGUL SYLLABLE IEUNG WI PHIEUPH - 0x9FA2: 0xC71F, //HANGUL SYLLABLE IEUNG WI HIEUH - 0x9FA3: 0xC722, //HANGUL SYLLABLE IEUNG YU SSANGKIYEOK - 0x9FA4: 0xC723, //HANGUL SYLLABLE IEUNG YU KIYEOKSIOS - 0x9FA5: 0xC725, //HANGUL SYLLABLE IEUNG YU NIEUNCIEUC - 0x9FA6: 0xC726, //HANGUL SYLLABLE IEUNG YU NIEUNHIEUH - 0x9FA7: 0xC727, //HANGUL SYLLABLE IEUNG YU TIKEUT - 0x9FA8: 0xC729, //HANGUL SYLLABLE IEUNG YU RIEULKIYEOK - 0x9FA9: 0xC72A, //HANGUL SYLLABLE IEUNG YU RIEULMIEUM - 0x9FAA: 0xC72B, //HANGUL SYLLABLE IEUNG YU RIEULPIEUP - 0x9FAB: 0xC72C, //HANGUL SYLLABLE IEUNG YU RIEULSIOS - 0x9FAC: 0xC72D, //HANGUL SYLLABLE IEUNG YU RIEULTHIEUTH - 0x9FAD: 0xC72E, //HANGUL SYLLABLE IEUNG YU RIEULPHIEUPH - 0x9FAE: 0xC72F, //HANGUL SYLLABLE IEUNG YU RIEULHIEUH - 0x9FAF: 0xC732, //HANGUL SYLLABLE IEUNG YU PIEUPSIOS - 0x9FB0: 0xC734, //HANGUL SYLLABLE IEUNG YU SSANGSIOS - 0x9FB1: 0xC736, //HANGUL SYLLABLE IEUNG YU CIEUC - 0x9FB2: 0xC738, //HANGUL SYLLABLE IEUNG YU KHIEUKH - 0x9FB3: 0xC739, //HANGUL SYLLABLE IEUNG YU THIEUTH - 0x9FB4: 0xC73A, //HANGUL SYLLABLE IEUNG YU PHIEUPH - 0x9FB5: 0xC73B, //HANGUL SYLLABLE IEUNG YU HIEUH - 0x9FB6: 0xC73E, //HANGUL SYLLABLE IEUNG EU SSANGKIYEOK - 0x9FB7: 0xC73F, //HANGUL SYLLABLE IEUNG EU KIYEOKSIOS - 0x9FB8: 0xC741, //HANGUL SYLLABLE IEUNG EU NIEUNCIEUC - 0x9FB9: 0xC742, //HANGUL SYLLABLE IEUNG EU NIEUNHIEUH - 0x9FBA: 0xC743, //HANGUL SYLLABLE IEUNG EU TIKEUT - 0x9FBB: 0xC745, //HANGUL SYLLABLE IEUNG EU RIEULKIYEOK - 0x9FBC: 0xC746, //HANGUL SYLLABLE IEUNG EU RIEULMIEUM - 0x9FBD: 0xC747, //HANGUL SYLLABLE IEUNG EU RIEULPIEUP - 0x9FBE: 0xC748, //HANGUL SYLLABLE IEUNG EU RIEULSIOS - 0x9FBF: 0xC749, //HANGUL SYLLABLE IEUNG EU RIEULTHIEUTH - 0x9FC0: 0xC74B, //HANGUL SYLLABLE IEUNG EU RIEULHIEUH - 0x9FC1: 0xC74E, //HANGUL SYLLABLE IEUNG EU PIEUPSIOS - 0x9FC2: 0xC750, //HANGUL SYLLABLE IEUNG EU SSANGSIOS - 0x9FC3: 0xC759, //HANGUL SYLLABLE IEUNG YI KIYEOK - 0x9FC4: 0xC75A, //HANGUL SYLLABLE IEUNG YI SSANGKIYEOK - 0x9FC5: 0xC75B, //HANGUL SYLLABLE IEUNG YI KIYEOKSIOS - 0x9FC6: 0xC75D, //HANGUL SYLLABLE IEUNG YI NIEUNCIEUC - 0x9FC7: 0xC75E, //HANGUL SYLLABLE IEUNG YI NIEUNHIEUH - 0x9FC8: 0xC75F, //HANGUL SYLLABLE IEUNG YI TIKEUT - 0x9FC9: 0xC761, //HANGUL SYLLABLE IEUNG YI RIEULKIYEOK - 0x9FCA: 0xC762, //HANGUL SYLLABLE IEUNG YI RIEULMIEUM - 0x9FCB: 0xC763, //HANGUL SYLLABLE IEUNG YI RIEULPIEUP - 0x9FCC: 0xC764, //HANGUL SYLLABLE IEUNG YI RIEULSIOS - 0x9FCD: 0xC765, //HANGUL SYLLABLE IEUNG YI RIEULTHIEUTH - 0x9FCE: 0xC766, //HANGUL SYLLABLE IEUNG YI RIEULPHIEUPH - 0x9FCF: 0xC767, //HANGUL SYLLABLE IEUNG YI RIEULHIEUH - 0x9FD0: 0xC769, //HANGUL SYLLABLE IEUNG YI PIEUP - 0x9FD1: 0xC76A, //HANGUL SYLLABLE IEUNG YI PIEUPSIOS - 0x9FD2: 0xC76C, //HANGUL SYLLABLE IEUNG YI SSANGSIOS - 0x9FD3: 0xC76D, //HANGUL SYLLABLE IEUNG YI IEUNG - 0x9FD4: 0xC76E, //HANGUL SYLLABLE IEUNG YI CIEUC - 0x9FD5: 0xC76F, //HANGUL SYLLABLE IEUNG YI CHIEUCH - 0x9FD6: 0xC770, //HANGUL SYLLABLE IEUNG YI KHIEUKH - 0x9FD7: 0xC771, //HANGUL SYLLABLE IEUNG YI THIEUTH - 0x9FD8: 0xC772, //HANGUL SYLLABLE IEUNG YI PHIEUPH - 0x9FD9: 0xC773, //HANGUL SYLLABLE IEUNG YI HIEUH - 0x9FDA: 0xC776, //HANGUL SYLLABLE IEUNG I SSANGKIYEOK - 0x9FDB: 0xC777, //HANGUL SYLLABLE IEUNG I KIYEOKSIOS - 0x9FDC: 0xC779, //HANGUL SYLLABLE IEUNG I NIEUNCIEUC - 0x9FDD: 0xC77A, //HANGUL SYLLABLE IEUNG I NIEUNHIEUH - 0x9FDE: 0xC77B, //HANGUL SYLLABLE IEUNG I TIKEUT - 0x9FDF: 0xC77F, //HANGUL SYLLABLE IEUNG I RIEULPIEUP - 0x9FE0: 0xC780, //HANGUL SYLLABLE IEUNG I RIEULSIOS - 0x9FE1: 0xC781, //HANGUL SYLLABLE IEUNG I RIEULTHIEUTH - 0x9FE2: 0xC782, //HANGUL SYLLABLE IEUNG I RIEULPHIEUPH - 0x9FE3: 0xC786, //HANGUL SYLLABLE IEUNG I PIEUPSIOS - 0x9FE4: 0xC78B, //HANGUL SYLLABLE IEUNG I CHIEUCH - 0x9FE5: 0xC78C, //HANGUL SYLLABLE IEUNG I KHIEUKH - 0x9FE6: 0xC78D, //HANGUL SYLLABLE IEUNG I THIEUTH - 0x9FE7: 0xC78F, //HANGUL SYLLABLE IEUNG I HIEUH - 0x9FE8: 0xC792, //HANGUL SYLLABLE CIEUC A SSANGKIYEOK - 0x9FE9: 0xC793, //HANGUL SYLLABLE CIEUC A KIYEOKSIOS - 0x9FEA: 0xC795, //HANGUL SYLLABLE CIEUC A NIEUNCIEUC - 0x9FEB: 0xC799, //HANGUL SYLLABLE CIEUC A RIEULKIYEOK - 0x9FEC: 0xC79B, //HANGUL SYLLABLE CIEUC A RIEULPIEUP - 0x9FED: 0xC79C, //HANGUL SYLLABLE CIEUC A RIEULSIOS - 0x9FEE: 0xC79D, //HANGUL SYLLABLE CIEUC A RIEULTHIEUTH - 0x9FEF: 0xC79E, //HANGUL SYLLABLE CIEUC A RIEULPHIEUPH - 0x9FF0: 0xC79F, //HANGUL SYLLABLE CIEUC A RIEULHIEUH - 0x9FF1: 0xC7A2, //HANGUL SYLLABLE CIEUC A PIEUPSIOS - 0x9FF2: 0xC7A7, //HANGUL SYLLABLE CIEUC A CHIEUCH - 0x9FF3: 0xC7A8, //HANGUL SYLLABLE CIEUC A KHIEUKH - 0x9FF4: 0xC7A9, //HANGUL SYLLABLE CIEUC A THIEUTH - 0x9FF5: 0xC7AA, //HANGUL SYLLABLE CIEUC A PHIEUPH - 0x9FF6: 0xC7AB, //HANGUL SYLLABLE CIEUC A HIEUH - 0x9FF7: 0xC7AE, //HANGUL SYLLABLE CIEUC AE SSANGKIYEOK - 0x9FF8: 0xC7AF, //HANGUL SYLLABLE CIEUC AE KIYEOKSIOS - 0x9FF9: 0xC7B1, //HANGUL SYLLABLE CIEUC AE NIEUNCIEUC - 0x9FFA: 0xC7B2, //HANGUL SYLLABLE CIEUC AE NIEUNHIEUH - 0x9FFB: 0xC7B3, //HANGUL SYLLABLE CIEUC AE TIKEUT - 0x9FFC: 0xC7B5, //HANGUL SYLLABLE CIEUC AE RIEULKIYEOK - 0x9FFD: 0xC7B6, //HANGUL SYLLABLE CIEUC AE RIEULMIEUM - 0x9FFE: 0xC7B7, //HANGUL SYLLABLE CIEUC AE RIEULPIEUP - 0xA041: 0xC7B8, //HANGUL SYLLABLE CIEUC AE RIEULSIOS - 0xA042: 0xC7B9, //HANGUL SYLLABLE CIEUC AE RIEULTHIEUTH - 0xA043: 0xC7BA, //HANGUL SYLLABLE CIEUC AE RIEULPHIEUPH - 0xA044: 0xC7BB, //HANGUL SYLLABLE CIEUC AE RIEULHIEUH - 0xA045: 0xC7BE, //HANGUL SYLLABLE CIEUC AE PIEUPSIOS - 0xA046: 0xC7C2, //HANGUL SYLLABLE CIEUC AE CIEUC - 0xA047: 0xC7C3, //HANGUL SYLLABLE CIEUC AE CHIEUCH - 0xA048: 0xC7C4, //HANGUL SYLLABLE CIEUC AE KHIEUKH - 0xA049: 0xC7C5, //HANGUL SYLLABLE CIEUC AE THIEUTH - 0xA04A: 0xC7C6, //HANGUL SYLLABLE CIEUC AE PHIEUPH - 0xA04B: 0xC7C7, //HANGUL SYLLABLE CIEUC AE HIEUH - 0xA04C: 0xC7CA, //HANGUL SYLLABLE CIEUC YA SSANGKIYEOK - 0xA04D: 0xC7CB, //HANGUL SYLLABLE CIEUC YA KIYEOKSIOS - 0xA04E: 0xC7CD, //HANGUL SYLLABLE CIEUC YA NIEUNCIEUC - 0xA04F: 0xC7CF, //HANGUL SYLLABLE CIEUC YA TIKEUT - 0xA050: 0xC7D1, //HANGUL SYLLABLE CIEUC YA RIEULKIYEOK - 0xA051: 0xC7D2, //HANGUL SYLLABLE CIEUC YA RIEULMIEUM - 0xA052: 0xC7D3, //HANGUL SYLLABLE CIEUC YA RIEULPIEUP - 0xA053: 0xC7D4, //HANGUL SYLLABLE CIEUC YA RIEULSIOS - 0xA054: 0xC7D5, //HANGUL SYLLABLE CIEUC YA RIEULTHIEUTH - 0xA055: 0xC7D6, //HANGUL SYLLABLE CIEUC YA RIEULPHIEUPH - 0xA056: 0xC7D7, //HANGUL SYLLABLE CIEUC YA RIEULHIEUH - 0xA057: 0xC7D9, //HANGUL SYLLABLE CIEUC YA PIEUP - 0xA058: 0xC7DA, //HANGUL SYLLABLE CIEUC YA PIEUPSIOS - 0xA059: 0xC7DB, //HANGUL SYLLABLE CIEUC YA SIOS - 0xA05A: 0xC7DC, //HANGUL SYLLABLE CIEUC YA SSANGSIOS - 0xA061: 0xC7DE, //HANGUL SYLLABLE CIEUC YA CIEUC - 0xA062: 0xC7DF, //HANGUL SYLLABLE CIEUC YA CHIEUCH - 0xA063: 0xC7E0, //HANGUL SYLLABLE CIEUC YA KHIEUKH - 0xA064: 0xC7E1, //HANGUL SYLLABLE CIEUC YA THIEUTH - 0xA065: 0xC7E2, //HANGUL SYLLABLE CIEUC YA PHIEUPH - 0xA066: 0xC7E3, //HANGUL SYLLABLE CIEUC YA HIEUH - 0xA067: 0xC7E5, //HANGUL SYLLABLE CIEUC YAE KIYEOK - 0xA068: 0xC7E6, //HANGUL SYLLABLE CIEUC YAE SSANGKIYEOK - 0xA069: 0xC7E7, //HANGUL SYLLABLE CIEUC YAE KIYEOKSIOS - 0xA06A: 0xC7E9, //HANGUL SYLLABLE CIEUC YAE NIEUNCIEUC - 0xA06B: 0xC7EA, //HANGUL SYLLABLE CIEUC YAE NIEUNHIEUH - 0xA06C: 0xC7EB, //HANGUL SYLLABLE CIEUC YAE TIKEUT - 0xA06D: 0xC7ED, //HANGUL SYLLABLE CIEUC YAE RIEULKIYEOK - 0xA06E: 0xC7EE, //HANGUL SYLLABLE CIEUC YAE RIEULMIEUM - 0xA06F: 0xC7EF, //HANGUL SYLLABLE CIEUC YAE RIEULPIEUP - 0xA070: 0xC7F0, //HANGUL SYLLABLE CIEUC YAE RIEULSIOS - 0xA071: 0xC7F1, //HANGUL SYLLABLE CIEUC YAE RIEULTHIEUTH - 0xA072: 0xC7F2, //HANGUL SYLLABLE CIEUC YAE RIEULPHIEUPH - 0xA073: 0xC7F3, //HANGUL SYLLABLE CIEUC YAE RIEULHIEUH - 0xA074: 0xC7F4, //HANGUL SYLLABLE CIEUC YAE MIEUM - 0xA075: 0xC7F5, //HANGUL SYLLABLE CIEUC YAE PIEUP - 0xA076: 0xC7F6, //HANGUL SYLLABLE CIEUC YAE PIEUPSIOS - 0xA077: 0xC7F7, //HANGUL SYLLABLE CIEUC YAE SIOS - 0xA078: 0xC7F8, //HANGUL SYLLABLE CIEUC YAE SSANGSIOS - 0xA079: 0xC7F9, //HANGUL SYLLABLE CIEUC YAE IEUNG - 0xA07A: 0xC7FA, //HANGUL SYLLABLE CIEUC YAE CIEUC - 0xA081: 0xC7FB, //HANGUL SYLLABLE CIEUC YAE CHIEUCH - 0xA082: 0xC7FC, //HANGUL SYLLABLE CIEUC YAE KHIEUKH - 0xA083: 0xC7FD, //HANGUL SYLLABLE CIEUC YAE THIEUTH - 0xA084: 0xC7FE, //HANGUL SYLLABLE CIEUC YAE PHIEUPH - 0xA085: 0xC7FF, //HANGUL SYLLABLE CIEUC YAE HIEUH - 0xA086: 0xC802, //HANGUL SYLLABLE CIEUC EO SSANGKIYEOK - 0xA087: 0xC803, //HANGUL SYLLABLE CIEUC EO KIYEOKSIOS - 0xA088: 0xC805, //HANGUL SYLLABLE CIEUC EO NIEUNCIEUC - 0xA089: 0xC806, //HANGUL SYLLABLE CIEUC EO NIEUNHIEUH - 0xA08A: 0xC807, //HANGUL SYLLABLE CIEUC EO TIKEUT - 0xA08B: 0xC809, //HANGUL SYLLABLE CIEUC EO RIEULKIYEOK - 0xA08C: 0xC80B, //HANGUL SYLLABLE CIEUC EO RIEULPIEUP - 0xA08D: 0xC80C, //HANGUL SYLLABLE CIEUC EO RIEULSIOS - 0xA08E: 0xC80D, //HANGUL SYLLABLE CIEUC EO RIEULTHIEUTH - 0xA08F: 0xC80E, //HANGUL SYLLABLE CIEUC EO RIEULPHIEUPH - 0xA090: 0xC80F, //HANGUL SYLLABLE CIEUC EO RIEULHIEUH - 0xA091: 0xC812, //HANGUL SYLLABLE CIEUC EO PIEUPSIOS - 0xA092: 0xC814, //HANGUL SYLLABLE CIEUC EO SSANGSIOS - 0xA093: 0xC817, //HANGUL SYLLABLE CIEUC EO CHIEUCH - 0xA094: 0xC818, //HANGUL SYLLABLE CIEUC EO KHIEUKH - 0xA095: 0xC819, //HANGUL SYLLABLE CIEUC EO THIEUTH - 0xA096: 0xC81A, //HANGUL SYLLABLE CIEUC EO PHIEUPH - 0xA097: 0xC81B, //HANGUL SYLLABLE CIEUC EO HIEUH - 0xA098: 0xC81E, //HANGUL SYLLABLE CIEUC E SSANGKIYEOK - 0xA099: 0xC81F, //HANGUL SYLLABLE CIEUC E KIYEOKSIOS - 0xA09A: 0xC821, //HANGUL SYLLABLE CIEUC E NIEUNCIEUC - 0xA09B: 0xC822, //HANGUL SYLLABLE CIEUC E NIEUNHIEUH - 0xA09C: 0xC823, //HANGUL SYLLABLE CIEUC E TIKEUT - 0xA09D: 0xC825, //HANGUL SYLLABLE CIEUC E RIEULKIYEOK - 0xA09E: 0xC826, //HANGUL SYLLABLE CIEUC E RIEULMIEUM - 0xA09F: 0xC827, //HANGUL SYLLABLE CIEUC E RIEULPIEUP - 0xA0A0: 0xC828, //HANGUL SYLLABLE CIEUC E RIEULSIOS - 0xA0A1: 0xC829, //HANGUL SYLLABLE CIEUC E RIEULTHIEUTH - 0xA0A2: 0xC82A, //HANGUL SYLLABLE CIEUC E RIEULPHIEUPH - 0xA0A3: 0xC82B, //HANGUL SYLLABLE CIEUC E RIEULHIEUH - 0xA0A4: 0xC82E, //HANGUL SYLLABLE CIEUC E PIEUPSIOS - 0xA0A5: 0xC830, //HANGUL SYLLABLE CIEUC E SSANGSIOS - 0xA0A6: 0xC832, //HANGUL SYLLABLE CIEUC E CIEUC - 0xA0A7: 0xC833, //HANGUL SYLLABLE CIEUC E CHIEUCH - 0xA0A8: 0xC834, //HANGUL SYLLABLE CIEUC E KHIEUKH - 0xA0A9: 0xC835, //HANGUL SYLLABLE CIEUC E THIEUTH - 0xA0AA: 0xC836, //HANGUL SYLLABLE CIEUC E PHIEUPH - 0xA0AB: 0xC837, //HANGUL SYLLABLE CIEUC E HIEUH - 0xA0AC: 0xC839, //HANGUL SYLLABLE CIEUC YEO KIYEOK - 0xA0AD: 0xC83A, //HANGUL SYLLABLE CIEUC YEO SSANGKIYEOK - 0xA0AE: 0xC83B, //HANGUL SYLLABLE CIEUC YEO KIYEOKSIOS - 0xA0AF: 0xC83D, //HANGUL SYLLABLE CIEUC YEO NIEUNCIEUC - 0xA0B0: 0xC83E, //HANGUL SYLLABLE CIEUC YEO NIEUNHIEUH - 0xA0B1: 0xC83F, //HANGUL SYLLABLE CIEUC YEO TIKEUT - 0xA0B2: 0xC841, //HANGUL SYLLABLE CIEUC YEO RIEULKIYEOK - 0xA0B3: 0xC842, //HANGUL SYLLABLE CIEUC YEO RIEULMIEUM - 0xA0B4: 0xC843, //HANGUL SYLLABLE CIEUC YEO RIEULPIEUP - 0xA0B5: 0xC844, //HANGUL SYLLABLE CIEUC YEO RIEULSIOS - 0xA0B6: 0xC845, //HANGUL SYLLABLE CIEUC YEO RIEULTHIEUTH - 0xA0B7: 0xC846, //HANGUL SYLLABLE CIEUC YEO RIEULPHIEUPH - 0xA0B8: 0xC847, //HANGUL SYLLABLE CIEUC YEO RIEULHIEUH - 0xA0B9: 0xC84A, //HANGUL SYLLABLE CIEUC YEO PIEUPSIOS - 0xA0BA: 0xC84B, //HANGUL SYLLABLE CIEUC YEO SIOS - 0xA0BB: 0xC84E, //HANGUL SYLLABLE CIEUC YEO CIEUC - 0xA0BC: 0xC84F, //HANGUL SYLLABLE CIEUC YEO CHIEUCH - 0xA0BD: 0xC850, //HANGUL SYLLABLE CIEUC YEO KHIEUKH - 0xA0BE: 0xC851, //HANGUL SYLLABLE CIEUC YEO THIEUTH - 0xA0BF: 0xC852, //HANGUL SYLLABLE CIEUC YEO PHIEUPH - 0xA0C0: 0xC853, //HANGUL SYLLABLE CIEUC YEO HIEUH - 0xA0C1: 0xC855, //HANGUL SYLLABLE CIEUC YE KIYEOK - 0xA0C2: 0xC856, //HANGUL SYLLABLE CIEUC YE SSANGKIYEOK - 0xA0C3: 0xC857, //HANGUL SYLLABLE CIEUC YE KIYEOKSIOS - 0xA0C4: 0xC858, //HANGUL SYLLABLE CIEUC YE NIEUN - 0xA0C5: 0xC859, //HANGUL SYLLABLE CIEUC YE NIEUNCIEUC - 0xA0C6: 0xC85A, //HANGUL SYLLABLE CIEUC YE NIEUNHIEUH - 0xA0C7: 0xC85B, //HANGUL SYLLABLE CIEUC YE TIKEUT - 0xA0C8: 0xC85C, //HANGUL SYLLABLE CIEUC YE RIEUL - 0xA0C9: 0xC85D, //HANGUL SYLLABLE CIEUC YE RIEULKIYEOK - 0xA0CA: 0xC85E, //HANGUL SYLLABLE CIEUC YE RIEULMIEUM - 0xA0CB: 0xC85F, //HANGUL SYLLABLE CIEUC YE RIEULPIEUP - 0xA0CC: 0xC860, //HANGUL SYLLABLE CIEUC YE RIEULSIOS - 0xA0CD: 0xC861, //HANGUL SYLLABLE CIEUC YE RIEULTHIEUTH - 0xA0CE: 0xC862, //HANGUL SYLLABLE CIEUC YE RIEULPHIEUPH - 0xA0CF: 0xC863, //HANGUL SYLLABLE CIEUC YE RIEULHIEUH - 0xA0D0: 0xC864, //HANGUL SYLLABLE CIEUC YE MIEUM - 0xA0D1: 0xC865, //HANGUL SYLLABLE CIEUC YE PIEUP - 0xA0D2: 0xC866, //HANGUL SYLLABLE CIEUC YE PIEUPSIOS - 0xA0D3: 0xC867, //HANGUL SYLLABLE CIEUC YE SIOS - 0xA0D4: 0xC868, //HANGUL SYLLABLE CIEUC YE SSANGSIOS - 0xA0D5: 0xC869, //HANGUL SYLLABLE CIEUC YE IEUNG - 0xA0D6: 0xC86A, //HANGUL SYLLABLE CIEUC YE CIEUC - 0xA0D7: 0xC86B, //HANGUL SYLLABLE CIEUC YE CHIEUCH - 0xA0D8: 0xC86C, //HANGUL SYLLABLE CIEUC YE KHIEUKH - 0xA0D9: 0xC86D, //HANGUL SYLLABLE CIEUC YE THIEUTH - 0xA0DA: 0xC86E, //HANGUL SYLLABLE CIEUC YE PHIEUPH - 0xA0DB: 0xC86F, //HANGUL SYLLABLE CIEUC YE HIEUH - 0xA0DC: 0xC872, //HANGUL SYLLABLE CIEUC O SSANGKIYEOK - 0xA0DD: 0xC873, //HANGUL SYLLABLE CIEUC O KIYEOKSIOS - 0xA0DE: 0xC875, //HANGUL SYLLABLE CIEUC O NIEUNCIEUC - 0xA0DF: 0xC876, //HANGUL SYLLABLE CIEUC O NIEUNHIEUH - 0xA0E0: 0xC877, //HANGUL SYLLABLE CIEUC O TIKEUT - 0xA0E1: 0xC879, //HANGUL SYLLABLE CIEUC O RIEULKIYEOK - 0xA0E2: 0xC87B, //HANGUL SYLLABLE CIEUC O RIEULPIEUP - 0xA0E3: 0xC87C, //HANGUL SYLLABLE CIEUC O RIEULSIOS - 0xA0E4: 0xC87D, //HANGUL SYLLABLE CIEUC O RIEULTHIEUTH - 0xA0E5: 0xC87E, //HANGUL SYLLABLE CIEUC O RIEULPHIEUPH - 0xA0E6: 0xC87F, //HANGUL SYLLABLE CIEUC O RIEULHIEUH - 0xA0E7: 0xC882, //HANGUL SYLLABLE CIEUC O PIEUPSIOS - 0xA0E8: 0xC884, //HANGUL SYLLABLE CIEUC O SSANGSIOS - 0xA0E9: 0xC888, //HANGUL SYLLABLE CIEUC O KHIEUKH - 0xA0EA: 0xC889, //HANGUL SYLLABLE CIEUC O THIEUTH - 0xA0EB: 0xC88A, //HANGUL SYLLABLE CIEUC O PHIEUPH - 0xA0EC: 0xC88E, //HANGUL SYLLABLE CIEUC WA SSANGKIYEOK - 0xA0ED: 0xC88F, //HANGUL SYLLABLE CIEUC WA KIYEOKSIOS - 0xA0EE: 0xC890, //HANGUL SYLLABLE CIEUC WA NIEUN - 0xA0EF: 0xC891, //HANGUL SYLLABLE CIEUC WA NIEUNCIEUC - 0xA0F0: 0xC892, //HANGUL SYLLABLE CIEUC WA NIEUNHIEUH - 0xA0F1: 0xC893, //HANGUL SYLLABLE CIEUC WA TIKEUT - 0xA0F2: 0xC895, //HANGUL SYLLABLE CIEUC WA RIEULKIYEOK - 0xA0F3: 0xC896, //HANGUL SYLLABLE CIEUC WA RIEULMIEUM - 0xA0F4: 0xC897, //HANGUL SYLLABLE CIEUC WA RIEULPIEUP - 0xA0F5: 0xC898, //HANGUL SYLLABLE CIEUC WA RIEULSIOS - 0xA0F6: 0xC899, //HANGUL SYLLABLE CIEUC WA RIEULTHIEUTH - 0xA0F7: 0xC89A, //HANGUL SYLLABLE CIEUC WA RIEULPHIEUPH - 0xA0F8: 0xC89B, //HANGUL SYLLABLE CIEUC WA RIEULHIEUH - 0xA0F9: 0xC89C, //HANGUL SYLLABLE CIEUC WA MIEUM - 0xA0FA: 0xC89E, //HANGUL SYLLABLE CIEUC WA PIEUPSIOS - 0xA0FB: 0xC8A0, //HANGUL SYLLABLE CIEUC WA SSANGSIOS - 0xA0FC: 0xC8A2, //HANGUL SYLLABLE CIEUC WA CIEUC - 0xA0FD: 0xC8A3, //HANGUL SYLLABLE CIEUC WA CHIEUCH - 0xA0FE: 0xC8A4, //HANGUL SYLLABLE CIEUC WA KHIEUKH - 0xA141: 0xC8A5, //HANGUL SYLLABLE CIEUC WA THIEUTH - 0xA142: 0xC8A6, //HANGUL SYLLABLE CIEUC WA PHIEUPH - 0xA143: 0xC8A7, //HANGUL SYLLABLE CIEUC WA HIEUH - 0xA144: 0xC8A9, //HANGUL SYLLABLE CIEUC WAE KIYEOK - 0xA145: 0xC8AA, //HANGUL SYLLABLE CIEUC WAE SSANGKIYEOK - 0xA146: 0xC8AB, //HANGUL SYLLABLE CIEUC WAE KIYEOKSIOS - 0xA147: 0xC8AC, //HANGUL SYLLABLE CIEUC WAE NIEUN - 0xA148: 0xC8AD, //HANGUL SYLLABLE CIEUC WAE NIEUNCIEUC - 0xA149: 0xC8AE, //HANGUL SYLLABLE CIEUC WAE NIEUNHIEUH - 0xA14A: 0xC8AF, //HANGUL SYLLABLE CIEUC WAE TIKEUT - 0xA14B: 0xC8B0, //HANGUL SYLLABLE CIEUC WAE RIEUL - 0xA14C: 0xC8B1, //HANGUL SYLLABLE CIEUC WAE RIEULKIYEOK - 0xA14D: 0xC8B2, //HANGUL SYLLABLE CIEUC WAE RIEULMIEUM - 0xA14E: 0xC8B3, //HANGUL SYLLABLE CIEUC WAE RIEULPIEUP - 0xA14F: 0xC8B4, //HANGUL SYLLABLE CIEUC WAE RIEULSIOS - 0xA150: 0xC8B5, //HANGUL SYLLABLE CIEUC WAE RIEULTHIEUTH - 0xA151: 0xC8B6, //HANGUL SYLLABLE CIEUC WAE RIEULPHIEUPH - 0xA152: 0xC8B7, //HANGUL SYLLABLE CIEUC WAE RIEULHIEUH - 0xA153: 0xC8B8, //HANGUL SYLLABLE CIEUC WAE MIEUM - 0xA154: 0xC8B9, //HANGUL SYLLABLE CIEUC WAE PIEUP - 0xA155: 0xC8BA, //HANGUL SYLLABLE CIEUC WAE PIEUPSIOS - 0xA156: 0xC8BB, //HANGUL SYLLABLE CIEUC WAE SIOS - 0xA157: 0xC8BE, //HANGUL SYLLABLE CIEUC WAE CIEUC - 0xA158: 0xC8BF, //HANGUL SYLLABLE CIEUC WAE CHIEUCH - 0xA159: 0xC8C0, //HANGUL SYLLABLE CIEUC WAE KHIEUKH - 0xA15A: 0xC8C1, //HANGUL SYLLABLE CIEUC WAE THIEUTH - 0xA161: 0xC8C2, //HANGUL SYLLABLE CIEUC WAE PHIEUPH - 0xA162: 0xC8C3, //HANGUL SYLLABLE CIEUC WAE HIEUH - 0xA163: 0xC8C5, //HANGUL SYLLABLE CIEUC OE KIYEOK - 0xA164: 0xC8C6, //HANGUL SYLLABLE CIEUC OE SSANGKIYEOK - 0xA165: 0xC8C7, //HANGUL SYLLABLE CIEUC OE KIYEOKSIOS - 0xA166: 0xC8C9, //HANGUL SYLLABLE CIEUC OE NIEUNCIEUC - 0xA167: 0xC8CA, //HANGUL SYLLABLE CIEUC OE NIEUNHIEUH - 0xA168: 0xC8CB, //HANGUL SYLLABLE CIEUC OE TIKEUT - 0xA169: 0xC8CD, //HANGUL SYLLABLE CIEUC OE RIEULKIYEOK - 0xA16A: 0xC8CE, //HANGUL SYLLABLE CIEUC OE RIEULMIEUM - 0xA16B: 0xC8CF, //HANGUL SYLLABLE CIEUC OE RIEULPIEUP - 0xA16C: 0xC8D0, //HANGUL SYLLABLE CIEUC OE RIEULSIOS - 0xA16D: 0xC8D1, //HANGUL SYLLABLE CIEUC OE RIEULTHIEUTH - 0xA16E: 0xC8D2, //HANGUL SYLLABLE CIEUC OE RIEULPHIEUPH - 0xA16F: 0xC8D3, //HANGUL SYLLABLE CIEUC OE RIEULHIEUH - 0xA170: 0xC8D6, //HANGUL SYLLABLE CIEUC OE PIEUPSIOS - 0xA171: 0xC8D8, //HANGUL SYLLABLE CIEUC OE SSANGSIOS - 0xA172: 0xC8DA, //HANGUL SYLLABLE CIEUC OE CIEUC - 0xA173: 0xC8DB, //HANGUL SYLLABLE CIEUC OE CHIEUCH - 0xA174: 0xC8DC, //HANGUL SYLLABLE CIEUC OE KHIEUKH - 0xA175: 0xC8DD, //HANGUL SYLLABLE CIEUC OE THIEUTH - 0xA176: 0xC8DE, //HANGUL SYLLABLE CIEUC OE PHIEUPH - 0xA177: 0xC8DF, //HANGUL SYLLABLE CIEUC OE HIEUH - 0xA178: 0xC8E2, //HANGUL SYLLABLE CIEUC YO SSANGKIYEOK - 0xA179: 0xC8E3, //HANGUL SYLLABLE CIEUC YO KIYEOKSIOS - 0xA17A: 0xC8E5, //HANGUL SYLLABLE CIEUC YO NIEUNCIEUC - 0xA181: 0xC8E6, //HANGUL SYLLABLE CIEUC YO NIEUNHIEUH - 0xA182: 0xC8E7, //HANGUL SYLLABLE CIEUC YO TIKEUT - 0xA183: 0xC8E8, //HANGUL SYLLABLE CIEUC YO RIEUL - 0xA184: 0xC8E9, //HANGUL SYLLABLE CIEUC YO RIEULKIYEOK - 0xA185: 0xC8EA, //HANGUL SYLLABLE CIEUC YO RIEULMIEUM - 0xA186: 0xC8EB, //HANGUL SYLLABLE CIEUC YO RIEULPIEUP - 0xA187: 0xC8EC, //HANGUL SYLLABLE CIEUC YO RIEULSIOS - 0xA188: 0xC8ED, //HANGUL SYLLABLE CIEUC YO RIEULTHIEUTH - 0xA189: 0xC8EE, //HANGUL SYLLABLE CIEUC YO RIEULPHIEUPH - 0xA18A: 0xC8EF, //HANGUL SYLLABLE CIEUC YO RIEULHIEUH - 0xA18B: 0xC8F0, //HANGUL SYLLABLE CIEUC YO MIEUM - 0xA18C: 0xC8F1, //HANGUL SYLLABLE CIEUC YO PIEUP - 0xA18D: 0xC8F2, //HANGUL SYLLABLE CIEUC YO PIEUPSIOS - 0xA18E: 0xC8F3, //HANGUL SYLLABLE CIEUC YO SIOS - 0xA18F: 0xC8F4, //HANGUL SYLLABLE CIEUC YO SSANGSIOS - 0xA190: 0xC8F6, //HANGUL SYLLABLE CIEUC YO CIEUC - 0xA191: 0xC8F7, //HANGUL SYLLABLE CIEUC YO CHIEUCH - 0xA192: 0xC8F8, //HANGUL SYLLABLE CIEUC YO KHIEUKH - 0xA193: 0xC8F9, //HANGUL SYLLABLE CIEUC YO THIEUTH - 0xA194: 0xC8FA, //HANGUL SYLLABLE CIEUC YO PHIEUPH - 0xA195: 0xC8FB, //HANGUL SYLLABLE CIEUC YO HIEUH - 0xA196: 0xC8FE, //HANGUL SYLLABLE CIEUC U SSANGKIYEOK - 0xA197: 0xC8FF, //HANGUL SYLLABLE CIEUC U KIYEOKSIOS - 0xA198: 0xC901, //HANGUL SYLLABLE CIEUC U NIEUNCIEUC - 0xA199: 0xC902, //HANGUL SYLLABLE CIEUC U NIEUNHIEUH - 0xA19A: 0xC903, //HANGUL SYLLABLE CIEUC U TIKEUT - 0xA19B: 0xC907, //HANGUL SYLLABLE CIEUC U RIEULPIEUP - 0xA19C: 0xC908, //HANGUL SYLLABLE CIEUC U RIEULSIOS - 0xA19D: 0xC909, //HANGUL SYLLABLE CIEUC U RIEULTHIEUTH - 0xA19E: 0xC90A, //HANGUL SYLLABLE CIEUC U RIEULPHIEUPH - 0xA19F: 0xC90B, //HANGUL SYLLABLE CIEUC U RIEULHIEUH - 0xA1A0: 0xC90E, //HANGUL SYLLABLE CIEUC U PIEUPSIOS - 0xA1A1: 0x3000, //IDEOGRAPHIC SPACE - 0xA1A2: 0x3001, //IDEOGRAPHIC COMMA - 0xA1A3: 0x3002, //IDEOGRAPHIC FULL STOP - 0xA1A4: 0x00B7, //MIDDLE DOT - 0xA1A5: 0x2025, //TWO DOT LEADER - 0xA1A6: 0x2026, //HORIZONTAL ELLIPSIS - 0xA1A7: 0x00A8, //DIAERESIS - 0xA1A8: 0x3003, //DITTO MARK - 0xA1A9: 0x00AD, //SOFT HYPHEN - 0xA1AA: 0x2015, //HORIZONTAL BAR - 0xA1AB: 0x2225, //PARALLEL TO - 0xA1AC: 0xFF3C, //FULLWIDTH REVERSE SOLIDUS - 0xA1AD: 0x223C, //TILDE OPERATOR - 0xA1AE: 0x2018, //LEFT SINGLE QUOTATION MARK - 0xA1AF: 0x2019, //RIGHT SINGLE QUOTATION MARK - 0xA1B0: 0x201C, //LEFT DOUBLE QUOTATION MARK - 0xA1B1: 0x201D, //RIGHT DOUBLE QUOTATION MARK - 0xA1B2: 0x3014, //LEFT TORTOISE SHELL BRACKET - 0xA1B3: 0x3015, //RIGHT TORTOISE SHELL BRACKET - 0xA1B4: 0x3008, //LEFT ANGLE BRACKET - 0xA1B5: 0x3009, //RIGHT ANGLE BRACKET - 0xA1B6: 0x300A, //LEFT DOUBLE ANGLE BRACKET - 0xA1B7: 0x300B, //RIGHT DOUBLE ANGLE BRACKET - 0xA1B8: 0x300C, //LEFT CORNER BRACKET - 0xA1B9: 0x300D, //RIGHT CORNER BRACKET - 0xA1BA: 0x300E, //LEFT WHITE CORNER BRACKET - 0xA1BB: 0x300F, //RIGHT WHITE CORNER BRACKET - 0xA1BC: 0x3010, //LEFT BLACK LENTICULAR BRACKET - 0xA1BD: 0x3011, //RIGHT BLACK LENTICULAR BRACKET - 0xA1BE: 0x00B1, //PLUS-MINUS SIGN - 0xA1BF: 0x00D7, //MULTIPLICATION SIGN - 0xA1C0: 0x00F7, //DIVISION SIGN - 0xA1C1: 0x2260, //NOT EQUAL TO - 0xA1C2: 0x2264, //LESS-THAN OR EQUAL TO - 0xA1C3: 0x2265, //GREATER-THAN OR EQUAL TO - 0xA1C4: 0x221E, //INFINITY - 0xA1C5: 0x2234, //THEREFORE - 0xA1C6: 0x00B0, //DEGREE SIGN - 0xA1C7: 0x2032, //PRIME - 0xA1C8: 0x2033, //DOUBLE PRIME - 0xA1C9: 0x2103, //DEGREE CELSIUS - 0xA1CA: 0x212B, //ANGSTROM SIGN - 0xA1CB: 0xFFE0, //FULLWIDTH CENT SIGN - 0xA1CC: 0xFFE1, //FULLWIDTH POUND SIGN - 0xA1CD: 0xFFE5, //FULLWIDTH YEN SIGN - 0xA1CE: 0x2642, //MALE SIGN - 0xA1CF: 0x2640, //FEMALE SIGN - 0xA1D0: 0x2220, //ANGLE - 0xA1D1: 0x22A5, //UP TACK - 0xA1D2: 0x2312, //ARC - 0xA1D3: 0x2202, //PARTIAL DIFFERENTIAL - 0xA1D4: 0x2207, //NABLA - 0xA1D5: 0x2261, //IDENTICAL TO - 0xA1D6: 0x2252, //APPROXIMATELY EQUAL TO OR THE IMAGE OF - 0xA1D7: 0x00A7, //SECTION SIGN - 0xA1D8: 0x203B, //REFERENCE MARK - 0xA1D9: 0x2606, //WHITE STAR - 0xA1DA: 0x2605, //BLACK STAR - 0xA1DB: 0x25CB, //WHITE CIRCLE - 0xA1DC: 0x25CF, //BLACK CIRCLE - 0xA1DD: 0x25CE, //BULLSEYE - 0xA1DE: 0x25C7, //WHITE DIAMOND - 0xA1DF: 0x25C6, //BLACK DIAMOND - 0xA1E0: 0x25A1, //WHITE SQUARE - 0xA1E1: 0x25A0, //BLACK SQUARE - 0xA1E2: 0x25B3, //WHITE UP-POINTING TRIANGLE - 0xA1E3: 0x25B2, //BLACK UP-POINTING TRIANGLE - 0xA1E4: 0x25BD, //WHITE DOWN-POINTING TRIANGLE - 0xA1E5: 0x25BC, //BLACK DOWN-POINTING TRIANGLE - 0xA1E6: 0x2192, //RIGHTWARDS ARROW - 0xA1E7: 0x2190, //LEFTWARDS ARROW - 0xA1E8: 0x2191, //UPWARDS ARROW - 0xA1E9: 0x2193, //DOWNWARDS ARROW - 0xA1EA: 0x2194, //LEFT RIGHT ARROW - 0xA1EB: 0x3013, //GETA MARK - 0xA1EC: 0x226A, //MUCH LESS-THAN - 0xA1ED: 0x226B, //MUCH GREATER-THAN - 0xA1EE: 0x221A, //SQUARE ROOT - 0xA1EF: 0x223D, //REVERSED TILDE - 0xA1F0: 0x221D, //PROPORTIONAL TO - 0xA1F1: 0x2235, //BECAUSE - 0xA1F2: 0x222B, //INTEGRAL - 0xA1F3: 0x222C, //DOUBLE INTEGRAL - 0xA1F4: 0x2208, //ELEMENT OF - 0xA1F5: 0x220B, //CONTAINS AS MEMBER - 0xA1F6: 0x2286, //SUBSET OF OR EQUAL TO - 0xA1F7: 0x2287, //SUPERSET OF OR EQUAL TO - 0xA1F8: 0x2282, //SUBSET OF - 0xA1F9: 0x2283, //SUPERSET OF - 0xA1FA: 0x222A, //UNION - 0xA1FB: 0x2229, //INTERSECTION - 0xA1FC: 0x2227, //LOGICAL AND - 0xA1FD: 0x2228, //LOGICAL OR - 0xA1FE: 0xFFE2, //FULLWIDTH NOT SIGN - 0xA241: 0xC910, //HANGUL SYLLABLE CIEUC U SSANGSIOS - 0xA242: 0xC912, //HANGUL SYLLABLE CIEUC U CIEUC - 0xA243: 0xC913, //HANGUL SYLLABLE CIEUC U CHIEUCH - 0xA244: 0xC914, //HANGUL SYLLABLE CIEUC U KHIEUKH - 0xA245: 0xC915, //HANGUL SYLLABLE CIEUC U THIEUTH - 0xA246: 0xC916, //HANGUL SYLLABLE CIEUC U PHIEUPH - 0xA247: 0xC917, //HANGUL SYLLABLE CIEUC U HIEUH - 0xA248: 0xC919, //HANGUL SYLLABLE CIEUC WEO KIYEOK - 0xA249: 0xC91A, //HANGUL SYLLABLE CIEUC WEO SSANGKIYEOK - 0xA24A: 0xC91B, //HANGUL SYLLABLE CIEUC WEO KIYEOKSIOS - 0xA24B: 0xC91C, //HANGUL SYLLABLE CIEUC WEO NIEUN - 0xA24C: 0xC91D, //HANGUL SYLLABLE CIEUC WEO NIEUNCIEUC - 0xA24D: 0xC91E, //HANGUL SYLLABLE CIEUC WEO NIEUNHIEUH - 0xA24E: 0xC91F, //HANGUL SYLLABLE CIEUC WEO TIKEUT - 0xA24F: 0xC920, //HANGUL SYLLABLE CIEUC WEO RIEUL - 0xA250: 0xC921, //HANGUL SYLLABLE CIEUC WEO RIEULKIYEOK - 0xA251: 0xC922, //HANGUL SYLLABLE CIEUC WEO RIEULMIEUM - 0xA252: 0xC923, //HANGUL SYLLABLE CIEUC WEO RIEULPIEUP - 0xA253: 0xC924, //HANGUL SYLLABLE CIEUC WEO RIEULSIOS - 0xA254: 0xC925, //HANGUL SYLLABLE CIEUC WEO RIEULTHIEUTH - 0xA255: 0xC926, //HANGUL SYLLABLE CIEUC WEO RIEULPHIEUPH - 0xA256: 0xC927, //HANGUL SYLLABLE CIEUC WEO RIEULHIEUH - 0xA257: 0xC928, //HANGUL SYLLABLE CIEUC WEO MIEUM - 0xA258: 0xC929, //HANGUL SYLLABLE CIEUC WEO PIEUP - 0xA259: 0xC92A, //HANGUL SYLLABLE CIEUC WEO PIEUPSIOS - 0xA25A: 0xC92B, //HANGUL SYLLABLE CIEUC WEO SIOS - 0xA261: 0xC92D, //HANGUL SYLLABLE CIEUC WEO IEUNG - 0xA262: 0xC92E, //HANGUL SYLLABLE CIEUC WEO CIEUC - 0xA263: 0xC92F, //HANGUL SYLLABLE CIEUC WEO CHIEUCH - 0xA264: 0xC930, //HANGUL SYLLABLE CIEUC WEO KHIEUKH - 0xA265: 0xC931, //HANGUL SYLLABLE CIEUC WEO THIEUTH - 0xA266: 0xC932, //HANGUL SYLLABLE CIEUC WEO PHIEUPH - 0xA267: 0xC933, //HANGUL SYLLABLE CIEUC WEO HIEUH - 0xA268: 0xC935, //HANGUL SYLLABLE CIEUC WE KIYEOK - 0xA269: 0xC936, //HANGUL SYLLABLE CIEUC WE SSANGKIYEOK - 0xA26A: 0xC937, //HANGUL SYLLABLE CIEUC WE KIYEOKSIOS - 0xA26B: 0xC938, //HANGUL SYLLABLE CIEUC WE NIEUN - 0xA26C: 0xC939, //HANGUL SYLLABLE CIEUC WE NIEUNCIEUC - 0xA26D: 0xC93A, //HANGUL SYLLABLE CIEUC WE NIEUNHIEUH - 0xA26E: 0xC93B, //HANGUL SYLLABLE CIEUC WE TIKEUT - 0xA26F: 0xC93C, //HANGUL SYLLABLE CIEUC WE RIEUL - 0xA270: 0xC93D, //HANGUL SYLLABLE CIEUC WE RIEULKIYEOK - 0xA271: 0xC93E, //HANGUL SYLLABLE CIEUC WE RIEULMIEUM - 0xA272: 0xC93F, //HANGUL SYLLABLE CIEUC WE RIEULPIEUP - 0xA273: 0xC940, //HANGUL SYLLABLE CIEUC WE RIEULSIOS - 0xA274: 0xC941, //HANGUL SYLLABLE CIEUC WE RIEULTHIEUTH - 0xA275: 0xC942, //HANGUL SYLLABLE CIEUC WE RIEULPHIEUPH - 0xA276: 0xC943, //HANGUL SYLLABLE CIEUC WE RIEULHIEUH - 0xA277: 0xC944, //HANGUL SYLLABLE CIEUC WE MIEUM - 0xA278: 0xC945, //HANGUL SYLLABLE CIEUC WE PIEUP - 0xA279: 0xC946, //HANGUL SYLLABLE CIEUC WE PIEUPSIOS - 0xA27A: 0xC947, //HANGUL SYLLABLE CIEUC WE SIOS - 0xA281: 0xC948, //HANGUL SYLLABLE CIEUC WE SSANGSIOS - 0xA282: 0xC949, //HANGUL SYLLABLE CIEUC WE IEUNG - 0xA283: 0xC94A, //HANGUL SYLLABLE CIEUC WE CIEUC - 0xA284: 0xC94B, //HANGUL SYLLABLE CIEUC WE CHIEUCH - 0xA285: 0xC94C, //HANGUL SYLLABLE CIEUC WE KHIEUKH - 0xA286: 0xC94D, //HANGUL SYLLABLE CIEUC WE THIEUTH - 0xA287: 0xC94E, //HANGUL SYLLABLE CIEUC WE PHIEUPH - 0xA288: 0xC94F, //HANGUL SYLLABLE CIEUC WE HIEUH - 0xA289: 0xC952, //HANGUL SYLLABLE CIEUC WI SSANGKIYEOK - 0xA28A: 0xC953, //HANGUL SYLLABLE CIEUC WI KIYEOKSIOS - 0xA28B: 0xC955, //HANGUL SYLLABLE CIEUC WI NIEUNCIEUC - 0xA28C: 0xC956, //HANGUL SYLLABLE CIEUC WI NIEUNHIEUH - 0xA28D: 0xC957, //HANGUL SYLLABLE CIEUC WI TIKEUT - 0xA28E: 0xC959, //HANGUL SYLLABLE CIEUC WI RIEULKIYEOK - 0xA28F: 0xC95A, //HANGUL SYLLABLE CIEUC WI RIEULMIEUM - 0xA290: 0xC95B, //HANGUL SYLLABLE CIEUC WI RIEULPIEUP - 0xA291: 0xC95C, //HANGUL SYLLABLE CIEUC WI RIEULSIOS - 0xA292: 0xC95D, //HANGUL SYLLABLE CIEUC WI RIEULTHIEUTH - 0xA293: 0xC95E, //HANGUL SYLLABLE CIEUC WI RIEULPHIEUPH - 0xA294: 0xC95F, //HANGUL SYLLABLE CIEUC WI RIEULHIEUH - 0xA295: 0xC962, //HANGUL SYLLABLE CIEUC WI PIEUPSIOS - 0xA296: 0xC964, //HANGUL SYLLABLE CIEUC WI SSANGSIOS - 0xA297: 0xC965, //HANGUL SYLLABLE CIEUC WI IEUNG - 0xA298: 0xC966, //HANGUL SYLLABLE CIEUC WI CIEUC - 0xA299: 0xC967, //HANGUL SYLLABLE CIEUC WI CHIEUCH - 0xA29A: 0xC968, //HANGUL SYLLABLE CIEUC WI KHIEUKH - 0xA29B: 0xC969, //HANGUL SYLLABLE CIEUC WI THIEUTH - 0xA29C: 0xC96A, //HANGUL SYLLABLE CIEUC WI PHIEUPH - 0xA29D: 0xC96B, //HANGUL SYLLABLE CIEUC WI HIEUH - 0xA29E: 0xC96D, //HANGUL SYLLABLE CIEUC YU KIYEOK - 0xA29F: 0xC96E, //HANGUL SYLLABLE CIEUC YU SSANGKIYEOK - 0xA2A0: 0xC96F, //HANGUL SYLLABLE CIEUC YU KIYEOKSIOS - 0xA2A1: 0x21D2, //RIGHTWARDS DOUBLE ARROW - 0xA2A2: 0x21D4, //LEFT RIGHT DOUBLE ARROW - 0xA2A3: 0x2200, //FOR ALL - 0xA2A4: 0x2203, //THERE EXISTS - 0xA2A5: 0x00B4, //ACUTE ACCENT - 0xA2A6: 0xFF5E, //FULLWIDTH TILDE - 0xA2A7: 0x02C7, //CARON - 0xA2A8: 0x02D8, //BREVE - 0xA2A9: 0x02DD, //DOUBLE ACUTE ACCENT - 0xA2AA: 0x02DA, //RING ABOVE - 0xA2AB: 0x02D9, //DOT ABOVE - 0xA2AC: 0x00B8, //CEDILLA - 0xA2AD: 0x02DB, //OGONEK - 0xA2AE: 0x00A1, //INVERTED EXCLAMATION MARK - 0xA2AF: 0x00BF, //INVERTED QUESTION MARK - 0xA2B0: 0x02D0, //MODIFIER LETTER TRIANGULAR COLON - 0xA2B1: 0x222E, //CONTOUR INTEGRAL - 0xA2B2: 0x2211, //N-ARY SUMMATION - 0xA2B3: 0x220F, //N-ARY PRODUCT - 0xA2B4: 0x00A4, //CURRENCY SIGN - 0xA2B5: 0x2109, //DEGREE FAHRENHEIT - 0xA2B6: 0x2030, //PER MILLE SIGN - 0xA2B7: 0x25C1, //WHITE LEFT-POINTING TRIANGLE - 0xA2B8: 0x25C0, //BLACK LEFT-POINTING TRIANGLE - 0xA2B9: 0x25B7, //WHITE RIGHT-POINTING TRIANGLE - 0xA2BA: 0x25B6, //BLACK RIGHT-POINTING TRIANGLE - 0xA2BB: 0x2664, //WHITE SPADE SUIT - 0xA2BC: 0x2660, //BLACK SPADE SUIT - 0xA2BD: 0x2661, //WHITE HEART SUIT - 0xA2BE: 0x2665, //BLACK HEART SUIT - 0xA2BF: 0x2667, //WHITE CLUB SUIT - 0xA2C0: 0x2663, //BLACK CLUB SUIT - 0xA2C1: 0x2299, //CIRCLED DOT OPERATOR - 0xA2C2: 0x25C8, //WHITE DIAMOND CONTAINING BLACK SMALL DIAMOND - 0xA2C3: 0x25A3, //WHITE SQUARE CONTAINING BLACK SMALL SQUARE - 0xA2C4: 0x25D0, //CIRCLE WITH LEFT HALF BLACK - 0xA2C5: 0x25D1, //CIRCLE WITH RIGHT HALF BLACK - 0xA2C6: 0x2592, //MEDIUM SHADE - 0xA2C7: 0x25A4, //SQUARE WITH HORIZONTAL FILL - 0xA2C8: 0x25A5, //SQUARE WITH VERTICAL FILL - 0xA2C9: 0x25A8, //SQUARE WITH UPPER RIGHT TO LOWER LEFT FILL - 0xA2CA: 0x25A7, //SQUARE WITH UPPER LEFT TO LOWER RIGHT FILL - 0xA2CB: 0x25A6, //SQUARE WITH ORTHOGONAL CROSSHATCH FILL - 0xA2CC: 0x25A9, //SQUARE WITH DIAGONAL CROSSHATCH FILL - 0xA2CD: 0x2668, //HOT SPRINGS - 0xA2CE: 0x260F, //WHITE TELEPHONE - 0xA2CF: 0x260E, //BLACK TELEPHONE - 0xA2D0: 0x261C, //WHITE LEFT POINTING INDEX - 0xA2D1: 0x261E, //WHITE RIGHT POINTING INDEX - 0xA2D2: 0x00B6, //PILCROW SIGN - 0xA2D3: 0x2020, //DAGGER - 0xA2D4: 0x2021, //DOUBLE DAGGER - 0xA2D5: 0x2195, //UP DOWN ARROW - 0xA2D6: 0x2197, //NORTH EAST ARROW - 0xA2D7: 0x2199, //SOUTH WEST ARROW - 0xA2D8: 0x2196, //NORTH WEST ARROW - 0xA2D9: 0x2198, //SOUTH EAST ARROW - 0xA2DA: 0x266D, //MUSIC FLAT SIGN - 0xA2DB: 0x2669, //QUARTER NOTE - 0xA2DC: 0x266A, //EIGHTH NOTE - 0xA2DD: 0x266C, //BEAMED SIXTEENTH NOTES - 0xA2DE: 0x327F, //KOREAN STANDARD SYMBOL - 0xA2DF: 0x321C, //PARENTHESIZED HANGUL CIEUC U - 0xA2E0: 0x2116, //NUMERO SIGN - 0xA2E1: 0x33C7, //SQUARE CO - 0xA2E2: 0x2122, //TRADE MARK SIGN - 0xA2E3: 0x33C2, //SQUARE AM - 0xA2E4: 0x33D8, //SQUARE PM - 0xA2E5: 0x2121, //TELEPHONE SIGN - 0xA2E6: 0x20AC, //EURO SIGN - 0xA2E7: 0x00AE, //REGISTERED SIGN - 0xA341: 0xC971, //HANGUL SYLLABLE CIEUC YU NIEUNCIEUC - 0xA342: 0xC972, //HANGUL SYLLABLE CIEUC YU NIEUNHIEUH - 0xA343: 0xC973, //HANGUL SYLLABLE CIEUC YU TIKEUT - 0xA344: 0xC975, //HANGUL SYLLABLE CIEUC YU RIEULKIYEOK - 0xA345: 0xC976, //HANGUL SYLLABLE CIEUC YU RIEULMIEUM - 0xA346: 0xC977, //HANGUL SYLLABLE CIEUC YU RIEULPIEUP - 0xA347: 0xC978, //HANGUL SYLLABLE CIEUC YU RIEULSIOS - 0xA348: 0xC979, //HANGUL SYLLABLE CIEUC YU RIEULTHIEUTH - 0xA349: 0xC97A, //HANGUL SYLLABLE CIEUC YU RIEULPHIEUPH - 0xA34A: 0xC97B, //HANGUL SYLLABLE CIEUC YU RIEULHIEUH - 0xA34B: 0xC97D, //HANGUL SYLLABLE CIEUC YU PIEUP - 0xA34C: 0xC97E, //HANGUL SYLLABLE CIEUC YU PIEUPSIOS - 0xA34D: 0xC97F, //HANGUL SYLLABLE CIEUC YU SIOS - 0xA34E: 0xC980, //HANGUL SYLLABLE CIEUC YU SSANGSIOS - 0xA34F: 0xC981, //HANGUL SYLLABLE CIEUC YU IEUNG - 0xA350: 0xC982, //HANGUL SYLLABLE CIEUC YU CIEUC - 0xA351: 0xC983, //HANGUL SYLLABLE CIEUC YU CHIEUCH - 0xA352: 0xC984, //HANGUL SYLLABLE CIEUC YU KHIEUKH - 0xA353: 0xC985, //HANGUL SYLLABLE CIEUC YU THIEUTH - 0xA354: 0xC986, //HANGUL SYLLABLE CIEUC YU PHIEUPH - 0xA355: 0xC987, //HANGUL SYLLABLE CIEUC YU HIEUH - 0xA356: 0xC98A, //HANGUL SYLLABLE CIEUC EU SSANGKIYEOK - 0xA357: 0xC98B, //HANGUL SYLLABLE CIEUC EU KIYEOKSIOS - 0xA358: 0xC98D, //HANGUL SYLLABLE CIEUC EU NIEUNCIEUC - 0xA359: 0xC98E, //HANGUL SYLLABLE CIEUC EU NIEUNHIEUH - 0xA35A: 0xC98F, //HANGUL SYLLABLE CIEUC EU TIKEUT - 0xA361: 0xC991, //HANGUL SYLLABLE CIEUC EU RIEULKIYEOK - 0xA362: 0xC992, //HANGUL SYLLABLE CIEUC EU RIEULMIEUM - 0xA363: 0xC993, //HANGUL SYLLABLE CIEUC EU RIEULPIEUP - 0xA364: 0xC994, //HANGUL SYLLABLE CIEUC EU RIEULSIOS - 0xA365: 0xC995, //HANGUL SYLLABLE CIEUC EU RIEULTHIEUTH - 0xA366: 0xC996, //HANGUL SYLLABLE CIEUC EU RIEULPHIEUPH - 0xA367: 0xC997, //HANGUL SYLLABLE CIEUC EU RIEULHIEUH - 0xA368: 0xC99A, //HANGUL SYLLABLE CIEUC EU PIEUPSIOS - 0xA369: 0xC99C, //HANGUL SYLLABLE CIEUC EU SSANGSIOS - 0xA36A: 0xC99E, //HANGUL SYLLABLE CIEUC EU CIEUC - 0xA36B: 0xC99F, //HANGUL SYLLABLE CIEUC EU CHIEUCH - 0xA36C: 0xC9A0, //HANGUL SYLLABLE CIEUC EU KHIEUKH - 0xA36D: 0xC9A1, //HANGUL SYLLABLE CIEUC EU THIEUTH - 0xA36E: 0xC9A2, //HANGUL SYLLABLE CIEUC EU PHIEUPH - 0xA36F: 0xC9A3, //HANGUL SYLLABLE CIEUC EU HIEUH - 0xA370: 0xC9A4, //HANGUL SYLLABLE CIEUC YI - 0xA371: 0xC9A5, //HANGUL SYLLABLE CIEUC YI KIYEOK - 0xA372: 0xC9A6, //HANGUL SYLLABLE CIEUC YI SSANGKIYEOK - 0xA373: 0xC9A7, //HANGUL SYLLABLE CIEUC YI KIYEOKSIOS - 0xA374: 0xC9A8, //HANGUL SYLLABLE CIEUC YI NIEUN - 0xA375: 0xC9A9, //HANGUL SYLLABLE CIEUC YI NIEUNCIEUC - 0xA376: 0xC9AA, //HANGUL SYLLABLE CIEUC YI NIEUNHIEUH - 0xA377: 0xC9AB, //HANGUL SYLLABLE CIEUC YI TIKEUT - 0xA378: 0xC9AC, //HANGUL SYLLABLE CIEUC YI RIEUL - 0xA379: 0xC9AD, //HANGUL SYLLABLE CIEUC YI RIEULKIYEOK - 0xA37A: 0xC9AE, //HANGUL SYLLABLE CIEUC YI RIEULMIEUM - 0xA381: 0xC9AF, //HANGUL SYLLABLE CIEUC YI RIEULPIEUP - 0xA382: 0xC9B0, //HANGUL SYLLABLE CIEUC YI RIEULSIOS - 0xA383: 0xC9B1, //HANGUL SYLLABLE CIEUC YI RIEULTHIEUTH - 0xA384: 0xC9B2, //HANGUL SYLLABLE CIEUC YI RIEULPHIEUPH - 0xA385: 0xC9B3, //HANGUL SYLLABLE CIEUC YI RIEULHIEUH - 0xA386: 0xC9B4, //HANGUL SYLLABLE CIEUC YI MIEUM - 0xA387: 0xC9B5, //HANGUL SYLLABLE CIEUC YI PIEUP - 0xA388: 0xC9B6, //HANGUL SYLLABLE CIEUC YI PIEUPSIOS - 0xA389: 0xC9B7, //HANGUL SYLLABLE CIEUC YI SIOS - 0xA38A: 0xC9B8, //HANGUL SYLLABLE CIEUC YI SSANGSIOS - 0xA38B: 0xC9B9, //HANGUL SYLLABLE CIEUC YI IEUNG - 0xA38C: 0xC9BA, //HANGUL SYLLABLE CIEUC YI CIEUC - 0xA38D: 0xC9BB, //HANGUL SYLLABLE CIEUC YI CHIEUCH - 0xA38E: 0xC9BC, //HANGUL SYLLABLE CIEUC YI KHIEUKH - 0xA38F: 0xC9BD, //HANGUL SYLLABLE CIEUC YI THIEUTH - 0xA390: 0xC9BE, //HANGUL SYLLABLE CIEUC YI PHIEUPH - 0xA391: 0xC9BF, //HANGUL SYLLABLE CIEUC YI HIEUH - 0xA392: 0xC9C2, //HANGUL SYLLABLE CIEUC I SSANGKIYEOK - 0xA393: 0xC9C3, //HANGUL SYLLABLE CIEUC I KIYEOKSIOS - 0xA394: 0xC9C5, //HANGUL SYLLABLE CIEUC I NIEUNCIEUC - 0xA395: 0xC9C6, //HANGUL SYLLABLE CIEUC I NIEUNHIEUH - 0xA396: 0xC9C9, //HANGUL SYLLABLE CIEUC I RIEULKIYEOK - 0xA397: 0xC9CB, //HANGUL SYLLABLE CIEUC I RIEULPIEUP - 0xA398: 0xC9CC, //HANGUL SYLLABLE CIEUC I RIEULSIOS - 0xA399: 0xC9CD, //HANGUL SYLLABLE CIEUC I RIEULTHIEUTH - 0xA39A: 0xC9CE, //HANGUL SYLLABLE CIEUC I RIEULPHIEUPH - 0xA39B: 0xC9CF, //HANGUL SYLLABLE CIEUC I RIEULHIEUH - 0xA39C: 0xC9D2, //HANGUL SYLLABLE CIEUC I PIEUPSIOS - 0xA39D: 0xC9D4, //HANGUL SYLLABLE CIEUC I SSANGSIOS - 0xA39E: 0xC9D7, //HANGUL SYLLABLE CIEUC I CHIEUCH - 0xA39F: 0xC9D8, //HANGUL SYLLABLE CIEUC I KHIEUKH - 0xA3A0: 0xC9DB, //HANGUL SYLLABLE CIEUC I HIEUH - 0xA3A1: 0xFF01, //FULLWIDTH EXCLAMATION MARK - 0xA3A2: 0xFF02, //FULLWIDTH QUOTATION MARK - 0xA3A3: 0xFF03, //FULLWIDTH NUMBER SIGN - 0xA3A4: 0xFF04, //FULLWIDTH DOLLAR SIGN - 0xA3A5: 0xFF05, //FULLWIDTH PERCENT SIGN - 0xA3A6: 0xFF06, //FULLWIDTH AMPERSAND - 0xA3A7: 0xFF07, //FULLWIDTH APOSTROPHE - 0xA3A8: 0xFF08, //FULLWIDTH LEFT PARENTHESIS - 0xA3A9: 0xFF09, //FULLWIDTH RIGHT PARENTHESIS - 0xA3AA: 0xFF0A, //FULLWIDTH ASTERISK - 0xA3AB: 0xFF0B, //FULLWIDTH PLUS SIGN - 0xA3AC: 0xFF0C, //FULLWIDTH COMMA - 0xA3AD: 0xFF0D, //FULLWIDTH HYPHEN-MINUS - 0xA3AE: 0xFF0E, //FULLWIDTH FULL STOP - 0xA3AF: 0xFF0F, //FULLWIDTH SOLIDUS - 0xA3B0: 0xFF10, //FULLWIDTH DIGIT ZERO - 0xA3B1: 0xFF11, //FULLWIDTH DIGIT ONE - 0xA3B2: 0xFF12, //FULLWIDTH DIGIT TWO - 0xA3B3: 0xFF13, //FULLWIDTH DIGIT THREE - 0xA3B4: 0xFF14, //FULLWIDTH DIGIT FOUR - 0xA3B5: 0xFF15, //FULLWIDTH DIGIT FIVE - 0xA3B6: 0xFF16, //FULLWIDTH DIGIT SIX - 0xA3B7: 0xFF17, //FULLWIDTH DIGIT SEVEN - 0xA3B8: 0xFF18, //FULLWIDTH DIGIT EIGHT - 0xA3B9: 0xFF19, //FULLWIDTH DIGIT NINE - 0xA3BA: 0xFF1A, //FULLWIDTH COLON - 0xA3BB: 0xFF1B, //FULLWIDTH SEMICOLON - 0xA3BC: 0xFF1C, //FULLWIDTH LESS-THAN SIGN - 0xA3BD: 0xFF1D, //FULLWIDTH EQUALS SIGN - 0xA3BE: 0xFF1E, //FULLWIDTH GREATER-THAN SIGN - 0xA3BF: 0xFF1F, //FULLWIDTH QUESTION MARK - 0xA3C0: 0xFF20, //FULLWIDTH COMMERCIAL AT - 0xA3C1: 0xFF21, //FULLWIDTH LATIN CAPITAL LETTER A - 0xA3C2: 0xFF22, //FULLWIDTH LATIN CAPITAL LETTER B - 0xA3C3: 0xFF23, //FULLWIDTH LATIN CAPITAL LETTER C - 0xA3C4: 0xFF24, //FULLWIDTH LATIN CAPITAL LETTER D - 0xA3C5: 0xFF25, //FULLWIDTH LATIN CAPITAL LETTER E - 0xA3C6: 0xFF26, //FULLWIDTH LATIN CAPITAL LETTER F - 0xA3C7: 0xFF27, //FULLWIDTH LATIN CAPITAL LETTER G - 0xA3C8: 0xFF28, //FULLWIDTH LATIN CAPITAL LETTER H - 0xA3C9: 0xFF29, //FULLWIDTH LATIN CAPITAL LETTER I - 0xA3CA: 0xFF2A, //FULLWIDTH LATIN CAPITAL LETTER J - 0xA3CB: 0xFF2B, //FULLWIDTH LATIN CAPITAL LETTER K - 0xA3CC: 0xFF2C, //FULLWIDTH LATIN CAPITAL LETTER L - 0xA3CD: 0xFF2D, //FULLWIDTH LATIN CAPITAL LETTER M - 0xA3CE: 0xFF2E, //FULLWIDTH LATIN CAPITAL LETTER N - 0xA3CF: 0xFF2F, //FULLWIDTH LATIN CAPITAL LETTER O - 0xA3D0: 0xFF30, //FULLWIDTH LATIN CAPITAL LETTER P - 0xA3D1: 0xFF31, //FULLWIDTH LATIN CAPITAL LETTER Q - 0xA3D2: 0xFF32, //FULLWIDTH LATIN CAPITAL LETTER R - 0xA3D3: 0xFF33, //FULLWIDTH LATIN CAPITAL LETTER S - 0xA3D4: 0xFF34, //FULLWIDTH LATIN CAPITAL LETTER T - 0xA3D5: 0xFF35, //FULLWIDTH LATIN CAPITAL LETTER U - 0xA3D6: 0xFF36, //FULLWIDTH LATIN CAPITAL LETTER V - 0xA3D7: 0xFF37, //FULLWIDTH LATIN CAPITAL LETTER W - 0xA3D8: 0xFF38, //FULLWIDTH LATIN CAPITAL LETTER X - 0xA3D9: 0xFF39, //FULLWIDTH LATIN CAPITAL LETTER Y - 0xA3DA: 0xFF3A, //FULLWIDTH LATIN CAPITAL LETTER Z - 0xA3DB: 0xFF3B, //FULLWIDTH LEFT SQUARE BRACKET - 0xA3DC: 0xFFE6, //FULLWIDTH WON SIGN - 0xA3DD: 0xFF3D, //FULLWIDTH RIGHT SQUARE BRACKET - 0xA3DE: 0xFF3E, //FULLWIDTH CIRCUMFLEX ACCENT - 0xA3DF: 0xFF3F, //FULLWIDTH LOW LINE - 0xA3E0: 0xFF40, //FULLWIDTH GRAVE ACCENT - 0xA3E1: 0xFF41, //FULLWIDTH LATIN SMALL LETTER A - 0xA3E2: 0xFF42, //FULLWIDTH LATIN SMALL LETTER B - 0xA3E3: 0xFF43, //FULLWIDTH LATIN SMALL LETTER C - 0xA3E4: 0xFF44, //FULLWIDTH LATIN SMALL LETTER D - 0xA3E5: 0xFF45, //FULLWIDTH LATIN SMALL LETTER E - 0xA3E6: 0xFF46, //FULLWIDTH LATIN SMALL LETTER F - 0xA3E7: 0xFF47, //FULLWIDTH LATIN SMALL LETTER G - 0xA3E8: 0xFF48, //FULLWIDTH LATIN SMALL LETTER H - 0xA3E9: 0xFF49, //FULLWIDTH LATIN SMALL LETTER I - 0xA3EA: 0xFF4A, //FULLWIDTH LATIN SMALL LETTER J - 0xA3EB: 0xFF4B, //FULLWIDTH LATIN SMALL LETTER K - 0xA3EC: 0xFF4C, //FULLWIDTH LATIN SMALL LETTER L - 0xA3ED: 0xFF4D, //FULLWIDTH LATIN SMALL LETTER M - 0xA3EE: 0xFF4E, //FULLWIDTH LATIN SMALL LETTER N - 0xA3EF: 0xFF4F, //FULLWIDTH LATIN SMALL LETTER O - 0xA3F0: 0xFF50, //FULLWIDTH LATIN SMALL LETTER P - 0xA3F1: 0xFF51, //FULLWIDTH LATIN SMALL LETTER Q - 0xA3F2: 0xFF52, //FULLWIDTH LATIN SMALL LETTER R - 0xA3F3: 0xFF53, //FULLWIDTH LATIN SMALL LETTER S - 0xA3F4: 0xFF54, //FULLWIDTH LATIN SMALL LETTER T - 0xA3F5: 0xFF55, //FULLWIDTH LATIN SMALL LETTER U - 0xA3F6: 0xFF56, //FULLWIDTH LATIN SMALL LETTER V - 0xA3F7: 0xFF57, //FULLWIDTH LATIN SMALL LETTER W - 0xA3F8: 0xFF58, //FULLWIDTH LATIN SMALL LETTER X - 0xA3F9: 0xFF59, //FULLWIDTH LATIN SMALL LETTER Y - 0xA3FA: 0xFF5A, //FULLWIDTH LATIN SMALL LETTER Z - 0xA3FB: 0xFF5B, //FULLWIDTH LEFT CURLY BRACKET - 0xA3FC: 0xFF5C, //FULLWIDTH VERTICAL LINE - 0xA3FD: 0xFF5D, //FULLWIDTH RIGHT CURLY BRACKET - 0xA3FE: 0xFFE3, //FULLWIDTH MACRON - 0xA441: 0xC9DE, //HANGUL SYLLABLE SSANGCIEUC A SSANGKIYEOK - 0xA442: 0xC9DF, //HANGUL SYLLABLE SSANGCIEUC A KIYEOKSIOS - 0xA443: 0xC9E1, //HANGUL SYLLABLE SSANGCIEUC A NIEUNCIEUC - 0xA444: 0xC9E3, //HANGUL SYLLABLE SSANGCIEUC A TIKEUT - 0xA445: 0xC9E5, //HANGUL SYLLABLE SSANGCIEUC A RIEULKIYEOK - 0xA446: 0xC9E6, //HANGUL SYLLABLE SSANGCIEUC A RIEULMIEUM - 0xA447: 0xC9E8, //HANGUL SYLLABLE SSANGCIEUC A RIEULSIOS - 0xA448: 0xC9E9, //HANGUL SYLLABLE SSANGCIEUC A RIEULTHIEUTH - 0xA449: 0xC9EA, //HANGUL SYLLABLE SSANGCIEUC A RIEULPHIEUPH - 0xA44A: 0xC9EB, //HANGUL SYLLABLE SSANGCIEUC A RIEULHIEUH - 0xA44B: 0xC9EE, //HANGUL SYLLABLE SSANGCIEUC A PIEUPSIOS - 0xA44C: 0xC9F2, //HANGUL SYLLABLE SSANGCIEUC A CIEUC - 0xA44D: 0xC9F3, //HANGUL SYLLABLE SSANGCIEUC A CHIEUCH - 0xA44E: 0xC9F4, //HANGUL SYLLABLE SSANGCIEUC A KHIEUKH - 0xA44F: 0xC9F5, //HANGUL SYLLABLE SSANGCIEUC A THIEUTH - 0xA450: 0xC9F6, //HANGUL SYLLABLE SSANGCIEUC A PHIEUPH - 0xA451: 0xC9F7, //HANGUL SYLLABLE SSANGCIEUC A HIEUH - 0xA452: 0xC9FA, //HANGUL SYLLABLE SSANGCIEUC AE SSANGKIYEOK - 0xA453: 0xC9FB, //HANGUL SYLLABLE SSANGCIEUC AE KIYEOKSIOS - 0xA454: 0xC9FD, //HANGUL SYLLABLE SSANGCIEUC AE NIEUNCIEUC - 0xA455: 0xC9FE, //HANGUL SYLLABLE SSANGCIEUC AE NIEUNHIEUH - 0xA456: 0xC9FF, //HANGUL SYLLABLE SSANGCIEUC AE TIKEUT - 0xA457: 0xCA01, //HANGUL SYLLABLE SSANGCIEUC AE RIEULKIYEOK - 0xA458: 0xCA02, //HANGUL SYLLABLE SSANGCIEUC AE RIEULMIEUM - 0xA459: 0xCA03, //HANGUL SYLLABLE SSANGCIEUC AE RIEULPIEUP - 0xA45A: 0xCA04, //HANGUL SYLLABLE SSANGCIEUC AE RIEULSIOS - 0xA461: 0xCA05, //HANGUL SYLLABLE SSANGCIEUC AE RIEULTHIEUTH - 0xA462: 0xCA06, //HANGUL SYLLABLE SSANGCIEUC AE RIEULPHIEUPH - 0xA463: 0xCA07, //HANGUL SYLLABLE SSANGCIEUC AE RIEULHIEUH - 0xA464: 0xCA0A, //HANGUL SYLLABLE SSANGCIEUC AE PIEUPSIOS - 0xA465: 0xCA0E, //HANGUL SYLLABLE SSANGCIEUC AE CIEUC - 0xA466: 0xCA0F, //HANGUL SYLLABLE SSANGCIEUC AE CHIEUCH - 0xA467: 0xCA10, //HANGUL SYLLABLE SSANGCIEUC AE KHIEUKH - 0xA468: 0xCA11, //HANGUL SYLLABLE SSANGCIEUC AE THIEUTH - 0xA469: 0xCA12, //HANGUL SYLLABLE SSANGCIEUC AE PHIEUPH - 0xA46A: 0xCA13, //HANGUL SYLLABLE SSANGCIEUC AE HIEUH - 0xA46B: 0xCA15, //HANGUL SYLLABLE SSANGCIEUC YA KIYEOK - 0xA46C: 0xCA16, //HANGUL SYLLABLE SSANGCIEUC YA SSANGKIYEOK - 0xA46D: 0xCA17, //HANGUL SYLLABLE SSANGCIEUC YA KIYEOKSIOS - 0xA46E: 0xCA19, //HANGUL SYLLABLE SSANGCIEUC YA NIEUNCIEUC - 0xA46F: 0xCA1A, //HANGUL SYLLABLE SSANGCIEUC YA NIEUNHIEUH - 0xA470: 0xCA1B, //HANGUL SYLLABLE SSANGCIEUC YA TIKEUT - 0xA471: 0xCA1C, //HANGUL SYLLABLE SSANGCIEUC YA RIEUL - 0xA472: 0xCA1D, //HANGUL SYLLABLE SSANGCIEUC YA RIEULKIYEOK - 0xA473: 0xCA1E, //HANGUL SYLLABLE SSANGCIEUC YA RIEULMIEUM - 0xA474: 0xCA1F, //HANGUL SYLLABLE SSANGCIEUC YA RIEULPIEUP - 0xA475: 0xCA20, //HANGUL SYLLABLE SSANGCIEUC YA RIEULSIOS - 0xA476: 0xCA21, //HANGUL SYLLABLE SSANGCIEUC YA RIEULTHIEUTH - 0xA477: 0xCA22, //HANGUL SYLLABLE SSANGCIEUC YA RIEULPHIEUPH - 0xA478: 0xCA23, //HANGUL SYLLABLE SSANGCIEUC YA RIEULHIEUH - 0xA479: 0xCA24, //HANGUL SYLLABLE SSANGCIEUC YA MIEUM - 0xA47A: 0xCA25, //HANGUL SYLLABLE SSANGCIEUC YA PIEUP - 0xA481: 0xCA26, //HANGUL SYLLABLE SSANGCIEUC YA PIEUPSIOS - 0xA482: 0xCA27, //HANGUL SYLLABLE SSANGCIEUC YA SIOS - 0xA483: 0xCA28, //HANGUL SYLLABLE SSANGCIEUC YA SSANGSIOS - 0xA484: 0xCA2A, //HANGUL SYLLABLE SSANGCIEUC YA CIEUC - 0xA485: 0xCA2B, //HANGUL SYLLABLE SSANGCIEUC YA CHIEUCH - 0xA486: 0xCA2C, //HANGUL SYLLABLE SSANGCIEUC YA KHIEUKH - 0xA487: 0xCA2D, //HANGUL SYLLABLE SSANGCIEUC YA THIEUTH - 0xA488: 0xCA2E, //HANGUL SYLLABLE SSANGCIEUC YA PHIEUPH - 0xA489: 0xCA2F, //HANGUL SYLLABLE SSANGCIEUC YA HIEUH - 0xA48A: 0xCA30, //HANGUL SYLLABLE SSANGCIEUC YAE - 0xA48B: 0xCA31, //HANGUL SYLLABLE SSANGCIEUC YAE KIYEOK - 0xA48C: 0xCA32, //HANGUL SYLLABLE SSANGCIEUC YAE SSANGKIYEOK - 0xA48D: 0xCA33, //HANGUL SYLLABLE SSANGCIEUC YAE KIYEOKSIOS - 0xA48E: 0xCA34, //HANGUL SYLLABLE SSANGCIEUC YAE NIEUN - 0xA48F: 0xCA35, //HANGUL SYLLABLE SSANGCIEUC YAE NIEUNCIEUC - 0xA490: 0xCA36, //HANGUL SYLLABLE SSANGCIEUC YAE NIEUNHIEUH - 0xA491: 0xCA37, //HANGUL SYLLABLE SSANGCIEUC YAE TIKEUT - 0xA492: 0xCA38, //HANGUL SYLLABLE SSANGCIEUC YAE RIEUL - 0xA493: 0xCA39, //HANGUL SYLLABLE SSANGCIEUC YAE RIEULKIYEOK - 0xA494: 0xCA3A, //HANGUL SYLLABLE SSANGCIEUC YAE RIEULMIEUM - 0xA495: 0xCA3B, //HANGUL SYLLABLE SSANGCIEUC YAE RIEULPIEUP - 0xA496: 0xCA3C, //HANGUL SYLLABLE SSANGCIEUC YAE RIEULSIOS - 0xA497: 0xCA3D, //HANGUL SYLLABLE SSANGCIEUC YAE RIEULTHIEUTH - 0xA498: 0xCA3E, //HANGUL SYLLABLE SSANGCIEUC YAE RIEULPHIEUPH - 0xA499: 0xCA3F, //HANGUL SYLLABLE SSANGCIEUC YAE RIEULHIEUH - 0xA49A: 0xCA40, //HANGUL SYLLABLE SSANGCIEUC YAE MIEUM - 0xA49B: 0xCA41, //HANGUL SYLLABLE SSANGCIEUC YAE PIEUP - 0xA49C: 0xCA42, //HANGUL SYLLABLE SSANGCIEUC YAE PIEUPSIOS - 0xA49D: 0xCA43, //HANGUL SYLLABLE SSANGCIEUC YAE SIOS - 0xA49E: 0xCA44, //HANGUL SYLLABLE SSANGCIEUC YAE SSANGSIOS - 0xA49F: 0xCA45, //HANGUL SYLLABLE SSANGCIEUC YAE IEUNG - 0xA4A0: 0xCA46, //HANGUL SYLLABLE SSANGCIEUC YAE CIEUC - 0xA4A1: 0x3131, //HANGUL LETTER KIYEOK - 0xA4A2: 0x3132, //HANGUL LETTER SSANGKIYEOK - 0xA4A3: 0x3133, //HANGUL LETTER KIYEOK-SIOS - 0xA4A4: 0x3134, //HANGUL LETTER NIEUN - 0xA4A5: 0x3135, //HANGUL LETTER NIEUN-CIEUC - 0xA4A6: 0x3136, //HANGUL LETTER NIEUN-HIEUH - 0xA4A7: 0x3137, //HANGUL LETTER TIKEUT - 0xA4A8: 0x3138, //HANGUL LETTER SSANGTIKEUT - 0xA4A9: 0x3139, //HANGUL LETTER RIEUL - 0xA4AA: 0x313A, //HANGUL LETTER RIEUL-KIYEOK - 0xA4AB: 0x313B, //HANGUL LETTER RIEUL-MIEUM - 0xA4AC: 0x313C, //HANGUL LETTER RIEUL-PIEUP - 0xA4AD: 0x313D, //HANGUL LETTER RIEUL-SIOS - 0xA4AE: 0x313E, //HANGUL LETTER RIEUL-THIEUTH - 0xA4AF: 0x313F, //HANGUL LETTER RIEUL-PHIEUPH - 0xA4B0: 0x3140, //HANGUL LETTER RIEUL-HIEUH - 0xA4B1: 0x3141, //HANGUL LETTER MIEUM - 0xA4B2: 0x3142, //HANGUL LETTER PIEUP - 0xA4B3: 0x3143, //HANGUL LETTER SSANGPIEUP - 0xA4B4: 0x3144, //HANGUL LETTER PIEUP-SIOS - 0xA4B5: 0x3145, //HANGUL LETTER SIOS - 0xA4B6: 0x3146, //HANGUL LETTER SSANGSIOS - 0xA4B7: 0x3147, //HANGUL LETTER IEUNG - 0xA4B8: 0x3148, //HANGUL LETTER CIEUC - 0xA4B9: 0x3149, //HANGUL LETTER SSANGCIEUC - 0xA4BA: 0x314A, //HANGUL LETTER CHIEUCH - 0xA4BB: 0x314B, //HANGUL LETTER KHIEUKH - 0xA4BC: 0x314C, //HANGUL LETTER THIEUTH - 0xA4BD: 0x314D, //HANGUL LETTER PHIEUPH - 0xA4BE: 0x314E, //HANGUL LETTER HIEUH - 0xA4BF: 0x314F, //HANGUL LETTER A - 0xA4C0: 0x3150, //HANGUL LETTER AE - 0xA4C1: 0x3151, //HANGUL LETTER YA - 0xA4C2: 0x3152, //HANGUL LETTER YAE - 0xA4C3: 0x3153, //HANGUL LETTER EO - 0xA4C4: 0x3154, //HANGUL LETTER E - 0xA4C5: 0x3155, //HANGUL LETTER YEO - 0xA4C6: 0x3156, //HANGUL LETTER YE - 0xA4C7: 0x3157, //HANGUL LETTER O - 0xA4C8: 0x3158, //HANGUL LETTER WA - 0xA4C9: 0x3159, //HANGUL LETTER WAE - 0xA4CA: 0x315A, //HANGUL LETTER OE - 0xA4CB: 0x315B, //HANGUL LETTER YO - 0xA4CC: 0x315C, //HANGUL LETTER U - 0xA4CD: 0x315D, //HANGUL LETTER WEO - 0xA4CE: 0x315E, //HANGUL LETTER WE - 0xA4CF: 0x315F, //HANGUL LETTER WI - 0xA4D0: 0x3160, //HANGUL LETTER YU - 0xA4D1: 0x3161, //HANGUL LETTER EU - 0xA4D2: 0x3162, //HANGUL LETTER YI - 0xA4D3: 0x3163, //HANGUL LETTER I - 0xA4D4: 0x3164, //HANGUL FILLER - 0xA4D5: 0x3165, //HANGUL LETTER SSANGNIEUN - 0xA4D6: 0x3166, //HANGUL LETTER NIEUN-TIKEUT - 0xA4D7: 0x3167, //HANGUL LETTER NIEUN-SIOS - 0xA4D8: 0x3168, //HANGUL LETTER NIEUN-PANSIOS - 0xA4D9: 0x3169, //HANGUL LETTER RIEUL-KIYEOK-SIOS - 0xA4DA: 0x316A, //HANGUL LETTER RIEUL-TIKEUT - 0xA4DB: 0x316B, //HANGUL LETTER RIEUL-PIEUP-SIOS - 0xA4DC: 0x316C, //HANGUL LETTER RIEUL-PANSIOS - 0xA4DD: 0x316D, //HANGUL LETTER RIEUL-YEORINHIEUH - 0xA4DE: 0x316E, //HANGUL LETTER MIEUM-PIEUP - 0xA4DF: 0x316F, //HANGUL LETTER MIEUM-SIOS - 0xA4E0: 0x3170, //HANGUL LETTER MIEUM-PANSIOS - 0xA4E1: 0x3171, //HANGUL LETTER KAPYEOUNMIEUM - 0xA4E2: 0x3172, //HANGUL LETTER PIEUP-KIYEOK - 0xA4E3: 0x3173, //HANGUL LETTER PIEUP-TIKEUT - 0xA4E4: 0x3174, //HANGUL LETTER PIEUP-SIOS-KIYEOK - 0xA4E5: 0x3175, //HANGUL LETTER PIEUP-SIOS-TIKEUT - 0xA4E6: 0x3176, //HANGUL LETTER PIEUP-CIEUC - 0xA4E7: 0x3177, //HANGUL LETTER PIEUP-THIEUTH - 0xA4E8: 0x3178, //HANGUL LETTER KAPYEOUNPIEUP - 0xA4E9: 0x3179, //HANGUL LETTER KAPYEOUNSSANGPIEUP - 0xA4EA: 0x317A, //HANGUL LETTER SIOS-KIYEOK - 0xA4EB: 0x317B, //HANGUL LETTER SIOS-NIEUN - 0xA4EC: 0x317C, //HANGUL LETTER SIOS-TIKEUT - 0xA4ED: 0x317D, //HANGUL LETTER SIOS-PIEUP - 0xA4EE: 0x317E, //HANGUL LETTER SIOS-CIEUC - 0xA4EF: 0x317F, //HANGUL LETTER PANSIOS - 0xA4F0: 0x3180, //HANGUL LETTER SSANGIEUNG - 0xA4F1: 0x3181, //HANGUL LETTER YESIEUNG - 0xA4F2: 0x3182, //HANGUL LETTER YESIEUNG-SIOS - 0xA4F3: 0x3183, //HANGUL LETTER YESIEUNG-PANSIOS - 0xA4F4: 0x3184, //HANGUL LETTER KAPYEOUNPHIEUPH - 0xA4F5: 0x3185, //HANGUL LETTER SSANGHIEUH - 0xA4F6: 0x3186, //HANGUL LETTER YEORINHIEUH - 0xA4F7: 0x3187, //HANGUL LETTER YO-YA - 0xA4F8: 0x3188, //HANGUL LETTER YO-YAE - 0xA4F9: 0x3189, //HANGUL LETTER YO-I - 0xA4FA: 0x318A, //HANGUL LETTER YU-YEO - 0xA4FB: 0x318B, //HANGUL LETTER YU-YE - 0xA4FC: 0x318C, //HANGUL LETTER YU-I - 0xA4FD: 0x318D, //HANGUL LETTER ARAEA - 0xA4FE: 0x318E, //HANGUL LETTER ARAEAE - 0xA541: 0xCA47, //HANGUL SYLLABLE SSANGCIEUC YAE CHIEUCH - 0xA542: 0xCA48, //HANGUL SYLLABLE SSANGCIEUC YAE KHIEUKH - 0xA543: 0xCA49, //HANGUL SYLLABLE SSANGCIEUC YAE THIEUTH - 0xA544: 0xCA4A, //HANGUL SYLLABLE SSANGCIEUC YAE PHIEUPH - 0xA545: 0xCA4B, //HANGUL SYLLABLE SSANGCIEUC YAE HIEUH - 0xA546: 0xCA4E, //HANGUL SYLLABLE SSANGCIEUC EO SSANGKIYEOK - 0xA547: 0xCA4F, //HANGUL SYLLABLE SSANGCIEUC EO KIYEOKSIOS - 0xA548: 0xCA51, //HANGUL SYLLABLE SSANGCIEUC EO NIEUNCIEUC - 0xA549: 0xCA52, //HANGUL SYLLABLE SSANGCIEUC EO NIEUNHIEUH - 0xA54A: 0xCA53, //HANGUL SYLLABLE SSANGCIEUC EO TIKEUT - 0xA54B: 0xCA55, //HANGUL SYLLABLE SSANGCIEUC EO RIEULKIYEOK - 0xA54C: 0xCA56, //HANGUL SYLLABLE SSANGCIEUC EO RIEULMIEUM - 0xA54D: 0xCA57, //HANGUL SYLLABLE SSANGCIEUC EO RIEULPIEUP - 0xA54E: 0xCA58, //HANGUL SYLLABLE SSANGCIEUC EO RIEULSIOS - 0xA54F: 0xCA59, //HANGUL SYLLABLE SSANGCIEUC EO RIEULTHIEUTH - 0xA550: 0xCA5A, //HANGUL SYLLABLE SSANGCIEUC EO RIEULPHIEUPH - 0xA551: 0xCA5B, //HANGUL SYLLABLE SSANGCIEUC EO RIEULHIEUH - 0xA552: 0xCA5E, //HANGUL SYLLABLE SSANGCIEUC EO PIEUPSIOS - 0xA553: 0xCA62, //HANGUL SYLLABLE SSANGCIEUC EO CIEUC - 0xA554: 0xCA63, //HANGUL SYLLABLE SSANGCIEUC EO CHIEUCH - 0xA555: 0xCA64, //HANGUL SYLLABLE SSANGCIEUC EO KHIEUKH - 0xA556: 0xCA65, //HANGUL SYLLABLE SSANGCIEUC EO THIEUTH - 0xA557: 0xCA66, //HANGUL SYLLABLE SSANGCIEUC EO PHIEUPH - 0xA558: 0xCA67, //HANGUL SYLLABLE SSANGCIEUC EO HIEUH - 0xA559: 0xCA69, //HANGUL SYLLABLE SSANGCIEUC E KIYEOK - 0xA55A: 0xCA6A, //HANGUL SYLLABLE SSANGCIEUC E SSANGKIYEOK - 0xA561: 0xCA6B, //HANGUL SYLLABLE SSANGCIEUC E KIYEOKSIOS - 0xA562: 0xCA6C, //HANGUL SYLLABLE SSANGCIEUC E NIEUN - 0xA563: 0xCA6D, //HANGUL SYLLABLE SSANGCIEUC E NIEUNCIEUC - 0xA564: 0xCA6E, //HANGUL SYLLABLE SSANGCIEUC E NIEUNHIEUH - 0xA565: 0xCA6F, //HANGUL SYLLABLE SSANGCIEUC E TIKEUT - 0xA566: 0xCA70, //HANGUL SYLLABLE SSANGCIEUC E RIEUL - 0xA567: 0xCA71, //HANGUL SYLLABLE SSANGCIEUC E RIEULKIYEOK - 0xA568: 0xCA72, //HANGUL SYLLABLE SSANGCIEUC E RIEULMIEUM - 0xA569: 0xCA73, //HANGUL SYLLABLE SSANGCIEUC E RIEULPIEUP - 0xA56A: 0xCA74, //HANGUL SYLLABLE SSANGCIEUC E RIEULSIOS - 0xA56B: 0xCA75, //HANGUL SYLLABLE SSANGCIEUC E RIEULTHIEUTH - 0xA56C: 0xCA76, //HANGUL SYLLABLE SSANGCIEUC E RIEULPHIEUPH - 0xA56D: 0xCA77, //HANGUL SYLLABLE SSANGCIEUC E RIEULHIEUH - 0xA56E: 0xCA78, //HANGUL SYLLABLE SSANGCIEUC E MIEUM - 0xA56F: 0xCA79, //HANGUL SYLLABLE SSANGCIEUC E PIEUP - 0xA570: 0xCA7A, //HANGUL SYLLABLE SSANGCIEUC E PIEUPSIOS - 0xA571: 0xCA7B, //HANGUL SYLLABLE SSANGCIEUC E SIOS - 0xA572: 0xCA7C, //HANGUL SYLLABLE SSANGCIEUC E SSANGSIOS - 0xA573: 0xCA7E, //HANGUL SYLLABLE SSANGCIEUC E CIEUC - 0xA574: 0xCA7F, //HANGUL SYLLABLE SSANGCIEUC E CHIEUCH - 0xA575: 0xCA80, //HANGUL SYLLABLE SSANGCIEUC E KHIEUKH - 0xA576: 0xCA81, //HANGUL SYLLABLE SSANGCIEUC E THIEUTH - 0xA577: 0xCA82, //HANGUL SYLLABLE SSANGCIEUC E PHIEUPH - 0xA578: 0xCA83, //HANGUL SYLLABLE SSANGCIEUC E HIEUH - 0xA579: 0xCA85, //HANGUL SYLLABLE SSANGCIEUC YEO KIYEOK - 0xA57A: 0xCA86, //HANGUL SYLLABLE SSANGCIEUC YEO SSANGKIYEOK - 0xA581: 0xCA87, //HANGUL SYLLABLE SSANGCIEUC YEO KIYEOKSIOS - 0xA582: 0xCA88, //HANGUL SYLLABLE SSANGCIEUC YEO NIEUN - 0xA583: 0xCA89, //HANGUL SYLLABLE SSANGCIEUC YEO NIEUNCIEUC - 0xA584: 0xCA8A, //HANGUL SYLLABLE SSANGCIEUC YEO NIEUNHIEUH - 0xA585: 0xCA8B, //HANGUL SYLLABLE SSANGCIEUC YEO TIKEUT - 0xA586: 0xCA8C, //HANGUL SYLLABLE SSANGCIEUC YEO RIEUL - 0xA587: 0xCA8D, //HANGUL SYLLABLE SSANGCIEUC YEO RIEULKIYEOK - 0xA588: 0xCA8E, //HANGUL SYLLABLE SSANGCIEUC YEO RIEULMIEUM - 0xA589: 0xCA8F, //HANGUL SYLLABLE SSANGCIEUC YEO RIEULPIEUP - 0xA58A: 0xCA90, //HANGUL SYLLABLE SSANGCIEUC YEO RIEULSIOS - 0xA58B: 0xCA91, //HANGUL SYLLABLE SSANGCIEUC YEO RIEULTHIEUTH - 0xA58C: 0xCA92, //HANGUL SYLLABLE SSANGCIEUC YEO RIEULPHIEUPH - 0xA58D: 0xCA93, //HANGUL SYLLABLE SSANGCIEUC YEO RIEULHIEUH - 0xA58E: 0xCA94, //HANGUL SYLLABLE SSANGCIEUC YEO MIEUM - 0xA58F: 0xCA95, //HANGUL SYLLABLE SSANGCIEUC YEO PIEUP - 0xA590: 0xCA96, //HANGUL SYLLABLE SSANGCIEUC YEO PIEUPSIOS - 0xA591: 0xCA97, //HANGUL SYLLABLE SSANGCIEUC YEO SIOS - 0xA592: 0xCA99, //HANGUL SYLLABLE SSANGCIEUC YEO IEUNG - 0xA593: 0xCA9A, //HANGUL SYLLABLE SSANGCIEUC YEO CIEUC - 0xA594: 0xCA9B, //HANGUL SYLLABLE SSANGCIEUC YEO CHIEUCH - 0xA595: 0xCA9C, //HANGUL SYLLABLE SSANGCIEUC YEO KHIEUKH - 0xA596: 0xCA9D, //HANGUL SYLLABLE SSANGCIEUC YEO THIEUTH - 0xA597: 0xCA9E, //HANGUL SYLLABLE SSANGCIEUC YEO PHIEUPH - 0xA598: 0xCA9F, //HANGUL SYLLABLE SSANGCIEUC YEO HIEUH - 0xA599: 0xCAA0, //HANGUL SYLLABLE SSANGCIEUC YE - 0xA59A: 0xCAA1, //HANGUL SYLLABLE SSANGCIEUC YE KIYEOK - 0xA59B: 0xCAA2, //HANGUL SYLLABLE SSANGCIEUC YE SSANGKIYEOK - 0xA59C: 0xCAA3, //HANGUL SYLLABLE SSANGCIEUC YE KIYEOKSIOS - 0xA59D: 0xCAA4, //HANGUL SYLLABLE SSANGCIEUC YE NIEUN - 0xA59E: 0xCAA5, //HANGUL SYLLABLE SSANGCIEUC YE NIEUNCIEUC - 0xA59F: 0xCAA6, //HANGUL SYLLABLE SSANGCIEUC YE NIEUNHIEUH - 0xA5A0: 0xCAA7, //HANGUL SYLLABLE SSANGCIEUC YE TIKEUT - 0xA5A1: 0x2170, //SMALL ROMAN NUMERAL ONE - 0xA5A2: 0x2171, //SMALL ROMAN NUMERAL TWO - 0xA5A3: 0x2172, //SMALL ROMAN NUMERAL THREE - 0xA5A4: 0x2173, //SMALL ROMAN NUMERAL FOUR - 0xA5A5: 0x2174, //SMALL ROMAN NUMERAL FIVE - 0xA5A6: 0x2175, //SMALL ROMAN NUMERAL SIX - 0xA5A7: 0x2176, //SMALL ROMAN NUMERAL SEVEN - 0xA5A8: 0x2177, //SMALL ROMAN NUMERAL EIGHT - 0xA5A9: 0x2178, //SMALL ROMAN NUMERAL NINE - 0xA5AA: 0x2179, //SMALL ROMAN NUMERAL TEN - 0xA5B0: 0x2160, //ROMAN NUMERAL ONE - 0xA5B1: 0x2161, //ROMAN NUMERAL TWO - 0xA5B2: 0x2162, //ROMAN NUMERAL THREE - 0xA5B3: 0x2163, //ROMAN NUMERAL FOUR - 0xA5B4: 0x2164, //ROMAN NUMERAL FIVE - 0xA5B5: 0x2165, //ROMAN NUMERAL SIX - 0xA5B6: 0x2166, //ROMAN NUMERAL SEVEN - 0xA5B7: 0x2167, //ROMAN NUMERAL EIGHT - 0xA5B8: 0x2168, //ROMAN NUMERAL NINE - 0xA5B9: 0x2169, //ROMAN NUMERAL TEN - 0xA5C1: 0x0391, //GREEK CAPITAL LETTER ALPHA - 0xA5C2: 0x0392, //GREEK CAPITAL LETTER BETA - 0xA5C3: 0x0393, //GREEK CAPITAL LETTER GAMMA - 0xA5C4: 0x0394, //GREEK CAPITAL LETTER DELTA - 0xA5C5: 0x0395, //GREEK CAPITAL LETTER EPSILON - 0xA5C6: 0x0396, //GREEK CAPITAL LETTER ZETA - 0xA5C7: 0x0397, //GREEK CAPITAL LETTER ETA - 0xA5C8: 0x0398, //GREEK CAPITAL LETTER THETA - 0xA5C9: 0x0399, //GREEK CAPITAL LETTER IOTA - 0xA5CA: 0x039A, //GREEK CAPITAL LETTER KAPPA - 0xA5CB: 0x039B, //GREEK CAPITAL LETTER LAMDA - 0xA5CC: 0x039C, //GREEK CAPITAL LETTER MU - 0xA5CD: 0x039D, //GREEK CAPITAL LETTER NU - 0xA5CE: 0x039E, //GREEK CAPITAL LETTER XI - 0xA5CF: 0x039F, //GREEK CAPITAL LETTER OMICRON - 0xA5D0: 0x03A0, //GREEK CAPITAL LETTER PI - 0xA5D1: 0x03A1, //GREEK CAPITAL LETTER RHO - 0xA5D2: 0x03A3, //GREEK CAPITAL LETTER SIGMA - 0xA5D3: 0x03A4, //GREEK CAPITAL LETTER TAU - 0xA5D4: 0x03A5, //GREEK CAPITAL LETTER UPSILON - 0xA5D5: 0x03A6, //GREEK CAPITAL LETTER PHI - 0xA5D6: 0x03A7, //GREEK CAPITAL LETTER CHI - 0xA5D7: 0x03A8, //GREEK CAPITAL LETTER PSI - 0xA5D8: 0x03A9, //GREEK CAPITAL LETTER OMEGA - 0xA5E1: 0x03B1, //GREEK SMALL LETTER ALPHA - 0xA5E2: 0x03B2, //GREEK SMALL LETTER BETA - 0xA5E3: 0x03B3, //GREEK SMALL LETTER GAMMA - 0xA5E4: 0x03B4, //GREEK SMALL LETTER DELTA - 0xA5E5: 0x03B5, //GREEK SMALL LETTER EPSILON - 0xA5E6: 0x03B6, //GREEK SMALL LETTER ZETA - 0xA5E7: 0x03B7, //GREEK SMALL LETTER ETA - 0xA5E8: 0x03B8, //GREEK SMALL LETTER THETA - 0xA5E9: 0x03B9, //GREEK SMALL LETTER IOTA - 0xA5EA: 0x03BA, //GREEK SMALL LETTER KAPPA - 0xA5EB: 0x03BB, //GREEK SMALL LETTER LAMDA - 0xA5EC: 0x03BC, //GREEK SMALL LETTER MU - 0xA5ED: 0x03BD, //GREEK SMALL LETTER NU - 0xA5EE: 0x03BE, //GREEK SMALL LETTER XI - 0xA5EF: 0x03BF, //GREEK SMALL LETTER OMICRON - 0xA5F0: 0x03C0, //GREEK SMALL LETTER PI - 0xA5F1: 0x03C1, //GREEK SMALL LETTER RHO - 0xA5F2: 0x03C3, //GREEK SMALL LETTER SIGMA - 0xA5F3: 0x03C4, //GREEK SMALL LETTER TAU - 0xA5F4: 0x03C5, //GREEK SMALL LETTER UPSILON - 0xA5F5: 0x03C6, //GREEK SMALL LETTER PHI - 0xA5F6: 0x03C7, //GREEK SMALL LETTER CHI - 0xA5F7: 0x03C8, //GREEK SMALL LETTER PSI - 0xA5F8: 0x03C9, //GREEK SMALL LETTER OMEGA - 0xA641: 0xCAA8, //HANGUL SYLLABLE SSANGCIEUC YE RIEUL - 0xA642: 0xCAA9, //HANGUL SYLLABLE SSANGCIEUC YE RIEULKIYEOK - 0xA643: 0xCAAA, //HANGUL SYLLABLE SSANGCIEUC YE RIEULMIEUM - 0xA644: 0xCAAB, //HANGUL SYLLABLE SSANGCIEUC YE RIEULPIEUP - 0xA645: 0xCAAC, //HANGUL SYLLABLE SSANGCIEUC YE RIEULSIOS - 0xA646: 0xCAAD, //HANGUL SYLLABLE SSANGCIEUC YE RIEULTHIEUTH - 0xA647: 0xCAAE, //HANGUL SYLLABLE SSANGCIEUC YE RIEULPHIEUPH - 0xA648: 0xCAAF, //HANGUL SYLLABLE SSANGCIEUC YE RIEULHIEUH - 0xA649: 0xCAB0, //HANGUL SYLLABLE SSANGCIEUC YE MIEUM - 0xA64A: 0xCAB1, //HANGUL SYLLABLE SSANGCIEUC YE PIEUP - 0xA64B: 0xCAB2, //HANGUL SYLLABLE SSANGCIEUC YE PIEUPSIOS - 0xA64C: 0xCAB3, //HANGUL SYLLABLE SSANGCIEUC YE SIOS - 0xA64D: 0xCAB4, //HANGUL SYLLABLE SSANGCIEUC YE SSANGSIOS - 0xA64E: 0xCAB5, //HANGUL SYLLABLE SSANGCIEUC YE IEUNG - 0xA64F: 0xCAB6, //HANGUL SYLLABLE SSANGCIEUC YE CIEUC - 0xA650: 0xCAB7, //HANGUL SYLLABLE SSANGCIEUC YE CHIEUCH - 0xA651: 0xCAB8, //HANGUL SYLLABLE SSANGCIEUC YE KHIEUKH - 0xA652: 0xCAB9, //HANGUL SYLLABLE SSANGCIEUC YE THIEUTH - 0xA653: 0xCABA, //HANGUL SYLLABLE SSANGCIEUC YE PHIEUPH - 0xA654: 0xCABB, //HANGUL SYLLABLE SSANGCIEUC YE HIEUH - 0xA655: 0xCABE, //HANGUL SYLLABLE SSANGCIEUC O SSANGKIYEOK - 0xA656: 0xCABF, //HANGUL SYLLABLE SSANGCIEUC O KIYEOKSIOS - 0xA657: 0xCAC1, //HANGUL SYLLABLE SSANGCIEUC O NIEUNCIEUC - 0xA658: 0xCAC2, //HANGUL SYLLABLE SSANGCIEUC O NIEUNHIEUH - 0xA659: 0xCAC3, //HANGUL SYLLABLE SSANGCIEUC O TIKEUT - 0xA65A: 0xCAC5, //HANGUL SYLLABLE SSANGCIEUC O RIEULKIYEOK - 0xA661: 0xCAC6, //HANGUL SYLLABLE SSANGCIEUC O RIEULMIEUM - 0xA662: 0xCAC7, //HANGUL SYLLABLE SSANGCIEUC O RIEULPIEUP - 0xA663: 0xCAC8, //HANGUL SYLLABLE SSANGCIEUC O RIEULSIOS - 0xA664: 0xCAC9, //HANGUL SYLLABLE SSANGCIEUC O RIEULTHIEUTH - 0xA665: 0xCACA, //HANGUL SYLLABLE SSANGCIEUC O RIEULPHIEUPH - 0xA666: 0xCACB, //HANGUL SYLLABLE SSANGCIEUC O RIEULHIEUH - 0xA667: 0xCACE, //HANGUL SYLLABLE SSANGCIEUC O PIEUPSIOS - 0xA668: 0xCAD0, //HANGUL SYLLABLE SSANGCIEUC O SSANGSIOS - 0xA669: 0xCAD2, //HANGUL SYLLABLE SSANGCIEUC O CIEUC - 0xA66A: 0xCAD4, //HANGUL SYLLABLE SSANGCIEUC O KHIEUKH - 0xA66B: 0xCAD5, //HANGUL SYLLABLE SSANGCIEUC O THIEUTH - 0xA66C: 0xCAD6, //HANGUL SYLLABLE SSANGCIEUC O PHIEUPH - 0xA66D: 0xCAD7, //HANGUL SYLLABLE SSANGCIEUC O HIEUH - 0xA66E: 0xCADA, //HANGUL SYLLABLE SSANGCIEUC WA SSANGKIYEOK - 0xA66F: 0xCADB, //HANGUL SYLLABLE SSANGCIEUC WA KIYEOKSIOS - 0xA670: 0xCADC, //HANGUL SYLLABLE SSANGCIEUC WA NIEUN - 0xA671: 0xCADD, //HANGUL SYLLABLE SSANGCIEUC WA NIEUNCIEUC - 0xA672: 0xCADE, //HANGUL SYLLABLE SSANGCIEUC WA NIEUNHIEUH - 0xA673: 0xCADF, //HANGUL SYLLABLE SSANGCIEUC WA TIKEUT - 0xA674: 0xCAE1, //HANGUL SYLLABLE SSANGCIEUC WA RIEULKIYEOK - 0xA675: 0xCAE2, //HANGUL SYLLABLE SSANGCIEUC WA RIEULMIEUM - 0xA676: 0xCAE3, //HANGUL SYLLABLE SSANGCIEUC WA RIEULPIEUP - 0xA677: 0xCAE4, //HANGUL SYLLABLE SSANGCIEUC WA RIEULSIOS - 0xA678: 0xCAE5, //HANGUL SYLLABLE SSANGCIEUC WA RIEULTHIEUTH - 0xA679: 0xCAE6, //HANGUL SYLLABLE SSANGCIEUC WA RIEULPHIEUPH - 0xA67A: 0xCAE7, //HANGUL SYLLABLE SSANGCIEUC WA RIEULHIEUH - 0xA681: 0xCAE8, //HANGUL SYLLABLE SSANGCIEUC WA MIEUM - 0xA682: 0xCAE9, //HANGUL SYLLABLE SSANGCIEUC WA PIEUP - 0xA683: 0xCAEA, //HANGUL SYLLABLE SSANGCIEUC WA PIEUPSIOS - 0xA684: 0xCAEB, //HANGUL SYLLABLE SSANGCIEUC WA SIOS - 0xA685: 0xCAED, //HANGUL SYLLABLE SSANGCIEUC WA IEUNG - 0xA686: 0xCAEE, //HANGUL SYLLABLE SSANGCIEUC WA CIEUC - 0xA687: 0xCAEF, //HANGUL SYLLABLE SSANGCIEUC WA CHIEUCH - 0xA688: 0xCAF0, //HANGUL SYLLABLE SSANGCIEUC WA KHIEUKH - 0xA689: 0xCAF1, //HANGUL SYLLABLE SSANGCIEUC WA THIEUTH - 0xA68A: 0xCAF2, //HANGUL SYLLABLE SSANGCIEUC WA PHIEUPH - 0xA68B: 0xCAF3, //HANGUL SYLLABLE SSANGCIEUC WA HIEUH - 0xA68C: 0xCAF5, //HANGUL SYLLABLE SSANGCIEUC WAE KIYEOK - 0xA68D: 0xCAF6, //HANGUL SYLLABLE SSANGCIEUC WAE SSANGKIYEOK - 0xA68E: 0xCAF7, //HANGUL SYLLABLE SSANGCIEUC WAE KIYEOKSIOS - 0xA68F: 0xCAF8, //HANGUL SYLLABLE SSANGCIEUC WAE NIEUN - 0xA690: 0xCAF9, //HANGUL SYLLABLE SSANGCIEUC WAE NIEUNCIEUC - 0xA691: 0xCAFA, //HANGUL SYLLABLE SSANGCIEUC WAE NIEUNHIEUH - 0xA692: 0xCAFB, //HANGUL SYLLABLE SSANGCIEUC WAE TIKEUT - 0xA693: 0xCAFC, //HANGUL SYLLABLE SSANGCIEUC WAE RIEUL - 0xA694: 0xCAFD, //HANGUL SYLLABLE SSANGCIEUC WAE RIEULKIYEOK - 0xA695: 0xCAFE, //HANGUL SYLLABLE SSANGCIEUC WAE RIEULMIEUM - 0xA696: 0xCAFF, //HANGUL SYLLABLE SSANGCIEUC WAE RIEULPIEUP - 0xA697: 0xCB00, //HANGUL SYLLABLE SSANGCIEUC WAE RIEULSIOS - 0xA698: 0xCB01, //HANGUL SYLLABLE SSANGCIEUC WAE RIEULTHIEUTH - 0xA699: 0xCB02, //HANGUL SYLLABLE SSANGCIEUC WAE RIEULPHIEUPH - 0xA69A: 0xCB03, //HANGUL SYLLABLE SSANGCIEUC WAE RIEULHIEUH - 0xA69B: 0xCB04, //HANGUL SYLLABLE SSANGCIEUC WAE MIEUM - 0xA69C: 0xCB05, //HANGUL SYLLABLE SSANGCIEUC WAE PIEUP - 0xA69D: 0xCB06, //HANGUL SYLLABLE SSANGCIEUC WAE PIEUPSIOS - 0xA69E: 0xCB07, //HANGUL SYLLABLE SSANGCIEUC WAE SIOS - 0xA69F: 0xCB09, //HANGUL SYLLABLE SSANGCIEUC WAE IEUNG - 0xA6A0: 0xCB0A, //HANGUL SYLLABLE SSANGCIEUC WAE CIEUC - 0xA6A1: 0x2500, //BOX DRAWINGS LIGHT HORIZONTAL - 0xA6A2: 0x2502, //BOX DRAWINGS LIGHT VERTICAL - 0xA6A3: 0x250C, //BOX DRAWINGS LIGHT DOWN AND RIGHT - 0xA6A4: 0x2510, //BOX DRAWINGS LIGHT DOWN AND LEFT - 0xA6A5: 0x2518, //BOX DRAWINGS LIGHT UP AND LEFT - 0xA6A6: 0x2514, //BOX DRAWINGS LIGHT UP AND RIGHT - 0xA6A7: 0x251C, //BOX DRAWINGS LIGHT VERTICAL AND RIGHT - 0xA6A8: 0x252C, //BOX DRAWINGS LIGHT DOWN AND HORIZONTAL - 0xA6A9: 0x2524, //BOX DRAWINGS LIGHT VERTICAL AND LEFT - 0xA6AA: 0x2534, //BOX DRAWINGS LIGHT UP AND HORIZONTAL - 0xA6AB: 0x253C, //BOX DRAWINGS LIGHT VERTICAL AND HORIZONTAL - 0xA6AC: 0x2501, //BOX DRAWINGS HEAVY HORIZONTAL - 0xA6AD: 0x2503, //BOX DRAWINGS HEAVY VERTICAL - 0xA6AE: 0x250F, //BOX DRAWINGS HEAVY DOWN AND RIGHT - 0xA6AF: 0x2513, //BOX DRAWINGS HEAVY DOWN AND LEFT - 0xA6B0: 0x251B, //BOX DRAWINGS HEAVY UP AND LEFT - 0xA6B1: 0x2517, //BOX DRAWINGS HEAVY UP AND RIGHT - 0xA6B2: 0x2523, //BOX DRAWINGS HEAVY VERTICAL AND RIGHT - 0xA6B3: 0x2533, //BOX DRAWINGS HEAVY DOWN AND HORIZONTAL - 0xA6B4: 0x252B, //BOX DRAWINGS HEAVY VERTICAL AND LEFT - 0xA6B5: 0x253B, //BOX DRAWINGS HEAVY UP AND HORIZONTAL - 0xA6B6: 0x254B, //BOX DRAWINGS HEAVY VERTICAL AND HORIZONTAL - 0xA6B7: 0x2520, //BOX DRAWINGS VERTICAL HEAVY AND RIGHT LIGHT - 0xA6B8: 0x252F, //BOX DRAWINGS DOWN LIGHT AND HORIZONTAL HEAVY - 0xA6B9: 0x2528, //BOX DRAWINGS VERTICAL HEAVY AND LEFT LIGHT - 0xA6BA: 0x2537, //BOX DRAWINGS UP LIGHT AND HORIZONTAL HEAVY - 0xA6BB: 0x253F, //BOX DRAWINGS VERTICAL LIGHT AND HORIZONTAL HEAVY - 0xA6BC: 0x251D, //BOX DRAWINGS VERTICAL LIGHT AND RIGHT HEAVY - 0xA6BD: 0x2530, //BOX DRAWINGS DOWN HEAVY AND HORIZONTAL LIGHT - 0xA6BE: 0x2525, //BOX DRAWINGS VERTICAL LIGHT AND LEFT HEAVY - 0xA6BF: 0x2538, //BOX DRAWINGS UP HEAVY AND HORIZONTAL LIGHT - 0xA6C0: 0x2542, //BOX DRAWINGS VERTICAL HEAVY AND HORIZONTAL LIGHT - 0xA6C1: 0x2512, //BOX DRAWINGS DOWN HEAVY AND LEFT LIGHT - 0xA6C2: 0x2511, //BOX DRAWINGS DOWN LIGHT AND LEFT HEAVY - 0xA6C3: 0x251A, //BOX DRAWINGS UP HEAVY AND LEFT LIGHT - 0xA6C4: 0x2519, //BOX DRAWINGS UP LIGHT AND LEFT HEAVY - 0xA6C5: 0x2516, //BOX DRAWINGS UP HEAVY AND RIGHT LIGHT - 0xA6C6: 0x2515, //BOX DRAWINGS UP LIGHT AND RIGHT HEAVY - 0xA6C7: 0x250E, //BOX DRAWINGS DOWN HEAVY AND RIGHT LIGHT - 0xA6C8: 0x250D, //BOX DRAWINGS DOWN LIGHT AND RIGHT HEAVY - 0xA6C9: 0x251E, //BOX DRAWINGS UP HEAVY AND RIGHT DOWN LIGHT - 0xA6CA: 0x251F, //BOX DRAWINGS DOWN HEAVY AND RIGHT UP LIGHT - 0xA6CB: 0x2521, //BOX DRAWINGS DOWN LIGHT AND RIGHT UP HEAVY - 0xA6CC: 0x2522, //BOX DRAWINGS UP LIGHT AND RIGHT DOWN HEAVY - 0xA6CD: 0x2526, //BOX DRAWINGS UP HEAVY AND LEFT DOWN LIGHT - 0xA6CE: 0x2527, //BOX DRAWINGS DOWN HEAVY AND LEFT UP LIGHT - 0xA6CF: 0x2529, //BOX DRAWINGS DOWN LIGHT AND LEFT UP HEAVY - 0xA6D0: 0x252A, //BOX DRAWINGS UP LIGHT AND LEFT DOWN HEAVY - 0xA6D1: 0x252D, //BOX DRAWINGS LEFT HEAVY AND RIGHT DOWN LIGHT - 0xA6D2: 0x252E, //BOX DRAWINGS RIGHT HEAVY AND LEFT DOWN LIGHT - 0xA6D3: 0x2531, //BOX DRAWINGS RIGHT LIGHT AND LEFT DOWN HEAVY - 0xA6D4: 0x2532, //BOX DRAWINGS LEFT LIGHT AND RIGHT DOWN HEAVY - 0xA6D5: 0x2535, //BOX DRAWINGS LEFT HEAVY AND RIGHT UP LIGHT - 0xA6D6: 0x2536, //BOX DRAWINGS RIGHT HEAVY AND LEFT UP LIGHT - 0xA6D7: 0x2539, //BOX DRAWINGS RIGHT LIGHT AND LEFT UP HEAVY - 0xA6D8: 0x253A, //BOX DRAWINGS LEFT LIGHT AND RIGHT UP HEAVY - 0xA6D9: 0x253D, //BOX DRAWINGS LEFT HEAVY AND RIGHT VERTICAL LIGHT - 0xA6DA: 0x253E, //BOX DRAWINGS RIGHT HEAVY AND LEFT VERTICAL LIGHT - 0xA6DB: 0x2540, //BOX DRAWINGS UP HEAVY AND DOWN HORIZONTAL LIGHT - 0xA6DC: 0x2541, //BOX DRAWINGS DOWN HEAVY AND UP HORIZONTAL LIGHT - 0xA6DD: 0x2543, //BOX DRAWINGS LEFT UP HEAVY AND RIGHT DOWN LIGHT - 0xA6DE: 0x2544, //BOX DRAWINGS RIGHT UP HEAVY AND LEFT DOWN LIGHT - 0xA6DF: 0x2545, //BOX DRAWINGS LEFT DOWN HEAVY AND RIGHT UP LIGHT - 0xA6E0: 0x2546, //BOX DRAWINGS RIGHT DOWN HEAVY AND LEFT UP LIGHT - 0xA6E1: 0x2547, //BOX DRAWINGS DOWN LIGHT AND UP HORIZONTAL HEAVY - 0xA6E2: 0x2548, //BOX DRAWINGS UP LIGHT AND DOWN HORIZONTAL HEAVY - 0xA6E3: 0x2549, //BOX DRAWINGS RIGHT LIGHT AND LEFT VERTICAL HEAVY - 0xA6E4: 0x254A, //BOX DRAWINGS LEFT LIGHT AND RIGHT VERTICAL HEAVY - 0xA741: 0xCB0B, //HANGUL SYLLABLE SSANGCIEUC WAE CHIEUCH - 0xA742: 0xCB0C, //HANGUL SYLLABLE SSANGCIEUC WAE KHIEUKH - 0xA743: 0xCB0D, //HANGUL SYLLABLE SSANGCIEUC WAE THIEUTH - 0xA744: 0xCB0E, //HANGUL SYLLABLE SSANGCIEUC WAE PHIEUPH - 0xA745: 0xCB0F, //HANGUL SYLLABLE SSANGCIEUC WAE HIEUH - 0xA746: 0xCB11, //HANGUL SYLLABLE SSANGCIEUC OE KIYEOK - 0xA747: 0xCB12, //HANGUL SYLLABLE SSANGCIEUC OE SSANGKIYEOK - 0xA748: 0xCB13, //HANGUL SYLLABLE SSANGCIEUC OE KIYEOKSIOS - 0xA749: 0xCB15, //HANGUL SYLLABLE SSANGCIEUC OE NIEUNCIEUC - 0xA74A: 0xCB16, //HANGUL SYLLABLE SSANGCIEUC OE NIEUNHIEUH - 0xA74B: 0xCB17, //HANGUL SYLLABLE SSANGCIEUC OE TIKEUT - 0xA74C: 0xCB19, //HANGUL SYLLABLE SSANGCIEUC OE RIEULKIYEOK - 0xA74D: 0xCB1A, //HANGUL SYLLABLE SSANGCIEUC OE RIEULMIEUM - 0xA74E: 0xCB1B, //HANGUL SYLLABLE SSANGCIEUC OE RIEULPIEUP - 0xA74F: 0xCB1C, //HANGUL SYLLABLE SSANGCIEUC OE RIEULSIOS - 0xA750: 0xCB1D, //HANGUL SYLLABLE SSANGCIEUC OE RIEULTHIEUTH - 0xA751: 0xCB1E, //HANGUL SYLLABLE SSANGCIEUC OE RIEULPHIEUPH - 0xA752: 0xCB1F, //HANGUL SYLLABLE SSANGCIEUC OE RIEULHIEUH - 0xA753: 0xCB22, //HANGUL SYLLABLE SSANGCIEUC OE PIEUPSIOS - 0xA754: 0xCB23, //HANGUL SYLLABLE SSANGCIEUC OE SIOS - 0xA755: 0xCB24, //HANGUL SYLLABLE SSANGCIEUC OE SSANGSIOS - 0xA756: 0xCB25, //HANGUL SYLLABLE SSANGCIEUC OE IEUNG - 0xA757: 0xCB26, //HANGUL SYLLABLE SSANGCIEUC OE CIEUC - 0xA758: 0xCB27, //HANGUL SYLLABLE SSANGCIEUC OE CHIEUCH - 0xA759: 0xCB28, //HANGUL SYLLABLE SSANGCIEUC OE KHIEUKH - 0xA75A: 0xCB29, //HANGUL SYLLABLE SSANGCIEUC OE THIEUTH - 0xA761: 0xCB2A, //HANGUL SYLLABLE SSANGCIEUC OE PHIEUPH - 0xA762: 0xCB2B, //HANGUL SYLLABLE SSANGCIEUC OE HIEUH - 0xA763: 0xCB2C, //HANGUL SYLLABLE SSANGCIEUC YO - 0xA764: 0xCB2D, //HANGUL SYLLABLE SSANGCIEUC YO KIYEOK - 0xA765: 0xCB2E, //HANGUL SYLLABLE SSANGCIEUC YO SSANGKIYEOK - 0xA766: 0xCB2F, //HANGUL SYLLABLE SSANGCIEUC YO KIYEOKSIOS - 0xA767: 0xCB30, //HANGUL SYLLABLE SSANGCIEUC YO NIEUN - 0xA768: 0xCB31, //HANGUL SYLLABLE SSANGCIEUC YO NIEUNCIEUC - 0xA769: 0xCB32, //HANGUL SYLLABLE SSANGCIEUC YO NIEUNHIEUH - 0xA76A: 0xCB33, //HANGUL SYLLABLE SSANGCIEUC YO TIKEUT - 0xA76B: 0xCB34, //HANGUL SYLLABLE SSANGCIEUC YO RIEUL - 0xA76C: 0xCB35, //HANGUL SYLLABLE SSANGCIEUC YO RIEULKIYEOK - 0xA76D: 0xCB36, //HANGUL SYLLABLE SSANGCIEUC YO RIEULMIEUM - 0xA76E: 0xCB37, //HANGUL SYLLABLE SSANGCIEUC YO RIEULPIEUP - 0xA76F: 0xCB38, //HANGUL SYLLABLE SSANGCIEUC YO RIEULSIOS - 0xA770: 0xCB39, //HANGUL SYLLABLE SSANGCIEUC YO RIEULTHIEUTH - 0xA771: 0xCB3A, //HANGUL SYLLABLE SSANGCIEUC YO RIEULPHIEUPH - 0xA772: 0xCB3B, //HANGUL SYLLABLE SSANGCIEUC YO RIEULHIEUH - 0xA773: 0xCB3C, //HANGUL SYLLABLE SSANGCIEUC YO MIEUM - 0xA774: 0xCB3D, //HANGUL SYLLABLE SSANGCIEUC YO PIEUP - 0xA775: 0xCB3E, //HANGUL SYLLABLE SSANGCIEUC YO PIEUPSIOS - 0xA776: 0xCB3F, //HANGUL SYLLABLE SSANGCIEUC YO SIOS - 0xA777: 0xCB40, //HANGUL SYLLABLE SSANGCIEUC YO SSANGSIOS - 0xA778: 0xCB42, //HANGUL SYLLABLE SSANGCIEUC YO CIEUC - 0xA779: 0xCB43, //HANGUL SYLLABLE SSANGCIEUC YO CHIEUCH - 0xA77A: 0xCB44, //HANGUL SYLLABLE SSANGCIEUC YO KHIEUKH - 0xA781: 0xCB45, //HANGUL SYLLABLE SSANGCIEUC YO THIEUTH - 0xA782: 0xCB46, //HANGUL SYLLABLE SSANGCIEUC YO PHIEUPH - 0xA783: 0xCB47, //HANGUL SYLLABLE SSANGCIEUC YO HIEUH - 0xA784: 0xCB4A, //HANGUL SYLLABLE SSANGCIEUC U SSANGKIYEOK - 0xA785: 0xCB4B, //HANGUL SYLLABLE SSANGCIEUC U KIYEOKSIOS - 0xA786: 0xCB4D, //HANGUL SYLLABLE SSANGCIEUC U NIEUNCIEUC - 0xA787: 0xCB4E, //HANGUL SYLLABLE SSANGCIEUC U NIEUNHIEUH - 0xA788: 0xCB4F, //HANGUL SYLLABLE SSANGCIEUC U TIKEUT - 0xA789: 0xCB51, //HANGUL SYLLABLE SSANGCIEUC U RIEULKIYEOK - 0xA78A: 0xCB52, //HANGUL SYLLABLE SSANGCIEUC U RIEULMIEUM - 0xA78B: 0xCB53, //HANGUL SYLLABLE SSANGCIEUC U RIEULPIEUP - 0xA78C: 0xCB54, //HANGUL SYLLABLE SSANGCIEUC U RIEULSIOS - 0xA78D: 0xCB55, //HANGUL SYLLABLE SSANGCIEUC U RIEULTHIEUTH - 0xA78E: 0xCB56, //HANGUL SYLLABLE SSANGCIEUC U RIEULPHIEUPH - 0xA78F: 0xCB57, //HANGUL SYLLABLE SSANGCIEUC U RIEULHIEUH - 0xA790: 0xCB5A, //HANGUL SYLLABLE SSANGCIEUC U PIEUPSIOS - 0xA791: 0xCB5B, //HANGUL SYLLABLE SSANGCIEUC U SIOS - 0xA792: 0xCB5C, //HANGUL SYLLABLE SSANGCIEUC U SSANGSIOS - 0xA793: 0xCB5E, //HANGUL SYLLABLE SSANGCIEUC U CIEUC - 0xA794: 0xCB5F, //HANGUL SYLLABLE SSANGCIEUC U CHIEUCH - 0xA795: 0xCB60, //HANGUL SYLLABLE SSANGCIEUC U KHIEUKH - 0xA796: 0xCB61, //HANGUL SYLLABLE SSANGCIEUC U THIEUTH - 0xA797: 0xCB62, //HANGUL SYLLABLE SSANGCIEUC U PHIEUPH - 0xA798: 0xCB63, //HANGUL SYLLABLE SSANGCIEUC U HIEUH - 0xA799: 0xCB65, //HANGUL SYLLABLE SSANGCIEUC WEO KIYEOK - 0xA79A: 0xCB66, //HANGUL SYLLABLE SSANGCIEUC WEO SSANGKIYEOK - 0xA79B: 0xCB67, //HANGUL SYLLABLE SSANGCIEUC WEO KIYEOKSIOS - 0xA79C: 0xCB68, //HANGUL SYLLABLE SSANGCIEUC WEO NIEUN - 0xA79D: 0xCB69, //HANGUL SYLLABLE SSANGCIEUC WEO NIEUNCIEUC - 0xA79E: 0xCB6A, //HANGUL SYLLABLE SSANGCIEUC WEO NIEUNHIEUH - 0xA79F: 0xCB6B, //HANGUL SYLLABLE SSANGCIEUC WEO TIKEUT - 0xA7A0: 0xCB6C, //HANGUL SYLLABLE SSANGCIEUC WEO RIEUL - 0xA7A1: 0x3395, //SQUARE MU L - 0xA7A2: 0x3396, //SQUARE ML - 0xA7A3: 0x3397, //SQUARE DL - 0xA7A4: 0x2113, //SCRIPT SMALL L - 0xA7A5: 0x3398, //SQUARE KL - 0xA7A6: 0x33C4, //SQUARE CC - 0xA7A7: 0x33A3, //SQUARE MM CUBED - 0xA7A8: 0x33A4, //SQUARE CM CUBED - 0xA7A9: 0x33A5, //SQUARE M CUBED - 0xA7AA: 0x33A6, //SQUARE KM CUBED - 0xA7AB: 0x3399, //SQUARE FM - 0xA7AC: 0x339A, //SQUARE NM - 0xA7AD: 0x339B, //SQUARE MU M - 0xA7AE: 0x339C, //SQUARE MM - 0xA7AF: 0x339D, //SQUARE CM - 0xA7B0: 0x339E, //SQUARE KM - 0xA7B1: 0x339F, //SQUARE MM SQUARED - 0xA7B2: 0x33A0, //SQUARE CM SQUARED - 0xA7B3: 0x33A1, //SQUARE M SQUARED - 0xA7B4: 0x33A2, //SQUARE KM SQUARED - 0xA7B5: 0x33CA, //SQUARE HA - 0xA7B6: 0x338D, //SQUARE MU G - 0xA7B7: 0x338E, //SQUARE MG - 0xA7B8: 0x338F, //SQUARE KG - 0xA7B9: 0x33CF, //SQUARE KT - 0xA7BA: 0x3388, //SQUARE CAL - 0xA7BB: 0x3389, //SQUARE KCAL - 0xA7BC: 0x33C8, //SQUARE DB - 0xA7BD: 0x33A7, //SQUARE M OVER S - 0xA7BE: 0x33A8, //SQUARE M OVER S SQUARED - 0xA7BF: 0x33B0, //SQUARE PS - 0xA7C0: 0x33B1, //SQUARE NS - 0xA7C1: 0x33B2, //SQUARE MU S - 0xA7C2: 0x33B3, //SQUARE MS - 0xA7C3: 0x33B4, //SQUARE PV - 0xA7C4: 0x33B5, //SQUARE NV - 0xA7C5: 0x33B6, //SQUARE MU V - 0xA7C6: 0x33B7, //SQUARE MV - 0xA7C7: 0x33B8, //SQUARE KV - 0xA7C8: 0x33B9, //SQUARE MV MEGA - 0xA7C9: 0x3380, //SQUARE PA AMPS - 0xA7CA: 0x3381, //SQUARE NA - 0xA7CB: 0x3382, //SQUARE MU A - 0xA7CC: 0x3383, //SQUARE MA - 0xA7CD: 0x3384, //SQUARE KA - 0xA7CE: 0x33BA, //SQUARE PW - 0xA7CF: 0x33BB, //SQUARE NW - 0xA7D0: 0x33BC, //SQUARE MU W - 0xA7D1: 0x33BD, //SQUARE MW - 0xA7D2: 0x33BE, //SQUARE KW - 0xA7D3: 0x33BF, //SQUARE MW MEGA - 0xA7D4: 0x3390, //SQUARE HZ - 0xA7D5: 0x3391, //SQUARE KHZ - 0xA7D6: 0x3392, //SQUARE MHZ - 0xA7D7: 0x3393, //SQUARE GHZ - 0xA7D8: 0x3394, //SQUARE THZ - 0xA7D9: 0x2126, //OHM SIGN - 0xA7DA: 0x33C0, //SQUARE K OHM - 0xA7DB: 0x33C1, //SQUARE M OHM - 0xA7DC: 0x338A, //SQUARE PF - 0xA7DD: 0x338B, //SQUARE NF - 0xA7DE: 0x338C, //SQUARE MU F - 0xA7DF: 0x33D6, //SQUARE MOL - 0xA7E0: 0x33C5, //SQUARE CD - 0xA7E1: 0x33AD, //SQUARE RAD - 0xA7E2: 0x33AE, //SQUARE RAD OVER S - 0xA7E3: 0x33AF, //SQUARE RAD OVER S SQUARED - 0xA7E4: 0x33DB, //SQUARE SR - 0xA7E5: 0x33A9, //SQUARE PA - 0xA7E6: 0x33AA, //SQUARE KPA - 0xA7E7: 0x33AB, //SQUARE MPA - 0xA7E8: 0x33AC, //SQUARE GPA - 0xA7E9: 0x33DD, //SQUARE WB - 0xA7EA: 0x33D0, //SQUARE LM - 0xA7EB: 0x33D3, //SQUARE LX - 0xA7EC: 0x33C3, //SQUARE BQ - 0xA7ED: 0x33C9, //SQUARE GY - 0xA7EE: 0x33DC, //SQUARE SV - 0xA7EF: 0x33C6, //SQUARE C OVER KG - 0xA841: 0xCB6D, //HANGUL SYLLABLE SSANGCIEUC WEO RIEULKIYEOK - 0xA842: 0xCB6E, //HANGUL SYLLABLE SSANGCIEUC WEO RIEULMIEUM - 0xA843: 0xCB6F, //HANGUL SYLLABLE SSANGCIEUC WEO RIEULPIEUP - 0xA844: 0xCB70, //HANGUL SYLLABLE SSANGCIEUC WEO RIEULSIOS - 0xA845: 0xCB71, //HANGUL SYLLABLE SSANGCIEUC WEO RIEULTHIEUTH - 0xA846: 0xCB72, //HANGUL SYLLABLE SSANGCIEUC WEO RIEULPHIEUPH - 0xA847: 0xCB73, //HANGUL SYLLABLE SSANGCIEUC WEO RIEULHIEUH - 0xA848: 0xCB74, //HANGUL SYLLABLE SSANGCIEUC WEO MIEUM - 0xA849: 0xCB75, //HANGUL SYLLABLE SSANGCIEUC WEO PIEUP - 0xA84A: 0xCB76, //HANGUL SYLLABLE SSANGCIEUC WEO PIEUPSIOS - 0xA84B: 0xCB77, //HANGUL SYLLABLE SSANGCIEUC WEO SIOS - 0xA84C: 0xCB7A, //HANGUL SYLLABLE SSANGCIEUC WEO CIEUC - 0xA84D: 0xCB7B, //HANGUL SYLLABLE SSANGCIEUC WEO CHIEUCH - 0xA84E: 0xCB7C, //HANGUL SYLLABLE SSANGCIEUC WEO KHIEUKH - 0xA84F: 0xCB7D, //HANGUL SYLLABLE SSANGCIEUC WEO THIEUTH - 0xA850: 0xCB7E, //HANGUL SYLLABLE SSANGCIEUC WEO PHIEUPH - 0xA851: 0xCB7F, //HANGUL SYLLABLE SSANGCIEUC WEO HIEUH - 0xA852: 0xCB80, //HANGUL SYLLABLE SSANGCIEUC WE - 0xA853: 0xCB81, //HANGUL SYLLABLE SSANGCIEUC WE KIYEOK - 0xA854: 0xCB82, //HANGUL SYLLABLE SSANGCIEUC WE SSANGKIYEOK - 0xA855: 0xCB83, //HANGUL SYLLABLE SSANGCIEUC WE KIYEOKSIOS - 0xA856: 0xCB84, //HANGUL SYLLABLE SSANGCIEUC WE NIEUN - 0xA857: 0xCB85, //HANGUL SYLLABLE SSANGCIEUC WE NIEUNCIEUC - 0xA858: 0xCB86, //HANGUL SYLLABLE SSANGCIEUC WE NIEUNHIEUH - 0xA859: 0xCB87, //HANGUL SYLLABLE SSANGCIEUC WE TIKEUT - 0xA85A: 0xCB88, //HANGUL SYLLABLE SSANGCIEUC WE RIEUL - 0xA861: 0xCB89, //HANGUL SYLLABLE SSANGCIEUC WE RIEULKIYEOK - 0xA862: 0xCB8A, //HANGUL SYLLABLE SSANGCIEUC WE RIEULMIEUM - 0xA863: 0xCB8B, //HANGUL SYLLABLE SSANGCIEUC WE RIEULPIEUP - 0xA864: 0xCB8C, //HANGUL SYLLABLE SSANGCIEUC WE RIEULSIOS - 0xA865: 0xCB8D, //HANGUL SYLLABLE SSANGCIEUC WE RIEULTHIEUTH - 0xA866: 0xCB8E, //HANGUL SYLLABLE SSANGCIEUC WE RIEULPHIEUPH - 0xA867: 0xCB8F, //HANGUL SYLLABLE SSANGCIEUC WE RIEULHIEUH - 0xA868: 0xCB90, //HANGUL SYLLABLE SSANGCIEUC WE MIEUM - 0xA869: 0xCB91, //HANGUL SYLLABLE SSANGCIEUC WE PIEUP - 0xA86A: 0xCB92, //HANGUL SYLLABLE SSANGCIEUC WE PIEUPSIOS - 0xA86B: 0xCB93, //HANGUL SYLLABLE SSANGCIEUC WE SIOS - 0xA86C: 0xCB94, //HANGUL SYLLABLE SSANGCIEUC WE SSANGSIOS - 0xA86D: 0xCB95, //HANGUL SYLLABLE SSANGCIEUC WE IEUNG - 0xA86E: 0xCB96, //HANGUL SYLLABLE SSANGCIEUC WE CIEUC - 0xA86F: 0xCB97, //HANGUL SYLLABLE SSANGCIEUC WE CHIEUCH - 0xA870: 0xCB98, //HANGUL SYLLABLE SSANGCIEUC WE KHIEUKH - 0xA871: 0xCB99, //HANGUL SYLLABLE SSANGCIEUC WE THIEUTH - 0xA872: 0xCB9A, //HANGUL SYLLABLE SSANGCIEUC WE PHIEUPH - 0xA873: 0xCB9B, //HANGUL SYLLABLE SSANGCIEUC WE HIEUH - 0xA874: 0xCB9D, //HANGUL SYLLABLE SSANGCIEUC WI KIYEOK - 0xA875: 0xCB9E, //HANGUL SYLLABLE SSANGCIEUC WI SSANGKIYEOK - 0xA876: 0xCB9F, //HANGUL SYLLABLE SSANGCIEUC WI KIYEOKSIOS - 0xA877: 0xCBA0, //HANGUL SYLLABLE SSANGCIEUC WI NIEUN - 0xA878: 0xCBA1, //HANGUL SYLLABLE SSANGCIEUC WI NIEUNCIEUC - 0xA879: 0xCBA2, //HANGUL SYLLABLE SSANGCIEUC WI NIEUNHIEUH - 0xA87A: 0xCBA3, //HANGUL SYLLABLE SSANGCIEUC WI TIKEUT - 0xA881: 0xCBA4, //HANGUL SYLLABLE SSANGCIEUC WI RIEUL - 0xA882: 0xCBA5, //HANGUL SYLLABLE SSANGCIEUC WI RIEULKIYEOK - 0xA883: 0xCBA6, //HANGUL SYLLABLE SSANGCIEUC WI RIEULMIEUM - 0xA884: 0xCBA7, //HANGUL SYLLABLE SSANGCIEUC WI RIEULPIEUP - 0xA885: 0xCBA8, //HANGUL SYLLABLE SSANGCIEUC WI RIEULSIOS - 0xA886: 0xCBA9, //HANGUL SYLLABLE SSANGCIEUC WI RIEULTHIEUTH - 0xA887: 0xCBAA, //HANGUL SYLLABLE SSANGCIEUC WI RIEULPHIEUPH - 0xA888: 0xCBAB, //HANGUL SYLLABLE SSANGCIEUC WI RIEULHIEUH - 0xA889: 0xCBAC, //HANGUL SYLLABLE SSANGCIEUC WI MIEUM - 0xA88A: 0xCBAD, //HANGUL SYLLABLE SSANGCIEUC WI PIEUP - 0xA88B: 0xCBAE, //HANGUL SYLLABLE SSANGCIEUC WI PIEUPSIOS - 0xA88C: 0xCBAF, //HANGUL SYLLABLE SSANGCIEUC WI SIOS - 0xA88D: 0xCBB0, //HANGUL SYLLABLE SSANGCIEUC WI SSANGSIOS - 0xA88E: 0xCBB1, //HANGUL SYLLABLE SSANGCIEUC WI IEUNG - 0xA88F: 0xCBB2, //HANGUL SYLLABLE SSANGCIEUC WI CIEUC - 0xA890: 0xCBB3, //HANGUL SYLLABLE SSANGCIEUC WI CHIEUCH - 0xA891: 0xCBB4, //HANGUL SYLLABLE SSANGCIEUC WI KHIEUKH - 0xA892: 0xCBB5, //HANGUL SYLLABLE SSANGCIEUC WI THIEUTH - 0xA893: 0xCBB6, //HANGUL SYLLABLE SSANGCIEUC WI PHIEUPH - 0xA894: 0xCBB7, //HANGUL SYLLABLE SSANGCIEUC WI HIEUH - 0xA895: 0xCBB9, //HANGUL SYLLABLE SSANGCIEUC YU KIYEOK - 0xA896: 0xCBBA, //HANGUL SYLLABLE SSANGCIEUC YU SSANGKIYEOK - 0xA897: 0xCBBB, //HANGUL SYLLABLE SSANGCIEUC YU KIYEOKSIOS - 0xA898: 0xCBBC, //HANGUL SYLLABLE SSANGCIEUC YU NIEUN - 0xA899: 0xCBBD, //HANGUL SYLLABLE SSANGCIEUC YU NIEUNCIEUC - 0xA89A: 0xCBBE, //HANGUL SYLLABLE SSANGCIEUC YU NIEUNHIEUH - 0xA89B: 0xCBBF, //HANGUL SYLLABLE SSANGCIEUC YU TIKEUT - 0xA89C: 0xCBC0, //HANGUL SYLLABLE SSANGCIEUC YU RIEUL - 0xA89D: 0xCBC1, //HANGUL SYLLABLE SSANGCIEUC YU RIEULKIYEOK - 0xA89E: 0xCBC2, //HANGUL SYLLABLE SSANGCIEUC YU RIEULMIEUM - 0xA89F: 0xCBC3, //HANGUL SYLLABLE SSANGCIEUC YU RIEULPIEUP - 0xA8A0: 0xCBC4, //HANGUL SYLLABLE SSANGCIEUC YU RIEULSIOS - 0xA8A1: 0x00C6, //LATIN CAPITAL LETTER AE - 0xA8A2: 0x00D0, //LATIN CAPITAL LETTER ETH - 0xA8A3: 0x00AA, //FEMININE ORDINAL INDICATOR - 0xA8A4: 0x0126, //LATIN CAPITAL LETTER H WITH STROKE - 0xA8A6: 0x0132, //LATIN CAPITAL LIGATURE IJ - 0xA8A8: 0x013F, //LATIN CAPITAL LETTER L WITH MIDDLE DOT - 0xA8A9: 0x0141, //LATIN CAPITAL LETTER L WITH STROKE - 0xA8AA: 0x00D8, //LATIN CAPITAL LETTER O WITH STROKE - 0xA8AB: 0x0152, //LATIN CAPITAL LIGATURE OE - 0xA8AC: 0x00BA, //MASCULINE ORDINAL INDICATOR - 0xA8AD: 0x00DE, //LATIN CAPITAL LETTER THORN - 0xA8AE: 0x0166, //LATIN CAPITAL LETTER T WITH STROKE - 0xA8AF: 0x014A, //LATIN CAPITAL LETTER ENG - 0xA8B1: 0x3260, //CIRCLED HANGUL KIYEOK - 0xA8B2: 0x3261, //CIRCLED HANGUL NIEUN - 0xA8B3: 0x3262, //CIRCLED HANGUL TIKEUT - 0xA8B4: 0x3263, //CIRCLED HANGUL RIEUL - 0xA8B5: 0x3264, //CIRCLED HANGUL MIEUM - 0xA8B6: 0x3265, //CIRCLED HANGUL PIEUP - 0xA8B7: 0x3266, //CIRCLED HANGUL SIOS - 0xA8B8: 0x3267, //CIRCLED HANGUL IEUNG - 0xA8B9: 0x3268, //CIRCLED HANGUL CIEUC - 0xA8BA: 0x3269, //CIRCLED HANGUL CHIEUCH - 0xA8BB: 0x326A, //CIRCLED HANGUL KHIEUKH - 0xA8BC: 0x326B, //CIRCLED HANGUL THIEUTH - 0xA8BD: 0x326C, //CIRCLED HANGUL PHIEUPH - 0xA8BE: 0x326D, //CIRCLED HANGUL HIEUH - 0xA8BF: 0x326E, //CIRCLED HANGUL KIYEOK A - 0xA8C0: 0x326F, //CIRCLED HANGUL NIEUN A - 0xA8C1: 0x3270, //CIRCLED HANGUL TIKEUT A - 0xA8C2: 0x3271, //CIRCLED HANGUL RIEUL A - 0xA8C3: 0x3272, //CIRCLED HANGUL MIEUM A - 0xA8C4: 0x3273, //CIRCLED HANGUL PIEUP A - 0xA8C5: 0x3274, //CIRCLED HANGUL SIOS A - 0xA8C6: 0x3275, //CIRCLED HANGUL IEUNG A - 0xA8C7: 0x3276, //CIRCLED HANGUL CIEUC A - 0xA8C8: 0x3277, //CIRCLED HANGUL CHIEUCH A - 0xA8C9: 0x3278, //CIRCLED HANGUL KHIEUKH A - 0xA8CA: 0x3279, //CIRCLED HANGUL THIEUTH A - 0xA8CB: 0x327A, //CIRCLED HANGUL PHIEUPH A - 0xA8CC: 0x327B, //CIRCLED HANGUL HIEUH A - 0xA8CD: 0x24D0, //CIRCLED LATIN SMALL LETTER A - 0xA8CE: 0x24D1, //CIRCLED LATIN SMALL LETTER B - 0xA8CF: 0x24D2, //CIRCLED LATIN SMALL LETTER C - 0xA8D0: 0x24D3, //CIRCLED LATIN SMALL LETTER D - 0xA8D1: 0x24D4, //CIRCLED LATIN SMALL LETTER E - 0xA8D2: 0x24D5, //CIRCLED LATIN SMALL LETTER F - 0xA8D3: 0x24D6, //CIRCLED LATIN SMALL LETTER G - 0xA8D4: 0x24D7, //CIRCLED LATIN SMALL LETTER H - 0xA8D5: 0x24D8, //CIRCLED LATIN SMALL LETTER I - 0xA8D6: 0x24D9, //CIRCLED LATIN SMALL LETTER J - 0xA8D7: 0x24DA, //CIRCLED LATIN SMALL LETTER K - 0xA8D8: 0x24DB, //CIRCLED LATIN SMALL LETTER L - 0xA8D9: 0x24DC, //CIRCLED LATIN SMALL LETTER M - 0xA8DA: 0x24DD, //CIRCLED LATIN SMALL LETTER N - 0xA8DB: 0x24DE, //CIRCLED LATIN SMALL LETTER O - 0xA8DC: 0x24DF, //CIRCLED LATIN SMALL LETTER P - 0xA8DD: 0x24E0, //CIRCLED LATIN SMALL LETTER Q - 0xA8DE: 0x24E1, //CIRCLED LATIN SMALL LETTER R - 0xA8DF: 0x24E2, //CIRCLED LATIN SMALL LETTER S - 0xA8E0: 0x24E3, //CIRCLED LATIN SMALL LETTER T - 0xA8E1: 0x24E4, //CIRCLED LATIN SMALL LETTER U - 0xA8E2: 0x24E5, //CIRCLED LATIN SMALL LETTER V - 0xA8E3: 0x24E6, //CIRCLED LATIN SMALL LETTER W - 0xA8E4: 0x24E7, //CIRCLED LATIN SMALL LETTER X - 0xA8E5: 0x24E8, //CIRCLED LATIN SMALL LETTER Y - 0xA8E6: 0x24E9, //CIRCLED LATIN SMALL LETTER Z - 0xA8E7: 0x2460, //CIRCLED DIGIT ONE - 0xA8E8: 0x2461, //CIRCLED DIGIT TWO - 0xA8E9: 0x2462, //CIRCLED DIGIT THREE - 0xA8EA: 0x2463, //CIRCLED DIGIT FOUR - 0xA8EB: 0x2464, //CIRCLED DIGIT FIVE - 0xA8EC: 0x2465, //CIRCLED DIGIT SIX - 0xA8ED: 0x2466, //CIRCLED DIGIT SEVEN - 0xA8EE: 0x2467, //CIRCLED DIGIT EIGHT - 0xA8EF: 0x2468, //CIRCLED DIGIT NINE - 0xA8F0: 0x2469, //CIRCLED NUMBER TEN - 0xA8F1: 0x246A, //CIRCLED NUMBER ELEVEN - 0xA8F2: 0x246B, //CIRCLED NUMBER TWELVE - 0xA8F3: 0x246C, //CIRCLED NUMBER THIRTEEN - 0xA8F4: 0x246D, //CIRCLED NUMBER FOURTEEN - 0xA8F5: 0x246E, //CIRCLED NUMBER FIFTEEN - 0xA8F6: 0x00BD, //VULGAR FRACTION ONE HALF - 0xA8F7: 0x2153, //VULGAR FRACTION ONE THIRD - 0xA8F8: 0x2154, //VULGAR FRACTION TWO THIRDS - 0xA8F9: 0x00BC, //VULGAR FRACTION ONE QUARTER - 0xA8FA: 0x00BE, //VULGAR FRACTION THREE QUARTERS - 0xA8FB: 0x215B, //VULGAR FRACTION ONE EIGHTH - 0xA8FC: 0x215C, //VULGAR FRACTION THREE EIGHTHS - 0xA8FD: 0x215D, //VULGAR FRACTION FIVE EIGHTHS - 0xA8FE: 0x215E, //VULGAR FRACTION SEVEN EIGHTHS - 0xA941: 0xCBC5, //HANGUL SYLLABLE SSANGCIEUC YU RIEULTHIEUTH - 0xA942: 0xCBC6, //HANGUL SYLLABLE SSANGCIEUC YU RIEULPHIEUPH - 0xA943: 0xCBC7, //HANGUL SYLLABLE SSANGCIEUC YU RIEULHIEUH - 0xA944: 0xCBC8, //HANGUL SYLLABLE SSANGCIEUC YU MIEUM - 0xA945: 0xCBC9, //HANGUL SYLLABLE SSANGCIEUC YU PIEUP - 0xA946: 0xCBCA, //HANGUL SYLLABLE SSANGCIEUC YU PIEUPSIOS - 0xA947: 0xCBCB, //HANGUL SYLLABLE SSANGCIEUC YU SIOS - 0xA948: 0xCBCC, //HANGUL SYLLABLE SSANGCIEUC YU SSANGSIOS - 0xA949: 0xCBCD, //HANGUL SYLLABLE SSANGCIEUC YU IEUNG - 0xA94A: 0xCBCE, //HANGUL SYLLABLE SSANGCIEUC YU CIEUC - 0xA94B: 0xCBCF, //HANGUL SYLLABLE SSANGCIEUC YU CHIEUCH - 0xA94C: 0xCBD0, //HANGUL SYLLABLE SSANGCIEUC YU KHIEUKH - 0xA94D: 0xCBD1, //HANGUL SYLLABLE SSANGCIEUC YU THIEUTH - 0xA94E: 0xCBD2, //HANGUL SYLLABLE SSANGCIEUC YU PHIEUPH - 0xA94F: 0xCBD3, //HANGUL SYLLABLE SSANGCIEUC YU HIEUH - 0xA950: 0xCBD5, //HANGUL SYLLABLE SSANGCIEUC EU KIYEOK - 0xA951: 0xCBD6, //HANGUL SYLLABLE SSANGCIEUC EU SSANGKIYEOK - 0xA952: 0xCBD7, //HANGUL SYLLABLE SSANGCIEUC EU KIYEOKSIOS - 0xA953: 0xCBD8, //HANGUL SYLLABLE SSANGCIEUC EU NIEUN - 0xA954: 0xCBD9, //HANGUL SYLLABLE SSANGCIEUC EU NIEUNCIEUC - 0xA955: 0xCBDA, //HANGUL SYLLABLE SSANGCIEUC EU NIEUNHIEUH - 0xA956: 0xCBDB, //HANGUL SYLLABLE SSANGCIEUC EU TIKEUT - 0xA957: 0xCBDC, //HANGUL SYLLABLE SSANGCIEUC EU RIEUL - 0xA958: 0xCBDD, //HANGUL SYLLABLE SSANGCIEUC EU RIEULKIYEOK - 0xA959: 0xCBDE, //HANGUL SYLLABLE SSANGCIEUC EU RIEULMIEUM - 0xA95A: 0xCBDF, //HANGUL SYLLABLE SSANGCIEUC EU RIEULPIEUP - 0xA961: 0xCBE0, //HANGUL SYLLABLE SSANGCIEUC EU RIEULSIOS - 0xA962: 0xCBE1, //HANGUL SYLLABLE SSANGCIEUC EU RIEULTHIEUTH - 0xA963: 0xCBE2, //HANGUL SYLLABLE SSANGCIEUC EU RIEULPHIEUPH - 0xA964: 0xCBE3, //HANGUL SYLLABLE SSANGCIEUC EU RIEULHIEUH - 0xA965: 0xCBE5, //HANGUL SYLLABLE SSANGCIEUC EU PIEUP - 0xA966: 0xCBE6, //HANGUL SYLLABLE SSANGCIEUC EU PIEUPSIOS - 0xA967: 0xCBE8, //HANGUL SYLLABLE SSANGCIEUC EU SSANGSIOS - 0xA968: 0xCBEA, //HANGUL SYLLABLE SSANGCIEUC EU CIEUC - 0xA969: 0xCBEB, //HANGUL SYLLABLE SSANGCIEUC EU CHIEUCH - 0xA96A: 0xCBEC, //HANGUL SYLLABLE SSANGCIEUC EU KHIEUKH - 0xA96B: 0xCBED, //HANGUL SYLLABLE SSANGCIEUC EU THIEUTH - 0xA96C: 0xCBEE, //HANGUL SYLLABLE SSANGCIEUC EU PHIEUPH - 0xA96D: 0xCBEF, //HANGUL SYLLABLE SSANGCIEUC EU HIEUH - 0xA96E: 0xCBF0, //HANGUL SYLLABLE SSANGCIEUC YI - 0xA96F: 0xCBF1, //HANGUL SYLLABLE SSANGCIEUC YI KIYEOK - 0xA970: 0xCBF2, //HANGUL SYLLABLE SSANGCIEUC YI SSANGKIYEOK - 0xA971: 0xCBF3, //HANGUL SYLLABLE SSANGCIEUC YI KIYEOKSIOS - 0xA972: 0xCBF4, //HANGUL SYLLABLE SSANGCIEUC YI NIEUN - 0xA973: 0xCBF5, //HANGUL SYLLABLE SSANGCIEUC YI NIEUNCIEUC - 0xA974: 0xCBF6, //HANGUL SYLLABLE SSANGCIEUC YI NIEUNHIEUH - 0xA975: 0xCBF7, //HANGUL SYLLABLE SSANGCIEUC YI TIKEUT - 0xA976: 0xCBF8, //HANGUL SYLLABLE SSANGCIEUC YI RIEUL - 0xA977: 0xCBF9, //HANGUL SYLLABLE SSANGCIEUC YI RIEULKIYEOK - 0xA978: 0xCBFA, //HANGUL SYLLABLE SSANGCIEUC YI RIEULMIEUM - 0xA979: 0xCBFB, //HANGUL SYLLABLE SSANGCIEUC YI RIEULPIEUP - 0xA97A: 0xCBFC, //HANGUL SYLLABLE SSANGCIEUC YI RIEULSIOS - 0xA981: 0xCBFD, //HANGUL SYLLABLE SSANGCIEUC YI RIEULTHIEUTH - 0xA982: 0xCBFE, //HANGUL SYLLABLE SSANGCIEUC YI RIEULPHIEUPH - 0xA983: 0xCBFF, //HANGUL SYLLABLE SSANGCIEUC YI RIEULHIEUH - 0xA984: 0xCC00, //HANGUL SYLLABLE SSANGCIEUC YI MIEUM - 0xA985: 0xCC01, //HANGUL SYLLABLE SSANGCIEUC YI PIEUP - 0xA986: 0xCC02, //HANGUL SYLLABLE SSANGCIEUC YI PIEUPSIOS - 0xA987: 0xCC03, //HANGUL SYLLABLE SSANGCIEUC YI SIOS - 0xA988: 0xCC04, //HANGUL SYLLABLE SSANGCIEUC YI SSANGSIOS - 0xA989: 0xCC05, //HANGUL SYLLABLE SSANGCIEUC YI IEUNG - 0xA98A: 0xCC06, //HANGUL SYLLABLE SSANGCIEUC YI CIEUC - 0xA98B: 0xCC07, //HANGUL SYLLABLE SSANGCIEUC YI CHIEUCH - 0xA98C: 0xCC08, //HANGUL SYLLABLE SSANGCIEUC YI KHIEUKH - 0xA98D: 0xCC09, //HANGUL SYLLABLE SSANGCIEUC YI THIEUTH - 0xA98E: 0xCC0A, //HANGUL SYLLABLE SSANGCIEUC YI PHIEUPH - 0xA98F: 0xCC0B, //HANGUL SYLLABLE SSANGCIEUC YI HIEUH - 0xA990: 0xCC0E, //HANGUL SYLLABLE SSANGCIEUC I SSANGKIYEOK - 0xA991: 0xCC0F, //HANGUL SYLLABLE SSANGCIEUC I KIYEOKSIOS - 0xA992: 0xCC11, //HANGUL SYLLABLE SSANGCIEUC I NIEUNCIEUC - 0xA993: 0xCC12, //HANGUL SYLLABLE SSANGCIEUC I NIEUNHIEUH - 0xA994: 0xCC13, //HANGUL SYLLABLE SSANGCIEUC I TIKEUT - 0xA995: 0xCC15, //HANGUL SYLLABLE SSANGCIEUC I RIEULKIYEOK - 0xA996: 0xCC16, //HANGUL SYLLABLE SSANGCIEUC I RIEULMIEUM - 0xA997: 0xCC17, //HANGUL SYLLABLE SSANGCIEUC I RIEULPIEUP - 0xA998: 0xCC18, //HANGUL SYLLABLE SSANGCIEUC I RIEULSIOS - 0xA999: 0xCC19, //HANGUL SYLLABLE SSANGCIEUC I RIEULTHIEUTH - 0xA99A: 0xCC1A, //HANGUL SYLLABLE SSANGCIEUC I RIEULPHIEUPH - 0xA99B: 0xCC1B, //HANGUL SYLLABLE SSANGCIEUC I RIEULHIEUH - 0xA99C: 0xCC1E, //HANGUL SYLLABLE SSANGCIEUC I PIEUPSIOS - 0xA99D: 0xCC1F, //HANGUL SYLLABLE SSANGCIEUC I SIOS - 0xA99E: 0xCC20, //HANGUL SYLLABLE SSANGCIEUC I SSANGSIOS - 0xA99F: 0xCC23, //HANGUL SYLLABLE SSANGCIEUC I CHIEUCH - 0xA9A0: 0xCC24, //HANGUL SYLLABLE SSANGCIEUC I KHIEUKH - 0xA9A1: 0x00E6, //LATIN SMALL LETTER AE - 0xA9A2: 0x0111, //LATIN SMALL LETTER D WITH STROKE - 0xA9A3: 0x00F0, //LATIN SMALL LETTER ETH - 0xA9A4: 0x0127, //LATIN SMALL LETTER H WITH STROKE - 0xA9A5: 0x0131, //LATIN SMALL LETTER DOTLESS I - 0xA9A6: 0x0133, //LATIN SMALL LIGATURE IJ - 0xA9A7: 0x0138, //LATIN SMALL LETTER KRA - 0xA9A8: 0x0140, //LATIN SMALL LETTER L WITH MIDDLE DOT - 0xA9A9: 0x0142, //LATIN SMALL LETTER L WITH STROKE - 0xA9AA: 0x00F8, //LATIN SMALL LETTER O WITH STROKE - 0xA9AB: 0x0153, //LATIN SMALL LIGATURE OE - 0xA9AC: 0x00DF, //LATIN SMALL LETTER SHARP S - 0xA9AD: 0x00FE, //LATIN SMALL LETTER THORN - 0xA9AE: 0x0167, //LATIN SMALL LETTER T WITH STROKE - 0xA9AF: 0x014B, //LATIN SMALL LETTER ENG - 0xA9B0: 0x0149, //LATIN SMALL LETTER N PRECEDED BY APOSTROPHE - 0xA9B1: 0x3200, //PARENTHESIZED HANGUL KIYEOK - 0xA9B2: 0x3201, //PARENTHESIZED HANGUL NIEUN - 0xA9B3: 0x3202, //PARENTHESIZED HANGUL TIKEUT - 0xA9B4: 0x3203, //PARENTHESIZED HANGUL RIEUL - 0xA9B5: 0x3204, //PARENTHESIZED HANGUL MIEUM - 0xA9B6: 0x3205, //PARENTHESIZED HANGUL PIEUP - 0xA9B7: 0x3206, //PARENTHESIZED HANGUL SIOS - 0xA9B8: 0x3207, //PARENTHESIZED HANGUL IEUNG - 0xA9B9: 0x3208, //PARENTHESIZED HANGUL CIEUC - 0xA9BA: 0x3209, //PARENTHESIZED HANGUL CHIEUCH - 0xA9BB: 0x320A, //PARENTHESIZED HANGUL KHIEUKH - 0xA9BC: 0x320B, //PARENTHESIZED HANGUL THIEUTH - 0xA9BD: 0x320C, //PARENTHESIZED HANGUL PHIEUPH - 0xA9BE: 0x320D, //PARENTHESIZED HANGUL HIEUH - 0xA9BF: 0x320E, //PARENTHESIZED HANGUL KIYEOK A - 0xA9C0: 0x320F, //PARENTHESIZED HANGUL NIEUN A - 0xA9C1: 0x3210, //PARENTHESIZED HANGUL TIKEUT A - 0xA9C2: 0x3211, //PARENTHESIZED HANGUL RIEUL A - 0xA9C3: 0x3212, //PARENTHESIZED HANGUL MIEUM A - 0xA9C4: 0x3213, //PARENTHESIZED HANGUL PIEUP A - 0xA9C5: 0x3214, //PARENTHESIZED HANGUL SIOS A - 0xA9C6: 0x3215, //PARENTHESIZED HANGUL IEUNG A - 0xA9C7: 0x3216, //PARENTHESIZED HANGUL CIEUC A - 0xA9C8: 0x3217, //PARENTHESIZED HANGUL CHIEUCH A - 0xA9C9: 0x3218, //PARENTHESIZED HANGUL KHIEUKH A - 0xA9CA: 0x3219, //PARENTHESIZED HANGUL THIEUTH A - 0xA9CB: 0x321A, //PARENTHESIZED HANGUL PHIEUPH A - 0xA9CC: 0x321B, //PARENTHESIZED HANGUL HIEUH A - 0xA9CD: 0x249C, //PARENTHESIZED LATIN SMALL LETTER A - 0xA9CE: 0x249D, //PARENTHESIZED LATIN SMALL LETTER B - 0xA9CF: 0x249E, //PARENTHESIZED LATIN SMALL LETTER C - 0xA9D0: 0x249F, //PARENTHESIZED LATIN SMALL LETTER D - 0xA9D1: 0x24A0, //PARENTHESIZED LATIN SMALL LETTER E - 0xA9D2: 0x24A1, //PARENTHESIZED LATIN SMALL LETTER F - 0xA9D3: 0x24A2, //PARENTHESIZED LATIN SMALL LETTER G - 0xA9D4: 0x24A3, //PARENTHESIZED LATIN SMALL LETTER H - 0xA9D5: 0x24A4, //PARENTHESIZED LATIN SMALL LETTER I - 0xA9D6: 0x24A5, //PARENTHESIZED LATIN SMALL LETTER J - 0xA9D7: 0x24A6, //PARENTHESIZED LATIN SMALL LETTER K - 0xA9D8: 0x24A7, //PARENTHESIZED LATIN SMALL LETTER L - 0xA9D9: 0x24A8, //PARENTHESIZED LATIN SMALL LETTER M - 0xA9DA: 0x24A9, //PARENTHESIZED LATIN SMALL LETTER N - 0xA9DB: 0x24AA, //PARENTHESIZED LATIN SMALL LETTER O - 0xA9DC: 0x24AB, //PARENTHESIZED LATIN SMALL LETTER P - 0xA9DD: 0x24AC, //PARENTHESIZED LATIN SMALL LETTER Q - 0xA9DE: 0x24AD, //PARENTHESIZED LATIN SMALL LETTER R - 0xA9DF: 0x24AE, //PARENTHESIZED LATIN SMALL LETTER S - 0xA9E0: 0x24AF, //PARENTHESIZED LATIN SMALL LETTER T - 0xA9E1: 0x24B0, //PARENTHESIZED LATIN SMALL LETTER U - 0xA9E2: 0x24B1, //PARENTHESIZED LATIN SMALL LETTER V - 0xA9E3: 0x24B2, //PARENTHESIZED LATIN SMALL LETTER W - 0xA9E4: 0x24B3, //PARENTHESIZED LATIN SMALL LETTER X - 0xA9E5: 0x24B4, //PARENTHESIZED LATIN SMALL LETTER Y - 0xA9E6: 0x24B5, //PARENTHESIZED LATIN SMALL LETTER Z - 0xA9E7: 0x2474, //PARENTHESIZED DIGIT ONE - 0xA9E8: 0x2475, //PARENTHESIZED DIGIT TWO - 0xA9E9: 0x2476, //PARENTHESIZED DIGIT THREE - 0xA9EA: 0x2477, //PARENTHESIZED DIGIT FOUR - 0xA9EB: 0x2478, //PARENTHESIZED DIGIT FIVE - 0xA9EC: 0x2479, //PARENTHESIZED DIGIT SIX - 0xA9ED: 0x247A, //PARENTHESIZED DIGIT SEVEN - 0xA9EE: 0x247B, //PARENTHESIZED DIGIT EIGHT - 0xA9EF: 0x247C, //PARENTHESIZED DIGIT NINE - 0xA9F0: 0x247D, //PARENTHESIZED NUMBER TEN - 0xA9F1: 0x247E, //PARENTHESIZED NUMBER ELEVEN - 0xA9F2: 0x247F, //PARENTHESIZED NUMBER TWELVE - 0xA9F3: 0x2480, //PARENTHESIZED NUMBER THIRTEEN - 0xA9F4: 0x2481, //PARENTHESIZED NUMBER FOURTEEN - 0xA9F5: 0x2482, //PARENTHESIZED NUMBER FIFTEEN - 0xA9F6: 0x00B9, //SUPERSCRIPT ONE - 0xA9F7: 0x00B2, //SUPERSCRIPT TWO - 0xA9F8: 0x00B3, //SUPERSCRIPT THREE - 0xA9F9: 0x2074, //SUPERSCRIPT FOUR - 0xA9FA: 0x207F, //SUPERSCRIPT LATIN SMALL LETTER N - 0xA9FB: 0x2081, //SUBSCRIPT ONE - 0xA9FC: 0x2082, //SUBSCRIPT TWO - 0xA9FD: 0x2083, //SUBSCRIPT THREE - 0xA9FE: 0x2084, //SUBSCRIPT FOUR - 0xAA41: 0xCC25, //HANGUL SYLLABLE SSANGCIEUC I THIEUTH - 0xAA42: 0xCC26, //HANGUL SYLLABLE SSANGCIEUC I PHIEUPH - 0xAA43: 0xCC2A, //HANGUL SYLLABLE CHIEUCH A SSANGKIYEOK - 0xAA44: 0xCC2B, //HANGUL SYLLABLE CHIEUCH A KIYEOKSIOS - 0xAA45: 0xCC2D, //HANGUL SYLLABLE CHIEUCH A NIEUNCIEUC - 0xAA46: 0xCC2F, //HANGUL SYLLABLE CHIEUCH A TIKEUT - 0xAA47: 0xCC31, //HANGUL SYLLABLE CHIEUCH A RIEULKIYEOK - 0xAA48: 0xCC32, //HANGUL SYLLABLE CHIEUCH A RIEULMIEUM - 0xAA49: 0xCC33, //HANGUL SYLLABLE CHIEUCH A RIEULPIEUP - 0xAA4A: 0xCC34, //HANGUL SYLLABLE CHIEUCH A RIEULSIOS - 0xAA4B: 0xCC35, //HANGUL SYLLABLE CHIEUCH A RIEULTHIEUTH - 0xAA4C: 0xCC36, //HANGUL SYLLABLE CHIEUCH A RIEULPHIEUPH - 0xAA4D: 0xCC37, //HANGUL SYLLABLE CHIEUCH A RIEULHIEUH - 0xAA4E: 0xCC3A, //HANGUL SYLLABLE CHIEUCH A PIEUPSIOS - 0xAA4F: 0xCC3F, //HANGUL SYLLABLE CHIEUCH A CHIEUCH - 0xAA50: 0xCC40, //HANGUL SYLLABLE CHIEUCH A KHIEUKH - 0xAA51: 0xCC41, //HANGUL SYLLABLE CHIEUCH A THIEUTH - 0xAA52: 0xCC42, //HANGUL SYLLABLE CHIEUCH A PHIEUPH - 0xAA53: 0xCC43, //HANGUL SYLLABLE CHIEUCH A HIEUH - 0xAA54: 0xCC46, //HANGUL SYLLABLE CHIEUCH AE SSANGKIYEOK - 0xAA55: 0xCC47, //HANGUL SYLLABLE CHIEUCH AE KIYEOKSIOS - 0xAA56: 0xCC49, //HANGUL SYLLABLE CHIEUCH AE NIEUNCIEUC - 0xAA57: 0xCC4A, //HANGUL SYLLABLE CHIEUCH AE NIEUNHIEUH - 0xAA58: 0xCC4B, //HANGUL SYLLABLE CHIEUCH AE TIKEUT - 0xAA59: 0xCC4D, //HANGUL SYLLABLE CHIEUCH AE RIEULKIYEOK - 0xAA5A: 0xCC4E, //HANGUL SYLLABLE CHIEUCH AE RIEULMIEUM - 0xAA61: 0xCC4F, //HANGUL SYLLABLE CHIEUCH AE RIEULPIEUP - 0xAA62: 0xCC50, //HANGUL SYLLABLE CHIEUCH AE RIEULSIOS - 0xAA63: 0xCC51, //HANGUL SYLLABLE CHIEUCH AE RIEULTHIEUTH - 0xAA64: 0xCC52, //HANGUL SYLLABLE CHIEUCH AE RIEULPHIEUPH - 0xAA65: 0xCC53, //HANGUL SYLLABLE CHIEUCH AE RIEULHIEUH - 0xAA66: 0xCC56, //HANGUL SYLLABLE CHIEUCH AE PIEUPSIOS - 0xAA67: 0xCC5A, //HANGUL SYLLABLE CHIEUCH AE CIEUC - 0xAA68: 0xCC5B, //HANGUL SYLLABLE CHIEUCH AE CHIEUCH - 0xAA69: 0xCC5C, //HANGUL SYLLABLE CHIEUCH AE KHIEUKH - 0xAA6A: 0xCC5D, //HANGUL SYLLABLE CHIEUCH AE THIEUTH - 0xAA6B: 0xCC5E, //HANGUL SYLLABLE CHIEUCH AE PHIEUPH - 0xAA6C: 0xCC5F, //HANGUL SYLLABLE CHIEUCH AE HIEUH - 0xAA6D: 0xCC61, //HANGUL SYLLABLE CHIEUCH YA KIYEOK - 0xAA6E: 0xCC62, //HANGUL SYLLABLE CHIEUCH YA SSANGKIYEOK - 0xAA6F: 0xCC63, //HANGUL SYLLABLE CHIEUCH YA KIYEOKSIOS - 0xAA70: 0xCC65, //HANGUL SYLLABLE CHIEUCH YA NIEUNCIEUC - 0xAA71: 0xCC67, //HANGUL SYLLABLE CHIEUCH YA TIKEUT - 0xAA72: 0xCC69, //HANGUL SYLLABLE CHIEUCH YA RIEULKIYEOK - 0xAA73: 0xCC6A, //HANGUL SYLLABLE CHIEUCH YA RIEULMIEUM - 0xAA74: 0xCC6B, //HANGUL SYLLABLE CHIEUCH YA RIEULPIEUP - 0xAA75: 0xCC6C, //HANGUL SYLLABLE CHIEUCH YA RIEULSIOS - 0xAA76: 0xCC6D, //HANGUL SYLLABLE CHIEUCH YA RIEULTHIEUTH - 0xAA77: 0xCC6E, //HANGUL SYLLABLE CHIEUCH YA RIEULPHIEUPH - 0xAA78: 0xCC6F, //HANGUL SYLLABLE CHIEUCH YA RIEULHIEUH - 0xAA79: 0xCC71, //HANGUL SYLLABLE CHIEUCH YA PIEUP - 0xAA7A: 0xCC72, //HANGUL SYLLABLE CHIEUCH YA PIEUPSIOS - 0xAA81: 0xCC73, //HANGUL SYLLABLE CHIEUCH YA SIOS - 0xAA82: 0xCC74, //HANGUL SYLLABLE CHIEUCH YA SSANGSIOS - 0xAA83: 0xCC76, //HANGUL SYLLABLE CHIEUCH YA CIEUC - 0xAA84: 0xCC77, //HANGUL SYLLABLE CHIEUCH YA CHIEUCH - 0xAA85: 0xCC78, //HANGUL SYLLABLE CHIEUCH YA KHIEUKH - 0xAA86: 0xCC79, //HANGUL SYLLABLE CHIEUCH YA THIEUTH - 0xAA87: 0xCC7A, //HANGUL SYLLABLE CHIEUCH YA PHIEUPH - 0xAA88: 0xCC7B, //HANGUL SYLLABLE CHIEUCH YA HIEUH - 0xAA89: 0xCC7C, //HANGUL SYLLABLE CHIEUCH YAE - 0xAA8A: 0xCC7D, //HANGUL SYLLABLE CHIEUCH YAE KIYEOK - 0xAA8B: 0xCC7E, //HANGUL SYLLABLE CHIEUCH YAE SSANGKIYEOK - 0xAA8C: 0xCC7F, //HANGUL SYLLABLE CHIEUCH YAE KIYEOKSIOS - 0xAA8D: 0xCC80, //HANGUL SYLLABLE CHIEUCH YAE NIEUN - 0xAA8E: 0xCC81, //HANGUL SYLLABLE CHIEUCH YAE NIEUNCIEUC - 0xAA8F: 0xCC82, //HANGUL SYLLABLE CHIEUCH YAE NIEUNHIEUH - 0xAA90: 0xCC83, //HANGUL SYLLABLE CHIEUCH YAE TIKEUT - 0xAA91: 0xCC84, //HANGUL SYLLABLE CHIEUCH YAE RIEUL - 0xAA92: 0xCC85, //HANGUL SYLLABLE CHIEUCH YAE RIEULKIYEOK - 0xAA93: 0xCC86, //HANGUL SYLLABLE CHIEUCH YAE RIEULMIEUM - 0xAA94: 0xCC87, //HANGUL SYLLABLE CHIEUCH YAE RIEULPIEUP - 0xAA95: 0xCC88, //HANGUL SYLLABLE CHIEUCH YAE RIEULSIOS - 0xAA96: 0xCC89, //HANGUL SYLLABLE CHIEUCH YAE RIEULTHIEUTH - 0xAA97: 0xCC8A, //HANGUL SYLLABLE CHIEUCH YAE RIEULPHIEUPH - 0xAA98: 0xCC8B, //HANGUL SYLLABLE CHIEUCH YAE RIEULHIEUH - 0xAA99: 0xCC8C, //HANGUL SYLLABLE CHIEUCH YAE MIEUM - 0xAA9A: 0xCC8D, //HANGUL SYLLABLE CHIEUCH YAE PIEUP - 0xAA9B: 0xCC8E, //HANGUL SYLLABLE CHIEUCH YAE PIEUPSIOS - 0xAA9C: 0xCC8F, //HANGUL SYLLABLE CHIEUCH YAE SIOS - 0xAA9D: 0xCC90, //HANGUL SYLLABLE CHIEUCH YAE SSANGSIOS - 0xAA9E: 0xCC91, //HANGUL SYLLABLE CHIEUCH YAE IEUNG - 0xAA9F: 0xCC92, //HANGUL SYLLABLE CHIEUCH YAE CIEUC - 0xAAA0: 0xCC93, //HANGUL SYLLABLE CHIEUCH YAE CHIEUCH - 0xAAA1: 0x3041, //HIRAGANA LETTER SMALL A - 0xAAA2: 0x3042, //HIRAGANA LETTER A - 0xAAA3: 0x3043, //HIRAGANA LETTER SMALL I - 0xAAA4: 0x3044, //HIRAGANA LETTER I - 0xAAA5: 0x3045, //HIRAGANA LETTER SMALL U - 0xAAA6: 0x3046, //HIRAGANA LETTER U - 0xAAA7: 0x3047, //HIRAGANA LETTER SMALL E - 0xAAA8: 0x3048, //HIRAGANA LETTER E - 0xAAA9: 0x3049, //HIRAGANA LETTER SMALL O - 0xAAAA: 0x304A, //HIRAGANA LETTER O - 0xAAAB: 0x304B, //HIRAGANA LETTER KA - 0xAAAC: 0x304C, //HIRAGANA LETTER GA - 0xAAAD: 0x304D, //HIRAGANA LETTER KI - 0xAAAE: 0x304E, //HIRAGANA LETTER GI - 0xAAAF: 0x304F, //HIRAGANA LETTER KU - 0xAAB0: 0x3050, //HIRAGANA LETTER GU - 0xAAB1: 0x3051, //HIRAGANA LETTER KE - 0xAAB2: 0x3052, //HIRAGANA LETTER GE - 0xAAB3: 0x3053, //HIRAGANA LETTER KO - 0xAAB4: 0x3054, //HIRAGANA LETTER GO - 0xAAB5: 0x3055, //HIRAGANA LETTER SA - 0xAAB6: 0x3056, //HIRAGANA LETTER ZA - 0xAAB7: 0x3057, //HIRAGANA LETTER SI - 0xAAB8: 0x3058, //HIRAGANA LETTER ZI - 0xAAB9: 0x3059, //HIRAGANA LETTER SU - 0xAABA: 0x305A, //HIRAGANA LETTER ZU - 0xAABB: 0x305B, //HIRAGANA LETTER SE - 0xAABC: 0x305C, //HIRAGANA LETTER ZE - 0xAABD: 0x305D, //HIRAGANA LETTER SO - 0xAABE: 0x305E, //HIRAGANA LETTER ZO - 0xAABF: 0x305F, //HIRAGANA LETTER TA - 0xAAC0: 0x3060, //HIRAGANA LETTER DA - 0xAAC1: 0x3061, //HIRAGANA LETTER TI - 0xAAC2: 0x3062, //HIRAGANA LETTER DI - 0xAAC3: 0x3063, //HIRAGANA LETTER SMALL TU - 0xAAC4: 0x3064, //HIRAGANA LETTER TU - 0xAAC5: 0x3065, //HIRAGANA LETTER DU - 0xAAC6: 0x3066, //HIRAGANA LETTER TE - 0xAAC7: 0x3067, //HIRAGANA LETTER DE - 0xAAC8: 0x3068, //HIRAGANA LETTER TO - 0xAAC9: 0x3069, //HIRAGANA LETTER DO - 0xAACA: 0x306A, //HIRAGANA LETTER NA - 0xAACB: 0x306B, //HIRAGANA LETTER NI - 0xAACC: 0x306C, //HIRAGANA LETTER NU - 0xAACD: 0x306D, //HIRAGANA LETTER NE - 0xAACE: 0x306E, //HIRAGANA LETTER NO - 0xAACF: 0x306F, //HIRAGANA LETTER HA - 0xAAD0: 0x3070, //HIRAGANA LETTER BA - 0xAAD1: 0x3071, //HIRAGANA LETTER PA - 0xAAD2: 0x3072, //HIRAGANA LETTER HI - 0xAAD3: 0x3073, //HIRAGANA LETTER BI - 0xAAD4: 0x3074, //HIRAGANA LETTER PI - 0xAAD5: 0x3075, //HIRAGANA LETTER HU - 0xAAD6: 0x3076, //HIRAGANA LETTER BU - 0xAAD7: 0x3077, //HIRAGANA LETTER PU - 0xAAD8: 0x3078, //HIRAGANA LETTER HE - 0xAAD9: 0x3079, //HIRAGANA LETTER BE - 0xAADA: 0x307A, //HIRAGANA LETTER PE - 0xAADB: 0x307B, //HIRAGANA LETTER HO - 0xAADC: 0x307C, //HIRAGANA LETTER BO - 0xAADD: 0x307D, //HIRAGANA LETTER PO - 0xAADE: 0x307E, //HIRAGANA LETTER MA - 0xAADF: 0x307F, //HIRAGANA LETTER MI - 0xAAE0: 0x3080, //HIRAGANA LETTER MU - 0xAAE1: 0x3081, //HIRAGANA LETTER ME - 0xAAE2: 0x3082, //HIRAGANA LETTER MO - 0xAAE3: 0x3083, //HIRAGANA LETTER SMALL YA - 0xAAE4: 0x3084, //HIRAGANA LETTER YA - 0xAAE5: 0x3085, //HIRAGANA LETTER SMALL YU - 0xAAE6: 0x3086, //HIRAGANA LETTER YU - 0xAAE7: 0x3087, //HIRAGANA LETTER SMALL YO - 0xAAE8: 0x3088, //HIRAGANA LETTER YO - 0xAAE9: 0x3089, //HIRAGANA LETTER RA - 0xAAEA: 0x308A, //HIRAGANA LETTER RI - 0xAAEB: 0x308B, //HIRAGANA LETTER RU - 0xAAEC: 0x308C, //HIRAGANA LETTER RE - 0xAAED: 0x308D, //HIRAGANA LETTER RO - 0xAAEE: 0x308E, //HIRAGANA LETTER SMALL WA - 0xAAEF: 0x308F, //HIRAGANA LETTER WA - 0xAAF0: 0x3090, //HIRAGANA LETTER WI - 0xAAF1: 0x3091, //HIRAGANA LETTER WE - 0xAAF2: 0x3092, //HIRAGANA LETTER WO - 0xAAF3: 0x3093, //HIRAGANA LETTER N - 0xAB41: 0xCC94, //HANGUL SYLLABLE CHIEUCH YAE KHIEUKH - 0xAB42: 0xCC95, //HANGUL SYLLABLE CHIEUCH YAE THIEUTH - 0xAB43: 0xCC96, //HANGUL SYLLABLE CHIEUCH YAE PHIEUPH - 0xAB44: 0xCC97, //HANGUL SYLLABLE CHIEUCH YAE HIEUH - 0xAB45: 0xCC9A, //HANGUL SYLLABLE CHIEUCH EO SSANGKIYEOK - 0xAB46: 0xCC9B, //HANGUL SYLLABLE CHIEUCH EO KIYEOKSIOS - 0xAB47: 0xCC9D, //HANGUL SYLLABLE CHIEUCH EO NIEUNCIEUC - 0xAB48: 0xCC9E, //HANGUL SYLLABLE CHIEUCH EO NIEUNHIEUH - 0xAB49: 0xCC9F, //HANGUL SYLLABLE CHIEUCH EO TIKEUT - 0xAB4A: 0xCCA1, //HANGUL SYLLABLE CHIEUCH EO RIEULKIYEOK - 0xAB4B: 0xCCA2, //HANGUL SYLLABLE CHIEUCH EO RIEULMIEUM - 0xAB4C: 0xCCA3, //HANGUL SYLLABLE CHIEUCH EO RIEULPIEUP - 0xAB4D: 0xCCA4, //HANGUL SYLLABLE CHIEUCH EO RIEULSIOS - 0xAB4E: 0xCCA5, //HANGUL SYLLABLE CHIEUCH EO RIEULTHIEUTH - 0xAB4F: 0xCCA6, //HANGUL SYLLABLE CHIEUCH EO RIEULPHIEUPH - 0xAB50: 0xCCA7, //HANGUL SYLLABLE CHIEUCH EO RIEULHIEUH - 0xAB51: 0xCCAA, //HANGUL SYLLABLE CHIEUCH EO PIEUPSIOS - 0xAB52: 0xCCAE, //HANGUL SYLLABLE CHIEUCH EO CIEUC - 0xAB53: 0xCCAF, //HANGUL SYLLABLE CHIEUCH EO CHIEUCH - 0xAB54: 0xCCB0, //HANGUL SYLLABLE CHIEUCH EO KHIEUKH - 0xAB55: 0xCCB1, //HANGUL SYLLABLE CHIEUCH EO THIEUTH - 0xAB56: 0xCCB2, //HANGUL SYLLABLE CHIEUCH EO PHIEUPH - 0xAB57: 0xCCB3, //HANGUL SYLLABLE CHIEUCH EO HIEUH - 0xAB58: 0xCCB6, //HANGUL SYLLABLE CHIEUCH E SSANGKIYEOK - 0xAB59: 0xCCB7, //HANGUL SYLLABLE CHIEUCH E KIYEOKSIOS - 0xAB5A: 0xCCB9, //HANGUL SYLLABLE CHIEUCH E NIEUNCIEUC - 0xAB61: 0xCCBA, //HANGUL SYLLABLE CHIEUCH E NIEUNHIEUH - 0xAB62: 0xCCBB, //HANGUL SYLLABLE CHIEUCH E TIKEUT - 0xAB63: 0xCCBD, //HANGUL SYLLABLE CHIEUCH E RIEULKIYEOK - 0xAB64: 0xCCBE, //HANGUL SYLLABLE CHIEUCH E RIEULMIEUM - 0xAB65: 0xCCBF, //HANGUL SYLLABLE CHIEUCH E RIEULPIEUP - 0xAB66: 0xCCC0, //HANGUL SYLLABLE CHIEUCH E RIEULSIOS - 0xAB67: 0xCCC1, //HANGUL SYLLABLE CHIEUCH E RIEULTHIEUTH - 0xAB68: 0xCCC2, //HANGUL SYLLABLE CHIEUCH E RIEULPHIEUPH - 0xAB69: 0xCCC3, //HANGUL SYLLABLE CHIEUCH E RIEULHIEUH - 0xAB6A: 0xCCC6, //HANGUL SYLLABLE CHIEUCH E PIEUPSIOS - 0xAB6B: 0xCCC8, //HANGUL SYLLABLE CHIEUCH E SSANGSIOS - 0xAB6C: 0xCCCA, //HANGUL SYLLABLE CHIEUCH E CIEUC - 0xAB6D: 0xCCCB, //HANGUL SYLLABLE CHIEUCH E CHIEUCH - 0xAB6E: 0xCCCC, //HANGUL SYLLABLE CHIEUCH E KHIEUKH - 0xAB6F: 0xCCCD, //HANGUL SYLLABLE CHIEUCH E THIEUTH - 0xAB70: 0xCCCE, //HANGUL SYLLABLE CHIEUCH E PHIEUPH - 0xAB71: 0xCCCF, //HANGUL SYLLABLE CHIEUCH E HIEUH - 0xAB72: 0xCCD1, //HANGUL SYLLABLE CHIEUCH YEO KIYEOK - 0xAB73: 0xCCD2, //HANGUL SYLLABLE CHIEUCH YEO SSANGKIYEOK - 0xAB74: 0xCCD3, //HANGUL SYLLABLE CHIEUCH YEO KIYEOKSIOS - 0xAB75: 0xCCD5, //HANGUL SYLLABLE CHIEUCH YEO NIEUNCIEUC - 0xAB76: 0xCCD6, //HANGUL SYLLABLE CHIEUCH YEO NIEUNHIEUH - 0xAB77: 0xCCD7, //HANGUL SYLLABLE CHIEUCH YEO TIKEUT - 0xAB78: 0xCCD8, //HANGUL SYLLABLE CHIEUCH YEO RIEUL - 0xAB79: 0xCCD9, //HANGUL SYLLABLE CHIEUCH YEO RIEULKIYEOK - 0xAB7A: 0xCCDA, //HANGUL SYLLABLE CHIEUCH YEO RIEULMIEUM - 0xAB81: 0xCCDB, //HANGUL SYLLABLE CHIEUCH YEO RIEULPIEUP - 0xAB82: 0xCCDC, //HANGUL SYLLABLE CHIEUCH YEO RIEULSIOS - 0xAB83: 0xCCDD, //HANGUL SYLLABLE CHIEUCH YEO RIEULTHIEUTH - 0xAB84: 0xCCDE, //HANGUL SYLLABLE CHIEUCH YEO RIEULPHIEUPH - 0xAB85: 0xCCDF, //HANGUL SYLLABLE CHIEUCH YEO RIEULHIEUH - 0xAB86: 0xCCE0, //HANGUL SYLLABLE CHIEUCH YEO MIEUM - 0xAB87: 0xCCE1, //HANGUL SYLLABLE CHIEUCH YEO PIEUP - 0xAB88: 0xCCE2, //HANGUL SYLLABLE CHIEUCH YEO PIEUPSIOS - 0xAB89: 0xCCE3, //HANGUL SYLLABLE CHIEUCH YEO SIOS - 0xAB8A: 0xCCE5, //HANGUL SYLLABLE CHIEUCH YEO IEUNG - 0xAB8B: 0xCCE6, //HANGUL SYLLABLE CHIEUCH YEO CIEUC - 0xAB8C: 0xCCE7, //HANGUL SYLLABLE CHIEUCH YEO CHIEUCH - 0xAB8D: 0xCCE8, //HANGUL SYLLABLE CHIEUCH YEO KHIEUKH - 0xAB8E: 0xCCE9, //HANGUL SYLLABLE CHIEUCH YEO THIEUTH - 0xAB8F: 0xCCEA, //HANGUL SYLLABLE CHIEUCH YEO PHIEUPH - 0xAB90: 0xCCEB, //HANGUL SYLLABLE CHIEUCH YEO HIEUH - 0xAB91: 0xCCED, //HANGUL SYLLABLE CHIEUCH YE KIYEOK - 0xAB92: 0xCCEE, //HANGUL SYLLABLE CHIEUCH YE SSANGKIYEOK - 0xAB93: 0xCCEF, //HANGUL SYLLABLE CHIEUCH YE KIYEOKSIOS - 0xAB94: 0xCCF1, //HANGUL SYLLABLE CHIEUCH YE NIEUNCIEUC - 0xAB95: 0xCCF2, //HANGUL SYLLABLE CHIEUCH YE NIEUNHIEUH - 0xAB96: 0xCCF3, //HANGUL SYLLABLE CHIEUCH YE TIKEUT - 0xAB97: 0xCCF4, //HANGUL SYLLABLE CHIEUCH YE RIEUL - 0xAB98: 0xCCF5, //HANGUL SYLLABLE CHIEUCH YE RIEULKIYEOK - 0xAB99: 0xCCF6, //HANGUL SYLLABLE CHIEUCH YE RIEULMIEUM - 0xAB9A: 0xCCF7, //HANGUL SYLLABLE CHIEUCH YE RIEULPIEUP - 0xAB9B: 0xCCF8, //HANGUL SYLLABLE CHIEUCH YE RIEULSIOS - 0xAB9C: 0xCCF9, //HANGUL SYLLABLE CHIEUCH YE RIEULTHIEUTH - 0xAB9D: 0xCCFA, //HANGUL SYLLABLE CHIEUCH YE RIEULPHIEUPH - 0xAB9E: 0xCCFB, //HANGUL SYLLABLE CHIEUCH YE RIEULHIEUH - 0xAB9F: 0xCCFC, //HANGUL SYLLABLE CHIEUCH YE MIEUM - 0xABA0: 0xCCFD, //HANGUL SYLLABLE CHIEUCH YE PIEUP - 0xABA1: 0x30A1, //KATAKANA LETTER SMALL A - 0xABA2: 0x30A2, //KATAKANA LETTER A - 0xABA3: 0x30A3, //KATAKANA LETTER SMALL I - 0xABA4: 0x30A4, //KATAKANA LETTER I - 0xABA5: 0x30A5, //KATAKANA LETTER SMALL U - 0xABA6: 0x30A6, //KATAKANA LETTER U - 0xABA7: 0x30A7, //KATAKANA LETTER SMALL E - 0xABA8: 0x30A8, //KATAKANA LETTER E - 0xABA9: 0x30A9, //KATAKANA LETTER SMALL O - 0xABAA: 0x30AA, //KATAKANA LETTER O - 0xABAB: 0x30AB, //KATAKANA LETTER KA - 0xABAC: 0x30AC, //KATAKANA LETTER GA - 0xABAD: 0x30AD, //KATAKANA LETTER KI - 0xABAE: 0x30AE, //KATAKANA LETTER GI - 0xABAF: 0x30AF, //KATAKANA LETTER KU - 0xABB0: 0x30B0, //KATAKANA LETTER GU - 0xABB1: 0x30B1, //KATAKANA LETTER KE - 0xABB2: 0x30B2, //KATAKANA LETTER GE - 0xABB3: 0x30B3, //KATAKANA LETTER KO - 0xABB4: 0x30B4, //KATAKANA LETTER GO - 0xABB5: 0x30B5, //KATAKANA LETTER SA - 0xABB6: 0x30B6, //KATAKANA LETTER ZA - 0xABB7: 0x30B7, //KATAKANA LETTER SI - 0xABB8: 0x30B8, //KATAKANA LETTER ZI - 0xABB9: 0x30B9, //KATAKANA LETTER SU - 0xABBA: 0x30BA, //KATAKANA LETTER ZU - 0xABBB: 0x30BB, //KATAKANA LETTER SE - 0xABBC: 0x30BC, //KATAKANA LETTER ZE - 0xABBD: 0x30BD, //KATAKANA LETTER SO - 0xABBE: 0x30BE, //KATAKANA LETTER ZO - 0xABBF: 0x30BF, //KATAKANA LETTER TA - 0xABC0: 0x30C0, //KATAKANA LETTER DA - 0xABC1: 0x30C1, //KATAKANA LETTER TI - 0xABC2: 0x30C2, //KATAKANA LETTER DI - 0xABC3: 0x30C3, //KATAKANA LETTER SMALL TU - 0xABC4: 0x30C4, //KATAKANA LETTER TU - 0xABC5: 0x30C5, //KATAKANA LETTER DU - 0xABC6: 0x30C6, //KATAKANA LETTER TE - 0xABC7: 0x30C7, //KATAKANA LETTER DE - 0xABC8: 0x30C8, //KATAKANA LETTER TO - 0xABC9: 0x30C9, //KATAKANA LETTER DO - 0xABCA: 0x30CA, //KATAKANA LETTER NA - 0xABCB: 0x30CB, //KATAKANA LETTER NI - 0xABCC: 0x30CC, //KATAKANA LETTER NU - 0xABCD: 0x30CD, //KATAKANA LETTER NE - 0xABCE: 0x30CE, //KATAKANA LETTER NO - 0xABCF: 0x30CF, //KATAKANA LETTER HA - 0xABD0: 0x30D0, //KATAKANA LETTER BA - 0xABD1: 0x30D1, //KATAKANA LETTER PA - 0xABD2: 0x30D2, //KATAKANA LETTER HI - 0xABD3: 0x30D3, //KATAKANA LETTER BI - 0xABD4: 0x30D4, //KATAKANA LETTER PI - 0xABD5: 0x30D5, //KATAKANA LETTER HU - 0xABD6: 0x30D6, //KATAKANA LETTER BU - 0xABD7: 0x30D7, //KATAKANA LETTER PU - 0xABD8: 0x30D8, //KATAKANA LETTER HE - 0xABD9: 0x30D9, //KATAKANA LETTER BE - 0xABDA: 0x30DA, //KATAKANA LETTER PE - 0xABDB: 0x30DB, //KATAKANA LETTER HO - 0xABDC: 0x30DC, //KATAKANA LETTER BO - 0xABDD: 0x30DD, //KATAKANA LETTER PO - 0xABDE: 0x30DE, //KATAKANA LETTER MA - 0xABDF: 0x30DF, //KATAKANA LETTER MI - 0xABE0: 0x30E0, //KATAKANA LETTER MU - 0xABE1: 0x30E1, //KATAKANA LETTER ME - 0xABE2: 0x30E2, //KATAKANA LETTER MO - 0xABE3: 0x30E3, //KATAKANA LETTER SMALL YA - 0xABE4: 0x30E4, //KATAKANA LETTER YA - 0xABE5: 0x30E5, //KATAKANA LETTER SMALL YU - 0xABE6: 0x30E6, //KATAKANA LETTER YU - 0xABE7: 0x30E7, //KATAKANA LETTER SMALL YO - 0xABE8: 0x30E8, //KATAKANA LETTER YO - 0xABE9: 0x30E9, //KATAKANA LETTER RA - 0xABEA: 0x30EA, //KATAKANA LETTER RI - 0xABEB: 0x30EB, //KATAKANA LETTER RU - 0xABEC: 0x30EC, //KATAKANA LETTER RE - 0xABED: 0x30ED, //KATAKANA LETTER RO - 0xABEE: 0x30EE, //KATAKANA LETTER SMALL WA - 0xABEF: 0x30EF, //KATAKANA LETTER WA - 0xABF0: 0x30F0, //KATAKANA LETTER WI - 0xABF1: 0x30F1, //KATAKANA LETTER WE - 0xABF2: 0x30F2, //KATAKANA LETTER WO - 0xABF3: 0x30F3, //KATAKANA LETTER N - 0xABF4: 0x30F4, //KATAKANA LETTER VU - 0xABF5: 0x30F5, //KATAKANA LETTER SMALL KA - 0xABF6: 0x30F6, //KATAKANA LETTER SMALL KE - 0xAC41: 0xCCFE, //HANGUL SYLLABLE CHIEUCH YE PIEUPSIOS - 0xAC42: 0xCCFF, //HANGUL SYLLABLE CHIEUCH YE SIOS - 0xAC43: 0xCD00, //HANGUL SYLLABLE CHIEUCH YE SSANGSIOS - 0xAC44: 0xCD02, //HANGUL SYLLABLE CHIEUCH YE CIEUC - 0xAC45: 0xCD03, //HANGUL SYLLABLE CHIEUCH YE CHIEUCH - 0xAC46: 0xCD04, //HANGUL SYLLABLE CHIEUCH YE KHIEUKH - 0xAC47: 0xCD05, //HANGUL SYLLABLE CHIEUCH YE THIEUTH - 0xAC48: 0xCD06, //HANGUL SYLLABLE CHIEUCH YE PHIEUPH - 0xAC49: 0xCD07, //HANGUL SYLLABLE CHIEUCH YE HIEUH - 0xAC4A: 0xCD0A, //HANGUL SYLLABLE CHIEUCH O SSANGKIYEOK - 0xAC4B: 0xCD0B, //HANGUL SYLLABLE CHIEUCH O KIYEOKSIOS - 0xAC4C: 0xCD0D, //HANGUL SYLLABLE CHIEUCH O NIEUNCIEUC - 0xAC4D: 0xCD0E, //HANGUL SYLLABLE CHIEUCH O NIEUNHIEUH - 0xAC4E: 0xCD0F, //HANGUL SYLLABLE CHIEUCH O TIKEUT - 0xAC4F: 0xCD11, //HANGUL SYLLABLE CHIEUCH O RIEULKIYEOK - 0xAC50: 0xCD12, //HANGUL SYLLABLE CHIEUCH O RIEULMIEUM - 0xAC51: 0xCD13, //HANGUL SYLLABLE CHIEUCH O RIEULPIEUP - 0xAC52: 0xCD14, //HANGUL SYLLABLE CHIEUCH O RIEULSIOS - 0xAC53: 0xCD15, //HANGUL SYLLABLE CHIEUCH O RIEULTHIEUTH - 0xAC54: 0xCD16, //HANGUL SYLLABLE CHIEUCH O RIEULPHIEUPH - 0xAC55: 0xCD17, //HANGUL SYLLABLE CHIEUCH O RIEULHIEUH - 0xAC56: 0xCD1A, //HANGUL SYLLABLE CHIEUCH O PIEUPSIOS - 0xAC57: 0xCD1C, //HANGUL SYLLABLE CHIEUCH O SSANGSIOS - 0xAC58: 0xCD1E, //HANGUL SYLLABLE CHIEUCH O CIEUC - 0xAC59: 0xCD1F, //HANGUL SYLLABLE CHIEUCH O CHIEUCH - 0xAC5A: 0xCD20, //HANGUL SYLLABLE CHIEUCH O KHIEUKH - 0xAC61: 0xCD21, //HANGUL SYLLABLE CHIEUCH O THIEUTH - 0xAC62: 0xCD22, //HANGUL SYLLABLE CHIEUCH O PHIEUPH - 0xAC63: 0xCD23, //HANGUL SYLLABLE CHIEUCH O HIEUH - 0xAC64: 0xCD25, //HANGUL SYLLABLE CHIEUCH WA KIYEOK - 0xAC65: 0xCD26, //HANGUL SYLLABLE CHIEUCH WA SSANGKIYEOK - 0xAC66: 0xCD27, //HANGUL SYLLABLE CHIEUCH WA KIYEOKSIOS - 0xAC67: 0xCD29, //HANGUL SYLLABLE CHIEUCH WA NIEUNCIEUC - 0xAC68: 0xCD2A, //HANGUL SYLLABLE CHIEUCH WA NIEUNHIEUH - 0xAC69: 0xCD2B, //HANGUL SYLLABLE CHIEUCH WA TIKEUT - 0xAC6A: 0xCD2D, //HANGUL SYLLABLE CHIEUCH WA RIEULKIYEOK - 0xAC6B: 0xCD2E, //HANGUL SYLLABLE CHIEUCH WA RIEULMIEUM - 0xAC6C: 0xCD2F, //HANGUL SYLLABLE CHIEUCH WA RIEULPIEUP - 0xAC6D: 0xCD30, //HANGUL SYLLABLE CHIEUCH WA RIEULSIOS - 0xAC6E: 0xCD31, //HANGUL SYLLABLE CHIEUCH WA RIEULTHIEUTH - 0xAC6F: 0xCD32, //HANGUL SYLLABLE CHIEUCH WA RIEULPHIEUPH - 0xAC70: 0xCD33, //HANGUL SYLLABLE CHIEUCH WA RIEULHIEUH - 0xAC71: 0xCD34, //HANGUL SYLLABLE CHIEUCH WA MIEUM - 0xAC72: 0xCD35, //HANGUL SYLLABLE CHIEUCH WA PIEUP - 0xAC73: 0xCD36, //HANGUL SYLLABLE CHIEUCH WA PIEUPSIOS - 0xAC74: 0xCD37, //HANGUL SYLLABLE CHIEUCH WA SIOS - 0xAC75: 0xCD38, //HANGUL SYLLABLE CHIEUCH WA SSANGSIOS - 0xAC76: 0xCD3A, //HANGUL SYLLABLE CHIEUCH WA CIEUC - 0xAC77: 0xCD3B, //HANGUL SYLLABLE CHIEUCH WA CHIEUCH - 0xAC78: 0xCD3C, //HANGUL SYLLABLE CHIEUCH WA KHIEUKH - 0xAC79: 0xCD3D, //HANGUL SYLLABLE CHIEUCH WA THIEUTH - 0xAC7A: 0xCD3E, //HANGUL SYLLABLE CHIEUCH WA PHIEUPH - 0xAC81: 0xCD3F, //HANGUL SYLLABLE CHIEUCH WA HIEUH - 0xAC82: 0xCD40, //HANGUL SYLLABLE CHIEUCH WAE - 0xAC83: 0xCD41, //HANGUL SYLLABLE CHIEUCH WAE KIYEOK - 0xAC84: 0xCD42, //HANGUL SYLLABLE CHIEUCH WAE SSANGKIYEOK - 0xAC85: 0xCD43, //HANGUL SYLLABLE CHIEUCH WAE KIYEOKSIOS - 0xAC86: 0xCD44, //HANGUL SYLLABLE CHIEUCH WAE NIEUN - 0xAC87: 0xCD45, //HANGUL SYLLABLE CHIEUCH WAE NIEUNCIEUC - 0xAC88: 0xCD46, //HANGUL SYLLABLE CHIEUCH WAE NIEUNHIEUH - 0xAC89: 0xCD47, //HANGUL SYLLABLE CHIEUCH WAE TIKEUT - 0xAC8A: 0xCD48, //HANGUL SYLLABLE CHIEUCH WAE RIEUL - 0xAC8B: 0xCD49, //HANGUL SYLLABLE CHIEUCH WAE RIEULKIYEOK - 0xAC8C: 0xCD4A, //HANGUL SYLLABLE CHIEUCH WAE RIEULMIEUM - 0xAC8D: 0xCD4B, //HANGUL SYLLABLE CHIEUCH WAE RIEULPIEUP - 0xAC8E: 0xCD4C, //HANGUL SYLLABLE CHIEUCH WAE RIEULSIOS - 0xAC8F: 0xCD4D, //HANGUL SYLLABLE CHIEUCH WAE RIEULTHIEUTH - 0xAC90: 0xCD4E, //HANGUL SYLLABLE CHIEUCH WAE RIEULPHIEUPH - 0xAC91: 0xCD4F, //HANGUL SYLLABLE CHIEUCH WAE RIEULHIEUH - 0xAC92: 0xCD50, //HANGUL SYLLABLE CHIEUCH WAE MIEUM - 0xAC93: 0xCD51, //HANGUL SYLLABLE CHIEUCH WAE PIEUP - 0xAC94: 0xCD52, //HANGUL SYLLABLE CHIEUCH WAE PIEUPSIOS - 0xAC95: 0xCD53, //HANGUL SYLLABLE CHIEUCH WAE SIOS - 0xAC96: 0xCD54, //HANGUL SYLLABLE CHIEUCH WAE SSANGSIOS - 0xAC97: 0xCD55, //HANGUL SYLLABLE CHIEUCH WAE IEUNG - 0xAC98: 0xCD56, //HANGUL SYLLABLE CHIEUCH WAE CIEUC - 0xAC99: 0xCD57, //HANGUL SYLLABLE CHIEUCH WAE CHIEUCH - 0xAC9A: 0xCD58, //HANGUL SYLLABLE CHIEUCH WAE KHIEUKH - 0xAC9B: 0xCD59, //HANGUL SYLLABLE CHIEUCH WAE THIEUTH - 0xAC9C: 0xCD5A, //HANGUL SYLLABLE CHIEUCH WAE PHIEUPH - 0xAC9D: 0xCD5B, //HANGUL SYLLABLE CHIEUCH WAE HIEUH - 0xAC9E: 0xCD5D, //HANGUL SYLLABLE CHIEUCH OE KIYEOK - 0xAC9F: 0xCD5E, //HANGUL SYLLABLE CHIEUCH OE SSANGKIYEOK - 0xACA0: 0xCD5F, //HANGUL SYLLABLE CHIEUCH OE KIYEOKSIOS - 0xACA1: 0x0410, //CYRILLIC CAPITAL LETTER A - 0xACA2: 0x0411, //CYRILLIC CAPITAL LETTER BE - 0xACA3: 0x0412, //CYRILLIC CAPITAL LETTER VE - 0xACA4: 0x0413, //CYRILLIC CAPITAL LETTER GHE - 0xACA5: 0x0414, //CYRILLIC CAPITAL LETTER DE - 0xACA6: 0x0415, //CYRILLIC CAPITAL LETTER IE - 0xACA7: 0x0401, //CYRILLIC CAPITAL LETTER IO - 0xACA8: 0x0416, //CYRILLIC CAPITAL LETTER ZHE - 0xACA9: 0x0417, //CYRILLIC CAPITAL LETTER ZE - 0xACAA: 0x0418, //CYRILLIC CAPITAL LETTER I - 0xACAB: 0x0419, //CYRILLIC CAPITAL LETTER SHORT I - 0xACAC: 0x041A, //CYRILLIC CAPITAL LETTER KA - 0xACAD: 0x041B, //CYRILLIC CAPITAL LETTER EL - 0xACAE: 0x041C, //CYRILLIC CAPITAL LETTER EM - 0xACAF: 0x041D, //CYRILLIC CAPITAL LETTER EN - 0xACB0: 0x041E, //CYRILLIC CAPITAL LETTER O - 0xACB1: 0x041F, //CYRILLIC CAPITAL LETTER PE - 0xACB2: 0x0420, //CYRILLIC CAPITAL LETTER ER - 0xACB3: 0x0421, //CYRILLIC CAPITAL LETTER ES - 0xACB4: 0x0422, //CYRILLIC CAPITAL LETTER TE - 0xACB5: 0x0423, //CYRILLIC CAPITAL LETTER U - 0xACB6: 0x0424, //CYRILLIC CAPITAL LETTER EF - 0xACB7: 0x0425, //CYRILLIC CAPITAL LETTER HA - 0xACB8: 0x0426, //CYRILLIC CAPITAL LETTER TSE - 0xACB9: 0x0427, //CYRILLIC CAPITAL LETTER CHE - 0xACBA: 0x0428, //CYRILLIC CAPITAL LETTER SHA - 0xACBB: 0x0429, //CYRILLIC CAPITAL LETTER SHCHA - 0xACBC: 0x042A, //CYRILLIC CAPITAL LETTER HARD SIGN - 0xACBD: 0x042B, //CYRILLIC CAPITAL LETTER YERU - 0xACBE: 0x042C, //CYRILLIC CAPITAL LETTER SOFT SIGN - 0xACBF: 0x042D, //CYRILLIC CAPITAL LETTER E - 0xACC0: 0x042E, //CYRILLIC CAPITAL LETTER YU - 0xACC1: 0x042F, //CYRILLIC CAPITAL LETTER YA - 0xACD1: 0x0430, //CYRILLIC SMALL LETTER A - 0xACD2: 0x0431, //CYRILLIC SMALL LETTER BE - 0xACD3: 0x0432, //CYRILLIC SMALL LETTER VE - 0xACD4: 0x0433, //CYRILLIC SMALL LETTER GHE - 0xACD5: 0x0434, //CYRILLIC SMALL LETTER DE - 0xACD6: 0x0435, //CYRILLIC SMALL LETTER IE - 0xACD7: 0x0451, //CYRILLIC SMALL LETTER IO - 0xACD8: 0x0436, //CYRILLIC SMALL LETTER ZHE - 0xACD9: 0x0437, //CYRILLIC SMALL LETTER ZE - 0xACDA: 0x0438, //CYRILLIC SMALL LETTER I - 0xACDB: 0x0439, //CYRILLIC SMALL LETTER SHORT I - 0xACDC: 0x043A, //CYRILLIC SMALL LETTER KA - 0xACDD: 0x043B, //CYRILLIC SMALL LETTER EL - 0xACDE: 0x043C, //CYRILLIC SMALL LETTER EM - 0xACDF: 0x043D, //CYRILLIC SMALL LETTER EN - 0xACE0: 0x043E, //CYRILLIC SMALL LETTER O - 0xACE1: 0x043F, //CYRILLIC SMALL LETTER PE - 0xACE2: 0x0440, //CYRILLIC SMALL LETTER ER - 0xACE3: 0x0441, //CYRILLIC SMALL LETTER ES - 0xACE4: 0x0442, //CYRILLIC SMALL LETTER TE - 0xACE5: 0x0443, //CYRILLIC SMALL LETTER U - 0xACE6: 0x0444, //CYRILLIC SMALL LETTER EF - 0xACE7: 0x0445, //CYRILLIC SMALL LETTER HA - 0xACE8: 0x0446, //CYRILLIC SMALL LETTER TSE - 0xACE9: 0x0447, //CYRILLIC SMALL LETTER CHE - 0xACEA: 0x0448, //CYRILLIC SMALL LETTER SHA - 0xACEB: 0x0449, //CYRILLIC SMALL LETTER SHCHA - 0xACEC: 0x044A, //CYRILLIC SMALL LETTER HARD SIGN - 0xACED: 0x044B, //CYRILLIC SMALL LETTER YERU - 0xACEE: 0x044C, //CYRILLIC SMALL LETTER SOFT SIGN - 0xACEF: 0x044D, //CYRILLIC SMALL LETTER E - 0xACF0: 0x044E, //CYRILLIC SMALL LETTER YU - 0xACF1: 0x044F, //CYRILLIC SMALL LETTER YA - 0xAD41: 0xCD61, //HANGUL SYLLABLE CHIEUCH OE NIEUNCIEUC - 0xAD42: 0xCD62, //HANGUL SYLLABLE CHIEUCH OE NIEUNHIEUH - 0xAD43: 0xCD63, //HANGUL SYLLABLE CHIEUCH OE TIKEUT - 0xAD44: 0xCD65, //HANGUL SYLLABLE CHIEUCH OE RIEULKIYEOK - 0xAD45: 0xCD66, //HANGUL SYLLABLE CHIEUCH OE RIEULMIEUM - 0xAD46: 0xCD67, //HANGUL SYLLABLE CHIEUCH OE RIEULPIEUP - 0xAD47: 0xCD68, //HANGUL SYLLABLE CHIEUCH OE RIEULSIOS - 0xAD48: 0xCD69, //HANGUL SYLLABLE CHIEUCH OE RIEULTHIEUTH - 0xAD49: 0xCD6A, //HANGUL SYLLABLE CHIEUCH OE RIEULPHIEUPH - 0xAD4A: 0xCD6B, //HANGUL SYLLABLE CHIEUCH OE RIEULHIEUH - 0xAD4B: 0xCD6E, //HANGUL SYLLABLE CHIEUCH OE PIEUPSIOS - 0xAD4C: 0xCD70, //HANGUL SYLLABLE CHIEUCH OE SSANGSIOS - 0xAD4D: 0xCD72, //HANGUL SYLLABLE CHIEUCH OE CIEUC - 0xAD4E: 0xCD73, //HANGUL SYLLABLE CHIEUCH OE CHIEUCH - 0xAD4F: 0xCD74, //HANGUL SYLLABLE CHIEUCH OE KHIEUKH - 0xAD50: 0xCD75, //HANGUL SYLLABLE CHIEUCH OE THIEUTH - 0xAD51: 0xCD76, //HANGUL SYLLABLE CHIEUCH OE PHIEUPH - 0xAD52: 0xCD77, //HANGUL SYLLABLE CHIEUCH OE HIEUH - 0xAD53: 0xCD79, //HANGUL SYLLABLE CHIEUCH YO KIYEOK - 0xAD54: 0xCD7A, //HANGUL SYLLABLE CHIEUCH YO SSANGKIYEOK - 0xAD55: 0xCD7B, //HANGUL SYLLABLE CHIEUCH YO KIYEOKSIOS - 0xAD56: 0xCD7C, //HANGUL SYLLABLE CHIEUCH YO NIEUN - 0xAD57: 0xCD7D, //HANGUL SYLLABLE CHIEUCH YO NIEUNCIEUC - 0xAD58: 0xCD7E, //HANGUL SYLLABLE CHIEUCH YO NIEUNHIEUH - 0xAD59: 0xCD7F, //HANGUL SYLLABLE CHIEUCH YO TIKEUT - 0xAD5A: 0xCD80, //HANGUL SYLLABLE CHIEUCH YO RIEUL - 0xAD61: 0xCD81, //HANGUL SYLLABLE CHIEUCH YO RIEULKIYEOK - 0xAD62: 0xCD82, //HANGUL SYLLABLE CHIEUCH YO RIEULMIEUM - 0xAD63: 0xCD83, //HANGUL SYLLABLE CHIEUCH YO RIEULPIEUP - 0xAD64: 0xCD84, //HANGUL SYLLABLE CHIEUCH YO RIEULSIOS - 0xAD65: 0xCD85, //HANGUL SYLLABLE CHIEUCH YO RIEULTHIEUTH - 0xAD66: 0xCD86, //HANGUL SYLLABLE CHIEUCH YO RIEULPHIEUPH - 0xAD67: 0xCD87, //HANGUL SYLLABLE CHIEUCH YO RIEULHIEUH - 0xAD68: 0xCD89, //HANGUL SYLLABLE CHIEUCH YO PIEUP - 0xAD69: 0xCD8A, //HANGUL SYLLABLE CHIEUCH YO PIEUPSIOS - 0xAD6A: 0xCD8B, //HANGUL SYLLABLE CHIEUCH YO SIOS - 0xAD6B: 0xCD8C, //HANGUL SYLLABLE CHIEUCH YO SSANGSIOS - 0xAD6C: 0xCD8D, //HANGUL SYLLABLE CHIEUCH YO IEUNG - 0xAD6D: 0xCD8E, //HANGUL SYLLABLE CHIEUCH YO CIEUC - 0xAD6E: 0xCD8F, //HANGUL SYLLABLE CHIEUCH YO CHIEUCH - 0xAD6F: 0xCD90, //HANGUL SYLLABLE CHIEUCH YO KHIEUKH - 0xAD70: 0xCD91, //HANGUL SYLLABLE CHIEUCH YO THIEUTH - 0xAD71: 0xCD92, //HANGUL SYLLABLE CHIEUCH YO PHIEUPH - 0xAD72: 0xCD93, //HANGUL SYLLABLE CHIEUCH YO HIEUH - 0xAD73: 0xCD96, //HANGUL SYLLABLE CHIEUCH U SSANGKIYEOK - 0xAD74: 0xCD97, //HANGUL SYLLABLE CHIEUCH U KIYEOKSIOS - 0xAD75: 0xCD99, //HANGUL SYLLABLE CHIEUCH U NIEUNCIEUC - 0xAD76: 0xCD9A, //HANGUL SYLLABLE CHIEUCH U NIEUNHIEUH - 0xAD77: 0xCD9B, //HANGUL SYLLABLE CHIEUCH U TIKEUT - 0xAD78: 0xCD9D, //HANGUL SYLLABLE CHIEUCH U RIEULKIYEOK - 0xAD79: 0xCD9E, //HANGUL SYLLABLE CHIEUCH U RIEULMIEUM - 0xAD7A: 0xCD9F, //HANGUL SYLLABLE CHIEUCH U RIEULPIEUP - 0xAD81: 0xCDA0, //HANGUL SYLLABLE CHIEUCH U RIEULSIOS - 0xAD82: 0xCDA1, //HANGUL SYLLABLE CHIEUCH U RIEULTHIEUTH - 0xAD83: 0xCDA2, //HANGUL SYLLABLE CHIEUCH U RIEULPHIEUPH - 0xAD84: 0xCDA3, //HANGUL SYLLABLE CHIEUCH U RIEULHIEUH - 0xAD85: 0xCDA6, //HANGUL SYLLABLE CHIEUCH U PIEUPSIOS - 0xAD86: 0xCDA8, //HANGUL SYLLABLE CHIEUCH U SSANGSIOS - 0xAD87: 0xCDAA, //HANGUL SYLLABLE CHIEUCH U CIEUC - 0xAD88: 0xCDAB, //HANGUL SYLLABLE CHIEUCH U CHIEUCH - 0xAD89: 0xCDAC, //HANGUL SYLLABLE CHIEUCH U KHIEUKH - 0xAD8A: 0xCDAD, //HANGUL SYLLABLE CHIEUCH U THIEUTH - 0xAD8B: 0xCDAE, //HANGUL SYLLABLE CHIEUCH U PHIEUPH - 0xAD8C: 0xCDAF, //HANGUL SYLLABLE CHIEUCH U HIEUH - 0xAD8D: 0xCDB1, //HANGUL SYLLABLE CHIEUCH WEO KIYEOK - 0xAD8E: 0xCDB2, //HANGUL SYLLABLE CHIEUCH WEO SSANGKIYEOK - 0xAD8F: 0xCDB3, //HANGUL SYLLABLE CHIEUCH WEO KIYEOKSIOS - 0xAD90: 0xCDB4, //HANGUL SYLLABLE CHIEUCH WEO NIEUN - 0xAD91: 0xCDB5, //HANGUL SYLLABLE CHIEUCH WEO NIEUNCIEUC - 0xAD92: 0xCDB6, //HANGUL SYLLABLE CHIEUCH WEO NIEUNHIEUH - 0xAD93: 0xCDB7, //HANGUL SYLLABLE CHIEUCH WEO TIKEUT - 0xAD94: 0xCDB8, //HANGUL SYLLABLE CHIEUCH WEO RIEUL - 0xAD95: 0xCDB9, //HANGUL SYLLABLE CHIEUCH WEO RIEULKIYEOK - 0xAD96: 0xCDBA, //HANGUL SYLLABLE CHIEUCH WEO RIEULMIEUM - 0xAD97: 0xCDBB, //HANGUL SYLLABLE CHIEUCH WEO RIEULPIEUP - 0xAD98: 0xCDBC, //HANGUL SYLLABLE CHIEUCH WEO RIEULSIOS - 0xAD99: 0xCDBD, //HANGUL SYLLABLE CHIEUCH WEO RIEULTHIEUTH - 0xAD9A: 0xCDBE, //HANGUL SYLLABLE CHIEUCH WEO RIEULPHIEUPH - 0xAD9B: 0xCDBF, //HANGUL SYLLABLE CHIEUCH WEO RIEULHIEUH - 0xAD9C: 0xCDC0, //HANGUL SYLLABLE CHIEUCH WEO MIEUM - 0xAD9D: 0xCDC1, //HANGUL SYLLABLE CHIEUCH WEO PIEUP - 0xAD9E: 0xCDC2, //HANGUL SYLLABLE CHIEUCH WEO PIEUPSIOS - 0xAD9F: 0xCDC3, //HANGUL SYLLABLE CHIEUCH WEO SIOS - 0xADA0: 0xCDC5, //HANGUL SYLLABLE CHIEUCH WEO IEUNG - 0xAE41: 0xCDC6, //HANGUL SYLLABLE CHIEUCH WEO CIEUC - 0xAE42: 0xCDC7, //HANGUL SYLLABLE CHIEUCH WEO CHIEUCH - 0xAE43: 0xCDC8, //HANGUL SYLLABLE CHIEUCH WEO KHIEUKH - 0xAE44: 0xCDC9, //HANGUL SYLLABLE CHIEUCH WEO THIEUTH - 0xAE45: 0xCDCA, //HANGUL SYLLABLE CHIEUCH WEO PHIEUPH - 0xAE46: 0xCDCB, //HANGUL SYLLABLE CHIEUCH WEO HIEUH - 0xAE47: 0xCDCD, //HANGUL SYLLABLE CHIEUCH WE KIYEOK - 0xAE48: 0xCDCE, //HANGUL SYLLABLE CHIEUCH WE SSANGKIYEOK - 0xAE49: 0xCDCF, //HANGUL SYLLABLE CHIEUCH WE KIYEOKSIOS - 0xAE4A: 0xCDD1, //HANGUL SYLLABLE CHIEUCH WE NIEUNCIEUC - 0xAE4B: 0xCDD2, //HANGUL SYLLABLE CHIEUCH WE NIEUNHIEUH - 0xAE4C: 0xCDD3, //HANGUL SYLLABLE CHIEUCH WE TIKEUT - 0xAE4D: 0xCDD4, //HANGUL SYLLABLE CHIEUCH WE RIEUL - 0xAE4E: 0xCDD5, //HANGUL SYLLABLE CHIEUCH WE RIEULKIYEOK - 0xAE4F: 0xCDD6, //HANGUL SYLLABLE CHIEUCH WE RIEULMIEUM - 0xAE50: 0xCDD7, //HANGUL SYLLABLE CHIEUCH WE RIEULPIEUP - 0xAE51: 0xCDD8, //HANGUL SYLLABLE CHIEUCH WE RIEULSIOS - 0xAE52: 0xCDD9, //HANGUL SYLLABLE CHIEUCH WE RIEULTHIEUTH - 0xAE53: 0xCDDA, //HANGUL SYLLABLE CHIEUCH WE RIEULPHIEUPH - 0xAE54: 0xCDDB, //HANGUL SYLLABLE CHIEUCH WE RIEULHIEUH - 0xAE55: 0xCDDC, //HANGUL SYLLABLE CHIEUCH WE MIEUM - 0xAE56: 0xCDDD, //HANGUL SYLLABLE CHIEUCH WE PIEUP - 0xAE57: 0xCDDE, //HANGUL SYLLABLE CHIEUCH WE PIEUPSIOS - 0xAE58: 0xCDDF, //HANGUL SYLLABLE CHIEUCH WE SIOS - 0xAE59: 0xCDE0, //HANGUL SYLLABLE CHIEUCH WE SSANGSIOS - 0xAE5A: 0xCDE1, //HANGUL SYLLABLE CHIEUCH WE IEUNG - 0xAE61: 0xCDE2, //HANGUL SYLLABLE CHIEUCH WE CIEUC - 0xAE62: 0xCDE3, //HANGUL SYLLABLE CHIEUCH WE CHIEUCH - 0xAE63: 0xCDE4, //HANGUL SYLLABLE CHIEUCH WE KHIEUKH - 0xAE64: 0xCDE5, //HANGUL SYLLABLE CHIEUCH WE THIEUTH - 0xAE65: 0xCDE6, //HANGUL SYLLABLE CHIEUCH WE PHIEUPH - 0xAE66: 0xCDE7, //HANGUL SYLLABLE CHIEUCH WE HIEUH - 0xAE67: 0xCDE9, //HANGUL SYLLABLE CHIEUCH WI KIYEOK - 0xAE68: 0xCDEA, //HANGUL SYLLABLE CHIEUCH WI SSANGKIYEOK - 0xAE69: 0xCDEB, //HANGUL SYLLABLE CHIEUCH WI KIYEOKSIOS - 0xAE6A: 0xCDED, //HANGUL SYLLABLE CHIEUCH WI NIEUNCIEUC - 0xAE6B: 0xCDEE, //HANGUL SYLLABLE CHIEUCH WI NIEUNHIEUH - 0xAE6C: 0xCDEF, //HANGUL SYLLABLE CHIEUCH WI TIKEUT - 0xAE6D: 0xCDF1, //HANGUL SYLLABLE CHIEUCH WI RIEULKIYEOK - 0xAE6E: 0xCDF2, //HANGUL SYLLABLE CHIEUCH WI RIEULMIEUM - 0xAE6F: 0xCDF3, //HANGUL SYLLABLE CHIEUCH WI RIEULPIEUP - 0xAE70: 0xCDF4, //HANGUL SYLLABLE CHIEUCH WI RIEULSIOS - 0xAE71: 0xCDF5, //HANGUL SYLLABLE CHIEUCH WI RIEULTHIEUTH - 0xAE72: 0xCDF6, //HANGUL SYLLABLE CHIEUCH WI RIEULPHIEUPH - 0xAE73: 0xCDF7, //HANGUL SYLLABLE CHIEUCH WI RIEULHIEUH - 0xAE74: 0xCDFA, //HANGUL SYLLABLE CHIEUCH WI PIEUPSIOS - 0xAE75: 0xCDFC, //HANGUL SYLLABLE CHIEUCH WI SSANGSIOS - 0xAE76: 0xCDFE, //HANGUL SYLLABLE CHIEUCH WI CIEUC - 0xAE77: 0xCDFF, //HANGUL SYLLABLE CHIEUCH WI CHIEUCH - 0xAE78: 0xCE00, //HANGUL SYLLABLE CHIEUCH WI KHIEUKH - 0xAE79: 0xCE01, //HANGUL SYLLABLE CHIEUCH WI THIEUTH - 0xAE7A: 0xCE02, //HANGUL SYLLABLE CHIEUCH WI PHIEUPH - 0xAE81: 0xCE03, //HANGUL SYLLABLE CHIEUCH WI HIEUH - 0xAE82: 0xCE05, //HANGUL SYLLABLE CHIEUCH YU KIYEOK - 0xAE83: 0xCE06, //HANGUL SYLLABLE CHIEUCH YU SSANGKIYEOK - 0xAE84: 0xCE07, //HANGUL SYLLABLE CHIEUCH YU KIYEOKSIOS - 0xAE85: 0xCE09, //HANGUL SYLLABLE CHIEUCH YU NIEUNCIEUC - 0xAE86: 0xCE0A, //HANGUL SYLLABLE CHIEUCH YU NIEUNHIEUH - 0xAE87: 0xCE0B, //HANGUL SYLLABLE CHIEUCH YU TIKEUT - 0xAE88: 0xCE0D, //HANGUL SYLLABLE CHIEUCH YU RIEULKIYEOK - 0xAE89: 0xCE0E, //HANGUL SYLLABLE CHIEUCH YU RIEULMIEUM - 0xAE8A: 0xCE0F, //HANGUL SYLLABLE CHIEUCH YU RIEULPIEUP - 0xAE8B: 0xCE10, //HANGUL SYLLABLE CHIEUCH YU RIEULSIOS - 0xAE8C: 0xCE11, //HANGUL SYLLABLE CHIEUCH YU RIEULTHIEUTH - 0xAE8D: 0xCE12, //HANGUL SYLLABLE CHIEUCH YU RIEULPHIEUPH - 0xAE8E: 0xCE13, //HANGUL SYLLABLE CHIEUCH YU RIEULHIEUH - 0xAE8F: 0xCE15, //HANGUL SYLLABLE CHIEUCH YU PIEUP - 0xAE90: 0xCE16, //HANGUL SYLLABLE CHIEUCH YU PIEUPSIOS - 0xAE91: 0xCE17, //HANGUL SYLLABLE CHIEUCH YU SIOS - 0xAE92: 0xCE18, //HANGUL SYLLABLE CHIEUCH YU SSANGSIOS - 0xAE93: 0xCE1A, //HANGUL SYLLABLE CHIEUCH YU CIEUC - 0xAE94: 0xCE1B, //HANGUL SYLLABLE CHIEUCH YU CHIEUCH - 0xAE95: 0xCE1C, //HANGUL SYLLABLE CHIEUCH YU KHIEUKH - 0xAE96: 0xCE1D, //HANGUL SYLLABLE CHIEUCH YU THIEUTH - 0xAE97: 0xCE1E, //HANGUL SYLLABLE CHIEUCH YU PHIEUPH - 0xAE98: 0xCE1F, //HANGUL SYLLABLE CHIEUCH YU HIEUH - 0xAE99: 0xCE22, //HANGUL SYLLABLE CHIEUCH EU SSANGKIYEOK - 0xAE9A: 0xCE23, //HANGUL SYLLABLE CHIEUCH EU KIYEOKSIOS - 0xAE9B: 0xCE25, //HANGUL SYLLABLE CHIEUCH EU NIEUNCIEUC - 0xAE9C: 0xCE26, //HANGUL SYLLABLE CHIEUCH EU NIEUNHIEUH - 0xAE9D: 0xCE27, //HANGUL SYLLABLE CHIEUCH EU TIKEUT - 0xAE9E: 0xCE29, //HANGUL SYLLABLE CHIEUCH EU RIEULKIYEOK - 0xAE9F: 0xCE2A, //HANGUL SYLLABLE CHIEUCH EU RIEULMIEUM - 0xAEA0: 0xCE2B, //HANGUL SYLLABLE CHIEUCH EU RIEULPIEUP - 0xAF41: 0xCE2C, //HANGUL SYLLABLE CHIEUCH EU RIEULSIOS - 0xAF42: 0xCE2D, //HANGUL SYLLABLE CHIEUCH EU RIEULTHIEUTH - 0xAF43: 0xCE2E, //HANGUL SYLLABLE CHIEUCH EU RIEULPHIEUPH - 0xAF44: 0xCE2F, //HANGUL SYLLABLE CHIEUCH EU RIEULHIEUH - 0xAF45: 0xCE32, //HANGUL SYLLABLE CHIEUCH EU PIEUPSIOS - 0xAF46: 0xCE34, //HANGUL SYLLABLE CHIEUCH EU SSANGSIOS - 0xAF47: 0xCE36, //HANGUL SYLLABLE CHIEUCH EU CIEUC - 0xAF48: 0xCE37, //HANGUL SYLLABLE CHIEUCH EU CHIEUCH - 0xAF49: 0xCE38, //HANGUL SYLLABLE CHIEUCH EU KHIEUKH - 0xAF4A: 0xCE39, //HANGUL SYLLABLE CHIEUCH EU THIEUTH - 0xAF4B: 0xCE3A, //HANGUL SYLLABLE CHIEUCH EU PHIEUPH - 0xAF4C: 0xCE3B, //HANGUL SYLLABLE CHIEUCH EU HIEUH - 0xAF4D: 0xCE3C, //HANGUL SYLLABLE CHIEUCH YI - 0xAF4E: 0xCE3D, //HANGUL SYLLABLE CHIEUCH YI KIYEOK - 0xAF4F: 0xCE3E, //HANGUL SYLLABLE CHIEUCH YI SSANGKIYEOK - 0xAF50: 0xCE3F, //HANGUL SYLLABLE CHIEUCH YI KIYEOKSIOS - 0xAF51: 0xCE40, //HANGUL SYLLABLE CHIEUCH YI NIEUN - 0xAF52: 0xCE41, //HANGUL SYLLABLE CHIEUCH YI NIEUNCIEUC - 0xAF53: 0xCE42, //HANGUL SYLLABLE CHIEUCH YI NIEUNHIEUH - 0xAF54: 0xCE43, //HANGUL SYLLABLE CHIEUCH YI TIKEUT - 0xAF55: 0xCE44, //HANGUL SYLLABLE CHIEUCH YI RIEUL - 0xAF56: 0xCE45, //HANGUL SYLLABLE CHIEUCH YI RIEULKIYEOK - 0xAF57: 0xCE46, //HANGUL SYLLABLE CHIEUCH YI RIEULMIEUM - 0xAF58: 0xCE47, //HANGUL SYLLABLE CHIEUCH YI RIEULPIEUP - 0xAF59: 0xCE48, //HANGUL SYLLABLE CHIEUCH YI RIEULSIOS - 0xAF5A: 0xCE49, //HANGUL SYLLABLE CHIEUCH YI RIEULTHIEUTH - 0xAF61: 0xCE4A, //HANGUL SYLLABLE CHIEUCH YI RIEULPHIEUPH - 0xAF62: 0xCE4B, //HANGUL SYLLABLE CHIEUCH YI RIEULHIEUH - 0xAF63: 0xCE4C, //HANGUL SYLLABLE CHIEUCH YI MIEUM - 0xAF64: 0xCE4D, //HANGUL SYLLABLE CHIEUCH YI PIEUP - 0xAF65: 0xCE4E, //HANGUL SYLLABLE CHIEUCH YI PIEUPSIOS - 0xAF66: 0xCE4F, //HANGUL SYLLABLE CHIEUCH YI SIOS - 0xAF67: 0xCE50, //HANGUL SYLLABLE CHIEUCH YI SSANGSIOS - 0xAF68: 0xCE51, //HANGUL SYLLABLE CHIEUCH YI IEUNG - 0xAF69: 0xCE52, //HANGUL SYLLABLE CHIEUCH YI CIEUC - 0xAF6A: 0xCE53, //HANGUL SYLLABLE CHIEUCH YI CHIEUCH - 0xAF6B: 0xCE54, //HANGUL SYLLABLE CHIEUCH YI KHIEUKH - 0xAF6C: 0xCE55, //HANGUL SYLLABLE CHIEUCH YI THIEUTH - 0xAF6D: 0xCE56, //HANGUL SYLLABLE CHIEUCH YI PHIEUPH - 0xAF6E: 0xCE57, //HANGUL SYLLABLE CHIEUCH YI HIEUH - 0xAF6F: 0xCE5A, //HANGUL SYLLABLE CHIEUCH I SSANGKIYEOK - 0xAF70: 0xCE5B, //HANGUL SYLLABLE CHIEUCH I KIYEOKSIOS - 0xAF71: 0xCE5D, //HANGUL SYLLABLE CHIEUCH I NIEUNCIEUC - 0xAF72: 0xCE5E, //HANGUL SYLLABLE CHIEUCH I NIEUNHIEUH - 0xAF73: 0xCE62, //HANGUL SYLLABLE CHIEUCH I RIEULMIEUM - 0xAF74: 0xCE63, //HANGUL SYLLABLE CHIEUCH I RIEULPIEUP - 0xAF75: 0xCE64, //HANGUL SYLLABLE CHIEUCH I RIEULSIOS - 0xAF76: 0xCE65, //HANGUL SYLLABLE CHIEUCH I RIEULTHIEUTH - 0xAF77: 0xCE66, //HANGUL SYLLABLE CHIEUCH I RIEULPHIEUPH - 0xAF78: 0xCE67, //HANGUL SYLLABLE CHIEUCH I RIEULHIEUH - 0xAF79: 0xCE6A, //HANGUL SYLLABLE CHIEUCH I PIEUPSIOS - 0xAF7A: 0xCE6C, //HANGUL SYLLABLE CHIEUCH I SSANGSIOS - 0xAF81: 0xCE6E, //HANGUL SYLLABLE CHIEUCH I CIEUC - 0xAF82: 0xCE6F, //HANGUL SYLLABLE CHIEUCH I CHIEUCH - 0xAF83: 0xCE70, //HANGUL SYLLABLE CHIEUCH I KHIEUKH - 0xAF84: 0xCE71, //HANGUL SYLLABLE CHIEUCH I THIEUTH - 0xAF85: 0xCE72, //HANGUL SYLLABLE CHIEUCH I PHIEUPH - 0xAF86: 0xCE73, //HANGUL SYLLABLE CHIEUCH I HIEUH - 0xAF87: 0xCE76, //HANGUL SYLLABLE KHIEUKH A SSANGKIYEOK - 0xAF88: 0xCE77, //HANGUL SYLLABLE KHIEUKH A KIYEOKSIOS - 0xAF89: 0xCE79, //HANGUL SYLLABLE KHIEUKH A NIEUNCIEUC - 0xAF8A: 0xCE7A, //HANGUL SYLLABLE KHIEUKH A NIEUNHIEUH - 0xAF8B: 0xCE7B, //HANGUL SYLLABLE KHIEUKH A TIKEUT - 0xAF8C: 0xCE7D, //HANGUL SYLLABLE KHIEUKH A RIEULKIYEOK - 0xAF8D: 0xCE7E, //HANGUL SYLLABLE KHIEUKH A RIEULMIEUM - 0xAF8E: 0xCE7F, //HANGUL SYLLABLE KHIEUKH A RIEULPIEUP - 0xAF8F: 0xCE80, //HANGUL SYLLABLE KHIEUKH A RIEULSIOS - 0xAF90: 0xCE81, //HANGUL SYLLABLE KHIEUKH A RIEULTHIEUTH - 0xAF91: 0xCE82, //HANGUL SYLLABLE KHIEUKH A RIEULPHIEUPH - 0xAF92: 0xCE83, //HANGUL SYLLABLE KHIEUKH A RIEULHIEUH - 0xAF93: 0xCE86, //HANGUL SYLLABLE KHIEUKH A PIEUPSIOS - 0xAF94: 0xCE88, //HANGUL SYLLABLE KHIEUKH A SSANGSIOS - 0xAF95: 0xCE8A, //HANGUL SYLLABLE KHIEUKH A CIEUC - 0xAF96: 0xCE8B, //HANGUL SYLLABLE KHIEUKH A CHIEUCH - 0xAF97: 0xCE8C, //HANGUL SYLLABLE KHIEUKH A KHIEUKH - 0xAF98: 0xCE8D, //HANGUL SYLLABLE KHIEUKH A THIEUTH - 0xAF99: 0xCE8E, //HANGUL SYLLABLE KHIEUKH A PHIEUPH - 0xAF9A: 0xCE8F, //HANGUL SYLLABLE KHIEUKH A HIEUH - 0xAF9B: 0xCE92, //HANGUL SYLLABLE KHIEUKH AE SSANGKIYEOK - 0xAF9C: 0xCE93, //HANGUL SYLLABLE KHIEUKH AE KIYEOKSIOS - 0xAF9D: 0xCE95, //HANGUL SYLLABLE KHIEUKH AE NIEUNCIEUC - 0xAF9E: 0xCE96, //HANGUL SYLLABLE KHIEUKH AE NIEUNHIEUH - 0xAF9F: 0xCE97, //HANGUL SYLLABLE KHIEUKH AE TIKEUT - 0xAFA0: 0xCE99, //HANGUL SYLLABLE KHIEUKH AE RIEULKIYEOK - 0xB041: 0xCE9A, //HANGUL SYLLABLE KHIEUKH AE RIEULMIEUM - 0xB042: 0xCE9B, //HANGUL SYLLABLE KHIEUKH AE RIEULPIEUP - 0xB043: 0xCE9C, //HANGUL SYLLABLE KHIEUKH AE RIEULSIOS - 0xB044: 0xCE9D, //HANGUL SYLLABLE KHIEUKH AE RIEULTHIEUTH - 0xB045: 0xCE9E, //HANGUL SYLLABLE KHIEUKH AE RIEULPHIEUPH - 0xB046: 0xCE9F, //HANGUL SYLLABLE KHIEUKH AE RIEULHIEUH - 0xB047: 0xCEA2, //HANGUL SYLLABLE KHIEUKH AE PIEUPSIOS - 0xB048: 0xCEA6, //HANGUL SYLLABLE KHIEUKH AE CIEUC - 0xB049: 0xCEA7, //HANGUL SYLLABLE KHIEUKH AE CHIEUCH - 0xB04A: 0xCEA8, //HANGUL SYLLABLE KHIEUKH AE KHIEUKH - 0xB04B: 0xCEA9, //HANGUL SYLLABLE KHIEUKH AE THIEUTH - 0xB04C: 0xCEAA, //HANGUL SYLLABLE KHIEUKH AE PHIEUPH - 0xB04D: 0xCEAB, //HANGUL SYLLABLE KHIEUKH AE HIEUH - 0xB04E: 0xCEAE, //HANGUL SYLLABLE KHIEUKH YA SSANGKIYEOK - 0xB04F: 0xCEAF, //HANGUL SYLLABLE KHIEUKH YA KIYEOKSIOS - 0xB050: 0xCEB0, //HANGUL SYLLABLE KHIEUKH YA NIEUN - 0xB051: 0xCEB1, //HANGUL SYLLABLE KHIEUKH YA NIEUNCIEUC - 0xB052: 0xCEB2, //HANGUL SYLLABLE KHIEUKH YA NIEUNHIEUH - 0xB053: 0xCEB3, //HANGUL SYLLABLE KHIEUKH YA TIKEUT - 0xB054: 0xCEB4, //HANGUL SYLLABLE KHIEUKH YA RIEUL - 0xB055: 0xCEB5, //HANGUL SYLLABLE KHIEUKH YA RIEULKIYEOK - 0xB056: 0xCEB6, //HANGUL SYLLABLE KHIEUKH YA RIEULMIEUM - 0xB057: 0xCEB7, //HANGUL SYLLABLE KHIEUKH YA RIEULPIEUP - 0xB058: 0xCEB8, //HANGUL SYLLABLE KHIEUKH YA RIEULSIOS - 0xB059: 0xCEB9, //HANGUL SYLLABLE KHIEUKH YA RIEULTHIEUTH - 0xB05A: 0xCEBA, //HANGUL SYLLABLE KHIEUKH YA RIEULPHIEUPH - 0xB061: 0xCEBB, //HANGUL SYLLABLE KHIEUKH YA RIEULHIEUH - 0xB062: 0xCEBC, //HANGUL SYLLABLE KHIEUKH YA MIEUM - 0xB063: 0xCEBD, //HANGUL SYLLABLE KHIEUKH YA PIEUP - 0xB064: 0xCEBE, //HANGUL SYLLABLE KHIEUKH YA PIEUPSIOS - 0xB065: 0xCEBF, //HANGUL SYLLABLE KHIEUKH YA SIOS - 0xB066: 0xCEC0, //HANGUL SYLLABLE KHIEUKH YA SSANGSIOS - 0xB067: 0xCEC2, //HANGUL SYLLABLE KHIEUKH YA CIEUC - 0xB068: 0xCEC3, //HANGUL SYLLABLE KHIEUKH YA CHIEUCH - 0xB069: 0xCEC4, //HANGUL SYLLABLE KHIEUKH YA KHIEUKH - 0xB06A: 0xCEC5, //HANGUL SYLLABLE KHIEUKH YA THIEUTH - 0xB06B: 0xCEC6, //HANGUL SYLLABLE KHIEUKH YA PHIEUPH - 0xB06C: 0xCEC7, //HANGUL SYLLABLE KHIEUKH YA HIEUH - 0xB06D: 0xCEC8, //HANGUL SYLLABLE KHIEUKH YAE - 0xB06E: 0xCEC9, //HANGUL SYLLABLE KHIEUKH YAE KIYEOK - 0xB06F: 0xCECA, //HANGUL SYLLABLE KHIEUKH YAE SSANGKIYEOK - 0xB070: 0xCECB, //HANGUL SYLLABLE KHIEUKH YAE KIYEOKSIOS - 0xB071: 0xCECC, //HANGUL SYLLABLE KHIEUKH YAE NIEUN - 0xB072: 0xCECD, //HANGUL SYLLABLE KHIEUKH YAE NIEUNCIEUC - 0xB073: 0xCECE, //HANGUL SYLLABLE KHIEUKH YAE NIEUNHIEUH - 0xB074: 0xCECF, //HANGUL SYLLABLE KHIEUKH YAE TIKEUT - 0xB075: 0xCED0, //HANGUL SYLLABLE KHIEUKH YAE RIEUL - 0xB076: 0xCED1, //HANGUL SYLLABLE KHIEUKH YAE RIEULKIYEOK - 0xB077: 0xCED2, //HANGUL SYLLABLE KHIEUKH YAE RIEULMIEUM - 0xB078: 0xCED3, //HANGUL SYLLABLE KHIEUKH YAE RIEULPIEUP - 0xB079: 0xCED4, //HANGUL SYLLABLE KHIEUKH YAE RIEULSIOS - 0xB07A: 0xCED5, //HANGUL SYLLABLE KHIEUKH YAE RIEULTHIEUTH - 0xB081: 0xCED6, //HANGUL SYLLABLE KHIEUKH YAE RIEULPHIEUPH - 0xB082: 0xCED7, //HANGUL SYLLABLE KHIEUKH YAE RIEULHIEUH - 0xB083: 0xCED8, //HANGUL SYLLABLE KHIEUKH YAE MIEUM - 0xB084: 0xCED9, //HANGUL SYLLABLE KHIEUKH YAE PIEUP - 0xB085: 0xCEDA, //HANGUL SYLLABLE KHIEUKH YAE PIEUPSIOS - 0xB086: 0xCEDB, //HANGUL SYLLABLE KHIEUKH YAE SIOS - 0xB087: 0xCEDC, //HANGUL SYLLABLE KHIEUKH YAE SSANGSIOS - 0xB088: 0xCEDD, //HANGUL SYLLABLE KHIEUKH YAE IEUNG - 0xB089: 0xCEDE, //HANGUL SYLLABLE KHIEUKH YAE CIEUC - 0xB08A: 0xCEDF, //HANGUL SYLLABLE KHIEUKH YAE CHIEUCH - 0xB08B: 0xCEE0, //HANGUL SYLLABLE KHIEUKH YAE KHIEUKH - 0xB08C: 0xCEE1, //HANGUL SYLLABLE KHIEUKH YAE THIEUTH - 0xB08D: 0xCEE2, //HANGUL SYLLABLE KHIEUKH YAE PHIEUPH - 0xB08E: 0xCEE3, //HANGUL SYLLABLE KHIEUKH YAE HIEUH - 0xB08F: 0xCEE6, //HANGUL SYLLABLE KHIEUKH EO SSANGKIYEOK - 0xB090: 0xCEE7, //HANGUL SYLLABLE KHIEUKH EO KIYEOKSIOS - 0xB091: 0xCEE9, //HANGUL SYLLABLE KHIEUKH EO NIEUNCIEUC - 0xB092: 0xCEEA, //HANGUL SYLLABLE KHIEUKH EO NIEUNHIEUH - 0xB093: 0xCEED, //HANGUL SYLLABLE KHIEUKH EO RIEULKIYEOK - 0xB094: 0xCEEE, //HANGUL SYLLABLE KHIEUKH EO RIEULMIEUM - 0xB095: 0xCEEF, //HANGUL SYLLABLE KHIEUKH EO RIEULPIEUP - 0xB096: 0xCEF0, //HANGUL SYLLABLE KHIEUKH EO RIEULSIOS - 0xB097: 0xCEF1, //HANGUL SYLLABLE KHIEUKH EO RIEULTHIEUTH - 0xB098: 0xCEF2, //HANGUL SYLLABLE KHIEUKH EO RIEULPHIEUPH - 0xB099: 0xCEF3, //HANGUL SYLLABLE KHIEUKH EO RIEULHIEUH - 0xB09A: 0xCEF6, //HANGUL SYLLABLE KHIEUKH EO PIEUPSIOS - 0xB09B: 0xCEFA, //HANGUL SYLLABLE KHIEUKH EO CIEUC - 0xB09C: 0xCEFB, //HANGUL SYLLABLE KHIEUKH EO CHIEUCH - 0xB09D: 0xCEFC, //HANGUL SYLLABLE KHIEUKH EO KHIEUKH - 0xB09E: 0xCEFD, //HANGUL SYLLABLE KHIEUKH EO THIEUTH - 0xB09F: 0xCEFE, //HANGUL SYLLABLE KHIEUKH EO PHIEUPH - 0xB0A0: 0xCEFF, //HANGUL SYLLABLE KHIEUKH EO HIEUH - 0xB0A1: 0xAC00, //HANGUL SYLLABLE KIYEOK A - 0xB0A2: 0xAC01, //HANGUL SYLLABLE KIYEOK A KIYEOK - 0xB0A3: 0xAC04, //HANGUL SYLLABLE KIYEOK A NIEUN - 0xB0A4: 0xAC07, //HANGUL SYLLABLE KIYEOK A TIKEUT - 0xB0A5: 0xAC08, //HANGUL SYLLABLE KIYEOK A RIEUL - 0xB0A6: 0xAC09, //HANGUL SYLLABLE KIYEOK A RIEULKIYEOK - 0xB0A7: 0xAC0A, //HANGUL SYLLABLE KIYEOK A RIEULMIEUM - 0xB0A8: 0xAC10, //HANGUL SYLLABLE KIYEOK A MIEUM - 0xB0A9: 0xAC11, //HANGUL SYLLABLE KIYEOK A PIEUP - 0xB0AA: 0xAC12, //HANGUL SYLLABLE KIYEOK A PIEUPSIOS - 0xB0AB: 0xAC13, //HANGUL SYLLABLE KIYEOK A SIOS - 0xB0AC: 0xAC14, //HANGUL SYLLABLE KIYEOK A SSANGSIOS - 0xB0AD: 0xAC15, //HANGUL SYLLABLE KIYEOK A IEUNG - 0xB0AE: 0xAC16, //HANGUL SYLLABLE KIYEOK A CIEUC - 0xB0AF: 0xAC17, //HANGUL SYLLABLE KIYEOK A CHIEUCH - 0xB0B0: 0xAC19, //HANGUL SYLLABLE KIYEOK A THIEUTH - 0xB0B1: 0xAC1A, //HANGUL SYLLABLE KIYEOK A PHIEUPH - 0xB0B2: 0xAC1B, //HANGUL SYLLABLE KIYEOK A HIEUH - 0xB0B3: 0xAC1C, //HANGUL SYLLABLE KIYEOK AE - 0xB0B4: 0xAC1D, //HANGUL SYLLABLE KIYEOK AE KIYEOK - 0xB0B5: 0xAC20, //HANGUL SYLLABLE KIYEOK AE NIEUN - 0xB0B6: 0xAC24, //HANGUL SYLLABLE KIYEOK AE RIEUL - 0xB0B7: 0xAC2C, //HANGUL SYLLABLE KIYEOK AE MIEUM - 0xB0B8: 0xAC2D, //HANGUL SYLLABLE KIYEOK AE PIEUP - 0xB0B9: 0xAC2F, //HANGUL SYLLABLE KIYEOK AE SIOS - 0xB0BA: 0xAC30, //HANGUL SYLLABLE KIYEOK AE SSANGSIOS - 0xB0BB: 0xAC31, //HANGUL SYLLABLE KIYEOK AE IEUNG - 0xB0BC: 0xAC38, //HANGUL SYLLABLE KIYEOK YA - 0xB0BD: 0xAC39, //HANGUL SYLLABLE KIYEOK YA KIYEOK - 0xB0BE: 0xAC3C, //HANGUL SYLLABLE KIYEOK YA NIEUN - 0xB0BF: 0xAC40, //HANGUL SYLLABLE KIYEOK YA RIEUL - 0xB0C0: 0xAC4B, //HANGUL SYLLABLE KIYEOK YA SIOS - 0xB0C1: 0xAC4D, //HANGUL SYLLABLE KIYEOK YA IEUNG - 0xB0C2: 0xAC54, //HANGUL SYLLABLE KIYEOK YAE - 0xB0C3: 0xAC58, //HANGUL SYLLABLE KIYEOK YAE NIEUN - 0xB0C4: 0xAC5C, //HANGUL SYLLABLE KIYEOK YAE RIEUL - 0xB0C5: 0xAC70, //HANGUL SYLLABLE KIYEOK EO - 0xB0C6: 0xAC71, //HANGUL SYLLABLE KIYEOK EO KIYEOK - 0xB0C7: 0xAC74, //HANGUL SYLLABLE KIYEOK EO NIEUN - 0xB0C8: 0xAC77, //HANGUL SYLLABLE KIYEOK EO TIKEUT - 0xB0C9: 0xAC78, //HANGUL SYLLABLE KIYEOK EO RIEUL - 0xB0CA: 0xAC7A, //HANGUL SYLLABLE KIYEOK EO RIEULMIEUM - 0xB0CB: 0xAC80, //HANGUL SYLLABLE KIYEOK EO MIEUM - 0xB0CC: 0xAC81, //HANGUL SYLLABLE KIYEOK EO PIEUP - 0xB0CD: 0xAC83, //HANGUL SYLLABLE KIYEOK EO SIOS - 0xB0CE: 0xAC84, //HANGUL SYLLABLE KIYEOK EO SSANGSIOS - 0xB0CF: 0xAC85, //HANGUL SYLLABLE KIYEOK EO IEUNG - 0xB0D0: 0xAC86, //HANGUL SYLLABLE KIYEOK EO CIEUC - 0xB0D1: 0xAC89, //HANGUL SYLLABLE KIYEOK EO THIEUTH - 0xB0D2: 0xAC8A, //HANGUL SYLLABLE KIYEOK EO PHIEUPH - 0xB0D3: 0xAC8B, //HANGUL SYLLABLE KIYEOK EO HIEUH - 0xB0D4: 0xAC8C, //HANGUL SYLLABLE KIYEOK E - 0xB0D5: 0xAC90, //HANGUL SYLLABLE KIYEOK E NIEUN - 0xB0D6: 0xAC94, //HANGUL SYLLABLE KIYEOK E RIEUL - 0xB0D7: 0xAC9C, //HANGUL SYLLABLE KIYEOK E MIEUM - 0xB0D8: 0xAC9D, //HANGUL SYLLABLE KIYEOK E PIEUP - 0xB0D9: 0xAC9F, //HANGUL SYLLABLE KIYEOK E SIOS - 0xB0DA: 0xACA0, //HANGUL SYLLABLE KIYEOK E SSANGSIOS - 0xB0DB: 0xACA1, //HANGUL SYLLABLE KIYEOK E IEUNG - 0xB0DC: 0xACA8, //HANGUL SYLLABLE KIYEOK YEO - 0xB0DD: 0xACA9, //HANGUL SYLLABLE KIYEOK YEO KIYEOK - 0xB0DE: 0xACAA, //HANGUL SYLLABLE KIYEOK YEO SSANGKIYEOK - 0xB0DF: 0xACAC, //HANGUL SYLLABLE KIYEOK YEO NIEUN - 0xB0E0: 0xACAF, //HANGUL SYLLABLE KIYEOK YEO TIKEUT - 0xB0E1: 0xACB0, //HANGUL SYLLABLE KIYEOK YEO RIEUL - 0xB0E2: 0xACB8, //HANGUL SYLLABLE KIYEOK YEO MIEUM - 0xB0E3: 0xACB9, //HANGUL SYLLABLE KIYEOK YEO PIEUP - 0xB0E4: 0xACBB, //HANGUL SYLLABLE KIYEOK YEO SIOS - 0xB0E5: 0xACBC, //HANGUL SYLLABLE KIYEOK YEO SSANGSIOS - 0xB0E6: 0xACBD, //HANGUL SYLLABLE KIYEOK YEO IEUNG - 0xB0E7: 0xACC1, //HANGUL SYLLABLE KIYEOK YEO THIEUTH - 0xB0E8: 0xACC4, //HANGUL SYLLABLE KIYEOK YE - 0xB0E9: 0xACC8, //HANGUL SYLLABLE KIYEOK YE NIEUN - 0xB0EA: 0xACCC, //HANGUL SYLLABLE KIYEOK YE RIEUL - 0xB0EB: 0xACD5, //HANGUL SYLLABLE KIYEOK YE PIEUP - 0xB0EC: 0xACD7, //HANGUL SYLLABLE KIYEOK YE SIOS - 0xB0ED: 0xACE0, //HANGUL SYLLABLE KIYEOK O - 0xB0EE: 0xACE1, //HANGUL SYLLABLE KIYEOK O KIYEOK - 0xB0EF: 0xACE4, //HANGUL SYLLABLE KIYEOK O NIEUN - 0xB0F0: 0xACE7, //HANGUL SYLLABLE KIYEOK O TIKEUT - 0xB0F1: 0xACE8, //HANGUL SYLLABLE KIYEOK O RIEUL - 0xB0F2: 0xACEA, //HANGUL SYLLABLE KIYEOK O RIEULMIEUM - 0xB0F3: 0xACEC, //HANGUL SYLLABLE KIYEOK O RIEULSIOS - 0xB0F4: 0xACEF, //HANGUL SYLLABLE KIYEOK O RIEULHIEUH - 0xB0F5: 0xACF0, //HANGUL SYLLABLE KIYEOK O MIEUM - 0xB0F6: 0xACF1, //HANGUL SYLLABLE KIYEOK O PIEUP - 0xB0F7: 0xACF3, //HANGUL SYLLABLE KIYEOK O SIOS - 0xB0F8: 0xACF5, //HANGUL SYLLABLE KIYEOK O IEUNG - 0xB0F9: 0xACF6, //HANGUL SYLLABLE KIYEOK O CIEUC - 0xB0FA: 0xACFC, //HANGUL SYLLABLE KIYEOK WA - 0xB0FB: 0xACFD, //HANGUL SYLLABLE KIYEOK WA KIYEOK - 0xB0FC: 0xAD00, //HANGUL SYLLABLE KIYEOK WA NIEUN - 0xB0FD: 0xAD04, //HANGUL SYLLABLE KIYEOK WA RIEUL - 0xB0FE: 0xAD06, //HANGUL SYLLABLE KIYEOK WA RIEULMIEUM - 0xB141: 0xCF02, //HANGUL SYLLABLE KHIEUKH E SSANGKIYEOK - 0xB142: 0xCF03, //HANGUL SYLLABLE KHIEUKH E KIYEOKSIOS - 0xB143: 0xCF05, //HANGUL SYLLABLE KHIEUKH E NIEUNCIEUC - 0xB144: 0xCF06, //HANGUL SYLLABLE KHIEUKH E NIEUNHIEUH - 0xB145: 0xCF07, //HANGUL SYLLABLE KHIEUKH E TIKEUT - 0xB146: 0xCF09, //HANGUL SYLLABLE KHIEUKH E RIEULKIYEOK - 0xB147: 0xCF0A, //HANGUL SYLLABLE KHIEUKH E RIEULMIEUM - 0xB148: 0xCF0B, //HANGUL SYLLABLE KHIEUKH E RIEULPIEUP - 0xB149: 0xCF0C, //HANGUL SYLLABLE KHIEUKH E RIEULSIOS - 0xB14A: 0xCF0D, //HANGUL SYLLABLE KHIEUKH E RIEULTHIEUTH - 0xB14B: 0xCF0E, //HANGUL SYLLABLE KHIEUKH E RIEULPHIEUPH - 0xB14C: 0xCF0F, //HANGUL SYLLABLE KHIEUKH E RIEULHIEUH - 0xB14D: 0xCF12, //HANGUL SYLLABLE KHIEUKH E PIEUPSIOS - 0xB14E: 0xCF14, //HANGUL SYLLABLE KHIEUKH E SSANGSIOS - 0xB14F: 0xCF16, //HANGUL SYLLABLE KHIEUKH E CIEUC - 0xB150: 0xCF17, //HANGUL SYLLABLE KHIEUKH E CHIEUCH - 0xB151: 0xCF18, //HANGUL SYLLABLE KHIEUKH E KHIEUKH - 0xB152: 0xCF19, //HANGUL SYLLABLE KHIEUKH E THIEUTH - 0xB153: 0xCF1A, //HANGUL SYLLABLE KHIEUKH E PHIEUPH - 0xB154: 0xCF1B, //HANGUL SYLLABLE KHIEUKH E HIEUH - 0xB155: 0xCF1D, //HANGUL SYLLABLE KHIEUKH YEO KIYEOK - 0xB156: 0xCF1E, //HANGUL SYLLABLE KHIEUKH YEO SSANGKIYEOK - 0xB157: 0xCF1F, //HANGUL SYLLABLE KHIEUKH YEO KIYEOKSIOS - 0xB158: 0xCF21, //HANGUL SYLLABLE KHIEUKH YEO NIEUNCIEUC - 0xB159: 0xCF22, //HANGUL SYLLABLE KHIEUKH YEO NIEUNHIEUH - 0xB15A: 0xCF23, //HANGUL SYLLABLE KHIEUKH YEO TIKEUT - 0xB161: 0xCF25, //HANGUL SYLLABLE KHIEUKH YEO RIEULKIYEOK - 0xB162: 0xCF26, //HANGUL SYLLABLE KHIEUKH YEO RIEULMIEUM - 0xB163: 0xCF27, //HANGUL SYLLABLE KHIEUKH YEO RIEULPIEUP - 0xB164: 0xCF28, //HANGUL SYLLABLE KHIEUKH YEO RIEULSIOS - 0xB165: 0xCF29, //HANGUL SYLLABLE KHIEUKH YEO RIEULTHIEUTH - 0xB166: 0xCF2A, //HANGUL SYLLABLE KHIEUKH YEO RIEULPHIEUPH - 0xB167: 0xCF2B, //HANGUL SYLLABLE KHIEUKH YEO RIEULHIEUH - 0xB168: 0xCF2E, //HANGUL SYLLABLE KHIEUKH YEO PIEUPSIOS - 0xB169: 0xCF32, //HANGUL SYLLABLE KHIEUKH YEO CIEUC - 0xB16A: 0xCF33, //HANGUL SYLLABLE KHIEUKH YEO CHIEUCH - 0xB16B: 0xCF34, //HANGUL SYLLABLE KHIEUKH YEO KHIEUKH - 0xB16C: 0xCF35, //HANGUL SYLLABLE KHIEUKH YEO THIEUTH - 0xB16D: 0xCF36, //HANGUL SYLLABLE KHIEUKH YEO PHIEUPH - 0xB16E: 0xCF37, //HANGUL SYLLABLE KHIEUKH YEO HIEUH - 0xB16F: 0xCF39, //HANGUL SYLLABLE KHIEUKH YE KIYEOK - 0xB170: 0xCF3A, //HANGUL SYLLABLE KHIEUKH YE SSANGKIYEOK - 0xB171: 0xCF3B, //HANGUL SYLLABLE KHIEUKH YE KIYEOKSIOS - 0xB172: 0xCF3C, //HANGUL SYLLABLE KHIEUKH YE NIEUN - 0xB173: 0xCF3D, //HANGUL SYLLABLE KHIEUKH YE NIEUNCIEUC - 0xB174: 0xCF3E, //HANGUL SYLLABLE KHIEUKH YE NIEUNHIEUH - 0xB175: 0xCF3F, //HANGUL SYLLABLE KHIEUKH YE TIKEUT - 0xB176: 0xCF40, //HANGUL SYLLABLE KHIEUKH YE RIEUL - 0xB177: 0xCF41, //HANGUL SYLLABLE KHIEUKH YE RIEULKIYEOK - 0xB178: 0xCF42, //HANGUL SYLLABLE KHIEUKH YE RIEULMIEUM - 0xB179: 0xCF43, //HANGUL SYLLABLE KHIEUKH YE RIEULPIEUP - 0xB17A: 0xCF44, //HANGUL SYLLABLE KHIEUKH YE RIEULSIOS - 0xB181: 0xCF45, //HANGUL SYLLABLE KHIEUKH YE RIEULTHIEUTH - 0xB182: 0xCF46, //HANGUL SYLLABLE KHIEUKH YE RIEULPHIEUPH - 0xB183: 0xCF47, //HANGUL SYLLABLE KHIEUKH YE RIEULHIEUH - 0xB184: 0xCF48, //HANGUL SYLLABLE KHIEUKH YE MIEUM - 0xB185: 0xCF49, //HANGUL SYLLABLE KHIEUKH YE PIEUP - 0xB186: 0xCF4A, //HANGUL SYLLABLE KHIEUKH YE PIEUPSIOS - 0xB187: 0xCF4B, //HANGUL SYLLABLE KHIEUKH YE SIOS - 0xB188: 0xCF4C, //HANGUL SYLLABLE KHIEUKH YE SSANGSIOS - 0xB189: 0xCF4D, //HANGUL SYLLABLE KHIEUKH YE IEUNG - 0xB18A: 0xCF4E, //HANGUL SYLLABLE KHIEUKH YE CIEUC - 0xB18B: 0xCF4F, //HANGUL SYLLABLE KHIEUKH YE CHIEUCH - 0xB18C: 0xCF50, //HANGUL SYLLABLE KHIEUKH YE KHIEUKH - 0xB18D: 0xCF51, //HANGUL SYLLABLE KHIEUKH YE THIEUTH - 0xB18E: 0xCF52, //HANGUL SYLLABLE KHIEUKH YE PHIEUPH - 0xB18F: 0xCF53, //HANGUL SYLLABLE KHIEUKH YE HIEUH - 0xB190: 0xCF56, //HANGUL SYLLABLE KHIEUKH O SSANGKIYEOK - 0xB191: 0xCF57, //HANGUL SYLLABLE KHIEUKH O KIYEOKSIOS - 0xB192: 0xCF59, //HANGUL SYLLABLE KHIEUKH O NIEUNCIEUC - 0xB193: 0xCF5A, //HANGUL SYLLABLE KHIEUKH O NIEUNHIEUH - 0xB194: 0xCF5B, //HANGUL SYLLABLE KHIEUKH O TIKEUT - 0xB195: 0xCF5D, //HANGUL SYLLABLE KHIEUKH O RIEULKIYEOK - 0xB196: 0xCF5E, //HANGUL SYLLABLE KHIEUKH O RIEULMIEUM - 0xB197: 0xCF5F, //HANGUL SYLLABLE KHIEUKH O RIEULPIEUP - 0xB198: 0xCF60, //HANGUL SYLLABLE KHIEUKH O RIEULSIOS - 0xB199: 0xCF61, //HANGUL SYLLABLE KHIEUKH O RIEULTHIEUTH - 0xB19A: 0xCF62, //HANGUL SYLLABLE KHIEUKH O RIEULPHIEUPH - 0xB19B: 0xCF63, //HANGUL SYLLABLE KHIEUKH O RIEULHIEUH - 0xB19C: 0xCF66, //HANGUL SYLLABLE KHIEUKH O PIEUPSIOS - 0xB19D: 0xCF68, //HANGUL SYLLABLE KHIEUKH O SSANGSIOS - 0xB19E: 0xCF6A, //HANGUL SYLLABLE KHIEUKH O CIEUC - 0xB19F: 0xCF6B, //HANGUL SYLLABLE KHIEUKH O CHIEUCH - 0xB1A0: 0xCF6C, //HANGUL SYLLABLE KHIEUKH O KHIEUKH - 0xB1A1: 0xAD0C, //HANGUL SYLLABLE KIYEOK WA MIEUM - 0xB1A2: 0xAD0D, //HANGUL SYLLABLE KIYEOK WA PIEUP - 0xB1A3: 0xAD0F, //HANGUL SYLLABLE KIYEOK WA SIOS - 0xB1A4: 0xAD11, //HANGUL SYLLABLE KIYEOK WA IEUNG - 0xB1A5: 0xAD18, //HANGUL SYLLABLE KIYEOK WAE - 0xB1A6: 0xAD1C, //HANGUL SYLLABLE KIYEOK WAE NIEUN - 0xB1A7: 0xAD20, //HANGUL SYLLABLE KIYEOK WAE RIEUL - 0xB1A8: 0xAD29, //HANGUL SYLLABLE KIYEOK WAE PIEUP - 0xB1A9: 0xAD2C, //HANGUL SYLLABLE KIYEOK WAE SSANGSIOS - 0xB1AA: 0xAD2D, //HANGUL SYLLABLE KIYEOK WAE IEUNG - 0xB1AB: 0xAD34, //HANGUL SYLLABLE KIYEOK OE - 0xB1AC: 0xAD35, //HANGUL SYLLABLE KIYEOK OE KIYEOK - 0xB1AD: 0xAD38, //HANGUL SYLLABLE KIYEOK OE NIEUN - 0xB1AE: 0xAD3C, //HANGUL SYLLABLE KIYEOK OE RIEUL - 0xB1AF: 0xAD44, //HANGUL SYLLABLE KIYEOK OE MIEUM - 0xB1B0: 0xAD45, //HANGUL SYLLABLE KIYEOK OE PIEUP - 0xB1B1: 0xAD47, //HANGUL SYLLABLE KIYEOK OE SIOS - 0xB1B2: 0xAD49, //HANGUL SYLLABLE KIYEOK OE IEUNG - 0xB1B3: 0xAD50, //HANGUL SYLLABLE KIYEOK YO - 0xB1B4: 0xAD54, //HANGUL SYLLABLE KIYEOK YO NIEUN - 0xB1B5: 0xAD58, //HANGUL SYLLABLE KIYEOK YO RIEUL - 0xB1B6: 0xAD61, //HANGUL SYLLABLE KIYEOK YO PIEUP - 0xB1B7: 0xAD63, //HANGUL SYLLABLE KIYEOK YO SIOS - 0xB1B8: 0xAD6C, //HANGUL SYLLABLE KIYEOK U - 0xB1B9: 0xAD6D, //HANGUL SYLLABLE KIYEOK U KIYEOK - 0xB1BA: 0xAD70, //HANGUL SYLLABLE KIYEOK U NIEUN - 0xB1BB: 0xAD73, //HANGUL SYLLABLE KIYEOK U TIKEUT - 0xB1BC: 0xAD74, //HANGUL SYLLABLE KIYEOK U RIEUL - 0xB1BD: 0xAD75, //HANGUL SYLLABLE KIYEOK U RIEULKIYEOK - 0xB1BE: 0xAD76, //HANGUL SYLLABLE KIYEOK U RIEULMIEUM - 0xB1BF: 0xAD7B, //HANGUL SYLLABLE KIYEOK U RIEULHIEUH - 0xB1C0: 0xAD7C, //HANGUL SYLLABLE KIYEOK U MIEUM - 0xB1C1: 0xAD7D, //HANGUL SYLLABLE KIYEOK U PIEUP - 0xB1C2: 0xAD7F, //HANGUL SYLLABLE KIYEOK U SIOS - 0xB1C3: 0xAD81, //HANGUL SYLLABLE KIYEOK U IEUNG - 0xB1C4: 0xAD82, //HANGUL SYLLABLE KIYEOK U CIEUC - 0xB1C5: 0xAD88, //HANGUL SYLLABLE KIYEOK WEO - 0xB1C6: 0xAD89, //HANGUL SYLLABLE KIYEOK WEO KIYEOK - 0xB1C7: 0xAD8C, //HANGUL SYLLABLE KIYEOK WEO NIEUN - 0xB1C8: 0xAD90, //HANGUL SYLLABLE KIYEOK WEO RIEUL - 0xB1C9: 0xAD9C, //HANGUL SYLLABLE KIYEOK WEO SSANGSIOS - 0xB1CA: 0xAD9D, //HANGUL SYLLABLE KIYEOK WEO IEUNG - 0xB1CB: 0xADA4, //HANGUL SYLLABLE KIYEOK WE - 0xB1CC: 0xADB7, //HANGUL SYLLABLE KIYEOK WE SIOS - 0xB1CD: 0xADC0, //HANGUL SYLLABLE KIYEOK WI - 0xB1CE: 0xADC1, //HANGUL SYLLABLE KIYEOK WI KIYEOK - 0xB1CF: 0xADC4, //HANGUL SYLLABLE KIYEOK WI NIEUN - 0xB1D0: 0xADC8, //HANGUL SYLLABLE KIYEOK WI RIEUL - 0xB1D1: 0xADD0, //HANGUL SYLLABLE KIYEOK WI MIEUM - 0xB1D2: 0xADD1, //HANGUL SYLLABLE KIYEOK WI PIEUP - 0xB1D3: 0xADD3, //HANGUL SYLLABLE KIYEOK WI SIOS - 0xB1D4: 0xADDC, //HANGUL SYLLABLE KIYEOK YU - 0xB1D5: 0xADE0, //HANGUL SYLLABLE KIYEOK YU NIEUN - 0xB1D6: 0xADE4, //HANGUL SYLLABLE KIYEOK YU RIEUL - 0xB1D7: 0xADF8, //HANGUL SYLLABLE KIYEOK EU - 0xB1D8: 0xADF9, //HANGUL SYLLABLE KIYEOK EU KIYEOK - 0xB1D9: 0xADFC, //HANGUL SYLLABLE KIYEOK EU NIEUN - 0xB1DA: 0xADFF, //HANGUL SYLLABLE KIYEOK EU TIKEUT - 0xB1DB: 0xAE00, //HANGUL SYLLABLE KIYEOK EU RIEUL - 0xB1DC: 0xAE01, //HANGUL SYLLABLE KIYEOK EU RIEULKIYEOK - 0xB1DD: 0xAE08, //HANGUL SYLLABLE KIYEOK EU MIEUM - 0xB1DE: 0xAE09, //HANGUL SYLLABLE KIYEOK EU PIEUP - 0xB1DF: 0xAE0B, //HANGUL SYLLABLE KIYEOK EU SIOS - 0xB1E0: 0xAE0D, //HANGUL SYLLABLE KIYEOK EU IEUNG - 0xB1E1: 0xAE14, //HANGUL SYLLABLE KIYEOK YI - 0xB1E2: 0xAE30, //HANGUL SYLLABLE KIYEOK I - 0xB1E3: 0xAE31, //HANGUL SYLLABLE KIYEOK I KIYEOK - 0xB1E4: 0xAE34, //HANGUL SYLLABLE KIYEOK I NIEUN - 0xB1E5: 0xAE37, //HANGUL SYLLABLE KIYEOK I TIKEUT - 0xB1E6: 0xAE38, //HANGUL SYLLABLE KIYEOK I RIEUL - 0xB1E7: 0xAE3A, //HANGUL SYLLABLE KIYEOK I RIEULMIEUM - 0xB1E8: 0xAE40, //HANGUL SYLLABLE KIYEOK I MIEUM - 0xB1E9: 0xAE41, //HANGUL SYLLABLE KIYEOK I PIEUP - 0xB1EA: 0xAE43, //HANGUL SYLLABLE KIYEOK I SIOS - 0xB1EB: 0xAE45, //HANGUL SYLLABLE KIYEOK I IEUNG - 0xB1EC: 0xAE46, //HANGUL SYLLABLE KIYEOK I CIEUC - 0xB1ED: 0xAE4A, //HANGUL SYLLABLE KIYEOK I PHIEUPH - 0xB1EE: 0xAE4C, //HANGUL SYLLABLE SSANGKIYEOK A - 0xB1EF: 0xAE4D, //HANGUL SYLLABLE SSANGKIYEOK A KIYEOK - 0xB1F0: 0xAE4E, //HANGUL SYLLABLE SSANGKIYEOK A SSANGKIYEOK - 0xB1F1: 0xAE50, //HANGUL SYLLABLE SSANGKIYEOK A NIEUN - 0xB1F2: 0xAE54, //HANGUL SYLLABLE SSANGKIYEOK A RIEUL - 0xB1F3: 0xAE56, //HANGUL SYLLABLE SSANGKIYEOK A RIEULMIEUM - 0xB1F4: 0xAE5C, //HANGUL SYLLABLE SSANGKIYEOK A MIEUM - 0xB1F5: 0xAE5D, //HANGUL SYLLABLE SSANGKIYEOK A PIEUP - 0xB1F6: 0xAE5F, //HANGUL SYLLABLE SSANGKIYEOK A SIOS - 0xB1F7: 0xAE60, //HANGUL SYLLABLE SSANGKIYEOK A SSANGSIOS - 0xB1F8: 0xAE61, //HANGUL SYLLABLE SSANGKIYEOK A IEUNG - 0xB1F9: 0xAE65, //HANGUL SYLLABLE SSANGKIYEOK A THIEUTH - 0xB1FA: 0xAE68, //HANGUL SYLLABLE SSANGKIYEOK AE - 0xB1FB: 0xAE69, //HANGUL SYLLABLE SSANGKIYEOK AE KIYEOK - 0xB1FC: 0xAE6C, //HANGUL SYLLABLE SSANGKIYEOK AE NIEUN - 0xB1FD: 0xAE70, //HANGUL SYLLABLE SSANGKIYEOK AE RIEUL - 0xB1FE: 0xAE78, //HANGUL SYLLABLE SSANGKIYEOK AE MIEUM - 0xB241: 0xCF6D, //HANGUL SYLLABLE KHIEUKH O THIEUTH - 0xB242: 0xCF6E, //HANGUL SYLLABLE KHIEUKH O PHIEUPH - 0xB243: 0xCF6F, //HANGUL SYLLABLE KHIEUKH O HIEUH - 0xB244: 0xCF72, //HANGUL SYLLABLE KHIEUKH WA SSANGKIYEOK - 0xB245: 0xCF73, //HANGUL SYLLABLE KHIEUKH WA KIYEOKSIOS - 0xB246: 0xCF75, //HANGUL SYLLABLE KHIEUKH WA NIEUNCIEUC - 0xB247: 0xCF76, //HANGUL SYLLABLE KHIEUKH WA NIEUNHIEUH - 0xB248: 0xCF77, //HANGUL SYLLABLE KHIEUKH WA TIKEUT - 0xB249: 0xCF79, //HANGUL SYLLABLE KHIEUKH WA RIEULKIYEOK - 0xB24A: 0xCF7A, //HANGUL SYLLABLE KHIEUKH WA RIEULMIEUM - 0xB24B: 0xCF7B, //HANGUL SYLLABLE KHIEUKH WA RIEULPIEUP - 0xB24C: 0xCF7C, //HANGUL SYLLABLE KHIEUKH WA RIEULSIOS - 0xB24D: 0xCF7D, //HANGUL SYLLABLE KHIEUKH WA RIEULTHIEUTH - 0xB24E: 0xCF7E, //HANGUL SYLLABLE KHIEUKH WA RIEULPHIEUPH - 0xB24F: 0xCF7F, //HANGUL SYLLABLE KHIEUKH WA RIEULHIEUH - 0xB250: 0xCF81, //HANGUL SYLLABLE KHIEUKH WA PIEUP - 0xB251: 0xCF82, //HANGUL SYLLABLE KHIEUKH WA PIEUPSIOS - 0xB252: 0xCF83, //HANGUL SYLLABLE KHIEUKH WA SIOS - 0xB253: 0xCF84, //HANGUL SYLLABLE KHIEUKH WA SSANGSIOS - 0xB254: 0xCF86, //HANGUL SYLLABLE KHIEUKH WA CIEUC - 0xB255: 0xCF87, //HANGUL SYLLABLE KHIEUKH WA CHIEUCH - 0xB256: 0xCF88, //HANGUL SYLLABLE KHIEUKH WA KHIEUKH - 0xB257: 0xCF89, //HANGUL SYLLABLE KHIEUKH WA THIEUTH - 0xB258: 0xCF8A, //HANGUL SYLLABLE KHIEUKH WA PHIEUPH - 0xB259: 0xCF8B, //HANGUL SYLLABLE KHIEUKH WA HIEUH - 0xB25A: 0xCF8D, //HANGUL SYLLABLE KHIEUKH WAE KIYEOK - 0xB261: 0xCF8E, //HANGUL SYLLABLE KHIEUKH WAE SSANGKIYEOK - 0xB262: 0xCF8F, //HANGUL SYLLABLE KHIEUKH WAE KIYEOKSIOS - 0xB263: 0xCF90, //HANGUL SYLLABLE KHIEUKH WAE NIEUN - 0xB264: 0xCF91, //HANGUL SYLLABLE KHIEUKH WAE NIEUNCIEUC - 0xB265: 0xCF92, //HANGUL SYLLABLE KHIEUKH WAE NIEUNHIEUH - 0xB266: 0xCF93, //HANGUL SYLLABLE KHIEUKH WAE TIKEUT - 0xB267: 0xCF94, //HANGUL SYLLABLE KHIEUKH WAE RIEUL - 0xB268: 0xCF95, //HANGUL SYLLABLE KHIEUKH WAE RIEULKIYEOK - 0xB269: 0xCF96, //HANGUL SYLLABLE KHIEUKH WAE RIEULMIEUM - 0xB26A: 0xCF97, //HANGUL SYLLABLE KHIEUKH WAE RIEULPIEUP - 0xB26B: 0xCF98, //HANGUL SYLLABLE KHIEUKH WAE RIEULSIOS - 0xB26C: 0xCF99, //HANGUL SYLLABLE KHIEUKH WAE RIEULTHIEUTH - 0xB26D: 0xCF9A, //HANGUL SYLLABLE KHIEUKH WAE RIEULPHIEUPH - 0xB26E: 0xCF9B, //HANGUL SYLLABLE KHIEUKH WAE RIEULHIEUH - 0xB26F: 0xCF9C, //HANGUL SYLLABLE KHIEUKH WAE MIEUM - 0xB270: 0xCF9D, //HANGUL SYLLABLE KHIEUKH WAE PIEUP - 0xB271: 0xCF9E, //HANGUL SYLLABLE KHIEUKH WAE PIEUPSIOS - 0xB272: 0xCF9F, //HANGUL SYLLABLE KHIEUKH WAE SIOS - 0xB273: 0xCFA0, //HANGUL SYLLABLE KHIEUKH WAE SSANGSIOS - 0xB274: 0xCFA2, //HANGUL SYLLABLE KHIEUKH WAE CIEUC - 0xB275: 0xCFA3, //HANGUL SYLLABLE KHIEUKH WAE CHIEUCH - 0xB276: 0xCFA4, //HANGUL SYLLABLE KHIEUKH WAE KHIEUKH - 0xB277: 0xCFA5, //HANGUL SYLLABLE KHIEUKH WAE THIEUTH - 0xB278: 0xCFA6, //HANGUL SYLLABLE KHIEUKH WAE PHIEUPH - 0xB279: 0xCFA7, //HANGUL SYLLABLE KHIEUKH WAE HIEUH - 0xB27A: 0xCFA9, //HANGUL SYLLABLE KHIEUKH OE KIYEOK - 0xB281: 0xCFAA, //HANGUL SYLLABLE KHIEUKH OE SSANGKIYEOK - 0xB282: 0xCFAB, //HANGUL SYLLABLE KHIEUKH OE KIYEOKSIOS - 0xB283: 0xCFAC, //HANGUL SYLLABLE KHIEUKH OE NIEUN - 0xB284: 0xCFAD, //HANGUL SYLLABLE KHIEUKH OE NIEUNCIEUC - 0xB285: 0xCFAE, //HANGUL SYLLABLE KHIEUKH OE NIEUNHIEUH - 0xB286: 0xCFAF, //HANGUL SYLLABLE KHIEUKH OE TIKEUT - 0xB287: 0xCFB1, //HANGUL SYLLABLE KHIEUKH OE RIEULKIYEOK - 0xB288: 0xCFB2, //HANGUL SYLLABLE KHIEUKH OE RIEULMIEUM - 0xB289: 0xCFB3, //HANGUL SYLLABLE KHIEUKH OE RIEULPIEUP - 0xB28A: 0xCFB4, //HANGUL SYLLABLE KHIEUKH OE RIEULSIOS - 0xB28B: 0xCFB5, //HANGUL SYLLABLE KHIEUKH OE RIEULTHIEUTH - 0xB28C: 0xCFB6, //HANGUL SYLLABLE KHIEUKH OE RIEULPHIEUPH - 0xB28D: 0xCFB7, //HANGUL SYLLABLE KHIEUKH OE RIEULHIEUH - 0xB28E: 0xCFB8, //HANGUL SYLLABLE KHIEUKH OE MIEUM - 0xB28F: 0xCFB9, //HANGUL SYLLABLE KHIEUKH OE PIEUP - 0xB290: 0xCFBA, //HANGUL SYLLABLE KHIEUKH OE PIEUPSIOS - 0xB291: 0xCFBB, //HANGUL SYLLABLE KHIEUKH OE SIOS - 0xB292: 0xCFBC, //HANGUL SYLLABLE KHIEUKH OE SSANGSIOS - 0xB293: 0xCFBD, //HANGUL SYLLABLE KHIEUKH OE IEUNG - 0xB294: 0xCFBE, //HANGUL SYLLABLE KHIEUKH OE CIEUC - 0xB295: 0xCFBF, //HANGUL SYLLABLE KHIEUKH OE CHIEUCH - 0xB296: 0xCFC0, //HANGUL SYLLABLE KHIEUKH OE KHIEUKH - 0xB297: 0xCFC1, //HANGUL SYLLABLE KHIEUKH OE THIEUTH - 0xB298: 0xCFC2, //HANGUL SYLLABLE KHIEUKH OE PHIEUPH - 0xB299: 0xCFC3, //HANGUL SYLLABLE KHIEUKH OE HIEUH - 0xB29A: 0xCFC5, //HANGUL SYLLABLE KHIEUKH YO KIYEOK - 0xB29B: 0xCFC6, //HANGUL SYLLABLE KHIEUKH YO SSANGKIYEOK - 0xB29C: 0xCFC7, //HANGUL SYLLABLE KHIEUKH YO KIYEOKSIOS - 0xB29D: 0xCFC8, //HANGUL SYLLABLE KHIEUKH YO NIEUN - 0xB29E: 0xCFC9, //HANGUL SYLLABLE KHIEUKH YO NIEUNCIEUC - 0xB29F: 0xCFCA, //HANGUL SYLLABLE KHIEUKH YO NIEUNHIEUH - 0xB2A0: 0xCFCB, //HANGUL SYLLABLE KHIEUKH YO TIKEUT - 0xB2A1: 0xAE79, //HANGUL SYLLABLE SSANGKIYEOK AE PIEUP - 0xB2A2: 0xAE7B, //HANGUL SYLLABLE SSANGKIYEOK AE SIOS - 0xB2A3: 0xAE7C, //HANGUL SYLLABLE SSANGKIYEOK AE SSANGSIOS - 0xB2A4: 0xAE7D, //HANGUL SYLLABLE SSANGKIYEOK AE IEUNG - 0xB2A5: 0xAE84, //HANGUL SYLLABLE SSANGKIYEOK YA - 0xB2A6: 0xAE85, //HANGUL SYLLABLE SSANGKIYEOK YA KIYEOK - 0xB2A7: 0xAE8C, //HANGUL SYLLABLE SSANGKIYEOK YA RIEUL - 0xB2A8: 0xAEBC, //HANGUL SYLLABLE SSANGKIYEOK EO - 0xB2A9: 0xAEBD, //HANGUL SYLLABLE SSANGKIYEOK EO KIYEOK - 0xB2AA: 0xAEBE, //HANGUL SYLLABLE SSANGKIYEOK EO SSANGKIYEOK - 0xB2AB: 0xAEC0, //HANGUL SYLLABLE SSANGKIYEOK EO NIEUN - 0xB2AC: 0xAEC4, //HANGUL SYLLABLE SSANGKIYEOK EO RIEUL - 0xB2AD: 0xAECC, //HANGUL SYLLABLE SSANGKIYEOK EO MIEUM - 0xB2AE: 0xAECD, //HANGUL SYLLABLE SSANGKIYEOK EO PIEUP - 0xB2AF: 0xAECF, //HANGUL SYLLABLE SSANGKIYEOK EO SIOS - 0xB2B0: 0xAED0, //HANGUL SYLLABLE SSANGKIYEOK EO SSANGSIOS - 0xB2B1: 0xAED1, //HANGUL SYLLABLE SSANGKIYEOK EO IEUNG - 0xB2B2: 0xAED8, //HANGUL SYLLABLE SSANGKIYEOK E - 0xB2B3: 0xAED9, //HANGUL SYLLABLE SSANGKIYEOK E KIYEOK - 0xB2B4: 0xAEDC, //HANGUL SYLLABLE SSANGKIYEOK E NIEUN - 0xB2B5: 0xAEE8, //HANGUL SYLLABLE SSANGKIYEOK E MIEUM - 0xB2B6: 0xAEEB, //HANGUL SYLLABLE SSANGKIYEOK E SIOS - 0xB2B7: 0xAEED, //HANGUL SYLLABLE SSANGKIYEOK E IEUNG - 0xB2B8: 0xAEF4, //HANGUL SYLLABLE SSANGKIYEOK YEO - 0xB2B9: 0xAEF8, //HANGUL SYLLABLE SSANGKIYEOK YEO NIEUN - 0xB2BA: 0xAEFC, //HANGUL SYLLABLE SSANGKIYEOK YEO RIEUL - 0xB2BB: 0xAF07, //HANGUL SYLLABLE SSANGKIYEOK YEO SIOS - 0xB2BC: 0xAF08, //HANGUL SYLLABLE SSANGKIYEOK YEO SSANGSIOS - 0xB2BD: 0xAF0D, //HANGUL SYLLABLE SSANGKIYEOK YEO THIEUTH - 0xB2BE: 0xAF10, //HANGUL SYLLABLE SSANGKIYEOK YE - 0xB2BF: 0xAF2C, //HANGUL SYLLABLE SSANGKIYEOK O - 0xB2C0: 0xAF2D, //HANGUL SYLLABLE SSANGKIYEOK O KIYEOK - 0xB2C1: 0xAF30, //HANGUL SYLLABLE SSANGKIYEOK O NIEUN - 0xB2C2: 0xAF32, //HANGUL SYLLABLE SSANGKIYEOK O NIEUNHIEUH - 0xB2C3: 0xAF34, //HANGUL SYLLABLE SSANGKIYEOK O RIEUL - 0xB2C4: 0xAF3C, //HANGUL SYLLABLE SSANGKIYEOK O MIEUM - 0xB2C5: 0xAF3D, //HANGUL SYLLABLE SSANGKIYEOK O PIEUP - 0xB2C6: 0xAF3F, //HANGUL SYLLABLE SSANGKIYEOK O SIOS - 0xB2C7: 0xAF41, //HANGUL SYLLABLE SSANGKIYEOK O IEUNG - 0xB2C8: 0xAF42, //HANGUL SYLLABLE SSANGKIYEOK O CIEUC - 0xB2C9: 0xAF43, //HANGUL SYLLABLE SSANGKIYEOK O CHIEUCH - 0xB2CA: 0xAF48, //HANGUL SYLLABLE SSANGKIYEOK WA - 0xB2CB: 0xAF49, //HANGUL SYLLABLE SSANGKIYEOK WA KIYEOK - 0xB2CC: 0xAF50, //HANGUL SYLLABLE SSANGKIYEOK WA RIEUL - 0xB2CD: 0xAF5C, //HANGUL SYLLABLE SSANGKIYEOK WA SSANGSIOS - 0xB2CE: 0xAF5D, //HANGUL SYLLABLE SSANGKIYEOK WA IEUNG - 0xB2CF: 0xAF64, //HANGUL SYLLABLE SSANGKIYEOK WAE - 0xB2D0: 0xAF65, //HANGUL SYLLABLE SSANGKIYEOK WAE KIYEOK - 0xB2D1: 0xAF79, //HANGUL SYLLABLE SSANGKIYEOK WAE IEUNG - 0xB2D2: 0xAF80, //HANGUL SYLLABLE SSANGKIYEOK OE - 0xB2D3: 0xAF84, //HANGUL SYLLABLE SSANGKIYEOK OE NIEUN - 0xB2D4: 0xAF88, //HANGUL SYLLABLE SSANGKIYEOK OE RIEUL - 0xB2D5: 0xAF90, //HANGUL SYLLABLE SSANGKIYEOK OE MIEUM - 0xB2D6: 0xAF91, //HANGUL SYLLABLE SSANGKIYEOK OE PIEUP - 0xB2D7: 0xAF95, //HANGUL SYLLABLE SSANGKIYEOK OE IEUNG - 0xB2D8: 0xAF9C, //HANGUL SYLLABLE SSANGKIYEOK YO - 0xB2D9: 0xAFB8, //HANGUL SYLLABLE SSANGKIYEOK U - 0xB2DA: 0xAFB9, //HANGUL SYLLABLE SSANGKIYEOK U KIYEOK - 0xB2DB: 0xAFBC, //HANGUL SYLLABLE SSANGKIYEOK U NIEUN - 0xB2DC: 0xAFC0, //HANGUL SYLLABLE SSANGKIYEOK U RIEUL - 0xB2DD: 0xAFC7, //HANGUL SYLLABLE SSANGKIYEOK U RIEULHIEUH - 0xB2DE: 0xAFC8, //HANGUL SYLLABLE SSANGKIYEOK U MIEUM - 0xB2DF: 0xAFC9, //HANGUL SYLLABLE SSANGKIYEOK U PIEUP - 0xB2E0: 0xAFCB, //HANGUL SYLLABLE SSANGKIYEOK U SIOS - 0xB2E1: 0xAFCD, //HANGUL SYLLABLE SSANGKIYEOK U IEUNG - 0xB2E2: 0xAFCE, //HANGUL SYLLABLE SSANGKIYEOK U CIEUC - 0xB2E3: 0xAFD4, //HANGUL SYLLABLE SSANGKIYEOK WEO - 0xB2E4: 0xAFDC, //HANGUL SYLLABLE SSANGKIYEOK WEO RIEUL - 0xB2E5: 0xAFE8, //HANGUL SYLLABLE SSANGKIYEOK WEO SSANGSIOS - 0xB2E6: 0xAFE9, //HANGUL SYLLABLE SSANGKIYEOK WEO IEUNG - 0xB2E7: 0xAFF0, //HANGUL SYLLABLE SSANGKIYEOK WE - 0xB2E8: 0xAFF1, //HANGUL SYLLABLE SSANGKIYEOK WE KIYEOK - 0xB2E9: 0xAFF4, //HANGUL SYLLABLE SSANGKIYEOK WE NIEUN - 0xB2EA: 0xAFF8, //HANGUL SYLLABLE SSANGKIYEOK WE RIEUL - 0xB2EB: 0xB000, //HANGUL SYLLABLE SSANGKIYEOK WE MIEUM - 0xB2EC: 0xB001, //HANGUL SYLLABLE SSANGKIYEOK WE PIEUP - 0xB2ED: 0xB004, //HANGUL SYLLABLE SSANGKIYEOK WE SSANGSIOS - 0xB2EE: 0xB00C, //HANGUL SYLLABLE SSANGKIYEOK WI - 0xB2EF: 0xB010, //HANGUL SYLLABLE SSANGKIYEOK WI NIEUN - 0xB2F0: 0xB014, //HANGUL SYLLABLE SSANGKIYEOK WI RIEUL - 0xB2F1: 0xB01C, //HANGUL SYLLABLE SSANGKIYEOK WI MIEUM - 0xB2F2: 0xB01D, //HANGUL SYLLABLE SSANGKIYEOK WI PIEUP - 0xB2F3: 0xB028, //HANGUL SYLLABLE SSANGKIYEOK YU - 0xB2F4: 0xB044, //HANGUL SYLLABLE SSANGKIYEOK EU - 0xB2F5: 0xB045, //HANGUL SYLLABLE SSANGKIYEOK EU KIYEOK - 0xB2F6: 0xB048, //HANGUL SYLLABLE SSANGKIYEOK EU NIEUN - 0xB2F7: 0xB04A, //HANGUL SYLLABLE SSANGKIYEOK EU NIEUNHIEUH - 0xB2F8: 0xB04C, //HANGUL SYLLABLE SSANGKIYEOK EU RIEUL - 0xB2F9: 0xB04E, //HANGUL SYLLABLE SSANGKIYEOK EU RIEULMIEUM - 0xB2FA: 0xB053, //HANGUL SYLLABLE SSANGKIYEOK EU RIEULHIEUH - 0xB2FB: 0xB054, //HANGUL SYLLABLE SSANGKIYEOK EU MIEUM - 0xB2FC: 0xB055, //HANGUL SYLLABLE SSANGKIYEOK EU PIEUP - 0xB2FD: 0xB057, //HANGUL SYLLABLE SSANGKIYEOK EU SIOS - 0xB2FE: 0xB059, //HANGUL SYLLABLE SSANGKIYEOK EU IEUNG - 0xB341: 0xCFCC, //HANGUL SYLLABLE KHIEUKH YO RIEUL - 0xB342: 0xCFCD, //HANGUL SYLLABLE KHIEUKH YO RIEULKIYEOK - 0xB343: 0xCFCE, //HANGUL SYLLABLE KHIEUKH YO RIEULMIEUM - 0xB344: 0xCFCF, //HANGUL SYLLABLE KHIEUKH YO RIEULPIEUP - 0xB345: 0xCFD0, //HANGUL SYLLABLE KHIEUKH YO RIEULSIOS - 0xB346: 0xCFD1, //HANGUL SYLLABLE KHIEUKH YO RIEULTHIEUTH - 0xB347: 0xCFD2, //HANGUL SYLLABLE KHIEUKH YO RIEULPHIEUPH - 0xB348: 0xCFD3, //HANGUL SYLLABLE KHIEUKH YO RIEULHIEUH - 0xB349: 0xCFD4, //HANGUL SYLLABLE KHIEUKH YO MIEUM - 0xB34A: 0xCFD5, //HANGUL SYLLABLE KHIEUKH YO PIEUP - 0xB34B: 0xCFD6, //HANGUL SYLLABLE KHIEUKH YO PIEUPSIOS - 0xB34C: 0xCFD7, //HANGUL SYLLABLE KHIEUKH YO SIOS - 0xB34D: 0xCFD8, //HANGUL SYLLABLE KHIEUKH YO SSANGSIOS - 0xB34E: 0xCFD9, //HANGUL SYLLABLE KHIEUKH YO IEUNG - 0xB34F: 0xCFDA, //HANGUL SYLLABLE KHIEUKH YO CIEUC - 0xB350: 0xCFDB, //HANGUL SYLLABLE KHIEUKH YO CHIEUCH - 0xB351: 0xCFDC, //HANGUL SYLLABLE KHIEUKH YO KHIEUKH - 0xB352: 0xCFDD, //HANGUL SYLLABLE KHIEUKH YO THIEUTH - 0xB353: 0xCFDE, //HANGUL SYLLABLE KHIEUKH YO PHIEUPH - 0xB354: 0xCFDF, //HANGUL SYLLABLE KHIEUKH YO HIEUH - 0xB355: 0xCFE2, //HANGUL SYLLABLE KHIEUKH U SSANGKIYEOK - 0xB356: 0xCFE3, //HANGUL SYLLABLE KHIEUKH U KIYEOKSIOS - 0xB357: 0xCFE5, //HANGUL SYLLABLE KHIEUKH U NIEUNCIEUC - 0xB358: 0xCFE6, //HANGUL SYLLABLE KHIEUKH U NIEUNHIEUH - 0xB359: 0xCFE7, //HANGUL SYLLABLE KHIEUKH U TIKEUT - 0xB35A: 0xCFE9, //HANGUL SYLLABLE KHIEUKH U RIEULKIYEOK - 0xB361: 0xCFEA, //HANGUL SYLLABLE KHIEUKH U RIEULMIEUM - 0xB362: 0xCFEB, //HANGUL SYLLABLE KHIEUKH U RIEULPIEUP - 0xB363: 0xCFEC, //HANGUL SYLLABLE KHIEUKH U RIEULSIOS - 0xB364: 0xCFED, //HANGUL SYLLABLE KHIEUKH U RIEULTHIEUTH - 0xB365: 0xCFEE, //HANGUL SYLLABLE KHIEUKH U RIEULPHIEUPH - 0xB366: 0xCFEF, //HANGUL SYLLABLE KHIEUKH U RIEULHIEUH - 0xB367: 0xCFF2, //HANGUL SYLLABLE KHIEUKH U PIEUPSIOS - 0xB368: 0xCFF4, //HANGUL SYLLABLE KHIEUKH U SSANGSIOS - 0xB369: 0xCFF6, //HANGUL SYLLABLE KHIEUKH U CIEUC - 0xB36A: 0xCFF7, //HANGUL SYLLABLE KHIEUKH U CHIEUCH - 0xB36B: 0xCFF8, //HANGUL SYLLABLE KHIEUKH U KHIEUKH - 0xB36C: 0xCFF9, //HANGUL SYLLABLE KHIEUKH U THIEUTH - 0xB36D: 0xCFFA, //HANGUL SYLLABLE KHIEUKH U PHIEUPH - 0xB36E: 0xCFFB, //HANGUL SYLLABLE KHIEUKH U HIEUH - 0xB36F: 0xCFFD, //HANGUL SYLLABLE KHIEUKH WEO KIYEOK - 0xB370: 0xCFFE, //HANGUL SYLLABLE KHIEUKH WEO SSANGKIYEOK - 0xB371: 0xCFFF, //HANGUL SYLLABLE KHIEUKH WEO KIYEOKSIOS - 0xB372: 0xD001, //HANGUL SYLLABLE KHIEUKH WEO NIEUNCIEUC - 0xB373: 0xD002, //HANGUL SYLLABLE KHIEUKH WEO NIEUNHIEUH - 0xB374: 0xD003, //HANGUL SYLLABLE KHIEUKH WEO TIKEUT - 0xB375: 0xD005, //HANGUL SYLLABLE KHIEUKH WEO RIEULKIYEOK - 0xB376: 0xD006, //HANGUL SYLLABLE KHIEUKH WEO RIEULMIEUM - 0xB377: 0xD007, //HANGUL SYLLABLE KHIEUKH WEO RIEULPIEUP - 0xB378: 0xD008, //HANGUL SYLLABLE KHIEUKH WEO RIEULSIOS - 0xB379: 0xD009, //HANGUL SYLLABLE KHIEUKH WEO RIEULTHIEUTH - 0xB37A: 0xD00A, //HANGUL SYLLABLE KHIEUKH WEO RIEULPHIEUPH - 0xB381: 0xD00B, //HANGUL SYLLABLE KHIEUKH WEO RIEULHIEUH - 0xB382: 0xD00C, //HANGUL SYLLABLE KHIEUKH WEO MIEUM - 0xB383: 0xD00D, //HANGUL SYLLABLE KHIEUKH WEO PIEUP - 0xB384: 0xD00E, //HANGUL SYLLABLE KHIEUKH WEO PIEUPSIOS - 0xB385: 0xD00F, //HANGUL SYLLABLE KHIEUKH WEO SIOS - 0xB386: 0xD010, //HANGUL SYLLABLE KHIEUKH WEO SSANGSIOS - 0xB387: 0xD012, //HANGUL SYLLABLE KHIEUKH WEO CIEUC - 0xB388: 0xD013, //HANGUL SYLLABLE KHIEUKH WEO CHIEUCH - 0xB389: 0xD014, //HANGUL SYLLABLE KHIEUKH WEO KHIEUKH - 0xB38A: 0xD015, //HANGUL SYLLABLE KHIEUKH WEO THIEUTH - 0xB38B: 0xD016, //HANGUL SYLLABLE KHIEUKH WEO PHIEUPH - 0xB38C: 0xD017, //HANGUL SYLLABLE KHIEUKH WEO HIEUH - 0xB38D: 0xD019, //HANGUL SYLLABLE KHIEUKH WE KIYEOK - 0xB38E: 0xD01A, //HANGUL SYLLABLE KHIEUKH WE SSANGKIYEOK - 0xB38F: 0xD01B, //HANGUL SYLLABLE KHIEUKH WE KIYEOKSIOS - 0xB390: 0xD01C, //HANGUL SYLLABLE KHIEUKH WE NIEUN - 0xB391: 0xD01D, //HANGUL SYLLABLE KHIEUKH WE NIEUNCIEUC - 0xB392: 0xD01E, //HANGUL SYLLABLE KHIEUKH WE NIEUNHIEUH - 0xB393: 0xD01F, //HANGUL SYLLABLE KHIEUKH WE TIKEUT - 0xB394: 0xD020, //HANGUL SYLLABLE KHIEUKH WE RIEUL - 0xB395: 0xD021, //HANGUL SYLLABLE KHIEUKH WE RIEULKIYEOK - 0xB396: 0xD022, //HANGUL SYLLABLE KHIEUKH WE RIEULMIEUM - 0xB397: 0xD023, //HANGUL SYLLABLE KHIEUKH WE RIEULPIEUP - 0xB398: 0xD024, //HANGUL SYLLABLE KHIEUKH WE RIEULSIOS - 0xB399: 0xD025, //HANGUL SYLLABLE KHIEUKH WE RIEULTHIEUTH - 0xB39A: 0xD026, //HANGUL SYLLABLE KHIEUKH WE RIEULPHIEUPH - 0xB39B: 0xD027, //HANGUL SYLLABLE KHIEUKH WE RIEULHIEUH - 0xB39C: 0xD028, //HANGUL SYLLABLE KHIEUKH WE MIEUM - 0xB39D: 0xD029, //HANGUL SYLLABLE KHIEUKH WE PIEUP - 0xB39E: 0xD02A, //HANGUL SYLLABLE KHIEUKH WE PIEUPSIOS - 0xB39F: 0xD02B, //HANGUL SYLLABLE KHIEUKH WE SIOS - 0xB3A0: 0xD02C, //HANGUL SYLLABLE KHIEUKH WE SSANGSIOS - 0xB3A1: 0xB05D, //HANGUL SYLLABLE SSANGKIYEOK EU THIEUTH - 0xB3A2: 0xB07C, //HANGUL SYLLABLE SSANGKIYEOK I - 0xB3A3: 0xB07D, //HANGUL SYLLABLE SSANGKIYEOK I KIYEOK - 0xB3A4: 0xB080, //HANGUL SYLLABLE SSANGKIYEOK I NIEUN - 0xB3A5: 0xB084, //HANGUL SYLLABLE SSANGKIYEOK I RIEUL - 0xB3A6: 0xB08C, //HANGUL SYLLABLE SSANGKIYEOK I MIEUM - 0xB3A7: 0xB08D, //HANGUL SYLLABLE SSANGKIYEOK I PIEUP - 0xB3A8: 0xB08F, //HANGUL SYLLABLE SSANGKIYEOK I SIOS - 0xB3A9: 0xB091, //HANGUL SYLLABLE SSANGKIYEOK I IEUNG - 0xB3AA: 0xB098, //HANGUL SYLLABLE NIEUN A - 0xB3AB: 0xB099, //HANGUL SYLLABLE NIEUN A KIYEOK - 0xB3AC: 0xB09A, //HANGUL SYLLABLE NIEUN A SSANGKIYEOK - 0xB3AD: 0xB09C, //HANGUL SYLLABLE NIEUN A NIEUN - 0xB3AE: 0xB09F, //HANGUL SYLLABLE NIEUN A TIKEUT - 0xB3AF: 0xB0A0, //HANGUL SYLLABLE NIEUN A RIEUL - 0xB3B0: 0xB0A1, //HANGUL SYLLABLE NIEUN A RIEULKIYEOK - 0xB3B1: 0xB0A2, //HANGUL SYLLABLE NIEUN A RIEULMIEUM - 0xB3B2: 0xB0A8, //HANGUL SYLLABLE NIEUN A MIEUM - 0xB3B3: 0xB0A9, //HANGUL SYLLABLE NIEUN A PIEUP - 0xB3B4: 0xB0AB, //HANGUL SYLLABLE NIEUN A SIOS - 0xB3B5: 0xB0AC, //HANGUL SYLLABLE NIEUN A SSANGSIOS - 0xB3B6: 0xB0AD, //HANGUL SYLLABLE NIEUN A IEUNG - 0xB3B7: 0xB0AE, //HANGUL SYLLABLE NIEUN A CIEUC - 0xB3B8: 0xB0AF, //HANGUL SYLLABLE NIEUN A CHIEUCH - 0xB3B9: 0xB0B1, //HANGUL SYLLABLE NIEUN A THIEUTH - 0xB3BA: 0xB0B3, //HANGUL SYLLABLE NIEUN A HIEUH - 0xB3BB: 0xB0B4, //HANGUL SYLLABLE NIEUN AE - 0xB3BC: 0xB0B5, //HANGUL SYLLABLE NIEUN AE KIYEOK - 0xB3BD: 0xB0B8, //HANGUL SYLLABLE NIEUN AE NIEUN - 0xB3BE: 0xB0BC, //HANGUL SYLLABLE NIEUN AE RIEUL - 0xB3BF: 0xB0C4, //HANGUL SYLLABLE NIEUN AE MIEUM - 0xB3C0: 0xB0C5, //HANGUL SYLLABLE NIEUN AE PIEUP - 0xB3C1: 0xB0C7, //HANGUL SYLLABLE NIEUN AE SIOS - 0xB3C2: 0xB0C8, //HANGUL SYLLABLE NIEUN AE SSANGSIOS - 0xB3C3: 0xB0C9, //HANGUL SYLLABLE NIEUN AE IEUNG - 0xB3C4: 0xB0D0, //HANGUL SYLLABLE NIEUN YA - 0xB3C5: 0xB0D1, //HANGUL SYLLABLE NIEUN YA KIYEOK - 0xB3C6: 0xB0D4, //HANGUL SYLLABLE NIEUN YA NIEUN - 0xB3C7: 0xB0D8, //HANGUL SYLLABLE NIEUN YA RIEUL - 0xB3C8: 0xB0E0, //HANGUL SYLLABLE NIEUN YA MIEUM - 0xB3C9: 0xB0E5, //HANGUL SYLLABLE NIEUN YA IEUNG - 0xB3CA: 0xB108, //HANGUL SYLLABLE NIEUN EO - 0xB3CB: 0xB109, //HANGUL SYLLABLE NIEUN EO KIYEOK - 0xB3CC: 0xB10B, //HANGUL SYLLABLE NIEUN EO KIYEOKSIOS - 0xB3CD: 0xB10C, //HANGUL SYLLABLE NIEUN EO NIEUN - 0xB3CE: 0xB110, //HANGUL SYLLABLE NIEUN EO RIEUL - 0xB3CF: 0xB112, //HANGUL SYLLABLE NIEUN EO RIEULMIEUM - 0xB3D0: 0xB113, //HANGUL SYLLABLE NIEUN EO RIEULPIEUP - 0xB3D1: 0xB118, //HANGUL SYLLABLE NIEUN EO MIEUM - 0xB3D2: 0xB119, //HANGUL SYLLABLE NIEUN EO PIEUP - 0xB3D3: 0xB11B, //HANGUL SYLLABLE NIEUN EO SIOS - 0xB3D4: 0xB11C, //HANGUL SYLLABLE NIEUN EO SSANGSIOS - 0xB3D5: 0xB11D, //HANGUL SYLLABLE NIEUN EO IEUNG - 0xB3D6: 0xB123, //HANGUL SYLLABLE NIEUN EO HIEUH - 0xB3D7: 0xB124, //HANGUL SYLLABLE NIEUN E - 0xB3D8: 0xB125, //HANGUL SYLLABLE NIEUN E KIYEOK - 0xB3D9: 0xB128, //HANGUL SYLLABLE NIEUN E NIEUN - 0xB3DA: 0xB12C, //HANGUL SYLLABLE NIEUN E RIEUL - 0xB3DB: 0xB134, //HANGUL SYLLABLE NIEUN E MIEUM - 0xB3DC: 0xB135, //HANGUL SYLLABLE NIEUN E PIEUP - 0xB3DD: 0xB137, //HANGUL SYLLABLE NIEUN E SIOS - 0xB3DE: 0xB138, //HANGUL SYLLABLE NIEUN E SSANGSIOS - 0xB3DF: 0xB139, //HANGUL SYLLABLE NIEUN E IEUNG - 0xB3E0: 0xB140, //HANGUL SYLLABLE NIEUN YEO - 0xB3E1: 0xB141, //HANGUL SYLLABLE NIEUN YEO KIYEOK - 0xB3E2: 0xB144, //HANGUL SYLLABLE NIEUN YEO NIEUN - 0xB3E3: 0xB148, //HANGUL SYLLABLE NIEUN YEO RIEUL - 0xB3E4: 0xB150, //HANGUL SYLLABLE NIEUN YEO MIEUM - 0xB3E5: 0xB151, //HANGUL SYLLABLE NIEUN YEO PIEUP - 0xB3E6: 0xB154, //HANGUL SYLLABLE NIEUN YEO SSANGSIOS - 0xB3E7: 0xB155, //HANGUL SYLLABLE NIEUN YEO IEUNG - 0xB3E8: 0xB158, //HANGUL SYLLABLE NIEUN YEO KHIEUKH - 0xB3E9: 0xB15C, //HANGUL SYLLABLE NIEUN YE - 0xB3EA: 0xB160, //HANGUL SYLLABLE NIEUN YE NIEUN - 0xB3EB: 0xB178, //HANGUL SYLLABLE NIEUN O - 0xB3EC: 0xB179, //HANGUL SYLLABLE NIEUN O KIYEOK - 0xB3ED: 0xB17C, //HANGUL SYLLABLE NIEUN O NIEUN - 0xB3EE: 0xB180, //HANGUL SYLLABLE NIEUN O RIEUL - 0xB3EF: 0xB182, //HANGUL SYLLABLE NIEUN O RIEULMIEUM - 0xB3F0: 0xB188, //HANGUL SYLLABLE NIEUN O MIEUM - 0xB3F1: 0xB189, //HANGUL SYLLABLE NIEUN O PIEUP - 0xB3F2: 0xB18B, //HANGUL SYLLABLE NIEUN O SIOS - 0xB3F3: 0xB18D, //HANGUL SYLLABLE NIEUN O IEUNG - 0xB3F4: 0xB192, //HANGUL SYLLABLE NIEUN O PHIEUPH - 0xB3F5: 0xB193, //HANGUL SYLLABLE NIEUN O HIEUH - 0xB3F6: 0xB194, //HANGUL SYLLABLE NIEUN WA - 0xB3F7: 0xB198, //HANGUL SYLLABLE NIEUN WA NIEUN - 0xB3F8: 0xB19C, //HANGUL SYLLABLE NIEUN WA RIEUL - 0xB3F9: 0xB1A8, //HANGUL SYLLABLE NIEUN WA SSANGSIOS - 0xB3FA: 0xB1CC, //HANGUL SYLLABLE NIEUN OE - 0xB3FB: 0xB1D0, //HANGUL SYLLABLE NIEUN OE NIEUN - 0xB3FC: 0xB1D4, //HANGUL SYLLABLE NIEUN OE RIEUL - 0xB3FD: 0xB1DC, //HANGUL SYLLABLE NIEUN OE MIEUM - 0xB3FE: 0xB1DD, //HANGUL SYLLABLE NIEUN OE PIEUP - 0xB441: 0xD02E, //HANGUL SYLLABLE KHIEUKH WE CIEUC - 0xB442: 0xD02F, //HANGUL SYLLABLE KHIEUKH WE CHIEUCH - 0xB443: 0xD030, //HANGUL SYLLABLE KHIEUKH WE KHIEUKH - 0xB444: 0xD031, //HANGUL SYLLABLE KHIEUKH WE THIEUTH - 0xB445: 0xD032, //HANGUL SYLLABLE KHIEUKH WE PHIEUPH - 0xB446: 0xD033, //HANGUL SYLLABLE KHIEUKH WE HIEUH - 0xB447: 0xD036, //HANGUL SYLLABLE KHIEUKH WI SSANGKIYEOK - 0xB448: 0xD037, //HANGUL SYLLABLE KHIEUKH WI KIYEOKSIOS - 0xB449: 0xD039, //HANGUL SYLLABLE KHIEUKH WI NIEUNCIEUC - 0xB44A: 0xD03A, //HANGUL SYLLABLE KHIEUKH WI NIEUNHIEUH - 0xB44B: 0xD03B, //HANGUL SYLLABLE KHIEUKH WI TIKEUT - 0xB44C: 0xD03D, //HANGUL SYLLABLE KHIEUKH WI RIEULKIYEOK - 0xB44D: 0xD03E, //HANGUL SYLLABLE KHIEUKH WI RIEULMIEUM - 0xB44E: 0xD03F, //HANGUL SYLLABLE KHIEUKH WI RIEULPIEUP - 0xB44F: 0xD040, //HANGUL SYLLABLE KHIEUKH WI RIEULSIOS - 0xB450: 0xD041, //HANGUL SYLLABLE KHIEUKH WI RIEULTHIEUTH - 0xB451: 0xD042, //HANGUL SYLLABLE KHIEUKH WI RIEULPHIEUPH - 0xB452: 0xD043, //HANGUL SYLLABLE KHIEUKH WI RIEULHIEUH - 0xB453: 0xD046, //HANGUL SYLLABLE KHIEUKH WI PIEUPSIOS - 0xB454: 0xD048, //HANGUL SYLLABLE KHIEUKH WI SSANGSIOS - 0xB455: 0xD04A, //HANGUL SYLLABLE KHIEUKH WI CIEUC - 0xB456: 0xD04B, //HANGUL SYLLABLE KHIEUKH WI CHIEUCH - 0xB457: 0xD04C, //HANGUL SYLLABLE KHIEUKH WI KHIEUKH - 0xB458: 0xD04D, //HANGUL SYLLABLE KHIEUKH WI THIEUTH - 0xB459: 0xD04E, //HANGUL SYLLABLE KHIEUKH WI PHIEUPH - 0xB45A: 0xD04F, //HANGUL SYLLABLE KHIEUKH WI HIEUH - 0xB461: 0xD051, //HANGUL SYLLABLE KHIEUKH YU KIYEOK - 0xB462: 0xD052, //HANGUL SYLLABLE KHIEUKH YU SSANGKIYEOK - 0xB463: 0xD053, //HANGUL SYLLABLE KHIEUKH YU KIYEOKSIOS - 0xB464: 0xD055, //HANGUL SYLLABLE KHIEUKH YU NIEUNCIEUC - 0xB465: 0xD056, //HANGUL SYLLABLE KHIEUKH YU NIEUNHIEUH - 0xB466: 0xD057, //HANGUL SYLLABLE KHIEUKH YU TIKEUT - 0xB467: 0xD059, //HANGUL SYLLABLE KHIEUKH YU RIEULKIYEOK - 0xB468: 0xD05A, //HANGUL SYLLABLE KHIEUKH YU RIEULMIEUM - 0xB469: 0xD05B, //HANGUL SYLLABLE KHIEUKH YU RIEULPIEUP - 0xB46A: 0xD05C, //HANGUL SYLLABLE KHIEUKH YU RIEULSIOS - 0xB46B: 0xD05D, //HANGUL SYLLABLE KHIEUKH YU RIEULTHIEUTH - 0xB46C: 0xD05E, //HANGUL SYLLABLE KHIEUKH YU RIEULPHIEUPH - 0xB46D: 0xD05F, //HANGUL SYLLABLE KHIEUKH YU RIEULHIEUH - 0xB46E: 0xD061, //HANGUL SYLLABLE KHIEUKH YU PIEUP - 0xB46F: 0xD062, //HANGUL SYLLABLE KHIEUKH YU PIEUPSIOS - 0xB470: 0xD063, //HANGUL SYLLABLE KHIEUKH YU SIOS - 0xB471: 0xD064, //HANGUL SYLLABLE KHIEUKH YU SSANGSIOS - 0xB472: 0xD065, //HANGUL SYLLABLE KHIEUKH YU IEUNG - 0xB473: 0xD066, //HANGUL SYLLABLE KHIEUKH YU CIEUC - 0xB474: 0xD067, //HANGUL SYLLABLE KHIEUKH YU CHIEUCH - 0xB475: 0xD068, //HANGUL SYLLABLE KHIEUKH YU KHIEUKH - 0xB476: 0xD069, //HANGUL SYLLABLE KHIEUKH YU THIEUTH - 0xB477: 0xD06A, //HANGUL SYLLABLE KHIEUKH YU PHIEUPH - 0xB478: 0xD06B, //HANGUL SYLLABLE KHIEUKH YU HIEUH - 0xB479: 0xD06E, //HANGUL SYLLABLE KHIEUKH EU SSANGKIYEOK - 0xB47A: 0xD06F, //HANGUL SYLLABLE KHIEUKH EU KIYEOKSIOS - 0xB481: 0xD071, //HANGUL SYLLABLE KHIEUKH EU NIEUNCIEUC - 0xB482: 0xD072, //HANGUL SYLLABLE KHIEUKH EU NIEUNHIEUH - 0xB483: 0xD073, //HANGUL SYLLABLE KHIEUKH EU TIKEUT - 0xB484: 0xD075, //HANGUL SYLLABLE KHIEUKH EU RIEULKIYEOK - 0xB485: 0xD076, //HANGUL SYLLABLE KHIEUKH EU RIEULMIEUM - 0xB486: 0xD077, //HANGUL SYLLABLE KHIEUKH EU RIEULPIEUP - 0xB487: 0xD078, //HANGUL SYLLABLE KHIEUKH EU RIEULSIOS - 0xB488: 0xD079, //HANGUL SYLLABLE KHIEUKH EU RIEULTHIEUTH - 0xB489: 0xD07A, //HANGUL SYLLABLE KHIEUKH EU RIEULPHIEUPH - 0xB48A: 0xD07B, //HANGUL SYLLABLE KHIEUKH EU RIEULHIEUH - 0xB48B: 0xD07E, //HANGUL SYLLABLE KHIEUKH EU PIEUPSIOS - 0xB48C: 0xD07F, //HANGUL SYLLABLE KHIEUKH EU SIOS - 0xB48D: 0xD080, //HANGUL SYLLABLE KHIEUKH EU SSANGSIOS - 0xB48E: 0xD082, //HANGUL SYLLABLE KHIEUKH EU CIEUC - 0xB48F: 0xD083, //HANGUL SYLLABLE KHIEUKH EU CHIEUCH - 0xB490: 0xD084, //HANGUL SYLLABLE KHIEUKH EU KHIEUKH - 0xB491: 0xD085, //HANGUL SYLLABLE KHIEUKH EU THIEUTH - 0xB492: 0xD086, //HANGUL SYLLABLE KHIEUKH EU PHIEUPH - 0xB493: 0xD087, //HANGUL SYLLABLE KHIEUKH EU HIEUH - 0xB494: 0xD088, //HANGUL SYLLABLE KHIEUKH YI - 0xB495: 0xD089, //HANGUL SYLLABLE KHIEUKH YI KIYEOK - 0xB496: 0xD08A, //HANGUL SYLLABLE KHIEUKH YI SSANGKIYEOK - 0xB497: 0xD08B, //HANGUL SYLLABLE KHIEUKH YI KIYEOKSIOS - 0xB498: 0xD08C, //HANGUL SYLLABLE KHIEUKH YI NIEUN - 0xB499: 0xD08D, //HANGUL SYLLABLE KHIEUKH YI NIEUNCIEUC - 0xB49A: 0xD08E, //HANGUL SYLLABLE KHIEUKH YI NIEUNHIEUH - 0xB49B: 0xD08F, //HANGUL SYLLABLE KHIEUKH YI TIKEUT - 0xB49C: 0xD090, //HANGUL SYLLABLE KHIEUKH YI RIEUL - 0xB49D: 0xD091, //HANGUL SYLLABLE KHIEUKH YI RIEULKIYEOK - 0xB49E: 0xD092, //HANGUL SYLLABLE KHIEUKH YI RIEULMIEUM - 0xB49F: 0xD093, //HANGUL SYLLABLE KHIEUKH YI RIEULPIEUP - 0xB4A0: 0xD094, //HANGUL SYLLABLE KHIEUKH YI RIEULSIOS - 0xB4A1: 0xB1DF, //HANGUL SYLLABLE NIEUN OE SIOS - 0xB4A2: 0xB1E8, //HANGUL SYLLABLE NIEUN YO - 0xB4A3: 0xB1E9, //HANGUL SYLLABLE NIEUN YO KIYEOK - 0xB4A4: 0xB1EC, //HANGUL SYLLABLE NIEUN YO NIEUN - 0xB4A5: 0xB1F0, //HANGUL SYLLABLE NIEUN YO RIEUL - 0xB4A6: 0xB1F9, //HANGUL SYLLABLE NIEUN YO PIEUP - 0xB4A7: 0xB1FB, //HANGUL SYLLABLE NIEUN YO SIOS - 0xB4A8: 0xB1FD, //HANGUL SYLLABLE NIEUN YO IEUNG - 0xB4A9: 0xB204, //HANGUL SYLLABLE NIEUN U - 0xB4AA: 0xB205, //HANGUL SYLLABLE NIEUN U KIYEOK - 0xB4AB: 0xB208, //HANGUL SYLLABLE NIEUN U NIEUN - 0xB4AC: 0xB20B, //HANGUL SYLLABLE NIEUN U TIKEUT - 0xB4AD: 0xB20C, //HANGUL SYLLABLE NIEUN U RIEUL - 0xB4AE: 0xB214, //HANGUL SYLLABLE NIEUN U MIEUM - 0xB4AF: 0xB215, //HANGUL SYLLABLE NIEUN U PIEUP - 0xB4B0: 0xB217, //HANGUL SYLLABLE NIEUN U SIOS - 0xB4B1: 0xB219, //HANGUL SYLLABLE NIEUN U IEUNG - 0xB4B2: 0xB220, //HANGUL SYLLABLE NIEUN WEO - 0xB4B3: 0xB234, //HANGUL SYLLABLE NIEUN WEO SSANGSIOS - 0xB4B4: 0xB23C, //HANGUL SYLLABLE NIEUN WE - 0xB4B5: 0xB258, //HANGUL SYLLABLE NIEUN WI - 0xB4B6: 0xB25C, //HANGUL SYLLABLE NIEUN WI NIEUN - 0xB4B7: 0xB260, //HANGUL SYLLABLE NIEUN WI RIEUL - 0xB4B8: 0xB268, //HANGUL SYLLABLE NIEUN WI MIEUM - 0xB4B9: 0xB269, //HANGUL SYLLABLE NIEUN WI PIEUP - 0xB4BA: 0xB274, //HANGUL SYLLABLE NIEUN YU - 0xB4BB: 0xB275, //HANGUL SYLLABLE NIEUN YU KIYEOK - 0xB4BC: 0xB27C, //HANGUL SYLLABLE NIEUN YU RIEUL - 0xB4BD: 0xB284, //HANGUL SYLLABLE NIEUN YU MIEUM - 0xB4BE: 0xB285, //HANGUL SYLLABLE NIEUN YU PIEUP - 0xB4BF: 0xB289, //HANGUL SYLLABLE NIEUN YU IEUNG - 0xB4C0: 0xB290, //HANGUL SYLLABLE NIEUN EU - 0xB4C1: 0xB291, //HANGUL SYLLABLE NIEUN EU KIYEOK - 0xB4C2: 0xB294, //HANGUL SYLLABLE NIEUN EU NIEUN - 0xB4C3: 0xB298, //HANGUL SYLLABLE NIEUN EU RIEUL - 0xB4C4: 0xB299, //HANGUL SYLLABLE NIEUN EU RIEULKIYEOK - 0xB4C5: 0xB29A, //HANGUL SYLLABLE NIEUN EU RIEULMIEUM - 0xB4C6: 0xB2A0, //HANGUL SYLLABLE NIEUN EU MIEUM - 0xB4C7: 0xB2A1, //HANGUL SYLLABLE NIEUN EU PIEUP - 0xB4C8: 0xB2A3, //HANGUL SYLLABLE NIEUN EU SIOS - 0xB4C9: 0xB2A5, //HANGUL SYLLABLE NIEUN EU IEUNG - 0xB4CA: 0xB2A6, //HANGUL SYLLABLE NIEUN EU CIEUC - 0xB4CB: 0xB2AA, //HANGUL SYLLABLE NIEUN EU PHIEUPH - 0xB4CC: 0xB2AC, //HANGUL SYLLABLE NIEUN YI - 0xB4CD: 0xB2B0, //HANGUL SYLLABLE NIEUN YI NIEUN - 0xB4CE: 0xB2B4, //HANGUL SYLLABLE NIEUN YI RIEUL - 0xB4CF: 0xB2C8, //HANGUL SYLLABLE NIEUN I - 0xB4D0: 0xB2C9, //HANGUL SYLLABLE NIEUN I KIYEOK - 0xB4D1: 0xB2CC, //HANGUL SYLLABLE NIEUN I NIEUN - 0xB4D2: 0xB2D0, //HANGUL SYLLABLE NIEUN I RIEUL - 0xB4D3: 0xB2D2, //HANGUL SYLLABLE NIEUN I RIEULMIEUM - 0xB4D4: 0xB2D8, //HANGUL SYLLABLE NIEUN I MIEUM - 0xB4D5: 0xB2D9, //HANGUL SYLLABLE NIEUN I PIEUP - 0xB4D6: 0xB2DB, //HANGUL SYLLABLE NIEUN I SIOS - 0xB4D7: 0xB2DD, //HANGUL SYLLABLE NIEUN I IEUNG - 0xB4D8: 0xB2E2, //HANGUL SYLLABLE NIEUN I PHIEUPH - 0xB4D9: 0xB2E4, //HANGUL SYLLABLE TIKEUT A - 0xB4DA: 0xB2E5, //HANGUL SYLLABLE TIKEUT A KIYEOK - 0xB4DB: 0xB2E6, //HANGUL SYLLABLE TIKEUT A SSANGKIYEOK - 0xB4DC: 0xB2E8, //HANGUL SYLLABLE TIKEUT A NIEUN - 0xB4DD: 0xB2EB, //HANGUL SYLLABLE TIKEUT A TIKEUT - 0xB4DE: 0xB2EC, //HANGUL SYLLABLE TIKEUT A RIEUL - 0xB4DF: 0xB2ED, //HANGUL SYLLABLE TIKEUT A RIEULKIYEOK - 0xB4E0: 0xB2EE, //HANGUL SYLLABLE TIKEUT A RIEULMIEUM - 0xB4E1: 0xB2EF, //HANGUL SYLLABLE TIKEUT A RIEULPIEUP - 0xB4E2: 0xB2F3, //HANGUL SYLLABLE TIKEUT A RIEULHIEUH - 0xB4E3: 0xB2F4, //HANGUL SYLLABLE TIKEUT A MIEUM - 0xB4E4: 0xB2F5, //HANGUL SYLLABLE TIKEUT A PIEUP - 0xB4E5: 0xB2F7, //HANGUL SYLLABLE TIKEUT A SIOS - 0xB4E6: 0xB2F8, //HANGUL SYLLABLE TIKEUT A SSANGSIOS - 0xB4E7: 0xB2F9, //HANGUL SYLLABLE TIKEUT A IEUNG - 0xB4E8: 0xB2FA, //HANGUL SYLLABLE TIKEUT A CIEUC - 0xB4E9: 0xB2FB, //HANGUL SYLLABLE TIKEUT A CHIEUCH - 0xB4EA: 0xB2FF, //HANGUL SYLLABLE TIKEUT A HIEUH - 0xB4EB: 0xB300, //HANGUL SYLLABLE TIKEUT AE - 0xB4EC: 0xB301, //HANGUL SYLLABLE TIKEUT AE KIYEOK - 0xB4ED: 0xB304, //HANGUL SYLLABLE TIKEUT AE NIEUN - 0xB4EE: 0xB308, //HANGUL SYLLABLE TIKEUT AE RIEUL - 0xB4EF: 0xB310, //HANGUL SYLLABLE TIKEUT AE MIEUM - 0xB4F0: 0xB311, //HANGUL SYLLABLE TIKEUT AE PIEUP - 0xB4F1: 0xB313, //HANGUL SYLLABLE TIKEUT AE SIOS - 0xB4F2: 0xB314, //HANGUL SYLLABLE TIKEUT AE SSANGSIOS - 0xB4F3: 0xB315, //HANGUL SYLLABLE TIKEUT AE IEUNG - 0xB4F4: 0xB31C, //HANGUL SYLLABLE TIKEUT YA - 0xB4F5: 0xB354, //HANGUL SYLLABLE TIKEUT EO - 0xB4F6: 0xB355, //HANGUL SYLLABLE TIKEUT EO KIYEOK - 0xB4F7: 0xB356, //HANGUL SYLLABLE TIKEUT EO SSANGKIYEOK - 0xB4F8: 0xB358, //HANGUL SYLLABLE TIKEUT EO NIEUN - 0xB4F9: 0xB35B, //HANGUL SYLLABLE TIKEUT EO TIKEUT - 0xB4FA: 0xB35C, //HANGUL SYLLABLE TIKEUT EO RIEUL - 0xB4FB: 0xB35E, //HANGUL SYLLABLE TIKEUT EO RIEULMIEUM - 0xB4FC: 0xB35F, //HANGUL SYLLABLE TIKEUT EO RIEULPIEUP - 0xB4FD: 0xB364, //HANGUL SYLLABLE TIKEUT EO MIEUM - 0xB4FE: 0xB365, //HANGUL SYLLABLE TIKEUT EO PIEUP - 0xB541: 0xD095, //HANGUL SYLLABLE KHIEUKH YI RIEULTHIEUTH - 0xB542: 0xD096, //HANGUL SYLLABLE KHIEUKH YI RIEULPHIEUPH - 0xB543: 0xD097, //HANGUL SYLLABLE KHIEUKH YI RIEULHIEUH - 0xB544: 0xD098, //HANGUL SYLLABLE KHIEUKH YI MIEUM - 0xB545: 0xD099, //HANGUL SYLLABLE KHIEUKH YI PIEUP - 0xB546: 0xD09A, //HANGUL SYLLABLE KHIEUKH YI PIEUPSIOS - 0xB547: 0xD09B, //HANGUL SYLLABLE KHIEUKH YI SIOS - 0xB548: 0xD09C, //HANGUL SYLLABLE KHIEUKH YI SSANGSIOS - 0xB549: 0xD09D, //HANGUL SYLLABLE KHIEUKH YI IEUNG - 0xB54A: 0xD09E, //HANGUL SYLLABLE KHIEUKH YI CIEUC - 0xB54B: 0xD09F, //HANGUL SYLLABLE KHIEUKH YI CHIEUCH - 0xB54C: 0xD0A0, //HANGUL SYLLABLE KHIEUKH YI KHIEUKH - 0xB54D: 0xD0A1, //HANGUL SYLLABLE KHIEUKH YI THIEUTH - 0xB54E: 0xD0A2, //HANGUL SYLLABLE KHIEUKH YI PHIEUPH - 0xB54F: 0xD0A3, //HANGUL SYLLABLE KHIEUKH YI HIEUH - 0xB550: 0xD0A6, //HANGUL SYLLABLE KHIEUKH I SSANGKIYEOK - 0xB551: 0xD0A7, //HANGUL SYLLABLE KHIEUKH I KIYEOKSIOS - 0xB552: 0xD0A9, //HANGUL SYLLABLE KHIEUKH I NIEUNCIEUC - 0xB553: 0xD0AA, //HANGUL SYLLABLE KHIEUKH I NIEUNHIEUH - 0xB554: 0xD0AB, //HANGUL SYLLABLE KHIEUKH I TIKEUT - 0xB555: 0xD0AD, //HANGUL SYLLABLE KHIEUKH I RIEULKIYEOK - 0xB556: 0xD0AE, //HANGUL SYLLABLE KHIEUKH I RIEULMIEUM - 0xB557: 0xD0AF, //HANGUL SYLLABLE KHIEUKH I RIEULPIEUP - 0xB558: 0xD0B0, //HANGUL SYLLABLE KHIEUKH I RIEULSIOS - 0xB559: 0xD0B1, //HANGUL SYLLABLE KHIEUKH I RIEULTHIEUTH - 0xB55A: 0xD0B2, //HANGUL SYLLABLE KHIEUKH I RIEULPHIEUPH - 0xB561: 0xD0B3, //HANGUL SYLLABLE KHIEUKH I RIEULHIEUH - 0xB562: 0xD0B6, //HANGUL SYLLABLE KHIEUKH I PIEUPSIOS - 0xB563: 0xD0B8, //HANGUL SYLLABLE KHIEUKH I SSANGSIOS - 0xB564: 0xD0BA, //HANGUL SYLLABLE KHIEUKH I CIEUC - 0xB565: 0xD0BB, //HANGUL SYLLABLE KHIEUKH I CHIEUCH - 0xB566: 0xD0BC, //HANGUL SYLLABLE KHIEUKH I KHIEUKH - 0xB567: 0xD0BD, //HANGUL SYLLABLE KHIEUKH I THIEUTH - 0xB568: 0xD0BE, //HANGUL SYLLABLE KHIEUKH I PHIEUPH - 0xB569: 0xD0BF, //HANGUL SYLLABLE KHIEUKH I HIEUH - 0xB56A: 0xD0C2, //HANGUL SYLLABLE THIEUTH A SSANGKIYEOK - 0xB56B: 0xD0C3, //HANGUL SYLLABLE THIEUTH A KIYEOKSIOS - 0xB56C: 0xD0C5, //HANGUL SYLLABLE THIEUTH A NIEUNCIEUC - 0xB56D: 0xD0C6, //HANGUL SYLLABLE THIEUTH A NIEUNHIEUH - 0xB56E: 0xD0C7, //HANGUL SYLLABLE THIEUTH A TIKEUT - 0xB56F: 0xD0CA, //HANGUL SYLLABLE THIEUTH A RIEULMIEUM - 0xB570: 0xD0CB, //HANGUL SYLLABLE THIEUTH A RIEULPIEUP - 0xB571: 0xD0CC, //HANGUL SYLLABLE THIEUTH A RIEULSIOS - 0xB572: 0xD0CD, //HANGUL SYLLABLE THIEUTH A RIEULTHIEUTH - 0xB573: 0xD0CE, //HANGUL SYLLABLE THIEUTH A RIEULPHIEUPH - 0xB574: 0xD0CF, //HANGUL SYLLABLE THIEUTH A RIEULHIEUH - 0xB575: 0xD0D2, //HANGUL SYLLABLE THIEUTH A PIEUPSIOS - 0xB576: 0xD0D6, //HANGUL SYLLABLE THIEUTH A CIEUC - 0xB577: 0xD0D7, //HANGUL SYLLABLE THIEUTH A CHIEUCH - 0xB578: 0xD0D8, //HANGUL SYLLABLE THIEUTH A KHIEUKH - 0xB579: 0xD0D9, //HANGUL SYLLABLE THIEUTH A THIEUTH - 0xB57A: 0xD0DA, //HANGUL SYLLABLE THIEUTH A PHIEUPH - 0xB581: 0xD0DB, //HANGUL SYLLABLE THIEUTH A HIEUH - 0xB582: 0xD0DE, //HANGUL SYLLABLE THIEUTH AE SSANGKIYEOK - 0xB583: 0xD0DF, //HANGUL SYLLABLE THIEUTH AE KIYEOKSIOS - 0xB584: 0xD0E1, //HANGUL SYLLABLE THIEUTH AE NIEUNCIEUC - 0xB585: 0xD0E2, //HANGUL SYLLABLE THIEUTH AE NIEUNHIEUH - 0xB586: 0xD0E3, //HANGUL SYLLABLE THIEUTH AE TIKEUT - 0xB587: 0xD0E5, //HANGUL SYLLABLE THIEUTH AE RIEULKIYEOK - 0xB588: 0xD0E6, //HANGUL SYLLABLE THIEUTH AE RIEULMIEUM - 0xB589: 0xD0E7, //HANGUL SYLLABLE THIEUTH AE RIEULPIEUP - 0xB58A: 0xD0E8, //HANGUL SYLLABLE THIEUTH AE RIEULSIOS - 0xB58B: 0xD0E9, //HANGUL SYLLABLE THIEUTH AE RIEULTHIEUTH - 0xB58C: 0xD0EA, //HANGUL SYLLABLE THIEUTH AE RIEULPHIEUPH - 0xB58D: 0xD0EB, //HANGUL SYLLABLE THIEUTH AE RIEULHIEUH - 0xB58E: 0xD0EE, //HANGUL SYLLABLE THIEUTH AE PIEUPSIOS - 0xB58F: 0xD0F2, //HANGUL SYLLABLE THIEUTH AE CIEUC - 0xB590: 0xD0F3, //HANGUL SYLLABLE THIEUTH AE CHIEUCH - 0xB591: 0xD0F4, //HANGUL SYLLABLE THIEUTH AE KHIEUKH - 0xB592: 0xD0F5, //HANGUL SYLLABLE THIEUTH AE THIEUTH - 0xB593: 0xD0F6, //HANGUL SYLLABLE THIEUTH AE PHIEUPH - 0xB594: 0xD0F7, //HANGUL SYLLABLE THIEUTH AE HIEUH - 0xB595: 0xD0F9, //HANGUL SYLLABLE THIEUTH YA KIYEOK - 0xB596: 0xD0FA, //HANGUL SYLLABLE THIEUTH YA SSANGKIYEOK - 0xB597: 0xD0FB, //HANGUL SYLLABLE THIEUTH YA KIYEOKSIOS - 0xB598: 0xD0FC, //HANGUL SYLLABLE THIEUTH YA NIEUN - 0xB599: 0xD0FD, //HANGUL SYLLABLE THIEUTH YA NIEUNCIEUC - 0xB59A: 0xD0FE, //HANGUL SYLLABLE THIEUTH YA NIEUNHIEUH - 0xB59B: 0xD0FF, //HANGUL SYLLABLE THIEUTH YA TIKEUT - 0xB59C: 0xD100, //HANGUL SYLLABLE THIEUTH YA RIEUL - 0xB59D: 0xD101, //HANGUL SYLLABLE THIEUTH YA RIEULKIYEOK - 0xB59E: 0xD102, //HANGUL SYLLABLE THIEUTH YA RIEULMIEUM - 0xB59F: 0xD103, //HANGUL SYLLABLE THIEUTH YA RIEULPIEUP - 0xB5A0: 0xD104, //HANGUL SYLLABLE THIEUTH YA RIEULSIOS - 0xB5A1: 0xB367, //HANGUL SYLLABLE TIKEUT EO SIOS - 0xB5A2: 0xB369, //HANGUL SYLLABLE TIKEUT EO IEUNG - 0xB5A3: 0xB36B, //HANGUL SYLLABLE TIKEUT EO CHIEUCH - 0xB5A4: 0xB36E, //HANGUL SYLLABLE TIKEUT EO PHIEUPH - 0xB5A5: 0xB370, //HANGUL SYLLABLE TIKEUT E - 0xB5A6: 0xB371, //HANGUL SYLLABLE TIKEUT E KIYEOK - 0xB5A7: 0xB374, //HANGUL SYLLABLE TIKEUT E NIEUN - 0xB5A8: 0xB378, //HANGUL SYLLABLE TIKEUT E RIEUL - 0xB5A9: 0xB380, //HANGUL SYLLABLE TIKEUT E MIEUM - 0xB5AA: 0xB381, //HANGUL SYLLABLE TIKEUT E PIEUP - 0xB5AB: 0xB383, //HANGUL SYLLABLE TIKEUT E SIOS - 0xB5AC: 0xB384, //HANGUL SYLLABLE TIKEUT E SSANGSIOS - 0xB5AD: 0xB385, //HANGUL SYLLABLE TIKEUT E IEUNG - 0xB5AE: 0xB38C, //HANGUL SYLLABLE TIKEUT YEO - 0xB5AF: 0xB390, //HANGUL SYLLABLE TIKEUT YEO NIEUN - 0xB5B0: 0xB394, //HANGUL SYLLABLE TIKEUT YEO RIEUL - 0xB5B1: 0xB3A0, //HANGUL SYLLABLE TIKEUT YEO SSANGSIOS - 0xB5B2: 0xB3A1, //HANGUL SYLLABLE TIKEUT YEO IEUNG - 0xB5B3: 0xB3A8, //HANGUL SYLLABLE TIKEUT YE - 0xB5B4: 0xB3AC, //HANGUL SYLLABLE TIKEUT YE NIEUN - 0xB5B5: 0xB3C4, //HANGUL SYLLABLE TIKEUT O - 0xB5B6: 0xB3C5, //HANGUL SYLLABLE TIKEUT O KIYEOK - 0xB5B7: 0xB3C8, //HANGUL SYLLABLE TIKEUT O NIEUN - 0xB5B8: 0xB3CB, //HANGUL SYLLABLE TIKEUT O TIKEUT - 0xB5B9: 0xB3CC, //HANGUL SYLLABLE TIKEUT O RIEUL - 0xB5BA: 0xB3CE, //HANGUL SYLLABLE TIKEUT O RIEULMIEUM - 0xB5BB: 0xB3D0, //HANGUL SYLLABLE TIKEUT O RIEULSIOS - 0xB5BC: 0xB3D4, //HANGUL SYLLABLE TIKEUT O MIEUM - 0xB5BD: 0xB3D5, //HANGUL SYLLABLE TIKEUT O PIEUP - 0xB5BE: 0xB3D7, //HANGUL SYLLABLE TIKEUT O SIOS - 0xB5BF: 0xB3D9, //HANGUL SYLLABLE TIKEUT O IEUNG - 0xB5C0: 0xB3DB, //HANGUL SYLLABLE TIKEUT O CHIEUCH - 0xB5C1: 0xB3DD, //HANGUL SYLLABLE TIKEUT O THIEUTH - 0xB5C2: 0xB3E0, //HANGUL SYLLABLE TIKEUT WA - 0xB5C3: 0xB3E4, //HANGUL SYLLABLE TIKEUT WA NIEUN - 0xB5C4: 0xB3E8, //HANGUL SYLLABLE TIKEUT WA RIEUL - 0xB5C5: 0xB3FC, //HANGUL SYLLABLE TIKEUT WAE - 0xB5C6: 0xB410, //HANGUL SYLLABLE TIKEUT WAE SSANGSIOS - 0xB5C7: 0xB418, //HANGUL SYLLABLE TIKEUT OE - 0xB5C8: 0xB41C, //HANGUL SYLLABLE TIKEUT OE NIEUN - 0xB5C9: 0xB420, //HANGUL SYLLABLE TIKEUT OE RIEUL - 0xB5CA: 0xB428, //HANGUL SYLLABLE TIKEUT OE MIEUM - 0xB5CB: 0xB429, //HANGUL SYLLABLE TIKEUT OE PIEUP - 0xB5CC: 0xB42B, //HANGUL SYLLABLE TIKEUT OE SIOS - 0xB5CD: 0xB434, //HANGUL SYLLABLE TIKEUT YO - 0xB5CE: 0xB450, //HANGUL SYLLABLE TIKEUT U - 0xB5CF: 0xB451, //HANGUL SYLLABLE TIKEUT U KIYEOK - 0xB5D0: 0xB454, //HANGUL SYLLABLE TIKEUT U NIEUN - 0xB5D1: 0xB458, //HANGUL SYLLABLE TIKEUT U RIEUL - 0xB5D2: 0xB460, //HANGUL SYLLABLE TIKEUT U MIEUM - 0xB5D3: 0xB461, //HANGUL SYLLABLE TIKEUT U PIEUP - 0xB5D4: 0xB463, //HANGUL SYLLABLE TIKEUT U SIOS - 0xB5D5: 0xB465, //HANGUL SYLLABLE TIKEUT U IEUNG - 0xB5D6: 0xB46C, //HANGUL SYLLABLE TIKEUT WEO - 0xB5D7: 0xB480, //HANGUL SYLLABLE TIKEUT WEO SSANGSIOS - 0xB5D8: 0xB488, //HANGUL SYLLABLE TIKEUT WE - 0xB5D9: 0xB49D, //HANGUL SYLLABLE TIKEUT WE IEUNG - 0xB5DA: 0xB4A4, //HANGUL SYLLABLE TIKEUT WI - 0xB5DB: 0xB4A8, //HANGUL SYLLABLE TIKEUT WI NIEUN - 0xB5DC: 0xB4AC, //HANGUL SYLLABLE TIKEUT WI RIEUL - 0xB5DD: 0xB4B5, //HANGUL SYLLABLE TIKEUT WI PIEUP - 0xB5DE: 0xB4B7, //HANGUL SYLLABLE TIKEUT WI SIOS - 0xB5DF: 0xB4B9, //HANGUL SYLLABLE TIKEUT WI IEUNG - 0xB5E0: 0xB4C0, //HANGUL SYLLABLE TIKEUT YU - 0xB5E1: 0xB4C4, //HANGUL SYLLABLE TIKEUT YU NIEUN - 0xB5E2: 0xB4C8, //HANGUL SYLLABLE TIKEUT YU RIEUL - 0xB5E3: 0xB4D0, //HANGUL SYLLABLE TIKEUT YU MIEUM - 0xB5E4: 0xB4D5, //HANGUL SYLLABLE TIKEUT YU IEUNG - 0xB5E5: 0xB4DC, //HANGUL SYLLABLE TIKEUT EU - 0xB5E6: 0xB4DD, //HANGUL SYLLABLE TIKEUT EU KIYEOK - 0xB5E7: 0xB4E0, //HANGUL SYLLABLE TIKEUT EU NIEUN - 0xB5E8: 0xB4E3, //HANGUL SYLLABLE TIKEUT EU TIKEUT - 0xB5E9: 0xB4E4, //HANGUL SYLLABLE TIKEUT EU RIEUL - 0xB5EA: 0xB4E6, //HANGUL SYLLABLE TIKEUT EU RIEULMIEUM - 0xB5EB: 0xB4EC, //HANGUL SYLLABLE TIKEUT EU MIEUM - 0xB5EC: 0xB4ED, //HANGUL SYLLABLE TIKEUT EU PIEUP - 0xB5ED: 0xB4EF, //HANGUL SYLLABLE TIKEUT EU SIOS - 0xB5EE: 0xB4F1, //HANGUL SYLLABLE TIKEUT EU IEUNG - 0xB5EF: 0xB4F8, //HANGUL SYLLABLE TIKEUT YI - 0xB5F0: 0xB514, //HANGUL SYLLABLE TIKEUT I - 0xB5F1: 0xB515, //HANGUL SYLLABLE TIKEUT I KIYEOK - 0xB5F2: 0xB518, //HANGUL SYLLABLE TIKEUT I NIEUN - 0xB5F3: 0xB51B, //HANGUL SYLLABLE TIKEUT I TIKEUT - 0xB5F4: 0xB51C, //HANGUL SYLLABLE TIKEUT I RIEUL - 0xB5F5: 0xB524, //HANGUL SYLLABLE TIKEUT I MIEUM - 0xB5F6: 0xB525, //HANGUL SYLLABLE TIKEUT I PIEUP - 0xB5F7: 0xB527, //HANGUL SYLLABLE TIKEUT I SIOS - 0xB5F8: 0xB528, //HANGUL SYLLABLE TIKEUT I SSANGSIOS - 0xB5F9: 0xB529, //HANGUL SYLLABLE TIKEUT I IEUNG - 0xB5FA: 0xB52A, //HANGUL SYLLABLE TIKEUT I CIEUC - 0xB5FB: 0xB530, //HANGUL SYLLABLE SSANGTIKEUT A - 0xB5FC: 0xB531, //HANGUL SYLLABLE SSANGTIKEUT A KIYEOK - 0xB5FD: 0xB534, //HANGUL SYLLABLE SSANGTIKEUT A NIEUN - 0xB5FE: 0xB538, //HANGUL SYLLABLE SSANGTIKEUT A RIEUL - 0xB641: 0xD105, //HANGUL SYLLABLE THIEUTH YA RIEULTHIEUTH - 0xB642: 0xD106, //HANGUL SYLLABLE THIEUTH YA RIEULPHIEUPH - 0xB643: 0xD107, //HANGUL SYLLABLE THIEUTH YA RIEULHIEUH - 0xB644: 0xD108, //HANGUL SYLLABLE THIEUTH YA MIEUM - 0xB645: 0xD109, //HANGUL SYLLABLE THIEUTH YA PIEUP - 0xB646: 0xD10A, //HANGUL SYLLABLE THIEUTH YA PIEUPSIOS - 0xB647: 0xD10B, //HANGUL SYLLABLE THIEUTH YA SIOS - 0xB648: 0xD10C, //HANGUL SYLLABLE THIEUTH YA SSANGSIOS - 0xB649: 0xD10E, //HANGUL SYLLABLE THIEUTH YA CIEUC - 0xB64A: 0xD10F, //HANGUL SYLLABLE THIEUTH YA CHIEUCH - 0xB64B: 0xD110, //HANGUL SYLLABLE THIEUTH YA KHIEUKH - 0xB64C: 0xD111, //HANGUL SYLLABLE THIEUTH YA THIEUTH - 0xB64D: 0xD112, //HANGUL SYLLABLE THIEUTH YA PHIEUPH - 0xB64E: 0xD113, //HANGUL SYLLABLE THIEUTH YA HIEUH - 0xB64F: 0xD114, //HANGUL SYLLABLE THIEUTH YAE - 0xB650: 0xD115, //HANGUL SYLLABLE THIEUTH YAE KIYEOK - 0xB651: 0xD116, //HANGUL SYLLABLE THIEUTH YAE SSANGKIYEOK - 0xB652: 0xD117, //HANGUL SYLLABLE THIEUTH YAE KIYEOKSIOS - 0xB653: 0xD118, //HANGUL SYLLABLE THIEUTH YAE NIEUN - 0xB654: 0xD119, //HANGUL SYLLABLE THIEUTH YAE NIEUNCIEUC - 0xB655: 0xD11A, //HANGUL SYLLABLE THIEUTH YAE NIEUNHIEUH - 0xB656: 0xD11B, //HANGUL SYLLABLE THIEUTH YAE TIKEUT - 0xB657: 0xD11C, //HANGUL SYLLABLE THIEUTH YAE RIEUL - 0xB658: 0xD11D, //HANGUL SYLLABLE THIEUTH YAE RIEULKIYEOK - 0xB659: 0xD11E, //HANGUL SYLLABLE THIEUTH YAE RIEULMIEUM - 0xB65A: 0xD11F, //HANGUL SYLLABLE THIEUTH YAE RIEULPIEUP - 0xB661: 0xD120, //HANGUL SYLLABLE THIEUTH YAE RIEULSIOS - 0xB662: 0xD121, //HANGUL SYLLABLE THIEUTH YAE RIEULTHIEUTH - 0xB663: 0xD122, //HANGUL SYLLABLE THIEUTH YAE RIEULPHIEUPH - 0xB664: 0xD123, //HANGUL SYLLABLE THIEUTH YAE RIEULHIEUH - 0xB665: 0xD124, //HANGUL SYLLABLE THIEUTH YAE MIEUM - 0xB666: 0xD125, //HANGUL SYLLABLE THIEUTH YAE PIEUP - 0xB667: 0xD126, //HANGUL SYLLABLE THIEUTH YAE PIEUPSIOS - 0xB668: 0xD127, //HANGUL SYLLABLE THIEUTH YAE SIOS - 0xB669: 0xD128, //HANGUL SYLLABLE THIEUTH YAE SSANGSIOS - 0xB66A: 0xD129, //HANGUL SYLLABLE THIEUTH YAE IEUNG - 0xB66B: 0xD12A, //HANGUL SYLLABLE THIEUTH YAE CIEUC - 0xB66C: 0xD12B, //HANGUL SYLLABLE THIEUTH YAE CHIEUCH - 0xB66D: 0xD12C, //HANGUL SYLLABLE THIEUTH YAE KHIEUKH - 0xB66E: 0xD12D, //HANGUL SYLLABLE THIEUTH YAE THIEUTH - 0xB66F: 0xD12E, //HANGUL SYLLABLE THIEUTH YAE PHIEUPH - 0xB670: 0xD12F, //HANGUL SYLLABLE THIEUTH YAE HIEUH - 0xB671: 0xD132, //HANGUL SYLLABLE THIEUTH EO SSANGKIYEOK - 0xB672: 0xD133, //HANGUL SYLLABLE THIEUTH EO KIYEOKSIOS - 0xB673: 0xD135, //HANGUL SYLLABLE THIEUTH EO NIEUNCIEUC - 0xB674: 0xD136, //HANGUL SYLLABLE THIEUTH EO NIEUNHIEUH - 0xB675: 0xD137, //HANGUL SYLLABLE THIEUTH EO TIKEUT - 0xB676: 0xD139, //HANGUL SYLLABLE THIEUTH EO RIEULKIYEOK - 0xB677: 0xD13B, //HANGUL SYLLABLE THIEUTH EO RIEULPIEUP - 0xB678: 0xD13C, //HANGUL SYLLABLE THIEUTH EO RIEULSIOS - 0xB679: 0xD13D, //HANGUL SYLLABLE THIEUTH EO RIEULTHIEUTH - 0xB67A: 0xD13E, //HANGUL SYLLABLE THIEUTH EO RIEULPHIEUPH - 0xB681: 0xD13F, //HANGUL SYLLABLE THIEUTH EO RIEULHIEUH - 0xB682: 0xD142, //HANGUL SYLLABLE THIEUTH EO PIEUPSIOS - 0xB683: 0xD146, //HANGUL SYLLABLE THIEUTH EO CIEUC - 0xB684: 0xD147, //HANGUL SYLLABLE THIEUTH EO CHIEUCH - 0xB685: 0xD148, //HANGUL SYLLABLE THIEUTH EO KHIEUKH - 0xB686: 0xD149, //HANGUL SYLLABLE THIEUTH EO THIEUTH - 0xB687: 0xD14A, //HANGUL SYLLABLE THIEUTH EO PHIEUPH - 0xB688: 0xD14B, //HANGUL SYLLABLE THIEUTH EO HIEUH - 0xB689: 0xD14E, //HANGUL SYLLABLE THIEUTH E SSANGKIYEOK - 0xB68A: 0xD14F, //HANGUL SYLLABLE THIEUTH E KIYEOKSIOS - 0xB68B: 0xD151, //HANGUL SYLLABLE THIEUTH E NIEUNCIEUC - 0xB68C: 0xD152, //HANGUL SYLLABLE THIEUTH E NIEUNHIEUH - 0xB68D: 0xD153, //HANGUL SYLLABLE THIEUTH E TIKEUT - 0xB68E: 0xD155, //HANGUL SYLLABLE THIEUTH E RIEULKIYEOK - 0xB68F: 0xD156, //HANGUL SYLLABLE THIEUTH E RIEULMIEUM - 0xB690: 0xD157, //HANGUL SYLLABLE THIEUTH E RIEULPIEUP - 0xB691: 0xD158, //HANGUL SYLLABLE THIEUTH E RIEULSIOS - 0xB692: 0xD159, //HANGUL SYLLABLE THIEUTH E RIEULTHIEUTH - 0xB693: 0xD15A, //HANGUL SYLLABLE THIEUTH E RIEULPHIEUPH - 0xB694: 0xD15B, //HANGUL SYLLABLE THIEUTH E RIEULHIEUH - 0xB695: 0xD15E, //HANGUL SYLLABLE THIEUTH E PIEUPSIOS - 0xB696: 0xD160, //HANGUL SYLLABLE THIEUTH E SSANGSIOS - 0xB697: 0xD162, //HANGUL SYLLABLE THIEUTH E CIEUC - 0xB698: 0xD163, //HANGUL SYLLABLE THIEUTH E CHIEUCH - 0xB699: 0xD164, //HANGUL SYLLABLE THIEUTH E KHIEUKH - 0xB69A: 0xD165, //HANGUL SYLLABLE THIEUTH E THIEUTH - 0xB69B: 0xD166, //HANGUL SYLLABLE THIEUTH E PHIEUPH - 0xB69C: 0xD167, //HANGUL SYLLABLE THIEUTH E HIEUH - 0xB69D: 0xD169, //HANGUL SYLLABLE THIEUTH YEO KIYEOK - 0xB69E: 0xD16A, //HANGUL SYLLABLE THIEUTH YEO SSANGKIYEOK - 0xB69F: 0xD16B, //HANGUL SYLLABLE THIEUTH YEO KIYEOKSIOS - 0xB6A0: 0xD16D, //HANGUL SYLLABLE THIEUTH YEO NIEUNCIEUC - 0xB6A1: 0xB540, //HANGUL SYLLABLE SSANGTIKEUT A MIEUM - 0xB6A2: 0xB541, //HANGUL SYLLABLE SSANGTIKEUT A PIEUP - 0xB6A3: 0xB543, //HANGUL SYLLABLE SSANGTIKEUT A SIOS - 0xB6A4: 0xB544, //HANGUL SYLLABLE SSANGTIKEUT A SSANGSIOS - 0xB6A5: 0xB545, //HANGUL SYLLABLE SSANGTIKEUT A IEUNG - 0xB6A6: 0xB54B, //HANGUL SYLLABLE SSANGTIKEUT A HIEUH - 0xB6A7: 0xB54C, //HANGUL SYLLABLE SSANGTIKEUT AE - 0xB6A8: 0xB54D, //HANGUL SYLLABLE SSANGTIKEUT AE KIYEOK - 0xB6A9: 0xB550, //HANGUL SYLLABLE SSANGTIKEUT AE NIEUN - 0xB6AA: 0xB554, //HANGUL SYLLABLE SSANGTIKEUT AE RIEUL - 0xB6AB: 0xB55C, //HANGUL SYLLABLE SSANGTIKEUT AE MIEUM - 0xB6AC: 0xB55D, //HANGUL SYLLABLE SSANGTIKEUT AE PIEUP - 0xB6AD: 0xB55F, //HANGUL SYLLABLE SSANGTIKEUT AE SIOS - 0xB6AE: 0xB560, //HANGUL SYLLABLE SSANGTIKEUT AE SSANGSIOS - 0xB6AF: 0xB561, //HANGUL SYLLABLE SSANGTIKEUT AE IEUNG - 0xB6B0: 0xB5A0, //HANGUL SYLLABLE SSANGTIKEUT EO - 0xB6B1: 0xB5A1, //HANGUL SYLLABLE SSANGTIKEUT EO KIYEOK - 0xB6B2: 0xB5A4, //HANGUL SYLLABLE SSANGTIKEUT EO NIEUN - 0xB6B3: 0xB5A8, //HANGUL SYLLABLE SSANGTIKEUT EO RIEUL - 0xB6B4: 0xB5AA, //HANGUL SYLLABLE SSANGTIKEUT EO RIEULMIEUM - 0xB6B5: 0xB5AB, //HANGUL SYLLABLE SSANGTIKEUT EO RIEULPIEUP - 0xB6B6: 0xB5B0, //HANGUL SYLLABLE SSANGTIKEUT EO MIEUM - 0xB6B7: 0xB5B1, //HANGUL SYLLABLE SSANGTIKEUT EO PIEUP - 0xB6B8: 0xB5B3, //HANGUL SYLLABLE SSANGTIKEUT EO SIOS - 0xB6B9: 0xB5B4, //HANGUL SYLLABLE SSANGTIKEUT EO SSANGSIOS - 0xB6BA: 0xB5B5, //HANGUL SYLLABLE SSANGTIKEUT EO IEUNG - 0xB6BB: 0xB5BB, //HANGUL SYLLABLE SSANGTIKEUT EO HIEUH - 0xB6BC: 0xB5BC, //HANGUL SYLLABLE SSANGTIKEUT E - 0xB6BD: 0xB5BD, //HANGUL SYLLABLE SSANGTIKEUT E KIYEOK - 0xB6BE: 0xB5C0, //HANGUL SYLLABLE SSANGTIKEUT E NIEUN - 0xB6BF: 0xB5C4, //HANGUL SYLLABLE SSANGTIKEUT E RIEUL - 0xB6C0: 0xB5CC, //HANGUL SYLLABLE SSANGTIKEUT E MIEUM - 0xB6C1: 0xB5CD, //HANGUL SYLLABLE SSANGTIKEUT E PIEUP - 0xB6C2: 0xB5CF, //HANGUL SYLLABLE SSANGTIKEUT E SIOS - 0xB6C3: 0xB5D0, //HANGUL SYLLABLE SSANGTIKEUT E SSANGSIOS - 0xB6C4: 0xB5D1, //HANGUL SYLLABLE SSANGTIKEUT E IEUNG - 0xB6C5: 0xB5D8, //HANGUL SYLLABLE SSANGTIKEUT YEO - 0xB6C6: 0xB5EC, //HANGUL SYLLABLE SSANGTIKEUT YEO SSANGSIOS - 0xB6C7: 0xB610, //HANGUL SYLLABLE SSANGTIKEUT O - 0xB6C8: 0xB611, //HANGUL SYLLABLE SSANGTIKEUT O KIYEOK - 0xB6C9: 0xB614, //HANGUL SYLLABLE SSANGTIKEUT O NIEUN - 0xB6CA: 0xB618, //HANGUL SYLLABLE SSANGTIKEUT O RIEUL - 0xB6CB: 0xB625, //HANGUL SYLLABLE SSANGTIKEUT O IEUNG - 0xB6CC: 0xB62C, //HANGUL SYLLABLE SSANGTIKEUT WA - 0xB6CD: 0xB634, //HANGUL SYLLABLE SSANGTIKEUT WA RIEUL - 0xB6CE: 0xB648, //HANGUL SYLLABLE SSANGTIKEUT WAE - 0xB6CF: 0xB664, //HANGUL SYLLABLE SSANGTIKEUT OE - 0xB6D0: 0xB668, //HANGUL SYLLABLE SSANGTIKEUT OE NIEUN - 0xB6D1: 0xB69C, //HANGUL SYLLABLE SSANGTIKEUT U - 0xB6D2: 0xB69D, //HANGUL SYLLABLE SSANGTIKEUT U KIYEOK - 0xB6D3: 0xB6A0, //HANGUL SYLLABLE SSANGTIKEUT U NIEUN - 0xB6D4: 0xB6A4, //HANGUL SYLLABLE SSANGTIKEUT U RIEUL - 0xB6D5: 0xB6AB, //HANGUL SYLLABLE SSANGTIKEUT U RIEULHIEUH - 0xB6D6: 0xB6AC, //HANGUL SYLLABLE SSANGTIKEUT U MIEUM - 0xB6D7: 0xB6B1, //HANGUL SYLLABLE SSANGTIKEUT U IEUNG - 0xB6D8: 0xB6D4, //HANGUL SYLLABLE SSANGTIKEUT WE - 0xB6D9: 0xB6F0, //HANGUL SYLLABLE SSANGTIKEUT WI - 0xB6DA: 0xB6F4, //HANGUL SYLLABLE SSANGTIKEUT WI NIEUN - 0xB6DB: 0xB6F8, //HANGUL SYLLABLE SSANGTIKEUT WI RIEUL - 0xB6DC: 0xB700, //HANGUL SYLLABLE SSANGTIKEUT WI MIEUM - 0xB6DD: 0xB701, //HANGUL SYLLABLE SSANGTIKEUT WI PIEUP - 0xB6DE: 0xB705, //HANGUL SYLLABLE SSANGTIKEUT WI IEUNG - 0xB6DF: 0xB728, //HANGUL SYLLABLE SSANGTIKEUT EU - 0xB6E0: 0xB729, //HANGUL SYLLABLE SSANGTIKEUT EU KIYEOK - 0xB6E1: 0xB72C, //HANGUL SYLLABLE SSANGTIKEUT EU NIEUN - 0xB6E2: 0xB72F, //HANGUL SYLLABLE SSANGTIKEUT EU TIKEUT - 0xB6E3: 0xB730, //HANGUL SYLLABLE SSANGTIKEUT EU RIEUL - 0xB6E4: 0xB738, //HANGUL SYLLABLE SSANGTIKEUT EU MIEUM - 0xB6E5: 0xB739, //HANGUL SYLLABLE SSANGTIKEUT EU PIEUP - 0xB6E6: 0xB73B, //HANGUL SYLLABLE SSANGTIKEUT EU SIOS - 0xB6E7: 0xB744, //HANGUL SYLLABLE SSANGTIKEUT YI - 0xB6E8: 0xB748, //HANGUL SYLLABLE SSANGTIKEUT YI NIEUN - 0xB6E9: 0xB74C, //HANGUL SYLLABLE SSANGTIKEUT YI RIEUL - 0xB6EA: 0xB754, //HANGUL SYLLABLE SSANGTIKEUT YI MIEUM - 0xB6EB: 0xB755, //HANGUL SYLLABLE SSANGTIKEUT YI PIEUP - 0xB6EC: 0xB760, //HANGUL SYLLABLE SSANGTIKEUT I - 0xB6ED: 0xB764, //HANGUL SYLLABLE SSANGTIKEUT I NIEUN - 0xB6EE: 0xB768, //HANGUL SYLLABLE SSANGTIKEUT I RIEUL - 0xB6EF: 0xB770, //HANGUL SYLLABLE SSANGTIKEUT I MIEUM - 0xB6F0: 0xB771, //HANGUL SYLLABLE SSANGTIKEUT I PIEUP - 0xB6F1: 0xB773, //HANGUL SYLLABLE SSANGTIKEUT I SIOS - 0xB6F2: 0xB775, //HANGUL SYLLABLE SSANGTIKEUT I IEUNG - 0xB6F3: 0xB77C, //HANGUL SYLLABLE RIEUL A - 0xB6F4: 0xB77D, //HANGUL SYLLABLE RIEUL A KIYEOK - 0xB6F5: 0xB780, //HANGUL SYLLABLE RIEUL A NIEUN - 0xB6F6: 0xB784, //HANGUL SYLLABLE RIEUL A RIEUL - 0xB6F7: 0xB78C, //HANGUL SYLLABLE RIEUL A MIEUM - 0xB6F8: 0xB78D, //HANGUL SYLLABLE RIEUL A PIEUP - 0xB6F9: 0xB78F, //HANGUL SYLLABLE RIEUL A SIOS - 0xB6FA: 0xB790, //HANGUL SYLLABLE RIEUL A SSANGSIOS - 0xB6FB: 0xB791, //HANGUL SYLLABLE RIEUL A IEUNG - 0xB6FC: 0xB792, //HANGUL SYLLABLE RIEUL A CIEUC - 0xB6FD: 0xB796, //HANGUL SYLLABLE RIEUL A PHIEUPH - 0xB6FE: 0xB797, //HANGUL SYLLABLE RIEUL A HIEUH - 0xB741: 0xD16E, //HANGUL SYLLABLE THIEUTH YEO NIEUNHIEUH - 0xB742: 0xD16F, //HANGUL SYLLABLE THIEUTH YEO TIKEUT - 0xB743: 0xD170, //HANGUL SYLLABLE THIEUTH YEO RIEUL - 0xB744: 0xD171, //HANGUL SYLLABLE THIEUTH YEO RIEULKIYEOK - 0xB745: 0xD172, //HANGUL SYLLABLE THIEUTH YEO RIEULMIEUM - 0xB746: 0xD173, //HANGUL SYLLABLE THIEUTH YEO RIEULPIEUP - 0xB747: 0xD174, //HANGUL SYLLABLE THIEUTH YEO RIEULSIOS - 0xB748: 0xD175, //HANGUL SYLLABLE THIEUTH YEO RIEULTHIEUTH - 0xB749: 0xD176, //HANGUL SYLLABLE THIEUTH YEO RIEULPHIEUPH - 0xB74A: 0xD177, //HANGUL SYLLABLE THIEUTH YEO RIEULHIEUH - 0xB74B: 0xD178, //HANGUL SYLLABLE THIEUTH YEO MIEUM - 0xB74C: 0xD179, //HANGUL SYLLABLE THIEUTH YEO PIEUP - 0xB74D: 0xD17A, //HANGUL SYLLABLE THIEUTH YEO PIEUPSIOS - 0xB74E: 0xD17B, //HANGUL SYLLABLE THIEUTH YEO SIOS - 0xB74F: 0xD17D, //HANGUL SYLLABLE THIEUTH YEO IEUNG - 0xB750: 0xD17E, //HANGUL SYLLABLE THIEUTH YEO CIEUC - 0xB751: 0xD17F, //HANGUL SYLLABLE THIEUTH YEO CHIEUCH - 0xB752: 0xD180, //HANGUL SYLLABLE THIEUTH YEO KHIEUKH - 0xB753: 0xD181, //HANGUL SYLLABLE THIEUTH YEO THIEUTH - 0xB754: 0xD182, //HANGUL SYLLABLE THIEUTH YEO PHIEUPH - 0xB755: 0xD183, //HANGUL SYLLABLE THIEUTH YEO HIEUH - 0xB756: 0xD185, //HANGUL SYLLABLE THIEUTH YE KIYEOK - 0xB757: 0xD186, //HANGUL SYLLABLE THIEUTH YE SSANGKIYEOK - 0xB758: 0xD187, //HANGUL SYLLABLE THIEUTH YE KIYEOKSIOS - 0xB759: 0xD189, //HANGUL SYLLABLE THIEUTH YE NIEUNCIEUC - 0xB75A: 0xD18A, //HANGUL SYLLABLE THIEUTH YE NIEUNHIEUH - 0xB761: 0xD18B, //HANGUL SYLLABLE THIEUTH YE TIKEUT - 0xB762: 0xD18C, //HANGUL SYLLABLE THIEUTH YE RIEUL - 0xB763: 0xD18D, //HANGUL SYLLABLE THIEUTH YE RIEULKIYEOK - 0xB764: 0xD18E, //HANGUL SYLLABLE THIEUTH YE RIEULMIEUM - 0xB765: 0xD18F, //HANGUL SYLLABLE THIEUTH YE RIEULPIEUP - 0xB766: 0xD190, //HANGUL SYLLABLE THIEUTH YE RIEULSIOS - 0xB767: 0xD191, //HANGUL SYLLABLE THIEUTH YE RIEULTHIEUTH - 0xB768: 0xD192, //HANGUL SYLLABLE THIEUTH YE RIEULPHIEUPH - 0xB769: 0xD193, //HANGUL SYLLABLE THIEUTH YE RIEULHIEUH - 0xB76A: 0xD194, //HANGUL SYLLABLE THIEUTH YE MIEUM - 0xB76B: 0xD195, //HANGUL SYLLABLE THIEUTH YE PIEUP - 0xB76C: 0xD196, //HANGUL SYLLABLE THIEUTH YE PIEUPSIOS - 0xB76D: 0xD197, //HANGUL SYLLABLE THIEUTH YE SIOS - 0xB76E: 0xD198, //HANGUL SYLLABLE THIEUTH YE SSANGSIOS - 0xB76F: 0xD199, //HANGUL SYLLABLE THIEUTH YE IEUNG - 0xB770: 0xD19A, //HANGUL SYLLABLE THIEUTH YE CIEUC - 0xB771: 0xD19B, //HANGUL SYLLABLE THIEUTH YE CHIEUCH - 0xB772: 0xD19C, //HANGUL SYLLABLE THIEUTH YE KHIEUKH - 0xB773: 0xD19D, //HANGUL SYLLABLE THIEUTH YE THIEUTH - 0xB774: 0xD19E, //HANGUL SYLLABLE THIEUTH YE PHIEUPH - 0xB775: 0xD19F, //HANGUL SYLLABLE THIEUTH YE HIEUH - 0xB776: 0xD1A2, //HANGUL SYLLABLE THIEUTH O SSANGKIYEOK - 0xB777: 0xD1A3, //HANGUL SYLLABLE THIEUTH O KIYEOKSIOS - 0xB778: 0xD1A5, //HANGUL SYLLABLE THIEUTH O NIEUNCIEUC - 0xB779: 0xD1A6, //HANGUL SYLLABLE THIEUTH O NIEUNHIEUH - 0xB77A: 0xD1A7, //HANGUL SYLLABLE THIEUTH O TIKEUT - 0xB781: 0xD1A9, //HANGUL SYLLABLE THIEUTH O RIEULKIYEOK - 0xB782: 0xD1AA, //HANGUL SYLLABLE THIEUTH O RIEULMIEUM - 0xB783: 0xD1AB, //HANGUL SYLLABLE THIEUTH O RIEULPIEUP - 0xB784: 0xD1AC, //HANGUL SYLLABLE THIEUTH O RIEULSIOS - 0xB785: 0xD1AD, //HANGUL SYLLABLE THIEUTH O RIEULTHIEUTH - 0xB786: 0xD1AE, //HANGUL SYLLABLE THIEUTH O RIEULPHIEUPH - 0xB787: 0xD1AF, //HANGUL SYLLABLE THIEUTH O RIEULHIEUH - 0xB788: 0xD1B2, //HANGUL SYLLABLE THIEUTH O PIEUPSIOS - 0xB789: 0xD1B4, //HANGUL SYLLABLE THIEUTH O SSANGSIOS - 0xB78A: 0xD1B6, //HANGUL SYLLABLE THIEUTH O CIEUC - 0xB78B: 0xD1B7, //HANGUL SYLLABLE THIEUTH O CHIEUCH - 0xB78C: 0xD1B8, //HANGUL SYLLABLE THIEUTH O KHIEUKH - 0xB78D: 0xD1B9, //HANGUL SYLLABLE THIEUTH O THIEUTH - 0xB78E: 0xD1BB, //HANGUL SYLLABLE THIEUTH O HIEUH - 0xB78F: 0xD1BD, //HANGUL SYLLABLE THIEUTH WA KIYEOK - 0xB790: 0xD1BE, //HANGUL SYLLABLE THIEUTH WA SSANGKIYEOK - 0xB791: 0xD1BF, //HANGUL SYLLABLE THIEUTH WA KIYEOKSIOS - 0xB792: 0xD1C1, //HANGUL SYLLABLE THIEUTH WA NIEUNCIEUC - 0xB793: 0xD1C2, //HANGUL SYLLABLE THIEUTH WA NIEUNHIEUH - 0xB794: 0xD1C3, //HANGUL SYLLABLE THIEUTH WA TIKEUT - 0xB795: 0xD1C4, //HANGUL SYLLABLE THIEUTH WA RIEUL - 0xB796: 0xD1C5, //HANGUL SYLLABLE THIEUTH WA RIEULKIYEOK - 0xB797: 0xD1C6, //HANGUL SYLLABLE THIEUTH WA RIEULMIEUM - 0xB798: 0xD1C7, //HANGUL SYLLABLE THIEUTH WA RIEULPIEUP - 0xB799: 0xD1C8, //HANGUL SYLLABLE THIEUTH WA RIEULSIOS - 0xB79A: 0xD1C9, //HANGUL SYLLABLE THIEUTH WA RIEULTHIEUTH - 0xB79B: 0xD1CA, //HANGUL SYLLABLE THIEUTH WA RIEULPHIEUPH - 0xB79C: 0xD1CB, //HANGUL SYLLABLE THIEUTH WA RIEULHIEUH - 0xB79D: 0xD1CC, //HANGUL SYLLABLE THIEUTH WA MIEUM - 0xB79E: 0xD1CD, //HANGUL SYLLABLE THIEUTH WA PIEUP - 0xB79F: 0xD1CE, //HANGUL SYLLABLE THIEUTH WA PIEUPSIOS - 0xB7A0: 0xD1CF, //HANGUL SYLLABLE THIEUTH WA SIOS - 0xB7A1: 0xB798, //HANGUL SYLLABLE RIEUL AE - 0xB7A2: 0xB799, //HANGUL SYLLABLE RIEUL AE KIYEOK - 0xB7A3: 0xB79C, //HANGUL SYLLABLE RIEUL AE NIEUN - 0xB7A4: 0xB7A0, //HANGUL SYLLABLE RIEUL AE RIEUL - 0xB7A5: 0xB7A8, //HANGUL SYLLABLE RIEUL AE MIEUM - 0xB7A6: 0xB7A9, //HANGUL SYLLABLE RIEUL AE PIEUP - 0xB7A7: 0xB7AB, //HANGUL SYLLABLE RIEUL AE SIOS - 0xB7A8: 0xB7AC, //HANGUL SYLLABLE RIEUL AE SSANGSIOS - 0xB7A9: 0xB7AD, //HANGUL SYLLABLE RIEUL AE IEUNG - 0xB7AA: 0xB7B4, //HANGUL SYLLABLE RIEUL YA - 0xB7AB: 0xB7B5, //HANGUL SYLLABLE RIEUL YA KIYEOK - 0xB7AC: 0xB7B8, //HANGUL SYLLABLE RIEUL YA NIEUN - 0xB7AD: 0xB7C7, //HANGUL SYLLABLE RIEUL YA SIOS - 0xB7AE: 0xB7C9, //HANGUL SYLLABLE RIEUL YA IEUNG - 0xB7AF: 0xB7EC, //HANGUL SYLLABLE RIEUL EO - 0xB7B0: 0xB7ED, //HANGUL SYLLABLE RIEUL EO KIYEOK - 0xB7B1: 0xB7F0, //HANGUL SYLLABLE RIEUL EO NIEUN - 0xB7B2: 0xB7F4, //HANGUL SYLLABLE RIEUL EO RIEUL - 0xB7B3: 0xB7FC, //HANGUL SYLLABLE RIEUL EO MIEUM - 0xB7B4: 0xB7FD, //HANGUL SYLLABLE RIEUL EO PIEUP - 0xB7B5: 0xB7FF, //HANGUL SYLLABLE RIEUL EO SIOS - 0xB7B6: 0xB800, //HANGUL SYLLABLE RIEUL EO SSANGSIOS - 0xB7B7: 0xB801, //HANGUL SYLLABLE RIEUL EO IEUNG - 0xB7B8: 0xB807, //HANGUL SYLLABLE RIEUL EO HIEUH - 0xB7B9: 0xB808, //HANGUL SYLLABLE RIEUL E - 0xB7BA: 0xB809, //HANGUL SYLLABLE RIEUL E KIYEOK - 0xB7BB: 0xB80C, //HANGUL SYLLABLE RIEUL E NIEUN - 0xB7BC: 0xB810, //HANGUL SYLLABLE RIEUL E RIEUL - 0xB7BD: 0xB818, //HANGUL SYLLABLE RIEUL E MIEUM - 0xB7BE: 0xB819, //HANGUL SYLLABLE RIEUL E PIEUP - 0xB7BF: 0xB81B, //HANGUL SYLLABLE RIEUL E SIOS - 0xB7C0: 0xB81D, //HANGUL SYLLABLE RIEUL E IEUNG - 0xB7C1: 0xB824, //HANGUL SYLLABLE RIEUL YEO - 0xB7C2: 0xB825, //HANGUL SYLLABLE RIEUL YEO KIYEOK - 0xB7C3: 0xB828, //HANGUL SYLLABLE RIEUL YEO NIEUN - 0xB7C4: 0xB82C, //HANGUL SYLLABLE RIEUL YEO RIEUL - 0xB7C5: 0xB834, //HANGUL SYLLABLE RIEUL YEO MIEUM - 0xB7C6: 0xB835, //HANGUL SYLLABLE RIEUL YEO PIEUP - 0xB7C7: 0xB837, //HANGUL SYLLABLE RIEUL YEO SIOS - 0xB7C8: 0xB838, //HANGUL SYLLABLE RIEUL YEO SSANGSIOS - 0xB7C9: 0xB839, //HANGUL SYLLABLE RIEUL YEO IEUNG - 0xB7CA: 0xB840, //HANGUL SYLLABLE RIEUL YE - 0xB7CB: 0xB844, //HANGUL SYLLABLE RIEUL YE NIEUN - 0xB7CC: 0xB851, //HANGUL SYLLABLE RIEUL YE PIEUP - 0xB7CD: 0xB853, //HANGUL SYLLABLE RIEUL YE SIOS - 0xB7CE: 0xB85C, //HANGUL SYLLABLE RIEUL O - 0xB7CF: 0xB85D, //HANGUL SYLLABLE RIEUL O KIYEOK - 0xB7D0: 0xB860, //HANGUL SYLLABLE RIEUL O NIEUN - 0xB7D1: 0xB864, //HANGUL SYLLABLE RIEUL O RIEUL - 0xB7D2: 0xB86C, //HANGUL SYLLABLE RIEUL O MIEUM - 0xB7D3: 0xB86D, //HANGUL SYLLABLE RIEUL O PIEUP - 0xB7D4: 0xB86F, //HANGUL SYLLABLE RIEUL O SIOS - 0xB7D5: 0xB871, //HANGUL SYLLABLE RIEUL O IEUNG - 0xB7D6: 0xB878, //HANGUL SYLLABLE RIEUL WA - 0xB7D7: 0xB87C, //HANGUL SYLLABLE RIEUL WA NIEUN - 0xB7D8: 0xB88D, //HANGUL SYLLABLE RIEUL WA IEUNG - 0xB7D9: 0xB8A8, //HANGUL SYLLABLE RIEUL WAE SSANGSIOS - 0xB7DA: 0xB8B0, //HANGUL SYLLABLE RIEUL OE - 0xB7DB: 0xB8B4, //HANGUL SYLLABLE RIEUL OE NIEUN - 0xB7DC: 0xB8B8, //HANGUL SYLLABLE RIEUL OE RIEUL - 0xB7DD: 0xB8C0, //HANGUL SYLLABLE RIEUL OE MIEUM - 0xB7DE: 0xB8C1, //HANGUL SYLLABLE RIEUL OE PIEUP - 0xB7DF: 0xB8C3, //HANGUL SYLLABLE RIEUL OE SIOS - 0xB7E0: 0xB8C5, //HANGUL SYLLABLE RIEUL OE IEUNG - 0xB7E1: 0xB8CC, //HANGUL SYLLABLE RIEUL YO - 0xB7E2: 0xB8D0, //HANGUL SYLLABLE RIEUL YO NIEUN - 0xB7E3: 0xB8D4, //HANGUL SYLLABLE RIEUL YO RIEUL - 0xB7E4: 0xB8DD, //HANGUL SYLLABLE RIEUL YO PIEUP - 0xB7E5: 0xB8DF, //HANGUL SYLLABLE RIEUL YO SIOS - 0xB7E6: 0xB8E1, //HANGUL SYLLABLE RIEUL YO IEUNG - 0xB7E7: 0xB8E8, //HANGUL SYLLABLE RIEUL U - 0xB7E8: 0xB8E9, //HANGUL SYLLABLE RIEUL U KIYEOK - 0xB7E9: 0xB8EC, //HANGUL SYLLABLE RIEUL U NIEUN - 0xB7EA: 0xB8F0, //HANGUL SYLLABLE RIEUL U RIEUL - 0xB7EB: 0xB8F8, //HANGUL SYLLABLE RIEUL U MIEUM - 0xB7EC: 0xB8F9, //HANGUL SYLLABLE RIEUL U PIEUP - 0xB7ED: 0xB8FB, //HANGUL SYLLABLE RIEUL U SIOS - 0xB7EE: 0xB8FD, //HANGUL SYLLABLE RIEUL U IEUNG - 0xB7EF: 0xB904, //HANGUL SYLLABLE RIEUL WEO - 0xB7F0: 0xB918, //HANGUL SYLLABLE RIEUL WEO SSANGSIOS - 0xB7F1: 0xB920, //HANGUL SYLLABLE RIEUL WE - 0xB7F2: 0xB93C, //HANGUL SYLLABLE RIEUL WI - 0xB7F3: 0xB93D, //HANGUL SYLLABLE RIEUL WI KIYEOK - 0xB7F4: 0xB940, //HANGUL SYLLABLE RIEUL WI NIEUN - 0xB7F5: 0xB944, //HANGUL SYLLABLE RIEUL WI RIEUL - 0xB7F6: 0xB94C, //HANGUL SYLLABLE RIEUL WI MIEUM - 0xB7F7: 0xB94F, //HANGUL SYLLABLE RIEUL WI SIOS - 0xB7F8: 0xB951, //HANGUL SYLLABLE RIEUL WI IEUNG - 0xB7F9: 0xB958, //HANGUL SYLLABLE RIEUL YU - 0xB7FA: 0xB959, //HANGUL SYLLABLE RIEUL YU KIYEOK - 0xB7FB: 0xB95C, //HANGUL SYLLABLE RIEUL YU NIEUN - 0xB7FC: 0xB960, //HANGUL SYLLABLE RIEUL YU RIEUL - 0xB7FD: 0xB968, //HANGUL SYLLABLE RIEUL YU MIEUM - 0xB7FE: 0xB969, //HANGUL SYLLABLE RIEUL YU PIEUP - 0xB841: 0xD1D0, //HANGUL SYLLABLE THIEUTH WA SSANGSIOS - 0xB842: 0xD1D1, //HANGUL SYLLABLE THIEUTH WA IEUNG - 0xB843: 0xD1D2, //HANGUL SYLLABLE THIEUTH WA CIEUC - 0xB844: 0xD1D3, //HANGUL SYLLABLE THIEUTH WA CHIEUCH - 0xB845: 0xD1D4, //HANGUL SYLLABLE THIEUTH WA KHIEUKH - 0xB846: 0xD1D5, //HANGUL SYLLABLE THIEUTH WA THIEUTH - 0xB847: 0xD1D6, //HANGUL SYLLABLE THIEUTH WA PHIEUPH - 0xB848: 0xD1D7, //HANGUL SYLLABLE THIEUTH WA HIEUH - 0xB849: 0xD1D9, //HANGUL SYLLABLE THIEUTH WAE KIYEOK - 0xB84A: 0xD1DA, //HANGUL SYLLABLE THIEUTH WAE SSANGKIYEOK - 0xB84B: 0xD1DB, //HANGUL SYLLABLE THIEUTH WAE KIYEOKSIOS - 0xB84C: 0xD1DC, //HANGUL SYLLABLE THIEUTH WAE NIEUN - 0xB84D: 0xD1DD, //HANGUL SYLLABLE THIEUTH WAE NIEUNCIEUC - 0xB84E: 0xD1DE, //HANGUL SYLLABLE THIEUTH WAE NIEUNHIEUH - 0xB84F: 0xD1DF, //HANGUL SYLLABLE THIEUTH WAE TIKEUT - 0xB850: 0xD1E0, //HANGUL SYLLABLE THIEUTH WAE RIEUL - 0xB851: 0xD1E1, //HANGUL SYLLABLE THIEUTH WAE RIEULKIYEOK - 0xB852: 0xD1E2, //HANGUL SYLLABLE THIEUTH WAE RIEULMIEUM - 0xB853: 0xD1E3, //HANGUL SYLLABLE THIEUTH WAE RIEULPIEUP - 0xB854: 0xD1E4, //HANGUL SYLLABLE THIEUTH WAE RIEULSIOS - 0xB855: 0xD1E5, //HANGUL SYLLABLE THIEUTH WAE RIEULTHIEUTH - 0xB856: 0xD1E6, //HANGUL SYLLABLE THIEUTH WAE RIEULPHIEUPH - 0xB857: 0xD1E7, //HANGUL SYLLABLE THIEUTH WAE RIEULHIEUH - 0xB858: 0xD1E8, //HANGUL SYLLABLE THIEUTH WAE MIEUM - 0xB859: 0xD1E9, //HANGUL SYLLABLE THIEUTH WAE PIEUP - 0xB85A: 0xD1EA, //HANGUL SYLLABLE THIEUTH WAE PIEUPSIOS - 0xB861: 0xD1EB, //HANGUL SYLLABLE THIEUTH WAE SIOS - 0xB862: 0xD1EC, //HANGUL SYLLABLE THIEUTH WAE SSANGSIOS - 0xB863: 0xD1ED, //HANGUL SYLLABLE THIEUTH WAE IEUNG - 0xB864: 0xD1EE, //HANGUL SYLLABLE THIEUTH WAE CIEUC - 0xB865: 0xD1EF, //HANGUL SYLLABLE THIEUTH WAE CHIEUCH - 0xB866: 0xD1F0, //HANGUL SYLLABLE THIEUTH WAE KHIEUKH - 0xB867: 0xD1F1, //HANGUL SYLLABLE THIEUTH WAE THIEUTH - 0xB868: 0xD1F2, //HANGUL SYLLABLE THIEUTH WAE PHIEUPH - 0xB869: 0xD1F3, //HANGUL SYLLABLE THIEUTH WAE HIEUH - 0xB86A: 0xD1F5, //HANGUL SYLLABLE THIEUTH OE KIYEOK - 0xB86B: 0xD1F6, //HANGUL SYLLABLE THIEUTH OE SSANGKIYEOK - 0xB86C: 0xD1F7, //HANGUL SYLLABLE THIEUTH OE KIYEOKSIOS - 0xB86D: 0xD1F9, //HANGUL SYLLABLE THIEUTH OE NIEUNCIEUC - 0xB86E: 0xD1FA, //HANGUL SYLLABLE THIEUTH OE NIEUNHIEUH - 0xB86F: 0xD1FB, //HANGUL SYLLABLE THIEUTH OE TIKEUT - 0xB870: 0xD1FC, //HANGUL SYLLABLE THIEUTH OE RIEUL - 0xB871: 0xD1FD, //HANGUL SYLLABLE THIEUTH OE RIEULKIYEOK - 0xB872: 0xD1FE, //HANGUL SYLLABLE THIEUTH OE RIEULMIEUM - 0xB873: 0xD1FF, //HANGUL SYLLABLE THIEUTH OE RIEULPIEUP - 0xB874: 0xD200, //HANGUL SYLLABLE THIEUTH OE RIEULSIOS - 0xB875: 0xD201, //HANGUL SYLLABLE THIEUTH OE RIEULTHIEUTH - 0xB876: 0xD202, //HANGUL SYLLABLE THIEUTH OE RIEULPHIEUPH - 0xB877: 0xD203, //HANGUL SYLLABLE THIEUTH OE RIEULHIEUH - 0xB878: 0xD204, //HANGUL SYLLABLE THIEUTH OE MIEUM - 0xB879: 0xD205, //HANGUL SYLLABLE THIEUTH OE PIEUP - 0xB87A: 0xD206, //HANGUL SYLLABLE THIEUTH OE PIEUPSIOS - 0xB881: 0xD208, //HANGUL SYLLABLE THIEUTH OE SSANGSIOS - 0xB882: 0xD20A, //HANGUL SYLLABLE THIEUTH OE CIEUC - 0xB883: 0xD20B, //HANGUL SYLLABLE THIEUTH OE CHIEUCH - 0xB884: 0xD20C, //HANGUL SYLLABLE THIEUTH OE KHIEUKH - 0xB885: 0xD20D, //HANGUL SYLLABLE THIEUTH OE THIEUTH - 0xB886: 0xD20E, //HANGUL SYLLABLE THIEUTH OE PHIEUPH - 0xB887: 0xD20F, //HANGUL SYLLABLE THIEUTH OE HIEUH - 0xB888: 0xD211, //HANGUL SYLLABLE THIEUTH YO KIYEOK - 0xB889: 0xD212, //HANGUL SYLLABLE THIEUTH YO SSANGKIYEOK - 0xB88A: 0xD213, //HANGUL SYLLABLE THIEUTH YO KIYEOKSIOS - 0xB88B: 0xD214, //HANGUL SYLLABLE THIEUTH YO NIEUN - 0xB88C: 0xD215, //HANGUL SYLLABLE THIEUTH YO NIEUNCIEUC - 0xB88D: 0xD216, //HANGUL SYLLABLE THIEUTH YO NIEUNHIEUH - 0xB88E: 0xD217, //HANGUL SYLLABLE THIEUTH YO TIKEUT - 0xB88F: 0xD218, //HANGUL SYLLABLE THIEUTH YO RIEUL - 0xB890: 0xD219, //HANGUL SYLLABLE THIEUTH YO RIEULKIYEOK - 0xB891: 0xD21A, //HANGUL SYLLABLE THIEUTH YO RIEULMIEUM - 0xB892: 0xD21B, //HANGUL SYLLABLE THIEUTH YO RIEULPIEUP - 0xB893: 0xD21C, //HANGUL SYLLABLE THIEUTH YO RIEULSIOS - 0xB894: 0xD21D, //HANGUL SYLLABLE THIEUTH YO RIEULTHIEUTH - 0xB895: 0xD21E, //HANGUL SYLLABLE THIEUTH YO RIEULPHIEUPH - 0xB896: 0xD21F, //HANGUL SYLLABLE THIEUTH YO RIEULHIEUH - 0xB897: 0xD220, //HANGUL SYLLABLE THIEUTH YO MIEUM - 0xB898: 0xD221, //HANGUL SYLLABLE THIEUTH YO PIEUP - 0xB899: 0xD222, //HANGUL SYLLABLE THIEUTH YO PIEUPSIOS - 0xB89A: 0xD223, //HANGUL SYLLABLE THIEUTH YO SIOS - 0xB89B: 0xD224, //HANGUL SYLLABLE THIEUTH YO SSANGSIOS - 0xB89C: 0xD225, //HANGUL SYLLABLE THIEUTH YO IEUNG - 0xB89D: 0xD226, //HANGUL SYLLABLE THIEUTH YO CIEUC - 0xB89E: 0xD227, //HANGUL SYLLABLE THIEUTH YO CHIEUCH - 0xB89F: 0xD228, //HANGUL SYLLABLE THIEUTH YO KHIEUKH - 0xB8A0: 0xD229, //HANGUL SYLLABLE THIEUTH YO THIEUTH - 0xB8A1: 0xB96B, //HANGUL SYLLABLE RIEUL YU SIOS - 0xB8A2: 0xB96D, //HANGUL SYLLABLE RIEUL YU IEUNG - 0xB8A3: 0xB974, //HANGUL SYLLABLE RIEUL EU - 0xB8A4: 0xB975, //HANGUL SYLLABLE RIEUL EU KIYEOK - 0xB8A5: 0xB978, //HANGUL SYLLABLE RIEUL EU NIEUN - 0xB8A6: 0xB97C, //HANGUL SYLLABLE RIEUL EU RIEUL - 0xB8A7: 0xB984, //HANGUL SYLLABLE RIEUL EU MIEUM - 0xB8A8: 0xB985, //HANGUL SYLLABLE RIEUL EU PIEUP - 0xB8A9: 0xB987, //HANGUL SYLLABLE RIEUL EU SIOS - 0xB8AA: 0xB989, //HANGUL SYLLABLE RIEUL EU IEUNG - 0xB8AB: 0xB98A, //HANGUL SYLLABLE RIEUL EU CIEUC - 0xB8AC: 0xB98D, //HANGUL SYLLABLE RIEUL EU THIEUTH - 0xB8AD: 0xB98E, //HANGUL SYLLABLE RIEUL EU PHIEUPH - 0xB8AE: 0xB9AC, //HANGUL SYLLABLE RIEUL I - 0xB8AF: 0xB9AD, //HANGUL SYLLABLE RIEUL I KIYEOK - 0xB8B0: 0xB9B0, //HANGUL SYLLABLE RIEUL I NIEUN - 0xB8B1: 0xB9B4, //HANGUL SYLLABLE RIEUL I RIEUL - 0xB8B2: 0xB9BC, //HANGUL SYLLABLE RIEUL I MIEUM - 0xB8B3: 0xB9BD, //HANGUL SYLLABLE RIEUL I PIEUP - 0xB8B4: 0xB9BF, //HANGUL SYLLABLE RIEUL I SIOS - 0xB8B5: 0xB9C1, //HANGUL SYLLABLE RIEUL I IEUNG - 0xB8B6: 0xB9C8, //HANGUL SYLLABLE MIEUM A - 0xB8B7: 0xB9C9, //HANGUL SYLLABLE MIEUM A KIYEOK - 0xB8B8: 0xB9CC, //HANGUL SYLLABLE MIEUM A NIEUN - 0xB8B9: 0xB9CE, //HANGUL SYLLABLE MIEUM A NIEUNHIEUH - 0xB8BA: 0xB9CF, //HANGUL SYLLABLE MIEUM A TIKEUT - 0xB8BB: 0xB9D0, //HANGUL SYLLABLE MIEUM A RIEUL - 0xB8BC: 0xB9D1, //HANGUL SYLLABLE MIEUM A RIEULKIYEOK - 0xB8BD: 0xB9D2, //HANGUL SYLLABLE MIEUM A RIEULMIEUM - 0xB8BE: 0xB9D8, //HANGUL SYLLABLE MIEUM A MIEUM - 0xB8BF: 0xB9D9, //HANGUL SYLLABLE MIEUM A PIEUP - 0xB8C0: 0xB9DB, //HANGUL SYLLABLE MIEUM A SIOS - 0xB8C1: 0xB9DD, //HANGUL SYLLABLE MIEUM A IEUNG - 0xB8C2: 0xB9DE, //HANGUL SYLLABLE MIEUM A CIEUC - 0xB8C3: 0xB9E1, //HANGUL SYLLABLE MIEUM A THIEUTH - 0xB8C4: 0xB9E3, //HANGUL SYLLABLE MIEUM A HIEUH - 0xB8C5: 0xB9E4, //HANGUL SYLLABLE MIEUM AE - 0xB8C6: 0xB9E5, //HANGUL SYLLABLE MIEUM AE KIYEOK - 0xB8C7: 0xB9E8, //HANGUL SYLLABLE MIEUM AE NIEUN - 0xB8C8: 0xB9EC, //HANGUL SYLLABLE MIEUM AE RIEUL - 0xB8C9: 0xB9F4, //HANGUL SYLLABLE MIEUM AE MIEUM - 0xB8CA: 0xB9F5, //HANGUL SYLLABLE MIEUM AE PIEUP - 0xB8CB: 0xB9F7, //HANGUL SYLLABLE MIEUM AE SIOS - 0xB8CC: 0xB9F8, //HANGUL SYLLABLE MIEUM AE SSANGSIOS - 0xB8CD: 0xB9F9, //HANGUL SYLLABLE MIEUM AE IEUNG - 0xB8CE: 0xB9FA, //HANGUL SYLLABLE MIEUM AE CIEUC - 0xB8CF: 0xBA00, //HANGUL SYLLABLE MIEUM YA - 0xB8D0: 0xBA01, //HANGUL SYLLABLE MIEUM YA KIYEOK - 0xB8D1: 0xBA08, //HANGUL SYLLABLE MIEUM YA RIEUL - 0xB8D2: 0xBA15, //HANGUL SYLLABLE MIEUM YA IEUNG - 0xB8D3: 0xBA38, //HANGUL SYLLABLE MIEUM EO - 0xB8D4: 0xBA39, //HANGUL SYLLABLE MIEUM EO KIYEOK - 0xB8D5: 0xBA3C, //HANGUL SYLLABLE MIEUM EO NIEUN - 0xB8D6: 0xBA40, //HANGUL SYLLABLE MIEUM EO RIEUL - 0xB8D7: 0xBA42, //HANGUL SYLLABLE MIEUM EO RIEULMIEUM - 0xB8D8: 0xBA48, //HANGUL SYLLABLE MIEUM EO MIEUM - 0xB8D9: 0xBA49, //HANGUL SYLLABLE MIEUM EO PIEUP - 0xB8DA: 0xBA4B, //HANGUL SYLLABLE MIEUM EO SIOS - 0xB8DB: 0xBA4D, //HANGUL SYLLABLE MIEUM EO IEUNG - 0xB8DC: 0xBA4E, //HANGUL SYLLABLE MIEUM EO CIEUC - 0xB8DD: 0xBA53, //HANGUL SYLLABLE MIEUM EO HIEUH - 0xB8DE: 0xBA54, //HANGUL SYLLABLE MIEUM E - 0xB8DF: 0xBA55, //HANGUL SYLLABLE MIEUM E KIYEOK - 0xB8E0: 0xBA58, //HANGUL SYLLABLE MIEUM E NIEUN - 0xB8E1: 0xBA5C, //HANGUL SYLLABLE MIEUM E RIEUL - 0xB8E2: 0xBA64, //HANGUL SYLLABLE MIEUM E MIEUM - 0xB8E3: 0xBA65, //HANGUL SYLLABLE MIEUM E PIEUP - 0xB8E4: 0xBA67, //HANGUL SYLLABLE MIEUM E SIOS - 0xB8E5: 0xBA68, //HANGUL SYLLABLE MIEUM E SSANGSIOS - 0xB8E6: 0xBA69, //HANGUL SYLLABLE MIEUM E IEUNG - 0xB8E7: 0xBA70, //HANGUL SYLLABLE MIEUM YEO - 0xB8E8: 0xBA71, //HANGUL SYLLABLE MIEUM YEO KIYEOK - 0xB8E9: 0xBA74, //HANGUL SYLLABLE MIEUM YEO NIEUN - 0xB8EA: 0xBA78, //HANGUL SYLLABLE MIEUM YEO RIEUL - 0xB8EB: 0xBA83, //HANGUL SYLLABLE MIEUM YEO SIOS - 0xB8EC: 0xBA84, //HANGUL SYLLABLE MIEUM YEO SSANGSIOS - 0xB8ED: 0xBA85, //HANGUL SYLLABLE MIEUM YEO IEUNG - 0xB8EE: 0xBA87, //HANGUL SYLLABLE MIEUM YEO CHIEUCH - 0xB8EF: 0xBA8C, //HANGUL SYLLABLE MIEUM YE - 0xB8F0: 0xBAA8, //HANGUL SYLLABLE MIEUM O - 0xB8F1: 0xBAA9, //HANGUL SYLLABLE MIEUM O KIYEOK - 0xB8F2: 0xBAAB, //HANGUL SYLLABLE MIEUM O KIYEOKSIOS - 0xB8F3: 0xBAAC, //HANGUL SYLLABLE MIEUM O NIEUN - 0xB8F4: 0xBAB0, //HANGUL SYLLABLE MIEUM O RIEUL - 0xB8F5: 0xBAB2, //HANGUL SYLLABLE MIEUM O RIEULMIEUM - 0xB8F6: 0xBAB8, //HANGUL SYLLABLE MIEUM O MIEUM - 0xB8F7: 0xBAB9, //HANGUL SYLLABLE MIEUM O PIEUP - 0xB8F8: 0xBABB, //HANGUL SYLLABLE MIEUM O SIOS - 0xB8F9: 0xBABD, //HANGUL SYLLABLE MIEUM O IEUNG - 0xB8FA: 0xBAC4, //HANGUL SYLLABLE MIEUM WA - 0xB8FB: 0xBAC8, //HANGUL SYLLABLE MIEUM WA NIEUN - 0xB8FC: 0xBAD8, //HANGUL SYLLABLE MIEUM WA SSANGSIOS - 0xB8FD: 0xBAD9, //HANGUL SYLLABLE MIEUM WA IEUNG - 0xB8FE: 0xBAFC, //HANGUL SYLLABLE MIEUM OE - 0xB941: 0xD22A, //HANGUL SYLLABLE THIEUTH YO PHIEUPH - 0xB942: 0xD22B, //HANGUL SYLLABLE THIEUTH YO HIEUH - 0xB943: 0xD22E, //HANGUL SYLLABLE THIEUTH U SSANGKIYEOK - 0xB944: 0xD22F, //HANGUL SYLLABLE THIEUTH U KIYEOKSIOS - 0xB945: 0xD231, //HANGUL SYLLABLE THIEUTH U NIEUNCIEUC - 0xB946: 0xD232, //HANGUL SYLLABLE THIEUTH U NIEUNHIEUH - 0xB947: 0xD233, //HANGUL SYLLABLE THIEUTH U TIKEUT - 0xB948: 0xD235, //HANGUL SYLLABLE THIEUTH U RIEULKIYEOK - 0xB949: 0xD236, //HANGUL SYLLABLE THIEUTH U RIEULMIEUM - 0xB94A: 0xD237, //HANGUL SYLLABLE THIEUTH U RIEULPIEUP - 0xB94B: 0xD238, //HANGUL SYLLABLE THIEUTH U RIEULSIOS - 0xB94C: 0xD239, //HANGUL SYLLABLE THIEUTH U RIEULTHIEUTH - 0xB94D: 0xD23A, //HANGUL SYLLABLE THIEUTH U RIEULPHIEUPH - 0xB94E: 0xD23B, //HANGUL SYLLABLE THIEUTH U RIEULHIEUH - 0xB94F: 0xD23E, //HANGUL SYLLABLE THIEUTH U PIEUPSIOS - 0xB950: 0xD240, //HANGUL SYLLABLE THIEUTH U SSANGSIOS - 0xB951: 0xD242, //HANGUL SYLLABLE THIEUTH U CIEUC - 0xB952: 0xD243, //HANGUL SYLLABLE THIEUTH U CHIEUCH - 0xB953: 0xD244, //HANGUL SYLLABLE THIEUTH U KHIEUKH - 0xB954: 0xD245, //HANGUL SYLLABLE THIEUTH U THIEUTH - 0xB955: 0xD246, //HANGUL SYLLABLE THIEUTH U PHIEUPH - 0xB956: 0xD247, //HANGUL SYLLABLE THIEUTH U HIEUH - 0xB957: 0xD249, //HANGUL SYLLABLE THIEUTH WEO KIYEOK - 0xB958: 0xD24A, //HANGUL SYLLABLE THIEUTH WEO SSANGKIYEOK - 0xB959: 0xD24B, //HANGUL SYLLABLE THIEUTH WEO KIYEOKSIOS - 0xB95A: 0xD24C, //HANGUL SYLLABLE THIEUTH WEO NIEUN - 0xB961: 0xD24D, //HANGUL SYLLABLE THIEUTH WEO NIEUNCIEUC - 0xB962: 0xD24E, //HANGUL SYLLABLE THIEUTH WEO NIEUNHIEUH - 0xB963: 0xD24F, //HANGUL SYLLABLE THIEUTH WEO TIKEUT - 0xB964: 0xD250, //HANGUL SYLLABLE THIEUTH WEO RIEUL - 0xB965: 0xD251, //HANGUL SYLLABLE THIEUTH WEO RIEULKIYEOK - 0xB966: 0xD252, //HANGUL SYLLABLE THIEUTH WEO RIEULMIEUM - 0xB967: 0xD253, //HANGUL SYLLABLE THIEUTH WEO RIEULPIEUP - 0xB968: 0xD254, //HANGUL SYLLABLE THIEUTH WEO RIEULSIOS - 0xB969: 0xD255, //HANGUL SYLLABLE THIEUTH WEO RIEULTHIEUTH - 0xB96A: 0xD256, //HANGUL SYLLABLE THIEUTH WEO RIEULPHIEUPH - 0xB96B: 0xD257, //HANGUL SYLLABLE THIEUTH WEO RIEULHIEUH - 0xB96C: 0xD258, //HANGUL SYLLABLE THIEUTH WEO MIEUM - 0xB96D: 0xD259, //HANGUL SYLLABLE THIEUTH WEO PIEUP - 0xB96E: 0xD25A, //HANGUL SYLLABLE THIEUTH WEO PIEUPSIOS - 0xB96F: 0xD25B, //HANGUL SYLLABLE THIEUTH WEO SIOS - 0xB970: 0xD25D, //HANGUL SYLLABLE THIEUTH WEO IEUNG - 0xB971: 0xD25E, //HANGUL SYLLABLE THIEUTH WEO CIEUC - 0xB972: 0xD25F, //HANGUL SYLLABLE THIEUTH WEO CHIEUCH - 0xB973: 0xD260, //HANGUL SYLLABLE THIEUTH WEO KHIEUKH - 0xB974: 0xD261, //HANGUL SYLLABLE THIEUTH WEO THIEUTH - 0xB975: 0xD262, //HANGUL SYLLABLE THIEUTH WEO PHIEUPH - 0xB976: 0xD263, //HANGUL SYLLABLE THIEUTH WEO HIEUH - 0xB977: 0xD265, //HANGUL SYLLABLE THIEUTH WE KIYEOK - 0xB978: 0xD266, //HANGUL SYLLABLE THIEUTH WE SSANGKIYEOK - 0xB979: 0xD267, //HANGUL SYLLABLE THIEUTH WE KIYEOKSIOS - 0xB97A: 0xD268, //HANGUL SYLLABLE THIEUTH WE NIEUN - 0xB981: 0xD269, //HANGUL SYLLABLE THIEUTH WE NIEUNCIEUC - 0xB982: 0xD26A, //HANGUL SYLLABLE THIEUTH WE NIEUNHIEUH - 0xB983: 0xD26B, //HANGUL SYLLABLE THIEUTH WE TIKEUT - 0xB984: 0xD26C, //HANGUL SYLLABLE THIEUTH WE RIEUL - 0xB985: 0xD26D, //HANGUL SYLLABLE THIEUTH WE RIEULKIYEOK - 0xB986: 0xD26E, //HANGUL SYLLABLE THIEUTH WE RIEULMIEUM - 0xB987: 0xD26F, //HANGUL SYLLABLE THIEUTH WE RIEULPIEUP - 0xB988: 0xD270, //HANGUL SYLLABLE THIEUTH WE RIEULSIOS - 0xB989: 0xD271, //HANGUL SYLLABLE THIEUTH WE RIEULTHIEUTH - 0xB98A: 0xD272, //HANGUL SYLLABLE THIEUTH WE RIEULPHIEUPH - 0xB98B: 0xD273, //HANGUL SYLLABLE THIEUTH WE RIEULHIEUH - 0xB98C: 0xD274, //HANGUL SYLLABLE THIEUTH WE MIEUM - 0xB98D: 0xD275, //HANGUL SYLLABLE THIEUTH WE PIEUP - 0xB98E: 0xD276, //HANGUL SYLLABLE THIEUTH WE PIEUPSIOS - 0xB98F: 0xD277, //HANGUL SYLLABLE THIEUTH WE SIOS - 0xB990: 0xD278, //HANGUL SYLLABLE THIEUTH WE SSANGSIOS - 0xB991: 0xD279, //HANGUL SYLLABLE THIEUTH WE IEUNG - 0xB992: 0xD27A, //HANGUL SYLLABLE THIEUTH WE CIEUC - 0xB993: 0xD27B, //HANGUL SYLLABLE THIEUTH WE CHIEUCH - 0xB994: 0xD27C, //HANGUL SYLLABLE THIEUTH WE KHIEUKH - 0xB995: 0xD27D, //HANGUL SYLLABLE THIEUTH WE THIEUTH - 0xB996: 0xD27E, //HANGUL SYLLABLE THIEUTH WE PHIEUPH - 0xB997: 0xD27F, //HANGUL SYLLABLE THIEUTH WE HIEUH - 0xB998: 0xD282, //HANGUL SYLLABLE THIEUTH WI SSANGKIYEOK - 0xB999: 0xD283, //HANGUL SYLLABLE THIEUTH WI KIYEOKSIOS - 0xB99A: 0xD285, //HANGUL SYLLABLE THIEUTH WI NIEUNCIEUC - 0xB99B: 0xD286, //HANGUL SYLLABLE THIEUTH WI NIEUNHIEUH - 0xB99C: 0xD287, //HANGUL SYLLABLE THIEUTH WI TIKEUT - 0xB99D: 0xD289, //HANGUL SYLLABLE THIEUTH WI RIEULKIYEOK - 0xB99E: 0xD28A, //HANGUL SYLLABLE THIEUTH WI RIEULMIEUM - 0xB99F: 0xD28B, //HANGUL SYLLABLE THIEUTH WI RIEULPIEUP - 0xB9A0: 0xD28C, //HANGUL SYLLABLE THIEUTH WI RIEULSIOS - 0xB9A1: 0xBB00, //HANGUL SYLLABLE MIEUM OE NIEUN - 0xB9A2: 0xBB04, //HANGUL SYLLABLE MIEUM OE RIEUL - 0xB9A3: 0xBB0D, //HANGUL SYLLABLE MIEUM OE PIEUP - 0xB9A4: 0xBB0F, //HANGUL SYLLABLE MIEUM OE SIOS - 0xB9A5: 0xBB11, //HANGUL SYLLABLE MIEUM OE IEUNG - 0xB9A6: 0xBB18, //HANGUL SYLLABLE MIEUM YO - 0xB9A7: 0xBB1C, //HANGUL SYLLABLE MIEUM YO NIEUN - 0xB9A8: 0xBB20, //HANGUL SYLLABLE MIEUM YO RIEUL - 0xB9A9: 0xBB29, //HANGUL SYLLABLE MIEUM YO PIEUP - 0xB9AA: 0xBB2B, //HANGUL SYLLABLE MIEUM YO SIOS - 0xB9AB: 0xBB34, //HANGUL SYLLABLE MIEUM U - 0xB9AC: 0xBB35, //HANGUL SYLLABLE MIEUM U KIYEOK - 0xB9AD: 0xBB36, //HANGUL SYLLABLE MIEUM U SSANGKIYEOK - 0xB9AE: 0xBB38, //HANGUL SYLLABLE MIEUM U NIEUN - 0xB9AF: 0xBB3B, //HANGUL SYLLABLE MIEUM U TIKEUT - 0xB9B0: 0xBB3C, //HANGUL SYLLABLE MIEUM U RIEUL - 0xB9B1: 0xBB3D, //HANGUL SYLLABLE MIEUM U RIEULKIYEOK - 0xB9B2: 0xBB3E, //HANGUL SYLLABLE MIEUM U RIEULMIEUM - 0xB9B3: 0xBB44, //HANGUL SYLLABLE MIEUM U MIEUM - 0xB9B4: 0xBB45, //HANGUL SYLLABLE MIEUM U PIEUP - 0xB9B5: 0xBB47, //HANGUL SYLLABLE MIEUM U SIOS - 0xB9B6: 0xBB49, //HANGUL SYLLABLE MIEUM U IEUNG - 0xB9B7: 0xBB4D, //HANGUL SYLLABLE MIEUM U THIEUTH - 0xB9B8: 0xBB4F, //HANGUL SYLLABLE MIEUM U HIEUH - 0xB9B9: 0xBB50, //HANGUL SYLLABLE MIEUM WEO - 0xB9BA: 0xBB54, //HANGUL SYLLABLE MIEUM WEO NIEUN - 0xB9BB: 0xBB58, //HANGUL SYLLABLE MIEUM WEO RIEUL - 0xB9BC: 0xBB61, //HANGUL SYLLABLE MIEUM WEO PIEUP - 0xB9BD: 0xBB63, //HANGUL SYLLABLE MIEUM WEO SIOS - 0xB9BE: 0xBB6C, //HANGUL SYLLABLE MIEUM WE - 0xB9BF: 0xBB88, //HANGUL SYLLABLE MIEUM WI - 0xB9C0: 0xBB8C, //HANGUL SYLLABLE MIEUM WI NIEUN - 0xB9C1: 0xBB90, //HANGUL SYLLABLE MIEUM WI RIEUL - 0xB9C2: 0xBBA4, //HANGUL SYLLABLE MIEUM YU - 0xB9C3: 0xBBA8, //HANGUL SYLLABLE MIEUM YU NIEUN - 0xB9C4: 0xBBAC, //HANGUL SYLLABLE MIEUM YU RIEUL - 0xB9C5: 0xBBB4, //HANGUL SYLLABLE MIEUM YU MIEUM - 0xB9C6: 0xBBB7, //HANGUL SYLLABLE MIEUM YU SIOS - 0xB9C7: 0xBBC0, //HANGUL SYLLABLE MIEUM EU - 0xB9C8: 0xBBC4, //HANGUL SYLLABLE MIEUM EU NIEUN - 0xB9C9: 0xBBC8, //HANGUL SYLLABLE MIEUM EU RIEUL - 0xB9CA: 0xBBD0, //HANGUL SYLLABLE MIEUM EU MIEUM - 0xB9CB: 0xBBD3, //HANGUL SYLLABLE MIEUM EU SIOS - 0xB9CC: 0xBBF8, //HANGUL SYLLABLE MIEUM I - 0xB9CD: 0xBBF9, //HANGUL SYLLABLE MIEUM I KIYEOK - 0xB9CE: 0xBBFC, //HANGUL SYLLABLE MIEUM I NIEUN - 0xB9CF: 0xBBFF, //HANGUL SYLLABLE MIEUM I TIKEUT - 0xB9D0: 0xBC00, //HANGUL SYLLABLE MIEUM I RIEUL - 0xB9D1: 0xBC02, //HANGUL SYLLABLE MIEUM I RIEULMIEUM - 0xB9D2: 0xBC08, //HANGUL SYLLABLE MIEUM I MIEUM - 0xB9D3: 0xBC09, //HANGUL SYLLABLE MIEUM I PIEUP - 0xB9D4: 0xBC0B, //HANGUL SYLLABLE MIEUM I SIOS - 0xB9D5: 0xBC0C, //HANGUL SYLLABLE MIEUM I SSANGSIOS - 0xB9D6: 0xBC0D, //HANGUL SYLLABLE MIEUM I IEUNG - 0xB9D7: 0xBC0F, //HANGUL SYLLABLE MIEUM I CHIEUCH - 0xB9D8: 0xBC11, //HANGUL SYLLABLE MIEUM I THIEUTH - 0xB9D9: 0xBC14, //HANGUL SYLLABLE PIEUP A - 0xB9DA: 0xBC15, //HANGUL SYLLABLE PIEUP A KIYEOK - 0xB9DB: 0xBC16, //HANGUL SYLLABLE PIEUP A SSANGKIYEOK - 0xB9DC: 0xBC17, //HANGUL SYLLABLE PIEUP A KIYEOKSIOS - 0xB9DD: 0xBC18, //HANGUL SYLLABLE PIEUP A NIEUN - 0xB9DE: 0xBC1B, //HANGUL SYLLABLE PIEUP A TIKEUT - 0xB9DF: 0xBC1C, //HANGUL SYLLABLE PIEUP A RIEUL - 0xB9E0: 0xBC1D, //HANGUL SYLLABLE PIEUP A RIEULKIYEOK - 0xB9E1: 0xBC1E, //HANGUL SYLLABLE PIEUP A RIEULMIEUM - 0xB9E2: 0xBC1F, //HANGUL SYLLABLE PIEUP A RIEULPIEUP - 0xB9E3: 0xBC24, //HANGUL SYLLABLE PIEUP A MIEUM - 0xB9E4: 0xBC25, //HANGUL SYLLABLE PIEUP A PIEUP - 0xB9E5: 0xBC27, //HANGUL SYLLABLE PIEUP A SIOS - 0xB9E6: 0xBC29, //HANGUL SYLLABLE PIEUP A IEUNG - 0xB9E7: 0xBC2D, //HANGUL SYLLABLE PIEUP A THIEUTH - 0xB9E8: 0xBC30, //HANGUL SYLLABLE PIEUP AE - 0xB9E9: 0xBC31, //HANGUL SYLLABLE PIEUP AE KIYEOK - 0xB9EA: 0xBC34, //HANGUL SYLLABLE PIEUP AE NIEUN - 0xB9EB: 0xBC38, //HANGUL SYLLABLE PIEUP AE RIEUL - 0xB9EC: 0xBC40, //HANGUL SYLLABLE PIEUP AE MIEUM - 0xB9ED: 0xBC41, //HANGUL SYLLABLE PIEUP AE PIEUP - 0xB9EE: 0xBC43, //HANGUL SYLLABLE PIEUP AE SIOS - 0xB9EF: 0xBC44, //HANGUL SYLLABLE PIEUP AE SSANGSIOS - 0xB9F0: 0xBC45, //HANGUL SYLLABLE PIEUP AE IEUNG - 0xB9F1: 0xBC49, //HANGUL SYLLABLE PIEUP AE THIEUTH - 0xB9F2: 0xBC4C, //HANGUL SYLLABLE PIEUP YA - 0xB9F3: 0xBC4D, //HANGUL SYLLABLE PIEUP YA KIYEOK - 0xB9F4: 0xBC50, //HANGUL SYLLABLE PIEUP YA NIEUN - 0xB9F5: 0xBC5D, //HANGUL SYLLABLE PIEUP YA PIEUP - 0xB9F6: 0xBC84, //HANGUL SYLLABLE PIEUP EO - 0xB9F7: 0xBC85, //HANGUL SYLLABLE PIEUP EO KIYEOK - 0xB9F8: 0xBC88, //HANGUL SYLLABLE PIEUP EO NIEUN - 0xB9F9: 0xBC8B, //HANGUL SYLLABLE PIEUP EO TIKEUT - 0xB9FA: 0xBC8C, //HANGUL SYLLABLE PIEUP EO RIEUL - 0xB9FB: 0xBC8E, //HANGUL SYLLABLE PIEUP EO RIEULMIEUM - 0xB9FC: 0xBC94, //HANGUL SYLLABLE PIEUP EO MIEUM - 0xB9FD: 0xBC95, //HANGUL SYLLABLE PIEUP EO PIEUP - 0xB9FE: 0xBC97, //HANGUL SYLLABLE PIEUP EO SIOS - 0xBA41: 0xD28D, //HANGUL SYLLABLE THIEUTH WI RIEULTHIEUTH - 0xBA42: 0xD28E, //HANGUL SYLLABLE THIEUTH WI RIEULPHIEUPH - 0xBA43: 0xD28F, //HANGUL SYLLABLE THIEUTH WI RIEULHIEUH - 0xBA44: 0xD292, //HANGUL SYLLABLE THIEUTH WI PIEUPSIOS - 0xBA45: 0xD293, //HANGUL SYLLABLE THIEUTH WI SIOS - 0xBA46: 0xD294, //HANGUL SYLLABLE THIEUTH WI SSANGSIOS - 0xBA47: 0xD296, //HANGUL SYLLABLE THIEUTH WI CIEUC - 0xBA48: 0xD297, //HANGUL SYLLABLE THIEUTH WI CHIEUCH - 0xBA49: 0xD298, //HANGUL SYLLABLE THIEUTH WI KHIEUKH - 0xBA4A: 0xD299, //HANGUL SYLLABLE THIEUTH WI THIEUTH - 0xBA4B: 0xD29A, //HANGUL SYLLABLE THIEUTH WI PHIEUPH - 0xBA4C: 0xD29B, //HANGUL SYLLABLE THIEUTH WI HIEUH - 0xBA4D: 0xD29D, //HANGUL SYLLABLE THIEUTH YU KIYEOK - 0xBA4E: 0xD29E, //HANGUL SYLLABLE THIEUTH YU SSANGKIYEOK - 0xBA4F: 0xD29F, //HANGUL SYLLABLE THIEUTH YU KIYEOKSIOS - 0xBA50: 0xD2A1, //HANGUL SYLLABLE THIEUTH YU NIEUNCIEUC - 0xBA51: 0xD2A2, //HANGUL SYLLABLE THIEUTH YU NIEUNHIEUH - 0xBA52: 0xD2A3, //HANGUL SYLLABLE THIEUTH YU TIKEUT - 0xBA53: 0xD2A5, //HANGUL SYLLABLE THIEUTH YU RIEULKIYEOK - 0xBA54: 0xD2A6, //HANGUL SYLLABLE THIEUTH YU RIEULMIEUM - 0xBA55: 0xD2A7, //HANGUL SYLLABLE THIEUTH YU RIEULPIEUP - 0xBA56: 0xD2A8, //HANGUL SYLLABLE THIEUTH YU RIEULSIOS - 0xBA57: 0xD2A9, //HANGUL SYLLABLE THIEUTH YU RIEULTHIEUTH - 0xBA58: 0xD2AA, //HANGUL SYLLABLE THIEUTH YU RIEULPHIEUPH - 0xBA59: 0xD2AB, //HANGUL SYLLABLE THIEUTH YU RIEULHIEUH - 0xBA5A: 0xD2AD, //HANGUL SYLLABLE THIEUTH YU PIEUP - 0xBA61: 0xD2AE, //HANGUL SYLLABLE THIEUTH YU PIEUPSIOS - 0xBA62: 0xD2AF, //HANGUL SYLLABLE THIEUTH YU SIOS - 0xBA63: 0xD2B0, //HANGUL SYLLABLE THIEUTH YU SSANGSIOS - 0xBA64: 0xD2B2, //HANGUL SYLLABLE THIEUTH YU CIEUC - 0xBA65: 0xD2B3, //HANGUL SYLLABLE THIEUTH YU CHIEUCH - 0xBA66: 0xD2B4, //HANGUL SYLLABLE THIEUTH YU KHIEUKH - 0xBA67: 0xD2B5, //HANGUL SYLLABLE THIEUTH YU THIEUTH - 0xBA68: 0xD2B6, //HANGUL SYLLABLE THIEUTH YU PHIEUPH - 0xBA69: 0xD2B7, //HANGUL SYLLABLE THIEUTH YU HIEUH - 0xBA6A: 0xD2BA, //HANGUL SYLLABLE THIEUTH EU SSANGKIYEOK - 0xBA6B: 0xD2BB, //HANGUL SYLLABLE THIEUTH EU KIYEOKSIOS - 0xBA6C: 0xD2BD, //HANGUL SYLLABLE THIEUTH EU NIEUNCIEUC - 0xBA6D: 0xD2BE, //HANGUL SYLLABLE THIEUTH EU NIEUNHIEUH - 0xBA6E: 0xD2C1, //HANGUL SYLLABLE THIEUTH EU RIEULKIYEOK - 0xBA6F: 0xD2C3, //HANGUL SYLLABLE THIEUTH EU RIEULPIEUP - 0xBA70: 0xD2C4, //HANGUL SYLLABLE THIEUTH EU RIEULSIOS - 0xBA71: 0xD2C5, //HANGUL SYLLABLE THIEUTH EU RIEULTHIEUTH - 0xBA72: 0xD2C6, //HANGUL SYLLABLE THIEUTH EU RIEULPHIEUPH - 0xBA73: 0xD2C7, //HANGUL SYLLABLE THIEUTH EU RIEULHIEUH - 0xBA74: 0xD2CA, //HANGUL SYLLABLE THIEUTH EU PIEUPSIOS - 0xBA75: 0xD2CC, //HANGUL SYLLABLE THIEUTH EU SSANGSIOS - 0xBA76: 0xD2CD, //HANGUL SYLLABLE THIEUTH EU IEUNG - 0xBA77: 0xD2CE, //HANGUL SYLLABLE THIEUTH EU CIEUC - 0xBA78: 0xD2CF, //HANGUL SYLLABLE THIEUTH EU CHIEUCH - 0xBA79: 0xD2D0, //HANGUL SYLLABLE THIEUTH EU KHIEUKH - 0xBA7A: 0xD2D1, //HANGUL SYLLABLE THIEUTH EU THIEUTH - 0xBA81: 0xD2D2, //HANGUL SYLLABLE THIEUTH EU PHIEUPH - 0xBA82: 0xD2D3, //HANGUL SYLLABLE THIEUTH EU HIEUH - 0xBA83: 0xD2D5, //HANGUL SYLLABLE THIEUTH YI KIYEOK - 0xBA84: 0xD2D6, //HANGUL SYLLABLE THIEUTH YI SSANGKIYEOK - 0xBA85: 0xD2D7, //HANGUL SYLLABLE THIEUTH YI KIYEOKSIOS - 0xBA86: 0xD2D9, //HANGUL SYLLABLE THIEUTH YI NIEUNCIEUC - 0xBA87: 0xD2DA, //HANGUL SYLLABLE THIEUTH YI NIEUNHIEUH - 0xBA88: 0xD2DB, //HANGUL SYLLABLE THIEUTH YI TIKEUT - 0xBA89: 0xD2DD, //HANGUL SYLLABLE THIEUTH YI RIEULKIYEOK - 0xBA8A: 0xD2DE, //HANGUL SYLLABLE THIEUTH YI RIEULMIEUM - 0xBA8B: 0xD2DF, //HANGUL SYLLABLE THIEUTH YI RIEULPIEUP - 0xBA8C: 0xD2E0, //HANGUL SYLLABLE THIEUTH YI RIEULSIOS - 0xBA8D: 0xD2E1, //HANGUL SYLLABLE THIEUTH YI RIEULTHIEUTH - 0xBA8E: 0xD2E2, //HANGUL SYLLABLE THIEUTH YI RIEULPHIEUPH - 0xBA8F: 0xD2E3, //HANGUL SYLLABLE THIEUTH YI RIEULHIEUH - 0xBA90: 0xD2E6, //HANGUL SYLLABLE THIEUTH YI PIEUPSIOS - 0xBA91: 0xD2E7, //HANGUL SYLLABLE THIEUTH YI SIOS - 0xBA92: 0xD2E8, //HANGUL SYLLABLE THIEUTH YI SSANGSIOS - 0xBA93: 0xD2E9, //HANGUL SYLLABLE THIEUTH YI IEUNG - 0xBA94: 0xD2EA, //HANGUL SYLLABLE THIEUTH YI CIEUC - 0xBA95: 0xD2EB, //HANGUL SYLLABLE THIEUTH YI CHIEUCH - 0xBA96: 0xD2EC, //HANGUL SYLLABLE THIEUTH YI KHIEUKH - 0xBA97: 0xD2ED, //HANGUL SYLLABLE THIEUTH YI THIEUTH - 0xBA98: 0xD2EE, //HANGUL SYLLABLE THIEUTH YI PHIEUPH - 0xBA99: 0xD2EF, //HANGUL SYLLABLE THIEUTH YI HIEUH - 0xBA9A: 0xD2F2, //HANGUL SYLLABLE THIEUTH I SSANGKIYEOK - 0xBA9B: 0xD2F3, //HANGUL SYLLABLE THIEUTH I KIYEOKSIOS - 0xBA9C: 0xD2F5, //HANGUL SYLLABLE THIEUTH I NIEUNCIEUC - 0xBA9D: 0xD2F6, //HANGUL SYLLABLE THIEUTH I NIEUNHIEUH - 0xBA9E: 0xD2F7, //HANGUL SYLLABLE THIEUTH I TIKEUT - 0xBA9F: 0xD2F9, //HANGUL SYLLABLE THIEUTH I RIEULKIYEOK - 0xBAA0: 0xD2FA, //HANGUL SYLLABLE THIEUTH I RIEULMIEUM - 0xBAA1: 0xBC99, //HANGUL SYLLABLE PIEUP EO IEUNG - 0xBAA2: 0xBC9A, //HANGUL SYLLABLE PIEUP EO CIEUC - 0xBAA3: 0xBCA0, //HANGUL SYLLABLE PIEUP E - 0xBAA4: 0xBCA1, //HANGUL SYLLABLE PIEUP E KIYEOK - 0xBAA5: 0xBCA4, //HANGUL SYLLABLE PIEUP E NIEUN - 0xBAA6: 0xBCA7, //HANGUL SYLLABLE PIEUP E TIKEUT - 0xBAA7: 0xBCA8, //HANGUL SYLLABLE PIEUP E RIEUL - 0xBAA8: 0xBCB0, //HANGUL SYLLABLE PIEUP E MIEUM - 0xBAA9: 0xBCB1, //HANGUL SYLLABLE PIEUP E PIEUP - 0xBAAA: 0xBCB3, //HANGUL SYLLABLE PIEUP E SIOS - 0xBAAB: 0xBCB4, //HANGUL SYLLABLE PIEUP E SSANGSIOS - 0xBAAC: 0xBCB5, //HANGUL SYLLABLE PIEUP E IEUNG - 0xBAAD: 0xBCBC, //HANGUL SYLLABLE PIEUP YEO - 0xBAAE: 0xBCBD, //HANGUL SYLLABLE PIEUP YEO KIYEOK - 0xBAAF: 0xBCC0, //HANGUL SYLLABLE PIEUP YEO NIEUN - 0xBAB0: 0xBCC4, //HANGUL SYLLABLE PIEUP YEO RIEUL - 0xBAB1: 0xBCCD, //HANGUL SYLLABLE PIEUP YEO PIEUP - 0xBAB2: 0xBCCF, //HANGUL SYLLABLE PIEUP YEO SIOS - 0xBAB3: 0xBCD0, //HANGUL SYLLABLE PIEUP YEO SSANGSIOS - 0xBAB4: 0xBCD1, //HANGUL SYLLABLE PIEUP YEO IEUNG - 0xBAB5: 0xBCD5, //HANGUL SYLLABLE PIEUP YEO THIEUTH - 0xBAB6: 0xBCD8, //HANGUL SYLLABLE PIEUP YE - 0xBAB7: 0xBCDC, //HANGUL SYLLABLE PIEUP YE NIEUN - 0xBAB8: 0xBCF4, //HANGUL SYLLABLE PIEUP O - 0xBAB9: 0xBCF5, //HANGUL SYLLABLE PIEUP O KIYEOK - 0xBABA: 0xBCF6, //HANGUL SYLLABLE PIEUP O SSANGKIYEOK - 0xBABB: 0xBCF8, //HANGUL SYLLABLE PIEUP O NIEUN - 0xBABC: 0xBCFC, //HANGUL SYLLABLE PIEUP O RIEUL - 0xBABD: 0xBD04, //HANGUL SYLLABLE PIEUP O MIEUM - 0xBABE: 0xBD05, //HANGUL SYLLABLE PIEUP O PIEUP - 0xBABF: 0xBD07, //HANGUL SYLLABLE PIEUP O SIOS - 0xBAC0: 0xBD09, //HANGUL SYLLABLE PIEUP O IEUNG - 0xBAC1: 0xBD10, //HANGUL SYLLABLE PIEUP WA - 0xBAC2: 0xBD14, //HANGUL SYLLABLE PIEUP WA NIEUN - 0xBAC3: 0xBD24, //HANGUL SYLLABLE PIEUP WA SSANGSIOS - 0xBAC4: 0xBD2C, //HANGUL SYLLABLE PIEUP WAE - 0xBAC5: 0xBD40, //HANGUL SYLLABLE PIEUP WAE SSANGSIOS - 0xBAC6: 0xBD48, //HANGUL SYLLABLE PIEUP OE - 0xBAC7: 0xBD49, //HANGUL SYLLABLE PIEUP OE KIYEOK - 0xBAC8: 0xBD4C, //HANGUL SYLLABLE PIEUP OE NIEUN - 0xBAC9: 0xBD50, //HANGUL SYLLABLE PIEUP OE RIEUL - 0xBACA: 0xBD58, //HANGUL SYLLABLE PIEUP OE MIEUM - 0xBACB: 0xBD59, //HANGUL SYLLABLE PIEUP OE PIEUP - 0xBACC: 0xBD64, //HANGUL SYLLABLE PIEUP YO - 0xBACD: 0xBD68, //HANGUL SYLLABLE PIEUP YO NIEUN - 0xBACE: 0xBD80, //HANGUL SYLLABLE PIEUP U - 0xBACF: 0xBD81, //HANGUL SYLLABLE PIEUP U KIYEOK - 0xBAD0: 0xBD84, //HANGUL SYLLABLE PIEUP U NIEUN - 0xBAD1: 0xBD87, //HANGUL SYLLABLE PIEUP U TIKEUT - 0xBAD2: 0xBD88, //HANGUL SYLLABLE PIEUP U RIEUL - 0xBAD3: 0xBD89, //HANGUL SYLLABLE PIEUP U RIEULKIYEOK - 0xBAD4: 0xBD8A, //HANGUL SYLLABLE PIEUP U RIEULMIEUM - 0xBAD5: 0xBD90, //HANGUL SYLLABLE PIEUP U MIEUM - 0xBAD6: 0xBD91, //HANGUL SYLLABLE PIEUP U PIEUP - 0xBAD7: 0xBD93, //HANGUL SYLLABLE PIEUP U SIOS - 0xBAD8: 0xBD95, //HANGUL SYLLABLE PIEUP U IEUNG - 0xBAD9: 0xBD99, //HANGUL SYLLABLE PIEUP U THIEUTH - 0xBADA: 0xBD9A, //HANGUL SYLLABLE PIEUP U PHIEUPH - 0xBADB: 0xBD9C, //HANGUL SYLLABLE PIEUP WEO - 0xBADC: 0xBDA4, //HANGUL SYLLABLE PIEUP WEO RIEUL - 0xBADD: 0xBDB0, //HANGUL SYLLABLE PIEUP WEO SSANGSIOS - 0xBADE: 0xBDB8, //HANGUL SYLLABLE PIEUP WE - 0xBADF: 0xBDD4, //HANGUL SYLLABLE PIEUP WI - 0xBAE0: 0xBDD5, //HANGUL SYLLABLE PIEUP WI KIYEOK - 0xBAE1: 0xBDD8, //HANGUL SYLLABLE PIEUP WI NIEUN - 0xBAE2: 0xBDDC, //HANGUL SYLLABLE PIEUP WI RIEUL - 0xBAE3: 0xBDE9, //HANGUL SYLLABLE PIEUP WI IEUNG - 0xBAE4: 0xBDF0, //HANGUL SYLLABLE PIEUP YU - 0xBAE5: 0xBDF4, //HANGUL SYLLABLE PIEUP YU NIEUN - 0xBAE6: 0xBDF8, //HANGUL SYLLABLE PIEUP YU RIEUL - 0xBAE7: 0xBE00, //HANGUL SYLLABLE PIEUP YU MIEUM - 0xBAE8: 0xBE03, //HANGUL SYLLABLE PIEUP YU SIOS - 0xBAE9: 0xBE05, //HANGUL SYLLABLE PIEUP YU IEUNG - 0xBAEA: 0xBE0C, //HANGUL SYLLABLE PIEUP EU - 0xBAEB: 0xBE0D, //HANGUL SYLLABLE PIEUP EU KIYEOK - 0xBAEC: 0xBE10, //HANGUL SYLLABLE PIEUP EU NIEUN - 0xBAED: 0xBE14, //HANGUL SYLLABLE PIEUP EU RIEUL - 0xBAEE: 0xBE1C, //HANGUL SYLLABLE PIEUP EU MIEUM - 0xBAEF: 0xBE1D, //HANGUL SYLLABLE PIEUP EU PIEUP - 0xBAF0: 0xBE1F, //HANGUL SYLLABLE PIEUP EU SIOS - 0xBAF1: 0xBE44, //HANGUL SYLLABLE PIEUP I - 0xBAF2: 0xBE45, //HANGUL SYLLABLE PIEUP I KIYEOK - 0xBAF3: 0xBE48, //HANGUL SYLLABLE PIEUP I NIEUN - 0xBAF4: 0xBE4C, //HANGUL SYLLABLE PIEUP I RIEUL - 0xBAF5: 0xBE4E, //HANGUL SYLLABLE PIEUP I RIEULMIEUM - 0xBAF6: 0xBE54, //HANGUL SYLLABLE PIEUP I MIEUM - 0xBAF7: 0xBE55, //HANGUL SYLLABLE PIEUP I PIEUP - 0xBAF8: 0xBE57, //HANGUL SYLLABLE PIEUP I SIOS - 0xBAF9: 0xBE59, //HANGUL SYLLABLE PIEUP I IEUNG - 0xBAFA: 0xBE5A, //HANGUL SYLLABLE PIEUP I CIEUC - 0xBAFB: 0xBE5B, //HANGUL SYLLABLE PIEUP I CHIEUCH - 0xBAFC: 0xBE60, //HANGUL SYLLABLE SSANGPIEUP A - 0xBAFD: 0xBE61, //HANGUL SYLLABLE SSANGPIEUP A KIYEOK - 0xBAFE: 0xBE64, //HANGUL SYLLABLE SSANGPIEUP A NIEUN - 0xBB41: 0xD2FB, //HANGUL SYLLABLE THIEUTH I RIEULPIEUP - 0xBB42: 0xD2FC, //HANGUL SYLLABLE THIEUTH I RIEULSIOS - 0xBB43: 0xD2FD, //HANGUL SYLLABLE THIEUTH I RIEULTHIEUTH - 0xBB44: 0xD2FE, //HANGUL SYLLABLE THIEUTH I RIEULPHIEUPH - 0xBB45: 0xD2FF, //HANGUL SYLLABLE THIEUTH I RIEULHIEUH - 0xBB46: 0xD302, //HANGUL SYLLABLE THIEUTH I PIEUPSIOS - 0xBB47: 0xD304, //HANGUL SYLLABLE THIEUTH I SSANGSIOS - 0xBB48: 0xD306, //HANGUL SYLLABLE THIEUTH I CIEUC - 0xBB49: 0xD307, //HANGUL SYLLABLE THIEUTH I CHIEUCH - 0xBB4A: 0xD308, //HANGUL SYLLABLE THIEUTH I KHIEUKH - 0xBB4B: 0xD309, //HANGUL SYLLABLE THIEUTH I THIEUTH - 0xBB4C: 0xD30A, //HANGUL SYLLABLE THIEUTH I PHIEUPH - 0xBB4D: 0xD30B, //HANGUL SYLLABLE THIEUTH I HIEUH - 0xBB4E: 0xD30F, //HANGUL SYLLABLE PHIEUPH A KIYEOKSIOS - 0xBB4F: 0xD311, //HANGUL SYLLABLE PHIEUPH A NIEUNCIEUC - 0xBB50: 0xD312, //HANGUL SYLLABLE PHIEUPH A NIEUNHIEUH - 0xBB51: 0xD313, //HANGUL SYLLABLE PHIEUPH A TIKEUT - 0xBB52: 0xD315, //HANGUL SYLLABLE PHIEUPH A RIEULKIYEOK - 0xBB53: 0xD317, //HANGUL SYLLABLE PHIEUPH A RIEULPIEUP - 0xBB54: 0xD318, //HANGUL SYLLABLE PHIEUPH A RIEULSIOS - 0xBB55: 0xD319, //HANGUL SYLLABLE PHIEUPH A RIEULTHIEUTH - 0xBB56: 0xD31A, //HANGUL SYLLABLE PHIEUPH A RIEULPHIEUPH - 0xBB57: 0xD31B, //HANGUL SYLLABLE PHIEUPH A RIEULHIEUH - 0xBB58: 0xD31E, //HANGUL SYLLABLE PHIEUPH A PIEUPSIOS - 0xBB59: 0xD322, //HANGUL SYLLABLE PHIEUPH A CIEUC - 0xBB5A: 0xD323, //HANGUL SYLLABLE PHIEUPH A CHIEUCH - 0xBB61: 0xD324, //HANGUL SYLLABLE PHIEUPH A KHIEUKH - 0xBB62: 0xD326, //HANGUL SYLLABLE PHIEUPH A PHIEUPH - 0xBB63: 0xD327, //HANGUL SYLLABLE PHIEUPH A HIEUH - 0xBB64: 0xD32A, //HANGUL SYLLABLE PHIEUPH AE SSANGKIYEOK - 0xBB65: 0xD32B, //HANGUL SYLLABLE PHIEUPH AE KIYEOKSIOS - 0xBB66: 0xD32D, //HANGUL SYLLABLE PHIEUPH AE NIEUNCIEUC - 0xBB67: 0xD32E, //HANGUL SYLLABLE PHIEUPH AE NIEUNHIEUH - 0xBB68: 0xD32F, //HANGUL SYLLABLE PHIEUPH AE TIKEUT - 0xBB69: 0xD331, //HANGUL SYLLABLE PHIEUPH AE RIEULKIYEOK - 0xBB6A: 0xD332, //HANGUL SYLLABLE PHIEUPH AE RIEULMIEUM - 0xBB6B: 0xD333, //HANGUL SYLLABLE PHIEUPH AE RIEULPIEUP - 0xBB6C: 0xD334, //HANGUL SYLLABLE PHIEUPH AE RIEULSIOS - 0xBB6D: 0xD335, //HANGUL SYLLABLE PHIEUPH AE RIEULTHIEUTH - 0xBB6E: 0xD336, //HANGUL SYLLABLE PHIEUPH AE RIEULPHIEUPH - 0xBB6F: 0xD337, //HANGUL SYLLABLE PHIEUPH AE RIEULHIEUH - 0xBB70: 0xD33A, //HANGUL SYLLABLE PHIEUPH AE PIEUPSIOS - 0xBB71: 0xD33E, //HANGUL SYLLABLE PHIEUPH AE CIEUC - 0xBB72: 0xD33F, //HANGUL SYLLABLE PHIEUPH AE CHIEUCH - 0xBB73: 0xD340, //HANGUL SYLLABLE PHIEUPH AE KHIEUKH - 0xBB74: 0xD341, //HANGUL SYLLABLE PHIEUPH AE THIEUTH - 0xBB75: 0xD342, //HANGUL SYLLABLE PHIEUPH AE PHIEUPH - 0xBB76: 0xD343, //HANGUL SYLLABLE PHIEUPH AE HIEUH - 0xBB77: 0xD346, //HANGUL SYLLABLE PHIEUPH YA SSANGKIYEOK - 0xBB78: 0xD347, //HANGUL SYLLABLE PHIEUPH YA KIYEOKSIOS - 0xBB79: 0xD348, //HANGUL SYLLABLE PHIEUPH YA NIEUN - 0xBB7A: 0xD349, //HANGUL SYLLABLE PHIEUPH YA NIEUNCIEUC - 0xBB81: 0xD34A, //HANGUL SYLLABLE PHIEUPH YA NIEUNHIEUH - 0xBB82: 0xD34B, //HANGUL SYLLABLE PHIEUPH YA TIKEUT - 0xBB83: 0xD34C, //HANGUL SYLLABLE PHIEUPH YA RIEUL - 0xBB84: 0xD34D, //HANGUL SYLLABLE PHIEUPH YA RIEULKIYEOK - 0xBB85: 0xD34E, //HANGUL SYLLABLE PHIEUPH YA RIEULMIEUM - 0xBB86: 0xD34F, //HANGUL SYLLABLE PHIEUPH YA RIEULPIEUP - 0xBB87: 0xD350, //HANGUL SYLLABLE PHIEUPH YA RIEULSIOS - 0xBB88: 0xD351, //HANGUL SYLLABLE PHIEUPH YA RIEULTHIEUTH - 0xBB89: 0xD352, //HANGUL SYLLABLE PHIEUPH YA RIEULPHIEUPH - 0xBB8A: 0xD353, //HANGUL SYLLABLE PHIEUPH YA RIEULHIEUH - 0xBB8B: 0xD354, //HANGUL SYLLABLE PHIEUPH YA MIEUM - 0xBB8C: 0xD355, //HANGUL SYLLABLE PHIEUPH YA PIEUP - 0xBB8D: 0xD356, //HANGUL SYLLABLE PHIEUPH YA PIEUPSIOS - 0xBB8E: 0xD357, //HANGUL SYLLABLE PHIEUPH YA SIOS - 0xBB8F: 0xD358, //HANGUL SYLLABLE PHIEUPH YA SSANGSIOS - 0xBB90: 0xD359, //HANGUL SYLLABLE PHIEUPH YA IEUNG - 0xBB91: 0xD35A, //HANGUL SYLLABLE PHIEUPH YA CIEUC - 0xBB92: 0xD35B, //HANGUL SYLLABLE PHIEUPH YA CHIEUCH - 0xBB93: 0xD35C, //HANGUL SYLLABLE PHIEUPH YA KHIEUKH - 0xBB94: 0xD35D, //HANGUL SYLLABLE PHIEUPH YA THIEUTH - 0xBB95: 0xD35E, //HANGUL SYLLABLE PHIEUPH YA PHIEUPH - 0xBB96: 0xD35F, //HANGUL SYLLABLE PHIEUPH YA HIEUH - 0xBB97: 0xD360, //HANGUL SYLLABLE PHIEUPH YAE - 0xBB98: 0xD361, //HANGUL SYLLABLE PHIEUPH YAE KIYEOK - 0xBB99: 0xD362, //HANGUL SYLLABLE PHIEUPH YAE SSANGKIYEOK - 0xBB9A: 0xD363, //HANGUL SYLLABLE PHIEUPH YAE KIYEOKSIOS - 0xBB9B: 0xD364, //HANGUL SYLLABLE PHIEUPH YAE NIEUN - 0xBB9C: 0xD365, //HANGUL SYLLABLE PHIEUPH YAE NIEUNCIEUC - 0xBB9D: 0xD366, //HANGUL SYLLABLE PHIEUPH YAE NIEUNHIEUH - 0xBB9E: 0xD367, //HANGUL SYLLABLE PHIEUPH YAE TIKEUT - 0xBB9F: 0xD368, //HANGUL SYLLABLE PHIEUPH YAE RIEUL - 0xBBA0: 0xD369, //HANGUL SYLLABLE PHIEUPH YAE RIEULKIYEOK - 0xBBA1: 0xBE68, //HANGUL SYLLABLE SSANGPIEUP A RIEUL - 0xBBA2: 0xBE6A, //HANGUL SYLLABLE SSANGPIEUP A RIEULMIEUM - 0xBBA3: 0xBE70, //HANGUL SYLLABLE SSANGPIEUP A MIEUM - 0xBBA4: 0xBE71, //HANGUL SYLLABLE SSANGPIEUP A PIEUP - 0xBBA5: 0xBE73, //HANGUL SYLLABLE SSANGPIEUP A SIOS - 0xBBA6: 0xBE74, //HANGUL SYLLABLE SSANGPIEUP A SSANGSIOS - 0xBBA7: 0xBE75, //HANGUL SYLLABLE SSANGPIEUP A IEUNG - 0xBBA8: 0xBE7B, //HANGUL SYLLABLE SSANGPIEUP A HIEUH - 0xBBA9: 0xBE7C, //HANGUL SYLLABLE SSANGPIEUP AE - 0xBBAA: 0xBE7D, //HANGUL SYLLABLE SSANGPIEUP AE KIYEOK - 0xBBAB: 0xBE80, //HANGUL SYLLABLE SSANGPIEUP AE NIEUN - 0xBBAC: 0xBE84, //HANGUL SYLLABLE SSANGPIEUP AE RIEUL - 0xBBAD: 0xBE8C, //HANGUL SYLLABLE SSANGPIEUP AE MIEUM - 0xBBAE: 0xBE8D, //HANGUL SYLLABLE SSANGPIEUP AE PIEUP - 0xBBAF: 0xBE8F, //HANGUL SYLLABLE SSANGPIEUP AE SIOS - 0xBBB0: 0xBE90, //HANGUL SYLLABLE SSANGPIEUP AE SSANGSIOS - 0xBBB1: 0xBE91, //HANGUL SYLLABLE SSANGPIEUP AE IEUNG - 0xBBB2: 0xBE98, //HANGUL SYLLABLE SSANGPIEUP YA - 0xBBB3: 0xBE99, //HANGUL SYLLABLE SSANGPIEUP YA KIYEOK - 0xBBB4: 0xBEA8, //HANGUL SYLLABLE SSANGPIEUP YA MIEUM - 0xBBB5: 0xBED0, //HANGUL SYLLABLE SSANGPIEUP EO - 0xBBB6: 0xBED1, //HANGUL SYLLABLE SSANGPIEUP EO KIYEOK - 0xBBB7: 0xBED4, //HANGUL SYLLABLE SSANGPIEUP EO NIEUN - 0xBBB8: 0xBED7, //HANGUL SYLLABLE SSANGPIEUP EO TIKEUT - 0xBBB9: 0xBED8, //HANGUL SYLLABLE SSANGPIEUP EO RIEUL - 0xBBBA: 0xBEE0, //HANGUL SYLLABLE SSANGPIEUP EO MIEUM - 0xBBBB: 0xBEE3, //HANGUL SYLLABLE SSANGPIEUP EO SIOS - 0xBBBC: 0xBEE4, //HANGUL SYLLABLE SSANGPIEUP EO SSANGSIOS - 0xBBBD: 0xBEE5, //HANGUL SYLLABLE SSANGPIEUP EO IEUNG - 0xBBBE: 0xBEEC, //HANGUL SYLLABLE SSANGPIEUP E - 0xBBBF: 0xBF01, //HANGUL SYLLABLE SSANGPIEUP E IEUNG - 0xBBC0: 0xBF08, //HANGUL SYLLABLE SSANGPIEUP YEO - 0xBBC1: 0xBF09, //HANGUL SYLLABLE SSANGPIEUP YEO KIYEOK - 0xBBC2: 0xBF18, //HANGUL SYLLABLE SSANGPIEUP YEO MIEUM - 0xBBC3: 0xBF19, //HANGUL SYLLABLE SSANGPIEUP YEO PIEUP - 0xBBC4: 0xBF1B, //HANGUL SYLLABLE SSANGPIEUP YEO SIOS - 0xBBC5: 0xBF1C, //HANGUL SYLLABLE SSANGPIEUP YEO SSANGSIOS - 0xBBC6: 0xBF1D, //HANGUL SYLLABLE SSANGPIEUP YEO IEUNG - 0xBBC7: 0xBF40, //HANGUL SYLLABLE SSANGPIEUP O - 0xBBC8: 0xBF41, //HANGUL SYLLABLE SSANGPIEUP O KIYEOK - 0xBBC9: 0xBF44, //HANGUL SYLLABLE SSANGPIEUP O NIEUN - 0xBBCA: 0xBF48, //HANGUL SYLLABLE SSANGPIEUP O RIEUL - 0xBBCB: 0xBF50, //HANGUL SYLLABLE SSANGPIEUP O MIEUM - 0xBBCC: 0xBF51, //HANGUL SYLLABLE SSANGPIEUP O PIEUP - 0xBBCD: 0xBF55, //HANGUL SYLLABLE SSANGPIEUP O IEUNG - 0xBBCE: 0xBF94, //HANGUL SYLLABLE SSANGPIEUP OE - 0xBBCF: 0xBFB0, //HANGUL SYLLABLE SSANGPIEUP YO - 0xBBD0: 0xBFC5, //HANGUL SYLLABLE SSANGPIEUP YO IEUNG - 0xBBD1: 0xBFCC, //HANGUL SYLLABLE SSANGPIEUP U - 0xBBD2: 0xBFCD, //HANGUL SYLLABLE SSANGPIEUP U KIYEOK - 0xBBD3: 0xBFD0, //HANGUL SYLLABLE SSANGPIEUP U NIEUN - 0xBBD4: 0xBFD4, //HANGUL SYLLABLE SSANGPIEUP U RIEUL - 0xBBD5: 0xBFDC, //HANGUL SYLLABLE SSANGPIEUP U MIEUM - 0xBBD6: 0xBFDF, //HANGUL SYLLABLE SSANGPIEUP U SIOS - 0xBBD7: 0xBFE1, //HANGUL SYLLABLE SSANGPIEUP U IEUNG - 0xBBD8: 0xC03C, //HANGUL SYLLABLE SSANGPIEUP YU - 0xBBD9: 0xC051, //HANGUL SYLLABLE SSANGPIEUP YU IEUNG - 0xBBDA: 0xC058, //HANGUL SYLLABLE SSANGPIEUP EU - 0xBBDB: 0xC05C, //HANGUL SYLLABLE SSANGPIEUP EU NIEUN - 0xBBDC: 0xC060, //HANGUL SYLLABLE SSANGPIEUP EU RIEUL - 0xBBDD: 0xC068, //HANGUL SYLLABLE SSANGPIEUP EU MIEUM - 0xBBDE: 0xC069, //HANGUL SYLLABLE SSANGPIEUP EU PIEUP - 0xBBDF: 0xC090, //HANGUL SYLLABLE SSANGPIEUP I - 0xBBE0: 0xC091, //HANGUL SYLLABLE SSANGPIEUP I KIYEOK - 0xBBE1: 0xC094, //HANGUL SYLLABLE SSANGPIEUP I NIEUN - 0xBBE2: 0xC098, //HANGUL SYLLABLE SSANGPIEUP I RIEUL - 0xBBE3: 0xC0A0, //HANGUL SYLLABLE SSANGPIEUP I MIEUM - 0xBBE4: 0xC0A1, //HANGUL SYLLABLE SSANGPIEUP I PIEUP - 0xBBE5: 0xC0A3, //HANGUL SYLLABLE SSANGPIEUP I SIOS - 0xBBE6: 0xC0A5, //HANGUL SYLLABLE SSANGPIEUP I IEUNG - 0xBBE7: 0xC0AC, //HANGUL SYLLABLE SIOS A - 0xBBE8: 0xC0AD, //HANGUL SYLLABLE SIOS A KIYEOK - 0xBBE9: 0xC0AF, //HANGUL SYLLABLE SIOS A KIYEOKSIOS - 0xBBEA: 0xC0B0, //HANGUL SYLLABLE SIOS A NIEUN - 0xBBEB: 0xC0B3, //HANGUL SYLLABLE SIOS A TIKEUT - 0xBBEC: 0xC0B4, //HANGUL SYLLABLE SIOS A RIEUL - 0xBBED: 0xC0B5, //HANGUL SYLLABLE SIOS A RIEULKIYEOK - 0xBBEE: 0xC0B6, //HANGUL SYLLABLE SIOS A RIEULMIEUM - 0xBBEF: 0xC0BC, //HANGUL SYLLABLE SIOS A MIEUM - 0xBBF0: 0xC0BD, //HANGUL SYLLABLE SIOS A PIEUP - 0xBBF1: 0xC0BF, //HANGUL SYLLABLE SIOS A SIOS - 0xBBF2: 0xC0C0, //HANGUL SYLLABLE SIOS A SSANGSIOS - 0xBBF3: 0xC0C1, //HANGUL SYLLABLE SIOS A IEUNG - 0xBBF4: 0xC0C5, //HANGUL SYLLABLE SIOS A THIEUTH - 0xBBF5: 0xC0C8, //HANGUL SYLLABLE SIOS AE - 0xBBF6: 0xC0C9, //HANGUL SYLLABLE SIOS AE KIYEOK - 0xBBF7: 0xC0CC, //HANGUL SYLLABLE SIOS AE NIEUN - 0xBBF8: 0xC0D0, //HANGUL SYLLABLE SIOS AE RIEUL - 0xBBF9: 0xC0D8, //HANGUL SYLLABLE SIOS AE MIEUM - 0xBBFA: 0xC0D9, //HANGUL SYLLABLE SIOS AE PIEUP - 0xBBFB: 0xC0DB, //HANGUL SYLLABLE SIOS AE SIOS - 0xBBFC: 0xC0DC, //HANGUL SYLLABLE SIOS AE SSANGSIOS - 0xBBFD: 0xC0DD, //HANGUL SYLLABLE SIOS AE IEUNG - 0xBBFE: 0xC0E4, //HANGUL SYLLABLE SIOS YA - 0xBC41: 0xD36A, //HANGUL SYLLABLE PHIEUPH YAE RIEULMIEUM - 0xBC42: 0xD36B, //HANGUL SYLLABLE PHIEUPH YAE RIEULPIEUP - 0xBC43: 0xD36C, //HANGUL SYLLABLE PHIEUPH YAE RIEULSIOS - 0xBC44: 0xD36D, //HANGUL SYLLABLE PHIEUPH YAE RIEULTHIEUTH - 0xBC45: 0xD36E, //HANGUL SYLLABLE PHIEUPH YAE RIEULPHIEUPH - 0xBC46: 0xD36F, //HANGUL SYLLABLE PHIEUPH YAE RIEULHIEUH - 0xBC47: 0xD370, //HANGUL SYLLABLE PHIEUPH YAE MIEUM - 0xBC48: 0xD371, //HANGUL SYLLABLE PHIEUPH YAE PIEUP - 0xBC49: 0xD372, //HANGUL SYLLABLE PHIEUPH YAE PIEUPSIOS - 0xBC4A: 0xD373, //HANGUL SYLLABLE PHIEUPH YAE SIOS - 0xBC4B: 0xD374, //HANGUL SYLLABLE PHIEUPH YAE SSANGSIOS - 0xBC4C: 0xD375, //HANGUL SYLLABLE PHIEUPH YAE IEUNG - 0xBC4D: 0xD376, //HANGUL SYLLABLE PHIEUPH YAE CIEUC - 0xBC4E: 0xD377, //HANGUL SYLLABLE PHIEUPH YAE CHIEUCH - 0xBC4F: 0xD378, //HANGUL SYLLABLE PHIEUPH YAE KHIEUKH - 0xBC50: 0xD379, //HANGUL SYLLABLE PHIEUPH YAE THIEUTH - 0xBC51: 0xD37A, //HANGUL SYLLABLE PHIEUPH YAE PHIEUPH - 0xBC52: 0xD37B, //HANGUL SYLLABLE PHIEUPH YAE HIEUH - 0xBC53: 0xD37E, //HANGUL SYLLABLE PHIEUPH EO SSANGKIYEOK - 0xBC54: 0xD37F, //HANGUL SYLLABLE PHIEUPH EO KIYEOKSIOS - 0xBC55: 0xD381, //HANGUL SYLLABLE PHIEUPH EO NIEUNCIEUC - 0xBC56: 0xD382, //HANGUL SYLLABLE PHIEUPH EO NIEUNHIEUH - 0xBC57: 0xD383, //HANGUL SYLLABLE PHIEUPH EO TIKEUT - 0xBC58: 0xD385, //HANGUL SYLLABLE PHIEUPH EO RIEULKIYEOK - 0xBC59: 0xD386, //HANGUL SYLLABLE PHIEUPH EO RIEULMIEUM - 0xBC5A: 0xD387, //HANGUL SYLLABLE PHIEUPH EO RIEULPIEUP - 0xBC61: 0xD388, //HANGUL SYLLABLE PHIEUPH EO RIEULSIOS - 0xBC62: 0xD389, //HANGUL SYLLABLE PHIEUPH EO RIEULTHIEUTH - 0xBC63: 0xD38A, //HANGUL SYLLABLE PHIEUPH EO RIEULPHIEUPH - 0xBC64: 0xD38B, //HANGUL SYLLABLE PHIEUPH EO RIEULHIEUH - 0xBC65: 0xD38E, //HANGUL SYLLABLE PHIEUPH EO PIEUPSIOS - 0xBC66: 0xD392, //HANGUL SYLLABLE PHIEUPH EO CIEUC - 0xBC67: 0xD393, //HANGUL SYLLABLE PHIEUPH EO CHIEUCH - 0xBC68: 0xD394, //HANGUL SYLLABLE PHIEUPH EO KHIEUKH - 0xBC69: 0xD395, //HANGUL SYLLABLE PHIEUPH EO THIEUTH - 0xBC6A: 0xD396, //HANGUL SYLLABLE PHIEUPH EO PHIEUPH - 0xBC6B: 0xD397, //HANGUL SYLLABLE PHIEUPH EO HIEUH - 0xBC6C: 0xD39A, //HANGUL SYLLABLE PHIEUPH E SSANGKIYEOK - 0xBC6D: 0xD39B, //HANGUL SYLLABLE PHIEUPH E KIYEOKSIOS - 0xBC6E: 0xD39D, //HANGUL SYLLABLE PHIEUPH E NIEUNCIEUC - 0xBC6F: 0xD39E, //HANGUL SYLLABLE PHIEUPH E NIEUNHIEUH - 0xBC70: 0xD39F, //HANGUL SYLLABLE PHIEUPH E TIKEUT - 0xBC71: 0xD3A1, //HANGUL SYLLABLE PHIEUPH E RIEULKIYEOK - 0xBC72: 0xD3A2, //HANGUL SYLLABLE PHIEUPH E RIEULMIEUM - 0xBC73: 0xD3A3, //HANGUL SYLLABLE PHIEUPH E RIEULPIEUP - 0xBC74: 0xD3A4, //HANGUL SYLLABLE PHIEUPH E RIEULSIOS - 0xBC75: 0xD3A5, //HANGUL SYLLABLE PHIEUPH E RIEULTHIEUTH - 0xBC76: 0xD3A6, //HANGUL SYLLABLE PHIEUPH E RIEULPHIEUPH - 0xBC77: 0xD3A7, //HANGUL SYLLABLE PHIEUPH E RIEULHIEUH - 0xBC78: 0xD3AA, //HANGUL SYLLABLE PHIEUPH E PIEUPSIOS - 0xBC79: 0xD3AC, //HANGUL SYLLABLE PHIEUPH E SSANGSIOS - 0xBC7A: 0xD3AE, //HANGUL SYLLABLE PHIEUPH E CIEUC - 0xBC81: 0xD3AF, //HANGUL SYLLABLE PHIEUPH E CHIEUCH - 0xBC82: 0xD3B0, //HANGUL SYLLABLE PHIEUPH E KHIEUKH - 0xBC83: 0xD3B1, //HANGUL SYLLABLE PHIEUPH E THIEUTH - 0xBC84: 0xD3B2, //HANGUL SYLLABLE PHIEUPH E PHIEUPH - 0xBC85: 0xD3B3, //HANGUL SYLLABLE PHIEUPH E HIEUH - 0xBC86: 0xD3B5, //HANGUL SYLLABLE PHIEUPH YEO KIYEOK - 0xBC87: 0xD3B6, //HANGUL SYLLABLE PHIEUPH YEO SSANGKIYEOK - 0xBC88: 0xD3B7, //HANGUL SYLLABLE PHIEUPH YEO KIYEOKSIOS - 0xBC89: 0xD3B9, //HANGUL SYLLABLE PHIEUPH YEO NIEUNCIEUC - 0xBC8A: 0xD3BA, //HANGUL SYLLABLE PHIEUPH YEO NIEUNHIEUH - 0xBC8B: 0xD3BB, //HANGUL SYLLABLE PHIEUPH YEO TIKEUT - 0xBC8C: 0xD3BD, //HANGUL SYLLABLE PHIEUPH YEO RIEULKIYEOK - 0xBC8D: 0xD3BE, //HANGUL SYLLABLE PHIEUPH YEO RIEULMIEUM - 0xBC8E: 0xD3BF, //HANGUL SYLLABLE PHIEUPH YEO RIEULPIEUP - 0xBC8F: 0xD3C0, //HANGUL SYLLABLE PHIEUPH YEO RIEULSIOS - 0xBC90: 0xD3C1, //HANGUL SYLLABLE PHIEUPH YEO RIEULTHIEUTH - 0xBC91: 0xD3C2, //HANGUL SYLLABLE PHIEUPH YEO RIEULPHIEUPH - 0xBC92: 0xD3C3, //HANGUL SYLLABLE PHIEUPH YEO RIEULHIEUH - 0xBC93: 0xD3C6, //HANGUL SYLLABLE PHIEUPH YEO PIEUPSIOS - 0xBC94: 0xD3C7, //HANGUL SYLLABLE PHIEUPH YEO SIOS - 0xBC95: 0xD3CA, //HANGUL SYLLABLE PHIEUPH YEO CIEUC - 0xBC96: 0xD3CB, //HANGUL SYLLABLE PHIEUPH YEO CHIEUCH - 0xBC97: 0xD3CC, //HANGUL SYLLABLE PHIEUPH YEO KHIEUKH - 0xBC98: 0xD3CD, //HANGUL SYLLABLE PHIEUPH YEO THIEUTH - 0xBC99: 0xD3CE, //HANGUL SYLLABLE PHIEUPH YEO PHIEUPH - 0xBC9A: 0xD3CF, //HANGUL SYLLABLE PHIEUPH YEO HIEUH - 0xBC9B: 0xD3D1, //HANGUL SYLLABLE PHIEUPH YE KIYEOK - 0xBC9C: 0xD3D2, //HANGUL SYLLABLE PHIEUPH YE SSANGKIYEOK - 0xBC9D: 0xD3D3, //HANGUL SYLLABLE PHIEUPH YE KIYEOKSIOS - 0xBC9E: 0xD3D4, //HANGUL SYLLABLE PHIEUPH YE NIEUN - 0xBC9F: 0xD3D5, //HANGUL SYLLABLE PHIEUPH YE NIEUNCIEUC - 0xBCA0: 0xD3D6, //HANGUL SYLLABLE PHIEUPH YE NIEUNHIEUH - 0xBCA1: 0xC0E5, //HANGUL SYLLABLE SIOS YA KIYEOK - 0xBCA2: 0xC0E8, //HANGUL SYLLABLE SIOS YA NIEUN - 0xBCA3: 0xC0EC, //HANGUL SYLLABLE SIOS YA RIEUL - 0xBCA4: 0xC0F4, //HANGUL SYLLABLE SIOS YA MIEUM - 0xBCA5: 0xC0F5, //HANGUL SYLLABLE SIOS YA PIEUP - 0xBCA6: 0xC0F7, //HANGUL SYLLABLE SIOS YA SIOS - 0xBCA7: 0xC0F9, //HANGUL SYLLABLE SIOS YA IEUNG - 0xBCA8: 0xC100, //HANGUL SYLLABLE SIOS YAE - 0xBCA9: 0xC104, //HANGUL SYLLABLE SIOS YAE NIEUN - 0xBCAA: 0xC108, //HANGUL SYLLABLE SIOS YAE RIEUL - 0xBCAB: 0xC110, //HANGUL SYLLABLE SIOS YAE MIEUM - 0xBCAC: 0xC115, //HANGUL SYLLABLE SIOS YAE IEUNG - 0xBCAD: 0xC11C, //HANGUL SYLLABLE SIOS EO - 0xBCAE: 0xC11D, //HANGUL SYLLABLE SIOS EO KIYEOK - 0xBCAF: 0xC11E, //HANGUL SYLLABLE SIOS EO SSANGKIYEOK - 0xBCB0: 0xC11F, //HANGUL SYLLABLE SIOS EO KIYEOKSIOS - 0xBCB1: 0xC120, //HANGUL SYLLABLE SIOS EO NIEUN - 0xBCB2: 0xC123, //HANGUL SYLLABLE SIOS EO TIKEUT - 0xBCB3: 0xC124, //HANGUL SYLLABLE SIOS EO RIEUL - 0xBCB4: 0xC126, //HANGUL SYLLABLE SIOS EO RIEULMIEUM - 0xBCB5: 0xC127, //HANGUL SYLLABLE SIOS EO RIEULPIEUP - 0xBCB6: 0xC12C, //HANGUL SYLLABLE SIOS EO MIEUM - 0xBCB7: 0xC12D, //HANGUL SYLLABLE SIOS EO PIEUP - 0xBCB8: 0xC12F, //HANGUL SYLLABLE SIOS EO SIOS - 0xBCB9: 0xC130, //HANGUL SYLLABLE SIOS EO SSANGSIOS - 0xBCBA: 0xC131, //HANGUL SYLLABLE SIOS EO IEUNG - 0xBCBB: 0xC136, //HANGUL SYLLABLE SIOS EO PHIEUPH - 0xBCBC: 0xC138, //HANGUL SYLLABLE SIOS E - 0xBCBD: 0xC139, //HANGUL SYLLABLE SIOS E KIYEOK - 0xBCBE: 0xC13C, //HANGUL SYLLABLE SIOS E NIEUN - 0xBCBF: 0xC140, //HANGUL SYLLABLE SIOS E RIEUL - 0xBCC0: 0xC148, //HANGUL SYLLABLE SIOS E MIEUM - 0xBCC1: 0xC149, //HANGUL SYLLABLE SIOS E PIEUP - 0xBCC2: 0xC14B, //HANGUL SYLLABLE SIOS E SIOS - 0xBCC3: 0xC14C, //HANGUL SYLLABLE SIOS E SSANGSIOS - 0xBCC4: 0xC14D, //HANGUL SYLLABLE SIOS E IEUNG - 0xBCC5: 0xC154, //HANGUL SYLLABLE SIOS YEO - 0xBCC6: 0xC155, //HANGUL SYLLABLE SIOS YEO KIYEOK - 0xBCC7: 0xC158, //HANGUL SYLLABLE SIOS YEO NIEUN - 0xBCC8: 0xC15C, //HANGUL SYLLABLE SIOS YEO RIEUL - 0xBCC9: 0xC164, //HANGUL SYLLABLE SIOS YEO MIEUM - 0xBCCA: 0xC165, //HANGUL SYLLABLE SIOS YEO PIEUP - 0xBCCB: 0xC167, //HANGUL SYLLABLE SIOS YEO SIOS - 0xBCCC: 0xC168, //HANGUL SYLLABLE SIOS YEO SSANGSIOS - 0xBCCD: 0xC169, //HANGUL SYLLABLE SIOS YEO IEUNG - 0xBCCE: 0xC170, //HANGUL SYLLABLE SIOS YE - 0xBCCF: 0xC174, //HANGUL SYLLABLE SIOS YE NIEUN - 0xBCD0: 0xC178, //HANGUL SYLLABLE SIOS YE RIEUL - 0xBCD1: 0xC185, //HANGUL SYLLABLE SIOS YE IEUNG - 0xBCD2: 0xC18C, //HANGUL SYLLABLE SIOS O - 0xBCD3: 0xC18D, //HANGUL SYLLABLE SIOS O KIYEOK - 0xBCD4: 0xC18E, //HANGUL SYLLABLE SIOS O SSANGKIYEOK - 0xBCD5: 0xC190, //HANGUL SYLLABLE SIOS O NIEUN - 0xBCD6: 0xC194, //HANGUL SYLLABLE SIOS O RIEUL - 0xBCD7: 0xC196, //HANGUL SYLLABLE SIOS O RIEULMIEUM - 0xBCD8: 0xC19C, //HANGUL SYLLABLE SIOS O MIEUM - 0xBCD9: 0xC19D, //HANGUL SYLLABLE SIOS O PIEUP - 0xBCDA: 0xC19F, //HANGUL SYLLABLE SIOS O SIOS - 0xBCDB: 0xC1A1, //HANGUL SYLLABLE SIOS O IEUNG - 0xBCDC: 0xC1A5, //HANGUL SYLLABLE SIOS O THIEUTH - 0xBCDD: 0xC1A8, //HANGUL SYLLABLE SIOS WA - 0xBCDE: 0xC1A9, //HANGUL SYLLABLE SIOS WA KIYEOK - 0xBCDF: 0xC1AC, //HANGUL SYLLABLE SIOS WA NIEUN - 0xBCE0: 0xC1B0, //HANGUL SYLLABLE SIOS WA RIEUL - 0xBCE1: 0xC1BD, //HANGUL SYLLABLE SIOS WA IEUNG - 0xBCE2: 0xC1C4, //HANGUL SYLLABLE SIOS WAE - 0xBCE3: 0xC1C8, //HANGUL SYLLABLE SIOS WAE NIEUN - 0xBCE4: 0xC1CC, //HANGUL SYLLABLE SIOS WAE RIEUL - 0xBCE5: 0xC1D4, //HANGUL SYLLABLE SIOS WAE MIEUM - 0xBCE6: 0xC1D7, //HANGUL SYLLABLE SIOS WAE SIOS - 0xBCE7: 0xC1D8, //HANGUL SYLLABLE SIOS WAE SSANGSIOS - 0xBCE8: 0xC1E0, //HANGUL SYLLABLE SIOS OE - 0xBCE9: 0xC1E4, //HANGUL SYLLABLE SIOS OE NIEUN - 0xBCEA: 0xC1E8, //HANGUL SYLLABLE SIOS OE RIEUL - 0xBCEB: 0xC1F0, //HANGUL SYLLABLE SIOS OE MIEUM - 0xBCEC: 0xC1F1, //HANGUL SYLLABLE SIOS OE PIEUP - 0xBCED: 0xC1F3, //HANGUL SYLLABLE SIOS OE SIOS - 0xBCEE: 0xC1FC, //HANGUL SYLLABLE SIOS YO - 0xBCEF: 0xC1FD, //HANGUL SYLLABLE SIOS YO KIYEOK - 0xBCF0: 0xC200, //HANGUL SYLLABLE SIOS YO NIEUN - 0xBCF1: 0xC204, //HANGUL SYLLABLE SIOS YO RIEUL - 0xBCF2: 0xC20C, //HANGUL SYLLABLE SIOS YO MIEUM - 0xBCF3: 0xC20D, //HANGUL SYLLABLE SIOS YO PIEUP - 0xBCF4: 0xC20F, //HANGUL SYLLABLE SIOS YO SIOS - 0xBCF5: 0xC211, //HANGUL SYLLABLE SIOS YO IEUNG - 0xBCF6: 0xC218, //HANGUL SYLLABLE SIOS U - 0xBCF7: 0xC219, //HANGUL SYLLABLE SIOS U KIYEOK - 0xBCF8: 0xC21C, //HANGUL SYLLABLE SIOS U NIEUN - 0xBCF9: 0xC21F, //HANGUL SYLLABLE SIOS U TIKEUT - 0xBCFA: 0xC220, //HANGUL SYLLABLE SIOS U RIEUL - 0xBCFB: 0xC228, //HANGUL SYLLABLE SIOS U MIEUM - 0xBCFC: 0xC229, //HANGUL SYLLABLE SIOS U PIEUP - 0xBCFD: 0xC22B, //HANGUL SYLLABLE SIOS U SIOS - 0xBCFE: 0xC22D, //HANGUL SYLLABLE SIOS U IEUNG - 0xBD41: 0xD3D7, //HANGUL SYLLABLE PHIEUPH YE TIKEUT - 0xBD42: 0xD3D9, //HANGUL SYLLABLE PHIEUPH YE RIEULKIYEOK - 0xBD43: 0xD3DA, //HANGUL SYLLABLE PHIEUPH YE RIEULMIEUM - 0xBD44: 0xD3DB, //HANGUL SYLLABLE PHIEUPH YE RIEULPIEUP - 0xBD45: 0xD3DC, //HANGUL SYLLABLE PHIEUPH YE RIEULSIOS - 0xBD46: 0xD3DD, //HANGUL SYLLABLE PHIEUPH YE RIEULTHIEUTH - 0xBD47: 0xD3DE, //HANGUL SYLLABLE PHIEUPH YE RIEULPHIEUPH - 0xBD48: 0xD3DF, //HANGUL SYLLABLE PHIEUPH YE RIEULHIEUH - 0xBD49: 0xD3E0, //HANGUL SYLLABLE PHIEUPH YE MIEUM - 0xBD4A: 0xD3E2, //HANGUL SYLLABLE PHIEUPH YE PIEUPSIOS - 0xBD4B: 0xD3E4, //HANGUL SYLLABLE PHIEUPH YE SSANGSIOS - 0xBD4C: 0xD3E5, //HANGUL SYLLABLE PHIEUPH YE IEUNG - 0xBD4D: 0xD3E6, //HANGUL SYLLABLE PHIEUPH YE CIEUC - 0xBD4E: 0xD3E7, //HANGUL SYLLABLE PHIEUPH YE CHIEUCH - 0xBD4F: 0xD3E8, //HANGUL SYLLABLE PHIEUPH YE KHIEUKH - 0xBD50: 0xD3E9, //HANGUL SYLLABLE PHIEUPH YE THIEUTH - 0xBD51: 0xD3EA, //HANGUL SYLLABLE PHIEUPH YE PHIEUPH - 0xBD52: 0xD3EB, //HANGUL SYLLABLE PHIEUPH YE HIEUH - 0xBD53: 0xD3EE, //HANGUL SYLLABLE PHIEUPH O SSANGKIYEOK - 0xBD54: 0xD3EF, //HANGUL SYLLABLE PHIEUPH O KIYEOKSIOS - 0xBD55: 0xD3F1, //HANGUL SYLLABLE PHIEUPH O NIEUNCIEUC - 0xBD56: 0xD3F2, //HANGUL SYLLABLE PHIEUPH O NIEUNHIEUH - 0xBD57: 0xD3F3, //HANGUL SYLLABLE PHIEUPH O TIKEUT - 0xBD58: 0xD3F5, //HANGUL SYLLABLE PHIEUPH O RIEULKIYEOK - 0xBD59: 0xD3F6, //HANGUL SYLLABLE PHIEUPH O RIEULMIEUM - 0xBD5A: 0xD3F7, //HANGUL SYLLABLE PHIEUPH O RIEULPIEUP - 0xBD61: 0xD3F8, //HANGUL SYLLABLE PHIEUPH O RIEULSIOS - 0xBD62: 0xD3F9, //HANGUL SYLLABLE PHIEUPH O RIEULTHIEUTH - 0xBD63: 0xD3FA, //HANGUL SYLLABLE PHIEUPH O RIEULPHIEUPH - 0xBD64: 0xD3FB, //HANGUL SYLLABLE PHIEUPH O RIEULHIEUH - 0xBD65: 0xD3FE, //HANGUL SYLLABLE PHIEUPH O PIEUPSIOS - 0xBD66: 0xD400, //HANGUL SYLLABLE PHIEUPH O SSANGSIOS - 0xBD67: 0xD402, //HANGUL SYLLABLE PHIEUPH O CIEUC - 0xBD68: 0xD403, //HANGUL SYLLABLE PHIEUPH O CHIEUCH - 0xBD69: 0xD404, //HANGUL SYLLABLE PHIEUPH O KHIEUKH - 0xBD6A: 0xD405, //HANGUL SYLLABLE PHIEUPH O THIEUTH - 0xBD6B: 0xD406, //HANGUL SYLLABLE PHIEUPH O PHIEUPH - 0xBD6C: 0xD407, //HANGUL SYLLABLE PHIEUPH O HIEUH - 0xBD6D: 0xD409, //HANGUL SYLLABLE PHIEUPH WA KIYEOK - 0xBD6E: 0xD40A, //HANGUL SYLLABLE PHIEUPH WA SSANGKIYEOK - 0xBD6F: 0xD40B, //HANGUL SYLLABLE PHIEUPH WA KIYEOKSIOS - 0xBD70: 0xD40C, //HANGUL SYLLABLE PHIEUPH WA NIEUN - 0xBD71: 0xD40D, //HANGUL SYLLABLE PHIEUPH WA NIEUNCIEUC - 0xBD72: 0xD40E, //HANGUL SYLLABLE PHIEUPH WA NIEUNHIEUH - 0xBD73: 0xD40F, //HANGUL SYLLABLE PHIEUPH WA TIKEUT - 0xBD74: 0xD410, //HANGUL SYLLABLE PHIEUPH WA RIEUL - 0xBD75: 0xD411, //HANGUL SYLLABLE PHIEUPH WA RIEULKIYEOK - 0xBD76: 0xD412, //HANGUL SYLLABLE PHIEUPH WA RIEULMIEUM - 0xBD77: 0xD413, //HANGUL SYLLABLE PHIEUPH WA RIEULPIEUP - 0xBD78: 0xD414, //HANGUL SYLLABLE PHIEUPH WA RIEULSIOS - 0xBD79: 0xD415, //HANGUL SYLLABLE PHIEUPH WA RIEULTHIEUTH - 0xBD7A: 0xD416, //HANGUL SYLLABLE PHIEUPH WA RIEULPHIEUPH - 0xBD81: 0xD417, //HANGUL SYLLABLE PHIEUPH WA RIEULHIEUH - 0xBD82: 0xD418, //HANGUL SYLLABLE PHIEUPH WA MIEUM - 0xBD83: 0xD419, //HANGUL SYLLABLE PHIEUPH WA PIEUP - 0xBD84: 0xD41A, //HANGUL SYLLABLE PHIEUPH WA PIEUPSIOS - 0xBD85: 0xD41B, //HANGUL SYLLABLE PHIEUPH WA SIOS - 0xBD86: 0xD41C, //HANGUL SYLLABLE PHIEUPH WA SSANGSIOS - 0xBD87: 0xD41E, //HANGUL SYLLABLE PHIEUPH WA CIEUC - 0xBD88: 0xD41F, //HANGUL SYLLABLE PHIEUPH WA CHIEUCH - 0xBD89: 0xD420, //HANGUL SYLLABLE PHIEUPH WA KHIEUKH - 0xBD8A: 0xD421, //HANGUL SYLLABLE PHIEUPH WA THIEUTH - 0xBD8B: 0xD422, //HANGUL SYLLABLE PHIEUPH WA PHIEUPH - 0xBD8C: 0xD423, //HANGUL SYLLABLE PHIEUPH WA HIEUH - 0xBD8D: 0xD424, //HANGUL SYLLABLE PHIEUPH WAE - 0xBD8E: 0xD425, //HANGUL SYLLABLE PHIEUPH WAE KIYEOK - 0xBD8F: 0xD426, //HANGUL SYLLABLE PHIEUPH WAE SSANGKIYEOK - 0xBD90: 0xD427, //HANGUL SYLLABLE PHIEUPH WAE KIYEOKSIOS - 0xBD91: 0xD428, //HANGUL SYLLABLE PHIEUPH WAE NIEUN - 0xBD92: 0xD429, //HANGUL SYLLABLE PHIEUPH WAE NIEUNCIEUC - 0xBD93: 0xD42A, //HANGUL SYLLABLE PHIEUPH WAE NIEUNHIEUH - 0xBD94: 0xD42B, //HANGUL SYLLABLE PHIEUPH WAE TIKEUT - 0xBD95: 0xD42C, //HANGUL SYLLABLE PHIEUPH WAE RIEUL - 0xBD96: 0xD42D, //HANGUL SYLLABLE PHIEUPH WAE RIEULKIYEOK - 0xBD97: 0xD42E, //HANGUL SYLLABLE PHIEUPH WAE RIEULMIEUM - 0xBD98: 0xD42F, //HANGUL SYLLABLE PHIEUPH WAE RIEULPIEUP - 0xBD99: 0xD430, //HANGUL SYLLABLE PHIEUPH WAE RIEULSIOS - 0xBD9A: 0xD431, //HANGUL SYLLABLE PHIEUPH WAE RIEULTHIEUTH - 0xBD9B: 0xD432, //HANGUL SYLLABLE PHIEUPH WAE RIEULPHIEUPH - 0xBD9C: 0xD433, //HANGUL SYLLABLE PHIEUPH WAE RIEULHIEUH - 0xBD9D: 0xD434, //HANGUL SYLLABLE PHIEUPH WAE MIEUM - 0xBD9E: 0xD435, //HANGUL SYLLABLE PHIEUPH WAE PIEUP - 0xBD9F: 0xD436, //HANGUL SYLLABLE PHIEUPH WAE PIEUPSIOS - 0xBDA0: 0xD437, //HANGUL SYLLABLE PHIEUPH WAE SIOS - 0xBDA1: 0xC22F, //HANGUL SYLLABLE SIOS U CHIEUCH - 0xBDA2: 0xC231, //HANGUL SYLLABLE SIOS U THIEUTH - 0xBDA3: 0xC232, //HANGUL SYLLABLE SIOS U PHIEUPH - 0xBDA4: 0xC234, //HANGUL SYLLABLE SIOS WEO - 0xBDA5: 0xC248, //HANGUL SYLLABLE SIOS WEO SSANGSIOS - 0xBDA6: 0xC250, //HANGUL SYLLABLE SIOS WE - 0xBDA7: 0xC251, //HANGUL SYLLABLE SIOS WE KIYEOK - 0xBDA8: 0xC254, //HANGUL SYLLABLE SIOS WE NIEUN - 0xBDA9: 0xC258, //HANGUL SYLLABLE SIOS WE RIEUL - 0xBDAA: 0xC260, //HANGUL SYLLABLE SIOS WE MIEUM - 0xBDAB: 0xC265, //HANGUL SYLLABLE SIOS WE IEUNG - 0xBDAC: 0xC26C, //HANGUL SYLLABLE SIOS WI - 0xBDAD: 0xC26D, //HANGUL SYLLABLE SIOS WI KIYEOK - 0xBDAE: 0xC270, //HANGUL SYLLABLE SIOS WI NIEUN - 0xBDAF: 0xC274, //HANGUL SYLLABLE SIOS WI RIEUL - 0xBDB0: 0xC27C, //HANGUL SYLLABLE SIOS WI MIEUM - 0xBDB1: 0xC27D, //HANGUL SYLLABLE SIOS WI PIEUP - 0xBDB2: 0xC27F, //HANGUL SYLLABLE SIOS WI SIOS - 0xBDB3: 0xC281, //HANGUL SYLLABLE SIOS WI IEUNG - 0xBDB4: 0xC288, //HANGUL SYLLABLE SIOS YU - 0xBDB5: 0xC289, //HANGUL SYLLABLE SIOS YU KIYEOK - 0xBDB6: 0xC290, //HANGUL SYLLABLE SIOS YU RIEUL - 0xBDB7: 0xC298, //HANGUL SYLLABLE SIOS YU MIEUM - 0xBDB8: 0xC29B, //HANGUL SYLLABLE SIOS YU SIOS - 0xBDB9: 0xC29D, //HANGUL SYLLABLE SIOS YU IEUNG - 0xBDBA: 0xC2A4, //HANGUL SYLLABLE SIOS EU - 0xBDBB: 0xC2A5, //HANGUL SYLLABLE SIOS EU KIYEOK - 0xBDBC: 0xC2A8, //HANGUL SYLLABLE SIOS EU NIEUN - 0xBDBD: 0xC2AC, //HANGUL SYLLABLE SIOS EU RIEUL - 0xBDBE: 0xC2AD, //HANGUL SYLLABLE SIOS EU RIEULKIYEOK - 0xBDBF: 0xC2B4, //HANGUL SYLLABLE SIOS EU MIEUM - 0xBDC0: 0xC2B5, //HANGUL SYLLABLE SIOS EU PIEUP - 0xBDC1: 0xC2B7, //HANGUL SYLLABLE SIOS EU SIOS - 0xBDC2: 0xC2B9, //HANGUL SYLLABLE SIOS EU IEUNG - 0xBDC3: 0xC2DC, //HANGUL SYLLABLE SIOS I - 0xBDC4: 0xC2DD, //HANGUL SYLLABLE SIOS I KIYEOK - 0xBDC5: 0xC2E0, //HANGUL SYLLABLE SIOS I NIEUN - 0xBDC6: 0xC2E3, //HANGUL SYLLABLE SIOS I TIKEUT - 0xBDC7: 0xC2E4, //HANGUL SYLLABLE SIOS I RIEUL - 0xBDC8: 0xC2EB, //HANGUL SYLLABLE SIOS I RIEULHIEUH - 0xBDC9: 0xC2EC, //HANGUL SYLLABLE SIOS I MIEUM - 0xBDCA: 0xC2ED, //HANGUL SYLLABLE SIOS I PIEUP - 0xBDCB: 0xC2EF, //HANGUL SYLLABLE SIOS I SIOS - 0xBDCC: 0xC2F1, //HANGUL SYLLABLE SIOS I IEUNG - 0xBDCD: 0xC2F6, //HANGUL SYLLABLE SIOS I PHIEUPH - 0xBDCE: 0xC2F8, //HANGUL SYLLABLE SSANGSIOS A - 0xBDCF: 0xC2F9, //HANGUL SYLLABLE SSANGSIOS A KIYEOK - 0xBDD0: 0xC2FB, //HANGUL SYLLABLE SSANGSIOS A KIYEOKSIOS - 0xBDD1: 0xC2FC, //HANGUL SYLLABLE SSANGSIOS A NIEUN - 0xBDD2: 0xC300, //HANGUL SYLLABLE SSANGSIOS A RIEUL - 0xBDD3: 0xC308, //HANGUL SYLLABLE SSANGSIOS A MIEUM - 0xBDD4: 0xC309, //HANGUL SYLLABLE SSANGSIOS A PIEUP - 0xBDD5: 0xC30C, //HANGUL SYLLABLE SSANGSIOS A SSANGSIOS - 0xBDD6: 0xC30D, //HANGUL SYLLABLE SSANGSIOS A IEUNG - 0xBDD7: 0xC313, //HANGUL SYLLABLE SSANGSIOS A HIEUH - 0xBDD8: 0xC314, //HANGUL SYLLABLE SSANGSIOS AE - 0xBDD9: 0xC315, //HANGUL SYLLABLE SSANGSIOS AE KIYEOK - 0xBDDA: 0xC318, //HANGUL SYLLABLE SSANGSIOS AE NIEUN - 0xBDDB: 0xC31C, //HANGUL SYLLABLE SSANGSIOS AE RIEUL - 0xBDDC: 0xC324, //HANGUL SYLLABLE SSANGSIOS AE MIEUM - 0xBDDD: 0xC325, //HANGUL SYLLABLE SSANGSIOS AE PIEUP - 0xBDDE: 0xC328, //HANGUL SYLLABLE SSANGSIOS AE SSANGSIOS - 0xBDDF: 0xC329, //HANGUL SYLLABLE SSANGSIOS AE IEUNG - 0xBDE0: 0xC345, //HANGUL SYLLABLE SSANGSIOS YA IEUNG - 0xBDE1: 0xC368, //HANGUL SYLLABLE SSANGSIOS EO - 0xBDE2: 0xC369, //HANGUL SYLLABLE SSANGSIOS EO KIYEOK - 0xBDE3: 0xC36C, //HANGUL SYLLABLE SSANGSIOS EO NIEUN - 0xBDE4: 0xC370, //HANGUL SYLLABLE SSANGSIOS EO RIEUL - 0xBDE5: 0xC372, //HANGUL SYLLABLE SSANGSIOS EO RIEULMIEUM - 0xBDE6: 0xC378, //HANGUL SYLLABLE SSANGSIOS EO MIEUM - 0xBDE7: 0xC379, //HANGUL SYLLABLE SSANGSIOS EO PIEUP - 0xBDE8: 0xC37C, //HANGUL SYLLABLE SSANGSIOS EO SSANGSIOS - 0xBDE9: 0xC37D, //HANGUL SYLLABLE SSANGSIOS EO IEUNG - 0xBDEA: 0xC384, //HANGUL SYLLABLE SSANGSIOS E - 0xBDEB: 0xC388, //HANGUL SYLLABLE SSANGSIOS E NIEUN - 0xBDEC: 0xC38C, //HANGUL SYLLABLE SSANGSIOS E RIEUL - 0xBDED: 0xC3C0, //HANGUL SYLLABLE SSANGSIOS YE NIEUN - 0xBDEE: 0xC3D8, //HANGUL SYLLABLE SSANGSIOS O - 0xBDEF: 0xC3D9, //HANGUL SYLLABLE SSANGSIOS O KIYEOK - 0xBDF0: 0xC3DC, //HANGUL SYLLABLE SSANGSIOS O NIEUN - 0xBDF1: 0xC3DF, //HANGUL SYLLABLE SSANGSIOS O TIKEUT - 0xBDF2: 0xC3E0, //HANGUL SYLLABLE SSANGSIOS O RIEUL - 0xBDF3: 0xC3E2, //HANGUL SYLLABLE SSANGSIOS O RIEULMIEUM - 0xBDF4: 0xC3E8, //HANGUL SYLLABLE SSANGSIOS O MIEUM - 0xBDF5: 0xC3E9, //HANGUL SYLLABLE SSANGSIOS O PIEUP - 0xBDF6: 0xC3ED, //HANGUL SYLLABLE SSANGSIOS O IEUNG - 0xBDF7: 0xC3F4, //HANGUL SYLLABLE SSANGSIOS WA - 0xBDF8: 0xC3F5, //HANGUL SYLLABLE SSANGSIOS WA KIYEOK - 0xBDF9: 0xC3F8, //HANGUL SYLLABLE SSANGSIOS WA NIEUN - 0xBDFA: 0xC408, //HANGUL SYLLABLE SSANGSIOS WA SSANGSIOS - 0xBDFB: 0xC410, //HANGUL SYLLABLE SSANGSIOS WAE - 0xBDFC: 0xC424, //HANGUL SYLLABLE SSANGSIOS WAE SSANGSIOS - 0xBDFD: 0xC42C, //HANGUL SYLLABLE SSANGSIOS OE - 0xBDFE: 0xC430, //HANGUL SYLLABLE SSANGSIOS OE NIEUN - 0xBE41: 0xD438, //HANGUL SYLLABLE PHIEUPH WAE SSANGSIOS - 0xBE42: 0xD439, //HANGUL SYLLABLE PHIEUPH WAE IEUNG - 0xBE43: 0xD43A, //HANGUL SYLLABLE PHIEUPH WAE CIEUC - 0xBE44: 0xD43B, //HANGUL SYLLABLE PHIEUPH WAE CHIEUCH - 0xBE45: 0xD43C, //HANGUL SYLLABLE PHIEUPH WAE KHIEUKH - 0xBE46: 0xD43D, //HANGUL SYLLABLE PHIEUPH WAE THIEUTH - 0xBE47: 0xD43E, //HANGUL SYLLABLE PHIEUPH WAE PHIEUPH - 0xBE48: 0xD43F, //HANGUL SYLLABLE PHIEUPH WAE HIEUH - 0xBE49: 0xD441, //HANGUL SYLLABLE PHIEUPH OE KIYEOK - 0xBE4A: 0xD442, //HANGUL SYLLABLE PHIEUPH OE SSANGKIYEOK - 0xBE4B: 0xD443, //HANGUL SYLLABLE PHIEUPH OE KIYEOKSIOS - 0xBE4C: 0xD445, //HANGUL SYLLABLE PHIEUPH OE NIEUNCIEUC - 0xBE4D: 0xD446, //HANGUL SYLLABLE PHIEUPH OE NIEUNHIEUH - 0xBE4E: 0xD447, //HANGUL SYLLABLE PHIEUPH OE TIKEUT - 0xBE4F: 0xD448, //HANGUL SYLLABLE PHIEUPH OE RIEUL - 0xBE50: 0xD449, //HANGUL SYLLABLE PHIEUPH OE RIEULKIYEOK - 0xBE51: 0xD44A, //HANGUL SYLLABLE PHIEUPH OE RIEULMIEUM - 0xBE52: 0xD44B, //HANGUL SYLLABLE PHIEUPH OE RIEULPIEUP - 0xBE53: 0xD44C, //HANGUL SYLLABLE PHIEUPH OE RIEULSIOS - 0xBE54: 0xD44D, //HANGUL SYLLABLE PHIEUPH OE RIEULTHIEUTH - 0xBE55: 0xD44E, //HANGUL SYLLABLE PHIEUPH OE RIEULPHIEUPH - 0xBE56: 0xD44F, //HANGUL SYLLABLE PHIEUPH OE RIEULHIEUH - 0xBE57: 0xD450, //HANGUL SYLLABLE PHIEUPH OE MIEUM - 0xBE58: 0xD451, //HANGUL SYLLABLE PHIEUPH OE PIEUP - 0xBE59: 0xD452, //HANGUL SYLLABLE PHIEUPH OE PIEUPSIOS - 0xBE5A: 0xD453, //HANGUL SYLLABLE PHIEUPH OE SIOS - 0xBE61: 0xD454, //HANGUL SYLLABLE PHIEUPH OE SSANGSIOS - 0xBE62: 0xD455, //HANGUL SYLLABLE PHIEUPH OE IEUNG - 0xBE63: 0xD456, //HANGUL SYLLABLE PHIEUPH OE CIEUC - 0xBE64: 0xD457, //HANGUL SYLLABLE PHIEUPH OE CHIEUCH - 0xBE65: 0xD458, //HANGUL SYLLABLE PHIEUPH OE KHIEUKH - 0xBE66: 0xD459, //HANGUL SYLLABLE PHIEUPH OE THIEUTH - 0xBE67: 0xD45A, //HANGUL SYLLABLE PHIEUPH OE PHIEUPH - 0xBE68: 0xD45B, //HANGUL SYLLABLE PHIEUPH OE HIEUH - 0xBE69: 0xD45D, //HANGUL SYLLABLE PHIEUPH YO KIYEOK - 0xBE6A: 0xD45E, //HANGUL SYLLABLE PHIEUPH YO SSANGKIYEOK - 0xBE6B: 0xD45F, //HANGUL SYLLABLE PHIEUPH YO KIYEOKSIOS - 0xBE6C: 0xD461, //HANGUL SYLLABLE PHIEUPH YO NIEUNCIEUC - 0xBE6D: 0xD462, //HANGUL SYLLABLE PHIEUPH YO NIEUNHIEUH - 0xBE6E: 0xD463, //HANGUL SYLLABLE PHIEUPH YO TIKEUT - 0xBE6F: 0xD465, //HANGUL SYLLABLE PHIEUPH YO RIEULKIYEOK - 0xBE70: 0xD466, //HANGUL SYLLABLE PHIEUPH YO RIEULMIEUM - 0xBE71: 0xD467, //HANGUL SYLLABLE PHIEUPH YO RIEULPIEUP - 0xBE72: 0xD468, //HANGUL SYLLABLE PHIEUPH YO RIEULSIOS - 0xBE73: 0xD469, //HANGUL SYLLABLE PHIEUPH YO RIEULTHIEUTH - 0xBE74: 0xD46A, //HANGUL SYLLABLE PHIEUPH YO RIEULPHIEUPH - 0xBE75: 0xD46B, //HANGUL SYLLABLE PHIEUPH YO RIEULHIEUH - 0xBE76: 0xD46C, //HANGUL SYLLABLE PHIEUPH YO MIEUM - 0xBE77: 0xD46E, //HANGUL SYLLABLE PHIEUPH YO PIEUPSIOS - 0xBE78: 0xD470, //HANGUL SYLLABLE PHIEUPH YO SSANGSIOS - 0xBE79: 0xD471, //HANGUL SYLLABLE PHIEUPH YO IEUNG - 0xBE7A: 0xD472, //HANGUL SYLLABLE PHIEUPH YO CIEUC - 0xBE81: 0xD473, //HANGUL SYLLABLE PHIEUPH YO CHIEUCH - 0xBE82: 0xD474, //HANGUL SYLLABLE PHIEUPH YO KHIEUKH - 0xBE83: 0xD475, //HANGUL SYLLABLE PHIEUPH YO THIEUTH - 0xBE84: 0xD476, //HANGUL SYLLABLE PHIEUPH YO PHIEUPH - 0xBE85: 0xD477, //HANGUL SYLLABLE PHIEUPH YO HIEUH - 0xBE86: 0xD47A, //HANGUL SYLLABLE PHIEUPH U SSANGKIYEOK - 0xBE87: 0xD47B, //HANGUL SYLLABLE PHIEUPH U KIYEOKSIOS - 0xBE88: 0xD47D, //HANGUL SYLLABLE PHIEUPH U NIEUNCIEUC - 0xBE89: 0xD47E, //HANGUL SYLLABLE PHIEUPH U NIEUNHIEUH - 0xBE8A: 0xD481, //HANGUL SYLLABLE PHIEUPH U RIEULKIYEOK - 0xBE8B: 0xD483, //HANGUL SYLLABLE PHIEUPH U RIEULPIEUP - 0xBE8C: 0xD484, //HANGUL SYLLABLE PHIEUPH U RIEULSIOS - 0xBE8D: 0xD485, //HANGUL SYLLABLE PHIEUPH U RIEULTHIEUTH - 0xBE8E: 0xD486, //HANGUL SYLLABLE PHIEUPH U RIEULPHIEUPH - 0xBE8F: 0xD487, //HANGUL SYLLABLE PHIEUPH U RIEULHIEUH - 0xBE90: 0xD48A, //HANGUL SYLLABLE PHIEUPH U PIEUPSIOS - 0xBE91: 0xD48C, //HANGUL SYLLABLE PHIEUPH U SSANGSIOS - 0xBE92: 0xD48E, //HANGUL SYLLABLE PHIEUPH U CIEUC - 0xBE93: 0xD48F, //HANGUL SYLLABLE PHIEUPH U CHIEUCH - 0xBE94: 0xD490, //HANGUL SYLLABLE PHIEUPH U KHIEUKH - 0xBE95: 0xD491, //HANGUL SYLLABLE PHIEUPH U THIEUTH - 0xBE96: 0xD492, //HANGUL SYLLABLE PHIEUPH U PHIEUPH - 0xBE97: 0xD493, //HANGUL SYLLABLE PHIEUPH U HIEUH - 0xBE98: 0xD495, //HANGUL SYLLABLE PHIEUPH WEO KIYEOK - 0xBE99: 0xD496, //HANGUL SYLLABLE PHIEUPH WEO SSANGKIYEOK - 0xBE9A: 0xD497, //HANGUL SYLLABLE PHIEUPH WEO KIYEOKSIOS - 0xBE9B: 0xD498, //HANGUL SYLLABLE PHIEUPH WEO NIEUN - 0xBE9C: 0xD499, //HANGUL SYLLABLE PHIEUPH WEO NIEUNCIEUC - 0xBE9D: 0xD49A, //HANGUL SYLLABLE PHIEUPH WEO NIEUNHIEUH - 0xBE9E: 0xD49B, //HANGUL SYLLABLE PHIEUPH WEO TIKEUT - 0xBE9F: 0xD49C, //HANGUL SYLLABLE PHIEUPH WEO RIEUL - 0xBEA0: 0xD49D, //HANGUL SYLLABLE PHIEUPH WEO RIEULKIYEOK - 0xBEA1: 0xC434, //HANGUL SYLLABLE SSANGSIOS OE RIEUL - 0xBEA2: 0xC43C, //HANGUL SYLLABLE SSANGSIOS OE MIEUM - 0xBEA3: 0xC43D, //HANGUL SYLLABLE SSANGSIOS OE PIEUP - 0xBEA4: 0xC448, //HANGUL SYLLABLE SSANGSIOS YO - 0xBEA5: 0xC464, //HANGUL SYLLABLE SSANGSIOS U - 0xBEA6: 0xC465, //HANGUL SYLLABLE SSANGSIOS U KIYEOK - 0xBEA7: 0xC468, //HANGUL SYLLABLE SSANGSIOS U NIEUN - 0xBEA8: 0xC46C, //HANGUL SYLLABLE SSANGSIOS U RIEUL - 0xBEA9: 0xC474, //HANGUL SYLLABLE SSANGSIOS U MIEUM - 0xBEAA: 0xC475, //HANGUL SYLLABLE SSANGSIOS U PIEUP - 0xBEAB: 0xC479, //HANGUL SYLLABLE SSANGSIOS U IEUNG - 0xBEAC: 0xC480, //HANGUL SYLLABLE SSANGSIOS WEO - 0xBEAD: 0xC494, //HANGUL SYLLABLE SSANGSIOS WEO SSANGSIOS - 0xBEAE: 0xC49C, //HANGUL SYLLABLE SSANGSIOS WE - 0xBEAF: 0xC4B8, //HANGUL SYLLABLE SSANGSIOS WI - 0xBEB0: 0xC4BC, //HANGUL SYLLABLE SSANGSIOS WI NIEUN - 0xBEB1: 0xC4E9, //HANGUL SYLLABLE SSANGSIOS YU IEUNG - 0xBEB2: 0xC4F0, //HANGUL SYLLABLE SSANGSIOS EU - 0xBEB3: 0xC4F1, //HANGUL SYLLABLE SSANGSIOS EU KIYEOK - 0xBEB4: 0xC4F4, //HANGUL SYLLABLE SSANGSIOS EU NIEUN - 0xBEB5: 0xC4F8, //HANGUL SYLLABLE SSANGSIOS EU RIEUL - 0xBEB6: 0xC4FA, //HANGUL SYLLABLE SSANGSIOS EU RIEULMIEUM - 0xBEB7: 0xC4FF, //HANGUL SYLLABLE SSANGSIOS EU RIEULHIEUH - 0xBEB8: 0xC500, //HANGUL SYLLABLE SSANGSIOS EU MIEUM - 0xBEB9: 0xC501, //HANGUL SYLLABLE SSANGSIOS EU PIEUP - 0xBEBA: 0xC50C, //HANGUL SYLLABLE SSANGSIOS YI - 0xBEBB: 0xC510, //HANGUL SYLLABLE SSANGSIOS YI NIEUN - 0xBEBC: 0xC514, //HANGUL SYLLABLE SSANGSIOS YI RIEUL - 0xBEBD: 0xC51C, //HANGUL SYLLABLE SSANGSIOS YI MIEUM - 0xBEBE: 0xC528, //HANGUL SYLLABLE SSANGSIOS I - 0xBEBF: 0xC529, //HANGUL SYLLABLE SSANGSIOS I KIYEOK - 0xBEC0: 0xC52C, //HANGUL SYLLABLE SSANGSIOS I NIEUN - 0xBEC1: 0xC530, //HANGUL SYLLABLE SSANGSIOS I RIEUL - 0xBEC2: 0xC538, //HANGUL SYLLABLE SSANGSIOS I MIEUM - 0xBEC3: 0xC539, //HANGUL SYLLABLE SSANGSIOS I PIEUP - 0xBEC4: 0xC53B, //HANGUL SYLLABLE SSANGSIOS I SIOS - 0xBEC5: 0xC53D, //HANGUL SYLLABLE SSANGSIOS I IEUNG - 0xBEC6: 0xC544, //HANGUL SYLLABLE IEUNG A - 0xBEC7: 0xC545, //HANGUL SYLLABLE IEUNG A KIYEOK - 0xBEC8: 0xC548, //HANGUL SYLLABLE IEUNG A NIEUN - 0xBEC9: 0xC549, //HANGUL SYLLABLE IEUNG A NIEUNCIEUC - 0xBECA: 0xC54A, //HANGUL SYLLABLE IEUNG A NIEUNHIEUH - 0xBECB: 0xC54C, //HANGUL SYLLABLE IEUNG A RIEUL - 0xBECC: 0xC54D, //HANGUL SYLLABLE IEUNG A RIEULKIYEOK - 0xBECD: 0xC54E, //HANGUL SYLLABLE IEUNG A RIEULMIEUM - 0xBECE: 0xC553, //HANGUL SYLLABLE IEUNG A RIEULHIEUH - 0xBECF: 0xC554, //HANGUL SYLLABLE IEUNG A MIEUM - 0xBED0: 0xC555, //HANGUL SYLLABLE IEUNG A PIEUP - 0xBED1: 0xC557, //HANGUL SYLLABLE IEUNG A SIOS - 0xBED2: 0xC558, //HANGUL SYLLABLE IEUNG A SSANGSIOS - 0xBED3: 0xC559, //HANGUL SYLLABLE IEUNG A IEUNG - 0xBED4: 0xC55D, //HANGUL SYLLABLE IEUNG A THIEUTH - 0xBED5: 0xC55E, //HANGUL SYLLABLE IEUNG A PHIEUPH - 0xBED6: 0xC560, //HANGUL SYLLABLE IEUNG AE - 0xBED7: 0xC561, //HANGUL SYLLABLE IEUNG AE KIYEOK - 0xBED8: 0xC564, //HANGUL SYLLABLE IEUNG AE NIEUN - 0xBED9: 0xC568, //HANGUL SYLLABLE IEUNG AE RIEUL - 0xBEDA: 0xC570, //HANGUL SYLLABLE IEUNG AE MIEUM - 0xBEDB: 0xC571, //HANGUL SYLLABLE IEUNG AE PIEUP - 0xBEDC: 0xC573, //HANGUL SYLLABLE IEUNG AE SIOS - 0xBEDD: 0xC574, //HANGUL SYLLABLE IEUNG AE SSANGSIOS - 0xBEDE: 0xC575, //HANGUL SYLLABLE IEUNG AE IEUNG - 0xBEDF: 0xC57C, //HANGUL SYLLABLE IEUNG YA - 0xBEE0: 0xC57D, //HANGUL SYLLABLE IEUNG YA KIYEOK - 0xBEE1: 0xC580, //HANGUL SYLLABLE IEUNG YA NIEUN - 0xBEE2: 0xC584, //HANGUL SYLLABLE IEUNG YA RIEUL - 0xBEE3: 0xC587, //HANGUL SYLLABLE IEUNG YA RIEULPIEUP - 0xBEE4: 0xC58C, //HANGUL SYLLABLE IEUNG YA MIEUM - 0xBEE5: 0xC58D, //HANGUL SYLLABLE IEUNG YA PIEUP - 0xBEE6: 0xC58F, //HANGUL SYLLABLE IEUNG YA SIOS - 0xBEE7: 0xC591, //HANGUL SYLLABLE IEUNG YA IEUNG - 0xBEE8: 0xC595, //HANGUL SYLLABLE IEUNG YA THIEUTH - 0xBEE9: 0xC597, //HANGUL SYLLABLE IEUNG YA HIEUH - 0xBEEA: 0xC598, //HANGUL SYLLABLE IEUNG YAE - 0xBEEB: 0xC59C, //HANGUL SYLLABLE IEUNG YAE NIEUN - 0xBEEC: 0xC5A0, //HANGUL SYLLABLE IEUNG YAE RIEUL - 0xBEED: 0xC5A9, //HANGUL SYLLABLE IEUNG YAE PIEUP - 0xBEEE: 0xC5B4, //HANGUL SYLLABLE IEUNG EO - 0xBEEF: 0xC5B5, //HANGUL SYLLABLE IEUNG EO KIYEOK - 0xBEF0: 0xC5B8, //HANGUL SYLLABLE IEUNG EO NIEUN - 0xBEF1: 0xC5B9, //HANGUL SYLLABLE IEUNG EO NIEUNCIEUC - 0xBEF2: 0xC5BB, //HANGUL SYLLABLE IEUNG EO TIKEUT - 0xBEF3: 0xC5BC, //HANGUL SYLLABLE IEUNG EO RIEUL - 0xBEF4: 0xC5BD, //HANGUL SYLLABLE IEUNG EO RIEULKIYEOK - 0xBEF5: 0xC5BE, //HANGUL SYLLABLE IEUNG EO RIEULMIEUM - 0xBEF6: 0xC5C4, //HANGUL SYLLABLE IEUNG EO MIEUM - 0xBEF7: 0xC5C5, //HANGUL SYLLABLE IEUNG EO PIEUP - 0xBEF8: 0xC5C6, //HANGUL SYLLABLE IEUNG EO PIEUPSIOS - 0xBEF9: 0xC5C7, //HANGUL SYLLABLE IEUNG EO SIOS - 0xBEFA: 0xC5C8, //HANGUL SYLLABLE IEUNG EO SSANGSIOS - 0xBEFB: 0xC5C9, //HANGUL SYLLABLE IEUNG EO IEUNG - 0xBEFC: 0xC5CA, //HANGUL SYLLABLE IEUNG EO CIEUC - 0xBEFD: 0xC5CC, //HANGUL SYLLABLE IEUNG EO KHIEUKH - 0xBEFE: 0xC5CE, //HANGUL SYLLABLE IEUNG EO PHIEUPH - 0xBF41: 0xD49E, //HANGUL SYLLABLE PHIEUPH WEO RIEULMIEUM - 0xBF42: 0xD49F, //HANGUL SYLLABLE PHIEUPH WEO RIEULPIEUP - 0xBF43: 0xD4A0, //HANGUL SYLLABLE PHIEUPH WEO RIEULSIOS - 0xBF44: 0xD4A1, //HANGUL SYLLABLE PHIEUPH WEO RIEULTHIEUTH - 0xBF45: 0xD4A2, //HANGUL SYLLABLE PHIEUPH WEO RIEULPHIEUPH - 0xBF46: 0xD4A3, //HANGUL SYLLABLE PHIEUPH WEO RIEULHIEUH - 0xBF47: 0xD4A4, //HANGUL SYLLABLE PHIEUPH WEO MIEUM - 0xBF48: 0xD4A5, //HANGUL SYLLABLE PHIEUPH WEO PIEUP - 0xBF49: 0xD4A6, //HANGUL SYLLABLE PHIEUPH WEO PIEUPSIOS - 0xBF4A: 0xD4A7, //HANGUL SYLLABLE PHIEUPH WEO SIOS - 0xBF4B: 0xD4A8, //HANGUL SYLLABLE PHIEUPH WEO SSANGSIOS - 0xBF4C: 0xD4AA, //HANGUL SYLLABLE PHIEUPH WEO CIEUC - 0xBF4D: 0xD4AB, //HANGUL SYLLABLE PHIEUPH WEO CHIEUCH - 0xBF4E: 0xD4AC, //HANGUL SYLLABLE PHIEUPH WEO KHIEUKH - 0xBF4F: 0xD4AD, //HANGUL SYLLABLE PHIEUPH WEO THIEUTH - 0xBF50: 0xD4AE, //HANGUL SYLLABLE PHIEUPH WEO PHIEUPH - 0xBF51: 0xD4AF, //HANGUL SYLLABLE PHIEUPH WEO HIEUH - 0xBF52: 0xD4B0, //HANGUL SYLLABLE PHIEUPH WE - 0xBF53: 0xD4B1, //HANGUL SYLLABLE PHIEUPH WE KIYEOK - 0xBF54: 0xD4B2, //HANGUL SYLLABLE PHIEUPH WE SSANGKIYEOK - 0xBF55: 0xD4B3, //HANGUL SYLLABLE PHIEUPH WE KIYEOKSIOS - 0xBF56: 0xD4B4, //HANGUL SYLLABLE PHIEUPH WE NIEUN - 0xBF57: 0xD4B5, //HANGUL SYLLABLE PHIEUPH WE NIEUNCIEUC - 0xBF58: 0xD4B6, //HANGUL SYLLABLE PHIEUPH WE NIEUNHIEUH - 0xBF59: 0xD4B7, //HANGUL SYLLABLE PHIEUPH WE TIKEUT - 0xBF5A: 0xD4B8, //HANGUL SYLLABLE PHIEUPH WE RIEUL - 0xBF61: 0xD4B9, //HANGUL SYLLABLE PHIEUPH WE RIEULKIYEOK - 0xBF62: 0xD4BA, //HANGUL SYLLABLE PHIEUPH WE RIEULMIEUM - 0xBF63: 0xD4BB, //HANGUL SYLLABLE PHIEUPH WE RIEULPIEUP - 0xBF64: 0xD4BC, //HANGUL SYLLABLE PHIEUPH WE RIEULSIOS - 0xBF65: 0xD4BD, //HANGUL SYLLABLE PHIEUPH WE RIEULTHIEUTH - 0xBF66: 0xD4BE, //HANGUL SYLLABLE PHIEUPH WE RIEULPHIEUPH - 0xBF67: 0xD4BF, //HANGUL SYLLABLE PHIEUPH WE RIEULHIEUH - 0xBF68: 0xD4C0, //HANGUL SYLLABLE PHIEUPH WE MIEUM - 0xBF69: 0xD4C1, //HANGUL SYLLABLE PHIEUPH WE PIEUP - 0xBF6A: 0xD4C2, //HANGUL SYLLABLE PHIEUPH WE PIEUPSIOS - 0xBF6B: 0xD4C3, //HANGUL SYLLABLE PHIEUPH WE SIOS - 0xBF6C: 0xD4C4, //HANGUL SYLLABLE PHIEUPH WE SSANGSIOS - 0xBF6D: 0xD4C5, //HANGUL SYLLABLE PHIEUPH WE IEUNG - 0xBF6E: 0xD4C6, //HANGUL SYLLABLE PHIEUPH WE CIEUC - 0xBF6F: 0xD4C7, //HANGUL SYLLABLE PHIEUPH WE CHIEUCH - 0xBF70: 0xD4C8, //HANGUL SYLLABLE PHIEUPH WE KHIEUKH - 0xBF71: 0xD4C9, //HANGUL SYLLABLE PHIEUPH WE THIEUTH - 0xBF72: 0xD4CA, //HANGUL SYLLABLE PHIEUPH WE PHIEUPH - 0xBF73: 0xD4CB, //HANGUL SYLLABLE PHIEUPH WE HIEUH - 0xBF74: 0xD4CD, //HANGUL SYLLABLE PHIEUPH WI KIYEOK - 0xBF75: 0xD4CE, //HANGUL SYLLABLE PHIEUPH WI SSANGKIYEOK - 0xBF76: 0xD4CF, //HANGUL SYLLABLE PHIEUPH WI KIYEOKSIOS - 0xBF77: 0xD4D1, //HANGUL SYLLABLE PHIEUPH WI NIEUNCIEUC - 0xBF78: 0xD4D2, //HANGUL SYLLABLE PHIEUPH WI NIEUNHIEUH - 0xBF79: 0xD4D3, //HANGUL SYLLABLE PHIEUPH WI TIKEUT - 0xBF7A: 0xD4D5, //HANGUL SYLLABLE PHIEUPH WI RIEULKIYEOK - 0xBF81: 0xD4D6, //HANGUL SYLLABLE PHIEUPH WI RIEULMIEUM - 0xBF82: 0xD4D7, //HANGUL SYLLABLE PHIEUPH WI RIEULPIEUP - 0xBF83: 0xD4D8, //HANGUL SYLLABLE PHIEUPH WI RIEULSIOS - 0xBF84: 0xD4D9, //HANGUL SYLLABLE PHIEUPH WI RIEULTHIEUTH - 0xBF85: 0xD4DA, //HANGUL SYLLABLE PHIEUPH WI RIEULPHIEUPH - 0xBF86: 0xD4DB, //HANGUL SYLLABLE PHIEUPH WI RIEULHIEUH - 0xBF87: 0xD4DD, //HANGUL SYLLABLE PHIEUPH WI PIEUP - 0xBF88: 0xD4DE, //HANGUL SYLLABLE PHIEUPH WI PIEUPSIOS - 0xBF89: 0xD4E0, //HANGUL SYLLABLE PHIEUPH WI SSANGSIOS - 0xBF8A: 0xD4E1, //HANGUL SYLLABLE PHIEUPH WI IEUNG - 0xBF8B: 0xD4E2, //HANGUL SYLLABLE PHIEUPH WI CIEUC - 0xBF8C: 0xD4E3, //HANGUL SYLLABLE PHIEUPH WI CHIEUCH - 0xBF8D: 0xD4E4, //HANGUL SYLLABLE PHIEUPH WI KHIEUKH - 0xBF8E: 0xD4E5, //HANGUL SYLLABLE PHIEUPH WI THIEUTH - 0xBF8F: 0xD4E6, //HANGUL SYLLABLE PHIEUPH WI PHIEUPH - 0xBF90: 0xD4E7, //HANGUL SYLLABLE PHIEUPH WI HIEUH - 0xBF91: 0xD4E9, //HANGUL SYLLABLE PHIEUPH YU KIYEOK - 0xBF92: 0xD4EA, //HANGUL SYLLABLE PHIEUPH YU SSANGKIYEOK - 0xBF93: 0xD4EB, //HANGUL SYLLABLE PHIEUPH YU KIYEOKSIOS - 0xBF94: 0xD4ED, //HANGUL SYLLABLE PHIEUPH YU NIEUNCIEUC - 0xBF95: 0xD4EE, //HANGUL SYLLABLE PHIEUPH YU NIEUNHIEUH - 0xBF96: 0xD4EF, //HANGUL SYLLABLE PHIEUPH YU TIKEUT - 0xBF97: 0xD4F1, //HANGUL SYLLABLE PHIEUPH YU RIEULKIYEOK - 0xBF98: 0xD4F2, //HANGUL SYLLABLE PHIEUPH YU RIEULMIEUM - 0xBF99: 0xD4F3, //HANGUL SYLLABLE PHIEUPH YU RIEULPIEUP - 0xBF9A: 0xD4F4, //HANGUL SYLLABLE PHIEUPH YU RIEULSIOS - 0xBF9B: 0xD4F5, //HANGUL SYLLABLE PHIEUPH YU RIEULTHIEUTH - 0xBF9C: 0xD4F6, //HANGUL SYLLABLE PHIEUPH YU RIEULPHIEUPH - 0xBF9D: 0xD4F7, //HANGUL SYLLABLE PHIEUPH YU RIEULHIEUH - 0xBF9E: 0xD4F9, //HANGUL SYLLABLE PHIEUPH YU PIEUP - 0xBF9F: 0xD4FA, //HANGUL SYLLABLE PHIEUPH YU PIEUPSIOS - 0xBFA0: 0xD4FC, //HANGUL SYLLABLE PHIEUPH YU SSANGSIOS - 0xBFA1: 0xC5D0, //HANGUL SYLLABLE IEUNG E - 0xBFA2: 0xC5D1, //HANGUL SYLLABLE IEUNG E KIYEOK - 0xBFA3: 0xC5D4, //HANGUL SYLLABLE IEUNG E NIEUN - 0xBFA4: 0xC5D8, //HANGUL SYLLABLE IEUNG E RIEUL - 0xBFA5: 0xC5E0, //HANGUL SYLLABLE IEUNG E MIEUM - 0xBFA6: 0xC5E1, //HANGUL SYLLABLE IEUNG E PIEUP - 0xBFA7: 0xC5E3, //HANGUL SYLLABLE IEUNG E SIOS - 0xBFA8: 0xC5E5, //HANGUL SYLLABLE IEUNG E IEUNG - 0xBFA9: 0xC5EC, //HANGUL SYLLABLE IEUNG YEO - 0xBFAA: 0xC5ED, //HANGUL SYLLABLE IEUNG YEO KIYEOK - 0xBFAB: 0xC5EE, //HANGUL SYLLABLE IEUNG YEO SSANGKIYEOK - 0xBFAC: 0xC5F0, //HANGUL SYLLABLE IEUNG YEO NIEUN - 0xBFAD: 0xC5F4, //HANGUL SYLLABLE IEUNG YEO RIEUL - 0xBFAE: 0xC5F6, //HANGUL SYLLABLE IEUNG YEO RIEULMIEUM - 0xBFAF: 0xC5F7, //HANGUL SYLLABLE IEUNG YEO RIEULPIEUP - 0xBFB0: 0xC5FC, //HANGUL SYLLABLE IEUNG YEO MIEUM - 0xBFB1: 0xC5FD, //HANGUL SYLLABLE IEUNG YEO PIEUP - 0xBFB2: 0xC5FE, //HANGUL SYLLABLE IEUNG YEO PIEUPSIOS - 0xBFB3: 0xC5FF, //HANGUL SYLLABLE IEUNG YEO SIOS - 0xBFB4: 0xC600, //HANGUL SYLLABLE IEUNG YEO SSANGSIOS - 0xBFB5: 0xC601, //HANGUL SYLLABLE IEUNG YEO IEUNG - 0xBFB6: 0xC605, //HANGUL SYLLABLE IEUNG YEO THIEUTH - 0xBFB7: 0xC606, //HANGUL SYLLABLE IEUNG YEO PHIEUPH - 0xBFB8: 0xC607, //HANGUL SYLLABLE IEUNG YEO HIEUH - 0xBFB9: 0xC608, //HANGUL SYLLABLE IEUNG YE - 0xBFBA: 0xC60C, //HANGUL SYLLABLE IEUNG YE NIEUN - 0xBFBB: 0xC610, //HANGUL SYLLABLE IEUNG YE RIEUL - 0xBFBC: 0xC618, //HANGUL SYLLABLE IEUNG YE MIEUM - 0xBFBD: 0xC619, //HANGUL SYLLABLE IEUNG YE PIEUP - 0xBFBE: 0xC61B, //HANGUL SYLLABLE IEUNG YE SIOS - 0xBFBF: 0xC61C, //HANGUL SYLLABLE IEUNG YE SSANGSIOS - 0xBFC0: 0xC624, //HANGUL SYLLABLE IEUNG O - 0xBFC1: 0xC625, //HANGUL SYLLABLE IEUNG O KIYEOK - 0xBFC2: 0xC628, //HANGUL SYLLABLE IEUNG O NIEUN - 0xBFC3: 0xC62C, //HANGUL SYLLABLE IEUNG O RIEUL - 0xBFC4: 0xC62D, //HANGUL SYLLABLE IEUNG O RIEULKIYEOK - 0xBFC5: 0xC62E, //HANGUL SYLLABLE IEUNG O RIEULMIEUM - 0xBFC6: 0xC630, //HANGUL SYLLABLE IEUNG O RIEULSIOS - 0xBFC7: 0xC633, //HANGUL SYLLABLE IEUNG O RIEULHIEUH - 0xBFC8: 0xC634, //HANGUL SYLLABLE IEUNG O MIEUM - 0xBFC9: 0xC635, //HANGUL SYLLABLE IEUNG O PIEUP - 0xBFCA: 0xC637, //HANGUL SYLLABLE IEUNG O SIOS - 0xBFCB: 0xC639, //HANGUL SYLLABLE IEUNG O IEUNG - 0xBFCC: 0xC63B, //HANGUL SYLLABLE IEUNG O CHIEUCH - 0xBFCD: 0xC640, //HANGUL SYLLABLE IEUNG WA - 0xBFCE: 0xC641, //HANGUL SYLLABLE IEUNG WA KIYEOK - 0xBFCF: 0xC644, //HANGUL SYLLABLE IEUNG WA NIEUN - 0xBFD0: 0xC648, //HANGUL SYLLABLE IEUNG WA RIEUL - 0xBFD1: 0xC650, //HANGUL SYLLABLE IEUNG WA MIEUM - 0xBFD2: 0xC651, //HANGUL SYLLABLE IEUNG WA PIEUP - 0xBFD3: 0xC653, //HANGUL SYLLABLE IEUNG WA SIOS - 0xBFD4: 0xC654, //HANGUL SYLLABLE IEUNG WA SSANGSIOS - 0xBFD5: 0xC655, //HANGUL SYLLABLE IEUNG WA IEUNG - 0xBFD6: 0xC65C, //HANGUL SYLLABLE IEUNG WAE - 0xBFD7: 0xC65D, //HANGUL SYLLABLE IEUNG WAE KIYEOK - 0xBFD8: 0xC660, //HANGUL SYLLABLE IEUNG WAE NIEUN - 0xBFD9: 0xC66C, //HANGUL SYLLABLE IEUNG WAE MIEUM - 0xBFDA: 0xC66F, //HANGUL SYLLABLE IEUNG WAE SIOS - 0xBFDB: 0xC671, //HANGUL SYLLABLE IEUNG WAE IEUNG - 0xBFDC: 0xC678, //HANGUL SYLLABLE IEUNG OE - 0xBFDD: 0xC679, //HANGUL SYLLABLE IEUNG OE KIYEOK - 0xBFDE: 0xC67C, //HANGUL SYLLABLE IEUNG OE NIEUN - 0xBFDF: 0xC680, //HANGUL SYLLABLE IEUNG OE RIEUL - 0xBFE0: 0xC688, //HANGUL SYLLABLE IEUNG OE MIEUM - 0xBFE1: 0xC689, //HANGUL SYLLABLE IEUNG OE PIEUP - 0xBFE2: 0xC68B, //HANGUL SYLLABLE IEUNG OE SIOS - 0xBFE3: 0xC68D, //HANGUL SYLLABLE IEUNG OE IEUNG - 0xBFE4: 0xC694, //HANGUL SYLLABLE IEUNG YO - 0xBFE5: 0xC695, //HANGUL SYLLABLE IEUNG YO KIYEOK - 0xBFE6: 0xC698, //HANGUL SYLLABLE IEUNG YO NIEUN - 0xBFE7: 0xC69C, //HANGUL SYLLABLE IEUNG YO RIEUL - 0xBFE8: 0xC6A4, //HANGUL SYLLABLE IEUNG YO MIEUM - 0xBFE9: 0xC6A5, //HANGUL SYLLABLE IEUNG YO PIEUP - 0xBFEA: 0xC6A7, //HANGUL SYLLABLE IEUNG YO SIOS - 0xBFEB: 0xC6A9, //HANGUL SYLLABLE IEUNG YO IEUNG - 0xBFEC: 0xC6B0, //HANGUL SYLLABLE IEUNG U - 0xBFED: 0xC6B1, //HANGUL SYLLABLE IEUNG U KIYEOK - 0xBFEE: 0xC6B4, //HANGUL SYLLABLE IEUNG U NIEUN - 0xBFEF: 0xC6B8, //HANGUL SYLLABLE IEUNG U RIEUL - 0xBFF0: 0xC6B9, //HANGUL SYLLABLE IEUNG U RIEULKIYEOK - 0xBFF1: 0xC6BA, //HANGUL SYLLABLE IEUNG U RIEULMIEUM - 0xBFF2: 0xC6C0, //HANGUL SYLLABLE IEUNG U MIEUM - 0xBFF3: 0xC6C1, //HANGUL SYLLABLE IEUNG U PIEUP - 0xBFF4: 0xC6C3, //HANGUL SYLLABLE IEUNG U SIOS - 0xBFF5: 0xC6C5, //HANGUL SYLLABLE IEUNG U IEUNG - 0xBFF6: 0xC6CC, //HANGUL SYLLABLE IEUNG WEO - 0xBFF7: 0xC6CD, //HANGUL SYLLABLE IEUNG WEO KIYEOK - 0xBFF8: 0xC6D0, //HANGUL SYLLABLE IEUNG WEO NIEUN - 0xBFF9: 0xC6D4, //HANGUL SYLLABLE IEUNG WEO RIEUL - 0xBFFA: 0xC6DC, //HANGUL SYLLABLE IEUNG WEO MIEUM - 0xBFFB: 0xC6DD, //HANGUL SYLLABLE IEUNG WEO PIEUP - 0xBFFC: 0xC6E0, //HANGUL SYLLABLE IEUNG WEO SSANGSIOS - 0xBFFD: 0xC6E1, //HANGUL SYLLABLE IEUNG WEO IEUNG - 0xBFFE: 0xC6E8, //HANGUL SYLLABLE IEUNG WE - 0xC041: 0xD4FE, //HANGUL SYLLABLE PHIEUPH YU CIEUC - 0xC042: 0xD4FF, //HANGUL SYLLABLE PHIEUPH YU CHIEUCH - 0xC043: 0xD500, //HANGUL SYLLABLE PHIEUPH YU KHIEUKH - 0xC044: 0xD501, //HANGUL SYLLABLE PHIEUPH YU THIEUTH - 0xC045: 0xD502, //HANGUL SYLLABLE PHIEUPH YU PHIEUPH - 0xC046: 0xD503, //HANGUL SYLLABLE PHIEUPH YU HIEUH - 0xC047: 0xD505, //HANGUL SYLLABLE PHIEUPH EU KIYEOK - 0xC048: 0xD506, //HANGUL SYLLABLE PHIEUPH EU SSANGKIYEOK - 0xC049: 0xD507, //HANGUL SYLLABLE PHIEUPH EU KIYEOKSIOS - 0xC04A: 0xD509, //HANGUL SYLLABLE PHIEUPH EU NIEUNCIEUC - 0xC04B: 0xD50A, //HANGUL SYLLABLE PHIEUPH EU NIEUNHIEUH - 0xC04C: 0xD50B, //HANGUL SYLLABLE PHIEUPH EU TIKEUT - 0xC04D: 0xD50D, //HANGUL SYLLABLE PHIEUPH EU RIEULKIYEOK - 0xC04E: 0xD50E, //HANGUL SYLLABLE PHIEUPH EU RIEULMIEUM - 0xC04F: 0xD50F, //HANGUL SYLLABLE PHIEUPH EU RIEULPIEUP - 0xC050: 0xD510, //HANGUL SYLLABLE PHIEUPH EU RIEULSIOS - 0xC051: 0xD511, //HANGUL SYLLABLE PHIEUPH EU RIEULTHIEUTH - 0xC052: 0xD512, //HANGUL SYLLABLE PHIEUPH EU RIEULPHIEUPH - 0xC053: 0xD513, //HANGUL SYLLABLE PHIEUPH EU RIEULHIEUH - 0xC054: 0xD516, //HANGUL SYLLABLE PHIEUPH EU PIEUPSIOS - 0xC055: 0xD518, //HANGUL SYLLABLE PHIEUPH EU SSANGSIOS - 0xC056: 0xD519, //HANGUL SYLLABLE PHIEUPH EU IEUNG - 0xC057: 0xD51A, //HANGUL SYLLABLE PHIEUPH EU CIEUC - 0xC058: 0xD51B, //HANGUL SYLLABLE PHIEUPH EU CHIEUCH - 0xC059: 0xD51C, //HANGUL SYLLABLE PHIEUPH EU KHIEUKH - 0xC05A: 0xD51D, //HANGUL SYLLABLE PHIEUPH EU THIEUTH - 0xC061: 0xD51E, //HANGUL SYLLABLE PHIEUPH EU PHIEUPH - 0xC062: 0xD51F, //HANGUL SYLLABLE PHIEUPH EU HIEUH - 0xC063: 0xD520, //HANGUL SYLLABLE PHIEUPH YI - 0xC064: 0xD521, //HANGUL SYLLABLE PHIEUPH YI KIYEOK - 0xC065: 0xD522, //HANGUL SYLLABLE PHIEUPH YI SSANGKIYEOK - 0xC066: 0xD523, //HANGUL SYLLABLE PHIEUPH YI KIYEOKSIOS - 0xC067: 0xD524, //HANGUL SYLLABLE PHIEUPH YI NIEUN - 0xC068: 0xD525, //HANGUL SYLLABLE PHIEUPH YI NIEUNCIEUC - 0xC069: 0xD526, //HANGUL SYLLABLE PHIEUPH YI NIEUNHIEUH - 0xC06A: 0xD527, //HANGUL SYLLABLE PHIEUPH YI TIKEUT - 0xC06B: 0xD528, //HANGUL SYLLABLE PHIEUPH YI RIEUL - 0xC06C: 0xD529, //HANGUL SYLLABLE PHIEUPH YI RIEULKIYEOK - 0xC06D: 0xD52A, //HANGUL SYLLABLE PHIEUPH YI RIEULMIEUM - 0xC06E: 0xD52B, //HANGUL SYLLABLE PHIEUPH YI RIEULPIEUP - 0xC06F: 0xD52C, //HANGUL SYLLABLE PHIEUPH YI RIEULSIOS - 0xC070: 0xD52D, //HANGUL SYLLABLE PHIEUPH YI RIEULTHIEUTH - 0xC071: 0xD52E, //HANGUL SYLLABLE PHIEUPH YI RIEULPHIEUPH - 0xC072: 0xD52F, //HANGUL SYLLABLE PHIEUPH YI RIEULHIEUH - 0xC073: 0xD530, //HANGUL SYLLABLE PHIEUPH YI MIEUM - 0xC074: 0xD531, //HANGUL SYLLABLE PHIEUPH YI PIEUP - 0xC075: 0xD532, //HANGUL SYLLABLE PHIEUPH YI PIEUPSIOS - 0xC076: 0xD533, //HANGUL SYLLABLE PHIEUPH YI SIOS - 0xC077: 0xD534, //HANGUL SYLLABLE PHIEUPH YI SSANGSIOS - 0xC078: 0xD535, //HANGUL SYLLABLE PHIEUPH YI IEUNG - 0xC079: 0xD536, //HANGUL SYLLABLE PHIEUPH YI CIEUC - 0xC07A: 0xD537, //HANGUL SYLLABLE PHIEUPH YI CHIEUCH - 0xC081: 0xD538, //HANGUL SYLLABLE PHIEUPH YI KHIEUKH - 0xC082: 0xD539, //HANGUL SYLLABLE PHIEUPH YI THIEUTH - 0xC083: 0xD53A, //HANGUL SYLLABLE PHIEUPH YI PHIEUPH - 0xC084: 0xD53B, //HANGUL SYLLABLE PHIEUPH YI HIEUH - 0xC085: 0xD53E, //HANGUL SYLLABLE PHIEUPH I SSANGKIYEOK - 0xC086: 0xD53F, //HANGUL SYLLABLE PHIEUPH I KIYEOKSIOS - 0xC087: 0xD541, //HANGUL SYLLABLE PHIEUPH I NIEUNCIEUC - 0xC088: 0xD542, //HANGUL SYLLABLE PHIEUPH I NIEUNHIEUH - 0xC089: 0xD543, //HANGUL SYLLABLE PHIEUPH I TIKEUT - 0xC08A: 0xD545, //HANGUL SYLLABLE PHIEUPH I RIEULKIYEOK - 0xC08B: 0xD546, //HANGUL SYLLABLE PHIEUPH I RIEULMIEUM - 0xC08C: 0xD547, //HANGUL SYLLABLE PHIEUPH I RIEULPIEUP - 0xC08D: 0xD548, //HANGUL SYLLABLE PHIEUPH I RIEULSIOS - 0xC08E: 0xD549, //HANGUL SYLLABLE PHIEUPH I RIEULTHIEUTH - 0xC08F: 0xD54A, //HANGUL SYLLABLE PHIEUPH I RIEULPHIEUPH - 0xC090: 0xD54B, //HANGUL SYLLABLE PHIEUPH I RIEULHIEUH - 0xC091: 0xD54E, //HANGUL SYLLABLE PHIEUPH I PIEUPSIOS - 0xC092: 0xD550, //HANGUL SYLLABLE PHIEUPH I SSANGSIOS - 0xC093: 0xD552, //HANGUL SYLLABLE PHIEUPH I CIEUC - 0xC094: 0xD553, //HANGUL SYLLABLE PHIEUPH I CHIEUCH - 0xC095: 0xD554, //HANGUL SYLLABLE PHIEUPH I KHIEUKH - 0xC096: 0xD555, //HANGUL SYLLABLE PHIEUPH I THIEUTH - 0xC097: 0xD556, //HANGUL SYLLABLE PHIEUPH I PHIEUPH - 0xC098: 0xD557, //HANGUL SYLLABLE PHIEUPH I HIEUH - 0xC099: 0xD55A, //HANGUL SYLLABLE HIEUH A SSANGKIYEOK - 0xC09A: 0xD55B, //HANGUL SYLLABLE HIEUH A KIYEOKSIOS - 0xC09B: 0xD55D, //HANGUL SYLLABLE HIEUH A NIEUNCIEUC - 0xC09C: 0xD55E, //HANGUL SYLLABLE HIEUH A NIEUNHIEUH - 0xC09D: 0xD55F, //HANGUL SYLLABLE HIEUH A TIKEUT - 0xC09E: 0xD561, //HANGUL SYLLABLE HIEUH A RIEULKIYEOK - 0xC09F: 0xD562, //HANGUL SYLLABLE HIEUH A RIEULMIEUM - 0xC0A0: 0xD563, //HANGUL SYLLABLE HIEUH A RIEULPIEUP - 0xC0A1: 0xC6E9, //HANGUL SYLLABLE IEUNG WE KIYEOK - 0xC0A2: 0xC6EC, //HANGUL SYLLABLE IEUNG WE NIEUN - 0xC0A3: 0xC6F0, //HANGUL SYLLABLE IEUNG WE RIEUL - 0xC0A4: 0xC6F8, //HANGUL SYLLABLE IEUNG WE MIEUM - 0xC0A5: 0xC6F9, //HANGUL SYLLABLE IEUNG WE PIEUP - 0xC0A6: 0xC6FD, //HANGUL SYLLABLE IEUNG WE IEUNG - 0xC0A7: 0xC704, //HANGUL SYLLABLE IEUNG WI - 0xC0A8: 0xC705, //HANGUL SYLLABLE IEUNG WI KIYEOK - 0xC0A9: 0xC708, //HANGUL SYLLABLE IEUNG WI NIEUN - 0xC0AA: 0xC70C, //HANGUL SYLLABLE IEUNG WI RIEUL - 0xC0AB: 0xC714, //HANGUL SYLLABLE IEUNG WI MIEUM - 0xC0AC: 0xC715, //HANGUL SYLLABLE IEUNG WI PIEUP - 0xC0AD: 0xC717, //HANGUL SYLLABLE IEUNG WI SIOS - 0xC0AE: 0xC719, //HANGUL SYLLABLE IEUNG WI IEUNG - 0xC0AF: 0xC720, //HANGUL SYLLABLE IEUNG YU - 0xC0B0: 0xC721, //HANGUL SYLLABLE IEUNG YU KIYEOK - 0xC0B1: 0xC724, //HANGUL SYLLABLE IEUNG YU NIEUN - 0xC0B2: 0xC728, //HANGUL SYLLABLE IEUNG YU RIEUL - 0xC0B3: 0xC730, //HANGUL SYLLABLE IEUNG YU MIEUM - 0xC0B4: 0xC731, //HANGUL SYLLABLE IEUNG YU PIEUP - 0xC0B5: 0xC733, //HANGUL SYLLABLE IEUNG YU SIOS - 0xC0B6: 0xC735, //HANGUL SYLLABLE IEUNG YU IEUNG - 0xC0B7: 0xC737, //HANGUL SYLLABLE IEUNG YU CHIEUCH - 0xC0B8: 0xC73C, //HANGUL SYLLABLE IEUNG EU - 0xC0B9: 0xC73D, //HANGUL SYLLABLE IEUNG EU KIYEOK - 0xC0BA: 0xC740, //HANGUL SYLLABLE IEUNG EU NIEUN - 0xC0BB: 0xC744, //HANGUL SYLLABLE IEUNG EU RIEUL - 0xC0BC: 0xC74A, //HANGUL SYLLABLE IEUNG EU RIEULPHIEUPH - 0xC0BD: 0xC74C, //HANGUL SYLLABLE IEUNG EU MIEUM - 0xC0BE: 0xC74D, //HANGUL SYLLABLE IEUNG EU PIEUP - 0xC0BF: 0xC74F, //HANGUL SYLLABLE IEUNG EU SIOS - 0xC0C0: 0xC751, //HANGUL SYLLABLE IEUNG EU IEUNG - 0xC0C1: 0xC752, //HANGUL SYLLABLE IEUNG EU CIEUC - 0xC0C2: 0xC753, //HANGUL SYLLABLE IEUNG EU CHIEUCH - 0xC0C3: 0xC754, //HANGUL SYLLABLE IEUNG EU KHIEUKH - 0xC0C4: 0xC755, //HANGUL SYLLABLE IEUNG EU THIEUTH - 0xC0C5: 0xC756, //HANGUL SYLLABLE IEUNG EU PHIEUPH - 0xC0C6: 0xC757, //HANGUL SYLLABLE IEUNG EU HIEUH - 0xC0C7: 0xC758, //HANGUL SYLLABLE IEUNG YI - 0xC0C8: 0xC75C, //HANGUL SYLLABLE IEUNG YI NIEUN - 0xC0C9: 0xC760, //HANGUL SYLLABLE IEUNG YI RIEUL - 0xC0CA: 0xC768, //HANGUL SYLLABLE IEUNG YI MIEUM - 0xC0CB: 0xC76B, //HANGUL SYLLABLE IEUNG YI SIOS - 0xC0CC: 0xC774, //HANGUL SYLLABLE IEUNG I - 0xC0CD: 0xC775, //HANGUL SYLLABLE IEUNG I KIYEOK - 0xC0CE: 0xC778, //HANGUL SYLLABLE IEUNG I NIEUN - 0xC0CF: 0xC77C, //HANGUL SYLLABLE IEUNG I RIEUL - 0xC0D0: 0xC77D, //HANGUL SYLLABLE IEUNG I RIEULKIYEOK - 0xC0D1: 0xC77E, //HANGUL SYLLABLE IEUNG I RIEULMIEUM - 0xC0D2: 0xC783, //HANGUL SYLLABLE IEUNG I RIEULHIEUH - 0xC0D3: 0xC784, //HANGUL SYLLABLE IEUNG I MIEUM - 0xC0D4: 0xC785, //HANGUL SYLLABLE IEUNG I PIEUP - 0xC0D5: 0xC787, //HANGUL SYLLABLE IEUNG I SIOS - 0xC0D6: 0xC788, //HANGUL SYLLABLE IEUNG I SSANGSIOS - 0xC0D7: 0xC789, //HANGUL SYLLABLE IEUNG I IEUNG - 0xC0D8: 0xC78A, //HANGUL SYLLABLE IEUNG I CIEUC - 0xC0D9: 0xC78E, //HANGUL SYLLABLE IEUNG I PHIEUPH - 0xC0DA: 0xC790, //HANGUL SYLLABLE CIEUC A - 0xC0DB: 0xC791, //HANGUL SYLLABLE CIEUC A KIYEOK - 0xC0DC: 0xC794, //HANGUL SYLLABLE CIEUC A NIEUN - 0xC0DD: 0xC796, //HANGUL SYLLABLE CIEUC A NIEUNHIEUH - 0xC0DE: 0xC797, //HANGUL SYLLABLE CIEUC A TIKEUT - 0xC0DF: 0xC798, //HANGUL SYLLABLE CIEUC A RIEUL - 0xC0E0: 0xC79A, //HANGUL SYLLABLE CIEUC A RIEULMIEUM - 0xC0E1: 0xC7A0, //HANGUL SYLLABLE CIEUC A MIEUM - 0xC0E2: 0xC7A1, //HANGUL SYLLABLE CIEUC A PIEUP - 0xC0E3: 0xC7A3, //HANGUL SYLLABLE CIEUC A SIOS - 0xC0E4: 0xC7A4, //HANGUL SYLLABLE CIEUC A SSANGSIOS - 0xC0E5: 0xC7A5, //HANGUL SYLLABLE CIEUC A IEUNG - 0xC0E6: 0xC7A6, //HANGUL SYLLABLE CIEUC A CIEUC - 0xC0E7: 0xC7AC, //HANGUL SYLLABLE CIEUC AE - 0xC0E8: 0xC7AD, //HANGUL SYLLABLE CIEUC AE KIYEOK - 0xC0E9: 0xC7B0, //HANGUL SYLLABLE CIEUC AE NIEUN - 0xC0EA: 0xC7B4, //HANGUL SYLLABLE CIEUC AE RIEUL - 0xC0EB: 0xC7BC, //HANGUL SYLLABLE CIEUC AE MIEUM - 0xC0EC: 0xC7BD, //HANGUL SYLLABLE CIEUC AE PIEUP - 0xC0ED: 0xC7BF, //HANGUL SYLLABLE CIEUC AE SIOS - 0xC0EE: 0xC7C0, //HANGUL SYLLABLE CIEUC AE SSANGSIOS - 0xC0EF: 0xC7C1, //HANGUL SYLLABLE CIEUC AE IEUNG - 0xC0F0: 0xC7C8, //HANGUL SYLLABLE CIEUC YA - 0xC0F1: 0xC7C9, //HANGUL SYLLABLE CIEUC YA KIYEOK - 0xC0F2: 0xC7CC, //HANGUL SYLLABLE CIEUC YA NIEUN - 0xC0F3: 0xC7CE, //HANGUL SYLLABLE CIEUC YA NIEUNHIEUH - 0xC0F4: 0xC7D0, //HANGUL SYLLABLE CIEUC YA RIEUL - 0xC0F5: 0xC7D8, //HANGUL SYLLABLE CIEUC YA MIEUM - 0xC0F6: 0xC7DD, //HANGUL SYLLABLE CIEUC YA IEUNG - 0xC0F7: 0xC7E4, //HANGUL SYLLABLE CIEUC YAE - 0xC0F8: 0xC7E8, //HANGUL SYLLABLE CIEUC YAE NIEUN - 0xC0F9: 0xC7EC, //HANGUL SYLLABLE CIEUC YAE RIEUL - 0xC0FA: 0xC800, //HANGUL SYLLABLE CIEUC EO - 0xC0FB: 0xC801, //HANGUL SYLLABLE CIEUC EO KIYEOK - 0xC0FC: 0xC804, //HANGUL SYLLABLE CIEUC EO NIEUN - 0xC0FD: 0xC808, //HANGUL SYLLABLE CIEUC EO RIEUL - 0xC0FE: 0xC80A, //HANGUL SYLLABLE CIEUC EO RIEULMIEUM - 0xC141: 0xD564, //HANGUL SYLLABLE HIEUH A RIEULSIOS - 0xC142: 0xD566, //HANGUL SYLLABLE HIEUH A RIEULPHIEUPH - 0xC143: 0xD567, //HANGUL SYLLABLE HIEUH A RIEULHIEUH - 0xC144: 0xD56A, //HANGUL SYLLABLE HIEUH A PIEUPSIOS - 0xC145: 0xD56C, //HANGUL SYLLABLE HIEUH A SSANGSIOS - 0xC146: 0xD56E, //HANGUL SYLLABLE HIEUH A CIEUC - 0xC147: 0xD56F, //HANGUL SYLLABLE HIEUH A CHIEUCH - 0xC148: 0xD570, //HANGUL SYLLABLE HIEUH A KHIEUKH - 0xC149: 0xD571, //HANGUL SYLLABLE HIEUH A THIEUTH - 0xC14A: 0xD572, //HANGUL SYLLABLE HIEUH A PHIEUPH - 0xC14B: 0xD573, //HANGUL SYLLABLE HIEUH A HIEUH - 0xC14C: 0xD576, //HANGUL SYLLABLE HIEUH AE SSANGKIYEOK - 0xC14D: 0xD577, //HANGUL SYLLABLE HIEUH AE KIYEOKSIOS - 0xC14E: 0xD579, //HANGUL SYLLABLE HIEUH AE NIEUNCIEUC - 0xC14F: 0xD57A, //HANGUL SYLLABLE HIEUH AE NIEUNHIEUH - 0xC150: 0xD57B, //HANGUL SYLLABLE HIEUH AE TIKEUT - 0xC151: 0xD57D, //HANGUL SYLLABLE HIEUH AE RIEULKIYEOK - 0xC152: 0xD57E, //HANGUL SYLLABLE HIEUH AE RIEULMIEUM - 0xC153: 0xD57F, //HANGUL SYLLABLE HIEUH AE RIEULPIEUP - 0xC154: 0xD580, //HANGUL SYLLABLE HIEUH AE RIEULSIOS - 0xC155: 0xD581, //HANGUL SYLLABLE HIEUH AE RIEULTHIEUTH - 0xC156: 0xD582, //HANGUL SYLLABLE HIEUH AE RIEULPHIEUPH - 0xC157: 0xD583, //HANGUL SYLLABLE HIEUH AE RIEULHIEUH - 0xC158: 0xD586, //HANGUL SYLLABLE HIEUH AE PIEUPSIOS - 0xC159: 0xD58A, //HANGUL SYLLABLE HIEUH AE CIEUC - 0xC15A: 0xD58B, //HANGUL SYLLABLE HIEUH AE CHIEUCH - 0xC161: 0xD58C, //HANGUL SYLLABLE HIEUH AE KHIEUKH - 0xC162: 0xD58D, //HANGUL SYLLABLE HIEUH AE THIEUTH - 0xC163: 0xD58E, //HANGUL SYLLABLE HIEUH AE PHIEUPH - 0xC164: 0xD58F, //HANGUL SYLLABLE HIEUH AE HIEUH - 0xC165: 0xD591, //HANGUL SYLLABLE HIEUH YA KIYEOK - 0xC166: 0xD592, //HANGUL SYLLABLE HIEUH YA SSANGKIYEOK - 0xC167: 0xD593, //HANGUL SYLLABLE HIEUH YA KIYEOKSIOS - 0xC168: 0xD594, //HANGUL SYLLABLE HIEUH YA NIEUN - 0xC169: 0xD595, //HANGUL SYLLABLE HIEUH YA NIEUNCIEUC - 0xC16A: 0xD596, //HANGUL SYLLABLE HIEUH YA NIEUNHIEUH - 0xC16B: 0xD597, //HANGUL SYLLABLE HIEUH YA TIKEUT - 0xC16C: 0xD598, //HANGUL SYLLABLE HIEUH YA RIEUL - 0xC16D: 0xD599, //HANGUL SYLLABLE HIEUH YA RIEULKIYEOK - 0xC16E: 0xD59A, //HANGUL SYLLABLE HIEUH YA RIEULMIEUM - 0xC16F: 0xD59B, //HANGUL SYLLABLE HIEUH YA RIEULPIEUP - 0xC170: 0xD59C, //HANGUL SYLLABLE HIEUH YA RIEULSIOS - 0xC171: 0xD59D, //HANGUL SYLLABLE HIEUH YA RIEULTHIEUTH - 0xC172: 0xD59E, //HANGUL SYLLABLE HIEUH YA RIEULPHIEUPH - 0xC173: 0xD59F, //HANGUL SYLLABLE HIEUH YA RIEULHIEUH - 0xC174: 0xD5A0, //HANGUL SYLLABLE HIEUH YA MIEUM - 0xC175: 0xD5A1, //HANGUL SYLLABLE HIEUH YA PIEUP - 0xC176: 0xD5A2, //HANGUL SYLLABLE HIEUH YA PIEUPSIOS - 0xC177: 0xD5A3, //HANGUL SYLLABLE HIEUH YA SIOS - 0xC178: 0xD5A4, //HANGUL SYLLABLE HIEUH YA SSANGSIOS - 0xC179: 0xD5A6, //HANGUL SYLLABLE HIEUH YA CIEUC - 0xC17A: 0xD5A7, //HANGUL SYLLABLE HIEUH YA CHIEUCH - 0xC181: 0xD5A8, //HANGUL SYLLABLE HIEUH YA KHIEUKH - 0xC182: 0xD5A9, //HANGUL SYLLABLE HIEUH YA THIEUTH - 0xC183: 0xD5AA, //HANGUL SYLLABLE HIEUH YA PHIEUPH - 0xC184: 0xD5AB, //HANGUL SYLLABLE HIEUH YA HIEUH - 0xC185: 0xD5AC, //HANGUL SYLLABLE HIEUH YAE - 0xC186: 0xD5AD, //HANGUL SYLLABLE HIEUH YAE KIYEOK - 0xC187: 0xD5AE, //HANGUL SYLLABLE HIEUH YAE SSANGKIYEOK - 0xC188: 0xD5AF, //HANGUL SYLLABLE HIEUH YAE KIYEOKSIOS - 0xC189: 0xD5B0, //HANGUL SYLLABLE HIEUH YAE NIEUN - 0xC18A: 0xD5B1, //HANGUL SYLLABLE HIEUH YAE NIEUNCIEUC - 0xC18B: 0xD5B2, //HANGUL SYLLABLE HIEUH YAE NIEUNHIEUH - 0xC18C: 0xD5B3, //HANGUL SYLLABLE HIEUH YAE TIKEUT - 0xC18D: 0xD5B4, //HANGUL SYLLABLE HIEUH YAE RIEUL - 0xC18E: 0xD5B5, //HANGUL SYLLABLE HIEUH YAE RIEULKIYEOK - 0xC18F: 0xD5B6, //HANGUL SYLLABLE HIEUH YAE RIEULMIEUM - 0xC190: 0xD5B7, //HANGUL SYLLABLE HIEUH YAE RIEULPIEUP - 0xC191: 0xD5B8, //HANGUL SYLLABLE HIEUH YAE RIEULSIOS - 0xC192: 0xD5B9, //HANGUL SYLLABLE HIEUH YAE RIEULTHIEUTH - 0xC193: 0xD5BA, //HANGUL SYLLABLE HIEUH YAE RIEULPHIEUPH - 0xC194: 0xD5BB, //HANGUL SYLLABLE HIEUH YAE RIEULHIEUH - 0xC195: 0xD5BC, //HANGUL SYLLABLE HIEUH YAE MIEUM - 0xC196: 0xD5BD, //HANGUL SYLLABLE HIEUH YAE PIEUP - 0xC197: 0xD5BE, //HANGUL SYLLABLE HIEUH YAE PIEUPSIOS - 0xC198: 0xD5BF, //HANGUL SYLLABLE HIEUH YAE SIOS - 0xC199: 0xD5C0, //HANGUL SYLLABLE HIEUH YAE SSANGSIOS - 0xC19A: 0xD5C1, //HANGUL SYLLABLE HIEUH YAE IEUNG - 0xC19B: 0xD5C2, //HANGUL SYLLABLE HIEUH YAE CIEUC - 0xC19C: 0xD5C3, //HANGUL SYLLABLE HIEUH YAE CHIEUCH - 0xC19D: 0xD5C4, //HANGUL SYLLABLE HIEUH YAE KHIEUKH - 0xC19E: 0xD5C5, //HANGUL SYLLABLE HIEUH YAE THIEUTH - 0xC19F: 0xD5C6, //HANGUL SYLLABLE HIEUH YAE PHIEUPH - 0xC1A0: 0xD5C7, //HANGUL SYLLABLE HIEUH YAE HIEUH - 0xC1A1: 0xC810, //HANGUL SYLLABLE CIEUC EO MIEUM - 0xC1A2: 0xC811, //HANGUL SYLLABLE CIEUC EO PIEUP - 0xC1A3: 0xC813, //HANGUL SYLLABLE CIEUC EO SIOS - 0xC1A4: 0xC815, //HANGUL SYLLABLE CIEUC EO IEUNG - 0xC1A5: 0xC816, //HANGUL SYLLABLE CIEUC EO CIEUC - 0xC1A6: 0xC81C, //HANGUL SYLLABLE CIEUC E - 0xC1A7: 0xC81D, //HANGUL SYLLABLE CIEUC E KIYEOK - 0xC1A8: 0xC820, //HANGUL SYLLABLE CIEUC E NIEUN - 0xC1A9: 0xC824, //HANGUL SYLLABLE CIEUC E RIEUL - 0xC1AA: 0xC82C, //HANGUL SYLLABLE CIEUC E MIEUM - 0xC1AB: 0xC82D, //HANGUL SYLLABLE CIEUC E PIEUP - 0xC1AC: 0xC82F, //HANGUL SYLLABLE CIEUC E SIOS - 0xC1AD: 0xC831, //HANGUL SYLLABLE CIEUC E IEUNG - 0xC1AE: 0xC838, //HANGUL SYLLABLE CIEUC YEO - 0xC1AF: 0xC83C, //HANGUL SYLLABLE CIEUC YEO NIEUN - 0xC1B0: 0xC840, //HANGUL SYLLABLE CIEUC YEO RIEUL - 0xC1B1: 0xC848, //HANGUL SYLLABLE CIEUC YEO MIEUM - 0xC1B2: 0xC849, //HANGUL SYLLABLE CIEUC YEO PIEUP - 0xC1B3: 0xC84C, //HANGUL SYLLABLE CIEUC YEO SSANGSIOS - 0xC1B4: 0xC84D, //HANGUL SYLLABLE CIEUC YEO IEUNG - 0xC1B5: 0xC854, //HANGUL SYLLABLE CIEUC YE - 0xC1B6: 0xC870, //HANGUL SYLLABLE CIEUC O - 0xC1B7: 0xC871, //HANGUL SYLLABLE CIEUC O KIYEOK - 0xC1B8: 0xC874, //HANGUL SYLLABLE CIEUC O NIEUN - 0xC1B9: 0xC878, //HANGUL SYLLABLE CIEUC O RIEUL - 0xC1BA: 0xC87A, //HANGUL SYLLABLE CIEUC O RIEULMIEUM - 0xC1BB: 0xC880, //HANGUL SYLLABLE CIEUC O MIEUM - 0xC1BC: 0xC881, //HANGUL SYLLABLE CIEUC O PIEUP - 0xC1BD: 0xC883, //HANGUL SYLLABLE CIEUC O SIOS - 0xC1BE: 0xC885, //HANGUL SYLLABLE CIEUC O IEUNG - 0xC1BF: 0xC886, //HANGUL SYLLABLE CIEUC O CIEUC - 0xC1C0: 0xC887, //HANGUL SYLLABLE CIEUC O CHIEUCH - 0xC1C1: 0xC88B, //HANGUL SYLLABLE CIEUC O HIEUH - 0xC1C2: 0xC88C, //HANGUL SYLLABLE CIEUC WA - 0xC1C3: 0xC88D, //HANGUL SYLLABLE CIEUC WA KIYEOK - 0xC1C4: 0xC894, //HANGUL SYLLABLE CIEUC WA RIEUL - 0xC1C5: 0xC89D, //HANGUL SYLLABLE CIEUC WA PIEUP - 0xC1C6: 0xC89F, //HANGUL SYLLABLE CIEUC WA SIOS - 0xC1C7: 0xC8A1, //HANGUL SYLLABLE CIEUC WA IEUNG - 0xC1C8: 0xC8A8, //HANGUL SYLLABLE CIEUC WAE - 0xC1C9: 0xC8BC, //HANGUL SYLLABLE CIEUC WAE SSANGSIOS - 0xC1CA: 0xC8BD, //HANGUL SYLLABLE CIEUC WAE IEUNG - 0xC1CB: 0xC8C4, //HANGUL SYLLABLE CIEUC OE - 0xC1CC: 0xC8C8, //HANGUL SYLLABLE CIEUC OE NIEUN - 0xC1CD: 0xC8CC, //HANGUL SYLLABLE CIEUC OE RIEUL - 0xC1CE: 0xC8D4, //HANGUL SYLLABLE CIEUC OE MIEUM - 0xC1CF: 0xC8D5, //HANGUL SYLLABLE CIEUC OE PIEUP - 0xC1D0: 0xC8D7, //HANGUL SYLLABLE CIEUC OE SIOS - 0xC1D1: 0xC8D9, //HANGUL SYLLABLE CIEUC OE IEUNG - 0xC1D2: 0xC8E0, //HANGUL SYLLABLE CIEUC YO - 0xC1D3: 0xC8E1, //HANGUL SYLLABLE CIEUC YO KIYEOK - 0xC1D4: 0xC8E4, //HANGUL SYLLABLE CIEUC YO NIEUN - 0xC1D5: 0xC8F5, //HANGUL SYLLABLE CIEUC YO IEUNG - 0xC1D6: 0xC8FC, //HANGUL SYLLABLE CIEUC U - 0xC1D7: 0xC8FD, //HANGUL SYLLABLE CIEUC U KIYEOK - 0xC1D8: 0xC900, //HANGUL SYLLABLE CIEUC U NIEUN - 0xC1D9: 0xC904, //HANGUL SYLLABLE CIEUC U RIEUL - 0xC1DA: 0xC905, //HANGUL SYLLABLE CIEUC U RIEULKIYEOK - 0xC1DB: 0xC906, //HANGUL SYLLABLE CIEUC U RIEULMIEUM - 0xC1DC: 0xC90C, //HANGUL SYLLABLE CIEUC U MIEUM - 0xC1DD: 0xC90D, //HANGUL SYLLABLE CIEUC U PIEUP - 0xC1DE: 0xC90F, //HANGUL SYLLABLE CIEUC U SIOS - 0xC1DF: 0xC911, //HANGUL SYLLABLE CIEUC U IEUNG - 0xC1E0: 0xC918, //HANGUL SYLLABLE CIEUC WEO - 0xC1E1: 0xC92C, //HANGUL SYLLABLE CIEUC WEO SSANGSIOS - 0xC1E2: 0xC934, //HANGUL SYLLABLE CIEUC WE - 0xC1E3: 0xC950, //HANGUL SYLLABLE CIEUC WI - 0xC1E4: 0xC951, //HANGUL SYLLABLE CIEUC WI KIYEOK - 0xC1E5: 0xC954, //HANGUL SYLLABLE CIEUC WI NIEUN - 0xC1E6: 0xC958, //HANGUL SYLLABLE CIEUC WI RIEUL - 0xC1E7: 0xC960, //HANGUL SYLLABLE CIEUC WI MIEUM - 0xC1E8: 0xC961, //HANGUL SYLLABLE CIEUC WI PIEUP - 0xC1E9: 0xC963, //HANGUL SYLLABLE CIEUC WI SIOS - 0xC1EA: 0xC96C, //HANGUL SYLLABLE CIEUC YU - 0xC1EB: 0xC970, //HANGUL SYLLABLE CIEUC YU NIEUN - 0xC1EC: 0xC974, //HANGUL SYLLABLE CIEUC YU RIEUL - 0xC1ED: 0xC97C, //HANGUL SYLLABLE CIEUC YU MIEUM - 0xC1EE: 0xC988, //HANGUL SYLLABLE CIEUC EU - 0xC1EF: 0xC989, //HANGUL SYLLABLE CIEUC EU KIYEOK - 0xC1F0: 0xC98C, //HANGUL SYLLABLE CIEUC EU NIEUN - 0xC1F1: 0xC990, //HANGUL SYLLABLE CIEUC EU RIEUL - 0xC1F2: 0xC998, //HANGUL SYLLABLE CIEUC EU MIEUM - 0xC1F3: 0xC999, //HANGUL SYLLABLE CIEUC EU PIEUP - 0xC1F4: 0xC99B, //HANGUL SYLLABLE CIEUC EU SIOS - 0xC1F5: 0xC99D, //HANGUL SYLLABLE CIEUC EU IEUNG - 0xC1F6: 0xC9C0, //HANGUL SYLLABLE CIEUC I - 0xC1F7: 0xC9C1, //HANGUL SYLLABLE CIEUC I KIYEOK - 0xC1F8: 0xC9C4, //HANGUL SYLLABLE CIEUC I NIEUN - 0xC1F9: 0xC9C7, //HANGUL SYLLABLE CIEUC I TIKEUT - 0xC1FA: 0xC9C8, //HANGUL SYLLABLE CIEUC I RIEUL - 0xC1FB: 0xC9CA, //HANGUL SYLLABLE CIEUC I RIEULMIEUM - 0xC1FC: 0xC9D0, //HANGUL SYLLABLE CIEUC I MIEUM - 0xC1FD: 0xC9D1, //HANGUL SYLLABLE CIEUC I PIEUP - 0xC1FE: 0xC9D3, //HANGUL SYLLABLE CIEUC I SIOS - 0xC241: 0xD5CA, //HANGUL SYLLABLE HIEUH EO SSANGKIYEOK - 0xC242: 0xD5CB, //HANGUL SYLLABLE HIEUH EO KIYEOKSIOS - 0xC243: 0xD5CD, //HANGUL SYLLABLE HIEUH EO NIEUNCIEUC - 0xC244: 0xD5CE, //HANGUL SYLLABLE HIEUH EO NIEUNHIEUH - 0xC245: 0xD5CF, //HANGUL SYLLABLE HIEUH EO TIKEUT - 0xC246: 0xD5D1, //HANGUL SYLLABLE HIEUH EO RIEULKIYEOK - 0xC247: 0xD5D3, //HANGUL SYLLABLE HIEUH EO RIEULPIEUP - 0xC248: 0xD5D4, //HANGUL SYLLABLE HIEUH EO RIEULSIOS - 0xC249: 0xD5D5, //HANGUL SYLLABLE HIEUH EO RIEULTHIEUTH - 0xC24A: 0xD5D6, //HANGUL SYLLABLE HIEUH EO RIEULPHIEUPH - 0xC24B: 0xD5D7, //HANGUL SYLLABLE HIEUH EO RIEULHIEUH - 0xC24C: 0xD5DA, //HANGUL SYLLABLE HIEUH EO PIEUPSIOS - 0xC24D: 0xD5DC, //HANGUL SYLLABLE HIEUH EO SSANGSIOS - 0xC24E: 0xD5DE, //HANGUL SYLLABLE HIEUH EO CIEUC - 0xC24F: 0xD5DF, //HANGUL SYLLABLE HIEUH EO CHIEUCH - 0xC250: 0xD5E0, //HANGUL SYLLABLE HIEUH EO KHIEUKH - 0xC251: 0xD5E1, //HANGUL SYLLABLE HIEUH EO THIEUTH - 0xC252: 0xD5E2, //HANGUL SYLLABLE HIEUH EO PHIEUPH - 0xC253: 0xD5E3, //HANGUL SYLLABLE HIEUH EO HIEUH - 0xC254: 0xD5E6, //HANGUL SYLLABLE HIEUH E SSANGKIYEOK - 0xC255: 0xD5E7, //HANGUL SYLLABLE HIEUH E KIYEOKSIOS - 0xC256: 0xD5E9, //HANGUL SYLLABLE HIEUH E NIEUNCIEUC - 0xC257: 0xD5EA, //HANGUL SYLLABLE HIEUH E NIEUNHIEUH - 0xC258: 0xD5EB, //HANGUL SYLLABLE HIEUH E TIKEUT - 0xC259: 0xD5ED, //HANGUL SYLLABLE HIEUH E RIEULKIYEOK - 0xC25A: 0xD5EE, //HANGUL SYLLABLE HIEUH E RIEULMIEUM - 0xC261: 0xD5EF, //HANGUL SYLLABLE HIEUH E RIEULPIEUP - 0xC262: 0xD5F0, //HANGUL SYLLABLE HIEUH E RIEULSIOS - 0xC263: 0xD5F1, //HANGUL SYLLABLE HIEUH E RIEULTHIEUTH - 0xC264: 0xD5F2, //HANGUL SYLLABLE HIEUH E RIEULPHIEUPH - 0xC265: 0xD5F3, //HANGUL SYLLABLE HIEUH E RIEULHIEUH - 0xC266: 0xD5F6, //HANGUL SYLLABLE HIEUH E PIEUPSIOS - 0xC267: 0xD5F8, //HANGUL SYLLABLE HIEUH E SSANGSIOS - 0xC268: 0xD5FA, //HANGUL SYLLABLE HIEUH E CIEUC - 0xC269: 0xD5FB, //HANGUL SYLLABLE HIEUH E CHIEUCH - 0xC26A: 0xD5FC, //HANGUL SYLLABLE HIEUH E KHIEUKH - 0xC26B: 0xD5FD, //HANGUL SYLLABLE HIEUH E THIEUTH - 0xC26C: 0xD5FE, //HANGUL SYLLABLE HIEUH E PHIEUPH - 0xC26D: 0xD5FF, //HANGUL SYLLABLE HIEUH E HIEUH - 0xC26E: 0xD602, //HANGUL SYLLABLE HIEUH YEO SSANGKIYEOK - 0xC26F: 0xD603, //HANGUL SYLLABLE HIEUH YEO KIYEOKSIOS - 0xC270: 0xD605, //HANGUL SYLLABLE HIEUH YEO NIEUNCIEUC - 0xC271: 0xD606, //HANGUL SYLLABLE HIEUH YEO NIEUNHIEUH - 0xC272: 0xD607, //HANGUL SYLLABLE HIEUH YEO TIKEUT - 0xC273: 0xD609, //HANGUL SYLLABLE HIEUH YEO RIEULKIYEOK - 0xC274: 0xD60A, //HANGUL SYLLABLE HIEUH YEO RIEULMIEUM - 0xC275: 0xD60B, //HANGUL SYLLABLE HIEUH YEO RIEULPIEUP - 0xC276: 0xD60C, //HANGUL SYLLABLE HIEUH YEO RIEULSIOS - 0xC277: 0xD60D, //HANGUL SYLLABLE HIEUH YEO RIEULTHIEUTH - 0xC278: 0xD60E, //HANGUL SYLLABLE HIEUH YEO RIEULPHIEUPH - 0xC279: 0xD60F, //HANGUL SYLLABLE HIEUH YEO RIEULHIEUH - 0xC27A: 0xD612, //HANGUL SYLLABLE HIEUH YEO PIEUPSIOS - 0xC281: 0xD616, //HANGUL SYLLABLE HIEUH YEO CIEUC - 0xC282: 0xD617, //HANGUL SYLLABLE HIEUH YEO CHIEUCH - 0xC283: 0xD618, //HANGUL SYLLABLE HIEUH YEO KHIEUKH - 0xC284: 0xD619, //HANGUL SYLLABLE HIEUH YEO THIEUTH - 0xC285: 0xD61A, //HANGUL SYLLABLE HIEUH YEO PHIEUPH - 0xC286: 0xD61B, //HANGUL SYLLABLE HIEUH YEO HIEUH - 0xC287: 0xD61D, //HANGUL SYLLABLE HIEUH YE KIYEOK - 0xC288: 0xD61E, //HANGUL SYLLABLE HIEUH YE SSANGKIYEOK - 0xC289: 0xD61F, //HANGUL SYLLABLE HIEUH YE KIYEOKSIOS - 0xC28A: 0xD621, //HANGUL SYLLABLE HIEUH YE NIEUNCIEUC - 0xC28B: 0xD622, //HANGUL SYLLABLE HIEUH YE NIEUNHIEUH - 0xC28C: 0xD623, //HANGUL SYLLABLE HIEUH YE TIKEUT - 0xC28D: 0xD625, //HANGUL SYLLABLE HIEUH YE RIEULKIYEOK - 0xC28E: 0xD626, //HANGUL SYLLABLE HIEUH YE RIEULMIEUM - 0xC28F: 0xD627, //HANGUL SYLLABLE HIEUH YE RIEULPIEUP - 0xC290: 0xD628, //HANGUL SYLLABLE HIEUH YE RIEULSIOS - 0xC291: 0xD629, //HANGUL SYLLABLE HIEUH YE RIEULTHIEUTH - 0xC292: 0xD62A, //HANGUL SYLLABLE HIEUH YE RIEULPHIEUPH - 0xC293: 0xD62B, //HANGUL SYLLABLE HIEUH YE RIEULHIEUH - 0xC294: 0xD62C, //HANGUL SYLLABLE HIEUH YE MIEUM - 0xC295: 0xD62E, //HANGUL SYLLABLE HIEUH YE PIEUPSIOS - 0xC296: 0xD62F, //HANGUL SYLLABLE HIEUH YE SIOS - 0xC297: 0xD630, //HANGUL SYLLABLE HIEUH YE SSANGSIOS - 0xC298: 0xD631, //HANGUL SYLLABLE HIEUH YE IEUNG - 0xC299: 0xD632, //HANGUL SYLLABLE HIEUH YE CIEUC - 0xC29A: 0xD633, //HANGUL SYLLABLE HIEUH YE CHIEUCH - 0xC29B: 0xD634, //HANGUL SYLLABLE HIEUH YE KHIEUKH - 0xC29C: 0xD635, //HANGUL SYLLABLE HIEUH YE THIEUTH - 0xC29D: 0xD636, //HANGUL SYLLABLE HIEUH YE PHIEUPH - 0xC29E: 0xD637, //HANGUL SYLLABLE HIEUH YE HIEUH - 0xC29F: 0xD63A, //HANGUL SYLLABLE HIEUH O SSANGKIYEOK - 0xC2A0: 0xD63B, //HANGUL SYLLABLE HIEUH O KIYEOKSIOS - 0xC2A1: 0xC9D5, //HANGUL SYLLABLE CIEUC I IEUNG - 0xC2A2: 0xC9D6, //HANGUL SYLLABLE CIEUC I CIEUC - 0xC2A3: 0xC9D9, //HANGUL SYLLABLE CIEUC I THIEUTH - 0xC2A4: 0xC9DA, //HANGUL SYLLABLE CIEUC I PHIEUPH - 0xC2A5: 0xC9DC, //HANGUL SYLLABLE SSANGCIEUC A - 0xC2A6: 0xC9DD, //HANGUL SYLLABLE SSANGCIEUC A KIYEOK - 0xC2A7: 0xC9E0, //HANGUL SYLLABLE SSANGCIEUC A NIEUN - 0xC2A8: 0xC9E2, //HANGUL SYLLABLE SSANGCIEUC A NIEUNHIEUH - 0xC2A9: 0xC9E4, //HANGUL SYLLABLE SSANGCIEUC A RIEUL - 0xC2AA: 0xC9E7, //HANGUL SYLLABLE SSANGCIEUC A RIEULPIEUP - 0xC2AB: 0xC9EC, //HANGUL SYLLABLE SSANGCIEUC A MIEUM - 0xC2AC: 0xC9ED, //HANGUL SYLLABLE SSANGCIEUC A PIEUP - 0xC2AD: 0xC9EF, //HANGUL SYLLABLE SSANGCIEUC A SIOS - 0xC2AE: 0xC9F0, //HANGUL SYLLABLE SSANGCIEUC A SSANGSIOS - 0xC2AF: 0xC9F1, //HANGUL SYLLABLE SSANGCIEUC A IEUNG - 0xC2B0: 0xC9F8, //HANGUL SYLLABLE SSANGCIEUC AE - 0xC2B1: 0xC9F9, //HANGUL SYLLABLE SSANGCIEUC AE KIYEOK - 0xC2B2: 0xC9FC, //HANGUL SYLLABLE SSANGCIEUC AE NIEUN - 0xC2B3: 0xCA00, //HANGUL SYLLABLE SSANGCIEUC AE RIEUL - 0xC2B4: 0xCA08, //HANGUL SYLLABLE SSANGCIEUC AE MIEUM - 0xC2B5: 0xCA09, //HANGUL SYLLABLE SSANGCIEUC AE PIEUP - 0xC2B6: 0xCA0B, //HANGUL SYLLABLE SSANGCIEUC AE SIOS - 0xC2B7: 0xCA0C, //HANGUL SYLLABLE SSANGCIEUC AE SSANGSIOS - 0xC2B8: 0xCA0D, //HANGUL SYLLABLE SSANGCIEUC AE IEUNG - 0xC2B9: 0xCA14, //HANGUL SYLLABLE SSANGCIEUC YA - 0xC2BA: 0xCA18, //HANGUL SYLLABLE SSANGCIEUC YA NIEUN - 0xC2BB: 0xCA29, //HANGUL SYLLABLE SSANGCIEUC YA IEUNG - 0xC2BC: 0xCA4C, //HANGUL SYLLABLE SSANGCIEUC EO - 0xC2BD: 0xCA4D, //HANGUL SYLLABLE SSANGCIEUC EO KIYEOK - 0xC2BE: 0xCA50, //HANGUL SYLLABLE SSANGCIEUC EO NIEUN - 0xC2BF: 0xCA54, //HANGUL SYLLABLE SSANGCIEUC EO RIEUL - 0xC2C0: 0xCA5C, //HANGUL SYLLABLE SSANGCIEUC EO MIEUM - 0xC2C1: 0xCA5D, //HANGUL SYLLABLE SSANGCIEUC EO PIEUP - 0xC2C2: 0xCA5F, //HANGUL SYLLABLE SSANGCIEUC EO SIOS - 0xC2C3: 0xCA60, //HANGUL SYLLABLE SSANGCIEUC EO SSANGSIOS - 0xC2C4: 0xCA61, //HANGUL SYLLABLE SSANGCIEUC EO IEUNG - 0xC2C5: 0xCA68, //HANGUL SYLLABLE SSANGCIEUC E - 0xC2C6: 0xCA7D, //HANGUL SYLLABLE SSANGCIEUC E IEUNG - 0xC2C7: 0xCA84, //HANGUL SYLLABLE SSANGCIEUC YEO - 0xC2C8: 0xCA98, //HANGUL SYLLABLE SSANGCIEUC YEO SSANGSIOS - 0xC2C9: 0xCABC, //HANGUL SYLLABLE SSANGCIEUC O - 0xC2CA: 0xCABD, //HANGUL SYLLABLE SSANGCIEUC O KIYEOK - 0xC2CB: 0xCAC0, //HANGUL SYLLABLE SSANGCIEUC O NIEUN - 0xC2CC: 0xCAC4, //HANGUL SYLLABLE SSANGCIEUC O RIEUL - 0xC2CD: 0xCACC, //HANGUL SYLLABLE SSANGCIEUC O MIEUM - 0xC2CE: 0xCACD, //HANGUL SYLLABLE SSANGCIEUC O PIEUP - 0xC2CF: 0xCACF, //HANGUL SYLLABLE SSANGCIEUC O SIOS - 0xC2D0: 0xCAD1, //HANGUL SYLLABLE SSANGCIEUC O IEUNG - 0xC2D1: 0xCAD3, //HANGUL SYLLABLE SSANGCIEUC O CHIEUCH - 0xC2D2: 0xCAD8, //HANGUL SYLLABLE SSANGCIEUC WA - 0xC2D3: 0xCAD9, //HANGUL SYLLABLE SSANGCIEUC WA KIYEOK - 0xC2D4: 0xCAE0, //HANGUL SYLLABLE SSANGCIEUC WA RIEUL - 0xC2D5: 0xCAEC, //HANGUL SYLLABLE SSANGCIEUC WA SSANGSIOS - 0xC2D6: 0xCAF4, //HANGUL SYLLABLE SSANGCIEUC WAE - 0xC2D7: 0xCB08, //HANGUL SYLLABLE SSANGCIEUC WAE SSANGSIOS - 0xC2D8: 0xCB10, //HANGUL SYLLABLE SSANGCIEUC OE - 0xC2D9: 0xCB14, //HANGUL SYLLABLE SSANGCIEUC OE NIEUN - 0xC2DA: 0xCB18, //HANGUL SYLLABLE SSANGCIEUC OE RIEUL - 0xC2DB: 0xCB20, //HANGUL SYLLABLE SSANGCIEUC OE MIEUM - 0xC2DC: 0xCB21, //HANGUL SYLLABLE SSANGCIEUC OE PIEUP - 0xC2DD: 0xCB41, //HANGUL SYLLABLE SSANGCIEUC YO IEUNG - 0xC2DE: 0xCB48, //HANGUL SYLLABLE SSANGCIEUC U - 0xC2DF: 0xCB49, //HANGUL SYLLABLE SSANGCIEUC U KIYEOK - 0xC2E0: 0xCB4C, //HANGUL SYLLABLE SSANGCIEUC U NIEUN - 0xC2E1: 0xCB50, //HANGUL SYLLABLE SSANGCIEUC U RIEUL - 0xC2E2: 0xCB58, //HANGUL SYLLABLE SSANGCIEUC U MIEUM - 0xC2E3: 0xCB59, //HANGUL SYLLABLE SSANGCIEUC U PIEUP - 0xC2E4: 0xCB5D, //HANGUL SYLLABLE SSANGCIEUC U IEUNG - 0xC2E5: 0xCB64, //HANGUL SYLLABLE SSANGCIEUC WEO - 0xC2E6: 0xCB78, //HANGUL SYLLABLE SSANGCIEUC WEO SSANGSIOS - 0xC2E7: 0xCB79, //HANGUL SYLLABLE SSANGCIEUC WEO IEUNG - 0xC2E8: 0xCB9C, //HANGUL SYLLABLE SSANGCIEUC WI - 0xC2E9: 0xCBB8, //HANGUL SYLLABLE SSANGCIEUC YU - 0xC2EA: 0xCBD4, //HANGUL SYLLABLE SSANGCIEUC EU - 0xC2EB: 0xCBE4, //HANGUL SYLLABLE SSANGCIEUC EU MIEUM - 0xC2EC: 0xCBE7, //HANGUL SYLLABLE SSANGCIEUC EU SIOS - 0xC2ED: 0xCBE9, //HANGUL SYLLABLE SSANGCIEUC EU IEUNG - 0xC2EE: 0xCC0C, //HANGUL SYLLABLE SSANGCIEUC I - 0xC2EF: 0xCC0D, //HANGUL SYLLABLE SSANGCIEUC I KIYEOK - 0xC2F0: 0xCC10, //HANGUL SYLLABLE SSANGCIEUC I NIEUN - 0xC2F1: 0xCC14, //HANGUL SYLLABLE SSANGCIEUC I RIEUL - 0xC2F2: 0xCC1C, //HANGUL SYLLABLE SSANGCIEUC I MIEUM - 0xC2F3: 0xCC1D, //HANGUL SYLLABLE SSANGCIEUC I PIEUP - 0xC2F4: 0xCC21, //HANGUL SYLLABLE SSANGCIEUC I IEUNG - 0xC2F5: 0xCC22, //HANGUL SYLLABLE SSANGCIEUC I CIEUC - 0xC2F6: 0xCC27, //HANGUL SYLLABLE SSANGCIEUC I HIEUH - 0xC2F7: 0xCC28, //HANGUL SYLLABLE CHIEUCH A - 0xC2F8: 0xCC29, //HANGUL SYLLABLE CHIEUCH A KIYEOK - 0xC2F9: 0xCC2C, //HANGUL SYLLABLE CHIEUCH A NIEUN - 0xC2FA: 0xCC2E, //HANGUL SYLLABLE CHIEUCH A NIEUNHIEUH - 0xC2FB: 0xCC30, //HANGUL SYLLABLE CHIEUCH A RIEUL - 0xC2FC: 0xCC38, //HANGUL SYLLABLE CHIEUCH A MIEUM - 0xC2FD: 0xCC39, //HANGUL SYLLABLE CHIEUCH A PIEUP - 0xC2FE: 0xCC3B, //HANGUL SYLLABLE CHIEUCH A SIOS - 0xC341: 0xD63D, //HANGUL SYLLABLE HIEUH O NIEUNCIEUC - 0xC342: 0xD63E, //HANGUL SYLLABLE HIEUH O NIEUNHIEUH - 0xC343: 0xD63F, //HANGUL SYLLABLE HIEUH O TIKEUT - 0xC344: 0xD641, //HANGUL SYLLABLE HIEUH O RIEULKIYEOK - 0xC345: 0xD642, //HANGUL SYLLABLE HIEUH O RIEULMIEUM - 0xC346: 0xD643, //HANGUL SYLLABLE HIEUH O RIEULPIEUP - 0xC347: 0xD644, //HANGUL SYLLABLE HIEUH O RIEULSIOS - 0xC348: 0xD646, //HANGUL SYLLABLE HIEUH O RIEULPHIEUPH - 0xC349: 0xD647, //HANGUL SYLLABLE HIEUH O RIEULHIEUH - 0xC34A: 0xD64A, //HANGUL SYLLABLE HIEUH O PIEUPSIOS - 0xC34B: 0xD64C, //HANGUL SYLLABLE HIEUH O SSANGSIOS - 0xC34C: 0xD64E, //HANGUL SYLLABLE HIEUH O CIEUC - 0xC34D: 0xD64F, //HANGUL SYLLABLE HIEUH O CHIEUCH - 0xC34E: 0xD650, //HANGUL SYLLABLE HIEUH O KHIEUKH - 0xC34F: 0xD652, //HANGUL SYLLABLE HIEUH O PHIEUPH - 0xC350: 0xD653, //HANGUL SYLLABLE HIEUH O HIEUH - 0xC351: 0xD656, //HANGUL SYLLABLE HIEUH WA SSANGKIYEOK - 0xC352: 0xD657, //HANGUL SYLLABLE HIEUH WA KIYEOKSIOS - 0xC353: 0xD659, //HANGUL SYLLABLE HIEUH WA NIEUNCIEUC - 0xC354: 0xD65A, //HANGUL SYLLABLE HIEUH WA NIEUNHIEUH - 0xC355: 0xD65B, //HANGUL SYLLABLE HIEUH WA TIKEUT - 0xC356: 0xD65D, //HANGUL SYLLABLE HIEUH WA RIEULKIYEOK - 0xC357: 0xD65E, //HANGUL SYLLABLE HIEUH WA RIEULMIEUM - 0xC358: 0xD65F, //HANGUL SYLLABLE HIEUH WA RIEULPIEUP - 0xC359: 0xD660, //HANGUL SYLLABLE HIEUH WA RIEULSIOS - 0xC35A: 0xD661, //HANGUL SYLLABLE HIEUH WA RIEULTHIEUTH - 0xC361: 0xD662, //HANGUL SYLLABLE HIEUH WA RIEULPHIEUPH - 0xC362: 0xD663, //HANGUL SYLLABLE HIEUH WA RIEULHIEUH - 0xC363: 0xD664, //HANGUL SYLLABLE HIEUH WA MIEUM - 0xC364: 0xD665, //HANGUL SYLLABLE HIEUH WA PIEUP - 0xC365: 0xD666, //HANGUL SYLLABLE HIEUH WA PIEUPSIOS - 0xC366: 0xD668, //HANGUL SYLLABLE HIEUH WA SSANGSIOS - 0xC367: 0xD66A, //HANGUL SYLLABLE HIEUH WA CIEUC - 0xC368: 0xD66B, //HANGUL SYLLABLE HIEUH WA CHIEUCH - 0xC369: 0xD66C, //HANGUL SYLLABLE HIEUH WA KHIEUKH - 0xC36A: 0xD66D, //HANGUL SYLLABLE HIEUH WA THIEUTH - 0xC36B: 0xD66E, //HANGUL SYLLABLE HIEUH WA PHIEUPH - 0xC36C: 0xD66F, //HANGUL SYLLABLE HIEUH WA HIEUH - 0xC36D: 0xD672, //HANGUL SYLLABLE HIEUH WAE SSANGKIYEOK - 0xC36E: 0xD673, //HANGUL SYLLABLE HIEUH WAE KIYEOKSIOS - 0xC36F: 0xD675, //HANGUL SYLLABLE HIEUH WAE NIEUNCIEUC - 0xC370: 0xD676, //HANGUL SYLLABLE HIEUH WAE NIEUNHIEUH - 0xC371: 0xD677, //HANGUL SYLLABLE HIEUH WAE TIKEUT - 0xC372: 0xD678, //HANGUL SYLLABLE HIEUH WAE RIEUL - 0xC373: 0xD679, //HANGUL SYLLABLE HIEUH WAE RIEULKIYEOK - 0xC374: 0xD67A, //HANGUL SYLLABLE HIEUH WAE RIEULMIEUM - 0xC375: 0xD67B, //HANGUL SYLLABLE HIEUH WAE RIEULPIEUP - 0xC376: 0xD67C, //HANGUL SYLLABLE HIEUH WAE RIEULSIOS - 0xC377: 0xD67D, //HANGUL SYLLABLE HIEUH WAE RIEULTHIEUTH - 0xC378: 0xD67E, //HANGUL SYLLABLE HIEUH WAE RIEULPHIEUPH - 0xC379: 0xD67F, //HANGUL SYLLABLE HIEUH WAE RIEULHIEUH - 0xC37A: 0xD680, //HANGUL SYLLABLE HIEUH WAE MIEUM - 0xC381: 0xD681, //HANGUL SYLLABLE HIEUH WAE PIEUP - 0xC382: 0xD682, //HANGUL SYLLABLE HIEUH WAE PIEUPSIOS - 0xC383: 0xD684, //HANGUL SYLLABLE HIEUH WAE SSANGSIOS - 0xC384: 0xD686, //HANGUL SYLLABLE HIEUH WAE CIEUC - 0xC385: 0xD687, //HANGUL SYLLABLE HIEUH WAE CHIEUCH - 0xC386: 0xD688, //HANGUL SYLLABLE HIEUH WAE KHIEUKH - 0xC387: 0xD689, //HANGUL SYLLABLE HIEUH WAE THIEUTH - 0xC388: 0xD68A, //HANGUL SYLLABLE HIEUH WAE PHIEUPH - 0xC389: 0xD68B, //HANGUL SYLLABLE HIEUH WAE HIEUH - 0xC38A: 0xD68E, //HANGUL SYLLABLE HIEUH OE SSANGKIYEOK - 0xC38B: 0xD68F, //HANGUL SYLLABLE HIEUH OE KIYEOKSIOS - 0xC38C: 0xD691, //HANGUL SYLLABLE HIEUH OE NIEUNCIEUC - 0xC38D: 0xD692, //HANGUL SYLLABLE HIEUH OE NIEUNHIEUH - 0xC38E: 0xD693, //HANGUL SYLLABLE HIEUH OE TIKEUT - 0xC38F: 0xD695, //HANGUL SYLLABLE HIEUH OE RIEULKIYEOK - 0xC390: 0xD696, //HANGUL SYLLABLE HIEUH OE RIEULMIEUM - 0xC391: 0xD697, //HANGUL SYLLABLE HIEUH OE RIEULPIEUP - 0xC392: 0xD698, //HANGUL SYLLABLE HIEUH OE RIEULSIOS - 0xC393: 0xD699, //HANGUL SYLLABLE HIEUH OE RIEULTHIEUTH - 0xC394: 0xD69A, //HANGUL SYLLABLE HIEUH OE RIEULPHIEUPH - 0xC395: 0xD69B, //HANGUL SYLLABLE HIEUH OE RIEULHIEUH - 0xC396: 0xD69C, //HANGUL SYLLABLE HIEUH OE MIEUM - 0xC397: 0xD69E, //HANGUL SYLLABLE HIEUH OE PIEUPSIOS - 0xC398: 0xD6A0, //HANGUL SYLLABLE HIEUH OE SSANGSIOS - 0xC399: 0xD6A2, //HANGUL SYLLABLE HIEUH OE CIEUC - 0xC39A: 0xD6A3, //HANGUL SYLLABLE HIEUH OE CHIEUCH - 0xC39B: 0xD6A4, //HANGUL SYLLABLE HIEUH OE KHIEUKH - 0xC39C: 0xD6A5, //HANGUL SYLLABLE HIEUH OE THIEUTH - 0xC39D: 0xD6A6, //HANGUL SYLLABLE HIEUH OE PHIEUPH - 0xC39E: 0xD6A7, //HANGUL SYLLABLE HIEUH OE HIEUH - 0xC39F: 0xD6A9, //HANGUL SYLLABLE HIEUH YO KIYEOK - 0xC3A0: 0xD6AA, //HANGUL SYLLABLE HIEUH YO SSANGKIYEOK - 0xC3A1: 0xCC3C, //HANGUL SYLLABLE CHIEUCH A SSANGSIOS - 0xC3A2: 0xCC3D, //HANGUL SYLLABLE CHIEUCH A IEUNG - 0xC3A3: 0xCC3E, //HANGUL SYLLABLE CHIEUCH A CIEUC - 0xC3A4: 0xCC44, //HANGUL SYLLABLE CHIEUCH AE - 0xC3A5: 0xCC45, //HANGUL SYLLABLE CHIEUCH AE KIYEOK - 0xC3A6: 0xCC48, //HANGUL SYLLABLE CHIEUCH AE NIEUN - 0xC3A7: 0xCC4C, //HANGUL SYLLABLE CHIEUCH AE RIEUL - 0xC3A8: 0xCC54, //HANGUL SYLLABLE CHIEUCH AE MIEUM - 0xC3A9: 0xCC55, //HANGUL SYLLABLE CHIEUCH AE PIEUP - 0xC3AA: 0xCC57, //HANGUL SYLLABLE CHIEUCH AE SIOS - 0xC3AB: 0xCC58, //HANGUL SYLLABLE CHIEUCH AE SSANGSIOS - 0xC3AC: 0xCC59, //HANGUL SYLLABLE CHIEUCH AE IEUNG - 0xC3AD: 0xCC60, //HANGUL SYLLABLE CHIEUCH YA - 0xC3AE: 0xCC64, //HANGUL SYLLABLE CHIEUCH YA NIEUN - 0xC3AF: 0xCC66, //HANGUL SYLLABLE CHIEUCH YA NIEUNHIEUH - 0xC3B0: 0xCC68, //HANGUL SYLLABLE CHIEUCH YA RIEUL - 0xC3B1: 0xCC70, //HANGUL SYLLABLE CHIEUCH YA MIEUM - 0xC3B2: 0xCC75, //HANGUL SYLLABLE CHIEUCH YA IEUNG - 0xC3B3: 0xCC98, //HANGUL SYLLABLE CHIEUCH EO - 0xC3B4: 0xCC99, //HANGUL SYLLABLE CHIEUCH EO KIYEOK - 0xC3B5: 0xCC9C, //HANGUL SYLLABLE CHIEUCH EO NIEUN - 0xC3B6: 0xCCA0, //HANGUL SYLLABLE CHIEUCH EO RIEUL - 0xC3B7: 0xCCA8, //HANGUL SYLLABLE CHIEUCH EO MIEUM - 0xC3B8: 0xCCA9, //HANGUL SYLLABLE CHIEUCH EO PIEUP - 0xC3B9: 0xCCAB, //HANGUL SYLLABLE CHIEUCH EO SIOS - 0xC3BA: 0xCCAC, //HANGUL SYLLABLE CHIEUCH EO SSANGSIOS - 0xC3BB: 0xCCAD, //HANGUL SYLLABLE CHIEUCH EO IEUNG - 0xC3BC: 0xCCB4, //HANGUL SYLLABLE CHIEUCH E - 0xC3BD: 0xCCB5, //HANGUL SYLLABLE CHIEUCH E KIYEOK - 0xC3BE: 0xCCB8, //HANGUL SYLLABLE CHIEUCH E NIEUN - 0xC3BF: 0xCCBC, //HANGUL SYLLABLE CHIEUCH E RIEUL - 0xC3C0: 0xCCC4, //HANGUL SYLLABLE CHIEUCH E MIEUM - 0xC3C1: 0xCCC5, //HANGUL SYLLABLE CHIEUCH E PIEUP - 0xC3C2: 0xCCC7, //HANGUL SYLLABLE CHIEUCH E SIOS - 0xC3C3: 0xCCC9, //HANGUL SYLLABLE CHIEUCH E IEUNG - 0xC3C4: 0xCCD0, //HANGUL SYLLABLE CHIEUCH YEO - 0xC3C5: 0xCCD4, //HANGUL SYLLABLE CHIEUCH YEO NIEUN - 0xC3C6: 0xCCE4, //HANGUL SYLLABLE CHIEUCH YEO SSANGSIOS - 0xC3C7: 0xCCEC, //HANGUL SYLLABLE CHIEUCH YE - 0xC3C8: 0xCCF0, //HANGUL SYLLABLE CHIEUCH YE NIEUN - 0xC3C9: 0xCD01, //HANGUL SYLLABLE CHIEUCH YE IEUNG - 0xC3CA: 0xCD08, //HANGUL SYLLABLE CHIEUCH O - 0xC3CB: 0xCD09, //HANGUL SYLLABLE CHIEUCH O KIYEOK - 0xC3CC: 0xCD0C, //HANGUL SYLLABLE CHIEUCH O NIEUN - 0xC3CD: 0xCD10, //HANGUL SYLLABLE CHIEUCH O RIEUL - 0xC3CE: 0xCD18, //HANGUL SYLLABLE CHIEUCH O MIEUM - 0xC3CF: 0xCD19, //HANGUL SYLLABLE CHIEUCH O PIEUP - 0xC3D0: 0xCD1B, //HANGUL SYLLABLE CHIEUCH O SIOS - 0xC3D1: 0xCD1D, //HANGUL SYLLABLE CHIEUCH O IEUNG - 0xC3D2: 0xCD24, //HANGUL SYLLABLE CHIEUCH WA - 0xC3D3: 0xCD28, //HANGUL SYLLABLE CHIEUCH WA NIEUN - 0xC3D4: 0xCD2C, //HANGUL SYLLABLE CHIEUCH WA RIEUL - 0xC3D5: 0xCD39, //HANGUL SYLLABLE CHIEUCH WA IEUNG - 0xC3D6: 0xCD5C, //HANGUL SYLLABLE CHIEUCH OE - 0xC3D7: 0xCD60, //HANGUL SYLLABLE CHIEUCH OE NIEUN - 0xC3D8: 0xCD64, //HANGUL SYLLABLE CHIEUCH OE RIEUL - 0xC3D9: 0xCD6C, //HANGUL SYLLABLE CHIEUCH OE MIEUM - 0xC3DA: 0xCD6D, //HANGUL SYLLABLE CHIEUCH OE PIEUP - 0xC3DB: 0xCD6F, //HANGUL SYLLABLE CHIEUCH OE SIOS - 0xC3DC: 0xCD71, //HANGUL SYLLABLE CHIEUCH OE IEUNG - 0xC3DD: 0xCD78, //HANGUL SYLLABLE CHIEUCH YO - 0xC3DE: 0xCD88, //HANGUL SYLLABLE CHIEUCH YO MIEUM - 0xC3DF: 0xCD94, //HANGUL SYLLABLE CHIEUCH U - 0xC3E0: 0xCD95, //HANGUL SYLLABLE CHIEUCH U KIYEOK - 0xC3E1: 0xCD98, //HANGUL SYLLABLE CHIEUCH U NIEUN - 0xC3E2: 0xCD9C, //HANGUL SYLLABLE CHIEUCH U RIEUL - 0xC3E3: 0xCDA4, //HANGUL SYLLABLE CHIEUCH U MIEUM - 0xC3E4: 0xCDA5, //HANGUL SYLLABLE CHIEUCH U PIEUP - 0xC3E5: 0xCDA7, //HANGUL SYLLABLE CHIEUCH U SIOS - 0xC3E6: 0xCDA9, //HANGUL SYLLABLE CHIEUCH U IEUNG - 0xC3E7: 0xCDB0, //HANGUL SYLLABLE CHIEUCH WEO - 0xC3E8: 0xCDC4, //HANGUL SYLLABLE CHIEUCH WEO SSANGSIOS - 0xC3E9: 0xCDCC, //HANGUL SYLLABLE CHIEUCH WE - 0xC3EA: 0xCDD0, //HANGUL SYLLABLE CHIEUCH WE NIEUN - 0xC3EB: 0xCDE8, //HANGUL SYLLABLE CHIEUCH WI - 0xC3EC: 0xCDEC, //HANGUL SYLLABLE CHIEUCH WI NIEUN - 0xC3ED: 0xCDF0, //HANGUL SYLLABLE CHIEUCH WI RIEUL - 0xC3EE: 0xCDF8, //HANGUL SYLLABLE CHIEUCH WI MIEUM - 0xC3EF: 0xCDF9, //HANGUL SYLLABLE CHIEUCH WI PIEUP - 0xC3F0: 0xCDFB, //HANGUL SYLLABLE CHIEUCH WI SIOS - 0xC3F1: 0xCDFD, //HANGUL SYLLABLE CHIEUCH WI IEUNG - 0xC3F2: 0xCE04, //HANGUL SYLLABLE CHIEUCH YU - 0xC3F3: 0xCE08, //HANGUL SYLLABLE CHIEUCH YU NIEUN - 0xC3F4: 0xCE0C, //HANGUL SYLLABLE CHIEUCH YU RIEUL - 0xC3F5: 0xCE14, //HANGUL SYLLABLE CHIEUCH YU MIEUM - 0xC3F6: 0xCE19, //HANGUL SYLLABLE CHIEUCH YU IEUNG - 0xC3F7: 0xCE20, //HANGUL SYLLABLE CHIEUCH EU - 0xC3F8: 0xCE21, //HANGUL SYLLABLE CHIEUCH EU KIYEOK - 0xC3F9: 0xCE24, //HANGUL SYLLABLE CHIEUCH EU NIEUN - 0xC3FA: 0xCE28, //HANGUL SYLLABLE CHIEUCH EU RIEUL - 0xC3FB: 0xCE30, //HANGUL SYLLABLE CHIEUCH EU MIEUM - 0xC3FC: 0xCE31, //HANGUL SYLLABLE CHIEUCH EU PIEUP - 0xC3FD: 0xCE33, //HANGUL SYLLABLE CHIEUCH EU SIOS - 0xC3FE: 0xCE35, //HANGUL SYLLABLE CHIEUCH EU IEUNG - 0xC441: 0xD6AB, //HANGUL SYLLABLE HIEUH YO KIYEOKSIOS - 0xC442: 0xD6AD, //HANGUL SYLLABLE HIEUH YO NIEUNCIEUC - 0xC443: 0xD6AE, //HANGUL SYLLABLE HIEUH YO NIEUNHIEUH - 0xC444: 0xD6AF, //HANGUL SYLLABLE HIEUH YO TIKEUT - 0xC445: 0xD6B1, //HANGUL SYLLABLE HIEUH YO RIEULKIYEOK - 0xC446: 0xD6B2, //HANGUL SYLLABLE HIEUH YO RIEULMIEUM - 0xC447: 0xD6B3, //HANGUL SYLLABLE HIEUH YO RIEULPIEUP - 0xC448: 0xD6B4, //HANGUL SYLLABLE HIEUH YO RIEULSIOS - 0xC449: 0xD6B5, //HANGUL SYLLABLE HIEUH YO RIEULTHIEUTH - 0xC44A: 0xD6B6, //HANGUL SYLLABLE HIEUH YO RIEULPHIEUPH - 0xC44B: 0xD6B7, //HANGUL SYLLABLE HIEUH YO RIEULHIEUH - 0xC44C: 0xD6B8, //HANGUL SYLLABLE HIEUH YO MIEUM - 0xC44D: 0xD6BA, //HANGUL SYLLABLE HIEUH YO PIEUPSIOS - 0xC44E: 0xD6BC, //HANGUL SYLLABLE HIEUH YO SSANGSIOS - 0xC44F: 0xD6BD, //HANGUL SYLLABLE HIEUH YO IEUNG - 0xC450: 0xD6BE, //HANGUL SYLLABLE HIEUH YO CIEUC - 0xC451: 0xD6BF, //HANGUL SYLLABLE HIEUH YO CHIEUCH - 0xC452: 0xD6C0, //HANGUL SYLLABLE HIEUH YO KHIEUKH - 0xC453: 0xD6C1, //HANGUL SYLLABLE HIEUH YO THIEUTH - 0xC454: 0xD6C2, //HANGUL SYLLABLE HIEUH YO PHIEUPH - 0xC455: 0xD6C3, //HANGUL SYLLABLE HIEUH YO HIEUH - 0xC456: 0xD6C6, //HANGUL SYLLABLE HIEUH U SSANGKIYEOK - 0xC457: 0xD6C7, //HANGUL SYLLABLE HIEUH U KIYEOKSIOS - 0xC458: 0xD6C9, //HANGUL SYLLABLE HIEUH U NIEUNCIEUC - 0xC459: 0xD6CA, //HANGUL SYLLABLE HIEUH U NIEUNHIEUH - 0xC45A: 0xD6CB, //HANGUL SYLLABLE HIEUH U TIKEUT - 0xC461: 0xD6CD, //HANGUL SYLLABLE HIEUH U RIEULKIYEOK - 0xC462: 0xD6CE, //HANGUL SYLLABLE HIEUH U RIEULMIEUM - 0xC463: 0xD6CF, //HANGUL SYLLABLE HIEUH U RIEULPIEUP - 0xC464: 0xD6D0, //HANGUL SYLLABLE HIEUH U RIEULSIOS - 0xC465: 0xD6D2, //HANGUL SYLLABLE HIEUH U RIEULPHIEUPH - 0xC466: 0xD6D3, //HANGUL SYLLABLE HIEUH U RIEULHIEUH - 0xC467: 0xD6D5, //HANGUL SYLLABLE HIEUH U PIEUP - 0xC468: 0xD6D6, //HANGUL SYLLABLE HIEUH U PIEUPSIOS - 0xC469: 0xD6D8, //HANGUL SYLLABLE HIEUH U SSANGSIOS - 0xC46A: 0xD6DA, //HANGUL SYLLABLE HIEUH U CIEUC - 0xC46B: 0xD6DB, //HANGUL SYLLABLE HIEUH U CHIEUCH - 0xC46C: 0xD6DC, //HANGUL SYLLABLE HIEUH U KHIEUKH - 0xC46D: 0xD6DD, //HANGUL SYLLABLE HIEUH U THIEUTH - 0xC46E: 0xD6DE, //HANGUL SYLLABLE HIEUH U PHIEUPH - 0xC46F: 0xD6DF, //HANGUL SYLLABLE HIEUH U HIEUH - 0xC470: 0xD6E1, //HANGUL SYLLABLE HIEUH WEO KIYEOK - 0xC471: 0xD6E2, //HANGUL SYLLABLE HIEUH WEO SSANGKIYEOK - 0xC472: 0xD6E3, //HANGUL SYLLABLE HIEUH WEO KIYEOKSIOS - 0xC473: 0xD6E5, //HANGUL SYLLABLE HIEUH WEO NIEUNCIEUC - 0xC474: 0xD6E6, //HANGUL SYLLABLE HIEUH WEO NIEUNHIEUH - 0xC475: 0xD6E7, //HANGUL SYLLABLE HIEUH WEO TIKEUT - 0xC476: 0xD6E9, //HANGUL SYLLABLE HIEUH WEO RIEULKIYEOK - 0xC477: 0xD6EA, //HANGUL SYLLABLE HIEUH WEO RIEULMIEUM - 0xC478: 0xD6EB, //HANGUL SYLLABLE HIEUH WEO RIEULPIEUP - 0xC479: 0xD6EC, //HANGUL SYLLABLE HIEUH WEO RIEULSIOS - 0xC47A: 0xD6ED, //HANGUL SYLLABLE HIEUH WEO RIEULTHIEUTH - 0xC481: 0xD6EE, //HANGUL SYLLABLE HIEUH WEO RIEULPHIEUPH - 0xC482: 0xD6EF, //HANGUL SYLLABLE HIEUH WEO RIEULHIEUH - 0xC483: 0xD6F1, //HANGUL SYLLABLE HIEUH WEO PIEUP - 0xC484: 0xD6F2, //HANGUL SYLLABLE HIEUH WEO PIEUPSIOS - 0xC485: 0xD6F3, //HANGUL SYLLABLE HIEUH WEO SIOS - 0xC486: 0xD6F4, //HANGUL SYLLABLE HIEUH WEO SSANGSIOS - 0xC487: 0xD6F6, //HANGUL SYLLABLE HIEUH WEO CIEUC - 0xC488: 0xD6F7, //HANGUL SYLLABLE HIEUH WEO CHIEUCH - 0xC489: 0xD6F8, //HANGUL SYLLABLE HIEUH WEO KHIEUKH - 0xC48A: 0xD6F9, //HANGUL SYLLABLE HIEUH WEO THIEUTH - 0xC48B: 0xD6FA, //HANGUL SYLLABLE HIEUH WEO PHIEUPH - 0xC48C: 0xD6FB, //HANGUL SYLLABLE HIEUH WEO HIEUH - 0xC48D: 0xD6FE, //HANGUL SYLLABLE HIEUH WE SSANGKIYEOK - 0xC48E: 0xD6FF, //HANGUL SYLLABLE HIEUH WE KIYEOKSIOS - 0xC48F: 0xD701, //HANGUL SYLLABLE HIEUH WE NIEUNCIEUC - 0xC490: 0xD702, //HANGUL SYLLABLE HIEUH WE NIEUNHIEUH - 0xC491: 0xD703, //HANGUL SYLLABLE HIEUH WE TIKEUT - 0xC492: 0xD705, //HANGUL SYLLABLE HIEUH WE RIEULKIYEOK - 0xC493: 0xD706, //HANGUL SYLLABLE HIEUH WE RIEULMIEUM - 0xC494: 0xD707, //HANGUL SYLLABLE HIEUH WE RIEULPIEUP - 0xC495: 0xD708, //HANGUL SYLLABLE HIEUH WE RIEULSIOS - 0xC496: 0xD709, //HANGUL SYLLABLE HIEUH WE RIEULTHIEUTH - 0xC497: 0xD70A, //HANGUL SYLLABLE HIEUH WE RIEULPHIEUPH - 0xC498: 0xD70B, //HANGUL SYLLABLE HIEUH WE RIEULHIEUH - 0xC499: 0xD70C, //HANGUL SYLLABLE HIEUH WE MIEUM - 0xC49A: 0xD70D, //HANGUL SYLLABLE HIEUH WE PIEUP - 0xC49B: 0xD70E, //HANGUL SYLLABLE HIEUH WE PIEUPSIOS - 0xC49C: 0xD70F, //HANGUL SYLLABLE HIEUH WE SIOS - 0xC49D: 0xD710, //HANGUL SYLLABLE HIEUH WE SSANGSIOS - 0xC49E: 0xD712, //HANGUL SYLLABLE HIEUH WE CIEUC - 0xC49F: 0xD713, //HANGUL SYLLABLE HIEUH WE CHIEUCH - 0xC4A0: 0xD714, //HANGUL SYLLABLE HIEUH WE KHIEUKH - 0xC4A1: 0xCE58, //HANGUL SYLLABLE CHIEUCH I - 0xC4A2: 0xCE59, //HANGUL SYLLABLE CHIEUCH I KIYEOK - 0xC4A3: 0xCE5C, //HANGUL SYLLABLE CHIEUCH I NIEUN - 0xC4A4: 0xCE5F, //HANGUL SYLLABLE CHIEUCH I TIKEUT - 0xC4A5: 0xCE60, //HANGUL SYLLABLE CHIEUCH I RIEUL - 0xC4A6: 0xCE61, //HANGUL SYLLABLE CHIEUCH I RIEULKIYEOK - 0xC4A7: 0xCE68, //HANGUL SYLLABLE CHIEUCH I MIEUM - 0xC4A8: 0xCE69, //HANGUL SYLLABLE CHIEUCH I PIEUP - 0xC4A9: 0xCE6B, //HANGUL SYLLABLE CHIEUCH I SIOS - 0xC4AA: 0xCE6D, //HANGUL SYLLABLE CHIEUCH I IEUNG - 0xC4AB: 0xCE74, //HANGUL SYLLABLE KHIEUKH A - 0xC4AC: 0xCE75, //HANGUL SYLLABLE KHIEUKH A KIYEOK - 0xC4AD: 0xCE78, //HANGUL SYLLABLE KHIEUKH A NIEUN - 0xC4AE: 0xCE7C, //HANGUL SYLLABLE KHIEUKH A RIEUL - 0xC4AF: 0xCE84, //HANGUL SYLLABLE KHIEUKH A MIEUM - 0xC4B0: 0xCE85, //HANGUL SYLLABLE KHIEUKH A PIEUP - 0xC4B1: 0xCE87, //HANGUL SYLLABLE KHIEUKH A SIOS - 0xC4B2: 0xCE89, //HANGUL SYLLABLE KHIEUKH A IEUNG - 0xC4B3: 0xCE90, //HANGUL SYLLABLE KHIEUKH AE - 0xC4B4: 0xCE91, //HANGUL SYLLABLE KHIEUKH AE KIYEOK - 0xC4B5: 0xCE94, //HANGUL SYLLABLE KHIEUKH AE NIEUN - 0xC4B6: 0xCE98, //HANGUL SYLLABLE KHIEUKH AE RIEUL - 0xC4B7: 0xCEA0, //HANGUL SYLLABLE KHIEUKH AE MIEUM - 0xC4B8: 0xCEA1, //HANGUL SYLLABLE KHIEUKH AE PIEUP - 0xC4B9: 0xCEA3, //HANGUL SYLLABLE KHIEUKH AE SIOS - 0xC4BA: 0xCEA4, //HANGUL SYLLABLE KHIEUKH AE SSANGSIOS - 0xC4BB: 0xCEA5, //HANGUL SYLLABLE KHIEUKH AE IEUNG - 0xC4BC: 0xCEAC, //HANGUL SYLLABLE KHIEUKH YA - 0xC4BD: 0xCEAD, //HANGUL SYLLABLE KHIEUKH YA KIYEOK - 0xC4BE: 0xCEC1, //HANGUL SYLLABLE KHIEUKH YA IEUNG - 0xC4BF: 0xCEE4, //HANGUL SYLLABLE KHIEUKH EO - 0xC4C0: 0xCEE5, //HANGUL SYLLABLE KHIEUKH EO KIYEOK - 0xC4C1: 0xCEE8, //HANGUL SYLLABLE KHIEUKH EO NIEUN - 0xC4C2: 0xCEEB, //HANGUL SYLLABLE KHIEUKH EO TIKEUT - 0xC4C3: 0xCEEC, //HANGUL SYLLABLE KHIEUKH EO RIEUL - 0xC4C4: 0xCEF4, //HANGUL SYLLABLE KHIEUKH EO MIEUM - 0xC4C5: 0xCEF5, //HANGUL SYLLABLE KHIEUKH EO PIEUP - 0xC4C6: 0xCEF7, //HANGUL SYLLABLE KHIEUKH EO SIOS - 0xC4C7: 0xCEF8, //HANGUL SYLLABLE KHIEUKH EO SSANGSIOS - 0xC4C8: 0xCEF9, //HANGUL SYLLABLE KHIEUKH EO IEUNG - 0xC4C9: 0xCF00, //HANGUL SYLLABLE KHIEUKH E - 0xC4CA: 0xCF01, //HANGUL SYLLABLE KHIEUKH E KIYEOK - 0xC4CB: 0xCF04, //HANGUL SYLLABLE KHIEUKH E NIEUN - 0xC4CC: 0xCF08, //HANGUL SYLLABLE KHIEUKH E RIEUL - 0xC4CD: 0xCF10, //HANGUL SYLLABLE KHIEUKH E MIEUM - 0xC4CE: 0xCF11, //HANGUL SYLLABLE KHIEUKH E PIEUP - 0xC4CF: 0xCF13, //HANGUL SYLLABLE KHIEUKH E SIOS - 0xC4D0: 0xCF15, //HANGUL SYLLABLE KHIEUKH E IEUNG - 0xC4D1: 0xCF1C, //HANGUL SYLLABLE KHIEUKH YEO - 0xC4D2: 0xCF20, //HANGUL SYLLABLE KHIEUKH YEO NIEUN - 0xC4D3: 0xCF24, //HANGUL SYLLABLE KHIEUKH YEO RIEUL - 0xC4D4: 0xCF2C, //HANGUL SYLLABLE KHIEUKH YEO MIEUM - 0xC4D5: 0xCF2D, //HANGUL SYLLABLE KHIEUKH YEO PIEUP - 0xC4D6: 0xCF2F, //HANGUL SYLLABLE KHIEUKH YEO SIOS - 0xC4D7: 0xCF30, //HANGUL SYLLABLE KHIEUKH YEO SSANGSIOS - 0xC4D8: 0xCF31, //HANGUL SYLLABLE KHIEUKH YEO IEUNG - 0xC4D9: 0xCF38, //HANGUL SYLLABLE KHIEUKH YE - 0xC4DA: 0xCF54, //HANGUL SYLLABLE KHIEUKH O - 0xC4DB: 0xCF55, //HANGUL SYLLABLE KHIEUKH O KIYEOK - 0xC4DC: 0xCF58, //HANGUL SYLLABLE KHIEUKH O NIEUN - 0xC4DD: 0xCF5C, //HANGUL SYLLABLE KHIEUKH O RIEUL - 0xC4DE: 0xCF64, //HANGUL SYLLABLE KHIEUKH O MIEUM - 0xC4DF: 0xCF65, //HANGUL SYLLABLE KHIEUKH O PIEUP - 0xC4E0: 0xCF67, //HANGUL SYLLABLE KHIEUKH O SIOS - 0xC4E1: 0xCF69, //HANGUL SYLLABLE KHIEUKH O IEUNG - 0xC4E2: 0xCF70, //HANGUL SYLLABLE KHIEUKH WA - 0xC4E3: 0xCF71, //HANGUL SYLLABLE KHIEUKH WA KIYEOK - 0xC4E4: 0xCF74, //HANGUL SYLLABLE KHIEUKH WA NIEUN - 0xC4E5: 0xCF78, //HANGUL SYLLABLE KHIEUKH WA RIEUL - 0xC4E6: 0xCF80, //HANGUL SYLLABLE KHIEUKH WA MIEUM - 0xC4E7: 0xCF85, //HANGUL SYLLABLE KHIEUKH WA IEUNG - 0xC4E8: 0xCF8C, //HANGUL SYLLABLE KHIEUKH WAE - 0xC4E9: 0xCFA1, //HANGUL SYLLABLE KHIEUKH WAE IEUNG - 0xC4EA: 0xCFA8, //HANGUL SYLLABLE KHIEUKH OE - 0xC4EB: 0xCFB0, //HANGUL SYLLABLE KHIEUKH OE RIEUL - 0xC4EC: 0xCFC4, //HANGUL SYLLABLE KHIEUKH YO - 0xC4ED: 0xCFE0, //HANGUL SYLLABLE KHIEUKH U - 0xC4EE: 0xCFE1, //HANGUL SYLLABLE KHIEUKH U KIYEOK - 0xC4EF: 0xCFE4, //HANGUL SYLLABLE KHIEUKH U NIEUN - 0xC4F0: 0xCFE8, //HANGUL SYLLABLE KHIEUKH U RIEUL - 0xC4F1: 0xCFF0, //HANGUL SYLLABLE KHIEUKH U MIEUM - 0xC4F2: 0xCFF1, //HANGUL SYLLABLE KHIEUKH U PIEUP - 0xC4F3: 0xCFF3, //HANGUL SYLLABLE KHIEUKH U SIOS - 0xC4F4: 0xCFF5, //HANGUL SYLLABLE KHIEUKH U IEUNG - 0xC4F5: 0xCFFC, //HANGUL SYLLABLE KHIEUKH WEO - 0xC4F6: 0xD000, //HANGUL SYLLABLE KHIEUKH WEO NIEUN - 0xC4F7: 0xD004, //HANGUL SYLLABLE KHIEUKH WEO RIEUL - 0xC4F8: 0xD011, //HANGUL SYLLABLE KHIEUKH WEO IEUNG - 0xC4F9: 0xD018, //HANGUL SYLLABLE KHIEUKH WE - 0xC4FA: 0xD02D, //HANGUL SYLLABLE KHIEUKH WE IEUNG - 0xC4FB: 0xD034, //HANGUL SYLLABLE KHIEUKH WI - 0xC4FC: 0xD035, //HANGUL SYLLABLE KHIEUKH WI KIYEOK - 0xC4FD: 0xD038, //HANGUL SYLLABLE KHIEUKH WI NIEUN - 0xC4FE: 0xD03C, //HANGUL SYLLABLE KHIEUKH WI RIEUL - 0xC541: 0xD715, //HANGUL SYLLABLE HIEUH WE THIEUTH - 0xC542: 0xD716, //HANGUL SYLLABLE HIEUH WE PHIEUPH - 0xC543: 0xD717, //HANGUL SYLLABLE HIEUH WE HIEUH - 0xC544: 0xD71A, //HANGUL SYLLABLE HIEUH WI SSANGKIYEOK - 0xC545: 0xD71B, //HANGUL SYLLABLE HIEUH WI KIYEOKSIOS - 0xC546: 0xD71D, //HANGUL SYLLABLE HIEUH WI NIEUNCIEUC - 0xC547: 0xD71E, //HANGUL SYLLABLE HIEUH WI NIEUNHIEUH - 0xC548: 0xD71F, //HANGUL SYLLABLE HIEUH WI TIKEUT - 0xC549: 0xD721, //HANGUL SYLLABLE HIEUH WI RIEULKIYEOK - 0xC54A: 0xD722, //HANGUL SYLLABLE HIEUH WI RIEULMIEUM - 0xC54B: 0xD723, //HANGUL SYLLABLE HIEUH WI RIEULPIEUP - 0xC54C: 0xD724, //HANGUL SYLLABLE HIEUH WI RIEULSIOS - 0xC54D: 0xD725, //HANGUL SYLLABLE HIEUH WI RIEULTHIEUTH - 0xC54E: 0xD726, //HANGUL SYLLABLE HIEUH WI RIEULPHIEUPH - 0xC54F: 0xD727, //HANGUL SYLLABLE HIEUH WI RIEULHIEUH - 0xC550: 0xD72A, //HANGUL SYLLABLE HIEUH WI PIEUPSIOS - 0xC551: 0xD72C, //HANGUL SYLLABLE HIEUH WI SSANGSIOS - 0xC552: 0xD72E, //HANGUL SYLLABLE HIEUH WI CIEUC - 0xC553: 0xD72F, //HANGUL SYLLABLE HIEUH WI CHIEUCH - 0xC554: 0xD730, //HANGUL SYLLABLE HIEUH WI KHIEUKH - 0xC555: 0xD731, //HANGUL SYLLABLE HIEUH WI THIEUTH - 0xC556: 0xD732, //HANGUL SYLLABLE HIEUH WI PHIEUPH - 0xC557: 0xD733, //HANGUL SYLLABLE HIEUH WI HIEUH - 0xC558: 0xD736, //HANGUL SYLLABLE HIEUH YU SSANGKIYEOK - 0xC559: 0xD737, //HANGUL SYLLABLE HIEUH YU KIYEOKSIOS - 0xC55A: 0xD739, //HANGUL SYLLABLE HIEUH YU NIEUNCIEUC - 0xC561: 0xD73A, //HANGUL SYLLABLE HIEUH YU NIEUNHIEUH - 0xC562: 0xD73B, //HANGUL SYLLABLE HIEUH YU TIKEUT - 0xC563: 0xD73D, //HANGUL SYLLABLE HIEUH YU RIEULKIYEOK - 0xC564: 0xD73E, //HANGUL SYLLABLE HIEUH YU RIEULMIEUM - 0xC565: 0xD73F, //HANGUL SYLLABLE HIEUH YU RIEULPIEUP - 0xC566: 0xD740, //HANGUL SYLLABLE HIEUH YU RIEULSIOS - 0xC567: 0xD741, //HANGUL SYLLABLE HIEUH YU RIEULTHIEUTH - 0xC568: 0xD742, //HANGUL SYLLABLE HIEUH YU RIEULPHIEUPH - 0xC569: 0xD743, //HANGUL SYLLABLE HIEUH YU RIEULHIEUH - 0xC56A: 0xD745, //HANGUL SYLLABLE HIEUH YU PIEUP - 0xC56B: 0xD746, //HANGUL SYLLABLE HIEUH YU PIEUPSIOS - 0xC56C: 0xD748, //HANGUL SYLLABLE HIEUH YU SSANGSIOS - 0xC56D: 0xD74A, //HANGUL SYLLABLE HIEUH YU CIEUC - 0xC56E: 0xD74B, //HANGUL SYLLABLE HIEUH YU CHIEUCH - 0xC56F: 0xD74C, //HANGUL SYLLABLE HIEUH YU KHIEUKH - 0xC570: 0xD74D, //HANGUL SYLLABLE HIEUH YU THIEUTH - 0xC571: 0xD74E, //HANGUL SYLLABLE HIEUH YU PHIEUPH - 0xC572: 0xD74F, //HANGUL SYLLABLE HIEUH YU HIEUH - 0xC573: 0xD752, //HANGUL SYLLABLE HIEUH EU SSANGKIYEOK - 0xC574: 0xD753, //HANGUL SYLLABLE HIEUH EU KIYEOKSIOS - 0xC575: 0xD755, //HANGUL SYLLABLE HIEUH EU NIEUNCIEUC - 0xC576: 0xD75A, //HANGUL SYLLABLE HIEUH EU RIEULMIEUM - 0xC577: 0xD75B, //HANGUL SYLLABLE HIEUH EU RIEULPIEUP - 0xC578: 0xD75C, //HANGUL SYLLABLE HIEUH EU RIEULSIOS - 0xC579: 0xD75D, //HANGUL SYLLABLE HIEUH EU RIEULTHIEUTH - 0xC57A: 0xD75E, //HANGUL SYLLABLE HIEUH EU RIEULPHIEUPH - 0xC581: 0xD75F, //HANGUL SYLLABLE HIEUH EU RIEULHIEUH - 0xC582: 0xD762, //HANGUL SYLLABLE HIEUH EU PIEUPSIOS - 0xC583: 0xD764, //HANGUL SYLLABLE HIEUH EU SSANGSIOS - 0xC584: 0xD766, //HANGUL SYLLABLE HIEUH EU CIEUC - 0xC585: 0xD767, //HANGUL SYLLABLE HIEUH EU CHIEUCH - 0xC586: 0xD768, //HANGUL SYLLABLE HIEUH EU KHIEUKH - 0xC587: 0xD76A, //HANGUL SYLLABLE HIEUH EU PHIEUPH - 0xC588: 0xD76B, //HANGUL SYLLABLE HIEUH EU HIEUH - 0xC589: 0xD76D, //HANGUL SYLLABLE HIEUH YI KIYEOK - 0xC58A: 0xD76E, //HANGUL SYLLABLE HIEUH YI SSANGKIYEOK - 0xC58B: 0xD76F, //HANGUL SYLLABLE HIEUH YI KIYEOKSIOS - 0xC58C: 0xD771, //HANGUL SYLLABLE HIEUH YI NIEUNCIEUC - 0xC58D: 0xD772, //HANGUL SYLLABLE HIEUH YI NIEUNHIEUH - 0xC58E: 0xD773, //HANGUL SYLLABLE HIEUH YI TIKEUT - 0xC58F: 0xD775, //HANGUL SYLLABLE HIEUH YI RIEULKIYEOK - 0xC590: 0xD776, //HANGUL SYLLABLE HIEUH YI RIEULMIEUM - 0xC591: 0xD777, //HANGUL SYLLABLE HIEUH YI RIEULPIEUP - 0xC592: 0xD778, //HANGUL SYLLABLE HIEUH YI RIEULSIOS - 0xC593: 0xD779, //HANGUL SYLLABLE HIEUH YI RIEULTHIEUTH - 0xC594: 0xD77A, //HANGUL SYLLABLE HIEUH YI RIEULPHIEUPH - 0xC595: 0xD77B, //HANGUL SYLLABLE HIEUH YI RIEULHIEUH - 0xC596: 0xD77E, //HANGUL SYLLABLE HIEUH YI PIEUPSIOS - 0xC597: 0xD77F, //HANGUL SYLLABLE HIEUH YI SIOS - 0xC598: 0xD780, //HANGUL SYLLABLE HIEUH YI SSANGSIOS - 0xC599: 0xD782, //HANGUL SYLLABLE HIEUH YI CIEUC - 0xC59A: 0xD783, //HANGUL SYLLABLE HIEUH YI CHIEUCH - 0xC59B: 0xD784, //HANGUL SYLLABLE HIEUH YI KHIEUKH - 0xC59C: 0xD785, //HANGUL SYLLABLE HIEUH YI THIEUTH - 0xC59D: 0xD786, //HANGUL SYLLABLE HIEUH YI PHIEUPH - 0xC59E: 0xD787, //HANGUL SYLLABLE HIEUH YI HIEUH - 0xC59F: 0xD78A, //HANGUL SYLLABLE HIEUH I SSANGKIYEOK - 0xC5A0: 0xD78B, //HANGUL SYLLABLE HIEUH I KIYEOKSIOS - 0xC5A1: 0xD044, //HANGUL SYLLABLE KHIEUKH WI MIEUM - 0xC5A2: 0xD045, //HANGUL SYLLABLE KHIEUKH WI PIEUP - 0xC5A3: 0xD047, //HANGUL SYLLABLE KHIEUKH WI SIOS - 0xC5A4: 0xD049, //HANGUL SYLLABLE KHIEUKH WI IEUNG - 0xC5A5: 0xD050, //HANGUL SYLLABLE KHIEUKH YU - 0xC5A6: 0xD054, //HANGUL SYLLABLE KHIEUKH YU NIEUN - 0xC5A7: 0xD058, //HANGUL SYLLABLE KHIEUKH YU RIEUL - 0xC5A8: 0xD060, //HANGUL SYLLABLE KHIEUKH YU MIEUM - 0xC5A9: 0xD06C, //HANGUL SYLLABLE KHIEUKH EU - 0xC5AA: 0xD06D, //HANGUL SYLLABLE KHIEUKH EU KIYEOK - 0xC5AB: 0xD070, //HANGUL SYLLABLE KHIEUKH EU NIEUN - 0xC5AC: 0xD074, //HANGUL SYLLABLE KHIEUKH EU RIEUL - 0xC5AD: 0xD07C, //HANGUL SYLLABLE KHIEUKH EU MIEUM - 0xC5AE: 0xD07D, //HANGUL SYLLABLE KHIEUKH EU PIEUP - 0xC5AF: 0xD081, //HANGUL SYLLABLE KHIEUKH EU IEUNG - 0xC5B0: 0xD0A4, //HANGUL SYLLABLE KHIEUKH I - 0xC5B1: 0xD0A5, //HANGUL SYLLABLE KHIEUKH I KIYEOK - 0xC5B2: 0xD0A8, //HANGUL SYLLABLE KHIEUKH I NIEUN - 0xC5B3: 0xD0AC, //HANGUL SYLLABLE KHIEUKH I RIEUL - 0xC5B4: 0xD0B4, //HANGUL SYLLABLE KHIEUKH I MIEUM - 0xC5B5: 0xD0B5, //HANGUL SYLLABLE KHIEUKH I PIEUP - 0xC5B6: 0xD0B7, //HANGUL SYLLABLE KHIEUKH I SIOS - 0xC5B7: 0xD0B9, //HANGUL SYLLABLE KHIEUKH I IEUNG - 0xC5B8: 0xD0C0, //HANGUL SYLLABLE THIEUTH A - 0xC5B9: 0xD0C1, //HANGUL SYLLABLE THIEUTH A KIYEOK - 0xC5BA: 0xD0C4, //HANGUL SYLLABLE THIEUTH A NIEUN - 0xC5BB: 0xD0C8, //HANGUL SYLLABLE THIEUTH A RIEUL - 0xC5BC: 0xD0C9, //HANGUL SYLLABLE THIEUTH A RIEULKIYEOK - 0xC5BD: 0xD0D0, //HANGUL SYLLABLE THIEUTH A MIEUM - 0xC5BE: 0xD0D1, //HANGUL SYLLABLE THIEUTH A PIEUP - 0xC5BF: 0xD0D3, //HANGUL SYLLABLE THIEUTH A SIOS - 0xC5C0: 0xD0D4, //HANGUL SYLLABLE THIEUTH A SSANGSIOS - 0xC5C1: 0xD0D5, //HANGUL SYLLABLE THIEUTH A IEUNG - 0xC5C2: 0xD0DC, //HANGUL SYLLABLE THIEUTH AE - 0xC5C3: 0xD0DD, //HANGUL SYLLABLE THIEUTH AE KIYEOK - 0xC5C4: 0xD0E0, //HANGUL SYLLABLE THIEUTH AE NIEUN - 0xC5C5: 0xD0E4, //HANGUL SYLLABLE THIEUTH AE RIEUL - 0xC5C6: 0xD0EC, //HANGUL SYLLABLE THIEUTH AE MIEUM - 0xC5C7: 0xD0ED, //HANGUL SYLLABLE THIEUTH AE PIEUP - 0xC5C8: 0xD0EF, //HANGUL SYLLABLE THIEUTH AE SIOS - 0xC5C9: 0xD0F0, //HANGUL SYLLABLE THIEUTH AE SSANGSIOS - 0xC5CA: 0xD0F1, //HANGUL SYLLABLE THIEUTH AE IEUNG - 0xC5CB: 0xD0F8, //HANGUL SYLLABLE THIEUTH YA - 0xC5CC: 0xD10D, //HANGUL SYLLABLE THIEUTH YA IEUNG - 0xC5CD: 0xD130, //HANGUL SYLLABLE THIEUTH EO - 0xC5CE: 0xD131, //HANGUL SYLLABLE THIEUTH EO KIYEOK - 0xC5CF: 0xD134, //HANGUL SYLLABLE THIEUTH EO NIEUN - 0xC5D0: 0xD138, //HANGUL SYLLABLE THIEUTH EO RIEUL - 0xC5D1: 0xD13A, //HANGUL SYLLABLE THIEUTH EO RIEULMIEUM - 0xC5D2: 0xD140, //HANGUL SYLLABLE THIEUTH EO MIEUM - 0xC5D3: 0xD141, //HANGUL SYLLABLE THIEUTH EO PIEUP - 0xC5D4: 0xD143, //HANGUL SYLLABLE THIEUTH EO SIOS - 0xC5D5: 0xD144, //HANGUL SYLLABLE THIEUTH EO SSANGSIOS - 0xC5D6: 0xD145, //HANGUL SYLLABLE THIEUTH EO IEUNG - 0xC5D7: 0xD14C, //HANGUL SYLLABLE THIEUTH E - 0xC5D8: 0xD14D, //HANGUL SYLLABLE THIEUTH E KIYEOK - 0xC5D9: 0xD150, //HANGUL SYLLABLE THIEUTH E NIEUN - 0xC5DA: 0xD154, //HANGUL SYLLABLE THIEUTH E RIEUL - 0xC5DB: 0xD15C, //HANGUL SYLLABLE THIEUTH E MIEUM - 0xC5DC: 0xD15D, //HANGUL SYLLABLE THIEUTH E PIEUP - 0xC5DD: 0xD15F, //HANGUL SYLLABLE THIEUTH E SIOS - 0xC5DE: 0xD161, //HANGUL SYLLABLE THIEUTH E IEUNG - 0xC5DF: 0xD168, //HANGUL SYLLABLE THIEUTH YEO - 0xC5E0: 0xD16C, //HANGUL SYLLABLE THIEUTH YEO NIEUN - 0xC5E1: 0xD17C, //HANGUL SYLLABLE THIEUTH YEO SSANGSIOS - 0xC5E2: 0xD184, //HANGUL SYLLABLE THIEUTH YE - 0xC5E3: 0xD188, //HANGUL SYLLABLE THIEUTH YE NIEUN - 0xC5E4: 0xD1A0, //HANGUL SYLLABLE THIEUTH O - 0xC5E5: 0xD1A1, //HANGUL SYLLABLE THIEUTH O KIYEOK - 0xC5E6: 0xD1A4, //HANGUL SYLLABLE THIEUTH O NIEUN - 0xC5E7: 0xD1A8, //HANGUL SYLLABLE THIEUTH O RIEUL - 0xC5E8: 0xD1B0, //HANGUL SYLLABLE THIEUTH O MIEUM - 0xC5E9: 0xD1B1, //HANGUL SYLLABLE THIEUTH O PIEUP - 0xC5EA: 0xD1B3, //HANGUL SYLLABLE THIEUTH O SIOS - 0xC5EB: 0xD1B5, //HANGUL SYLLABLE THIEUTH O IEUNG - 0xC5EC: 0xD1BA, //HANGUL SYLLABLE THIEUTH O PHIEUPH - 0xC5ED: 0xD1BC, //HANGUL SYLLABLE THIEUTH WA - 0xC5EE: 0xD1C0, //HANGUL SYLLABLE THIEUTH WA NIEUN - 0xC5EF: 0xD1D8, //HANGUL SYLLABLE THIEUTH WAE - 0xC5F0: 0xD1F4, //HANGUL SYLLABLE THIEUTH OE - 0xC5F1: 0xD1F8, //HANGUL SYLLABLE THIEUTH OE NIEUN - 0xC5F2: 0xD207, //HANGUL SYLLABLE THIEUTH OE SIOS - 0xC5F3: 0xD209, //HANGUL SYLLABLE THIEUTH OE IEUNG - 0xC5F4: 0xD210, //HANGUL SYLLABLE THIEUTH YO - 0xC5F5: 0xD22C, //HANGUL SYLLABLE THIEUTH U - 0xC5F6: 0xD22D, //HANGUL SYLLABLE THIEUTH U KIYEOK - 0xC5F7: 0xD230, //HANGUL SYLLABLE THIEUTH U NIEUN - 0xC5F8: 0xD234, //HANGUL SYLLABLE THIEUTH U RIEUL - 0xC5F9: 0xD23C, //HANGUL SYLLABLE THIEUTH U MIEUM - 0xC5FA: 0xD23D, //HANGUL SYLLABLE THIEUTH U PIEUP - 0xC5FB: 0xD23F, //HANGUL SYLLABLE THIEUTH U SIOS - 0xC5FC: 0xD241, //HANGUL SYLLABLE THIEUTH U IEUNG - 0xC5FD: 0xD248, //HANGUL SYLLABLE THIEUTH WEO - 0xC5FE: 0xD25C, //HANGUL SYLLABLE THIEUTH WEO SSANGSIOS - 0xC641: 0xD78D, //HANGUL SYLLABLE HIEUH I NIEUNCIEUC - 0xC642: 0xD78E, //HANGUL SYLLABLE HIEUH I NIEUNHIEUH - 0xC643: 0xD78F, //HANGUL SYLLABLE HIEUH I TIKEUT - 0xC644: 0xD791, //HANGUL SYLLABLE HIEUH I RIEULKIYEOK - 0xC645: 0xD792, //HANGUL SYLLABLE HIEUH I RIEULMIEUM - 0xC646: 0xD793, //HANGUL SYLLABLE HIEUH I RIEULPIEUP - 0xC647: 0xD794, //HANGUL SYLLABLE HIEUH I RIEULSIOS - 0xC648: 0xD795, //HANGUL SYLLABLE HIEUH I RIEULTHIEUTH - 0xC649: 0xD796, //HANGUL SYLLABLE HIEUH I RIEULPHIEUPH - 0xC64A: 0xD797, //HANGUL SYLLABLE HIEUH I RIEULHIEUH - 0xC64B: 0xD79A, //HANGUL SYLLABLE HIEUH I PIEUPSIOS - 0xC64C: 0xD79C, //HANGUL SYLLABLE HIEUH I SSANGSIOS - 0xC64D: 0xD79E, //HANGUL SYLLABLE HIEUH I CIEUC - 0xC64E: 0xD79F, //HANGUL SYLLABLE HIEUH I CHIEUCH - 0xC64F: 0xD7A0, //HANGUL SYLLABLE HIEUH I KHIEUKH - 0xC650: 0xD7A1, //HANGUL SYLLABLE HIEUH I THIEUTH - 0xC651: 0xD7A2, //HANGUL SYLLABLE HIEUH I PHIEUPH - 0xC652: 0xD7A3, //HANGUL SYLLABLE HIEUH I HIEUH - 0xC6A1: 0xD264, //HANGUL SYLLABLE THIEUTH WE - 0xC6A2: 0xD280, //HANGUL SYLLABLE THIEUTH WI - 0xC6A3: 0xD281, //HANGUL SYLLABLE THIEUTH WI KIYEOK - 0xC6A4: 0xD284, //HANGUL SYLLABLE THIEUTH WI NIEUN - 0xC6A5: 0xD288, //HANGUL SYLLABLE THIEUTH WI RIEUL - 0xC6A6: 0xD290, //HANGUL SYLLABLE THIEUTH WI MIEUM - 0xC6A7: 0xD291, //HANGUL SYLLABLE THIEUTH WI PIEUP - 0xC6A8: 0xD295, //HANGUL SYLLABLE THIEUTH WI IEUNG - 0xC6A9: 0xD29C, //HANGUL SYLLABLE THIEUTH YU - 0xC6AA: 0xD2A0, //HANGUL SYLLABLE THIEUTH YU NIEUN - 0xC6AB: 0xD2A4, //HANGUL SYLLABLE THIEUTH YU RIEUL - 0xC6AC: 0xD2AC, //HANGUL SYLLABLE THIEUTH YU MIEUM - 0xC6AD: 0xD2B1, //HANGUL SYLLABLE THIEUTH YU IEUNG - 0xC6AE: 0xD2B8, //HANGUL SYLLABLE THIEUTH EU - 0xC6AF: 0xD2B9, //HANGUL SYLLABLE THIEUTH EU KIYEOK - 0xC6B0: 0xD2BC, //HANGUL SYLLABLE THIEUTH EU NIEUN - 0xC6B1: 0xD2BF, //HANGUL SYLLABLE THIEUTH EU TIKEUT - 0xC6B2: 0xD2C0, //HANGUL SYLLABLE THIEUTH EU RIEUL - 0xC6B3: 0xD2C2, //HANGUL SYLLABLE THIEUTH EU RIEULMIEUM - 0xC6B4: 0xD2C8, //HANGUL SYLLABLE THIEUTH EU MIEUM - 0xC6B5: 0xD2C9, //HANGUL SYLLABLE THIEUTH EU PIEUP - 0xC6B6: 0xD2CB, //HANGUL SYLLABLE THIEUTH EU SIOS - 0xC6B7: 0xD2D4, //HANGUL SYLLABLE THIEUTH YI - 0xC6B8: 0xD2D8, //HANGUL SYLLABLE THIEUTH YI NIEUN - 0xC6B9: 0xD2DC, //HANGUL SYLLABLE THIEUTH YI RIEUL - 0xC6BA: 0xD2E4, //HANGUL SYLLABLE THIEUTH YI MIEUM - 0xC6BB: 0xD2E5, //HANGUL SYLLABLE THIEUTH YI PIEUP - 0xC6BC: 0xD2F0, //HANGUL SYLLABLE THIEUTH I - 0xC6BD: 0xD2F1, //HANGUL SYLLABLE THIEUTH I KIYEOK - 0xC6BE: 0xD2F4, //HANGUL SYLLABLE THIEUTH I NIEUN - 0xC6BF: 0xD2F8, //HANGUL SYLLABLE THIEUTH I RIEUL - 0xC6C0: 0xD300, //HANGUL SYLLABLE THIEUTH I MIEUM - 0xC6C1: 0xD301, //HANGUL SYLLABLE THIEUTH I PIEUP - 0xC6C2: 0xD303, //HANGUL SYLLABLE THIEUTH I SIOS - 0xC6C3: 0xD305, //HANGUL SYLLABLE THIEUTH I IEUNG - 0xC6C4: 0xD30C, //HANGUL SYLLABLE PHIEUPH A - 0xC6C5: 0xD30D, //HANGUL SYLLABLE PHIEUPH A KIYEOK - 0xC6C6: 0xD30E, //HANGUL SYLLABLE PHIEUPH A SSANGKIYEOK - 0xC6C7: 0xD310, //HANGUL SYLLABLE PHIEUPH A NIEUN - 0xC6C8: 0xD314, //HANGUL SYLLABLE PHIEUPH A RIEUL - 0xC6C9: 0xD316, //HANGUL SYLLABLE PHIEUPH A RIEULMIEUM - 0xC6CA: 0xD31C, //HANGUL SYLLABLE PHIEUPH A MIEUM - 0xC6CB: 0xD31D, //HANGUL SYLLABLE PHIEUPH A PIEUP - 0xC6CC: 0xD31F, //HANGUL SYLLABLE PHIEUPH A SIOS - 0xC6CD: 0xD320, //HANGUL SYLLABLE PHIEUPH A SSANGSIOS - 0xC6CE: 0xD321, //HANGUL SYLLABLE PHIEUPH A IEUNG - 0xC6CF: 0xD325, //HANGUL SYLLABLE PHIEUPH A THIEUTH - 0xC6D0: 0xD328, //HANGUL SYLLABLE PHIEUPH AE - 0xC6D1: 0xD329, //HANGUL SYLLABLE PHIEUPH AE KIYEOK - 0xC6D2: 0xD32C, //HANGUL SYLLABLE PHIEUPH AE NIEUN - 0xC6D3: 0xD330, //HANGUL SYLLABLE PHIEUPH AE RIEUL - 0xC6D4: 0xD338, //HANGUL SYLLABLE PHIEUPH AE MIEUM - 0xC6D5: 0xD339, //HANGUL SYLLABLE PHIEUPH AE PIEUP - 0xC6D6: 0xD33B, //HANGUL SYLLABLE PHIEUPH AE SIOS - 0xC6D7: 0xD33C, //HANGUL SYLLABLE PHIEUPH AE SSANGSIOS - 0xC6D8: 0xD33D, //HANGUL SYLLABLE PHIEUPH AE IEUNG - 0xC6D9: 0xD344, //HANGUL SYLLABLE PHIEUPH YA - 0xC6DA: 0xD345, //HANGUL SYLLABLE PHIEUPH YA KIYEOK - 0xC6DB: 0xD37C, //HANGUL SYLLABLE PHIEUPH EO - 0xC6DC: 0xD37D, //HANGUL SYLLABLE PHIEUPH EO KIYEOK - 0xC6DD: 0xD380, //HANGUL SYLLABLE PHIEUPH EO NIEUN - 0xC6DE: 0xD384, //HANGUL SYLLABLE PHIEUPH EO RIEUL - 0xC6DF: 0xD38C, //HANGUL SYLLABLE PHIEUPH EO MIEUM - 0xC6E0: 0xD38D, //HANGUL SYLLABLE PHIEUPH EO PIEUP - 0xC6E1: 0xD38F, //HANGUL SYLLABLE PHIEUPH EO SIOS - 0xC6E2: 0xD390, //HANGUL SYLLABLE PHIEUPH EO SSANGSIOS - 0xC6E3: 0xD391, //HANGUL SYLLABLE PHIEUPH EO IEUNG - 0xC6E4: 0xD398, //HANGUL SYLLABLE PHIEUPH E - 0xC6E5: 0xD399, //HANGUL SYLLABLE PHIEUPH E KIYEOK - 0xC6E6: 0xD39C, //HANGUL SYLLABLE PHIEUPH E NIEUN - 0xC6E7: 0xD3A0, //HANGUL SYLLABLE PHIEUPH E RIEUL - 0xC6E8: 0xD3A8, //HANGUL SYLLABLE PHIEUPH E MIEUM - 0xC6E9: 0xD3A9, //HANGUL SYLLABLE PHIEUPH E PIEUP - 0xC6EA: 0xD3AB, //HANGUL SYLLABLE PHIEUPH E SIOS - 0xC6EB: 0xD3AD, //HANGUL SYLLABLE PHIEUPH E IEUNG - 0xC6EC: 0xD3B4, //HANGUL SYLLABLE PHIEUPH YEO - 0xC6ED: 0xD3B8, //HANGUL SYLLABLE PHIEUPH YEO NIEUN - 0xC6EE: 0xD3BC, //HANGUL SYLLABLE PHIEUPH YEO RIEUL - 0xC6EF: 0xD3C4, //HANGUL SYLLABLE PHIEUPH YEO MIEUM - 0xC6F0: 0xD3C5, //HANGUL SYLLABLE PHIEUPH YEO PIEUP - 0xC6F1: 0xD3C8, //HANGUL SYLLABLE PHIEUPH YEO SSANGSIOS - 0xC6F2: 0xD3C9, //HANGUL SYLLABLE PHIEUPH YEO IEUNG - 0xC6F3: 0xD3D0, //HANGUL SYLLABLE PHIEUPH YE - 0xC6F4: 0xD3D8, //HANGUL SYLLABLE PHIEUPH YE RIEUL - 0xC6F5: 0xD3E1, //HANGUL SYLLABLE PHIEUPH YE PIEUP - 0xC6F6: 0xD3E3, //HANGUL SYLLABLE PHIEUPH YE SIOS - 0xC6F7: 0xD3EC, //HANGUL SYLLABLE PHIEUPH O - 0xC6F8: 0xD3ED, //HANGUL SYLLABLE PHIEUPH O KIYEOK - 0xC6F9: 0xD3F0, //HANGUL SYLLABLE PHIEUPH O NIEUN - 0xC6FA: 0xD3F4, //HANGUL SYLLABLE PHIEUPH O RIEUL - 0xC6FB: 0xD3FC, //HANGUL SYLLABLE PHIEUPH O MIEUM - 0xC6FC: 0xD3FD, //HANGUL SYLLABLE PHIEUPH O PIEUP - 0xC6FD: 0xD3FF, //HANGUL SYLLABLE PHIEUPH O SIOS - 0xC6FE: 0xD401, //HANGUL SYLLABLE PHIEUPH O IEUNG - 0xC7A1: 0xD408, //HANGUL SYLLABLE PHIEUPH WA - 0xC7A2: 0xD41D, //HANGUL SYLLABLE PHIEUPH WA IEUNG - 0xC7A3: 0xD440, //HANGUL SYLLABLE PHIEUPH OE - 0xC7A4: 0xD444, //HANGUL SYLLABLE PHIEUPH OE NIEUN - 0xC7A5: 0xD45C, //HANGUL SYLLABLE PHIEUPH YO - 0xC7A6: 0xD460, //HANGUL SYLLABLE PHIEUPH YO NIEUN - 0xC7A7: 0xD464, //HANGUL SYLLABLE PHIEUPH YO RIEUL - 0xC7A8: 0xD46D, //HANGUL SYLLABLE PHIEUPH YO PIEUP - 0xC7A9: 0xD46F, //HANGUL SYLLABLE PHIEUPH YO SIOS - 0xC7AA: 0xD478, //HANGUL SYLLABLE PHIEUPH U - 0xC7AB: 0xD479, //HANGUL SYLLABLE PHIEUPH U KIYEOK - 0xC7AC: 0xD47C, //HANGUL SYLLABLE PHIEUPH U NIEUN - 0xC7AD: 0xD47F, //HANGUL SYLLABLE PHIEUPH U TIKEUT - 0xC7AE: 0xD480, //HANGUL SYLLABLE PHIEUPH U RIEUL - 0xC7AF: 0xD482, //HANGUL SYLLABLE PHIEUPH U RIEULMIEUM - 0xC7B0: 0xD488, //HANGUL SYLLABLE PHIEUPH U MIEUM - 0xC7B1: 0xD489, //HANGUL SYLLABLE PHIEUPH U PIEUP - 0xC7B2: 0xD48B, //HANGUL SYLLABLE PHIEUPH U SIOS - 0xC7B3: 0xD48D, //HANGUL SYLLABLE PHIEUPH U IEUNG - 0xC7B4: 0xD494, //HANGUL SYLLABLE PHIEUPH WEO - 0xC7B5: 0xD4A9, //HANGUL SYLLABLE PHIEUPH WEO IEUNG - 0xC7B6: 0xD4CC, //HANGUL SYLLABLE PHIEUPH WI - 0xC7B7: 0xD4D0, //HANGUL SYLLABLE PHIEUPH WI NIEUN - 0xC7B8: 0xD4D4, //HANGUL SYLLABLE PHIEUPH WI RIEUL - 0xC7B9: 0xD4DC, //HANGUL SYLLABLE PHIEUPH WI MIEUM - 0xC7BA: 0xD4DF, //HANGUL SYLLABLE PHIEUPH WI SIOS - 0xC7BB: 0xD4E8, //HANGUL SYLLABLE PHIEUPH YU - 0xC7BC: 0xD4EC, //HANGUL SYLLABLE PHIEUPH YU NIEUN - 0xC7BD: 0xD4F0, //HANGUL SYLLABLE PHIEUPH YU RIEUL - 0xC7BE: 0xD4F8, //HANGUL SYLLABLE PHIEUPH YU MIEUM - 0xC7BF: 0xD4FB, //HANGUL SYLLABLE PHIEUPH YU SIOS - 0xC7C0: 0xD4FD, //HANGUL SYLLABLE PHIEUPH YU IEUNG - 0xC7C1: 0xD504, //HANGUL SYLLABLE PHIEUPH EU - 0xC7C2: 0xD508, //HANGUL SYLLABLE PHIEUPH EU NIEUN - 0xC7C3: 0xD50C, //HANGUL SYLLABLE PHIEUPH EU RIEUL - 0xC7C4: 0xD514, //HANGUL SYLLABLE PHIEUPH EU MIEUM - 0xC7C5: 0xD515, //HANGUL SYLLABLE PHIEUPH EU PIEUP - 0xC7C6: 0xD517, //HANGUL SYLLABLE PHIEUPH EU SIOS - 0xC7C7: 0xD53C, //HANGUL SYLLABLE PHIEUPH I - 0xC7C8: 0xD53D, //HANGUL SYLLABLE PHIEUPH I KIYEOK - 0xC7C9: 0xD540, //HANGUL SYLLABLE PHIEUPH I NIEUN - 0xC7CA: 0xD544, //HANGUL SYLLABLE PHIEUPH I RIEUL - 0xC7CB: 0xD54C, //HANGUL SYLLABLE PHIEUPH I MIEUM - 0xC7CC: 0xD54D, //HANGUL SYLLABLE PHIEUPH I PIEUP - 0xC7CD: 0xD54F, //HANGUL SYLLABLE PHIEUPH I SIOS - 0xC7CE: 0xD551, //HANGUL SYLLABLE PHIEUPH I IEUNG - 0xC7CF: 0xD558, //HANGUL SYLLABLE HIEUH A - 0xC7D0: 0xD559, //HANGUL SYLLABLE HIEUH A KIYEOK - 0xC7D1: 0xD55C, //HANGUL SYLLABLE HIEUH A NIEUN - 0xC7D2: 0xD560, //HANGUL SYLLABLE HIEUH A RIEUL - 0xC7D3: 0xD565, //HANGUL SYLLABLE HIEUH A RIEULTHIEUTH - 0xC7D4: 0xD568, //HANGUL SYLLABLE HIEUH A MIEUM - 0xC7D5: 0xD569, //HANGUL SYLLABLE HIEUH A PIEUP - 0xC7D6: 0xD56B, //HANGUL SYLLABLE HIEUH A SIOS - 0xC7D7: 0xD56D, //HANGUL SYLLABLE HIEUH A IEUNG - 0xC7D8: 0xD574, //HANGUL SYLLABLE HIEUH AE - 0xC7D9: 0xD575, //HANGUL SYLLABLE HIEUH AE KIYEOK - 0xC7DA: 0xD578, //HANGUL SYLLABLE HIEUH AE NIEUN - 0xC7DB: 0xD57C, //HANGUL SYLLABLE HIEUH AE RIEUL - 0xC7DC: 0xD584, //HANGUL SYLLABLE HIEUH AE MIEUM - 0xC7DD: 0xD585, //HANGUL SYLLABLE HIEUH AE PIEUP - 0xC7DE: 0xD587, //HANGUL SYLLABLE HIEUH AE SIOS - 0xC7DF: 0xD588, //HANGUL SYLLABLE HIEUH AE SSANGSIOS - 0xC7E0: 0xD589, //HANGUL SYLLABLE HIEUH AE IEUNG - 0xC7E1: 0xD590, //HANGUL SYLLABLE HIEUH YA - 0xC7E2: 0xD5A5, //HANGUL SYLLABLE HIEUH YA IEUNG - 0xC7E3: 0xD5C8, //HANGUL SYLLABLE HIEUH EO - 0xC7E4: 0xD5C9, //HANGUL SYLLABLE HIEUH EO KIYEOK - 0xC7E5: 0xD5CC, //HANGUL SYLLABLE HIEUH EO NIEUN - 0xC7E6: 0xD5D0, //HANGUL SYLLABLE HIEUH EO RIEUL - 0xC7E7: 0xD5D2, //HANGUL SYLLABLE HIEUH EO RIEULMIEUM - 0xC7E8: 0xD5D8, //HANGUL SYLLABLE HIEUH EO MIEUM - 0xC7E9: 0xD5D9, //HANGUL SYLLABLE HIEUH EO PIEUP - 0xC7EA: 0xD5DB, //HANGUL SYLLABLE HIEUH EO SIOS - 0xC7EB: 0xD5DD, //HANGUL SYLLABLE HIEUH EO IEUNG - 0xC7EC: 0xD5E4, //HANGUL SYLLABLE HIEUH E - 0xC7ED: 0xD5E5, //HANGUL SYLLABLE HIEUH E KIYEOK - 0xC7EE: 0xD5E8, //HANGUL SYLLABLE HIEUH E NIEUN - 0xC7EF: 0xD5EC, //HANGUL SYLLABLE HIEUH E RIEUL - 0xC7F0: 0xD5F4, //HANGUL SYLLABLE HIEUH E MIEUM - 0xC7F1: 0xD5F5, //HANGUL SYLLABLE HIEUH E PIEUP - 0xC7F2: 0xD5F7, //HANGUL SYLLABLE HIEUH E SIOS - 0xC7F3: 0xD5F9, //HANGUL SYLLABLE HIEUH E IEUNG - 0xC7F4: 0xD600, //HANGUL SYLLABLE HIEUH YEO - 0xC7F5: 0xD601, //HANGUL SYLLABLE HIEUH YEO KIYEOK - 0xC7F6: 0xD604, //HANGUL SYLLABLE HIEUH YEO NIEUN - 0xC7F7: 0xD608, //HANGUL SYLLABLE HIEUH YEO RIEUL - 0xC7F8: 0xD610, //HANGUL SYLLABLE HIEUH YEO MIEUM - 0xC7F9: 0xD611, //HANGUL SYLLABLE HIEUH YEO PIEUP - 0xC7FA: 0xD613, //HANGUL SYLLABLE HIEUH YEO SIOS - 0xC7FB: 0xD614, //HANGUL SYLLABLE HIEUH YEO SSANGSIOS - 0xC7FC: 0xD615, //HANGUL SYLLABLE HIEUH YEO IEUNG - 0xC7FD: 0xD61C, //HANGUL SYLLABLE HIEUH YE - 0xC7FE: 0xD620, //HANGUL SYLLABLE HIEUH YE NIEUN - 0xC8A1: 0xD624, //HANGUL SYLLABLE HIEUH YE RIEUL - 0xC8A2: 0xD62D, //HANGUL SYLLABLE HIEUH YE PIEUP - 0xC8A3: 0xD638, //HANGUL SYLLABLE HIEUH O - 0xC8A4: 0xD639, //HANGUL SYLLABLE HIEUH O KIYEOK - 0xC8A5: 0xD63C, //HANGUL SYLLABLE HIEUH O NIEUN - 0xC8A6: 0xD640, //HANGUL SYLLABLE HIEUH O RIEUL - 0xC8A7: 0xD645, //HANGUL SYLLABLE HIEUH O RIEULTHIEUTH - 0xC8A8: 0xD648, //HANGUL SYLLABLE HIEUH O MIEUM - 0xC8A9: 0xD649, //HANGUL SYLLABLE HIEUH O PIEUP - 0xC8AA: 0xD64B, //HANGUL SYLLABLE HIEUH O SIOS - 0xC8AB: 0xD64D, //HANGUL SYLLABLE HIEUH O IEUNG - 0xC8AC: 0xD651, //HANGUL SYLLABLE HIEUH O THIEUTH - 0xC8AD: 0xD654, //HANGUL SYLLABLE HIEUH WA - 0xC8AE: 0xD655, //HANGUL SYLLABLE HIEUH WA KIYEOK - 0xC8AF: 0xD658, //HANGUL SYLLABLE HIEUH WA NIEUN - 0xC8B0: 0xD65C, //HANGUL SYLLABLE HIEUH WA RIEUL - 0xC8B1: 0xD667, //HANGUL SYLLABLE HIEUH WA SIOS - 0xC8B2: 0xD669, //HANGUL SYLLABLE HIEUH WA IEUNG - 0xC8B3: 0xD670, //HANGUL SYLLABLE HIEUH WAE - 0xC8B4: 0xD671, //HANGUL SYLLABLE HIEUH WAE KIYEOK - 0xC8B5: 0xD674, //HANGUL SYLLABLE HIEUH WAE NIEUN - 0xC8B6: 0xD683, //HANGUL SYLLABLE HIEUH WAE SIOS - 0xC8B7: 0xD685, //HANGUL SYLLABLE HIEUH WAE IEUNG - 0xC8B8: 0xD68C, //HANGUL SYLLABLE HIEUH OE - 0xC8B9: 0xD68D, //HANGUL SYLLABLE HIEUH OE KIYEOK - 0xC8BA: 0xD690, //HANGUL SYLLABLE HIEUH OE NIEUN - 0xC8BB: 0xD694, //HANGUL SYLLABLE HIEUH OE RIEUL - 0xC8BC: 0xD69D, //HANGUL SYLLABLE HIEUH OE PIEUP - 0xC8BD: 0xD69F, //HANGUL SYLLABLE HIEUH OE SIOS - 0xC8BE: 0xD6A1, //HANGUL SYLLABLE HIEUH OE IEUNG - 0xC8BF: 0xD6A8, //HANGUL SYLLABLE HIEUH YO - 0xC8C0: 0xD6AC, //HANGUL SYLLABLE HIEUH YO NIEUN - 0xC8C1: 0xD6B0, //HANGUL SYLLABLE HIEUH YO RIEUL - 0xC8C2: 0xD6B9, //HANGUL SYLLABLE HIEUH YO PIEUP - 0xC8C3: 0xD6BB, //HANGUL SYLLABLE HIEUH YO SIOS - 0xC8C4: 0xD6C4, //HANGUL SYLLABLE HIEUH U - 0xC8C5: 0xD6C5, //HANGUL SYLLABLE HIEUH U KIYEOK - 0xC8C6: 0xD6C8, //HANGUL SYLLABLE HIEUH U NIEUN - 0xC8C7: 0xD6CC, //HANGUL SYLLABLE HIEUH U RIEUL - 0xC8C8: 0xD6D1, //HANGUL SYLLABLE HIEUH U RIEULTHIEUTH - 0xC8C9: 0xD6D4, //HANGUL SYLLABLE HIEUH U MIEUM - 0xC8CA: 0xD6D7, //HANGUL SYLLABLE HIEUH U SIOS - 0xC8CB: 0xD6D9, //HANGUL SYLLABLE HIEUH U IEUNG - 0xC8CC: 0xD6E0, //HANGUL SYLLABLE HIEUH WEO - 0xC8CD: 0xD6E4, //HANGUL SYLLABLE HIEUH WEO NIEUN - 0xC8CE: 0xD6E8, //HANGUL SYLLABLE HIEUH WEO RIEUL - 0xC8CF: 0xD6F0, //HANGUL SYLLABLE HIEUH WEO MIEUM - 0xC8D0: 0xD6F5, //HANGUL SYLLABLE HIEUH WEO IEUNG - 0xC8D1: 0xD6FC, //HANGUL SYLLABLE HIEUH WE - 0xC8D2: 0xD6FD, //HANGUL SYLLABLE HIEUH WE KIYEOK - 0xC8D3: 0xD700, //HANGUL SYLLABLE HIEUH WE NIEUN - 0xC8D4: 0xD704, //HANGUL SYLLABLE HIEUH WE RIEUL - 0xC8D5: 0xD711, //HANGUL SYLLABLE HIEUH WE IEUNG - 0xC8D6: 0xD718, //HANGUL SYLLABLE HIEUH WI - 0xC8D7: 0xD719, //HANGUL SYLLABLE HIEUH WI KIYEOK - 0xC8D8: 0xD71C, //HANGUL SYLLABLE HIEUH WI NIEUN - 0xC8D9: 0xD720, //HANGUL SYLLABLE HIEUH WI RIEUL - 0xC8DA: 0xD728, //HANGUL SYLLABLE HIEUH WI MIEUM - 0xC8DB: 0xD729, //HANGUL SYLLABLE HIEUH WI PIEUP - 0xC8DC: 0xD72B, //HANGUL SYLLABLE HIEUH WI SIOS - 0xC8DD: 0xD72D, //HANGUL SYLLABLE HIEUH WI IEUNG - 0xC8DE: 0xD734, //HANGUL SYLLABLE HIEUH YU - 0xC8DF: 0xD735, //HANGUL SYLLABLE HIEUH YU KIYEOK - 0xC8E0: 0xD738, //HANGUL SYLLABLE HIEUH YU NIEUN - 0xC8E1: 0xD73C, //HANGUL SYLLABLE HIEUH YU RIEUL - 0xC8E2: 0xD744, //HANGUL SYLLABLE HIEUH YU MIEUM - 0xC8E3: 0xD747, //HANGUL SYLLABLE HIEUH YU SIOS - 0xC8E4: 0xD749, //HANGUL SYLLABLE HIEUH YU IEUNG - 0xC8E5: 0xD750, //HANGUL SYLLABLE HIEUH EU - 0xC8E6: 0xD751, //HANGUL SYLLABLE HIEUH EU KIYEOK - 0xC8E7: 0xD754, //HANGUL SYLLABLE HIEUH EU NIEUN - 0xC8E8: 0xD756, //HANGUL SYLLABLE HIEUH EU NIEUNHIEUH - 0xC8E9: 0xD757, //HANGUL SYLLABLE HIEUH EU TIKEUT - 0xC8EA: 0xD758, //HANGUL SYLLABLE HIEUH EU RIEUL - 0xC8EB: 0xD759, //HANGUL SYLLABLE HIEUH EU RIEULKIYEOK - 0xC8EC: 0xD760, //HANGUL SYLLABLE HIEUH EU MIEUM - 0xC8ED: 0xD761, //HANGUL SYLLABLE HIEUH EU PIEUP - 0xC8EE: 0xD763, //HANGUL SYLLABLE HIEUH EU SIOS - 0xC8EF: 0xD765, //HANGUL SYLLABLE HIEUH EU IEUNG - 0xC8F0: 0xD769, //HANGUL SYLLABLE HIEUH EU THIEUTH - 0xC8F1: 0xD76C, //HANGUL SYLLABLE HIEUH YI - 0xC8F2: 0xD770, //HANGUL SYLLABLE HIEUH YI NIEUN - 0xC8F3: 0xD774, //HANGUL SYLLABLE HIEUH YI RIEUL - 0xC8F4: 0xD77C, //HANGUL SYLLABLE HIEUH YI MIEUM - 0xC8F5: 0xD77D, //HANGUL SYLLABLE HIEUH YI PIEUP - 0xC8F6: 0xD781, //HANGUL SYLLABLE HIEUH YI IEUNG - 0xC8F7: 0xD788, //HANGUL SYLLABLE HIEUH I - 0xC8F8: 0xD789, //HANGUL SYLLABLE HIEUH I KIYEOK - 0xC8F9: 0xD78C, //HANGUL SYLLABLE HIEUH I NIEUN - 0xC8FA: 0xD790, //HANGUL SYLLABLE HIEUH I RIEUL - 0xC8FB: 0xD798, //HANGUL SYLLABLE HIEUH I MIEUM - 0xC8FC: 0xD799, //HANGUL SYLLABLE HIEUH I PIEUP - 0xC8FD: 0xD79B, //HANGUL SYLLABLE HIEUH I SIOS - 0xC8FE: 0xD79D, //HANGUL SYLLABLE HIEUH I IEUNG - 0xCAA1: 0x4F3D, //CJK UNIFIED IDEOGRAPH - 0xCAA2: 0x4F73, //CJK UNIFIED IDEOGRAPH - 0xCAA3: 0x5047, //CJK UNIFIED IDEOGRAPH - 0xCAA4: 0x50F9, //CJK UNIFIED IDEOGRAPH - 0xCAA5: 0x52A0, //CJK UNIFIED IDEOGRAPH - 0xCAA6: 0x53EF, //CJK UNIFIED IDEOGRAPH - 0xCAA7: 0x5475, //CJK UNIFIED IDEOGRAPH - 0xCAA8: 0x54E5, //CJK UNIFIED IDEOGRAPH - 0xCAA9: 0x5609, //CJK UNIFIED IDEOGRAPH - 0xCAAA: 0x5AC1, //CJK UNIFIED IDEOGRAPH - 0xCAAB: 0x5BB6, //CJK UNIFIED IDEOGRAPH - 0xCAAC: 0x6687, //CJK UNIFIED IDEOGRAPH - 0xCAAD: 0x67B6, //CJK UNIFIED IDEOGRAPH - 0xCAAE: 0x67B7, //CJK UNIFIED IDEOGRAPH - 0xCAAF: 0x67EF, //CJK UNIFIED IDEOGRAPH - 0xCAB0: 0x6B4C, //CJK UNIFIED IDEOGRAPH - 0xCAB1: 0x73C2, //CJK UNIFIED IDEOGRAPH - 0xCAB2: 0x75C2, //CJK UNIFIED IDEOGRAPH - 0xCAB3: 0x7A3C, //CJK UNIFIED IDEOGRAPH - 0xCAB4: 0x82DB, //CJK UNIFIED IDEOGRAPH - 0xCAB5: 0x8304, //CJK UNIFIED IDEOGRAPH - 0xCAB6: 0x8857, //CJK UNIFIED IDEOGRAPH - 0xCAB7: 0x8888, //CJK UNIFIED IDEOGRAPH - 0xCAB8: 0x8A36, //CJK UNIFIED IDEOGRAPH - 0xCAB9: 0x8CC8, //CJK UNIFIED IDEOGRAPH - 0xCABA: 0x8DCF, //CJK UNIFIED IDEOGRAPH - 0xCABB: 0x8EFB, //CJK UNIFIED IDEOGRAPH - 0xCABC: 0x8FE6, //CJK UNIFIED IDEOGRAPH - 0xCABD: 0x99D5, //CJK UNIFIED IDEOGRAPH - 0xCABE: 0x523B, //CJK UNIFIED IDEOGRAPH - 0xCABF: 0x5374, //CJK UNIFIED IDEOGRAPH - 0xCAC0: 0x5404, //CJK UNIFIED IDEOGRAPH - 0xCAC1: 0x606A, //CJK UNIFIED IDEOGRAPH - 0xCAC2: 0x6164, //CJK UNIFIED IDEOGRAPH - 0xCAC3: 0x6BBC, //CJK UNIFIED IDEOGRAPH - 0xCAC4: 0x73CF, //CJK UNIFIED IDEOGRAPH - 0xCAC5: 0x811A, //CJK UNIFIED IDEOGRAPH - 0xCAC6: 0x89BA, //CJK UNIFIED IDEOGRAPH - 0xCAC7: 0x89D2, //CJK UNIFIED IDEOGRAPH - 0xCAC8: 0x95A3, //CJK UNIFIED IDEOGRAPH - 0xCAC9: 0x4F83, //CJK UNIFIED IDEOGRAPH - 0xCACA: 0x520A, //CJK UNIFIED IDEOGRAPH - 0xCACB: 0x58BE, //CJK UNIFIED IDEOGRAPH - 0xCACC: 0x5978, //CJK UNIFIED IDEOGRAPH - 0xCACD: 0x59E6, //CJK UNIFIED IDEOGRAPH - 0xCACE: 0x5E72, //CJK UNIFIED IDEOGRAPH - 0xCACF: 0x5E79, //CJK UNIFIED IDEOGRAPH - 0xCAD0: 0x61C7, //CJK UNIFIED IDEOGRAPH - 0xCAD1: 0x63C0, //CJK UNIFIED IDEOGRAPH - 0xCAD2: 0x6746, //CJK UNIFIED IDEOGRAPH - 0xCAD3: 0x67EC, //CJK UNIFIED IDEOGRAPH - 0xCAD4: 0x687F, //CJK UNIFIED IDEOGRAPH - 0xCAD5: 0x6F97, //CJK UNIFIED IDEOGRAPH - 0xCAD6: 0x764E, //CJK UNIFIED IDEOGRAPH - 0xCAD7: 0x770B, //CJK UNIFIED IDEOGRAPH - 0xCAD8: 0x78F5, //CJK UNIFIED IDEOGRAPH - 0xCAD9: 0x7A08, //CJK UNIFIED IDEOGRAPH - 0xCADA: 0x7AFF, //CJK UNIFIED IDEOGRAPH - 0xCADB: 0x7C21, //CJK UNIFIED IDEOGRAPH - 0xCADC: 0x809D, //CJK UNIFIED IDEOGRAPH - 0xCADD: 0x826E, //CJK UNIFIED IDEOGRAPH - 0xCADE: 0x8271, //CJK UNIFIED IDEOGRAPH - 0xCADF: 0x8AEB, //CJK UNIFIED IDEOGRAPH - 0xCAE0: 0x9593, //CJK UNIFIED IDEOGRAPH - 0xCAE1: 0x4E6B, //CJK UNIFIED IDEOGRAPH - 0xCAE2: 0x559D, //CJK UNIFIED IDEOGRAPH - 0xCAE3: 0x66F7, //CJK UNIFIED IDEOGRAPH - 0xCAE4: 0x6E34, //CJK UNIFIED IDEOGRAPH - 0xCAE5: 0x78A3, //CJK UNIFIED IDEOGRAPH - 0xCAE6: 0x7AED, //CJK UNIFIED IDEOGRAPH - 0xCAE7: 0x845B, //CJK UNIFIED IDEOGRAPH - 0xCAE8: 0x8910, //CJK UNIFIED IDEOGRAPH - 0xCAE9: 0x874E, //CJK UNIFIED IDEOGRAPH - 0xCAEA: 0x97A8, //CJK UNIFIED IDEOGRAPH - 0xCAEB: 0x52D8, //CJK UNIFIED IDEOGRAPH - 0xCAEC: 0x574E, //CJK UNIFIED IDEOGRAPH - 0xCAED: 0x582A, //CJK UNIFIED IDEOGRAPH - 0xCAEE: 0x5D4C, //CJK UNIFIED IDEOGRAPH - 0xCAEF: 0x611F, //CJK UNIFIED IDEOGRAPH - 0xCAF0: 0x61BE, //CJK UNIFIED IDEOGRAPH - 0xCAF1: 0x6221, //CJK UNIFIED IDEOGRAPH - 0xCAF2: 0x6562, //CJK UNIFIED IDEOGRAPH - 0xCAF3: 0x67D1, //CJK UNIFIED IDEOGRAPH - 0xCAF4: 0x6A44, //CJK UNIFIED IDEOGRAPH - 0xCAF5: 0x6E1B, //CJK UNIFIED IDEOGRAPH - 0xCAF6: 0x7518, //CJK UNIFIED IDEOGRAPH - 0xCAF7: 0x75B3, //CJK UNIFIED IDEOGRAPH - 0xCAF8: 0x76E3, //CJK UNIFIED IDEOGRAPH - 0xCAF9: 0x77B0, //CJK UNIFIED IDEOGRAPH - 0xCAFA: 0x7D3A, //CJK UNIFIED IDEOGRAPH - 0xCAFB: 0x90AF, //CJK UNIFIED IDEOGRAPH - 0xCAFC: 0x9451, //CJK UNIFIED IDEOGRAPH - 0xCAFD: 0x9452, //CJK UNIFIED IDEOGRAPH - 0xCAFE: 0x9F95, //CJK UNIFIED IDEOGRAPH - 0xCBA1: 0x5323, //CJK UNIFIED IDEOGRAPH - 0xCBA2: 0x5CAC, //CJK UNIFIED IDEOGRAPH - 0xCBA3: 0x7532, //CJK UNIFIED IDEOGRAPH - 0xCBA4: 0x80DB, //CJK UNIFIED IDEOGRAPH - 0xCBA5: 0x9240, //CJK UNIFIED IDEOGRAPH - 0xCBA6: 0x9598, //CJK UNIFIED IDEOGRAPH - 0xCBA7: 0x525B, //CJK UNIFIED IDEOGRAPH - 0xCBA8: 0x5808, //CJK UNIFIED IDEOGRAPH - 0xCBA9: 0x59DC, //CJK UNIFIED IDEOGRAPH - 0xCBAA: 0x5CA1, //CJK UNIFIED IDEOGRAPH - 0xCBAB: 0x5D17, //CJK UNIFIED IDEOGRAPH - 0xCBAC: 0x5EB7, //CJK UNIFIED IDEOGRAPH - 0xCBAD: 0x5F3A, //CJK UNIFIED IDEOGRAPH - 0xCBAE: 0x5F4A, //CJK UNIFIED IDEOGRAPH - 0xCBAF: 0x6177, //CJK UNIFIED IDEOGRAPH - 0xCBB0: 0x6C5F, //CJK UNIFIED IDEOGRAPH - 0xCBB1: 0x757A, //CJK UNIFIED IDEOGRAPH - 0xCBB2: 0x7586, //CJK UNIFIED IDEOGRAPH - 0xCBB3: 0x7CE0, //CJK UNIFIED IDEOGRAPH - 0xCBB4: 0x7D73, //CJK UNIFIED IDEOGRAPH - 0xCBB5: 0x7DB1, //CJK UNIFIED IDEOGRAPH - 0xCBB6: 0x7F8C, //CJK UNIFIED IDEOGRAPH - 0xCBB7: 0x8154, //CJK UNIFIED IDEOGRAPH - 0xCBB8: 0x8221, //CJK UNIFIED IDEOGRAPH - 0xCBB9: 0x8591, //CJK UNIFIED IDEOGRAPH - 0xCBBA: 0x8941, //CJK UNIFIED IDEOGRAPH - 0xCBBB: 0x8B1B, //CJK UNIFIED IDEOGRAPH - 0xCBBC: 0x92FC, //CJK UNIFIED IDEOGRAPH - 0xCBBD: 0x964D, //CJK UNIFIED IDEOGRAPH - 0xCBBE: 0x9C47, //CJK UNIFIED IDEOGRAPH - 0xCBBF: 0x4ECB, //CJK UNIFIED IDEOGRAPH - 0xCBC0: 0x4EF7, //CJK UNIFIED IDEOGRAPH - 0xCBC1: 0x500B, //CJK UNIFIED IDEOGRAPH - 0xCBC2: 0x51F1, //CJK UNIFIED IDEOGRAPH - 0xCBC3: 0x584F, //CJK UNIFIED IDEOGRAPH - 0xCBC4: 0x6137, //CJK UNIFIED IDEOGRAPH - 0xCBC5: 0x613E, //CJK UNIFIED IDEOGRAPH - 0xCBC6: 0x6168, //CJK UNIFIED IDEOGRAPH - 0xCBC7: 0x6539, //CJK UNIFIED IDEOGRAPH - 0xCBC8: 0x69EA, //CJK UNIFIED IDEOGRAPH - 0xCBC9: 0x6F11, //CJK UNIFIED IDEOGRAPH - 0xCBCA: 0x75A5, //CJK UNIFIED IDEOGRAPH - 0xCBCB: 0x7686, //CJK UNIFIED IDEOGRAPH - 0xCBCC: 0x76D6, //CJK UNIFIED IDEOGRAPH - 0xCBCD: 0x7B87, //CJK UNIFIED IDEOGRAPH - 0xCBCE: 0x82A5, //CJK UNIFIED IDEOGRAPH - 0xCBCF: 0x84CB, //CJK UNIFIED IDEOGRAPH - 0xCBD0: 0xF900, //CJK COMPATIBILITY IDEOGRAPH - 0xCBD1: 0x93A7, //CJK UNIFIED IDEOGRAPH - 0xCBD2: 0x958B, //CJK UNIFIED IDEOGRAPH - 0xCBD3: 0x5580, //CJK UNIFIED IDEOGRAPH - 0xCBD4: 0x5BA2, //CJK UNIFIED IDEOGRAPH - 0xCBD5: 0x5751, //CJK UNIFIED IDEOGRAPH - 0xCBD6: 0xF901, //CJK COMPATIBILITY IDEOGRAPH - 0xCBD7: 0x7CB3, //CJK UNIFIED IDEOGRAPH - 0xCBD8: 0x7FB9, //CJK UNIFIED IDEOGRAPH - 0xCBD9: 0x91B5, //CJK UNIFIED IDEOGRAPH - 0xCBDA: 0x5028, //CJK UNIFIED IDEOGRAPH - 0xCBDB: 0x53BB, //CJK UNIFIED IDEOGRAPH - 0xCBDC: 0x5C45, //CJK UNIFIED IDEOGRAPH - 0xCBDD: 0x5DE8, //CJK UNIFIED IDEOGRAPH - 0xCBDE: 0x62D2, //CJK UNIFIED IDEOGRAPH - 0xCBDF: 0x636E, //CJK UNIFIED IDEOGRAPH - 0xCBE0: 0x64DA, //CJK UNIFIED IDEOGRAPH - 0xCBE1: 0x64E7, //CJK UNIFIED IDEOGRAPH - 0xCBE2: 0x6E20, //CJK UNIFIED IDEOGRAPH - 0xCBE3: 0x70AC, //CJK UNIFIED IDEOGRAPH - 0xCBE4: 0x795B, //CJK UNIFIED IDEOGRAPH - 0xCBE5: 0x8DDD, //CJK UNIFIED IDEOGRAPH - 0xCBE6: 0x8E1E, //CJK UNIFIED IDEOGRAPH - 0xCBE7: 0xF902, //CJK COMPATIBILITY IDEOGRAPH - 0xCBE8: 0x907D, //CJK UNIFIED IDEOGRAPH - 0xCBE9: 0x9245, //CJK UNIFIED IDEOGRAPH - 0xCBEA: 0x92F8, //CJK UNIFIED IDEOGRAPH - 0xCBEB: 0x4E7E, //CJK UNIFIED IDEOGRAPH - 0xCBEC: 0x4EF6, //CJK UNIFIED IDEOGRAPH - 0xCBED: 0x5065, //CJK UNIFIED IDEOGRAPH - 0xCBEE: 0x5DFE, //CJK UNIFIED IDEOGRAPH - 0xCBEF: 0x5EFA, //CJK UNIFIED IDEOGRAPH - 0xCBF0: 0x6106, //CJK UNIFIED IDEOGRAPH - 0xCBF1: 0x6957, //CJK UNIFIED IDEOGRAPH - 0xCBF2: 0x8171, //CJK UNIFIED IDEOGRAPH - 0xCBF3: 0x8654, //CJK UNIFIED IDEOGRAPH - 0xCBF4: 0x8E47, //CJK UNIFIED IDEOGRAPH - 0xCBF5: 0x9375, //CJK UNIFIED IDEOGRAPH - 0xCBF6: 0x9A2B, //CJK UNIFIED IDEOGRAPH - 0xCBF7: 0x4E5E, //CJK UNIFIED IDEOGRAPH - 0xCBF8: 0x5091, //CJK UNIFIED IDEOGRAPH - 0xCBF9: 0x6770, //CJK UNIFIED IDEOGRAPH - 0xCBFA: 0x6840, //CJK UNIFIED IDEOGRAPH - 0xCBFB: 0x5109, //CJK UNIFIED IDEOGRAPH - 0xCBFC: 0x528D, //CJK UNIFIED IDEOGRAPH - 0xCBFD: 0x5292, //CJK UNIFIED IDEOGRAPH - 0xCBFE: 0x6AA2, //CJK UNIFIED IDEOGRAPH - 0xCCA1: 0x77BC, //CJK UNIFIED IDEOGRAPH - 0xCCA2: 0x9210, //CJK UNIFIED IDEOGRAPH - 0xCCA3: 0x9ED4, //CJK UNIFIED IDEOGRAPH - 0xCCA4: 0x52AB, //CJK UNIFIED IDEOGRAPH - 0xCCA5: 0x602F, //CJK UNIFIED IDEOGRAPH - 0xCCA6: 0x8FF2, //CJK UNIFIED IDEOGRAPH - 0xCCA7: 0x5048, //CJK UNIFIED IDEOGRAPH - 0xCCA8: 0x61A9, //CJK UNIFIED IDEOGRAPH - 0xCCA9: 0x63ED, //CJK UNIFIED IDEOGRAPH - 0xCCAA: 0x64CA, //CJK UNIFIED IDEOGRAPH - 0xCCAB: 0x683C, //CJK UNIFIED IDEOGRAPH - 0xCCAC: 0x6A84, //CJK UNIFIED IDEOGRAPH - 0xCCAD: 0x6FC0, //CJK UNIFIED IDEOGRAPH - 0xCCAE: 0x8188, //CJK UNIFIED IDEOGRAPH - 0xCCAF: 0x89A1, //CJK UNIFIED IDEOGRAPH - 0xCCB0: 0x9694, //CJK UNIFIED IDEOGRAPH - 0xCCB1: 0x5805, //CJK UNIFIED IDEOGRAPH - 0xCCB2: 0x727D, //CJK UNIFIED IDEOGRAPH - 0xCCB3: 0x72AC, //CJK UNIFIED IDEOGRAPH - 0xCCB4: 0x7504, //CJK UNIFIED IDEOGRAPH - 0xCCB5: 0x7D79, //CJK UNIFIED IDEOGRAPH - 0xCCB6: 0x7E6D, //CJK UNIFIED IDEOGRAPH - 0xCCB7: 0x80A9, //CJK UNIFIED IDEOGRAPH - 0xCCB8: 0x898B, //CJK UNIFIED IDEOGRAPH - 0xCCB9: 0x8B74, //CJK UNIFIED IDEOGRAPH - 0xCCBA: 0x9063, //CJK UNIFIED IDEOGRAPH - 0xCCBB: 0x9D51, //CJK UNIFIED IDEOGRAPH - 0xCCBC: 0x6289, //CJK UNIFIED IDEOGRAPH - 0xCCBD: 0x6C7A, //CJK UNIFIED IDEOGRAPH - 0xCCBE: 0x6F54, //CJK UNIFIED IDEOGRAPH - 0xCCBF: 0x7D50, //CJK UNIFIED IDEOGRAPH - 0xCCC0: 0x7F3A, //CJK UNIFIED IDEOGRAPH - 0xCCC1: 0x8A23, //CJK UNIFIED IDEOGRAPH - 0xCCC2: 0x517C, //CJK UNIFIED IDEOGRAPH - 0xCCC3: 0x614A, //CJK UNIFIED IDEOGRAPH - 0xCCC4: 0x7B9D, //CJK UNIFIED IDEOGRAPH - 0xCCC5: 0x8B19, //CJK UNIFIED IDEOGRAPH - 0xCCC6: 0x9257, //CJK UNIFIED IDEOGRAPH - 0xCCC7: 0x938C, //CJK UNIFIED IDEOGRAPH - 0xCCC8: 0x4EAC, //CJK UNIFIED IDEOGRAPH - 0xCCC9: 0x4FD3, //CJK UNIFIED IDEOGRAPH - 0xCCCA: 0x501E, //CJK UNIFIED IDEOGRAPH - 0xCCCB: 0x50BE, //CJK UNIFIED IDEOGRAPH - 0xCCCC: 0x5106, //CJK UNIFIED IDEOGRAPH - 0xCCCD: 0x52C1, //CJK UNIFIED IDEOGRAPH - 0xCCCE: 0x52CD, //CJK UNIFIED IDEOGRAPH - 0xCCCF: 0x537F, //CJK UNIFIED IDEOGRAPH - 0xCCD0: 0x5770, //CJK UNIFIED IDEOGRAPH - 0xCCD1: 0x5883, //CJK UNIFIED IDEOGRAPH - 0xCCD2: 0x5E9A, //CJK UNIFIED IDEOGRAPH - 0xCCD3: 0x5F91, //CJK UNIFIED IDEOGRAPH - 0xCCD4: 0x6176, //CJK UNIFIED IDEOGRAPH - 0xCCD5: 0x61AC, //CJK UNIFIED IDEOGRAPH - 0xCCD6: 0x64CE, //CJK UNIFIED IDEOGRAPH - 0xCCD7: 0x656C, //CJK UNIFIED IDEOGRAPH - 0xCCD8: 0x666F, //CJK UNIFIED IDEOGRAPH - 0xCCD9: 0x66BB, //CJK UNIFIED IDEOGRAPH - 0xCCDA: 0x66F4, //CJK UNIFIED IDEOGRAPH - 0xCCDB: 0x6897, //CJK UNIFIED IDEOGRAPH - 0xCCDC: 0x6D87, //CJK UNIFIED IDEOGRAPH - 0xCCDD: 0x7085, //CJK UNIFIED IDEOGRAPH - 0xCCDE: 0x70F1, //CJK UNIFIED IDEOGRAPH - 0xCCDF: 0x749F, //CJK UNIFIED IDEOGRAPH - 0xCCE0: 0x74A5, //CJK UNIFIED IDEOGRAPH - 0xCCE1: 0x74CA, //CJK UNIFIED IDEOGRAPH - 0xCCE2: 0x75D9, //CJK UNIFIED IDEOGRAPH - 0xCCE3: 0x786C, //CJK UNIFIED IDEOGRAPH - 0xCCE4: 0x78EC, //CJK UNIFIED IDEOGRAPH - 0xCCE5: 0x7ADF, //CJK UNIFIED IDEOGRAPH - 0xCCE6: 0x7AF6, //CJK UNIFIED IDEOGRAPH - 0xCCE7: 0x7D45, //CJK UNIFIED IDEOGRAPH - 0xCCE8: 0x7D93, //CJK UNIFIED IDEOGRAPH - 0xCCE9: 0x8015, //CJK UNIFIED IDEOGRAPH - 0xCCEA: 0x803F, //CJK UNIFIED IDEOGRAPH - 0xCCEB: 0x811B, //CJK UNIFIED IDEOGRAPH - 0xCCEC: 0x8396, //CJK UNIFIED IDEOGRAPH - 0xCCED: 0x8B66, //CJK UNIFIED IDEOGRAPH - 0xCCEE: 0x8F15, //CJK UNIFIED IDEOGRAPH - 0xCCEF: 0x9015, //CJK UNIFIED IDEOGRAPH - 0xCCF0: 0x93E1, //CJK UNIFIED IDEOGRAPH - 0xCCF1: 0x9803, //CJK UNIFIED IDEOGRAPH - 0xCCF2: 0x9838, //CJK UNIFIED IDEOGRAPH - 0xCCF3: 0x9A5A, //CJK UNIFIED IDEOGRAPH - 0xCCF4: 0x9BE8, //CJK UNIFIED IDEOGRAPH - 0xCCF5: 0x4FC2, //CJK UNIFIED IDEOGRAPH - 0xCCF6: 0x5553, //CJK UNIFIED IDEOGRAPH - 0xCCF7: 0x583A, //CJK UNIFIED IDEOGRAPH - 0xCCF8: 0x5951, //CJK UNIFIED IDEOGRAPH - 0xCCF9: 0x5B63, //CJK UNIFIED IDEOGRAPH - 0xCCFA: 0x5C46, //CJK UNIFIED IDEOGRAPH - 0xCCFB: 0x60B8, //CJK UNIFIED IDEOGRAPH - 0xCCFC: 0x6212, //CJK UNIFIED IDEOGRAPH - 0xCCFD: 0x6842, //CJK UNIFIED IDEOGRAPH - 0xCCFE: 0x68B0, //CJK UNIFIED IDEOGRAPH - 0xCDA1: 0x68E8, //CJK UNIFIED IDEOGRAPH - 0xCDA2: 0x6EAA, //CJK UNIFIED IDEOGRAPH - 0xCDA3: 0x754C, //CJK UNIFIED IDEOGRAPH - 0xCDA4: 0x7678, //CJK UNIFIED IDEOGRAPH - 0xCDA5: 0x78CE, //CJK UNIFIED IDEOGRAPH - 0xCDA6: 0x7A3D, //CJK UNIFIED IDEOGRAPH - 0xCDA7: 0x7CFB, //CJK UNIFIED IDEOGRAPH - 0xCDA8: 0x7E6B, //CJK UNIFIED IDEOGRAPH - 0xCDA9: 0x7E7C, //CJK UNIFIED IDEOGRAPH - 0xCDAA: 0x8A08, //CJK UNIFIED IDEOGRAPH - 0xCDAB: 0x8AA1, //CJK UNIFIED IDEOGRAPH - 0xCDAC: 0x8C3F, //CJK UNIFIED IDEOGRAPH - 0xCDAD: 0x968E, //CJK UNIFIED IDEOGRAPH - 0xCDAE: 0x9DC4, //CJK UNIFIED IDEOGRAPH - 0xCDAF: 0x53E4, //CJK UNIFIED IDEOGRAPH - 0xCDB0: 0x53E9, //CJK UNIFIED IDEOGRAPH - 0xCDB1: 0x544A, //CJK UNIFIED IDEOGRAPH - 0xCDB2: 0x5471, //CJK UNIFIED IDEOGRAPH - 0xCDB3: 0x56FA, //CJK UNIFIED IDEOGRAPH - 0xCDB4: 0x59D1, //CJK UNIFIED IDEOGRAPH - 0xCDB5: 0x5B64, //CJK UNIFIED IDEOGRAPH - 0xCDB6: 0x5C3B, //CJK UNIFIED IDEOGRAPH - 0xCDB7: 0x5EAB, //CJK UNIFIED IDEOGRAPH - 0xCDB8: 0x62F7, //CJK UNIFIED IDEOGRAPH - 0xCDB9: 0x6537, //CJK UNIFIED IDEOGRAPH - 0xCDBA: 0x6545, //CJK UNIFIED IDEOGRAPH - 0xCDBB: 0x6572, //CJK UNIFIED IDEOGRAPH - 0xCDBC: 0x66A0, //CJK UNIFIED IDEOGRAPH - 0xCDBD: 0x67AF, //CJK UNIFIED IDEOGRAPH - 0xCDBE: 0x69C1, //CJK UNIFIED IDEOGRAPH - 0xCDBF: 0x6CBD, //CJK UNIFIED IDEOGRAPH - 0xCDC0: 0x75FC, //CJK UNIFIED IDEOGRAPH - 0xCDC1: 0x7690, //CJK UNIFIED IDEOGRAPH - 0xCDC2: 0x777E, //CJK UNIFIED IDEOGRAPH - 0xCDC3: 0x7A3F, //CJK UNIFIED IDEOGRAPH - 0xCDC4: 0x7F94, //CJK UNIFIED IDEOGRAPH - 0xCDC5: 0x8003, //CJK UNIFIED IDEOGRAPH - 0xCDC6: 0x80A1, //CJK UNIFIED IDEOGRAPH - 0xCDC7: 0x818F, //CJK UNIFIED IDEOGRAPH - 0xCDC8: 0x82E6, //CJK UNIFIED IDEOGRAPH - 0xCDC9: 0x82FD, //CJK UNIFIED IDEOGRAPH - 0xCDCA: 0x83F0, //CJK UNIFIED IDEOGRAPH - 0xCDCB: 0x85C1, //CJK UNIFIED IDEOGRAPH - 0xCDCC: 0x8831, //CJK UNIFIED IDEOGRAPH - 0xCDCD: 0x88B4, //CJK UNIFIED IDEOGRAPH - 0xCDCE: 0x8AA5, //CJK UNIFIED IDEOGRAPH - 0xCDCF: 0xF903, //CJK COMPATIBILITY IDEOGRAPH - 0xCDD0: 0x8F9C, //CJK UNIFIED IDEOGRAPH - 0xCDD1: 0x932E, //CJK UNIFIED IDEOGRAPH - 0xCDD2: 0x96C7, //CJK UNIFIED IDEOGRAPH - 0xCDD3: 0x9867, //CJK UNIFIED IDEOGRAPH - 0xCDD4: 0x9AD8, //CJK UNIFIED IDEOGRAPH - 0xCDD5: 0x9F13, //CJK UNIFIED IDEOGRAPH - 0xCDD6: 0x54ED, //CJK UNIFIED IDEOGRAPH - 0xCDD7: 0x659B, //CJK UNIFIED IDEOGRAPH - 0xCDD8: 0x66F2, //CJK UNIFIED IDEOGRAPH - 0xCDD9: 0x688F, //CJK UNIFIED IDEOGRAPH - 0xCDDA: 0x7A40, //CJK UNIFIED IDEOGRAPH - 0xCDDB: 0x8C37, //CJK UNIFIED IDEOGRAPH - 0xCDDC: 0x9D60, //CJK UNIFIED IDEOGRAPH - 0xCDDD: 0x56F0, //CJK UNIFIED IDEOGRAPH - 0xCDDE: 0x5764, //CJK UNIFIED IDEOGRAPH - 0xCDDF: 0x5D11, //CJK UNIFIED IDEOGRAPH - 0xCDE0: 0x6606, //CJK UNIFIED IDEOGRAPH - 0xCDE1: 0x68B1, //CJK UNIFIED IDEOGRAPH - 0xCDE2: 0x68CD, //CJK UNIFIED IDEOGRAPH - 0xCDE3: 0x6EFE, //CJK UNIFIED IDEOGRAPH - 0xCDE4: 0x7428, //CJK UNIFIED IDEOGRAPH - 0xCDE5: 0x889E, //CJK UNIFIED IDEOGRAPH - 0xCDE6: 0x9BE4, //CJK UNIFIED IDEOGRAPH - 0xCDE7: 0x6C68, //CJK UNIFIED IDEOGRAPH - 0xCDE8: 0xF904, //CJK COMPATIBILITY IDEOGRAPH - 0xCDE9: 0x9AA8, //CJK UNIFIED IDEOGRAPH - 0xCDEA: 0x4F9B, //CJK UNIFIED IDEOGRAPH - 0xCDEB: 0x516C, //CJK UNIFIED IDEOGRAPH - 0xCDEC: 0x5171, //CJK UNIFIED IDEOGRAPH - 0xCDED: 0x529F, //CJK UNIFIED IDEOGRAPH - 0xCDEE: 0x5B54, //CJK UNIFIED IDEOGRAPH - 0xCDEF: 0x5DE5, //CJK UNIFIED IDEOGRAPH - 0xCDF0: 0x6050, //CJK UNIFIED IDEOGRAPH - 0xCDF1: 0x606D, //CJK UNIFIED IDEOGRAPH - 0xCDF2: 0x62F1, //CJK UNIFIED IDEOGRAPH - 0xCDF3: 0x63A7, //CJK UNIFIED IDEOGRAPH - 0xCDF4: 0x653B, //CJK UNIFIED IDEOGRAPH - 0xCDF5: 0x73D9, //CJK UNIFIED IDEOGRAPH - 0xCDF6: 0x7A7A, //CJK UNIFIED IDEOGRAPH - 0xCDF7: 0x86A3, //CJK UNIFIED IDEOGRAPH - 0xCDF8: 0x8CA2, //CJK UNIFIED IDEOGRAPH - 0xCDF9: 0x978F, //CJK UNIFIED IDEOGRAPH - 0xCDFA: 0x4E32, //CJK UNIFIED IDEOGRAPH - 0xCDFB: 0x5BE1, //CJK UNIFIED IDEOGRAPH - 0xCDFC: 0x6208, //CJK UNIFIED IDEOGRAPH - 0xCDFD: 0x679C, //CJK UNIFIED IDEOGRAPH - 0xCDFE: 0x74DC, //CJK UNIFIED IDEOGRAPH - 0xCEA1: 0x79D1, //CJK UNIFIED IDEOGRAPH - 0xCEA2: 0x83D3, //CJK UNIFIED IDEOGRAPH - 0xCEA3: 0x8A87, //CJK UNIFIED IDEOGRAPH - 0xCEA4: 0x8AB2, //CJK UNIFIED IDEOGRAPH - 0xCEA5: 0x8DE8, //CJK UNIFIED IDEOGRAPH - 0xCEA6: 0x904E, //CJK UNIFIED IDEOGRAPH - 0xCEA7: 0x934B, //CJK UNIFIED IDEOGRAPH - 0xCEA8: 0x9846, //CJK UNIFIED IDEOGRAPH - 0xCEA9: 0x5ED3, //CJK UNIFIED IDEOGRAPH - 0xCEAA: 0x69E8, //CJK UNIFIED IDEOGRAPH - 0xCEAB: 0x85FF, //CJK UNIFIED IDEOGRAPH - 0xCEAC: 0x90ED, //CJK UNIFIED IDEOGRAPH - 0xCEAD: 0xF905, //CJK COMPATIBILITY IDEOGRAPH - 0xCEAE: 0x51A0, //CJK UNIFIED IDEOGRAPH - 0xCEAF: 0x5B98, //CJK UNIFIED IDEOGRAPH - 0xCEB0: 0x5BEC, //CJK UNIFIED IDEOGRAPH - 0xCEB1: 0x6163, //CJK UNIFIED IDEOGRAPH - 0xCEB2: 0x68FA, //CJK UNIFIED IDEOGRAPH - 0xCEB3: 0x6B3E, //CJK UNIFIED IDEOGRAPH - 0xCEB4: 0x704C, //CJK UNIFIED IDEOGRAPH - 0xCEB5: 0x742F, //CJK UNIFIED IDEOGRAPH - 0xCEB6: 0x74D8, //CJK UNIFIED IDEOGRAPH - 0xCEB7: 0x7BA1, //CJK UNIFIED IDEOGRAPH - 0xCEB8: 0x7F50, //CJK UNIFIED IDEOGRAPH - 0xCEB9: 0x83C5, //CJK UNIFIED IDEOGRAPH - 0xCEBA: 0x89C0, //CJK UNIFIED IDEOGRAPH - 0xCEBB: 0x8CAB, //CJK UNIFIED IDEOGRAPH - 0xCEBC: 0x95DC, //CJK UNIFIED IDEOGRAPH - 0xCEBD: 0x9928, //CJK UNIFIED IDEOGRAPH - 0xCEBE: 0x522E, //CJK UNIFIED IDEOGRAPH - 0xCEBF: 0x605D, //CJK UNIFIED IDEOGRAPH - 0xCEC0: 0x62EC, //CJK UNIFIED IDEOGRAPH - 0xCEC1: 0x9002, //CJK UNIFIED IDEOGRAPH - 0xCEC2: 0x4F8A, //CJK UNIFIED IDEOGRAPH - 0xCEC3: 0x5149, //CJK UNIFIED IDEOGRAPH - 0xCEC4: 0x5321, //CJK UNIFIED IDEOGRAPH - 0xCEC5: 0x58D9, //CJK UNIFIED IDEOGRAPH - 0xCEC6: 0x5EE3, //CJK UNIFIED IDEOGRAPH - 0xCEC7: 0x66E0, //CJK UNIFIED IDEOGRAPH - 0xCEC8: 0x6D38, //CJK UNIFIED IDEOGRAPH - 0xCEC9: 0x709A, //CJK UNIFIED IDEOGRAPH - 0xCECA: 0x72C2, //CJK UNIFIED IDEOGRAPH - 0xCECB: 0x73D6, //CJK UNIFIED IDEOGRAPH - 0xCECC: 0x7B50, //CJK UNIFIED IDEOGRAPH - 0xCECD: 0x80F1, //CJK UNIFIED IDEOGRAPH - 0xCECE: 0x945B, //CJK UNIFIED IDEOGRAPH - 0xCECF: 0x5366, //CJK UNIFIED IDEOGRAPH - 0xCED0: 0x639B, //CJK UNIFIED IDEOGRAPH - 0xCED1: 0x7F6B, //CJK UNIFIED IDEOGRAPH - 0xCED2: 0x4E56, //CJK UNIFIED IDEOGRAPH - 0xCED3: 0x5080, //CJK UNIFIED IDEOGRAPH - 0xCED4: 0x584A, //CJK UNIFIED IDEOGRAPH - 0xCED5: 0x58DE, //CJK UNIFIED IDEOGRAPH - 0xCED6: 0x602A, //CJK UNIFIED IDEOGRAPH - 0xCED7: 0x6127, //CJK UNIFIED IDEOGRAPH - 0xCED8: 0x62D0, //CJK UNIFIED IDEOGRAPH - 0xCED9: 0x69D0, //CJK UNIFIED IDEOGRAPH - 0xCEDA: 0x9B41, //CJK UNIFIED IDEOGRAPH - 0xCEDB: 0x5B8F, //CJK UNIFIED IDEOGRAPH - 0xCEDC: 0x7D18, //CJK UNIFIED IDEOGRAPH - 0xCEDD: 0x80B1, //CJK UNIFIED IDEOGRAPH - 0xCEDE: 0x8F5F, //CJK UNIFIED IDEOGRAPH - 0xCEDF: 0x4EA4, //CJK UNIFIED IDEOGRAPH - 0xCEE0: 0x50D1, //CJK UNIFIED IDEOGRAPH - 0xCEE1: 0x54AC, //CJK UNIFIED IDEOGRAPH - 0xCEE2: 0x55AC, //CJK UNIFIED IDEOGRAPH - 0xCEE3: 0x5B0C, //CJK UNIFIED IDEOGRAPH - 0xCEE4: 0x5DA0, //CJK UNIFIED IDEOGRAPH - 0xCEE5: 0x5DE7, //CJK UNIFIED IDEOGRAPH - 0xCEE6: 0x652A, //CJK UNIFIED IDEOGRAPH - 0xCEE7: 0x654E, //CJK UNIFIED IDEOGRAPH - 0xCEE8: 0x6821, //CJK UNIFIED IDEOGRAPH - 0xCEE9: 0x6A4B, //CJK UNIFIED IDEOGRAPH - 0xCEEA: 0x72E1, //CJK UNIFIED IDEOGRAPH - 0xCEEB: 0x768E, //CJK UNIFIED IDEOGRAPH - 0xCEEC: 0x77EF, //CJK UNIFIED IDEOGRAPH - 0xCEED: 0x7D5E, //CJK UNIFIED IDEOGRAPH - 0xCEEE: 0x7FF9, //CJK UNIFIED IDEOGRAPH - 0xCEEF: 0x81A0, //CJK UNIFIED IDEOGRAPH - 0xCEF0: 0x854E, //CJK UNIFIED IDEOGRAPH - 0xCEF1: 0x86DF, //CJK UNIFIED IDEOGRAPH - 0xCEF2: 0x8F03, //CJK UNIFIED IDEOGRAPH - 0xCEF3: 0x8F4E, //CJK UNIFIED IDEOGRAPH - 0xCEF4: 0x90CA, //CJK UNIFIED IDEOGRAPH - 0xCEF5: 0x9903, //CJK UNIFIED IDEOGRAPH - 0xCEF6: 0x9A55, //CJK UNIFIED IDEOGRAPH - 0xCEF7: 0x9BAB, //CJK UNIFIED IDEOGRAPH - 0xCEF8: 0x4E18, //CJK UNIFIED IDEOGRAPH - 0xCEF9: 0x4E45, //CJK UNIFIED IDEOGRAPH - 0xCEFA: 0x4E5D, //CJK UNIFIED IDEOGRAPH - 0xCEFB: 0x4EC7, //CJK UNIFIED IDEOGRAPH - 0xCEFC: 0x4FF1, //CJK UNIFIED IDEOGRAPH - 0xCEFD: 0x5177, //CJK UNIFIED IDEOGRAPH - 0xCEFE: 0x52FE, //CJK UNIFIED IDEOGRAPH - 0xCFA1: 0x5340, //CJK UNIFIED IDEOGRAPH - 0xCFA2: 0x53E3, //CJK UNIFIED IDEOGRAPH - 0xCFA3: 0x53E5, //CJK UNIFIED IDEOGRAPH - 0xCFA4: 0x548E, //CJK UNIFIED IDEOGRAPH - 0xCFA5: 0x5614, //CJK UNIFIED IDEOGRAPH - 0xCFA6: 0x5775, //CJK UNIFIED IDEOGRAPH - 0xCFA7: 0x57A2, //CJK UNIFIED IDEOGRAPH - 0xCFA8: 0x5BC7, //CJK UNIFIED IDEOGRAPH - 0xCFA9: 0x5D87, //CJK UNIFIED IDEOGRAPH - 0xCFAA: 0x5ED0, //CJK UNIFIED IDEOGRAPH - 0xCFAB: 0x61FC, //CJK UNIFIED IDEOGRAPH - 0xCFAC: 0x62D8, //CJK UNIFIED IDEOGRAPH - 0xCFAD: 0x6551, //CJK UNIFIED IDEOGRAPH - 0xCFAE: 0x67B8, //CJK UNIFIED IDEOGRAPH - 0xCFAF: 0x67E9, //CJK UNIFIED IDEOGRAPH - 0xCFB0: 0x69CB, //CJK UNIFIED IDEOGRAPH - 0xCFB1: 0x6B50, //CJK UNIFIED IDEOGRAPH - 0xCFB2: 0x6BC6, //CJK UNIFIED IDEOGRAPH - 0xCFB3: 0x6BEC, //CJK UNIFIED IDEOGRAPH - 0xCFB4: 0x6C42, //CJK UNIFIED IDEOGRAPH - 0xCFB5: 0x6E9D, //CJK UNIFIED IDEOGRAPH - 0xCFB6: 0x7078, //CJK UNIFIED IDEOGRAPH - 0xCFB7: 0x72D7, //CJK UNIFIED IDEOGRAPH - 0xCFB8: 0x7396, //CJK UNIFIED IDEOGRAPH - 0xCFB9: 0x7403, //CJK UNIFIED IDEOGRAPH - 0xCFBA: 0x77BF, //CJK UNIFIED IDEOGRAPH - 0xCFBB: 0x77E9, //CJK UNIFIED IDEOGRAPH - 0xCFBC: 0x7A76, //CJK UNIFIED IDEOGRAPH - 0xCFBD: 0x7D7F, //CJK UNIFIED IDEOGRAPH - 0xCFBE: 0x8009, //CJK UNIFIED IDEOGRAPH - 0xCFBF: 0x81FC, //CJK UNIFIED IDEOGRAPH - 0xCFC0: 0x8205, //CJK UNIFIED IDEOGRAPH - 0xCFC1: 0x820A, //CJK UNIFIED IDEOGRAPH - 0xCFC2: 0x82DF, //CJK UNIFIED IDEOGRAPH - 0xCFC3: 0x8862, //CJK UNIFIED IDEOGRAPH - 0xCFC4: 0x8B33, //CJK UNIFIED IDEOGRAPH - 0xCFC5: 0x8CFC, //CJK UNIFIED IDEOGRAPH - 0xCFC6: 0x8EC0, //CJK UNIFIED IDEOGRAPH - 0xCFC7: 0x9011, //CJK UNIFIED IDEOGRAPH - 0xCFC8: 0x90B1, //CJK UNIFIED IDEOGRAPH - 0xCFC9: 0x9264, //CJK UNIFIED IDEOGRAPH - 0xCFCA: 0x92B6, //CJK UNIFIED IDEOGRAPH - 0xCFCB: 0x99D2, //CJK UNIFIED IDEOGRAPH - 0xCFCC: 0x9A45, //CJK UNIFIED IDEOGRAPH - 0xCFCD: 0x9CE9, //CJK UNIFIED IDEOGRAPH - 0xCFCE: 0x9DD7, //CJK UNIFIED IDEOGRAPH - 0xCFCF: 0x9F9C, //CJK UNIFIED IDEOGRAPH - 0xCFD0: 0x570B, //CJK UNIFIED IDEOGRAPH - 0xCFD1: 0x5C40, //CJK UNIFIED IDEOGRAPH - 0xCFD2: 0x83CA, //CJK UNIFIED IDEOGRAPH - 0xCFD3: 0x97A0, //CJK UNIFIED IDEOGRAPH - 0xCFD4: 0x97AB, //CJK UNIFIED IDEOGRAPH - 0xCFD5: 0x9EB4, //CJK UNIFIED IDEOGRAPH - 0xCFD6: 0x541B, //CJK UNIFIED IDEOGRAPH - 0xCFD7: 0x7A98, //CJK UNIFIED IDEOGRAPH - 0xCFD8: 0x7FA4, //CJK UNIFIED IDEOGRAPH - 0xCFD9: 0x88D9, //CJK UNIFIED IDEOGRAPH - 0xCFDA: 0x8ECD, //CJK UNIFIED IDEOGRAPH - 0xCFDB: 0x90E1, //CJK UNIFIED IDEOGRAPH - 0xCFDC: 0x5800, //CJK UNIFIED IDEOGRAPH - 0xCFDD: 0x5C48, //CJK UNIFIED IDEOGRAPH - 0xCFDE: 0x6398, //CJK UNIFIED IDEOGRAPH - 0xCFDF: 0x7A9F, //CJK UNIFIED IDEOGRAPH - 0xCFE0: 0x5BAE, //CJK UNIFIED IDEOGRAPH - 0xCFE1: 0x5F13, //CJK UNIFIED IDEOGRAPH - 0xCFE2: 0x7A79, //CJK UNIFIED IDEOGRAPH - 0xCFE3: 0x7AAE, //CJK UNIFIED IDEOGRAPH - 0xCFE4: 0x828E, //CJK UNIFIED IDEOGRAPH - 0xCFE5: 0x8EAC, //CJK UNIFIED IDEOGRAPH - 0xCFE6: 0x5026, //CJK UNIFIED IDEOGRAPH - 0xCFE7: 0x5238, //CJK UNIFIED IDEOGRAPH - 0xCFE8: 0x52F8, //CJK UNIFIED IDEOGRAPH - 0xCFE9: 0x5377, //CJK UNIFIED IDEOGRAPH - 0xCFEA: 0x5708, //CJK UNIFIED IDEOGRAPH - 0xCFEB: 0x62F3, //CJK UNIFIED IDEOGRAPH - 0xCFEC: 0x6372, //CJK UNIFIED IDEOGRAPH - 0xCFED: 0x6B0A, //CJK UNIFIED IDEOGRAPH - 0xCFEE: 0x6DC3, //CJK UNIFIED IDEOGRAPH - 0xCFEF: 0x7737, //CJK UNIFIED IDEOGRAPH - 0xCFF0: 0x53A5, //CJK UNIFIED IDEOGRAPH - 0xCFF1: 0x7357, //CJK UNIFIED IDEOGRAPH - 0xCFF2: 0x8568, //CJK UNIFIED IDEOGRAPH - 0xCFF3: 0x8E76, //CJK UNIFIED IDEOGRAPH - 0xCFF4: 0x95D5, //CJK UNIFIED IDEOGRAPH - 0xCFF5: 0x673A, //CJK UNIFIED IDEOGRAPH - 0xCFF6: 0x6AC3, //CJK UNIFIED IDEOGRAPH - 0xCFF7: 0x6F70, //CJK UNIFIED IDEOGRAPH - 0xCFF8: 0x8A6D, //CJK UNIFIED IDEOGRAPH - 0xCFF9: 0x8ECC, //CJK UNIFIED IDEOGRAPH - 0xCFFA: 0x994B, //CJK UNIFIED IDEOGRAPH - 0xCFFB: 0xF906, //CJK COMPATIBILITY IDEOGRAPH - 0xCFFC: 0x6677, //CJK UNIFIED IDEOGRAPH - 0xCFFD: 0x6B78, //CJK UNIFIED IDEOGRAPH - 0xCFFE: 0x8CB4, //CJK UNIFIED IDEOGRAPH - 0xD0A1: 0x9B3C, //CJK UNIFIED IDEOGRAPH - 0xD0A2: 0xF907, //CJK COMPATIBILITY IDEOGRAPH - 0xD0A3: 0x53EB, //CJK UNIFIED IDEOGRAPH - 0xD0A4: 0x572D, //CJK UNIFIED IDEOGRAPH - 0xD0A5: 0x594E, //CJK UNIFIED IDEOGRAPH - 0xD0A6: 0x63C6, //CJK UNIFIED IDEOGRAPH - 0xD0A7: 0x69FB, //CJK UNIFIED IDEOGRAPH - 0xD0A8: 0x73EA, //CJK UNIFIED IDEOGRAPH - 0xD0A9: 0x7845, //CJK UNIFIED IDEOGRAPH - 0xD0AA: 0x7ABA, //CJK UNIFIED IDEOGRAPH - 0xD0AB: 0x7AC5, //CJK UNIFIED IDEOGRAPH - 0xD0AC: 0x7CFE, //CJK UNIFIED IDEOGRAPH - 0xD0AD: 0x8475, //CJK UNIFIED IDEOGRAPH - 0xD0AE: 0x898F, //CJK UNIFIED IDEOGRAPH - 0xD0AF: 0x8D73, //CJK UNIFIED IDEOGRAPH - 0xD0B0: 0x9035, //CJK UNIFIED IDEOGRAPH - 0xD0B1: 0x95A8, //CJK UNIFIED IDEOGRAPH - 0xD0B2: 0x52FB, //CJK UNIFIED IDEOGRAPH - 0xD0B3: 0x5747, //CJK UNIFIED IDEOGRAPH - 0xD0B4: 0x7547, //CJK UNIFIED IDEOGRAPH - 0xD0B5: 0x7B60, //CJK UNIFIED IDEOGRAPH - 0xD0B6: 0x83CC, //CJK UNIFIED IDEOGRAPH - 0xD0B7: 0x921E, //CJK UNIFIED IDEOGRAPH - 0xD0B8: 0xF908, //CJK COMPATIBILITY IDEOGRAPH - 0xD0B9: 0x6A58, //CJK UNIFIED IDEOGRAPH - 0xD0BA: 0x514B, //CJK UNIFIED IDEOGRAPH - 0xD0BB: 0x524B, //CJK UNIFIED IDEOGRAPH - 0xD0BC: 0x5287, //CJK UNIFIED IDEOGRAPH - 0xD0BD: 0x621F, //CJK UNIFIED IDEOGRAPH - 0xD0BE: 0x68D8, //CJK UNIFIED IDEOGRAPH - 0xD0BF: 0x6975, //CJK UNIFIED IDEOGRAPH - 0xD0C0: 0x9699, //CJK UNIFIED IDEOGRAPH - 0xD0C1: 0x50C5, //CJK UNIFIED IDEOGRAPH - 0xD0C2: 0x52A4, //CJK UNIFIED IDEOGRAPH - 0xD0C3: 0x52E4, //CJK UNIFIED IDEOGRAPH - 0xD0C4: 0x61C3, //CJK UNIFIED IDEOGRAPH - 0xD0C5: 0x65A4, //CJK UNIFIED IDEOGRAPH - 0xD0C6: 0x6839, //CJK UNIFIED IDEOGRAPH - 0xD0C7: 0x69FF, //CJK UNIFIED IDEOGRAPH - 0xD0C8: 0x747E, //CJK UNIFIED IDEOGRAPH - 0xD0C9: 0x7B4B, //CJK UNIFIED IDEOGRAPH - 0xD0CA: 0x82B9, //CJK UNIFIED IDEOGRAPH - 0xD0CB: 0x83EB, //CJK UNIFIED IDEOGRAPH - 0xD0CC: 0x89B2, //CJK UNIFIED IDEOGRAPH - 0xD0CD: 0x8B39, //CJK UNIFIED IDEOGRAPH - 0xD0CE: 0x8FD1, //CJK UNIFIED IDEOGRAPH - 0xD0CF: 0x9949, //CJK UNIFIED IDEOGRAPH - 0xD0D0: 0xF909, //CJK COMPATIBILITY IDEOGRAPH - 0xD0D1: 0x4ECA, //CJK UNIFIED IDEOGRAPH - 0xD0D2: 0x5997, //CJK UNIFIED IDEOGRAPH - 0xD0D3: 0x64D2, //CJK UNIFIED IDEOGRAPH - 0xD0D4: 0x6611, //CJK UNIFIED IDEOGRAPH - 0xD0D5: 0x6A8E, //CJK UNIFIED IDEOGRAPH - 0xD0D6: 0x7434, //CJK UNIFIED IDEOGRAPH - 0xD0D7: 0x7981, //CJK UNIFIED IDEOGRAPH - 0xD0D8: 0x79BD, //CJK UNIFIED IDEOGRAPH - 0xD0D9: 0x82A9, //CJK UNIFIED IDEOGRAPH - 0xD0DA: 0x887E, //CJK UNIFIED IDEOGRAPH - 0xD0DB: 0x887F, //CJK UNIFIED IDEOGRAPH - 0xD0DC: 0x895F, //CJK UNIFIED IDEOGRAPH - 0xD0DD: 0xF90A, //CJK COMPATIBILITY IDEOGRAPH - 0xD0DE: 0x9326, //CJK UNIFIED IDEOGRAPH - 0xD0DF: 0x4F0B, //CJK UNIFIED IDEOGRAPH - 0xD0E0: 0x53CA, //CJK UNIFIED IDEOGRAPH - 0xD0E1: 0x6025, //CJK UNIFIED IDEOGRAPH - 0xD0E2: 0x6271, //CJK UNIFIED IDEOGRAPH - 0xD0E3: 0x6C72, //CJK UNIFIED IDEOGRAPH - 0xD0E4: 0x7D1A, //CJK UNIFIED IDEOGRAPH - 0xD0E5: 0x7D66, //CJK UNIFIED IDEOGRAPH - 0xD0E6: 0x4E98, //CJK UNIFIED IDEOGRAPH - 0xD0E7: 0x5162, //CJK UNIFIED IDEOGRAPH - 0xD0E8: 0x77DC, //CJK UNIFIED IDEOGRAPH - 0xD0E9: 0x80AF, //CJK UNIFIED IDEOGRAPH - 0xD0EA: 0x4F01, //CJK UNIFIED IDEOGRAPH - 0xD0EB: 0x4F0E, //CJK UNIFIED IDEOGRAPH - 0xD0EC: 0x5176, //CJK UNIFIED IDEOGRAPH - 0xD0ED: 0x5180, //CJK UNIFIED IDEOGRAPH - 0xD0EE: 0x55DC, //CJK UNIFIED IDEOGRAPH - 0xD0EF: 0x5668, //CJK UNIFIED IDEOGRAPH - 0xD0F0: 0x573B, //CJK UNIFIED IDEOGRAPH - 0xD0F1: 0x57FA, //CJK UNIFIED IDEOGRAPH - 0xD0F2: 0x57FC, //CJK UNIFIED IDEOGRAPH - 0xD0F3: 0x5914, //CJK UNIFIED IDEOGRAPH - 0xD0F4: 0x5947, //CJK UNIFIED IDEOGRAPH - 0xD0F5: 0x5993, //CJK UNIFIED IDEOGRAPH - 0xD0F6: 0x5BC4, //CJK UNIFIED IDEOGRAPH - 0xD0F7: 0x5C90, //CJK UNIFIED IDEOGRAPH - 0xD0F8: 0x5D0E, //CJK UNIFIED IDEOGRAPH - 0xD0F9: 0x5DF1, //CJK UNIFIED IDEOGRAPH - 0xD0FA: 0x5E7E, //CJK UNIFIED IDEOGRAPH - 0xD0FB: 0x5FCC, //CJK UNIFIED IDEOGRAPH - 0xD0FC: 0x6280, //CJK UNIFIED IDEOGRAPH - 0xD0FD: 0x65D7, //CJK UNIFIED IDEOGRAPH - 0xD0FE: 0x65E3, //CJK UNIFIED IDEOGRAPH - 0xD1A1: 0x671E, //CJK UNIFIED IDEOGRAPH - 0xD1A2: 0x671F, //CJK UNIFIED IDEOGRAPH - 0xD1A3: 0x675E, //CJK UNIFIED IDEOGRAPH - 0xD1A4: 0x68CB, //CJK UNIFIED IDEOGRAPH - 0xD1A5: 0x68C4, //CJK UNIFIED IDEOGRAPH - 0xD1A6: 0x6A5F, //CJK UNIFIED IDEOGRAPH - 0xD1A7: 0x6B3A, //CJK UNIFIED IDEOGRAPH - 0xD1A8: 0x6C23, //CJK UNIFIED IDEOGRAPH - 0xD1A9: 0x6C7D, //CJK UNIFIED IDEOGRAPH - 0xD1AA: 0x6C82, //CJK UNIFIED IDEOGRAPH - 0xD1AB: 0x6DC7, //CJK UNIFIED IDEOGRAPH - 0xD1AC: 0x7398, //CJK UNIFIED IDEOGRAPH - 0xD1AD: 0x7426, //CJK UNIFIED IDEOGRAPH - 0xD1AE: 0x742A, //CJK UNIFIED IDEOGRAPH - 0xD1AF: 0x7482, //CJK UNIFIED IDEOGRAPH - 0xD1B0: 0x74A3, //CJK UNIFIED IDEOGRAPH - 0xD1B1: 0x7578, //CJK UNIFIED IDEOGRAPH - 0xD1B2: 0x757F, //CJK UNIFIED IDEOGRAPH - 0xD1B3: 0x7881, //CJK UNIFIED IDEOGRAPH - 0xD1B4: 0x78EF, //CJK UNIFIED IDEOGRAPH - 0xD1B5: 0x7941, //CJK UNIFIED IDEOGRAPH - 0xD1B6: 0x7947, //CJK UNIFIED IDEOGRAPH - 0xD1B7: 0x7948, //CJK UNIFIED IDEOGRAPH - 0xD1B8: 0x797A, //CJK UNIFIED IDEOGRAPH - 0xD1B9: 0x7B95, //CJK UNIFIED IDEOGRAPH - 0xD1BA: 0x7D00, //CJK UNIFIED IDEOGRAPH - 0xD1BB: 0x7DBA, //CJK UNIFIED IDEOGRAPH - 0xD1BC: 0x7F88, //CJK UNIFIED IDEOGRAPH - 0xD1BD: 0x8006, //CJK UNIFIED IDEOGRAPH - 0xD1BE: 0x802D, //CJK UNIFIED IDEOGRAPH - 0xD1BF: 0x808C, //CJK UNIFIED IDEOGRAPH - 0xD1C0: 0x8A18, //CJK UNIFIED IDEOGRAPH - 0xD1C1: 0x8B4F, //CJK UNIFIED IDEOGRAPH - 0xD1C2: 0x8C48, //CJK UNIFIED IDEOGRAPH - 0xD1C3: 0x8D77, //CJK UNIFIED IDEOGRAPH - 0xD1C4: 0x9321, //CJK UNIFIED IDEOGRAPH - 0xD1C5: 0x9324, //CJK UNIFIED IDEOGRAPH - 0xD1C6: 0x98E2, //CJK UNIFIED IDEOGRAPH - 0xD1C7: 0x9951, //CJK UNIFIED IDEOGRAPH - 0xD1C8: 0x9A0E, //CJK UNIFIED IDEOGRAPH - 0xD1C9: 0x9A0F, //CJK UNIFIED IDEOGRAPH - 0xD1CA: 0x9A65, //CJK UNIFIED IDEOGRAPH - 0xD1CB: 0x9E92, //CJK UNIFIED IDEOGRAPH - 0xD1CC: 0x7DCA, //CJK UNIFIED IDEOGRAPH - 0xD1CD: 0x4F76, //CJK UNIFIED IDEOGRAPH - 0xD1CE: 0x5409, //CJK UNIFIED IDEOGRAPH - 0xD1CF: 0x62EE, //CJK UNIFIED IDEOGRAPH - 0xD1D0: 0x6854, //CJK UNIFIED IDEOGRAPH - 0xD1D1: 0x91D1, //CJK UNIFIED IDEOGRAPH - 0xD1D2: 0x55AB, //CJK UNIFIED IDEOGRAPH - 0xD1D3: 0x513A, //CJK UNIFIED IDEOGRAPH - 0xD1D4: 0xF90B, //CJK COMPATIBILITY IDEOGRAPH - 0xD1D5: 0xF90C, //CJK COMPATIBILITY IDEOGRAPH - 0xD1D6: 0x5A1C, //CJK UNIFIED IDEOGRAPH - 0xD1D7: 0x61E6, //CJK UNIFIED IDEOGRAPH - 0xD1D8: 0xF90D, //CJK COMPATIBILITY IDEOGRAPH - 0xD1D9: 0x62CF, //CJK UNIFIED IDEOGRAPH - 0xD1DA: 0x62FF, //CJK UNIFIED IDEOGRAPH - 0xD1DB: 0xF90E, //CJK COMPATIBILITY IDEOGRAPH - 0xD1DC: 0xF90F, //CJK COMPATIBILITY IDEOGRAPH - 0xD1DD: 0xF910, //CJK COMPATIBILITY IDEOGRAPH - 0xD1DE: 0xF911, //CJK COMPATIBILITY IDEOGRAPH - 0xD1DF: 0xF912, //CJK COMPATIBILITY IDEOGRAPH - 0xD1E0: 0xF913, //CJK COMPATIBILITY IDEOGRAPH - 0xD1E1: 0x90A3, //CJK UNIFIED IDEOGRAPH - 0xD1E2: 0xF914, //CJK COMPATIBILITY IDEOGRAPH - 0xD1E3: 0xF915, //CJK COMPATIBILITY IDEOGRAPH - 0xD1E4: 0xF916, //CJK COMPATIBILITY IDEOGRAPH - 0xD1E5: 0xF917, //CJK COMPATIBILITY IDEOGRAPH - 0xD1E6: 0xF918, //CJK COMPATIBILITY IDEOGRAPH - 0xD1E7: 0x8AFE, //CJK UNIFIED IDEOGRAPH - 0xD1E8: 0xF919, //CJK COMPATIBILITY IDEOGRAPH - 0xD1E9: 0xF91A, //CJK COMPATIBILITY IDEOGRAPH - 0xD1EA: 0xF91B, //CJK COMPATIBILITY IDEOGRAPH - 0xD1EB: 0xF91C, //CJK COMPATIBILITY IDEOGRAPH - 0xD1EC: 0x6696, //CJK UNIFIED IDEOGRAPH - 0xD1ED: 0xF91D, //CJK COMPATIBILITY IDEOGRAPH - 0xD1EE: 0x7156, //CJK UNIFIED IDEOGRAPH - 0xD1EF: 0xF91E, //CJK COMPATIBILITY IDEOGRAPH - 0xD1F0: 0xF91F, //CJK COMPATIBILITY IDEOGRAPH - 0xD1F1: 0x96E3, //CJK UNIFIED IDEOGRAPH - 0xD1F2: 0xF920, //CJK COMPATIBILITY IDEOGRAPH - 0xD1F3: 0x634F, //CJK UNIFIED IDEOGRAPH - 0xD1F4: 0x637A, //CJK UNIFIED IDEOGRAPH - 0xD1F5: 0x5357, //CJK UNIFIED IDEOGRAPH - 0xD1F6: 0xF921, //CJK COMPATIBILITY IDEOGRAPH - 0xD1F7: 0x678F, //CJK UNIFIED IDEOGRAPH - 0xD1F8: 0x6960, //CJK UNIFIED IDEOGRAPH - 0xD1F9: 0x6E73, //CJK UNIFIED IDEOGRAPH - 0xD1FA: 0xF922, //CJK COMPATIBILITY IDEOGRAPH - 0xD1FB: 0x7537, //CJK UNIFIED IDEOGRAPH - 0xD1FC: 0xF923, //CJK COMPATIBILITY IDEOGRAPH - 0xD1FD: 0xF924, //CJK COMPATIBILITY IDEOGRAPH - 0xD1FE: 0xF925, //CJK COMPATIBILITY IDEOGRAPH - 0xD2A1: 0x7D0D, //CJK UNIFIED IDEOGRAPH - 0xD2A2: 0xF926, //CJK COMPATIBILITY IDEOGRAPH - 0xD2A3: 0xF927, //CJK COMPATIBILITY IDEOGRAPH - 0xD2A4: 0x8872, //CJK UNIFIED IDEOGRAPH - 0xD2A5: 0x56CA, //CJK UNIFIED IDEOGRAPH - 0xD2A6: 0x5A18, //CJK UNIFIED IDEOGRAPH - 0xD2A7: 0xF928, //CJK COMPATIBILITY IDEOGRAPH - 0xD2A8: 0xF929, //CJK COMPATIBILITY IDEOGRAPH - 0xD2A9: 0xF92A, //CJK COMPATIBILITY IDEOGRAPH - 0xD2AA: 0xF92B, //CJK COMPATIBILITY IDEOGRAPH - 0xD2AB: 0xF92C, //CJK COMPATIBILITY IDEOGRAPH - 0xD2AC: 0x4E43, //CJK UNIFIED IDEOGRAPH - 0xD2AD: 0xF92D, //CJK COMPATIBILITY IDEOGRAPH - 0xD2AE: 0x5167, //CJK UNIFIED IDEOGRAPH - 0xD2AF: 0x5948, //CJK UNIFIED IDEOGRAPH - 0xD2B0: 0x67F0, //CJK UNIFIED IDEOGRAPH - 0xD2B1: 0x8010, //CJK UNIFIED IDEOGRAPH - 0xD2B2: 0xF92E, //CJK COMPATIBILITY IDEOGRAPH - 0xD2B3: 0x5973, //CJK UNIFIED IDEOGRAPH - 0xD2B4: 0x5E74, //CJK UNIFIED IDEOGRAPH - 0xD2B5: 0x649A, //CJK UNIFIED IDEOGRAPH - 0xD2B6: 0x79CA, //CJK UNIFIED IDEOGRAPH - 0xD2B7: 0x5FF5, //CJK UNIFIED IDEOGRAPH - 0xD2B8: 0x606C, //CJK UNIFIED IDEOGRAPH - 0xD2B9: 0x62C8, //CJK UNIFIED IDEOGRAPH - 0xD2BA: 0x637B, //CJK UNIFIED IDEOGRAPH - 0xD2BB: 0x5BE7, //CJK UNIFIED IDEOGRAPH - 0xD2BC: 0x5BD7, //CJK UNIFIED IDEOGRAPH - 0xD2BD: 0x52AA, //CJK UNIFIED IDEOGRAPH - 0xD2BE: 0xF92F, //CJK COMPATIBILITY IDEOGRAPH - 0xD2BF: 0x5974, //CJK UNIFIED IDEOGRAPH - 0xD2C0: 0x5F29, //CJK UNIFIED IDEOGRAPH - 0xD2C1: 0x6012, //CJK UNIFIED IDEOGRAPH - 0xD2C2: 0xF930, //CJK COMPATIBILITY IDEOGRAPH - 0xD2C3: 0xF931, //CJK COMPATIBILITY IDEOGRAPH - 0xD2C4: 0xF932, //CJK COMPATIBILITY IDEOGRAPH - 0xD2C5: 0x7459, //CJK UNIFIED IDEOGRAPH - 0xD2C6: 0xF933, //CJK COMPATIBILITY IDEOGRAPH - 0xD2C7: 0xF934, //CJK COMPATIBILITY IDEOGRAPH - 0xD2C8: 0xF935, //CJK COMPATIBILITY IDEOGRAPH - 0xD2C9: 0xF936, //CJK COMPATIBILITY IDEOGRAPH - 0xD2CA: 0xF937, //CJK COMPATIBILITY IDEOGRAPH - 0xD2CB: 0xF938, //CJK COMPATIBILITY IDEOGRAPH - 0xD2CC: 0x99D1, //CJK UNIFIED IDEOGRAPH - 0xD2CD: 0xF939, //CJK COMPATIBILITY IDEOGRAPH - 0xD2CE: 0xF93A, //CJK COMPATIBILITY IDEOGRAPH - 0xD2CF: 0xF93B, //CJK COMPATIBILITY IDEOGRAPH - 0xD2D0: 0xF93C, //CJK COMPATIBILITY IDEOGRAPH - 0xD2D1: 0xF93D, //CJK COMPATIBILITY IDEOGRAPH - 0xD2D2: 0xF93E, //CJK COMPATIBILITY IDEOGRAPH - 0xD2D3: 0xF93F, //CJK COMPATIBILITY IDEOGRAPH - 0xD2D4: 0xF940, //CJK COMPATIBILITY IDEOGRAPH - 0xD2D5: 0xF941, //CJK COMPATIBILITY IDEOGRAPH - 0xD2D6: 0xF942, //CJK COMPATIBILITY IDEOGRAPH - 0xD2D7: 0xF943, //CJK COMPATIBILITY IDEOGRAPH - 0xD2D8: 0x6FC3, //CJK UNIFIED IDEOGRAPH - 0xD2D9: 0xF944, //CJK COMPATIBILITY IDEOGRAPH - 0xD2DA: 0xF945, //CJK COMPATIBILITY IDEOGRAPH - 0xD2DB: 0x81BF, //CJK UNIFIED IDEOGRAPH - 0xD2DC: 0x8FB2, //CJK UNIFIED IDEOGRAPH - 0xD2DD: 0x60F1, //CJK UNIFIED IDEOGRAPH - 0xD2DE: 0xF946, //CJK COMPATIBILITY IDEOGRAPH - 0xD2DF: 0xF947, //CJK COMPATIBILITY IDEOGRAPH - 0xD2E0: 0x8166, //CJK UNIFIED IDEOGRAPH - 0xD2E1: 0xF948, //CJK COMPATIBILITY IDEOGRAPH - 0xD2E2: 0xF949, //CJK COMPATIBILITY IDEOGRAPH - 0xD2E3: 0x5C3F, //CJK UNIFIED IDEOGRAPH - 0xD2E4: 0xF94A, //CJK COMPATIBILITY IDEOGRAPH - 0xD2E5: 0xF94B, //CJK COMPATIBILITY IDEOGRAPH - 0xD2E6: 0xF94C, //CJK COMPATIBILITY IDEOGRAPH - 0xD2E7: 0xF94D, //CJK COMPATIBILITY IDEOGRAPH - 0xD2E8: 0xF94E, //CJK COMPATIBILITY IDEOGRAPH - 0xD2E9: 0xF94F, //CJK COMPATIBILITY IDEOGRAPH - 0xD2EA: 0xF950, //CJK COMPATIBILITY IDEOGRAPH - 0xD2EB: 0xF951, //CJK COMPATIBILITY IDEOGRAPH - 0xD2EC: 0x5AE9, //CJK UNIFIED IDEOGRAPH - 0xD2ED: 0x8A25, //CJK UNIFIED IDEOGRAPH - 0xD2EE: 0x677B, //CJK UNIFIED IDEOGRAPH - 0xD2EF: 0x7D10, //CJK UNIFIED IDEOGRAPH - 0xD2F0: 0xF952, //CJK COMPATIBILITY IDEOGRAPH - 0xD2F1: 0xF953, //CJK COMPATIBILITY IDEOGRAPH - 0xD2F2: 0xF954, //CJK COMPATIBILITY IDEOGRAPH - 0xD2F3: 0xF955, //CJK COMPATIBILITY IDEOGRAPH - 0xD2F4: 0xF956, //CJK COMPATIBILITY IDEOGRAPH - 0xD2F5: 0xF957, //CJK COMPATIBILITY IDEOGRAPH - 0xD2F6: 0x80FD, //CJK UNIFIED IDEOGRAPH - 0xD2F7: 0xF958, //CJK COMPATIBILITY IDEOGRAPH - 0xD2F8: 0xF959, //CJK COMPATIBILITY IDEOGRAPH - 0xD2F9: 0x5C3C, //CJK UNIFIED IDEOGRAPH - 0xD2FA: 0x6CE5, //CJK UNIFIED IDEOGRAPH - 0xD2FB: 0x533F, //CJK UNIFIED IDEOGRAPH - 0xD2FC: 0x6EBA, //CJK UNIFIED IDEOGRAPH - 0xD2FD: 0x591A, //CJK UNIFIED IDEOGRAPH - 0xD2FE: 0x8336, //CJK UNIFIED IDEOGRAPH - 0xD3A1: 0x4E39, //CJK UNIFIED IDEOGRAPH - 0xD3A2: 0x4EB6, //CJK UNIFIED IDEOGRAPH - 0xD3A3: 0x4F46, //CJK UNIFIED IDEOGRAPH - 0xD3A4: 0x55AE, //CJK UNIFIED IDEOGRAPH - 0xD3A5: 0x5718, //CJK UNIFIED IDEOGRAPH - 0xD3A6: 0x58C7, //CJK UNIFIED IDEOGRAPH - 0xD3A7: 0x5F56, //CJK UNIFIED IDEOGRAPH - 0xD3A8: 0x65B7, //CJK UNIFIED IDEOGRAPH - 0xD3A9: 0x65E6, //CJK UNIFIED IDEOGRAPH - 0xD3AA: 0x6A80, //CJK UNIFIED IDEOGRAPH - 0xD3AB: 0x6BB5, //CJK UNIFIED IDEOGRAPH - 0xD3AC: 0x6E4D, //CJK UNIFIED IDEOGRAPH - 0xD3AD: 0x77ED, //CJK UNIFIED IDEOGRAPH - 0xD3AE: 0x7AEF, //CJK UNIFIED IDEOGRAPH - 0xD3AF: 0x7C1E, //CJK UNIFIED IDEOGRAPH - 0xD3B0: 0x7DDE, //CJK UNIFIED IDEOGRAPH - 0xD3B1: 0x86CB, //CJK UNIFIED IDEOGRAPH - 0xD3B2: 0x8892, //CJK UNIFIED IDEOGRAPH - 0xD3B3: 0x9132, //CJK UNIFIED IDEOGRAPH - 0xD3B4: 0x935B, //CJK UNIFIED IDEOGRAPH - 0xD3B5: 0x64BB, //CJK UNIFIED IDEOGRAPH - 0xD3B6: 0x6FBE, //CJK UNIFIED IDEOGRAPH - 0xD3B7: 0x737A, //CJK UNIFIED IDEOGRAPH - 0xD3B8: 0x75B8, //CJK UNIFIED IDEOGRAPH - 0xD3B9: 0x9054, //CJK UNIFIED IDEOGRAPH - 0xD3BA: 0x5556, //CJK UNIFIED IDEOGRAPH - 0xD3BB: 0x574D, //CJK UNIFIED IDEOGRAPH - 0xD3BC: 0x61BA, //CJK UNIFIED IDEOGRAPH - 0xD3BD: 0x64D4, //CJK UNIFIED IDEOGRAPH - 0xD3BE: 0x66C7, //CJK UNIFIED IDEOGRAPH - 0xD3BF: 0x6DE1, //CJK UNIFIED IDEOGRAPH - 0xD3C0: 0x6E5B, //CJK UNIFIED IDEOGRAPH - 0xD3C1: 0x6F6D, //CJK UNIFIED IDEOGRAPH - 0xD3C2: 0x6FB9, //CJK UNIFIED IDEOGRAPH - 0xD3C3: 0x75F0, //CJK UNIFIED IDEOGRAPH - 0xD3C4: 0x8043, //CJK UNIFIED IDEOGRAPH - 0xD3C5: 0x81BD, //CJK UNIFIED IDEOGRAPH - 0xD3C6: 0x8541, //CJK UNIFIED IDEOGRAPH - 0xD3C7: 0x8983, //CJK UNIFIED IDEOGRAPH - 0xD3C8: 0x8AC7, //CJK UNIFIED IDEOGRAPH - 0xD3C9: 0x8B5A, //CJK UNIFIED IDEOGRAPH - 0xD3CA: 0x931F, //CJK UNIFIED IDEOGRAPH - 0xD3CB: 0x6C93, //CJK UNIFIED IDEOGRAPH - 0xD3CC: 0x7553, //CJK UNIFIED IDEOGRAPH - 0xD3CD: 0x7B54, //CJK UNIFIED IDEOGRAPH - 0xD3CE: 0x8E0F, //CJK UNIFIED IDEOGRAPH - 0xD3CF: 0x905D, //CJK UNIFIED IDEOGRAPH - 0xD3D0: 0x5510, //CJK UNIFIED IDEOGRAPH - 0xD3D1: 0x5802, //CJK UNIFIED IDEOGRAPH - 0xD3D2: 0x5858, //CJK UNIFIED IDEOGRAPH - 0xD3D3: 0x5E62, //CJK UNIFIED IDEOGRAPH - 0xD3D4: 0x6207, //CJK UNIFIED IDEOGRAPH - 0xD3D5: 0x649E, //CJK UNIFIED IDEOGRAPH - 0xD3D6: 0x68E0, //CJK UNIFIED IDEOGRAPH - 0xD3D7: 0x7576, //CJK UNIFIED IDEOGRAPH - 0xD3D8: 0x7CD6, //CJK UNIFIED IDEOGRAPH - 0xD3D9: 0x87B3, //CJK UNIFIED IDEOGRAPH - 0xD3DA: 0x9EE8, //CJK UNIFIED IDEOGRAPH - 0xD3DB: 0x4EE3, //CJK UNIFIED IDEOGRAPH - 0xD3DC: 0x5788, //CJK UNIFIED IDEOGRAPH - 0xD3DD: 0x576E, //CJK UNIFIED IDEOGRAPH - 0xD3DE: 0x5927, //CJK UNIFIED IDEOGRAPH - 0xD3DF: 0x5C0D, //CJK UNIFIED IDEOGRAPH - 0xD3E0: 0x5CB1, //CJK UNIFIED IDEOGRAPH - 0xD3E1: 0x5E36, //CJK UNIFIED IDEOGRAPH - 0xD3E2: 0x5F85, //CJK UNIFIED IDEOGRAPH - 0xD3E3: 0x6234, //CJK UNIFIED IDEOGRAPH - 0xD3E4: 0x64E1, //CJK UNIFIED IDEOGRAPH - 0xD3E5: 0x73B3, //CJK UNIFIED IDEOGRAPH - 0xD3E6: 0x81FA, //CJK UNIFIED IDEOGRAPH - 0xD3E7: 0x888B, //CJK UNIFIED IDEOGRAPH - 0xD3E8: 0x8CB8, //CJK UNIFIED IDEOGRAPH - 0xD3E9: 0x968A, //CJK UNIFIED IDEOGRAPH - 0xD3EA: 0x9EDB, //CJK UNIFIED IDEOGRAPH - 0xD3EB: 0x5B85, //CJK UNIFIED IDEOGRAPH - 0xD3EC: 0x5FB7, //CJK UNIFIED IDEOGRAPH - 0xD3ED: 0x60B3, //CJK UNIFIED IDEOGRAPH - 0xD3EE: 0x5012, //CJK UNIFIED IDEOGRAPH - 0xD3EF: 0x5200, //CJK UNIFIED IDEOGRAPH - 0xD3F0: 0x5230, //CJK UNIFIED IDEOGRAPH - 0xD3F1: 0x5716, //CJK UNIFIED IDEOGRAPH - 0xD3F2: 0x5835, //CJK UNIFIED IDEOGRAPH - 0xD3F3: 0x5857, //CJK UNIFIED IDEOGRAPH - 0xD3F4: 0x5C0E, //CJK UNIFIED IDEOGRAPH - 0xD3F5: 0x5C60, //CJK UNIFIED IDEOGRAPH - 0xD3F6: 0x5CF6, //CJK UNIFIED IDEOGRAPH - 0xD3F7: 0x5D8B, //CJK UNIFIED IDEOGRAPH - 0xD3F8: 0x5EA6, //CJK UNIFIED IDEOGRAPH - 0xD3F9: 0x5F92, //CJK UNIFIED IDEOGRAPH - 0xD3FA: 0x60BC, //CJK UNIFIED IDEOGRAPH - 0xD3FB: 0x6311, //CJK UNIFIED IDEOGRAPH - 0xD3FC: 0x6389, //CJK UNIFIED IDEOGRAPH - 0xD3FD: 0x6417, //CJK UNIFIED IDEOGRAPH - 0xD3FE: 0x6843, //CJK UNIFIED IDEOGRAPH - 0xD4A1: 0x68F9, //CJK UNIFIED IDEOGRAPH - 0xD4A2: 0x6AC2, //CJK UNIFIED IDEOGRAPH - 0xD4A3: 0x6DD8, //CJK UNIFIED IDEOGRAPH - 0xD4A4: 0x6E21, //CJK UNIFIED IDEOGRAPH - 0xD4A5: 0x6ED4, //CJK UNIFIED IDEOGRAPH - 0xD4A6: 0x6FE4, //CJK UNIFIED IDEOGRAPH - 0xD4A7: 0x71FE, //CJK UNIFIED IDEOGRAPH - 0xD4A8: 0x76DC, //CJK UNIFIED IDEOGRAPH - 0xD4A9: 0x7779, //CJK UNIFIED IDEOGRAPH - 0xD4AA: 0x79B1, //CJK UNIFIED IDEOGRAPH - 0xD4AB: 0x7A3B, //CJK UNIFIED IDEOGRAPH - 0xD4AC: 0x8404, //CJK UNIFIED IDEOGRAPH - 0xD4AD: 0x89A9, //CJK UNIFIED IDEOGRAPH - 0xD4AE: 0x8CED, //CJK UNIFIED IDEOGRAPH - 0xD4AF: 0x8DF3, //CJK UNIFIED IDEOGRAPH - 0xD4B0: 0x8E48, //CJK UNIFIED IDEOGRAPH - 0xD4B1: 0x9003, //CJK UNIFIED IDEOGRAPH - 0xD4B2: 0x9014, //CJK UNIFIED IDEOGRAPH - 0xD4B3: 0x9053, //CJK UNIFIED IDEOGRAPH - 0xD4B4: 0x90FD, //CJK UNIFIED IDEOGRAPH - 0xD4B5: 0x934D, //CJK UNIFIED IDEOGRAPH - 0xD4B6: 0x9676, //CJK UNIFIED IDEOGRAPH - 0xD4B7: 0x97DC, //CJK UNIFIED IDEOGRAPH - 0xD4B8: 0x6BD2, //CJK UNIFIED IDEOGRAPH - 0xD4B9: 0x7006, //CJK UNIFIED IDEOGRAPH - 0xD4BA: 0x7258, //CJK UNIFIED IDEOGRAPH - 0xD4BB: 0x72A2, //CJK UNIFIED IDEOGRAPH - 0xD4BC: 0x7368, //CJK UNIFIED IDEOGRAPH - 0xD4BD: 0x7763, //CJK UNIFIED IDEOGRAPH - 0xD4BE: 0x79BF, //CJK UNIFIED IDEOGRAPH - 0xD4BF: 0x7BE4, //CJK UNIFIED IDEOGRAPH - 0xD4C0: 0x7E9B, //CJK UNIFIED IDEOGRAPH - 0xD4C1: 0x8B80, //CJK UNIFIED IDEOGRAPH - 0xD4C2: 0x58A9, //CJK UNIFIED IDEOGRAPH - 0xD4C3: 0x60C7, //CJK UNIFIED IDEOGRAPH - 0xD4C4: 0x6566, //CJK UNIFIED IDEOGRAPH - 0xD4C5: 0x65FD, //CJK UNIFIED IDEOGRAPH - 0xD4C6: 0x66BE, //CJK UNIFIED IDEOGRAPH - 0xD4C7: 0x6C8C, //CJK UNIFIED IDEOGRAPH - 0xD4C8: 0x711E, //CJK UNIFIED IDEOGRAPH - 0xD4C9: 0x71C9, //CJK UNIFIED IDEOGRAPH - 0xD4CA: 0x8C5A, //CJK UNIFIED IDEOGRAPH - 0xD4CB: 0x9813, //CJK UNIFIED IDEOGRAPH - 0xD4CC: 0x4E6D, //CJK UNIFIED IDEOGRAPH - 0xD4CD: 0x7A81, //CJK UNIFIED IDEOGRAPH - 0xD4CE: 0x4EDD, //CJK UNIFIED IDEOGRAPH - 0xD4CF: 0x51AC, //CJK UNIFIED IDEOGRAPH - 0xD4D0: 0x51CD, //CJK UNIFIED IDEOGRAPH - 0xD4D1: 0x52D5, //CJK UNIFIED IDEOGRAPH - 0xD4D2: 0x540C, //CJK UNIFIED IDEOGRAPH - 0xD4D3: 0x61A7, //CJK UNIFIED IDEOGRAPH - 0xD4D4: 0x6771, //CJK UNIFIED IDEOGRAPH - 0xD4D5: 0x6850, //CJK UNIFIED IDEOGRAPH - 0xD4D6: 0x68DF, //CJK UNIFIED IDEOGRAPH - 0xD4D7: 0x6D1E, //CJK UNIFIED IDEOGRAPH - 0xD4D8: 0x6F7C, //CJK UNIFIED IDEOGRAPH - 0xD4D9: 0x75BC, //CJK UNIFIED IDEOGRAPH - 0xD4DA: 0x77B3, //CJK UNIFIED IDEOGRAPH - 0xD4DB: 0x7AE5, //CJK UNIFIED IDEOGRAPH - 0xD4DC: 0x80F4, //CJK UNIFIED IDEOGRAPH - 0xD4DD: 0x8463, //CJK UNIFIED IDEOGRAPH - 0xD4DE: 0x9285, //CJK UNIFIED IDEOGRAPH - 0xD4DF: 0x515C, //CJK UNIFIED IDEOGRAPH - 0xD4E0: 0x6597, //CJK UNIFIED IDEOGRAPH - 0xD4E1: 0x675C, //CJK UNIFIED IDEOGRAPH - 0xD4E2: 0x6793, //CJK UNIFIED IDEOGRAPH - 0xD4E3: 0x75D8, //CJK UNIFIED IDEOGRAPH - 0xD4E4: 0x7AC7, //CJK UNIFIED IDEOGRAPH - 0xD4E5: 0x8373, //CJK UNIFIED IDEOGRAPH - 0xD4E6: 0xF95A, //CJK COMPATIBILITY IDEOGRAPH - 0xD4E7: 0x8C46, //CJK UNIFIED IDEOGRAPH - 0xD4E8: 0x9017, //CJK UNIFIED IDEOGRAPH - 0xD4E9: 0x982D, //CJK UNIFIED IDEOGRAPH - 0xD4EA: 0x5C6F, //CJK UNIFIED IDEOGRAPH - 0xD4EB: 0x81C0, //CJK UNIFIED IDEOGRAPH - 0xD4EC: 0x829A, //CJK UNIFIED IDEOGRAPH - 0xD4ED: 0x9041, //CJK UNIFIED IDEOGRAPH - 0xD4EE: 0x906F, //CJK UNIFIED IDEOGRAPH - 0xD4EF: 0x920D, //CJK UNIFIED IDEOGRAPH - 0xD4F0: 0x5F97, //CJK UNIFIED IDEOGRAPH - 0xD4F1: 0x5D9D, //CJK UNIFIED IDEOGRAPH - 0xD4F2: 0x6A59, //CJK UNIFIED IDEOGRAPH - 0xD4F3: 0x71C8, //CJK UNIFIED IDEOGRAPH - 0xD4F4: 0x767B, //CJK UNIFIED IDEOGRAPH - 0xD4F5: 0x7B49, //CJK UNIFIED IDEOGRAPH - 0xD4F6: 0x85E4, //CJK UNIFIED IDEOGRAPH - 0xD4F7: 0x8B04, //CJK UNIFIED IDEOGRAPH - 0xD4F8: 0x9127, //CJK UNIFIED IDEOGRAPH - 0xD4F9: 0x9A30, //CJK UNIFIED IDEOGRAPH - 0xD4FA: 0x5587, //CJK UNIFIED IDEOGRAPH - 0xD4FB: 0x61F6, //CJK UNIFIED IDEOGRAPH - 0xD4FC: 0xF95B, //CJK COMPATIBILITY IDEOGRAPH - 0xD4FD: 0x7669, //CJK UNIFIED IDEOGRAPH - 0xD4FE: 0x7F85, //CJK UNIFIED IDEOGRAPH - 0xD5A1: 0x863F, //CJK UNIFIED IDEOGRAPH - 0xD5A2: 0x87BA, //CJK UNIFIED IDEOGRAPH - 0xD5A3: 0x88F8, //CJK UNIFIED IDEOGRAPH - 0xD5A4: 0x908F, //CJK UNIFIED IDEOGRAPH - 0xD5A5: 0xF95C, //CJK COMPATIBILITY IDEOGRAPH - 0xD5A6: 0x6D1B, //CJK UNIFIED IDEOGRAPH - 0xD5A7: 0x70D9, //CJK UNIFIED IDEOGRAPH - 0xD5A8: 0x73DE, //CJK UNIFIED IDEOGRAPH - 0xD5A9: 0x7D61, //CJK UNIFIED IDEOGRAPH - 0xD5AA: 0x843D, //CJK UNIFIED IDEOGRAPH - 0xD5AB: 0xF95D, //CJK COMPATIBILITY IDEOGRAPH - 0xD5AC: 0x916A, //CJK UNIFIED IDEOGRAPH - 0xD5AD: 0x99F1, //CJK UNIFIED IDEOGRAPH - 0xD5AE: 0xF95E, //CJK COMPATIBILITY IDEOGRAPH - 0xD5AF: 0x4E82, //CJK UNIFIED IDEOGRAPH - 0xD5B0: 0x5375, //CJK UNIFIED IDEOGRAPH - 0xD5B1: 0x6B04, //CJK UNIFIED IDEOGRAPH - 0xD5B2: 0x6B12, //CJK UNIFIED IDEOGRAPH - 0xD5B3: 0x703E, //CJK UNIFIED IDEOGRAPH - 0xD5B4: 0x721B, //CJK UNIFIED IDEOGRAPH - 0xD5B5: 0x862D, //CJK UNIFIED IDEOGRAPH - 0xD5B6: 0x9E1E, //CJK UNIFIED IDEOGRAPH - 0xD5B7: 0x524C, //CJK UNIFIED IDEOGRAPH - 0xD5B8: 0x8FA3, //CJK UNIFIED IDEOGRAPH - 0xD5B9: 0x5D50, //CJK UNIFIED IDEOGRAPH - 0xD5BA: 0x64E5, //CJK UNIFIED IDEOGRAPH - 0xD5BB: 0x652C, //CJK UNIFIED IDEOGRAPH - 0xD5BC: 0x6B16, //CJK UNIFIED IDEOGRAPH - 0xD5BD: 0x6FEB, //CJK UNIFIED IDEOGRAPH - 0xD5BE: 0x7C43, //CJK UNIFIED IDEOGRAPH - 0xD5BF: 0x7E9C, //CJK UNIFIED IDEOGRAPH - 0xD5C0: 0x85CD, //CJK UNIFIED IDEOGRAPH - 0xD5C1: 0x8964, //CJK UNIFIED IDEOGRAPH - 0xD5C2: 0x89BD, //CJK UNIFIED IDEOGRAPH - 0xD5C3: 0x62C9, //CJK UNIFIED IDEOGRAPH - 0xD5C4: 0x81D8, //CJK UNIFIED IDEOGRAPH - 0xD5C5: 0x881F, //CJK UNIFIED IDEOGRAPH - 0xD5C6: 0x5ECA, //CJK UNIFIED IDEOGRAPH - 0xD5C7: 0x6717, //CJK UNIFIED IDEOGRAPH - 0xD5C8: 0x6D6A, //CJK UNIFIED IDEOGRAPH - 0xD5C9: 0x72FC, //CJK UNIFIED IDEOGRAPH - 0xD5CA: 0x7405, //CJK UNIFIED IDEOGRAPH - 0xD5CB: 0x746F, //CJK UNIFIED IDEOGRAPH - 0xD5CC: 0x8782, //CJK UNIFIED IDEOGRAPH - 0xD5CD: 0x90DE, //CJK UNIFIED IDEOGRAPH - 0xD5CE: 0x4F86, //CJK UNIFIED IDEOGRAPH - 0xD5CF: 0x5D0D, //CJK UNIFIED IDEOGRAPH - 0xD5D0: 0x5FA0, //CJK UNIFIED IDEOGRAPH - 0xD5D1: 0x840A, //CJK UNIFIED IDEOGRAPH - 0xD5D2: 0x51B7, //CJK UNIFIED IDEOGRAPH - 0xD5D3: 0x63A0, //CJK UNIFIED IDEOGRAPH - 0xD5D4: 0x7565, //CJK UNIFIED IDEOGRAPH - 0xD5D5: 0x4EAE, //CJK UNIFIED IDEOGRAPH - 0xD5D6: 0x5006, //CJK UNIFIED IDEOGRAPH - 0xD5D7: 0x5169, //CJK UNIFIED IDEOGRAPH - 0xD5D8: 0x51C9, //CJK UNIFIED IDEOGRAPH - 0xD5D9: 0x6881, //CJK UNIFIED IDEOGRAPH - 0xD5DA: 0x6A11, //CJK UNIFIED IDEOGRAPH - 0xD5DB: 0x7CAE, //CJK UNIFIED IDEOGRAPH - 0xD5DC: 0x7CB1, //CJK UNIFIED IDEOGRAPH - 0xD5DD: 0x7CE7, //CJK UNIFIED IDEOGRAPH - 0xD5DE: 0x826F, //CJK UNIFIED IDEOGRAPH - 0xD5DF: 0x8AD2, //CJK UNIFIED IDEOGRAPH - 0xD5E0: 0x8F1B, //CJK UNIFIED IDEOGRAPH - 0xD5E1: 0x91CF, //CJK UNIFIED IDEOGRAPH - 0xD5E2: 0x4FB6, //CJK UNIFIED IDEOGRAPH - 0xD5E3: 0x5137, //CJK UNIFIED IDEOGRAPH - 0xD5E4: 0x52F5, //CJK UNIFIED IDEOGRAPH - 0xD5E5: 0x5442, //CJK UNIFIED IDEOGRAPH - 0xD5E6: 0x5EEC, //CJK UNIFIED IDEOGRAPH - 0xD5E7: 0x616E, //CJK UNIFIED IDEOGRAPH - 0xD5E8: 0x623E, //CJK UNIFIED IDEOGRAPH - 0xD5E9: 0x65C5, //CJK UNIFIED IDEOGRAPH - 0xD5EA: 0x6ADA, //CJK UNIFIED IDEOGRAPH - 0xD5EB: 0x6FFE, //CJK UNIFIED IDEOGRAPH - 0xD5EC: 0x792A, //CJK UNIFIED IDEOGRAPH - 0xD5ED: 0x85DC, //CJK UNIFIED IDEOGRAPH - 0xD5EE: 0x8823, //CJK UNIFIED IDEOGRAPH - 0xD5EF: 0x95AD, //CJK UNIFIED IDEOGRAPH - 0xD5F0: 0x9A62, //CJK UNIFIED IDEOGRAPH - 0xD5F1: 0x9A6A, //CJK UNIFIED IDEOGRAPH - 0xD5F2: 0x9E97, //CJK UNIFIED IDEOGRAPH - 0xD5F3: 0x9ECE, //CJK UNIFIED IDEOGRAPH - 0xD5F4: 0x529B, //CJK UNIFIED IDEOGRAPH - 0xD5F5: 0x66C6, //CJK UNIFIED IDEOGRAPH - 0xD5F6: 0x6B77, //CJK UNIFIED IDEOGRAPH - 0xD5F7: 0x701D, //CJK UNIFIED IDEOGRAPH - 0xD5F8: 0x792B, //CJK UNIFIED IDEOGRAPH - 0xD5F9: 0x8F62, //CJK UNIFIED IDEOGRAPH - 0xD5FA: 0x9742, //CJK UNIFIED IDEOGRAPH - 0xD5FB: 0x6190, //CJK UNIFIED IDEOGRAPH - 0xD5FC: 0x6200, //CJK UNIFIED IDEOGRAPH - 0xD5FD: 0x6523, //CJK UNIFIED IDEOGRAPH - 0xD5FE: 0x6F23, //CJK UNIFIED IDEOGRAPH - 0xD6A1: 0x7149, //CJK UNIFIED IDEOGRAPH - 0xD6A2: 0x7489, //CJK UNIFIED IDEOGRAPH - 0xD6A3: 0x7DF4, //CJK UNIFIED IDEOGRAPH - 0xD6A4: 0x806F, //CJK UNIFIED IDEOGRAPH - 0xD6A5: 0x84EE, //CJK UNIFIED IDEOGRAPH - 0xD6A6: 0x8F26, //CJK UNIFIED IDEOGRAPH - 0xD6A7: 0x9023, //CJK UNIFIED IDEOGRAPH - 0xD6A8: 0x934A, //CJK UNIFIED IDEOGRAPH - 0xD6A9: 0x51BD, //CJK UNIFIED IDEOGRAPH - 0xD6AA: 0x5217, //CJK UNIFIED IDEOGRAPH - 0xD6AB: 0x52A3, //CJK UNIFIED IDEOGRAPH - 0xD6AC: 0x6D0C, //CJK UNIFIED IDEOGRAPH - 0xD6AD: 0x70C8, //CJK UNIFIED IDEOGRAPH - 0xD6AE: 0x88C2, //CJK UNIFIED IDEOGRAPH - 0xD6AF: 0x5EC9, //CJK UNIFIED IDEOGRAPH - 0xD6B0: 0x6582, //CJK UNIFIED IDEOGRAPH - 0xD6B1: 0x6BAE, //CJK UNIFIED IDEOGRAPH - 0xD6B2: 0x6FC2, //CJK UNIFIED IDEOGRAPH - 0xD6B3: 0x7C3E, //CJK UNIFIED IDEOGRAPH - 0xD6B4: 0x7375, //CJK UNIFIED IDEOGRAPH - 0xD6B5: 0x4EE4, //CJK UNIFIED IDEOGRAPH - 0xD6B6: 0x4F36, //CJK UNIFIED IDEOGRAPH - 0xD6B7: 0x56F9, //CJK UNIFIED IDEOGRAPH - 0xD6B8: 0xF95F, //CJK COMPATIBILITY IDEOGRAPH - 0xD6B9: 0x5CBA, //CJK UNIFIED IDEOGRAPH - 0xD6BA: 0x5DBA, //CJK UNIFIED IDEOGRAPH - 0xD6BB: 0x601C, //CJK UNIFIED IDEOGRAPH - 0xD6BC: 0x73B2, //CJK UNIFIED IDEOGRAPH - 0xD6BD: 0x7B2D, //CJK UNIFIED IDEOGRAPH - 0xD6BE: 0x7F9A, //CJK UNIFIED IDEOGRAPH - 0xD6BF: 0x7FCE, //CJK UNIFIED IDEOGRAPH - 0xD6C0: 0x8046, //CJK UNIFIED IDEOGRAPH - 0xD6C1: 0x901E, //CJK UNIFIED IDEOGRAPH - 0xD6C2: 0x9234, //CJK UNIFIED IDEOGRAPH - 0xD6C3: 0x96F6, //CJK UNIFIED IDEOGRAPH - 0xD6C4: 0x9748, //CJK UNIFIED IDEOGRAPH - 0xD6C5: 0x9818, //CJK UNIFIED IDEOGRAPH - 0xD6C6: 0x9F61, //CJK UNIFIED IDEOGRAPH - 0xD6C7: 0x4F8B, //CJK UNIFIED IDEOGRAPH - 0xD6C8: 0x6FA7, //CJK UNIFIED IDEOGRAPH - 0xD6C9: 0x79AE, //CJK UNIFIED IDEOGRAPH - 0xD6CA: 0x91B4, //CJK UNIFIED IDEOGRAPH - 0xD6CB: 0x96B7, //CJK UNIFIED IDEOGRAPH - 0xD6CC: 0x52DE, //CJK UNIFIED IDEOGRAPH - 0xD6CD: 0xF960, //CJK COMPATIBILITY IDEOGRAPH - 0xD6CE: 0x6488, //CJK UNIFIED IDEOGRAPH - 0xD6CF: 0x64C4, //CJK UNIFIED IDEOGRAPH - 0xD6D0: 0x6AD3, //CJK UNIFIED IDEOGRAPH - 0xD6D1: 0x6F5E, //CJK UNIFIED IDEOGRAPH - 0xD6D2: 0x7018, //CJK UNIFIED IDEOGRAPH - 0xD6D3: 0x7210, //CJK UNIFIED IDEOGRAPH - 0xD6D4: 0x76E7, //CJK UNIFIED IDEOGRAPH - 0xD6D5: 0x8001, //CJK UNIFIED IDEOGRAPH - 0xD6D6: 0x8606, //CJK UNIFIED IDEOGRAPH - 0xD6D7: 0x865C, //CJK UNIFIED IDEOGRAPH - 0xD6D8: 0x8DEF, //CJK UNIFIED IDEOGRAPH - 0xD6D9: 0x8F05, //CJK UNIFIED IDEOGRAPH - 0xD6DA: 0x9732, //CJK UNIFIED IDEOGRAPH - 0xD6DB: 0x9B6F, //CJK UNIFIED IDEOGRAPH - 0xD6DC: 0x9DFA, //CJK UNIFIED IDEOGRAPH - 0xD6DD: 0x9E75, //CJK UNIFIED IDEOGRAPH - 0xD6DE: 0x788C, //CJK UNIFIED IDEOGRAPH - 0xD6DF: 0x797F, //CJK UNIFIED IDEOGRAPH - 0xD6E0: 0x7DA0, //CJK UNIFIED IDEOGRAPH - 0xD6E1: 0x83C9, //CJK UNIFIED IDEOGRAPH - 0xD6E2: 0x9304, //CJK UNIFIED IDEOGRAPH - 0xD6E3: 0x9E7F, //CJK UNIFIED IDEOGRAPH - 0xD6E4: 0x9E93, //CJK UNIFIED IDEOGRAPH - 0xD6E5: 0x8AD6, //CJK UNIFIED IDEOGRAPH - 0xD6E6: 0x58DF, //CJK UNIFIED IDEOGRAPH - 0xD6E7: 0x5F04, //CJK UNIFIED IDEOGRAPH - 0xD6E8: 0x6727, //CJK UNIFIED IDEOGRAPH - 0xD6E9: 0x7027, //CJK UNIFIED IDEOGRAPH - 0xD6EA: 0x74CF, //CJK UNIFIED IDEOGRAPH - 0xD6EB: 0x7C60, //CJK UNIFIED IDEOGRAPH - 0xD6EC: 0x807E, //CJK UNIFIED IDEOGRAPH - 0xD6ED: 0x5121, //CJK UNIFIED IDEOGRAPH - 0xD6EE: 0x7028, //CJK UNIFIED IDEOGRAPH - 0xD6EF: 0x7262, //CJK UNIFIED IDEOGRAPH - 0xD6F0: 0x78CA, //CJK UNIFIED IDEOGRAPH - 0xD6F1: 0x8CC2, //CJK UNIFIED IDEOGRAPH - 0xD6F2: 0x8CDA, //CJK UNIFIED IDEOGRAPH - 0xD6F3: 0x8CF4, //CJK UNIFIED IDEOGRAPH - 0xD6F4: 0x96F7, //CJK UNIFIED IDEOGRAPH - 0xD6F5: 0x4E86, //CJK UNIFIED IDEOGRAPH - 0xD6F6: 0x50DA, //CJK UNIFIED IDEOGRAPH - 0xD6F7: 0x5BEE, //CJK UNIFIED IDEOGRAPH - 0xD6F8: 0x5ED6, //CJK UNIFIED IDEOGRAPH - 0xD6F9: 0x6599, //CJK UNIFIED IDEOGRAPH - 0xD6FA: 0x71CE, //CJK UNIFIED IDEOGRAPH - 0xD6FB: 0x7642, //CJK UNIFIED IDEOGRAPH - 0xD6FC: 0x77AD, //CJK UNIFIED IDEOGRAPH - 0xD6FD: 0x804A, //CJK UNIFIED IDEOGRAPH - 0xD6FE: 0x84FC, //CJK UNIFIED IDEOGRAPH - 0xD7A1: 0x907C, //CJK UNIFIED IDEOGRAPH - 0xD7A2: 0x9B27, //CJK UNIFIED IDEOGRAPH - 0xD7A3: 0x9F8D, //CJK UNIFIED IDEOGRAPH - 0xD7A4: 0x58D8, //CJK UNIFIED IDEOGRAPH - 0xD7A5: 0x5A41, //CJK UNIFIED IDEOGRAPH - 0xD7A6: 0x5C62, //CJK UNIFIED IDEOGRAPH - 0xD7A7: 0x6A13, //CJK UNIFIED IDEOGRAPH - 0xD7A8: 0x6DDA, //CJK UNIFIED IDEOGRAPH - 0xD7A9: 0x6F0F, //CJK UNIFIED IDEOGRAPH - 0xD7AA: 0x763B, //CJK UNIFIED IDEOGRAPH - 0xD7AB: 0x7D2F, //CJK UNIFIED IDEOGRAPH - 0xD7AC: 0x7E37, //CJK UNIFIED IDEOGRAPH - 0xD7AD: 0x851E, //CJK UNIFIED IDEOGRAPH - 0xD7AE: 0x8938, //CJK UNIFIED IDEOGRAPH - 0xD7AF: 0x93E4, //CJK UNIFIED IDEOGRAPH - 0xD7B0: 0x964B, //CJK UNIFIED IDEOGRAPH - 0xD7B1: 0x5289, //CJK UNIFIED IDEOGRAPH - 0xD7B2: 0x65D2, //CJK UNIFIED IDEOGRAPH - 0xD7B3: 0x67F3, //CJK UNIFIED IDEOGRAPH - 0xD7B4: 0x69B4, //CJK UNIFIED IDEOGRAPH - 0xD7B5: 0x6D41, //CJK UNIFIED IDEOGRAPH - 0xD7B6: 0x6E9C, //CJK UNIFIED IDEOGRAPH - 0xD7B7: 0x700F, //CJK UNIFIED IDEOGRAPH - 0xD7B8: 0x7409, //CJK UNIFIED IDEOGRAPH - 0xD7B9: 0x7460, //CJK UNIFIED IDEOGRAPH - 0xD7BA: 0x7559, //CJK UNIFIED IDEOGRAPH - 0xD7BB: 0x7624, //CJK UNIFIED IDEOGRAPH - 0xD7BC: 0x786B, //CJK UNIFIED IDEOGRAPH - 0xD7BD: 0x8B2C, //CJK UNIFIED IDEOGRAPH - 0xD7BE: 0x985E, //CJK UNIFIED IDEOGRAPH - 0xD7BF: 0x516D, //CJK UNIFIED IDEOGRAPH - 0xD7C0: 0x622E, //CJK UNIFIED IDEOGRAPH - 0xD7C1: 0x9678, //CJK UNIFIED IDEOGRAPH - 0xD7C2: 0x4F96, //CJK UNIFIED IDEOGRAPH - 0xD7C3: 0x502B, //CJK UNIFIED IDEOGRAPH - 0xD7C4: 0x5D19, //CJK UNIFIED IDEOGRAPH - 0xD7C5: 0x6DEA, //CJK UNIFIED IDEOGRAPH - 0xD7C6: 0x7DB8, //CJK UNIFIED IDEOGRAPH - 0xD7C7: 0x8F2A, //CJK UNIFIED IDEOGRAPH - 0xD7C8: 0x5F8B, //CJK UNIFIED IDEOGRAPH - 0xD7C9: 0x6144, //CJK UNIFIED IDEOGRAPH - 0xD7CA: 0x6817, //CJK UNIFIED IDEOGRAPH - 0xD7CB: 0xF961, //CJK COMPATIBILITY IDEOGRAPH - 0xD7CC: 0x9686, //CJK UNIFIED IDEOGRAPH - 0xD7CD: 0x52D2, //CJK UNIFIED IDEOGRAPH - 0xD7CE: 0x808B, //CJK UNIFIED IDEOGRAPH - 0xD7CF: 0x51DC, //CJK UNIFIED IDEOGRAPH - 0xD7D0: 0x51CC, //CJK UNIFIED IDEOGRAPH - 0xD7D1: 0x695E, //CJK UNIFIED IDEOGRAPH - 0xD7D2: 0x7A1C, //CJK UNIFIED IDEOGRAPH - 0xD7D3: 0x7DBE, //CJK UNIFIED IDEOGRAPH - 0xD7D4: 0x83F1, //CJK UNIFIED IDEOGRAPH - 0xD7D5: 0x9675, //CJK UNIFIED IDEOGRAPH - 0xD7D6: 0x4FDA, //CJK UNIFIED IDEOGRAPH - 0xD7D7: 0x5229, //CJK UNIFIED IDEOGRAPH - 0xD7D8: 0x5398, //CJK UNIFIED IDEOGRAPH - 0xD7D9: 0x540F, //CJK UNIFIED IDEOGRAPH - 0xD7DA: 0x550E, //CJK UNIFIED IDEOGRAPH - 0xD7DB: 0x5C65, //CJK UNIFIED IDEOGRAPH - 0xD7DC: 0x60A7, //CJK UNIFIED IDEOGRAPH - 0xD7DD: 0x674E, //CJK UNIFIED IDEOGRAPH - 0xD7DE: 0x68A8, //CJK UNIFIED IDEOGRAPH - 0xD7DF: 0x6D6C, //CJK UNIFIED IDEOGRAPH - 0xD7E0: 0x7281, //CJK UNIFIED IDEOGRAPH - 0xD7E1: 0x72F8, //CJK UNIFIED IDEOGRAPH - 0xD7E2: 0x7406, //CJK UNIFIED IDEOGRAPH - 0xD7E3: 0x7483, //CJK UNIFIED IDEOGRAPH - 0xD7E4: 0xF962, //CJK COMPATIBILITY IDEOGRAPH - 0xD7E5: 0x75E2, //CJK UNIFIED IDEOGRAPH - 0xD7E6: 0x7C6C, //CJK UNIFIED IDEOGRAPH - 0xD7E7: 0x7F79, //CJK UNIFIED IDEOGRAPH - 0xD7E8: 0x7FB8, //CJK UNIFIED IDEOGRAPH - 0xD7E9: 0x8389, //CJK UNIFIED IDEOGRAPH - 0xD7EA: 0x88CF, //CJK UNIFIED IDEOGRAPH - 0xD7EB: 0x88E1, //CJK UNIFIED IDEOGRAPH - 0xD7EC: 0x91CC, //CJK UNIFIED IDEOGRAPH - 0xD7ED: 0x91D0, //CJK UNIFIED IDEOGRAPH - 0xD7EE: 0x96E2, //CJK UNIFIED IDEOGRAPH - 0xD7EF: 0x9BC9, //CJK UNIFIED IDEOGRAPH - 0xD7F0: 0x541D, //CJK UNIFIED IDEOGRAPH - 0xD7F1: 0x6F7E, //CJK UNIFIED IDEOGRAPH - 0xD7F2: 0x71D0, //CJK UNIFIED IDEOGRAPH - 0xD7F3: 0x7498, //CJK UNIFIED IDEOGRAPH - 0xD7F4: 0x85FA, //CJK UNIFIED IDEOGRAPH - 0xD7F5: 0x8EAA, //CJK UNIFIED IDEOGRAPH - 0xD7F6: 0x96A3, //CJK UNIFIED IDEOGRAPH - 0xD7F7: 0x9C57, //CJK UNIFIED IDEOGRAPH - 0xD7F8: 0x9E9F, //CJK UNIFIED IDEOGRAPH - 0xD7F9: 0x6797, //CJK UNIFIED IDEOGRAPH - 0xD7FA: 0x6DCB, //CJK UNIFIED IDEOGRAPH - 0xD7FB: 0x7433, //CJK UNIFIED IDEOGRAPH - 0xD7FC: 0x81E8, //CJK UNIFIED IDEOGRAPH - 0xD7FD: 0x9716, //CJK UNIFIED IDEOGRAPH - 0xD7FE: 0x782C, //CJK UNIFIED IDEOGRAPH - 0xD8A1: 0x7ACB, //CJK UNIFIED IDEOGRAPH - 0xD8A2: 0x7B20, //CJK UNIFIED IDEOGRAPH - 0xD8A3: 0x7C92, //CJK UNIFIED IDEOGRAPH - 0xD8A4: 0x6469, //CJK UNIFIED IDEOGRAPH - 0xD8A5: 0x746A, //CJK UNIFIED IDEOGRAPH - 0xD8A6: 0x75F2, //CJK UNIFIED IDEOGRAPH - 0xD8A7: 0x78BC, //CJK UNIFIED IDEOGRAPH - 0xD8A8: 0x78E8, //CJK UNIFIED IDEOGRAPH - 0xD8A9: 0x99AC, //CJK UNIFIED IDEOGRAPH - 0xD8AA: 0x9B54, //CJK UNIFIED IDEOGRAPH - 0xD8AB: 0x9EBB, //CJK UNIFIED IDEOGRAPH - 0xD8AC: 0x5BDE, //CJK UNIFIED IDEOGRAPH - 0xD8AD: 0x5E55, //CJK UNIFIED IDEOGRAPH - 0xD8AE: 0x6F20, //CJK UNIFIED IDEOGRAPH - 0xD8AF: 0x819C, //CJK UNIFIED IDEOGRAPH - 0xD8B0: 0x83AB, //CJK UNIFIED IDEOGRAPH - 0xD8B1: 0x9088, //CJK UNIFIED IDEOGRAPH - 0xD8B2: 0x4E07, //CJK UNIFIED IDEOGRAPH - 0xD8B3: 0x534D, //CJK UNIFIED IDEOGRAPH - 0xD8B4: 0x5A29, //CJK UNIFIED IDEOGRAPH - 0xD8B5: 0x5DD2, //CJK UNIFIED IDEOGRAPH - 0xD8B6: 0x5F4E, //CJK UNIFIED IDEOGRAPH - 0xD8B7: 0x6162, //CJK UNIFIED IDEOGRAPH - 0xD8B8: 0x633D, //CJK UNIFIED IDEOGRAPH - 0xD8B9: 0x6669, //CJK UNIFIED IDEOGRAPH - 0xD8BA: 0x66FC, //CJK UNIFIED IDEOGRAPH - 0xD8BB: 0x6EFF, //CJK UNIFIED IDEOGRAPH - 0xD8BC: 0x6F2B, //CJK UNIFIED IDEOGRAPH - 0xD8BD: 0x7063, //CJK UNIFIED IDEOGRAPH - 0xD8BE: 0x779E, //CJK UNIFIED IDEOGRAPH - 0xD8BF: 0x842C, //CJK UNIFIED IDEOGRAPH - 0xD8C0: 0x8513, //CJK UNIFIED IDEOGRAPH - 0xD8C1: 0x883B, //CJK UNIFIED IDEOGRAPH - 0xD8C2: 0x8F13, //CJK UNIFIED IDEOGRAPH - 0xD8C3: 0x9945, //CJK UNIFIED IDEOGRAPH - 0xD8C4: 0x9C3B, //CJK UNIFIED IDEOGRAPH - 0xD8C5: 0x551C, //CJK UNIFIED IDEOGRAPH - 0xD8C6: 0x62B9, //CJK UNIFIED IDEOGRAPH - 0xD8C7: 0x672B, //CJK UNIFIED IDEOGRAPH - 0xD8C8: 0x6CAB, //CJK UNIFIED IDEOGRAPH - 0xD8C9: 0x8309, //CJK UNIFIED IDEOGRAPH - 0xD8CA: 0x896A, //CJK UNIFIED IDEOGRAPH - 0xD8CB: 0x977A, //CJK UNIFIED IDEOGRAPH - 0xD8CC: 0x4EA1, //CJK UNIFIED IDEOGRAPH - 0xD8CD: 0x5984, //CJK UNIFIED IDEOGRAPH - 0xD8CE: 0x5FD8, //CJK UNIFIED IDEOGRAPH - 0xD8CF: 0x5FD9, //CJK UNIFIED IDEOGRAPH - 0xD8D0: 0x671B, //CJK UNIFIED IDEOGRAPH - 0xD8D1: 0x7DB2, //CJK UNIFIED IDEOGRAPH - 0xD8D2: 0x7F54, //CJK UNIFIED IDEOGRAPH - 0xD8D3: 0x8292, //CJK UNIFIED IDEOGRAPH - 0xD8D4: 0x832B, //CJK UNIFIED IDEOGRAPH - 0xD8D5: 0x83BD, //CJK UNIFIED IDEOGRAPH - 0xD8D6: 0x8F1E, //CJK UNIFIED IDEOGRAPH - 0xD8D7: 0x9099, //CJK UNIFIED IDEOGRAPH - 0xD8D8: 0x57CB, //CJK UNIFIED IDEOGRAPH - 0xD8D9: 0x59B9, //CJK UNIFIED IDEOGRAPH - 0xD8DA: 0x5A92, //CJK UNIFIED IDEOGRAPH - 0xD8DB: 0x5BD0, //CJK UNIFIED IDEOGRAPH - 0xD8DC: 0x6627, //CJK UNIFIED IDEOGRAPH - 0xD8DD: 0x679A, //CJK UNIFIED IDEOGRAPH - 0xD8DE: 0x6885, //CJK UNIFIED IDEOGRAPH - 0xD8DF: 0x6BCF, //CJK UNIFIED IDEOGRAPH - 0xD8E0: 0x7164, //CJK UNIFIED IDEOGRAPH - 0xD8E1: 0x7F75, //CJK UNIFIED IDEOGRAPH - 0xD8E2: 0x8CB7, //CJK UNIFIED IDEOGRAPH - 0xD8E3: 0x8CE3, //CJK UNIFIED IDEOGRAPH - 0xD8E4: 0x9081, //CJK UNIFIED IDEOGRAPH - 0xD8E5: 0x9B45, //CJK UNIFIED IDEOGRAPH - 0xD8E6: 0x8108, //CJK UNIFIED IDEOGRAPH - 0xD8E7: 0x8C8A, //CJK UNIFIED IDEOGRAPH - 0xD8E8: 0x964C, //CJK UNIFIED IDEOGRAPH - 0xD8E9: 0x9A40, //CJK UNIFIED IDEOGRAPH - 0xD8EA: 0x9EA5, //CJK UNIFIED IDEOGRAPH - 0xD8EB: 0x5B5F, //CJK UNIFIED IDEOGRAPH - 0xD8EC: 0x6C13, //CJK UNIFIED IDEOGRAPH - 0xD8ED: 0x731B, //CJK UNIFIED IDEOGRAPH - 0xD8EE: 0x76F2, //CJK UNIFIED IDEOGRAPH - 0xD8EF: 0x76DF, //CJK UNIFIED IDEOGRAPH - 0xD8F0: 0x840C, //CJK UNIFIED IDEOGRAPH - 0xD8F1: 0x51AA, //CJK UNIFIED IDEOGRAPH - 0xD8F2: 0x8993, //CJK UNIFIED IDEOGRAPH - 0xD8F3: 0x514D, //CJK UNIFIED IDEOGRAPH - 0xD8F4: 0x5195, //CJK UNIFIED IDEOGRAPH - 0xD8F5: 0x52C9, //CJK UNIFIED IDEOGRAPH - 0xD8F6: 0x68C9, //CJK UNIFIED IDEOGRAPH - 0xD8F7: 0x6C94, //CJK UNIFIED IDEOGRAPH - 0xD8F8: 0x7704, //CJK UNIFIED IDEOGRAPH - 0xD8F9: 0x7720, //CJK UNIFIED IDEOGRAPH - 0xD8FA: 0x7DBF, //CJK UNIFIED IDEOGRAPH - 0xD8FB: 0x7DEC, //CJK UNIFIED IDEOGRAPH - 0xD8FC: 0x9762, //CJK UNIFIED IDEOGRAPH - 0xD8FD: 0x9EB5, //CJK UNIFIED IDEOGRAPH - 0xD8FE: 0x6EC5, //CJK UNIFIED IDEOGRAPH - 0xD9A1: 0x8511, //CJK UNIFIED IDEOGRAPH - 0xD9A2: 0x51A5, //CJK UNIFIED IDEOGRAPH - 0xD9A3: 0x540D, //CJK UNIFIED IDEOGRAPH - 0xD9A4: 0x547D, //CJK UNIFIED IDEOGRAPH - 0xD9A5: 0x660E, //CJK UNIFIED IDEOGRAPH - 0xD9A6: 0x669D, //CJK UNIFIED IDEOGRAPH - 0xD9A7: 0x6927, //CJK UNIFIED IDEOGRAPH - 0xD9A8: 0x6E9F, //CJK UNIFIED IDEOGRAPH - 0xD9A9: 0x76BF, //CJK UNIFIED IDEOGRAPH - 0xD9AA: 0x7791, //CJK UNIFIED IDEOGRAPH - 0xD9AB: 0x8317, //CJK UNIFIED IDEOGRAPH - 0xD9AC: 0x84C2, //CJK UNIFIED IDEOGRAPH - 0xD9AD: 0x879F, //CJK UNIFIED IDEOGRAPH - 0xD9AE: 0x9169, //CJK UNIFIED IDEOGRAPH - 0xD9AF: 0x9298, //CJK UNIFIED IDEOGRAPH - 0xD9B0: 0x9CF4, //CJK UNIFIED IDEOGRAPH - 0xD9B1: 0x8882, //CJK UNIFIED IDEOGRAPH - 0xD9B2: 0x4FAE, //CJK UNIFIED IDEOGRAPH - 0xD9B3: 0x5192, //CJK UNIFIED IDEOGRAPH - 0xD9B4: 0x52DF, //CJK UNIFIED IDEOGRAPH - 0xD9B5: 0x59C6, //CJK UNIFIED IDEOGRAPH - 0xD9B6: 0x5E3D, //CJK UNIFIED IDEOGRAPH - 0xD9B7: 0x6155, //CJK UNIFIED IDEOGRAPH - 0xD9B8: 0x6478, //CJK UNIFIED IDEOGRAPH - 0xD9B9: 0x6479, //CJK UNIFIED IDEOGRAPH - 0xD9BA: 0x66AE, //CJK UNIFIED IDEOGRAPH - 0xD9BB: 0x67D0, //CJK UNIFIED IDEOGRAPH - 0xD9BC: 0x6A21, //CJK UNIFIED IDEOGRAPH - 0xD9BD: 0x6BCD, //CJK UNIFIED IDEOGRAPH - 0xD9BE: 0x6BDB, //CJK UNIFIED IDEOGRAPH - 0xD9BF: 0x725F, //CJK UNIFIED IDEOGRAPH - 0xD9C0: 0x7261, //CJK UNIFIED IDEOGRAPH - 0xD9C1: 0x7441, //CJK UNIFIED IDEOGRAPH - 0xD9C2: 0x7738, //CJK UNIFIED IDEOGRAPH - 0xD9C3: 0x77DB, //CJK UNIFIED IDEOGRAPH - 0xD9C4: 0x8017, //CJK UNIFIED IDEOGRAPH - 0xD9C5: 0x82BC, //CJK UNIFIED IDEOGRAPH - 0xD9C6: 0x8305, //CJK UNIFIED IDEOGRAPH - 0xD9C7: 0x8B00, //CJK UNIFIED IDEOGRAPH - 0xD9C8: 0x8B28, //CJK UNIFIED IDEOGRAPH - 0xD9C9: 0x8C8C, //CJK UNIFIED IDEOGRAPH - 0xD9CA: 0x6728, //CJK UNIFIED IDEOGRAPH - 0xD9CB: 0x6C90, //CJK UNIFIED IDEOGRAPH - 0xD9CC: 0x7267, //CJK UNIFIED IDEOGRAPH - 0xD9CD: 0x76EE, //CJK UNIFIED IDEOGRAPH - 0xD9CE: 0x7766, //CJK UNIFIED IDEOGRAPH - 0xD9CF: 0x7A46, //CJK UNIFIED IDEOGRAPH - 0xD9D0: 0x9DA9, //CJK UNIFIED IDEOGRAPH - 0xD9D1: 0x6B7F, //CJK UNIFIED IDEOGRAPH - 0xD9D2: 0x6C92, //CJK UNIFIED IDEOGRAPH - 0xD9D3: 0x5922, //CJK UNIFIED IDEOGRAPH - 0xD9D4: 0x6726, //CJK UNIFIED IDEOGRAPH - 0xD9D5: 0x8499, //CJK UNIFIED IDEOGRAPH - 0xD9D6: 0x536F, //CJK UNIFIED IDEOGRAPH - 0xD9D7: 0x5893, //CJK UNIFIED IDEOGRAPH - 0xD9D8: 0x5999, //CJK UNIFIED IDEOGRAPH - 0xD9D9: 0x5EDF, //CJK UNIFIED IDEOGRAPH - 0xD9DA: 0x63CF, //CJK UNIFIED IDEOGRAPH - 0xD9DB: 0x6634, //CJK UNIFIED IDEOGRAPH - 0xD9DC: 0x6773, //CJK UNIFIED IDEOGRAPH - 0xD9DD: 0x6E3A, //CJK UNIFIED IDEOGRAPH - 0xD9DE: 0x732B, //CJK UNIFIED IDEOGRAPH - 0xD9DF: 0x7AD7, //CJK UNIFIED IDEOGRAPH - 0xD9E0: 0x82D7, //CJK UNIFIED IDEOGRAPH - 0xD9E1: 0x9328, //CJK UNIFIED IDEOGRAPH - 0xD9E2: 0x52D9, //CJK UNIFIED IDEOGRAPH - 0xD9E3: 0x5DEB, //CJK UNIFIED IDEOGRAPH - 0xD9E4: 0x61AE, //CJK UNIFIED IDEOGRAPH - 0xD9E5: 0x61CB, //CJK UNIFIED IDEOGRAPH - 0xD9E6: 0x620A, //CJK UNIFIED IDEOGRAPH - 0xD9E7: 0x62C7, //CJK UNIFIED IDEOGRAPH - 0xD9E8: 0x64AB, //CJK UNIFIED IDEOGRAPH - 0xD9E9: 0x65E0, //CJK UNIFIED IDEOGRAPH - 0xD9EA: 0x6959, //CJK UNIFIED IDEOGRAPH - 0xD9EB: 0x6B66, //CJK UNIFIED IDEOGRAPH - 0xD9EC: 0x6BCB, //CJK UNIFIED IDEOGRAPH - 0xD9ED: 0x7121, //CJK UNIFIED IDEOGRAPH - 0xD9EE: 0x73F7, //CJK UNIFIED IDEOGRAPH - 0xD9EF: 0x755D, //CJK UNIFIED IDEOGRAPH - 0xD9F0: 0x7E46, //CJK UNIFIED IDEOGRAPH - 0xD9F1: 0x821E, //CJK UNIFIED IDEOGRAPH - 0xD9F2: 0x8302, //CJK UNIFIED IDEOGRAPH - 0xD9F3: 0x856A, //CJK UNIFIED IDEOGRAPH - 0xD9F4: 0x8AA3, //CJK UNIFIED IDEOGRAPH - 0xD9F5: 0x8CBF, //CJK UNIFIED IDEOGRAPH - 0xD9F6: 0x9727, //CJK UNIFIED IDEOGRAPH - 0xD9F7: 0x9D61, //CJK UNIFIED IDEOGRAPH - 0xD9F8: 0x58A8, //CJK UNIFIED IDEOGRAPH - 0xD9F9: 0x9ED8, //CJK UNIFIED IDEOGRAPH - 0xD9FA: 0x5011, //CJK UNIFIED IDEOGRAPH - 0xD9FB: 0x520E, //CJK UNIFIED IDEOGRAPH - 0xD9FC: 0x543B, //CJK UNIFIED IDEOGRAPH - 0xD9FD: 0x554F, //CJK UNIFIED IDEOGRAPH - 0xD9FE: 0x6587, //CJK UNIFIED IDEOGRAPH - 0xDAA1: 0x6C76, //CJK UNIFIED IDEOGRAPH - 0xDAA2: 0x7D0A, //CJK UNIFIED IDEOGRAPH - 0xDAA3: 0x7D0B, //CJK UNIFIED IDEOGRAPH - 0xDAA4: 0x805E, //CJK UNIFIED IDEOGRAPH - 0xDAA5: 0x868A, //CJK UNIFIED IDEOGRAPH - 0xDAA6: 0x9580, //CJK UNIFIED IDEOGRAPH - 0xDAA7: 0x96EF, //CJK UNIFIED IDEOGRAPH - 0xDAA8: 0x52FF, //CJK UNIFIED IDEOGRAPH - 0xDAA9: 0x6C95, //CJK UNIFIED IDEOGRAPH - 0xDAAA: 0x7269, //CJK UNIFIED IDEOGRAPH - 0xDAAB: 0x5473, //CJK UNIFIED IDEOGRAPH - 0xDAAC: 0x5A9A, //CJK UNIFIED IDEOGRAPH - 0xDAAD: 0x5C3E, //CJK UNIFIED IDEOGRAPH - 0xDAAE: 0x5D4B, //CJK UNIFIED IDEOGRAPH - 0xDAAF: 0x5F4C, //CJK UNIFIED IDEOGRAPH - 0xDAB0: 0x5FAE, //CJK UNIFIED IDEOGRAPH - 0xDAB1: 0x672A, //CJK UNIFIED IDEOGRAPH - 0xDAB2: 0x68B6, //CJK UNIFIED IDEOGRAPH - 0xDAB3: 0x6963, //CJK UNIFIED IDEOGRAPH - 0xDAB4: 0x6E3C, //CJK UNIFIED IDEOGRAPH - 0xDAB5: 0x6E44, //CJK UNIFIED IDEOGRAPH - 0xDAB6: 0x7709, //CJK UNIFIED IDEOGRAPH - 0xDAB7: 0x7C73, //CJK UNIFIED IDEOGRAPH - 0xDAB8: 0x7F8E, //CJK UNIFIED IDEOGRAPH - 0xDAB9: 0x8587, //CJK UNIFIED IDEOGRAPH - 0xDABA: 0x8B0E, //CJK UNIFIED IDEOGRAPH - 0xDABB: 0x8FF7, //CJK UNIFIED IDEOGRAPH - 0xDABC: 0x9761, //CJK UNIFIED IDEOGRAPH - 0xDABD: 0x9EF4, //CJK UNIFIED IDEOGRAPH - 0xDABE: 0x5CB7, //CJK UNIFIED IDEOGRAPH - 0xDABF: 0x60B6, //CJK UNIFIED IDEOGRAPH - 0xDAC0: 0x610D, //CJK UNIFIED IDEOGRAPH - 0xDAC1: 0x61AB, //CJK UNIFIED IDEOGRAPH - 0xDAC2: 0x654F, //CJK UNIFIED IDEOGRAPH - 0xDAC3: 0x65FB, //CJK UNIFIED IDEOGRAPH - 0xDAC4: 0x65FC, //CJK UNIFIED IDEOGRAPH - 0xDAC5: 0x6C11, //CJK UNIFIED IDEOGRAPH - 0xDAC6: 0x6CEF, //CJK UNIFIED IDEOGRAPH - 0xDAC7: 0x739F, //CJK UNIFIED IDEOGRAPH - 0xDAC8: 0x73C9, //CJK UNIFIED IDEOGRAPH - 0xDAC9: 0x7DE1, //CJK UNIFIED IDEOGRAPH - 0xDACA: 0x9594, //CJK UNIFIED IDEOGRAPH - 0xDACB: 0x5BC6, //CJK UNIFIED IDEOGRAPH - 0xDACC: 0x871C, //CJK UNIFIED IDEOGRAPH - 0xDACD: 0x8B10, //CJK UNIFIED IDEOGRAPH - 0xDACE: 0x525D, //CJK UNIFIED IDEOGRAPH - 0xDACF: 0x535A, //CJK UNIFIED IDEOGRAPH - 0xDAD0: 0x62CD, //CJK UNIFIED IDEOGRAPH - 0xDAD1: 0x640F, //CJK UNIFIED IDEOGRAPH - 0xDAD2: 0x64B2, //CJK UNIFIED IDEOGRAPH - 0xDAD3: 0x6734, //CJK UNIFIED IDEOGRAPH - 0xDAD4: 0x6A38, //CJK UNIFIED IDEOGRAPH - 0xDAD5: 0x6CCA, //CJK UNIFIED IDEOGRAPH - 0xDAD6: 0x73C0, //CJK UNIFIED IDEOGRAPH - 0xDAD7: 0x749E, //CJK UNIFIED IDEOGRAPH - 0xDAD8: 0x7B94, //CJK UNIFIED IDEOGRAPH - 0xDAD9: 0x7C95, //CJK UNIFIED IDEOGRAPH - 0xDADA: 0x7E1B, //CJK UNIFIED IDEOGRAPH - 0xDADB: 0x818A, //CJK UNIFIED IDEOGRAPH - 0xDADC: 0x8236, //CJK UNIFIED IDEOGRAPH - 0xDADD: 0x8584, //CJK UNIFIED IDEOGRAPH - 0xDADE: 0x8FEB, //CJK UNIFIED IDEOGRAPH - 0xDADF: 0x96F9, //CJK UNIFIED IDEOGRAPH - 0xDAE0: 0x99C1, //CJK UNIFIED IDEOGRAPH - 0xDAE1: 0x4F34, //CJK UNIFIED IDEOGRAPH - 0xDAE2: 0x534A, //CJK UNIFIED IDEOGRAPH - 0xDAE3: 0x53CD, //CJK UNIFIED IDEOGRAPH - 0xDAE4: 0x53DB, //CJK UNIFIED IDEOGRAPH - 0xDAE5: 0x62CC, //CJK UNIFIED IDEOGRAPH - 0xDAE6: 0x642C, //CJK UNIFIED IDEOGRAPH - 0xDAE7: 0x6500, //CJK UNIFIED IDEOGRAPH - 0xDAE8: 0x6591, //CJK UNIFIED IDEOGRAPH - 0xDAE9: 0x69C3, //CJK UNIFIED IDEOGRAPH - 0xDAEA: 0x6CEE, //CJK UNIFIED IDEOGRAPH - 0xDAEB: 0x6F58, //CJK UNIFIED IDEOGRAPH - 0xDAEC: 0x73ED, //CJK UNIFIED IDEOGRAPH - 0xDAED: 0x7554, //CJK UNIFIED IDEOGRAPH - 0xDAEE: 0x7622, //CJK UNIFIED IDEOGRAPH - 0xDAEF: 0x76E4, //CJK UNIFIED IDEOGRAPH - 0xDAF0: 0x76FC, //CJK UNIFIED IDEOGRAPH - 0xDAF1: 0x78D0, //CJK UNIFIED IDEOGRAPH - 0xDAF2: 0x78FB, //CJK UNIFIED IDEOGRAPH - 0xDAF3: 0x792C, //CJK UNIFIED IDEOGRAPH - 0xDAF4: 0x7D46, //CJK UNIFIED IDEOGRAPH - 0xDAF5: 0x822C, //CJK UNIFIED IDEOGRAPH - 0xDAF6: 0x87E0, //CJK UNIFIED IDEOGRAPH - 0xDAF7: 0x8FD4, //CJK UNIFIED IDEOGRAPH - 0xDAF8: 0x9812, //CJK UNIFIED IDEOGRAPH - 0xDAF9: 0x98EF, //CJK UNIFIED IDEOGRAPH - 0xDAFA: 0x52C3, //CJK UNIFIED IDEOGRAPH - 0xDAFB: 0x62D4, //CJK UNIFIED IDEOGRAPH - 0xDAFC: 0x64A5, //CJK UNIFIED IDEOGRAPH - 0xDAFD: 0x6E24, //CJK UNIFIED IDEOGRAPH - 0xDAFE: 0x6F51, //CJK UNIFIED IDEOGRAPH - 0xDBA1: 0x767C, //CJK UNIFIED IDEOGRAPH - 0xDBA2: 0x8DCB, //CJK UNIFIED IDEOGRAPH - 0xDBA3: 0x91B1, //CJK UNIFIED IDEOGRAPH - 0xDBA4: 0x9262, //CJK UNIFIED IDEOGRAPH - 0xDBA5: 0x9AEE, //CJK UNIFIED IDEOGRAPH - 0xDBA6: 0x9B43, //CJK UNIFIED IDEOGRAPH - 0xDBA7: 0x5023, //CJK UNIFIED IDEOGRAPH - 0xDBA8: 0x508D, //CJK UNIFIED IDEOGRAPH - 0xDBA9: 0x574A, //CJK UNIFIED IDEOGRAPH - 0xDBAA: 0x59A8, //CJK UNIFIED IDEOGRAPH - 0xDBAB: 0x5C28, //CJK UNIFIED IDEOGRAPH - 0xDBAC: 0x5E47, //CJK UNIFIED IDEOGRAPH - 0xDBAD: 0x5F77, //CJK UNIFIED IDEOGRAPH - 0xDBAE: 0x623F, //CJK UNIFIED IDEOGRAPH - 0xDBAF: 0x653E, //CJK UNIFIED IDEOGRAPH - 0xDBB0: 0x65B9, //CJK UNIFIED IDEOGRAPH - 0xDBB1: 0x65C1, //CJK UNIFIED IDEOGRAPH - 0xDBB2: 0x6609, //CJK UNIFIED IDEOGRAPH - 0xDBB3: 0x678B, //CJK UNIFIED IDEOGRAPH - 0xDBB4: 0x699C, //CJK UNIFIED IDEOGRAPH - 0xDBB5: 0x6EC2, //CJK UNIFIED IDEOGRAPH - 0xDBB6: 0x78C5, //CJK UNIFIED IDEOGRAPH - 0xDBB7: 0x7D21, //CJK UNIFIED IDEOGRAPH - 0xDBB8: 0x80AA, //CJK UNIFIED IDEOGRAPH - 0xDBB9: 0x8180, //CJK UNIFIED IDEOGRAPH - 0xDBBA: 0x822B, //CJK UNIFIED IDEOGRAPH - 0xDBBB: 0x82B3, //CJK UNIFIED IDEOGRAPH - 0xDBBC: 0x84A1, //CJK UNIFIED IDEOGRAPH - 0xDBBD: 0x868C, //CJK UNIFIED IDEOGRAPH - 0xDBBE: 0x8A2A, //CJK UNIFIED IDEOGRAPH - 0xDBBF: 0x8B17, //CJK UNIFIED IDEOGRAPH - 0xDBC0: 0x90A6, //CJK UNIFIED IDEOGRAPH - 0xDBC1: 0x9632, //CJK UNIFIED IDEOGRAPH - 0xDBC2: 0x9F90, //CJK UNIFIED IDEOGRAPH - 0xDBC3: 0x500D, //CJK UNIFIED IDEOGRAPH - 0xDBC4: 0x4FF3, //CJK UNIFIED IDEOGRAPH - 0xDBC5: 0xF963, //CJK COMPATIBILITY IDEOGRAPH - 0xDBC6: 0x57F9, //CJK UNIFIED IDEOGRAPH - 0xDBC7: 0x5F98, //CJK UNIFIED IDEOGRAPH - 0xDBC8: 0x62DC, //CJK UNIFIED IDEOGRAPH - 0xDBC9: 0x6392, //CJK UNIFIED IDEOGRAPH - 0xDBCA: 0x676F, //CJK UNIFIED IDEOGRAPH - 0xDBCB: 0x6E43, //CJK UNIFIED IDEOGRAPH - 0xDBCC: 0x7119, //CJK UNIFIED IDEOGRAPH - 0xDBCD: 0x76C3, //CJK UNIFIED IDEOGRAPH - 0xDBCE: 0x80CC, //CJK UNIFIED IDEOGRAPH - 0xDBCF: 0x80DA, //CJK UNIFIED IDEOGRAPH - 0xDBD0: 0x88F4, //CJK UNIFIED IDEOGRAPH - 0xDBD1: 0x88F5, //CJK UNIFIED IDEOGRAPH - 0xDBD2: 0x8919, //CJK UNIFIED IDEOGRAPH - 0xDBD3: 0x8CE0, //CJK UNIFIED IDEOGRAPH - 0xDBD4: 0x8F29, //CJK UNIFIED IDEOGRAPH - 0xDBD5: 0x914D, //CJK UNIFIED IDEOGRAPH - 0xDBD6: 0x966A, //CJK UNIFIED IDEOGRAPH - 0xDBD7: 0x4F2F, //CJK UNIFIED IDEOGRAPH - 0xDBD8: 0x4F70, //CJK UNIFIED IDEOGRAPH - 0xDBD9: 0x5E1B, //CJK UNIFIED IDEOGRAPH - 0xDBDA: 0x67CF, //CJK UNIFIED IDEOGRAPH - 0xDBDB: 0x6822, //CJK UNIFIED IDEOGRAPH - 0xDBDC: 0x767D, //CJK UNIFIED IDEOGRAPH - 0xDBDD: 0x767E, //CJK UNIFIED IDEOGRAPH - 0xDBDE: 0x9B44, //CJK UNIFIED IDEOGRAPH - 0xDBDF: 0x5E61, //CJK UNIFIED IDEOGRAPH - 0xDBE0: 0x6A0A, //CJK UNIFIED IDEOGRAPH - 0xDBE1: 0x7169, //CJK UNIFIED IDEOGRAPH - 0xDBE2: 0x71D4, //CJK UNIFIED IDEOGRAPH - 0xDBE3: 0x756A, //CJK UNIFIED IDEOGRAPH - 0xDBE4: 0xF964, //CJK COMPATIBILITY IDEOGRAPH - 0xDBE5: 0x7E41, //CJK UNIFIED IDEOGRAPH - 0xDBE6: 0x8543, //CJK UNIFIED IDEOGRAPH - 0xDBE7: 0x85E9, //CJK UNIFIED IDEOGRAPH - 0xDBE8: 0x98DC, //CJK UNIFIED IDEOGRAPH - 0xDBE9: 0x4F10, //CJK UNIFIED IDEOGRAPH - 0xDBEA: 0x7B4F, //CJK UNIFIED IDEOGRAPH - 0xDBEB: 0x7F70, //CJK UNIFIED IDEOGRAPH - 0xDBEC: 0x95A5, //CJK UNIFIED IDEOGRAPH - 0xDBED: 0x51E1, //CJK UNIFIED IDEOGRAPH - 0xDBEE: 0x5E06, //CJK UNIFIED IDEOGRAPH - 0xDBEF: 0x68B5, //CJK UNIFIED IDEOGRAPH - 0xDBF0: 0x6C3E, //CJK UNIFIED IDEOGRAPH - 0xDBF1: 0x6C4E, //CJK UNIFIED IDEOGRAPH - 0xDBF2: 0x6CDB, //CJK UNIFIED IDEOGRAPH - 0xDBF3: 0x72AF, //CJK UNIFIED IDEOGRAPH - 0xDBF4: 0x7BC4, //CJK UNIFIED IDEOGRAPH - 0xDBF5: 0x8303, //CJK UNIFIED IDEOGRAPH - 0xDBF6: 0x6CD5, //CJK UNIFIED IDEOGRAPH - 0xDBF7: 0x743A, //CJK UNIFIED IDEOGRAPH - 0xDBF8: 0x50FB, //CJK UNIFIED IDEOGRAPH - 0xDBF9: 0x5288, //CJK UNIFIED IDEOGRAPH - 0xDBFA: 0x58C1, //CJK UNIFIED IDEOGRAPH - 0xDBFB: 0x64D8, //CJK UNIFIED IDEOGRAPH - 0xDBFC: 0x6A97, //CJK UNIFIED IDEOGRAPH - 0xDBFD: 0x74A7, //CJK UNIFIED IDEOGRAPH - 0xDBFE: 0x7656, //CJK UNIFIED IDEOGRAPH - 0xDCA1: 0x78A7, //CJK UNIFIED IDEOGRAPH - 0xDCA2: 0x8617, //CJK UNIFIED IDEOGRAPH - 0xDCA3: 0x95E2, //CJK UNIFIED IDEOGRAPH - 0xDCA4: 0x9739, //CJK UNIFIED IDEOGRAPH - 0xDCA5: 0xF965, //CJK COMPATIBILITY IDEOGRAPH - 0xDCA6: 0x535E, //CJK UNIFIED IDEOGRAPH - 0xDCA7: 0x5F01, //CJK UNIFIED IDEOGRAPH - 0xDCA8: 0x8B8A, //CJK UNIFIED IDEOGRAPH - 0xDCA9: 0x8FA8, //CJK UNIFIED IDEOGRAPH - 0xDCAA: 0x8FAF, //CJK UNIFIED IDEOGRAPH - 0xDCAB: 0x908A, //CJK UNIFIED IDEOGRAPH - 0xDCAC: 0x5225, //CJK UNIFIED IDEOGRAPH - 0xDCAD: 0x77A5, //CJK UNIFIED IDEOGRAPH - 0xDCAE: 0x9C49, //CJK UNIFIED IDEOGRAPH - 0xDCAF: 0x9F08, //CJK UNIFIED IDEOGRAPH - 0xDCB0: 0x4E19, //CJK UNIFIED IDEOGRAPH - 0xDCB1: 0x5002, //CJK UNIFIED IDEOGRAPH - 0xDCB2: 0x5175, //CJK UNIFIED IDEOGRAPH - 0xDCB3: 0x5C5B, //CJK UNIFIED IDEOGRAPH - 0xDCB4: 0x5E77, //CJK UNIFIED IDEOGRAPH - 0xDCB5: 0x661E, //CJK UNIFIED IDEOGRAPH - 0xDCB6: 0x663A, //CJK UNIFIED IDEOGRAPH - 0xDCB7: 0x67C4, //CJK UNIFIED IDEOGRAPH - 0xDCB8: 0x68C5, //CJK UNIFIED IDEOGRAPH - 0xDCB9: 0x70B3, //CJK UNIFIED IDEOGRAPH - 0xDCBA: 0x7501, //CJK UNIFIED IDEOGRAPH - 0xDCBB: 0x75C5, //CJK UNIFIED IDEOGRAPH - 0xDCBC: 0x79C9, //CJK UNIFIED IDEOGRAPH - 0xDCBD: 0x7ADD, //CJK UNIFIED IDEOGRAPH - 0xDCBE: 0x8F27, //CJK UNIFIED IDEOGRAPH - 0xDCBF: 0x9920, //CJK UNIFIED IDEOGRAPH - 0xDCC0: 0x9A08, //CJK UNIFIED IDEOGRAPH - 0xDCC1: 0x4FDD, //CJK UNIFIED IDEOGRAPH - 0xDCC2: 0x5821, //CJK UNIFIED IDEOGRAPH - 0xDCC3: 0x5831, //CJK UNIFIED IDEOGRAPH - 0xDCC4: 0x5BF6, //CJK UNIFIED IDEOGRAPH - 0xDCC5: 0x666E, //CJK UNIFIED IDEOGRAPH - 0xDCC6: 0x6B65, //CJK UNIFIED IDEOGRAPH - 0xDCC7: 0x6D11, //CJK UNIFIED IDEOGRAPH - 0xDCC8: 0x6E7A, //CJK UNIFIED IDEOGRAPH - 0xDCC9: 0x6F7D, //CJK UNIFIED IDEOGRAPH - 0xDCCA: 0x73E4, //CJK UNIFIED IDEOGRAPH - 0xDCCB: 0x752B, //CJK UNIFIED IDEOGRAPH - 0xDCCC: 0x83E9, //CJK UNIFIED IDEOGRAPH - 0xDCCD: 0x88DC, //CJK UNIFIED IDEOGRAPH - 0xDCCE: 0x8913, //CJK UNIFIED IDEOGRAPH - 0xDCCF: 0x8B5C, //CJK UNIFIED IDEOGRAPH - 0xDCD0: 0x8F14, //CJK UNIFIED IDEOGRAPH - 0xDCD1: 0x4F0F, //CJK UNIFIED IDEOGRAPH - 0xDCD2: 0x50D5, //CJK UNIFIED IDEOGRAPH - 0xDCD3: 0x5310, //CJK UNIFIED IDEOGRAPH - 0xDCD4: 0x535C, //CJK UNIFIED IDEOGRAPH - 0xDCD5: 0x5B93, //CJK UNIFIED IDEOGRAPH - 0xDCD6: 0x5FA9, //CJK UNIFIED IDEOGRAPH - 0xDCD7: 0x670D, //CJK UNIFIED IDEOGRAPH - 0xDCD8: 0x798F, //CJK UNIFIED IDEOGRAPH - 0xDCD9: 0x8179, //CJK UNIFIED IDEOGRAPH - 0xDCDA: 0x832F, //CJK UNIFIED IDEOGRAPH - 0xDCDB: 0x8514, //CJK UNIFIED IDEOGRAPH - 0xDCDC: 0x8907, //CJK UNIFIED IDEOGRAPH - 0xDCDD: 0x8986, //CJK UNIFIED IDEOGRAPH - 0xDCDE: 0x8F39, //CJK UNIFIED IDEOGRAPH - 0xDCDF: 0x8F3B, //CJK UNIFIED IDEOGRAPH - 0xDCE0: 0x99A5, //CJK UNIFIED IDEOGRAPH - 0xDCE1: 0x9C12, //CJK UNIFIED IDEOGRAPH - 0xDCE2: 0x672C, //CJK UNIFIED IDEOGRAPH - 0xDCE3: 0x4E76, //CJK UNIFIED IDEOGRAPH - 0xDCE4: 0x4FF8, //CJK UNIFIED IDEOGRAPH - 0xDCE5: 0x5949, //CJK UNIFIED IDEOGRAPH - 0xDCE6: 0x5C01, //CJK UNIFIED IDEOGRAPH - 0xDCE7: 0x5CEF, //CJK UNIFIED IDEOGRAPH - 0xDCE8: 0x5CF0, //CJK UNIFIED IDEOGRAPH - 0xDCE9: 0x6367, //CJK UNIFIED IDEOGRAPH - 0xDCEA: 0x68D2, //CJK UNIFIED IDEOGRAPH - 0xDCEB: 0x70FD, //CJK UNIFIED IDEOGRAPH - 0xDCEC: 0x71A2, //CJK UNIFIED IDEOGRAPH - 0xDCED: 0x742B, //CJK UNIFIED IDEOGRAPH - 0xDCEE: 0x7E2B, //CJK UNIFIED IDEOGRAPH - 0xDCEF: 0x84EC, //CJK UNIFIED IDEOGRAPH - 0xDCF0: 0x8702, //CJK UNIFIED IDEOGRAPH - 0xDCF1: 0x9022, //CJK UNIFIED IDEOGRAPH - 0xDCF2: 0x92D2, //CJK UNIFIED IDEOGRAPH - 0xDCF3: 0x9CF3, //CJK UNIFIED IDEOGRAPH - 0xDCF4: 0x4E0D, //CJK UNIFIED IDEOGRAPH - 0xDCF5: 0x4ED8, //CJK UNIFIED IDEOGRAPH - 0xDCF6: 0x4FEF, //CJK UNIFIED IDEOGRAPH - 0xDCF7: 0x5085, //CJK UNIFIED IDEOGRAPH - 0xDCF8: 0x5256, //CJK UNIFIED IDEOGRAPH - 0xDCF9: 0x526F, //CJK UNIFIED IDEOGRAPH - 0xDCFA: 0x5426, //CJK UNIFIED IDEOGRAPH - 0xDCFB: 0x5490, //CJK UNIFIED IDEOGRAPH - 0xDCFC: 0x57E0, //CJK UNIFIED IDEOGRAPH - 0xDCFD: 0x592B, //CJK UNIFIED IDEOGRAPH - 0xDCFE: 0x5A66, //CJK UNIFIED IDEOGRAPH - 0xDDA1: 0x5B5A, //CJK UNIFIED IDEOGRAPH - 0xDDA2: 0x5B75, //CJK UNIFIED IDEOGRAPH - 0xDDA3: 0x5BCC, //CJK UNIFIED IDEOGRAPH - 0xDDA4: 0x5E9C, //CJK UNIFIED IDEOGRAPH - 0xDDA5: 0xF966, //CJK COMPATIBILITY IDEOGRAPH - 0xDDA6: 0x6276, //CJK UNIFIED IDEOGRAPH - 0xDDA7: 0x6577, //CJK UNIFIED IDEOGRAPH - 0xDDA8: 0x65A7, //CJK UNIFIED IDEOGRAPH - 0xDDA9: 0x6D6E, //CJK UNIFIED IDEOGRAPH - 0xDDAA: 0x6EA5, //CJK UNIFIED IDEOGRAPH - 0xDDAB: 0x7236, //CJK UNIFIED IDEOGRAPH - 0xDDAC: 0x7B26, //CJK UNIFIED IDEOGRAPH - 0xDDAD: 0x7C3F, //CJK UNIFIED IDEOGRAPH - 0xDDAE: 0x7F36, //CJK UNIFIED IDEOGRAPH - 0xDDAF: 0x8150, //CJK UNIFIED IDEOGRAPH - 0xDDB0: 0x8151, //CJK UNIFIED IDEOGRAPH - 0xDDB1: 0x819A, //CJK UNIFIED IDEOGRAPH - 0xDDB2: 0x8240, //CJK UNIFIED IDEOGRAPH - 0xDDB3: 0x8299, //CJK UNIFIED IDEOGRAPH - 0xDDB4: 0x83A9, //CJK UNIFIED IDEOGRAPH - 0xDDB5: 0x8A03, //CJK UNIFIED IDEOGRAPH - 0xDDB6: 0x8CA0, //CJK UNIFIED IDEOGRAPH - 0xDDB7: 0x8CE6, //CJK UNIFIED IDEOGRAPH - 0xDDB8: 0x8CFB, //CJK UNIFIED IDEOGRAPH - 0xDDB9: 0x8D74, //CJK UNIFIED IDEOGRAPH - 0xDDBA: 0x8DBA, //CJK UNIFIED IDEOGRAPH - 0xDDBB: 0x90E8, //CJK UNIFIED IDEOGRAPH - 0xDDBC: 0x91DC, //CJK UNIFIED IDEOGRAPH - 0xDDBD: 0x961C, //CJK UNIFIED IDEOGRAPH - 0xDDBE: 0x9644, //CJK UNIFIED IDEOGRAPH - 0xDDBF: 0x99D9, //CJK UNIFIED IDEOGRAPH - 0xDDC0: 0x9CE7, //CJK UNIFIED IDEOGRAPH - 0xDDC1: 0x5317, //CJK UNIFIED IDEOGRAPH - 0xDDC2: 0x5206, //CJK UNIFIED IDEOGRAPH - 0xDDC3: 0x5429, //CJK UNIFIED IDEOGRAPH - 0xDDC4: 0x5674, //CJK UNIFIED IDEOGRAPH - 0xDDC5: 0x58B3, //CJK UNIFIED IDEOGRAPH - 0xDDC6: 0x5954, //CJK UNIFIED IDEOGRAPH - 0xDDC7: 0x596E, //CJK UNIFIED IDEOGRAPH - 0xDDC8: 0x5FFF, //CJK UNIFIED IDEOGRAPH - 0xDDC9: 0x61A4, //CJK UNIFIED IDEOGRAPH - 0xDDCA: 0x626E, //CJK UNIFIED IDEOGRAPH - 0xDDCB: 0x6610, //CJK UNIFIED IDEOGRAPH - 0xDDCC: 0x6C7E, //CJK UNIFIED IDEOGRAPH - 0xDDCD: 0x711A, //CJK UNIFIED IDEOGRAPH - 0xDDCE: 0x76C6, //CJK UNIFIED IDEOGRAPH - 0xDDCF: 0x7C89, //CJK UNIFIED IDEOGRAPH - 0xDDD0: 0x7CDE, //CJK UNIFIED IDEOGRAPH - 0xDDD1: 0x7D1B, //CJK UNIFIED IDEOGRAPH - 0xDDD2: 0x82AC, //CJK UNIFIED IDEOGRAPH - 0xDDD3: 0x8CC1, //CJK UNIFIED IDEOGRAPH - 0xDDD4: 0x96F0, //CJK UNIFIED IDEOGRAPH - 0xDDD5: 0xF967, //CJK COMPATIBILITY IDEOGRAPH - 0xDDD6: 0x4F5B, //CJK UNIFIED IDEOGRAPH - 0xDDD7: 0x5F17, //CJK UNIFIED IDEOGRAPH - 0xDDD8: 0x5F7F, //CJK UNIFIED IDEOGRAPH - 0xDDD9: 0x62C2, //CJK UNIFIED IDEOGRAPH - 0xDDDA: 0x5D29, //CJK UNIFIED IDEOGRAPH - 0xDDDB: 0x670B, //CJK UNIFIED IDEOGRAPH - 0xDDDC: 0x68DA, //CJK UNIFIED IDEOGRAPH - 0xDDDD: 0x787C, //CJK UNIFIED IDEOGRAPH - 0xDDDE: 0x7E43, //CJK UNIFIED IDEOGRAPH - 0xDDDF: 0x9D6C, //CJK UNIFIED IDEOGRAPH - 0xDDE0: 0x4E15, //CJK UNIFIED IDEOGRAPH - 0xDDE1: 0x5099, //CJK UNIFIED IDEOGRAPH - 0xDDE2: 0x5315, //CJK UNIFIED IDEOGRAPH - 0xDDE3: 0x532A, //CJK UNIFIED IDEOGRAPH - 0xDDE4: 0x5351, //CJK UNIFIED IDEOGRAPH - 0xDDE5: 0x5983, //CJK UNIFIED IDEOGRAPH - 0xDDE6: 0x5A62, //CJK UNIFIED IDEOGRAPH - 0xDDE7: 0x5E87, //CJK UNIFIED IDEOGRAPH - 0xDDE8: 0x60B2, //CJK UNIFIED IDEOGRAPH - 0xDDE9: 0x618A, //CJK UNIFIED IDEOGRAPH - 0xDDEA: 0x6249, //CJK UNIFIED IDEOGRAPH - 0xDDEB: 0x6279, //CJK UNIFIED IDEOGRAPH - 0xDDEC: 0x6590, //CJK UNIFIED IDEOGRAPH - 0xDDED: 0x6787, //CJK UNIFIED IDEOGRAPH - 0xDDEE: 0x69A7, //CJK UNIFIED IDEOGRAPH - 0xDDEF: 0x6BD4, //CJK UNIFIED IDEOGRAPH - 0xDDF0: 0x6BD6, //CJK UNIFIED IDEOGRAPH - 0xDDF1: 0x6BD7, //CJK UNIFIED IDEOGRAPH - 0xDDF2: 0x6BD8, //CJK UNIFIED IDEOGRAPH - 0xDDF3: 0x6CB8, //CJK UNIFIED IDEOGRAPH - 0xDDF4: 0xF968, //CJK COMPATIBILITY IDEOGRAPH - 0xDDF5: 0x7435, //CJK UNIFIED IDEOGRAPH - 0xDDF6: 0x75FA, //CJK UNIFIED IDEOGRAPH - 0xDDF7: 0x7812, //CJK UNIFIED IDEOGRAPH - 0xDDF8: 0x7891, //CJK UNIFIED IDEOGRAPH - 0xDDF9: 0x79D5, //CJK UNIFIED IDEOGRAPH - 0xDDFA: 0x79D8, //CJK UNIFIED IDEOGRAPH - 0xDDFB: 0x7C83, //CJK UNIFIED IDEOGRAPH - 0xDDFC: 0x7DCB, //CJK UNIFIED IDEOGRAPH - 0xDDFD: 0x7FE1, //CJK UNIFIED IDEOGRAPH - 0xDDFE: 0x80A5, //CJK UNIFIED IDEOGRAPH - 0xDEA1: 0x813E, //CJK UNIFIED IDEOGRAPH - 0xDEA2: 0x81C2, //CJK UNIFIED IDEOGRAPH - 0xDEA3: 0x83F2, //CJK UNIFIED IDEOGRAPH - 0xDEA4: 0x871A, //CJK UNIFIED IDEOGRAPH - 0xDEA5: 0x88E8, //CJK UNIFIED IDEOGRAPH - 0xDEA6: 0x8AB9, //CJK UNIFIED IDEOGRAPH - 0xDEA7: 0x8B6C, //CJK UNIFIED IDEOGRAPH - 0xDEA8: 0x8CBB, //CJK UNIFIED IDEOGRAPH - 0xDEA9: 0x9119, //CJK UNIFIED IDEOGRAPH - 0xDEAA: 0x975E, //CJK UNIFIED IDEOGRAPH - 0xDEAB: 0x98DB, //CJK UNIFIED IDEOGRAPH - 0xDEAC: 0x9F3B, //CJK UNIFIED IDEOGRAPH - 0xDEAD: 0x56AC, //CJK UNIFIED IDEOGRAPH - 0xDEAE: 0x5B2A, //CJK UNIFIED IDEOGRAPH - 0xDEAF: 0x5F6C, //CJK UNIFIED IDEOGRAPH - 0xDEB0: 0x658C, //CJK UNIFIED IDEOGRAPH - 0xDEB1: 0x6AB3, //CJK UNIFIED IDEOGRAPH - 0xDEB2: 0x6BAF, //CJK UNIFIED IDEOGRAPH - 0xDEB3: 0x6D5C, //CJK UNIFIED IDEOGRAPH - 0xDEB4: 0x6FF1, //CJK UNIFIED IDEOGRAPH - 0xDEB5: 0x7015, //CJK UNIFIED IDEOGRAPH - 0xDEB6: 0x725D, //CJK UNIFIED IDEOGRAPH - 0xDEB7: 0x73AD, //CJK UNIFIED IDEOGRAPH - 0xDEB8: 0x8CA7, //CJK UNIFIED IDEOGRAPH - 0xDEB9: 0x8CD3, //CJK UNIFIED IDEOGRAPH - 0xDEBA: 0x983B, //CJK UNIFIED IDEOGRAPH - 0xDEBB: 0x6191, //CJK UNIFIED IDEOGRAPH - 0xDEBC: 0x6C37, //CJK UNIFIED IDEOGRAPH - 0xDEBD: 0x8058, //CJK UNIFIED IDEOGRAPH - 0xDEBE: 0x9A01, //CJK UNIFIED IDEOGRAPH - 0xDEBF: 0x4E4D, //CJK UNIFIED IDEOGRAPH - 0xDEC0: 0x4E8B, //CJK UNIFIED IDEOGRAPH - 0xDEC1: 0x4E9B, //CJK UNIFIED IDEOGRAPH - 0xDEC2: 0x4ED5, //CJK UNIFIED IDEOGRAPH - 0xDEC3: 0x4F3A, //CJK UNIFIED IDEOGRAPH - 0xDEC4: 0x4F3C, //CJK UNIFIED IDEOGRAPH - 0xDEC5: 0x4F7F, //CJK UNIFIED IDEOGRAPH - 0xDEC6: 0x4FDF, //CJK UNIFIED IDEOGRAPH - 0xDEC7: 0x50FF, //CJK UNIFIED IDEOGRAPH - 0xDEC8: 0x53F2, //CJK UNIFIED IDEOGRAPH - 0xDEC9: 0x53F8, //CJK UNIFIED IDEOGRAPH - 0xDECA: 0x5506, //CJK UNIFIED IDEOGRAPH - 0xDECB: 0x55E3, //CJK UNIFIED IDEOGRAPH - 0xDECC: 0x56DB, //CJK UNIFIED IDEOGRAPH - 0xDECD: 0x58EB, //CJK UNIFIED IDEOGRAPH - 0xDECE: 0x5962, //CJK UNIFIED IDEOGRAPH - 0xDECF: 0x5A11, //CJK UNIFIED IDEOGRAPH - 0xDED0: 0x5BEB, //CJK UNIFIED IDEOGRAPH - 0xDED1: 0x5BFA, //CJK UNIFIED IDEOGRAPH - 0xDED2: 0x5C04, //CJK UNIFIED IDEOGRAPH - 0xDED3: 0x5DF3, //CJK UNIFIED IDEOGRAPH - 0xDED4: 0x5E2B, //CJK UNIFIED IDEOGRAPH - 0xDED5: 0x5F99, //CJK UNIFIED IDEOGRAPH - 0xDED6: 0x601D, //CJK UNIFIED IDEOGRAPH - 0xDED7: 0x6368, //CJK UNIFIED IDEOGRAPH - 0xDED8: 0x659C, //CJK UNIFIED IDEOGRAPH - 0xDED9: 0x65AF, //CJK UNIFIED IDEOGRAPH - 0xDEDA: 0x67F6, //CJK UNIFIED IDEOGRAPH - 0xDEDB: 0x67FB, //CJK UNIFIED IDEOGRAPH - 0xDEDC: 0x68AD, //CJK UNIFIED IDEOGRAPH - 0xDEDD: 0x6B7B, //CJK UNIFIED IDEOGRAPH - 0xDEDE: 0x6C99, //CJK UNIFIED IDEOGRAPH - 0xDEDF: 0x6CD7, //CJK UNIFIED IDEOGRAPH - 0xDEE0: 0x6E23, //CJK UNIFIED IDEOGRAPH - 0xDEE1: 0x7009, //CJK UNIFIED IDEOGRAPH - 0xDEE2: 0x7345, //CJK UNIFIED IDEOGRAPH - 0xDEE3: 0x7802, //CJK UNIFIED IDEOGRAPH - 0xDEE4: 0x793E, //CJK UNIFIED IDEOGRAPH - 0xDEE5: 0x7940, //CJK UNIFIED IDEOGRAPH - 0xDEE6: 0x7960, //CJK UNIFIED IDEOGRAPH - 0xDEE7: 0x79C1, //CJK UNIFIED IDEOGRAPH - 0xDEE8: 0x7BE9, //CJK UNIFIED IDEOGRAPH - 0xDEE9: 0x7D17, //CJK UNIFIED IDEOGRAPH - 0xDEEA: 0x7D72, //CJK UNIFIED IDEOGRAPH - 0xDEEB: 0x8086, //CJK UNIFIED IDEOGRAPH - 0xDEEC: 0x820D, //CJK UNIFIED IDEOGRAPH - 0xDEED: 0x838E, //CJK UNIFIED IDEOGRAPH - 0xDEEE: 0x84D1, //CJK UNIFIED IDEOGRAPH - 0xDEEF: 0x86C7, //CJK UNIFIED IDEOGRAPH - 0xDEF0: 0x88DF, //CJK UNIFIED IDEOGRAPH - 0xDEF1: 0x8A50, //CJK UNIFIED IDEOGRAPH - 0xDEF2: 0x8A5E, //CJK UNIFIED IDEOGRAPH - 0xDEF3: 0x8B1D, //CJK UNIFIED IDEOGRAPH - 0xDEF4: 0x8CDC, //CJK UNIFIED IDEOGRAPH - 0xDEF5: 0x8D66, //CJK UNIFIED IDEOGRAPH - 0xDEF6: 0x8FAD, //CJK UNIFIED IDEOGRAPH - 0xDEF7: 0x90AA, //CJK UNIFIED IDEOGRAPH - 0xDEF8: 0x98FC, //CJK UNIFIED IDEOGRAPH - 0xDEF9: 0x99DF, //CJK UNIFIED IDEOGRAPH - 0xDEFA: 0x9E9D, //CJK UNIFIED IDEOGRAPH - 0xDEFB: 0x524A, //CJK UNIFIED IDEOGRAPH - 0xDEFC: 0xF969, //CJK COMPATIBILITY IDEOGRAPH - 0xDEFD: 0x6714, //CJK UNIFIED IDEOGRAPH - 0xDEFE: 0xF96A, //CJK COMPATIBILITY IDEOGRAPH - 0xDFA1: 0x5098, //CJK UNIFIED IDEOGRAPH - 0xDFA2: 0x522A, //CJK UNIFIED IDEOGRAPH - 0xDFA3: 0x5C71, //CJK UNIFIED IDEOGRAPH - 0xDFA4: 0x6563, //CJK UNIFIED IDEOGRAPH - 0xDFA5: 0x6C55, //CJK UNIFIED IDEOGRAPH - 0xDFA6: 0x73CA, //CJK UNIFIED IDEOGRAPH - 0xDFA7: 0x7523, //CJK UNIFIED IDEOGRAPH - 0xDFA8: 0x759D, //CJK UNIFIED IDEOGRAPH - 0xDFA9: 0x7B97, //CJK UNIFIED IDEOGRAPH - 0xDFAA: 0x849C, //CJK UNIFIED IDEOGRAPH - 0xDFAB: 0x9178, //CJK UNIFIED IDEOGRAPH - 0xDFAC: 0x9730, //CJK UNIFIED IDEOGRAPH - 0xDFAD: 0x4E77, //CJK UNIFIED IDEOGRAPH - 0xDFAE: 0x6492, //CJK UNIFIED IDEOGRAPH - 0xDFAF: 0x6BBA, //CJK UNIFIED IDEOGRAPH - 0xDFB0: 0x715E, //CJK UNIFIED IDEOGRAPH - 0xDFB1: 0x85A9, //CJK UNIFIED IDEOGRAPH - 0xDFB2: 0x4E09, //CJK UNIFIED IDEOGRAPH - 0xDFB3: 0xF96B, //CJK COMPATIBILITY IDEOGRAPH - 0xDFB4: 0x6749, //CJK UNIFIED IDEOGRAPH - 0xDFB5: 0x68EE, //CJK UNIFIED IDEOGRAPH - 0xDFB6: 0x6E17, //CJK UNIFIED IDEOGRAPH - 0xDFB7: 0x829F, //CJK UNIFIED IDEOGRAPH - 0xDFB8: 0x8518, //CJK UNIFIED IDEOGRAPH - 0xDFB9: 0x886B, //CJK UNIFIED IDEOGRAPH - 0xDFBA: 0x63F7, //CJK UNIFIED IDEOGRAPH - 0xDFBB: 0x6F81, //CJK UNIFIED IDEOGRAPH - 0xDFBC: 0x9212, //CJK UNIFIED IDEOGRAPH - 0xDFBD: 0x98AF, //CJK UNIFIED IDEOGRAPH - 0xDFBE: 0x4E0A, //CJK UNIFIED IDEOGRAPH - 0xDFBF: 0x50B7, //CJK UNIFIED IDEOGRAPH - 0xDFC0: 0x50CF, //CJK UNIFIED IDEOGRAPH - 0xDFC1: 0x511F, //CJK UNIFIED IDEOGRAPH - 0xDFC2: 0x5546, //CJK UNIFIED IDEOGRAPH - 0xDFC3: 0x55AA, //CJK UNIFIED IDEOGRAPH - 0xDFC4: 0x5617, //CJK UNIFIED IDEOGRAPH - 0xDFC5: 0x5B40, //CJK UNIFIED IDEOGRAPH - 0xDFC6: 0x5C19, //CJK UNIFIED IDEOGRAPH - 0xDFC7: 0x5CE0, //CJK UNIFIED IDEOGRAPH - 0xDFC8: 0x5E38, //CJK UNIFIED IDEOGRAPH - 0xDFC9: 0x5E8A, //CJK UNIFIED IDEOGRAPH - 0xDFCA: 0x5EA0, //CJK UNIFIED IDEOGRAPH - 0xDFCB: 0x5EC2, //CJK UNIFIED IDEOGRAPH - 0xDFCC: 0x60F3, //CJK UNIFIED IDEOGRAPH - 0xDFCD: 0x6851, //CJK UNIFIED IDEOGRAPH - 0xDFCE: 0x6A61, //CJK UNIFIED IDEOGRAPH - 0xDFCF: 0x6E58, //CJK UNIFIED IDEOGRAPH - 0xDFD0: 0x723D, //CJK UNIFIED IDEOGRAPH - 0xDFD1: 0x7240, //CJK UNIFIED IDEOGRAPH - 0xDFD2: 0x72C0, //CJK UNIFIED IDEOGRAPH - 0xDFD3: 0x76F8, //CJK UNIFIED IDEOGRAPH - 0xDFD4: 0x7965, //CJK UNIFIED IDEOGRAPH - 0xDFD5: 0x7BB1, //CJK UNIFIED IDEOGRAPH - 0xDFD6: 0x7FD4, //CJK UNIFIED IDEOGRAPH - 0xDFD7: 0x88F3, //CJK UNIFIED IDEOGRAPH - 0xDFD8: 0x89F4, //CJK UNIFIED IDEOGRAPH - 0xDFD9: 0x8A73, //CJK UNIFIED IDEOGRAPH - 0xDFDA: 0x8C61, //CJK UNIFIED IDEOGRAPH - 0xDFDB: 0x8CDE, //CJK UNIFIED IDEOGRAPH - 0xDFDC: 0x971C, //CJK UNIFIED IDEOGRAPH - 0xDFDD: 0x585E, //CJK UNIFIED IDEOGRAPH - 0xDFDE: 0x74BD, //CJK UNIFIED IDEOGRAPH - 0xDFDF: 0x8CFD, //CJK UNIFIED IDEOGRAPH - 0xDFE0: 0x55C7, //CJK UNIFIED IDEOGRAPH - 0xDFE1: 0xF96C, //CJK COMPATIBILITY IDEOGRAPH - 0xDFE2: 0x7A61, //CJK UNIFIED IDEOGRAPH - 0xDFE3: 0x7D22, //CJK UNIFIED IDEOGRAPH - 0xDFE4: 0x8272, //CJK UNIFIED IDEOGRAPH - 0xDFE5: 0x7272, //CJK UNIFIED IDEOGRAPH - 0xDFE6: 0x751F, //CJK UNIFIED IDEOGRAPH - 0xDFE7: 0x7525, //CJK UNIFIED IDEOGRAPH - 0xDFE8: 0xF96D, //CJK COMPATIBILITY IDEOGRAPH - 0xDFE9: 0x7B19, //CJK UNIFIED IDEOGRAPH - 0xDFEA: 0x5885, //CJK UNIFIED IDEOGRAPH - 0xDFEB: 0x58FB, //CJK UNIFIED IDEOGRAPH - 0xDFEC: 0x5DBC, //CJK UNIFIED IDEOGRAPH - 0xDFED: 0x5E8F, //CJK UNIFIED IDEOGRAPH - 0xDFEE: 0x5EB6, //CJK UNIFIED IDEOGRAPH - 0xDFEF: 0x5F90, //CJK UNIFIED IDEOGRAPH - 0xDFF0: 0x6055, //CJK UNIFIED IDEOGRAPH - 0xDFF1: 0x6292, //CJK UNIFIED IDEOGRAPH - 0xDFF2: 0x637F, //CJK UNIFIED IDEOGRAPH - 0xDFF3: 0x654D, //CJK UNIFIED IDEOGRAPH - 0xDFF4: 0x6691, //CJK UNIFIED IDEOGRAPH - 0xDFF5: 0x66D9, //CJK UNIFIED IDEOGRAPH - 0xDFF6: 0x66F8, //CJK UNIFIED IDEOGRAPH - 0xDFF7: 0x6816, //CJK UNIFIED IDEOGRAPH - 0xDFF8: 0x68F2, //CJK UNIFIED IDEOGRAPH - 0xDFF9: 0x7280, //CJK UNIFIED IDEOGRAPH - 0xDFFA: 0x745E, //CJK UNIFIED IDEOGRAPH - 0xDFFB: 0x7B6E, //CJK UNIFIED IDEOGRAPH - 0xDFFC: 0x7D6E, //CJK UNIFIED IDEOGRAPH - 0xDFFD: 0x7DD6, //CJK UNIFIED IDEOGRAPH - 0xDFFE: 0x7F72, //CJK UNIFIED IDEOGRAPH - 0xE0A1: 0x80E5, //CJK UNIFIED IDEOGRAPH - 0xE0A2: 0x8212, //CJK UNIFIED IDEOGRAPH - 0xE0A3: 0x85AF, //CJK UNIFIED IDEOGRAPH - 0xE0A4: 0x897F, //CJK UNIFIED IDEOGRAPH - 0xE0A5: 0x8A93, //CJK UNIFIED IDEOGRAPH - 0xE0A6: 0x901D, //CJK UNIFIED IDEOGRAPH - 0xE0A7: 0x92E4, //CJK UNIFIED IDEOGRAPH - 0xE0A8: 0x9ECD, //CJK UNIFIED IDEOGRAPH - 0xE0A9: 0x9F20, //CJK UNIFIED IDEOGRAPH - 0xE0AA: 0x5915, //CJK UNIFIED IDEOGRAPH - 0xE0AB: 0x596D, //CJK UNIFIED IDEOGRAPH - 0xE0AC: 0x5E2D, //CJK UNIFIED IDEOGRAPH - 0xE0AD: 0x60DC, //CJK UNIFIED IDEOGRAPH - 0xE0AE: 0x6614, //CJK UNIFIED IDEOGRAPH - 0xE0AF: 0x6673, //CJK UNIFIED IDEOGRAPH - 0xE0B0: 0x6790, //CJK UNIFIED IDEOGRAPH - 0xE0B1: 0x6C50, //CJK UNIFIED IDEOGRAPH - 0xE0B2: 0x6DC5, //CJK UNIFIED IDEOGRAPH - 0xE0B3: 0x6F5F, //CJK UNIFIED IDEOGRAPH - 0xE0B4: 0x77F3, //CJK UNIFIED IDEOGRAPH - 0xE0B5: 0x78A9, //CJK UNIFIED IDEOGRAPH - 0xE0B6: 0x84C6, //CJK UNIFIED IDEOGRAPH - 0xE0B7: 0x91CB, //CJK UNIFIED IDEOGRAPH - 0xE0B8: 0x932B, //CJK UNIFIED IDEOGRAPH - 0xE0B9: 0x4ED9, //CJK UNIFIED IDEOGRAPH - 0xE0BA: 0x50CA, //CJK UNIFIED IDEOGRAPH - 0xE0BB: 0x5148, //CJK UNIFIED IDEOGRAPH - 0xE0BC: 0x5584, //CJK UNIFIED IDEOGRAPH - 0xE0BD: 0x5B0B, //CJK UNIFIED IDEOGRAPH - 0xE0BE: 0x5BA3, //CJK UNIFIED IDEOGRAPH - 0xE0BF: 0x6247, //CJK UNIFIED IDEOGRAPH - 0xE0C0: 0x657E, //CJK UNIFIED IDEOGRAPH - 0xE0C1: 0x65CB, //CJK UNIFIED IDEOGRAPH - 0xE0C2: 0x6E32, //CJK UNIFIED IDEOGRAPH - 0xE0C3: 0x717D, //CJK UNIFIED IDEOGRAPH - 0xE0C4: 0x7401, //CJK UNIFIED IDEOGRAPH - 0xE0C5: 0x7444, //CJK UNIFIED IDEOGRAPH - 0xE0C6: 0x7487, //CJK UNIFIED IDEOGRAPH - 0xE0C7: 0x74BF, //CJK UNIFIED IDEOGRAPH - 0xE0C8: 0x766C, //CJK UNIFIED IDEOGRAPH - 0xE0C9: 0x79AA, //CJK UNIFIED IDEOGRAPH - 0xE0CA: 0x7DDA, //CJK UNIFIED IDEOGRAPH - 0xE0CB: 0x7E55, //CJK UNIFIED IDEOGRAPH - 0xE0CC: 0x7FA8, //CJK UNIFIED IDEOGRAPH - 0xE0CD: 0x817A, //CJK UNIFIED IDEOGRAPH - 0xE0CE: 0x81B3, //CJK UNIFIED IDEOGRAPH - 0xE0CF: 0x8239, //CJK UNIFIED IDEOGRAPH - 0xE0D0: 0x861A, //CJK UNIFIED IDEOGRAPH - 0xE0D1: 0x87EC, //CJK UNIFIED IDEOGRAPH - 0xE0D2: 0x8A75, //CJK UNIFIED IDEOGRAPH - 0xE0D3: 0x8DE3, //CJK UNIFIED IDEOGRAPH - 0xE0D4: 0x9078, //CJK UNIFIED IDEOGRAPH - 0xE0D5: 0x9291, //CJK UNIFIED IDEOGRAPH - 0xE0D6: 0x9425, //CJK UNIFIED IDEOGRAPH - 0xE0D7: 0x994D, //CJK UNIFIED IDEOGRAPH - 0xE0D8: 0x9BAE, //CJK UNIFIED IDEOGRAPH - 0xE0D9: 0x5368, //CJK UNIFIED IDEOGRAPH - 0xE0DA: 0x5C51, //CJK UNIFIED IDEOGRAPH - 0xE0DB: 0x6954, //CJK UNIFIED IDEOGRAPH - 0xE0DC: 0x6CC4, //CJK UNIFIED IDEOGRAPH - 0xE0DD: 0x6D29, //CJK UNIFIED IDEOGRAPH - 0xE0DE: 0x6E2B, //CJK UNIFIED IDEOGRAPH - 0xE0DF: 0x820C, //CJK UNIFIED IDEOGRAPH - 0xE0E0: 0x859B, //CJK UNIFIED IDEOGRAPH - 0xE0E1: 0x893B, //CJK UNIFIED IDEOGRAPH - 0xE0E2: 0x8A2D, //CJK UNIFIED IDEOGRAPH - 0xE0E3: 0x8AAA, //CJK UNIFIED IDEOGRAPH - 0xE0E4: 0x96EA, //CJK UNIFIED IDEOGRAPH - 0xE0E5: 0x9F67, //CJK UNIFIED IDEOGRAPH - 0xE0E6: 0x5261, //CJK UNIFIED IDEOGRAPH - 0xE0E7: 0x66B9, //CJK UNIFIED IDEOGRAPH - 0xE0E8: 0x6BB2, //CJK UNIFIED IDEOGRAPH - 0xE0E9: 0x7E96, //CJK UNIFIED IDEOGRAPH - 0xE0EA: 0x87FE, //CJK UNIFIED IDEOGRAPH - 0xE0EB: 0x8D0D, //CJK UNIFIED IDEOGRAPH - 0xE0EC: 0x9583, //CJK UNIFIED IDEOGRAPH - 0xE0ED: 0x965D, //CJK UNIFIED IDEOGRAPH - 0xE0EE: 0x651D, //CJK UNIFIED IDEOGRAPH - 0xE0EF: 0x6D89, //CJK UNIFIED IDEOGRAPH - 0xE0F0: 0x71EE, //CJK UNIFIED IDEOGRAPH - 0xE0F1: 0xF96E, //CJK COMPATIBILITY IDEOGRAPH - 0xE0F2: 0x57CE, //CJK UNIFIED IDEOGRAPH - 0xE0F3: 0x59D3, //CJK UNIFIED IDEOGRAPH - 0xE0F4: 0x5BAC, //CJK UNIFIED IDEOGRAPH - 0xE0F5: 0x6027, //CJK UNIFIED IDEOGRAPH - 0xE0F6: 0x60FA, //CJK UNIFIED IDEOGRAPH - 0xE0F7: 0x6210, //CJK UNIFIED IDEOGRAPH - 0xE0F8: 0x661F, //CJK UNIFIED IDEOGRAPH - 0xE0F9: 0x665F, //CJK UNIFIED IDEOGRAPH - 0xE0FA: 0x7329, //CJK UNIFIED IDEOGRAPH - 0xE0FB: 0x73F9, //CJK UNIFIED IDEOGRAPH - 0xE0FC: 0x76DB, //CJK UNIFIED IDEOGRAPH - 0xE0FD: 0x7701, //CJK UNIFIED IDEOGRAPH - 0xE0FE: 0x7B6C, //CJK UNIFIED IDEOGRAPH - 0xE1A1: 0x8056, //CJK UNIFIED IDEOGRAPH - 0xE1A2: 0x8072, //CJK UNIFIED IDEOGRAPH - 0xE1A3: 0x8165, //CJK UNIFIED IDEOGRAPH - 0xE1A4: 0x8AA0, //CJK UNIFIED IDEOGRAPH - 0xE1A5: 0x9192, //CJK UNIFIED IDEOGRAPH - 0xE1A6: 0x4E16, //CJK UNIFIED IDEOGRAPH - 0xE1A7: 0x52E2, //CJK UNIFIED IDEOGRAPH - 0xE1A8: 0x6B72, //CJK UNIFIED IDEOGRAPH - 0xE1A9: 0x6D17, //CJK UNIFIED IDEOGRAPH - 0xE1AA: 0x7A05, //CJK UNIFIED IDEOGRAPH - 0xE1AB: 0x7B39, //CJK UNIFIED IDEOGRAPH - 0xE1AC: 0x7D30, //CJK UNIFIED IDEOGRAPH - 0xE1AD: 0xF96F, //CJK COMPATIBILITY IDEOGRAPH - 0xE1AE: 0x8CB0, //CJK UNIFIED IDEOGRAPH - 0xE1AF: 0x53EC, //CJK UNIFIED IDEOGRAPH - 0xE1B0: 0x562F, //CJK UNIFIED IDEOGRAPH - 0xE1B1: 0x5851, //CJK UNIFIED IDEOGRAPH - 0xE1B2: 0x5BB5, //CJK UNIFIED IDEOGRAPH - 0xE1B3: 0x5C0F, //CJK UNIFIED IDEOGRAPH - 0xE1B4: 0x5C11, //CJK UNIFIED IDEOGRAPH - 0xE1B5: 0x5DE2, //CJK UNIFIED IDEOGRAPH - 0xE1B6: 0x6240, //CJK UNIFIED IDEOGRAPH - 0xE1B7: 0x6383, //CJK UNIFIED IDEOGRAPH - 0xE1B8: 0x6414, //CJK UNIFIED IDEOGRAPH - 0xE1B9: 0x662D, //CJK UNIFIED IDEOGRAPH - 0xE1BA: 0x68B3, //CJK UNIFIED IDEOGRAPH - 0xE1BB: 0x6CBC, //CJK UNIFIED IDEOGRAPH - 0xE1BC: 0x6D88, //CJK UNIFIED IDEOGRAPH - 0xE1BD: 0x6EAF, //CJK UNIFIED IDEOGRAPH - 0xE1BE: 0x701F, //CJK UNIFIED IDEOGRAPH - 0xE1BF: 0x70A4, //CJK UNIFIED IDEOGRAPH - 0xE1C0: 0x71D2, //CJK UNIFIED IDEOGRAPH - 0xE1C1: 0x7526, //CJK UNIFIED IDEOGRAPH - 0xE1C2: 0x758F, //CJK UNIFIED IDEOGRAPH - 0xE1C3: 0x758E, //CJK UNIFIED IDEOGRAPH - 0xE1C4: 0x7619, //CJK UNIFIED IDEOGRAPH - 0xE1C5: 0x7B11, //CJK UNIFIED IDEOGRAPH - 0xE1C6: 0x7BE0, //CJK UNIFIED IDEOGRAPH - 0xE1C7: 0x7C2B, //CJK UNIFIED IDEOGRAPH - 0xE1C8: 0x7D20, //CJK UNIFIED IDEOGRAPH - 0xE1C9: 0x7D39, //CJK UNIFIED IDEOGRAPH - 0xE1CA: 0x852C, //CJK UNIFIED IDEOGRAPH - 0xE1CB: 0x856D, //CJK UNIFIED IDEOGRAPH - 0xE1CC: 0x8607, //CJK UNIFIED IDEOGRAPH - 0xE1CD: 0x8A34, //CJK UNIFIED IDEOGRAPH - 0xE1CE: 0x900D, //CJK UNIFIED IDEOGRAPH - 0xE1CF: 0x9061, //CJK UNIFIED IDEOGRAPH - 0xE1D0: 0x90B5, //CJK UNIFIED IDEOGRAPH - 0xE1D1: 0x92B7, //CJK UNIFIED IDEOGRAPH - 0xE1D2: 0x97F6, //CJK UNIFIED IDEOGRAPH - 0xE1D3: 0x9A37, //CJK UNIFIED IDEOGRAPH - 0xE1D4: 0x4FD7, //CJK UNIFIED IDEOGRAPH - 0xE1D5: 0x5C6C, //CJK UNIFIED IDEOGRAPH - 0xE1D6: 0x675F, //CJK UNIFIED IDEOGRAPH - 0xE1D7: 0x6D91, //CJK UNIFIED IDEOGRAPH - 0xE1D8: 0x7C9F, //CJK UNIFIED IDEOGRAPH - 0xE1D9: 0x7E8C, //CJK UNIFIED IDEOGRAPH - 0xE1DA: 0x8B16, //CJK UNIFIED IDEOGRAPH - 0xE1DB: 0x8D16, //CJK UNIFIED IDEOGRAPH - 0xE1DC: 0x901F, //CJK UNIFIED IDEOGRAPH - 0xE1DD: 0x5B6B, //CJK UNIFIED IDEOGRAPH - 0xE1DE: 0x5DFD, //CJK UNIFIED IDEOGRAPH - 0xE1DF: 0x640D, //CJK UNIFIED IDEOGRAPH - 0xE1E0: 0x84C0, //CJK UNIFIED IDEOGRAPH - 0xE1E1: 0x905C, //CJK UNIFIED IDEOGRAPH - 0xE1E2: 0x98E1, //CJK UNIFIED IDEOGRAPH - 0xE1E3: 0x7387, //CJK UNIFIED IDEOGRAPH - 0xE1E4: 0x5B8B, //CJK UNIFIED IDEOGRAPH - 0xE1E5: 0x609A, //CJK UNIFIED IDEOGRAPH - 0xE1E6: 0x677E, //CJK UNIFIED IDEOGRAPH - 0xE1E7: 0x6DDE, //CJK UNIFIED IDEOGRAPH - 0xE1E8: 0x8A1F, //CJK UNIFIED IDEOGRAPH - 0xE1E9: 0x8AA6, //CJK UNIFIED IDEOGRAPH - 0xE1EA: 0x9001, //CJK UNIFIED IDEOGRAPH - 0xE1EB: 0x980C, //CJK UNIFIED IDEOGRAPH - 0xE1EC: 0x5237, //CJK UNIFIED IDEOGRAPH - 0xE1ED: 0xF970, //CJK COMPATIBILITY IDEOGRAPH - 0xE1EE: 0x7051, //CJK UNIFIED IDEOGRAPH - 0xE1EF: 0x788E, //CJK UNIFIED IDEOGRAPH - 0xE1F0: 0x9396, //CJK UNIFIED IDEOGRAPH - 0xE1F1: 0x8870, //CJK UNIFIED IDEOGRAPH - 0xE1F2: 0x91D7, //CJK UNIFIED IDEOGRAPH - 0xE1F3: 0x4FEE, //CJK UNIFIED IDEOGRAPH - 0xE1F4: 0x53D7, //CJK UNIFIED IDEOGRAPH - 0xE1F5: 0x55FD, //CJK UNIFIED IDEOGRAPH - 0xE1F6: 0x56DA, //CJK UNIFIED IDEOGRAPH - 0xE1F7: 0x5782, //CJK UNIFIED IDEOGRAPH - 0xE1F8: 0x58FD, //CJK UNIFIED IDEOGRAPH - 0xE1F9: 0x5AC2, //CJK UNIFIED IDEOGRAPH - 0xE1FA: 0x5B88, //CJK UNIFIED IDEOGRAPH - 0xE1FB: 0x5CAB, //CJK UNIFIED IDEOGRAPH - 0xE1FC: 0x5CC0, //CJK UNIFIED IDEOGRAPH - 0xE1FD: 0x5E25, //CJK UNIFIED IDEOGRAPH - 0xE1FE: 0x6101, //CJK UNIFIED IDEOGRAPH - 0xE2A1: 0x620D, //CJK UNIFIED IDEOGRAPH - 0xE2A2: 0x624B, //CJK UNIFIED IDEOGRAPH - 0xE2A3: 0x6388, //CJK UNIFIED IDEOGRAPH - 0xE2A4: 0x641C, //CJK UNIFIED IDEOGRAPH - 0xE2A5: 0x6536, //CJK UNIFIED IDEOGRAPH - 0xE2A6: 0x6578, //CJK UNIFIED IDEOGRAPH - 0xE2A7: 0x6A39, //CJK UNIFIED IDEOGRAPH - 0xE2A8: 0x6B8A, //CJK UNIFIED IDEOGRAPH - 0xE2A9: 0x6C34, //CJK UNIFIED IDEOGRAPH - 0xE2AA: 0x6D19, //CJK UNIFIED IDEOGRAPH - 0xE2AB: 0x6F31, //CJK UNIFIED IDEOGRAPH - 0xE2AC: 0x71E7, //CJK UNIFIED IDEOGRAPH - 0xE2AD: 0x72E9, //CJK UNIFIED IDEOGRAPH - 0xE2AE: 0x7378, //CJK UNIFIED IDEOGRAPH - 0xE2AF: 0x7407, //CJK UNIFIED IDEOGRAPH - 0xE2B0: 0x74B2, //CJK UNIFIED IDEOGRAPH - 0xE2B1: 0x7626, //CJK UNIFIED IDEOGRAPH - 0xE2B2: 0x7761, //CJK UNIFIED IDEOGRAPH - 0xE2B3: 0x79C0, //CJK UNIFIED IDEOGRAPH - 0xE2B4: 0x7A57, //CJK UNIFIED IDEOGRAPH - 0xE2B5: 0x7AEA, //CJK UNIFIED IDEOGRAPH - 0xE2B6: 0x7CB9, //CJK UNIFIED IDEOGRAPH - 0xE2B7: 0x7D8F, //CJK UNIFIED IDEOGRAPH - 0xE2B8: 0x7DAC, //CJK UNIFIED IDEOGRAPH - 0xE2B9: 0x7E61, //CJK UNIFIED IDEOGRAPH - 0xE2BA: 0x7F9E, //CJK UNIFIED IDEOGRAPH - 0xE2BB: 0x8129, //CJK UNIFIED IDEOGRAPH - 0xE2BC: 0x8331, //CJK UNIFIED IDEOGRAPH - 0xE2BD: 0x8490, //CJK UNIFIED IDEOGRAPH - 0xE2BE: 0x84DA, //CJK UNIFIED IDEOGRAPH - 0xE2BF: 0x85EA, //CJK UNIFIED IDEOGRAPH - 0xE2C0: 0x8896, //CJK UNIFIED IDEOGRAPH - 0xE2C1: 0x8AB0, //CJK UNIFIED IDEOGRAPH - 0xE2C2: 0x8B90, //CJK UNIFIED IDEOGRAPH - 0xE2C3: 0x8F38, //CJK UNIFIED IDEOGRAPH - 0xE2C4: 0x9042, //CJK UNIFIED IDEOGRAPH - 0xE2C5: 0x9083, //CJK UNIFIED IDEOGRAPH - 0xE2C6: 0x916C, //CJK UNIFIED IDEOGRAPH - 0xE2C7: 0x9296, //CJK UNIFIED IDEOGRAPH - 0xE2C8: 0x92B9, //CJK UNIFIED IDEOGRAPH - 0xE2C9: 0x968B, //CJK UNIFIED IDEOGRAPH - 0xE2CA: 0x96A7, //CJK UNIFIED IDEOGRAPH - 0xE2CB: 0x96A8, //CJK UNIFIED IDEOGRAPH - 0xE2CC: 0x96D6, //CJK UNIFIED IDEOGRAPH - 0xE2CD: 0x9700, //CJK UNIFIED IDEOGRAPH - 0xE2CE: 0x9808, //CJK UNIFIED IDEOGRAPH - 0xE2CF: 0x9996, //CJK UNIFIED IDEOGRAPH - 0xE2D0: 0x9AD3, //CJK UNIFIED IDEOGRAPH - 0xE2D1: 0x9B1A, //CJK UNIFIED IDEOGRAPH - 0xE2D2: 0x53D4, //CJK UNIFIED IDEOGRAPH - 0xE2D3: 0x587E, //CJK UNIFIED IDEOGRAPH - 0xE2D4: 0x5919, //CJK UNIFIED IDEOGRAPH - 0xE2D5: 0x5B70, //CJK UNIFIED IDEOGRAPH - 0xE2D6: 0x5BBF, //CJK UNIFIED IDEOGRAPH - 0xE2D7: 0x6DD1, //CJK UNIFIED IDEOGRAPH - 0xE2D8: 0x6F5A, //CJK UNIFIED IDEOGRAPH - 0xE2D9: 0x719F, //CJK UNIFIED IDEOGRAPH - 0xE2DA: 0x7421, //CJK UNIFIED IDEOGRAPH - 0xE2DB: 0x74B9, //CJK UNIFIED IDEOGRAPH - 0xE2DC: 0x8085, //CJK UNIFIED IDEOGRAPH - 0xE2DD: 0x83FD, //CJK UNIFIED IDEOGRAPH - 0xE2DE: 0x5DE1, //CJK UNIFIED IDEOGRAPH - 0xE2DF: 0x5F87, //CJK UNIFIED IDEOGRAPH - 0xE2E0: 0x5FAA, //CJK UNIFIED IDEOGRAPH - 0xE2E1: 0x6042, //CJK UNIFIED IDEOGRAPH - 0xE2E2: 0x65EC, //CJK UNIFIED IDEOGRAPH - 0xE2E3: 0x6812, //CJK UNIFIED IDEOGRAPH - 0xE2E4: 0x696F, //CJK UNIFIED IDEOGRAPH - 0xE2E5: 0x6A53, //CJK UNIFIED IDEOGRAPH - 0xE2E6: 0x6B89, //CJK UNIFIED IDEOGRAPH - 0xE2E7: 0x6D35, //CJK UNIFIED IDEOGRAPH - 0xE2E8: 0x6DF3, //CJK UNIFIED IDEOGRAPH - 0xE2E9: 0x73E3, //CJK UNIFIED IDEOGRAPH - 0xE2EA: 0x76FE, //CJK UNIFIED IDEOGRAPH - 0xE2EB: 0x77AC, //CJK UNIFIED IDEOGRAPH - 0xE2EC: 0x7B4D, //CJK UNIFIED IDEOGRAPH - 0xE2ED: 0x7D14, //CJK UNIFIED IDEOGRAPH - 0xE2EE: 0x8123, //CJK UNIFIED IDEOGRAPH - 0xE2EF: 0x821C, //CJK UNIFIED IDEOGRAPH - 0xE2F0: 0x8340, //CJK UNIFIED IDEOGRAPH - 0xE2F1: 0x84F4, //CJK UNIFIED IDEOGRAPH - 0xE2F2: 0x8563, //CJK UNIFIED IDEOGRAPH - 0xE2F3: 0x8A62, //CJK UNIFIED IDEOGRAPH - 0xE2F4: 0x8AC4, //CJK UNIFIED IDEOGRAPH - 0xE2F5: 0x9187, //CJK UNIFIED IDEOGRAPH - 0xE2F6: 0x931E, //CJK UNIFIED IDEOGRAPH - 0xE2F7: 0x9806, //CJK UNIFIED IDEOGRAPH - 0xE2F8: 0x99B4, //CJK UNIFIED IDEOGRAPH - 0xE2F9: 0x620C, //CJK UNIFIED IDEOGRAPH - 0xE2FA: 0x8853, //CJK UNIFIED IDEOGRAPH - 0xE2FB: 0x8FF0, //CJK UNIFIED IDEOGRAPH - 0xE2FC: 0x9265, //CJK UNIFIED IDEOGRAPH - 0xE2FD: 0x5D07, //CJK UNIFIED IDEOGRAPH - 0xE2FE: 0x5D27, //CJK UNIFIED IDEOGRAPH - 0xE3A1: 0x5D69, //CJK UNIFIED IDEOGRAPH - 0xE3A2: 0x745F, //CJK UNIFIED IDEOGRAPH - 0xE3A3: 0x819D, //CJK UNIFIED IDEOGRAPH - 0xE3A4: 0x8768, //CJK UNIFIED IDEOGRAPH - 0xE3A5: 0x6FD5, //CJK UNIFIED IDEOGRAPH - 0xE3A6: 0x62FE, //CJK UNIFIED IDEOGRAPH - 0xE3A7: 0x7FD2, //CJK UNIFIED IDEOGRAPH - 0xE3A8: 0x8936, //CJK UNIFIED IDEOGRAPH - 0xE3A9: 0x8972, //CJK UNIFIED IDEOGRAPH - 0xE3AA: 0x4E1E, //CJK UNIFIED IDEOGRAPH - 0xE3AB: 0x4E58, //CJK UNIFIED IDEOGRAPH - 0xE3AC: 0x50E7, //CJK UNIFIED IDEOGRAPH - 0xE3AD: 0x52DD, //CJK UNIFIED IDEOGRAPH - 0xE3AE: 0x5347, //CJK UNIFIED IDEOGRAPH - 0xE3AF: 0x627F, //CJK UNIFIED IDEOGRAPH - 0xE3B0: 0x6607, //CJK UNIFIED IDEOGRAPH - 0xE3B1: 0x7E69, //CJK UNIFIED IDEOGRAPH - 0xE3B2: 0x8805, //CJK UNIFIED IDEOGRAPH - 0xE3B3: 0x965E, //CJK UNIFIED IDEOGRAPH - 0xE3B4: 0x4F8D, //CJK UNIFIED IDEOGRAPH - 0xE3B5: 0x5319, //CJK UNIFIED IDEOGRAPH - 0xE3B6: 0x5636, //CJK UNIFIED IDEOGRAPH - 0xE3B7: 0x59CB, //CJK UNIFIED IDEOGRAPH - 0xE3B8: 0x5AA4, //CJK UNIFIED IDEOGRAPH - 0xE3B9: 0x5C38, //CJK UNIFIED IDEOGRAPH - 0xE3BA: 0x5C4E, //CJK UNIFIED IDEOGRAPH - 0xE3BB: 0x5C4D, //CJK UNIFIED IDEOGRAPH - 0xE3BC: 0x5E02, //CJK UNIFIED IDEOGRAPH - 0xE3BD: 0x5F11, //CJK UNIFIED IDEOGRAPH - 0xE3BE: 0x6043, //CJK UNIFIED IDEOGRAPH - 0xE3BF: 0x65BD, //CJK UNIFIED IDEOGRAPH - 0xE3C0: 0x662F, //CJK UNIFIED IDEOGRAPH - 0xE3C1: 0x6642, //CJK UNIFIED IDEOGRAPH - 0xE3C2: 0x67BE, //CJK UNIFIED IDEOGRAPH - 0xE3C3: 0x67F4, //CJK UNIFIED IDEOGRAPH - 0xE3C4: 0x731C, //CJK UNIFIED IDEOGRAPH - 0xE3C5: 0x77E2, //CJK UNIFIED IDEOGRAPH - 0xE3C6: 0x793A, //CJK UNIFIED IDEOGRAPH - 0xE3C7: 0x7FC5, //CJK UNIFIED IDEOGRAPH - 0xE3C8: 0x8494, //CJK UNIFIED IDEOGRAPH - 0xE3C9: 0x84CD, //CJK UNIFIED IDEOGRAPH - 0xE3CA: 0x8996, //CJK UNIFIED IDEOGRAPH - 0xE3CB: 0x8A66, //CJK UNIFIED IDEOGRAPH - 0xE3CC: 0x8A69, //CJK UNIFIED IDEOGRAPH - 0xE3CD: 0x8AE1, //CJK UNIFIED IDEOGRAPH - 0xE3CE: 0x8C55, //CJK UNIFIED IDEOGRAPH - 0xE3CF: 0x8C7A, //CJK UNIFIED IDEOGRAPH - 0xE3D0: 0x57F4, //CJK UNIFIED IDEOGRAPH - 0xE3D1: 0x5BD4, //CJK UNIFIED IDEOGRAPH - 0xE3D2: 0x5F0F, //CJK UNIFIED IDEOGRAPH - 0xE3D3: 0x606F, //CJK UNIFIED IDEOGRAPH - 0xE3D4: 0x62ED, //CJK UNIFIED IDEOGRAPH - 0xE3D5: 0x690D, //CJK UNIFIED IDEOGRAPH - 0xE3D6: 0x6B96, //CJK UNIFIED IDEOGRAPH - 0xE3D7: 0x6E5C, //CJK UNIFIED IDEOGRAPH - 0xE3D8: 0x7184, //CJK UNIFIED IDEOGRAPH - 0xE3D9: 0x7BD2, //CJK UNIFIED IDEOGRAPH - 0xE3DA: 0x8755, //CJK UNIFIED IDEOGRAPH - 0xE3DB: 0x8B58, //CJK UNIFIED IDEOGRAPH - 0xE3DC: 0x8EFE, //CJK UNIFIED IDEOGRAPH - 0xE3DD: 0x98DF, //CJK UNIFIED IDEOGRAPH - 0xE3DE: 0x98FE, //CJK UNIFIED IDEOGRAPH - 0xE3DF: 0x4F38, //CJK UNIFIED IDEOGRAPH - 0xE3E0: 0x4F81, //CJK UNIFIED IDEOGRAPH - 0xE3E1: 0x4FE1, //CJK UNIFIED IDEOGRAPH - 0xE3E2: 0x547B, //CJK UNIFIED IDEOGRAPH - 0xE3E3: 0x5A20, //CJK UNIFIED IDEOGRAPH - 0xE3E4: 0x5BB8, //CJK UNIFIED IDEOGRAPH - 0xE3E5: 0x613C, //CJK UNIFIED IDEOGRAPH - 0xE3E6: 0x65B0, //CJK UNIFIED IDEOGRAPH - 0xE3E7: 0x6668, //CJK UNIFIED IDEOGRAPH - 0xE3E8: 0x71FC, //CJK UNIFIED IDEOGRAPH - 0xE3E9: 0x7533, //CJK UNIFIED IDEOGRAPH - 0xE3EA: 0x795E, //CJK UNIFIED IDEOGRAPH - 0xE3EB: 0x7D33, //CJK UNIFIED IDEOGRAPH - 0xE3EC: 0x814E, //CJK UNIFIED IDEOGRAPH - 0xE3ED: 0x81E3, //CJK UNIFIED IDEOGRAPH - 0xE3EE: 0x8398, //CJK UNIFIED IDEOGRAPH - 0xE3EF: 0x85AA, //CJK UNIFIED IDEOGRAPH - 0xE3F0: 0x85CE, //CJK UNIFIED IDEOGRAPH - 0xE3F1: 0x8703, //CJK UNIFIED IDEOGRAPH - 0xE3F2: 0x8A0A, //CJK UNIFIED IDEOGRAPH - 0xE3F3: 0x8EAB, //CJK UNIFIED IDEOGRAPH - 0xE3F4: 0x8F9B, //CJK UNIFIED IDEOGRAPH - 0xE3F5: 0xF971, //CJK COMPATIBILITY IDEOGRAPH - 0xE3F6: 0x8FC5, //CJK UNIFIED IDEOGRAPH - 0xE3F7: 0x5931, //CJK UNIFIED IDEOGRAPH - 0xE3F8: 0x5BA4, //CJK UNIFIED IDEOGRAPH - 0xE3F9: 0x5BE6, //CJK UNIFIED IDEOGRAPH - 0xE3FA: 0x6089, //CJK UNIFIED IDEOGRAPH - 0xE3FB: 0x5BE9, //CJK UNIFIED IDEOGRAPH - 0xE3FC: 0x5C0B, //CJK UNIFIED IDEOGRAPH - 0xE3FD: 0x5FC3, //CJK UNIFIED IDEOGRAPH - 0xE3FE: 0x6C81, //CJK UNIFIED IDEOGRAPH - 0xE4A1: 0xF972, //CJK COMPATIBILITY IDEOGRAPH - 0xE4A2: 0x6DF1, //CJK UNIFIED IDEOGRAPH - 0xE4A3: 0x700B, //CJK UNIFIED IDEOGRAPH - 0xE4A4: 0x751A, //CJK UNIFIED IDEOGRAPH - 0xE4A5: 0x82AF, //CJK UNIFIED IDEOGRAPH - 0xE4A6: 0x8AF6, //CJK UNIFIED IDEOGRAPH - 0xE4A7: 0x4EC0, //CJK UNIFIED IDEOGRAPH - 0xE4A8: 0x5341, //CJK UNIFIED IDEOGRAPH - 0xE4A9: 0xF973, //CJK COMPATIBILITY IDEOGRAPH - 0xE4AA: 0x96D9, //CJK UNIFIED IDEOGRAPH - 0xE4AB: 0x6C0F, //CJK UNIFIED IDEOGRAPH - 0xE4AC: 0x4E9E, //CJK UNIFIED IDEOGRAPH - 0xE4AD: 0x4FC4, //CJK UNIFIED IDEOGRAPH - 0xE4AE: 0x5152, //CJK UNIFIED IDEOGRAPH - 0xE4AF: 0x555E, //CJK UNIFIED IDEOGRAPH - 0xE4B0: 0x5A25, //CJK UNIFIED IDEOGRAPH - 0xE4B1: 0x5CE8, //CJK UNIFIED IDEOGRAPH - 0xE4B2: 0x6211, //CJK UNIFIED IDEOGRAPH - 0xE4B3: 0x7259, //CJK UNIFIED IDEOGRAPH - 0xE4B4: 0x82BD, //CJK UNIFIED IDEOGRAPH - 0xE4B5: 0x83AA, //CJK UNIFIED IDEOGRAPH - 0xE4B6: 0x86FE, //CJK UNIFIED IDEOGRAPH - 0xE4B7: 0x8859, //CJK UNIFIED IDEOGRAPH - 0xE4B8: 0x8A1D, //CJK UNIFIED IDEOGRAPH - 0xE4B9: 0x963F, //CJK UNIFIED IDEOGRAPH - 0xE4BA: 0x96C5, //CJK UNIFIED IDEOGRAPH - 0xE4BB: 0x9913, //CJK UNIFIED IDEOGRAPH - 0xE4BC: 0x9D09, //CJK UNIFIED IDEOGRAPH - 0xE4BD: 0x9D5D, //CJK UNIFIED IDEOGRAPH - 0xE4BE: 0x580A, //CJK UNIFIED IDEOGRAPH - 0xE4BF: 0x5CB3, //CJK UNIFIED IDEOGRAPH - 0xE4C0: 0x5DBD, //CJK UNIFIED IDEOGRAPH - 0xE4C1: 0x5E44, //CJK UNIFIED IDEOGRAPH - 0xE4C2: 0x60E1, //CJK UNIFIED IDEOGRAPH - 0xE4C3: 0x6115, //CJK UNIFIED IDEOGRAPH - 0xE4C4: 0x63E1, //CJK UNIFIED IDEOGRAPH - 0xE4C5: 0x6A02, //CJK UNIFIED IDEOGRAPH - 0xE4C6: 0x6E25, //CJK UNIFIED IDEOGRAPH - 0xE4C7: 0x9102, //CJK UNIFIED IDEOGRAPH - 0xE4C8: 0x9354, //CJK UNIFIED IDEOGRAPH - 0xE4C9: 0x984E, //CJK UNIFIED IDEOGRAPH - 0xE4CA: 0x9C10, //CJK UNIFIED IDEOGRAPH - 0xE4CB: 0x9F77, //CJK UNIFIED IDEOGRAPH - 0xE4CC: 0x5B89, //CJK UNIFIED IDEOGRAPH - 0xE4CD: 0x5CB8, //CJK UNIFIED IDEOGRAPH - 0xE4CE: 0x6309, //CJK UNIFIED IDEOGRAPH - 0xE4CF: 0x664F, //CJK UNIFIED IDEOGRAPH - 0xE4D0: 0x6848, //CJK UNIFIED IDEOGRAPH - 0xE4D1: 0x773C, //CJK UNIFIED IDEOGRAPH - 0xE4D2: 0x96C1, //CJK UNIFIED IDEOGRAPH - 0xE4D3: 0x978D, //CJK UNIFIED IDEOGRAPH - 0xE4D4: 0x9854, //CJK UNIFIED IDEOGRAPH - 0xE4D5: 0x9B9F, //CJK UNIFIED IDEOGRAPH - 0xE4D6: 0x65A1, //CJK UNIFIED IDEOGRAPH - 0xE4D7: 0x8B01, //CJK UNIFIED IDEOGRAPH - 0xE4D8: 0x8ECB, //CJK UNIFIED IDEOGRAPH - 0xE4D9: 0x95BC, //CJK UNIFIED IDEOGRAPH - 0xE4DA: 0x5535, //CJK UNIFIED IDEOGRAPH - 0xE4DB: 0x5CA9, //CJK UNIFIED IDEOGRAPH - 0xE4DC: 0x5DD6, //CJK UNIFIED IDEOGRAPH - 0xE4DD: 0x5EB5, //CJK UNIFIED IDEOGRAPH - 0xE4DE: 0x6697, //CJK UNIFIED IDEOGRAPH - 0xE4DF: 0x764C, //CJK UNIFIED IDEOGRAPH - 0xE4E0: 0x83F4, //CJK UNIFIED IDEOGRAPH - 0xE4E1: 0x95C7, //CJK UNIFIED IDEOGRAPH - 0xE4E2: 0x58D3, //CJK UNIFIED IDEOGRAPH - 0xE4E3: 0x62BC, //CJK UNIFIED IDEOGRAPH - 0xE4E4: 0x72CE, //CJK UNIFIED IDEOGRAPH - 0xE4E5: 0x9D28, //CJK UNIFIED IDEOGRAPH - 0xE4E6: 0x4EF0, //CJK UNIFIED IDEOGRAPH - 0xE4E7: 0x592E, //CJK UNIFIED IDEOGRAPH - 0xE4E8: 0x600F, //CJK UNIFIED IDEOGRAPH - 0xE4E9: 0x663B, //CJK UNIFIED IDEOGRAPH - 0xE4EA: 0x6B83, //CJK UNIFIED IDEOGRAPH - 0xE4EB: 0x79E7, //CJK UNIFIED IDEOGRAPH - 0xE4EC: 0x9D26, //CJK UNIFIED IDEOGRAPH - 0xE4ED: 0x5393, //CJK UNIFIED IDEOGRAPH - 0xE4EE: 0x54C0, //CJK UNIFIED IDEOGRAPH - 0xE4EF: 0x57C3, //CJK UNIFIED IDEOGRAPH - 0xE4F0: 0x5D16, //CJK UNIFIED IDEOGRAPH - 0xE4F1: 0x611B, //CJK UNIFIED IDEOGRAPH - 0xE4F2: 0x66D6, //CJK UNIFIED IDEOGRAPH - 0xE4F3: 0x6DAF, //CJK UNIFIED IDEOGRAPH - 0xE4F4: 0x788D, //CJK UNIFIED IDEOGRAPH - 0xE4F5: 0x827E, //CJK UNIFIED IDEOGRAPH - 0xE4F6: 0x9698, //CJK UNIFIED IDEOGRAPH - 0xE4F7: 0x9744, //CJK UNIFIED IDEOGRAPH - 0xE4F8: 0x5384, //CJK UNIFIED IDEOGRAPH - 0xE4F9: 0x627C, //CJK UNIFIED IDEOGRAPH - 0xE4FA: 0x6396, //CJK UNIFIED IDEOGRAPH - 0xE4FB: 0x6DB2, //CJK UNIFIED IDEOGRAPH - 0xE4FC: 0x7E0A, //CJK UNIFIED IDEOGRAPH - 0xE4FD: 0x814B, //CJK UNIFIED IDEOGRAPH - 0xE4FE: 0x984D, //CJK UNIFIED IDEOGRAPH - 0xE5A1: 0x6AFB, //CJK UNIFIED IDEOGRAPH - 0xE5A2: 0x7F4C, //CJK UNIFIED IDEOGRAPH - 0xE5A3: 0x9DAF, //CJK UNIFIED IDEOGRAPH - 0xE5A4: 0x9E1A, //CJK UNIFIED IDEOGRAPH - 0xE5A5: 0x4E5F, //CJK UNIFIED IDEOGRAPH - 0xE5A6: 0x503B, //CJK UNIFIED IDEOGRAPH - 0xE5A7: 0x51B6, //CJK UNIFIED IDEOGRAPH - 0xE5A8: 0x591C, //CJK UNIFIED IDEOGRAPH - 0xE5A9: 0x60F9, //CJK UNIFIED IDEOGRAPH - 0xE5AA: 0x63F6, //CJK UNIFIED IDEOGRAPH - 0xE5AB: 0x6930, //CJK UNIFIED IDEOGRAPH - 0xE5AC: 0x723A, //CJK UNIFIED IDEOGRAPH - 0xE5AD: 0x8036, //CJK UNIFIED IDEOGRAPH - 0xE5AE: 0xF974, //CJK COMPATIBILITY IDEOGRAPH - 0xE5AF: 0x91CE, //CJK UNIFIED IDEOGRAPH - 0xE5B0: 0x5F31, //CJK UNIFIED IDEOGRAPH - 0xE5B1: 0xF975, //CJK COMPATIBILITY IDEOGRAPH - 0xE5B2: 0xF976, //CJK COMPATIBILITY IDEOGRAPH - 0xE5B3: 0x7D04, //CJK UNIFIED IDEOGRAPH - 0xE5B4: 0x82E5, //CJK UNIFIED IDEOGRAPH - 0xE5B5: 0x846F, //CJK UNIFIED IDEOGRAPH - 0xE5B6: 0x84BB, //CJK UNIFIED IDEOGRAPH - 0xE5B7: 0x85E5, //CJK UNIFIED IDEOGRAPH - 0xE5B8: 0x8E8D, //CJK UNIFIED IDEOGRAPH - 0xE5B9: 0xF977, //CJK COMPATIBILITY IDEOGRAPH - 0xE5BA: 0x4F6F, //CJK UNIFIED IDEOGRAPH - 0xE5BB: 0xF978, //CJK COMPATIBILITY IDEOGRAPH - 0xE5BC: 0xF979, //CJK COMPATIBILITY IDEOGRAPH - 0xE5BD: 0x58E4, //CJK UNIFIED IDEOGRAPH - 0xE5BE: 0x5B43, //CJK UNIFIED IDEOGRAPH - 0xE5BF: 0x6059, //CJK UNIFIED IDEOGRAPH - 0xE5C0: 0x63DA, //CJK UNIFIED IDEOGRAPH - 0xE5C1: 0x6518, //CJK UNIFIED IDEOGRAPH - 0xE5C2: 0x656D, //CJK UNIFIED IDEOGRAPH - 0xE5C3: 0x6698, //CJK UNIFIED IDEOGRAPH - 0xE5C4: 0xF97A, //CJK COMPATIBILITY IDEOGRAPH - 0xE5C5: 0x694A, //CJK UNIFIED IDEOGRAPH - 0xE5C6: 0x6A23, //CJK UNIFIED IDEOGRAPH - 0xE5C7: 0x6D0B, //CJK UNIFIED IDEOGRAPH - 0xE5C8: 0x7001, //CJK UNIFIED IDEOGRAPH - 0xE5C9: 0x716C, //CJK UNIFIED IDEOGRAPH - 0xE5CA: 0x75D2, //CJK UNIFIED IDEOGRAPH - 0xE5CB: 0x760D, //CJK UNIFIED IDEOGRAPH - 0xE5CC: 0x79B3, //CJK UNIFIED IDEOGRAPH - 0xE5CD: 0x7A70, //CJK UNIFIED IDEOGRAPH - 0xE5CE: 0xF97B, //CJK COMPATIBILITY IDEOGRAPH - 0xE5CF: 0x7F8A, //CJK UNIFIED IDEOGRAPH - 0xE5D0: 0xF97C, //CJK COMPATIBILITY IDEOGRAPH - 0xE5D1: 0x8944, //CJK UNIFIED IDEOGRAPH - 0xE5D2: 0xF97D, //CJK COMPATIBILITY IDEOGRAPH - 0xE5D3: 0x8B93, //CJK UNIFIED IDEOGRAPH - 0xE5D4: 0x91C0, //CJK UNIFIED IDEOGRAPH - 0xE5D5: 0x967D, //CJK UNIFIED IDEOGRAPH - 0xE5D6: 0xF97E, //CJK COMPATIBILITY IDEOGRAPH - 0xE5D7: 0x990A, //CJK UNIFIED IDEOGRAPH - 0xE5D8: 0x5704, //CJK UNIFIED IDEOGRAPH - 0xE5D9: 0x5FA1, //CJK UNIFIED IDEOGRAPH - 0xE5DA: 0x65BC, //CJK UNIFIED IDEOGRAPH - 0xE5DB: 0x6F01, //CJK UNIFIED IDEOGRAPH - 0xE5DC: 0x7600, //CJK UNIFIED IDEOGRAPH - 0xE5DD: 0x79A6, //CJK UNIFIED IDEOGRAPH - 0xE5DE: 0x8A9E, //CJK UNIFIED IDEOGRAPH - 0xE5DF: 0x99AD, //CJK UNIFIED IDEOGRAPH - 0xE5E0: 0x9B5A, //CJK UNIFIED IDEOGRAPH - 0xE5E1: 0x9F6C, //CJK UNIFIED IDEOGRAPH - 0xE5E2: 0x5104, //CJK UNIFIED IDEOGRAPH - 0xE5E3: 0x61B6, //CJK UNIFIED IDEOGRAPH - 0xE5E4: 0x6291, //CJK UNIFIED IDEOGRAPH - 0xE5E5: 0x6A8D, //CJK UNIFIED IDEOGRAPH - 0xE5E6: 0x81C6, //CJK UNIFIED IDEOGRAPH - 0xE5E7: 0x5043, //CJK UNIFIED IDEOGRAPH - 0xE5E8: 0x5830, //CJK UNIFIED IDEOGRAPH - 0xE5E9: 0x5F66, //CJK UNIFIED IDEOGRAPH - 0xE5EA: 0x7109, //CJK UNIFIED IDEOGRAPH - 0xE5EB: 0x8A00, //CJK UNIFIED IDEOGRAPH - 0xE5EC: 0x8AFA, //CJK UNIFIED IDEOGRAPH - 0xE5ED: 0x5B7C, //CJK UNIFIED IDEOGRAPH - 0xE5EE: 0x8616, //CJK UNIFIED IDEOGRAPH - 0xE5EF: 0x4FFA, //CJK UNIFIED IDEOGRAPH - 0xE5F0: 0x513C, //CJK UNIFIED IDEOGRAPH - 0xE5F1: 0x56B4, //CJK UNIFIED IDEOGRAPH - 0xE5F2: 0x5944, //CJK UNIFIED IDEOGRAPH - 0xE5F3: 0x63A9, //CJK UNIFIED IDEOGRAPH - 0xE5F4: 0x6DF9, //CJK UNIFIED IDEOGRAPH - 0xE5F5: 0x5DAA, //CJK UNIFIED IDEOGRAPH - 0xE5F6: 0x696D, //CJK UNIFIED IDEOGRAPH - 0xE5F7: 0x5186, //CJK UNIFIED IDEOGRAPH - 0xE5F8: 0x4E88, //CJK UNIFIED IDEOGRAPH - 0xE5F9: 0x4F59, //CJK UNIFIED IDEOGRAPH - 0xE5FA: 0xF97F, //CJK COMPATIBILITY IDEOGRAPH - 0xE5FB: 0xF980, //CJK COMPATIBILITY IDEOGRAPH - 0xE5FC: 0xF981, //CJK COMPATIBILITY IDEOGRAPH - 0xE5FD: 0x5982, //CJK UNIFIED IDEOGRAPH - 0xE5FE: 0xF982, //CJK COMPATIBILITY IDEOGRAPH - 0xE6A1: 0xF983, //CJK COMPATIBILITY IDEOGRAPH - 0xE6A2: 0x6B5F, //CJK UNIFIED IDEOGRAPH - 0xE6A3: 0x6C5D, //CJK UNIFIED IDEOGRAPH - 0xE6A4: 0xF984, //CJK COMPATIBILITY IDEOGRAPH - 0xE6A5: 0x74B5, //CJK UNIFIED IDEOGRAPH - 0xE6A6: 0x7916, //CJK UNIFIED IDEOGRAPH - 0xE6A7: 0xF985, //CJK COMPATIBILITY IDEOGRAPH - 0xE6A8: 0x8207, //CJK UNIFIED IDEOGRAPH - 0xE6A9: 0x8245, //CJK UNIFIED IDEOGRAPH - 0xE6AA: 0x8339, //CJK UNIFIED IDEOGRAPH - 0xE6AB: 0x8F3F, //CJK UNIFIED IDEOGRAPH - 0xE6AC: 0x8F5D, //CJK UNIFIED IDEOGRAPH - 0xE6AD: 0xF986, //CJK COMPATIBILITY IDEOGRAPH - 0xE6AE: 0x9918, //CJK UNIFIED IDEOGRAPH - 0xE6AF: 0xF987, //CJK COMPATIBILITY IDEOGRAPH - 0xE6B0: 0xF988, //CJK COMPATIBILITY IDEOGRAPH - 0xE6B1: 0xF989, //CJK COMPATIBILITY IDEOGRAPH - 0xE6B2: 0x4EA6, //CJK UNIFIED IDEOGRAPH - 0xE6B3: 0xF98A, //CJK COMPATIBILITY IDEOGRAPH - 0xE6B4: 0x57DF, //CJK UNIFIED IDEOGRAPH - 0xE6B5: 0x5F79, //CJK UNIFIED IDEOGRAPH - 0xE6B6: 0x6613, //CJK UNIFIED IDEOGRAPH - 0xE6B7: 0xF98B, //CJK COMPATIBILITY IDEOGRAPH - 0xE6B8: 0xF98C, //CJK COMPATIBILITY IDEOGRAPH - 0xE6B9: 0x75AB, //CJK UNIFIED IDEOGRAPH - 0xE6BA: 0x7E79, //CJK UNIFIED IDEOGRAPH - 0xE6BB: 0x8B6F, //CJK UNIFIED IDEOGRAPH - 0xE6BC: 0xF98D, //CJK COMPATIBILITY IDEOGRAPH - 0xE6BD: 0x9006, //CJK UNIFIED IDEOGRAPH - 0xE6BE: 0x9A5B, //CJK UNIFIED IDEOGRAPH - 0xE6BF: 0x56A5, //CJK UNIFIED IDEOGRAPH - 0xE6C0: 0x5827, //CJK UNIFIED IDEOGRAPH - 0xE6C1: 0x59F8, //CJK UNIFIED IDEOGRAPH - 0xE6C2: 0x5A1F, //CJK UNIFIED IDEOGRAPH - 0xE6C3: 0x5BB4, //CJK UNIFIED IDEOGRAPH - 0xE6C4: 0xF98E, //CJK COMPATIBILITY IDEOGRAPH - 0xE6C5: 0x5EF6, //CJK UNIFIED IDEOGRAPH - 0xE6C6: 0xF98F, //CJK COMPATIBILITY IDEOGRAPH - 0xE6C7: 0xF990, //CJK COMPATIBILITY IDEOGRAPH - 0xE6C8: 0x6350, //CJK UNIFIED IDEOGRAPH - 0xE6C9: 0x633B, //CJK UNIFIED IDEOGRAPH - 0xE6CA: 0xF991, //CJK COMPATIBILITY IDEOGRAPH - 0xE6CB: 0x693D, //CJK UNIFIED IDEOGRAPH - 0xE6CC: 0x6C87, //CJK UNIFIED IDEOGRAPH - 0xE6CD: 0x6CBF, //CJK UNIFIED IDEOGRAPH - 0xE6CE: 0x6D8E, //CJK UNIFIED IDEOGRAPH - 0xE6CF: 0x6D93, //CJK UNIFIED IDEOGRAPH - 0xE6D0: 0x6DF5, //CJK UNIFIED IDEOGRAPH - 0xE6D1: 0x6F14, //CJK UNIFIED IDEOGRAPH - 0xE6D2: 0xF992, //CJK COMPATIBILITY IDEOGRAPH - 0xE6D3: 0x70DF, //CJK UNIFIED IDEOGRAPH - 0xE6D4: 0x7136, //CJK UNIFIED IDEOGRAPH - 0xE6D5: 0x7159, //CJK UNIFIED IDEOGRAPH - 0xE6D6: 0xF993, //CJK COMPATIBILITY IDEOGRAPH - 0xE6D7: 0x71C3, //CJK UNIFIED IDEOGRAPH - 0xE6D8: 0x71D5, //CJK UNIFIED IDEOGRAPH - 0xE6D9: 0xF994, //CJK COMPATIBILITY IDEOGRAPH - 0xE6DA: 0x784F, //CJK UNIFIED IDEOGRAPH - 0xE6DB: 0x786F, //CJK UNIFIED IDEOGRAPH - 0xE6DC: 0xF995, //CJK COMPATIBILITY IDEOGRAPH - 0xE6DD: 0x7B75, //CJK UNIFIED IDEOGRAPH - 0xE6DE: 0x7DE3, //CJK UNIFIED IDEOGRAPH - 0xE6DF: 0xF996, //CJK COMPATIBILITY IDEOGRAPH - 0xE6E0: 0x7E2F, //CJK UNIFIED IDEOGRAPH - 0xE6E1: 0xF997, //CJK COMPATIBILITY IDEOGRAPH - 0xE6E2: 0x884D, //CJK UNIFIED IDEOGRAPH - 0xE6E3: 0x8EDF, //CJK UNIFIED IDEOGRAPH - 0xE6E4: 0xF998, //CJK COMPATIBILITY IDEOGRAPH - 0xE6E5: 0xF999, //CJK COMPATIBILITY IDEOGRAPH - 0xE6E6: 0xF99A, //CJK COMPATIBILITY IDEOGRAPH - 0xE6E7: 0x925B, //CJK UNIFIED IDEOGRAPH - 0xE6E8: 0xF99B, //CJK COMPATIBILITY IDEOGRAPH - 0xE6E9: 0x9CF6, //CJK UNIFIED IDEOGRAPH - 0xE6EA: 0xF99C, //CJK COMPATIBILITY IDEOGRAPH - 0xE6EB: 0xF99D, //CJK COMPATIBILITY IDEOGRAPH - 0xE6EC: 0xF99E, //CJK COMPATIBILITY IDEOGRAPH - 0xE6ED: 0x6085, //CJK UNIFIED IDEOGRAPH - 0xE6EE: 0x6D85, //CJK UNIFIED IDEOGRAPH - 0xE6EF: 0xF99F, //CJK COMPATIBILITY IDEOGRAPH - 0xE6F0: 0x71B1, //CJK UNIFIED IDEOGRAPH - 0xE6F1: 0xF9A0, //CJK COMPATIBILITY IDEOGRAPH - 0xE6F2: 0xF9A1, //CJK COMPATIBILITY IDEOGRAPH - 0xE6F3: 0x95B1, //CJK UNIFIED IDEOGRAPH - 0xE6F4: 0x53AD, //CJK UNIFIED IDEOGRAPH - 0xE6F5: 0xF9A2, //CJK COMPATIBILITY IDEOGRAPH - 0xE6F6: 0xF9A3, //CJK COMPATIBILITY IDEOGRAPH - 0xE6F7: 0xF9A4, //CJK COMPATIBILITY IDEOGRAPH - 0xE6F8: 0x67D3, //CJK UNIFIED IDEOGRAPH - 0xE6F9: 0xF9A5, //CJK COMPATIBILITY IDEOGRAPH - 0xE6FA: 0x708E, //CJK UNIFIED IDEOGRAPH - 0xE6FB: 0x7130, //CJK UNIFIED IDEOGRAPH - 0xE6FC: 0x7430, //CJK UNIFIED IDEOGRAPH - 0xE6FD: 0x8276, //CJK UNIFIED IDEOGRAPH - 0xE6FE: 0x82D2, //CJK UNIFIED IDEOGRAPH - 0xE7A1: 0xF9A6, //CJK COMPATIBILITY IDEOGRAPH - 0xE7A2: 0x95BB, //CJK UNIFIED IDEOGRAPH - 0xE7A3: 0x9AE5, //CJK UNIFIED IDEOGRAPH - 0xE7A4: 0x9E7D, //CJK UNIFIED IDEOGRAPH - 0xE7A5: 0x66C4, //CJK UNIFIED IDEOGRAPH - 0xE7A6: 0xF9A7, //CJK COMPATIBILITY IDEOGRAPH - 0xE7A7: 0x71C1, //CJK UNIFIED IDEOGRAPH - 0xE7A8: 0x8449, //CJK UNIFIED IDEOGRAPH - 0xE7A9: 0xF9A8, //CJK COMPATIBILITY IDEOGRAPH - 0xE7AA: 0xF9A9, //CJK COMPATIBILITY IDEOGRAPH - 0xE7AB: 0x584B, //CJK UNIFIED IDEOGRAPH - 0xE7AC: 0xF9AA, //CJK COMPATIBILITY IDEOGRAPH - 0xE7AD: 0xF9AB, //CJK COMPATIBILITY IDEOGRAPH - 0xE7AE: 0x5DB8, //CJK UNIFIED IDEOGRAPH - 0xE7AF: 0x5F71, //CJK UNIFIED IDEOGRAPH - 0xE7B0: 0xF9AC, //CJK COMPATIBILITY IDEOGRAPH - 0xE7B1: 0x6620, //CJK UNIFIED IDEOGRAPH - 0xE7B2: 0x668E, //CJK UNIFIED IDEOGRAPH - 0xE7B3: 0x6979, //CJK UNIFIED IDEOGRAPH - 0xE7B4: 0x69AE, //CJK UNIFIED IDEOGRAPH - 0xE7B5: 0x6C38, //CJK UNIFIED IDEOGRAPH - 0xE7B6: 0x6CF3, //CJK UNIFIED IDEOGRAPH - 0xE7B7: 0x6E36, //CJK UNIFIED IDEOGRAPH - 0xE7B8: 0x6F41, //CJK UNIFIED IDEOGRAPH - 0xE7B9: 0x6FDA, //CJK UNIFIED IDEOGRAPH - 0xE7BA: 0x701B, //CJK UNIFIED IDEOGRAPH - 0xE7BB: 0x702F, //CJK UNIFIED IDEOGRAPH - 0xE7BC: 0x7150, //CJK UNIFIED IDEOGRAPH - 0xE7BD: 0x71DF, //CJK UNIFIED IDEOGRAPH - 0xE7BE: 0x7370, //CJK UNIFIED IDEOGRAPH - 0xE7BF: 0xF9AD, //CJK COMPATIBILITY IDEOGRAPH - 0xE7C0: 0x745B, //CJK UNIFIED IDEOGRAPH - 0xE7C1: 0xF9AE, //CJK COMPATIBILITY IDEOGRAPH - 0xE7C2: 0x74D4, //CJK UNIFIED IDEOGRAPH - 0xE7C3: 0x76C8, //CJK UNIFIED IDEOGRAPH - 0xE7C4: 0x7A4E, //CJK UNIFIED IDEOGRAPH - 0xE7C5: 0x7E93, //CJK UNIFIED IDEOGRAPH - 0xE7C6: 0xF9AF, //CJK COMPATIBILITY IDEOGRAPH - 0xE7C7: 0xF9B0, //CJK COMPATIBILITY IDEOGRAPH - 0xE7C8: 0x82F1, //CJK UNIFIED IDEOGRAPH - 0xE7C9: 0x8A60, //CJK UNIFIED IDEOGRAPH - 0xE7CA: 0x8FCE, //CJK UNIFIED IDEOGRAPH - 0xE7CB: 0xF9B1, //CJK COMPATIBILITY IDEOGRAPH - 0xE7CC: 0x9348, //CJK UNIFIED IDEOGRAPH - 0xE7CD: 0xF9B2, //CJK COMPATIBILITY IDEOGRAPH - 0xE7CE: 0x9719, //CJK UNIFIED IDEOGRAPH - 0xE7CF: 0xF9B3, //CJK COMPATIBILITY IDEOGRAPH - 0xE7D0: 0xF9B4, //CJK COMPATIBILITY IDEOGRAPH - 0xE7D1: 0x4E42, //CJK UNIFIED IDEOGRAPH - 0xE7D2: 0x502A, //CJK UNIFIED IDEOGRAPH - 0xE7D3: 0xF9B5, //CJK COMPATIBILITY IDEOGRAPH - 0xE7D4: 0x5208, //CJK UNIFIED IDEOGRAPH - 0xE7D5: 0x53E1, //CJK UNIFIED IDEOGRAPH - 0xE7D6: 0x66F3, //CJK UNIFIED IDEOGRAPH - 0xE7D7: 0x6C6D, //CJK UNIFIED IDEOGRAPH - 0xE7D8: 0x6FCA, //CJK UNIFIED IDEOGRAPH - 0xE7D9: 0x730A, //CJK UNIFIED IDEOGRAPH - 0xE7DA: 0x777F, //CJK UNIFIED IDEOGRAPH - 0xE7DB: 0x7A62, //CJK UNIFIED IDEOGRAPH - 0xE7DC: 0x82AE, //CJK UNIFIED IDEOGRAPH - 0xE7DD: 0x85DD, //CJK UNIFIED IDEOGRAPH - 0xE7DE: 0x8602, //CJK UNIFIED IDEOGRAPH - 0xE7DF: 0xF9B6, //CJK COMPATIBILITY IDEOGRAPH - 0xE7E0: 0x88D4, //CJK UNIFIED IDEOGRAPH - 0xE7E1: 0x8A63, //CJK UNIFIED IDEOGRAPH - 0xE7E2: 0x8B7D, //CJK UNIFIED IDEOGRAPH - 0xE7E3: 0x8C6B, //CJK UNIFIED IDEOGRAPH - 0xE7E4: 0xF9B7, //CJK COMPATIBILITY IDEOGRAPH - 0xE7E5: 0x92B3, //CJK UNIFIED IDEOGRAPH - 0xE7E6: 0xF9B8, //CJK COMPATIBILITY IDEOGRAPH - 0xE7E7: 0x9713, //CJK UNIFIED IDEOGRAPH - 0xE7E8: 0x9810, //CJK UNIFIED IDEOGRAPH - 0xE7E9: 0x4E94, //CJK UNIFIED IDEOGRAPH - 0xE7EA: 0x4F0D, //CJK UNIFIED IDEOGRAPH - 0xE7EB: 0x4FC9, //CJK UNIFIED IDEOGRAPH - 0xE7EC: 0x50B2, //CJK UNIFIED IDEOGRAPH - 0xE7ED: 0x5348, //CJK UNIFIED IDEOGRAPH - 0xE7EE: 0x543E, //CJK UNIFIED IDEOGRAPH - 0xE7EF: 0x5433, //CJK UNIFIED IDEOGRAPH - 0xE7F0: 0x55DA, //CJK UNIFIED IDEOGRAPH - 0xE7F1: 0x5862, //CJK UNIFIED IDEOGRAPH - 0xE7F2: 0x58BA, //CJK UNIFIED IDEOGRAPH - 0xE7F3: 0x5967, //CJK UNIFIED IDEOGRAPH - 0xE7F4: 0x5A1B, //CJK UNIFIED IDEOGRAPH - 0xE7F5: 0x5BE4, //CJK UNIFIED IDEOGRAPH - 0xE7F6: 0x609F, //CJK UNIFIED IDEOGRAPH - 0xE7F7: 0xF9B9, //CJK COMPATIBILITY IDEOGRAPH - 0xE7F8: 0x61CA, //CJK UNIFIED IDEOGRAPH - 0xE7F9: 0x6556, //CJK UNIFIED IDEOGRAPH - 0xE7FA: 0x65FF, //CJK UNIFIED IDEOGRAPH - 0xE7FB: 0x6664, //CJK UNIFIED IDEOGRAPH - 0xE7FC: 0x68A7, //CJK UNIFIED IDEOGRAPH - 0xE7FD: 0x6C5A, //CJK UNIFIED IDEOGRAPH - 0xE7FE: 0x6FB3, //CJK UNIFIED IDEOGRAPH - 0xE8A1: 0x70CF, //CJK UNIFIED IDEOGRAPH - 0xE8A2: 0x71AC, //CJK UNIFIED IDEOGRAPH - 0xE8A3: 0x7352, //CJK UNIFIED IDEOGRAPH - 0xE8A4: 0x7B7D, //CJK UNIFIED IDEOGRAPH - 0xE8A5: 0x8708, //CJK UNIFIED IDEOGRAPH - 0xE8A6: 0x8AA4, //CJK UNIFIED IDEOGRAPH - 0xE8A7: 0x9C32, //CJK UNIFIED IDEOGRAPH - 0xE8A8: 0x9F07, //CJK UNIFIED IDEOGRAPH - 0xE8A9: 0x5C4B, //CJK UNIFIED IDEOGRAPH - 0xE8AA: 0x6C83, //CJK UNIFIED IDEOGRAPH - 0xE8AB: 0x7344, //CJK UNIFIED IDEOGRAPH - 0xE8AC: 0x7389, //CJK UNIFIED IDEOGRAPH - 0xE8AD: 0x923A, //CJK UNIFIED IDEOGRAPH - 0xE8AE: 0x6EAB, //CJK UNIFIED IDEOGRAPH - 0xE8AF: 0x7465, //CJK UNIFIED IDEOGRAPH - 0xE8B0: 0x761F, //CJK UNIFIED IDEOGRAPH - 0xE8B1: 0x7A69, //CJK UNIFIED IDEOGRAPH - 0xE8B2: 0x7E15, //CJK UNIFIED IDEOGRAPH - 0xE8B3: 0x860A, //CJK UNIFIED IDEOGRAPH - 0xE8B4: 0x5140, //CJK UNIFIED IDEOGRAPH - 0xE8B5: 0x58C5, //CJK UNIFIED IDEOGRAPH - 0xE8B6: 0x64C1, //CJK UNIFIED IDEOGRAPH - 0xE8B7: 0x74EE, //CJK UNIFIED IDEOGRAPH - 0xE8B8: 0x7515, //CJK UNIFIED IDEOGRAPH - 0xE8B9: 0x7670, //CJK UNIFIED IDEOGRAPH - 0xE8BA: 0x7FC1, //CJK UNIFIED IDEOGRAPH - 0xE8BB: 0x9095, //CJK UNIFIED IDEOGRAPH - 0xE8BC: 0x96CD, //CJK UNIFIED IDEOGRAPH - 0xE8BD: 0x9954, //CJK UNIFIED IDEOGRAPH - 0xE8BE: 0x6E26, //CJK UNIFIED IDEOGRAPH - 0xE8BF: 0x74E6, //CJK UNIFIED IDEOGRAPH - 0xE8C0: 0x7AA9, //CJK UNIFIED IDEOGRAPH - 0xE8C1: 0x7AAA, //CJK UNIFIED IDEOGRAPH - 0xE8C2: 0x81E5, //CJK UNIFIED IDEOGRAPH - 0xE8C3: 0x86D9, //CJK UNIFIED IDEOGRAPH - 0xE8C4: 0x8778, //CJK UNIFIED IDEOGRAPH - 0xE8C5: 0x8A1B, //CJK UNIFIED IDEOGRAPH - 0xE8C6: 0x5A49, //CJK UNIFIED IDEOGRAPH - 0xE8C7: 0x5B8C, //CJK UNIFIED IDEOGRAPH - 0xE8C8: 0x5B9B, //CJK UNIFIED IDEOGRAPH - 0xE8C9: 0x68A1, //CJK UNIFIED IDEOGRAPH - 0xE8CA: 0x6900, //CJK UNIFIED IDEOGRAPH - 0xE8CB: 0x6D63, //CJK UNIFIED IDEOGRAPH - 0xE8CC: 0x73A9, //CJK UNIFIED IDEOGRAPH - 0xE8CD: 0x7413, //CJK UNIFIED IDEOGRAPH - 0xE8CE: 0x742C, //CJK UNIFIED IDEOGRAPH - 0xE8CF: 0x7897, //CJK UNIFIED IDEOGRAPH - 0xE8D0: 0x7DE9, //CJK UNIFIED IDEOGRAPH - 0xE8D1: 0x7FEB, //CJK UNIFIED IDEOGRAPH - 0xE8D2: 0x8118, //CJK UNIFIED IDEOGRAPH - 0xE8D3: 0x8155, //CJK UNIFIED IDEOGRAPH - 0xE8D4: 0x839E, //CJK UNIFIED IDEOGRAPH - 0xE8D5: 0x8C4C, //CJK UNIFIED IDEOGRAPH - 0xE8D6: 0x962E, //CJK UNIFIED IDEOGRAPH - 0xE8D7: 0x9811, //CJK UNIFIED IDEOGRAPH - 0xE8D8: 0x66F0, //CJK UNIFIED IDEOGRAPH - 0xE8D9: 0x5F80, //CJK UNIFIED IDEOGRAPH - 0xE8DA: 0x65FA, //CJK UNIFIED IDEOGRAPH - 0xE8DB: 0x6789, //CJK UNIFIED IDEOGRAPH - 0xE8DC: 0x6C6A, //CJK UNIFIED IDEOGRAPH - 0xE8DD: 0x738B, //CJK UNIFIED IDEOGRAPH - 0xE8DE: 0x502D, //CJK UNIFIED IDEOGRAPH - 0xE8DF: 0x5A03, //CJK UNIFIED IDEOGRAPH - 0xE8E0: 0x6B6A, //CJK UNIFIED IDEOGRAPH - 0xE8E1: 0x77EE, //CJK UNIFIED IDEOGRAPH - 0xE8E2: 0x5916, //CJK UNIFIED IDEOGRAPH - 0xE8E3: 0x5D6C, //CJK UNIFIED IDEOGRAPH - 0xE8E4: 0x5DCD, //CJK UNIFIED IDEOGRAPH - 0xE8E5: 0x7325, //CJK UNIFIED IDEOGRAPH - 0xE8E6: 0x754F, //CJK UNIFIED IDEOGRAPH - 0xE8E7: 0xF9BA, //CJK COMPATIBILITY IDEOGRAPH - 0xE8E8: 0xF9BB, //CJK COMPATIBILITY IDEOGRAPH - 0xE8E9: 0x50E5, //CJK UNIFIED IDEOGRAPH - 0xE8EA: 0x51F9, //CJK UNIFIED IDEOGRAPH - 0xE8EB: 0x582F, //CJK UNIFIED IDEOGRAPH - 0xE8EC: 0x592D, //CJK UNIFIED IDEOGRAPH - 0xE8ED: 0x5996, //CJK UNIFIED IDEOGRAPH - 0xE8EE: 0x59DA, //CJK UNIFIED IDEOGRAPH - 0xE8EF: 0x5BE5, //CJK UNIFIED IDEOGRAPH - 0xE8F0: 0xF9BC, //CJK COMPATIBILITY IDEOGRAPH - 0xE8F1: 0xF9BD, //CJK COMPATIBILITY IDEOGRAPH - 0xE8F2: 0x5DA2, //CJK UNIFIED IDEOGRAPH - 0xE8F3: 0x62D7, //CJK UNIFIED IDEOGRAPH - 0xE8F4: 0x6416, //CJK UNIFIED IDEOGRAPH - 0xE8F5: 0x6493, //CJK UNIFIED IDEOGRAPH - 0xE8F6: 0x64FE, //CJK UNIFIED IDEOGRAPH - 0xE8F7: 0xF9BE, //CJK COMPATIBILITY IDEOGRAPH - 0xE8F8: 0x66DC, //CJK UNIFIED IDEOGRAPH - 0xE8F9: 0xF9BF, //CJK COMPATIBILITY IDEOGRAPH - 0xE8FA: 0x6A48, //CJK UNIFIED IDEOGRAPH - 0xE8FB: 0xF9C0, //CJK COMPATIBILITY IDEOGRAPH - 0xE8FC: 0x71FF, //CJK UNIFIED IDEOGRAPH - 0xE8FD: 0x7464, //CJK UNIFIED IDEOGRAPH - 0xE8FE: 0xF9C1, //CJK COMPATIBILITY IDEOGRAPH - 0xE9A1: 0x7A88, //CJK UNIFIED IDEOGRAPH - 0xE9A2: 0x7AAF, //CJK UNIFIED IDEOGRAPH - 0xE9A3: 0x7E47, //CJK UNIFIED IDEOGRAPH - 0xE9A4: 0x7E5E, //CJK UNIFIED IDEOGRAPH - 0xE9A5: 0x8000, //CJK UNIFIED IDEOGRAPH - 0xE9A6: 0x8170, //CJK UNIFIED IDEOGRAPH - 0xE9A7: 0xF9C2, //CJK COMPATIBILITY IDEOGRAPH - 0xE9A8: 0x87EF, //CJK UNIFIED IDEOGRAPH - 0xE9A9: 0x8981, //CJK UNIFIED IDEOGRAPH - 0xE9AA: 0x8B20, //CJK UNIFIED IDEOGRAPH - 0xE9AB: 0x9059, //CJK UNIFIED IDEOGRAPH - 0xE9AC: 0xF9C3, //CJK COMPATIBILITY IDEOGRAPH - 0xE9AD: 0x9080, //CJK UNIFIED IDEOGRAPH - 0xE9AE: 0x9952, //CJK UNIFIED IDEOGRAPH - 0xE9AF: 0x617E, //CJK UNIFIED IDEOGRAPH - 0xE9B0: 0x6B32, //CJK UNIFIED IDEOGRAPH - 0xE9B1: 0x6D74, //CJK UNIFIED IDEOGRAPH - 0xE9B2: 0x7E1F, //CJK UNIFIED IDEOGRAPH - 0xE9B3: 0x8925, //CJK UNIFIED IDEOGRAPH - 0xE9B4: 0x8FB1, //CJK UNIFIED IDEOGRAPH - 0xE9B5: 0x4FD1, //CJK UNIFIED IDEOGRAPH - 0xE9B6: 0x50AD, //CJK UNIFIED IDEOGRAPH - 0xE9B7: 0x5197, //CJK UNIFIED IDEOGRAPH - 0xE9B8: 0x52C7, //CJK UNIFIED IDEOGRAPH - 0xE9B9: 0x57C7, //CJK UNIFIED IDEOGRAPH - 0xE9BA: 0x5889, //CJK UNIFIED IDEOGRAPH - 0xE9BB: 0x5BB9, //CJK UNIFIED IDEOGRAPH - 0xE9BC: 0x5EB8, //CJK UNIFIED IDEOGRAPH - 0xE9BD: 0x6142, //CJK UNIFIED IDEOGRAPH - 0xE9BE: 0x6995, //CJK UNIFIED IDEOGRAPH - 0xE9BF: 0x6D8C, //CJK UNIFIED IDEOGRAPH - 0xE9C0: 0x6E67, //CJK UNIFIED IDEOGRAPH - 0xE9C1: 0x6EB6, //CJK UNIFIED IDEOGRAPH - 0xE9C2: 0x7194, //CJK UNIFIED IDEOGRAPH - 0xE9C3: 0x7462, //CJK UNIFIED IDEOGRAPH - 0xE9C4: 0x7528, //CJK UNIFIED IDEOGRAPH - 0xE9C5: 0x752C, //CJK UNIFIED IDEOGRAPH - 0xE9C6: 0x8073, //CJK UNIFIED IDEOGRAPH - 0xE9C7: 0x8338, //CJK UNIFIED IDEOGRAPH - 0xE9C8: 0x84C9, //CJK UNIFIED IDEOGRAPH - 0xE9C9: 0x8E0A, //CJK UNIFIED IDEOGRAPH - 0xE9CA: 0x9394, //CJK UNIFIED IDEOGRAPH - 0xE9CB: 0x93DE, //CJK UNIFIED IDEOGRAPH - 0xE9CC: 0xF9C4, //CJK COMPATIBILITY IDEOGRAPH - 0xE9CD: 0x4E8E, //CJK UNIFIED IDEOGRAPH - 0xE9CE: 0x4F51, //CJK UNIFIED IDEOGRAPH - 0xE9CF: 0x5076, //CJK UNIFIED IDEOGRAPH - 0xE9D0: 0x512A, //CJK UNIFIED IDEOGRAPH - 0xE9D1: 0x53C8, //CJK UNIFIED IDEOGRAPH - 0xE9D2: 0x53CB, //CJK UNIFIED IDEOGRAPH - 0xE9D3: 0x53F3, //CJK UNIFIED IDEOGRAPH - 0xE9D4: 0x5B87, //CJK UNIFIED IDEOGRAPH - 0xE9D5: 0x5BD3, //CJK UNIFIED IDEOGRAPH - 0xE9D6: 0x5C24, //CJK UNIFIED IDEOGRAPH - 0xE9D7: 0x611A, //CJK UNIFIED IDEOGRAPH - 0xE9D8: 0x6182, //CJK UNIFIED IDEOGRAPH - 0xE9D9: 0x65F4, //CJK UNIFIED IDEOGRAPH - 0xE9DA: 0x725B, //CJK UNIFIED IDEOGRAPH - 0xE9DB: 0x7397, //CJK UNIFIED IDEOGRAPH - 0xE9DC: 0x7440, //CJK UNIFIED IDEOGRAPH - 0xE9DD: 0x76C2, //CJK UNIFIED IDEOGRAPH - 0xE9DE: 0x7950, //CJK UNIFIED IDEOGRAPH - 0xE9DF: 0x7991, //CJK UNIFIED IDEOGRAPH - 0xE9E0: 0x79B9, //CJK UNIFIED IDEOGRAPH - 0xE9E1: 0x7D06, //CJK UNIFIED IDEOGRAPH - 0xE9E2: 0x7FBD, //CJK UNIFIED IDEOGRAPH - 0xE9E3: 0x828B, //CJK UNIFIED IDEOGRAPH - 0xE9E4: 0x85D5, //CJK UNIFIED IDEOGRAPH - 0xE9E5: 0x865E, //CJK UNIFIED IDEOGRAPH - 0xE9E6: 0x8FC2, //CJK UNIFIED IDEOGRAPH - 0xE9E7: 0x9047, //CJK UNIFIED IDEOGRAPH - 0xE9E8: 0x90F5, //CJK UNIFIED IDEOGRAPH - 0xE9E9: 0x91EA, //CJK UNIFIED IDEOGRAPH - 0xE9EA: 0x9685, //CJK UNIFIED IDEOGRAPH - 0xE9EB: 0x96E8, //CJK UNIFIED IDEOGRAPH - 0xE9EC: 0x96E9, //CJK UNIFIED IDEOGRAPH - 0xE9ED: 0x52D6, //CJK UNIFIED IDEOGRAPH - 0xE9EE: 0x5F67, //CJK UNIFIED IDEOGRAPH - 0xE9EF: 0x65ED, //CJK UNIFIED IDEOGRAPH - 0xE9F0: 0x6631, //CJK UNIFIED IDEOGRAPH - 0xE9F1: 0x682F, //CJK UNIFIED IDEOGRAPH - 0xE9F2: 0x715C, //CJK UNIFIED IDEOGRAPH - 0xE9F3: 0x7A36, //CJK UNIFIED IDEOGRAPH - 0xE9F4: 0x90C1, //CJK UNIFIED IDEOGRAPH - 0xE9F5: 0x980A, //CJK UNIFIED IDEOGRAPH - 0xE9F6: 0x4E91, //CJK UNIFIED IDEOGRAPH - 0xE9F7: 0xF9C5, //CJK COMPATIBILITY IDEOGRAPH - 0xE9F8: 0x6A52, //CJK UNIFIED IDEOGRAPH - 0xE9F9: 0x6B9E, //CJK UNIFIED IDEOGRAPH - 0xE9FA: 0x6F90, //CJK UNIFIED IDEOGRAPH - 0xE9FB: 0x7189, //CJK UNIFIED IDEOGRAPH - 0xE9FC: 0x8018, //CJK UNIFIED IDEOGRAPH - 0xE9FD: 0x82B8, //CJK UNIFIED IDEOGRAPH - 0xE9FE: 0x8553, //CJK UNIFIED IDEOGRAPH - 0xEAA1: 0x904B, //CJK UNIFIED IDEOGRAPH - 0xEAA2: 0x9695, //CJK UNIFIED IDEOGRAPH - 0xEAA3: 0x96F2, //CJK UNIFIED IDEOGRAPH - 0xEAA4: 0x97FB, //CJK UNIFIED IDEOGRAPH - 0xEAA5: 0x851A, //CJK UNIFIED IDEOGRAPH - 0xEAA6: 0x9B31, //CJK UNIFIED IDEOGRAPH - 0xEAA7: 0x4E90, //CJK UNIFIED IDEOGRAPH - 0xEAA8: 0x718A, //CJK UNIFIED IDEOGRAPH - 0xEAA9: 0x96C4, //CJK UNIFIED IDEOGRAPH - 0xEAAA: 0x5143, //CJK UNIFIED IDEOGRAPH - 0xEAAB: 0x539F, //CJK UNIFIED IDEOGRAPH - 0xEAAC: 0x54E1, //CJK UNIFIED IDEOGRAPH - 0xEAAD: 0x5713, //CJK UNIFIED IDEOGRAPH - 0xEAAE: 0x5712, //CJK UNIFIED IDEOGRAPH - 0xEAAF: 0x57A3, //CJK UNIFIED IDEOGRAPH - 0xEAB0: 0x5A9B, //CJK UNIFIED IDEOGRAPH - 0xEAB1: 0x5AC4, //CJK UNIFIED IDEOGRAPH - 0xEAB2: 0x5BC3, //CJK UNIFIED IDEOGRAPH - 0xEAB3: 0x6028, //CJK UNIFIED IDEOGRAPH - 0xEAB4: 0x613F, //CJK UNIFIED IDEOGRAPH - 0xEAB5: 0x63F4, //CJK UNIFIED IDEOGRAPH - 0xEAB6: 0x6C85, //CJK UNIFIED IDEOGRAPH - 0xEAB7: 0x6D39, //CJK UNIFIED IDEOGRAPH - 0xEAB8: 0x6E72, //CJK UNIFIED IDEOGRAPH - 0xEAB9: 0x6E90, //CJK UNIFIED IDEOGRAPH - 0xEABA: 0x7230, //CJK UNIFIED IDEOGRAPH - 0xEABB: 0x733F, //CJK UNIFIED IDEOGRAPH - 0xEABC: 0x7457, //CJK UNIFIED IDEOGRAPH - 0xEABD: 0x82D1, //CJK UNIFIED IDEOGRAPH - 0xEABE: 0x8881, //CJK UNIFIED IDEOGRAPH - 0xEABF: 0x8F45, //CJK UNIFIED IDEOGRAPH - 0xEAC0: 0x9060, //CJK UNIFIED IDEOGRAPH - 0xEAC1: 0xF9C6, //CJK COMPATIBILITY IDEOGRAPH - 0xEAC2: 0x9662, //CJK UNIFIED IDEOGRAPH - 0xEAC3: 0x9858, //CJK UNIFIED IDEOGRAPH - 0xEAC4: 0x9D1B, //CJK UNIFIED IDEOGRAPH - 0xEAC5: 0x6708, //CJK UNIFIED IDEOGRAPH - 0xEAC6: 0x8D8A, //CJK UNIFIED IDEOGRAPH - 0xEAC7: 0x925E, //CJK UNIFIED IDEOGRAPH - 0xEAC8: 0x4F4D, //CJK UNIFIED IDEOGRAPH - 0xEAC9: 0x5049, //CJK UNIFIED IDEOGRAPH - 0xEACA: 0x50DE, //CJK UNIFIED IDEOGRAPH - 0xEACB: 0x5371, //CJK UNIFIED IDEOGRAPH - 0xEACC: 0x570D, //CJK UNIFIED IDEOGRAPH - 0xEACD: 0x59D4, //CJK UNIFIED IDEOGRAPH - 0xEACE: 0x5A01, //CJK UNIFIED IDEOGRAPH - 0xEACF: 0x5C09, //CJK UNIFIED IDEOGRAPH - 0xEAD0: 0x6170, //CJK UNIFIED IDEOGRAPH - 0xEAD1: 0x6690, //CJK UNIFIED IDEOGRAPH - 0xEAD2: 0x6E2D, //CJK UNIFIED IDEOGRAPH - 0xEAD3: 0x7232, //CJK UNIFIED IDEOGRAPH - 0xEAD4: 0x744B, //CJK UNIFIED IDEOGRAPH - 0xEAD5: 0x7DEF, //CJK UNIFIED IDEOGRAPH - 0xEAD6: 0x80C3, //CJK UNIFIED IDEOGRAPH - 0xEAD7: 0x840E, //CJK UNIFIED IDEOGRAPH - 0xEAD8: 0x8466, //CJK UNIFIED IDEOGRAPH - 0xEAD9: 0x853F, //CJK UNIFIED IDEOGRAPH - 0xEADA: 0x875F, //CJK UNIFIED IDEOGRAPH - 0xEADB: 0x885B, //CJK UNIFIED IDEOGRAPH - 0xEADC: 0x8918, //CJK UNIFIED IDEOGRAPH - 0xEADD: 0x8B02, //CJK UNIFIED IDEOGRAPH - 0xEADE: 0x9055, //CJK UNIFIED IDEOGRAPH - 0xEADF: 0x97CB, //CJK UNIFIED IDEOGRAPH - 0xEAE0: 0x9B4F, //CJK UNIFIED IDEOGRAPH - 0xEAE1: 0x4E73, //CJK UNIFIED IDEOGRAPH - 0xEAE2: 0x4F91, //CJK UNIFIED IDEOGRAPH - 0xEAE3: 0x5112, //CJK UNIFIED IDEOGRAPH - 0xEAE4: 0x516A, //CJK UNIFIED IDEOGRAPH - 0xEAE5: 0xF9C7, //CJK COMPATIBILITY IDEOGRAPH - 0xEAE6: 0x552F, //CJK UNIFIED IDEOGRAPH - 0xEAE7: 0x55A9, //CJK UNIFIED IDEOGRAPH - 0xEAE8: 0x5B7A, //CJK UNIFIED IDEOGRAPH - 0xEAE9: 0x5BA5, //CJK UNIFIED IDEOGRAPH - 0xEAEA: 0x5E7C, //CJK UNIFIED IDEOGRAPH - 0xEAEB: 0x5E7D, //CJK UNIFIED IDEOGRAPH - 0xEAEC: 0x5EBE, //CJK UNIFIED IDEOGRAPH - 0xEAED: 0x60A0, //CJK UNIFIED IDEOGRAPH - 0xEAEE: 0x60DF, //CJK UNIFIED IDEOGRAPH - 0xEAEF: 0x6108, //CJK UNIFIED IDEOGRAPH - 0xEAF0: 0x6109, //CJK UNIFIED IDEOGRAPH - 0xEAF1: 0x63C4, //CJK UNIFIED IDEOGRAPH - 0xEAF2: 0x6538, //CJK UNIFIED IDEOGRAPH - 0xEAF3: 0x6709, //CJK UNIFIED IDEOGRAPH - 0xEAF4: 0xF9C8, //CJK COMPATIBILITY IDEOGRAPH - 0xEAF5: 0x67D4, //CJK UNIFIED IDEOGRAPH - 0xEAF6: 0x67DA, //CJK UNIFIED IDEOGRAPH - 0xEAF7: 0xF9C9, //CJK COMPATIBILITY IDEOGRAPH - 0xEAF8: 0x6961, //CJK UNIFIED IDEOGRAPH - 0xEAF9: 0x6962, //CJK UNIFIED IDEOGRAPH - 0xEAFA: 0x6CB9, //CJK UNIFIED IDEOGRAPH - 0xEAFB: 0x6D27, //CJK UNIFIED IDEOGRAPH - 0xEAFC: 0xF9CA, //CJK COMPATIBILITY IDEOGRAPH - 0xEAFD: 0x6E38, //CJK UNIFIED IDEOGRAPH - 0xEAFE: 0xF9CB, //CJK COMPATIBILITY IDEOGRAPH - 0xEBA1: 0x6FE1, //CJK UNIFIED IDEOGRAPH - 0xEBA2: 0x7336, //CJK UNIFIED IDEOGRAPH - 0xEBA3: 0x7337, //CJK UNIFIED IDEOGRAPH - 0xEBA4: 0xF9CC, //CJK COMPATIBILITY IDEOGRAPH - 0xEBA5: 0x745C, //CJK UNIFIED IDEOGRAPH - 0xEBA6: 0x7531, //CJK UNIFIED IDEOGRAPH - 0xEBA7: 0xF9CD, //CJK COMPATIBILITY IDEOGRAPH - 0xEBA8: 0x7652, //CJK UNIFIED IDEOGRAPH - 0xEBA9: 0xF9CE, //CJK COMPATIBILITY IDEOGRAPH - 0xEBAA: 0xF9CF, //CJK COMPATIBILITY IDEOGRAPH - 0xEBAB: 0x7DAD, //CJK UNIFIED IDEOGRAPH - 0xEBAC: 0x81FE, //CJK UNIFIED IDEOGRAPH - 0xEBAD: 0x8438, //CJK UNIFIED IDEOGRAPH - 0xEBAE: 0x88D5, //CJK UNIFIED IDEOGRAPH - 0xEBAF: 0x8A98, //CJK UNIFIED IDEOGRAPH - 0xEBB0: 0x8ADB, //CJK UNIFIED IDEOGRAPH - 0xEBB1: 0x8AED, //CJK UNIFIED IDEOGRAPH - 0xEBB2: 0x8E30, //CJK UNIFIED IDEOGRAPH - 0xEBB3: 0x8E42, //CJK UNIFIED IDEOGRAPH - 0xEBB4: 0x904A, //CJK UNIFIED IDEOGRAPH - 0xEBB5: 0x903E, //CJK UNIFIED IDEOGRAPH - 0xEBB6: 0x907A, //CJK UNIFIED IDEOGRAPH - 0xEBB7: 0x9149, //CJK UNIFIED IDEOGRAPH - 0xEBB8: 0x91C9, //CJK UNIFIED IDEOGRAPH - 0xEBB9: 0x936E, //CJK UNIFIED IDEOGRAPH - 0xEBBA: 0xF9D0, //CJK COMPATIBILITY IDEOGRAPH - 0xEBBB: 0xF9D1, //CJK COMPATIBILITY IDEOGRAPH - 0xEBBC: 0x5809, //CJK UNIFIED IDEOGRAPH - 0xEBBD: 0xF9D2, //CJK COMPATIBILITY IDEOGRAPH - 0xEBBE: 0x6BD3, //CJK UNIFIED IDEOGRAPH - 0xEBBF: 0x8089, //CJK UNIFIED IDEOGRAPH - 0xEBC0: 0x80B2, //CJK UNIFIED IDEOGRAPH - 0xEBC1: 0xF9D3, //CJK COMPATIBILITY IDEOGRAPH - 0xEBC2: 0xF9D4, //CJK COMPATIBILITY IDEOGRAPH - 0xEBC3: 0x5141, //CJK UNIFIED IDEOGRAPH - 0xEBC4: 0x596B, //CJK UNIFIED IDEOGRAPH - 0xEBC5: 0x5C39, //CJK UNIFIED IDEOGRAPH - 0xEBC6: 0xF9D5, //CJK COMPATIBILITY IDEOGRAPH - 0xEBC7: 0xF9D6, //CJK COMPATIBILITY IDEOGRAPH - 0xEBC8: 0x6F64, //CJK UNIFIED IDEOGRAPH - 0xEBC9: 0x73A7, //CJK UNIFIED IDEOGRAPH - 0xEBCA: 0x80E4, //CJK UNIFIED IDEOGRAPH - 0xEBCB: 0x8D07, //CJK UNIFIED IDEOGRAPH - 0xEBCC: 0xF9D7, //CJK COMPATIBILITY IDEOGRAPH - 0xEBCD: 0x9217, //CJK UNIFIED IDEOGRAPH - 0xEBCE: 0x958F, //CJK UNIFIED IDEOGRAPH - 0xEBCF: 0xF9D8, //CJK COMPATIBILITY IDEOGRAPH - 0xEBD0: 0xF9D9, //CJK COMPATIBILITY IDEOGRAPH - 0xEBD1: 0xF9DA, //CJK COMPATIBILITY IDEOGRAPH - 0xEBD2: 0xF9DB, //CJK COMPATIBILITY IDEOGRAPH - 0xEBD3: 0x807F, //CJK UNIFIED IDEOGRAPH - 0xEBD4: 0x620E, //CJK UNIFIED IDEOGRAPH - 0xEBD5: 0x701C, //CJK UNIFIED IDEOGRAPH - 0xEBD6: 0x7D68, //CJK UNIFIED IDEOGRAPH - 0xEBD7: 0x878D, //CJK UNIFIED IDEOGRAPH - 0xEBD8: 0xF9DC, //CJK COMPATIBILITY IDEOGRAPH - 0xEBD9: 0x57A0, //CJK UNIFIED IDEOGRAPH - 0xEBDA: 0x6069, //CJK UNIFIED IDEOGRAPH - 0xEBDB: 0x6147, //CJK UNIFIED IDEOGRAPH - 0xEBDC: 0x6BB7, //CJK UNIFIED IDEOGRAPH - 0xEBDD: 0x8ABE, //CJK UNIFIED IDEOGRAPH - 0xEBDE: 0x9280, //CJK UNIFIED IDEOGRAPH - 0xEBDF: 0x96B1, //CJK UNIFIED IDEOGRAPH - 0xEBE0: 0x4E59, //CJK UNIFIED IDEOGRAPH - 0xEBE1: 0x541F, //CJK UNIFIED IDEOGRAPH - 0xEBE2: 0x6DEB, //CJK UNIFIED IDEOGRAPH - 0xEBE3: 0x852D, //CJK UNIFIED IDEOGRAPH - 0xEBE4: 0x9670, //CJK UNIFIED IDEOGRAPH - 0xEBE5: 0x97F3, //CJK UNIFIED IDEOGRAPH - 0xEBE6: 0x98EE, //CJK UNIFIED IDEOGRAPH - 0xEBE7: 0x63D6, //CJK UNIFIED IDEOGRAPH - 0xEBE8: 0x6CE3, //CJK UNIFIED IDEOGRAPH - 0xEBE9: 0x9091, //CJK UNIFIED IDEOGRAPH - 0xEBEA: 0x51DD, //CJK UNIFIED IDEOGRAPH - 0xEBEB: 0x61C9, //CJK UNIFIED IDEOGRAPH - 0xEBEC: 0x81BA, //CJK UNIFIED IDEOGRAPH - 0xEBED: 0x9DF9, //CJK UNIFIED IDEOGRAPH - 0xEBEE: 0x4F9D, //CJK UNIFIED IDEOGRAPH - 0xEBEF: 0x501A, //CJK UNIFIED IDEOGRAPH - 0xEBF0: 0x5100, //CJK UNIFIED IDEOGRAPH - 0xEBF1: 0x5B9C, //CJK UNIFIED IDEOGRAPH - 0xEBF2: 0x610F, //CJK UNIFIED IDEOGRAPH - 0xEBF3: 0x61FF, //CJK UNIFIED IDEOGRAPH - 0xEBF4: 0x64EC, //CJK UNIFIED IDEOGRAPH - 0xEBF5: 0x6905, //CJK UNIFIED IDEOGRAPH - 0xEBF6: 0x6BC5, //CJK UNIFIED IDEOGRAPH - 0xEBF7: 0x7591, //CJK UNIFIED IDEOGRAPH - 0xEBF8: 0x77E3, //CJK UNIFIED IDEOGRAPH - 0xEBF9: 0x7FA9, //CJK UNIFIED IDEOGRAPH - 0xEBFA: 0x8264, //CJK UNIFIED IDEOGRAPH - 0xEBFB: 0x858F, //CJK UNIFIED IDEOGRAPH - 0xEBFC: 0x87FB, //CJK UNIFIED IDEOGRAPH - 0xEBFD: 0x8863, //CJK UNIFIED IDEOGRAPH - 0xEBFE: 0x8ABC, //CJK UNIFIED IDEOGRAPH - 0xECA1: 0x8B70, //CJK UNIFIED IDEOGRAPH - 0xECA2: 0x91AB, //CJK UNIFIED IDEOGRAPH - 0xECA3: 0x4E8C, //CJK UNIFIED IDEOGRAPH - 0xECA4: 0x4EE5, //CJK UNIFIED IDEOGRAPH - 0xECA5: 0x4F0A, //CJK UNIFIED IDEOGRAPH - 0xECA6: 0xF9DD, //CJK COMPATIBILITY IDEOGRAPH - 0xECA7: 0xF9DE, //CJK COMPATIBILITY IDEOGRAPH - 0xECA8: 0x5937, //CJK UNIFIED IDEOGRAPH - 0xECA9: 0x59E8, //CJK UNIFIED IDEOGRAPH - 0xECAA: 0xF9DF, //CJK COMPATIBILITY IDEOGRAPH - 0xECAB: 0x5DF2, //CJK UNIFIED IDEOGRAPH - 0xECAC: 0x5F1B, //CJK UNIFIED IDEOGRAPH - 0xECAD: 0x5F5B, //CJK UNIFIED IDEOGRAPH - 0xECAE: 0x6021, //CJK UNIFIED IDEOGRAPH - 0xECAF: 0xF9E0, //CJK COMPATIBILITY IDEOGRAPH - 0xECB0: 0xF9E1, //CJK COMPATIBILITY IDEOGRAPH - 0xECB1: 0xF9E2, //CJK COMPATIBILITY IDEOGRAPH - 0xECB2: 0xF9E3, //CJK COMPATIBILITY IDEOGRAPH - 0xECB3: 0x723E, //CJK UNIFIED IDEOGRAPH - 0xECB4: 0x73E5, //CJK UNIFIED IDEOGRAPH - 0xECB5: 0xF9E4, //CJK COMPATIBILITY IDEOGRAPH - 0xECB6: 0x7570, //CJK UNIFIED IDEOGRAPH - 0xECB7: 0x75CD, //CJK UNIFIED IDEOGRAPH - 0xECB8: 0xF9E5, //CJK COMPATIBILITY IDEOGRAPH - 0xECB9: 0x79FB, //CJK UNIFIED IDEOGRAPH - 0xECBA: 0xF9E6, //CJK COMPATIBILITY IDEOGRAPH - 0xECBB: 0x800C, //CJK UNIFIED IDEOGRAPH - 0xECBC: 0x8033, //CJK UNIFIED IDEOGRAPH - 0xECBD: 0x8084, //CJK UNIFIED IDEOGRAPH - 0xECBE: 0x82E1, //CJK UNIFIED IDEOGRAPH - 0xECBF: 0x8351, //CJK UNIFIED IDEOGRAPH - 0xECC0: 0xF9E7, //CJK COMPATIBILITY IDEOGRAPH - 0xECC1: 0xF9E8, //CJK COMPATIBILITY IDEOGRAPH - 0xECC2: 0x8CBD, //CJK UNIFIED IDEOGRAPH - 0xECC3: 0x8CB3, //CJK UNIFIED IDEOGRAPH - 0xECC4: 0x9087, //CJK UNIFIED IDEOGRAPH - 0xECC5: 0xF9E9, //CJK COMPATIBILITY IDEOGRAPH - 0xECC6: 0xF9EA, //CJK COMPATIBILITY IDEOGRAPH - 0xECC7: 0x98F4, //CJK UNIFIED IDEOGRAPH - 0xECC8: 0x990C, //CJK UNIFIED IDEOGRAPH - 0xECC9: 0xF9EB, //CJK COMPATIBILITY IDEOGRAPH - 0xECCA: 0xF9EC, //CJK COMPATIBILITY IDEOGRAPH - 0xECCB: 0x7037, //CJK UNIFIED IDEOGRAPH - 0xECCC: 0x76CA, //CJK UNIFIED IDEOGRAPH - 0xECCD: 0x7FCA, //CJK UNIFIED IDEOGRAPH - 0xECCE: 0x7FCC, //CJK UNIFIED IDEOGRAPH - 0xECCF: 0x7FFC, //CJK UNIFIED IDEOGRAPH - 0xECD0: 0x8B1A, //CJK UNIFIED IDEOGRAPH - 0xECD1: 0x4EBA, //CJK UNIFIED IDEOGRAPH - 0xECD2: 0x4EC1, //CJK UNIFIED IDEOGRAPH - 0xECD3: 0x5203, //CJK UNIFIED IDEOGRAPH - 0xECD4: 0x5370, //CJK UNIFIED IDEOGRAPH - 0xECD5: 0xF9ED, //CJK COMPATIBILITY IDEOGRAPH - 0xECD6: 0x54BD, //CJK UNIFIED IDEOGRAPH - 0xECD7: 0x56E0, //CJK UNIFIED IDEOGRAPH - 0xECD8: 0x59FB, //CJK UNIFIED IDEOGRAPH - 0xECD9: 0x5BC5, //CJK UNIFIED IDEOGRAPH - 0xECDA: 0x5F15, //CJK UNIFIED IDEOGRAPH - 0xECDB: 0x5FCD, //CJK UNIFIED IDEOGRAPH - 0xECDC: 0x6E6E, //CJK UNIFIED IDEOGRAPH - 0xECDD: 0xF9EE, //CJK COMPATIBILITY IDEOGRAPH - 0xECDE: 0xF9EF, //CJK COMPATIBILITY IDEOGRAPH - 0xECDF: 0x7D6A, //CJK UNIFIED IDEOGRAPH - 0xECE0: 0x8335, //CJK UNIFIED IDEOGRAPH - 0xECE1: 0xF9F0, //CJK COMPATIBILITY IDEOGRAPH - 0xECE2: 0x8693, //CJK UNIFIED IDEOGRAPH - 0xECE3: 0x8A8D, //CJK UNIFIED IDEOGRAPH - 0xECE4: 0xF9F1, //CJK COMPATIBILITY IDEOGRAPH - 0xECE5: 0x976D, //CJK UNIFIED IDEOGRAPH - 0xECE6: 0x9777, //CJK UNIFIED IDEOGRAPH - 0xECE7: 0xF9F2, //CJK COMPATIBILITY IDEOGRAPH - 0xECE8: 0xF9F3, //CJK COMPATIBILITY IDEOGRAPH - 0xECE9: 0x4E00, //CJK UNIFIED IDEOGRAPH - 0xECEA: 0x4F5A, //CJK UNIFIED IDEOGRAPH - 0xECEB: 0x4F7E, //CJK UNIFIED IDEOGRAPH - 0xECEC: 0x58F9, //CJK UNIFIED IDEOGRAPH - 0xECED: 0x65E5, //CJK UNIFIED IDEOGRAPH - 0xECEE: 0x6EA2, //CJK UNIFIED IDEOGRAPH - 0xECEF: 0x9038, //CJK UNIFIED IDEOGRAPH - 0xECF0: 0x93B0, //CJK UNIFIED IDEOGRAPH - 0xECF1: 0x99B9, //CJK UNIFIED IDEOGRAPH - 0xECF2: 0x4EFB, //CJK UNIFIED IDEOGRAPH - 0xECF3: 0x58EC, //CJK UNIFIED IDEOGRAPH - 0xECF4: 0x598A, //CJK UNIFIED IDEOGRAPH - 0xECF5: 0x59D9, //CJK UNIFIED IDEOGRAPH - 0xECF6: 0x6041, //CJK UNIFIED IDEOGRAPH - 0xECF7: 0xF9F4, //CJK COMPATIBILITY IDEOGRAPH - 0xECF8: 0xF9F5, //CJK COMPATIBILITY IDEOGRAPH - 0xECF9: 0x7A14, //CJK UNIFIED IDEOGRAPH - 0xECFA: 0xF9F6, //CJK COMPATIBILITY IDEOGRAPH - 0xECFB: 0x834F, //CJK UNIFIED IDEOGRAPH - 0xECFC: 0x8CC3, //CJK UNIFIED IDEOGRAPH - 0xECFD: 0x5165, //CJK UNIFIED IDEOGRAPH - 0xECFE: 0x5344, //CJK UNIFIED IDEOGRAPH - 0xEDA1: 0xF9F7, //CJK COMPATIBILITY IDEOGRAPH - 0xEDA2: 0xF9F8, //CJK COMPATIBILITY IDEOGRAPH - 0xEDA3: 0xF9F9, //CJK COMPATIBILITY IDEOGRAPH - 0xEDA4: 0x4ECD, //CJK UNIFIED IDEOGRAPH - 0xEDA5: 0x5269, //CJK UNIFIED IDEOGRAPH - 0xEDA6: 0x5B55, //CJK UNIFIED IDEOGRAPH - 0xEDA7: 0x82BF, //CJK UNIFIED IDEOGRAPH - 0xEDA8: 0x4ED4, //CJK UNIFIED IDEOGRAPH - 0xEDA9: 0x523A, //CJK UNIFIED IDEOGRAPH - 0xEDAA: 0x54A8, //CJK UNIFIED IDEOGRAPH - 0xEDAB: 0x59C9, //CJK UNIFIED IDEOGRAPH - 0xEDAC: 0x59FF, //CJK UNIFIED IDEOGRAPH - 0xEDAD: 0x5B50, //CJK UNIFIED IDEOGRAPH - 0xEDAE: 0x5B57, //CJK UNIFIED IDEOGRAPH - 0xEDAF: 0x5B5C, //CJK UNIFIED IDEOGRAPH - 0xEDB0: 0x6063, //CJK UNIFIED IDEOGRAPH - 0xEDB1: 0x6148, //CJK UNIFIED IDEOGRAPH - 0xEDB2: 0x6ECB, //CJK UNIFIED IDEOGRAPH - 0xEDB3: 0x7099, //CJK UNIFIED IDEOGRAPH - 0xEDB4: 0x716E, //CJK UNIFIED IDEOGRAPH - 0xEDB5: 0x7386, //CJK UNIFIED IDEOGRAPH - 0xEDB6: 0x74F7, //CJK UNIFIED IDEOGRAPH - 0xEDB7: 0x75B5, //CJK UNIFIED IDEOGRAPH - 0xEDB8: 0x78C1, //CJK UNIFIED IDEOGRAPH - 0xEDB9: 0x7D2B, //CJK UNIFIED IDEOGRAPH - 0xEDBA: 0x8005, //CJK UNIFIED IDEOGRAPH - 0xEDBB: 0x81EA, //CJK UNIFIED IDEOGRAPH - 0xEDBC: 0x8328, //CJK UNIFIED IDEOGRAPH - 0xEDBD: 0x8517, //CJK UNIFIED IDEOGRAPH - 0xEDBE: 0x85C9, //CJK UNIFIED IDEOGRAPH - 0xEDBF: 0x8AEE, //CJK UNIFIED IDEOGRAPH - 0xEDC0: 0x8CC7, //CJK UNIFIED IDEOGRAPH - 0xEDC1: 0x96CC, //CJK UNIFIED IDEOGRAPH - 0xEDC2: 0x4F5C, //CJK UNIFIED IDEOGRAPH - 0xEDC3: 0x52FA, //CJK UNIFIED IDEOGRAPH - 0xEDC4: 0x56BC, //CJK UNIFIED IDEOGRAPH - 0xEDC5: 0x65AB, //CJK UNIFIED IDEOGRAPH - 0xEDC6: 0x6628, //CJK UNIFIED IDEOGRAPH - 0xEDC7: 0x707C, //CJK UNIFIED IDEOGRAPH - 0xEDC8: 0x70B8, //CJK UNIFIED IDEOGRAPH - 0xEDC9: 0x7235, //CJK UNIFIED IDEOGRAPH - 0xEDCA: 0x7DBD, //CJK UNIFIED IDEOGRAPH - 0xEDCB: 0x828D, //CJK UNIFIED IDEOGRAPH - 0xEDCC: 0x914C, //CJK UNIFIED IDEOGRAPH - 0xEDCD: 0x96C0, //CJK UNIFIED IDEOGRAPH - 0xEDCE: 0x9D72, //CJK UNIFIED IDEOGRAPH - 0xEDCF: 0x5B71, //CJK UNIFIED IDEOGRAPH - 0xEDD0: 0x68E7, //CJK UNIFIED IDEOGRAPH - 0xEDD1: 0x6B98, //CJK UNIFIED IDEOGRAPH - 0xEDD2: 0x6F7A, //CJK UNIFIED IDEOGRAPH - 0xEDD3: 0x76DE, //CJK UNIFIED IDEOGRAPH - 0xEDD4: 0x5C91, //CJK UNIFIED IDEOGRAPH - 0xEDD5: 0x66AB, //CJK UNIFIED IDEOGRAPH - 0xEDD6: 0x6F5B, //CJK UNIFIED IDEOGRAPH - 0xEDD7: 0x7BB4, //CJK UNIFIED IDEOGRAPH - 0xEDD8: 0x7C2A, //CJK UNIFIED IDEOGRAPH - 0xEDD9: 0x8836, //CJK UNIFIED IDEOGRAPH - 0xEDDA: 0x96DC, //CJK UNIFIED IDEOGRAPH - 0xEDDB: 0x4E08, //CJK UNIFIED IDEOGRAPH - 0xEDDC: 0x4ED7, //CJK UNIFIED IDEOGRAPH - 0xEDDD: 0x5320, //CJK UNIFIED IDEOGRAPH - 0xEDDE: 0x5834, //CJK UNIFIED IDEOGRAPH - 0xEDDF: 0x58BB, //CJK UNIFIED IDEOGRAPH - 0xEDE0: 0x58EF, //CJK UNIFIED IDEOGRAPH - 0xEDE1: 0x596C, //CJK UNIFIED IDEOGRAPH - 0xEDE2: 0x5C07, //CJK UNIFIED IDEOGRAPH - 0xEDE3: 0x5E33, //CJK UNIFIED IDEOGRAPH - 0xEDE4: 0x5E84, //CJK UNIFIED IDEOGRAPH - 0xEDE5: 0x5F35, //CJK UNIFIED IDEOGRAPH - 0xEDE6: 0x638C, //CJK UNIFIED IDEOGRAPH - 0xEDE7: 0x66B2, //CJK UNIFIED IDEOGRAPH - 0xEDE8: 0x6756, //CJK UNIFIED IDEOGRAPH - 0xEDE9: 0x6A1F, //CJK UNIFIED IDEOGRAPH - 0xEDEA: 0x6AA3, //CJK UNIFIED IDEOGRAPH - 0xEDEB: 0x6B0C, //CJK UNIFIED IDEOGRAPH - 0xEDEC: 0x6F3F, //CJK UNIFIED IDEOGRAPH - 0xEDED: 0x7246, //CJK UNIFIED IDEOGRAPH - 0xEDEE: 0xF9FA, //CJK COMPATIBILITY IDEOGRAPH - 0xEDEF: 0x7350, //CJK UNIFIED IDEOGRAPH - 0xEDF0: 0x748B, //CJK UNIFIED IDEOGRAPH - 0xEDF1: 0x7AE0, //CJK UNIFIED IDEOGRAPH - 0xEDF2: 0x7CA7, //CJK UNIFIED IDEOGRAPH - 0xEDF3: 0x8178, //CJK UNIFIED IDEOGRAPH - 0xEDF4: 0x81DF, //CJK UNIFIED IDEOGRAPH - 0xEDF5: 0x81E7, //CJK UNIFIED IDEOGRAPH - 0xEDF6: 0x838A, //CJK UNIFIED IDEOGRAPH - 0xEDF7: 0x846C, //CJK UNIFIED IDEOGRAPH - 0xEDF8: 0x8523, //CJK UNIFIED IDEOGRAPH - 0xEDF9: 0x8594, //CJK UNIFIED IDEOGRAPH - 0xEDFA: 0x85CF, //CJK UNIFIED IDEOGRAPH - 0xEDFB: 0x88DD, //CJK UNIFIED IDEOGRAPH - 0xEDFC: 0x8D13, //CJK UNIFIED IDEOGRAPH - 0xEDFD: 0x91AC, //CJK UNIFIED IDEOGRAPH - 0xEDFE: 0x9577, //CJK UNIFIED IDEOGRAPH - 0xEEA1: 0x969C, //CJK UNIFIED IDEOGRAPH - 0xEEA2: 0x518D, //CJK UNIFIED IDEOGRAPH - 0xEEA3: 0x54C9, //CJK UNIFIED IDEOGRAPH - 0xEEA4: 0x5728, //CJK UNIFIED IDEOGRAPH - 0xEEA5: 0x5BB0, //CJK UNIFIED IDEOGRAPH - 0xEEA6: 0x624D, //CJK UNIFIED IDEOGRAPH - 0xEEA7: 0x6750, //CJK UNIFIED IDEOGRAPH - 0xEEA8: 0x683D, //CJK UNIFIED IDEOGRAPH - 0xEEA9: 0x6893, //CJK UNIFIED IDEOGRAPH - 0xEEAA: 0x6E3D, //CJK UNIFIED IDEOGRAPH - 0xEEAB: 0x6ED3, //CJK UNIFIED IDEOGRAPH - 0xEEAC: 0x707D, //CJK UNIFIED IDEOGRAPH - 0xEEAD: 0x7E21, //CJK UNIFIED IDEOGRAPH - 0xEEAE: 0x88C1, //CJK UNIFIED IDEOGRAPH - 0xEEAF: 0x8CA1, //CJK UNIFIED IDEOGRAPH - 0xEEB0: 0x8F09, //CJK UNIFIED IDEOGRAPH - 0xEEB1: 0x9F4B, //CJK UNIFIED IDEOGRAPH - 0xEEB2: 0x9F4E, //CJK UNIFIED IDEOGRAPH - 0xEEB3: 0x722D, //CJK UNIFIED IDEOGRAPH - 0xEEB4: 0x7B8F, //CJK UNIFIED IDEOGRAPH - 0xEEB5: 0x8ACD, //CJK UNIFIED IDEOGRAPH - 0xEEB6: 0x931A, //CJK UNIFIED IDEOGRAPH - 0xEEB7: 0x4F47, //CJK UNIFIED IDEOGRAPH - 0xEEB8: 0x4F4E, //CJK UNIFIED IDEOGRAPH - 0xEEB9: 0x5132, //CJK UNIFIED IDEOGRAPH - 0xEEBA: 0x5480, //CJK UNIFIED IDEOGRAPH - 0xEEBB: 0x59D0, //CJK UNIFIED IDEOGRAPH - 0xEEBC: 0x5E95, //CJK UNIFIED IDEOGRAPH - 0xEEBD: 0x62B5, //CJK UNIFIED IDEOGRAPH - 0xEEBE: 0x6775, //CJK UNIFIED IDEOGRAPH - 0xEEBF: 0x696E, //CJK UNIFIED IDEOGRAPH - 0xEEC0: 0x6A17, //CJK UNIFIED IDEOGRAPH - 0xEEC1: 0x6CAE, //CJK UNIFIED IDEOGRAPH - 0xEEC2: 0x6E1A, //CJK UNIFIED IDEOGRAPH - 0xEEC3: 0x72D9, //CJK UNIFIED IDEOGRAPH - 0xEEC4: 0x732A, //CJK UNIFIED IDEOGRAPH - 0xEEC5: 0x75BD, //CJK UNIFIED IDEOGRAPH - 0xEEC6: 0x7BB8, //CJK UNIFIED IDEOGRAPH - 0xEEC7: 0x7D35, //CJK UNIFIED IDEOGRAPH - 0xEEC8: 0x82E7, //CJK UNIFIED IDEOGRAPH - 0xEEC9: 0x83F9, //CJK UNIFIED IDEOGRAPH - 0xEECA: 0x8457, //CJK UNIFIED IDEOGRAPH - 0xEECB: 0x85F7, //CJK UNIFIED IDEOGRAPH - 0xEECC: 0x8A5B, //CJK UNIFIED IDEOGRAPH - 0xEECD: 0x8CAF, //CJK UNIFIED IDEOGRAPH - 0xEECE: 0x8E87, //CJK UNIFIED IDEOGRAPH - 0xEECF: 0x9019, //CJK UNIFIED IDEOGRAPH - 0xEED0: 0x90B8, //CJK UNIFIED IDEOGRAPH - 0xEED1: 0x96CE, //CJK UNIFIED IDEOGRAPH - 0xEED2: 0x9F5F, //CJK UNIFIED IDEOGRAPH - 0xEED3: 0x52E3, //CJK UNIFIED IDEOGRAPH - 0xEED4: 0x540A, //CJK UNIFIED IDEOGRAPH - 0xEED5: 0x5AE1, //CJK UNIFIED IDEOGRAPH - 0xEED6: 0x5BC2, //CJK UNIFIED IDEOGRAPH - 0xEED7: 0x6458, //CJK UNIFIED IDEOGRAPH - 0xEED8: 0x6575, //CJK UNIFIED IDEOGRAPH - 0xEED9: 0x6EF4, //CJK UNIFIED IDEOGRAPH - 0xEEDA: 0x72C4, //CJK UNIFIED IDEOGRAPH - 0xEEDB: 0xF9FB, //CJK COMPATIBILITY IDEOGRAPH - 0xEEDC: 0x7684, //CJK UNIFIED IDEOGRAPH - 0xEEDD: 0x7A4D, //CJK UNIFIED IDEOGRAPH - 0xEEDE: 0x7B1B, //CJK UNIFIED IDEOGRAPH - 0xEEDF: 0x7C4D, //CJK UNIFIED IDEOGRAPH - 0xEEE0: 0x7E3E, //CJK UNIFIED IDEOGRAPH - 0xEEE1: 0x7FDF, //CJK UNIFIED IDEOGRAPH - 0xEEE2: 0x837B, //CJK UNIFIED IDEOGRAPH - 0xEEE3: 0x8B2B, //CJK UNIFIED IDEOGRAPH - 0xEEE4: 0x8CCA, //CJK UNIFIED IDEOGRAPH - 0xEEE5: 0x8D64, //CJK UNIFIED IDEOGRAPH - 0xEEE6: 0x8DE1, //CJK UNIFIED IDEOGRAPH - 0xEEE7: 0x8E5F, //CJK UNIFIED IDEOGRAPH - 0xEEE8: 0x8FEA, //CJK UNIFIED IDEOGRAPH - 0xEEE9: 0x8FF9, //CJK UNIFIED IDEOGRAPH - 0xEEEA: 0x9069, //CJK UNIFIED IDEOGRAPH - 0xEEEB: 0x93D1, //CJK UNIFIED IDEOGRAPH - 0xEEEC: 0x4F43, //CJK UNIFIED IDEOGRAPH - 0xEEED: 0x4F7A, //CJK UNIFIED IDEOGRAPH - 0xEEEE: 0x50B3, //CJK UNIFIED IDEOGRAPH - 0xEEEF: 0x5168, //CJK UNIFIED IDEOGRAPH - 0xEEF0: 0x5178, //CJK UNIFIED IDEOGRAPH - 0xEEF1: 0x524D, //CJK UNIFIED IDEOGRAPH - 0xEEF2: 0x526A, //CJK UNIFIED IDEOGRAPH - 0xEEF3: 0x5861, //CJK UNIFIED IDEOGRAPH - 0xEEF4: 0x587C, //CJK UNIFIED IDEOGRAPH - 0xEEF5: 0x5960, //CJK UNIFIED IDEOGRAPH - 0xEEF6: 0x5C08, //CJK UNIFIED IDEOGRAPH - 0xEEF7: 0x5C55, //CJK UNIFIED IDEOGRAPH - 0xEEF8: 0x5EDB, //CJK UNIFIED IDEOGRAPH - 0xEEF9: 0x609B, //CJK UNIFIED IDEOGRAPH - 0xEEFA: 0x6230, //CJK UNIFIED IDEOGRAPH - 0xEEFB: 0x6813, //CJK UNIFIED IDEOGRAPH - 0xEEFC: 0x6BBF, //CJK UNIFIED IDEOGRAPH - 0xEEFD: 0x6C08, //CJK UNIFIED IDEOGRAPH - 0xEEFE: 0x6FB1, //CJK UNIFIED IDEOGRAPH - 0xEFA1: 0x714E, //CJK UNIFIED IDEOGRAPH - 0xEFA2: 0x7420, //CJK UNIFIED IDEOGRAPH - 0xEFA3: 0x7530, //CJK UNIFIED IDEOGRAPH - 0xEFA4: 0x7538, //CJK UNIFIED IDEOGRAPH - 0xEFA5: 0x7551, //CJK UNIFIED IDEOGRAPH - 0xEFA6: 0x7672, //CJK UNIFIED IDEOGRAPH - 0xEFA7: 0x7B4C, //CJK UNIFIED IDEOGRAPH - 0xEFA8: 0x7B8B, //CJK UNIFIED IDEOGRAPH - 0xEFA9: 0x7BAD, //CJK UNIFIED IDEOGRAPH - 0xEFAA: 0x7BC6, //CJK UNIFIED IDEOGRAPH - 0xEFAB: 0x7E8F, //CJK UNIFIED IDEOGRAPH - 0xEFAC: 0x8A6E, //CJK UNIFIED IDEOGRAPH - 0xEFAD: 0x8F3E, //CJK UNIFIED IDEOGRAPH - 0xEFAE: 0x8F49, //CJK UNIFIED IDEOGRAPH - 0xEFAF: 0x923F, //CJK UNIFIED IDEOGRAPH - 0xEFB0: 0x9293, //CJK UNIFIED IDEOGRAPH - 0xEFB1: 0x9322, //CJK UNIFIED IDEOGRAPH - 0xEFB2: 0x942B, //CJK UNIFIED IDEOGRAPH - 0xEFB3: 0x96FB, //CJK UNIFIED IDEOGRAPH - 0xEFB4: 0x985A, //CJK UNIFIED IDEOGRAPH - 0xEFB5: 0x986B, //CJK UNIFIED IDEOGRAPH - 0xEFB6: 0x991E, //CJK UNIFIED IDEOGRAPH - 0xEFB7: 0x5207, //CJK UNIFIED IDEOGRAPH - 0xEFB8: 0x622A, //CJK UNIFIED IDEOGRAPH - 0xEFB9: 0x6298, //CJK UNIFIED IDEOGRAPH - 0xEFBA: 0x6D59, //CJK UNIFIED IDEOGRAPH - 0xEFBB: 0x7664, //CJK UNIFIED IDEOGRAPH - 0xEFBC: 0x7ACA, //CJK UNIFIED IDEOGRAPH - 0xEFBD: 0x7BC0, //CJK UNIFIED IDEOGRAPH - 0xEFBE: 0x7D76, //CJK UNIFIED IDEOGRAPH - 0xEFBF: 0x5360, //CJK UNIFIED IDEOGRAPH - 0xEFC0: 0x5CBE, //CJK UNIFIED IDEOGRAPH - 0xEFC1: 0x5E97, //CJK UNIFIED IDEOGRAPH - 0xEFC2: 0x6F38, //CJK UNIFIED IDEOGRAPH - 0xEFC3: 0x70B9, //CJK UNIFIED IDEOGRAPH - 0xEFC4: 0x7C98, //CJK UNIFIED IDEOGRAPH - 0xEFC5: 0x9711, //CJK UNIFIED IDEOGRAPH - 0xEFC6: 0x9B8E, //CJK UNIFIED IDEOGRAPH - 0xEFC7: 0x9EDE, //CJK UNIFIED IDEOGRAPH - 0xEFC8: 0x63A5, //CJK UNIFIED IDEOGRAPH - 0xEFC9: 0x647A, //CJK UNIFIED IDEOGRAPH - 0xEFCA: 0x8776, //CJK UNIFIED IDEOGRAPH - 0xEFCB: 0x4E01, //CJK UNIFIED IDEOGRAPH - 0xEFCC: 0x4E95, //CJK UNIFIED IDEOGRAPH - 0xEFCD: 0x4EAD, //CJK UNIFIED IDEOGRAPH - 0xEFCE: 0x505C, //CJK UNIFIED IDEOGRAPH - 0xEFCF: 0x5075, //CJK UNIFIED IDEOGRAPH - 0xEFD0: 0x5448, //CJK UNIFIED IDEOGRAPH - 0xEFD1: 0x59C3, //CJK UNIFIED IDEOGRAPH - 0xEFD2: 0x5B9A, //CJK UNIFIED IDEOGRAPH - 0xEFD3: 0x5E40, //CJK UNIFIED IDEOGRAPH - 0xEFD4: 0x5EAD, //CJK UNIFIED IDEOGRAPH - 0xEFD5: 0x5EF7, //CJK UNIFIED IDEOGRAPH - 0xEFD6: 0x5F81, //CJK UNIFIED IDEOGRAPH - 0xEFD7: 0x60C5, //CJK UNIFIED IDEOGRAPH - 0xEFD8: 0x633A, //CJK UNIFIED IDEOGRAPH - 0xEFD9: 0x653F, //CJK UNIFIED IDEOGRAPH - 0xEFDA: 0x6574, //CJK UNIFIED IDEOGRAPH - 0xEFDB: 0x65CC, //CJK UNIFIED IDEOGRAPH - 0xEFDC: 0x6676, //CJK UNIFIED IDEOGRAPH - 0xEFDD: 0x6678, //CJK UNIFIED IDEOGRAPH - 0xEFDE: 0x67FE, //CJK UNIFIED IDEOGRAPH - 0xEFDF: 0x6968, //CJK UNIFIED IDEOGRAPH - 0xEFE0: 0x6A89, //CJK UNIFIED IDEOGRAPH - 0xEFE1: 0x6B63, //CJK UNIFIED IDEOGRAPH - 0xEFE2: 0x6C40, //CJK UNIFIED IDEOGRAPH - 0xEFE3: 0x6DC0, //CJK UNIFIED IDEOGRAPH - 0xEFE4: 0x6DE8, //CJK UNIFIED IDEOGRAPH - 0xEFE5: 0x6E1F, //CJK UNIFIED IDEOGRAPH - 0xEFE6: 0x6E5E, //CJK UNIFIED IDEOGRAPH - 0xEFE7: 0x701E, //CJK UNIFIED IDEOGRAPH - 0xEFE8: 0x70A1, //CJK UNIFIED IDEOGRAPH - 0xEFE9: 0x738E, //CJK UNIFIED IDEOGRAPH - 0xEFEA: 0x73FD, //CJK UNIFIED IDEOGRAPH - 0xEFEB: 0x753A, //CJK UNIFIED IDEOGRAPH - 0xEFEC: 0x775B, //CJK UNIFIED IDEOGRAPH - 0xEFED: 0x7887, //CJK UNIFIED IDEOGRAPH - 0xEFEE: 0x798E, //CJK UNIFIED IDEOGRAPH - 0xEFEF: 0x7A0B, //CJK UNIFIED IDEOGRAPH - 0xEFF0: 0x7A7D, //CJK UNIFIED IDEOGRAPH - 0xEFF1: 0x7CBE, //CJK UNIFIED IDEOGRAPH - 0xEFF2: 0x7D8E, //CJK UNIFIED IDEOGRAPH - 0xEFF3: 0x8247, //CJK UNIFIED IDEOGRAPH - 0xEFF4: 0x8A02, //CJK UNIFIED IDEOGRAPH - 0xEFF5: 0x8AEA, //CJK UNIFIED IDEOGRAPH - 0xEFF6: 0x8C9E, //CJK UNIFIED IDEOGRAPH - 0xEFF7: 0x912D, //CJK UNIFIED IDEOGRAPH - 0xEFF8: 0x914A, //CJK UNIFIED IDEOGRAPH - 0xEFF9: 0x91D8, //CJK UNIFIED IDEOGRAPH - 0xEFFA: 0x9266, //CJK UNIFIED IDEOGRAPH - 0xEFFB: 0x92CC, //CJK UNIFIED IDEOGRAPH - 0xEFFC: 0x9320, //CJK UNIFIED IDEOGRAPH - 0xEFFD: 0x9706, //CJK UNIFIED IDEOGRAPH - 0xEFFE: 0x9756, //CJK UNIFIED IDEOGRAPH - 0xF0A1: 0x975C, //CJK UNIFIED IDEOGRAPH - 0xF0A2: 0x9802, //CJK UNIFIED IDEOGRAPH - 0xF0A3: 0x9F0E, //CJK UNIFIED IDEOGRAPH - 0xF0A4: 0x5236, //CJK UNIFIED IDEOGRAPH - 0xF0A5: 0x5291, //CJK UNIFIED IDEOGRAPH - 0xF0A6: 0x557C, //CJK UNIFIED IDEOGRAPH - 0xF0A7: 0x5824, //CJK UNIFIED IDEOGRAPH - 0xF0A8: 0x5E1D, //CJK UNIFIED IDEOGRAPH - 0xF0A9: 0x5F1F, //CJK UNIFIED IDEOGRAPH - 0xF0AA: 0x608C, //CJK UNIFIED IDEOGRAPH - 0xF0AB: 0x63D0, //CJK UNIFIED IDEOGRAPH - 0xF0AC: 0x68AF, //CJK UNIFIED IDEOGRAPH - 0xF0AD: 0x6FDF, //CJK UNIFIED IDEOGRAPH - 0xF0AE: 0x796D, //CJK UNIFIED IDEOGRAPH - 0xF0AF: 0x7B2C, //CJK UNIFIED IDEOGRAPH - 0xF0B0: 0x81CD, //CJK UNIFIED IDEOGRAPH - 0xF0B1: 0x85BA, //CJK UNIFIED IDEOGRAPH - 0xF0B2: 0x88FD, //CJK UNIFIED IDEOGRAPH - 0xF0B3: 0x8AF8, //CJK UNIFIED IDEOGRAPH - 0xF0B4: 0x8E44, //CJK UNIFIED IDEOGRAPH - 0xF0B5: 0x918D, //CJK UNIFIED IDEOGRAPH - 0xF0B6: 0x9664, //CJK UNIFIED IDEOGRAPH - 0xF0B7: 0x969B, //CJK UNIFIED IDEOGRAPH - 0xF0B8: 0x973D, //CJK UNIFIED IDEOGRAPH - 0xF0B9: 0x984C, //CJK UNIFIED IDEOGRAPH - 0xF0BA: 0x9F4A, //CJK UNIFIED IDEOGRAPH - 0xF0BB: 0x4FCE, //CJK UNIFIED IDEOGRAPH - 0xF0BC: 0x5146, //CJK UNIFIED IDEOGRAPH - 0xF0BD: 0x51CB, //CJK UNIFIED IDEOGRAPH - 0xF0BE: 0x52A9, //CJK UNIFIED IDEOGRAPH - 0xF0BF: 0x5632, //CJK UNIFIED IDEOGRAPH - 0xF0C0: 0x5F14, //CJK UNIFIED IDEOGRAPH - 0xF0C1: 0x5F6B, //CJK UNIFIED IDEOGRAPH - 0xF0C2: 0x63AA, //CJK UNIFIED IDEOGRAPH - 0xF0C3: 0x64CD, //CJK UNIFIED IDEOGRAPH - 0xF0C4: 0x65E9, //CJK UNIFIED IDEOGRAPH - 0xF0C5: 0x6641, //CJK UNIFIED IDEOGRAPH - 0xF0C6: 0x66FA, //CJK UNIFIED IDEOGRAPH - 0xF0C7: 0x66F9, //CJK UNIFIED IDEOGRAPH - 0xF0C8: 0x671D, //CJK UNIFIED IDEOGRAPH - 0xF0C9: 0x689D, //CJK UNIFIED IDEOGRAPH - 0xF0CA: 0x68D7, //CJK UNIFIED IDEOGRAPH - 0xF0CB: 0x69FD, //CJK UNIFIED IDEOGRAPH - 0xF0CC: 0x6F15, //CJK UNIFIED IDEOGRAPH - 0xF0CD: 0x6F6E, //CJK UNIFIED IDEOGRAPH - 0xF0CE: 0x7167, //CJK UNIFIED IDEOGRAPH - 0xF0CF: 0x71E5, //CJK UNIFIED IDEOGRAPH - 0xF0D0: 0x722A, //CJK UNIFIED IDEOGRAPH - 0xF0D1: 0x74AA, //CJK UNIFIED IDEOGRAPH - 0xF0D2: 0x773A, //CJK UNIFIED IDEOGRAPH - 0xF0D3: 0x7956, //CJK UNIFIED IDEOGRAPH - 0xF0D4: 0x795A, //CJK UNIFIED IDEOGRAPH - 0xF0D5: 0x79DF, //CJK UNIFIED IDEOGRAPH - 0xF0D6: 0x7A20, //CJK UNIFIED IDEOGRAPH - 0xF0D7: 0x7A95, //CJK UNIFIED IDEOGRAPH - 0xF0D8: 0x7C97, //CJK UNIFIED IDEOGRAPH - 0xF0D9: 0x7CDF, //CJK UNIFIED IDEOGRAPH - 0xF0DA: 0x7D44, //CJK UNIFIED IDEOGRAPH - 0xF0DB: 0x7E70, //CJK UNIFIED IDEOGRAPH - 0xF0DC: 0x8087, //CJK UNIFIED IDEOGRAPH - 0xF0DD: 0x85FB, //CJK UNIFIED IDEOGRAPH - 0xF0DE: 0x86A4, //CJK UNIFIED IDEOGRAPH - 0xF0DF: 0x8A54, //CJK UNIFIED IDEOGRAPH - 0xF0E0: 0x8ABF, //CJK UNIFIED IDEOGRAPH - 0xF0E1: 0x8D99, //CJK UNIFIED IDEOGRAPH - 0xF0E2: 0x8E81, //CJK UNIFIED IDEOGRAPH - 0xF0E3: 0x9020, //CJK UNIFIED IDEOGRAPH - 0xF0E4: 0x906D, //CJK UNIFIED IDEOGRAPH - 0xF0E5: 0x91E3, //CJK UNIFIED IDEOGRAPH - 0xF0E6: 0x963B, //CJK UNIFIED IDEOGRAPH - 0xF0E7: 0x96D5, //CJK UNIFIED IDEOGRAPH - 0xF0E8: 0x9CE5, //CJK UNIFIED IDEOGRAPH - 0xF0E9: 0x65CF, //CJK UNIFIED IDEOGRAPH - 0xF0EA: 0x7C07, //CJK UNIFIED IDEOGRAPH - 0xF0EB: 0x8DB3, //CJK UNIFIED IDEOGRAPH - 0xF0EC: 0x93C3, //CJK UNIFIED IDEOGRAPH - 0xF0ED: 0x5B58, //CJK UNIFIED IDEOGRAPH - 0xF0EE: 0x5C0A, //CJK UNIFIED IDEOGRAPH - 0xF0EF: 0x5352, //CJK UNIFIED IDEOGRAPH - 0xF0F0: 0x62D9, //CJK UNIFIED IDEOGRAPH - 0xF0F1: 0x731D, //CJK UNIFIED IDEOGRAPH - 0xF0F2: 0x5027, //CJK UNIFIED IDEOGRAPH - 0xF0F3: 0x5B97, //CJK UNIFIED IDEOGRAPH - 0xF0F4: 0x5F9E, //CJK UNIFIED IDEOGRAPH - 0xF0F5: 0x60B0, //CJK UNIFIED IDEOGRAPH - 0xF0F6: 0x616B, //CJK UNIFIED IDEOGRAPH - 0xF0F7: 0x68D5, //CJK UNIFIED IDEOGRAPH - 0xF0F8: 0x6DD9, //CJK UNIFIED IDEOGRAPH - 0xF0F9: 0x742E, //CJK UNIFIED IDEOGRAPH - 0xF0FA: 0x7A2E, //CJK UNIFIED IDEOGRAPH - 0xF0FB: 0x7D42, //CJK UNIFIED IDEOGRAPH - 0xF0FC: 0x7D9C, //CJK UNIFIED IDEOGRAPH - 0xF0FD: 0x7E31, //CJK UNIFIED IDEOGRAPH - 0xF0FE: 0x816B, //CJK UNIFIED IDEOGRAPH - 0xF1A1: 0x8E2A, //CJK UNIFIED IDEOGRAPH - 0xF1A2: 0x8E35, //CJK UNIFIED IDEOGRAPH - 0xF1A3: 0x937E, //CJK UNIFIED IDEOGRAPH - 0xF1A4: 0x9418, //CJK UNIFIED IDEOGRAPH - 0xF1A5: 0x4F50, //CJK UNIFIED IDEOGRAPH - 0xF1A6: 0x5750, //CJK UNIFIED IDEOGRAPH - 0xF1A7: 0x5DE6, //CJK UNIFIED IDEOGRAPH - 0xF1A8: 0x5EA7, //CJK UNIFIED IDEOGRAPH - 0xF1A9: 0x632B, //CJK UNIFIED IDEOGRAPH - 0xF1AA: 0x7F6A, //CJK UNIFIED IDEOGRAPH - 0xF1AB: 0x4E3B, //CJK UNIFIED IDEOGRAPH - 0xF1AC: 0x4F4F, //CJK UNIFIED IDEOGRAPH - 0xF1AD: 0x4F8F, //CJK UNIFIED IDEOGRAPH - 0xF1AE: 0x505A, //CJK UNIFIED IDEOGRAPH - 0xF1AF: 0x59DD, //CJK UNIFIED IDEOGRAPH - 0xF1B0: 0x80C4, //CJK UNIFIED IDEOGRAPH - 0xF1B1: 0x546A, //CJK UNIFIED IDEOGRAPH - 0xF1B2: 0x5468, //CJK UNIFIED IDEOGRAPH - 0xF1B3: 0x55FE, //CJK UNIFIED IDEOGRAPH - 0xF1B4: 0x594F, //CJK UNIFIED IDEOGRAPH - 0xF1B5: 0x5B99, //CJK UNIFIED IDEOGRAPH - 0xF1B6: 0x5DDE, //CJK UNIFIED IDEOGRAPH - 0xF1B7: 0x5EDA, //CJK UNIFIED IDEOGRAPH - 0xF1B8: 0x665D, //CJK UNIFIED IDEOGRAPH - 0xF1B9: 0x6731, //CJK UNIFIED IDEOGRAPH - 0xF1BA: 0x67F1, //CJK UNIFIED IDEOGRAPH - 0xF1BB: 0x682A, //CJK UNIFIED IDEOGRAPH - 0xF1BC: 0x6CE8, //CJK UNIFIED IDEOGRAPH - 0xF1BD: 0x6D32, //CJK UNIFIED IDEOGRAPH - 0xF1BE: 0x6E4A, //CJK UNIFIED IDEOGRAPH - 0xF1BF: 0x6F8D, //CJK UNIFIED IDEOGRAPH - 0xF1C0: 0x70B7, //CJK UNIFIED IDEOGRAPH - 0xF1C1: 0x73E0, //CJK UNIFIED IDEOGRAPH - 0xF1C2: 0x7587, //CJK UNIFIED IDEOGRAPH - 0xF1C3: 0x7C4C, //CJK UNIFIED IDEOGRAPH - 0xF1C4: 0x7D02, //CJK UNIFIED IDEOGRAPH - 0xF1C5: 0x7D2C, //CJK UNIFIED IDEOGRAPH - 0xF1C6: 0x7DA2, //CJK UNIFIED IDEOGRAPH - 0xF1C7: 0x821F, //CJK UNIFIED IDEOGRAPH - 0xF1C8: 0x86DB, //CJK UNIFIED IDEOGRAPH - 0xF1C9: 0x8A3B, //CJK UNIFIED IDEOGRAPH - 0xF1CA: 0x8A85, //CJK UNIFIED IDEOGRAPH - 0xF1CB: 0x8D70, //CJK UNIFIED IDEOGRAPH - 0xF1CC: 0x8E8A, //CJK UNIFIED IDEOGRAPH - 0xF1CD: 0x8F33, //CJK UNIFIED IDEOGRAPH - 0xF1CE: 0x9031, //CJK UNIFIED IDEOGRAPH - 0xF1CF: 0x914E, //CJK UNIFIED IDEOGRAPH - 0xF1D0: 0x9152, //CJK UNIFIED IDEOGRAPH - 0xF1D1: 0x9444, //CJK UNIFIED IDEOGRAPH - 0xF1D2: 0x99D0, //CJK UNIFIED IDEOGRAPH - 0xF1D3: 0x7AF9, //CJK UNIFIED IDEOGRAPH - 0xF1D4: 0x7CA5, //CJK UNIFIED IDEOGRAPH - 0xF1D5: 0x4FCA, //CJK UNIFIED IDEOGRAPH - 0xF1D6: 0x5101, //CJK UNIFIED IDEOGRAPH - 0xF1D7: 0x51C6, //CJK UNIFIED IDEOGRAPH - 0xF1D8: 0x57C8, //CJK UNIFIED IDEOGRAPH - 0xF1D9: 0x5BEF, //CJK UNIFIED IDEOGRAPH - 0xF1DA: 0x5CFB, //CJK UNIFIED IDEOGRAPH - 0xF1DB: 0x6659, //CJK UNIFIED IDEOGRAPH - 0xF1DC: 0x6A3D, //CJK UNIFIED IDEOGRAPH - 0xF1DD: 0x6D5A, //CJK UNIFIED IDEOGRAPH - 0xF1DE: 0x6E96, //CJK UNIFIED IDEOGRAPH - 0xF1DF: 0x6FEC, //CJK UNIFIED IDEOGRAPH - 0xF1E0: 0x710C, //CJK UNIFIED IDEOGRAPH - 0xF1E1: 0x756F, //CJK UNIFIED IDEOGRAPH - 0xF1E2: 0x7AE3, //CJK UNIFIED IDEOGRAPH - 0xF1E3: 0x8822, //CJK UNIFIED IDEOGRAPH - 0xF1E4: 0x9021, //CJK UNIFIED IDEOGRAPH - 0xF1E5: 0x9075, //CJK UNIFIED IDEOGRAPH - 0xF1E6: 0x96CB, //CJK UNIFIED IDEOGRAPH - 0xF1E7: 0x99FF, //CJK UNIFIED IDEOGRAPH - 0xF1E8: 0x8301, //CJK UNIFIED IDEOGRAPH - 0xF1E9: 0x4E2D, //CJK UNIFIED IDEOGRAPH - 0xF1EA: 0x4EF2, //CJK UNIFIED IDEOGRAPH - 0xF1EB: 0x8846, //CJK UNIFIED IDEOGRAPH - 0xF1EC: 0x91CD, //CJK UNIFIED IDEOGRAPH - 0xF1ED: 0x537D, //CJK UNIFIED IDEOGRAPH - 0xF1EE: 0x6ADB, //CJK UNIFIED IDEOGRAPH - 0xF1EF: 0x696B, //CJK UNIFIED IDEOGRAPH - 0xF1F0: 0x6C41, //CJK UNIFIED IDEOGRAPH - 0xF1F1: 0x847A, //CJK UNIFIED IDEOGRAPH - 0xF1F2: 0x589E, //CJK UNIFIED IDEOGRAPH - 0xF1F3: 0x618E, //CJK UNIFIED IDEOGRAPH - 0xF1F4: 0x66FE, //CJK UNIFIED IDEOGRAPH - 0xF1F5: 0x62EF, //CJK UNIFIED IDEOGRAPH - 0xF1F6: 0x70DD, //CJK UNIFIED IDEOGRAPH - 0xF1F7: 0x7511, //CJK UNIFIED IDEOGRAPH - 0xF1F8: 0x75C7, //CJK UNIFIED IDEOGRAPH - 0xF1F9: 0x7E52, //CJK UNIFIED IDEOGRAPH - 0xF1FA: 0x84B8, //CJK UNIFIED IDEOGRAPH - 0xF1FB: 0x8B49, //CJK UNIFIED IDEOGRAPH - 0xF1FC: 0x8D08, //CJK UNIFIED IDEOGRAPH - 0xF1FD: 0x4E4B, //CJK UNIFIED IDEOGRAPH - 0xF1FE: 0x53EA, //CJK UNIFIED IDEOGRAPH - 0xF2A1: 0x54AB, //CJK UNIFIED IDEOGRAPH - 0xF2A2: 0x5730, //CJK UNIFIED IDEOGRAPH - 0xF2A3: 0x5740, //CJK UNIFIED IDEOGRAPH - 0xF2A4: 0x5FD7, //CJK UNIFIED IDEOGRAPH - 0xF2A5: 0x6301, //CJK UNIFIED IDEOGRAPH - 0xF2A6: 0x6307, //CJK UNIFIED IDEOGRAPH - 0xF2A7: 0x646F, //CJK UNIFIED IDEOGRAPH - 0xF2A8: 0x652F, //CJK UNIFIED IDEOGRAPH - 0xF2A9: 0x65E8, //CJK UNIFIED IDEOGRAPH - 0xF2AA: 0x667A, //CJK UNIFIED IDEOGRAPH - 0xF2AB: 0x679D, //CJK UNIFIED IDEOGRAPH - 0xF2AC: 0x67B3, //CJK UNIFIED IDEOGRAPH - 0xF2AD: 0x6B62, //CJK UNIFIED IDEOGRAPH - 0xF2AE: 0x6C60, //CJK UNIFIED IDEOGRAPH - 0xF2AF: 0x6C9A, //CJK UNIFIED IDEOGRAPH - 0xF2B0: 0x6F2C, //CJK UNIFIED IDEOGRAPH - 0xF2B1: 0x77E5, //CJK UNIFIED IDEOGRAPH - 0xF2B2: 0x7825, //CJK UNIFIED IDEOGRAPH - 0xF2B3: 0x7949, //CJK UNIFIED IDEOGRAPH - 0xF2B4: 0x7957, //CJK UNIFIED IDEOGRAPH - 0xF2B5: 0x7D19, //CJK UNIFIED IDEOGRAPH - 0xF2B6: 0x80A2, //CJK UNIFIED IDEOGRAPH - 0xF2B7: 0x8102, //CJK UNIFIED IDEOGRAPH - 0xF2B8: 0x81F3, //CJK UNIFIED IDEOGRAPH - 0xF2B9: 0x829D, //CJK UNIFIED IDEOGRAPH - 0xF2BA: 0x82B7, //CJK UNIFIED IDEOGRAPH - 0xF2BB: 0x8718, //CJK UNIFIED IDEOGRAPH - 0xF2BC: 0x8A8C, //CJK UNIFIED IDEOGRAPH - 0xF2BD: 0xF9FC, //CJK COMPATIBILITY IDEOGRAPH - 0xF2BE: 0x8D04, //CJK UNIFIED IDEOGRAPH - 0xF2BF: 0x8DBE, //CJK UNIFIED IDEOGRAPH - 0xF2C0: 0x9072, //CJK UNIFIED IDEOGRAPH - 0xF2C1: 0x76F4, //CJK UNIFIED IDEOGRAPH - 0xF2C2: 0x7A19, //CJK UNIFIED IDEOGRAPH - 0xF2C3: 0x7A37, //CJK UNIFIED IDEOGRAPH - 0xF2C4: 0x7E54, //CJK UNIFIED IDEOGRAPH - 0xF2C5: 0x8077, //CJK UNIFIED IDEOGRAPH - 0xF2C6: 0x5507, //CJK UNIFIED IDEOGRAPH - 0xF2C7: 0x55D4, //CJK UNIFIED IDEOGRAPH - 0xF2C8: 0x5875, //CJK UNIFIED IDEOGRAPH - 0xF2C9: 0x632F, //CJK UNIFIED IDEOGRAPH - 0xF2CA: 0x6422, //CJK UNIFIED IDEOGRAPH - 0xF2CB: 0x6649, //CJK UNIFIED IDEOGRAPH - 0xF2CC: 0x664B, //CJK UNIFIED IDEOGRAPH - 0xF2CD: 0x686D, //CJK UNIFIED IDEOGRAPH - 0xF2CE: 0x699B, //CJK UNIFIED IDEOGRAPH - 0xF2CF: 0x6B84, //CJK UNIFIED IDEOGRAPH - 0xF2D0: 0x6D25, //CJK UNIFIED IDEOGRAPH - 0xF2D1: 0x6EB1, //CJK UNIFIED IDEOGRAPH - 0xF2D2: 0x73CD, //CJK UNIFIED IDEOGRAPH - 0xF2D3: 0x7468, //CJK UNIFIED IDEOGRAPH - 0xF2D4: 0x74A1, //CJK UNIFIED IDEOGRAPH - 0xF2D5: 0x755B, //CJK UNIFIED IDEOGRAPH - 0xF2D6: 0x75B9, //CJK UNIFIED IDEOGRAPH - 0xF2D7: 0x76E1, //CJK UNIFIED IDEOGRAPH - 0xF2D8: 0x771E, //CJK UNIFIED IDEOGRAPH - 0xF2D9: 0x778B, //CJK UNIFIED IDEOGRAPH - 0xF2DA: 0x79E6, //CJK UNIFIED IDEOGRAPH - 0xF2DB: 0x7E09, //CJK UNIFIED IDEOGRAPH - 0xF2DC: 0x7E1D, //CJK UNIFIED IDEOGRAPH - 0xF2DD: 0x81FB, //CJK UNIFIED IDEOGRAPH - 0xF2DE: 0x852F, //CJK UNIFIED IDEOGRAPH - 0xF2DF: 0x8897, //CJK UNIFIED IDEOGRAPH - 0xF2E0: 0x8A3A, //CJK UNIFIED IDEOGRAPH - 0xF2E1: 0x8CD1, //CJK UNIFIED IDEOGRAPH - 0xF2E2: 0x8EEB, //CJK UNIFIED IDEOGRAPH - 0xF2E3: 0x8FB0, //CJK UNIFIED IDEOGRAPH - 0xF2E4: 0x9032, //CJK UNIFIED IDEOGRAPH - 0xF2E5: 0x93AD, //CJK UNIFIED IDEOGRAPH - 0xF2E6: 0x9663, //CJK UNIFIED IDEOGRAPH - 0xF2E7: 0x9673, //CJK UNIFIED IDEOGRAPH - 0xF2E8: 0x9707, //CJK UNIFIED IDEOGRAPH - 0xF2E9: 0x4F84, //CJK UNIFIED IDEOGRAPH - 0xF2EA: 0x53F1, //CJK UNIFIED IDEOGRAPH - 0xF2EB: 0x59EA, //CJK UNIFIED IDEOGRAPH - 0xF2EC: 0x5AC9, //CJK UNIFIED IDEOGRAPH - 0xF2ED: 0x5E19, //CJK UNIFIED IDEOGRAPH - 0xF2EE: 0x684E, //CJK UNIFIED IDEOGRAPH - 0xF2EF: 0x74C6, //CJK UNIFIED IDEOGRAPH - 0xF2F0: 0x75BE, //CJK UNIFIED IDEOGRAPH - 0xF2F1: 0x79E9, //CJK UNIFIED IDEOGRAPH - 0xF2F2: 0x7A92, //CJK UNIFIED IDEOGRAPH - 0xF2F3: 0x81A3, //CJK UNIFIED IDEOGRAPH - 0xF2F4: 0x86ED, //CJK UNIFIED IDEOGRAPH - 0xF2F5: 0x8CEA, //CJK UNIFIED IDEOGRAPH - 0xF2F6: 0x8DCC, //CJK UNIFIED IDEOGRAPH - 0xF2F7: 0x8FED, //CJK UNIFIED IDEOGRAPH - 0xF2F8: 0x659F, //CJK UNIFIED IDEOGRAPH - 0xF2F9: 0x6715, //CJK UNIFIED IDEOGRAPH - 0xF2FA: 0xF9FD, //CJK COMPATIBILITY IDEOGRAPH - 0xF2FB: 0x57F7, //CJK UNIFIED IDEOGRAPH - 0xF2FC: 0x6F57, //CJK UNIFIED IDEOGRAPH - 0xF2FD: 0x7DDD, //CJK UNIFIED IDEOGRAPH - 0xF2FE: 0x8F2F, //CJK UNIFIED IDEOGRAPH - 0xF3A1: 0x93F6, //CJK UNIFIED IDEOGRAPH - 0xF3A2: 0x96C6, //CJK UNIFIED IDEOGRAPH - 0xF3A3: 0x5FB5, //CJK UNIFIED IDEOGRAPH - 0xF3A4: 0x61F2, //CJK UNIFIED IDEOGRAPH - 0xF3A5: 0x6F84, //CJK UNIFIED IDEOGRAPH - 0xF3A6: 0x4E14, //CJK UNIFIED IDEOGRAPH - 0xF3A7: 0x4F98, //CJK UNIFIED IDEOGRAPH - 0xF3A8: 0x501F, //CJK UNIFIED IDEOGRAPH - 0xF3A9: 0x53C9, //CJK UNIFIED IDEOGRAPH - 0xF3AA: 0x55DF, //CJK UNIFIED IDEOGRAPH - 0xF3AB: 0x5D6F, //CJK UNIFIED IDEOGRAPH - 0xF3AC: 0x5DEE, //CJK UNIFIED IDEOGRAPH - 0xF3AD: 0x6B21, //CJK UNIFIED IDEOGRAPH - 0xF3AE: 0x6B64, //CJK UNIFIED IDEOGRAPH - 0xF3AF: 0x78CB, //CJK UNIFIED IDEOGRAPH - 0xF3B0: 0x7B9A, //CJK UNIFIED IDEOGRAPH - 0xF3B1: 0xF9FE, //CJK COMPATIBILITY IDEOGRAPH - 0xF3B2: 0x8E49, //CJK UNIFIED IDEOGRAPH - 0xF3B3: 0x8ECA, //CJK UNIFIED IDEOGRAPH - 0xF3B4: 0x906E, //CJK UNIFIED IDEOGRAPH - 0xF3B5: 0x6349, //CJK UNIFIED IDEOGRAPH - 0xF3B6: 0x643E, //CJK UNIFIED IDEOGRAPH - 0xF3B7: 0x7740, //CJK UNIFIED IDEOGRAPH - 0xF3B8: 0x7A84, //CJK UNIFIED IDEOGRAPH - 0xF3B9: 0x932F, //CJK UNIFIED IDEOGRAPH - 0xF3BA: 0x947F, //CJK UNIFIED IDEOGRAPH - 0xF3BB: 0x9F6A, //CJK UNIFIED IDEOGRAPH - 0xF3BC: 0x64B0, //CJK UNIFIED IDEOGRAPH - 0xF3BD: 0x6FAF, //CJK UNIFIED IDEOGRAPH - 0xF3BE: 0x71E6, //CJK UNIFIED IDEOGRAPH - 0xF3BF: 0x74A8, //CJK UNIFIED IDEOGRAPH - 0xF3C0: 0x74DA, //CJK UNIFIED IDEOGRAPH - 0xF3C1: 0x7AC4, //CJK UNIFIED IDEOGRAPH - 0xF3C2: 0x7C12, //CJK UNIFIED IDEOGRAPH - 0xF3C3: 0x7E82, //CJK UNIFIED IDEOGRAPH - 0xF3C4: 0x7CB2, //CJK UNIFIED IDEOGRAPH - 0xF3C5: 0x7E98, //CJK UNIFIED IDEOGRAPH - 0xF3C6: 0x8B9A, //CJK UNIFIED IDEOGRAPH - 0xF3C7: 0x8D0A, //CJK UNIFIED IDEOGRAPH - 0xF3C8: 0x947D, //CJK UNIFIED IDEOGRAPH - 0xF3C9: 0x9910, //CJK UNIFIED IDEOGRAPH - 0xF3CA: 0x994C, //CJK UNIFIED IDEOGRAPH - 0xF3CB: 0x5239, //CJK UNIFIED IDEOGRAPH - 0xF3CC: 0x5BDF, //CJK UNIFIED IDEOGRAPH - 0xF3CD: 0x64E6, //CJK UNIFIED IDEOGRAPH - 0xF3CE: 0x672D, //CJK UNIFIED IDEOGRAPH - 0xF3CF: 0x7D2E, //CJK UNIFIED IDEOGRAPH - 0xF3D0: 0x50ED, //CJK UNIFIED IDEOGRAPH - 0xF3D1: 0x53C3, //CJK UNIFIED IDEOGRAPH - 0xF3D2: 0x5879, //CJK UNIFIED IDEOGRAPH - 0xF3D3: 0x6158, //CJK UNIFIED IDEOGRAPH - 0xF3D4: 0x6159, //CJK UNIFIED IDEOGRAPH - 0xF3D5: 0x61FA, //CJK UNIFIED IDEOGRAPH - 0xF3D6: 0x65AC, //CJK UNIFIED IDEOGRAPH - 0xF3D7: 0x7AD9, //CJK UNIFIED IDEOGRAPH - 0xF3D8: 0x8B92, //CJK UNIFIED IDEOGRAPH - 0xF3D9: 0x8B96, //CJK UNIFIED IDEOGRAPH - 0xF3DA: 0x5009, //CJK UNIFIED IDEOGRAPH - 0xF3DB: 0x5021, //CJK UNIFIED IDEOGRAPH - 0xF3DC: 0x5275, //CJK UNIFIED IDEOGRAPH - 0xF3DD: 0x5531, //CJK UNIFIED IDEOGRAPH - 0xF3DE: 0x5A3C, //CJK UNIFIED IDEOGRAPH - 0xF3DF: 0x5EE0, //CJK UNIFIED IDEOGRAPH - 0xF3E0: 0x5F70, //CJK UNIFIED IDEOGRAPH - 0xF3E1: 0x6134, //CJK UNIFIED IDEOGRAPH - 0xF3E2: 0x655E, //CJK UNIFIED IDEOGRAPH - 0xF3E3: 0x660C, //CJK UNIFIED IDEOGRAPH - 0xF3E4: 0x6636, //CJK UNIFIED IDEOGRAPH - 0xF3E5: 0x66A2, //CJK UNIFIED IDEOGRAPH - 0xF3E6: 0x69CD, //CJK UNIFIED IDEOGRAPH - 0xF3E7: 0x6EC4, //CJK UNIFIED IDEOGRAPH - 0xF3E8: 0x6F32, //CJK UNIFIED IDEOGRAPH - 0xF3E9: 0x7316, //CJK UNIFIED IDEOGRAPH - 0xF3EA: 0x7621, //CJK UNIFIED IDEOGRAPH - 0xF3EB: 0x7A93, //CJK UNIFIED IDEOGRAPH - 0xF3EC: 0x8139, //CJK UNIFIED IDEOGRAPH - 0xF3ED: 0x8259, //CJK UNIFIED IDEOGRAPH - 0xF3EE: 0x83D6, //CJK UNIFIED IDEOGRAPH - 0xF3EF: 0x84BC, //CJK UNIFIED IDEOGRAPH - 0xF3F0: 0x50B5, //CJK UNIFIED IDEOGRAPH - 0xF3F1: 0x57F0, //CJK UNIFIED IDEOGRAPH - 0xF3F2: 0x5BC0, //CJK UNIFIED IDEOGRAPH - 0xF3F3: 0x5BE8, //CJK UNIFIED IDEOGRAPH - 0xF3F4: 0x5F69, //CJK UNIFIED IDEOGRAPH - 0xF3F5: 0x63A1, //CJK UNIFIED IDEOGRAPH - 0xF3F6: 0x7826, //CJK UNIFIED IDEOGRAPH - 0xF3F7: 0x7DB5, //CJK UNIFIED IDEOGRAPH - 0xF3F8: 0x83DC, //CJK UNIFIED IDEOGRAPH - 0xF3F9: 0x8521, //CJK UNIFIED IDEOGRAPH - 0xF3FA: 0x91C7, //CJK UNIFIED IDEOGRAPH - 0xF3FB: 0x91F5, //CJK UNIFIED IDEOGRAPH - 0xF3FC: 0x518A, //CJK UNIFIED IDEOGRAPH - 0xF3FD: 0x67F5, //CJK UNIFIED IDEOGRAPH - 0xF3FE: 0x7B56, //CJK UNIFIED IDEOGRAPH - 0xF4A1: 0x8CAC, //CJK UNIFIED IDEOGRAPH - 0xF4A2: 0x51C4, //CJK UNIFIED IDEOGRAPH - 0xF4A3: 0x59BB, //CJK UNIFIED IDEOGRAPH - 0xF4A4: 0x60BD, //CJK UNIFIED IDEOGRAPH - 0xF4A5: 0x8655, //CJK UNIFIED IDEOGRAPH - 0xF4A6: 0x501C, //CJK UNIFIED IDEOGRAPH - 0xF4A7: 0xF9FF, //CJK COMPATIBILITY IDEOGRAPH - 0xF4A8: 0x5254, //CJK UNIFIED IDEOGRAPH - 0xF4A9: 0x5C3A, //CJK UNIFIED IDEOGRAPH - 0xF4AA: 0x617D, //CJK UNIFIED IDEOGRAPH - 0xF4AB: 0x621A, //CJK UNIFIED IDEOGRAPH - 0xF4AC: 0x62D3, //CJK UNIFIED IDEOGRAPH - 0xF4AD: 0x64F2, //CJK UNIFIED IDEOGRAPH - 0xF4AE: 0x65A5, //CJK UNIFIED IDEOGRAPH - 0xF4AF: 0x6ECC, //CJK UNIFIED IDEOGRAPH - 0xF4B0: 0x7620, //CJK UNIFIED IDEOGRAPH - 0xF4B1: 0x810A, //CJK UNIFIED IDEOGRAPH - 0xF4B2: 0x8E60, //CJK UNIFIED IDEOGRAPH - 0xF4B3: 0x965F, //CJK UNIFIED IDEOGRAPH - 0xF4B4: 0x96BB, //CJK UNIFIED IDEOGRAPH - 0xF4B5: 0x4EDF, //CJK UNIFIED IDEOGRAPH - 0xF4B6: 0x5343, //CJK UNIFIED IDEOGRAPH - 0xF4B7: 0x5598, //CJK UNIFIED IDEOGRAPH - 0xF4B8: 0x5929, //CJK UNIFIED IDEOGRAPH - 0xF4B9: 0x5DDD, //CJK UNIFIED IDEOGRAPH - 0xF4BA: 0x64C5, //CJK UNIFIED IDEOGRAPH - 0xF4BB: 0x6CC9, //CJK UNIFIED IDEOGRAPH - 0xF4BC: 0x6DFA, //CJK UNIFIED IDEOGRAPH - 0xF4BD: 0x7394, //CJK UNIFIED IDEOGRAPH - 0xF4BE: 0x7A7F, //CJK UNIFIED IDEOGRAPH - 0xF4BF: 0x821B, //CJK UNIFIED IDEOGRAPH - 0xF4C0: 0x85A6, //CJK UNIFIED IDEOGRAPH - 0xF4C1: 0x8CE4, //CJK UNIFIED IDEOGRAPH - 0xF4C2: 0x8E10, //CJK UNIFIED IDEOGRAPH - 0xF4C3: 0x9077, //CJK UNIFIED IDEOGRAPH - 0xF4C4: 0x91E7, //CJK UNIFIED IDEOGRAPH - 0xF4C5: 0x95E1, //CJK UNIFIED IDEOGRAPH - 0xF4C6: 0x9621, //CJK UNIFIED IDEOGRAPH - 0xF4C7: 0x97C6, //CJK UNIFIED IDEOGRAPH - 0xF4C8: 0x51F8, //CJK UNIFIED IDEOGRAPH - 0xF4C9: 0x54F2, //CJK UNIFIED IDEOGRAPH - 0xF4CA: 0x5586, //CJK UNIFIED IDEOGRAPH - 0xF4CB: 0x5FB9, //CJK UNIFIED IDEOGRAPH - 0xF4CC: 0x64A4, //CJK UNIFIED IDEOGRAPH - 0xF4CD: 0x6F88, //CJK UNIFIED IDEOGRAPH - 0xF4CE: 0x7DB4, //CJK UNIFIED IDEOGRAPH - 0xF4CF: 0x8F1F, //CJK UNIFIED IDEOGRAPH - 0xF4D0: 0x8F4D, //CJK UNIFIED IDEOGRAPH - 0xF4D1: 0x9435, //CJK UNIFIED IDEOGRAPH - 0xF4D2: 0x50C9, //CJK UNIFIED IDEOGRAPH - 0xF4D3: 0x5C16, //CJK UNIFIED IDEOGRAPH - 0xF4D4: 0x6CBE, //CJK UNIFIED IDEOGRAPH - 0xF4D5: 0x6DFB, //CJK UNIFIED IDEOGRAPH - 0xF4D6: 0x751B, //CJK UNIFIED IDEOGRAPH - 0xF4D7: 0x77BB, //CJK UNIFIED IDEOGRAPH - 0xF4D8: 0x7C3D, //CJK UNIFIED IDEOGRAPH - 0xF4D9: 0x7C64, //CJK UNIFIED IDEOGRAPH - 0xF4DA: 0x8A79, //CJK UNIFIED IDEOGRAPH - 0xF4DB: 0x8AC2, //CJK UNIFIED IDEOGRAPH - 0xF4DC: 0x581E, //CJK UNIFIED IDEOGRAPH - 0xF4DD: 0x59BE, //CJK UNIFIED IDEOGRAPH - 0xF4DE: 0x5E16, //CJK UNIFIED IDEOGRAPH - 0xF4DF: 0x6377, //CJK UNIFIED IDEOGRAPH - 0xF4E0: 0x7252, //CJK UNIFIED IDEOGRAPH - 0xF4E1: 0x758A, //CJK UNIFIED IDEOGRAPH - 0xF4E2: 0x776B, //CJK UNIFIED IDEOGRAPH - 0xF4E3: 0x8ADC, //CJK UNIFIED IDEOGRAPH - 0xF4E4: 0x8CBC, //CJK UNIFIED IDEOGRAPH - 0xF4E5: 0x8F12, //CJK UNIFIED IDEOGRAPH - 0xF4E6: 0x5EF3, //CJK UNIFIED IDEOGRAPH - 0xF4E7: 0x6674, //CJK UNIFIED IDEOGRAPH - 0xF4E8: 0x6DF8, //CJK UNIFIED IDEOGRAPH - 0xF4E9: 0x807D, //CJK UNIFIED IDEOGRAPH - 0xF4EA: 0x83C1, //CJK UNIFIED IDEOGRAPH - 0xF4EB: 0x8ACB, //CJK UNIFIED IDEOGRAPH - 0xF4EC: 0x9751, //CJK UNIFIED IDEOGRAPH - 0xF4ED: 0x9BD6, //CJK UNIFIED IDEOGRAPH - 0xF4EE: 0xFA00, //CJK COMPATIBILITY IDEOGRAPH - 0xF4EF: 0x5243, //CJK UNIFIED IDEOGRAPH - 0xF4F0: 0x66FF, //CJK UNIFIED IDEOGRAPH - 0xF4F1: 0x6D95, //CJK UNIFIED IDEOGRAPH - 0xF4F2: 0x6EEF, //CJK UNIFIED IDEOGRAPH - 0xF4F3: 0x7DE0, //CJK UNIFIED IDEOGRAPH - 0xF4F4: 0x8AE6, //CJK UNIFIED IDEOGRAPH - 0xF4F5: 0x902E, //CJK UNIFIED IDEOGRAPH - 0xF4F6: 0x905E, //CJK UNIFIED IDEOGRAPH - 0xF4F7: 0x9AD4, //CJK UNIFIED IDEOGRAPH - 0xF4F8: 0x521D, //CJK UNIFIED IDEOGRAPH - 0xF4F9: 0x527F, //CJK UNIFIED IDEOGRAPH - 0xF4FA: 0x54E8, //CJK UNIFIED IDEOGRAPH - 0xF4FB: 0x6194, //CJK UNIFIED IDEOGRAPH - 0xF4FC: 0x6284, //CJK UNIFIED IDEOGRAPH - 0xF4FD: 0x62DB, //CJK UNIFIED IDEOGRAPH - 0xF4FE: 0x68A2, //CJK UNIFIED IDEOGRAPH - 0xF5A1: 0x6912, //CJK UNIFIED IDEOGRAPH - 0xF5A2: 0x695A, //CJK UNIFIED IDEOGRAPH - 0xF5A3: 0x6A35, //CJK UNIFIED IDEOGRAPH - 0xF5A4: 0x7092, //CJK UNIFIED IDEOGRAPH - 0xF5A5: 0x7126, //CJK UNIFIED IDEOGRAPH - 0xF5A6: 0x785D, //CJK UNIFIED IDEOGRAPH - 0xF5A7: 0x7901, //CJK UNIFIED IDEOGRAPH - 0xF5A8: 0x790E, //CJK UNIFIED IDEOGRAPH - 0xF5A9: 0x79D2, //CJK UNIFIED IDEOGRAPH - 0xF5AA: 0x7A0D, //CJK UNIFIED IDEOGRAPH - 0xF5AB: 0x8096, //CJK UNIFIED IDEOGRAPH - 0xF5AC: 0x8278, //CJK UNIFIED IDEOGRAPH - 0xF5AD: 0x82D5, //CJK UNIFIED IDEOGRAPH - 0xF5AE: 0x8349, //CJK UNIFIED IDEOGRAPH - 0xF5AF: 0x8549, //CJK UNIFIED IDEOGRAPH - 0xF5B0: 0x8C82, //CJK UNIFIED IDEOGRAPH - 0xF5B1: 0x8D85, //CJK UNIFIED IDEOGRAPH - 0xF5B2: 0x9162, //CJK UNIFIED IDEOGRAPH - 0xF5B3: 0x918B, //CJK UNIFIED IDEOGRAPH - 0xF5B4: 0x91AE, //CJK UNIFIED IDEOGRAPH - 0xF5B5: 0x4FC3, //CJK UNIFIED IDEOGRAPH - 0xF5B6: 0x56D1, //CJK UNIFIED IDEOGRAPH - 0xF5B7: 0x71ED, //CJK UNIFIED IDEOGRAPH - 0xF5B8: 0x77D7, //CJK UNIFIED IDEOGRAPH - 0xF5B9: 0x8700, //CJK UNIFIED IDEOGRAPH - 0xF5BA: 0x89F8, //CJK UNIFIED IDEOGRAPH - 0xF5BB: 0x5BF8, //CJK UNIFIED IDEOGRAPH - 0xF5BC: 0x5FD6, //CJK UNIFIED IDEOGRAPH - 0xF5BD: 0x6751, //CJK UNIFIED IDEOGRAPH - 0xF5BE: 0x90A8, //CJK UNIFIED IDEOGRAPH - 0xF5BF: 0x53E2, //CJK UNIFIED IDEOGRAPH - 0xF5C0: 0x585A, //CJK UNIFIED IDEOGRAPH - 0xF5C1: 0x5BF5, //CJK UNIFIED IDEOGRAPH - 0xF5C2: 0x60A4, //CJK UNIFIED IDEOGRAPH - 0xF5C3: 0x6181, //CJK UNIFIED IDEOGRAPH - 0xF5C4: 0x6460, //CJK UNIFIED IDEOGRAPH - 0xF5C5: 0x7E3D, //CJK UNIFIED IDEOGRAPH - 0xF5C6: 0x8070, //CJK UNIFIED IDEOGRAPH - 0xF5C7: 0x8525, //CJK UNIFIED IDEOGRAPH - 0xF5C8: 0x9283, //CJK UNIFIED IDEOGRAPH - 0xF5C9: 0x64AE, //CJK UNIFIED IDEOGRAPH - 0xF5CA: 0x50AC, //CJK UNIFIED IDEOGRAPH - 0xF5CB: 0x5D14, //CJK UNIFIED IDEOGRAPH - 0xF5CC: 0x6700, //CJK UNIFIED IDEOGRAPH - 0xF5CD: 0x589C, //CJK UNIFIED IDEOGRAPH - 0xF5CE: 0x62BD, //CJK UNIFIED IDEOGRAPH - 0xF5CF: 0x63A8, //CJK UNIFIED IDEOGRAPH - 0xF5D0: 0x690E, //CJK UNIFIED IDEOGRAPH - 0xF5D1: 0x6978, //CJK UNIFIED IDEOGRAPH - 0xF5D2: 0x6A1E, //CJK UNIFIED IDEOGRAPH - 0xF5D3: 0x6E6B, //CJK UNIFIED IDEOGRAPH - 0xF5D4: 0x76BA, //CJK UNIFIED IDEOGRAPH - 0xF5D5: 0x79CB, //CJK UNIFIED IDEOGRAPH - 0xF5D6: 0x82BB, //CJK UNIFIED IDEOGRAPH - 0xF5D7: 0x8429, //CJK UNIFIED IDEOGRAPH - 0xF5D8: 0x8ACF, //CJK UNIFIED IDEOGRAPH - 0xF5D9: 0x8DA8, //CJK UNIFIED IDEOGRAPH - 0xF5DA: 0x8FFD, //CJK UNIFIED IDEOGRAPH - 0xF5DB: 0x9112, //CJK UNIFIED IDEOGRAPH - 0xF5DC: 0x914B, //CJK UNIFIED IDEOGRAPH - 0xF5DD: 0x919C, //CJK UNIFIED IDEOGRAPH - 0xF5DE: 0x9310, //CJK UNIFIED IDEOGRAPH - 0xF5DF: 0x9318, //CJK UNIFIED IDEOGRAPH - 0xF5E0: 0x939A, //CJK UNIFIED IDEOGRAPH - 0xF5E1: 0x96DB, //CJK UNIFIED IDEOGRAPH - 0xF5E2: 0x9A36, //CJK UNIFIED IDEOGRAPH - 0xF5E3: 0x9C0D, //CJK UNIFIED IDEOGRAPH - 0xF5E4: 0x4E11, //CJK UNIFIED IDEOGRAPH - 0xF5E5: 0x755C, //CJK UNIFIED IDEOGRAPH - 0xF5E6: 0x795D, //CJK UNIFIED IDEOGRAPH - 0xF5E7: 0x7AFA, //CJK UNIFIED IDEOGRAPH - 0xF5E8: 0x7B51, //CJK UNIFIED IDEOGRAPH - 0xF5E9: 0x7BC9, //CJK UNIFIED IDEOGRAPH - 0xF5EA: 0x7E2E, //CJK UNIFIED IDEOGRAPH - 0xF5EB: 0x84C4, //CJK UNIFIED IDEOGRAPH - 0xF5EC: 0x8E59, //CJK UNIFIED IDEOGRAPH - 0xF5ED: 0x8E74, //CJK UNIFIED IDEOGRAPH - 0xF5EE: 0x8EF8, //CJK UNIFIED IDEOGRAPH - 0xF5EF: 0x9010, //CJK UNIFIED IDEOGRAPH - 0xF5F0: 0x6625, //CJK UNIFIED IDEOGRAPH - 0xF5F1: 0x693F, //CJK UNIFIED IDEOGRAPH - 0xF5F2: 0x7443, //CJK UNIFIED IDEOGRAPH - 0xF5F3: 0x51FA, //CJK UNIFIED IDEOGRAPH - 0xF5F4: 0x672E, //CJK UNIFIED IDEOGRAPH - 0xF5F5: 0x9EDC, //CJK UNIFIED IDEOGRAPH - 0xF5F6: 0x5145, //CJK UNIFIED IDEOGRAPH - 0xF5F7: 0x5FE0, //CJK UNIFIED IDEOGRAPH - 0xF5F8: 0x6C96, //CJK UNIFIED IDEOGRAPH - 0xF5F9: 0x87F2, //CJK UNIFIED IDEOGRAPH - 0xF5FA: 0x885D, //CJK UNIFIED IDEOGRAPH - 0xF5FB: 0x8877, //CJK UNIFIED IDEOGRAPH - 0xF5FC: 0x60B4, //CJK UNIFIED IDEOGRAPH - 0xF5FD: 0x81B5, //CJK UNIFIED IDEOGRAPH - 0xF5FE: 0x8403, //CJK UNIFIED IDEOGRAPH - 0xF6A1: 0x8D05, //CJK UNIFIED IDEOGRAPH - 0xF6A2: 0x53D6, //CJK UNIFIED IDEOGRAPH - 0xF6A3: 0x5439, //CJK UNIFIED IDEOGRAPH - 0xF6A4: 0x5634, //CJK UNIFIED IDEOGRAPH - 0xF6A5: 0x5A36, //CJK UNIFIED IDEOGRAPH - 0xF6A6: 0x5C31, //CJK UNIFIED IDEOGRAPH - 0xF6A7: 0x708A, //CJK UNIFIED IDEOGRAPH - 0xF6A8: 0x7FE0, //CJK UNIFIED IDEOGRAPH - 0xF6A9: 0x805A, //CJK UNIFIED IDEOGRAPH - 0xF6AA: 0x8106, //CJK UNIFIED IDEOGRAPH - 0xF6AB: 0x81ED, //CJK UNIFIED IDEOGRAPH - 0xF6AC: 0x8DA3, //CJK UNIFIED IDEOGRAPH - 0xF6AD: 0x9189, //CJK UNIFIED IDEOGRAPH - 0xF6AE: 0x9A5F, //CJK UNIFIED IDEOGRAPH - 0xF6AF: 0x9DF2, //CJK UNIFIED IDEOGRAPH - 0xF6B0: 0x5074, //CJK UNIFIED IDEOGRAPH - 0xF6B1: 0x4EC4, //CJK UNIFIED IDEOGRAPH - 0xF6B2: 0x53A0, //CJK UNIFIED IDEOGRAPH - 0xF6B3: 0x60FB, //CJK UNIFIED IDEOGRAPH - 0xF6B4: 0x6E2C, //CJK UNIFIED IDEOGRAPH - 0xF6B5: 0x5C64, //CJK UNIFIED IDEOGRAPH - 0xF6B6: 0x4F88, //CJK UNIFIED IDEOGRAPH - 0xF6B7: 0x5024, //CJK UNIFIED IDEOGRAPH - 0xF6B8: 0x55E4, //CJK UNIFIED IDEOGRAPH - 0xF6B9: 0x5CD9, //CJK UNIFIED IDEOGRAPH - 0xF6BA: 0x5E5F, //CJK UNIFIED IDEOGRAPH - 0xF6BB: 0x6065, //CJK UNIFIED IDEOGRAPH - 0xF6BC: 0x6894, //CJK UNIFIED IDEOGRAPH - 0xF6BD: 0x6CBB, //CJK UNIFIED IDEOGRAPH - 0xF6BE: 0x6DC4, //CJK UNIFIED IDEOGRAPH - 0xF6BF: 0x71BE, //CJK UNIFIED IDEOGRAPH - 0xF6C0: 0x75D4, //CJK UNIFIED IDEOGRAPH - 0xF6C1: 0x75F4, //CJK UNIFIED IDEOGRAPH - 0xF6C2: 0x7661, //CJK UNIFIED IDEOGRAPH - 0xF6C3: 0x7A1A, //CJK UNIFIED IDEOGRAPH - 0xF6C4: 0x7A49, //CJK UNIFIED IDEOGRAPH - 0xF6C5: 0x7DC7, //CJK UNIFIED IDEOGRAPH - 0xF6C6: 0x7DFB, //CJK UNIFIED IDEOGRAPH - 0xF6C7: 0x7F6E, //CJK UNIFIED IDEOGRAPH - 0xF6C8: 0x81F4, //CJK UNIFIED IDEOGRAPH - 0xF6C9: 0x86A9, //CJK UNIFIED IDEOGRAPH - 0xF6CA: 0x8F1C, //CJK UNIFIED IDEOGRAPH - 0xF6CB: 0x96C9, //CJK UNIFIED IDEOGRAPH - 0xF6CC: 0x99B3, //CJK UNIFIED IDEOGRAPH - 0xF6CD: 0x9F52, //CJK UNIFIED IDEOGRAPH - 0xF6CE: 0x5247, //CJK UNIFIED IDEOGRAPH - 0xF6CF: 0x52C5, //CJK UNIFIED IDEOGRAPH - 0xF6D0: 0x98ED, //CJK UNIFIED IDEOGRAPH - 0xF6D1: 0x89AA, //CJK UNIFIED IDEOGRAPH - 0xF6D2: 0x4E03, //CJK UNIFIED IDEOGRAPH - 0xF6D3: 0x67D2, //CJK UNIFIED IDEOGRAPH - 0xF6D4: 0x6F06, //CJK UNIFIED IDEOGRAPH - 0xF6D5: 0x4FB5, //CJK UNIFIED IDEOGRAPH - 0xF6D6: 0x5BE2, //CJK UNIFIED IDEOGRAPH - 0xF6D7: 0x6795, //CJK UNIFIED IDEOGRAPH - 0xF6D8: 0x6C88, //CJK UNIFIED IDEOGRAPH - 0xF6D9: 0x6D78, //CJK UNIFIED IDEOGRAPH - 0xF6DA: 0x741B, //CJK UNIFIED IDEOGRAPH - 0xF6DB: 0x7827, //CJK UNIFIED IDEOGRAPH - 0xF6DC: 0x91DD, //CJK UNIFIED IDEOGRAPH - 0xF6DD: 0x937C, //CJK UNIFIED IDEOGRAPH - 0xF6DE: 0x87C4, //CJK UNIFIED IDEOGRAPH - 0xF6DF: 0x79E4, //CJK UNIFIED IDEOGRAPH - 0xF6E0: 0x7A31, //CJK UNIFIED IDEOGRAPH - 0xF6E1: 0x5FEB, //CJK UNIFIED IDEOGRAPH - 0xF6E2: 0x4ED6, //CJK UNIFIED IDEOGRAPH - 0xF6E3: 0x54A4, //CJK UNIFIED IDEOGRAPH - 0xF6E4: 0x553E, //CJK UNIFIED IDEOGRAPH - 0xF6E5: 0x58AE, //CJK UNIFIED IDEOGRAPH - 0xF6E6: 0x59A5, //CJK UNIFIED IDEOGRAPH - 0xF6E7: 0x60F0, //CJK UNIFIED IDEOGRAPH - 0xF6E8: 0x6253, //CJK UNIFIED IDEOGRAPH - 0xF6E9: 0x62D6, //CJK UNIFIED IDEOGRAPH - 0xF6EA: 0x6736, //CJK UNIFIED IDEOGRAPH - 0xF6EB: 0x6955, //CJK UNIFIED IDEOGRAPH - 0xF6EC: 0x8235, //CJK UNIFIED IDEOGRAPH - 0xF6ED: 0x9640, //CJK UNIFIED IDEOGRAPH - 0xF6EE: 0x99B1, //CJK UNIFIED IDEOGRAPH - 0xF6EF: 0x99DD, //CJK UNIFIED IDEOGRAPH - 0xF6F0: 0x502C, //CJK UNIFIED IDEOGRAPH - 0xF6F1: 0x5353, //CJK UNIFIED IDEOGRAPH - 0xF6F2: 0x5544, //CJK UNIFIED IDEOGRAPH - 0xF6F3: 0x577C, //CJK UNIFIED IDEOGRAPH - 0xF6F4: 0xFA01, //CJK COMPATIBILITY IDEOGRAPH - 0xF6F5: 0x6258, //CJK UNIFIED IDEOGRAPH - 0xF6F6: 0xFA02, //CJK COMPATIBILITY IDEOGRAPH - 0xF6F7: 0x64E2, //CJK UNIFIED IDEOGRAPH - 0xF6F8: 0x666B, //CJK UNIFIED IDEOGRAPH - 0xF6F9: 0x67DD, //CJK UNIFIED IDEOGRAPH - 0xF6FA: 0x6FC1, //CJK UNIFIED IDEOGRAPH - 0xF6FB: 0x6FEF, //CJK UNIFIED IDEOGRAPH - 0xF6FC: 0x7422, //CJK UNIFIED IDEOGRAPH - 0xF6FD: 0x7438, //CJK UNIFIED IDEOGRAPH - 0xF6FE: 0x8A17, //CJK UNIFIED IDEOGRAPH - 0xF7A1: 0x9438, //CJK UNIFIED IDEOGRAPH - 0xF7A2: 0x5451, //CJK UNIFIED IDEOGRAPH - 0xF7A3: 0x5606, //CJK UNIFIED IDEOGRAPH - 0xF7A4: 0x5766, //CJK UNIFIED IDEOGRAPH - 0xF7A5: 0x5F48, //CJK UNIFIED IDEOGRAPH - 0xF7A6: 0x619A, //CJK UNIFIED IDEOGRAPH - 0xF7A7: 0x6B4E, //CJK UNIFIED IDEOGRAPH - 0xF7A8: 0x7058, //CJK UNIFIED IDEOGRAPH - 0xF7A9: 0x70AD, //CJK UNIFIED IDEOGRAPH - 0xF7AA: 0x7DBB, //CJK UNIFIED IDEOGRAPH - 0xF7AB: 0x8A95, //CJK UNIFIED IDEOGRAPH - 0xF7AC: 0x596A, //CJK UNIFIED IDEOGRAPH - 0xF7AD: 0x812B, //CJK UNIFIED IDEOGRAPH - 0xF7AE: 0x63A2, //CJK UNIFIED IDEOGRAPH - 0xF7AF: 0x7708, //CJK UNIFIED IDEOGRAPH - 0xF7B0: 0x803D, //CJK UNIFIED IDEOGRAPH - 0xF7B1: 0x8CAA, //CJK UNIFIED IDEOGRAPH - 0xF7B2: 0x5854, //CJK UNIFIED IDEOGRAPH - 0xF7B3: 0x642D, //CJK UNIFIED IDEOGRAPH - 0xF7B4: 0x69BB, //CJK UNIFIED IDEOGRAPH - 0xF7B5: 0x5B95, //CJK UNIFIED IDEOGRAPH - 0xF7B6: 0x5E11, //CJK UNIFIED IDEOGRAPH - 0xF7B7: 0x6E6F, //CJK UNIFIED IDEOGRAPH - 0xF7B8: 0xFA03, //CJK COMPATIBILITY IDEOGRAPH - 0xF7B9: 0x8569, //CJK UNIFIED IDEOGRAPH - 0xF7BA: 0x514C, //CJK UNIFIED IDEOGRAPH - 0xF7BB: 0x53F0, //CJK UNIFIED IDEOGRAPH - 0xF7BC: 0x592A, //CJK UNIFIED IDEOGRAPH - 0xF7BD: 0x6020, //CJK UNIFIED IDEOGRAPH - 0xF7BE: 0x614B, //CJK UNIFIED IDEOGRAPH - 0xF7BF: 0x6B86, //CJK UNIFIED IDEOGRAPH - 0xF7C0: 0x6C70, //CJK UNIFIED IDEOGRAPH - 0xF7C1: 0x6CF0, //CJK UNIFIED IDEOGRAPH - 0xF7C2: 0x7B1E, //CJK UNIFIED IDEOGRAPH - 0xF7C3: 0x80CE, //CJK UNIFIED IDEOGRAPH - 0xF7C4: 0x82D4, //CJK UNIFIED IDEOGRAPH - 0xF7C5: 0x8DC6, //CJK UNIFIED IDEOGRAPH - 0xF7C6: 0x90B0, //CJK UNIFIED IDEOGRAPH - 0xF7C7: 0x98B1, //CJK UNIFIED IDEOGRAPH - 0xF7C8: 0xFA04, //CJK COMPATIBILITY IDEOGRAPH - 0xF7C9: 0x64C7, //CJK UNIFIED IDEOGRAPH - 0xF7CA: 0x6FA4, //CJK UNIFIED IDEOGRAPH - 0xF7CB: 0x6491, //CJK UNIFIED IDEOGRAPH - 0xF7CC: 0x6504, //CJK UNIFIED IDEOGRAPH - 0xF7CD: 0x514E, //CJK UNIFIED IDEOGRAPH - 0xF7CE: 0x5410, //CJK UNIFIED IDEOGRAPH - 0xF7CF: 0x571F, //CJK UNIFIED IDEOGRAPH - 0xF7D0: 0x8A0E, //CJK UNIFIED IDEOGRAPH - 0xF7D1: 0x615F, //CJK UNIFIED IDEOGRAPH - 0xF7D2: 0x6876, //CJK UNIFIED IDEOGRAPH - 0xF7D3: 0xFA05, //CJK COMPATIBILITY IDEOGRAPH - 0xF7D4: 0x75DB, //CJK UNIFIED IDEOGRAPH - 0xF7D5: 0x7B52, //CJK UNIFIED IDEOGRAPH - 0xF7D6: 0x7D71, //CJK UNIFIED IDEOGRAPH - 0xF7D7: 0x901A, //CJK UNIFIED IDEOGRAPH - 0xF7D8: 0x5806, //CJK UNIFIED IDEOGRAPH - 0xF7D9: 0x69CC, //CJK UNIFIED IDEOGRAPH - 0xF7DA: 0x817F, //CJK UNIFIED IDEOGRAPH - 0xF7DB: 0x892A, //CJK UNIFIED IDEOGRAPH - 0xF7DC: 0x9000, //CJK UNIFIED IDEOGRAPH - 0xF7DD: 0x9839, //CJK UNIFIED IDEOGRAPH - 0xF7DE: 0x5078, //CJK UNIFIED IDEOGRAPH - 0xF7DF: 0x5957, //CJK UNIFIED IDEOGRAPH - 0xF7E0: 0x59AC, //CJK UNIFIED IDEOGRAPH - 0xF7E1: 0x6295, //CJK UNIFIED IDEOGRAPH - 0xF7E2: 0x900F, //CJK UNIFIED IDEOGRAPH - 0xF7E3: 0x9B2A, //CJK UNIFIED IDEOGRAPH - 0xF7E4: 0x615D, //CJK UNIFIED IDEOGRAPH - 0xF7E5: 0x7279, //CJK UNIFIED IDEOGRAPH - 0xF7E6: 0x95D6, //CJK UNIFIED IDEOGRAPH - 0xF7E7: 0x5761, //CJK UNIFIED IDEOGRAPH - 0xF7E8: 0x5A46, //CJK UNIFIED IDEOGRAPH - 0xF7E9: 0x5DF4, //CJK UNIFIED IDEOGRAPH - 0xF7EA: 0x628A, //CJK UNIFIED IDEOGRAPH - 0xF7EB: 0x64AD, //CJK UNIFIED IDEOGRAPH - 0xF7EC: 0x64FA, //CJK UNIFIED IDEOGRAPH - 0xF7ED: 0x6777, //CJK UNIFIED IDEOGRAPH - 0xF7EE: 0x6CE2, //CJK UNIFIED IDEOGRAPH - 0xF7EF: 0x6D3E, //CJK UNIFIED IDEOGRAPH - 0xF7F0: 0x722C, //CJK UNIFIED IDEOGRAPH - 0xF7F1: 0x7436, //CJK UNIFIED IDEOGRAPH - 0xF7F2: 0x7834, //CJK UNIFIED IDEOGRAPH - 0xF7F3: 0x7F77, //CJK UNIFIED IDEOGRAPH - 0xF7F4: 0x82AD, //CJK UNIFIED IDEOGRAPH - 0xF7F5: 0x8DDB, //CJK UNIFIED IDEOGRAPH - 0xF7F6: 0x9817, //CJK UNIFIED IDEOGRAPH - 0xF7F7: 0x5224, //CJK UNIFIED IDEOGRAPH - 0xF7F8: 0x5742, //CJK UNIFIED IDEOGRAPH - 0xF7F9: 0x677F, //CJK UNIFIED IDEOGRAPH - 0xF7FA: 0x7248, //CJK UNIFIED IDEOGRAPH - 0xF7FB: 0x74E3, //CJK UNIFIED IDEOGRAPH - 0xF7FC: 0x8CA9, //CJK UNIFIED IDEOGRAPH - 0xF7FD: 0x8FA6, //CJK UNIFIED IDEOGRAPH - 0xF7FE: 0x9211, //CJK UNIFIED IDEOGRAPH - 0xF8A1: 0x962A, //CJK UNIFIED IDEOGRAPH - 0xF8A2: 0x516B, //CJK UNIFIED IDEOGRAPH - 0xF8A3: 0x53ED, //CJK UNIFIED IDEOGRAPH - 0xF8A4: 0x634C, //CJK UNIFIED IDEOGRAPH - 0xF8A5: 0x4F69, //CJK UNIFIED IDEOGRAPH - 0xF8A6: 0x5504, //CJK UNIFIED IDEOGRAPH - 0xF8A7: 0x6096, //CJK UNIFIED IDEOGRAPH - 0xF8A8: 0x6557, //CJK UNIFIED IDEOGRAPH - 0xF8A9: 0x6C9B, //CJK UNIFIED IDEOGRAPH - 0xF8AA: 0x6D7F, //CJK UNIFIED IDEOGRAPH - 0xF8AB: 0x724C, //CJK UNIFIED IDEOGRAPH - 0xF8AC: 0x72FD, //CJK UNIFIED IDEOGRAPH - 0xF8AD: 0x7A17, //CJK UNIFIED IDEOGRAPH - 0xF8AE: 0x8987, //CJK UNIFIED IDEOGRAPH - 0xF8AF: 0x8C9D, //CJK UNIFIED IDEOGRAPH - 0xF8B0: 0x5F6D, //CJK UNIFIED IDEOGRAPH - 0xF8B1: 0x6F8E, //CJK UNIFIED IDEOGRAPH - 0xF8B2: 0x70F9, //CJK UNIFIED IDEOGRAPH - 0xF8B3: 0x81A8, //CJK UNIFIED IDEOGRAPH - 0xF8B4: 0x610E, //CJK UNIFIED IDEOGRAPH - 0xF8B5: 0x4FBF, //CJK UNIFIED IDEOGRAPH - 0xF8B6: 0x504F, //CJK UNIFIED IDEOGRAPH - 0xF8B7: 0x6241, //CJK UNIFIED IDEOGRAPH - 0xF8B8: 0x7247, //CJK UNIFIED IDEOGRAPH - 0xF8B9: 0x7BC7, //CJK UNIFIED IDEOGRAPH - 0xF8BA: 0x7DE8, //CJK UNIFIED IDEOGRAPH - 0xF8BB: 0x7FE9, //CJK UNIFIED IDEOGRAPH - 0xF8BC: 0x904D, //CJK UNIFIED IDEOGRAPH - 0xF8BD: 0x97AD, //CJK UNIFIED IDEOGRAPH - 0xF8BE: 0x9A19, //CJK UNIFIED IDEOGRAPH - 0xF8BF: 0x8CB6, //CJK UNIFIED IDEOGRAPH - 0xF8C0: 0x576A, //CJK UNIFIED IDEOGRAPH - 0xF8C1: 0x5E73, //CJK UNIFIED IDEOGRAPH - 0xF8C2: 0x67B0, //CJK UNIFIED IDEOGRAPH - 0xF8C3: 0x840D, //CJK UNIFIED IDEOGRAPH - 0xF8C4: 0x8A55, //CJK UNIFIED IDEOGRAPH - 0xF8C5: 0x5420, //CJK UNIFIED IDEOGRAPH - 0xF8C6: 0x5B16, //CJK UNIFIED IDEOGRAPH - 0xF8C7: 0x5E63, //CJK UNIFIED IDEOGRAPH - 0xF8C8: 0x5EE2, //CJK UNIFIED IDEOGRAPH - 0xF8C9: 0x5F0A, //CJK UNIFIED IDEOGRAPH - 0xF8CA: 0x6583, //CJK UNIFIED IDEOGRAPH - 0xF8CB: 0x80BA, //CJK UNIFIED IDEOGRAPH - 0xF8CC: 0x853D, //CJK UNIFIED IDEOGRAPH - 0xF8CD: 0x9589, //CJK UNIFIED IDEOGRAPH - 0xF8CE: 0x965B, //CJK UNIFIED IDEOGRAPH - 0xF8CF: 0x4F48, //CJK UNIFIED IDEOGRAPH - 0xF8D0: 0x5305, //CJK UNIFIED IDEOGRAPH - 0xF8D1: 0x530D, //CJK UNIFIED IDEOGRAPH - 0xF8D2: 0x530F, //CJK UNIFIED IDEOGRAPH - 0xF8D3: 0x5486, //CJK UNIFIED IDEOGRAPH - 0xF8D4: 0x54FA, //CJK UNIFIED IDEOGRAPH - 0xF8D5: 0x5703, //CJK UNIFIED IDEOGRAPH - 0xF8D6: 0x5E03, //CJK UNIFIED IDEOGRAPH - 0xF8D7: 0x6016, //CJK UNIFIED IDEOGRAPH - 0xF8D8: 0x629B, //CJK UNIFIED IDEOGRAPH - 0xF8D9: 0x62B1, //CJK UNIFIED IDEOGRAPH - 0xF8DA: 0x6355, //CJK UNIFIED IDEOGRAPH - 0xF8DB: 0xFA06, //CJK COMPATIBILITY IDEOGRAPH - 0xF8DC: 0x6CE1, //CJK UNIFIED IDEOGRAPH - 0xF8DD: 0x6D66, //CJK UNIFIED IDEOGRAPH - 0xF8DE: 0x75B1, //CJK UNIFIED IDEOGRAPH - 0xF8DF: 0x7832, //CJK UNIFIED IDEOGRAPH - 0xF8E0: 0x80DE, //CJK UNIFIED IDEOGRAPH - 0xF8E1: 0x812F, //CJK UNIFIED IDEOGRAPH - 0xF8E2: 0x82DE, //CJK UNIFIED IDEOGRAPH - 0xF8E3: 0x8461, //CJK UNIFIED IDEOGRAPH - 0xF8E4: 0x84B2, //CJK UNIFIED IDEOGRAPH - 0xF8E5: 0x888D, //CJK UNIFIED IDEOGRAPH - 0xF8E6: 0x8912, //CJK UNIFIED IDEOGRAPH - 0xF8E7: 0x900B, //CJK UNIFIED IDEOGRAPH - 0xF8E8: 0x92EA, //CJK UNIFIED IDEOGRAPH - 0xF8E9: 0x98FD, //CJK UNIFIED IDEOGRAPH - 0xF8EA: 0x9B91, //CJK UNIFIED IDEOGRAPH - 0xF8EB: 0x5E45, //CJK UNIFIED IDEOGRAPH - 0xF8EC: 0x66B4, //CJK UNIFIED IDEOGRAPH - 0xF8ED: 0x66DD, //CJK UNIFIED IDEOGRAPH - 0xF8EE: 0x7011, //CJK UNIFIED IDEOGRAPH - 0xF8EF: 0x7206, //CJK UNIFIED IDEOGRAPH - 0xF8F0: 0xFA07, //CJK COMPATIBILITY IDEOGRAPH - 0xF8F1: 0x4FF5, //CJK UNIFIED IDEOGRAPH - 0xF8F2: 0x527D, //CJK UNIFIED IDEOGRAPH - 0xF8F3: 0x5F6A, //CJK UNIFIED IDEOGRAPH - 0xF8F4: 0x6153, //CJK UNIFIED IDEOGRAPH - 0xF8F5: 0x6753, //CJK UNIFIED IDEOGRAPH - 0xF8F6: 0x6A19, //CJK UNIFIED IDEOGRAPH - 0xF8F7: 0x6F02, //CJK UNIFIED IDEOGRAPH - 0xF8F8: 0x74E2, //CJK UNIFIED IDEOGRAPH - 0xF8F9: 0x7968, //CJK UNIFIED IDEOGRAPH - 0xF8FA: 0x8868, //CJK UNIFIED IDEOGRAPH - 0xF8FB: 0x8C79, //CJK UNIFIED IDEOGRAPH - 0xF8FC: 0x98C7, //CJK UNIFIED IDEOGRAPH - 0xF8FD: 0x98C4, //CJK UNIFIED IDEOGRAPH - 0xF8FE: 0x9A43, //CJK UNIFIED IDEOGRAPH - 0xF9A1: 0x54C1, //CJK UNIFIED IDEOGRAPH - 0xF9A2: 0x7A1F, //CJK UNIFIED IDEOGRAPH - 0xF9A3: 0x6953, //CJK UNIFIED IDEOGRAPH - 0xF9A4: 0x8AF7, //CJK UNIFIED IDEOGRAPH - 0xF9A5: 0x8C4A, //CJK UNIFIED IDEOGRAPH - 0xF9A6: 0x98A8, //CJK UNIFIED IDEOGRAPH - 0xF9A7: 0x99AE, //CJK UNIFIED IDEOGRAPH - 0xF9A8: 0x5F7C, //CJK UNIFIED IDEOGRAPH - 0xF9A9: 0x62AB, //CJK UNIFIED IDEOGRAPH - 0xF9AA: 0x75B2, //CJK UNIFIED IDEOGRAPH - 0xF9AB: 0x76AE, //CJK UNIFIED IDEOGRAPH - 0xF9AC: 0x88AB, //CJK UNIFIED IDEOGRAPH - 0xF9AD: 0x907F, //CJK UNIFIED IDEOGRAPH - 0xF9AE: 0x9642, //CJK UNIFIED IDEOGRAPH - 0xF9AF: 0x5339, //CJK UNIFIED IDEOGRAPH - 0xF9B0: 0x5F3C, //CJK UNIFIED IDEOGRAPH - 0xF9B1: 0x5FC5, //CJK UNIFIED IDEOGRAPH - 0xF9B2: 0x6CCC, //CJK UNIFIED IDEOGRAPH - 0xF9B3: 0x73CC, //CJK UNIFIED IDEOGRAPH - 0xF9B4: 0x7562, //CJK UNIFIED IDEOGRAPH - 0xF9B5: 0x758B, //CJK UNIFIED IDEOGRAPH - 0xF9B6: 0x7B46, //CJK UNIFIED IDEOGRAPH - 0xF9B7: 0x82FE, //CJK UNIFIED IDEOGRAPH - 0xF9B8: 0x999D, //CJK UNIFIED IDEOGRAPH - 0xF9B9: 0x4E4F, //CJK UNIFIED IDEOGRAPH - 0xF9BA: 0x903C, //CJK UNIFIED IDEOGRAPH - 0xF9BB: 0x4E0B, //CJK UNIFIED IDEOGRAPH - 0xF9BC: 0x4F55, //CJK UNIFIED IDEOGRAPH - 0xF9BD: 0x53A6, //CJK UNIFIED IDEOGRAPH - 0xF9BE: 0x590F, //CJK UNIFIED IDEOGRAPH - 0xF9BF: 0x5EC8, //CJK UNIFIED IDEOGRAPH - 0xF9C0: 0x6630, //CJK UNIFIED IDEOGRAPH - 0xF9C1: 0x6CB3, //CJK UNIFIED IDEOGRAPH - 0xF9C2: 0x7455, //CJK UNIFIED IDEOGRAPH - 0xF9C3: 0x8377, //CJK UNIFIED IDEOGRAPH - 0xF9C4: 0x8766, //CJK UNIFIED IDEOGRAPH - 0xF9C5: 0x8CC0, //CJK UNIFIED IDEOGRAPH - 0xF9C6: 0x9050, //CJK UNIFIED IDEOGRAPH - 0xF9C7: 0x971E, //CJK UNIFIED IDEOGRAPH - 0xF9C8: 0x9C15, //CJK UNIFIED IDEOGRAPH - 0xF9C9: 0x58D1, //CJK UNIFIED IDEOGRAPH - 0xF9CA: 0x5B78, //CJK UNIFIED IDEOGRAPH - 0xF9CB: 0x8650, //CJK UNIFIED IDEOGRAPH - 0xF9CC: 0x8B14, //CJK UNIFIED IDEOGRAPH - 0xF9CD: 0x9DB4, //CJK UNIFIED IDEOGRAPH - 0xF9CE: 0x5BD2, //CJK UNIFIED IDEOGRAPH - 0xF9CF: 0x6068, //CJK UNIFIED IDEOGRAPH - 0xF9D0: 0x608D, //CJK UNIFIED IDEOGRAPH - 0xF9D1: 0x65F1, //CJK UNIFIED IDEOGRAPH - 0xF9D2: 0x6C57, //CJK UNIFIED IDEOGRAPH - 0xF9D3: 0x6F22, //CJK UNIFIED IDEOGRAPH - 0xF9D4: 0x6FA3, //CJK UNIFIED IDEOGRAPH - 0xF9D5: 0x701A, //CJK UNIFIED IDEOGRAPH - 0xF9D6: 0x7F55, //CJK UNIFIED IDEOGRAPH - 0xF9D7: 0x7FF0, //CJK UNIFIED IDEOGRAPH - 0xF9D8: 0x9591, //CJK UNIFIED IDEOGRAPH - 0xF9D9: 0x9592, //CJK UNIFIED IDEOGRAPH - 0xF9DA: 0x9650, //CJK UNIFIED IDEOGRAPH - 0xF9DB: 0x97D3, //CJK UNIFIED IDEOGRAPH - 0xF9DC: 0x5272, //CJK UNIFIED IDEOGRAPH - 0xF9DD: 0x8F44, //CJK UNIFIED IDEOGRAPH - 0xF9DE: 0x51FD, //CJK UNIFIED IDEOGRAPH - 0xF9DF: 0x542B, //CJK UNIFIED IDEOGRAPH - 0xF9E0: 0x54B8, //CJK UNIFIED IDEOGRAPH - 0xF9E1: 0x5563, //CJK UNIFIED IDEOGRAPH - 0xF9E2: 0x558A, //CJK UNIFIED IDEOGRAPH - 0xF9E3: 0x6ABB, //CJK UNIFIED IDEOGRAPH - 0xF9E4: 0x6DB5, //CJK UNIFIED IDEOGRAPH - 0xF9E5: 0x7DD8, //CJK UNIFIED IDEOGRAPH - 0xF9E6: 0x8266, //CJK UNIFIED IDEOGRAPH - 0xF9E7: 0x929C, //CJK UNIFIED IDEOGRAPH - 0xF9E8: 0x9677, //CJK UNIFIED IDEOGRAPH - 0xF9E9: 0x9E79, //CJK UNIFIED IDEOGRAPH - 0xF9EA: 0x5408, //CJK UNIFIED IDEOGRAPH - 0xF9EB: 0x54C8, //CJK UNIFIED IDEOGRAPH - 0xF9EC: 0x76D2, //CJK UNIFIED IDEOGRAPH - 0xF9ED: 0x86E4, //CJK UNIFIED IDEOGRAPH - 0xF9EE: 0x95A4, //CJK UNIFIED IDEOGRAPH - 0xF9EF: 0x95D4, //CJK UNIFIED IDEOGRAPH - 0xF9F0: 0x965C, //CJK UNIFIED IDEOGRAPH - 0xF9F1: 0x4EA2, //CJK UNIFIED IDEOGRAPH - 0xF9F2: 0x4F09, //CJK UNIFIED IDEOGRAPH - 0xF9F3: 0x59EE, //CJK UNIFIED IDEOGRAPH - 0xF9F4: 0x5AE6, //CJK UNIFIED IDEOGRAPH - 0xF9F5: 0x5DF7, //CJK UNIFIED IDEOGRAPH - 0xF9F6: 0x6052, //CJK UNIFIED IDEOGRAPH - 0xF9F7: 0x6297, //CJK UNIFIED IDEOGRAPH - 0xF9F8: 0x676D, //CJK UNIFIED IDEOGRAPH - 0xF9F9: 0x6841, //CJK UNIFIED IDEOGRAPH - 0xF9FA: 0x6C86, //CJK UNIFIED IDEOGRAPH - 0xF9FB: 0x6E2F, //CJK UNIFIED IDEOGRAPH - 0xF9FC: 0x7F38, //CJK UNIFIED IDEOGRAPH - 0xF9FD: 0x809B, //CJK UNIFIED IDEOGRAPH - 0xF9FE: 0x822A, //CJK UNIFIED IDEOGRAPH - 0xFAA1: 0xFA08, //CJK COMPATIBILITY IDEOGRAPH - 0xFAA2: 0xFA09, //CJK COMPATIBILITY IDEOGRAPH - 0xFAA3: 0x9805, //CJK UNIFIED IDEOGRAPH - 0xFAA4: 0x4EA5, //CJK UNIFIED IDEOGRAPH - 0xFAA5: 0x5055, //CJK UNIFIED IDEOGRAPH - 0xFAA6: 0x54B3, //CJK UNIFIED IDEOGRAPH - 0xFAA7: 0x5793, //CJK UNIFIED IDEOGRAPH - 0xFAA8: 0x595A, //CJK UNIFIED IDEOGRAPH - 0xFAA9: 0x5B69, //CJK UNIFIED IDEOGRAPH - 0xFAAA: 0x5BB3, //CJK UNIFIED IDEOGRAPH - 0xFAAB: 0x61C8, //CJK UNIFIED IDEOGRAPH - 0xFAAC: 0x6977, //CJK UNIFIED IDEOGRAPH - 0xFAAD: 0x6D77, //CJK UNIFIED IDEOGRAPH - 0xFAAE: 0x7023, //CJK UNIFIED IDEOGRAPH - 0xFAAF: 0x87F9, //CJK UNIFIED IDEOGRAPH - 0xFAB0: 0x89E3, //CJK UNIFIED IDEOGRAPH - 0xFAB1: 0x8A72, //CJK UNIFIED IDEOGRAPH - 0xFAB2: 0x8AE7, //CJK UNIFIED IDEOGRAPH - 0xFAB3: 0x9082, //CJK UNIFIED IDEOGRAPH - 0xFAB4: 0x99ED, //CJK UNIFIED IDEOGRAPH - 0xFAB5: 0x9AB8, //CJK UNIFIED IDEOGRAPH - 0xFAB6: 0x52BE, //CJK UNIFIED IDEOGRAPH - 0xFAB7: 0x6838, //CJK UNIFIED IDEOGRAPH - 0xFAB8: 0x5016, //CJK UNIFIED IDEOGRAPH - 0xFAB9: 0x5E78, //CJK UNIFIED IDEOGRAPH - 0xFABA: 0x674F, //CJK UNIFIED IDEOGRAPH - 0xFABB: 0x8347, //CJK UNIFIED IDEOGRAPH - 0xFABC: 0x884C, //CJK UNIFIED IDEOGRAPH - 0xFABD: 0x4EAB, //CJK UNIFIED IDEOGRAPH - 0xFABE: 0x5411, //CJK UNIFIED IDEOGRAPH - 0xFABF: 0x56AE, //CJK UNIFIED IDEOGRAPH - 0xFAC0: 0x73E6, //CJK UNIFIED IDEOGRAPH - 0xFAC1: 0x9115, //CJK UNIFIED IDEOGRAPH - 0xFAC2: 0x97FF, //CJK UNIFIED IDEOGRAPH - 0xFAC3: 0x9909, //CJK UNIFIED IDEOGRAPH - 0xFAC4: 0x9957, //CJK UNIFIED IDEOGRAPH - 0xFAC5: 0x9999, //CJK UNIFIED IDEOGRAPH - 0xFAC6: 0x5653, //CJK UNIFIED IDEOGRAPH - 0xFAC7: 0x589F, //CJK UNIFIED IDEOGRAPH - 0xFAC8: 0x865B, //CJK UNIFIED IDEOGRAPH - 0xFAC9: 0x8A31, //CJK UNIFIED IDEOGRAPH - 0xFACA: 0x61B2, //CJK UNIFIED IDEOGRAPH - 0xFACB: 0x6AF6, //CJK UNIFIED IDEOGRAPH - 0xFACC: 0x737B, //CJK UNIFIED IDEOGRAPH - 0xFACD: 0x8ED2, //CJK UNIFIED IDEOGRAPH - 0xFACE: 0x6B47, //CJK UNIFIED IDEOGRAPH - 0xFACF: 0x96AA, //CJK UNIFIED IDEOGRAPH - 0xFAD0: 0x9A57, //CJK UNIFIED IDEOGRAPH - 0xFAD1: 0x5955, //CJK UNIFIED IDEOGRAPH - 0xFAD2: 0x7200, //CJK UNIFIED IDEOGRAPH - 0xFAD3: 0x8D6B, //CJK UNIFIED IDEOGRAPH - 0xFAD4: 0x9769, //CJK UNIFIED IDEOGRAPH - 0xFAD5: 0x4FD4, //CJK UNIFIED IDEOGRAPH - 0xFAD6: 0x5CF4, //CJK UNIFIED IDEOGRAPH - 0xFAD7: 0x5F26, //CJK UNIFIED IDEOGRAPH - 0xFAD8: 0x61F8, //CJK UNIFIED IDEOGRAPH - 0xFAD9: 0x665B, //CJK UNIFIED IDEOGRAPH - 0xFADA: 0x6CEB, //CJK UNIFIED IDEOGRAPH - 0xFADB: 0x70AB, //CJK UNIFIED IDEOGRAPH - 0xFADC: 0x7384, //CJK UNIFIED IDEOGRAPH - 0xFADD: 0x73B9, //CJK UNIFIED IDEOGRAPH - 0xFADE: 0x73FE, //CJK UNIFIED IDEOGRAPH - 0xFADF: 0x7729, //CJK UNIFIED IDEOGRAPH - 0xFAE0: 0x774D, //CJK UNIFIED IDEOGRAPH - 0xFAE1: 0x7D43, //CJK UNIFIED IDEOGRAPH - 0xFAE2: 0x7D62, //CJK UNIFIED IDEOGRAPH - 0xFAE3: 0x7E23, //CJK UNIFIED IDEOGRAPH - 0xFAE4: 0x8237, //CJK UNIFIED IDEOGRAPH - 0xFAE5: 0x8852, //CJK UNIFIED IDEOGRAPH - 0xFAE6: 0xFA0A, //CJK COMPATIBILITY IDEOGRAPH - 0xFAE7: 0x8CE2, //CJK UNIFIED IDEOGRAPH - 0xFAE8: 0x9249, //CJK UNIFIED IDEOGRAPH - 0xFAE9: 0x986F, //CJK UNIFIED IDEOGRAPH - 0xFAEA: 0x5B51, //CJK UNIFIED IDEOGRAPH - 0xFAEB: 0x7A74, //CJK UNIFIED IDEOGRAPH - 0xFAEC: 0x8840, //CJK UNIFIED IDEOGRAPH - 0xFAED: 0x9801, //CJK UNIFIED IDEOGRAPH - 0xFAEE: 0x5ACC, //CJK UNIFIED IDEOGRAPH - 0xFAEF: 0x4FE0, //CJK UNIFIED IDEOGRAPH - 0xFAF0: 0x5354, //CJK UNIFIED IDEOGRAPH - 0xFAF1: 0x593E, //CJK UNIFIED IDEOGRAPH - 0xFAF2: 0x5CFD, //CJK UNIFIED IDEOGRAPH - 0xFAF3: 0x633E, //CJK UNIFIED IDEOGRAPH - 0xFAF4: 0x6D79, //CJK UNIFIED IDEOGRAPH - 0xFAF5: 0x72F9, //CJK UNIFIED IDEOGRAPH - 0xFAF6: 0x8105, //CJK UNIFIED IDEOGRAPH - 0xFAF7: 0x8107, //CJK UNIFIED IDEOGRAPH - 0xFAF8: 0x83A2, //CJK UNIFIED IDEOGRAPH - 0xFAF9: 0x92CF, //CJK UNIFIED IDEOGRAPH - 0xFAFA: 0x9830, //CJK UNIFIED IDEOGRAPH - 0xFAFB: 0x4EA8, //CJK UNIFIED IDEOGRAPH - 0xFAFC: 0x5144, //CJK UNIFIED IDEOGRAPH - 0xFAFD: 0x5211, //CJK UNIFIED IDEOGRAPH - 0xFAFE: 0x578B, //CJK UNIFIED IDEOGRAPH - 0xFBA1: 0x5F62, //CJK UNIFIED IDEOGRAPH - 0xFBA2: 0x6CC2, //CJK UNIFIED IDEOGRAPH - 0xFBA3: 0x6ECE, //CJK UNIFIED IDEOGRAPH - 0xFBA4: 0x7005, //CJK UNIFIED IDEOGRAPH - 0xFBA5: 0x7050, //CJK UNIFIED IDEOGRAPH - 0xFBA6: 0x70AF, //CJK UNIFIED IDEOGRAPH - 0xFBA7: 0x7192, //CJK UNIFIED IDEOGRAPH - 0xFBA8: 0x73E9, //CJK UNIFIED IDEOGRAPH - 0xFBA9: 0x7469, //CJK UNIFIED IDEOGRAPH - 0xFBAA: 0x834A, //CJK UNIFIED IDEOGRAPH - 0xFBAB: 0x87A2, //CJK UNIFIED IDEOGRAPH - 0xFBAC: 0x8861, //CJK UNIFIED IDEOGRAPH - 0xFBAD: 0x9008, //CJK UNIFIED IDEOGRAPH - 0xFBAE: 0x90A2, //CJK UNIFIED IDEOGRAPH - 0xFBAF: 0x93A3, //CJK UNIFIED IDEOGRAPH - 0xFBB0: 0x99A8, //CJK UNIFIED IDEOGRAPH - 0xFBB1: 0x516E, //CJK UNIFIED IDEOGRAPH - 0xFBB2: 0x5F57, //CJK UNIFIED IDEOGRAPH - 0xFBB3: 0x60E0, //CJK UNIFIED IDEOGRAPH - 0xFBB4: 0x6167, //CJK UNIFIED IDEOGRAPH - 0xFBB5: 0x66B3, //CJK UNIFIED IDEOGRAPH - 0xFBB6: 0x8559, //CJK UNIFIED IDEOGRAPH - 0xFBB7: 0x8E4A, //CJK UNIFIED IDEOGRAPH - 0xFBB8: 0x91AF, //CJK UNIFIED IDEOGRAPH - 0xFBB9: 0x978B, //CJK UNIFIED IDEOGRAPH - 0xFBBA: 0x4E4E, //CJK UNIFIED IDEOGRAPH - 0xFBBB: 0x4E92, //CJK UNIFIED IDEOGRAPH - 0xFBBC: 0x547C, //CJK UNIFIED IDEOGRAPH - 0xFBBD: 0x58D5, //CJK UNIFIED IDEOGRAPH - 0xFBBE: 0x58FA, //CJK UNIFIED IDEOGRAPH - 0xFBBF: 0x597D, //CJK UNIFIED IDEOGRAPH - 0xFBC0: 0x5CB5, //CJK UNIFIED IDEOGRAPH - 0xFBC1: 0x5F27, //CJK UNIFIED IDEOGRAPH - 0xFBC2: 0x6236, //CJK UNIFIED IDEOGRAPH - 0xFBC3: 0x6248, //CJK UNIFIED IDEOGRAPH - 0xFBC4: 0x660A, //CJK UNIFIED IDEOGRAPH - 0xFBC5: 0x6667, //CJK UNIFIED IDEOGRAPH - 0xFBC6: 0x6BEB, //CJK UNIFIED IDEOGRAPH - 0xFBC7: 0x6D69, //CJK UNIFIED IDEOGRAPH - 0xFBC8: 0x6DCF, //CJK UNIFIED IDEOGRAPH - 0xFBC9: 0x6E56, //CJK UNIFIED IDEOGRAPH - 0xFBCA: 0x6EF8, //CJK UNIFIED IDEOGRAPH - 0xFBCB: 0x6F94, //CJK UNIFIED IDEOGRAPH - 0xFBCC: 0x6FE0, //CJK UNIFIED IDEOGRAPH - 0xFBCD: 0x6FE9, //CJK UNIFIED IDEOGRAPH - 0xFBCE: 0x705D, //CJK UNIFIED IDEOGRAPH - 0xFBCF: 0x72D0, //CJK UNIFIED IDEOGRAPH - 0xFBD0: 0x7425, //CJK UNIFIED IDEOGRAPH - 0xFBD1: 0x745A, //CJK UNIFIED IDEOGRAPH - 0xFBD2: 0x74E0, //CJK UNIFIED IDEOGRAPH - 0xFBD3: 0x7693, //CJK UNIFIED IDEOGRAPH - 0xFBD4: 0x795C, //CJK UNIFIED IDEOGRAPH - 0xFBD5: 0x7CCA, //CJK UNIFIED IDEOGRAPH - 0xFBD6: 0x7E1E, //CJK UNIFIED IDEOGRAPH - 0xFBD7: 0x80E1, //CJK UNIFIED IDEOGRAPH - 0xFBD8: 0x82A6, //CJK UNIFIED IDEOGRAPH - 0xFBD9: 0x846B, //CJK UNIFIED IDEOGRAPH - 0xFBDA: 0x84BF, //CJK UNIFIED IDEOGRAPH - 0xFBDB: 0x864E, //CJK UNIFIED IDEOGRAPH - 0xFBDC: 0x865F, //CJK UNIFIED IDEOGRAPH - 0xFBDD: 0x8774, //CJK UNIFIED IDEOGRAPH - 0xFBDE: 0x8B77, //CJK UNIFIED IDEOGRAPH - 0xFBDF: 0x8C6A, //CJK UNIFIED IDEOGRAPH - 0xFBE0: 0x93AC, //CJK UNIFIED IDEOGRAPH - 0xFBE1: 0x9800, //CJK UNIFIED IDEOGRAPH - 0xFBE2: 0x9865, //CJK UNIFIED IDEOGRAPH - 0xFBE3: 0x60D1, //CJK UNIFIED IDEOGRAPH - 0xFBE4: 0x6216, //CJK UNIFIED IDEOGRAPH - 0xFBE5: 0x9177, //CJK UNIFIED IDEOGRAPH - 0xFBE6: 0x5A5A, //CJK UNIFIED IDEOGRAPH - 0xFBE7: 0x660F, //CJK UNIFIED IDEOGRAPH - 0xFBE8: 0x6DF7, //CJK UNIFIED IDEOGRAPH - 0xFBE9: 0x6E3E, //CJK UNIFIED IDEOGRAPH - 0xFBEA: 0x743F, //CJK UNIFIED IDEOGRAPH - 0xFBEB: 0x9B42, //CJK UNIFIED IDEOGRAPH - 0xFBEC: 0x5FFD, //CJK UNIFIED IDEOGRAPH - 0xFBED: 0x60DA, //CJK UNIFIED IDEOGRAPH - 0xFBEE: 0x7B0F, //CJK UNIFIED IDEOGRAPH - 0xFBEF: 0x54C4, //CJK UNIFIED IDEOGRAPH - 0xFBF0: 0x5F18, //CJK UNIFIED IDEOGRAPH - 0xFBF1: 0x6C5E, //CJK UNIFIED IDEOGRAPH - 0xFBF2: 0x6CD3, //CJK UNIFIED IDEOGRAPH - 0xFBF3: 0x6D2A, //CJK UNIFIED IDEOGRAPH - 0xFBF4: 0x70D8, //CJK UNIFIED IDEOGRAPH - 0xFBF5: 0x7D05, //CJK UNIFIED IDEOGRAPH - 0xFBF6: 0x8679, //CJK UNIFIED IDEOGRAPH - 0xFBF7: 0x8A0C, //CJK UNIFIED IDEOGRAPH - 0xFBF8: 0x9D3B, //CJK UNIFIED IDEOGRAPH - 0xFBF9: 0x5316, //CJK UNIFIED IDEOGRAPH - 0xFBFA: 0x548C, //CJK UNIFIED IDEOGRAPH - 0xFBFB: 0x5B05, //CJK UNIFIED IDEOGRAPH - 0xFBFC: 0x6A3A, //CJK UNIFIED IDEOGRAPH - 0xFBFD: 0x706B, //CJK UNIFIED IDEOGRAPH - 0xFBFE: 0x7575, //CJK UNIFIED IDEOGRAPH - 0xFCA1: 0x798D, //CJK UNIFIED IDEOGRAPH - 0xFCA2: 0x79BE, //CJK UNIFIED IDEOGRAPH - 0xFCA3: 0x82B1, //CJK UNIFIED IDEOGRAPH - 0xFCA4: 0x83EF, //CJK UNIFIED IDEOGRAPH - 0xFCA5: 0x8A71, //CJK UNIFIED IDEOGRAPH - 0xFCA6: 0x8B41, //CJK UNIFIED IDEOGRAPH - 0xFCA7: 0x8CA8, //CJK UNIFIED IDEOGRAPH - 0xFCA8: 0x9774, //CJK UNIFIED IDEOGRAPH - 0xFCA9: 0xFA0B, //CJK COMPATIBILITY IDEOGRAPH - 0xFCAA: 0x64F4, //CJK UNIFIED IDEOGRAPH - 0xFCAB: 0x652B, //CJK UNIFIED IDEOGRAPH - 0xFCAC: 0x78BA, //CJK UNIFIED IDEOGRAPH - 0xFCAD: 0x78BB, //CJK UNIFIED IDEOGRAPH - 0xFCAE: 0x7A6B, //CJK UNIFIED IDEOGRAPH - 0xFCAF: 0x4E38, //CJK UNIFIED IDEOGRAPH - 0xFCB0: 0x559A, //CJK UNIFIED IDEOGRAPH - 0xFCB1: 0x5950, //CJK UNIFIED IDEOGRAPH - 0xFCB2: 0x5BA6, //CJK UNIFIED IDEOGRAPH - 0xFCB3: 0x5E7B, //CJK UNIFIED IDEOGRAPH - 0xFCB4: 0x60A3, //CJK UNIFIED IDEOGRAPH - 0xFCB5: 0x63DB, //CJK UNIFIED IDEOGRAPH - 0xFCB6: 0x6B61, //CJK UNIFIED IDEOGRAPH - 0xFCB7: 0x6665, //CJK UNIFIED IDEOGRAPH - 0xFCB8: 0x6853, //CJK UNIFIED IDEOGRAPH - 0xFCB9: 0x6E19, //CJK UNIFIED IDEOGRAPH - 0xFCBA: 0x7165, //CJK UNIFIED IDEOGRAPH - 0xFCBB: 0x74B0, //CJK UNIFIED IDEOGRAPH - 0xFCBC: 0x7D08, //CJK UNIFIED IDEOGRAPH - 0xFCBD: 0x9084, //CJK UNIFIED IDEOGRAPH - 0xFCBE: 0x9A69, //CJK UNIFIED IDEOGRAPH - 0xFCBF: 0x9C25, //CJK UNIFIED IDEOGRAPH - 0xFCC0: 0x6D3B, //CJK UNIFIED IDEOGRAPH - 0xFCC1: 0x6ED1, //CJK UNIFIED IDEOGRAPH - 0xFCC2: 0x733E, //CJK UNIFIED IDEOGRAPH - 0xFCC3: 0x8C41, //CJK UNIFIED IDEOGRAPH - 0xFCC4: 0x95CA, //CJK UNIFIED IDEOGRAPH - 0xFCC5: 0x51F0, //CJK UNIFIED IDEOGRAPH - 0xFCC6: 0x5E4C, //CJK UNIFIED IDEOGRAPH - 0xFCC7: 0x5FA8, //CJK UNIFIED IDEOGRAPH - 0xFCC8: 0x604D, //CJK UNIFIED IDEOGRAPH - 0xFCC9: 0x60F6, //CJK UNIFIED IDEOGRAPH - 0xFCCA: 0x6130, //CJK UNIFIED IDEOGRAPH - 0xFCCB: 0x614C, //CJK UNIFIED IDEOGRAPH - 0xFCCC: 0x6643, //CJK UNIFIED IDEOGRAPH - 0xFCCD: 0x6644, //CJK UNIFIED IDEOGRAPH - 0xFCCE: 0x69A5, //CJK UNIFIED IDEOGRAPH - 0xFCCF: 0x6CC1, //CJK UNIFIED IDEOGRAPH - 0xFCD0: 0x6E5F, //CJK UNIFIED IDEOGRAPH - 0xFCD1: 0x6EC9, //CJK UNIFIED IDEOGRAPH - 0xFCD2: 0x6F62, //CJK UNIFIED IDEOGRAPH - 0xFCD3: 0x714C, //CJK UNIFIED IDEOGRAPH - 0xFCD4: 0x749C, //CJK UNIFIED IDEOGRAPH - 0xFCD5: 0x7687, //CJK UNIFIED IDEOGRAPH - 0xFCD6: 0x7BC1, //CJK UNIFIED IDEOGRAPH - 0xFCD7: 0x7C27, //CJK UNIFIED IDEOGRAPH - 0xFCD8: 0x8352, //CJK UNIFIED IDEOGRAPH - 0xFCD9: 0x8757, //CJK UNIFIED IDEOGRAPH - 0xFCDA: 0x9051, //CJK UNIFIED IDEOGRAPH - 0xFCDB: 0x968D, //CJK UNIFIED IDEOGRAPH - 0xFCDC: 0x9EC3, //CJK UNIFIED IDEOGRAPH - 0xFCDD: 0x532F, //CJK UNIFIED IDEOGRAPH - 0xFCDE: 0x56DE, //CJK UNIFIED IDEOGRAPH - 0xFCDF: 0x5EFB, //CJK UNIFIED IDEOGRAPH - 0xFCE0: 0x5F8A, //CJK UNIFIED IDEOGRAPH - 0xFCE1: 0x6062, //CJK UNIFIED IDEOGRAPH - 0xFCE2: 0x6094, //CJK UNIFIED IDEOGRAPH - 0xFCE3: 0x61F7, //CJK UNIFIED IDEOGRAPH - 0xFCE4: 0x6666, //CJK UNIFIED IDEOGRAPH - 0xFCE5: 0x6703, //CJK UNIFIED IDEOGRAPH - 0xFCE6: 0x6A9C, //CJK UNIFIED IDEOGRAPH - 0xFCE7: 0x6DEE, //CJK UNIFIED IDEOGRAPH - 0xFCE8: 0x6FAE, //CJK UNIFIED IDEOGRAPH - 0xFCE9: 0x7070, //CJK UNIFIED IDEOGRAPH - 0xFCEA: 0x736A, //CJK UNIFIED IDEOGRAPH - 0xFCEB: 0x7E6A, //CJK UNIFIED IDEOGRAPH - 0xFCEC: 0x81BE, //CJK UNIFIED IDEOGRAPH - 0xFCED: 0x8334, //CJK UNIFIED IDEOGRAPH - 0xFCEE: 0x86D4, //CJK UNIFIED IDEOGRAPH - 0xFCEF: 0x8AA8, //CJK UNIFIED IDEOGRAPH - 0xFCF0: 0x8CC4, //CJK UNIFIED IDEOGRAPH - 0xFCF1: 0x5283, //CJK UNIFIED IDEOGRAPH - 0xFCF2: 0x7372, //CJK UNIFIED IDEOGRAPH - 0xFCF3: 0x5B96, //CJK UNIFIED IDEOGRAPH - 0xFCF4: 0x6A6B, //CJK UNIFIED IDEOGRAPH - 0xFCF5: 0x9404, //CJK UNIFIED IDEOGRAPH - 0xFCF6: 0x54EE, //CJK UNIFIED IDEOGRAPH - 0xFCF7: 0x5686, //CJK UNIFIED IDEOGRAPH - 0xFCF8: 0x5B5D, //CJK UNIFIED IDEOGRAPH - 0xFCF9: 0x6548, //CJK UNIFIED IDEOGRAPH - 0xFCFA: 0x6585, //CJK UNIFIED IDEOGRAPH - 0xFCFB: 0x66C9, //CJK UNIFIED IDEOGRAPH - 0xFCFC: 0x689F, //CJK UNIFIED IDEOGRAPH - 0xFCFD: 0x6D8D, //CJK UNIFIED IDEOGRAPH - 0xFCFE: 0x6DC6, //CJK UNIFIED IDEOGRAPH - 0xFDA1: 0x723B, //CJK UNIFIED IDEOGRAPH - 0xFDA2: 0x80B4, //CJK UNIFIED IDEOGRAPH - 0xFDA3: 0x9175, //CJK UNIFIED IDEOGRAPH - 0xFDA4: 0x9A4D, //CJK UNIFIED IDEOGRAPH - 0xFDA5: 0x4FAF, //CJK UNIFIED IDEOGRAPH - 0xFDA6: 0x5019, //CJK UNIFIED IDEOGRAPH - 0xFDA7: 0x539A, //CJK UNIFIED IDEOGRAPH - 0xFDA8: 0x540E, //CJK UNIFIED IDEOGRAPH - 0xFDA9: 0x543C, //CJK UNIFIED IDEOGRAPH - 0xFDAA: 0x5589, //CJK UNIFIED IDEOGRAPH - 0xFDAB: 0x55C5, //CJK UNIFIED IDEOGRAPH - 0xFDAC: 0x5E3F, //CJK UNIFIED IDEOGRAPH - 0xFDAD: 0x5F8C, //CJK UNIFIED IDEOGRAPH - 0xFDAE: 0x673D, //CJK UNIFIED IDEOGRAPH - 0xFDAF: 0x7166, //CJK UNIFIED IDEOGRAPH - 0xFDB0: 0x73DD, //CJK UNIFIED IDEOGRAPH - 0xFDB1: 0x9005, //CJK UNIFIED IDEOGRAPH - 0xFDB2: 0x52DB, //CJK UNIFIED IDEOGRAPH - 0xFDB3: 0x52F3, //CJK UNIFIED IDEOGRAPH - 0xFDB4: 0x5864, //CJK UNIFIED IDEOGRAPH - 0xFDB5: 0x58CE, //CJK UNIFIED IDEOGRAPH - 0xFDB6: 0x7104, //CJK UNIFIED IDEOGRAPH - 0xFDB7: 0x718F, //CJK UNIFIED IDEOGRAPH - 0xFDB8: 0x71FB, //CJK UNIFIED IDEOGRAPH - 0xFDB9: 0x85B0, //CJK UNIFIED IDEOGRAPH - 0xFDBA: 0x8A13, //CJK UNIFIED IDEOGRAPH - 0xFDBB: 0x6688, //CJK UNIFIED IDEOGRAPH - 0xFDBC: 0x85A8, //CJK UNIFIED IDEOGRAPH - 0xFDBD: 0x55A7, //CJK UNIFIED IDEOGRAPH - 0xFDBE: 0x6684, //CJK UNIFIED IDEOGRAPH - 0xFDBF: 0x714A, //CJK UNIFIED IDEOGRAPH - 0xFDC0: 0x8431, //CJK UNIFIED IDEOGRAPH - 0xFDC1: 0x5349, //CJK UNIFIED IDEOGRAPH - 0xFDC2: 0x5599, //CJK UNIFIED IDEOGRAPH - 0xFDC3: 0x6BC1, //CJK UNIFIED IDEOGRAPH - 0xFDC4: 0x5F59, //CJK UNIFIED IDEOGRAPH - 0xFDC5: 0x5FBD, //CJK UNIFIED IDEOGRAPH - 0xFDC6: 0x63EE, //CJK UNIFIED IDEOGRAPH - 0xFDC7: 0x6689, //CJK UNIFIED IDEOGRAPH - 0xFDC8: 0x7147, //CJK UNIFIED IDEOGRAPH - 0xFDC9: 0x8AF1, //CJK UNIFIED IDEOGRAPH - 0xFDCA: 0x8F1D, //CJK UNIFIED IDEOGRAPH - 0xFDCB: 0x9EBE, //CJK UNIFIED IDEOGRAPH - 0xFDCC: 0x4F11, //CJK UNIFIED IDEOGRAPH - 0xFDCD: 0x643A, //CJK UNIFIED IDEOGRAPH - 0xFDCE: 0x70CB, //CJK UNIFIED IDEOGRAPH - 0xFDCF: 0x7566, //CJK UNIFIED IDEOGRAPH - 0xFDD0: 0x8667, //CJK UNIFIED IDEOGRAPH - 0xFDD1: 0x6064, //CJK UNIFIED IDEOGRAPH - 0xFDD2: 0x8B4E, //CJK UNIFIED IDEOGRAPH - 0xFDD3: 0x9DF8, //CJK UNIFIED IDEOGRAPH - 0xFDD4: 0x5147, //CJK UNIFIED IDEOGRAPH - 0xFDD5: 0x51F6, //CJK UNIFIED IDEOGRAPH - 0xFDD6: 0x5308, //CJK UNIFIED IDEOGRAPH - 0xFDD7: 0x6D36, //CJK UNIFIED IDEOGRAPH - 0xFDD8: 0x80F8, //CJK UNIFIED IDEOGRAPH - 0xFDD9: 0x9ED1, //CJK UNIFIED IDEOGRAPH - 0xFDDA: 0x6615, //CJK UNIFIED IDEOGRAPH - 0xFDDB: 0x6B23, //CJK UNIFIED IDEOGRAPH - 0xFDDC: 0x7098, //CJK UNIFIED IDEOGRAPH - 0xFDDD: 0x75D5, //CJK UNIFIED IDEOGRAPH - 0xFDDE: 0x5403, //CJK UNIFIED IDEOGRAPH - 0xFDDF: 0x5C79, //CJK UNIFIED IDEOGRAPH - 0xFDE0: 0x7D07, //CJK UNIFIED IDEOGRAPH - 0xFDE1: 0x8A16, //CJK UNIFIED IDEOGRAPH - 0xFDE2: 0x6B20, //CJK UNIFIED IDEOGRAPH - 0xFDE3: 0x6B3D, //CJK UNIFIED IDEOGRAPH - 0xFDE4: 0x6B46, //CJK UNIFIED IDEOGRAPH - 0xFDE5: 0x5438, //CJK UNIFIED IDEOGRAPH - 0xFDE6: 0x6070, //CJK UNIFIED IDEOGRAPH - 0xFDE7: 0x6D3D, //CJK UNIFIED IDEOGRAPH - 0xFDE8: 0x7FD5, //CJK UNIFIED IDEOGRAPH - 0xFDE9: 0x8208, //CJK UNIFIED IDEOGRAPH - 0xFDEA: 0x50D6, //CJK UNIFIED IDEOGRAPH - 0xFDEB: 0x51DE, //CJK UNIFIED IDEOGRAPH - 0xFDEC: 0x559C, //CJK UNIFIED IDEOGRAPH - 0xFDED: 0x566B, //CJK UNIFIED IDEOGRAPH - 0xFDEE: 0x56CD, //CJK UNIFIED IDEOGRAPH - 0xFDEF: 0x59EC, //CJK UNIFIED IDEOGRAPH - 0xFDF0: 0x5B09, //CJK UNIFIED IDEOGRAPH - 0xFDF1: 0x5E0C, //CJK UNIFIED IDEOGRAPH - 0xFDF2: 0x6199, //CJK UNIFIED IDEOGRAPH - 0xFDF3: 0x6198, //CJK UNIFIED IDEOGRAPH - 0xFDF4: 0x6231, //CJK UNIFIED IDEOGRAPH - 0xFDF5: 0x665E, //CJK UNIFIED IDEOGRAPH - 0xFDF6: 0x66E6, //CJK UNIFIED IDEOGRAPH - 0xFDF7: 0x7199, //CJK UNIFIED IDEOGRAPH - 0xFDF8: 0x71B9, //CJK UNIFIED IDEOGRAPH - 0xFDF9: 0x71BA, //CJK UNIFIED IDEOGRAPH - 0xFDFA: 0x72A7, //CJK UNIFIED IDEOGRAPH - 0xFDFB: 0x79A7, //CJK UNIFIED IDEOGRAPH - 0xFDFC: 0x7A00, //CJK UNIFIED IDEOGRAPH - 0xFDFD: 0x7FB2, //CJK UNIFIED IDEOGRAPH - 0xFDFE: 0x8A70, //CJK UNIFIED IDEOGRAPH - }, -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/cp950.go b/vendor/github.com/denisenkom/go-mssqldb/cp950.go deleted file mode 100644 index cbf25cb91..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/cp950.go +++ /dev/null @@ -1,13767 +0,0 @@ -package mssql - -var cp950 *charsetMap = &charsetMap{ - sb: [256]rune{ - 0x0000, //NULL - 0x0001, //START OF HEADING - 0x0002, //START OF TEXT - 0x0003, //END OF TEXT - 0x0004, //END OF TRANSMISSION - 0x0005, //ENQUIRY - 0x0006, //ACKNOWLEDGE - 0x0007, //BELL - 0x0008, //BACKSPACE - 0x0009, //HORIZONTAL TABULATION - 0x000A, //LINE FEED - 0x000B, //VERTICAL TABULATION - 0x000C, //FORM FEED - 0x000D, //CARRIAGE RETURN - 0x000E, //SHIFT OUT - 0x000F, //SHIFT IN - 0x0010, //DATA LINK ESCAPE - 0x0011, //DEVICE CONTROL ONE - 0x0012, //DEVICE CONTROL TWO - 0x0013, //DEVICE CONTROL THREE - 0x0014, //DEVICE CONTROL FOUR - 0x0015, //NEGATIVE ACKNOWLEDGE - 0x0016, //SYNCHRONOUS IDLE - 0x0017, //END OF TRANSMISSION BLOCK - 0x0018, //CANCEL - 0x0019, //END OF MEDIUM - 0x001A, //SUBSTITUTE - 0x001B, //ESCAPE - 0x001C, //FILE SEPARATOR - 0x001D, //GROUP SEPARATOR - 0x001E, //RECORD SEPARATOR - 0x001F, //UNIT SEPARATOR - 0x0020, //SPACE - 0x0021, //EXCLAMATION MARK - 0x0022, //QUOTATION MARK - 0x0023, //NUMBER SIGN - 0x0024, //DOLLAR SIGN - 0x0025, //PERCENT SIGN - 0x0026, //AMPERSAND - 0x0027, //APOSTROPHE - 0x0028, //LEFT PARENTHESIS - 0x0029, //RIGHT PARENTHESIS - 0x002A, //ASTERISK - 0x002B, //PLUS SIGN - 0x002C, //COMMA - 0x002D, //HYPHEN-MINUS - 0x002E, //FULL STOP - 0x002F, //SOLIDUS - 0x0030, //DIGIT ZERO - 0x0031, //DIGIT ONE - 0x0032, //DIGIT TWO - 0x0033, //DIGIT THREE - 0x0034, //DIGIT FOUR - 0x0035, //DIGIT FIVE - 0x0036, //DIGIT SIX - 0x0037, //DIGIT SEVEN - 0x0038, //DIGIT EIGHT - 0x0039, //DIGIT NINE - 0x003A, //COLON - 0x003B, //SEMICOLON - 0x003C, //LESS-THAN SIGN - 0x003D, //EQUALS SIGN - 0x003E, //GREATER-THAN SIGN - 0x003F, //QUESTION MARK - 0x0040, //COMMERCIAL AT - 0x0041, //LATIN CAPITAL LETTER A - 0x0042, //LATIN CAPITAL LETTER B - 0x0043, //LATIN CAPITAL LETTER C - 0x0044, //LATIN CAPITAL LETTER D - 0x0045, //LATIN CAPITAL LETTER E - 0x0046, //LATIN CAPITAL LETTER F - 0x0047, //LATIN CAPITAL LETTER G - 0x0048, //LATIN CAPITAL LETTER H - 0x0049, //LATIN CAPITAL LETTER I - 0x004A, //LATIN CAPITAL LETTER J - 0x004B, //LATIN CAPITAL LETTER K - 0x004C, //LATIN CAPITAL LETTER L - 0x004D, //LATIN CAPITAL LETTER M - 0x004E, //LATIN CAPITAL LETTER N - 0x004F, //LATIN CAPITAL LETTER O - 0x0050, //LATIN CAPITAL LETTER P - 0x0051, //LATIN CAPITAL LETTER Q - 0x0052, //LATIN CAPITAL LETTER R - 0x0053, //LATIN CAPITAL LETTER S - 0x0054, //LATIN CAPITAL LETTER T - 0x0055, //LATIN CAPITAL LETTER U - 0x0056, //LATIN CAPITAL LETTER V - 0x0057, //LATIN CAPITAL LETTER W - 0x0058, //LATIN CAPITAL LETTER X - 0x0059, //LATIN CAPITAL LETTER Y - 0x005A, //LATIN CAPITAL LETTER Z - 0x005B, //LEFT SQUARE BRACKET - 0x005C, //REVERSE SOLIDUS - 0x005D, //RIGHT SQUARE BRACKET - 0x005E, //CIRCUMFLEX ACCENT - 0x005F, //LOW LINE - 0x0060, //GRAVE ACCENT - 0x0061, //LATIN SMALL LETTER A - 0x0062, //LATIN SMALL LETTER B - 0x0063, //LATIN SMALL LETTER C - 0x0064, //LATIN SMALL LETTER D - 0x0065, //LATIN SMALL LETTER E - 0x0066, //LATIN SMALL LETTER F - 0x0067, //LATIN SMALL LETTER G - 0x0068, //LATIN SMALL LETTER H - 0x0069, //LATIN SMALL LETTER I - 0x006A, //LATIN SMALL LETTER J - 0x006B, //LATIN SMALL LETTER K - 0x006C, //LATIN SMALL LETTER L - 0x006D, //LATIN SMALL LETTER M - 0x006E, //LATIN SMALL LETTER N - 0x006F, //LATIN SMALL LETTER O - 0x0070, //LATIN SMALL LETTER P - 0x0071, //LATIN SMALL LETTER Q - 0x0072, //LATIN SMALL LETTER R - 0x0073, //LATIN SMALL LETTER S - 0x0074, //LATIN SMALL LETTER T - 0x0075, //LATIN SMALL LETTER U - 0x0076, //LATIN SMALL LETTER V - 0x0077, //LATIN SMALL LETTER W - 0x0078, //LATIN SMALL LETTER X - 0x0079, //LATIN SMALL LETTER Y - 0x007A, //LATIN SMALL LETTER Z - 0x007B, //LEFT CURLY BRACKET - 0x007C, //VERTICAL LINE - 0x007D, //RIGHT CURLY BRACKET - 0x007E, //TILDE - 0x007F, //DELETE - 0xFFFD, //UNDEFINED - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - -1, //DBCS LEAD BYTE - 0xFFFD, //UNDEFINED - }, - db: map[int]rune{ - 0xA140: 0x3000, //IDEOGRAPHIC SPACE - 0xA141: 0xFF0C, //FULLWIDTH COMMA - 0xA142: 0x3001, //IDEOGRAPHIC COMMA - 0xA143: 0x3002, //IDEOGRAPHIC FULL STOP - 0xA144: 0xFF0E, //FULLWIDTH FULL STOP - 0xA145: 0x2027, //HYPHENATION POINT - 0xA146: 0xFF1B, //FULLWIDTH SEMICOLON - 0xA147: 0xFF1A, //FULLWIDTH COLON - 0xA148: 0xFF1F, //FULLWIDTH QUESTION MARK - 0xA149: 0xFF01, //FULLWIDTH EXCLAMATION MARK - 0xA14A: 0xFE30, //PRESENTATION FORM FOR VERTICAL TWO DOT LEADER - 0xA14B: 0x2026, //HORIZONTAL ELLIPSIS - 0xA14C: 0x2025, //TWO DOT LEADER - 0xA14D: 0xFE50, //SMALL COMMA - 0xA14E: 0xFE51, //SMALL IDEOGRAPHIC COMMA - 0xA14F: 0xFE52, //SMALL FULL STOP - 0xA150: 0x00B7, //MIDDLE DOT - 0xA151: 0xFE54, //SMALL SEMICOLON - 0xA152: 0xFE55, //SMALL COLON - 0xA153: 0xFE56, //SMALL QUESTION MARK - 0xA154: 0xFE57, //SMALL EXCLAMATION MARK - 0xA155: 0xFF5C, //FULLWIDTH VERTICAL LINE - 0xA156: 0x2013, //EN DASH - 0xA157: 0xFE31, //PRESENTATION FORM FOR VERTICAL EM DASH - 0xA158: 0x2014, //EM DASH - 0xA159: 0xFE33, //PRESENTATION FORM FOR VERTICAL LOW LINE - 0xA15A: 0x2574, //BOX DRAWINGS LIGHT LEFT - 0xA15B: 0xFE34, //PRESENTATION FORM FOR VERTICAL WAVY LOW LINE - 0xA15C: 0xFE4F, //WAVY LOW LINE - 0xA15D: 0xFF08, //FULLWIDTH LEFT PARENTHESIS - 0xA15E: 0xFF09, //FULLWIDTH RIGHT PARENTHESIS - 0xA15F: 0xFE35, //PRESENTATION FORM FOR VERTICAL LEFT PARENTHESIS - 0xA160: 0xFE36, //PRESENTATION FORM FOR VERTICAL RIGHT PARENTHESIS - 0xA161: 0xFF5B, //FULLWIDTH LEFT CURLY BRACKET - 0xA162: 0xFF5D, //FULLWIDTH RIGHT CURLY BRACKET - 0xA163: 0xFE37, //PRESENTATION FORM FOR VERTICAL LEFT CURLY BRACKET - 0xA164: 0xFE38, //PRESENTATION FORM FOR VERTICAL RIGHT CURLY BRACKET - 0xA165: 0x3014, //LEFT TORTOISE SHELL BRACKET - 0xA166: 0x3015, //RIGHT TORTOISE SHELL BRACKET - 0xA167: 0xFE39, //PRESENTATION FORM FOR VERTICAL LEFT TORTOISE SHELL BRACKET - 0xA168: 0xFE3A, //PRESENTATION FORM FOR VERTICAL RIGHT TORTOISE SHELL BRACKET - 0xA169: 0x3010, //LEFT BLACK LENTICULAR BRACKET - 0xA16A: 0x3011, //RIGHT BLACK LENTICULAR BRACKET - 0xA16B: 0xFE3B, //PRESENTATION FORM FOR VERTICAL LEFT BLACK LENTICULAR BRACKET - 0xA16C: 0xFE3C, //PRESENTATION FORM FOR VERTICAL RIGHT BLACK LENTICULAR BRACKET - 0xA16D: 0x300A, //LEFT DOUBLE ANGLE BRACKET - 0xA16E: 0x300B, //RIGHT DOUBLE ANGLE BRACKET - 0xA16F: 0xFE3D, //PRESENTATION FORM FOR VERTICAL LEFT DOUBLE ANGLE BRACKET - 0xA170: 0xFE3E, //PRESENTATION FORM FOR VERTICAL RIGHT DOUBLE ANGLE BRACKET - 0xA171: 0x3008, //LEFT ANGLE BRACKET - 0xA172: 0x3009, //RIGHT ANGLE BRACKET - 0xA173: 0xFE3F, //PRESENTATION FORM FOR VERTICAL LEFT ANGLE BRACKET - 0xA174: 0xFE40, //PRESENTATION FORM FOR VERTICAL RIGHT ANGLE BRACKET - 0xA175: 0x300C, //LEFT CORNER BRACKET - 0xA176: 0x300D, //RIGHT CORNER BRACKET - 0xA177: 0xFE41, //PRESENTATION FORM FOR VERTICAL LEFT CORNER BRACKET - 0xA178: 0xFE42, //PRESENTATION FORM FOR VERTICAL RIGHT CORNER BRACKET - 0xA179: 0x300E, //LEFT WHITE CORNER BRACKET - 0xA17A: 0x300F, //RIGHT WHITE CORNER BRACKET - 0xA17B: 0xFE43, //PRESENTATION FORM FOR VERTICAL LEFT WHITE CORNER BRACKET - 0xA17C: 0xFE44, //PRESENTATION FORM FOR VERTICAL RIGHT WHITE CORNER BRACKET - 0xA17D: 0xFE59, //SMALL LEFT PARENTHESIS - 0xA17E: 0xFE5A, //SMALL RIGHT PARENTHESIS - 0xA1A1: 0xFE5B, //SMALL LEFT CURLY BRACKET - 0xA1A2: 0xFE5C, //SMALL RIGHT CURLY BRACKET - 0xA1A3: 0xFE5D, //SMALL LEFT TORTOISE SHELL BRACKET - 0xA1A4: 0xFE5E, //SMALL RIGHT TORTOISE SHELL BRACKET - 0xA1A5: 0x2018, //LEFT SINGLE QUOTATION MARK - 0xA1A6: 0x2019, //RIGHT SINGLE QUOTATION MARK - 0xA1A7: 0x201C, //LEFT DOUBLE QUOTATION MARK - 0xA1A8: 0x201D, //RIGHT DOUBLE QUOTATION MARK - 0xA1A9: 0x301D, //REVERSED DOUBLE PRIME QUOTATION MARK - 0xA1AA: 0x301E, //DOUBLE PRIME QUOTATION MARK - 0xA1AB: 0x2035, //REVERSED PRIME - 0xA1AC: 0x2032, //PRIME - 0xA1AD: 0xFF03, //FULLWIDTH NUMBER SIGN - 0xA1AE: 0xFF06, //FULLWIDTH AMPERSAND - 0xA1AF: 0xFF0A, //FULLWIDTH ASTERISK - 0xA1B0: 0x203B, //REFERENCE MARK - 0xA1B1: 0x00A7, //SECTION SIGN - 0xA1B2: 0x3003, //DITTO MARK - 0xA1B3: 0x25CB, //WHITE CIRCLE - 0xA1B4: 0x25CF, //BLACK CIRCLE - 0xA1B5: 0x25B3, //WHITE UP-POINTING TRIANGLE - 0xA1B6: 0x25B2, //BLACK UP-POINTING TRIANGLE - 0xA1B7: 0x25CE, //BULLSEYE - 0xA1B8: 0x2606, //WHITE STAR - 0xA1B9: 0x2605, //BLACK STAR - 0xA1BA: 0x25C7, //WHITE DIAMOND - 0xA1BB: 0x25C6, //BLACK DIAMOND - 0xA1BC: 0x25A1, //WHITE SQUARE - 0xA1BD: 0x25A0, //BLACK SQUARE - 0xA1BE: 0x25BD, //WHITE DOWN-POINTING TRIANGLE - 0xA1BF: 0x25BC, //BLACK DOWN-POINTING TRIANGLE - 0xA1C0: 0x32A3, //CIRCLED IDEOGRAPH CORRECT - 0xA1C1: 0x2105, //CARE OF - 0xA1C2: 0x00AF, //MACRON - 0xA1C3: 0xFFE3, //FULLWIDTH MACRON - 0xA1C4: 0xFF3F, //FULLWIDTH LOW LINE - 0xA1C5: 0x02CD, //MODIFIER LETTER LOW MACRON - 0xA1C6: 0xFE49, //DASHED OVERLINE - 0xA1C7: 0xFE4A, //CENTRELINE OVERLINE - 0xA1C8: 0xFE4D, //DASHED LOW LINE - 0xA1C9: 0xFE4E, //CENTRELINE LOW LINE - 0xA1CA: 0xFE4B, //WAVY OVERLINE - 0xA1CB: 0xFE4C, //DOUBLE WAVY OVERLINE - 0xA1CC: 0xFE5F, //SMALL NUMBER SIGN - 0xA1CD: 0xFE60, //SMALL AMPERSAND - 0xA1CE: 0xFE61, //SMALL ASTERISK - 0xA1CF: 0xFF0B, //FULLWIDTH PLUS SIGN - 0xA1D0: 0xFF0D, //FULLWIDTH HYPHEN-MINUS - 0xA1D1: 0x00D7, //MULTIPLICATION SIGN - 0xA1D2: 0x00F7, //DIVISION SIGN - 0xA1D3: 0x00B1, //PLUS-MINUS SIGN - 0xA1D4: 0x221A, //SQUARE ROOT - 0xA1D5: 0xFF1C, //FULLWIDTH LESS-THAN SIGN - 0xA1D6: 0xFF1E, //FULLWIDTH GREATER-THAN SIGN - 0xA1D7: 0xFF1D, //FULLWIDTH EQUALS SIGN - 0xA1D8: 0x2266, //LESS-THAN OVER EQUAL TO - 0xA1D9: 0x2267, //GREATER-THAN OVER EQUAL TO - 0xA1DA: 0x2260, //NOT EQUAL TO - 0xA1DB: 0x221E, //INFINITY - 0xA1DC: 0x2252, //APPROXIMATELY EQUAL TO OR THE IMAGE OF - 0xA1DD: 0x2261, //IDENTICAL TO - 0xA1DE: 0xFE62, //SMALL PLUS SIGN - 0xA1DF: 0xFE63, //SMALL HYPHEN-MINUS - 0xA1E0: 0xFE64, //SMALL LESS-THAN SIGN - 0xA1E1: 0xFE65, //SMALL GREATER-THAN SIGN - 0xA1E2: 0xFE66, //SMALL EQUALS SIGN - 0xA1E3: 0xFF5E, //FULLWIDTH TILDE - 0xA1E4: 0x2229, //INTERSECTION - 0xA1E5: 0x222A, //UNION - 0xA1E6: 0x22A5, //UP TACK - 0xA1E7: 0x2220, //ANGLE - 0xA1E8: 0x221F, //RIGHT ANGLE - 0xA1E9: 0x22BF, //RIGHT TRIANGLE - 0xA1EA: 0x33D2, //SQUARE LOG - 0xA1EB: 0x33D1, //SQUARE LN - 0xA1EC: 0x222B, //INTEGRAL - 0xA1ED: 0x222E, //CONTOUR INTEGRAL - 0xA1EE: 0x2235, //BECAUSE - 0xA1EF: 0x2234, //THEREFORE - 0xA1F0: 0x2640, //FEMALE SIGN - 0xA1F1: 0x2642, //MALE SIGN - 0xA1F2: 0x2295, //CIRCLED PLUS - 0xA1F3: 0x2299, //CIRCLED DOT OPERATOR - 0xA1F4: 0x2191, //UPWARDS ARROW - 0xA1F5: 0x2193, //DOWNWARDS ARROW - 0xA1F6: 0x2190, //LEFTWARDS ARROW - 0xA1F7: 0x2192, //RIGHTWARDS ARROW - 0xA1F8: 0x2196, //NORTH WEST ARROW - 0xA1F9: 0x2197, //NORTH EAST ARROW - 0xA1FA: 0x2199, //SOUTH WEST ARROW - 0xA1FB: 0x2198, //SOUTH EAST ARROW - 0xA1FC: 0x2225, //PARALLEL TO - 0xA1FD: 0x2223, //DIVIDES - 0xA1FE: 0xFF0F, //FULLWIDTH SOLIDUS - 0xA240: 0xFF3C, //FULLWIDTH REVERSE SOLIDUS - 0xA241: 0x2215, //DIVISION SLASH - 0xA242: 0xFE68, //SMALL REVERSE SOLIDUS - 0xA243: 0xFF04, //FULLWIDTH DOLLAR SIGN - 0xA244: 0xFFE5, //FULLWIDTH YEN SIGN - 0xA245: 0x3012, //POSTAL MARK - 0xA246: 0xFFE0, //FULLWIDTH CENT SIGN - 0xA247: 0xFFE1, //FULLWIDTH POUND SIGN - 0xA248: 0xFF05, //FULLWIDTH PERCENT SIGN - 0xA249: 0xFF20, //FULLWIDTH COMMERCIAL AT - 0xA24A: 0x2103, //DEGREE CELSIUS - 0xA24B: 0x2109, //DEGREE FAHRENHEIT - 0xA24C: 0xFE69, //SMALL DOLLAR SIGN - 0xA24D: 0xFE6A, //SMALL PERCENT SIGN - 0xA24E: 0xFE6B, //SMALL COMMERCIAL AT - 0xA24F: 0x33D5, //SQUARE MIL - 0xA250: 0x339C, //SQUARE MM - 0xA251: 0x339D, //SQUARE CM - 0xA252: 0x339E, //SQUARE KM - 0xA253: 0x33CE, //SQUARE KM CAPITAL - 0xA254: 0x33A1, //SQUARE M SQUARED - 0xA255: 0x338E, //SQUARE MG - 0xA256: 0x338F, //SQUARE KG - 0xA257: 0x33C4, //SQUARE CC - 0xA258: 0x00B0, //DEGREE SIGN - 0xA259: 0x5159, //CJK UNIFIED IDEOGRAPH - 0xA25A: 0x515B, //CJK UNIFIED IDEOGRAPH - 0xA25B: 0x515E, //CJK UNIFIED IDEOGRAPH - 0xA25C: 0x515D, //CJK UNIFIED IDEOGRAPH - 0xA25D: 0x5161, //CJK UNIFIED IDEOGRAPH - 0xA25E: 0x5163, //CJK UNIFIED IDEOGRAPH - 0xA25F: 0x55E7, //CJK UNIFIED IDEOGRAPH - 0xA260: 0x74E9, //CJK UNIFIED IDEOGRAPH - 0xA261: 0x7CCE, //CJK UNIFIED IDEOGRAPH - 0xA262: 0x2581, //LOWER ONE EIGHTH BLOCK - 0xA263: 0x2582, //LOWER ONE QUARTER BLOCK - 0xA264: 0x2583, //LOWER THREE EIGHTHS BLOCK - 0xA265: 0x2584, //LOWER HALF BLOCK - 0xA266: 0x2585, //LOWER FIVE EIGHTHS BLOCK - 0xA267: 0x2586, //LOWER THREE QUARTERS BLOCK - 0xA268: 0x2587, //LOWER SEVEN EIGHTHS BLOCK - 0xA269: 0x2588, //FULL BLOCK - 0xA26A: 0x258F, //LEFT ONE EIGHTH BLOCK - 0xA26B: 0x258E, //LEFT ONE QUARTER BLOCK - 0xA26C: 0x258D, //LEFT THREE EIGHTHS BLOCK - 0xA26D: 0x258C, //LEFT HALF BLOCK - 0xA26E: 0x258B, //LEFT FIVE EIGHTHS BLOCK - 0xA26F: 0x258A, //LEFT THREE QUARTERS BLOCK - 0xA270: 0x2589, //LEFT SEVEN EIGHTHS BLOCK - 0xA271: 0x253C, //BOX DRAWINGS LIGHT VERTICAL AND HORIZONTAL - 0xA272: 0x2534, //BOX DRAWINGS LIGHT UP AND HORIZONTAL - 0xA273: 0x252C, //BOX DRAWINGS LIGHT DOWN AND HORIZONTAL - 0xA274: 0x2524, //BOX DRAWINGS LIGHT VERTICAL AND LEFT - 0xA275: 0x251C, //BOX DRAWINGS LIGHT VERTICAL AND RIGHT - 0xA276: 0x2594, //UPPER ONE EIGHTH BLOCK - 0xA277: 0x2500, //BOX DRAWINGS LIGHT HORIZONTAL - 0xA278: 0x2502, //BOX DRAWINGS LIGHT VERTICAL - 0xA279: 0x2595, //RIGHT ONE EIGHTH BLOCK - 0xA27A: 0x250C, //BOX DRAWINGS LIGHT DOWN AND RIGHT - 0xA27B: 0x2510, //BOX DRAWINGS LIGHT DOWN AND LEFT - 0xA27C: 0x2514, //BOX DRAWINGS LIGHT UP AND RIGHT - 0xA27D: 0x2518, //BOX DRAWINGS LIGHT UP AND LEFT - 0xA27E: 0x256D, //BOX DRAWINGS LIGHT ARC DOWN AND RIGHT - 0xA2A1: 0x256E, //BOX DRAWINGS LIGHT ARC DOWN AND LEFT - 0xA2A2: 0x2570, //BOX DRAWINGS LIGHT ARC UP AND RIGHT - 0xA2A3: 0x256F, //BOX DRAWINGS LIGHT ARC UP AND LEFT - 0xA2A4: 0x2550, //BOX DRAWINGS DOUBLE HORIZONTAL - 0xA2A5: 0x255E, //BOX DRAWINGS VERTICAL SINGLE AND RIGHT DOUBLE - 0xA2A6: 0x256A, //BOX DRAWINGS VERTICAL SINGLE AND HORIZONTAL DOUBLE - 0xA2A7: 0x2561, //BOX DRAWINGS VERTICAL SINGLE AND LEFT DOUBLE - 0xA2A8: 0x25E2, //BLACK LOWER RIGHT TRIANGLE - 0xA2A9: 0x25E3, //BLACK LOWER LEFT TRIANGLE - 0xA2AA: 0x25E5, //BLACK UPPER RIGHT TRIANGLE - 0xA2AB: 0x25E4, //BLACK UPPER LEFT TRIANGLE - 0xA2AC: 0x2571, //BOX DRAWINGS LIGHT DIAGONAL UPPER RIGHT TO LOWER LEFT - 0xA2AD: 0x2572, //BOX DRAWINGS LIGHT DIAGONAL UPPER LEFT TO LOWER RIGHT - 0xA2AE: 0x2573, //BOX DRAWINGS LIGHT DIAGONAL CROSS - 0xA2AF: 0xFF10, //FULLWIDTH DIGIT ZERO - 0xA2B0: 0xFF11, //FULLWIDTH DIGIT ONE - 0xA2B1: 0xFF12, //FULLWIDTH DIGIT TWO - 0xA2B2: 0xFF13, //FULLWIDTH DIGIT THREE - 0xA2B3: 0xFF14, //FULLWIDTH DIGIT FOUR - 0xA2B4: 0xFF15, //FULLWIDTH DIGIT FIVE - 0xA2B5: 0xFF16, //FULLWIDTH DIGIT SIX - 0xA2B6: 0xFF17, //FULLWIDTH DIGIT SEVEN - 0xA2B7: 0xFF18, //FULLWIDTH DIGIT EIGHT - 0xA2B8: 0xFF19, //FULLWIDTH DIGIT NINE - 0xA2B9: 0x2160, //ROMAN NUMERAL ONE - 0xA2BA: 0x2161, //ROMAN NUMERAL TWO - 0xA2BB: 0x2162, //ROMAN NUMERAL THREE - 0xA2BC: 0x2163, //ROMAN NUMERAL FOUR - 0xA2BD: 0x2164, //ROMAN NUMERAL FIVE - 0xA2BE: 0x2165, //ROMAN NUMERAL SIX - 0xA2BF: 0x2166, //ROMAN NUMERAL SEVEN - 0xA2C0: 0x2167, //ROMAN NUMERAL EIGHT - 0xA2C1: 0x2168, //ROMAN NUMERAL NINE - 0xA2C2: 0x2169, //ROMAN NUMERAL TEN - 0xA2C3: 0x3021, //HANGZHOU NUMERAL ONE - 0xA2C4: 0x3022, //HANGZHOU NUMERAL TWO - 0xA2C5: 0x3023, //HANGZHOU NUMERAL THREE - 0xA2C6: 0x3024, //HANGZHOU NUMERAL FOUR - 0xA2C7: 0x3025, //HANGZHOU NUMERAL FIVE - 0xA2C8: 0x3026, //HANGZHOU NUMERAL SIX - 0xA2C9: 0x3027, //HANGZHOU NUMERAL SEVEN - 0xA2CA: 0x3028, //HANGZHOU NUMERAL EIGHT - 0xA2CB: 0x3029, //HANGZHOU NUMERAL NINE - 0xA2CC: 0x5341, //CJK UNIFIED IDEOGRAPH - 0xA2CD: 0x5344, //CJK UNIFIED IDEOGRAPH - 0xA2CE: 0x5345, //CJK UNIFIED IDEOGRAPH - 0xA2CF: 0xFF21, //FULLWIDTH LATIN CAPITAL LETTER A - 0xA2D0: 0xFF22, //FULLWIDTH LATIN CAPITAL LETTER B - 0xA2D1: 0xFF23, //FULLWIDTH LATIN CAPITAL LETTER C - 0xA2D2: 0xFF24, //FULLWIDTH LATIN CAPITAL LETTER D - 0xA2D3: 0xFF25, //FULLWIDTH LATIN CAPITAL LETTER E - 0xA2D4: 0xFF26, //FULLWIDTH LATIN CAPITAL LETTER F - 0xA2D5: 0xFF27, //FULLWIDTH LATIN CAPITAL LETTER G - 0xA2D6: 0xFF28, //FULLWIDTH LATIN CAPITAL LETTER H - 0xA2D7: 0xFF29, //FULLWIDTH LATIN CAPITAL LETTER I - 0xA2D8: 0xFF2A, //FULLWIDTH LATIN CAPITAL LETTER J - 0xA2D9: 0xFF2B, //FULLWIDTH LATIN CAPITAL LETTER K - 0xA2DA: 0xFF2C, //FULLWIDTH LATIN CAPITAL LETTER L - 0xA2DB: 0xFF2D, //FULLWIDTH LATIN CAPITAL LETTER M - 0xA2DC: 0xFF2E, //FULLWIDTH LATIN CAPITAL LETTER N - 0xA2DD: 0xFF2F, //FULLWIDTH LATIN CAPITAL LETTER O - 0xA2DE: 0xFF30, //FULLWIDTH LATIN CAPITAL LETTER P - 0xA2DF: 0xFF31, //FULLWIDTH LATIN CAPITAL LETTER Q - 0xA2E0: 0xFF32, //FULLWIDTH LATIN CAPITAL LETTER R - 0xA2E1: 0xFF33, //FULLWIDTH LATIN CAPITAL LETTER S - 0xA2E2: 0xFF34, //FULLWIDTH LATIN CAPITAL LETTER T - 0xA2E3: 0xFF35, //FULLWIDTH LATIN CAPITAL LETTER U - 0xA2E4: 0xFF36, //FULLWIDTH LATIN CAPITAL LETTER V - 0xA2E5: 0xFF37, //FULLWIDTH LATIN CAPITAL LETTER W - 0xA2E6: 0xFF38, //FULLWIDTH LATIN CAPITAL LETTER X - 0xA2E7: 0xFF39, //FULLWIDTH LATIN CAPITAL LETTER Y - 0xA2E8: 0xFF3A, //FULLWIDTH LATIN CAPITAL LETTER Z - 0xA2E9: 0xFF41, //FULLWIDTH LATIN SMALL LETTER A - 0xA2EA: 0xFF42, //FULLWIDTH LATIN SMALL LETTER B - 0xA2EB: 0xFF43, //FULLWIDTH LATIN SMALL LETTER C - 0xA2EC: 0xFF44, //FULLWIDTH LATIN SMALL LETTER D - 0xA2ED: 0xFF45, //FULLWIDTH LATIN SMALL LETTER E - 0xA2EE: 0xFF46, //FULLWIDTH LATIN SMALL LETTER F - 0xA2EF: 0xFF47, //FULLWIDTH LATIN SMALL LETTER G - 0xA2F0: 0xFF48, //FULLWIDTH LATIN SMALL LETTER H - 0xA2F1: 0xFF49, //FULLWIDTH LATIN SMALL LETTER I - 0xA2F2: 0xFF4A, //FULLWIDTH LATIN SMALL LETTER J - 0xA2F3: 0xFF4B, //FULLWIDTH LATIN SMALL LETTER K - 0xA2F4: 0xFF4C, //FULLWIDTH LATIN SMALL LETTER L - 0xA2F5: 0xFF4D, //FULLWIDTH LATIN SMALL LETTER M - 0xA2F6: 0xFF4E, //FULLWIDTH LATIN SMALL LETTER N - 0xA2F7: 0xFF4F, //FULLWIDTH LATIN SMALL LETTER O - 0xA2F8: 0xFF50, //FULLWIDTH LATIN SMALL LETTER P - 0xA2F9: 0xFF51, //FULLWIDTH LATIN SMALL LETTER Q - 0xA2FA: 0xFF52, //FULLWIDTH LATIN SMALL LETTER R - 0xA2FB: 0xFF53, //FULLWIDTH LATIN SMALL LETTER S - 0xA2FC: 0xFF54, //FULLWIDTH LATIN SMALL LETTER T - 0xA2FD: 0xFF55, //FULLWIDTH LATIN SMALL LETTER U - 0xA2FE: 0xFF56, //FULLWIDTH LATIN SMALL LETTER V - 0xA340: 0xFF57, //FULLWIDTH LATIN SMALL LETTER W - 0xA341: 0xFF58, //FULLWIDTH LATIN SMALL LETTER X - 0xA342: 0xFF59, //FULLWIDTH LATIN SMALL LETTER Y - 0xA343: 0xFF5A, //FULLWIDTH LATIN SMALL LETTER Z - 0xA344: 0x0391, //GREEK CAPITAL LETTER ALPHA - 0xA345: 0x0392, //GREEK CAPITAL LETTER BETA - 0xA346: 0x0393, //GREEK CAPITAL LETTER GAMMA - 0xA347: 0x0394, //GREEK CAPITAL LETTER DELTA - 0xA348: 0x0395, //GREEK CAPITAL LETTER EPSILON - 0xA349: 0x0396, //GREEK CAPITAL LETTER ZETA - 0xA34A: 0x0397, //GREEK CAPITAL LETTER ETA - 0xA34B: 0x0398, //GREEK CAPITAL LETTER THETA - 0xA34C: 0x0399, //GREEK CAPITAL LETTER IOTA - 0xA34D: 0x039A, //GREEK CAPITAL LETTER KAPPA - 0xA34E: 0x039B, //GREEK CAPITAL LETTER LAMDA - 0xA34F: 0x039C, //GREEK CAPITAL LETTER MU - 0xA350: 0x039D, //GREEK CAPITAL LETTER NU - 0xA351: 0x039E, //GREEK CAPITAL LETTER XI - 0xA352: 0x039F, //GREEK CAPITAL LETTER OMICRON - 0xA353: 0x03A0, //GREEK CAPITAL LETTER PI - 0xA354: 0x03A1, //GREEK CAPITAL LETTER RHO - 0xA355: 0x03A3, //GREEK CAPITAL LETTER SIGMA - 0xA356: 0x03A4, //GREEK CAPITAL LETTER TAU - 0xA357: 0x03A5, //GREEK CAPITAL LETTER UPSILON - 0xA358: 0x03A6, //GREEK CAPITAL LETTER PHI - 0xA359: 0x03A7, //GREEK CAPITAL LETTER CHI - 0xA35A: 0x03A8, //GREEK CAPITAL LETTER PSI - 0xA35B: 0x03A9, //GREEK CAPITAL LETTER OMEGA - 0xA35C: 0x03B1, //GREEK SMALL LETTER ALPHA - 0xA35D: 0x03B2, //GREEK SMALL LETTER BETA - 0xA35E: 0x03B3, //GREEK SMALL LETTER GAMMA - 0xA35F: 0x03B4, //GREEK SMALL LETTER DELTA - 0xA360: 0x03B5, //GREEK SMALL LETTER EPSILON - 0xA361: 0x03B6, //GREEK SMALL LETTER ZETA - 0xA362: 0x03B7, //GREEK SMALL LETTER ETA - 0xA363: 0x03B8, //GREEK SMALL LETTER THETA - 0xA364: 0x03B9, //GREEK SMALL LETTER IOTA - 0xA365: 0x03BA, //GREEK SMALL LETTER KAPPA - 0xA366: 0x03BB, //GREEK SMALL LETTER LAMDA - 0xA367: 0x03BC, //GREEK SMALL LETTER MU - 0xA368: 0x03BD, //GREEK SMALL LETTER NU - 0xA369: 0x03BE, //GREEK SMALL LETTER XI - 0xA36A: 0x03BF, //GREEK SMALL LETTER OMICRON - 0xA36B: 0x03C0, //GREEK SMALL LETTER PI - 0xA36C: 0x03C1, //GREEK SMALL LETTER RHO - 0xA36D: 0x03C3, //GREEK SMALL LETTER SIGMA - 0xA36E: 0x03C4, //GREEK SMALL LETTER TAU - 0xA36F: 0x03C5, //GREEK SMALL LETTER UPSILON - 0xA370: 0x03C6, //GREEK SMALL LETTER PHI - 0xA371: 0x03C7, //GREEK SMALL LETTER CHI - 0xA372: 0x03C8, //GREEK SMALL LETTER PSI - 0xA373: 0x03C9, //GREEK SMALL LETTER OMEGA - 0xA374: 0x3105, //BOPOMOFO LETTER B - 0xA375: 0x3106, //BOPOMOFO LETTER P - 0xA376: 0x3107, //BOPOMOFO LETTER M - 0xA377: 0x3108, //BOPOMOFO LETTER F - 0xA378: 0x3109, //BOPOMOFO LETTER D - 0xA379: 0x310A, //BOPOMOFO LETTER T - 0xA37A: 0x310B, //BOPOMOFO LETTER N - 0xA37B: 0x310C, //BOPOMOFO LETTER L - 0xA37C: 0x310D, //BOPOMOFO LETTER G - 0xA37D: 0x310E, //BOPOMOFO LETTER K - 0xA37E: 0x310F, //BOPOMOFO LETTER H - 0xA3A1: 0x3110, //BOPOMOFO LETTER J - 0xA3A2: 0x3111, //BOPOMOFO LETTER Q - 0xA3A3: 0x3112, //BOPOMOFO LETTER X - 0xA3A4: 0x3113, //BOPOMOFO LETTER ZH - 0xA3A5: 0x3114, //BOPOMOFO LETTER CH - 0xA3A6: 0x3115, //BOPOMOFO LETTER SH - 0xA3A7: 0x3116, //BOPOMOFO LETTER R - 0xA3A8: 0x3117, //BOPOMOFO LETTER Z - 0xA3A9: 0x3118, //BOPOMOFO LETTER C - 0xA3AA: 0x3119, //BOPOMOFO LETTER S - 0xA3AB: 0x311A, //BOPOMOFO LETTER A - 0xA3AC: 0x311B, //BOPOMOFO LETTER O - 0xA3AD: 0x311C, //BOPOMOFO LETTER E - 0xA3AE: 0x311D, //BOPOMOFO LETTER EH - 0xA3AF: 0x311E, //BOPOMOFO LETTER AI - 0xA3B0: 0x311F, //BOPOMOFO LETTER EI - 0xA3B1: 0x3120, //BOPOMOFO LETTER AU - 0xA3B2: 0x3121, //BOPOMOFO LETTER OU - 0xA3B3: 0x3122, //BOPOMOFO LETTER AN - 0xA3B4: 0x3123, //BOPOMOFO LETTER EN - 0xA3B5: 0x3124, //BOPOMOFO LETTER ANG - 0xA3B6: 0x3125, //BOPOMOFO LETTER ENG - 0xA3B7: 0x3126, //BOPOMOFO LETTER ER - 0xA3B8: 0x3127, //BOPOMOFO LETTER I - 0xA3B9: 0x3128, //BOPOMOFO LETTER U - 0xA3BA: 0x3129, //BOPOMOFO LETTER IU - 0xA3BB: 0x02D9, //DOT ABOVE - 0xA3BC: 0x02C9, //MODIFIER LETTER MACRON - 0xA3BD: 0x02CA, //MODIFIER LETTER ACUTE ACCENT - 0xA3BE: 0x02C7, //CARON - 0xA3BF: 0x02CB, //MODIFIER LETTER GRAVE ACCENT - 0xA3E1: 0x20AC, //EURO SIGN - 0xA440: 0x4E00, //CJK UNIFIED IDEOGRAPH - 0xA441: 0x4E59, //CJK UNIFIED IDEOGRAPH - 0xA442: 0x4E01, //CJK UNIFIED IDEOGRAPH - 0xA443: 0x4E03, //CJK UNIFIED IDEOGRAPH - 0xA444: 0x4E43, //CJK UNIFIED IDEOGRAPH - 0xA445: 0x4E5D, //CJK UNIFIED IDEOGRAPH - 0xA446: 0x4E86, //CJK UNIFIED IDEOGRAPH - 0xA447: 0x4E8C, //CJK UNIFIED IDEOGRAPH - 0xA448: 0x4EBA, //CJK UNIFIED IDEOGRAPH - 0xA449: 0x513F, //CJK UNIFIED IDEOGRAPH - 0xA44A: 0x5165, //CJK UNIFIED IDEOGRAPH - 0xA44B: 0x516B, //CJK UNIFIED IDEOGRAPH - 0xA44C: 0x51E0, //CJK UNIFIED IDEOGRAPH - 0xA44D: 0x5200, //CJK UNIFIED IDEOGRAPH - 0xA44E: 0x5201, //CJK UNIFIED IDEOGRAPH - 0xA44F: 0x529B, //CJK UNIFIED IDEOGRAPH - 0xA450: 0x5315, //CJK UNIFIED IDEOGRAPH - 0xA451: 0x5341, //CJK UNIFIED IDEOGRAPH - 0xA452: 0x535C, //CJK UNIFIED IDEOGRAPH - 0xA453: 0x53C8, //CJK UNIFIED IDEOGRAPH - 0xA454: 0x4E09, //CJK UNIFIED IDEOGRAPH - 0xA455: 0x4E0B, //CJK UNIFIED IDEOGRAPH - 0xA456: 0x4E08, //CJK UNIFIED IDEOGRAPH - 0xA457: 0x4E0A, //CJK UNIFIED IDEOGRAPH - 0xA458: 0x4E2B, //CJK UNIFIED IDEOGRAPH - 0xA459: 0x4E38, //CJK UNIFIED IDEOGRAPH - 0xA45A: 0x51E1, //CJK UNIFIED IDEOGRAPH - 0xA45B: 0x4E45, //CJK UNIFIED IDEOGRAPH - 0xA45C: 0x4E48, //CJK UNIFIED IDEOGRAPH - 0xA45D: 0x4E5F, //CJK UNIFIED IDEOGRAPH - 0xA45E: 0x4E5E, //CJK UNIFIED IDEOGRAPH - 0xA45F: 0x4E8E, //CJK UNIFIED IDEOGRAPH - 0xA460: 0x4EA1, //CJK UNIFIED IDEOGRAPH - 0xA461: 0x5140, //CJK UNIFIED IDEOGRAPH - 0xA462: 0x5203, //CJK UNIFIED IDEOGRAPH - 0xA463: 0x52FA, //CJK UNIFIED IDEOGRAPH - 0xA464: 0x5343, //CJK UNIFIED IDEOGRAPH - 0xA465: 0x53C9, //CJK UNIFIED IDEOGRAPH - 0xA466: 0x53E3, //CJK UNIFIED IDEOGRAPH - 0xA467: 0x571F, //CJK UNIFIED IDEOGRAPH - 0xA468: 0x58EB, //CJK UNIFIED IDEOGRAPH - 0xA469: 0x5915, //CJK UNIFIED IDEOGRAPH - 0xA46A: 0x5927, //CJK UNIFIED IDEOGRAPH - 0xA46B: 0x5973, //CJK UNIFIED IDEOGRAPH - 0xA46C: 0x5B50, //CJK UNIFIED IDEOGRAPH - 0xA46D: 0x5B51, //CJK UNIFIED IDEOGRAPH - 0xA46E: 0x5B53, //CJK UNIFIED IDEOGRAPH - 0xA46F: 0x5BF8, //CJK UNIFIED IDEOGRAPH - 0xA470: 0x5C0F, //CJK UNIFIED IDEOGRAPH - 0xA471: 0x5C22, //CJK UNIFIED IDEOGRAPH - 0xA472: 0x5C38, //CJK UNIFIED IDEOGRAPH - 0xA473: 0x5C71, //CJK UNIFIED IDEOGRAPH - 0xA474: 0x5DDD, //CJK UNIFIED IDEOGRAPH - 0xA475: 0x5DE5, //CJK UNIFIED IDEOGRAPH - 0xA476: 0x5DF1, //CJK UNIFIED IDEOGRAPH - 0xA477: 0x5DF2, //CJK UNIFIED IDEOGRAPH - 0xA478: 0x5DF3, //CJK UNIFIED IDEOGRAPH - 0xA479: 0x5DFE, //CJK UNIFIED IDEOGRAPH - 0xA47A: 0x5E72, //CJK UNIFIED IDEOGRAPH - 0xA47B: 0x5EFE, //CJK UNIFIED IDEOGRAPH - 0xA47C: 0x5F0B, //CJK UNIFIED IDEOGRAPH - 0xA47D: 0x5F13, //CJK UNIFIED IDEOGRAPH - 0xA47E: 0x624D, //CJK UNIFIED IDEOGRAPH - 0xA4A1: 0x4E11, //CJK UNIFIED IDEOGRAPH - 0xA4A2: 0x4E10, //CJK UNIFIED IDEOGRAPH - 0xA4A3: 0x4E0D, //CJK UNIFIED IDEOGRAPH - 0xA4A4: 0x4E2D, //CJK UNIFIED IDEOGRAPH - 0xA4A5: 0x4E30, //CJK UNIFIED IDEOGRAPH - 0xA4A6: 0x4E39, //CJK UNIFIED IDEOGRAPH - 0xA4A7: 0x4E4B, //CJK UNIFIED IDEOGRAPH - 0xA4A8: 0x5C39, //CJK UNIFIED IDEOGRAPH - 0xA4A9: 0x4E88, //CJK UNIFIED IDEOGRAPH - 0xA4AA: 0x4E91, //CJK UNIFIED IDEOGRAPH - 0xA4AB: 0x4E95, //CJK UNIFIED IDEOGRAPH - 0xA4AC: 0x4E92, //CJK UNIFIED IDEOGRAPH - 0xA4AD: 0x4E94, //CJK UNIFIED IDEOGRAPH - 0xA4AE: 0x4EA2, //CJK UNIFIED IDEOGRAPH - 0xA4AF: 0x4EC1, //CJK UNIFIED IDEOGRAPH - 0xA4B0: 0x4EC0, //CJK UNIFIED IDEOGRAPH - 0xA4B1: 0x4EC3, //CJK UNIFIED IDEOGRAPH - 0xA4B2: 0x4EC6, //CJK UNIFIED IDEOGRAPH - 0xA4B3: 0x4EC7, //CJK UNIFIED IDEOGRAPH - 0xA4B4: 0x4ECD, //CJK UNIFIED IDEOGRAPH - 0xA4B5: 0x4ECA, //CJK UNIFIED IDEOGRAPH - 0xA4B6: 0x4ECB, //CJK UNIFIED IDEOGRAPH - 0xA4B7: 0x4EC4, //CJK UNIFIED IDEOGRAPH - 0xA4B8: 0x5143, //CJK UNIFIED IDEOGRAPH - 0xA4B9: 0x5141, //CJK UNIFIED IDEOGRAPH - 0xA4BA: 0x5167, //CJK UNIFIED IDEOGRAPH - 0xA4BB: 0x516D, //CJK UNIFIED IDEOGRAPH - 0xA4BC: 0x516E, //CJK UNIFIED IDEOGRAPH - 0xA4BD: 0x516C, //CJK UNIFIED IDEOGRAPH - 0xA4BE: 0x5197, //CJK UNIFIED IDEOGRAPH - 0xA4BF: 0x51F6, //CJK UNIFIED IDEOGRAPH - 0xA4C0: 0x5206, //CJK UNIFIED IDEOGRAPH - 0xA4C1: 0x5207, //CJK UNIFIED IDEOGRAPH - 0xA4C2: 0x5208, //CJK UNIFIED IDEOGRAPH - 0xA4C3: 0x52FB, //CJK UNIFIED IDEOGRAPH - 0xA4C4: 0x52FE, //CJK UNIFIED IDEOGRAPH - 0xA4C5: 0x52FF, //CJK UNIFIED IDEOGRAPH - 0xA4C6: 0x5316, //CJK UNIFIED IDEOGRAPH - 0xA4C7: 0x5339, //CJK UNIFIED IDEOGRAPH - 0xA4C8: 0x5348, //CJK UNIFIED IDEOGRAPH - 0xA4C9: 0x5347, //CJK UNIFIED IDEOGRAPH - 0xA4CA: 0x5345, //CJK UNIFIED IDEOGRAPH - 0xA4CB: 0x535E, //CJK UNIFIED IDEOGRAPH - 0xA4CC: 0x5384, //CJK UNIFIED IDEOGRAPH - 0xA4CD: 0x53CB, //CJK UNIFIED IDEOGRAPH - 0xA4CE: 0x53CA, //CJK UNIFIED IDEOGRAPH - 0xA4CF: 0x53CD, //CJK UNIFIED IDEOGRAPH - 0xA4D0: 0x58EC, //CJK UNIFIED IDEOGRAPH - 0xA4D1: 0x5929, //CJK UNIFIED IDEOGRAPH - 0xA4D2: 0x592B, //CJK UNIFIED IDEOGRAPH - 0xA4D3: 0x592A, //CJK UNIFIED IDEOGRAPH - 0xA4D4: 0x592D, //CJK UNIFIED IDEOGRAPH - 0xA4D5: 0x5B54, //CJK UNIFIED IDEOGRAPH - 0xA4D6: 0x5C11, //CJK UNIFIED IDEOGRAPH - 0xA4D7: 0x5C24, //CJK UNIFIED IDEOGRAPH - 0xA4D8: 0x5C3A, //CJK UNIFIED IDEOGRAPH - 0xA4D9: 0x5C6F, //CJK UNIFIED IDEOGRAPH - 0xA4DA: 0x5DF4, //CJK UNIFIED IDEOGRAPH - 0xA4DB: 0x5E7B, //CJK UNIFIED IDEOGRAPH - 0xA4DC: 0x5EFF, //CJK UNIFIED IDEOGRAPH - 0xA4DD: 0x5F14, //CJK UNIFIED IDEOGRAPH - 0xA4DE: 0x5F15, //CJK UNIFIED IDEOGRAPH - 0xA4DF: 0x5FC3, //CJK UNIFIED IDEOGRAPH - 0xA4E0: 0x6208, //CJK UNIFIED IDEOGRAPH - 0xA4E1: 0x6236, //CJK UNIFIED IDEOGRAPH - 0xA4E2: 0x624B, //CJK UNIFIED IDEOGRAPH - 0xA4E3: 0x624E, //CJK UNIFIED IDEOGRAPH - 0xA4E4: 0x652F, //CJK UNIFIED IDEOGRAPH - 0xA4E5: 0x6587, //CJK UNIFIED IDEOGRAPH - 0xA4E6: 0x6597, //CJK UNIFIED IDEOGRAPH - 0xA4E7: 0x65A4, //CJK UNIFIED IDEOGRAPH - 0xA4E8: 0x65B9, //CJK UNIFIED IDEOGRAPH - 0xA4E9: 0x65E5, //CJK UNIFIED IDEOGRAPH - 0xA4EA: 0x66F0, //CJK UNIFIED IDEOGRAPH - 0xA4EB: 0x6708, //CJK UNIFIED IDEOGRAPH - 0xA4EC: 0x6728, //CJK UNIFIED IDEOGRAPH - 0xA4ED: 0x6B20, //CJK UNIFIED IDEOGRAPH - 0xA4EE: 0x6B62, //CJK UNIFIED IDEOGRAPH - 0xA4EF: 0x6B79, //CJK UNIFIED IDEOGRAPH - 0xA4F0: 0x6BCB, //CJK UNIFIED IDEOGRAPH - 0xA4F1: 0x6BD4, //CJK UNIFIED IDEOGRAPH - 0xA4F2: 0x6BDB, //CJK UNIFIED IDEOGRAPH - 0xA4F3: 0x6C0F, //CJK UNIFIED IDEOGRAPH - 0xA4F4: 0x6C34, //CJK UNIFIED IDEOGRAPH - 0xA4F5: 0x706B, //CJK UNIFIED IDEOGRAPH - 0xA4F6: 0x722A, //CJK UNIFIED IDEOGRAPH - 0xA4F7: 0x7236, //CJK UNIFIED IDEOGRAPH - 0xA4F8: 0x723B, //CJK UNIFIED IDEOGRAPH - 0xA4F9: 0x7247, //CJK UNIFIED IDEOGRAPH - 0xA4FA: 0x7259, //CJK UNIFIED IDEOGRAPH - 0xA4FB: 0x725B, //CJK UNIFIED IDEOGRAPH - 0xA4FC: 0x72AC, //CJK UNIFIED IDEOGRAPH - 0xA4FD: 0x738B, //CJK UNIFIED IDEOGRAPH - 0xA4FE: 0x4E19, //CJK UNIFIED IDEOGRAPH - 0xA540: 0x4E16, //CJK UNIFIED IDEOGRAPH - 0xA541: 0x4E15, //CJK UNIFIED IDEOGRAPH - 0xA542: 0x4E14, //CJK UNIFIED IDEOGRAPH - 0xA543: 0x4E18, //CJK UNIFIED IDEOGRAPH - 0xA544: 0x4E3B, //CJK UNIFIED IDEOGRAPH - 0xA545: 0x4E4D, //CJK UNIFIED IDEOGRAPH - 0xA546: 0x4E4F, //CJK UNIFIED IDEOGRAPH - 0xA547: 0x4E4E, //CJK UNIFIED IDEOGRAPH - 0xA548: 0x4EE5, //CJK UNIFIED IDEOGRAPH - 0xA549: 0x4ED8, //CJK UNIFIED IDEOGRAPH - 0xA54A: 0x4ED4, //CJK UNIFIED IDEOGRAPH - 0xA54B: 0x4ED5, //CJK UNIFIED IDEOGRAPH - 0xA54C: 0x4ED6, //CJK UNIFIED IDEOGRAPH - 0xA54D: 0x4ED7, //CJK UNIFIED IDEOGRAPH - 0xA54E: 0x4EE3, //CJK UNIFIED IDEOGRAPH - 0xA54F: 0x4EE4, //CJK UNIFIED IDEOGRAPH - 0xA550: 0x4ED9, //CJK UNIFIED IDEOGRAPH - 0xA551: 0x4EDE, //CJK UNIFIED IDEOGRAPH - 0xA552: 0x5145, //CJK UNIFIED IDEOGRAPH - 0xA553: 0x5144, //CJK UNIFIED IDEOGRAPH - 0xA554: 0x5189, //CJK UNIFIED IDEOGRAPH - 0xA555: 0x518A, //CJK UNIFIED IDEOGRAPH - 0xA556: 0x51AC, //CJK UNIFIED IDEOGRAPH - 0xA557: 0x51F9, //CJK UNIFIED IDEOGRAPH - 0xA558: 0x51FA, //CJK UNIFIED IDEOGRAPH - 0xA559: 0x51F8, //CJK UNIFIED IDEOGRAPH - 0xA55A: 0x520A, //CJK UNIFIED IDEOGRAPH - 0xA55B: 0x52A0, //CJK UNIFIED IDEOGRAPH - 0xA55C: 0x529F, //CJK UNIFIED IDEOGRAPH - 0xA55D: 0x5305, //CJK UNIFIED IDEOGRAPH - 0xA55E: 0x5306, //CJK UNIFIED IDEOGRAPH - 0xA55F: 0x5317, //CJK UNIFIED IDEOGRAPH - 0xA560: 0x531D, //CJK UNIFIED IDEOGRAPH - 0xA561: 0x4EDF, //CJK UNIFIED IDEOGRAPH - 0xA562: 0x534A, //CJK UNIFIED IDEOGRAPH - 0xA563: 0x5349, //CJK UNIFIED IDEOGRAPH - 0xA564: 0x5361, //CJK UNIFIED IDEOGRAPH - 0xA565: 0x5360, //CJK UNIFIED IDEOGRAPH - 0xA566: 0x536F, //CJK UNIFIED IDEOGRAPH - 0xA567: 0x536E, //CJK UNIFIED IDEOGRAPH - 0xA568: 0x53BB, //CJK UNIFIED IDEOGRAPH - 0xA569: 0x53EF, //CJK UNIFIED IDEOGRAPH - 0xA56A: 0x53E4, //CJK UNIFIED IDEOGRAPH - 0xA56B: 0x53F3, //CJK UNIFIED IDEOGRAPH - 0xA56C: 0x53EC, //CJK UNIFIED IDEOGRAPH - 0xA56D: 0x53EE, //CJK UNIFIED IDEOGRAPH - 0xA56E: 0x53E9, //CJK UNIFIED IDEOGRAPH - 0xA56F: 0x53E8, //CJK UNIFIED IDEOGRAPH - 0xA570: 0x53FC, //CJK UNIFIED IDEOGRAPH - 0xA571: 0x53F8, //CJK UNIFIED IDEOGRAPH - 0xA572: 0x53F5, //CJK UNIFIED IDEOGRAPH - 0xA573: 0x53EB, //CJK UNIFIED IDEOGRAPH - 0xA574: 0x53E6, //CJK UNIFIED IDEOGRAPH - 0xA575: 0x53EA, //CJK UNIFIED IDEOGRAPH - 0xA576: 0x53F2, //CJK UNIFIED IDEOGRAPH - 0xA577: 0x53F1, //CJK UNIFIED IDEOGRAPH - 0xA578: 0x53F0, //CJK UNIFIED IDEOGRAPH - 0xA579: 0x53E5, //CJK UNIFIED IDEOGRAPH - 0xA57A: 0x53ED, //CJK UNIFIED IDEOGRAPH - 0xA57B: 0x53FB, //CJK UNIFIED IDEOGRAPH - 0xA57C: 0x56DB, //CJK UNIFIED IDEOGRAPH - 0xA57D: 0x56DA, //CJK UNIFIED IDEOGRAPH - 0xA57E: 0x5916, //CJK UNIFIED IDEOGRAPH - 0xA5A1: 0x592E, //CJK UNIFIED IDEOGRAPH - 0xA5A2: 0x5931, //CJK UNIFIED IDEOGRAPH - 0xA5A3: 0x5974, //CJK UNIFIED IDEOGRAPH - 0xA5A4: 0x5976, //CJK UNIFIED IDEOGRAPH - 0xA5A5: 0x5B55, //CJK UNIFIED IDEOGRAPH - 0xA5A6: 0x5B83, //CJK UNIFIED IDEOGRAPH - 0xA5A7: 0x5C3C, //CJK UNIFIED IDEOGRAPH - 0xA5A8: 0x5DE8, //CJK UNIFIED IDEOGRAPH - 0xA5A9: 0x5DE7, //CJK UNIFIED IDEOGRAPH - 0xA5AA: 0x5DE6, //CJK UNIFIED IDEOGRAPH - 0xA5AB: 0x5E02, //CJK UNIFIED IDEOGRAPH - 0xA5AC: 0x5E03, //CJK UNIFIED IDEOGRAPH - 0xA5AD: 0x5E73, //CJK UNIFIED IDEOGRAPH - 0xA5AE: 0x5E7C, //CJK UNIFIED IDEOGRAPH - 0xA5AF: 0x5F01, //CJK UNIFIED IDEOGRAPH - 0xA5B0: 0x5F18, //CJK UNIFIED IDEOGRAPH - 0xA5B1: 0x5F17, //CJK UNIFIED IDEOGRAPH - 0xA5B2: 0x5FC5, //CJK UNIFIED IDEOGRAPH - 0xA5B3: 0x620A, //CJK UNIFIED IDEOGRAPH - 0xA5B4: 0x6253, //CJK UNIFIED IDEOGRAPH - 0xA5B5: 0x6254, //CJK UNIFIED IDEOGRAPH - 0xA5B6: 0x6252, //CJK UNIFIED IDEOGRAPH - 0xA5B7: 0x6251, //CJK UNIFIED IDEOGRAPH - 0xA5B8: 0x65A5, //CJK UNIFIED IDEOGRAPH - 0xA5B9: 0x65E6, //CJK UNIFIED IDEOGRAPH - 0xA5BA: 0x672E, //CJK UNIFIED IDEOGRAPH - 0xA5BB: 0x672C, //CJK UNIFIED IDEOGRAPH - 0xA5BC: 0x672A, //CJK UNIFIED IDEOGRAPH - 0xA5BD: 0x672B, //CJK UNIFIED IDEOGRAPH - 0xA5BE: 0x672D, //CJK UNIFIED IDEOGRAPH - 0xA5BF: 0x6B63, //CJK UNIFIED IDEOGRAPH - 0xA5C0: 0x6BCD, //CJK UNIFIED IDEOGRAPH - 0xA5C1: 0x6C11, //CJK UNIFIED IDEOGRAPH - 0xA5C2: 0x6C10, //CJK UNIFIED IDEOGRAPH - 0xA5C3: 0x6C38, //CJK UNIFIED IDEOGRAPH - 0xA5C4: 0x6C41, //CJK UNIFIED IDEOGRAPH - 0xA5C5: 0x6C40, //CJK UNIFIED IDEOGRAPH - 0xA5C6: 0x6C3E, //CJK UNIFIED IDEOGRAPH - 0xA5C7: 0x72AF, //CJK UNIFIED IDEOGRAPH - 0xA5C8: 0x7384, //CJK UNIFIED IDEOGRAPH - 0xA5C9: 0x7389, //CJK UNIFIED IDEOGRAPH - 0xA5CA: 0x74DC, //CJK UNIFIED IDEOGRAPH - 0xA5CB: 0x74E6, //CJK UNIFIED IDEOGRAPH - 0xA5CC: 0x7518, //CJK UNIFIED IDEOGRAPH - 0xA5CD: 0x751F, //CJK UNIFIED IDEOGRAPH - 0xA5CE: 0x7528, //CJK UNIFIED IDEOGRAPH - 0xA5CF: 0x7529, //CJK UNIFIED IDEOGRAPH - 0xA5D0: 0x7530, //CJK UNIFIED IDEOGRAPH - 0xA5D1: 0x7531, //CJK UNIFIED IDEOGRAPH - 0xA5D2: 0x7532, //CJK UNIFIED IDEOGRAPH - 0xA5D3: 0x7533, //CJK UNIFIED IDEOGRAPH - 0xA5D4: 0x758B, //CJK UNIFIED IDEOGRAPH - 0xA5D5: 0x767D, //CJK UNIFIED IDEOGRAPH - 0xA5D6: 0x76AE, //CJK UNIFIED IDEOGRAPH - 0xA5D7: 0x76BF, //CJK UNIFIED IDEOGRAPH - 0xA5D8: 0x76EE, //CJK UNIFIED IDEOGRAPH - 0xA5D9: 0x77DB, //CJK UNIFIED IDEOGRAPH - 0xA5DA: 0x77E2, //CJK UNIFIED IDEOGRAPH - 0xA5DB: 0x77F3, //CJK UNIFIED IDEOGRAPH - 0xA5DC: 0x793A, //CJK UNIFIED IDEOGRAPH - 0xA5DD: 0x79BE, //CJK UNIFIED IDEOGRAPH - 0xA5DE: 0x7A74, //CJK UNIFIED IDEOGRAPH - 0xA5DF: 0x7ACB, //CJK UNIFIED IDEOGRAPH - 0xA5E0: 0x4E1E, //CJK UNIFIED IDEOGRAPH - 0xA5E1: 0x4E1F, //CJK UNIFIED IDEOGRAPH - 0xA5E2: 0x4E52, //CJK UNIFIED IDEOGRAPH - 0xA5E3: 0x4E53, //CJK UNIFIED IDEOGRAPH - 0xA5E4: 0x4E69, //CJK UNIFIED IDEOGRAPH - 0xA5E5: 0x4E99, //CJK UNIFIED IDEOGRAPH - 0xA5E6: 0x4EA4, //CJK UNIFIED IDEOGRAPH - 0xA5E7: 0x4EA6, //CJK UNIFIED IDEOGRAPH - 0xA5E8: 0x4EA5, //CJK UNIFIED IDEOGRAPH - 0xA5E9: 0x4EFF, //CJK UNIFIED IDEOGRAPH - 0xA5EA: 0x4F09, //CJK UNIFIED IDEOGRAPH - 0xA5EB: 0x4F19, //CJK UNIFIED IDEOGRAPH - 0xA5EC: 0x4F0A, //CJK UNIFIED IDEOGRAPH - 0xA5ED: 0x4F15, //CJK UNIFIED IDEOGRAPH - 0xA5EE: 0x4F0D, //CJK UNIFIED IDEOGRAPH - 0xA5EF: 0x4F10, //CJK UNIFIED IDEOGRAPH - 0xA5F0: 0x4F11, //CJK UNIFIED IDEOGRAPH - 0xA5F1: 0x4F0F, //CJK UNIFIED IDEOGRAPH - 0xA5F2: 0x4EF2, //CJK UNIFIED IDEOGRAPH - 0xA5F3: 0x4EF6, //CJK UNIFIED IDEOGRAPH - 0xA5F4: 0x4EFB, //CJK UNIFIED IDEOGRAPH - 0xA5F5: 0x4EF0, //CJK UNIFIED IDEOGRAPH - 0xA5F6: 0x4EF3, //CJK UNIFIED IDEOGRAPH - 0xA5F7: 0x4EFD, //CJK UNIFIED IDEOGRAPH - 0xA5F8: 0x4F01, //CJK UNIFIED IDEOGRAPH - 0xA5F9: 0x4F0B, //CJK UNIFIED IDEOGRAPH - 0xA5FA: 0x5149, //CJK UNIFIED IDEOGRAPH - 0xA5FB: 0x5147, //CJK UNIFIED IDEOGRAPH - 0xA5FC: 0x5146, //CJK UNIFIED IDEOGRAPH - 0xA5FD: 0x5148, //CJK UNIFIED IDEOGRAPH - 0xA5FE: 0x5168, //CJK UNIFIED IDEOGRAPH - 0xA640: 0x5171, //CJK UNIFIED IDEOGRAPH - 0xA641: 0x518D, //CJK UNIFIED IDEOGRAPH - 0xA642: 0x51B0, //CJK UNIFIED IDEOGRAPH - 0xA643: 0x5217, //CJK UNIFIED IDEOGRAPH - 0xA644: 0x5211, //CJK UNIFIED IDEOGRAPH - 0xA645: 0x5212, //CJK UNIFIED IDEOGRAPH - 0xA646: 0x520E, //CJK UNIFIED IDEOGRAPH - 0xA647: 0x5216, //CJK UNIFIED IDEOGRAPH - 0xA648: 0x52A3, //CJK UNIFIED IDEOGRAPH - 0xA649: 0x5308, //CJK UNIFIED IDEOGRAPH - 0xA64A: 0x5321, //CJK UNIFIED IDEOGRAPH - 0xA64B: 0x5320, //CJK UNIFIED IDEOGRAPH - 0xA64C: 0x5370, //CJK UNIFIED IDEOGRAPH - 0xA64D: 0x5371, //CJK UNIFIED IDEOGRAPH - 0xA64E: 0x5409, //CJK UNIFIED IDEOGRAPH - 0xA64F: 0x540F, //CJK UNIFIED IDEOGRAPH - 0xA650: 0x540C, //CJK UNIFIED IDEOGRAPH - 0xA651: 0x540A, //CJK UNIFIED IDEOGRAPH - 0xA652: 0x5410, //CJK UNIFIED IDEOGRAPH - 0xA653: 0x5401, //CJK UNIFIED IDEOGRAPH - 0xA654: 0x540B, //CJK UNIFIED IDEOGRAPH - 0xA655: 0x5404, //CJK UNIFIED IDEOGRAPH - 0xA656: 0x5411, //CJK UNIFIED IDEOGRAPH - 0xA657: 0x540D, //CJK UNIFIED IDEOGRAPH - 0xA658: 0x5408, //CJK UNIFIED IDEOGRAPH - 0xA659: 0x5403, //CJK UNIFIED IDEOGRAPH - 0xA65A: 0x540E, //CJK UNIFIED IDEOGRAPH - 0xA65B: 0x5406, //CJK UNIFIED IDEOGRAPH - 0xA65C: 0x5412, //CJK UNIFIED IDEOGRAPH - 0xA65D: 0x56E0, //CJK UNIFIED IDEOGRAPH - 0xA65E: 0x56DE, //CJK UNIFIED IDEOGRAPH - 0xA65F: 0x56DD, //CJK UNIFIED IDEOGRAPH - 0xA660: 0x5733, //CJK UNIFIED IDEOGRAPH - 0xA661: 0x5730, //CJK UNIFIED IDEOGRAPH - 0xA662: 0x5728, //CJK UNIFIED IDEOGRAPH - 0xA663: 0x572D, //CJK UNIFIED IDEOGRAPH - 0xA664: 0x572C, //CJK UNIFIED IDEOGRAPH - 0xA665: 0x572F, //CJK UNIFIED IDEOGRAPH - 0xA666: 0x5729, //CJK UNIFIED IDEOGRAPH - 0xA667: 0x5919, //CJK UNIFIED IDEOGRAPH - 0xA668: 0x591A, //CJK UNIFIED IDEOGRAPH - 0xA669: 0x5937, //CJK UNIFIED IDEOGRAPH - 0xA66A: 0x5938, //CJK UNIFIED IDEOGRAPH - 0xA66B: 0x5984, //CJK UNIFIED IDEOGRAPH - 0xA66C: 0x5978, //CJK UNIFIED IDEOGRAPH - 0xA66D: 0x5983, //CJK UNIFIED IDEOGRAPH - 0xA66E: 0x597D, //CJK UNIFIED IDEOGRAPH - 0xA66F: 0x5979, //CJK UNIFIED IDEOGRAPH - 0xA670: 0x5982, //CJK UNIFIED IDEOGRAPH - 0xA671: 0x5981, //CJK UNIFIED IDEOGRAPH - 0xA672: 0x5B57, //CJK UNIFIED IDEOGRAPH - 0xA673: 0x5B58, //CJK UNIFIED IDEOGRAPH - 0xA674: 0x5B87, //CJK UNIFIED IDEOGRAPH - 0xA675: 0x5B88, //CJK UNIFIED IDEOGRAPH - 0xA676: 0x5B85, //CJK UNIFIED IDEOGRAPH - 0xA677: 0x5B89, //CJK UNIFIED IDEOGRAPH - 0xA678: 0x5BFA, //CJK UNIFIED IDEOGRAPH - 0xA679: 0x5C16, //CJK UNIFIED IDEOGRAPH - 0xA67A: 0x5C79, //CJK UNIFIED IDEOGRAPH - 0xA67B: 0x5DDE, //CJK UNIFIED IDEOGRAPH - 0xA67C: 0x5E06, //CJK UNIFIED IDEOGRAPH - 0xA67D: 0x5E76, //CJK UNIFIED IDEOGRAPH - 0xA67E: 0x5E74, //CJK UNIFIED IDEOGRAPH - 0xA6A1: 0x5F0F, //CJK UNIFIED IDEOGRAPH - 0xA6A2: 0x5F1B, //CJK UNIFIED IDEOGRAPH - 0xA6A3: 0x5FD9, //CJK UNIFIED IDEOGRAPH - 0xA6A4: 0x5FD6, //CJK UNIFIED IDEOGRAPH - 0xA6A5: 0x620E, //CJK UNIFIED IDEOGRAPH - 0xA6A6: 0x620C, //CJK UNIFIED IDEOGRAPH - 0xA6A7: 0x620D, //CJK UNIFIED IDEOGRAPH - 0xA6A8: 0x6210, //CJK UNIFIED IDEOGRAPH - 0xA6A9: 0x6263, //CJK UNIFIED IDEOGRAPH - 0xA6AA: 0x625B, //CJK UNIFIED IDEOGRAPH - 0xA6AB: 0x6258, //CJK UNIFIED IDEOGRAPH - 0xA6AC: 0x6536, //CJK UNIFIED IDEOGRAPH - 0xA6AD: 0x65E9, //CJK UNIFIED IDEOGRAPH - 0xA6AE: 0x65E8, //CJK UNIFIED IDEOGRAPH - 0xA6AF: 0x65EC, //CJK UNIFIED IDEOGRAPH - 0xA6B0: 0x65ED, //CJK UNIFIED IDEOGRAPH - 0xA6B1: 0x66F2, //CJK UNIFIED IDEOGRAPH - 0xA6B2: 0x66F3, //CJK UNIFIED IDEOGRAPH - 0xA6B3: 0x6709, //CJK UNIFIED IDEOGRAPH - 0xA6B4: 0x673D, //CJK UNIFIED IDEOGRAPH - 0xA6B5: 0x6734, //CJK UNIFIED IDEOGRAPH - 0xA6B6: 0x6731, //CJK UNIFIED IDEOGRAPH - 0xA6B7: 0x6735, //CJK UNIFIED IDEOGRAPH - 0xA6B8: 0x6B21, //CJK UNIFIED IDEOGRAPH - 0xA6B9: 0x6B64, //CJK UNIFIED IDEOGRAPH - 0xA6BA: 0x6B7B, //CJK UNIFIED IDEOGRAPH - 0xA6BB: 0x6C16, //CJK UNIFIED IDEOGRAPH - 0xA6BC: 0x6C5D, //CJK UNIFIED IDEOGRAPH - 0xA6BD: 0x6C57, //CJK UNIFIED IDEOGRAPH - 0xA6BE: 0x6C59, //CJK UNIFIED IDEOGRAPH - 0xA6BF: 0x6C5F, //CJK UNIFIED IDEOGRAPH - 0xA6C0: 0x6C60, //CJK UNIFIED IDEOGRAPH - 0xA6C1: 0x6C50, //CJK UNIFIED IDEOGRAPH - 0xA6C2: 0x6C55, //CJK UNIFIED IDEOGRAPH - 0xA6C3: 0x6C61, //CJK UNIFIED IDEOGRAPH - 0xA6C4: 0x6C5B, //CJK UNIFIED IDEOGRAPH - 0xA6C5: 0x6C4D, //CJK UNIFIED IDEOGRAPH - 0xA6C6: 0x6C4E, //CJK UNIFIED IDEOGRAPH - 0xA6C7: 0x7070, //CJK UNIFIED IDEOGRAPH - 0xA6C8: 0x725F, //CJK UNIFIED IDEOGRAPH - 0xA6C9: 0x725D, //CJK UNIFIED IDEOGRAPH - 0xA6CA: 0x767E, //CJK UNIFIED IDEOGRAPH - 0xA6CB: 0x7AF9, //CJK UNIFIED IDEOGRAPH - 0xA6CC: 0x7C73, //CJK UNIFIED IDEOGRAPH - 0xA6CD: 0x7CF8, //CJK UNIFIED IDEOGRAPH - 0xA6CE: 0x7F36, //CJK UNIFIED IDEOGRAPH - 0xA6CF: 0x7F8A, //CJK UNIFIED IDEOGRAPH - 0xA6D0: 0x7FBD, //CJK UNIFIED IDEOGRAPH - 0xA6D1: 0x8001, //CJK UNIFIED IDEOGRAPH - 0xA6D2: 0x8003, //CJK UNIFIED IDEOGRAPH - 0xA6D3: 0x800C, //CJK UNIFIED IDEOGRAPH - 0xA6D4: 0x8012, //CJK UNIFIED IDEOGRAPH - 0xA6D5: 0x8033, //CJK UNIFIED IDEOGRAPH - 0xA6D6: 0x807F, //CJK UNIFIED IDEOGRAPH - 0xA6D7: 0x8089, //CJK UNIFIED IDEOGRAPH - 0xA6D8: 0x808B, //CJK UNIFIED IDEOGRAPH - 0xA6D9: 0x808C, //CJK UNIFIED IDEOGRAPH - 0xA6DA: 0x81E3, //CJK UNIFIED IDEOGRAPH - 0xA6DB: 0x81EA, //CJK UNIFIED IDEOGRAPH - 0xA6DC: 0x81F3, //CJK UNIFIED IDEOGRAPH - 0xA6DD: 0x81FC, //CJK UNIFIED IDEOGRAPH - 0xA6DE: 0x820C, //CJK UNIFIED IDEOGRAPH - 0xA6DF: 0x821B, //CJK UNIFIED IDEOGRAPH - 0xA6E0: 0x821F, //CJK UNIFIED IDEOGRAPH - 0xA6E1: 0x826E, //CJK UNIFIED IDEOGRAPH - 0xA6E2: 0x8272, //CJK UNIFIED IDEOGRAPH - 0xA6E3: 0x827E, //CJK UNIFIED IDEOGRAPH - 0xA6E4: 0x866B, //CJK UNIFIED IDEOGRAPH - 0xA6E5: 0x8840, //CJK UNIFIED IDEOGRAPH - 0xA6E6: 0x884C, //CJK UNIFIED IDEOGRAPH - 0xA6E7: 0x8863, //CJK UNIFIED IDEOGRAPH - 0xA6E8: 0x897F, //CJK UNIFIED IDEOGRAPH - 0xA6E9: 0x9621, //CJK UNIFIED IDEOGRAPH - 0xA6EA: 0x4E32, //CJK UNIFIED IDEOGRAPH - 0xA6EB: 0x4EA8, //CJK UNIFIED IDEOGRAPH - 0xA6EC: 0x4F4D, //CJK UNIFIED IDEOGRAPH - 0xA6ED: 0x4F4F, //CJK UNIFIED IDEOGRAPH - 0xA6EE: 0x4F47, //CJK UNIFIED IDEOGRAPH - 0xA6EF: 0x4F57, //CJK UNIFIED IDEOGRAPH - 0xA6F0: 0x4F5E, //CJK UNIFIED IDEOGRAPH - 0xA6F1: 0x4F34, //CJK UNIFIED IDEOGRAPH - 0xA6F2: 0x4F5B, //CJK UNIFIED IDEOGRAPH - 0xA6F3: 0x4F55, //CJK UNIFIED IDEOGRAPH - 0xA6F4: 0x4F30, //CJK UNIFIED IDEOGRAPH - 0xA6F5: 0x4F50, //CJK UNIFIED IDEOGRAPH - 0xA6F6: 0x4F51, //CJK UNIFIED IDEOGRAPH - 0xA6F7: 0x4F3D, //CJK UNIFIED IDEOGRAPH - 0xA6F8: 0x4F3A, //CJK UNIFIED IDEOGRAPH - 0xA6F9: 0x4F38, //CJK UNIFIED IDEOGRAPH - 0xA6FA: 0x4F43, //CJK UNIFIED IDEOGRAPH - 0xA6FB: 0x4F54, //CJK UNIFIED IDEOGRAPH - 0xA6FC: 0x4F3C, //CJK UNIFIED IDEOGRAPH - 0xA6FD: 0x4F46, //CJK UNIFIED IDEOGRAPH - 0xA6FE: 0x4F63, //CJK UNIFIED IDEOGRAPH - 0xA740: 0x4F5C, //CJK UNIFIED IDEOGRAPH - 0xA741: 0x4F60, //CJK UNIFIED IDEOGRAPH - 0xA742: 0x4F2F, //CJK UNIFIED IDEOGRAPH - 0xA743: 0x4F4E, //CJK UNIFIED IDEOGRAPH - 0xA744: 0x4F36, //CJK UNIFIED IDEOGRAPH - 0xA745: 0x4F59, //CJK UNIFIED IDEOGRAPH - 0xA746: 0x4F5D, //CJK UNIFIED IDEOGRAPH - 0xA747: 0x4F48, //CJK UNIFIED IDEOGRAPH - 0xA748: 0x4F5A, //CJK UNIFIED IDEOGRAPH - 0xA749: 0x514C, //CJK UNIFIED IDEOGRAPH - 0xA74A: 0x514B, //CJK UNIFIED IDEOGRAPH - 0xA74B: 0x514D, //CJK UNIFIED IDEOGRAPH - 0xA74C: 0x5175, //CJK UNIFIED IDEOGRAPH - 0xA74D: 0x51B6, //CJK UNIFIED IDEOGRAPH - 0xA74E: 0x51B7, //CJK UNIFIED IDEOGRAPH - 0xA74F: 0x5225, //CJK UNIFIED IDEOGRAPH - 0xA750: 0x5224, //CJK UNIFIED IDEOGRAPH - 0xA751: 0x5229, //CJK UNIFIED IDEOGRAPH - 0xA752: 0x522A, //CJK UNIFIED IDEOGRAPH - 0xA753: 0x5228, //CJK UNIFIED IDEOGRAPH - 0xA754: 0x52AB, //CJK UNIFIED IDEOGRAPH - 0xA755: 0x52A9, //CJK UNIFIED IDEOGRAPH - 0xA756: 0x52AA, //CJK UNIFIED IDEOGRAPH - 0xA757: 0x52AC, //CJK UNIFIED IDEOGRAPH - 0xA758: 0x5323, //CJK UNIFIED IDEOGRAPH - 0xA759: 0x5373, //CJK UNIFIED IDEOGRAPH - 0xA75A: 0x5375, //CJK UNIFIED IDEOGRAPH - 0xA75B: 0x541D, //CJK UNIFIED IDEOGRAPH - 0xA75C: 0x542D, //CJK UNIFIED IDEOGRAPH - 0xA75D: 0x541E, //CJK UNIFIED IDEOGRAPH - 0xA75E: 0x543E, //CJK UNIFIED IDEOGRAPH - 0xA75F: 0x5426, //CJK UNIFIED IDEOGRAPH - 0xA760: 0x544E, //CJK UNIFIED IDEOGRAPH - 0xA761: 0x5427, //CJK UNIFIED IDEOGRAPH - 0xA762: 0x5446, //CJK UNIFIED IDEOGRAPH - 0xA763: 0x5443, //CJK UNIFIED IDEOGRAPH - 0xA764: 0x5433, //CJK UNIFIED IDEOGRAPH - 0xA765: 0x5448, //CJK UNIFIED IDEOGRAPH - 0xA766: 0x5442, //CJK UNIFIED IDEOGRAPH - 0xA767: 0x541B, //CJK UNIFIED IDEOGRAPH - 0xA768: 0x5429, //CJK UNIFIED IDEOGRAPH - 0xA769: 0x544A, //CJK UNIFIED IDEOGRAPH - 0xA76A: 0x5439, //CJK UNIFIED IDEOGRAPH - 0xA76B: 0x543B, //CJK UNIFIED IDEOGRAPH - 0xA76C: 0x5438, //CJK UNIFIED IDEOGRAPH - 0xA76D: 0x542E, //CJK UNIFIED IDEOGRAPH - 0xA76E: 0x5435, //CJK UNIFIED IDEOGRAPH - 0xA76F: 0x5436, //CJK UNIFIED IDEOGRAPH - 0xA770: 0x5420, //CJK UNIFIED IDEOGRAPH - 0xA771: 0x543C, //CJK UNIFIED IDEOGRAPH - 0xA772: 0x5440, //CJK UNIFIED IDEOGRAPH - 0xA773: 0x5431, //CJK UNIFIED IDEOGRAPH - 0xA774: 0x542B, //CJK UNIFIED IDEOGRAPH - 0xA775: 0x541F, //CJK UNIFIED IDEOGRAPH - 0xA776: 0x542C, //CJK UNIFIED IDEOGRAPH - 0xA777: 0x56EA, //CJK UNIFIED IDEOGRAPH - 0xA778: 0x56F0, //CJK UNIFIED IDEOGRAPH - 0xA779: 0x56E4, //CJK UNIFIED IDEOGRAPH - 0xA77A: 0x56EB, //CJK UNIFIED IDEOGRAPH - 0xA77B: 0x574A, //CJK UNIFIED IDEOGRAPH - 0xA77C: 0x5751, //CJK UNIFIED IDEOGRAPH - 0xA77D: 0x5740, //CJK UNIFIED IDEOGRAPH - 0xA77E: 0x574D, //CJK UNIFIED IDEOGRAPH - 0xA7A1: 0x5747, //CJK UNIFIED IDEOGRAPH - 0xA7A2: 0x574E, //CJK UNIFIED IDEOGRAPH - 0xA7A3: 0x573E, //CJK UNIFIED IDEOGRAPH - 0xA7A4: 0x5750, //CJK UNIFIED IDEOGRAPH - 0xA7A5: 0x574F, //CJK UNIFIED IDEOGRAPH - 0xA7A6: 0x573B, //CJK UNIFIED IDEOGRAPH - 0xA7A7: 0x58EF, //CJK UNIFIED IDEOGRAPH - 0xA7A8: 0x593E, //CJK UNIFIED IDEOGRAPH - 0xA7A9: 0x599D, //CJK UNIFIED IDEOGRAPH - 0xA7AA: 0x5992, //CJK UNIFIED IDEOGRAPH - 0xA7AB: 0x59A8, //CJK UNIFIED IDEOGRAPH - 0xA7AC: 0x599E, //CJK UNIFIED IDEOGRAPH - 0xA7AD: 0x59A3, //CJK UNIFIED IDEOGRAPH - 0xA7AE: 0x5999, //CJK UNIFIED IDEOGRAPH - 0xA7AF: 0x5996, //CJK UNIFIED IDEOGRAPH - 0xA7B0: 0x598D, //CJK UNIFIED IDEOGRAPH - 0xA7B1: 0x59A4, //CJK UNIFIED IDEOGRAPH - 0xA7B2: 0x5993, //CJK UNIFIED IDEOGRAPH - 0xA7B3: 0x598A, //CJK UNIFIED IDEOGRAPH - 0xA7B4: 0x59A5, //CJK UNIFIED IDEOGRAPH - 0xA7B5: 0x5B5D, //CJK UNIFIED IDEOGRAPH - 0xA7B6: 0x5B5C, //CJK UNIFIED IDEOGRAPH - 0xA7B7: 0x5B5A, //CJK UNIFIED IDEOGRAPH - 0xA7B8: 0x5B5B, //CJK UNIFIED IDEOGRAPH - 0xA7B9: 0x5B8C, //CJK UNIFIED IDEOGRAPH - 0xA7BA: 0x5B8B, //CJK UNIFIED IDEOGRAPH - 0xA7BB: 0x5B8F, //CJK UNIFIED IDEOGRAPH - 0xA7BC: 0x5C2C, //CJK UNIFIED IDEOGRAPH - 0xA7BD: 0x5C40, //CJK UNIFIED IDEOGRAPH - 0xA7BE: 0x5C41, //CJK UNIFIED IDEOGRAPH - 0xA7BF: 0x5C3F, //CJK UNIFIED IDEOGRAPH - 0xA7C0: 0x5C3E, //CJK UNIFIED IDEOGRAPH - 0xA7C1: 0x5C90, //CJK UNIFIED IDEOGRAPH - 0xA7C2: 0x5C91, //CJK UNIFIED IDEOGRAPH - 0xA7C3: 0x5C94, //CJK UNIFIED IDEOGRAPH - 0xA7C4: 0x5C8C, //CJK UNIFIED IDEOGRAPH - 0xA7C5: 0x5DEB, //CJK UNIFIED IDEOGRAPH - 0xA7C6: 0x5E0C, //CJK UNIFIED IDEOGRAPH - 0xA7C7: 0x5E8F, //CJK UNIFIED IDEOGRAPH - 0xA7C8: 0x5E87, //CJK UNIFIED IDEOGRAPH - 0xA7C9: 0x5E8A, //CJK UNIFIED IDEOGRAPH - 0xA7CA: 0x5EF7, //CJK UNIFIED IDEOGRAPH - 0xA7CB: 0x5F04, //CJK UNIFIED IDEOGRAPH - 0xA7CC: 0x5F1F, //CJK UNIFIED IDEOGRAPH - 0xA7CD: 0x5F64, //CJK UNIFIED IDEOGRAPH - 0xA7CE: 0x5F62, //CJK UNIFIED IDEOGRAPH - 0xA7CF: 0x5F77, //CJK UNIFIED IDEOGRAPH - 0xA7D0: 0x5F79, //CJK UNIFIED IDEOGRAPH - 0xA7D1: 0x5FD8, //CJK UNIFIED IDEOGRAPH - 0xA7D2: 0x5FCC, //CJK UNIFIED IDEOGRAPH - 0xA7D3: 0x5FD7, //CJK UNIFIED IDEOGRAPH - 0xA7D4: 0x5FCD, //CJK UNIFIED IDEOGRAPH - 0xA7D5: 0x5FF1, //CJK UNIFIED IDEOGRAPH - 0xA7D6: 0x5FEB, //CJK UNIFIED IDEOGRAPH - 0xA7D7: 0x5FF8, //CJK UNIFIED IDEOGRAPH - 0xA7D8: 0x5FEA, //CJK UNIFIED IDEOGRAPH - 0xA7D9: 0x6212, //CJK UNIFIED IDEOGRAPH - 0xA7DA: 0x6211, //CJK UNIFIED IDEOGRAPH - 0xA7DB: 0x6284, //CJK UNIFIED IDEOGRAPH - 0xA7DC: 0x6297, //CJK UNIFIED IDEOGRAPH - 0xA7DD: 0x6296, //CJK UNIFIED IDEOGRAPH - 0xA7DE: 0x6280, //CJK UNIFIED IDEOGRAPH - 0xA7DF: 0x6276, //CJK UNIFIED IDEOGRAPH - 0xA7E0: 0x6289, //CJK UNIFIED IDEOGRAPH - 0xA7E1: 0x626D, //CJK UNIFIED IDEOGRAPH - 0xA7E2: 0x628A, //CJK UNIFIED IDEOGRAPH - 0xA7E3: 0x627C, //CJK UNIFIED IDEOGRAPH - 0xA7E4: 0x627E, //CJK UNIFIED IDEOGRAPH - 0xA7E5: 0x6279, //CJK UNIFIED IDEOGRAPH - 0xA7E6: 0x6273, //CJK UNIFIED IDEOGRAPH - 0xA7E7: 0x6292, //CJK UNIFIED IDEOGRAPH - 0xA7E8: 0x626F, //CJK UNIFIED IDEOGRAPH - 0xA7E9: 0x6298, //CJK UNIFIED IDEOGRAPH - 0xA7EA: 0x626E, //CJK UNIFIED IDEOGRAPH - 0xA7EB: 0x6295, //CJK UNIFIED IDEOGRAPH - 0xA7EC: 0x6293, //CJK UNIFIED IDEOGRAPH - 0xA7ED: 0x6291, //CJK UNIFIED IDEOGRAPH - 0xA7EE: 0x6286, //CJK UNIFIED IDEOGRAPH - 0xA7EF: 0x6539, //CJK UNIFIED IDEOGRAPH - 0xA7F0: 0x653B, //CJK UNIFIED IDEOGRAPH - 0xA7F1: 0x6538, //CJK UNIFIED IDEOGRAPH - 0xA7F2: 0x65F1, //CJK UNIFIED IDEOGRAPH - 0xA7F3: 0x66F4, //CJK UNIFIED IDEOGRAPH - 0xA7F4: 0x675F, //CJK UNIFIED IDEOGRAPH - 0xA7F5: 0x674E, //CJK UNIFIED IDEOGRAPH - 0xA7F6: 0x674F, //CJK UNIFIED IDEOGRAPH - 0xA7F7: 0x6750, //CJK UNIFIED IDEOGRAPH - 0xA7F8: 0x6751, //CJK UNIFIED IDEOGRAPH - 0xA7F9: 0x675C, //CJK UNIFIED IDEOGRAPH - 0xA7FA: 0x6756, //CJK UNIFIED IDEOGRAPH - 0xA7FB: 0x675E, //CJK UNIFIED IDEOGRAPH - 0xA7FC: 0x6749, //CJK UNIFIED IDEOGRAPH - 0xA7FD: 0x6746, //CJK UNIFIED IDEOGRAPH - 0xA7FE: 0x6760, //CJK UNIFIED IDEOGRAPH - 0xA840: 0x6753, //CJK UNIFIED IDEOGRAPH - 0xA841: 0x6757, //CJK UNIFIED IDEOGRAPH - 0xA842: 0x6B65, //CJK UNIFIED IDEOGRAPH - 0xA843: 0x6BCF, //CJK UNIFIED IDEOGRAPH - 0xA844: 0x6C42, //CJK UNIFIED IDEOGRAPH - 0xA845: 0x6C5E, //CJK UNIFIED IDEOGRAPH - 0xA846: 0x6C99, //CJK UNIFIED IDEOGRAPH - 0xA847: 0x6C81, //CJK UNIFIED IDEOGRAPH - 0xA848: 0x6C88, //CJK UNIFIED IDEOGRAPH - 0xA849: 0x6C89, //CJK UNIFIED IDEOGRAPH - 0xA84A: 0x6C85, //CJK UNIFIED IDEOGRAPH - 0xA84B: 0x6C9B, //CJK UNIFIED IDEOGRAPH - 0xA84C: 0x6C6A, //CJK UNIFIED IDEOGRAPH - 0xA84D: 0x6C7A, //CJK UNIFIED IDEOGRAPH - 0xA84E: 0x6C90, //CJK UNIFIED IDEOGRAPH - 0xA84F: 0x6C70, //CJK UNIFIED IDEOGRAPH - 0xA850: 0x6C8C, //CJK UNIFIED IDEOGRAPH - 0xA851: 0x6C68, //CJK UNIFIED IDEOGRAPH - 0xA852: 0x6C96, //CJK UNIFIED IDEOGRAPH - 0xA853: 0x6C92, //CJK UNIFIED IDEOGRAPH - 0xA854: 0x6C7D, //CJK UNIFIED IDEOGRAPH - 0xA855: 0x6C83, //CJK UNIFIED IDEOGRAPH - 0xA856: 0x6C72, //CJK UNIFIED IDEOGRAPH - 0xA857: 0x6C7E, //CJK UNIFIED IDEOGRAPH - 0xA858: 0x6C74, //CJK UNIFIED IDEOGRAPH - 0xA859: 0x6C86, //CJK UNIFIED IDEOGRAPH - 0xA85A: 0x6C76, //CJK UNIFIED IDEOGRAPH - 0xA85B: 0x6C8D, //CJK UNIFIED IDEOGRAPH - 0xA85C: 0x6C94, //CJK UNIFIED IDEOGRAPH - 0xA85D: 0x6C98, //CJK UNIFIED IDEOGRAPH - 0xA85E: 0x6C82, //CJK UNIFIED IDEOGRAPH - 0xA85F: 0x7076, //CJK UNIFIED IDEOGRAPH - 0xA860: 0x707C, //CJK UNIFIED IDEOGRAPH - 0xA861: 0x707D, //CJK UNIFIED IDEOGRAPH - 0xA862: 0x7078, //CJK UNIFIED IDEOGRAPH - 0xA863: 0x7262, //CJK UNIFIED IDEOGRAPH - 0xA864: 0x7261, //CJK UNIFIED IDEOGRAPH - 0xA865: 0x7260, //CJK UNIFIED IDEOGRAPH - 0xA866: 0x72C4, //CJK UNIFIED IDEOGRAPH - 0xA867: 0x72C2, //CJK UNIFIED IDEOGRAPH - 0xA868: 0x7396, //CJK UNIFIED IDEOGRAPH - 0xA869: 0x752C, //CJK UNIFIED IDEOGRAPH - 0xA86A: 0x752B, //CJK UNIFIED IDEOGRAPH - 0xA86B: 0x7537, //CJK UNIFIED IDEOGRAPH - 0xA86C: 0x7538, //CJK UNIFIED IDEOGRAPH - 0xA86D: 0x7682, //CJK UNIFIED IDEOGRAPH - 0xA86E: 0x76EF, //CJK UNIFIED IDEOGRAPH - 0xA86F: 0x77E3, //CJK UNIFIED IDEOGRAPH - 0xA870: 0x79C1, //CJK UNIFIED IDEOGRAPH - 0xA871: 0x79C0, //CJK UNIFIED IDEOGRAPH - 0xA872: 0x79BF, //CJK UNIFIED IDEOGRAPH - 0xA873: 0x7A76, //CJK UNIFIED IDEOGRAPH - 0xA874: 0x7CFB, //CJK UNIFIED IDEOGRAPH - 0xA875: 0x7F55, //CJK UNIFIED IDEOGRAPH - 0xA876: 0x8096, //CJK UNIFIED IDEOGRAPH - 0xA877: 0x8093, //CJK UNIFIED IDEOGRAPH - 0xA878: 0x809D, //CJK UNIFIED IDEOGRAPH - 0xA879: 0x8098, //CJK UNIFIED IDEOGRAPH - 0xA87A: 0x809B, //CJK UNIFIED IDEOGRAPH - 0xA87B: 0x809A, //CJK UNIFIED IDEOGRAPH - 0xA87C: 0x80B2, //CJK UNIFIED IDEOGRAPH - 0xA87D: 0x826F, //CJK UNIFIED IDEOGRAPH - 0xA87E: 0x8292, //CJK UNIFIED IDEOGRAPH - 0xA8A1: 0x828B, //CJK UNIFIED IDEOGRAPH - 0xA8A2: 0x828D, //CJK UNIFIED IDEOGRAPH - 0xA8A3: 0x898B, //CJK UNIFIED IDEOGRAPH - 0xA8A4: 0x89D2, //CJK UNIFIED IDEOGRAPH - 0xA8A5: 0x8A00, //CJK UNIFIED IDEOGRAPH - 0xA8A6: 0x8C37, //CJK UNIFIED IDEOGRAPH - 0xA8A7: 0x8C46, //CJK UNIFIED IDEOGRAPH - 0xA8A8: 0x8C55, //CJK UNIFIED IDEOGRAPH - 0xA8A9: 0x8C9D, //CJK UNIFIED IDEOGRAPH - 0xA8AA: 0x8D64, //CJK UNIFIED IDEOGRAPH - 0xA8AB: 0x8D70, //CJK UNIFIED IDEOGRAPH - 0xA8AC: 0x8DB3, //CJK UNIFIED IDEOGRAPH - 0xA8AD: 0x8EAB, //CJK UNIFIED IDEOGRAPH - 0xA8AE: 0x8ECA, //CJK UNIFIED IDEOGRAPH - 0xA8AF: 0x8F9B, //CJK UNIFIED IDEOGRAPH - 0xA8B0: 0x8FB0, //CJK UNIFIED IDEOGRAPH - 0xA8B1: 0x8FC2, //CJK UNIFIED IDEOGRAPH - 0xA8B2: 0x8FC6, //CJK UNIFIED IDEOGRAPH - 0xA8B3: 0x8FC5, //CJK UNIFIED IDEOGRAPH - 0xA8B4: 0x8FC4, //CJK UNIFIED IDEOGRAPH - 0xA8B5: 0x5DE1, //CJK UNIFIED IDEOGRAPH - 0xA8B6: 0x9091, //CJK UNIFIED IDEOGRAPH - 0xA8B7: 0x90A2, //CJK UNIFIED IDEOGRAPH - 0xA8B8: 0x90AA, //CJK UNIFIED IDEOGRAPH - 0xA8B9: 0x90A6, //CJK UNIFIED IDEOGRAPH - 0xA8BA: 0x90A3, //CJK UNIFIED IDEOGRAPH - 0xA8BB: 0x9149, //CJK UNIFIED IDEOGRAPH - 0xA8BC: 0x91C6, //CJK UNIFIED IDEOGRAPH - 0xA8BD: 0x91CC, //CJK UNIFIED IDEOGRAPH - 0xA8BE: 0x9632, //CJK UNIFIED IDEOGRAPH - 0xA8BF: 0x962E, //CJK UNIFIED IDEOGRAPH - 0xA8C0: 0x9631, //CJK UNIFIED IDEOGRAPH - 0xA8C1: 0x962A, //CJK UNIFIED IDEOGRAPH - 0xA8C2: 0x962C, //CJK UNIFIED IDEOGRAPH - 0xA8C3: 0x4E26, //CJK UNIFIED IDEOGRAPH - 0xA8C4: 0x4E56, //CJK UNIFIED IDEOGRAPH - 0xA8C5: 0x4E73, //CJK UNIFIED IDEOGRAPH - 0xA8C6: 0x4E8B, //CJK UNIFIED IDEOGRAPH - 0xA8C7: 0x4E9B, //CJK UNIFIED IDEOGRAPH - 0xA8C8: 0x4E9E, //CJK UNIFIED IDEOGRAPH - 0xA8C9: 0x4EAB, //CJK UNIFIED IDEOGRAPH - 0xA8CA: 0x4EAC, //CJK UNIFIED IDEOGRAPH - 0xA8CB: 0x4F6F, //CJK UNIFIED IDEOGRAPH - 0xA8CC: 0x4F9D, //CJK UNIFIED IDEOGRAPH - 0xA8CD: 0x4F8D, //CJK UNIFIED IDEOGRAPH - 0xA8CE: 0x4F73, //CJK UNIFIED IDEOGRAPH - 0xA8CF: 0x4F7F, //CJK UNIFIED IDEOGRAPH - 0xA8D0: 0x4F6C, //CJK UNIFIED IDEOGRAPH - 0xA8D1: 0x4F9B, //CJK UNIFIED IDEOGRAPH - 0xA8D2: 0x4F8B, //CJK UNIFIED IDEOGRAPH - 0xA8D3: 0x4F86, //CJK UNIFIED IDEOGRAPH - 0xA8D4: 0x4F83, //CJK UNIFIED IDEOGRAPH - 0xA8D5: 0x4F70, //CJK UNIFIED IDEOGRAPH - 0xA8D6: 0x4F75, //CJK UNIFIED IDEOGRAPH - 0xA8D7: 0x4F88, //CJK UNIFIED IDEOGRAPH - 0xA8D8: 0x4F69, //CJK UNIFIED IDEOGRAPH - 0xA8D9: 0x4F7B, //CJK UNIFIED IDEOGRAPH - 0xA8DA: 0x4F96, //CJK UNIFIED IDEOGRAPH - 0xA8DB: 0x4F7E, //CJK UNIFIED IDEOGRAPH - 0xA8DC: 0x4F8F, //CJK UNIFIED IDEOGRAPH - 0xA8DD: 0x4F91, //CJK UNIFIED IDEOGRAPH - 0xA8DE: 0x4F7A, //CJK UNIFIED IDEOGRAPH - 0xA8DF: 0x5154, //CJK UNIFIED IDEOGRAPH - 0xA8E0: 0x5152, //CJK UNIFIED IDEOGRAPH - 0xA8E1: 0x5155, //CJK UNIFIED IDEOGRAPH - 0xA8E2: 0x5169, //CJK UNIFIED IDEOGRAPH - 0xA8E3: 0x5177, //CJK UNIFIED IDEOGRAPH - 0xA8E4: 0x5176, //CJK UNIFIED IDEOGRAPH - 0xA8E5: 0x5178, //CJK UNIFIED IDEOGRAPH - 0xA8E6: 0x51BD, //CJK UNIFIED IDEOGRAPH - 0xA8E7: 0x51FD, //CJK UNIFIED IDEOGRAPH - 0xA8E8: 0x523B, //CJK UNIFIED IDEOGRAPH - 0xA8E9: 0x5238, //CJK UNIFIED IDEOGRAPH - 0xA8EA: 0x5237, //CJK UNIFIED IDEOGRAPH - 0xA8EB: 0x523A, //CJK UNIFIED IDEOGRAPH - 0xA8EC: 0x5230, //CJK UNIFIED IDEOGRAPH - 0xA8ED: 0x522E, //CJK UNIFIED IDEOGRAPH - 0xA8EE: 0x5236, //CJK UNIFIED IDEOGRAPH - 0xA8EF: 0x5241, //CJK UNIFIED IDEOGRAPH - 0xA8F0: 0x52BE, //CJK UNIFIED IDEOGRAPH - 0xA8F1: 0x52BB, //CJK UNIFIED IDEOGRAPH - 0xA8F2: 0x5352, //CJK UNIFIED IDEOGRAPH - 0xA8F3: 0x5354, //CJK UNIFIED IDEOGRAPH - 0xA8F4: 0x5353, //CJK UNIFIED IDEOGRAPH - 0xA8F5: 0x5351, //CJK UNIFIED IDEOGRAPH - 0xA8F6: 0x5366, //CJK UNIFIED IDEOGRAPH - 0xA8F7: 0x5377, //CJK UNIFIED IDEOGRAPH - 0xA8F8: 0x5378, //CJK UNIFIED IDEOGRAPH - 0xA8F9: 0x5379, //CJK UNIFIED IDEOGRAPH - 0xA8FA: 0x53D6, //CJK UNIFIED IDEOGRAPH - 0xA8FB: 0x53D4, //CJK UNIFIED IDEOGRAPH - 0xA8FC: 0x53D7, //CJK UNIFIED IDEOGRAPH - 0xA8FD: 0x5473, //CJK UNIFIED IDEOGRAPH - 0xA8FE: 0x5475, //CJK UNIFIED IDEOGRAPH - 0xA940: 0x5496, //CJK UNIFIED IDEOGRAPH - 0xA941: 0x5478, //CJK UNIFIED IDEOGRAPH - 0xA942: 0x5495, //CJK UNIFIED IDEOGRAPH - 0xA943: 0x5480, //CJK UNIFIED IDEOGRAPH - 0xA944: 0x547B, //CJK UNIFIED IDEOGRAPH - 0xA945: 0x5477, //CJK UNIFIED IDEOGRAPH - 0xA946: 0x5484, //CJK UNIFIED IDEOGRAPH - 0xA947: 0x5492, //CJK UNIFIED IDEOGRAPH - 0xA948: 0x5486, //CJK UNIFIED IDEOGRAPH - 0xA949: 0x547C, //CJK UNIFIED IDEOGRAPH - 0xA94A: 0x5490, //CJK UNIFIED IDEOGRAPH - 0xA94B: 0x5471, //CJK UNIFIED IDEOGRAPH - 0xA94C: 0x5476, //CJK UNIFIED IDEOGRAPH - 0xA94D: 0x548C, //CJK UNIFIED IDEOGRAPH - 0xA94E: 0x549A, //CJK UNIFIED IDEOGRAPH - 0xA94F: 0x5462, //CJK UNIFIED IDEOGRAPH - 0xA950: 0x5468, //CJK UNIFIED IDEOGRAPH - 0xA951: 0x548B, //CJK UNIFIED IDEOGRAPH - 0xA952: 0x547D, //CJK UNIFIED IDEOGRAPH - 0xA953: 0x548E, //CJK UNIFIED IDEOGRAPH - 0xA954: 0x56FA, //CJK UNIFIED IDEOGRAPH - 0xA955: 0x5783, //CJK UNIFIED IDEOGRAPH - 0xA956: 0x5777, //CJK UNIFIED IDEOGRAPH - 0xA957: 0x576A, //CJK UNIFIED IDEOGRAPH - 0xA958: 0x5769, //CJK UNIFIED IDEOGRAPH - 0xA959: 0x5761, //CJK UNIFIED IDEOGRAPH - 0xA95A: 0x5766, //CJK UNIFIED IDEOGRAPH - 0xA95B: 0x5764, //CJK UNIFIED IDEOGRAPH - 0xA95C: 0x577C, //CJK UNIFIED IDEOGRAPH - 0xA95D: 0x591C, //CJK UNIFIED IDEOGRAPH - 0xA95E: 0x5949, //CJK UNIFIED IDEOGRAPH - 0xA95F: 0x5947, //CJK UNIFIED IDEOGRAPH - 0xA960: 0x5948, //CJK UNIFIED IDEOGRAPH - 0xA961: 0x5944, //CJK UNIFIED IDEOGRAPH - 0xA962: 0x5954, //CJK UNIFIED IDEOGRAPH - 0xA963: 0x59BE, //CJK UNIFIED IDEOGRAPH - 0xA964: 0x59BB, //CJK UNIFIED IDEOGRAPH - 0xA965: 0x59D4, //CJK UNIFIED IDEOGRAPH - 0xA966: 0x59B9, //CJK UNIFIED IDEOGRAPH - 0xA967: 0x59AE, //CJK UNIFIED IDEOGRAPH - 0xA968: 0x59D1, //CJK UNIFIED IDEOGRAPH - 0xA969: 0x59C6, //CJK UNIFIED IDEOGRAPH - 0xA96A: 0x59D0, //CJK UNIFIED IDEOGRAPH - 0xA96B: 0x59CD, //CJK UNIFIED IDEOGRAPH - 0xA96C: 0x59CB, //CJK UNIFIED IDEOGRAPH - 0xA96D: 0x59D3, //CJK UNIFIED IDEOGRAPH - 0xA96E: 0x59CA, //CJK UNIFIED IDEOGRAPH - 0xA96F: 0x59AF, //CJK UNIFIED IDEOGRAPH - 0xA970: 0x59B3, //CJK UNIFIED IDEOGRAPH - 0xA971: 0x59D2, //CJK UNIFIED IDEOGRAPH - 0xA972: 0x59C5, //CJK UNIFIED IDEOGRAPH - 0xA973: 0x5B5F, //CJK UNIFIED IDEOGRAPH - 0xA974: 0x5B64, //CJK UNIFIED IDEOGRAPH - 0xA975: 0x5B63, //CJK UNIFIED IDEOGRAPH - 0xA976: 0x5B97, //CJK UNIFIED IDEOGRAPH - 0xA977: 0x5B9A, //CJK UNIFIED IDEOGRAPH - 0xA978: 0x5B98, //CJK UNIFIED IDEOGRAPH - 0xA979: 0x5B9C, //CJK UNIFIED IDEOGRAPH - 0xA97A: 0x5B99, //CJK UNIFIED IDEOGRAPH - 0xA97B: 0x5B9B, //CJK UNIFIED IDEOGRAPH - 0xA97C: 0x5C1A, //CJK UNIFIED IDEOGRAPH - 0xA97D: 0x5C48, //CJK UNIFIED IDEOGRAPH - 0xA97E: 0x5C45, //CJK UNIFIED IDEOGRAPH - 0xA9A1: 0x5C46, //CJK UNIFIED IDEOGRAPH - 0xA9A2: 0x5CB7, //CJK UNIFIED IDEOGRAPH - 0xA9A3: 0x5CA1, //CJK UNIFIED IDEOGRAPH - 0xA9A4: 0x5CB8, //CJK UNIFIED IDEOGRAPH - 0xA9A5: 0x5CA9, //CJK UNIFIED IDEOGRAPH - 0xA9A6: 0x5CAB, //CJK UNIFIED IDEOGRAPH - 0xA9A7: 0x5CB1, //CJK UNIFIED IDEOGRAPH - 0xA9A8: 0x5CB3, //CJK UNIFIED IDEOGRAPH - 0xA9A9: 0x5E18, //CJK UNIFIED IDEOGRAPH - 0xA9AA: 0x5E1A, //CJK UNIFIED IDEOGRAPH - 0xA9AB: 0x5E16, //CJK UNIFIED IDEOGRAPH - 0xA9AC: 0x5E15, //CJK UNIFIED IDEOGRAPH - 0xA9AD: 0x5E1B, //CJK UNIFIED IDEOGRAPH - 0xA9AE: 0x5E11, //CJK UNIFIED IDEOGRAPH - 0xA9AF: 0x5E78, //CJK UNIFIED IDEOGRAPH - 0xA9B0: 0x5E9A, //CJK UNIFIED IDEOGRAPH - 0xA9B1: 0x5E97, //CJK UNIFIED IDEOGRAPH - 0xA9B2: 0x5E9C, //CJK UNIFIED IDEOGRAPH - 0xA9B3: 0x5E95, //CJK UNIFIED IDEOGRAPH - 0xA9B4: 0x5E96, //CJK UNIFIED IDEOGRAPH - 0xA9B5: 0x5EF6, //CJK UNIFIED IDEOGRAPH - 0xA9B6: 0x5F26, //CJK UNIFIED IDEOGRAPH - 0xA9B7: 0x5F27, //CJK UNIFIED IDEOGRAPH - 0xA9B8: 0x5F29, //CJK UNIFIED IDEOGRAPH - 0xA9B9: 0x5F80, //CJK UNIFIED IDEOGRAPH - 0xA9BA: 0x5F81, //CJK UNIFIED IDEOGRAPH - 0xA9BB: 0x5F7F, //CJK UNIFIED IDEOGRAPH - 0xA9BC: 0x5F7C, //CJK UNIFIED IDEOGRAPH - 0xA9BD: 0x5FDD, //CJK UNIFIED IDEOGRAPH - 0xA9BE: 0x5FE0, //CJK UNIFIED IDEOGRAPH - 0xA9BF: 0x5FFD, //CJK UNIFIED IDEOGRAPH - 0xA9C0: 0x5FF5, //CJK UNIFIED IDEOGRAPH - 0xA9C1: 0x5FFF, //CJK UNIFIED IDEOGRAPH - 0xA9C2: 0x600F, //CJK UNIFIED IDEOGRAPH - 0xA9C3: 0x6014, //CJK UNIFIED IDEOGRAPH - 0xA9C4: 0x602F, //CJK UNIFIED IDEOGRAPH - 0xA9C5: 0x6035, //CJK UNIFIED IDEOGRAPH - 0xA9C6: 0x6016, //CJK UNIFIED IDEOGRAPH - 0xA9C7: 0x602A, //CJK UNIFIED IDEOGRAPH - 0xA9C8: 0x6015, //CJK UNIFIED IDEOGRAPH - 0xA9C9: 0x6021, //CJK UNIFIED IDEOGRAPH - 0xA9CA: 0x6027, //CJK UNIFIED IDEOGRAPH - 0xA9CB: 0x6029, //CJK UNIFIED IDEOGRAPH - 0xA9CC: 0x602B, //CJK UNIFIED IDEOGRAPH - 0xA9CD: 0x601B, //CJK UNIFIED IDEOGRAPH - 0xA9CE: 0x6216, //CJK UNIFIED IDEOGRAPH - 0xA9CF: 0x6215, //CJK UNIFIED IDEOGRAPH - 0xA9D0: 0x623F, //CJK UNIFIED IDEOGRAPH - 0xA9D1: 0x623E, //CJK UNIFIED IDEOGRAPH - 0xA9D2: 0x6240, //CJK UNIFIED IDEOGRAPH - 0xA9D3: 0x627F, //CJK UNIFIED IDEOGRAPH - 0xA9D4: 0x62C9, //CJK UNIFIED IDEOGRAPH - 0xA9D5: 0x62CC, //CJK UNIFIED IDEOGRAPH - 0xA9D6: 0x62C4, //CJK UNIFIED IDEOGRAPH - 0xA9D7: 0x62BF, //CJK UNIFIED IDEOGRAPH - 0xA9D8: 0x62C2, //CJK UNIFIED IDEOGRAPH - 0xA9D9: 0x62B9, //CJK UNIFIED IDEOGRAPH - 0xA9DA: 0x62D2, //CJK UNIFIED IDEOGRAPH - 0xA9DB: 0x62DB, //CJK UNIFIED IDEOGRAPH - 0xA9DC: 0x62AB, //CJK UNIFIED IDEOGRAPH - 0xA9DD: 0x62D3, //CJK UNIFIED IDEOGRAPH - 0xA9DE: 0x62D4, //CJK UNIFIED IDEOGRAPH - 0xA9DF: 0x62CB, //CJK UNIFIED IDEOGRAPH - 0xA9E0: 0x62C8, //CJK UNIFIED IDEOGRAPH - 0xA9E1: 0x62A8, //CJK UNIFIED IDEOGRAPH - 0xA9E2: 0x62BD, //CJK UNIFIED IDEOGRAPH - 0xA9E3: 0x62BC, //CJK UNIFIED IDEOGRAPH - 0xA9E4: 0x62D0, //CJK UNIFIED IDEOGRAPH - 0xA9E5: 0x62D9, //CJK UNIFIED IDEOGRAPH - 0xA9E6: 0x62C7, //CJK UNIFIED IDEOGRAPH - 0xA9E7: 0x62CD, //CJK UNIFIED IDEOGRAPH - 0xA9E8: 0x62B5, //CJK UNIFIED IDEOGRAPH - 0xA9E9: 0x62DA, //CJK UNIFIED IDEOGRAPH - 0xA9EA: 0x62B1, //CJK UNIFIED IDEOGRAPH - 0xA9EB: 0x62D8, //CJK UNIFIED IDEOGRAPH - 0xA9EC: 0x62D6, //CJK UNIFIED IDEOGRAPH - 0xA9ED: 0x62D7, //CJK UNIFIED IDEOGRAPH - 0xA9EE: 0x62C6, //CJK UNIFIED IDEOGRAPH - 0xA9EF: 0x62AC, //CJK UNIFIED IDEOGRAPH - 0xA9F0: 0x62CE, //CJK UNIFIED IDEOGRAPH - 0xA9F1: 0x653E, //CJK UNIFIED IDEOGRAPH - 0xA9F2: 0x65A7, //CJK UNIFIED IDEOGRAPH - 0xA9F3: 0x65BC, //CJK UNIFIED IDEOGRAPH - 0xA9F4: 0x65FA, //CJK UNIFIED IDEOGRAPH - 0xA9F5: 0x6614, //CJK UNIFIED IDEOGRAPH - 0xA9F6: 0x6613, //CJK UNIFIED IDEOGRAPH - 0xA9F7: 0x660C, //CJK UNIFIED IDEOGRAPH - 0xA9F8: 0x6606, //CJK UNIFIED IDEOGRAPH - 0xA9F9: 0x6602, //CJK UNIFIED IDEOGRAPH - 0xA9FA: 0x660E, //CJK UNIFIED IDEOGRAPH - 0xA9FB: 0x6600, //CJK UNIFIED IDEOGRAPH - 0xA9FC: 0x660F, //CJK UNIFIED IDEOGRAPH - 0xA9FD: 0x6615, //CJK UNIFIED IDEOGRAPH - 0xA9FE: 0x660A, //CJK UNIFIED IDEOGRAPH - 0xAA40: 0x6607, //CJK UNIFIED IDEOGRAPH - 0xAA41: 0x670D, //CJK UNIFIED IDEOGRAPH - 0xAA42: 0x670B, //CJK UNIFIED IDEOGRAPH - 0xAA43: 0x676D, //CJK UNIFIED IDEOGRAPH - 0xAA44: 0x678B, //CJK UNIFIED IDEOGRAPH - 0xAA45: 0x6795, //CJK UNIFIED IDEOGRAPH - 0xAA46: 0x6771, //CJK UNIFIED IDEOGRAPH - 0xAA47: 0x679C, //CJK UNIFIED IDEOGRAPH - 0xAA48: 0x6773, //CJK UNIFIED IDEOGRAPH - 0xAA49: 0x6777, //CJK UNIFIED IDEOGRAPH - 0xAA4A: 0x6787, //CJK UNIFIED IDEOGRAPH - 0xAA4B: 0x679D, //CJK UNIFIED IDEOGRAPH - 0xAA4C: 0x6797, //CJK UNIFIED IDEOGRAPH - 0xAA4D: 0x676F, //CJK UNIFIED IDEOGRAPH - 0xAA4E: 0x6770, //CJK UNIFIED IDEOGRAPH - 0xAA4F: 0x677F, //CJK UNIFIED IDEOGRAPH - 0xAA50: 0x6789, //CJK UNIFIED IDEOGRAPH - 0xAA51: 0x677E, //CJK UNIFIED IDEOGRAPH - 0xAA52: 0x6790, //CJK UNIFIED IDEOGRAPH - 0xAA53: 0x6775, //CJK UNIFIED IDEOGRAPH - 0xAA54: 0x679A, //CJK UNIFIED IDEOGRAPH - 0xAA55: 0x6793, //CJK UNIFIED IDEOGRAPH - 0xAA56: 0x677C, //CJK UNIFIED IDEOGRAPH - 0xAA57: 0x676A, //CJK UNIFIED IDEOGRAPH - 0xAA58: 0x6772, //CJK UNIFIED IDEOGRAPH - 0xAA59: 0x6B23, //CJK UNIFIED IDEOGRAPH - 0xAA5A: 0x6B66, //CJK UNIFIED IDEOGRAPH - 0xAA5B: 0x6B67, //CJK UNIFIED IDEOGRAPH - 0xAA5C: 0x6B7F, //CJK UNIFIED IDEOGRAPH - 0xAA5D: 0x6C13, //CJK UNIFIED IDEOGRAPH - 0xAA5E: 0x6C1B, //CJK UNIFIED IDEOGRAPH - 0xAA5F: 0x6CE3, //CJK UNIFIED IDEOGRAPH - 0xAA60: 0x6CE8, //CJK UNIFIED IDEOGRAPH - 0xAA61: 0x6CF3, //CJK UNIFIED IDEOGRAPH - 0xAA62: 0x6CB1, //CJK UNIFIED IDEOGRAPH - 0xAA63: 0x6CCC, //CJK UNIFIED IDEOGRAPH - 0xAA64: 0x6CE5, //CJK UNIFIED IDEOGRAPH - 0xAA65: 0x6CB3, //CJK UNIFIED IDEOGRAPH - 0xAA66: 0x6CBD, //CJK UNIFIED IDEOGRAPH - 0xAA67: 0x6CBE, //CJK UNIFIED IDEOGRAPH - 0xAA68: 0x6CBC, //CJK UNIFIED IDEOGRAPH - 0xAA69: 0x6CE2, //CJK UNIFIED IDEOGRAPH - 0xAA6A: 0x6CAB, //CJK UNIFIED IDEOGRAPH - 0xAA6B: 0x6CD5, //CJK UNIFIED IDEOGRAPH - 0xAA6C: 0x6CD3, //CJK UNIFIED IDEOGRAPH - 0xAA6D: 0x6CB8, //CJK UNIFIED IDEOGRAPH - 0xAA6E: 0x6CC4, //CJK UNIFIED IDEOGRAPH - 0xAA6F: 0x6CB9, //CJK UNIFIED IDEOGRAPH - 0xAA70: 0x6CC1, //CJK UNIFIED IDEOGRAPH - 0xAA71: 0x6CAE, //CJK UNIFIED IDEOGRAPH - 0xAA72: 0x6CD7, //CJK UNIFIED IDEOGRAPH - 0xAA73: 0x6CC5, //CJK UNIFIED IDEOGRAPH - 0xAA74: 0x6CF1, //CJK UNIFIED IDEOGRAPH - 0xAA75: 0x6CBF, //CJK UNIFIED IDEOGRAPH - 0xAA76: 0x6CBB, //CJK UNIFIED IDEOGRAPH - 0xAA77: 0x6CE1, //CJK UNIFIED IDEOGRAPH - 0xAA78: 0x6CDB, //CJK UNIFIED IDEOGRAPH - 0xAA79: 0x6CCA, //CJK UNIFIED IDEOGRAPH - 0xAA7A: 0x6CAC, //CJK UNIFIED IDEOGRAPH - 0xAA7B: 0x6CEF, //CJK UNIFIED IDEOGRAPH - 0xAA7C: 0x6CDC, //CJK UNIFIED IDEOGRAPH - 0xAA7D: 0x6CD6, //CJK UNIFIED IDEOGRAPH - 0xAA7E: 0x6CE0, //CJK UNIFIED IDEOGRAPH - 0xAAA1: 0x7095, //CJK UNIFIED IDEOGRAPH - 0xAAA2: 0x708E, //CJK UNIFIED IDEOGRAPH - 0xAAA3: 0x7092, //CJK UNIFIED IDEOGRAPH - 0xAAA4: 0x708A, //CJK UNIFIED IDEOGRAPH - 0xAAA5: 0x7099, //CJK UNIFIED IDEOGRAPH - 0xAAA6: 0x722C, //CJK UNIFIED IDEOGRAPH - 0xAAA7: 0x722D, //CJK UNIFIED IDEOGRAPH - 0xAAA8: 0x7238, //CJK UNIFIED IDEOGRAPH - 0xAAA9: 0x7248, //CJK UNIFIED IDEOGRAPH - 0xAAAA: 0x7267, //CJK UNIFIED IDEOGRAPH - 0xAAAB: 0x7269, //CJK UNIFIED IDEOGRAPH - 0xAAAC: 0x72C0, //CJK UNIFIED IDEOGRAPH - 0xAAAD: 0x72CE, //CJK UNIFIED IDEOGRAPH - 0xAAAE: 0x72D9, //CJK UNIFIED IDEOGRAPH - 0xAAAF: 0x72D7, //CJK UNIFIED IDEOGRAPH - 0xAAB0: 0x72D0, //CJK UNIFIED IDEOGRAPH - 0xAAB1: 0x73A9, //CJK UNIFIED IDEOGRAPH - 0xAAB2: 0x73A8, //CJK UNIFIED IDEOGRAPH - 0xAAB3: 0x739F, //CJK UNIFIED IDEOGRAPH - 0xAAB4: 0x73AB, //CJK UNIFIED IDEOGRAPH - 0xAAB5: 0x73A5, //CJK UNIFIED IDEOGRAPH - 0xAAB6: 0x753D, //CJK UNIFIED IDEOGRAPH - 0xAAB7: 0x759D, //CJK UNIFIED IDEOGRAPH - 0xAAB8: 0x7599, //CJK UNIFIED IDEOGRAPH - 0xAAB9: 0x759A, //CJK UNIFIED IDEOGRAPH - 0xAABA: 0x7684, //CJK UNIFIED IDEOGRAPH - 0xAABB: 0x76C2, //CJK UNIFIED IDEOGRAPH - 0xAABC: 0x76F2, //CJK UNIFIED IDEOGRAPH - 0xAABD: 0x76F4, //CJK UNIFIED IDEOGRAPH - 0xAABE: 0x77E5, //CJK UNIFIED IDEOGRAPH - 0xAABF: 0x77FD, //CJK UNIFIED IDEOGRAPH - 0xAAC0: 0x793E, //CJK UNIFIED IDEOGRAPH - 0xAAC1: 0x7940, //CJK UNIFIED IDEOGRAPH - 0xAAC2: 0x7941, //CJK UNIFIED IDEOGRAPH - 0xAAC3: 0x79C9, //CJK UNIFIED IDEOGRAPH - 0xAAC4: 0x79C8, //CJK UNIFIED IDEOGRAPH - 0xAAC5: 0x7A7A, //CJK UNIFIED IDEOGRAPH - 0xAAC6: 0x7A79, //CJK UNIFIED IDEOGRAPH - 0xAAC7: 0x7AFA, //CJK UNIFIED IDEOGRAPH - 0xAAC8: 0x7CFE, //CJK UNIFIED IDEOGRAPH - 0xAAC9: 0x7F54, //CJK UNIFIED IDEOGRAPH - 0xAACA: 0x7F8C, //CJK UNIFIED IDEOGRAPH - 0xAACB: 0x7F8B, //CJK UNIFIED IDEOGRAPH - 0xAACC: 0x8005, //CJK UNIFIED IDEOGRAPH - 0xAACD: 0x80BA, //CJK UNIFIED IDEOGRAPH - 0xAACE: 0x80A5, //CJK UNIFIED IDEOGRAPH - 0xAACF: 0x80A2, //CJK UNIFIED IDEOGRAPH - 0xAAD0: 0x80B1, //CJK UNIFIED IDEOGRAPH - 0xAAD1: 0x80A1, //CJK UNIFIED IDEOGRAPH - 0xAAD2: 0x80AB, //CJK UNIFIED IDEOGRAPH - 0xAAD3: 0x80A9, //CJK UNIFIED IDEOGRAPH - 0xAAD4: 0x80B4, //CJK UNIFIED IDEOGRAPH - 0xAAD5: 0x80AA, //CJK UNIFIED IDEOGRAPH - 0xAAD6: 0x80AF, //CJK UNIFIED IDEOGRAPH - 0xAAD7: 0x81E5, //CJK UNIFIED IDEOGRAPH - 0xAAD8: 0x81FE, //CJK UNIFIED IDEOGRAPH - 0xAAD9: 0x820D, //CJK UNIFIED IDEOGRAPH - 0xAADA: 0x82B3, //CJK UNIFIED IDEOGRAPH - 0xAADB: 0x829D, //CJK UNIFIED IDEOGRAPH - 0xAADC: 0x8299, //CJK UNIFIED IDEOGRAPH - 0xAADD: 0x82AD, //CJK UNIFIED IDEOGRAPH - 0xAADE: 0x82BD, //CJK UNIFIED IDEOGRAPH - 0xAADF: 0x829F, //CJK UNIFIED IDEOGRAPH - 0xAAE0: 0x82B9, //CJK UNIFIED IDEOGRAPH - 0xAAE1: 0x82B1, //CJK UNIFIED IDEOGRAPH - 0xAAE2: 0x82AC, //CJK UNIFIED IDEOGRAPH - 0xAAE3: 0x82A5, //CJK UNIFIED IDEOGRAPH - 0xAAE4: 0x82AF, //CJK UNIFIED IDEOGRAPH - 0xAAE5: 0x82B8, //CJK UNIFIED IDEOGRAPH - 0xAAE6: 0x82A3, //CJK UNIFIED IDEOGRAPH - 0xAAE7: 0x82B0, //CJK UNIFIED IDEOGRAPH - 0xAAE8: 0x82BE, //CJK UNIFIED IDEOGRAPH - 0xAAE9: 0x82B7, //CJK UNIFIED IDEOGRAPH - 0xAAEA: 0x864E, //CJK UNIFIED IDEOGRAPH - 0xAAEB: 0x8671, //CJK UNIFIED IDEOGRAPH - 0xAAEC: 0x521D, //CJK UNIFIED IDEOGRAPH - 0xAAED: 0x8868, //CJK UNIFIED IDEOGRAPH - 0xAAEE: 0x8ECB, //CJK UNIFIED IDEOGRAPH - 0xAAEF: 0x8FCE, //CJK UNIFIED IDEOGRAPH - 0xAAF0: 0x8FD4, //CJK UNIFIED IDEOGRAPH - 0xAAF1: 0x8FD1, //CJK UNIFIED IDEOGRAPH - 0xAAF2: 0x90B5, //CJK UNIFIED IDEOGRAPH - 0xAAF3: 0x90B8, //CJK UNIFIED IDEOGRAPH - 0xAAF4: 0x90B1, //CJK UNIFIED IDEOGRAPH - 0xAAF5: 0x90B6, //CJK UNIFIED IDEOGRAPH - 0xAAF6: 0x91C7, //CJK UNIFIED IDEOGRAPH - 0xAAF7: 0x91D1, //CJK UNIFIED IDEOGRAPH - 0xAAF8: 0x9577, //CJK UNIFIED IDEOGRAPH - 0xAAF9: 0x9580, //CJK UNIFIED IDEOGRAPH - 0xAAFA: 0x961C, //CJK UNIFIED IDEOGRAPH - 0xAAFB: 0x9640, //CJK UNIFIED IDEOGRAPH - 0xAAFC: 0x963F, //CJK UNIFIED IDEOGRAPH - 0xAAFD: 0x963B, //CJK UNIFIED IDEOGRAPH - 0xAAFE: 0x9644, //CJK UNIFIED IDEOGRAPH - 0xAB40: 0x9642, //CJK UNIFIED IDEOGRAPH - 0xAB41: 0x96B9, //CJK UNIFIED IDEOGRAPH - 0xAB42: 0x96E8, //CJK UNIFIED IDEOGRAPH - 0xAB43: 0x9752, //CJK UNIFIED IDEOGRAPH - 0xAB44: 0x975E, //CJK UNIFIED IDEOGRAPH - 0xAB45: 0x4E9F, //CJK UNIFIED IDEOGRAPH - 0xAB46: 0x4EAD, //CJK UNIFIED IDEOGRAPH - 0xAB47: 0x4EAE, //CJK UNIFIED IDEOGRAPH - 0xAB48: 0x4FE1, //CJK UNIFIED IDEOGRAPH - 0xAB49: 0x4FB5, //CJK UNIFIED IDEOGRAPH - 0xAB4A: 0x4FAF, //CJK UNIFIED IDEOGRAPH - 0xAB4B: 0x4FBF, //CJK UNIFIED IDEOGRAPH - 0xAB4C: 0x4FE0, //CJK UNIFIED IDEOGRAPH - 0xAB4D: 0x4FD1, //CJK UNIFIED IDEOGRAPH - 0xAB4E: 0x4FCF, //CJK UNIFIED IDEOGRAPH - 0xAB4F: 0x4FDD, //CJK UNIFIED IDEOGRAPH - 0xAB50: 0x4FC3, //CJK UNIFIED IDEOGRAPH - 0xAB51: 0x4FB6, //CJK UNIFIED IDEOGRAPH - 0xAB52: 0x4FD8, //CJK UNIFIED IDEOGRAPH - 0xAB53: 0x4FDF, //CJK UNIFIED IDEOGRAPH - 0xAB54: 0x4FCA, //CJK UNIFIED IDEOGRAPH - 0xAB55: 0x4FD7, //CJK UNIFIED IDEOGRAPH - 0xAB56: 0x4FAE, //CJK UNIFIED IDEOGRAPH - 0xAB57: 0x4FD0, //CJK UNIFIED IDEOGRAPH - 0xAB58: 0x4FC4, //CJK UNIFIED IDEOGRAPH - 0xAB59: 0x4FC2, //CJK UNIFIED IDEOGRAPH - 0xAB5A: 0x4FDA, //CJK UNIFIED IDEOGRAPH - 0xAB5B: 0x4FCE, //CJK UNIFIED IDEOGRAPH - 0xAB5C: 0x4FDE, //CJK UNIFIED IDEOGRAPH - 0xAB5D: 0x4FB7, //CJK UNIFIED IDEOGRAPH - 0xAB5E: 0x5157, //CJK UNIFIED IDEOGRAPH - 0xAB5F: 0x5192, //CJK UNIFIED IDEOGRAPH - 0xAB60: 0x5191, //CJK UNIFIED IDEOGRAPH - 0xAB61: 0x51A0, //CJK UNIFIED IDEOGRAPH - 0xAB62: 0x524E, //CJK UNIFIED IDEOGRAPH - 0xAB63: 0x5243, //CJK UNIFIED IDEOGRAPH - 0xAB64: 0x524A, //CJK UNIFIED IDEOGRAPH - 0xAB65: 0x524D, //CJK UNIFIED IDEOGRAPH - 0xAB66: 0x524C, //CJK UNIFIED IDEOGRAPH - 0xAB67: 0x524B, //CJK UNIFIED IDEOGRAPH - 0xAB68: 0x5247, //CJK UNIFIED IDEOGRAPH - 0xAB69: 0x52C7, //CJK UNIFIED IDEOGRAPH - 0xAB6A: 0x52C9, //CJK UNIFIED IDEOGRAPH - 0xAB6B: 0x52C3, //CJK UNIFIED IDEOGRAPH - 0xAB6C: 0x52C1, //CJK UNIFIED IDEOGRAPH - 0xAB6D: 0x530D, //CJK UNIFIED IDEOGRAPH - 0xAB6E: 0x5357, //CJK UNIFIED IDEOGRAPH - 0xAB6F: 0x537B, //CJK UNIFIED IDEOGRAPH - 0xAB70: 0x539A, //CJK UNIFIED IDEOGRAPH - 0xAB71: 0x53DB, //CJK UNIFIED IDEOGRAPH - 0xAB72: 0x54AC, //CJK UNIFIED IDEOGRAPH - 0xAB73: 0x54C0, //CJK UNIFIED IDEOGRAPH - 0xAB74: 0x54A8, //CJK UNIFIED IDEOGRAPH - 0xAB75: 0x54CE, //CJK UNIFIED IDEOGRAPH - 0xAB76: 0x54C9, //CJK UNIFIED IDEOGRAPH - 0xAB77: 0x54B8, //CJK UNIFIED IDEOGRAPH - 0xAB78: 0x54A6, //CJK UNIFIED IDEOGRAPH - 0xAB79: 0x54B3, //CJK UNIFIED IDEOGRAPH - 0xAB7A: 0x54C7, //CJK UNIFIED IDEOGRAPH - 0xAB7B: 0x54C2, //CJK UNIFIED IDEOGRAPH - 0xAB7C: 0x54BD, //CJK UNIFIED IDEOGRAPH - 0xAB7D: 0x54AA, //CJK UNIFIED IDEOGRAPH - 0xAB7E: 0x54C1, //CJK UNIFIED IDEOGRAPH - 0xABA1: 0x54C4, //CJK UNIFIED IDEOGRAPH - 0xABA2: 0x54C8, //CJK UNIFIED IDEOGRAPH - 0xABA3: 0x54AF, //CJK UNIFIED IDEOGRAPH - 0xABA4: 0x54AB, //CJK UNIFIED IDEOGRAPH - 0xABA5: 0x54B1, //CJK UNIFIED IDEOGRAPH - 0xABA6: 0x54BB, //CJK UNIFIED IDEOGRAPH - 0xABA7: 0x54A9, //CJK UNIFIED IDEOGRAPH - 0xABA8: 0x54A7, //CJK UNIFIED IDEOGRAPH - 0xABA9: 0x54BF, //CJK UNIFIED IDEOGRAPH - 0xABAA: 0x56FF, //CJK UNIFIED IDEOGRAPH - 0xABAB: 0x5782, //CJK UNIFIED IDEOGRAPH - 0xABAC: 0x578B, //CJK UNIFIED IDEOGRAPH - 0xABAD: 0x57A0, //CJK UNIFIED IDEOGRAPH - 0xABAE: 0x57A3, //CJK UNIFIED IDEOGRAPH - 0xABAF: 0x57A2, //CJK UNIFIED IDEOGRAPH - 0xABB0: 0x57CE, //CJK UNIFIED IDEOGRAPH - 0xABB1: 0x57AE, //CJK UNIFIED IDEOGRAPH - 0xABB2: 0x5793, //CJK UNIFIED IDEOGRAPH - 0xABB3: 0x5955, //CJK UNIFIED IDEOGRAPH - 0xABB4: 0x5951, //CJK UNIFIED IDEOGRAPH - 0xABB5: 0x594F, //CJK UNIFIED IDEOGRAPH - 0xABB6: 0x594E, //CJK UNIFIED IDEOGRAPH - 0xABB7: 0x5950, //CJK UNIFIED IDEOGRAPH - 0xABB8: 0x59DC, //CJK UNIFIED IDEOGRAPH - 0xABB9: 0x59D8, //CJK UNIFIED IDEOGRAPH - 0xABBA: 0x59FF, //CJK UNIFIED IDEOGRAPH - 0xABBB: 0x59E3, //CJK UNIFIED IDEOGRAPH - 0xABBC: 0x59E8, //CJK UNIFIED IDEOGRAPH - 0xABBD: 0x5A03, //CJK UNIFIED IDEOGRAPH - 0xABBE: 0x59E5, //CJK UNIFIED IDEOGRAPH - 0xABBF: 0x59EA, //CJK UNIFIED IDEOGRAPH - 0xABC0: 0x59DA, //CJK UNIFIED IDEOGRAPH - 0xABC1: 0x59E6, //CJK UNIFIED IDEOGRAPH - 0xABC2: 0x5A01, //CJK UNIFIED IDEOGRAPH - 0xABC3: 0x59FB, //CJK UNIFIED IDEOGRAPH - 0xABC4: 0x5B69, //CJK UNIFIED IDEOGRAPH - 0xABC5: 0x5BA3, //CJK UNIFIED IDEOGRAPH - 0xABC6: 0x5BA6, //CJK UNIFIED IDEOGRAPH - 0xABC7: 0x5BA4, //CJK UNIFIED IDEOGRAPH - 0xABC8: 0x5BA2, //CJK UNIFIED IDEOGRAPH - 0xABC9: 0x5BA5, //CJK UNIFIED IDEOGRAPH - 0xABCA: 0x5C01, //CJK UNIFIED IDEOGRAPH - 0xABCB: 0x5C4E, //CJK UNIFIED IDEOGRAPH - 0xABCC: 0x5C4F, //CJK UNIFIED IDEOGRAPH - 0xABCD: 0x5C4D, //CJK UNIFIED IDEOGRAPH - 0xABCE: 0x5C4B, //CJK UNIFIED IDEOGRAPH - 0xABCF: 0x5CD9, //CJK UNIFIED IDEOGRAPH - 0xABD0: 0x5CD2, //CJK UNIFIED IDEOGRAPH - 0xABD1: 0x5DF7, //CJK UNIFIED IDEOGRAPH - 0xABD2: 0x5E1D, //CJK UNIFIED IDEOGRAPH - 0xABD3: 0x5E25, //CJK UNIFIED IDEOGRAPH - 0xABD4: 0x5E1F, //CJK UNIFIED IDEOGRAPH - 0xABD5: 0x5E7D, //CJK UNIFIED IDEOGRAPH - 0xABD6: 0x5EA0, //CJK UNIFIED IDEOGRAPH - 0xABD7: 0x5EA6, //CJK UNIFIED IDEOGRAPH - 0xABD8: 0x5EFA, //CJK UNIFIED IDEOGRAPH - 0xABD9: 0x5F08, //CJK UNIFIED IDEOGRAPH - 0xABDA: 0x5F2D, //CJK UNIFIED IDEOGRAPH - 0xABDB: 0x5F65, //CJK UNIFIED IDEOGRAPH - 0xABDC: 0x5F88, //CJK UNIFIED IDEOGRAPH - 0xABDD: 0x5F85, //CJK UNIFIED IDEOGRAPH - 0xABDE: 0x5F8A, //CJK UNIFIED IDEOGRAPH - 0xABDF: 0x5F8B, //CJK UNIFIED IDEOGRAPH - 0xABE0: 0x5F87, //CJK UNIFIED IDEOGRAPH - 0xABE1: 0x5F8C, //CJK UNIFIED IDEOGRAPH - 0xABE2: 0x5F89, //CJK UNIFIED IDEOGRAPH - 0xABE3: 0x6012, //CJK UNIFIED IDEOGRAPH - 0xABE4: 0x601D, //CJK UNIFIED IDEOGRAPH - 0xABE5: 0x6020, //CJK UNIFIED IDEOGRAPH - 0xABE6: 0x6025, //CJK UNIFIED IDEOGRAPH - 0xABE7: 0x600E, //CJK UNIFIED IDEOGRAPH - 0xABE8: 0x6028, //CJK UNIFIED IDEOGRAPH - 0xABE9: 0x604D, //CJK UNIFIED IDEOGRAPH - 0xABEA: 0x6070, //CJK UNIFIED IDEOGRAPH - 0xABEB: 0x6068, //CJK UNIFIED IDEOGRAPH - 0xABEC: 0x6062, //CJK UNIFIED IDEOGRAPH - 0xABED: 0x6046, //CJK UNIFIED IDEOGRAPH - 0xABEE: 0x6043, //CJK UNIFIED IDEOGRAPH - 0xABEF: 0x606C, //CJK UNIFIED IDEOGRAPH - 0xABF0: 0x606B, //CJK UNIFIED IDEOGRAPH - 0xABF1: 0x606A, //CJK UNIFIED IDEOGRAPH - 0xABF2: 0x6064, //CJK UNIFIED IDEOGRAPH - 0xABF3: 0x6241, //CJK UNIFIED IDEOGRAPH - 0xABF4: 0x62DC, //CJK UNIFIED IDEOGRAPH - 0xABF5: 0x6316, //CJK UNIFIED IDEOGRAPH - 0xABF6: 0x6309, //CJK UNIFIED IDEOGRAPH - 0xABF7: 0x62FC, //CJK UNIFIED IDEOGRAPH - 0xABF8: 0x62ED, //CJK UNIFIED IDEOGRAPH - 0xABF9: 0x6301, //CJK UNIFIED IDEOGRAPH - 0xABFA: 0x62EE, //CJK UNIFIED IDEOGRAPH - 0xABFB: 0x62FD, //CJK UNIFIED IDEOGRAPH - 0xABFC: 0x6307, //CJK UNIFIED IDEOGRAPH - 0xABFD: 0x62F1, //CJK UNIFIED IDEOGRAPH - 0xABFE: 0x62F7, //CJK UNIFIED IDEOGRAPH - 0xAC40: 0x62EF, //CJK UNIFIED IDEOGRAPH - 0xAC41: 0x62EC, //CJK UNIFIED IDEOGRAPH - 0xAC42: 0x62FE, //CJK UNIFIED IDEOGRAPH - 0xAC43: 0x62F4, //CJK UNIFIED IDEOGRAPH - 0xAC44: 0x6311, //CJK UNIFIED IDEOGRAPH - 0xAC45: 0x6302, //CJK UNIFIED IDEOGRAPH - 0xAC46: 0x653F, //CJK UNIFIED IDEOGRAPH - 0xAC47: 0x6545, //CJK UNIFIED IDEOGRAPH - 0xAC48: 0x65AB, //CJK UNIFIED IDEOGRAPH - 0xAC49: 0x65BD, //CJK UNIFIED IDEOGRAPH - 0xAC4A: 0x65E2, //CJK UNIFIED IDEOGRAPH - 0xAC4B: 0x6625, //CJK UNIFIED IDEOGRAPH - 0xAC4C: 0x662D, //CJK UNIFIED IDEOGRAPH - 0xAC4D: 0x6620, //CJK UNIFIED IDEOGRAPH - 0xAC4E: 0x6627, //CJK UNIFIED IDEOGRAPH - 0xAC4F: 0x662F, //CJK UNIFIED IDEOGRAPH - 0xAC50: 0x661F, //CJK UNIFIED IDEOGRAPH - 0xAC51: 0x6628, //CJK UNIFIED IDEOGRAPH - 0xAC52: 0x6631, //CJK UNIFIED IDEOGRAPH - 0xAC53: 0x6624, //CJK UNIFIED IDEOGRAPH - 0xAC54: 0x66F7, //CJK UNIFIED IDEOGRAPH - 0xAC55: 0x67FF, //CJK UNIFIED IDEOGRAPH - 0xAC56: 0x67D3, //CJK UNIFIED IDEOGRAPH - 0xAC57: 0x67F1, //CJK UNIFIED IDEOGRAPH - 0xAC58: 0x67D4, //CJK UNIFIED IDEOGRAPH - 0xAC59: 0x67D0, //CJK UNIFIED IDEOGRAPH - 0xAC5A: 0x67EC, //CJK UNIFIED IDEOGRAPH - 0xAC5B: 0x67B6, //CJK UNIFIED IDEOGRAPH - 0xAC5C: 0x67AF, //CJK UNIFIED IDEOGRAPH - 0xAC5D: 0x67F5, //CJK UNIFIED IDEOGRAPH - 0xAC5E: 0x67E9, //CJK UNIFIED IDEOGRAPH - 0xAC5F: 0x67EF, //CJK UNIFIED IDEOGRAPH - 0xAC60: 0x67C4, //CJK UNIFIED IDEOGRAPH - 0xAC61: 0x67D1, //CJK UNIFIED IDEOGRAPH - 0xAC62: 0x67B4, //CJK UNIFIED IDEOGRAPH - 0xAC63: 0x67DA, //CJK UNIFIED IDEOGRAPH - 0xAC64: 0x67E5, //CJK UNIFIED IDEOGRAPH - 0xAC65: 0x67B8, //CJK UNIFIED IDEOGRAPH - 0xAC66: 0x67CF, //CJK UNIFIED IDEOGRAPH - 0xAC67: 0x67DE, //CJK UNIFIED IDEOGRAPH - 0xAC68: 0x67F3, //CJK UNIFIED IDEOGRAPH - 0xAC69: 0x67B0, //CJK UNIFIED IDEOGRAPH - 0xAC6A: 0x67D9, //CJK UNIFIED IDEOGRAPH - 0xAC6B: 0x67E2, //CJK UNIFIED IDEOGRAPH - 0xAC6C: 0x67DD, //CJK UNIFIED IDEOGRAPH - 0xAC6D: 0x67D2, //CJK UNIFIED IDEOGRAPH - 0xAC6E: 0x6B6A, //CJK UNIFIED IDEOGRAPH - 0xAC6F: 0x6B83, //CJK UNIFIED IDEOGRAPH - 0xAC70: 0x6B86, //CJK UNIFIED IDEOGRAPH - 0xAC71: 0x6BB5, //CJK UNIFIED IDEOGRAPH - 0xAC72: 0x6BD2, //CJK UNIFIED IDEOGRAPH - 0xAC73: 0x6BD7, //CJK UNIFIED IDEOGRAPH - 0xAC74: 0x6C1F, //CJK UNIFIED IDEOGRAPH - 0xAC75: 0x6CC9, //CJK UNIFIED IDEOGRAPH - 0xAC76: 0x6D0B, //CJK UNIFIED IDEOGRAPH - 0xAC77: 0x6D32, //CJK UNIFIED IDEOGRAPH - 0xAC78: 0x6D2A, //CJK UNIFIED IDEOGRAPH - 0xAC79: 0x6D41, //CJK UNIFIED IDEOGRAPH - 0xAC7A: 0x6D25, //CJK UNIFIED IDEOGRAPH - 0xAC7B: 0x6D0C, //CJK UNIFIED IDEOGRAPH - 0xAC7C: 0x6D31, //CJK UNIFIED IDEOGRAPH - 0xAC7D: 0x6D1E, //CJK UNIFIED IDEOGRAPH - 0xAC7E: 0x6D17, //CJK UNIFIED IDEOGRAPH - 0xACA1: 0x6D3B, //CJK UNIFIED IDEOGRAPH - 0xACA2: 0x6D3D, //CJK UNIFIED IDEOGRAPH - 0xACA3: 0x6D3E, //CJK UNIFIED IDEOGRAPH - 0xACA4: 0x6D36, //CJK UNIFIED IDEOGRAPH - 0xACA5: 0x6D1B, //CJK UNIFIED IDEOGRAPH - 0xACA6: 0x6CF5, //CJK UNIFIED IDEOGRAPH - 0xACA7: 0x6D39, //CJK UNIFIED IDEOGRAPH - 0xACA8: 0x6D27, //CJK UNIFIED IDEOGRAPH - 0xACA9: 0x6D38, //CJK UNIFIED IDEOGRAPH - 0xACAA: 0x6D29, //CJK UNIFIED IDEOGRAPH - 0xACAB: 0x6D2E, //CJK UNIFIED IDEOGRAPH - 0xACAC: 0x6D35, //CJK UNIFIED IDEOGRAPH - 0xACAD: 0x6D0E, //CJK UNIFIED IDEOGRAPH - 0xACAE: 0x6D2B, //CJK UNIFIED IDEOGRAPH - 0xACAF: 0x70AB, //CJK UNIFIED IDEOGRAPH - 0xACB0: 0x70BA, //CJK UNIFIED IDEOGRAPH - 0xACB1: 0x70B3, //CJK UNIFIED IDEOGRAPH - 0xACB2: 0x70AC, //CJK UNIFIED IDEOGRAPH - 0xACB3: 0x70AF, //CJK UNIFIED IDEOGRAPH - 0xACB4: 0x70AD, //CJK UNIFIED IDEOGRAPH - 0xACB5: 0x70B8, //CJK UNIFIED IDEOGRAPH - 0xACB6: 0x70AE, //CJK UNIFIED IDEOGRAPH - 0xACB7: 0x70A4, //CJK UNIFIED IDEOGRAPH - 0xACB8: 0x7230, //CJK UNIFIED IDEOGRAPH - 0xACB9: 0x7272, //CJK UNIFIED IDEOGRAPH - 0xACBA: 0x726F, //CJK UNIFIED IDEOGRAPH - 0xACBB: 0x7274, //CJK UNIFIED IDEOGRAPH - 0xACBC: 0x72E9, //CJK UNIFIED IDEOGRAPH - 0xACBD: 0x72E0, //CJK UNIFIED IDEOGRAPH - 0xACBE: 0x72E1, //CJK UNIFIED IDEOGRAPH - 0xACBF: 0x73B7, //CJK UNIFIED IDEOGRAPH - 0xACC0: 0x73CA, //CJK UNIFIED IDEOGRAPH - 0xACC1: 0x73BB, //CJK UNIFIED IDEOGRAPH - 0xACC2: 0x73B2, //CJK UNIFIED IDEOGRAPH - 0xACC3: 0x73CD, //CJK UNIFIED IDEOGRAPH - 0xACC4: 0x73C0, //CJK UNIFIED IDEOGRAPH - 0xACC5: 0x73B3, //CJK UNIFIED IDEOGRAPH - 0xACC6: 0x751A, //CJK UNIFIED IDEOGRAPH - 0xACC7: 0x752D, //CJK UNIFIED IDEOGRAPH - 0xACC8: 0x754F, //CJK UNIFIED IDEOGRAPH - 0xACC9: 0x754C, //CJK UNIFIED IDEOGRAPH - 0xACCA: 0x754E, //CJK UNIFIED IDEOGRAPH - 0xACCB: 0x754B, //CJK UNIFIED IDEOGRAPH - 0xACCC: 0x75AB, //CJK UNIFIED IDEOGRAPH - 0xACCD: 0x75A4, //CJK UNIFIED IDEOGRAPH - 0xACCE: 0x75A5, //CJK UNIFIED IDEOGRAPH - 0xACCF: 0x75A2, //CJK UNIFIED IDEOGRAPH - 0xACD0: 0x75A3, //CJK UNIFIED IDEOGRAPH - 0xACD1: 0x7678, //CJK UNIFIED IDEOGRAPH - 0xACD2: 0x7686, //CJK UNIFIED IDEOGRAPH - 0xACD3: 0x7687, //CJK UNIFIED IDEOGRAPH - 0xACD4: 0x7688, //CJK UNIFIED IDEOGRAPH - 0xACD5: 0x76C8, //CJK UNIFIED IDEOGRAPH - 0xACD6: 0x76C6, //CJK UNIFIED IDEOGRAPH - 0xACD7: 0x76C3, //CJK UNIFIED IDEOGRAPH - 0xACD8: 0x76C5, //CJK UNIFIED IDEOGRAPH - 0xACD9: 0x7701, //CJK UNIFIED IDEOGRAPH - 0xACDA: 0x76F9, //CJK UNIFIED IDEOGRAPH - 0xACDB: 0x76F8, //CJK UNIFIED IDEOGRAPH - 0xACDC: 0x7709, //CJK UNIFIED IDEOGRAPH - 0xACDD: 0x770B, //CJK UNIFIED IDEOGRAPH - 0xACDE: 0x76FE, //CJK UNIFIED IDEOGRAPH - 0xACDF: 0x76FC, //CJK UNIFIED IDEOGRAPH - 0xACE0: 0x7707, //CJK UNIFIED IDEOGRAPH - 0xACE1: 0x77DC, //CJK UNIFIED IDEOGRAPH - 0xACE2: 0x7802, //CJK UNIFIED IDEOGRAPH - 0xACE3: 0x7814, //CJK UNIFIED IDEOGRAPH - 0xACE4: 0x780C, //CJK UNIFIED IDEOGRAPH - 0xACE5: 0x780D, //CJK UNIFIED IDEOGRAPH - 0xACE6: 0x7946, //CJK UNIFIED IDEOGRAPH - 0xACE7: 0x7949, //CJK UNIFIED IDEOGRAPH - 0xACE8: 0x7948, //CJK UNIFIED IDEOGRAPH - 0xACE9: 0x7947, //CJK UNIFIED IDEOGRAPH - 0xACEA: 0x79B9, //CJK UNIFIED IDEOGRAPH - 0xACEB: 0x79BA, //CJK UNIFIED IDEOGRAPH - 0xACEC: 0x79D1, //CJK UNIFIED IDEOGRAPH - 0xACED: 0x79D2, //CJK UNIFIED IDEOGRAPH - 0xACEE: 0x79CB, //CJK UNIFIED IDEOGRAPH - 0xACEF: 0x7A7F, //CJK UNIFIED IDEOGRAPH - 0xACF0: 0x7A81, //CJK UNIFIED IDEOGRAPH - 0xACF1: 0x7AFF, //CJK UNIFIED IDEOGRAPH - 0xACF2: 0x7AFD, //CJK UNIFIED IDEOGRAPH - 0xACF3: 0x7C7D, //CJK UNIFIED IDEOGRAPH - 0xACF4: 0x7D02, //CJK UNIFIED IDEOGRAPH - 0xACF5: 0x7D05, //CJK UNIFIED IDEOGRAPH - 0xACF6: 0x7D00, //CJK UNIFIED IDEOGRAPH - 0xACF7: 0x7D09, //CJK UNIFIED IDEOGRAPH - 0xACF8: 0x7D07, //CJK UNIFIED IDEOGRAPH - 0xACF9: 0x7D04, //CJK UNIFIED IDEOGRAPH - 0xACFA: 0x7D06, //CJK UNIFIED IDEOGRAPH - 0xACFB: 0x7F38, //CJK UNIFIED IDEOGRAPH - 0xACFC: 0x7F8E, //CJK UNIFIED IDEOGRAPH - 0xACFD: 0x7FBF, //CJK UNIFIED IDEOGRAPH - 0xACFE: 0x8004, //CJK UNIFIED IDEOGRAPH - 0xAD40: 0x8010, //CJK UNIFIED IDEOGRAPH - 0xAD41: 0x800D, //CJK UNIFIED IDEOGRAPH - 0xAD42: 0x8011, //CJK UNIFIED IDEOGRAPH - 0xAD43: 0x8036, //CJK UNIFIED IDEOGRAPH - 0xAD44: 0x80D6, //CJK UNIFIED IDEOGRAPH - 0xAD45: 0x80E5, //CJK UNIFIED IDEOGRAPH - 0xAD46: 0x80DA, //CJK UNIFIED IDEOGRAPH - 0xAD47: 0x80C3, //CJK UNIFIED IDEOGRAPH - 0xAD48: 0x80C4, //CJK UNIFIED IDEOGRAPH - 0xAD49: 0x80CC, //CJK UNIFIED IDEOGRAPH - 0xAD4A: 0x80E1, //CJK UNIFIED IDEOGRAPH - 0xAD4B: 0x80DB, //CJK UNIFIED IDEOGRAPH - 0xAD4C: 0x80CE, //CJK UNIFIED IDEOGRAPH - 0xAD4D: 0x80DE, //CJK UNIFIED IDEOGRAPH - 0xAD4E: 0x80E4, //CJK UNIFIED IDEOGRAPH - 0xAD4F: 0x80DD, //CJK UNIFIED IDEOGRAPH - 0xAD50: 0x81F4, //CJK UNIFIED IDEOGRAPH - 0xAD51: 0x8222, //CJK UNIFIED IDEOGRAPH - 0xAD52: 0x82E7, //CJK UNIFIED IDEOGRAPH - 0xAD53: 0x8303, //CJK UNIFIED IDEOGRAPH - 0xAD54: 0x8305, //CJK UNIFIED IDEOGRAPH - 0xAD55: 0x82E3, //CJK UNIFIED IDEOGRAPH - 0xAD56: 0x82DB, //CJK UNIFIED IDEOGRAPH - 0xAD57: 0x82E6, //CJK UNIFIED IDEOGRAPH - 0xAD58: 0x8304, //CJK UNIFIED IDEOGRAPH - 0xAD59: 0x82E5, //CJK UNIFIED IDEOGRAPH - 0xAD5A: 0x8302, //CJK UNIFIED IDEOGRAPH - 0xAD5B: 0x8309, //CJK UNIFIED IDEOGRAPH - 0xAD5C: 0x82D2, //CJK UNIFIED IDEOGRAPH - 0xAD5D: 0x82D7, //CJK UNIFIED IDEOGRAPH - 0xAD5E: 0x82F1, //CJK UNIFIED IDEOGRAPH - 0xAD5F: 0x8301, //CJK UNIFIED IDEOGRAPH - 0xAD60: 0x82DC, //CJK UNIFIED IDEOGRAPH - 0xAD61: 0x82D4, //CJK UNIFIED IDEOGRAPH - 0xAD62: 0x82D1, //CJK UNIFIED IDEOGRAPH - 0xAD63: 0x82DE, //CJK UNIFIED IDEOGRAPH - 0xAD64: 0x82D3, //CJK UNIFIED IDEOGRAPH - 0xAD65: 0x82DF, //CJK UNIFIED IDEOGRAPH - 0xAD66: 0x82EF, //CJK UNIFIED IDEOGRAPH - 0xAD67: 0x8306, //CJK UNIFIED IDEOGRAPH - 0xAD68: 0x8650, //CJK UNIFIED IDEOGRAPH - 0xAD69: 0x8679, //CJK UNIFIED IDEOGRAPH - 0xAD6A: 0x867B, //CJK UNIFIED IDEOGRAPH - 0xAD6B: 0x867A, //CJK UNIFIED IDEOGRAPH - 0xAD6C: 0x884D, //CJK UNIFIED IDEOGRAPH - 0xAD6D: 0x886B, //CJK UNIFIED IDEOGRAPH - 0xAD6E: 0x8981, //CJK UNIFIED IDEOGRAPH - 0xAD6F: 0x89D4, //CJK UNIFIED IDEOGRAPH - 0xAD70: 0x8A08, //CJK UNIFIED IDEOGRAPH - 0xAD71: 0x8A02, //CJK UNIFIED IDEOGRAPH - 0xAD72: 0x8A03, //CJK UNIFIED IDEOGRAPH - 0xAD73: 0x8C9E, //CJK UNIFIED IDEOGRAPH - 0xAD74: 0x8CA0, //CJK UNIFIED IDEOGRAPH - 0xAD75: 0x8D74, //CJK UNIFIED IDEOGRAPH - 0xAD76: 0x8D73, //CJK UNIFIED IDEOGRAPH - 0xAD77: 0x8DB4, //CJK UNIFIED IDEOGRAPH - 0xAD78: 0x8ECD, //CJK UNIFIED IDEOGRAPH - 0xAD79: 0x8ECC, //CJK UNIFIED IDEOGRAPH - 0xAD7A: 0x8FF0, //CJK UNIFIED IDEOGRAPH - 0xAD7B: 0x8FE6, //CJK UNIFIED IDEOGRAPH - 0xAD7C: 0x8FE2, //CJK UNIFIED IDEOGRAPH - 0xAD7D: 0x8FEA, //CJK UNIFIED IDEOGRAPH - 0xAD7E: 0x8FE5, //CJK UNIFIED IDEOGRAPH - 0xADA1: 0x8FED, //CJK UNIFIED IDEOGRAPH - 0xADA2: 0x8FEB, //CJK UNIFIED IDEOGRAPH - 0xADA3: 0x8FE4, //CJK UNIFIED IDEOGRAPH - 0xADA4: 0x8FE8, //CJK UNIFIED IDEOGRAPH - 0xADA5: 0x90CA, //CJK UNIFIED IDEOGRAPH - 0xADA6: 0x90CE, //CJK UNIFIED IDEOGRAPH - 0xADA7: 0x90C1, //CJK UNIFIED IDEOGRAPH - 0xADA8: 0x90C3, //CJK UNIFIED IDEOGRAPH - 0xADA9: 0x914B, //CJK UNIFIED IDEOGRAPH - 0xADAA: 0x914A, //CJK UNIFIED IDEOGRAPH - 0xADAB: 0x91CD, //CJK UNIFIED IDEOGRAPH - 0xADAC: 0x9582, //CJK UNIFIED IDEOGRAPH - 0xADAD: 0x9650, //CJK UNIFIED IDEOGRAPH - 0xADAE: 0x964B, //CJK UNIFIED IDEOGRAPH - 0xADAF: 0x964C, //CJK UNIFIED IDEOGRAPH - 0xADB0: 0x964D, //CJK UNIFIED IDEOGRAPH - 0xADB1: 0x9762, //CJK UNIFIED IDEOGRAPH - 0xADB2: 0x9769, //CJK UNIFIED IDEOGRAPH - 0xADB3: 0x97CB, //CJK UNIFIED IDEOGRAPH - 0xADB4: 0x97ED, //CJK UNIFIED IDEOGRAPH - 0xADB5: 0x97F3, //CJK UNIFIED IDEOGRAPH - 0xADB6: 0x9801, //CJK UNIFIED IDEOGRAPH - 0xADB7: 0x98A8, //CJK UNIFIED IDEOGRAPH - 0xADB8: 0x98DB, //CJK UNIFIED IDEOGRAPH - 0xADB9: 0x98DF, //CJK UNIFIED IDEOGRAPH - 0xADBA: 0x9996, //CJK UNIFIED IDEOGRAPH - 0xADBB: 0x9999, //CJK UNIFIED IDEOGRAPH - 0xADBC: 0x4E58, //CJK UNIFIED IDEOGRAPH - 0xADBD: 0x4EB3, //CJK UNIFIED IDEOGRAPH - 0xADBE: 0x500C, //CJK UNIFIED IDEOGRAPH - 0xADBF: 0x500D, //CJK UNIFIED IDEOGRAPH - 0xADC0: 0x5023, //CJK UNIFIED IDEOGRAPH - 0xADC1: 0x4FEF, //CJK UNIFIED IDEOGRAPH - 0xADC2: 0x5026, //CJK UNIFIED IDEOGRAPH - 0xADC3: 0x5025, //CJK UNIFIED IDEOGRAPH - 0xADC4: 0x4FF8, //CJK UNIFIED IDEOGRAPH - 0xADC5: 0x5029, //CJK UNIFIED IDEOGRAPH - 0xADC6: 0x5016, //CJK UNIFIED IDEOGRAPH - 0xADC7: 0x5006, //CJK UNIFIED IDEOGRAPH - 0xADC8: 0x503C, //CJK UNIFIED IDEOGRAPH - 0xADC9: 0x501F, //CJK UNIFIED IDEOGRAPH - 0xADCA: 0x501A, //CJK UNIFIED IDEOGRAPH - 0xADCB: 0x5012, //CJK UNIFIED IDEOGRAPH - 0xADCC: 0x5011, //CJK UNIFIED IDEOGRAPH - 0xADCD: 0x4FFA, //CJK UNIFIED IDEOGRAPH - 0xADCE: 0x5000, //CJK UNIFIED IDEOGRAPH - 0xADCF: 0x5014, //CJK UNIFIED IDEOGRAPH - 0xADD0: 0x5028, //CJK UNIFIED IDEOGRAPH - 0xADD1: 0x4FF1, //CJK UNIFIED IDEOGRAPH - 0xADD2: 0x5021, //CJK UNIFIED IDEOGRAPH - 0xADD3: 0x500B, //CJK UNIFIED IDEOGRAPH - 0xADD4: 0x5019, //CJK UNIFIED IDEOGRAPH - 0xADD5: 0x5018, //CJK UNIFIED IDEOGRAPH - 0xADD6: 0x4FF3, //CJK UNIFIED IDEOGRAPH - 0xADD7: 0x4FEE, //CJK UNIFIED IDEOGRAPH - 0xADD8: 0x502D, //CJK UNIFIED IDEOGRAPH - 0xADD9: 0x502A, //CJK UNIFIED IDEOGRAPH - 0xADDA: 0x4FFE, //CJK UNIFIED IDEOGRAPH - 0xADDB: 0x502B, //CJK UNIFIED IDEOGRAPH - 0xADDC: 0x5009, //CJK UNIFIED IDEOGRAPH - 0xADDD: 0x517C, //CJK UNIFIED IDEOGRAPH - 0xADDE: 0x51A4, //CJK UNIFIED IDEOGRAPH - 0xADDF: 0x51A5, //CJK UNIFIED IDEOGRAPH - 0xADE0: 0x51A2, //CJK UNIFIED IDEOGRAPH - 0xADE1: 0x51CD, //CJK UNIFIED IDEOGRAPH - 0xADE2: 0x51CC, //CJK UNIFIED IDEOGRAPH - 0xADE3: 0x51C6, //CJK UNIFIED IDEOGRAPH - 0xADE4: 0x51CB, //CJK UNIFIED IDEOGRAPH - 0xADE5: 0x5256, //CJK UNIFIED IDEOGRAPH - 0xADE6: 0x525C, //CJK UNIFIED IDEOGRAPH - 0xADE7: 0x5254, //CJK UNIFIED IDEOGRAPH - 0xADE8: 0x525B, //CJK UNIFIED IDEOGRAPH - 0xADE9: 0x525D, //CJK UNIFIED IDEOGRAPH - 0xADEA: 0x532A, //CJK UNIFIED IDEOGRAPH - 0xADEB: 0x537F, //CJK UNIFIED IDEOGRAPH - 0xADEC: 0x539F, //CJK UNIFIED IDEOGRAPH - 0xADED: 0x539D, //CJK UNIFIED IDEOGRAPH - 0xADEE: 0x53DF, //CJK UNIFIED IDEOGRAPH - 0xADEF: 0x54E8, //CJK UNIFIED IDEOGRAPH - 0xADF0: 0x5510, //CJK UNIFIED IDEOGRAPH - 0xADF1: 0x5501, //CJK UNIFIED IDEOGRAPH - 0xADF2: 0x5537, //CJK UNIFIED IDEOGRAPH - 0xADF3: 0x54FC, //CJK UNIFIED IDEOGRAPH - 0xADF4: 0x54E5, //CJK UNIFIED IDEOGRAPH - 0xADF5: 0x54F2, //CJK UNIFIED IDEOGRAPH - 0xADF6: 0x5506, //CJK UNIFIED IDEOGRAPH - 0xADF7: 0x54FA, //CJK UNIFIED IDEOGRAPH - 0xADF8: 0x5514, //CJK UNIFIED IDEOGRAPH - 0xADF9: 0x54E9, //CJK UNIFIED IDEOGRAPH - 0xADFA: 0x54ED, //CJK UNIFIED IDEOGRAPH - 0xADFB: 0x54E1, //CJK UNIFIED IDEOGRAPH - 0xADFC: 0x5509, //CJK UNIFIED IDEOGRAPH - 0xADFD: 0x54EE, //CJK UNIFIED IDEOGRAPH - 0xADFE: 0x54EA, //CJK UNIFIED IDEOGRAPH - 0xAE40: 0x54E6, //CJK UNIFIED IDEOGRAPH - 0xAE41: 0x5527, //CJK UNIFIED IDEOGRAPH - 0xAE42: 0x5507, //CJK UNIFIED IDEOGRAPH - 0xAE43: 0x54FD, //CJK UNIFIED IDEOGRAPH - 0xAE44: 0x550F, //CJK UNIFIED IDEOGRAPH - 0xAE45: 0x5703, //CJK UNIFIED IDEOGRAPH - 0xAE46: 0x5704, //CJK UNIFIED IDEOGRAPH - 0xAE47: 0x57C2, //CJK UNIFIED IDEOGRAPH - 0xAE48: 0x57D4, //CJK UNIFIED IDEOGRAPH - 0xAE49: 0x57CB, //CJK UNIFIED IDEOGRAPH - 0xAE4A: 0x57C3, //CJK UNIFIED IDEOGRAPH - 0xAE4B: 0x5809, //CJK UNIFIED IDEOGRAPH - 0xAE4C: 0x590F, //CJK UNIFIED IDEOGRAPH - 0xAE4D: 0x5957, //CJK UNIFIED IDEOGRAPH - 0xAE4E: 0x5958, //CJK UNIFIED IDEOGRAPH - 0xAE4F: 0x595A, //CJK UNIFIED IDEOGRAPH - 0xAE50: 0x5A11, //CJK UNIFIED IDEOGRAPH - 0xAE51: 0x5A18, //CJK UNIFIED IDEOGRAPH - 0xAE52: 0x5A1C, //CJK UNIFIED IDEOGRAPH - 0xAE53: 0x5A1F, //CJK UNIFIED IDEOGRAPH - 0xAE54: 0x5A1B, //CJK UNIFIED IDEOGRAPH - 0xAE55: 0x5A13, //CJK UNIFIED IDEOGRAPH - 0xAE56: 0x59EC, //CJK UNIFIED IDEOGRAPH - 0xAE57: 0x5A20, //CJK UNIFIED IDEOGRAPH - 0xAE58: 0x5A23, //CJK UNIFIED IDEOGRAPH - 0xAE59: 0x5A29, //CJK UNIFIED IDEOGRAPH - 0xAE5A: 0x5A25, //CJK UNIFIED IDEOGRAPH - 0xAE5B: 0x5A0C, //CJK UNIFIED IDEOGRAPH - 0xAE5C: 0x5A09, //CJK UNIFIED IDEOGRAPH - 0xAE5D: 0x5B6B, //CJK UNIFIED IDEOGRAPH - 0xAE5E: 0x5C58, //CJK UNIFIED IDEOGRAPH - 0xAE5F: 0x5BB0, //CJK UNIFIED IDEOGRAPH - 0xAE60: 0x5BB3, //CJK UNIFIED IDEOGRAPH - 0xAE61: 0x5BB6, //CJK UNIFIED IDEOGRAPH - 0xAE62: 0x5BB4, //CJK UNIFIED IDEOGRAPH - 0xAE63: 0x5BAE, //CJK UNIFIED IDEOGRAPH - 0xAE64: 0x5BB5, //CJK UNIFIED IDEOGRAPH - 0xAE65: 0x5BB9, //CJK UNIFIED IDEOGRAPH - 0xAE66: 0x5BB8, //CJK UNIFIED IDEOGRAPH - 0xAE67: 0x5C04, //CJK UNIFIED IDEOGRAPH - 0xAE68: 0x5C51, //CJK UNIFIED IDEOGRAPH - 0xAE69: 0x5C55, //CJK UNIFIED IDEOGRAPH - 0xAE6A: 0x5C50, //CJK UNIFIED IDEOGRAPH - 0xAE6B: 0x5CED, //CJK UNIFIED IDEOGRAPH - 0xAE6C: 0x5CFD, //CJK UNIFIED IDEOGRAPH - 0xAE6D: 0x5CFB, //CJK UNIFIED IDEOGRAPH - 0xAE6E: 0x5CEA, //CJK UNIFIED IDEOGRAPH - 0xAE6F: 0x5CE8, //CJK UNIFIED IDEOGRAPH - 0xAE70: 0x5CF0, //CJK UNIFIED IDEOGRAPH - 0xAE71: 0x5CF6, //CJK UNIFIED IDEOGRAPH - 0xAE72: 0x5D01, //CJK UNIFIED IDEOGRAPH - 0xAE73: 0x5CF4, //CJK UNIFIED IDEOGRAPH - 0xAE74: 0x5DEE, //CJK UNIFIED IDEOGRAPH - 0xAE75: 0x5E2D, //CJK UNIFIED IDEOGRAPH - 0xAE76: 0x5E2B, //CJK UNIFIED IDEOGRAPH - 0xAE77: 0x5EAB, //CJK UNIFIED IDEOGRAPH - 0xAE78: 0x5EAD, //CJK UNIFIED IDEOGRAPH - 0xAE79: 0x5EA7, //CJK UNIFIED IDEOGRAPH - 0xAE7A: 0x5F31, //CJK UNIFIED IDEOGRAPH - 0xAE7B: 0x5F92, //CJK UNIFIED IDEOGRAPH - 0xAE7C: 0x5F91, //CJK UNIFIED IDEOGRAPH - 0xAE7D: 0x5F90, //CJK UNIFIED IDEOGRAPH - 0xAE7E: 0x6059, //CJK UNIFIED IDEOGRAPH - 0xAEA1: 0x6063, //CJK UNIFIED IDEOGRAPH - 0xAEA2: 0x6065, //CJK UNIFIED IDEOGRAPH - 0xAEA3: 0x6050, //CJK UNIFIED IDEOGRAPH - 0xAEA4: 0x6055, //CJK UNIFIED IDEOGRAPH - 0xAEA5: 0x606D, //CJK UNIFIED IDEOGRAPH - 0xAEA6: 0x6069, //CJK UNIFIED IDEOGRAPH - 0xAEA7: 0x606F, //CJK UNIFIED IDEOGRAPH - 0xAEA8: 0x6084, //CJK UNIFIED IDEOGRAPH - 0xAEA9: 0x609F, //CJK UNIFIED IDEOGRAPH - 0xAEAA: 0x609A, //CJK UNIFIED IDEOGRAPH - 0xAEAB: 0x608D, //CJK UNIFIED IDEOGRAPH - 0xAEAC: 0x6094, //CJK UNIFIED IDEOGRAPH - 0xAEAD: 0x608C, //CJK UNIFIED IDEOGRAPH - 0xAEAE: 0x6085, //CJK UNIFIED IDEOGRAPH - 0xAEAF: 0x6096, //CJK UNIFIED IDEOGRAPH - 0xAEB0: 0x6247, //CJK UNIFIED IDEOGRAPH - 0xAEB1: 0x62F3, //CJK UNIFIED IDEOGRAPH - 0xAEB2: 0x6308, //CJK UNIFIED IDEOGRAPH - 0xAEB3: 0x62FF, //CJK UNIFIED IDEOGRAPH - 0xAEB4: 0x634E, //CJK UNIFIED IDEOGRAPH - 0xAEB5: 0x633E, //CJK UNIFIED IDEOGRAPH - 0xAEB6: 0x632F, //CJK UNIFIED IDEOGRAPH - 0xAEB7: 0x6355, //CJK UNIFIED IDEOGRAPH - 0xAEB8: 0x6342, //CJK UNIFIED IDEOGRAPH - 0xAEB9: 0x6346, //CJK UNIFIED IDEOGRAPH - 0xAEBA: 0x634F, //CJK UNIFIED IDEOGRAPH - 0xAEBB: 0x6349, //CJK UNIFIED IDEOGRAPH - 0xAEBC: 0x633A, //CJK UNIFIED IDEOGRAPH - 0xAEBD: 0x6350, //CJK UNIFIED IDEOGRAPH - 0xAEBE: 0x633D, //CJK UNIFIED IDEOGRAPH - 0xAEBF: 0x632A, //CJK UNIFIED IDEOGRAPH - 0xAEC0: 0x632B, //CJK UNIFIED IDEOGRAPH - 0xAEC1: 0x6328, //CJK UNIFIED IDEOGRAPH - 0xAEC2: 0x634D, //CJK UNIFIED IDEOGRAPH - 0xAEC3: 0x634C, //CJK UNIFIED IDEOGRAPH - 0xAEC4: 0x6548, //CJK UNIFIED IDEOGRAPH - 0xAEC5: 0x6549, //CJK UNIFIED IDEOGRAPH - 0xAEC6: 0x6599, //CJK UNIFIED IDEOGRAPH - 0xAEC7: 0x65C1, //CJK UNIFIED IDEOGRAPH - 0xAEC8: 0x65C5, //CJK UNIFIED IDEOGRAPH - 0xAEC9: 0x6642, //CJK UNIFIED IDEOGRAPH - 0xAECA: 0x6649, //CJK UNIFIED IDEOGRAPH - 0xAECB: 0x664F, //CJK UNIFIED IDEOGRAPH - 0xAECC: 0x6643, //CJK UNIFIED IDEOGRAPH - 0xAECD: 0x6652, //CJK UNIFIED IDEOGRAPH - 0xAECE: 0x664C, //CJK UNIFIED IDEOGRAPH - 0xAECF: 0x6645, //CJK UNIFIED IDEOGRAPH - 0xAED0: 0x6641, //CJK UNIFIED IDEOGRAPH - 0xAED1: 0x66F8, //CJK UNIFIED IDEOGRAPH - 0xAED2: 0x6714, //CJK UNIFIED IDEOGRAPH - 0xAED3: 0x6715, //CJK UNIFIED IDEOGRAPH - 0xAED4: 0x6717, //CJK UNIFIED IDEOGRAPH - 0xAED5: 0x6821, //CJK UNIFIED IDEOGRAPH - 0xAED6: 0x6838, //CJK UNIFIED IDEOGRAPH - 0xAED7: 0x6848, //CJK UNIFIED IDEOGRAPH - 0xAED8: 0x6846, //CJK UNIFIED IDEOGRAPH - 0xAED9: 0x6853, //CJK UNIFIED IDEOGRAPH - 0xAEDA: 0x6839, //CJK UNIFIED IDEOGRAPH - 0xAEDB: 0x6842, //CJK UNIFIED IDEOGRAPH - 0xAEDC: 0x6854, //CJK UNIFIED IDEOGRAPH - 0xAEDD: 0x6829, //CJK UNIFIED IDEOGRAPH - 0xAEDE: 0x68B3, //CJK UNIFIED IDEOGRAPH - 0xAEDF: 0x6817, //CJK UNIFIED IDEOGRAPH - 0xAEE0: 0x684C, //CJK UNIFIED IDEOGRAPH - 0xAEE1: 0x6851, //CJK UNIFIED IDEOGRAPH - 0xAEE2: 0x683D, //CJK UNIFIED IDEOGRAPH - 0xAEE3: 0x67F4, //CJK UNIFIED IDEOGRAPH - 0xAEE4: 0x6850, //CJK UNIFIED IDEOGRAPH - 0xAEE5: 0x6840, //CJK UNIFIED IDEOGRAPH - 0xAEE6: 0x683C, //CJK UNIFIED IDEOGRAPH - 0xAEE7: 0x6843, //CJK UNIFIED IDEOGRAPH - 0xAEE8: 0x682A, //CJK UNIFIED IDEOGRAPH - 0xAEE9: 0x6845, //CJK UNIFIED IDEOGRAPH - 0xAEEA: 0x6813, //CJK UNIFIED IDEOGRAPH - 0xAEEB: 0x6818, //CJK UNIFIED IDEOGRAPH - 0xAEEC: 0x6841, //CJK UNIFIED IDEOGRAPH - 0xAEED: 0x6B8A, //CJK UNIFIED IDEOGRAPH - 0xAEEE: 0x6B89, //CJK UNIFIED IDEOGRAPH - 0xAEEF: 0x6BB7, //CJK UNIFIED IDEOGRAPH - 0xAEF0: 0x6C23, //CJK UNIFIED IDEOGRAPH - 0xAEF1: 0x6C27, //CJK UNIFIED IDEOGRAPH - 0xAEF2: 0x6C28, //CJK UNIFIED IDEOGRAPH - 0xAEF3: 0x6C26, //CJK UNIFIED IDEOGRAPH - 0xAEF4: 0x6C24, //CJK UNIFIED IDEOGRAPH - 0xAEF5: 0x6CF0, //CJK UNIFIED IDEOGRAPH - 0xAEF6: 0x6D6A, //CJK UNIFIED IDEOGRAPH - 0xAEF7: 0x6D95, //CJK UNIFIED IDEOGRAPH - 0xAEF8: 0x6D88, //CJK UNIFIED IDEOGRAPH - 0xAEF9: 0x6D87, //CJK UNIFIED IDEOGRAPH - 0xAEFA: 0x6D66, //CJK UNIFIED IDEOGRAPH - 0xAEFB: 0x6D78, //CJK UNIFIED IDEOGRAPH - 0xAEFC: 0x6D77, //CJK UNIFIED IDEOGRAPH - 0xAEFD: 0x6D59, //CJK UNIFIED IDEOGRAPH - 0xAEFE: 0x6D93, //CJK UNIFIED IDEOGRAPH - 0xAF40: 0x6D6C, //CJK UNIFIED IDEOGRAPH - 0xAF41: 0x6D89, //CJK UNIFIED IDEOGRAPH - 0xAF42: 0x6D6E, //CJK UNIFIED IDEOGRAPH - 0xAF43: 0x6D5A, //CJK UNIFIED IDEOGRAPH - 0xAF44: 0x6D74, //CJK UNIFIED IDEOGRAPH - 0xAF45: 0x6D69, //CJK UNIFIED IDEOGRAPH - 0xAF46: 0x6D8C, //CJK UNIFIED IDEOGRAPH - 0xAF47: 0x6D8A, //CJK UNIFIED IDEOGRAPH - 0xAF48: 0x6D79, //CJK UNIFIED IDEOGRAPH - 0xAF49: 0x6D85, //CJK UNIFIED IDEOGRAPH - 0xAF4A: 0x6D65, //CJK UNIFIED IDEOGRAPH - 0xAF4B: 0x6D94, //CJK UNIFIED IDEOGRAPH - 0xAF4C: 0x70CA, //CJK UNIFIED IDEOGRAPH - 0xAF4D: 0x70D8, //CJK UNIFIED IDEOGRAPH - 0xAF4E: 0x70E4, //CJK UNIFIED IDEOGRAPH - 0xAF4F: 0x70D9, //CJK UNIFIED IDEOGRAPH - 0xAF50: 0x70C8, //CJK UNIFIED IDEOGRAPH - 0xAF51: 0x70CF, //CJK UNIFIED IDEOGRAPH - 0xAF52: 0x7239, //CJK UNIFIED IDEOGRAPH - 0xAF53: 0x7279, //CJK UNIFIED IDEOGRAPH - 0xAF54: 0x72FC, //CJK UNIFIED IDEOGRAPH - 0xAF55: 0x72F9, //CJK UNIFIED IDEOGRAPH - 0xAF56: 0x72FD, //CJK UNIFIED IDEOGRAPH - 0xAF57: 0x72F8, //CJK UNIFIED IDEOGRAPH - 0xAF58: 0x72F7, //CJK UNIFIED IDEOGRAPH - 0xAF59: 0x7386, //CJK UNIFIED IDEOGRAPH - 0xAF5A: 0x73ED, //CJK UNIFIED IDEOGRAPH - 0xAF5B: 0x7409, //CJK UNIFIED IDEOGRAPH - 0xAF5C: 0x73EE, //CJK UNIFIED IDEOGRAPH - 0xAF5D: 0x73E0, //CJK UNIFIED IDEOGRAPH - 0xAF5E: 0x73EA, //CJK UNIFIED IDEOGRAPH - 0xAF5F: 0x73DE, //CJK UNIFIED IDEOGRAPH - 0xAF60: 0x7554, //CJK UNIFIED IDEOGRAPH - 0xAF61: 0x755D, //CJK UNIFIED IDEOGRAPH - 0xAF62: 0x755C, //CJK UNIFIED IDEOGRAPH - 0xAF63: 0x755A, //CJK UNIFIED IDEOGRAPH - 0xAF64: 0x7559, //CJK UNIFIED IDEOGRAPH - 0xAF65: 0x75BE, //CJK UNIFIED IDEOGRAPH - 0xAF66: 0x75C5, //CJK UNIFIED IDEOGRAPH - 0xAF67: 0x75C7, //CJK UNIFIED IDEOGRAPH - 0xAF68: 0x75B2, //CJK UNIFIED IDEOGRAPH - 0xAF69: 0x75B3, //CJK UNIFIED IDEOGRAPH - 0xAF6A: 0x75BD, //CJK UNIFIED IDEOGRAPH - 0xAF6B: 0x75BC, //CJK UNIFIED IDEOGRAPH - 0xAF6C: 0x75B9, //CJK UNIFIED IDEOGRAPH - 0xAF6D: 0x75C2, //CJK UNIFIED IDEOGRAPH - 0xAF6E: 0x75B8, //CJK UNIFIED IDEOGRAPH - 0xAF6F: 0x768B, //CJK UNIFIED IDEOGRAPH - 0xAF70: 0x76B0, //CJK UNIFIED IDEOGRAPH - 0xAF71: 0x76CA, //CJK UNIFIED IDEOGRAPH - 0xAF72: 0x76CD, //CJK UNIFIED IDEOGRAPH - 0xAF73: 0x76CE, //CJK UNIFIED IDEOGRAPH - 0xAF74: 0x7729, //CJK UNIFIED IDEOGRAPH - 0xAF75: 0x771F, //CJK UNIFIED IDEOGRAPH - 0xAF76: 0x7720, //CJK UNIFIED IDEOGRAPH - 0xAF77: 0x7728, //CJK UNIFIED IDEOGRAPH - 0xAF78: 0x77E9, //CJK UNIFIED IDEOGRAPH - 0xAF79: 0x7830, //CJK UNIFIED IDEOGRAPH - 0xAF7A: 0x7827, //CJK UNIFIED IDEOGRAPH - 0xAF7B: 0x7838, //CJK UNIFIED IDEOGRAPH - 0xAF7C: 0x781D, //CJK UNIFIED IDEOGRAPH - 0xAF7D: 0x7834, //CJK UNIFIED IDEOGRAPH - 0xAF7E: 0x7837, //CJK UNIFIED IDEOGRAPH - 0xAFA1: 0x7825, //CJK UNIFIED IDEOGRAPH - 0xAFA2: 0x782D, //CJK UNIFIED IDEOGRAPH - 0xAFA3: 0x7820, //CJK UNIFIED IDEOGRAPH - 0xAFA4: 0x781F, //CJK UNIFIED IDEOGRAPH - 0xAFA5: 0x7832, //CJK UNIFIED IDEOGRAPH - 0xAFA6: 0x7955, //CJK UNIFIED IDEOGRAPH - 0xAFA7: 0x7950, //CJK UNIFIED IDEOGRAPH - 0xAFA8: 0x7960, //CJK UNIFIED IDEOGRAPH - 0xAFA9: 0x795F, //CJK UNIFIED IDEOGRAPH - 0xAFAA: 0x7956, //CJK UNIFIED IDEOGRAPH - 0xAFAB: 0x795E, //CJK UNIFIED IDEOGRAPH - 0xAFAC: 0x795D, //CJK UNIFIED IDEOGRAPH - 0xAFAD: 0x7957, //CJK UNIFIED IDEOGRAPH - 0xAFAE: 0x795A, //CJK UNIFIED IDEOGRAPH - 0xAFAF: 0x79E4, //CJK UNIFIED IDEOGRAPH - 0xAFB0: 0x79E3, //CJK UNIFIED IDEOGRAPH - 0xAFB1: 0x79E7, //CJK UNIFIED IDEOGRAPH - 0xAFB2: 0x79DF, //CJK UNIFIED IDEOGRAPH - 0xAFB3: 0x79E6, //CJK UNIFIED IDEOGRAPH - 0xAFB4: 0x79E9, //CJK UNIFIED IDEOGRAPH - 0xAFB5: 0x79D8, //CJK UNIFIED IDEOGRAPH - 0xAFB6: 0x7A84, //CJK UNIFIED IDEOGRAPH - 0xAFB7: 0x7A88, //CJK UNIFIED IDEOGRAPH - 0xAFB8: 0x7AD9, //CJK UNIFIED IDEOGRAPH - 0xAFB9: 0x7B06, //CJK UNIFIED IDEOGRAPH - 0xAFBA: 0x7B11, //CJK UNIFIED IDEOGRAPH - 0xAFBB: 0x7C89, //CJK UNIFIED IDEOGRAPH - 0xAFBC: 0x7D21, //CJK UNIFIED IDEOGRAPH - 0xAFBD: 0x7D17, //CJK UNIFIED IDEOGRAPH - 0xAFBE: 0x7D0B, //CJK UNIFIED IDEOGRAPH - 0xAFBF: 0x7D0A, //CJK UNIFIED IDEOGRAPH - 0xAFC0: 0x7D20, //CJK UNIFIED IDEOGRAPH - 0xAFC1: 0x7D22, //CJK UNIFIED IDEOGRAPH - 0xAFC2: 0x7D14, //CJK UNIFIED IDEOGRAPH - 0xAFC3: 0x7D10, //CJK UNIFIED IDEOGRAPH - 0xAFC4: 0x7D15, //CJK UNIFIED IDEOGRAPH - 0xAFC5: 0x7D1A, //CJK UNIFIED IDEOGRAPH - 0xAFC6: 0x7D1C, //CJK UNIFIED IDEOGRAPH - 0xAFC7: 0x7D0D, //CJK UNIFIED IDEOGRAPH - 0xAFC8: 0x7D19, //CJK UNIFIED IDEOGRAPH - 0xAFC9: 0x7D1B, //CJK UNIFIED IDEOGRAPH - 0xAFCA: 0x7F3A, //CJK UNIFIED IDEOGRAPH - 0xAFCB: 0x7F5F, //CJK UNIFIED IDEOGRAPH - 0xAFCC: 0x7F94, //CJK UNIFIED IDEOGRAPH - 0xAFCD: 0x7FC5, //CJK UNIFIED IDEOGRAPH - 0xAFCE: 0x7FC1, //CJK UNIFIED IDEOGRAPH - 0xAFCF: 0x8006, //CJK UNIFIED IDEOGRAPH - 0xAFD0: 0x8018, //CJK UNIFIED IDEOGRAPH - 0xAFD1: 0x8015, //CJK UNIFIED IDEOGRAPH - 0xAFD2: 0x8019, //CJK UNIFIED IDEOGRAPH - 0xAFD3: 0x8017, //CJK UNIFIED IDEOGRAPH - 0xAFD4: 0x803D, //CJK UNIFIED IDEOGRAPH - 0xAFD5: 0x803F, //CJK UNIFIED IDEOGRAPH - 0xAFD6: 0x80F1, //CJK UNIFIED IDEOGRAPH - 0xAFD7: 0x8102, //CJK UNIFIED IDEOGRAPH - 0xAFD8: 0x80F0, //CJK UNIFIED IDEOGRAPH - 0xAFD9: 0x8105, //CJK UNIFIED IDEOGRAPH - 0xAFDA: 0x80ED, //CJK UNIFIED IDEOGRAPH - 0xAFDB: 0x80F4, //CJK UNIFIED IDEOGRAPH - 0xAFDC: 0x8106, //CJK UNIFIED IDEOGRAPH - 0xAFDD: 0x80F8, //CJK UNIFIED IDEOGRAPH - 0xAFDE: 0x80F3, //CJK UNIFIED IDEOGRAPH - 0xAFDF: 0x8108, //CJK UNIFIED IDEOGRAPH - 0xAFE0: 0x80FD, //CJK UNIFIED IDEOGRAPH - 0xAFE1: 0x810A, //CJK UNIFIED IDEOGRAPH - 0xAFE2: 0x80FC, //CJK UNIFIED IDEOGRAPH - 0xAFE3: 0x80EF, //CJK UNIFIED IDEOGRAPH - 0xAFE4: 0x81ED, //CJK UNIFIED IDEOGRAPH - 0xAFE5: 0x81EC, //CJK UNIFIED IDEOGRAPH - 0xAFE6: 0x8200, //CJK UNIFIED IDEOGRAPH - 0xAFE7: 0x8210, //CJK UNIFIED IDEOGRAPH - 0xAFE8: 0x822A, //CJK UNIFIED IDEOGRAPH - 0xAFE9: 0x822B, //CJK UNIFIED IDEOGRAPH - 0xAFEA: 0x8228, //CJK UNIFIED IDEOGRAPH - 0xAFEB: 0x822C, //CJK UNIFIED IDEOGRAPH - 0xAFEC: 0x82BB, //CJK UNIFIED IDEOGRAPH - 0xAFED: 0x832B, //CJK UNIFIED IDEOGRAPH - 0xAFEE: 0x8352, //CJK UNIFIED IDEOGRAPH - 0xAFEF: 0x8354, //CJK UNIFIED IDEOGRAPH - 0xAFF0: 0x834A, //CJK UNIFIED IDEOGRAPH - 0xAFF1: 0x8338, //CJK UNIFIED IDEOGRAPH - 0xAFF2: 0x8350, //CJK UNIFIED IDEOGRAPH - 0xAFF3: 0x8349, //CJK UNIFIED IDEOGRAPH - 0xAFF4: 0x8335, //CJK UNIFIED IDEOGRAPH - 0xAFF5: 0x8334, //CJK UNIFIED IDEOGRAPH - 0xAFF6: 0x834F, //CJK UNIFIED IDEOGRAPH - 0xAFF7: 0x8332, //CJK UNIFIED IDEOGRAPH - 0xAFF8: 0x8339, //CJK UNIFIED IDEOGRAPH - 0xAFF9: 0x8336, //CJK UNIFIED IDEOGRAPH - 0xAFFA: 0x8317, //CJK UNIFIED IDEOGRAPH - 0xAFFB: 0x8340, //CJK UNIFIED IDEOGRAPH - 0xAFFC: 0x8331, //CJK UNIFIED IDEOGRAPH - 0xAFFD: 0x8328, //CJK UNIFIED IDEOGRAPH - 0xAFFE: 0x8343, //CJK UNIFIED IDEOGRAPH - 0xB040: 0x8654, //CJK UNIFIED IDEOGRAPH - 0xB041: 0x868A, //CJK UNIFIED IDEOGRAPH - 0xB042: 0x86AA, //CJK UNIFIED IDEOGRAPH - 0xB043: 0x8693, //CJK UNIFIED IDEOGRAPH - 0xB044: 0x86A4, //CJK UNIFIED IDEOGRAPH - 0xB045: 0x86A9, //CJK UNIFIED IDEOGRAPH - 0xB046: 0x868C, //CJK UNIFIED IDEOGRAPH - 0xB047: 0x86A3, //CJK UNIFIED IDEOGRAPH - 0xB048: 0x869C, //CJK UNIFIED IDEOGRAPH - 0xB049: 0x8870, //CJK UNIFIED IDEOGRAPH - 0xB04A: 0x8877, //CJK UNIFIED IDEOGRAPH - 0xB04B: 0x8881, //CJK UNIFIED IDEOGRAPH - 0xB04C: 0x8882, //CJK UNIFIED IDEOGRAPH - 0xB04D: 0x887D, //CJK UNIFIED IDEOGRAPH - 0xB04E: 0x8879, //CJK UNIFIED IDEOGRAPH - 0xB04F: 0x8A18, //CJK UNIFIED IDEOGRAPH - 0xB050: 0x8A10, //CJK UNIFIED IDEOGRAPH - 0xB051: 0x8A0E, //CJK UNIFIED IDEOGRAPH - 0xB052: 0x8A0C, //CJK UNIFIED IDEOGRAPH - 0xB053: 0x8A15, //CJK UNIFIED IDEOGRAPH - 0xB054: 0x8A0A, //CJK UNIFIED IDEOGRAPH - 0xB055: 0x8A17, //CJK UNIFIED IDEOGRAPH - 0xB056: 0x8A13, //CJK UNIFIED IDEOGRAPH - 0xB057: 0x8A16, //CJK UNIFIED IDEOGRAPH - 0xB058: 0x8A0F, //CJK UNIFIED IDEOGRAPH - 0xB059: 0x8A11, //CJK UNIFIED IDEOGRAPH - 0xB05A: 0x8C48, //CJK UNIFIED IDEOGRAPH - 0xB05B: 0x8C7A, //CJK UNIFIED IDEOGRAPH - 0xB05C: 0x8C79, //CJK UNIFIED IDEOGRAPH - 0xB05D: 0x8CA1, //CJK UNIFIED IDEOGRAPH - 0xB05E: 0x8CA2, //CJK UNIFIED IDEOGRAPH - 0xB05F: 0x8D77, //CJK UNIFIED IDEOGRAPH - 0xB060: 0x8EAC, //CJK UNIFIED IDEOGRAPH - 0xB061: 0x8ED2, //CJK UNIFIED IDEOGRAPH - 0xB062: 0x8ED4, //CJK UNIFIED IDEOGRAPH - 0xB063: 0x8ECF, //CJK UNIFIED IDEOGRAPH - 0xB064: 0x8FB1, //CJK UNIFIED IDEOGRAPH - 0xB065: 0x9001, //CJK UNIFIED IDEOGRAPH - 0xB066: 0x9006, //CJK UNIFIED IDEOGRAPH - 0xB067: 0x8FF7, //CJK UNIFIED IDEOGRAPH - 0xB068: 0x9000, //CJK UNIFIED IDEOGRAPH - 0xB069: 0x8FFA, //CJK UNIFIED IDEOGRAPH - 0xB06A: 0x8FF4, //CJK UNIFIED IDEOGRAPH - 0xB06B: 0x9003, //CJK UNIFIED IDEOGRAPH - 0xB06C: 0x8FFD, //CJK UNIFIED IDEOGRAPH - 0xB06D: 0x9005, //CJK UNIFIED IDEOGRAPH - 0xB06E: 0x8FF8, //CJK UNIFIED IDEOGRAPH - 0xB06F: 0x9095, //CJK UNIFIED IDEOGRAPH - 0xB070: 0x90E1, //CJK UNIFIED IDEOGRAPH - 0xB071: 0x90DD, //CJK UNIFIED IDEOGRAPH - 0xB072: 0x90E2, //CJK UNIFIED IDEOGRAPH - 0xB073: 0x9152, //CJK UNIFIED IDEOGRAPH - 0xB074: 0x914D, //CJK UNIFIED IDEOGRAPH - 0xB075: 0x914C, //CJK UNIFIED IDEOGRAPH - 0xB076: 0x91D8, //CJK UNIFIED IDEOGRAPH - 0xB077: 0x91DD, //CJK UNIFIED IDEOGRAPH - 0xB078: 0x91D7, //CJK UNIFIED IDEOGRAPH - 0xB079: 0x91DC, //CJK UNIFIED IDEOGRAPH - 0xB07A: 0x91D9, //CJK UNIFIED IDEOGRAPH - 0xB07B: 0x9583, //CJK UNIFIED IDEOGRAPH - 0xB07C: 0x9662, //CJK UNIFIED IDEOGRAPH - 0xB07D: 0x9663, //CJK UNIFIED IDEOGRAPH - 0xB07E: 0x9661, //CJK UNIFIED IDEOGRAPH - 0xB0A1: 0x965B, //CJK UNIFIED IDEOGRAPH - 0xB0A2: 0x965D, //CJK UNIFIED IDEOGRAPH - 0xB0A3: 0x9664, //CJK UNIFIED IDEOGRAPH - 0xB0A4: 0x9658, //CJK UNIFIED IDEOGRAPH - 0xB0A5: 0x965E, //CJK UNIFIED IDEOGRAPH - 0xB0A6: 0x96BB, //CJK UNIFIED IDEOGRAPH - 0xB0A7: 0x98E2, //CJK UNIFIED IDEOGRAPH - 0xB0A8: 0x99AC, //CJK UNIFIED IDEOGRAPH - 0xB0A9: 0x9AA8, //CJK UNIFIED IDEOGRAPH - 0xB0AA: 0x9AD8, //CJK UNIFIED IDEOGRAPH - 0xB0AB: 0x9B25, //CJK UNIFIED IDEOGRAPH - 0xB0AC: 0x9B32, //CJK UNIFIED IDEOGRAPH - 0xB0AD: 0x9B3C, //CJK UNIFIED IDEOGRAPH - 0xB0AE: 0x4E7E, //CJK UNIFIED IDEOGRAPH - 0xB0AF: 0x507A, //CJK UNIFIED IDEOGRAPH - 0xB0B0: 0x507D, //CJK UNIFIED IDEOGRAPH - 0xB0B1: 0x505C, //CJK UNIFIED IDEOGRAPH - 0xB0B2: 0x5047, //CJK UNIFIED IDEOGRAPH - 0xB0B3: 0x5043, //CJK UNIFIED IDEOGRAPH - 0xB0B4: 0x504C, //CJK UNIFIED IDEOGRAPH - 0xB0B5: 0x505A, //CJK UNIFIED IDEOGRAPH - 0xB0B6: 0x5049, //CJK UNIFIED IDEOGRAPH - 0xB0B7: 0x5065, //CJK UNIFIED IDEOGRAPH - 0xB0B8: 0x5076, //CJK UNIFIED IDEOGRAPH - 0xB0B9: 0x504E, //CJK UNIFIED IDEOGRAPH - 0xB0BA: 0x5055, //CJK UNIFIED IDEOGRAPH - 0xB0BB: 0x5075, //CJK UNIFIED IDEOGRAPH - 0xB0BC: 0x5074, //CJK UNIFIED IDEOGRAPH - 0xB0BD: 0x5077, //CJK UNIFIED IDEOGRAPH - 0xB0BE: 0x504F, //CJK UNIFIED IDEOGRAPH - 0xB0BF: 0x500F, //CJK UNIFIED IDEOGRAPH - 0xB0C0: 0x506F, //CJK UNIFIED IDEOGRAPH - 0xB0C1: 0x506D, //CJK UNIFIED IDEOGRAPH - 0xB0C2: 0x515C, //CJK UNIFIED IDEOGRAPH - 0xB0C3: 0x5195, //CJK UNIFIED IDEOGRAPH - 0xB0C4: 0x51F0, //CJK UNIFIED IDEOGRAPH - 0xB0C5: 0x526A, //CJK UNIFIED IDEOGRAPH - 0xB0C6: 0x526F, //CJK UNIFIED IDEOGRAPH - 0xB0C7: 0x52D2, //CJK UNIFIED IDEOGRAPH - 0xB0C8: 0x52D9, //CJK UNIFIED IDEOGRAPH - 0xB0C9: 0x52D8, //CJK UNIFIED IDEOGRAPH - 0xB0CA: 0x52D5, //CJK UNIFIED IDEOGRAPH - 0xB0CB: 0x5310, //CJK UNIFIED IDEOGRAPH - 0xB0CC: 0x530F, //CJK UNIFIED IDEOGRAPH - 0xB0CD: 0x5319, //CJK UNIFIED IDEOGRAPH - 0xB0CE: 0x533F, //CJK UNIFIED IDEOGRAPH - 0xB0CF: 0x5340, //CJK UNIFIED IDEOGRAPH - 0xB0D0: 0x533E, //CJK UNIFIED IDEOGRAPH - 0xB0D1: 0x53C3, //CJK UNIFIED IDEOGRAPH - 0xB0D2: 0x66FC, //CJK UNIFIED IDEOGRAPH - 0xB0D3: 0x5546, //CJK UNIFIED IDEOGRAPH - 0xB0D4: 0x556A, //CJK UNIFIED IDEOGRAPH - 0xB0D5: 0x5566, //CJK UNIFIED IDEOGRAPH - 0xB0D6: 0x5544, //CJK UNIFIED IDEOGRAPH - 0xB0D7: 0x555E, //CJK UNIFIED IDEOGRAPH - 0xB0D8: 0x5561, //CJK UNIFIED IDEOGRAPH - 0xB0D9: 0x5543, //CJK UNIFIED IDEOGRAPH - 0xB0DA: 0x554A, //CJK UNIFIED IDEOGRAPH - 0xB0DB: 0x5531, //CJK UNIFIED IDEOGRAPH - 0xB0DC: 0x5556, //CJK UNIFIED IDEOGRAPH - 0xB0DD: 0x554F, //CJK UNIFIED IDEOGRAPH - 0xB0DE: 0x5555, //CJK UNIFIED IDEOGRAPH - 0xB0DF: 0x552F, //CJK UNIFIED IDEOGRAPH - 0xB0E0: 0x5564, //CJK UNIFIED IDEOGRAPH - 0xB0E1: 0x5538, //CJK UNIFIED IDEOGRAPH - 0xB0E2: 0x552E, //CJK UNIFIED IDEOGRAPH - 0xB0E3: 0x555C, //CJK UNIFIED IDEOGRAPH - 0xB0E4: 0x552C, //CJK UNIFIED IDEOGRAPH - 0xB0E5: 0x5563, //CJK UNIFIED IDEOGRAPH - 0xB0E6: 0x5533, //CJK UNIFIED IDEOGRAPH - 0xB0E7: 0x5541, //CJK UNIFIED IDEOGRAPH - 0xB0E8: 0x5557, //CJK UNIFIED IDEOGRAPH - 0xB0E9: 0x5708, //CJK UNIFIED IDEOGRAPH - 0xB0EA: 0x570B, //CJK UNIFIED IDEOGRAPH - 0xB0EB: 0x5709, //CJK UNIFIED IDEOGRAPH - 0xB0EC: 0x57DF, //CJK UNIFIED IDEOGRAPH - 0xB0ED: 0x5805, //CJK UNIFIED IDEOGRAPH - 0xB0EE: 0x580A, //CJK UNIFIED IDEOGRAPH - 0xB0EF: 0x5806, //CJK UNIFIED IDEOGRAPH - 0xB0F0: 0x57E0, //CJK UNIFIED IDEOGRAPH - 0xB0F1: 0x57E4, //CJK UNIFIED IDEOGRAPH - 0xB0F2: 0x57FA, //CJK UNIFIED IDEOGRAPH - 0xB0F3: 0x5802, //CJK UNIFIED IDEOGRAPH - 0xB0F4: 0x5835, //CJK UNIFIED IDEOGRAPH - 0xB0F5: 0x57F7, //CJK UNIFIED IDEOGRAPH - 0xB0F6: 0x57F9, //CJK UNIFIED IDEOGRAPH - 0xB0F7: 0x5920, //CJK UNIFIED IDEOGRAPH - 0xB0F8: 0x5962, //CJK UNIFIED IDEOGRAPH - 0xB0F9: 0x5A36, //CJK UNIFIED IDEOGRAPH - 0xB0FA: 0x5A41, //CJK UNIFIED IDEOGRAPH - 0xB0FB: 0x5A49, //CJK UNIFIED IDEOGRAPH - 0xB0FC: 0x5A66, //CJK UNIFIED IDEOGRAPH - 0xB0FD: 0x5A6A, //CJK UNIFIED IDEOGRAPH - 0xB0FE: 0x5A40, //CJK UNIFIED IDEOGRAPH - 0xB140: 0x5A3C, //CJK UNIFIED IDEOGRAPH - 0xB141: 0x5A62, //CJK UNIFIED IDEOGRAPH - 0xB142: 0x5A5A, //CJK UNIFIED IDEOGRAPH - 0xB143: 0x5A46, //CJK UNIFIED IDEOGRAPH - 0xB144: 0x5A4A, //CJK UNIFIED IDEOGRAPH - 0xB145: 0x5B70, //CJK UNIFIED IDEOGRAPH - 0xB146: 0x5BC7, //CJK UNIFIED IDEOGRAPH - 0xB147: 0x5BC5, //CJK UNIFIED IDEOGRAPH - 0xB148: 0x5BC4, //CJK UNIFIED IDEOGRAPH - 0xB149: 0x5BC2, //CJK UNIFIED IDEOGRAPH - 0xB14A: 0x5BBF, //CJK UNIFIED IDEOGRAPH - 0xB14B: 0x5BC6, //CJK UNIFIED IDEOGRAPH - 0xB14C: 0x5C09, //CJK UNIFIED IDEOGRAPH - 0xB14D: 0x5C08, //CJK UNIFIED IDEOGRAPH - 0xB14E: 0x5C07, //CJK UNIFIED IDEOGRAPH - 0xB14F: 0x5C60, //CJK UNIFIED IDEOGRAPH - 0xB150: 0x5C5C, //CJK UNIFIED IDEOGRAPH - 0xB151: 0x5C5D, //CJK UNIFIED IDEOGRAPH - 0xB152: 0x5D07, //CJK UNIFIED IDEOGRAPH - 0xB153: 0x5D06, //CJK UNIFIED IDEOGRAPH - 0xB154: 0x5D0E, //CJK UNIFIED IDEOGRAPH - 0xB155: 0x5D1B, //CJK UNIFIED IDEOGRAPH - 0xB156: 0x5D16, //CJK UNIFIED IDEOGRAPH - 0xB157: 0x5D22, //CJK UNIFIED IDEOGRAPH - 0xB158: 0x5D11, //CJK UNIFIED IDEOGRAPH - 0xB159: 0x5D29, //CJK UNIFIED IDEOGRAPH - 0xB15A: 0x5D14, //CJK UNIFIED IDEOGRAPH - 0xB15B: 0x5D19, //CJK UNIFIED IDEOGRAPH - 0xB15C: 0x5D24, //CJK UNIFIED IDEOGRAPH - 0xB15D: 0x5D27, //CJK UNIFIED IDEOGRAPH - 0xB15E: 0x5D17, //CJK UNIFIED IDEOGRAPH - 0xB15F: 0x5DE2, //CJK UNIFIED IDEOGRAPH - 0xB160: 0x5E38, //CJK UNIFIED IDEOGRAPH - 0xB161: 0x5E36, //CJK UNIFIED IDEOGRAPH - 0xB162: 0x5E33, //CJK UNIFIED IDEOGRAPH - 0xB163: 0x5E37, //CJK UNIFIED IDEOGRAPH - 0xB164: 0x5EB7, //CJK UNIFIED IDEOGRAPH - 0xB165: 0x5EB8, //CJK UNIFIED IDEOGRAPH - 0xB166: 0x5EB6, //CJK UNIFIED IDEOGRAPH - 0xB167: 0x5EB5, //CJK UNIFIED IDEOGRAPH - 0xB168: 0x5EBE, //CJK UNIFIED IDEOGRAPH - 0xB169: 0x5F35, //CJK UNIFIED IDEOGRAPH - 0xB16A: 0x5F37, //CJK UNIFIED IDEOGRAPH - 0xB16B: 0x5F57, //CJK UNIFIED IDEOGRAPH - 0xB16C: 0x5F6C, //CJK UNIFIED IDEOGRAPH - 0xB16D: 0x5F69, //CJK UNIFIED IDEOGRAPH - 0xB16E: 0x5F6B, //CJK UNIFIED IDEOGRAPH - 0xB16F: 0x5F97, //CJK UNIFIED IDEOGRAPH - 0xB170: 0x5F99, //CJK UNIFIED IDEOGRAPH - 0xB171: 0x5F9E, //CJK UNIFIED IDEOGRAPH - 0xB172: 0x5F98, //CJK UNIFIED IDEOGRAPH - 0xB173: 0x5FA1, //CJK UNIFIED IDEOGRAPH - 0xB174: 0x5FA0, //CJK UNIFIED IDEOGRAPH - 0xB175: 0x5F9C, //CJK UNIFIED IDEOGRAPH - 0xB176: 0x607F, //CJK UNIFIED IDEOGRAPH - 0xB177: 0x60A3, //CJK UNIFIED IDEOGRAPH - 0xB178: 0x6089, //CJK UNIFIED IDEOGRAPH - 0xB179: 0x60A0, //CJK UNIFIED IDEOGRAPH - 0xB17A: 0x60A8, //CJK UNIFIED IDEOGRAPH - 0xB17B: 0x60CB, //CJK UNIFIED IDEOGRAPH - 0xB17C: 0x60B4, //CJK UNIFIED IDEOGRAPH - 0xB17D: 0x60E6, //CJK UNIFIED IDEOGRAPH - 0xB17E: 0x60BD, //CJK UNIFIED IDEOGRAPH - 0xB1A1: 0x60C5, //CJK UNIFIED IDEOGRAPH - 0xB1A2: 0x60BB, //CJK UNIFIED IDEOGRAPH - 0xB1A3: 0x60B5, //CJK UNIFIED IDEOGRAPH - 0xB1A4: 0x60DC, //CJK UNIFIED IDEOGRAPH - 0xB1A5: 0x60BC, //CJK UNIFIED IDEOGRAPH - 0xB1A6: 0x60D8, //CJK UNIFIED IDEOGRAPH - 0xB1A7: 0x60D5, //CJK UNIFIED IDEOGRAPH - 0xB1A8: 0x60C6, //CJK UNIFIED IDEOGRAPH - 0xB1A9: 0x60DF, //CJK UNIFIED IDEOGRAPH - 0xB1AA: 0x60B8, //CJK UNIFIED IDEOGRAPH - 0xB1AB: 0x60DA, //CJK UNIFIED IDEOGRAPH - 0xB1AC: 0x60C7, //CJK UNIFIED IDEOGRAPH - 0xB1AD: 0x621A, //CJK UNIFIED IDEOGRAPH - 0xB1AE: 0x621B, //CJK UNIFIED IDEOGRAPH - 0xB1AF: 0x6248, //CJK UNIFIED IDEOGRAPH - 0xB1B0: 0x63A0, //CJK UNIFIED IDEOGRAPH - 0xB1B1: 0x63A7, //CJK UNIFIED IDEOGRAPH - 0xB1B2: 0x6372, //CJK UNIFIED IDEOGRAPH - 0xB1B3: 0x6396, //CJK UNIFIED IDEOGRAPH - 0xB1B4: 0x63A2, //CJK UNIFIED IDEOGRAPH - 0xB1B5: 0x63A5, //CJK UNIFIED IDEOGRAPH - 0xB1B6: 0x6377, //CJK UNIFIED IDEOGRAPH - 0xB1B7: 0x6367, //CJK UNIFIED IDEOGRAPH - 0xB1B8: 0x6398, //CJK UNIFIED IDEOGRAPH - 0xB1B9: 0x63AA, //CJK UNIFIED IDEOGRAPH - 0xB1BA: 0x6371, //CJK UNIFIED IDEOGRAPH - 0xB1BB: 0x63A9, //CJK UNIFIED IDEOGRAPH - 0xB1BC: 0x6389, //CJK UNIFIED IDEOGRAPH - 0xB1BD: 0x6383, //CJK UNIFIED IDEOGRAPH - 0xB1BE: 0x639B, //CJK UNIFIED IDEOGRAPH - 0xB1BF: 0x636B, //CJK UNIFIED IDEOGRAPH - 0xB1C0: 0x63A8, //CJK UNIFIED IDEOGRAPH - 0xB1C1: 0x6384, //CJK UNIFIED IDEOGRAPH - 0xB1C2: 0x6388, //CJK UNIFIED IDEOGRAPH - 0xB1C3: 0x6399, //CJK UNIFIED IDEOGRAPH - 0xB1C4: 0x63A1, //CJK UNIFIED IDEOGRAPH - 0xB1C5: 0x63AC, //CJK UNIFIED IDEOGRAPH - 0xB1C6: 0x6392, //CJK UNIFIED IDEOGRAPH - 0xB1C7: 0x638F, //CJK UNIFIED IDEOGRAPH - 0xB1C8: 0x6380, //CJK UNIFIED IDEOGRAPH - 0xB1C9: 0x637B, //CJK UNIFIED IDEOGRAPH - 0xB1CA: 0x6369, //CJK UNIFIED IDEOGRAPH - 0xB1CB: 0x6368, //CJK UNIFIED IDEOGRAPH - 0xB1CC: 0x637A, //CJK UNIFIED IDEOGRAPH - 0xB1CD: 0x655D, //CJK UNIFIED IDEOGRAPH - 0xB1CE: 0x6556, //CJK UNIFIED IDEOGRAPH - 0xB1CF: 0x6551, //CJK UNIFIED IDEOGRAPH - 0xB1D0: 0x6559, //CJK UNIFIED IDEOGRAPH - 0xB1D1: 0x6557, //CJK UNIFIED IDEOGRAPH - 0xB1D2: 0x555F, //CJK UNIFIED IDEOGRAPH - 0xB1D3: 0x654F, //CJK UNIFIED IDEOGRAPH - 0xB1D4: 0x6558, //CJK UNIFIED IDEOGRAPH - 0xB1D5: 0x6555, //CJK UNIFIED IDEOGRAPH - 0xB1D6: 0x6554, //CJK UNIFIED IDEOGRAPH - 0xB1D7: 0x659C, //CJK UNIFIED IDEOGRAPH - 0xB1D8: 0x659B, //CJK UNIFIED IDEOGRAPH - 0xB1D9: 0x65AC, //CJK UNIFIED IDEOGRAPH - 0xB1DA: 0x65CF, //CJK UNIFIED IDEOGRAPH - 0xB1DB: 0x65CB, //CJK UNIFIED IDEOGRAPH - 0xB1DC: 0x65CC, //CJK UNIFIED IDEOGRAPH - 0xB1DD: 0x65CE, //CJK UNIFIED IDEOGRAPH - 0xB1DE: 0x665D, //CJK UNIFIED IDEOGRAPH - 0xB1DF: 0x665A, //CJK UNIFIED IDEOGRAPH - 0xB1E0: 0x6664, //CJK UNIFIED IDEOGRAPH - 0xB1E1: 0x6668, //CJK UNIFIED IDEOGRAPH - 0xB1E2: 0x6666, //CJK UNIFIED IDEOGRAPH - 0xB1E3: 0x665E, //CJK UNIFIED IDEOGRAPH - 0xB1E4: 0x66F9, //CJK UNIFIED IDEOGRAPH - 0xB1E5: 0x52D7, //CJK UNIFIED IDEOGRAPH - 0xB1E6: 0x671B, //CJK UNIFIED IDEOGRAPH - 0xB1E7: 0x6881, //CJK UNIFIED IDEOGRAPH - 0xB1E8: 0x68AF, //CJK UNIFIED IDEOGRAPH - 0xB1E9: 0x68A2, //CJK UNIFIED IDEOGRAPH - 0xB1EA: 0x6893, //CJK UNIFIED IDEOGRAPH - 0xB1EB: 0x68B5, //CJK UNIFIED IDEOGRAPH - 0xB1EC: 0x687F, //CJK UNIFIED IDEOGRAPH - 0xB1ED: 0x6876, //CJK UNIFIED IDEOGRAPH - 0xB1EE: 0x68B1, //CJK UNIFIED IDEOGRAPH - 0xB1EF: 0x68A7, //CJK UNIFIED IDEOGRAPH - 0xB1F0: 0x6897, //CJK UNIFIED IDEOGRAPH - 0xB1F1: 0x68B0, //CJK UNIFIED IDEOGRAPH - 0xB1F2: 0x6883, //CJK UNIFIED IDEOGRAPH - 0xB1F3: 0x68C4, //CJK UNIFIED IDEOGRAPH - 0xB1F4: 0x68AD, //CJK UNIFIED IDEOGRAPH - 0xB1F5: 0x6886, //CJK UNIFIED IDEOGRAPH - 0xB1F6: 0x6885, //CJK UNIFIED IDEOGRAPH - 0xB1F7: 0x6894, //CJK UNIFIED IDEOGRAPH - 0xB1F8: 0x689D, //CJK UNIFIED IDEOGRAPH - 0xB1F9: 0x68A8, //CJK UNIFIED IDEOGRAPH - 0xB1FA: 0x689F, //CJK UNIFIED IDEOGRAPH - 0xB1FB: 0x68A1, //CJK UNIFIED IDEOGRAPH - 0xB1FC: 0x6882, //CJK UNIFIED IDEOGRAPH - 0xB1FD: 0x6B32, //CJK UNIFIED IDEOGRAPH - 0xB1FE: 0x6BBA, //CJK UNIFIED IDEOGRAPH - 0xB240: 0x6BEB, //CJK UNIFIED IDEOGRAPH - 0xB241: 0x6BEC, //CJK UNIFIED IDEOGRAPH - 0xB242: 0x6C2B, //CJK UNIFIED IDEOGRAPH - 0xB243: 0x6D8E, //CJK UNIFIED IDEOGRAPH - 0xB244: 0x6DBC, //CJK UNIFIED IDEOGRAPH - 0xB245: 0x6DF3, //CJK UNIFIED IDEOGRAPH - 0xB246: 0x6DD9, //CJK UNIFIED IDEOGRAPH - 0xB247: 0x6DB2, //CJK UNIFIED IDEOGRAPH - 0xB248: 0x6DE1, //CJK UNIFIED IDEOGRAPH - 0xB249: 0x6DCC, //CJK UNIFIED IDEOGRAPH - 0xB24A: 0x6DE4, //CJK UNIFIED IDEOGRAPH - 0xB24B: 0x6DFB, //CJK UNIFIED IDEOGRAPH - 0xB24C: 0x6DFA, //CJK UNIFIED IDEOGRAPH - 0xB24D: 0x6E05, //CJK UNIFIED IDEOGRAPH - 0xB24E: 0x6DC7, //CJK UNIFIED IDEOGRAPH - 0xB24F: 0x6DCB, //CJK UNIFIED IDEOGRAPH - 0xB250: 0x6DAF, //CJK UNIFIED IDEOGRAPH - 0xB251: 0x6DD1, //CJK UNIFIED IDEOGRAPH - 0xB252: 0x6DAE, //CJK UNIFIED IDEOGRAPH - 0xB253: 0x6DDE, //CJK UNIFIED IDEOGRAPH - 0xB254: 0x6DF9, //CJK UNIFIED IDEOGRAPH - 0xB255: 0x6DB8, //CJK UNIFIED IDEOGRAPH - 0xB256: 0x6DF7, //CJK UNIFIED IDEOGRAPH - 0xB257: 0x6DF5, //CJK UNIFIED IDEOGRAPH - 0xB258: 0x6DC5, //CJK UNIFIED IDEOGRAPH - 0xB259: 0x6DD2, //CJK UNIFIED IDEOGRAPH - 0xB25A: 0x6E1A, //CJK UNIFIED IDEOGRAPH - 0xB25B: 0x6DB5, //CJK UNIFIED IDEOGRAPH - 0xB25C: 0x6DDA, //CJK UNIFIED IDEOGRAPH - 0xB25D: 0x6DEB, //CJK UNIFIED IDEOGRAPH - 0xB25E: 0x6DD8, //CJK UNIFIED IDEOGRAPH - 0xB25F: 0x6DEA, //CJK UNIFIED IDEOGRAPH - 0xB260: 0x6DF1, //CJK UNIFIED IDEOGRAPH - 0xB261: 0x6DEE, //CJK UNIFIED IDEOGRAPH - 0xB262: 0x6DE8, //CJK UNIFIED IDEOGRAPH - 0xB263: 0x6DC6, //CJK UNIFIED IDEOGRAPH - 0xB264: 0x6DC4, //CJK UNIFIED IDEOGRAPH - 0xB265: 0x6DAA, //CJK UNIFIED IDEOGRAPH - 0xB266: 0x6DEC, //CJK UNIFIED IDEOGRAPH - 0xB267: 0x6DBF, //CJK UNIFIED IDEOGRAPH - 0xB268: 0x6DE6, //CJK UNIFIED IDEOGRAPH - 0xB269: 0x70F9, //CJK UNIFIED IDEOGRAPH - 0xB26A: 0x7109, //CJK UNIFIED IDEOGRAPH - 0xB26B: 0x710A, //CJK UNIFIED IDEOGRAPH - 0xB26C: 0x70FD, //CJK UNIFIED IDEOGRAPH - 0xB26D: 0x70EF, //CJK UNIFIED IDEOGRAPH - 0xB26E: 0x723D, //CJK UNIFIED IDEOGRAPH - 0xB26F: 0x727D, //CJK UNIFIED IDEOGRAPH - 0xB270: 0x7281, //CJK UNIFIED IDEOGRAPH - 0xB271: 0x731C, //CJK UNIFIED IDEOGRAPH - 0xB272: 0x731B, //CJK UNIFIED IDEOGRAPH - 0xB273: 0x7316, //CJK UNIFIED IDEOGRAPH - 0xB274: 0x7313, //CJK UNIFIED IDEOGRAPH - 0xB275: 0x7319, //CJK UNIFIED IDEOGRAPH - 0xB276: 0x7387, //CJK UNIFIED IDEOGRAPH - 0xB277: 0x7405, //CJK UNIFIED IDEOGRAPH - 0xB278: 0x740A, //CJK UNIFIED IDEOGRAPH - 0xB279: 0x7403, //CJK UNIFIED IDEOGRAPH - 0xB27A: 0x7406, //CJK UNIFIED IDEOGRAPH - 0xB27B: 0x73FE, //CJK UNIFIED IDEOGRAPH - 0xB27C: 0x740D, //CJK UNIFIED IDEOGRAPH - 0xB27D: 0x74E0, //CJK UNIFIED IDEOGRAPH - 0xB27E: 0x74F6, //CJK UNIFIED IDEOGRAPH - 0xB2A1: 0x74F7, //CJK UNIFIED IDEOGRAPH - 0xB2A2: 0x751C, //CJK UNIFIED IDEOGRAPH - 0xB2A3: 0x7522, //CJK UNIFIED IDEOGRAPH - 0xB2A4: 0x7565, //CJK UNIFIED IDEOGRAPH - 0xB2A5: 0x7566, //CJK UNIFIED IDEOGRAPH - 0xB2A6: 0x7562, //CJK UNIFIED IDEOGRAPH - 0xB2A7: 0x7570, //CJK UNIFIED IDEOGRAPH - 0xB2A8: 0x758F, //CJK UNIFIED IDEOGRAPH - 0xB2A9: 0x75D4, //CJK UNIFIED IDEOGRAPH - 0xB2AA: 0x75D5, //CJK UNIFIED IDEOGRAPH - 0xB2AB: 0x75B5, //CJK UNIFIED IDEOGRAPH - 0xB2AC: 0x75CA, //CJK UNIFIED IDEOGRAPH - 0xB2AD: 0x75CD, //CJK UNIFIED IDEOGRAPH - 0xB2AE: 0x768E, //CJK UNIFIED IDEOGRAPH - 0xB2AF: 0x76D4, //CJK UNIFIED IDEOGRAPH - 0xB2B0: 0x76D2, //CJK UNIFIED IDEOGRAPH - 0xB2B1: 0x76DB, //CJK UNIFIED IDEOGRAPH - 0xB2B2: 0x7737, //CJK UNIFIED IDEOGRAPH - 0xB2B3: 0x773E, //CJK UNIFIED IDEOGRAPH - 0xB2B4: 0x773C, //CJK UNIFIED IDEOGRAPH - 0xB2B5: 0x7736, //CJK UNIFIED IDEOGRAPH - 0xB2B6: 0x7738, //CJK UNIFIED IDEOGRAPH - 0xB2B7: 0x773A, //CJK UNIFIED IDEOGRAPH - 0xB2B8: 0x786B, //CJK UNIFIED IDEOGRAPH - 0xB2B9: 0x7843, //CJK UNIFIED IDEOGRAPH - 0xB2BA: 0x784E, //CJK UNIFIED IDEOGRAPH - 0xB2BB: 0x7965, //CJK UNIFIED IDEOGRAPH - 0xB2BC: 0x7968, //CJK UNIFIED IDEOGRAPH - 0xB2BD: 0x796D, //CJK UNIFIED IDEOGRAPH - 0xB2BE: 0x79FB, //CJK UNIFIED IDEOGRAPH - 0xB2BF: 0x7A92, //CJK UNIFIED IDEOGRAPH - 0xB2C0: 0x7A95, //CJK UNIFIED IDEOGRAPH - 0xB2C1: 0x7B20, //CJK UNIFIED IDEOGRAPH - 0xB2C2: 0x7B28, //CJK UNIFIED IDEOGRAPH - 0xB2C3: 0x7B1B, //CJK UNIFIED IDEOGRAPH - 0xB2C4: 0x7B2C, //CJK UNIFIED IDEOGRAPH - 0xB2C5: 0x7B26, //CJK UNIFIED IDEOGRAPH - 0xB2C6: 0x7B19, //CJK UNIFIED IDEOGRAPH - 0xB2C7: 0x7B1E, //CJK UNIFIED IDEOGRAPH - 0xB2C8: 0x7B2E, //CJK UNIFIED IDEOGRAPH - 0xB2C9: 0x7C92, //CJK UNIFIED IDEOGRAPH - 0xB2CA: 0x7C97, //CJK UNIFIED IDEOGRAPH - 0xB2CB: 0x7C95, //CJK UNIFIED IDEOGRAPH - 0xB2CC: 0x7D46, //CJK UNIFIED IDEOGRAPH - 0xB2CD: 0x7D43, //CJK UNIFIED IDEOGRAPH - 0xB2CE: 0x7D71, //CJK UNIFIED IDEOGRAPH - 0xB2CF: 0x7D2E, //CJK UNIFIED IDEOGRAPH - 0xB2D0: 0x7D39, //CJK UNIFIED IDEOGRAPH - 0xB2D1: 0x7D3C, //CJK UNIFIED IDEOGRAPH - 0xB2D2: 0x7D40, //CJK UNIFIED IDEOGRAPH - 0xB2D3: 0x7D30, //CJK UNIFIED IDEOGRAPH - 0xB2D4: 0x7D33, //CJK UNIFIED IDEOGRAPH - 0xB2D5: 0x7D44, //CJK UNIFIED IDEOGRAPH - 0xB2D6: 0x7D2F, //CJK UNIFIED IDEOGRAPH - 0xB2D7: 0x7D42, //CJK UNIFIED IDEOGRAPH - 0xB2D8: 0x7D32, //CJK UNIFIED IDEOGRAPH - 0xB2D9: 0x7D31, //CJK UNIFIED IDEOGRAPH - 0xB2DA: 0x7F3D, //CJK UNIFIED IDEOGRAPH - 0xB2DB: 0x7F9E, //CJK UNIFIED IDEOGRAPH - 0xB2DC: 0x7F9A, //CJK UNIFIED IDEOGRAPH - 0xB2DD: 0x7FCC, //CJK UNIFIED IDEOGRAPH - 0xB2DE: 0x7FCE, //CJK UNIFIED IDEOGRAPH - 0xB2DF: 0x7FD2, //CJK UNIFIED IDEOGRAPH - 0xB2E0: 0x801C, //CJK UNIFIED IDEOGRAPH - 0xB2E1: 0x804A, //CJK UNIFIED IDEOGRAPH - 0xB2E2: 0x8046, //CJK UNIFIED IDEOGRAPH - 0xB2E3: 0x812F, //CJK UNIFIED IDEOGRAPH - 0xB2E4: 0x8116, //CJK UNIFIED IDEOGRAPH - 0xB2E5: 0x8123, //CJK UNIFIED IDEOGRAPH - 0xB2E6: 0x812B, //CJK UNIFIED IDEOGRAPH - 0xB2E7: 0x8129, //CJK UNIFIED IDEOGRAPH - 0xB2E8: 0x8130, //CJK UNIFIED IDEOGRAPH - 0xB2E9: 0x8124, //CJK UNIFIED IDEOGRAPH - 0xB2EA: 0x8202, //CJK UNIFIED IDEOGRAPH - 0xB2EB: 0x8235, //CJK UNIFIED IDEOGRAPH - 0xB2EC: 0x8237, //CJK UNIFIED IDEOGRAPH - 0xB2ED: 0x8236, //CJK UNIFIED IDEOGRAPH - 0xB2EE: 0x8239, //CJK UNIFIED IDEOGRAPH - 0xB2EF: 0x838E, //CJK UNIFIED IDEOGRAPH - 0xB2F0: 0x839E, //CJK UNIFIED IDEOGRAPH - 0xB2F1: 0x8398, //CJK UNIFIED IDEOGRAPH - 0xB2F2: 0x8378, //CJK UNIFIED IDEOGRAPH - 0xB2F3: 0x83A2, //CJK UNIFIED IDEOGRAPH - 0xB2F4: 0x8396, //CJK UNIFIED IDEOGRAPH - 0xB2F5: 0x83BD, //CJK UNIFIED IDEOGRAPH - 0xB2F6: 0x83AB, //CJK UNIFIED IDEOGRAPH - 0xB2F7: 0x8392, //CJK UNIFIED IDEOGRAPH - 0xB2F8: 0x838A, //CJK UNIFIED IDEOGRAPH - 0xB2F9: 0x8393, //CJK UNIFIED IDEOGRAPH - 0xB2FA: 0x8389, //CJK UNIFIED IDEOGRAPH - 0xB2FB: 0x83A0, //CJK UNIFIED IDEOGRAPH - 0xB2FC: 0x8377, //CJK UNIFIED IDEOGRAPH - 0xB2FD: 0x837B, //CJK UNIFIED IDEOGRAPH - 0xB2FE: 0x837C, //CJK UNIFIED IDEOGRAPH - 0xB340: 0x8386, //CJK UNIFIED IDEOGRAPH - 0xB341: 0x83A7, //CJK UNIFIED IDEOGRAPH - 0xB342: 0x8655, //CJK UNIFIED IDEOGRAPH - 0xB343: 0x5F6A, //CJK UNIFIED IDEOGRAPH - 0xB344: 0x86C7, //CJK UNIFIED IDEOGRAPH - 0xB345: 0x86C0, //CJK UNIFIED IDEOGRAPH - 0xB346: 0x86B6, //CJK UNIFIED IDEOGRAPH - 0xB347: 0x86C4, //CJK UNIFIED IDEOGRAPH - 0xB348: 0x86B5, //CJK UNIFIED IDEOGRAPH - 0xB349: 0x86C6, //CJK UNIFIED IDEOGRAPH - 0xB34A: 0x86CB, //CJK UNIFIED IDEOGRAPH - 0xB34B: 0x86B1, //CJK UNIFIED IDEOGRAPH - 0xB34C: 0x86AF, //CJK UNIFIED IDEOGRAPH - 0xB34D: 0x86C9, //CJK UNIFIED IDEOGRAPH - 0xB34E: 0x8853, //CJK UNIFIED IDEOGRAPH - 0xB34F: 0x889E, //CJK UNIFIED IDEOGRAPH - 0xB350: 0x8888, //CJK UNIFIED IDEOGRAPH - 0xB351: 0x88AB, //CJK UNIFIED IDEOGRAPH - 0xB352: 0x8892, //CJK UNIFIED IDEOGRAPH - 0xB353: 0x8896, //CJK UNIFIED IDEOGRAPH - 0xB354: 0x888D, //CJK UNIFIED IDEOGRAPH - 0xB355: 0x888B, //CJK UNIFIED IDEOGRAPH - 0xB356: 0x8993, //CJK UNIFIED IDEOGRAPH - 0xB357: 0x898F, //CJK UNIFIED IDEOGRAPH - 0xB358: 0x8A2A, //CJK UNIFIED IDEOGRAPH - 0xB359: 0x8A1D, //CJK UNIFIED IDEOGRAPH - 0xB35A: 0x8A23, //CJK UNIFIED IDEOGRAPH - 0xB35B: 0x8A25, //CJK UNIFIED IDEOGRAPH - 0xB35C: 0x8A31, //CJK UNIFIED IDEOGRAPH - 0xB35D: 0x8A2D, //CJK UNIFIED IDEOGRAPH - 0xB35E: 0x8A1F, //CJK UNIFIED IDEOGRAPH - 0xB35F: 0x8A1B, //CJK UNIFIED IDEOGRAPH - 0xB360: 0x8A22, //CJK UNIFIED IDEOGRAPH - 0xB361: 0x8C49, //CJK UNIFIED IDEOGRAPH - 0xB362: 0x8C5A, //CJK UNIFIED IDEOGRAPH - 0xB363: 0x8CA9, //CJK UNIFIED IDEOGRAPH - 0xB364: 0x8CAC, //CJK UNIFIED IDEOGRAPH - 0xB365: 0x8CAB, //CJK UNIFIED IDEOGRAPH - 0xB366: 0x8CA8, //CJK UNIFIED IDEOGRAPH - 0xB367: 0x8CAA, //CJK UNIFIED IDEOGRAPH - 0xB368: 0x8CA7, //CJK UNIFIED IDEOGRAPH - 0xB369: 0x8D67, //CJK UNIFIED IDEOGRAPH - 0xB36A: 0x8D66, //CJK UNIFIED IDEOGRAPH - 0xB36B: 0x8DBE, //CJK UNIFIED IDEOGRAPH - 0xB36C: 0x8DBA, //CJK UNIFIED IDEOGRAPH - 0xB36D: 0x8EDB, //CJK UNIFIED IDEOGRAPH - 0xB36E: 0x8EDF, //CJK UNIFIED IDEOGRAPH - 0xB36F: 0x9019, //CJK UNIFIED IDEOGRAPH - 0xB370: 0x900D, //CJK UNIFIED IDEOGRAPH - 0xB371: 0x901A, //CJK UNIFIED IDEOGRAPH - 0xB372: 0x9017, //CJK UNIFIED IDEOGRAPH - 0xB373: 0x9023, //CJK UNIFIED IDEOGRAPH - 0xB374: 0x901F, //CJK UNIFIED IDEOGRAPH - 0xB375: 0x901D, //CJK UNIFIED IDEOGRAPH - 0xB376: 0x9010, //CJK UNIFIED IDEOGRAPH - 0xB377: 0x9015, //CJK UNIFIED IDEOGRAPH - 0xB378: 0x901E, //CJK UNIFIED IDEOGRAPH - 0xB379: 0x9020, //CJK UNIFIED IDEOGRAPH - 0xB37A: 0x900F, //CJK UNIFIED IDEOGRAPH - 0xB37B: 0x9022, //CJK UNIFIED IDEOGRAPH - 0xB37C: 0x9016, //CJK UNIFIED IDEOGRAPH - 0xB37D: 0x901B, //CJK UNIFIED IDEOGRAPH - 0xB37E: 0x9014, //CJK UNIFIED IDEOGRAPH - 0xB3A1: 0x90E8, //CJK UNIFIED IDEOGRAPH - 0xB3A2: 0x90ED, //CJK UNIFIED IDEOGRAPH - 0xB3A3: 0x90FD, //CJK UNIFIED IDEOGRAPH - 0xB3A4: 0x9157, //CJK UNIFIED IDEOGRAPH - 0xB3A5: 0x91CE, //CJK UNIFIED IDEOGRAPH - 0xB3A6: 0x91F5, //CJK UNIFIED IDEOGRAPH - 0xB3A7: 0x91E6, //CJK UNIFIED IDEOGRAPH - 0xB3A8: 0x91E3, //CJK UNIFIED IDEOGRAPH - 0xB3A9: 0x91E7, //CJK UNIFIED IDEOGRAPH - 0xB3AA: 0x91ED, //CJK UNIFIED IDEOGRAPH - 0xB3AB: 0x91E9, //CJK UNIFIED IDEOGRAPH - 0xB3AC: 0x9589, //CJK UNIFIED IDEOGRAPH - 0xB3AD: 0x966A, //CJK UNIFIED IDEOGRAPH - 0xB3AE: 0x9675, //CJK UNIFIED IDEOGRAPH - 0xB3AF: 0x9673, //CJK UNIFIED IDEOGRAPH - 0xB3B0: 0x9678, //CJK UNIFIED IDEOGRAPH - 0xB3B1: 0x9670, //CJK UNIFIED IDEOGRAPH - 0xB3B2: 0x9674, //CJK UNIFIED IDEOGRAPH - 0xB3B3: 0x9676, //CJK UNIFIED IDEOGRAPH - 0xB3B4: 0x9677, //CJK UNIFIED IDEOGRAPH - 0xB3B5: 0x966C, //CJK UNIFIED IDEOGRAPH - 0xB3B6: 0x96C0, //CJK UNIFIED IDEOGRAPH - 0xB3B7: 0x96EA, //CJK UNIFIED IDEOGRAPH - 0xB3B8: 0x96E9, //CJK UNIFIED IDEOGRAPH - 0xB3B9: 0x7AE0, //CJK UNIFIED IDEOGRAPH - 0xB3BA: 0x7ADF, //CJK UNIFIED IDEOGRAPH - 0xB3BB: 0x9802, //CJK UNIFIED IDEOGRAPH - 0xB3BC: 0x9803, //CJK UNIFIED IDEOGRAPH - 0xB3BD: 0x9B5A, //CJK UNIFIED IDEOGRAPH - 0xB3BE: 0x9CE5, //CJK UNIFIED IDEOGRAPH - 0xB3BF: 0x9E75, //CJK UNIFIED IDEOGRAPH - 0xB3C0: 0x9E7F, //CJK UNIFIED IDEOGRAPH - 0xB3C1: 0x9EA5, //CJK UNIFIED IDEOGRAPH - 0xB3C2: 0x9EBB, //CJK UNIFIED IDEOGRAPH - 0xB3C3: 0x50A2, //CJK UNIFIED IDEOGRAPH - 0xB3C4: 0x508D, //CJK UNIFIED IDEOGRAPH - 0xB3C5: 0x5085, //CJK UNIFIED IDEOGRAPH - 0xB3C6: 0x5099, //CJK UNIFIED IDEOGRAPH - 0xB3C7: 0x5091, //CJK UNIFIED IDEOGRAPH - 0xB3C8: 0x5080, //CJK UNIFIED IDEOGRAPH - 0xB3C9: 0x5096, //CJK UNIFIED IDEOGRAPH - 0xB3CA: 0x5098, //CJK UNIFIED IDEOGRAPH - 0xB3CB: 0x509A, //CJK UNIFIED IDEOGRAPH - 0xB3CC: 0x6700, //CJK UNIFIED IDEOGRAPH - 0xB3CD: 0x51F1, //CJK UNIFIED IDEOGRAPH - 0xB3CE: 0x5272, //CJK UNIFIED IDEOGRAPH - 0xB3CF: 0x5274, //CJK UNIFIED IDEOGRAPH - 0xB3D0: 0x5275, //CJK UNIFIED IDEOGRAPH - 0xB3D1: 0x5269, //CJK UNIFIED IDEOGRAPH - 0xB3D2: 0x52DE, //CJK UNIFIED IDEOGRAPH - 0xB3D3: 0x52DD, //CJK UNIFIED IDEOGRAPH - 0xB3D4: 0x52DB, //CJK UNIFIED IDEOGRAPH - 0xB3D5: 0x535A, //CJK UNIFIED IDEOGRAPH - 0xB3D6: 0x53A5, //CJK UNIFIED IDEOGRAPH - 0xB3D7: 0x557B, //CJK UNIFIED IDEOGRAPH - 0xB3D8: 0x5580, //CJK UNIFIED IDEOGRAPH - 0xB3D9: 0x55A7, //CJK UNIFIED IDEOGRAPH - 0xB3DA: 0x557C, //CJK UNIFIED IDEOGRAPH - 0xB3DB: 0x558A, //CJK UNIFIED IDEOGRAPH - 0xB3DC: 0x559D, //CJK UNIFIED IDEOGRAPH - 0xB3DD: 0x5598, //CJK UNIFIED IDEOGRAPH - 0xB3DE: 0x5582, //CJK UNIFIED IDEOGRAPH - 0xB3DF: 0x559C, //CJK UNIFIED IDEOGRAPH - 0xB3E0: 0x55AA, //CJK UNIFIED IDEOGRAPH - 0xB3E1: 0x5594, //CJK UNIFIED IDEOGRAPH - 0xB3E2: 0x5587, //CJK UNIFIED IDEOGRAPH - 0xB3E3: 0x558B, //CJK UNIFIED IDEOGRAPH - 0xB3E4: 0x5583, //CJK UNIFIED IDEOGRAPH - 0xB3E5: 0x55B3, //CJK UNIFIED IDEOGRAPH - 0xB3E6: 0x55AE, //CJK UNIFIED IDEOGRAPH - 0xB3E7: 0x559F, //CJK UNIFIED IDEOGRAPH - 0xB3E8: 0x553E, //CJK UNIFIED IDEOGRAPH - 0xB3E9: 0x55B2, //CJK UNIFIED IDEOGRAPH - 0xB3EA: 0x559A, //CJK UNIFIED IDEOGRAPH - 0xB3EB: 0x55BB, //CJK UNIFIED IDEOGRAPH - 0xB3EC: 0x55AC, //CJK UNIFIED IDEOGRAPH - 0xB3ED: 0x55B1, //CJK UNIFIED IDEOGRAPH - 0xB3EE: 0x557E, //CJK UNIFIED IDEOGRAPH - 0xB3EF: 0x5589, //CJK UNIFIED IDEOGRAPH - 0xB3F0: 0x55AB, //CJK UNIFIED IDEOGRAPH - 0xB3F1: 0x5599, //CJK UNIFIED IDEOGRAPH - 0xB3F2: 0x570D, //CJK UNIFIED IDEOGRAPH - 0xB3F3: 0x582F, //CJK UNIFIED IDEOGRAPH - 0xB3F4: 0x582A, //CJK UNIFIED IDEOGRAPH - 0xB3F5: 0x5834, //CJK UNIFIED IDEOGRAPH - 0xB3F6: 0x5824, //CJK UNIFIED IDEOGRAPH - 0xB3F7: 0x5830, //CJK UNIFIED IDEOGRAPH - 0xB3F8: 0x5831, //CJK UNIFIED IDEOGRAPH - 0xB3F9: 0x5821, //CJK UNIFIED IDEOGRAPH - 0xB3FA: 0x581D, //CJK UNIFIED IDEOGRAPH - 0xB3FB: 0x5820, //CJK UNIFIED IDEOGRAPH - 0xB3FC: 0x58F9, //CJK UNIFIED IDEOGRAPH - 0xB3FD: 0x58FA, //CJK UNIFIED IDEOGRAPH - 0xB3FE: 0x5960, //CJK UNIFIED IDEOGRAPH - 0xB440: 0x5A77, //CJK UNIFIED IDEOGRAPH - 0xB441: 0x5A9A, //CJK UNIFIED IDEOGRAPH - 0xB442: 0x5A7F, //CJK UNIFIED IDEOGRAPH - 0xB443: 0x5A92, //CJK UNIFIED IDEOGRAPH - 0xB444: 0x5A9B, //CJK UNIFIED IDEOGRAPH - 0xB445: 0x5AA7, //CJK UNIFIED IDEOGRAPH - 0xB446: 0x5B73, //CJK UNIFIED IDEOGRAPH - 0xB447: 0x5B71, //CJK UNIFIED IDEOGRAPH - 0xB448: 0x5BD2, //CJK UNIFIED IDEOGRAPH - 0xB449: 0x5BCC, //CJK UNIFIED IDEOGRAPH - 0xB44A: 0x5BD3, //CJK UNIFIED IDEOGRAPH - 0xB44B: 0x5BD0, //CJK UNIFIED IDEOGRAPH - 0xB44C: 0x5C0A, //CJK UNIFIED IDEOGRAPH - 0xB44D: 0x5C0B, //CJK UNIFIED IDEOGRAPH - 0xB44E: 0x5C31, //CJK UNIFIED IDEOGRAPH - 0xB44F: 0x5D4C, //CJK UNIFIED IDEOGRAPH - 0xB450: 0x5D50, //CJK UNIFIED IDEOGRAPH - 0xB451: 0x5D34, //CJK UNIFIED IDEOGRAPH - 0xB452: 0x5D47, //CJK UNIFIED IDEOGRAPH - 0xB453: 0x5DFD, //CJK UNIFIED IDEOGRAPH - 0xB454: 0x5E45, //CJK UNIFIED IDEOGRAPH - 0xB455: 0x5E3D, //CJK UNIFIED IDEOGRAPH - 0xB456: 0x5E40, //CJK UNIFIED IDEOGRAPH - 0xB457: 0x5E43, //CJK UNIFIED IDEOGRAPH - 0xB458: 0x5E7E, //CJK UNIFIED IDEOGRAPH - 0xB459: 0x5ECA, //CJK UNIFIED IDEOGRAPH - 0xB45A: 0x5EC1, //CJK UNIFIED IDEOGRAPH - 0xB45B: 0x5EC2, //CJK UNIFIED IDEOGRAPH - 0xB45C: 0x5EC4, //CJK UNIFIED IDEOGRAPH - 0xB45D: 0x5F3C, //CJK UNIFIED IDEOGRAPH - 0xB45E: 0x5F6D, //CJK UNIFIED IDEOGRAPH - 0xB45F: 0x5FA9, //CJK UNIFIED IDEOGRAPH - 0xB460: 0x5FAA, //CJK UNIFIED IDEOGRAPH - 0xB461: 0x5FA8, //CJK UNIFIED IDEOGRAPH - 0xB462: 0x60D1, //CJK UNIFIED IDEOGRAPH - 0xB463: 0x60E1, //CJK UNIFIED IDEOGRAPH - 0xB464: 0x60B2, //CJK UNIFIED IDEOGRAPH - 0xB465: 0x60B6, //CJK UNIFIED IDEOGRAPH - 0xB466: 0x60E0, //CJK UNIFIED IDEOGRAPH - 0xB467: 0x611C, //CJK UNIFIED IDEOGRAPH - 0xB468: 0x6123, //CJK UNIFIED IDEOGRAPH - 0xB469: 0x60FA, //CJK UNIFIED IDEOGRAPH - 0xB46A: 0x6115, //CJK UNIFIED IDEOGRAPH - 0xB46B: 0x60F0, //CJK UNIFIED IDEOGRAPH - 0xB46C: 0x60FB, //CJK UNIFIED IDEOGRAPH - 0xB46D: 0x60F4, //CJK UNIFIED IDEOGRAPH - 0xB46E: 0x6168, //CJK UNIFIED IDEOGRAPH - 0xB46F: 0x60F1, //CJK UNIFIED IDEOGRAPH - 0xB470: 0x610E, //CJK UNIFIED IDEOGRAPH - 0xB471: 0x60F6, //CJK UNIFIED IDEOGRAPH - 0xB472: 0x6109, //CJK UNIFIED IDEOGRAPH - 0xB473: 0x6100, //CJK UNIFIED IDEOGRAPH - 0xB474: 0x6112, //CJK UNIFIED IDEOGRAPH - 0xB475: 0x621F, //CJK UNIFIED IDEOGRAPH - 0xB476: 0x6249, //CJK UNIFIED IDEOGRAPH - 0xB477: 0x63A3, //CJK UNIFIED IDEOGRAPH - 0xB478: 0x638C, //CJK UNIFIED IDEOGRAPH - 0xB479: 0x63CF, //CJK UNIFIED IDEOGRAPH - 0xB47A: 0x63C0, //CJK UNIFIED IDEOGRAPH - 0xB47B: 0x63E9, //CJK UNIFIED IDEOGRAPH - 0xB47C: 0x63C9, //CJK UNIFIED IDEOGRAPH - 0xB47D: 0x63C6, //CJK UNIFIED IDEOGRAPH - 0xB47E: 0x63CD, //CJK UNIFIED IDEOGRAPH - 0xB4A1: 0x63D2, //CJK UNIFIED IDEOGRAPH - 0xB4A2: 0x63E3, //CJK UNIFIED IDEOGRAPH - 0xB4A3: 0x63D0, //CJK UNIFIED IDEOGRAPH - 0xB4A4: 0x63E1, //CJK UNIFIED IDEOGRAPH - 0xB4A5: 0x63D6, //CJK UNIFIED IDEOGRAPH - 0xB4A6: 0x63ED, //CJK UNIFIED IDEOGRAPH - 0xB4A7: 0x63EE, //CJK UNIFIED IDEOGRAPH - 0xB4A8: 0x6376, //CJK UNIFIED IDEOGRAPH - 0xB4A9: 0x63F4, //CJK UNIFIED IDEOGRAPH - 0xB4AA: 0x63EA, //CJK UNIFIED IDEOGRAPH - 0xB4AB: 0x63DB, //CJK UNIFIED IDEOGRAPH - 0xB4AC: 0x6452, //CJK UNIFIED IDEOGRAPH - 0xB4AD: 0x63DA, //CJK UNIFIED IDEOGRAPH - 0xB4AE: 0x63F9, //CJK UNIFIED IDEOGRAPH - 0xB4AF: 0x655E, //CJK UNIFIED IDEOGRAPH - 0xB4B0: 0x6566, //CJK UNIFIED IDEOGRAPH - 0xB4B1: 0x6562, //CJK UNIFIED IDEOGRAPH - 0xB4B2: 0x6563, //CJK UNIFIED IDEOGRAPH - 0xB4B3: 0x6591, //CJK UNIFIED IDEOGRAPH - 0xB4B4: 0x6590, //CJK UNIFIED IDEOGRAPH - 0xB4B5: 0x65AF, //CJK UNIFIED IDEOGRAPH - 0xB4B6: 0x666E, //CJK UNIFIED IDEOGRAPH - 0xB4B7: 0x6670, //CJK UNIFIED IDEOGRAPH - 0xB4B8: 0x6674, //CJK UNIFIED IDEOGRAPH - 0xB4B9: 0x6676, //CJK UNIFIED IDEOGRAPH - 0xB4BA: 0x666F, //CJK UNIFIED IDEOGRAPH - 0xB4BB: 0x6691, //CJK UNIFIED IDEOGRAPH - 0xB4BC: 0x667A, //CJK UNIFIED IDEOGRAPH - 0xB4BD: 0x667E, //CJK UNIFIED IDEOGRAPH - 0xB4BE: 0x6677, //CJK UNIFIED IDEOGRAPH - 0xB4BF: 0x66FE, //CJK UNIFIED IDEOGRAPH - 0xB4C0: 0x66FF, //CJK UNIFIED IDEOGRAPH - 0xB4C1: 0x671F, //CJK UNIFIED IDEOGRAPH - 0xB4C2: 0x671D, //CJK UNIFIED IDEOGRAPH - 0xB4C3: 0x68FA, //CJK UNIFIED IDEOGRAPH - 0xB4C4: 0x68D5, //CJK UNIFIED IDEOGRAPH - 0xB4C5: 0x68E0, //CJK UNIFIED IDEOGRAPH - 0xB4C6: 0x68D8, //CJK UNIFIED IDEOGRAPH - 0xB4C7: 0x68D7, //CJK UNIFIED IDEOGRAPH - 0xB4C8: 0x6905, //CJK UNIFIED IDEOGRAPH - 0xB4C9: 0x68DF, //CJK UNIFIED IDEOGRAPH - 0xB4CA: 0x68F5, //CJK UNIFIED IDEOGRAPH - 0xB4CB: 0x68EE, //CJK UNIFIED IDEOGRAPH - 0xB4CC: 0x68E7, //CJK UNIFIED IDEOGRAPH - 0xB4CD: 0x68F9, //CJK UNIFIED IDEOGRAPH - 0xB4CE: 0x68D2, //CJK UNIFIED IDEOGRAPH - 0xB4CF: 0x68F2, //CJK UNIFIED IDEOGRAPH - 0xB4D0: 0x68E3, //CJK UNIFIED IDEOGRAPH - 0xB4D1: 0x68CB, //CJK UNIFIED IDEOGRAPH - 0xB4D2: 0x68CD, //CJK UNIFIED IDEOGRAPH - 0xB4D3: 0x690D, //CJK UNIFIED IDEOGRAPH - 0xB4D4: 0x6912, //CJK UNIFIED IDEOGRAPH - 0xB4D5: 0x690E, //CJK UNIFIED IDEOGRAPH - 0xB4D6: 0x68C9, //CJK UNIFIED IDEOGRAPH - 0xB4D7: 0x68DA, //CJK UNIFIED IDEOGRAPH - 0xB4D8: 0x696E, //CJK UNIFIED IDEOGRAPH - 0xB4D9: 0x68FB, //CJK UNIFIED IDEOGRAPH - 0xB4DA: 0x6B3E, //CJK UNIFIED IDEOGRAPH - 0xB4DB: 0x6B3A, //CJK UNIFIED IDEOGRAPH - 0xB4DC: 0x6B3D, //CJK UNIFIED IDEOGRAPH - 0xB4DD: 0x6B98, //CJK UNIFIED IDEOGRAPH - 0xB4DE: 0x6B96, //CJK UNIFIED IDEOGRAPH - 0xB4DF: 0x6BBC, //CJK UNIFIED IDEOGRAPH - 0xB4E0: 0x6BEF, //CJK UNIFIED IDEOGRAPH - 0xB4E1: 0x6C2E, //CJK UNIFIED IDEOGRAPH - 0xB4E2: 0x6C2F, //CJK UNIFIED IDEOGRAPH - 0xB4E3: 0x6C2C, //CJK UNIFIED IDEOGRAPH - 0xB4E4: 0x6E2F, //CJK UNIFIED IDEOGRAPH - 0xB4E5: 0x6E38, //CJK UNIFIED IDEOGRAPH - 0xB4E6: 0x6E54, //CJK UNIFIED IDEOGRAPH - 0xB4E7: 0x6E21, //CJK UNIFIED IDEOGRAPH - 0xB4E8: 0x6E32, //CJK UNIFIED IDEOGRAPH - 0xB4E9: 0x6E67, //CJK UNIFIED IDEOGRAPH - 0xB4EA: 0x6E4A, //CJK UNIFIED IDEOGRAPH - 0xB4EB: 0x6E20, //CJK UNIFIED IDEOGRAPH - 0xB4EC: 0x6E25, //CJK UNIFIED IDEOGRAPH - 0xB4ED: 0x6E23, //CJK UNIFIED IDEOGRAPH - 0xB4EE: 0x6E1B, //CJK UNIFIED IDEOGRAPH - 0xB4EF: 0x6E5B, //CJK UNIFIED IDEOGRAPH - 0xB4F0: 0x6E58, //CJK UNIFIED IDEOGRAPH - 0xB4F1: 0x6E24, //CJK UNIFIED IDEOGRAPH - 0xB4F2: 0x6E56, //CJK UNIFIED IDEOGRAPH - 0xB4F3: 0x6E6E, //CJK UNIFIED IDEOGRAPH - 0xB4F4: 0x6E2D, //CJK UNIFIED IDEOGRAPH - 0xB4F5: 0x6E26, //CJK UNIFIED IDEOGRAPH - 0xB4F6: 0x6E6F, //CJK UNIFIED IDEOGRAPH - 0xB4F7: 0x6E34, //CJK UNIFIED IDEOGRAPH - 0xB4F8: 0x6E4D, //CJK UNIFIED IDEOGRAPH - 0xB4F9: 0x6E3A, //CJK UNIFIED IDEOGRAPH - 0xB4FA: 0x6E2C, //CJK UNIFIED IDEOGRAPH - 0xB4FB: 0x6E43, //CJK UNIFIED IDEOGRAPH - 0xB4FC: 0x6E1D, //CJK UNIFIED IDEOGRAPH - 0xB4FD: 0x6E3E, //CJK UNIFIED IDEOGRAPH - 0xB4FE: 0x6ECB, //CJK UNIFIED IDEOGRAPH - 0xB540: 0x6E89, //CJK UNIFIED IDEOGRAPH - 0xB541: 0x6E19, //CJK UNIFIED IDEOGRAPH - 0xB542: 0x6E4E, //CJK UNIFIED IDEOGRAPH - 0xB543: 0x6E63, //CJK UNIFIED IDEOGRAPH - 0xB544: 0x6E44, //CJK UNIFIED IDEOGRAPH - 0xB545: 0x6E72, //CJK UNIFIED IDEOGRAPH - 0xB546: 0x6E69, //CJK UNIFIED IDEOGRAPH - 0xB547: 0x6E5F, //CJK UNIFIED IDEOGRAPH - 0xB548: 0x7119, //CJK UNIFIED IDEOGRAPH - 0xB549: 0x711A, //CJK UNIFIED IDEOGRAPH - 0xB54A: 0x7126, //CJK UNIFIED IDEOGRAPH - 0xB54B: 0x7130, //CJK UNIFIED IDEOGRAPH - 0xB54C: 0x7121, //CJK UNIFIED IDEOGRAPH - 0xB54D: 0x7136, //CJK UNIFIED IDEOGRAPH - 0xB54E: 0x716E, //CJK UNIFIED IDEOGRAPH - 0xB54F: 0x711C, //CJK UNIFIED IDEOGRAPH - 0xB550: 0x724C, //CJK UNIFIED IDEOGRAPH - 0xB551: 0x7284, //CJK UNIFIED IDEOGRAPH - 0xB552: 0x7280, //CJK UNIFIED IDEOGRAPH - 0xB553: 0x7336, //CJK UNIFIED IDEOGRAPH - 0xB554: 0x7325, //CJK UNIFIED IDEOGRAPH - 0xB555: 0x7334, //CJK UNIFIED IDEOGRAPH - 0xB556: 0x7329, //CJK UNIFIED IDEOGRAPH - 0xB557: 0x743A, //CJK UNIFIED IDEOGRAPH - 0xB558: 0x742A, //CJK UNIFIED IDEOGRAPH - 0xB559: 0x7433, //CJK UNIFIED IDEOGRAPH - 0xB55A: 0x7422, //CJK UNIFIED IDEOGRAPH - 0xB55B: 0x7425, //CJK UNIFIED IDEOGRAPH - 0xB55C: 0x7435, //CJK UNIFIED IDEOGRAPH - 0xB55D: 0x7436, //CJK UNIFIED IDEOGRAPH - 0xB55E: 0x7434, //CJK UNIFIED IDEOGRAPH - 0xB55F: 0x742F, //CJK UNIFIED IDEOGRAPH - 0xB560: 0x741B, //CJK UNIFIED IDEOGRAPH - 0xB561: 0x7426, //CJK UNIFIED IDEOGRAPH - 0xB562: 0x7428, //CJK UNIFIED IDEOGRAPH - 0xB563: 0x7525, //CJK UNIFIED IDEOGRAPH - 0xB564: 0x7526, //CJK UNIFIED IDEOGRAPH - 0xB565: 0x756B, //CJK UNIFIED IDEOGRAPH - 0xB566: 0x756A, //CJK UNIFIED IDEOGRAPH - 0xB567: 0x75E2, //CJK UNIFIED IDEOGRAPH - 0xB568: 0x75DB, //CJK UNIFIED IDEOGRAPH - 0xB569: 0x75E3, //CJK UNIFIED IDEOGRAPH - 0xB56A: 0x75D9, //CJK UNIFIED IDEOGRAPH - 0xB56B: 0x75D8, //CJK UNIFIED IDEOGRAPH - 0xB56C: 0x75DE, //CJK UNIFIED IDEOGRAPH - 0xB56D: 0x75E0, //CJK UNIFIED IDEOGRAPH - 0xB56E: 0x767B, //CJK UNIFIED IDEOGRAPH - 0xB56F: 0x767C, //CJK UNIFIED IDEOGRAPH - 0xB570: 0x7696, //CJK UNIFIED IDEOGRAPH - 0xB571: 0x7693, //CJK UNIFIED IDEOGRAPH - 0xB572: 0x76B4, //CJK UNIFIED IDEOGRAPH - 0xB573: 0x76DC, //CJK UNIFIED IDEOGRAPH - 0xB574: 0x774F, //CJK UNIFIED IDEOGRAPH - 0xB575: 0x77ED, //CJK UNIFIED IDEOGRAPH - 0xB576: 0x785D, //CJK UNIFIED IDEOGRAPH - 0xB577: 0x786C, //CJK UNIFIED IDEOGRAPH - 0xB578: 0x786F, //CJK UNIFIED IDEOGRAPH - 0xB579: 0x7A0D, //CJK UNIFIED IDEOGRAPH - 0xB57A: 0x7A08, //CJK UNIFIED IDEOGRAPH - 0xB57B: 0x7A0B, //CJK UNIFIED IDEOGRAPH - 0xB57C: 0x7A05, //CJK UNIFIED IDEOGRAPH - 0xB57D: 0x7A00, //CJK UNIFIED IDEOGRAPH - 0xB57E: 0x7A98, //CJK UNIFIED IDEOGRAPH - 0xB5A1: 0x7A97, //CJK UNIFIED IDEOGRAPH - 0xB5A2: 0x7A96, //CJK UNIFIED IDEOGRAPH - 0xB5A3: 0x7AE5, //CJK UNIFIED IDEOGRAPH - 0xB5A4: 0x7AE3, //CJK UNIFIED IDEOGRAPH - 0xB5A5: 0x7B49, //CJK UNIFIED IDEOGRAPH - 0xB5A6: 0x7B56, //CJK UNIFIED IDEOGRAPH - 0xB5A7: 0x7B46, //CJK UNIFIED IDEOGRAPH - 0xB5A8: 0x7B50, //CJK UNIFIED IDEOGRAPH - 0xB5A9: 0x7B52, //CJK UNIFIED IDEOGRAPH - 0xB5AA: 0x7B54, //CJK UNIFIED IDEOGRAPH - 0xB5AB: 0x7B4D, //CJK UNIFIED IDEOGRAPH - 0xB5AC: 0x7B4B, //CJK UNIFIED IDEOGRAPH - 0xB5AD: 0x7B4F, //CJK UNIFIED IDEOGRAPH - 0xB5AE: 0x7B51, //CJK UNIFIED IDEOGRAPH - 0xB5AF: 0x7C9F, //CJK UNIFIED IDEOGRAPH - 0xB5B0: 0x7CA5, //CJK UNIFIED IDEOGRAPH - 0xB5B1: 0x7D5E, //CJK UNIFIED IDEOGRAPH - 0xB5B2: 0x7D50, //CJK UNIFIED IDEOGRAPH - 0xB5B3: 0x7D68, //CJK UNIFIED IDEOGRAPH - 0xB5B4: 0x7D55, //CJK UNIFIED IDEOGRAPH - 0xB5B5: 0x7D2B, //CJK UNIFIED IDEOGRAPH - 0xB5B6: 0x7D6E, //CJK UNIFIED IDEOGRAPH - 0xB5B7: 0x7D72, //CJK UNIFIED IDEOGRAPH - 0xB5B8: 0x7D61, //CJK UNIFIED IDEOGRAPH - 0xB5B9: 0x7D66, //CJK UNIFIED IDEOGRAPH - 0xB5BA: 0x7D62, //CJK UNIFIED IDEOGRAPH - 0xB5BB: 0x7D70, //CJK UNIFIED IDEOGRAPH - 0xB5BC: 0x7D73, //CJK UNIFIED IDEOGRAPH - 0xB5BD: 0x5584, //CJK UNIFIED IDEOGRAPH - 0xB5BE: 0x7FD4, //CJK UNIFIED IDEOGRAPH - 0xB5BF: 0x7FD5, //CJK UNIFIED IDEOGRAPH - 0xB5C0: 0x800B, //CJK UNIFIED IDEOGRAPH - 0xB5C1: 0x8052, //CJK UNIFIED IDEOGRAPH - 0xB5C2: 0x8085, //CJK UNIFIED IDEOGRAPH - 0xB5C3: 0x8155, //CJK UNIFIED IDEOGRAPH - 0xB5C4: 0x8154, //CJK UNIFIED IDEOGRAPH - 0xB5C5: 0x814B, //CJK UNIFIED IDEOGRAPH - 0xB5C6: 0x8151, //CJK UNIFIED IDEOGRAPH - 0xB5C7: 0x814E, //CJK UNIFIED IDEOGRAPH - 0xB5C8: 0x8139, //CJK UNIFIED IDEOGRAPH - 0xB5C9: 0x8146, //CJK UNIFIED IDEOGRAPH - 0xB5CA: 0x813E, //CJK UNIFIED IDEOGRAPH - 0xB5CB: 0x814C, //CJK UNIFIED IDEOGRAPH - 0xB5CC: 0x8153, //CJK UNIFIED IDEOGRAPH - 0xB5CD: 0x8174, //CJK UNIFIED IDEOGRAPH - 0xB5CE: 0x8212, //CJK UNIFIED IDEOGRAPH - 0xB5CF: 0x821C, //CJK UNIFIED IDEOGRAPH - 0xB5D0: 0x83E9, //CJK UNIFIED IDEOGRAPH - 0xB5D1: 0x8403, //CJK UNIFIED IDEOGRAPH - 0xB5D2: 0x83F8, //CJK UNIFIED IDEOGRAPH - 0xB5D3: 0x840D, //CJK UNIFIED IDEOGRAPH - 0xB5D4: 0x83E0, //CJK UNIFIED IDEOGRAPH - 0xB5D5: 0x83C5, //CJK UNIFIED IDEOGRAPH - 0xB5D6: 0x840B, //CJK UNIFIED IDEOGRAPH - 0xB5D7: 0x83C1, //CJK UNIFIED IDEOGRAPH - 0xB5D8: 0x83EF, //CJK UNIFIED IDEOGRAPH - 0xB5D9: 0x83F1, //CJK UNIFIED IDEOGRAPH - 0xB5DA: 0x83F4, //CJK UNIFIED IDEOGRAPH - 0xB5DB: 0x8457, //CJK UNIFIED IDEOGRAPH - 0xB5DC: 0x840A, //CJK UNIFIED IDEOGRAPH - 0xB5DD: 0x83F0, //CJK UNIFIED IDEOGRAPH - 0xB5DE: 0x840C, //CJK UNIFIED IDEOGRAPH - 0xB5DF: 0x83CC, //CJK UNIFIED IDEOGRAPH - 0xB5E0: 0x83FD, //CJK UNIFIED IDEOGRAPH - 0xB5E1: 0x83F2, //CJK UNIFIED IDEOGRAPH - 0xB5E2: 0x83CA, //CJK UNIFIED IDEOGRAPH - 0xB5E3: 0x8438, //CJK UNIFIED IDEOGRAPH - 0xB5E4: 0x840E, //CJK UNIFIED IDEOGRAPH - 0xB5E5: 0x8404, //CJK UNIFIED IDEOGRAPH - 0xB5E6: 0x83DC, //CJK UNIFIED IDEOGRAPH - 0xB5E7: 0x8407, //CJK UNIFIED IDEOGRAPH - 0xB5E8: 0x83D4, //CJK UNIFIED IDEOGRAPH - 0xB5E9: 0x83DF, //CJK UNIFIED IDEOGRAPH - 0xB5EA: 0x865B, //CJK UNIFIED IDEOGRAPH - 0xB5EB: 0x86DF, //CJK UNIFIED IDEOGRAPH - 0xB5EC: 0x86D9, //CJK UNIFIED IDEOGRAPH - 0xB5ED: 0x86ED, //CJK UNIFIED IDEOGRAPH - 0xB5EE: 0x86D4, //CJK UNIFIED IDEOGRAPH - 0xB5EF: 0x86DB, //CJK UNIFIED IDEOGRAPH - 0xB5F0: 0x86E4, //CJK UNIFIED IDEOGRAPH - 0xB5F1: 0x86D0, //CJK UNIFIED IDEOGRAPH - 0xB5F2: 0x86DE, //CJK UNIFIED IDEOGRAPH - 0xB5F3: 0x8857, //CJK UNIFIED IDEOGRAPH - 0xB5F4: 0x88C1, //CJK UNIFIED IDEOGRAPH - 0xB5F5: 0x88C2, //CJK UNIFIED IDEOGRAPH - 0xB5F6: 0x88B1, //CJK UNIFIED IDEOGRAPH - 0xB5F7: 0x8983, //CJK UNIFIED IDEOGRAPH - 0xB5F8: 0x8996, //CJK UNIFIED IDEOGRAPH - 0xB5F9: 0x8A3B, //CJK UNIFIED IDEOGRAPH - 0xB5FA: 0x8A60, //CJK UNIFIED IDEOGRAPH - 0xB5FB: 0x8A55, //CJK UNIFIED IDEOGRAPH - 0xB5FC: 0x8A5E, //CJK UNIFIED IDEOGRAPH - 0xB5FD: 0x8A3C, //CJK UNIFIED IDEOGRAPH - 0xB5FE: 0x8A41, //CJK UNIFIED IDEOGRAPH - 0xB640: 0x8A54, //CJK UNIFIED IDEOGRAPH - 0xB641: 0x8A5B, //CJK UNIFIED IDEOGRAPH - 0xB642: 0x8A50, //CJK UNIFIED IDEOGRAPH - 0xB643: 0x8A46, //CJK UNIFIED IDEOGRAPH - 0xB644: 0x8A34, //CJK UNIFIED IDEOGRAPH - 0xB645: 0x8A3A, //CJK UNIFIED IDEOGRAPH - 0xB646: 0x8A36, //CJK UNIFIED IDEOGRAPH - 0xB647: 0x8A56, //CJK UNIFIED IDEOGRAPH - 0xB648: 0x8C61, //CJK UNIFIED IDEOGRAPH - 0xB649: 0x8C82, //CJK UNIFIED IDEOGRAPH - 0xB64A: 0x8CAF, //CJK UNIFIED IDEOGRAPH - 0xB64B: 0x8CBC, //CJK UNIFIED IDEOGRAPH - 0xB64C: 0x8CB3, //CJK UNIFIED IDEOGRAPH - 0xB64D: 0x8CBD, //CJK UNIFIED IDEOGRAPH - 0xB64E: 0x8CC1, //CJK UNIFIED IDEOGRAPH - 0xB64F: 0x8CBB, //CJK UNIFIED IDEOGRAPH - 0xB650: 0x8CC0, //CJK UNIFIED IDEOGRAPH - 0xB651: 0x8CB4, //CJK UNIFIED IDEOGRAPH - 0xB652: 0x8CB7, //CJK UNIFIED IDEOGRAPH - 0xB653: 0x8CB6, //CJK UNIFIED IDEOGRAPH - 0xB654: 0x8CBF, //CJK UNIFIED IDEOGRAPH - 0xB655: 0x8CB8, //CJK UNIFIED IDEOGRAPH - 0xB656: 0x8D8A, //CJK UNIFIED IDEOGRAPH - 0xB657: 0x8D85, //CJK UNIFIED IDEOGRAPH - 0xB658: 0x8D81, //CJK UNIFIED IDEOGRAPH - 0xB659: 0x8DCE, //CJK UNIFIED IDEOGRAPH - 0xB65A: 0x8DDD, //CJK UNIFIED IDEOGRAPH - 0xB65B: 0x8DCB, //CJK UNIFIED IDEOGRAPH - 0xB65C: 0x8DDA, //CJK UNIFIED IDEOGRAPH - 0xB65D: 0x8DD1, //CJK UNIFIED IDEOGRAPH - 0xB65E: 0x8DCC, //CJK UNIFIED IDEOGRAPH - 0xB65F: 0x8DDB, //CJK UNIFIED IDEOGRAPH - 0xB660: 0x8DC6, //CJK UNIFIED IDEOGRAPH - 0xB661: 0x8EFB, //CJK UNIFIED IDEOGRAPH - 0xB662: 0x8EF8, //CJK UNIFIED IDEOGRAPH - 0xB663: 0x8EFC, //CJK UNIFIED IDEOGRAPH - 0xB664: 0x8F9C, //CJK UNIFIED IDEOGRAPH - 0xB665: 0x902E, //CJK UNIFIED IDEOGRAPH - 0xB666: 0x9035, //CJK UNIFIED IDEOGRAPH - 0xB667: 0x9031, //CJK UNIFIED IDEOGRAPH - 0xB668: 0x9038, //CJK UNIFIED IDEOGRAPH - 0xB669: 0x9032, //CJK UNIFIED IDEOGRAPH - 0xB66A: 0x9036, //CJK UNIFIED IDEOGRAPH - 0xB66B: 0x9102, //CJK UNIFIED IDEOGRAPH - 0xB66C: 0x90F5, //CJK UNIFIED IDEOGRAPH - 0xB66D: 0x9109, //CJK UNIFIED IDEOGRAPH - 0xB66E: 0x90FE, //CJK UNIFIED IDEOGRAPH - 0xB66F: 0x9163, //CJK UNIFIED IDEOGRAPH - 0xB670: 0x9165, //CJK UNIFIED IDEOGRAPH - 0xB671: 0x91CF, //CJK UNIFIED IDEOGRAPH - 0xB672: 0x9214, //CJK UNIFIED IDEOGRAPH - 0xB673: 0x9215, //CJK UNIFIED IDEOGRAPH - 0xB674: 0x9223, //CJK UNIFIED IDEOGRAPH - 0xB675: 0x9209, //CJK UNIFIED IDEOGRAPH - 0xB676: 0x921E, //CJK UNIFIED IDEOGRAPH - 0xB677: 0x920D, //CJK UNIFIED IDEOGRAPH - 0xB678: 0x9210, //CJK UNIFIED IDEOGRAPH - 0xB679: 0x9207, //CJK UNIFIED IDEOGRAPH - 0xB67A: 0x9211, //CJK UNIFIED IDEOGRAPH - 0xB67B: 0x9594, //CJK UNIFIED IDEOGRAPH - 0xB67C: 0x958F, //CJK UNIFIED IDEOGRAPH - 0xB67D: 0x958B, //CJK UNIFIED IDEOGRAPH - 0xB67E: 0x9591, //CJK UNIFIED IDEOGRAPH - 0xB6A1: 0x9593, //CJK UNIFIED IDEOGRAPH - 0xB6A2: 0x9592, //CJK UNIFIED IDEOGRAPH - 0xB6A3: 0x958E, //CJK UNIFIED IDEOGRAPH - 0xB6A4: 0x968A, //CJK UNIFIED IDEOGRAPH - 0xB6A5: 0x968E, //CJK UNIFIED IDEOGRAPH - 0xB6A6: 0x968B, //CJK UNIFIED IDEOGRAPH - 0xB6A7: 0x967D, //CJK UNIFIED IDEOGRAPH - 0xB6A8: 0x9685, //CJK UNIFIED IDEOGRAPH - 0xB6A9: 0x9686, //CJK UNIFIED IDEOGRAPH - 0xB6AA: 0x968D, //CJK UNIFIED IDEOGRAPH - 0xB6AB: 0x9672, //CJK UNIFIED IDEOGRAPH - 0xB6AC: 0x9684, //CJK UNIFIED IDEOGRAPH - 0xB6AD: 0x96C1, //CJK UNIFIED IDEOGRAPH - 0xB6AE: 0x96C5, //CJK UNIFIED IDEOGRAPH - 0xB6AF: 0x96C4, //CJK UNIFIED IDEOGRAPH - 0xB6B0: 0x96C6, //CJK UNIFIED IDEOGRAPH - 0xB6B1: 0x96C7, //CJK UNIFIED IDEOGRAPH - 0xB6B2: 0x96EF, //CJK UNIFIED IDEOGRAPH - 0xB6B3: 0x96F2, //CJK UNIFIED IDEOGRAPH - 0xB6B4: 0x97CC, //CJK UNIFIED IDEOGRAPH - 0xB6B5: 0x9805, //CJK UNIFIED IDEOGRAPH - 0xB6B6: 0x9806, //CJK UNIFIED IDEOGRAPH - 0xB6B7: 0x9808, //CJK UNIFIED IDEOGRAPH - 0xB6B8: 0x98E7, //CJK UNIFIED IDEOGRAPH - 0xB6B9: 0x98EA, //CJK UNIFIED IDEOGRAPH - 0xB6BA: 0x98EF, //CJK UNIFIED IDEOGRAPH - 0xB6BB: 0x98E9, //CJK UNIFIED IDEOGRAPH - 0xB6BC: 0x98F2, //CJK UNIFIED IDEOGRAPH - 0xB6BD: 0x98ED, //CJK UNIFIED IDEOGRAPH - 0xB6BE: 0x99AE, //CJK UNIFIED IDEOGRAPH - 0xB6BF: 0x99AD, //CJK UNIFIED IDEOGRAPH - 0xB6C0: 0x9EC3, //CJK UNIFIED IDEOGRAPH - 0xB6C1: 0x9ECD, //CJK UNIFIED IDEOGRAPH - 0xB6C2: 0x9ED1, //CJK UNIFIED IDEOGRAPH - 0xB6C3: 0x4E82, //CJK UNIFIED IDEOGRAPH - 0xB6C4: 0x50AD, //CJK UNIFIED IDEOGRAPH - 0xB6C5: 0x50B5, //CJK UNIFIED IDEOGRAPH - 0xB6C6: 0x50B2, //CJK UNIFIED IDEOGRAPH - 0xB6C7: 0x50B3, //CJK UNIFIED IDEOGRAPH - 0xB6C8: 0x50C5, //CJK UNIFIED IDEOGRAPH - 0xB6C9: 0x50BE, //CJK UNIFIED IDEOGRAPH - 0xB6CA: 0x50AC, //CJK UNIFIED IDEOGRAPH - 0xB6CB: 0x50B7, //CJK UNIFIED IDEOGRAPH - 0xB6CC: 0x50BB, //CJK UNIFIED IDEOGRAPH - 0xB6CD: 0x50AF, //CJK UNIFIED IDEOGRAPH - 0xB6CE: 0x50C7, //CJK UNIFIED IDEOGRAPH - 0xB6CF: 0x527F, //CJK UNIFIED IDEOGRAPH - 0xB6D0: 0x5277, //CJK UNIFIED IDEOGRAPH - 0xB6D1: 0x527D, //CJK UNIFIED IDEOGRAPH - 0xB6D2: 0x52DF, //CJK UNIFIED IDEOGRAPH - 0xB6D3: 0x52E6, //CJK UNIFIED IDEOGRAPH - 0xB6D4: 0x52E4, //CJK UNIFIED IDEOGRAPH - 0xB6D5: 0x52E2, //CJK UNIFIED IDEOGRAPH - 0xB6D6: 0x52E3, //CJK UNIFIED IDEOGRAPH - 0xB6D7: 0x532F, //CJK UNIFIED IDEOGRAPH - 0xB6D8: 0x55DF, //CJK UNIFIED IDEOGRAPH - 0xB6D9: 0x55E8, //CJK UNIFIED IDEOGRAPH - 0xB6DA: 0x55D3, //CJK UNIFIED IDEOGRAPH - 0xB6DB: 0x55E6, //CJK UNIFIED IDEOGRAPH - 0xB6DC: 0x55CE, //CJK UNIFIED IDEOGRAPH - 0xB6DD: 0x55DC, //CJK UNIFIED IDEOGRAPH - 0xB6DE: 0x55C7, //CJK UNIFIED IDEOGRAPH - 0xB6DF: 0x55D1, //CJK UNIFIED IDEOGRAPH - 0xB6E0: 0x55E3, //CJK UNIFIED IDEOGRAPH - 0xB6E1: 0x55E4, //CJK UNIFIED IDEOGRAPH - 0xB6E2: 0x55EF, //CJK UNIFIED IDEOGRAPH - 0xB6E3: 0x55DA, //CJK UNIFIED IDEOGRAPH - 0xB6E4: 0x55E1, //CJK UNIFIED IDEOGRAPH - 0xB6E5: 0x55C5, //CJK UNIFIED IDEOGRAPH - 0xB6E6: 0x55C6, //CJK UNIFIED IDEOGRAPH - 0xB6E7: 0x55E5, //CJK UNIFIED IDEOGRAPH - 0xB6E8: 0x55C9, //CJK UNIFIED IDEOGRAPH - 0xB6E9: 0x5712, //CJK UNIFIED IDEOGRAPH - 0xB6EA: 0x5713, //CJK UNIFIED IDEOGRAPH - 0xB6EB: 0x585E, //CJK UNIFIED IDEOGRAPH - 0xB6EC: 0x5851, //CJK UNIFIED IDEOGRAPH - 0xB6ED: 0x5858, //CJK UNIFIED IDEOGRAPH - 0xB6EE: 0x5857, //CJK UNIFIED IDEOGRAPH - 0xB6EF: 0x585A, //CJK UNIFIED IDEOGRAPH - 0xB6F0: 0x5854, //CJK UNIFIED IDEOGRAPH - 0xB6F1: 0x586B, //CJK UNIFIED IDEOGRAPH - 0xB6F2: 0x584C, //CJK UNIFIED IDEOGRAPH - 0xB6F3: 0x586D, //CJK UNIFIED IDEOGRAPH - 0xB6F4: 0x584A, //CJK UNIFIED IDEOGRAPH - 0xB6F5: 0x5862, //CJK UNIFIED IDEOGRAPH - 0xB6F6: 0x5852, //CJK UNIFIED IDEOGRAPH - 0xB6F7: 0x584B, //CJK UNIFIED IDEOGRAPH - 0xB6F8: 0x5967, //CJK UNIFIED IDEOGRAPH - 0xB6F9: 0x5AC1, //CJK UNIFIED IDEOGRAPH - 0xB6FA: 0x5AC9, //CJK UNIFIED IDEOGRAPH - 0xB6FB: 0x5ACC, //CJK UNIFIED IDEOGRAPH - 0xB6FC: 0x5ABE, //CJK UNIFIED IDEOGRAPH - 0xB6FD: 0x5ABD, //CJK UNIFIED IDEOGRAPH - 0xB6FE: 0x5ABC, //CJK UNIFIED IDEOGRAPH - 0xB740: 0x5AB3, //CJK UNIFIED IDEOGRAPH - 0xB741: 0x5AC2, //CJK UNIFIED IDEOGRAPH - 0xB742: 0x5AB2, //CJK UNIFIED IDEOGRAPH - 0xB743: 0x5D69, //CJK UNIFIED IDEOGRAPH - 0xB744: 0x5D6F, //CJK UNIFIED IDEOGRAPH - 0xB745: 0x5E4C, //CJK UNIFIED IDEOGRAPH - 0xB746: 0x5E79, //CJK UNIFIED IDEOGRAPH - 0xB747: 0x5EC9, //CJK UNIFIED IDEOGRAPH - 0xB748: 0x5EC8, //CJK UNIFIED IDEOGRAPH - 0xB749: 0x5F12, //CJK UNIFIED IDEOGRAPH - 0xB74A: 0x5F59, //CJK UNIFIED IDEOGRAPH - 0xB74B: 0x5FAC, //CJK UNIFIED IDEOGRAPH - 0xB74C: 0x5FAE, //CJK UNIFIED IDEOGRAPH - 0xB74D: 0x611A, //CJK UNIFIED IDEOGRAPH - 0xB74E: 0x610F, //CJK UNIFIED IDEOGRAPH - 0xB74F: 0x6148, //CJK UNIFIED IDEOGRAPH - 0xB750: 0x611F, //CJK UNIFIED IDEOGRAPH - 0xB751: 0x60F3, //CJK UNIFIED IDEOGRAPH - 0xB752: 0x611B, //CJK UNIFIED IDEOGRAPH - 0xB753: 0x60F9, //CJK UNIFIED IDEOGRAPH - 0xB754: 0x6101, //CJK UNIFIED IDEOGRAPH - 0xB755: 0x6108, //CJK UNIFIED IDEOGRAPH - 0xB756: 0x614E, //CJK UNIFIED IDEOGRAPH - 0xB757: 0x614C, //CJK UNIFIED IDEOGRAPH - 0xB758: 0x6144, //CJK UNIFIED IDEOGRAPH - 0xB759: 0x614D, //CJK UNIFIED IDEOGRAPH - 0xB75A: 0x613E, //CJK UNIFIED IDEOGRAPH - 0xB75B: 0x6134, //CJK UNIFIED IDEOGRAPH - 0xB75C: 0x6127, //CJK UNIFIED IDEOGRAPH - 0xB75D: 0x610D, //CJK UNIFIED IDEOGRAPH - 0xB75E: 0x6106, //CJK UNIFIED IDEOGRAPH - 0xB75F: 0x6137, //CJK UNIFIED IDEOGRAPH - 0xB760: 0x6221, //CJK UNIFIED IDEOGRAPH - 0xB761: 0x6222, //CJK UNIFIED IDEOGRAPH - 0xB762: 0x6413, //CJK UNIFIED IDEOGRAPH - 0xB763: 0x643E, //CJK UNIFIED IDEOGRAPH - 0xB764: 0x641E, //CJK UNIFIED IDEOGRAPH - 0xB765: 0x642A, //CJK UNIFIED IDEOGRAPH - 0xB766: 0x642D, //CJK UNIFIED IDEOGRAPH - 0xB767: 0x643D, //CJK UNIFIED IDEOGRAPH - 0xB768: 0x642C, //CJK UNIFIED IDEOGRAPH - 0xB769: 0x640F, //CJK UNIFIED IDEOGRAPH - 0xB76A: 0x641C, //CJK UNIFIED IDEOGRAPH - 0xB76B: 0x6414, //CJK UNIFIED IDEOGRAPH - 0xB76C: 0x640D, //CJK UNIFIED IDEOGRAPH - 0xB76D: 0x6436, //CJK UNIFIED IDEOGRAPH - 0xB76E: 0x6416, //CJK UNIFIED IDEOGRAPH - 0xB76F: 0x6417, //CJK UNIFIED IDEOGRAPH - 0xB770: 0x6406, //CJK UNIFIED IDEOGRAPH - 0xB771: 0x656C, //CJK UNIFIED IDEOGRAPH - 0xB772: 0x659F, //CJK UNIFIED IDEOGRAPH - 0xB773: 0x65B0, //CJK UNIFIED IDEOGRAPH - 0xB774: 0x6697, //CJK UNIFIED IDEOGRAPH - 0xB775: 0x6689, //CJK UNIFIED IDEOGRAPH - 0xB776: 0x6687, //CJK UNIFIED IDEOGRAPH - 0xB777: 0x6688, //CJK UNIFIED IDEOGRAPH - 0xB778: 0x6696, //CJK UNIFIED IDEOGRAPH - 0xB779: 0x6684, //CJK UNIFIED IDEOGRAPH - 0xB77A: 0x6698, //CJK UNIFIED IDEOGRAPH - 0xB77B: 0x668D, //CJK UNIFIED IDEOGRAPH - 0xB77C: 0x6703, //CJK UNIFIED IDEOGRAPH - 0xB77D: 0x6994, //CJK UNIFIED IDEOGRAPH - 0xB77E: 0x696D, //CJK UNIFIED IDEOGRAPH - 0xB7A1: 0x695A, //CJK UNIFIED IDEOGRAPH - 0xB7A2: 0x6977, //CJK UNIFIED IDEOGRAPH - 0xB7A3: 0x6960, //CJK UNIFIED IDEOGRAPH - 0xB7A4: 0x6954, //CJK UNIFIED IDEOGRAPH - 0xB7A5: 0x6975, //CJK UNIFIED IDEOGRAPH - 0xB7A6: 0x6930, //CJK UNIFIED IDEOGRAPH - 0xB7A7: 0x6982, //CJK UNIFIED IDEOGRAPH - 0xB7A8: 0x694A, //CJK UNIFIED IDEOGRAPH - 0xB7A9: 0x6968, //CJK UNIFIED IDEOGRAPH - 0xB7AA: 0x696B, //CJK UNIFIED IDEOGRAPH - 0xB7AB: 0x695E, //CJK UNIFIED IDEOGRAPH - 0xB7AC: 0x6953, //CJK UNIFIED IDEOGRAPH - 0xB7AD: 0x6979, //CJK UNIFIED IDEOGRAPH - 0xB7AE: 0x6986, //CJK UNIFIED IDEOGRAPH - 0xB7AF: 0x695D, //CJK UNIFIED IDEOGRAPH - 0xB7B0: 0x6963, //CJK UNIFIED IDEOGRAPH - 0xB7B1: 0x695B, //CJK UNIFIED IDEOGRAPH - 0xB7B2: 0x6B47, //CJK UNIFIED IDEOGRAPH - 0xB7B3: 0x6B72, //CJK UNIFIED IDEOGRAPH - 0xB7B4: 0x6BC0, //CJK UNIFIED IDEOGRAPH - 0xB7B5: 0x6BBF, //CJK UNIFIED IDEOGRAPH - 0xB7B6: 0x6BD3, //CJK UNIFIED IDEOGRAPH - 0xB7B7: 0x6BFD, //CJK UNIFIED IDEOGRAPH - 0xB7B8: 0x6EA2, //CJK UNIFIED IDEOGRAPH - 0xB7B9: 0x6EAF, //CJK UNIFIED IDEOGRAPH - 0xB7BA: 0x6ED3, //CJK UNIFIED IDEOGRAPH - 0xB7BB: 0x6EB6, //CJK UNIFIED IDEOGRAPH - 0xB7BC: 0x6EC2, //CJK UNIFIED IDEOGRAPH - 0xB7BD: 0x6E90, //CJK UNIFIED IDEOGRAPH - 0xB7BE: 0x6E9D, //CJK UNIFIED IDEOGRAPH - 0xB7BF: 0x6EC7, //CJK UNIFIED IDEOGRAPH - 0xB7C0: 0x6EC5, //CJK UNIFIED IDEOGRAPH - 0xB7C1: 0x6EA5, //CJK UNIFIED IDEOGRAPH - 0xB7C2: 0x6E98, //CJK UNIFIED IDEOGRAPH - 0xB7C3: 0x6EBC, //CJK UNIFIED IDEOGRAPH - 0xB7C4: 0x6EBA, //CJK UNIFIED IDEOGRAPH - 0xB7C5: 0x6EAB, //CJK UNIFIED IDEOGRAPH - 0xB7C6: 0x6ED1, //CJK UNIFIED IDEOGRAPH - 0xB7C7: 0x6E96, //CJK UNIFIED IDEOGRAPH - 0xB7C8: 0x6E9C, //CJK UNIFIED IDEOGRAPH - 0xB7C9: 0x6EC4, //CJK UNIFIED IDEOGRAPH - 0xB7CA: 0x6ED4, //CJK UNIFIED IDEOGRAPH - 0xB7CB: 0x6EAA, //CJK UNIFIED IDEOGRAPH - 0xB7CC: 0x6EA7, //CJK UNIFIED IDEOGRAPH - 0xB7CD: 0x6EB4, //CJK UNIFIED IDEOGRAPH - 0xB7CE: 0x714E, //CJK UNIFIED IDEOGRAPH - 0xB7CF: 0x7159, //CJK UNIFIED IDEOGRAPH - 0xB7D0: 0x7169, //CJK UNIFIED IDEOGRAPH - 0xB7D1: 0x7164, //CJK UNIFIED IDEOGRAPH - 0xB7D2: 0x7149, //CJK UNIFIED IDEOGRAPH - 0xB7D3: 0x7167, //CJK UNIFIED IDEOGRAPH - 0xB7D4: 0x715C, //CJK UNIFIED IDEOGRAPH - 0xB7D5: 0x716C, //CJK UNIFIED IDEOGRAPH - 0xB7D6: 0x7166, //CJK UNIFIED IDEOGRAPH - 0xB7D7: 0x714C, //CJK UNIFIED IDEOGRAPH - 0xB7D8: 0x7165, //CJK UNIFIED IDEOGRAPH - 0xB7D9: 0x715E, //CJK UNIFIED IDEOGRAPH - 0xB7DA: 0x7146, //CJK UNIFIED IDEOGRAPH - 0xB7DB: 0x7168, //CJK UNIFIED IDEOGRAPH - 0xB7DC: 0x7156, //CJK UNIFIED IDEOGRAPH - 0xB7DD: 0x723A, //CJK UNIFIED IDEOGRAPH - 0xB7DE: 0x7252, //CJK UNIFIED IDEOGRAPH - 0xB7DF: 0x7337, //CJK UNIFIED IDEOGRAPH - 0xB7E0: 0x7345, //CJK UNIFIED IDEOGRAPH - 0xB7E1: 0x733F, //CJK UNIFIED IDEOGRAPH - 0xB7E2: 0x733E, //CJK UNIFIED IDEOGRAPH - 0xB7E3: 0x746F, //CJK UNIFIED IDEOGRAPH - 0xB7E4: 0x745A, //CJK UNIFIED IDEOGRAPH - 0xB7E5: 0x7455, //CJK UNIFIED IDEOGRAPH - 0xB7E6: 0x745F, //CJK UNIFIED IDEOGRAPH - 0xB7E7: 0x745E, //CJK UNIFIED IDEOGRAPH - 0xB7E8: 0x7441, //CJK UNIFIED IDEOGRAPH - 0xB7E9: 0x743F, //CJK UNIFIED IDEOGRAPH - 0xB7EA: 0x7459, //CJK UNIFIED IDEOGRAPH - 0xB7EB: 0x745B, //CJK UNIFIED IDEOGRAPH - 0xB7EC: 0x745C, //CJK UNIFIED IDEOGRAPH - 0xB7ED: 0x7576, //CJK UNIFIED IDEOGRAPH - 0xB7EE: 0x7578, //CJK UNIFIED IDEOGRAPH - 0xB7EF: 0x7600, //CJK UNIFIED IDEOGRAPH - 0xB7F0: 0x75F0, //CJK UNIFIED IDEOGRAPH - 0xB7F1: 0x7601, //CJK UNIFIED IDEOGRAPH - 0xB7F2: 0x75F2, //CJK UNIFIED IDEOGRAPH - 0xB7F3: 0x75F1, //CJK UNIFIED IDEOGRAPH - 0xB7F4: 0x75FA, //CJK UNIFIED IDEOGRAPH - 0xB7F5: 0x75FF, //CJK UNIFIED IDEOGRAPH - 0xB7F6: 0x75F4, //CJK UNIFIED IDEOGRAPH - 0xB7F7: 0x75F3, //CJK UNIFIED IDEOGRAPH - 0xB7F8: 0x76DE, //CJK UNIFIED IDEOGRAPH - 0xB7F9: 0x76DF, //CJK UNIFIED IDEOGRAPH - 0xB7FA: 0x775B, //CJK UNIFIED IDEOGRAPH - 0xB7FB: 0x776B, //CJK UNIFIED IDEOGRAPH - 0xB7FC: 0x7766, //CJK UNIFIED IDEOGRAPH - 0xB7FD: 0x775E, //CJK UNIFIED IDEOGRAPH - 0xB7FE: 0x7763, //CJK UNIFIED IDEOGRAPH - 0xB840: 0x7779, //CJK UNIFIED IDEOGRAPH - 0xB841: 0x776A, //CJK UNIFIED IDEOGRAPH - 0xB842: 0x776C, //CJK UNIFIED IDEOGRAPH - 0xB843: 0x775C, //CJK UNIFIED IDEOGRAPH - 0xB844: 0x7765, //CJK UNIFIED IDEOGRAPH - 0xB845: 0x7768, //CJK UNIFIED IDEOGRAPH - 0xB846: 0x7762, //CJK UNIFIED IDEOGRAPH - 0xB847: 0x77EE, //CJK UNIFIED IDEOGRAPH - 0xB848: 0x788E, //CJK UNIFIED IDEOGRAPH - 0xB849: 0x78B0, //CJK UNIFIED IDEOGRAPH - 0xB84A: 0x7897, //CJK UNIFIED IDEOGRAPH - 0xB84B: 0x7898, //CJK UNIFIED IDEOGRAPH - 0xB84C: 0x788C, //CJK UNIFIED IDEOGRAPH - 0xB84D: 0x7889, //CJK UNIFIED IDEOGRAPH - 0xB84E: 0x787C, //CJK UNIFIED IDEOGRAPH - 0xB84F: 0x7891, //CJK UNIFIED IDEOGRAPH - 0xB850: 0x7893, //CJK UNIFIED IDEOGRAPH - 0xB851: 0x787F, //CJK UNIFIED IDEOGRAPH - 0xB852: 0x797A, //CJK UNIFIED IDEOGRAPH - 0xB853: 0x797F, //CJK UNIFIED IDEOGRAPH - 0xB854: 0x7981, //CJK UNIFIED IDEOGRAPH - 0xB855: 0x842C, //CJK UNIFIED IDEOGRAPH - 0xB856: 0x79BD, //CJK UNIFIED IDEOGRAPH - 0xB857: 0x7A1C, //CJK UNIFIED IDEOGRAPH - 0xB858: 0x7A1A, //CJK UNIFIED IDEOGRAPH - 0xB859: 0x7A20, //CJK UNIFIED IDEOGRAPH - 0xB85A: 0x7A14, //CJK UNIFIED IDEOGRAPH - 0xB85B: 0x7A1F, //CJK UNIFIED IDEOGRAPH - 0xB85C: 0x7A1E, //CJK UNIFIED IDEOGRAPH - 0xB85D: 0x7A9F, //CJK UNIFIED IDEOGRAPH - 0xB85E: 0x7AA0, //CJK UNIFIED IDEOGRAPH - 0xB85F: 0x7B77, //CJK UNIFIED IDEOGRAPH - 0xB860: 0x7BC0, //CJK UNIFIED IDEOGRAPH - 0xB861: 0x7B60, //CJK UNIFIED IDEOGRAPH - 0xB862: 0x7B6E, //CJK UNIFIED IDEOGRAPH - 0xB863: 0x7B67, //CJK UNIFIED IDEOGRAPH - 0xB864: 0x7CB1, //CJK UNIFIED IDEOGRAPH - 0xB865: 0x7CB3, //CJK UNIFIED IDEOGRAPH - 0xB866: 0x7CB5, //CJK UNIFIED IDEOGRAPH - 0xB867: 0x7D93, //CJK UNIFIED IDEOGRAPH - 0xB868: 0x7D79, //CJK UNIFIED IDEOGRAPH - 0xB869: 0x7D91, //CJK UNIFIED IDEOGRAPH - 0xB86A: 0x7D81, //CJK UNIFIED IDEOGRAPH - 0xB86B: 0x7D8F, //CJK UNIFIED IDEOGRAPH - 0xB86C: 0x7D5B, //CJK UNIFIED IDEOGRAPH - 0xB86D: 0x7F6E, //CJK UNIFIED IDEOGRAPH - 0xB86E: 0x7F69, //CJK UNIFIED IDEOGRAPH - 0xB86F: 0x7F6A, //CJK UNIFIED IDEOGRAPH - 0xB870: 0x7F72, //CJK UNIFIED IDEOGRAPH - 0xB871: 0x7FA9, //CJK UNIFIED IDEOGRAPH - 0xB872: 0x7FA8, //CJK UNIFIED IDEOGRAPH - 0xB873: 0x7FA4, //CJK UNIFIED IDEOGRAPH - 0xB874: 0x8056, //CJK UNIFIED IDEOGRAPH - 0xB875: 0x8058, //CJK UNIFIED IDEOGRAPH - 0xB876: 0x8086, //CJK UNIFIED IDEOGRAPH - 0xB877: 0x8084, //CJK UNIFIED IDEOGRAPH - 0xB878: 0x8171, //CJK UNIFIED IDEOGRAPH - 0xB879: 0x8170, //CJK UNIFIED IDEOGRAPH - 0xB87A: 0x8178, //CJK UNIFIED IDEOGRAPH - 0xB87B: 0x8165, //CJK UNIFIED IDEOGRAPH - 0xB87C: 0x816E, //CJK UNIFIED IDEOGRAPH - 0xB87D: 0x8173, //CJK UNIFIED IDEOGRAPH - 0xB87E: 0x816B, //CJK UNIFIED IDEOGRAPH - 0xB8A1: 0x8179, //CJK UNIFIED IDEOGRAPH - 0xB8A2: 0x817A, //CJK UNIFIED IDEOGRAPH - 0xB8A3: 0x8166, //CJK UNIFIED IDEOGRAPH - 0xB8A4: 0x8205, //CJK UNIFIED IDEOGRAPH - 0xB8A5: 0x8247, //CJK UNIFIED IDEOGRAPH - 0xB8A6: 0x8482, //CJK UNIFIED IDEOGRAPH - 0xB8A7: 0x8477, //CJK UNIFIED IDEOGRAPH - 0xB8A8: 0x843D, //CJK UNIFIED IDEOGRAPH - 0xB8A9: 0x8431, //CJK UNIFIED IDEOGRAPH - 0xB8AA: 0x8475, //CJK UNIFIED IDEOGRAPH - 0xB8AB: 0x8466, //CJK UNIFIED IDEOGRAPH - 0xB8AC: 0x846B, //CJK UNIFIED IDEOGRAPH - 0xB8AD: 0x8449, //CJK UNIFIED IDEOGRAPH - 0xB8AE: 0x846C, //CJK UNIFIED IDEOGRAPH - 0xB8AF: 0x845B, //CJK UNIFIED IDEOGRAPH - 0xB8B0: 0x843C, //CJK UNIFIED IDEOGRAPH - 0xB8B1: 0x8435, //CJK UNIFIED IDEOGRAPH - 0xB8B2: 0x8461, //CJK UNIFIED IDEOGRAPH - 0xB8B3: 0x8463, //CJK UNIFIED IDEOGRAPH - 0xB8B4: 0x8469, //CJK UNIFIED IDEOGRAPH - 0xB8B5: 0x846D, //CJK UNIFIED IDEOGRAPH - 0xB8B6: 0x8446, //CJK UNIFIED IDEOGRAPH - 0xB8B7: 0x865E, //CJK UNIFIED IDEOGRAPH - 0xB8B8: 0x865C, //CJK UNIFIED IDEOGRAPH - 0xB8B9: 0x865F, //CJK UNIFIED IDEOGRAPH - 0xB8BA: 0x86F9, //CJK UNIFIED IDEOGRAPH - 0xB8BB: 0x8713, //CJK UNIFIED IDEOGRAPH - 0xB8BC: 0x8708, //CJK UNIFIED IDEOGRAPH - 0xB8BD: 0x8707, //CJK UNIFIED IDEOGRAPH - 0xB8BE: 0x8700, //CJK UNIFIED IDEOGRAPH - 0xB8BF: 0x86FE, //CJK UNIFIED IDEOGRAPH - 0xB8C0: 0x86FB, //CJK UNIFIED IDEOGRAPH - 0xB8C1: 0x8702, //CJK UNIFIED IDEOGRAPH - 0xB8C2: 0x8703, //CJK UNIFIED IDEOGRAPH - 0xB8C3: 0x8706, //CJK UNIFIED IDEOGRAPH - 0xB8C4: 0x870A, //CJK UNIFIED IDEOGRAPH - 0xB8C5: 0x8859, //CJK UNIFIED IDEOGRAPH - 0xB8C6: 0x88DF, //CJK UNIFIED IDEOGRAPH - 0xB8C7: 0x88D4, //CJK UNIFIED IDEOGRAPH - 0xB8C8: 0x88D9, //CJK UNIFIED IDEOGRAPH - 0xB8C9: 0x88DC, //CJK UNIFIED IDEOGRAPH - 0xB8CA: 0x88D8, //CJK UNIFIED IDEOGRAPH - 0xB8CB: 0x88DD, //CJK UNIFIED IDEOGRAPH - 0xB8CC: 0x88E1, //CJK UNIFIED IDEOGRAPH - 0xB8CD: 0x88CA, //CJK UNIFIED IDEOGRAPH - 0xB8CE: 0x88D5, //CJK UNIFIED IDEOGRAPH - 0xB8CF: 0x88D2, //CJK UNIFIED IDEOGRAPH - 0xB8D0: 0x899C, //CJK UNIFIED IDEOGRAPH - 0xB8D1: 0x89E3, //CJK UNIFIED IDEOGRAPH - 0xB8D2: 0x8A6B, //CJK UNIFIED IDEOGRAPH - 0xB8D3: 0x8A72, //CJK UNIFIED IDEOGRAPH - 0xB8D4: 0x8A73, //CJK UNIFIED IDEOGRAPH - 0xB8D5: 0x8A66, //CJK UNIFIED IDEOGRAPH - 0xB8D6: 0x8A69, //CJK UNIFIED IDEOGRAPH - 0xB8D7: 0x8A70, //CJK UNIFIED IDEOGRAPH - 0xB8D8: 0x8A87, //CJK UNIFIED IDEOGRAPH - 0xB8D9: 0x8A7C, //CJK UNIFIED IDEOGRAPH - 0xB8DA: 0x8A63, //CJK UNIFIED IDEOGRAPH - 0xB8DB: 0x8AA0, //CJK UNIFIED IDEOGRAPH - 0xB8DC: 0x8A71, //CJK UNIFIED IDEOGRAPH - 0xB8DD: 0x8A85, //CJK UNIFIED IDEOGRAPH - 0xB8DE: 0x8A6D, //CJK UNIFIED IDEOGRAPH - 0xB8DF: 0x8A62, //CJK UNIFIED IDEOGRAPH - 0xB8E0: 0x8A6E, //CJK UNIFIED IDEOGRAPH - 0xB8E1: 0x8A6C, //CJK UNIFIED IDEOGRAPH - 0xB8E2: 0x8A79, //CJK UNIFIED IDEOGRAPH - 0xB8E3: 0x8A7B, //CJK UNIFIED IDEOGRAPH - 0xB8E4: 0x8A3E, //CJK UNIFIED IDEOGRAPH - 0xB8E5: 0x8A68, //CJK UNIFIED IDEOGRAPH - 0xB8E6: 0x8C62, //CJK UNIFIED IDEOGRAPH - 0xB8E7: 0x8C8A, //CJK UNIFIED IDEOGRAPH - 0xB8E8: 0x8C89, //CJK UNIFIED IDEOGRAPH - 0xB8E9: 0x8CCA, //CJK UNIFIED IDEOGRAPH - 0xB8EA: 0x8CC7, //CJK UNIFIED IDEOGRAPH - 0xB8EB: 0x8CC8, //CJK UNIFIED IDEOGRAPH - 0xB8EC: 0x8CC4, //CJK UNIFIED IDEOGRAPH - 0xB8ED: 0x8CB2, //CJK UNIFIED IDEOGRAPH - 0xB8EE: 0x8CC3, //CJK UNIFIED IDEOGRAPH - 0xB8EF: 0x8CC2, //CJK UNIFIED IDEOGRAPH - 0xB8F0: 0x8CC5, //CJK UNIFIED IDEOGRAPH - 0xB8F1: 0x8DE1, //CJK UNIFIED IDEOGRAPH - 0xB8F2: 0x8DDF, //CJK UNIFIED IDEOGRAPH - 0xB8F3: 0x8DE8, //CJK UNIFIED IDEOGRAPH - 0xB8F4: 0x8DEF, //CJK UNIFIED IDEOGRAPH - 0xB8F5: 0x8DF3, //CJK UNIFIED IDEOGRAPH - 0xB8F6: 0x8DFA, //CJK UNIFIED IDEOGRAPH - 0xB8F7: 0x8DEA, //CJK UNIFIED IDEOGRAPH - 0xB8F8: 0x8DE4, //CJK UNIFIED IDEOGRAPH - 0xB8F9: 0x8DE6, //CJK UNIFIED IDEOGRAPH - 0xB8FA: 0x8EB2, //CJK UNIFIED IDEOGRAPH - 0xB8FB: 0x8F03, //CJK UNIFIED IDEOGRAPH - 0xB8FC: 0x8F09, //CJK UNIFIED IDEOGRAPH - 0xB8FD: 0x8EFE, //CJK UNIFIED IDEOGRAPH - 0xB8FE: 0x8F0A, //CJK UNIFIED IDEOGRAPH - 0xB940: 0x8F9F, //CJK UNIFIED IDEOGRAPH - 0xB941: 0x8FB2, //CJK UNIFIED IDEOGRAPH - 0xB942: 0x904B, //CJK UNIFIED IDEOGRAPH - 0xB943: 0x904A, //CJK UNIFIED IDEOGRAPH - 0xB944: 0x9053, //CJK UNIFIED IDEOGRAPH - 0xB945: 0x9042, //CJK UNIFIED IDEOGRAPH - 0xB946: 0x9054, //CJK UNIFIED IDEOGRAPH - 0xB947: 0x903C, //CJK UNIFIED IDEOGRAPH - 0xB948: 0x9055, //CJK UNIFIED IDEOGRAPH - 0xB949: 0x9050, //CJK UNIFIED IDEOGRAPH - 0xB94A: 0x9047, //CJK UNIFIED IDEOGRAPH - 0xB94B: 0x904F, //CJK UNIFIED IDEOGRAPH - 0xB94C: 0x904E, //CJK UNIFIED IDEOGRAPH - 0xB94D: 0x904D, //CJK UNIFIED IDEOGRAPH - 0xB94E: 0x9051, //CJK UNIFIED IDEOGRAPH - 0xB94F: 0x903E, //CJK UNIFIED IDEOGRAPH - 0xB950: 0x9041, //CJK UNIFIED IDEOGRAPH - 0xB951: 0x9112, //CJK UNIFIED IDEOGRAPH - 0xB952: 0x9117, //CJK UNIFIED IDEOGRAPH - 0xB953: 0x916C, //CJK UNIFIED IDEOGRAPH - 0xB954: 0x916A, //CJK UNIFIED IDEOGRAPH - 0xB955: 0x9169, //CJK UNIFIED IDEOGRAPH - 0xB956: 0x91C9, //CJK UNIFIED IDEOGRAPH - 0xB957: 0x9237, //CJK UNIFIED IDEOGRAPH - 0xB958: 0x9257, //CJK UNIFIED IDEOGRAPH - 0xB959: 0x9238, //CJK UNIFIED IDEOGRAPH - 0xB95A: 0x923D, //CJK UNIFIED IDEOGRAPH - 0xB95B: 0x9240, //CJK UNIFIED IDEOGRAPH - 0xB95C: 0x923E, //CJK UNIFIED IDEOGRAPH - 0xB95D: 0x925B, //CJK UNIFIED IDEOGRAPH - 0xB95E: 0x924B, //CJK UNIFIED IDEOGRAPH - 0xB95F: 0x9264, //CJK UNIFIED IDEOGRAPH - 0xB960: 0x9251, //CJK UNIFIED IDEOGRAPH - 0xB961: 0x9234, //CJK UNIFIED IDEOGRAPH - 0xB962: 0x9249, //CJK UNIFIED IDEOGRAPH - 0xB963: 0x924D, //CJK UNIFIED IDEOGRAPH - 0xB964: 0x9245, //CJK UNIFIED IDEOGRAPH - 0xB965: 0x9239, //CJK UNIFIED IDEOGRAPH - 0xB966: 0x923F, //CJK UNIFIED IDEOGRAPH - 0xB967: 0x925A, //CJK UNIFIED IDEOGRAPH - 0xB968: 0x9598, //CJK UNIFIED IDEOGRAPH - 0xB969: 0x9698, //CJK UNIFIED IDEOGRAPH - 0xB96A: 0x9694, //CJK UNIFIED IDEOGRAPH - 0xB96B: 0x9695, //CJK UNIFIED IDEOGRAPH - 0xB96C: 0x96CD, //CJK UNIFIED IDEOGRAPH - 0xB96D: 0x96CB, //CJK UNIFIED IDEOGRAPH - 0xB96E: 0x96C9, //CJK UNIFIED IDEOGRAPH - 0xB96F: 0x96CA, //CJK UNIFIED IDEOGRAPH - 0xB970: 0x96F7, //CJK UNIFIED IDEOGRAPH - 0xB971: 0x96FB, //CJK UNIFIED IDEOGRAPH - 0xB972: 0x96F9, //CJK UNIFIED IDEOGRAPH - 0xB973: 0x96F6, //CJK UNIFIED IDEOGRAPH - 0xB974: 0x9756, //CJK UNIFIED IDEOGRAPH - 0xB975: 0x9774, //CJK UNIFIED IDEOGRAPH - 0xB976: 0x9776, //CJK UNIFIED IDEOGRAPH - 0xB977: 0x9810, //CJK UNIFIED IDEOGRAPH - 0xB978: 0x9811, //CJK UNIFIED IDEOGRAPH - 0xB979: 0x9813, //CJK UNIFIED IDEOGRAPH - 0xB97A: 0x980A, //CJK UNIFIED IDEOGRAPH - 0xB97B: 0x9812, //CJK UNIFIED IDEOGRAPH - 0xB97C: 0x980C, //CJK UNIFIED IDEOGRAPH - 0xB97D: 0x98FC, //CJK UNIFIED IDEOGRAPH - 0xB97E: 0x98F4, //CJK UNIFIED IDEOGRAPH - 0xB9A1: 0x98FD, //CJK UNIFIED IDEOGRAPH - 0xB9A2: 0x98FE, //CJK UNIFIED IDEOGRAPH - 0xB9A3: 0x99B3, //CJK UNIFIED IDEOGRAPH - 0xB9A4: 0x99B1, //CJK UNIFIED IDEOGRAPH - 0xB9A5: 0x99B4, //CJK UNIFIED IDEOGRAPH - 0xB9A6: 0x9AE1, //CJK UNIFIED IDEOGRAPH - 0xB9A7: 0x9CE9, //CJK UNIFIED IDEOGRAPH - 0xB9A8: 0x9E82, //CJK UNIFIED IDEOGRAPH - 0xB9A9: 0x9F0E, //CJK UNIFIED IDEOGRAPH - 0xB9AA: 0x9F13, //CJK UNIFIED IDEOGRAPH - 0xB9AB: 0x9F20, //CJK UNIFIED IDEOGRAPH - 0xB9AC: 0x50E7, //CJK UNIFIED IDEOGRAPH - 0xB9AD: 0x50EE, //CJK UNIFIED IDEOGRAPH - 0xB9AE: 0x50E5, //CJK UNIFIED IDEOGRAPH - 0xB9AF: 0x50D6, //CJK UNIFIED IDEOGRAPH - 0xB9B0: 0x50ED, //CJK UNIFIED IDEOGRAPH - 0xB9B1: 0x50DA, //CJK UNIFIED IDEOGRAPH - 0xB9B2: 0x50D5, //CJK UNIFIED IDEOGRAPH - 0xB9B3: 0x50CF, //CJK UNIFIED IDEOGRAPH - 0xB9B4: 0x50D1, //CJK UNIFIED IDEOGRAPH - 0xB9B5: 0x50F1, //CJK UNIFIED IDEOGRAPH - 0xB9B6: 0x50CE, //CJK UNIFIED IDEOGRAPH - 0xB9B7: 0x50E9, //CJK UNIFIED IDEOGRAPH - 0xB9B8: 0x5162, //CJK UNIFIED IDEOGRAPH - 0xB9B9: 0x51F3, //CJK UNIFIED IDEOGRAPH - 0xB9BA: 0x5283, //CJK UNIFIED IDEOGRAPH - 0xB9BB: 0x5282, //CJK UNIFIED IDEOGRAPH - 0xB9BC: 0x5331, //CJK UNIFIED IDEOGRAPH - 0xB9BD: 0x53AD, //CJK UNIFIED IDEOGRAPH - 0xB9BE: 0x55FE, //CJK UNIFIED IDEOGRAPH - 0xB9BF: 0x5600, //CJK UNIFIED IDEOGRAPH - 0xB9C0: 0x561B, //CJK UNIFIED IDEOGRAPH - 0xB9C1: 0x5617, //CJK UNIFIED IDEOGRAPH - 0xB9C2: 0x55FD, //CJK UNIFIED IDEOGRAPH - 0xB9C3: 0x5614, //CJK UNIFIED IDEOGRAPH - 0xB9C4: 0x5606, //CJK UNIFIED IDEOGRAPH - 0xB9C5: 0x5609, //CJK UNIFIED IDEOGRAPH - 0xB9C6: 0x560D, //CJK UNIFIED IDEOGRAPH - 0xB9C7: 0x560E, //CJK UNIFIED IDEOGRAPH - 0xB9C8: 0x55F7, //CJK UNIFIED IDEOGRAPH - 0xB9C9: 0x5616, //CJK UNIFIED IDEOGRAPH - 0xB9CA: 0x561F, //CJK UNIFIED IDEOGRAPH - 0xB9CB: 0x5608, //CJK UNIFIED IDEOGRAPH - 0xB9CC: 0x5610, //CJK UNIFIED IDEOGRAPH - 0xB9CD: 0x55F6, //CJK UNIFIED IDEOGRAPH - 0xB9CE: 0x5718, //CJK UNIFIED IDEOGRAPH - 0xB9CF: 0x5716, //CJK UNIFIED IDEOGRAPH - 0xB9D0: 0x5875, //CJK UNIFIED IDEOGRAPH - 0xB9D1: 0x587E, //CJK UNIFIED IDEOGRAPH - 0xB9D2: 0x5883, //CJK UNIFIED IDEOGRAPH - 0xB9D3: 0x5893, //CJK UNIFIED IDEOGRAPH - 0xB9D4: 0x588A, //CJK UNIFIED IDEOGRAPH - 0xB9D5: 0x5879, //CJK UNIFIED IDEOGRAPH - 0xB9D6: 0x5885, //CJK UNIFIED IDEOGRAPH - 0xB9D7: 0x587D, //CJK UNIFIED IDEOGRAPH - 0xB9D8: 0x58FD, //CJK UNIFIED IDEOGRAPH - 0xB9D9: 0x5925, //CJK UNIFIED IDEOGRAPH - 0xB9DA: 0x5922, //CJK UNIFIED IDEOGRAPH - 0xB9DB: 0x5924, //CJK UNIFIED IDEOGRAPH - 0xB9DC: 0x596A, //CJK UNIFIED IDEOGRAPH - 0xB9DD: 0x5969, //CJK UNIFIED IDEOGRAPH - 0xB9DE: 0x5AE1, //CJK UNIFIED IDEOGRAPH - 0xB9DF: 0x5AE6, //CJK UNIFIED IDEOGRAPH - 0xB9E0: 0x5AE9, //CJK UNIFIED IDEOGRAPH - 0xB9E1: 0x5AD7, //CJK UNIFIED IDEOGRAPH - 0xB9E2: 0x5AD6, //CJK UNIFIED IDEOGRAPH - 0xB9E3: 0x5AD8, //CJK UNIFIED IDEOGRAPH - 0xB9E4: 0x5AE3, //CJK UNIFIED IDEOGRAPH - 0xB9E5: 0x5B75, //CJK UNIFIED IDEOGRAPH - 0xB9E6: 0x5BDE, //CJK UNIFIED IDEOGRAPH - 0xB9E7: 0x5BE7, //CJK UNIFIED IDEOGRAPH - 0xB9E8: 0x5BE1, //CJK UNIFIED IDEOGRAPH - 0xB9E9: 0x5BE5, //CJK UNIFIED IDEOGRAPH - 0xB9EA: 0x5BE6, //CJK UNIFIED IDEOGRAPH - 0xB9EB: 0x5BE8, //CJK UNIFIED IDEOGRAPH - 0xB9EC: 0x5BE2, //CJK UNIFIED IDEOGRAPH - 0xB9ED: 0x5BE4, //CJK UNIFIED IDEOGRAPH - 0xB9EE: 0x5BDF, //CJK UNIFIED IDEOGRAPH - 0xB9EF: 0x5C0D, //CJK UNIFIED IDEOGRAPH - 0xB9F0: 0x5C62, //CJK UNIFIED IDEOGRAPH - 0xB9F1: 0x5D84, //CJK UNIFIED IDEOGRAPH - 0xB9F2: 0x5D87, //CJK UNIFIED IDEOGRAPH - 0xB9F3: 0x5E5B, //CJK UNIFIED IDEOGRAPH - 0xB9F4: 0x5E63, //CJK UNIFIED IDEOGRAPH - 0xB9F5: 0x5E55, //CJK UNIFIED IDEOGRAPH - 0xB9F6: 0x5E57, //CJK UNIFIED IDEOGRAPH - 0xB9F7: 0x5E54, //CJK UNIFIED IDEOGRAPH - 0xB9F8: 0x5ED3, //CJK UNIFIED IDEOGRAPH - 0xB9F9: 0x5ED6, //CJK UNIFIED IDEOGRAPH - 0xB9FA: 0x5F0A, //CJK UNIFIED IDEOGRAPH - 0xB9FB: 0x5F46, //CJK UNIFIED IDEOGRAPH - 0xB9FC: 0x5F70, //CJK UNIFIED IDEOGRAPH - 0xB9FD: 0x5FB9, //CJK UNIFIED IDEOGRAPH - 0xB9FE: 0x6147, //CJK UNIFIED IDEOGRAPH - 0xBA40: 0x613F, //CJK UNIFIED IDEOGRAPH - 0xBA41: 0x614B, //CJK UNIFIED IDEOGRAPH - 0xBA42: 0x6177, //CJK UNIFIED IDEOGRAPH - 0xBA43: 0x6162, //CJK UNIFIED IDEOGRAPH - 0xBA44: 0x6163, //CJK UNIFIED IDEOGRAPH - 0xBA45: 0x615F, //CJK UNIFIED IDEOGRAPH - 0xBA46: 0x615A, //CJK UNIFIED IDEOGRAPH - 0xBA47: 0x6158, //CJK UNIFIED IDEOGRAPH - 0xBA48: 0x6175, //CJK UNIFIED IDEOGRAPH - 0xBA49: 0x622A, //CJK UNIFIED IDEOGRAPH - 0xBA4A: 0x6487, //CJK UNIFIED IDEOGRAPH - 0xBA4B: 0x6458, //CJK UNIFIED IDEOGRAPH - 0xBA4C: 0x6454, //CJK UNIFIED IDEOGRAPH - 0xBA4D: 0x64A4, //CJK UNIFIED IDEOGRAPH - 0xBA4E: 0x6478, //CJK UNIFIED IDEOGRAPH - 0xBA4F: 0x645F, //CJK UNIFIED IDEOGRAPH - 0xBA50: 0x647A, //CJK UNIFIED IDEOGRAPH - 0xBA51: 0x6451, //CJK UNIFIED IDEOGRAPH - 0xBA52: 0x6467, //CJK UNIFIED IDEOGRAPH - 0xBA53: 0x6434, //CJK UNIFIED IDEOGRAPH - 0xBA54: 0x646D, //CJK UNIFIED IDEOGRAPH - 0xBA55: 0x647B, //CJK UNIFIED IDEOGRAPH - 0xBA56: 0x6572, //CJK UNIFIED IDEOGRAPH - 0xBA57: 0x65A1, //CJK UNIFIED IDEOGRAPH - 0xBA58: 0x65D7, //CJK UNIFIED IDEOGRAPH - 0xBA59: 0x65D6, //CJK UNIFIED IDEOGRAPH - 0xBA5A: 0x66A2, //CJK UNIFIED IDEOGRAPH - 0xBA5B: 0x66A8, //CJK UNIFIED IDEOGRAPH - 0xBA5C: 0x669D, //CJK UNIFIED IDEOGRAPH - 0xBA5D: 0x699C, //CJK UNIFIED IDEOGRAPH - 0xBA5E: 0x69A8, //CJK UNIFIED IDEOGRAPH - 0xBA5F: 0x6995, //CJK UNIFIED IDEOGRAPH - 0xBA60: 0x69C1, //CJK UNIFIED IDEOGRAPH - 0xBA61: 0x69AE, //CJK UNIFIED IDEOGRAPH - 0xBA62: 0x69D3, //CJK UNIFIED IDEOGRAPH - 0xBA63: 0x69CB, //CJK UNIFIED IDEOGRAPH - 0xBA64: 0x699B, //CJK UNIFIED IDEOGRAPH - 0xBA65: 0x69B7, //CJK UNIFIED IDEOGRAPH - 0xBA66: 0x69BB, //CJK UNIFIED IDEOGRAPH - 0xBA67: 0x69AB, //CJK UNIFIED IDEOGRAPH - 0xBA68: 0x69B4, //CJK UNIFIED IDEOGRAPH - 0xBA69: 0x69D0, //CJK UNIFIED IDEOGRAPH - 0xBA6A: 0x69CD, //CJK UNIFIED IDEOGRAPH - 0xBA6B: 0x69AD, //CJK UNIFIED IDEOGRAPH - 0xBA6C: 0x69CC, //CJK UNIFIED IDEOGRAPH - 0xBA6D: 0x69A6, //CJK UNIFIED IDEOGRAPH - 0xBA6E: 0x69C3, //CJK UNIFIED IDEOGRAPH - 0xBA6F: 0x69A3, //CJK UNIFIED IDEOGRAPH - 0xBA70: 0x6B49, //CJK UNIFIED IDEOGRAPH - 0xBA71: 0x6B4C, //CJK UNIFIED IDEOGRAPH - 0xBA72: 0x6C33, //CJK UNIFIED IDEOGRAPH - 0xBA73: 0x6F33, //CJK UNIFIED IDEOGRAPH - 0xBA74: 0x6F14, //CJK UNIFIED IDEOGRAPH - 0xBA75: 0x6EFE, //CJK UNIFIED IDEOGRAPH - 0xBA76: 0x6F13, //CJK UNIFIED IDEOGRAPH - 0xBA77: 0x6EF4, //CJK UNIFIED IDEOGRAPH - 0xBA78: 0x6F29, //CJK UNIFIED IDEOGRAPH - 0xBA79: 0x6F3E, //CJK UNIFIED IDEOGRAPH - 0xBA7A: 0x6F20, //CJK UNIFIED IDEOGRAPH - 0xBA7B: 0x6F2C, //CJK UNIFIED IDEOGRAPH - 0xBA7C: 0x6F0F, //CJK UNIFIED IDEOGRAPH - 0xBA7D: 0x6F02, //CJK UNIFIED IDEOGRAPH - 0xBA7E: 0x6F22, //CJK UNIFIED IDEOGRAPH - 0xBAA1: 0x6EFF, //CJK UNIFIED IDEOGRAPH - 0xBAA2: 0x6EEF, //CJK UNIFIED IDEOGRAPH - 0xBAA3: 0x6F06, //CJK UNIFIED IDEOGRAPH - 0xBAA4: 0x6F31, //CJK UNIFIED IDEOGRAPH - 0xBAA5: 0x6F38, //CJK UNIFIED IDEOGRAPH - 0xBAA6: 0x6F32, //CJK UNIFIED IDEOGRAPH - 0xBAA7: 0x6F23, //CJK UNIFIED IDEOGRAPH - 0xBAA8: 0x6F15, //CJK UNIFIED IDEOGRAPH - 0xBAA9: 0x6F2B, //CJK UNIFIED IDEOGRAPH - 0xBAAA: 0x6F2F, //CJK UNIFIED IDEOGRAPH - 0xBAAB: 0x6F88, //CJK UNIFIED IDEOGRAPH - 0xBAAC: 0x6F2A, //CJK UNIFIED IDEOGRAPH - 0xBAAD: 0x6EEC, //CJK UNIFIED IDEOGRAPH - 0xBAAE: 0x6F01, //CJK UNIFIED IDEOGRAPH - 0xBAAF: 0x6EF2, //CJK UNIFIED IDEOGRAPH - 0xBAB0: 0x6ECC, //CJK UNIFIED IDEOGRAPH - 0xBAB1: 0x6EF7, //CJK UNIFIED IDEOGRAPH - 0xBAB2: 0x7194, //CJK UNIFIED IDEOGRAPH - 0xBAB3: 0x7199, //CJK UNIFIED IDEOGRAPH - 0xBAB4: 0x717D, //CJK UNIFIED IDEOGRAPH - 0xBAB5: 0x718A, //CJK UNIFIED IDEOGRAPH - 0xBAB6: 0x7184, //CJK UNIFIED IDEOGRAPH - 0xBAB7: 0x7192, //CJK UNIFIED IDEOGRAPH - 0xBAB8: 0x723E, //CJK UNIFIED IDEOGRAPH - 0xBAB9: 0x7292, //CJK UNIFIED IDEOGRAPH - 0xBABA: 0x7296, //CJK UNIFIED IDEOGRAPH - 0xBABB: 0x7344, //CJK UNIFIED IDEOGRAPH - 0xBABC: 0x7350, //CJK UNIFIED IDEOGRAPH - 0xBABD: 0x7464, //CJK UNIFIED IDEOGRAPH - 0xBABE: 0x7463, //CJK UNIFIED IDEOGRAPH - 0xBABF: 0x746A, //CJK UNIFIED IDEOGRAPH - 0xBAC0: 0x7470, //CJK UNIFIED IDEOGRAPH - 0xBAC1: 0x746D, //CJK UNIFIED IDEOGRAPH - 0xBAC2: 0x7504, //CJK UNIFIED IDEOGRAPH - 0xBAC3: 0x7591, //CJK UNIFIED IDEOGRAPH - 0xBAC4: 0x7627, //CJK UNIFIED IDEOGRAPH - 0xBAC5: 0x760D, //CJK UNIFIED IDEOGRAPH - 0xBAC6: 0x760B, //CJK UNIFIED IDEOGRAPH - 0xBAC7: 0x7609, //CJK UNIFIED IDEOGRAPH - 0xBAC8: 0x7613, //CJK UNIFIED IDEOGRAPH - 0xBAC9: 0x76E1, //CJK UNIFIED IDEOGRAPH - 0xBACA: 0x76E3, //CJK UNIFIED IDEOGRAPH - 0xBACB: 0x7784, //CJK UNIFIED IDEOGRAPH - 0xBACC: 0x777D, //CJK UNIFIED IDEOGRAPH - 0xBACD: 0x777F, //CJK UNIFIED IDEOGRAPH - 0xBACE: 0x7761, //CJK UNIFIED IDEOGRAPH - 0xBACF: 0x78C1, //CJK UNIFIED IDEOGRAPH - 0xBAD0: 0x789F, //CJK UNIFIED IDEOGRAPH - 0xBAD1: 0x78A7, //CJK UNIFIED IDEOGRAPH - 0xBAD2: 0x78B3, //CJK UNIFIED IDEOGRAPH - 0xBAD3: 0x78A9, //CJK UNIFIED IDEOGRAPH - 0xBAD4: 0x78A3, //CJK UNIFIED IDEOGRAPH - 0xBAD5: 0x798E, //CJK UNIFIED IDEOGRAPH - 0xBAD6: 0x798F, //CJK UNIFIED IDEOGRAPH - 0xBAD7: 0x798D, //CJK UNIFIED IDEOGRAPH - 0xBAD8: 0x7A2E, //CJK UNIFIED IDEOGRAPH - 0xBAD9: 0x7A31, //CJK UNIFIED IDEOGRAPH - 0xBADA: 0x7AAA, //CJK UNIFIED IDEOGRAPH - 0xBADB: 0x7AA9, //CJK UNIFIED IDEOGRAPH - 0xBADC: 0x7AED, //CJK UNIFIED IDEOGRAPH - 0xBADD: 0x7AEF, //CJK UNIFIED IDEOGRAPH - 0xBADE: 0x7BA1, //CJK UNIFIED IDEOGRAPH - 0xBADF: 0x7B95, //CJK UNIFIED IDEOGRAPH - 0xBAE0: 0x7B8B, //CJK UNIFIED IDEOGRAPH - 0xBAE1: 0x7B75, //CJK UNIFIED IDEOGRAPH - 0xBAE2: 0x7B97, //CJK UNIFIED IDEOGRAPH - 0xBAE3: 0x7B9D, //CJK UNIFIED IDEOGRAPH - 0xBAE4: 0x7B94, //CJK UNIFIED IDEOGRAPH - 0xBAE5: 0x7B8F, //CJK UNIFIED IDEOGRAPH - 0xBAE6: 0x7BB8, //CJK UNIFIED IDEOGRAPH - 0xBAE7: 0x7B87, //CJK UNIFIED IDEOGRAPH - 0xBAE8: 0x7B84, //CJK UNIFIED IDEOGRAPH - 0xBAE9: 0x7CB9, //CJK UNIFIED IDEOGRAPH - 0xBAEA: 0x7CBD, //CJK UNIFIED IDEOGRAPH - 0xBAEB: 0x7CBE, //CJK UNIFIED IDEOGRAPH - 0xBAEC: 0x7DBB, //CJK UNIFIED IDEOGRAPH - 0xBAED: 0x7DB0, //CJK UNIFIED IDEOGRAPH - 0xBAEE: 0x7D9C, //CJK UNIFIED IDEOGRAPH - 0xBAEF: 0x7DBD, //CJK UNIFIED IDEOGRAPH - 0xBAF0: 0x7DBE, //CJK UNIFIED IDEOGRAPH - 0xBAF1: 0x7DA0, //CJK UNIFIED IDEOGRAPH - 0xBAF2: 0x7DCA, //CJK UNIFIED IDEOGRAPH - 0xBAF3: 0x7DB4, //CJK UNIFIED IDEOGRAPH - 0xBAF4: 0x7DB2, //CJK UNIFIED IDEOGRAPH - 0xBAF5: 0x7DB1, //CJK UNIFIED IDEOGRAPH - 0xBAF6: 0x7DBA, //CJK UNIFIED IDEOGRAPH - 0xBAF7: 0x7DA2, //CJK UNIFIED IDEOGRAPH - 0xBAF8: 0x7DBF, //CJK UNIFIED IDEOGRAPH - 0xBAF9: 0x7DB5, //CJK UNIFIED IDEOGRAPH - 0xBAFA: 0x7DB8, //CJK UNIFIED IDEOGRAPH - 0xBAFB: 0x7DAD, //CJK UNIFIED IDEOGRAPH - 0xBAFC: 0x7DD2, //CJK UNIFIED IDEOGRAPH - 0xBAFD: 0x7DC7, //CJK UNIFIED IDEOGRAPH - 0xBAFE: 0x7DAC, //CJK UNIFIED IDEOGRAPH - 0xBB40: 0x7F70, //CJK UNIFIED IDEOGRAPH - 0xBB41: 0x7FE0, //CJK UNIFIED IDEOGRAPH - 0xBB42: 0x7FE1, //CJK UNIFIED IDEOGRAPH - 0xBB43: 0x7FDF, //CJK UNIFIED IDEOGRAPH - 0xBB44: 0x805E, //CJK UNIFIED IDEOGRAPH - 0xBB45: 0x805A, //CJK UNIFIED IDEOGRAPH - 0xBB46: 0x8087, //CJK UNIFIED IDEOGRAPH - 0xBB47: 0x8150, //CJK UNIFIED IDEOGRAPH - 0xBB48: 0x8180, //CJK UNIFIED IDEOGRAPH - 0xBB49: 0x818F, //CJK UNIFIED IDEOGRAPH - 0xBB4A: 0x8188, //CJK UNIFIED IDEOGRAPH - 0xBB4B: 0x818A, //CJK UNIFIED IDEOGRAPH - 0xBB4C: 0x817F, //CJK UNIFIED IDEOGRAPH - 0xBB4D: 0x8182, //CJK UNIFIED IDEOGRAPH - 0xBB4E: 0x81E7, //CJK UNIFIED IDEOGRAPH - 0xBB4F: 0x81FA, //CJK UNIFIED IDEOGRAPH - 0xBB50: 0x8207, //CJK UNIFIED IDEOGRAPH - 0xBB51: 0x8214, //CJK UNIFIED IDEOGRAPH - 0xBB52: 0x821E, //CJK UNIFIED IDEOGRAPH - 0xBB53: 0x824B, //CJK UNIFIED IDEOGRAPH - 0xBB54: 0x84C9, //CJK UNIFIED IDEOGRAPH - 0xBB55: 0x84BF, //CJK UNIFIED IDEOGRAPH - 0xBB56: 0x84C6, //CJK UNIFIED IDEOGRAPH - 0xBB57: 0x84C4, //CJK UNIFIED IDEOGRAPH - 0xBB58: 0x8499, //CJK UNIFIED IDEOGRAPH - 0xBB59: 0x849E, //CJK UNIFIED IDEOGRAPH - 0xBB5A: 0x84B2, //CJK UNIFIED IDEOGRAPH - 0xBB5B: 0x849C, //CJK UNIFIED IDEOGRAPH - 0xBB5C: 0x84CB, //CJK UNIFIED IDEOGRAPH - 0xBB5D: 0x84B8, //CJK UNIFIED IDEOGRAPH - 0xBB5E: 0x84C0, //CJK UNIFIED IDEOGRAPH - 0xBB5F: 0x84D3, //CJK UNIFIED IDEOGRAPH - 0xBB60: 0x8490, //CJK UNIFIED IDEOGRAPH - 0xBB61: 0x84BC, //CJK UNIFIED IDEOGRAPH - 0xBB62: 0x84D1, //CJK UNIFIED IDEOGRAPH - 0xBB63: 0x84CA, //CJK UNIFIED IDEOGRAPH - 0xBB64: 0x873F, //CJK UNIFIED IDEOGRAPH - 0xBB65: 0x871C, //CJK UNIFIED IDEOGRAPH - 0xBB66: 0x873B, //CJK UNIFIED IDEOGRAPH - 0xBB67: 0x8722, //CJK UNIFIED IDEOGRAPH - 0xBB68: 0x8725, //CJK UNIFIED IDEOGRAPH - 0xBB69: 0x8734, //CJK UNIFIED IDEOGRAPH - 0xBB6A: 0x8718, //CJK UNIFIED IDEOGRAPH - 0xBB6B: 0x8755, //CJK UNIFIED IDEOGRAPH - 0xBB6C: 0x8737, //CJK UNIFIED IDEOGRAPH - 0xBB6D: 0x8729, //CJK UNIFIED IDEOGRAPH - 0xBB6E: 0x88F3, //CJK UNIFIED IDEOGRAPH - 0xBB6F: 0x8902, //CJK UNIFIED IDEOGRAPH - 0xBB70: 0x88F4, //CJK UNIFIED IDEOGRAPH - 0xBB71: 0x88F9, //CJK UNIFIED IDEOGRAPH - 0xBB72: 0x88F8, //CJK UNIFIED IDEOGRAPH - 0xBB73: 0x88FD, //CJK UNIFIED IDEOGRAPH - 0xBB74: 0x88E8, //CJK UNIFIED IDEOGRAPH - 0xBB75: 0x891A, //CJK UNIFIED IDEOGRAPH - 0xBB76: 0x88EF, //CJK UNIFIED IDEOGRAPH - 0xBB77: 0x8AA6, //CJK UNIFIED IDEOGRAPH - 0xBB78: 0x8A8C, //CJK UNIFIED IDEOGRAPH - 0xBB79: 0x8A9E, //CJK UNIFIED IDEOGRAPH - 0xBB7A: 0x8AA3, //CJK UNIFIED IDEOGRAPH - 0xBB7B: 0x8A8D, //CJK UNIFIED IDEOGRAPH - 0xBB7C: 0x8AA1, //CJK UNIFIED IDEOGRAPH - 0xBB7D: 0x8A93, //CJK UNIFIED IDEOGRAPH - 0xBB7E: 0x8AA4, //CJK UNIFIED IDEOGRAPH - 0xBBA1: 0x8AAA, //CJK UNIFIED IDEOGRAPH - 0xBBA2: 0x8AA5, //CJK UNIFIED IDEOGRAPH - 0xBBA3: 0x8AA8, //CJK UNIFIED IDEOGRAPH - 0xBBA4: 0x8A98, //CJK UNIFIED IDEOGRAPH - 0xBBA5: 0x8A91, //CJK UNIFIED IDEOGRAPH - 0xBBA6: 0x8A9A, //CJK UNIFIED IDEOGRAPH - 0xBBA7: 0x8AA7, //CJK UNIFIED IDEOGRAPH - 0xBBA8: 0x8C6A, //CJK UNIFIED IDEOGRAPH - 0xBBA9: 0x8C8D, //CJK UNIFIED IDEOGRAPH - 0xBBAA: 0x8C8C, //CJK UNIFIED IDEOGRAPH - 0xBBAB: 0x8CD3, //CJK UNIFIED IDEOGRAPH - 0xBBAC: 0x8CD1, //CJK UNIFIED IDEOGRAPH - 0xBBAD: 0x8CD2, //CJK UNIFIED IDEOGRAPH - 0xBBAE: 0x8D6B, //CJK UNIFIED IDEOGRAPH - 0xBBAF: 0x8D99, //CJK UNIFIED IDEOGRAPH - 0xBBB0: 0x8D95, //CJK UNIFIED IDEOGRAPH - 0xBBB1: 0x8DFC, //CJK UNIFIED IDEOGRAPH - 0xBBB2: 0x8F14, //CJK UNIFIED IDEOGRAPH - 0xBBB3: 0x8F12, //CJK UNIFIED IDEOGRAPH - 0xBBB4: 0x8F15, //CJK UNIFIED IDEOGRAPH - 0xBBB5: 0x8F13, //CJK UNIFIED IDEOGRAPH - 0xBBB6: 0x8FA3, //CJK UNIFIED IDEOGRAPH - 0xBBB7: 0x9060, //CJK UNIFIED IDEOGRAPH - 0xBBB8: 0x9058, //CJK UNIFIED IDEOGRAPH - 0xBBB9: 0x905C, //CJK UNIFIED IDEOGRAPH - 0xBBBA: 0x9063, //CJK UNIFIED IDEOGRAPH - 0xBBBB: 0x9059, //CJK UNIFIED IDEOGRAPH - 0xBBBC: 0x905E, //CJK UNIFIED IDEOGRAPH - 0xBBBD: 0x9062, //CJK UNIFIED IDEOGRAPH - 0xBBBE: 0x905D, //CJK UNIFIED IDEOGRAPH - 0xBBBF: 0x905B, //CJK UNIFIED IDEOGRAPH - 0xBBC0: 0x9119, //CJK UNIFIED IDEOGRAPH - 0xBBC1: 0x9118, //CJK UNIFIED IDEOGRAPH - 0xBBC2: 0x911E, //CJK UNIFIED IDEOGRAPH - 0xBBC3: 0x9175, //CJK UNIFIED IDEOGRAPH - 0xBBC4: 0x9178, //CJK UNIFIED IDEOGRAPH - 0xBBC5: 0x9177, //CJK UNIFIED IDEOGRAPH - 0xBBC6: 0x9174, //CJK UNIFIED IDEOGRAPH - 0xBBC7: 0x9278, //CJK UNIFIED IDEOGRAPH - 0xBBC8: 0x9280, //CJK UNIFIED IDEOGRAPH - 0xBBC9: 0x9285, //CJK UNIFIED IDEOGRAPH - 0xBBCA: 0x9298, //CJK UNIFIED IDEOGRAPH - 0xBBCB: 0x9296, //CJK UNIFIED IDEOGRAPH - 0xBBCC: 0x927B, //CJK UNIFIED IDEOGRAPH - 0xBBCD: 0x9293, //CJK UNIFIED IDEOGRAPH - 0xBBCE: 0x929C, //CJK UNIFIED IDEOGRAPH - 0xBBCF: 0x92A8, //CJK UNIFIED IDEOGRAPH - 0xBBD0: 0x927C, //CJK UNIFIED IDEOGRAPH - 0xBBD1: 0x9291, //CJK UNIFIED IDEOGRAPH - 0xBBD2: 0x95A1, //CJK UNIFIED IDEOGRAPH - 0xBBD3: 0x95A8, //CJK UNIFIED IDEOGRAPH - 0xBBD4: 0x95A9, //CJK UNIFIED IDEOGRAPH - 0xBBD5: 0x95A3, //CJK UNIFIED IDEOGRAPH - 0xBBD6: 0x95A5, //CJK UNIFIED IDEOGRAPH - 0xBBD7: 0x95A4, //CJK UNIFIED IDEOGRAPH - 0xBBD8: 0x9699, //CJK UNIFIED IDEOGRAPH - 0xBBD9: 0x969C, //CJK UNIFIED IDEOGRAPH - 0xBBDA: 0x969B, //CJK UNIFIED IDEOGRAPH - 0xBBDB: 0x96CC, //CJK UNIFIED IDEOGRAPH - 0xBBDC: 0x96D2, //CJK UNIFIED IDEOGRAPH - 0xBBDD: 0x9700, //CJK UNIFIED IDEOGRAPH - 0xBBDE: 0x977C, //CJK UNIFIED IDEOGRAPH - 0xBBDF: 0x9785, //CJK UNIFIED IDEOGRAPH - 0xBBE0: 0x97F6, //CJK UNIFIED IDEOGRAPH - 0xBBE1: 0x9817, //CJK UNIFIED IDEOGRAPH - 0xBBE2: 0x9818, //CJK UNIFIED IDEOGRAPH - 0xBBE3: 0x98AF, //CJK UNIFIED IDEOGRAPH - 0xBBE4: 0x98B1, //CJK UNIFIED IDEOGRAPH - 0xBBE5: 0x9903, //CJK UNIFIED IDEOGRAPH - 0xBBE6: 0x9905, //CJK UNIFIED IDEOGRAPH - 0xBBE7: 0x990C, //CJK UNIFIED IDEOGRAPH - 0xBBE8: 0x9909, //CJK UNIFIED IDEOGRAPH - 0xBBE9: 0x99C1, //CJK UNIFIED IDEOGRAPH - 0xBBEA: 0x9AAF, //CJK UNIFIED IDEOGRAPH - 0xBBEB: 0x9AB0, //CJK UNIFIED IDEOGRAPH - 0xBBEC: 0x9AE6, //CJK UNIFIED IDEOGRAPH - 0xBBED: 0x9B41, //CJK UNIFIED IDEOGRAPH - 0xBBEE: 0x9B42, //CJK UNIFIED IDEOGRAPH - 0xBBEF: 0x9CF4, //CJK UNIFIED IDEOGRAPH - 0xBBF0: 0x9CF6, //CJK UNIFIED IDEOGRAPH - 0xBBF1: 0x9CF3, //CJK UNIFIED IDEOGRAPH - 0xBBF2: 0x9EBC, //CJK UNIFIED IDEOGRAPH - 0xBBF3: 0x9F3B, //CJK UNIFIED IDEOGRAPH - 0xBBF4: 0x9F4A, //CJK UNIFIED IDEOGRAPH - 0xBBF5: 0x5104, //CJK UNIFIED IDEOGRAPH - 0xBBF6: 0x5100, //CJK UNIFIED IDEOGRAPH - 0xBBF7: 0x50FB, //CJK UNIFIED IDEOGRAPH - 0xBBF8: 0x50F5, //CJK UNIFIED IDEOGRAPH - 0xBBF9: 0x50F9, //CJK UNIFIED IDEOGRAPH - 0xBBFA: 0x5102, //CJK UNIFIED IDEOGRAPH - 0xBBFB: 0x5108, //CJK UNIFIED IDEOGRAPH - 0xBBFC: 0x5109, //CJK UNIFIED IDEOGRAPH - 0xBBFD: 0x5105, //CJK UNIFIED IDEOGRAPH - 0xBBFE: 0x51DC, //CJK UNIFIED IDEOGRAPH - 0xBC40: 0x5287, //CJK UNIFIED IDEOGRAPH - 0xBC41: 0x5288, //CJK UNIFIED IDEOGRAPH - 0xBC42: 0x5289, //CJK UNIFIED IDEOGRAPH - 0xBC43: 0x528D, //CJK UNIFIED IDEOGRAPH - 0xBC44: 0x528A, //CJK UNIFIED IDEOGRAPH - 0xBC45: 0x52F0, //CJK UNIFIED IDEOGRAPH - 0xBC46: 0x53B2, //CJK UNIFIED IDEOGRAPH - 0xBC47: 0x562E, //CJK UNIFIED IDEOGRAPH - 0xBC48: 0x563B, //CJK UNIFIED IDEOGRAPH - 0xBC49: 0x5639, //CJK UNIFIED IDEOGRAPH - 0xBC4A: 0x5632, //CJK UNIFIED IDEOGRAPH - 0xBC4B: 0x563F, //CJK UNIFIED IDEOGRAPH - 0xBC4C: 0x5634, //CJK UNIFIED IDEOGRAPH - 0xBC4D: 0x5629, //CJK UNIFIED IDEOGRAPH - 0xBC4E: 0x5653, //CJK UNIFIED IDEOGRAPH - 0xBC4F: 0x564E, //CJK UNIFIED IDEOGRAPH - 0xBC50: 0x5657, //CJK UNIFIED IDEOGRAPH - 0xBC51: 0x5674, //CJK UNIFIED IDEOGRAPH - 0xBC52: 0x5636, //CJK UNIFIED IDEOGRAPH - 0xBC53: 0x562F, //CJK UNIFIED IDEOGRAPH - 0xBC54: 0x5630, //CJK UNIFIED IDEOGRAPH - 0xBC55: 0x5880, //CJK UNIFIED IDEOGRAPH - 0xBC56: 0x589F, //CJK UNIFIED IDEOGRAPH - 0xBC57: 0x589E, //CJK UNIFIED IDEOGRAPH - 0xBC58: 0x58B3, //CJK UNIFIED IDEOGRAPH - 0xBC59: 0x589C, //CJK UNIFIED IDEOGRAPH - 0xBC5A: 0x58AE, //CJK UNIFIED IDEOGRAPH - 0xBC5B: 0x58A9, //CJK UNIFIED IDEOGRAPH - 0xBC5C: 0x58A6, //CJK UNIFIED IDEOGRAPH - 0xBC5D: 0x596D, //CJK UNIFIED IDEOGRAPH - 0xBC5E: 0x5B09, //CJK UNIFIED IDEOGRAPH - 0xBC5F: 0x5AFB, //CJK UNIFIED IDEOGRAPH - 0xBC60: 0x5B0B, //CJK UNIFIED IDEOGRAPH - 0xBC61: 0x5AF5, //CJK UNIFIED IDEOGRAPH - 0xBC62: 0x5B0C, //CJK UNIFIED IDEOGRAPH - 0xBC63: 0x5B08, //CJK UNIFIED IDEOGRAPH - 0xBC64: 0x5BEE, //CJK UNIFIED IDEOGRAPH - 0xBC65: 0x5BEC, //CJK UNIFIED IDEOGRAPH - 0xBC66: 0x5BE9, //CJK UNIFIED IDEOGRAPH - 0xBC67: 0x5BEB, //CJK UNIFIED IDEOGRAPH - 0xBC68: 0x5C64, //CJK UNIFIED IDEOGRAPH - 0xBC69: 0x5C65, //CJK UNIFIED IDEOGRAPH - 0xBC6A: 0x5D9D, //CJK UNIFIED IDEOGRAPH - 0xBC6B: 0x5D94, //CJK UNIFIED IDEOGRAPH - 0xBC6C: 0x5E62, //CJK UNIFIED IDEOGRAPH - 0xBC6D: 0x5E5F, //CJK UNIFIED IDEOGRAPH - 0xBC6E: 0x5E61, //CJK UNIFIED IDEOGRAPH - 0xBC6F: 0x5EE2, //CJK UNIFIED IDEOGRAPH - 0xBC70: 0x5EDA, //CJK UNIFIED IDEOGRAPH - 0xBC71: 0x5EDF, //CJK UNIFIED IDEOGRAPH - 0xBC72: 0x5EDD, //CJK UNIFIED IDEOGRAPH - 0xBC73: 0x5EE3, //CJK UNIFIED IDEOGRAPH - 0xBC74: 0x5EE0, //CJK UNIFIED IDEOGRAPH - 0xBC75: 0x5F48, //CJK UNIFIED IDEOGRAPH - 0xBC76: 0x5F71, //CJK UNIFIED IDEOGRAPH - 0xBC77: 0x5FB7, //CJK UNIFIED IDEOGRAPH - 0xBC78: 0x5FB5, //CJK UNIFIED IDEOGRAPH - 0xBC79: 0x6176, //CJK UNIFIED IDEOGRAPH - 0xBC7A: 0x6167, //CJK UNIFIED IDEOGRAPH - 0xBC7B: 0x616E, //CJK UNIFIED IDEOGRAPH - 0xBC7C: 0x615D, //CJK UNIFIED IDEOGRAPH - 0xBC7D: 0x6155, //CJK UNIFIED IDEOGRAPH - 0xBC7E: 0x6182, //CJK UNIFIED IDEOGRAPH - 0xBCA1: 0x617C, //CJK UNIFIED IDEOGRAPH - 0xBCA2: 0x6170, //CJK UNIFIED IDEOGRAPH - 0xBCA3: 0x616B, //CJK UNIFIED IDEOGRAPH - 0xBCA4: 0x617E, //CJK UNIFIED IDEOGRAPH - 0xBCA5: 0x61A7, //CJK UNIFIED IDEOGRAPH - 0xBCA6: 0x6190, //CJK UNIFIED IDEOGRAPH - 0xBCA7: 0x61AB, //CJK UNIFIED IDEOGRAPH - 0xBCA8: 0x618E, //CJK UNIFIED IDEOGRAPH - 0xBCA9: 0x61AC, //CJK UNIFIED IDEOGRAPH - 0xBCAA: 0x619A, //CJK UNIFIED IDEOGRAPH - 0xBCAB: 0x61A4, //CJK UNIFIED IDEOGRAPH - 0xBCAC: 0x6194, //CJK UNIFIED IDEOGRAPH - 0xBCAD: 0x61AE, //CJK UNIFIED IDEOGRAPH - 0xBCAE: 0x622E, //CJK UNIFIED IDEOGRAPH - 0xBCAF: 0x6469, //CJK UNIFIED IDEOGRAPH - 0xBCB0: 0x646F, //CJK UNIFIED IDEOGRAPH - 0xBCB1: 0x6479, //CJK UNIFIED IDEOGRAPH - 0xBCB2: 0x649E, //CJK UNIFIED IDEOGRAPH - 0xBCB3: 0x64B2, //CJK UNIFIED IDEOGRAPH - 0xBCB4: 0x6488, //CJK UNIFIED IDEOGRAPH - 0xBCB5: 0x6490, //CJK UNIFIED IDEOGRAPH - 0xBCB6: 0x64B0, //CJK UNIFIED IDEOGRAPH - 0xBCB7: 0x64A5, //CJK UNIFIED IDEOGRAPH - 0xBCB8: 0x6493, //CJK UNIFIED IDEOGRAPH - 0xBCB9: 0x6495, //CJK UNIFIED IDEOGRAPH - 0xBCBA: 0x64A9, //CJK UNIFIED IDEOGRAPH - 0xBCBB: 0x6492, //CJK UNIFIED IDEOGRAPH - 0xBCBC: 0x64AE, //CJK UNIFIED IDEOGRAPH - 0xBCBD: 0x64AD, //CJK UNIFIED IDEOGRAPH - 0xBCBE: 0x64AB, //CJK UNIFIED IDEOGRAPH - 0xBCBF: 0x649A, //CJK UNIFIED IDEOGRAPH - 0xBCC0: 0x64AC, //CJK UNIFIED IDEOGRAPH - 0xBCC1: 0x6499, //CJK UNIFIED IDEOGRAPH - 0xBCC2: 0x64A2, //CJK UNIFIED IDEOGRAPH - 0xBCC3: 0x64B3, //CJK UNIFIED IDEOGRAPH - 0xBCC4: 0x6575, //CJK UNIFIED IDEOGRAPH - 0xBCC5: 0x6577, //CJK UNIFIED IDEOGRAPH - 0xBCC6: 0x6578, //CJK UNIFIED IDEOGRAPH - 0xBCC7: 0x66AE, //CJK UNIFIED IDEOGRAPH - 0xBCC8: 0x66AB, //CJK UNIFIED IDEOGRAPH - 0xBCC9: 0x66B4, //CJK UNIFIED IDEOGRAPH - 0xBCCA: 0x66B1, //CJK UNIFIED IDEOGRAPH - 0xBCCB: 0x6A23, //CJK UNIFIED IDEOGRAPH - 0xBCCC: 0x6A1F, //CJK UNIFIED IDEOGRAPH - 0xBCCD: 0x69E8, //CJK UNIFIED IDEOGRAPH - 0xBCCE: 0x6A01, //CJK UNIFIED IDEOGRAPH - 0xBCCF: 0x6A1E, //CJK UNIFIED IDEOGRAPH - 0xBCD0: 0x6A19, //CJK UNIFIED IDEOGRAPH - 0xBCD1: 0x69FD, //CJK UNIFIED IDEOGRAPH - 0xBCD2: 0x6A21, //CJK UNIFIED IDEOGRAPH - 0xBCD3: 0x6A13, //CJK UNIFIED IDEOGRAPH - 0xBCD4: 0x6A0A, //CJK UNIFIED IDEOGRAPH - 0xBCD5: 0x69F3, //CJK UNIFIED IDEOGRAPH - 0xBCD6: 0x6A02, //CJK UNIFIED IDEOGRAPH - 0xBCD7: 0x6A05, //CJK UNIFIED IDEOGRAPH - 0xBCD8: 0x69ED, //CJK UNIFIED IDEOGRAPH - 0xBCD9: 0x6A11, //CJK UNIFIED IDEOGRAPH - 0xBCDA: 0x6B50, //CJK UNIFIED IDEOGRAPH - 0xBCDB: 0x6B4E, //CJK UNIFIED IDEOGRAPH - 0xBCDC: 0x6BA4, //CJK UNIFIED IDEOGRAPH - 0xBCDD: 0x6BC5, //CJK UNIFIED IDEOGRAPH - 0xBCDE: 0x6BC6, //CJK UNIFIED IDEOGRAPH - 0xBCDF: 0x6F3F, //CJK UNIFIED IDEOGRAPH - 0xBCE0: 0x6F7C, //CJK UNIFIED IDEOGRAPH - 0xBCE1: 0x6F84, //CJK UNIFIED IDEOGRAPH - 0xBCE2: 0x6F51, //CJK UNIFIED IDEOGRAPH - 0xBCE3: 0x6F66, //CJK UNIFIED IDEOGRAPH - 0xBCE4: 0x6F54, //CJK UNIFIED IDEOGRAPH - 0xBCE5: 0x6F86, //CJK UNIFIED IDEOGRAPH - 0xBCE6: 0x6F6D, //CJK UNIFIED IDEOGRAPH - 0xBCE7: 0x6F5B, //CJK UNIFIED IDEOGRAPH - 0xBCE8: 0x6F78, //CJK UNIFIED IDEOGRAPH - 0xBCE9: 0x6F6E, //CJK UNIFIED IDEOGRAPH - 0xBCEA: 0x6F8E, //CJK UNIFIED IDEOGRAPH - 0xBCEB: 0x6F7A, //CJK UNIFIED IDEOGRAPH - 0xBCEC: 0x6F70, //CJK UNIFIED IDEOGRAPH - 0xBCED: 0x6F64, //CJK UNIFIED IDEOGRAPH - 0xBCEE: 0x6F97, //CJK UNIFIED IDEOGRAPH - 0xBCEF: 0x6F58, //CJK UNIFIED IDEOGRAPH - 0xBCF0: 0x6ED5, //CJK UNIFIED IDEOGRAPH - 0xBCF1: 0x6F6F, //CJK UNIFIED IDEOGRAPH - 0xBCF2: 0x6F60, //CJK UNIFIED IDEOGRAPH - 0xBCF3: 0x6F5F, //CJK UNIFIED IDEOGRAPH - 0xBCF4: 0x719F, //CJK UNIFIED IDEOGRAPH - 0xBCF5: 0x71AC, //CJK UNIFIED IDEOGRAPH - 0xBCF6: 0x71B1, //CJK UNIFIED IDEOGRAPH - 0xBCF7: 0x71A8, //CJK UNIFIED IDEOGRAPH - 0xBCF8: 0x7256, //CJK UNIFIED IDEOGRAPH - 0xBCF9: 0x729B, //CJK UNIFIED IDEOGRAPH - 0xBCFA: 0x734E, //CJK UNIFIED IDEOGRAPH - 0xBCFB: 0x7357, //CJK UNIFIED IDEOGRAPH - 0xBCFC: 0x7469, //CJK UNIFIED IDEOGRAPH - 0xBCFD: 0x748B, //CJK UNIFIED IDEOGRAPH - 0xBCFE: 0x7483, //CJK UNIFIED IDEOGRAPH - 0xBD40: 0x747E, //CJK UNIFIED IDEOGRAPH - 0xBD41: 0x7480, //CJK UNIFIED IDEOGRAPH - 0xBD42: 0x757F, //CJK UNIFIED IDEOGRAPH - 0xBD43: 0x7620, //CJK UNIFIED IDEOGRAPH - 0xBD44: 0x7629, //CJK UNIFIED IDEOGRAPH - 0xBD45: 0x761F, //CJK UNIFIED IDEOGRAPH - 0xBD46: 0x7624, //CJK UNIFIED IDEOGRAPH - 0xBD47: 0x7626, //CJK UNIFIED IDEOGRAPH - 0xBD48: 0x7621, //CJK UNIFIED IDEOGRAPH - 0xBD49: 0x7622, //CJK UNIFIED IDEOGRAPH - 0xBD4A: 0x769A, //CJK UNIFIED IDEOGRAPH - 0xBD4B: 0x76BA, //CJK UNIFIED IDEOGRAPH - 0xBD4C: 0x76E4, //CJK UNIFIED IDEOGRAPH - 0xBD4D: 0x778E, //CJK UNIFIED IDEOGRAPH - 0xBD4E: 0x7787, //CJK UNIFIED IDEOGRAPH - 0xBD4F: 0x778C, //CJK UNIFIED IDEOGRAPH - 0xBD50: 0x7791, //CJK UNIFIED IDEOGRAPH - 0xBD51: 0x778B, //CJK UNIFIED IDEOGRAPH - 0xBD52: 0x78CB, //CJK UNIFIED IDEOGRAPH - 0xBD53: 0x78C5, //CJK UNIFIED IDEOGRAPH - 0xBD54: 0x78BA, //CJK UNIFIED IDEOGRAPH - 0xBD55: 0x78CA, //CJK UNIFIED IDEOGRAPH - 0xBD56: 0x78BE, //CJK UNIFIED IDEOGRAPH - 0xBD57: 0x78D5, //CJK UNIFIED IDEOGRAPH - 0xBD58: 0x78BC, //CJK UNIFIED IDEOGRAPH - 0xBD59: 0x78D0, //CJK UNIFIED IDEOGRAPH - 0xBD5A: 0x7A3F, //CJK UNIFIED IDEOGRAPH - 0xBD5B: 0x7A3C, //CJK UNIFIED IDEOGRAPH - 0xBD5C: 0x7A40, //CJK UNIFIED IDEOGRAPH - 0xBD5D: 0x7A3D, //CJK UNIFIED IDEOGRAPH - 0xBD5E: 0x7A37, //CJK UNIFIED IDEOGRAPH - 0xBD5F: 0x7A3B, //CJK UNIFIED IDEOGRAPH - 0xBD60: 0x7AAF, //CJK UNIFIED IDEOGRAPH - 0xBD61: 0x7AAE, //CJK UNIFIED IDEOGRAPH - 0xBD62: 0x7BAD, //CJK UNIFIED IDEOGRAPH - 0xBD63: 0x7BB1, //CJK UNIFIED IDEOGRAPH - 0xBD64: 0x7BC4, //CJK UNIFIED IDEOGRAPH - 0xBD65: 0x7BB4, //CJK UNIFIED IDEOGRAPH - 0xBD66: 0x7BC6, //CJK UNIFIED IDEOGRAPH - 0xBD67: 0x7BC7, //CJK UNIFIED IDEOGRAPH - 0xBD68: 0x7BC1, //CJK UNIFIED IDEOGRAPH - 0xBD69: 0x7BA0, //CJK UNIFIED IDEOGRAPH - 0xBD6A: 0x7BCC, //CJK UNIFIED IDEOGRAPH - 0xBD6B: 0x7CCA, //CJK UNIFIED IDEOGRAPH - 0xBD6C: 0x7DE0, //CJK UNIFIED IDEOGRAPH - 0xBD6D: 0x7DF4, //CJK UNIFIED IDEOGRAPH - 0xBD6E: 0x7DEF, //CJK UNIFIED IDEOGRAPH - 0xBD6F: 0x7DFB, //CJK UNIFIED IDEOGRAPH - 0xBD70: 0x7DD8, //CJK UNIFIED IDEOGRAPH - 0xBD71: 0x7DEC, //CJK UNIFIED IDEOGRAPH - 0xBD72: 0x7DDD, //CJK UNIFIED IDEOGRAPH - 0xBD73: 0x7DE8, //CJK UNIFIED IDEOGRAPH - 0xBD74: 0x7DE3, //CJK UNIFIED IDEOGRAPH - 0xBD75: 0x7DDA, //CJK UNIFIED IDEOGRAPH - 0xBD76: 0x7DDE, //CJK UNIFIED IDEOGRAPH - 0xBD77: 0x7DE9, //CJK UNIFIED IDEOGRAPH - 0xBD78: 0x7D9E, //CJK UNIFIED IDEOGRAPH - 0xBD79: 0x7DD9, //CJK UNIFIED IDEOGRAPH - 0xBD7A: 0x7DF2, //CJK UNIFIED IDEOGRAPH - 0xBD7B: 0x7DF9, //CJK UNIFIED IDEOGRAPH - 0xBD7C: 0x7F75, //CJK UNIFIED IDEOGRAPH - 0xBD7D: 0x7F77, //CJK UNIFIED IDEOGRAPH - 0xBD7E: 0x7FAF, //CJK UNIFIED IDEOGRAPH - 0xBDA1: 0x7FE9, //CJK UNIFIED IDEOGRAPH - 0xBDA2: 0x8026, //CJK UNIFIED IDEOGRAPH - 0xBDA3: 0x819B, //CJK UNIFIED IDEOGRAPH - 0xBDA4: 0x819C, //CJK UNIFIED IDEOGRAPH - 0xBDA5: 0x819D, //CJK UNIFIED IDEOGRAPH - 0xBDA6: 0x81A0, //CJK UNIFIED IDEOGRAPH - 0xBDA7: 0x819A, //CJK UNIFIED IDEOGRAPH - 0xBDA8: 0x8198, //CJK UNIFIED IDEOGRAPH - 0xBDA9: 0x8517, //CJK UNIFIED IDEOGRAPH - 0xBDAA: 0x853D, //CJK UNIFIED IDEOGRAPH - 0xBDAB: 0x851A, //CJK UNIFIED IDEOGRAPH - 0xBDAC: 0x84EE, //CJK UNIFIED IDEOGRAPH - 0xBDAD: 0x852C, //CJK UNIFIED IDEOGRAPH - 0xBDAE: 0x852D, //CJK UNIFIED IDEOGRAPH - 0xBDAF: 0x8513, //CJK UNIFIED IDEOGRAPH - 0xBDB0: 0x8511, //CJK UNIFIED IDEOGRAPH - 0xBDB1: 0x8523, //CJK UNIFIED IDEOGRAPH - 0xBDB2: 0x8521, //CJK UNIFIED IDEOGRAPH - 0xBDB3: 0x8514, //CJK UNIFIED IDEOGRAPH - 0xBDB4: 0x84EC, //CJK UNIFIED IDEOGRAPH - 0xBDB5: 0x8525, //CJK UNIFIED IDEOGRAPH - 0xBDB6: 0x84FF, //CJK UNIFIED IDEOGRAPH - 0xBDB7: 0x8506, //CJK UNIFIED IDEOGRAPH - 0xBDB8: 0x8782, //CJK UNIFIED IDEOGRAPH - 0xBDB9: 0x8774, //CJK UNIFIED IDEOGRAPH - 0xBDBA: 0x8776, //CJK UNIFIED IDEOGRAPH - 0xBDBB: 0x8760, //CJK UNIFIED IDEOGRAPH - 0xBDBC: 0x8766, //CJK UNIFIED IDEOGRAPH - 0xBDBD: 0x8778, //CJK UNIFIED IDEOGRAPH - 0xBDBE: 0x8768, //CJK UNIFIED IDEOGRAPH - 0xBDBF: 0x8759, //CJK UNIFIED IDEOGRAPH - 0xBDC0: 0x8757, //CJK UNIFIED IDEOGRAPH - 0xBDC1: 0x874C, //CJK UNIFIED IDEOGRAPH - 0xBDC2: 0x8753, //CJK UNIFIED IDEOGRAPH - 0xBDC3: 0x885B, //CJK UNIFIED IDEOGRAPH - 0xBDC4: 0x885D, //CJK UNIFIED IDEOGRAPH - 0xBDC5: 0x8910, //CJK UNIFIED IDEOGRAPH - 0xBDC6: 0x8907, //CJK UNIFIED IDEOGRAPH - 0xBDC7: 0x8912, //CJK UNIFIED IDEOGRAPH - 0xBDC8: 0x8913, //CJK UNIFIED IDEOGRAPH - 0xBDC9: 0x8915, //CJK UNIFIED IDEOGRAPH - 0xBDCA: 0x890A, //CJK UNIFIED IDEOGRAPH - 0xBDCB: 0x8ABC, //CJK UNIFIED IDEOGRAPH - 0xBDCC: 0x8AD2, //CJK UNIFIED IDEOGRAPH - 0xBDCD: 0x8AC7, //CJK UNIFIED IDEOGRAPH - 0xBDCE: 0x8AC4, //CJK UNIFIED IDEOGRAPH - 0xBDCF: 0x8A95, //CJK UNIFIED IDEOGRAPH - 0xBDD0: 0x8ACB, //CJK UNIFIED IDEOGRAPH - 0xBDD1: 0x8AF8, //CJK UNIFIED IDEOGRAPH - 0xBDD2: 0x8AB2, //CJK UNIFIED IDEOGRAPH - 0xBDD3: 0x8AC9, //CJK UNIFIED IDEOGRAPH - 0xBDD4: 0x8AC2, //CJK UNIFIED IDEOGRAPH - 0xBDD5: 0x8ABF, //CJK UNIFIED IDEOGRAPH - 0xBDD6: 0x8AB0, //CJK UNIFIED IDEOGRAPH - 0xBDD7: 0x8AD6, //CJK UNIFIED IDEOGRAPH - 0xBDD8: 0x8ACD, //CJK UNIFIED IDEOGRAPH - 0xBDD9: 0x8AB6, //CJK UNIFIED IDEOGRAPH - 0xBDDA: 0x8AB9, //CJK UNIFIED IDEOGRAPH - 0xBDDB: 0x8ADB, //CJK UNIFIED IDEOGRAPH - 0xBDDC: 0x8C4C, //CJK UNIFIED IDEOGRAPH - 0xBDDD: 0x8C4E, //CJK UNIFIED IDEOGRAPH - 0xBDDE: 0x8C6C, //CJK UNIFIED IDEOGRAPH - 0xBDDF: 0x8CE0, //CJK UNIFIED IDEOGRAPH - 0xBDE0: 0x8CDE, //CJK UNIFIED IDEOGRAPH - 0xBDE1: 0x8CE6, //CJK UNIFIED IDEOGRAPH - 0xBDE2: 0x8CE4, //CJK UNIFIED IDEOGRAPH - 0xBDE3: 0x8CEC, //CJK UNIFIED IDEOGRAPH - 0xBDE4: 0x8CED, //CJK UNIFIED IDEOGRAPH - 0xBDE5: 0x8CE2, //CJK UNIFIED IDEOGRAPH - 0xBDE6: 0x8CE3, //CJK UNIFIED IDEOGRAPH - 0xBDE7: 0x8CDC, //CJK UNIFIED IDEOGRAPH - 0xBDE8: 0x8CEA, //CJK UNIFIED IDEOGRAPH - 0xBDE9: 0x8CE1, //CJK UNIFIED IDEOGRAPH - 0xBDEA: 0x8D6D, //CJK UNIFIED IDEOGRAPH - 0xBDEB: 0x8D9F, //CJK UNIFIED IDEOGRAPH - 0xBDEC: 0x8DA3, //CJK UNIFIED IDEOGRAPH - 0xBDED: 0x8E2B, //CJK UNIFIED IDEOGRAPH - 0xBDEE: 0x8E10, //CJK UNIFIED IDEOGRAPH - 0xBDEF: 0x8E1D, //CJK UNIFIED IDEOGRAPH - 0xBDF0: 0x8E22, //CJK UNIFIED IDEOGRAPH - 0xBDF1: 0x8E0F, //CJK UNIFIED IDEOGRAPH - 0xBDF2: 0x8E29, //CJK UNIFIED IDEOGRAPH - 0xBDF3: 0x8E1F, //CJK UNIFIED IDEOGRAPH - 0xBDF4: 0x8E21, //CJK UNIFIED IDEOGRAPH - 0xBDF5: 0x8E1E, //CJK UNIFIED IDEOGRAPH - 0xBDF6: 0x8EBA, //CJK UNIFIED IDEOGRAPH - 0xBDF7: 0x8F1D, //CJK UNIFIED IDEOGRAPH - 0xBDF8: 0x8F1B, //CJK UNIFIED IDEOGRAPH - 0xBDF9: 0x8F1F, //CJK UNIFIED IDEOGRAPH - 0xBDFA: 0x8F29, //CJK UNIFIED IDEOGRAPH - 0xBDFB: 0x8F26, //CJK UNIFIED IDEOGRAPH - 0xBDFC: 0x8F2A, //CJK UNIFIED IDEOGRAPH - 0xBDFD: 0x8F1C, //CJK UNIFIED IDEOGRAPH - 0xBDFE: 0x8F1E, //CJK UNIFIED IDEOGRAPH - 0xBE40: 0x8F25, //CJK UNIFIED IDEOGRAPH - 0xBE41: 0x9069, //CJK UNIFIED IDEOGRAPH - 0xBE42: 0x906E, //CJK UNIFIED IDEOGRAPH - 0xBE43: 0x9068, //CJK UNIFIED IDEOGRAPH - 0xBE44: 0x906D, //CJK UNIFIED IDEOGRAPH - 0xBE45: 0x9077, //CJK UNIFIED IDEOGRAPH - 0xBE46: 0x9130, //CJK UNIFIED IDEOGRAPH - 0xBE47: 0x912D, //CJK UNIFIED IDEOGRAPH - 0xBE48: 0x9127, //CJK UNIFIED IDEOGRAPH - 0xBE49: 0x9131, //CJK UNIFIED IDEOGRAPH - 0xBE4A: 0x9187, //CJK UNIFIED IDEOGRAPH - 0xBE4B: 0x9189, //CJK UNIFIED IDEOGRAPH - 0xBE4C: 0x918B, //CJK UNIFIED IDEOGRAPH - 0xBE4D: 0x9183, //CJK UNIFIED IDEOGRAPH - 0xBE4E: 0x92C5, //CJK UNIFIED IDEOGRAPH - 0xBE4F: 0x92BB, //CJK UNIFIED IDEOGRAPH - 0xBE50: 0x92B7, //CJK UNIFIED IDEOGRAPH - 0xBE51: 0x92EA, //CJK UNIFIED IDEOGRAPH - 0xBE52: 0x92AC, //CJK UNIFIED IDEOGRAPH - 0xBE53: 0x92E4, //CJK UNIFIED IDEOGRAPH - 0xBE54: 0x92C1, //CJK UNIFIED IDEOGRAPH - 0xBE55: 0x92B3, //CJK UNIFIED IDEOGRAPH - 0xBE56: 0x92BC, //CJK UNIFIED IDEOGRAPH - 0xBE57: 0x92D2, //CJK UNIFIED IDEOGRAPH - 0xBE58: 0x92C7, //CJK UNIFIED IDEOGRAPH - 0xBE59: 0x92F0, //CJK UNIFIED IDEOGRAPH - 0xBE5A: 0x92B2, //CJK UNIFIED IDEOGRAPH - 0xBE5B: 0x95AD, //CJK UNIFIED IDEOGRAPH - 0xBE5C: 0x95B1, //CJK UNIFIED IDEOGRAPH - 0xBE5D: 0x9704, //CJK UNIFIED IDEOGRAPH - 0xBE5E: 0x9706, //CJK UNIFIED IDEOGRAPH - 0xBE5F: 0x9707, //CJK UNIFIED IDEOGRAPH - 0xBE60: 0x9709, //CJK UNIFIED IDEOGRAPH - 0xBE61: 0x9760, //CJK UNIFIED IDEOGRAPH - 0xBE62: 0x978D, //CJK UNIFIED IDEOGRAPH - 0xBE63: 0x978B, //CJK UNIFIED IDEOGRAPH - 0xBE64: 0x978F, //CJK UNIFIED IDEOGRAPH - 0xBE65: 0x9821, //CJK UNIFIED IDEOGRAPH - 0xBE66: 0x982B, //CJK UNIFIED IDEOGRAPH - 0xBE67: 0x981C, //CJK UNIFIED IDEOGRAPH - 0xBE68: 0x98B3, //CJK UNIFIED IDEOGRAPH - 0xBE69: 0x990A, //CJK UNIFIED IDEOGRAPH - 0xBE6A: 0x9913, //CJK UNIFIED IDEOGRAPH - 0xBE6B: 0x9912, //CJK UNIFIED IDEOGRAPH - 0xBE6C: 0x9918, //CJK UNIFIED IDEOGRAPH - 0xBE6D: 0x99DD, //CJK UNIFIED IDEOGRAPH - 0xBE6E: 0x99D0, //CJK UNIFIED IDEOGRAPH - 0xBE6F: 0x99DF, //CJK UNIFIED IDEOGRAPH - 0xBE70: 0x99DB, //CJK UNIFIED IDEOGRAPH - 0xBE71: 0x99D1, //CJK UNIFIED IDEOGRAPH - 0xBE72: 0x99D5, //CJK UNIFIED IDEOGRAPH - 0xBE73: 0x99D2, //CJK UNIFIED IDEOGRAPH - 0xBE74: 0x99D9, //CJK UNIFIED IDEOGRAPH - 0xBE75: 0x9AB7, //CJK UNIFIED IDEOGRAPH - 0xBE76: 0x9AEE, //CJK UNIFIED IDEOGRAPH - 0xBE77: 0x9AEF, //CJK UNIFIED IDEOGRAPH - 0xBE78: 0x9B27, //CJK UNIFIED IDEOGRAPH - 0xBE79: 0x9B45, //CJK UNIFIED IDEOGRAPH - 0xBE7A: 0x9B44, //CJK UNIFIED IDEOGRAPH - 0xBE7B: 0x9B77, //CJK UNIFIED IDEOGRAPH - 0xBE7C: 0x9B6F, //CJK UNIFIED IDEOGRAPH - 0xBE7D: 0x9D06, //CJK UNIFIED IDEOGRAPH - 0xBE7E: 0x9D09, //CJK UNIFIED IDEOGRAPH - 0xBEA1: 0x9D03, //CJK UNIFIED IDEOGRAPH - 0xBEA2: 0x9EA9, //CJK UNIFIED IDEOGRAPH - 0xBEA3: 0x9EBE, //CJK UNIFIED IDEOGRAPH - 0xBEA4: 0x9ECE, //CJK UNIFIED IDEOGRAPH - 0xBEA5: 0x58A8, //CJK UNIFIED IDEOGRAPH - 0xBEA6: 0x9F52, //CJK UNIFIED IDEOGRAPH - 0xBEA7: 0x5112, //CJK UNIFIED IDEOGRAPH - 0xBEA8: 0x5118, //CJK UNIFIED IDEOGRAPH - 0xBEA9: 0x5114, //CJK UNIFIED IDEOGRAPH - 0xBEAA: 0x5110, //CJK UNIFIED IDEOGRAPH - 0xBEAB: 0x5115, //CJK UNIFIED IDEOGRAPH - 0xBEAC: 0x5180, //CJK UNIFIED IDEOGRAPH - 0xBEAD: 0x51AA, //CJK UNIFIED IDEOGRAPH - 0xBEAE: 0x51DD, //CJK UNIFIED IDEOGRAPH - 0xBEAF: 0x5291, //CJK UNIFIED IDEOGRAPH - 0xBEB0: 0x5293, //CJK UNIFIED IDEOGRAPH - 0xBEB1: 0x52F3, //CJK UNIFIED IDEOGRAPH - 0xBEB2: 0x5659, //CJK UNIFIED IDEOGRAPH - 0xBEB3: 0x566B, //CJK UNIFIED IDEOGRAPH - 0xBEB4: 0x5679, //CJK UNIFIED IDEOGRAPH - 0xBEB5: 0x5669, //CJK UNIFIED IDEOGRAPH - 0xBEB6: 0x5664, //CJK UNIFIED IDEOGRAPH - 0xBEB7: 0x5678, //CJK UNIFIED IDEOGRAPH - 0xBEB8: 0x566A, //CJK UNIFIED IDEOGRAPH - 0xBEB9: 0x5668, //CJK UNIFIED IDEOGRAPH - 0xBEBA: 0x5665, //CJK UNIFIED IDEOGRAPH - 0xBEBB: 0x5671, //CJK UNIFIED IDEOGRAPH - 0xBEBC: 0x566F, //CJK UNIFIED IDEOGRAPH - 0xBEBD: 0x566C, //CJK UNIFIED IDEOGRAPH - 0xBEBE: 0x5662, //CJK UNIFIED IDEOGRAPH - 0xBEBF: 0x5676, //CJK UNIFIED IDEOGRAPH - 0xBEC0: 0x58C1, //CJK UNIFIED IDEOGRAPH - 0xBEC1: 0x58BE, //CJK UNIFIED IDEOGRAPH - 0xBEC2: 0x58C7, //CJK UNIFIED IDEOGRAPH - 0xBEC3: 0x58C5, //CJK UNIFIED IDEOGRAPH - 0xBEC4: 0x596E, //CJK UNIFIED IDEOGRAPH - 0xBEC5: 0x5B1D, //CJK UNIFIED IDEOGRAPH - 0xBEC6: 0x5B34, //CJK UNIFIED IDEOGRAPH - 0xBEC7: 0x5B78, //CJK UNIFIED IDEOGRAPH - 0xBEC8: 0x5BF0, //CJK UNIFIED IDEOGRAPH - 0xBEC9: 0x5C0E, //CJK UNIFIED IDEOGRAPH - 0xBECA: 0x5F4A, //CJK UNIFIED IDEOGRAPH - 0xBECB: 0x61B2, //CJK UNIFIED IDEOGRAPH - 0xBECC: 0x6191, //CJK UNIFIED IDEOGRAPH - 0xBECD: 0x61A9, //CJK UNIFIED IDEOGRAPH - 0xBECE: 0x618A, //CJK UNIFIED IDEOGRAPH - 0xBECF: 0x61CD, //CJK UNIFIED IDEOGRAPH - 0xBED0: 0x61B6, //CJK UNIFIED IDEOGRAPH - 0xBED1: 0x61BE, //CJK UNIFIED IDEOGRAPH - 0xBED2: 0x61CA, //CJK UNIFIED IDEOGRAPH - 0xBED3: 0x61C8, //CJK UNIFIED IDEOGRAPH - 0xBED4: 0x6230, //CJK UNIFIED IDEOGRAPH - 0xBED5: 0x64C5, //CJK UNIFIED IDEOGRAPH - 0xBED6: 0x64C1, //CJK UNIFIED IDEOGRAPH - 0xBED7: 0x64CB, //CJK UNIFIED IDEOGRAPH - 0xBED8: 0x64BB, //CJK UNIFIED IDEOGRAPH - 0xBED9: 0x64BC, //CJK UNIFIED IDEOGRAPH - 0xBEDA: 0x64DA, //CJK UNIFIED IDEOGRAPH - 0xBEDB: 0x64C4, //CJK UNIFIED IDEOGRAPH - 0xBEDC: 0x64C7, //CJK UNIFIED IDEOGRAPH - 0xBEDD: 0x64C2, //CJK UNIFIED IDEOGRAPH - 0xBEDE: 0x64CD, //CJK UNIFIED IDEOGRAPH - 0xBEDF: 0x64BF, //CJK UNIFIED IDEOGRAPH - 0xBEE0: 0x64D2, //CJK UNIFIED IDEOGRAPH - 0xBEE1: 0x64D4, //CJK UNIFIED IDEOGRAPH - 0xBEE2: 0x64BE, //CJK UNIFIED IDEOGRAPH - 0xBEE3: 0x6574, //CJK UNIFIED IDEOGRAPH - 0xBEE4: 0x66C6, //CJK UNIFIED IDEOGRAPH - 0xBEE5: 0x66C9, //CJK UNIFIED IDEOGRAPH - 0xBEE6: 0x66B9, //CJK UNIFIED IDEOGRAPH - 0xBEE7: 0x66C4, //CJK UNIFIED IDEOGRAPH - 0xBEE8: 0x66C7, //CJK UNIFIED IDEOGRAPH - 0xBEE9: 0x66B8, //CJK UNIFIED IDEOGRAPH - 0xBEEA: 0x6A3D, //CJK UNIFIED IDEOGRAPH - 0xBEEB: 0x6A38, //CJK UNIFIED IDEOGRAPH - 0xBEEC: 0x6A3A, //CJK UNIFIED IDEOGRAPH - 0xBEED: 0x6A59, //CJK UNIFIED IDEOGRAPH - 0xBEEE: 0x6A6B, //CJK UNIFIED IDEOGRAPH - 0xBEEF: 0x6A58, //CJK UNIFIED IDEOGRAPH - 0xBEF0: 0x6A39, //CJK UNIFIED IDEOGRAPH - 0xBEF1: 0x6A44, //CJK UNIFIED IDEOGRAPH - 0xBEF2: 0x6A62, //CJK UNIFIED IDEOGRAPH - 0xBEF3: 0x6A61, //CJK UNIFIED IDEOGRAPH - 0xBEF4: 0x6A4B, //CJK UNIFIED IDEOGRAPH - 0xBEF5: 0x6A47, //CJK UNIFIED IDEOGRAPH - 0xBEF6: 0x6A35, //CJK UNIFIED IDEOGRAPH - 0xBEF7: 0x6A5F, //CJK UNIFIED IDEOGRAPH - 0xBEF8: 0x6A48, //CJK UNIFIED IDEOGRAPH - 0xBEF9: 0x6B59, //CJK UNIFIED IDEOGRAPH - 0xBEFA: 0x6B77, //CJK UNIFIED IDEOGRAPH - 0xBEFB: 0x6C05, //CJK UNIFIED IDEOGRAPH - 0xBEFC: 0x6FC2, //CJK UNIFIED IDEOGRAPH - 0xBEFD: 0x6FB1, //CJK UNIFIED IDEOGRAPH - 0xBEFE: 0x6FA1, //CJK UNIFIED IDEOGRAPH - 0xBF40: 0x6FC3, //CJK UNIFIED IDEOGRAPH - 0xBF41: 0x6FA4, //CJK UNIFIED IDEOGRAPH - 0xBF42: 0x6FC1, //CJK UNIFIED IDEOGRAPH - 0xBF43: 0x6FA7, //CJK UNIFIED IDEOGRAPH - 0xBF44: 0x6FB3, //CJK UNIFIED IDEOGRAPH - 0xBF45: 0x6FC0, //CJK UNIFIED IDEOGRAPH - 0xBF46: 0x6FB9, //CJK UNIFIED IDEOGRAPH - 0xBF47: 0x6FB6, //CJK UNIFIED IDEOGRAPH - 0xBF48: 0x6FA6, //CJK UNIFIED IDEOGRAPH - 0xBF49: 0x6FA0, //CJK UNIFIED IDEOGRAPH - 0xBF4A: 0x6FB4, //CJK UNIFIED IDEOGRAPH - 0xBF4B: 0x71BE, //CJK UNIFIED IDEOGRAPH - 0xBF4C: 0x71C9, //CJK UNIFIED IDEOGRAPH - 0xBF4D: 0x71D0, //CJK UNIFIED IDEOGRAPH - 0xBF4E: 0x71D2, //CJK UNIFIED IDEOGRAPH - 0xBF4F: 0x71C8, //CJK UNIFIED IDEOGRAPH - 0xBF50: 0x71D5, //CJK UNIFIED IDEOGRAPH - 0xBF51: 0x71B9, //CJK UNIFIED IDEOGRAPH - 0xBF52: 0x71CE, //CJK UNIFIED IDEOGRAPH - 0xBF53: 0x71D9, //CJK UNIFIED IDEOGRAPH - 0xBF54: 0x71DC, //CJK UNIFIED IDEOGRAPH - 0xBF55: 0x71C3, //CJK UNIFIED IDEOGRAPH - 0xBF56: 0x71C4, //CJK UNIFIED IDEOGRAPH - 0xBF57: 0x7368, //CJK UNIFIED IDEOGRAPH - 0xBF58: 0x749C, //CJK UNIFIED IDEOGRAPH - 0xBF59: 0x74A3, //CJK UNIFIED IDEOGRAPH - 0xBF5A: 0x7498, //CJK UNIFIED IDEOGRAPH - 0xBF5B: 0x749F, //CJK UNIFIED IDEOGRAPH - 0xBF5C: 0x749E, //CJK UNIFIED IDEOGRAPH - 0xBF5D: 0x74E2, //CJK UNIFIED IDEOGRAPH - 0xBF5E: 0x750C, //CJK UNIFIED IDEOGRAPH - 0xBF5F: 0x750D, //CJK UNIFIED IDEOGRAPH - 0xBF60: 0x7634, //CJK UNIFIED IDEOGRAPH - 0xBF61: 0x7638, //CJK UNIFIED IDEOGRAPH - 0xBF62: 0x763A, //CJK UNIFIED IDEOGRAPH - 0xBF63: 0x76E7, //CJK UNIFIED IDEOGRAPH - 0xBF64: 0x76E5, //CJK UNIFIED IDEOGRAPH - 0xBF65: 0x77A0, //CJK UNIFIED IDEOGRAPH - 0xBF66: 0x779E, //CJK UNIFIED IDEOGRAPH - 0xBF67: 0x779F, //CJK UNIFIED IDEOGRAPH - 0xBF68: 0x77A5, //CJK UNIFIED IDEOGRAPH - 0xBF69: 0x78E8, //CJK UNIFIED IDEOGRAPH - 0xBF6A: 0x78DA, //CJK UNIFIED IDEOGRAPH - 0xBF6B: 0x78EC, //CJK UNIFIED IDEOGRAPH - 0xBF6C: 0x78E7, //CJK UNIFIED IDEOGRAPH - 0xBF6D: 0x79A6, //CJK UNIFIED IDEOGRAPH - 0xBF6E: 0x7A4D, //CJK UNIFIED IDEOGRAPH - 0xBF6F: 0x7A4E, //CJK UNIFIED IDEOGRAPH - 0xBF70: 0x7A46, //CJK UNIFIED IDEOGRAPH - 0xBF71: 0x7A4C, //CJK UNIFIED IDEOGRAPH - 0xBF72: 0x7A4B, //CJK UNIFIED IDEOGRAPH - 0xBF73: 0x7ABA, //CJK UNIFIED IDEOGRAPH - 0xBF74: 0x7BD9, //CJK UNIFIED IDEOGRAPH - 0xBF75: 0x7C11, //CJK UNIFIED IDEOGRAPH - 0xBF76: 0x7BC9, //CJK UNIFIED IDEOGRAPH - 0xBF77: 0x7BE4, //CJK UNIFIED IDEOGRAPH - 0xBF78: 0x7BDB, //CJK UNIFIED IDEOGRAPH - 0xBF79: 0x7BE1, //CJK UNIFIED IDEOGRAPH - 0xBF7A: 0x7BE9, //CJK UNIFIED IDEOGRAPH - 0xBF7B: 0x7BE6, //CJK UNIFIED IDEOGRAPH - 0xBF7C: 0x7CD5, //CJK UNIFIED IDEOGRAPH - 0xBF7D: 0x7CD6, //CJK UNIFIED IDEOGRAPH - 0xBF7E: 0x7E0A, //CJK UNIFIED IDEOGRAPH - 0xBFA1: 0x7E11, //CJK UNIFIED IDEOGRAPH - 0xBFA2: 0x7E08, //CJK UNIFIED IDEOGRAPH - 0xBFA3: 0x7E1B, //CJK UNIFIED IDEOGRAPH - 0xBFA4: 0x7E23, //CJK UNIFIED IDEOGRAPH - 0xBFA5: 0x7E1E, //CJK UNIFIED IDEOGRAPH - 0xBFA6: 0x7E1D, //CJK UNIFIED IDEOGRAPH - 0xBFA7: 0x7E09, //CJK UNIFIED IDEOGRAPH - 0xBFA8: 0x7E10, //CJK UNIFIED IDEOGRAPH - 0xBFA9: 0x7F79, //CJK UNIFIED IDEOGRAPH - 0xBFAA: 0x7FB2, //CJK UNIFIED IDEOGRAPH - 0xBFAB: 0x7FF0, //CJK UNIFIED IDEOGRAPH - 0xBFAC: 0x7FF1, //CJK UNIFIED IDEOGRAPH - 0xBFAD: 0x7FEE, //CJK UNIFIED IDEOGRAPH - 0xBFAE: 0x8028, //CJK UNIFIED IDEOGRAPH - 0xBFAF: 0x81B3, //CJK UNIFIED IDEOGRAPH - 0xBFB0: 0x81A9, //CJK UNIFIED IDEOGRAPH - 0xBFB1: 0x81A8, //CJK UNIFIED IDEOGRAPH - 0xBFB2: 0x81FB, //CJK UNIFIED IDEOGRAPH - 0xBFB3: 0x8208, //CJK UNIFIED IDEOGRAPH - 0xBFB4: 0x8258, //CJK UNIFIED IDEOGRAPH - 0xBFB5: 0x8259, //CJK UNIFIED IDEOGRAPH - 0xBFB6: 0x854A, //CJK UNIFIED IDEOGRAPH - 0xBFB7: 0x8559, //CJK UNIFIED IDEOGRAPH - 0xBFB8: 0x8548, //CJK UNIFIED IDEOGRAPH - 0xBFB9: 0x8568, //CJK UNIFIED IDEOGRAPH - 0xBFBA: 0x8569, //CJK UNIFIED IDEOGRAPH - 0xBFBB: 0x8543, //CJK UNIFIED IDEOGRAPH - 0xBFBC: 0x8549, //CJK UNIFIED IDEOGRAPH - 0xBFBD: 0x856D, //CJK UNIFIED IDEOGRAPH - 0xBFBE: 0x856A, //CJK UNIFIED IDEOGRAPH - 0xBFBF: 0x855E, //CJK UNIFIED IDEOGRAPH - 0xBFC0: 0x8783, //CJK UNIFIED IDEOGRAPH - 0xBFC1: 0x879F, //CJK UNIFIED IDEOGRAPH - 0xBFC2: 0x879E, //CJK UNIFIED IDEOGRAPH - 0xBFC3: 0x87A2, //CJK UNIFIED IDEOGRAPH - 0xBFC4: 0x878D, //CJK UNIFIED IDEOGRAPH - 0xBFC5: 0x8861, //CJK UNIFIED IDEOGRAPH - 0xBFC6: 0x892A, //CJK UNIFIED IDEOGRAPH - 0xBFC7: 0x8932, //CJK UNIFIED IDEOGRAPH - 0xBFC8: 0x8925, //CJK UNIFIED IDEOGRAPH - 0xBFC9: 0x892B, //CJK UNIFIED IDEOGRAPH - 0xBFCA: 0x8921, //CJK UNIFIED IDEOGRAPH - 0xBFCB: 0x89AA, //CJK UNIFIED IDEOGRAPH - 0xBFCC: 0x89A6, //CJK UNIFIED IDEOGRAPH - 0xBFCD: 0x8AE6, //CJK UNIFIED IDEOGRAPH - 0xBFCE: 0x8AFA, //CJK UNIFIED IDEOGRAPH - 0xBFCF: 0x8AEB, //CJK UNIFIED IDEOGRAPH - 0xBFD0: 0x8AF1, //CJK UNIFIED IDEOGRAPH - 0xBFD1: 0x8B00, //CJK UNIFIED IDEOGRAPH - 0xBFD2: 0x8ADC, //CJK UNIFIED IDEOGRAPH - 0xBFD3: 0x8AE7, //CJK UNIFIED IDEOGRAPH - 0xBFD4: 0x8AEE, //CJK UNIFIED IDEOGRAPH - 0xBFD5: 0x8AFE, //CJK UNIFIED IDEOGRAPH - 0xBFD6: 0x8B01, //CJK UNIFIED IDEOGRAPH - 0xBFD7: 0x8B02, //CJK UNIFIED IDEOGRAPH - 0xBFD8: 0x8AF7, //CJK UNIFIED IDEOGRAPH - 0xBFD9: 0x8AED, //CJK UNIFIED IDEOGRAPH - 0xBFDA: 0x8AF3, //CJK UNIFIED IDEOGRAPH - 0xBFDB: 0x8AF6, //CJK UNIFIED IDEOGRAPH - 0xBFDC: 0x8AFC, //CJK UNIFIED IDEOGRAPH - 0xBFDD: 0x8C6B, //CJK UNIFIED IDEOGRAPH - 0xBFDE: 0x8C6D, //CJK UNIFIED IDEOGRAPH - 0xBFDF: 0x8C93, //CJK UNIFIED IDEOGRAPH - 0xBFE0: 0x8CF4, //CJK UNIFIED IDEOGRAPH - 0xBFE1: 0x8E44, //CJK UNIFIED IDEOGRAPH - 0xBFE2: 0x8E31, //CJK UNIFIED IDEOGRAPH - 0xBFE3: 0x8E34, //CJK UNIFIED IDEOGRAPH - 0xBFE4: 0x8E42, //CJK UNIFIED IDEOGRAPH - 0xBFE5: 0x8E39, //CJK UNIFIED IDEOGRAPH - 0xBFE6: 0x8E35, //CJK UNIFIED IDEOGRAPH - 0xBFE7: 0x8F3B, //CJK UNIFIED IDEOGRAPH - 0xBFE8: 0x8F2F, //CJK UNIFIED IDEOGRAPH - 0xBFE9: 0x8F38, //CJK UNIFIED IDEOGRAPH - 0xBFEA: 0x8F33, //CJK UNIFIED IDEOGRAPH - 0xBFEB: 0x8FA8, //CJK UNIFIED IDEOGRAPH - 0xBFEC: 0x8FA6, //CJK UNIFIED IDEOGRAPH - 0xBFED: 0x9075, //CJK UNIFIED IDEOGRAPH - 0xBFEE: 0x9074, //CJK UNIFIED IDEOGRAPH - 0xBFEF: 0x9078, //CJK UNIFIED IDEOGRAPH - 0xBFF0: 0x9072, //CJK UNIFIED IDEOGRAPH - 0xBFF1: 0x907C, //CJK UNIFIED IDEOGRAPH - 0xBFF2: 0x907A, //CJK UNIFIED IDEOGRAPH - 0xBFF3: 0x9134, //CJK UNIFIED IDEOGRAPH - 0xBFF4: 0x9192, //CJK UNIFIED IDEOGRAPH - 0xBFF5: 0x9320, //CJK UNIFIED IDEOGRAPH - 0xBFF6: 0x9336, //CJK UNIFIED IDEOGRAPH - 0xBFF7: 0x92F8, //CJK UNIFIED IDEOGRAPH - 0xBFF8: 0x9333, //CJK UNIFIED IDEOGRAPH - 0xBFF9: 0x932F, //CJK UNIFIED IDEOGRAPH - 0xBFFA: 0x9322, //CJK UNIFIED IDEOGRAPH - 0xBFFB: 0x92FC, //CJK UNIFIED IDEOGRAPH - 0xBFFC: 0x932B, //CJK UNIFIED IDEOGRAPH - 0xBFFD: 0x9304, //CJK UNIFIED IDEOGRAPH - 0xBFFE: 0x931A, //CJK UNIFIED IDEOGRAPH - 0xC040: 0x9310, //CJK UNIFIED IDEOGRAPH - 0xC041: 0x9326, //CJK UNIFIED IDEOGRAPH - 0xC042: 0x9321, //CJK UNIFIED IDEOGRAPH - 0xC043: 0x9315, //CJK UNIFIED IDEOGRAPH - 0xC044: 0x932E, //CJK UNIFIED IDEOGRAPH - 0xC045: 0x9319, //CJK UNIFIED IDEOGRAPH - 0xC046: 0x95BB, //CJK UNIFIED IDEOGRAPH - 0xC047: 0x96A7, //CJK UNIFIED IDEOGRAPH - 0xC048: 0x96A8, //CJK UNIFIED IDEOGRAPH - 0xC049: 0x96AA, //CJK UNIFIED IDEOGRAPH - 0xC04A: 0x96D5, //CJK UNIFIED IDEOGRAPH - 0xC04B: 0x970E, //CJK UNIFIED IDEOGRAPH - 0xC04C: 0x9711, //CJK UNIFIED IDEOGRAPH - 0xC04D: 0x9716, //CJK UNIFIED IDEOGRAPH - 0xC04E: 0x970D, //CJK UNIFIED IDEOGRAPH - 0xC04F: 0x9713, //CJK UNIFIED IDEOGRAPH - 0xC050: 0x970F, //CJK UNIFIED IDEOGRAPH - 0xC051: 0x975B, //CJK UNIFIED IDEOGRAPH - 0xC052: 0x975C, //CJK UNIFIED IDEOGRAPH - 0xC053: 0x9766, //CJK UNIFIED IDEOGRAPH - 0xC054: 0x9798, //CJK UNIFIED IDEOGRAPH - 0xC055: 0x9830, //CJK UNIFIED IDEOGRAPH - 0xC056: 0x9838, //CJK UNIFIED IDEOGRAPH - 0xC057: 0x983B, //CJK UNIFIED IDEOGRAPH - 0xC058: 0x9837, //CJK UNIFIED IDEOGRAPH - 0xC059: 0x982D, //CJK UNIFIED IDEOGRAPH - 0xC05A: 0x9839, //CJK UNIFIED IDEOGRAPH - 0xC05B: 0x9824, //CJK UNIFIED IDEOGRAPH - 0xC05C: 0x9910, //CJK UNIFIED IDEOGRAPH - 0xC05D: 0x9928, //CJK UNIFIED IDEOGRAPH - 0xC05E: 0x991E, //CJK UNIFIED IDEOGRAPH - 0xC05F: 0x991B, //CJK UNIFIED IDEOGRAPH - 0xC060: 0x9921, //CJK UNIFIED IDEOGRAPH - 0xC061: 0x991A, //CJK UNIFIED IDEOGRAPH - 0xC062: 0x99ED, //CJK UNIFIED IDEOGRAPH - 0xC063: 0x99E2, //CJK UNIFIED IDEOGRAPH - 0xC064: 0x99F1, //CJK UNIFIED IDEOGRAPH - 0xC065: 0x9AB8, //CJK UNIFIED IDEOGRAPH - 0xC066: 0x9ABC, //CJK UNIFIED IDEOGRAPH - 0xC067: 0x9AFB, //CJK UNIFIED IDEOGRAPH - 0xC068: 0x9AED, //CJK UNIFIED IDEOGRAPH - 0xC069: 0x9B28, //CJK UNIFIED IDEOGRAPH - 0xC06A: 0x9B91, //CJK UNIFIED IDEOGRAPH - 0xC06B: 0x9D15, //CJK UNIFIED IDEOGRAPH - 0xC06C: 0x9D23, //CJK UNIFIED IDEOGRAPH - 0xC06D: 0x9D26, //CJK UNIFIED IDEOGRAPH - 0xC06E: 0x9D28, //CJK UNIFIED IDEOGRAPH - 0xC06F: 0x9D12, //CJK UNIFIED IDEOGRAPH - 0xC070: 0x9D1B, //CJK UNIFIED IDEOGRAPH - 0xC071: 0x9ED8, //CJK UNIFIED IDEOGRAPH - 0xC072: 0x9ED4, //CJK UNIFIED IDEOGRAPH - 0xC073: 0x9F8D, //CJK UNIFIED IDEOGRAPH - 0xC074: 0x9F9C, //CJK UNIFIED IDEOGRAPH - 0xC075: 0x512A, //CJK UNIFIED IDEOGRAPH - 0xC076: 0x511F, //CJK UNIFIED IDEOGRAPH - 0xC077: 0x5121, //CJK UNIFIED IDEOGRAPH - 0xC078: 0x5132, //CJK UNIFIED IDEOGRAPH - 0xC079: 0x52F5, //CJK UNIFIED IDEOGRAPH - 0xC07A: 0x568E, //CJK UNIFIED IDEOGRAPH - 0xC07B: 0x5680, //CJK UNIFIED IDEOGRAPH - 0xC07C: 0x5690, //CJK UNIFIED IDEOGRAPH - 0xC07D: 0x5685, //CJK UNIFIED IDEOGRAPH - 0xC07E: 0x5687, //CJK UNIFIED IDEOGRAPH - 0xC0A1: 0x568F, //CJK UNIFIED IDEOGRAPH - 0xC0A2: 0x58D5, //CJK UNIFIED IDEOGRAPH - 0xC0A3: 0x58D3, //CJK UNIFIED IDEOGRAPH - 0xC0A4: 0x58D1, //CJK UNIFIED IDEOGRAPH - 0xC0A5: 0x58CE, //CJK UNIFIED IDEOGRAPH - 0xC0A6: 0x5B30, //CJK UNIFIED IDEOGRAPH - 0xC0A7: 0x5B2A, //CJK UNIFIED IDEOGRAPH - 0xC0A8: 0x5B24, //CJK UNIFIED IDEOGRAPH - 0xC0A9: 0x5B7A, //CJK UNIFIED IDEOGRAPH - 0xC0AA: 0x5C37, //CJK UNIFIED IDEOGRAPH - 0xC0AB: 0x5C68, //CJK UNIFIED IDEOGRAPH - 0xC0AC: 0x5DBC, //CJK UNIFIED IDEOGRAPH - 0xC0AD: 0x5DBA, //CJK UNIFIED IDEOGRAPH - 0xC0AE: 0x5DBD, //CJK UNIFIED IDEOGRAPH - 0xC0AF: 0x5DB8, //CJK UNIFIED IDEOGRAPH - 0xC0B0: 0x5E6B, //CJK UNIFIED IDEOGRAPH - 0xC0B1: 0x5F4C, //CJK UNIFIED IDEOGRAPH - 0xC0B2: 0x5FBD, //CJK UNIFIED IDEOGRAPH - 0xC0B3: 0x61C9, //CJK UNIFIED IDEOGRAPH - 0xC0B4: 0x61C2, //CJK UNIFIED IDEOGRAPH - 0xC0B5: 0x61C7, //CJK UNIFIED IDEOGRAPH - 0xC0B6: 0x61E6, //CJK UNIFIED IDEOGRAPH - 0xC0B7: 0x61CB, //CJK UNIFIED IDEOGRAPH - 0xC0B8: 0x6232, //CJK UNIFIED IDEOGRAPH - 0xC0B9: 0x6234, //CJK UNIFIED IDEOGRAPH - 0xC0BA: 0x64CE, //CJK UNIFIED IDEOGRAPH - 0xC0BB: 0x64CA, //CJK UNIFIED IDEOGRAPH - 0xC0BC: 0x64D8, //CJK UNIFIED IDEOGRAPH - 0xC0BD: 0x64E0, //CJK UNIFIED IDEOGRAPH - 0xC0BE: 0x64F0, //CJK UNIFIED IDEOGRAPH - 0xC0BF: 0x64E6, //CJK UNIFIED IDEOGRAPH - 0xC0C0: 0x64EC, //CJK UNIFIED IDEOGRAPH - 0xC0C1: 0x64F1, //CJK UNIFIED IDEOGRAPH - 0xC0C2: 0x64E2, //CJK UNIFIED IDEOGRAPH - 0xC0C3: 0x64ED, //CJK UNIFIED IDEOGRAPH - 0xC0C4: 0x6582, //CJK UNIFIED IDEOGRAPH - 0xC0C5: 0x6583, //CJK UNIFIED IDEOGRAPH - 0xC0C6: 0x66D9, //CJK UNIFIED IDEOGRAPH - 0xC0C7: 0x66D6, //CJK UNIFIED IDEOGRAPH - 0xC0C8: 0x6A80, //CJK UNIFIED IDEOGRAPH - 0xC0C9: 0x6A94, //CJK UNIFIED IDEOGRAPH - 0xC0CA: 0x6A84, //CJK UNIFIED IDEOGRAPH - 0xC0CB: 0x6AA2, //CJK UNIFIED IDEOGRAPH - 0xC0CC: 0x6A9C, //CJK UNIFIED IDEOGRAPH - 0xC0CD: 0x6ADB, //CJK UNIFIED IDEOGRAPH - 0xC0CE: 0x6AA3, //CJK UNIFIED IDEOGRAPH - 0xC0CF: 0x6A7E, //CJK UNIFIED IDEOGRAPH - 0xC0D0: 0x6A97, //CJK UNIFIED IDEOGRAPH - 0xC0D1: 0x6A90, //CJK UNIFIED IDEOGRAPH - 0xC0D2: 0x6AA0, //CJK UNIFIED IDEOGRAPH - 0xC0D3: 0x6B5C, //CJK UNIFIED IDEOGRAPH - 0xC0D4: 0x6BAE, //CJK UNIFIED IDEOGRAPH - 0xC0D5: 0x6BDA, //CJK UNIFIED IDEOGRAPH - 0xC0D6: 0x6C08, //CJK UNIFIED IDEOGRAPH - 0xC0D7: 0x6FD8, //CJK UNIFIED IDEOGRAPH - 0xC0D8: 0x6FF1, //CJK UNIFIED IDEOGRAPH - 0xC0D9: 0x6FDF, //CJK UNIFIED IDEOGRAPH - 0xC0DA: 0x6FE0, //CJK UNIFIED IDEOGRAPH - 0xC0DB: 0x6FDB, //CJK UNIFIED IDEOGRAPH - 0xC0DC: 0x6FE4, //CJK UNIFIED IDEOGRAPH - 0xC0DD: 0x6FEB, //CJK UNIFIED IDEOGRAPH - 0xC0DE: 0x6FEF, //CJK UNIFIED IDEOGRAPH - 0xC0DF: 0x6F80, //CJK UNIFIED IDEOGRAPH - 0xC0E0: 0x6FEC, //CJK UNIFIED IDEOGRAPH - 0xC0E1: 0x6FE1, //CJK UNIFIED IDEOGRAPH - 0xC0E2: 0x6FE9, //CJK UNIFIED IDEOGRAPH - 0xC0E3: 0x6FD5, //CJK UNIFIED IDEOGRAPH - 0xC0E4: 0x6FEE, //CJK UNIFIED IDEOGRAPH - 0xC0E5: 0x6FF0, //CJK UNIFIED IDEOGRAPH - 0xC0E6: 0x71E7, //CJK UNIFIED IDEOGRAPH - 0xC0E7: 0x71DF, //CJK UNIFIED IDEOGRAPH - 0xC0E8: 0x71EE, //CJK UNIFIED IDEOGRAPH - 0xC0E9: 0x71E6, //CJK UNIFIED IDEOGRAPH - 0xC0EA: 0x71E5, //CJK UNIFIED IDEOGRAPH - 0xC0EB: 0x71ED, //CJK UNIFIED IDEOGRAPH - 0xC0EC: 0x71EC, //CJK UNIFIED IDEOGRAPH - 0xC0ED: 0x71F4, //CJK UNIFIED IDEOGRAPH - 0xC0EE: 0x71E0, //CJK UNIFIED IDEOGRAPH - 0xC0EF: 0x7235, //CJK UNIFIED IDEOGRAPH - 0xC0F0: 0x7246, //CJK UNIFIED IDEOGRAPH - 0xC0F1: 0x7370, //CJK UNIFIED IDEOGRAPH - 0xC0F2: 0x7372, //CJK UNIFIED IDEOGRAPH - 0xC0F3: 0x74A9, //CJK UNIFIED IDEOGRAPH - 0xC0F4: 0x74B0, //CJK UNIFIED IDEOGRAPH - 0xC0F5: 0x74A6, //CJK UNIFIED IDEOGRAPH - 0xC0F6: 0x74A8, //CJK UNIFIED IDEOGRAPH - 0xC0F7: 0x7646, //CJK UNIFIED IDEOGRAPH - 0xC0F8: 0x7642, //CJK UNIFIED IDEOGRAPH - 0xC0F9: 0x764C, //CJK UNIFIED IDEOGRAPH - 0xC0FA: 0x76EA, //CJK UNIFIED IDEOGRAPH - 0xC0FB: 0x77B3, //CJK UNIFIED IDEOGRAPH - 0xC0FC: 0x77AA, //CJK UNIFIED IDEOGRAPH - 0xC0FD: 0x77B0, //CJK UNIFIED IDEOGRAPH - 0xC0FE: 0x77AC, //CJK UNIFIED IDEOGRAPH - 0xC140: 0x77A7, //CJK UNIFIED IDEOGRAPH - 0xC141: 0x77AD, //CJK UNIFIED IDEOGRAPH - 0xC142: 0x77EF, //CJK UNIFIED IDEOGRAPH - 0xC143: 0x78F7, //CJK UNIFIED IDEOGRAPH - 0xC144: 0x78FA, //CJK UNIFIED IDEOGRAPH - 0xC145: 0x78F4, //CJK UNIFIED IDEOGRAPH - 0xC146: 0x78EF, //CJK UNIFIED IDEOGRAPH - 0xC147: 0x7901, //CJK UNIFIED IDEOGRAPH - 0xC148: 0x79A7, //CJK UNIFIED IDEOGRAPH - 0xC149: 0x79AA, //CJK UNIFIED IDEOGRAPH - 0xC14A: 0x7A57, //CJK UNIFIED IDEOGRAPH - 0xC14B: 0x7ABF, //CJK UNIFIED IDEOGRAPH - 0xC14C: 0x7C07, //CJK UNIFIED IDEOGRAPH - 0xC14D: 0x7C0D, //CJK UNIFIED IDEOGRAPH - 0xC14E: 0x7BFE, //CJK UNIFIED IDEOGRAPH - 0xC14F: 0x7BF7, //CJK UNIFIED IDEOGRAPH - 0xC150: 0x7C0C, //CJK UNIFIED IDEOGRAPH - 0xC151: 0x7BE0, //CJK UNIFIED IDEOGRAPH - 0xC152: 0x7CE0, //CJK UNIFIED IDEOGRAPH - 0xC153: 0x7CDC, //CJK UNIFIED IDEOGRAPH - 0xC154: 0x7CDE, //CJK UNIFIED IDEOGRAPH - 0xC155: 0x7CE2, //CJK UNIFIED IDEOGRAPH - 0xC156: 0x7CDF, //CJK UNIFIED IDEOGRAPH - 0xC157: 0x7CD9, //CJK UNIFIED IDEOGRAPH - 0xC158: 0x7CDD, //CJK UNIFIED IDEOGRAPH - 0xC159: 0x7E2E, //CJK UNIFIED IDEOGRAPH - 0xC15A: 0x7E3E, //CJK UNIFIED IDEOGRAPH - 0xC15B: 0x7E46, //CJK UNIFIED IDEOGRAPH - 0xC15C: 0x7E37, //CJK UNIFIED IDEOGRAPH - 0xC15D: 0x7E32, //CJK UNIFIED IDEOGRAPH - 0xC15E: 0x7E43, //CJK UNIFIED IDEOGRAPH - 0xC15F: 0x7E2B, //CJK UNIFIED IDEOGRAPH - 0xC160: 0x7E3D, //CJK UNIFIED IDEOGRAPH - 0xC161: 0x7E31, //CJK UNIFIED IDEOGRAPH - 0xC162: 0x7E45, //CJK UNIFIED IDEOGRAPH - 0xC163: 0x7E41, //CJK UNIFIED IDEOGRAPH - 0xC164: 0x7E34, //CJK UNIFIED IDEOGRAPH - 0xC165: 0x7E39, //CJK UNIFIED IDEOGRAPH - 0xC166: 0x7E48, //CJK UNIFIED IDEOGRAPH - 0xC167: 0x7E35, //CJK UNIFIED IDEOGRAPH - 0xC168: 0x7E3F, //CJK UNIFIED IDEOGRAPH - 0xC169: 0x7E2F, //CJK UNIFIED IDEOGRAPH - 0xC16A: 0x7F44, //CJK UNIFIED IDEOGRAPH - 0xC16B: 0x7FF3, //CJK UNIFIED IDEOGRAPH - 0xC16C: 0x7FFC, //CJK UNIFIED IDEOGRAPH - 0xC16D: 0x8071, //CJK UNIFIED IDEOGRAPH - 0xC16E: 0x8072, //CJK UNIFIED IDEOGRAPH - 0xC16F: 0x8070, //CJK UNIFIED IDEOGRAPH - 0xC170: 0x806F, //CJK UNIFIED IDEOGRAPH - 0xC171: 0x8073, //CJK UNIFIED IDEOGRAPH - 0xC172: 0x81C6, //CJK UNIFIED IDEOGRAPH - 0xC173: 0x81C3, //CJK UNIFIED IDEOGRAPH - 0xC174: 0x81BA, //CJK UNIFIED IDEOGRAPH - 0xC175: 0x81C2, //CJK UNIFIED IDEOGRAPH - 0xC176: 0x81C0, //CJK UNIFIED IDEOGRAPH - 0xC177: 0x81BF, //CJK UNIFIED IDEOGRAPH - 0xC178: 0x81BD, //CJK UNIFIED IDEOGRAPH - 0xC179: 0x81C9, //CJK UNIFIED IDEOGRAPH - 0xC17A: 0x81BE, //CJK UNIFIED IDEOGRAPH - 0xC17B: 0x81E8, //CJK UNIFIED IDEOGRAPH - 0xC17C: 0x8209, //CJK UNIFIED IDEOGRAPH - 0xC17D: 0x8271, //CJK UNIFIED IDEOGRAPH - 0xC17E: 0x85AA, //CJK UNIFIED IDEOGRAPH - 0xC1A1: 0x8584, //CJK UNIFIED IDEOGRAPH - 0xC1A2: 0x857E, //CJK UNIFIED IDEOGRAPH - 0xC1A3: 0x859C, //CJK UNIFIED IDEOGRAPH - 0xC1A4: 0x8591, //CJK UNIFIED IDEOGRAPH - 0xC1A5: 0x8594, //CJK UNIFIED IDEOGRAPH - 0xC1A6: 0x85AF, //CJK UNIFIED IDEOGRAPH - 0xC1A7: 0x859B, //CJK UNIFIED IDEOGRAPH - 0xC1A8: 0x8587, //CJK UNIFIED IDEOGRAPH - 0xC1A9: 0x85A8, //CJK UNIFIED IDEOGRAPH - 0xC1AA: 0x858A, //CJK UNIFIED IDEOGRAPH - 0xC1AB: 0x8667, //CJK UNIFIED IDEOGRAPH - 0xC1AC: 0x87C0, //CJK UNIFIED IDEOGRAPH - 0xC1AD: 0x87D1, //CJK UNIFIED IDEOGRAPH - 0xC1AE: 0x87B3, //CJK UNIFIED IDEOGRAPH - 0xC1AF: 0x87D2, //CJK UNIFIED IDEOGRAPH - 0xC1B0: 0x87C6, //CJK UNIFIED IDEOGRAPH - 0xC1B1: 0x87AB, //CJK UNIFIED IDEOGRAPH - 0xC1B2: 0x87BB, //CJK UNIFIED IDEOGRAPH - 0xC1B3: 0x87BA, //CJK UNIFIED IDEOGRAPH - 0xC1B4: 0x87C8, //CJK UNIFIED IDEOGRAPH - 0xC1B5: 0x87CB, //CJK UNIFIED IDEOGRAPH - 0xC1B6: 0x893B, //CJK UNIFIED IDEOGRAPH - 0xC1B7: 0x8936, //CJK UNIFIED IDEOGRAPH - 0xC1B8: 0x8944, //CJK UNIFIED IDEOGRAPH - 0xC1B9: 0x8938, //CJK UNIFIED IDEOGRAPH - 0xC1BA: 0x893D, //CJK UNIFIED IDEOGRAPH - 0xC1BB: 0x89AC, //CJK UNIFIED IDEOGRAPH - 0xC1BC: 0x8B0E, //CJK UNIFIED IDEOGRAPH - 0xC1BD: 0x8B17, //CJK UNIFIED IDEOGRAPH - 0xC1BE: 0x8B19, //CJK UNIFIED IDEOGRAPH - 0xC1BF: 0x8B1B, //CJK UNIFIED IDEOGRAPH - 0xC1C0: 0x8B0A, //CJK UNIFIED IDEOGRAPH - 0xC1C1: 0x8B20, //CJK UNIFIED IDEOGRAPH - 0xC1C2: 0x8B1D, //CJK UNIFIED IDEOGRAPH - 0xC1C3: 0x8B04, //CJK UNIFIED IDEOGRAPH - 0xC1C4: 0x8B10, //CJK UNIFIED IDEOGRAPH - 0xC1C5: 0x8C41, //CJK UNIFIED IDEOGRAPH - 0xC1C6: 0x8C3F, //CJK UNIFIED IDEOGRAPH - 0xC1C7: 0x8C73, //CJK UNIFIED IDEOGRAPH - 0xC1C8: 0x8CFA, //CJK UNIFIED IDEOGRAPH - 0xC1C9: 0x8CFD, //CJK UNIFIED IDEOGRAPH - 0xC1CA: 0x8CFC, //CJK UNIFIED IDEOGRAPH - 0xC1CB: 0x8CF8, //CJK UNIFIED IDEOGRAPH - 0xC1CC: 0x8CFB, //CJK UNIFIED IDEOGRAPH - 0xC1CD: 0x8DA8, //CJK UNIFIED IDEOGRAPH - 0xC1CE: 0x8E49, //CJK UNIFIED IDEOGRAPH - 0xC1CF: 0x8E4B, //CJK UNIFIED IDEOGRAPH - 0xC1D0: 0x8E48, //CJK UNIFIED IDEOGRAPH - 0xC1D1: 0x8E4A, //CJK UNIFIED IDEOGRAPH - 0xC1D2: 0x8F44, //CJK UNIFIED IDEOGRAPH - 0xC1D3: 0x8F3E, //CJK UNIFIED IDEOGRAPH - 0xC1D4: 0x8F42, //CJK UNIFIED IDEOGRAPH - 0xC1D5: 0x8F45, //CJK UNIFIED IDEOGRAPH - 0xC1D6: 0x8F3F, //CJK UNIFIED IDEOGRAPH - 0xC1D7: 0x907F, //CJK UNIFIED IDEOGRAPH - 0xC1D8: 0x907D, //CJK UNIFIED IDEOGRAPH - 0xC1D9: 0x9084, //CJK UNIFIED IDEOGRAPH - 0xC1DA: 0x9081, //CJK UNIFIED IDEOGRAPH - 0xC1DB: 0x9082, //CJK UNIFIED IDEOGRAPH - 0xC1DC: 0x9080, //CJK UNIFIED IDEOGRAPH - 0xC1DD: 0x9139, //CJK UNIFIED IDEOGRAPH - 0xC1DE: 0x91A3, //CJK UNIFIED IDEOGRAPH - 0xC1DF: 0x919E, //CJK UNIFIED IDEOGRAPH - 0xC1E0: 0x919C, //CJK UNIFIED IDEOGRAPH - 0xC1E1: 0x934D, //CJK UNIFIED IDEOGRAPH - 0xC1E2: 0x9382, //CJK UNIFIED IDEOGRAPH - 0xC1E3: 0x9328, //CJK UNIFIED IDEOGRAPH - 0xC1E4: 0x9375, //CJK UNIFIED IDEOGRAPH - 0xC1E5: 0x934A, //CJK UNIFIED IDEOGRAPH - 0xC1E6: 0x9365, //CJK UNIFIED IDEOGRAPH - 0xC1E7: 0x934B, //CJK UNIFIED IDEOGRAPH - 0xC1E8: 0x9318, //CJK UNIFIED IDEOGRAPH - 0xC1E9: 0x937E, //CJK UNIFIED IDEOGRAPH - 0xC1EA: 0x936C, //CJK UNIFIED IDEOGRAPH - 0xC1EB: 0x935B, //CJK UNIFIED IDEOGRAPH - 0xC1EC: 0x9370, //CJK UNIFIED IDEOGRAPH - 0xC1ED: 0x935A, //CJK UNIFIED IDEOGRAPH - 0xC1EE: 0x9354, //CJK UNIFIED IDEOGRAPH - 0xC1EF: 0x95CA, //CJK UNIFIED IDEOGRAPH - 0xC1F0: 0x95CB, //CJK UNIFIED IDEOGRAPH - 0xC1F1: 0x95CC, //CJK UNIFIED IDEOGRAPH - 0xC1F2: 0x95C8, //CJK UNIFIED IDEOGRAPH - 0xC1F3: 0x95C6, //CJK UNIFIED IDEOGRAPH - 0xC1F4: 0x96B1, //CJK UNIFIED IDEOGRAPH - 0xC1F5: 0x96B8, //CJK UNIFIED IDEOGRAPH - 0xC1F6: 0x96D6, //CJK UNIFIED IDEOGRAPH - 0xC1F7: 0x971C, //CJK UNIFIED IDEOGRAPH - 0xC1F8: 0x971E, //CJK UNIFIED IDEOGRAPH - 0xC1F9: 0x97A0, //CJK UNIFIED IDEOGRAPH - 0xC1FA: 0x97D3, //CJK UNIFIED IDEOGRAPH - 0xC1FB: 0x9846, //CJK UNIFIED IDEOGRAPH - 0xC1FC: 0x98B6, //CJK UNIFIED IDEOGRAPH - 0xC1FD: 0x9935, //CJK UNIFIED IDEOGRAPH - 0xC1FE: 0x9A01, //CJK UNIFIED IDEOGRAPH - 0xC240: 0x99FF, //CJK UNIFIED IDEOGRAPH - 0xC241: 0x9BAE, //CJK UNIFIED IDEOGRAPH - 0xC242: 0x9BAB, //CJK UNIFIED IDEOGRAPH - 0xC243: 0x9BAA, //CJK UNIFIED IDEOGRAPH - 0xC244: 0x9BAD, //CJK UNIFIED IDEOGRAPH - 0xC245: 0x9D3B, //CJK UNIFIED IDEOGRAPH - 0xC246: 0x9D3F, //CJK UNIFIED IDEOGRAPH - 0xC247: 0x9E8B, //CJK UNIFIED IDEOGRAPH - 0xC248: 0x9ECF, //CJK UNIFIED IDEOGRAPH - 0xC249: 0x9EDE, //CJK UNIFIED IDEOGRAPH - 0xC24A: 0x9EDC, //CJK UNIFIED IDEOGRAPH - 0xC24B: 0x9EDD, //CJK UNIFIED IDEOGRAPH - 0xC24C: 0x9EDB, //CJK UNIFIED IDEOGRAPH - 0xC24D: 0x9F3E, //CJK UNIFIED IDEOGRAPH - 0xC24E: 0x9F4B, //CJK UNIFIED IDEOGRAPH - 0xC24F: 0x53E2, //CJK UNIFIED IDEOGRAPH - 0xC250: 0x5695, //CJK UNIFIED IDEOGRAPH - 0xC251: 0x56AE, //CJK UNIFIED IDEOGRAPH - 0xC252: 0x58D9, //CJK UNIFIED IDEOGRAPH - 0xC253: 0x58D8, //CJK UNIFIED IDEOGRAPH - 0xC254: 0x5B38, //CJK UNIFIED IDEOGRAPH - 0xC255: 0x5F5D, //CJK UNIFIED IDEOGRAPH - 0xC256: 0x61E3, //CJK UNIFIED IDEOGRAPH - 0xC257: 0x6233, //CJK UNIFIED IDEOGRAPH - 0xC258: 0x64F4, //CJK UNIFIED IDEOGRAPH - 0xC259: 0x64F2, //CJK UNIFIED IDEOGRAPH - 0xC25A: 0x64FE, //CJK UNIFIED IDEOGRAPH - 0xC25B: 0x6506, //CJK UNIFIED IDEOGRAPH - 0xC25C: 0x64FA, //CJK UNIFIED IDEOGRAPH - 0xC25D: 0x64FB, //CJK UNIFIED IDEOGRAPH - 0xC25E: 0x64F7, //CJK UNIFIED IDEOGRAPH - 0xC25F: 0x65B7, //CJK UNIFIED IDEOGRAPH - 0xC260: 0x66DC, //CJK UNIFIED IDEOGRAPH - 0xC261: 0x6726, //CJK UNIFIED IDEOGRAPH - 0xC262: 0x6AB3, //CJK UNIFIED IDEOGRAPH - 0xC263: 0x6AAC, //CJK UNIFIED IDEOGRAPH - 0xC264: 0x6AC3, //CJK UNIFIED IDEOGRAPH - 0xC265: 0x6ABB, //CJK UNIFIED IDEOGRAPH - 0xC266: 0x6AB8, //CJK UNIFIED IDEOGRAPH - 0xC267: 0x6AC2, //CJK UNIFIED IDEOGRAPH - 0xC268: 0x6AAE, //CJK UNIFIED IDEOGRAPH - 0xC269: 0x6AAF, //CJK UNIFIED IDEOGRAPH - 0xC26A: 0x6B5F, //CJK UNIFIED IDEOGRAPH - 0xC26B: 0x6B78, //CJK UNIFIED IDEOGRAPH - 0xC26C: 0x6BAF, //CJK UNIFIED IDEOGRAPH - 0xC26D: 0x7009, //CJK UNIFIED IDEOGRAPH - 0xC26E: 0x700B, //CJK UNIFIED IDEOGRAPH - 0xC26F: 0x6FFE, //CJK UNIFIED IDEOGRAPH - 0xC270: 0x7006, //CJK UNIFIED IDEOGRAPH - 0xC271: 0x6FFA, //CJK UNIFIED IDEOGRAPH - 0xC272: 0x7011, //CJK UNIFIED IDEOGRAPH - 0xC273: 0x700F, //CJK UNIFIED IDEOGRAPH - 0xC274: 0x71FB, //CJK UNIFIED IDEOGRAPH - 0xC275: 0x71FC, //CJK UNIFIED IDEOGRAPH - 0xC276: 0x71FE, //CJK UNIFIED IDEOGRAPH - 0xC277: 0x71F8, //CJK UNIFIED IDEOGRAPH - 0xC278: 0x7377, //CJK UNIFIED IDEOGRAPH - 0xC279: 0x7375, //CJK UNIFIED IDEOGRAPH - 0xC27A: 0x74A7, //CJK UNIFIED IDEOGRAPH - 0xC27B: 0x74BF, //CJK UNIFIED IDEOGRAPH - 0xC27C: 0x7515, //CJK UNIFIED IDEOGRAPH - 0xC27D: 0x7656, //CJK UNIFIED IDEOGRAPH - 0xC27E: 0x7658, //CJK UNIFIED IDEOGRAPH - 0xC2A1: 0x7652, //CJK UNIFIED IDEOGRAPH - 0xC2A2: 0x77BD, //CJK UNIFIED IDEOGRAPH - 0xC2A3: 0x77BF, //CJK UNIFIED IDEOGRAPH - 0xC2A4: 0x77BB, //CJK UNIFIED IDEOGRAPH - 0xC2A5: 0x77BC, //CJK UNIFIED IDEOGRAPH - 0xC2A6: 0x790E, //CJK UNIFIED IDEOGRAPH - 0xC2A7: 0x79AE, //CJK UNIFIED IDEOGRAPH - 0xC2A8: 0x7A61, //CJK UNIFIED IDEOGRAPH - 0xC2A9: 0x7A62, //CJK UNIFIED IDEOGRAPH - 0xC2AA: 0x7A60, //CJK UNIFIED IDEOGRAPH - 0xC2AB: 0x7AC4, //CJK UNIFIED IDEOGRAPH - 0xC2AC: 0x7AC5, //CJK UNIFIED IDEOGRAPH - 0xC2AD: 0x7C2B, //CJK UNIFIED IDEOGRAPH - 0xC2AE: 0x7C27, //CJK UNIFIED IDEOGRAPH - 0xC2AF: 0x7C2A, //CJK UNIFIED IDEOGRAPH - 0xC2B0: 0x7C1E, //CJK UNIFIED IDEOGRAPH - 0xC2B1: 0x7C23, //CJK UNIFIED IDEOGRAPH - 0xC2B2: 0x7C21, //CJK UNIFIED IDEOGRAPH - 0xC2B3: 0x7CE7, //CJK UNIFIED IDEOGRAPH - 0xC2B4: 0x7E54, //CJK UNIFIED IDEOGRAPH - 0xC2B5: 0x7E55, //CJK UNIFIED IDEOGRAPH - 0xC2B6: 0x7E5E, //CJK UNIFIED IDEOGRAPH - 0xC2B7: 0x7E5A, //CJK UNIFIED IDEOGRAPH - 0xC2B8: 0x7E61, //CJK UNIFIED IDEOGRAPH - 0xC2B9: 0x7E52, //CJK UNIFIED IDEOGRAPH - 0xC2BA: 0x7E59, //CJK UNIFIED IDEOGRAPH - 0xC2BB: 0x7F48, //CJK UNIFIED IDEOGRAPH - 0xC2BC: 0x7FF9, //CJK UNIFIED IDEOGRAPH - 0xC2BD: 0x7FFB, //CJK UNIFIED IDEOGRAPH - 0xC2BE: 0x8077, //CJK UNIFIED IDEOGRAPH - 0xC2BF: 0x8076, //CJK UNIFIED IDEOGRAPH - 0xC2C0: 0x81CD, //CJK UNIFIED IDEOGRAPH - 0xC2C1: 0x81CF, //CJK UNIFIED IDEOGRAPH - 0xC2C2: 0x820A, //CJK UNIFIED IDEOGRAPH - 0xC2C3: 0x85CF, //CJK UNIFIED IDEOGRAPH - 0xC2C4: 0x85A9, //CJK UNIFIED IDEOGRAPH - 0xC2C5: 0x85CD, //CJK UNIFIED IDEOGRAPH - 0xC2C6: 0x85D0, //CJK UNIFIED IDEOGRAPH - 0xC2C7: 0x85C9, //CJK UNIFIED IDEOGRAPH - 0xC2C8: 0x85B0, //CJK UNIFIED IDEOGRAPH - 0xC2C9: 0x85BA, //CJK UNIFIED IDEOGRAPH - 0xC2CA: 0x85B9, //CJK UNIFIED IDEOGRAPH - 0xC2CB: 0x85A6, //CJK UNIFIED IDEOGRAPH - 0xC2CC: 0x87EF, //CJK UNIFIED IDEOGRAPH - 0xC2CD: 0x87EC, //CJK UNIFIED IDEOGRAPH - 0xC2CE: 0x87F2, //CJK UNIFIED IDEOGRAPH - 0xC2CF: 0x87E0, //CJK UNIFIED IDEOGRAPH - 0xC2D0: 0x8986, //CJK UNIFIED IDEOGRAPH - 0xC2D1: 0x89B2, //CJK UNIFIED IDEOGRAPH - 0xC2D2: 0x89F4, //CJK UNIFIED IDEOGRAPH - 0xC2D3: 0x8B28, //CJK UNIFIED IDEOGRAPH - 0xC2D4: 0x8B39, //CJK UNIFIED IDEOGRAPH - 0xC2D5: 0x8B2C, //CJK UNIFIED IDEOGRAPH - 0xC2D6: 0x8B2B, //CJK UNIFIED IDEOGRAPH - 0xC2D7: 0x8C50, //CJK UNIFIED IDEOGRAPH - 0xC2D8: 0x8D05, //CJK UNIFIED IDEOGRAPH - 0xC2D9: 0x8E59, //CJK UNIFIED IDEOGRAPH - 0xC2DA: 0x8E63, //CJK UNIFIED IDEOGRAPH - 0xC2DB: 0x8E66, //CJK UNIFIED IDEOGRAPH - 0xC2DC: 0x8E64, //CJK UNIFIED IDEOGRAPH - 0xC2DD: 0x8E5F, //CJK UNIFIED IDEOGRAPH - 0xC2DE: 0x8E55, //CJK UNIFIED IDEOGRAPH - 0xC2DF: 0x8EC0, //CJK UNIFIED IDEOGRAPH - 0xC2E0: 0x8F49, //CJK UNIFIED IDEOGRAPH - 0xC2E1: 0x8F4D, //CJK UNIFIED IDEOGRAPH - 0xC2E2: 0x9087, //CJK UNIFIED IDEOGRAPH - 0xC2E3: 0x9083, //CJK UNIFIED IDEOGRAPH - 0xC2E4: 0x9088, //CJK UNIFIED IDEOGRAPH - 0xC2E5: 0x91AB, //CJK UNIFIED IDEOGRAPH - 0xC2E6: 0x91AC, //CJK UNIFIED IDEOGRAPH - 0xC2E7: 0x91D0, //CJK UNIFIED IDEOGRAPH - 0xC2E8: 0x9394, //CJK UNIFIED IDEOGRAPH - 0xC2E9: 0x938A, //CJK UNIFIED IDEOGRAPH - 0xC2EA: 0x9396, //CJK UNIFIED IDEOGRAPH - 0xC2EB: 0x93A2, //CJK UNIFIED IDEOGRAPH - 0xC2EC: 0x93B3, //CJK UNIFIED IDEOGRAPH - 0xC2ED: 0x93AE, //CJK UNIFIED IDEOGRAPH - 0xC2EE: 0x93AC, //CJK UNIFIED IDEOGRAPH - 0xC2EF: 0x93B0, //CJK UNIFIED IDEOGRAPH - 0xC2F0: 0x9398, //CJK UNIFIED IDEOGRAPH - 0xC2F1: 0x939A, //CJK UNIFIED IDEOGRAPH - 0xC2F2: 0x9397, //CJK UNIFIED IDEOGRAPH - 0xC2F3: 0x95D4, //CJK UNIFIED IDEOGRAPH - 0xC2F4: 0x95D6, //CJK UNIFIED IDEOGRAPH - 0xC2F5: 0x95D0, //CJK UNIFIED IDEOGRAPH - 0xC2F6: 0x95D5, //CJK UNIFIED IDEOGRAPH - 0xC2F7: 0x96E2, //CJK UNIFIED IDEOGRAPH - 0xC2F8: 0x96DC, //CJK UNIFIED IDEOGRAPH - 0xC2F9: 0x96D9, //CJK UNIFIED IDEOGRAPH - 0xC2FA: 0x96DB, //CJK UNIFIED IDEOGRAPH - 0xC2FB: 0x96DE, //CJK UNIFIED IDEOGRAPH - 0xC2FC: 0x9724, //CJK UNIFIED IDEOGRAPH - 0xC2FD: 0x97A3, //CJK UNIFIED IDEOGRAPH - 0xC2FE: 0x97A6, //CJK UNIFIED IDEOGRAPH - 0xC340: 0x97AD, //CJK UNIFIED IDEOGRAPH - 0xC341: 0x97F9, //CJK UNIFIED IDEOGRAPH - 0xC342: 0x984D, //CJK UNIFIED IDEOGRAPH - 0xC343: 0x984F, //CJK UNIFIED IDEOGRAPH - 0xC344: 0x984C, //CJK UNIFIED IDEOGRAPH - 0xC345: 0x984E, //CJK UNIFIED IDEOGRAPH - 0xC346: 0x9853, //CJK UNIFIED IDEOGRAPH - 0xC347: 0x98BA, //CJK UNIFIED IDEOGRAPH - 0xC348: 0x993E, //CJK UNIFIED IDEOGRAPH - 0xC349: 0x993F, //CJK UNIFIED IDEOGRAPH - 0xC34A: 0x993D, //CJK UNIFIED IDEOGRAPH - 0xC34B: 0x992E, //CJK UNIFIED IDEOGRAPH - 0xC34C: 0x99A5, //CJK UNIFIED IDEOGRAPH - 0xC34D: 0x9A0E, //CJK UNIFIED IDEOGRAPH - 0xC34E: 0x9AC1, //CJK UNIFIED IDEOGRAPH - 0xC34F: 0x9B03, //CJK UNIFIED IDEOGRAPH - 0xC350: 0x9B06, //CJK UNIFIED IDEOGRAPH - 0xC351: 0x9B4F, //CJK UNIFIED IDEOGRAPH - 0xC352: 0x9B4E, //CJK UNIFIED IDEOGRAPH - 0xC353: 0x9B4D, //CJK UNIFIED IDEOGRAPH - 0xC354: 0x9BCA, //CJK UNIFIED IDEOGRAPH - 0xC355: 0x9BC9, //CJK UNIFIED IDEOGRAPH - 0xC356: 0x9BFD, //CJK UNIFIED IDEOGRAPH - 0xC357: 0x9BC8, //CJK UNIFIED IDEOGRAPH - 0xC358: 0x9BC0, //CJK UNIFIED IDEOGRAPH - 0xC359: 0x9D51, //CJK UNIFIED IDEOGRAPH - 0xC35A: 0x9D5D, //CJK UNIFIED IDEOGRAPH - 0xC35B: 0x9D60, //CJK UNIFIED IDEOGRAPH - 0xC35C: 0x9EE0, //CJK UNIFIED IDEOGRAPH - 0xC35D: 0x9F15, //CJK UNIFIED IDEOGRAPH - 0xC35E: 0x9F2C, //CJK UNIFIED IDEOGRAPH - 0xC35F: 0x5133, //CJK UNIFIED IDEOGRAPH - 0xC360: 0x56A5, //CJK UNIFIED IDEOGRAPH - 0xC361: 0x58DE, //CJK UNIFIED IDEOGRAPH - 0xC362: 0x58DF, //CJK UNIFIED IDEOGRAPH - 0xC363: 0x58E2, //CJK UNIFIED IDEOGRAPH - 0xC364: 0x5BF5, //CJK UNIFIED IDEOGRAPH - 0xC365: 0x9F90, //CJK UNIFIED IDEOGRAPH - 0xC366: 0x5EEC, //CJK UNIFIED IDEOGRAPH - 0xC367: 0x61F2, //CJK UNIFIED IDEOGRAPH - 0xC368: 0x61F7, //CJK UNIFIED IDEOGRAPH - 0xC369: 0x61F6, //CJK UNIFIED IDEOGRAPH - 0xC36A: 0x61F5, //CJK UNIFIED IDEOGRAPH - 0xC36B: 0x6500, //CJK UNIFIED IDEOGRAPH - 0xC36C: 0x650F, //CJK UNIFIED IDEOGRAPH - 0xC36D: 0x66E0, //CJK UNIFIED IDEOGRAPH - 0xC36E: 0x66DD, //CJK UNIFIED IDEOGRAPH - 0xC36F: 0x6AE5, //CJK UNIFIED IDEOGRAPH - 0xC370: 0x6ADD, //CJK UNIFIED IDEOGRAPH - 0xC371: 0x6ADA, //CJK UNIFIED IDEOGRAPH - 0xC372: 0x6AD3, //CJK UNIFIED IDEOGRAPH - 0xC373: 0x701B, //CJK UNIFIED IDEOGRAPH - 0xC374: 0x701F, //CJK UNIFIED IDEOGRAPH - 0xC375: 0x7028, //CJK UNIFIED IDEOGRAPH - 0xC376: 0x701A, //CJK UNIFIED IDEOGRAPH - 0xC377: 0x701D, //CJK UNIFIED IDEOGRAPH - 0xC378: 0x7015, //CJK UNIFIED IDEOGRAPH - 0xC379: 0x7018, //CJK UNIFIED IDEOGRAPH - 0xC37A: 0x7206, //CJK UNIFIED IDEOGRAPH - 0xC37B: 0x720D, //CJK UNIFIED IDEOGRAPH - 0xC37C: 0x7258, //CJK UNIFIED IDEOGRAPH - 0xC37D: 0x72A2, //CJK UNIFIED IDEOGRAPH - 0xC37E: 0x7378, //CJK UNIFIED IDEOGRAPH - 0xC3A1: 0x737A, //CJK UNIFIED IDEOGRAPH - 0xC3A2: 0x74BD, //CJK UNIFIED IDEOGRAPH - 0xC3A3: 0x74CA, //CJK UNIFIED IDEOGRAPH - 0xC3A4: 0x74E3, //CJK UNIFIED IDEOGRAPH - 0xC3A5: 0x7587, //CJK UNIFIED IDEOGRAPH - 0xC3A6: 0x7586, //CJK UNIFIED IDEOGRAPH - 0xC3A7: 0x765F, //CJK UNIFIED IDEOGRAPH - 0xC3A8: 0x7661, //CJK UNIFIED IDEOGRAPH - 0xC3A9: 0x77C7, //CJK UNIFIED IDEOGRAPH - 0xC3AA: 0x7919, //CJK UNIFIED IDEOGRAPH - 0xC3AB: 0x79B1, //CJK UNIFIED IDEOGRAPH - 0xC3AC: 0x7A6B, //CJK UNIFIED IDEOGRAPH - 0xC3AD: 0x7A69, //CJK UNIFIED IDEOGRAPH - 0xC3AE: 0x7C3E, //CJK UNIFIED IDEOGRAPH - 0xC3AF: 0x7C3F, //CJK UNIFIED IDEOGRAPH - 0xC3B0: 0x7C38, //CJK UNIFIED IDEOGRAPH - 0xC3B1: 0x7C3D, //CJK UNIFIED IDEOGRAPH - 0xC3B2: 0x7C37, //CJK UNIFIED IDEOGRAPH - 0xC3B3: 0x7C40, //CJK UNIFIED IDEOGRAPH - 0xC3B4: 0x7E6B, //CJK UNIFIED IDEOGRAPH - 0xC3B5: 0x7E6D, //CJK UNIFIED IDEOGRAPH - 0xC3B6: 0x7E79, //CJK UNIFIED IDEOGRAPH - 0xC3B7: 0x7E69, //CJK UNIFIED IDEOGRAPH - 0xC3B8: 0x7E6A, //CJK UNIFIED IDEOGRAPH - 0xC3B9: 0x7F85, //CJK UNIFIED IDEOGRAPH - 0xC3BA: 0x7E73, //CJK UNIFIED IDEOGRAPH - 0xC3BB: 0x7FB6, //CJK UNIFIED IDEOGRAPH - 0xC3BC: 0x7FB9, //CJK UNIFIED IDEOGRAPH - 0xC3BD: 0x7FB8, //CJK UNIFIED IDEOGRAPH - 0xC3BE: 0x81D8, //CJK UNIFIED IDEOGRAPH - 0xC3BF: 0x85E9, //CJK UNIFIED IDEOGRAPH - 0xC3C0: 0x85DD, //CJK UNIFIED IDEOGRAPH - 0xC3C1: 0x85EA, //CJK UNIFIED IDEOGRAPH - 0xC3C2: 0x85D5, //CJK UNIFIED IDEOGRAPH - 0xC3C3: 0x85E4, //CJK UNIFIED IDEOGRAPH - 0xC3C4: 0x85E5, //CJK UNIFIED IDEOGRAPH - 0xC3C5: 0x85F7, //CJK UNIFIED IDEOGRAPH - 0xC3C6: 0x87FB, //CJK UNIFIED IDEOGRAPH - 0xC3C7: 0x8805, //CJK UNIFIED IDEOGRAPH - 0xC3C8: 0x880D, //CJK UNIFIED IDEOGRAPH - 0xC3C9: 0x87F9, //CJK UNIFIED IDEOGRAPH - 0xC3CA: 0x87FE, //CJK UNIFIED IDEOGRAPH - 0xC3CB: 0x8960, //CJK UNIFIED IDEOGRAPH - 0xC3CC: 0x895F, //CJK UNIFIED IDEOGRAPH - 0xC3CD: 0x8956, //CJK UNIFIED IDEOGRAPH - 0xC3CE: 0x895E, //CJK UNIFIED IDEOGRAPH - 0xC3CF: 0x8B41, //CJK UNIFIED IDEOGRAPH - 0xC3D0: 0x8B5C, //CJK UNIFIED IDEOGRAPH - 0xC3D1: 0x8B58, //CJK UNIFIED IDEOGRAPH - 0xC3D2: 0x8B49, //CJK UNIFIED IDEOGRAPH - 0xC3D3: 0x8B5A, //CJK UNIFIED IDEOGRAPH - 0xC3D4: 0x8B4E, //CJK UNIFIED IDEOGRAPH - 0xC3D5: 0x8B4F, //CJK UNIFIED IDEOGRAPH - 0xC3D6: 0x8B46, //CJK UNIFIED IDEOGRAPH - 0xC3D7: 0x8B59, //CJK UNIFIED IDEOGRAPH - 0xC3D8: 0x8D08, //CJK UNIFIED IDEOGRAPH - 0xC3D9: 0x8D0A, //CJK UNIFIED IDEOGRAPH - 0xC3DA: 0x8E7C, //CJK UNIFIED IDEOGRAPH - 0xC3DB: 0x8E72, //CJK UNIFIED IDEOGRAPH - 0xC3DC: 0x8E87, //CJK UNIFIED IDEOGRAPH - 0xC3DD: 0x8E76, //CJK UNIFIED IDEOGRAPH - 0xC3DE: 0x8E6C, //CJK UNIFIED IDEOGRAPH - 0xC3DF: 0x8E7A, //CJK UNIFIED IDEOGRAPH - 0xC3E0: 0x8E74, //CJK UNIFIED IDEOGRAPH - 0xC3E1: 0x8F54, //CJK UNIFIED IDEOGRAPH - 0xC3E2: 0x8F4E, //CJK UNIFIED IDEOGRAPH - 0xC3E3: 0x8FAD, //CJK UNIFIED IDEOGRAPH - 0xC3E4: 0x908A, //CJK UNIFIED IDEOGRAPH - 0xC3E5: 0x908B, //CJK UNIFIED IDEOGRAPH - 0xC3E6: 0x91B1, //CJK UNIFIED IDEOGRAPH - 0xC3E7: 0x91AE, //CJK UNIFIED IDEOGRAPH - 0xC3E8: 0x93E1, //CJK UNIFIED IDEOGRAPH - 0xC3E9: 0x93D1, //CJK UNIFIED IDEOGRAPH - 0xC3EA: 0x93DF, //CJK UNIFIED IDEOGRAPH - 0xC3EB: 0x93C3, //CJK UNIFIED IDEOGRAPH - 0xC3EC: 0x93C8, //CJK UNIFIED IDEOGRAPH - 0xC3ED: 0x93DC, //CJK UNIFIED IDEOGRAPH - 0xC3EE: 0x93DD, //CJK UNIFIED IDEOGRAPH - 0xC3EF: 0x93D6, //CJK UNIFIED IDEOGRAPH - 0xC3F0: 0x93E2, //CJK UNIFIED IDEOGRAPH - 0xC3F1: 0x93CD, //CJK UNIFIED IDEOGRAPH - 0xC3F2: 0x93D8, //CJK UNIFIED IDEOGRAPH - 0xC3F3: 0x93E4, //CJK UNIFIED IDEOGRAPH - 0xC3F4: 0x93D7, //CJK UNIFIED IDEOGRAPH - 0xC3F5: 0x93E8, //CJK UNIFIED IDEOGRAPH - 0xC3F6: 0x95DC, //CJK UNIFIED IDEOGRAPH - 0xC3F7: 0x96B4, //CJK UNIFIED IDEOGRAPH - 0xC3F8: 0x96E3, //CJK UNIFIED IDEOGRAPH - 0xC3F9: 0x972A, //CJK UNIFIED IDEOGRAPH - 0xC3FA: 0x9727, //CJK UNIFIED IDEOGRAPH - 0xC3FB: 0x9761, //CJK UNIFIED IDEOGRAPH - 0xC3FC: 0x97DC, //CJK UNIFIED IDEOGRAPH - 0xC3FD: 0x97FB, //CJK UNIFIED IDEOGRAPH - 0xC3FE: 0x985E, //CJK UNIFIED IDEOGRAPH - 0xC440: 0x9858, //CJK UNIFIED IDEOGRAPH - 0xC441: 0x985B, //CJK UNIFIED IDEOGRAPH - 0xC442: 0x98BC, //CJK UNIFIED IDEOGRAPH - 0xC443: 0x9945, //CJK UNIFIED IDEOGRAPH - 0xC444: 0x9949, //CJK UNIFIED IDEOGRAPH - 0xC445: 0x9A16, //CJK UNIFIED IDEOGRAPH - 0xC446: 0x9A19, //CJK UNIFIED IDEOGRAPH - 0xC447: 0x9B0D, //CJK UNIFIED IDEOGRAPH - 0xC448: 0x9BE8, //CJK UNIFIED IDEOGRAPH - 0xC449: 0x9BE7, //CJK UNIFIED IDEOGRAPH - 0xC44A: 0x9BD6, //CJK UNIFIED IDEOGRAPH - 0xC44B: 0x9BDB, //CJK UNIFIED IDEOGRAPH - 0xC44C: 0x9D89, //CJK UNIFIED IDEOGRAPH - 0xC44D: 0x9D61, //CJK UNIFIED IDEOGRAPH - 0xC44E: 0x9D72, //CJK UNIFIED IDEOGRAPH - 0xC44F: 0x9D6A, //CJK UNIFIED IDEOGRAPH - 0xC450: 0x9D6C, //CJK UNIFIED IDEOGRAPH - 0xC451: 0x9E92, //CJK UNIFIED IDEOGRAPH - 0xC452: 0x9E97, //CJK UNIFIED IDEOGRAPH - 0xC453: 0x9E93, //CJK UNIFIED IDEOGRAPH - 0xC454: 0x9EB4, //CJK UNIFIED IDEOGRAPH - 0xC455: 0x52F8, //CJK UNIFIED IDEOGRAPH - 0xC456: 0x56A8, //CJK UNIFIED IDEOGRAPH - 0xC457: 0x56B7, //CJK UNIFIED IDEOGRAPH - 0xC458: 0x56B6, //CJK UNIFIED IDEOGRAPH - 0xC459: 0x56B4, //CJK UNIFIED IDEOGRAPH - 0xC45A: 0x56BC, //CJK UNIFIED IDEOGRAPH - 0xC45B: 0x58E4, //CJK UNIFIED IDEOGRAPH - 0xC45C: 0x5B40, //CJK UNIFIED IDEOGRAPH - 0xC45D: 0x5B43, //CJK UNIFIED IDEOGRAPH - 0xC45E: 0x5B7D, //CJK UNIFIED IDEOGRAPH - 0xC45F: 0x5BF6, //CJK UNIFIED IDEOGRAPH - 0xC460: 0x5DC9, //CJK UNIFIED IDEOGRAPH - 0xC461: 0x61F8, //CJK UNIFIED IDEOGRAPH - 0xC462: 0x61FA, //CJK UNIFIED IDEOGRAPH - 0xC463: 0x6518, //CJK UNIFIED IDEOGRAPH - 0xC464: 0x6514, //CJK UNIFIED IDEOGRAPH - 0xC465: 0x6519, //CJK UNIFIED IDEOGRAPH - 0xC466: 0x66E6, //CJK UNIFIED IDEOGRAPH - 0xC467: 0x6727, //CJK UNIFIED IDEOGRAPH - 0xC468: 0x6AEC, //CJK UNIFIED IDEOGRAPH - 0xC469: 0x703E, //CJK UNIFIED IDEOGRAPH - 0xC46A: 0x7030, //CJK UNIFIED IDEOGRAPH - 0xC46B: 0x7032, //CJK UNIFIED IDEOGRAPH - 0xC46C: 0x7210, //CJK UNIFIED IDEOGRAPH - 0xC46D: 0x737B, //CJK UNIFIED IDEOGRAPH - 0xC46E: 0x74CF, //CJK UNIFIED IDEOGRAPH - 0xC46F: 0x7662, //CJK UNIFIED IDEOGRAPH - 0xC470: 0x7665, //CJK UNIFIED IDEOGRAPH - 0xC471: 0x7926, //CJK UNIFIED IDEOGRAPH - 0xC472: 0x792A, //CJK UNIFIED IDEOGRAPH - 0xC473: 0x792C, //CJK UNIFIED IDEOGRAPH - 0xC474: 0x792B, //CJK UNIFIED IDEOGRAPH - 0xC475: 0x7AC7, //CJK UNIFIED IDEOGRAPH - 0xC476: 0x7AF6, //CJK UNIFIED IDEOGRAPH - 0xC477: 0x7C4C, //CJK UNIFIED IDEOGRAPH - 0xC478: 0x7C43, //CJK UNIFIED IDEOGRAPH - 0xC479: 0x7C4D, //CJK UNIFIED IDEOGRAPH - 0xC47A: 0x7CEF, //CJK UNIFIED IDEOGRAPH - 0xC47B: 0x7CF0, //CJK UNIFIED IDEOGRAPH - 0xC47C: 0x8FAE, //CJK UNIFIED IDEOGRAPH - 0xC47D: 0x7E7D, //CJK UNIFIED IDEOGRAPH - 0xC47E: 0x7E7C, //CJK UNIFIED IDEOGRAPH - 0xC4A1: 0x7E82, //CJK UNIFIED IDEOGRAPH - 0xC4A2: 0x7F4C, //CJK UNIFIED IDEOGRAPH - 0xC4A3: 0x8000, //CJK UNIFIED IDEOGRAPH - 0xC4A4: 0x81DA, //CJK UNIFIED IDEOGRAPH - 0xC4A5: 0x8266, //CJK UNIFIED IDEOGRAPH - 0xC4A6: 0x85FB, //CJK UNIFIED IDEOGRAPH - 0xC4A7: 0x85F9, //CJK UNIFIED IDEOGRAPH - 0xC4A8: 0x8611, //CJK UNIFIED IDEOGRAPH - 0xC4A9: 0x85FA, //CJK UNIFIED IDEOGRAPH - 0xC4AA: 0x8606, //CJK UNIFIED IDEOGRAPH - 0xC4AB: 0x860B, //CJK UNIFIED IDEOGRAPH - 0xC4AC: 0x8607, //CJK UNIFIED IDEOGRAPH - 0xC4AD: 0x860A, //CJK UNIFIED IDEOGRAPH - 0xC4AE: 0x8814, //CJK UNIFIED IDEOGRAPH - 0xC4AF: 0x8815, //CJK UNIFIED IDEOGRAPH - 0xC4B0: 0x8964, //CJK UNIFIED IDEOGRAPH - 0xC4B1: 0x89BA, //CJK UNIFIED IDEOGRAPH - 0xC4B2: 0x89F8, //CJK UNIFIED IDEOGRAPH - 0xC4B3: 0x8B70, //CJK UNIFIED IDEOGRAPH - 0xC4B4: 0x8B6C, //CJK UNIFIED IDEOGRAPH - 0xC4B5: 0x8B66, //CJK UNIFIED IDEOGRAPH - 0xC4B6: 0x8B6F, //CJK UNIFIED IDEOGRAPH - 0xC4B7: 0x8B5F, //CJK UNIFIED IDEOGRAPH - 0xC4B8: 0x8B6B, //CJK UNIFIED IDEOGRAPH - 0xC4B9: 0x8D0F, //CJK UNIFIED IDEOGRAPH - 0xC4BA: 0x8D0D, //CJK UNIFIED IDEOGRAPH - 0xC4BB: 0x8E89, //CJK UNIFIED IDEOGRAPH - 0xC4BC: 0x8E81, //CJK UNIFIED IDEOGRAPH - 0xC4BD: 0x8E85, //CJK UNIFIED IDEOGRAPH - 0xC4BE: 0x8E82, //CJK UNIFIED IDEOGRAPH - 0xC4BF: 0x91B4, //CJK UNIFIED IDEOGRAPH - 0xC4C0: 0x91CB, //CJK UNIFIED IDEOGRAPH - 0xC4C1: 0x9418, //CJK UNIFIED IDEOGRAPH - 0xC4C2: 0x9403, //CJK UNIFIED IDEOGRAPH - 0xC4C3: 0x93FD, //CJK UNIFIED IDEOGRAPH - 0xC4C4: 0x95E1, //CJK UNIFIED IDEOGRAPH - 0xC4C5: 0x9730, //CJK UNIFIED IDEOGRAPH - 0xC4C6: 0x98C4, //CJK UNIFIED IDEOGRAPH - 0xC4C7: 0x9952, //CJK UNIFIED IDEOGRAPH - 0xC4C8: 0x9951, //CJK UNIFIED IDEOGRAPH - 0xC4C9: 0x99A8, //CJK UNIFIED IDEOGRAPH - 0xC4CA: 0x9A2B, //CJK UNIFIED IDEOGRAPH - 0xC4CB: 0x9A30, //CJK UNIFIED IDEOGRAPH - 0xC4CC: 0x9A37, //CJK UNIFIED IDEOGRAPH - 0xC4CD: 0x9A35, //CJK UNIFIED IDEOGRAPH - 0xC4CE: 0x9C13, //CJK UNIFIED IDEOGRAPH - 0xC4CF: 0x9C0D, //CJK UNIFIED IDEOGRAPH - 0xC4D0: 0x9E79, //CJK UNIFIED IDEOGRAPH - 0xC4D1: 0x9EB5, //CJK UNIFIED IDEOGRAPH - 0xC4D2: 0x9EE8, //CJK UNIFIED IDEOGRAPH - 0xC4D3: 0x9F2F, //CJK UNIFIED IDEOGRAPH - 0xC4D4: 0x9F5F, //CJK UNIFIED IDEOGRAPH - 0xC4D5: 0x9F63, //CJK UNIFIED IDEOGRAPH - 0xC4D6: 0x9F61, //CJK UNIFIED IDEOGRAPH - 0xC4D7: 0x5137, //CJK UNIFIED IDEOGRAPH - 0xC4D8: 0x5138, //CJK UNIFIED IDEOGRAPH - 0xC4D9: 0x56C1, //CJK UNIFIED IDEOGRAPH - 0xC4DA: 0x56C0, //CJK UNIFIED IDEOGRAPH - 0xC4DB: 0x56C2, //CJK UNIFIED IDEOGRAPH - 0xC4DC: 0x5914, //CJK UNIFIED IDEOGRAPH - 0xC4DD: 0x5C6C, //CJK UNIFIED IDEOGRAPH - 0xC4DE: 0x5DCD, //CJK UNIFIED IDEOGRAPH - 0xC4DF: 0x61FC, //CJK UNIFIED IDEOGRAPH - 0xC4E0: 0x61FE, //CJK UNIFIED IDEOGRAPH - 0xC4E1: 0x651D, //CJK UNIFIED IDEOGRAPH - 0xC4E2: 0x651C, //CJK UNIFIED IDEOGRAPH - 0xC4E3: 0x6595, //CJK UNIFIED IDEOGRAPH - 0xC4E4: 0x66E9, //CJK UNIFIED IDEOGRAPH - 0xC4E5: 0x6AFB, //CJK UNIFIED IDEOGRAPH - 0xC4E6: 0x6B04, //CJK UNIFIED IDEOGRAPH - 0xC4E7: 0x6AFA, //CJK UNIFIED IDEOGRAPH - 0xC4E8: 0x6BB2, //CJK UNIFIED IDEOGRAPH - 0xC4E9: 0x704C, //CJK UNIFIED IDEOGRAPH - 0xC4EA: 0x721B, //CJK UNIFIED IDEOGRAPH - 0xC4EB: 0x72A7, //CJK UNIFIED IDEOGRAPH - 0xC4EC: 0x74D6, //CJK UNIFIED IDEOGRAPH - 0xC4ED: 0x74D4, //CJK UNIFIED IDEOGRAPH - 0xC4EE: 0x7669, //CJK UNIFIED IDEOGRAPH - 0xC4EF: 0x77D3, //CJK UNIFIED IDEOGRAPH - 0xC4F0: 0x7C50, //CJK UNIFIED IDEOGRAPH - 0xC4F1: 0x7E8F, //CJK UNIFIED IDEOGRAPH - 0xC4F2: 0x7E8C, //CJK UNIFIED IDEOGRAPH - 0xC4F3: 0x7FBC, //CJK UNIFIED IDEOGRAPH - 0xC4F4: 0x8617, //CJK UNIFIED IDEOGRAPH - 0xC4F5: 0x862D, //CJK UNIFIED IDEOGRAPH - 0xC4F6: 0x861A, //CJK UNIFIED IDEOGRAPH - 0xC4F7: 0x8823, //CJK UNIFIED IDEOGRAPH - 0xC4F8: 0x8822, //CJK UNIFIED IDEOGRAPH - 0xC4F9: 0x8821, //CJK UNIFIED IDEOGRAPH - 0xC4FA: 0x881F, //CJK UNIFIED IDEOGRAPH - 0xC4FB: 0x896A, //CJK UNIFIED IDEOGRAPH - 0xC4FC: 0x896C, //CJK UNIFIED IDEOGRAPH - 0xC4FD: 0x89BD, //CJK UNIFIED IDEOGRAPH - 0xC4FE: 0x8B74, //CJK UNIFIED IDEOGRAPH - 0xC540: 0x8B77, //CJK UNIFIED IDEOGRAPH - 0xC541: 0x8B7D, //CJK UNIFIED IDEOGRAPH - 0xC542: 0x8D13, //CJK UNIFIED IDEOGRAPH - 0xC543: 0x8E8A, //CJK UNIFIED IDEOGRAPH - 0xC544: 0x8E8D, //CJK UNIFIED IDEOGRAPH - 0xC545: 0x8E8B, //CJK UNIFIED IDEOGRAPH - 0xC546: 0x8F5F, //CJK UNIFIED IDEOGRAPH - 0xC547: 0x8FAF, //CJK UNIFIED IDEOGRAPH - 0xC548: 0x91BA, //CJK UNIFIED IDEOGRAPH - 0xC549: 0x942E, //CJK UNIFIED IDEOGRAPH - 0xC54A: 0x9433, //CJK UNIFIED IDEOGRAPH - 0xC54B: 0x9435, //CJK UNIFIED IDEOGRAPH - 0xC54C: 0x943A, //CJK UNIFIED IDEOGRAPH - 0xC54D: 0x9438, //CJK UNIFIED IDEOGRAPH - 0xC54E: 0x9432, //CJK UNIFIED IDEOGRAPH - 0xC54F: 0x942B, //CJK UNIFIED IDEOGRAPH - 0xC550: 0x95E2, //CJK UNIFIED IDEOGRAPH - 0xC551: 0x9738, //CJK UNIFIED IDEOGRAPH - 0xC552: 0x9739, //CJK UNIFIED IDEOGRAPH - 0xC553: 0x9732, //CJK UNIFIED IDEOGRAPH - 0xC554: 0x97FF, //CJK UNIFIED IDEOGRAPH - 0xC555: 0x9867, //CJK UNIFIED IDEOGRAPH - 0xC556: 0x9865, //CJK UNIFIED IDEOGRAPH - 0xC557: 0x9957, //CJK UNIFIED IDEOGRAPH - 0xC558: 0x9A45, //CJK UNIFIED IDEOGRAPH - 0xC559: 0x9A43, //CJK UNIFIED IDEOGRAPH - 0xC55A: 0x9A40, //CJK UNIFIED IDEOGRAPH - 0xC55B: 0x9A3E, //CJK UNIFIED IDEOGRAPH - 0xC55C: 0x9ACF, //CJK UNIFIED IDEOGRAPH - 0xC55D: 0x9B54, //CJK UNIFIED IDEOGRAPH - 0xC55E: 0x9B51, //CJK UNIFIED IDEOGRAPH - 0xC55F: 0x9C2D, //CJK UNIFIED IDEOGRAPH - 0xC560: 0x9C25, //CJK UNIFIED IDEOGRAPH - 0xC561: 0x9DAF, //CJK UNIFIED IDEOGRAPH - 0xC562: 0x9DB4, //CJK UNIFIED IDEOGRAPH - 0xC563: 0x9DC2, //CJK UNIFIED IDEOGRAPH - 0xC564: 0x9DB8, //CJK UNIFIED IDEOGRAPH - 0xC565: 0x9E9D, //CJK UNIFIED IDEOGRAPH - 0xC566: 0x9EEF, //CJK UNIFIED IDEOGRAPH - 0xC567: 0x9F19, //CJK UNIFIED IDEOGRAPH - 0xC568: 0x9F5C, //CJK UNIFIED IDEOGRAPH - 0xC569: 0x9F66, //CJK UNIFIED IDEOGRAPH - 0xC56A: 0x9F67, //CJK UNIFIED IDEOGRAPH - 0xC56B: 0x513C, //CJK UNIFIED IDEOGRAPH - 0xC56C: 0x513B, //CJK UNIFIED IDEOGRAPH - 0xC56D: 0x56C8, //CJK UNIFIED IDEOGRAPH - 0xC56E: 0x56CA, //CJK UNIFIED IDEOGRAPH - 0xC56F: 0x56C9, //CJK UNIFIED IDEOGRAPH - 0xC570: 0x5B7F, //CJK UNIFIED IDEOGRAPH - 0xC571: 0x5DD4, //CJK UNIFIED IDEOGRAPH - 0xC572: 0x5DD2, //CJK UNIFIED IDEOGRAPH - 0xC573: 0x5F4E, //CJK UNIFIED IDEOGRAPH - 0xC574: 0x61FF, //CJK UNIFIED IDEOGRAPH - 0xC575: 0x6524, //CJK UNIFIED IDEOGRAPH - 0xC576: 0x6B0A, //CJK UNIFIED IDEOGRAPH - 0xC577: 0x6B61, //CJK UNIFIED IDEOGRAPH - 0xC578: 0x7051, //CJK UNIFIED IDEOGRAPH - 0xC579: 0x7058, //CJK UNIFIED IDEOGRAPH - 0xC57A: 0x7380, //CJK UNIFIED IDEOGRAPH - 0xC57B: 0x74E4, //CJK UNIFIED IDEOGRAPH - 0xC57C: 0x758A, //CJK UNIFIED IDEOGRAPH - 0xC57D: 0x766E, //CJK UNIFIED IDEOGRAPH - 0xC57E: 0x766C, //CJK UNIFIED IDEOGRAPH - 0xC5A1: 0x79B3, //CJK UNIFIED IDEOGRAPH - 0xC5A2: 0x7C60, //CJK UNIFIED IDEOGRAPH - 0xC5A3: 0x7C5F, //CJK UNIFIED IDEOGRAPH - 0xC5A4: 0x807E, //CJK UNIFIED IDEOGRAPH - 0xC5A5: 0x807D, //CJK UNIFIED IDEOGRAPH - 0xC5A6: 0x81DF, //CJK UNIFIED IDEOGRAPH - 0xC5A7: 0x8972, //CJK UNIFIED IDEOGRAPH - 0xC5A8: 0x896F, //CJK UNIFIED IDEOGRAPH - 0xC5A9: 0x89FC, //CJK UNIFIED IDEOGRAPH - 0xC5AA: 0x8B80, //CJK UNIFIED IDEOGRAPH - 0xC5AB: 0x8D16, //CJK UNIFIED IDEOGRAPH - 0xC5AC: 0x8D17, //CJK UNIFIED IDEOGRAPH - 0xC5AD: 0x8E91, //CJK UNIFIED IDEOGRAPH - 0xC5AE: 0x8E93, //CJK UNIFIED IDEOGRAPH - 0xC5AF: 0x8F61, //CJK UNIFIED IDEOGRAPH - 0xC5B0: 0x9148, //CJK UNIFIED IDEOGRAPH - 0xC5B1: 0x9444, //CJK UNIFIED IDEOGRAPH - 0xC5B2: 0x9451, //CJK UNIFIED IDEOGRAPH - 0xC5B3: 0x9452, //CJK UNIFIED IDEOGRAPH - 0xC5B4: 0x973D, //CJK UNIFIED IDEOGRAPH - 0xC5B5: 0x973E, //CJK UNIFIED IDEOGRAPH - 0xC5B6: 0x97C3, //CJK UNIFIED IDEOGRAPH - 0xC5B7: 0x97C1, //CJK UNIFIED IDEOGRAPH - 0xC5B8: 0x986B, //CJK UNIFIED IDEOGRAPH - 0xC5B9: 0x9955, //CJK UNIFIED IDEOGRAPH - 0xC5BA: 0x9A55, //CJK UNIFIED IDEOGRAPH - 0xC5BB: 0x9A4D, //CJK UNIFIED IDEOGRAPH - 0xC5BC: 0x9AD2, //CJK UNIFIED IDEOGRAPH - 0xC5BD: 0x9B1A, //CJK UNIFIED IDEOGRAPH - 0xC5BE: 0x9C49, //CJK UNIFIED IDEOGRAPH - 0xC5BF: 0x9C31, //CJK UNIFIED IDEOGRAPH - 0xC5C0: 0x9C3E, //CJK UNIFIED IDEOGRAPH - 0xC5C1: 0x9C3B, //CJK UNIFIED IDEOGRAPH - 0xC5C2: 0x9DD3, //CJK UNIFIED IDEOGRAPH - 0xC5C3: 0x9DD7, //CJK UNIFIED IDEOGRAPH - 0xC5C4: 0x9F34, //CJK UNIFIED IDEOGRAPH - 0xC5C5: 0x9F6C, //CJK UNIFIED IDEOGRAPH - 0xC5C6: 0x9F6A, //CJK UNIFIED IDEOGRAPH - 0xC5C7: 0x9F94, //CJK UNIFIED IDEOGRAPH - 0xC5C8: 0x56CC, //CJK UNIFIED IDEOGRAPH - 0xC5C9: 0x5DD6, //CJK UNIFIED IDEOGRAPH - 0xC5CA: 0x6200, //CJK UNIFIED IDEOGRAPH - 0xC5CB: 0x6523, //CJK UNIFIED IDEOGRAPH - 0xC5CC: 0x652B, //CJK UNIFIED IDEOGRAPH - 0xC5CD: 0x652A, //CJK UNIFIED IDEOGRAPH - 0xC5CE: 0x66EC, //CJK UNIFIED IDEOGRAPH - 0xC5CF: 0x6B10, //CJK UNIFIED IDEOGRAPH - 0xC5D0: 0x74DA, //CJK UNIFIED IDEOGRAPH - 0xC5D1: 0x7ACA, //CJK UNIFIED IDEOGRAPH - 0xC5D2: 0x7C64, //CJK UNIFIED IDEOGRAPH - 0xC5D3: 0x7C63, //CJK UNIFIED IDEOGRAPH - 0xC5D4: 0x7C65, //CJK UNIFIED IDEOGRAPH - 0xC5D5: 0x7E93, //CJK UNIFIED IDEOGRAPH - 0xC5D6: 0x7E96, //CJK UNIFIED IDEOGRAPH - 0xC5D7: 0x7E94, //CJK UNIFIED IDEOGRAPH - 0xC5D8: 0x81E2, //CJK UNIFIED IDEOGRAPH - 0xC5D9: 0x8638, //CJK UNIFIED IDEOGRAPH - 0xC5DA: 0x863F, //CJK UNIFIED IDEOGRAPH - 0xC5DB: 0x8831, //CJK UNIFIED IDEOGRAPH - 0xC5DC: 0x8B8A, //CJK UNIFIED IDEOGRAPH - 0xC5DD: 0x9090, //CJK UNIFIED IDEOGRAPH - 0xC5DE: 0x908F, //CJK UNIFIED IDEOGRAPH - 0xC5DF: 0x9463, //CJK UNIFIED IDEOGRAPH - 0xC5E0: 0x9460, //CJK UNIFIED IDEOGRAPH - 0xC5E1: 0x9464, //CJK UNIFIED IDEOGRAPH - 0xC5E2: 0x9768, //CJK UNIFIED IDEOGRAPH - 0xC5E3: 0x986F, //CJK UNIFIED IDEOGRAPH - 0xC5E4: 0x995C, //CJK UNIFIED IDEOGRAPH - 0xC5E5: 0x9A5A, //CJK UNIFIED IDEOGRAPH - 0xC5E6: 0x9A5B, //CJK UNIFIED IDEOGRAPH - 0xC5E7: 0x9A57, //CJK UNIFIED IDEOGRAPH - 0xC5E8: 0x9AD3, //CJK UNIFIED IDEOGRAPH - 0xC5E9: 0x9AD4, //CJK UNIFIED IDEOGRAPH - 0xC5EA: 0x9AD1, //CJK UNIFIED IDEOGRAPH - 0xC5EB: 0x9C54, //CJK UNIFIED IDEOGRAPH - 0xC5EC: 0x9C57, //CJK UNIFIED IDEOGRAPH - 0xC5ED: 0x9C56, //CJK UNIFIED IDEOGRAPH - 0xC5EE: 0x9DE5, //CJK UNIFIED IDEOGRAPH - 0xC5EF: 0x9E9F, //CJK UNIFIED IDEOGRAPH - 0xC5F0: 0x9EF4, //CJK UNIFIED IDEOGRAPH - 0xC5F1: 0x56D1, //CJK UNIFIED IDEOGRAPH - 0xC5F2: 0x58E9, //CJK UNIFIED IDEOGRAPH - 0xC5F3: 0x652C, //CJK UNIFIED IDEOGRAPH - 0xC5F4: 0x705E, //CJK UNIFIED IDEOGRAPH - 0xC5F5: 0x7671, //CJK UNIFIED IDEOGRAPH - 0xC5F6: 0x7672, //CJK UNIFIED IDEOGRAPH - 0xC5F7: 0x77D7, //CJK UNIFIED IDEOGRAPH - 0xC5F8: 0x7F50, //CJK UNIFIED IDEOGRAPH - 0xC5F9: 0x7F88, //CJK UNIFIED IDEOGRAPH - 0xC5FA: 0x8836, //CJK UNIFIED IDEOGRAPH - 0xC5FB: 0x8839, //CJK UNIFIED IDEOGRAPH - 0xC5FC: 0x8862, //CJK UNIFIED IDEOGRAPH - 0xC5FD: 0x8B93, //CJK UNIFIED IDEOGRAPH - 0xC5FE: 0x8B92, //CJK UNIFIED IDEOGRAPH - 0xC640: 0x8B96, //CJK UNIFIED IDEOGRAPH - 0xC641: 0x8277, //CJK UNIFIED IDEOGRAPH - 0xC642: 0x8D1B, //CJK UNIFIED IDEOGRAPH - 0xC643: 0x91C0, //CJK UNIFIED IDEOGRAPH - 0xC644: 0x946A, //CJK UNIFIED IDEOGRAPH - 0xC645: 0x9742, //CJK UNIFIED IDEOGRAPH - 0xC646: 0x9748, //CJK UNIFIED IDEOGRAPH - 0xC647: 0x9744, //CJK UNIFIED IDEOGRAPH - 0xC648: 0x97C6, //CJK UNIFIED IDEOGRAPH - 0xC649: 0x9870, //CJK UNIFIED IDEOGRAPH - 0xC64A: 0x9A5F, //CJK UNIFIED IDEOGRAPH - 0xC64B: 0x9B22, //CJK UNIFIED IDEOGRAPH - 0xC64C: 0x9B58, //CJK UNIFIED IDEOGRAPH - 0xC64D: 0x9C5F, //CJK UNIFIED IDEOGRAPH - 0xC64E: 0x9DF9, //CJK UNIFIED IDEOGRAPH - 0xC64F: 0x9DFA, //CJK UNIFIED IDEOGRAPH - 0xC650: 0x9E7C, //CJK UNIFIED IDEOGRAPH - 0xC651: 0x9E7D, //CJK UNIFIED IDEOGRAPH - 0xC652: 0x9F07, //CJK UNIFIED IDEOGRAPH - 0xC653: 0x9F77, //CJK UNIFIED IDEOGRAPH - 0xC654: 0x9F72, //CJK UNIFIED IDEOGRAPH - 0xC655: 0x5EF3, //CJK UNIFIED IDEOGRAPH - 0xC656: 0x6B16, //CJK UNIFIED IDEOGRAPH - 0xC657: 0x7063, //CJK UNIFIED IDEOGRAPH - 0xC658: 0x7C6C, //CJK UNIFIED IDEOGRAPH - 0xC659: 0x7C6E, //CJK UNIFIED IDEOGRAPH - 0xC65A: 0x883B, //CJK UNIFIED IDEOGRAPH - 0xC65B: 0x89C0, //CJK UNIFIED IDEOGRAPH - 0xC65C: 0x8EA1, //CJK UNIFIED IDEOGRAPH - 0xC65D: 0x91C1, //CJK UNIFIED IDEOGRAPH - 0xC65E: 0x9472, //CJK UNIFIED IDEOGRAPH - 0xC65F: 0x9470, //CJK UNIFIED IDEOGRAPH - 0xC660: 0x9871, //CJK UNIFIED IDEOGRAPH - 0xC661: 0x995E, //CJK UNIFIED IDEOGRAPH - 0xC662: 0x9AD6, //CJK UNIFIED IDEOGRAPH - 0xC663: 0x9B23, //CJK UNIFIED IDEOGRAPH - 0xC664: 0x9ECC, //CJK UNIFIED IDEOGRAPH - 0xC665: 0x7064, //CJK UNIFIED IDEOGRAPH - 0xC666: 0x77DA, //CJK UNIFIED IDEOGRAPH - 0xC667: 0x8B9A, //CJK UNIFIED IDEOGRAPH - 0xC668: 0x9477, //CJK UNIFIED IDEOGRAPH - 0xC669: 0x97C9, //CJK UNIFIED IDEOGRAPH - 0xC66A: 0x9A62, //CJK UNIFIED IDEOGRAPH - 0xC66B: 0x9A65, //CJK UNIFIED IDEOGRAPH - 0xC66C: 0x7E9C, //CJK UNIFIED IDEOGRAPH - 0xC66D: 0x8B9C, //CJK UNIFIED IDEOGRAPH - 0xC66E: 0x8EAA, //CJK UNIFIED IDEOGRAPH - 0xC66F: 0x91C5, //CJK UNIFIED IDEOGRAPH - 0xC670: 0x947D, //CJK UNIFIED IDEOGRAPH - 0xC671: 0x947E, //CJK UNIFIED IDEOGRAPH - 0xC672: 0x947C, //CJK UNIFIED IDEOGRAPH - 0xC673: 0x9C77, //CJK UNIFIED IDEOGRAPH - 0xC674: 0x9C78, //CJK UNIFIED IDEOGRAPH - 0xC675: 0x9EF7, //CJK UNIFIED IDEOGRAPH - 0xC676: 0x8C54, //CJK UNIFIED IDEOGRAPH - 0xC677: 0x947F, //CJK UNIFIED IDEOGRAPH - 0xC678: 0x9E1A, //CJK UNIFIED IDEOGRAPH - 0xC679: 0x7228, //CJK UNIFIED IDEOGRAPH - 0xC67A: 0x9A6A, //CJK UNIFIED IDEOGRAPH - 0xC67B: 0x9B31, //CJK UNIFIED IDEOGRAPH - 0xC67C: 0x9E1B, //CJK UNIFIED IDEOGRAPH - 0xC67D: 0x9E1E, //CJK UNIFIED IDEOGRAPH - 0xC67E: 0x7C72, //CJK UNIFIED IDEOGRAPH - 0xC940: 0x4E42, //CJK UNIFIED IDEOGRAPH - 0xC941: 0x4E5C, //CJK UNIFIED IDEOGRAPH - 0xC942: 0x51F5, //CJK UNIFIED IDEOGRAPH - 0xC943: 0x531A, //CJK UNIFIED IDEOGRAPH - 0xC944: 0x5382, //CJK UNIFIED IDEOGRAPH - 0xC945: 0x4E07, //CJK UNIFIED IDEOGRAPH - 0xC946: 0x4E0C, //CJK UNIFIED IDEOGRAPH - 0xC947: 0x4E47, //CJK UNIFIED IDEOGRAPH - 0xC948: 0x4E8D, //CJK UNIFIED IDEOGRAPH - 0xC949: 0x56D7, //CJK UNIFIED IDEOGRAPH - 0xC94A: 0xFA0C, //CJK COMPATIBILITY IDEOGRAPH - 0xC94B: 0x5C6E, //CJK UNIFIED IDEOGRAPH - 0xC94C: 0x5F73, //CJK UNIFIED IDEOGRAPH - 0xC94D: 0x4E0F, //CJK UNIFIED IDEOGRAPH - 0xC94E: 0x5187, //CJK UNIFIED IDEOGRAPH - 0xC94F: 0x4E0E, //CJK UNIFIED IDEOGRAPH - 0xC950: 0x4E2E, //CJK UNIFIED IDEOGRAPH - 0xC951: 0x4E93, //CJK UNIFIED IDEOGRAPH - 0xC952: 0x4EC2, //CJK UNIFIED IDEOGRAPH - 0xC953: 0x4EC9, //CJK UNIFIED IDEOGRAPH - 0xC954: 0x4EC8, //CJK UNIFIED IDEOGRAPH - 0xC955: 0x5198, //CJK UNIFIED IDEOGRAPH - 0xC956: 0x52FC, //CJK UNIFIED IDEOGRAPH - 0xC957: 0x536C, //CJK UNIFIED IDEOGRAPH - 0xC958: 0x53B9, //CJK UNIFIED IDEOGRAPH - 0xC959: 0x5720, //CJK UNIFIED IDEOGRAPH - 0xC95A: 0x5903, //CJK UNIFIED IDEOGRAPH - 0xC95B: 0x592C, //CJK UNIFIED IDEOGRAPH - 0xC95C: 0x5C10, //CJK UNIFIED IDEOGRAPH - 0xC95D: 0x5DFF, //CJK UNIFIED IDEOGRAPH - 0xC95E: 0x65E1, //CJK UNIFIED IDEOGRAPH - 0xC95F: 0x6BB3, //CJK UNIFIED IDEOGRAPH - 0xC960: 0x6BCC, //CJK UNIFIED IDEOGRAPH - 0xC961: 0x6C14, //CJK UNIFIED IDEOGRAPH - 0xC962: 0x723F, //CJK UNIFIED IDEOGRAPH - 0xC963: 0x4E31, //CJK UNIFIED IDEOGRAPH - 0xC964: 0x4E3C, //CJK UNIFIED IDEOGRAPH - 0xC965: 0x4EE8, //CJK UNIFIED IDEOGRAPH - 0xC966: 0x4EDC, //CJK UNIFIED IDEOGRAPH - 0xC967: 0x4EE9, //CJK UNIFIED IDEOGRAPH - 0xC968: 0x4EE1, //CJK UNIFIED IDEOGRAPH - 0xC969: 0x4EDD, //CJK UNIFIED IDEOGRAPH - 0xC96A: 0x4EDA, //CJK UNIFIED IDEOGRAPH - 0xC96B: 0x520C, //CJK UNIFIED IDEOGRAPH - 0xC96C: 0x531C, //CJK UNIFIED IDEOGRAPH - 0xC96D: 0x534C, //CJK UNIFIED IDEOGRAPH - 0xC96E: 0x5722, //CJK UNIFIED IDEOGRAPH - 0xC96F: 0x5723, //CJK UNIFIED IDEOGRAPH - 0xC970: 0x5917, //CJK UNIFIED IDEOGRAPH - 0xC971: 0x592F, //CJK UNIFIED IDEOGRAPH - 0xC972: 0x5B81, //CJK UNIFIED IDEOGRAPH - 0xC973: 0x5B84, //CJK UNIFIED IDEOGRAPH - 0xC974: 0x5C12, //CJK UNIFIED IDEOGRAPH - 0xC975: 0x5C3B, //CJK UNIFIED IDEOGRAPH - 0xC976: 0x5C74, //CJK UNIFIED IDEOGRAPH - 0xC977: 0x5C73, //CJK UNIFIED IDEOGRAPH - 0xC978: 0x5E04, //CJK UNIFIED IDEOGRAPH - 0xC979: 0x5E80, //CJK UNIFIED IDEOGRAPH - 0xC97A: 0x5E82, //CJK UNIFIED IDEOGRAPH - 0xC97B: 0x5FC9, //CJK UNIFIED IDEOGRAPH - 0xC97C: 0x6209, //CJK UNIFIED IDEOGRAPH - 0xC97D: 0x6250, //CJK UNIFIED IDEOGRAPH - 0xC97E: 0x6C15, //CJK UNIFIED IDEOGRAPH - 0xC9A1: 0x6C36, //CJK UNIFIED IDEOGRAPH - 0xC9A2: 0x6C43, //CJK UNIFIED IDEOGRAPH - 0xC9A3: 0x6C3F, //CJK UNIFIED IDEOGRAPH - 0xC9A4: 0x6C3B, //CJK UNIFIED IDEOGRAPH - 0xC9A5: 0x72AE, //CJK UNIFIED IDEOGRAPH - 0xC9A6: 0x72B0, //CJK UNIFIED IDEOGRAPH - 0xC9A7: 0x738A, //CJK UNIFIED IDEOGRAPH - 0xC9A8: 0x79B8, //CJK UNIFIED IDEOGRAPH - 0xC9A9: 0x808A, //CJK UNIFIED IDEOGRAPH - 0xC9AA: 0x961E, //CJK UNIFIED IDEOGRAPH - 0xC9AB: 0x4F0E, //CJK UNIFIED IDEOGRAPH - 0xC9AC: 0x4F18, //CJK UNIFIED IDEOGRAPH - 0xC9AD: 0x4F2C, //CJK UNIFIED IDEOGRAPH - 0xC9AE: 0x4EF5, //CJK UNIFIED IDEOGRAPH - 0xC9AF: 0x4F14, //CJK UNIFIED IDEOGRAPH - 0xC9B0: 0x4EF1, //CJK UNIFIED IDEOGRAPH - 0xC9B1: 0x4F00, //CJK UNIFIED IDEOGRAPH - 0xC9B2: 0x4EF7, //CJK UNIFIED IDEOGRAPH - 0xC9B3: 0x4F08, //CJK UNIFIED IDEOGRAPH - 0xC9B4: 0x4F1D, //CJK UNIFIED IDEOGRAPH - 0xC9B5: 0x4F02, //CJK UNIFIED IDEOGRAPH - 0xC9B6: 0x4F05, //CJK UNIFIED IDEOGRAPH - 0xC9B7: 0x4F22, //CJK UNIFIED IDEOGRAPH - 0xC9B8: 0x4F13, //CJK UNIFIED IDEOGRAPH - 0xC9B9: 0x4F04, //CJK UNIFIED IDEOGRAPH - 0xC9BA: 0x4EF4, //CJK UNIFIED IDEOGRAPH - 0xC9BB: 0x4F12, //CJK UNIFIED IDEOGRAPH - 0xC9BC: 0x51B1, //CJK UNIFIED IDEOGRAPH - 0xC9BD: 0x5213, //CJK UNIFIED IDEOGRAPH - 0xC9BE: 0x5209, //CJK UNIFIED IDEOGRAPH - 0xC9BF: 0x5210, //CJK UNIFIED IDEOGRAPH - 0xC9C0: 0x52A6, //CJK UNIFIED IDEOGRAPH - 0xC9C1: 0x5322, //CJK UNIFIED IDEOGRAPH - 0xC9C2: 0x531F, //CJK UNIFIED IDEOGRAPH - 0xC9C3: 0x534D, //CJK UNIFIED IDEOGRAPH - 0xC9C4: 0x538A, //CJK UNIFIED IDEOGRAPH - 0xC9C5: 0x5407, //CJK UNIFIED IDEOGRAPH - 0xC9C6: 0x56E1, //CJK UNIFIED IDEOGRAPH - 0xC9C7: 0x56DF, //CJK UNIFIED IDEOGRAPH - 0xC9C8: 0x572E, //CJK UNIFIED IDEOGRAPH - 0xC9C9: 0x572A, //CJK UNIFIED IDEOGRAPH - 0xC9CA: 0x5734, //CJK UNIFIED IDEOGRAPH - 0xC9CB: 0x593C, //CJK UNIFIED IDEOGRAPH - 0xC9CC: 0x5980, //CJK UNIFIED IDEOGRAPH - 0xC9CD: 0x597C, //CJK UNIFIED IDEOGRAPH - 0xC9CE: 0x5985, //CJK UNIFIED IDEOGRAPH - 0xC9CF: 0x597B, //CJK UNIFIED IDEOGRAPH - 0xC9D0: 0x597E, //CJK UNIFIED IDEOGRAPH - 0xC9D1: 0x5977, //CJK UNIFIED IDEOGRAPH - 0xC9D2: 0x597F, //CJK UNIFIED IDEOGRAPH - 0xC9D3: 0x5B56, //CJK UNIFIED IDEOGRAPH - 0xC9D4: 0x5C15, //CJK UNIFIED IDEOGRAPH - 0xC9D5: 0x5C25, //CJK UNIFIED IDEOGRAPH - 0xC9D6: 0x5C7C, //CJK UNIFIED IDEOGRAPH - 0xC9D7: 0x5C7A, //CJK UNIFIED IDEOGRAPH - 0xC9D8: 0x5C7B, //CJK UNIFIED IDEOGRAPH - 0xC9D9: 0x5C7E, //CJK UNIFIED IDEOGRAPH - 0xC9DA: 0x5DDF, //CJK UNIFIED IDEOGRAPH - 0xC9DB: 0x5E75, //CJK UNIFIED IDEOGRAPH - 0xC9DC: 0x5E84, //CJK UNIFIED IDEOGRAPH - 0xC9DD: 0x5F02, //CJK UNIFIED IDEOGRAPH - 0xC9DE: 0x5F1A, //CJK UNIFIED IDEOGRAPH - 0xC9DF: 0x5F74, //CJK UNIFIED IDEOGRAPH - 0xC9E0: 0x5FD5, //CJK UNIFIED IDEOGRAPH - 0xC9E1: 0x5FD4, //CJK UNIFIED IDEOGRAPH - 0xC9E2: 0x5FCF, //CJK UNIFIED IDEOGRAPH - 0xC9E3: 0x625C, //CJK UNIFIED IDEOGRAPH - 0xC9E4: 0x625E, //CJK UNIFIED IDEOGRAPH - 0xC9E5: 0x6264, //CJK UNIFIED IDEOGRAPH - 0xC9E6: 0x6261, //CJK UNIFIED IDEOGRAPH - 0xC9E7: 0x6266, //CJK UNIFIED IDEOGRAPH - 0xC9E8: 0x6262, //CJK UNIFIED IDEOGRAPH - 0xC9E9: 0x6259, //CJK UNIFIED IDEOGRAPH - 0xC9EA: 0x6260, //CJK UNIFIED IDEOGRAPH - 0xC9EB: 0x625A, //CJK UNIFIED IDEOGRAPH - 0xC9EC: 0x6265, //CJK UNIFIED IDEOGRAPH - 0xC9ED: 0x65EF, //CJK UNIFIED IDEOGRAPH - 0xC9EE: 0x65EE, //CJK UNIFIED IDEOGRAPH - 0xC9EF: 0x673E, //CJK UNIFIED IDEOGRAPH - 0xC9F0: 0x6739, //CJK UNIFIED IDEOGRAPH - 0xC9F1: 0x6738, //CJK UNIFIED IDEOGRAPH - 0xC9F2: 0x673B, //CJK UNIFIED IDEOGRAPH - 0xC9F3: 0x673A, //CJK UNIFIED IDEOGRAPH - 0xC9F4: 0x673F, //CJK UNIFIED IDEOGRAPH - 0xC9F5: 0x673C, //CJK UNIFIED IDEOGRAPH - 0xC9F6: 0x6733, //CJK UNIFIED IDEOGRAPH - 0xC9F7: 0x6C18, //CJK UNIFIED IDEOGRAPH - 0xC9F8: 0x6C46, //CJK UNIFIED IDEOGRAPH - 0xC9F9: 0x6C52, //CJK UNIFIED IDEOGRAPH - 0xC9FA: 0x6C5C, //CJK UNIFIED IDEOGRAPH - 0xC9FB: 0x6C4F, //CJK UNIFIED IDEOGRAPH - 0xC9FC: 0x6C4A, //CJK UNIFIED IDEOGRAPH - 0xC9FD: 0x6C54, //CJK UNIFIED IDEOGRAPH - 0xC9FE: 0x6C4B, //CJK UNIFIED IDEOGRAPH - 0xCA40: 0x6C4C, //CJK UNIFIED IDEOGRAPH - 0xCA41: 0x7071, //CJK UNIFIED IDEOGRAPH - 0xCA42: 0x725E, //CJK UNIFIED IDEOGRAPH - 0xCA43: 0x72B4, //CJK UNIFIED IDEOGRAPH - 0xCA44: 0x72B5, //CJK UNIFIED IDEOGRAPH - 0xCA45: 0x738E, //CJK UNIFIED IDEOGRAPH - 0xCA46: 0x752A, //CJK UNIFIED IDEOGRAPH - 0xCA47: 0x767F, //CJK UNIFIED IDEOGRAPH - 0xCA48: 0x7A75, //CJK UNIFIED IDEOGRAPH - 0xCA49: 0x7F51, //CJK UNIFIED IDEOGRAPH - 0xCA4A: 0x8278, //CJK UNIFIED IDEOGRAPH - 0xCA4B: 0x827C, //CJK UNIFIED IDEOGRAPH - 0xCA4C: 0x8280, //CJK UNIFIED IDEOGRAPH - 0xCA4D: 0x827D, //CJK UNIFIED IDEOGRAPH - 0xCA4E: 0x827F, //CJK UNIFIED IDEOGRAPH - 0xCA4F: 0x864D, //CJK UNIFIED IDEOGRAPH - 0xCA50: 0x897E, //CJK UNIFIED IDEOGRAPH - 0xCA51: 0x9099, //CJK UNIFIED IDEOGRAPH - 0xCA52: 0x9097, //CJK UNIFIED IDEOGRAPH - 0xCA53: 0x9098, //CJK UNIFIED IDEOGRAPH - 0xCA54: 0x909B, //CJK UNIFIED IDEOGRAPH - 0xCA55: 0x9094, //CJK UNIFIED IDEOGRAPH - 0xCA56: 0x9622, //CJK UNIFIED IDEOGRAPH - 0xCA57: 0x9624, //CJK UNIFIED IDEOGRAPH - 0xCA58: 0x9620, //CJK UNIFIED IDEOGRAPH - 0xCA59: 0x9623, //CJK UNIFIED IDEOGRAPH - 0xCA5A: 0x4F56, //CJK UNIFIED IDEOGRAPH - 0xCA5B: 0x4F3B, //CJK UNIFIED IDEOGRAPH - 0xCA5C: 0x4F62, //CJK UNIFIED IDEOGRAPH - 0xCA5D: 0x4F49, //CJK UNIFIED IDEOGRAPH - 0xCA5E: 0x4F53, //CJK UNIFIED IDEOGRAPH - 0xCA5F: 0x4F64, //CJK UNIFIED IDEOGRAPH - 0xCA60: 0x4F3E, //CJK UNIFIED IDEOGRAPH - 0xCA61: 0x4F67, //CJK UNIFIED IDEOGRAPH - 0xCA62: 0x4F52, //CJK UNIFIED IDEOGRAPH - 0xCA63: 0x4F5F, //CJK UNIFIED IDEOGRAPH - 0xCA64: 0x4F41, //CJK UNIFIED IDEOGRAPH - 0xCA65: 0x4F58, //CJK UNIFIED IDEOGRAPH - 0xCA66: 0x4F2D, //CJK UNIFIED IDEOGRAPH - 0xCA67: 0x4F33, //CJK UNIFIED IDEOGRAPH - 0xCA68: 0x4F3F, //CJK UNIFIED IDEOGRAPH - 0xCA69: 0x4F61, //CJK UNIFIED IDEOGRAPH - 0xCA6A: 0x518F, //CJK UNIFIED IDEOGRAPH - 0xCA6B: 0x51B9, //CJK UNIFIED IDEOGRAPH - 0xCA6C: 0x521C, //CJK UNIFIED IDEOGRAPH - 0xCA6D: 0x521E, //CJK UNIFIED IDEOGRAPH - 0xCA6E: 0x5221, //CJK UNIFIED IDEOGRAPH - 0xCA6F: 0x52AD, //CJK UNIFIED IDEOGRAPH - 0xCA70: 0x52AE, //CJK UNIFIED IDEOGRAPH - 0xCA71: 0x5309, //CJK UNIFIED IDEOGRAPH - 0xCA72: 0x5363, //CJK UNIFIED IDEOGRAPH - 0xCA73: 0x5372, //CJK UNIFIED IDEOGRAPH - 0xCA74: 0x538E, //CJK UNIFIED IDEOGRAPH - 0xCA75: 0x538F, //CJK UNIFIED IDEOGRAPH - 0xCA76: 0x5430, //CJK UNIFIED IDEOGRAPH - 0xCA77: 0x5437, //CJK UNIFIED IDEOGRAPH - 0xCA78: 0x542A, //CJK UNIFIED IDEOGRAPH - 0xCA79: 0x5454, //CJK UNIFIED IDEOGRAPH - 0xCA7A: 0x5445, //CJK UNIFIED IDEOGRAPH - 0xCA7B: 0x5419, //CJK UNIFIED IDEOGRAPH - 0xCA7C: 0x541C, //CJK UNIFIED IDEOGRAPH - 0xCA7D: 0x5425, //CJK UNIFIED IDEOGRAPH - 0xCA7E: 0x5418, //CJK UNIFIED IDEOGRAPH - 0xCAA1: 0x543D, //CJK UNIFIED IDEOGRAPH - 0xCAA2: 0x544F, //CJK UNIFIED IDEOGRAPH - 0xCAA3: 0x5441, //CJK UNIFIED IDEOGRAPH - 0xCAA4: 0x5428, //CJK UNIFIED IDEOGRAPH - 0xCAA5: 0x5424, //CJK UNIFIED IDEOGRAPH - 0xCAA6: 0x5447, //CJK UNIFIED IDEOGRAPH - 0xCAA7: 0x56EE, //CJK UNIFIED IDEOGRAPH - 0xCAA8: 0x56E7, //CJK UNIFIED IDEOGRAPH - 0xCAA9: 0x56E5, //CJK UNIFIED IDEOGRAPH - 0xCAAA: 0x5741, //CJK UNIFIED IDEOGRAPH - 0xCAAB: 0x5745, //CJK UNIFIED IDEOGRAPH - 0xCAAC: 0x574C, //CJK UNIFIED IDEOGRAPH - 0xCAAD: 0x5749, //CJK UNIFIED IDEOGRAPH - 0xCAAE: 0x574B, //CJK UNIFIED IDEOGRAPH - 0xCAAF: 0x5752, //CJK UNIFIED IDEOGRAPH - 0xCAB0: 0x5906, //CJK UNIFIED IDEOGRAPH - 0xCAB1: 0x5940, //CJK UNIFIED IDEOGRAPH - 0xCAB2: 0x59A6, //CJK UNIFIED IDEOGRAPH - 0xCAB3: 0x5998, //CJK UNIFIED IDEOGRAPH - 0xCAB4: 0x59A0, //CJK UNIFIED IDEOGRAPH - 0xCAB5: 0x5997, //CJK UNIFIED IDEOGRAPH - 0xCAB6: 0x598E, //CJK UNIFIED IDEOGRAPH - 0xCAB7: 0x59A2, //CJK UNIFIED IDEOGRAPH - 0xCAB8: 0x5990, //CJK UNIFIED IDEOGRAPH - 0xCAB9: 0x598F, //CJK UNIFIED IDEOGRAPH - 0xCABA: 0x59A7, //CJK UNIFIED IDEOGRAPH - 0xCABB: 0x59A1, //CJK UNIFIED IDEOGRAPH - 0xCABC: 0x5B8E, //CJK UNIFIED IDEOGRAPH - 0xCABD: 0x5B92, //CJK UNIFIED IDEOGRAPH - 0xCABE: 0x5C28, //CJK UNIFIED IDEOGRAPH - 0xCABF: 0x5C2A, //CJK UNIFIED IDEOGRAPH - 0xCAC0: 0x5C8D, //CJK UNIFIED IDEOGRAPH - 0xCAC1: 0x5C8F, //CJK UNIFIED IDEOGRAPH - 0xCAC2: 0x5C88, //CJK UNIFIED IDEOGRAPH - 0xCAC3: 0x5C8B, //CJK UNIFIED IDEOGRAPH - 0xCAC4: 0x5C89, //CJK UNIFIED IDEOGRAPH - 0xCAC5: 0x5C92, //CJK UNIFIED IDEOGRAPH - 0xCAC6: 0x5C8A, //CJK UNIFIED IDEOGRAPH - 0xCAC7: 0x5C86, //CJK UNIFIED IDEOGRAPH - 0xCAC8: 0x5C93, //CJK UNIFIED IDEOGRAPH - 0xCAC9: 0x5C95, //CJK UNIFIED IDEOGRAPH - 0xCACA: 0x5DE0, //CJK UNIFIED IDEOGRAPH - 0xCACB: 0x5E0A, //CJK UNIFIED IDEOGRAPH - 0xCACC: 0x5E0E, //CJK UNIFIED IDEOGRAPH - 0xCACD: 0x5E8B, //CJK UNIFIED IDEOGRAPH - 0xCACE: 0x5E89, //CJK UNIFIED IDEOGRAPH - 0xCACF: 0x5E8C, //CJK UNIFIED IDEOGRAPH - 0xCAD0: 0x5E88, //CJK UNIFIED IDEOGRAPH - 0xCAD1: 0x5E8D, //CJK UNIFIED IDEOGRAPH - 0xCAD2: 0x5F05, //CJK UNIFIED IDEOGRAPH - 0xCAD3: 0x5F1D, //CJK UNIFIED IDEOGRAPH - 0xCAD4: 0x5F78, //CJK UNIFIED IDEOGRAPH - 0xCAD5: 0x5F76, //CJK UNIFIED IDEOGRAPH - 0xCAD6: 0x5FD2, //CJK UNIFIED IDEOGRAPH - 0xCAD7: 0x5FD1, //CJK UNIFIED IDEOGRAPH - 0xCAD8: 0x5FD0, //CJK UNIFIED IDEOGRAPH - 0xCAD9: 0x5FED, //CJK UNIFIED IDEOGRAPH - 0xCADA: 0x5FE8, //CJK UNIFIED IDEOGRAPH - 0xCADB: 0x5FEE, //CJK UNIFIED IDEOGRAPH - 0xCADC: 0x5FF3, //CJK UNIFIED IDEOGRAPH - 0xCADD: 0x5FE1, //CJK UNIFIED IDEOGRAPH - 0xCADE: 0x5FE4, //CJK UNIFIED IDEOGRAPH - 0xCADF: 0x5FE3, //CJK UNIFIED IDEOGRAPH - 0xCAE0: 0x5FFA, //CJK UNIFIED IDEOGRAPH - 0xCAE1: 0x5FEF, //CJK UNIFIED IDEOGRAPH - 0xCAE2: 0x5FF7, //CJK UNIFIED IDEOGRAPH - 0xCAE3: 0x5FFB, //CJK UNIFIED IDEOGRAPH - 0xCAE4: 0x6000, //CJK UNIFIED IDEOGRAPH - 0xCAE5: 0x5FF4, //CJK UNIFIED IDEOGRAPH - 0xCAE6: 0x623A, //CJK UNIFIED IDEOGRAPH - 0xCAE7: 0x6283, //CJK UNIFIED IDEOGRAPH - 0xCAE8: 0x628C, //CJK UNIFIED IDEOGRAPH - 0xCAE9: 0x628E, //CJK UNIFIED IDEOGRAPH - 0xCAEA: 0x628F, //CJK UNIFIED IDEOGRAPH - 0xCAEB: 0x6294, //CJK UNIFIED IDEOGRAPH - 0xCAEC: 0x6287, //CJK UNIFIED IDEOGRAPH - 0xCAED: 0x6271, //CJK UNIFIED IDEOGRAPH - 0xCAEE: 0x627B, //CJK UNIFIED IDEOGRAPH - 0xCAEF: 0x627A, //CJK UNIFIED IDEOGRAPH - 0xCAF0: 0x6270, //CJK UNIFIED IDEOGRAPH - 0xCAF1: 0x6281, //CJK UNIFIED IDEOGRAPH - 0xCAF2: 0x6288, //CJK UNIFIED IDEOGRAPH - 0xCAF3: 0x6277, //CJK UNIFIED IDEOGRAPH - 0xCAF4: 0x627D, //CJK UNIFIED IDEOGRAPH - 0xCAF5: 0x6272, //CJK UNIFIED IDEOGRAPH - 0xCAF6: 0x6274, //CJK UNIFIED IDEOGRAPH - 0xCAF7: 0x6537, //CJK UNIFIED IDEOGRAPH - 0xCAF8: 0x65F0, //CJK UNIFIED IDEOGRAPH - 0xCAF9: 0x65F4, //CJK UNIFIED IDEOGRAPH - 0xCAFA: 0x65F3, //CJK UNIFIED IDEOGRAPH - 0xCAFB: 0x65F2, //CJK UNIFIED IDEOGRAPH - 0xCAFC: 0x65F5, //CJK UNIFIED IDEOGRAPH - 0xCAFD: 0x6745, //CJK UNIFIED IDEOGRAPH - 0xCAFE: 0x6747, //CJK UNIFIED IDEOGRAPH - 0xCB40: 0x6759, //CJK UNIFIED IDEOGRAPH - 0xCB41: 0x6755, //CJK UNIFIED IDEOGRAPH - 0xCB42: 0x674C, //CJK UNIFIED IDEOGRAPH - 0xCB43: 0x6748, //CJK UNIFIED IDEOGRAPH - 0xCB44: 0x675D, //CJK UNIFIED IDEOGRAPH - 0xCB45: 0x674D, //CJK UNIFIED IDEOGRAPH - 0xCB46: 0x675A, //CJK UNIFIED IDEOGRAPH - 0xCB47: 0x674B, //CJK UNIFIED IDEOGRAPH - 0xCB48: 0x6BD0, //CJK UNIFIED IDEOGRAPH - 0xCB49: 0x6C19, //CJK UNIFIED IDEOGRAPH - 0xCB4A: 0x6C1A, //CJK UNIFIED IDEOGRAPH - 0xCB4B: 0x6C78, //CJK UNIFIED IDEOGRAPH - 0xCB4C: 0x6C67, //CJK UNIFIED IDEOGRAPH - 0xCB4D: 0x6C6B, //CJK UNIFIED IDEOGRAPH - 0xCB4E: 0x6C84, //CJK UNIFIED IDEOGRAPH - 0xCB4F: 0x6C8B, //CJK UNIFIED IDEOGRAPH - 0xCB50: 0x6C8F, //CJK UNIFIED IDEOGRAPH - 0xCB51: 0x6C71, //CJK UNIFIED IDEOGRAPH - 0xCB52: 0x6C6F, //CJK UNIFIED IDEOGRAPH - 0xCB53: 0x6C69, //CJK UNIFIED IDEOGRAPH - 0xCB54: 0x6C9A, //CJK UNIFIED IDEOGRAPH - 0xCB55: 0x6C6D, //CJK UNIFIED IDEOGRAPH - 0xCB56: 0x6C87, //CJK UNIFIED IDEOGRAPH - 0xCB57: 0x6C95, //CJK UNIFIED IDEOGRAPH - 0xCB58: 0x6C9C, //CJK UNIFIED IDEOGRAPH - 0xCB59: 0x6C66, //CJK UNIFIED IDEOGRAPH - 0xCB5A: 0x6C73, //CJK UNIFIED IDEOGRAPH - 0xCB5B: 0x6C65, //CJK UNIFIED IDEOGRAPH - 0xCB5C: 0x6C7B, //CJK UNIFIED IDEOGRAPH - 0xCB5D: 0x6C8E, //CJK UNIFIED IDEOGRAPH - 0xCB5E: 0x7074, //CJK UNIFIED IDEOGRAPH - 0xCB5F: 0x707A, //CJK UNIFIED IDEOGRAPH - 0xCB60: 0x7263, //CJK UNIFIED IDEOGRAPH - 0xCB61: 0x72BF, //CJK UNIFIED IDEOGRAPH - 0xCB62: 0x72BD, //CJK UNIFIED IDEOGRAPH - 0xCB63: 0x72C3, //CJK UNIFIED IDEOGRAPH - 0xCB64: 0x72C6, //CJK UNIFIED IDEOGRAPH - 0xCB65: 0x72C1, //CJK UNIFIED IDEOGRAPH - 0xCB66: 0x72BA, //CJK UNIFIED IDEOGRAPH - 0xCB67: 0x72C5, //CJK UNIFIED IDEOGRAPH - 0xCB68: 0x7395, //CJK UNIFIED IDEOGRAPH - 0xCB69: 0x7397, //CJK UNIFIED IDEOGRAPH - 0xCB6A: 0x7393, //CJK UNIFIED IDEOGRAPH - 0xCB6B: 0x7394, //CJK UNIFIED IDEOGRAPH - 0xCB6C: 0x7392, //CJK UNIFIED IDEOGRAPH - 0xCB6D: 0x753A, //CJK UNIFIED IDEOGRAPH - 0xCB6E: 0x7539, //CJK UNIFIED IDEOGRAPH - 0xCB6F: 0x7594, //CJK UNIFIED IDEOGRAPH - 0xCB70: 0x7595, //CJK UNIFIED IDEOGRAPH - 0xCB71: 0x7681, //CJK UNIFIED IDEOGRAPH - 0xCB72: 0x793D, //CJK UNIFIED IDEOGRAPH - 0xCB73: 0x8034, //CJK UNIFIED IDEOGRAPH - 0xCB74: 0x8095, //CJK UNIFIED IDEOGRAPH - 0xCB75: 0x8099, //CJK UNIFIED IDEOGRAPH - 0xCB76: 0x8090, //CJK UNIFIED IDEOGRAPH - 0xCB77: 0x8092, //CJK UNIFIED IDEOGRAPH - 0xCB78: 0x809C, //CJK UNIFIED IDEOGRAPH - 0xCB79: 0x8290, //CJK UNIFIED IDEOGRAPH - 0xCB7A: 0x828F, //CJK UNIFIED IDEOGRAPH - 0xCB7B: 0x8285, //CJK UNIFIED IDEOGRAPH - 0xCB7C: 0x828E, //CJK UNIFIED IDEOGRAPH - 0xCB7D: 0x8291, //CJK UNIFIED IDEOGRAPH - 0xCB7E: 0x8293, //CJK UNIFIED IDEOGRAPH - 0xCBA1: 0x828A, //CJK UNIFIED IDEOGRAPH - 0xCBA2: 0x8283, //CJK UNIFIED IDEOGRAPH - 0xCBA3: 0x8284, //CJK UNIFIED IDEOGRAPH - 0xCBA4: 0x8C78, //CJK UNIFIED IDEOGRAPH - 0xCBA5: 0x8FC9, //CJK UNIFIED IDEOGRAPH - 0xCBA6: 0x8FBF, //CJK UNIFIED IDEOGRAPH - 0xCBA7: 0x909F, //CJK UNIFIED IDEOGRAPH - 0xCBA8: 0x90A1, //CJK UNIFIED IDEOGRAPH - 0xCBA9: 0x90A5, //CJK UNIFIED IDEOGRAPH - 0xCBAA: 0x909E, //CJK UNIFIED IDEOGRAPH - 0xCBAB: 0x90A7, //CJK UNIFIED IDEOGRAPH - 0xCBAC: 0x90A0, //CJK UNIFIED IDEOGRAPH - 0xCBAD: 0x9630, //CJK UNIFIED IDEOGRAPH - 0xCBAE: 0x9628, //CJK UNIFIED IDEOGRAPH - 0xCBAF: 0x962F, //CJK UNIFIED IDEOGRAPH - 0xCBB0: 0x962D, //CJK UNIFIED IDEOGRAPH - 0xCBB1: 0x4E33, //CJK UNIFIED IDEOGRAPH - 0xCBB2: 0x4F98, //CJK UNIFIED IDEOGRAPH - 0xCBB3: 0x4F7C, //CJK UNIFIED IDEOGRAPH - 0xCBB4: 0x4F85, //CJK UNIFIED IDEOGRAPH - 0xCBB5: 0x4F7D, //CJK UNIFIED IDEOGRAPH - 0xCBB6: 0x4F80, //CJK UNIFIED IDEOGRAPH - 0xCBB7: 0x4F87, //CJK UNIFIED IDEOGRAPH - 0xCBB8: 0x4F76, //CJK UNIFIED IDEOGRAPH - 0xCBB9: 0x4F74, //CJK UNIFIED IDEOGRAPH - 0xCBBA: 0x4F89, //CJK UNIFIED IDEOGRAPH - 0xCBBB: 0x4F84, //CJK UNIFIED IDEOGRAPH - 0xCBBC: 0x4F77, //CJK UNIFIED IDEOGRAPH - 0xCBBD: 0x4F4C, //CJK UNIFIED IDEOGRAPH - 0xCBBE: 0x4F97, //CJK UNIFIED IDEOGRAPH - 0xCBBF: 0x4F6A, //CJK UNIFIED IDEOGRAPH - 0xCBC0: 0x4F9A, //CJK UNIFIED IDEOGRAPH - 0xCBC1: 0x4F79, //CJK UNIFIED IDEOGRAPH - 0xCBC2: 0x4F81, //CJK UNIFIED IDEOGRAPH - 0xCBC3: 0x4F78, //CJK UNIFIED IDEOGRAPH - 0xCBC4: 0x4F90, //CJK UNIFIED IDEOGRAPH - 0xCBC5: 0x4F9C, //CJK UNIFIED IDEOGRAPH - 0xCBC6: 0x4F94, //CJK UNIFIED IDEOGRAPH - 0xCBC7: 0x4F9E, //CJK UNIFIED IDEOGRAPH - 0xCBC8: 0x4F92, //CJK UNIFIED IDEOGRAPH - 0xCBC9: 0x4F82, //CJK UNIFIED IDEOGRAPH - 0xCBCA: 0x4F95, //CJK UNIFIED IDEOGRAPH - 0xCBCB: 0x4F6B, //CJK UNIFIED IDEOGRAPH - 0xCBCC: 0x4F6E, //CJK UNIFIED IDEOGRAPH - 0xCBCD: 0x519E, //CJK UNIFIED IDEOGRAPH - 0xCBCE: 0x51BC, //CJK UNIFIED IDEOGRAPH - 0xCBCF: 0x51BE, //CJK UNIFIED IDEOGRAPH - 0xCBD0: 0x5235, //CJK UNIFIED IDEOGRAPH - 0xCBD1: 0x5232, //CJK UNIFIED IDEOGRAPH - 0xCBD2: 0x5233, //CJK UNIFIED IDEOGRAPH - 0xCBD3: 0x5246, //CJK UNIFIED IDEOGRAPH - 0xCBD4: 0x5231, //CJK UNIFIED IDEOGRAPH - 0xCBD5: 0x52BC, //CJK UNIFIED IDEOGRAPH - 0xCBD6: 0x530A, //CJK UNIFIED IDEOGRAPH - 0xCBD7: 0x530B, //CJK UNIFIED IDEOGRAPH - 0xCBD8: 0x533C, //CJK UNIFIED IDEOGRAPH - 0xCBD9: 0x5392, //CJK UNIFIED IDEOGRAPH - 0xCBDA: 0x5394, //CJK UNIFIED IDEOGRAPH - 0xCBDB: 0x5487, //CJK UNIFIED IDEOGRAPH - 0xCBDC: 0x547F, //CJK UNIFIED IDEOGRAPH - 0xCBDD: 0x5481, //CJK UNIFIED IDEOGRAPH - 0xCBDE: 0x5491, //CJK UNIFIED IDEOGRAPH - 0xCBDF: 0x5482, //CJK UNIFIED IDEOGRAPH - 0xCBE0: 0x5488, //CJK UNIFIED IDEOGRAPH - 0xCBE1: 0x546B, //CJK UNIFIED IDEOGRAPH - 0xCBE2: 0x547A, //CJK UNIFIED IDEOGRAPH - 0xCBE3: 0x547E, //CJK UNIFIED IDEOGRAPH - 0xCBE4: 0x5465, //CJK UNIFIED IDEOGRAPH - 0xCBE5: 0x546C, //CJK UNIFIED IDEOGRAPH - 0xCBE6: 0x5474, //CJK UNIFIED IDEOGRAPH - 0xCBE7: 0x5466, //CJK UNIFIED IDEOGRAPH - 0xCBE8: 0x548D, //CJK UNIFIED IDEOGRAPH - 0xCBE9: 0x546F, //CJK UNIFIED IDEOGRAPH - 0xCBEA: 0x5461, //CJK UNIFIED IDEOGRAPH - 0xCBEB: 0x5460, //CJK UNIFIED IDEOGRAPH - 0xCBEC: 0x5498, //CJK UNIFIED IDEOGRAPH - 0xCBED: 0x5463, //CJK UNIFIED IDEOGRAPH - 0xCBEE: 0x5467, //CJK UNIFIED IDEOGRAPH - 0xCBEF: 0x5464, //CJK UNIFIED IDEOGRAPH - 0xCBF0: 0x56F7, //CJK UNIFIED IDEOGRAPH - 0xCBF1: 0x56F9, //CJK UNIFIED IDEOGRAPH - 0xCBF2: 0x576F, //CJK UNIFIED IDEOGRAPH - 0xCBF3: 0x5772, //CJK UNIFIED IDEOGRAPH - 0xCBF4: 0x576D, //CJK UNIFIED IDEOGRAPH - 0xCBF5: 0x576B, //CJK UNIFIED IDEOGRAPH - 0xCBF6: 0x5771, //CJK UNIFIED IDEOGRAPH - 0xCBF7: 0x5770, //CJK UNIFIED IDEOGRAPH - 0xCBF8: 0x5776, //CJK UNIFIED IDEOGRAPH - 0xCBF9: 0x5780, //CJK UNIFIED IDEOGRAPH - 0xCBFA: 0x5775, //CJK UNIFIED IDEOGRAPH - 0xCBFB: 0x577B, //CJK UNIFIED IDEOGRAPH - 0xCBFC: 0x5773, //CJK UNIFIED IDEOGRAPH - 0xCBFD: 0x5774, //CJK UNIFIED IDEOGRAPH - 0xCBFE: 0x5762, //CJK UNIFIED IDEOGRAPH - 0xCC40: 0x5768, //CJK UNIFIED IDEOGRAPH - 0xCC41: 0x577D, //CJK UNIFIED IDEOGRAPH - 0xCC42: 0x590C, //CJK UNIFIED IDEOGRAPH - 0xCC43: 0x5945, //CJK UNIFIED IDEOGRAPH - 0xCC44: 0x59B5, //CJK UNIFIED IDEOGRAPH - 0xCC45: 0x59BA, //CJK UNIFIED IDEOGRAPH - 0xCC46: 0x59CF, //CJK UNIFIED IDEOGRAPH - 0xCC47: 0x59CE, //CJK UNIFIED IDEOGRAPH - 0xCC48: 0x59B2, //CJK UNIFIED IDEOGRAPH - 0xCC49: 0x59CC, //CJK UNIFIED IDEOGRAPH - 0xCC4A: 0x59C1, //CJK UNIFIED IDEOGRAPH - 0xCC4B: 0x59B6, //CJK UNIFIED IDEOGRAPH - 0xCC4C: 0x59BC, //CJK UNIFIED IDEOGRAPH - 0xCC4D: 0x59C3, //CJK UNIFIED IDEOGRAPH - 0xCC4E: 0x59D6, //CJK UNIFIED IDEOGRAPH - 0xCC4F: 0x59B1, //CJK UNIFIED IDEOGRAPH - 0xCC50: 0x59BD, //CJK UNIFIED IDEOGRAPH - 0xCC51: 0x59C0, //CJK UNIFIED IDEOGRAPH - 0xCC52: 0x59C8, //CJK UNIFIED IDEOGRAPH - 0xCC53: 0x59B4, //CJK UNIFIED IDEOGRAPH - 0xCC54: 0x59C7, //CJK UNIFIED IDEOGRAPH - 0xCC55: 0x5B62, //CJK UNIFIED IDEOGRAPH - 0xCC56: 0x5B65, //CJK UNIFIED IDEOGRAPH - 0xCC57: 0x5B93, //CJK UNIFIED IDEOGRAPH - 0xCC58: 0x5B95, //CJK UNIFIED IDEOGRAPH - 0xCC59: 0x5C44, //CJK UNIFIED IDEOGRAPH - 0xCC5A: 0x5C47, //CJK UNIFIED IDEOGRAPH - 0xCC5B: 0x5CAE, //CJK UNIFIED IDEOGRAPH - 0xCC5C: 0x5CA4, //CJK UNIFIED IDEOGRAPH - 0xCC5D: 0x5CA0, //CJK UNIFIED IDEOGRAPH - 0xCC5E: 0x5CB5, //CJK UNIFIED IDEOGRAPH - 0xCC5F: 0x5CAF, //CJK UNIFIED IDEOGRAPH - 0xCC60: 0x5CA8, //CJK UNIFIED IDEOGRAPH - 0xCC61: 0x5CAC, //CJK UNIFIED IDEOGRAPH - 0xCC62: 0x5C9F, //CJK UNIFIED IDEOGRAPH - 0xCC63: 0x5CA3, //CJK UNIFIED IDEOGRAPH - 0xCC64: 0x5CAD, //CJK UNIFIED IDEOGRAPH - 0xCC65: 0x5CA2, //CJK UNIFIED IDEOGRAPH - 0xCC66: 0x5CAA, //CJK UNIFIED IDEOGRAPH - 0xCC67: 0x5CA7, //CJK UNIFIED IDEOGRAPH - 0xCC68: 0x5C9D, //CJK UNIFIED IDEOGRAPH - 0xCC69: 0x5CA5, //CJK UNIFIED IDEOGRAPH - 0xCC6A: 0x5CB6, //CJK UNIFIED IDEOGRAPH - 0xCC6B: 0x5CB0, //CJK UNIFIED IDEOGRAPH - 0xCC6C: 0x5CA6, //CJK UNIFIED IDEOGRAPH - 0xCC6D: 0x5E17, //CJK UNIFIED IDEOGRAPH - 0xCC6E: 0x5E14, //CJK UNIFIED IDEOGRAPH - 0xCC6F: 0x5E19, //CJK UNIFIED IDEOGRAPH - 0xCC70: 0x5F28, //CJK UNIFIED IDEOGRAPH - 0xCC71: 0x5F22, //CJK UNIFIED IDEOGRAPH - 0xCC72: 0x5F23, //CJK UNIFIED IDEOGRAPH - 0xCC73: 0x5F24, //CJK UNIFIED IDEOGRAPH - 0xCC74: 0x5F54, //CJK UNIFIED IDEOGRAPH - 0xCC75: 0x5F82, //CJK UNIFIED IDEOGRAPH - 0xCC76: 0x5F7E, //CJK UNIFIED IDEOGRAPH - 0xCC77: 0x5F7D, //CJK UNIFIED IDEOGRAPH - 0xCC78: 0x5FDE, //CJK UNIFIED IDEOGRAPH - 0xCC79: 0x5FE5, //CJK UNIFIED IDEOGRAPH - 0xCC7A: 0x602D, //CJK UNIFIED IDEOGRAPH - 0xCC7B: 0x6026, //CJK UNIFIED IDEOGRAPH - 0xCC7C: 0x6019, //CJK UNIFIED IDEOGRAPH - 0xCC7D: 0x6032, //CJK UNIFIED IDEOGRAPH - 0xCC7E: 0x600B, //CJK UNIFIED IDEOGRAPH - 0xCCA1: 0x6034, //CJK UNIFIED IDEOGRAPH - 0xCCA2: 0x600A, //CJK UNIFIED IDEOGRAPH - 0xCCA3: 0x6017, //CJK UNIFIED IDEOGRAPH - 0xCCA4: 0x6033, //CJK UNIFIED IDEOGRAPH - 0xCCA5: 0x601A, //CJK UNIFIED IDEOGRAPH - 0xCCA6: 0x601E, //CJK UNIFIED IDEOGRAPH - 0xCCA7: 0x602C, //CJK UNIFIED IDEOGRAPH - 0xCCA8: 0x6022, //CJK UNIFIED IDEOGRAPH - 0xCCA9: 0x600D, //CJK UNIFIED IDEOGRAPH - 0xCCAA: 0x6010, //CJK UNIFIED IDEOGRAPH - 0xCCAB: 0x602E, //CJK UNIFIED IDEOGRAPH - 0xCCAC: 0x6013, //CJK UNIFIED IDEOGRAPH - 0xCCAD: 0x6011, //CJK UNIFIED IDEOGRAPH - 0xCCAE: 0x600C, //CJK UNIFIED IDEOGRAPH - 0xCCAF: 0x6009, //CJK UNIFIED IDEOGRAPH - 0xCCB0: 0x601C, //CJK UNIFIED IDEOGRAPH - 0xCCB1: 0x6214, //CJK UNIFIED IDEOGRAPH - 0xCCB2: 0x623D, //CJK UNIFIED IDEOGRAPH - 0xCCB3: 0x62AD, //CJK UNIFIED IDEOGRAPH - 0xCCB4: 0x62B4, //CJK UNIFIED IDEOGRAPH - 0xCCB5: 0x62D1, //CJK UNIFIED IDEOGRAPH - 0xCCB6: 0x62BE, //CJK UNIFIED IDEOGRAPH - 0xCCB7: 0x62AA, //CJK UNIFIED IDEOGRAPH - 0xCCB8: 0x62B6, //CJK UNIFIED IDEOGRAPH - 0xCCB9: 0x62CA, //CJK UNIFIED IDEOGRAPH - 0xCCBA: 0x62AE, //CJK UNIFIED IDEOGRAPH - 0xCCBB: 0x62B3, //CJK UNIFIED IDEOGRAPH - 0xCCBC: 0x62AF, //CJK UNIFIED IDEOGRAPH - 0xCCBD: 0x62BB, //CJK UNIFIED IDEOGRAPH - 0xCCBE: 0x62A9, //CJK UNIFIED IDEOGRAPH - 0xCCBF: 0x62B0, //CJK UNIFIED IDEOGRAPH - 0xCCC0: 0x62B8, //CJK UNIFIED IDEOGRAPH - 0xCCC1: 0x653D, //CJK UNIFIED IDEOGRAPH - 0xCCC2: 0x65A8, //CJK UNIFIED IDEOGRAPH - 0xCCC3: 0x65BB, //CJK UNIFIED IDEOGRAPH - 0xCCC4: 0x6609, //CJK UNIFIED IDEOGRAPH - 0xCCC5: 0x65FC, //CJK UNIFIED IDEOGRAPH - 0xCCC6: 0x6604, //CJK UNIFIED IDEOGRAPH - 0xCCC7: 0x6612, //CJK UNIFIED IDEOGRAPH - 0xCCC8: 0x6608, //CJK UNIFIED IDEOGRAPH - 0xCCC9: 0x65FB, //CJK UNIFIED IDEOGRAPH - 0xCCCA: 0x6603, //CJK UNIFIED IDEOGRAPH - 0xCCCB: 0x660B, //CJK UNIFIED IDEOGRAPH - 0xCCCC: 0x660D, //CJK UNIFIED IDEOGRAPH - 0xCCCD: 0x6605, //CJK UNIFIED IDEOGRAPH - 0xCCCE: 0x65FD, //CJK UNIFIED IDEOGRAPH - 0xCCCF: 0x6611, //CJK UNIFIED IDEOGRAPH - 0xCCD0: 0x6610, //CJK UNIFIED IDEOGRAPH - 0xCCD1: 0x66F6, //CJK UNIFIED IDEOGRAPH - 0xCCD2: 0x670A, //CJK UNIFIED IDEOGRAPH - 0xCCD3: 0x6785, //CJK UNIFIED IDEOGRAPH - 0xCCD4: 0x676C, //CJK UNIFIED IDEOGRAPH - 0xCCD5: 0x678E, //CJK UNIFIED IDEOGRAPH - 0xCCD6: 0x6792, //CJK UNIFIED IDEOGRAPH - 0xCCD7: 0x6776, //CJK UNIFIED IDEOGRAPH - 0xCCD8: 0x677B, //CJK UNIFIED IDEOGRAPH - 0xCCD9: 0x6798, //CJK UNIFIED IDEOGRAPH - 0xCCDA: 0x6786, //CJK UNIFIED IDEOGRAPH - 0xCCDB: 0x6784, //CJK UNIFIED IDEOGRAPH - 0xCCDC: 0x6774, //CJK UNIFIED IDEOGRAPH - 0xCCDD: 0x678D, //CJK UNIFIED IDEOGRAPH - 0xCCDE: 0x678C, //CJK UNIFIED IDEOGRAPH - 0xCCDF: 0x677A, //CJK UNIFIED IDEOGRAPH - 0xCCE0: 0x679F, //CJK UNIFIED IDEOGRAPH - 0xCCE1: 0x6791, //CJK UNIFIED IDEOGRAPH - 0xCCE2: 0x6799, //CJK UNIFIED IDEOGRAPH - 0xCCE3: 0x6783, //CJK UNIFIED IDEOGRAPH - 0xCCE4: 0x677D, //CJK UNIFIED IDEOGRAPH - 0xCCE5: 0x6781, //CJK UNIFIED IDEOGRAPH - 0xCCE6: 0x6778, //CJK UNIFIED IDEOGRAPH - 0xCCE7: 0x6779, //CJK UNIFIED IDEOGRAPH - 0xCCE8: 0x6794, //CJK UNIFIED IDEOGRAPH - 0xCCE9: 0x6B25, //CJK UNIFIED IDEOGRAPH - 0xCCEA: 0x6B80, //CJK UNIFIED IDEOGRAPH - 0xCCEB: 0x6B7E, //CJK UNIFIED IDEOGRAPH - 0xCCEC: 0x6BDE, //CJK UNIFIED IDEOGRAPH - 0xCCED: 0x6C1D, //CJK UNIFIED IDEOGRAPH - 0xCCEE: 0x6C93, //CJK UNIFIED IDEOGRAPH - 0xCCEF: 0x6CEC, //CJK UNIFIED IDEOGRAPH - 0xCCF0: 0x6CEB, //CJK UNIFIED IDEOGRAPH - 0xCCF1: 0x6CEE, //CJK UNIFIED IDEOGRAPH - 0xCCF2: 0x6CD9, //CJK UNIFIED IDEOGRAPH - 0xCCF3: 0x6CB6, //CJK UNIFIED IDEOGRAPH - 0xCCF4: 0x6CD4, //CJK UNIFIED IDEOGRAPH - 0xCCF5: 0x6CAD, //CJK UNIFIED IDEOGRAPH - 0xCCF6: 0x6CE7, //CJK UNIFIED IDEOGRAPH - 0xCCF7: 0x6CB7, //CJK UNIFIED IDEOGRAPH - 0xCCF8: 0x6CD0, //CJK UNIFIED IDEOGRAPH - 0xCCF9: 0x6CC2, //CJK UNIFIED IDEOGRAPH - 0xCCFA: 0x6CBA, //CJK UNIFIED IDEOGRAPH - 0xCCFB: 0x6CC3, //CJK UNIFIED IDEOGRAPH - 0xCCFC: 0x6CC6, //CJK UNIFIED IDEOGRAPH - 0xCCFD: 0x6CED, //CJK UNIFIED IDEOGRAPH - 0xCCFE: 0x6CF2, //CJK UNIFIED IDEOGRAPH - 0xCD40: 0x6CD2, //CJK UNIFIED IDEOGRAPH - 0xCD41: 0x6CDD, //CJK UNIFIED IDEOGRAPH - 0xCD42: 0x6CB4, //CJK UNIFIED IDEOGRAPH - 0xCD43: 0x6C8A, //CJK UNIFIED IDEOGRAPH - 0xCD44: 0x6C9D, //CJK UNIFIED IDEOGRAPH - 0xCD45: 0x6C80, //CJK UNIFIED IDEOGRAPH - 0xCD46: 0x6CDE, //CJK UNIFIED IDEOGRAPH - 0xCD47: 0x6CC0, //CJK UNIFIED IDEOGRAPH - 0xCD48: 0x6D30, //CJK UNIFIED IDEOGRAPH - 0xCD49: 0x6CCD, //CJK UNIFIED IDEOGRAPH - 0xCD4A: 0x6CC7, //CJK UNIFIED IDEOGRAPH - 0xCD4B: 0x6CB0, //CJK UNIFIED IDEOGRAPH - 0xCD4C: 0x6CF9, //CJK UNIFIED IDEOGRAPH - 0xCD4D: 0x6CCF, //CJK UNIFIED IDEOGRAPH - 0xCD4E: 0x6CE9, //CJK UNIFIED IDEOGRAPH - 0xCD4F: 0x6CD1, //CJK UNIFIED IDEOGRAPH - 0xCD50: 0x7094, //CJK UNIFIED IDEOGRAPH - 0xCD51: 0x7098, //CJK UNIFIED IDEOGRAPH - 0xCD52: 0x7085, //CJK UNIFIED IDEOGRAPH - 0xCD53: 0x7093, //CJK UNIFIED IDEOGRAPH - 0xCD54: 0x7086, //CJK UNIFIED IDEOGRAPH - 0xCD55: 0x7084, //CJK UNIFIED IDEOGRAPH - 0xCD56: 0x7091, //CJK UNIFIED IDEOGRAPH - 0xCD57: 0x7096, //CJK UNIFIED IDEOGRAPH - 0xCD58: 0x7082, //CJK UNIFIED IDEOGRAPH - 0xCD59: 0x709A, //CJK UNIFIED IDEOGRAPH - 0xCD5A: 0x7083, //CJK UNIFIED IDEOGRAPH - 0xCD5B: 0x726A, //CJK UNIFIED IDEOGRAPH - 0xCD5C: 0x72D6, //CJK UNIFIED IDEOGRAPH - 0xCD5D: 0x72CB, //CJK UNIFIED IDEOGRAPH - 0xCD5E: 0x72D8, //CJK UNIFIED IDEOGRAPH - 0xCD5F: 0x72C9, //CJK UNIFIED IDEOGRAPH - 0xCD60: 0x72DC, //CJK UNIFIED IDEOGRAPH - 0xCD61: 0x72D2, //CJK UNIFIED IDEOGRAPH - 0xCD62: 0x72D4, //CJK UNIFIED IDEOGRAPH - 0xCD63: 0x72DA, //CJK UNIFIED IDEOGRAPH - 0xCD64: 0x72CC, //CJK UNIFIED IDEOGRAPH - 0xCD65: 0x72D1, //CJK UNIFIED IDEOGRAPH - 0xCD66: 0x73A4, //CJK UNIFIED IDEOGRAPH - 0xCD67: 0x73A1, //CJK UNIFIED IDEOGRAPH - 0xCD68: 0x73AD, //CJK UNIFIED IDEOGRAPH - 0xCD69: 0x73A6, //CJK UNIFIED IDEOGRAPH - 0xCD6A: 0x73A2, //CJK UNIFIED IDEOGRAPH - 0xCD6B: 0x73A0, //CJK UNIFIED IDEOGRAPH - 0xCD6C: 0x73AC, //CJK UNIFIED IDEOGRAPH - 0xCD6D: 0x739D, //CJK UNIFIED IDEOGRAPH - 0xCD6E: 0x74DD, //CJK UNIFIED IDEOGRAPH - 0xCD6F: 0x74E8, //CJK UNIFIED IDEOGRAPH - 0xCD70: 0x753F, //CJK UNIFIED IDEOGRAPH - 0xCD71: 0x7540, //CJK UNIFIED IDEOGRAPH - 0xCD72: 0x753E, //CJK UNIFIED IDEOGRAPH - 0xCD73: 0x758C, //CJK UNIFIED IDEOGRAPH - 0xCD74: 0x7598, //CJK UNIFIED IDEOGRAPH - 0xCD75: 0x76AF, //CJK UNIFIED IDEOGRAPH - 0xCD76: 0x76F3, //CJK UNIFIED IDEOGRAPH - 0xCD77: 0x76F1, //CJK UNIFIED IDEOGRAPH - 0xCD78: 0x76F0, //CJK UNIFIED IDEOGRAPH - 0xCD79: 0x76F5, //CJK UNIFIED IDEOGRAPH - 0xCD7A: 0x77F8, //CJK UNIFIED IDEOGRAPH - 0xCD7B: 0x77FC, //CJK UNIFIED IDEOGRAPH - 0xCD7C: 0x77F9, //CJK UNIFIED IDEOGRAPH - 0xCD7D: 0x77FB, //CJK UNIFIED IDEOGRAPH - 0xCD7E: 0x77FA, //CJK UNIFIED IDEOGRAPH - 0xCDA1: 0x77F7, //CJK UNIFIED IDEOGRAPH - 0xCDA2: 0x7942, //CJK UNIFIED IDEOGRAPH - 0xCDA3: 0x793F, //CJK UNIFIED IDEOGRAPH - 0xCDA4: 0x79C5, //CJK UNIFIED IDEOGRAPH - 0xCDA5: 0x7A78, //CJK UNIFIED IDEOGRAPH - 0xCDA6: 0x7A7B, //CJK UNIFIED IDEOGRAPH - 0xCDA7: 0x7AFB, //CJK UNIFIED IDEOGRAPH - 0xCDA8: 0x7C75, //CJK UNIFIED IDEOGRAPH - 0xCDA9: 0x7CFD, //CJK UNIFIED IDEOGRAPH - 0xCDAA: 0x8035, //CJK UNIFIED IDEOGRAPH - 0xCDAB: 0x808F, //CJK UNIFIED IDEOGRAPH - 0xCDAC: 0x80AE, //CJK UNIFIED IDEOGRAPH - 0xCDAD: 0x80A3, //CJK UNIFIED IDEOGRAPH - 0xCDAE: 0x80B8, //CJK UNIFIED IDEOGRAPH - 0xCDAF: 0x80B5, //CJK UNIFIED IDEOGRAPH - 0xCDB0: 0x80AD, //CJK UNIFIED IDEOGRAPH - 0xCDB1: 0x8220, //CJK UNIFIED IDEOGRAPH - 0xCDB2: 0x82A0, //CJK UNIFIED IDEOGRAPH - 0xCDB3: 0x82C0, //CJK UNIFIED IDEOGRAPH - 0xCDB4: 0x82AB, //CJK UNIFIED IDEOGRAPH - 0xCDB5: 0x829A, //CJK UNIFIED IDEOGRAPH - 0xCDB6: 0x8298, //CJK UNIFIED IDEOGRAPH - 0xCDB7: 0x829B, //CJK UNIFIED IDEOGRAPH - 0xCDB8: 0x82B5, //CJK UNIFIED IDEOGRAPH - 0xCDB9: 0x82A7, //CJK UNIFIED IDEOGRAPH - 0xCDBA: 0x82AE, //CJK UNIFIED IDEOGRAPH - 0xCDBB: 0x82BC, //CJK UNIFIED IDEOGRAPH - 0xCDBC: 0x829E, //CJK UNIFIED IDEOGRAPH - 0xCDBD: 0x82BA, //CJK UNIFIED IDEOGRAPH - 0xCDBE: 0x82B4, //CJK UNIFIED IDEOGRAPH - 0xCDBF: 0x82A8, //CJK UNIFIED IDEOGRAPH - 0xCDC0: 0x82A1, //CJK UNIFIED IDEOGRAPH - 0xCDC1: 0x82A9, //CJK UNIFIED IDEOGRAPH - 0xCDC2: 0x82C2, //CJK UNIFIED IDEOGRAPH - 0xCDC3: 0x82A4, //CJK UNIFIED IDEOGRAPH - 0xCDC4: 0x82C3, //CJK UNIFIED IDEOGRAPH - 0xCDC5: 0x82B6, //CJK UNIFIED IDEOGRAPH - 0xCDC6: 0x82A2, //CJK UNIFIED IDEOGRAPH - 0xCDC7: 0x8670, //CJK UNIFIED IDEOGRAPH - 0xCDC8: 0x866F, //CJK UNIFIED IDEOGRAPH - 0xCDC9: 0x866D, //CJK UNIFIED IDEOGRAPH - 0xCDCA: 0x866E, //CJK UNIFIED IDEOGRAPH - 0xCDCB: 0x8C56, //CJK UNIFIED IDEOGRAPH - 0xCDCC: 0x8FD2, //CJK UNIFIED IDEOGRAPH - 0xCDCD: 0x8FCB, //CJK UNIFIED IDEOGRAPH - 0xCDCE: 0x8FD3, //CJK UNIFIED IDEOGRAPH - 0xCDCF: 0x8FCD, //CJK UNIFIED IDEOGRAPH - 0xCDD0: 0x8FD6, //CJK UNIFIED IDEOGRAPH - 0xCDD1: 0x8FD5, //CJK UNIFIED IDEOGRAPH - 0xCDD2: 0x8FD7, //CJK UNIFIED IDEOGRAPH - 0xCDD3: 0x90B2, //CJK UNIFIED IDEOGRAPH - 0xCDD4: 0x90B4, //CJK UNIFIED IDEOGRAPH - 0xCDD5: 0x90AF, //CJK UNIFIED IDEOGRAPH - 0xCDD6: 0x90B3, //CJK UNIFIED IDEOGRAPH - 0xCDD7: 0x90B0, //CJK UNIFIED IDEOGRAPH - 0xCDD8: 0x9639, //CJK UNIFIED IDEOGRAPH - 0xCDD9: 0x963D, //CJK UNIFIED IDEOGRAPH - 0xCDDA: 0x963C, //CJK UNIFIED IDEOGRAPH - 0xCDDB: 0x963A, //CJK UNIFIED IDEOGRAPH - 0xCDDC: 0x9643, //CJK UNIFIED IDEOGRAPH - 0xCDDD: 0x4FCD, //CJK UNIFIED IDEOGRAPH - 0xCDDE: 0x4FC5, //CJK UNIFIED IDEOGRAPH - 0xCDDF: 0x4FD3, //CJK UNIFIED IDEOGRAPH - 0xCDE0: 0x4FB2, //CJK UNIFIED IDEOGRAPH - 0xCDE1: 0x4FC9, //CJK UNIFIED IDEOGRAPH - 0xCDE2: 0x4FCB, //CJK UNIFIED IDEOGRAPH - 0xCDE3: 0x4FC1, //CJK UNIFIED IDEOGRAPH - 0xCDE4: 0x4FD4, //CJK UNIFIED IDEOGRAPH - 0xCDE5: 0x4FDC, //CJK UNIFIED IDEOGRAPH - 0xCDE6: 0x4FD9, //CJK UNIFIED IDEOGRAPH - 0xCDE7: 0x4FBB, //CJK UNIFIED IDEOGRAPH - 0xCDE8: 0x4FB3, //CJK UNIFIED IDEOGRAPH - 0xCDE9: 0x4FDB, //CJK UNIFIED IDEOGRAPH - 0xCDEA: 0x4FC7, //CJK UNIFIED IDEOGRAPH - 0xCDEB: 0x4FD6, //CJK UNIFIED IDEOGRAPH - 0xCDEC: 0x4FBA, //CJK UNIFIED IDEOGRAPH - 0xCDED: 0x4FC0, //CJK UNIFIED IDEOGRAPH - 0xCDEE: 0x4FB9, //CJK UNIFIED IDEOGRAPH - 0xCDEF: 0x4FEC, //CJK UNIFIED IDEOGRAPH - 0xCDF0: 0x5244, //CJK UNIFIED IDEOGRAPH - 0xCDF1: 0x5249, //CJK UNIFIED IDEOGRAPH - 0xCDF2: 0x52C0, //CJK UNIFIED IDEOGRAPH - 0xCDF3: 0x52C2, //CJK UNIFIED IDEOGRAPH - 0xCDF4: 0x533D, //CJK UNIFIED IDEOGRAPH - 0xCDF5: 0x537C, //CJK UNIFIED IDEOGRAPH - 0xCDF6: 0x5397, //CJK UNIFIED IDEOGRAPH - 0xCDF7: 0x5396, //CJK UNIFIED IDEOGRAPH - 0xCDF8: 0x5399, //CJK UNIFIED IDEOGRAPH - 0xCDF9: 0x5398, //CJK UNIFIED IDEOGRAPH - 0xCDFA: 0x54BA, //CJK UNIFIED IDEOGRAPH - 0xCDFB: 0x54A1, //CJK UNIFIED IDEOGRAPH - 0xCDFC: 0x54AD, //CJK UNIFIED IDEOGRAPH - 0xCDFD: 0x54A5, //CJK UNIFIED IDEOGRAPH - 0xCDFE: 0x54CF, //CJK UNIFIED IDEOGRAPH - 0xCE40: 0x54C3, //CJK UNIFIED IDEOGRAPH - 0xCE41: 0x830D, //CJK UNIFIED IDEOGRAPH - 0xCE42: 0x54B7, //CJK UNIFIED IDEOGRAPH - 0xCE43: 0x54AE, //CJK UNIFIED IDEOGRAPH - 0xCE44: 0x54D6, //CJK UNIFIED IDEOGRAPH - 0xCE45: 0x54B6, //CJK UNIFIED IDEOGRAPH - 0xCE46: 0x54C5, //CJK UNIFIED IDEOGRAPH - 0xCE47: 0x54C6, //CJK UNIFIED IDEOGRAPH - 0xCE48: 0x54A0, //CJK UNIFIED IDEOGRAPH - 0xCE49: 0x5470, //CJK UNIFIED IDEOGRAPH - 0xCE4A: 0x54BC, //CJK UNIFIED IDEOGRAPH - 0xCE4B: 0x54A2, //CJK UNIFIED IDEOGRAPH - 0xCE4C: 0x54BE, //CJK UNIFIED IDEOGRAPH - 0xCE4D: 0x5472, //CJK UNIFIED IDEOGRAPH - 0xCE4E: 0x54DE, //CJK UNIFIED IDEOGRAPH - 0xCE4F: 0x54B0, //CJK UNIFIED IDEOGRAPH - 0xCE50: 0x57B5, //CJK UNIFIED IDEOGRAPH - 0xCE51: 0x579E, //CJK UNIFIED IDEOGRAPH - 0xCE52: 0x579F, //CJK UNIFIED IDEOGRAPH - 0xCE53: 0x57A4, //CJK UNIFIED IDEOGRAPH - 0xCE54: 0x578C, //CJK UNIFIED IDEOGRAPH - 0xCE55: 0x5797, //CJK UNIFIED IDEOGRAPH - 0xCE56: 0x579D, //CJK UNIFIED IDEOGRAPH - 0xCE57: 0x579B, //CJK UNIFIED IDEOGRAPH - 0xCE58: 0x5794, //CJK UNIFIED IDEOGRAPH - 0xCE59: 0x5798, //CJK UNIFIED IDEOGRAPH - 0xCE5A: 0x578F, //CJK UNIFIED IDEOGRAPH - 0xCE5B: 0x5799, //CJK UNIFIED IDEOGRAPH - 0xCE5C: 0x57A5, //CJK UNIFIED IDEOGRAPH - 0xCE5D: 0x579A, //CJK UNIFIED IDEOGRAPH - 0xCE5E: 0x5795, //CJK UNIFIED IDEOGRAPH - 0xCE5F: 0x58F4, //CJK UNIFIED IDEOGRAPH - 0xCE60: 0x590D, //CJK UNIFIED IDEOGRAPH - 0xCE61: 0x5953, //CJK UNIFIED IDEOGRAPH - 0xCE62: 0x59E1, //CJK UNIFIED IDEOGRAPH - 0xCE63: 0x59DE, //CJK UNIFIED IDEOGRAPH - 0xCE64: 0x59EE, //CJK UNIFIED IDEOGRAPH - 0xCE65: 0x5A00, //CJK UNIFIED IDEOGRAPH - 0xCE66: 0x59F1, //CJK UNIFIED IDEOGRAPH - 0xCE67: 0x59DD, //CJK UNIFIED IDEOGRAPH - 0xCE68: 0x59FA, //CJK UNIFIED IDEOGRAPH - 0xCE69: 0x59FD, //CJK UNIFIED IDEOGRAPH - 0xCE6A: 0x59FC, //CJK UNIFIED IDEOGRAPH - 0xCE6B: 0x59F6, //CJK UNIFIED IDEOGRAPH - 0xCE6C: 0x59E4, //CJK UNIFIED IDEOGRAPH - 0xCE6D: 0x59F2, //CJK UNIFIED IDEOGRAPH - 0xCE6E: 0x59F7, //CJK UNIFIED IDEOGRAPH - 0xCE6F: 0x59DB, //CJK UNIFIED IDEOGRAPH - 0xCE70: 0x59E9, //CJK UNIFIED IDEOGRAPH - 0xCE71: 0x59F3, //CJK UNIFIED IDEOGRAPH - 0xCE72: 0x59F5, //CJK UNIFIED IDEOGRAPH - 0xCE73: 0x59E0, //CJK UNIFIED IDEOGRAPH - 0xCE74: 0x59FE, //CJK UNIFIED IDEOGRAPH - 0xCE75: 0x59F4, //CJK UNIFIED IDEOGRAPH - 0xCE76: 0x59ED, //CJK UNIFIED IDEOGRAPH - 0xCE77: 0x5BA8, //CJK UNIFIED IDEOGRAPH - 0xCE78: 0x5C4C, //CJK UNIFIED IDEOGRAPH - 0xCE79: 0x5CD0, //CJK UNIFIED IDEOGRAPH - 0xCE7A: 0x5CD8, //CJK UNIFIED IDEOGRAPH - 0xCE7B: 0x5CCC, //CJK UNIFIED IDEOGRAPH - 0xCE7C: 0x5CD7, //CJK UNIFIED IDEOGRAPH - 0xCE7D: 0x5CCB, //CJK UNIFIED IDEOGRAPH - 0xCE7E: 0x5CDB, //CJK UNIFIED IDEOGRAPH - 0xCEA1: 0x5CDE, //CJK UNIFIED IDEOGRAPH - 0xCEA2: 0x5CDA, //CJK UNIFIED IDEOGRAPH - 0xCEA3: 0x5CC9, //CJK UNIFIED IDEOGRAPH - 0xCEA4: 0x5CC7, //CJK UNIFIED IDEOGRAPH - 0xCEA5: 0x5CCA, //CJK UNIFIED IDEOGRAPH - 0xCEA6: 0x5CD6, //CJK UNIFIED IDEOGRAPH - 0xCEA7: 0x5CD3, //CJK UNIFIED IDEOGRAPH - 0xCEA8: 0x5CD4, //CJK UNIFIED IDEOGRAPH - 0xCEA9: 0x5CCF, //CJK UNIFIED IDEOGRAPH - 0xCEAA: 0x5CC8, //CJK UNIFIED IDEOGRAPH - 0xCEAB: 0x5CC6, //CJK UNIFIED IDEOGRAPH - 0xCEAC: 0x5CCE, //CJK UNIFIED IDEOGRAPH - 0xCEAD: 0x5CDF, //CJK UNIFIED IDEOGRAPH - 0xCEAE: 0x5CF8, //CJK UNIFIED IDEOGRAPH - 0xCEAF: 0x5DF9, //CJK UNIFIED IDEOGRAPH - 0xCEB0: 0x5E21, //CJK UNIFIED IDEOGRAPH - 0xCEB1: 0x5E22, //CJK UNIFIED IDEOGRAPH - 0xCEB2: 0x5E23, //CJK UNIFIED IDEOGRAPH - 0xCEB3: 0x5E20, //CJK UNIFIED IDEOGRAPH - 0xCEB4: 0x5E24, //CJK UNIFIED IDEOGRAPH - 0xCEB5: 0x5EB0, //CJK UNIFIED IDEOGRAPH - 0xCEB6: 0x5EA4, //CJK UNIFIED IDEOGRAPH - 0xCEB7: 0x5EA2, //CJK UNIFIED IDEOGRAPH - 0xCEB8: 0x5E9B, //CJK UNIFIED IDEOGRAPH - 0xCEB9: 0x5EA3, //CJK UNIFIED IDEOGRAPH - 0xCEBA: 0x5EA5, //CJK UNIFIED IDEOGRAPH - 0xCEBB: 0x5F07, //CJK UNIFIED IDEOGRAPH - 0xCEBC: 0x5F2E, //CJK UNIFIED IDEOGRAPH - 0xCEBD: 0x5F56, //CJK UNIFIED IDEOGRAPH - 0xCEBE: 0x5F86, //CJK UNIFIED IDEOGRAPH - 0xCEBF: 0x6037, //CJK UNIFIED IDEOGRAPH - 0xCEC0: 0x6039, //CJK UNIFIED IDEOGRAPH - 0xCEC1: 0x6054, //CJK UNIFIED IDEOGRAPH - 0xCEC2: 0x6072, //CJK UNIFIED IDEOGRAPH - 0xCEC3: 0x605E, //CJK UNIFIED IDEOGRAPH - 0xCEC4: 0x6045, //CJK UNIFIED IDEOGRAPH - 0xCEC5: 0x6053, //CJK UNIFIED IDEOGRAPH - 0xCEC6: 0x6047, //CJK UNIFIED IDEOGRAPH - 0xCEC7: 0x6049, //CJK UNIFIED IDEOGRAPH - 0xCEC8: 0x605B, //CJK UNIFIED IDEOGRAPH - 0xCEC9: 0x604C, //CJK UNIFIED IDEOGRAPH - 0xCECA: 0x6040, //CJK UNIFIED IDEOGRAPH - 0xCECB: 0x6042, //CJK UNIFIED IDEOGRAPH - 0xCECC: 0x605F, //CJK UNIFIED IDEOGRAPH - 0xCECD: 0x6024, //CJK UNIFIED IDEOGRAPH - 0xCECE: 0x6044, //CJK UNIFIED IDEOGRAPH - 0xCECF: 0x6058, //CJK UNIFIED IDEOGRAPH - 0xCED0: 0x6066, //CJK UNIFIED IDEOGRAPH - 0xCED1: 0x606E, //CJK UNIFIED IDEOGRAPH - 0xCED2: 0x6242, //CJK UNIFIED IDEOGRAPH - 0xCED3: 0x6243, //CJK UNIFIED IDEOGRAPH - 0xCED4: 0x62CF, //CJK UNIFIED IDEOGRAPH - 0xCED5: 0x630D, //CJK UNIFIED IDEOGRAPH - 0xCED6: 0x630B, //CJK UNIFIED IDEOGRAPH - 0xCED7: 0x62F5, //CJK UNIFIED IDEOGRAPH - 0xCED8: 0x630E, //CJK UNIFIED IDEOGRAPH - 0xCED9: 0x6303, //CJK UNIFIED IDEOGRAPH - 0xCEDA: 0x62EB, //CJK UNIFIED IDEOGRAPH - 0xCEDB: 0x62F9, //CJK UNIFIED IDEOGRAPH - 0xCEDC: 0x630F, //CJK UNIFIED IDEOGRAPH - 0xCEDD: 0x630C, //CJK UNIFIED IDEOGRAPH - 0xCEDE: 0x62F8, //CJK UNIFIED IDEOGRAPH - 0xCEDF: 0x62F6, //CJK UNIFIED IDEOGRAPH - 0xCEE0: 0x6300, //CJK UNIFIED IDEOGRAPH - 0xCEE1: 0x6313, //CJK UNIFIED IDEOGRAPH - 0xCEE2: 0x6314, //CJK UNIFIED IDEOGRAPH - 0xCEE3: 0x62FA, //CJK UNIFIED IDEOGRAPH - 0xCEE4: 0x6315, //CJK UNIFIED IDEOGRAPH - 0xCEE5: 0x62FB, //CJK UNIFIED IDEOGRAPH - 0xCEE6: 0x62F0, //CJK UNIFIED IDEOGRAPH - 0xCEE7: 0x6541, //CJK UNIFIED IDEOGRAPH - 0xCEE8: 0x6543, //CJK UNIFIED IDEOGRAPH - 0xCEE9: 0x65AA, //CJK UNIFIED IDEOGRAPH - 0xCEEA: 0x65BF, //CJK UNIFIED IDEOGRAPH - 0xCEEB: 0x6636, //CJK UNIFIED IDEOGRAPH - 0xCEEC: 0x6621, //CJK UNIFIED IDEOGRAPH - 0xCEED: 0x6632, //CJK UNIFIED IDEOGRAPH - 0xCEEE: 0x6635, //CJK UNIFIED IDEOGRAPH - 0xCEEF: 0x661C, //CJK UNIFIED IDEOGRAPH - 0xCEF0: 0x6626, //CJK UNIFIED IDEOGRAPH - 0xCEF1: 0x6622, //CJK UNIFIED IDEOGRAPH - 0xCEF2: 0x6633, //CJK UNIFIED IDEOGRAPH - 0xCEF3: 0x662B, //CJK UNIFIED IDEOGRAPH - 0xCEF4: 0x663A, //CJK UNIFIED IDEOGRAPH - 0xCEF5: 0x661D, //CJK UNIFIED IDEOGRAPH - 0xCEF6: 0x6634, //CJK UNIFIED IDEOGRAPH - 0xCEF7: 0x6639, //CJK UNIFIED IDEOGRAPH - 0xCEF8: 0x662E, //CJK UNIFIED IDEOGRAPH - 0xCEF9: 0x670F, //CJK UNIFIED IDEOGRAPH - 0xCEFA: 0x6710, //CJK UNIFIED IDEOGRAPH - 0xCEFB: 0x67C1, //CJK UNIFIED IDEOGRAPH - 0xCEFC: 0x67F2, //CJK UNIFIED IDEOGRAPH - 0xCEFD: 0x67C8, //CJK UNIFIED IDEOGRAPH - 0xCEFE: 0x67BA, //CJK UNIFIED IDEOGRAPH - 0xCF40: 0x67DC, //CJK UNIFIED IDEOGRAPH - 0xCF41: 0x67BB, //CJK UNIFIED IDEOGRAPH - 0xCF42: 0x67F8, //CJK UNIFIED IDEOGRAPH - 0xCF43: 0x67D8, //CJK UNIFIED IDEOGRAPH - 0xCF44: 0x67C0, //CJK UNIFIED IDEOGRAPH - 0xCF45: 0x67B7, //CJK UNIFIED IDEOGRAPH - 0xCF46: 0x67C5, //CJK UNIFIED IDEOGRAPH - 0xCF47: 0x67EB, //CJK UNIFIED IDEOGRAPH - 0xCF48: 0x67E4, //CJK UNIFIED IDEOGRAPH - 0xCF49: 0x67DF, //CJK UNIFIED IDEOGRAPH - 0xCF4A: 0x67B5, //CJK UNIFIED IDEOGRAPH - 0xCF4B: 0x67CD, //CJK UNIFIED IDEOGRAPH - 0xCF4C: 0x67B3, //CJK UNIFIED IDEOGRAPH - 0xCF4D: 0x67F7, //CJK UNIFIED IDEOGRAPH - 0xCF4E: 0x67F6, //CJK UNIFIED IDEOGRAPH - 0xCF4F: 0x67EE, //CJK UNIFIED IDEOGRAPH - 0xCF50: 0x67E3, //CJK UNIFIED IDEOGRAPH - 0xCF51: 0x67C2, //CJK UNIFIED IDEOGRAPH - 0xCF52: 0x67B9, //CJK UNIFIED IDEOGRAPH - 0xCF53: 0x67CE, //CJK UNIFIED IDEOGRAPH - 0xCF54: 0x67E7, //CJK UNIFIED IDEOGRAPH - 0xCF55: 0x67F0, //CJK UNIFIED IDEOGRAPH - 0xCF56: 0x67B2, //CJK UNIFIED IDEOGRAPH - 0xCF57: 0x67FC, //CJK UNIFIED IDEOGRAPH - 0xCF58: 0x67C6, //CJK UNIFIED IDEOGRAPH - 0xCF59: 0x67ED, //CJK UNIFIED IDEOGRAPH - 0xCF5A: 0x67CC, //CJK UNIFIED IDEOGRAPH - 0xCF5B: 0x67AE, //CJK UNIFIED IDEOGRAPH - 0xCF5C: 0x67E6, //CJK UNIFIED IDEOGRAPH - 0xCF5D: 0x67DB, //CJK UNIFIED IDEOGRAPH - 0xCF5E: 0x67FA, //CJK UNIFIED IDEOGRAPH - 0xCF5F: 0x67C9, //CJK UNIFIED IDEOGRAPH - 0xCF60: 0x67CA, //CJK UNIFIED IDEOGRAPH - 0xCF61: 0x67C3, //CJK UNIFIED IDEOGRAPH - 0xCF62: 0x67EA, //CJK UNIFIED IDEOGRAPH - 0xCF63: 0x67CB, //CJK UNIFIED IDEOGRAPH - 0xCF64: 0x6B28, //CJK UNIFIED IDEOGRAPH - 0xCF65: 0x6B82, //CJK UNIFIED IDEOGRAPH - 0xCF66: 0x6B84, //CJK UNIFIED IDEOGRAPH - 0xCF67: 0x6BB6, //CJK UNIFIED IDEOGRAPH - 0xCF68: 0x6BD6, //CJK UNIFIED IDEOGRAPH - 0xCF69: 0x6BD8, //CJK UNIFIED IDEOGRAPH - 0xCF6A: 0x6BE0, //CJK UNIFIED IDEOGRAPH - 0xCF6B: 0x6C20, //CJK UNIFIED IDEOGRAPH - 0xCF6C: 0x6C21, //CJK UNIFIED IDEOGRAPH - 0xCF6D: 0x6D28, //CJK UNIFIED IDEOGRAPH - 0xCF6E: 0x6D34, //CJK UNIFIED IDEOGRAPH - 0xCF6F: 0x6D2D, //CJK UNIFIED IDEOGRAPH - 0xCF70: 0x6D1F, //CJK UNIFIED IDEOGRAPH - 0xCF71: 0x6D3C, //CJK UNIFIED IDEOGRAPH - 0xCF72: 0x6D3F, //CJK UNIFIED IDEOGRAPH - 0xCF73: 0x6D12, //CJK UNIFIED IDEOGRAPH - 0xCF74: 0x6D0A, //CJK UNIFIED IDEOGRAPH - 0xCF75: 0x6CDA, //CJK UNIFIED IDEOGRAPH - 0xCF76: 0x6D33, //CJK UNIFIED IDEOGRAPH - 0xCF77: 0x6D04, //CJK UNIFIED IDEOGRAPH - 0xCF78: 0x6D19, //CJK UNIFIED IDEOGRAPH - 0xCF79: 0x6D3A, //CJK UNIFIED IDEOGRAPH - 0xCF7A: 0x6D1A, //CJK UNIFIED IDEOGRAPH - 0xCF7B: 0x6D11, //CJK UNIFIED IDEOGRAPH - 0xCF7C: 0x6D00, //CJK UNIFIED IDEOGRAPH - 0xCF7D: 0x6D1D, //CJK UNIFIED IDEOGRAPH - 0xCF7E: 0x6D42, //CJK UNIFIED IDEOGRAPH - 0xCFA1: 0x6D01, //CJK UNIFIED IDEOGRAPH - 0xCFA2: 0x6D18, //CJK UNIFIED IDEOGRAPH - 0xCFA3: 0x6D37, //CJK UNIFIED IDEOGRAPH - 0xCFA4: 0x6D03, //CJK UNIFIED IDEOGRAPH - 0xCFA5: 0x6D0F, //CJK UNIFIED IDEOGRAPH - 0xCFA6: 0x6D40, //CJK UNIFIED IDEOGRAPH - 0xCFA7: 0x6D07, //CJK UNIFIED IDEOGRAPH - 0xCFA8: 0x6D20, //CJK UNIFIED IDEOGRAPH - 0xCFA9: 0x6D2C, //CJK UNIFIED IDEOGRAPH - 0xCFAA: 0x6D08, //CJK UNIFIED IDEOGRAPH - 0xCFAB: 0x6D22, //CJK UNIFIED IDEOGRAPH - 0xCFAC: 0x6D09, //CJK UNIFIED IDEOGRAPH - 0xCFAD: 0x6D10, //CJK UNIFIED IDEOGRAPH - 0xCFAE: 0x70B7, //CJK UNIFIED IDEOGRAPH - 0xCFAF: 0x709F, //CJK UNIFIED IDEOGRAPH - 0xCFB0: 0x70BE, //CJK UNIFIED IDEOGRAPH - 0xCFB1: 0x70B1, //CJK UNIFIED IDEOGRAPH - 0xCFB2: 0x70B0, //CJK UNIFIED IDEOGRAPH - 0xCFB3: 0x70A1, //CJK UNIFIED IDEOGRAPH - 0xCFB4: 0x70B4, //CJK UNIFIED IDEOGRAPH - 0xCFB5: 0x70B5, //CJK UNIFIED IDEOGRAPH - 0xCFB6: 0x70A9, //CJK UNIFIED IDEOGRAPH - 0xCFB7: 0x7241, //CJK UNIFIED IDEOGRAPH - 0xCFB8: 0x7249, //CJK UNIFIED IDEOGRAPH - 0xCFB9: 0x724A, //CJK UNIFIED IDEOGRAPH - 0xCFBA: 0x726C, //CJK UNIFIED IDEOGRAPH - 0xCFBB: 0x7270, //CJK UNIFIED IDEOGRAPH - 0xCFBC: 0x7273, //CJK UNIFIED IDEOGRAPH - 0xCFBD: 0x726E, //CJK UNIFIED IDEOGRAPH - 0xCFBE: 0x72CA, //CJK UNIFIED IDEOGRAPH - 0xCFBF: 0x72E4, //CJK UNIFIED IDEOGRAPH - 0xCFC0: 0x72E8, //CJK UNIFIED IDEOGRAPH - 0xCFC1: 0x72EB, //CJK UNIFIED IDEOGRAPH - 0xCFC2: 0x72DF, //CJK UNIFIED IDEOGRAPH - 0xCFC3: 0x72EA, //CJK UNIFIED IDEOGRAPH - 0xCFC4: 0x72E6, //CJK UNIFIED IDEOGRAPH - 0xCFC5: 0x72E3, //CJK UNIFIED IDEOGRAPH - 0xCFC6: 0x7385, //CJK UNIFIED IDEOGRAPH - 0xCFC7: 0x73CC, //CJK UNIFIED IDEOGRAPH - 0xCFC8: 0x73C2, //CJK UNIFIED IDEOGRAPH - 0xCFC9: 0x73C8, //CJK UNIFIED IDEOGRAPH - 0xCFCA: 0x73C5, //CJK UNIFIED IDEOGRAPH - 0xCFCB: 0x73B9, //CJK UNIFIED IDEOGRAPH - 0xCFCC: 0x73B6, //CJK UNIFIED IDEOGRAPH - 0xCFCD: 0x73B5, //CJK UNIFIED IDEOGRAPH - 0xCFCE: 0x73B4, //CJK UNIFIED IDEOGRAPH - 0xCFCF: 0x73EB, //CJK UNIFIED IDEOGRAPH - 0xCFD0: 0x73BF, //CJK UNIFIED IDEOGRAPH - 0xCFD1: 0x73C7, //CJK UNIFIED IDEOGRAPH - 0xCFD2: 0x73BE, //CJK UNIFIED IDEOGRAPH - 0xCFD3: 0x73C3, //CJK UNIFIED IDEOGRAPH - 0xCFD4: 0x73C6, //CJK UNIFIED IDEOGRAPH - 0xCFD5: 0x73B8, //CJK UNIFIED IDEOGRAPH - 0xCFD6: 0x73CB, //CJK UNIFIED IDEOGRAPH - 0xCFD7: 0x74EC, //CJK UNIFIED IDEOGRAPH - 0xCFD8: 0x74EE, //CJK UNIFIED IDEOGRAPH - 0xCFD9: 0x752E, //CJK UNIFIED IDEOGRAPH - 0xCFDA: 0x7547, //CJK UNIFIED IDEOGRAPH - 0xCFDB: 0x7548, //CJK UNIFIED IDEOGRAPH - 0xCFDC: 0x75A7, //CJK UNIFIED IDEOGRAPH - 0xCFDD: 0x75AA, //CJK UNIFIED IDEOGRAPH - 0xCFDE: 0x7679, //CJK UNIFIED IDEOGRAPH - 0xCFDF: 0x76C4, //CJK UNIFIED IDEOGRAPH - 0xCFE0: 0x7708, //CJK UNIFIED IDEOGRAPH - 0xCFE1: 0x7703, //CJK UNIFIED IDEOGRAPH - 0xCFE2: 0x7704, //CJK UNIFIED IDEOGRAPH - 0xCFE3: 0x7705, //CJK UNIFIED IDEOGRAPH - 0xCFE4: 0x770A, //CJK UNIFIED IDEOGRAPH - 0xCFE5: 0x76F7, //CJK UNIFIED IDEOGRAPH - 0xCFE6: 0x76FB, //CJK UNIFIED IDEOGRAPH - 0xCFE7: 0x76FA, //CJK UNIFIED IDEOGRAPH - 0xCFE8: 0x77E7, //CJK UNIFIED IDEOGRAPH - 0xCFE9: 0x77E8, //CJK UNIFIED IDEOGRAPH - 0xCFEA: 0x7806, //CJK UNIFIED IDEOGRAPH - 0xCFEB: 0x7811, //CJK UNIFIED IDEOGRAPH - 0xCFEC: 0x7812, //CJK UNIFIED IDEOGRAPH - 0xCFED: 0x7805, //CJK UNIFIED IDEOGRAPH - 0xCFEE: 0x7810, //CJK UNIFIED IDEOGRAPH - 0xCFEF: 0x780F, //CJK UNIFIED IDEOGRAPH - 0xCFF0: 0x780E, //CJK UNIFIED IDEOGRAPH - 0xCFF1: 0x7809, //CJK UNIFIED IDEOGRAPH - 0xCFF2: 0x7803, //CJK UNIFIED IDEOGRAPH - 0xCFF3: 0x7813, //CJK UNIFIED IDEOGRAPH - 0xCFF4: 0x794A, //CJK UNIFIED IDEOGRAPH - 0xCFF5: 0x794C, //CJK UNIFIED IDEOGRAPH - 0xCFF6: 0x794B, //CJK UNIFIED IDEOGRAPH - 0xCFF7: 0x7945, //CJK UNIFIED IDEOGRAPH - 0xCFF8: 0x7944, //CJK UNIFIED IDEOGRAPH - 0xCFF9: 0x79D5, //CJK UNIFIED IDEOGRAPH - 0xCFFA: 0x79CD, //CJK UNIFIED IDEOGRAPH - 0xCFFB: 0x79CF, //CJK UNIFIED IDEOGRAPH - 0xCFFC: 0x79D6, //CJK UNIFIED IDEOGRAPH - 0xCFFD: 0x79CE, //CJK UNIFIED IDEOGRAPH - 0xCFFE: 0x7A80, //CJK UNIFIED IDEOGRAPH - 0xD040: 0x7A7E, //CJK UNIFIED IDEOGRAPH - 0xD041: 0x7AD1, //CJK UNIFIED IDEOGRAPH - 0xD042: 0x7B00, //CJK UNIFIED IDEOGRAPH - 0xD043: 0x7B01, //CJK UNIFIED IDEOGRAPH - 0xD044: 0x7C7A, //CJK UNIFIED IDEOGRAPH - 0xD045: 0x7C78, //CJK UNIFIED IDEOGRAPH - 0xD046: 0x7C79, //CJK UNIFIED IDEOGRAPH - 0xD047: 0x7C7F, //CJK UNIFIED IDEOGRAPH - 0xD048: 0x7C80, //CJK UNIFIED IDEOGRAPH - 0xD049: 0x7C81, //CJK UNIFIED IDEOGRAPH - 0xD04A: 0x7D03, //CJK UNIFIED IDEOGRAPH - 0xD04B: 0x7D08, //CJK UNIFIED IDEOGRAPH - 0xD04C: 0x7D01, //CJK UNIFIED IDEOGRAPH - 0xD04D: 0x7F58, //CJK UNIFIED IDEOGRAPH - 0xD04E: 0x7F91, //CJK UNIFIED IDEOGRAPH - 0xD04F: 0x7F8D, //CJK UNIFIED IDEOGRAPH - 0xD050: 0x7FBE, //CJK UNIFIED IDEOGRAPH - 0xD051: 0x8007, //CJK UNIFIED IDEOGRAPH - 0xD052: 0x800E, //CJK UNIFIED IDEOGRAPH - 0xD053: 0x800F, //CJK UNIFIED IDEOGRAPH - 0xD054: 0x8014, //CJK UNIFIED IDEOGRAPH - 0xD055: 0x8037, //CJK UNIFIED IDEOGRAPH - 0xD056: 0x80D8, //CJK UNIFIED IDEOGRAPH - 0xD057: 0x80C7, //CJK UNIFIED IDEOGRAPH - 0xD058: 0x80E0, //CJK UNIFIED IDEOGRAPH - 0xD059: 0x80D1, //CJK UNIFIED IDEOGRAPH - 0xD05A: 0x80C8, //CJK UNIFIED IDEOGRAPH - 0xD05B: 0x80C2, //CJK UNIFIED IDEOGRAPH - 0xD05C: 0x80D0, //CJK UNIFIED IDEOGRAPH - 0xD05D: 0x80C5, //CJK UNIFIED IDEOGRAPH - 0xD05E: 0x80E3, //CJK UNIFIED IDEOGRAPH - 0xD05F: 0x80D9, //CJK UNIFIED IDEOGRAPH - 0xD060: 0x80DC, //CJK UNIFIED IDEOGRAPH - 0xD061: 0x80CA, //CJK UNIFIED IDEOGRAPH - 0xD062: 0x80D5, //CJK UNIFIED IDEOGRAPH - 0xD063: 0x80C9, //CJK UNIFIED IDEOGRAPH - 0xD064: 0x80CF, //CJK UNIFIED IDEOGRAPH - 0xD065: 0x80D7, //CJK UNIFIED IDEOGRAPH - 0xD066: 0x80E6, //CJK UNIFIED IDEOGRAPH - 0xD067: 0x80CD, //CJK UNIFIED IDEOGRAPH - 0xD068: 0x81FF, //CJK UNIFIED IDEOGRAPH - 0xD069: 0x8221, //CJK UNIFIED IDEOGRAPH - 0xD06A: 0x8294, //CJK UNIFIED IDEOGRAPH - 0xD06B: 0x82D9, //CJK UNIFIED IDEOGRAPH - 0xD06C: 0x82FE, //CJK UNIFIED IDEOGRAPH - 0xD06D: 0x82F9, //CJK UNIFIED IDEOGRAPH - 0xD06E: 0x8307, //CJK UNIFIED IDEOGRAPH - 0xD06F: 0x82E8, //CJK UNIFIED IDEOGRAPH - 0xD070: 0x8300, //CJK UNIFIED IDEOGRAPH - 0xD071: 0x82D5, //CJK UNIFIED IDEOGRAPH - 0xD072: 0x833A, //CJK UNIFIED IDEOGRAPH - 0xD073: 0x82EB, //CJK UNIFIED IDEOGRAPH - 0xD074: 0x82D6, //CJK UNIFIED IDEOGRAPH - 0xD075: 0x82F4, //CJK UNIFIED IDEOGRAPH - 0xD076: 0x82EC, //CJK UNIFIED IDEOGRAPH - 0xD077: 0x82E1, //CJK UNIFIED IDEOGRAPH - 0xD078: 0x82F2, //CJK UNIFIED IDEOGRAPH - 0xD079: 0x82F5, //CJK UNIFIED IDEOGRAPH - 0xD07A: 0x830C, //CJK UNIFIED IDEOGRAPH - 0xD07B: 0x82FB, //CJK UNIFIED IDEOGRAPH - 0xD07C: 0x82F6, //CJK UNIFIED IDEOGRAPH - 0xD07D: 0x82F0, //CJK UNIFIED IDEOGRAPH - 0xD07E: 0x82EA, //CJK UNIFIED IDEOGRAPH - 0xD0A1: 0x82E4, //CJK UNIFIED IDEOGRAPH - 0xD0A2: 0x82E0, //CJK UNIFIED IDEOGRAPH - 0xD0A3: 0x82FA, //CJK UNIFIED IDEOGRAPH - 0xD0A4: 0x82F3, //CJK UNIFIED IDEOGRAPH - 0xD0A5: 0x82ED, //CJK UNIFIED IDEOGRAPH - 0xD0A6: 0x8677, //CJK UNIFIED IDEOGRAPH - 0xD0A7: 0x8674, //CJK UNIFIED IDEOGRAPH - 0xD0A8: 0x867C, //CJK UNIFIED IDEOGRAPH - 0xD0A9: 0x8673, //CJK UNIFIED IDEOGRAPH - 0xD0AA: 0x8841, //CJK UNIFIED IDEOGRAPH - 0xD0AB: 0x884E, //CJK UNIFIED IDEOGRAPH - 0xD0AC: 0x8867, //CJK UNIFIED IDEOGRAPH - 0xD0AD: 0x886A, //CJK UNIFIED IDEOGRAPH - 0xD0AE: 0x8869, //CJK UNIFIED IDEOGRAPH - 0xD0AF: 0x89D3, //CJK UNIFIED IDEOGRAPH - 0xD0B0: 0x8A04, //CJK UNIFIED IDEOGRAPH - 0xD0B1: 0x8A07, //CJK UNIFIED IDEOGRAPH - 0xD0B2: 0x8D72, //CJK UNIFIED IDEOGRAPH - 0xD0B3: 0x8FE3, //CJK UNIFIED IDEOGRAPH - 0xD0B4: 0x8FE1, //CJK UNIFIED IDEOGRAPH - 0xD0B5: 0x8FEE, //CJK UNIFIED IDEOGRAPH - 0xD0B6: 0x8FE0, //CJK UNIFIED IDEOGRAPH - 0xD0B7: 0x90F1, //CJK UNIFIED IDEOGRAPH - 0xD0B8: 0x90BD, //CJK UNIFIED IDEOGRAPH - 0xD0B9: 0x90BF, //CJK UNIFIED IDEOGRAPH - 0xD0BA: 0x90D5, //CJK UNIFIED IDEOGRAPH - 0xD0BB: 0x90C5, //CJK UNIFIED IDEOGRAPH - 0xD0BC: 0x90BE, //CJK UNIFIED IDEOGRAPH - 0xD0BD: 0x90C7, //CJK UNIFIED IDEOGRAPH - 0xD0BE: 0x90CB, //CJK UNIFIED IDEOGRAPH - 0xD0BF: 0x90C8, //CJK UNIFIED IDEOGRAPH - 0xD0C0: 0x91D4, //CJK UNIFIED IDEOGRAPH - 0xD0C1: 0x91D3, //CJK UNIFIED IDEOGRAPH - 0xD0C2: 0x9654, //CJK UNIFIED IDEOGRAPH - 0xD0C3: 0x964F, //CJK UNIFIED IDEOGRAPH - 0xD0C4: 0x9651, //CJK UNIFIED IDEOGRAPH - 0xD0C5: 0x9653, //CJK UNIFIED IDEOGRAPH - 0xD0C6: 0x964A, //CJK UNIFIED IDEOGRAPH - 0xD0C7: 0x964E, //CJK UNIFIED IDEOGRAPH - 0xD0C8: 0x501E, //CJK UNIFIED IDEOGRAPH - 0xD0C9: 0x5005, //CJK UNIFIED IDEOGRAPH - 0xD0CA: 0x5007, //CJK UNIFIED IDEOGRAPH - 0xD0CB: 0x5013, //CJK UNIFIED IDEOGRAPH - 0xD0CC: 0x5022, //CJK UNIFIED IDEOGRAPH - 0xD0CD: 0x5030, //CJK UNIFIED IDEOGRAPH - 0xD0CE: 0x501B, //CJK UNIFIED IDEOGRAPH - 0xD0CF: 0x4FF5, //CJK UNIFIED IDEOGRAPH - 0xD0D0: 0x4FF4, //CJK UNIFIED IDEOGRAPH - 0xD0D1: 0x5033, //CJK UNIFIED IDEOGRAPH - 0xD0D2: 0x5037, //CJK UNIFIED IDEOGRAPH - 0xD0D3: 0x502C, //CJK UNIFIED IDEOGRAPH - 0xD0D4: 0x4FF6, //CJK UNIFIED IDEOGRAPH - 0xD0D5: 0x4FF7, //CJK UNIFIED IDEOGRAPH - 0xD0D6: 0x5017, //CJK UNIFIED IDEOGRAPH - 0xD0D7: 0x501C, //CJK UNIFIED IDEOGRAPH - 0xD0D8: 0x5020, //CJK UNIFIED IDEOGRAPH - 0xD0D9: 0x5027, //CJK UNIFIED IDEOGRAPH - 0xD0DA: 0x5035, //CJK UNIFIED IDEOGRAPH - 0xD0DB: 0x502F, //CJK UNIFIED IDEOGRAPH - 0xD0DC: 0x5031, //CJK UNIFIED IDEOGRAPH - 0xD0DD: 0x500E, //CJK UNIFIED IDEOGRAPH - 0xD0DE: 0x515A, //CJK UNIFIED IDEOGRAPH - 0xD0DF: 0x5194, //CJK UNIFIED IDEOGRAPH - 0xD0E0: 0x5193, //CJK UNIFIED IDEOGRAPH - 0xD0E1: 0x51CA, //CJK UNIFIED IDEOGRAPH - 0xD0E2: 0x51C4, //CJK UNIFIED IDEOGRAPH - 0xD0E3: 0x51C5, //CJK UNIFIED IDEOGRAPH - 0xD0E4: 0x51C8, //CJK UNIFIED IDEOGRAPH - 0xD0E5: 0x51CE, //CJK UNIFIED IDEOGRAPH - 0xD0E6: 0x5261, //CJK UNIFIED IDEOGRAPH - 0xD0E7: 0x525A, //CJK UNIFIED IDEOGRAPH - 0xD0E8: 0x5252, //CJK UNIFIED IDEOGRAPH - 0xD0E9: 0x525E, //CJK UNIFIED IDEOGRAPH - 0xD0EA: 0x525F, //CJK UNIFIED IDEOGRAPH - 0xD0EB: 0x5255, //CJK UNIFIED IDEOGRAPH - 0xD0EC: 0x5262, //CJK UNIFIED IDEOGRAPH - 0xD0ED: 0x52CD, //CJK UNIFIED IDEOGRAPH - 0xD0EE: 0x530E, //CJK UNIFIED IDEOGRAPH - 0xD0EF: 0x539E, //CJK UNIFIED IDEOGRAPH - 0xD0F0: 0x5526, //CJK UNIFIED IDEOGRAPH - 0xD0F1: 0x54E2, //CJK UNIFIED IDEOGRAPH - 0xD0F2: 0x5517, //CJK UNIFIED IDEOGRAPH - 0xD0F3: 0x5512, //CJK UNIFIED IDEOGRAPH - 0xD0F4: 0x54E7, //CJK UNIFIED IDEOGRAPH - 0xD0F5: 0x54F3, //CJK UNIFIED IDEOGRAPH - 0xD0F6: 0x54E4, //CJK UNIFIED IDEOGRAPH - 0xD0F7: 0x551A, //CJK UNIFIED IDEOGRAPH - 0xD0F8: 0x54FF, //CJK UNIFIED IDEOGRAPH - 0xD0F9: 0x5504, //CJK UNIFIED IDEOGRAPH - 0xD0FA: 0x5508, //CJK UNIFIED IDEOGRAPH - 0xD0FB: 0x54EB, //CJK UNIFIED IDEOGRAPH - 0xD0FC: 0x5511, //CJK UNIFIED IDEOGRAPH - 0xD0FD: 0x5505, //CJK UNIFIED IDEOGRAPH - 0xD0FE: 0x54F1, //CJK UNIFIED IDEOGRAPH - 0xD140: 0x550A, //CJK UNIFIED IDEOGRAPH - 0xD141: 0x54FB, //CJK UNIFIED IDEOGRAPH - 0xD142: 0x54F7, //CJK UNIFIED IDEOGRAPH - 0xD143: 0x54F8, //CJK UNIFIED IDEOGRAPH - 0xD144: 0x54E0, //CJK UNIFIED IDEOGRAPH - 0xD145: 0x550E, //CJK UNIFIED IDEOGRAPH - 0xD146: 0x5503, //CJK UNIFIED IDEOGRAPH - 0xD147: 0x550B, //CJK UNIFIED IDEOGRAPH - 0xD148: 0x5701, //CJK UNIFIED IDEOGRAPH - 0xD149: 0x5702, //CJK UNIFIED IDEOGRAPH - 0xD14A: 0x57CC, //CJK UNIFIED IDEOGRAPH - 0xD14B: 0x5832, //CJK UNIFIED IDEOGRAPH - 0xD14C: 0x57D5, //CJK UNIFIED IDEOGRAPH - 0xD14D: 0x57D2, //CJK UNIFIED IDEOGRAPH - 0xD14E: 0x57BA, //CJK UNIFIED IDEOGRAPH - 0xD14F: 0x57C6, //CJK UNIFIED IDEOGRAPH - 0xD150: 0x57BD, //CJK UNIFIED IDEOGRAPH - 0xD151: 0x57BC, //CJK UNIFIED IDEOGRAPH - 0xD152: 0x57B8, //CJK UNIFIED IDEOGRAPH - 0xD153: 0x57B6, //CJK UNIFIED IDEOGRAPH - 0xD154: 0x57BF, //CJK UNIFIED IDEOGRAPH - 0xD155: 0x57C7, //CJK UNIFIED IDEOGRAPH - 0xD156: 0x57D0, //CJK UNIFIED IDEOGRAPH - 0xD157: 0x57B9, //CJK UNIFIED IDEOGRAPH - 0xD158: 0x57C1, //CJK UNIFIED IDEOGRAPH - 0xD159: 0x590E, //CJK UNIFIED IDEOGRAPH - 0xD15A: 0x594A, //CJK UNIFIED IDEOGRAPH - 0xD15B: 0x5A19, //CJK UNIFIED IDEOGRAPH - 0xD15C: 0x5A16, //CJK UNIFIED IDEOGRAPH - 0xD15D: 0x5A2D, //CJK UNIFIED IDEOGRAPH - 0xD15E: 0x5A2E, //CJK UNIFIED IDEOGRAPH - 0xD15F: 0x5A15, //CJK UNIFIED IDEOGRAPH - 0xD160: 0x5A0F, //CJK UNIFIED IDEOGRAPH - 0xD161: 0x5A17, //CJK UNIFIED IDEOGRAPH - 0xD162: 0x5A0A, //CJK UNIFIED IDEOGRAPH - 0xD163: 0x5A1E, //CJK UNIFIED IDEOGRAPH - 0xD164: 0x5A33, //CJK UNIFIED IDEOGRAPH - 0xD165: 0x5B6C, //CJK UNIFIED IDEOGRAPH - 0xD166: 0x5BA7, //CJK UNIFIED IDEOGRAPH - 0xD167: 0x5BAD, //CJK UNIFIED IDEOGRAPH - 0xD168: 0x5BAC, //CJK UNIFIED IDEOGRAPH - 0xD169: 0x5C03, //CJK UNIFIED IDEOGRAPH - 0xD16A: 0x5C56, //CJK UNIFIED IDEOGRAPH - 0xD16B: 0x5C54, //CJK UNIFIED IDEOGRAPH - 0xD16C: 0x5CEC, //CJK UNIFIED IDEOGRAPH - 0xD16D: 0x5CFF, //CJK UNIFIED IDEOGRAPH - 0xD16E: 0x5CEE, //CJK UNIFIED IDEOGRAPH - 0xD16F: 0x5CF1, //CJK UNIFIED IDEOGRAPH - 0xD170: 0x5CF7, //CJK UNIFIED IDEOGRAPH - 0xD171: 0x5D00, //CJK UNIFIED IDEOGRAPH - 0xD172: 0x5CF9, //CJK UNIFIED IDEOGRAPH - 0xD173: 0x5E29, //CJK UNIFIED IDEOGRAPH - 0xD174: 0x5E28, //CJK UNIFIED IDEOGRAPH - 0xD175: 0x5EA8, //CJK UNIFIED IDEOGRAPH - 0xD176: 0x5EAE, //CJK UNIFIED IDEOGRAPH - 0xD177: 0x5EAA, //CJK UNIFIED IDEOGRAPH - 0xD178: 0x5EAC, //CJK UNIFIED IDEOGRAPH - 0xD179: 0x5F33, //CJK UNIFIED IDEOGRAPH - 0xD17A: 0x5F30, //CJK UNIFIED IDEOGRAPH - 0xD17B: 0x5F67, //CJK UNIFIED IDEOGRAPH - 0xD17C: 0x605D, //CJK UNIFIED IDEOGRAPH - 0xD17D: 0x605A, //CJK UNIFIED IDEOGRAPH - 0xD17E: 0x6067, //CJK UNIFIED IDEOGRAPH - 0xD1A1: 0x6041, //CJK UNIFIED IDEOGRAPH - 0xD1A2: 0x60A2, //CJK UNIFIED IDEOGRAPH - 0xD1A3: 0x6088, //CJK UNIFIED IDEOGRAPH - 0xD1A4: 0x6080, //CJK UNIFIED IDEOGRAPH - 0xD1A5: 0x6092, //CJK UNIFIED IDEOGRAPH - 0xD1A6: 0x6081, //CJK UNIFIED IDEOGRAPH - 0xD1A7: 0x609D, //CJK UNIFIED IDEOGRAPH - 0xD1A8: 0x6083, //CJK UNIFIED IDEOGRAPH - 0xD1A9: 0x6095, //CJK UNIFIED IDEOGRAPH - 0xD1AA: 0x609B, //CJK UNIFIED IDEOGRAPH - 0xD1AB: 0x6097, //CJK UNIFIED IDEOGRAPH - 0xD1AC: 0x6087, //CJK UNIFIED IDEOGRAPH - 0xD1AD: 0x609C, //CJK UNIFIED IDEOGRAPH - 0xD1AE: 0x608E, //CJK UNIFIED IDEOGRAPH - 0xD1AF: 0x6219, //CJK UNIFIED IDEOGRAPH - 0xD1B0: 0x6246, //CJK UNIFIED IDEOGRAPH - 0xD1B1: 0x62F2, //CJK UNIFIED IDEOGRAPH - 0xD1B2: 0x6310, //CJK UNIFIED IDEOGRAPH - 0xD1B3: 0x6356, //CJK UNIFIED IDEOGRAPH - 0xD1B4: 0x632C, //CJK UNIFIED IDEOGRAPH - 0xD1B5: 0x6344, //CJK UNIFIED IDEOGRAPH - 0xD1B6: 0x6345, //CJK UNIFIED IDEOGRAPH - 0xD1B7: 0x6336, //CJK UNIFIED IDEOGRAPH - 0xD1B8: 0x6343, //CJK UNIFIED IDEOGRAPH - 0xD1B9: 0x63E4, //CJK UNIFIED IDEOGRAPH - 0xD1BA: 0x6339, //CJK UNIFIED IDEOGRAPH - 0xD1BB: 0x634B, //CJK UNIFIED IDEOGRAPH - 0xD1BC: 0x634A, //CJK UNIFIED IDEOGRAPH - 0xD1BD: 0x633C, //CJK UNIFIED IDEOGRAPH - 0xD1BE: 0x6329, //CJK UNIFIED IDEOGRAPH - 0xD1BF: 0x6341, //CJK UNIFIED IDEOGRAPH - 0xD1C0: 0x6334, //CJK UNIFIED IDEOGRAPH - 0xD1C1: 0x6358, //CJK UNIFIED IDEOGRAPH - 0xD1C2: 0x6354, //CJK UNIFIED IDEOGRAPH - 0xD1C3: 0x6359, //CJK UNIFIED IDEOGRAPH - 0xD1C4: 0x632D, //CJK UNIFIED IDEOGRAPH - 0xD1C5: 0x6347, //CJK UNIFIED IDEOGRAPH - 0xD1C6: 0x6333, //CJK UNIFIED IDEOGRAPH - 0xD1C7: 0x635A, //CJK UNIFIED IDEOGRAPH - 0xD1C8: 0x6351, //CJK UNIFIED IDEOGRAPH - 0xD1C9: 0x6338, //CJK UNIFIED IDEOGRAPH - 0xD1CA: 0x6357, //CJK UNIFIED IDEOGRAPH - 0xD1CB: 0x6340, //CJK UNIFIED IDEOGRAPH - 0xD1CC: 0x6348, //CJK UNIFIED IDEOGRAPH - 0xD1CD: 0x654A, //CJK UNIFIED IDEOGRAPH - 0xD1CE: 0x6546, //CJK UNIFIED IDEOGRAPH - 0xD1CF: 0x65C6, //CJK UNIFIED IDEOGRAPH - 0xD1D0: 0x65C3, //CJK UNIFIED IDEOGRAPH - 0xD1D1: 0x65C4, //CJK UNIFIED IDEOGRAPH - 0xD1D2: 0x65C2, //CJK UNIFIED IDEOGRAPH - 0xD1D3: 0x664A, //CJK UNIFIED IDEOGRAPH - 0xD1D4: 0x665F, //CJK UNIFIED IDEOGRAPH - 0xD1D5: 0x6647, //CJK UNIFIED IDEOGRAPH - 0xD1D6: 0x6651, //CJK UNIFIED IDEOGRAPH - 0xD1D7: 0x6712, //CJK UNIFIED IDEOGRAPH - 0xD1D8: 0x6713, //CJK UNIFIED IDEOGRAPH - 0xD1D9: 0x681F, //CJK UNIFIED IDEOGRAPH - 0xD1DA: 0x681A, //CJK UNIFIED IDEOGRAPH - 0xD1DB: 0x6849, //CJK UNIFIED IDEOGRAPH - 0xD1DC: 0x6832, //CJK UNIFIED IDEOGRAPH - 0xD1DD: 0x6833, //CJK UNIFIED IDEOGRAPH - 0xD1DE: 0x683B, //CJK UNIFIED IDEOGRAPH - 0xD1DF: 0x684B, //CJK UNIFIED IDEOGRAPH - 0xD1E0: 0x684F, //CJK UNIFIED IDEOGRAPH - 0xD1E1: 0x6816, //CJK UNIFIED IDEOGRAPH - 0xD1E2: 0x6831, //CJK UNIFIED IDEOGRAPH - 0xD1E3: 0x681C, //CJK UNIFIED IDEOGRAPH - 0xD1E4: 0x6835, //CJK UNIFIED IDEOGRAPH - 0xD1E5: 0x682B, //CJK UNIFIED IDEOGRAPH - 0xD1E6: 0x682D, //CJK UNIFIED IDEOGRAPH - 0xD1E7: 0x682F, //CJK UNIFIED IDEOGRAPH - 0xD1E8: 0x684E, //CJK UNIFIED IDEOGRAPH - 0xD1E9: 0x6844, //CJK UNIFIED IDEOGRAPH - 0xD1EA: 0x6834, //CJK UNIFIED IDEOGRAPH - 0xD1EB: 0x681D, //CJK UNIFIED IDEOGRAPH - 0xD1EC: 0x6812, //CJK UNIFIED IDEOGRAPH - 0xD1ED: 0x6814, //CJK UNIFIED IDEOGRAPH - 0xD1EE: 0x6826, //CJK UNIFIED IDEOGRAPH - 0xD1EF: 0x6828, //CJK UNIFIED IDEOGRAPH - 0xD1F0: 0x682E, //CJK UNIFIED IDEOGRAPH - 0xD1F1: 0x684D, //CJK UNIFIED IDEOGRAPH - 0xD1F2: 0x683A, //CJK UNIFIED IDEOGRAPH - 0xD1F3: 0x6825, //CJK UNIFIED IDEOGRAPH - 0xD1F4: 0x6820, //CJK UNIFIED IDEOGRAPH - 0xD1F5: 0x6B2C, //CJK UNIFIED IDEOGRAPH - 0xD1F6: 0x6B2F, //CJK UNIFIED IDEOGRAPH - 0xD1F7: 0x6B2D, //CJK UNIFIED IDEOGRAPH - 0xD1F8: 0x6B31, //CJK UNIFIED IDEOGRAPH - 0xD1F9: 0x6B34, //CJK UNIFIED IDEOGRAPH - 0xD1FA: 0x6B6D, //CJK UNIFIED IDEOGRAPH - 0xD1FB: 0x8082, //CJK UNIFIED IDEOGRAPH - 0xD1FC: 0x6B88, //CJK UNIFIED IDEOGRAPH - 0xD1FD: 0x6BE6, //CJK UNIFIED IDEOGRAPH - 0xD1FE: 0x6BE4, //CJK UNIFIED IDEOGRAPH - 0xD240: 0x6BE8, //CJK UNIFIED IDEOGRAPH - 0xD241: 0x6BE3, //CJK UNIFIED IDEOGRAPH - 0xD242: 0x6BE2, //CJK UNIFIED IDEOGRAPH - 0xD243: 0x6BE7, //CJK UNIFIED IDEOGRAPH - 0xD244: 0x6C25, //CJK UNIFIED IDEOGRAPH - 0xD245: 0x6D7A, //CJK UNIFIED IDEOGRAPH - 0xD246: 0x6D63, //CJK UNIFIED IDEOGRAPH - 0xD247: 0x6D64, //CJK UNIFIED IDEOGRAPH - 0xD248: 0x6D76, //CJK UNIFIED IDEOGRAPH - 0xD249: 0x6D0D, //CJK UNIFIED IDEOGRAPH - 0xD24A: 0x6D61, //CJK UNIFIED IDEOGRAPH - 0xD24B: 0x6D92, //CJK UNIFIED IDEOGRAPH - 0xD24C: 0x6D58, //CJK UNIFIED IDEOGRAPH - 0xD24D: 0x6D62, //CJK UNIFIED IDEOGRAPH - 0xD24E: 0x6D6D, //CJK UNIFIED IDEOGRAPH - 0xD24F: 0x6D6F, //CJK UNIFIED IDEOGRAPH - 0xD250: 0x6D91, //CJK UNIFIED IDEOGRAPH - 0xD251: 0x6D8D, //CJK UNIFIED IDEOGRAPH - 0xD252: 0x6DEF, //CJK UNIFIED IDEOGRAPH - 0xD253: 0x6D7F, //CJK UNIFIED IDEOGRAPH - 0xD254: 0x6D86, //CJK UNIFIED IDEOGRAPH - 0xD255: 0x6D5E, //CJK UNIFIED IDEOGRAPH - 0xD256: 0x6D67, //CJK UNIFIED IDEOGRAPH - 0xD257: 0x6D60, //CJK UNIFIED IDEOGRAPH - 0xD258: 0x6D97, //CJK UNIFIED IDEOGRAPH - 0xD259: 0x6D70, //CJK UNIFIED IDEOGRAPH - 0xD25A: 0x6D7C, //CJK UNIFIED IDEOGRAPH - 0xD25B: 0x6D5F, //CJK UNIFIED IDEOGRAPH - 0xD25C: 0x6D82, //CJK UNIFIED IDEOGRAPH - 0xD25D: 0x6D98, //CJK UNIFIED IDEOGRAPH - 0xD25E: 0x6D2F, //CJK UNIFIED IDEOGRAPH - 0xD25F: 0x6D68, //CJK UNIFIED IDEOGRAPH - 0xD260: 0x6D8B, //CJK UNIFIED IDEOGRAPH - 0xD261: 0x6D7E, //CJK UNIFIED IDEOGRAPH - 0xD262: 0x6D80, //CJK UNIFIED IDEOGRAPH - 0xD263: 0x6D84, //CJK UNIFIED IDEOGRAPH - 0xD264: 0x6D16, //CJK UNIFIED IDEOGRAPH - 0xD265: 0x6D83, //CJK UNIFIED IDEOGRAPH - 0xD266: 0x6D7B, //CJK UNIFIED IDEOGRAPH - 0xD267: 0x6D7D, //CJK UNIFIED IDEOGRAPH - 0xD268: 0x6D75, //CJK UNIFIED IDEOGRAPH - 0xD269: 0x6D90, //CJK UNIFIED IDEOGRAPH - 0xD26A: 0x70DC, //CJK UNIFIED IDEOGRAPH - 0xD26B: 0x70D3, //CJK UNIFIED IDEOGRAPH - 0xD26C: 0x70D1, //CJK UNIFIED IDEOGRAPH - 0xD26D: 0x70DD, //CJK UNIFIED IDEOGRAPH - 0xD26E: 0x70CB, //CJK UNIFIED IDEOGRAPH - 0xD26F: 0x7F39, //CJK UNIFIED IDEOGRAPH - 0xD270: 0x70E2, //CJK UNIFIED IDEOGRAPH - 0xD271: 0x70D7, //CJK UNIFIED IDEOGRAPH - 0xD272: 0x70D2, //CJK UNIFIED IDEOGRAPH - 0xD273: 0x70DE, //CJK UNIFIED IDEOGRAPH - 0xD274: 0x70E0, //CJK UNIFIED IDEOGRAPH - 0xD275: 0x70D4, //CJK UNIFIED IDEOGRAPH - 0xD276: 0x70CD, //CJK UNIFIED IDEOGRAPH - 0xD277: 0x70C5, //CJK UNIFIED IDEOGRAPH - 0xD278: 0x70C6, //CJK UNIFIED IDEOGRAPH - 0xD279: 0x70C7, //CJK UNIFIED IDEOGRAPH - 0xD27A: 0x70DA, //CJK UNIFIED IDEOGRAPH - 0xD27B: 0x70CE, //CJK UNIFIED IDEOGRAPH - 0xD27C: 0x70E1, //CJK UNIFIED IDEOGRAPH - 0xD27D: 0x7242, //CJK UNIFIED IDEOGRAPH - 0xD27E: 0x7278, //CJK UNIFIED IDEOGRAPH - 0xD2A1: 0x7277, //CJK UNIFIED IDEOGRAPH - 0xD2A2: 0x7276, //CJK UNIFIED IDEOGRAPH - 0xD2A3: 0x7300, //CJK UNIFIED IDEOGRAPH - 0xD2A4: 0x72FA, //CJK UNIFIED IDEOGRAPH - 0xD2A5: 0x72F4, //CJK UNIFIED IDEOGRAPH - 0xD2A6: 0x72FE, //CJK UNIFIED IDEOGRAPH - 0xD2A7: 0x72F6, //CJK UNIFIED IDEOGRAPH - 0xD2A8: 0x72F3, //CJK UNIFIED IDEOGRAPH - 0xD2A9: 0x72FB, //CJK UNIFIED IDEOGRAPH - 0xD2AA: 0x7301, //CJK UNIFIED IDEOGRAPH - 0xD2AB: 0x73D3, //CJK UNIFIED IDEOGRAPH - 0xD2AC: 0x73D9, //CJK UNIFIED IDEOGRAPH - 0xD2AD: 0x73E5, //CJK UNIFIED IDEOGRAPH - 0xD2AE: 0x73D6, //CJK UNIFIED IDEOGRAPH - 0xD2AF: 0x73BC, //CJK UNIFIED IDEOGRAPH - 0xD2B0: 0x73E7, //CJK UNIFIED IDEOGRAPH - 0xD2B1: 0x73E3, //CJK UNIFIED IDEOGRAPH - 0xD2B2: 0x73E9, //CJK UNIFIED IDEOGRAPH - 0xD2B3: 0x73DC, //CJK UNIFIED IDEOGRAPH - 0xD2B4: 0x73D2, //CJK UNIFIED IDEOGRAPH - 0xD2B5: 0x73DB, //CJK UNIFIED IDEOGRAPH - 0xD2B6: 0x73D4, //CJK UNIFIED IDEOGRAPH - 0xD2B7: 0x73DD, //CJK UNIFIED IDEOGRAPH - 0xD2B8: 0x73DA, //CJK UNIFIED IDEOGRAPH - 0xD2B9: 0x73D7, //CJK UNIFIED IDEOGRAPH - 0xD2BA: 0x73D8, //CJK UNIFIED IDEOGRAPH - 0xD2BB: 0x73E8, //CJK UNIFIED IDEOGRAPH - 0xD2BC: 0x74DE, //CJK UNIFIED IDEOGRAPH - 0xD2BD: 0x74DF, //CJK UNIFIED IDEOGRAPH - 0xD2BE: 0x74F4, //CJK UNIFIED IDEOGRAPH - 0xD2BF: 0x74F5, //CJK UNIFIED IDEOGRAPH - 0xD2C0: 0x7521, //CJK UNIFIED IDEOGRAPH - 0xD2C1: 0x755B, //CJK UNIFIED IDEOGRAPH - 0xD2C2: 0x755F, //CJK UNIFIED IDEOGRAPH - 0xD2C3: 0x75B0, //CJK UNIFIED IDEOGRAPH - 0xD2C4: 0x75C1, //CJK UNIFIED IDEOGRAPH - 0xD2C5: 0x75BB, //CJK UNIFIED IDEOGRAPH - 0xD2C6: 0x75C4, //CJK UNIFIED IDEOGRAPH - 0xD2C7: 0x75C0, //CJK UNIFIED IDEOGRAPH - 0xD2C8: 0x75BF, //CJK UNIFIED IDEOGRAPH - 0xD2C9: 0x75B6, //CJK UNIFIED IDEOGRAPH - 0xD2CA: 0x75BA, //CJK UNIFIED IDEOGRAPH - 0xD2CB: 0x768A, //CJK UNIFIED IDEOGRAPH - 0xD2CC: 0x76C9, //CJK UNIFIED IDEOGRAPH - 0xD2CD: 0x771D, //CJK UNIFIED IDEOGRAPH - 0xD2CE: 0x771B, //CJK UNIFIED IDEOGRAPH - 0xD2CF: 0x7710, //CJK UNIFIED IDEOGRAPH - 0xD2D0: 0x7713, //CJK UNIFIED IDEOGRAPH - 0xD2D1: 0x7712, //CJK UNIFIED IDEOGRAPH - 0xD2D2: 0x7723, //CJK UNIFIED IDEOGRAPH - 0xD2D3: 0x7711, //CJK UNIFIED IDEOGRAPH - 0xD2D4: 0x7715, //CJK UNIFIED IDEOGRAPH - 0xD2D5: 0x7719, //CJK UNIFIED IDEOGRAPH - 0xD2D6: 0x771A, //CJK UNIFIED IDEOGRAPH - 0xD2D7: 0x7722, //CJK UNIFIED IDEOGRAPH - 0xD2D8: 0x7727, //CJK UNIFIED IDEOGRAPH - 0xD2D9: 0x7823, //CJK UNIFIED IDEOGRAPH - 0xD2DA: 0x782C, //CJK UNIFIED IDEOGRAPH - 0xD2DB: 0x7822, //CJK UNIFIED IDEOGRAPH - 0xD2DC: 0x7835, //CJK UNIFIED IDEOGRAPH - 0xD2DD: 0x782F, //CJK UNIFIED IDEOGRAPH - 0xD2DE: 0x7828, //CJK UNIFIED IDEOGRAPH - 0xD2DF: 0x782E, //CJK UNIFIED IDEOGRAPH - 0xD2E0: 0x782B, //CJK UNIFIED IDEOGRAPH - 0xD2E1: 0x7821, //CJK UNIFIED IDEOGRAPH - 0xD2E2: 0x7829, //CJK UNIFIED IDEOGRAPH - 0xD2E3: 0x7833, //CJK UNIFIED IDEOGRAPH - 0xD2E4: 0x782A, //CJK UNIFIED IDEOGRAPH - 0xD2E5: 0x7831, //CJK UNIFIED IDEOGRAPH - 0xD2E6: 0x7954, //CJK UNIFIED IDEOGRAPH - 0xD2E7: 0x795B, //CJK UNIFIED IDEOGRAPH - 0xD2E8: 0x794F, //CJK UNIFIED IDEOGRAPH - 0xD2E9: 0x795C, //CJK UNIFIED IDEOGRAPH - 0xD2EA: 0x7953, //CJK UNIFIED IDEOGRAPH - 0xD2EB: 0x7952, //CJK UNIFIED IDEOGRAPH - 0xD2EC: 0x7951, //CJK UNIFIED IDEOGRAPH - 0xD2ED: 0x79EB, //CJK UNIFIED IDEOGRAPH - 0xD2EE: 0x79EC, //CJK UNIFIED IDEOGRAPH - 0xD2EF: 0x79E0, //CJK UNIFIED IDEOGRAPH - 0xD2F0: 0x79EE, //CJK UNIFIED IDEOGRAPH - 0xD2F1: 0x79ED, //CJK UNIFIED IDEOGRAPH - 0xD2F2: 0x79EA, //CJK UNIFIED IDEOGRAPH - 0xD2F3: 0x79DC, //CJK UNIFIED IDEOGRAPH - 0xD2F4: 0x79DE, //CJK UNIFIED IDEOGRAPH - 0xD2F5: 0x79DD, //CJK UNIFIED IDEOGRAPH - 0xD2F6: 0x7A86, //CJK UNIFIED IDEOGRAPH - 0xD2F7: 0x7A89, //CJK UNIFIED IDEOGRAPH - 0xD2F8: 0x7A85, //CJK UNIFIED IDEOGRAPH - 0xD2F9: 0x7A8B, //CJK UNIFIED IDEOGRAPH - 0xD2FA: 0x7A8C, //CJK UNIFIED IDEOGRAPH - 0xD2FB: 0x7A8A, //CJK UNIFIED IDEOGRAPH - 0xD2FC: 0x7A87, //CJK UNIFIED IDEOGRAPH - 0xD2FD: 0x7AD8, //CJK UNIFIED IDEOGRAPH - 0xD2FE: 0x7B10, //CJK UNIFIED IDEOGRAPH - 0xD340: 0x7B04, //CJK UNIFIED IDEOGRAPH - 0xD341: 0x7B13, //CJK UNIFIED IDEOGRAPH - 0xD342: 0x7B05, //CJK UNIFIED IDEOGRAPH - 0xD343: 0x7B0F, //CJK UNIFIED IDEOGRAPH - 0xD344: 0x7B08, //CJK UNIFIED IDEOGRAPH - 0xD345: 0x7B0A, //CJK UNIFIED IDEOGRAPH - 0xD346: 0x7B0E, //CJK UNIFIED IDEOGRAPH - 0xD347: 0x7B09, //CJK UNIFIED IDEOGRAPH - 0xD348: 0x7B12, //CJK UNIFIED IDEOGRAPH - 0xD349: 0x7C84, //CJK UNIFIED IDEOGRAPH - 0xD34A: 0x7C91, //CJK UNIFIED IDEOGRAPH - 0xD34B: 0x7C8A, //CJK UNIFIED IDEOGRAPH - 0xD34C: 0x7C8C, //CJK UNIFIED IDEOGRAPH - 0xD34D: 0x7C88, //CJK UNIFIED IDEOGRAPH - 0xD34E: 0x7C8D, //CJK UNIFIED IDEOGRAPH - 0xD34F: 0x7C85, //CJK UNIFIED IDEOGRAPH - 0xD350: 0x7D1E, //CJK UNIFIED IDEOGRAPH - 0xD351: 0x7D1D, //CJK UNIFIED IDEOGRAPH - 0xD352: 0x7D11, //CJK UNIFIED IDEOGRAPH - 0xD353: 0x7D0E, //CJK UNIFIED IDEOGRAPH - 0xD354: 0x7D18, //CJK UNIFIED IDEOGRAPH - 0xD355: 0x7D16, //CJK UNIFIED IDEOGRAPH - 0xD356: 0x7D13, //CJK UNIFIED IDEOGRAPH - 0xD357: 0x7D1F, //CJK UNIFIED IDEOGRAPH - 0xD358: 0x7D12, //CJK UNIFIED IDEOGRAPH - 0xD359: 0x7D0F, //CJK UNIFIED IDEOGRAPH - 0xD35A: 0x7D0C, //CJK UNIFIED IDEOGRAPH - 0xD35B: 0x7F5C, //CJK UNIFIED IDEOGRAPH - 0xD35C: 0x7F61, //CJK UNIFIED IDEOGRAPH - 0xD35D: 0x7F5E, //CJK UNIFIED IDEOGRAPH - 0xD35E: 0x7F60, //CJK UNIFIED IDEOGRAPH - 0xD35F: 0x7F5D, //CJK UNIFIED IDEOGRAPH - 0xD360: 0x7F5B, //CJK UNIFIED IDEOGRAPH - 0xD361: 0x7F96, //CJK UNIFIED IDEOGRAPH - 0xD362: 0x7F92, //CJK UNIFIED IDEOGRAPH - 0xD363: 0x7FC3, //CJK UNIFIED IDEOGRAPH - 0xD364: 0x7FC2, //CJK UNIFIED IDEOGRAPH - 0xD365: 0x7FC0, //CJK UNIFIED IDEOGRAPH - 0xD366: 0x8016, //CJK UNIFIED IDEOGRAPH - 0xD367: 0x803E, //CJK UNIFIED IDEOGRAPH - 0xD368: 0x8039, //CJK UNIFIED IDEOGRAPH - 0xD369: 0x80FA, //CJK UNIFIED IDEOGRAPH - 0xD36A: 0x80F2, //CJK UNIFIED IDEOGRAPH - 0xD36B: 0x80F9, //CJK UNIFIED IDEOGRAPH - 0xD36C: 0x80F5, //CJK UNIFIED IDEOGRAPH - 0xD36D: 0x8101, //CJK UNIFIED IDEOGRAPH - 0xD36E: 0x80FB, //CJK UNIFIED IDEOGRAPH - 0xD36F: 0x8100, //CJK UNIFIED IDEOGRAPH - 0xD370: 0x8201, //CJK UNIFIED IDEOGRAPH - 0xD371: 0x822F, //CJK UNIFIED IDEOGRAPH - 0xD372: 0x8225, //CJK UNIFIED IDEOGRAPH - 0xD373: 0x8333, //CJK UNIFIED IDEOGRAPH - 0xD374: 0x832D, //CJK UNIFIED IDEOGRAPH - 0xD375: 0x8344, //CJK UNIFIED IDEOGRAPH - 0xD376: 0x8319, //CJK UNIFIED IDEOGRAPH - 0xD377: 0x8351, //CJK UNIFIED IDEOGRAPH - 0xD378: 0x8325, //CJK UNIFIED IDEOGRAPH - 0xD379: 0x8356, //CJK UNIFIED IDEOGRAPH - 0xD37A: 0x833F, //CJK UNIFIED IDEOGRAPH - 0xD37B: 0x8341, //CJK UNIFIED IDEOGRAPH - 0xD37C: 0x8326, //CJK UNIFIED IDEOGRAPH - 0xD37D: 0x831C, //CJK UNIFIED IDEOGRAPH - 0xD37E: 0x8322, //CJK UNIFIED IDEOGRAPH - 0xD3A1: 0x8342, //CJK UNIFIED IDEOGRAPH - 0xD3A2: 0x834E, //CJK UNIFIED IDEOGRAPH - 0xD3A3: 0x831B, //CJK UNIFIED IDEOGRAPH - 0xD3A4: 0x832A, //CJK UNIFIED IDEOGRAPH - 0xD3A5: 0x8308, //CJK UNIFIED IDEOGRAPH - 0xD3A6: 0x833C, //CJK UNIFIED IDEOGRAPH - 0xD3A7: 0x834D, //CJK UNIFIED IDEOGRAPH - 0xD3A8: 0x8316, //CJK UNIFIED IDEOGRAPH - 0xD3A9: 0x8324, //CJK UNIFIED IDEOGRAPH - 0xD3AA: 0x8320, //CJK UNIFIED IDEOGRAPH - 0xD3AB: 0x8337, //CJK UNIFIED IDEOGRAPH - 0xD3AC: 0x832F, //CJK UNIFIED IDEOGRAPH - 0xD3AD: 0x8329, //CJK UNIFIED IDEOGRAPH - 0xD3AE: 0x8347, //CJK UNIFIED IDEOGRAPH - 0xD3AF: 0x8345, //CJK UNIFIED IDEOGRAPH - 0xD3B0: 0x834C, //CJK UNIFIED IDEOGRAPH - 0xD3B1: 0x8353, //CJK UNIFIED IDEOGRAPH - 0xD3B2: 0x831E, //CJK UNIFIED IDEOGRAPH - 0xD3B3: 0x832C, //CJK UNIFIED IDEOGRAPH - 0xD3B4: 0x834B, //CJK UNIFIED IDEOGRAPH - 0xD3B5: 0x8327, //CJK UNIFIED IDEOGRAPH - 0xD3B6: 0x8348, //CJK UNIFIED IDEOGRAPH - 0xD3B7: 0x8653, //CJK UNIFIED IDEOGRAPH - 0xD3B8: 0x8652, //CJK UNIFIED IDEOGRAPH - 0xD3B9: 0x86A2, //CJK UNIFIED IDEOGRAPH - 0xD3BA: 0x86A8, //CJK UNIFIED IDEOGRAPH - 0xD3BB: 0x8696, //CJK UNIFIED IDEOGRAPH - 0xD3BC: 0x868D, //CJK UNIFIED IDEOGRAPH - 0xD3BD: 0x8691, //CJK UNIFIED IDEOGRAPH - 0xD3BE: 0x869E, //CJK UNIFIED IDEOGRAPH - 0xD3BF: 0x8687, //CJK UNIFIED IDEOGRAPH - 0xD3C0: 0x8697, //CJK UNIFIED IDEOGRAPH - 0xD3C1: 0x8686, //CJK UNIFIED IDEOGRAPH - 0xD3C2: 0x868B, //CJK UNIFIED IDEOGRAPH - 0xD3C3: 0x869A, //CJK UNIFIED IDEOGRAPH - 0xD3C4: 0x8685, //CJK UNIFIED IDEOGRAPH - 0xD3C5: 0x86A5, //CJK UNIFIED IDEOGRAPH - 0xD3C6: 0x8699, //CJK UNIFIED IDEOGRAPH - 0xD3C7: 0x86A1, //CJK UNIFIED IDEOGRAPH - 0xD3C8: 0x86A7, //CJK UNIFIED IDEOGRAPH - 0xD3C9: 0x8695, //CJK UNIFIED IDEOGRAPH - 0xD3CA: 0x8698, //CJK UNIFIED IDEOGRAPH - 0xD3CB: 0x868E, //CJK UNIFIED IDEOGRAPH - 0xD3CC: 0x869D, //CJK UNIFIED IDEOGRAPH - 0xD3CD: 0x8690, //CJK UNIFIED IDEOGRAPH - 0xD3CE: 0x8694, //CJK UNIFIED IDEOGRAPH - 0xD3CF: 0x8843, //CJK UNIFIED IDEOGRAPH - 0xD3D0: 0x8844, //CJK UNIFIED IDEOGRAPH - 0xD3D1: 0x886D, //CJK UNIFIED IDEOGRAPH - 0xD3D2: 0x8875, //CJK UNIFIED IDEOGRAPH - 0xD3D3: 0x8876, //CJK UNIFIED IDEOGRAPH - 0xD3D4: 0x8872, //CJK UNIFIED IDEOGRAPH - 0xD3D5: 0x8880, //CJK UNIFIED IDEOGRAPH - 0xD3D6: 0x8871, //CJK UNIFIED IDEOGRAPH - 0xD3D7: 0x887F, //CJK UNIFIED IDEOGRAPH - 0xD3D8: 0x886F, //CJK UNIFIED IDEOGRAPH - 0xD3D9: 0x8883, //CJK UNIFIED IDEOGRAPH - 0xD3DA: 0x887E, //CJK UNIFIED IDEOGRAPH - 0xD3DB: 0x8874, //CJK UNIFIED IDEOGRAPH - 0xD3DC: 0x887C, //CJK UNIFIED IDEOGRAPH - 0xD3DD: 0x8A12, //CJK UNIFIED IDEOGRAPH - 0xD3DE: 0x8C47, //CJK UNIFIED IDEOGRAPH - 0xD3DF: 0x8C57, //CJK UNIFIED IDEOGRAPH - 0xD3E0: 0x8C7B, //CJK UNIFIED IDEOGRAPH - 0xD3E1: 0x8CA4, //CJK UNIFIED IDEOGRAPH - 0xD3E2: 0x8CA3, //CJK UNIFIED IDEOGRAPH - 0xD3E3: 0x8D76, //CJK UNIFIED IDEOGRAPH - 0xD3E4: 0x8D78, //CJK UNIFIED IDEOGRAPH - 0xD3E5: 0x8DB5, //CJK UNIFIED IDEOGRAPH - 0xD3E6: 0x8DB7, //CJK UNIFIED IDEOGRAPH - 0xD3E7: 0x8DB6, //CJK UNIFIED IDEOGRAPH - 0xD3E8: 0x8ED1, //CJK UNIFIED IDEOGRAPH - 0xD3E9: 0x8ED3, //CJK UNIFIED IDEOGRAPH - 0xD3EA: 0x8FFE, //CJK UNIFIED IDEOGRAPH - 0xD3EB: 0x8FF5, //CJK UNIFIED IDEOGRAPH - 0xD3EC: 0x9002, //CJK UNIFIED IDEOGRAPH - 0xD3ED: 0x8FFF, //CJK UNIFIED IDEOGRAPH - 0xD3EE: 0x8FFB, //CJK UNIFIED IDEOGRAPH - 0xD3EF: 0x9004, //CJK UNIFIED IDEOGRAPH - 0xD3F0: 0x8FFC, //CJK UNIFIED IDEOGRAPH - 0xD3F1: 0x8FF6, //CJK UNIFIED IDEOGRAPH - 0xD3F2: 0x90D6, //CJK UNIFIED IDEOGRAPH - 0xD3F3: 0x90E0, //CJK UNIFIED IDEOGRAPH - 0xD3F4: 0x90D9, //CJK UNIFIED IDEOGRAPH - 0xD3F5: 0x90DA, //CJK UNIFIED IDEOGRAPH - 0xD3F6: 0x90E3, //CJK UNIFIED IDEOGRAPH - 0xD3F7: 0x90DF, //CJK UNIFIED IDEOGRAPH - 0xD3F8: 0x90E5, //CJK UNIFIED IDEOGRAPH - 0xD3F9: 0x90D8, //CJK UNIFIED IDEOGRAPH - 0xD3FA: 0x90DB, //CJK UNIFIED IDEOGRAPH - 0xD3FB: 0x90D7, //CJK UNIFIED IDEOGRAPH - 0xD3FC: 0x90DC, //CJK UNIFIED IDEOGRAPH - 0xD3FD: 0x90E4, //CJK UNIFIED IDEOGRAPH - 0xD3FE: 0x9150, //CJK UNIFIED IDEOGRAPH - 0xD440: 0x914E, //CJK UNIFIED IDEOGRAPH - 0xD441: 0x914F, //CJK UNIFIED IDEOGRAPH - 0xD442: 0x91D5, //CJK UNIFIED IDEOGRAPH - 0xD443: 0x91E2, //CJK UNIFIED IDEOGRAPH - 0xD444: 0x91DA, //CJK UNIFIED IDEOGRAPH - 0xD445: 0x965C, //CJK UNIFIED IDEOGRAPH - 0xD446: 0x965F, //CJK UNIFIED IDEOGRAPH - 0xD447: 0x96BC, //CJK UNIFIED IDEOGRAPH - 0xD448: 0x98E3, //CJK UNIFIED IDEOGRAPH - 0xD449: 0x9ADF, //CJK UNIFIED IDEOGRAPH - 0xD44A: 0x9B2F, //CJK UNIFIED IDEOGRAPH - 0xD44B: 0x4E7F, //CJK UNIFIED IDEOGRAPH - 0xD44C: 0x5070, //CJK UNIFIED IDEOGRAPH - 0xD44D: 0x506A, //CJK UNIFIED IDEOGRAPH - 0xD44E: 0x5061, //CJK UNIFIED IDEOGRAPH - 0xD44F: 0x505E, //CJK UNIFIED IDEOGRAPH - 0xD450: 0x5060, //CJK UNIFIED IDEOGRAPH - 0xD451: 0x5053, //CJK UNIFIED IDEOGRAPH - 0xD452: 0x504B, //CJK UNIFIED IDEOGRAPH - 0xD453: 0x505D, //CJK UNIFIED IDEOGRAPH - 0xD454: 0x5072, //CJK UNIFIED IDEOGRAPH - 0xD455: 0x5048, //CJK UNIFIED IDEOGRAPH - 0xD456: 0x504D, //CJK UNIFIED IDEOGRAPH - 0xD457: 0x5041, //CJK UNIFIED IDEOGRAPH - 0xD458: 0x505B, //CJK UNIFIED IDEOGRAPH - 0xD459: 0x504A, //CJK UNIFIED IDEOGRAPH - 0xD45A: 0x5062, //CJK UNIFIED IDEOGRAPH - 0xD45B: 0x5015, //CJK UNIFIED IDEOGRAPH - 0xD45C: 0x5045, //CJK UNIFIED IDEOGRAPH - 0xD45D: 0x505F, //CJK UNIFIED IDEOGRAPH - 0xD45E: 0x5069, //CJK UNIFIED IDEOGRAPH - 0xD45F: 0x506B, //CJK UNIFIED IDEOGRAPH - 0xD460: 0x5063, //CJK UNIFIED IDEOGRAPH - 0xD461: 0x5064, //CJK UNIFIED IDEOGRAPH - 0xD462: 0x5046, //CJK UNIFIED IDEOGRAPH - 0xD463: 0x5040, //CJK UNIFIED IDEOGRAPH - 0xD464: 0x506E, //CJK UNIFIED IDEOGRAPH - 0xD465: 0x5073, //CJK UNIFIED IDEOGRAPH - 0xD466: 0x5057, //CJK UNIFIED IDEOGRAPH - 0xD467: 0x5051, //CJK UNIFIED IDEOGRAPH - 0xD468: 0x51D0, //CJK UNIFIED IDEOGRAPH - 0xD469: 0x526B, //CJK UNIFIED IDEOGRAPH - 0xD46A: 0x526D, //CJK UNIFIED IDEOGRAPH - 0xD46B: 0x526C, //CJK UNIFIED IDEOGRAPH - 0xD46C: 0x526E, //CJK UNIFIED IDEOGRAPH - 0xD46D: 0x52D6, //CJK UNIFIED IDEOGRAPH - 0xD46E: 0x52D3, //CJK UNIFIED IDEOGRAPH - 0xD46F: 0x532D, //CJK UNIFIED IDEOGRAPH - 0xD470: 0x539C, //CJK UNIFIED IDEOGRAPH - 0xD471: 0x5575, //CJK UNIFIED IDEOGRAPH - 0xD472: 0x5576, //CJK UNIFIED IDEOGRAPH - 0xD473: 0x553C, //CJK UNIFIED IDEOGRAPH - 0xD474: 0x554D, //CJK UNIFIED IDEOGRAPH - 0xD475: 0x5550, //CJK UNIFIED IDEOGRAPH - 0xD476: 0x5534, //CJK UNIFIED IDEOGRAPH - 0xD477: 0x552A, //CJK UNIFIED IDEOGRAPH - 0xD478: 0x5551, //CJK UNIFIED IDEOGRAPH - 0xD479: 0x5562, //CJK UNIFIED IDEOGRAPH - 0xD47A: 0x5536, //CJK UNIFIED IDEOGRAPH - 0xD47B: 0x5535, //CJK UNIFIED IDEOGRAPH - 0xD47C: 0x5530, //CJK UNIFIED IDEOGRAPH - 0xD47D: 0x5552, //CJK UNIFIED IDEOGRAPH - 0xD47E: 0x5545, //CJK UNIFIED IDEOGRAPH - 0xD4A1: 0x550C, //CJK UNIFIED IDEOGRAPH - 0xD4A2: 0x5532, //CJK UNIFIED IDEOGRAPH - 0xD4A3: 0x5565, //CJK UNIFIED IDEOGRAPH - 0xD4A4: 0x554E, //CJK UNIFIED IDEOGRAPH - 0xD4A5: 0x5539, //CJK UNIFIED IDEOGRAPH - 0xD4A6: 0x5548, //CJK UNIFIED IDEOGRAPH - 0xD4A7: 0x552D, //CJK UNIFIED IDEOGRAPH - 0xD4A8: 0x553B, //CJK UNIFIED IDEOGRAPH - 0xD4A9: 0x5540, //CJK UNIFIED IDEOGRAPH - 0xD4AA: 0x554B, //CJK UNIFIED IDEOGRAPH - 0xD4AB: 0x570A, //CJK UNIFIED IDEOGRAPH - 0xD4AC: 0x5707, //CJK UNIFIED IDEOGRAPH - 0xD4AD: 0x57FB, //CJK UNIFIED IDEOGRAPH - 0xD4AE: 0x5814, //CJK UNIFIED IDEOGRAPH - 0xD4AF: 0x57E2, //CJK UNIFIED IDEOGRAPH - 0xD4B0: 0x57F6, //CJK UNIFIED IDEOGRAPH - 0xD4B1: 0x57DC, //CJK UNIFIED IDEOGRAPH - 0xD4B2: 0x57F4, //CJK UNIFIED IDEOGRAPH - 0xD4B3: 0x5800, //CJK UNIFIED IDEOGRAPH - 0xD4B4: 0x57ED, //CJK UNIFIED IDEOGRAPH - 0xD4B5: 0x57FD, //CJK UNIFIED IDEOGRAPH - 0xD4B6: 0x5808, //CJK UNIFIED IDEOGRAPH - 0xD4B7: 0x57F8, //CJK UNIFIED IDEOGRAPH - 0xD4B8: 0x580B, //CJK UNIFIED IDEOGRAPH - 0xD4B9: 0x57F3, //CJK UNIFIED IDEOGRAPH - 0xD4BA: 0x57CF, //CJK UNIFIED IDEOGRAPH - 0xD4BB: 0x5807, //CJK UNIFIED IDEOGRAPH - 0xD4BC: 0x57EE, //CJK UNIFIED IDEOGRAPH - 0xD4BD: 0x57E3, //CJK UNIFIED IDEOGRAPH - 0xD4BE: 0x57F2, //CJK UNIFIED IDEOGRAPH - 0xD4BF: 0x57E5, //CJK UNIFIED IDEOGRAPH - 0xD4C0: 0x57EC, //CJK UNIFIED IDEOGRAPH - 0xD4C1: 0x57E1, //CJK UNIFIED IDEOGRAPH - 0xD4C2: 0x580E, //CJK UNIFIED IDEOGRAPH - 0xD4C3: 0x57FC, //CJK UNIFIED IDEOGRAPH - 0xD4C4: 0x5810, //CJK UNIFIED IDEOGRAPH - 0xD4C5: 0x57E7, //CJK UNIFIED IDEOGRAPH - 0xD4C6: 0x5801, //CJK UNIFIED IDEOGRAPH - 0xD4C7: 0x580C, //CJK UNIFIED IDEOGRAPH - 0xD4C8: 0x57F1, //CJK UNIFIED IDEOGRAPH - 0xD4C9: 0x57E9, //CJK UNIFIED IDEOGRAPH - 0xD4CA: 0x57F0, //CJK UNIFIED IDEOGRAPH - 0xD4CB: 0x580D, //CJK UNIFIED IDEOGRAPH - 0xD4CC: 0x5804, //CJK UNIFIED IDEOGRAPH - 0xD4CD: 0x595C, //CJK UNIFIED IDEOGRAPH - 0xD4CE: 0x5A60, //CJK UNIFIED IDEOGRAPH - 0xD4CF: 0x5A58, //CJK UNIFIED IDEOGRAPH - 0xD4D0: 0x5A55, //CJK UNIFIED IDEOGRAPH - 0xD4D1: 0x5A67, //CJK UNIFIED IDEOGRAPH - 0xD4D2: 0x5A5E, //CJK UNIFIED IDEOGRAPH - 0xD4D3: 0x5A38, //CJK UNIFIED IDEOGRAPH - 0xD4D4: 0x5A35, //CJK UNIFIED IDEOGRAPH - 0xD4D5: 0x5A6D, //CJK UNIFIED IDEOGRAPH - 0xD4D6: 0x5A50, //CJK UNIFIED IDEOGRAPH - 0xD4D7: 0x5A5F, //CJK UNIFIED IDEOGRAPH - 0xD4D8: 0x5A65, //CJK UNIFIED IDEOGRAPH - 0xD4D9: 0x5A6C, //CJK UNIFIED IDEOGRAPH - 0xD4DA: 0x5A53, //CJK UNIFIED IDEOGRAPH - 0xD4DB: 0x5A64, //CJK UNIFIED IDEOGRAPH - 0xD4DC: 0x5A57, //CJK UNIFIED IDEOGRAPH - 0xD4DD: 0x5A43, //CJK UNIFIED IDEOGRAPH - 0xD4DE: 0x5A5D, //CJK UNIFIED IDEOGRAPH - 0xD4DF: 0x5A52, //CJK UNIFIED IDEOGRAPH - 0xD4E0: 0x5A44, //CJK UNIFIED IDEOGRAPH - 0xD4E1: 0x5A5B, //CJK UNIFIED IDEOGRAPH - 0xD4E2: 0x5A48, //CJK UNIFIED IDEOGRAPH - 0xD4E3: 0x5A8E, //CJK UNIFIED IDEOGRAPH - 0xD4E4: 0x5A3E, //CJK UNIFIED IDEOGRAPH - 0xD4E5: 0x5A4D, //CJK UNIFIED IDEOGRAPH - 0xD4E6: 0x5A39, //CJK UNIFIED IDEOGRAPH - 0xD4E7: 0x5A4C, //CJK UNIFIED IDEOGRAPH - 0xD4E8: 0x5A70, //CJK UNIFIED IDEOGRAPH - 0xD4E9: 0x5A69, //CJK UNIFIED IDEOGRAPH - 0xD4EA: 0x5A47, //CJK UNIFIED IDEOGRAPH - 0xD4EB: 0x5A51, //CJK UNIFIED IDEOGRAPH - 0xD4EC: 0x5A56, //CJK UNIFIED IDEOGRAPH - 0xD4ED: 0x5A42, //CJK UNIFIED IDEOGRAPH - 0xD4EE: 0x5A5C, //CJK UNIFIED IDEOGRAPH - 0xD4EF: 0x5B72, //CJK UNIFIED IDEOGRAPH - 0xD4F0: 0x5B6E, //CJK UNIFIED IDEOGRAPH - 0xD4F1: 0x5BC1, //CJK UNIFIED IDEOGRAPH - 0xD4F2: 0x5BC0, //CJK UNIFIED IDEOGRAPH - 0xD4F3: 0x5C59, //CJK UNIFIED IDEOGRAPH - 0xD4F4: 0x5D1E, //CJK UNIFIED IDEOGRAPH - 0xD4F5: 0x5D0B, //CJK UNIFIED IDEOGRAPH - 0xD4F6: 0x5D1D, //CJK UNIFIED IDEOGRAPH - 0xD4F7: 0x5D1A, //CJK UNIFIED IDEOGRAPH - 0xD4F8: 0x5D20, //CJK UNIFIED IDEOGRAPH - 0xD4F9: 0x5D0C, //CJK UNIFIED IDEOGRAPH - 0xD4FA: 0x5D28, //CJK UNIFIED IDEOGRAPH - 0xD4FB: 0x5D0D, //CJK UNIFIED IDEOGRAPH - 0xD4FC: 0x5D26, //CJK UNIFIED IDEOGRAPH - 0xD4FD: 0x5D25, //CJK UNIFIED IDEOGRAPH - 0xD4FE: 0x5D0F, //CJK UNIFIED IDEOGRAPH - 0xD540: 0x5D30, //CJK UNIFIED IDEOGRAPH - 0xD541: 0x5D12, //CJK UNIFIED IDEOGRAPH - 0xD542: 0x5D23, //CJK UNIFIED IDEOGRAPH - 0xD543: 0x5D1F, //CJK UNIFIED IDEOGRAPH - 0xD544: 0x5D2E, //CJK UNIFIED IDEOGRAPH - 0xD545: 0x5E3E, //CJK UNIFIED IDEOGRAPH - 0xD546: 0x5E34, //CJK UNIFIED IDEOGRAPH - 0xD547: 0x5EB1, //CJK UNIFIED IDEOGRAPH - 0xD548: 0x5EB4, //CJK UNIFIED IDEOGRAPH - 0xD549: 0x5EB9, //CJK UNIFIED IDEOGRAPH - 0xD54A: 0x5EB2, //CJK UNIFIED IDEOGRAPH - 0xD54B: 0x5EB3, //CJK UNIFIED IDEOGRAPH - 0xD54C: 0x5F36, //CJK UNIFIED IDEOGRAPH - 0xD54D: 0x5F38, //CJK UNIFIED IDEOGRAPH - 0xD54E: 0x5F9B, //CJK UNIFIED IDEOGRAPH - 0xD54F: 0x5F96, //CJK UNIFIED IDEOGRAPH - 0xD550: 0x5F9F, //CJK UNIFIED IDEOGRAPH - 0xD551: 0x608A, //CJK UNIFIED IDEOGRAPH - 0xD552: 0x6090, //CJK UNIFIED IDEOGRAPH - 0xD553: 0x6086, //CJK UNIFIED IDEOGRAPH - 0xD554: 0x60BE, //CJK UNIFIED IDEOGRAPH - 0xD555: 0x60B0, //CJK UNIFIED IDEOGRAPH - 0xD556: 0x60BA, //CJK UNIFIED IDEOGRAPH - 0xD557: 0x60D3, //CJK UNIFIED IDEOGRAPH - 0xD558: 0x60D4, //CJK UNIFIED IDEOGRAPH - 0xD559: 0x60CF, //CJK UNIFIED IDEOGRAPH - 0xD55A: 0x60E4, //CJK UNIFIED IDEOGRAPH - 0xD55B: 0x60D9, //CJK UNIFIED IDEOGRAPH - 0xD55C: 0x60DD, //CJK UNIFIED IDEOGRAPH - 0xD55D: 0x60C8, //CJK UNIFIED IDEOGRAPH - 0xD55E: 0x60B1, //CJK UNIFIED IDEOGRAPH - 0xD55F: 0x60DB, //CJK UNIFIED IDEOGRAPH - 0xD560: 0x60B7, //CJK UNIFIED IDEOGRAPH - 0xD561: 0x60CA, //CJK UNIFIED IDEOGRAPH - 0xD562: 0x60BF, //CJK UNIFIED IDEOGRAPH - 0xD563: 0x60C3, //CJK UNIFIED IDEOGRAPH - 0xD564: 0x60CD, //CJK UNIFIED IDEOGRAPH - 0xD565: 0x60C0, //CJK UNIFIED IDEOGRAPH - 0xD566: 0x6332, //CJK UNIFIED IDEOGRAPH - 0xD567: 0x6365, //CJK UNIFIED IDEOGRAPH - 0xD568: 0x638A, //CJK UNIFIED IDEOGRAPH - 0xD569: 0x6382, //CJK UNIFIED IDEOGRAPH - 0xD56A: 0x637D, //CJK UNIFIED IDEOGRAPH - 0xD56B: 0x63BD, //CJK UNIFIED IDEOGRAPH - 0xD56C: 0x639E, //CJK UNIFIED IDEOGRAPH - 0xD56D: 0x63AD, //CJK UNIFIED IDEOGRAPH - 0xD56E: 0x639D, //CJK UNIFIED IDEOGRAPH - 0xD56F: 0x6397, //CJK UNIFIED IDEOGRAPH - 0xD570: 0x63AB, //CJK UNIFIED IDEOGRAPH - 0xD571: 0x638E, //CJK UNIFIED IDEOGRAPH - 0xD572: 0x636F, //CJK UNIFIED IDEOGRAPH - 0xD573: 0x6387, //CJK UNIFIED IDEOGRAPH - 0xD574: 0x6390, //CJK UNIFIED IDEOGRAPH - 0xD575: 0x636E, //CJK UNIFIED IDEOGRAPH - 0xD576: 0x63AF, //CJK UNIFIED IDEOGRAPH - 0xD577: 0x6375, //CJK UNIFIED IDEOGRAPH - 0xD578: 0x639C, //CJK UNIFIED IDEOGRAPH - 0xD579: 0x636D, //CJK UNIFIED IDEOGRAPH - 0xD57A: 0x63AE, //CJK UNIFIED IDEOGRAPH - 0xD57B: 0x637C, //CJK UNIFIED IDEOGRAPH - 0xD57C: 0x63A4, //CJK UNIFIED IDEOGRAPH - 0xD57D: 0x633B, //CJK UNIFIED IDEOGRAPH - 0xD57E: 0x639F, //CJK UNIFIED IDEOGRAPH - 0xD5A1: 0x6378, //CJK UNIFIED IDEOGRAPH - 0xD5A2: 0x6385, //CJK UNIFIED IDEOGRAPH - 0xD5A3: 0x6381, //CJK UNIFIED IDEOGRAPH - 0xD5A4: 0x6391, //CJK UNIFIED IDEOGRAPH - 0xD5A5: 0x638D, //CJK UNIFIED IDEOGRAPH - 0xD5A6: 0x6370, //CJK UNIFIED IDEOGRAPH - 0xD5A7: 0x6553, //CJK UNIFIED IDEOGRAPH - 0xD5A8: 0x65CD, //CJK UNIFIED IDEOGRAPH - 0xD5A9: 0x6665, //CJK UNIFIED IDEOGRAPH - 0xD5AA: 0x6661, //CJK UNIFIED IDEOGRAPH - 0xD5AB: 0x665B, //CJK UNIFIED IDEOGRAPH - 0xD5AC: 0x6659, //CJK UNIFIED IDEOGRAPH - 0xD5AD: 0x665C, //CJK UNIFIED IDEOGRAPH - 0xD5AE: 0x6662, //CJK UNIFIED IDEOGRAPH - 0xD5AF: 0x6718, //CJK UNIFIED IDEOGRAPH - 0xD5B0: 0x6879, //CJK UNIFIED IDEOGRAPH - 0xD5B1: 0x6887, //CJK UNIFIED IDEOGRAPH - 0xD5B2: 0x6890, //CJK UNIFIED IDEOGRAPH - 0xD5B3: 0x689C, //CJK UNIFIED IDEOGRAPH - 0xD5B4: 0x686D, //CJK UNIFIED IDEOGRAPH - 0xD5B5: 0x686E, //CJK UNIFIED IDEOGRAPH - 0xD5B6: 0x68AE, //CJK UNIFIED IDEOGRAPH - 0xD5B7: 0x68AB, //CJK UNIFIED IDEOGRAPH - 0xD5B8: 0x6956, //CJK UNIFIED IDEOGRAPH - 0xD5B9: 0x686F, //CJK UNIFIED IDEOGRAPH - 0xD5BA: 0x68A3, //CJK UNIFIED IDEOGRAPH - 0xD5BB: 0x68AC, //CJK UNIFIED IDEOGRAPH - 0xD5BC: 0x68A9, //CJK UNIFIED IDEOGRAPH - 0xD5BD: 0x6875, //CJK UNIFIED IDEOGRAPH - 0xD5BE: 0x6874, //CJK UNIFIED IDEOGRAPH - 0xD5BF: 0x68B2, //CJK UNIFIED IDEOGRAPH - 0xD5C0: 0x688F, //CJK UNIFIED IDEOGRAPH - 0xD5C1: 0x6877, //CJK UNIFIED IDEOGRAPH - 0xD5C2: 0x6892, //CJK UNIFIED IDEOGRAPH - 0xD5C3: 0x687C, //CJK UNIFIED IDEOGRAPH - 0xD5C4: 0x686B, //CJK UNIFIED IDEOGRAPH - 0xD5C5: 0x6872, //CJK UNIFIED IDEOGRAPH - 0xD5C6: 0x68AA, //CJK UNIFIED IDEOGRAPH - 0xD5C7: 0x6880, //CJK UNIFIED IDEOGRAPH - 0xD5C8: 0x6871, //CJK UNIFIED IDEOGRAPH - 0xD5C9: 0x687E, //CJK UNIFIED IDEOGRAPH - 0xD5CA: 0x689B, //CJK UNIFIED IDEOGRAPH - 0xD5CB: 0x6896, //CJK UNIFIED IDEOGRAPH - 0xD5CC: 0x688B, //CJK UNIFIED IDEOGRAPH - 0xD5CD: 0x68A0, //CJK UNIFIED IDEOGRAPH - 0xD5CE: 0x6889, //CJK UNIFIED IDEOGRAPH - 0xD5CF: 0x68A4, //CJK UNIFIED IDEOGRAPH - 0xD5D0: 0x6878, //CJK UNIFIED IDEOGRAPH - 0xD5D1: 0x687B, //CJK UNIFIED IDEOGRAPH - 0xD5D2: 0x6891, //CJK UNIFIED IDEOGRAPH - 0xD5D3: 0x688C, //CJK UNIFIED IDEOGRAPH - 0xD5D4: 0x688A, //CJK UNIFIED IDEOGRAPH - 0xD5D5: 0x687D, //CJK UNIFIED IDEOGRAPH - 0xD5D6: 0x6B36, //CJK UNIFIED IDEOGRAPH - 0xD5D7: 0x6B33, //CJK UNIFIED IDEOGRAPH - 0xD5D8: 0x6B37, //CJK UNIFIED IDEOGRAPH - 0xD5D9: 0x6B38, //CJK UNIFIED IDEOGRAPH - 0xD5DA: 0x6B91, //CJK UNIFIED IDEOGRAPH - 0xD5DB: 0x6B8F, //CJK UNIFIED IDEOGRAPH - 0xD5DC: 0x6B8D, //CJK UNIFIED IDEOGRAPH - 0xD5DD: 0x6B8E, //CJK UNIFIED IDEOGRAPH - 0xD5DE: 0x6B8C, //CJK UNIFIED IDEOGRAPH - 0xD5DF: 0x6C2A, //CJK UNIFIED IDEOGRAPH - 0xD5E0: 0x6DC0, //CJK UNIFIED IDEOGRAPH - 0xD5E1: 0x6DAB, //CJK UNIFIED IDEOGRAPH - 0xD5E2: 0x6DB4, //CJK UNIFIED IDEOGRAPH - 0xD5E3: 0x6DB3, //CJK UNIFIED IDEOGRAPH - 0xD5E4: 0x6E74, //CJK UNIFIED IDEOGRAPH - 0xD5E5: 0x6DAC, //CJK UNIFIED IDEOGRAPH - 0xD5E6: 0x6DE9, //CJK UNIFIED IDEOGRAPH - 0xD5E7: 0x6DE2, //CJK UNIFIED IDEOGRAPH - 0xD5E8: 0x6DB7, //CJK UNIFIED IDEOGRAPH - 0xD5E9: 0x6DF6, //CJK UNIFIED IDEOGRAPH - 0xD5EA: 0x6DD4, //CJK UNIFIED IDEOGRAPH - 0xD5EB: 0x6E00, //CJK UNIFIED IDEOGRAPH - 0xD5EC: 0x6DC8, //CJK UNIFIED IDEOGRAPH - 0xD5ED: 0x6DE0, //CJK UNIFIED IDEOGRAPH - 0xD5EE: 0x6DDF, //CJK UNIFIED IDEOGRAPH - 0xD5EF: 0x6DD6, //CJK UNIFIED IDEOGRAPH - 0xD5F0: 0x6DBE, //CJK UNIFIED IDEOGRAPH - 0xD5F1: 0x6DE5, //CJK UNIFIED IDEOGRAPH - 0xD5F2: 0x6DDC, //CJK UNIFIED IDEOGRAPH - 0xD5F3: 0x6DDD, //CJK UNIFIED IDEOGRAPH - 0xD5F4: 0x6DDB, //CJK UNIFIED IDEOGRAPH - 0xD5F5: 0x6DF4, //CJK UNIFIED IDEOGRAPH - 0xD5F6: 0x6DCA, //CJK UNIFIED IDEOGRAPH - 0xD5F7: 0x6DBD, //CJK UNIFIED IDEOGRAPH - 0xD5F8: 0x6DED, //CJK UNIFIED IDEOGRAPH - 0xD5F9: 0x6DF0, //CJK UNIFIED IDEOGRAPH - 0xD5FA: 0x6DBA, //CJK UNIFIED IDEOGRAPH - 0xD5FB: 0x6DD5, //CJK UNIFIED IDEOGRAPH - 0xD5FC: 0x6DC2, //CJK UNIFIED IDEOGRAPH - 0xD5FD: 0x6DCF, //CJK UNIFIED IDEOGRAPH - 0xD5FE: 0x6DC9, //CJK UNIFIED IDEOGRAPH - 0xD640: 0x6DD0, //CJK UNIFIED IDEOGRAPH - 0xD641: 0x6DF2, //CJK UNIFIED IDEOGRAPH - 0xD642: 0x6DD3, //CJK UNIFIED IDEOGRAPH - 0xD643: 0x6DFD, //CJK UNIFIED IDEOGRAPH - 0xD644: 0x6DD7, //CJK UNIFIED IDEOGRAPH - 0xD645: 0x6DCD, //CJK UNIFIED IDEOGRAPH - 0xD646: 0x6DE3, //CJK UNIFIED IDEOGRAPH - 0xD647: 0x6DBB, //CJK UNIFIED IDEOGRAPH - 0xD648: 0x70FA, //CJK UNIFIED IDEOGRAPH - 0xD649: 0x710D, //CJK UNIFIED IDEOGRAPH - 0xD64A: 0x70F7, //CJK UNIFIED IDEOGRAPH - 0xD64B: 0x7117, //CJK UNIFIED IDEOGRAPH - 0xD64C: 0x70F4, //CJK UNIFIED IDEOGRAPH - 0xD64D: 0x710C, //CJK UNIFIED IDEOGRAPH - 0xD64E: 0x70F0, //CJK UNIFIED IDEOGRAPH - 0xD64F: 0x7104, //CJK UNIFIED IDEOGRAPH - 0xD650: 0x70F3, //CJK UNIFIED IDEOGRAPH - 0xD651: 0x7110, //CJK UNIFIED IDEOGRAPH - 0xD652: 0x70FC, //CJK UNIFIED IDEOGRAPH - 0xD653: 0x70FF, //CJK UNIFIED IDEOGRAPH - 0xD654: 0x7106, //CJK UNIFIED IDEOGRAPH - 0xD655: 0x7113, //CJK UNIFIED IDEOGRAPH - 0xD656: 0x7100, //CJK UNIFIED IDEOGRAPH - 0xD657: 0x70F8, //CJK UNIFIED IDEOGRAPH - 0xD658: 0x70F6, //CJK UNIFIED IDEOGRAPH - 0xD659: 0x710B, //CJK UNIFIED IDEOGRAPH - 0xD65A: 0x7102, //CJK UNIFIED IDEOGRAPH - 0xD65B: 0x710E, //CJK UNIFIED IDEOGRAPH - 0xD65C: 0x727E, //CJK UNIFIED IDEOGRAPH - 0xD65D: 0x727B, //CJK UNIFIED IDEOGRAPH - 0xD65E: 0x727C, //CJK UNIFIED IDEOGRAPH - 0xD65F: 0x727F, //CJK UNIFIED IDEOGRAPH - 0xD660: 0x731D, //CJK UNIFIED IDEOGRAPH - 0xD661: 0x7317, //CJK UNIFIED IDEOGRAPH - 0xD662: 0x7307, //CJK UNIFIED IDEOGRAPH - 0xD663: 0x7311, //CJK UNIFIED IDEOGRAPH - 0xD664: 0x7318, //CJK UNIFIED IDEOGRAPH - 0xD665: 0x730A, //CJK UNIFIED IDEOGRAPH - 0xD666: 0x7308, //CJK UNIFIED IDEOGRAPH - 0xD667: 0x72FF, //CJK UNIFIED IDEOGRAPH - 0xD668: 0x730F, //CJK UNIFIED IDEOGRAPH - 0xD669: 0x731E, //CJK UNIFIED IDEOGRAPH - 0xD66A: 0x7388, //CJK UNIFIED IDEOGRAPH - 0xD66B: 0x73F6, //CJK UNIFIED IDEOGRAPH - 0xD66C: 0x73F8, //CJK UNIFIED IDEOGRAPH - 0xD66D: 0x73F5, //CJK UNIFIED IDEOGRAPH - 0xD66E: 0x7404, //CJK UNIFIED IDEOGRAPH - 0xD66F: 0x7401, //CJK UNIFIED IDEOGRAPH - 0xD670: 0x73FD, //CJK UNIFIED IDEOGRAPH - 0xD671: 0x7407, //CJK UNIFIED IDEOGRAPH - 0xD672: 0x7400, //CJK UNIFIED IDEOGRAPH - 0xD673: 0x73FA, //CJK UNIFIED IDEOGRAPH - 0xD674: 0x73FC, //CJK UNIFIED IDEOGRAPH - 0xD675: 0x73FF, //CJK UNIFIED IDEOGRAPH - 0xD676: 0x740C, //CJK UNIFIED IDEOGRAPH - 0xD677: 0x740B, //CJK UNIFIED IDEOGRAPH - 0xD678: 0x73F4, //CJK UNIFIED IDEOGRAPH - 0xD679: 0x7408, //CJK UNIFIED IDEOGRAPH - 0xD67A: 0x7564, //CJK UNIFIED IDEOGRAPH - 0xD67B: 0x7563, //CJK UNIFIED IDEOGRAPH - 0xD67C: 0x75CE, //CJK UNIFIED IDEOGRAPH - 0xD67D: 0x75D2, //CJK UNIFIED IDEOGRAPH - 0xD67E: 0x75CF, //CJK UNIFIED IDEOGRAPH - 0xD6A1: 0x75CB, //CJK UNIFIED IDEOGRAPH - 0xD6A2: 0x75CC, //CJK UNIFIED IDEOGRAPH - 0xD6A3: 0x75D1, //CJK UNIFIED IDEOGRAPH - 0xD6A4: 0x75D0, //CJK UNIFIED IDEOGRAPH - 0xD6A5: 0x768F, //CJK UNIFIED IDEOGRAPH - 0xD6A6: 0x7689, //CJK UNIFIED IDEOGRAPH - 0xD6A7: 0x76D3, //CJK UNIFIED IDEOGRAPH - 0xD6A8: 0x7739, //CJK UNIFIED IDEOGRAPH - 0xD6A9: 0x772F, //CJK UNIFIED IDEOGRAPH - 0xD6AA: 0x772D, //CJK UNIFIED IDEOGRAPH - 0xD6AB: 0x7731, //CJK UNIFIED IDEOGRAPH - 0xD6AC: 0x7732, //CJK UNIFIED IDEOGRAPH - 0xD6AD: 0x7734, //CJK UNIFIED IDEOGRAPH - 0xD6AE: 0x7733, //CJK UNIFIED IDEOGRAPH - 0xD6AF: 0x773D, //CJK UNIFIED IDEOGRAPH - 0xD6B0: 0x7725, //CJK UNIFIED IDEOGRAPH - 0xD6B1: 0x773B, //CJK UNIFIED IDEOGRAPH - 0xD6B2: 0x7735, //CJK UNIFIED IDEOGRAPH - 0xD6B3: 0x7848, //CJK UNIFIED IDEOGRAPH - 0xD6B4: 0x7852, //CJK UNIFIED IDEOGRAPH - 0xD6B5: 0x7849, //CJK UNIFIED IDEOGRAPH - 0xD6B6: 0x784D, //CJK UNIFIED IDEOGRAPH - 0xD6B7: 0x784A, //CJK UNIFIED IDEOGRAPH - 0xD6B8: 0x784C, //CJK UNIFIED IDEOGRAPH - 0xD6B9: 0x7826, //CJK UNIFIED IDEOGRAPH - 0xD6BA: 0x7845, //CJK UNIFIED IDEOGRAPH - 0xD6BB: 0x7850, //CJK UNIFIED IDEOGRAPH - 0xD6BC: 0x7964, //CJK UNIFIED IDEOGRAPH - 0xD6BD: 0x7967, //CJK UNIFIED IDEOGRAPH - 0xD6BE: 0x7969, //CJK UNIFIED IDEOGRAPH - 0xD6BF: 0x796A, //CJK UNIFIED IDEOGRAPH - 0xD6C0: 0x7963, //CJK UNIFIED IDEOGRAPH - 0xD6C1: 0x796B, //CJK UNIFIED IDEOGRAPH - 0xD6C2: 0x7961, //CJK UNIFIED IDEOGRAPH - 0xD6C3: 0x79BB, //CJK UNIFIED IDEOGRAPH - 0xD6C4: 0x79FA, //CJK UNIFIED IDEOGRAPH - 0xD6C5: 0x79F8, //CJK UNIFIED IDEOGRAPH - 0xD6C6: 0x79F6, //CJK UNIFIED IDEOGRAPH - 0xD6C7: 0x79F7, //CJK UNIFIED IDEOGRAPH - 0xD6C8: 0x7A8F, //CJK UNIFIED IDEOGRAPH - 0xD6C9: 0x7A94, //CJK UNIFIED IDEOGRAPH - 0xD6CA: 0x7A90, //CJK UNIFIED IDEOGRAPH - 0xD6CB: 0x7B35, //CJK UNIFIED IDEOGRAPH - 0xD6CC: 0x7B47, //CJK UNIFIED IDEOGRAPH - 0xD6CD: 0x7B34, //CJK UNIFIED IDEOGRAPH - 0xD6CE: 0x7B25, //CJK UNIFIED IDEOGRAPH - 0xD6CF: 0x7B30, //CJK UNIFIED IDEOGRAPH - 0xD6D0: 0x7B22, //CJK UNIFIED IDEOGRAPH - 0xD6D1: 0x7B24, //CJK UNIFIED IDEOGRAPH - 0xD6D2: 0x7B33, //CJK UNIFIED IDEOGRAPH - 0xD6D3: 0x7B18, //CJK UNIFIED IDEOGRAPH - 0xD6D4: 0x7B2A, //CJK UNIFIED IDEOGRAPH - 0xD6D5: 0x7B1D, //CJK UNIFIED IDEOGRAPH - 0xD6D6: 0x7B31, //CJK UNIFIED IDEOGRAPH - 0xD6D7: 0x7B2B, //CJK UNIFIED IDEOGRAPH - 0xD6D8: 0x7B2D, //CJK UNIFIED IDEOGRAPH - 0xD6D9: 0x7B2F, //CJK UNIFIED IDEOGRAPH - 0xD6DA: 0x7B32, //CJK UNIFIED IDEOGRAPH - 0xD6DB: 0x7B38, //CJK UNIFIED IDEOGRAPH - 0xD6DC: 0x7B1A, //CJK UNIFIED IDEOGRAPH - 0xD6DD: 0x7B23, //CJK UNIFIED IDEOGRAPH - 0xD6DE: 0x7C94, //CJK UNIFIED IDEOGRAPH - 0xD6DF: 0x7C98, //CJK UNIFIED IDEOGRAPH - 0xD6E0: 0x7C96, //CJK UNIFIED IDEOGRAPH - 0xD6E1: 0x7CA3, //CJK UNIFIED IDEOGRAPH - 0xD6E2: 0x7D35, //CJK UNIFIED IDEOGRAPH - 0xD6E3: 0x7D3D, //CJK UNIFIED IDEOGRAPH - 0xD6E4: 0x7D38, //CJK UNIFIED IDEOGRAPH - 0xD6E5: 0x7D36, //CJK UNIFIED IDEOGRAPH - 0xD6E6: 0x7D3A, //CJK UNIFIED IDEOGRAPH - 0xD6E7: 0x7D45, //CJK UNIFIED IDEOGRAPH - 0xD6E8: 0x7D2C, //CJK UNIFIED IDEOGRAPH - 0xD6E9: 0x7D29, //CJK UNIFIED IDEOGRAPH - 0xD6EA: 0x7D41, //CJK UNIFIED IDEOGRAPH - 0xD6EB: 0x7D47, //CJK UNIFIED IDEOGRAPH - 0xD6EC: 0x7D3E, //CJK UNIFIED IDEOGRAPH - 0xD6ED: 0x7D3F, //CJK UNIFIED IDEOGRAPH - 0xD6EE: 0x7D4A, //CJK UNIFIED IDEOGRAPH - 0xD6EF: 0x7D3B, //CJK UNIFIED IDEOGRAPH - 0xD6F0: 0x7D28, //CJK UNIFIED IDEOGRAPH - 0xD6F1: 0x7F63, //CJK UNIFIED IDEOGRAPH - 0xD6F2: 0x7F95, //CJK UNIFIED IDEOGRAPH - 0xD6F3: 0x7F9C, //CJK UNIFIED IDEOGRAPH - 0xD6F4: 0x7F9D, //CJK UNIFIED IDEOGRAPH - 0xD6F5: 0x7F9B, //CJK UNIFIED IDEOGRAPH - 0xD6F6: 0x7FCA, //CJK UNIFIED IDEOGRAPH - 0xD6F7: 0x7FCB, //CJK UNIFIED IDEOGRAPH - 0xD6F8: 0x7FCD, //CJK UNIFIED IDEOGRAPH - 0xD6F9: 0x7FD0, //CJK UNIFIED IDEOGRAPH - 0xD6FA: 0x7FD1, //CJK UNIFIED IDEOGRAPH - 0xD6FB: 0x7FC7, //CJK UNIFIED IDEOGRAPH - 0xD6FC: 0x7FCF, //CJK UNIFIED IDEOGRAPH - 0xD6FD: 0x7FC9, //CJK UNIFIED IDEOGRAPH - 0xD6FE: 0x801F, //CJK UNIFIED IDEOGRAPH - 0xD740: 0x801E, //CJK UNIFIED IDEOGRAPH - 0xD741: 0x801B, //CJK UNIFIED IDEOGRAPH - 0xD742: 0x8047, //CJK UNIFIED IDEOGRAPH - 0xD743: 0x8043, //CJK UNIFIED IDEOGRAPH - 0xD744: 0x8048, //CJK UNIFIED IDEOGRAPH - 0xD745: 0x8118, //CJK UNIFIED IDEOGRAPH - 0xD746: 0x8125, //CJK UNIFIED IDEOGRAPH - 0xD747: 0x8119, //CJK UNIFIED IDEOGRAPH - 0xD748: 0x811B, //CJK UNIFIED IDEOGRAPH - 0xD749: 0x812D, //CJK UNIFIED IDEOGRAPH - 0xD74A: 0x811F, //CJK UNIFIED IDEOGRAPH - 0xD74B: 0x812C, //CJK UNIFIED IDEOGRAPH - 0xD74C: 0x811E, //CJK UNIFIED IDEOGRAPH - 0xD74D: 0x8121, //CJK UNIFIED IDEOGRAPH - 0xD74E: 0x8115, //CJK UNIFIED IDEOGRAPH - 0xD74F: 0x8127, //CJK UNIFIED IDEOGRAPH - 0xD750: 0x811D, //CJK UNIFIED IDEOGRAPH - 0xD751: 0x8122, //CJK UNIFIED IDEOGRAPH - 0xD752: 0x8211, //CJK UNIFIED IDEOGRAPH - 0xD753: 0x8238, //CJK UNIFIED IDEOGRAPH - 0xD754: 0x8233, //CJK UNIFIED IDEOGRAPH - 0xD755: 0x823A, //CJK UNIFIED IDEOGRAPH - 0xD756: 0x8234, //CJK UNIFIED IDEOGRAPH - 0xD757: 0x8232, //CJK UNIFIED IDEOGRAPH - 0xD758: 0x8274, //CJK UNIFIED IDEOGRAPH - 0xD759: 0x8390, //CJK UNIFIED IDEOGRAPH - 0xD75A: 0x83A3, //CJK UNIFIED IDEOGRAPH - 0xD75B: 0x83A8, //CJK UNIFIED IDEOGRAPH - 0xD75C: 0x838D, //CJK UNIFIED IDEOGRAPH - 0xD75D: 0x837A, //CJK UNIFIED IDEOGRAPH - 0xD75E: 0x8373, //CJK UNIFIED IDEOGRAPH - 0xD75F: 0x83A4, //CJK UNIFIED IDEOGRAPH - 0xD760: 0x8374, //CJK UNIFIED IDEOGRAPH - 0xD761: 0x838F, //CJK UNIFIED IDEOGRAPH - 0xD762: 0x8381, //CJK UNIFIED IDEOGRAPH - 0xD763: 0x8395, //CJK UNIFIED IDEOGRAPH - 0xD764: 0x8399, //CJK UNIFIED IDEOGRAPH - 0xD765: 0x8375, //CJK UNIFIED IDEOGRAPH - 0xD766: 0x8394, //CJK UNIFIED IDEOGRAPH - 0xD767: 0x83A9, //CJK UNIFIED IDEOGRAPH - 0xD768: 0x837D, //CJK UNIFIED IDEOGRAPH - 0xD769: 0x8383, //CJK UNIFIED IDEOGRAPH - 0xD76A: 0x838C, //CJK UNIFIED IDEOGRAPH - 0xD76B: 0x839D, //CJK UNIFIED IDEOGRAPH - 0xD76C: 0x839B, //CJK UNIFIED IDEOGRAPH - 0xD76D: 0x83AA, //CJK UNIFIED IDEOGRAPH - 0xD76E: 0x838B, //CJK UNIFIED IDEOGRAPH - 0xD76F: 0x837E, //CJK UNIFIED IDEOGRAPH - 0xD770: 0x83A5, //CJK UNIFIED IDEOGRAPH - 0xD771: 0x83AF, //CJK UNIFIED IDEOGRAPH - 0xD772: 0x8388, //CJK UNIFIED IDEOGRAPH - 0xD773: 0x8397, //CJK UNIFIED IDEOGRAPH - 0xD774: 0x83B0, //CJK UNIFIED IDEOGRAPH - 0xD775: 0x837F, //CJK UNIFIED IDEOGRAPH - 0xD776: 0x83A6, //CJK UNIFIED IDEOGRAPH - 0xD777: 0x8387, //CJK UNIFIED IDEOGRAPH - 0xD778: 0x83AE, //CJK UNIFIED IDEOGRAPH - 0xD779: 0x8376, //CJK UNIFIED IDEOGRAPH - 0xD77A: 0x839A, //CJK UNIFIED IDEOGRAPH - 0xD77B: 0x8659, //CJK UNIFIED IDEOGRAPH - 0xD77C: 0x8656, //CJK UNIFIED IDEOGRAPH - 0xD77D: 0x86BF, //CJK UNIFIED IDEOGRAPH - 0xD77E: 0x86B7, //CJK UNIFIED IDEOGRAPH - 0xD7A1: 0x86C2, //CJK UNIFIED IDEOGRAPH - 0xD7A2: 0x86C1, //CJK UNIFIED IDEOGRAPH - 0xD7A3: 0x86C5, //CJK UNIFIED IDEOGRAPH - 0xD7A4: 0x86BA, //CJK UNIFIED IDEOGRAPH - 0xD7A5: 0x86B0, //CJK UNIFIED IDEOGRAPH - 0xD7A6: 0x86C8, //CJK UNIFIED IDEOGRAPH - 0xD7A7: 0x86B9, //CJK UNIFIED IDEOGRAPH - 0xD7A8: 0x86B3, //CJK UNIFIED IDEOGRAPH - 0xD7A9: 0x86B8, //CJK UNIFIED IDEOGRAPH - 0xD7AA: 0x86CC, //CJK UNIFIED IDEOGRAPH - 0xD7AB: 0x86B4, //CJK UNIFIED IDEOGRAPH - 0xD7AC: 0x86BB, //CJK UNIFIED IDEOGRAPH - 0xD7AD: 0x86BC, //CJK UNIFIED IDEOGRAPH - 0xD7AE: 0x86C3, //CJK UNIFIED IDEOGRAPH - 0xD7AF: 0x86BD, //CJK UNIFIED IDEOGRAPH - 0xD7B0: 0x86BE, //CJK UNIFIED IDEOGRAPH - 0xD7B1: 0x8852, //CJK UNIFIED IDEOGRAPH - 0xD7B2: 0x8889, //CJK UNIFIED IDEOGRAPH - 0xD7B3: 0x8895, //CJK UNIFIED IDEOGRAPH - 0xD7B4: 0x88A8, //CJK UNIFIED IDEOGRAPH - 0xD7B5: 0x88A2, //CJK UNIFIED IDEOGRAPH - 0xD7B6: 0x88AA, //CJK UNIFIED IDEOGRAPH - 0xD7B7: 0x889A, //CJK UNIFIED IDEOGRAPH - 0xD7B8: 0x8891, //CJK UNIFIED IDEOGRAPH - 0xD7B9: 0x88A1, //CJK UNIFIED IDEOGRAPH - 0xD7BA: 0x889F, //CJK UNIFIED IDEOGRAPH - 0xD7BB: 0x8898, //CJK UNIFIED IDEOGRAPH - 0xD7BC: 0x88A7, //CJK UNIFIED IDEOGRAPH - 0xD7BD: 0x8899, //CJK UNIFIED IDEOGRAPH - 0xD7BE: 0x889B, //CJK UNIFIED IDEOGRAPH - 0xD7BF: 0x8897, //CJK UNIFIED IDEOGRAPH - 0xD7C0: 0x88A4, //CJK UNIFIED IDEOGRAPH - 0xD7C1: 0x88AC, //CJK UNIFIED IDEOGRAPH - 0xD7C2: 0x888C, //CJK UNIFIED IDEOGRAPH - 0xD7C3: 0x8893, //CJK UNIFIED IDEOGRAPH - 0xD7C4: 0x888E, //CJK UNIFIED IDEOGRAPH - 0xD7C5: 0x8982, //CJK UNIFIED IDEOGRAPH - 0xD7C6: 0x89D6, //CJK UNIFIED IDEOGRAPH - 0xD7C7: 0x89D9, //CJK UNIFIED IDEOGRAPH - 0xD7C8: 0x89D5, //CJK UNIFIED IDEOGRAPH - 0xD7C9: 0x8A30, //CJK UNIFIED IDEOGRAPH - 0xD7CA: 0x8A27, //CJK UNIFIED IDEOGRAPH - 0xD7CB: 0x8A2C, //CJK UNIFIED IDEOGRAPH - 0xD7CC: 0x8A1E, //CJK UNIFIED IDEOGRAPH - 0xD7CD: 0x8C39, //CJK UNIFIED IDEOGRAPH - 0xD7CE: 0x8C3B, //CJK UNIFIED IDEOGRAPH - 0xD7CF: 0x8C5C, //CJK UNIFIED IDEOGRAPH - 0xD7D0: 0x8C5D, //CJK UNIFIED IDEOGRAPH - 0xD7D1: 0x8C7D, //CJK UNIFIED IDEOGRAPH - 0xD7D2: 0x8CA5, //CJK UNIFIED IDEOGRAPH - 0xD7D3: 0x8D7D, //CJK UNIFIED IDEOGRAPH - 0xD7D4: 0x8D7B, //CJK UNIFIED IDEOGRAPH - 0xD7D5: 0x8D79, //CJK UNIFIED IDEOGRAPH - 0xD7D6: 0x8DBC, //CJK UNIFIED IDEOGRAPH - 0xD7D7: 0x8DC2, //CJK UNIFIED IDEOGRAPH - 0xD7D8: 0x8DB9, //CJK UNIFIED IDEOGRAPH - 0xD7D9: 0x8DBF, //CJK UNIFIED IDEOGRAPH - 0xD7DA: 0x8DC1, //CJK UNIFIED IDEOGRAPH - 0xD7DB: 0x8ED8, //CJK UNIFIED IDEOGRAPH - 0xD7DC: 0x8EDE, //CJK UNIFIED IDEOGRAPH - 0xD7DD: 0x8EDD, //CJK UNIFIED IDEOGRAPH - 0xD7DE: 0x8EDC, //CJK UNIFIED IDEOGRAPH - 0xD7DF: 0x8ED7, //CJK UNIFIED IDEOGRAPH - 0xD7E0: 0x8EE0, //CJK UNIFIED IDEOGRAPH - 0xD7E1: 0x8EE1, //CJK UNIFIED IDEOGRAPH - 0xD7E2: 0x9024, //CJK UNIFIED IDEOGRAPH - 0xD7E3: 0x900B, //CJK UNIFIED IDEOGRAPH - 0xD7E4: 0x9011, //CJK UNIFIED IDEOGRAPH - 0xD7E5: 0x901C, //CJK UNIFIED IDEOGRAPH - 0xD7E6: 0x900C, //CJK UNIFIED IDEOGRAPH - 0xD7E7: 0x9021, //CJK UNIFIED IDEOGRAPH - 0xD7E8: 0x90EF, //CJK UNIFIED IDEOGRAPH - 0xD7E9: 0x90EA, //CJK UNIFIED IDEOGRAPH - 0xD7EA: 0x90F0, //CJK UNIFIED IDEOGRAPH - 0xD7EB: 0x90F4, //CJK UNIFIED IDEOGRAPH - 0xD7EC: 0x90F2, //CJK UNIFIED IDEOGRAPH - 0xD7ED: 0x90F3, //CJK UNIFIED IDEOGRAPH - 0xD7EE: 0x90D4, //CJK UNIFIED IDEOGRAPH - 0xD7EF: 0x90EB, //CJK UNIFIED IDEOGRAPH - 0xD7F0: 0x90EC, //CJK UNIFIED IDEOGRAPH - 0xD7F1: 0x90E9, //CJK UNIFIED IDEOGRAPH - 0xD7F2: 0x9156, //CJK UNIFIED IDEOGRAPH - 0xD7F3: 0x9158, //CJK UNIFIED IDEOGRAPH - 0xD7F4: 0x915A, //CJK UNIFIED IDEOGRAPH - 0xD7F5: 0x9153, //CJK UNIFIED IDEOGRAPH - 0xD7F6: 0x9155, //CJK UNIFIED IDEOGRAPH - 0xD7F7: 0x91EC, //CJK UNIFIED IDEOGRAPH - 0xD7F8: 0x91F4, //CJK UNIFIED IDEOGRAPH - 0xD7F9: 0x91F1, //CJK UNIFIED IDEOGRAPH - 0xD7FA: 0x91F3, //CJK UNIFIED IDEOGRAPH - 0xD7FB: 0x91F8, //CJK UNIFIED IDEOGRAPH - 0xD7FC: 0x91E4, //CJK UNIFIED IDEOGRAPH - 0xD7FD: 0x91F9, //CJK UNIFIED IDEOGRAPH - 0xD7FE: 0x91EA, //CJK UNIFIED IDEOGRAPH - 0xD840: 0x91EB, //CJK UNIFIED IDEOGRAPH - 0xD841: 0x91F7, //CJK UNIFIED IDEOGRAPH - 0xD842: 0x91E8, //CJK UNIFIED IDEOGRAPH - 0xD843: 0x91EE, //CJK UNIFIED IDEOGRAPH - 0xD844: 0x957A, //CJK UNIFIED IDEOGRAPH - 0xD845: 0x9586, //CJK UNIFIED IDEOGRAPH - 0xD846: 0x9588, //CJK UNIFIED IDEOGRAPH - 0xD847: 0x967C, //CJK UNIFIED IDEOGRAPH - 0xD848: 0x966D, //CJK UNIFIED IDEOGRAPH - 0xD849: 0x966B, //CJK UNIFIED IDEOGRAPH - 0xD84A: 0x9671, //CJK UNIFIED IDEOGRAPH - 0xD84B: 0x966F, //CJK UNIFIED IDEOGRAPH - 0xD84C: 0x96BF, //CJK UNIFIED IDEOGRAPH - 0xD84D: 0x976A, //CJK UNIFIED IDEOGRAPH - 0xD84E: 0x9804, //CJK UNIFIED IDEOGRAPH - 0xD84F: 0x98E5, //CJK UNIFIED IDEOGRAPH - 0xD850: 0x9997, //CJK UNIFIED IDEOGRAPH - 0xD851: 0x509B, //CJK UNIFIED IDEOGRAPH - 0xD852: 0x5095, //CJK UNIFIED IDEOGRAPH - 0xD853: 0x5094, //CJK UNIFIED IDEOGRAPH - 0xD854: 0x509E, //CJK UNIFIED IDEOGRAPH - 0xD855: 0x508B, //CJK UNIFIED IDEOGRAPH - 0xD856: 0x50A3, //CJK UNIFIED IDEOGRAPH - 0xD857: 0x5083, //CJK UNIFIED IDEOGRAPH - 0xD858: 0x508C, //CJK UNIFIED IDEOGRAPH - 0xD859: 0x508E, //CJK UNIFIED IDEOGRAPH - 0xD85A: 0x509D, //CJK UNIFIED IDEOGRAPH - 0xD85B: 0x5068, //CJK UNIFIED IDEOGRAPH - 0xD85C: 0x509C, //CJK UNIFIED IDEOGRAPH - 0xD85D: 0x5092, //CJK UNIFIED IDEOGRAPH - 0xD85E: 0x5082, //CJK UNIFIED IDEOGRAPH - 0xD85F: 0x5087, //CJK UNIFIED IDEOGRAPH - 0xD860: 0x515F, //CJK UNIFIED IDEOGRAPH - 0xD861: 0x51D4, //CJK UNIFIED IDEOGRAPH - 0xD862: 0x5312, //CJK UNIFIED IDEOGRAPH - 0xD863: 0x5311, //CJK UNIFIED IDEOGRAPH - 0xD864: 0x53A4, //CJK UNIFIED IDEOGRAPH - 0xD865: 0x53A7, //CJK UNIFIED IDEOGRAPH - 0xD866: 0x5591, //CJK UNIFIED IDEOGRAPH - 0xD867: 0x55A8, //CJK UNIFIED IDEOGRAPH - 0xD868: 0x55A5, //CJK UNIFIED IDEOGRAPH - 0xD869: 0x55AD, //CJK UNIFIED IDEOGRAPH - 0xD86A: 0x5577, //CJK UNIFIED IDEOGRAPH - 0xD86B: 0x5645, //CJK UNIFIED IDEOGRAPH - 0xD86C: 0x55A2, //CJK UNIFIED IDEOGRAPH - 0xD86D: 0x5593, //CJK UNIFIED IDEOGRAPH - 0xD86E: 0x5588, //CJK UNIFIED IDEOGRAPH - 0xD86F: 0x558F, //CJK UNIFIED IDEOGRAPH - 0xD870: 0x55B5, //CJK UNIFIED IDEOGRAPH - 0xD871: 0x5581, //CJK UNIFIED IDEOGRAPH - 0xD872: 0x55A3, //CJK UNIFIED IDEOGRAPH - 0xD873: 0x5592, //CJK UNIFIED IDEOGRAPH - 0xD874: 0x55A4, //CJK UNIFIED IDEOGRAPH - 0xD875: 0x557D, //CJK UNIFIED IDEOGRAPH - 0xD876: 0x558C, //CJK UNIFIED IDEOGRAPH - 0xD877: 0x55A6, //CJK UNIFIED IDEOGRAPH - 0xD878: 0x557F, //CJK UNIFIED IDEOGRAPH - 0xD879: 0x5595, //CJK UNIFIED IDEOGRAPH - 0xD87A: 0x55A1, //CJK UNIFIED IDEOGRAPH - 0xD87B: 0x558E, //CJK UNIFIED IDEOGRAPH - 0xD87C: 0x570C, //CJK UNIFIED IDEOGRAPH - 0xD87D: 0x5829, //CJK UNIFIED IDEOGRAPH - 0xD87E: 0x5837, //CJK UNIFIED IDEOGRAPH - 0xD8A1: 0x5819, //CJK UNIFIED IDEOGRAPH - 0xD8A2: 0x581E, //CJK UNIFIED IDEOGRAPH - 0xD8A3: 0x5827, //CJK UNIFIED IDEOGRAPH - 0xD8A4: 0x5823, //CJK UNIFIED IDEOGRAPH - 0xD8A5: 0x5828, //CJK UNIFIED IDEOGRAPH - 0xD8A6: 0x57F5, //CJK UNIFIED IDEOGRAPH - 0xD8A7: 0x5848, //CJK UNIFIED IDEOGRAPH - 0xD8A8: 0x5825, //CJK UNIFIED IDEOGRAPH - 0xD8A9: 0x581C, //CJK UNIFIED IDEOGRAPH - 0xD8AA: 0x581B, //CJK UNIFIED IDEOGRAPH - 0xD8AB: 0x5833, //CJK UNIFIED IDEOGRAPH - 0xD8AC: 0x583F, //CJK UNIFIED IDEOGRAPH - 0xD8AD: 0x5836, //CJK UNIFIED IDEOGRAPH - 0xD8AE: 0x582E, //CJK UNIFIED IDEOGRAPH - 0xD8AF: 0x5839, //CJK UNIFIED IDEOGRAPH - 0xD8B0: 0x5838, //CJK UNIFIED IDEOGRAPH - 0xD8B1: 0x582D, //CJK UNIFIED IDEOGRAPH - 0xD8B2: 0x582C, //CJK UNIFIED IDEOGRAPH - 0xD8B3: 0x583B, //CJK UNIFIED IDEOGRAPH - 0xD8B4: 0x5961, //CJK UNIFIED IDEOGRAPH - 0xD8B5: 0x5AAF, //CJK UNIFIED IDEOGRAPH - 0xD8B6: 0x5A94, //CJK UNIFIED IDEOGRAPH - 0xD8B7: 0x5A9F, //CJK UNIFIED IDEOGRAPH - 0xD8B8: 0x5A7A, //CJK UNIFIED IDEOGRAPH - 0xD8B9: 0x5AA2, //CJK UNIFIED IDEOGRAPH - 0xD8BA: 0x5A9E, //CJK UNIFIED IDEOGRAPH - 0xD8BB: 0x5A78, //CJK UNIFIED IDEOGRAPH - 0xD8BC: 0x5AA6, //CJK UNIFIED IDEOGRAPH - 0xD8BD: 0x5A7C, //CJK UNIFIED IDEOGRAPH - 0xD8BE: 0x5AA5, //CJK UNIFIED IDEOGRAPH - 0xD8BF: 0x5AAC, //CJK UNIFIED IDEOGRAPH - 0xD8C0: 0x5A95, //CJK UNIFIED IDEOGRAPH - 0xD8C1: 0x5AAE, //CJK UNIFIED IDEOGRAPH - 0xD8C2: 0x5A37, //CJK UNIFIED IDEOGRAPH - 0xD8C3: 0x5A84, //CJK UNIFIED IDEOGRAPH - 0xD8C4: 0x5A8A, //CJK UNIFIED IDEOGRAPH - 0xD8C5: 0x5A97, //CJK UNIFIED IDEOGRAPH - 0xD8C6: 0x5A83, //CJK UNIFIED IDEOGRAPH - 0xD8C7: 0x5A8B, //CJK UNIFIED IDEOGRAPH - 0xD8C8: 0x5AA9, //CJK UNIFIED IDEOGRAPH - 0xD8C9: 0x5A7B, //CJK UNIFIED IDEOGRAPH - 0xD8CA: 0x5A7D, //CJK UNIFIED IDEOGRAPH - 0xD8CB: 0x5A8C, //CJK UNIFIED IDEOGRAPH - 0xD8CC: 0x5A9C, //CJK UNIFIED IDEOGRAPH - 0xD8CD: 0x5A8F, //CJK UNIFIED IDEOGRAPH - 0xD8CE: 0x5A93, //CJK UNIFIED IDEOGRAPH - 0xD8CF: 0x5A9D, //CJK UNIFIED IDEOGRAPH - 0xD8D0: 0x5BEA, //CJK UNIFIED IDEOGRAPH - 0xD8D1: 0x5BCD, //CJK UNIFIED IDEOGRAPH - 0xD8D2: 0x5BCB, //CJK UNIFIED IDEOGRAPH - 0xD8D3: 0x5BD4, //CJK UNIFIED IDEOGRAPH - 0xD8D4: 0x5BD1, //CJK UNIFIED IDEOGRAPH - 0xD8D5: 0x5BCA, //CJK UNIFIED IDEOGRAPH - 0xD8D6: 0x5BCE, //CJK UNIFIED IDEOGRAPH - 0xD8D7: 0x5C0C, //CJK UNIFIED IDEOGRAPH - 0xD8D8: 0x5C30, //CJK UNIFIED IDEOGRAPH - 0xD8D9: 0x5D37, //CJK UNIFIED IDEOGRAPH - 0xD8DA: 0x5D43, //CJK UNIFIED IDEOGRAPH - 0xD8DB: 0x5D6B, //CJK UNIFIED IDEOGRAPH - 0xD8DC: 0x5D41, //CJK UNIFIED IDEOGRAPH - 0xD8DD: 0x5D4B, //CJK UNIFIED IDEOGRAPH - 0xD8DE: 0x5D3F, //CJK UNIFIED IDEOGRAPH - 0xD8DF: 0x5D35, //CJK UNIFIED IDEOGRAPH - 0xD8E0: 0x5D51, //CJK UNIFIED IDEOGRAPH - 0xD8E1: 0x5D4E, //CJK UNIFIED IDEOGRAPH - 0xD8E2: 0x5D55, //CJK UNIFIED IDEOGRAPH - 0xD8E3: 0x5D33, //CJK UNIFIED IDEOGRAPH - 0xD8E4: 0x5D3A, //CJK UNIFIED IDEOGRAPH - 0xD8E5: 0x5D52, //CJK UNIFIED IDEOGRAPH - 0xD8E6: 0x5D3D, //CJK UNIFIED IDEOGRAPH - 0xD8E7: 0x5D31, //CJK UNIFIED IDEOGRAPH - 0xD8E8: 0x5D59, //CJK UNIFIED IDEOGRAPH - 0xD8E9: 0x5D42, //CJK UNIFIED IDEOGRAPH - 0xD8EA: 0x5D39, //CJK UNIFIED IDEOGRAPH - 0xD8EB: 0x5D49, //CJK UNIFIED IDEOGRAPH - 0xD8EC: 0x5D38, //CJK UNIFIED IDEOGRAPH - 0xD8ED: 0x5D3C, //CJK UNIFIED IDEOGRAPH - 0xD8EE: 0x5D32, //CJK UNIFIED IDEOGRAPH - 0xD8EF: 0x5D36, //CJK UNIFIED IDEOGRAPH - 0xD8F0: 0x5D40, //CJK UNIFIED IDEOGRAPH - 0xD8F1: 0x5D45, //CJK UNIFIED IDEOGRAPH - 0xD8F2: 0x5E44, //CJK UNIFIED IDEOGRAPH - 0xD8F3: 0x5E41, //CJK UNIFIED IDEOGRAPH - 0xD8F4: 0x5F58, //CJK UNIFIED IDEOGRAPH - 0xD8F5: 0x5FA6, //CJK UNIFIED IDEOGRAPH - 0xD8F6: 0x5FA5, //CJK UNIFIED IDEOGRAPH - 0xD8F7: 0x5FAB, //CJK UNIFIED IDEOGRAPH - 0xD8F8: 0x60C9, //CJK UNIFIED IDEOGRAPH - 0xD8F9: 0x60B9, //CJK UNIFIED IDEOGRAPH - 0xD8FA: 0x60CC, //CJK UNIFIED IDEOGRAPH - 0xD8FB: 0x60E2, //CJK UNIFIED IDEOGRAPH - 0xD8FC: 0x60CE, //CJK UNIFIED IDEOGRAPH - 0xD8FD: 0x60C4, //CJK UNIFIED IDEOGRAPH - 0xD8FE: 0x6114, //CJK UNIFIED IDEOGRAPH - 0xD940: 0x60F2, //CJK UNIFIED IDEOGRAPH - 0xD941: 0x610A, //CJK UNIFIED IDEOGRAPH - 0xD942: 0x6116, //CJK UNIFIED IDEOGRAPH - 0xD943: 0x6105, //CJK UNIFIED IDEOGRAPH - 0xD944: 0x60F5, //CJK UNIFIED IDEOGRAPH - 0xD945: 0x6113, //CJK UNIFIED IDEOGRAPH - 0xD946: 0x60F8, //CJK UNIFIED IDEOGRAPH - 0xD947: 0x60FC, //CJK UNIFIED IDEOGRAPH - 0xD948: 0x60FE, //CJK UNIFIED IDEOGRAPH - 0xD949: 0x60C1, //CJK UNIFIED IDEOGRAPH - 0xD94A: 0x6103, //CJK UNIFIED IDEOGRAPH - 0xD94B: 0x6118, //CJK UNIFIED IDEOGRAPH - 0xD94C: 0x611D, //CJK UNIFIED IDEOGRAPH - 0xD94D: 0x6110, //CJK UNIFIED IDEOGRAPH - 0xD94E: 0x60FF, //CJK UNIFIED IDEOGRAPH - 0xD94F: 0x6104, //CJK UNIFIED IDEOGRAPH - 0xD950: 0x610B, //CJK UNIFIED IDEOGRAPH - 0xD951: 0x624A, //CJK UNIFIED IDEOGRAPH - 0xD952: 0x6394, //CJK UNIFIED IDEOGRAPH - 0xD953: 0x63B1, //CJK UNIFIED IDEOGRAPH - 0xD954: 0x63B0, //CJK UNIFIED IDEOGRAPH - 0xD955: 0x63CE, //CJK UNIFIED IDEOGRAPH - 0xD956: 0x63E5, //CJK UNIFIED IDEOGRAPH - 0xD957: 0x63E8, //CJK UNIFIED IDEOGRAPH - 0xD958: 0x63EF, //CJK UNIFIED IDEOGRAPH - 0xD959: 0x63C3, //CJK UNIFIED IDEOGRAPH - 0xD95A: 0x649D, //CJK UNIFIED IDEOGRAPH - 0xD95B: 0x63F3, //CJK UNIFIED IDEOGRAPH - 0xD95C: 0x63CA, //CJK UNIFIED IDEOGRAPH - 0xD95D: 0x63E0, //CJK UNIFIED IDEOGRAPH - 0xD95E: 0x63F6, //CJK UNIFIED IDEOGRAPH - 0xD95F: 0x63D5, //CJK UNIFIED IDEOGRAPH - 0xD960: 0x63F2, //CJK UNIFIED IDEOGRAPH - 0xD961: 0x63F5, //CJK UNIFIED IDEOGRAPH - 0xD962: 0x6461, //CJK UNIFIED IDEOGRAPH - 0xD963: 0x63DF, //CJK UNIFIED IDEOGRAPH - 0xD964: 0x63BE, //CJK UNIFIED IDEOGRAPH - 0xD965: 0x63DD, //CJK UNIFIED IDEOGRAPH - 0xD966: 0x63DC, //CJK UNIFIED IDEOGRAPH - 0xD967: 0x63C4, //CJK UNIFIED IDEOGRAPH - 0xD968: 0x63D8, //CJK UNIFIED IDEOGRAPH - 0xD969: 0x63D3, //CJK UNIFIED IDEOGRAPH - 0xD96A: 0x63C2, //CJK UNIFIED IDEOGRAPH - 0xD96B: 0x63C7, //CJK UNIFIED IDEOGRAPH - 0xD96C: 0x63CC, //CJK UNIFIED IDEOGRAPH - 0xD96D: 0x63CB, //CJK UNIFIED IDEOGRAPH - 0xD96E: 0x63C8, //CJK UNIFIED IDEOGRAPH - 0xD96F: 0x63F0, //CJK UNIFIED IDEOGRAPH - 0xD970: 0x63D7, //CJK UNIFIED IDEOGRAPH - 0xD971: 0x63D9, //CJK UNIFIED IDEOGRAPH - 0xD972: 0x6532, //CJK UNIFIED IDEOGRAPH - 0xD973: 0x6567, //CJK UNIFIED IDEOGRAPH - 0xD974: 0x656A, //CJK UNIFIED IDEOGRAPH - 0xD975: 0x6564, //CJK UNIFIED IDEOGRAPH - 0xD976: 0x655C, //CJK UNIFIED IDEOGRAPH - 0xD977: 0x6568, //CJK UNIFIED IDEOGRAPH - 0xD978: 0x6565, //CJK UNIFIED IDEOGRAPH - 0xD979: 0x658C, //CJK UNIFIED IDEOGRAPH - 0xD97A: 0x659D, //CJK UNIFIED IDEOGRAPH - 0xD97B: 0x659E, //CJK UNIFIED IDEOGRAPH - 0xD97C: 0x65AE, //CJK UNIFIED IDEOGRAPH - 0xD97D: 0x65D0, //CJK UNIFIED IDEOGRAPH - 0xD97E: 0x65D2, //CJK UNIFIED IDEOGRAPH - 0xD9A1: 0x667C, //CJK UNIFIED IDEOGRAPH - 0xD9A2: 0x666C, //CJK UNIFIED IDEOGRAPH - 0xD9A3: 0x667B, //CJK UNIFIED IDEOGRAPH - 0xD9A4: 0x6680, //CJK UNIFIED IDEOGRAPH - 0xD9A5: 0x6671, //CJK UNIFIED IDEOGRAPH - 0xD9A6: 0x6679, //CJK UNIFIED IDEOGRAPH - 0xD9A7: 0x666A, //CJK UNIFIED IDEOGRAPH - 0xD9A8: 0x6672, //CJK UNIFIED IDEOGRAPH - 0xD9A9: 0x6701, //CJK UNIFIED IDEOGRAPH - 0xD9AA: 0x690C, //CJK UNIFIED IDEOGRAPH - 0xD9AB: 0x68D3, //CJK UNIFIED IDEOGRAPH - 0xD9AC: 0x6904, //CJK UNIFIED IDEOGRAPH - 0xD9AD: 0x68DC, //CJK UNIFIED IDEOGRAPH - 0xD9AE: 0x692A, //CJK UNIFIED IDEOGRAPH - 0xD9AF: 0x68EC, //CJK UNIFIED IDEOGRAPH - 0xD9B0: 0x68EA, //CJK UNIFIED IDEOGRAPH - 0xD9B1: 0x68F1, //CJK UNIFIED IDEOGRAPH - 0xD9B2: 0x690F, //CJK UNIFIED IDEOGRAPH - 0xD9B3: 0x68D6, //CJK UNIFIED IDEOGRAPH - 0xD9B4: 0x68F7, //CJK UNIFIED IDEOGRAPH - 0xD9B5: 0x68EB, //CJK UNIFIED IDEOGRAPH - 0xD9B6: 0x68E4, //CJK UNIFIED IDEOGRAPH - 0xD9B7: 0x68F6, //CJK UNIFIED IDEOGRAPH - 0xD9B8: 0x6913, //CJK UNIFIED IDEOGRAPH - 0xD9B9: 0x6910, //CJK UNIFIED IDEOGRAPH - 0xD9BA: 0x68F3, //CJK UNIFIED IDEOGRAPH - 0xD9BB: 0x68E1, //CJK UNIFIED IDEOGRAPH - 0xD9BC: 0x6907, //CJK UNIFIED IDEOGRAPH - 0xD9BD: 0x68CC, //CJK UNIFIED IDEOGRAPH - 0xD9BE: 0x6908, //CJK UNIFIED IDEOGRAPH - 0xD9BF: 0x6970, //CJK UNIFIED IDEOGRAPH - 0xD9C0: 0x68B4, //CJK UNIFIED IDEOGRAPH - 0xD9C1: 0x6911, //CJK UNIFIED IDEOGRAPH - 0xD9C2: 0x68EF, //CJK UNIFIED IDEOGRAPH - 0xD9C3: 0x68C6, //CJK UNIFIED IDEOGRAPH - 0xD9C4: 0x6914, //CJK UNIFIED IDEOGRAPH - 0xD9C5: 0x68F8, //CJK UNIFIED IDEOGRAPH - 0xD9C6: 0x68D0, //CJK UNIFIED IDEOGRAPH - 0xD9C7: 0x68FD, //CJK UNIFIED IDEOGRAPH - 0xD9C8: 0x68FC, //CJK UNIFIED IDEOGRAPH - 0xD9C9: 0x68E8, //CJK UNIFIED IDEOGRAPH - 0xD9CA: 0x690B, //CJK UNIFIED IDEOGRAPH - 0xD9CB: 0x690A, //CJK UNIFIED IDEOGRAPH - 0xD9CC: 0x6917, //CJK UNIFIED IDEOGRAPH - 0xD9CD: 0x68CE, //CJK UNIFIED IDEOGRAPH - 0xD9CE: 0x68C8, //CJK UNIFIED IDEOGRAPH - 0xD9CF: 0x68DD, //CJK UNIFIED IDEOGRAPH - 0xD9D0: 0x68DE, //CJK UNIFIED IDEOGRAPH - 0xD9D1: 0x68E6, //CJK UNIFIED IDEOGRAPH - 0xD9D2: 0x68F4, //CJK UNIFIED IDEOGRAPH - 0xD9D3: 0x68D1, //CJK UNIFIED IDEOGRAPH - 0xD9D4: 0x6906, //CJK UNIFIED IDEOGRAPH - 0xD9D5: 0x68D4, //CJK UNIFIED IDEOGRAPH - 0xD9D6: 0x68E9, //CJK UNIFIED IDEOGRAPH - 0xD9D7: 0x6915, //CJK UNIFIED IDEOGRAPH - 0xD9D8: 0x6925, //CJK UNIFIED IDEOGRAPH - 0xD9D9: 0x68C7, //CJK UNIFIED IDEOGRAPH - 0xD9DA: 0x6B39, //CJK UNIFIED IDEOGRAPH - 0xD9DB: 0x6B3B, //CJK UNIFIED IDEOGRAPH - 0xD9DC: 0x6B3F, //CJK UNIFIED IDEOGRAPH - 0xD9DD: 0x6B3C, //CJK UNIFIED IDEOGRAPH - 0xD9DE: 0x6B94, //CJK UNIFIED IDEOGRAPH - 0xD9DF: 0x6B97, //CJK UNIFIED IDEOGRAPH - 0xD9E0: 0x6B99, //CJK UNIFIED IDEOGRAPH - 0xD9E1: 0x6B95, //CJK UNIFIED IDEOGRAPH - 0xD9E2: 0x6BBD, //CJK UNIFIED IDEOGRAPH - 0xD9E3: 0x6BF0, //CJK UNIFIED IDEOGRAPH - 0xD9E4: 0x6BF2, //CJK UNIFIED IDEOGRAPH - 0xD9E5: 0x6BF3, //CJK UNIFIED IDEOGRAPH - 0xD9E6: 0x6C30, //CJK UNIFIED IDEOGRAPH - 0xD9E7: 0x6DFC, //CJK UNIFIED IDEOGRAPH - 0xD9E8: 0x6E46, //CJK UNIFIED IDEOGRAPH - 0xD9E9: 0x6E47, //CJK UNIFIED IDEOGRAPH - 0xD9EA: 0x6E1F, //CJK UNIFIED IDEOGRAPH - 0xD9EB: 0x6E49, //CJK UNIFIED IDEOGRAPH - 0xD9EC: 0x6E88, //CJK UNIFIED IDEOGRAPH - 0xD9ED: 0x6E3C, //CJK UNIFIED IDEOGRAPH - 0xD9EE: 0x6E3D, //CJK UNIFIED IDEOGRAPH - 0xD9EF: 0x6E45, //CJK UNIFIED IDEOGRAPH - 0xD9F0: 0x6E62, //CJK UNIFIED IDEOGRAPH - 0xD9F1: 0x6E2B, //CJK UNIFIED IDEOGRAPH - 0xD9F2: 0x6E3F, //CJK UNIFIED IDEOGRAPH - 0xD9F3: 0x6E41, //CJK UNIFIED IDEOGRAPH - 0xD9F4: 0x6E5D, //CJK UNIFIED IDEOGRAPH - 0xD9F5: 0x6E73, //CJK UNIFIED IDEOGRAPH - 0xD9F6: 0x6E1C, //CJK UNIFIED IDEOGRAPH - 0xD9F7: 0x6E33, //CJK UNIFIED IDEOGRAPH - 0xD9F8: 0x6E4B, //CJK UNIFIED IDEOGRAPH - 0xD9F9: 0x6E40, //CJK UNIFIED IDEOGRAPH - 0xD9FA: 0x6E51, //CJK UNIFIED IDEOGRAPH - 0xD9FB: 0x6E3B, //CJK UNIFIED IDEOGRAPH - 0xD9FC: 0x6E03, //CJK UNIFIED IDEOGRAPH - 0xD9FD: 0x6E2E, //CJK UNIFIED IDEOGRAPH - 0xD9FE: 0x6E5E, //CJK UNIFIED IDEOGRAPH - 0xDA40: 0x6E68, //CJK UNIFIED IDEOGRAPH - 0xDA41: 0x6E5C, //CJK UNIFIED IDEOGRAPH - 0xDA42: 0x6E61, //CJK UNIFIED IDEOGRAPH - 0xDA43: 0x6E31, //CJK UNIFIED IDEOGRAPH - 0xDA44: 0x6E28, //CJK UNIFIED IDEOGRAPH - 0xDA45: 0x6E60, //CJK UNIFIED IDEOGRAPH - 0xDA46: 0x6E71, //CJK UNIFIED IDEOGRAPH - 0xDA47: 0x6E6B, //CJK UNIFIED IDEOGRAPH - 0xDA48: 0x6E39, //CJK UNIFIED IDEOGRAPH - 0xDA49: 0x6E22, //CJK UNIFIED IDEOGRAPH - 0xDA4A: 0x6E30, //CJK UNIFIED IDEOGRAPH - 0xDA4B: 0x6E53, //CJK UNIFIED IDEOGRAPH - 0xDA4C: 0x6E65, //CJK UNIFIED IDEOGRAPH - 0xDA4D: 0x6E27, //CJK UNIFIED IDEOGRAPH - 0xDA4E: 0x6E78, //CJK UNIFIED IDEOGRAPH - 0xDA4F: 0x6E64, //CJK UNIFIED IDEOGRAPH - 0xDA50: 0x6E77, //CJK UNIFIED IDEOGRAPH - 0xDA51: 0x6E55, //CJK UNIFIED IDEOGRAPH - 0xDA52: 0x6E79, //CJK UNIFIED IDEOGRAPH - 0xDA53: 0x6E52, //CJK UNIFIED IDEOGRAPH - 0xDA54: 0x6E66, //CJK UNIFIED IDEOGRAPH - 0xDA55: 0x6E35, //CJK UNIFIED IDEOGRAPH - 0xDA56: 0x6E36, //CJK UNIFIED IDEOGRAPH - 0xDA57: 0x6E5A, //CJK UNIFIED IDEOGRAPH - 0xDA58: 0x7120, //CJK UNIFIED IDEOGRAPH - 0xDA59: 0x711E, //CJK UNIFIED IDEOGRAPH - 0xDA5A: 0x712F, //CJK UNIFIED IDEOGRAPH - 0xDA5B: 0x70FB, //CJK UNIFIED IDEOGRAPH - 0xDA5C: 0x712E, //CJK UNIFIED IDEOGRAPH - 0xDA5D: 0x7131, //CJK UNIFIED IDEOGRAPH - 0xDA5E: 0x7123, //CJK UNIFIED IDEOGRAPH - 0xDA5F: 0x7125, //CJK UNIFIED IDEOGRAPH - 0xDA60: 0x7122, //CJK UNIFIED IDEOGRAPH - 0xDA61: 0x7132, //CJK UNIFIED IDEOGRAPH - 0xDA62: 0x711F, //CJK UNIFIED IDEOGRAPH - 0xDA63: 0x7128, //CJK UNIFIED IDEOGRAPH - 0xDA64: 0x713A, //CJK UNIFIED IDEOGRAPH - 0xDA65: 0x711B, //CJK UNIFIED IDEOGRAPH - 0xDA66: 0x724B, //CJK UNIFIED IDEOGRAPH - 0xDA67: 0x725A, //CJK UNIFIED IDEOGRAPH - 0xDA68: 0x7288, //CJK UNIFIED IDEOGRAPH - 0xDA69: 0x7289, //CJK UNIFIED IDEOGRAPH - 0xDA6A: 0x7286, //CJK UNIFIED IDEOGRAPH - 0xDA6B: 0x7285, //CJK UNIFIED IDEOGRAPH - 0xDA6C: 0x728B, //CJK UNIFIED IDEOGRAPH - 0xDA6D: 0x7312, //CJK UNIFIED IDEOGRAPH - 0xDA6E: 0x730B, //CJK UNIFIED IDEOGRAPH - 0xDA6F: 0x7330, //CJK UNIFIED IDEOGRAPH - 0xDA70: 0x7322, //CJK UNIFIED IDEOGRAPH - 0xDA71: 0x7331, //CJK UNIFIED IDEOGRAPH - 0xDA72: 0x7333, //CJK UNIFIED IDEOGRAPH - 0xDA73: 0x7327, //CJK UNIFIED IDEOGRAPH - 0xDA74: 0x7332, //CJK UNIFIED IDEOGRAPH - 0xDA75: 0x732D, //CJK UNIFIED IDEOGRAPH - 0xDA76: 0x7326, //CJK UNIFIED IDEOGRAPH - 0xDA77: 0x7323, //CJK UNIFIED IDEOGRAPH - 0xDA78: 0x7335, //CJK UNIFIED IDEOGRAPH - 0xDA79: 0x730C, //CJK UNIFIED IDEOGRAPH - 0xDA7A: 0x742E, //CJK UNIFIED IDEOGRAPH - 0xDA7B: 0x742C, //CJK UNIFIED IDEOGRAPH - 0xDA7C: 0x7430, //CJK UNIFIED IDEOGRAPH - 0xDA7D: 0x742B, //CJK UNIFIED IDEOGRAPH - 0xDA7E: 0x7416, //CJK UNIFIED IDEOGRAPH - 0xDAA1: 0x741A, //CJK UNIFIED IDEOGRAPH - 0xDAA2: 0x7421, //CJK UNIFIED IDEOGRAPH - 0xDAA3: 0x742D, //CJK UNIFIED IDEOGRAPH - 0xDAA4: 0x7431, //CJK UNIFIED IDEOGRAPH - 0xDAA5: 0x7424, //CJK UNIFIED IDEOGRAPH - 0xDAA6: 0x7423, //CJK UNIFIED IDEOGRAPH - 0xDAA7: 0x741D, //CJK UNIFIED IDEOGRAPH - 0xDAA8: 0x7429, //CJK UNIFIED IDEOGRAPH - 0xDAA9: 0x7420, //CJK UNIFIED IDEOGRAPH - 0xDAAA: 0x7432, //CJK UNIFIED IDEOGRAPH - 0xDAAB: 0x74FB, //CJK UNIFIED IDEOGRAPH - 0xDAAC: 0x752F, //CJK UNIFIED IDEOGRAPH - 0xDAAD: 0x756F, //CJK UNIFIED IDEOGRAPH - 0xDAAE: 0x756C, //CJK UNIFIED IDEOGRAPH - 0xDAAF: 0x75E7, //CJK UNIFIED IDEOGRAPH - 0xDAB0: 0x75DA, //CJK UNIFIED IDEOGRAPH - 0xDAB1: 0x75E1, //CJK UNIFIED IDEOGRAPH - 0xDAB2: 0x75E6, //CJK UNIFIED IDEOGRAPH - 0xDAB3: 0x75DD, //CJK UNIFIED IDEOGRAPH - 0xDAB4: 0x75DF, //CJK UNIFIED IDEOGRAPH - 0xDAB5: 0x75E4, //CJK UNIFIED IDEOGRAPH - 0xDAB6: 0x75D7, //CJK UNIFIED IDEOGRAPH - 0xDAB7: 0x7695, //CJK UNIFIED IDEOGRAPH - 0xDAB8: 0x7692, //CJK UNIFIED IDEOGRAPH - 0xDAB9: 0x76DA, //CJK UNIFIED IDEOGRAPH - 0xDABA: 0x7746, //CJK UNIFIED IDEOGRAPH - 0xDABB: 0x7747, //CJK UNIFIED IDEOGRAPH - 0xDABC: 0x7744, //CJK UNIFIED IDEOGRAPH - 0xDABD: 0x774D, //CJK UNIFIED IDEOGRAPH - 0xDABE: 0x7745, //CJK UNIFIED IDEOGRAPH - 0xDABF: 0x774A, //CJK UNIFIED IDEOGRAPH - 0xDAC0: 0x774E, //CJK UNIFIED IDEOGRAPH - 0xDAC1: 0x774B, //CJK UNIFIED IDEOGRAPH - 0xDAC2: 0x774C, //CJK UNIFIED IDEOGRAPH - 0xDAC3: 0x77DE, //CJK UNIFIED IDEOGRAPH - 0xDAC4: 0x77EC, //CJK UNIFIED IDEOGRAPH - 0xDAC5: 0x7860, //CJK UNIFIED IDEOGRAPH - 0xDAC6: 0x7864, //CJK UNIFIED IDEOGRAPH - 0xDAC7: 0x7865, //CJK UNIFIED IDEOGRAPH - 0xDAC8: 0x785C, //CJK UNIFIED IDEOGRAPH - 0xDAC9: 0x786D, //CJK UNIFIED IDEOGRAPH - 0xDACA: 0x7871, //CJK UNIFIED IDEOGRAPH - 0xDACB: 0x786A, //CJK UNIFIED IDEOGRAPH - 0xDACC: 0x786E, //CJK UNIFIED IDEOGRAPH - 0xDACD: 0x7870, //CJK UNIFIED IDEOGRAPH - 0xDACE: 0x7869, //CJK UNIFIED IDEOGRAPH - 0xDACF: 0x7868, //CJK UNIFIED IDEOGRAPH - 0xDAD0: 0x785E, //CJK UNIFIED IDEOGRAPH - 0xDAD1: 0x7862, //CJK UNIFIED IDEOGRAPH - 0xDAD2: 0x7974, //CJK UNIFIED IDEOGRAPH - 0xDAD3: 0x7973, //CJK UNIFIED IDEOGRAPH - 0xDAD4: 0x7972, //CJK UNIFIED IDEOGRAPH - 0xDAD5: 0x7970, //CJK UNIFIED IDEOGRAPH - 0xDAD6: 0x7A02, //CJK UNIFIED IDEOGRAPH - 0xDAD7: 0x7A0A, //CJK UNIFIED IDEOGRAPH - 0xDAD8: 0x7A03, //CJK UNIFIED IDEOGRAPH - 0xDAD9: 0x7A0C, //CJK UNIFIED IDEOGRAPH - 0xDADA: 0x7A04, //CJK UNIFIED IDEOGRAPH - 0xDADB: 0x7A99, //CJK UNIFIED IDEOGRAPH - 0xDADC: 0x7AE6, //CJK UNIFIED IDEOGRAPH - 0xDADD: 0x7AE4, //CJK UNIFIED IDEOGRAPH - 0xDADE: 0x7B4A, //CJK UNIFIED IDEOGRAPH - 0xDADF: 0x7B3B, //CJK UNIFIED IDEOGRAPH - 0xDAE0: 0x7B44, //CJK UNIFIED IDEOGRAPH - 0xDAE1: 0x7B48, //CJK UNIFIED IDEOGRAPH - 0xDAE2: 0x7B4C, //CJK UNIFIED IDEOGRAPH - 0xDAE3: 0x7B4E, //CJK UNIFIED IDEOGRAPH - 0xDAE4: 0x7B40, //CJK UNIFIED IDEOGRAPH - 0xDAE5: 0x7B58, //CJK UNIFIED IDEOGRAPH - 0xDAE6: 0x7B45, //CJK UNIFIED IDEOGRAPH - 0xDAE7: 0x7CA2, //CJK UNIFIED IDEOGRAPH - 0xDAE8: 0x7C9E, //CJK UNIFIED IDEOGRAPH - 0xDAE9: 0x7CA8, //CJK UNIFIED IDEOGRAPH - 0xDAEA: 0x7CA1, //CJK UNIFIED IDEOGRAPH - 0xDAEB: 0x7D58, //CJK UNIFIED IDEOGRAPH - 0xDAEC: 0x7D6F, //CJK UNIFIED IDEOGRAPH - 0xDAED: 0x7D63, //CJK UNIFIED IDEOGRAPH - 0xDAEE: 0x7D53, //CJK UNIFIED IDEOGRAPH - 0xDAEF: 0x7D56, //CJK UNIFIED IDEOGRAPH - 0xDAF0: 0x7D67, //CJK UNIFIED IDEOGRAPH - 0xDAF1: 0x7D6A, //CJK UNIFIED IDEOGRAPH - 0xDAF2: 0x7D4F, //CJK UNIFIED IDEOGRAPH - 0xDAF3: 0x7D6D, //CJK UNIFIED IDEOGRAPH - 0xDAF4: 0x7D5C, //CJK UNIFIED IDEOGRAPH - 0xDAF5: 0x7D6B, //CJK UNIFIED IDEOGRAPH - 0xDAF6: 0x7D52, //CJK UNIFIED IDEOGRAPH - 0xDAF7: 0x7D54, //CJK UNIFIED IDEOGRAPH - 0xDAF8: 0x7D69, //CJK UNIFIED IDEOGRAPH - 0xDAF9: 0x7D51, //CJK UNIFIED IDEOGRAPH - 0xDAFA: 0x7D5F, //CJK UNIFIED IDEOGRAPH - 0xDAFB: 0x7D4E, //CJK UNIFIED IDEOGRAPH - 0xDAFC: 0x7F3E, //CJK UNIFIED IDEOGRAPH - 0xDAFD: 0x7F3F, //CJK UNIFIED IDEOGRAPH - 0xDAFE: 0x7F65, //CJK UNIFIED IDEOGRAPH - 0xDB40: 0x7F66, //CJK UNIFIED IDEOGRAPH - 0xDB41: 0x7FA2, //CJK UNIFIED IDEOGRAPH - 0xDB42: 0x7FA0, //CJK UNIFIED IDEOGRAPH - 0xDB43: 0x7FA1, //CJK UNIFIED IDEOGRAPH - 0xDB44: 0x7FD7, //CJK UNIFIED IDEOGRAPH - 0xDB45: 0x8051, //CJK UNIFIED IDEOGRAPH - 0xDB46: 0x804F, //CJK UNIFIED IDEOGRAPH - 0xDB47: 0x8050, //CJK UNIFIED IDEOGRAPH - 0xDB48: 0x80FE, //CJK UNIFIED IDEOGRAPH - 0xDB49: 0x80D4, //CJK UNIFIED IDEOGRAPH - 0xDB4A: 0x8143, //CJK UNIFIED IDEOGRAPH - 0xDB4B: 0x814A, //CJK UNIFIED IDEOGRAPH - 0xDB4C: 0x8152, //CJK UNIFIED IDEOGRAPH - 0xDB4D: 0x814F, //CJK UNIFIED IDEOGRAPH - 0xDB4E: 0x8147, //CJK UNIFIED IDEOGRAPH - 0xDB4F: 0x813D, //CJK UNIFIED IDEOGRAPH - 0xDB50: 0x814D, //CJK UNIFIED IDEOGRAPH - 0xDB51: 0x813A, //CJK UNIFIED IDEOGRAPH - 0xDB52: 0x81E6, //CJK UNIFIED IDEOGRAPH - 0xDB53: 0x81EE, //CJK UNIFIED IDEOGRAPH - 0xDB54: 0x81F7, //CJK UNIFIED IDEOGRAPH - 0xDB55: 0x81F8, //CJK UNIFIED IDEOGRAPH - 0xDB56: 0x81F9, //CJK UNIFIED IDEOGRAPH - 0xDB57: 0x8204, //CJK UNIFIED IDEOGRAPH - 0xDB58: 0x823C, //CJK UNIFIED IDEOGRAPH - 0xDB59: 0x823D, //CJK UNIFIED IDEOGRAPH - 0xDB5A: 0x823F, //CJK UNIFIED IDEOGRAPH - 0xDB5B: 0x8275, //CJK UNIFIED IDEOGRAPH - 0xDB5C: 0x833B, //CJK UNIFIED IDEOGRAPH - 0xDB5D: 0x83CF, //CJK UNIFIED IDEOGRAPH - 0xDB5E: 0x83F9, //CJK UNIFIED IDEOGRAPH - 0xDB5F: 0x8423, //CJK UNIFIED IDEOGRAPH - 0xDB60: 0x83C0, //CJK UNIFIED IDEOGRAPH - 0xDB61: 0x83E8, //CJK UNIFIED IDEOGRAPH - 0xDB62: 0x8412, //CJK UNIFIED IDEOGRAPH - 0xDB63: 0x83E7, //CJK UNIFIED IDEOGRAPH - 0xDB64: 0x83E4, //CJK UNIFIED IDEOGRAPH - 0xDB65: 0x83FC, //CJK UNIFIED IDEOGRAPH - 0xDB66: 0x83F6, //CJK UNIFIED IDEOGRAPH - 0xDB67: 0x8410, //CJK UNIFIED IDEOGRAPH - 0xDB68: 0x83C6, //CJK UNIFIED IDEOGRAPH - 0xDB69: 0x83C8, //CJK UNIFIED IDEOGRAPH - 0xDB6A: 0x83EB, //CJK UNIFIED IDEOGRAPH - 0xDB6B: 0x83E3, //CJK UNIFIED IDEOGRAPH - 0xDB6C: 0x83BF, //CJK UNIFIED IDEOGRAPH - 0xDB6D: 0x8401, //CJK UNIFIED IDEOGRAPH - 0xDB6E: 0x83DD, //CJK UNIFIED IDEOGRAPH - 0xDB6F: 0x83E5, //CJK UNIFIED IDEOGRAPH - 0xDB70: 0x83D8, //CJK UNIFIED IDEOGRAPH - 0xDB71: 0x83FF, //CJK UNIFIED IDEOGRAPH - 0xDB72: 0x83E1, //CJK UNIFIED IDEOGRAPH - 0xDB73: 0x83CB, //CJK UNIFIED IDEOGRAPH - 0xDB74: 0x83CE, //CJK UNIFIED IDEOGRAPH - 0xDB75: 0x83D6, //CJK UNIFIED IDEOGRAPH - 0xDB76: 0x83F5, //CJK UNIFIED IDEOGRAPH - 0xDB77: 0x83C9, //CJK UNIFIED IDEOGRAPH - 0xDB78: 0x8409, //CJK UNIFIED IDEOGRAPH - 0xDB79: 0x840F, //CJK UNIFIED IDEOGRAPH - 0xDB7A: 0x83DE, //CJK UNIFIED IDEOGRAPH - 0xDB7B: 0x8411, //CJK UNIFIED IDEOGRAPH - 0xDB7C: 0x8406, //CJK UNIFIED IDEOGRAPH - 0xDB7D: 0x83C2, //CJK UNIFIED IDEOGRAPH - 0xDB7E: 0x83F3, //CJK UNIFIED IDEOGRAPH - 0xDBA1: 0x83D5, //CJK UNIFIED IDEOGRAPH - 0xDBA2: 0x83FA, //CJK UNIFIED IDEOGRAPH - 0xDBA3: 0x83C7, //CJK UNIFIED IDEOGRAPH - 0xDBA4: 0x83D1, //CJK UNIFIED IDEOGRAPH - 0xDBA5: 0x83EA, //CJK UNIFIED IDEOGRAPH - 0xDBA6: 0x8413, //CJK UNIFIED IDEOGRAPH - 0xDBA7: 0x83C3, //CJK UNIFIED IDEOGRAPH - 0xDBA8: 0x83EC, //CJK UNIFIED IDEOGRAPH - 0xDBA9: 0x83EE, //CJK UNIFIED IDEOGRAPH - 0xDBAA: 0x83C4, //CJK UNIFIED IDEOGRAPH - 0xDBAB: 0x83FB, //CJK UNIFIED IDEOGRAPH - 0xDBAC: 0x83D7, //CJK UNIFIED IDEOGRAPH - 0xDBAD: 0x83E2, //CJK UNIFIED IDEOGRAPH - 0xDBAE: 0x841B, //CJK UNIFIED IDEOGRAPH - 0xDBAF: 0x83DB, //CJK UNIFIED IDEOGRAPH - 0xDBB0: 0x83FE, //CJK UNIFIED IDEOGRAPH - 0xDBB1: 0x86D8, //CJK UNIFIED IDEOGRAPH - 0xDBB2: 0x86E2, //CJK UNIFIED IDEOGRAPH - 0xDBB3: 0x86E6, //CJK UNIFIED IDEOGRAPH - 0xDBB4: 0x86D3, //CJK UNIFIED IDEOGRAPH - 0xDBB5: 0x86E3, //CJK UNIFIED IDEOGRAPH - 0xDBB6: 0x86DA, //CJK UNIFIED IDEOGRAPH - 0xDBB7: 0x86EA, //CJK UNIFIED IDEOGRAPH - 0xDBB8: 0x86DD, //CJK UNIFIED IDEOGRAPH - 0xDBB9: 0x86EB, //CJK UNIFIED IDEOGRAPH - 0xDBBA: 0x86DC, //CJK UNIFIED IDEOGRAPH - 0xDBBB: 0x86EC, //CJK UNIFIED IDEOGRAPH - 0xDBBC: 0x86E9, //CJK UNIFIED IDEOGRAPH - 0xDBBD: 0x86D7, //CJK UNIFIED IDEOGRAPH - 0xDBBE: 0x86E8, //CJK UNIFIED IDEOGRAPH - 0xDBBF: 0x86D1, //CJK UNIFIED IDEOGRAPH - 0xDBC0: 0x8848, //CJK UNIFIED IDEOGRAPH - 0xDBC1: 0x8856, //CJK UNIFIED IDEOGRAPH - 0xDBC2: 0x8855, //CJK UNIFIED IDEOGRAPH - 0xDBC3: 0x88BA, //CJK UNIFIED IDEOGRAPH - 0xDBC4: 0x88D7, //CJK UNIFIED IDEOGRAPH - 0xDBC5: 0x88B9, //CJK UNIFIED IDEOGRAPH - 0xDBC6: 0x88B8, //CJK UNIFIED IDEOGRAPH - 0xDBC7: 0x88C0, //CJK UNIFIED IDEOGRAPH - 0xDBC8: 0x88BE, //CJK UNIFIED IDEOGRAPH - 0xDBC9: 0x88B6, //CJK UNIFIED IDEOGRAPH - 0xDBCA: 0x88BC, //CJK UNIFIED IDEOGRAPH - 0xDBCB: 0x88B7, //CJK UNIFIED IDEOGRAPH - 0xDBCC: 0x88BD, //CJK UNIFIED IDEOGRAPH - 0xDBCD: 0x88B2, //CJK UNIFIED IDEOGRAPH - 0xDBCE: 0x8901, //CJK UNIFIED IDEOGRAPH - 0xDBCF: 0x88C9, //CJK UNIFIED IDEOGRAPH - 0xDBD0: 0x8995, //CJK UNIFIED IDEOGRAPH - 0xDBD1: 0x8998, //CJK UNIFIED IDEOGRAPH - 0xDBD2: 0x8997, //CJK UNIFIED IDEOGRAPH - 0xDBD3: 0x89DD, //CJK UNIFIED IDEOGRAPH - 0xDBD4: 0x89DA, //CJK UNIFIED IDEOGRAPH - 0xDBD5: 0x89DB, //CJK UNIFIED IDEOGRAPH - 0xDBD6: 0x8A4E, //CJK UNIFIED IDEOGRAPH - 0xDBD7: 0x8A4D, //CJK UNIFIED IDEOGRAPH - 0xDBD8: 0x8A39, //CJK UNIFIED IDEOGRAPH - 0xDBD9: 0x8A59, //CJK UNIFIED IDEOGRAPH - 0xDBDA: 0x8A40, //CJK UNIFIED IDEOGRAPH - 0xDBDB: 0x8A57, //CJK UNIFIED IDEOGRAPH - 0xDBDC: 0x8A58, //CJK UNIFIED IDEOGRAPH - 0xDBDD: 0x8A44, //CJK UNIFIED IDEOGRAPH - 0xDBDE: 0x8A45, //CJK UNIFIED IDEOGRAPH - 0xDBDF: 0x8A52, //CJK UNIFIED IDEOGRAPH - 0xDBE0: 0x8A48, //CJK UNIFIED IDEOGRAPH - 0xDBE1: 0x8A51, //CJK UNIFIED IDEOGRAPH - 0xDBE2: 0x8A4A, //CJK UNIFIED IDEOGRAPH - 0xDBE3: 0x8A4C, //CJK UNIFIED IDEOGRAPH - 0xDBE4: 0x8A4F, //CJK UNIFIED IDEOGRAPH - 0xDBE5: 0x8C5F, //CJK UNIFIED IDEOGRAPH - 0xDBE6: 0x8C81, //CJK UNIFIED IDEOGRAPH - 0xDBE7: 0x8C80, //CJK UNIFIED IDEOGRAPH - 0xDBE8: 0x8CBA, //CJK UNIFIED IDEOGRAPH - 0xDBE9: 0x8CBE, //CJK UNIFIED IDEOGRAPH - 0xDBEA: 0x8CB0, //CJK UNIFIED IDEOGRAPH - 0xDBEB: 0x8CB9, //CJK UNIFIED IDEOGRAPH - 0xDBEC: 0x8CB5, //CJK UNIFIED IDEOGRAPH - 0xDBED: 0x8D84, //CJK UNIFIED IDEOGRAPH - 0xDBEE: 0x8D80, //CJK UNIFIED IDEOGRAPH - 0xDBEF: 0x8D89, //CJK UNIFIED IDEOGRAPH - 0xDBF0: 0x8DD8, //CJK UNIFIED IDEOGRAPH - 0xDBF1: 0x8DD3, //CJK UNIFIED IDEOGRAPH - 0xDBF2: 0x8DCD, //CJK UNIFIED IDEOGRAPH - 0xDBF3: 0x8DC7, //CJK UNIFIED IDEOGRAPH - 0xDBF4: 0x8DD6, //CJK UNIFIED IDEOGRAPH - 0xDBF5: 0x8DDC, //CJK UNIFIED IDEOGRAPH - 0xDBF6: 0x8DCF, //CJK UNIFIED IDEOGRAPH - 0xDBF7: 0x8DD5, //CJK UNIFIED IDEOGRAPH - 0xDBF8: 0x8DD9, //CJK UNIFIED IDEOGRAPH - 0xDBF9: 0x8DC8, //CJK UNIFIED IDEOGRAPH - 0xDBFA: 0x8DD7, //CJK UNIFIED IDEOGRAPH - 0xDBFB: 0x8DC5, //CJK UNIFIED IDEOGRAPH - 0xDBFC: 0x8EEF, //CJK UNIFIED IDEOGRAPH - 0xDBFD: 0x8EF7, //CJK UNIFIED IDEOGRAPH - 0xDBFE: 0x8EFA, //CJK UNIFIED IDEOGRAPH - 0xDC40: 0x8EF9, //CJK UNIFIED IDEOGRAPH - 0xDC41: 0x8EE6, //CJK UNIFIED IDEOGRAPH - 0xDC42: 0x8EEE, //CJK UNIFIED IDEOGRAPH - 0xDC43: 0x8EE5, //CJK UNIFIED IDEOGRAPH - 0xDC44: 0x8EF5, //CJK UNIFIED IDEOGRAPH - 0xDC45: 0x8EE7, //CJK UNIFIED IDEOGRAPH - 0xDC46: 0x8EE8, //CJK UNIFIED IDEOGRAPH - 0xDC47: 0x8EF6, //CJK UNIFIED IDEOGRAPH - 0xDC48: 0x8EEB, //CJK UNIFIED IDEOGRAPH - 0xDC49: 0x8EF1, //CJK UNIFIED IDEOGRAPH - 0xDC4A: 0x8EEC, //CJK UNIFIED IDEOGRAPH - 0xDC4B: 0x8EF4, //CJK UNIFIED IDEOGRAPH - 0xDC4C: 0x8EE9, //CJK UNIFIED IDEOGRAPH - 0xDC4D: 0x902D, //CJK UNIFIED IDEOGRAPH - 0xDC4E: 0x9034, //CJK UNIFIED IDEOGRAPH - 0xDC4F: 0x902F, //CJK UNIFIED IDEOGRAPH - 0xDC50: 0x9106, //CJK UNIFIED IDEOGRAPH - 0xDC51: 0x912C, //CJK UNIFIED IDEOGRAPH - 0xDC52: 0x9104, //CJK UNIFIED IDEOGRAPH - 0xDC53: 0x90FF, //CJK UNIFIED IDEOGRAPH - 0xDC54: 0x90FC, //CJK UNIFIED IDEOGRAPH - 0xDC55: 0x9108, //CJK UNIFIED IDEOGRAPH - 0xDC56: 0x90F9, //CJK UNIFIED IDEOGRAPH - 0xDC57: 0x90FB, //CJK UNIFIED IDEOGRAPH - 0xDC58: 0x9101, //CJK UNIFIED IDEOGRAPH - 0xDC59: 0x9100, //CJK UNIFIED IDEOGRAPH - 0xDC5A: 0x9107, //CJK UNIFIED IDEOGRAPH - 0xDC5B: 0x9105, //CJK UNIFIED IDEOGRAPH - 0xDC5C: 0x9103, //CJK UNIFIED IDEOGRAPH - 0xDC5D: 0x9161, //CJK UNIFIED IDEOGRAPH - 0xDC5E: 0x9164, //CJK UNIFIED IDEOGRAPH - 0xDC5F: 0x915F, //CJK UNIFIED IDEOGRAPH - 0xDC60: 0x9162, //CJK UNIFIED IDEOGRAPH - 0xDC61: 0x9160, //CJK UNIFIED IDEOGRAPH - 0xDC62: 0x9201, //CJK UNIFIED IDEOGRAPH - 0xDC63: 0x920A, //CJK UNIFIED IDEOGRAPH - 0xDC64: 0x9225, //CJK UNIFIED IDEOGRAPH - 0xDC65: 0x9203, //CJK UNIFIED IDEOGRAPH - 0xDC66: 0x921A, //CJK UNIFIED IDEOGRAPH - 0xDC67: 0x9226, //CJK UNIFIED IDEOGRAPH - 0xDC68: 0x920F, //CJK UNIFIED IDEOGRAPH - 0xDC69: 0x920C, //CJK UNIFIED IDEOGRAPH - 0xDC6A: 0x9200, //CJK UNIFIED IDEOGRAPH - 0xDC6B: 0x9212, //CJK UNIFIED IDEOGRAPH - 0xDC6C: 0x91FF, //CJK UNIFIED IDEOGRAPH - 0xDC6D: 0x91FD, //CJK UNIFIED IDEOGRAPH - 0xDC6E: 0x9206, //CJK UNIFIED IDEOGRAPH - 0xDC6F: 0x9204, //CJK UNIFIED IDEOGRAPH - 0xDC70: 0x9227, //CJK UNIFIED IDEOGRAPH - 0xDC71: 0x9202, //CJK UNIFIED IDEOGRAPH - 0xDC72: 0x921C, //CJK UNIFIED IDEOGRAPH - 0xDC73: 0x9224, //CJK UNIFIED IDEOGRAPH - 0xDC74: 0x9219, //CJK UNIFIED IDEOGRAPH - 0xDC75: 0x9217, //CJK UNIFIED IDEOGRAPH - 0xDC76: 0x9205, //CJK UNIFIED IDEOGRAPH - 0xDC77: 0x9216, //CJK UNIFIED IDEOGRAPH - 0xDC78: 0x957B, //CJK UNIFIED IDEOGRAPH - 0xDC79: 0x958D, //CJK UNIFIED IDEOGRAPH - 0xDC7A: 0x958C, //CJK UNIFIED IDEOGRAPH - 0xDC7B: 0x9590, //CJK UNIFIED IDEOGRAPH - 0xDC7C: 0x9687, //CJK UNIFIED IDEOGRAPH - 0xDC7D: 0x967E, //CJK UNIFIED IDEOGRAPH - 0xDC7E: 0x9688, //CJK UNIFIED IDEOGRAPH - 0xDCA1: 0x9689, //CJK UNIFIED IDEOGRAPH - 0xDCA2: 0x9683, //CJK UNIFIED IDEOGRAPH - 0xDCA3: 0x9680, //CJK UNIFIED IDEOGRAPH - 0xDCA4: 0x96C2, //CJK UNIFIED IDEOGRAPH - 0xDCA5: 0x96C8, //CJK UNIFIED IDEOGRAPH - 0xDCA6: 0x96C3, //CJK UNIFIED IDEOGRAPH - 0xDCA7: 0x96F1, //CJK UNIFIED IDEOGRAPH - 0xDCA8: 0x96F0, //CJK UNIFIED IDEOGRAPH - 0xDCA9: 0x976C, //CJK UNIFIED IDEOGRAPH - 0xDCAA: 0x9770, //CJK UNIFIED IDEOGRAPH - 0xDCAB: 0x976E, //CJK UNIFIED IDEOGRAPH - 0xDCAC: 0x9807, //CJK UNIFIED IDEOGRAPH - 0xDCAD: 0x98A9, //CJK UNIFIED IDEOGRAPH - 0xDCAE: 0x98EB, //CJK UNIFIED IDEOGRAPH - 0xDCAF: 0x9CE6, //CJK UNIFIED IDEOGRAPH - 0xDCB0: 0x9EF9, //CJK UNIFIED IDEOGRAPH - 0xDCB1: 0x4E83, //CJK UNIFIED IDEOGRAPH - 0xDCB2: 0x4E84, //CJK UNIFIED IDEOGRAPH - 0xDCB3: 0x4EB6, //CJK UNIFIED IDEOGRAPH - 0xDCB4: 0x50BD, //CJK UNIFIED IDEOGRAPH - 0xDCB5: 0x50BF, //CJK UNIFIED IDEOGRAPH - 0xDCB6: 0x50C6, //CJK UNIFIED IDEOGRAPH - 0xDCB7: 0x50AE, //CJK UNIFIED IDEOGRAPH - 0xDCB8: 0x50C4, //CJK UNIFIED IDEOGRAPH - 0xDCB9: 0x50CA, //CJK UNIFIED IDEOGRAPH - 0xDCBA: 0x50B4, //CJK UNIFIED IDEOGRAPH - 0xDCBB: 0x50C8, //CJK UNIFIED IDEOGRAPH - 0xDCBC: 0x50C2, //CJK UNIFIED IDEOGRAPH - 0xDCBD: 0x50B0, //CJK UNIFIED IDEOGRAPH - 0xDCBE: 0x50C1, //CJK UNIFIED IDEOGRAPH - 0xDCBF: 0x50BA, //CJK UNIFIED IDEOGRAPH - 0xDCC0: 0x50B1, //CJK UNIFIED IDEOGRAPH - 0xDCC1: 0x50CB, //CJK UNIFIED IDEOGRAPH - 0xDCC2: 0x50C9, //CJK UNIFIED IDEOGRAPH - 0xDCC3: 0x50B6, //CJK UNIFIED IDEOGRAPH - 0xDCC4: 0x50B8, //CJK UNIFIED IDEOGRAPH - 0xDCC5: 0x51D7, //CJK UNIFIED IDEOGRAPH - 0xDCC6: 0x527A, //CJK UNIFIED IDEOGRAPH - 0xDCC7: 0x5278, //CJK UNIFIED IDEOGRAPH - 0xDCC8: 0x527B, //CJK UNIFIED IDEOGRAPH - 0xDCC9: 0x527C, //CJK UNIFIED IDEOGRAPH - 0xDCCA: 0x55C3, //CJK UNIFIED IDEOGRAPH - 0xDCCB: 0x55DB, //CJK UNIFIED IDEOGRAPH - 0xDCCC: 0x55CC, //CJK UNIFIED IDEOGRAPH - 0xDCCD: 0x55D0, //CJK UNIFIED IDEOGRAPH - 0xDCCE: 0x55CB, //CJK UNIFIED IDEOGRAPH - 0xDCCF: 0x55CA, //CJK UNIFIED IDEOGRAPH - 0xDCD0: 0x55DD, //CJK UNIFIED IDEOGRAPH - 0xDCD1: 0x55C0, //CJK UNIFIED IDEOGRAPH - 0xDCD2: 0x55D4, //CJK UNIFIED IDEOGRAPH - 0xDCD3: 0x55C4, //CJK UNIFIED IDEOGRAPH - 0xDCD4: 0x55E9, //CJK UNIFIED IDEOGRAPH - 0xDCD5: 0x55BF, //CJK UNIFIED IDEOGRAPH - 0xDCD6: 0x55D2, //CJK UNIFIED IDEOGRAPH - 0xDCD7: 0x558D, //CJK UNIFIED IDEOGRAPH - 0xDCD8: 0x55CF, //CJK UNIFIED IDEOGRAPH - 0xDCD9: 0x55D5, //CJK UNIFIED IDEOGRAPH - 0xDCDA: 0x55E2, //CJK UNIFIED IDEOGRAPH - 0xDCDB: 0x55D6, //CJK UNIFIED IDEOGRAPH - 0xDCDC: 0x55C8, //CJK UNIFIED IDEOGRAPH - 0xDCDD: 0x55F2, //CJK UNIFIED IDEOGRAPH - 0xDCDE: 0x55CD, //CJK UNIFIED IDEOGRAPH - 0xDCDF: 0x55D9, //CJK UNIFIED IDEOGRAPH - 0xDCE0: 0x55C2, //CJK UNIFIED IDEOGRAPH - 0xDCE1: 0x5714, //CJK UNIFIED IDEOGRAPH - 0xDCE2: 0x5853, //CJK UNIFIED IDEOGRAPH - 0xDCE3: 0x5868, //CJK UNIFIED IDEOGRAPH - 0xDCE4: 0x5864, //CJK UNIFIED IDEOGRAPH - 0xDCE5: 0x584F, //CJK UNIFIED IDEOGRAPH - 0xDCE6: 0x584D, //CJK UNIFIED IDEOGRAPH - 0xDCE7: 0x5849, //CJK UNIFIED IDEOGRAPH - 0xDCE8: 0x586F, //CJK UNIFIED IDEOGRAPH - 0xDCE9: 0x5855, //CJK UNIFIED IDEOGRAPH - 0xDCEA: 0x584E, //CJK UNIFIED IDEOGRAPH - 0xDCEB: 0x585D, //CJK UNIFIED IDEOGRAPH - 0xDCEC: 0x5859, //CJK UNIFIED IDEOGRAPH - 0xDCED: 0x5865, //CJK UNIFIED IDEOGRAPH - 0xDCEE: 0x585B, //CJK UNIFIED IDEOGRAPH - 0xDCEF: 0x583D, //CJK UNIFIED IDEOGRAPH - 0xDCF0: 0x5863, //CJK UNIFIED IDEOGRAPH - 0xDCF1: 0x5871, //CJK UNIFIED IDEOGRAPH - 0xDCF2: 0x58FC, //CJK UNIFIED IDEOGRAPH - 0xDCF3: 0x5AC7, //CJK UNIFIED IDEOGRAPH - 0xDCF4: 0x5AC4, //CJK UNIFIED IDEOGRAPH - 0xDCF5: 0x5ACB, //CJK UNIFIED IDEOGRAPH - 0xDCF6: 0x5ABA, //CJK UNIFIED IDEOGRAPH - 0xDCF7: 0x5AB8, //CJK UNIFIED IDEOGRAPH - 0xDCF8: 0x5AB1, //CJK UNIFIED IDEOGRAPH - 0xDCF9: 0x5AB5, //CJK UNIFIED IDEOGRAPH - 0xDCFA: 0x5AB0, //CJK UNIFIED IDEOGRAPH - 0xDCFB: 0x5ABF, //CJK UNIFIED IDEOGRAPH - 0xDCFC: 0x5AC8, //CJK UNIFIED IDEOGRAPH - 0xDCFD: 0x5ABB, //CJK UNIFIED IDEOGRAPH - 0xDCFE: 0x5AC6, //CJK UNIFIED IDEOGRAPH - 0xDD40: 0x5AB7, //CJK UNIFIED IDEOGRAPH - 0xDD41: 0x5AC0, //CJK UNIFIED IDEOGRAPH - 0xDD42: 0x5ACA, //CJK UNIFIED IDEOGRAPH - 0xDD43: 0x5AB4, //CJK UNIFIED IDEOGRAPH - 0xDD44: 0x5AB6, //CJK UNIFIED IDEOGRAPH - 0xDD45: 0x5ACD, //CJK UNIFIED IDEOGRAPH - 0xDD46: 0x5AB9, //CJK UNIFIED IDEOGRAPH - 0xDD47: 0x5A90, //CJK UNIFIED IDEOGRAPH - 0xDD48: 0x5BD6, //CJK UNIFIED IDEOGRAPH - 0xDD49: 0x5BD8, //CJK UNIFIED IDEOGRAPH - 0xDD4A: 0x5BD9, //CJK UNIFIED IDEOGRAPH - 0xDD4B: 0x5C1F, //CJK UNIFIED IDEOGRAPH - 0xDD4C: 0x5C33, //CJK UNIFIED IDEOGRAPH - 0xDD4D: 0x5D71, //CJK UNIFIED IDEOGRAPH - 0xDD4E: 0x5D63, //CJK UNIFIED IDEOGRAPH - 0xDD4F: 0x5D4A, //CJK UNIFIED IDEOGRAPH - 0xDD50: 0x5D65, //CJK UNIFIED IDEOGRAPH - 0xDD51: 0x5D72, //CJK UNIFIED IDEOGRAPH - 0xDD52: 0x5D6C, //CJK UNIFIED IDEOGRAPH - 0xDD53: 0x5D5E, //CJK UNIFIED IDEOGRAPH - 0xDD54: 0x5D68, //CJK UNIFIED IDEOGRAPH - 0xDD55: 0x5D67, //CJK UNIFIED IDEOGRAPH - 0xDD56: 0x5D62, //CJK UNIFIED IDEOGRAPH - 0xDD57: 0x5DF0, //CJK UNIFIED IDEOGRAPH - 0xDD58: 0x5E4F, //CJK UNIFIED IDEOGRAPH - 0xDD59: 0x5E4E, //CJK UNIFIED IDEOGRAPH - 0xDD5A: 0x5E4A, //CJK UNIFIED IDEOGRAPH - 0xDD5B: 0x5E4D, //CJK UNIFIED IDEOGRAPH - 0xDD5C: 0x5E4B, //CJK UNIFIED IDEOGRAPH - 0xDD5D: 0x5EC5, //CJK UNIFIED IDEOGRAPH - 0xDD5E: 0x5ECC, //CJK UNIFIED IDEOGRAPH - 0xDD5F: 0x5EC6, //CJK UNIFIED IDEOGRAPH - 0xDD60: 0x5ECB, //CJK UNIFIED IDEOGRAPH - 0xDD61: 0x5EC7, //CJK UNIFIED IDEOGRAPH - 0xDD62: 0x5F40, //CJK UNIFIED IDEOGRAPH - 0xDD63: 0x5FAF, //CJK UNIFIED IDEOGRAPH - 0xDD64: 0x5FAD, //CJK UNIFIED IDEOGRAPH - 0xDD65: 0x60F7, //CJK UNIFIED IDEOGRAPH - 0xDD66: 0x6149, //CJK UNIFIED IDEOGRAPH - 0xDD67: 0x614A, //CJK UNIFIED IDEOGRAPH - 0xDD68: 0x612B, //CJK UNIFIED IDEOGRAPH - 0xDD69: 0x6145, //CJK UNIFIED IDEOGRAPH - 0xDD6A: 0x6136, //CJK UNIFIED IDEOGRAPH - 0xDD6B: 0x6132, //CJK UNIFIED IDEOGRAPH - 0xDD6C: 0x612E, //CJK UNIFIED IDEOGRAPH - 0xDD6D: 0x6146, //CJK UNIFIED IDEOGRAPH - 0xDD6E: 0x612F, //CJK UNIFIED IDEOGRAPH - 0xDD6F: 0x614F, //CJK UNIFIED IDEOGRAPH - 0xDD70: 0x6129, //CJK UNIFIED IDEOGRAPH - 0xDD71: 0x6140, //CJK UNIFIED IDEOGRAPH - 0xDD72: 0x6220, //CJK UNIFIED IDEOGRAPH - 0xDD73: 0x9168, //CJK UNIFIED IDEOGRAPH - 0xDD74: 0x6223, //CJK UNIFIED IDEOGRAPH - 0xDD75: 0x6225, //CJK UNIFIED IDEOGRAPH - 0xDD76: 0x6224, //CJK UNIFIED IDEOGRAPH - 0xDD77: 0x63C5, //CJK UNIFIED IDEOGRAPH - 0xDD78: 0x63F1, //CJK UNIFIED IDEOGRAPH - 0xDD79: 0x63EB, //CJK UNIFIED IDEOGRAPH - 0xDD7A: 0x6410, //CJK UNIFIED IDEOGRAPH - 0xDD7B: 0x6412, //CJK UNIFIED IDEOGRAPH - 0xDD7C: 0x6409, //CJK UNIFIED IDEOGRAPH - 0xDD7D: 0x6420, //CJK UNIFIED IDEOGRAPH - 0xDD7E: 0x6424, //CJK UNIFIED IDEOGRAPH - 0xDDA1: 0x6433, //CJK UNIFIED IDEOGRAPH - 0xDDA2: 0x6443, //CJK UNIFIED IDEOGRAPH - 0xDDA3: 0x641F, //CJK UNIFIED IDEOGRAPH - 0xDDA4: 0x6415, //CJK UNIFIED IDEOGRAPH - 0xDDA5: 0x6418, //CJK UNIFIED IDEOGRAPH - 0xDDA6: 0x6439, //CJK UNIFIED IDEOGRAPH - 0xDDA7: 0x6437, //CJK UNIFIED IDEOGRAPH - 0xDDA8: 0x6422, //CJK UNIFIED IDEOGRAPH - 0xDDA9: 0x6423, //CJK UNIFIED IDEOGRAPH - 0xDDAA: 0x640C, //CJK UNIFIED IDEOGRAPH - 0xDDAB: 0x6426, //CJK UNIFIED IDEOGRAPH - 0xDDAC: 0x6430, //CJK UNIFIED IDEOGRAPH - 0xDDAD: 0x6428, //CJK UNIFIED IDEOGRAPH - 0xDDAE: 0x6441, //CJK UNIFIED IDEOGRAPH - 0xDDAF: 0x6435, //CJK UNIFIED IDEOGRAPH - 0xDDB0: 0x642F, //CJK UNIFIED IDEOGRAPH - 0xDDB1: 0x640A, //CJK UNIFIED IDEOGRAPH - 0xDDB2: 0x641A, //CJK UNIFIED IDEOGRAPH - 0xDDB3: 0x6440, //CJK UNIFIED IDEOGRAPH - 0xDDB4: 0x6425, //CJK UNIFIED IDEOGRAPH - 0xDDB5: 0x6427, //CJK UNIFIED IDEOGRAPH - 0xDDB6: 0x640B, //CJK UNIFIED IDEOGRAPH - 0xDDB7: 0x63E7, //CJK UNIFIED IDEOGRAPH - 0xDDB8: 0x641B, //CJK UNIFIED IDEOGRAPH - 0xDDB9: 0x642E, //CJK UNIFIED IDEOGRAPH - 0xDDBA: 0x6421, //CJK UNIFIED IDEOGRAPH - 0xDDBB: 0x640E, //CJK UNIFIED IDEOGRAPH - 0xDDBC: 0x656F, //CJK UNIFIED IDEOGRAPH - 0xDDBD: 0x6592, //CJK UNIFIED IDEOGRAPH - 0xDDBE: 0x65D3, //CJK UNIFIED IDEOGRAPH - 0xDDBF: 0x6686, //CJK UNIFIED IDEOGRAPH - 0xDDC0: 0x668C, //CJK UNIFIED IDEOGRAPH - 0xDDC1: 0x6695, //CJK UNIFIED IDEOGRAPH - 0xDDC2: 0x6690, //CJK UNIFIED IDEOGRAPH - 0xDDC3: 0x668B, //CJK UNIFIED IDEOGRAPH - 0xDDC4: 0x668A, //CJK UNIFIED IDEOGRAPH - 0xDDC5: 0x6699, //CJK UNIFIED IDEOGRAPH - 0xDDC6: 0x6694, //CJK UNIFIED IDEOGRAPH - 0xDDC7: 0x6678, //CJK UNIFIED IDEOGRAPH - 0xDDC8: 0x6720, //CJK UNIFIED IDEOGRAPH - 0xDDC9: 0x6966, //CJK UNIFIED IDEOGRAPH - 0xDDCA: 0x695F, //CJK UNIFIED IDEOGRAPH - 0xDDCB: 0x6938, //CJK UNIFIED IDEOGRAPH - 0xDDCC: 0x694E, //CJK UNIFIED IDEOGRAPH - 0xDDCD: 0x6962, //CJK UNIFIED IDEOGRAPH - 0xDDCE: 0x6971, //CJK UNIFIED IDEOGRAPH - 0xDDCF: 0x693F, //CJK UNIFIED IDEOGRAPH - 0xDDD0: 0x6945, //CJK UNIFIED IDEOGRAPH - 0xDDD1: 0x696A, //CJK UNIFIED IDEOGRAPH - 0xDDD2: 0x6939, //CJK UNIFIED IDEOGRAPH - 0xDDD3: 0x6942, //CJK UNIFIED IDEOGRAPH - 0xDDD4: 0x6957, //CJK UNIFIED IDEOGRAPH - 0xDDD5: 0x6959, //CJK UNIFIED IDEOGRAPH - 0xDDD6: 0x697A, //CJK UNIFIED IDEOGRAPH - 0xDDD7: 0x6948, //CJK UNIFIED IDEOGRAPH - 0xDDD8: 0x6949, //CJK UNIFIED IDEOGRAPH - 0xDDD9: 0x6935, //CJK UNIFIED IDEOGRAPH - 0xDDDA: 0x696C, //CJK UNIFIED IDEOGRAPH - 0xDDDB: 0x6933, //CJK UNIFIED IDEOGRAPH - 0xDDDC: 0x693D, //CJK UNIFIED IDEOGRAPH - 0xDDDD: 0x6965, //CJK UNIFIED IDEOGRAPH - 0xDDDE: 0x68F0, //CJK UNIFIED IDEOGRAPH - 0xDDDF: 0x6978, //CJK UNIFIED IDEOGRAPH - 0xDDE0: 0x6934, //CJK UNIFIED IDEOGRAPH - 0xDDE1: 0x6969, //CJK UNIFIED IDEOGRAPH - 0xDDE2: 0x6940, //CJK UNIFIED IDEOGRAPH - 0xDDE3: 0x696F, //CJK UNIFIED IDEOGRAPH - 0xDDE4: 0x6944, //CJK UNIFIED IDEOGRAPH - 0xDDE5: 0x6976, //CJK UNIFIED IDEOGRAPH - 0xDDE6: 0x6958, //CJK UNIFIED IDEOGRAPH - 0xDDE7: 0x6941, //CJK UNIFIED IDEOGRAPH - 0xDDE8: 0x6974, //CJK UNIFIED IDEOGRAPH - 0xDDE9: 0x694C, //CJK UNIFIED IDEOGRAPH - 0xDDEA: 0x693B, //CJK UNIFIED IDEOGRAPH - 0xDDEB: 0x694B, //CJK UNIFIED IDEOGRAPH - 0xDDEC: 0x6937, //CJK UNIFIED IDEOGRAPH - 0xDDED: 0x695C, //CJK UNIFIED IDEOGRAPH - 0xDDEE: 0x694F, //CJK UNIFIED IDEOGRAPH - 0xDDEF: 0x6951, //CJK UNIFIED IDEOGRAPH - 0xDDF0: 0x6932, //CJK UNIFIED IDEOGRAPH - 0xDDF1: 0x6952, //CJK UNIFIED IDEOGRAPH - 0xDDF2: 0x692F, //CJK UNIFIED IDEOGRAPH - 0xDDF3: 0x697B, //CJK UNIFIED IDEOGRAPH - 0xDDF4: 0x693C, //CJK UNIFIED IDEOGRAPH - 0xDDF5: 0x6B46, //CJK UNIFIED IDEOGRAPH - 0xDDF6: 0x6B45, //CJK UNIFIED IDEOGRAPH - 0xDDF7: 0x6B43, //CJK UNIFIED IDEOGRAPH - 0xDDF8: 0x6B42, //CJK UNIFIED IDEOGRAPH - 0xDDF9: 0x6B48, //CJK UNIFIED IDEOGRAPH - 0xDDFA: 0x6B41, //CJK UNIFIED IDEOGRAPH - 0xDDFB: 0x6B9B, //CJK UNIFIED IDEOGRAPH - 0xDDFC: 0xFA0D, //CJK COMPATIBILITY IDEOGRAPH - 0xDDFD: 0x6BFB, //CJK UNIFIED IDEOGRAPH - 0xDDFE: 0x6BFC, //CJK UNIFIED IDEOGRAPH - 0xDE40: 0x6BF9, //CJK UNIFIED IDEOGRAPH - 0xDE41: 0x6BF7, //CJK UNIFIED IDEOGRAPH - 0xDE42: 0x6BF8, //CJK UNIFIED IDEOGRAPH - 0xDE43: 0x6E9B, //CJK UNIFIED IDEOGRAPH - 0xDE44: 0x6ED6, //CJK UNIFIED IDEOGRAPH - 0xDE45: 0x6EC8, //CJK UNIFIED IDEOGRAPH - 0xDE46: 0x6E8F, //CJK UNIFIED IDEOGRAPH - 0xDE47: 0x6EC0, //CJK UNIFIED IDEOGRAPH - 0xDE48: 0x6E9F, //CJK UNIFIED IDEOGRAPH - 0xDE49: 0x6E93, //CJK UNIFIED IDEOGRAPH - 0xDE4A: 0x6E94, //CJK UNIFIED IDEOGRAPH - 0xDE4B: 0x6EA0, //CJK UNIFIED IDEOGRAPH - 0xDE4C: 0x6EB1, //CJK UNIFIED IDEOGRAPH - 0xDE4D: 0x6EB9, //CJK UNIFIED IDEOGRAPH - 0xDE4E: 0x6EC6, //CJK UNIFIED IDEOGRAPH - 0xDE4F: 0x6ED2, //CJK UNIFIED IDEOGRAPH - 0xDE50: 0x6EBD, //CJK UNIFIED IDEOGRAPH - 0xDE51: 0x6EC1, //CJK UNIFIED IDEOGRAPH - 0xDE52: 0x6E9E, //CJK UNIFIED IDEOGRAPH - 0xDE53: 0x6EC9, //CJK UNIFIED IDEOGRAPH - 0xDE54: 0x6EB7, //CJK UNIFIED IDEOGRAPH - 0xDE55: 0x6EB0, //CJK UNIFIED IDEOGRAPH - 0xDE56: 0x6ECD, //CJK UNIFIED IDEOGRAPH - 0xDE57: 0x6EA6, //CJK UNIFIED IDEOGRAPH - 0xDE58: 0x6ECF, //CJK UNIFIED IDEOGRAPH - 0xDE59: 0x6EB2, //CJK UNIFIED IDEOGRAPH - 0xDE5A: 0x6EBE, //CJK UNIFIED IDEOGRAPH - 0xDE5B: 0x6EC3, //CJK UNIFIED IDEOGRAPH - 0xDE5C: 0x6EDC, //CJK UNIFIED IDEOGRAPH - 0xDE5D: 0x6ED8, //CJK UNIFIED IDEOGRAPH - 0xDE5E: 0x6E99, //CJK UNIFIED IDEOGRAPH - 0xDE5F: 0x6E92, //CJK UNIFIED IDEOGRAPH - 0xDE60: 0x6E8E, //CJK UNIFIED IDEOGRAPH - 0xDE61: 0x6E8D, //CJK UNIFIED IDEOGRAPH - 0xDE62: 0x6EA4, //CJK UNIFIED IDEOGRAPH - 0xDE63: 0x6EA1, //CJK UNIFIED IDEOGRAPH - 0xDE64: 0x6EBF, //CJK UNIFIED IDEOGRAPH - 0xDE65: 0x6EB3, //CJK UNIFIED IDEOGRAPH - 0xDE66: 0x6ED0, //CJK UNIFIED IDEOGRAPH - 0xDE67: 0x6ECA, //CJK UNIFIED IDEOGRAPH - 0xDE68: 0x6E97, //CJK UNIFIED IDEOGRAPH - 0xDE69: 0x6EAE, //CJK UNIFIED IDEOGRAPH - 0xDE6A: 0x6EA3, //CJK UNIFIED IDEOGRAPH - 0xDE6B: 0x7147, //CJK UNIFIED IDEOGRAPH - 0xDE6C: 0x7154, //CJK UNIFIED IDEOGRAPH - 0xDE6D: 0x7152, //CJK UNIFIED IDEOGRAPH - 0xDE6E: 0x7163, //CJK UNIFIED IDEOGRAPH - 0xDE6F: 0x7160, //CJK UNIFIED IDEOGRAPH - 0xDE70: 0x7141, //CJK UNIFIED IDEOGRAPH - 0xDE71: 0x715D, //CJK UNIFIED IDEOGRAPH - 0xDE72: 0x7162, //CJK UNIFIED IDEOGRAPH - 0xDE73: 0x7172, //CJK UNIFIED IDEOGRAPH - 0xDE74: 0x7178, //CJK UNIFIED IDEOGRAPH - 0xDE75: 0x716A, //CJK UNIFIED IDEOGRAPH - 0xDE76: 0x7161, //CJK UNIFIED IDEOGRAPH - 0xDE77: 0x7142, //CJK UNIFIED IDEOGRAPH - 0xDE78: 0x7158, //CJK UNIFIED IDEOGRAPH - 0xDE79: 0x7143, //CJK UNIFIED IDEOGRAPH - 0xDE7A: 0x714B, //CJK UNIFIED IDEOGRAPH - 0xDE7B: 0x7170, //CJK UNIFIED IDEOGRAPH - 0xDE7C: 0x715F, //CJK UNIFIED IDEOGRAPH - 0xDE7D: 0x7150, //CJK UNIFIED IDEOGRAPH - 0xDE7E: 0x7153, //CJK UNIFIED IDEOGRAPH - 0xDEA1: 0x7144, //CJK UNIFIED IDEOGRAPH - 0xDEA2: 0x714D, //CJK UNIFIED IDEOGRAPH - 0xDEA3: 0x715A, //CJK UNIFIED IDEOGRAPH - 0xDEA4: 0x724F, //CJK UNIFIED IDEOGRAPH - 0xDEA5: 0x728D, //CJK UNIFIED IDEOGRAPH - 0xDEA6: 0x728C, //CJK UNIFIED IDEOGRAPH - 0xDEA7: 0x7291, //CJK UNIFIED IDEOGRAPH - 0xDEA8: 0x7290, //CJK UNIFIED IDEOGRAPH - 0xDEA9: 0x728E, //CJK UNIFIED IDEOGRAPH - 0xDEAA: 0x733C, //CJK UNIFIED IDEOGRAPH - 0xDEAB: 0x7342, //CJK UNIFIED IDEOGRAPH - 0xDEAC: 0x733B, //CJK UNIFIED IDEOGRAPH - 0xDEAD: 0x733A, //CJK UNIFIED IDEOGRAPH - 0xDEAE: 0x7340, //CJK UNIFIED IDEOGRAPH - 0xDEAF: 0x734A, //CJK UNIFIED IDEOGRAPH - 0xDEB0: 0x7349, //CJK UNIFIED IDEOGRAPH - 0xDEB1: 0x7444, //CJK UNIFIED IDEOGRAPH - 0xDEB2: 0x744A, //CJK UNIFIED IDEOGRAPH - 0xDEB3: 0x744B, //CJK UNIFIED IDEOGRAPH - 0xDEB4: 0x7452, //CJK UNIFIED IDEOGRAPH - 0xDEB5: 0x7451, //CJK UNIFIED IDEOGRAPH - 0xDEB6: 0x7457, //CJK UNIFIED IDEOGRAPH - 0xDEB7: 0x7440, //CJK UNIFIED IDEOGRAPH - 0xDEB8: 0x744F, //CJK UNIFIED IDEOGRAPH - 0xDEB9: 0x7450, //CJK UNIFIED IDEOGRAPH - 0xDEBA: 0x744E, //CJK UNIFIED IDEOGRAPH - 0xDEBB: 0x7442, //CJK UNIFIED IDEOGRAPH - 0xDEBC: 0x7446, //CJK UNIFIED IDEOGRAPH - 0xDEBD: 0x744D, //CJK UNIFIED IDEOGRAPH - 0xDEBE: 0x7454, //CJK UNIFIED IDEOGRAPH - 0xDEBF: 0x74E1, //CJK UNIFIED IDEOGRAPH - 0xDEC0: 0x74FF, //CJK UNIFIED IDEOGRAPH - 0xDEC1: 0x74FE, //CJK UNIFIED IDEOGRAPH - 0xDEC2: 0x74FD, //CJK UNIFIED IDEOGRAPH - 0xDEC3: 0x751D, //CJK UNIFIED IDEOGRAPH - 0xDEC4: 0x7579, //CJK UNIFIED IDEOGRAPH - 0xDEC5: 0x7577, //CJK UNIFIED IDEOGRAPH - 0xDEC6: 0x6983, //CJK UNIFIED IDEOGRAPH - 0xDEC7: 0x75EF, //CJK UNIFIED IDEOGRAPH - 0xDEC8: 0x760F, //CJK UNIFIED IDEOGRAPH - 0xDEC9: 0x7603, //CJK UNIFIED IDEOGRAPH - 0xDECA: 0x75F7, //CJK UNIFIED IDEOGRAPH - 0xDECB: 0x75FE, //CJK UNIFIED IDEOGRAPH - 0xDECC: 0x75FC, //CJK UNIFIED IDEOGRAPH - 0xDECD: 0x75F9, //CJK UNIFIED IDEOGRAPH - 0xDECE: 0x75F8, //CJK UNIFIED IDEOGRAPH - 0xDECF: 0x7610, //CJK UNIFIED IDEOGRAPH - 0xDED0: 0x75FB, //CJK UNIFIED IDEOGRAPH - 0xDED1: 0x75F6, //CJK UNIFIED IDEOGRAPH - 0xDED2: 0x75ED, //CJK UNIFIED IDEOGRAPH - 0xDED3: 0x75F5, //CJK UNIFIED IDEOGRAPH - 0xDED4: 0x75FD, //CJK UNIFIED IDEOGRAPH - 0xDED5: 0x7699, //CJK UNIFIED IDEOGRAPH - 0xDED6: 0x76B5, //CJK UNIFIED IDEOGRAPH - 0xDED7: 0x76DD, //CJK UNIFIED IDEOGRAPH - 0xDED8: 0x7755, //CJK UNIFIED IDEOGRAPH - 0xDED9: 0x775F, //CJK UNIFIED IDEOGRAPH - 0xDEDA: 0x7760, //CJK UNIFIED IDEOGRAPH - 0xDEDB: 0x7752, //CJK UNIFIED IDEOGRAPH - 0xDEDC: 0x7756, //CJK UNIFIED IDEOGRAPH - 0xDEDD: 0x775A, //CJK UNIFIED IDEOGRAPH - 0xDEDE: 0x7769, //CJK UNIFIED IDEOGRAPH - 0xDEDF: 0x7767, //CJK UNIFIED IDEOGRAPH - 0xDEE0: 0x7754, //CJK UNIFIED IDEOGRAPH - 0xDEE1: 0x7759, //CJK UNIFIED IDEOGRAPH - 0xDEE2: 0x776D, //CJK UNIFIED IDEOGRAPH - 0xDEE3: 0x77E0, //CJK UNIFIED IDEOGRAPH - 0xDEE4: 0x7887, //CJK UNIFIED IDEOGRAPH - 0xDEE5: 0x789A, //CJK UNIFIED IDEOGRAPH - 0xDEE6: 0x7894, //CJK UNIFIED IDEOGRAPH - 0xDEE7: 0x788F, //CJK UNIFIED IDEOGRAPH - 0xDEE8: 0x7884, //CJK UNIFIED IDEOGRAPH - 0xDEE9: 0x7895, //CJK UNIFIED IDEOGRAPH - 0xDEEA: 0x7885, //CJK UNIFIED IDEOGRAPH - 0xDEEB: 0x7886, //CJK UNIFIED IDEOGRAPH - 0xDEEC: 0x78A1, //CJK UNIFIED IDEOGRAPH - 0xDEED: 0x7883, //CJK UNIFIED IDEOGRAPH - 0xDEEE: 0x7879, //CJK UNIFIED IDEOGRAPH - 0xDEEF: 0x7899, //CJK UNIFIED IDEOGRAPH - 0xDEF0: 0x7880, //CJK UNIFIED IDEOGRAPH - 0xDEF1: 0x7896, //CJK UNIFIED IDEOGRAPH - 0xDEF2: 0x787B, //CJK UNIFIED IDEOGRAPH - 0xDEF3: 0x797C, //CJK UNIFIED IDEOGRAPH - 0xDEF4: 0x7982, //CJK UNIFIED IDEOGRAPH - 0xDEF5: 0x797D, //CJK UNIFIED IDEOGRAPH - 0xDEF6: 0x7979, //CJK UNIFIED IDEOGRAPH - 0xDEF7: 0x7A11, //CJK UNIFIED IDEOGRAPH - 0xDEF8: 0x7A18, //CJK UNIFIED IDEOGRAPH - 0xDEF9: 0x7A19, //CJK UNIFIED IDEOGRAPH - 0xDEFA: 0x7A12, //CJK UNIFIED IDEOGRAPH - 0xDEFB: 0x7A17, //CJK UNIFIED IDEOGRAPH - 0xDEFC: 0x7A15, //CJK UNIFIED IDEOGRAPH - 0xDEFD: 0x7A22, //CJK UNIFIED IDEOGRAPH - 0xDEFE: 0x7A13, //CJK UNIFIED IDEOGRAPH - 0xDF40: 0x7A1B, //CJK UNIFIED IDEOGRAPH - 0xDF41: 0x7A10, //CJK UNIFIED IDEOGRAPH - 0xDF42: 0x7AA3, //CJK UNIFIED IDEOGRAPH - 0xDF43: 0x7AA2, //CJK UNIFIED IDEOGRAPH - 0xDF44: 0x7A9E, //CJK UNIFIED IDEOGRAPH - 0xDF45: 0x7AEB, //CJK UNIFIED IDEOGRAPH - 0xDF46: 0x7B66, //CJK UNIFIED IDEOGRAPH - 0xDF47: 0x7B64, //CJK UNIFIED IDEOGRAPH - 0xDF48: 0x7B6D, //CJK UNIFIED IDEOGRAPH - 0xDF49: 0x7B74, //CJK UNIFIED IDEOGRAPH - 0xDF4A: 0x7B69, //CJK UNIFIED IDEOGRAPH - 0xDF4B: 0x7B72, //CJK UNIFIED IDEOGRAPH - 0xDF4C: 0x7B65, //CJK UNIFIED IDEOGRAPH - 0xDF4D: 0x7B73, //CJK UNIFIED IDEOGRAPH - 0xDF4E: 0x7B71, //CJK UNIFIED IDEOGRAPH - 0xDF4F: 0x7B70, //CJK UNIFIED IDEOGRAPH - 0xDF50: 0x7B61, //CJK UNIFIED IDEOGRAPH - 0xDF51: 0x7B78, //CJK UNIFIED IDEOGRAPH - 0xDF52: 0x7B76, //CJK UNIFIED IDEOGRAPH - 0xDF53: 0x7B63, //CJK UNIFIED IDEOGRAPH - 0xDF54: 0x7CB2, //CJK UNIFIED IDEOGRAPH - 0xDF55: 0x7CB4, //CJK UNIFIED IDEOGRAPH - 0xDF56: 0x7CAF, //CJK UNIFIED IDEOGRAPH - 0xDF57: 0x7D88, //CJK UNIFIED IDEOGRAPH - 0xDF58: 0x7D86, //CJK UNIFIED IDEOGRAPH - 0xDF59: 0x7D80, //CJK UNIFIED IDEOGRAPH - 0xDF5A: 0x7D8D, //CJK UNIFIED IDEOGRAPH - 0xDF5B: 0x7D7F, //CJK UNIFIED IDEOGRAPH - 0xDF5C: 0x7D85, //CJK UNIFIED IDEOGRAPH - 0xDF5D: 0x7D7A, //CJK UNIFIED IDEOGRAPH - 0xDF5E: 0x7D8E, //CJK UNIFIED IDEOGRAPH - 0xDF5F: 0x7D7B, //CJK UNIFIED IDEOGRAPH - 0xDF60: 0x7D83, //CJK UNIFIED IDEOGRAPH - 0xDF61: 0x7D7C, //CJK UNIFIED IDEOGRAPH - 0xDF62: 0x7D8C, //CJK UNIFIED IDEOGRAPH - 0xDF63: 0x7D94, //CJK UNIFIED IDEOGRAPH - 0xDF64: 0x7D84, //CJK UNIFIED IDEOGRAPH - 0xDF65: 0x7D7D, //CJK UNIFIED IDEOGRAPH - 0xDF66: 0x7D92, //CJK UNIFIED IDEOGRAPH - 0xDF67: 0x7F6D, //CJK UNIFIED IDEOGRAPH - 0xDF68: 0x7F6B, //CJK UNIFIED IDEOGRAPH - 0xDF69: 0x7F67, //CJK UNIFIED IDEOGRAPH - 0xDF6A: 0x7F68, //CJK UNIFIED IDEOGRAPH - 0xDF6B: 0x7F6C, //CJK UNIFIED IDEOGRAPH - 0xDF6C: 0x7FA6, //CJK UNIFIED IDEOGRAPH - 0xDF6D: 0x7FA5, //CJK UNIFIED IDEOGRAPH - 0xDF6E: 0x7FA7, //CJK UNIFIED IDEOGRAPH - 0xDF6F: 0x7FDB, //CJK UNIFIED IDEOGRAPH - 0xDF70: 0x7FDC, //CJK UNIFIED IDEOGRAPH - 0xDF71: 0x8021, //CJK UNIFIED IDEOGRAPH - 0xDF72: 0x8164, //CJK UNIFIED IDEOGRAPH - 0xDF73: 0x8160, //CJK UNIFIED IDEOGRAPH - 0xDF74: 0x8177, //CJK UNIFIED IDEOGRAPH - 0xDF75: 0x815C, //CJK UNIFIED IDEOGRAPH - 0xDF76: 0x8169, //CJK UNIFIED IDEOGRAPH - 0xDF77: 0x815B, //CJK UNIFIED IDEOGRAPH - 0xDF78: 0x8162, //CJK UNIFIED IDEOGRAPH - 0xDF79: 0x8172, //CJK UNIFIED IDEOGRAPH - 0xDF7A: 0x6721, //CJK UNIFIED IDEOGRAPH - 0xDF7B: 0x815E, //CJK UNIFIED IDEOGRAPH - 0xDF7C: 0x8176, //CJK UNIFIED IDEOGRAPH - 0xDF7D: 0x8167, //CJK UNIFIED IDEOGRAPH - 0xDF7E: 0x816F, //CJK UNIFIED IDEOGRAPH - 0xDFA1: 0x8144, //CJK UNIFIED IDEOGRAPH - 0xDFA2: 0x8161, //CJK UNIFIED IDEOGRAPH - 0xDFA3: 0x821D, //CJK UNIFIED IDEOGRAPH - 0xDFA4: 0x8249, //CJK UNIFIED IDEOGRAPH - 0xDFA5: 0x8244, //CJK UNIFIED IDEOGRAPH - 0xDFA6: 0x8240, //CJK UNIFIED IDEOGRAPH - 0xDFA7: 0x8242, //CJK UNIFIED IDEOGRAPH - 0xDFA8: 0x8245, //CJK UNIFIED IDEOGRAPH - 0xDFA9: 0x84F1, //CJK UNIFIED IDEOGRAPH - 0xDFAA: 0x843F, //CJK UNIFIED IDEOGRAPH - 0xDFAB: 0x8456, //CJK UNIFIED IDEOGRAPH - 0xDFAC: 0x8476, //CJK UNIFIED IDEOGRAPH - 0xDFAD: 0x8479, //CJK UNIFIED IDEOGRAPH - 0xDFAE: 0x848F, //CJK UNIFIED IDEOGRAPH - 0xDFAF: 0x848D, //CJK UNIFIED IDEOGRAPH - 0xDFB0: 0x8465, //CJK UNIFIED IDEOGRAPH - 0xDFB1: 0x8451, //CJK UNIFIED IDEOGRAPH - 0xDFB2: 0x8440, //CJK UNIFIED IDEOGRAPH - 0xDFB3: 0x8486, //CJK UNIFIED IDEOGRAPH - 0xDFB4: 0x8467, //CJK UNIFIED IDEOGRAPH - 0xDFB5: 0x8430, //CJK UNIFIED IDEOGRAPH - 0xDFB6: 0x844D, //CJK UNIFIED IDEOGRAPH - 0xDFB7: 0x847D, //CJK UNIFIED IDEOGRAPH - 0xDFB8: 0x845A, //CJK UNIFIED IDEOGRAPH - 0xDFB9: 0x8459, //CJK UNIFIED IDEOGRAPH - 0xDFBA: 0x8474, //CJK UNIFIED IDEOGRAPH - 0xDFBB: 0x8473, //CJK UNIFIED IDEOGRAPH - 0xDFBC: 0x845D, //CJK UNIFIED IDEOGRAPH - 0xDFBD: 0x8507, //CJK UNIFIED IDEOGRAPH - 0xDFBE: 0x845E, //CJK UNIFIED IDEOGRAPH - 0xDFBF: 0x8437, //CJK UNIFIED IDEOGRAPH - 0xDFC0: 0x843A, //CJK UNIFIED IDEOGRAPH - 0xDFC1: 0x8434, //CJK UNIFIED IDEOGRAPH - 0xDFC2: 0x847A, //CJK UNIFIED IDEOGRAPH - 0xDFC3: 0x8443, //CJK UNIFIED IDEOGRAPH - 0xDFC4: 0x8478, //CJK UNIFIED IDEOGRAPH - 0xDFC5: 0x8432, //CJK UNIFIED IDEOGRAPH - 0xDFC6: 0x8445, //CJK UNIFIED IDEOGRAPH - 0xDFC7: 0x8429, //CJK UNIFIED IDEOGRAPH - 0xDFC8: 0x83D9, //CJK UNIFIED IDEOGRAPH - 0xDFC9: 0x844B, //CJK UNIFIED IDEOGRAPH - 0xDFCA: 0x842F, //CJK UNIFIED IDEOGRAPH - 0xDFCB: 0x8442, //CJK UNIFIED IDEOGRAPH - 0xDFCC: 0x842D, //CJK UNIFIED IDEOGRAPH - 0xDFCD: 0x845F, //CJK UNIFIED IDEOGRAPH - 0xDFCE: 0x8470, //CJK UNIFIED IDEOGRAPH - 0xDFCF: 0x8439, //CJK UNIFIED IDEOGRAPH - 0xDFD0: 0x844E, //CJK UNIFIED IDEOGRAPH - 0xDFD1: 0x844C, //CJK UNIFIED IDEOGRAPH - 0xDFD2: 0x8452, //CJK UNIFIED IDEOGRAPH - 0xDFD3: 0x846F, //CJK UNIFIED IDEOGRAPH - 0xDFD4: 0x84C5, //CJK UNIFIED IDEOGRAPH - 0xDFD5: 0x848E, //CJK UNIFIED IDEOGRAPH - 0xDFD6: 0x843B, //CJK UNIFIED IDEOGRAPH - 0xDFD7: 0x8447, //CJK UNIFIED IDEOGRAPH - 0xDFD8: 0x8436, //CJK UNIFIED IDEOGRAPH - 0xDFD9: 0x8433, //CJK UNIFIED IDEOGRAPH - 0xDFDA: 0x8468, //CJK UNIFIED IDEOGRAPH - 0xDFDB: 0x847E, //CJK UNIFIED IDEOGRAPH - 0xDFDC: 0x8444, //CJK UNIFIED IDEOGRAPH - 0xDFDD: 0x842B, //CJK UNIFIED IDEOGRAPH - 0xDFDE: 0x8460, //CJK UNIFIED IDEOGRAPH - 0xDFDF: 0x8454, //CJK UNIFIED IDEOGRAPH - 0xDFE0: 0x846E, //CJK UNIFIED IDEOGRAPH - 0xDFE1: 0x8450, //CJK UNIFIED IDEOGRAPH - 0xDFE2: 0x870B, //CJK UNIFIED IDEOGRAPH - 0xDFE3: 0x8704, //CJK UNIFIED IDEOGRAPH - 0xDFE4: 0x86F7, //CJK UNIFIED IDEOGRAPH - 0xDFE5: 0x870C, //CJK UNIFIED IDEOGRAPH - 0xDFE6: 0x86FA, //CJK UNIFIED IDEOGRAPH - 0xDFE7: 0x86D6, //CJK UNIFIED IDEOGRAPH - 0xDFE8: 0x86F5, //CJK UNIFIED IDEOGRAPH - 0xDFE9: 0x874D, //CJK UNIFIED IDEOGRAPH - 0xDFEA: 0x86F8, //CJK UNIFIED IDEOGRAPH - 0xDFEB: 0x870E, //CJK UNIFIED IDEOGRAPH - 0xDFEC: 0x8709, //CJK UNIFIED IDEOGRAPH - 0xDFED: 0x8701, //CJK UNIFIED IDEOGRAPH - 0xDFEE: 0x86F6, //CJK UNIFIED IDEOGRAPH - 0xDFEF: 0x870D, //CJK UNIFIED IDEOGRAPH - 0xDFF0: 0x8705, //CJK UNIFIED IDEOGRAPH - 0xDFF1: 0x88D6, //CJK UNIFIED IDEOGRAPH - 0xDFF2: 0x88CB, //CJK UNIFIED IDEOGRAPH - 0xDFF3: 0x88CD, //CJK UNIFIED IDEOGRAPH - 0xDFF4: 0x88CE, //CJK UNIFIED IDEOGRAPH - 0xDFF5: 0x88DE, //CJK UNIFIED IDEOGRAPH - 0xDFF6: 0x88DB, //CJK UNIFIED IDEOGRAPH - 0xDFF7: 0x88DA, //CJK UNIFIED IDEOGRAPH - 0xDFF8: 0x88CC, //CJK UNIFIED IDEOGRAPH - 0xDFF9: 0x88D0, //CJK UNIFIED IDEOGRAPH - 0xDFFA: 0x8985, //CJK UNIFIED IDEOGRAPH - 0xDFFB: 0x899B, //CJK UNIFIED IDEOGRAPH - 0xDFFC: 0x89DF, //CJK UNIFIED IDEOGRAPH - 0xDFFD: 0x89E5, //CJK UNIFIED IDEOGRAPH - 0xDFFE: 0x89E4, //CJK UNIFIED IDEOGRAPH - 0xE040: 0x89E1, //CJK UNIFIED IDEOGRAPH - 0xE041: 0x89E0, //CJK UNIFIED IDEOGRAPH - 0xE042: 0x89E2, //CJK UNIFIED IDEOGRAPH - 0xE043: 0x89DC, //CJK UNIFIED IDEOGRAPH - 0xE044: 0x89E6, //CJK UNIFIED IDEOGRAPH - 0xE045: 0x8A76, //CJK UNIFIED IDEOGRAPH - 0xE046: 0x8A86, //CJK UNIFIED IDEOGRAPH - 0xE047: 0x8A7F, //CJK UNIFIED IDEOGRAPH - 0xE048: 0x8A61, //CJK UNIFIED IDEOGRAPH - 0xE049: 0x8A3F, //CJK UNIFIED IDEOGRAPH - 0xE04A: 0x8A77, //CJK UNIFIED IDEOGRAPH - 0xE04B: 0x8A82, //CJK UNIFIED IDEOGRAPH - 0xE04C: 0x8A84, //CJK UNIFIED IDEOGRAPH - 0xE04D: 0x8A75, //CJK UNIFIED IDEOGRAPH - 0xE04E: 0x8A83, //CJK UNIFIED IDEOGRAPH - 0xE04F: 0x8A81, //CJK UNIFIED IDEOGRAPH - 0xE050: 0x8A74, //CJK UNIFIED IDEOGRAPH - 0xE051: 0x8A7A, //CJK UNIFIED IDEOGRAPH - 0xE052: 0x8C3C, //CJK UNIFIED IDEOGRAPH - 0xE053: 0x8C4B, //CJK UNIFIED IDEOGRAPH - 0xE054: 0x8C4A, //CJK UNIFIED IDEOGRAPH - 0xE055: 0x8C65, //CJK UNIFIED IDEOGRAPH - 0xE056: 0x8C64, //CJK UNIFIED IDEOGRAPH - 0xE057: 0x8C66, //CJK UNIFIED IDEOGRAPH - 0xE058: 0x8C86, //CJK UNIFIED IDEOGRAPH - 0xE059: 0x8C84, //CJK UNIFIED IDEOGRAPH - 0xE05A: 0x8C85, //CJK UNIFIED IDEOGRAPH - 0xE05B: 0x8CCC, //CJK UNIFIED IDEOGRAPH - 0xE05C: 0x8D68, //CJK UNIFIED IDEOGRAPH - 0xE05D: 0x8D69, //CJK UNIFIED IDEOGRAPH - 0xE05E: 0x8D91, //CJK UNIFIED IDEOGRAPH - 0xE05F: 0x8D8C, //CJK UNIFIED IDEOGRAPH - 0xE060: 0x8D8E, //CJK UNIFIED IDEOGRAPH - 0xE061: 0x8D8F, //CJK UNIFIED IDEOGRAPH - 0xE062: 0x8D8D, //CJK UNIFIED IDEOGRAPH - 0xE063: 0x8D93, //CJK UNIFIED IDEOGRAPH - 0xE064: 0x8D94, //CJK UNIFIED IDEOGRAPH - 0xE065: 0x8D90, //CJK UNIFIED IDEOGRAPH - 0xE066: 0x8D92, //CJK UNIFIED IDEOGRAPH - 0xE067: 0x8DF0, //CJK UNIFIED IDEOGRAPH - 0xE068: 0x8DE0, //CJK UNIFIED IDEOGRAPH - 0xE069: 0x8DEC, //CJK UNIFIED IDEOGRAPH - 0xE06A: 0x8DF1, //CJK UNIFIED IDEOGRAPH - 0xE06B: 0x8DEE, //CJK UNIFIED IDEOGRAPH - 0xE06C: 0x8DD0, //CJK UNIFIED IDEOGRAPH - 0xE06D: 0x8DE9, //CJK UNIFIED IDEOGRAPH - 0xE06E: 0x8DE3, //CJK UNIFIED IDEOGRAPH - 0xE06F: 0x8DE2, //CJK UNIFIED IDEOGRAPH - 0xE070: 0x8DE7, //CJK UNIFIED IDEOGRAPH - 0xE071: 0x8DF2, //CJK UNIFIED IDEOGRAPH - 0xE072: 0x8DEB, //CJK UNIFIED IDEOGRAPH - 0xE073: 0x8DF4, //CJK UNIFIED IDEOGRAPH - 0xE074: 0x8F06, //CJK UNIFIED IDEOGRAPH - 0xE075: 0x8EFF, //CJK UNIFIED IDEOGRAPH - 0xE076: 0x8F01, //CJK UNIFIED IDEOGRAPH - 0xE077: 0x8F00, //CJK UNIFIED IDEOGRAPH - 0xE078: 0x8F05, //CJK UNIFIED IDEOGRAPH - 0xE079: 0x8F07, //CJK UNIFIED IDEOGRAPH - 0xE07A: 0x8F08, //CJK UNIFIED IDEOGRAPH - 0xE07B: 0x8F02, //CJK UNIFIED IDEOGRAPH - 0xE07C: 0x8F0B, //CJK UNIFIED IDEOGRAPH - 0xE07D: 0x9052, //CJK UNIFIED IDEOGRAPH - 0xE07E: 0x903F, //CJK UNIFIED IDEOGRAPH - 0xE0A1: 0x9044, //CJK UNIFIED IDEOGRAPH - 0xE0A2: 0x9049, //CJK UNIFIED IDEOGRAPH - 0xE0A3: 0x903D, //CJK UNIFIED IDEOGRAPH - 0xE0A4: 0x9110, //CJK UNIFIED IDEOGRAPH - 0xE0A5: 0x910D, //CJK UNIFIED IDEOGRAPH - 0xE0A6: 0x910F, //CJK UNIFIED IDEOGRAPH - 0xE0A7: 0x9111, //CJK UNIFIED IDEOGRAPH - 0xE0A8: 0x9116, //CJK UNIFIED IDEOGRAPH - 0xE0A9: 0x9114, //CJK UNIFIED IDEOGRAPH - 0xE0AA: 0x910B, //CJK UNIFIED IDEOGRAPH - 0xE0AB: 0x910E, //CJK UNIFIED IDEOGRAPH - 0xE0AC: 0x916E, //CJK UNIFIED IDEOGRAPH - 0xE0AD: 0x916F, //CJK UNIFIED IDEOGRAPH - 0xE0AE: 0x9248, //CJK UNIFIED IDEOGRAPH - 0xE0AF: 0x9252, //CJK UNIFIED IDEOGRAPH - 0xE0B0: 0x9230, //CJK UNIFIED IDEOGRAPH - 0xE0B1: 0x923A, //CJK UNIFIED IDEOGRAPH - 0xE0B2: 0x9266, //CJK UNIFIED IDEOGRAPH - 0xE0B3: 0x9233, //CJK UNIFIED IDEOGRAPH - 0xE0B4: 0x9265, //CJK UNIFIED IDEOGRAPH - 0xE0B5: 0x925E, //CJK UNIFIED IDEOGRAPH - 0xE0B6: 0x9283, //CJK UNIFIED IDEOGRAPH - 0xE0B7: 0x922E, //CJK UNIFIED IDEOGRAPH - 0xE0B8: 0x924A, //CJK UNIFIED IDEOGRAPH - 0xE0B9: 0x9246, //CJK UNIFIED IDEOGRAPH - 0xE0BA: 0x926D, //CJK UNIFIED IDEOGRAPH - 0xE0BB: 0x926C, //CJK UNIFIED IDEOGRAPH - 0xE0BC: 0x924F, //CJK UNIFIED IDEOGRAPH - 0xE0BD: 0x9260, //CJK UNIFIED IDEOGRAPH - 0xE0BE: 0x9267, //CJK UNIFIED IDEOGRAPH - 0xE0BF: 0x926F, //CJK UNIFIED IDEOGRAPH - 0xE0C0: 0x9236, //CJK UNIFIED IDEOGRAPH - 0xE0C1: 0x9261, //CJK UNIFIED IDEOGRAPH - 0xE0C2: 0x9270, //CJK UNIFIED IDEOGRAPH - 0xE0C3: 0x9231, //CJK UNIFIED IDEOGRAPH - 0xE0C4: 0x9254, //CJK UNIFIED IDEOGRAPH - 0xE0C5: 0x9263, //CJK UNIFIED IDEOGRAPH - 0xE0C6: 0x9250, //CJK UNIFIED IDEOGRAPH - 0xE0C7: 0x9272, //CJK UNIFIED IDEOGRAPH - 0xE0C8: 0x924E, //CJK UNIFIED IDEOGRAPH - 0xE0C9: 0x9253, //CJK UNIFIED IDEOGRAPH - 0xE0CA: 0x924C, //CJK UNIFIED IDEOGRAPH - 0xE0CB: 0x9256, //CJK UNIFIED IDEOGRAPH - 0xE0CC: 0x9232, //CJK UNIFIED IDEOGRAPH - 0xE0CD: 0x959F, //CJK UNIFIED IDEOGRAPH - 0xE0CE: 0x959C, //CJK UNIFIED IDEOGRAPH - 0xE0CF: 0x959E, //CJK UNIFIED IDEOGRAPH - 0xE0D0: 0x959B, //CJK UNIFIED IDEOGRAPH - 0xE0D1: 0x9692, //CJK UNIFIED IDEOGRAPH - 0xE0D2: 0x9693, //CJK UNIFIED IDEOGRAPH - 0xE0D3: 0x9691, //CJK UNIFIED IDEOGRAPH - 0xE0D4: 0x9697, //CJK UNIFIED IDEOGRAPH - 0xE0D5: 0x96CE, //CJK UNIFIED IDEOGRAPH - 0xE0D6: 0x96FA, //CJK UNIFIED IDEOGRAPH - 0xE0D7: 0x96FD, //CJK UNIFIED IDEOGRAPH - 0xE0D8: 0x96F8, //CJK UNIFIED IDEOGRAPH - 0xE0D9: 0x96F5, //CJK UNIFIED IDEOGRAPH - 0xE0DA: 0x9773, //CJK UNIFIED IDEOGRAPH - 0xE0DB: 0x9777, //CJK UNIFIED IDEOGRAPH - 0xE0DC: 0x9778, //CJK UNIFIED IDEOGRAPH - 0xE0DD: 0x9772, //CJK UNIFIED IDEOGRAPH - 0xE0DE: 0x980F, //CJK UNIFIED IDEOGRAPH - 0xE0DF: 0x980D, //CJK UNIFIED IDEOGRAPH - 0xE0E0: 0x980E, //CJK UNIFIED IDEOGRAPH - 0xE0E1: 0x98AC, //CJK UNIFIED IDEOGRAPH - 0xE0E2: 0x98F6, //CJK UNIFIED IDEOGRAPH - 0xE0E3: 0x98F9, //CJK UNIFIED IDEOGRAPH - 0xE0E4: 0x99AF, //CJK UNIFIED IDEOGRAPH - 0xE0E5: 0x99B2, //CJK UNIFIED IDEOGRAPH - 0xE0E6: 0x99B0, //CJK UNIFIED IDEOGRAPH - 0xE0E7: 0x99B5, //CJK UNIFIED IDEOGRAPH - 0xE0E8: 0x9AAD, //CJK UNIFIED IDEOGRAPH - 0xE0E9: 0x9AAB, //CJK UNIFIED IDEOGRAPH - 0xE0EA: 0x9B5B, //CJK UNIFIED IDEOGRAPH - 0xE0EB: 0x9CEA, //CJK UNIFIED IDEOGRAPH - 0xE0EC: 0x9CED, //CJK UNIFIED IDEOGRAPH - 0xE0ED: 0x9CE7, //CJK UNIFIED IDEOGRAPH - 0xE0EE: 0x9E80, //CJK UNIFIED IDEOGRAPH - 0xE0EF: 0x9EFD, //CJK UNIFIED IDEOGRAPH - 0xE0F0: 0x50E6, //CJK UNIFIED IDEOGRAPH - 0xE0F1: 0x50D4, //CJK UNIFIED IDEOGRAPH - 0xE0F2: 0x50D7, //CJK UNIFIED IDEOGRAPH - 0xE0F3: 0x50E8, //CJK UNIFIED IDEOGRAPH - 0xE0F4: 0x50F3, //CJK UNIFIED IDEOGRAPH - 0xE0F5: 0x50DB, //CJK UNIFIED IDEOGRAPH - 0xE0F6: 0x50EA, //CJK UNIFIED IDEOGRAPH - 0xE0F7: 0x50DD, //CJK UNIFIED IDEOGRAPH - 0xE0F8: 0x50E4, //CJK UNIFIED IDEOGRAPH - 0xE0F9: 0x50D3, //CJK UNIFIED IDEOGRAPH - 0xE0FA: 0x50EC, //CJK UNIFIED IDEOGRAPH - 0xE0FB: 0x50F0, //CJK UNIFIED IDEOGRAPH - 0xE0FC: 0x50EF, //CJK UNIFIED IDEOGRAPH - 0xE0FD: 0x50E3, //CJK UNIFIED IDEOGRAPH - 0xE0FE: 0x50E0, //CJK UNIFIED IDEOGRAPH - 0xE140: 0x51D8, //CJK UNIFIED IDEOGRAPH - 0xE141: 0x5280, //CJK UNIFIED IDEOGRAPH - 0xE142: 0x5281, //CJK UNIFIED IDEOGRAPH - 0xE143: 0x52E9, //CJK UNIFIED IDEOGRAPH - 0xE144: 0x52EB, //CJK UNIFIED IDEOGRAPH - 0xE145: 0x5330, //CJK UNIFIED IDEOGRAPH - 0xE146: 0x53AC, //CJK UNIFIED IDEOGRAPH - 0xE147: 0x5627, //CJK UNIFIED IDEOGRAPH - 0xE148: 0x5615, //CJK UNIFIED IDEOGRAPH - 0xE149: 0x560C, //CJK UNIFIED IDEOGRAPH - 0xE14A: 0x5612, //CJK UNIFIED IDEOGRAPH - 0xE14B: 0x55FC, //CJK UNIFIED IDEOGRAPH - 0xE14C: 0x560F, //CJK UNIFIED IDEOGRAPH - 0xE14D: 0x561C, //CJK UNIFIED IDEOGRAPH - 0xE14E: 0x5601, //CJK UNIFIED IDEOGRAPH - 0xE14F: 0x5613, //CJK UNIFIED IDEOGRAPH - 0xE150: 0x5602, //CJK UNIFIED IDEOGRAPH - 0xE151: 0x55FA, //CJK UNIFIED IDEOGRAPH - 0xE152: 0x561D, //CJK UNIFIED IDEOGRAPH - 0xE153: 0x5604, //CJK UNIFIED IDEOGRAPH - 0xE154: 0x55FF, //CJK UNIFIED IDEOGRAPH - 0xE155: 0x55F9, //CJK UNIFIED IDEOGRAPH - 0xE156: 0x5889, //CJK UNIFIED IDEOGRAPH - 0xE157: 0x587C, //CJK UNIFIED IDEOGRAPH - 0xE158: 0x5890, //CJK UNIFIED IDEOGRAPH - 0xE159: 0x5898, //CJK UNIFIED IDEOGRAPH - 0xE15A: 0x5886, //CJK UNIFIED IDEOGRAPH - 0xE15B: 0x5881, //CJK UNIFIED IDEOGRAPH - 0xE15C: 0x587F, //CJK UNIFIED IDEOGRAPH - 0xE15D: 0x5874, //CJK UNIFIED IDEOGRAPH - 0xE15E: 0x588B, //CJK UNIFIED IDEOGRAPH - 0xE15F: 0x587A, //CJK UNIFIED IDEOGRAPH - 0xE160: 0x5887, //CJK UNIFIED IDEOGRAPH - 0xE161: 0x5891, //CJK UNIFIED IDEOGRAPH - 0xE162: 0x588E, //CJK UNIFIED IDEOGRAPH - 0xE163: 0x5876, //CJK UNIFIED IDEOGRAPH - 0xE164: 0x5882, //CJK UNIFIED IDEOGRAPH - 0xE165: 0x5888, //CJK UNIFIED IDEOGRAPH - 0xE166: 0x587B, //CJK UNIFIED IDEOGRAPH - 0xE167: 0x5894, //CJK UNIFIED IDEOGRAPH - 0xE168: 0x588F, //CJK UNIFIED IDEOGRAPH - 0xE169: 0x58FE, //CJK UNIFIED IDEOGRAPH - 0xE16A: 0x596B, //CJK UNIFIED IDEOGRAPH - 0xE16B: 0x5ADC, //CJK UNIFIED IDEOGRAPH - 0xE16C: 0x5AEE, //CJK UNIFIED IDEOGRAPH - 0xE16D: 0x5AE5, //CJK UNIFIED IDEOGRAPH - 0xE16E: 0x5AD5, //CJK UNIFIED IDEOGRAPH - 0xE16F: 0x5AEA, //CJK UNIFIED IDEOGRAPH - 0xE170: 0x5ADA, //CJK UNIFIED IDEOGRAPH - 0xE171: 0x5AED, //CJK UNIFIED IDEOGRAPH - 0xE172: 0x5AEB, //CJK UNIFIED IDEOGRAPH - 0xE173: 0x5AF3, //CJK UNIFIED IDEOGRAPH - 0xE174: 0x5AE2, //CJK UNIFIED IDEOGRAPH - 0xE175: 0x5AE0, //CJK UNIFIED IDEOGRAPH - 0xE176: 0x5ADB, //CJK UNIFIED IDEOGRAPH - 0xE177: 0x5AEC, //CJK UNIFIED IDEOGRAPH - 0xE178: 0x5ADE, //CJK UNIFIED IDEOGRAPH - 0xE179: 0x5ADD, //CJK UNIFIED IDEOGRAPH - 0xE17A: 0x5AD9, //CJK UNIFIED IDEOGRAPH - 0xE17B: 0x5AE8, //CJK UNIFIED IDEOGRAPH - 0xE17C: 0x5ADF, //CJK UNIFIED IDEOGRAPH - 0xE17D: 0x5B77, //CJK UNIFIED IDEOGRAPH - 0xE17E: 0x5BE0, //CJK UNIFIED IDEOGRAPH - 0xE1A1: 0x5BE3, //CJK UNIFIED IDEOGRAPH - 0xE1A2: 0x5C63, //CJK UNIFIED IDEOGRAPH - 0xE1A3: 0x5D82, //CJK UNIFIED IDEOGRAPH - 0xE1A4: 0x5D80, //CJK UNIFIED IDEOGRAPH - 0xE1A5: 0x5D7D, //CJK UNIFIED IDEOGRAPH - 0xE1A6: 0x5D86, //CJK UNIFIED IDEOGRAPH - 0xE1A7: 0x5D7A, //CJK UNIFIED IDEOGRAPH - 0xE1A8: 0x5D81, //CJK UNIFIED IDEOGRAPH - 0xE1A9: 0x5D77, //CJK UNIFIED IDEOGRAPH - 0xE1AA: 0x5D8A, //CJK UNIFIED IDEOGRAPH - 0xE1AB: 0x5D89, //CJK UNIFIED IDEOGRAPH - 0xE1AC: 0x5D88, //CJK UNIFIED IDEOGRAPH - 0xE1AD: 0x5D7E, //CJK UNIFIED IDEOGRAPH - 0xE1AE: 0x5D7C, //CJK UNIFIED IDEOGRAPH - 0xE1AF: 0x5D8D, //CJK UNIFIED IDEOGRAPH - 0xE1B0: 0x5D79, //CJK UNIFIED IDEOGRAPH - 0xE1B1: 0x5D7F, //CJK UNIFIED IDEOGRAPH - 0xE1B2: 0x5E58, //CJK UNIFIED IDEOGRAPH - 0xE1B3: 0x5E59, //CJK UNIFIED IDEOGRAPH - 0xE1B4: 0x5E53, //CJK UNIFIED IDEOGRAPH - 0xE1B5: 0x5ED8, //CJK UNIFIED IDEOGRAPH - 0xE1B6: 0x5ED1, //CJK UNIFIED IDEOGRAPH - 0xE1B7: 0x5ED7, //CJK UNIFIED IDEOGRAPH - 0xE1B8: 0x5ECE, //CJK UNIFIED IDEOGRAPH - 0xE1B9: 0x5EDC, //CJK UNIFIED IDEOGRAPH - 0xE1BA: 0x5ED5, //CJK UNIFIED IDEOGRAPH - 0xE1BB: 0x5ED9, //CJK UNIFIED IDEOGRAPH - 0xE1BC: 0x5ED2, //CJK UNIFIED IDEOGRAPH - 0xE1BD: 0x5ED4, //CJK UNIFIED IDEOGRAPH - 0xE1BE: 0x5F44, //CJK UNIFIED IDEOGRAPH - 0xE1BF: 0x5F43, //CJK UNIFIED IDEOGRAPH - 0xE1C0: 0x5F6F, //CJK UNIFIED IDEOGRAPH - 0xE1C1: 0x5FB6, //CJK UNIFIED IDEOGRAPH - 0xE1C2: 0x612C, //CJK UNIFIED IDEOGRAPH - 0xE1C3: 0x6128, //CJK UNIFIED IDEOGRAPH - 0xE1C4: 0x6141, //CJK UNIFIED IDEOGRAPH - 0xE1C5: 0x615E, //CJK UNIFIED IDEOGRAPH - 0xE1C6: 0x6171, //CJK UNIFIED IDEOGRAPH - 0xE1C7: 0x6173, //CJK UNIFIED IDEOGRAPH - 0xE1C8: 0x6152, //CJK UNIFIED IDEOGRAPH - 0xE1C9: 0x6153, //CJK UNIFIED IDEOGRAPH - 0xE1CA: 0x6172, //CJK UNIFIED IDEOGRAPH - 0xE1CB: 0x616C, //CJK UNIFIED IDEOGRAPH - 0xE1CC: 0x6180, //CJK UNIFIED IDEOGRAPH - 0xE1CD: 0x6174, //CJK UNIFIED IDEOGRAPH - 0xE1CE: 0x6154, //CJK UNIFIED IDEOGRAPH - 0xE1CF: 0x617A, //CJK UNIFIED IDEOGRAPH - 0xE1D0: 0x615B, //CJK UNIFIED IDEOGRAPH - 0xE1D1: 0x6165, //CJK UNIFIED IDEOGRAPH - 0xE1D2: 0x613B, //CJK UNIFIED IDEOGRAPH - 0xE1D3: 0x616A, //CJK UNIFIED IDEOGRAPH - 0xE1D4: 0x6161, //CJK UNIFIED IDEOGRAPH - 0xE1D5: 0x6156, //CJK UNIFIED IDEOGRAPH - 0xE1D6: 0x6229, //CJK UNIFIED IDEOGRAPH - 0xE1D7: 0x6227, //CJK UNIFIED IDEOGRAPH - 0xE1D8: 0x622B, //CJK UNIFIED IDEOGRAPH - 0xE1D9: 0x642B, //CJK UNIFIED IDEOGRAPH - 0xE1DA: 0x644D, //CJK UNIFIED IDEOGRAPH - 0xE1DB: 0x645B, //CJK UNIFIED IDEOGRAPH - 0xE1DC: 0x645D, //CJK UNIFIED IDEOGRAPH - 0xE1DD: 0x6474, //CJK UNIFIED IDEOGRAPH - 0xE1DE: 0x6476, //CJK UNIFIED IDEOGRAPH - 0xE1DF: 0x6472, //CJK UNIFIED IDEOGRAPH - 0xE1E0: 0x6473, //CJK UNIFIED IDEOGRAPH - 0xE1E1: 0x647D, //CJK UNIFIED IDEOGRAPH - 0xE1E2: 0x6475, //CJK UNIFIED IDEOGRAPH - 0xE1E3: 0x6466, //CJK UNIFIED IDEOGRAPH - 0xE1E4: 0x64A6, //CJK UNIFIED IDEOGRAPH - 0xE1E5: 0x644E, //CJK UNIFIED IDEOGRAPH - 0xE1E6: 0x6482, //CJK UNIFIED IDEOGRAPH - 0xE1E7: 0x645E, //CJK UNIFIED IDEOGRAPH - 0xE1E8: 0x645C, //CJK UNIFIED IDEOGRAPH - 0xE1E9: 0x644B, //CJK UNIFIED IDEOGRAPH - 0xE1EA: 0x6453, //CJK UNIFIED IDEOGRAPH - 0xE1EB: 0x6460, //CJK UNIFIED IDEOGRAPH - 0xE1EC: 0x6450, //CJK UNIFIED IDEOGRAPH - 0xE1ED: 0x647F, //CJK UNIFIED IDEOGRAPH - 0xE1EE: 0x643F, //CJK UNIFIED IDEOGRAPH - 0xE1EF: 0x646C, //CJK UNIFIED IDEOGRAPH - 0xE1F0: 0x646B, //CJK UNIFIED IDEOGRAPH - 0xE1F1: 0x6459, //CJK UNIFIED IDEOGRAPH - 0xE1F2: 0x6465, //CJK UNIFIED IDEOGRAPH - 0xE1F3: 0x6477, //CJK UNIFIED IDEOGRAPH - 0xE1F4: 0x6573, //CJK UNIFIED IDEOGRAPH - 0xE1F5: 0x65A0, //CJK UNIFIED IDEOGRAPH - 0xE1F6: 0x66A1, //CJK UNIFIED IDEOGRAPH - 0xE1F7: 0x66A0, //CJK UNIFIED IDEOGRAPH - 0xE1F8: 0x669F, //CJK UNIFIED IDEOGRAPH - 0xE1F9: 0x6705, //CJK UNIFIED IDEOGRAPH - 0xE1FA: 0x6704, //CJK UNIFIED IDEOGRAPH - 0xE1FB: 0x6722, //CJK UNIFIED IDEOGRAPH - 0xE1FC: 0x69B1, //CJK UNIFIED IDEOGRAPH - 0xE1FD: 0x69B6, //CJK UNIFIED IDEOGRAPH - 0xE1FE: 0x69C9, //CJK UNIFIED IDEOGRAPH - 0xE240: 0x69A0, //CJK UNIFIED IDEOGRAPH - 0xE241: 0x69CE, //CJK UNIFIED IDEOGRAPH - 0xE242: 0x6996, //CJK UNIFIED IDEOGRAPH - 0xE243: 0x69B0, //CJK UNIFIED IDEOGRAPH - 0xE244: 0x69AC, //CJK UNIFIED IDEOGRAPH - 0xE245: 0x69BC, //CJK UNIFIED IDEOGRAPH - 0xE246: 0x6991, //CJK UNIFIED IDEOGRAPH - 0xE247: 0x6999, //CJK UNIFIED IDEOGRAPH - 0xE248: 0x698E, //CJK UNIFIED IDEOGRAPH - 0xE249: 0x69A7, //CJK UNIFIED IDEOGRAPH - 0xE24A: 0x698D, //CJK UNIFIED IDEOGRAPH - 0xE24B: 0x69A9, //CJK UNIFIED IDEOGRAPH - 0xE24C: 0x69BE, //CJK UNIFIED IDEOGRAPH - 0xE24D: 0x69AF, //CJK UNIFIED IDEOGRAPH - 0xE24E: 0x69BF, //CJK UNIFIED IDEOGRAPH - 0xE24F: 0x69C4, //CJK UNIFIED IDEOGRAPH - 0xE250: 0x69BD, //CJK UNIFIED IDEOGRAPH - 0xE251: 0x69A4, //CJK UNIFIED IDEOGRAPH - 0xE252: 0x69D4, //CJK UNIFIED IDEOGRAPH - 0xE253: 0x69B9, //CJK UNIFIED IDEOGRAPH - 0xE254: 0x69CA, //CJK UNIFIED IDEOGRAPH - 0xE255: 0x699A, //CJK UNIFIED IDEOGRAPH - 0xE256: 0x69CF, //CJK UNIFIED IDEOGRAPH - 0xE257: 0x69B3, //CJK UNIFIED IDEOGRAPH - 0xE258: 0x6993, //CJK UNIFIED IDEOGRAPH - 0xE259: 0x69AA, //CJK UNIFIED IDEOGRAPH - 0xE25A: 0x69A1, //CJK UNIFIED IDEOGRAPH - 0xE25B: 0x699E, //CJK UNIFIED IDEOGRAPH - 0xE25C: 0x69D9, //CJK UNIFIED IDEOGRAPH - 0xE25D: 0x6997, //CJK UNIFIED IDEOGRAPH - 0xE25E: 0x6990, //CJK UNIFIED IDEOGRAPH - 0xE25F: 0x69C2, //CJK UNIFIED IDEOGRAPH - 0xE260: 0x69B5, //CJK UNIFIED IDEOGRAPH - 0xE261: 0x69A5, //CJK UNIFIED IDEOGRAPH - 0xE262: 0x69C6, //CJK UNIFIED IDEOGRAPH - 0xE263: 0x6B4A, //CJK UNIFIED IDEOGRAPH - 0xE264: 0x6B4D, //CJK UNIFIED IDEOGRAPH - 0xE265: 0x6B4B, //CJK UNIFIED IDEOGRAPH - 0xE266: 0x6B9E, //CJK UNIFIED IDEOGRAPH - 0xE267: 0x6B9F, //CJK UNIFIED IDEOGRAPH - 0xE268: 0x6BA0, //CJK UNIFIED IDEOGRAPH - 0xE269: 0x6BC3, //CJK UNIFIED IDEOGRAPH - 0xE26A: 0x6BC4, //CJK UNIFIED IDEOGRAPH - 0xE26B: 0x6BFE, //CJK UNIFIED IDEOGRAPH - 0xE26C: 0x6ECE, //CJK UNIFIED IDEOGRAPH - 0xE26D: 0x6EF5, //CJK UNIFIED IDEOGRAPH - 0xE26E: 0x6EF1, //CJK UNIFIED IDEOGRAPH - 0xE26F: 0x6F03, //CJK UNIFIED IDEOGRAPH - 0xE270: 0x6F25, //CJK UNIFIED IDEOGRAPH - 0xE271: 0x6EF8, //CJK UNIFIED IDEOGRAPH - 0xE272: 0x6F37, //CJK UNIFIED IDEOGRAPH - 0xE273: 0x6EFB, //CJK UNIFIED IDEOGRAPH - 0xE274: 0x6F2E, //CJK UNIFIED IDEOGRAPH - 0xE275: 0x6F09, //CJK UNIFIED IDEOGRAPH - 0xE276: 0x6F4E, //CJK UNIFIED IDEOGRAPH - 0xE277: 0x6F19, //CJK UNIFIED IDEOGRAPH - 0xE278: 0x6F1A, //CJK UNIFIED IDEOGRAPH - 0xE279: 0x6F27, //CJK UNIFIED IDEOGRAPH - 0xE27A: 0x6F18, //CJK UNIFIED IDEOGRAPH - 0xE27B: 0x6F3B, //CJK UNIFIED IDEOGRAPH - 0xE27C: 0x6F12, //CJK UNIFIED IDEOGRAPH - 0xE27D: 0x6EED, //CJK UNIFIED IDEOGRAPH - 0xE27E: 0x6F0A, //CJK UNIFIED IDEOGRAPH - 0xE2A1: 0x6F36, //CJK UNIFIED IDEOGRAPH - 0xE2A2: 0x6F73, //CJK UNIFIED IDEOGRAPH - 0xE2A3: 0x6EF9, //CJK UNIFIED IDEOGRAPH - 0xE2A4: 0x6EEE, //CJK UNIFIED IDEOGRAPH - 0xE2A5: 0x6F2D, //CJK UNIFIED IDEOGRAPH - 0xE2A6: 0x6F40, //CJK UNIFIED IDEOGRAPH - 0xE2A7: 0x6F30, //CJK UNIFIED IDEOGRAPH - 0xE2A8: 0x6F3C, //CJK UNIFIED IDEOGRAPH - 0xE2A9: 0x6F35, //CJK UNIFIED IDEOGRAPH - 0xE2AA: 0x6EEB, //CJK UNIFIED IDEOGRAPH - 0xE2AB: 0x6F07, //CJK UNIFIED IDEOGRAPH - 0xE2AC: 0x6F0E, //CJK UNIFIED IDEOGRAPH - 0xE2AD: 0x6F43, //CJK UNIFIED IDEOGRAPH - 0xE2AE: 0x6F05, //CJK UNIFIED IDEOGRAPH - 0xE2AF: 0x6EFD, //CJK UNIFIED IDEOGRAPH - 0xE2B0: 0x6EF6, //CJK UNIFIED IDEOGRAPH - 0xE2B1: 0x6F39, //CJK UNIFIED IDEOGRAPH - 0xE2B2: 0x6F1C, //CJK UNIFIED IDEOGRAPH - 0xE2B3: 0x6EFC, //CJK UNIFIED IDEOGRAPH - 0xE2B4: 0x6F3A, //CJK UNIFIED IDEOGRAPH - 0xE2B5: 0x6F1F, //CJK UNIFIED IDEOGRAPH - 0xE2B6: 0x6F0D, //CJK UNIFIED IDEOGRAPH - 0xE2B7: 0x6F1E, //CJK UNIFIED IDEOGRAPH - 0xE2B8: 0x6F08, //CJK UNIFIED IDEOGRAPH - 0xE2B9: 0x6F21, //CJK UNIFIED IDEOGRAPH - 0xE2BA: 0x7187, //CJK UNIFIED IDEOGRAPH - 0xE2BB: 0x7190, //CJK UNIFIED IDEOGRAPH - 0xE2BC: 0x7189, //CJK UNIFIED IDEOGRAPH - 0xE2BD: 0x7180, //CJK UNIFIED IDEOGRAPH - 0xE2BE: 0x7185, //CJK UNIFIED IDEOGRAPH - 0xE2BF: 0x7182, //CJK UNIFIED IDEOGRAPH - 0xE2C0: 0x718F, //CJK UNIFIED IDEOGRAPH - 0xE2C1: 0x717B, //CJK UNIFIED IDEOGRAPH - 0xE2C2: 0x7186, //CJK UNIFIED IDEOGRAPH - 0xE2C3: 0x7181, //CJK UNIFIED IDEOGRAPH - 0xE2C4: 0x7197, //CJK UNIFIED IDEOGRAPH - 0xE2C5: 0x7244, //CJK UNIFIED IDEOGRAPH - 0xE2C6: 0x7253, //CJK UNIFIED IDEOGRAPH - 0xE2C7: 0x7297, //CJK UNIFIED IDEOGRAPH - 0xE2C8: 0x7295, //CJK UNIFIED IDEOGRAPH - 0xE2C9: 0x7293, //CJK UNIFIED IDEOGRAPH - 0xE2CA: 0x7343, //CJK UNIFIED IDEOGRAPH - 0xE2CB: 0x734D, //CJK UNIFIED IDEOGRAPH - 0xE2CC: 0x7351, //CJK UNIFIED IDEOGRAPH - 0xE2CD: 0x734C, //CJK UNIFIED IDEOGRAPH - 0xE2CE: 0x7462, //CJK UNIFIED IDEOGRAPH - 0xE2CF: 0x7473, //CJK UNIFIED IDEOGRAPH - 0xE2D0: 0x7471, //CJK UNIFIED IDEOGRAPH - 0xE2D1: 0x7475, //CJK UNIFIED IDEOGRAPH - 0xE2D2: 0x7472, //CJK UNIFIED IDEOGRAPH - 0xE2D3: 0x7467, //CJK UNIFIED IDEOGRAPH - 0xE2D4: 0x746E, //CJK UNIFIED IDEOGRAPH - 0xE2D5: 0x7500, //CJK UNIFIED IDEOGRAPH - 0xE2D6: 0x7502, //CJK UNIFIED IDEOGRAPH - 0xE2D7: 0x7503, //CJK UNIFIED IDEOGRAPH - 0xE2D8: 0x757D, //CJK UNIFIED IDEOGRAPH - 0xE2D9: 0x7590, //CJK UNIFIED IDEOGRAPH - 0xE2DA: 0x7616, //CJK UNIFIED IDEOGRAPH - 0xE2DB: 0x7608, //CJK UNIFIED IDEOGRAPH - 0xE2DC: 0x760C, //CJK UNIFIED IDEOGRAPH - 0xE2DD: 0x7615, //CJK UNIFIED IDEOGRAPH - 0xE2DE: 0x7611, //CJK UNIFIED IDEOGRAPH - 0xE2DF: 0x760A, //CJK UNIFIED IDEOGRAPH - 0xE2E0: 0x7614, //CJK UNIFIED IDEOGRAPH - 0xE2E1: 0x76B8, //CJK UNIFIED IDEOGRAPH - 0xE2E2: 0x7781, //CJK UNIFIED IDEOGRAPH - 0xE2E3: 0x777C, //CJK UNIFIED IDEOGRAPH - 0xE2E4: 0x7785, //CJK UNIFIED IDEOGRAPH - 0xE2E5: 0x7782, //CJK UNIFIED IDEOGRAPH - 0xE2E6: 0x776E, //CJK UNIFIED IDEOGRAPH - 0xE2E7: 0x7780, //CJK UNIFIED IDEOGRAPH - 0xE2E8: 0x776F, //CJK UNIFIED IDEOGRAPH - 0xE2E9: 0x777E, //CJK UNIFIED IDEOGRAPH - 0xE2EA: 0x7783, //CJK UNIFIED IDEOGRAPH - 0xE2EB: 0x78B2, //CJK UNIFIED IDEOGRAPH - 0xE2EC: 0x78AA, //CJK UNIFIED IDEOGRAPH - 0xE2ED: 0x78B4, //CJK UNIFIED IDEOGRAPH - 0xE2EE: 0x78AD, //CJK UNIFIED IDEOGRAPH - 0xE2EF: 0x78A8, //CJK UNIFIED IDEOGRAPH - 0xE2F0: 0x787E, //CJK UNIFIED IDEOGRAPH - 0xE2F1: 0x78AB, //CJK UNIFIED IDEOGRAPH - 0xE2F2: 0x789E, //CJK UNIFIED IDEOGRAPH - 0xE2F3: 0x78A5, //CJK UNIFIED IDEOGRAPH - 0xE2F4: 0x78A0, //CJK UNIFIED IDEOGRAPH - 0xE2F5: 0x78AC, //CJK UNIFIED IDEOGRAPH - 0xE2F6: 0x78A2, //CJK UNIFIED IDEOGRAPH - 0xE2F7: 0x78A4, //CJK UNIFIED IDEOGRAPH - 0xE2F8: 0x7998, //CJK UNIFIED IDEOGRAPH - 0xE2F9: 0x798A, //CJK UNIFIED IDEOGRAPH - 0xE2FA: 0x798B, //CJK UNIFIED IDEOGRAPH - 0xE2FB: 0x7996, //CJK UNIFIED IDEOGRAPH - 0xE2FC: 0x7995, //CJK UNIFIED IDEOGRAPH - 0xE2FD: 0x7994, //CJK UNIFIED IDEOGRAPH - 0xE2FE: 0x7993, //CJK UNIFIED IDEOGRAPH - 0xE340: 0x7997, //CJK UNIFIED IDEOGRAPH - 0xE341: 0x7988, //CJK UNIFIED IDEOGRAPH - 0xE342: 0x7992, //CJK UNIFIED IDEOGRAPH - 0xE343: 0x7990, //CJK UNIFIED IDEOGRAPH - 0xE344: 0x7A2B, //CJK UNIFIED IDEOGRAPH - 0xE345: 0x7A4A, //CJK UNIFIED IDEOGRAPH - 0xE346: 0x7A30, //CJK UNIFIED IDEOGRAPH - 0xE347: 0x7A2F, //CJK UNIFIED IDEOGRAPH - 0xE348: 0x7A28, //CJK UNIFIED IDEOGRAPH - 0xE349: 0x7A26, //CJK UNIFIED IDEOGRAPH - 0xE34A: 0x7AA8, //CJK UNIFIED IDEOGRAPH - 0xE34B: 0x7AAB, //CJK UNIFIED IDEOGRAPH - 0xE34C: 0x7AAC, //CJK UNIFIED IDEOGRAPH - 0xE34D: 0x7AEE, //CJK UNIFIED IDEOGRAPH - 0xE34E: 0x7B88, //CJK UNIFIED IDEOGRAPH - 0xE34F: 0x7B9C, //CJK UNIFIED IDEOGRAPH - 0xE350: 0x7B8A, //CJK UNIFIED IDEOGRAPH - 0xE351: 0x7B91, //CJK UNIFIED IDEOGRAPH - 0xE352: 0x7B90, //CJK UNIFIED IDEOGRAPH - 0xE353: 0x7B96, //CJK UNIFIED IDEOGRAPH - 0xE354: 0x7B8D, //CJK UNIFIED IDEOGRAPH - 0xE355: 0x7B8C, //CJK UNIFIED IDEOGRAPH - 0xE356: 0x7B9B, //CJK UNIFIED IDEOGRAPH - 0xE357: 0x7B8E, //CJK UNIFIED IDEOGRAPH - 0xE358: 0x7B85, //CJK UNIFIED IDEOGRAPH - 0xE359: 0x7B98, //CJK UNIFIED IDEOGRAPH - 0xE35A: 0x5284, //CJK UNIFIED IDEOGRAPH - 0xE35B: 0x7B99, //CJK UNIFIED IDEOGRAPH - 0xE35C: 0x7BA4, //CJK UNIFIED IDEOGRAPH - 0xE35D: 0x7B82, //CJK UNIFIED IDEOGRAPH - 0xE35E: 0x7CBB, //CJK UNIFIED IDEOGRAPH - 0xE35F: 0x7CBF, //CJK UNIFIED IDEOGRAPH - 0xE360: 0x7CBC, //CJK UNIFIED IDEOGRAPH - 0xE361: 0x7CBA, //CJK UNIFIED IDEOGRAPH - 0xE362: 0x7DA7, //CJK UNIFIED IDEOGRAPH - 0xE363: 0x7DB7, //CJK UNIFIED IDEOGRAPH - 0xE364: 0x7DC2, //CJK UNIFIED IDEOGRAPH - 0xE365: 0x7DA3, //CJK UNIFIED IDEOGRAPH - 0xE366: 0x7DAA, //CJK UNIFIED IDEOGRAPH - 0xE367: 0x7DC1, //CJK UNIFIED IDEOGRAPH - 0xE368: 0x7DC0, //CJK UNIFIED IDEOGRAPH - 0xE369: 0x7DC5, //CJK UNIFIED IDEOGRAPH - 0xE36A: 0x7D9D, //CJK UNIFIED IDEOGRAPH - 0xE36B: 0x7DCE, //CJK UNIFIED IDEOGRAPH - 0xE36C: 0x7DC4, //CJK UNIFIED IDEOGRAPH - 0xE36D: 0x7DC6, //CJK UNIFIED IDEOGRAPH - 0xE36E: 0x7DCB, //CJK UNIFIED IDEOGRAPH - 0xE36F: 0x7DCC, //CJK UNIFIED IDEOGRAPH - 0xE370: 0x7DAF, //CJK UNIFIED IDEOGRAPH - 0xE371: 0x7DB9, //CJK UNIFIED IDEOGRAPH - 0xE372: 0x7D96, //CJK UNIFIED IDEOGRAPH - 0xE373: 0x7DBC, //CJK UNIFIED IDEOGRAPH - 0xE374: 0x7D9F, //CJK UNIFIED IDEOGRAPH - 0xE375: 0x7DA6, //CJK UNIFIED IDEOGRAPH - 0xE376: 0x7DAE, //CJK UNIFIED IDEOGRAPH - 0xE377: 0x7DA9, //CJK UNIFIED IDEOGRAPH - 0xE378: 0x7DA1, //CJK UNIFIED IDEOGRAPH - 0xE379: 0x7DC9, //CJK UNIFIED IDEOGRAPH - 0xE37A: 0x7F73, //CJK UNIFIED IDEOGRAPH - 0xE37B: 0x7FE2, //CJK UNIFIED IDEOGRAPH - 0xE37C: 0x7FE3, //CJK UNIFIED IDEOGRAPH - 0xE37D: 0x7FE5, //CJK UNIFIED IDEOGRAPH - 0xE37E: 0x7FDE, //CJK UNIFIED IDEOGRAPH - 0xE3A1: 0x8024, //CJK UNIFIED IDEOGRAPH - 0xE3A2: 0x805D, //CJK UNIFIED IDEOGRAPH - 0xE3A3: 0x805C, //CJK UNIFIED IDEOGRAPH - 0xE3A4: 0x8189, //CJK UNIFIED IDEOGRAPH - 0xE3A5: 0x8186, //CJK UNIFIED IDEOGRAPH - 0xE3A6: 0x8183, //CJK UNIFIED IDEOGRAPH - 0xE3A7: 0x8187, //CJK UNIFIED IDEOGRAPH - 0xE3A8: 0x818D, //CJK UNIFIED IDEOGRAPH - 0xE3A9: 0x818C, //CJK UNIFIED IDEOGRAPH - 0xE3AA: 0x818B, //CJK UNIFIED IDEOGRAPH - 0xE3AB: 0x8215, //CJK UNIFIED IDEOGRAPH - 0xE3AC: 0x8497, //CJK UNIFIED IDEOGRAPH - 0xE3AD: 0x84A4, //CJK UNIFIED IDEOGRAPH - 0xE3AE: 0x84A1, //CJK UNIFIED IDEOGRAPH - 0xE3AF: 0x849F, //CJK UNIFIED IDEOGRAPH - 0xE3B0: 0x84BA, //CJK UNIFIED IDEOGRAPH - 0xE3B1: 0x84CE, //CJK UNIFIED IDEOGRAPH - 0xE3B2: 0x84C2, //CJK UNIFIED IDEOGRAPH - 0xE3B3: 0x84AC, //CJK UNIFIED IDEOGRAPH - 0xE3B4: 0x84AE, //CJK UNIFIED IDEOGRAPH - 0xE3B5: 0x84AB, //CJK UNIFIED IDEOGRAPH - 0xE3B6: 0x84B9, //CJK UNIFIED IDEOGRAPH - 0xE3B7: 0x84B4, //CJK UNIFIED IDEOGRAPH - 0xE3B8: 0x84C1, //CJK UNIFIED IDEOGRAPH - 0xE3B9: 0x84CD, //CJK UNIFIED IDEOGRAPH - 0xE3BA: 0x84AA, //CJK UNIFIED IDEOGRAPH - 0xE3BB: 0x849A, //CJK UNIFIED IDEOGRAPH - 0xE3BC: 0x84B1, //CJK UNIFIED IDEOGRAPH - 0xE3BD: 0x84D0, //CJK UNIFIED IDEOGRAPH - 0xE3BE: 0x849D, //CJK UNIFIED IDEOGRAPH - 0xE3BF: 0x84A7, //CJK UNIFIED IDEOGRAPH - 0xE3C0: 0x84BB, //CJK UNIFIED IDEOGRAPH - 0xE3C1: 0x84A2, //CJK UNIFIED IDEOGRAPH - 0xE3C2: 0x8494, //CJK UNIFIED IDEOGRAPH - 0xE3C3: 0x84C7, //CJK UNIFIED IDEOGRAPH - 0xE3C4: 0x84CC, //CJK UNIFIED IDEOGRAPH - 0xE3C5: 0x849B, //CJK UNIFIED IDEOGRAPH - 0xE3C6: 0x84A9, //CJK UNIFIED IDEOGRAPH - 0xE3C7: 0x84AF, //CJK UNIFIED IDEOGRAPH - 0xE3C8: 0x84A8, //CJK UNIFIED IDEOGRAPH - 0xE3C9: 0x84D6, //CJK UNIFIED IDEOGRAPH - 0xE3CA: 0x8498, //CJK UNIFIED IDEOGRAPH - 0xE3CB: 0x84B6, //CJK UNIFIED IDEOGRAPH - 0xE3CC: 0x84CF, //CJK UNIFIED IDEOGRAPH - 0xE3CD: 0x84A0, //CJK UNIFIED IDEOGRAPH - 0xE3CE: 0x84D7, //CJK UNIFIED IDEOGRAPH - 0xE3CF: 0x84D4, //CJK UNIFIED IDEOGRAPH - 0xE3D0: 0x84D2, //CJK UNIFIED IDEOGRAPH - 0xE3D1: 0x84DB, //CJK UNIFIED IDEOGRAPH - 0xE3D2: 0x84B0, //CJK UNIFIED IDEOGRAPH - 0xE3D3: 0x8491, //CJK UNIFIED IDEOGRAPH - 0xE3D4: 0x8661, //CJK UNIFIED IDEOGRAPH - 0xE3D5: 0x8733, //CJK UNIFIED IDEOGRAPH - 0xE3D6: 0x8723, //CJK UNIFIED IDEOGRAPH - 0xE3D7: 0x8728, //CJK UNIFIED IDEOGRAPH - 0xE3D8: 0x876B, //CJK UNIFIED IDEOGRAPH - 0xE3D9: 0x8740, //CJK UNIFIED IDEOGRAPH - 0xE3DA: 0x872E, //CJK UNIFIED IDEOGRAPH - 0xE3DB: 0x871E, //CJK UNIFIED IDEOGRAPH - 0xE3DC: 0x8721, //CJK UNIFIED IDEOGRAPH - 0xE3DD: 0x8719, //CJK UNIFIED IDEOGRAPH - 0xE3DE: 0x871B, //CJK UNIFIED IDEOGRAPH - 0xE3DF: 0x8743, //CJK UNIFIED IDEOGRAPH - 0xE3E0: 0x872C, //CJK UNIFIED IDEOGRAPH - 0xE3E1: 0x8741, //CJK UNIFIED IDEOGRAPH - 0xE3E2: 0x873E, //CJK UNIFIED IDEOGRAPH - 0xE3E3: 0x8746, //CJK UNIFIED IDEOGRAPH - 0xE3E4: 0x8720, //CJK UNIFIED IDEOGRAPH - 0xE3E5: 0x8732, //CJK UNIFIED IDEOGRAPH - 0xE3E6: 0x872A, //CJK UNIFIED IDEOGRAPH - 0xE3E7: 0x872D, //CJK UNIFIED IDEOGRAPH - 0xE3E8: 0x873C, //CJK UNIFIED IDEOGRAPH - 0xE3E9: 0x8712, //CJK UNIFIED IDEOGRAPH - 0xE3EA: 0x873A, //CJK UNIFIED IDEOGRAPH - 0xE3EB: 0x8731, //CJK UNIFIED IDEOGRAPH - 0xE3EC: 0x8735, //CJK UNIFIED IDEOGRAPH - 0xE3ED: 0x8742, //CJK UNIFIED IDEOGRAPH - 0xE3EE: 0x8726, //CJK UNIFIED IDEOGRAPH - 0xE3EF: 0x8727, //CJK UNIFIED IDEOGRAPH - 0xE3F0: 0x8738, //CJK UNIFIED IDEOGRAPH - 0xE3F1: 0x8724, //CJK UNIFIED IDEOGRAPH - 0xE3F2: 0x871A, //CJK UNIFIED IDEOGRAPH - 0xE3F3: 0x8730, //CJK UNIFIED IDEOGRAPH - 0xE3F4: 0x8711, //CJK UNIFIED IDEOGRAPH - 0xE3F5: 0x88F7, //CJK UNIFIED IDEOGRAPH - 0xE3F6: 0x88E7, //CJK UNIFIED IDEOGRAPH - 0xE3F7: 0x88F1, //CJK UNIFIED IDEOGRAPH - 0xE3F8: 0x88F2, //CJK UNIFIED IDEOGRAPH - 0xE3F9: 0x88FA, //CJK UNIFIED IDEOGRAPH - 0xE3FA: 0x88FE, //CJK UNIFIED IDEOGRAPH - 0xE3FB: 0x88EE, //CJK UNIFIED IDEOGRAPH - 0xE3FC: 0x88FC, //CJK UNIFIED IDEOGRAPH - 0xE3FD: 0x88F6, //CJK UNIFIED IDEOGRAPH - 0xE3FE: 0x88FB, //CJK UNIFIED IDEOGRAPH - 0xE440: 0x88F0, //CJK UNIFIED IDEOGRAPH - 0xE441: 0x88EC, //CJK UNIFIED IDEOGRAPH - 0xE442: 0x88EB, //CJK UNIFIED IDEOGRAPH - 0xE443: 0x899D, //CJK UNIFIED IDEOGRAPH - 0xE444: 0x89A1, //CJK UNIFIED IDEOGRAPH - 0xE445: 0x899F, //CJK UNIFIED IDEOGRAPH - 0xE446: 0x899E, //CJK UNIFIED IDEOGRAPH - 0xE447: 0x89E9, //CJK UNIFIED IDEOGRAPH - 0xE448: 0x89EB, //CJK UNIFIED IDEOGRAPH - 0xE449: 0x89E8, //CJK UNIFIED IDEOGRAPH - 0xE44A: 0x8AAB, //CJK UNIFIED IDEOGRAPH - 0xE44B: 0x8A99, //CJK UNIFIED IDEOGRAPH - 0xE44C: 0x8A8B, //CJK UNIFIED IDEOGRAPH - 0xE44D: 0x8A92, //CJK UNIFIED IDEOGRAPH - 0xE44E: 0x8A8F, //CJK UNIFIED IDEOGRAPH - 0xE44F: 0x8A96, //CJK UNIFIED IDEOGRAPH - 0xE450: 0x8C3D, //CJK UNIFIED IDEOGRAPH - 0xE451: 0x8C68, //CJK UNIFIED IDEOGRAPH - 0xE452: 0x8C69, //CJK UNIFIED IDEOGRAPH - 0xE453: 0x8CD5, //CJK UNIFIED IDEOGRAPH - 0xE454: 0x8CCF, //CJK UNIFIED IDEOGRAPH - 0xE455: 0x8CD7, //CJK UNIFIED IDEOGRAPH - 0xE456: 0x8D96, //CJK UNIFIED IDEOGRAPH - 0xE457: 0x8E09, //CJK UNIFIED IDEOGRAPH - 0xE458: 0x8E02, //CJK UNIFIED IDEOGRAPH - 0xE459: 0x8DFF, //CJK UNIFIED IDEOGRAPH - 0xE45A: 0x8E0D, //CJK UNIFIED IDEOGRAPH - 0xE45B: 0x8DFD, //CJK UNIFIED IDEOGRAPH - 0xE45C: 0x8E0A, //CJK UNIFIED IDEOGRAPH - 0xE45D: 0x8E03, //CJK UNIFIED IDEOGRAPH - 0xE45E: 0x8E07, //CJK UNIFIED IDEOGRAPH - 0xE45F: 0x8E06, //CJK UNIFIED IDEOGRAPH - 0xE460: 0x8E05, //CJK UNIFIED IDEOGRAPH - 0xE461: 0x8DFE, //CJK UNIFIED IDEOGRAPH - 0xE462: 0x8E00, //CJK UNIFIED IDEOGRAPH - 0xE463: 0x8E04, //CJK UNIFIED IDEOGRAPH - 0xE464: 0x8F10, //CJK UNIFIED IDEOGRAPH - 0xE465: 0x8F11, //CJK UNIFIED IDEOGRAPH - 0xE466: 0x8F0E, //CJK UNIFIED IDEOGRAPH - 0xE467: 0x8F0D, //CJK UNIFIED IDEOGRAPH - 0xE468: 0x9123, //CJK UNIFIED IDEOGRAPH - 0xE469: 0x911C, //CJK UNIFIED IDEOGRAPH - 0xE46A: 0x9120, //CJK UNIFIED IDEOGRAPH - 0xE46B: 0x9122, //CJK UNIFIED IDEOGRAPH - 0xE46C: 0x911F, //CJK UNIFIED IDEOGRAPH - 0xE46D: 0x911D, //CJK UNIFIED IDEOGRAPH - 0xE46E: 0x911A, //CJK UNIFIED IDEOGRAPH - 0xE46F: 0x9124, //CJK UNIFIED IDEOGRAPH - 0xE470: 0x9121, //CJK UNIFIED IDEOGRAPH - 0xE471: 0x911B, //CJK UNIFIED IDEOGRAPH - 0xE472: 0x917A, //CJK UNIFIED IDEOGRAPH - 0xE473: 0x9172, //CJK UNIFIED IDEOGRAPH - 0xE474: 0x9179, //CJK UNIFIED IDEOGRAPH - 0xE475: 0x9173, //CJK UNIFIED IDEOGRAPH - 0xE476: 0x92A5, //CJK UNIFIED IDEOGRAPH - 0xE477: 0x92A4, //CJK UNIFIED IDEOGRAPH - 0xE478: 0x9276, //CJK UNIFIED IDEOGRAPH - 0xE479: 0x929B, //CJK UNIFIED IDEOGRAPH - 0xE47A: 0x927A, //CJK UNIFIED IDEOGRAPH - 0xE47B: 0x92A0, //CJK UNIFIED IDEOGRAPH - 0xE47C: 0x9294, //CJK UNIFIED IDEOGRAPH - 0xE47D: 0x92AA, //CJK UNIFIED IDEOGRAPH - 0xE47E: 0x928D, //CJK UNIFIED IDEOGRAPH - 0xE4A1: 0x92A6, //CJK UNIFIED IDEOGRAPH - 0xE4A2: 0x929A, //CJK UNIFIED IDEOGRAPH - 0xE4A3: 0x92AB, //CJK UNIFIED IDEOGRAPH - 0xE4A4: 0x9279, //CJK UNIFIED IDEOGRAPH - 0xE4A5: 0x9297, //CJK UNIFIED IDEOGRAPH - 0xE4A6: 0x927F, //CJK UNIFIED IDEOGRAPH - 0xE4A7: 0x92A3, //CJK UNIFIED IDEOGRAPH - 0xE4A8: 0x92EE, //CJK UNIFIED IDEOGRAPH - 0xE4A9: 0x928E, //CJK UNIFIED IDEOGRAPH - 0xE4AA: 0x9282, //CJK UNIFIED IDEOGRAPH - 0xE4AB: 0x9295, //CJK UNIFIED IDEOGRAPH - 0xE4AC: 0x92A2, //CJK UNIFIED IDEOGRAPH - 0xE4AD: 0x927D, //CJK UNIFIED IDEOGRAPH - 0xE4AE: 0x9288, //CJK UNIFIED IDEOGRAPH - 0xE4AF: 0x92A1, //CJK UNIFIED IDEOGRAPH - 0xE4B0: 0x928A, //CJK UNIFIED IDEOGRAPH - 0xE4B1: 0x9286, //CJK UNIFIED IDEOGRAPH - 0xE4B2: 0x928C, //CJK UNIFIED IDEOGRAPH - 0xE4B3: 0x9299, //CJK UNIFIED IDEOGRAPH - 0xE4B4: 0x92A7, //CJK UNIFIED IDEOGRAPH - 0xE4B5: 0x927E, //CJK UNIFIED IDEOGRAPH - 0xE4B6: 0x9287, //CJK UNIFIED IDEOGRAPH - 0xE4B7: 0x92A9, //CJK UNIFIED IDEOGRAPH - 0xE4B8: 0x929D, //CJK UNIFIED IDEOGRAPH - 0xE4B9: 0x928B, //CJK UNIFIED IDEOGRAPH - 0xE4BA: 0x922D, //CJK UNIFIED IDEOGRAPH - 0xE4BB: 0x969E, //CJK UNIFIED IDEOGRAPH - 0xE4BC: 0x96A1, //CJK UNIFIED IDEOGRAPH - 0xE4BD: 0x96FF, //CJK UNIFIED IDEOGRAPH - 0xE4BE: 0x9758, //CJK UNIFIED IDEOGRAPH - 0xE4BF: 0x977D, //CJK UNIFIED IDEOGRAPH - 0xE4C0: 0x977A, //CJK UNIFIED IDEOGRAPH - 0xE4C1: 0x977E, //CJK UNIFIED IDEOGRAPH - 0xE4C2: 0x9783, //CJK UNIFIED IDEOGRAPH - 0xE4C3: 0x9780, //CJK UNIFIED IDEOGRAPH - 0xE4C4: 0x9782, //CJK UNIFIED IDEOGRAPH - 0xE4C5: 0x977B, //CJK UNIFIED IDEOGRAPH - 0xE4C6: 0x9784, //CJK UNIFIED IDEOGRAPH - 0xE4C7: 0x9781, //CJK UNIFIED IDEOGRAPH - 0xE4C8: 0x977F, //CJK UNIFIED IDEOGRAPH - 0xE4C9: 0x97CE, //CJK UNIFIED IDEOGRAPH - 0xE4CA: 0x97CD, //CJK UNIFIED IDEOGRAPH - 0xE4CB: 0x9816, //CJK UNIFIED IDEOGRAPH - 0xE4CC: 0x98AD, //CJK UNIFIED IDEOGRAPH - 0xE4CD: 0x98AE, //CJK UNIFIED IDEOGRAPH - 0xE4CE: 0x9902, //CJK UNIFIED IDEOGRAPH - 0xE4CF: 0x9900, //CJK UNIFIED IDEOGRAPH - 0xE4D0: 0x9907, //CJK UNIFIED IDEOGRAPH - 0xE4D1: 0x999D, //CJK UNIFIED IDEOGRAPH - 0xE4D2: 0x999C, //CJK UNIFIED IDEOGRAPH - 0xE4D3: 0x99C3, //CJK UNIFIED IDEOGRAPH - 0xE4D4: 0x99B9, //CJK UNIFIED IDEOGRAPH - 0xE4D5: 0x99BB, //CJK UNIFIED IDEOGRAPH - 0xE4D6: 0x99BA, //CJK UNIFIED IDEOGRAPH - 0xE4D7: 0x99C2, //CJK UNIFIED IDEOGRAPH - 0xE4D8: 0x99BD, //CJK UNIFIED IDEOGRAPH - 0xE4D9: 0x99C7, //CJK UNIFIED IDEOGRAPH - 0xE4DA: 0x9AB1, //CJK UNIFIED IDEOGRAPH - 0xE4DB: 0x9AE3, //CJK UNIFIED IDEOGRAPH - 0xE4DC: 0x9AE7, //CJK UNIFIED IDEOGRAPH - 0xE4DD: 0x9B3E, //CJK UNIFIED IDEOGRAPH - 0xE4DE: 0x9B3F, //CJK UNIFIED IDEOGRAPH - 0xE4DF: 0x9B60, //CJK UNIFIED IDEOGRAPH - 0xE4E0: 0x9B61, //CJK UNIFIED IDEOGRAPH - 0xE4E1: 0x9B5F, //CJK UNIFIED IDEOGRAPH - 0xE4E2: 0x9CF1, //CJK UNIFIED IDEOGRAPH - 0xE4E3: 0x9CF2, //CJK UNIFIED IDEOGRAPH - 0xE4E4: 0x9CF5, //CJK UNIFIED IDEOGRAPH - 0xE4E5: 0x9EA7, //CJK UNIFIED IDEOGRAPH - 0xE4E6: 0x50FF, //CJK UNIFIED IDEOGRAPH - 0xE4E7: 0x5103, //CJK UNIFIED IDEOGRAPH - 0xE4E8: 0x5130, //CJK UNIFIED IDEOGRAPH - 0xE4E9: 0x50F8, //CJK UNIFIED IDEOGRAPH - 0xE4EA: 0x5106, //CJK UNIFIED IDEOGRAPH - 0xE4EB: 0x5107, //CJK UNIFIED IDEOGRAPH - 0xE4EC: 0x50F6, //CJK UNIFIED IDEOGRAPH - 0xE4ED: 0x50FE, //CJK UNIFIED IDEOGRAPH - 0xE4EE: 0x510B, //CJK UNIFIED IDEOGRAPH - 0xE4EF: 0x510C, //CJK UNIFIED IDEOGRAPH - 0xE4F0: 0x50FD, //CJK UNIFIED IDEOGRAPH - 0xE4F1: 0x510A, //CJK UNIFIED IDEOGRAPH - 0xE4F2: 0x528B, //CJK UNIFIED IDEOGRAPH - 0xE4F3: 0x528C, //CJK UNIFIED IDEOGRAPH - 0xE4F4: 0x52F1, //CJK UNIFIED IDEOGRAPH - 0xE4F5: 0x52EF, //CJK UNIFIED IDEOGRAPH - 0xE4F6: 0x5648, //CJK UNIFIED IDEOGRAPH - 0xE4F7: 0x5642, //CJK UNIFIED IDEOGRAPH - 0xE4F8: 0x564C, //CJK UNIFIED IDEOGRAPH - 0xE4F9: 0x5635, //CJK UNIFIED IDEOGRAPH - 0xE4FA: 0x5641, //CJK UNIFIED IDEOGRAPH - 0xE4FB: 0x564A, //CJK UNIFIED IDEOGRAPH - 0xE4FC: 0x5649, //CJK UNIFIED IDEOGRAPH - 0xE4FD: 0x5646, //CJK UNIFIED IDEOGRAPH - 0xE4FE: 0x5658, //CJK UNIFIED IDEOGRAPH - 0xE540: 0x565A, //CJK UNIFIED IDEOGRAPH - 0xE541: 0x5640, //CJK UNIFIED IDEOGRAPH - 0xE542: 0x5633, //CJK UNIFIED IDEOGRAPH - 0xE543: 0x563D, //CJK UNIFIED IDEOGRAPH - 0xE544: 0x562C, //CJK UNIFIED IDEOGRAPH - 0xE545: 0x563E, //CJK UNIFIED IDEOGRAPH - 0xE546: 0x5638, //CJK UNIFIED IDEOGRAPH - 0xE547: 0x562A, //CJK UNIFIED IDEOGRAPH - 0xE548: 0x563A, //CJK UNIFIED IDEOGRAPH - 0xE549: 0x571A, //CJK UNIFIED IDEOGRAPH - 0xE54A: 0x58AB, //CJK UNIFIED IDEOGRAPH - 0xE54B: 0x589D, //CJK UNIFIED IDEOGRAPH - 0xE54C: 0x58B1, //CJK UNIFIED IDEOGRAPH - 0xE54D: 0x58A0, //CJK UNIFIED IDEOGRAPH - 0xE54E: 0x58A3, //CJK UNIFIED IDEOGRAPH - 0xE54F: 0x58AF, //CJK UNIFIED IDEOGRAPH - 0xE550: 0x58AC, //CJK UNIFIED IDEOGRAPH - 0xE551: 0x58A5, //CJK UNIFIED IDEOGRAPH - 0xE552: 0x58A1, //CJK UNIFIED IDEOGRAPH - 0xE553: 0x58FF, //CJK UNIFIED IDEOGRAPH - 0xE554: 0x5AFF, //CJK UNIFIED IDEOGRAPH - 0xE555: 0x5AF4, //CJK UNIFIED IDEOGRAPH - 0xE556: 0x5AFD, //CJK UNIFIED IDEOGRAPH - 0xE557: 0x5AF7, //CJK UNIFIED IDEOGRAPH - 0xE558: 0x5AF6, //CJK UNIFIED IDEOGRAPH - 0xE559: 0x5B03, //CJK UNIFIED IDEOGRAPH - 0xE55A: 0x5AF8, //CJK UNIFIED IDEOGRAPH - 0xE55B: 0x5B02, //CJK UNIFIED IDEOGRAPH - 0xE55C: 0x5AF9, //CJK UNIFIED IDEOGRAPH - 0xE55D: 0x5B01, //CJK UNIFIED IDEOGRAPH - 0xE55E: 0x5B07, //CJK UNIFIED IDEOGRAPH - 0xE55F: 0x5B05, //CJK UNIFIED IDEOGRAPH - 0xE560: 0x5B0F, //CJK UNIFIED IDEOGRAPH - 0xE561: 0x5C67, //CJK UNIFIED IDEOGRAPH - 0xE562: 0x5D99, //CJK UNIFIED IDEOGRAPH - 0xE563: 0x5D97, //CJK UNIFIED IDEOGRAPH - 0xE564: 0x5D9F, //CJK UNIFIED IDEOGRAPH - 0xE565: 0x5D92, //CJK UNIFIED IDEOGRAPH - 0xE566: 0x5DA2, //CJK UNIFIED IDEOGRAPH - 0xE567: 0x5D93, //CJK UNIFIED IDEOGRAPH - 0xE568: 0x5D95, //CJK UNIFIED IDEOGRAPH - 0xE569: 0x5DA0, //CJK UNIFIED IDEOGRAPH - 0xE56A: 0x5D9C, //CJK UNIFIED IDEOGRAPH - 0xE56B: 0x5DA1, //CJK UNIFIED IDEOGRAPH - 0xE56C: 0x5D9A, //CJK UNIFIED IDEOGRAPH - 0xE56D: 0x5D9E, //CJK UNIFIED IDEOGRAPH - 0xE56E: 0x5E69, //CJK UNIFIED IDEOGRAPH - 0xE56F: 0x5E5D, //CJK UNIFIED IDEOGRAPH - 0xE570: 0x5E60, //CJK UNIFIED IDEOGRAPH - 0xE571: 0x5E5C, //CJK UNIFIED IDEOGRAPH - 0xE572: 0x7DF3, //CJK UNIFIED IDEOGRAPH - 0xE573: 0x5EDB, //CJK UNIFIED IDEOGRAPH - 0xE574: 0x5EDE, //CJK UNIFIED IDEOGRAPH - 0xE575: 0x5EE1, //CJK UNIFIED IDEOGRAPH - 0xE576: 0x5F49, //CJK UNIFIED IDEOGRAPH - 0xE577: 0x5FB2, //CJK UNIFIED IDEOGRAPH - 0xE578: 0x618B, //CJK UNIFIED IDEOGRAPH - 0xE579: 0x6183, //CJK UNIFIED IDEOGRAPH - 0xE57A: 0x6179, //CJK UNIFIED IDEOGRAPH - 0xE57B: 0x61B1, //CJK UNIFIED IDEOGRAPH - 0xE57C: 0x61B0, //CJK UNIFIED IDEOGRAPH - 0xE57D: 0x61A2, //CJK UNIFIED IDEOGRAPH - 0xE57E: 0x6189, //CJK UNIFIED IDEOGRAPH - 0xE5A1: 0x619B, //CJK UNIFIED IDEOGRAPH - 0xE5A2: 0x6193, //CJK UNIFIED IDEOGRAPH - 0xE5A3: 0x61AF, //CJK UNIFIED IDEOGRAPH - 0xE5A4: 0x61AD, //CJK UNIFIED IDEOGRAPH - 0xE5A5: 0x619F, //CJK UNIFIED IDEOGRAPH - 0xE5A6: 0x6192, //CJK UNIFIED IDEOGRAPH - 0xE5A7: 0x61AA, //CJK UNIFIED IDEOGRAPH - 0xE5A8: 0x61A1, //CJK UNIFIED IDEOGRAPH - 0xE5A9: 0x618D, //CJK UNIFIED IDEOGRAPH - 0xE5AA: 0x6166, //CJK UNIFIED IDEOGRAPH - 0xE5AB: 0x61B3, //CJK UNIFIED IDEOGRAPH - 0xE5AC: 0x622D, //CJK UNIFIED IDEOGRAPH - 0xE5AD: 0x646E, //CJK UNIFIED IDEOGRAPH - 0xE5AE: 0x6470, //CJK UNIFIED IDEOGRAPH - 0xE5AF: 0x6496, //CJK UNIFIED IDEOGRAPH - 0xE5B0: 0x64A0, //CJK UNIFIED IDEOGRAPH - 0xE5B1: 0x6485, //CJK UNIFIED IDEOGRAPH - 0xE5B2: 0x6497, //CJK UNIFIED IDEOGRAPH - 0xE5B3: 0x649C, //CJK UNIFIED IDEOGRAPH - 0xE5B4: 0x648F, //CJK UNIFIED IDEOGRAPH - 0xE5B5: 0x648B, //CJK UNIFIED IDEOGRAPH - 0xE5B6: 0x648A, //CJK UNIFIED IDEOGRAPH - 0xE5B7: 0x648C, //CJK UNIFIED IDEOGRAPH - 0xE5B8: 0x64A3, //CJK UNIFIED IDEOGRAPH - 0xE5B9: 0x649F, //CJK UNIFIED IDEOGRAPH - 0xE5BA: 0x6468, //CJK UNIFIED IDEOGRAPH - 0xE5BB: 0x64B1, //CJK UNIFIED IDEOGRAPH - 0xE5BC: 0x6498, //CJK UNIFIED IDEOGRAPH - 0xE5BD: 0x6576, //CJK UNIFIED IDEOGRAPH - 0xE5BE: 0x657A, //CJK UNIFIED IDEOGRAPH - 0xE5BF: 0x6579, //CJK UNIFIED IDEOGRAPH - 0xE5C0: 0x657B, //CJK UNIFIED IDEOGRAPH - 0xE5C1: 0x65B2, //CJK UNIFIED IDEOGRAPH - 0xE5C2: 0x65B3, //CJK UNIFIED IDEOGRAPH - 0xE5C3: 0x66B5, //CJK UNIFIED IDEOGRAPH - 0xE5C4: 0x66B0, //CJK UNIFIED IDEOGRAPH - 0xE5C5: 0x66A9, //CJK UNIFIED IDEOGRAPH - 0xE5C6: 0x66B2, //CJK UNIFIED IDEOGRAPH - 0xE5C7: 0x66B7, //CJK UNIFIED IDEOGRAPH - 0xE5C8: 0x66AA, //CJK UNIFIED IDEOGRAPH - 0xE5C9: 0x66AF, //CJK UNIFIED IDEOGRAPH - 0xE5CA: 0x6A00, //CJK UNIFIED IDEOGRAPH - 0xE5CB: 0x6A06, //CJK UNIFIED IDEOGRAPH - 0xE5CC: 0x6A17, //CJK UNIFIED IDEOGRAPH - 0xE5CD: 0x69E5, //CJK UNIFIED IDEOGRAPH - 0xE5CE: 0x69F8, //CJK UNIFIED IDEOGRAPH - 0xE5CF: 0x6A15, //CJK UNIFIED IDEOGRAPH - 0xE5D0: 0x69F1, //CJK UNIFIED IDEOGRAPH - 0xE5D1: 0x69E4, //CJK UNIFIED IDEOGRAPH - 0xE5D2: 0x6A20, //CJK UNIFIED IDEOGRAPH - 0xE5D3: 0x69FF, //CJK UNIFIED IDEOGRAPH - 0xE5D4: 0x69EC, //CJK UNIFIED IDEOGRAPH - 0xE5D5: 0x69E2, //CJK UNIFIED IDEOGRAPH - 0xE5D6: 0x6A1B, //CJK UNIFIED IDEOGRAPH - 0xE5D7: 0x6A1D, //CJK UNIFIED IDEOGRAPH - 0xE5D8: 0x69FE, //CJK UNIFIED IDEOGRAPH - 0xE5D9: 0x6A27, //CJK UNIFIED IDEOGRAPH - 0xE5DA: 0x69F2, //CJK UNIFIED IDEOGRAPH - 0xE5DB: 0x69EE, //CJK UNIFIED IDEOGRAPH - 0xE5DC: 0x6A14, //CJK UNIFIED IDEOGRAPH - 0xE5DD: 0x69F7, //CJK UNIFIED IDEOGRAPH - 0xE5DE: 0x69E7, //CJK UNIFIED IDEOGRAPH - 0xE5DF: 0x6A40, //CJK UNIFIED IDEOGRAPH - 0xE5E0: 0x6A08, //CJK UNIFIED IDEOGRAPH - 0xE5E1: 0x69E6, //CJK UNIFIED IDEOGRAPH - 0xE5E2: 0x69FB, //CJK UNIFIED IDEOGRAPH - 0xE5E3: 0x6A0D, //CJK UNIFIED IDEOGRAPH - 0xE5E4: 0x69FC, //CJK UNIFIED IDEOGRAPH - 0xE5E5: 0x69EB, //CJK UNIFIED IDEOGRAPH - 0xE5E6: 0x6A09, //CJK UNIFIED IDEOGRAPH - 0xE5E7: 0x6A04, //CJK UNIFIED IDEOGRAPH - 0xE5E8: 0x6A18, //CJK UNIFIED IDEOGRAPH - 0xE5E9: 0x6A25, //CJK UNIFIED IDEOGRAPH - 0xE5EA: 0x6A0F, //CJK UNIFIED IDEOGRAPH - 0xE5EB: 0x69F6, //CJK UNIFIED IDEOGRAPH - 0xE5EC: 0x6A26, //CJK UNIFIED IDEOGRAPH - 0xE5ED: 0x6A07, //CJK UNIFIED IDEOGRAPH - 0xE5EE: 0x69F4, //CJK UNIFIED IDEOGRAPH - 0xE5EF: 0x6A16, //CJK UNIFIED IDEOGRAPH - 0xE5F0: 0x6B51, //CJK UNIFIED IDEOGRAPH - 0xE5F1: 0x6BA5, //CJK UNIFIED IDEOGRAPH - 0xE5F2: 0x6BA3, //CJK UNIFIED IDEOGRAPH - 0xE5F3: 0x6BA2, //CJK UNIFIED IDEOGRAPH - 0xE5F4: 0x6BA6, //CJK UNIFIED IDEOGRAPH - 0xE5F5: 0x6C01, //CJK UNIFIED IDEOGRAPH - 0xE5F6: 0x6C00, //CJK UNIFIED IDEOGRAPH - 0xE5F7: 0x6BFF, //CJK UNIFIED IDEOGRAPH - 0xE5F8: 0x6C02, //CJK UNIFIED IDEOGRAPH - 0xE5F9: 0x6F41, //CJK UNIFIED IDEOGRAPH - 0xE5FA: 0x6F26, //CJK UNIFIED IDEOGRAPH - 0xE5FB: 0x6F7E, //CJK UNIFIED IDEOGRAPH - 0xE5FC: 0x6F87, //CJK UNIFIED IDEOGRAPH - 0xE5FD: 0x6FC6, //CJK UNIFIED IDEOGRAPH - 0xE5FE: 0x6F92, //CJK UNIFIED IDEOGRAPH - 0xE640: 0x6F8D, //CJK UNIFIED IDEOGRAPH - 0xE641: 0x6F89, //CJK UNIFIED IDEOGRAPH - 0xE642: 0x6F8C, //CJK UNIFIED IDEOGRAPH - 0xE643: 0x6F62, //CJK UNIFIED IDEOGRAPH - 0xE644: 0x6F4F, //CJK UNIFIED IDEOGRAPH - 0xE645: 0x6F85, //CJK UNIFIED IDEOGRAPH - 0xE646: 0x6F5A, //CJK UNIFIED IDEOGRAPH - 0xE647: 0x6F96, //CJK UNIFIED IDEOGRAPH - 0xE648: 0x6F76, //CJK UNIFIED IDEOGRAPH - 0xE649: 0x6F6C, //CJK UNIFIED IDEOGRAPH - 0xE64A: 0x6F82, //CJK UNIFIED IDEOGRAPH - 0xE64B: 0x6F55, //CJK UNIFIED IDEOGRAPH - 0xE64C: 0x6F72, //CJK UNIFIED IDEOGRAPH - 0xE64D: 0x6F52, //CJK UNIFIED IDEOGRAPH - 0xE64E: 0x6F50, //CJK UNIFIED IDEOGRAPH - 0xE64F: 0x6F57, //CJK UNIFIED IDEOGRAPH - 0xE650: 0x6F94, //CJK UNIFIED IDEOGRAPH - 0xE651: 0x6F93, //CJK UNIFIED IDEOGRAPH - 0xE652: 0x6F5D, //CJK UNIFIED IDEOGRAPH - 0xE653: 0x6F00, //CJK UNIFIED IDEOGRAPH - 0xE654: 0x6F61, //CJK UNIFIED IDEOGRAPH - 0xE655: 0x6F6B, //CJK UNIFIED IDEOGRAPH - 0xE656: 0x6F7D, //CJK UNIFIED IDEOGRAPH - 0xE657: 0x6F67, //CJK UNIFIED IDEOGRAPH - 0xE658: 0x6F90, //CJK UNIFIED IDEOGRAPH - 0xE659: 0x6F53, //CJK UNIFIED IDEOGRAPH - 0xE65A: 0x6F8B, //CJK UNIFIED IDEOGRAPH - 0xE65B: 0x6F69, //CJK UNIFIED IDEOGRAPH - 0xE65C: 0x6F7F, //CJK UNIFIED IDEOGRAPH - 0xE65D: 0x6F95, //CJK UNIFIED IDEOGRAPH - 0xE65E: 0x6F63, //CJK UNIFIED IDEOGRAPH - 0xE65F: 0x6F77, //CJK UNIFIED IDEOGRAPH - 0xE660: 0x6F6A, //CJK UNIFIED IDEOGRAPH - 0xE661: 0x6F7B, //CJK UNIFIED IDEOGRAPH - 0xE662: 0x71B2, //CJK UNIFIED IDEOGRAPH - 0xE663: 0x71AF, //CJK UNIFIED IDEOGRAPH - 0xE664: 0x719B, //CJK UNIFIED IDEOGRAPH - 0xE665: 0x71B0, //CJK UNIFIED IDEOGRAPH - 0xE666: 0x71A0, //CJK UNIFIED IDEOGRAPH - 0xE667: 0x719A, //CJK UNIFIED IDEOGRAPH - 0xE668: 0x71A9, //CJK UNIFIED IDEOGRAPH - 0xE669: 0x71B5, //CJK UNIFIED IDEOGRAPH - 0xE66A: 0x719D, //CJK UNIFIED IDEOGRAPH - 0xE66B: 0x71A5, //CJK UNIFIED IDEOGRAPH - 0xE66C: 0x719E, //CJK UNIFIED IDEOGRAPH - 0xE66D: 0x71A4, //CJK UNIFIED IDEOGRAPH - 0xE66E: 0x71A1, //CJK UNIFIED IDEOGRAPH - 0xE66F: 0x71AA, //CJK UNIFIED IDEOGRAPH - 0xE670: 0x719C, //CJK UNIFIED IDEOGRAPH - 0xE671: 0x71A7, //CJK UNIFIED IDEOGRAPH - 0xE672: 0x71B3, //CJK UNIFIED IDEOGRAPH - 0xE673: 0x7298, //CJK UNIFIED IDEOGRAPH - 0xE674: 0x729A, //CJK UNIFIED IDEOGRAPH - 0xE675: 0x7358, //CJK UNIFIED IDEOGRAPH - 0xE676: 0x7352, //CJK UNIFIED IDEOGRAPH - 0xE677: 0x735E, //CJK UNIFIED IDEOGRAPH - 0xE678: 0x735F, //CJK UNIFIED IDEOGRAPH - 0xE679: 0x7360, //CJK UNIFIED IDEOGRAPH - 0xE67A: 0x735D, //CJK UNIFIED IDEOGRAPH - 0xE67B: 0x735B, //CJK UNIFIED IDEOGRAPH - 0xE67C: 0x7361, //CJK UNIFIED IDEOGRAPH - 0xE67D: 0x735A, //CJK UNIFIED IDEOGRAPH - 0xE67E: 0x7359, //CJK UNIFIED IDEOGRAPH - 0xE6A1: 0x7362, //CJK UNIFIED IDEOGRAPH - 0xE6A2: 0x7487, //CJK UNIFIED IDEOGRAPH - 0xE6A3: 0x7489, //CJK UNIFIED IDEOGRAPH - 0xE6A4: 0x748A, //CJK UNIFIED IDEOGRAPH - 0xE6A5: 0x7486, //CJK UNIFIED IDEOGRAPH - 0xE6A6: 0x7481, //CJK UNIFIED IDEOGRAPH - 0xE6A7: 0x747D, //CJK UNIFIED IDEOGRAPH - 0xE6A8: 0x7485, //CJK UNIFIED IDEOGRAPH - 0xE6A9: 0x7488, //CJK UNIFIED IDEOGRAPH - 0xE6AA: 0x747C, //CJK UNIFIED IDEOGRAPH - 0xE6AB: 0x7479, //CJK UNIFIED IDEOGRAPH - 0xE6AC: 0x7508, //CJK UNIFIED IDEOGRAPH - 0xE6AD: 0x7507, //CJK UNIFIED IDEOGRAPH - 0xE6AE: 0x757E, //CJK UNIFIED IDEOGRAPH - 0xE6AF: 0x7625, //CJK UNIFIED IDEOGRAPH - 0xE6B0: 0x761E, //CJK UNIFIED IDEOGRAPH - 0xE6B1: 0x7619, //CJK UNIFIED IDEOGRAPH - 0xE6B2: 0x761D, //CJK UNIFIED IDEOGRAPH - 0xE6B3: 0x761C, //CJK UNIFIED IDEOGRAPH - 0xE6B4: 0x7623, //CJK UNIFIED IDEOGRAPH - 0xE6B5: 0x761A, //CJK UNIFIED IDEOGRAPH - 0xE6B6: 0x7628, //CJK UNIFIED IDEOGRAPH - 0xE6B7: 0x761B, //CJK UNIFIED IDEOGRAPH - 0xE6B8: 0x769C, //CJK UNIFIED IDEOGRAPH - 0xE6B9: 0x769D, //CJK UNIFIED IDEOGRAPH - 0xE6BA: 0x769E, //CJK UNIFIED IDEOGRAPH - 0xE6BB: 0x769B, //CJK UNIFIED IDEOGRAPH - 0xE6BC: 0x778D, //CJK UNIFIED IDEOGRAPH - 0xE6BD: 0x778F, //CJK UNIFIED IDEOGRAPH - 0xE6BE: 0x7789, //CJK UNIFIED IDEOGRAPH - 0xE6BF: 0x7788, //CJK UNIFIED IDEOGRAPH - 0xE6C0: 0x78CD, //CJK UNIFIED IDEOGRAPH - 0xE6C1: 0x78BB, //CJK UNIFIED IDEOGRAPH - 0xE6C2: 0x78CF, //CJK UNIFIED IDEOGRAPH - 0xE6C3: 0x78CC, //CJK UNIFIED IDEOGRAPH - 0xE6C4: 0x78D1, //CJK UNIFIED IDEOGRAPH - 0xE6C5: 0x78CE, //CJK UNIFIED IDEOGRAPH - 0xE6C6: 0x78D4, //CJK UNIFIED IDEOGRAPH - 0xE6C7: 0x78C8, //CJK UNIFIED IDEOGRAPH - 0xE6C8: 0x78C3, //CJK UNIFIED IDEOGRAPH - 0xE6C9: 0x78C4, //CJK UNIFIED IDEOGRAPH - 0xE6CA: 0x78C9, //CJK UNIFIED IDEOGRAPH - 0xE6CB: 0x799A, //CJK UNIFIED IDEOGRAPH - 0xE6CC: 0x79A1, //CJK UNIFIED IDEOGRAPH - 0xE6CD: 0x79A0, //CJK UNIFIED IDEOGRAPH - 0xE6CE: 0x799C, //CJK UNIFIED IDEOGRAPH - 0xE6CF: 0x79A2, //CJK UNIFIED IDEOGRAPH - 0xE6D0: 0x799B, //CJK UNIFIED IDEOGRAPH - 0xE6D1: 0x6B76, //CJK UNIFIED IDEOGRAPH - 0xE6D2: 0x7A39, //CJK UNIFIED IDEOGRAPH - 0xE6D3: 0x7AB2, //CJK UNIFIED IDEOGRAPH - 0xE6D4: 0x7AB4, //CJK UNIFIED IDEOGRAPH - 0xE6D5: 0x7AB3, //CJK UNIFIED IDEOGRAPH - 0xE6D6: 0x7BB7, //CJK UNIFIED IDEOGRAPH - 0xE6D7: 0x7BCB, //CJK UNIFIED IDEOGRAPH - 0xE6D8: 0x7BBE, //CJK UNIFIED IDEOGRAPH - 0xE6D9: 0x7BAC, //CJK UNIFIED IDEOGRAPH - 0xE6DA: 0x7BCE, //CJK UNIFIED IDEOGRAPH - 0xE6DB: 0x7BAF, //CJK UNIFIED IDEOGRAPH - 0xE6DC: 0x7BB9, //CJK UNIFIED IDEOGRAPH - 0xE6DD: 0x7BCA, //CJK UNIFIED IDEOGRAPH - 0xE6DE: 0x7BB5, //CJK UNIFIED IDEOGRAPH - 0xE6DF: 0x7CC5, //CJK UNIFIED IDEOGRAPH - 0xE6E0: 0x7CC8, //CJK UNIFIED IDEOGRAPH - 0xE6E1: 0x7CCC, //CJK UNIFIED IDEOGRAPH - 0xE6E2: 0x7CCB, //CJK UNIFIED IDEOGRAPH - 0xE6E3: 0x7DF7, //CJK UNIFIED IDEOGRAPH - 0xE6E4: 0x7DDB, //CJK UNIFIED IDEOGRAPH - 0xE6E5: 0x7DEA, //CJK UNIFIED IDEOGRAPH - 0xE6E6: 0x7DE7, //CJK UNIFIED IDEOGRAPH - 0xE6E7: 0x7DD7, //CJK UNIFIED IDEOGRAPH - 0xE6E8: 0x7DE1, //CJK UNIFIED IDEOGRAPH - 0xE6E9: 0x7E03, //CJK UNIFIED IDEOGRAPH - 0xE6EA: 0x7DFA, //CJK UNIFIED IDEOGRAPH - 0xE6EB: 0x7DE6, //CJK UNIFIED IDEOGRAPH - 0xE6EC: 0x7DF6, //CJK UNIFIED IDEOGRAPH - 0xE6ED: 0x7DF1, //CJK UNIFIED IDEOGRAPH - 0xE6EE: 0x7DF0, //CJK UNIFIED IDEOGRAPH - 0xE6EF: 0x7DEE, //CJK UNIFIED IDEOGRAPH - 0xE6F0: 0x7DDF, //CJK UNIFIED IDEOGRAPH - 0xE6F1: 0x7F76, //CJK UNIFIED IDEOGRAPH - 0xE6F2: 0x7FAC, //CJK UNIFIED IDEOGRAPH - 0xE6F3: 0x7FB0, //CJK UNIFIED IDEOGRAPH - 0xE6F4: 0x7FAD, //CJK UNIFIED IDEOGRAPH - 0xE6F5: 0x7FED, //CJK UNIFIED IDEOGRAPH - 0xE6F6: 0x7FEB, //CJK UNIFIED IDEOGRAPH - 0xE6F7: 0x7FEA, //CJK UNIFIED IDEOGRAPH - 0xE6F8: 0x7FEC, //CJK UNIFIED IDEOGRAPH - 0xE6F9: 0x7FE6, //CJK UNIFIED IDEOGRAPH - 0xE6FA: 0x7FE8, //CJK UNIFIED IDEOGRAPH - 0xE6FB: 0x8064, //CJK UNIFIED IDEOGRAPH - 0xE6FC: 0x8067, //CJK UNIFIED IDEOGRAPH - 0xE6FD: 0x81A3, //CJK UNIFIED IDEOGRAPH - 0xE6FE: 0x819F, //CJK UNIFIED IDEOGRAPH - 0xE740: 0x819E, //CJK UNIFIED IDEOGRAPH - 0xE741: 0x8195, //CJK UNIFIED IDEOGRAPH - 0xE742: 0x81A2, //CJK UNIFIED IDEOGRAPH - 0xE743: 0x8199, //CJK UNIFIED IDEOGRAPH - 0xE744: 0x8197, //CJK UNIFIED IDEOGRAPH - 0xE745: 0x8216, //CJK UNIFIED IDEOGRAPH - 0xE746: 0x824F, //CJK UNIFIED IDEOGRAPH - 0xE747: 0x8253, //CJK UNIFIED IDEOGRAPH - 0xE748: 0x8252, //CJK UNIFIED IDEOGRAPH - 0xE749: 0x8250, //CJK UNIFIED IDEOGRAPH - 0xE74A: 0x824E, //CJK UNIFIED IDEOGRAPH - 0xE74B: 0x8251, //CJK UNIFIED IDEOGRAPH - 0xE74C: 0x8524, //CJK UNIFIED IDEOGRAPH - 0xE74D: 0x853B, //CJK UNIFIED IDEOGRAPH - 0xE74E: 0x850F, //CJK UNIFIED IDEOGRAPH - 0xE74F: 0x8500, //CJK UNIFIED IDEOGRAPH - 0xE750: 0x8529, //CJK UNIFIED IDEOGRAPH - 0xE751: 0x850E, //CJK UNIFIED IDEOGRAPH - 0xE752: 0x8509, //CJK UNIFIED IDEOGRAPH - 0xE753: 0x850D, //CJK UNIFIED IDEOGRAPH - 0xE754: 0x851F, //CJK UNIFIED IDEOGRAPH - 0xE755: 0x850A, //CJK UNIFIED IDEOGRAPH - 0xE756: 0x8527, //CJK UNIFIED IDEOGRAPH - 0xE757: 0x851C, //CJK UNIFIED IDEOGRAPH - 0xE758: 0x84FB, //CJK UNIFIED IDEOGRAPH - 0xE759: 0x852B, //CJK UNIFIED IDEOGRAPH - 0xE75A: 0x84FA, //CJK UNIFIED IDEOGRAPH - 0xE75B: 0x8508, //CJK UNIFIED IDEOGRAPH - 0xE75C: 0x850C, //CJK UNIFIED IDEOGRAPH - 0xE75D: 0x84F4, //CJK UNIFIED IDEOGRAPH - 0xE75E: 0x852A, //CJK UNIFIED IDEOGRAPH - 0xE75F: 0x84F2, //CJK UNIFIED IDEOGRAPH - 0xE760: 0x8515, //CJK UNIFIED IDEOGRAPH - 0xE761: 0x84F7, //CJK UNIFIED IDEOGRAPH - 0xE762: 0x84EB, //CJK UNIFIED IDEOGRAPH - 0xE763: 0x84F3, //CJK UNIFIED IDEOGRAPH - 0xE764: 0x84FC, //CJK UNIFIED IDEOGRAPH - 0xE765: 0x8512, //CJK UNIFIED IDEOGRAPH - 0xE766: 0x84EA, //CJK UNIFIED IDEOGRAPH - 0xE767: 0x84E9, //CJK UNIFIED IDEOGRAPH - 0xE768: 0x8516, //CJK UNIFIED IDEOGRAPH - 0xE769: 0x84FE, //CJK UNIFIED IDEOGRAPH - 0xE76A: 0x8528, //CJK UNIFIED IDEOGRAPH - 0xE76B: 0x851D, //CJK UNIFIED IDEOGRAPH - 0xE76C: 0x852E, //CJK UNIFIED IDEOGRAPH - 0xE76D: 0x8502, //CJK UNIFIED IDEOGRAPH - 0xE76E: 0x84FD, //CJK UNIFIED IDEOGRAPH - 0xE76F: 0x851E, //CJK UNIFIED IDEOGRAPH - 0xE770: 0x84F6, //CJK UNIFIED IDEOGRAPH - 0xE771: 0x8531, //CJK UNIFIED IDEOGRAPH - 0xE772: 0x8526, //CJK UNIFIED IDEOGRAPH - 0xE773: 0x84E7, //CJK UNIFIED IDEOGRAPH - 0xE774: 0x84E8, //CJK UNIFIED IDEOGRAPH - 0xE775: 0x84F0, //CJK UNIFIED IDEOGRAPH - 0xE776: 0x84EF, //CJK UNIFIED IDEOGRAPH - 0xE777: 0x84F9, //CJK UNIFIED IDEOGRAPH - 0xE778: 0x8518, //CJK UNIFIED IDEOGRAPH - 0xE779: 0x8520, //CJK UNIFIED IDEOGRAPH - 0xE77A: 0x8530, //CJK UNIFIED IDEOGRAPH - 0xE77B: 0x850B, //CJK UNIFIED IDEOGRAPH - 0xE77C: 0x8519, //CJK UNIFIED IDEOGRAPH - 0xE77D: 0x852F, //CJK UNIFIED IDEOGRAPH - 0xE77E: 0x8662, //CJK UNIFIED IDEOGRAPH - 0xE7A1: 0x8756, //CJK UNIFIED IDEOGRAPH - 0xE7A2: 0x8763, //CJK UNIFIED IDEOGRAPH - 0xE7A3: 0x8764, //CJK UNIFIED IDEOGRAPH - 0xE7A4: 0x8777, //CJK UNIFIED IDEOGRAPH - 0xE7A5: 0x87E1, //CJK UNIFIED IDEOGRAPH - 0xE7A6: 0x8773, //CJK UNIFIED IDEOGRAPH - 0xE7A7: 0x8758, //CJK UNIFIED IDEOGRAPH - 0xE7A8: 0x8754, //CJK UNIFIED IDEOGRAPH - 0xE7A9: 0x875B, //CJK UNIFIED IDEOGRAPH - 0xE7AA: 0x8752, //CJK UNIFIED IDEOGRAPH - 0xE7AB: 0x8761, //CJK UNIFIED IDEOGRAPH - 0xE7AC: 0x875A, //CJK UNIFIED IDEOGRAPH - 0xE7AD: 0x8751, //CJK UNIFIED IDEOGRAPH - 0xE7AE: 0x875E, //CJK UNIFIED IDEOGRAPH - 0xE7AF: 0x876D, //CJK UNIFIED IDEOGRAPH - 0xE7B0: 0x876A, //CJK UNIFIED IDEOGRAPH - 0xE7B1: 0x8750, //CJK UNIFIED IDEOGRAPH - 0xE7B2: 0x874E, //CJK UNIFIED IDEOGRAPH - 0xE7B3: 0x875F, //CJK UNIFIED IDEOGRAPH - 0xE7B4: 0x875D, //CJK UNIFIED IDEOGRAPH - 0xE7B5: 0x876F, //CJK UNIFIED IDEOGRAPH - 0xE7B6: 0x876C, //CJK UNIFIED IDEOGRAPH - 0xE7B7: 0x877A, //CJK UNIFIED IDEOGRAPH - 0xE7B8: 0x876E, //CJK UNIFIED IDEOGRAPH - 0xE7B9: 0x875C, //CJK UNIFIED IDEOGRAPH - 0xE7BA: 0x8765, //CJK UNIFIED IDEOGRAPH - 0xE7BB: 0x874F, //CJK UNIFIED IDEOGRAPH - 0xE7BC: 0x877B, //CJK UNIFIED IDEOGRAPH - 0xE7BD: 0x8775, //CJK UNIFIED IDEOGRAPH - 0xE7BE: 0x8762, //CJK UNIFIED IDEOGRAPH - 0xE7BF: 0x8767, //CJK UNIFIED IDEOGRAPH - 0xE7C0: 0x8769, //CJK UNIFIED IDEOGRAPH - 0xE7C1: 0x885A, //CJK UNIFIED IDEOGRAPH - 0xE7C2: 0x8905, //CJK UNIFIED IDEOGRAPH - 0xE7C3: 0x890C, //CJK UNIFIED IDEOGRAPH - 0xE7C4: 0x8914, //CJK UNIFIED IDEOGRAPH - 0xE7C5: 0x890B, //CJK UNIFIED IDEOGRAPH - 0xE7C6: 0x8917, //CJK UNIFIED IDEOGRAPH - 0xE7C7: 0x8918, //CJK UNIFIED IDEOGRAPH - 0xE7C8: 0x8919, //CJK UNIFIED IDEOGRAPH - 0xE7C9: 0x8906, //CJK UNIFIED IDEOGRAPH - 0xE7CA: 0x8916, //CJK UNIFIED IDEOGRAPH - 0xE7CB: 0x8911, //CJK UNIFIED IDEOGRAPH - 0xE7CC: 0x890E, //CJK UNIFIED IDEOGRAPH - 0xE7CD: 0x8909, //CJK UNIFIED IDEOGRAPH - 0xE7CE: 0x89A2, //CJK UNIFIED IDEOGRAPH - 0xE7CF: 0x89A4, //CJK UNIFIED IDEOGRAPH - 0xE7D0: 0x89A3, //CJK UNIFIED IDEOGRAPH - 0xE7D1: 0x89ED, //CJK UNIFIED IDEOGRAPH - 0xE7D2: 0x89F0, //CJK UNIFIED IDEOGRAPH - 0xE7D3: 0x89EC, //CJK UNIFIED IDEOGRAPH - 0xE7D4: 0x8ACF, //CJK UNIFIED IDEOGRAPH - 0xE7D5: 0x8AC6, //CJK UNIFIED IDEOGRAPH - 0xE7D6: 0x8AB8, //CJK UNIFIED IDEOGRAPH - 0xE7D7: 0x8AD3, //CJK UNIFIED IDEOGRAPH - 0xE7D8: 0x8AD1, //CJK UNIFIED IDEOGRAPH - 0xE7D9: 0x8AD4, //CJK UNIFIED IDEOGRAPH - 0xE7DA: 0x8AD5, //CJK UNIFIED IDEOGRAPH - 0xE7DB: 0x8ABB, //CJK UNIFIED IDEOGRAPH - 0xE7DC: 0x8AD7, //CJK UNIFIED IDEOGRAPH - 0xE7DD: 0x8ABE, //CJK UNIFIED IDEOGRAPH - 0xE7DE: 0x8AC0, //CJK UNIFIED IDEOGRAPH - 0xE7DF: 0x8AC5, //CJK UNIFIED IDEOGRAPH - 0xE7E0: 0x8AD8, //CJK UNIFIED IDEOGRAPH - 0xE7E1: 0x8AC3, //CJK UNIFIED IDEOGRAPH - 0xE7E2: 0x8ABA, //CJK UNIFIED IDEOGRAPH - 0xE7E3: 0x8ABD, //CJK UNIFIED IDEOGRAPH - 0xE7E4: 0x8AD9, //CJK UNIFIED IDEOGRAPH - 0xE7E5: 0x8C3E, //CJK UNIFIED IDEOGRAPH - 0xE7E6: 0x8C4D, //CJK UNIFIED IDEOGRAPH - 0xE7E7: 0x8C8F, //CJK UNIFIED IDEOGRAPH - 0xE7E8: 0x8CE5, //CJK UNIFIED IDEOGRAPH - 0xE7E9: 0x8CDF, //CJK UNIFIED IDEOGRAPH - 0xE7EA: 0x8CD9, //CJK UNIFIED IDEOGRAPH - 0xE7EB: 0x8CE8, //CJK UNIFIED IDEOGRAPH - 0xE7EC: 0x8CDA, //CJK UNIFIED IDEOGRAPH - 0xE7ED: 0x8CDD, //CJK UNIFIED IDEOGRAPH - 0xE7EE: 0x8CE7, //CJK UNIFIED IDEOGRAPH - 0xE7EF: 0x8DA0, //CJK UNIFIED IDEOGRAPH - 0xE7F0: 0x8D9C, //CJK UNIFIED IDEOGRAPH - 0xE7F1: 0x8DA1, //CJK UNIFIED IDEOGRAPH - 0xE7F2: 0x8D9B, //CJK UNIFIED IDEOGRAPH - 0xE7F3: 0x8E20, //CJK UNIFIED IDEOGRAPH - 0xE7F4: 0x8E23, //CJK UNIFIED IDEOGRAPH - 0xE7F5: 0x8E25, //CJK UNIFIED IDEOGRAPH - 0xE7F6: 0x8E24, //CJK UNIFIED IDEOGRAPH - 0xE7F7: 0x8E2E, //CJK UNIFIED IDEOGRAPH - 0xE7F8: 0x8E15, //CJK UNIFIED IDEOGRAPH - 0xE7F9: 0x8E1B, //CJK UNIFIED IDEOGRAPH - 0xE7FA: 0x8E16, //CJK UNIFIED IDEOGRAPH - 0xE7FB: 0x8E11, //CJK UNIFIED IDEOGRAPH - 0xE7FC: 0x8E19, //CJK UNIFIED IDEOGRAPH - 0xE7FD: 0x8E26, //CJK UNIFIED IDEOGRAPH - 0xE7FE: 0x8E27, //CJK UNIFIED IDEOGRAPH - 0xE840: 0x8E14, //CJK UNIFIED IDEOGRAPH - 0xE841: 0x8E12, //CJK UNIFIED IDEOGRAPH - 0xE842: 0x8E18, //CJK UNIFIED IDEOGRAPH - 0xE843: 0x8E13, //CJK UNIFIED IDEOGRAPH - 0xE844: 0x8E1C, //CJK UNIFIED IDEOGRAPH - 0xE845: 0x8E17, //CJK UNIFIED IDEOGRAPH - 0xE846: 0x8E1A, //CJK UNIFIED IDEOGRAPH - 0xE847: 0x8F2C, //CJK UNIFIED IDEOGRAPH - 0xE848: 0x8F24, //CJK UNIFIED IDEOGRAPH - 0xE849: 0x8F18, //CJK UNIFIED IDEOGRAPH - 0xE84A: 0x8F1A, //CJK UNIFIED IDEOGRAPH - 0xE84B: 0x8F20, //CJK UNIFIED IDEOGRAPH - 0xE84C: 0x8F23, //CJK UNIFIED IDEOGRAPH - 0xE84D: 0x8F16, //CJK UNIFIED IDEOGRAPH - 0xE84E: 0x8F17, //CJK UNIFIED IDEOGRAPH - 0xE84F: 0x9073, //CJK UNIFIED IDEOGRAPH - 0xE850: 0x9070, //CJK UNIFIED IDEOGRAPH - 0xE851: 0x906F, //CJK UNIFIED IDEOGRAPH - 0xE852: 0x9067, //CJK UNIFIED IDEOGRAPH - 0xE853: 0x906B, //CJK UNIFIED IDEOGRAPH - 0xE854: 0x912F, //CJK UNIFIED IDEOGRAPH - 0xE855: 0x912B, //CJK UNIFIED IDEOGRAPH - 0xE856: 0x9129, //CJK UNIFIED IDEOGRAPH - 0xE857: 0x912A, //CJK UNIFIED IDEOGRAPH - 0xE858: 0x9132, //CJK UNIFIED IDEOGRAPH - 0xE859: 0x9126, //CJK UNIFIED IDEOGRAPH - 0xE85A: 0x912E, //CJK UNIFIED IDEOGRAPH - 0xE85B: 0x9185, //CJK UNIFIED IDEOGRAPH - 0xE85C: 0x9186, //CJK UNIFIED IDEOGRAPH - 0xE85D: 0x918A, //CJK UNIFIED IDEOGRAPH - 0xE85E: 0x9181, //CJK UNIFIED IDEOGRAPH - 0xE85F: 0x9182, //CJK UNIFIED IDEOGRAPH - 0xE860: 0x9184, //CJK UNIFIED IDEOGRAPH - 0xE861: 0x9180, //CJK UNIFIED IDEOGRAPH - 0xE862: 0x92D0, //CJK UNIFIED IDEOGRAPH - 0xE863: 0x92C3, //CJK UNIFIED IDEOGRAPH - 0xE864: 0x92C4, //CJK UNIFIED IDEOGRAPH - 0xE865: 0x92C0, //CJK UNIFIED IDEOGRAPH - 0xE866: 0x92D9, //CJK UNIFIED IDEOGRAPH - 0xE867: 0x92B6, //CJK UNIFIED IDEOGRAPH - 0xE868: 0x92CF, //CJK UNIFIED IDEOGRAPH - 0xE869: 0x92F1, //CJK UNIFIED IDEOGRAPH - 0xE86A: 0x92DF, //CJK UNIFIED IDEOGRAPH - 0xE86B: 0x92D8, //CJK UNIFIED IDEOGRAPH - 0xE86C: 0x92E9, //CJK UNIFIED IDEOGRAPH - 0xE86D: 0x92D7, //CJK UNIFIED IDEOGRAPH - 0xE86E: 0x92DD, //CJK UNIFIED IDEOGRAPH - 0xE86F: 0x92CC, //CJK UNIFIED IDEOGRAPH - 0xE870: 0x92EF, //CJK UNIFIED IDEOGRAPH - 0xE871: 0x92C2, //CJK UNIFIED IDEOGRAPH - 0xE872: 0x92E8, //CJK UNIFIED IDEOGRAPH - 0xE873: 0x92CA, //CJK UNIFIED IDEOGRAPH - 0xE874: 0x92C8, //CJK UNIFIED IDEOGRAPH - 0xE875: 0x92CE, //CJK UNIFIED IDEOGRAPH - 0xE876: 0x92E6, //CJK UNIFIED IDEOGRAPH - 0xE877: 0x92CD, //CJK UNIFIED IDEOGRAPH - 0xE878: 0x92D5, //CJK UNIFIED IDEOGRAPH - 0xE879: 0x92C9, //CJK UNIFIED IDEOGRAPH - 0xE87A: 0x92E0, //CJK UNIFIED IDEOGRAPH - 0xE87B: 0x92DE, //CJK UNIFIED IDEOGRAPH - 0xE87C: 0x92E7, //CJK UNIFIED IDEOGRAPH - 0xE87D: 0x92D1, //CJK UNIFIED IDEOGRAPH - 0xE87E: 0x92D3, //CJK UNIFIED IDEOGRAPH - 0xE8A1: 0x92B5, //CJK UNIFIED IDEOGRAPH - 0xE8A2: 0x92E1, //CJK UNIFIED IDEOGRAPH - 0xE8A3: 0x92C6, //CJK UNIFIED IDEOGRAPH - 0xE8A4: 0x92B4, //CJK UNIFIED IDEOGRAPH - 0xE8A5: 0x957C, //CJK UNIFIED IDEOGRAPH - 0xE8A6: 0x95AC, //CJK UNIFIED IDEOGRAPH - 0xE8A7: 0x95AB, //CJK UNIFIED IDEOGRAPH - 0xE8A8: 0x95AE, //CJK UNIFIED IDEOGRAPH - 0xE8A9: 0x95B0, //CJK UNIFIED IDEOGRAPH - 0xE8AA: 0x96A4, //CJK UNIFIED IDEOGRAPH - 0xE8AB: 0x96A2, //CJK UNIFIED IDEOGRAPH - 0xE8AC: 0x96D3, //CJK UNIFIED IDEOGRAPH - 0xE8AD: 0x9705, //CJK UNIFIED IDEOGRAPH - 0xE8AE: 0x9708, //CJK UNIFIED IDEOGRAPH - 0xE8AF: 0x9702, //CJK UNIFIED IDEOGRAPH - 0xE8B0: 0x975A, //CJK UNIFIED IDEOGRAPH - 0xE8B1: 0x978A, //CJK UNIFIED IDEOGRAPH - 0xE8B2: 0x978E, //CJK UNIFIED IDEOGRAPH - 0xE8B3: 0x9788, //CJK UNIFIED IDEOGRAPH - 0xE8B4: 0x97D0, //CJK UNIFIED IDEOGRAPH - 0xE8B5: 0x97CF, //CJK UNIFIED IDEOGRAPH - 0xE8B6: 0x981E, //CJK UNIFIED IDEOGRAPH - 0xE8B7: 0x981D, //CJK UNIFIED IDEOGRAPH - 0xE8B8: 0x9826, //CJK UNIFIED IDEOGRAPH - 0xE8B9: 0x9829, //CJK UNIFIED IDEOGRAPH - 0xE8BA: 0x9828, //CJK UNIFIED IDEOGRAPH - 0xE8BB: 0x9820, //CJK UNIFIED IDEOGRAPH - 0xE8BC: 0x981B, //CJK UNIFIED IDEOGRAPH - 0xE8BD: 0x9827, //CJK UNIFIED IDEOGRAPH - 0xE8BE: 0x98B2, //CJK UNIFIED IDEOGRAPH - 0xE8BF: 0x9908, //CJK UNIFIED IDEOGRAPH - 0xE8C0: 0x98FA, //CJK UNIFIED IDEOGRAPH - 0xE8C1: 0x9911, //CJK UNIFIED IDEOGRAPH - 0xE8C2: 0x9914, //CJK UNIFIED IDEOGRAPH - 0xE8C3: 0x9916, //CJK UNIFIED IDEOGRAPH - 0xE8C4: 0x9917, //CJK UNIFIED IDEOGRAPH - 0xE8C5: 0x9915, //CJK UNIFIED IDEOGRAPH - 0xE8C6: 0x99DC, //CJK UNIFIED IDEOGRAPH - 0xE8C7: 0x99CD, //CJK UNIFIED IDEOGRAPH - 0xE8C8: 0x99CF, //CJK UNIFIED IDEOGRAPH - 0xE8C9: 0x99D3, //CJK UNIFIED IDEOGRAPH - 0xE8CA: 0x99D4, //CJK UNIFIED IDEOGRAPH - 0xE8CB: 0x99CE, //CJK UNIFIED IDEOGRAPH - 0xE8CC: 0x99C9, //CJK UNIFIED IDEOGRAPH - 0xE8CD: 0x99D6, //CJK UNIFIED IDEOGRAPH - 0xE8CE: 0x99D8, //CJK UNIFIED IDEOGRAPH - 0xE8CF: 0x99CB, //CJK UNIFIED IDEOGRAPH - 0xE8D0: 0x99D7, //CJK UNIFIED IDEOGRAPH - 0xE8D1: 0x99CC, //CJK UNIFIED IDEOGRAPH - 0xE8D2: 0x9AB3, //CJK UNIFIED IDEOGRAPH - 0xE8D3: 0x9AEC, //CJK UNIFIED IDEOGRAPH - 0xE8D4: 0x9AEB, //CJK UNIFIED IDEOGRAPH - 0xE8D5: 0x9AF3, //CJK UNIFIED IDEOGRAPH - 0xE8D6: 0x9AF2, //CJK UNIFIED IDEOGRAPH - 0xE8D7: 0x9AF1, //CJK UNIFIED IDEOGRAPH - 0xE8D8: 0x9B46, //CJK UNIFIED IDEOGRAPH - 0xE8D9: 0x9B43, //CJK UNIFIED IDEOGRAPH - 0xE8DA: 0x9B67, //CJK UNIFIED IDEOGRAPH - 0xE8DB: 0x9B74, //CJK UNIFIED IDEOGRAPH - 0xE8DC: 0x9B71, //CJK UNIFIED IDEOGRAPH - 0xE8DD: 0x9B66, //CJK UNIFIED IDEOGRAPH - 0xE8DE: 0x9B76, //CJK UNIFIED IDEOGRAPH - 0xE8DF: 0x9B75, //CJK UNIFIED IDEOGRAPH - 0xE8E0: 0x9B70, //CJK UNIFIED IDEOGRAPH - 0xE8E1: 0x9B68, //CJK UNIFIED IDEOGRAPH - 0xE8E2: 0x9B64, //CJK UNIFIED IDEOGRAPH - 0xE8E3: 0x9B6C, //CJK UNIFIED IDEOGRAPH - 0xE8E4: 0x9CFC, //CJK UNIFIED IDEOGRAPH - 0xE8E5: 0x9CFA, //CJK UNIFIED IDEOGRAPH - 0xE8E6: 0x9CFD, //CJK UNIFIED IDEOGRAPH - 0xE8E7: 0x9CFF, //CJK UNIFIED IDEOGRAPH - 0xE8E8: 0x9CF7, //CJK UNIFIED IDEOGRAPH - 0xE8E9: 0x9D07, //CJK UNIFIED IDEOGRAPH - 0xE8EA: 0x9D00, //CJK UNIFIED IDEOGRAPH - 0xE8EB: 0x9CF9, //CJK UNIFIED IDEOGRAPH - 0xE8EC: 0x9CFB, //CJK UNIFIED IDEOGRAPH - 0xE8ED: 0x9D08, //CJK UNIFIED IDEOGRAPH - 0xE8EE: 0x9D05, //CJK UNIFIED IDEOGRAPH - 0xE8EF: 0x9D04, //CJK UNIFIED IDEOGRAPH - 0xE8F0: 0x9E83, //CJK UNIFIED IDEOGRAPH - 0xE8F1: 0x9ED3, //CJK UNIFIED IDEOGRAPH - 0xE8F2: 0x9F0F, //CJK UNIFIED IDEOGRAPH - 0xE8F3: 0x9F10, //CJK UNIFIED IDEOGRAPH - 0xE8F4: 0x511C, //CJK UNIFIED IDEOGRAPH - 0xE8F5: 0x5113, //CJK UNIFIED IDEOGRAPH - 0xE8F6: 0x5117, //CJK UNIFIED IDEOGRAPH - 0xE8F7: 0x511A, //CJK UNIFIED IDEOGRAPH - 0xE8F8: 0x5111, //CJK UNIFIED IDEOGRAPH - 0xE8F9: 0x51DE, //CJK UNIFIED IDEOGRAPH - 0xE8FA: 0x5334, //CJK UNIFIED IDEOGRAPH - 0xE8FB: 0x53E1, //CJK UNIFIED IDEOGRAPH - 0xE8FC: 0x5670, //CJK UNIFIED IDEOGRAPH - 0xE8FD: 0x5660, //CJK UNIFIED IDEOGRAPH - 0xE8FE: 0x566E, //CJK UNIFIED IDEOGRAPH - 0xE940: 0x5673, //CJK UNIFIED IDEOGRAPH - 0xE941: 0x5666, //CJK UNIFIED IDEOGRAPH - 0xE942: 0x5663, //CJK UNIFIED IDEOGRAPH - 0xE943: 0x566D, //CJK UNIFIED IDEOGRAPH - 0xE944: 0x5672, //CJK UNIFIED IDEOGRAPH - 0xE945: 0x565E, //CJK UNIFIED IDEOGRAPH - 0xE946: 0x5677, //CJK UNIFIED IDEOGRAPH - 0xE947: 0x571C, //CJK UNIFIED IDEOGRAPH - 0xE948: 0x571B, //CJK UNIFIED IDEOGRAPH - 0xE949: 0x58C8, //CJK UNIFIED IDEOGRAPH - 0xE94A: 0x58BD, //CJK UNIFIED IDEOGRAPH - 0xE94B: 0x58C9, //CJK UNIFIED IDEOGRAPH - 0xE94C: 0x58BF, //CJK UNIFIED IDEOGRAPH - 0xE94D: 0x58BA, //CJK UNIFIED IDEOGRAPH - 0xE94E: 0x58C2, //CJK UNIFIED IDEOGRAPH - 0xE94F: 0x58BC, //CJK UNIFIED IDEOGRAPH - 0xE950: 0x58C6, //CJK UNIFIED IDEOGRAPH - 0xE951: 0x5B17, //CJK UNIFIED IDEOGRAPH - 0xE952: 0x5B19, //CJK UNIFIED IDEOGRAPH - 0xE953: 0x5B1B, //CJK UNIFIED IDEOGRAPH - 0xE954: 0x5B21, //CJK UNIFIED IDEOGRAPH - 0xE955: 0x5B14, //CJK UNIFIED IDEOGRAPH - 0xE956: 0x5B13, //CJK UNIFIED IDEOGRAPH - 0xE957: 0x5B10, //CJK UNIFIED IDEOGRAPH - 0xE958: 0x5B16, //CJK UNIFIED IDEOGRAPH - 0xE959: 0x5B28, //CJK UNIFIED IDEOGRAPH - 0xE95A: 0x5B1A, //CJK UNIFIED IDEOGRAPH - 0xE95B: 0x5B20, //CJK UNIFIED IDEOGRAPH - 0xE95C: 0x5B1E, //CJK UNIFIED IDEOGRAPH - 0xE95D: 0x5BEF, //CJK UNIFIED IDEOGRAPH - 0xE95E: 0x5DAC, //CJK UNIFIED IDEOGRAPH - 0xE95F: 0x5DB1, //CJK UNIFIED IDEOGRAPH - 0xE960: 0x5DA9, //CJK UNIFIED IDEOGRAPH - 0xE961: 0x5DA7, //CJK UNIFIED IDEOGRAPH - 0xE962: 0x5DB5, //CJK UNIFIED IDEOGRAPH - 0xE963: 0x5DB0, //CJK UNIFIED IDEOGRAPH - 0xE964: 0x5DAE, //CJK UNIFIED IDEOGRAPH - 0xE965: 0x5DAA, //CJK UNIFIED IDEOGRAPH - 0xE966: 0x5DA8, //CJK UNIFIED IDEOGRAPH - 0xE967: 0x5DB2, //CJK UNIFIED IDEOGRAPH - 0xE968: 0x5DAD, //CJK UNIFIED IDEOGRAPH - 0xE969: 0x5DAF, //CJK UNIFIED IDEOGRAPH - 0xE96A: 0x5DB4, //CJK UNIFIED IDEOGRAPH - 0xE96B: 0x5E67, //CJK UNIFIED IDEOGRAPH - 0xE96C: 0x5E68, //CJK UNIFIED IDEOGRAPH - 0xE96D: 0x5E66, //CJK UNIFIED IDEOGRAPH - 0xE96E: 0x5E6F, //CJK UNIFIED IDEOGRAPH - 0xE96F: 0x5EE9, //CJK UNIFIED IDEOGRAPH - 0xE970: 0x5EE7, //CJK UNIFIED IDEOGRAPH - 0xE971: 0x5EE6, //CJK UNIFIED IDEOGRAPH - 0xE972: 0x5EE8, //CJK UNIFIED IDEOGRAPH - 0xE973: 0x5EE5, //CJK UNIFIED IDEOGRAPH - 0xE974: 0x5F4B, //CJK UNIFIED IDEOGRAPH - 0xE975: 0x5FBC, //CJK UNIFIED IDEOGRAPH - 0xE976: 0x619D, //CJK UNIFIED IDEOGRAPH - 0xE977: 0x61A8, //CJK UNIFIED IDEOGRAPH - 0xE978: 0x6196, //CJK UNIFIED IDEOGRAPH - 0xE979: 0x61C5, //CJK UNIFIED IDEOGRAPH - 0xE97A: 0x61B4, //CJK UNIFIED IDEOGRAPH - 0xE97B: 0x61C6, //CJK UNIFIED IDEOGRAPH - 0xE97C: 0x61C1, //CJK UNIFIED IDEOGRAPH - 0xE97D: 0x61CC, //CJK UNIFIED IDEOGRAPH - 0xE97E: 0x61BA, //CJK UNIFIED IDEOGRAPH - 0xE9A1: 0x61BF, //CJK UNIFIED IDEOGRAPH - 0xE9A2: 0x61B8, //CJK UNIFIED IDEOGRAPH - 0xE9A3: 0x618C, //CJK UNIFIED IDEOGRAPH - 0xE9A4: 0x64D7, //CJK UNIFIED IDEOGRAPH - 0xE9A5: 0x64D6, //CJK UNIFIED IDEOGRAPH - 0xE9A6: 0x64D0, //CJK UNIFIED IDEOGRAPH - 0xE9A7: 0x64CF, //CJK UNIFIED IDEOGRAPH - 0xE9A8: 0x64C9, //CJK UNIFIED IDEOGRAPH - 0xE9A9: 0x64BD, //CJK UNIFIED IDEOGRAPH - 0xE9AA: 0x6489, //CJK UNIFIED IDEOGRAPH - 0xE9AB: 0x64C3, //CJK UNIFIED IDEOGRAPH - 0xE9AC: 0x64DB, //CJK UNIFIED IDEOGRAPH - 0xE9AD: 0x64F3, //CJK UNIFIED IDEOGRAPH - 0xE9AE: 0x64D9, //CJK UNIFIED IDEOGRAPH - 0xE9AF: 0x6533, //CJK UNIFIED IDEOGRAPH - 0xE9B0: 0x657F, //CJK UNIFIED IDEOGRAPH - 0xE9B1: 0x657C, //CJK UNIFIED IDEOGRAPH - 0xE9B2: 0x65A2, //CJK UNIFIED IDEOGRAPH - 0xE9B3: 0x66C8, //CJK UNIFIED IDEOGRAPH - 0xE9B4: 0x66BE, //CJK UNIFIED IDEOGRAPH - 0xE9B5: 0x66C0, //CJK UNIFIED IDEOGRAPH - 0xE9B6: 0x66CA, //CJK UNIFIED IDEOGRAPH - 0xE9B7: 0x66CB, //CJK UNIFIED IDEOGRAPH - 0xE9B8: 0x66CF, //CJK UNIFIED IDEOGRAPH - 0xE9B9: 0x66BD, //CJK UNIFIED IDEOGRAPH - 0xE9BA: 0x66BB, //CJK UNIFIED IDEOGRAPH - 0xE9BB: 0x66BA, //CJK UNIFIED IDEOGRAPH - 0xE9BC: 0x66CC, //CJK UNIFIED IDEOGRAPH - 0xE9BD: 0x6723, //CJK UNIFIED IDEOGRAPH - 0xE9BE: 0x6A34, //CJK UNIFIED IDEOGRAPH - 0xE9BF: 0x6A66, //CJK UNIFIED IDEOGRAPH - 0xE9C0: 0x6A49, //CJK UNIFIED IDEOGRAPH - 0xE9C1: 0x6A67, //CJK UNIFIED IDEOGRAPH - 0xE9C2: 0x6A32, //CJK UNIFIED IDEOGRAPH - 0xE9C3: 0x6A68, //CJK UNIFIED IDEOGRAPH - 0xE9C4: 0x6A3E, //CJK UNIFIED IDEOGRAPH - 0xE9C5: 0x6A5D, //CJK UNIFIED IDEOGRAPH - 0xE9C6: 0x6A6D, //CJK UNIFIED IDEOGRAPH - 0xE9C7: 0x6A76, //CJK UNIFIED IDEOGRAPH - 0xE9C8: 0x6A5B, //CJK UNIFIED IDEOGRAPH - 0xE9C9: 0x6A51, //CJK UNIFIED IDEOGRAPH - 0xE9CA: 0x6A28, //CJK UNIFIED IDEOGRAPH - 0xE9CB: 0x6A5A, //CJK UNIFIED IDEOGRAPH - 0xE9CC: 0x6A3B, //CJK UNIFIED IDEOGRAPH - 0xE9CD: 0x6A3F, //CJK UNIFIED IDEOGRAPH - 0xE9CE: 0x6A41, //CJK UNIFIED IDEOGRAPH - 0xE9CF: 0x6A6A, //CJK UNIFIED IDEOGRAPH - 0xE9D0: 0x6A64, //CJK UNIFIED IDEOGRAPH - 0xE9D1: 0x6A50, //CJK UNIFIED IDEOGRAPH - 0xE9D2: 0x6A4F, //CJK UNIFIED IDEOGRAPH - 0xE9D3: 0x6A54, //CJK UNIFIED IDEOGRAPH - 0xE9D4: 0x6A6F, //CJK UNIFIED IDEOGRAPH - 0xE9D5: 0x6A69, //CJK UNIFIED IDEOGRAPH - 0xE9D6: 0x6A60, //CJK UNIFIED IDEOGRAPH - 0xE9D7: 0x6A3C, //CJK UNIFIED IDEOGRAPH - 0xE9D8: 0x6A5E, //CJK UNIFIED IDEOGRAPH - 0xE9D9: 0x6A56, //CJK UNIFIED IDEOGRAPH - 0xE9DA: 0x6A55, //CJK UNIFIED IDEOGRAPH - 0xE9DB: 0x6A4D, //CJK UNIFIED IDEOGRAPH - 0xE9DC: 0x6A4E, //CJK UNIFIED IDEOGRAPH - 0xE9DD: 0x6A46, //CJK UNIFIED IDEOGRAPH - 0xE9DE: 0x6B55, //CJK UNIFIED IDEOGRAPH - 0xE9DF: 0x6B54, //CJK UNIFIED IDEOGRAPH - 0xE9E0: 0x6B56, //CJK UNIFIED IDEOGRAPH - 0xE9E1: 0x6BA7, //CJK UNIFIED IDEOGRAPH - 0xE9E2: 0x6BAA, //CJK UNIFIED IDEOGRAPH - 0xE9E3: 0x6BAB, //CJK UNIFIED IDEOGRAPH - 0xE9E4: 0x6BC8, //CJK UNIFIED IDEOGRAPH - 0xE9E5: 0x6BC7, //CJK UNIFIED IDEOGRAPH - 0xE9E6: 0x6C04, //CJK UNIFIED IDEOGRAPH - 0xE9E7: 0x6C03, //CJK UNIFIED IDEOGRAPH - 0xE9E8: 0x6C06, //CJK UNIFIED IDEOGRAPH - 0xE9E9: 0x6FAD, //CJK UNIFIED IDEOGRAPH - 0xE9EA: 0x6FCB, //CJK UNIFIED IDEOGRAPH - 0xE9EB: 0x6FA3, //CJK UNIFIED IDEOGRAPH - 0xE9EC: 0x6FC7, //CJK UNIFIED IDEOGRAPH - 0xE9ED: 0x6FBC, //CJK UNIFIED IDEOGRAPH - 0xE9EE: 0x6FCE, //CJK UNIFIED IDEOGRAPH - 0xE9EF: 0x6FC8, //CJK UNIFIED IDEOGRAPH - 0xE9F0: 0x6F5E, //CJK UNIFIED IDEOGRAPH - 0xE9F1: 0x6FC4, //CJK UNIFIED IDEOGRAPH - 0xE9F2: 0x6FBD, //CJK UNIFIED IDEOGRAPH - 0xE9F3: 0x6F9E, //CJK UNIFIED IDEOGRAPH - 0xE9F4: 0x6FCA, //CJK UNIFIED IDEOGRAPH - 0xE9F5: 0x6FA8, //CJK UNIFIED IDEOGRAPH - 0xE9F6: 0x7004, //CJK UNIFIED IDEOGRAPH - 0xE9F7: 0x6FA5, //CJK UNIFIED IDEOGRAPH - 0xE9F8: 0x6FAE, //CJK UNIFIED IDEOGRAPH - 0xE9F9: 0x6FBA, //CJK UNIFIED IDEOGRAPH - 0xE9FA: 0x6FAC, //CJK UNIFIED IDEOGRAPH - 0xE9FB: 0x6FAA, //CJK UNIFIED IDEOGRAPH - 0xE9FC: 0x6FCF, //CJK UNIFIED IDEOGRAPH - 0xE9FD: 0x6FBF, //CJK UNIFIED IDEOGRAPH - 0xE9FE: 0x6FB8, //CJK UNIFIED IDEOGRAPH - 0xEA40: 0x6FA2, //CJK UNIFIED IDEOGRAPH - 0xEA41: 0x6FC9, //CJK UNIFIED IDEOGRAPH - 0xEA42: 0x6FAB, //CJK UNIFIED IDEOGRAPH - 0xEA43: 0x6FCD, //CJK UNIFIED IDEOGRAPH - 0xEA44: 0x6FAF, //CJK UNIFIED IDEOGRAPH - 0xEA45: 0x6FB2, //CJK UNIFIED IDEOGRAPH - 0xEA46: 0x6FB0, //CJK UNIFIED IDEOGRAPH - 0xEA47: 0x71C5, //CJK UNIFIED IDEOGRAPH - 0xEA48: 0x71C2, //CJK UNIFIED IDEOGRAPH - 0xEA49: 0x71BF, //CJK UNIFIED IDEOGRAPH - 0xEA4A: 0x71B8, //CJK UNIFIED IDEOGRAPH - 0xEA4B: 0x71D6, //CJK UNIFIED IDEOGRAPH - 0xEA4C: 0x71C0, //CJK UNIFIED IDEOGRAPH - 0xEA4D: 0x71C1, //CJK UNIFIED IDEOGRAPH - 0xEA4E: 0x71CB, //CJK UNIFIED IDEOGRAPH - 0xEA4F: 0x71D4, //CJK UNIFIED IDEOGRAPH - 0xEA50: 0x71CA, //CJK UNIFIED IDEOGRAPH - 0xEA51: 0x71C7, //CJK UNIFIED IDEOGRAPH - 0xEA52: 0x71CF, //CJK UNIFIED IDEOGRAPH - 0xEA53: 0x71BD, //CJK UNIFIED IDEOGRAPH - 0xEA54: 0x71D8, //CJK UNIFIED IDEOGRAPH - 0xEA55: 0x71BC, //CJK UNIFIED IDEOGRAPH - 0xEA56: 0x71C6, //CJK UNIFIED IDEOGRAPH - 0xEA57: 0x71DA, //CJK UNIFIED IDEOGRAPH - 0xEA58: 0x71DB, //CJK UNIFIED IDEOGRAPH - 0xEA59: 0x729D, //CJK UNIFIED IDEOGRAPH - 0xEA5A: 0x729E, //CJK UNIFIED IDEOGRAPH - 0xEA5B: 0x7369, //CJK UNIFIED IDEOGRAPH - 0xEA5C: 0x7366, //CJK UNIFIED IDEOGRAPH - 0xEA5D: 0x7367, //CJK UNIFIED IDEOGRAPH - 0xEA5E: 0x736C, //CJK UNIFIED IDEOGRAPH - 0xEA5F: 0x7365, //CJK UNIFIED IDEOGRAPH - 0xEA60: 0x736B, //CJK UNIFIED IDEOGRAPH - 0xEA61: 0x736A, //CJK UNIFIED IDEOGRAPH - 0xEA62: 0x747F, //CJK UNIFIED IDEOGRAPH - 0xEA63: 0x749A, //CJK UNIFIED IDEOGRAPH - 0xEA64: 0x74A0, //CJK UNIFIED IDEOGRAPH - 0xEA65: 0x7494, //CJK UNIFIED IDEOGRAPH - 0xEA66: 0x7492, //CJK UNIFIED IDEOGRAPH - 0xEA67: 0x7495, //CJK UNIFIED IDEOGRAPH - 0xEA68: 0x74A1, //CJK UNIFIED IDEOGRAPH - 0xEA69: 0x750B, //CJK UNIFIED IDEOGRAPH - 0xEA6A: 0x7580, //CJK UNIFIED IDEOGRAPH - 0xEA6B: 0x762F, //CJK UNIFIED IDEOGRAPH - 0xEA6C: 0x762D, //CJK UNIFIED IDEOGRAPH - 0xEA6D: 0x7631, //CJK UNIFIED IDEOGRAPH - 0xEA6E: 0x763D, //CJK UNIFIED IDEOGRAPH - 0xEA6F: 0x7633, //CJK UNIFIED IDEOGRAPH - 0xEA70: 0x763C, //CJK UNIFIED IDEOGRAPH - 0xEA71: 0x7635, //CJK UNIFIED IDEOGRAPH - 0xEA72: 0x7632, //CJK UNIFIED IDEOGRAPH - 0xEA73: 0x7630, //CJK UNIFIED IDEOGRAPH - 0xEA74: 0x76BB, //CJK UNIFIED IDEOGRAPH - 0xEA75: 0x76E6, //CJK UNIFIED IDEOGRAPH - 0xEA76: 0x779A, //CJK UNIFIED IDEOGRAPH - 0xEA77: 0x779D, //CJK UNIFIED IDEOGRAPH - 0xEA78: 0x77A1, //CJK UNIFIED IDEOGRAPH - 0xEA79: 0x779C, //CJK UNIFIED IDEOGRAPH - 0xEA7A: 0x779B, //CJK UNIFIED IDEOGRAPH - 0xEA7B: 0x77A2, //CJK UNIFIED IDEOGRAPH - 0xEA7C: 0x77A3, //CJK UNIFIED IDEOGRAPH - 0xEA7D: 0x7795, //CJK UNIFIED IDEOGRAPH - 0xEA7E: 0x7799, //CJK UNIFIED IDEOGRAPH - 0xEAA1: 0x7797, //CJK UNIFIED IDEOGRAPH - 0xEAA2: 0x78DD, //CJK UNIFIED IDEOGRAPH - 0xEAA3: 0x78E9, //CJK UNIFIED IDEOGRAPH - 0xEAA4: 0x78E5, //CJK UNIFIED IDEOGRAPH - 0xEAA5: 0x78EA, //CJK UNIFIED IDEOGRAPH - 0xEAA6: 0x78DE, //CJK UNIFIED IDEOGRAPH - 0xEAA7: 0x78E3, //CJK UNIFIED IDEOGRAPH - 0xEAA8: 0x78DB, //CJK UNIFIED IDEOGRAPH - 0xEAA9: 0x78E1, //CJK UNIFIED IDEOGRAPH - 0xEAAA: 0x78E2, //CJK UNIFIED IDEOGRAPH - 0xEAAB: 0x78ED, //CJK UNIFIED IDEOGRAPH - 0xEAAC: 0x78DF, //CJK UNIFIED IDEOGRAPH - 0xEAAD: 0x78E0, //CJK UNIFIED IDEOGRAPH - 0xEAAE: 0x79A4, //CJK UNIFIED IDEOGRAPH - 0xEAAF: 0x7A44, //CJK UNIFIED IDEOGRAPH - 0xEAB0: 0x7A48, //CJK UNIFIED IDEOGRAPH - 0xEAB1: 0x7A47, //CJK UNIFIED IDEOGRAPH - 0xEAB2: 0x7AB6, //CJK UNIFIED IDEOGRAPH - 0xEAB3: 0x7AB8, //CJK UNIFIED IDEOGRAPH - 0xEAB4: 0x7AB5, //CJK UNIFIED IDEOGRAPH - 0xEAB5: 0x7AB1, //CJK UNIFIED IDEOGRAPH - 0xEAB6: 0x7AB7, //CJK UNIFIED IDEOGRAPH - 0xEAB7: 0x7BDE, //CJK UNIFIED IDEOGRAPH - 0xEAB8: 0x7BE3, //CJK UNIFIED IDEOGRAPH - 0xEAB9: 0x7BE7, //CJK UNIFIED IDEOGRAPH - 0xEABA: 0x7BDD, //CJK UNIFIED IDEOGRAPH - 0xEABB: 0x7BD5, //CJK UNIFIED IDEOGRAPH - 0xEABC: 0x7BE5, //CJK UNIFIED IDEOGRAPH - 0xEABD: 0x7BDA, //CJK UNIFIED IDEOGRAPH - 0xEABE: 0x7BE8, //CJK UNIFIED IDEOGRAPH - 0xEABF: 0x7BF9, //CJK UNIFIED IDEOGRAPH - 0xEAC0: 0x7BD4, //CJK UNIFIED IDEOGRAPH - 0xEAC1: 0x7BEA, //CJK UNIFIED IDEOGRAPH - 0xEAC2: 0x7BE2, //CJK UNIFIED IDEOGRAPH - 0xEAC3: 0x7BDC, //CJK UNIFIED IDEOGRAPH - 0xEAC4: 0x7BEB, //CJK UNIFIED IDEOGRAPH - 0xEAC5: 0x7BD8, //CJK UNIFIED IDEOGRAPH - 0xEAC6: 0x7BDF, //CJK UNIFIED IDEOGRAPH - 0xEAC7: 0x7CD2, //CJK UNIFIED IDEOGRAPH - 0xEAC8: 0x7CD4, //CJK UNIFIED IDEOGRAPH - 0xEAC9: 0x7CD7, //CJK UNIFIED IDEOGRAPH - 0xEACA: 0x7CD0, //CJK UNIFIED IDEOGRAPH - 0xEACB: 0x7CD1, //CJK UNIFIED IDEOGRAPH - 0xEACC: 0x7E12, //CJK UNIFIED IDEOGRAPH - 0xEACD: 0x7E21, //CJK UNIFIED IDEOGRAPH - 0xEACE: 0x7E17, //CJK UNIFIED IDEOGRAPH - 0xEACF: 0x7E0C, //CJK UNIFIED IDEOGRAPH - 0xEAD0: 0x7E1F, //CJK UNIFIED IDEOGRAPH - 0xEAD1: 0x7E20, //CJK UNIFIED IDEOGRAPH - 0xEAD2: 0x7E13, //CJK UNIFIED IDEOGRAPH - 0xEAD3: 0x7E0E, //CJK UNIFIED IDEOGRAPH - 0xEAD4: 0x7E1C, //CJK UNIFIED IDEOGRAPH - 0xEAD5: 0x7E15, //CJK UNIFIED IDEOGRAPH - 0xEAD6: 0x7E1A, //CJK UNIFIED IDEOGRAPH - 0xEAD7: 0x7E22, //CJK UNIFIED IDEOGRAPH - 0xEAD8: 0x7E0B, //CJK UNIFIED IDEOGRAPH - 0xEAD9: 0x7E0F, //CJK UNIFIED IDEOGRAPH - 0xEADA: 0x7E16, //CJK UNIFIED IDEOGRAPH - 0xEADB: 0x7E0D, //CJK UNIFIED IDEOGRAPH - 0xEADC: 0x7E14, //CJK UNIFIED IDEOGRAPH - 0xEADD: 0x7E25, //CJK UNIFIED IDEOGRAPH - 0xEADE: 0x7E24, //CJK UNIFIED IDEOGRAPH - 0xEADF: 0x7F43, //CJK UNIFIED IDEOGRAPH - 0xEAE0: 0x7F7B, //CJK UNIFIED IDEOGRAPH - 0xEAE1: 0x7F7C, //CJK UNIFIED IDEOGRAPH - 0xEAE2: 0x7F7A, //CJK UNIFIED IDEOGRAPH - 0xEAE3: 0x7FB1, //CJK UNIFIED IDEOGRAPH - 0xEAE4: 0x7FEF, //CJK UNIFIED IDEOGRAPH - 0xEAE5: 0x802A, //CJK UNIFIED IDEOGRAPH - 0xEAE6: 0x8029, //CJK UNIFIED IDEOGRAPH - 0xEAE7: 0x806C, //CJK UNIFIED IDEOGRAPH - 0xEAE8: 0x81B1, //CJK UNIFIED IDEOGRAPH - 0xEAE9: 0x81A6, //CJK UNIFIED IDEOGRAPH - 0xEAEA: 0x81AE, //CJK UNIFIED IDEOGRAPH - 0xEAEB: 0x81B9, //CJK UNIFIED IDEOGRAPH - 0xEAEC: 0x81B5, //CJK UNIFIED IDEOGRAPH - 0xEAED: 0x81AB, //CJK UNIFIED IDEOGRAPH - 0xEAEE: 0x81B0, //CJK UNIFIED IDEOGRAPH - 0xEAEF: 0x81AC, //CJK UNIFIED IDEOGRAPH - 0xEAF0: 0x81B4, //CJK UNIFIED IDEOGRAPH - 0xEAF1: 0x81B2, //CJK UNIFIED IDEOGRAPH - 0xEAF2: 0x81B7, //CJK UNIFIED IDEOGRAPH - 0xEAF3: 0x81A7, //CJK UNIFIED IDEOGRAPH - 0xEAF4: 0x81F2, //CJK UNIFIED IDEOGRAPH - 0xEAF5: 0x8255, //CJK UNIFIED IDEOGRAPH - 0xEAF6: 0x8256, //CJK UNIFIED IDEOGRAPH - 0xEAF7: 0x8257, //CJK UNIFIED IDEOGRAPH - 0xEAF8: 0x8556, //CJK UNIFIED IDEOGRAPH - 0xEAF9: 0x8545, //CJK UNIFIED IDEOGRAPH - 0xEAFA: 0x856B, //CJK UNIFIED IDEOGRAPH - 0xEAFB: 0x854D, //CJK UNIFIED IDEOGRAPH - 0xEAFC: 0x8553, //CJK UNIFIED IDEOGRAPH - 0xEAFD: 0x8561, //CJK UNIFIED IDEOGRAPH - 0xEAFE: 0x8558, //CJK UNIFIED IDEOGRAPH - 0xEB40: 0x8540, //CJK UNIFIED IDEOGRAPH - 0xEB41: 0x8546, //CJK UNIFIED IDEOGRAPH - 0xEB42: 0x8564, //CJK UNIFIED IDEOGRAPH - 0xEB43: 0x8541, //CJK UNIFIED IDEOGRAPH - 0xEB44: 0x8562, //CJK UNIFIED IDEOGRAPH - 0xEB45: 0x8544, //CJK UNIFIED IDEOGRAPH - 0xEB46: 0x8551, //CJK UNIFIED IDEOGRAPH - 0xEB47: 0x8547, //CJK UNIFIED IDEOGRAPH - 0xEB48: 0x8563, //CJK UNIFIED IDEOGRAPH - 0xEB49: 0x853E, //CJK UNIFIED IDEOGRAPH - 0xEB4A: 0x855B, //CJK UNIFIED IDEOGRAPH - 0xEB4B: 0x8571, //CJK UNIFIED IDEOGRAPH - 0xEB4C: 0x854E, //CJK UNIFIED IDEOGRAPH - 0xEB4D: 0x856E, //CJK UNIFIED IDEOGRAPH - 0xEB4E: 0x8575, //CJK UNIFIED IDEOGRAPH - 0xEB4F: 0x8555, //CJK UNIFIED IDEOGRAPH - 0xEB50: 0x8567, //CJK UNIFIED IDEOGRAPH - 0xEB51: 0x8560, //CJK UNIFIED IDEOGRAPH - 0xEB52: 0x858C, //CJK UNIFIED IDEOGRAPH - 0xEB53: 0x8566, //CJK UNIFIED IDEOGRAPH - 0xEB54: 0x855D, //CJK UNIFIED IDEOGRAPH - 0xEB55: 0x8554, //CJK UNIFIED IDEOGRAPH - 0xEB56: 0x8565, //CJK UNIFIED IDEOGRAPH - 0xEB57: 0x856C, //CJK UNIFIED IDEOGRAPH - 0xEB58: 0x8663, //CJK UNIFIED IDEOGRAPH - 0xEB59: 0x8665, //CJK UNIFIED IDEOGRAPH - 0xEB5A: 0x8664, //CJK UNIFIED IDEOGRAPH - 0xEB5B: 0x879B, //CJK UNIFIED IDEOGRAPH - 0xEB5C: 0x878F, //CJK UNIFIED IDEOGRAPH - 0xEB5D: 0x8797, //CJK UNIFIED IDEOGRAPH - 0xEB5E: 0x8793, //CJK UNIFIED IDEOGRAPH - 0xEB5F: 0x8792, //CJK UNIFIED IDEOGRAPH - 0xEB60: 0x8788, //CJK UNIFIED IDEOGRAPH - 0xEB61: 0x8781, //CJK UNIFIED IDEOGRAPH - 0xEB62: 0x8796, //CJK UNIFIED IDEOGRAPH - 0xEB63: 0x8798, //CJK UNIFIED IDEOGRAPH - 0xEB64: 0x8779, //CJK UNIFIED IDEOGRAPH - 0xEB65: 0x8787, //CJK UNIFIED IDEOGRAPH - 0xEB66: 0x87A3, //CJK UNIFIED IDEOGRAPH - 0xEB67: 0x8785, //CJK UNIFIED IDEOGRAPH - 0xEB68: 0x8790, //CJK UNIFIED IDEOGRAPH - 0xEB69: 0x8791, //CJK UNIFIED IDEOGRAPH - 0xEB6A: 0x879D, //CJK UNIFIED IDEOGRAPH - 0xEB6B: 0x8784, //CJK UNIFIED IDEOGRAPH - 0xEB6C: 0x8794, //CJK UNIFIED IDEOGRAPH - 0xEB6D: 0x879C, //CJK UNIFIED IDEOGRAPH - 0xEB6E: 0x879A, //CJK UNIFIED IDEOGRAPH - 0xEB6F: 0x8789, //CJK UNIFIED IDEOGRAPH - 0xEB70: 0x891E, //CJK UNIFIED IDEOGRAPH - 0xEB71: 0x8926, //CJK UNIFIED IDEOGRAPH - 0xEB72: 0x8930, //CJK UNIFIED IDEOGRAPH - 0xEB73: 0x892D, //CJK UNIFIED IDEOGRAPH - 0xEB74: 0x892E, //CJK UNIFIED IDEOGRAPH - 0xEB75: 0x8927, //CJK UNIFIED IDEOGRAPH - 0xEB76: 0x8931, //CJK UNIFIED IDEOGRAPH - 0xEB77: 0x8922, //CJK UNIFIED IDEOGRAPH - 0xEB78: 0x8929, //CJK UNIFIED IDEOGRAPH - 0xEB79: 0x8923, //CJK UNIFIED IDEOGRAPH - 0xEB7A: 0x892F, //CJK UNIFIED IDEOGRAPH - 0xEB7B: 0x892C, //CJK UNIFIED IDEOGRAPH - 0xEB7C: 0x891F, //CJK UNIFIED IDEOGRAPH - 0xEB7D: 0x89F1, //CJK UNIFIED IDEOGRAPH - 0xEB7E: 0x8AE0, //CJK UNIFIED IDEOGRAPH - 0xEBA1: 0x8AE2, //CJK UNIFIED IDEOGRAPH - 0xEBA2: 0x8AF2, //CJK UNIFIED IDEOGRAPH - 0xEBA3: 0x8AF4, //CJK UNIFIED IDEOGRAPH - 0xEBA4: 0x8AF5, //CJK UNIFIED IDEOGRAPH - 0xEBA5: 0x8ADD, //CJK UNIFIED IDEOGRAPH - 0xEBA6: 0x8B14, //CJK UNIFIED IDEOGRAPH - 0xEBA7: 0x8AE4, //CJK UNIFIED IDEOGRAPH - 0xEBA8: 0x8ADF, //CJK UNIFIED IDEOGRAPH - 0xEBA9: 0x8AF0, //CJK UNIFIED IDEOGRAPH - 0xEBAA: 0x8AC8, //CJK UNIFIED IDEOGRAPH - 0xEBAB: 0x8ADE, //CJK UNIFIED IDEOGRAPH - 0xEBAC: 0x8AE1, //CJK UNIFIED IDEOGRAPH - 0xEBAD: 0x8AE8, //CJK UNIFIED IDEOGRAPH - 0xEBAE: 0x8AFF, //CJK UNIFIED IDEOGRAPH - 0xEBAF: 0x8AEF, //CJK UNIFIED IDEOGRAPH - 0xEBB0: 0x8AFB, //CJK UNIFIED IDEOGRAPH - 0xEBB1: 0x8C91, //CJK UNIFIED IDEOGRAPH - 0xEBB2: 0x8C92, //CJK UNIFIED IDEOGRAPH - 0xEBB3: 0x8C90, //CJK UNIFIED IDEOGRAPH - 0xEBB4: 0x8CF5, //CJK UNIFIED IDEOGRAPH - 0xEBB5: 0x8CEE, //CJK UNIFIED IDEOGRAPH - 0xEBB6: 0x8CF1, //CJK UNIFIED IDEOGRAPH - 0xEBB7: 0x8CF0, //CJK UNIFIED IDEOGRAPH - 0xEBB8: 0x8CF3, //CJK UNIFIED IDEOGRAPH - 0xEBB9: 0x8D6C, //CJK UNIFIED IDEOGRAPH - 0xEBBA: 0x8D6E, //CJK UNIFIED IDEOGRAPH - 0xEBBB: 0x8DA5, //CJK UNIFIED IDEOGRAPH - 0xEBBC: 0x8DA7, //CJK UNIFIED IDEOGRAPH - 0xEBBD: 0x8E33, //CJK UNIFIED IDEOGRAPH - 0xEBBE: 0x8E3E, //CJK UNIFIED IDEOGRAPH - 0xEBBF: 0x8E38, //CJK UNIFIED IDEOGRAPH - 0xEBC0: 0x8E40, //CJK UNIFIED IDEOGRAPH - 0xEBC1: 0x8E45, //CJK UNIFIED IDEOGRAPH - 0xEBC2: 0x8E36, //CJK UNIFIED IDEOGRAPH - 0xEBC3: 0x8E3C, //CJK UNIFIED IDEOGRAPH - 0xEBC4: 0x8E3D, //CJK UNIFIED IDEOGRAPH - 0xEBC5: 0x8E41, //CJK UNIFIED IDEOGRAPH - 0xEBC6: 0x8E30, //CJK UNIFIED IDEOGRAPH - 0xEBC7: 0x8E3F, //CJK UNIFIED IDEOGRAPH - 0xEBC8: 0x8EBD, //CJK UNIFIED IDEOGRAPH - 0xEBC9: 0x8F36, //CJK UNIFIED IDEOGRAPH - 0xEBCA: 0x8F2E, //CJK UNIFIED IDEOGRAPH - 0xEBCB: 0x8F35, //CJK UNIFIED IDEOGRAPH - 0xEBCC: 0x8F32, //CJK UNIFIED IDEOGRAPH - 0xEBCD: 0x8F39, //CJK UNIFIED IDEOGRAPH - 0xEBCE: 0x8F37, //CJK UNIFIED IDEOGRAPH - 0xEBCF: 0x8F34, //CJK UNIFIED IDEOGRAPH - 0xEBD0: 0x9076, //CJK UNIFIED IDEOGRAPH - 0xEBD1: 0x9079, //CJK UNIFIED IDEOGRAPH - 0xEBD2: 0x907B, //CJK UNIFIED IDEOGRAPH - 0xEBD3: 0x9086, //CJK UNIFIED IDEOGRAPH - 0xEBD4: 0x90FA, //CJK UNIFIED IDEOGRAPH - 0xEBD5: 0x9133, //CJK UNIFIED IDEOGRAPH - 0xEBD6: 0x9135, //CJK UNIFIED IDEOGRAPH - 0xEBD7: 0x9136, //CJK UNIFIED IDEOGRAPH - 0xEBD8: 0x9193, //CJK UNIFIED IDEOGRAPH - 0xEBD9: 0x9190, //CJK UNIFIED IDEOGRAPH - 0xEBDA: 0x9191, //CJK UNIFIED IDEOGRAPH - 0xEBDB: 0x918D, //CJK UNIFIED IDEOGRAPH - 0xEBDC: 0x918F, //CJK UNIFIED IDEOGRAPH - 0xEBDD: 0x9327, //CJK UNIFIED IDEOGRAPH - 0xEBDE: 0x931E, //CJK UNIFIED IDEOGRAPH - 0xEBDF: 0x9308, //CJK UNIFIED IDEOGRAPH - 0xEBE0: 0x931F, //CJK UNIFIED IDEOGRAPH - 0xEBE1: 0x9306, //CJK UNIFIED IDEOGRAPH - 0xEBE2: 0x930F, //CJK UNIFIED IDEOGRAPH - 0xEBE3: 0x937A, //CJK UNIFIED IDEOGRAPH - 0xEBE4: 0x9338, //CJK UNIFIED IDEOGRAPH - 0xEBE5: 0x933C, //CJK UNIFIED IDEOGRAPH - 0xEBE6: 0x931B, //CJK UNIFIED IDEOGRAPH - 0xEBE7: 0x9323, //CJK UNIFIED IDEOGRAPH - 0xEBE8: 0x9312, //CJK UNIFIED IDEOGRAPH - 0xEBE9: 0x9301, //CJK UNIFIED IDEOGRAPH - 0xEBEA: 0x9346, //CJK UNIFIED IDEOGRAPH - 0xEBEB: 0x932D, //CJK UNIFIED IDEOGRAPH - 0xEBEC: 0x930E, //CJK UNIFIED IDEOGRAPH - 0xEBED: 0x930D, //CJK UNIFIED IDEOGRAPH - 0xEBEE: 0x92CB, //CJK UNIFIED IDEOGRAPH - 0xEBEF: 0x931D, //CJK UNIFIED IDEOGRAPH - 0xEBF0: 0x92FA, //CJK UNIFIED IDEOGRAPH - 0xEBF1: 0x9325, //CJK UNIFIED IDEOGRAPH - 0xEBF2: 0x9313, //CJK UNIFIED IDEOGRAPH - 0xEBF3: 0x92F9, //CJK UNIFIED IDEOGRAPH - 0xEBF4: 0x92F7, //CJK UNIFIED IDEOGRAPH - 0xEBF5: 0x9334, //CJK UNIFIED IDEOGRAPH - 0xEBF6: 0x9302, //CJK UNIFIED IDEOGRAPH - 0xEBF7: 0x9324, //CJK UNIFIED IDEOGRAPH - 0xEBF8: 0x92FF, //CJK UNIFIED IDEOGRAPH - 0xEBF9: 0x9329, //CJK UNIFIED IDEOGRAPH - 0xEBFA: 0x9339, //CJK UNIFIED IDEOGRAPH - 0xEBFB: 0x9335, //CJK UNIFIED IDEOGRAPH - 0xEBFC: 0x932A, //CJK UNIFIED IDEOGRAPH - 0xEBFD: 0x9314, //CJK UNIFIED IDEOGRAPH - 0xEBFE: 0x930C, //CJK UNIFIED IDEOGRAPH - 0xEC40: 0x930B, //CJK UNIFIED IDEOGRAPH - 0xEC41: 0x92FE, //CJK UNIFIED IDEOGRAPH - 0xEC42: 0x9309, //CJK UNIFIED IDEOGRAPH - 0xEC43: 0x9300, //CJK UNIFIED IDEOGRAPH - 0xEC44: 0x92FB, //CJK UNIFIED IDEOGRAPH - 0xEC45: 0x9316, //CJK UNIFIED IDEOGRAPH - 0xEC46: 0x95BC, //CJK UNIFIED IDEOGRAPH - 0xEC47: 0x95CD, //CJK UNIFIED IDEOGRAPH - 0xEC48: 0x95BE, //CJK UNIFIED IDEOGRAPH - 0xEC49: 0x95B9, //CJK UNIFIED IDEOGRAPH - 0xEC4A: 0x95BA, //CJK UNIFIED IDEOGRAPH - 0xEC4B: 0x95B6, //CJK UNIFIED IDEOGRAPH - 0xEC4C: 0x95BF, //CJK UNIFIED IDEOGRAPH - 0xEC4D: 0x95B5, //CJK UNIFIED IDEOGRAPH - 0xEC4E: 0x95BD, //CJK UNIFIED IDEOGRAPH - 0xEC4F: 0x96A9, //CJK UNIFIED IDEOGRAPH - 0xEC50: 0x96D4, //CJK UNIFIED IDEOGRAPH - 0xEC51: 0x970B, //CJK UNIFIED IDEOGRAPH - 0xEC52: 0x9712, //CJK UNIFIED IDEOGRAPH - 0xEC53: 0x9710, //CJK UNIFIED IDEOGRAPH - 0xEC54: 0x9799, //CJK UNIFIED IDEOGRAPH - 0xEC55: 0x9797, //CJK UNIFIED IDEOGRAPH - 0xEC56: 0x9794, //CJK UNIFIED IDEOGRAPH - 0xEC57: 0x97F0, //CJK UNIFIED IDEOGRAPH - 0xEC58: 0x97F8, //CJK UNIFIED IDEOGRAPH - 0xEC59: 0x9835, //CJK UNIFIED IDEOGRAPH - 0xEC5A: 0x982F, //CJK UNIFIED IDEOGRAPH - 0xEC5B: 0x9832, //CJK UNIFIED IDEOGRAPH - 0xEC5C: 0x9924, //CJK UNIFIED IDEOGRAPH - 0xEC5D: 0x991F, //CJK UNIFIED IDEOGRAPH - 0xEC5E: 0x9927, //CJK UNIFIED IDEOGRAPH - 0xEC5F: 0x9929, //CJK UNIFIED IDEOGRAPH - 0xEC60: 0x999E, //CJK UNIFIED IDEOGRAPH - 0xEC61: 0x99EE, //CJK UNIFIED IDEOGRAPH - 0xEC62: 0x99EC, //CJK UNIFIED IDEOGRAPH - 0xEC63: 0x99E5, //CJK UNIFIED IDEOGRAPH - 0xEC64: 0x99E4, //CJK UNIFIED IDEOGRAPH - 0xEC65: 0x99F0, //CJK UNIFIED IDEOGRAPH - 0xEC66: 0x99E3, //CJK UNIFIED IDEOGRAPH - 0xEC67: 0x99EA, //CJK UNIFIED IDEOGRAPH - 0xEC68: 0x99E9, //CJK UNIFIED IDEOGRAPH - 0xEC69: 0x99E7, //CJK UNIFIED IDEOGRAPH - 0xEC6A: 0x9AB9, //CJK UNIFIED IDEOGRAPH - 0xEC6B: 0x9ABF, //CJK UNIFIED IDEOGRAPH - 0xEC6C: 0x9AB4, //CJK UNIFIED IDEOGRAPH - 0xEC6D: 0x9ABB, //CJK UNIFIED IDEOGRAPH - 0xEC6E: 0x9AF6, //CJK UNIFIED IDEOGRAPH - 0xEC6F: 0x9AFA, //CJK UNIFIED IDEOGRAPH - 0xEC70: 0x9AF9, //CJK UNIFIED IDEOGRAPH - 0xEC71: 0x9AF7, //CJK UNIFIED IDEOGRAPH - 0xEC72: 0x9B33, //CJK UNIFIED IDEOGRAPH - 0xEC73: 0x9B80, //CJK UNIFIED IDEOGRAPH - 0xEC74: 0x9B85, //CJK UNIFIED IDEOGRAPH - 0xEC75: 0x9B87, //CJK UNIFIED IDEOGRAPH - 0xEC76: 0x9B7C, //CJK UNIFIED IDEOGRAPH - 0xEC77: 0x9B7E, //CJK UNIFIED IDEOGRAPH - 0xEC78: 0x9B7B, //CJK UNIFIED IDEOGRAPH - 0xEC79: 0x9B82, //CJK UNIFIED IDEOGRAPH - 0xEC7A: 0x9B93, //CJK UNIFIED IDEOGRAPH - 0xEC7B: 0x9B92, //CJK UNIFIED IDEOGRAPH - 0xEC7C: 0x9B90, //CJK UNIFIED IDEOGRAPH - 0xEC7D: 0x9B7A, //CJK UNIFIED IDEOGRAPH - 0xEC7E: 0x9B95, //CJK UNIFIED IDEOGRAPH - 0xECA1: 0x9B7D, //CJK UNIFIED IDEOGRAPH - 0xECA2: 0x9B88, //CJK UNIFIED IDEOGRAPH - 0xECA3: 0x9D25, //CJK UNIFIED IDEOGRAPH - 0xECA4: 0x9D17, //CJK UNIFIED IDEOGRAPH - 0xECA5: 0x9D20, //CJK UNIFIED IDEOGRAPH - 0xECA6: 0x9D1E, //CJK UNIFIED IDEOGRAPH - 0xECA7: 0x9D14, //CJK UNIFIED IDEOGRAPH - 0xECA8: 0x9D29, //CJK UNIFIED IDEOGRAPH - 0xECA9: 0x9D1D, //CJK UNIFIED IDEOGRAPH - 0xECAA: 0x9D18, //CJK UNIFIED IDEOGRAPH - 0xECAB: 0x9D22, //CJK UNIFIED IDEOGRAPH - 0xECAC: 0x9D10, //CJK UNIFIED IDEOGRAPH - 0xECAD: 0x9D19, //CJK UNIFIED IDEOGRAPH - 0xECAE: 0x9D1F, //CJK UNIFIED IDEOGRAPH - 0xECAF: 0x9E88, //CJK UNIFIED IDEOGRAPH - 0xECB0: 0x9E86, //CJK UNIFIED IDEOGRAPH - 0xECB1: 0x9E87, //CJK UNIFIED IDEOGRAPH - 0xECB2: 0x9EAE, //CJK UNIFIED IDEOGRAPH - 0xECB3: 0x9EAD, //CJK UNIFIED IDEOGRAPH - 0xECB4: 0x9ED5, //CJK UNIFIED IDEOGRAPH - 0xECB5: 0x9ED6, //CJK UNIFIED IDEOGRAPH - 0xECB6: 0x9EFA, //CJK UNIFIED IDEOGRAPH - 0xECB7: 0x9F12, //CJK UNIFIED IDEOGRAPH - 0xECB8: 0x9F3D, //CJK UNIFIED IDEOGRAPH - 0xECB9: 0x5126, //CJK UNIFIED IDEOGRAPH - 0xECBA: 0x5125, //CJK UNIFIED IDEOGRAPH - 0xECBB: 0x5122, //CJK UNIFIED IDEOGRAPH - 0xECBC: 0x5124, //CJK UNIFIED IDEOGRAPH - 0xECBD: 0x5120, //CJK UNIFIED IDEOGRAPH - 0xECBE: 0x5129, //CJK UNIFIED IDEOGRAPH - 0xECBF: 0x52F4, //CJK UNIFIED IDEOGRAPH - 0xECC0: 0x5693, //CJK UNIFIED IDEOGRAPH - 0xECC1: 0x568C, //CJK UNIFIED IDEOGRAPH - 0xECC2: 0x568D, //CJK UNIFIED IDEOGRAPH - 0xECC3: 0x5686, //CJK UNIFIED IDEOGRAPH - 0xECC4: 0x5684, //CJK UNIFIED IDEOGRAPH - 0xECC5: 0x5683, //CJK UNIFIED IDEOGRAPH - 0xECC6: 0x567E, //CJK UNIFIED IDEOGRAPH - 0xECC7: 0x5682, //CJK UNIFIED IDEOGRAPH - 0xECC8: 0x567F, //CJK UNIFIED IDEOGRAPH - 0xECC9: 0x5681, //CJK UNIFIED IDEOGRAPH - 0xECCA: 0x58D6, //CJK UNIFIED IDEOGRAPH - 0xECCB: 0x58D4, //CJK UNIFIED IDEOGRAPH - 0xECCC: 0x58CF, //CJK UNIFIED IDEOGRAPH - 0xECCD: 0x58D2, //CJK UNIFIED IDEOGRAPH - 0xECCE: 0x5B2D, //CJK UNIFIED IDEOGRAPH - 0xECCF: 0x5B25, //CJK UNIFIED IDEOGRAPH - 0xECD0: 0x5B32, //CJK UNIFIED IDEOGRAPH - 0xECD1: 0x5B23, //CJK UNIFIED IDEOGRAPH - 0xECD2: 0x5B2C, //CJK UNIFIED IDEOGRAPH - 0xECD3: 0x5B27, //CJK UNIFIED IDEOGRAPH - 0xECD4: 0x5B26, //CJK UNIFIED IDEOGRAPH - 0xECD5: 0x5B2F, //CJK UNIFIED IDEOGRAPH - 0xECD6: 0x5B2E, //CJK UNIFIED IDEOGRAPH - 0xECD7: 0x5B7B, //CJK UNIFIED IDEOGRAPH - 0xECD8: 0x5BF1, //CJK UNIFIED IDEOGRAPH - 0xECD9: 0x5BF2, //CJK UNIFIED IDEOGRAPH - 0xECDA: 0x5DB7, //CJK UNIFIED IDEOGRAPH - 0xECDB: 0x5E6C, //CJK UNIFIED IDEOGRAPH - 0xECDC: 0x5E6A, //CJK UNIFIED IDEOGRAPH - 0xECDD: 0x5FBE, //CJK UNIFIED IDEOGRAPH - 0xECDE: 0x5FBB, //CJK UNIFIED IDEOGRAPH - 0xECDF: 0x61C3, //CJK UNIFIED IDEOGRAPH - 0xECE0: 0x61B5, //CJK UNIFIED IDEOGRAPH - 0xECE1: 0x61BC, //CJK UNIFIED IDEOGRAPH - 0xECE2: 0x61E7, //CJK UNIFIED IDEOGRAPH - 0xECE3: 0x61E0, //CJK UNIFIED IDEOGRAPH - 0xECE4: 0x61E5, //CJK UNIFIED IDEOGRAPH - 0xECE5: 0x61E4, //CJK UNIFIED IDEOGRAPH - 0xECE6: 0x61E8, //CJK UNIFIED IDEOGRAPH - 0xECE7: 0x61DE, //CJK UNIFIED IDEOGRAPH - 0xECE8: 0x64EF, //CJK UNIFIED IDEOGRAPH - 0xECE9: 0x64E9, //CJK UNIFIED IDEOGRAPH - 0xECEA: 0x64E3, //CJK UNIFIED IDEOGRAPH - 0xECEB: 0x64EB, //CJK UNIFIED IDEOGRAPH - 0xECEC: 0x64E4, //CJK UNIFIED IDEOGRAPH - 0xECED: 0x64E8, //CJK UNIFIED IDEOGRAPH - 0xECEE: 0x6581, //CJK UNIFIED IDEOGRAPH - 0xECEF: 0x6580, //CJK UNIFIED IDEOGRAPH - 0xECF0: 0x65B6, //CJK UNIFIED IDEOGRAPH - 0xECF1: 0x65DA, //CJK UNIFIED IDEOGRAPH - 0xECF2: 0x66D2, //CJK UNIFIED IDEOGRAPH - 0xECF3: 0x6A8D, //CJK UNIFIED IDEOGRAPH - 0xECF4: 0x6A96, //CJK UNIFIED IDEOGRAPH - 0xECF5: 0x6A81, //CJK UNIFIED IDEOGRAPH - 0xECF6: 0x6AA5, //CJK UNIFIED IDEOGRAPH - 0xECF7: 0x6A89, //CJK UNIFIED IDEOGRAPH - 0xECF8: 0x6A9F, //CJK UNIFIED IDEOGRAPH - 0xECF9: 0x6A9B, //CJK UNIFIED IDEOGRAPH - 0xECFA: 0x6AA1, //CJK UNIFIED IDEOGRAPH - 0xECFB: 0x6A9E, //CJK UNIFIED IDEOGRAPH - 0xECFC: 0x6A87, //CJK UNIFIED IDEOGRAPH - 0xECFD: 0x6A93, //CJK UNIFIED IDEOGRAPH - 0xECFE: 0x6A8E, //CJK UNIFIED IDEOGRAPH - 0xED40: 0x6A95, //CJK UNIFIED IDEOGRAPH - 0xED41: 0x6A83, //CJK UNIFIED IDEOGRAPH - 0xED42: 0x6AA8, //CJK UNIFIED IDEOGRAPH - 0xED43: 0x6AA4, //CJK UNIFIED IDEOGRAPH - 0xED44: 0x6A91, //CJK UNIFIED IDEOGRAPH - 0xED45: 0x6A7F, //CJK UNIFIED IDEOGRAPH - 0xED46: 0x6AA6, //CJK UNIFIED IDEOGRAPH - 0xED47: 0x6A9A, //CJK UNIFIED IDEOGRAPH - 0xED48: 0x6A85, //CJK UNIFIED IDEOGRAPH - 0xED49: 0x6A8C, //CJK UNIFIED IDEOGRAPH - 0xED4A: 0x6A92, //CJK UNIFIED IDEOGRAPH - 0xED4B: 0x6B5B, //CJK UNIFIED IDEOGRAPH - 0xED4C: 0x6BAD, //CJK UNIFIED IDEOGRAPH - 0xED4D: 0x6C09, //CJK UNIFIED IDEOGRAPH - 0xED4E: 0x6FCC, //CJK UNIFIED IDEOGRAPH - 0xED4F: 0x6FA9, //CJK UNIFIED IDEOGRAPH - 0xED50: 0x6FF4, //CJK UNIFIED IDEOGRAPH - 0xED51: 0x6FD4, //CJK UNIFIED IDEOGRAPH - 0xED52: 0x6FE3, //CJK UNIFIED IDEOGRAPH - 0xED53: 0x6FDC, //CJK UNIFIED IDEOGRAPH - 0xED54: 0x6FED, //CJK UNIFIED IDEOGRAPH - 0xED55: 0x6FE7, //CJK UNIFIED IDEOGRAPH - 0xED56: 0x6FE6, //CJK UNIFIED IDEOGRAPH - 0xED57: 0x6FDE, //CJK UNIFIED IDEOGRAPH - 0xED58: 0x6FF2, //CJK UNIFIED IDEOGRAPH - 0xED59: 0x6FDD, //CJK UNIFIED IDEOGRAPH - 0xED5A: 0x6FE2, //CJK UNIFIED IDEOGRAPH - 0xED5B: 0x6FE8, //CJK UNIFIED IDEOGRAPH - 0xED5C: 0x71E1, //CJK UNIFIED IDEOGRAPH - 0xED5D: 0x71F1, //CJK UNIFIED IDEOGRAPH - 0xED5E: 0x71E8, //CJK UNIFIED IDEOGRAPH - 0xED5F: 0x71F2, //CJK UNIFIED IDEOGRAPH - 0xED60: 0x71E4, //CJK UNIFIED IDEOGRAPH - 0xED61: 0x71F0, //CJK UNIFIED IDEOGRAPH - 0xED62: 0x71E2, //CJK UNIFIED IDEOGRAPH - 0xED63: 0x7373, //CJK UNIFIED IDEOGRAPH - 0xED64: 0x736E, //CJK UNIFIED IDEOGRAPH - 0xED65: 0x736F, //CJK UNIFIED IDEOGRAPH - 0xED66: 0x7497, //CJK UNIFIED IDEOGRAPH - 0xED67: 0x74B2, //CJK UNIFIED IDEOGRAPH - 0xED68: 0x74AB, //CJK UNIFIED IDEOGRAPH - 0xED69: 0x7490, //CJK UNIFIED IDEOGRAPH - 0xED6A: 0x74AA, //CJK UNIFIED IDEOGRAPH - 0xED6B: 0x74AD, //CJK UNIFIED IDEOGRAPH - 0xED6C: 0x74B1, //CJK UNIFIED IDEOGRAPH - 0xED6D: 0x74A5, //CJK UNIFIED IDEOGRAPH - 0xED6E: 0x74AF, //CJK UNIFIED IDEOGRAPH - 0xED6F: 0x7510, //CJK UNIFIED IDEOGRAPH - 0xED70: 0x7511, //CJK UNIFIED IDEOGRAPH - 0xED71: 0x7512, //CJK UNIFIED IDEOGRAPH - 0xED72: 0x750F, //CJK UNIFIED IDEOGRAPH - 0xED73: 0x7584, //CJK UNIFIED IDEOGRAPH - 0xED74: 0x7643, //CJK UNIFIED IDEOGRAPH - 0xED75: 0x7648, //CJK UNIFIED IDEOGRAPH - 0xED76: 0x7649, //CJK UNIFIED IDEOGRAPH - 0xED77: 0x7647, //CJK UNIFIED IDEOGRAPH - 0xED78: 0x76A4, //CJK UNIFIED IDEOGRAPH - 0xED79: 0x76E9, //CJK UNIFIED IDEOGRAPH - 0xED7A: 0x77B5, //CJK UNIFIED IDEOGRAPH - 0xED7B: 0x77AB, //CJK UNIFIED IDEOGRAPH - 0xED7C: 0x77B2, //CJK UNIFIED IDEOGRAPH - 0xED7D: 0x77B7, //CJK UNIFIED IDEOGRAPH - 0xED7E: 0x77B6, //CJK UNIFIED IDEOGRAPH - 0xEDA1: 0x77B4, //CJK UNIFIED IDEOGRAPH - 0xEDA2: 0x77B1, //CJK UNIFIED IDEOGRAPH - 0xEDA3: 0x77A8, //CJK UNIFIED IDEOGRAPH - 0xEDA4: 0x77F0, //CJK UNIFIED IDEOGRAPH - 0xEDA5: 0x78F3, //CJK UNIFIED IDEOGRAPH - 0xEDA6: 0x78FD, //CJK UNIFIED IDEOGRAPH - 0xEDA7: 0x7902, //CJK UNIFIED IDEOGRAPH - 0xEDA8: 0x78FB, //CJK UNIFIED IDEOGRAPH - 0xEDA9: 0x78FC, //CJK UNIFIED IDEOGRAPH - 0xEDAA: 0x78F2, //CJK UNIFIED IDEOGRAPH - 0xEDAB: 0x7905, //CJK UNIFIED IDEOGRAPH - 0xEDAC: 0x78F9, //CJK UNIFIED IDEOGRAPH - 0xEDAD: 0x78FE, //CJK UNIFIED IDEOGRAPH - 0xEDAE: 0x7904, //CJK UNIFIED IDEOGRAPH - 0xEDAF: 0x79AB, //CJK UNIFIED IDEOGRAPH - 0xEDB0: 0x79A8, //CJK UNIFIED IDEOGRAPH - 0xEDB1: 0x7A5C, //CJK UNIFIED IDEOGRAPH - 0xEDB2: 0x7A5B, //CJK UNIFIED IDEOGRAPH - 0xEDB3: 0x7A56, //CJK UNIFIED IDEOGRAPH - 0xEDB4: 0x7A58, //CJK UNIFIED IDEOGRAPH - 0xEDB5: 0x7A54, //CJK UNIFIED IDEOGRAPH - 0xEDB6: 0x7A5A, //CJK UNIFIED IDEOGRAPH - 0xEDB7: 0x7ABE, //CJK UNIFIED IDEOGRAPH - 0xEDB8: 0x7AC0, //CJK UNIFIED IDEOGRAPH - 0xEDB9: 0x7AC1, //CJK UNIFIED IDEOGRAPH - 0xEDBA: 0x7C05, //CJK UNIFIED IDEOGRAPH - 0xEDBB: 0x7C0F, //CJK UNIFIED IDEOGRAPH - 0xEDBC: 0x7BF2, //CJK UNIFIED IDEOGRAPH - 0xEDBD: 0x7C00, //CJK UNIFIED IDEOGRAPH - 0xEDBE: 0x7BFF, //CJK UNIFIED IDEOGRAPH - 0xEDBF: 0x7BFB, //CJK UNIFIED IDEOGRAPH - 0xEDC0: 0x7C0E, //CJK UNIFIED IDEOGRAPH - 0xEDC1: 0x7BF4, //CJK UNIFIED IDEOGRAPH - 0xEDC2: 0x7C0B, //CJK UNIFIED IDEOGRAPH - 0xEDC3: 0x7BF3, //CJK UNIFIED IDEOGRAPH - 0xEDC4: 0x7C02, //CJK UNIFIED IDEOGRAPH - 0xEDC5: 0x7C09, //CJK UNIFIED IDEOGRAPH - 0xEDC6: 0x7C03, //CJK UNIFIED IDEOGRAPH - 0xEDC7: 0x7C01, //CJK UNIFIED IDEOGRAPH - 0xEDC8: 0x7BF8, //CJK UNIFIED IDEOGRAPH - 0xEDC9: 0x7BFD, //CJK UNIFIED IDEOGRAPH - 0xEDCA: 0x7C06, //CJK UNIFIED IDEOGRAPH - 0xEDCB: 0x7BF0, //CJK UNIFIED IDEOGRAPH - 0xEDCC: 0x7BF1, //CJK UNIFIED IDEOGRAPH - 0xEDCD: 0x7C10, //CJK UNIFIED IDEOGRAPH - 0xEDCE: 0x7C0A, //CJK UNIFIED IDEOGRAPH - 0xEDCF: 0x7CE8, //CJK UNIFIED IDEOGRAPH - 0xEDD0: 0x7E2D, //CJK UNIFIED IDEOGRAPH - 0xEDD1: 0x7E3C, //CJK UNIFIED IDEOGRAPH - 0xEDD2: 0x7E42, //CJK UNIFIED IDEOGRAPH - 0xEDD3: 0x7E33, //CJK UNIFIED IDEOGRAPH - 0xEDD4: 0x9848, //CJK UNIFIED IDEOGRAPH - 0xEDD5: 0x7E38, //CJK UNIFIED IDEOGRAPH - 0xEDD6: 0x7E2A, //CJK UNIFIED IDEOGRAPH - 0xEDD7: 0x7E49, //CJK UNIFIED IDEOGRAPH - 0xEDD8: 0x7E40, //CJK UNIFIED IDEOGRAPH - 0xEDD9: 0x7E47, //CJK UNIFIED IDEOGRAPH - 0xEDDA: 0x7E29, //CJK UNIFIED IDEOGRAPH - 0xEDDB: 0x7E4C, //CJK UNIFIED IDEOGRAPH - 0xEDDC: 0x7E30, //CJK UNIFIED IDEOGRAPH - 0xEDDD: 0x7E3B, //CJK UNIFIED IDEOGRAPH - 0xEDDE: 0x7E36, //CJK UNIFIED IDEOGRAPH - 0xEDDF: 0x7E44, //CJK UNIFIED IDEOGRAPH - 0xEDE0: 0x7E3A, //CJK UNIFIED IDEOGRAPH - 0xEDE1: 0x7F45, //CJK UNIFIED IDEOGRAPH - 0xEDE2: 0x7F7F, //CJK UNIFIED IDEOGRAPH - 0xEDE3: 0x7F7E, //CJK UNIFIED IDEOGRAPH - 0xEDE4: 0x7F7D, //CJK UNIFIED IDEOGRAPH - 0xEDE5: 0x7FF4, //CJK UNIFIED IDEOGRAPH - 0xEDE6: 0x7FF2, //CJK UNIFIED IDEOGRAPH - 0xEDE7: 0x802C, //CJK UNIFIED IDEOGRAPH - 0xEDE8: 0x81BB, //CJK UNIFIED IDEOGRAPH - 0xEDE9: 0x81C4, //CJK UNIFIED IDEOGRAPH - 0xEDEA: 0x81CC, //CJK UNIFIED IDEOGRAPH - 0xEDEB: 0x81CA, //CJK UNIFIED IDEOGRAPH - 0xEDEC: 0x81C5, //CJK UNIFIED IDEOGRAPH - 0xEDED: 0x81C7, //CJK UNIFIED IDEOGRAPH - 0xEDEE: 0x81BC, //CJK UNIFIED IDEOGRAPH - 0xEDEF: 0x81E9, //CJK UNIFIED IDEOGRAPH - 0xEDF0: 0x825B, //CJK UNIFIED IDEOGRAPH - 0xEDF1: 0x825A, //CJK UNIFIED IDEOGRAPH - 0xEDF2: 0x825C, //CJK UNIFIED IDEOGRAPH - 0xEDF3: 0x8583, //CJK UNIFIED IDEOGRAPH - 0xEDF4: 0x8580, //CJK UNIFIED IDEOGRAPH - 0xEDF5: 0x858F, //CJK UNIFIED IDEOGRAPH - 0xEDF6: 0x85A7, //CJK UNIFIED IDEOGRAPH - 0xEDF7: 0x8595, //CJK UNIFIED IDEOGRAPH - 0xEDF8: 0x85A0, //CJK UNIFIED IDEOGRAPH - 0xEDF9: 0x858B, //CJK UNIFIED IDEOGRAPH - 0xEDFA: 0x85A3, //CJK UNIFIED IDEOGRAPH - 0xEDFB: 0x857B, //CJK UNIFIED IDEOGRAPH - 0xEDFC: 0x85A4, //CJK UNIFIED IDEOGRAPH - 0xEDFD: 0x859A, //CJK UNIFIED IDEOGRAPH - 0xEDFE: 0x859E, //CJK UNIFIED IDEOGRAPH - 0xEE40: 0x8577, //CJK UNIFIED IDEOGRAPH - 0xEE41: 0x857C, //CJK UNIFIED IDEOGRAPH - 0xEE42: 0x8589, //CJK UNIFIED IDEOGRAPH - 0xEE43: 0x85A1, //CJK UNIFIED IDEOGRAPH - 0xEE44: 0x857A, //CJK UNIFIED IDEOGRAPH - 0xEE45: 0x8578, //CJK UNIFIED IDEOGRAPH - 0xEE46: 0x8557, //CJK UNIFIED IDEOGRAPH - 0xEE47: 0x858E, //CJK UNIFIED IDEOGRAPH - 0xEE48: 0x8596, //CJK UNIFIED IDEOGRAPH - 0xEE49: 0x8586, //CJK UNIFIED IDEOGRAPH - 0xEE4A: 0x858D, //CJK UNIFIED IDEOGRAPH - 0xEE4B: 0x8599, //CJK UNIFIED IDEOGRAPH - 0xEE4C: 0x859D, //CJK UNIFIED IDEOGRAPH - 0xEE4D: 0x8581, //CJK UNIFIED IDEOGRAPH - 0xEE4E: 0x85A2, //CJK UNIFIED IDEOGRAPH - 0xEE4F: 0x8582, //CJK UNIFIED IDEOGRAPH - 0xEE50: 0x8588, //CJK UNIFIED IDEOGRAPH - 0xEE51: 0x8585, //CJK UNIFIED IDEOGRAPH - 0xEE52: 0x8579, //CJK UNIFIED IDEOGRAPH - 0xEE53: 0x8576, //CJK UNIFIED IDEOGRAPH - 0xEE54: 0x8598, //CJK UNIFIED IDEOGRAPH - 0xEE55: 0x8590, //CJK UNIFIED IDEOGRAPH - 0xEE56: 0x859F, //CJK UNIFIED IDEOGRAPH - 0xEE57: 0x8668, //CJK UNIFIED IDEOGRAPH - 0xEE58: 0x87BE, //CJK UNIFIED IDEOGRAPH - 0xEE59: 0x87AA, //CJK UNIFIED IDEOGRAPH - 0xEE5A: 0x87AD, //CJK UNIFIED IDEOGRAPH - 0xEE5B: 0x87C5, //CJK UNIFIED IDEOGRAPH - 0xEE5C: 0x87B0, //CJK UNIFIED IDEOGRAPH - 0xEE5D: 0x87AC, //CJK UNIFIED IDEOGRAPH - 0xEE5E: 0x87B9, //CJK UNIFIED IDEOGRAPH - 0xEE5F: 0x87B5, //CJK UNIFIED IDEOGRAPH - 0xEE60: 0x87BC, //CJK UNIFIED IDEOGRAPH - 0xEE61: 0x87AE, //CJK UNIFIED IDEOGRAPH - 0xEE62: 0x87C9, //CJK UNIFIED IDEOGRAPH - 0xEE63: 0x87C3, //CJK UNIFIED IDEOGRAPH - 0xEE64: 0x87C2, //CJK UNIFIED IDEOGRAPH - 0xEE65: 0x87CC, //CJK UNIFIED IDEOGRAPH - 0xEE66: 0x87B7, //CJK UNIFIED IDEOGRAPH - 0xEE67: 0x87AF, //CJK UNIFIED IDEOGRAPH - 0xEE68: 0x87C4, //CJK UNIFIED IDEOGRAPH - 0xEE69: 0x87CA, //CJK UNIFIED IDEOGRAPH - 0xEE6A: 0x87B4, //CJK UNIFIED IDEOGRAPH - 0xEE6B: 0x87B6, //CJK UNIFIED IDEOGRAPH - 0xEE6C: 0x87BF, //CJK UNIFIED IDEOGRAPH - 0xEE6D: 0x87B8, //CJK UNIFIED IDEOGRAPH - 0xEE6E: 0x87BD, //CJK UNIFIED IDEOGRAPH - 0xEE6F: 0x87DE, //CJK UNIFIED IDEOGRAPH - 0xEE70: 0x87B2, //CJK UNIFIED IDEOGRAPH - 0xEE71: 0x8935, //CJK UNIFIED IDEOGRAPH - 0xEE72: 0x8933, //CJK UNIFIED IDEOGRAPH - 0xEE73: 0x893C, //CJK UNIFIED IDEOGRAPH - 0xEE74: 0x893E, //CJK UNIFIED IDEOGRAPH - 0xEE75: 0x8941, //CJK UNIFIED IDEOGRAPH - 0xEE76: 0x8952, //CJK UNIFIED IDEOGRAPH - 0xEE77: 0x8937, //CJK UNIFIED IDEOGRAPH - 0xEE78: 0x8942, //CJK UNIFIED IDEOGRAPH - 0xEE79: 0x89AD, //CJK UNIFIED IDEOGRAPH - 0xEE7A: 0x89AF, //CJK UNIFIED IDEOGRAPH - 0xEE7B: 0x89AE, //CJK UNIFIED IDEOGRAPH - 0xEE7C: 0x89F2, //CJK UNIFIED IDEOGRAPH - 0xEE7D: 0x89F3, //CJK UNIFIED IDEOGRAPH - 0xEE7E: 0x8B1E, //CJK UNIFIED IDEOGRAPH - 0xEEA1: 0x8B18, //CJK UNIFIED IDEOGRAPH - 0xEEA2: 0x8B16, //CJK UNIFIED IDEOGRAPH - 0xEEA3: 0x8B11, //CJK UNIFIED IDEOGRAPH - 0xEEA4: 0x8B05, //CJK UNIFIED IDEOGRAPH - 0xEEA5: 0x8B0B, //CJK UNIFIED IDEOGRAPH - 0xEEA6: 0x8B22, //CJK UNIFIED IDEOGRAPH - 0xEEA7: 0x8B0F, //CJK UNIFIED IDEOGRAPH - 0xEEA8: 0x8B12, //CJK UNIFIED IDEOGRAPH - 0xEEA9: 0x8B15, //CJK UNIFIED IDEOGRAPH - 0xEEAA: 0x8B07, //CJK UNIFIED IDEOGRAPH - 0xEEAB: 0x8B0D, //CJK UNIFIED IDEOGRAPH - 0xEEAC: 0x8B08, //CJK UNIFIED IDEOGRAPH - 0xEEAD: 0x8B06, //CJK UNIFIED IDEOGRAPH - 0xEEAE: 0x8B1C, //CJK UNIFIED IDEOGRAPH - 0xEEAF: 0x8B13, //CJK UNIFIED IDEOGRAPH - 0xEEB0: 0x8B1A, //CJK UNIFIED IDEOGRAPH - 0xEEB1: 0x8C4F, //CJK UNIFIED IDEOGRAPH - 0xEEB2: 0x8C70, //CJK UNIFIED IDEOGRAPH - 0xEEB3: 0x8C72, //CJK UNIFIED IDEOGRAPH - 0xEEB4: 0x8C71, //CJK UNIFIED IDEOGRAPH - 0xEEB5: 0x8C6F, //CJK UNIFIED IDEOGRAPH - 0xEEB6: 0x8C95, //CJK UNIFIED IDEOGRAPH - 0xEEB7: 0x8C94, //CJK UNIFIED IDEOGRAPH - 0xEEB8: 0x8CF9, //CJK UNIFIED IDEOGRAPH - 0xEEB9: 0x8D6F, //CJK UNIFIED IDEOGRAPH - 0xEEBA: 0x8E4E, //CJK UNIFIED IDEOGRAPH - 0xEEBB: 0x8E4D, //CJK UNIFIED IDEOGRAPH - 0xEEBC: 0x8E53, //CJK UNIFIED IDEOGRAPH - 0xEEBD: 0x8E50, //CJK UNIFIED IDEOGRAPH - 0xEEBE: 0x8E4C, //CJK UNIFIED IDEOGRAPH - 0xEEBF: 0x8E47, //CJK UNIFIED IDEOGRAPH - 0xEEC0: 0x8F43, //CJK UNIFIED IDEOGRAPH - 0xEEC1: 0x8F40, //CJK UNIFIED IDEOGRAPH - 0xEEC2: 0x9085, //CJK UNIFIED IDEOGRAPH - 0xEEC3: 0x907E, //CJK UNIFIED IDEOGRAPH - 0xEEC4: 0x9138, //CJK UNIFIED IDEOGRAPH - 0xEEC5: 0x919A, //CJK UNIFIED IDEOGRAPH - 0xEEC6: 0x91A2, //CJK UNIFIED IDEOGRAPH - 0xEEC7: 0x919B, //CJK UNIFIED IDEOGRAPH - 0xEEC8: 0x9199, //CJK UNIFIED IDEOGRAPH - 0xEEC9: 0x919F, //CJK UNIFIED IDEOGRAPH - 0xEECA: 0x91A1, //CJK UNIFIED IDEOGRAPH - 0xEECB: 0x919D, //CJK UNIFIED IDEOGRAPH - 0xEECC: 0x91A0, //CJK UNIFIED IDEOGRAPH - 0xEECD: 0x93A1, //CJK UNIFIED IDEOGRAPH - 0xEECE: 0x9383, //CJK UNIFIED IDEOGRAPH - 0xEECF: 0x93AF, //CJK UNIFIED IDEOGRAPH - 0xEED0: 0x9364, //CJK UNIFIED IDEOGRAPH - 0xEED1: 0x9356, //CJK UNIFIED IDEOGRAPH - 0xEED2: 0x9347, //CJK UNIFIED IDEOGRAPH - 0xEED3: 0x937C, //CJK UNIFIED IDEOGRAPH - 0xEED4: 0x9358, //CJK UNIFIED IDEOGRAPH - 0xEED5: 0x935C, //CJK UNIFIED IDEOGRAPH - 0xEED6: 0x9376, //CJK UNIFIED IDEOGRAPH - 0xEED7: 0x9349, //CJK UNIFIED IDEOGRAPH - 0xEED8: 0x9350, //CJK UNIFIED IDEOGRAPH - 0xEED9: 0x9351, //CJK UNIFIED IDEOGRAPH - 0xEEDA: 0x9360, //CJK UNIFIED IDEOGRAPH - 0xEEDB: 0x936D, //CJK UNIFIED IDEOGRAPH - 0xEEDC: 0x938F, //CJK UNIFIED IDEOGRAPH - 0xEEDD: 0x934C, //CJK UNIFIED IDEOGRAPH - 0xEEDE: 0x936A, //CJK UNIFIED IDEOGRAPH - 0xEEDF: 0x9379, //CJK UNIFIED IDEOGRAPH - 0xEEE0: 0x9357, //CJK UNIFIED IDEOGRAPH - 0xEEE1: 0x9355, //CJK UNIFIED IDEOGRAPH - 0xEEE2: 0x9352, //CJK UNIFIED IDEOGRAPH - 0xEEE3: 0x934F, //CJK UNIFIED IDEOGRAPH - 0xEEE4: 0x9371, //CJK UNIFIED IDEOGRAPH - 0xEEE5: 0x9377, //CJK UNIFIED IDEOGRAPH - 0xEEE6: 0x937B, //CJK UNIFIED IDEOGRAPH - 0xEEE7: 0x9361, //CJK UNIFIED IDEOGRAPH - 0xEEE8: 0x935E, //CJK UNIFIED IDEOGRAPH - 0xEEE9: 0x9363, //CJK UNIFIED IDEOGRAPH - 0xEEEA: 0x9367, //CJK UNIFIED IDEOGRAPH - 0xEEEB: 0x9380, //CJK UNIFIED IDEOGRAPH - 0xEEEC: 0x934E, //CJK UNIFIED IDEOGRAPH - 0xEEED: 0x9359, //CJK UNIFIED IDEOGRAPH - 0xEEEE: 0x95C7, //CJK UNIFIED IDEOGRAPH - 0xEEEF: 0x95C0, //CJK UNIFIED IDEOGRAPH - 0xEEF0: 0x95C9, //CJK UNIFIED IDEOGRAPH - 0xEEF1: 0x95C3, //CJK UNIFIED IDEOGRAPH - 0xEEF2: 0x95C5, //CJK UNIFIED IDEOGRAPH - 0xEEF3: 0x95B7, //CJK UNIFIED IDEOGRAPH - 0xEEF4: 0x96AE, //CJK UNIFIED IDEOGRAPH - 0xEEF5: 0x96B0, //CJK UNIFIED IDEOGRAPH - 0xEEF6: 0x96AC, //CJK UNIFIED IDEOGRAPH - 0xEEF7: 0x9720, //CJK UNIFIED IDEOGRAPH - 0xEEF8: 0x971F, //CJK UNIFIED IDEOGRAPH - 0xEEF9: 0x9718, //CJK UNIFIED IDEOGRAPH - 0xEEFA: 0x971D, //CJK UNIFIED IDEOGRAPH - 0xEEFB: 0x9719, //CJK UNIFIED IDEOGRAPH - 0xEEFC: 0x979A, //CJK UNIFIED IDEOGRAPH - 0xEEFD: 0x97A1, //CJK UNIFIED IDEOGRAPH - 0xEEFE: 0x979C, //CJK UNIFIED IDEOGRAPH - 0xEF40: 0x979E, //CJK UNIFIED IDEOGRAPH - 0xEF41: 0x979D, //CJK UNIFIED IDEOGRAPH - 0xEF42: 0x97D5, //CJK UNIFIED IDEOGRAPH - 0xEF43: 0x97D4, //CJK UNIFIED IDEOGRAPH - 0xEF44: 0x97F1, //CJK UNIFIED IDEOGRAPH - 0xEF45: 0x9841, //CJK UNIFIED IDEOGRAPH - 0xEF46: 0x9844, //CJK UNIFIED IDEOGRAPH - 0xEF47: 0x984A, //CJK UNIFIED IDEOGRAPH - 0xEF48: 0x9849, //CJK UNIFIED IDEOGRAPH - 0xEF49: 0x9845, //CJK UNIFIED IDEOGRAPH - 0xEF4A: 0x9843, //CJK UNIFIED IDEOGRAPH - 0xEF4B: 0x9925, //CJK UNIFIED IDEOGRAPH - 0xEF4C: 0x992B, //CJK UNIFIED IDEOGRAPH - 0xEF4D: 0x992C, //CJK UNIFIED IDEOGRAPH - 0xEF4E: 0x992A, //CJK UNIFIED IDEOGRAPH - 0xEF4F: 0x9933, //CJK UNIFIED IDEOGRAPH - 0xEF50: 0x9932, //CJK UNIFIED IDEOGRAPH - 0xEF51: 0x992F, //CJK UNIFIED IDEOGRAPH - 0xEF52: 0x992D, //CJK UNIFIED IDEOGRAPH - 0xEF53: 0x9931, //CJK UNIFIED IDEOGRAPH - 0xEF54: 0x9930, //CJK UNIFIED IDEOGRAPH - 0xEF55: 0x9998, //CJK UNIFIED IDEOGRAPH - 0xEF56: 0x99A3, //CJK UNIFIED IDEOGRAPH - 0xEF57: 0x99A1, //CJK UNIFIED IDEOGRAPH - 0xEF58: 0x9A02, //CJK UNIFIED IDEOGRAPH - 0xEF59: 0x99FA, //CJK UNIFIED IDEOGRAPH - 0xEF5A: 0x99F4, //CJK UNIFIED IDEOGRAPH - 0xEF5B: 0x99F7, //CJK UNIFIED IDEOGRAPH - 0xEF5C: 0x99F9, //CJK UNIFIED IDEOGRAPH - 0xEF5D: 0x99F8, //CJK UNIFIED IDEOGRAPH - 0xEF5E: 0x99F6, //CJK UNIFIED IDEOGRAPH - 0xEF5F: 0x99FB, //CJK UNIFIED IDEOGRAPH - 0xEF60: 0x99FD, //CJK UNIFIED IDEOGRAPH - 0xEF61: 0x99FE, //CJK UNIFIED IDEOGRAPH - 0xEF62: 0x99FC, //CJK UNIFIED IDEOGRAPH - 0xEF63: 0x9A03, //CJK UNIFIED IDEOGRAPH - 0xEF64: 0x9ABE, //CJK UNIFIED IDEOGRAPH - 0xEF65: 0x9AFE, //CJK UNIFIED IDEOGRAPH - 0xEF66: 0x9AFD, //CJK UNIFIED IDEOGRAPH - 0xEF67: 0x9B01, //CJK UNIFIED IDEOGRAPH - 0xEF68: 0x9AFC, //CJK UNIFIED IDEOGRAPH - 0xEF69: 0x9B48, //CJK UNIFIED IDEOGRAPH - 0xEF6A: 0x9B9A, //CJK UNIFIED IDEOGRAPH - 0xEF6B: 0x9BA8, //CJK UNIFIED IDEOGRAPH - 0xEF6C: 0x9B9E, //CJK UNIFIED IDEOGRAPH - 0xEF6D: 0x9B9B, //CJK UNIFIED IDEOGRAPH - 0xEF6E: 0x9BA6, //CJK UNIFIED IDEOGRAPH - 0xEF6F: 0x9BA1, //CJK UNIFIED IDEOGRAPH - 0xEF70: 0x9BA5, //CJK UNIFIED IDEOGRAPH - 0xEF71: 0x9BA4, //CJK UNIFIED IDEOGRAPH - 0xEF72: 0x9B86, //CJK UNIFIED IDEOGRAPH - 0xEF73: 0x9BA2, //CJK UNIFIED IDEOGRAPH - 0xEF74: 0x9BA0, //CJK UNIFIED IDEOGRAPH - 0xEF75: 0x9BAF, //CJK UNIFIED IDEOGRAPH - 0xEF76: 0x9D33, //CJK UNIFIED IDEOGRAPH - 0xEF77: 0x9D41, //CJK UNIFIED IDEOGRAPH - 0xEF78: 0x9D67, //CJK UNIFIED IDEOGRAPH - 0xEF79: 0x9D36, //CJK UNIFIED IDEOGRAPH - 0xEF7A: 0x9D2E, //CJK UNIFIED IDEOGRAPH - 0xEF7B: 0x9D2F, //CJK UNIFIED IDEOGRAPH - 0xEF7C: 0x9D31, //CJK UNIFIED IDEOGRAPH - 0xEF7D: 0x9D38, //CJK UNIFIED IDEOGRAPH - 0xEF7E: 0x9D30, //CJK UNIFIED IDEOGRAPH - 0xEFA1: 0x9D45, //CJK UNIFIED IDEOGRAPH - 0xEFA2: 0x9D42, //CJK UNIFIED IDEOGRAPH - 0xEFA3: 0x9D43, //CJK UNIFIED IDEOGRAPH - 0xEFA4: 0x9D3E, //CJK UNIFIED IDEOGRAPH - 0xEFA5: 0x9D37, //CJK UNIFIED IDEOGRAPH - 0xEFA6: 0x9D40, //CJK UNIFIED IDEOGRAPH - 0xEFA7: 0x9D3D, //CJK UNIFIED IDEOGRAPH - 0xEFA8: 0x7FF5, //CJK UNIFIED IDEOGRAPH - 0xEFA9: 0x9D2D, //CJK UNIFIED IDEOGRAPH - 0xEFAA: 0x9E8A, //CJK UNIFIED IDEOGRAPH - 0xEFAB: 0x9E89, //CJK UNIFIED IDEOGRAPH - 0xEFAC: 0x9E8D, //CJK UNIFIED IDEOGRAPH - 0xEFAD: 0x9EB0, //CJK UNIFIED IDEOGRAPH - 0xEFAE: 0x9EC8, //CJK UNIFIED IDEOGRAPH - 0xEFAF: 0x9EDA, //CJK UNIFIED IDEOGRAPH - 0xEFB0: 0x9EFB, //CJK UNIFIED IDEOGRAPH - 0xEFB1: 0x9EFF, //CJK UNIFIED IDEOGRAPH - 0xEFB2: 0x9F24, //CJK UNIFIED IDEOGRAPH - 0xEFB3: 0x9F23, //CJK UNIFIED IDEOGRAPH - 0xEFB4: 0x9F22, //CJK UNIFIED IDEOGRAPH - 0xEFB5: 0x9F54, //CJK UNIFIED IDEOGRAPH - 0xEFB6: 0x9FA0, //CJK UNIFIED IDEOGRAPH - 0xEFB7: 0x5131, //CJK UNIFIED IDEOGRAPH - 0xEFB8: 0x512D, //CJK UNIFIED IDEOGRAPH - 0xEFB9: 0x512E, //CJK UNIFIED IDEOGRAPH - 0xEFBA: 0x5698, //CJK UNIFIED IDEOGRAPH - 0xEFBB: 0x569C, //CJK UNIFIED IDEOGRAPH - 0xEFBC: 0x5697, //CJK UNIFIED IDEOGRAPH - 0xEFBD: 0x569A, //CJK UNIFIED IDEOGRAPH - 0xEFBE: 0x569D, //CJK UNIFIED IDEOGRAPH - 0xEFBF: 0x5699, //CJK UNIFIED IDEOGRAPH - 0xEFC0: 0x5970, //CJK UNIFIED IDEOGRAPH - 0xEFC1: 0x5B3C, //CJK UNIFIED IDEOGRAPH - 0xEFC2: 0x5C69, //CJK UNIFIED IDEOGRAPH - 0xEFC3: 0x5C6A, //CJK UNIFIED IDEOGRAPH - 0xEFC4: 0x5DC0, //CJK UNIFIED IDEOGRAPH - 0xEFC5: 0x5E6D, //CJK UNIFIED IDEOGRAPH - 0xEFC6: 0x5E6E, //CJK UNIFIED IDEOGRAPH - 0xEFC7: 0x61D8, //CJK UNIFIED IDEOGRAPH - 0xEFC8: 0x61DF, //CJK UNIFIED IDEOGRAPH - 0xEFC9: 0x61ED, //CJK UNIFIED IDEOGRAPH - 0xEFCA: 0x61EE, //CJK UNIFIED IDEOGRAPH - 0xEFCB: 0x61F1, //CJK UNIFIED IDEOGRAPH - 0xEFCC: 0x61EA, //CJK UNIFIED IDEOGRAPH - 0xEFCD: 0x61F0, //CJK UNIFIED IDEOGRAPH - 0xEFCE: 0x61EB, //CJK UNIFIED IDEOGRAPH - 0xEFCF: 0x61D6, //CJK UNIFIED IDEOGRAPH - 0xEFD0: 0x61E9, //CJK UNIFIED IDEOGRAPH - 0xEFD1: 0x64FF, //CJK UNIFIED IDEOGRAPH - 0xEFD2: 0x6504, //CJK UNIFIED IDEOGRAPH - 0xEFD3: 0x64FD, //CJK UNIFIED IDEOGRAPH - 0xEFD4: 0x64F8, //CJK UNIFIED IDEOGRAPH - 0xEFD5: 0x6501, //CJK UNIFIED IDEOGRAPH - 0xEFD6: 0x6503, //CJK UNIFIED IDEOGRAPH - 0xEFD7: 0x64FC, //CJK UNIFIED IDEOGRAPH - 0xEFD8: 0x6594, //CJK UNIFIED IDEOGRAPH - 0xEFD9: 0x65DB, //CJK UNIFIED IDEOGRAPH - 0xEFDA: 0x66DA, //CJK UNIFIED IDEOGRAPH - 0xEFDB: 0x66DB, //CJK UNIFIED IDEOGRAPH - 0xEFDC: 0x66D8, //CJK UNIFIED IDEOGRAPH - 0xEFDD: 0x6AC5, //CJK UNIFIED IDEOGRAPH - 0xEFDE: 0x6AB9, //CJK UNIFIED IDEOGRAPH - 0xEFDF: 0x6ABD, //CJK UNIFIED IDEOGRAPH - 0xEFE0: 0x6AE1, //CJK UNIFIED IDEOGRAPH - 0xEFE1: 0x6AC6, //CJK UNIFIED IDEOGRAPH - 0xEFE2: 0x6ABA, //CJK UNIFIED IDEOGRAPH - 0xEFE3: 0x6AB6, //CJK UNIFIED IDEOGRAPH - 0xEFE4: 0x6AB7, //CJK UNIFIED IDEOGRAPH - 0xEFE5: 0x6AC7, //CJK UNIFIED IDEOGRAPH - 0xEFE6: 0x6AB4, //CJK UNIFIED IDEOGRAPH - 0xEFE7: 0x6AAD, //CJK UNIFIED IDEOGRAPH - 0xEFE8: 0x6B5E, //CJK UNIFIED IDEOGRAPH - 0xEFE9: 0x6BC9, //CJK UNIFIED IDEOGRAPH - 0xEFEA: 0x6C0B, //CJK UNIFIED IDEOGRAPH - 0xEFEB: 0x7007, //CJK UNIFIED IDEOGRAPH - 0xEFEC: 0x700C, //CJK UNIFIED IDEOGRAPH - 0xEFED: 0x700D, //CJK UNIFIED IDEOGRAPH - 0xEFEE: 0x7001, //CJK UNIFIED IDEOGRAPH - 0xEFEF: 0x7005, //CJK UNIFIED IDEOGRAPH - 0xEFF0: 0x7014, //CJK UNIFIED IDEOGRAPH - 0xEFF1: 0x700E, //CJK UNIFIED IDEOGRAPH - 0xEFF2: 0x6FFF, //CJK UNIFIED IDEOGRAPH - 0xEFF3: 0x7000, //CJK UNIFIED IDEOGRAPH - 0xEFF4: 0x6FFB, //CJK UNIFIED IDEOGRAPH - 0xEFF5: 0x7026, //CJK UNIFIED IDEOGRAPH - 0xEFF6: 0x6FFC, //CJK UNIFIED IDEOGRAPH - 0xEFF7: 0x6FF7, //CJK UNIFIED IDEOGRAPH - 0xEFF8: 0x700A, //CJK UNIFIED IDEOGRAPH - 0xEFF9: 0x7201, //CJK UNIFIED IDEOGRAPH - 0xEFFA: 0x71FF, //CJK UNIFIED IDEOGRAPH - 0xEFFB: 0x71F9, //CJK UNIFIED IDEOGRAPH - 0xEFFC: 0x7203, //CJK UNIFIED IDEOGRAPH - 0xEFFD: 0x71FD, //CJK UNIFIED IDEOGRAPH - 0xEFFE: 0x7376, //CJK UNIFIED IDEOGRAPH - 0xF040: 0x74B8, //CJK UNIFIED IDEOGRAPH - 0xF041: 0x74C0, //CJK UNIFIED IDEOGRAPH - 0xF042: 0x74B5, //CJK UNIFIED IDEOGRAPH - 0xF043: 0x74C1, //CJK UNIFIED IDEOGRAPH - 0xF044: 0x74BE, //CJK UNIFIED IDEOGRAPH - 0xF045: 0x74B6, //CJK UNIFIED IDEOGRAPH - 0xF046: 0x74BB, //CJK UNIFIED IDEOGRAPH - 0xF047: 0x74C2, //CJK UNIFIED IDEOGRAPH - 0xF048: 0x7514, //CJK UNIFIED IDEOGRAPH - 0xF049: 0x7513, //CJK UNIFIED IDEOGRAPH - 0xF04A: 0x765C, //CJK UNIFIED IDEOGRAPH - 0xF04B: 0x7664, //CJK UNIFIED IDEOGRAPH - 0xF04C: 0x7659, //CJK UNIFIED IDEOGRAPH - 0xF04D: 0x7650, //CJK UNIFIED IDEOGRAPH - 0xF04E: 0x7653, //CJK UNIFIED IDEOGRAPH - 0xF04F: 0x7657, //CJK UNIFIED IDEOGRAPH - 0xF050: 0x765A, //CJK UNIFIED IDEOGRAPH - 0xF051: 0x76A6, //CJK UNIFIED IDEOGRAPH - 0xF052: 0x76BD, //CJK UNIFIED IDEOGRAPH - 0xF053: 0x76EC, //CJK UNIFIED IDEOGRAPH - 0xF054: 0x77C2, //CJK UNIFIED IDEOGRAPH - 0xF055: 0x77BA, //CJK UNIFIED IDEOGRAPH - 0xF056: 0x78FF, //CJK UNIFIED IDEOGRAPH - 0xF057: 0x790C, //CJK UNIFIED IDEOGRAPH - 0xF058: 0x7913, //CJK UNIFIED IDEOGRAPH - 0xF059: 0x7914, //CJK UNIFIED IDEOGRAPH - 0xF05A: 0x7909, //CJK UNIFIED IDEOGRAPH - 0xF05B: 0x7910, //CJK UNIFIED IDEOGRAPH - 0xF05C: 0x7912, //CJK UNIFIED IDEOGRAPH - 0xF05D: 0x7911, //CJK UNIFIED IDEOGRAPH - 0xF05E: 0x79AD, //CJK UNIFIED IDEOGRAPH - 0xF05F: 0x79AC, //CJK UNIFIED IDEOGRAPH - 0xF060: 0x7A5F, //CJK UNIFIED IDEOGRAPH - 0xF061: 0x7C1C, //CJK UNIFIED IDEOGRAPH - 0xF062: 0x7C29, //CJK UNIFIED IDEOGRAPH - 0xF063: 0x7C19, //CJK UNIFIED IDEOGRAPH - 0xF064: 0x7C20, //CJK UNIFIED IDEOGRAPH - 0xF065: 0x7C1F, //CJK UNIFIED IDEOGRAPH - 0xF066: 0x7C2D, //CJK UNIFIED IDEOGRAPH - 0xF067: 0x7C1D, //CJK UNIFIED IDEOGRAPH - 0xF068: 0x7C26, //CJK UNIFIED IDEOGRAPH - 0xF069: 0x7C28, //CJK UNIFIED IDEOGRAPH - 0xF06A: 0x7C22, //CJK UNIFIED IDEOGRAPH - 0xF06B: 0x7C25, //CJK UNIFIED IDEOGRAPH - 0xF06C: 0x7C30, //CJK UNIFIED IDEOGRAPH - 0xF06D: 0x7E5C, //CJK UNIFIED IDEOGRAPH - 0xF06E: 0x7E50, //CJK UNIFIED IDEOGRAPH - 0xF06F: 0x7E56, //CJK UNIFIED IDEOGRAPH - 0xF070: 0x7E63, //CJK UNIFIED IDEOGRAPH - 0xF071: 0x7E58, //CJK UNIFIED IDEOGRAPH - 0xF072: 0x7E62, //CJK UNIFIED IDEOGRAPH - 0xF073: 0x7E5F, //CJK UNIFIED IDEOGRAPH - 0xF074: 0x7E51, //CJK UNIFIED IDEOGRAPH - 0xF075: 0x7E60, //CJK UNIFIED IDEOGRAPH - 0xF076: 0x7E57, //CJK UNIFIED IDEOGRAPH - 0xF077: 0x7E53, //CJK UNIFIED IDEOGRAPH - 0xF078: 0x7FB5, //CJK UNIFIED IDEOGRAPH - 0xF079: 0x7FB3, //CJK UNIFIED IDEOGRAPH - 0xF07A: 0x7FF7, //CJK UNIFIED IDEOGRAPH - 0xF07B: 0x7FF8, //CJK UNIFIED IDEOGRAPH - 0xF07C: 0x8075, //CJK UNIFIED IDEOGRAPH - 0xF07D: 0x81D1, //CJK UNIFIED IDEOGRAPH - 0xF07E: 0x81D2, //CJK UNIFIED IDEOGRAPH - 0xF0A1: 0x81D0, //CJK UNIFIED IDEOGRAPH - 0xF0A2: 0x825F, //CJK UNIFIED IDEOGRAPH - 0xF0A3: 0x825E, //CJK UNIFIED IDEOGRAPH - 0xF0A4: 0x85B4, //CJK UNIFIED IDEOGRAPH - 0xF0A5: 0x85C6, //CJK UNIFIED IDEOGRAPH - 0xF0A6: 0x85C0, //CJK UNIFIED IDEOGRAPH - 0xF0A7: 0x85C3, //CJK UNIFIED IDEOGRAPH - 0xF0A8: 0x85C2, //CJK UNIFIED IDEOGRAPH - 0xF0A9: 0x85B3, //CJK UNIFIED IDEOGRAPH - 0xF0AA: 0x85B5, //CJK UNIFIED IDEOGRAPH - 0xF0AB: 0x85BD, //CJK UNIFIED IDEOGRAPH - 0xF0AC: 0x85C7, //CJK UNIFIED IDEOGRAPH - 0xF0AD: 0x85C4, //CJK UNIFIED IDEOGRAPH - 0xF0AE: 0x85BF, //CJK UNIFIED IDEOGRAPH - 0xF0AF: 0x85CB, //CJK UNIFIED IDEOGRAPH - 0xF0B0: 0x85CE, //CJK UNIFIED IDEOGRAPH - 0xF0B1: 0x85C8, //CJK UNIFIED IDEOGRAPH - 0xF0B2: 0x85C5, //CJK UNIFIED IDEOGRAPH - 0xF0B3: 0x85B1, //CJK UNIFIED IDEOGRAPH - 0xF0B4: 0x85B6, //CJK UNIFIED IDEOGRAPH - 0xF0B5: 0x85D2, //CJK UNIFIED IDEOGRAPH - 0xF0B6: 0x8624, //CJK UNIFIED IDEOGRAPH - 0xF0B7: 0x85B8, //CJK UNIFIED IDEOGRAPH - 0xF0B8: 0x85B7, //CJK UNIFIED IDEOGRAPH - 0xF0B9: 0x85BE, //CJK UNIFIED IDEOGRAPH - 0xF0BA: 0x8669, //CJK UNIFIED IDEOGRAPH - 0xF0BB: 0x87E7, //CJK UNIFIED IDEOGRAPH - 0xF0BC: 0x87E6, //CJK UNIFIED IDEOGRAPH - 0xF0BD: 0x87E2, //CJK UNIFIED IDEOGRAPH - 0xF0BE: 0x87DB, //CJK UNIFIED IDEOGRAPH - 0xF0BF: 0x87EB, //CJK UNIFIED IDEOGRAPH - 0xF0C0: 0x87EA, //CJK UNIFIED IDEOGRAPH - 0xF0C1: 0x87E5, //CJK UNIFIED IDEOGRAPH - 0xF0C2: 0x87DF, //CJK UNIFIED IDEOGRAPH - 0xF0C3: 0x87F3, //CJK UNIFIED IDEOGRAPH - 0xF0C4: 0x87E4, //CJK UNIFIED IDEOGRAPH - 0xF0C5: 0x87D4, //CJK UNIFIED IDEOGRAPH - 0xF0C6: 0x87DC, //CJK UNIFIED IDEOGRAPH - 0xF0C7: 0x87D3, //CJK UNIFIED IDEOGRAPH - 0xF0C8: 0x87ED, //CJK UNIFIED IDEOGRAPH - 0xF0C9: 0x87D8, //CJK UNIFIED IDEOGRAPH - 0xF0CA: 0x87E3, //CJK UNIFIED IDEOGRAPH - 0xF0CB: 0x87A4, //CJK UNIFIED IDEOGRAPH - 0xF0CC: 0x87D7, //CJK UNIFIED IDEOGRAPH - 0xF0CD: 0x87D9, //CJK UNIFIED IDEOGRAPH - 0xF0CE: 0x8801, //CJK UNIFIED IDEOGRAPH - 0xF0CF: 0x87F4, //CJK UNIFIED IDEOGRAPH - 0xF0D0: 0x87E8, //CJK UNIFIED IDEOGRAPH - 0xF0D1: 0x87DD, //CJK UNIFIED IDEOGRAPH - 0xF0D2: 0x8953, //CJK UNIFIED IDEOGRAPH - 0xF0D3: 0x894B, //CJK UNIFIED IDEOGRAPH - 0xF0D4: 0x894F, //CJK UNIFIED IDEOGRAPH - 0xF0D5: 0x894C, //CJK UNIFIED IDEOGRAPH - 0xF0D6: 0x8946, //CJK UNIFIED IDEOGRAPH - 0xF0D7: 0x8950, //CJK UNIFIED IDEOGRAPH - 0xF0D8: 0x8951, //CJK UNIFIED IDEOGRAPH - 0xF0D9: 0x8949, //CJK UNIFIED IDEOGRAPH - 0xF0DA: 0x8B2A, //CJK UNIFIED IDEOGRAPH - 0xF0DB: 0x8B27, //CJK UNIFIED IDEOGRAPH - 0xF0DC: 0x8B23, //CJK UNIFIED IDEOGRAPH - 0xF0DD: 0x8B33, //CJK UNIFIED IDEOGRAPH - 0xF0DE: 0x8B30, //CJK UNIFIED IDEOGRAPH - 0xF0DF: 0x8B35, //CJK UNIFIED IDEOGRAPH - 0xF0E0: 0x8B47, //CJK UNIFIED IDEOGRAPH - 0xF0E1: 0x8B2F, //CJK UNIFIED IDEOGRAPH - 0xF0E2: 0x8B3C, //CJK UNIFIED IDEOGRAPH - 0xF0E3: 0x8B3E, //CJK UNIFIED IDEOGRAPH - 0xF0E4: 0x8B31, //CJK UNIFIED IDEOGRAPH - 0xF0E5: 0x8B25, //CJK UNIFIED IDEOGRAPH - 0xF0E6: 0x8B37, //CJK UNIFIED IDEOGRAPH - 0xF0E7: 0x8B26, //CJK UNIFIED IDEOGRAPH - 0xF0E8: 0x8B36, //CJK UNIFIED IDEOGRAPH - 0xF0E9: 0x8B2E, //CJK UNIFIED IDEOGRAPH - 0xF0EA: 0x8B24, //CJK UNIFIED IDEOGRAPH - 0xF0EB: 0x8B3B, //CJK UNIFIED IDEOGRAPH - 0xF0EC: 0x8B3D, //CJK UNIFIED IDEOGRAPH - 0xF0ED: 0x8B3A, //CJK UNIFIED IDEOGRAPH - 0xF0EE: 0x8C42, //CJK UNIFIED IDEOGRAPH - 0xF0EF: 0x8C75, //CJK UNIFIED IDEOGRAPH - 0xF0F0: 0x8C99, //CJK UNIFIED IDEOGRAPH - 0xF0F1: 0x8C98, //CJK UNIFIED IDEOGRAPH - 0xF0F2: 0x8C97, //CJK UNIFIED IDEOGRAPH - 0xF0F3: 0x8CFE, //CJK UNIFIED IDEOGRAPH - 0xF0F4: 0x8D04, //CJK UNIFIED IDEOGRAPH - 0xF0F5: 0x8D02, //CJK UNIFIED IDEOGRAPH - 0xF0F6: 0x8D00, //CJK UNIFIED IDEOGRAPH - 0xF0F7: 0x8E5C, //CJK UNIFIED IDEOGRAPH - 0xF0F8: 0x8E62, //CJK UNIFIED IDEOGRAPH - 0xF0F9: 0x8E60, //CJK UNIFIED IDEOGRAPH - 0xF0FA: 0x8E57, //CJK UNIFIED IDEOGRAPH - 0xF0FB: 0x8E56, //CJK UNIFIED IDEOGRAPH - 0xF0FC: 0x8E5E, //CJK UNIFIED IDEOGRAPH - 0xF0FD: 0x8E65, //CJK UNIFIED IDEOGRAPH - 0xF0FE: 0x8E67, //CJK UNIFIED IDEOGRAPH - 0xF140: 0x8E5B, //CJK UNIFIED IDEOGRAPH - 0xF141: 0x8E5A, //CJK UNIFIED IDEOGRAPH - 0xF142: 0x8E61, //CJK UNIFIED IDEOGRAPH - 0xF143: 0x8E5D, //CJK UNIFIED IDEOGRAPH - 0xF144: 0x8E69, //CJK UNIFIED IDEOGRAPH - 0xF145: 0x8E54, //CJK UNIFIED IDEOGRAPH - 0xF146: 0x8F46, //CJK UNIFIED IDEOGRAPH - 0xF147: 0x8F47, //CJK UNIFIED IDEOGRAPH - 0xF148: 0x8F48, //CJK UNIFIED IDEOGRAPH - 0xF149: 0x8F4B, //CJK UNIFIED IDEOGRAPH - 0xF14A: 0x9128, //CJK UNIFIED IDEOGRAPH - 0xF14B: 0x913A, //CJK UNIFIED IDEOGRAPH - 0xF14C: 0x913B, //CJK UNIFIED IDEOGRAPH - 0xF14D: 0x913E, //CJK UNIFIED IDEOGRAPH - 0xF14E: 0x91A8, //CJK UNIFIED IDEOGRAPH - 0xF14F: 0x91A5, //CJK UNIFIED IDEOGRAPH - 0xF150: 0x91A7, //CJK UNIFIED IDEOGRAPH - 0xF151: 0x91AF, //CJK UNIFIED IDEOGRAPH - 0xF152: 0x91AA, //CJK UNIFIED IDEOGRAPH - 0xF153: 0x93B5, //CJK UNIFIED IDEOGRAPH - 0xF154: 0x938C, //CJK UNIFIED IDEOGRAPH - 0xF155: 0x9392, //CJK UNIFIED IDEOGRAPH - 0xF156: 0x93B7, //CJK UNIFIED IDEOGRAPH - 0xF157: 0x939B, //CJK UNIFIED IDEOGRAPH - 0xF158: 0x939D, //CJK UNIFIED IDEOGRAPH - 0xF159: 0x9389, //CJK UNIFIED IDEOGRAPH - 0xF15A: 0x93A7, //CJK UNIFIED IDEOGRAPH - 0xF15B: 0x938E, //CJK UNIFIED IDEOGRAPH - 0xF15C: 0x93AA, //CJK UNIFIED IDEOGRAPH - 0xF15D: 0x939E, //CJK UNIFIED IDEOGRAPH - 0xF15E: 0x93A6, //CJK UNIFIED IDEOGRAPH - 0xF15F: 0x9395, //CJK UNIFIED IDEOGRAPH - 0xF160: 0x9388, //CJK UNIFIED IDEOGRAPH - 0xF161: 0x9399, //CJK UNIFIED IDEOGRAPH - 0xF162: 0x939F, //CJK UNIFIED IDEOGRAPH - 0xF163: 0x938D, //CJK UNIFIED IDEOGRAPH - 0xF164: 0x93B1, //CJK UNIFIED IDEOGRAPH - 0xF165: 0x9391, //CJK UNIFIED IDEOGRAPH - 0xF166: 0x93B2, //CJK UNIFIED IDEOGRAPH - 0xF167: 0x93A4, //CJK UNIFIED IDEOGRAPH - 0xF168: 0x93A8, //CJK UNIFIED IDEOGRAPH - 0xF169: 0x93B4, //CJK UNIFIED IDEOGRAPH - 0xF16A: 0x93A3, //CJK UNIFIED IDEOGRAPH - 0xF16B: 0x93A5, //CJK UNIFIED IDEOGRAPH - 0xF16C: 0x95D2, //CJK UNIFIED IDEOGRAPH - 0xF16D: 0x95D3, //CJK UNIFIED IDEOGRAPH - 0xF16E: 0x95D1, //CJK UNIFIED IDEOGRAPH - 0xF16F: 0x96B3, //CJK UNIFIED IDEOGRAPH - 0xF170: 0x96D7, //CJK UNIFIED IDEOGRAPH - 0xF171: 0x96DA, //CJK UNIFIED IDEOGRAPH - 0xF172: 0x5DC2, //CJK UNIFIED IDEOGRAPH - 0xF173: 0x96DF, //CJK UNIFIED IDEOGRAPH - 0xF174: 0x96D8, //CJK UNIFIED IDEOGRAPH - 0xF175: 0x96DD, //CJK UNIFIED IDEOGRAPH - 0xF176: 0x9723, //CJK UNIFIED IDEOGRAPH - 0xF177: 0x9722, //CJK UNIFIED IDEOGRAPH - 0xF178: 0x9725, //CJK UNIFIED IDEOGRAPH - 0xF179: 0x97AC, //CJK UNIFIED IDEOGRAPH - 0xF17A: 0x97AE, //CJK UNIFIED IDEOGRAPH - 0xF17B: 0x97A8, //CJK UNIFIED IDEOGRAPH - 0xF17C: 0x97AB, //CJK UNIFIED IDEOGRAPH - 0xF17D: 0x97A4, //CJK UNIFIED IDEOGRAPH - 0xF17E: 0x97AA, //CJK UNIFIED IDEOGRAPH - 0xF1A1: 0x97A2, //CJK UNIFIED IDEOGRAPH - 0xF1A2: 0x97A5, //CJK UNIFIED IDEOGRAPH - 0xF1A3: 0x97D7, //CJK UNIFIED IDEOGRAPH - 0xF1A4: 0x97D9, //CJK UNIFIED IDEOGRAPH - 0xF1A5: 0x97D6, //CJK UNIFIED IDEOGRAPH - 0xF1A6: 0x97D8, //CJK UNIFIED IDEOGRAPH - 0xF1A7: 0x97FA, //CJK UNIFIED IDEOGRAPH - 0xF1A8: 0x9850, //CJK UNIFIED IDEOGRAPH - 0xF1A9: 0x9851, //CJK UNIFIED IDEOGRAPH - 0xF1AA: 0x9852, //CJK UNIFIED IDEOGRAPH - 0xF1AB: 0x98B8, //CJK UNIFIED IDEOGRAPH - 0xF1AC: 0x9941, //CJK UNIFIED IDEOGRAPH - 0xF1AD: 0x993C, //CJK UNIFIED IDEOGRAPH - 0xF1AE: 0x993A, //CJK UNIFIED IDEOGRAPH - 0xF1AF: 0x9A0F, //CJK UNIFIED IDEOGRAPH - 0xF1B0: 0x9A0B, //CJK UNIFIED IDEOGRAPH - 0xF1B1: 0x9A09, //CJK UNIFIED IDEOGRAPH - 0xF1B2: 0x9A0D, //CJK UNIFIED IDEOGRAPH - 0xF1B3: 0x9A04, //CJK UNIFIED IDEOGRAPH - 0xF1B4: 0x9A11, //CJK UNIFIED IDEOGRAPH - 0xF1B5: 0x9A0A, //CJK UNIFIED IDEOGRAPH - 0xF1B6: 0x9A05, //CJK UNIFIED IDEOGRAPH - 0xF1B7: 0x9A07, //CJK UNIFIED IDEOGRAPH - 0xF1B8: 0x9A06, //CJK UNIFIED IDEOGRAPH - 0xF1B9: 0x9AC0, //CJK UNIFIED IDEOGRAPH - 0xF1BA: 0x9ADC, //CJK UNIFIED IDEOGRAPH - 0xF1BB: 0x9B08, //CJK UNIFIED IDEOGRAPH - 0xF1BC: 0x9B04, //CJK UNIFIED IDEOGRAPH - 0xF1BD: 0x9B05, //CJK UNIFIED IDEOGRAPH - 0xF1BE: 0x9B29, //CJK UNIFIED IDEOGRAPH - 0xF1BF: 0x9B35, //CJK UNIFIED IDEOGRAPH - 0xF1C0: 0x9B4A, //CJK UNIFIED IDEOGRAPH - 0xF1C1: 0x9B4C, //CJK UNIFIED IDEOGRAPH - 0xF1C2: 0x9B4B, //CJK UNIFIED IDEOGRAPH - 0xF1C3: 0x9BC7, //CJK UNIFIED IDEOGRAPH - 0xF1C4: 0x9BC6, //CJK UNIFIED IDEOGRAPH - 0xF1C5: 0x9BC3, //CJK UNIFIED IDEOGRAPH - 0xF1C6: 0x9BBF, //CJK UNIFIED IDEOGRAPH - 0xF1C7: 0x9BC1, //CJK UNIFIED IDEOGRAPH - 0xF1C8: 0x9BB5, //CJK UNIFIED IDEOGRAPH - 0xF1C9: 0x9BB8, //CJK UNIFIED IDEOGRAPH - 0xF1CA: 0x9BD3, //CJK UNIFIED IDEOGRAPH - 0xF1CB: 0x9BB6, //CJK UNIFIED IDEOGRAPH - 0xF1CC: 0x9BC4, //CJK UNIFIED IDEOGRAPH - 0xF1CD: 0x9BB9, //CJK UNIFIED IDEOGRAPH - 0xF1CE: 0x9BBD, //CJK UNIFIED IDEOGRAPH - 0xF1CF: 0x9D5C, //CJK UNIFIED IDEOGRAPH - 0xF1D0: 0x9D53, //CJK UNIFIED IDEOGRAPH - 0xF1D1: 0x9D4F, //CJK UNIFIED IDEOGRAPH - 0xF1D2: 0x9D4A, //CJK UNIFIED IDEOGRAPH - 0xF1D3: 0x9D5B, //CJK UNIFIED IDEOGRAPH - 0xF1D4: 0x9D4B, //CJK UNIFIED IDEOGRAPH - 0xF1D5: 0x9D59, //CJK UNIFIED IDEOGRAPH - 0xF1D6: 0x9D56, //CJK UNIFIED IDEOGRAPH - 0xF1D7: 0x9D4C, //CJK UNIFIED IDEOGRAPH - 0xF1D8: 0x9D57, //CJK UNIFIED IDEOGRAPH - 0xF1D9: 0x9D52, //CJK UNIFIED IDEOGRAPH - 0xF1DA: 0x9D54, //CJK UNIFIED IDEOGRAPH - 0xF1DB: 0x9D5F, //CJK UNIFIED IDEOGRAPH - 0xF1DC: 0x9D58, //CJK UNIFIED IDEOGRAPH - 0xF1DD: 0x9D5A, //CJK UNIFIED IDEOGRAPH - 0xF1DE: 0x9E8E, //CJK UNIFIED IDEOGRAPH - 0xF1DF: 0x9E8C, //CJK UNIFIED IDEOGRAPH - 0xF1E0: 0x9EDF, //CJK UNIFIED IDEOGRAPH - 0xF1E1: 0x9F01, //CJK UNIFIED IDEOGRAPH - 0xF1E2: 0x9F00, //CJK UNIFIED IDEOGRAPH - 0xF1E3: 0x9F16, //CJK UNIFIED IDEOGRAPH - 0xF1E4: 0x9F25, //CJK UNIFIED IDEOGRAPH - 0xF1E5: 0x9F2B, //CJK UNIFIED IDEOGRAPH - 0xF1E6: 0x9F2A, //CJK UNIFIED IDEOGRAPH - 0xF1E7: 0x9F29, //CJK UNIFIED IDEOGRAPH - 0xF1E8: 0x9F28, //CJK UNIFIED IDEOGRAPH - 0xF1E9: 0x9F4C, //CJK UNIFIED IDEOGRAPH - 0xF1EA: 0x9F55, //CJK UNIFIED IDEOGRAPH - 0xF1EB: 0x5134, //CJK UNIFIED IDEOGRAPH - 0xF1EC: 0x5135, //CJK UNIFIED IDEOGRAPH - 0xF1ED: 0x5296, //CJK UNIFIED IDEOGRAPH - 0xF1EE: 0x52F7, //CJK UNIFIED IDEOGRAPH - 0xF1EF: 0x53B4, //CJK UNIFIED IDEOGRAPH - 0xF1F0: 0x56AB, //CJK UNIFIED IDEOGRAPH - 0xF1F1: 0x56AD, //CJK UNIFIED IDEOGRAPH - 0xF1F2: 0x56A6, //CJK UNIFIED IDEOGRAPH - 0xF1F3: 0x56A7, //CJK UNIFIED IDEOGRAPH - 0xF1F4: 0x56AA, //CJK UNIFIED IDEOGRAPH - 0xF1F5: 0x56AC, //CJK UNIFIED IDEOGRAPH - 0xF1F6: 0x58DA, //CJK UNIFIED IDEOGRAPH - 0xF1F7: 0x58DD, //CJK UNIFIED IDEOGRAPH - 0xF1F8: 0x58DB, //CJK UNIFIED IDEOGRAPH - 0xF1F9: 0x5912, //CJK UNIFIED IDEOGRAPH - 0xF1FA: 0x5B3D, //CJK UNIFIED IDEOGRAPH - 0xF1FB: 0x5B3E, //CJK UNIFIED IDEOGRAPH - 0xF1FC: 0x5B3F, //CJK UNIFIED IDEOGRAPH - 0xF1FD: 0x5DC3, //CJK UNIFIED IDEOGRAPH - 0xF1FE: 0x5E70, //CJK UNIFIED IDEOGRAPH - 0xF240: 0x5FBF, //CJK UNIFIED IDEOGRAPH - 0xF241: 0x61FB, //CJK UNIFIED IDEOGRAPH - 0xF242: 0x6507, //CJK UNIFIED IDEOGRAPH - 0xF243: 0x6510, //CJK UNIFIED IDEOGRAPH - 0xF244: 0x650D, //CJK UNIFIED IDEOGRAPH - 0xF245: 0x6509, //CJK UNIFIED IDEOGRAPH - 0xF246: 0x650C, //CJK UNIFIED IDEOGRAPH - 0xF247: 0x650E, //CJK UNIFIED IDEOGRAPH - 0xF248: 0x6584, //CJK UNIFIED IDEOGRAPH - 0xF249: 0x65DE, //CJK UNIFIED IDEOGRAPH - 0xF24A: 0x65DD, //CJK UNIFIED IDEOGRAPH - 0xF24B: 0x66DE, //CJK UNIFIED IDEOGRAPH - 0xF24C: 0x6AE7, //CJK UNIFIED IDEOGRAPH - 0xF24D: 0x6AE0, //CJK UNIFIED IDEOGRAPH - 0xF24E: 0x6ACC, //CJK UNIFIED IDEOGRAPH - 0xF24F: 0x6AD1, //CJK UNIFIED IDEOGRAPH - 0xF250: 0x6AD9, //CJK UNIFIED IDEOGRAPH - 0xF251: 0x6ACB, //CJK UNIFIED IDEOGRAPH - 0xF252: 0x6ADF, //CJK UNIFIED IDEOGRAPH - 0xF253: 0x6ADC, //CJK UNIFIED IDEOGRAPH - 0xF254: 0x6AD0, //CJK UNIFIED IDEOGRAPH - 0xF255: 0x6AEB, //CJK UNIFIED IDEOGRAPH - 0xF256: 0x6ACF, //CJK UNIFIED IDEOGRAPH - 0xF257: 0x6ACD, //CJK UNIFIED IDEOGRAPH - 0xF258: 0x6ADE, //CJK UNIFIED IDEOGRAPH - 0xF259: 0x6B60, //CJK UNIFIED IDEOGRAPH - 0xF25A: 0x6BB0, //CJK UNIFIED IDEOGRAPH - 0xF25B: 0x6C0C, //CJK UNIFIED IDEOGRAPH - 0xF25C: 0x7019, //CJK UNIFIED IDEOGRAPH - 0xF25D: 0x7027, //CJK UNIFIED IDEOGRAPH - 0xF25E: 0x7020, //CJK UNIFIED IDEOGRAPH - 0xF25F: 0x7016, //CJK UNIFIED IDEOGRAPH - 0xF260: 0x702B, //CJK UNIFIED IDEOGRAPH - 0xF261: 0x7021, //CJK UNIFIED IDEOGRAPH - 0xF262: 0x7022, //CJK UNIFIED IDEOGRAPH - 0xF263: 0x7023, //CJK UNIFIED IDEOGRAPH - 0xF264: 0x7029, //CJK UNIFIED IDEOGRAPH - 0xF265: 0x7017, //CJK UNIFIED IDEOGRAPH - 0xF266: 0x7024, //CJK UNIFIED IDEOGRAPH - 0xF267: 0x701C, //CJK UNIFIED IDEOGRAPH - 0xF268: 0x702A, //CJK UNIFIED IDEOGRAPH - 0xF269: 0x720C, //CJK UNIFIED IDEOGRAPH - 0xF26A: 0x720A, //CJK UNIFIED IDEOGRAPH - 0xF26B: 0x7207, //CJK UNIFIED IDEOGRAPH - 0xF26C: 0x7202, //CJK UNIFIED IDEOGRAPH - 0xF26D: 0x7205, //CJK UNIFIED IDEOGRAPH - 0xF26E: 0x72A5, //CJK UNIFIED IDEOGRAPH - 0xF26F: 0x72A6, //CJK UNIFIED IDEOGRAPH - 0xF270: 0x72A4, //CJK UNIFIED IDEOGRAPH - 0xF271: 0x72A3, //CJK UNIFIED IDEOGRAPH - 0xF272: 0x72A1, //CJK UNIFIED IDEOGRAPH - 0xF273: 0x74CB, //CJK UNIFIED IDEOGRAPH - 0xF274: 0x74C5, //CJK UNIFIED IDEOGRAPH - 0xF275: 0x74B7, //CJK UNIFIED IDEOGRAPH - 0xF276: 0x74C3, //CJK UNIFIED IDEOGRAPH - 0xF277: 0x7516, //CJK UNIFIED IDEOGRAPH - 0xF278: 0x7660, //CJK UNIFIED IDEOGRAPH - 0xF279: 0x77C9, //CJK UNIFIED IDEOGRAPH - 0xF27A: 0x77CA, //CJK UNIFIED IDEOGRAPH - 0xF27B: 0x77C4, //CJK UNIFIED IDEOGRAPH - 0xF27C: 0x77F1, //CJK UNIFIED IDEOGRAPH - 0xF27D: 0x791D, //CJK UNIFIED IDEOGRAPH - 0xF27E: 0x791B, //CJK UNIFIED IDEOGRAPH - 0xF2A1: 0x7921, //CJK UNIFIED IDEOGRAPH - 0xF2A2: 0x791C, //CJK UNIFIED IDEOGRAPH - 0xF2A3: 0x7917, //CJK UNIFIED IDEOGRAPH - 0xF2A4: 0x791E, //CJK UNIFIED IDEOGRAPH - 0xF2A5: 0x79B0, //CJK UNIFIED IDEOGRAPH - 0xF2A6: 0x7A67, //CJK UNIFIED IDEOGRAPH - 0xF2A7: 0x7A68, //CJK UNIFIED IDEOGRAPH - 0xF2A8: 0x7C33, //CJK UNIFIED IDEOGRAPH - 0xF2A9: 0x7C3C, //CJK UNIFIED IDEOGRAPH - 0xF2AA: 0x7C39, //CJK UNIFIED IDEOGRAPH - 0xF2AB: 0x7C2C, //CJK UNIFIED IDEOGRAPH - 0xF2AC: 0x7C3B, //CJK UNIFIED IDEOGRAPH - 0xF2AD: 0x7CEC, //CJK UNIFIED IDEOGRAPH - 0xF2AE: 0x7CEA, //CJK UNIFIED IDEOGRAPH - 0xF2AF: 0x7E76, //CJK UNIFIED IDEOGRAPH - 0xF2B0: 0x7E75, //CJK UNIFIED IDEOGRAPH - 0xF2B1: 0x7E78, //CJK UNIFIED IDEOGRAPH - 0xF2B2: 0x7E70, //CJK UNIFIED IDEOGRAPH - 0xF2B3: 0x7E77, //CJK UNIFIED IDEOGRAPH - 0xF2B4: 0x7E6F, //CJK UNIFIED IDEOGRAPH - 0xF2B5: 0x7E7A, //CJK UNIFIED IDEOGRAPH - 0xF2B6: 0x7E72, //CJK UNIFIED IDEOGRAPH - 0xF2B7: 0x7E74, //CJK UNIFIED IDEOGRAPH - 0xF2B8: 0x7E68, //CJK UNIFIED IDEOGRAPH - 0xF2B9: 0x7F4B, //CJK UNIFIED IDEOGRAPH - 0xF2BA: 0x7F4A, //CJK UNIFIED IDEOGRAPH - 0xF2BB: 0x7F83, //CJK UNIFIED IDEOGRAPH - 0xF2BC: 0x7F86, //CJK UNIFIED IDEOGRAPH - 0xF2BD: 0x7FB7, //CJK UNIFIED IDEOGRAPH - 0xF2BE: 0x7FFD, //CJK UNIFIED IDEOGRAPH - 0xF2BF: 0x7FFE, //CJK UNIFIED IDEOGRAPH - 0xF2C0: 0x8078, //CJK UNIFIED IDEOGRAPH - 0xF2C1: 0x81D7, //CJK UNIFIED IDEOGRAPH - 0xF2C2: 0x81D5, //CJK UNIFIED IDEOGRAPH - 0xF2C3: 0x8264, //CJK UNIFIED IDEOGRAPH - 0xF2C4: 0x8261, //CJK UNIFIED IDEOGRAPH - 0xF2C5: 0x8263, //CJK UNIFIED IDEOGRAPH - 0xF2C6: 0x85EB, //CJK UNIFIED IDEOGRAPH - 0xF2C7: 0x85F1, //CJK UNIFIED IDEOGRAPH - 0xF2C8: 0x85ED, //CJK UNIFIED IDEOGRAPH - 0xF2C9: 0x85D9, //CJK UNIFIED IDEOGRAPH - 0xF2CA: 0x85E1, //CJK UNIFIED IDEOGRAPH - 0xF2CB: 0x85E8, //CJK UNIFIED IDEOGRAPH - 0xF2CC: 0x85DA, //CJK UNIFIED IDEOGRAPH - 0xF2CD: 0x85D7, //CJK UNIFIED IDEOGRAPH - 0xF2CE: 0x85EC, //CJK UNIFIED IDEOGRAPH - 0xF2CF: 0x85F2, //CJK UNIFIED IDEOGRAPH - 0xF2D0: 0x85F8, //CJK UNIFIED IDEOGRAPH - 0xF2D1: 0x85D8, //CJK UNIFIED IDEOGRAPH - 0xF2D2: 0x85DF, //CJK UNIFIED IDEOGRAPH - 0xF2D3: 0x85E3, //CJK UNIFIED IDEOGRAPH - 0xF2D4: 0x85DC, //CJK UNIFIED IDEOGRAPH - 0xF2D5: 0x85D1, //CJK UNIFIED IDEOGRAPH - 0xF2D6: 0x85F0, //CJK UNIFIED IDEOGRAPH - 0xF2D7: 0x85E6, //CJK UNIFIED IDEOGRAPH - 0xF2D8: 0x85EF, //CJK UNIFIED IDEOGRAPH - 0xF2D9: 0x85DE, //CJK UNIFIED IDEOGRAPH - 0xF2DA: 0x85E2, //CJK UNIFIED IDEOGRAPH - 0xF2DB: 0x8800, //CJK UNIFIED IDEOGRAPH - 0xF2DC: 0x87FA, //CJK UNIFIED IDEOGRAPH - 0xF2DD: 0x8803, //CJK UNIFIED IDEOGRAPH - 0xF2DE: 0x87F6, //CJK UNIFIED IDEOGRAPH - 0xF2DF: 0x87F7, //CJK UNIFIED IDEOGRAPH - 0xF2E0: 0x8809, //CJK UNIFIED IDEOGRAPH - 0xF2E1: 0x880C, //CJK UNIFIED IDEOGRAPH - 0xF2E2: 0x880B, //CJK UNIFIED IDEOGRAPH - 0xF2E3: 0x8806, //CJK UNIFIED IDEOGRAPH - 0xF2E4: 0x87FC, //CJK UNIFIED IDEOGRAPH - 0xF2E5: 0x8808, //CJK UNIFIED IDEOGRAPH - 0xF2E6: 0x87FF, //CJK UNIFIED IDEOGRAPH - 0xF2E7: 0x880A, //CJK UNIFIED IDEOGRAPH - 0xF2E8: 0x8802, //CJK UNIFIED IDEOGRAPH - 0xF2E9: 0x8962, //CJK UNIFIED IDEOGRAPH - 0xF2EA: 0x895A, //CJK UNIFIED IDEOGRAPH - 0xF2EB: 0x895B, //CJK UNIFIED IDEOGRAPH - 0xF2EC: 0x8957, //CJK UNIFIED IDEOGRAPH - 0xF2ED: 0x8961, //CJK UNIFIED IDEOGRAPH - 0xF2EE: 0x895C, //CJK UNIFIED IDEOGRAPH - 0xF2EF: 0x8958, //CJK UNIFIED IDEOGRAPH - 0xF2F0: 0x895D, //CJK UNIFIED IDEOGRAPH - 0xF2F1: 0x8959, //CJK UNIFIED IDEOGRAPH - 0xF2F2: 0x8988, //CJK UNIFIED IDEOGRAPH - 0xF2F3: 0x89B7, //CJK UNIFIED IDEOGRAPH - 0xF2F4: 0x89B6, //CJK UNIFIED IDEOGRAPH - 0xF2F5: 0x89F6, //CJK UNIFIED IDEOGRAPH - 0xF2F6: 0x8B50, //CJK UNIFIED IDEOGRAPH - 0xF2F7: 0x8B48, //CJK UNIFIED IDEOGRAPH - 0xF2F8: 0x8B4A, //CJK UNIFIED IDEOGRAPH - 0xF2F9: 0x8B40, //CJK UNIFIED IDEOGRAPH - 0xF2FA: 0x8B53, //CJK UNIFIED IDEOGRAPH - 0xF2FB: 0x8B56, //CJK UNIFIED IDEOGRAPH - 0xF2FC: 0x8B54, //CJK UNIFIED IDEOGRAPH - 0xF2FD: 0x8B4B, //CJK UNIFIED IDEOGRAPH - 0xF2FE: 0x8B55, //CJK UNIFIED IDEOGRAPH - 0xF340: 0x8B51, //CJK UNIFIED IDEOGRAPH - 0xF341: 0x8B42, //CJK UNIFIED IDEOGRAPH - 0xF342: 0x8B52, //CJK UNIFIED IDEOGRAPH - 0xF343: 0x8B57, //CJK UNIFIED IDEOGRAPH - 0xF344: 0x8C43, //CJK UNIFIED IDEOGRAPH - 0xF345: 0x8C77, //CJK UNIFIED IDEOGRAPH - 0xF346: 0x8C76, //CJK UNIFIED IDEOGRAPH - 0xF347: 0x8C9A, //CJK UNIFIED IDEOGRAPH - 0xF348: 0x8D06, //CJK UNIFIED IDEOGRAPH - 0xF349: 0x8D07, //CJK UNIFIED IDEOGRAPH - 0xF34A: 0x8D09, //CJK UNIFIED IDEOGRAPH - 0xF34B: 0x8DAC, //CJK UNIFIED IDEOGRAPH - 0xF34C: 0x8DAA, //CJK UNIFIED IDEOGRAPH - 0xF34D: 0x8DAD, //CJK UNIFIED IDEOGRAPH - 0xF34E: 0x8DAB, //CJK UNIFIED IDEOGRAPH - 0xF34F: 0x8E6D, //CJK UNIFIED IDEOGRAPH - 0xF350: 0x8E78, //CJK UNIFIED IDEOGRAPH - 0xF351: 0x8E73, //CJK UNIFIED IDEOGRAPH - 0xF352: 0x8E6A, //CJK UNIFIED IDEOGRAPH - 0xF353: 0x8E6F, //CJK UNIFIED IDEOGRAPH - 0xF354: 0x8E7B, //CJK UNIFIED IDEOGRAPH - 0xF355: 0x8EC2, //CJK UNIFIED IDEOGRAPH - 0xF356: 0x8F52, //CJK UNIFIED IDEOGRAPH - 0xF357: 0x8F51, //CJK UNIFIED IDEOGRAPH - 0xF358: 0x8F4F, //CJK UNIFIED IDEOGRAPH - 0xF359: 0x8F50, //CJK UNIFIED IDEOGRAPH - 0xF35A: 0x8F53, //CJK UNIFIED IDEOGRAPH - 0xF35B: 0x8FB4, //CJK UNIFIED IDEOGRAPH - 0xF35C: 0x9140, //CJK UNIFIED IDEOGRAPH - 0xF35D: 0x913F, //CJK UNIFIED IDEOGRAPH - 0xF35E: 0x91B0, //CJK UNIFIED IDEOGRAPH - 0xF35F: 0x91AD, //CJK UNIFIED IDEOGRAPH - 0xF360: 0x93DE, //CJK UNIFIED IDEOGRAPH - 0xF361: 0x93C7, //CJK UNIFIED IDEOGRAPH - 0xF362: 0x93CF, //CJK UNIFIED IDEOGRAPH - 0xF363: 0x93C2, //CJK UNIFIED IDEOGRAPH - 0xF364: 0x93DA, //CJK UNIFIED IDEOGRAPH - 0xF365: 0x93D0, //CJK UNIFIED IDEOGRAPH - 0xF366: 0x93F9, //CJK UNIFIED IDEOGRAPH - 0xF367: 0x93EC, //CJK UNIFIED IDEOGRAPH - 0xF368: 0x93CC, //CJK UNIFIED IDEOGRAPH - 0xF369: 0x93D9, //CJK UNIFIED IDEOGRAPH - 0xF36A: 0x93A9, //CJK UNIFIED IDEOGRAPH - 0xF36B: 0x93E6, //CJK UNIFIED IDEOGRAPH - 0xF36C: 0x93CA, //CJK UNIFIED IDEOGRAPH - 0xF36D: 0x93D4, //CJK UNIFIED IDEOGRAPH - 0xF36E: 0x93EE, //CJK UNIFIED IDEOGRAPH - 0xF36F: 0x93E3, //CJK UNIFIED IDEOGRAPH - 0xF370: 0x93D5, //CJK UNIFIED IDEOGRAPH - 0xF371: 0x93C4, //CJK UNIFIED IDEOGRAPH - 0xF372: 0x93CE, //CJK UNIFIED IDEOGRAPH - 0xF373: 0x93C0, //CJK UNIFIED IDEOGRAPH - 0xF374: 0x93D2, //CJK UNIFIED IDEOGRAPH - 0xF375: 0x93E7, //CJK UNIFIED IDEOGRAPH - 0xF376: 0x957D, //CJK UNIFIED IDEOGRAPH - 0xF377: 0x95DA, //CJK UNIFIED IDEOGRAPH - 0xF378: 0x95DB, //CJK UNIFIED IDEOGRAPH - 0xF379: 0x96E1, //CJK UNIFIED IDEOGRAPH - 0xF37A: 0x9729, //CJK UNIFIED IDEOGRAPH - 0xF37B: 0x972B, //CJK UNIFIED IDEOGRAPH - 0xF37C: 0x972C, //CJK UNIFIED IDEOGRAPH - 0xF37D: 0x9728, //CJK UNIFIED IDEOGRAPH - 0xF37E: 0x9726, //CJK UNIFIED IDEOGRAPH - 0xF3A1: 0x97B3, //CJK UNIFIED IDEOGRAPH - 0xF3A2: 0x97B7, //CJK UNIFIED IDEOGRAPH - 0xF3A3: 0x97B6, //CJK UNIFIED IDEOGRAPH - 0xF3A4: 0x97DD, //CJK UNIFIED IDEOGRAPH - 0xF3A5: 0x97DE, //CJK UNIFIED IDEOGRAPH - 0xF3A6: 0x97DF, //CJK UNIFIED IDEOGRAPH - 0xF3A7: 0x985C, //CJK UNIFIED IDEOGRAPH - 0xF3A8: 0x9859, //CJK UNIFIED IDEOGRAPH - 0xF3A9: 0x985D, //CJK UNIFIED IDEOGRAPH - 0xF3AA: 0x9857, //CJK UNIFIED IDEOGRAPH - 0xF3AB: 0x98BF, //CJK UNIFIED IDEOGRAPH - 0xF3AC: 0x98BD, //CJK UNIFIED IDEOGRAPH - 0xF3AD: 0x98BB, //CJK UNIFIED IDEOGRAPH - 0xF3AE: 0x98BE, //CJK UNIFIED IDEOGRAPH - 0xF3AF: 0x9948, //CJK UNIFIED IDEOGRAPH - 0xF3B0: 0x9947, //CJK UNIFIED IDEOGRAPH - 0xF3B1: 0x9943, //CJK UNIFIED IDEOGRAPH - 0xF3B2: 0x99A6, //CJK UNIFIED IDEOGRAPH - 0xF3B3: 0x99A7, //CJK UNIFIED IDEOGRAPH - 0xF3B4: 0x9A1A, //CJK UNIFIED IDEOGRAPH - 0xF3B5: 0x9A15, //CJK UNIFIED IDEOGRAPH - 0xF3B6: 0x9A25, //CJK UNIFIED IDEOGRAPH - 0xF3B7: 0x9A1D, //CJK UNIFIED IDEOGRAPH - 0xF3B8: 0x9A24, //CJK UNIFIED IDEOGRAPH - 0xF3B9: 0x9A1B, //CJK UNIFIED IDEOGRAPH - 0xF3BA: 0x9A22, //CJK UNIFIED IDEOGRAPH - 0xF3BB: 0x9A20, //CJK UNIFIED IDEOGRAPH - 0xF3BC: 0x9A27, //CJK UNIFIED IDEOGRAPH - 0xF3BD: 0x9A23, //CJK UNIFIED IDEOGRAPH - 0xF3BE: 0x9A1E, //CJK UNIFIED IDEOGRAPH - 0xF3BF: 0x9A1C, //CJK UNIFIED IDEOGRAPH - 0xF3C0: 0x9A14, //CJK UNIFIED IDEOGRAPH - 0xF3C1: 0x9AC2, //CJK UNIFIED IDEOGRAPH - 0xF3C2: 0x9B0B, //CJK UNIFIED IDEOGRAPH - 0xF3C3: 0x9B0A, //CJK UNIFIED IDEOGRAPH - 0xF3C4: 0x9B0E, //CJK UNIFIED IDEOGRAPH - 0xF3C5: 0x9B0C, //CJK UNIFIED IDEOGRAPH - 0xF3C6: 0x9B37, //CJK UNIFIED IDEOGRAPH - 0xF3C7: 0x9BEA, //CJK UNIFIED IDEOGRAPH - 0xF3C8: 0x9BEB, //CJK UNIFIED IDEOGRAPH - 0xF3C9: 0x9BE0, //CJK UNIFIED IDEOGRAPH - 0xF3CA: 0x9BDE, //CJK UNIFIED IDEOGRAPH - 0xF3CB: 0x9BE4, //CJK UNIFIED IDEOGRAPH - 0xF3CC: 0x9BE6, //CJK UNIFIED IDEOGRAPH - 0xF3CD: 0x9BE2, //CJK UNIFIED IDEOGRAPH - 0xF3CE: 0x9BF0, //CJK UNIFIED IDEOGRAPH - 0xF3CF: 0x9BD4, //CJK UNIFIED IDEOGRAPH - 0xF3D0: 0x9BD7, //CJK UNIFIED IDEOGRAPH - 0xF3D1: 0x9BEC, //CJK UNIFIED IDEOGRAPH - 0xF3D2: 0x9BDC, //CJK UNIFIED IDEOGRAPH - 0xF3D3: 0x9BD9, //CJK UNIFIED IDEOGRAPH - 0xF3D4: 0x9BE5, //CJK UNIFIED IDEOGRAPH - 0xF3D5: 0x9BD5, //CJK UNIFIED IDEOGRAPH - 0xF3D6: 0x9BE1, //CJK UNIFIED IDEOGRAPH - 0xF3D7: 0x9BDA, //CJK UNIFIED IDEOGRAPH - 0xF3D8: 0x9D77, //CJK UNIFIED IDEOGRAPH - 0xF3D9: 0x9D81, //CJK UNIFIED IDEOGRAPH - 0xF3DA: 0x9D8A, //CJK UNIFIED IDEOGRAPH - 0xF3DB: 0x9D84, //CJK UNIFIED IDEOGRAPH - 0xF3DC: 0x9D88, //CJK UNIFIED IDEOGRAPH - 0xF3DD: 0x9D71, //CJK UNIFIED IDEOGRAPH - 0xF3DE: 0x9D80, //CJK UNIFIED IDEOGRAPH - 0xF3DF: 0x9D78, //CJK UNIFIED IDEOGRAPH - 0xF3E0: 0x9D86, //CJK UNIFIED IDEOGRAPH - 0xF3E1: 0x9D8B, //CJK UNIFIED IDEOGRAPH - 0xF3E2: 0x9D8C, //CJK UNIFIED IDEOGRAPH - 0xF3E3: 0x9D7D, //CJK UNIFIED IDEOGRAPH - 0xF3E4: 0x9D6B, //CJK UNIFIED IDEOGRAPH - 0xF3E5: 0x9D74, //CJK UNIFIED IDEOGRAPH - 0xF3E6: 0x9D75, //CJK UNIFIED IDEOGRAPH - 0xF3E7: 0x9D70, //CJK UNIFIED IDEOGRAPH - 0xF3E8: 0x9D69, //CJK UNIFIED IDEOGRAPH - 0xF3E9: 0x9D85, //CJK UNIFIED IDEOGRAPH - 0xF3EA: 0x9D73, //CJK UNIFIED IDEOGRAPH - 0xF3EB: 0x9D7B, //CJK UNIFIED IDEOGRAPH - 0xF3EC: 0x9D82, //CJK UNIFIED IDEOGRAPH - 0xF3ED: 0x9D6F, //CJK UNIFIED IDEOGRAPH - 0xF3EE: 0x9D79, //CJK UNIFIED IDEOGRAPH - 0xF3EF: 0x9D7F, //CJK UNIFIED IDEOGRAPH - 0xF3F0: 0x9D87, //CJK UNIFIED IDEOGRAPH - 0xF3F1: 0x9D68, //CJK UNIFIED IDEOGRAPH - 0xF3F2: 0x9E94, //CJK UNIFIED IDEOGRAPH - 0xF3F3: 0x9E91, //CJK UNIFIED IDEOGRAPH - 0xF3F4: 0x9EC0, //CJK UNIFIED IDEOGRAPH - 0xF3F5: 0x9EFC, //CJK UNIFIED IDEOGRAPH - 0xF3F6: 0x9F2D, //CJK UNIFIED IDEOGRAPH - 0xF3F7: 0x9F40, //CJK UNIFIED IDEOGRAPH - 0xF3F8: 0x9F41, //CJK UNIFIED IDEOGRAPH - 0xF3F9: 0x9F4D, //CJK UNIFIED IDEOGRAPH - 0xF3FA: 0x9F56, //CJK UNIFIED IDEOGRAPH - 0xF3FB: 0x9F57, //CJK UNIFIED IDEOGRAPH - 0xF3FC: 0x9F58, //CJK UNIFIED IDEOGRAPH - 0xF3FD: 0x5337, //CJK UNIFIED IDEOGRAPH - 0xF3FE: 0x56B2, //CJK UNIFIED IDEOGRAPH - 0xF440: 0x56B5, //CJK UNIFIED IDEOGRAPH - 0xF441: 0x56B3, //CJK UNIFIED IDEOGRAPH - 0xF442: 0x58E3, //CJK UNIFIED IDEOGRAPH - 0xF443: 0x5B45, //CJK UNIFIED IDEOGRAPH - 0xF444: 0x5DC6, //CJK UNIFIED IDEOGRAPH - 0xF445: 0x5DC7, //CJK UNIFIED IDEOGRAPH - 0xF446: 0x5EEE, //CJK UNIFIED IDEOGRAPH - 0xF447: 0x5EEF, //CJK UNIFIED IDEOGRAPH - 0xF448: 0x5FC0, //CJK UNIFIED IDEOGRAPH - 0xF449: 0x5FC1, //CJK UNIFIED IDEOGRAPH - 0xF44A: 0x61F9, //CJK UNIFIED IDEOGRAPH - 0xF44B: 0x6517, //CJK UNIFIED IDEOGRAPH - 0xF44C: 0x6516, //CJK UNIFIED IDEOGRAPH - 0xF44D: 0x6515, //CJK UNIFIED IDEOGRAPH - 0xF44E: 0x6513, //CJK UNIFIED IDEOGRAPH - 0xF44F: 0x65DF, //CJK UNIFIED IDEOGRAPH - 0xF450: 0x66E8, //CJK UNIFIED IDEOGRAPH - 0xF451: 0x66E3, //CJK UNIFIED IDEOGRAPH - 0xF452: 0x66E4, //CJK UNIFIED IDEOGRAPH - 0xF453: 0x6AF3, //CJK UNIFIED IDEOGRAPH - 0xF454: 0x6AF0, //CJK UNIFIED IDEOGRAPH - 0xF455: 0x6AEA, //CJK UNIFIED IDEOGRAPH - 0xF456: 0x6AE8, //CJK UNIFIED IDEOGRAPH - 0xF457: 0x6AF9, //CJK UNIFIED IDEOGRAPH - 0xF458: 0x6AF1, //CJK UNIFIED IDEOGRAPH - 0xF459: 0x6AEE, //CJK UNIFIED IDEOGRAPH - 0xF45A: 0x6AEF, //CJK UNIFIED IDEOGRAPH - 0xF45B: 0x703C, //CJK UNIFIED IDEOGRAPH - 0xF45C: 0x7035, //CJK UNIFIED IDEOGRAPH - 0xF45D: 0x702F, //CJK UNIFIED IDEOGRAPH - 0xF45E: 0x7037, //CJK UNIFIED IDEOGRAPH - 0xF45F: 0x7034, //CJK UNIFIED IDEOGRAPH - 0xF460: 0x7031, //CJK UNIFIED IDEOGRAPH - 0xF461: 0x7042, //CJK UNIFIED IDEOGRAPH - 0xF462: 0x7038, //CJK UNIFIED IDEOGRAPH - 0xF463: 0x703F, //CJK UNIFIED IDEOGRAPH - 0xF464: 0x703A, //CJK UNIFIED IDEOGRAPH - 0xF465: 0x7039, //CJK UNIFIED IDEOGRAPH - 0xF466: 0x7040, //CJK UNIFIED IDEOGRAPH - 0xF467: 0x703B, //CJK UNIFIED IDEOGRAPH - 0xF468: 0x7033, //CJK UNIFIED IDEOGRAPH - 0xF469: 0x7041, //CJK UNIFIED IDEOGRAPH - 0xF46A: 0x7213, //CJK UNIFIED IDEOGRAPH - 0xF46B: 0x7214, //CJK UNIFIED IDEOGRAPH - 0xF46C: 0x72A8, //CJK UNIFIED IDEOGRAPH - 0xF46D: 0x737D, //CJK UNIFIED IDEOGRAPH - 0xF46E: 0x737C, //CJK UNIFIED IDEOGRAPH - 0xF46F: 0x74BA, //CJK UNIFIED IDEOGRAPH - 0xF470: 0x76AB, //CJK UNIFIED IDEOGRAPH - 0xF471: 0x76AA, //CJK UNIFIED IDEOGRAPH - 0xF472: 0x76BE, //CJK UNIFIED IDEOGRAPH - 0xF473: 0x76ED, //CJK UNIFIED IDEOGRAPH - 0xF474: 0x77CC, //CJK UNIFIED IDEOGRAPH - 0xF475: 0x77CE, //CJK UNIFIED IDEOGRAPH - 0xF476: 0x77CF, //CJK UNIFIED IDEOGRAPH - 0xF477: 0x77CD, //CJK UNIFIED IDEOGRAPH - 0xF478: 0x77F2, //CJK UNIFIED IDEOGRAPH - 0xF479: 0x7925, //CJK UNIFIED IDEOGRAPH - 0xF47A: 0x7923, //CJK UNIFIED IDEOGRAPH - 0xF47B: 0x7927, //CJK UNIFIED IDEOGRAPH - 0xF47C: 0x7928, //CJK UNIFIED IDEOGRAPH - 0xF47D: 0x7924, //CJK UNIFIED IDEOGRAPH - 0xF47E: 0x7929, //CJK UNIFIED IDEOGRAPH - 0xF4A1: 0x79B2, //CJK UNIFIED IDEOGRAPH - 0xF4A2: 0x7A6E, //CJK UNIFIED IDEOGRAPH - 0xF4A3: 0x7A6C, //CJK UNIFIED IDEOGRAPH - 0xF4A4: 0x7A6D, //CJK UNIFIED IDEOGRAPH - 0xF4A5: 0x7AF7, //CJK UNIFIED IDEOGRAPH - 0xF4A6: 0x7C49, //CJK UNIFIED IDEOGRAPH - 0xF4A7: 0x7C48, //CJK UNIFIED IDEOGRAPH - 0xF4A8: 0x7C4A, //CJK UNIFIED IDEOGRAPH - 0xF4A9: 0x7C47, //CJK UNIFIED IDEOGRAPH - 0xF4AA: 0x7C45, //CJK UNIFIED IDEOGRAPH - 0xF4AB: 0x7CEE, //CJK UNIFIED IDEOGRAPH - 0xF4AC: 0x7E7B, //CJK UNIFIED IDEOGRAPH - 0xF4AD: 0x7E7E, //CJK UNIFIED IDEOGRAPH - 0xF4AE: 0x7E81, //CJK UNIFIED IDEOGRAPH - 0xF4AF: 0x7E80, //CJK UNIFIED IDEOGRAPH - 0xF4B0: 0x7FBA, //CJK UNIFIED IDEOGRAPH - 0xF4B1: 0x7FFF, //CJK UNIFIED IDEOGRAPH - 0xF4B2: 0x8079, //CJK UNIFIED IDEOGRAPH - 0xF4B3: 0x81DB, //CJK UNIFIED IDEOGRAPH - 0xF4B4: 0x81D9, //CJK UNIFIED IDEOGRAPH - 0xF4B5: 0x820B, //CJK UNIFIED IDEOGRAPH - 0xF4B6: 0x8268, //CJK UNIFIED IDEOGRAPH - 0xF4B7: 0x8269, //CJK UNIFIED IDEOGRAPH - 0xF4B8: 0x8622, //CJK UNIFIED IDEOGRAPH - 0xF4B9: 0x85FF, //CJK UNIFIED IDEOGRAPH - 0xF4BA: 0x8601, //CJK UNIFIED IDEOGRAPH - 0xF4BB: 0x85FE, //CJK UNIFIED IDEOGRAPH - 0xF4BC: 0x861B, //CJK UNIFIED IDEOGRAPH - 0xF4BD: 0x8600, //CJK UNIFIED IDEOGRAPH - 0xF4BE: 0x85F6, //CJK UNIFIED IDEOGRAPH - 0xF4BF: 0x8604, //CJK UNIFIED IDEOGRAPH - 0xF4C0: 0x8609, //CJK UNIFIED IDEOGRAPH - 0xF4C1: 0x8605, //CJK UNIFIED IDEOGRAPH - 0xF4C2: 0x860C, //CJK UNIFIED IDEOGRAPH - 0xF4C3: 0x85FD, //CJK UNIFIED IDEOGRAPH - 0xF4C4: 0x8819, //CJK UNIFIED IDEOGRAPH - 0xF4C5: 0x8810, //CJK UNIFIED IDEOGRAPH - 0xF4C6: 0x8811, //CJK UNIFIED IDEOGRAPH - 0xF4C7: 0x8817, //CJK UNIFIED IDEOGRAPH - 0xF4C8: 0x8813, //CJK UNIFIED IDEOGRAPH - 0xF4C9: 0x8816, //CJK UNIFIED IDEOGRAPH - 0xF4CA: 0x8963, //CJK UNIFIED IDEOGRAPH - 0xF4CB: 0x8966, //CJK UNIFIED IDEOGRAPH - 0xF4CC: 0x89B9, //CJK UNIFIED IDEOGRAPH - 0xF4CD: 0x89F7, //CJK UNIFIED IDEOGRAPH - 0xF4CE: 0x8B60, //CJK UNIFIED IDEOGRAPH - 0xF4CF: 0x8B6A, //CJK UNIFIED IDEOGRAPH - 0xF4D0: 0x8B5D, //CJK UNIFIED IDEOGRAPH - 0xF4D1: 0x8B68, //CJK UNIFIED IDEOGRAPH - 0xF4D2: 0x8B63, //CJK UNIFIED IDEOGRAPH - 0xF4D3: 0x8B65, //CJK UNIFIED IDEOGRAPH - 0xF4D4: 0x8B67, //CJK UNIFIED IDEOGRAPH - 0xF4D5: 0x8B6D, //CJK UNIFIED IDEOGRAPH - 0xF4D6: 0x8DAE, //CJK UNIFIED IDEOGRAPH - 0xF4D7: 0x8E86, //CJK UNIFIED IDEOGRAPH - 0xF4D8: 0x8E88, //CJK UNIFIED IDEOGRAPH - 0xF4D9: 0x8E84, //CJK UNIFIED IDEOGRAPH - 0xF4DA: 0x8F59, //CJK UNIFIED IDEOGRAPH - 0xF4DB: 0x8F56, //CJK UNIFIED IDEOGRAPH - 0xF4DC: 0x8F57, //CJK UNIFIED IDEOGRAPH - 0xF4DD: 0x8F55, //CJK UNIFIED IDEOGRAPH - 0xF4DE: 0x8F58, //CJK UNIFIED IDEOGRAPH - 0xF4DF: 0x8F5A, //CJK UNIFIED IDEOGRAPH - 0xF4E0: 0x908D, //CJK UNIFIED IDEOGRAPH - 0xF4E1: 0x9143, //CJK UNIFIED IDEOGRAPH - 0xF4E2: 0x9141, //CJK UNIFIED IDEOGRAPH - 0xF4E3: 0x91B7, //CJK UNIFIED IDEOGRAPH - 0xF4E4: 0x91B5, //CJK UNIFIED IDEOGRAPH - 0xF4E5: 0x91B2, //CJK UNIFIED IDEOGRAPH - 0xF4E6: 0x91B3, //CJK UNIFIED IDEOGRAPH - 0xF4E7: 0x940B, //CJK UNIFIED IDEOGRAPH - 0xF4E8: 0x9413, //CJK UNIFIED IDEOGRAPH - 0xF4E9: 0x93FB, //CJK UNIFIED IDEOGRAPH - 0xF4EA: 0x9420, //CJK UNIFIED IDEOGRAPH - 0xF4EB: 0x940F, //CJK UNIFIED IDEOGRAPH - 0xF4EC: 0x9414, //CJK UNIFIED IDEOGRAPH - 0xF4ED: 0x93FE, //CJK UNIFIED IDEOGRAPH - 0xF4EE: 0x9415, //CJK UNIFIED IDEOGRAPH - 0xF4EF: 0x9410, //CJK UNIFIED IDEOGRAPH - 0xF4F0: 0x9428, //CJK UNIFIED IDEOGRAPH - 0xF4F1: 0x9419, //CJK UNIFIED IDEOGRAPH - 0xF4F2: 0x940D, //CJK UNIFIED IDEOGRAPH - 0xF4F3: 0x93F5, //CJK UNIFIED IDEOGRAPH - 0xF4F4: 0x9400, //CJK UNIFIED IDEOGRAPH - 0xF4F5: 0x93F7, //CJK UNIFIED IDEOGRAPH - 0xF4F6: 0x9407, //CJK UNIFIED IDEOGRAPH - 0xF4F7: 0x940E, //CJK UNIFIED IDEOGRAPH - 0xF4F8: 0x9416, //CJK UNIFIED IDEOGRAPH - 0xF4F9: 0x9412, //CJK UNIFIED IDEOGRAPH - 0xF4FA: 0x93FA, //CJK UNIFIED IDEOGRAPH - 0xF4FB: 0x9409, //CJK UNIFIED IDEOGRAPH - 0xF4FC: 0x93F8, //CJK UNIFIED IDEOGRAPH - 0xF4FD: 0x940A, //CJK UNIFIED IDEOGRAPH - 0xF4FE: 0x93FF, //CJK UNIFIED IDEOGRAPH - 0xF540: 0x93FC, //CJK UNIFIED IDEOGRAPH - 0xF541: 0x940C, //CJK UNIFIED IDEOGRAPH - 0xF542: 0x93F6, //CJK UNIFIED IDEOGRAPH - 0xF543: 0x9411, //CJK UNIFIED IDEOGRAPH - 0xF544: 0x9406, //CJK UNIFIED IDEOGRAPH - 0xF545: 0x95DE, //CJK UNIFIED IDEOGRAPH - 0xF546: 0x95E0, //CJK UNIFIED IDEOGRAPH - 0xF547: 0x95DF, //CJK UNIFIED IDEOGRAPH - 0xF548: 0x972E, //CJK UNIFIED IDEOGRAPH - 0xF549: 0x972F, //CJK UNIFIED IDEOGRAPH - 0xF54A: 0x97B9, //CJK UNIFIED IDEOGRAPH - 0xF54B: 0x97BB, //CJK UNIFIED IDEOGRAPH - 0xF54C: 0x97FD, //CJK UNIFIED IDEOGRAPH - 0xF54D: 0x97FE, //CJK UNIFIED IDEOGRAPH - 0xF54E: 0x9860, //CJK UNIFIED IDEOGRAPH - 0xF54F: 0x9862, //CJK UNIFIED IDEOGRAPH - 0xF550: 0x9863, //CJK UNIFIED IDEOGRAPH - 0xF551: 0x985F, //CJK UNIFIED IDEOGRAPH - 0xF552: 0x98C1, //CJK UNIFIED IDEOGRAPH - 0xF553: 0x98C2, //CJK UNIFIED IDEOGRAPH - 0xF554: 0x9950, //CJK UNIFIED IDEOGRAPH - 0xF555: 0x994E, //CJK UNIFIED IDEOGRAPH - 0xF556: 0x9959, //CJK UNIFIED IDEOGRAPH - 0xF557: 0x994C, //CJK UNIFIED IDEOGRAPH - 0xF558: 0x994B, //CJK UNIFIED IDEOGRAPH - 0xF559: 0x9953, //CJK UNIFIED IDEOGRAPH - 0xF55A: 0x9A32, //CJK UNIFIED IDEOGRAPH - 0xF55B: 0x9A34, //CJK UNIFIED IDEOGRAPH - 0xF55C: 0x9A31, //CJK UNIFIED IDEOGRAPH - 0xF55D: 0x9A2C, //CJK UNIFIED IDEOGRAPH - 0xF55E: 0x9A2A, //CJK UNIFIED IDEOGRAPH - 0xF55F: 0x9A36, //CJK UNIFIED IDEOGRAPH - 0xF560: 0x9A29, //CJK UNIFIED IDEOGRAPH - 0xF561: 0x9A2E, //CJK UNIFIED IDEOGRAPH - 0xF562: 0x9A38, //CJK UNIFIED IDEOGRAPH - 0xF563: 0x9A2D, //CJK UNIFIED IDEOGRAPH - 0xF564: 0x9AC7, //CJK UNIFIED IDEOGRAPH - 0xF565: 0x9ACA, //CJK UNIFIED IDEOGRAPH - 0xF566: 0x9AC6, //CJK UNIFIED IDEOGRAPH - 0xF567: 0x9B10, //CJK UNIFIED IDEOGRAPH - 0xF568: 0x9B12, //CJK UNIFIED IDEOGRAPH - 0xF569: 0x9B11, //CJK UNIFIED IDEOGRAPH - 0xF56A: 0x9C0B, //CJK UNIFIED IDEOGRAPH - 0xF56B: 0x9C08, //CJK UNIFIED IDEOGRAPH - 0xF56C: 0x9BF7, //CJK UNIFIED IDEOGRAPH - 0xF56D: 0x9C05, //CJK UNIFIED IDEOGRAPH - 0xF56E: 0x9C12, //CJK UNIFIED IDEOGRAPH - 0xF56F: 0x9BF8, //CJK UNIFIED IDEOGRAPH - 0xF570: 0x9C40, //CJK UNIFIED IDEOGRAPH - 0xF571: 0x9C07, //CJK UNIFIED IDEOGRAPH - 0xF572: 0x9C0E, //CJK UNIFIED IDEOGRAPH - 0xF573: 0x9C06, //CJK UNIFIED IDEOGRAPH - 0xF574: 0x9C17, //CJK UNIFIED IDEOGRAPH - 0xF575: 0x9C14, //CJK UNIFIED IDEOGRAPH - 0xF576: 0x9C09, //CJK UNIFIED IDEOGRAPH - 0xF577: 0x9D9F, //CJK UNIFIED IDEOGRAPH - 0xF578: 0x9D99, //CJK UNIFIED IDEOGRAPH - 0xF579: 0x9DA4, //CJK UNIFIED IDEOGRAPH - 0xF57A: 0x9D9D, //CJK UNIFIED IDEOGRAPH - 0xF57B: 0x9D92, //CJK UNIFIED IDEOGRAPH - 0xF57C: 0x9D98, //CJK UNIFIED IDEOGRAPH - 0xF57D: 0x9D90, //CJK UNIFIED IDEOGRAPH - 0xF57E: 0x9D9B, //CJK UNIFIED IDEOGRAPH - 0xF5A1: 0x9DA0, //CJK UNIFIED IDEOGRAPH - 0xF5A2: 0x9D94, //CJK UNIFIED IDEOGRAPH - 0xF5A3: 0x9D9C, //CJK UNIFIED IDEOGRAPH - 0xF5A4: 0x9DAA, //CJK UNIFIED IDEOGRAPH - 0xF5A5: 0x9D97, //CJK UNIFIED IDEOGRAPH - 0xF5A6: 0x9DA1, //CJK UNIFIED IDEOGRAPH - 0xF5A7: 0x9D9A, //CJK UNIFIED IDEOGRAPH - 0xF5A8: 0x9DA2, //CJK UNIFIED IDEOGRAPH - 0xF5A9: 0x9DA8, //CJK UNIFIED IDEOGRAPH - 0xF5AA: 0x9D9E, //CJK UNIFIED IDEOGRAPH - 0xF5AB: 0x9DA3, //CJK UNIFIED IDEOGRAPH - 0xF5AC: 0x9DBF, //CJK UNIFIED IDEOGRAPH - 0xF5AD: 0x9DA9, //CJK UNIFIED IDEOGRAPH - 0xF5AE: 0x9D96, //CJK UNIFIED IDEOGRAPH - 0xF5AF: 0x9DA6, //CJK UNIFIED IDEOGRAPH - 0xF5B0: 0x9DA7, //CJK UNIFIED IDEOGRAPH - 0xF5B1: 0x9E99, //CJK UNIFIED IDEOGRAPH - 0xF5B2: 0x9E9B, //CJK UNIFIED IDEOGRAPH - 0xF5B3: 0x9E9A, //CJK UNIFIED IDEOGRAPH - 0xF5B4: 0x9EE5, //CJK UNIFIED IDEOGRAPH - 0xF5B5: 0x9EE4, //CJK UNIFIED IDEOGRAPH - 0xF5B6: 0x9EE7, //CJK UNIFIED IDEOGRAPH - 0xF5B7: 0x9EE6, //CJK UNIFIED IDEOGRAPH - 0xF5B8: 0x9F30, //CJK UNIFIED IDEOGRAPH - 0xF5B9: 0x9F2E, //CJK UNIFIED IDEOGRAPH - 0xF5BA: 0x9F5B, //CJK UNIFIED IDEOGRAPH - 0xF5BB: 0x9F60, //CJK UNIFIED IDEOGRAPH - 0xF5BC: 0x9F5E, //CJK UNIFIED IDEOGRAPH - 0xF5BD: 0x9F5D, //CJK UNIFIED IDEOGRAPH - 0xF5BE: 0x9F59, //CJK UNIFIED IDEOGRAPH - 0xF5BF: 0x9F91, //CJK UNIFIED IDEOGRAPH - 0xF5C0: 0x513A, //CJK UNIFIED IDEOGRAPH - 0xF5C1: 0x5139, //CJK UNIFIED IDEOGRAPH - 0xF5C2: 0x5298, //CJK UNIFIED IDEOGRAPH - 0xF5C3: 0x5297, //CJK UNIFIED IDEOGRAPH - 0xF5C4: 0x56C3, //CJK UNIFIED IDEOGRAPH - 0xF5C5: 0x56BD, //CJK UNIFIED IDEOGRAPH - 0xF5C6: 0x56BE, //CJK UNIFIED IDEOGRAPH - 0xF5C7: 0x5B48, //CJK UNIFIED IDEOGRAPH - 0xF5C8: 0x5B47, //CJK UNIFIED IDEOGRAPH - 0xF5C9: 0x5DCB, //CJK UNIFIED IDEOGRAPH - 0xF5CA: 0x5DCF, //CJK UNIFIED IDEOGRAPH - 0xF5CB: 0x5EF1, //CJK UNIFIED IDEOGRAPH - 0xF5CC: 0x61FD, //CJK UNIFIED IDEOGRAPH - 0xF5CD: 0x651B, //CJK UNIFIED IDEOGRAPH - 0xF5CE: 0x6B02, //CJK UNIFIED IDEOGRAPH - 0xF5CF: 0x6AFC, //CJK UNIFIED IDEOGRAPH - 0xF5D0: 0x6B03, //CJK UNIFIED IDEOGRAPH - 0xF5D1: 0x6AF8, //CJK UNIFIED IDEOGRAPH - 0xF5D2: 0x6B00, //CJK UNIFIED IDEOGRAPH - 0xF5D3: 0x7043, //CJK UNIFIED IDEOGRAPH - 0xF5D4: 0x7044, //CJK UNIFIED IDEOGRAPH - 0xF5D5: 0x704A, //CJK UNIFIED IDEOGRAPH - 0xF5D6: 0x7048, //CJK UNIFIED IDEOGRAPH - 0xF5D7: 0x7049, //CJK UNIFIED IDEOGRAPH - 0xF5D8: 0x7045, //CJK UNIFIED IDEOGRAPH - 0xF5D9: 0x7046, //CJK UNIFIED IDEOGRAPH - 0xF5DA: 0x721D, //CJK UNIFIED IDEOGRAPH - 0xF5DB: 0x721A, //CJK UNIFIED IDEOGRAPH - 0xF5DC: 0x7219, //CJK UNIFIED IDEOGRAPH - 0xF5DD: 0x737E, //CJK UNIFIED IDEOGRAPH - 0xF5DE: 0x7517, //CJK UNIFIED IDEOGRAPH - 0xF5DF: 0x766A, //CJK UNIFIED IDEOGRAPH - 0xF5E0: 0x77D0, //CJK UNIFIED IDEOGRAPH - 0xF5E1: 0x792D, //CJK UNIFIED IDEOGRAPH - 0xF5E2: 0x7931, //CJK UNIFIED IDEOGRAPH - 0xF5E3: 0x792F, //CJK UNIFIED IDEOGRAPH - 0xF5E4: 0x7C54, //CJK UNIFIED IDEOGRAPH - 0xF5E5: 0x7C53, //CJK UNIFIED IDEOGRAPH - 0xF5E6: 0x7CF2, //CJK UNIFIED IDEOGRAPH - 0xF5E7: 0x7E8A, //CJK UNIFIED IDEOGRAPH - 0xF5E8: 0x7E87, //CJK UNIFIED IDEOGRAPH - 0xF5E9: 0x7E88, //CJK UNIFIED IDEOGRAPH - 0xF5EA: 0x7E8B, //CJK UNIFIED IDEOGRAPH - 0xF5EB: 0x7E86, //CJK UNIFIED IDEOGRAPH - 0xF5EC: 0x7E8D, //CJK UNIFIED IDEOGRAPH - 0xF5ED: 0x7F4D, //CJK UNIFIED IDEOGRAPH - 0xF5EE: 0x7FBB, //CJK UNIFIED IDEOGRAPH - 0xF5EF: 0x8030, //CJK UNIFIED IDEOGRAPH - 0xF5F0: 0x81DD, //CJK UNIFIED IDEOGRAPH - 0xF5F1: 0x8618, //CJK UNIFIED IDEOGRAPH - 0xF5F2: 0x862A, //CJK UNIFIED IDEOGRAPH - 0xF5F3: 0x8626, //CJK UNIFIED IDEOGRAPH - 0xF5F4: 0x861F, //CJK UNIFIED IDEOGRAPH - 0xF5F5: 0x8623, //CJK UNIFIED IDEOGRAPH - 0xF5F6: 0x861C, //CJK UNIFIED IDEOGRAPH - 0xF5F7: 0x8619, //CJK UNIFIED IDEOGRAPH - 0xF5F8: 0x8627, //CJK UNIFIED IDEOGRAPH - 0xF5F9: 0x862E, //CJK UNIFIED IDEOGRAPH - 0xF5FA: 0x8621, //CJK UNIFIED IDEOGRAPH - 0xF5FB: 0x8620, //CJK UNIFIED IDEOGRAPH - 0xF5FC: 0x8629, //CJK UNIFIED IDEOGRAPH - 0xF5FD: 0x861E, //CJK UNIFIED IDEOGRAPH - 0xF5FE: 0x8625, //CJK UNIFIED IDEOGRAPH - 0xF640: 0x8829, //CJK UNIFIED IDEOGRAPH - 0xF641: 0x881D, //CJK UNIFIED IDEOGRAPH - 0xF642: 0x881B, //CJK UNIFIED IDEOGRAPH - 0xF643: 0x8820, //CJK UNIFIED IDEOGRAPH - 0xF644: 0x8824, //CJK UNIFIED IDEOGRAPH - 0xF645: 0x881C, //CJK UNIFIED IDEOGRAPH - 0xF646: 0x882B, //CJK UNIFIED IDEOGRAPH - 0xF647: 0x884A, //CJK UNIFIED IDEOGRAPH - 0xF648: 0x896D, //CJK UNIFIED IDEOGRAPH - 0xF649: 0x8969, //CJK UNIFIED IDEOGRAPH - 0xF64A: 0x896E, //CJK UNIFIED IDEOGRAPH - 0xF64B: 0x896B, //CJK UNIFIED IDEOGRAPH - 0xF64C: 0x89FA, //CJK UNIFIED IDEOGRAPH - 0xF64D: 0x8B79, //CJK UNIFIED IDEOGRAPH - 0xF64E: 0x8B78, //CJK UNIFIED IDEOGRAPH - 0xF64F: 0x8B45, //CJK UNIFIED IDEOGRAPH - 0xF650: 0x8B7A, //CJK UNIFIED IDEOGRAPH - 0xF651: 0x8B7B, //CJK UNIFIED IDEOGRAPH - 0xF652: 0x8D10, //CJK UNIFIED IDEOGRAPH - 0xF653: 0x8D14, //CJK UNIFIED IDEOGRAPH - 0xF654: 0x8DAF, //CJK UNIFIED IDEOGRAPH - 0xF655: 0x8E8E, //CJK UNIFIED IDEOGRAPH - 0xF656: 0x8E8C, //CJK UNIFIED IDEOGRAPH - 0xF657: 0x8F5E, //CJK UNIFIED IDEOGRAPH - 0xF658: 0x8F5B, //CJK UNIFIED IDEOGRAPH - 0xF659: 0x8F5D, //CJK UNIFIED IDEOGRAPH - 0xF65A: 0x9146, //CJK UNIFIED IDEOGRAPH - 0xF65B: 0x9144, //CJK UNIFIED IDEOGRAPH - 0xF65C: 0x9145, //CJK UNIFIED IDEOGRAPH - 0xF65D: 0x91B9, //CJK UNIFIED IDEOGRAPH - 0xF65E: 0x943F, //CJK UNIFIED IDEOGRAPH - 0xF65F: 0x943B, //CJK UNIFIED IDEOGRAPH - 0xF660: 0x9436, //CJK UNIFIED IDEOGRAPH - 0xF661: 0x9429, //CJK UNIFIED IDEOGRAPH - 0xF662: 0x943D, //CJK UNIFIED IDEOGRAPH - 0xF663: 0x943C, //CJK UNIFIED IDEOGRAPH - 0xF664: 0x9430, //CJK UNIFIED IDEOGRAPH - 0xF665: 0x9439, //CJK UNIFIED IDEOGRAPH - 0xF666: 0x942A, //CJK UNIFIED IDEOGRAPH - 0xF667: 0x9437, //CJK UNIFIED IDEOGRAPH - 0xF668: 0x942C, //CJK UNIFIED IDEOGRAPH - 0xF669: 0x9440, //CJK UNIFIED IDEOGRAPH - 0xF66A: 0x9431, //CJK UNIFIED IDEOGRAPH - 0xF66B: 0x95E5, //CJK UNIFIED IDEOGRAPH - 0xF66C: 0x95E4, //CJK UNIFIED IDEOGRAPH - 0xF66D: 0x95E3, //CJK UNIFIED IDEOGRAPH - 0xF66E: 0x9735, //CJK UNIFIED IDEOGRAPH - 0xF66F: 0x973A, //CJK UNIFIED IDEOGRAPH - 0xF670: 0x97BF, //CJK UNIFIED IDEOGRAPH - 0xF671: 0x97E1, //CJK UNIFIED IDEOGRAPH - 0xF672: 0x9864, //CJK UNIFIED IDEOGRAPH - 0xF673: 0x98C9, //CJK UNIFIED IDEOGRAPH - 0xF674: 0x98C6, //CJK UNIFIED IDEOGRAPH - 0xF675: 0x98C0, //CJK UNIFIED IDEOGRAPH - 0xF676: 0x9958, //CJK UNIFIED IDEOGRAPH - 0xF677: 0x9956, //CJK UNIFIED IDEOGRAPH - 0xF678: 0x9A39, //CJK UNIFIED IDEOGRAPH - 0xF679: 0x9A3D, //CJK UNIFIED IDEOGRAPH - 0xF67A: 0x9A46, //CJK UNIFIED IDEOGRAPH - 0xF67B: 0x9A44, //CJK UNIFIED IDEOGRAPH - 0xF67C: 0x9A42, //CJK UNIFIED IDEOGRAPH - 0xF67D: 0x9A41, //CJK UNIFIED IDEOGRAPH - 0xF67E: 0x9A3A, //CJK UNIFIED IDEOGRAPH - 0xF6A1: 0x9A3F, //CJK UNIFIED IDEOGRAPH - 0xF6A2: 0x9ACD, //CJK UNIFIED IDEOGRAPH - 0xF6A3: 0x9B15, //CJK UNIFIED IDEOGRAPH - 0xF6A4: 0x9B17, //CJK UNIFIED IDEOGRAPH - 0xF6A5: 0x9B18, //CJK UNIFIED IDEOGRAPH - 0xF6A6: 0x9B16, //CJK UNIFIED IDEOGRAPH - 0xF6A7: 0x9B3A, //CJK UNIFIED IDEOGRAPH - 0xF6A8: 0x9B52, //CJK UNIFIED IDEOGRAPH - 0xF6A9: 0x9C2B, //CJK UNIFIED IDEOGRAPH - 0xF6AA: 0x9C1D, //CJK UNIFIED IDEOGRAPH - 0xF6AB: 0x9C1C, //CJK UNIFIED IDEOGRAPH - 0xF6AC: 0x9C2C, //CJK UNIFIED IDEOGRAPH - 0xF6AD: 0x9C23, //CJK UNIFIED IDEOGRAPH - 0xF6AE: 0x9C28, //CJK UNIFIED IDEOGRAPH - 0xF6AF: 0x9C29, //CJK UNIFIED IDEOGRAPH - 0xF6B0: 0x9C24, //CJK UNIFIED IDEOGRAPH - 0xF6B1: 0x9C21, //CJK UNIFIED IDEOGRAPH - 0xF6B2: 0x9DB7, //CJK UNIFIED IDEOGRAPH - 0xF6B3: 0x9DB6, //CJK UNIFIED IDEOGRAPH - 0xF6B4: 0x9DBC, //CJK UNIFIED IDEOGRAPH - 0xF6B5: 0x9DC1, //CJK UNIFIED IDEOGRAPH - 0xF6B6: 0x9DC7, //CJK UNIFIED IDEOGRAPH - 0xF6B7: 0x9DCA, //CJK UNIFIED IDEOGRAPH - 0xF6B8: 0x9DCF, //CJK UNIFIED IDEOGRAPH - 0xF6B9: 0x9DBE, //CJK UNIFIED IDEOGRAPH - 0xF6BA: 0x9DC5, //CJK UNIFIED IDEOGRAPH - 0xF6BB: 0x9DC3, //CJK UNIFIED IDEOGRAPH - 0xF6BC: 0x9DBB, //CJK UNIFIED IDEOGRAPH - 0xF6BD: 0x9DB5, //CJK UNIFIED IDEOGRAPH - 0xF6BE: 0x9DCE, //CJK UNIFIED IDEOGRAPH - 0xF6BF: 0x9DB9, //CJK UNIFIED IDEOGRAPH - 0xF6C0: 0x9DBA, //CJK UNIFIED IDEOGRAPH - 0xF6C1: 0x9DAC, //CJK UNIFIED IDEOGRAPH - 0xF6C2: 0x9DC8, //CJK UNIFIED IDEOGRAPH - 0xF6C3: 0x9DB1, //CJK UNIFIED IDEOGRAPH - 0xF6C4: 0x9DAD, //CJK UNIFIED IDEOGRAPH - 0xF6C5: 0x9DCC, //CJK UNIFIED IDEOGRAPH - 0xF6C6: 0x9DB3, //CJK UNIFIED IDEOGRAPH - 0xF6C7: 0x9DCD, //CJK UNIFIED IDEOGRAPH - 0xF6C8: 0x9DB2, //CJK UNIFIED IDEOGRAPH - 0xF6C9: 0x9E7A, //CJK UNIFIED IDEOGRAPH - 0xF6CA: 0x9E9C, //CJK UNIFIED IDEOGRAPH - 0xF6CB: 0x9EEB, //CJK UNIFIED IDEOGRAPH - 0xF6CC: 0x9EEE, //CJK UNIFIED IDEOGRAPH - 0xF6CD: 0x9EED, //CJK UNIFIED IDEOGRAPH - 0xF6CE: 0x9F1B, //CJK UNIFIED IDEOGRAPH - 0xF6CF: 0x9F18, //CJK UNIFIED IDEOGRAPH - 0xF6D0: 0x9F1A, //CJK UNIFIED IDEOGRAPH - 0xF6D1: 0x9F31, //CJK UNIFIED IDEOGRAPH - 0xF6D2: 0x9F4E, //CJK UNIFIED IDEOGRAPH - 0xF6D3: 0x9F65, //CJK UNIFIED IDEOGRAPH - 0xF6D4: 0x9F64, //CJK UNIFIED IDEOGRAPH - 0xF6D5: 0x9F92, //CJK UNIFIED IDEOGRAPH - 0xF6D6: 0x4EB9, //CJK UNIFIED IDEOGRAPH - 0xF6D7: 0x56C6, //CJK UNIFIED IDEOGRAPH - 0xF6D8: 0x56C5, //CJK UNIFIED IDEOGRAPH - 0xF6D9: 0x56CB, //CJK UNIFIED IDEOGRAPH - 0xF6DA: 0x5971, //CJK UNIFIED IDEOGRAPH - 0xF6DB: 0x5B4B, //CJK UNIFIED IDEOGRAPH - 0xF6DC: 0x5B4C, //CJK UNIFIED IDEOGRAPH - 0xF6DD: 0x5DD5, //CJK UNIFIED IDEOGRAPH - 0xF6DE: 0x5DD1, //CJK UNIFIED IDEOGRAPH - 0xF6DF: 0x5EF2, //CJK UNIFIED IDEOGRAPH - 0xF6E0: 0x6521, //CJK UNIFIED IDEOGRAPH - 0xF6E1: 0x6520, //CJK UNIFIED IDEOGRAPH - 0xF6E2: 0x6526, //CJK UNIFIED IDEOGRAPH - 0xF6E3: 0x6522, //CJK UNIFIED IDEOGRAPH - 0xF6E4: 0x6B0B, //CJK UNIFIED IDEOGRAPH - 0xF6E5: 0x6B08, //CJK UNIFIED IDEOGRAPH - 0xF6E6: 0x6B09, //CJK UNIFIED IDEOGRAPH - 0xF6E7: 0x6C0D, //CJK UNIFIED IDEOGRAPH - 0xF6E8: 0x7055, //CJK UNIFIED IDEOGRAPH - 0xF6E9: 0x7056, //CJK UNIFIED IDEOGRAPH - 0xF6EA: 0x7057, //CJK UNIFIED IDEOGRAPH - 0xF6EB: 0x7052, //CJK UNIFIED IDEOGRAPH - 0xF6EC: 0x721E, //CJK UNIFIED IDEOGRAPH - 0xF6ED: 0x721F, //CJK UNIFIED IDEOGRAPH - 0xF6EE: 0x72A9, //CJK UNIFIED IDEOGRAPH - 0xF6EF: 0x737F, //CJK UNIFIED IDEOGRAPH - 0xF6F0: 0x74D8, //CJK UNIFIED IDEOGRAPH - 0xF6F1: 0x74D5, //CJK UNIFIED IDEOGRAPH - 0xF6F2: 0x74D9, //CJK UNIFIED IDEOGRAPH - 0xF6F3: 0x74D7, //CJK UNIFIED IDEOGRAPH - 0xF6F4: 0x766D, //CJK UNIFIED IDEOGRAPH - 0xF6F5: 0x76AD, //CJK UNIFIED IDEOGRAPH - 0xF6F6: 0x7935, //CJK UNIFIED IDEOGRAPH - 0xF6F7: 0x79B4, //CJK UNIFIED IDEOGRAPH - 0xF6F8: 0x7A70, //CJK UNIFIED IDEOGRAPH - 0xF6F9: 0x7A71, //CJK UNIFIED IDEOGRAPH - 0xF6FA: 0x7C57, //CJK UNIFIED IDEOGRAPH - 0xF6FB: 0x7C5C, //CJK UNIFIED IDEOGRAPH - 0xF6FC: 0x7C59, //CJK UNIFIED IDEOGRAPH - 0xF6FD: 0x7C5B, //CJK UNIFIED IDEOGRAPH - 0xF6FE: 0x7C5A, //CJK UNIFIED IDEOGRAPH - 0xF740: 0x7CF4, //CJK UNIFIED IDEOGRAPH - 0xF741: 0x7CF1, //CJK UNIFIED IDEOGRAPH - 0xF742: 0x7E91, //CJK UNIFIED IDEOGRAPH - 0xF743: 0x7F4F, //CJK UNIFIED IDEOGRAPH - 0xF744: 0x7F87, //CJK UNIFIED IDEOGRAPH - 0xF745: 0x81DE, //CJK UNIFIED IDEOGRAPH - 0xF746: 0x826B, //CJK UNIFIED IDEOGRAPH - 0xF747: 0x8634, //CJK UNIFIED IDEOGRAPH - 0xF748: 0x8635, //CJK UNIFIED IDEOGRAPH - 0xF749: 0x8633, //CJK UNIFIED IDEOGRAPH - 0xF74A: 0x862C, //CJK UNIFIED IDEOGRAPH - 0xF74B: 0x8632, //CJK UNIFIED IDEOGRAPH - 0xF74C: 0x8636, //CJK UNIFIED IDEOGRAPH - 0xF74D: 0x882C, //CJK UNIFIED IDEOGRAPH - 0xF74E: 0x8828, //CJK UNIFIED IDEOGRAPH - 0xF74F: 0x8826, //CJK UNIFIED IDEOGRAPH - 0xF750: 0x882A, //CJK UNIFIED IDEOGRAPH - 0xF751: 0x8825, //CJK UNIFIED IDEOGRAPH - 0xF752: 0x8971, //CJK UNIFIED IDEOGRAPH - 0xF753: 0x89BF, //CJK UNIFIED IDEOGRAPH - 0xF754: 0x89BE, //CJK UNIFIED IDEOGRAPH - 0xF755: 0x89FB, //CJK UNIFIED IDEOGRAPH - 0xF756: 0x8B7E, //CJK UNIFIED IDEOGRAPH - 0xF757: 0x8B84, //CJK UNIFIED IDEOGRAPH - 0xF758: 0x8B82, //CJK UNIFIED IDEOGRAPH - 0xF759: 0x8B86, //CJK UNIFIED IDEOGRAPH - 0xF75A: 0x8B85, //CJK UNIFIED IDEOGRAPH - 0xF75B: 0x8B7F, //CJK UNIFIED IDEOGRAPH - 0xF75C: 0x8D15, //CJK UNIFIED IDEOGRAPH - 0xF75D: 0x8E95, //CJK UNIFIED IDEOGRAPH - 0xF75E: 0x8E94, //CJK UNIFIED IDEOGRAPH - 0xF75F: 0x8E9A, //CJK UNIFIED IDEOGRAPH - 0xF760: 0x8E92, //CJK UNIFIED IDEOGRAPH - 0xF761: 0x8E90, //CJK UNIFIED IDEOGRAPH - 0xF762: 0x8E96, //CJK UNIFIED IDEOGRAPH - 0xF763: 0x8E97, //CJK UNIFIED IDEOGRAPH - 0xF764: 0x8F60, //CJK UNIFIED IDEOGRAPH - 0xF765: 0x8F62, //CJK UNIFIED IDEOGRAPH - 0xF766: 0x9147, //CJK UNIFIED IDEOGRAPH - 0xF767: 0x944C, //CJK UNIFIED IDEOGRAPH - 0xF768: 0x9450, //CJK UNIFIED IDEOGRAPH - 0xF769: 0x944A, //CJK UNIFIED IDEOGRAPH - 0xF76A: 0x944B, //CJK UNIFIED IDEOGRAPH - 0xF76B: 0x944F, //CJK UNIFIED IDEOGRAPH - 0xF76C: 0x9447, //CJK UNIFIED IDEOGRAPH - 0xF76D: 0x9445, //CJK UNIFIED IDEOGRAPH - 0xF76E: 0x9448, //CJK UNIFIED IDEOGRAPH - 0xF76F: 0x9449, //CJK UNIFIED IDEOGRAPH - 0xF770: 0x9446, //CJK UNIFIED IDEOGRAPH - 0xF771: 0x973F, //CJK UNIFIED IDEOGRAPH - 0xF772: 0x97E3, //CJK UNIFIED IDEOGRAPH - 0xF773: 0x986A, //CJK UNIFIED IDEOGRAPH - 0xF774: 0x9869, //CJK UNIFIED IDEOGRAPH - 0xF775: 0x98CB, //CJK UNIFIED IDEOGRAPH - 0xF776: 0x9954, //CJK UNIFIED IDEOGRAPH - 0xF777: 0x995B, //CJK UNIFIED IDEOGRAPH - 0xF778: 0x9A4E, //CJK UNIFIED IDEOGRAPH - 0xF779: 0x9A53, //CJK UNIFIED IDEOGRAPH - 0xF77A: 0x9A54, //CJK UNIFIED IDEOGRAPH - 0xF77B: 0x9A4C, //CJK UNIFIED IDEOGRAPH - 0xF77C: 0x9A4F, //CJK UNIFIED IDEOGRAPH - 0xF77D: 0x9A48, //CJK UNIFIED IDEOGRAPH - 0xF77E: 0x9A4A, //CJK UNIFIED IDEOGRAPH - 0xF7A1: 0x9A49, //CJK UNIFIED IDEOGRAPH - 0xF7A2: 0x9A52, //CJK UNIFIED IDEOGRAPH - 0xF7A3: 0x9A50, //CJK UNIFIED IDEOGRAPH - 0xF7A4: 0x9AD0, //CJK UNIFIED IDEOGRAPH - 0xF7A5: 0x9B19, //CJK UNIFIED IDEOGRAPH - 0xF7A6: 0x9B2B, //CJK UNIFIED IDEOGRAPH - 0xF7A7: 0x9B3B, //CJK UNIFIED IDEOGRAPH - 0xF7A8: 0x9B56, //CJK UNIFIED IDEOGRAPH - 0xF7A9: 0x9B55, //CJK UNIFIED IDEOGRAPH - 0xF7AA: 0x9C46, //CJK UNIFIED IDEOGRAPH - 0xF7AB: 0x9C48, //CJK UNIFIED IDEOGRAPH - 0xF7AC: 0x9C3F, //CJK UNIFIED IDEOGRAPH - 0xF7AD: 0x9C44, //CJK UNIFIED IDEOGRAPH - 0xF7AE: 0x9C39, //CJK UNIFIED IDEOGRAPH - 0xF7AF: 0x9C33, //CJK UNIFIED IDEOGRAPH - 0xF7B0: 0x9C41, //CJK UNIFIED IDEOGRAPH - 0xF7B1: 0x9C3C, //CJK UNIFIED IDEOGRAPH - 0xF7B2: 0x9C37, //CJK UNIFIED IDEOGRAPH - 0xF7B3: 0x9C34, //CJK UNIFIED IDEOGRAPH - 0xF7B4: 0x9C32, //CJK UNIFIED IDEOGRAPH - 0xF7B5: 0x9C3D, //CJK UNIFIED IDEOGRAPH - 0xF7B6: 0x9C36, //CJK UNIFIED IDEOGRAPH - 0xF7B7: 0x9DDB, //CJK UNIFIED IDEOGRAPH - 0xF7B8: 0x9DD2, //CJK UNIFIED IDEOGRAPH - 0xF7B9: 0x9DDE, //CJK UNIFIED IDEOGRAPH - 0xF7BA: 0x9DDA, //CJK UNIFIED IDEOGRAPH - 0xF7BB: 0x9DCB, //CJK UNIFIED IDEOGRAPH - 0xF7BC: 0x9DD0, //CJK UNIFIED IDEOGRAPH - 0xF7BD: 0x9DDC, //CJK UNIFIED IDEOGRAPH - 0xF7BE: 0x9DD1, //CJK UNIFIED IDEOGRAPH - 0xF7BF: 0x9DDF, //CJK UNIFIED IDEOGRAPH - 0xF7C0: 0x9DE9, //CJK UNIFIED IDEOGRAPH - 0xF7C1: 0x9DD9, //CJK UNIFIED IDEOGRAPH - 0xF7C2: 0x9DD8, //CJK UNIFIED IDEOGRAPH - 0xF7C3: 0x9DD6, //CJK UNIFIED IDEOGRAPH - 0xF7C4: 0x9DF5, //CJK UNIFIED IDEOGRAPH - 0xF7C5: 0x9DD5, //CJK UNIFIED IDEOGRAPH - 0xF7C6: 0x9DDD, //CJK UNIFIED IDEOGRAPH - 0xF7C7: 0x9EB6, //CJK UNIFIED IDEOGRAPH - 0xF7C8: 0x9EF0, //CJK UNIFIED IDEOGRAPH - 0xF7C9: 0x9F35, //CJK UNIFIED IDEOGRAPH - 0xF7CA: 0x9F33, //CJK UNIFIED IDEOGRAPH - 0xF7CB: 0x9F32, //CJK UNIFIED IDEOGRAPH - 0xF7CC: 0x9F42, //CJK UNIFIED IDEOGRAPH - 0xF7CD: 0x9F6B, //CJK UNIFIED IDEOGRAPH - 0xF7CE: 0x9F95, //CJK UNIFIED IDEOGRAPH - 0xF7CF: 0x9FA2, //CJK UNIFIED IDEOGRAPH - 0xF7D0: 0x513D, //CJK UNIFIED IDEOGRAPH - 0xF7D1: 0x5299, //CJK UNIFIED IDEOGRAPH - 0xF7D2: 0x58E8, //CJK UNIFIED IDEOGRAPH - 0xF7D3: 0x58E7, //CJK UNIFIED IDEOGRAPH - 0xF7D4: 0x5972, //CJK UNIFIED IDEOGRAPH - 0xF7D5: 0x5B4D, //CJK UNIFIED IDEOGRAPH - 0xF7D6: 0x5DD8, //CJK UNIFIED IDEOGRAPH - 0xF7D7: 0x882F, //CJK UNIFIED IDEOGRAPH - 0xF7D8: 0x5F4F, //CJK UNIFIED IDEOGRAPH - 0xF7D9: 0x6201, //CJK UNIFIED IDEOGRAPH - 0xF7DA: 0x6203, //CJK UNIFIED IDEOGRAPH - 0xF7DB: 0x6204, //CJK UNIFIED IDEOGRAPH - 0xF7DC: 0x6529, //CJK UNIFIED IDEOGRAPH - 0xF7DD: 0x6525, //CJK UNIFIED IDEOGRAPH - 0xF7DE: 0x6596, //CJK UNIFIED IDEOGRAPH - 0xF7DF: 0x66EB, //CJK UNIFIED IDEOGRAPH - 0xF7E0: 0x6B11, //CJK UNIFIED IDEOGRAPH - 0xF7E1: 0x6B12, //CJK UNIFIED IDEOGRAPH - 0xF7E2: 0x6B0F, //CJK UNIFIED IDEOGRAPH - 0xF7E3: 0x6BCA, //CJK UNIFIED IDEOGRAPH - 0xF7E4: 0x705B, //CJK UNIFIED IDEOGRAPH - 0xF7E5: 0x705A, //CJK UNIFIED IDEOGRAPH - 0xF7E6: 0x7222, //CJK UNIFIED IDEOGRAPH - 0xF7E7: 0x7382, //CJK UNIFIED IDEOGRAPH - 0xF7E8: 0x7381, //CJK UNIFIED IDEOGRAPH - 0xF7E9: 0x7383, //CJK UNIFIED IDEOGRAPH - 0xF7EA: 0x7670, //CJK UNIFIED IDEOGRAPH - 0xF7EB: 0x77D4, //CJK UNIFIED IDEOGRAPH - 0xF7EC: 0x7C67, //CJK UNIFIED IDEOGRAPH - 0xF7ED: 0x7C66, //CJK UNIFIED IDEOGRAPH - 0xF7EE: 0x7E95, //CJK UNIFIED IDEOGRAPH - 0xF7EF: 0x826C, //CJK UNIFIED IDEOGRAPH - 0xF7F0: 0x863A, //CJK UNIFIED IDEOGRAPH - 0xF7F1: 0x8640, //CJK UNIFIED IDEOGRAPH - 0xF7F2: 0x8639, //CJK UNIFIED IDEOGRAPH - 0xF7F3: 0x863C, //CJK UNIFIED IDEOGRAPH - 0xF7F4: 0x8631, //CJK UNIFIED IDEOGRAPH - 0xF7F5: 0x863B, //CJK UNIFIED IDEOGRAPH - 0xF7F6: 0x863E, //CJK UNIFIED IDEOGRAPH - 0xF7F7: 0x8830, //CJK UNIFIED IDEOGRAPH - 0xF7F8: 0x8832, //CJK UNIFIED IDEOGRAPH - 0xF7F9: 0x882E, //CJK UNIFIED IDEOGRAPH - 0xF7FA: 0x8833, //CJK UNIFIED IDEOGRAPH - 0xF7FB: 0x8976, //CJK UNIFIED IDEOGRAPH - 0xF7FC: 0x8974, //CJK UNIFIED IDEOGRAPH - 0xF7FD: 0x8973, //CJK UNIFIED IDEOGRAPH - 0xF7FE: 0x89FE, //CJK UNIFIED IDEOGRAPH - 0xF840: 0x8B8C, //CJK UNIFIED IDEOGRAPH - 0xF841: 0x8B8E, //CJK UNIFIED IDEOGRAPH - 0xF842: 0x8B8B, //CJK UNIFIED IDEOGRAPH - 0xF843: 0x8B88, //CJK UNIFIED IDEOGRAPH - 0xF844: 0x8C45, //CJK UNIFIED IDEOGRAPH - 0xF845: 0x8D19, //CJK UNIFIED IDEOGRAPH - 0xF846: 0x8E98, //CJK UNIFIED IDEOGRAPH - 0xF847: 0x8F64, //CJK UNIFIED IDEOGRAPH - 0xF848: 0x8F63, //CJK UNIFIED IDEOGRAPH - 0xF849: 0x91BC, //CJK UNIFIED IDEOGRAPH - 0xF84A: 0x9462, //CJK UNIFIED IDEOGRAPH - 0xF84B: 0x9455, //CJK UNIFIED IDEOGRAPH - 0xF84C: 0x945D, //CJK UNIFIED IDEOGRAPH - 0xF84D: 0x9457, //CJK UNIFIED IDEOGRAPH - 0xF84E: 0x945E, //CJK UNIFIED IDEOGRAPH - 0xF84F: 0x97C4, //CJK UNIFIED IDEOGRAPH - 0xF850: 0x97C5, //CJK UNIFIED IDEOGRAPH - 0xF851: 0x9800, //CJK UNIFIED IDEOGRAPH - 0xF852: 0x9A56, //CJK UNIFIED IDEOGRAPH - 0xF853: 0x9A59, //CJK UNIFIED IDEOGRAPH - 0xF854: 0x9B1E, //CJK UNIFIED IDEOGRAPH - 0xF855: 0x9B1F, //CJK UNIFIED IDEOGRAPH - 0xF856: 0x9B20, //CJK UNIFIED IDEOGRAPH - 0xF857: 0x9C52, //CJK UNIFIED IDEOGRAPH - 0xF858: 0x9C58, //CJK UNIFIED IDEOGRAPH - 0xF859: 0x9C50, //CJK UNIFIED IDEOGRAPH - 0xF85A: 0x9C4A, //CJK UNIFIED IDEOGRAPH - 0xF85B: 0x9C4D, //CJK UNIFIED IDEOGRAPH - 0xF85C: 0x9C4B, //CJK UNIFIED IDEOGRAPH - 0xF85D: 0x9C55, //CJK UNIFIED IDEOGRAPH - 0xF85E: 0x9C59, //CJK UNIFIED IDEOGRAPH - 0xF85F: 0x9C4C, //CJK UNIFIED IDEOGRAPH - 0xF860: 0x9C4E, //CJK UNIFIED IDEOGRAPH - 0xF861: 0x9DFB, //CJK UNIFIED IDEOGRAPH - 0xF862: 0x9DF7, //CJK UNIFIED IDEOGRAPH - 0xF863: 0x9DEF, //CJK UNIFIED IDEOGRAPH - 0xF864: 0x9DE3, //CJK UNIFIED IDEOGRAPH - 0xF865: 0x9DEB, //CJK UNIFIED IDEOGRAPH - 0xF866: 0x9DF8, //CJK UNIFIED IDEOGRAPH - 0xF867: 0x9DE4, //CJK UNIFIED IDEOGRAPH - 0xF868: 0x9DF6, //CJK UNIFIED IDEOGRAPH - 0xF869: 0x9DE1, //CJK UNIFIED IDEOGRAPH - 0xF86A: 0x9DEE, //CJK UNIFIED IDEOGRAPH - 0xF86B: 0x9DE6, //CJK UNIFIED IDEOGRAPH - 0xF86C: 0x9DF2, //CJK UNIFIED IDEOGRAPH - 0xF86D: 0x9DF0, //CJK UNIFIED IDEOGRAPH - 0xF86E: 0x9DE2, //CJK UNIFIED IDEOGRAPH - 0xF86F: 0x9DEC, //CJK UNIFIED IDEOGRAPH - 0xF870: 0x9DF4, //CJK UNIFIED IDEOGRAPH - 0xF871: 0x9DF3, //CJK UNIFIED IDEOGRAPH - 0xF872: 0x9DE8, //CJK UNIFIED IDEOGRAPH - 0xF873: 0x9DED, //CJK UNIFIED IDEOGRAPH - 0xF874: 0x9EC2, //CJK UNIFIED IDEOGRAPH - 0xF875: 0x9ED0, //CJK UNIFIED IDEOGRAPH - 0xF876: 0x9EF2, //CJK UNIFIED IDEOGRAPH - 0xF877: 0x9EF3, //CJK UNIFIED IDEOGRAPH - 0xF878: 0x9F06, //CJK UNIFIED IDEOGRAPH - 0xF879: 0x9F1C, //CJK UNIFIED IDEOGRAPH - 0xF87A: 0x9F38, //CJK UNIFIED IDEOGRAPH - 0xF87B: 0x9F37, //CJK UNIFIED IDEOGRAPH - 0xF87C: 0x9F36, //CJK UNIFIED IDEOGRAPH - 0xF87D: 0x9F43, //CJK UNIFIED IDEOGRAPH - 0xF87E: 0x9F4F, //CJK UNIFIED IDEOGRAPH - 0xF8A1: 0x9F71, //CJK UNIFIED IDEOGRAPH - 0xF8A2: 0x9F70, //CJK UNIFIED IDEOGRAPH - 0xF8A3: 0x9F6E, //CJK UNIFIED IDEOGRAPH - 0xF8A4: 0x9F6F, //CJK UNIFIED IDEOGRAPH - 0xF8A5: 0x56D3, //CJK UNIFIED IDEOGRAPH - 0xF8A6: 0x56CD, //CJK UNIFIED IDEOGRAPH - 0xF8A7: 0x5B4E, //CJK UNIFIED IDEOGRAPH - 0xF8A8: 0x5C6D, //CJK UNIFIED IDEOGRAPH - 0xF8A9: 0x652D, //CJK UNIFIED IDEOGRAPH - 0xF8AA: 0x66ED, //CJK UNIFIED IDEOGRAPH - 0xF8AB: 0x66EE, //CJK UNIFIED IDEOGRAPH - 0xF8AC: 0x6B13, //CJK UNIFIED IDEOGRAPH - 0xF8AD: 0x705F, //CJK UNIFIED IDEOGRAPH - 0xF8AE: 0x7061, //CJK UNIFIED IDEOGRAPH - 0xF8AF: 0x705D, //CJK UNIFIED IDEOGRAPH - 0xF8B0: 0x7060, //CJK UNIFIED IDEOGRAPH - 0xF8B1: 0x7223, //CJK UNIFIED IDEOGRAPH - 0xF8B2: 0x74DB, //CJK UNIFIED IDEOGRAPH - 0xF8B3: 0x74E5, //CJK UNIFIED IDEOGRAPH - 0xF8B4: 0x77D5, //CJK UNIFIED IDEOGRAPH - 0xF8B5: 0x7938, //CJK UNIFIED IDEOGRAPH - 0xF8B6: 0x79B7, //CJK UNIFIED IDEOGRAPH - 0xF8B7: 0x79B6, //CJK UNIFIED IDEOGRAPH - 0xF8B8: 0x7C6A, //CJK UNIFIED IDEOGRAPH - 0xF8B9: 0x7E97, //CJK UNIFIED IDEOGRAPH - 0xF8BA: 0x7F89, //CJK UNIFIED IDEOGRAPH - 0xF8BB: 0x826D, //CJK UNIFIED IDEOGRAPH - 0xF8BC: 0x8643, //CJK UNIFIED IDEOGRAPH - 0xF8BD: 0x8838, //CJK UNIFIED IDEOGRAPH - 0xF8BE: 0x8837, //CJK UNIFIED IDEOGRAPH - 0xF8BF: 0x8835, //CJK UNIFIED IDEOGRAPH - 0xF8C0: 0x884B, //CJK UNIFIED IDEOGRAPH - 0xF8C1: 0x8B94, //CJK UNIFIED IDEOGRAPH - 0xF8C2: 0x8B95, //CJK UNIFIED IDEOGRAPH - 0xF8C3: 0x8E9E, //CJK UNIFIED IDEOGRAPH - 0xF8C4: 0x8E9F, //CJK UNIFIED IDEOGRAPH - 0xF8C5: 0x8EA0, //CJK UNIFIED IDEOGRAPH - 0xF8C6: 0x8E9D, //CJK UNIFIED IDEOGRAPH - 0xF8C7: 0x91BE, //CJK UNIFIED IDEOGRAPH - 0xF8C8: 0x91BD, //CJK UNIFIED IDEOGRAPH - 0xF8C9: 0x91C2, //CJK UNIFIED IDEOGRAPH - 0xF8CA: 0x946B, //CJK UNIFIED IDEOGRAPH - 0xF8CB: 0x9468, //CJK UNIFIED IDEOGRAPH - 0xF8CC: 0x9469, //CJK UNIFIED IDEOGRAPH - 0xF8CD: 0x96E5, //CJK UNIFIED IDEOGRAPH - 0xF8CE: 0x9746, //CJK UNIFIED IDEOGRAPH - 0xF8CF: 0x9743, //CJK UNIFIED IDEOGRAPH - 0xF8D0: 0x9747, //CJK UNIFIED IDEOGRAPH - 0xF8D1: 0x97C7, //CJK UNIFIED IDEOGRAPH - 0xF8D2: 0x97E5, //CJK UNIFIED IDEOGRAPH - 0xF8D3: 0x9A5E, //CJK UNIFIED IDEOGRAPH - 0xF8D4: 0x9AD5, //CJK UNIFIED IDEOGRAPH - 0xF8D5: 0x9B59, //CJK UNIFIED IDEOGRAPH - 0xF8D6: 0x9C63, //CJK UNIFIED IDEOGRAPH - 0xF8D7: 0x9C67, //CJK UNIFIED IDEOGRAPH - 0xF8D8: 0x9C66, //CJK UNIFIED IDEOGRAPH - 0xF8D9: 0x9C62, //CJK UNIFIED IDEOGRAPH - 0xF8DA: 0x9C5E, //CJK UNIFIED IDEOGRAPH - 0xF8DB: 0x9C60, //CJK UNIFIED IDEOGRAPH - 0xF8DC: 0x9E02, //CJK UNIFIED IDEOGRAPH - 0xF8DD: 0x9DFE, //CJK UNIFIED IDEOGRAPH - 0xF8DE: 0x9E07, //CJK UNIFIED IDEOGRAPH - 0xF8DF: 0x9E03, //CJK UNIFIED IDEOGRAPH - 0xF8E0: 0x9E06, //CJK UNIFIED IDEOGRAPH - 0xF8E1: 0x9E05, //CJK UNIFIED IDEOGRAPH - 0xF8E2: 0x9E00, //CJK UNIFIED IDEOGRAPH - 0xF8E3: 0x9E01, //CJK UNIFIED IDEOGRAPH - 0xF8E4: 0x9E09, //CJK UNIFIED IDEOGRAPH - 0xF8E5: 0x9DFF, //CJK UNIFIED IDEOGRAPH - 0xF8E6: 0x9DFD, //CJK UNIFIED IDEOGRAPH - 0xF8E7: 0x9E04, //CJK UNIFIED IDEOGRAPH - 0xF8E8: 0x9EA0, //CJK UNIFIED IDEOGRAPH - 0xF8E9: 0x9F1E, //CJK UNIFIED IDEOGRAPH - 0xF8EA: 0x9F46, //CJK UNIFIED IDEOGRAPH - 0xF8EB: 0x9F74, //CJK UNIFIED IDEOGRAPH - 0xF8EC: 0x9F75, //CJK UNIFIED IDEOGRAPH - 0xF8ED: 0x9F76, //CJK UNIFIED IDEOGRAPH - 0xF8EE: 0x56D4, //CJK UNIFIED IDEOGRAPH - 0xF8EF: 0x652E, //CJK UNIFIED IDEOGRAPH - 0xF8F0: 0x65B8, //CJK UNIFIED IDEOGRAPH - 0xF8F1: 0x6B18, //CJK UNIFIED IDEOGRAPH - 0xF8F2: 0x6B19, //CJK UNIFIED IDEOGRAPH - 0xF8F3: 0x6B17, //CJK UNIFIED IDEOGRAPH - 0xF8F4: 0x6B1A, //CJK UNIFIED IDEOGRAPH - 0xF8F5: 0x7062, //CJK UNIFIED IDEOGRAPH - 0xF8F6: 0x7226, //CJK UNIFIED IDEOGRAPH - 0xF8F7: 0x72AA, //CJK UNIFIED IDEOGRAPH - 0xF8F8: 0x77D8, //CJK UNIFIED IDEOGRAPH - 0xF8F9: 0x77D9, //CJK UNIFIED IDEOGRAPH - 0xF8FA: 0x7939, //CJK UNIFIED IDEOGRAPH - 0xF8FB: 0x7C69, //CJK UNIFIED IDEOGRAPH - 0xF8FC: 0x7C6B, //CJK UNIFIED IDEOGRAPH - 0xF8FD: 0x7CF6, //CJK UNIFIED IDEOGRAPH - 0xF8FE: 0x7E9A, //CJK UNIFIED IDEOGRAPH - 0xF940: 0x7E98, //CJK UNIFIED IDEOGRAPH - 0xF941: 0x7E9B, //CJK UNIFIED IDEOGRAPH - 0xF942: 0x7E99, //CJK UNIFIED IDEOGRAPH - 0xF943: 0x81E0, //CJK UNIFIED IDEOGRAPH - 0xF944: 0x81E1, //CJK UNIFIED IDEOGRAPH - 0xF945: 0x8646, //CJK UNIFIED IDEOGRAPH - 0xF946: 0x8647, //CJK UNIFIED IDEOGRAPH - 0xF947: 0x8648, //CJK UNIFIED IDEOGRAPH - 0xF948: 0x8979, //CJK UNIFIED IDEOGRAPH - 0xF949: 0x897A, //CJK UNIFIED IDEOGRAPH - 0xF94A: 0x897C, //CJK UNIFIED IDEOGRAPH - 0xF94B: 0x897B, //CJK UNIFIED IDEOGRAPH - 0xF94C: 0x89FF, //CJK UNIFIED IDEOGRAPH - 0xF94D: 0x8B98, //CJK UNIFIED IDEOGRAPH - 0xF94E: 0x8B99, //CJK UNIFIED IDEOGRAPH - 0xF94F: 0x8EA5, //CJK UNIFIED IDEOGRAPH - 0xF950: 0x8EA4, //CJK UNIFIED IDEOGRAPH - 0xF951: 0x8EA3, //CJK UNIFIED IDEOGRAPH - 0xF952: 0x946E, //CJK UNIFIED IDEOGRAPH - 0xF953: 0x946D, //CJK UNIFIED IDEOGRAPH - 0xF954: 0x946F, //CJK UNIFIED IDEOGRAPH - 0xF955: 0x9471, //CJK UNIFIED IDEOGRAPH - 0xF956: 0x9473, //CJK UNIFIED IDEOGRAPH - 0xF957: 0x9749, //CJK UNIFIED IDEOGRAPH - 0xF958: 0x9872, //CJK UNIFIED IDEOGRAPH - 0xF959: 0x995F, //CJK UNIFIED IDEOGRAPH - 0xF95A: 0x9C68, //CJK UNIFIED IDEOGRAPH - 0xF95B: 0x9C6E, //CJK UNIFIED IDEOGRAPH - 0xF95C: 0x9C6D, //CJK UNIFIED IDEOGRAPH - 0xF95D: 0x9E0B, //CJK UNIFIED IDEOGRAPH - 0xF95E: 0x9E0D, //CJK UNIFIED IDEOGRAPH - 0xF95F: 0x9E10, //CJK UNIFIED IDEOGRAPH - 0xF960: 0x9E0F, //CJK UNIFIED IDEOGRAPH - 0xF961: 0x9E12, //CJK UNIFIED IDEOGRAPH - 0xF962: 0x9E11, //CJK UNIFIED IDEOGRAPH - 0xF963: 0x9EA1, //CJK UNIFIED IDEOGRAPH - 0xF964: 0x9EF5, //CJK UNIFIED IDEOGRAPH - 0xF965: 0x9F09, //CJK UNIFIED IDEOGRAPH - 0xF966: 0x9F47, //CJK UNIFIED IDEOGRAPH - 0xF967: 0x9F78, //CJK UNIFIED IDEOGRAPH - 0xF968: 0x9F7B, //CJK UNIFIED IDEOGRAPH - 0xF969: 0x9F7A, //CJK UNIFIED IDEOGRAPH - 0xF96A: 0x9F79, //CJK UNIFIED IDEOGRAPH - 0xF96B: 0x571E, //CJK UNIFIED IDEOGRAPH - 0xF96C: 0x7066, //CJK UNIFIED IDEOGRAPH - 0xF96D: 0x7C6F, //CJK UNIFIED IDEOGRAPH - 0xF96E: 0x883C, //CJK UNIFIED IDEOGRAPH - 0xF96F: 0x8DB2, //CJK UNIFIED IDEOGRAPH - 0xF970: 0x8EA6, //CJK UNIFIED IDEOGRAPH - 0xF971: 0x91C3, //CJK UNIFIED IDEOGRAPH - 0xF972: 0x9474, //CJK UNIFIED IDEOGRAPH - 0xF973: 0x9478, //CJK UNIFIED IDEOGRAPH - 0xF974: 0x9476, //CJK UNIFIED IDEOGRAPH - 0xF975: 0x9475, //CJK UNIFIED IDEOGRAPH - 0xF976: 0x9A60, //CJK UNIFIED IDEOGRAPH - 0xF977: 0x9C74, //CJK UNIFIED IDEOGRAPH - 0xF978: 0x9C73, //CJK UNIFIED IDEOGRAPH - 0xF979: 0x9C71, //CJK UNIFIED IDEOGRAPH - 0xF97A: 0x9C75, //CJK UNIFIED IDEOGRAPH - 0xF97B: 0x9E14, //CJK UNIFIED IDEOGRAPH - 0xF97C: 0x9E13, //CJK UNIFIED IDEOGRAPH - 0xF97D: 0x9EF6, //CJK UNIFIED IDEOGRAPH - 0xF97E: 0x9F0A, //CJK UNIFIED IDEOGRAPH - 0xF9A1: 0x9FA4, //CJK UNIFIED IDEOGRAPH - 0xF9A2: 0x7068, //CJK UNIFIED IDEOGRAPH - 0xF9A3: 0x7065, //CJK UNIFIED IDEOGRAPH - 0xF9A4: 0x7CF7, //CJK UNIFIED IDEOGRAPH - 0xF9A5: 0x866A, //CJK UNIFIED IDEOGRAPH - 0xF9A6: 0x883E, //CJK UNIFIED IDEOGRAPH - 0xF9A7: 0x883D, //CJK UNIFIED IDEOGRAPH - 0xF9A8: 0x883F, //CJK UNIFIED IDEOGRAPH - 0xF9A9: 0x8B9E, //CJK UNIFIED IDEOGRAPH - 0xF9AA: 0x8C9C, //CJK UNIFIED IDEOGRAPH - 0xF9AB: 0x8EA9, //CJK UNIFIED IDEOGRAPH - 0xF9AC: 0x8EC9, //CJK UNIFIED IDEOGRAPH - 0xF9AD: 0x974B, //CJK UNIFIED IDEOGRAPH - 0xF9AE: 0x9873, //CJK UNIFIED IDEOGRAPH - 0xF9AF: 0x9874, //CJK UNIFIED IDEOGRAPH - 0xF9B0: 0x98CC, //CJK UNIFIED IDEOGRAPH - 0xF9B1: 0x9961, //CJK UNIFIED IDEOGRAPH - 0xF9B2: 0x99AB, //CJK UNIFIED IDEOGRAPH - 0xF9B3: 0x9A64, //CJK UNIFIED IDEOGRAPH - 0xF9B4: 0x9A66, //CJK UNIFIED IDEOGRAPH - 0xF9B5: 0x9A67, //CJK UNIFIED IDEOGRAPH - 0xF9B6: 0x9B24, //CJK UNIFIED IDEOGRAPH - 0xF9B7: 0x9E15, //CJK UNIFIED IDEOGRAPH - 0xF9B8: 0x9E17, //CJK UNIFIED IDEOGRAPH - 0xF9B9: 0x9F48, //CJK UNIFIED IDEOGRAPH - 0xF9BA: 0x6207, //CJK UNIFIED IDEOGRAPH - 0xF9BB: 0x6B1E, //CJK UNIFIED IDEOGRAPH - 0xF9BC: 0x7227, //CJK UNIFIED IDEOGRAPH - 0xF9BD: 0x864C, //CJK UNIFIED IDEOGRAPH - 0xF9BE: 0x8EA8, //CJK UNIFIED IDEOGRAPH - 0xF9BF: 0x9482, //CJK UNIFIED IDEOGRAPH - 0xF9C0: 0x9480, //CJK UNIFIED IDEOGRAPH - 0xF9C1: 0x9481, //CJK UNIFIED IDEOGRAPH - 0xF9C2: 0x9A69, //CJK UNIFIED IDEOGRAPH - 0xF9C3: 0x9A68, //CJK UNIFIED IDEOGRAPH - 0xF9C4: 0x9B2E, //CJK UNIFIED IDEOGRAPH - 0xF9C5: 0x9E19, //CJK UNIFIED IDEOGRAPH - 0xF9C6: 0x7229, //CJK UNIFIED IDEOGRAPH - 0xF9C7: 0x864B, //CJK UNIFIED IDEOGRAPH - 0xF9C8: 0x8B9F, //CJK UNIFIED IDEOGRAPH - 0xF9C9: 0x9483, //CJK UNIFIED IDEOGRAPH - 0xF9CA: 0x9C79, //CJK UNIFIED IDEOGRAPH - 0xF9CB: 0x9EB7, //CJK UNIFIED IDEOGRAPH - 0xF9CC: 0x7675, //CJK UNIFIED IDEOGRAPH - 0xF9CD: 0x9A6B, //CJK UNIFIED IDEOGRAPH - 0xF9CE: 0x9C7A, //CJK UNIFIED IDEOGRAPH - 0xF9CF: 0x9E1D, //CJK UNIFIED IDEOGRAPH - 0xF9D0: 0x7069, //CJK UNIFIED IDEOGRAPH - 0xF9D1: 0x706A, //CJK UNIFIED IDEOGRAPH - 0xF9D2: 0x9EA4, //CJK UNIFIED IDEOGRAPH - 0xF9D3: 0x9F7E, //CJK UNIFIED IDEOGRAPH - 0xF9D4: 0x9F49, //CJK UNIFIED IDEOGRAPH - 0xF9D5: 0x9F98, //CJK UNIFIED IDEOGRAPH - 0xF9D6: 0x7881, //CJK UNIFIED IDEOGRAPH - 0xF9D7: 0x92B9, //CJK UNIFIED IDEOGRAPH - 0xF9D8: 0x88CF, //CJK UNIFIED IDEOGRAPH - 0xF9D9: 0x58BB, //CJK UNIFIED IDEOGRAPH - 0xF9DA: 0x6052, //CJK UNIFIED IDEOGRAPH - 0xF9DB: 0x7CA7, //CJK UNIFIED IDEOGRAPH - 0xF9DC: 0x5AFA, //CJK UNIFIED IDEOGRAPH - 0xF9DD: 0x2554, //BOX DRAWINGS DOUBLE DOWN AND RIGHT - 0xF9DE: 0x2566, //BOX DRAWINGS DOUBLE DOWN AND HORIZONTAL - 0xF9DF: 0x2557, //BOX DRAWINGS DOUBLE DOWN AND LEFT - 0xF9E0: 0x2560, //BOX DRAWINGS DOUBLE VERTICAL AND RIGHT - 0xF9E1: 0x256C, //BOX DRAWINGS DOUBLE VERTICAL AND HORIZONTAL - 0xF9E2: 0x2563, //BOX DRAWINGS DOUBLE VERTICAL AND LEFT - 0xF9E3: 0x255A, //BOX DRAWINGS DOUBLE UP AND RIGHT - 0xF9E4: 0x2569, //BOX DRAWINGS DOUBLE UP AND HORIZONTAL - 0xF9E5: 0x255D, //BOX DRAWINGS DOUBLE UP AND LEFT - 0xF9E6: 0x2552, //BOX DRAWINGS DOWN SINGLE AND RIGHT DOUBLE - 0xF9E7: 0x2564, //BOX DRAWINGS DOWN SINGLE AND HORIZONTAL DOUBLE - 0xF9E8: 0x2555, //BOX DRAWINGS DOWN SINGLE AND LEFT DOUBLE - 0xF9E9: 0x255E, //BOX DRAWINGS VERTICAL SINGLE AND RIGHT DOUBLE - 0xF9EA: 0x256A, //BOX DRAWINGS VERTICAL SINGLE AND HORIZONTAL DOUBLE - 0xF9EB: 0x2561, //BOX DRAWINGS VERTICAL SINGLE AND LEFT DOUBLE - 0xF9EC: 0x2558, //BOX DRAWINGS UP SINGLE AND RIGHT DOUBLE - 0xF9ED: 0x2567, //BOX DRAWINGS UP SINGLE AND HORIZONTAL DOUBLE - 0xF9EE: 0x255B, //BOX DRAWINGS UP SINGLE AND LEFT DOUBLE - 0xF9EF: 0x2553, //BOX DRAWINGS DOWN DOUBLE AND RIGHT SINGLE - 0xF9F0: 0x2565, //BOX DRAWINGS DOWN DOUBLE AND HORIZONTAL SINGLE - 0xF9F1: 0x2556, //BOX DRAWINGS DOWN DOUBLE AND LEFT SINGLE - 0xF9F2: 0x255F, //BOX DRAWINGS VERTICAL DOUBLE AND RIGHT SINGLE - 0xF9F3: 0x256B, //BOX DRAWINGS VERTICAL DOUBLE AND HORIZONTAL SINGLE - 0xF9F4: 0x2562, //BOX DRAWINGS VERTICAL DOUBLE AND LEFT SINGLE - 0xF9F5: 0x2559, //BOX DRAWINGS UP DOUBLE AND RIGHT SINGLE - 0xF9F6: 0x2568, //BOX DRAWINGS UP DOUBLE AND HORIZONTAL SINGLE - 0xF9F7: 0x255C, //BOX DRAWINGS UP DOUBLE AND LEFT SINGLE - 0xF9F8: 0x2551, //BOX DRAWINGS DOUBLE VERTICAL - 0xF9F9: 0x2550, //BOX DRAWINGS DOUBLE HORIZONTAL - 0xF9FA: 0x256D, //BOX DRAWINGS LIGHT ARC DOWN AND RIGHT - 0xF9FB: 0x256E, //BOX DRAWINGS LIGHT ARC DOWN AND LEFT - 0xF9FC: 0x2570, //BOX DRAWINGS LIGHT ARC UP AND RIGHT - 0xF9FD: 0x256F, //BOX DRAWINGS LIGHT ARC UP AND LEFT - 0xF9FE: 0x2593, //DARK SHADE - }, -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/decimal.go b/vendor/github.com/denisenkom/go-mssqldb/decimal.go deleted file mode 100644 index 76f3a6b5b..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/decimal.go +++ /dev/null @@ -1,115 +0,0 @@ -package mssql - -import ( - "encoding/binary" - "errors" - "math" - "math/big" -) - -// http://msdn.microsoft.com/en-us/library/ee780893.aspx -type Decimal struct { - integer [4]uint32 - positive bool - prec uint8 - scale uint8 -} - -var scaletblflt64 [39]float64 - -func (d Decimal) ToFloat64() float64 { - val := float64(0) - for i := 3; i >= 0; i-- { - val *= 0x100000000 - val += float64(d.integer[i]) - } - if !d.positive { - val = -val - } - if d.scale != 0 { - val /= scaletblflt64[d.scale] - } - return val -} - -func Float64ToDecimal(f float64) (Decimal, error) { - var dec Decimal - if math.IsNaN(f) { - return dec, errors.New("NaN") - } - if math.IsInf(f, 0) { - return dec, errors.New("Infinity can't be converted to decimal") - } - dec.positive = f >= 0 - if !dec.positive { - f = math.Abs(f) - } - if f > 3.402823669209385e+38 { - return dec, errors.New("Float value is out of range") - } - dec.prec = 20 - var integer float64 - for dec.scale = 0; dec.scale <= 20; dec.scale++ { - integer = f * scaletblflt64[dec.scale] - _, frac := math.Modf(integer) - if frac == 0 { - break - } - } - for i := 0; i < 4; i++ { - mod := math.Mod(integer, 0x100000000) - integer -= mod - integer /= 0x100000000 - dec.integer[i] = uint32(mod) - } - return dec, nil -} - -func init() { - var acc float64 = 1 - for i := 0; i <= 38; i++ { - scaletblflt64[i] = acc - acc *= 10 - } -} - -func (d Decimal) Bytes() []byte { - bytes := make([]byte, 16) - binary.BigEndian.PutUint32(bytes[0:4], d.integer[3]) - binary.BigEndian.PutUint32(bytes[4:8], d.integer[2]) - binary.BigEndian.PutUint32(bytes[8:12], d.integer[1]) - binary.BigEndian.PutUint32(bytes[12:16], d.integer[0]) - var x big.Int - x.SetBytes(bytes) - if !d.positive { - x.Neg(&x) - } - return scaleBytes(x.String(), d.scale) -} - -func scaleBytes(s string, scale uint8) []byte { - z := make([]byte, 0, len(s)+1) - if s[0] == '-' || s[0] == '+' { - z = append(z, byte(s[0])) - s = s[1:] - } - pos := len(s) - int(scale) - if pos <= 0 { - z = append(z, byte('0')) - } else if pos > 0 { - z = append(z, []byte(s[:pos])...) - } - if scale > 0 { - z = append(z, byte('.')) - for pos < 0 { - z = append(z, byte('0')) - pos++ - } - z = append(z, []byte(s[pos:])...) - } - return z -} - -func (d Decimal) String() string { - return string(d.Bytes()) -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/decimal_test.go b/vendor/github.com/denisenkom/go-mssqldb/decimal_test.go deleted file mode 100644 index 80df0da9a..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/decimal_test.go +++ /dev/null @@ -1,82 +0,0 @@ -package mssql - -import ( - "testing" -) - -func TestToString(t *testing.T) { - values := []struct { - dec Decimal - s string - }{ - {Decimal{positive: true, prec: 10, scale: 0, integer: [4]uint32{1, 0, 0, 0}}, "1"}, - {Decimal{positive: false, prec: 10, scale: 0, integer: [4]uint32{1, 0, 0, 0}}, "-1"}, - {Decimal{positive: true, prec: 10, scale: 1, integer: [4]uint32{1, 0, 0, 0}}, "0.1"}, - {Decimal{positive: false, prec: 10, scale: 1, integer: [4]uint32{1, 0, 0, 0}}, "-0.1"}, - {Decimal{positive: true, prec: 10, scale: 2, integer: [4]uint32{100, 0, 0, 0}}, "1.00"}, - {Decimal{positive: false, prec: 10, scale: 2, integer: [4]uint32{100, 0, 0, 0}}, "-1.00"}, - {Decimal{positive: true, prec: 30, scale: 0, integer: [4]uint32{0, 1, 0, 0}}, "4294967296"}, // 2^32 - {Decimal{positive: true, prec: 30, scale: 0, integer: [4]uint32{0, 0, 1, 0}}, "18446744073709551616"}, // 2^64 - {Decimal{positive: true, prec: 30, scale: 0, integer: [4]uint32{0, 1, 1, 0}}, "18446744078004518912"}, // 2^64+2^32 - } - for _, v := range values { - if v.dec.String() != v.s { - t.Error("String values don't match ", v.dec.String(), v.s) - } - } -} - -func TestToFloat64(t *testing.T) { - values := []struct { - dec Decimal - flt float64 - }{ - {Decimal{positive: true, prec: 1}, - 0.0}, - {Decimal{positive: true, prec: 1, integer: [4]uint32{1}}, - 1.0}, - {Decimal{positive: false, prec: 1, integer: [4]uint32{1}}, - -1.0}, - {Decimal{positive: true, prec: 1, scale: 1, integer: [4]uint32{5}}, - 0.5}, - {Decimal{positive: true, prec: 38, integer: [4]uint32{0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff}}, - 3.402823669209385e+38}, - {Decimal{positive: true, prec: 38, scale: 3, integer: [4]uint32{0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff}}, - 3.402823669209385e+35}, - } - for _, v := range values { - if v.dec.ToFloat64() != v.flt { - t.Error("ToFloat values don't match ", v.dec.ToFloat64(), v.flt) - } - } -} - -func TestFromFloat64(t *testing.T) { - values := []struct { - dec Decimal - flt float64 - }{ - {Decimal{positive: true, prec: 20}, - 0.0}, - {Decimal{positive: true, prec: 20, integer: [4]uint32{1}}, - 1.0}, - {Decimal{positive: false, prec: 20, integer: [4]uint32{1}}, - -1.0}, - {Decimal{positive: true, prec: 20, scale: 1, integer: [4]uint32{5}}, - 0.5}, - {Decimal{positive: true, prec: 20, integer: [4]uint32{0, 0, 0xfffff000, 0xffffffff}}, - 3.402823669209384e+38}, - //{Decimal{positive: true, prec: 20, scale: 3, integer: [4]uint32{0, 0, 0xfffff000, 0xffffffff}}, - // 3.402823669209385e+35}, - } - for _, v := range values { - decfromflt, err := Float64ToDecimal(v.flt) - if err == nil { - if decfromflt != v.dec { - t.Error("FromFloat values don't match ", decfromflt, v.dec) - } - } else { - t.Error("Float64ToDecimal failed with error:", err.Error()) - } - } -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/error.go b/vendor/github.com/denisenkom/go-mssqldb/error.go deleted file mode 100644 index 20a0bb901..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/error.go +++ /dev/null @@ -1,39 +0,0 @@ -package mssql - -import ( - "fmt" -) - -type Error struct { - Number int32 - State uint8 - Class uint8 - Message string - ServerName string - ProcName string - LineNo int32 -} - -func (e Error) Error() string { - return "mssql: " + e.Message -} - -type StreamError struct { - Message string -} - -func (e StreamError) Error() string { - return e.Message -} - -func streamErrorf(format string, v ...interface{}) StreamError { - return StreamError{"Invalid TDS stream: " + fmt.Sprintf(format, v...)} -} - -func badStreamPanic(err error) { - panic(err) -} - -func badStreamPanicf(format string, v ...interface{}) { - panic(streamErrorf(format, v...)) -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/examples/simple.go b/vendor/github.com/denisenkom/go-mssqldb/examples/simple.go deleted file mode 100644 index ce06fa8ee..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/examples/simple.go +++ /dev/null @@ -1,53 +0,0 @@ -package main - -import _ "github.com/denisenkom/go-mssqldb" -import "database/sql" -import "log" -import "fmt" -import "flag" - -var debug = flag.Bool("debug", false, "enable debugging") -var password = flag.String("password", "", "the database password") -var port *int = flag.Int("port", 1433, "the database port") -var server = flag.String("server", "", "the database server") -var user = flag.String("user", "", "the database user") - -func main() { - flag.Parse() // parse the command line args - - if *debug { - fmt.Printf(" password:%s\n", *password) - fmt.Printf(" port:%d\n", *port) - fmt.Printf(" server:%s\n", *server) - fmt.Printf(" user:%s\n", *user) - } - - connString := fmt.Sprintf("server=%s;user id=%s;password=%s;port=%d", *server, *user, *password, *port) - if *debug { - fmt.Printf(" connString:%s\n", connString) - } - conn, err := sql.Open("mssql", connString) - if err != nil { - log.Fatal("Open connection failed:", err.Error()) - } - defer conn.Close() - - stmt, err := conn.Prepare("select 1, 'abc'") - if err != nil { - log.Fatal("Prepare failed:", err.Error()) - } - defer stmt.Close() - - row := stmt.QueryRow() - var somenumber int64 - var somechars string - err = row.Scan(&somenumber, &somechars) - if err != nil { - log.Fatal("Scan failed:", err.Error()) - } - fmt.Printf("somenumber:%d\n", somenumber) - fmt.Printf("somechars:%s\n", somechars) - - fmt.Printf("bye\n") - -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/examples/tsql.go b/vendor/github.com/denisenkom/go-mssqldb/examples/tsql.go deleted file mode 100644 index 409404a0b..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/examples/tsql.go +++ /dev/null @@ -1,119 +0,0 @@ -package main - -import ( - "bufio" - "database/sql" - "flag" - "fmt" - "io" - "os" - "time" - - _ "github.com/denisenkom/go-mssqldb" -) - -func main() { - var ( - userid = flag.String("U", "", "login_id") - password = flag.String("P", "", "password") - server = flag.String("S", "localhost", "server_name[\\instance_name]") - database = flag.String("d", "", "db_name") - ) - flag.Parse() - - dsn := "server=" + *server + ";user id=" + *userid + ";password=" + *password + ";database=" + *database - db, err := sql.Open("mssql", dsn) - if err != nil { - fmt.Println("Cannot connect: ", err.Error()) - return - } - err = db.Ping() - if err != nil { - fmt.Println("Cannot connect: ", err.Error()) - return - } - defer db.Close() - r := bufio.NewReader(os.Stdin) - for { - _, err = os.Stdout.Write([]byte("> ")) - if err != nil { - fmt.Println(err) - return - } - cmd, err := r.ReadString('\n') - if err != nil { - if err == io.EOF { - fmt.Println() - return - } - fmt.Println(err) - return - } - err = exec(db, cmd) - if err != nil { - fmt.Println(err) - } - } -} - -func exec(db *sql.DB, cmd string) error { - rows, err := db.Query(cmd) - if err != nil { - return err - } - defer rows.Close() - cols, err := rows.Columns() - if err != nil { - return err - } - if cols == nil { - return nil - } - vals := make([]interface{}, len(cols)) - for i := 0; i < len(cols); i++ { - vals[i] = new(interface{}) - if i != 0 { - fmt.Print("\t") - } - fmt.Print(cols[i]) - } - fmt.Println() - for rows.Next() { - err = rows.Scan(vals...) - if err != nil { - fmt.Println(err) - continue - } - for i := 0; i < len(vals); i++ { - if i != 0 { - fmt.Print("\t") - } - printValue(vals[i].(*interface{})) - } - fmt.Println() - - } - if rows.Err() != nil { - return rows.Err() - } - return nil -} - -func printValue(pval *interface{}) { - switch v := (*pval).(type) { - case nil: - fmt.Print("NULL") - case bool: - if v { - fmt.Print("1") - } else { - fmt.Print("0") - } - case []byte: - fmt.Print(string(v)) - case time.Time: - fmt.Print(v.Format("2006-01-02 15:04:05.999")) - default: - fmt.Print(v) - } -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/log.go b/vendor/github.com/denisenkom/go-mssqldb/log.go deleted file mode 100644 index f350aed09..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/log.go +++ /dev/null @@ -1,23 +0,0 @@ -package mssql - -import ( - "log" -) - -type Logger log.Logger - -func (logger *Logger) Printf(format string, v ...interface{}) { - if logger != nil { - (*log.Logger)(logger).Printf(format, v...) - } else { - log.Printf(format, v...) - } -} - -func (logger *Logger) Println(v ...interface{}) { - if logger != nil { - (*log.Logger)(logger).Println(v...) - } else { - log.Println(v...) - } -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/mssql.go b/vendor/github.com/denisenkom/go-mssqldb/mssql.go deleted file mode 100644 index b675d910e..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/mssql.go +++ /dev/null @@ -1,472 +0,0 @@ -package mssql - -import ( - "database/sql" - "database/sql/driver" - "encoding/binary" - "errors" - "fmt" - "io" - "log" - "math" - "net" - "strings" - "sync" - "time" -) - -var partnersCache partners = partners{mu: sync.RWMutex{}, v: make(map[string]string)} - -func init() { - sql.Register("mssql", &MssqlDriver{}) -} - -type MssqlDriver struct { - log *log.Logger -} - -func (d *MssqlDriver) SetLogger(logger *log.Logger) { - d.log = logger -} - -func CheckBadConn(err error) error { - if err == io.EOF { - return driver.ErrBadConn - } - neterr, ok := err.(net.Error) - if !ok || (!neterr.Timeout() && neterr.Temporary()) { - return err - } - return driver.ErrBadConn -} - -type MssqlConn struct { - sess *tdsSession -} - -func (c *MssqlConn) Commit() error { - headers := []headerStruct{ - {hdrtype: dataStmHdrTransDescr, - data: transDescrHdr{c.sess.tranid, 1}.pack()}, - } - if err := sendCommitXact(c.sess.buf, headers, "", 0, 0, ""); err != nil { - return err - } - - tokchan := make(chan tokenStruct, 5) - go processResponse(c.sess, tokchan) - for tok := range tokchan { - switch token := tok.(type) { - case error: - return token - } - } - return nil -} - -func (c *MssqlConn) Rollback() error { - headers := []headerStruct{ - {hdrtype: dataStmHdrTransDescr, - data: transDescrHdr{c.sess.tranid, 1}.pack()}, - } - if err := sendRollbackXact(c.sess.buf, headers, "", 0, 0, ""); err != nil { - return err - } - - tokchan := make(chan tokenStruct, 5) - go processResponse(c.sess, tokchan) - for tok := range tokchan { - switch token := tok.(type) { - case error: - return token - } - } - return nil -} - -func (c *MssqlConn) Begin() (driver.Tx, error) { - headers := []headerStruct{ - {hdrtype: dataStmHdrTransDescr, - data: transDescrHdr{0, 1}.pack()}, - } - if err := sendBeginXact(c.sess.buf, headers, 0, ""); err != nil { - return nil, CheckBadConn(err) - } - tokchan := make(chan tokenStruct, 5) - go processResponse(c.sess, tokchan) - for tok := range tokchan { - switch token := tok.(type) { - case error: - if c.sess.tranid != 0 { - return nil, token - } - return nil, CheckBadConn(token) - } - } - // successful BEGINXACT request will return sess.tranid - // for started transaction - return c, nil -} - -func parseConnectionString(dsn string) (res map[string]string) { - res = map[string]string{} - parts := strings.Split(dsn, ";") - for _, part := range parts { - if len(part) == 0 { - continue - } - lst := strings.SplitN(part, "=", 2) - name := strings.TrimSpace(strings.ToLower(lst[0])) - if len(name) == 0 { - continue - } - var value string = "" - if len(lst) > 1 { - value = strings.TrimSpace(lst[1]) - } - res[name] = value - } - return res -} - -func (d *MssqlDriver) Open(dsn string) (driver.Conn, error) { - params := parseConnectionString(dsn) - - conn, err := openConnection(dsn, params) - if err != nil { - return nil, err - } - - conn.sess.log = (*Logger)(d.log) - return conn, nil -} - -func openConnection(dsn string, params map[string]string) (*MssqlConn, error) { - sess, err := connect(params) - if err != nil { - partner := partnersCache.Get(dsn) - if partner == "" { - partner = params["failoverpartner"] - // remove the failoverpartner entry to prevent infinite recursion - delete(params, "failoverpartner") - if port, ok := params["failoverport"]; ok { - params["port"] = port - } - } - - if partner != "" { - params["server"] = partner - return openConnection(dsn, params) - } - - return nil, err - } - - if partner := sess.partner; partner != "" { - // append an instance so the port will be ignored when this value is used; - // tds does not provide the port number. - if !strings.Contains(partner, `\`) { - partner += `\.` - } - partnersCache.Set(dsn, partner) - } - - return &MssqlConn{sess}, nil -} - -func (c *MssqlConn) Close() error { - return c.sess.buf.transport.Close() -} - -type MssqlStmt struct { - c *MssqlConn - query string - paramCount int -} - -func (c *MssqlConn) Prepare(query string) (driver.Stmt, error) { - q, paramCount := parseParams(query) - return &MssqlStmt{c, q, paramCount}, nil -} - -func (s *MssqlStmt) Close() error { - return nil -} - -func (s *MssqlStmt) NumInput() int { - return s.paramCount -} - -func (s *MssqlStmt) sendQuery(args []driver.Value) (err error) { - headers := []headerStruct{ - {hdrtype: dataStmHdrTransDescr, - data: transDescrHdr{s.c.sess.tranid, 1}.pack()}, - } - if len(args) != s.paramCount { - return errors.New(fmt.Sprintf("sql: expected %d parameters, got %d", s.paramCount, len(args))) - } - if s.c.sess.logFlags&logSQL != 0 { - s.c.sess.log.Println(s.query) - } - if s.c.sess.logFlags&logParams != 0 && len(args) > 0 { - for i := 0; i < len(args); i++ { - s.c.sess.log.Printf("\t@p%d\t%v\n", i+1, args[i]) - } - - } - if len(args) == 0 { - if err = sendSqlBatch72(s.c.sess.buf, s.query, headers); err != nil { - if s.c.sess.tranid != 0 { - return err - } - return CheckBadConn(err) - } - } else { - params := make([]Param, len(args)+2) - decls := make([]string, len(args)) - params[0], err = s.makeParam(s.query) - if err != nil { - return - } - for i, val := range args { - params[i+2], err = s.makeParam(val) - if err != nil { - return - } - name := fmt.Sprintf("@p%d", i+1) - params[i+2].Name = name - decls[i] = fmt.Sprintf("%s %s", name, makeDecl(params[i+2].ti)) - } - params[1], err = s.makeParam(strings.Join(decls, ",")) - if err != nil { - return - } - if err = sendRpc(s.c.sess.buf, headers, Sp_ExecuteSql, 0, params); err != nil { - if s.c.sess.tranid != 0 { - return err - } - return CheckBadConn(err) - } - } - return -} - -func (s *MssqlStmt) Query(args []driver.Value) (res driver.Rows, err error) { - if err = s.sendQuery(args); err != nil { - return - } - tokchan := make(chan tokenStruct, 5) - go processResponse(s.c.sess, tokchan) - // process metadata - var cols []string -loop: - for tok := range tokchan { - switch token := tok.(type) { - case doneStruct: - break loop - case []columnStruct: - cols = make([]string, len(token)) - for i, col := range token { - cols[i] = col.ColName - } - break loop - case error: - if s.c.sess.tranid != 0 { - return nil, token - } - return nil, CheckBadConn(token) - } - } - return &MssqlRows{sess: s.c.sess, tokchan: tokchan, cols: cols}, nil -} - -func (s *MssqlStmt) Exec(args []driver.Value) (res driver.Result, err error) { - if err = s.sendQuery(args); err != nil { - return - } - tokchan := make(chan tokenStruct, 5) - go processResponse(s.c.sess, tokchan) - var rowCount int64 - for token := range tokchan { - switch token := token.(type) { - case doneInProcStruct: - if token.Status&doneCount != 0 { - rowCount = int64(token.RowCount) - } - case doneStruct: - if token.Status&doneCount != 0 { - rowCount = int64(token.RowCount) - } - case error: - if s.c.sess.logFlags&logErrors != 0 { - s.c.sess.log.Println("got error:", token) - } - if s.c.sess.tranid != 0 { - return nil, token - } - return nil, CheckBadConn(token) - } - } - return &MssqlResult{s.c, rowCount}, nil -} - -type MssqlRows struct { - sess *tdsSession - cols []string - tokchan chan tokenStruct -} - -func (rc *MssqlRows) Close() error { - for _ = range rc.tokchan { - } - rc.tokchan = nil - return nil -} - -func (rc *MssqlRows) Columns() (res []string) { - return rc.cols -} - -func (rc *MssqlRows) Next(dest []driver.Value) (err error) { - for tok := range rc.tokchan { - switch tokdata := tok.(type) { - case []columnStruct: - return streamErrorf("Unexpected token COLMETADATA") - case []interface{}: - for i := range dest { - dest[i] = tokdata[i] - } - return nil - case error: - return tokdata - } - } - return io.EOF -} - -func (s *MssqlStmt) makeParam(val driver.Value) (res Param, err error) { - if val == nil { - res.ti.TypeId = typeNVarChar - res.buffer = nil - res.ti.Size = 2 - return - } - switch val := val.(type) { - case int64: - res.ti.TypeId = typeIntN - res.buffer = make([]byte, 8) - res.ti.Size = 8 - binary.LittleEndian.PutUint64(res.buffer, uint64(val)) - case float64: - res.ti.TypeId = typeFltN - res.ti.Size = 8 - res.buffer = make([]byte, 8) - binary.LittleEndian.PutUint64(res.buffer, math.Float64bits(val)) - case []byte: - res.ti.TypeId = typeBigVarBin - res.ti.Size = len(val) - res.buffer = val - case string: - res.ti.TypeId = typeNVarChar - res.buffer = str2ucs2(val) - res.ti.Size = len(res.buffer) - case bool: - res.ti.TypeId = typeBitN - res.ti.Size = 1 - res.buffer = make([]byte, 1) - if val { - res.buffer[0] = 1 - } - case time.Time: - if s.c.sess.loginAck.TDSVersion >= verTDS73 { - res.ti.TypeId = typeDateTimeOffsetN - res.ti.Scale = 7 - res.ti.Size = 10 - buf := make([]byte, 10) - res.buffer = buf - days, ns := dateTime2(val) - ns /= 100 - buf[0] = byte(ns) - buf[1] = byte(ns >> 8) - buf[2] = byte(ns >> 16) - buf[3] = byte(ns >> 24) - buf[4] = byte(ns >> 32) - buf[5] = byte(days) - buf[6] = byte(days >> 8) - buf[7] = byte(days >> 16) - _, offset := val.Zone() - offset /= 60 - buf[8] = byte(offset) - buf[9] = byte(offset >> 8) - } else { - res.ti.TypeId = typeDateTimeN - res.ti.Size = 8 - res.buffer = make([]byte, 8) - ref := time.Date(1900, 1, 1, 0, 0, 0, 0, time.UTC) - dur := val.Sub(ref) - days := dur / (24 * time.Hour) - tm := (300 * (dur % (24 * time.Hour))) / time.Second - binary.LittleEndian.PutUint32(res.buffer[0:4], uint32(days)) - binary.LittleEndian.PutUint32(res.buffer[4:8], uint32(tm)) - } - default: - err = fmt.Errorf("mssql: unknown type for %T", val) - return - } - return -} - -type MssqlResult struct { - c *MssqlConn - rowsAffected int64 -} - -func (r *MssqlResult) RowsAffected() (int64, error) { - return r.rowsAffected, nil -} - -func (r *MssqlResult) LastInsertId() (int64, error) { - s, err := r.c.Prepare("select cast(@@identity as bigint)") - if err != nil { - return 0, err - } - defer s.Close() - rows, err := s.Query(nil) - if err != nil { - return 0, err - } - defer rows.Close() - dest := make([]driver.Value, 1) - err = rows.Next(dest) - if err != nil { - return 0, err - } - if dest[0] == nil { - return -1, errors.New("There is no generated identity value") - } - lastInsertId := dest[0].(int64) - return lastInsertId, nil -} - -type partners struct { - mu sync.RWMutex - v map[string]string -} - -func (p *partners) Set(key, value string) error { - p.mu.Lock() - defer p.mu.Unlock() - if _, ok := p.v[key]; ok { - return errors.New("key already exists") - } - - p.v[key] = value - return nil -} - -func (p *partners) Get(key string) (value string) { - p.mu.RLock() - value = p.v[key] - p.mu.RUnlock() - return -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/mssql_go1.3.go b/vendor/github.com/denisenkom/go-mssqldb/mssql_go1.3.go deleted file mode 100644 index 22c6891d8..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/mssql_go1.3.go +++ /dev/null @@ -1,11 +0,0 @@ -// +build go1.3 - -package mssql - -import ( - "net" -) - -func createDialer(p *connectParams) *net.Dialer { - return &net.Dialer{Timeout: p.dial_timeout, KeepAlive: p.keepAlive} -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/mssql_go1.3pre.go b/vendor/github.com/denisenkom/go-mssqldb/mssql_go1.3pre.go deleted file mode 100644 index 3c7e72716..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/mssql_go1.3pre.go +++ /dev/null @@ -1,11 +0,0 @@ -// +build !go1.3 - -package mssql - -import ( - "net" -) - -func createDialer(p *connectParams) *net.Dialer { - return &net.Dialer{Timeout: p.dial_timeout} -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/net.go b/vendor/github.com/denisenkom/go-mssqldb/net.go deleted file mode 100644 index 72a87340d..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/net.go +++ /dev/null @@ -1,99 +0,0 @@ -package mssql - -import ( - "fmt" - "net" - "time" -) - -type timeoutConn struct { - c net.Conn - timeout time.Duration - buf *tdsBuffer - packetPending bool - continueRead bool -} - -func NewTimeoutConn(conn net.Conn, timeout time.Duration) *timeoutConn { - return &timeoutConn{ - c: conn, - timeout: timeout, - } -} - -func (c *timeoutConn) Read(b []byte) (n int, err error) { - if c.buf != nil { - if c.packetPending { - c.packetPending = false - err = c.buf.FinishPacket() - if err != nil { - err = fmt.Errorf("Cannot send handshake packet: %s", err.Error()) - return - } - c.continueRead = false - } - if !c.continueRead { - var packet uint8 - packet, err = c.buf.BeginRead() - if err != nil { - err = fmt.Errorf("Cannot read handshake packet: %s", err.Error()) - return - } - if packet != packPrelogin { - err = fmt.Errorf("unexpected packet %d, expecting prelogin", packet) - return - } - c.continueRead = true - } - n, err = c.buf.Read(b) - return - } - err = c.c.SetDeadline(time.Now().Add(c.timeout)) - if err != nil { - return - } - return c.c.Read(b) -} - -func (c *timeoutConn) Write(b []byte) (n int, err error) { - if c.buf != nil { - if !c.packetPending { - c.buf.BeginPacket(packPrelogin) - c.packetPending = true - } - n, err = c.buf.Write(b) - if err != nil { - return - } - return - } - err = c.c.SetDeadline(time.Now().Add(c.timeout)) - if err != nil { - return - } - return c.c.Write(b) -} - -func (c timeoutConn) Close() error { - return c.c.Close() -} - -func (c timeoutConn) LocalAddr() net.Addr { - return c.c.LocalAddr() -} - -func (c timeoutConn) RemoteAddr() net.Addr { - return c.c.RemoteAddr() -} - -func (c timeoutConn) SetDeadline(t time.Time) error { - panic("Not implemented") -} - -func (c timeoutConn) SetReadDeadline(t time.Time) error { - panic("Not implemented") -} - -func (c timeoutConn) SetWriteDeadline(t time.Time) error { - panic("Not implemented") -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/ntlm.go b/vendor/github.com/denisenkom/go-mssqldb/ntlm.go deleted file mode 100644 index f853435c6..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/ntlm.go +++ /dev/null @@ -1,283 +0,0 @@ -// +build !windows - -package mssql - -import ( - "crypto/des" - "crypto/md5" - "crypto/rand" - "encoding/binary" - "errors" - "strings" - "unicode/utf16" - - "golang.org/x/crypto/md4" -) - -const ( - NEGOTIATE_MESSAGE = 1 - CHALLENGE_MESSAGE = 2 - AUTHENTICATE_MESSAGE = 3 -) - -const ( - NEGOTIATE_UNICODE = 0x00000001 - NEGOTIATE_OEM = 0x00000002 - NEGOTIATE_TARGET = 0x00000004 - NEGOTIATE_SIGN = 0x00000010 - NEGOTIATE_SEAL = 0x00000020 - NEGOTIATE_DATAGRAM = 0x00000040 - NEGOTIATE_LMKEY = 0x00000080 - NEGOTIATE_NTLM = 0x00000200 - NEGOTIATE_ANONYMOUS = 0x00000800 - NEGOTIATE_OEM_DOMAIN_SUPPLIED = 0x00001000 - NEGOTIATE_OEM_WORKSTATION_SUPPLIED = 0x00002000 - NEGOTIATE_ALWAYS_SIGN = 0x00008000 - NEGOTIATE_TARGET_TYPE_DOMAIN = 0x00010000 - NEGOTIATE_TARGET_TYPE_SERVER = 0x00020000 - NEGOTIATE_EXTENDED_SESSIONSECURITY = 0x00080000 - NEGOTIATE_IDENTIFY = 0x00100000 - REQUEST_NON_NT_SESSION_KEY = 0x00400000 - NEGOTIATE_TARGET_INFO = 0x00800000 - NEGOTIATE_VERSION = 0x02000000 - NEGOTIATE_128 = 0x20000000 - NEGOTIATE_KEY_EXCH = 0x40000000 - NEGOTIATE_56 = 0x80000000 -) - -const NEGOTIATE_FLAGS = NEGOTIATE_UNICODE | - NEGOTIATE_NTLM | - NEGOTIATE_OEM_DOMAIN_SUPPLIED | - NEGOTIATE_OEM_WORKSTATION_SUPPLIED | - NEGOTIATE_ALWAYS_SIGN | - NEGOTIATE_EXTENDED_SESSIONSECURITY - -type NTLMAuth struct { - Domain string - UserName string - Password string - Workstation string -} - -func getAuth(user, password, service, workstation string) (Auth, bool) { - if !strings.ContainsRune(user, '\\') { - return nil, false - } - domain_user := strings.SplitN(user, "\\", 2) - return &NTLMAuth{ - Domain: domain_user[0], - UserName: domain_user[1], - Password: password, - Workstation: workstation, - }, true -} - -func utf16le(val string) []byte { - var v []byte - for _, r := range val { - if utf16.IsSurrogate(r) { - r1, r2 := utf16.EncodeRune(r) - v = append(v, byte(r1), byte(r1>>8)) - v = append(v, byte(r2), byte(r2>>8)) - } else { - v = append(v, byte(r), byte(r>>8)) - } - } - return v -} - -func (auth *NTLMAuth) InitialBytes() ([]byte, error) { - domain_len := len(auth.Domain) - workstation_len := len(auth.Workstation) - msg := make([]byte, 40+domain_len+workstation_len) - copy(msg, []byte("NTLMSSP\x00")) - binary.LittleEndian.PutUint32(msg[8:], NEGOTIATE_MESSAGE) - binary.LittleEndian.PutUint32(msg[12:], NEGOTIATE_FLAGS) - // Domain Name Fields - binary.LittleEndian.PutUint16(msg[16:], uint16(domain_len)) - binary.LittleEndian.PutUint16(msg[18:], uint16(domain_len)) - binary.LittleEndian.PutUint32(msg[20:], 40) - // Workstation Fields - binary.LittleEndian.PutUint16(msg[24:], uint16(workstation_len)) - binary.LittleEndian.PutUint16(msg[26:], uint16(workstation_len)) - binary.LittleEndian.PutUint32(msg[28:], uint32(40+domain_len)) - // Version - binary.LittleEndian.PutUint32(msg[32:], 0) - binary.LittleEndian.PutUint32(msg[36:], 0) - // Payload - copy(msg[40:], auth.Domain) - copy(msg[40+domain_len:], auth.Workstation) - return msg, nil -} - -var errorNTLM = errors.New("NTLM protocol error") - -func createDesKey(bytes, material []byte) { - material[0] = bytes[0] - material[1] = (byte)(bytes[0]<<7 | (bytes[1]&0xff)>>1) - material[2] = (byte)(bytes[1]<<6 | (bytes[2]&0xff)>>2) - material[3] = (byte)(bytes[2]<<5 | (bytes[3]&0xff)>>3) - material[4] = (byte)(bytes[3]<<4 | (bytes[4]&0xff)>>4) - material[5] = (byte)(bytes[4]<<3 | (bytes[5]&0xff)>>5) - material[6] = (byte)(bytes[5]<<2 | (bytes[6]&0xff)>>6) - material[7] = (byte)(bytes[6] << 1) -} - -func oddParity(bytes []byte) { - for i := 0; i < len(bytes); i++ { - b := bytes[i] - needsParity := (((b >> 7) ^ (b >> 6) ^ (b >> 5) ^ (b >> 4) ^ (b >> 3) ^ (b >> 2) ^ (b >> 1)) & 0x01) == 0 - if needsParity { - bytes[i] = bytes[i] | byte(0x01) - } else { - bytes[i] = bytes[i] & byte(0xfe) - } - } -} - -func encryptDes(key []byte, cleartext []byte, ciphertext []byte) { - var desKey [8]byte - createDesKey(key, desKey[:]) - cipher, err := des.NewCipher(desKey[:]) - if err != nil { - panic(err) - } - cipher.Encrypt(ciphertext, cleartext) -} - -func response(challenge [8]byte, hash [21]byte) (ret [24]byte) { - encryptDes(hash[:7], challenge[:], ret[:8]) - encryptDes(hash[7:14], challenge[:], ret[8:16]) - encryptDes(hash[14:], challenge[:], ret[16:]) - return -} - -func lmHash(password string) (hash [21]byte) { - var lmpass [14]byte - copy(lmpass[:14], []byte(strings.ToUpper(password))) - magic := []byte("KGS!@#$%") - encryptDes(lmpass[:7], magic, hash[:8]) - encryptDes(lmpass[7:], magic, hash[8:]) - return -} - -func lmResponse(challenge [8]byte, password string) [24]byte { - hash := lmHash(password) - return response(challenge, hash) -} - -func ntlmHash(password string) (hash [21]byte) { - h := md4.New() - h.Write(utf16le(password)) - h.Sum(hash[:0]) - return -} - -func ntResponse(challenge [8]byte, password string) [24]byte { - hash := ntlmHash(password) - return response(challenge, hash) -} - -func clientChallenge() (nonce [8]byte) { - _, err := rand.Read(nonce[:]) - if err != nil { - panic(err) - } - return -} - -func ntlmSessionResponse(clientNonce [8]byte, serverChallenge [8]byte, password string) [24]byte { - var sessionHash [16]byte - h := md5.New() - h.Write(serverChallenge[:]) - h.Write(clientNonce[:]) - h.Sum(sessionHash[:0]) - var hash [8]byte - copy(hash[:], sessionHash[:8]) - passwordHash := ntlmHash(password) - return response(hash, passwordHash) -} - -func (auth *NTLMAuth) NextBytes(bytes []byte) ([]byte, error) { - if string(bytes[0:8]) != "NTLMSSP\x00" { - return nil, errorNTLM - } - if binary.LittleEndian.Uint32(bytes[8:12]) != CHALLENGE_MESSAGE { - return nil, errorNTLM - } - flags := binary.LittleEndian.Uint32(bytes[20:24]) - var challenge [8]byte - copy(challenge[:], bytes[24:32]) - - var lm, nt []byte - if (flags & NEGOTIATE_EXTENDED_SESSIONSECURITY) != 0 { - nonce := clientChallenge() - var lm_bytes [24]byte - copy(lm_bytes[:8], nonce[:]) - lm = lm_bytes[:] - nt_bytes := ntlmSessionResponse(nonce, challenge, auth.Password) - nt = nt_bytes[:] - } else { - lm_bytes := lmResponse(challenge, auth.Password) - lm = lm_bytes[:] - nt_bytes := ntResponse(challenge, auth.Password) - nt = nt_bytes[:] - } - lm_len := len(lm) - nt_len := len(nt) - - domain16 := utf16le(auth.Domain) - domain_len := len(domain16) - user16 := utf16le(auth.UserName) - user_len := len(user16) - workstation16 := utf16le(auth.Workstation) - workstation_len := len(workstation16) - - msg := make([]byte, 88+lm_len+nt_len+domain_len+user_len+workstation_len) - copy(msg, []byte("NTLMSSP\x00")) - binary.LittleEndian.PutUint32(msg[8:], AUTHENTICATE_MESSAGE) - // Lm Challenge Response Fields - binary.LittleEndian.PutUint16(msg[12:], uint16(lm_len)) - binary.LittleEndian.PutUint16(msg[14:], uint16(lm_len)) - binary.LittleEndian.PutUint32(msg[16:], 88) - // Nt Challenge Response Fields - binary.LittleEndian.PutUint16(msg[20:], uint16(nt_len)) - binary.LittleEndian.PutUint16(msg[22:], uint16(nt_len)) - binary.LittleEndian.PutUint32(msg[24:], uint32(88+lm_len)) - // Domain Name Fields - binary.LittleEndian.PutUint16(msg[28:], uint16(domain_len)) - binary.LittleEndian.PutUint16(msg[30:], uint16(domain_len)) - binary.LittleEndian.PutUint32(msg[32:], uint32(88+lm_len+nt_len)) - // User Name Fields - binary.LittleEndian.PutUint16(msg[36:], uint16(user_len)) - binary.LittleEndian.PutUint16(msg[38:], uint16(user_len)) - binary.LittleEndian.PutUint32(msg[40:], uint32(88+lm_len+nt_len+domain_len)) - // Workstation Fields - binary.LittleEndian.PutUint16(msg[44:], uint16(workstation_len)) - binary.LittleEndian.PutUint16(msg[46:], uint16(workstation_len)) - binary.LittleEndian.PutUint32(msg[48:], uint32(88+lm_len+nt_len+domain_len+user_len)) - // Encrypted Random Session Key Fields - binary.LittleEndian.PutUint16(msg[52:], 0) - binary.LittleEndian.PutUint16(msg[54:], 0) - binary.LittleEndian.PutUint32(msg[56:], uint32(88+lm_len+nt_len+domain_len+user_len+workstation_len)) - // Negotiate Flags - binary.LittleEndian.PutUint32(msg[60:], flags) - // Version - binary.LittleEndian.PutUint32(msg[64:], 0) - binary.LittleEndian.PutUint32(msg[68:], 0) - // MIC - binary.LittleEndian.PutUint32(msg[72:], 0) - binary.LittleEndian.PutUint32(msg[76:], 0) - binary.LittleEndian.PutUint32(msg[88:], 0) - binary.LittleEndian.PutUint32(msg[84:], 0) - // Payload - copy(msg[88:], lm) - copy(msg[88+lm_len:], nt) - copy(msg[88+lm_len+nt_len:], domain16) - copy(msg[88+lm_len+nt_len+domain_len:], user16) - copy(msg[88+lm_len+nt_len+domain_len+user_len:], workstation16) - return msg, nil -} - -func (auth *NTLMAuth) Free() { -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/ntlm_test.go b/vendor/github.com/denisenkom/go-mssqldb/ntlm_test.go deleted file mode 100644 index db56f4e38..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/ntlm_test.go +++ /dev/null @@ -1,76 +0,0 @@ -// +build !windows - -package mssql - -import ( - "encoding/hex" - "testing" -) - -func TestLMOWFv1(t *testing.T) { - hash := lmHash("Password") - val := [21]byte{ - 0xe5, 0x2c, 0xac, 0x67, 0x41, 0x9a, 0x9a, 0x22, - 0x4a, 0x3b, 0x10, 0x8f, 0x3f, 0xa6, 0xcb, 0x6d, - 0, 0, 0, 0, 0, - } - if hash != val { - t.Errorf("got:\n%sexpected:\n%s", hex.Dump(hash[:]), hex.Dump(val[:])) - } -} - -func TestNTLMOWFv1(t *testing.T) { - hash := ntlmHash("Password") - val := [21]byte{ - 0xa4, 0xf4, 0x9c, 0x40, 0x65, 0x10, 0xbd, 0xca, 0xb6, 0x82, 0x4e, 0xe7, 0xc3, 0x0f, 0xd8, 0x52, - 0, 0, 0, 0, 0, - } - if hash != val { - t.Errorf("got:\n%sexpected:\n%s", hex.Dump(hash[:]), hex.Dump(val[:])) - } -} - -func TestNTLMv1Response(t *testing.T) { - challenge := [8]byte{ - 0x01, 0x23, 0x45, 0x67, 0x89, 0xab, 0xcd, 0xef, - } - nt := ntResponse(challenge, "Password") - val := [24]byte{ - 0x67, 0xc4, 0x30, 0x11, 0xf3, 0x02, 0x98, 0xa2, 0xad, 0x35, 0xec, 0xe6, 0x4f, 0x16, 0x33, 0x1c, - 0x44, 0xbd, 0xbe, 0xd9, 0x27, 0x84, 0x1f, 0x94, - } - if nt != val { - t.Errorf("got:\n%sexpected:\n%s", hex.Dump(nt[:]), hex.Dump(val[:])) - } -} - -func TestLMv1Response(t *testing.T) { - challenge := [8]byte{ - 0x01, 0x23, 0x45, 0x67, 0x89, 0xab, 0xcd, 0xef, - } - nt := lmResponse(challenge, "Password") - val := [24]byte{ - 0x98, 0xde, 0xf7, 0xb8, 0x7f, 0x88, 0xaa, 0x5d, 0xaf, 0xe2, 0xdf, 0x77, 0x96, 0x88, 0xa1, 0x72, - 0xde, 0xf1, 0x1c, 0x7d, 0x5c, 0xcd, 0xef, 0x13, - } - if nt != val { - t.Errorf("got:\n%sexpected:\n%s", hex.Dump(nt[:]), hex.Dump(val[:])) - } -} - -func TestNTLMSessionResponse(t *testing.T) { - challenge := [8]byte{ - 0x01, 0x23, 0x45, 0x67, 0x89, 0xab, 0xcd, 0xef, - } - nonce := [8]byte{ - 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, - } - nt := ntlmSessionResponse(nonce, challenge, "Password") - val := [24]byte{ - 0x75, 0x37, 0xf8, 0x03, 0xae, 0x36, 0x71, 0x28, 0xca, 0x45, 0x82, 0x04, 0xbd, 0xe7, 0xca, 0xf8, - 0x1e, 0x97, 0xed, 0x26, 0x83, 0x26, 0x72, 0x32, - } - if nt != val { - t.Errorf("got:\n%sexpected:\n%s", hex.Dump(nt[:]), hex.Dump(val[:])) - } -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/parser.go b/vendor/github.com/denisenkom/go-mssqldb/parser.go deleted file mode 100644 index 9e37c16a6..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/parser.go +++ /dev/null @@ -1,227 +0,0 @@ -package mssql - -import ( - "bytes" - "io" - "strconv" -) - -type parser struct { - r *bytes.Reader - w bytes.Buffer - paramCount int - paramMax int -} - -func (p *parser) next() (rune, bool) { - ch, _, err := p.r.ReadRune() - if err != nil { - if err != io.EOF { - panic(err) - } - return 0, false - } - return ch, true -} - -func (p *parser) unread() { - err := p.r.UnreadRune() - if err != nil { - panic(err) - } -} - -func (p *parser) write(ch rune) { - p.w.WriteRune(ch) -} - -type stateFunc func(*parser) stateFunc - -func parseParams(query string) (string, int) { - p := &parser{ - r: bytes.NewReader([]byte(query)), - } - state := parseNormal - for state != nil { - state = state(p) - } - return p.w.String(), p.paramMax -} - -func parseNormal(p *parser) stateFunc { - for { - ch, ok := p.next() - if !ok { - return nil - } - if ch == '?' { - return parseParameter - } else if ch == '$' || ch == ':' { - ch2, ok := p.next() - if !ok { - p.write(ch) - return nil - } - p.unread() - if ch2 >= '0' && ch2 <= '9' { - return parseParameter - } - } - p.write(ch) - switch ch { - case '\'': - return parseQuote - case '"': - return parseDoubleQuote - case '[': - return parseBracket - case '-': - return parseLineComment - case '/': - return parseComment - } - } -} - -func parseParameter(p *parser) stateFunc { - var paramN int - var ok bool - for { - var ch rune - ch, ok = p.next() - if ok && ch >= '0' && ch <= '9' { - paramN = paramN*10 + int(ch-'0') - } else { - break - } - } - if ok { - p.unread() - } - if paramN == 0 { - p.paramCount++ - paramN = p.paramCount - } - if paramN > p.paramMax { - p.paramMax = paramN - } - p.w.WriteString("@p") - p.w.WriteString(strconv.Itoa(paramN)) - if !ok { - return nil - } - return parseNormal -} - -func parseQuote(p *parser) stateFunc { - for { - ch, ok := p.next() - if !ok { - return nil - } - p.write(ch) - if ch == '\'' { - return parseNormal - } - } -} - -func parseDoubleQuote(p *parser) stateFunc { - for { - ch, ok := p.next() - if !ok { - return nil - } - p.write(ch) - if ch == '"' { - return parseNormal - } - } -} - -func parseBracket(p *parser) stateFunc { - for { - ch, ok := p.next() - if !ok { - return nil - } - p.write(ch) - if ch == ']' { - ch, ok = p.next() - if !ok { - return nil - } - if ch != ']' { - p.unread() - return parseNormal - } - p.write(ch) - } - } -} - -func parseLineComment(p *parser) stateFunc { - ch, ok := p.next() - if !ok { - return nil - } - if ch != '-' { - p.unread() - return parseNormal - } - p.write(ch) - for { - ch, ok = p.next() - if !ok { - return nil - } - p.write(ch) - if ch == '\n' { - return parseNormal - } - } -} - -func parseComment(p *parser) stateFunc { - var nested int - ch, ok := p.next() - if !ok { - return nil - } - if ch != '*' { - p.unread() - return parseNormal - } - p.write(ch) - for { - ch, ok = p.next() - if !ok { - return nil - } - p.write(ch) - for ch == '*' { - ch, ok = p.next() - if !ok { - return nil - } - p.write(ch) - if ch == '/' { - if nested == 0 { - return parseNormal - } else { - nested-- - } - } - } - for ch == '/' { - ch, ok = p.next() - if !ok { - return nil - } - p.write(ch) - if ch == '*' { - nested++ - } - } - } -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/parser_test.go b/vendor/github.com/denisenkom/go-mssqldb/parser_test.go deleted file mode 100644 index 0901b2a89..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/parser_test.go +++ /dev/null @@ -1,50 +0,0 @@ -package mssql - -import ( - "testing" -) - -func TestParseParams(t *testing.T) { - values := []struct { - s string - d string - n int - }{ - {"select ?", "select @p1", 1}, - {"select ?, ?", "select @p1, @p2", 2}, - {"select ? -- ?", "select @p1 -- ?", 1}, - {"select ? -- ?\n, ?", "select @p1 -- ?\n, @p2", 2}, - {"select ? - ?", "select @p1 - @p2", 2}, - {"select ? /* ? */, ?", "select @p1 /* ? */, @p2", 2}, - {"select ? /* ? * ? */, ?", "select @p1 /* ? * ? */, @p2", 2}, - {"select \"foo?\", [foo?], 'foo?', ?", "select \"foo?\", [foo?], 'foo?', @p1", 1}, - {"select \"x\"\"y\", [x]]y], 'x''y', ?", "select \"x\"\"y\", [x]]y], 'x''y', @p1", 1}, - {"select \"foo?\", ?", "select \"foo?\", @p1", 1}, - {"select 'foo?', ?", "select 'foo?', @p1", 1}, - {"select [foo?], ?", "select [foo?], @p1", 1}, - {"select $1", "select @p1", 1}, - {"select $1, $2", "select @p1, @p2", 2}, - {"select $1, $1", "select @p1, @p1", 1}, - {"select :1", "select @p1", 1}, - {"select :1, :2", "select @p1, @p2", 2}, - {"select :1, :1", "select @p1, @p1", 1}, - {"select ?1", "select @p1", 1}, - {"select ?1, ?2", "select @p1, @p2", 2}, - {"select ?1, ?1", "select @p1, @p1", 1}, - {"select $12", "select @p12", 12}, - {"select ? /* ? /* ? */ ? */ ?", "select @p1 /* ? /* ? */ ? */ @p2", 2}, - {"select ? /* ? / ? */ ?", "select @p1 /* ? / ? */ @p2", 2}, - {"select $", "select $", 0}, - {"select x::y", "select x::y", 0}, - } - - for _, v := range values { - d, n := parseParams(v.s) - if d != v.d { - t.Error("Parse params don't match ", d, v.d) - } - if n != v.n { - t.Error("Parse number of params don't match", n, v.n) - } - } -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/queries_test.go b/vendor/github.com/denisenkom/go-mssqldb/queries_test.go deleted file mode 100644 index 0f0a7c00e..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/queries_test.go +++ /dev/null @@ -1,685 +0,0 @@ -package mssql - -import ( - "bytes" - "database/sql" - "fmt" - "log" - "math" - "net" - "os" - "strings" - "testing" - "time" -) - -func TestSelect(t *testing.T) { - conn := open(t) - defer conn.Close() - - type testStruct struct { - sql string - val interface{} - } - - longstr := strings.Repeat("x", 10000) - - values := []testStruct{ - {"1", int64(1)}, - {"-1", int64(-1)}, - {"cast(1 as int)", int64(1)}, - {"cast(-1 as int)", int64(-1)}, - {"cast(1 as tinyint)", int64(1)}, - {"cast(1 as smallint)", int64(1)}, - {"cast(-1 as smallint)", int64(-1)}, - {"cast(1 as bigint)", int64(1)}, - {"cast(-1 as bigint)", int64(-1)}, - {"cast(1 as bit)", true}, - {"cast(0 as bit)", false}, - {"'abc'", string("abc")}, - {"cast(0.5 as float)", float64(0.5)}, - {"cast(0.5 as real)", float64(0.5)}, - {"cast(1 as decimal)", []byte("1")}, - {"cast(1.2345 as money)", []byte("1.2345")}, - {"cast(-1.2345 as money)", []byte("-1.2345")}, - {"cast(1.2345 as smallmoney)", []byte("1.2345")}, - {"cast(-1.2345 as smallmoney)", []byte("-1.2345")}, - {"cast(0.5 as decimal(18,1))", []byte("0.5")}, - {"cast(-0.5 as decimal(18,1))", []byte("-0.5")}, - {"cast(-0.5 as numeric(18,1))", []byte("-0.5")}, - {"cast(4294967296 as numeric(20,0))", []byte("4294967296")}, - {"cast(-0.5 as numeric(18,2))", []byte("-0.50")}, - {"N'abc'", string("abc")}, - {"cast(null as nvarchar(3))", nil}, - {"NULL", nil}, - {"cast('2000-01-01' as datetime)", time.Date(2000, 1, 1, 0, 0, 0, 0, time.UTC)}, - {"cast('2000-01-01T12:13:14.12' as datetime)", - time.Date(2000, 1, 1, 12, 13, 14, 120000000, time.UTC)}, - {"cast('2014-06-26 11:08:09.673' as datetime)", time.Date(2014, 06, 26, 11, 8, 9, 673000000, time.UTC)}, - {"cast(NULL as datetime)", nil}, - {"cast('2000-01-01T12:13:00' as smalldatetime)", - time.Date(2000, 1, 1, 12, 13, 0, 0, time.UTC)}, - {"cast(0x6F9619FF8B86D011B42D00C04FC964FF as uniqueidentifier)", - []byte{0x6F, 0x96, 0x19, 0xFF, 0x8B, 0x86, 0xD0, 0x11, 0xB4, 0x2D, 0x00, 0xC0, 0x4F, 0xC9, 0x64, 0xFF}}, - {"cast(NULL as uniqueidentifier)", nil}, - {"cast(0x1234 as varbinary(2))", []byte{0x12, 0x34}}, - {"cast(N'abc' as nvarchar(max))", "abc"}, - {"cast(null as nvarchar(max))", nil}, - {"cast('' as xml)", ""}, - {"cast('abc' as text)", "abc"}, - {"cast(null as text)", nil}, - {"cast(N'abc' as ntext)", "abc"}, - {"cast(0x1234 as image)", []byte{0x12, 0x34}}, - {"cast(N'проверка' as nvarchar(max))", "проверка"}, - {"cast(N'Δοκιμή' as nvarchar(max))", "Δοκιμή"}, - {"cast(cast(N'สวัสดี' as nvarchar(max)) collate Thai_CI_AI as varchar(max))", "สวัสดี"}, // cp874 - {"cast(cast(N'你好' as nvarchar(max)) collate Chinese_PRC_CI_AI as varchar(max))", "你好"}, // cp936 - {"cast(cast(N'こんにちは' as nvarchar(max)) collate Japanese_CI_AI as varchar(max))", "こんにちは"}, // cp939 - {"cast(cast(N'안녕하세요.' as nvarchar(max)) collate Korean_90_CI_AI as varchar(max))", "안녕하세요."}, // cp949 - {"cast(cast(N'你好' as nvarchar(max)) collate Chinese_Hong_Kong_Stroke_90_CI_AI as varchar(max))", "你好"}, // cp950 - {"cast(cast(N'cześć' as nvarchar(max)) collate Polish_CI_AI as varchar(max))", "cześć"}, // cp1250 - {"cast(cast(N'Алло' as nvarchar(max)) collate Cyrillic_General_CI_AI as varchar(max))", "Алло"}, // cp1251 - {"cast(cast(N'Bonjour' as nvarchar(max)) collate French_CI_AI as varchar(max))", "Bonjour"}, // cp1252 - {"cast(cast(N'Γεια σας' as nvarchar(max)) collate Greek_CI_AI as varchar(max))", "Γεια σας"}, // cp1253 - {"cast(cast(N'Merhaba' as nvarchar(max)) collate Turkish_CI_AI as varchar(max))", "Merhaba"}, // cp1254 - {"cast(cast(N'שלום' as nvarchar(max)) collate Hebrew_CI_AI as varchar(max))", "שלום"}, // cp1255 - {"cast(cast(N'مرحبا' as nvarchar(max)) collate Arabic_CI_AI as varchar(max))", "مرحبا"}, // cp1256 - {"cast(cast(N'Sveiki' as nvarchar(max)) collate Lithuanian_CI_AI as varchar(max))", "Sveiki"}, // cp1257 - {"cast(cast(N'chào' as nvarchar(max)) collate Vietnamese_CI_AI as varchar(max))", "chào"}, // cp1258 - {fmt.Sprintf("cast(N'%s' as nvarchar(max))", longstr), longstr}, - {"cast(NULL as sql_variant)", nil}, - {"cast(cast(0x6F9619FF8B86D011B42D00C04FC964FF as uniqueidentifier) as sql_variant)", - []byte{0x6F, 0x96, 0x19, 0xFF, 0x8B, 0x86, 0xD0, 0x11, 0xB4, 0x2D, 0x00, 0xC0, 0x4F, 0xC9, 0x64, 0xFF}}, - {"cast(cast(1 as bit) as sql_variant)", true}, - {"cast(cast(10 as tinyint) as sql_variant)", int64(10)}, - {"cast(cast(-10 as smallint) as sql_variant)", int64(-10)}, - {"cast(cast(-20 as int) as sql_variant)", int64(-20)}, - {"cast(cast(-20 as bigint) as sql_variant)", int64(-20)}, - {"cast(cast('2000-01-01' as datetime) as sql_variant)", time.Date(2000, 1, 1, 0, 0, 0, 0, time.UTC)}, - {"cast(cast('2000-01-01T12:13:00' as smalldatetime) as sql_variant)", - time.Date(2000, 1, 1, 12, 13, 0, 0, time.UTC)}, - {"cast(cast(0.125 as real) as sql_variant)", float64(0.125)}, - {"cast(cast(0.125 as float) as sql_variant)", float64(0.125)}, - {"cast(cast(1.2345 as smallmoney) as sql_variant)", []byte("1.2345")}, - {"cast(cast(1.2345 as money) as sql_variant)", []byte("1.2345")}, - {"cast(cast(0x1234 as varbinary(2)) as sql_variant)", []byte{0x12, 0x34}}, - {"cast(cast(0x1234 as binary(2)) as sql_variant)", []byte{0x12, 0x34}}, - {"cast(cast(-0.5 as decimal(18,1)) as sql_variant)", []byte("-0.5")}, - {"cast(cast(-0.5 as numeric(18,1)) as sql_variant)", []byte("-0.5")}, - {"cast(cast('abc' as varchar(3)) as sql_variant)", "abc"}, - {"cast(cast('abc' as char(3)) as sql_variant)", "abc"}, - {"cast(N'abc' as sql_variant)", "abc"}, - } - - for _, test := range values { - stmt, err := conn.Prepare("select " + test.sql) - if err != nil { - t.Error("Prepare failed:", test.sql, err.Error()) - return - } - defer stmt.Close() - - row := stmt.QueryRow() - var retval interface{} - err = row.Scan(&retval) - if err != nil { - t.Error("Scan failed:", test.sql, err.Error()) - continue - } - var same bool - switch decodedval := retval.(type) { - case []byte: - switch decodedvaltest := test.val.(type) { - case []byte: - same = bytes.Equal(decodedval, decodedvaltest) - default: - same = false - } - default: - same = retval == test.val - } - if !same { - t.Errorf("Values don't match '%s' '%s' for test: %s", retval, test.val, test.sql) - continue - } - } -} - -func TestSelectNewTypes(t *testing.T) { - conn := open(t) - defer conn.Close() - var ver string - err := conn.QueryRow("select SERVERPROPERTY('productversion')").Scan(&ver) - if err != nil { - t.Fatalf("cannot select productversion: %s", err) - } - var n int - _, err = fmt.Sscanf(ver, "%d", &n) - if err != nil { - t.Fatalf("cannot parse productversion: %s", err) - } - // 8 is SQL 2000, 9 is SQL 2005, 10 is SQL 2008, 11 is SQL 2012 - if n < 10 { - return - } - // run tests for new data types available only in SQL Server 2008 and later - type testStruct struct { - sql string - val interface{} - } - values := []testStruct{ - {"cast('2000-01-01' as date)", - time.Date(2000, 1, 1, 0, 0, 0, 0, time.UTC)}, - {"cast(NULL as date)", nil}, - {"cast('00:00:45.123' as time(3))", - time.Date(1, 1, 1, 00, 00, 45, 123000000, time.UTC)}, - {"cast('11:56:45.123' as time(3))", - time.Date(1, 1, 1, 11, 56, 45, 123000000, time.UTC)}, - {"cast('11:56:45' as time(0))", - time.Date(1, 1, 1, 11, 56, 45, 0, time.UTC)}, - {"cast('2010-11-15T11:56:45.123' as datetime2(3))", - time.Date(2010, 11, 15, 11, 56, 45, 123000000, time.UTC)}, - {"cast('2010-11-15T11:56:45' as datetime2(0))", - time.Date(2010, 11, 15, 11, 56, 45, 0, time.UTC)}, - //{"cast('2010-11-15T11:56:45.123+10:00' as datetimeoffset(3))", - // time.Date(2010, 11, 15, 11, 56, 45, 123000000, time.FixedZone("", 10*60*60)) }, - {"cast(cast('2000-01-01' as date) as sql_variant)", - time.Date(2000, 1, 1, 0, 0, 0, 0, time.UTC)}, - {"cast(cast('00:00:45.123' as time(3)) as sql_variant)", - time.Date(1, 1, 1, 00, 00, 45, 123000000, time.UTC)}, - {"cast(cast('2010-11-15T11:56:45.123' as datetime2(3)) as sql_variant)", - time.Date(2010, 11, 15, 11, 56, 45, 123000000, time.UTC)}, - //{"cast(cast('2010-11-15T11:56:45.123+10:00' as datetimeoffset(3)) as sql_variant)", - // time.Date(2010, 11, 15, 11, 56, 45, 123000000, time.FixedZone("", 10*60*60)) }, - } - for _, test := range values { - stmt, err := conn.Prepare("select " + test.sql) - if err != nil { - t.Error("Prepare failed:", test.sql, err.Error()) - return - } - defer stmt.Close() - - row := stmt.QueryRow() - var retval interface{} - err = row.Scan(&retval) - if err != nil { - t.Error("Scan failed:", test.sql, err.Error()) - continue - } - if retval != test.val { - t.Errorf("Values don't match '%s' '%s' for test: %s", retval, test.val, test.sql) - continue - } - } -} - -func TestTrans(t *testing.T) { - conn := open(t) - defer conn.Close() - - var tx *sql.Tx - var err error - if tx, err = conn.Begin(); err != nil { - t.Fatal("Begin failed", err.Error()) - } - if err = tx.Commit(); err != nil { - t.Fatal("Commit failed", err.Error()) - } - - if tx, err = conn.Begin(); err != nil { - t.Fatal("Begin failed", err.Error()) - } - if _, err = tx.Exec("create table #abc (fld int)"); err != nil { - t.Fatal("Create table failed", err.Error()) - } - if err = tx.Rollback(); err != nil { - t.Fatal("Rollback failed", err.Error()) - } -} - -func TestParams(t *testing.T) { - longstr := strings.Repeat("x", 10000) - longbytes := make([]byte, 10000) - values := []interface{}{ - int64(5), - "hello", - "", - []byte{1, 2, 3}, - []byte{}, - float64(1.12313554), - true, - false, - nil, - longstr, - longbytes, - } - - conn := open(t) - defer conn.Close() - - for _, val := range values { - row := conn.QueryRow("select ?", val) - var retval interface{} - err := row.Scan(&retval) - if err != nil { - t.Error("Scan failed", err.Error()) - return - } - var same bool - switch decodedval := retval.(type) { - case []byte: - switch decodedvaltest := val.(type) { - case []byte: - same = bytes.Equal(decodedval, decodedvaltest) - default: - same = false - } - default: - same = retval == val - } - if !same { - t.Error("Value don't match", retval, val) - return - } - } -} - -func TestExec(t *testing.T) { - conn := open(t) - defer conn.Close() - - res, err := conn.Exec("create table #abc (fld int)") - if err != nil { - t.Fatal("Exec failed", err.Error()) - } - _ = res -} - -func TestDefaultTimeout(t *testing.T) { - if testing.Short() { - return - } - conn := open(t) - defer conn.Close() - - res, err := conn.Exec("waitfor delay '00:31'") - if err == nil { - t.Fatal("Exec should fail with timeout") - } - if neterr, ok := err.(net.Error); !ok || !neterr.Timeout() { - t.Fatal("Exec should fail with timeout, failed with", err) - } - _ = res -} - -func TestShortTimeout(t *testing.T) { - if testing.Short() { - return - } - dsn := makeConnStr() + ";Connection Timeout=2" - conn, err := sql.Open("mssql", dsn) - if err != nil { - t.Fatal("Open connection failed:", err.Error()) - } - defer conn.Close() - - res, err := conn.Exec("waitfor delay '00:03'") - if err == nil { - t.Fatal("Exec should fail with timeout") - } - if neterr, ok := err.(net.Error); !ok || !neterr.Timeout() { - t.Fatal("Exec should fail with timeout, failed with", err) - } - _ = res -} - -func TestTwoQueries(t *testing.T) { - conn := open(t) - defer conn.Close() - - rows, err := conn.Query("select 1") - if err != nil { - t.Fatal("First exec failed", err) - } - if !rows.Next() { - t.Fatal("First query didn't return row") - } - var i int - if err = rows.Scan(&i); err != nil { - t.Fatal("Scan failed", err) - } - if i != 1 { - t.Fatalf("Wrong value returned %d, should be 1", i) - } - - if rows, err = conn.Query("select 2"); err != nil { - t.Fatal("Second query failed", err) - } - if !rows.Next() { - t.Fatal("Second query didn't return row") - } - if err = rows.Scan(&i); err != nil { - t.Fatal("Scan failed", err) - } - if i != 2 { - t.Fatalf("Wrong value returned %d, should be 2", i) - } -} - -func TestError(t *testing.T) { - conn := open(t) - defer conn.Close() - - _, err := conn.Query("exec bad") - if err == nil { - t.Fatal("Query should fail") - } - - if sqlerr, ok := err.(Error); !ok { - t.Fatalf("Should be sql error, actually %T, %v", err, err) - } else { - if sqlerr.Number != 2812 { // Could not find stored procedure 'bad' - t.Fatalf("Should be specific error code 2812, actually %d %s", sqlerr.Number, sqlerr) - } - } -} - -func TestQueryNoRows(t *testing.T) { - conn := open(t) - defer conn.Close() - - var rows *sql.Rows - var err error - if rows, err = conn.Query("create table #abc (fld int)"); err != nil { - t.Fatal("Query failed", err) - } - if rows.Next() { - t.Fatal("Query shoulnd't return any rows") - } -} - -func TestQueryManyNullsRow(t *testing.T) { - conn := open(t) - defer conn.Close() - - var row *sql.Row - var err error - if row = conn.QueryRow("select null, null, null, null, null, null, null, null"); err != nil { - t.Fatal("Query failed", err) - } - var v [8]sql.NullInt64 - if err = row.Scan(&v[0], &v[1], &v[2], &v[3], &v[4], &v[5], &v[6], &v[7]); err != nil { - t.Fatal("Scan failed", err) - } -} - -func TestOrderBy(t *testing.T) { - conn := open(t) - defer conn.Close() - - tx, err := conn.Begin() - if err != nil { - t.Fatal("Begin tran failed", err) - } - defer tx.Rollback() - - _, err = tx.Exec("if (exists(select * from INFORMATION_SCHEMA.TABLES where TABLE_NAME='tbl')) drop table tbl") - if err != nil { - t.Fatal("Drop table failed", err) - } - - _, err = tx.Exec("create table tbl (fld1 int primary key, fld2 int)") - if err != nil { - t.Fatal("Create table failed", err) - } - _, err = tx.Exec("insert into tbl (fld1, fld2) values (1, 2)") - if err != nil { - t.Fatal("Insert failed", err) - } - _, err = tx.Exec("insert into tbl (fld1, fld2) values (2, 1)") - if err != nil { - t.Fatal("Insert failed", err) - } - - rows, err := tx.Query("select * from tbl order by fld1") - if err != nil { - t.Fatal("Query failed", err) - } - - for rows.Next() { - var fld1 int32 - var fld2 int32 - err = rows.Scan(&fld1, &fld2) - if err != nil { - t.Fatal("Scan failed", err) - } - } - - err = rows.Err() - if err != nil { - t.Fatal("Rows have errors", err) - } -} - -func TestScanDecimal(t *testing.T) { - conn := open(t) - defer conn.Close() - - var f float64 - err := conn.QueryRow("select cast(0.5 as numeric(25,1))").Scan(&f) - if err != nil { - t.Error("query row / scan failed:", err.Error()) - return - } - if math.Abs(f-0.5) > 0.000001 { - t.Error("Value is not 0.5:", f) - return - } - - var s string - err = conn.QueryRow("select cast(-0.05 as numeric(25,2))").Scan(&s) - if err != nil { - t.Error("query row / scan failed:", err.Error()) - return - } - if s != "-0.05" { - t.Error("Value is not -0.05:", s) - return - } -} - -func TestAffectedRows(t *testing.T) { - conn := open(t) - defer conn.Close() - - tx, err := conn.Begin() - if err != nil { - t.Fatal("Begin tran failed", err) - } - defer tx.Rollback() - - res, err := tx.Exec("create table #foo (bar int)") - if err != nil { - t.Fatal("create table failed") - } - n, err := res.RowsAffected() - if err != nil { - t.Fatal("rows affected failed") - } - if n != 0 { - t.Error("Expected 0 rows affected, got ", n) - } - - res, err = tx.Exec("insert into #foo (bar) values (1)") - if err != nil { - t.Fatal("insert failed") - } - n, err = res.RowsAffected() - if err != nil { - t.Fatal("rows affected failed") - } - if n != 1 { - t.Error("Expected 1 row affected, got ", n) - } - - res, err = tx.Exec("insert into #foo (bar) values (?)", 2) - if err != nil { - t.Fatal("insert failed") - } - n, err = res.RowsAffected() - if err != nil { - t.Fatal("rows affected failed") - } - if n != 1 { - t.Error("Expected 1 row affected, got ", n) - } -} - -func TestIdentity(t *testing.T) { - conn := open(t) - defer conn.Close() - - tx, err := conn.Begin() - if err != nil { - t.Fatal("Begin tran failed", err) - } - defer tx.Rollback() - - res, err := tx.Exec("create table #foo (bar int identity, baz int unique)") - if err != nil { - t.Fatal("create table failed") - } - - res, err = tx.Exec("insert into #foo (baz) values (1)") - if err != nil { - t.Fatal("insert failed") - } - n, err := res.LastInsertId() - if err != nil { - t.Fatal("last insert id failed") - } - if n != 1 { - t.Error("Expected 1 for identity, got ", n) - } - - res, err = tx.Exec("insert into #foo (baz) values (20)") - if err != nil { - t.Fatal("insert failed") - } - n, err = res.LastInsertId() - if err != nil { - t.Fatal("last insert id failed") - } - if n != 2 { - t.Error("Expected 2 for identity, got ", n) - } - - res, err = tx.Exec("insert into #foo (baz) values (1)") - if err == nil { - t.Fatal("insert should fail") - } - - res, err = tx.Exec("insert into #foo (baz) values (?)", 1) - if err == nil { - t.Fatal("insert should fail") - } -} - -func TestDateTimeParam(t *testing.T) { - conn := open(t) - defer conn.Close() - - t1, err := time.Parse("2006-01-02 15:04:05.99", "2004-06-03 12:13:14.15") - if err != nil { - t.Error("time parse failed", err.Error()) - return - } - var t2 time.Time - err = conn.QueryRow("select ?", t1).Scan(&t2) - if err != nil { - t.Error("select / scan failed", err.Error()) - return - } - if t1.Sub(t2) != 0 { - t.Errorf("datetime does not match: '%s' '%s' delta: %d", t1, t2, t1.Sub(t2)) - return - } -} - -func TestBigQuery(t *testing.T) { - conn := open(t) - defer conn.Close() - rows, err := conn.Query(`WITH n(n) AS - ( - SELECT 1 - UNION ALL - SELECT n+1 FROM n WHERE n < 10000 - ) - SELECT n, @@version FROM n ORDER BY n - OPTION (MAXRECURSION 10000);`) - if err != nil { - t.Fatal("cannot exec query", err) - } - rows.Next() - rows.Close() - var res int - err = conn.QueryRow("select 0").Scan(&res) - if err != nil { - t.Fatal("cannot scan value", err) - } - if res != 0 { - t.Fatal("expected 0, got ", res) - } -} - -func TestBug32(t *testing.T) { - conn := open(t) - defer conn.Close() - - tx, err := conn.Begin() - if err != nil { - t.Fatal("Begin tran failed", err) - } - defer tx.Rollback() - - _, err = tx.Exec("if (exists(select * from INFORMATION_SCHEMA.TABLES where TABLE_NAME='tbl')) drop table tbl") - if err != nil { - t.Fatal("Drop table failed", err) - } - - _, err = tx.Exec("create table tbl(a int primary key,fld bit null)") - if err != nil { - t.Fatal("Create table failed", err) - } - - _, err = tx.Exec("insert into tbl (a,fld) values (1,nullif(?, ''))", "") - if err != nil { - t.Fatal("Insert failed", err) - } -} - -func TestLogging(t *testing.T) { - flags := log.Flags() - defer func() { - log.SetFlags(flags) - log.SetOutput(os.Stderr) - }() - log.SetFlags(0) - var b bytes.Buffer - log.SetOutput(&b) - - dsn := makeConnStr() + ";Log=2" - conn, err := sql.Open("mssql", dsn) - if err != nil { - t.Fatal("Open connection failed:", err.Error()) - } - defer conn.Close() - _, err = conn.Exec("print 'test'") - if err != nil { - t.Fatal("Exec print failed", err.Error()) - } - if b.String() != "test\n" { - t.Fatal("logging test failed, got", b.String()) - } -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/rpc.go b/vendor/github.com/denisenkom/go-mssqldb/rpc.go deleted file mode 100644 index 00b9b1e21..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/rpc.go +++ /dev/null @@ -1,100 +0,0 @@ -package mssql - -import ( - "encoding/binary" -) - -type ProcId struct { - id uint16 - name string -} - -// parameter flags -const ( - fByRevValue = 1 - fDefaultValue = 2 -) - -type Param struct { - Name string - Flags uint8 - ti typeInfo - buffer []byte -} - -func MakeProcId(name string) (res ProcId) { - res.name = name - if len(name) == 0 { - panic("Proc name shouln't be empty") - } - if len(name) >= 0xffff { - panic("Invalid length of procedure name, should be less than 0xffff") - } - return res -} - -const ( - fWithRecomp = 1 - fNoMetaData = 2 - fReuseMetaData = 4 -) - -var ( - Sp_Cursor = ProcId{1, ""} - Sp_CursorOpen = ProcId{2, ""} - Sp_CursorPrepare = ProcId{3, ""} - Sp_CursorExecute = ProcId{4, ""} - Sp_CursorPrepExec = ProcId{5, ""} - Sp_CursorUnprepare = ProcId{6, ""} - Sp_CursorFetch = ProcId{7, ""} - Sp_CursorOption = ProcId{8, ""} - Sp_CursorClose = ProcId{9, ""} - Sp_ExecuteSql = ProcId{10, ""} - Sp_Prepare = ProcId{11, ""} - Sp_PrepExec = ProcId{13, ""} - Sp_PrepExecRpc = ProcId{14, ""} - Sp_Unprepare = ProcId{15, ""} -) - -// http://msdn.microsoft.com/en-us/library/dd357576.aspx -func sendRpc(buf *tdsBuffer, headers []headerStruct, proc ProcId, flags uint16, params []Param) (err error) { - buf.BeginPacket(packRPCRequest) - writeAllHeaders(buf, headers) - if len(proc.name) == 0 { - var idswitch uint16 = 0xffff - err = binary.Write(buf, binary.LittleEndian, &idswitch) - if err != nil { - return - } - err = binary.Write(buf, binary.LittleEndian, &proc.id) - if err != nil { - return - } - } else { - err = writeUsVarChar(buf, proc.name) - if err != nil { - return - } - } - err = binary.Write(buf, binary.LittleEndian, &flags) - if err != nil { - return - } - for _, param := range params { - if err = writeBVarChar(buf, param.Name); err != nil { - return - } - if err = binary.Write(buf, binary.LittleEndian, param.Flags); err != nil { - return - } - err = writeTypeInfo(buf, ¶m.ti) - if err != nil { - return - } - err = param.ti.Writer(buf, param.ti, param.buffer) - if err != nil { - return - } - } - return buf.FinishPacket() -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/sspi_windows.go b/vendor/github.com/denisenkom/go-mssqldb/sspi_windows.go deleted file mode 100644 index a6e95051c..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/sspi_windows.go +++ /dev/null @@ -1,266 +0,0 @@ -package mssql - -import ( - "fmt" - "strings" - "syscall" - "unsafe" -) - -var ( - secur32_dll = syscall.NewLazyDLL("secur32.dll") - initSecurityInterface = secur32_dll.NewProc("InitSecurityInterfaceW") - sec_fn *SecurityFunctionTable -) - -func init() { - ptr, _, _ := initSecurityInterface.Call() - sec_fn = (*SecurityFunctionTable)(unsafe.Pointer(ptr)) -} - -const ( - SEC_E_OK = 0 - SECPKG_CRED_OUTBOUND = 2 - SEC_WINNT_AUTH_IDENTITY_UNICODE = 2 - ISC_REQ_DELEGATE = 0x00000001 - ISC_REQ_REPLAY_DETECT = 0x00000004 - ISC_REQ_SEQUENCE_DETECT = 0x00000008 - ISC_REQ_CONFIDENTIALITY = 0x00000010 - ISC_REQ_CONNECTION = 0x00000800 - SECURITY_NETWORK_DREP = 0 - SEC_I_CONTINUE_NEEDED = 0x00090312 - SEC_I_COMPLETE_NEEDED = 0x00090313 - SEC_I_COMPLETE_AND_CONTINUE = 0x00090314 - SECBUFFER_VERSION = 0 - SECBUFFER_TOKEN = 2 - NTLMBUF_LEN = 12000 -) - -const ISC_REQ = ISC_REQ_CONFIDENTIALITY | - ISC_REQ_REPLAY_DETECT | - ISC_REQ_SEQUENCE_DETECT | - ISC_REQ_CONNECTION | - ISC_REQ_DELEGATE - -type SecurityFunctionTable struct { - dwVersion uint32 - EnumerateSecurityPackages uintptr - QueryCredentialsAttributes uintptr - AcquireCredentialsHandle uintptr - FreeCredentialsHandle uintptr - Reserved2 uintptr - InitializeSecurityContext uintptr - AcceptSecurityContext uintptr - CompleteAuthToken uintptr - DeleteSecurityContext uintptr - ApplyControlToken uintptr - QueryContextAttributes uintptr - ImpersonateSecurityContext uintptr - RevertSecurityContext uintptr - MakeSignature uintptr - VerifySignature uintptr - FreeContextBuffer uintptr - QuerySecurityPackageInfo uintptr - Reserved3 uintptr - Reserved4 uintptr - Reserved5 uintptr - Reserved6 uintptr - Reserved7 uintptr - Reserved8 uintptr - QuerySecurityContextToken uintptr - EncryptMessage uintptr - DecryptMessage uintptr -} - -type SEC_WINNT_AUTH_IDENTITY struct { - User *uint16 - UserLength uint32 - Domain *uint16 - DomainLength uint32 - Password *uint16 - PasswordLength uint32 - Flags uint32 -} - -type TimeStamp struct { - LowPart uint32 - HighPart int32 -} - -type SecHandle struct { - dwLower uintptr - dwUpper uintptr -} - -type SecBuffer struct { - cbBuffer uint32 - BufferType uint32 - pvBuffer *byte -} - -type SecBufferDesc struct { - ulVersion uint32 - cBuffers uint32 - pBuffers *SecBuffer -} - -type SSPIAuth struct { - Domain string - UserName string - Password string - Service string - cred SecHandle - ctxt SecHandle -} - -func getAuth(user, password, service, workstation string) (Auth, bool) { - if user == "" { - return &SSPIAuth{Service: service}, true - } - if !strings.ContainsRune(user, '\\') { - return nil, false - } - domain_user := strings.SplitN(user, "\\", 2) - return &SSPIAuth{ - Domain: domain_user[0], - UserName: domain_user[1], - Password: password, - Service: service, - }, true -} - -func (auth *SSPIAuth) InitialBytes() ([]byte, error) { - var identity *SEC_WINNT_AUTH_IDENTITY - if auth.UserName != "" { - identity = &SEC_WINNT_AUTH_IDENTITY{ - Flags: SEC_WINNT_AUTH_IDENTITY_UNICODE, - Password: syscall.StringToUTF16Ptr(auth.Password), - PasswordLength: uint32(len(auth.Password)), - Domain: syscall.StringToUTF16Ptr(auth.Domain), - DomainLength: uint32(len(auth.Domain)), - User: syscall.StringToUTF16Ptr(auth.UserName), - UserLength: uint32(len(auth.UserName)), - } - } - var ts TimeStamp - sec_ok, _, _ := syscall.Syscall9(sec_fn.AcquireCredentialsHandle, - 9, - 0, - uintptr(unsafe.Pointer(syscall.StringToUTF16Ptr("Negotiate"))), - SECPKG_CRED_OUTBOUND, - 0, - uintptr(unsafe.Pointer(identity)), - 0, - 0, - uintptr(unsafe.Pointer(&auth.cred)), - uintptr(unsafe.Pointer(&ts))) - if sec_ok != SEC_E_OK { - return nil, fmt.Errorf("AcquireCredentialsHandle failed %x", sec_ok) - } - - var buf SecBuffer - var desc SecBufferDesc - desc.ulVersion = SECBUFFER_VERSION - desc.cBuffers = 1 - desc.pBuffers = &buf - - outbuf := make([]byte, NTLMBUF_LEN) - buf.cbBuffer = NTLMBUF_LEN - buf.BufferType = SECBUFFER_TOKEN - buf.pvBuffer = &outbuf[0] - - var attrs uint32 - sec_ok, _, _ = syscall.Syscall12(sec_fn.InitializeSecurityContext, - 12, - uintptr(unsafe.Pointer(&auth.cred)), - 0, - uintptr(unsafe.Pointer(syscall.StringToUTF16Ptr(auth.Service))), - ISC_REQ, - 0, - SECURITY_NETWORK_DREP, - 0, - 0, - uintptr(unsafe.Pointer(&auth.ctxt)), - uintptr(unsafe.Pointer(&desc)), - uintptr(unsafe.Pointer(&attrs)), - uintptr(unsafe.Pointer(&ts))) - if sec_ok == SEC_I_COMPLETE_AND_CONTINUE || - sec_ok == SEC_I_COMPLETE_NEEDED { - syscall.Syscall6(sec_fn.CompleteAuthToken, - 2, - uintptr(unsafe.Pointer(&auth.ctxt)), - uintptr(unsafe.Pointer(&desc)), - 0, 0, 0, 0) - } else if sec_ok != SEC_E_OK && - sec_ok != SEC_I_CONTINUE_NEEDED { - syscall.Syscall6(sec_fn.FreeCredentialsHandle, - 1, - uintptr(unsafe.Pointer(&auth.cred)), - 0, 0, 0, 0, 0) - return nil, fmt.Errorf("InitialBytes InitializeSecurityContext failed %x", sec_ok) - } - return outbuf[:buf.cbBuffer], nil -} - -func (auth *SSPIAuth) NextBytes(bytes []byte) ([]byte, error) { - var in_buf, out_buf SecBuffer - var in_desc, out_desc SecBufferDesc - - in_desc.ulVersion = SECBUFFER_VERSION - in_desc.cBuffers = 1 - in_desc.pBuffers = &in_buf - - out_desc.ulVersion = SECBUFFER_VERSION - out_desc.cBuffers = 1 - out_desc.pBuffers = &out_buf - - in_buf.BufferType = SECBUFFER_TOKEN - in_buf.pvBuffer = &bytes[0] - in_buf.cbBuffer = uint32(len(bytes)) - - outbuf := make([]byte, NTLMBUF_LEN) - out_buf.BufferType = SECBUFFER_TOKEN - out_buf.pvBuffer = &outbuf[0] - out_buf.cbBuffer = NTLMBUF_LEN - - var attrs uint32 - var ts TimeStamp - sec_ok, _, _ := syscall.Syscall12(sec_fn.InitializeSecurityContext, - 12, - uintptr(unsafe.Pointer(&auth.cred)), - uintptr(unsafe.Pointer(&auth.ctxt)), - uintptr(unsafe.Pointer(syscall.StringToUTF16Ptr(auth.Service))), - ISC_REQ, - 0, - SECURITY_NETWORK_DREP, - uintptr(unsafe.Pointer(&in_desc)), - 0, - uintptr(unsafe.Pointer(&auth.ctxt)), - uintptr(unsafe.Pointer(&out_desc)), - uintptr(unsafe.Pointer(&attrs)), - uintptr(unsafe.Pointer(&ts))) - if sec_ok == SEC_I_COMPLETE_AND_CONTINUE || - sec_ok == SEC_I_COMPLETE_NEEDED { - syscall.Syscall6(sec_fn.CompleteAuthToken, - 2, - uintptr(unsafe.Pointer(&auth.ctxt)), - uintptr(unsafe.Pointer(&out_desc)), - 0, 0, 0, 0) - } else if sec_ok != SEC_E_OK && - sec_ok != SEC_I_CONTINUE_NEEDED { - return nil, fmt.Errorf("NextBytes InitializeSecurityContext failed %x", sec_ok) - } - - return outbuf[:out_buf.cbBuffer], nil -} - -func (auth *SSPIAuth) Free() { - syscall.Syscall6(sec_fn.DeleteSecurityContext, - 1, - uintptr(unsafe.Pointer(&auth.ctxt)), - 0, 0, 0, 0, 0) - syscall.Syscall6(sec_fn.FreeCredentialsHandle, - 1, - uintptr(unsafe.Pointer(&auth.cred)), - 0, 0, 0, 0, 0) -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/tds.go b/vendor/github.com/denisenkom/go-mssqldb/tds.go deleted file mode 100644 index 16718ee49..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/tds.go +++ /dev/null @@ -1,995 +0,0 @@ -package mssql - -import ( - "crypto/tls" - "crypto/x509" - "encoding/binary" - "errors" - "fmt" - "io" - "io/ioutil" - "net" - "os" - "sort" - "strconv" - "strings" - "time" - "unicode/utf16" - "unicode/utf8" -) - -func parseInstances(msg []byte) map[string]map[string]string { - results := map[string]map[string]string{} - if len(msg) > 3 && msg[0] == 5 { - out_s := string(msg[3:]) - tokens := strings.Split(out_s, ";") - instdict := map[string]string{} - got_name := false - var name string - for _, token := range tokens { - if got_name { - instdict[name] = token - got_name = false - } else { - name = token - if len(name) == 0 { - if len(instdict) == 0 { - break - } - results[strings.ToUpper(instdict["InstanceName"])] = instdict - instdict = map[string]string{} - continue - } - got_name = true - } - } - } - return results -} - -func getInstances(address string) (map[string]map[string]string, error) { - conn, err := net.DialTimeout("udp", address+":1434", 5*time.Second) - if err != nil { - return nil, err - } - defer conn.Close() - _, err = conn.Write([]byte{3}) - if err != nil { - return nil, err - } - var resp = make([]byte, 16*1024-1) - read, err := conn.Read(resp) - if err != nil { - return nil, err - } - return parseInstances(resp[:read]), nil -} - -// tds versions -const ( - verTDS70 = 0x70000000 - verTDS71 = 0x71000000 - verTDS71rev1 = 0x71000001 - verTDS72 = 0x72090002 - verTDS73A = 0x730A0003 - verTDS73 = verTDS73A - verTDS73B = 0x730B0003 - verTDS74 = 0x74000004 -) - -// packet types -const ( - packSQLBatch = 1 - packRPCRequest = 3 - packReply = 4 - packCancel = 6 - packBulkLoadBCP = 7 - packTransMgrReq = 14 - packNormal = 15 - packLogin7 = 16 - packSSPIMessage = 17 - packPrelogin = 18 -) - -// prelogin fields -// http://msdn.microsoft.com/en-us/library/dd357559.aspx -const ( - preloginVERSION = 0 - preloginENCRYPTION = 1 - preloginINSTOPT = 2 - preloginTHREADID = 3 - preloginMARS = 4 - preloginTRACEID = 5 - preloginTERMINATOR = 0xff -) - -const ( - encryptOff = 0 // Encryption is available but off. - encryptOn = 1 // Encryption is available and on. - encryptNotSup = 2 // Encryption is not available. - encryptReq = 3 // Encryption is required. -) - -type tdsSession struct { - buf *tdsBuffer - loginAck loginAckStruct - database string - partner string - columns []columnStruct - tranid uint64 - logFlags uint64 - log *Logger - routedServer string - routedPort uint16 -} - -const ( - logErrors = 1 - logMessages = 2 - logRows = 4 - logSQL = 8 - logParams = 16 - logTransaction = 32 -) - -type columnStruct struct { - UserType uint32 - Flags uint16 - ColName string - ti typeInfo -} - -type KeySlice []uint8 - -func (p KeySlice) Len() int { return len(p) } -func (p KeySlice) Less(i, j int) bool { return p[i] < p[j] } -func (p KeySlice) Swap(i, j int) { p[i], p[j] = p[j], p[i] } - -// http://msdn.microsoft.com/en-us/library/dd357559.aspx -func writePrelogin(w *tdsBuffer, fields map[uint8][]byte) error { - var err error - - w.BeginPacket(packPrelogin) - offset := uint16(5*len(fields) + 1) - keys := make(KeySlice, 0, len(fields)) - for k, _ := range fields { - keys = append(keys, k) - } - sort.Sort(keys) - // writing header - for _, k := range keys { - err = w.WriteByte(k) - if err != nil { - return err - } - err = binary.Write(w, binary.BigEndian, offset) - if err != nil { - return err - } - v := fields[k] - size := uint16(len(v)) - err = binary.Write(w, binary.BigEndian, size) - if err != nil { - return err - } - offset += size - } - err = w.WriteByte(preloginTERMINATOR) - if err != nil { - return err - } - // writing values - for _, k := range keys { - v := fields[k] - written, err := w.Write(v) - if err != nil { - return err - } - if written != len(v) { - return errors.New("Write method didn't write the whole value") - } - } - return w.FinishPacket() -} - -func readPrelogin(r *tdsBuffer) (map[uint8][]byte, error) { - packet_type, err := r.BeginRead() - if err != nil { - return nil, err - } - struct_buf, err := ioutil.ReadAll(r) - if err != nil { - return nil, err - } - if packet_type != 4 { - return nil, errors.New("Invalid respones, expected packet type 4, PRELOGIN RESPONSE") - } - offset := 0 - results := map[uint8][]byte{} - for true { - rec_type := struct_buf[offset] - if rec_type == preloginTERMINATOR { - break - } - - rec_offset := binary.BigEndian.Uint16(struct_buf[offset+1:]) - rec_len := binary.BigEndian.Uint16(struct_buf[offset+3:]) - value := struct_buf[rec_offset : rec_offset+rec_len] - results[rec_type] = value - offset += 5 - } - return results, nil -} - -// OptionFlags2 -// http://msdn.microsoft.com/en-us/library/dd304019.aspx -const ( - fLanguageFatal = 1 - fODBC = 2 - fTransBoundary = 4 - fCacheConnect = 8 - fIntSecurity = 0x80 -) - -// TypeFlags -const ( - // 4 bits for fSQLType - // 1 bit for fOLEDB - fReadOnlyIntent = 32 -) - -type login struct { - TDSVersion uint32 - PacketSize uint32 - ClientProgVer uint32 - ClientPID uint32 - ConnectionID uint32 - OptionFlags1 uint8 - OptionFlags2 uint8 - TypeFlags uint8 - OptionFlags3 uint8 - ClientTimeZone int32 - ClientLCID uint32 - HostName string - UserName string - Password string - AppName string - ServerName string - CtlIntName string - Language string - Database string - ClientID [6]byte - SSPI []byte - AtchDBFile string - ChangePassword string -} - -type loginHeader struct { - Length uint32 - TDSVersion uint32 - PacketSize uint32 - ClientProgVer uint32 - ClientPID uint32 - ConnectionID uint32 - OptionFlags1 uint8 - OptionFlags2 uint8 - TypeFlags uint8 - OptionFlags3 uint8 - ClientTimeZone int32 - ClientLCID uint32 - HostNameOffset uint16 - HostNameLength uint16 - UserNameOffset uint16 - UserNameLength uint16 - PasswordOffset uint16 - PasswordLength uint16 - AppNameOffset uint16 - AppNameLength uint16 - ServerNameOffset uint16 - ServerNameLength uint16 - ExtensionOffset uint16 - ExtensionLenght uint16 - CtlIntNameOffset uint16 - CtlIntNameLength uint16 - LanguageOffset uint16 - LanguageLength uint16 - DatabaseOffset uint16 - DatabaseLength uint16 - ClientID [6]byte - SSPIOffset uint16 - SSPILength uint16 - AtchDBFileOffset uint16 - AtchDBFileLength uint16 - ChangePasswordOffset uint16 - ChangePasswordLength uint16 - SSPILongLength uint32 -} - -// convert Go string to UTF-16 encoded []byte (littleEndian) -// done manually rather than using bytes and binary packages -// for performance reasons -func str2ucs2(s string) []byte { - res := utf16.Encode([]rune(s)) - ucs2 := make([]byte, 2*len(res)) - for i := 0; i < len(res); i++ { - ucs2[2*i] = byte(res[i]) - ucs2[2*i+1] = byte(res[i] >> 8) - } - return ucs2 -} - -func ucs22str(s []byte) (string, error) { - if len(s)%2 != 0 { - return "", fmt.Errorf("Illegal UCS2 string length: %d", len(s)) - } - buf := make([]uint16, len(s)/2) - for i := 0; i < len(s); i += 2 { - buf[i/2] = binary.LittleEndian.Uint16(s[i:]) - } - return string(utf16.Decode(buf)), nil -} - -func manglePassword(password string) []byte { - var ucs2password []byte = str2ucs2(password) - for i, ch := range ucs2password { - ucs2password[i] = ((ch<<4)&0xff | (ch >> 4)) ^ 0xA5 - } - return ucs2password -} - -// http://msdn.microsoft.com/en-us/library/dd304019.aspx -func sendLogin(w *tdsBuffer, login login) error { - w.BeginPacket(packLogin7) - hostname := str2ucs2(login.HostName) - username := str2ucs2(login.UserName) - password := manglePassword(login.Password) - appname := str2ucs2(login.AppName) - servername := str2ucs2(login.ServerName) - ctlintname := str2ucs2(login.CtlIntName) - language := str2ucs2(login.Language) - database := str2ucs2(login.Database) - atchdbfile := str2ucs2(login.AtchDBFile) - changepassword := str2ucs2(login.ChangePassword) - hdr := loginHeader{ - TDSVersion: login.TDSVersion, - PacketSize: login.PacketSize, - ClientProgVer: login.ClientProgVer, - ClientPID: login.ClientPID, - ConnectionID: login.ConnectionID, - OptionFlags1: login.OptionFlags1, - OptionFlags2: login.OptionFlags2, - TypeFlags: login.TypeFlags, - OptionFlags3: login.OptionFlags3, - ClientTimeZone: login.ClientTimeZone, - ClientLCID: login.ClientLCID, - HostNameLength: uint16(utf8.RuneCountInString(login.HostName)), - UserNameLength: uint16(utf8.RuneCountInString(login.UserName)), - PasswordLength: uint16(utf8.RuneCountInString(login.Password)), - AppNameLength: uint16(utf8.RuneCountInString(login.AppName)), - ServerNameLength: uint16(utf8.RuneCountInString(login.ServerName)), - CtlIntNameLength: uint16(utf8.RuneCountInString(login.CtlIntName)), - LanguageLength: uint16(utf8.RuneCountInString(login.Language)), - DatabaseLength: uint16(utf8.RuneCountInString(login.Database)), - ClientID: login.ClientID, - SSPILength: uint16(len(login.SSPI)), - AtchDBFileLength: uint16(utf8.RuneCountInString(login.AtchDBFile)), - ChangePasswordLength: uint16(utf8.RuneCountInString(login.ChangePassword)), - } - offset := uint16(binary.Size(hdr)) - hdr.HostNameOffset = offset - offset += uint16(len(hostname)) - hdr.UserNameOffset = offset - offset += uint16(len(username)) - hdr.PasswordOffset = offset - offset += uint16(len(password)) - hdr.AppNameOffset = offset - offset += uint16(len(appname)) - hdr.ServerNameOffset = offset - offset += uint16(len(servername)) - hdr.CtlIntNameOffset = offset - offset += uint16(len(ctlintname)) - hdr.LanguageOffset = offset - offset += uint16(len(language)) - hdr.DatabaseOffset = offset - offset += uint16(len(database)) - hdr.SSPIOffset = offset - offset += uint16(len(login.SSPI)) - hdr.AtchDBFileOffset = offset - offset += uint16(len(atchdbfile)) - hdr.ChangePasswordOffset = offset - offset += uint16(len(changepassword)) - hdr.Length = uint32(offset) - var err error - err = binary.Write(w, binary.LittleEndian, &hdr) - if err != nil { - return err - } - _, err = w.Write(hostname) - if err != nil { - return err - } - _, err = w.Write(username) - if err != nil { - return err - } - _, err = w.Write(password) - if err != nil { - return err - } - _, err = w.Write(appname) - if err != nil { - return err - } - _, err = w.Write(servername) - if err != nil { - return err - } - _, err = w.Write(ctlintname) - if err != nil { - return err - } - _, err = w.Write(language) - if err != nil { - return err - } - _, err = w.Write(database) - if err != nil { - return err - } - _, err = w.Write(login.SSPI) - if err != nil { - return err - } - _, err = w.Write(atchdbfile) - if err != nil { - return err - } - _, err = w.Write(changepassword) - if err != nil { - return err - } - return w.FinishPacket() -} - -func readUcs2(r io.Reader, numchars int) (res string, err error) { - buf := make([]byte, numchars*2) - _, err = io.ReadFull(r, buf) - if err != nil { - return "", err - } - return ucs22str(buf) -} - -func readUsVarChar(r io.Reader) (res string, err error) { - var numchars uint16 - err = binary.Read(r, binary.LittleEndian, &numchars) - if err != nil { - return "", err - } - return readUcs2(r, int(numchars)) -} - -func writeUsVarChar(w io.Writer, s string) (err error) { - buf := str2ucs2(s) - var numchars int = len(buf) / 2 - if numchars > 0xffff { - panic("invalid size for US_VARCHAR") - } - err = binary.Write(w, binary.LittleEndian, uint16(numchars)) - if err != nil { - return - } - _, err = w.Write(buf) - return -} - -func readBVarChar(r io.Reader) (res string, err error) { - var numchars uint8 - err = binary.Read(r, binary.LittleEndian, &numchars) - if err != nil { - return "", err - } - return readUcs2(r, int(numchars)) -} - -func writeBVarChar(w io.Writer, s string) (err error) { - buf := str2ucs2(s) - var numchars int = len(buf) / 2 - if numchars > 0xff { - panic("invalid size for B_VARCHAR") - } - err = binary.Write(w, binary.LittleEndian, uint8(numchars)) - if err != nil { - return - } - _, err = w.Write(buf) - return -} - -func readBVarByte(r io.Reader) (res []byte, err error) { - var length uint8 - err = binary.Read(r, binary.LittleEndian, &length) - if err != nil { - return - } - res = make([]byte, length) - _, err = io.ReadFull(r, res) - return -} - -func readUshort(r io.Reader) (res uint16, err error) { - err = binary.Read(r, binary.LittleEndian, &res) - return -} - -func readByte(r io.Reader) (res byte, err error) { - var b [1]byte - _, err = r.Read(b[:]) - res = b[0] - return -} - -// Packet Data Stream Headers -// http://msdn.microsoft.com/en-us/library/dd304953.aspx -type headerStruct struct { - hdrtype uint16 - data []byte -} - -const ( - dataStmHdrQueryNotif = 1 // query notifications - dataStmHdrTransDescr = 2 // MARS transaction descriptor (required) - dataStmHdrTraceActivity = 3 -) - -// MARS Transaction Descriptor Header -// http://msdn.microsoft.com/en-us/library/dd340515.aspx -type transDescrHdr struct { - transDescr uint64 // transaction descriptor returned from ENVCHANGE - outstandingReqCnt uint32 // outstanding request count -} - -func (hdr transDescrHdr) pack() (res []byte) { - res = make([]byte, 8+4) - binary.LittleEndian.PutUint64(res, hdr.transDescr) - binary.LittleEndian.PutUint32(res[8:], hdr.outstandingReqCnt) - return res -} - -func writeAllHeaders(w io.Writer, headers []headerStruct) (err error) { - // calculatint total length - var totallen uint32 = 4 - for _, hdr := range headers { - totallen += 4 + 2 + uint32(len(hdr.data)) - } - // writing - err = binary.Write(w, binary.LittleEndian, totallen) - if err != nil { - return err - } - for _, hdr := range headers { - var headerlen uint32 = 4 + 2 + uint32(len(hdr.data)) - err = binary.Write(w, binary.LittleEndian, headerlen) - if err != nil { - return err - } - err = binary.Write(w, binary.LittleEndian, hdr.hdrtype) - if err != nil { - return err - } - _, err = w.Write(hdr.data) - if err != nil { - return err - } - } - return nil -} - -func sendSqlBatch72(buf *tdsBuffer, - sqltext string, - headers []headerStruct) (err error) { - buf.BeginPacket(packSQLBatch) - - writeAllHeaders(buf, headers) - - _, err = buf.Write(str2ucs2(sqltext)) - if err != nil { - return err - } - return buf.FinishPacket() -} - -type connectParams struct { - logFlags uint64 - port uint64 - host string - instance string - database string - user string - password string - dial_timeout time.Duration - conn_timeout time.Duration - keepAlive time.Duration - encrypt bool - disableEncryption bool - trustServerCertificate bool - certificate string - hostInCertificate string - serverSPN string - workstation string - appname string - typeFlags uint8 -} - -func parseConnectParams(params map[string]string) (*connectParams, error) { - var p connectParams - strlog, ok := params["log"] - if ok { - var err error - p.logFlags, err = strconv.ParseUint(strlog, 10, 0) - if err != nil { - return nil, fmt.Errorf("Invalid log parameter '%s': %s", strlog, err.Error()) - } - } - server := params["server"] - parts := strings.SplitN(server, "\\", 2) - p.host = parts[0] - if p.host == "." || strings.ToUpper(p.host) == "(LOCAL)" || p.host == "" { - p.host = "localhost" - } - if len(parts) > 1 { - p.instance = parts[1] - } - p.database = params["database"] - p.user = params["user id"] - p.password = params["password"] - p.port = 1433 - if p.instance != "" { - p.instance = strings.ToUpper(p.instance) - instances, err := getInstances(p.host) - if err != nil { - f := "Unable to get instances from Sql Server Browser on host %v: %v" - return nil, fmt.Errorf(f, p.host, err.Error()) - } - strport, ok := instances[p.instance]["tcp"] - if !ok { - f := "No instance matching '%v' returned from host '%v'" - return nil, fmt.Errorf(f, p.instance, p.host) - } - p.port, err = strconv.ParseUint(strport, 0, 16) - if err != nil { - f := "Invalid tcp port returned from Sql Server Browser '%v': %v" - return nil, fmt.Errorf(f, strport, err.Error()) - } - } else { - strport, ok := params["port"] - if ok { - var err error - p.port, err = strconv.ParseUint(strport, 0, 16) - if err != nil { - f := "Invalid tcp port '%v': %v" - return nil, fmt.Errorf(f, strport, err.Error()) - } - } - } - p.dial_timeout = 5 * time.Second - p.conn_timeout = 30 * time.Second - strconntimeout, ok := params["connection timeout"] - if ok { - timeout, err := strconv.ParseUint(strconntimeout, 0, 16) - if err != nil { - f := "Invalid connection timeout '%v': %v" - return nil, fmt.Errorf(f, strconntimeout, err.Error()) - } - p.conn_timeout = time.Duration(timeout) * time.Second - } - strdialtimeout, ok := params["dial timeout"] - if ok { - timeout, err := strconv.ParseUint(strdialtimeout, 0, 16) - if err != nil { - f := "Invalid dial timeout '%v': %v" - return nil, fmt.Errorf(f, strdialtimeout, err.Error()) - } - p.dial_timeout = time.Duration(timeout) * time.Second - } - keepAlive, ok := params["keepalive"] - if ok { - timeout, err := strconv.ParseUint(keepAlive, 0, 16) - if err != nil { - f := "Invalid keepAlive value '%s': %s" - return nil, fmt.Errorf(f, keepAlive, err.Error()) - } - p.keepAlive = time.Duration(timeout) * time.Second - } - encrypt, ok := params["encrypt"] - if ok { - if strings.ToUpper(encrypt) == "DISABLE" { - p.disableEncryption = true - } else { - var err error - p.encrypt, err = strconv.ParseBool(encrypt) - if err != nil { - f := "Invalid encrypt '%s': %s" - return nil, fmt.Errorf(f, encrypt, err.Error()) - } - } - } else { - p.trustServerCertificate = true - } - trust, ok := params["trustservercertificate"] - if ok { - var err error - p.trustServerCertificate, err = strconv.ParseBool(trust) - if err != nil { - f := "Invalid trust server certificate '%s': %s" - return nil, fmt.Errorf(f, trust, err.Error()) - } - } - p.certificate = params["certificate"] - p.hostInCertificate, ok = params["hostnameincertificate"] - if !ok { - p.hostInCertificate = p.host - } - - serverSPN, ok := params["ServerSPN"] - if ok { - p.serverSPN = serverSPN - } else { - p.serverSPN = fmt.Sprintf("MSSQLSvc/%s:%d", p.host, p.port) - } - - workstation, ok := params["Workstation ID"] - if ok { - p.workstation = workstation - } else { - workstation, err := os.Hostname() - if err == nil { - p.workstation = workstation - } - } - - appname, ok := params["app name"] - if !ok { - appname = "go-mssqldb" - } - p.appname = appname - - appintent, ok := params["applicationintent"] - if ok { - if appintent == "ReadOnly" { - p.typeFlags |= fReadOnlyIntent - } - } - - return &p, nil -} - -type Auth interface { - InitialBytes() ([]byte, error) - NextBytes([]byte) ([]byte, error) - Free() -} - -// SQL Server AlwaysOn Availability Group Listeners are bound by DNS to a -// list of IP addresses. So if there is more than one, try them all and -// use the first one that allows a connection. -func dialConnection(p *connectParams) (conn net.Conn, err error) { - var ips []net.IP - ips, err = net.LookupIP(p.host) - if err != nil { - ip := net.ParseIP(p.host) - if ip == nil { - return nil, err - } - ips = []net.IP{ip} - } - if len(ips) == 1 { - d := createDialer(p) - addr := net.JoinHostPort(ips[0].String(), strconv.Itoa(int(p.port))) - conn, err = d.Dial("tcp", addr) - - } else { - //Try Dials in parallel to avoid waiting for timeouts. - connChan := make(chan net.Conn, len(ips)) - errChan := make(chan error, len(ips)) - for _, ip := range ips { - go func(ip net.IP) { - d := createDialer(p) - addr := net.JoinHostPort(ip.String(), strconv.Itoa(int(p.port))) - conn, err := d.Dial("tcp", addr) - if err == nil { - connChan <- conn - } else { - errChan <- err - } - }(ip) - } - // Wait for either the *first* successful connection, or all the errors - wait_loop: - for i, _ := range ips { - select { - case conn = <-connChan: - // Got a connection to use, close any others - go func(n int) { - for i := 0; i < n; i++ { - select { - case conn := <-connChan: - conn.Close() - case <-errChan: - } - } - }(len(ips) - i - 1) - break wait_loop - case err = <-errChan: - } - } - } - if err != nil { - f := "Unable to open tcp connection with host '%v:%v': %v" - return nil, fmt.Errorf(f, p.host, p.port, err.Error()) - } - - return conn, err -} - -func connect(params map[string]string) (res *tdsSession, err error) { - p, err := parseConnectParams(params) - if err != nil { - return nil, err - } - -initiate_connection: - conn, err := dialConnection(p) - if err != nil { - return nil, err - } - - toconn := NewTimeoutConn(conn, p.conn_timeout) - - outbuf := newTdsBuffer(4096, toconn) - sess := tdsSession{ - buf: outbuf, - logFlags: p.logFlags, - } - - instance_buf := []byte(p.instance) - instance_buf = append(instance_buf, 0) // zero terminate instance name - var encrypt byte - if p.disableEncryption { - encrypt = encryptNotSup - } else if p.encrypt { - encrypt = encryptOn - } else { - encrypt = encryptOff - } - fields := map[uint8][]byte{ - preloginVERSION: {0, 0, 0, 0, 0, 0}, - preloginENCRYPTION: {encrypt}, - preloginINSTOPT: instance_buf, - preloginTHREADID: {0, 0, 0, 0}, - preloginMARS: {0}, // MARS disabled - } - - err = writePrelogin(outbuf, fields) - if err != nil { - return nil, err - } - - fields, err = readPrelogin(outbuf) - if err != nil { - return nil, err - } - - encryptBytes, ok := fields[preloginENCRYPTION] - if !ok { - return nil, fmt.Errorf("Encrypt negotiation failed") - } - encrypt = encryptBytes[0] - if p.encrypt && (encrypt == encryptNotSup || encrypt == encryptOff) { - return nil, fmt.Errorf("Server does not support encryption") - } - - if encrypt != encryptNotSup { - var config tls.Config - if p.certificate != "" { - pem, err := ioutil.ReadFile(p.certificate) - if err != nil { - f := "Cannot read certificate '%s': %s" - return nil, fmt.Errorf(f, p.certificate, err.Error()) - } - certs := x509.NewCertPool() - certs.AppendCertsFromPEM(pem) - config.RootCAs = certs - } - if p.trustServerCertificate { - config.InsecureSkipVerify = true - } - config.ServerName = p.hostInCertificate - outbuf.transport = conn - toconn.buf = outbuf - tlsConn := tls.Client(toconn, &config) - err = tlsConn.Handshake() - toconn.buf = nil - outbuf.transport = tlsConn - if err != nil { - f := "TLS Handshake failed: %s" - return nil, fmt.Errorf(f, err.Error()) - } - if encrypt == encryptOff { - outbuf.afterFirst = func() { - outbuf.transport = toconn - } - } - } - - login := login{ - TDSVersion: verTDS74, - PacketSize: uint32(len(outbuf.buf)), - Database: p.database, - OptionFlags2: fODBC, // to get unlimited TEXTSIZE - HostName: p.workstation, - ServerName: p.host, - AppName: p.appname, - TypeFlags: p.typeFlags, - } - auth, auth_ok := getAuth(p.user, p.password, p.serverSPN, p.workstation) - if auth_ok { - login.SSPI, err = auth.InitialBytes() - if err != nil { - return nil, err - } - login.OptionFlags2 |= fIntSecurity - defer auth.Free() - } else { - login.UserName = p.user - login.Password = p.password - } - err = sendLogin(outbuf, login) - if err != nil { - return nil, err - } - - // processing login response - var sspi_msg []byte -continue_login: - tokchan := make(chan tokenStruct, 5) - go processResponse(&sess, tokchan) - success := false - for tok := range tokchan { - switch token := tok.(type) { - case sspiMsg: - sspi_msg, err = auth.NextBytes(token) - if err != nil { - return nil, err - } - case loginAckStruct: - success = true - sess.loginAck = token - case error: - return nil, fmt.Errorf("Login error: %s", token.Error()) - } - } - if sspi_msg != nil { - outbuf.BeginPacket(packSSPIMessage) - _, err = outbuf.Write(sspi_msg) - if err != nil { - return nil, err - } - err = outbuf.FinishPacket() - if err != nil { - return nil, err - } - sspi_msg = nil - goto continue_login - } - if !success { - return nil, fmt.Errorf("Login failed") - } - if sess.routedServer != "" { - toconn.Close() - p.host = sess.routedServer - p.port = uint64(sess.routedPort) - goto initiate_connection - } - return &sess, nil -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/tds_test.go b/vendor/github.com/denisenkom/go-mssqldb/tds_test.go deleted file mode 100644 index 7d4ddda25..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/tds_test.go +++ /dev/null @@ -1,336 +0,0 @@ -package mssql - -import ( - "bytes" - "database/sql" - "encoding/hex" - "fmt" - "os" - "testing" - "time" -) - -type MockTransport struct { - bytes.Buffer -} - -func (t *MockTransport) Close() error { - return nil -} - -func TestSendLogin(t *testing.T) { - buf := newTdsBuffer(1024, new(MockTransport)) - login := login{ - TDSVersion: verTDS73, - PacketSize: 0x1000, - ClientProgVer: 0x01060100, - ClientPID: 100, - ClientTimeZone: -4 * 60, - ClientID: [6]byte{0x12, 0x34, 0x56, 0x78, 0x90, 0xab}, - OptionFlags1: 0xe0, - OptionFlags3: 8, - HostName: "subdev1", - UserName: "test", - Password: "testpwd", - AppName: "appname", - ServerName: "servername", - CtlIntName: "library", - Language: "en", - Database: "database", - ClientLCID: 0x204, - AtchDBFile: "filepath", - } - err := sendLogin(buf, login) - if err != nil { - t.Error("sendLogin should succeed") - } - ref := []byte{ - 16, 1, 0, 222, 0, 0, 1, 0, 198 + 16, 0, 0, 0, 3, 0, 10, 115, 0, 16, 0, 0, 0, 1, - 6, 1, 100, 0, 0, 0, 0, 0, 0, 0, 224, 0, 0, 8, 16, 255, 255, 255, 4, 2, 0, - 0, 94, 0, 7, 0, 108, 0, 4, 0, 116, 0, 7, 0, 130, 0, 7, 0, 144, 0, 10, 0, 0, - 0, 0, 0, 164, 0, 7, 0, 178, 0, 2, 0, 182, 0, 8, 0, 18, 52, 86, 120, 144, 171, - 198, 0, 0, 0, 198, 0, 8, 0, 214, 0, 0, 0, 0, 0, 0, 0, 115, 0, 117, 0, 98, - 0, 100, 0, 101, 0, 118, 0, 49, 0, 116, 0, 101, 0, 115, 0, 116, 0, 226, 165, - 243, 165, 146, 165, 226, 165, 162, 165, 210, 165, 227, 165, 97, 0, 112, - 0, 112, 0, 110, 0, 97, 0, 109, 0, 101, 0, 115, 0, 101, 0, 114, 0, 118, 0, - 101, 0, 114, 0, 110, 0, 97, 0, 109, 0, 101, 0, 108, 0, 105, 0, 98, 0, 114, - 0, 97, 0, 114, 0, 121, 0, 101, 0, 110, 0, 100, 0, 97, 0, 116, 0, 97, 0, 98, - 0, 97, 0, 115, 0, 101, 0, 102, 0, 105, 0, 108, 0, 101, 0, 112, 0, 97, 0, - 116, 0, 104, 0} - out := buf.buf[:buf.pos] - if !bytes.Equal(ref, out) { - t.Error("input output don't match") - fmt.Print(hex.Dump(ref)) - fmt.Print(hex.Dump(out)) - } -} - -func TestSendSqlBatch(t *testing.T) { - addr := os.Getenv("HOST") - instance := os.Getenv("INSTANCE") - - conn, err := connect(map[string]string{ - "server": fmt.Sprintf("%s\\%s", addr, instance), - "user id": os.Getenv("SQLUSER"), - "password": os.Getenv("SQLPASSWORD"), - "database": os.Getenv("DATABASE"), - }) - if err != nil { - t.Error("Open connection failed:", err.Error()) - return - } - defer conn.buf.transport.Close() - - headers := []headerStruct{ - {hdrtype: dataStmHdrTransDescr, - data: transDescrHdr{0, 1}.pack()}, - } - err = sendSqlBatch72(conn.buf, "select 1", headers) - if err != nil { - t.Error("Sending sql batch failed", err.Error()) - return - } - - ch := make(chan tokenStruct, 5) - go processResponse(conn, ch) - - var lastRow []interface{} -loop: - for tok := range ch { - switch token := tok.(type) { - case doneStruct: - break loop - case []columnStruct: - conn.columns = token - case []interface{}: - lastRow = token - default: - fmt.Println("unknown token", tok) - } - } - - switch value := lastRow[0].(type) { - case int32: - if value != 1 { - t.Error("Invalid value returned, should be 1", value) - return - } - } -} - -func makeConnStr() string { - addr := os.Getenv("HOST") - instance := os.Getenv("INSTANCE") - user := os.Getenv("SQLUSER") - password := os.Getenv("SQLPASSWORD") - database := os.Getenv("DATABASE") - return fmt.Sprintf( - "Server=%s\\%s;User Id=%s;Password=%s;Database=%s;log=63", - addr, instance, user, password, database) -} - -func open(t *testing.T) *sql.DB { - conn, err := sql.Open("mssql", makeConnStr()) - if err != nil { - t.Error("Open connection failed:", err.Error()) - return nil - } - return conn -} - -func TestConnect(t *testing.T) { - conn, err := sql.Open("mssql", makeConnStr()) - if err != nil { - t.Error("Open connection failed:", err.Error()) - return - } - defer conn.Close() -} - -func TestBadConnect(t *testing.T) { - badDsns := []string{ - //"Server=badhost", - fmt.Sprintf("Server=%s\\%s;User ID=baduser;Password=badpwd", - os.Getenv("HOST"), os.Getenv("INSTANCE")), - } - for _, badDsn := range badDsns { - conn, err := sql.Open("mssql", badDsn) - if err != nil { - t.Error("Open connection failed:", err.Error()) - } - defer conn.Close() - err = conn.Ping() - if err == nil { - t.Error("Ping should fail for connection: ", badDsn) - } - } -} - -func simpleQuery(conn *sql.DB, t *testing.T) (stmt *sql.Stmt) { - stmt, err := conn.Prepare("select 1 as a") - if err != nil { - t.Error("Prepare failed:", err.Error()) - return nil - } - return stmt -} - -func checkSimpleQuery(rows *sql.Rows, t *testing.T) { - numrows := 0 - for rows.Next() { - var val int - err := rows.Scan(&val) - if err != nil { - t.Error("Scan failed:", err.Error()) - } - if val != 1 { - t.Error("query should return 1") - } - numrows++ - } - if numrows != 1 { - t.Error("query should return 1 row, returned", numrows) - } -} - -func TestQuery(t *testing.T) { - conn := open(t) - if conn == nil { - return - } - defer conn.Close() - - stmt := simpleQuery(conn, t) - if stmt == nil { - return - } - defer stmt.Close() - - rows, err := stmt.Query() - if err != nil { - t.Error("Query failed:", err.Error()) - } - defer rows.Close() - - columns, err := rows.Columns() - if err != nil { - t.Error("getting columns failed", err.Error()) - } - if len(columns) != 1 && columns[0] != "a" { - t.Error("returned incorrect columns (expected ['a']):", columns) - } - - checkSimpleQuery(rows, t) -} - -func TestMultipleQueriesSequentialy(t *testing.T) { - - conn := open(t) - defer conn.Close() - - stmt, err := conn.Prepare("select 1 as a") - if err != nil { - t.Error("Prepare failed:", err.Error()) - return - } - defer stmt.Close() - - rows, err := stmt.Query() - if err != nil { - t.Error("Query failed:", err.Error()) - return - } - defer rows.Close() - checkSimpleQuery(rows, t) - - rows, err = stmt.Query() - if err != nil { - t.Error("Query failed:", err.Error()) - return - } - defer rows.Close() - checkSimpleQuery(rows, t) -} - -func TestMultipleQueryClose(t *testing.T) { - conn := open(t) - defer conn.Close() - - stmt, err := conn.Prepare("select 1 as a") - if err != nil { - t.Error("Prepare failed:", err.Error()) - return - } - defer stmt.Close() - - rows, err := stmt.Query() - if err != nil { - t.Error("Query failed:", err.Error()) - return - } - rows.Close() - - rows, err = stmt.Query() - if err != nil { - t.Error("Query failed:", err.Error()) - return - } - defer rows.Close() - checkSimpleQuery(rows, t) -} - -func TestPing(t *testing.T) { - conn := open(t) - defer conn.Close() - conn.Ping() -} - -func TestSecureWithInvalidHostName(t *testing.T) { - dsn := makeConnStr() + ";Encrypt=true;TrustServerCertificate=false;hostNameInCertificate=foo.bar" - conn, err := sql.Open("mssql", dsn) - if err != nil { - t.Fatal("Open connection failed:", err.Error()) - } - defer conn.Close() - err = conn.Ping() - if err == nil { - t.Fatal("Connected to fake foo.bar server") - } -} - -func TestSecureConnection(t *testing.T) { - dsn := makeConnStr() + ";Encrypt=true;TrustServerCertificate=true" - conn, err := sql.Open("mssql", dsn) - if err != nil { - t.Fatal("Open connection failed:", err.Error()) - } - defer conn.Close() - var msg string - err = conn.QueryRow("select 'secret'").Scan(&msg) - if err != nil { - t.Fatal("cannot scan value", err) - } - if msg != "secret" { - t.Fatal("expected secret, got: ", msg) - } - var secure bool - err = conn.QueryRow("select encrypt_option from sys.dm_exec_connections where session_id=@@SPID").Scan(&secure) - if err != nil { - t.Fatal("cannot scan value", err) - } - if !secure { - t.Fatal("connection is not encrypted") - } -} - -func TestParseConnectParamsKeepAlive(t *testing.T) { - params := parseConnectionString("keepAlive=60") - parsedParams, err := parseConnectParams(params) - if err != nil { - t.Fatal("cannot parse params: ", err) - } - - if parsedParams.keepAlive != time.Duration(60)*time.Second { - t.Fail() - } -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/token.go b/vendor/github.com/denisenkom/go-mssqldb/token.go deleted file mode 100644 index 3292bf74b..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/token.go +++ /dev/null @@ -1,432 +0,0 @@ -package mssql - -import ( - "encoding/binary" - "io" - "strconv" - "strings" -) - -// token ids -const ( - tokenReturnStatus = 121 // 0x79 - tokenColMetadata = 129 // 0x81 - tokenOrder = 169 // 0xA9 - tokenError = 170 // 0xAA - tokenInfo = 171 // 0xAB - tokenLoginAck = 173 // 0xad - tokenRow = 209 // 0xd1 - tokenNbcRow = 210 // 0xd2 - tokenEnvChange = 227 // 0xE3 - tokenSSPI = 237 // 0xED - tokenDone = 253 // 0xFD - tokenDoneProc = 254 - tokenDoneInProc = 255 -) - -// done flags -const ( - doneFinal = 0 - doneMore = 1 - doneError = 2 - doneInxact = 4 - doneCount = 0x10 - doneAttn = 0x20 - doneSrvError = 0x100 -) - -// ENVCHANGE types -// http://msdn.microsoft.com/en-us/library/dd303449.aspx -const ( - envTypDatabase = 1 - envTypLanguage = 2 - envTypCharset = 3 - envTypPacketSize = 4 - envTypBeginTran = 8 - envTypCommitTran = 9 - envTypRollbackTran = 10 - envDatabaseMirrorPartner = 13 - envRouting = 20 -) - -// interface for all tokens -type tokenStruct interface{} - -type orderStruct struct { - ColIds []uint16 -} - -type doneStruct struct { - Status uint16 - CurCmd uint16 - RowCount uint64 -} - -type doneInProcStruct doneStruct - -var doneFlags2str = map[uint16]string{ - doneFinal: "final", - doneMore: "more", - doneError: "error", - doneInxact: "inxact", - doneCount: "count", - doneAttn: "attn", - doneSrvError: "srverror", -} - -func doneFlags2Str(flags uint16) string { - strs := make([]string, 0, len(doneFlags2str)) - for flag, tag := range doneFlags2str { - if flags&flag != 0 { - strs = append(strs, tag) - } - } - return strings.Join(strs, "|") -} - -// ENVCHANGE stream -// http://msdn.microsoft.com/en-us/library/dd303449.aspx -func processEnvChg(sess *tdsSession) { - size := sess.buf.uint16() - r := &io.LimitedReader{R: sess.buf, N: int64(size)} - for { - var err error - var envtype uint8 - err = binary.Read(r, binary.LittleEndian, &envtype) - if err == io.EOF { - return - } - if err != nil { - badStreamPanic(err) - } - switch envtype { - case envTypDatabase: - sess.database, err = readBVarChar(r) - if err != nil { - badStreamPanic(err) - } - _, err = readBVarChar(r) - if err != nil { - badStreamPanic(err) - } - case envTypPacketSize: - packetsize, err := readBVarChar(r) - if err != nil { - badStreamPanic(err) - } - _, err = readBVarChar(r) - if err != nil { - badStreamPanic(err) - } - packetsizei, err := strconv.Atoi(packetsize) - if err != nil { - badStreamPanicf("Invalid Packet size value returned from server (%s): %s", packetsize, err.Error()) - } - if len(sess.buf.buf) != packetsizei { - newbuf := make([]byte, packetsizei) - copy(newbuf, sess.buf.buf) - sess.buf.buf = newbuf - } - case envTypBeginTran: - tranid, err := readBVarByte(r) - if len(tranid) != 8 { - badStreamPanicf("invalid size of transaction identifier: %d", len(tranid)) - } - sess.tranid = binary.LittleEndian.Uint64(tranid) - if err != nil { - badStreamPanic(err) - } - if sess.logFlags&logTransaction != 0 { - sess.log.Printf("BEGIN TRANSACTION %x\n", sess.tranid) - } - _, err = readBVarByte(r) - if err != nil { - badStreamPanic(err) - } - case envTypCommitTran, envTypRollbackTran: - _, err = readBVarByte(r) - if err != nil { - badStreamPanic(err) - } - _, err = readBVarByte(r) - if err != nil { - badStreamPanic(err) - } - if sess.logFlags&logTransaction != 0 { - if envtype == envTypCommitTran { - sess.log.Printf("COMMIT TRANSACTION %x\n", sess.tranid) - } else { - sess.log.Printf("ROLLBACK TRANSACTION %x\n", sess.tranid) - } - } - sess.tranid = 0 - case envDatabaseMirrorPartner: - sess.partner, err = readBVarChar(r) - if err != nil { - badStreamPanic(err) - } - _, err = readBVarChar(r) - if err != nil { - badStreamPanic(err) - } - case envRouting: - // RoutingData message is: - // ValueLength USHORT - // Protocol (TCP = 0) BYTE - // ProtocolProperty (new port) USHORT - // AlternateServer US_VARCHAR - _, err := readUshort(r) - if err != nil { - badStreamPanic(err) - } - protocol, err := readByte(r) - if err != nil || protocol != 0 { - badStreamPanic(err) - } - newPort, err := readUshort(r) - if err != nil { - badStreamPanic(err) - } - newServer, err := readUsVarChar(r) - if err != nil { - badStreamPanic(err) - } - // consume the OLDVALUE = %x00 %x00 - _, err = readUshort(r) - if err != nil { - badStreamPanic(err) - } - sess.routedServer = newServer - sess.routedPort = newPort - default: - // ignore unknown env change types - _, err = readBVarByte(r) - if err != nil { - badStreamPanic(err) - } - _, err = readBVarByte(r) - if err != nil { - badStreamPanic(err) - } - } - - } -} - -type returnStatus int32 - -// http://msdn.microsoft.com/en-us/library/dd358180.aspx -func parseReturnStatus(r *tdsBuffer) returnStatus { - return returnStatus(r.int32()) -} - -func parseOrder(r *tdsBuffer) (res orderStruct) { - len := int(r.uint16()) - res.ColIds = make([]uint16, len/2) - for i := 0; i < len/2; i++ { - res.ColIds[i] = r.uint16() - } - return res -} - -func parseDone(r *tdsBuffer) (res doneStruct) { - res.Status = r.uint16() - res.CurCmd = r.uint16() - res.RowCount = r.uint64() - return res -} - -func parseDoneInProc(r *tdsBuffer) (res doneInProcStruct) { - res.Status = r.uint16() - res.CurCmd = r.uint16() - res.RowCount = r.uint64() - return res -} - -type sspiMsg []byte - -func parseSSPIMsg(r *tdsBuffer) sspiMsg { - size := r.uint16() - buf := make([]byte, size) - r.ReadFull(buf) - return sspiMsg(buf) -} - -type loginAckStruct struct { - Interface uint8 - TDSVersion uint32 - ProgName string - ProgVer uint32 -} - -func parseLoginAck(r *tdsBuffer) loginAckStruct { - size := r.uint16() - buf := make([]byte, size) - r.ReadFull(buf) - var res loginAckStruct - res.Interface = buf[0] - res.TDSVersion = binary.BigEndian.Uint32(buf[1:]) - prognamelen := buf[1+4] - var err error - if res.ProgName, err = ucs22str(buf[1+4+1 : 1+4+1+prognamelen*2]); err != nil { - badStreamPanic(err) - } - res.ProgVer = binary.BigEndian.Uint32(buf[size-4:]) - return res -} - -// http://msdn.microsoft.com/en-us/library/dd357363.aspx -func parseColMetadata72(r *tdsBuffer) (columns []columnStruct) { - count := r.uint16() - if count == 0xffff { - // no metadata is sent - return nil - } - columns = make([]columnStruct, count) - for i := range columns { - column := &columns[i] - column.UserType = r.uint32() - column.Flags = r.uint16() - - // parsing TYPE_INFO structure - column.ti = readTypeInfo(r) - column.ColName = r.BVarChar() - } - return columns -} - -// http://msdn.microsoft.com/en-us/library/dd357254.aspx -func parseRow(r *tdsBuffer, columns []columnStruct, row []interface{}) { - for i, column := range columns { - row[i] = column.ti.Reader(&column.ti, r) - } -} - -// http://msdn.microsoft.com/en-us/library/dd304783.aspx -func parseNbcRow(r *tdsBuffer, columns []columnStruct, row []interface{}) { - bitlen := (len(columns) + 7) / 8 - pres := make([]byte, bitlen) - r.ReadFull(pres) - for i, col := range columns { - if pres[i/8]&(1<<(uint(i)%8)) != 0 { - row[i] = nil - continue - } - row[i] = col.ti.Reader(&col.ti, r) - } -} - -// http://msdn.microsoft.com/en-us/library/dd304156.aspx -func parseError72(r *tdsBuffer) (res Error) { - length := r.uint16() - _ = length // ignore length - res.Number = r.int32() - res.State = r.byte() - res.Class = r.byte() - res.Message = r.UsVarChar() - res.ServerName = r.BVarChar() - res.ProcName = r.BVarChar() - res.LineNo = r.int32() - return -} - -// http://msdn.microsoft.com/en-us/library/dd304156.aspx -func parseInfo(r *tdsBuffer) (res Error) { - length := r.uint16() - _ = length // ignore length - res.Number = r.int32() - res.State = r.byte() - res.Class = r.byte() - res.Message = r.UsVarChar() - res.ServerName = r.BVarChar() - res.ProcName = r.BVarChar() - res.LineNo = r.int32() - return -} - -func processResponse(sess *tdsSession, ch chan tokenStruct) { - defer func() { - if err := recover(); err != nil { - ch <- err - } - close(ch) - }() - packet_type, err := sess.buf.BeginRead() - if err != nil { - ch <- err - return - } - if packet_type != packReply { - badStreamPanicf("invalid response packet type, expected REPLY, actual: %d", packet_type) - } - var columns []columnStruct - var lastError Error - var failed bool - for { - token := sess.buf.byte() - switch token { - case tokenSSPI: - ch <- parseSSPIMsg(sess.buf) - return - case tokenReturnStatus: - returnStatus := parseReturnStatus(sess.buf) - ch <- returnStatus - case tokenLoginAck: - loginAck := parseLoginAck(sess.buf) - ch <- loginAck - case tokenOrder: - order := parseOrder(sess.buf) - ch <- order - case tokenDoneInProc: - done := parseDoneInProc(sess.buf) - if sess.logFlags&logRows != 0 && done.Status&doneCount != 0 { - sess.log.Printf("(%d row(s) affected)\n", done.RowCount) - } - ch <- done - case tokenDone, tokenDoneProc: - done := parseDone(sess.buf) - if sess.logFlags&logRows != 0 && done.Status&doneCount != 0 { - sess.log.Printf("(%d row(s) affected)\n", done.RowCount) - } - if done.Status&doneError != 0 || failed { - ch <- lastError - return - } - if done.Status&doneSrvError != 0 { - lastError.Message = "Server Error" - ch <- lastError - return - } - ch <- done - if done.Status&doneMore == 0 { - return - } - case tokenColMetadata: - columns = parseColMetadata72(sess.buf) - ch <- columns - case tokenRow: - row := make([]interface{}, len(columns)) - parseRow(sess.buf, columns, row) - ch <- row - case tokenNbcRow: - row := make([]interface{}, len(columns)) - parseNbcRow(sess.buf, columns, row) - ch <- row - case tokenEnvChange: - processEnvChg(sess) - case tokenError: - lastError = parseError72(sess.buf) - failed = true - if sess.logFlags&logErrors != 0 { - sess.log.Println(lastError.Message) - } - case tokenInfo: - info := parseInfo(sess.buf) - if sess.logFlags&logMessages != 0 { - sess.log.Println(info.Message) - } - default: - badStreamPanicf("Unknown token type: %d", token) - } - } -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/tran.go b/vendor/github.com/denisenkom/go-mssqldb/tran.go deleted file mode 100644 index ae3810766..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/tran.go +++ /dev/null @@ -1,99 +0,0 @@ -// Transaction Manager requests -// http://msdn.microsoft.com/en-us/library/dd339887.aspx -package mssql - -import ( - "encoding/binary" -) - -const ( - tmGetDtcAddr = 0 - tmPropagateXact = 1 - tmBeginXact = 5 - tmPromoteXact = 6 - tmCommitXact = 7 - tmRollbackXact = 8 - tmSaveXact = 9 -) - -func sendBeginXact(buf *tdsBuffer, headers []headerStruct, isolation uint8, - name string) (err error) { - buf.BeginPacket(packTransMgrReq) - writeAllHeaders(buf, headers) - var rqtype uint16 = tmBeginXact - err = binary.Write(buf, binary.LittleEndian, &rqtype) - if err != nil { - return - } - err = binary.Write(buf, binary.LittleEndian, &isolation) - if err != nil { - return - } - err = writeBVarChar(buf, name) - if err != nil { - return - } - return buf.FinishPacket() -} - -const ( - fBeginXact = 1 -) - -func sendCommitXact(buf *tdsBuffer, headers []headerStruct, name string, flags uint8, isolation uint8, newname string) error { - buf.BeginPacket(packTransMgrReq) - writeAllHeaders(buf, headers) - var rqtype uint16 = tmCommitXact - err := binary.Write(buf, binary.LittleEndian, &rqtype) - if err != nil { - return err - } - err = writeBVarChar(buf, name) - if err != nil { - return err - } - err = binary.Write(buf, binary.LittleEndian, &flags) - if err != nil { - return err - } - if flags&fBeginXact != 0 { - err = binary.Write(buf, binary.LittleEndian, &isolation) - if err != nil { - return err - } - err = writeBVarChar(buf, name) - if err != nil { - return err - } - } - return buf.FinishPacket() -} - -func sendRollbackXact(buf *tdsBuffer, headers []headerStruct, name string, flags uint8, isolation uint8, newname string) error { - buf.BeginPacket(packTransMgrReq) - writeAllHeaders(buf, headers) - var rqtype uint16 = tmRollbackXact - err := binary.Write(buf, binary.LittleEndian, &rqtype) - if err != nil { - return err - } - err = writeBVarChar(buf, name) - if err != nil { - return err - } - err = binary.Write(buf, binary.LittleEndian, &flags) - if err != nil { - return err - } - if flags&fBeginXact != 0 { - err = binary.Write(buf, binary.LittleEndian, &isolation) - if err != nil { - return err - } - err = writeBVarChar(buf, name) - if err != nil { - return err - } - } - return buf.FinishPacket() -} diff --git a/vendor/github.com/denisenkom/go-mssqldb/types.go b/vendor/github.com/denisenkom/go-mssqldb/types.go deleted file mode 100644 index c06d6c7aa..000000000 --- a/vendor/github.com/denisenkom/go-mssqldb/types.go +++ /dev/null @@ -1,847 +0,0 @@ -package mssql - -import ( - "bytes" - "encoding/binary" - "fmt" - "io" - "math" - "strconv" - "time" -) - -// fixed-length data types -// http://msdn.microsoft.com/en-us/library/dd341171.aspx -const ( - typeNull = 0x1f - typeInt1 = 0x30 - typeBit = 0x32 - typeInt2 = 0x34 - typeInt4 = 0x38 - typeDateTim4 = 0x3a - typeFlt4 = 0x3b - typeMoney = 0x3c - typeDateTime = 0x3d - typeFlt8 = 0x3e - typeMoney4 = 0x7a - typeInt8 = 0x7f -) - -// variable-length data types -// http://msdn.microsoft.com/en-us/library/dd358341.aspx -const ( - // byte len types - typeGuid = 0x24 - typeIntN = 0x26 - typeDecimal = 0x37 // legacy - typeNumeric = 0x3f // legacy - typeBitN = 0x68 - typeDecimalN = 0x6a - typeNumericN = 0x6c - typeFltN = 0x6d - typeMoneyN = 0x6e - typeDateTimeN = 0x6f - typeDateN = 0x28 - typeTimeN = 0x29 - typeDateTime2N = 0x2a - typeDateTimeOffsetN = 0x2b - typeChar = 0x2f // legacy - typeVarChar = 0x27 // legacy - typeBinary = 0x2d // legacy - typeVarBinary = 0x25 // legacy - - // short length types - typeBigVarBin = 0xa5 - typeBigVarChar = 0xa7 - typeBigBinary = 0xad - typeBigChar = 0xaf - typeNVarChar = 0xe7 - typeNChar = 0xef - typeXml = 0xf1 - typeUdt = 0xf0 - - // long length types - typeText = 0x23 - typeImage = 0x22 - typeNText = 0x63 - typeVariant = 0x62 -) - -// TYPE_INFO rule -// http://msdn.microsoft.com/en-us/library/dd358284.aspx -type typeInfo struct { - TypeId uint8 - Size int - Scale uint8 - Prec uint8 - Buffer []byte - Collation collation - Reader func(ti *typeInfo, r *tdsBuffer) (res interface{}) - Writer func(w io.Writer, ti typeInfo, buf []byte) (err error) -} - -func readTypeInfo(r *tdsBuffer) (res typeInfo) { - res.TypeId = r.byte() - switch res.TypeId { - case typeNull, typeInt1, typeBit, typeInt2, typeInt4, typeDateTim4, - typeFlt4, typeMoney, typeDateTime, typeFlt8, typeMoney4, typeInt8: - // those are fixed length types - switch res.TypeId { - case typeNull: - res.Size = 0 - case typeInt1, typeBit: - res.Size = 1 - case typeInt2: - res.Size = 2 - case typeInt4, typeDateTim4, typeFlt4, typeMoney4: - res.Size = 4 - case typeMoney, typeDateTime, typeFlt8, typeInt8: - res.Size = 8 - } - res.Reader = readFixedType - res.Buffer = make([]byte, res.Size) - default: // all others are VARLENTYPE - readVarLen(&res, r) - } - return -} - -func writeTypeInfo(w io.Writer, ti *typeInfo) (err error) { - err = binary.Write(w, binary.LittleEndian, ti.TypeId) - if err != nil { - return - } - switch ti.TypeId { - case typeNull, typeInt1, typeBit, typeInt2, typeInt4, typeDateTim4, - typeFlt4, typeMoney, typeDateTime, typeFlt8, typeMoney4, typeInt8: - // those are fixed length types - default: // all others are VARLENTYPE - err = writeVarLen(w, ti) - if err != nil { - return - } - } - return -} - -func writeVarLen(w io.Writer, ti *typeInfo) (err error) { - switch ti.TypeId { - case typeDateN: - - case typeTimeN, typeDateTime2N, typeDateTimeOffsetN: - if err = binary.Write(w, binary.LittleEndian, ti.Scale); err != nil { - return - } - ti.Writer = writeByteLenType - case typeGuid, typeIntN, typeDecimal, typeNumeric, - typeBitN, typeDecimalN, typeNumericN, typeFltN, - typeMoneyN, typeDateTimeN, typeChar, - typeVarChar, typeBinary, typeVarBinary: - // byle len types - if ti.Size > 0xff { - panic("Invalid size for BYLELEN_TYPE") - } - if err = binary.Write(w, binary.LittleEndian, uint8(ti.Size)); err != nil { - return - } - switch ti.TypeId { - case typeDecimal, typeNumeric, typeDecimalN, typeNumericN: - err = binary.Write(w, binary.LittleEndian, ti.Prec) - if err != nil { - return - } - err = binary.Write(w, binary.LittleEndian, ti.Scale) - if err != nil { - return - } - } - ti.Writer = writeByteLenType - case typeBigVarBin, typeBigVarChar, typeBigBinary, typeBigChar, - typeNVarChar, typeNChar, typeXml, typeUdt: - // short len types - if ti.Size > 8000 || ti.Size == 0 { - if err = binary.Write(w, binary.LittleEndian, uint16(0xffff)); err != nil { - return - } - ti.Writer = writePLPType - } else { - if err = binary.Write(w, binary.LittleEndian, uint16(ti.Size)); err != nil { - return - } - ti.Writer = writeShortLenType - } - switch ti.TypeId { - case typeBigVarChar, typeBigChar, typeNVarChar, typeNChar: - if err = writeCollation(w, ti.Collation); err != nil { - return - } - case typeXml: - var schemapresent uint8 = 0 - if err = binary.Write(w, binary.LittleEndian, schemapresent); err != nil { - return - } - } - case typeText, typeImage, typeNText, typeVariant: - // LONGLEN_TYPE - panic("LONGLEN_TYPE not implemented") - default: - panic("Invalid type") - } - return -} - -// http://msdn.microsoft.com/en-us/library/ee780895.aspx -func decodeDateTim4(buf []byte) time.Time { - days := binary.LittleEndian.Uint16(buf) - mins := binary.LittleEndian.Uint16(buf[2:]) - return time.Date(1900, 1, 1+int(days), - 0, int(mins), 0, 0, time.UTC) -} - -func decodeDateTime(buf []byte) time.Time { - days := int32(binary.LittleEndian.Uint32(buf)) - tm := binary.LittleEndian.Uint32(buf[4:]) - ns := int(math.Trunc(float64(tm%300)/0.3+0.5)) * 1000000 - secs := int(tm / 300) - return time.Date(1900, 1, 1+int(days), - 0, 0, secs, ns, time.UTC) -} - -func readFixedType(ti *typeInfo, r *tdsBuffer) (res interface{}) { - r.ReadFull(ti.Buffer) - buf := ti.Buffer - switch ti.TypeId { - case typeNull: - return nil - case typeInt1: - return int64(buf[0]) - case typeBit: - return buf[0] != 0 - case typeInt2: - return int64(int16(binary.LittleEndian.Uint16(buf))) - case typeInt4: - return int64(int32(binary.LittleEndian.Uint32(buf))) - case typeDateTim4: - return decodeDateTim4(buf) - case typeFlt4: - return math.Float32frombits(binary.LittleEndian.Uint32(buf)) - case typeMoney4: - return decodeMoney4(buf) - case typeMoney: - return decodeMoney(buf) - case typeDateTime: - return decodeDateTime(buf) - case typeFlt8: - return math.Float64frombits(binary.LittleEndian.Uint64(buf)) - case typeInt8: - return int64(binary.LittleEndian.Uint64(buf)) - default: - badStreamPanicf("Invalid typeid") - } - panic("shoulnd't get here") -} - -func writeFixedType(w io.Writer, ti typeInfo, buf []byte) (err error) { - _, err = w.Write(buf) - return -} - -func readByteLenType(ti *typeInfo, r *tdsBuffer) (res interface{}) { - size := r.byte() - if size == 0 { - return nil - } - r.ReadFull(ti.Buffer[:size]) - buf := ti.Buffer[:size] - switch ti.TypeId { - case typeDateN: - if len(buf) != 3 { - badStreamPanicf("Invalid size for DATENTYPE") - } - return decodeDate(buf) - case typeTimeN: - return decodeTime(ti.Scale, buf) - case typeDateTime2N: - return decodeDateTime2(ti.Scale, buf) - case typeDateTimeOffsetN: - return decodeDateTimeOffset(ti.Scale, buf) - case typeGuid: - return decodeGuid(buf) - case typeIntN: - switch len(buf) { - case 1: - return int64(buf[0]) - case 2: - return int64(int16((binary.LittleEndian.Uint16(buf)))) - case 4: - return int64(int32(binary.LittleEndian.Uint32(buf))) - case 8: - return int64(binary.LittleEndian.Uint64(buf)) - default: - badStreamPanicf("Invalid size for INTNTYPE") - } - case typeDecimal, typeNumeric, typeDecimalN, typeNumericN: - return decodeDecimal(ti.Prec, ti.Scale, buf) - case typeBitN: - if len(buf) != 1 { - badStreamPanicf("Invalid size for BITNTYPE") - } - return buf[0] != 0 - case typeFltN: - switch len(buf) { - case 4: - return float64(math.Float32frombits(binary.LittleEndian.Uint32(buf))) - case 8: - return math.Float64frombits(binary.LittleEndian.Uint64(buf)) - default: - badStreamPanicf("Invalid size for FLTNTYPE") - } - case typeMoneyN: - switch len(buf) { - case 4: - return decodeMoney4(buf) - case 8: - return decodeMoney(buf) - default: - badStreamPanicf("Invalid size for MONEYNTYPE") - } - case typeDateTimeN: - switch len(buf) { - case 4: - return decodeDateTim4(buf) - case 8: - return decodeDateTime(buf) - default: - badStreamPanicf("Invalid size for DATETIMENTYPE") - } - case typeChar, typeVarChar: - return decodeChar(ti.Collation, buf) - case typeBinary, typeVarBinary: - // a copy, because the backing array for ti.Buffer is reused - // and can be overwritten by the next row while this row waits - // in a buffered chan - cpy := make([]byte, len(buf)) - copy(cpy, buf) - return cpy - default: - badStreamPanicf("Invalid typeid") - } - panic("shoulnd't get here") -} - -func writeByteLenType(w io.Writer, ti typeInfo, buf []byte) (err error) { - if ti.Size > 0xff { - panic("Invalid size for BYTELEN_TYPE") - } - err = binary.Write(w, binary.LittleEndian, uint8(ti.Size)) - if err != nil { - return - } - _, err = w.Write(buf) - return -} - -func readShortLenType(ti *typeInfo, r *tdsBuffer) (res interface{}) { - size := r.uint16() - if size == 0xffff { - return nil - } - r.ReadFull(ti.Buffer[:size]) - buf := ti.Buffer[:size] - switch ti.TypeId { - case typeBigVarChar, typeBigChar: - return decodeChar(ti.Collation, buf) - case typeBigVarBin, typeBigBinary: - // a copy, because the backing array for ti.Buffer is reused - // and can be overwritten by the next row while this row waits - // in a buffered chan - cpy := make([]byte, len(buf)) - copy(cpy, buf) - return cpy - case typeNVarChar, typeNChar: - return decodeNChar(buf) - case typeUdt: - return decodeUdt(*ti, buf) - default: - badStreamPanicf("Invalid typeid") - } - panic("shoulnd't get here") -} - -func writeShortLenType(w io.Writer, ti typeInfo, buf []byte) (err error) { - if buf == nil { - err = binary.Write(w, binary.LittleEndian, uint16(0xffff)) - return - } - if ti.Size > 0xfffe { - panic("Invalid size for USHORTLEN_TYPE") - } - err = binary.Write(w, binary.LittleEndian, uint16(ti.Size)) - if err != nil { - return - } - _, err = w.Write(buf) - return -} - -func readLongLenType(ti *typeInfo, r *tdsBuffer) (res interface{}) { - // information about this format can be found here: - // http://msdn.microsoft.com/en-us/library/dd304783.aspx - // and here: - // http://msdn.microsoft.com/en-us/library/dd357254.aspx - textptrsize := r.byte() - if textptrsize == 0 { - return nil - } - textptr := make([]byte, textptrsize) - r.ReadFull(textptr) - timestamp := r.uint64() - _ = timestamp // ignore timestamp - size := r.int32() - if size == -1 { - return nil - } - buf := make([]byte, size) - r.ReadFull(buf) - switch ti.TypeId { - case typeText: - return decodeChar(ti.Collation, buf) - case typeImage: - return buf - case typeNText: - return decodeNChar(buf) - default: - badStreamPanicf("Invalid typeid") - } - panic("shoulnd't get here") -} - -// reads variant value -// http://msdn.microsoft.com/en-us/library/dd303302.aspx -func readVariantType(ti *typeInfo, r *tdsBuffer) (res interface{}) { - size := r.int32() - if size == 0 { - return nil - } - vartype := r.byte() - propbytes := int32(r.byte()) - switch vartype { - case typeGuid: - buf := make([]byte, size-2-propbytes) - r.ReadFull(buf) - return buf - case typeBit: - return r.byte() != 0 - case typeInt1: - return int64(r.byte()) - case typeInt2: - return int64(int16(r.uint16())) - case typeInt4: - return int64(r.int32()) - case typeInt8: - return int64(r.uint64()) - case typeDateTime: - buf := make([]byte, size-2-propbytes) - r.ReadFull(buf) - return decodeDateTime(buf) - case typeDateTim4: - buf := make([]byte, size-2-propbytes) - r.ReadFull(buf) - return decodeDateTim4(buf) - case typeFlt4: - return float64(math.Float32frombits(r.uint32())) - case typeFlt8: - return math.Float64frombits(r.uint64()) - case typeMoney4: - buf := make([]byte, size-2-propbytes) - r.ReadFull(buf) - return decodeMoney4(buf) - case typeMoney: - buf := make([]byte, size-2-propbytes) - r.ReadFull(buf) - return decodeMoney(buf) - case typeDateN: - buf := make([]byte, size-2-propbytes) - r.ReadFull(buf) - return decodeDate(buf) - case typeTimeN: - scale := r.byte() - buf := make([]byte, size-2-propbytes) - r.ReadFull(buf) - return decodeTime(scale, buf) - case typeDateTime2N: - scale := r.byte() - buf := make([]byte, size-2-propbytes) - r.ReadFull(buf) - return decodeDateTime2(scale, buf) - case typeDateTimeOffsetN: - scale := r.byte() - buf := make([]byte, size-2-propbytes) - r.ReadFull(buf) - return decodeDateTimeOffset(scale, buf) - case typeBigVarBin, typeBigBinary: - r.uint16() // max length, ignoring - buf := make([]byte, size-2-propbytes) - r.ReadFull(buf) - return buf - case typeDecimalN, typeNumericN: - prec := r.byte() - scale := r.byte() - buf := make([]byte, size-2-propbytes) - r.ReadFull(buf) - return decodeDecimal(prec, scale, buf) - case typeBigVarChar, typeBigChar: - col := readCollation(r) - r.uint16() // max length, ignoring - buf := make([]byte, size-2-propbytes) - r.ReadFull(buf) - return decodeChar(col, buf) - case typeNVarChar, typeNChar: - _ = readCollation(r) - r.uint16() // max length, ignoring - buf := make([]byte, size-2-propbytes) - r.ReadFull(buf) - return decodeNChar(buf) - default: - badStreamPanicf("Invalid variant typeid") - } - panic("shoulnd't get here") -} - -// partially length prefixed stream -// http://msdn.microsoft.com/en-us/library/dd340469.aspx -func readPLPType(ti *typeInfo, r *tdsBuffer) (res interface{}) { - size := r.uint64() - var buf *bytes.Buffer - switch size { - case 0xffffffffffffffff: - // null - return nil - case 0xfffffffffffffffe: - // size unknown - buf = bytes.NewBuffer(make([]byte, 0, 1000)) - default: - buf = bytes.NewBuffer(make([]byte, 0, size)) - } - for true { - chunksize := r.uint32() - if chunksize == 0 { - break - } - if _, err := io.CopyN(buf, r, int64(chunksize)); err != nil { - badStreamPanicf("Reading PLP type failed: %s", err.Error()) - } - } - switch ti.TypeId { - case typeXml: - return decodeXml(*ti, buf.Bytes()) - case typeBigVarChar, typeBigChar, typeText: - return decodeChar(ti.Collation, buf.Bytes()) - case typeBigVarBin, typeBigBinary, typeImage: - return buf.Bytes() - case typeNVarChar, typeNChar, typeNText: - return decodeNChar(buf.Bytes()) - case typeUdt: - return decodeUdt(*ti, buf.Bytes()) - } - panic("shoulnd't get here") -} - -func writePLPType(w io.Writer, ti typeInfo, buf []byte) (err error) { - if err = binary.Write(w, binary.LittleEndian, uint64(len(buf))); err != nil { - return - } - for { - chunksize := uint32(len(buf)) - if err = binary.Write(w, binary.LittleEndian, chunksize); err != nil { - return - } - if chunksize == 0 { - return - } - if _, err = w.Write(buf[:chunksize]); err != nil { - return - } - buf = buf[chunksize:] - } -} - -func readVarLen(ti *typeInfo, r *tdsBuffer) { - switch ti.TypeId { - case typeDateN: - ti.Size = 3 - ti.Reader = readByteLenType - ti.Buffer = make([]byte, ti.Size) - case typeTimeN, typeDateTime2N, typeDateTimeOffsetN: - ti.Scale = r.byte() - switch ti.Scale { - case 0, 1, 2: - ti.Size = 3 - case 3, 4: - ti.Size = 4 - case 5, 6, 7: - ti.Size = 5 - default: - badStreamPanicf("Invalid scale for TIME/DATETIME2/DATETIMEOFFSET type") - } - switch ti.TypeId { - case typeDateTime2N: - ti.Size += 3 - case typeDateTimeOffsetN: - ti.Size += 5 - } - ti.Reader = readByteLenType - ti.Buffer = make([]byte, ti.Size) - case typeGuid, typeIntN, typeDecimal, typeNumeric, - typeBitN, typeDecimalN, typeNumericN, typeFltN, - typeMoneyN, typeDateTimeN, typeChar, - typeVarChar, typeBinary, typeVarBinary: - // byle len types - ti.Size = int(r.byte()) - ti.Buffer = make([]byte, ti.Size) - switch ti.TypeId { - case typeDecimal, typeNumeric, typeDecimalN, typeNumericN: - ti.Prec = r.byte() - ti.Scale = r.byte() - } - ti.Reader = readByteLenType - case typeXml: - schemapresent := r.byte() - if schemapresent != 0 { - // just ignore this for now - // dbname - r.BVarChar() - // owning schema - r.BVarChar() - // xml schema collection - r.UsVarChar() - } - ti.Reader = readPLPType - case typeBigVarBin, typeBigVarChar, typeBigBinary, typeBigChar, - typeNVarChar, typeNChar, typeUdt: - // short len types - ti.Size = int(r.uint16()) - switch ti.TypeId { - case typeBigVarChar, typeBigChar, typeNVarChar, typeNChar: - ti.Collation = readCollation(r) - } - if ti.Size == 0xffff { - ti.Reader = readPLPType - } else { - ti.Buffer = make([]byte, ti.Size) - ti.Reader = readShortLenType - } - case typeText, typeImage, typeNText, typeVariant: - // LONGLEN_TYPE - ti.Size = int(r.int32()) - switch ti.TypeId { - case typeText, typeNText: - ti.Collation = readCollation(r) - // ignore tablenames - numparts := int(r.byte()) - for i := 0; i < numparts; i++ { - r.UsVarChar() - } - ti.Reader = readLongLenType - case typeImage: - // ignore tablenames - numparts := int(r.byte()) - for i := 0; i < numparts; i++ { - r.UsVarChar() - } - ti.Reader = readLongLenType - case typeXml: - panic("XMLTYPE not implemented") - case typeVariant: - ti.Reader = readVariantType - } - default: - badStreamPanicf("Invalid type %d", ti.TypeId) - } - return -} - -func decodeMoney(buf []byte) []byte { - money := int64(uint64(buf[4]) | - uint64(buf[5])<<8 | - uint64(buf[6])<<16 | - uint64(buf[7])<<24 | - uint64(buf[0])<<32 | - uint64(buf[1])<<40 | - uint64(buf[2])<<48 | - uint64(buf[3])<<56) - return scaleBytes(strconv.FormatInt(money, 10), 4) -} - -func decodeMoney4(buf []byte) []byte { - money := int32(binary.LittleEndian.Uint32(buf[0:4])) - return scaleBytes(strconv.FormatInt(int64(money), 10), 4) -} - -func decodeGuid(buf []byte) []byte { - res := make([]byte, 16) - copy(res, buf) - return res -} - -func decodeDecimal(prec uint8, scale uint8, buf []byte) []byte { - var sign uint8 - sign = buf[0] - dec := Decimal{ - positive: sign != 0, - prec: prec, - scale: scale, - } - buf = buf[1:] - l := len(buf) / 4 - for i := 0; i < l; i++ { - dec.integer[i] = binary.LittleEndian.Uint32(buf[0:4]) - buf = buf[4:] - } - return dec.Bytes() -} - -// http://msdn.microsoft.com/en-us/library/ee780895.aspx -func decodeDateInt(buf []byte) (days int) { - return int(buf[0]) + int(buf[1])*256 + int(buf[2])*256*256 -} - -func decodeDate(buf []byte) time.Time { - return time.Date(1, 1, 1+decodeDateInt(buf), 0, 0, 0, 0, time.UTC) -} - -func decodeTimeInt(scale uint8, buf []byte) (sec int, ns int) { - var acc uint64 = 0 - for i := len(buf) - 1; i >= 0; i-- { - acc <<= 8 - acc |= uint64(buf[i]) - } - for i := 0; i < 7-int(scale); i++ { - acc *= 10 - } - nsbig := acc * 100 - sec = int(nsbig / 1000000000) - ns = int(nsbig % 1000000000) - return -} - -func decodeTime(scale uint8, buf []byte) time.Time { - sec, ns := decodeTimeInt(scale, buf) - return time.Date(1, 1, 1, 0, 0, sec, ns, time.UTC) -} - -func decodeDateTime2(scale uint8, buf []byte) time.Time { - timesize := len(buf) - 3 - sec, ns := decodeTimeInt(scale, buf[:timesize]) - days := decodeDateInt(buf[timesize:]) - return time.Date(1, 1, 1+days, 0, 0, sec, ns, time.UTC) -} - -func decodeDateTimeOffset(scale uint8, buf []byte) time.Time { - timesize := len(buf) - 3 - 2 - sec, ns := decodeTimeInt(scale, buf[:timesize]) - buf = buf[timesize:] - days := decodeDateInt(buf[:3]) - buf = buf[3:] - offset := int(int16(binary.LittleEndian.Uint16(buf))) // in mins - return time.Date(1, 1, 1+days, 0, 0, sec+offset*60, ns, - time.FixedZone("", offset*60)) -} - -func divFloor(x int64, y int64) int64 { - q := x / y - r := x % y - if r != 0 && ((r < 0) != (y < 0)) { - q-- - } - return q -} - -func dateTime2(t time.Time) (days int32, ns int64) { - // number of days since Jan 1 1970 UTC - days64 := divFloor(t.Unix(), 24*60*60) - // number of days since Jan 1 1 UTC - days = int32(days64) + 1969*365 + 1969/4 - 1969/100 + 1969/400 - // number of seconds within day - secs := t.Unix() - days64*24*60*60 - // number of nanoseconds within day - ns = secs*1e9 + int64(t.Nanosecond()) - return -} - -func decodeChar(col collation, buf []byte) string { - return charset2utf8(col, buf) -} - -func decodeUcs2(buf []byte) string { - res, err := ucs22str(buf) - if err != nil { - badStreamPanicf("Invalid UCS2 encoding: %s", err.Error()) - } - return res -} - -func decodeNChar(buf []byte) string { - return decodeUcs2(buf) -} - -func decodeXml(ti typeInfo, buf []byte) string { - return decodeUcs2(buf) -} - -func decodeUdt(ti typeInfo, buf []byte) int { - panic("Not implemented") -} - -func makeDecl(ti typeInfo) string { - switch ti.TypeId { - case typeInt8: - return "bigint" - case typeFlt4: - return "real" - case typeIntN: - switch ti.Size { - case 1: - return "tinyint" - case 2: - return "smallint" - case 4: - return "int" - case 8: - return "bigint" - default: - panic("invalid size of INTNTYPE") - } - case typeFlt8: - return "float" - case typeFltN: - switch ti.Size { - case 4: - return "real" - case 8: - return "float" - default: - panic("invalid size of FLNNTYPE") - } - case typeBigVarBin: - if ti.Size > 8000 || ti.Size == 0 { - return fmt.Sprintf("varbinary(max)") - } else { - return fmt.Sprintf("varbinary(%d)", ti.Size) - } - case typeNVarChar: - if ti.Size > 8000 || ti.Size == 0 { - return fmt.Sprintf("nvarchar(max)") - } else { - return fmt.Sprintf("nvarchar(%d)", ti.Size/2) - } - case typeBit, typeBitN: - return "bit" - case typeDateTimeN: - return "datetime" - case typeDateTimeOffsetN: - return fmt.Sprintf("datetimeoffset(%d)", ti.Scale) - default: - panic(fmt.Sprintf("not implemented makeDecl for type %d", ti.TypeId)) - } -} diff --git a/vendor/github.com/dgrijalva/jwt-go/cmd/jwt/app.go b/vendor/github.com/dgrijalva/jwt-go/cmd/jwt/app.go deleted file mode 100644 index 62cb9a46e..000000000 --- a/vendor/github.com/dgrijalva/jwt-go/cmd/jwt/app.go +++ /dev/null @@ -1,186 +0,0 @@ -// A useful example app. You can use this to debug your tokens on the command line. -// This is also a great place to look at how you might use this library. -// -// Example usage: -// The following will create and sign a token, then verify it and output the original claims. -// echo {\"foo\":\"bar\"} | bin/jwt -key test/sample_key -alg RS256 -sign - | bin/jwt -key test/sample_key.pub -verify - -package main - -import ( - "encoding/json" - "flag" - "fmt" - "io" - "io/ioutil" - "os" - "regexp" - - "github.com/dgrijalva/jwt-go" -) - -var ( - // Options - flagAlg = flag.String("alg", "", "signing algorithm identifier") - flagKey = flag.String("key", "", "path to key file or '-' to read from stdin") - flagCompact = flag.Bool("compact", false, "output compact JSON") - flagDebug = flag.Bool("debug", false, "print out all kinds of debug data") - - // Modes - exactly one of these is required - flagSign = flag.String("sign", "", "path to claims object to sign or '-' to read from stdin") - flagVerify = flag.String("verify", "", "path to JWT token to verify or '-' to read from stdin") -) - -func main() { - // Usage message if you ask for -help or if you mess up inputs. - flag.Usage = func() { - fmt.Fprintf(os.Stderr, "Usage of %s:\n", os.Args[0]) - fmt.Fprintf(os.Stderr, " One of the following flags is required: sign, verify\n") - flag.PrintDefaults() - } - - // Parse command line options - flag.Parse() - - // Do the thing. If something goes wrong, print error to stderr - // and exit with a non-zero status code - if err := start(); err != nil { - fmt.Fprintf(os.Stderr, "Error: %v\n", err) - os.Exit(1) - } -} - -// Figure out which thing to do and then do that -func start() error { - if *flagSign != "" { - return signToken() - } else if *flagVerify != "" { - return verifyToken() - } else { - flag.Usage() - return fmt.Errorf("None of the required flags are present. What do you want me to do?") - } -} - -// Helper func: Read input from specified file or stdin -func loadData(p string) ([]byte, error) { - if p == "" { - return nil, fmt.Errorf("No path specified") - } - - var rdr io.Reader - if p == "-" { - rdr = os.Stdin - } else { - if f, err := os.Open(p); err == nil { - rdr = f - defer f.Close() - } else { - return nil, err - } - } - return ioutil.ReadAll(rdr) -} - -// Print a json object in accordance with the prophecy (or the command line options) -func printJSON(j interface{}) error { - var out []byte - var err error - - if *flagCompact == false { - out, err = json.MarshalIndent(j, "", " ") - } else { - out, err = json.Marshal(j) - } - - if err == nil { - fmt.Println(string(out)) - } - - return err -} - -// Verify a token and output the claims. This is a great example -// of how to verify and view a token. -func verifyToken() error { - // get the token - tokData, err := loadData(*flagVerify) - if err != nil { - return fmt.Errorf("Couldn't read token: %v", err) - } - - // trim possible whitespace from token - tokData = regexp.MustCompile(`\s*$`).ReplaceAll(tokData, []byte{}) - if *flagDebug { - fmt.Fprintf(os.Stderr, "Token len: %v bytes\n", len(tokData)) - } - - // Parse the token. Load the key from command line option - token, err := jwt.Parse(string(tokData), func(t *jwt.Token) (interface{}, error) { - return loadData(*flagKey) - }) - - // Print some debug data - if *flagDebug && token != nil { - fmt.Fprintf(os.Stderr, "Header:\n%v\n", token.Header) - fmt.Fprintf(os.Stderr, "Claims:\n%v\n", token.Claims) - } - - // Print an error if we can't parse for some reason - if err != nil { - return fmt.Errorf("Couldn't parse token: %v", err) - } - - // Is token invalid? - if !token.Valid { - return fmt.Errorf("Token is invalid") - } - - // Print the token details - if err := printJSON(token.Claims); err != nil { - return fmt.Errorf("Failed to output claims: %v", err) - } - - return nil -} - -// Create, sign, and output a token. This is a great, simple example of -// how to use this library to create and sign a token. -func signToken() error { - // get the token data from command line arguments - tokData, err := loadData(*flagSign) - if err != nil { - return fmt.Errorf("Couldn't read token: %v", err) - } else if *flagDebug { - fmt.Fprintf(os.Stderr, "Token: %v bytes", len(tokData)) - } - - // parse the JSON of the claims - var claims map[string]interface{} - if err := json.Unmarshal(tokData, &claims); err != nil { - return fmt.Errorf("Couldn't parse claims JSON: %v", err) - } - - // get the key - keyData, err := loadData(*flagKey) - if err != nil { - return fmt.Errorf("Couldn't read key: %v", err) - } - - // get the signing alg - alg := jwt.GetSigningMethod(*flagAlg) - if alg == nil { - return fmt.Errorf("Couldn't find signing method: %v", *flagAlg) - } - - // create a new token - token := jwt.New(alg) - token.Claims = claims - - if out, err := token.SignedString(keyData); err == nil { - fmt.Println(out) - } else { - return fmt.Errorf("Error signing token: %v", err) - } - - return nil -} diff --git a/vendor/github.com/dgrijalva/jwt-go/ecdsa_test.go b/vendor/github.com/dgrijalva/jwt-go/ecdsa_test.go deleted file mode 100644 index 98e3e5edb..000000000 --- a/vendor/github.com/dgrijalva/jwt-go/ecdsa_test.go +++ /dev/null @@ -1,100 +0,0 @@ -package jwt_test - -import ( - "crypto/ecdsa" - "io/ioutil" - "strings" - "testing" - - "github.com/dgrijalva/jwt-go" -) - -var ecdsaTestData = []struct { - name string - keys map[string]string - tokenString string - alg string - claims map[string]interface{} - valid bool -}{ - { - "Basic ES256", - map[string]string{"private": "test/ec256-private.pem", "public": "test/ec256-public.pem"}, - "eyJhbGciOiJFUzI1NiIsInR5cCI6IkpXVCJ9.eyJmb28iOiJiYXIifQ.MEQCIHoSJnmGlPaVQDqacx_2XlXEhhqtWceVopjomc2PJLtdAiAUTeGPoNYxZw0z8mgOnnIcjoxRuNDVZvybRZF3wR1l8w", - "ES256", - map[string]interface{}{"foo": "bar"}, - true, - }, - { - "Basic ES384", - map[string]string{"private": "test/ec384-private.pem", "public": "test/ec384-public.pem"}, - "eyJhbGciOiJFUzM4NCIsInR5cCI6IkpXVCJ9.eyJmb28iOiJiYXIifQ.MGUCMQCHBr61FXDuFY9xUhyp8iWQAuBIaSgaf1z2j_8XrKcCfzTPzoSa3SZKq-m3L492xe8CMG3kafRMeuaN5Aw8ZJxmOLhkTo4D3-LaGzcaUWINvWvkwFMl7dMC863s0gov6xvXuA", - "ES384", - map[string]interface{}{"foo": "bar"}, - true, - }, - { - "Basic ES512", - map[string]string{"private": "test/ec512-private.pem", "public": "test/ec512-public.pem"}, - "eyJhbGciOiJFUzUxMiIsInR5cCI6IkpXVCJ9.eyJmb28iOiJiYXIifQ.MIGIAkIAmVKjdJE5lG1byOFgZZVTeNDRp6E7SNvUj0UrvpzoBH6nrleWVTcwfHzbwWuooNpPADDSFR_Ql3ze-Vwwi8hBqQsCQgHn-ZooL8zegkOVeEEsqd7WHWdhb8UekFCYw3X8JnNP-D3wvZQ1-tkkHakt5gZ2-xO29TxfSPun4ViGkMYa7Q4N-Q", - "ES512", - map[string]interface{}{"foo": "bar"}, - true, - }, - { - "basic ES256 invalid: foo => bar", - map[string]string{"private": "test/ec256-private.pem", "public": "test/ec256-public.pem"}, - "eyJhbGciOiJFUzI1NiIsInR5cCI6IkpXVCJ9.eyJmb28iOiJiYXIifQ.MEQCIHoSJnmGlPaVQDqacx_2XlXEhhqtWceVopjomc2PJLtdAiAUTeGPoNYxZw0z8mgOnnIcjoxRuNDVZvybRZF3wR1l8W", - "ES256", - map[string]interface{}{"foo": "bar"}, - false, - }, -} - -func TestECDSAVerify(t *testing.T) { - for _, data := range ecdsaTestData { - var err error - - key, _ := ioutil.ReadFile(data.keys["public"]) - - var ecdsaKey *ecdsa.PublicKey - if ecdsaKey, err = jwt.ParseECPublicKeyFromPEM(key); err != nil { - t.Errorf("Unable to parse ECDSA public key: %v", err) - } - - parts := strings.Split(data.tokenString, ".") - - method := jwt.GetSigningMethod(data.alg) - err = method.Verify(strings.Join(parts[0:2], "."), parts[2], ecdsaKey) - if data.valid && err != nil { - t.Errorf("[%v] Error while verifying key: %v", data.name, err) - } - if !data.valid && err == nil { - t.Errorf("[%v] Invalid key passed validation", data.name) - } - } -} - -func TestECDSASign(t *testing.T) { - for _, data := range ecdsaTestData { - var err error - key, _ := ioutil.ReadFile(data.keys["private"]) - - var ecdsaKey *ecdsa.PrivateKey - if ecdsaKey, err = jwt.ParseECPrivateKeyFromPEM(key); err != nil { - t.Errorf("Unable to parse ECDSA private key: %v", err) - } - - if data.valid { - parts := strings.Split(data.tokenString, ".") - method := jwt.GetSigningMethod(data.alg) - sig, err := method.Sign(strings.Join(parts[0:2], "."), ecdsaKey) - if err != nil { - t.Errorf("[%v] Error signing token: %v", data.name, err) - } - if sig == parts[2] { - t.Errorf("[%v] Identical signatures\nbefore:\n%v\nafter:\n%v", data.name, parts[2], sig) - } - } - } -} diff --git a/vendor/github.com/dgrijalva/jwt-go/example_test.go b/vendor/github.com/dgrijalva/jwt-go/example_test.go deleted file mode 100644 index edb48e4db..000000000 --- a/vendor/github.com/dgrijalva/jwt-go/example_test.go +++ /dev/null @@ -1,52 +0,0 @@ -package jwt_test - -import ( - "fmt" - "github.com/dgrijalva/jwt-go" - "time" -) - -func ExampleParse(myToken string, myLookupKey func(interface{}) (interface{}, error)) { - token, err := jwt.Parse(myToken, func(token *jwt.Token) (interface{}, error) { - return myLookupKey(token.Header["kid"]) - }) - - if err == nil && token.Valid { - fmt.Println("Your token is valid. I like your style.") - } else { - fmt.Println("This token is terrible! I cannot accept this.") - } -} - -func ExampleNew(mySigningKey []byte) (string, error) { - // Create the token - token := jwt.New(jwt.SigningMethodHS256) - // Set some claims - token.Claims["foo"] = "bar" - token.Claims["exp"] = time.Now().Add(time.Hour * 72).Unix() - // Sign and get the complete encoded token as a string - tokenString, err := token.SignedString(mySigningKey) - return tokenString, err -} - -func ExampleParse_errorChecking(myToken string, myLookupKey func(interface{}) (interface{}, error)) { - token, err := jwt.Parse(myToken, func(token *jwt.Token) (interface{}, error) { - return myLookupKey(token.Header["kid"]) - }) - - if token.Valid { - fmt.Println("You look nice today") - } else if ve, ok := err.(*jwt.ValidationError); ok { - if ve.Errors&jwt.ValidationErrorMalformed != 0 { - fmt.Println("That's not even a token") - } else if ve.Errors&(jwt.ValidationErrorExpired|jwt.ValidationErrorNotValidYet) != 0 { - // Token is either expired or not active yet - fmt.Println("Timing is everything") - } else { - fmt.Println("Couldn't handle this token:", err) - } - } else { - fmt.Println("Couldn't handle this token:", err) - } - -} diff --git a/vendor/github.com/dgrijalva/jwt-go/hmac_test.go b/vendor/github.com/dgrijalva/jwt-go/hmac_test.go deleted file mode 100644 index c7e114f4f..000000000 --- a/vendor/github.com/dgrijalva/jwt-go/hmac_test.go +++ /dev/null @@ -1,91 +0,0 @@ -package jwt_test - -import ( - "github.com/dgrijalva/jwt-go" - "io/ioutil" - "strings" - "testing" -) - -var hmacTestData = []struct { - name string - tokenString string - alg string - claims map[string]interface{} - valid bool -}{ - { - "web sample", - "eyJ0eXAiOiJKV1QiLA0KICJhbGciOiJIUzI1NiJ9.eyJpc3MiOiJqb2UiLA0KICJleHAiOjEzMDA4MTkzODAsDQogImh0dHA6Ly9leGFtcGxlLmNvbS9pc19yb290Ijp0cnVlfQ.dBjftJeZ4CVP-mB92K27uhbUJU1p1r_wW1gFWFOEjXk", - "HS256", - map[string]interface{}{"iss": "joe", "exp": 1300819380, "http://example.com/is_root": true}, - true, - }, - { - "HS384", - "eyJhbGciOiJIUzM4NCIsInR5cCI6IkpXVCJ9.eyJleHAiOjEuMzAwODE5MzhlKzA5LCJodHRwOi8vZXhhbXBsZS5jb20vaXNfcm9vdCI6dHJ1ZSwiaXNzIjoiam9lIn0.KWZEuOD5lbBxZ34g7F-SlVLAQ_r5KApWNWlZIIMyQVz5Zs58a7XdNzj5_0EcNoOy", - "HS384", - map[string]interface{}{"iss": "joe", "exp": 1300819380, "http://example.com/is_root": true}, - true, - }, - { - "HS512", - "eyJhbGciOiJIUzUxMiIsInR5cCI6IkpXVCJ9.eyJleHAiOjEuMzAwODE5MzhlKzA5LCJodHRwOi8vZXhhbXBsZS5jb20vaXNfcm9vdCI6dHJ1ZSwiaXNzIjoiam9lIn0.CN7YijRX6Aw1n2jyI2Id1w90ja-DEMYiWixhYCyHnrZ1VfJRaFQz1bEbjjA5Fn4CLYaUG432dEYmSbS4Saokmw", - "HS512", - map[string]interface{}{"iss": "joe", "exp": 1300819380, "http://example.com/is_root": true}, - true, - }, - { - "web sample: invalid", - "eyJ0eXAiOiJKV1QiLA0KICJhbGciOiJIUzI1NiJ9.eyJpc3MiOiJqb2UiLA0KICJleHAiOjEzMDA4MTkzODAsDQogImh0dHA6Ly9leGFtcGxlLmNvbS9pc19yb290Ijp0cnVlfQ.dBjftJeZ4CVP-mB92K27uhbUJU1p1r_wW1gFWFOEjXo", - "HS256", - map[string]interface{}{"iss": "joe", "exp": 1300819380, "http://example.com/is_root": true}, - false, - }, -} - -// Sample data from http://tools.ietf.org/html/draft-jones-json-web-signature-04#appendix-A.1 -var hmacTestKey, _ = ioutil.ReadFile("test/hmacTestKey") - -func TestHMACVerify(t *testing.T) { - for _, data := range hmacTestData { - parts := strings.Split(data.tokenString, ".") - - method := jwt.GetSigningMethod(data.alg) - err := method.Verify(strings.Join(parts[0:2], "."), parts[2], hmacTestKey) - if data.valid && err != nil { - t.Errorf("[%v] Error while verifying key: %v", data.name, err) - } - if !data.valid && err == nil { - t.Errorf("[%v] Invalid key passed validation", data.name) - } - } -} - -func TestHMACSign(t *testing.T) { - for _, data := range hmacTestData { - if data.valid { - parts := strings.Split(data.tokenString, ".") - method := jwt.GetSigningMethod(data.alg) - sig, err := method.Sign(strings.Join(parts[0:2], "."), hmacTestKey) - if err != nil { - t.Errorf("[%v] Error signing token: %v", data.name, err) - } - if sig != parts[2] { - t.Errorf("[%v] Incorrect signature.\nwas:\n%v\nexpecting:\n%v", data.name, sig, parts[2]) - } - } - } -} - -func BenchmarkHS256Signing(b *testing.B) { - benchmarkSigning(b, jwt.SigningMethodHS256, hmacTestKey) -} - -func BenchmarkHS384Signing(b *testing.B) { - benchmarkSigning(b, jwt.SigningMethodHS384, hmacTestKey) -} - -func BenchmarkHS512Signing(b *testing.B) { - benchmarkSigning(b, jwt.SigningMethodHS512, hmacTestKey) -} diff --git a/vendor/github.com/dgrijalva/jwt-go/jwt_test.go b/vendor/github.com/dgrijalva/jwt-go/jwt_test.go deleted file mode 100644 index 9108dedb4..000000000 --- a/vendor/github.com/dgrijalva/jwt-go/jwt_test.go +++ /dev/null @@ -1,187 +0,0 @@ -package jwt_test - -import ( - "fmt" - "github.com/dgrijalva/jwt-go" - "io/ioutil" - "net/http" - "reflect" - "testing" - "time" -) - -var ( - jwtTestDefaultKey []byte - defaultKeyFunc jwt.Keyfunc = func(t *jwt.Token) (interface{}, error) { return jwtTestDefaultKey, nil } - emptyKeyFunc jwt.Keyfunc = func(t *jwt.Token) (interface{}, error) { return nil, nil } - errorKeyFunc jwt.Keyfunc = func(t *jwt.Token) (interface{}, error) { return nil, fmt.Errorf("error loading key") } - nilKeyFunc jwt.Keyfunc = nil -) - -var jwtTestData = []struct { - name string - tokenString string - keyfunc jwt.Keyfunc - claims map[string]interface{} - valid bool - errors uint32 -}{ - { - "basic", - "eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiJ9.eyJmb28iOiJiYXIifQ.FhkiHkoESI_cG3NPigFrxEk9Z60_oXrOT2vGm9Pn6RDgYNovYORQmmA0zs1AoAOf09ly2Nx2YAg6ABqAYga1AcMFkJljwxTT5fYphTuqpWdy4BELeSYJx5Ty2gmr8e7RonuUztrdD5WfPqLKMm1Ozp_T6zALpRmwTIW0QPnaBXaQD90FplAg46Iy1UlDKr-Eupy0i5SLch5Q-p2ZpaL_5fnTIUDlxC3pWhJTyx_71qDI-mAA_5lE_VdroOeflG56sSmDxopPEG3bFlSu1eowyBfxtu0_CuVd-M42RU75Zc4Gsj6uV77MBtbMrf4_7M_NUTSgoIF3fRqxrj0NzihIBg", - defaultKeyFunc, - map[string]interface{}{"foo": "bar"}, - true, - 0, - }, - { - "basic expired", - "", // autogen - defaultKeyFunc, - map[string]interface{}{"foo": "bar", "exp": float64(time.Now().Unix() - 100)}, - false, - jwt.ValidationErrorExpired, - }, - { - "basic nbf", - "", // autogen - defaultKeyFunc, - map[string]interface{}{"foo": "bar", "nbf": float64(time.Now().Unix() + 100)}, - false, - jwt.ValidationErrorNotValidYet, - }, - { - "expired and nbf", - "", // autogen - defaultKeyFunc, - map[string]interface{}{"foo": "bar", "nbf": float64(time.Now().Unix() + 100), "exp": float64(time.Now().Unix() - 100)}, - false, - jwt.ValidationErrorNotValidYet | jwt.ValidationErrorExpired, - }, - { - "basic invalid", - "eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiJ9.eyJmb28iOiJiYXIifQ.EhkiHkoESI_cG3NPigFrxEk9Z60_oXrOT2vGm9Pn6RDgYNovYORQmmA0zs1AoAOf09ly2Nx2YAg6ABqAYga1AcMFkJljwxTT5fYphTuqpWdy4BELeSYJx5Ty2gmr8e7RonuUztrdD5WfPqLKMm1Ozp_T6zALpRmwTIW0QPnaBXaQD90FplAg46Iy1UlDKr-Eupy0i5SLch5Q-p2ZpaL_5fnTIUDlxC3pWhJTyx_71qDI-mAA_5lE_VdroOeflG56sSmDxopPEG3bFlSu1eowyBfxtu0_CuVd-M42RU75Zc4Gsj6uV77MBtbMrf4_7M_NUTSgoIF3fRqxrj0NzihIBg", - defaultKeyFunc, - map[string]interface{}{"foo": "bar"}, - false, - jwt.ValidationErrorSignatureInvalid, - }, - { - "basic nokeyfunc", - "eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiJ9.eyJmb28iOiJiYXIifQ.FhkiHkoESI_cG3NPigFrxEk9Z60_oXrOT2vGm9Pn6RDgYNovYORQmmA0zs1AoAOf09ly2Nx2YAg6ABqAYga1AcMFkJljwxTT5fYphTuqpWdy4BELeSYJx5Ty2gmr8e7RonuUztrdD5WfPqLKMm1Ozp_T6zALpRmwTIW0QPnaBXaQD90FplAg46Iy1UlDKr-Eupy0i5SLch5Q-p2ZpaL_5fnTIUDlxC3pWhJTyx_71qDI-mAA_5lE_VdroOeflG56sSmDxopPEG3bFlSu1eowyBfxtu0_CuVd-M42RU75Zc4Gsj6uV77MBtbMrf4_7M_NUTSgoIF3fRqxrj0NzihIBg", - nilKeyFunc, - map[string]interface{}{"foo": "bar"}, - false, - jwt.ValidationErrorUnverifiable, - }, - { - "basic nokey", - "eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiJ9.eyJmb28iOiJiYXIifQ.FhkiHkoESI_cG3NPigFrxEk9Z60_oXrOT2vGm9Pn6RDgYNovYORQmmA0zs1AoAOf09ly2Nx2YAg6ABqAYga1AcMFkJljwxTT5fYphTuqpWdy4BELeSYJx5Ty2gmr8e7RonuUztrdD5WfPqLKMm1Ozp_T6zALpRmwTIW0QPnaBXaQD90FplAg46Iy1UlDKr-Eupy0i5SLch5Q-p2ZpaL_5fnTIUDlxC3pWhJTyx_71qDI-mAA_5lE_VdroOeflG56sSmDxopPEG3bFlSu1eowyBfxtu0_CuVd-M42RU75Zc4Gsj6uV77MBtbMrf4_7M_NUTSgoIF3fRqxrj0NzihIBg", - emptyKeyFunc, - map[string]interface{}{"foo": "bar"}, - false, - jwt.ValidationErrorSignatureInvalid, - }, - { - "basic errorkey", - "eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiJ9.eyJmb28iOiJiYXIifQ.FhkiHkoESI_cG3NPigFrxEk9Z60_oXrOT2vGm9Pn6RDgYNovYORQmmA0zs1AoAOf09ly2Nx2YAg6ABqAYga1AcMFkJljwxTT5fYphTuqpWdy4BELeSYJx5Ty2gmr8e7RonuUztrdD5WfPqLKMm1Ozp_T6zALpRmwTIW0QPnaBXaQD90FplAg46Iy1UlDKr-Eupy0i5SLch5Q-p2ZpaL_5fnTIUDlxC3pWhJTyx_71qDI-mAA_5lE_VdroOeflG56sSmDxopPEG3bFlSu1eowyBfxtu0_CuVd-M42RU75Zc4Gsj6uV77MBtbMrf4_7M_NUTSgoIF3fRqxrj0NzihIBg", - errorKeyFunc, - map[string]interface{}{"foo": "bar"}, - false, - jwt.ValidationErrorUnverifiable, - }, -} - -func init() { - var e error - if jwtTestDefaultKey, e = ioutil.ReadFile("test/sample_key.pub"); e != nil { - panic(e) - } -} - -func makeSample(c map[string]interface{}) string { - key, e := ioutil.ReadFile("test/sample_key") - if e != nil { - panic(e.Error()) - } - - token := jwt.New(jwt.SigningMethodRS256) - token.Claims = c - s, e := token.SignedString(key) - - if e != nil { - panic(e.Error()) - } - - return s -} - -func TestJWT(t *testing.T) { - for _, data := range jwtTestData { - if data.tokenString == "" { - data.tokenString = makeSample(data.claims) - } - token, err := jwt.Parse(data.tokenString, data.keyfunc) - - if !reflect.DeepEqual(data.claims, token.Claims) { - t.Errorf("[%v] Claims mismatch. Expecting: %v Got: %v", data.name, data.claims, token.Claims) - } - if data.valid && err != nil { - t.Errorf("[%v] Error while verifying token: %T:%v", data.name, err, err) - } - if !data.valid && err == nil { - t.Errorf("[%v] Invalid token passed validation", data.name) - } - if data.errors != 0 { - if err == nil { - t.Errorf("[%v] Expecting error. Didn't get one.", data.name) - } else { - // compare the bitfield part of the error - if err.(*jwt.ValidationError).Errors != data.errors { - t.Errorf("[%v] Errors don't match expectation", data.name) - } - - } - } - } -} - -func TestParseRequest(t *testing.T) { - // Bearer token request - for _, data := range jwtTestData { - if data.tokenString == "" { - data.tokenString = makeSample(data.claims) - } - - r, _ := http.NewRequest("GET", "/", nil) - r.Header.Set("Authorization", fmt.Sprintf("Bearer %v", data.tokenString)) - token, err := jwt.ParseFromRequest(r, data.keyfunc) - - if token == nil { - t.Errorf("[%v] Token was not found: %v", data.name, err) - continue - } - if !reflect.DeepEqual(data.claims, token.Claims) { - t.Errorf("[%v] Claims mismatch. Expecting: %v Got: %v", data.name, data.claims, token.Claims) - } - if data.valid && err != nil { - t.Errorf("[%v] Error while verifying token: %v", data.name, err) - } - if !data.valid && err == nil { - t.Errorf("[%v] Invalid token passed validation", data.name) - } - } -} - -// Helper method for benchmarking various methods -func benchmarkSigning(b *testing.B, method jwt.SigningMethod, key interface{}) { - t := jwt.New(method) - b.RunParallel(func(pb *testing.PB) { - for pb.Next() { - if _, err := t.SignedString(key); err != nil { - b.Fatal(err) - } - } - }) - -} diff --git a/vendor/github.com/dgrijalva/jwt-go/rsa_pss_test.go b/vendor/github.com/dgrijalva/jwt-go/rsa_pss_test.go deleted file mode 100644 index 9045aaf34..000000000 --- a/vendor/github.com/dgrijalva/jwt-go/rsa_pss_test.go +++ /dev/null @@ -1,96 +0,0 @@ -// +build go1.4 - -package jwt_test - -import ( - "crypto/rsa" - "io/ioutil" - "strings" - "testing" - - "github.com/dgrijalva/jwt-go" -) - -var rsaPSSTestData = []struct { - name string - tokenString string - alg string - claims map[string]interface{} - valid bool -}{ - { - "Basic PS256", - "eyJhbGciOiJQUzI1NiIsInR5cCI6IkpXVCJ9.eyJmb28iOiJiYXIifQ.PPG4xyDVY8ffp4CcxofNmsTDXsrVG2npdQuibLhJbv4ClyPTUtR5giNSvuxo03kB6I8VXVr0Y9X7UxhJVEoJOmULAwRWaUsDnIewQa101cVhMa6iR8X37kfFoiZ6NkS-c7henVkkQWu2HtotkEtQvN5hFlk8IevXXPmvZlhQhwzB1sGzGYnoi1zOfuL98d3BIjUjtlwii5w6gYG2AEEzp7HnHCsb3jIwUPdq86Oe6hIFjtBwduIK90ca4UqzARpcfwxHwVLMpatKask00AgGVI0ysdk0BLMjmLutquD03XbThHScC2C2_Pp4cHWgMzvbgLU2RYYZcZRKr46QeNgz9w", - "PS256", - map[string]interface{}{"foo": "bar"}, - true, - }, - { - "Basic PS384", - "eyJhbGciOiJQUzM4NCIsInR5cCI6IkpXVCJ9.eyJmb28iOiJiYXIifQ.w7-qqgj97gK4fJsq_DCqdYQiylJjzWONvD0qWWWhqEOFk2P1eDULPnqHRnjgTXoO4HAw4YIWCsZPet7nR3Xxq4ZhMqvKW8b7KlfRTb9cH8zqFvzMmybQ4jv2hKc3bXYqVow3AoR7hN_CWXI3Dv6Kd2X5xhtxRHI6IL39oTVDUQ74LACe-9t4c3QRPuj6Pq1H4FAT2E2kW_0KOc6EQhCLWEhm2Z2__OZskDC8AiPpP8Kv4k2vB7l0IKQu8Pr4RcNBlqJdq8dA5D3hk5TLxP8V5nG1Ib80MOMMqoS3FQvSLyolFX-R_jZ3-zfq6Ebsqr0yEb0AH2CfsECF7935Pa0FKQ", - "PS384", - map[string]interface{}{"foo": "bar"}, - true, - }, - { - "Basic PS512", - "eyJhbGciOiJQUzUxMiIsInR5cCI6IkpXVCJ9.eyJmb28iOiJiYXIifQ.GX1HWGzFaJevuSLavqqFYaW8_TpvcjQ8KfC5fXiSDzSiT9UD9nB_ikSmDNyDILNdtjZLSvVKfXxZJqCfefxAtiozEDDdJthZ-F0uO4SPFHlGiXszvKeodh7BuTWRI2wL9-ZO4mFa8nq3GMeQAfo9cx11i7nfN8n2YNQ9SHGovG7_T_AvaMZB_jT6jkDHpwGR9mz7x1sycckEo6teLdHRnH_ZdlHlxqknmyTu8Odr5Xh0sJFOL8BepWbbvIIn-P161rRHHiDWFv6nhlHwZnVzjx7HQrWSGb6-s2cdLie9QL_8XaMcUpjLkfOMKkDOfHo6AvpL7Jbwi83Z2ZTHjJWB-A", - "PS512", - map[string]interface{}{"foo": "bar"}, - true, - }, - { - "basic PS256 invalid: foo => bar", - "eyJhbGciOiJQUzI1NiIsInR5cCI6IkpXVCJ9.eyJmb28iOiJiYXIifQ.PPG4xyDVY8ffp4CcxofNmsTDXsrVG2npdQuibLhJbv4ClyPTUtR5giNSvuxo03kB6I8VXVr0Y9X7UxhJVEoJOmULAwRWaUsDnIewQa101cVhMa6iR8X37kfFoiZ6NkS-c7henVkkQWu2HtotkEtQvN5hFlk8IevXXPmvZlhQhwzB1sGzGYnoi1zOfuL98d3BIjUjtlwii5w6gYG2AEEzp7HnHCsb3jIwUPdq86Oe6hIFjtBwduIK90ca4UqzARpcfwxHwVLMpatKask00AgGVI0ysdk0BLMjmLutquD03XbThHScC2C2_Pp4cHWgMzvbgLU2RYYZcZRKr46QeNgz9W", - "PS256", - map[string]interface{}{"foo": "bar"}, - false, - }, -} - -func TestRSAPSSVerify(t *testing.T) { - var err error - - key, _ := ioutil.ReadFile("test/sample_key.pub") - var rsaPSSKey *rsa.PublicKey - if rsaPSSKey, err = jwt.ParseRSAPublicKeyFromPEM(key); err != nil { - t.Errorf("Unable to parse RSA public key: %v", err) - } - - for _, data := range rsaPSSTestData { - parts := strings.Split(data.tokenString, ".") - - method := jwt.GetSigningMethod(data.alg) - err := method.Verify(strings.Join(parts[0:2], "."), parts[2], rsaPSSKey) - if data.valid && err != nil { - t.Errorf("[%v] Error while verifying key: %v", data.name, err) - } - if !data.valid && err == nil { - t.Errorf("[%v] Invalid key passed validation", data.name) - } - } -} - -func TestRSAPSSSign(t *testing.T) { - var err error - - key, _ := ioutil.ReadFile("test/sample_key") - var rsaPSSKey *rsa.PrivateKey - if rsaPSSKey, err = jwt.ParseRSAPrivateKeyFromPEM(key); err != nil { - t.Errorf("Unable to parse RSA private key: %v", err) - } - - for _, data := range rsaPSSTestData { - if data.valid { - parts := strings.Split(data.tokenString, ".") - method := jwt.GetSigningMethod(data.alg) - sig, err := method.Sign(strings.Join(parts[0:2], "."), rsaPSSKey) - if err != nil { - t.Errorf("[%v] Error signing token: %v", data.name, err) - } - if sig == parts[2] { - t.Errorf("[%v] Signatures shouldn't match\nnew:\n%v\noriginal:\n%v", data.name, sig, parts[2]) - } - } - } -} diff --git a/vendor/github.com/dgrijalva/jwt-go/rsa_test.go b/vendor/github.com/dgrijalva/jwt-go/rsa_test.go deleted file mode 100644 index 13ba1fcdc..000000000 --- a/vendor/github.com/dgrijalva/jwt-go/rsa_test.go +++ /dev/null @@ -1,174 +0,0 @@ -package jwt_test - -import ( - "github.com/dgrijalva/jwt-go" - "io/ioutil" - "strings" - "testing" -) - -var rsaTestData = []struct { - name string - tokenString string - alg string - claims map[string]interface{} - valid bool -}{ - { - "Basic RS256", - "eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiJ9.eyJmb28iOiJiYXIifQ.FhkiHkoESI_cG3NPigFrxEk9Z60_oXrOT2vGm9Pn6RDgYNovYORQmmA0zs1AoAOf09ly2Nx2YAg6ABqAYga1AcMFkJljwxTT5fYphTuqpWdy4BELeSYJx5Ty2gmr8e7RonuUztrdD5WfPqLKMm1Ozp_T6zALpRmwTIW0QPnaBXaQD90FplAg46Iy1UlDKr-Eupy0i5SLch5Q-p2ZpaL_5fnTIUDlxC3pWhJTyx_71qDI-mAA_5lE_VdroOeflG56sSmDxopPEG3bFlSu1eowyBfxtu0_CuVd-M42RU75Zc4Gsj6uV77MBtbMrf4_7M_NUTSgoIF3fRqxrj0NzihIBg", - "RS256", - map[string]interface{}{"foo": "bar"}, - true, - }, - { - "Basic RS384", - "eyJhbGciOiJSUzM4NCIsInR5cCI6IkpXVCJ9.eyJmb28iOiJiYXIifQ.W-jEzRfBigtCWsinvVVuldiuilzVdU5ty0MvpLaSaqK9PlAWWlDQ1VIQ_qSKzwL5IXaZkvZFJXT3yL3n7OUVu7zCNJzdwznbC8Z-b0z2lYvcklJYi2VOFRcGbJtXUqgjk2oGsiqUMUMOLP70TTefkpsgqDxbRh9CDUfpOJgW-dU7cmgaoswe3wjUAUi6B6G2YEaiuXC0XScQYSYVKIzgKXJV8Zw-7AN_DBUI4GkTpsvQ9fVVjZM9csQiEXhYekyrKu1nu_POpQonGd8yqkIyXPECNmmqH5jH4sFiF67XhD7_JpkvLziBpI-uh86evBUadmHhb9Otqw3uV3NTaXLzJw", - "RS384", - map[string]interface{}{"foo": "bar"}, - true, - }, - { - "Basic RS512", - "eyJhbGciOiJSUzUxMiIsInR5cCI6IkpXVCJ9.eyJmb28iOiJiYXIifQ.zBlLlmRrUxx4SJPUbV37Q1joRcI9EW13grnKduK3wtYKmDXbgDpF1cZ6B-2Jsm5RB8REmMiLpGms-EjXhgnyh2TSHE-9W2gA_jvshegLWtwRVDX40ODSkTb7OVuaWgiy9y7llvcknFBTIg-FnVPVpXMmeV_pvwQyhaz1SSwSPrDyxEmksz1hq7YONXhXPpGaNbMMeDTNP_1oj8DZaqTIL9TwV8_1wb2Odt_Fy58Ke2RVFijsOLdnyEAjt2n9Mxihu9i3PhNBkkxa2GbnXBfq3kzvZ_xxGGopLdHhJjcGWXO-NiwI9_tiu14NRv4L2xC0ItD9Yz68v2ZIZEp_DuzwRQ", - "RS512", - map[string]interface{}{"foo": "bar"}, - true, - }, - { - "basic invalid: foo => bar", - "eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiJ9.eyJmb28iOiJiYXIifQ.EhkiHkoESI_cG3NPigFrxEk9Z60_oXrOT2vGm9Pn6RDgYNovYORQmmA0zs1AoAOf09ly2Nx2YAg6ABqAYga1AcMFkJljwxTT5fYphTuqpWdy4BELeSYJx5Ty2gmr8e7RonuUztrdD5WfPqLKMm1Ozp_T6zALpRmwTIW0QPnaBXaQD90FplAg46Iy1UlDKr-Eupy0i5SLch5Q-p2ZpaL_5fnTIUDlxC3pWhJTyx_71qDI-mAA_5lE_VdroOeflG56sSmDxopPEG3bFlSu1eowyBfxtu0_CuVd-M42RU75Zc4Gsj6uV77MBtbMrf4_7M_NUTSgoIF3fRqxrj0NzihIBg", - "RS256", - map[string]interface{}{"foo": "bar"}, - false, - }, -} - -func TestRSAVerify(t *testing.T) { - key, _ := ioutil.ReadFile("test/sample_key.pub") - - for _, data := range rsaTestData { - parts := strings.Split(data.tokenString, ".") - - method := jwt.GetSigningMethod(data.alg) - err := method.Verify(strings.Join(parts[0:2], "."), parts[2], key) - if data.valid && err != nil { - t.Errorf("[%v] Error while verifying key: %v", data.name, err) - } - if !data.valid && err == nil { - t.Errorf("[%v] Invalid key passed validation", data.name) - } - } -} - -func TestRSASign(t *testing.T) { - key, _ := ioutil.ReadFile("test/sample_key") - - for _, data := range rsaTestData { - if data.valid { - parts := strings.Split(data.tokenString, ".") - method := jwt.GetSigningMethod(data.alg) - sig, err := method.Sign(strings.Join(parts[0:2], "."), key) - if err != nil { - t.Errorf("[%v] Error signing token: %v", data.name, err) - } - if sig != parts[2] { - t.Errorf("[%v] Incorrect signature.\nwas:\n%v\nexpecting:\n%v", data.name, sig, parts[2]) - } - } - } -} - -func TestRSAVerifyWithPreParsedPrivateKey(t *testing.T) { - key, _ := ioutil.ReadFile("test/sample_key.pub") - parsedKey, err := jwt.ParseRSAPublicKeyFromPEM(key) - if err != nil { - t.Fatal(err) - } - testData := rsaTestData[0] - parts := strings.Split(testData.tokenString, ".") - err = jwt.SigningMethodRS256.Verify(strings.Join(parts[0:2], "."), parts[2], parsedKey) - if err != nil { - t.Errorf("[%v] Error while verifying key: %v", testData.name, err) - } -} - -func TestRSAWithPreParsedPrivateKey(t *testing.T) { - key, _ := ioutil.ReadFile("test/sample_key") - parsedKey, err := jwt.ParseRSAPrivateKeyFromPEM(key) - if err != nil { - t.Fatal(err) - } - testData := rsaTestData[0] - parts := strings.Split(testData.tokenString, ".") - sig, err := jwt.SigningMethodRS256.Sign(strings.Join(parts[0:2], "."), parsedKey) - if err != nil { - t.Errorf("[%v] Error signing token: %v", testData.name, err) - } - if sig != parts[2] { - t.Errorf("[%v] Incorrect signature.\nwas:\n%v\nexpecting:\n%v", testData.name, sig, parts[2]) - } -} - -func TestRSAKeyParsing(t *testing.T) { - key, _ := ioutil.ReadFile("test/sample_key") - pubKey, _ := ioutil.ReadFile("test/sample_key.pub") - badKey := []byte("All your base are belong to key") - - // Test parsePrivateKey - if _, e := jwt.ParseRSAPrivateKeyFromPEM(key); e != nil { - t.Errorf("Failed to parse valid private key: %v", e) - } - - if k, e := jwt.ParseRSAPrivateKeyFromPEM(pubKey); e == nil { - t.Errorf("Parsed public key as valid private key: %v", k) - } - - if k, e := jwt.ParseRSAPrivateKeyFromPEM(badKey); e == nil { - t.Errorf("Parsed invalid key as valid private key: %v", k) - } - - // Test parsePublicKey - if _, e := jwt.ParseRSAPublicKeyFromPEM(pubKey); e != nil { - t.Errorf("Failed to parse valid public key: %v", e) - } - - if k, e := jwt.ParseRSAPublicKeyFromPEM(key); e == nil { - t.Errorf("Parsed private key as valid public key: %v", k) - } - - if k, e := jwt.ParseRSAPublicKeyFromPEM(badKey); e == nil { - t.Errorf("Parsed invalid key as valid private key: %v", k) - } - -} - -func BenchmarkRS256Signing(b *testing.B) { - key, _ := ioutil.ReadFile("test/sample_key") - parsedKey, err := jwt.ParseRSAPrivateKeyFromPEM(key) - if err != nil { - b.Fatal(err) - } - - benchmarkSigning(b, jwt.SigningMethodRS256, parsedKey) -} - -func BenchmarkRS384Signing(b *testing.B) { - key, _ := ioutil.ReadFile("test/sample_key") - parsedKey, err := jwt.ParseRSAPrivateKeyFromPEM(key) - if err != nil { - b.Fatal(err) - } - - benchmarkSigning(b, jwt.SigningMethodRS384, parsedKey) -} - -func BenchmarkRS512Signing(b *testing.B) { - key, _ := ioutil.ReadFile("test/sample_key") - parsedKey, err := jwt.ParseRSAPrivateKeyFromPEM(key) - if err != nil { - b.Fatal(err) - } - - benchmarkSigning(b, jwt.SigningMethodRS512, parsedKey) -} diff --git a/vendor/github.com/dgrijalva/jwt-go/test/ec256-private.pem b/vendor/github.com/dgrijalva/jwt-go/test/ec256-private.pem deleted file mode 100644 index a6882b3e5..000000000 --- a/vendor/github.com/dgrijalva/jwt-go/test/ec256-private.pem +++ /dev/null @@ -1,5 +0,0 @@ ------BEGIN EC PRIVATE KEY----- -MHcCAQEEIAh5qA3rmqQQuu0vbKV/+zouz/y/Iy2pLpIcWUSyImSwoAoGCCqGSM49 -AwEHoUQDQgAEYD54V/vp+54P9DXarYqx4MPcm+HKRIQzNasYSoRQHQ/6S6Ps8tpM -cT+KvIIC8W/e9k0W7Cm72M1P9jU7SLf/vg== ------END EC PRIVATE KEY----- diff --git a/vendor/github.com/dgrijalva/jwt-go/test/ec256-public.pem b/vendor/github.com/dgrijalva/jwt-go/test/ec256-public.pem deleted file mode 100644 index 7191361e7..000000000 --- a/vendor/github.com/dgrijalva/jwt-go/test/ec256-public.pem +++ /dev/null @@ -1,4 +0,0 @@ ------BEGIN PUBLIC KEY----- -MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEYD54V/vp+54P9DXarYqx4MPcm+HK -RIQzNasYSoRQHQ/6S6Ps8tpMcT+KvIIC8W/e9k0W7Cm72M1P9jU7SLf/vg== ------END PUBLIC KEY----- diff --git a/vendor/github.com/dgrijalva/jwt-go/test/ec384-private.pem b/vendor/github.com/dgrijalva/jwt-go/test/ec384-private.pem deleted file mode 100644 index a86c823e5..000000000 --- a/vendor/github.com/dgrijalva/jwt-go/test/ec384-private.pem +++ /dev/null @@ -1,6 +0,0 @@ ------BEGIN EC PRIVATE KEY----- -MIGkAgEBBDCaCvMHKhcG/qT7xsNLYnDT7sE/D+TtWIol1ROdaK1a564vx5pHbsRy -SEKcIxISi1igBwYFK4EEACKhZANiAATYa7rJaU7feLMqrAx6adZFNQOpaUH/Uylb -ZLriOLON5YFVwtVUpO1FfEXZUIQpptRPtc5ixIPY658yhBSb6irfIJUSP9aYTflJ -GKk/mDkK4t8mWBzhiD5B6jg9cEGhGgA= ------END EC PRIVATE KEY----- diff --git a/vendor/github.com/dgrijalva/jwt-go/test/ec384-public.pem b/vendor/github.com/dgrijalva/jwt-go/test/ec384-public.pem deleted file mode 100644 index e80d00564..000000000 --- a/vendor/github.com/dgrijalva/jwt-go/test/ec384-public.pem +++ /dev/null @@ -1,5 +0,0 @@ ------BEGIN PUBLIC KEY----- -MHYwEAYHKoZIzj0CAQYFK4EEACIDYgAE2Gu6yWlO33izKqwMemnWRTUDqWlB/1Mp -W2S64jizjeWBVcLVVKTtRXxF2VCEKabUT7XOYsSD2OufMoQUm+oq3yCVEj/WmE35 -SRipP5g5CuLfJlgc4Yg+Qeo4PXBBoRoA ------END PUBLIC KEY----- diff --git a/vendor/github.com/dgrijalva/jwt-go/test/ec512-private.pem b/vendor/github.com/dgrijalva/jwt-go/test/ec512-private.pem deleted file mode 100644 index 213afaf13..000000000 --- a/vendor/github.com/dgrijalva/jwt-go/test/ec512-private.pem +++ /dev/null @@ -1,7 +0,0 @@ ------BEGIN EC PRIVATE KEY----- -MIHcAgEBBEIB0pE4uFaWRx7t03BsYlYvF1YvKaBGyvoakxnodm9ou0R9wC+sJAjH -QZZJikOg4SwNqgQ/hyrOuDK2oAVHhgVGcYmgBwYFK4EEACOhgYkDgYYABAAJXIuw -12MUzpHggia9POBFYXSxaOGKGbMjIyDI+6q7wi7LMw3HgbaOmgIqFG72o8JBQwYN -4IbXHf+f86CRY1AA2wHzbHvt6IhkCXTNxBEffa1yMUgu8n9cKKF2iLgyQKcKqW33 -8fGOw/n3Rm2Yd/EB56u2rnD29qS+nOM9eGS+gy39OQ== ------END EC PRIVATE KEY----- diff --git a/vendor/github.com/dgrijalva/jwt-go/test/ec512-public.pem b/vendor/github.com/dgrijalva/jwt-go/test/ec512-public.pem deleted file mode 100644 index 02ea02203..000000000 --- a/vendor/github.com/dgrijalva/jwt-go/test/ec512-public.pem +++ /dev/null @@ -1,6 +0,0 @@ ------BEGIN PUBLIC KEY----- -MIGbMBAGByqGSM49AgEGBSuBBAAjA4GGAAQACVyLsNdjFM6R4IImvTzgRWF0sWjh -ihmzIyMgyPuqu8IuyzMNx4G2jpoCKhRu9qPCQUMGDeCG1x3/n/OgkWNQANsB82x7 -7eiIZAl0zcQRH32tcjFILvJ/XCihdoi4MkCnCqlt9/HxjsP590ZtmHfxAeertq5w -9vakvpzjPXhkvoMt/Tk= ------END PUBLIC KEY----- diff --git a/vendor/github.com/dgrijalva/jwt-go/test/hmacTestKey b/vendor/github.com/dgrijalva/jwt-go/test/hmacTestKey deleted file mode 100644 index 435b8ddb3..000000000 --- a/vendor/github.com/dgrijalva/jwt-go/test/hmacTestKey +++ /dev/null @@ -1 +0,0 @@ -#5K+~ew{Z(T(P.ZGwb="=.!r.O͚gЀ \ No newline at end of file diff --git a/vendor/github.com/dgrijalva/jwt-go/test/sample_key b/vendor/github.com/dgrijalva/jwt-go/test/sample_key deleted file mode 100644 index abdbade31..000000000 --- a/vendor/github.com/dgrijalva/jwt-go/test/sample_key +++ /dev/null @@ -1,27 +0,0 @@ ------BEGIN RSA PRIVATE KEY----- -MIIEowIBAAKCAQEA4f5wg5l2hKsTeNem/V41fGnJm6gOdrj8ym3rFkEU/wT8RDtn -SgFEZOQpHEgQ7JL38xUfU0Y3g6aYw9QT0hJ7mCpz9Er5qLaMXJwZxzHzAahlfA0i -cqabvJOMvQtzD6uQv6wPEyZtDTWiQi9AXwBpHssPnpYGIn20ZZuNlX2BrClciHhC -PUIIZOQn/MmqTD31jSyjoQoV7MhhMTATKJx2XrHhR+1DcKJzQBSTAGnpYVaqpsAR -ap+nwRipr3nUTuxyGohBTSmjJ2usSeQXHI3bODIRe1AuTyHceAbewn8b462yEWKA -Rdpd9AjQW5SIVPfdsz5B6GlYQ5LdYKtznTuy7wIDAQABAoIBAQCwia1k7+2oZ2d3 -n6agCAbqIE1QXfCmh41ZqJHbOY3oRQG3X1wpcGH4Gk+O+zDVTV2JszdcOt7E5dAy -MaomETAhRxB7hlIOnEN7WKm+dGNrKRvV0wDU5ReFMRHg31/Lnu8c+5BvGjZX+ky9 -POIhFFYJqwCRlopGSUIxmVj5rSgtzk3iWOQXr+ah1bjEXvlxDOWkHN6YfpV5ThdE -KdBIPGEVqa63r9n2h+qazKrtiRqJqGnOrHzOECYbRFYhexsNFz7YT02xdfSHn7gM -IvabDDP/Qp0PjE1jdouiMaFHYnLBbgvlnZW9yuVf/rpXTUq/njxIXMmvmEyyvSDn -FcFikB8pAoGBAPF77hK4m3/rdGT7X8a/gwvZ2R121aBcdPwEaUhvj/36dx596zvY -mEOjrWfZhF083/nYWE2kVquj2wjs+otCLfifEEgXcVPTnEOPO9Zg3uNSL0nNQghj -FuD3iGLTUBCtM66oTe0jLSslHe8gLGEQqyMzHOzYxNqibxcOZIe8Qt0NAoGBAO+U -I5+XWjWEgDmvyC3TrOSf/KCGjtu0TSv30ipv27bDLMrpvPmD/5lpptTFwcxvVhCs -2b+chCjlghFSWFbBULBrfci2FtliClOVMYrlNBdUSJhf3aYSG2Doe6Bgt1n2CpNn -/iu37Y3NfemZBJA7hNl4dYe+f+uzM87cdQ214+jrAoGAXA0XxX8ll2+ToOLJsaNT -OvNB9h9Uc5qK5X5w+7G7O998BN2PC/MWp8H+2fVqpXgNENpNXttkRm1hk1dych86 -EunfdPuqsX+as44oCyJGFHVBnWpm33eWQw9YqANRI+pCJzP08I5WK3osnPiwshd+ -hR54yjgfYhBFNI7B95PmEQkCgYBzFSz7h1+s34Ycr8SvxsOBWxymG5zaCsUbPsL0 -4aCgLScCHb9J+E86aVbbVFdglYa5Id7DPTL61ixhl7WZjujspeXZGSbmq0Kcnckb -mDgqkLECiOJW2NHP/j0McAkDLL4tysF8TLDO8gvuvzNC+WQ6drO2ThrypLVZQ+ry -eBIPmwKBgEZxhqa0gVvHQG/7Od69KWj4eJP28kq13RhKay8JOoN0vPmspXJo1HY3 -CKuHRG+AP579dncdUnOMvfXOtkdM4vk0+hWASBQzM9xzVcztCa+koAugjVaLS9A+ -9uQoqEeVNTckxx0S2bYevRy7hGQmUJTyQm3j1zEUR5jpdbL83Fbq ------END RSA PRIVATE KEY----- diff --git a/vendor/github.com/dgrijalva/jwt-go/test/sample_key.pub b/vendor/github.com/dgrijalva/jwt-go/test/sample_key.pub deleted file mode 100644 index 03dc982ac..000000000 --- a/vendor/github.com/dgrijalva/jwt-go/test/sample_key.pub +++ /dev/null @@ -1,9 +0,0 @@ ------BEGIN PUBLIC KEY----- -MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA4f5wg5l2hKsTeNem/V41 -fGnJm6gOdrj8ym3rFkEU/wT8RDtnSgFEZOQpHEgQ7JL38xUfU0Y3g6aYw9QT0hJ7 -mCpz9Er5qLaMXJwZxzHzAahlfA0icqabvJOMvQtzD6uQv6wPEyZtDTWiQi9AXwBp -HssPnpYGIn20ZZuNlX2BrClciHhCPUIIZOQn/MmqTD31jSyjoQoV7MhhMTATKJx2 -XrHhR+1DcKJzQBSTAGnpYVaqpsARap+nwRipr3nUTuxyGohBTSmjJ2usSeQXHI3b -ODIRe1AuTyHceAbewn8b462yEWKARdpd9AjQW5SIVPfdsz5B6GlYQ5LdYKtznTuy -7wIDAQAB ------END PUBLIC KEY----- diff --git a/vendor/github.com/docker/docker/LICENSE b/vendor/github.com/docker/docker/LICENSE new file mode 100644 index 000000000..c7a3f0cfd --- /dev/null +++ b/vendor/github.com/docker/docker/LICENSE @@ -0,0 +1,191 @@ + + Apache License + Version 2.0, January 2004 + https://www.apache.org/licenses/ + + TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION + + 1. Definitions. + + "License" shall mean the terms and conditions for use, reproduction, + and distribution as defined by Sections 1 through 9 of this document. + + "Licensor" shall mean the copyright owner or entity authorized by + the copyright owner that is granting the License. + + "Legal Entity" shall mean the union of the acting entity and all + other entities that control, are controlled by, or are under common + control with that entity. For the purposes of this definition, + "control" means (i) the power, direct or indirect, to cause the + direction or management of such entity, whether by contract or + otherwise, or (ii) ownership of fifty percent (50%) or more of the + outstanding shares, or (iii) beneficial ownership of such entity. + + "You" (or "Your") shall mean an individual or Legal Entity + exercising permissions granted by this License. + + "Source" form shall mean the preferred form for making modifications, + including but not limited to software source code, documentation + source, and configuration files. + + "Object" form shall mean any form resulting from mechanical + transformation or translation of a Source form, including but + not limited to compiled object code, generated documentation, + and conversions to other media types. + + "Work" shall mean the work of authorship, whether in Source or + Object form, made available under the License, as indicated by a + copyright notice that is included in or attached to the work + (an example is provided in the Appendix below). + + "Derivative Works" shall mean any work, whether in Source or Object + form, that is based on (or derived from) the Work and for which the + editorial revisions, annotations, elaborations, or other modifications + represent, as a whole, an original work of authorship. For the purposes + of this License, Derivative Works shall not include works that remain + separable from, or merely link (or bind by name) to the interfaces of, + the Work and Derivative Works thereof. + + "Contribution" shall mean any work of authorship, including + the original version of the Work and any modifications or additions + to that Work or Derivative Works thereof, that is intentionally + submitted to Licensor for inclusion in the Work by the copyright owner + or by an individual or Legal Entity authorized to submit on behalf of + the copyright owner. For the purposes of this definition, "submitted" + means any form of electronic, verbal, or written communication sent + to the Licensor or its representatives, including but not limited to + communication on electronic mailing lists, source code control systems, + and issue tracking systems that are managed by, or on behalf of, the + Licensor for the purpose of discussing and improving the Work, but + excluding communication that is conspicuously marked or otherwise + designated in writing by the copyright owner as "Not a Contribution." + + "Contributor" shall mean Licensor and any individual or Legal Entity + on behalf of whom a Contribution has been received by Licensor and + subsequently incorporated within the Work. + + 2. Grant of Copyright License. Subject to the terms and conditions of + this License, each Contributor hereby grants to You a perpetual, + worldwide, non-exclusive, no-charge, royalty-free, irrevocable + copyright license to reproduce, prepare Derivative Works of, + publicly display, publicly perform, sublicense, and distribute the + Work and such Derivative Works in Source or Object form. + + 3. Grant of Patent License. Subject to the terms and conditions of + this License, each Contributor hereby grants to You a perpetual, + worldwide, non-exclusive, no-charge, royalty-free, irrevocable + (except as stated in this section) patent license to make, have made, + use, offer to sell, sell, import, and otherwise transfer the Work, + where such license applies only to those patent claims licensable + by such Contributor that are necessarily infringed by their + Contribution(s) alone or by combination of their Contribution(s) + with the Work to which such Contribution(s) was submitted. If You + institute patent litigation against any entity (including a + cross-claim or counterclaim in a lawsuit) alleging that the Work + or a Contribution incorporated within the Work constitutes direct + or contributory patent infringement, then any patent licenses + granted to You under this License for that Work shall terminate + as of the date such litigation is filed. + + 4. Redistribution. You may reproduce and distribute copies of the + Work or Derivative Works thereof in any medium, with or without + modifications, and in Source or Object form, provided that You + meet the following conditions: + + (a) You must give any other recipients of the Work or + Derivative Works a copy of this License; and + + (b) You must cause any modified files to carry prominent notices + stating that You changed the files; and + + (c) You must retain, in the Source form of any Derivative Works + that You distribute, all copyright, patent, trademark, and + attribution notices from the Source form of the Work, + excluding those notices that do not pertain to any part of + the Derivative Works; and + + (d) If the Work includes a "NOTICE" text file as part of its + distribution, then any Derivative Works that You distribute must + include a readable copy of the attribution notices contained + within such NOTICE file, excluding those notices that do not + pertain to any part of the Derivative Works, in at least one + of the following places: within a NOTICE text file distributed + as part of the Derivative Works; within the Source form or + documentation, if provided along with the Derivative Works; or, + within a display generated by the Derivative Works, if and + wherever such third-party notices normally appear. The contents + of the NOTICE file are for informational purposes only and + do not modify the License. You may add Your own attribution + notices within Derivative Works that You distribute, alongside + or as an addendum to the NOTICE text from the Work, provided + that such additional attribution notices cannot be construed + as modifying the License. + + You may add Your own copyright statement to Your modifications and + may provide additional or different license terms and conditions + for use, reproduction, or distribution of Your modifications, or + for any such Derivative Works as a whole, provided Your use, + reproduction, and distribution of the Work otherwise complies with + the conditions stated in this License. + + 5. Submission of Contributions. Unless You explicitly state otherwise, + any Contribution intentionally submitted for inclusion in the Work + by You to the Licensor shall be under the terms and conditions of + this License, without any additional terms or conditions. + Notwithstanding the above, nothing herein shall supersede or modify + the terms of any separate license agreement you may have executed + with Licensor regarding such Contributions. + + 6. Trademarks. This License does not grant permission to use the trade + names, trademarks, service marks, or product names of the Licensor, + except as required for reasonable and customary use in describing the + origin of the Work and reproducing the content of the NOTICE file. + + 7. Disclaimer of Warranty. Unless required by applicable law or + agreed to in writing, Licensor provides the Work (and each + Contributor provides its Contributions) on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or + implied, including, without limitation, any warranties or conditions + of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A + PARTICULAR PURPOSE. You are solely responsible for determining the + appropriateness of using or redistributing the Work and assume any + risks associated with Your exercise of permissions under this License. + + 8. Limitation of Liability. In no event and under no legal theory, + whether in tort (including negligence), contract, or otherwise, + unless required by applicable law (such as deliberate and grossly + negligent acts) or agreed to in writing, shall any Contributor be + liable to You for damages, including any direct, indirect, special, + incidental, or consequential damages of any character arising as a + result of this License or out of the use or inability to use the + Work (including but not limited to damages for loss of goodwill, + work stoppage, computer failure or malfunction, or any and all + other commercial damages or losses), even if such Contributor + has been advised of the possibility of such damages. + + 9. Accepting Warranty or Additional Liability. While redistributing + the Work or Derivative Works thereof, You may choose to offer, + and charge a fee for, acceptance of support, warranty, indemnity, + or other liability obligations and/or rights consistent with this + License. However, in accepting such obligations, You may act only + on Your own behalf and on Your sole responsibility, not on behalf + of any other Contributor, and only if You agree to indemnify, + defend, and hold each Contributor harmless for any liability + incurred by, or claims asserted against, such Contributor by reason + of your accepting any such warranty or additional liability. + + END OF TERMS AND CONDITIONS + + Copyright 2013-2015 Docker, Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. diff --git a/vendor/github.com/docker/docker/NOTICE b/vendor/github.com/docker/docker/NOTICE new file mode 100644 index 000000000..6e6f469ab --- /dev/null +++ b/vendor/github.com/docker/docker/NOTICE @@ -0,0 +1,19 @@ +Docker +Copyright 2012-2015 Docker, Inc. + +This product includes software developed at Docker, Inc. (https://www.docker.com). + +This product contains software (https://github.com/kr/pty) developed +by Keith Rarick, licensed under the MIT License. + +The following is courtesy of our legal counsel: + + +Use and transfer of Docker may be subject to certain restrictions by the +United States and other governments. +It is your responsibility to ensure that your use and/or transfer does not +violate applicable laws. + +For more information, please see https://www.bis.doc.gov + +See also https://www.apache.org/dev/crypto.html and/or seek legal counsel. diff --git a/vendor/github.com/docker/docker/pkg/stdcopy/stdcopy_test.go b/vendor/github.com/docker/docker/pkg/stdcopy/stdcopy_test.go deleted file mode 100644 index a9fd73a49..000000000 --- a/vendor/github.com/docker/docker/pkg/stdcopy/stdcopy_test.go +++ /dev/null @@ -1,85 +0,0 @@ -package stdcopy - -import ( - "bytes" - "io/ioutil" - "strings" - "testing" -) - -func TestNewStdWriter(t *testing.T) { - writer := NewStdWriter(ioutil.Discard, Stdout) - if writer == nil { - t.Fatalf("NewStdWriter with an invalid StdType should not return nil.") - } -} - -func TestWriteWithUnitializedStdWriter(t *testing.T) { - writer := StdWriter{ - Writer: nil, - prefix: Stdout, - sizeBuf: make([]byte, 4), - } - n, err := writer.Write([]byte("Something here")) - if n != 0 || err == nil { - t.Fatalf("Should fail when given an uncomplete or uninitialized StdWriter") - } -} - -func TestWriteWithNilBytes(t *testing.T) { - writer := NewStdWriter(ioutil.Discard, Stdout) - n, err := writer.Write(nil) - if err != nil { - t.Fatalf("Shouldn't have fail when given no data") - } - if n > 0 { - t.Fatalf("Write should have written 0 byte, but has written %d", n) - } -} - -func TestWrite(t *testing.T) { - writer := NewStdWriter(ioutil.Discard, Stdout) - data := []byte("Test StdWrite.Write") - n, err := writer.Write(data) - if err != nil { - t.Fatalf("Error while writing with StdWrite") - } - if n != len(data) { - t.Fatalf("Write should have writen %d byte but wrote %d.", len(data), n) - } -} - -func TestStdCopyWithInvalidInputHeader(t *testing.T) { - dstOut := NewStdWriter(ioutil.Discard, Stdout) - dstErr := NewStdWriter(ioutil.Discard, Stderr) - src := strings.NewReader("Invalid input") - _, err := StdCopy(dstOut, dstErr, src) - if err == nil { - t.Fatal("StdCopy with invalid input header should fail.") - } -} - -func TestStdCopyWithCorruptedPrefix(t *testing.T) { - data := []byte{0x01, 0x02, 0x03} - src := bytes.NewReader(data) - written, err := StdCopy(nil, nil, src) - if err != nil { - t.Fatalf("StdCopy should not return an error with corrupted prefix.") - } - if written != 0 { - t.Fatalf("StdCopy should have written 0, but has written %d", written) - } -} - -func BenchmarkWrite(b *testing.B) { - w := NewStdWriter(ioutil.Discard, Stdout) - data := []byte("Test line for testing stdwriter performance\n") - data = bytes.Repeat(data, 100) - b.SetBytes(int64(len(data))) - b.ResetTimer() - for i := 0; i < b.N; i++ { - if _, err := w.Write(data); err != nil { - b.Fatal(err) - } - } -} diff --git a/vendor/github.com/docker/docker/pkg/units/duration_test.go b/vendor/github.com/docker/docker/pkg/units/duration_test.go deleted file mode 100644 index fcfb6b7bb..000000000 --- a/vendor/github.com/docker/docker/pkg/units/duration_test.go +++ /dev/null @@ -1,46 +0,0 @@ -package units - -import ( - "testing" - "time" -) - -func TestHumanDuration(t *testing.T) { - // Useful duration abstractions - day := 24 * time.Hour - week := 7 * day - month := 30 * day - year := 365 * day - - assertEquals(t, "Less than a second", HumanDuration(450*time.Millisecond)) - assertEquals(t, "47 seconds", HumanDuration(47*time.Second)) - assertEquals(t, "About a minute", HumanDuration(1*time.Minute)) - assertEquals(t, "3 minutes", HumanDuration(3*time.Minute)) - assertEquals(t, "35 minutes", HumanDuration(35*time.Minute)) - assertEquals(t, "35 minutes", HumanDuration(35*time.Minute+40*time.Second)) - assertEquals(t, "About an hour", HumanDuration(1*time.Hour)) - assertEquals(t, "About an hour", HumanDuration(1*time.Hour+45*time.Minute)) - assertEquals(t, "3 hours", HumanDuration(3*time.Hour)) - assertEquals(t, "3 hours", HumanDuration(3*time.Hour+59*time.Minute)) - assertEquals(t, "4 hours", HumanDuration(3*time.Hour+60*time.Minute)) - assertEquals(t, "24 hours", HumanDuration(24*time.Hour)) - assertEquals(t, "36 hours", HumanDuration(1*day+12*time.Hour)) - assertEquals(t, "2 days", HumanDuration(2*day)) - assertEquals(t, "7 days", HumanDuration(7*day)) - assertEquals(t, "13 days", HumanDuration(13*day+5*time.Hour)) - assertEquals(t, "2 weeks", HumanDuration(2*week)) - assertEquals(t, "2 weeks", HumanDuration(2*week+4*day)) - assertEquals(t, "3 weeks", HumanDuration(3*week)) - assertEquals(t, "4 weeks", HumanDuration(4*week)) - assertEquals(t, "4 weeks", HumanDuration(4*week+3*day)) - assertEquals(t, "4 weeks", HumanDuration(1*month)) - assertEquals(t, "6 weeks", HumanDuration(1*month+2*week)) - assertEquals(t, "8 weeks", HumanDuration(2*month)) - assertEquals(t, "3 months", HumanDuration(3*month+1*week)) - assertEquals(t, "5 months", HumanDuration(5*month+2*week)) - assertEquals(t, "13 months", HumanDuration(13*month)) - assertEquals(t, "23 months", HumanDuration(23*month)) - assertEquals(t, "24 months", HumanDuration(24*month)) - assertEquals(t, "2 years", HumanDuration(24*month+2*week)) - assertEquals(t, "3 years", HumanDuration(3*year+2*month)) -} diff --git a/vendor/github.com/docker/docker/pkg/units/size_test.go b/vendor/github.com/docker/docker/pkg/units/size_test.go deleted file mode 100644 index 67c3b81e6..000000000 --- a/vendor/github.com/docker/docker/pkg/units/size_test.go +++ /dev/null @@ -1,108 +0,0 @@ -package units - -import ( - "reflect" - "runtime" - "strings" - "testing" -) - -func TestBytesSize(t *testing.T) { - assertEquals(t, "1 KiB", BytesSize(1024)) - assertEquals(t, "1 MiB", BytesSize(1024*1024)) - assertEquals(t, "1 MiB", BytesSize(1048576)) - assertEquals(t, "2 MiB", BytesSize(2*MiB)) - assertEquals(t, "3.42 GiB", BytesSize(3.42*GiB)) - assertEquals(t, "5.372 TiB", BytesSize(5.372*TiB)) - assertEquals(t, "2.22 PiB", BytesSize(2.22*PiB)) -} - -func TestHumanSize(t *testing.T) { - assertEquals(t, "1 kB", HumanSize(1000)) - assertEquals(t, "1.024 kB", HumanSize(1024)) - assertEquals(t, "1 MB", HumanSize(1000000)) - assertEquals(t, "1.049 MB", HumanSize(1048576)) - assertEquals(t, "2 MB", HumanSize(2*MB)) - assertEquals(t, "3.42 GB", HumanSize(float64(3.42*GB))) - assertEquals(t, "5.372 TB", HumanSize(float64(5.372*TB))) - assertEquals(t, "2.22 PB", HumanSize(float64(2.22*PB))) -} - -func TestFromHumanSize(t *testing.T) { - assertSuccessEquals(t, 32, FromHumanSize, "32") - assertSuccessEquals(t, 32, FromHumanSize, "32b") - assertSuccessEquals(t, 32, FromHumanSize, "32B") - assertSuccessEquals(t, 32*KB, FromHumanSize, "32k") - assertSuccessEquals(t, 32*KB, FromHumanSize, "32K") - assertSuccessEquals(t, 32*KB, FromHumanSize, "32kb") - assertSuccessEquals(t, 32*KB, FromHumanSize, "32Kb") - assertSuccessEquals(t, 32*MB, FromHumanSize, "32Mb") - assertSuccessEquals(t, 32*GB, FromHumanSize, "32Gb") - assertSuccessEquals(t, 32*TB, FromHumanSize, "32Tb") - assertSuccessEquals(t, 32*PB, FromHumanSize, "32Pb") - - assertError(t, FromHumanSize, "") - assertError(t, FromHumanSize, "hello") - assertError(t, FromHumanSize, "-32") - assertError(t, FromHumanSize, "32.3") - assertError(t, FromHumanSize, " 32 ") - assertError(t, FromHumanSize, "32.3Kb") - assertError(t, FromHumanSize, "32 mb") - assertError(t, FromHumanSize, "32m b") - assertError(t, FromHumanSize, "32bm") -} - -func TestRAMInBytes(t *testing.T) { - assertSuccessEquals(t, 32, RAMInBytes, "32") - assertSuccessEquals(t, 32, RAMInBytes, "32b") - assertSuccessEquals(t, 32, RAMInBytes, "32B") - assertSuccessEquals(t, 32*KiB, RAMInBytes, "32k") - assertSuccessEquals(t, 32*KiB, RAMInBytes, "32K") - assertSuccessEquals(t, 32*KiB, RAMInBytes, "32kb") - assertSuccessEquals(t, 32*KiB, RAMInBytes, "32Kb") - assertSuccessEquals(t, 32*MiB, RAMInBytes, "32Mb") - assertSuccessEquals(t, 32*GiB, RAMInBytes, "32Gb") - assertSuccessEquals(t, 32*TiB, RAMInBytes, "32Tb") - assertSuccessEquals(t, 32*PiB, RAMInBytes, "32Pb") - assertSuccessEquals(t, 32*PiB, RAMInBytes, "32PB") - assertSuccessEquals(t, 32*PiB, RAMInBytes, "32P") - - assertError(t, RAMInBytes, "") - assertError(t, RAMInBytes, "hello") - assertError(t, RAMInBytes, "-32") - assertError(t, RAMInBytes, "32.3") - assertError(t, RAMInBytes, " 32 ") - assertError(t, RAMInBytes, "32.3Kb") - assertError(t, RAMInBytes, "32 mb") - assertError(t, RAMInBytes, "32m b") - assertError(t, RAMInBytes, "32bm") -} - -func assertEquals(t *testing.T, expected, actual interface{}) { - if expected != actual { - t.Errorf("Expected '%v' but got '%v'", expected, actual) - } -} - -// func that maps to the parse function signatures as testing abstraction -type parseFn func(string) (int64, error) - -// Define 'String()' for pretty-print -func (fn parseFn) String() string { - fnName := runtime.FuncForPC(reflect.ValueOf(fn).Pointer()).Name() - return fnName[strings.LastIndex(fnName, ".")+1:] -} - -func assertSuccessEquals(t *testing.T, expected int64, fn parseFn, arg string) { - res, err := fn(arg) - if err != nil || res != expected { - t.Errorf("%s(\"%s\") -> expected '%d' but got '%d' with error '%v'", fn, arg, expected, res, err) - } -} - -func assertError(t *testing.T, fn parseFn, arg string) { - res, err := fn(arg) - if err == nil && res != -1 { - t.Errorf("%s(\"%s\") -> expected error but got '%d'", fn, arg, res) - } -} diff --git a/vendor/github.com/docker/go-units/CONTRIBUTING.md b/vendor/github.com/docker/go-units/CONTRIBUTING.md new file mode 100644 index 000000000..9ea86d784 --- /dev/null +++ b/vendor/github.com/docker/go-units/CONTRIBUTING.md @@ -0,0 +1,67 @@ +# Contributing to go-units + +Want to hack on go-units? Awesome! Here are instructions to get you started. + +go-units is a part of the [Docker](https://www.docker.com) project, and follows +the same rules and principles. If you're already familiar with the way +Docker does things, you'll feel right at home. + +Otherwise, go read Docker's +[contributions guidelines](https://github.com/docker/docker/blob/master/CONTRIBUTING.md), +[issue triaging](https://github.com/docker/docker/blob/master/project/ISSUE-TRIAGE.md), +[review process](https://github.com/docker/docker/blob/master/project/REVIEWING.md) and +[branches and tags](https://github.com/docker/docker/blob/master/project/BRANCHES-AND-TAGS.md). + +### Sign your work + +The sign-off is a simple line at the end of the explanation for the patch. Your +signature certifies that you wrote the patch or otherwise have the right to pass +it on as an open-source patch. The rules are pretty simple: if you can certify +the below (from [developercertificate.org](http://developercertificate.org/)): + +``` +Developer Certificate of Origin +Version 1.1 + +Copyright (C) 2004, 2006 The Linux Foundation and its contributors. +660 York Street, Suite 102, +San Francisco, CA 94110 USA + +Everyone is permitted to copy and distribute verbatim copies of this +license document, but changing it is not allowed. + +Developer's Certificate of Origin 1.1 + +By making a contribution to this project, I certify that: + +(a) The contribution was created in whole or in part by me and I + have the right to submit it under the open source license + indicated in the file; or + +(b) The contribution is based upon previous work that, to the best + of my knowledge, is covered under an appropriate open source + license and I have the right under that license to submit that + work with modifications, whether created in whole or in part + by me, under the same open source license (unless I am + permitted to submit under a different license), as indicated + in the file; or + +(c) The contribution was provided directly to me by some other + person who certified (a), (b) or (c) and I have not modified + it. + +(d) I understand and agree that this project and the contribution + are public and that a record of the contribution (including all + personal information I submit with it, including my sign-off) is + maintained indefinitely and may be redistributed consistent with + this project or the open source license(s) involved. +``` + +Then you just add a line to every git commit message: + + Signed-off-by: Joe Smith + +Use your real name (sorry, no pseudonyms or anonymous contributions.) + +If you set your `user.name` and `user.email` git configs, you can sign your +commit automatically with `git commit -s`. diff --git a/vendor/github.com/docker/go-units/LICENSE.code b/vendor/github.com/docker/go-units/LICENSE.code new file mode 100644 index 000000000..b55b37bc3 --- /dev/null +++ b/vendor/github.com/docker/go-units/LICENSE.code @@ -0,0 +1,191 @@ + + Apache License + Version 2.0, January 2004 + https://www.apache.org/licenses/ + + TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION + + 1. Definitions. + + "License" shall mean the terms and conditions for use, reproduction, + and distribution as defined by Sections 1 through 9 of this document. + + "Licensor" shall mean the copyright owner or entity authorized by + the copyright owner that is granting the License. + + "Legal Entity" shall mean the union of the acting entity and all + other entities that control, are controlled by, or are under common + control with that entity. For the purposes of this definition, + "control" means (i) the power, direct or indirect, to cause the + direction or management of such entity, whether by contract or + otherwise, or (ii) ownership of fifty percent (50%) or more of the + outstanding shares, or (iii) beneficial ownership of such entity. + + "You" (or "Your") shall mean an individual or Legal Entity + exercising permissions granted by this License. + + "Source" form shall mean the preferred form for making modifications, + including but not limited to software source code, documentation + source, and configuration files. + + "Object" form shall mean any form resulting from mechanical + transformation or translation of a Source form, including but + not limited to compiled object code, generated documentation, + and conversions to other media types. + + "Work" shall mean the work of authorship, whether in Source or + Object form, made available under the License, as indicated by a + copyright notice that is included in or attached to the work + (an example is provided in the Appendix below). + + "Derivative Works" shall mean any work, whether in Source or Object + form, that is based on (or derived from) the Work and for which the + editorial revisions, annotations, elaborations, or other modifications + represent, as a whole, an original work of authorship. For the purposes + of this License, Derivative Works shall not include works that remain + separable from, or merely link (or bind by name) to the interfaces of, + the Work and Derivative Works thereof. + + "Contribution" shall mean any work of authorship, including + the original version of the Work and any modifications or additions + to that Work or Derivative Works thereof, that is intentionally + submitted to Licensor for inclusion in the Work by the copyright owner + or by an individual or Legal Entity authorized to submit on behalf of + the copyright owner. For the purposes of this definition, "submitted" + means any form of electronic, verbal, or written communication sent + to the Licensor or its representatives, including but not limited to + communication on electronic mailing lists, source code control systems, + and issue tracking systems that are managed by, or on behalf of, the + Licensor for the purpose of discussing and improving the Work, but + excluding communication that is conspicuously marked or otherwise + designated in writing by the copyright owner as "Not a Contribution." + + "Contributor" shall mean Licensor and any individual or Legal Entity + on behalf of whom a Contribution has been received by Licensor and + subsequently incorporated within the Work. + + 2. Grant of Copyright License. Subject to the terms and conditions of + this License, each Contributor hereby grants to You a perpetual, + worldwide, non-exclusive, no-charge, royalty-free, irrevocable + copyright license to reproduce, prepare Derivative Works of, + publicly display, publicly perform, sublicense, and distribute the + Work and such Derivative Works in Source or Object form. + + 3. Grant of Patent License. Subject to the terms and conditions of + this License, each Contributor hereby grants to You a perpetual, + worldwide, non-exclusive, no-charge, royalty-free, irrevocable + (except as stated in this section) patent license to make, have made, + use, offer to sell, sell, import, and otherwise transfer the Work, + where such license applies only to those patent claims licensable + by such Contributor that are necessarily infringed by their + Contribution(s) alone or by combination of their Contribution(s) + with the Work to which such Contribution(s) was submitted. If You + institute patent litigation against any entity (including a + cross-claim or counterclaim in a lawsuit) alleging that the Work + or a Contribution incorporated within the Work constitutes direct + or contributory patent infringement, then any patent licenses + granted to You under this License for that Work shall terminate + as of the date such litigation is filed. + + 4. Redistribution. You may reproduce and distribute copies of the + Work or Derivative Works thereof in any medium, with or without + modifications, and in Source or Object form, provided that You + meet the following conditions: + + (a) You must give any other recipients of the Work or + Derivative Works a copy of this License; and + + (b) You must cause any modified files to carry prominent notices + stating that You changed the files; and + + (c) You must retain, in the Source form of any Derivative Works + that You distribute, all copyright, patent, trademark, and + attribution notices from the Source form of the Work, + excluding those notices that do not pertain to any part of + the Derivative Works; and + + (d) If the Work includes a "NOTICE" text file as part of its + distribution, then any Derivative Works that You distribute must + include a readable copy of the attribution notices contained + within such NOTICE file, excluding those notices that do not + pertain to any part of the Derivative Works, in at least one + of the following places: within a NOTICE text file distributed + as part of the Derivative Works; within the Source form or + documentation, if provided along with the Derivative Works; or, + within a display generated by the Derivative Works, if and + wherever such third-party notices normally appear. The contents + of the NOTICE file are for informational purposes only and + do not modify the License. You may add Your own attribution + notices within Derivative Works that You distribute, alongside + or as an addendum to the NOTICE text from the Work, provided + that such additional attribution notices cannot be construed + as modifying the License. + + You may add Your own copyright statement to Your modifications and + may provide additional or different license terms and conditions + for use, reproduction, or distribution of Your modifications, or + for any such Derivative Works as a whole, provided Your use, + reproduction, and distribution of the Work otherwise complies with + the conditions stated in this License. + + 5. Submission of Contributions. Unless You explicitly state otherwise, + any Contribution intentionally submitted for inclusion in the Work + by You to the Licensor shall be under the terms and conditions of + this License, without any additional terms or conditions. + Notwithstanding the above, nothing herein shall supersede or modify + the terms of any separate license agreement you may have executed + with Licensor regarding such Contributions. + + 6. Trademarks. This License does not grant permission to use the trade + names, trademarks, service marks, or product names of the Licensor, + except as required for reasonable and customary use in describing the + origin of the Work and reproducing the content of the NOTICE file. + + 7. Disclaimer of Warranty. Unless required by applicable law or + agreed to in writing, Licensor provides the Work (and each + Contributor provides its Contributions) on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or + implied, including, without limitation, any warranties or conditions + of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A + PARTICULAR PURPOSE. You are solely responsible for determining the + appropriateness of using or redistributing the Work and assume any + risks associated with Your exercise of permissions under this License. + + 8. Limitation of Liability. In no event and under no legal theory, + whether in tort (including negligence), contract, or otherwise, + unless required by applicable law (such as deliberate and grossly + negligent acts) or agreed to in writing, shall any Contributor be + liable to You for damages, including any direct, indirect, special, + incidental, or consequential damages of any character arising as a + result of this License or out of the use or inability to use the + Work (including but not limited to damages for loss of goodwill, + work stoppage, computer failure or malfunction, or any and all + other commercial damages or losses), even if such Contributor + has been advised of the possibility of such damages. + + 9. Accepting Warranty or Additional Liability. While redistributing + the Work or Derivative Works thereof, You may choose to offer, + and charge a fee for, acceptance of support, warranty, indemnity, + or other liability obligations and/or rights consistent with this + License. However, in accepting such obligations, You may act only + on Your own behalf and on Your sole responsibility, not on behalf + of any other Contributor, and only if You agree to indemnify, + defend, and hold each Contributor harmless for any liability + incurred by, or claims asserted against, such Contributor by reason + of your accepting any such warranty or additional liability. + + END OF TERMS AND CONDITIONS + + Copyright 2015 Docker, Inc. + + Licensed under the Apache License, Version 2.0 (the "License"); + you may not use this file except in compliance with the License. + You may obtain a copy of the License at + + https://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. diff --git a/vendor/github.com/docker/go-units/LICENSE.docs b/vendor/github.com/docker/go-units/LICENSE.docs new file mode 100644 index 000000000..e26cd4fc8 --- /dev/null +++ b/vendor/github.com/docker/go-units/LICENSE.docs @@ -0,0 +1,425 @@ +Attribution-ShareAlike 4.0 International + +======================================================================= + +Creative Commons Corporation ("Creative Commons") is not a law firm and +does not provide legal services or legal advice. Distribution of +Creative Commons public licenses does not create a lawyer-client or +other relationship. Creative Commons makes its licenses and related +information available on an "as-is" basis. Creative Commons gives no +warranties regarding its licenses, any material licensed under their +terms and conditions, or any related information. Creative Commons +disclaims all liability for damages resulting from their use to the +fullest extent possible. + +Using Creative Commons Public Licenses + +Creative Commons public licenses provide a standard set of terms and +conditions that creators and other rights holders may use to share +original works of authorship and other material subject to copyright +and certain other rights specified in the public license below. The +following considerations are for informational purposes only, are not +exhaustive, and do not form part of our licenses. + + Considerations for licensors: Our public licenses are + intended for use by those authorized to give the public + permission to use material in ways otherwise restricted by + copyright and certain other rights. Our licenses are + irrevocable. Licensors should read and understand the terms + and conditions of the license they choose before applying it. + Licensors should also secure all rights necessary before + applying our licenses so that the public can reuse the + material as expected. Licensors should clearly mark any + material not subject to the license. This includes other CC- + licensed material, or material used under an exception or + limitation to copyright. More considerations for licensors: + wiki.creativecommons.org/Considerations_for_licensors + + Considerations for the public: By using one of our public + licenses, a licensor grants the public permission to use the + licensed material under specified terms and conditions. If + the licensor's permission is not necessary for any reason--for + example, because of any applicable exception or limitation to + copyright--then that use is not regulated by the license. Our + licenses grant only permissions under copyright and certain + other rights that a licensor has authority to grant. Use of + the licensed material may still be restricted for other + reasons, including because others have copyright or other + rights in the material. A licensor may make special requests, + such as asking that all changes be marked or described. + Although not required by our licenses, you are encouraged to + respect those requests where reasonable. More_considerations + for the public: + wiki.creativecommons.org/Considerations_for_licensees + +======================================================================= + +Creative Commons Attribution-ShareAlike 4.0 International Public +License + +By exercising the Licensed Rights (defined below), You accept and agree +to be bound by the terms and conditions of this Creative Commons +Attribution-ShareAlike 4.0 International Public License ("Public +License"). To the extent this Public License may be interpreted as a +contract, You are granted the Licensed Rights in consideration of Your +acceptance of these terms and conditions, and the Licensor grants You +such rights in consideration of benefits the Licensor receives from +making the Licensed Material available under these terms and +conditions. + + +Section 1 -- Definitions. + + a. Adapted Material means material subject to Copyright and Similar + Rights that is derived from or based upon the Licensed Material + and in which the Licensed Material is translated, altered, + arranged, transformed, or otherwise modified in a manner requiring + permission under the Copyright and Similar Rights held by the + Licensor. For purposes of this Public License, where the Licensed + Material is a musical work, performance, or sound recording, + Adapted Material is always produced where the Licensed Material is + synched in timed relation with a moving image. + + b. Adapter's License means the license You apply to Your Copyright + and Similar Rights in Your contributions to Adapted Material in + accordance with the terms and conditions of this Public License. + + c. BY-SA Compatible License means a license listed at + creativecommons.org/compatiblelicenses, approved by Creative + Commons as essentially the equivalent of this Public License. + + d. Copyright and Similar Rights means copyright and/or similar rights + closely related to copyright including, without limitation, + performance, broadcast, sound recording, and Sui Generis Database + Rights, without regard to how the rights are labeled or + categorized. For purposes of this Public License, the rights + specified in Section 2(b)(1)-(2) are not Copyright and Similar + Rights. + + e. Effective Technological Measures means those measures that, in the + absence of proper authority, may not be circumvented under laws + fulfilling obligations under Article 11 of the WIPO Copyright + Treaty adopted on December 20, 1996, and/or similar international + agreements. + + f. Exceptions and Limitations means fair use, fair dealing, and/or + any other exception or limitation to Copyright and Similar Rights + that applies to Your use of the Licensed Material. + + g. License Elements means the license attributes listed in the name + of a Creative Commons Public License. The License Elements of this + Public License are Attribution and ShareAlike. + + h. Licensed Material means the artistic or literary work, database, + or other material to which the Licensor applied this Public + License. + + i. Licensed Rights means the rights granted to You subject to the + terms and conditions of this Public License, which are limited to + all Copyright and Similar Rights that apply to Your use of the + Licensed Material and that the Licensor has authority to license. + + j. Licensor means the individual(s) or entity(ies) granting rights + under this Public License. + + k. Share means to provide material to the public by any means or + process that requires permission under the Licensed Rights, such + as reproduction, public display, public performance, distribution, + dissemination, communication, or importation, and to make material + available to the public including in ways that members of the + public may access the material from a place and at a time + individually chosen by them. + + l. Sui Generis Database Rights means rights other than copyright + resulting from Directive 96/9/EC of the European Parliament and of + the Council of 11 March 1996 on the legal protection of databases, + as amended and/or succeeded, as well as other essentially + equivalent rights anywhere in the world. + + m. You means the individual or entity exercising the Licensed Rights + under this Public License. Your has a corresponding meaning. + + +Section 2 -- Scope. + + a. License grant. + + 1. Subject to the terms and conditions of this Public License, + the Licensor hereby grants You a worldwide, royalty-free, + non-sublicensable, non-exclusive, irrevocable license to + exercise the Licensed Rights in the Licensed Material to: + + a. reproduce and Share the Licensed Material, in whole or + in part; and + + b. produce, reproduce, and Share Adapted Material. + + 2. Exceptions and Limitations. For the avoidance of doubt, where + Exceptions and Limitations apply to Your use, this Public + License does not apply, and You do not need to comply with + its terms and conditions. + + 3. Term. The term of this Public License is specified in Section + 6(a). + + 4. Media and formats; technical modifications allowed. The + Licensor authorizes You to exercise the Licensed Rights in + all media and formats whether now known or hereafter created, + and to make technical modifications necessary to do so. The + Licensor waives and/or agrees not to assert any right or + authority to forbid You from making technical modifications + necessary to exercise the Licensed Rights, including + technical modifications necessary to circumvent Effective + Technological Measures. For purposes of this Public License, + simply making modifications authorized by this Section 2(a) + (4) never produces Adapted Material. + + 5. Downstream recipients. + + a. Offer from the Licensor -- Licensed Material. Every + recipient of the Licensed Material automatically + receives an offer from the Licensor to exercise the + Licensed Rights under the terms and conditions of this + Public License. + + b. Additional offer from the Licensor -- Adapted Material. + Every recipient of Adapted Material from You + automatically receives an offer from the Licensor to + exercise the Licensed Rights in the Adapted Material + under the conditions of the Adapter's License You apply. + + c. No downstream restrictions. You may not offer or impose + any additional or different terms or conditions on, or + apply any Effective Technological Measures to, the + Licensed Material if doing so restricts exercise of the + Licensed Rights by any recipient of the Licensed + Material. + + 6. No endorsement. Nothing in this Public License constitutes or + may be construed as permission to assert or imply that You + are, or that Your use of the Licensed Material is, connected + with, or sponsored, endorsed, or granted official status by, + the Licensor or others designated to receive attribution as + provided in Section 3(a)(1)(A)(i). + + b. Other rights. + + 1. Moral rights, such as the right of integrity, are not + licensed under this Public License, nor are publicity, + privacy, and/or other similar personality rights; however, to + the extent possible, the Licensor waives and/or agrees not to + assert any such rights held by the Licensor to the limited + extent necessary to allow You to exercise the Licensed + Rights, but not otherwise. + + 2. Patent and trademark rights are not licensed under this + Public License. + + 3. To the extent possible, the Licensor waives any right to + collect royalties from You for the exercise of the Licensed + Rights, whether directly or through a collecting society + under any voluntary or waivable statutory or compulsory + licensing scheme. In all other cases the Licensor expressly + reserves any right to collect such royalties. + + +Section 3 -- License Conditions. + +Your exercise of the Licensed Rights is expressly made subject to the +following conditions. + + a. Attribution. + + 1. If You Share the Licensed Material (including in modified + form), You must: + + a. retain the following if it is supplied by the Licensor + with the Licensed Material: + + i. identification of the creator(s) of the Licensed + Material and any others designated to receive + attribution, in any reasonable manner requested by + the Licensor (including by pseudonym if + designated); + + ii. a copyright notice; + + iii. a notice that refers to this Public License; + + iv. a notice that refers to the disclaimer of + warranties; + + v. a URI or hyperlink to the Licensed Material to the + extent reasonably practicable; + + b. indicate if You modified the Licensed Material and + retain an indication of any previous modifications; and + + c. indicate the Licensed Material is licensed under this + Public License, and include the text of, or the URI or + hyperlink to, this Public License. + + 2. You may satisfy the conditions in Section 3(a)(1) in any + reasonable manner based on the medium, means, and context in + which You Share the Licensed Material. For example, it may be + reasonable to satisfy the conditions by providing a URI or + hyperlink to a resource that includes the required + information. + + 3. If requested by the Licensor, You must remove any of the + information required by Section 3(a)(1)(A) to the extent + reasonably practicable. + + b. ShareAlike. + + In addition to the conditions in Section 3(a), if You Share + Adapted Material You produce, the following conditions also apply. + + 1. The Adapter's License You apply must be a Creative Commons + license with the same License Elements, this version or + later, or a BY-SA Compatible License. + + 2. You must include the text of, or the URI or hyperlink to, the + Adapter's License You apply. You may satisfy this condition + in any reasonable manner based on the medium, means, and + context in which You Share Adapted Material. + + 3. You may not offer or impose any additional or different terms + or conditions on, or apply any Effective Technological + Measures to, Adapted Material that restrict exercise of the + rights granted under the Adapter's License You apply. + + +Section 4 -- Sui Generis Database Rights. + +Where the Licensed Rights include Sui Generis Database Rights that +apply to Your use of the Licensed Material: + + a. for the avoidance of doubt, Section 2(a)(1) grants You the right + to extract, reuse, reproduce, and Share all or a substantial + portion of the contents of the database; + + b. if You include all or a substantial portion of the database + contents in a database in which You have Sui Generis Database + Rights, then the database in which You have Sui Generis Database + Rights (but not its individual contents) is Adapted Material, + + including for purposes of Section 3(b); and + c. You must comply with the conditions in Section 3(a) if You Share + all or a substantial portion of the contents of the database. + +For the avoidance of doubt, this Section 4 supplements and does not +replace Your obligations under this Public License where the Licensed +Rights include other Copyright and Similar Rights. + + +Section 5 -- Disclaimer of Warranties and Limitation of Liability. + + a. UNLESS OTHERWISE SEPARATELY UNDERTAKEN BY THE LICENSOR, TO THE + EXTENT POSSIBLE, THE LICENSOR OFFERS THE LICENSED MATERIAL AS-IS + AND AS-AVAILABLE, AND MAKES NO REPRESENTATIONS OR WARRANTIES OF + ANY KIND CONCERNING THE LICENSED MATERIAL, WHETHER EXPRESS, + IMPLIED, STATUTORY, OR OTHER. THIS INCLUDES, WITHOUT LIMITATION, + WARRANTIES OF TITLE, MERCHANTABILITY, FITNESS FOR A PARTICULAR + PURPOSE, NON-INFRINGEMENT, ABSENCE OF LATENT OR OTHER DEFECTS, + ACCURACY, OR THE PRESENCE OR ABSENCE OF ERRORS, WHETHER OR NOT + KNOWN OR DISCOVERABLE. WHERE DISCLAIMERS OF WARRANTIES ARE NOT + ALLOWED IN FULL OR IN PART, THIS DISCLAIMER MAY NOT APPLY TO YOU. + + b. TO THE EXTENT POSSIBLE, IN NO EVENT WILL THE LICENSOR BE LIABLE + TO YOU ON ANY LEGAL THEORY (INCLUDING, WITHOUT LIMITATION, + NEGLIGENCE) OR OTHERWISE FOR ANY DIRECT, SPECIAL, INDIRECT, + INCIDENTAL, CONSEQUENTIAL, PUNITIVE, EXEMPLARY, OR OTHER LOSSES, + COSTS, EXPENSES, OR DAMAGES ARISING OUT OF THIS PUBLIC LICENSE OR + USE OF THE LICENSED MATERIAL, EVEN IF THE LICENSOR HAS BEEN + ADVISED OF THE POSSIBILITY OF SUCH LOSSES, COSTS, EXPENSES, OR + DAMAGES. WHERE A LIMITATION OF LIABILITY IS NOT ALLOWED IN FULL OR + IN PART, THIS LIMITATION MAY NOT APPLY TO YOU. + + c. The disclaimer of warranties and limitation of liability provided + above shall be interpreted in a manner that, to the extent + possible, most closely approximates an absolute disclaimer and + waiver of all liability. + + +Section 6 -- Term and Termination. + + a. This Public License applies for the term of the Copyright and + Similar Rights licensed here. However, if You fail to comply with + this Public License, then Your rights under this Public License + terminate automatically. + + b. Where Your right to use the Licensed Material has terminated under + Section 6(a), it reinstates: + + 1. automatically as of the date the violation is cured, provided + it is cured within 30 days of Your discovery of the + violation; or + + 2. upon express reinstatement by the Licensor. + + For the avoidance of doubt, this Section 6(b) does not affect any + right the Licensor may have to seek remedies for Your violations + of this Public License. + + c. For the avoidance of doubt, the Licensor may also offer the + Licensed Material under separate terms or conditions or stop + distributing the Licensed Material at any time; however, doing so + will not terminate this Public License. + + d. Sections 1, 5, 6, 7, and 8 survive termination of this Public + License. + + +Section 7 -- Other Terms and Conditions. + + a. The Licensor shall not be bound by any additional or different + terms or conditions communicated by You unless expressly agreed. + + b. Any arrangements, understandings, or agreements regarding the + Licensed Material not stated herein are separate from and + independent of the terms and conditions of this Public License. + + +Section 8 -- Interpretation. + + a. For the avoidance of doubt, this Public License does not, and + shall not be interpreted to, reduce, limit, restrict, or impose + conditions on any use of the Licensed Material that could lawfully + be made without permission under this Public License. + + b. To the extent possible, if any provision of this Public License is + deemed unenforceable, it shall be automatically reformed to the + minimum extent necessary to make it enforceable. If the provision + cannot be reformed, it shall be severed from this Public License + without affecting the enforceability of the remaining terms and + conditions. + + c. No term or condition of this Public License will be waived and no + failure to comply consented to unless expressly agreed to by the + Licensor. + + d. Nothing in this Public License constitutes or may be interpreted + as a limitation upon, or waiver of, any privileges and immunities + that apply to the Licensor or You, including from the legal + processes of any jurisdiction or authority. + + +======================================================================= + +Creative Commons is not a party to its public licenses. +Notwithstanding, Creative Commons may elect to apply one of its public +licenses to material it publishes and in those instances will be +considered the "Licensor." Except for the limited purpose of indicating +that material is shared under a Creative Commons public license or as +otherwise permitted by the Creative Commons policies published at +creativecommons.org/policies, Creative Commons does not authorize the +use of the trademark "Creative Commons" or any other trademark or logo +of Creative Commons without its prior written consent including, +without limitation, in connection with any unauthorized modifications +to any of its public licenses or any other arrangements, +understandings, or agreements concerning use of licensed material. For +the avoidance of doubt, this paragraph does not form part of the public +licenses. + +Creative Commons may be contacted at creativecommons.org. diff --git a/vendor/github.com/docker/go-units/MAINTAINERS b/vendor/github.com/docker/go-units/MAINTAINERS new file mode 100644 index 000000000..477be8b21 --- /dev/null +++ b/vendor/github.com/docker/go-units/MAINTAINERS @@ -0,0 +1,27 @@ +# go-connections maintainers file +# +# This file describes who runs the docker/go-connections project and how. +# This is a living document - if you see something out of date or missing, speak up! +# +# It is structured to be consumable by both humans and programs. +# To extract its contents programmatically, use any TOML-compliant parser. +# +# This file is compiled into the MAINTAINERS file in docker/opensource. +# +[Org] + [Org."Core maintainers"] + people = [ + "calavera", + ] + +[people] + +# A reference list of all people associated with the project. +# All other sections should refer to people by their canonical key +# in the people section. + + # ADD YOURSELF HERE IN ALPHABETICAL ORDER + [people.calavera] + Name = "David Calavera" + Email = "david.calavera@gmail.com" + GitHub = "calavera" diff --git a/vendor/github.com/docker/go-units/README.md b/vendor/github.com/docker/go-units/README.md new file mode 100644 index 000000000..3ce4d79da --- /dev/null +++ b/vendor/github.com/docker/go-units/README.md @@ -0,0 +1,18 @@ +[![GoDoc](https://godoc.org/github.com/docker/go-units?status.svg)](https://godoc.org/github.com/docker/go-units) + +# Introduction + +go-units is a library to transform human friendly measurements into machine friendly values. + +## Usage + +See the [docs in godoc](https://godoc.org/github.com/docker/go-units) for examples and documentation. + +## Copyright and license + +Copyright © 2015 Docker, Inc. All rights reserved, except as follows. Code +is released under the Apache 2.0 license. The README.md file, and files in the +"docs" folder are licensed under the Creative Commons Attribution 4.0 +International License under the terms and conditions set forth in the file +"LICENSE.docs". You may obtain a duplicate copy of the same license, titled +CC-BY-SA-4.0, at http://creativecommons.org/licenses/by/4.0/. diff --git a/vendor/github.com/docker/go-units/circle.yml b/vendor/github.com/docker/go-units/circle.yml new file mode 100644 index 000000000..9043b3547 --- /dev/null +++ b/vendor/github.com/docker/go-units/circle.yml @@ -0,0 +1,11 @@ +dependencies: + post: + # install golint + - go get github.com/golang/lint/golint + +test: + pre: + # run analysis before tests + - go vet ./... + - test -z "$(golint ./... | tee /dev/stderr)" + - test -z "$(gofmt -s -l . | tee /dev/stderr)" diff --git a/vendor/github.com/docker/docker/pkg/units/duration.go b/vendor/github.com/docker/go-units/duration.go similarity index 84% rename from vendor/github.com/docker/docker/pkg/units/duration.go rename to vendor/github.com/docker/go-units/duration.go index 44012aafb..c219a8a96 100644 --- a/vendor/github.com/docker/docker/pkg/units/duration.go +++ b/vendor/github.com/docker/go-units/duration.go @@ -1,3 +1,5 @@ +// Package units provides helper function to parse and print size and time units +// in human-readable format. package units import ( @@ -6,7 +8,7 @@ import ( ) // HumanDuration returns a human-readable approximation of a duration -// (eg. "About a minute", "4 hours ago", etc.) +// (eg. "About a minute", "4 hours ago", etc.). func HumanDuration(d time.Duration) string { if seconds := int(d.Seconds()); seconds < 1 { return "Less than a second" diff --git a/vendor/github.com/docker/docker/pkg/units/size.go b/vendor/github.com/docker/go-units/size.go similarity index 80% rename from vendor/github.com/docker/docker/pkg/units/size.go rename to vendor/github.com/docker/go-units/size.go index 9e84697ca..989edd29b 100644 --- a/vendor/github.com/docker/docker/pkg/units/size.go +++ b/vendor/github.com/docker/go-units/size.go @@ -31,14 +31,14 @@ type unitMap map[string]int64 var ( decimalMap = unitMap{"k": KB, "m": MB, "g": GB, "t": TB, "p": PB} binaryMap = unitMap{"k": KiB, "m": MiB, "g": GiB, "t": TiB, "p": PiB} - sizeRegex = regexp.MustCompile(`^(\d+)([kKmMgGtTpP])?[bB]?$`) + sizeRegex = regexp.MustCompile(`^(\d+(\.\d+)*) ?([kKmMgGtTpP])?[bB]?$`) ) var decimapAbbrs = []string{"B", "kB", "MB", "GB", "TB", "PB", "EB", "ZB", "YB"} var binaryAbbrs = []string{"B", "KiB", "MiB", "GiB", "TiB", "PiB", "EiB", "ZiB", "YiB"} // CustomSize returns a human-readable approximation of a size -// using custom format +// using custom format. func CustomSize(format string, size float64, base float64, _map []string) string { i := 0 for size >= base { @@ -49,17 +49,19 @@ func CustomSize(format string, size float64, base float64, _map []string) string } // HumanSize returns a human-readable approximation of a size -// using SI standard (eg. "44kB", "17MB") +// capped at 4 valid numbers (eg. "2.746 MB", "796 KB"). func HumanSize(size float64) string { return CustomSize("%.4g %s", size, 1000.0, decimapAbbrs) } +// BytesSize returns a human-readable size in bytes, kibibytes, +// mebibytes, gibibytes, or tebibytes (eg. "44kiB", "17MiB"). func BytesSize(size float64) string { return CustomSize("%.4g %s", size, 1024.0, binaryAbbrs) } // FromHumanSize returns an integer from a human-readable specification of a -// size using SI standard (eg. "44kB", "17MB") +// size using SI standard (eg. "44kB", "17MB"). func FromHumanSize(size string) (int64, error) { return parseSize(size, decimalMap) } @@ -72,22 +74,22 @@ func RAMInBytes(size string) (int64, error) { return parseSize(size, binaryMap) } -// Parses the human-readable size string into the amount it represents +// Parses the human-readable size string into the amount it represents. func parseSize(sizeStr string, uMap unitMap) (int64, error) { matches := sizeRegex.FindStringSubmatch(sizeStr) - if len(matches) != 3 { + if len(matches) != 4 { return -1, fmt.Errorf("invalid size: '%s'", sizeStr) } - size, err := strconv.ParseInt(matches[1], 10, 0) + size, err := strconv.ParseFloat(matches[1], 64) if err != nil { return -1, err } - unitPrefix := strings.ToLower(matches[2]) + unitPrefix := strings.ToLower(matches[3]) if mul, ok := uMap[unitPrefix]; ok { - size *= mul + size *= float64(mul) } - return size, nil + return int64(size), nil } diff --git a/vendor/github.com/docker/go-units/ulimit.go b/vendor/github.com/docker/go-units/ulimit.go new file mode 100644 index 000000000..5ac7fd825 --- /dev/null +++ b/vendor/github.com/docker/go-units/ulimit.go @@ -0,0 +1,118 @@ +package units + +import ( + "fmt" + "strconv" + "strings" +) + +// Ulimit is a human friendly version of Rlimit. +type Ulimit struct { + Name string + Hard int64 + Soft int64 +} + +// Rlimit specifies the resource limits, such as max open files. +type Rlimit struct { + Type int `json:"type,omitempty"` + Hard uint64 `json:"hard,omitempty"` + Soft uint64 `json:"soft,omitempty"` +} + +const ( + // magic numbers for making the syscall + // some of these are defined in the syscall package, but not all. + // Also since Windows client doesn't get access to the syscall package, need to + // define these here + rlimitAs = 9 + rlimitCore = 4 + rlimitCPU = 0 + rlimitData = 2 + rlimitFsize = 1 + rlimitLocks = 10 + rlimitMemlock = 8 + rlimitMsgqueue = 12 + rlimitNice = 13 + rlimitNofile = 7 + rlimitNproc = 6 + rlimitRss = 5 + rlimitRtprio = 14 + rlimitRttime = 15 + rlimitSigpending = 11 + rlimitStack = 3 +) + +var ulimitNameMapping = map[string]int{ + //"as": rlimitAs, // Disabled since this doesn't seem usable with the way Docker inits a container. + "core": rlimitCore, + "cpu": rlimitCPU, + "data": rlimitData, + "fsize": rlimitFsize, + "locks": rlimitLocks, + "memlock": rlimitMemlock, + "msgqueue": rlimitMsgqueue, + "nice": rlimitNice, + "nofile": rlimitNofile, + "nproc": rlimitNproc, + "rss": rlimitRss, + "rtprio": rlimitRtprio, + "rttime": rlimitRttime, + "sigpending": rlimitSigpending, + "stack": rlimitStack, +} + +// ParseUlimit parses and returns a Ulimit from the specified string. +func ParseUlimit(val string) (*Ulimit, error) { + parts := strings.SplitN(val, "=", 2) + if len(parts) != 2 { + return nil, fmt.Errorf("invalid ulimit argument: %s", val) + } + + if _, exists := ulimitNameMapping[parts[0]]; !exists { + return nil, fmt.Errorf("invalid ulimit type: %s", parts[0]) + } + + var ( + soft int64 + hard = &soft // default to soft in case no hard was set + temp int64 + err error + ) + switch limitVals := strings.Split(parts[1], ":"); len(limitVals) { + case 2: + temp, err = strconv.ParseInt(limitVals[1], 10, 64) + if err != nil { + return nil, err + } + hard = &temp + fallthrough + case 1: + soft, err = strconv.ParseInt(limitVals[0], 10, 64) + if err != nil { + return nil, err + } + default: + return nil, fmt.Errorf("too many limit value arguments - %s, can only have up to two, `soft[:hard]`", parts[1]) + } + + if soft > *hard { + return nil, fmt.Errorf("ulimit soft limit must be less than or equal to hard limit: %d > %d", soft, *hard) + } + + return &Ulimit{Name: parts[0], Soft: soft, Hard: *hard}, nil +} + +// GetRlimit returns the RLimit corresponding to Ulimit. +func (u *Ulimit) GetRlimit() (*Rlimit, error) { + t, exists := ulimitNameMapping[u.Name] + if !exists { + return nil, fmt.Errorf("invalid ulimit name %s", u.Name) + } + + return &Rlimit{Type: t, Soft: uint64(u.Soft), Hard: uint64(u.Hard)}, nil +} + +func (u *Ulimit) String() string { + return fmt.Sprintf("%s=%d:%d", u.Name, u.Soft, u.Hard) +} diff --git a/vendor/github.com/dustin/go-broadcast/README.markdown b/vendor/github.com/dustin/go-broadcast/README.markdown deleted file mode 100644 index 863ae2714..000000000 --- a/vendor/github.com/dustin/go-broadcast/README.markdown +++ /dev/null @@ -1,5 +0,0 @@ -pubsubbing channels. - -This project primarily exists because I've been copying and pasting -the exact same two files into numerous projects. It does work well, -though. diff --git a/vendor/github.com/dustin/go-broadcast/broadcaster.go b/vendor/github.com/dustin/go-broadcast/broadcaster.go deleted file mode 100644 index 9c113f596..000000000 --- a/vendor/github.com/dustin/go-broadcast/broadcaster.go +++ /dev/null @@ -1,86 +0,0 @@ -/* -Package broadcast provides pubsub of messages over channels. - -A provider has a Broadcaster into which it Submits messages and into -which subscribers Register to pick up those messages. - -*/ -package broadcast - -type broadcaster struct { - input chan interface{} - reg chan chan<- interface{} - unreg chan chan<- interface{} - - outputs map[chan<- interface{}]bool -} - -// The Broadcaster interface describes the main entry points to -// broadcasters. -type Broadcaster interface { - // Register a new channel to receive broadcasts - Register(chan<- interface{}) - // Unregister a channel so that it no longer receives broadcasts. - Unregister(chan<- interface{}) - // Shut this broadcaster down. - Close() error - // Submit a new object to all subscribers - Submit(interface{}) -} - -func (b *broadcaster) broadcast(m interface{}) { - for ch := range b.outputs { - ch <- m - } -} - -func (b *broadcaster) run() { - for { - select { - case m := <-b.input: - b.broadcast(m) - case ch, ok := <-b.reg: - if ok { - b.outputs[ch] = true - } else { - return - } - case ch := <-b.unreg: - delete(b.outputs, ch) - } - } -} - -// NewBroadcaster creates a new broadcaster with the given input -// channel buffer length. -func NewBroadcaster(buflen int) Broadcaster { - b := &broadcaster{ - input: make(chan interface{}, buflen), - reg: make(chan chan<- interface{}), - unreg: make(chan chan<- interface{}), - outputs: make(map[chan<- interface{}]bool), - } - - go b.run() - - return b -} - -func (b *broadcaster) Register(newch chan<- interface{}) { - b.reg <- newch -} - -func (b *broadcaster) Unregister(newch chan<- interface{}) { - b.unreg <- newch -} - -func (b *broadcaster) Close() error { - close(b.reg) - return nil -} - -func (b *broadcaster) Submit(m interface{}) { - if b != nil { - b.input <- m - } -} diff --git a/vendor/github.com/dustin/go-broadcast/broadcaster_test.go b/vendor/github.com/dustin/go-broadcast/broadcaster_test.go deleted file mode 100644 index 6c431d5e0..000000000 --- a/vendor/github.com/dustin/go-broadcast/broadcaster_test.go +++ /dev/null @@ -1,100 +0,0 @@ -package broadcast - -import ( - "sync" - "testing" -) - -func TestBroadcast(t *testing.T) { - wg := sync.WaitGroup{} - - b := NewBroadcaster(100) - defer b.Close() - - for i := 0; i < 5; i++ { - wg.Add(1) - - cch := make(chan interface{}) - - b.Register(cch) - - go func() { - defer wg.Done() - defer b.Unregister(cch) - <-cch - }() - - } - - b.Submit(1) - - wg.Wait() -} - -func TestBroadcastCleanup(t *testing.T) { - b := NewBroadcaster(100) - b.Register(make(chan interface{})) - b.Close() -} - -func echoer(chin, chout chan interface{}) { - for m := range chin { - chout <- m - } -} - -func BenchmarkDirectSend(b *testing.B) { - chout := make(chan interface{}) - chin := make(chan interface{}) - defer close(chin) - - go echoer(chin, chout) - - for i := 0; i < b.N; i++ { - chin <- nil - <-chout - } -} - -func BenchmarkBrodcast(b *testing.B) { - chout := make(chan interface{}) - - bc := NewBroadcaster(0) - defer bc.Close() - bc.Register(chout) - - for i := 0; i < b.N; i++ { - bc.Submit(nil) - <-chout - } -} - -func BenchmarkParallelDirectSend(b *testing.B) { - chout := make(chan interface{}) - chin := make(chan interface{}) - defer close(chin) - - go echoer(chin, chout) - - b.RunParallel(func(pb *testing.PB) { - for pb.Next() { - chin <- nil - <-chout - } - }) -} - -func BenchmarkParallelBrodcast(b *testing.B) { - chout := make(chan interface{}) - - bc := NewBroadcaster(0) - defer bc.Close() - bc.Register(chout) - - b.RunParallel(func(pb *testing.PB) { - for pb.Next() { - bc.Submit(nil) - <-chout - } - }) -} diff --git a/vendor/github.com/dustin/go-broadcast/mux_observer.go b/vendor/github.com/dustin/go-broadcast/mux_observer.go deleted file mode 100644 index 38d0dcb18..000000000 --- a/vendor/github.com/dustin/go-broadcast/mux_observer.go +++ /dev/null @@ -1,133 +0,0 @@ -package broadcast - -type taggedObservation struct { - sub *subObserver - ob interface{} -} - -const ( - register = iota - unregister - purge -) - -type taggedRegReq struct { - sub *subObserver - ch chan<- interface{} - regType int -} - -// A MuxObserver multiplexes several streams of observations onto a -// single delivery goroutine. -type MuxObserver struct { - subs map[*subObserver]map[chan<- interface{}]bool - reg chan taggedRegReq - input chan taggedObservation -} - -// NewMuxObserver constructs a new MuxObserver. -// -// qlen is the size of the channel buffer for observations sent into -// the mux observer and reglen is the size of the channel buffer for -// registration/unregistration events. -func NewMuxObserver(qlen, reglen int) *MuxObserver { - rv := &MuxObserver{ - subs: map[*subObserver]map[chan<- interface{}]bool{}, - reg: make(chan taggedRegReq, reglen), - input: make(chan taggedObservation, qlen), - } - go rv.run() - return rv -} - -// Close shuts down this mux observer. -func (m *MuxObserver) Close() error { - close(m.reg) - return nil -} - -func (m *MuxObserver) broadcast(to taggedObservation) { - for ch := range m.subs[to.sub] { - ch <- to.ob - } -} - -func (m *MuxObserver) doReg(tr taggedRegReq) { - mm, exists := m.subs[tr.sub] - if !exists { - mm = map[chan<- interface{}]bool{} - m.subs[tr.sub] = mm - } - mm[tr.ch] = true -} - -func (m *MuxObserver) doUnreg(tr taggedRegReq) { - mm, exists := m.subs[tr.sub] - if exists { - delete(mm, tr.ch) - if len(mm) == 0 { - delete(m.subs, tr.sub) - } - } -} - -func (m *MuxObserver) handleReg(tr taggedRegReq) { - switch tr.regType { - case register: - m.doReg(tr) - case unregister: - m.doUnreg(tr) - case purge: - delete(m.subs, tr.sub) - } -} - -func (m *MuxObserver) run() { - for { - select { - case tr, ok := <-m.reg: - if ok { - m.handleReg(tr) - } else { - return - } - default: - select { - case to := <-m.input: - m.broadcast(to) - case tr, ok := <-m.reg: - if ok { - m.handleReg(tr) - } else { - return - } - } - } - } -} - -// Sub creates a new sub-broadcaster from this MuxObserver. -func (m *MuxObserver) Sub() Broadcaster { - return &subObserver{m} -} - -type subObserver struct { - mo *MuxObserver -} - -func (s *subObserver) Register(ch chan<- interface{}) { - s.mo.reg <- taggedRegReq{s, ch, register} -} - -func (s *subObserver) Unregister(ch chan<- interface{}) { - s.mo.reg <- taggedRegReq{s, ch, unregister} -} - -func (s *subObserver) Close() error { - s.mo.reg <- taggedRegReq{s, nil, purge} - return nil -} - -func (s *subObserver) Submit(ob interface{}) { - s.mo.input <- taggedObservation{s, ob} -} diff --git a/vendor/github.com/dustin/go-broadcast/mux_observer_test.go b/vendor/github.com/dustin/go-broadcast/mux_observer_test.go deleted file mode 100644 index e395720e2..000000000 --- a/vendor/github.com/dustin/go-broadcast/mux_observer_test.go +++ /dev/null @@ -1,67 +0,0 @@ -package broadcast - -import ( - "sync" - "testing" -) - -func TestMuxBroadcast(t *testing.T) { - wg := sync.WaitGroup{} - - mo := NewMuxObserver(0, 0) - defer mo.Close() - - b1 := mo.Sub() - defer b1.Close() - - b2 := mo.Sub() - defer b2.Close() - - for i := 0; i < 5; i++ { - wg.Add(2) - - cch1 := make(chan interface{}) - b1.Register(cch1) - cch2 := make(chan interface{}) - b2.Register(cch2) - - go func() { - defer wg.Done() - defer b1.Unregister(cch1) - <-cch1 - }() - go func() { - defer wg.Done() - defer b2.Unregister(cch2) - <-cch2 - }() - - } - - go b1.Submit(1) - go b2.Submit(1) - - wg.Wait() -} - -func TestMuxBroadcastCleanup(t *testing.T) { - mo := NewMuxObserver(0, 0) - b := mo.Sub() - b.Register(make(chan interface{})) - b.Close() - mo.Close() -} - -func BenchmarkMuxBrodcast(b *testing.B) { - chout := make(chan interface{}) - - mo := NewMuxObserver(0, 0) - defer mo.Close() - bc := mo.Sub() - bc.Register(chout) - - for i := 0; i < b.N; i++ { - bc.Submit(nil) - <-chout - } -} diff --git a/vendor/github.com/eknkc/amber/amber_test.go b/vendor/github.com/eknkc/amber/amber_test.go deleted file mode 100644 index a9f0b4541..000000000 --- a/vendor/github.com/eknkc/amber/amber_test.go +++ /dev/null @@ -1,313 +0,0 @@ -package amber - -import ( - "bytes" - "strings" - "testing" -) - -func Test_Doctype(t *testing.T) { - res, err := run(`!!! 5`, nil) - - if err != nil { - t.Fatal(err.Error()) - } else { - expect(res, ``, t) - } -} - -func Test_Nesting(t *testing.T) { - res, err := run(`html - head - title - body`, nil) - - if err != nil { - t.Fatal(err.Error()) - } else { - expect(res, ``, t) - } -} - -func Test_Mixin(t *testing.T) { - res, err := run(` - mixin a($a) - p #{$a} - - +a(1)`, nil) - - if err != nil { - t.Fatal(err.Error()) - } else { - expect(res, `

1

`, t) - } -} - -func Test_Mixin_NoArguments(t *testing.T) { - res, err := run(` - mixin a() - p Testing - - +a()`, nil) - - if err != nil { - t.Fatal(err.Error()) - } else { - expect(res, `

Testing

`, t) - } -} - -func Test_Mixin_MultiArguments(t *testing.T) { - res, err := run(` - mixin a($a, $b, $c, $d) - p #{$a} #{$b} #{$c} #{$d} - - +a("a", "b", "c", A)`, map[string]int{"A": 2}) - - if err != nil { - t.Fatal(err.Error()) - } else { - expect(res, `

a b c 2

`, t) - } -} - -func Test_ClassName(t *testing.T) { - res, err := run(`div.test - p.test1.test2 - [class=$] - .test3`, "test4") - - if err != nil { - t.Fatal(err.Error()) - } else { - expect(res, `

`, t) - } -} - -func Test_Id(t *testing.T) { - res, err := run(`div#test - p#test1#test2`, nil) - - if err != nil { - t.Fatal(err.Error()) - } else { - expect(res, `

`, t) - } -} - -func Test_Attribute(t *testing.T) { - res, err := run(`div[name="Test"][foo="bar"].testclass - p - [style="text-align: center; color: maroon"]`, nil) - - if err != nil { - t.Fatal(err.Error()) - } else { - expect(res, `

`, t) - } -} - -func Test_EmptyAttribute(t *testing.T) { - res, err := run(`div[name]`, nil) - - if err != nil { - t.Fatal(err.Error()) - } else { - expect(res, `
`, t) - } -} - -func Test_RawText(t *testing.T) { - res, err := run(`html - script - var a = 5; - alert(a) - style - body { - color: white - }`, nil) - - if err != nil { - t.Fatal(err.Error()) - } else { - expect(res, "", t) - } -} - -func Test_Empty(t *testing.T) { - res, err := run(``, nil) - - if err != nil { - t.Fatal(err.Error()) - } else { - expect(res, ``, t) - } -} - -func Test_ArithmeticExpression(t *testing.T) { - res, err := run(`#{A + B * C}`, map[string]int{"A": 2, "B": 3, "C": 4}) - - if err != nil { - t.Fatal(err.Error()) - } else { - expect(res, `14`, t) - } -} - -func Test_BooleanExpression(t *testing.T) { - res, err := run(`#{C - A < B}`, map[string]int{"A": 2, "B": 3, "C": 4}) - - if err != nil { - t.Fatal(err.Error()) - } else { - expect(res, `true`, t) - } -} - -func Test_FuncCall(t *testing.T) { - res, err := run(`div[data-map=json($)]`, map[string]int{"A": 2, "B": 3, "C": 4}) - - if err != nil { - t.Fatal(err.Error()) - } else { - expect(res, `
`, t) - } -} - -func Test_Multiple_File_Inheritance(t *testing.T) { - tmpl, err := CompileDir("samples/", DefaultDirOptions, DefaultOptions) - if err != nil { - t.Fatal(err.Error()) - } - - t1a, ok := tmpl["multilevel.inheritance.a"] - if ok != true || t1a == nil { - t.Fatal("CompileDir, template not found.") - } - - t1b, ok := tmpl["multilevel.inheritance.b"] - if ok != true || t1b == nil { - t.Fatal("CompileDir, template not found.") - } - - t1c, ok := tmpl["multilevel.inheritance.c"] - if ok != true || t1c == nil { - t.Fatal("CompileDir, template not found.") - } - - var res bytes.Buffer - t1c.Execute(&res, nil) - expect(strings.TrimSpace(res.String()), "

This is C

", t) -} - -func Failing_Test_CompileDir(t *testing.T) { - tmpl, err := CompileDir("samples/", DefaultDirOptions, DefaultOptions) - - // Test Compilation - if err != nil { - t.Fatal(err.Error()) - } - - // Make sure files are added to map correctly - val1, ok := tmpl["basic"] - if ok != true || val1 == nil { - t.Fatal("CompileDir, template not found.") - } - val2, ok := tmpl["inherit"] - if ok != true || val2 == nil { - t.Fatal("CompileDir, template not found.") - } - val3, ok := tmpl["compiledir_test/basic"] - if ok != true || val3 == nil { - t.Fatal("CompileDir, template not found.") - } - val4, ok := tmpl["compiledir_test/compiledir_test/basic"] - if ok != true || val4 == nil { - t.Fatal("CompileDir, template not found.") - } - - // Make sure file parsing is the same - var doc1, doc2 bytes.Buffer - val1.Execute(&doc1, nil) - val4.Execute(&doc2, nil) - expect(doc1.String(), doc2.String(), t) - - // Check against CompileFile - compilefile, err := CompileFile("samples/basic.amber", DefaultOptions) - if err != nil { - t.Fatal(err.Error()) - } - var doc3 bytes.Buffer - compilefile.Execute(&doc3, nil) - expect(doc1.String(), doc3.String(), t) - expect(doc2.String(), doc3.String(), t) - -} - -func Benchmark_Parse(b *testing.B) { - code := ` - !!! 5 - html - head - title Test Title - body - nav#mainNav[data-foo="bar"] - div#content - div.left - div.center - block center - p Main Content - .long ? somevar && someothervar - div.right` - - for i := 0; i < b.N; i++ { - cmp := New() - cmp.Parse(code) - } -} - -func Benchmark_Compile(b *testing.B) { - b.StopTimer() - - code := ` - !!! 5 - html - head - title Test Title - body - nav#mainNav[data-foo="bar"] - div#content - div.left - div.center - block center - p Main Content - .long ? somevar && someothervar - div.right` - - cmp := New() - cmp.Parse(code) - - b.StartTimer() - - for i := 0; i < b.N; i++ { - cmp.CompileString() - } -} - -func expect(cur, expected string, t *testing.T) { - if cur != expected { - t.Fatalf("Expected {%s} got {%s}.", expected, cur) - } -} - -func run(tpl string, data interface{}) (string, error) { - t, err := Compile(tpl, Options{false, false}) - if err != nil { - return "", err - } - var buf bytes.Buffer - if err = t.Execute(&buf, data); err != nil { - return "", err - } - return strings.TrimSpace(buf.String()), nil -} diff --git a/vendor/github.com/eknkc/amber/amberc/cli.go b/vendor/github.com/eknkc/amber/amberc/cli.go deleted file mode 100644 index 4ce316336..000000000 --- a/vendor/github.com/eknkc/amber/amberc/cli.go +++ /dev/null @@ -1,48 +0,0 @@ -package main - -import ( - "flag" - "fmt" - amber "github.com/eknkc/amber" - "os" -) - -var prettyPrint bool -var lineNumbers bool - -func init() { - flag.BoolVar(&prettyPrint, "prettyprint", true, "Use pretty indentation in output html.") - flag.BoolVar(&prettyPrint, "pp", true, "Use pretty indentation in output html.") - - flag.BoolVar(&lineNumbers, "linenos", true, "Enable debugging information in output html.") - flag.BoolVar(&lineNumbers, "ln", true, "Enable debugging information in output html.") - - flag.Parse() -} - -func main() { - input := flag.Arg(0) - - if len(input) == 0 { - fmt.Fprintln(os.Stderr, "Please provide an input file. (amberc input.amber)") - os.Exit(1) - } - - cmp := amber.New() - cmp.PrettyPrint = prettyPrint - cmp.LineNumbers = lineNumbers - - err := cmp.ParseFile(input) - - if err != nil { - fmt.Fprintln(os.Stderr, err) - os.Exit(1) - } - - err = cmp.CompileWriter(os.Stdout) - - if err != nil { - fmt.Fprintln(os.Stderr, err) - os.Exit(1) - } -} diff --git a/vendor/github.com/eknkc/amber/samples/basic.amber b/vendor/github.com/eknkc/amber/samples/basic.amber deleted file mode 100644 index 96f73271b..000000000 --- a/vendor/github.com/eknkc/amber/samples/basic.amber +++ /dev/null @@ -1,28 +0,0 @@ -!!! 5 -html - head - title Hello - - meta[name="description"][value="This is a sample"] - - script[type="text/javascript"] - var hw = "Hello World!" - alert(hw) - - style[type="text/css"] - body { - background: maroon; - color: white - } - - body - header#mainHeader - ul - li.active - a[href="/"] Main Page - [title="Main Page"] - - footer - | Hey - br - | There diff --git a/vendor/github.com/eknkc/amber/samples/compiledir_test/basic.amber b/vendor/github.com/eknkc/amber/samples/compiledir_test/basic.amber deleted file mode 100644 index 96f73271b..000000000 --- a/vendor/github.com/eknkc/amber/samples/compiledir_test/basic.amber +++ /dev/null @@ -1,28 +0,0 @@ -!!! 5 -html - head - title Hello - - meta[name="description"][value="This is a sample"] - - script[type="text/javascript"] - var hw = "Hello World!" - alert(hw) - - style[type="text/css"] - body { - background: maroon; - color: white - } - - body - header#mainHeader - ul - li.active - a[href="/"] Main Page - [title="Main Page"] - - footer - | Hey - br - | There diff --git a/vendor/github.com/eknkc/amber/samples/compiledir_test/compiledir_test/basic.amber b/vendor/github.com/eknkc/amber/samples/compiledir_test/compiledir_test/basic.amber deleted file mode 100644 index 96f73271b..000000000 --- a/vendor/github.com/eknkc/amber/samples/compiledir_test/compiledir_test/basic.amber +++ /dev/null @@ -1,28 +0,0 @@ -!!! 5 -html - head - title Hello - - meta[name="description"][value="This is a sample"] - - script[type="text/javascript"] - var hw = "Hello World!" - alert(hw) - - style[type="text/css"] - body { - background: maroon; - color: white - } - - body - header#mainHeader - ul - li.active - a[href="/"] Main Page - [title="Main Page"] - - footer - | Hey - br - | There diff --git a/vendor/github.com/eknkc/amber/samples/inherit.amber b/vendor/github.com/eknkc/amber/samples/inherit.amber deleted file mode 100644 index afb38bb60..000000000 --- a/vendor/github.com/eknkc/amber/samples/inherit.amber +++ /dev/null @@ -1,11 +0,0 @@ -extends inherit.master.amber - -block append meta - meta[name="keywords"][content="These are added by the child template"] - -block menu - li Item 1 - li Item 2 - -block content - p Content from child template diff --git a/vendor/github.com/eknkc/amber/samples/inherit.master.amber b/vendor/github.com/eknkc/amber/samples/inherit.master.amber deleted file mode 100644 index 66cf82cd7..000000000 --- a/vendor/github.com/eknkc/amber/samples/inherit.master.amber +++ /dev/null @@ -1,16 +0,0 @@ -!!! transitional -html - head - title Hello - - block meta - meta[name="description"][value="This is a sample"] - - body - header#mainHeader - ul - block menu - - div#content - block content - diff --git a/vendor/github.com/eknkc/amber/samples/multilevel.inheritance.a.amber b/vendor/github.com/eknkc/amber/samples/multilevel.inheritance.a.amber deleted file mode 100644 index 2e2c45ac4..000000000 --- a/vendor/github.com/eknkc/amber/samples/multilevel.inheritance.a.amber +++ /dev/null @@ -1,2 +0,0 @@ -block overwriteme - p This is A diff --git a/vendor/github.com/eknkc/amber/samples/multilevel.inheritance.b.amber b/vendor/github.com/eknkc/amber/samples/multilevel.inheritance.b.amber deleted file mode 100644 index 23b699f52..000000000 --- a/vendor/github.com/eknkc/amber/samples/multilevel.inheritance.b.amber +++ /dev/null @@ -1,4 +0,0 @@ -extends multilevel.inheritance.a.amber - -block overwriteme - p This is B diff --git a/vendor/github.com/eknkc/amber/samples/multilevel.inheritance.c.amber b/vendor/github.com/eknkc/amber/samples/multilevel.inheritance.c.amber deleted file mode 100644 index 3cce2ee93..000000000 --- a/vendor/github.com/eknkc/amber/samples/multilevel.inheritance.c.amber +++ /dev/null @@ -1,4 +0,0 @@ -extends multilevel.inheritance.b.amber - -block overwriteme - p This is C diff --git a/vendor/github.com/elazarl/go-bindata-assetfs/go-bindata-assetfs/main.go b/vendor/github.com/elazarl/go-bindata-assetfs/go-bindata-assetfs/main.go deleted file mode 100644 index a5b2b5eef..000000000 --- a/vendor/github.com/elazarl/go-bindata-assetfs/go-bindata-assetfs/main.go +++ /dev/null @@ -1,97 +0,0 @@ -package main - -import ( - "bufio" - "bytes" - "flag" - "fmt" - "os" - "os/exec" - "strings" -) - -const bindatafile = "bindata.go" - -func isDebug(args []string) bool { - flagset := flag.NewFlagSet("", flag.ContinueOnError) - debug := flagset.Bool("debug", false, "") - debugArgs := make([]string, 0) - for _, arg := range args { - if strings.HasPrefix(arg, "-debug") { - debugArgs = append(debugArgs, arg) - } - } - flagset.Parse(debugArgs) - if debug == nil { - return false - } - return *debug -} - -func main() { - if _, err := exec.LookPath("go-bindata"); err != nil { - fmt.Println("Cannot find go-bindata executable in path") - fmt.Println("Maybe you need: go get github.com/elazarl/go-bindata-assetfs/...") - os.Exit(1) - } - cmd := exec.Command("go-bindata", os.Args[1:]...) - cmd.Stdin = os.Stdin - cmd.Stdout = os.Stdout - cmd.Stderr = os.Stderr - if err := cmd.Run(); err != nil { - os.Exit(1) - } - in, err := os.Open(bindatafile) - if err != nil { - fmt.Fprintln(os.Stderr, "Cannot read", bindatafile, err) - return - } - out, err := os.Create("bindata_assetfs.go") - if err != nil { - fmt.Fprintln(os.Stderr, "Cannot write 'bindata_assetfs.go'", err) - return - } - debug := isDebug(os.Args[1:]) - r := bufio.NewReader(in) - done := false - for line, isPrefix, err := r.ReadLine(); err == nil; line, isPrefix, err = r.ReadLine() { - if !isPrefix { - line = append(line, '\n') - } - if _, err := out.Write(line); err != nil { - fmt.Fprintln(os.Stderr, "Cannot write to 'bindata_assetfs.go'", err) - return - } - if !done && !isPrefix && bytes.HasPrefix(line, []byte("import (")) { - if debug { - fmt.Fprintln(out, "\t\"net/http\"") - } else { - fmt.Fprintln(out, "\t\"github.com/elazarl/go-bindata-assetfs\"") - } - done = true - } - } - if debug { - fmt.Fprintln(out, ` -func assetFS() http.FileSystem { - for k := range _bintree.Children { - return http.Dir(k) - } - panic("unreachable") -}`) - } else { - fmt.Fprintln(out, ` -func assetFS() *assetfs.AssetFS { - for k := range _bintree.Children { - return &assetfs.AssetFS{Asset: Asset, AssetDir: AssetDir, Prefix: k} - } - panic("unreachable") -}`) - } - // Close files BEFORE remove calls (don't use defer). - in.Close() - out.Close() - if err := os.Remove(bindatafile); err != nil { - fmt.Fprintln(os.Stderr, "Cannot remove", bindatafile, err) - } -} diff --git a/vendor/github.com/dustin/go-broadcast/LICENSE b/vendor/github.com/franela/goblin/LICENSE similarity index 94% rename from vendor/github.com/dustin/go-broadcast/LICENSE rename to vendor/github.com/franela/goblin/LICENSE index b01ef8026..b2d652206 100644 --- a/vendor/github.com/dustin/go-broadcast/LICENSE +++ b/vendor/github.com/franela/goblin/LICENSE @@ -1,4 +1,4 @@ -Copyright (c) 2013 Dustin Sallings +Copyright (c) 2013 Marcos Lilljedahl and Jonathan Leibiusky Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/vendor/github.com/franela/goblin/Makefile b/vendor/github.com/franela/goblin/Makefile new file mode 100644 index 000000000..66763dc8c --- /dev/null +++ b/vendor/github.com/franela/goblin/Makefile @@ -0,0 +1,3 @@ +export GOPATH=$(shell pwd) +test: + go test -v diff --git a/vendor/github.com/franela/goblin/README.md b/vendor/github.com/franela/goblin/README.md new file mode 100644 index 000000000..d9f847e10 --- /dev/null +++ b/vendor/github.com/franela/goblin/README.md @@ -0,0 +1,141 @@ +[![Build Status](https://travis-ci.org/franela/goblin.png?branch=master)](https://travis-ci.org/franela/goblin) +Goblin +====== + +![](https://github.com/marcosnils/goblin/blob/master/goblin_logo.jpg?raw=true) + +A [Mocha](http://visionmedia.github.io/mocha/) like BDD testing framework for Go + +No extensive documentation nor complicated steps to get it running + +Run tests as usual with `go test` + +Colorful reports and beautiful syntax + + +Why Goblin? +----------- + +Inspired by the flexibility and simplicity of Node BDD and frustrated by the +rigorousness of Go way of testing, we wanted to bring a new tool to +write self-describing and comprehensive code. + + + +What do I get with it? +---------------------- + +- Preserve the exact same syntax and behaviour as Node's Mocha +- Nest as many `Describe` and `It` blocks as you want +- Use `Before`, `BeforeEach`, `After` and `AfterEach` for setup and teardown your tests +- No need to remember confusing parameters in `Describe` and `It` blocks +- Use a declarative and expressive language to write your tests +- Plug different assertion libraries ([Gomega](https://github.com/onsi/gomega) supported so far) +- Skip your tests the same way as you would do in Mocha +- Automatic terminal support for colored outputs +- Two line setup is all you need to get up running + + + +How do I use it? +---------------- + +Since ```go test``` is not currently extensive, you will have to hook Goblin to it. You do that by +adding a single test method in your test file. All your goblin tests will be implemented inside this function. + +```go +package foobar + +import ( + "testing" + . "github.com/franela/goblin" +) + +func Test(t *testing.T) { + g := Goblin(t) + g.Describe("Numbers", func() { + g.It("Should add two numbers ", func() { + g.Assert(1+1).Equal(2) + }) + g.It("Should match equal numbers", func() { + g.Assert(2).Equal(4) + }) + g.It("Should substract two numbers") + }) +} +``` + +Ouput will be something like: + +![](https://github.com/marcosnils/goblin/blob/master/goblin_output.png?raw=true) + +Nice and easy, right? + +Can I do asynchronous tests? +---------------------------- + +Yes! Goblin will help you to test asynchronous things, like goroutines, etc. You just need to add a ```done``` parameter to the handler function of your ```It```. This handler function should be called when your test passes. + +```go + ... + g.Describe("Numbers", func() { + g.It("Should add two numbers asynchronously", func(done Done) { + go func() { + g.Assert(1+1).Equal(2) + done() + }() + }) + }) + ... +``` + +Goblin will wait for the ```done``` call, a ```Fail``` call or any false assertion. + +How do I use it with Gomega? +---------------------------- + +Gomega is a nice assertion framework. But it doesn't provide a nice way to hook it to testing frameworks. It should just panic instead of requiring a fail function. There is an issue about that [here](https://github.com/onsi/gomega/issues/5). +While this is being discussed and hopefully fixed, the way to use Gomega with Goblin is: + +```go +package foobar + +import ( + "testing" + . "github.com/franela/goblin" + . "github.com/onsi/gomega" +) + +func Test(t *testing.T) { + g := Goblin(t) + + //special hook for gomega + RegisterFailHandler(func(m string, _ ...int) { g.Fail(m) }) + + g.Describe("lala", func() { + g.It("lslslslsls", func() { + Expect(1).To(Equal(10)) + }) + }) +} +``` + + +FAQ: +---- + +### How do I run specific tests? + +If `-goblin.run=$REGES` is supplied to the `go test` command then only tests that match the supplied regex will run + + +TODO: +----- + +We do have a couple of [issues](https://github.com/franela/goblin/issues) pending we'll be addressing soon. But feel free to +contribute and send us PRs (with tests please :smile:). + +Contributions: +------------ + +Special thanks to [Leandro Reox](https://github.com/leandroreox) (Leitan) for the goblin logo. diff --git a/vendor/github.com/franela/goblin/assertions.go b/vendor/github.com/franela/goblin/assertions.go new file mode 100644 index 000000000..5ccae7daf --- /dev/null +++ b/vendor/github.com/franela/goblin/assertions.go @@ -0,0 +1,59 @@ +package goblin + +import ( + "fmt" + "reflect" + "strings" +) + +type Assertion struct { + src interface{} + fail func(interface{}) +} + +func objectsAreEqual(a, b interface{}) bool { + if reflect.TypeOf(a) != reflect.TypeOf(b) { + return false + } + + if reflect.DeepEqual(a, b) { + return true + } + + if fmt.Sprintf("%#v", a) == fmt.Sprintf("%#v", b) { + return true + } + + return false +} + +func formatMessages(messages ...string) string { + if len(messages) > 0 { + return ", " + strings.Join(messages, " ") + } + return "" +} + +func (a *Assertion) Eql(dst interface{}) { + a.Equal(dst) +} + +func (a *Assertion) Equal(dst interface{}) { + if !objectsAreEqual(a.src, dst) { + a.fail(fmt.Sprintf("%#v %s %#v", a.src, "does not equal", dst)) + } +} + +func (a *Assertion) IsTrue(messages ...string) { + if !objectsAreEqual(a.src, true) { + message := fmt.Sprintf("%v %s%s", a.src, "expected false to be truthy", formatMessages(messages...)) + a.fail(message) + } +} + +func (a *Assertion) IsFalse(messages ...string) { + if !objectsAreEqual(a.src, false) { + message := fmt.Sprintf("%v %s%s", a.src, "expected true to be falsey", formatMessages(messages...)) + a.fail(message) + } +} diff --git a/vendor/github.com/franela/goblin/goblin.go b/vendor/github.com/franela/goblin/goblin.go new file mode 100644 index 000000000..e029548bc --- /dev/null +++ b/vendor/github.com/franela/goblin/goblin.go @@ -0,0 +1,294 @@ +package goblin + +import ( + "flag" + "fmt" + "regexp" + "runtime" + "sync" + "testing" + "time" +) + +type Done func(error ...interface{}) + +type Runnable interface { + run(*G) bool +} + +func (g *G) Describe(name string, h func()) { + d := &Describe{name: name, h: h, parent: g.parent} + + if d.parent != nil { + d.parent.children = append(d.parent.children, Runnable(d)) + } + + g.parent = d + + h() + + g.parent = d.parent + + if g.parent == nil && d.hasTests { + g.reporter.begin() + if d.run(g) { + g.t.Fail() + } + g.reporter.end() + } +} + +type Describe struct { + name string + h func() + children []Runnable + befores []func() + afters []func() + afterEach []func() + beforeEach []func() + hasTests bool + parent *Describe +} + +func (d *Describe) runBeforeEach() { + if d.parent != nil { + d.parent.runBeforeEach() + } + + for _, b := range d.beforeEach { + b() + } +} + +func (d *Describe) runAfterEach() { + + if d.parent != nil { + d.parent.runAfterEach() + } + + for _, a := range d.afterEach { + a() + } +} + +func (d *Describe) run(g *G) bool { + failed := false + if d.hasTests { + g.reporter.beginDescribe(d.name) + + for _, b := range d.befores { + b() + } + + for _, r := range d.children { + if r.run(g) { + failed = true + } + } + + for _, a := range d.afters { + a() + } + + g.reporter.endDescribe() + } + + return failed +} + +type Failure struct { + stack []string + testName string + message string +} + +type It struct { + h interface{} + name string + parent *Describe + failure *Failure + reporter Reporter + isAsync bool +} + +func (it *It) run(g *G) bool { + g.currentIt = it + + if it.h == nil { + g.reporter.itIsPending(it.name) + return false + } + //TODO: should handle errors for beforeEach + it.parent.runBeforeEach() + + runIt(g, it.h) + + it.parent.runAfterEach() + + failed := false + if it.failure != nil { + failed = true + } + + if failed { + g.reporter.itFailed(it.name) + g.reporter.failure(it.failure) + } else { + g.reporter.itPassed(it.name) + } + return failed +} + +func (it *It) failed(msg string, stack []string) { + it.failure = &Failure{stack: stack, message: msg, testName: it.parent.name + " " + it.name} +} + +func parseFlags() { + //Flag parsing + flag.Parse() + if *regexParam != "" { + runRegex = regexp.MustCompile(*regexParam) + } else { + runRegex = nil + } +} + +var timeout = flag.Duration("goblin.timeout", 5*time.Second, "Sets default timeouts for all tests") +var isTty = flag.Bool("goblin.tty", true, "Sets the default output format (color / monochrome)") +var regexParam = flag.String("goblin.run", "", "Runs only tests which match the supplied regex") +var runRegex *regexp.Regexp + +func init() { + parseFlags() +} + +func Goblin(t *testing.T, arguments ...string) *G { + g := &G{t: t, timeout: *timeout} + var fancy TextFancier + if *isTty { + fancy = &TerminalFancier{} + } else { + fancy = &Monochrome{} + } + + g.reporter = Reporter(&DetailedReporter{fancy: fancy}) + return g +} + +func runIt(g *G, h interface{}) { + defer timeTrack(time.Now(), g) + g.mutex.Lock() + g.timedOut = false + g.mutex.Unlock() + g.shouldContinue = make(chan bool) + if call, ok := h.(func()); ok { + // the test is synchronous + go func(c chan bool) { call(); c <- true }(g.shouldContinue) + } else if call, ok := h.(func(Done)); ok { + doneCalled := 0 + go func(c chan bool) { + call(func(msg ...interface{}) { + if len(msg) > 0 { + g.Fail(msg) + } else { + doneCalled++ + if doneCalled > 1 { + g.Fail("Done called multiple times") + } + c <- true + } + }) + }(g.shouldContinue) + } else { + panic("Not implemented.") + } + select { + case <-g.shouldContinue: + case <-time.After(g.timeout): + //Set to nil as it shouldn't continue + g.shouldContinue = nil + g.timedOut = true + g.Fail("Test exceeded " + fmt.Sprintf("%s", g.timeout)) + } +} + +type G struct { + t *testing.T + parent *Describe + currentIt *It + timeout time.Duration + reporter Reporter + timedOut bool + shouldContinue chan bool + mutex sync.Mutex +} + +func (g *G) SetReporter(r Reporter) { + g.reporter = r +} + +func (g *G) It(name string, h ...interface{}) { + if matchesRegex(name) { + it := &It{name: name, parent: g.parent, reporter: g.reporter} + notifyParents(g.parent) + if len(h) > 0 { + it.h = h[0] + } + g.parent.children = append(g.parent.children, Runnable(it)) + } +} + +func matchesRegex(value string) bool { + if runRegex != nil { + return runRegex.MatchString(value) + } + return true +} + +func notifyParents(d *Describe) { + d.hasTests = true + if d.parent != nil { + notifyParents(d.parent) + } +} + +func (g *G) Before(h func()) { + g.parent.befores = append(g.parent.befores, h) +} + +func (g *G) BeforeEach(h func()) { + g.parent.beforeEach = append(g.parent.beforeEach, h) +} + +func (g *G) After(h func()) { + g.parent.afters = append(g.parent.afters, h) +} + +func (g *G) AfterEach(h func()) { + g.parent.afterEach = append(g.parent.afterEach, h) +} + +func (g *G) Assert(src interface{}) *Assertion { + return &Assertion{src: src, fail: g.Fail} +} + +func timeTrack(start time.Time, g *G) { + g.reporter.itTook(time.Since(start)) +} + +func (g *G) Fail(error interface{}) { + //Skips 7 stacks due to the functions between the stack and the test + stack := ResolveStack(4) + message := fmt.Sprintf("%v", error) + g.currentIt.failed(message, stack) + if g.shouldContinue != nil { + g.shouldContinue <- true + } + g.mutex.Lock() + defer g.mutex.Unlock() + if !g.timedOut { + //Stop test function execution + runtime.Goexit() + } + +} diff --git a/vendor/github.com/franela/goblin/goblin_logo.jpg b/vendor/github.com/franela/goblin/goblin_logo.jpg new file mode 100644 index 000000000..44534f297 Binary files /dev/null and b/vendor/github.com/franela/goblin/goblin_logo.jpg differ diff --git a/vendor/github.com/franela/goblin/goblin_output.png b/vendor/github.com/franela/goblin/goblin_output.png new file mode 100644 index 000000000..be3c9ea7a Binary files /dev/null and b/vendor/github.com/franela/goblin/goblin_output.png differ diff --git a/vendor/github.com/franela/goblin/mono_reporter.go b/vendor/github.com/franela/goblin/mono_reporter.go new file mode 100644 index 000000000..04d6e5e3a --- /dev/null +++ b/vendor/github.com/franela/goblin/mono_reporter.go @@ -0,0 +1,26 @@ +package goblin + +import () + +type Monochrome struct { +} + +func (self *Monochrome) Red(text string) string { + return "!" + text +} + +func (self *Monochrome) Gray(text string) string { + return text +} + +func (self *Monochrome) Cyan(text string) string { + return text +} + +func (self *Monochrome) WithCheck(text string) string { + return ">>>" + text +} + +func (self *Monochrome) Green(text string) string { + return text +} diff --git a/vendor/github.com/franela/goblin/reporting.go b/vendor/github.com/franela/goblin/reporting.go new file mode 100644 index 000000000..1d67d662d --- /dev/null +++ b/vendor/github.com/franela/goblin/reporting.go @@ -0,0 +1,137 @@ +package goblin + +import ( + "fmt" + "strconv" + "strings" + "time" +) + +type Reporter interface { + beginDescribe(string) + endDescribe() + begin() + end() + failure(*Failure) + itTook(time.Duration) + itFailed(string) + itPassed(string) + itIsPending(string) +} + +type TextFancier interface { + Red(text string) string + Gray(text string) string + Cyan(text string) string + Green(text string) string + WithCheck(text string) string +} + +type DetailedReporter struct { + level, failed, passed, pending int + failures []*Failure + executionTime, totalExecutionTime time.Duration + fancy TextFancier +} + +func (r *DetailedReporter) SetTextFancier(f TextFancier) { + r.fancy = f +} + +type TerminalFancier struct { +} + +func (self *TerminalFancier) Red(text string) string { + return "\033[31m" + text + "\033[0m" +} + +func (self *TerminalFancier) Gray(text string) string { + return "\033[90m" + text + "\033[0m" +} + +func (self *TerminalFancier) Cyan(text string) string { + return "\033[36m" + text + "\033[0m" +} + +func (self *TerminalFancier) Green(text string) string { + return "\033[32m" + text + "\033[0m" +} + +func (self *TerminalFancier) WithCheck(text string) string { + return "\033[32m\u2713\033[0m " + text +} + +func (r *DetailedReporter) getSpace() string { + return strings.Repeat(" ", (r.level+1)*2) +} + +func (r *DetailedReporter) failure(failure *Failure) { + r.failures = append(r.failures, failure) +} + +func (r *DetailedReporter) print(text string) { + fmt.Printf("%v%v\n", r.getSpace(), text) +} + +func (r *DetailedReporter) printWithCheck(text string) { + fmt.Printf("%v%v\n", r.getSpace(), r.fancy.WithCheck(text)) +} + +func (r *DetailedReporter) beginDescribe(name string) { + fmt.Println("") + r.print(name) + r.level++ +} + +func (r *DetailedReporter) endDescribe() { + r.level-- +} + +func (r *DetailedReporter) itTook(duration time.Duration) { + r.executionTime = duration + r.totalExecutionTime += duration +} + +func (r *DetailedReporter) itFailed(name string) { + r.failed++ + r.print(r.fancy.Red(strconv.Itoa(r.failed) + ") " + name)) +} + +func (r *DetailedReporter) itPassed(name string) { + r.passed++ + r.printWithCheck(r.fancy.Gray(name)) +} + +func (r *DetailedReporter) itIsPending(name string) { + r.pending++ + r.print(r.fancy.Cyan("- " + name)) +} + +func (r *DetailedReporter) begin() { +} + +func (r *DetailedReporter) end() { + comp := fmt.Sprintf("%d tests complete", r.passed) + t := fmt.Sprintf("(%d ms)", r.totalExecutionTime/time.Millisecond) + + //fmt.Printf("\n\n \033[32m%d tests complete\033[0m \033[90m(%d ms)\033[0m\n", r.passed, r.totalExecutionTime/time.Millisecond) + fmt.Printf("\n\n %v %v\n", r.fancy.Green(comp), r.fancy.Gray(t)) + + if r.pending > 0 { + pend := fmt.Sprintf("%d test(s) pending", r.pending) + fmt.Printf(" %v\n\n", r.fancy.Cyan(pend)) + } + + if len(r.failures) > 0 { + fmt.Printf("%s \n\n", r.fancy.Red(fmt.Sprintf(" %d tests failed:", len(r.failures)))) + + } + + for i, failure := range r.failures { + fmt.Printf(" %d) %s:\n\n", i+1, failure.testName) + fmt.Printf(" %s\n", r.fancy.Red(failure.message)) + for _, stackItem := range failure.stack { + fmt.Printf(" %s\n", r.fancy.Gray(stackItem)) + } + } +} diff --git a/vendor/github.com/franela/goblin/resolver.go b/vendor/github.com/franela/goblin/resolver.go new file mode 100644 index 000000000..125fcec9c --- /dev/null +++ b/vendor/github.com/franela/goblin/resolver.go @@ -0,0 +1,21 @@ +package goblin + +import ( + "runtime/debug" + "strings" +) + +func ResolveStack(skip int) []string { + return cleanStack(debug.Stack(), skip) +} + +func cleanStack(stack []byte, skip int) []string { + arrayStack := strings.Split(string(stack), "\n") + var finalStack []string + for i := skip; i < len(arrayStack); i++ { + if strings.Contains(arrayStack[i], ".go") { + finalStack = append(finalStack, arrayStack[i]) + } + } + return finalStack +} diff --git a/vendor/github.com/getsentry/raven-go/Dockerfile.test b/vendor/github.com/getsentry/raven-go/Dockerfile.test deleted file mode 100644 index e0aa037b1..000000000 --- a/vendor/github.com/getsentry/raven-go/Dockerfile.test +++ /dev/null @@ -1,11 +0,0 @@ -FROM golang:1.4 - -RUN mkdir -p /go/src/github.com/getsentry/raven-go -WORKDIR /go/src/github.com/getsentry/raven-go -ENV GOPATH /go - -RUN go install -race std && go get golang.org/x/tools/cmd/cover - -COPY . /go/src/github.com/getsentry/raven-go - -CMD ["./runtests.sh"] diff --git a/vendor/github.com/getsentry/raven-go/README.md b/vendor/github.com/getsentry/raven-go/README.md deleted file mode 100644 index a5373ce87..000000000 --- a/vendor/github.com/getsentry/raven-go/README.md +++ /dev/null @@ -1,12 +0,0 @@ -# raven [![Build Status](https://travis-ci.org/getsentry/raven-go.png?branch=master)](https://travis-ci.org/getsentry/raven-go) - -raven is a Go client for the [Sentry](https://github.com/getsentry/sentry) -event/error logging system. - -[**Documentation**](http://godoc.org/github.com/getsentry/raven-go). - -## Installation - -```text -go get github.com/getsentry/raven-go -``` diff --git a/vendor/github.com/getsentry/raven-go/client.go b/vendor/github.com/getsentry/raven-go/client.go deleted file mode 100644 index f514c7456..000000000 --- a/vendor/github.com/getsentry/raven-go/client.go +++ /dev/null @@ -1,683 +0,0 @@ -// Package raven implements a client for the Sentry error logging service. -package raven - -import ( - "bytes" - "compress/zlib" - "crypto/rand" - "encoding/base64" - "encoding/hex" - "encoding/json" - "errors" - "fmt" - "io" - "io/ioutil" - "net/http" - "net/url" - "os" - "runtime" - "strings" - "sync" - "time" -) - -const ( - userAgent = "raven-go/1.0" - timestampFormat = `"2006-01-02T15:04:05"` -) - -var ( - ErrPacketDropped = errors.New("raven: packet dropped") - ErrUnableToUnmarshalJSON = errors.New("raven: unable to unmarshal JSON") - ErrMissingUser = errors.New("raven: dsn missing public key and/or password") - ErrMissingPrivateKey = errors.New("raven: dsn missing private key") - ErrMissingProjectID = errors.New("raven: dsn missing project id") -) - -type Severity string - -// http://docs.python.org/2/howto/logging.html#logging-levels -const ( - DEBUG = Severity("debug") - INFO = Severity("info") - WARNING = Severity("warning") - ERROR = Severity("error") - FATAL = Severity("fatal") -) - -type Timestamp time.Time - -func (t Timestamp) MarshalJSON() ([]byte, error) { - return []byte(time.Time(t).UTC().Format(timestampFormat)), nil -} - -func (timestamp *Timestamp) UnmarshalJSON(data []byte) error { - t, err := time.Parse(timestampFormat, string(data)) - if err != nil { - return err - } - - *timestamp = Timestamp(t) - return nil -} - -// An Interface is a Sentry interface that will be serialized as JSON. -// It must implement json.Marshaler or use json struct tags. -type Interface interface { - // The Sentry class name. Example: sentry.interfaces.Stacktrace - Class() string -} - -type Culpriter interface { - Culprit() string -} - -type Transport interface { - Send(url, authHeader string, packet *Packet) error -} - -type outgoingPacket struct { - packet *Packet - ch chan error -} - -type Tag struct { - Key string - Value string -} - -type Tags []Tag - -func (tag *Tag) MarshalJSON() ([]byte, error) { - return json.Marshal([2]string{tag.Key, tag.Value}) -} - -func (t *Tag) UnmarshalJSON(data []byte) error { - var tag [2]string - if err := json.Unmarshal(data, &tag); err != nil { - return err - } - *t = Tag{tag[0], tag[1]} - return nil -} - -func (t *Tags) UnmarshalJSON(data []byte) error { - var tags []Tag - - switch data[0] { - case '[': - // Unmarshal into []Tag - if err := json.Unmarshal(data, &tags); err != nil { - return err - } - case '{': - // Unmarshal into map[string]string - tagMap := make(map[string]string) - if err := json.Unmarshal(data, &tagMap); err != nil { - return err - } - - // Convert to []Tag - for k, v := range tagMap { - tags = append(tags, Tag{k, v}) - } - default: - return ErrUnableToUnmarshalJSON - } - - *t = tags - return nil -} - -// http://sentry.readthedocs.org/en/latest/developer/client/index.html#building-the-json-packet -type Packet struct { - // Required - Message string `json:"message"` - - // Required, set automatically by Client.Send/Report via Packet.Init if blank - EventID string `json:"event_id"` - Project string `json:"project"` - Timestamp Timestamp `json:"timestamp"` - Level Severity `json:"level"` - Logger string `json:"logger"` - - // Optional - Platform string `json:"platform,omitempty"` - Culprit string `json:"culprit,omitempty"` - ServerName string `json:"server_name,omitempty"` - Release string `json:"release,omitempty"` - Tags Tags `json:"tags,omitempty"` - Modules []map[string]string `json:"modules,omitempty"` - Extra map[string]interface{} `json:"extra,omitempty"` - - Interfaces []Interface `json:"-"` -} - -// NewPacket constructs a packet with the specified message and interfaces. -func NewPacket(message string, interfaces ...Interface) *Packet { - extra := map[string]interface{}{ - "runtime.Version": runtime.Version(), - "runtime.NumCPU": runtime.NumCPU(), - "runtime.GOMAXPROCS": runtime.GOMAXPROCS(0), // 0 just returns the current value - "runtime.NumGoroutine": runtime.NumGoroutine(), - } - return &Packet{ - Message: message, - Interfaces: interfaces, - Extra: extra, - } -} - -// Init initializes required fields in a packet. It is typically called by -// Client.Send/Report automatically. -func (packet *Packet) Init(project string) error { - if packet.Project == "" { - packet.Project = project - } - if packet.EventID == "" { - var err error - packet.EventID, err = uuid() - if err != nil { - return err - } - } - if time.Time(packet.Timestamp).IsZero() { - packet.Timestamp = Timestamp(time.Now()) - } - if packet.Level == "" { - packet.Level = ERROR - } - if packet.Logger == "" { - packet.Logger = "root" - } - if packet.ServerName == "" { - packet.ServerName = hostname - } - if packet.Platform == "" { - packet.Platform = "go" - } - - if packet.Culprit == "" { - for _, inter := range packet.Interfaces { - if c, ok := inter.(Culpriter); ok { - packet.Culprit = c.Culprit() - if packet.Culprit != "" { - break - } - } - } - } - - return nil -} - -func (packet *Packet) AddTags(tags map[string]string) { - for k, v := range tags { - packet.Tags = append(packet.Tags, Tag{k, v}) - } -} - -func uuid() (string, error) { - id := make([]byte, 16) - _, err := io.ReadFull(rand.Reader, id) - if err != nil { - return "", err - } - id[6] &= 0x0F // clear version - id[6] |= 0x40 // set version to 4 (random uuid) - id[8] &= 0x3F // clear variant - id[8] |= 0x80 // set to IETF variant - return hex.EncodeToString(id), nil -} - -func (packet *Packet) JSON() []byte { - packetJSON, _ := json.Marshal(packet) - - interfaces := make(map[string]Interface, len(packet.Interfaces)) - for _, inter := range packet.Interfaces { - interfaces[inter.Class()] = inter - } - - if len(interfaces) > 0 { - interfaceJSON, _ := json.Marshal(interfaces) - packetJSON[len(packetJSON)-1] = ',' - packetJSON = append(packetJSON, interfaceJSON[1:]...) - } - - return packetJSON -} - -type context struct { - user *User - http *Http - tags map[string]string -} - -func (c *context) SetUser(u *User) { c.user = u } -func (c *context) SetHttp(h *Http) { c.http = h } -func (c *context) SetTags(t map[string]string) { - if c.tags == nil { - c.tags = make(map[string]string) - } - for k, v := range t { - c.tags[k] = v - } -} -func (c *context) Clear() { - c.user = nil - c.http = nil - c.tags = nil -} - -// Return a list of interfaces to be used in appending with the rest -func (c *context) interfaces() []Interface { - len, i := 0, 0 - if c.user != nil { - len++ - } - if c.http != nil { - len++ - } - interfaces := make([]Interface, len) - if c.user != nil { - interfaces[i] = c.user - i++ - } - if c.http != nil { - interfaces[i] = c.http - i++ - } - return interfaces -} - -// The maximum number of packets that will be buffered waiting to be delivered. -// Packets will be dropped if the buffer is full. Used by NewClient. -var MaxQueueBuffer = 100 - -func newClient(tags map[string]string) *Client { - client := &Client{ - Transport: &HTTPTransport{}, - Tags: tags, - context: &context{}, - queue: make(chan *outgoingPacket, MaxQueueBuffer), - } - go client.worker() - client.SetDSN(os.Getenv("SENTRY_DSN")) - return client -} - -// New constructs a new Sentry client instance -func New(dsn string) (*Client, error) { - client := newClient(nil) - return client, client.SetDSN(dsn) -} - -// NewWithTags constructs a new Sentry client instance with default tags. -func NewWithTags(dsn string, tags map[string]string) (*Client, error) { - client := newClient(tags) - return client, client.SetDSN(dsn) -} - -// NewClient constructs a Sentry client and spawns a background goroutine to -// handle packets sent by Client.Report. -// -// Deprecated: use New and NewWithTags instead -func NewClient(dsn string, tags map[string]string) (*Client, error) { - client := newClient(tags) - return client, client.SetDSN(dsn) -} - -// Client encapsulates a connection to a Sentry server. It must be initialized -// by calling NewClient. Modification of fields concurrently with Send or after -// calling Report for the first time is not thread-safe. -type Client struct { - Tags map[string]string - - Transport Transport - - // DropHandler is called when a packet is dropped because the buffer is full. - DropHandler func(*Packet) - - // Context that will get appending to all packets - context *context - - mu sync.RWMutex - url string - projectID string - authHeader string - release string - queue chan *outgoingPacket - - // A WaitGroup to keep track of all currently in-progress captures - // This is intended to be used with Client.Wait() to assure that - // all messages have been transported before exiting the process. - wg sync.WaitGroup -} - -// Initialize a default *Client instance -var DefaultClient = newClient(nil) - -// SetDSN updates a client with a new DSN. It safe to call after and -// concurrently with calls to Report and Send. -func (client *Client) SetDSN(dsn string) error { - if dsn == "" { - return nil - } - - client.mu.Lock() - defer client.mu.Unlock() - - uri, err := url.Parse(dsn) - if err != nil { - return err - } - - if uri.User == nil { - return ErrMissingUser - } - publicKey := uri.User.Username() - secretKey, ok := uri.User.Password() - if !ok { - return ErrMissingPrivateKey - } - uri.User = nil - - if idx := strings.LastIndex(uri.Path, "/"); idx != -1 { - client.projectID = uri.Path[idx+1:] - uri.Path = uri.Path[:idx+1] + "api/" + client.projectID + "/store/" - } - if client.projectID == "" { - return ErrMissingProjectID - } - - client.url = uri.String() - - client.authHeader = fmt.Sprintf("Sentry sentry_version=4, sentry_key=%s, sentry_secret=%s", publicKey, secretKey) - - return nil -} - -// Sets the DSN for the default *Client instance -func SetDSN(dsn string) error { return DefaultClient.SetDSN(dsn) } - -// SetRelease sets the "release" tag. -func (client *Client) SetRelease(release string) { - client.mu.Lock() - defer client.mu.Unlock() - client.release = release -} - -// SetRelease sets the "release" tag on the default *Client -func SetRelease(release string) { DefaultClient.SetRelease(release) } - -func (client *Client) worker() { - for outgoingPacket := range client.queue { - - client.mu.RLock() - url, authHeader := client.url, client.authHeader - client.mu.RUnlock() - - outgoingPacket.ch <- client.Transport.Send(url, authHeader, outgoingPacket.packet) - client.wg.Done() - } -} - -// Capture asynchronously delivers a packet to the Sentry server. It is a no-op -// when client is nil. A channel is provided if it is important to check for a -// send's success. -func (client *Client) Capture(packet *Packet, captureTags map[string]string) (eventID string, ch chan error) { - if client == nil { - return - } - - // Keep track of all running Captures so that we can wait for them all to finish - // *Must* call client.wg.Done() on any path that indicates that an event was - // finished being acted upon, whether success or failure - client.wg.Add(1) - - ch = make(chan error, 1) - - // Merge capture tags and client tags - packet.AddTags(captureTags) - packet.AddTags(client.Tags) - packet.AddTags(client.context.tags) - - // Initialize any required packet fields - client.mu.RLock() - projectID := client.projectID - release := client.release - client.mu.RUnlock() - - err := packet.Init(projectID) - if err != nil { - ch <- err - client.wg.Done() - return - } - packet.Release = release - - outgoingPacket := &outgoingPacket{packet, ch} - - select { - case client.queue <- outgoingPacket: - default: - // Send would block, drop the packet - if client.DropHandler != nil { - client.DropHandler(packet) - } - ch <- ErrPacketDropped - client.wg.Done() - } - - return packet.EventID, ch -} - -// Capture asynchronously delivers a packet to the Sentry server with the default *Client. -// It is a no-op when client is nil. A channel is provided if it is important to check for a -// send's success. -func Capture(packet *Packet, captureTags map[string]string) (eventID string, ch chan error) { - return DefaultClient.Capture(packet, captureTags) -} - -// CaptureMessage formats and delivers a string message to the Sentry server. -func (client *Client) CaptureMessage(message string, tags map[string]string, interfaces ...Interface) string { - if client == nil { - return "" - } - - packet := NewPacket(message, append(append(interfaces, client.context.interfaces()...), &Message{message, nil})...) - eventID, _ := client.Capture(packet, tags) - - return eventID -} - -// CaptureMessage formats and delivers a string message to the Sentry server with the default *Client -func CaptureMessage(message string, tags map[string]string, interfaces ...Interface) string { - return DefaultClient.CaptureMessage(message, tags, interfaces...) -} - -// CaptureMessageAndWait is identical to CaptureMessage except it blocks and waits for the message to be sent. -func (client *Client) CaptureMessageAndWait(message string, tags map[string]string, interfaces ...Interface) string { - if client == nil { - return "" - } - - packet := NewPacket(message, append(append(interfaces, client.context.interfaces()...), &Message{message, nil})...) - eventID, ch := client.Capture(packet, tags) - <-ch - - return eventID -} - -// CaptureMessageAndWait is identical to CaptureMessage except it blocks and waits for the message to be sent. -func CaptureMessageAndWait(message string, tags map[string]string, interfaces ...Interface) string { - return DefaultClient.CaptureMessageAndWait(message, tags, interfaces...) -} - -// CaptureErrors formats and delivers an error to the Sentry server. -// Adds a stacktrace to the packet, excluding the call to this method. -func (client *Client) CaptureError(err error, tags map[string]string, interfaces ...Interface) string { - if client == nil { - return "" - } - - packet := NewPacket(err.Error(), append(append(interfaces, client.context.interfaces()...), NewException(err, NewStacktrace(1, 3, nil)))...) - eventID, _ := client.Capture(packet, tags) - - return eventID -} - -// CaptureErrors formats and delivers an error to the Sentry server using the default *Client. -// Adds a stacktrace to the packet, excluding the call to this method. -func CaptureError(err error, tags map[string]string, interfaces ...Interface) string { - return DefaultClient.CaptureError(err, tags, interfaces...) -} - -// CaptureErrorAndWait is identical to CaptureError, except it blocks and assures that the event was sent -func (client *Client) CaptureErrorAndWait(err error, tags map[string]string, interfaces ...Interface) string { - if client == nil { - return "" - } - - packet := NewPacket(err.Error(), append(append(interfaces, client.context.interfaces()...), NewException(err, NewStacktrace(1, 3, nil)))...) - eventID, ch := client.Capture(packet, tags) - <-ch - - return eventID -} - -// CaptureErrorAndWait is identical to CaptureError, except it blocks and assures that the event was sent -func CaptureErrorAndWait(err error, tags map[string]string, interfaces ...Interface) string { - return DefaultClient.CaptureErrorAndWait(err, tags, interfaces...) -} - -// CapturePanic calls f and then recovers and reports a panic to the Sentry server if it occurs. -func (client *Client) CapturePanic(f func(), tags map[string]string, interfaces ...Interface) { - // Note: This doesn't need to check for client, because we still want to go through the defer/recover path - // Down the line, Capture will be noop'd, so while this does a _tiny_ bit of overhead constructing the - // *Packet just to be thrown away, this should not be the normal case. Could be refactored to - // be completely noop though if we cared. - defer func() { - var packet *Packet - switch rval := recover().(type) { - case nil: - return - case error: - packet = NewPacket(rval.Error(), append(append(interfaces, client.context.interfaces()...), NewException(rval, NewStacktrace(2, 3, nil)))...) - default: - rvalStr := fmt.Sprint(rval) - packet = NewPacket(rvalStr, append(append(interfaces, client.context.interfaces()...), NewException(errors.New(rvalStr), NewStacktrace(2, 3, nil)))...) - } - - client.Capture(packet, tags) - }() - - f() -} - -// CapturePanic calls f and then recovers and reports a panic to the Sentry server if it occurs. -func CapturePanic(f func(), tags map[string]string, interfaces ...Interface) { - DefaultClient.CapturePanic(f, tags, interfaces...) -} - -func (client *Client) Close() { - close(client.queue) -} - -func Close() { DefaultClient.Close() } - -// Wait blocks and waits for all events to finish being sent to Sentry server -func (client *Client) Wait() { - client.wg.Wait() -} - -// Wait blocks and waits for all events to finish being sent to Sentry server -func Wait() { DefaultClient.Wait() } - -func (client *Client) URL() string { - client.mu.RLock() - defer client.mu.RUnlock() - - return client.url -} - -func URL() string { return DefaultClient.URL() } - -func (client *Client) ProjectID() string { - client.mu.RLock() - defer client.mu.RUnlock() - - return client.projectID -} - -func ProjectID() string { return DefaultClient.ProjectID() } - -func (client *Client) Release() string { - client.mu.RLock() - defer client.mu.RUnlock() - - return client.release -} - -func Release() string { return DefaultClient.Release() } - -func (c *Client) SetUserContext(u *User) { c.context.SetUser(u) } -func (c *Client) SetHttpContext(h *Http) { c.context.SetHttp(h) } -func (c *Client) SetTagsContext(t map[string]string) { c.context.SetTags(t) } -func (c *Client) ClearContext() { c.context.Clear() } - -func SetUserContext(u *User) { DefaultClient.SetUserContext(u) } -func SetHttpContext(h *Http) { DefaultClient.SetHttpContext(h) } -func SetTagsContext(t map[string]string) { DefaultClient.SetTagsContext(t) } -func ClearContext() { DefaultClient.ClearContext() } - -// HTTPTransport is the default transport, delivering packets to Sentry via the -// HTTP API. -type HTTPTransport struct { - Http http.Client -} - -func (t *HTTPTransport) Send(url, authHeader string, packet *Packet) error { - if url == "" { - return nil - } - - body, contentType := serializedPacket(packet) - req, _ := http.NewRequest("POST", url, body) - req.Header.Set("X-Sentry-Auth", authHeader) - req.Header.Set("User-Agent", userAgent) - req.Header.Set("Content-Type", contentType) - res, err := t.Http.Do(req) - if err != nil { - return err - } - io.Copy(ioutil.Discard, res.Body) - res.Body.Close() - if res.StatusCode != 200 { - return fmt.Errorf("raven: got http status %d", res.StatusCode) - } - return nil -} - -func serializedPacket(packet *Packet) (r io.Reader, contentType string) { - packetJSON := packet.JSON() - - // Only deflate/base64 the packet if it is bigger than 1KB, as there is - // overhead. - if len(packetJSON) > 1000 { - buf := &bytes.Buffer{} - b64 := base64.NewEncoder(base64.StdEncoding, buf) - deflate, _ := zlib.NewWriterLevel(b64, zlib.BestCompression) - deflate.Write(packetJSON) - deflate.Close() - b64.Close() - return buf, "application/octet-stream" - } - return bytes.NewReader(packetJSON), "application/json" -} - -var hostname string - -func init() { - hostname, _ = os.Hostname() -} diff --git a/vendor/github.com/getsentry/raven-go/client_test.go b/vendor/github.com/getsentry/raven-go/client_test.go deleted file mode 100644 index 632c8d4a0..000000000 --- a/vendor/github.com/getsentry/raven-go/client_test.go +++ /dev/null @@ -1,150 +0,0 @@ -package raven - -import ( - "encoding/json" - "reflect" - "testing" - "time" -) - -type testInterface struct{} - -func (t *testInterface) Class() string { return "sentry.interfaces.Test" } -func (t *testInterface) Culprit() string { return "codez" } - -func TestPacketJSON(t *testing.T) { - packet := &Packet{ - Project: "1", - EventID: "2", - Platform: "linux", - Culprit: "caused_by", - ServerName: "host1", - Release: "721e41770371db95eee98ca2707686226b993eda", - Message: "test", - Timestamp: Timestamp(time.Date(2000, 01, 01, 0, 0, 0, 0, time.UTC)), - Level: ERROR, - Logger: "com.getsentry.raven-go.logger-test-packet-json", - Tags: []Tag{Tag{"foo", "bar"}}, - Interfaces: []Interface{&Message{Message: "foo"}}, - } - - packet.AddTags(map[string]string{"foo": "foo"}) - packet.AddTags(map[string]string{"baz": "buzz"}) - - expected := `{"message":"test","event_id":"2","project":"1","timestamp":"2000-01-01T00:00:00","level":"error","logger":"com.getsentry.raven-go.logger-test-packet-json","platform":"linux","culprit":"caused_by","server_name":"host1","release":"721e41770371db95eee98ca2707686226b993eda","tags":[["foo","bar"],["foo","foo"],["baz","buzz"]],"logentry":{"message":"foo"}}` - actual := string(packet.JSON()) - - if actual != expected { - t.Errorf("incorrect json; got %s, want %s", actual, expected) - } -} - -func TestPacketInit(t *testing.T) { - packet := &Packet{Message: "a", Interfaces: []Interface{&testInterface{}}} - packet.Init("foo") - - if packet.Project != "foo" { - t.Error("incorrect Project:", packet.Project) - } - if packet.Culprit != "codez" { - t.Error("incorrect Culprit:", packet.Culprit) - } - if packet.ServerName == "" { - t.Errorf("ServerName should not be empty") - } - if packet.Level != ERROR { - t.Errorf("incorrect Level: got %d, want %d", packet.Level, ERROR) - } - if packet.Logger != "root" { - t.Errorf("incorrect Logger: got %s, want %s", packet.Logger, "root") - } - if time.Time(packet.Timestamp).IsZero() { - t.Error("Timestamp is zero") - } - if len(packet.EventID) != 32 { - t.Error("incorrect EventID:", packet.EventID) - } -} - -func TestSetDSN(t *testing.T) { - client := &Client{} - client.SetDSN("https://u:p@example.com/sentry/1") - - if client.url != "https://example.com/sentry/api/1/store/" { - t.Error("incorrect url:", client.url) - } - if client.projectID != "1" { - t.Error("incorrect projectID:", client.projectID) - } - if client.authHeader != "Sentry sentry_version=4, sentry_key=u, sentry_secret=p" { - t.Error("incorrect authHeader:", client.authHeader) - } -} - -func TestUnmarshalTag(t *testing.T) { - actual := new(Tag) - if err := json.Unmarshal([]byte(`["foo","bar"]`), actual); err != nil { - t.Fatal("unable to decode JSON:", err) - } - - expected := &Tag{Key: "foo", Value: "bar"} - if !reflect.DeepEqual(actual, expected) { - t.Errorf("incorrect Tag: wanted '%+v' and got '%+v'", expected, actual) - } -} - -func TestUnmarshalTags(t *testing.T) { - tests := []struct { - Input string - Expected Tags - }{ - { - `{"foo":"bar"}`, - Tags{Tag{Key: "foo", Value: "bar"}}, - }, - { - `[["foo","bar"],["bar","baz"]]`, - Tags{Tag{Key: "foo", Value: "bar"}, Tag{Key: "bar", Value: "baz"}}, - }, - } - - for _, test := range tests { - var actual Tags - if err := json.Unmarshal([]byte(test.Input), &actual); err != nil { - t.Fatal("unable to decode JSON:", err) - } - - if !reflect.DeepEqual(actual, test.Expected) { - t.Errorf("incorrect Tags: wanted '%+v' and got '%+v'", test.Expected, actual) - } - } -} - -func TestMarshalTimestamp(t *testing.T) { - timestamp := Timestamp(time.Date(2000, 01, 02, 03, 04, 05, 0, time.UTC)) - expected := `"2000-01-02T03:04:05"` - - actual, err := json.Marshal(timestamp) - if err != nil { - t.Error(err) - } - - if string(actual) != expected { - t.Errorf("incorrect string; got %s, want %s", actual, expected) - } -} - -func TestUnmarshalTimestamp(t *testing.T) { - timestamp := `"2000-01-02T03:04:05"` - expected := Timestamp(time.Date(2000, 01, 02, 03, 04, 05, 0, time.UTC)) - - var actual Timestamp - err := json.Unmarshal([]byte(timestamp), &actual) - if err != nil { - t.Error(err) - } - - if actual != expected { - t.Errorf("incorrect string; got %s, want %s", actual, expected) - } -} diff --git a/vendor/github.com/getsentry/raven-go/docs/Makefile b/vendor/github.com/getsentry/raven-go/docs/Makefile deleted file mode 100644 index 60f8b8439..000000000 --- a/vendor/github.com/getsentry/raven-go/docs/Makefile +++ /dev/null @@ -1,153 +0,0 @@ -# Makefile for Sphinx documentation -# - -# You can set these variables from the command line. -SPHINXOPTS = -SPHINXBUILD = sphinx-build -PAPER = -BUILDDIR = _build - -# Internal variables. -PAPEROPT_a4 = -D latex_paper_size=a4 -PAPEROPT_letter = -D latex_paper_size=letter -ALLSPHINXOPTS = -d $(BUILDDIR)/doctrees $(PAPEROPT_$(PAPER)) $(SPHINXOPTS) . -# the i18n builder cannot share the environment and doctrees with the others -I18NSPHINXOPTS = $(PAPEROPT_$(PAPER)) $(SPHINXOPTS) . - -.PHONY: help clean html dirhtml singlehtml pickle json htmlhelp qthelp devhelp epub latex latexpdf text man changes linkcheck doctest gettext - -help: - @echo "Please use \`make ' where is one of" - @echo " html to make standalone HTML files" - @echo " dirhtml to make HTML files named index.html in directories" - @echo " singlehtml to make a single large HTML file" - @echo " pickle to make pickle files" - @echo " json to make JSON files" - @echo " htmlhelp to make HTML files and a HTML help project" - @echo " qthelp to make HTML files and a qthelp project" - @echo " devhelp to make HTML files and a Devhelp project" - @echo " epub to make an epub" - @echo " latex to make LaTeX files, you can set PAPER=a4 or PAPER=letter" - @echo " latexpdf to make LaTeX files and run them through pdflatex" - @echo " text to make text files" - @echo " man to make manual pages" - @echo " texinfo to make Texinfo files" - @echo " info to make Texinfo files and run them through makeinfo" - @echo " gettext to make PO message catalogs" - @echo " changes to make an overview of all changed/added/deprecated items" - @echo " linkcheck to check all external links for integrity" - @echo " doctest to run all doctests embedded in the documentation (if enabled)" - -clean: - -rm -rf $(BUILDDIR)/* - -html: - $(SPHINXBUILD) -b html $(ALLSPHINXOPTS) $(BUILDDIR)/html - @echo - @echo "Build finished. The HTML pages are in $(BUILDDIR)/html." - -dirhtml: - $(SPHINXBUILD) -b dirhtml $(ALLSPHINXOPTS) $(BUILDDIR)/dirhtml - @echo - @echo "Build finished. The HTML pages are in $(BUILDDIR)/dirhtml." - -singlehtml: - $(SPHINXBUILD) -b singlehtml $(ALLSPHINXOPTS) $(BUILDDIR)/singlehtml - @echo - @echo "Build finished. The HTML page is in $(BUILDDIR)/singlehtml." - -pickle: - $(SPHINXBUILD) -b pickle $(ALLSPHINXOPTS) $(BUILDDIR)/pickle - @echo - @echo "Build finished; now you can process the pickle files." - -json: - $(SPHINXBUILD) -b json $(ALLSPHINXOPTS) $(BUILDDIR)/json - @echo - @echo "Build finished; now you can process the JSON files." - -htmlhelp: - $(SPHINXBUILD) -b htmlhelp $(ALLSPHINXOPTS) $(BUILDDIR)/htmlhelp - @echo - @echo "Build finished; now you can run HTML Help Workshop with the" \ - ".hhp project file in $(BUILDDIR)/htmlhelp." - -qthelp: - $(SPHINXBUILD) -b qthelp $(ALLSPHINXOPTS) $(BUILDDIR)/qthelp - @echo - @echo "Build finished; now you can run "qcollectiongenerator" with the" \ - ".qhcp project file in $(BUILDDIR)/qthelp, like this:" - @echo "# qcollectiongenerator $(BUILDDIR)/qthelp/raven-js.qhcp" - @echo "To view the help file:" - @echo "# assistant -collectionFile $(BUILDDIR)/qthelp/raven-js.qhc" - -devhelp: - $(SPHINXBUILD) -b devhelp $(ALLSPHINXOPTS) $(BUILDDIR)/devhelp - @echo - @echo "Build finished." - @echo "To view the help file:" - @echo "# mkdir -p $$HOME/.local/share/devhelp/raven-js" - @echo "# ln -s $(BUILDDIR)/devhelp $$HOME/.local/share/devhelp/raven-js" - @echo "# devhelp" - -epub: - $(SPHINXBUILD) -b epub $(ALLSPHINXOPTS) $(BUILDDIR)/epub - @echo - @echo "Build finished. The epub file is in $(BUILDDIR)/epub." - -latex: - $(SPHINXBUILD) -b latex $(ALLSPHINXOPTS) $(BUILDDIR)/latex - @echo - @echo "Build finished; the LaTeX files are in $(BUILDDIR)/latex." - @echo "Run \`make' in that directory to run these through (pdf)latex" \ - "(use \`make latexpdf' here to do that automatically)." - -latexpdf: - $(SPHINXBUILD) -b latex $(ALLSPHINXOPTS) $(BUILDDIR)/latex - @echo "Running LaTeX files through pdflatex..." - $(MAKE) -C $(BUILDDIR)/latex all-pdf - @echo "pdflatex finished; the PDF files are in $(BUILDDIR)/latex." - -text: - $(SPHINXBUILD) -b text $(ALLSPHINXOPTS) $(BUILDDIR)/text - @echo - @echo "Build finished. The text files are in $(BUILDDIR)/text." - -man: - $(SPHINXBUILD) -b man $(ALLSPHINXOPTS) $(BUILDDIR)/man - @echo - @echo "Build finished. The manual pages are in $(BUILDDIR)/man." - -texinfo: - $(SPHINXBUILD) -b texinfo $(ALLSPHINXOPTS) $(BUILDDIR)/texinfo - @echo - @echo "Build finished. The Texinfo files are in $(BUILDDIR)/texinfo." - @echo "Run \`make' in that directory to run these through makeinfo" \ - "(use \`make info' here to do that automatically)." - -info: - $(SPHINXBUILD) -b texinfo $(ALLSPHINXOPTS) $(BUILDDIR)/texinfo - @echo "Running Texinfo files through makeinfo..." - make -C $(BUILDDIR)/texinfo info - @echo "makeinfo finished; the Info files are in $(BUILDDIR)/texinfo." - -gettext: - $(SPHINXBUILD) -b gettext $(I18NSPHINXOPTS) $(BUILDDIR)/locale - @echo - @echo "Build finished. The message catalogs are in $(BUILDDIR)/locale." - -changes: - $(SPHINXBUILD) -b changes $(ALLSPHINXOPTS) $(BUILDDIR)/changes - @echo - @echo "The overview file is in $(BUILDDIR)/changes." - -linkcheck: - $(SPHINXBUILD) -b linkcheck $(ALLSPHINXOPTS) $(BUILDDIR)/linkcheck - @echo - @echo "Link check complete; look for any errors in the above output " \ - "or in $(BUILDDIR)/linkcheck/output.txt." - -doctest: - $(SPHINXBUILD) -b doctest $(ALLSPHINXOPTS) $(BUILDDIR)/doctest - @echo "Testing of doctests in the sources finished, look at the " \ - "results in $(BUILDDIR)/doctest/output.txt." diff --git a/vendor/github.com/getsentry/raven-go/docs/conf.py b/vendor/github.com/getsentry/raven-go/docs/conf.py deleted file mode 100644 index 611c0012d..000000000 --- a/vendor/github.com/getsentry/raven-go/docs/conf.py +++ /dev/null @@ -1,248 +0,0 @@ -# -*- coding: utf-8 -*- -# -# raven-go documentation build configuration file, created by -# sphinx-quickstart on Mon Jan 21 21:04:27 2013. -# -# This file is execfile()d with the current directory set to its containing dir. -# -# Note that not all possible configuration values are present in this -# autogenerated file. -# -# All configuration values have a default; values that are commented out -# serve to show the default. - -import sys, os, datetime - -# If extensions (or modules to document with autodoc) are in another directory, -# add these directories to sys.path here. If the directory is relative to the -# documentation root, use os.path.abspath to make it absolute, like shown here. -#sys.path.insert(0, os.path.abspath('.')) - -# -- General configuration ----------------------------------------------------- - -# If your documentation needs a minimal Sphinx version, state it here. -#needs_sphinx = '1.0' - -# Add any Sphinx extension module names here, as strings. They can be extensions -# coming with Sphinx (named 'sphinx.ext.*') or your custom ones. -extensions = [] - -# Add any paths that contain templates here, relative to this directory. -templates_path = ['_templates'] - -# The suffix of source filenames. -source_suffix = '.rst' - -# The encoding of source files. -#source_encoding = 'utf-8-sig' - -# The master toctree document. -master_doc = 'index' - -# General information about the project. -project = u'raven-go' -copyright = u'%s, Functional Software Inc.' % datetime.date.today().year - -# The version info for the project you're documenting, acts as replacement for -# |version| and |release|, also used in various other places throughout the -# built documents. -# - -# The full version, including alpha/beta/rc tags. -release = '0.0.0' -# The short X.Y version. -version = release.rsplit('.', 1)[0] - -# The language for content autogenerated by Sphinx. Refer to documentation -# for a list of supported languages. -#language = None - -# There are two options for replacing |today|: either, you set today to some -# non-false value, then it is used: -#today = '' -# Else, today_fmt is used as the format for a strftime call. -#today_fmt = '%B %d, %Y' - -# List of patterns, relative to source directory, that match files and -# directories to ignore when looking for source files. -exclude_patterns = ['_build'] - -# The reST default role (used for this markup: `text`) to use for all documents. -#default_role = None - -# If true, '()' will be appended to :func: etc. cross-reference text. -#add_function_parentheses = True - -# If true, the current module name will be prepended to all description -# unit titles (such as .. function::). -#add_module_names = True - -# If true, sectionauthor and moduleauthor directives will be shown in the -# output. They are ignored by default. -#show_authors = False - -# The name of the Pygments (syntax highlighting) style to use. -pygments_style = 'sphinx' - -# A list of ignored prefixes for module index sorting. -#modindex_common_prefix = [] - - -# -- Options for HTML output --------------------------------------------------- - -# The theme to use for HTML and HTML Help pages. See the documentation for -# a list of builtin themes. -html_theme = 'default' - -# Theme options are theme-specific and customize the look and feel of a theme -# further. For a list of options available for each theme, see the -# documentation. -#html_theme_options = {} - -# Add any paths that contain custom themes here, relative to this directory. -#html_theme_path = [] - -# The name for this set of Sphinx documents. If None, it defaults to -# " v documentation". -#html_title = None - -# A shorter title for the navigation bar. Default is the same as html_title. -#html_short_title = None - -# The name of an image file (relative to this directory) to place at the top -# of the sidebar. -#html_logo = None - -# The name of an image file (within the static path) to use as favicon of the -# docs. This file should be a Windows icon file (.ico) being 16x16 or 32x32 -# pixels large. -#html_favicon = None - -# Add any paths that contain custom static files (such as style sheets) here, -# relative to this directory. They are copied after the builtin static files, -# so a file named "default.css" will overwrite the builtin "default.css". -html_static_path = ['_static'] - -# If not '', a 'Last updated on:' timestamp is inserted at every page bottom, -# using the given strftime format. -#html_last_updated_fmt = '%b %d, %Y' - -# If true, SmartyPants will be used to convert quotes and dashes to -# typographically correct entities. -#html_use_smartypants = True - -# Custom sidebar templates, maps document names to template names. -#html_sidebars = {} - -# Additional templates that should be rendered to pages, maps page names to -# template names. -#html_additional_pages = {} - -# If false, no module index is generated. -#html_domain_indices = True - -# If false, no index is generated. -#html_use_index = True - -# If true, the index is split into individual pages for each letter. -#html_split_index = False - -# If true, links to the reST sources are added to the pages. -#html_show_sourcelink = True - -# If true, "Created using Sphinx" is shown in the HTML footer. Default is True. -#html_show_sphinx = True - -# If true, "(C) Copyright ..." is shown in the HTML footer. Default is True. -#html_show_copyright = True - -# If true, an OpenSearch description file will be output, and all pages will -# contain a tag referring to it. The value of this option must be the -# base URL from which the finished HTML is served. -#html_use_opensearch = '' - -# This is the file name suffix for HTML files (e.g. ".xhtml"). -#html_file_suffix = None - -# Output file base name for HTML help builder. -htmlhelp_basename = 'raven-godoc' - - -# -- Options for LaTeX output -------------------------------------------------- - -latex_elements = { -# The paper size ('letterpaper' or 'a4paper'). -#'papersize': 'letterpaper', - -# The font size ('10pt', '11pt' or '12pt'). -#'pointsize': '10pt', - -# Additional stuff for the LaTeX preamble. -#'preamble': '', -} - -# Grouping the document tree into LaTeX files. List of tuples -# (source start file, target name, title, author, documentclass [howto/manual]). -latex_documents = [ - ('index', 'raven-go.tex', u'raven-go Documentation', - u'Functional Software Inc.', 'manual'), -] - -# The name of an image file (relative to this directory) to place at the top of -# the title page. -#latex_logo = None - -# For "manual" documents, if this is true, then toplevel headings are parts, -# not chapters. -#latex_use_parts = False - -# If true, show page references after internal links. -#latex_show_pagerefs = False - -# If true, show URL addresses after external links. -#latex_show_urls = False - -# Documents to append as an appendix to all manuals. -#latex_appendices = [] - -# If false, no module index is generated. -#latex_domain_indices = True - - -# -- Options for manual page output -------------------------------------------- - -# One entry per manual page. List of tuples -# (source start file, name, description, authors, manual section). -man_pages = [ - ('index', 'raven-go', u'raven-go Documentation', - [u'Functional Software Inc.'], 1) -] - -# If true, show URL addresses after external links. -#man_show_urls = False - - -# -- Options for Texinfo output ------------------------------------------------ - -# Grouping the document tree into Texinfo files. List of tuples -# (source start file, target name, title, author, -# dir menu entry, description, category) -texinfo_documents = [ - ('index', 'raven-go', u'raven-go Documentation', - u'Functional Software Inc.', 'raven-go', 'One line description of project.', - 'Miscellaneous'), -] - -# Documents to append as an appendix to all manuals. -#texinfo_appendices = [] - -# If false, no module index is generated. -#texinfo_domain_indices = True - -# How to display URL addresses: 'footnote', 'no', or 'inline'. -#texinfo_show_urls = 'footnote' - -if os.environ.get('SENTRY_FEDERATED_DOCS') != '1': - sys.path.insert(0, os.path.abspath('_sentryext')) - import sentryext - sentryext.activate() diff --git a/vendor/github.com/getsentry/raven-go/docs/index.rst b/vendor/github.com/getsentry/raven-go/docs/index.rst deleted file mode 100644 index b570b9497..000000000 --- a/vendor/github.com/getsentry/raven-go/docs/index.rst +++ /dev/null @@ -1,41 +0,0 @@ -.. sentry:edition:: self - - Raven Go - ======== - -.. sentry:edition:: hosted, on-premise - - .. class:: platform-go - - Go - == - -Raven-Go provides a Sentry client implementation for the Go programming -language. - -Installation ------------- - -Raven-Go can be installed like any other Go library through ``go get``:: - - $ go get github.com/getsentry/raven-go - -Minimal Example ---------------- - -.. sourcecode:: go - - package main - - import ( - "github.com/getsentry/raven-go" - ) - - func main() { - raven.SetDSN("___DSN___") - - _, err := DoSomethingThatFails() - if err != nil { - raven.CaptureErrorAndWait(err, nil); - } - } diff --git a/vendor/github.com/getsentry/raven-go/docs/make.bat b/vendor/github.com/getsentry/raven-go/docs/make.bat deleted file mode 100644 index 13e2848a4..000000000 --- a/vendor/github.com/getsentry/raven-go/docs/make.bat +++ /dev/null @@ -1,190 +0,0 @@ -@ECHO OFF - -REM Command file for Sphinx documentation - -if "%SPHINXBUILD%" == "" ( - set SPHINXBUILD=sphinx-build -) -set BUILDDIR=_build -set ALLSPHINXOPTS=-d %BUILDDIR%/doctrees %SPHINXOPTS% . -set I18NSPHINXOPTS=%SPHINXOPTS% . -if NOT "%PAPER%" == "" ( - set ALLSPHINXOPTS=-D latex_paper_size=%PAPER% %ALLSPHINXOPTS% - set I18NSPHINXOPTS=-D latex_paper_size=%PAPER% %I18NSPHINXOPTS% -) - -if "%1" == "" goto help - -if "%1" == "help" ( - :help - echo.Please use `make ^` where ^ is one of - echo. html to make standalone HTML files - echo. dirhtml to make HTML files named index.html in directories - echo. singlehtml to make a single large HTML file - echo. pickle to make pickle files - echo. json to make JSON files - echo. htmlhelp to make HTML files and a HTML help project - echo. qthelp to make HTML files and a qthelp project - echo. devhelp to make HTML files and a Devhelp project - echo. epub to make an epub - echo. latex to make LaTeX files, you can set PAPER=a4 or PAPER=letter - echo. text to make text files - echo. man to make manual pages - echo. texinfo to make Texinfo files - echo. gettext to make PO message catalogs - echo. changes to make an overview over all changed/added/deprecated items - echo. linkcheck to check all external links for integrity - echo. doctest to run all doctests embedded in the documentation if enabled - goto end -) - -if "%1" == "clean" ( - for /d %%i in (%BUILDDIR%\*) do rmdir /q /s %%i - del /q /s %BUILDDIR%\* - goto end -) - -if "%1" == "html" ( - %SPHINXBUILD% -b html %ALLSPHINXOPTS% %BUILDDIR%/html - if errorlevel 1 exit /b 1 - echo. - echo.Build finished. The HTML pages are in %BUILDDIR%/html. - goto end -) - -if "%1" == "dirhtml" ( - %SPHINXBUILD% -b dirhtml %ALLSPHINXOPTS% %BUILDDIR%/dirhtml - if errorlevel 1 exit /b 1 - echo. - echo.Build finished. The HTML pages are in %BUILDDIR%/dirhtml. - goto end -) - -if "%1" == "singlehtml" ( - %SPHINXBUILD% -b singlehtml %ALLSPHINXOPTS% %BUILDDIR%/singlehtml - if errorlevel 1 exit /b 1 - echo. - echo.Build finished. The HTML pages are in %BUILDDIR%/singlehtml. - goto end -) - -if "%1" == "pickle" ( - %SPHINXBUILD% -b pickle %ALLSPHINXOPTS% %BUILDDIR%/pickle - if errorlevel 1 exit /b 1 - echo. - echo.Build finished; now you can process the pickle files. - goto end -) - -if "%1" == "json" ( - %SPHINXBUILD% -b json %ALLSPHINXOPTS% %BUILDDIR%/json - if errorlevel 1 exit /b 1 - echo. - echo.Build finished; now you can process the JSON files. - goto end -) - -if "%1" == "htmlhelp" ( - %SPHINXBUILD% -b htmlhelp %ALLSPHINXOPTS% %BUILDDIR%/htmlhelp - if errorlevel 1 exit /b 1 - echo. - echo.Build finished; now you can run HTML Help Workshop with the ^ -.hhp project file in %BUILDDIR%/htmlhelp. - goto end -) - -if "%1" == "qthelp" ( - %SPHINXBUILD% -b qthelp %ALLSPHINXOPTS% %BUILDDIR%/qthelp - if errorlevel 1 exit /b 1 - echo. - echo.Build finished; now you can run "qcollectiongenerator" with the ^ -.qhcp project file in %BUILDDIR%/qthelp, like this: - echo.^> qcollectiongenerator %BUILDDIR%\qthelp\raven-js.qhcp - echo.To view the help file: - echo.^> assistant -collectionFile %BUILDDIR%\qthelp\raven-js.ghc - goto end -) - -if "%1" == "devhelp" ( - %SPHINXBUILD% -b devhelp %ALLSPHINXOPTS% %BUILDDIR%/devhelp - if errorlevel 1 exit /b 1 - echo. - echo.Build finished. - goto end -) - -if "%1" == "epub" ( - %SPHINXBUILD% -b epub %ALLSPHINXOPTS% %BUILDDIR%/epub - if errorlevel 1 exit /b 1 - echo. - echo.Build finished. The epub file is in %BUILDDIR%/epub. - goto end -) - -if "%1" == "latex" ( - %SPHINXBUILD% -b latex %ALLSPHINXOPTS% %BUILDDIR%/latex - if errorlevel 1 exit /b 1 - echo. - echo.Build finished; the LaTeX files are in %BUILDDIR%/latex. - goto end -) - -if "%1" == "text" ( - %SPHINXBUILD% -b text %ALLSPHINXOPTS% %BUILDDIR%/text - if errorlevel 1 exit /b 1 - echo. - echo.Build finished. The text files are in %BUILDDIR%/text. - goto end -) - -if "%1" == "man" ( - %SPHINXBUILD% -b man %ALLSPHINXOPTS% %BUILDDIR%/man - if errorlevel 1 exit /b 1 - echo. - echo.Build finished. The manual pages are in %BUILDDIR%/man. - goto end -) - -if "%1" == "texinfo" ( - %SPHINXBUILD% -b texinfo %ALLSPHINXOPTS% %BUILDDIR%/texinfo - if errorlevel 1 exit /b 1 - echo. - echo.Build finished. The Texinfo files are in %BUILDDIR%/texinfo. - goto end -) - -if "%1" == "gettext" ( - %SPHINXBUILD% -b gettext %I18NSPHINXOPTS% %BUILDDIR%/locale - if errorlevel 1 exit /b 1 - echo. - echo.Build finished. The message catalogs are in %BUILDDIR%/locale. - goto end -) - -if "%1" == "changes" ( - %SPHINXBUILD% -b changes %ALLSPHINXOPTS% %BUILDDIR%/changes - if errorlevel 1 exit /b 1 - echo. - echo.The overview file is in %BUILDDIR%/changes. - goto end -) - -if "%1" == "linkcheck" ( - %SPHINXBUILD% -b linkcheck %ALLSPHINXOPTS% %BUILDDIR%/linkcheck - if errorlevel 1 exit /b 1 - echo. - echo.Link check complete; look for any errors in the above output ^ -or in %BUILDDIR%/linkcheck/output.txt. - goto end -) - -if "%1" == "doctest" ( - %SPHINXBUILD% -b doctest %ALLSPHINXOPTS% %BUILDDIR%/doctest - if errorlevel 1 exit /b 1 - echo. - echo.Testing of doctests in the sources finished, look at the ^ -results in %BUILDDIR%/doctest/output.txt. - goto end -) - -:end diff --git a/vendor/github.com/getsentry/raven-go/docs/sentry-doc-config.json b/vendor/github.com/getsentry/raven-go/docs/sentry-doc-config.json deleted file mode 100644 index fbbb91979..000000000 --- a/vendor/github.com/getsentry/raven-go/docs/sentry-doc-config.json +++ /dev/null @@ -1,15 +0,0 @@ -{ - "wizards": { - "go": { - "name": "Go", - "client_lib": "raven-go", - "is_framework": false, - "doc_link": "", - "snippets": [ - "index#installation", - "index#configuring-the-client", - "index#reporting-errors" - ] - } - } -} diff --git a/vendor/github.com/getsentry/raven-go/example/example.go b/vendor/github.com/getsentry/raven-go/example/example.go deleted file mode 100644 index 43d887a2c..000000000 --- a/vendor/github.com/getsentry/raven-go/example/example.go +++ /dev/null @@ -1,42 +0,0 @@ -package main - -import ( - "errors" - "fmt" - "github.com/getsentry/raven-go" - "log" - "net/http" - "os" -) - -func trace() *raven.Stacktrace { - return raven.NewStacktrace(0, 2, nil) -} - -func main() { - client, err := raven.NewWithTags(os.Args[1], map[string]string{"foo": "bar"}) - if err != nil { - log.Fatal(err) - } - httpReq, _ := http.NewRequest("GET", "http://example.com/foo?bar=true", nil) - httpReq.RemoteAddr = "127.0.0.1:80" - httpReq.Header = http.Header{"Content-Type": {"text/html"}, "Content-Length": {"42"}} - packet := &raven.Packet{Message: "Test report", Interfaces: []raven.Interface{raven.NewException(errors.New("example"), trace()), raven.NewHttp(httpReq)}} - _, ch := client.Capture(packet, nil) - if err = <-ch; err != nil { - log.Fatal(err) - } - log.Print("sent packet successfully") -} - -// CheckError sends error report to sentry and records event id and error name to the logs -func CheckError(err error, r *http.Request) { - client, err := raven.NewWithTags(os.Args[1], map[string]string{"foo": "bar"}) - if err != nil { - log.Fatal(err) - } - packet := raven.NewPacket(err.Error(), raven.NewException(err, trace()), raven.NewHttp(r)) - eventID, _ := client.Capture(packet, nil) - message := fmt.Sprintf("Error event with id \"%s\" - %s", eventID, err.Error()) - log.Println(message) -} diff --git a/vendor/github.com/getsentry/raven-go/examples_test.go b/vendor/github.com/getsentry/raven-go/examples_test.go deleted file mode 100644 index 57b90d170..000000000 --- a/vendor/github.com/getsentry/raven-go/examples_test.go +++ /dev/null @@ -1,28 +0,0 @@ -package raven - -import ( - "fmt" - "log" - "net/http" -) - -func Example() { - // ... i.e. raisedErr is incoming error - var raisedErr error - // sentry DSN generated by Sentry server - var sentryDSN string - // r is a request performed when error occured - var r *http.Request - client, err := New(sentryDSN) - if err != nil { - log.Fatal(err) - } - trace := NewStacktrace(0, 2, nil) - packet := NewPacket(raisedErr.Error(), NewException(raisedErr, trace), NewHttp(r)) - eventID, ch := client.Capture(packet, nil) - if err = <-ch; err != nil { - log.Fatal(err) - } - message := fmt.Sprintf("Captured error with id %s: %q", eventID, raisedErr) - log.Println(message) -} diff --git a/vendor/github.com/getsentry/raven-go/exception.go b/vendor/github.com/getsentry/raven-go/exception.go deleted file mode 100644 index 14a42a442..000000000 --- a/vendor/github.com/getsentry/raven-go/exception.go +++ /dev/null @@ -1,41 +0,0 @@ -package raven - -import ( - "reflect" - "regexp" -) - -var errorMsgPattern = regexp.MustCompile(`\A(\w+): (.+)\z`) - -func NewException(err error, stacktrace *Stacktrace) *Exception { - msg := err.Error() - ex := &Exception{ - Stacktrace: stacktrace, - Value: msg, - Type: reflect.TypeOf(err).String(), - } - if m := errorMsgPattern.FindStringSubmatch(msg); m != nil { - ex.Module, ex.Value = m[1], m[2] - } - return ex -} - -// http://sentry.readthedocs.org/en/latest/developer/interfaces/index.html#sentry.interfaces.Exception -type Exception struct { - // Required - Value string `json:"value"` - - // Optional - Type string `json:"type,omitempty"` - Module string `json:"module,omitempty"` - Stacktrace *Stacktrace `json:"stacktrace,omitempty"` -} - -func (e *Exception) Class() string { return "exception" } - -func (e *Exception) Culprit() string { - if e.Stacktrace == nil { - return "" - } - return e.Stacktrace.Culprit() -} diff --git a/vendor/github.com/getsentry/raven-go/exception_test.go b/vendor/github.com/getsentry/raven-go/exception_test.go deleted file mode 100644 index f7d3ce43d..000000000 --- a/vendor/github.com/getsentry/raven-go/exception_test.go +++ /dev/null @@ -1,29 +0,0 @@ -package raven - -import ( - "errors" - "testing" -) - -var newExceptionTests = []struct { - err error - Exception -}{ - {errors.New("foobar"), Exception{Value: "foobar", Type: "*errors.errorString"}}, - {errors.New("bar: foobar"), Exception{Value: "foobar", Type: "*errors.errorString", Module: "bar"}}, -} - -func TestNewException(t *testing.T) { - for _, test := range newExceptionTests { - actual := NewException(test.err, nil) - if actual.Value != test.Value { - t.Errorf("incorrect Value: got %s, want %s", actual.Value, test.Value) - } - if actual.Type != test.Type { - t.Errorf("incorrect Type: got %s, want %s", actual.Type, test.Type) - } - if actual.Module != test.Module { - t.Errorf("incorrect Module: got %s, want %s", actual.Module, test.Module) - } - } -} diff --git a/vendor/github.com/getsentry/raven-go/http.go b/vendor/github.com/getsentry/raven-go/http.go deleted file mode 100644 index ac75f4b3c..000000000 --- a/vendor/github.com/getsentry/raven-go/http.go +++ /dev/null @@ -1,84 +0,0 @@ -package raven - -import ( - "errors" - "fmt" - "net" - "net/http" - "net/url" - "runtime/debug" - "strings" -) - -func NewHttp(req *http.Request) *Http { - proto := "http" - if req.TLS != nil || req.Header.Get("X-Forwarded-Proto") == "https" { - proto = "https" - } - h := &Http{ - Method: req.Method, - Cookies: req.Header.Get("Cookie"), - Query: sanitizeQuery(req.URL.Query()).Encode(), - URL: proto + "://" + req.Host + req.URL.Path, - Headers: make(map[string]string, len(req.Header)), - } - if addr, port, err := net.SplitHostPort(req.RemoteAddr); err == nil { - h.Env = map[string]string{"REMOTE_ADDR": addr, "REMOTE_PORT": port} - } - for k, v := range req.Header { - h.Headers[k] = strings.Join(v, ",") - } - return h -} - -var querySecretFields = []string{"password", "passphrase", "passwd", "secret"} - -func sanitizeQuery(query url.Values) url.Values { - for _, keyword := range querySecretFields { - for field := range query { - if strings.Contains(field, keyword) { - query[field] = []string{"********"} - } - } - } - return query -} - -// http://sentry.readthedocs.org/en/latest/developer/interfaces/index.html#sentry.interfaces.Http -type Http struct { - // Required - URL string `json:"url"` - Method string `json:"method"` - Query string `json:"query_string,omitempty"` - - // Optional - Cookies string `json:"cookies,omitempty"` - Headers map[string]string `json:"headers,omitempty"` - Env map[string]string `json:"env,omitempty"` - - // Must be either a string or map[string]string - Data interface{} `json:"data,omitempty"` -} - -func (h *Http) Class() string { return "request" } - -// Recovery handler to wrap the stdlib net/http Mux. -// Example: -// http.HandleFunc("/", raven.RecoveryHandler(func(w http.ResponseWriter, r *http.Request) { -// ... -// })) -func RecoveryHandler(handler func(http.ResponseWriter, *http.Request)) func(http.ResponseWriter, *http.Request) { - return func(w http.ResponseWriter, r *http.Request) { - defer func() { - if rval := recover(); rval != nil { - debug.PrintStack() - rvalStr := fmt.Sprint(rval) - packet := NewPacket(rvalStr, NewException(errors.New(rvalStr), NewStacktrace(2, 3, nil)), NewHttp(r)) - Capture(packet, nil) - w.WriteHeader(http.StatusInternalServerError) - } - }() - - handler(w, r) - } -} diff --git a/vendor/github.com/getsentry/raven-go/http_test.go b/vendor/github.com/getsentry/raven-go/http_test.go deleted file mode 100644 index 7d611b1e3..000000000 --- a/vendor/github.com/getsentry/raven-go/http_test.go +++ /dev/null @@ -1,149 +0,0 @@ -package raven - -import ( - "net/http" - "net/url" - "reflect" - "testing" -) - -type testcase struct { - request *http.Request - *Http -} - -func newBaseRequest() *http.Request { - u, _ := url.Parse("http://example.com/") - header := make(http.Header) - header.Add("Foo", "bar") - - req := &http.Request{ - Method: "GET", - URL: u, - Proto: "HTTP/1.1", - ProtoMajor: 1, - ProtoMinor: 1, - Header: header, - Host: u.Host, - RemoteAddr: "127.0.0.1:8000", - } - return req -} - -func newBaseHttp() *Http { - h := &Http{ - Method: "GET", - Cookies: "", - Query: "", - URL: "http://example.com/", - Headers: map[string]string{"Foo": "bar"}, - Env: map[string]string{"REMOTE_ADDR": "127.0.0.1", "REMOTE_PORT": "8000"}, - } - return h -} - -func NewRequest() testcase { - return testcase{newBaseRequest(), newBaseHttp()} -} - -func NewRequestIPV6() testcase { - req := newBaseRequest() - req.RemoteAddr = "[:1]:8000" - - h := newBaseHttp() - h.Env = map[string]string{"REMOTE_ADDR": ":1", "REMOTE_PORT": "8000"} - return testcase{req, h} -} - -func NewRequestMultipleHeaders() testcase { - req := newBaseRequest() - req.Header.Add("Foo", "baz") - - h := newBaseHttp() - h.Headers["Foo"] = "bar,baz" - return testcase{req, h} -} - -func NewSecureRequest() testcase { - req := newBaseRequest() - req.Header.Add("X-Forwarded-Proto", "https") - - h := newBaseHttp() - h.URL = "https://example.com/" - h.Headers["X-Forwarded-Proto"] = "https" - return testcase{req, h} -} - -func NewCookiesRequest() testcase { - val := "foo=bar; bar=baz" - req := newBaseRequest() - req.Header.Add("Cookie", val) - - h := newBaseHttp() - h.Cookies = val - h.Headers["Cookie"] = val - return testcase{req, h} -} - -var newHttpTests = []testcase{ - NewRequest(), - NewRequestIPV6(), - NewRequestMultipleHeaders(), - NewSecureRequest(), - NewCookiesRequest(), -} - -func TestNewHttp(t *testing.T) { - for _, test := range newHttpTests { - actual := NewHttp(test.request) - if actual.Method != test.Method { - t.Errorf("incorrect Method: got %s, want %s", actual.Method, test.Method) - } - if actual.Cookies != test.Cookies { - t.Errorf("incorrect Cookies: got %s, want %s", actual.Cookies, test.Cookies) - } - if actual.Query != test.Query { - t.Errorf("incorrect Query: got %s, want %s", actual.Query, test.Query) - } - if actual.URL != test.URL { - t.Errorf("incorrect URL: got %s, want %s", actual.URL, test.URL) - } - if !reflect.DeepEqual(actual.Headers, test.Headers) { - t.Errorf("incorrect Headers: got %+v, want %+v", actual.Headers, test.Headers) - } - if !reflect.DeepEqual(actual.Env, test.Env) { - t.Errorf("incorrect Env: got %+v, want %+v", actual.Env, test.Env) - } - if !reflect.DeepEqual(actual.Data, test.Data) { - t.Errorf("incorrect Data: got %+v, want %+v", actual.Data, test.Data) - } - } -} - -var sanitizeQueryTests = []struct { - input, output string -}{ - {"foo=bar", "foo=bar"}, - {"password=foo", "password=********"}, - {"passphrase=foo", "passphrase=********"}, - {"passwd=foo", "passwd=********"}, - {"secret=foo", "secret=********"}, - {"secretstuff=foo", "secretstuff=********"}, - {"foo=bar&secret=foo", "foo=bar&secret=********"}, - {"secret=foo&secret=bar", "secret=********"}, -} - -func parseQuery(q string) url.Values { - r, _ := url.ParseQuery(q) - return r -} - -func TestSanitizeQuery(t *testing.T) { - for _, test := range sanitizeQueryTests { - actual := sanitizeQuery(parseQuery(test.input)) - expected := parseQuery(test.output) - if !reflect.DeepEqual(actual, expected) { - t.Errorf("incorrect sanitization: got %+v, want %+v", actual, expected) - } - } -} diff --git a/vendor/github.com/getsentry/raven-go/interfaces.go b/vendor/github.com/getsentry/raven-go/interfaces.go deleted file mode 100644 index 5eea1e232..000000000 --- a/vendor/github.com/getsentry/raven-go/interfaces.go +++ /dev/null @@ -1,49 +0,0 @@ -package raven - -// http://sentry.readthedocs.org/en/latest/developer/interfaces/index.html#sentry.interfaces.Message -type Message struct { - // Required - Message string `json:"message"` - - // Optional - Params []interface{} `json:"params,omitempty"` -} - -func (m *Message) Class() string { return "logentry" } - -// http://sentry.readthedocs.org/en/latest/developer/interfaces/index.html#sentry.interfaces.Template -type Template struct { - // Required - Filename string `json:"filename"` - Lineno int `json:"lineno"` - ContextLine string `json:"context_line"` - - // Optional - PreContext []string `json:"pre_context,omitempty"` - PostContext []string `json:"post_context,omitempty"` - AbsolutePath string `json:"abs_path,omitempty"` -} - -func (t *Template) Class() string { return "template" } - -// http://sentry.readthedocs.org/en/latest/developer/interfaces/index.html#sentry.interfaces.User -type User struct { - // All fields are optional - ID string `json:"id,omitempty"` - Username string `json:"username,omitempty"` - Email string `json:"email,omitempty"` - IP string `json:"ip_address,omitempty"` -} - -func (h *User) Class() string { return "user" } - -// http://sentry.readthedocs.org/en/latest/developer/interfaces/index.html#sentry.interfaces.Query -type Query struct { - // Required - Query string `json:"query"` - - // Optional - Engine string `json:"engine,omitempty"` -} - -func (q *Query) Class() string { return "query" } diff --git a/vendor/github.com/getsentry/raven-go/runtests.sh b/vendor/github.com/getsentry/raven-go/runtests.sh deleted file mode 100644 index 9ed279c96..000000000 --- a/vendor/github.com/getsentry/raven-go/runtests.sh +++ /dev/null @@ -1,4 +0,0 @@ -#!/bin/bash -go test -race ./... -go test -cover ./... -go test -v ./... diff --git a/vendor/github.com/getsentry/raven-go/stacktrace.go b/vendor/github.com/getsentry/raven-go/stacktrace.go deleted file mode 100644 index 642569d63..000000000 --- a/vendor/github.com/getsentry/raven-go/stacktrace.go +++ /dev/null @@ -1,205 +0,0 @@ -// Copyright 2011 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. -// Some code from the runtime/debug package of the Go standard library. - -package raven - -import ( - "bytes" - "go/build" - "io/ioutil" - "path/filepath" - "runtime" - "strings" - "sync" -) - -// http://sentry.readthedocs.org/en/latest/developer/interfaces/index.html#sentry.interfaces.Stacktrace -type Stacktrace struct { - // Required - Frames []*StacktraceFrame `json:"frames"` -} - -func (s *Stacktrace) Class() string { return "stacktrace" } - -func (s *Stacktrace) Culprit() string { - for i := len(s.Frames) - 1; i >= 0; i-- { - frame := s.Frames[i] - if frame.InApp == true && frame.Module != "" && frame.Function != "" { - return frame.Module + "." + frame.Function - } - } - return "" -} - -type StacktraceFrame struct { - // At least one required - Filename string `json:"filename,omitempty"` - Function string `json:"function,omitempty"` - Module string `json:"module,omitempty"` - - // Optional - Lineno int `json:"lineno,omitempty"` - Colno int `json:"colno,omitempty"` - AbsolutePath string `json:"abs_path,omitempty"` - ContextLine string `json:"context_line,omitempty"` - PreContext []string `json:"pre_context,omitempty"` - PostContext []string `json:"post_context,omitempty"` - InApp bool `json:"in_app"` -} - -// Intialize and populate a new stacktrace, skipping skip frames. -// -// context is the number of surrounding lines that should be included for context. -// Setting context to 3 would try to get seven lines. Setting context to -1 returns -// one line with no surrounding context, and 0 returns no context. -// -// appPackagePrefixes is a list of prefixes used to check whether a package should -// be considered "in app". -func NewStacktrace(skip int, context int, appPackagePrefixes []string) *Stacktrace { - var frames []*StacktraceFrame - for i := 1 + skip; ; i++ { - pc, file, line, ok := runtime.Caller(i) - if !ok { - break - } - frame := NewStacktraceFrame(pc, file, line, context, appPackagePrefixes) - if frame != nil { - frames = append(frames, frame) - } - } - // Sentry wants the frames with the oldest first, so reverse them - for i, j := 0, len(frames)-1; i < j; i, j = i+1, j-1 { - frames[i], frames[j] = frames[j], frames[i] - } - return &Stacktrace{frames} -} - -// Build a single frame using data returned from runtime.Caller. -// -// context is the number of surrounding lines that should be included for context. -// Setting context to 3 would try to get seven lines. Setting context to -1 returns -// one line with no surrounding context, and 0 returns no context. -// -// appPackagePrefixes is a list of prefixes used to check whether a package should -// be considered "in app". -func NewStacktraceFrame(pc uintptr, file string, line, context int, appPackagePrefixes []string) *StacktraceFrame { - frame := &StacktraceFrame{AbsolutePath: file, Filename: trimPath(file), Lineno: line, InApp: false} - frame.Module, frame.Function = functionName(pc) - - // `runtime.goexit` is effectively a placeholder that comes from - // runtime/asm_amd64.s and is meaningless. - if frame.Module == "runtime" && frame.Function == "goexit" { - return nil - } - - if frame.Module == "main" { - frame.InApp = true - } else { - for _, prefix := range appPackagePrefixes { - if strings.HasPrefix(frame.Module, prefix) && !strings.Contains(frame.Module, "vendor") && !strings.Contains(frame.Module, "third_party") { - frame.InApp = true - } - } - } - - if context > 0 { - contextLines, lineIdx := fileContext(file, line, context) - if len(contextLines) > 0 { - for i, line := range contextLines { - switch { - case i < lineIdx: - frame.PreContext = append(frame.PreContext, string(line)) - case i == lineIdx: - frame.ContextLine = string(line) - default: - frame.PostContext = append(frame.PostContext, string(line)) - } - } - } - } else if context == -1 { - contextLine, _ := fileContext(file, line, 0) - if len(contextLine) > 0 { - frame.ContextLine = string(contextLine[0]) - } - } - return frame -} - -// Retrieve the name of the package and function containing the PC. -func functionName(pc uintptr) (pack string, name string) { - fn := runtime.FuncForPC(pc) - if fn == nil { - return - } - name = fn.Name() - // We get this: - // runtime/debug.*T·ptrmethod - // and want this: - // pack = runtime/debug - // name = *T.ptrmethod - if idx := strings.LastIndex(name, "."); idx != -1 { - pack = name[:idx] - name = name[idx+1:] - } - name = strings.Replace(name, "·", ".", -1) - return -} - -var fileCacheLock sync.Mutex -var fileCache = make(map[string][][]byte) - -func fileContext(filename string, line, context int) ([][]byte, int) { - fileCacheLock.Lock() - defer fileCacheLock.Unlock() - lines, ok := fileCache[filename] - if !ok { - data, err := ioutil.ReadFile(filename) - if err != nil { - return nil, 0 - } - lines = bytes.Split(data, []byte{'\n'}) - fileCache[filename] = lines - } - line-- // stack trace lines are 1-indexed - start := line - context - var idx int - if start < 0 { - start = 0 - idx = line - } else { - idx = context - } - end := line + context + 1 - if line >= len(lines) { - return nil, 0 - } - if end > len(lines) { - end = len(lines) - } - return lines[start:end], idx -} - -var trimPaths []string - -// Try to trim the GOROOT or GOPATH prefix off of a filename -func trimPath(filename string) string { - for _, prefix := range trimPaths { - if trimmed := strings.TrimPrefix(filename, prefix); len(trimmed) < len(filename) { - return trimmed - } - } - return filename -} - -func init() { - // Collect all source directories, and make sure they - // end in a trailing "separator" - for _, prefix := range build.Default.SrcDirs() { - if prefix[len(prefix)-1] != filepath.Separator { - prefix += string(filepath.Separator) - } - trimPaths = append(trimPaths, prefix) - } -} diff --git a/vendor/github.com/getsentry/raven-go/stacktrace_test.go b/vendor/github.com/getsentry/raven-go/stacktrace_test.go deleted file mode 100644 index b213c8191..000000000 --- a/vendor/github.com/getsentry/raven-go/stacktrace_test.go +++ /dev/null @@ -1,133 +0,0 @@ -package raven - -import ( - "fmt" - "go/build" - "path/filepath" - "runtime" - "strings" - "testing" -) - -type FunctionNameTest struct { - skip int - pack string - name string -} - -var ( - thisFile string - thisPackage string - functionNameTests []FunctionNameTest -) - -func TestFunctionName(t *testing.T) { - for _, test := range functionNameTests { - pc, _, _, _ := runtime.Caller(test.skip) - pack, name := functionName(pc) - - if pack != test.pack { - t.Errorf("incorrect package; got %s, want %s", pack, test.pack) - } - if name != test.name { - t.Errorf("incorrect function; got %s, want %s", name, test.name) - } - } -} - -func TestStacktrace(t *testing.T) { - st := trace() - if st == nil { - t.Error("got nil stacktrace") - } - if len(st.Frames) == 0 { - t.Error("got zero frames") - } - - f := st.Frames[len(st.Frames)-1] - if f.Filename != thisFile { - t.Errorf("incorrect Filename; got %s, want %s", f.Filename, thisFile) - } - if !strings.HasSuffix(f.AbsolutePath, thisFile) { - t.Error("incorrect AbsolutePath:", f.AbsolutePath) - } - if f.Function != "trace" { - t.Error("incorrect Function:", f.Function) - } - if f.Module != thisPackage { - t.Error("incorrect Module:", f.Module) - } - if f.Lineno != 83 { - t.Error("incorrect Lineno:", f.Lineno) - } - if f.ContextLine != "\treturn NewStacktrace(0, 2, []string{thisPackage})" { - t.Errorf("incorrect ContextLine: %#v", f.ContextLine) - } - if len(f.PreContext) != 2 || f.PreContext[0] != "// a" || f.PreContext[1] != "func trace() *Stacktrace {" { - t.Errorf("incorrect PreContext %#v", f.PreContext) - } - if len(f.PostContext) != 2 || f.PostContext[0] != "\t// b" || f.PostContext[1] != "}" { - t.Errorf("incorrect PostContext %#v", f.PostContext) - } - if !f.InApp { - t.Error("expected InApp to be true") - } - - if st.Culprit() != fmt.Sprintf("%s.trace", thisPackage) { - t.Error("incorrect Culprit:", st.Culprit()) - } -} - -// a -func trace() *Stacktrace { - return NewStacktrace(0, 2, []string{thisPackage}) - // b -} - -func derivePackage() (file, pack string) { - // Get file name by seeking caller's file name. - _, callerFile, _, ok := runtime.Caller(1) - if !ok { - return - } - - // Trim file name - file = callerFile - for _, dir := range build.Default.SrcDirs() { - dir := dir + string(filepath.Separator) - if trimmed := strings.TrimPrefix(callerFile, dir); len(trimmed) < len(file) { - file = trimmed - } - } - - // Now derive package name - dir := filepath.Dir(callerFile) - - dirPkg, err := build.ImportDir(dir, build.AllowBinary) - if err != nil { - return - } - - pack = dirPkg.ImportPath - return -} - -func init() { - thisFile, thisPackage = derivePackage() - functionNameTests = []FunctionNameTest{ - {0, thisPackage, "TestFunctionName"}, - {1, "testing", "tRunner"}, - {2, "runtime", "goexit"}, - {100, "", ""}, - } -} - -// TestNewStacktrace_outOfBounds verifies that a context exceeding the number -// of lines in a file does not cause a panic. -func TestNewStacktrace_outOfBounds(t *testing.T) { - st := NewStacktrace(0, 1000000, []string{thisPackage}) - f := st.Frames[len(st.Frames)-1] - if f.ContextLine != "\tst := NewStacktrace(0, 1000000, []string{thisPackage})" { - t.Errorf("incorrect ContextLine: %#v", f.ContextLine) - } -} diff --git a/vendor/github.com/getsentry/raven-go/writer.go b/vendor/github.com/getsentry/raven-go/writer.go deleted file mode 100644 index 61f7a9108..000000000 --- a/vendor/github.com/getsentry/raven-go/writer.go +++ /dev/null @@ -1,20 +0,0 @@ -package raven - -type Writer struct { - Client *Client - Level Severity - Logger string // Logger name reported to Sentry -} - -// Write formats the byte slice p into a string, and sends a message to -// Sentry at the severity level indicated by the Writer w. -func (w *Writer) Write(p []byte) (int, error) { - message := string(p) - - packet := NewPacket(message, &Message{message, nil}) - packet.Level = w.Level - packet.Logger = w.Logger - w.Client.Capture(packet, nil) - - return len(p), nil -} diff --git a/vendor/github.com/gin-gonic/gin/CHANGELOG.md b/vendor/github.com/gin-gonic/gin/CHANGELOG.md index 5b5b6addf..82f1bead8 100644 --- a/vendor/github.com/gin-gonic/gin/CHANGELOG.md +++ b/vendor/github.com/gin-gonic/gin/CHANGELOG.md @@ -2,7 +2,7 @@ ###Gin 1.0rc2 (...) -- [PERFORMANCE] Fast path for writting Content-Type. +- [PERFORMANCE] Fast path for writing Content-Type. - [PERFORMANCE] Much faster 404 routing - [PERFORMANCE] Allocation optimizations - [PERFORMANCE] Faster root tree lookup diff --git a/vendor/github.com/gin-gonic/gin/Godeps/Godeps.json b/vendor/github.com/gin-gonic/gin/Godeps/Godeps.json deleted file mode 100644 index ebda5138a..000000000 --- a/vendor/github.com/gin-gonic/gin/Godeps/Godeps.json +++ /dev/null @@ -1,39 +0,0 @@ -{ - "ImportPath": "github.com/gin-gonic/gin", - "GoVersion": "go1.4.2", - "Packages": [ - "./..." - ], - "Deps": [ - { - "ImportPath": "github.com/dustin/go-broadcast", - "Rev": "3bdf6d4a7164a50bc19d5f230e2981d87d2584f1" - }, - { - "ImportPath": "github.com/manucorporat/sse", - "Rev": "c142f0f1baea5cef7f98a8a6c222f6134368c1f5" - }, - { - "ImportPath": "github.com/manucorporat/stats", - "Rev": "8f2d6ace262eba462e9beb552382c98be51d807b" - }, - { - "ImportPath": "github.com/mattn/go-colorable", - "Rev": "d67e0b7d1797975196499f79bcc322c08b9f218b" - }, - { - "ImportPath": "github.com/stretchr/testify/assert", - "Comment": "v1.0", - "Rev": "232e8563676cd15c3a36ba5e675ad4312ac4cb11" - }, - { - "ImportPath": "golang.org/x/net/context", - "Rev": "621fff363a1d9ad7fdd0bfa9d80a42881267deb4" - }, - { - "ImportPath": "gopkg.in/bluesuncorp/validator.v5", - "Comment": "v5.4", - "Rev": "07cbdd2e6dfd947b002e83c13b775c7580fab2d5" - } - ] -} diff --git a/vendor/github.com/gin-gonic/gin/README.md b/vendor/github.com/gin-gonic/gin/README.md index e83952d68..2a111d298 100644 --- a/vendor/github.com/gin-gonic/gin/README.md +++ b/vendor/github.com/gin-gonic/gin/README.md @@ -1,6 +1,6 @@ #Gin Web Framework - + [![Build Status](https://travis-ci.org/gin-gonic/gin.svg)](https://travis-ci.org/gin-gonic/gin) [![Coverage Status](https://coveralls.io/repos/gin-gonic/gin/badge.svg?branch=master)](https://coveralls.io/r/gin-gonic/gin?branch=master) [![GoDoc](https://godoc.org/github.com/gin-gonic/gin?status.svg)](https://godoc.org/github.com/gin-gonic/gin) @@ -12,7 +12,7 @@ Gin is a web framework written in Golang. It features a martini-like API with mu ![Gin console logger](https://gin-gonic.github.io/gin/other/console.png) -``` +```sh $ cat test.go ``` ```go @@ -23,9 +23,11 @@ import "github.com/gin-gonic/gin" func main() { r := gin.Default() r.GET("/ping", func(c *gin.Context) { - c.String(200, "pong") + c.JSON(200, gin.H{ + "message": "hello world", + }) }) - r.Run(":8080") // listen and serve on 0.0.0.0:8080 + r.Run() // listen and server on 0.0.0.0:8080 } ``` @@ -84,7 +86,7 @@ BenchmarkZeus_GithubAll | 2000 | 944234 | 300688 | 2648 1. Download and install it: ```sh -go get github.com/gin-gonic/gin +$ go get github.com/gin-gonic/gin ``` 2. Import it in your code: @@ -110,8 +112,10 @@ func main() { router.HEAD("/someHead", head) router.OPTIONS("/someOptions", options) - // Listen and server on 0.0.0.0:8080 - router.Run(":8080") + // By default it serves on :8080 unless a + // PORT environment variable was defined. + router.Run() + // router.Run.Run(":3000") for a hard coded port } ``` @@ -128,7 +132,7 @@ func main() { }) // However, this one will match /user/john/ and also /user/john/send - // If no other routers match /user/john, it will redirect to /user/join/ + // If no other routers match /user/john, it will redirect to /user/john/ router.GET("/user/:name/*action", func(c *gin.Context) { name := c.Param("name") action := c.Param("action") @@ -143,17 +147,17 @@ func main() { #### Querystring parameters ```go func main() { - router := gin.Default() + router := gin.Default() - // Query string parameters are parsed using the existing underlying request object. - // The request responds to a url matching: /welcome?firstname=Jane&lastname=Doe - router.GET("/welcome", func(c *gin.Context) { - firstname := c.DefaultQuery("firstname", "Guest") - lastname := c.Query("lastname") // shortcut for c.Request.URL.Query().Get("lastname") + // Query string parameters are parsed using the existing underlying request object. + // The request responds to a url matching: /welcome?firstname=Jane&lastname=Doe + router.GET("/welcome", func(c *gin.Context) { + firstname := c.DefaultQuery("firstname", "Guest") + lastname := c.Query("lastname") // shortcut for c.Request.URL.Query().Get("lastname") - c.String(http.StatusOK, "Hello %s %s", firstname, lastname) - }) - router.Run(":8080") + c.String(http.StatusOK, "Hello %s %s", firstname, lastname) + }) + router.Run(":8080") } ``` @@ -161,18 +165,19 @@ func main() { ```go func main() { - router := gin.Default() + router := gin.Default() - router.POST("/form_post", func(c *gin.Context) { - message := c.PostForm("message") - nick := c.DefaultPostForm("nick", "anonymous") + router.POST("/form_post", func(c *gin.Context) { + message := c.PostForm("message") + nick := c.DefaultPostForm("nick", "anonymous") - c.JSON(200, gin.H{ - "status": "posted", - "message": message, - }) - }) - router.Run(":8080") + c.JSON(200, gin.H{ + "status": "posted", + "message": message, + "nick": nick, + }) + }) + router.Run(":8080") } ``` @@ -190,19 +195,20 @@ func main() { router := gin.Default() router.POST("/post", func(c *gin.Context) { - id := c.Query("id") - page := c.DefaultQuery("id", "0") - name := c.PostForm("name") - message := c.PostForm("message") - fmt.Println("id: %s; page: %s; name: %s; message: %s", id, page, name, message) + id := c.Query("id") + page := c.DefaultQuery("page", "0") + name := c.PostForm("name") + message := c.PostForm("message") + + fmt.Printf("id: %s; page: %s; name: %s; message: %s", id, page, name, message) }) router.Run(":8080") } ``` ``` -id: 1234; page: 0; name: manu; message: this_is_great +id: 1234; page: 1; name: manu; message: this_is_great ``` @@ -301,30 +307,30 @@ type Login struct { func main() { router := gin.Default() - // Example for binding JSON ({"user": "manu", "password": "123"}) + // Example for binding JSON ({"user": "manu", "password": "123"}) router.POST("/loginJSON", func(c *gin.Context) { var json Login - if c.BindJSON(&json) == nil { - if json.User == "manu" && json.Password == "123" { - c.JSON(http.StatusOK, gin.H{"status": "you are logged in"}) - } else { - c.JSON(http.StatusUnauthorized, gin.H{"status": "unauthorized"}) - } - } + if c.BindJSON(&json) == nil { + if json.User == "manu" && json.Password == "123" { + c.JSON(http.StatusOK, gin.H{"status": "you are logged in"}) + } else { + c.JSON(http.StatusUnauthorized, gin.H{"status": "unauthorized"}) + } + } }) - // Example for binding a HTML form (user=manu&password=123) - router.POST("/loginForm", func(c *gin.Context) { - var form Login - // This will infer what binder to use depending on the content-type header. - if c.Bind(&form) == nil { - if form.User == "manu" && form.Password == "123" { - c.JSON(http.StatusOK, gin.H{"status": "you are logged in"}) - } else { - c.JSON(http.StatusUnauthorized, gin.H{"status": "unauthorized"}) - } - } - }) + // Example for binding a HTML form (user=manu&password=123) + router.POST("/loginForm", func(c *gin.Context) { + var form Login + // This will infer what binder to use depending on the content-type header. + if c.Bind(&form) == nil { + if form.User == "manu" && form.Password == "123" { + c.JSON(http.StatusOK, gin.H{"status": "you are logged in"}) + } else { + c.JSON(http.StatusUnauthorized, gin.H{"status": "unauthorized"}) + } + } + }) // Listen and server on 0.0.0.0:8080 router.Run(":8080") @@ -353,21 +359,21 @@ func main() { // c.BindWith(&form, binding.Form) // or you can simply use autobinding with Bind method: var form LoginForm - // in this case proper binding will be automatically selected + // in this case proper binding will be automatically selected if c.Bind(&form) == nil { - if form.User == "user" && form.Password == "password" { - c.JSON(200, gin.H{"status": "you are logged in"}) - } else { - c.JSON(401, gin.H{"status": "unauthorized"}) - } - } + if form.User == "user" && form.Password == "password" { + c.JSON(200, gin.H{"status": "you are logged in"}) + } else { + c.JSON(401, gin.H{"status": "unauthorized"}) + } + } }) router.Run(":8080") } ``` Test it with: -```bash +```sh $ curl -v --form user=user --form password=password http://localhost:8080/login ``` @@ -411,13 +417,13 @@ func main() { ```go func main() { - router := gin.Default() - router.Static("/assets", "./assets") - router.StaticFS("/more_static", http.Dir("my_file_system")) - router.StaticFile("/favicon.ico", "./resources/favicon.ico") + router := gin.Default() + router.Static("/assets", "./assets") + router.StaticFS("/more_static", http.Dir("my_file_system")) + router.StaticFile("/favicon.ico", "./resources/favicon.ico") - // Listen and server on 0.0.0.0:8080 - router.Run(":8080") + // Listen and server on 0.0.0.0:8080 + router.Run(":8080") } ``` @@ -438,11 +444,53 @@ func main() { router.Run(":8080") } ``` +templates/index.tmpl ```html + +

+ {{ .title }} +

+ +``` + +Using templates with same name in different directories + +```go +func main() { + router := gin.Default() + router.LoadHTMLGlob("templates/**/*") + router.GET("/posts/index", func(c *gin.Context) { + c.HTML(http.StatusOK, "posts/index.tmpl", gin.H{ + "title": "Posts", + }) + }) + router.GET("/users/index", func(c *gin.Context) { + c.HTML(http.StatusOK, "users/index.tmpl", gin.H{ + "title": "Users", + }) + }) + router.Run(":8080") +} +``` +templates/posts/index.tmpl +```html +{{ define "posts/index.tmpl" }}

{{ .title }}

+

Using posts/index.tmpl

+{{ end }} +``` +templates/users/index.tmpl +```html +{{ define "users/index.tmpl" }} +

+ {{ .title }} +

+

Using users/index.tmpl

+ +{{ end }} ``` You can also use your own html template render @@ -559,17 +607,16 @@ func main() { r.GET("/long_async", func(c *gin.Context) { // create copy to be used inside the goroutine - c_cp := c.Copy() + cCp := c.Copy() go func() { // simulate a long task with time.Sleep(). 5 seconds time.Sleep(5 * time.Second) // note than you are using the copied context "c_cp", IMPORTANT - log.Println("Done! in path " + c_cp.Request.URL.Path) + log.Println("Done! in path " + cCp.Request.URL.Path) }() }) - r.GET("/long_sync", func(c *gin.Context) { // simulate a long task with time.Sleep(). 5 seconds time.Sleep(5 * time.Second) @@ -578,8 +625,8 @@ func main() { log.Println("Done! in path " + c.Request.URL.Path) }) - // Listen and server on 0.0.0.0:8080 - r.Run(":8080") + // Listen and server on 0.0.0.0:8080 + r.Run(":8080") } ``` @@ -609,3 +656,22 @@ func main() { s.ListenAndServe() } ``` + +#### Graceful restart or stop + +Do you want to graceful restart or stop your web server? +There be some ways. + +We can using fvbock/endless to replace the default ListenAndServe + +Refer the issue for more details: + +https://github.com/gin-gonic/gin/issues/296 + +```go +router := gin.Default() +router.GET("/", handler) +// [...] +endless.ListenAndServe(":4242", router) + +``` diff --git a/vendor/github.com/gin-gonic/gin/auth.go b/vendor/github.com/gin-gonic/gin/auth.go index ab4e35d76..125e659f2 100644 --- a/vendor/github.com/gin-gonic/gin/auth.go +++ b/vendor/github.com/gin-gonic/gin/auth.go @@ -65,14 +65,10 @@ func BasicAuth(accounts Accounts) HandlerFunc { } func processAccounts(accounts Accounts) authPairs { - if len(accounts) == 0 { - panic("Empty list of authorized credentials") - } + assert1(len(accounts) > 0, "Empty list of authorized credentials") pairs := make(authPairs, 0, len(accounts)) for user, password := range accounts { - if len(user) == 0 { - panic("User can not be empty") - } + assert1(len(user) > 0, "User can not be empty") value := authorizationHeader(user, password) pairs = append(pairs, authPair{ Value: value, diff --git a/vendor/github.com/gin-gonic/gin/auth_test.go b/vendor/github.com/gin-gonic/gin/auth_test.go deleted file mode 100644 index b22d9ced6..000000000 --- a/vendor/github.com/gin-gonic/gin/auth_test.go +++ /dev/null @@ -1,146 +0,0 @@ -// Copyright 2014 Manu Martinez-Almeida. All rights reserved. -// Use of this source code is governed by a MIT style -// license that can be found in the LICENSE file. - -package gin - -import ( - "encoding/base64" - "net/http" - "net/http/httptest" - "testing" - - "github.com/stretchr/testify/assert" -) - -func TestBasicAuth(t *testing.T) { - pairs := processAccounts(Accounts{ - "admin": "password", - "foo": "bar", - "bar": "foo", - }) - - assert.Len(t, pairs, 3) - assert.Contains(t, pairs, authPair{ - User: "bar", - Value: "Basic YmFyOmZvbw==", - }) - assert.Contains(t, pairs, authPair{ - User: "foo", - Value: "Basic Zm9vOmJhcg==", - }) - assert.Contains(t, pairs, authPair{ - User: "admin", - Value: "Basic YWRtaW46cGFzc3dvcmQ=", - }) -} - -func TestBasicAuthFails(t *testing.T) { - assert.Panics(t, func() { processAccounts(nil) }) - assert.Panics(t, func() { - processAccounts(Accounts{ - "": "password", - "foo": "bar", - }) - }) -} - -func TestBasicAuthSearchCredential(t *testing.T) { - pairs := processAccounts(Accounts{ - "admin": "password", - "foo": "bar", - "bar": "foo", - }) - - user, found := pairs.searchCredential(authorizationHeader("admin", "password")) - assert.Equal(t, user, "admin") - assert.True(t, found) - - user, found = pairs.searchCredential(authorizationHeader("foo", "bar")) - assert.Equal(t, user, "foo") - assert.True(t, found) - - user, found = pairs.searchCredential(authorizationHeader("bar", "foo")) - assert.Equal(t, user, "bar") - assert.True(t, found) - - user, found = pairs.searchCredential(authorizationHeader("admins", "password")) - assert.Empty(t, user) - assert.False(t, found) - - user, found = pairs.searchCredential(authorizationHeader("foo", "bar ")) - assert.Empty(t, user) - assert.False(t, found) - - user, found = pairs.searchCredential("") - assert.Empty(t, user) - assert.False(t, found) -} - -func TestBasicAuthAuthorizationHeader(t *testing.T) { - assert.Equal(t, authorizationHeader("admin", "password"), "Basic YWRtaW46cGFzc3dvcmQ=") -} - -func TestBasicAuthSecureCompare(t *testing.T) { - assert.True(t, secureCompare("1234567890", "1234567890")) - assert.False(t, secureCompare("123456789", "1234567890")) - assert.False(t, secureCompare("12345678900", "1234567890")) - assert.False(t, secureCompare("1234567891", "1234567890")) -} - -func TestBasicAuthSucceed(t *testing.T) { - accounts := Accounts{"admin": "password"} - router := New() - router.Use(BasicAuth(accounts)) - router.GET("/login", func(c *Context) { - c.String(200, c.MustGet(AuthUserKey).(string)) - }) - - w := httptest.NewRecorder() - req, _ := http.NewRequest("GET", "/login", nil) - req.Header.Set("Authorization", authorizationHeader("admin", "password")) - router.ServeHTTP(w, req) - - assert.Equal(t, w.Code, 200) - assert.Equal(t, w.Body.String(), "admin") -} - -func TestBasicAuth401(t *testing.T) { - called := false - accounts := Accounts{"foo": "bar"} - router := New() - router.Use(BasicAuth(accounts)) - router.GET("/login", func(c *Context) { - called = true - c.String(200, c.MustGet(AuthUserKey).(string)) - }) - - w := httptest.NewRecorder() - req, _ := http.NewRequest("GET", "/login", nil) - req.Header.Set("Authorization", "Basic "+base64.StdEncoding.EncodeToString([]byte("admin:password"))) - router.ServeHTTP(w, req) - - assert.False(t, called) - assert.Equal(t, w.Code, 401) - assert.Equal(t, w.HeaderMap.Get("WWW-Authenticate"), "Basic realm=\"Authorization Required\"") -} - -func TestBasicAuth401WithCustomRealm(t *testing.T) { - called := false - accounts := Accounts{"foo": "bar"} - router := New() - router.Use(BasicAuthForRealm(accounts, "My Custom \"Realm\"")) - router.GET("/login", func(c *Context) { - called = true - c.String(200, c.MustGet(AuthUserKey).(string)) - }) - - w := httptest.NewRecorder() - req, _ := http.NewRequest("GET", "/login", nil) - req.Header.Set("Authorization", "Basic "+base64.StdEncoding.EncodeToString([]byte("admin:password"))) - router.ServeHTTP(w, req) - - assert.False(t, called) - assert.Equal(t, w.Code, 401) - assert.Equal(t, w.HeaderMap.Get("WWW-Authenticate"), "Basic realm=\"My Custom \\\"Realm\\\"\"") -} diff --git a/vendor/github.com/gin-gonic/gin/benchmarks_test.go b/vendor/github.com/gin-gonic/gin/benchmarks_test.go deleted file mode 100644 index 8a1c91a96..000000000 --- a/vendor/github.com/gin-gonic/gin/benchmarks_test.go +++ /dev/null @@ -1,157 +0,0 @@ -package gin - -import ( - "html/template" - "net/http" - "testing" -) - -func BenchmarkOneRoute(B *testing.B) { - router := New() - router.GET("/ping", func(c *Context) {}) - runRequest(B, router, "GET", "/ping") -} - -func BenchmarkRecoveryMiddleware(B *testing.B) { - router := New() - router.Use(Recovery()) - router.GET("/", func(c *Context) {}) - runRequest(B, router, "GET", "/") -} - -func BenchmarkLoggerMiddleware(B *testing.B) { - router := New() - router.Use(LoggerWithWriter(newMockWriter())) - router.GET("/", func(c *Context) {}) - runRequest(B, router, "GET", "/") -} - -func BenchmarkManyHandlers(B *testing.B) { - router := New() - router.Use(Recovery(), LoggerWithWriter(newMockWriter())) - router.Use(func(c *Context) {}) - router.Use(func(c *Context) {}) - router.GET("/ping", func(c *Context) {}) - runRequest(B, router, "GET", "/ping") -} - -func Benchmark5Params(B *testing.B) { - DefaultWriter = newMockWriter() - router := New() - router.Use(func(c *Context) {}) - router.GET("/param/:param1/:params2/:param3/:param4/:param5", func(c *Context) {}) - runRequest(B, router, "GET", "/param/path/to/parameter/john/12345") -} - -func BenchmarkOneRouteJSON(B *testing.B) { - router := New() - data := struct { - Status string `json:"status"` - }{"ok"} - router.GET("/json", func(c *Context) { - c.JSON(200, data) - }) - runRequest(B, router, "GET", "/json") -} - -var htmlContentType = []string{"text/html; charset=utf-8"} - -func BenchmarkOneRouteHTML(B *testing.B) { - router := New() - t := template.Must(template.New("index").Parse(` -

{{.}}

`)) - router.SetHTMLTemplate(t) - - router.GET("/html", func(c *Context) { - c.HTML(200, "index", "hola") - }) - runRequest(B, router, "GET", "/html") -} - -func BenchmarkOneRouteSet(B *testing.B) { - router := New() - router.GET("/ping", func(c *Context) { - c.Set("key", "value") - }) - runRequest(B, router, "GET", "/ping") -} - -func BenchmarkOneRouteString(B *testing.B) { - router := New() - router.GET("/text", func(c *Context) { - c.String(200, "this is a plain text") - }) - runRequest(B, router, "GET", "/text") -} - -func BenchmarkManyRoutesFist(B *testing.B) { - router := New() - router.Any("/ping", func(c *Context) {}) - runRequest(B, router, "GET", "/ping") -} - -func BenchmarkManyRoutesLast(B *testing.B) { - router := New() - router.Any("/ping", func(c *Context) {}) - runRequest(B, router, "OPTIONS", "/ping") -} - -func Benchmark404(B *testing.B) { - router := New() - router.Any("/something", func(c *Context) {}) - router.NoRoute(func(c *Context) {}) - runRequest(B, router, "GET", "/ping") -} - -func Benchmark404Many(B *testing.B) { - router := New() - router.GET("/", func(c *Context) {}) - router.GET("/path/to/something", func(c *Context) {}) - router.GET("/post/:id", func(c *Context) {}) - router.GET("/view/:id", func(c *Context) {}) - router.GET("/favicon.ico", func(c *Context) {}) - router.GET("/robots.txt", func(c *Context) {}) - router.GET("/delete/:id", func(c *Context) {}) - router.GET("/user/:id/:mode", func(c *Context) {}) - - router.NoRoute(func(c *Context) {}) - runRequest(B, router, "GET", "/viewfake") -} - -type mockWriter struct { - headers http.Header -} - -func newMockWriter() *mockWriter { - return &mockWriter{ - http.Header{}, - } -} - -func (m *mockWriter) Header() (h http.Header) { - return m.headers -} - -func (m *mockWriter) Write(p []byte) (n int, err error) { - return len(p), nil -} - -func (m *mockWriter) WriteString(s string) (n int, err error) { - return len(s), nil -} - -func (m *mockWriter) WriteHeader(int) {} - -func runRequest(B *testing.B, r *Engine, method, path string) { - // create fake request - req, err := http.NewRequest(method, path, nil) - if err != nil { - panic(err) - } - w := newMockWriter() - B.ReportAllocs() - B.ResetTimer() - for i := 0; i < B.N; i++ { - r.ServeHTTP(w, req) - } -} diff --git a/vendor/github.com/gin-gonic/gin/binding/binding.go b/vendor/github.com/gin-gonic/gin/binding/binding.go index 9cf701dfb..dc7397f1c 100644 --- a/vendor/github.com/gin-gonic/gin/binding/binding.go +++ b/vendor/github.com/gin-gonic/gin/binding/binding.go @@ -14,6 +14,7 @@ const ( MIMEPlain = "text/plain" MIMEPOSTForm = "application/x-www-form-urlencoded" MIMEMultipartPOSTForm = "multipart/form-data" + MIMEPROTOBUF = "application/x-protobuf" ) type Binding interface { @@ -38,6 +39,7 @@ var ( Form = formBinding{} FormPost = formPostBinding{} FormMultipart = formMultipartBinding{} + ProtoBuf = protobufBinding{} ) func Default(method, contentType string) Binding { @@ -49,6 +51,8 @@ func Default(method, contentType string) Binding { return JSON case MIMEXML, MIMEXML2: return XML + case MIMEPROTOBUF: + return ProtoBuf default: //case MIMEPOSTForm, MIMEMultipartPOSTForm: return Form } diff --git a/vendor/github.com/gin-gonic/gin/binding/binding_test.go b/vendor/github.com/gin-gonic/gin/binding/binding_test.go deleted file mode 100644 index 713e2e5af..000000000 --- a/vendor/github.com/gin-gonic/gin/binding/binding_test.go +++ /dev/null @@ -1,162 +0,0 @@ -// Copyright 2014 Manu Martinez-Almeida. All rights reserved. -// Use of this source code is governed by a MIT style -// license that can be found in the LICENSE file. - -package binding - -import ( - "bytes" - "mime/multipart" - "net/http" - "testing" - - "github.com/stretchr/testify/assert" -) - -type FooStruct struct { - Foo string `json:"foo" form:"foo" xml:"foo" binding:"required"` -} - -type FooBarStruct struct { - FooStruct - Bar string `json:"bar" form:"bar" xml:"bar" binding:"required"` -} - -func TestBindingDefault(t *testing.T) { - assert.Equal(t, Default("GET", ""), Form) - assert.Equal(t, Default("GET", MIMEJSON), Form) - - assert.Equal(t, Default("POST", MIMEJSON), JSON) - assert.Equal(t, Default("PUT", MIMEJSON), JSON) - - assert.Equal(t, Default("POST", MIMEXML), XML) - assert.Equal(t, Default("PUT", MIMEXML2), XML) - - assert.Equal(t, Default("POST", MIMEPOSTForm), Form) - assert.Equal(t, Default("PUT", MIMEPOSTForm), Form) - - assert.Equal(t, Default("POST", MIMEMultipartPOSTForm), Form) - assert.Equal(t, Default("PUT", MIMEMultipartPOSTForm), Form) -} - -func TestBindingJSON(t *testing.T) { - testBodyBinding(t, - JSON, "json", - "/", "/", - `{"foo": "bar"}`, `{"bar": "foo"}`) -} - -func TestBindingForm(t *testing.T) { - testFormBinding(t, "POST", - "/", "/", - "foo=bar&bar=foo", "bar2=foo") -} - -func TestBindingForm2(t *testing.T) { - testFormBinding(t, "GET", - "/?foo=bar&bar=foo", "/?bar2=foo", - "", "") -} - -func TestBindingXML(t *testing.T) { - testBodyBinding(t, - XML, "xml", - "/", "/", - "bar", "foo") -} - -func createFormPostRequest() *http.Request { - req, _ := http.NewRequest("POST", "/?foo=getfoo&bar=getbar", bytes.NewBufferString("foo=bar&bar=foo")) - req.Header.Set("Content-Type", MIMEPOSTForm) - return req -} - -func createFormMultipartRequest() *http.Request { - boundary := "--testboundary" - body := new(bytes.Buffer) - mw := multipart.NewWriter(body) - defer mw.Close() - - mw.SetBoundary(boundary) - mw.WriteField("foo", "bar") - mw.WriteField("bar", "foo") - req, _ := http.NewRequest("POST", "/?foo=getfoo&bar=getbar", body) - req.Header.Set("Content-Type", MIMEMultipartPOSTForm+"; boundary="+boundary) - return req -} - -func TestBindingFormPost(t *testing.T) { - req := createFormPostRequest() - var obj FooBarStruct - FormPost.Bind(req, &obj) - - assert.Equal(t, obj.Foo, "bar") - assert.Equal(t, obj.Bar, "foo") -} - -func TestBindingFormMultipart(t *testing.T) { - req := createFormMultipartRequest() - var obj FooBarStruct - FormMultipart.Bind(req, &obj) - - assert.Equal(t, obj.Foo, "bar") - assert.Equal(t, obj.Bar, "foo") -} - -func TestValidationFails(t *testing.T) { - var obj FooStruct - req := requestWithBody("POST", "/", `{"bar": "foo"}`) - err := JSON.Bind(req, &obj) - assert.Error(t, err) -} - -func TestValidationDisabled(t *testing.T) { - backup := Validator - Validator = nil - defer func() { Validator = backup }() - - var obj FooStruct - req := requestWithBody("POST", "/", `{"bar": "foo"}`) - err := JSON.Bind(req, &obj) - assert.NoError(t, err) -} - -func testFormBinding(t *testing.T, method, path, badPath, body, badBody string) { - b := Form - assert.Equal(t, b.Name(), "form") - - obj := FooBarStruct{} - req := requestWithBody(method, path, body) - if method == "POST" { - req.Header.Add("Content-Type", MIMEPOSTForm) - } - err := b.Bind(req, &obj) - assert.NoError(t, err) - assert.Equal(t, obj.Foo, "bar") - assert.Equal(t, obj.Bar, "foo") - - obj = FooBarStruct{} - req = requestWithBody(method, badPath, badBody) - err = JSON.Bind(req, &obj) - assert.Error(t, err) -} - -func testBodyBinding(t *testing.T, b Binding, name, path, badPath, body, badBody string) { - assert.Equal(t, b.Name(), name) - - obj := FooStruct{} - req := requestWithBody("POST", path, body) - err := b.Bind(req, &obj) - assert.NoError(t, err) - assert.Equal(t, obj.Foo, "bar") - - obj = FooStruct{} - req = requestWithBody("POST", badPath, badBody) - err = JSON.Bind(req, &obj) - assert.Error(t, err) -} - -func requestWithBody(method, path, body string) (req *http.Request) { - req, _ = http.NewRequest(method, path, bytes.NewBufferString(body)) - return -} diff --git a/vendor/github.com/gin-gonic/gin/binding/default_validator.go b/vendor/github.com/gin-gonic/gin/binding/default_validator.go index 7f12152b0..760728bbe 100644 --- a/vendor/github.com/gin-gonic/gin/binding/default_validator.go +++ b/vendor/github.com/gin-gonic/gin/binding/default_validator.go @@ -4,7 +4,7 @@ import ( "reflect" "sync" - "gopkg.in/bluesuncorp/validator.v5" + "gopkg.in/go-playground/validator.v8" ) type defaultValidator struct { @@ -26,7 +26,8 @@ func (v *defaultValidator) ValidateStruct(obj interface{}) error { func (v *defaultValidator) lazyinit() { v.once.Do(func() { - v.validate = validator.New("binding", validator.BakedInValidators) + config := &validator.Config{TagName: "binding"} + v.validate = validator.New(config) }) } diff --git a/vendor/github.com/gin-gonic/gin/binding/protobuf.go b/vendor/github.com/gin-gonic/gin/binding/protobuf.go new file mode 100644 index 000000000..d6bef029e --- /dev/null +++ b/vendor/github.com/gin-gonic/gin/binding/protobuf.go @@ -0,0 +1,35 @@ +// Copyright 2014 Manu Martinez-Almeida. All rights reserved. +// Use of this source code is governed by a MIT style +// license that can be found in the LICENSE file. + +package binding + +import ( + "github.com/golang/protobuf/proto" + + "io/ioutil" + "net/http" +) + +type protobufBinding struct{} + +func (_ protobufBinding) Name() string { + return "protobuf" +} + +func (_ protobufBinding) Bind(req *http.Request, obj interface{}) error { + + buf, err := ioutil.ReadAll(req.Body) + if err != nil { + return err + } + + if err = proto.Unmarshal(buf, obj.(proto.Message)); err != nil { + return err + } + + //Here it's same to return validate(obj), but util now we cann't add `binding:""` to the struct + //which automatically generate by gen-proto + return nil + //return validate(obj) +} diff --git a/vendor/github.com/gin-gonic/gin/binding/validate_test.go b/vendor/github.com/gin-gonic/gin/binding/validate_test.go deleted file mode 100644 index 27ba7b667..000000000 --- a/vendor/github.com/gin-gonic/gin/binding/validate_test.go +++ /dev/null @@ -1,69 +0,0 @@ -// Copyright 2014 Manu Martinez-Almeida. All rights reserved. -// Use of this source code is governed by a MIT style -// license that can be found in the LICENSE file. - -package binding - -import ( - "testing" - - "github.com/stretchr/testify/assert" -) - -type struct1 struct { - Value float64 `binding:"required"` -} - -type struct2 struct { - RequiredValue string `binding:"required"` - Value float64 -} - -type struct3 struct { - Integer int - String string - BasicSlice []int - Boolean bool - - RequiredInteger int `binding:"required"` - RequiredString string `binding:"required"` - RequiredAnotherStruct struct1 `binding:"required"` - RequiredBasicSlice []int `binding:"required"` - RequiredComplexSlice []struct2 `binding:"required"` - RequiredBoolean bool `binding:"required"` -} - -func createStruct() struct3 { - return struct3{ - RequiredInteger: 2, - RequiredString: "hello", - RequiredAnotherStruct: struct1{1.5}, - RequiredBasicSlice: []int{1, 2, 3, 4}, - RequiredComplexSlice: []struct2{ - {RequiredValue: "A"}, - {RequiredValue: "B"}, - }, - RequiredBoolean: true, - } -} - -func TestValidateGoodObject(t *testing.T) { - test := createStruct() - assert.Nil(t, validate(&test)) -} - -type Object map[string]interface{} -type MyObjects []Object - -func TestValidateSlice(t *testing.T) { - var obj MyObjects - var obj2 Object - var nu = 10 - - assert.NoError(t, validate(obj)) - assert.NoError(t, validate(&obj)) - assert.NoError(t, validate(obj2)) - assert.NoError(t, validate(&obj2)) - assert.NoError(t, validate(nu)) - assert.NoError(t, validate(&nu)) -} diff --git a/vendor/github.com/gin-gonic/gin/context.go b/vendor/github.com/gin-gonic/gin/context.go index b784c14bb..2fb69b738 100644 --- a/vendor/github.com/gin-gonic/gin/context.go +++ b/vendor/github.com/gin-gonic/gin/context.go @@ -8,7 +8,9 @@ import ( "errors" "io" "math" + "net" "net/http" + "net/url" "strings" "time" @@ -101,10 +103,10 @@ func (c *Context) IsAborted() bool { return c.index >= abortIndex } -// Abort stops the system to continue calling the pending handlers in the chain. -// Let's say you have an authorization middleware that validates if the request is authorized -// if the authorization fails (the password does not match). This method (Abort()) should be called -// in order to stop the execution of the actual handler. +// Abort prevents pending handlers from being called. Note that this will not stop the current handler. +// Let's say you have an authorization middleware that validates that the current request is authorized. If the +// authorization fails (ex: the password does not match), call Abort to ensure the remaining handlers +// for this request are not called. func (c *Context) Abort() { c.index = abortIndex } @@ -112,7 +114,7 @@ func (c *Context) Abort() { // AbortWithStatus calls `Abort()` and writes the headers with the specified status code. // For example, a failed attempt to authentificate a request could use: context.AbortWithStatus(401). func (c *Context) AbortWithStatus(code int) { - c.Writer.WriteHeader(code) + c.Status(code) c.Abort() } @@ -181,50 +183,52 @@ func (c *Context) MustGet(key string) interface{} { /************ INPUT DATA ************/ /************************************/ -// Query is a shortcut for c.Request.URL.Query().Get(key) -// It is used to return the url query values. -// ?id=1234&name=Manu -// c.Query("id") == "1234" -// c.Query("name") == "Manu" -// c.Query("wtf") == "" -func (c *Context) Query(key string) (va string) { - va, _ = c.query(key) - return -} - -// PostForm is a shortcut for c.Request.PostFormValue(key) -func (c *Context) PostForm(key string) (va string) { - va, _ = c.postForm(key) - return -} - -// Param is a shortcut for c.Params.ByName(key) +// Param returns the value of the URL param. +// It is a shortcut for c.Params.ByName(key) +// router.GET("/user/:id", func(c *gin.Context) { +// // a GET request to /user/john +// id := c.Param("id") // id == "john" +// }) func (c *Context) Param(key string) string { return c.Params.ByName(key) } -func (c *Context) DefaultPostForm(key, defaultValue string) string { - if va, ok := c.postForm(key); ok { - return va - } - return defaultValue +// Query returns the keyed url query value if it exists, +// othewise it returns an empty string `("")`. +// It is shortcut for `c.Request.URL.Query().Get(key)` +// GET /path?id=1234&name=Manu&value= +// c.Query("id") == "1234" +// c.Query("name") == "Manu" +// c.Query("value") == "" +// c.Query("wtf") == "" +func (c *Context) Query(key string) string { + value, _ := c.GetQuery(key) + return value } -// DefaultQuery returns the keyed url query value if it exists, othewise it returns the -// specified defaultValue. -// ``` -// /?name=Manu -// c.DefaultQuery("name", "unknown") == "Manu" -// c.DefaultQuery("id", "none") == "none" -// ``` +// DefaultQuery returns the keyed url query value if it exists, +// othewise it returns the specified defaultValue string. +// See: Query() and GetQuery() for further information. +// GET /?name=Manu&lastname= +// c.DefaultQuery("name", "unknown") == "Manu" +// c.DefaultQuery("id", "none") == "none" +// c.DefaultQuery("lastname", "none") == "" func (c *Context) DefaultQuery(key, defaultValue string) string { - if va, ok := c.query(key); ok { - return va + if value, ok := c.GetQuery(key); ok { + return value } return defaultValue } -func (c *Context) query(key string) (string, bool) { +// GetQuery is like Query(), it returns the keyed url query value +// if it exists `(value, true)` (even when the value is an empty string), +// othewise it returns `("", false)`. +// It is shortcut for `c.Request.URL.Query().Get(key)` +// GET /?name=Manu&lastname= +// ("Manu", true) == c.GetQuery("name") +// ("", false) == c.GetQuery("id") +// ("", true) == c.GetQuery("lastname") +func (c *Context) GetQuery(key string) (string, bool) { req := c.Request if values, ok := req.URL.Query()[key]; ok && len(values) > 0 { return values[0], true @@ -232,7 +236,31 @@ func (c *Context) query(key string) (string, bool) { return "", false } -func (c *Context) postForm(key string) (string, bool) { +// PostForm returns the specified key from a POST urlencoded form or multipart form +// when it exists, otherwise it returns an empty string `("")`. +func (c *Context) PostForm(key string) string { + value, _ := c.GetPostForm(key) + return value +} + +// PostForm returns the specified key from a POST urlencoded form or multipart form +// when it exists, otherwise it returns the specified defaultValue string. +// See: PostForm() and GetPostForm() for further information. +func (c *Context) DefaultPostForm(key, defaultValue string) string { + if value, ok := c.GetPostForm(key); ok { + return value + } + return defaultValue +} + +// GetPostForm is like PostForm(key). It returns the specified key from a POST urlencoded +// form or multipart form when it exists `(value, true)` (even when the value is an empty string), +// otherwise it returns ("", false). +// For example, during a PATCH request to update the user's email: +// email=mail@example.com --> ("mail@example.com", true) := GetPostForm("email") // set email to "mail@example.com" +// email= --> ("", true) := GetPostForm("email") // set email to "" +// --> ("", false) := GetPostForm("email") // do nothing with email +func (c *Context) GetPostForm(key string) (string, bool) { req := c.Request req.ParseMultipartForm(32 << 20) // 32 MB if values := req.PostForm[key]; len(values) > 0 { @@ -248,8 +276,8 @@ func (c *Context) postForm(key string) (string, bool) { // Bind checks the Content-Type to select a binding engine automatically, // Depending the "Content-Type" header different bindings are used: -// "application/json" --> JSON binding -// "application/xml" --> XML binding +// "application/json" --> JSON binding +// "application/xml" --> XML binding // otherwise --> returns an error // If Parses the request's body as JSON if Content-Type == "application/json" using JSON or XML as a JSON input. // It decodes the json payload into the struct specified as a pointer. @@ -291,7 +319,10 @@ func (c *Context) ClientIP() string { return clientIP } } - return strings.TrimSpace(c.Request.RemoteAddr) + if ip, _, err := net.SplitHostPort(strings.TrimSpace(c.Request.RemoteAddr)); err == nil { + return ip + } + return "" } // ContentType returns the Content-Type header of the request. @@ -310,6 +341,10 @@ func (c *Context) requestHeader(key string) string { /******** RESPONSE RENDERING ********/ /************************************/ +func (c *Context) Status(code int) { + c.writermem.WriteHeader(code) +} + // Header is a intelligent shortcut for c.Writer.Header().Set(key, value) // It writes a header in the response. // If value == "", this method removes the header `c.Writer.Header().Del(key)` @@ -321,16 +356,43 @@ func (c *Context) Header(key, value string) { } } -func (c *Context) Render(code int, r render.Render) { - c.writermem.WriteHeader(code) - if err := r.Render(c.Writer); err != nil { - c.renderError(err) +func (c *Context) SetCookie( + name string, + value string, + maxAge int, + path string, + domain string, + secure bool, + httpOnly bool, +) { + if path == "" { + path = "/" } + http.SetCookie(c.Writer, &http.Cookie{ + Name: name, + Value: url.QueryEscape(value), + MaxAge: maxAge, + Path: path, + Domain: domain, + Secure: secure, + HttpOnly: httpOnly, + }) } -func (c *Context) renderError(err error) { - debugPrintError(err) - c.AbortWithError(500, err).SetType(ErrorTypeRender) +func (c *Context) Cookie(name string) (string, error) { + cookie, err := c.Request.Cookie(name) + if err != nil { + return "", err + } + val, _ := url.QueryUnescape(cookie.Value) + return val, nil +} + +func (c *Context) Render(code int, r render.Render) { + c.Status(code) + if err := r.Render(c.Writer); err != nil { + panic(err) + } } // HTML renders the HTTP template specified by its file name. @@ -352,9 +414,9 @@ func (c *Context) IndentedJSON(code int, obj interface{}) { // JSON serializes the given struct as JSON into the response body. // It also sets the Content-Type as "application/json". func (c *Context) JSON(code int, obj interface{}) { - c.writermem.WriteHeader(code) + c.Status(code) if err := render.WriteJSON(c.Writer, obj); err != nil { - c.renderError(err) + panic(err) } } @@ -366,7 +428,7 @@ func (c *Context) XML(code int, obj interface{}) { // String writes the given string into the response body. func (c *Context) String(code int, format string, values ...interface{}) { - c.writermem.WriteHeader(code) + c.Status(code) render.WriteString(c.Writer, format, values) } @@ -408,9 +470,9 @@ func (c *Context) Stream(step func(w io.Writer) bool) { case <-clientGone: return default: - keepopen := step(w) + keepOpen := step(w) w.Flush() - if !keepopen { + if !keepOpen { return } } @@ -450,9 +512,8 @@ func (c *Context) Negotiate(code int, config Negotiate) { } func (c *Context) NegotiateFormat(offered ...string) string { - if len(offered) == 0 { - panic("you must provide at least one offer") - } + assert1(len(offered) > 0, "you must provide at least one offer") + if c.Accepted == nil { c.Accepted = parseAccept(c.requestHeader("Accept")) } diff --git a/vendor/github.com/gin-gonic/gin/context_test.go b/vendor/github.com/gin-gonic/gin/context_test.go deleted file mode 100644 index efdba7b24..000000000 --- a/vendor/github.com/gin-gonic/gin/context_test.go +++ /dev/null @@ -1,607 +0,0 @@ -// Copyright 2014 Manu Martinez-Almeida. All rights reserved. -// Use of this source code is governed by a MIT style -// license that can be found in the LICENSE file. - -package gin - -import ( - "bytes" - "errors" - "html/template" - "mime/multipart" - "net/http" - "net/http/httptest" - "testing" - "time" - - "github.com/manucorporat/sse" - "github.com/stretchr/testify/assert" -) - -// Unit tests TODO -// func (c *Context) File(filepath string) { -// func (c *Context) Negotiate(code int, config Negotiate) { -// BAD case: func (c *Context) Render(code int, render render.Render, obj ...interface{}) { -// test that information is not leaked when reusing Contexts (using the Pool) - -func createTestContext() (c *Context, w *httptest.ResponseRecorder, r *Engine) { - w = httptest.NewRecorder() - r = New() - c = r.allocateContext() - c.reset() - c.writermem.reset(w) - return -} - -func createMultipartRequest() *http.Request { - boundary := "--testboundary" - body := new(bytes.Buffer) - mw := multipart.NewWriter(body) - defer mw.Close() - - must(mw.SetBoundary(boundary)) - must(mw.WriteField("foo", "bar")) - must(mw.WriteField("bar", "foo")) - must(mw.WriteField("bar", "foo2")) - must(mw.WriteField("array", "first")) - must(mw.WriteField("array", "second")) - req, err := http.NewRequest("POST", "/", body) - must(err) - req.Header.Set("Content-Type", MIMEMultipartPOSTForm+"; boundary="+boundary) - return req -} - -func must(err error) { - if err != nil { - panic(err.Error()) - } -} - -func TestContextReset(t *testing.T) { - router := New() - c := router.allocateContext() - assert.Equal(t, c.engine, router) - - c.index = 2 - c.Writer = &responseWriter{ResponseWriter: httptest.NewRecorder()} - c.Params = Params{Param{}} - c.Error(errors.New("test")) - c.Set("foo", "bar") - c.reset() - - assert.False(t, c.IsAborted()) - assert.Nil(t, c.Keys) - assert.Nil(t, c.Accepted) - assert.Len(t, c.Errors, 0) - assert.Empty(t, c.Errors.Errors()) - assert.Empty(t, c.Errors.ByType(ErrorTypeAny)) - assert.Len(t, c.Params, 0) - assert.EqualValues(t, c.index, -1) - assert.Equal(t, c.Writer.(*responseWriter), &c.writermem) -} - -func TestContextHandlers(t *testing.T) { - c, _, _ := createTestContext() - assert.Nil(t, c.handlers) - assert.Nil(t, c.handlers.Last()) - - c.handlers = HandlersChain{} - assert.NotNil(t, c.handlers) - assert.Nil(t, c.handlers.Last()) - - f := func(c *Context) {} - g := func(c *Context) {} - - c.handlers = HandlersChain{f} - compareFunc(t, f, c.handlers.Last()) - - c.handlers = HandlersChain{f, g} - compareFunc(t, g, c.handlers.Last()) -} - -// TestContextSetGet tests that a parameter is set correctly on the -// current context and can be retrieved using Get. -func TestContextSetGet(t *testing.T) { - c, _, _ := createTestContext() - c.Set("foo", "bar") - - value, err := c.Get("foo") - assert.Equal(t, value, "bar") - assert.True(t, err) - - value, err = c.Get("foo2") - assert.Nil(t, value) - assert.False(t, err) - - assert.Equal(t, c.MustGet("foo"), "bar") - assert.Panics(t, func() { c.MustGet("no_exist") }) -} - -func TestContextSetGetValues(t *testing.T) { - c, _, _ := createTestContext() - c.Set("string", "this is a string") - c.Set("int32", int32(-42)) - c.Set("int64", int64(42424242424242)) - c.Set("uint64", uint64(42)) - c.Set("float32", float32(4.2)) - c.Set("float64", 4.2) - var a interface{} = 1 - c.Set("intInterface", a) - - assert.Exactly(t, c.MustGet("string").(string), "this is a string") - assert.Exactly(t, c.MustGet("int32").(int32), int32(-42)) - assert.Exactly(t, c.MustGet("int64").(int64), int64(42424242424242)) - assert.Exactly(t, c.MustGet("uint64").(uint64), uint64(42)) - assert.Exactly(t, c.MustGet("float32").(float32), float32(4.2)) - assert.Exactly(t, c.MustGet("float64").(float64), 4.2) - assert.Exactly(t, c.MustGet("intInterface").(int), 1) - -} - -func TestContextCopy(t *testing.T) { - c, _, _ := createTestContext() - c.index = 2 - c.Request, _ = http.NewRequest("POST", "/hola", nil) - c.handlers = HandlersChain{func(c *Context) {}} - c.Params = Params{Param{Key: "foo", Value: "bar"}} - c.Set("foo", "bar") - - cp := c.Copy() - assert.Nil(t, cp.handlers) - assert.Nil(t, cp.writermem.ResponseWriter) - assert.Equal(t, &cp.writermem, cp.Writer.(*responseWriter)) - assert.Equal(t, cp.Request, c.Request) - assert.Equal(t, cp.index, abortIndex) - assert.Equal(t, cp.Keys, c.Keys) - assert.Equal(t, cp.engine, c.engine) - assert.Equal(t, cp.Params, c.Params) -} - -func TestContextHandlerName(t *testing.T) { - c, _, _ := createTestContext() - c.handlers = HandlersChain{func(c *Context) {}, handlerNameTest} - - assert.Equal(t, c.HandlerName(), "github.com/gin-gonic/gin.handlerNameTest") -} - -func handlerNameTest(c *Context) { - -} - -func TestContextQuery(t *testing.T) { - c, _, _ := createTestContext() - c.Request, _ = http.NewRequest("GET", "http://example.com/?foo=bar&page=10", nil) - - assert.Equal(t, c.DefaultQuery("foo", "none"), "bar") - assert.Equal(t, c.Query("foo"), "bar") - assert.Empty(t, c.PostForm("foo")) - - assert.Equal(t, c.DefaultQuery("page", "0"), "10") - assert.Equal(t, c.Query("page"), "10") - assert.Empty(t, c.PostForm("page")) - - assert.Equal(t, c.DefaultQuery("NoKey", "nada"), "nada") - assert.Empty(t, c.Query("NoKey")) - assert.Empty(t, c.PostForm("NoKey")) -} - -func TestContextQueryAndPostForm(t *testing.T) { - c, _, _ := createTestContext() - body := bytes.NewBufferString("foo=bar&page=11&both=POST&foo=second") - c.Request, _ = http.NewRequest("POST", "/?both=GET&id=main&id=omit&array[]=first&array[]=second", body) - c.Request.Header.Add("Content-Type", MIMEPOSTForm) - - assert.Equal(t, c.DefaultPostForm("foo", "none"), "bar") - assert.Equal(t, c.PostForm("foo"), "bar") - assert.Empty(t, c.Query("foo")) - - assert.Equal(t, c.DefaultPostForm("page", "0"), "11") - assert.Equal(t, c.PostForm("page"), "11") - assert.Equal(t, c.Query("page"), "") - - assert.Equal(t, c.PostForm("both"), "POST") - assert.Equal(t, c.Query("both"), "GET") - - assert.Equal(t, c.DefaultPostForm("id", "000"), "000") - assert.Equal(t, c.Query("id"), "main") - assert.Empty(t, c.PostForm("id")) - - assert.Equal(t, c.DefaultPostForm("NoKey", "nada"), "nada") - assert.Empty(t, c.PostForm("NoKey")) - assert.Empty(t, c.Query("NoKey")) - - var obj struct { - Foo string `form:"foo"` - ID string `form:"id"` - Page string `form:"page"` - Both string `form:"both"` - Array []string `form:"array[]"` - } - assert.NoError(t, c.Bind(&obj)) - assert.Equal(t, obj.Foo, "bar") - assert.Equal(t, obj.ID, "main") - assert.Equal(t, obj.Page, "11") - assert.Equal(t, obj.Both, "POST") - assert.Equal(t, obj.Array, []string{"first", "second"}) -} - -func TestContextPostFormMultipart(t *testing.T) { - c, _, _ := createTestContext() - c.Request = createMultipartRequest() - - var obj struct { - Foo string `form:"foo"` - Bar string `form:"bar"` - Array []string `form:"array"` - } - assert.NoError(t, c.Bind(&obj)) - assert.Equal(t, obj.Bar, "foo") - assert.Equal(t, obj.Foo, "bar") - assert.Equal(t, obj.Array, []string{"first", "second"}) - - assert.Empty(t, c.Query("foo")) - assert.Empty(t, c.Query("bar")) - assert.Equal(t, c.PostForm("foo"), "bar") - assert.Equal(t, c.PostForm("array"), "first") - assert.Equal(t, c.PostForm("bar"), "foo") -} - -// Tests that the response is serialized as JSON -// and Content-Type is set to application/json -func TestContextRenderJSON(t *testing.T) { - c, w, _ := createTestContext() - c.JSON(201, H{"foo": "bar"}) - - assert.Equal(t, w.Code, 201) - assert.Equal(t, w.Body.String(), "{\"foo\":\"bar\"}\n") - assert.Equal(t, w.HeaderMap.Get("Content-Type"), "application/json; charset=utf-8") -} - -// Tests that the response is serialized as JSON -// we change the content-type before -func TestContextRenderAPIJSON(t *testing.T) { - c, w, _ := createTestContext() - c.Header("Content-Type", "application/vnd.api+json") - c.JSON(201, H{"foo": "bar"}) - - assert.Equal(t, w.Code, 201) - assert.Equal(t, w.Body.String(), "{\"foo\":\"bar\"}\n") - assert.Equal(t, w.HeaderMap.Get("Content-Type"), "application/vnd.api+json") -} - -// Tests that the response is serialized as JSON -// and Content-Type is set to application/json -func TestContextRenderIndentedJSON(t *testing.T) { - c, w, _ := createTestContext() - c.IndentedJSON(201, H{"foo": "bar", "bar": "foo", "nested": H{"foo": "bar"}}) - - assert.Equal(t, w.Code, 201) - assert.Equal(t, w.Body.String(), "{\n \"bar\": \"foo\",\n \"foo\": \"bar\",\n \"nested\": {\n \"foo\": \"bar\"\n }\n}") - assert.Equal(t, w.HeaderMap.Get("Content-Type"), "application/json; charset=utf-8") -} - -// Tests that the response executes the templates -// and responds with Content-Type set to text/html -func TestContextRenderHTML(t *testing.T) { - c, w, router := createTestContext() - templ := template.Must(template.New("t").Parse(`Hello {{.name}}`)) - router.SetHTMLTemplate(templ) - - c.HTML(201, "t", H{"name": "alexandernyquist"}) - - assert.Equal(t, w.Code, 201) - assert.Equal(t, w.Body.String(), "Hello alexandernyquist") - assert.Equal(t, w.HeaderMap.Get("Content-Type"), "text/html; charset=utf-8") -} - -// TestContextXML tests that the response is serialized as XML -// and Content-Type is set to application/xml -func TestContextRenderXML(t *testing.T) { - c, w, _ := createTestContext() - c.XML(201, H{"foo": "bar"}) - - assert.Equal(t, w.Code, 201) - assert.Equal(t, w.Body.String(), "bar") - assert.Equal(t, w.HeaderMap.Get("Content-Type"), "application/xml; charset=utf-8") -} - -// TestContextString tests that the response is returned -// with Content-Type set to text/plain -func TestContextRenderString(t *testing.T) { - c, w, _ := createTestContext() - c.String(201, "test %s %d", "string", 2) - - assert.Equal(t, w.Code, 201) - assert.Equal(t, w.Body.String(), "test string 2") - assert.Equal(t, w.HeaderMap.Get("Content-Type"), "text/plain; charset=utf-8") -} - -// TestContextString tests that the response is returned -// with Content-Type set to text/html -func TestContextRenderHTMLString(t *testing.T) { - c, w, _ := createTestContext() - c.Header("Content-Type", "text/html; charset=utf-8") - c.String(201, "%s %d", "string", 3) - - assert.Equal(t, w.Code, 201) - assert.Equal(t, w.Body.String(), "string 3") - assert.Equal(t, w.HeaderMap.Get("Content-Type"), "text/html; charset=utf-8") -} - -// TestContextData tests that the response can be written from `bytesting` -// with specified MIME type -func TestContextRenderData(t *testing.T) { - c, w, _ := createTestContext() - c.Data(201, "text/csv", []byte(`foo,bar`)) - - assert.Equal(t, w.Code, 201) - assert.Equal(t, w.Body.String(), "foo,bar") - assert.Equal(t, w.HeaderMap.Get("Content-Type"), "text/csv") -} - -func TestContextRenderSSE(t *testing.T) { - c, w, _ := createTestContext() - c.SSEvent("float", 1.5) - c.Render(-1, sse.Event{ - Id: "123", - Data: "text", - }) - c.SSEvent("chat", H{ - "foo": "bar", - "bar": "foo", - }) - - assert.Equal(t, w.Body.String(), "event:float\ndata:1.5\n\nid:123\ndata:text\n\nevent:chat\ndata:{\"bar\":\"foo\",\"foo\":\"bar\"}\n\n") -} - -func TestContextRenderFile(t *testing.T) { - c, w, _ := createTestContext() - c.Request, _ = http.NewRequest("GET", "/", nil) - c.File("./gin.go") - - assert.Equal(t, w.Code, 200) - assert.Contains(t, w.Body.String(), "func New() *Engine {") - assert.Equal(t, w.HeaderMap.Get("Content-Type"), "text/plain; charset=utf-8") -} - -func TestContextHeaders(t *testing.T) { - c, _, _ := createTestContext() - c.Header("Content-Type", "text/plain") - c.Header("X-Custom", "value") - - assert.Equal(t, c.Writer.Header().Get("Content-Type"), "text/plain") - assert.Equal(t, c.Writer.Header().Get("X-Custom"), "value") - - c.Header("Content-Type", "text/html") - c.Header("X-Custom", "") - - assert.Equal(t, c.Writer.Header().Get("Content-Type"), "text/html") - _, exist := c.Writer.Header()["X-Custom"] - assert.False(t, exist) -} - -// TODO -func TestContextRenderRedirectWithRelativePath(t *testing.T) { - c, w, _ := createTestContext() - c.Request, _ = http.NewRequest("POST", "http://example.com", nil) - assert.Panics(t, func() { c.Redirect(299, "/new_path") }) - assert.Panics(t, func() { c.Redirect(309, "/new_path") }) - - c.Redirect(302, "/path") - c.Writer.WriteHeaderNow() - assert.Equal(t, w.Code, 302) - assert.Equal(t, w.Header().Get("Location"), "/path") -} - -func TestContextRenderRedirectWithAbsolutePath(t *testing.T) { - c, w, _ := createTestContext() - c.Request, _ = http.NewRequest("POST", "http://example.com", nil) - c.Redirect(302, "http://google.com") - c.Writer.WriteHeaderNow() - - assert.Equal(t, w.Code, 302) - assert.Equal(t, w.Header().Get("Location"), "http://google.com") -} - -func TestContextNegotiationFormat(t *testing.T) { - c, _, _ := createTestContext() - c.Request, _ = http.NewRequest("POST", "", nil) - - assert.Panics(t, func() { c.NegotiateFormat() }) - assert.Equal(t, c.NegotiateFormat(MIMEJSON, MIMEXML), MIMEJSON) - assert.Equal(t, c.NegotiateFormat(MIMEHTML, MIMEJSON), MIMEHTML) -} - -func TestContextNegotiationFormatWithAccept(t *testing.T) { - c, _, _ := createTestContext() - c.Request, _ = http.NewRequest("POST", "/", nil) - c.Request.Header.Add("Accept", "text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8") - - assert.Equal(t, c.NegotiateFormat(MIMEJSON, MIMEXML), MIMEXML) - assert.Equal(t, c.NegotiateFormat(MIMEXML, MIMEHTML), MIMEHTML) - assert.Equal(t, c.NegotiateFormat(MIMEJSON), "") -} - -func TestContextNegotiationFormatCustum(t *testing.T) { - c, _, _ := createTestContext() - c.Request, _ = http.NewRequest("POST", "/", nil) - c.Request.Header.Add("Accept", "text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8") - - c.Accepted = nil - c.SetAccepted(MIMEJSON, MIMEXML) - - assert.Equal(t, c.NegotiateFormat(MIMEJSON, MIMEXML), MIMEJSON) - assert.Equal(t, c.NegotiateFormat(MIMEXML, MIMEHTML), MIMEXML) - assert.Equal(t, c.NegotiateFormat(MIMEJSON), MIMEJSON) -} - -func TestContextIsAborted(t *testing.T) { - c, _, _ := createTestContext() - assert.False(t, c.IsAborted()) - - c.Abort() - assert.True(t, c.IsAborted()) - - c.Next() - assert.True(t, c.IsAborted()) - - c.index++ - assert.True(t, c.IsAborted()) -} - -// TestContextData tests that the response can be written from `bytesting` -// with specified MIME type -func TestContextAbortWithStatus(t *testing.T) { - c, w, _ := createTestContext() - c.index = 4 - c.AbortWithStatus(401) - c.Writer.WriteHeaderNow() - - assert.Equal(t, c.index, abortIndex) - assert.Equal(t, c.Writer.Status(), 401) - assert.Equal(t, w.Code, 401) - assert.True(t, c.IsAborted()) -} - -func TestContextError(t *testing.T) { - c, _, _ := createTestContext() - assert.Empty(t, c.Errors) - - c.Error(errors.New("first error")) - assert.Len(t, c.Errors, 1) - assert.Equal(t, c.Errors.String(), "Error #01: first error\n") - - c.Error(&Error{ - Err: errors.New("second error"), - Meta: "some data 2", - Type: ErrorTypePublic, - }) - assert.Len(t, c.Errors, 2) - - assert.Equal(t, c.Errors[0].Err, errors.New("first error")) - assert.Nil(t, c.Errors[0].Meta) - assert.Equal(t, c.Errors[0].Type, ErrorTypePrivate) - - assert.Equal(t, c.Errors[1].Err, errors.New("second error")) - assert.Equal(t, c.Errors[1].Meta, "some data 2") - assert.Equal(t, c.Errors[1].Type, ErrorTypePublic) - - assert.Equal(t, c.Errors.Last(), c.Errors[1]) -} - -func TestContextTypedError(t *testing.T) { - c, _, _ := createTestContext() - c.Error(errors.New("externo 0")).SetType(ErrorTypePublic) - c.Error(errors.New("interno 0")).SetType(ErrorTypePrivate) - - for _, err := range c.Errors.ByType(ErrorTypePublic) { - assert.Equal(t, err.Type, ErrorTypePublic) - } - for _, err := range c.Errors.ByType(ErrorTypePrivate) { - assert.Equal(t, err.Type, ErrorTypePrivate) - } - assert.Equal(t, c.Errors.Errors(), []string{"externo 0", "interno 0"}) -} - -func TestContextAbortWithError(t *testing.T) { - c, w, _ := createTestContext() - c.AbortWithError(401, errors.New("bad input")).SetMeta("some input") - c.Writer.WriteHeaderNow() - - assert.Equal(t, w.Code, 401) - assert.Equal(t, c.index, abortIndex) - assert.True(t, c.IsAborted()) -} - -func TestContextClientIP(t *testing.T) { - c, _, _ := createTestContext() - c.Request, _ = http.NewRequest("POST", "/", nil) - - c.Request.Header.Set("X-Real-IP", " 10.10.10.10 ") - c.Request.Header.Set("X-Forwarded-For", " 20.20.20.20, 30.30.30.30") - c.Request.RemoteAddr = " 40.40.40.40 " - - assert.Equal(t, c.ClientIP(), "10.10.10.10") - - c.Request.Header.Del("X-Real-IP") - assert.Equal(t, c.ClientIP(), "20.20.20.20") - - c.Request.Header.Set("X-Forwarded-For", "30.30.30.30 ") - assert.Equal(t, c.ClientIP(), "30.30.30.30") - - c.Request.Header.Del("X-Forwarded-For") - assert.Equal(t, c.ClientIP(), "40.40.40.40") -} - -func TestContextContentType(t *testing.T) { - c, _, _ := createTestContext() - c.Request, _ = http.NewRequest("POST", "/", nil) - c.Request.Header.Set("Content-Type", "application/json; charset=utf-8") - - assert.Equal(t, c.ContentType(), "application/json") -} - -func TestContextAutoBindJSON(t *testing.T) { - c, _, _ := createTestContext() - c.Request, _ = http.NewRequest("POST", "/", bytes.NewBufferString("{\"foo\":\"bar\", \"bar\":\"foo\"}")) - c.Request.Header.Add("Content-Type", MIMEJSON) - - var obj struct { - Foo string `json:"foo"` - Bar string `json:"bar"` - } - assert.NoError(t, c.Bind(&obj)) - assert.Equal(t, obj.Bar, "foo") - assert.Equal(t, obj.Foo, "bar") - assert.Empty(t, c.Errors) -} - -func TestContextBindWithJSON(t *testing.T) { - c, w, _ := createTestContext() - c.Request, _ = http.NewRequest("POST", "/", bytes.NewBufferString("{\"foo\":\"bar\", \"bar\":\"foo\"}")) - c.Request.Header.Add("Content-Type", MIMEXML) // set fake content-type - - var obj struct { - Foo string `json:"foo"` - Bar string `json:"bar"` - } - assert.NoError(t, c.BindJSON(&obj)) - assert.Equal(t, obj.Bar, "foo") - assert.Equal(t, obj.Foo, "bar") - assert.Equal(t, w.Body.Len(), 0) -} - -func TestContextBadAutoBind(t *testing.T) { - c, w, _ := createTestContext() - c.Request, _ = http.NewRequest("POST", "http://example.com", bytes.NewBufferString("\"foo\":\"bar\", \"bar\":\"foo\"}")) - c.Request.Header.Add("Content-Type", MIMEJSON) - var obj struct { - Foo string `json:"foo"` - Bar string `json:"bar"` - } - - assert.False(t, c.IsAborted()) - assert.Error(t, c.Bind(&obj)) - c.Writer.WriteHeaderNow() - - assert.Empty(t, obj.Bar) - assert.Empty(t, obj.Foo) - assert.Equal(t, w.Code, 400) - assert.True(t, c.IsAborted()) -} - -func TestContextGolangContext(t *testing.T) { - c, _, _ := createTestContext() - c.Request, _ = http.NewRequest("POST", "/", bytes.NewBufferString("{\"foo\":\"bar\", \"bar\":\"foo\"}")) - assert.NoError(t, c.Err()) - assert.Nil(t, c.Done()) - ti, ok := c.Deadline() - assert.Equal(t, ti, time.Time{}) - assert.False(t, ok) - assert.Equal(t, c.Value(0), c.Request) - assert.Nil(t, c.Value("foo")) - - c.Set("foo", "bar") - assert.Equal(t, c.Value("foo"), "bar") - assert.Nil(t, c.Value(1)) -} diff --git a/vendor/github.com/gin-gonic/gin/debug.go b/vendor/github.com/gin-gonic/gin/debug.go index 0836fc563..a121591a8 100644 --- a/vendor/github.com/gin-gonic/gin/debug.go +++ b/vendor/github.com/gin-gonic/gin/debug.go @@ -24,7 +24,7 @@ func debugPrintRoute(httpMethod, absolutePath string, handlers HandlersChain) { if IsDebugging() { nuHandlers := len(handlers) handlerName := nameOfFunction(handlers.Last()) - debugPrint("%-5s %-25s --> %s (%d handlers)\n", httpMethod, absolutePath, handlerName, nuHandlers) + debugPrint("%-6s %-25s --> %s (%d handlers)\n", httpMethod, absolutePath, handlerName, nuHandlers) } } diff --git a/vendor/github.com/gin-gonic/gin/debug_test.go b/vendor/github.com/gin-gonic/gin/debug_test.go deleted file mode 100644 index 7a352e6ec..000000000 --- a/vendor/github.com/gin-gonic/gin/debug_test.go +++ /dev/null @@ -1,77 +0,0 @@ -// Copyright 2014 Manu Martinez-Almeida. All rights reserved. -// Use of this source code is governed by a MIT style -// license that can be found in the LICENSE file. - -package gin - -import ( - "bytes" - "errors" - "io" - "log" - "os" - "testing" - - "github.com/stretchr/testify/assert" -) - -// TODO -// func debugRoute(httpMethod, absolutePath string, handlers HandlersChain) { -// func debugPrint(format string, values ...interface{}) { - -func TestIsDebugging(t *testing.T) { - SetMode(DebugMode) - assert.True(t, IsDebugging()) - SetMode(ReleaseMode) - assert.False(t, IsDebugging()) - SetMode(TestMode) - assert.False(t, IsDebugging()) -} - -func TestDebugPrint(t *testing.T) { - var w bytes.Buffer - setup(&w) - defer teardown() - - SetMode(ReleaseMode) - debugPrint("DEBUG this!") - SetMode(TestMode) - debugPrint("DEBUG this!") - assert.Empty(t, w.String()) - - SetMode(DebugMode) - debugPrint("these are %d %s\n", 2, "error messages") - assert.Equal(t, w.String(), "[GIN-debug] these are 2 error messages\n") -} - -func TestDebugPrintError(t *testing.T) { - var w bytes.Buffer - setup(&w) - defer teardown() - - SetMode(DebugMode) - debugPrintError(nil) - assert.Empty(t, w.String()) - - debugPrintError(errors.New("this is an error")) - assert.Equal(t, w.String(), "[GIN-debug] [ERROR] this is an error\n") -} - -func TestDebugPrintRoutes(t *testing.T) { - var w bytes.Buffer - setup(&w) - defer teardown() - - debugPrintRoute("GET", "/path/to/route/:param", HandlersChain{func(c *Context) {}, handlerNameTest}) - assert.Equal(t, w.String(), "[GIN-debug] GET /path/to/route/:param --> github.com/gin-gonic/gin.handlerNameTest (2 handlers)\n") -} - -func setup(w io.Writer) { - SetMode(DebugMode) - log.SetOutput(w) -} - -func teardown() { - SetMode(TestMode) - log.SetOutput(os.Stdout) -} diff --git a/vendor/github.com/gin-gonic/gin/deprecated.go b/vendor/github.com/gin-gonic/gin/deprecated.go index b2e874f01..0488a9b01 100644 --- a/vendor/github.com/gin-gonic/gin/deprecated.go +++ b/vendor/github.com/gin-gonic/gin/deprecated.go @@ -3,3 +3,10 @@ // license that can be found in the LICENSE file. package gin + +import "log" + +func (c *Context) GetCookie(name string) (string, error) { + log.Println("GetCookie() method is deprecated. Use Cookie() instead.") + return c.Cookie(name) +} diff --git a/vendor/github.com/gin-gonic/gin/errors.go b/vendor/github.com/gin-gonic/gin/errors.go index e829c886b..bced19aa0 100644 --- a/vendor/github.com/gin-gonic/gin/errors.go +++ b/vendor/github.com/gin-gonic/gin/errors.go @@ -109,13 +109,11 @@ func (a errorMsgs) Last() *Error { } // Returns an array will all the error messages. -// Example -// ``` -// c.Error(errors.New("first")) -// c.Error(errors.New("second")) -// c.Error(errors.New("third")) -// c.Errors.Errors() // == []string{"first", "second", "third"} -// `` +// Example: +// c.Error(errors.New("first")) +// c.Error(errors.New("second")) +// c.Error(errors.New("third")) +// c.Errors.Errors() // == []string{"first", "second", "third"} func (a errorMsgs) Errors() []string { if len(a) == 0 { return nil diff --git a/vendor/github.com/gin-gonic/gin/errors_test.go b/vendor/github.com/gin-gonic/gin/errors_test.go deleted file mode 100644 index c9a3407b7..000000000 --- a/vendor/github.com/gin-gonic/gin/errors_test.go +++ /dev/null @@ -1,99 +0,0 @@ -// Copyright 2014 Manu Martinez-Almeida. All rights reserved. -// Use of this source code is governed by a MIT style -// license that can be found in the LICENSE file. - -package gin - -import ( - "encoding/json" - "errors" - "testing" - - "github.com/stretchr/testify/assert" -) - -func TestError(t *testing.T) { - baseError := errors.New("test error") - err := &Error{ - Err: baseError, - Type: ErrorTypePrivate, - } - assert.Equal(t, err.Error(), baseError.Error()) - assert.Equal(t, err.JSON(), H{"error": baseError.Error()}) - - assert.Equal(t, err.SetType(ErrorTypePublic), err) - assert.Equal(t, err.Type, ErrorTypePublic) - - assert.Equal(t, err.SetMeta("some data"), err) - assert.Equal(t, err.Meta, "some data") - assert.Equal(t, err.JSON(), H{ - "error": baseError.Error(), - "meta": "some data", - }) - - jsonBytes, _ := json.Marshal(err) - assert.Equal(t, string(jsonBytes), "{\"error\":\"test error\",\"meta\":\"some data\"}") - - err.SetMeta(H{ - "status": "200", - "data": "some data", - }) - assert.Equal(t, err.JSON(), H{ - "error": baseError.Error(), - "status": "200", - "data": "some data", - }) - - err.SetMeta(H{ - "error": "custom error", - "status": "200", - "data": "some data", - }) - assert.Equal(t, err.JSON(), H{ - "error": "custom error", - "status": "200", - "data": "some data", - }) -} - -func TestErrorSlice(t *testing.T) { - errs := errorMsgs{ - {Err: errors.New("first"), Type: ErrorTypePrivate}, - {Err: errors.New("second"), Type: ErrorTypePrivate, Meta: "some data"}, - {Err: errors.New("third"), Type: ErrorTypePublic, Meta: H{"status": "400"}}, - } - - assert.Equal(t, errs, errs.ByType(ErrorTypeAny)) - assert.Equal(t, errs.Last().Error(), "third") - assert.Equal(t, errs.Errors(), []string{"first", "second", "third"}) - assert.Equal(t, errs.ByType(ErrorTypePublic).Errors(), []string{"third"}) - assert.Equal(t, errs.ByType(ErrorTypePrivate).Errors(), []string{"first", "second"}) - assert.Equal(t, errs.ByType(ErrorTypePublic|ErrorTypePrivate).Errors(), []string{"first", "second", "third"}) - assert.Empty(t, errs.ByType(ErrorTypeBind)) - assert.Empty(t, errs.ByType(ErrorTypeBind).String()) - - assert.Equal(t, errs.String(), `Error #01: first -Error #02: second - Meta: some data -Error #03: third - Meta: map[status:400] -`) - assert.Equal(t, errs.JSON(), []interface{}{ - H{"error": "first"}, - H{"error": "second", "meta": "some data"}, - H{"error": "third", "status": "400"}, - }) - jsonBytes, _ := json.Marshal(errs) - assert.Equal(t, string(jsonBytes), "[{\"error\":\"first\"},{\"error\":\"second\",\"meta\":\"some data\"},{\"error\":\"third\",\"status\":\"400\"}]") - errs = errorMsgs{ - {Err: errors.New("first"), Type: ErrorTypePrivate}, - } - assert.Equal(t, errs.JSON(), H{"error": "first"}) - jsonBytes, _ = json.Marshal(errs) - assert.Equal(t, string(jsonBytes), "{\"error\":\"first\"}") - - errs = errorMsgs{} - assert.Nil(t, errs.Last()) - assert.Nil(t, errs.JSON()) - assert.Empty(t, errs.String()) -} diff --git a/vendor/github.com/gin-gonic/gin/examples/app-engine/README.md b/vendor/github.com/gin-gonic/gin/examples/app-engine/README.md deleted file mode 100644 index 48505de83..000000000 --- a/vendor/github.com/gin-gonic/gin/examples/app-engine/README.md +++ /dev/null @@ -1,7 +0,0 @@ -# Guide to run Gin under App Engine LOCAL Development Server - -1. Download, install and setup Go in your computer. (That includes setting your `$GOPATH`.) -2. Download SDK for your platform from here: `https://developers.google.com/appengine/downloads?hl=es#Google_App_Engine_SDK_for_Go` -3. Download Gin source code using: `$ go get github.com/gin-gonic/gin` -4. Navigate to examples folder: `$ cd $GOPATH/src/github.com/gin-gonic/gin/examples/` -5. Run it: `$ goapp serve app-engine/` \ No newline at end of file diff --git a/vendor/github.com/gin-gonic/gin/examples/app-engine/app.yaml b/vendor/github.com/gin-gonic/gin/examples/app-engine/app.yaml deleted file mode 100644 index 5f20cf3f2..000000000 --- a/vendor/github.com/gin-gonic/gin/examples/app-engine/app.yaml +++ /dev/null @@ -1,8 +0,0 @@ -application: hello -version: 1 -runtime: go -api_version: go1 - -handlers: -- url: /.* - script: _go_app \ No newline at end of file diff --git a/vendor/github.com/gin-gonic/gin/examples/app-engine/hello.go b/vendor/github.com/gin-gonic/gin/examples/app-engine/hello.go deleted file mode 100644 index f5daf824b..000000000 --- a/vendor/github.com/gin-gonic/gin/examples/app-engine/hello.go +++ /dev/null @@ -1,23 +0,0 @@ -package hello - -import ( - "net/http" - "github.com/gin-gonic/gin" -) - -// This function's name is a must. App Engine uses it to drive the requests properly. -func init() { - // Starts a new Gin instance with no middle-ware - r := gin.New() - - // Define your handlers - r.GET("/", func(c *gin.Context){ - c.String(200, "Hello World!") - }) - r.GET("/ping", func(c *gin.Context){ - c.String(200, "pong") - }) - - // Handle all requests using net/http - http.Handle("/", r) -} \ No newline at end of file diff --git a/vendor/github.com/gin-gonic/gin/examples/basic/main.go b/vendor/github.com/gin-gonic/gin/examples/basic/main.go deleted file mode 100644 index 80f2bd3c7..000000000 --- a/vendor/github.com/gin-gonic/gin/examples/basic/main.go +++ /dev/null @@ -1,56 +0,0 @@ -package main - -import ( - "github.com/gin-gonic/gin" -) - -var DB = make(map[string]string) - -func main() { - r := gin.Default() - - // Ping test - r.GET("/ping", func(c *gin.Context) { - c.String(200, "pong") - }) - - // Get user value - r.GET("/user/:name", func(c *gin.Context) { - user := c.Params.ByName("name") - value, ok := DB[user] - if ok { - c.JSON(200, gin.H{"user": user, "value": value}) - } else { - c.JSON(200, gin.H{"user": user, "status": "no value"}) - } - }) - - // Authorized group (uses gin.BasicAuth() middleware) - // Same than: - // authorized := r.Group("/") - // authorized.Use(gin.BasicAuth(gin.Credentials{ - // "foo": "bar", - // "manu": "123", - //})) - authorized := r.Group("/", gin.BasicAuth(gin.Accounts{ - "foo": "bar", // user:foo password:bar - "manu": "123", // user:manu password:123 - })) - - authorized.POST("admin", func(c *gin.Context) { - user := c.MustGet(gin.AuthUserKey).(string) - - // Parse JSON - var json struct { - Value string `json:"value" binding:"required"` - } - - if c.Bind(&json) == nil { - DB[user] = json.Value - c.JSON(200, gin.H{"status": "ok"}) - } - }) - - // Listen and Server in 0.0.0.0:8080 - r.Run(":8080") -} diff --git a/vendor/github.com/gin-gonic/gin/examples/realtime-advanced/main.go b/vendor/github.com/gin-gonic/gin/examples/realtime-advanced/main.go deleted file mode 100644 index 1f3c8585f..000000000 --- a/vendor/github.com/gin-gonic/gin/examples/realtime-advanced/main.go +++ /dev/null @@ -1,39 +0,0 @@ -package main - -import ( - "fmt" - "runtime" - - "github.com/gin-gonic/gin" -) - -func main() { - ConfigRuntime() - StartWorkers() - StartGin() -} - -func ConfigRuntime() { - nuCPU := runtime.NumCPU() - runtime.GOMAXPROCS(nuCPU) - fmt.Printf("Running with %d CPUs\n", nuCPU) -} - -func StartWorkers() { - go statsWorker() -} - -func StartGin() { - gin.SetMode(gin.ReleaseMode) - - router := gin.New() - router.Use(rateLimit, gin.Recovery()) - router.LoadHTMLGlob("resources/*.templ.html") - router.Static("/static", "resources/static") - router.GET("/", index) - router.GET("/room/:roomid", roomGET) - router.POST("/room-post/:roomid", roomPOST) - router.GET("/stream/:roomid", streamRoom) - - router.Run(":80") -} diff --git a/vendor/github.com/gin-gonic/gin/examples/realtime-advanced/resources/static/epoch.min.css b/vendor/github.com/gin-gonic/gin/examples/realtime-advanced/resources/static/epoch.min.css deleted file mode 100644 index 47a80cdc2..000000000 --- a/vendor/github.com/gin-gonic/gin/examples/realtime-advanced/resources/static/epoch.min.css +++ /dev/null @@ -1 +0,0 @@ -.epoch .axis path,.epoch .axis line{shape-rendering:crispEdges;}.epoch .axis.canvas .tick line{shape-rendering:geometricPrecision;}div#_canvas_css_reference{width:0;height:0;position:absolute;top:-1000px;left:-1000px;}div#_canvas_css_reference svg{position:absolute;width:0;height:0;top:-1000px;left:-1000px;}.epoch{font-family:"Helvetica Neue",Helvetica,Arial,sans-serif;font-size:12pt;}.epoch .axis path,.epoch .axis line{fill:none;stroke:#000;}.epoch .axis .tick text{font-size:9pt;}.epoch .line{fill:none;stroke-width:2px;}.epoch.sparklines .line{stroke-width:1px;}.epoch .area{stroke:none;}.epoch .arc.pie{stroke:#fff;stroke-width:1.5px;}.epoch .arc.pie text{stroke:none;fill:white;font-size:9pt;}.epoch .gauge-labels .value{text-anchor:middle;font-size:140%;fill:#666;}.epoch.gauge-tiny{width:120px;height:90px;}.epoch.gauge-tiny .gauge-labels .value{font-size:80%;}.epoch.gauge-tiny .gauge .arc.outer{stroke-width:2px;}.epoch.gauge-small{width:180px;height:135px;}.epoch.gauge-small .gauge-labels .value{font-size:120%;}.epoch.gauge-small .gauge .arc.outer{stroke-width:3px;}.epoch.gauge-medium{width:240px;height:180px;}.epoch.gauge-medium .gauge .arc.outer{stroke-width:3px;}.epoch.gauge-large{width:320px;height:240px;}.epoch.gauge-large .gauge-labels .value{font-size:180%;}.epoch .gauge .arc.outer{stroke-width:4px;stroke:#666;}.epoch .gauge .arc.inner{stroke-width:1px;stroke:#555;}.epoch .gauge .tick{stroke-width:1px;stroke:#555;}.epoch .gauge .needle{fill:orange;}.epoch .gauge .needle-base{fill:#666;}.epoch div.ref.category1,.epoch.category10 div.ref.category1{background-color:#1f77b4;}.epoch .category1 .line,.epoch.category10 .category1 .line{stroke:#1f77b4;}.epoch .category1 .area,.epoch .category1 .dot,.epoch.category10 .category1 .area,.epoch.category10 .category1 .dot{fill:#1f77b4;stroke:rgba(0, 0, 0, 0);}.epoch .arc.category1 path,.epoch.category10 .arc.category1 path{fill:#1f77b4;}.epoch .bar.category1,.epoch.category10 .bar.category1{fill:#1f77b4;}.epoch div.ref.category2,.epoch.category10 div.ref.category2{background-color:#ff7f0e;}.epoch .category2 .line,.epoch.category10 .category2 .line{stroke:#ff7f0e;}.epoch .category2 .area,.epoch .category2 .dot,.epoch.category10 .category2 .area,.epoch.category10 .category2 .dot{fill:#ff7f0e;stroke:rgba(0, 0, 0, 0);}.epoch .arc.category2 path,.epoch.category10 .arc.category2 path{fill:#ff7f0e;}.epoch .bar.category2,.epoch.category10 .bar.category2{fill:#ff7f0e;}.epoch div.ref.category3,.epoch.category10 div.ref.category3{background-color:#2ca02c;}.epoch .category3 .line,.epoch.category10 .category3 .line{stroke:#2ca02c;}.epoch .category3 .area,.epoch .category3 .dot,.epoch.category10 .category3 .area,.epoch.category10 .category3 .dot{fill:#2ca02c;stroke:rgba(0, 0, 0, 0);}.epoch .arc.category3 path,.epoch.category10 .arc.category3 path{fill:#2ca02c;}.epoch .bar.category3,.epoch.category10 .bar.category3{fill:#2ca02c;}.epoch div.ref.category4,.epoch.category10 div.ref.category4{background-color:#d62728;}.epoch .category4 .line,.epoch.category10 .category4 .line{stroke:#d62728;}.epoch .category4 .area,.epoch .category4 .dot,.epoch.category10 .category4 .area,.epoch.category10 .category4 .dot{fill:#d62728;stroke:rgba(0, 0, 0, 0);}.epoch .arc.category4 path,.epoch.category10 .arc.category4 path{fill:#d62728;}.epoch .bar.category4,.epoch.category10 .bar.category4{fill:#d62728;}.epoch div.ref.category5,.epoch.category10 div.ref.category5{background-color:#9467bd;}.epoch .category5 .line,.epoch.category10 .category5 .line{stroke:#9467bd;}.epoch .category5 .area,.epoch .category5 .dot,.epoch.category10 .category5 .area,.epoch.category10 .category5 .dot{fill:#9467bd;stroke:rgba(0, 0, 0, 0);}.epoch .arc.category5 path,.epoch.category10 .arc.category5 path{fill:#9467bd;}.epoch .bar.category5,.epoch.category10 .bar.category5{fill:#9467bd;}.epoch div.ref.category6,.epoch.category10 div.ref.category6{background-color:#8c564b;}.epoch .category6 .line,.epoch.category10 .category6 .line{stroke:#8c564b;}.epoch .category6 .area,.epoch .category6 .dot,.epoch.category10 .category6 .area,.epoch.category10 .category6 .dot{fill:#8c564b;stroke:rgba(0, 0, 0, 0);}.epoch .arc.category6 path,.epoch.category10 .arc.category6 path{fill:#8c564b;}.epoch .bar.category6,.epoch.category10 .bar.category6{fill:#8c564b;}.epoch div.ref.category7,.epoch.category10 div.ref.category7{background-color:#e377c2;}.epoch .category7 .line,.epoch.category10 .category7 .line{stroke:#e377c2;}.epoch .category7 .area,.epoch .category7 .dot,.epoch.category10 .category7 .area,.epoch.category10 .category7 .dot{fill:#e377c2;stroke:rgba(0, 0, 0, 0);}.epoch .arc.category7 path,.epoch.category10 .arc.category7 path{fill:#e377c2;}.epoch .bar.category7,.epoch.category10 .bar.category7{fill:#e377c2;}.epoch div.ref.category8,.epoch.category10 div.ref.category8{background-color:#7f7f7f;}.epoch .category8 .line,.epoch.category10 .category8 .line{stroke:#7f7f7f;}.epoch .category8 .area,.epoch .category8 .dot,.epoch.category10 .category8 .area,.epoch.category10 .category8 .dot{fill:#7f7f7f;stroke:rgba(0, 0, 0, 0);}.epoch .arc.category8 path,.epoch.category10 .arc.category8 path{fill:#7f7f7f;}.epoch .bar.category8,.epoch.category10 .bar.category8{fill:#7f7f7f;}.epoch div.ref.category9,.epoch.category10 div.ref.category9{background-color:#bcbd22;}.epoch .category9 .line,.epoch.category10 .category9 .line{stroke:#bcbd22;}.epoch .category9 .area,.epoch .category9 .dot,.epoch.category10 .category9 .area,.epoch.category10 .category9 .dot{fill:#bcbd22;stroke:rgba(0, 0, 0, 0);}.epoch .arc.category9 path,.epoch.category10 .arc.category9 path{fill:#bcbd22;}.epoch .bar.category9,.epoch.category10 .bar.category9{fill:#bcbd22;}.epoch div.ref.category10,.epoch.category10 div.ref.category10{background-color:#17becf;}.epoch .category10 .line,.epoch.category10 .category10 .line{stroke:#17becf;}.epoch .category10 .area,.epoch .category10 .dot,.epoch.category10 .category10 .area,.epoch.category10 .category10 .dot{fill:#17becf;stroke:rgba(0, 0, 0, 0);}.epoch .arc.category10 path,.epoch.category10 .arc.category10 path{fill:#17becf;}.epoch .bar.category10,.epoch.category10 .bar.category10{fill:#17becf;}.epoch.category20 div.ref.category1{background-color:#1f77b4;}.epoch.category20 .category1 .line{stroke:#1f77b4;}.epoch.category20 .category1 .area,.epoch.category20 .category1 .dot{fill:#1f77b4;stroke:rgba(0, 0, 0, 0);}.epoch.category20 .arc.category1 path{fill:#1f77b4;}.epoch.category20 .bar.category1{fill:#1f77b4;}.epoch.category20 div.ref.category2{background-color:#aec7e8;}.epoch.category20 .category2 .line{stroke:#aec7e8;}.epoch.category20 .category2 .area,.epoch.category20 .category2 .dot{fill:#aec7e8;stroke:rgba(0, 0, 0, 0);}.epoch.category20 .arc.category2 path{fill:#aec7e8;}.epoch.category20 .bar.category2{fill:#aec7e8;}.epoch.category20 div.ref.category3{background-color:#ff7f0e;}.epoch.category20 .category3 .line{stroke:#ff7f0e;}.epoch.category20 .category3 .area,.epoch.category20 .category3 .dot{fill:#ff7f0e;stroke:rgba(0, 0, 0, 0);}.epoch.category20 .arc.category3 path{fill:#ff7f0e;}.epoch.category20 .bar.category3{fill:#ff7f0e;}.epoch.category20 div.ref.category4{background-color:#ffbb78;}.epoch.category20 .category4 .line{stroke:#ffbb78;}.epoch.category20 .category4 .area,.epoch.category20 .category4 .dot{fill:#ffbb78;stroke:rgba(0, 0, 0, 0);}.epoch.category20 .arc.category4 path{fill:#ffbb78;}.epoch.category20 .bar.category4{fill:#ffbb78;}.epoch.category20 div.ref.category5{background-color:#2ca02c;}.epoch.category20 .category5 .line{stroke:#2ca02c;}.epoch.category20 .category5 .area,.epoch.category20 .category5 .dot{fill:#2ca02c;stroke:rgba(0, 0, 0, 0);}.epoch.category20 .arc.category5 path{fill:#2ca02c;}.epoch.category20 .bar.category5{fill:#2ca02c;}.epoch.category20 div.ref.category6{background-color:#98df8a;}.epoch.category20 .category6 .line{stroke:#98df8a;}.epoch.category20 .category6 .area,.epoch.category20 .category6 .dot{fill:#98df8a;stroke:rgba(0, 0, 0, 0);}.epoch.category20 .arc.category6 path{fill:#98df8a;}.epoch.category20 .bar.category6{fill:#98df8a;}.epoch.category20 div.ref.category7{background-color:#d62728;}.epoch.category20 .category7 .line{stroke:#d62728;}.epoch.category20 .category7 .area,.epoch.category20 .category7 .dot{fill:#d62728;stroke:rgba(0, 0, 0, 0);}.epoch.category20 .arc.category7 path{fill:#d62728;}.epoch.category20 .bar.category7{fill:#d62728;}.epoch.category20 div.ref.category8{background-color:#ff9896;}.epoch.category20 .category8 .line{stroke:#ff9896;}.epoch.category20 .category8 .area,.epoch.category20 .category8 .dot{fill:#ff9896;stroke:rgba(0, 0, 0, 0);}.epoch.category20 .arc.category8 path{fill:#ff9896;}.epoch.category20 .bar.category8{fill:#ff9896;}.epoch.category20 div.ref.category9{background-color:#9467bd;}.epoch.category20 .category9 .line{stroke:#9467bd;}.epoch.category20 .category9 .area,.epoch.category20 .category9 .dot{fill:#9467bd;stroke:rgba(0, 0, 0, 0);}.epoch.category20 .arc.category9 path{fill:#9467bd;}.epoch.category20 .bar.category9{fill:#9467bd;}.epoch.category20 div.ref.category10{background-color:#c5b0d5;}.epoch.category20 .category10 .line{stroke:#c5b0d5;}.epoch.category20 .category10 .area,.epoch.category20 .category10 .dot{fill:#c5b0d5;stroke:rgba(0, 0, 0, 0);}.epoch.category20 .arc.category10 path{fill:#c5b0d5;}.epoch.category20 .bar.category10{fill:#c5b0d5;}.epoch.category20 div.ref.category11{background-color:#8c564b;}.epoch.category20 .category11 .line{stroke:#8c564b;}.epoch.category20 .category11 .area,.epoch.category20 .category11 .dot{fill:#8c564b;stroke:rgba(0, 0, 0, 0);}.epoch.category20 .arc.category11 path{fill:#8c564b;}.epoch.category20 .bar.category11{fill:#8c564b;}.epoch.category20 div.ref.category12{background-color:#c49c94;}.epoch.category20 .category12 .line{stroke:#c49c94;}.epoch.category20 .category12 .area,.epoch.category20 .category12 .dot{fill:#c49c94;stroke:rgba(0, 0, 0, 0);}.epoch.category20 .arc.category12 path{fill:#c49c94;}.epoch.category20 .bar.category12{fill:#c49c94;}.epoch.category20 div.ref.category13{background-color:#e377c2;}.epoch.category20 .category13 .line{stroke:#e377c2;}.epoch.category20 .category13 .area,.epoch.category20 .category13 .dot{fill:#e377c2;stroke:rgba(0, 0, 0, 0);}.epoch.category20 .arc.category13 path{fill:#e377c2;}.epoch.category20 .bar.category13{fill:#e377c2;}.epoch.category20 div.ref.category14{background-color:#f7b6d2;}.epoch.category20 .category14 .line{stroke:#f7b6d2;}.epoch.category20 .category14 .area,.epoch.category20 .category14 .dot{fill:#f7b6d2;stroke:rgba(0, 0, 0, 0);}.epoch.category20 .arc.category14 path{fill:#f7b6d2;}.epoch.category20 .bar.category14{fill:#f7b6d2;}.epoch.category20 div.ref.category15{background-color:#7f7f7f;}.epoch.category20 .category15 .line{stroke:#7f7f7f;}.epoch.category20 .category15 .area,.epoch.category20 .category15 .dot{fill:#7f7f7f;stroke:rgba(0, 0, 0, 0);}.epoch.category20 .arc.category15 path{fill:#7f7f7f;}.epoch.category20 .bar.category15{fill:#7f7f7f;}.epoch.category20 div.ref.category16{background-color:#c7c7c7;}.epoch.category20 .category16 .line{stroke:#c7c7c7;}.epoch.category20 .category16 .area,.epoch.category20 .category16 .dot{fill:#c7c7c7;stroke:rgba(0, 0, 0, 0);}.epoch.category20 .arc.category16 path{fill:#c7c7c7;}.epoch.category20 .bar.category16{fill:#c7c7c7;}.epoch.category20 div.ref.category17{background-color:#bcbd22;}.epoch.category20 .category17 .line{stroke:#bcbd22;}.epoch.category20 .category17 .area,.epoch.category20 .category17 .dot{fill:#bcbd22;stroke:rgba(0, 0, 0, 0);}.epoch.category20 .arc.category17 path{fill:#bcbd22;}.epoch.category20 .bar.category17{fill:#bcbd22;}.epoch.category20 div.ref.category18{background-color:#dbdb8d;}.epoch.category20 .category18 .line{stroke:#dbdb8d;}.epoch.category20 .category18 .area,.epoch.category20 .category18 .dot{fill:#dbdb8d;stroke:rgba(0, 0, 0, 0);}.epoch.category20 .arc.category18 path{fill:#dbdb8d;}.epoch.category20 .bar.category18{fill:#dbdb8d;}.epoch.category20 div.ref.category19{background-color:#17becf;}.epoch.category20 .category19 .line{stroke:#17becf;}.epoch.category20 .category19 .area,.epoch.category20 .category19 .dot{fill:#17becf;stroke:rgba(0, 0, 0, 0);}.epoch.category20 .arc.category19 path{fill:#17becf;}.epoch.category20 .bar.category19{fill:#17becf;}.epoch.category20 div.ref.category20{background-color:#9edae5;}.epoch.category20 .category20 .line{stroke:#9edae5;}.epoch.category20 .category20 .area,.epoch.category20 .category20 .dot{fill:#9edae5;stroke:rgba(0, 0, 0, 0);}.epoch.category20 .arc.category20 path{fill:#9edae5;}.epoch.category20 .bar.category20{fill:#9edae5;}.epoch.category20b div.ref.category1{background-color:#393b79;}.epoch.category20b .category1 .line{stroke:#393b79;}.epoch.category20b .category1 .area,.epoch.category20b .category1 .dot{fill:#393b79;stroke:rgba(0, 0, 0, 0);}.epoch.category20b .arc.category1 path{fill:#393b79;}.epoch.category20b .bar.category1{fill:#393b79;}.epoch.category20b div.ref.category2{background-color:#5254a3;}.epoch.category20b .category2 .line{stroke:#5254a3;}.epoch.category20b .category2 .area,.epoch.category20b .category2 .dot{fill:#5254a3;stroke:rgba(0, 0, 0, 0);}.epoch.category20b .arc.category2 path{fill:#5254a3;}.epoch.category20b .bar.category2{fill:#5254a3;}.epoch.category20b div.ref.category3{background-color:#6b6ecf;}.epoch.category20b .category3 .line{stroke:#6b6ecf;}.epoch.category20b .category3 .area,.epoch.category20b .category3 .dot{fill:#6b6ecf;stroke:rgba(0, 0, 0, 0);}.epoch.category20b .arc.category3 path{fill:#6b6ecf;}.epoch.category20b .bar.category3{fill:#6b6ecf;}.epoch.category20b div.ref.category4{background-color:#9c9ede;}.epoch.category20b .category4 .line{stroke:#9c9ede;}.epoch.category20b .category4 .area,.epoch.category20b .category4 .dot{fill:#9c9ede;stroke:rgba(0, 0, 0, 0);}.epoch.category20b .arc.category4 path{fill:#9c9ede;}.epoch.category20b .bar.category4{fill:#9c9ede;}.epoch.category20b div.ref.category5{background-color:#637939;}.epoch.category20b .category5 .line{stroke:#637939;}.epoch.category20b .category5 .area,.epoch.category20b .category5 .dot{fill:#637939;stroke:rgba(0, 0, 0, 0);}.epoch.category20b .arc.category5 path{fill:#637939;}.epoch.category20b .bar.category5{fill:#637939;}.epoch.category20b div.ref.category6{background-color:#8ca252;}.epoch.category20b .category6 .line{stroke:#8ca252;}.epoch.category20b .category6 .area,.epoch.category20b .category6 .dot{fill:#8ca252;stroke:rgba(0, 0, 0, 0);}.epoch.category20b .arc.category6 path{fill:#8ca252;}.epoch.category20b .bar.category6{fill:#8ca252;}.epoch.category20b div.ref.category7{background-color:#b5cf6b;}.epoch.category20b .category7 .line{stroke:#b5cf6b;}.epoch.category20b .category7 .area,.epoch.category20b .category7 .dot{fill:#b5cf6b;stroke:rgba(0, 0, 0, 0);}.epoch.category20b .arc.category7 path{fill:#b5cf6b;}.epoch.category20b .bar.category7{fill:#b5cf6b;}.epoch.category20b div.ref.category8{background-color:#cedb9c;}.epoch.category20b .category8 .line{stroke:#cedb9c;}.epoch.category20b .category8 .area,.epoch.category20b .category8 .dot{fill:#cedb9c;stroke:rgba(0, 0, 0, 0);}.epoch.category20b .arc.category8 path{fill:#cedb9c;}.epoch.category20b .bar.category8{fill:#cedb9c;}.epoch.category20b div.ref.category9{background-color:#8c6d31;}.epoch.category20b .category9 .line{stroke:#8c6d31;}.epoch.category20b .category9 .area,.epoch.category20b .category9 .dot{fill:#8c6d31;stroke:rgba(0, 0, 0, 0);}.epoch.category20b .arc.category9 path{fill:#8c6d31;}.epoch.category20b .bar.category9{fill:#8c6d31;}.epoch.category20b div.ref.category10{background-color:#bd9e39;}.epoch.category20b .category10 .line{stroke:#bd9e39;}.epoch.category20b .category10 .area,.epoch.category20b .category10 .dot{fill:#bd9e39;stroke:rgba(0, 0, 0, 0);}.epoch.category20b .arc.category10 path{fill:#bd9e39;}.epoch.category20b .bar.category10{fill:#bd9e39;}.epoch.category20b div.ref.category11{background-color:#e7ba52;}.epoch.category20b .category11 .line{stroke:#e7ba52;}.epoch.category20b .category11 .area,.epoch.category20b .category11 .dot{fill:#e7ba52;stroke:rgba(0, 0, 0, 0);}.epoch.category20b .arc.category11 path{fill:#e7ba52;}.epoch.category20b .bar.category11{fill:#e7ba52;}.epoch.category20b div.ref.category12{background-color:#e7cb94;}.epoch.category20b .category12 .line{stroke:#e7cb94;}.epoch.category20b .category12 .area,.epoch.category20b .category12 .dot{fill:#e7cb94;stroke:rgba(0, 0, 0, 0);}.epoch.category20b .arc.category12 path{fill:#e7cb94;}.epoch.category20b .bar.category12{fill:#e7cb94;}.epoch.category20b div.ref.category13{background-color:#843c39;}.epoch.category20b .category13 .line{stroke:#843c39;}.epoch.category20b .category13 .area,.epoch.category20b .category13 .dot{fill:#843c39;stroke:rgba(0, 0, 0, 0);}.epoch.category20b .arc.category13 path{fill:#843c39;}.epoch.category20b .bar.category13{fill:#843c39;}.epoch.category20b div.ref.category14{background-color:#ad494a;}.epoch.category20b .category14 .line{stroke:#ad494a;}.epoch.category20b .category14 .area,.epoch.category20b .category14 .dot{fill:#ad494a;stroke:rgba(0, 0, 0, 0);}.epoch.category20b .arc.category14 path{fill:#ad494a;}.epoch.category20b .bar.category14{fill:#ad494a;}.epoch.category20b div.ref.category15{background-color:#d6616b;}.epoch.category20b .category15 .line{stroke:#d6616b;}.epoch.category20b .category15 .area,.epoch.category20b .category15 .dot{fill:#d6616b;stroke:rgba(0, 0, 0, 0);}.epoch.category20b .arc.category15 path{fill:#d6616b;}.epoch.category20b .bar.category15{fill:#d6616b;}.epoch.category20b div.ref.category16{background-color:#e7969c;}.epoch.category20b .category16 .line{stroke:#e7969c;}.epoch.category20b .category16 .area,.epoch.category20b .category16 .dot{fill:#e7969c;stroke:rgba(0, 0, 0, 0);}.epoch.category20b .arc.category16 path{fill:#e7969c;}.epoch.category20b .bar.category16{fill:#e7969c;}.epoch.category20b div.ref.category17{background-color:#7b4173;}.epoch.category20b .category17 .line{stroke:#7b4173;}.epoch.category20b .category17 .area,.epoch.category20b .category17 .dot{fill:#7b4173;stroke:rgba(0, 0, 0, 0);}.epoch.category20b .arc.category17 path{fill:#7b4173;}.epoch.category20b .bar.category17{fill:#7b4173;}.epoch.category20b div.ref.category18{background-color:#a55194;}.epoch.category20b .category18 .line{stroke:#a55194;}.epoch.category20b .category18 .area,.epoch.category20b .category18 .dot{fill:#a55194;stroke:rgba(0, 0, 0, 0);}.epoch.category20b .arc.category18 path{fill:#a55194;}.epoch.category20b .bar.category18{fill:#a55194;}.epoch.category20b div.ref.category19{background-color:#ce6dbd;}.epoch.category20b .category19 .line{stroke:#ce6dbd;}.epoch.category20b .category19 .area,.epoch.category20b .category19 .dot{fill:#ce6dbd;stroke:rgba(0, 0, 0, 0);}.epoch.category20b .arc.category19 path{fill:#ce6dbd;}.epoch.category20b .bar.category19{fill:#ce6dbd;}.epoch.category20b div.ref.category20{background-color:#de9ed6;}.epoch.category20b .category20 .line{stroke:#de9ed6;}.epoch.category20b .category20 .area,.epoch.category20b .category20 .dot{fill:#de9ed6;stroke:rgba(0, 0, 0, 0);}.epoch.category20b .arc.category20 path{fill:#de9ed6;}.epoch.category20b .bar.category20{fill:#de9ed6;}.epoch.category20c div.ref.category1{background-color:#3182bd;}.epoch.category20c .category1 .line{stroke:#3182bd;}.epoch.category20c .category1 .area,.epoch.category20c .category1 .dot{fill:#3182bd;stroke:rgba(0, 0, 0, 0);}.epoch.category20c .arc.category1 path{fill:#3182bd;}.epoch.category20c .bar.category1{fill:#3182bd;}.epoch.category20c div.ref.category2{background-color:#6baed6;}.epoch.category20c .category2 .line{stroke:#6baed6;}.epoch.category20c .category2 .area,.epoch.category20c .category2 .dot{fill:#6baed6;stroke:rgba(0, 0, 0, 0);}.epoch.category20c .arc.category2 path{fill:#6baed6;}.epoch.category20c .bar.category2{fill:#6baed6;}.epoch.category20c div.ref.category3{background-color:#9ecae1;}.epoch.category20c .category3 .line{stroke:#9ecae1;}.epoch.category20c .category3 .area,.epoch.category20c .category3 .dot{fill:#9ecae1;stroke:rgba(0, 0, 0, 0);}.epoch.category20c .arc.category3 path{fill:#9ecae1;}.epoch.category20c .bar.category3{fill:#9ecae1;}.epoch.category20c div.ref.category4{background-color:#c6dbef;}.epoch.category20c .category4 .line{stroke:#c6dbef;}.epoch.category20c .category4 .area,.epoch.category20c .category4 .dot{fill:#c6dbef;stroke:rgba(0, 0, 0, 0);}.epoch.category20c .arc.category4 path{fill:#c6dbef;}.epoch.category20c .bar.category4{fill:#c6dbef;}.epoch.category20c div.ref.category5{background-color:#e6550d;}.epoch.category20c .category5 .line{stroke:#e6550d;}.epoch.category20c .category5 .area,.epoch.category20c .category5 .dot{fill:#e6550d;stroke:rgba(0, 0, 0, 0);}.epoch.category20c .arc.category5 path{fill:#e6550d;}.epoch.category20c .bar.category5{fill:#e6550d;}.epoch.category20c div.ref.category6{background-color:#fd8d3c;}.epoch.category20c .category6 .line{stroke:#fd8d3c;}.epoch.category20c .category6 .area,.epoch.category20c .category6 .dot{fill:#fd8d3c;stroke:rgba(0, 0, 0, 0);}.epoch.category20c .arc.category6 path{fill:#fd8d3c;}.epoch.category20c .bar.category6{fill:#fd8d3c;}.epoch.category20c div.ref.category7{background-color:#fdae6b;}.epoch.category20c .category7 .line{stroke:#fdae6b;}.epoch.category20c .category7 .area,.epoch.category20c .category7 .dot{fill:#fdae6b;stroke:rgba(0, 0, 0, 0);}.epoch.category20c .arc.category7 path{fill:#fdae6b;}.epoch.category20c .bar.category7{fill:#fdae6b;}.epoch.category20c div.ref.category8{background-color:#fdd0a2;}.epoch.category20c .category8 .line{stroke:#fdd0a2;}.epoch.category20c .category8 .area,.epoch.category20c .category8 .dot{fill:#fdd0a2;stroke:rgba(0, 0, 0, 0);}.epoch.category20c .arc.category8 path{fill:#fdd0a2;}.epoch.category20c .bar.category8{fill:#fdd0a2;}.epoch.category20c div.ref.category9{background-color:#31a354;}.epoch.category20c .category9 .line{stroke:#31a354;}.epoch.category20c .category9 .area,.epoch.category20c .category9 .dot{fill:#31a354;stroke:rgba(0, 0, 0, 0);}.epoch.category20c .arc.category9 path{fill:#31a354;}.epoch.category20c .bar.category9{fill:#31a354;}.epoch.category20c div.ref.category10{background-color:#74c476;}.epoch.category20c .category10 .line{stroke:#74c476;}.epoch.category20c .category10 .area,.epoch.category20c .category10 .dot{fill:#74c476;stroke:rgba(0, 0, 0, 0);}.epoch.category20c .arc.category10 path{fill:#74c476;}.epoch.category20c .bar.category10{fill:#74c476;}.epoch.category20c div.ref.category11{background-color:#a1d99b;}.epoch.category20c .category11 .line{stroke:#a1d99b;}.epoch.category20c .category11 .area,.epoch.category20c .category11 .dot{fill:#a1d99b;stroke:rgba(0, 0, 0, 0);}.epoch.category20c .arc.category11 path{fill:#a1d99b;}.epoch.category20c .bar.category11{fill:#a1d99b;}.epoch.category20c div.ref.category12{background-color:#c7e9c0;}.epoch.category20c .category12 .line{stroke:#c7e9c0;}.epoch.category20c .category12 .area,.epoch.category20c .category12 .dot{fill:#c7e9c0;stroke:rgba(0, 0, 0, 0);}.epoch.category20c .arc.category12 path{fill:#c7e9c0;}.epoch.category20c .bar.category12{fill:#c7e9c0;}.epoch.category20c div.ref.category13{background-color:#756bb1;}.epoch.category20c .category13 .line{stroke:#756bb1;}.epoch.category20c .category13 .area,.epoch.category20c .category13 .dot{fill:#756bb1;stroke:rgba(0, 0, 0, 0);}.epoch.category20c .arc.category13 path{fill:#756bb1;}.epoch.category20c .bar.category13{fill:#756bb1;}.epoch.category20c div.ref.category14{background-color:#9e9ac8;}.epoch.category20c .category14 .line{stroke:#9e9ac8;}.epoch.category20c .category14 .area,.epoch.category20c .category14 .dot{fill:#9e9ac8;stroke:rgba(0, 0, 0, 0);}.epoch.category20c .arc.category14 path{fill:#9e9ac8;}.epoch.category20c .bar.category14{fill:#9e9ac8;}.epoch.category20c div.ref.category15{background-color:#bcbddc;}.epoch.category20c .category15 .line{stroke:#bcbddc;}.epoch.category20c .category15 .area,.epoch.category20c .category15 .dot{fill:#bcbddc;stroke:rgba(0, 0, 0, 0);}.epoch.category20c .arc.category15 path{fill:#bcbddc;}.epoch.category20c .bar.category15{fill:#bcbddc;}.epoch.category20c div.ref.category16{background-color:#dadaeb;}.epoch.category20c .category16 .line{stroke:#dadaeb;}.epoch.category20c .category16 .area,.epoch.category20c .category16 .dot{fill:#dadaeb;stroke:rgba(0, 0, 0, 0);}.epoch.category20c .arc.category16 path{fill:#dadaeb;}.epoch.category20c .bar.category16{fill:#dadaeb;}.epoch.category20c div.ref.category17{background-color:#636363;}.epoch.category20c .category17 .line{stroke:#636363;}.epoch.category20c .category17 .area,.epoch.category20c .category17 .dot{fill:#636363;stroke:rgba(0, 0, 0, 0);}.epoch.category20c .arc.category17 path{fill:#636363;}.epoch.category20c .bar.category17{fill:#636363;}.epoch.category20c div.ref.category18{background-color:#969696;}.epoch.category20c .category18 .line{stroke:#969696;}.epoch.category20c .category18 .area,.epoch.category20c .category18 .dot{fill:#969696;stroke:rgba(0, 0, 0, 0);}.epoch.category20c .arc.category18 path{fill:#969696;}.epoch.category20c .bar.category18{fill:#969696;}.epoch.category20c div.ref.category19{background-color:#bdbdbd;}.epoch.category20c .category19 .line{stroke:#bdbdbd;}.epoch.category20c .category19 .area,.epoch.category20c .category19 .dot{fill:#bdbdbd;stroke:rgba(0, 0, 0, 0);}.epoch.category20c .arc.category19 path{fill:#bdbdbd;}.epoch.category20c .bar.category19{fill:#bdbdbd;}.epoch.category20c div.ref.category20{background-color:#d9d9d9;}.epoch.category20c .category20 .line{stroke:#d9d9d9;}.epoch.category20c .category20 .area,.epoch.category20c .category20 .dot{fill:#d9d9d9;stroke:rgba(0, 0, 0, 0);}.epoch.category20c .arc.category20 path{fill:#d9d9d9;}.epoch.category20c .bar.category20{fill:#d9d9d9;}.epoch .category1 .bucket,.epoch.heatmap5 .category1 .bucket{fill:#1f77b4;}.epoch .category2 .bucket,.epoch.heatmap5 .category2 .bucket{fill:#2ca02c;}.epoch .category3 .bucket,.epoch.heatmap5 .category3 .bucket{fill:#d62728;}.epoch .category4 .bucket,.epoch.heatmap5 .category4 .bucket{fill:#8c564b;}.epoch .category5 .bucket,.epoch.heatmap5 .category5 .bucket{fill:#7f7f7f;}.epoch-theme-dark .epoch .axis path,.epoch-theme-dark .epoch .axis line{stroke:#d0d0d0;}.epoch-theme-dark .epoch .axis .tick text{fill:#d0d0d0;}.epoch-theme-dark .arc.pie{stroke:#333;}.epoch-theme-dark .arc.pie text{fill:#333;}.epoch-theme-dark .epoch .gauge-labels .value{fill:#BBB;}.epoch-theme-dark .epoch .gauge .arc.outer{stroke:#999;}.epoch-theme-dark .epoch .gauge .arc.inner{stroke:#AAA;}.epoch-theme-dark .epoch .gauge .tick{stroke:#AAA;}.epoch-theme-dark .epoch .gauge .needle{fill:#F3DE88;}.epoch-theme-dark .epoch .gauge .needle-base{fill:#999;}.epoch-theme-dark .epoch div.ref.category1,.epoch-theme-dark .epoch.category10 div.ref.category1{background-color:#909CFF;}.epoch-theme-dark .epoch .category1 .line,.epoch-theme-dark .epoch.category10 .category1 .line{stroke:#909CFF;}.epoch-theme-dark .epoch .category1 .area,.epoch-theme-dark .epoch .category1 .dot,.epoch-theme-dark .epoch.category10 .category1 .area,.epoch-theme-dark .epoch.category10 .category1 .dot{fill:#909CFF;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch .arc.category1 path,.epoch-theme-dark .epoch.category10 .arc.category1 path{fill:#909CFF;}.epoch-theme-dark .epoch .bar.category1,.epoch-theme-dark .epoch.category10 .bar.category1{fill:#909CFF;}.epoch-theme-dark .epoch div.ref.category2,.epoch-theme-dark .epoch.category10 div.ref.category2{background-color:#FFAC89;}.epoch-theme-dark .epoch .category2 .line,.epoch-theme-dark .epoch.category10 .category2 .line{stroke:#FFAC89;}.epoch-theme-dark .epoch .category2 .area,.epoch-theme-dark .epoch .category2 .dot,.epoch-theme-dark .epoch.category10 .category2 .area,.epoch-theme-dark .epoch.category10 .category2 .dot{fill:#FFAC89;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch .arc.category2 path,.epoch-theme-dark .epoch.category10 .arc.category2 path{fill:#FFAC89;}.epoch-theme-dark .epoch .bar.category2,.epoch-theme-dark .epoch.category10 .bar.category2{fill:#FFAC89;}.epoch-theme-dark .epoch div.ref.category3,.epoch-theme-dark .epoch.category10 div.ref.category3{background-color:#E889E8;}.epoch-theme-dark .epoch .category3 .line,.epoch-theme-dark .epoch.category10 .category3 .line{stroke:#E889E8;}.epoch-theme-dark .epoch .category3 .area,.epoch-theme-dark .epoch .category3 .dot,.epoch-theme-dark .epoch.category10 .category3 .area,.epoch-theme-dark .epoch.category10 .category3 .dot{fill:#E889E8;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch .arc.category3 path,.epoch-theme-dark .epoch.category10 .arc.category3 path{fill:#E889E8;}.epoch-theme-dark .epoch .bar.category3,.epoch-theme-dark .epoch.category10 .bar.category3{fill:#E889E8;}.epoch-theme-dark .epoch div.ref.category4,.epoch-theme-dark .epoch.category10 div.ref.category4{background-color:#78E8D3;}.epoch-theme-dark .epoch .category4 .line,.epoch-theme-dark .epoch.category10 .category4 .line{stroke:#78E8D3;}.epoch-theme-dark .epoch .category4 .area,.epoch-theme-dark .epoch .category4 .dot,.epoch-theme-dark .epoch.category10 .category4 .area,.epoch-theme-dark .epoch.category10 .category4 .dot{fill:#78E8D3;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch .arc.category4 path,.epoch-theme-dark .epoch.category10 .arc.category4 path{fill:#78E8D3;}.epoch-theme-dark .epoch .bar.category4,.epoch-theme-dark .epoch.category10 .bar.category4{fill:#78E8D3;}.epoch-theme-dark .epoch div.ref.category5,.epoch-theme-dark .epoch.category10 div.ref.category5{background-color:#C2FF97;}.epoch-theme-dark .epoch .category5 .line,.epoch-theme-dark .epoch.category10 .category5 .line{stroke:#C2FF97;}.epoch-theme-dark .epoch .category5 .area,.epoch-theme-dark .epoch .category5 .dot,.epoch-theme-dark .epoch.category10 .category5 .area,.epoch-theme-dark .epoch.category10 .category5 .dot{fill:#C2FF97;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch .arc.category5 path,.epoch-theme-dark .epoch.category10 .arc.category5 path{fill:#C2FF97;}.epoch-theme-dark .epoch .bar.category5,.epoch-theme-dark .epoch.category10 .bar.category5{fill:#C2FF97;}.epoch-theme-dark .epoch div.ref.category6,.epoch-theme-dark .epoch.category10 div.ref.category6{background-color:#B7BCD1;}.epoch-theme-dark .epoch .category6 .line,.epoch-theme-dark .epoch.category10 .category6 .line{stroke:#B7BCD1;}.epoch-theme-dark .epoch .category6 .area,.epoch-theme-dark .epoch .category6 .dot,.epoch-theme-dark .epoch.category10 .category6 .area,.epoch-theme-dark .epoch.category10 .category6 .dot{fill:#B7BCD1;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch .arc.category6 path,.epoch-theme-dark .epoch.category10 .arc.category6 path{fill:#B7BCD1;}.epoch-theme-dark .epoch .bar.category6,.epoch-theme-dark .epoch.category10 .bar.category6{fill:#B7BCD1;}.epoch-theme-dark .epoch div.ref.category7,.epoch-theme-dark .epoch.category10 div.ref.category7{background-color:#FF857F;}.epoch-theme-dark .epoch .category7 .line,.epoch-theme-dark .epoch.category10 .category7 .line{stroke:#FF857F;}.epoch-theme-dark .epoch .category7 .area,.epoch-theme-dark .epoch .category7 .dot,.epoch-theme-dark .epoch.category10 .category7 .area,.epoch-theme-dark .epoch.category10 .category7 .dot{fill:#FF857F;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch .arc.category7 path,.epoch-theme-dark .epoch.category10 .arc.category7 path{fill:#FF857F;}.epoch-theme-dark .epoch .bar.category7,.epoch-theme-dark .epoch.category10 .bar.category7{fill:#FF857F;}.epoch-theme-dark .epoch div.ref.category8,.epoch-theme-dark .epoch.category10 div.ref.category8{background-color:#F3DE88;}.epoch-theme-dark .epoch .category8 .line,.epoch-theme-dark .epoch.category10 .category8 .line{stroke:#F3DE88;}.epoch-theme-dark .epoch .category8 .area,.epoch-theme-dark .epoch .category8 .dot,.epoch-theme-dark .epoch.category10 .category8 .area,.epoch-theme-dark .epoch.category10 .category8 .dot{fill:#F3DE88;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch .arc.category8 path,.epoch-theme-dark .epoch.category10 .arc.category8 path{fill:#F3DE88;}.epoch-theme-dark .epoch .bar.category8,.epoch-theme-dark .epoch.category10 .bar.category8{fill:#F3DE88;}.epoch-theme-dark .epoch div.ref.category9,.epoch-theme-dark .epoch.category10 div.ref.category9{background-color:#C9935E;}.epoch-theme-dark .epoch .category9 .line,.epoch-theme-dark .epoch.category10 .category9 .line{stroke:#C9935E;}.epoch-theme-dark .epoch .category9 .area,.epoch-theme-dark .epoch .category9 .dot,.epoch-theme-dark .epoch.category10 .category9 .area,.epoch-theme-dark .epoch.category10 .category9 .dot{fill:#C9935E;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch .arc.category9 path,.epoch-theme-dark .epoch.category10 .arc.category9 path{fill:#C9935E;}.epoch-theme-dark .epoch .bar.category9,.epoch-theme-dark .epoch.category10 .bar.category9{fill:#C9935E;}.epoch-theme-dark .epoch div.ref.category10,.epoch-theme-dark .epoch.category10 div.ref.category10{background-color:#A488FF;}.epoch-theme-dark .epoch .category10 .line,.epoch-theme-dark .epoch.category10 .category10 .line{stroke:#A488FF;}.epoch-theme-dark .epoch .category10 .area,.epoch-theme-dark .epoch .category10 .dot,.epoch-theme-dark .epoch.category10 .category10 .area,.epoch-theme-dark .epoch.category10 .category10 .dot{fill:#A488FF;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch .arc.category10 path,.epoch-theme-dark .epoch.category10 .arc.category10 path{fill:#A488FF;}.epoch-theme-dark .epoch .bar.category10,.epoch-theme-dark .epoch.category10 .bar.category10{fill:#A488FF;}.epoch-theme-dark .epoch.category20 div.ref.category1{background-color:#909CFF;}.epoch-theme-dark .epoch.category20 .category1 .line{stroke:#909CFF;}.epoch-theme-dark .epoch.category20 .category1 .area,.epoch-theme-dark .epoch.category20 .category1 .dot{fill:#909CFF;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20 .arc.category1 path{fill:#909CFF;}.epoch-theme-dark .epoch.category20 .bar.category1{fill:#909CFF;}.epoch-theme-dark .epoch.category20 div.ref.category2{background-color:#626AAD;}.epoch-theme-dark .epoch.category20 .category2 .line{stroke:#626AAD;}.epoch-theme-dark .epoch.category20 .category2 .area,.epoch-theme-dark .epoch.category20 .category2 .dot{fill:#626AAD;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20 .arc.category2 path{fill:#626AAD;}.epoch-theme-dark .epoch.category20 .bar.category2{fill:#626AAD;}.epoch-theme-dark .epoch.category20 div.ref.category3{background-color:#FFAC89;}.epoch-theme-dark .epoch.category20 .category3 .line{stroke:#FFAC89;}.epoch-theme-dark .epoch.category20 .category3 .area,.epoch-theme-dark .epoch.category20 .category3 .dot{fill:#FFAC89;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20 .arc.category3 path{fill:#FFAC89;}.epoch-theme-dark .epoch.category20 .bar.category3{fill:#FFAC89;}.epoch-theme-dark .epoch.category20 div.ref.category4{background-color:#BD7F66;}.epoch-theme-dark .epoch.category20 .category4 .line{stroke:#BD7F66;}.epoch-theme-dark .epoch.category20 .category4 .area,.epoch-theme-dark .epoch.category20 .category4 .dot{fill:#BD7F66;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20 .arc.category4 path{fill:#BD7F66;}.epoch-theme-dark .epoch.category20 .bar.category4{fill:#BD7F66;}.epoch-theme-dark .epoch.category20 div.ref.category5{background-color:#E889E8;}.epoch-theme-dark .epoch.category20 .category5 .line{stroke:#E889E8;}.epoch-theme-dark .epoch.category20 .category5 .area,.epoch-theme-dark .epoch.category20 .category5 .dot{fill:#E889E8;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20 .arc.category5 path{fill:#E889E8;}.epoch-theme-dark .epoch.category20 .bar.category5{fill:#E889E8;}.epoch-theme-dark .epoch.category20 div.ref.category6{background-color:#995A99;}.epoch-theme-dark .epoch.category20 .category6 .line{stroke:#995A99;}.epoch-theme-dark .epoch.category20 .category6 .area,.epoch-theme-dark .epoch.category20 .category6 .dot{fill:#995A99;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20 .arc.category6 path{fill:#995A99;}.epoch-theme-dark .epoch.category20 .bar.category6{fill:#995A99;}.epoch-theme-dark .epoch.category20 div.ref.category7{background-color:#78E8D3;}.epoch-theme-dark .epoch.category20 .category7 .line{stroke:#78E8D3;}.epoch-theme-dark .epoch.category20 .category7 .area,.epoch-theme-dark .epoch.category20 .category7 .dot{fill:#78E8D3;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20 .arc.category7 path{fill:#78E8D3;}.epoch-theme-dark .epoch.category20 .bar.category7{fill:#78E8D3;}.epoch-theme-dark .epoch.category20 div.ref.category8{background-color:#4F998C;}.epoch-theme-dark .epoch.category20 .category8 .line{stroke:#4F998C;}.epoch-theme-dark .epoch.category20 .category8 .area,.epoch-theme-dark .epoch.category20 .category8 .dot{fill:#4F998C;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20 .arc.category8 path{fill:#4F998C;}.epoch-theme-dark .epoch.category20 .bar.category8{fill:#4F998C;}.epoch-theme-dark .epoch.category20 div.ref.category9{background-color:#C2FF97;}.epoch-theme-dark .epoch.category20 .category9 .line{stroke:#C2FF97;}.epoch-theme-dark .epoch.category20 .category9 .area,.epoch-theme-dark .epoch.category20 .category9 .dot{fill:#C2FF97;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20 .arc.category9 path{fill:#C2FF97;}.epoch-theme-dark .epoch.category20 .bar.category9{fill:#C2FF97;}.epoch-theme-dark .epoch.category20 div.ref.category10{background-color:#789E5E;}.epoch-theme-dark .epoch.category20 .category10 .line{stroke:#789E5E;}.epoch-theme-dark .epoch.category20 .category10 .area,.epoch-theme-dark .epoch.category20 .category10 .dot{fill:#789E5E;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20 .arc.category10 path{fill:#789E5E;}.epoch-theme-dark .epoch.category20 .bar.category10{fill:#789E5E;}.epoch-theme-dark .epoch.category20 div.ref.category11{background-color:#B7BCD1;}.epoch-theme-dark .epoch.category20 .category11 .line{stroke:#B7BCD1;}.epoch-theme-dark .epoch.category20 .category11 .area,.epoch-theme-dark .epoch.category20 .category11 .dot{fill:#B7BCD1;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20 .arc.category11 path{fill:#B7BCD1;}.epoch-theme-dark .epoch.category20 .bar.category11{fill:#B7BCD1;}.epoch-theme-dark .epoch.category20 div.ref.category12{background-color:#7F8391;}.epoch-theme-dark .epoch.category20 .category12 .line{stroke:#7F8391;}.epoch-theme-dark .epoch.category20 .category12 .area,.epoch-theme-dark .epoch.category20 .category12 .dot{fill:#7F8391;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20 .arc.category12 path{fill:#7F8391;}.epoch-theme-dark .epoch.category20 .bar.category12{fill:#7F8391;}.epoch-theme-dark .epoch.category20 div.ref.category13{background-color:#CCB889;}.epoch-theme-dark .epoch.category20 .category13 .line{stroke:#CCB889;}.epoch-theme-dark .epoch.category20 .category13 .area,.epoch-theme-dark .epoch.category20 .category13 .dot{fill:#CCB889;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20 .arc.category13 path{fill:#CCB889;}.epoch-theme-dark .epoch.category20 .bar.category13{fill:#CCB889;}.epoch-theme-dark .epoch.category20 div.ref.category14{background-color:#A1906B;}.epoch-theme-dark .epoch.category20 .category14 .line{stroke:#A1906B;}.epoch-theme-dark .epoch.category20 .category14 .area,.epoch-theme-dark .epoch.category20 .category14 .dot{fill:#A1906B;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20 .arc.category14 path{fill:#A1906B;}.epoch-theme-dark .epoch.category20 .bar.category14{fill:#A1906B;}.epoch-theme-dark .epoch.category20 div.ref.category15{background-color:#F3DE88;}.epoch-theme-dark .epoch.category20 .category15 .line{stroke:#F3DE88;}.epoch-theme-dark .epoch.category20 .category15 .area,.epoch-theme-dark .epoch.category20 .category15 .dot{fill:#F3DE88;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20 .arc.category15 path{fill:#F3DE88;}.epoch-theme-dark .epoch.category20 .bar.category15{fill:#F3DE88;}.epoch-theme-dark .epoch.category20 div.ref.category16{background-color:#A89A5E;}.epoch-theme-dark .epoch.category20 .category16 .line{stroke:#A89A5E;}.epoch-theme-dark .epoch.category20 .category16 .area,.epoch-theme-dark .epoch.category20 .category16 .dot{fill:#A89A5E;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20 .arc.category16 path{fill:#A89A5E;}.epoch-theme-dark .epoch.category20 .bar.category16{fill:#A89A5E;}.epoch-theme-dark .epoch.category20 div.ref.category17{background-color:#FF857F;}.epoch-theme-dark .epoch.category20 .category17 .line{stroke:#FF857F;}.epoch-theme-dark .epoch.category20 .category17 .area,.epoch-theme-dark .epoch.category20 .category17 .dot{fill:#FF857F;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20 .arc.category17 path{fill:#FF857F;}.epoch-theme-dark .epoch.category20 .bar.category17{fill:#FF857F;}.epoch-theme-dark .epoch.category20 div.ref.category18{background-color:#BA615D;}.epoch-theme-dark .epoch.category20 .category18 .line{stroke:#BA615D;}.epoch-theme-dark .epoch.category20 .category18 .area,.epoch-theme-dark .epoch.category20 .category18 .dot{fill:#BA615D;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20 .arc.category18 path{fill:#BA615D;}.epoch-theme-dark .epoch.category20 .bar.category18{fill:#BA615D;}.epoch-theme-dark .epoch.category20 div.ref.category19{background-color:#A488FF;}.epoch-theme-dark .epoch.category20 .category19 .line{stroke:#A488FF;}.epoch-theme-dark .epoch.category20 .category19 .area,.epoch-theme-dark .epoch.category20 .category19 .dot{fill:#A488FF;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20 .arc.category19 path{fill:#A488FF;}.epoch-theme-dark .epoch.category20 .bar.category19{fill:#A488FF;}.epoch-theme-dark .epoch.category20 div.ref.category20{background-color:#7662B8;}.epoch-theme-dark .epoch.category20 .category20 .line{stroke:#7662B8;}.epoch-theme-dark .epoch.category20 .category20 .area,.epoch-theme-dark .epoch.category20 .category20 .dot{fill:#7662B8;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20 .arc.category20 path{fill:#7662B8;}.epoch-theme-dark .epoch.category20 .bar.category20{fill:#7662B8;}.epoch-theme-dark .epoch.category20b div.ref.category1{background-color:#909CFF;}.epoch-theme-dark .epoch.category20b .category1 .line{stroke:#909CFF;}.epoch-theme-dark .epoch.category20b .category1 .area,.epoch-theme-dark .epoch.category20b .category1 .dot{fill:#909CFF;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20b .arc.category1 path{fill:#909CFF;}.epoch-theme-dark .epoch.category20b .bar.category1{fill:#909CFF;}.epoch-theme-dark .epoch.category20b div.ref.category2{background-color:#7680D1;}.epoch-theme-dark .epoch.category20b .category2 .line{stroke:#7680D1;}.epoch-theme-dark .epoch.category20b .category2 .area,.epoch-theme-dark .epoch.category20b .category2 .dot{fill:#7680D1;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20b .arc.category2 path{fill:#7680D1;}.epoch-theme-dark .epoch.category20b .bar.category2{fill:#7680D1;}.epoch-theme-dark .epoch.category20b div.ref.category3{background-color:#656DB2;}.epoch-theme-dark .epoch.category20b .category3 .line{stroke:#656DB2;}.epoch-theme-dark .epoch.category20b .category3 .area,.epoch-theme-dark .epoch.category20b .category3 .dot{fill:#656DB2;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20b .arc.category3 path{fill:#656DB2;}.epoch-theme-dark .epoch.category20b .bar.category3{fill:#656DB2;}.epoch-theme-dark .epoch.category20b div.ref.category4{background-color:#525992;}.epoch-theme-dark .epoch.category20b .category4 .line{stroke:#525992;}.epoch-theme-dark .epoch.category20b .category4 .area,.epoch-theme-dark .epoch.category20b .category4 .dot{fill:#525992;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20b .arc.category4 path{fill:#525992;}.epoch-theme-dark .epoch.category20b .bar.category4{fill:#525992;}.epoch-theme-dark .epoch.category20b div.ref.category5{background-color:#FFAC89;}.epoch-theme-dark .epoch.category20b .category5 .line{stroke:#FFAC89;}.epoch-theme-dark .epoch.category20b .category5 .area,.epoch-theme-dark .epoch.category20b .category5 .dot{fill:#FFAC89;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20b .arc.category5 path{fill:#FFAC89;}.epoch-theme-dark .epoch.category20b .bar.category5{fill:#FFAC89;}.epoch-theme-dark .epoch.category20b div.ref.category6{background-color:#D18D71;}.epoch-theme-dark .epoch.category20b .category6 .line{stroke:#D18D71;}.epoch-theme-dark .epoch.category20b .category6 .area,.epoch-theme-dark .epoch.category20b .category6 .dot{fill:#D18D71;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20b .arc.category6 path{fill:#D18D71;}.epoch-theme-dark .epoch.category20b .bar.category6{fill:#D18D71;}.epoch-theme-dark .epoch.category20b div.ref.category7{background-color:#AB735C;}.epoch-theme-dark .epoch.category20b .category7 .line{stroke:#AB735C;}.epoch-theme-dark .epoch.category20b .category7 .area,.epoch-theme-dark .epoch.category20b .category7 .dot{fill:#AB735C;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20b .arc.category7 path{fill:#AB735C;}.epoch-theme-dark .epoch.category20b .bar.category7{fill:#AB735C;}.epoch-theme-dark .epoch.category20b div.ref.category8{background-color:#92624E;}.epoch-theme-dark .epoch.category20b .category8 .line{stroke:#92624E;}.epoch-theme-dark .epoch.category20b .category8 .area,.epoch-theme-dark .epoch.category20b .category8 .dot{fill:#92624E;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20b .arc.category8 path{fill:#92624E;}.epoch-theme-dark .epoch.category20b .bar.category8{fill:#92624E;}.epoch-theme-dark .epoch.category20b div.ref.category9{background-color:#E889E8;}.epoch-theme-dark .epoch.category20b .category9 .line{stroke:#E889E8;}.epoch-theme-dark .epoch.category20b .category9 .area,.epoch-theme-dark .epoch.category20b .category9 .dot{fill:#E889E8;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20b .arc.category9 path{fill:#E889E8;}.epoch-theme-dark .epoch.category20b .bar.category9{fill:#E889E8;}.epoch-theme-dark .epoch.category20b div.ref.category10{background-color:#BA6EBA;}.epoch-theme-dark .epoch.category20b .category10 .line{stroke:#BA6EBA;}.epoch-theme-dark .epoch.category20b .category10 .area,.epoch-theme-dark .epoch.category20b .category10 .dot{fill:#BA6EBA;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20b .arc.category10 path{fill:#BA6EBA;}.epoch-theme-dark .epoch.category20b .bar.category10{fill:#BA6EBA;}.epoch-theme-dark .epoch.category20b div.ref.category11{background-color:#9B5C9B;}.epoch-theme-dark .epoch.category20b .category11 .line{stroke:#9B5C9B;}.epoch-theme-dark .epoch.category20b .category11 .area,.epoch-theme-dark .epoch.category20b .category11 .dot{fill:#9B5C9B;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20b .arc.category11 path{fill:#9B5C9B;}.epoch-theme-dark .epoch.category20b .bar.category11{fill:#9B5C9B;}.epoch-theme-dark .epoch.category20b div.ref.category12{background-color:#7B487B;}.epoch-theme-dark .epoch.category20b .category12 .line{stroke:#7B487B;}.epoch-theme-dark .epoch.category20b .category12 .area,.epoch-theme-dark .epoch.category20b .category12 .dot{fill:#7B487B;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20b .arc.category12 path{fill:#7B487B;}.epoch-theme-dark .epoch.category20b .bar.category12{fill:#7B487B;}.epoch-theme-dark .epoch.category20b div.ref.category13{background-color:#78E8D3;}.epoch-theme-dark .epoch.category20b .category13 .line{stroke:#78E8D3;}.epoch-theme-dark .epoch.category20b .category13 .area,.epoch-theme-dark .epoch.category20b .category13 .dot{fill:#78E8D3;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20b .arc.category13 path{fill:#78E8D3;}.epoch-theme-dark .epoch.category20b .bar.category13{fill:#78E8D3;}.epoch-theme-dark .epoch.category20b div.ref.category14{background-color:#60BAAA;}.epoch-theme-dark .epoch.category20b .category14 .line{stroke:#60BAAA;}.epoch-theme-dark .epoch.category20b .category14 .area,.epoch-theme-dark .epoch.category20b .category14 .dot{fill:#60BAAA;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20b .arc.category14 path{fill:#60BAAA;}.epoch-theme-dark .epoch.category20b .bar.category14{fill:#60BAAA;}.epoch-theme-dark .epoch.category20b div.ref.category15{background-color:#509B8D;}.epoch-theme-dark .epoch.category20b .category15 .line{stroke:#509B8D;}.epoch-theme-dark .epoch.category20b .category15 .area,.epoch-theme-dark .epoch.category20b .category15 .dot{fill:#509B8D;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20b .arc.category15 path{fill:#509B8D;}.epoch-theme-dark .epoch.category20b .bar.category15{fill:#509B8D;}.epoch-theme-dark .epoch.category20b div.ref.category16{background-color:#3F7B70;}.epoch-theme-dark .epoch.category20b .category16 .line{stroke:#3F7B70;}.epoch-theme-dark .epoch.category20b .category16 .area,.epoch-theme-dark .epoch.category20b .category16 .dot{fill:#3F7B70;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20b .arc.category16 path{fill:#3F7B70;}.epoch-theme-dark .epoch.category20b .bar.category16{fill:#3F7B70;}.epoch-theme-dark .epoch.category20b div.ref.category17{background-color:#C2FF97;}.epoch-theme-dark .epoch.category20b .category17 .line{stroke:#C2FF97;}.epoch-theme-dark .epoch.category20b .category17 .area,.epoch-theme-dark .epoch.category20b .category17 .dot{fill:#C2FF97;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20b .arc.category17 path{fill:#C2FF97;}.epoch-theme-dark .epoch.category20b .bar.category17{fill:#C2FF97;}.epoch-theme-dark .epoch.category20b div.ref.category18{background-color:#9FD17C;}.epoch-theme-dark .epoch.category20b .category18 .line{stroke:#9FD17C;}.epoch-theme-dark .epoch.category20b .category18 .area,.epoch-theme-dark .epoch.category20b .category18 .dot{fill:#9FD17C;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20b .arc.category18 path{fill:#9FD17C;}.epoch-theme-dark .epoch.category20b .bar.category18{fill:#9FD17C;}.epoch-theme-dark .epoch.category20b div.ref.category19{background-color:#7DA361;}.epoch-theme-dark .epoch.category20b .category19 .line{stroke:#7DA361;}.epoch-theme-dark .epoch.category20b .category19 .area,.epoch-theme-dark .epoch.category20b .category19 .dot{fill:#7DA361;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20b .arc.category19 path{fill:#7DA361;}.epoch-theme-dark .epoch.category20b .bar.category19{fill:#7DA361;}.epoch-theme-dark .epoch.category20b div.ref.category20{background-color:#65854E;}.epoch-theme-dark .epoch.category20b .category20 .line{stroke:#65854E;}.epoch-theme-dark .epoch.category20b .category20 .area,.epoch-theme-dark .epoch.category20b .category20 .dot{fill:#65854E;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20b .arc.category20 path{fill:#65854E;}.epoch-theme-dark .epoch.category20b .bar.category20{fill:#65854E;}.epoch-theme-dark .epoch.category20c div.ref.category1{background-color:#B7BCD1;}.epoch-theme-dark .epoch.category20c .category1 .line{stroke:#B7BCD1;}.epoch-theme-dark .epoch.category20c .category1 .area,.epoch-theme-dark .epoch.category20c .category1 .dot{fill:#B7BCD1;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20c .arc.category1 path{fill:#B7BCD1;}.epoch-theme-dark .epoch.category20c .bar.category1{fill:#B7BCD1;}.epoch-theme-dark .epoch.category20c div.ref.category2{background-color:#979DAD;}.epoch-theme-dark .epoch.category20c .category2 .line{stroke:#979DAD;}.epoch-theme-dark .epoch.category20c .category2 .area,.epoch-theme-dark .epoch.category20c .category2 .dot{fill:#979DAD;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20c .arc.category2 path{fill:#979DAD;}.epoch-theme-dark .epoch.category20c .bar.category2{fill:#979DAD;}.epoch-theme-dark .epoch.category20c div.ref.category3{background-color:#6E717D;}.epoch-theme-dark .epoch.category20c .category3 .line{stroke:#6E717D;}.epoch-theme-dark .epoch.category20c .category3 .area,.epoch-theme-dark .epoch.category20c .category3 .dot{fill:#6E717D;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20c .arc.category3 path{fill:#6E717D;}.epoch-theme-dark .epoch.category20c .bar.category3{fill:#6E717D;}.epoch-theme-dark .epoch.category20c div.ref.category4{background-color:#595C66;}.epoch-theme-dark .epoch.category20c .category4 .line{stroke:#595C66;}.epoch-theme-dark .epoch.category20c .category4 .area,.epoch-theme-dark .epoch.category20c .category4 .dot{fill:#595C66;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20c .arc.category4 path{fill:#595C66;}.epoch-theme-dark .epoch.category20c .bar.category4{fill:#595C66;}.epoch-theme-dark .epoch.category20c div.ref.category5{background-color:#FF857F;}.epoch-theme-dark .epoch.category20c .category5 .line{stroke:#FF857F;}.epoch-theme-dark .epoch.category20c .category5 .area,.epoch-theme-dark .epoch.category20c .category5 .dot{fill:#FF857F;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20c .arc.category5 path{fill:#FF857F;}.epoch-theme-dark .epoch.category20c .bar.category5{fill:#FF857F;}.epoch-theme-dark .epoch.category20c div.ref.category6{background-color:#DE746E;}.epoch-theme-dark .epoch.category20c .category6 .line{stroke:#DE746E;}.epoch-theme-dark .epoch.category20c .category6 .area,.epoch-theme-dark .epoch.category20c .category6 .dot{fill:#DE746E;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20c .arc.category6 path{fill:#DE746E;}.epoch-theme-dark .epoch.category20c .bar.category6{fill:#DE746E;}.epoch-theme-dark .epoch.category20c div.ref.category7{background-color:#B55F5A;}.epoch-theme-dark .epoch.category20c .category7 .line{stroke:#B55F5A;}.epoch-theme-dark .epoch.category20c .category7 .area,.epoch-theme-dark .epoch.category20c .category7 .dot{fill:#B55F5A;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20c .arc.category7 path{fill:#B55F5A;}.epoch-theme-dark .epoch.category20c .bar.category7{fill:#B55F5A;}.epoch-theme-dark .epoch.category20c div.ref.category8{background-color:#964E4B;}.epoch-theme-dark .epoch.category20c .category8 .line{stroke:#964E4B;}.epoch-theme-dark .epoch.category20c .category8 .area,.epoch-theme-dark .epoch.category20c .category8 .dot{fill:#964E4B;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20c .arc.category8 path{fill:#964E4B;}.epoch-theme-dark .epoch.category20c .bar.category8{fill:#964E4B;}.epoch-theme-dark .epoch.category20c div.ref.category9{background-color:#F3DE88;}.epoch-theme-dark .epoch.category20c .category9 .line{stroke:#F3DE88;}.epoch-theme-dark .epoch.category20c .category9 .area,.epoch-theme-dark .epoch.category20c .category9 .dot{fill:#F3DE88;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20c .arc.category9 path{fill:#F3DE88;}.epoch-theme-dark .epoch.category20c .bar.category9{fill:#F3DE88;}.epoch-theme-dark .epoch.category20c div.ref.category10{background-color:#DBC87B;}.epoch-theme-dark .epoch.category20c .category10 .line{stroke:#DBC87B;}.epoch-theme-dark .epoch.category20c .category10 .area,.epoch-theme-dark .epoch.category20c .category10 .dot{fill:#DBC87B;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20c .arc.category10 path{fill:#DBC87B;}.epoch-theme-dark .epoch.category20c .bar.category10{fill:#DBC87B;}.epoch-theme-dark .epoch.category20c div.ref.category11{background-color:#BAAA68;}.epoch-theme-dark .epoch.category20c .category11 .line{stroke:#BAAA68;}.epoch-theme-dark .epoch.category20c .category11 .area,.epoch-theme-dark .epoch.category20c .category11 .dot{fill:#BAAA68;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20c .arc.category11 path{fill:#BAAA68;}.epoch-theme-dark .epoch.category20c .bar.category11{fill:#BAAA68;}.epoch-theme-dark .epoch.category20c div.ref.category12{background-color:#918551;}.epoch-theme-dark .epoch.category20c .category12 .line{stroke:#918551;}.epoch-theme-dark .epoch.category20c .category12 .area,.epoch-theme-dark .epoch.category20c .category12 .dot{fill:#918551;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20c .arc.category12 path{fill:#918551;}.epoch-theme-dark .epoch.category20c .bar.category12{fill:#918551;}.epoch-theme-dark .epoch.category20c div.ref.category13{background-color:#C9935E;}.epoch-theme-dark .epoch.category20c .category13 .line{stroke:#C9935E;}.epoch-theme-dark .epoch.category20c .category13 .area,.epoch-theme-dark .epoch.category20c .category13 .dot{fill:#C9935E;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20c .arc.category13 path{fill:#C9935E;}.epoch-theme-dark .epoch.category20c .bar.category13{fill:#C9935E;}.epoch-theme-dark .epoch.category20c div.ref.category14{background-color:#B58455;}.epoch-theme-dark .epoch.category20c .category14 .line{stroke:#B58455;}.epoch-theme-dark .epoch.category20c .category14 .area,.epoch-theme-dark .epoch.category20c .category14 .dot{fill:#B58455;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20c .arc.category14 path{fill:#B58455;}.epoch-theme-dark .epoch.category20c .bar.category14{fill:#B58455;}.epoch-theme-dark .epoch.category20c div.ref.category15{background-color:#997048;}.epoch-theme-dark .epoch.category20c .category15 .line{stroke:#997048;}.epoch-theme-dark .epoch.category20c .category15 .area,.epoch-theme-dark .epoch.category20c .category15 .dot{fill:#997048;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20c .arc.category15 path{fill:#997048;}.epoch-theme-dark .epoch.category20c .bar.category15{fill:#997048;}.epoch-theme-dark .epoch.category20c div.ref.category16{background-color:#735436;}.epoch-theme-dark .epoch.category20c .category16 .line{stroke:#735436;}.epoch-theme-dark .epoch.category20c .category16 .area,.epoch-theme-dark .epoch.category20c .category16 .dot{fill:#735436;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20c .arc.category16 path{fill:#735436;}.epoch-theme-dark .epoch.category20c .bar.category16{fill:#735436;}.epoch-theme-dark .epoch.category20c div.ref.category17{background-color:#A488FF;}.epoch-theme-dark .epoch.category20c .category17 .line{stroke:#A488FF;}.epoch-theme-dark .epoch.category20c .category17 .area,.epoch-theme-dark .epoch.category20c .category17 .dot{fill:#A488FF;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20c .arc.category17 path{fill:#A488FF;}.epoch-theme-dark .epoch.category20c .bar.category17{fill:#A488FF;}.epoch-theme-dark .epoch.category20c div.ref.category18{background-color:#8670D1;}.epoch-theme-dark .epoch.category20c .category18 .line{stroke:#8670D1;}.epoch-theme-dark .epoch.category20c .category18 .area,.epoch-theme-dark .epoch.category20c .category18 .dot{fill:#8670D1;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20c .arc.category18 path{fill:#8670D1;}.epoch-theme-dark .epoch.category20c .bar.category18{fill:#8670D1;}.epoch-theme-dark .epoch.category20c div.ref.category19{background-color:#705CAD;}.epoch-theme-dark .epoch.category20c .category19 .line{stroke:#705CAD;}.epoch-theme-dark .epoch.category20c .category19 .area,.epoch-theme-dark .epoch.category20c .category19 .dot{fill:#705CAD;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20c .arc.category19 path{fill:#705CAD;}.epoch-theme-dark .epoch.category20c .bar.category19{fill:#705CAD;}.epoch-theme-dark .epoch.category20c div.ref.category20{background-color:#52447F;}.epoch-theme-dark .epoch.category20c .category20 .line{stroke:#52447F;}.epoch-theme-dark .epoch.category20c .category20 .area,.epoch-theme-dark .epoch.category20c .category20 .dot{fill:#52447F;stroke:rgba(0, 0, 0, 0);}.epoch-theme-dark .epoch.category20c .arc.category20 path{fill:#52447F;}.epoch-theme-dark .epoch.category20c .bar.category20{fill:#52447F;} \ No newline at end of file diff --git a/vendor/github.com/gin-gonic/gin/examples/realtime-advanced/resources/static/prismjs.min.css b/vendor/github.com/gin-gonic/gin/examples/realtime-advanced/resources/static/prismjs.min.css deleted file mode 100644 index 0d9d8fb13..000000000 --- a/vendor/github.com/gin-gonic/gin/examples/realtime-advanced/resources/static/prismjs.min.css +++ /dev/null @@ -1,137 +0,0 @@ -/* http://prismjs.com/download.html?themes=prism&languages=clike+javascript+go */ -/** - * prism.js default theme for JavaScript, CSS and HTML - * Based on dabblet (http://dabblet.com) - * @author Lea Verou - */ - -code[class*="language-"], -pre[class*="language-"] { - color: black; - text-shadow: 0 1px white; - font-family: Consolas, Monaco, 'Andale Mono', monospace; - direction: ltr; - text-align: left; - white-space: pre; - word-spacing: normal; - word-break: normal; - line-height: 1.5; - - -moz-tab-size: 4; - -o-tab-size: 4; - tab-size: 4; - - -webkit-hyphens: none; - -moz-hyphens: none; - -ms-hyphens: none; - hyphens: none; -} - -pre[class*="language-"]::-moz-selection, pre[class*="language-"] ::-moz-selection, -code[class*="language-"]::-moz-selection, code[class*="language-"] ::-moz-selection { - text-shadow: none; - background: #b3d4fc; -} - -pre[class*="language-"]::selection, pre[class*="language-"] ::selection, -code[class*="language-"]::selection, code[class*="language-"] ::selection { - text-shadow: none; - background: #b3d4fc; -} - -@media print { - code[class*="language-"], - pre[class*="language-"] { - text-shadow: none; - } -} - -/* Code blocks */ -pre[class*="language-"] { - padding: 1em; - margin: .5em 0; - overflow: auto; -} - -:not(pre) > code[class*="language-"], -pre[class*="language-"] { - background: #f5f2f0; -} - -/* Inline code */ -:not(pre) > code[class*="language-"] { - padding: .1em; - border-radius: .3em; -} - -.token.comment, -.token.prolog, -.token.doctype, -.token.cdata { - color: slategray; -} - -.token.punctuation { - color: #999; -} - -.namespace { - opacity: .7; -} - -.token.property, -.token.tag, -.token.boolean, -.token.number, -.token.constant, -.token.symbol, -.token.deleted { - color: #905; -} - -.token.selector, -.token.attr-name, -.token.string, -.token.char, -.token.builtin, -.token.inserted { - color: #690; -} - -.token.operator, -.token.entity, -.token.url, -.language-css .token.string, -.style .token.string { - color: #a67f59; - background: hsla(0, 0%, 100%, .5); -} - -.token.atrule, -.token.attr-value, -.token.keyword { - color: #07a; -} - -.token.function { - color: #DD4A68; -} - -.token.regex, -.token.important, -.token.variable { - color: #e90; -} - -.token.important, -.token.bold { - font-weight: bold; -} -.token.italic { - font-style: italic; -} - -.token.entity { - cursor: help; -} - diff --git a/vendor/github.com/gin-gonic/gin/examples/realtime-advanced/resources/static/realtime.js b/vendor/github.com/gin-gonic/gin/examples/realtime-advanced/resources/static/realtime.js deleted file mode 100644 index 919dae26c..000000000 --- a/vendor/github.com/gin-gonic/gin/examples/realtime-advanced/resources/static/realtime.js +++ /dev/null @@ -1,144 +0,0 @@ - - -function StartRealtime(roomid, timestamp) { - StartEpoch(timestamp); - StartSSE(roomid); - StartForm(); -} - -function StartForm() { - $('#chat-message').focus(); - $('#chat-form').ajaxForm(function() { - $('#chat-message').val(''); - $('#chat-message').focus(); - }); -} - -function StartEpoch(timestamp) { - var windowSize = 60; - var height = 200; - var defaultData = histogram(windowSize, timestamp); - - window.heapChart = $('#heapChart').epoch({ - type: 'time.area', - axes: ['bottom', 'left'], - height: height, - historySize: 10, - data: [ - {values: defaultData}, - {values: defaultData} - ] - }); - - window.mallocsChart = $('#mallocsChart').epoch({ - type: 'time.area', - axes: ['bottom', 'left'], - height: height, - historySize: 10, - data: [ - {values: defaultData}, - {values: defaultData} - ] - }); - - window.messagesChart = $('#messagesChart').epoch({ - type: 'time.line', - axes: ['bottom', 'left'], - height: 240, - historySize: 10, - data: [ - {values: defaultData}, - {values: defaultData}, - {values: defaultData} - ] - }); -} - -function StartSSE(roomid) { - if (!window.EventSource) { - alert("EventSource is not enabled in this browser"); - return; - } - var source = new EventSource('/stream/'+roomid); - source.addEventListener('message', newChatMessage, false); - source.addEventListener('stats', stats, false); -} - -function stats(e) { - var data = parseJSONStats(e.data); - heapChart.push(data.heap); - mallocsChart.push(data.mallocs); - messagesChart.push(data.messages); -} - -function parseJSONStats(e) { - var data = jQuery.parseJSON(e); - var timestamp = data.timestamp; - - var heap = [ - {time: timestamp, y: data.HeapInuse}, - {time: timestamp, y: data.StackInuse} - ]; - - var mallocs = [ - {time: timestamp, y: data.Mallocs}, - {time: timestamp, y: data.Frees} - ]; - var messages = [ - {time: timestamp, y: data.Connected}, - {time: timestamp, y: data.Inbound}, - {time: timestamp, y: data.Outbound} - ]; - - return { - heap: heap, - mallocs: mallocs, - messages: messages - } -} - -function newChatMessage(e) { - var data = jQuery.parseJSON(e.data); - var nick = data.nick; - var message = data.message; - var style = rowStyle(nick); - var html = ""+nick+""+message+""; - $('#chat').append(html); - - $("#chat-scroll").scrollTop($("#chat-scroll")[0].scrollHeight); -} - -function histogram(windowSize, timestamp) { - var entries = new Array(windowSize); - for(var i = 0; i < windowSize; i++) { - entries[i] = {time: (timestamp-windowSize+i-1), y:0}; - } - return entries; -} - -var entityMap = { - "&": "&", - "<": "<", - ">": ">", - '"': '"', - "'": ''', - "/": '/' -}; - -function rowStyle(nick) { - var classes = ['active', 'success', 'info', 'warning', 'danger']; - var index = hashCode(nick)%5; - return classes[index]; -} - -function hashCode(s){ - return Math.abs(s.split("").reduce(function(a,b){a=((a<<5)-a)+b.charCodeAt(0);return a&a},0)); -} - -function escapeHtml(string) { - return String(string).replace(/[&<>"'\/]/g, function (s) { - return entityMap[s]; - }); -} - -window.StartRealtime = StartRealtime diff --git a/vendor/github.com/gin-gonic/gin/examples/realtime-advanced/rooms.go b/vendor/github.com/gin-gonic/gin/examples/realtime-advanced/rooms.go deleted file mode 100644 index 82396ba37..000000000 --- a/vendor/github.com/gin-gonic/gin/examples/realtime-advanced/rooms.go +++ /dev/null @@ -1,25 +0,0 @@ -package main - -import "github.com/dustin/go-broadcast" - -var roomChannels = make(map[string]broadcast.Broadcaster) - -func openListener(roomid string) chan interface{} { - listener := make(chan interface{}) - room(roomid).Register(listener) - return listener -} - -func closeListener(roomid string, listener chan interface{}) { - room(roomid).Unregister(listener) - close(listener) -} - -func room(roomid string) broadcast.Broadcaster { - b, ok := roomChannels[roomid] - if !ok { - b = broadcast.NewBroadcaster(10) - roomChannels[roomid] = b - } - return b -} diff --git a/vendor/github.com/gin-gonic/gin/examples/realtime-advanced/routes.go b/vendor/github.com/gin-gonic/gin/examples/realtime-advanced/routes.go deleted file mode 100644 index b18775658..000000000 --- a/vendor/github.com/gin-gonic/gin/examples/realtime-advanced/routes.go +++ /dev/null @@ -1,96 +0,0 @@ -package main - -import ( - "fmt" - "html" - "io" - "strings" - "time" - - "github.com/gin-gonic/gin" -) - -func rateLimit(c *gin.Context) { - - ip := c.ClientIP() - value := int(ips.Add(ip, 1)) - if value%50 == 0 { - fmt.Printf("ip: %s, count: %d\n", ip, value) - } - if value >= 200 { - if value%200 == 0 { - fmt.Println("ip blocked") - } - c.Abort() - c.String(503, "you were automatically banned :)") - } -} - -func index(c *gin.Context) { - c.Redirect(301, "/room/hn") -} - -func roomGET(c *gin.Context) { - roomid := c.Param("roomid") - nick := c.Query("nick") - if len(nick) < 2 { - nick = "" - } - if len(nick) > 13 { - nick = nick[0:12] + "..." - } - c.HTML(200, "room_login.templ.html", gin.H{ - "roomid": roomid, - "nick": nick, - "timestamp": time.Now().Unix(), - }) - -} - -func roomPOST(c *gin.Context) { - roomid := c.Param("roomid") - nick := c.Query("nick") - message := c.PostForm("message") - message = strings.TrimSpace(message) - - validMessage := len(message) > 1 && len(message) < 200 - validNick := len(nick) > 1 && len(nick) < 14 - if !validMessage || !validNick { - c.JSON(400, gin.H{ - "status": "failed", - "error": "the message or nickname is too long", - }) - return - } - - post := gin.H{ - "nick": html.EscapeString(nick), - "message": html.EscapeString(message), - } - messages.Add("inbound", 1) - room(roomid).Submit(post) - c.JSON(200, post) -} - -func streamRoom(c *gin.Context) { - roomid := c.Param("roomid") - listener := openListener(roomid) - ticker := time.NewTicker(1 * time.Second) - users.Add("connected", 1) - defer func() { - closeListener(roomid, listener) - ticker.Stop() - users.Add("disconnected", 1) - }() - - c.Stream(func(w io.Writer) bool { - select { - case msg := <-listener: - messages.Add("outbound", 1) - c.SSEvent("message", msg) - case <-ticker.C: - c.SSEvent("stats", Stats()) - } - return true - }) -} diff --git a/vendor/github.com/gin-gonic/gin/examples/realtime-advanced/stats.go b/vendor/github.com/gin-gonic/gin/examples/realtime-advanced/stats.go deleted file mode 100644 index c36ecc781..000000000 --- a/vendor/github.com/gin-gonic/gin/examples/realtime-advanced/stats.go +++ /dev/null @@ -1,56 +0,0 @@ -package main - -import ( - "runtime" - "sync" - "time" - - "github.com/manucorporat/stats" -) - -var ips = stats.New() -var messages = stats.New() -var users = stats.New() -var mutexStats sync.RWMutex -var savedStats map[string]uint64 - -func statsWorker() { - c := time.Tick(1 * time.Second) - var lastMallocs uint64 = 0 - var lastFrees uint64 = 0 - for _ = range c { - var stats runtime.MemStats - runtime.ReadMemStats(&stats) - - mutexStats.Lock() - savedStats = map[string]uint64{ - "timestamp": uint64(time.Now().Unix()), - "HeapInuse": stats.HeapInuse, - "StackInuse": stats.StackInuse, - "Mallocs": (stats.Mallocs - lastMallocs), - "Frees": (stats.Frees - lastFrees), - "Inbound": uint64(messages.Get("inbound")), - "Outbound": uint64(messages.Get("outbound")), - "Connected": connectedUsers(), - } - lastMallocs = stats.Mallocs - lastFrees = stats.Frees - messages.Reset() - mutexStats.Unlock() - } -} - -func connectedUsers() uint64 { - connected := users.Get("connected") - users.Get("disconnected") - if connected < 0 { - return 0 - } - return uint64(connected) -} - -func Stats() map[string]uint64 { - mutexStats.RLock() - defer mutexStats.RUnlock() - - return savedStats -} diff --git a/vendor/github.com/gin-gonic/gin/examples/realtime-chat/main.go b/vendor/github.com/gin-gonic/gin/examples/realtime-chat/main.go deleted file mode 100644 index e4b55a0f0..000000000 --- a/vendor/github.com/gin-gonic/gin/examples/realtime-chat/main.go +++ /dev/null @@ -1,58 +0,0 @@ -package main - -import ( - "fmt" - "io" - "math/rand" - - "github.com/gin-gonic/gin" -) - -func main() { - router := gin.Default() - router.SetHTMLTemplate(html) - - router.GET("/room/:roomid", roomGET) - router.POST("/room/:roomid", roomPOST) - router.DELETE("/room/:roomid", roomDELETE) - router.GET("/stream/:roomid", stream) - - router.Run(":8080") -} - -func stream(c *gin.Context) { - roomid := c.Param("roomid") - listener := openListener(roomid) - defer closeListener(roomid, listener) - - c.Stream(func(w io.Writer) bool { - c.SSEvent("message", <-listener) - return true - }) -} - -func roomGET(c *gin.Context) { - roomid := c.Param("roomid") - userid := fmt.Sprint(rand.Int31()) - c.HTML(200, "chat_room", gin.H{ - "roomid": roomid, - "userid": userid, - }) -} - -func roomPOST(c *gin.Context) { - roomid := c.Param("roomid") - userid := c.PostForm("user") - message := c.PostForm("message") - room(roomid).Submit(userid + ": " + message) - - c.JSON(200, gin.H{ - "status": "success", - "message": message, - }) -} - -func roomDELETE(c *gin.Context) { - roomid := c.Param("roomid") - deleteBroadcast(roomid) -} diff --git a/vendor/github.com/gin-gonic/gin/examples/realtime-chat/rooms.go b/vendor/github.com/gin-gonic/gin/examples/realtime-chat/rooms.go deleted file mode 100644 index 8c62bece1..000000000 --- a/vendor/github.com/gin-gonic/gin/examples/realtime-chat/rooms.go +++ /dev/null @@ -1,33 +0,0 @@ -package main - -import "github.com/dustin/go-broadcast" - -var roomChannels = make(map[string]broadcast.Broadcaster) - -func openListener(roomid string) chan interface{} { - listener := make(chan interface{}) - room(roomid).Register(listener) - return listener -} - -func closeListener(roomid string, listener chan interface{}) { - room(roomid).Unregister(listener) - close(listener) -} - -func deleteBroadcast(roomid string) { - b, ok := roomChannels[roomid] - if ok { - b.Close() - delete(roomChannels, roomid) - } -} - -func room(roomid string) broadcast.Broadcaster { - b, ok := roomChannels[roomid] - if !ok { - b = broadcast.NewBroadcaster(10) - roomChannels[roomid] = b - } - return b -} diff --git a/vendor/github.com/gin-gonic/gin/examples/realtime-chat/template.go b/vendor/github.com/gin-gonic/gin/examples/realtime-chat/template.go deleted file mode 100644 index b9024de6d..000000000 --- a/vendor/github.com/gin-gonic/gin/examples/realtime-chat/template.go +++ /dev/null @@ -1,44 +0,0 @@ -package main - -import "html/template" - -var html = template.Must(template.New("chat_room").Parse(` - - - {{.roomid}} - - - - - - -

Welcome to {{.roomid}} room

-
-
- User: - Message: - -
- - -`)) diff --git a/vendor/github.com/gin-gonic/gin/gin.go b/vendor/github.com/gin-gonic/gin/gin.go index 3834d67e5..fb1df9cd0 100644 --- a/vendor/github.com/gin-gonic/gin/gin.go +++ b/vendor/github.com/gin-gonic/gin/gin.go @@ -113,7 +113,7 @@ func New() *Engine { // Default returns an Engine instance with the Logger and Recovery middleware already attached. func Default() *Engine { engine := New() - engine.Use(Recovery(), Logger()) + engine.Use(Logger(), Recovery()) return engine } @@ -178,25 +178,15 @@ func (engine *Engine) rebuild405Handlers() { } func (engine *Engine) addRoute(method, path string, handlers HandlersChain) { + assert1(path[0] == '/', "path must begin with '/'") + assert1(len(method) > 0, "HTTP method can not be empty") + assert1(len(handlers) > 0, "there must be at least one handler") + debugPrintRoute(method, path, handlers) - - if path[0] != '/' { - panic("path must begin with '/'") - } - if method == "" { - panic("HTTP method can not be empty") - } - if len(handlers) == 0 { - panic("there must be at least one handler") - } - root := engine.trees.get(method) if root == nil { root = new(node) - engine.trees = append(engine.trees, methodTree{ - method: method, - root: root, - }) + engine.trees = append(engine.trees, methodTree{method: method, root: root}) } root.addRoute(path, handlers) } @@ -227,7 +217,7 @@ func iterate(path, method string, routes RoutesInfo, root *node) RoutesInfo { // Run attaches the router to a http.Server and starts listening and serving HTTP requests. // It is a shortcut for http.ListenAndServe(addr, router) -// Note: this method will block the calling goroutine undefinitelly unless an error happens. +// Note: this method will block the calling goroutine indefinitely unless an error happens. func (engine *Engine) Run(addr ...string) (err error) { defer func() { debugPrintError(err) }() @@ -239,7 +229,7 @@ func (engine *Engine) Run(addr ...string) (err error) { // RunTLS attaches the router to a http.Server and starts listening and serving HTTPS (secure) requests. // It is a shortcut for http.ListenAndServeTLS(addr, certFile, keyFile, router) -// Note: this method will block the calling goroutine undefinitelly unless an error happens. +// Note: this method will block the calling goroutine indefinitely unless an error happens. func (engine *Engine) RunTLS(addr string, certFile string, keyFile string) (err error) { debugPrint("Listening and serving HTTPS on %s\n", addr) defer func() { debugPrintError(err) }() @@ -250,7 +240,7 @@ func (engine *Engine) RunTLS(addr string, certFile string, keyFile string) (err // RunUnix attaches the router to a http.Server and starts listening and serving HTTP requests // through the specified unix socket (ie. a file). -// Note: this method will block the calling goroutine undefinitelly unless an error happens. +// Note: this method will block the calling goroutine indefinitely unless an error happens. func (engine *Engine) RunUnix(file string) (err error) { debugPrint("Listening and serving HTTP on unix:/%s", file) defer func() { debugPrintError(err) }() diff --git a/vendor/github.com/gin-gonic/gin/gin_integration_test.go b/vendor/github.com/gin-gonic/gin/gin_integration_test.go deleted file mode 100644 index 4777c0c9a..000000000 --- a/vendor/github.com/gin-gonic/gin/gin_integration_test.go +++ /dev/null @@ -1,105 +0,0 @@ -package gin - -import ( - "bufio" - "fmt" - "io/ioutil" - "net" - "net/http" - "os" - "testing" - "time" - - "github.com/stretchr/testify/assert" -) - -func testRequest(t *testing.T, url string) { - resp, err := http.Get(url) - defer resp.Body.Close() - assert.NoError(t, err) - - body, ioerr := ioutil.ReadAll(resp.Body) - assert.NoError(t, ioerr) - assert.Equal(t, "it worked", string(body), "resp body should match") - assert.Equal(t, "200 OK", resp.Status, "should get a 200") -} - -func TestRunEmpty(t *testing.T) { - os.Setenv("PORT", "") - router := New() - go func() { - router.GET("/example", func(c *Context) { c.String(http.StatusOK, "it worked") }) - assert.NoError(t, router.Run()) - }() - // have to wait for the goroutine to start and run the server - // otherwise the main thread will complete - time.Sleep(5 * time.Millisecond) - - assert.Error(t, router.Run(":8080")) - testRequest(t, "http://localhost:8080/example") -} - -func TestRunEmptyWithEnv(t *testing.T) { - os.Setenv("PORT", "3123") - router := New() - go func() { - router.GET("/example", func(c *Context) { c.String(http.StatusOK, "it worked") }) - assert.NoError(t, router.Run()) - }() - // have to wait for the goroutine to start and run the server - // otherwise the main thread will complete - time.Sleep(5 * time.Millisecond) - - assert.Error(t, router.Run(":3123")) - testRequest(t, "http://localhost:3123/example") -} - -func TestRunTooMuchParams(t *testing.T) { - router := New() - assert.Panics(t, func() { - router.Run("2", "2") - }) -} - -func TestRunWithPort(t *testing.T) { - router := New() - go func() { - router.GET("/example", func(c *Context) { c.String(http.StatusOK, "it worked") }) - assert.NoError(t, router.Run(":5150")) - }() - // have to wait for the goroutine to start and run the server - // otherwise the main thread will complete - time.Sleep(5 * time.Millisecond) - - assert.Error(t, router.Run(":5150")) - testRequest(t, "http://localhost:5150/example") -} - -func TestUnixSocket(t *testing.T) { - router := New() - - go func() { - router.GET("/example", func(c *Context) { c.String(http.StatusOK, "it worked") }) - assert.NoError(t, router.RunUnix("/tmp/unix_unit_test")) - }() - // have to wait for the goroutine to start and run the server - // otherwise the main thread will complete - time.Sleep(5 * time.Millisecond) - - c, err := net.Dial("unix", "/tmp/unix_unit_test") - assert.NoError(t, err) - - fmt.Fprintf(c, "GET /example HTTP/1.0\r\n\r\n") - scanner := bufio.NewScanner(c) - var response string - for scanner.Scan() { - response += scanner.Text() - } - assert.Contains(t, response, "HTTP/1.0 200", "should get a 200") - assert.Contains(t, response, "it worked", "resp body should match") -} - -func TestBadUnixSocket(t *testing.T) { - router := New() - assert.Error(t, router.RunUnix("#/tmp/unix_unit_test")) -} diff --git a/vendor/github.com/gin-gonic/gin/gin_test.go b/vendor/github.com/gin-gonic/gin/gin_test.go deleted file mode 100644 index b3b0eb6ba..000000000 --- a/vendor/github.com/gin-gonic/gin/gin_test.go +++ /dev/null @@ -1,245 +0,0 @@ -// Copyright 2014 Manu Martinez-Almeida. All rights reserved. -// Use of this source code is governed by a MIT style -// license that can be found in the LICENSE file. - -package gin - -import ( - "reflect" - "testing" - - "github.com/stretchr/testify/assert" -) - -//TODO -// func (engine *Engine) LoadHTMLGlob(pattern string) { -// func (engine *Engine) LoadHTMLFiles(files ...string) { -// func (engine *Engine) RunTLS(addr string, cert string, key string) error { - -func init() { - SetMode(TestMode) -} - -func TestCreateEngine(t *testing.T) { - router := New() - assert.Equal(t, "/", router.basePath) - assert.Equal(t, router.engine, router) - assert.Empty(t, router.Handlers) -} - -// func TestLoadHTMLDebugMode(t *testing.T) { -// router := New() -// SetMode(DebugMode) -// router.LoadHTMLGlob("*.testtmpl") -// r := router.HTMLRender.(render.HTMLDebug) -// assert.Empty(t, r.Files) -// assert.Equal(t, r.Glob, "*.testtmpl") -// -// router.LoadHTMLFiles("index.html.testtmpl", "login.html.testtmpl") -// r = router.HTMLRender.(render.HTMLDebug) -// assert.Empty(t, r.Glob) -// assert.Equal(t, r.Files, []string{"index.html", "login.html"}) -// SetMode(TestMode) -// } - -func TestLoadHTMLReleaseMode(t *testing.T) { - -} - -func TestAddRoute(t *testing.T) { - router := New() - router.addRoute("GET", "/", HandlersChain{func(_ *Context) {}}) - - assert.Len(t, router.trees, 1) - assert.NotNil(t, router.trees.get("GET")) - assert.Nil(t, router.trees.get("POST")) - - router.addRoute("POST", "/", HandlersChain{func(_ *Context) {}}) - - assert.Len(t, router.trees, 2) - assert.NotNil(t, router.trees.get("GET")) - assert.NotNil(t, router.trees.get("POST")) - - router.addRoute("POST", "/post", HandlersChain{func(_ *Context) {}}) - assert.Len(t, router.trees, 2) -} - -func TestAddRouteFails(t *testing.T) { - router := New() - assert.Panics(t, func() { router.addRoute("", "/", HandlersChain{func(_ *Context) {}}) }) - assert.Panics(t, func() { router.addRoute("GET", "a", HandlersChain{func(_ *Context) {}}) }) - assert.Panics(t, func() { router.addRoute("GET", "/", HandlersChain{}) }) - - router.addRoute("POST", "/post", HandlersChain{func(_ *Context) {}}) - assert.Panics(t, func() { - router.addRoute("POST", "/post", HandlersChain{func(_ *Context) {}}) - }) -} - -func TestCreateDefaultRouter(t *testing.T) { - router := Default() - assert.Len(t, router.Handlers, 2) -} - -func TestNoRouteWithoutGlobalHandlers(t *testing.T) { - var middleware0 HandlerFunc = func(c *Context) {} - var middleware1 HandlerFunc = func(c *Context) {} - - router := New() - - router.NoRoute(middleware0) - assert.Nil(t, router.Handlers) - assert.Len(t, router.noRoute, 1) - assert.Len(t, router.allNoRoute, 1) - compareFunc(t, router.noRoute[0], middleware0) - compareFunc(t, router.allNoRoute[0], middleware0) - - router.NoRoute(middleware1, middleware0) - assert.Len(t, router.noRoute, 2) - assert.Len(t, router.allNoRoute, 2) - compareFunc(t, router.noRoute[0], middleware1) - compareFunc(t, router.allNoRoute[0], middleware1) - compareFunc(t, router.noRoute[1], middleware0) - compareFunc(t, router.allNoRoute[1], middleware0) -} - -func TestNoRouteWithGlobalHandlers(t *testing.T) { - var middleware0 HandlerFunc = func(c *Context) {} - var middleware1 HandlerFunc = func(c *Context) {} - var middleware2 HandlerFunc = func(c *Context) {} - - router := New() - router.Use(middleware2) - - router.NoRoute(middleware0) - assert.Len(t, router.allNoRoute, 2) - assert.Len(t, router.Handlers, 1) - assert.Len(t, router.noRoute, 1) - - compareFunc(t, router.Handlers[0], middleware2) - compareFunc(t, router.noRoute[0], middleware0) - compareFunc(t, router.allNoRoute[0], middleware2) - compareFunc(t, router.allNoRoute[1], middleware0) - - router.Use(middleware1) - assert.Len(t, router.allNoRoute, 3) - assert.Len(t, router.Handlers, 2) - assert.Len(t, router.noRoute, 1) - - compareFunc(t, router.Handlers[0], middleware2) - compareFunc(t, router.Handlers[1], middleware1) - compareFunc(t, router.noRoute[0], middleware0) - compareFunc(t, router.allNoRoute[0], middleware2) - compareFunc(t, router.allNoRoute[1], middleware1) - compareFunc(t, router.allNoRoute[2], middleware0) -} - -func TestNoMethodWithoutGlobalHandlers(t *testing.T) { - var middleware0 HandlerFunc = func(c *Context) {} - var middleware1 HandlerFunc = func(c *Context) {} - - router := New() - - router.NoMethod(middleware0) - assert.Empty(t, router.Handlers) - assert.Len(t, router.noMethod, 1) - assert.Len(t, router.allNoMethod, 1) - compareFunc(t, router.noMethod[0], middleware0) - compareFunc(t, router.allNoMethod[0], middleware0) - - router.NoMethod(middleware1, middleware0) - assert.Len(t, router.noMethod, 2) - assert.Len(t, router.allNoMethod, 2) - compareFunc(t, router.noMethod[0], middleware1) - compareFunc(t, router.allNoMethod[0], middleware1) - compareFunc(t, router.noMethod[1], middleware0) - compareFunc(t, router.allNoMethod[1], middleware0) -} - -func TestRebuild404Handlers(t *testing.T) { - -} - -func TestNoMethodWithGlobalHandlers(t *testing.T) { - var middleware0 HandlerFunc = func(c *Context) {} - var middleware1 HandlerFunc = func(c *Context) {} - var middleware2 HandlerFunc = func(c *Context) {} - - router := New() - router.Use(middleware2) - - router.NoMethod(middleware0) - assert.Len(t, router.allNoMethod, 2) - assert.Len(t, router.Handlers, 1) - assert.Len(t, router.noMethod, 1) - - compareFunc(t, router.Handlers[0], middleware2) - compareFunc(t, router.noMethod[0], middleware0) - compareFunc(t, router.allNoMethod[0], middleware2) - compareFunc(t, router.allNoMethod[1], middleware0) - - router.Use(middleware1) - assert.Len(t, router.allNoMethod, 3) - assert.Len(t, router.Handlers, 2) - assert.Len(t, router.noMethod, 1) - - compareFunc(t, router.Handlers[0], middleware2) - compareFunc(t, router.Handlers[1], middleware1) - compareFunc(t, router.noMethod[0], middleware0) - compareFunc(t, router.allNoMethod[0], middleware2) - compareFunc(t, router.allNoMethod[1], middleware1) - compareFunc(t, router.allNoMethod[2], middleware0) -} - -func compareFunc(t *testing.T, a, b interface{}) { - sf1 := reflect.ValueOf(a) - sf2 := reflect.ValueOf(b) - if sf1.Pointer() != sf2.Pointer() { - t.Error("different functions") - } -} - -func TestListOfRoutes(t *testing.T) { - router := New() - router.GET("/favicon.ico", handler_test1) - router.GET("/", handler_test1) - group := router.Group("/users") - { - group.GET("/", handler_test2) - group.GET("/:id", handler_test1) - group.POST("/:id", handler_test2) - } - router.Static("/static", ".") - - list := router.Routes() - - assert.Len(t, list, 7) - assert.Contains(t, list, RouteInfo{ - Method: "GET", - Path: "/favicon.ico", - Handler: "github.com/gin-gonic/gin.handler_test1", - }) - assert.Contains(t, list, RouteInfo{ - Method: "GET", - Path: "/", - Handler: "github.com/gin-gonic/gin.handler_test1", - }) - assert.Contains(t, list, RouteInfo{ - Method: "GET", - Path: "/users/", - Handler: "github.com/gin-gonic/gin.handler_test2", - }) - assert.Contains(t, list, RouteInfo{ - Method: "GET", - Path: "/users/:id", - Handler: "github.com/gin-gonic/gin.handler_test1", - }) - assert.Contains(t, list, RouteInfo{ - Method: "POST", - Path: "/users/:id", - Handler: "github.com/gin-gonic/gin.handler_test2", - }) -} - -func handler_test1(c *Context) {} -func handler_test2(c *Context) {} diff --git a/vendor/github.com/gin-gonic/gin/githubapi_test.go b/vendor/github.com/gin-gonic/gin/githubapi_test.go deleted file mode 100644 index 2227fa6ae..000000000 --- a/vendor/github.com/gin-gonic/gin/githubapi_test.go +++ /dev/null @@ -1,389 +0,0 @@ -// Copyright 2014 Manu Martinez-Almeida. All rights reserved. -// Use of this source code is governed by a MIT style -// license that can be found in the LICENSE file. - -package gin - -import ( - "bytes" - "fmt" - "math/rand" - "net/http" - "net/http/httptest" - "testing" - - "github.com/stretchr/testify/assert" -) - -type route struct { - method string - path string -} - -// http://developer.github.com/v3/ -var githubAPI = []route{ - // OAuth Authorizations - {"GET", "/authorizations"}, - {"GET", "/authorizations/:id"}, - {"POST", "/authorizations"}, - //{"PUT", "/authorizations/clients/:client_id"}, - //{"PATCH", "/authorizations/:id"}, - {"DELETE", "/authorizations/:id"}, - {"GET", "/applications/:client_id/tokens/:access_token"}, - {"DELETE", "/applications/:client_id/tokens"}, - {"DELETE", "/applications/:client_id/tokens/:access_token"}, - - // Activity - {"GET", "/events"}, - {"GET", "/repos/:owner/:repo/events"}, - {"GET", "/networks/:owner/:repo/events"}, - {"GET", "/orgs/:org/events"}, - {"GET", "/users/:user/received_events"}, - {"GET", "/users/:user/received_events/public"}, - {"GET", "/users/:user/events"}, - {"GET", "/users/:user/events/public"}, - {"GET", "/users/:user/events/orgs/:org"}, - {"GET", "/feeds"}, - {"GET", "/notifications"}, - {"GET", "/repos/:owner/:repo/notifications"}, - {"PUT", "/notifications"}, - {"PUT", "/repos/:owner/:repo/notifications"}, - {"GET", "/notifications/threads/:id"}, - //{"PATCH", "/notifications/threads/:id"}, - {"GET", "/notifications/threads/:id/subscription"}, - {"PUT", "/notifications/threads/:id/subscription"}, - {"DELETE", "/notifications/threads/:id/subscription"}, - {"GET", "/repos/:owner/:repo/stargazers"}, - {"GET", "/users/:user/starred"}, - {"GET", "/user/starred"}, - {"GET", "/user/starred/:owner/:repo"}, - {"PUT", "/user/starred/:owner/:repo"}, - {"DELETE", "/user/starred/:owner/:repo"}, - {"GET", "/repos/:owner/:repo/subscribers"}, - {"GET", "/users/:user/subscriptions"}, - {"GET", "/user/subscriptions"}, - {"GET", "/repos/:owner/:repo/subscription"}, - {"PUT", "/repos/:owner/:repo/subscription"}, - {"DELETE", "/repos/:owner/:repo/subscription"}, - {"GET", "/user/subscriptions/:owner/:repo"}, - {"PUT", "/user/subscriptions/:owner/:repo"}, - {"DELETE", "/user/subscriptions/:owner/:repo"}, - - // Gists - {"GET", "/users/:user/gists"}, - {"GET", "/gists"}, - //{"GET", "/gists/public"}, - //{"GET", "/gists/starred"}, - {"GET", "/gists/:id"}, - {"POST", "/gists"}, - //{"PATCH", "/gists/:id"}, - {"PUT", "/gists/:id/star"}, - {"DELETE", "/gists/:id/star"}, - {"GET", "/gists/:id/star"}, - {"POST", "/gists/:id/forks"}, - {"DELETE", "/gists/:id"}, - - // Git Data - {"GET", "/repos/:owner/:repo/git/blobs/:sha"}, - {"POST", "/repos/:owner/:repo/git/blobs"}, - {"GET", "/repos/:owner/:repo/git/commits/:sha"}, - {"POST", "/repos/:owner/:repo/git/commits"}, - //{"GET", "/repos/:owner/:repo/git/refs/*ref"}, - {"GET", "/repos/:owner/:repo/git/refs"}, - {"POST", "/repos/:owner/:repo/git/refs"}, - //{"PATCH", "/repos/:owner/:repo/git/refs/*ref"}, - //{"DELETE", "/repos/:owner/:repo/git/refs/*ref"}, - {"GET", "/repos/:owner/:repo/git/tags/:sha"}, - {"POST", "/repos/:owner/:repo/git/tags"}, - {"GET", "/repos/:owner/:repo/git/trees/:sha"}, - {"POST", "/repos/:owner/:repo/git/trees"}, - - // Issues - {"GET", "/issues"}, - {"GET", "/user/issues"}, - {"GET", "/orgs/:org/issues"}, - {"GET", "/repos/:owner/:repo/issues"}, - {"GET", "/repos/:owner/:repo/issues/:number"}, - {"POST", "/repos/:owner/:repo/issues"}, - //{"PATCH", "/repos/:owner/:repo/issues/:number"}, - {"GET", "/repos/:owner/:repo/assignees"}, - {"GET", "/repos/:owner/:repo/assignees/:assignee"}, - {"GET", "/repos/:owner/:repo/issues/:number/comments"}, - //{"GET", "/repos/:owner/:repo/issues/comments"}, - //{"GET", "/repos/:owner/:repo/issues/comments/:id"}, - {"POST", "/repos/:owner/:repo/issues/:number/comments"}, - //{"PATCH", "/repos/:owner/:repo/issues/comments/:id"}, - //{"DELETE", "/repos/:owner/:repo/issues/comments/:id"}, - {"GET", "/repos/:owner/:repo/issues/:number/events"}, - //{"GET", "/repos/:owner/:repo/issues/events"}, - //{"GET", "/repos/:owner/:repo/issues/events/:id"}, - {"GET", "/repos/:owner/:repo/labels"}, - {"GET", "/repos/:owner/:repo/labels/:name"}, - {"POST", "/repos/:owner/:repo/labels"}, - //{"PATCH", "/repos/:owner/:repo/labels/:name"}, - {"DELETE", "/repos/:owner/:repo/labels/:name"}, - {"GET", "/repos/:owner/:repo/issues/:number/labels"}, - {"POST", "/repos/:owner/:repo/issues/:number/labels"}, - {"DELETE", "/repos/:owner/:repo/issues/:number/labels/:name"}, - {"PUT", "/repos/:owner/:repo/issues/:number/labels"}, - {"DELETE", "/repos/:owner/:repo/issues/:number/labels"}, - {"GET", "/repos/:owner/:repo/milestones/:number/labels"}, - {"GET", "/repos/:owner/:repo/milestones"}, - {"GET", "/repos/:owner/:repo/milestones/:number"}, - {"POST", "/repos/:owner/:repo/milestones"}, - //{"PATCH", "/repos/:owner/:repo/milestones/:number"}, - {"DELETE", "/repos/:owner/:repo/milestones/:number"}, - - // Miscellaneous - {"GET", "/emojis"}, - {"GET", "/gitignore/templates"}, - {"GET", "/gitignore/templates/:name"}, - {"POST", "/markdown"}, - {"POST", "/markdown/raw"}, - {"GET", "/meta"}, - {"GET", "/rate_limit"}, - - // Organizations - {"GET", "/users/:user/orgs"}, - {"GET", "/user/orgs"}, - {"GET", "/orgs/:org"}, - //{"PATCH", "/orgs/:org"}, - {"GET", "/orgs/:org/members"}, - {"GET", "/orgs/:org/members/:user"}, - {"DELETE", "/orgs/:org/members/:user"}, - {"GET", "/orgs/:org/public_members"}, - {"GET", "/orgs/:org/public_members/:user"}, - {"PUT", "/orgs/:org/public_members/:user"}, - {"DELETE", "/orgs/:org/public_members/:user"}, - {"GET", "/orgs/:org/teams"}, - {"GET", "/teams/:id"}, - {"POST", "/orgs/:org/teams"}, - //{"PATCH", "/teams/:id"}, - {"DELETE", "/teams/:id"}, - {"GET", "/teams/:id/members"}, - {"GET", "/teams/:id/members/:user"}, - {"PUT", "/teams/:id/members/:user"}, - {"DELETE", "/teams/:id/members/:user"}, - {"GET", "/teams/:id/repos"}, - {"GET", "/teams/:id/repos/:owner/:repo"}, - {"PUT", "/teams/:id/repos/:owner/:repo"}, - {"DELETE", "/teams/:id/repos/:owner/:repo"}, - {"GET", "/user/teams"}, - - // Pull Requests - {"GET", "/repos/:owner/:repo/pulls"}, - {"GET", "/repos/:owner/:repo/pulls/:number"}, - {"POST", "/repos/:owner/:repo/pulls"}, - //{"PATCH", "/repos/:owner/:repo/pulls/:number"}, - {"GET", "/repos/:owner/:repo/pulls/:number/commits"}, - {"GET", "/repos/:owner/:repo/pulls/:number/files"}, - {"GET", "/repos/:owner/:repo/pulls/:number/merge"}, - {"PUT", "/repos/:owner/:repo/pulls/:number/merge"}, - {"GET", "/repos/:owner/:repo/pulls/:number/comments"}, - //{"GET", "/repos/:owner/:repo/pulls/comments"}, - //{"GET", "/repos/:owner/:repo/pulls/comments/:number"}, - {"PUT", "/repos/:owner/:repo/pulls/:number/comments"}, - //{"PATCH", "/repos/:owner/:repo/pulls/comments/:number"}, - //{"DELETE", "/repos/:owner/:repo/pulls/comments/:number"}, - - // Repositories - {"GET", "/user/repos"}, - {"GET", "/users/:user/repos"}, - {"GET", "/orgs/:org/repos"}, - {"GET", "/repositories"}, - {"POST", "/user/repos"}, - {"POST", "/orgs/:org/repos"}, - {"GET", "/repos/:owner/:repo"}, - //{"PATCH", "/repos/:owner/:repo"}, - {"GET", "/repos/:owner/:repo/contributors"}, - {"GET", "/repos/:owner/:repo/languages"}, - {"GET", "/repos/:owner/:repo/teams"}, - {"GET", "/repos/:owner/:repo/tags"}, - {"GET", "/repos/:owner/:repo/branches"}, - {"GET", "/repos/:owner/:repo/branches/:branch"}, - {"DELETE", "/repos/:owner/:repo"}, - {"GET", "/repos/:owner/:repo/collaborators"}, - {"GET", "/repos/:owner/:repo/collaborators/:user"}, - {"PUT", "/repos/:owner/:repo/collaborators/:user"}, - {"DELETE", "/repos/:owner/:repo/collaborators/:user"}, - {"GET", "/repos/:owner/:repo/comments"}, - {"GET", "/repos/:owner/:repo/commits/:sha/comments"}, - {"POST", "/repos/:owner/:repo/commits/:sha/comments"}, - {"GET", "/repos/:owner/:repo/comments/:id"}, - //{"PATCH", "/repos/:owner/:repo/comments/:id"}, - {"DELETE", "/repos/:owner/:repo/comments/:id"}, - {"GET", "/repos/:owner/:repo/commits"}, - {"GET", "/repos/:owner/:repo/commits/:sha"}, - {"GET", "/repos/:owner/:repo/readme"}, - //{"GET", "/repos/:owner/:repo/contents/*path"}, - //{"PUT", "/repos/:owner/:repo/contents/*path"}, - //{"DELETE", "/repos/:owner/:repo/contents/*path"}, - //{"GET", "/repos/:owner/:repo/:archive_format/:ref"}, - {"GET", "/repos/:owner/:repo/keys"}, - {"GET", "/repos/:owner/:repo/keys/:id"}, - {"POST", "/repos/:owner/:repo/keys"}, - //{"PATCH", "/repos/:owner/:repo/keys/:id"}, - {"DELETE", "/repos/:owner/:repo/keys/:id"}, - {"GET", "/repos/:owner/:repo/downloads"}, - {"GET", "/repos/:owner/:repo/downloads/:id"}, - {"DELETE", "/repos/:owner/:repo/downloads/:id"}, - {"GET", "/repos/:owner/:repo/forks"}, - {"POST", "/repos/:owner/:repo/forks"}, - {"GET", "/repos/:owner/:repo/hooks"}, - {"GET", "/repos/:owner/:repo/hooks/:id"}, - {"POST", "/repos/:owner/:repo/hooks"}, - //{"PATCH", "/repos/:owner/:repo/hooks/:id"}, - {"POST", "/repos/:owner/:repo/hooks/:id/tests"}, - {"DELETE", "/repos/:owner/:repo/hooks/:id"}, - {"POST", "/repos/:owner/:repo/merges"}, - {"GET", "/repos/:owner/:repo/releases"}, - {"GET", "/repos/:owner/:repo/releases/:id"}, - {"POST", "/repos/:owner/:repo/releases"}, - //{"PATCH", "/repos/:owner/:repo/releases/:id"}, - {"DELETE", "/repos/:owner/:repo/releases/:id"}, - {"GET", "/repos/:owner/:repo/releases/:id/assets"}, - {"GET", "/repos/:owner/:repo/stats/contributors"}, - {"GET", "/repos/:owner/:repo/stats/commit_activity"}, - {"GET", "/repos/:owner/:repo/stats/code_frequency"}, - {"GET", "/repos/:owner/:repo/stats/participation"}, - {"GET", "/repos/:owner/:repo/stats/punch_card"}, - {"GET", "/repos/:owner/:repo/statuses/:ref"}, - {"POST", "/repos/:owner/:repo/statuses/:ref"}, - - // Search - {"GET", "/search/repositories"}, - {"GET", "/search/code"}, - {"GET", "/search/issues"}, - {"GET", "/search/users"}, - {"GET", "/legacy/issues/search/:owner/:repository/:state/:keyword"}, - {"GET", "/legacy/repos/search/:keyword"}, - {"GET", "/legacy/user/search/:keyword"}, - {"GET", "/legacy/user/email/:email"}, - - // Users - {"GET", "/users/:user"}, - {"GET", "/user"}, - //{"PATCH", "/user"}, - {"GET", "/users"}, - {"GET", "/user/emails"}, - {"POST", "/user/emails"}, - {"DELETE", "/user/emails"}, - {"GET", "/users/:user/followers"}, - {"GET", "/user/followers"}, - {"GET", "/users/:user/following"}, - {"GET", "/user/following"}, - {"GET", "/user/following/:user"}, - {"GET", "/users/:user/following/:target_user"}, - {"PUT", "/user/following/:user"}, - {"DELETE", "/user/following/:user"}, - {"GET", "/users/:user/keys"}, - {"GET", "/user/keys"}, - {"GET", "/user/keys/:id"}, - {"POST", "/user/keys"}, - //{"PATCH", "/user/keys/:id"}, - {"DELETE", "/user/keys/:id"}, -} - -func githubConfigRouter(router *Engine) { - for _, route := range githubAPI { - router.Handle(route.method, route.path, func(c *Context) { - output := make(map[string]string, len(c.Params)+1) - output["status"] = "good" - for _, param := range c.Params { - output[param.Key] = param.Value - } - c.JSON(200, output) - }) - } -} - -func TestGithubAPI(t *testing.T) { - DefaultWriter = newMockWriter() - router := Default() - githubConfigRouter(router) - - for _, route := range githubAPI { - path, values := exampleFromPath(route.path) - w := performRequest(router, route.method, path) - - // TEST - assert.Contains(t, w.Body.String(), "\"status\":\"good\"") - for _, value := range values { - str := fmt.Sprintf("\"%s\":\"%s\"", value.Key, value.Value) - assert.Contains(t, w.Body.String(), str) - } - } -} - -func exampleFromPath(path string) (string, Params) { - output := new(bytes.Buffer) - params := make(Params, 0, 6) - start := -1 - for i, c := range path { - if c == ':' { - start = i + 1 - } - if start >= 0 { - if c == '/' { - value := fmt.Sprint(rand.Intn(100000)) - params = append(params, Param{ - Key: path[start:i], - Value: value, - }) - output.WriteString(value) - output.WriteRune(c) - start = -1 - } - } else { - output.WriteRune(c) - } - } - if start >= 0 { - value := fmt.Sprint(rand.Intn(100000)) - params = append(params, Param{ - Key: path[start:len(path)], - Value: value, - }) - output.WriteString(value) - } - - return output.String(), params -} - -func BenchmarkGithub(b *testing.B) { - router := New() - githubConfigRouter(router) - runRequest(b, router, "GET", "/legacy/issues/search/:owner/:repository/:state/:keyword") -} - -func BenchmarkParallelGithub(b *testing.B) { - DefaultWriter = newMockWriter() - router := New() - githubConfigRouter(router) - - req, _ := http.NewRequest("POST", "/repos/manucorporat/sse/git/blobs", nil) - - b.RunParallel(func(pb *testing.PB) { - // Each goroutine has its own bytes.Buffer. - for pb.Next() { - w := httptest.NewRecorder() - router.ServeHTTP(w, req) - } - }) -} - -func BenchmarkParallelGithubDefault(b *testing.B) { - DefaultWriter = newMockWriter() - router := Default() - githubConfigRouter(router) - - req, _ := http.NewRequest("POST", "/repos/manucorporat/sse/git/blobs", nil) - - b.RunParallel(func(pb *testing.PB) { - // Each goroutine has its own bytes.Buffer. - for pb.Next() { - w := httptest.NewRecorder() - router.ServeHTTP(w, req) - } - }) -} diff --git a/vendor/github.com/gin-gonic/gin/logger.go b/vendor/github.com/gin-gonic/gin/logger.go index e0f9b3673..c5d4c3e24 100644 --- a/vendor/github.com/gin-gonic/gin/logger.go +++ b/vendor/github.com/gin-gonic/gin/logger.go @@ -46,7 +46,17 @@ func Logger() HandlerFunc { // Instance a Logger middleware with the specified writter buffer. // Example: os.Stdout, a file opened in write mode, a socket... -func LoggerWithWriter(out io.Writer) HandlerFunc { +func LoggerWithWriter(out io.Writer, notlogged ...string) HandlerFunc { + var skip map[string]struct{} + + if length := len(notlogged); length > 0 { + skip = make(map[string]struct{}, length) + + for _, path := range notlogged { + skip[path] = struct{}{} + } + } + return func(c *Context) { // Start timer start := time.Now() @@ -55,26 +65,29 @@ func LoggerWithWriter(out io.Writer) HandlerFunc { // Process request c.Next() - // Stop timer - end := time.Now() - latency := end.Sub(start) + // Log only when path is not being skipped + if _, ok := skip[path]; !ok { + // Stop timer + end := time.Now() + latency := end.Sub(start) - clientIP := c.ClientIP() - method := c.Request.Method - statusCode := c.Writer.Status() - statusColor := colorForStatus(statusCode) - methodColor := colorForMethod(method) - comment := c.Errors.ByType(ErrorTypePrivate).String() + clientIP := c.ClientIP() + method := c.Request.Method + statusCode := c.Writer.Status() + statusColor := colorForStatus(statusCode) + methodColor := colorForMethod(method) + comment := c.Errors.ByType(ErrorTypePrivate).String() - fmt.Fprintf(out, "[GIN] %v |%s %3d %s| %13v | %s |%s %s %-7s %s\n%s", - end.Format("2006/01/02 - 15:04:05"), - statusColor, statusCode, reset, - latency, - clientIP, - methodColor, reset, method, - path, - comment, - ) + fmt.Fprintf(out, "[GIN] %v |%s %3d %s| %13v | %s |%s %s %-7s %s\n%s", + end.Format("2006/01/02 - 15:04:05"), + statusColor, statusCode, reset, + latency, + clientIP, + methodColor, reset, method, + path, + comment, + ) + } } } diff --git a/vendor/github.com/gin-gonic/gin/logger_test.go b/vendor/github.com/gin-gonic/gin/logger_test.go deleted file mode 100644 index 267f9c5b2..000000000 --- a/vendor/github.com/gin-gonic/gin/logger_test.go +++ /dev/null @@ -1,126 +0,0 @@ -// Copyright 2014 Manu Martinez-Almeida. All rights reserved. -// Use of this source code is governed by a MIT style -// license that can be found in the LICENSE file. - -package gin - -import ( - "bytes" - "errors" - "testing" - - "github.com/stretchr/testify/assert" -) - -//TODO -// func (engine *Engine) LoadHTMLGlob(pattern string) { -// func (engine *Engine) LoadHTMLFiles(files ...string) { -// func (engine *Engine) Run(addr string) error { -// func (engine *Engine) RunTLS(addr string, cert string, key string) error { - -func init() { - SetMode(TestMode) -} - -func TestLogger(t *testing.T) { - buffer := new(bytes.Buffer) - router := New() - router.Use(LoggerWithWriter(buffer)) - router.GET("/example", func(c *Context) {}) - router.POST("/example", func(c *Context) {}) - router.PUT("/example", func(c *Context) {}) - router.DELETE("/example", func(c *Context) {}) - router.PATCH("/example", func(c *Context) {}) - router.HEAD("/example", func(c *Context) {}) - router.OPTIONS("/example", func(c *Context) {}) - - performRequest(router, "GET", "/example") - assert.Contains(t, buffer.String(), "200") - assert.Contains(t, buffer.String(), "GET") - assert.Contains(t, buffer.String(), "/example") - - // I wrote these first (extending the above) but then realized they are more - // like integration tests because they test the whole logging process rather - // than individual functions. Im not sure where these should go. - - performRequest(router, "POST", "/example") - assert.Contains(t, buffer.String(), "200") - assert.Contains(t, buffer.String(), "POST") - assert.Contains(t, buffer.String(), "/example") - - performRequest(router, "PUT", "/example") - assert.Contains(t, buffer.String(), "200") - assert.Contains(t, buffer.String(), "PUT") - assert.Contains(t, buffer.String(), "/example") - - performRequest(router, "DELETE", "/example") - assert.Contains(t, buffer.String(), "200") - assert.Contains(t, buffer.String(), "DELETE") - assert.Contains(t, buffer.String(), "/example") - - performRequest(router, "PATCH", "/example") - assert.Contains(t, buffer.String(), "200") - assert.Contains(t, buffer.String(), "PATCH") - assert.Contains(t, buffer.String(), "/example") - - performRequest(router, "HEAD", "/example") - assert.Contains(t, buffer.String(), "200") - assert.Contains(t, buffer.String(), "HEAD") - assert.Contains(t, buffer.String(), "/example") - - performRequest(router, "OPTIONS", "/example") - assert.Contains(t, buffer.String(), "200") - assert.Contains(t, buffer.String(), "OPTIONS") - assert.Contains(t, buffer.String(), "/example") - - performRequest(router, "GET", "/notfound") - assert.Contains(t, buffer.String(), "404") - assert.Contains(t, buffer.String(), "GET") - assert.Contains(t, buffer.String(), "/notfound") - -} - -func TestColorForMethod(t *testing.T) { - assert.Equal(t, colorForMethod("GET"), string([]byte{27, 91, 57, 55, 59, 52, 52, 109}), "get should be blue") - assert.Equal(t, colorForMethod("POST"), string([]byte{27, 91, 57, 55, 59, 52, 54, 109}), "post should be cyan") - assert.Equal(t, colorForMethod("PUT"), string([]byte{27, 91, 57, 55, 59, 52, 51, 109}), "put should be yellow") - assert.Equal(t, colorForMethod("DELETE"), string([]byte{27, 91, 57, 55, 59, 52, 49, 109}), "delete should be red") - assert.Equal(t, colorForMethod("PATCH"), string([]byte{27, 91, 57, 55, 59, 52, 50, 109}), "patch should be green") - assert.Equal(t, colorForMethod("HEAD"), string([]byte{27, 91, 57, 55, 59, 52, 53, 109}), "head should be magenta") - assert.Equal(t, colorForMethod("OPTIONS"), string([]byte{27, 91, 57, 48, 59, 52, 55, 109}), "options should be white") - assert.Equal(t, colorForMethod("TRACE"), string([]byte{27, 91, 48, 109}), "trace is not defined and should be the reset color") -} - -func TestColorForStatus(t *testing.T) { - assert.Equal(t, colorForStatus(200), string([]byte{27, 91, 57, 55, 59, 52, 50, 109}), "2xx should be green") - assert.Equal(t, colorForStatus(301), string([]byte{27, 91, 57, 48, 59, 52, 55, 109}), "3xx should be white") - assert.Equal(t, colorForStatus(404), string([]byte{27, 91, 57, 55, 59, 52, 51, 109}), "4xx should be yellow") - assert.Equal(t, colorForStatus(2), string([]byte{27, 91, 57, 55, 59, 52, 49, 109}), "other things should be red") -} - -func TestErrorLogger(t *testing.T) { - router := New() - router.Use(ErrorLogger()) - router.GET("/error", func(c *Context) { - c.Error(errors.New("this is an error")) - }) - router.GET("/abort", func(c *Context) { - c.AbortWithError(401, errors.New("no authorized")) - }) - router.GET("/print", func(c *Context) { - c.Error(errors.New("this is an error")) - c.String(500, "hola!") - }) - - w := performRequest(router, "GET", "/error") - assert.Equal(t, w.Code, 200) - assert.Equal(t, w.Body.String(), "{\"error\":\"this is an error\"}\n") - - w = performRequest(router, "GET", "/abort") - assert.Equal(t, w.Code, 401) - assert.Equal(t, w.Body.String(), "{\"error\":\"no authorized\"}\n") - - w = performRequest(router, "GET", "/print") - assert.Equal(t, w.Code, 500) - assert.Equal(t, w.Body.String(), "hola!") -} diff --git a/vendor/github.com/gin-gonic/gin/logo.jpg b/vendor/github.com/gin-gonic/gin/logo.jpg new file mode 100644 index 000000000..bb51852e4 Binary files /dev/null and b/vendor/github.com/gin-gonic/gin/logo.jpg differ diff --git a/vendor/github.com/gin-gonic/gin/middleware_test.go b/vendor/github.com/gin-gonic/gin/middleware_test.go deleted file mode 100644 index 61d27c9e6..000000000 --- a/vendor/github.com/gin-gonic/gin/middleware_test.go +++ /dev/null @@ -1,255 +0,0 @@ -// Copyright 2014 Manu Martinez-Almeida. All rights reserved. -// Use of this source code is governed by a MIT style -// license that can be found in the LICENSE file. - -package gin - -import ( - "errors" - - "testing" - - "github.com/manucorporat/sse" - "github.com/stretchr/testify/assert" -) - -func TestMiddlewareGeneralCase(t *testing.T) { - signature := "" - router := New() - router.Use(func(c *Context) { - signature += "A" - c.Next() - signature += "B" - }) - router.Use(func(c *Context) { - signature += "C" - }) - router.GET("/", func(c *Context) { - signature += "D" - }) - router.NoRoute(func(c *Context) { - signature += " X " - }) - router.NoMethod(func(c *Context) { - signature += " XX " - }) - // RUN - w := performRequest(router, "GET", "/") - - // TEST - assert.Equal(t, w.Code, 200) - assert.Equal(t, signature, "ACDB") -} - -func TestMiddlewareNoRoute(t *testing.T) { - signature := "" - router := New() - router.Use(func(c *Context) { - signature += "A" - c.Next() - signature += "B" - }) - router.Use(func(c *Context) { - signature += "C" - c.Next() - c.Next() - c.Next() - c.Next() - signature += "D" - }) - router.NoRoute(func(c *Context) { - signature += "E" - c.Next() - signature += "F" - }, func(c *Context) { - signature += "G" - c.Next() - signature += "H" - }) - router.NoMethod(func(c *Context) { - signature += " X " - }) - // RUN - w := performRequest(router, "GET", "/") - - // TEST - assert.Equal(t, w.Code, 404) - assert.Equal(t, signature, "ACEGHFDB") -} - -func TestMiddlewareNoMethodEnabled(t *testing.T) { - signature := "" - router := New() - router.HandleMethodNotAllowed = true - router.Use(func(c *Context) { - signature += "A" - c.Next() - signature += "B" - }) - router.Use(func(c *Context) { - signature += "C" - c.Next() - signature += "D" - }) - router.NoMethod(func(c *Context) { - signature += "E" - c.Next() - signature += "F" - }, func(c *Context) { - signature += "G" - c.Next() - signature += "H" - }) - router.NoRoute(func(c *Context) { - signature += " X " - }) - router.POST("/", func(c *Context) { - signature += " XX " - }) - // RUN - w := performRequest(router, "GET", "/") - - // TEST - assert.Equal(t, w.Code, 405) - assert.Equal(t, signature, "ACEGHFDB") -} - -func TestMiddlewareNoMethodDisabled(t *testing.T) { - signature := "" - router := New() - router.HandleMethodNotAllowed = false - router.Use(func(c *Context) { - signature += "A" - c.Next() - signature += "B" - }) - router.Use(func(c *Context) { - signature += "C" - c.Next() - signature += "D" - }) - router.NoMethod(func(c *Context) { - signature += "E" - c.Next() - signature += "F" - }, func(c *Context) { - signature += "G" - c.Next() - signature += "H" - }) - router.NoRoute(func(c *Context) { - signature += " X " - }) - router.POST("/", func(c *Context) { - signature += " XX " - }) - // RUN - w := performRequest(router, "GET", "/") - - // TEST - assert.Equal(t, w.Code, 404) - assert.Equal(t, signature, "AC X DB") -} - -func TestMiddlewareAbort(t *testing.T) { - signature := "" - router := New() - router.Use(func(c *Context) { - signature += "A" - }) - router.Use(func(c *Context) { - signature += "C" - c.AbortWithStatus(401) - c.Next() - signature += "D" - }) - router.GET("/", func(c *Context) { - signature += " X " - c.Next() - signature += " XX " - }) - - // RUN - w := performRequest(router, "GET", "/") - - // TEST - assert.Equal(t, w.Code, 401) - assert.Equal(t, signature, "ACD") -} - -func TestMiddlewareAbortHandlersChainAndNext(t *testing.T) { - signature := "" - router := New() - router.Use(func(c *Context) { - signature += "A" - c.Next() - c.AbortWithStatus(410) - signature += "B" - - }) - router.GET("/", func(c *Context) { - signature += "C" - c.Next() - }) - // RUN - w := performRequest(router, "GET", "/") - - // TEST - assert.Equal(t, w.Code, 410) - assert.Equal(t, signature, "ACB") -} - -// TestFailHandlersChain - ensure that Fail interrupt used middleware in fifo order as -// as well as Abort -func TestMiddlewareFailHandlersChain(t *testing.T) { - // SETUP - signature := "" - router := New() - router.Use(func(context *Context) { - signature += "A" - context.AbortWithError(500, errors.New("foo")) - }) - router.Use(func(context *Context) { - signature += "B" - context.Next() - signature += "C" - }) - // RUN - w := performRequest(router, "GET", "/") - - // TEST - assert.Equal(t, w.Code, 500) - assert.Equal(t, signature, "A") -} - -func TestMiddlewareWrite(t *testing.T) { - router := New() - router.Use(func(c *Context) { - c.String(400, "hola\n") - }) - router.Use(func(c *Context) { - c.XML(400, H{"foo": "bar"}) - }) - router.Use(func(c *Context) { - c.JSON(400, H{"foo": "bar"}) - }) - router.GET("/", func(c *Context) { - c.JSON(400, H{"foo": "bar"}) - }, func(c *Context) { - c.Render(400, sse.Event{ - Event: "test", - Data: "message", - }) - }) - - w := performRequest(router, "GET", "/") - - assert.Equal(t, w.Code, 400) - assert.Equal(t, w.Body.String(), `hola -bar{"foo":"bar"} -{"foo":"bar"} -event:test -data:message - -`) -} diff --git a/vendor/github.com/gin-gonic/gin/mode.go b/vendor/github.com/gin-gonic/gin/mode.go index 15efaeb87..bf9e995bf 100644 --- a/vendor/github.com/gin-gonic/gin/mode.go +++ b/vendor/github.com/gin-gonic/gin/mode.go @@ -9,7 +9,6 @@ import ( "os" "github.com/gin-gonic/gin/binding" - "github.com/mattn/go-colorable" ) const ENV_GIN_MODE = "GIN_MODE" @@ -25,7 +24,16 @@ const ( testCode = iota ) -var DefaultWriter io.Writer = colorable.NewColorableStdout() +// DefaultWriter is the default io.Writer used the Gin for debug output and +// middleware output like Logger() or Recovery(). +// Note that both Logger and Recovery provides custom ways to configure their +// output io.Writer. +// To support coloring in Windows use: +// import "github.com/mattn/go-colorable" +// gin.DefaultWriter = colorable.NewColorableStdout() +var DefaultWriter io.Writer = os.Stdout +var DefaultErrorWriter io.Writer = os.Stderr + var ginMode int = debugCode var modeName string = DebugMode diff --git a/vendor/github.com/gin-gonic/gin/mode_test.go b/vendor/github.com/gin-gonic/gin/mode_test.go deleted file mode 100644 index 2a23d85e9..000000000 --- a/vendor/github.com/gin-gonic/gin/mode_test.go +++ /dev/null @@ -1,31 +0,0 @@ -// Copyright 2014 Manu Martinez-Almeida. All rights reserved. -// Use of this source code is governed by a MIT style -// license that can be found in the LICENSE file. - -package gin - -import ( - "testing" - - "github.com/stretchr/testify/assert" -) - -func init() { - SetMode(TestMode) -} - -func TestSetMode(t *testing.T) { - SetMode(DebugMode) - assert.Equal(t, ginMode, debugCode) - assert.Equal(t, Mode(), DebugMode) - - SetMode(ReleaseMode) - assert.Equal(t, ginMode, releaseCode) - assert.Equal(t, Mode(), ReleaseMode) - - SetMode(TestMode) - assert.Equal(t, ginMode, testCode) - assert.Equal(t, Mode(), TestMode) - - assert.Panics(t, func() { SetMode("unknown") }) -} diff --git a/vendor/github.com/gin-gonic/gin/path_test.go b/vendor/github.com/gin-gonic/gin/path_test.go deleted file mode 100644 index 01cb758a4..000000000 --- a/vendor/github.com/gin-gonic/gin/path_test.go +++ /dev/null @@ -1,88 +0,0 @@ -// Copyright 2013 Julien Schmidt. All rights reserved. -// Based on the path package, Copyright 2009 The Go Authors. -// Use of this source code is governed by a BSD-style license that can be found -// in the LICENSE file. - -package gin - -import ( - "runtime" - "testing" - - "github.com/stretchr/testify/assert" -) - -var cleanTests = []struct { - path, result string -}{ - // Already clean - {"/", "/"}, - {"/abc", "/abc"}, - {"/a/b/c", "/a/b/c"}, - {"/abc/", "/abc/"}, - {"/a/b/c/", "/a/b/c/"}, - - // missing root - {"", "/"}, - {"abc", "/abc"}, - {"abc/def", "/abc/def"}, - {"a/b/c", "/a/b/c"}, - - // Remove doubled slash - {"//", "/"}, - {"/abc//", "/abc/"}, - {"/abc/def//", "/abc/def/"}, - {"/a/b/c//", "/a/b/c/"}, - {"/abc//def//ghi", "/abc/def/ghi"}, - {"//abc", "/abc"}, - {"///abc", "/abc"}, - {"//abc//", "/abc/"}, - - // Remove . elements - {".", "/"}, - {"./", "/"}, - {"/abc/./def", "/abc/def"}, - {"/./abc/def", "/abc/def"}, - {"/abc/.", "/abc/"}, - - // Remove .. elements - {"..", "/"}, - {"../", "/"}, - {"../../", "/"}, - {"../..", "/"}, - {"../../abc", "/abc"}, - {"/abc/def/ghi/../jkl", "/abc/def/jkl"}, - {"/abc/def/../ghi/../jkl", "/abc/jkl"}, - {"/abc/def/..", "/abc"}, - {"/abc/def/../..", "/"}, - {"/abc/def/../../..", "/"}, - {"/abc/def/../../..", "/"}, - {"/abc/def/../../../ghi/jkl/../../../mno", "/mno"}, - - // Combinations - {"abc/./../def", "/def"}, - {"abc//./../def", "/def"}, - {"abc/../../././../def", "/def"}, -} - -func TestPathClean(t *testing.T) { - for _, test := range cleanTests { - assert.Equal(t, cleanPath(test.path), test.result) - assert.Equal(t, cleanPath(test.result), test.result) - } -} - -func TestPathCleanMallocs(t *testing.T) { - if testing.Short() { - t.Skip("skipping malloc count in short mode") - } - if runtime.GOMAXPROCS(0) > 1 { - t.Log("skipping AllocsPerRun checks; GOMAXPROCS>1") - return - } - - for _, test := range cleanTests { - allocs := testing.AllocsPerRun(100, func() { cleanPath(test.result) }) - assert.EqualValues(t, allocs, 0) - } -} diff --git a/vendor/github.com/gin-gonic/gin/recovery.go b/vendor/github.com/gin-gonic/gin/recovery.go index e296e3390..c502f3553 100644 --- a/vendor/github.com/gin-gonic/gin/recovery.go +++ b/vendor/github.com/gin-gonic/gin/recovery.go @@ -10,6 +10,7 @@ import ( "io" "io/ioutil" "log" + "net/http/httputil" "runtime" ) @@ -22,20 +23,21 @@ var ( // Recovery returns a middleware that recovers from any panics and writes a 500 if there was one. func Recovery() HandlerFunc { - return RecoveryWithWriter(DefaultWriter) + return RecoveryWithWriter(DefaultErrorWriter) } func RecoveryWithWriter(out io.Writer) HandlerFunc { var logger *log.Logger if out != nil { - logger = log.New(out, "", log.LstdFlags) + logger = log.New(out, "\n\n\x1b[31m", log.LstdFlags) } return func(c *Context) { defer func() { if err := recover(); err != nil { if logger != nil { stack := stack(3) - logger.Printf("Panic recovery -> %s\n%s\n", err, stack) + httprequest, _ := httputil.DumpRequest(c.Request, false) + logger.Printf("[Recovery] panic recovered:\n%s\n%s\n%s%s", string(httprequest), err, stack, reset) } c.AbortWithStatus(500) } diff --git a/vendor/github.com/gin-gonic/gin/recovery_test.go b/vendor/github.com/gin-gonic/gin/recovery_test.go deleted file mode 100644 index 39e71e816..000000000 --- a/vendor/github.com/gin-gonic/gin/recovery_test.go +++ /dev/null @@ -1,42 +0,0 @@ -// Copyright 2014 Manu Martinez-Almeida. All rights reserved. -// Use of this source code is governed by a MIT style -// license that can be found in the LICENSE file. - -package gin - -import ( - "bytes" - "testing" - - "github.com/stretchr/testify/assert" -) - -// TestPanicInHandler assert that panic has been recovered. -func TestPanicInHandler(t *testing.T) { - buffer := new(bytes.Buffer) - router := New() - router.Use(RecoveryWithWriter(buffer)) - router.GET("/recovery", func(_ *Context) { - panic("Oupps, Houston, we have a problem") - }) - // RUN - w := performRequest(router, "GET", "/recovery") - // TEST - assert.Equal(t, w.Code, 500) - assert.Contains(t, buffer.String(), "Panic recovery -> Oupps, Houston, we have a problem") - assert.Contains(t, buffer.String(), "TestPanicInHandler") -} - -// TestPanicWithAbort assert that panic has been recovered even if context.Abort was used. -func TestPanicWithAbort(t *testing.T) { - router := New() - router.Use(RecoveryWithWriter(nil)) - router.GET("/recovery", func(c *Context) { - c.AbortWithStatus(400) - panic("Oupps, Houston, we have a problem") - }) - // RUN - w := performRequest(router, "GET", "/recovery") - // TEST - assert.Equal(t, w.Code, 500) // NOT SURE -} diff --git a/vendor/github.com/gin-gonic/gin/render/redirect.go b/vendor/github.com/gin-gonic/gin/render/redirect.go index d64e4d75e..bd48d7d83 100644 --- a/vendor/github.com/gin-gonic/gin/render/redirect.go +++ b/vendor/github.com/gin-gonic/gin/render/redirect.go @@ -16,7 +16,7 @@ type Redirect struct { } func (r Redirect) Render(w http.ResponseWriter) error { - if r.Code < 300 || r.Code > 308 { + if (r.Code < 300 || r.Code > 308) && r.Code != 201 { panic(fmt.Sprintf("Cannot redirect with status code %d", r.Code)) } http.Redirect(w, r.Request, r.Location, r.Code) diff --git a/vendor/github.com/gin-gonic/gin/render/render_test.go b/vendor/github.com/gin-gonic/gin/render/render_test.go deleted file mode 100644 index 7a6ffb7d5..000000000 --- a/vendor/github.com/gin-gonic/gin/render/render_test.go +++ /dev/null @@ -1,130 +0,0 @@ -// Copyright 2014 Manu Martinez-Almeida. All rights reserved. -// Use of this source code is governed by a MIT style -// license that can be found in the LICENSE file. - -package render - -import ( - "encoding/xml" - "html/template" - "net/http/httptest" - "testing" - - "github.com/stretchr/testify/assert" -) - -// TODO unit tests -// test errors - -func TestRenderJSON(t *testing.T) { - w := httptest.NewRecorder() - data := map[string]interface{}{ - "foo": "bar", - } - - err := (JSON{data}).Render(w) - - assert.NoError(t, err) - assert.Equal(t, w.Body.String(), "{\"foo\":\"bar\"}\n") - assert.Equal(t, w.Header().Get("Content-Type"), "application/json; charset=utf-8") -} - -func TestRenderIndentedJSON(t *testing.T) { - w := httptest.NewRecorder() - data := map[string]interface{}{ - "foo": "bar", - "bar": "foo", - } - - err := (IndentedJSON{data}).Render(w) - - assert.NoError(t, err) - assert.Equal(t, w.Body.String(), "{\n \"bar\": \"foo\",\n \"foo\": \"bar\"\n}") - assert.Equal(t, w.Header().Get("Content-Type"), "application/json; charset=utf-8") -} - -type xmlmap map[string]interface{} - -// Allows type H to be used with xml.Marshal -func (h xmlmap) MarshalXML(e *xml.Encoder, start xml.StartElement) error { - start.Name = xml.Name{ - Space: "", - Local: "map", - } - if err := e.EncodeToken(start); err != nil { - return err - } - for key, value := range h { - elem := xml.StartElement{ - Name: xml.Name{Space: "", Local: key}, - Attr: []xml.Attr{}, - } - if err := e.EncodeElement(value, elem); err != nil { - return err - } - } - if err := e.EncodeToken(xml.EndElement{Name: start.Name}); err != nil { - return err - } - return nil -} - -func TestRenderXML(t *testing.T) { - w := httptest.NewRecorder() - data := xmlmap{ - "foo": "bar", - } - - err := (XML{data}).Render(w) - - assert.NoError(t, err) - assert.Equal(t, w.Body.String(), "bar") - assert.Equal(t, w.Header().Get("Content-Type"), "application/xml; charset=utf-8") -} - -func TestRenderRedirect(t *testing.T) { - // TODO -} - -func TestRenderData(t *testing.T) { - w := httptest.NewRecorder() - data := []byte("#!PNG some raw data") - - err := (Data{ - ContentType: "image/png", - Data: data, - }).Render(w) - - assert.NoError(t, err) - assert.Equal(t, w.Body.String(), "#!PNG some raw data") - assert.Equal(t, w.Header().Get("Content-Type"), "image/png") -} - -func TestRenderString(t *testing.T) { - w := httptest.NewRecorder() - - err := (String{ - Format: "hola %s %d", - Data: []interface{}{"manu", 2}, - }).Render(w) - - assert.NoError(t, err) - assert.Equal(t, w.Body.String(), "hola manu 2") - assert.Equal(t, w.Header().Get("Content-Type"), "text/plain; charset=utf-8") -} - -func TestRenderHTMLTemplate(t *testing.T) { - w := httptest.NewRecorder() - templ := template.Must(template.New("t").Parse(`Hello {{.name}}`)) - - htmlRender := HTMLProduction{Template: templ} - instance := htmlRender.Instance("t", map[string]interface{}{ - "name": "alexandernyquist", - }) - - err := instance.Render(w) - - assert.NoError(t, err) - assert.Equal(t, w.Body.String(), "Hello alexandernyquist") - assert.Equal(t, w.Header().Get("Content-Type"), "text/html; charset=utf-8") -} diff --git a/vendor/github.com/gin-gonic/gin/response_writer_test.go b/vendor/github.com/gin-gonic/gin/response_writer_test.go deleted file mode 100644 index 7306d1925..000000000 --- a/vendor/github.com/gin-gonic/gin/response_writer_test.go +++ /dev/null @@ -1,115 +0,0 @@ -// Copyright 2014 Manu Martinez-Almeida. All rights reserved. -// Use of this source code is governed by a MIT style -// license that can be found in the LICENSE file. - -package gin - -import ( - "net/http" - "net/http/httptest" - "testing" - - "github.com/stretchr/testify/assert" -) - -// TODO -// func (w *responseWriter) Hijack() (net.Conn, *bufio.ReadWriter, error) { -// func (w *responseWriter) CloseNotify() <-chan bool { -// func (w *responseWriter) Flush() { - -var _ ResponseWriter = &responseWriter{} -var _ http.ResponseWriter = &responseWriter{} -var _ http.ResponseWriter = ResponseWriter(&responseWriter{}) -var _ http.Hijacker = ResponseWriter(&responseWriter{}) -var _ http.Flusher = ResponseWriter(&responseWriter{}) -var _ http.CloseNotifier = ResponseWriter(&responseWriter{}) - -func init() { - SetMode(TestMode) -} - -func TestResponseWriterReset(t *testing.T) { - testWritter := httptest.NewRecorder() - writer := &responseWriter{} - var w ResponseWriter = writer - - writer.reset(testWritter) - assert.Equal(t, writer.size, -1) - assert.Equal(t, writer.status, 200) - assert.Equal(t, writer.ResponseWriter, testWritter) - assert.Equal(t, w.Size(), -1) - assert.Equal(t, w.Status(), 200) - assert.False(t, w.Written()) -} - -func TestResponseWriterWriteHeader(t *testing.T) { - testWritter := httptest.NewRecorder() - writer := &responseWriter{} - writer.reset(testWritter) - w := ResponseWriter(writer) - - w.WriteHeader(300) - assert.False(t, w.Written()) - assert.Equal(t, w.Status(), 300) - assert.NotEqual(t, testWritter.Code, 300) - - w.WriteHeader(-1) - assert.Equal(t, w.Status(), 300) -} - -func TestResponseWriterWriteHeadersNow(t *testing.T) { - testWritter := httptest.NewRecorder() - writer := &responseWriter{} - writer.reset(testWritter) - w := ResponseWriter(writer) - - w.WriteHeader(300) - w.WriteHeaderNow() - - assert.True(t, w.Written()) - assert.Equal(t, w.Size(), 0) - assert.Equal(t, testWritter.Code, 300) - - writer.size = 10 - w.WriteHeaderNow() - assert.Equal(t, w.Size(), 10) -} - -func TestResponseWriterWrite(t *testing.T) { - testWritter := httptest.NewRecorder() - writer := &responseWriter{} - writer.reset(testWritter) - w := ResponseWriter(writer) - - n, err := w.Write([]byte("hola")) - assert.Equal(t, n, 4) - assert.Equal(t, w.Size(), 4) - assert.Equal(t, w.Status(), 200) - assert.Equal(t, testWritter.Code, 200) - assert.Equal(t, testWritter.Body.String(), "hola") - assert.NoError(t, err) - - n, err = w.Write([]byte(" adios")) - assert.Equal(t, n, 6) - assert.Equal(t, w.Size(), 10) - assert.Equal(t, testWritter.Body.String(), "hola adios") - assert.NoError(t, err) -} - -func TestResponseWriterHijack(t *testing.T) { - testWritter := httptest.NewRecorder() - writer := &responseWriter{} - writer.reset(testWritter) - w := ResponseWriter(writer) - - assert.Panics(t, func() { - w.Hijack() - }) - assert.True(t, w.Written()) - - assert.Panics(t, func() { - w.CloseNotify() - }) - - w.Flush() -} diff --git a/vendor/github.com/gin-gonic/gin/routergroup_test.go b/vendor/github.com/gin-gonic/gin/routergroup_test.go deleted file mode 100644 index b0589b52e..000000000 --- a/vendor/github.com/gin-gonic/gin/routergroup_test.go +++ /dev/null @@ -1,177 +0,0 @@ -// Copyright 2014 Manu Martinez-Almeida. All rights reserved. -// Use of this source code is governed by a MIT style -// license that can be found in the LICENSE file. - -package gin - -import ( - "testing" - - "github.com/stretchr/testify/assert" -) - -func init() { - SetMode(TestMode) -} - -func TestRouterGroupBasic(t *testing.T) { - router := New() - group := router.Group("/hola", func(c *Context) {}) - group.Use(func(c *Context) {}) - - assert.Len(t, group.Handlers, 2) - assert.Equal(t, group.BasePath(), "/hola") - assert.Equal(t, group.engine, router) - - group2 := group.Group("manu") - group2.Use(func(c *Context) {}, func(c *Context) {}) - - assert.Len(t, group2.Handlers, 4) - assert.Equal(t, group2.BasePath(), "/hola/manu") - assert.Equal(t, group2.engine, router) -} - -func TestRouterGroupBasicHandle(t *testing.T) { - performRequestInGroup(t, "GET") - performRequestInGroup(t, "POST") - performRequestInGroup(t, "PUT") - performRequestInGroup(t, "PATCH") - performRequestInGroup(t, "DELETE") - performRequestInGroup(t, "HEAD") - performRequestInGroup(t, "OPTIONS") -} - -func performRequestInGroup(t *testing.T, method string) { - router := New() - v1 := router.Group("v1", func(c *Context) {}) - assert.Equal(t, v1.BasePath(), "/v1") - - login := v1.Group("/login/", func(c *Context) {}, func(c *Context) {}) - assert.Equal(t, login.BasePath(), "/v1/login/") - - handler := func(c *Context) { - c.String(400, "the method was %s and index %d", c.Request.Method, c.index) - } - - switch method { - case "GET": - v1.GET("/test", handler) - login.GET("/test", handler) - case "POST": - v1.POST("/test", handler) - login.POST("/test", handler) - case "PUT": - v1.PUT("/test", handler) - login.PUT("/test", handler) - case "PATCH": - v1.PATCH("/test", handler) - login.PATCH("/test", handler) - case "DELETE": - v1.DELETE("/test", handler) - login.DELETE("/test", handler) - case "HEAD": - v1.HEAD("/test", handler) - login.HEAD("/test", handler) - case "OPTIONS": - v1.OPTIONS("/test", handler) - login.OPTIONS("/test", handler) - default: - panic("unknown method") - } - - w := performRequest(router, method, "/v1/login/test") - assert.Equal(t, w.Code, 400) - assert.Equal(t, w.Body.String(), "the method was "+method+" and index 3") - - w = performRequest(router, method, "/v1/test") - assert.Equal(t, w.Code, 400) - assert.Equal(t, w.Body.String(), "the method was "+method+" and index 1") -} - -func TestRouterGroupInvalidStatic(t *testing.T) { - router := New() - assert.Panics(t, func() { - router.Static("/path/:param", "/") - }) - - assert.Panics(t, func() { - router.Static("/path/*param", "/") - }) -} - -func TestRouterGroupInvalidStaticFile(t *testing.T) { - router := New() - assert.Panics(t, func() { - router.StaticFile("/path/:param", "favicon.ico") - }) - - assert.Panics(t, func() { - router.StaticFile("/path/*param", "favicon.ico") - }) -} - -func TestRouterGroupTooManyHandlers(t *testing.T) { - router := New() - handlers1 := make([]HandlerFunc, 40) - router.Use(handlers1...) - - handlers2 := make([]HandlerFunc, 26) - assert.Panics(t, func() { - router.Use(handlers2...) - }) - assert.Panics(t, func() { - router.GET("/", handlers2...) - }) -} - -func TestRouterGroupBadMethod(t *testing.T) { - router := New() - assert.Panics(t, func() { - router.Handle("get", "/") - }) - assert.Panics(t, func() { - router.Handle(" GET", "/") - }) - assert.Panics(t, func() { - router.Handle("GET ", "/") - }) - assert.Panics(t, func() { - router.Handle("", "/") - }) - assert.Panics(t, func() { - router.Handle("PO ST", "/") - }) - assert.Panics(t, func() { - router.Handle("1GET", "/") - }) - assert.Panics(t, func() { - router.Handle("PATCh", "/") - }) -} - -func TestRouterGroupPipeline(t *testing.T) { - router := New() - testRoutesInterface(t, router) - - v1 := router.Group("/v1") - testRoutesInterface(t, v1) -} - -func testRoutesInterface(t *testing.T, r IRoutes) { - handler := func(c *Context) {} - assert.Equal(t, r, r.Use(handler)) - - assert.Equal(t, r, r.Handle("GET", "/handler", handler)) - assert.Equal(t, r, r.Any("/any", handler)) - assert.Equal(t, r, r.GET("/", handler)) - assert.Equal(t, r, r.POST("/", handler)) - assert.Equal(t, r, r.DELETE("/", handler)) - assert.Equal(t, r, r.PATCH("/", handler)) - assert.Equal(t, r, r.PUT("/", handler)) - assert.Equal(t, r, r.OPTIONS("/", handler)) - assert.Equal(t, r, r.HEAD("/", handler)) - - assert.Equal(t, r, r.StaticFile("/file", ".")) - assert.Equal(t, r, r.Static("/static", ".")) - assert.Equal(t, r, r.StaticFS("/static2", Dir(".", false))) -} diff --git a/vendor/github.com/gin-gonic/gin/routes_test.go b/vendor/github.com/gin-gonic/gin/routes_test.go deleted file mode 100644 index 32f009835..000000000 --- a/vendor/github.com/gin-gonic/gin/routes_test.go +++ /dev/null @@ -1,402 +0,0 @@ -// Copyright 2014 Manu Martinez-Almeida. All rights reserved. -// Use of this source code is governed by a MIT style -// license that can be found in the LICENSE file. - -package gin - -import ( - "fmt" - "io/ioutil" - "net/http" - "net/http/httptest" - "os" - "path/filepath" - "testing" - - "github.com/stretchr/testify/assert" -) - -func performRequest(r http.Handler, method, path string) *httptest.ResponseRecorder { - req, _ := http.NewRequest(method, path, nil) - w := httptest.NewRecorder() - r.ServeHTTP(w, req) - return w -} - -func testRouteOK(method string, t *testing.T) { - passed := false - passedAny := false - r := New() - r.Any("/test2", func(c *Context) { - passedAny = true - }) - r.Handle(method, "/test", func(c *Context) { - passed = true - }) - - w := performRequest(r, method, "/test") - assert.True(t, passed) - assert.Equal(t, w.Code, http.StatusOK) - - performRequest(r, method, "/test2") - assert.True(t, passedAny) -} - -// TestSingleRouteOK tests that POST route is correctly invoked. -func testRouteNotOK(method string, t *testing.T) { - passed := false - router := New() - router.Handle(method, "/test_2", func(c *Context) { - passed = true - }) - - w := performRequest(router, method, "/test") - - assert.False(t, passed) - assert.Equal(t, w.Code, http.StatusNotFound) -} - -// TestSingleRouteOK tests that POST route is correctly invoked. -func testRouteNotOK2(method string, t *testing.T) { - passed := false - router := New() - router.HandleMethodNotAllowed = true - var methodRoute string - if method == "POST" { - methodRoute = "GET" - } else { - methodRoute = "POST" - } - router.Handle(methodRoute, "/test", func(c *Context) { - passed = true - }) - - w := performRequest(router, method, "/test") - - assert.False(t, passed) - assert.Equal(t, w.Code, http.StatusMethodNotAllowed) -} - -func TestRouterMethod(t *testing.T) { - router := New() - router.PUT("/hey2", func(c *Context) { - c.String(200, "sup2") - }) - - router.PUT("/hey", func(c *Context) { - c.String(200, "called") - }) - - router.PUT("/hey3", func(c *Context) { - c.String(200, "sup3") - }) - - w := performRequest(router, "PUT", "/hey") - - assert.Equal(t, w.Code, 200) - assert.Equal(t, w.Body.String(), "called") -} - -func TestRouterGroupRouteOK(t *testing.T) { - testRouteOK("GET", t) - testRouteOK("POST", t) - testRouteOK("PUT", t) - testRouteOK("PATCH", t) - testRouteOK("HEAD", t) - testRouteOK("OPTIONS", t) - testRouteOK("DELETE", t) - testRouteOK("CONNECT", t) - testRouteOK("TRACE", t) -} - -func TestRouteNotOK(t *testing.T) { - testRouteNotOK("GET", t) - testRouteNotOK("POST", t) - testRouteNotOK("PUT", t) - testRouteNotOK("PATCH", t) - testRouteNotOK("HEAD", t) - testRouteNotOK("OPTIONS", t) - testRouteNotOK("DELETE", t) - testRouteNotOK("CONNECT", t) - testRouteNotOK("TRACE", t) -} - -func TestRouteNotOK2(t *testing.T) { - testRouteNotOK2("GET", t) - testRouteNotOK2("POST", t) - testRouteNotOK2("PUT", t) - testRouteNotOK2("PATCH", t) - testRouteNotOK2("HEAD", t) - testRouteNotOK2("OPTIONS", t) - testRouteNotOK2("DELETE", t) - testRouteNotOK2("CONNECT", t) - testRouteNotOK2("TRACE", t) -} - -func TestRouteRedirectTrailingSlash(t *testing.T) { - router := New() - router.RedirectFixedPath = false - router.RedirectTrailingSlash = true - router.GET("/path", func(c *Context) {}) - router.GET("/path2/", func(c *Context) {}) - router.POST("/path3", func(c *Context) {}) - router.PUT("/path4/", func(c *Context) {}) - - w := performRequest(router, "GET", "/path/") - assert.Equal(t, w.Header().Get("Location"), "/path") - assert.Equal(t, w.Code, 301) - - w = performRequest(router, "GET", "/path2") - assert.Equal(t, w.Header().Get("Location"), "/path2/") - assert.Equal(t, w.Code, 301) - - w = performRequest(router, "POST", "/path3/") - assert.Equal(t, w.Header().Get("Location"), "/path3") - assert.Equal(t, w.Code, 307) - - w = performRequest(router, "PUT", "/path4") - assert.Equal(t, w.Header().Get("Location"), "/path4/") - assert.Equal(t, w.Code, 307) - - w = performRequest(router, "GET", "/path") - assert.Equal(t, w.Code, 200) - - w = performRequest(router, "GET", "/path2/") - assert.Equal(t, w.Code, 200) - - w = performRequest(router, "POST", "/path3") - assert.Equal(t, w.Code, 200) - - w = performRequest(router, "PUT", "/path4/") - assert.Equal(t, w.Code, 200) - - router.RedirectTrailingSlash = false - - w = performRequest(router, "GET", "/path/") - assert.Equal(t, w.Code, 404) - w = performRequest(router, "GET", "/path2") - assert.Equal(t, w.Code, 404) - w = performRequest(router, "POST", "/path3/") - assert.Equal(t, w.Code, 404) - w = performRequest(router, "PUT", "/path4") - assert.Equal(t, w.Code, 404) -} - -func TestRouteRedirectFixedPath(t *testing.T) { - router := New() - router.RedirectFixedPath = true - router.RedirectTrailingSlash = false - - router.GET("/path", func(c *Context) {}) - router.GET("/Path2", func(c *Context) {}) - router.POST("/PATH3", func(c *Context) {}) - router.POST("/Path4/", func(c *Context) {}) - - w := performRequest(router, "GET", "/PATH") - assert.Equal(t, w.Header().Get("Location"), "/path") - assert.Equal(t, w.Code, 301) - - w = performRequest(router, "GET", "/path2") - assert.Equal(t, w.Header().Get("Location"), "/Path2") - assert.Equal(t, w.Code, 301) - - w = performRequest(router, "POST", "/path3") - assert.Equal(t, w.Header().Get("Location"), "/PATH3") - assert.Equal(t, w.Code, 307) - - w = performRequest(router, "POST", "/path4") - assert.Equal(t, w.Header().Get("Location"), "/Path4/") - assert.Equal(t, w.Code, 307) -} - -// TestContextParamsGet tests that a parameter can be parsed from the URL. -func TestRouteParamsByName(t *testing.T) { - name := "" - lastName := "" - wild := "" - router := New() - router.GET("/test/:name/:last_name/*wild", func(c *Context) { - name = c.Params.ByName("name") - lastName = c.Params.ByName("last_name") - var ok bool - wild, ok = c.Params.Get("wild") - - assert.True(t, ok) - assert.Equal(t, name, c.Param("name")) - assert.Equal(t, name, c.Param("name")) - assert.Equal(t, lastName, c.Param("last_name")) - - assert.Empty(t, c.Param("wtf")) - assert.Empty(t, c.Params.ByName("wtf")) - - wtf, ok := c.Params.Get("wtf") - assert.Empty(t, wtf) - assert.False(t, ok) - }) - - w := performRequest(router, "GET", "/test/john/smith/is/super/great") - - assert.Equal(t, w.Code, 200) - assert.Equal(t, name, "john") - assert.Equal(t, lastName, "smith") - assert.Equal(t, wild, "/is/super/great") -} - -// TestHandleStaticFile - ensure the static file handles properly -func TestRouteStaticFile(t *testing.T) { - // SETUP file - testRoot, _ := os.Getwd() - f, err := ioutil.TempFile(testRoot, "") - if err != nil { - t.Error(err) - } - defer os.Remove(f.Name()) - f.WriteString("Gin Web Framework") - f.Close() - - dir, filename := filepath.Split(f.Name()) - - // SETUP gin - router := New() - router.Static("/using_static", dir) - router.StaticFile("/result", f.Name()) - - w := performRequest(router, "GET", "/using_static/"+filename) - w2 := performRequest(router, "GET", "/result") - - assert.Equal(t, w, w2) - assert.Equal(t, w.Code, 200) - assert.Equal(t, w.Body.String(), "Gin Web Framework") - assert.Equal(t, w.HeaderMap.Get("Content-Type"), "text/plain; charset=utf-8") - - w3 := performRequest(router, "HEAD", "/using_static/"+filename) - w4 := performRequest(router, "HEAD", "/result") - - assert.Equal(t, w3, w4) - assert.Equal(t, w3.Code, 200) -} - -// TestHandleStaticDir - ensure the root/sub dir handles properly -func TestRouteStaticListingDir(t *testing.T) { - router := New() - router.StaticFS("/", Dir("./", true)) - - w := performRequest(router, "GET", "/") - - assert.Equal(t, w.Code, 200) - assert.Contains(t, w.Body.String(), "gin.go") - assert.Equal(t, w.HeaderMap.Get("Content-Type"), "text/html; charset=utf-8") -} - -// TestHandleHeadToDir - ensure the root/sub dir handles properly -func TestRouteStaticNoListing(t *testing.T) { - router := New() - router.Static("/", "./") - - w := performRequest(router, "GET", "/") - - assert.Equal(t, w.Code, 404) - assert.NotContains(t, w.Body.String(), "gin.go") -} - -func TestRouterMiddlewareAndStatic(t *testing.T) { - router := New() - static := router.Group("/", func(c *Context) { - c.Writer.Header().Add("Last-Modified", "Mon, 02 Jan 2006 15:04:05 MST") - c.Writer.Header().Add("Expires", "Mon, 02 Jan 2006 15:04:05 MST") - c.Writer.Header().Add("X-GIN", "Gin Framework") - }) - static.Static("/", "./") - - w := performRequest(router, "GET", "/gin.go") - - assert.Equal(t, w.Code, 200) - assert.Contains(t, w.Body.String(), "package gin") - assert.Equal(t, w.HeaderMap.Get("Content-Type"), "text/plain; charset=utf-8") - assert.NotEqual(t, w.HeaderMap.Get("Last-Modified"), "Mon, 02 Jan 2006 15:04:05 MST") - assert.Equal(t, w.HeaderMap.Get("Expires"), "Mon, 02 Jan 2006 15:04:05 MST") - assert.Equal(t, w.HeaderMap.Get("x-GIN"), "Gin Framework") -} - -func TestRouteNotAllowedEnabled(t *testing.T) { - router := New() - router.HandleMethodNotAllowed = true - router.POST("/path", func(c *Context) {}) - w := performRequest(router, "GET", "/path") - assert.Equal(t, w.Code, http.StatusMethodNotAllowed) - - router.NoMethod(func(c *Context) { - c.String(http.StatusTeapot, "responseText") - }) - w = performRequest(router, "GET", "/path") - assert.Equal(t, w.Body.String(), "responseText") - assert.Equal(t, w.Code, http.StatusTeapot) -} - -func TestRouteNotAllowedDisabled(t *testing.T) { - router := New() - router.HandleMethodNotAllowed = false - router.POST("/path", func(c *Context) {}) - w := performRequest(router, "GET", "/path") - assert.Equal(t, w.Code, 404) - - router.NoMethod(func(c *Context) { - c.String(http.StatusTeapot, "responseText") - }) - w = performRequest(router, "GET", "/path") - assert.Equal(t, w.Body.String(), "404 page not found") - assert.Equal(t, w.Code, 404) -} - -func TestRouterNotFound(t *testing.T) { - router := New() - router.RedirectFixedPath = true - router.GET("/path", func(c *Context) {}) - router.GET("/dir/", func(c *Context) {}) - router.GET("/", func(c *Context) {}) - - testRoutes := []struct { - route string - code int - header string - }{ - {"/path/", 301, "map[Location:[/path]]"}, // TSR -/ - {"/dir", 301, "map[Location:[/dir/]]"}, // TSR +/ - {"", 301, "map[Location:[/]]"}, // TSR +/ - {"/PATH", 301, "map[Location:[/path]]"}, // Fixed Case - {"/DIR/", 301, "map[Location:[/dir/]]"}, // Fixed Case - {"/PATH/", 301, "map[Location:[/path]]"}, // Fixed Case -/ - {"/DIR", 301, "map[Location:[/dir/]]"}, // Fixed Case +/ - {"/../path", 301, "map[Location:[/path]]"}, // CleanPath - {"/nope", 404, ""}, // NotFound - } - for _, tr := range testRoutes { - w := performRequest(router, "GET", tr.route) - assert.Equal(t, w.Code, tr.code) - if w.Code != 404 { - assert.Equal(t, fmt.Sprint(w.Header()), tr.header) - } - } - - // Test custom not found handler - var notFound bool - router.NoRoute(func(c *Context) { - c.AbortWithStatus(404) - notFound = true - }) - w := performRequest(router, "GET", "/nope") - assert.Equal(t, w.Code, 404) - assert.True(t, notFound) - - // Test other method than GET (want 307 instead of 301) - router.PATCH("/path", func(c *Context) {}) - w = performRequest(router, "PATCH", "/path/") - assert.Equal(t, w.Code, 307) - assert.Equal(t, fmt.Sprint(w.Header()), "map[Location:[/path]]") - - // Test special case where no node for the prefix "/" exists - router = New() - router.GET("/a", func(c *Context) {}) - w = performRequest(router, "GET", "/") - assert.Equal(t, w.Code, 404) -} diff --git a/vendor/github.com/gin-gonic/gin/test_helpers.go b/vendor/github.com/gin-gonic/gin/test_helpers.go new file mode 100644 index 000000000..7d8020c3e --- /dev/null +++ b/vendor/github.com/gin-gonic/gin/test_helpers.go @@ -0,0 +1,14 @@ +package gin + +import ( + "net/http/httptest" +) + +func CreateTestContext() (c *Context, w *httptest.ResponseRecorder, r *Engine) { + w = httptest.NewRecorder() + r = New() + c = r.allocateContext() + c.reset() + c.writermem.reset(w) + return +} diff --git a/vendor/github.com/gin-gonic/gin/tree.go b/vendor/github.com/gin-gonic/gin/tree.go index c87e0d89b..4f2082ee6 100644 --- a/vendor/github.com/gin-gonic/gin/tree.go +++ b/vendor/github.com/gin-gonic/gin/tree.go @@ -76,9 +76,10 @@ func countParams(path string) uint8 { type nodeType uint8 const ( - static nodeType = 0 - param nodeType = 1 - catchAll nodeType = 2 + static nodeType = iota // default + root + param + catchAll ) type node struct { @@ -238,6 +239,7 @@ func (n *node) addRoute(path string, handlers HandlersChain) { } } else { // Empty tree n.insertChild(numParams, path, fullPath, handlers) + n.nType = root } } @@ -452,6 +454,11 @@ walk: // Outer loop for walking the tree return } + if path == "/" && n.wildChild && n.nType != root { + tsr = true + return + } + // No handle found. Check if a handle for this path + a // trailing slash exists for trailing slash recommendation for i := 0; i < len(n.indices); i++ { diff --git a/vendor/github.com/gin-gonic/gin/tree_test.go b/vendor/github.com/gin-gonic/gin/tree_test.go deleted file mode 100644 index 4e2cb7f69..000000000 --- a/vendor/github.com/gin-gonic/gin/tree_test.go +++ /dev/null @@ -1,608 +0,0 @@ -// Copyright 2013 Julien Schmidt. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be found -// in the LICENSE file. - -package gin - -import ( - "fmt" - "reflect" - "strings" - "testing" -) - -func printChildren(n *node, prefix string) { - fmt.Printf(" %02d:%02d %s%s[%d] %v %t %d \r\n", n.priority, n.maxParams, prefix, n.path, len(n.children), n.handlers, n.wildChild, n.nType) - for l := len(n.path); l > 0; l-- { - prefix += " " - } - for _, child := range n.children { - printChildren(child, prefix) - } -} - -// Used as a workaround since we can't compare functions or their adresses -var fakeHandlerValue string - -func fakeHandler(val string) HandlersChain { - return HandlersChain{func(c *Context) { - fakeHandlerValue = val - }} -} - -type testRequests []struct { - path string - nilHandler bool - route string - ps Params -} - -func checkRequests(t *testing.T, tree *node, requests testRequests) { - for _, request := range requests { - handler, ps, _ := tree.getValue(request.path, nil) - - if handler == nil { - if !request.nilHandler { - t.Errorf("handle mismatch for route '%s': Expected non-nil handle", request.path) - } - } else if request.nilHandler { - t.Errorf("handle mismatch for route '%s': Expected nil handle", request.path) - } else { - handler[0](nil) - if fakeHandlerValue != request.route { - t.Errorf("handle mismatch for route '%s': Wrong handle (%s != %s)", request.path, fakeHandlerValue, request.route) - } - } - - if !reflect.DeepEqual(ps, request.ps) { - t.Errorf("Params mismatch for route '%s'", request.path) - } - } -} - -func checkPriorities(t *testing.T, n *node) uint32 { - var prio uint32 - for i := range n.children { - prio += checkPriorities(t, n.children[i]) - } - - if n.handlers != nil { - prio++ - } - - if n.priority != prio { - t.Errorf( - "priority mismatch for node '%s': is %d, should be %d", - n.path, n.priority, prio, - ) - } - - return prio -} - -func checkMaxParams(t *testing.T, n *node) uint8 { - var maxParams uint8 - for i := range n.children { - params := checkMaxParams(t, n.children[i]) - if params > maxParams { - maxParams = params - } - } - if n.nType != static && !n.wildChild { - maxParams++ - } - - if n.maxParams != maxParams { - t.Errorf( - "maxParams mismatch for node '%s': is %d, should be %d", - n.path, n.maxParams, maxParams, - ) - } - - return maxParams -} - -func TestCountParams(t *testing.T) { - if countParams("/path/:param1/static/*catch-all") != 2 { - t.Fail() - } - if countParams(strings.Repeat("/:param", 256)) != 255 { - t.Fail() - } -} - -func TestTreeAddAndGet(t *testing.T) { - tree := &node{} - - routes := [...]string{ - "/hi", - "/contact", - "/co", - "/c", - "/a", - "/ab", - "/doc/", - "/doc/go_faq.html", - "/doc/go1.html", - "/α", - "/β", - } - for _, route := range routes { - tree.addRoute(route, fakeHandler(route)) - } - - //printChildren(tree, "") - - checkRequests(t, tree, testRequests{ - {"/a", false, "/a", nil}, - {"/", true, "", nil}, - {"/hi", false, "/hi", nil}, - {"/contact", false, "/contact", nil}, - {"/co", false, "/co", nil}, - {"/con", true, "", nil}, // key mismatch - {"/cona", true, "", nil}, // key mismatch - {"/no", true, "", nil}, // no matching child - {"/ab", false, "/ab", nil}, - {"/α", false, "/α", nil}, - {"/β", false, "/β", nil}, - }) - - checkPriorities(t, tree) - checkMaxParams(t, tree) -} - -func TestTreeWildcard(t *testing.T) { - tree := &node{} - - routes := [...]string{ - "/", - "/cmd/:tool/:sub", - "/cmd/:tool/", - "/src/*filepath", - "/search/", - "/search/:query", - "/user_:name", - "/user_:name/about", - "/files/:dir/*filepath", - "/doc/", - "/doc/go_faq.html", - "/doc/go1.html", - "/info/:user/public", - "/info/:user/project/:project", - } - for _, route := range routes { - tree.addRoute(route, fakeHandler(route)) - } - - //printChildren(tree, "") - - checkRequests(t, tree, testRequests{ - {"/", false, "/", nil}, - {"/cmd/test/", false, "/cmd/:tool/", Params{Param{"tool", "test"}}}, - {"/cmd/test", true, "", Params{Param{"tool", "test"}}}, - {"/cmd/test/3", false, "/cmd/:tool/:sub", Params{Param{"tool", "test"}, Param{"sub", "3"}}}, - {"/src/", false, "/src/*filepath", Params{Param{"filepath", "/"}}}, - {"/src/some/file.png", false, "/src/*filepath", Params{Param{"filepath", "/some/file.png"}}}, - {"/search/", false, "/search/", nil}, - {"/search/someth!ng+in+ünìcodé", false, "/search/:query", Params{Param{"query", "someth!ng+in+ünìcodé"}}}, - {"/search/someth!ng+in+ünìcodé/", true, "", Params{Param{"query", "someth!ng+in+ünìcodé"}}}, - {"/user_gopher", false, "/user_:name", Params{Param{"name", "gopher"}}}, - {"/user_gopher/about", false, "/user_:name/about", Params{Param{"name", "gopher"}}}, - {"/files/js/inc/framework.js", false, "/files/:dir/*filepath", Params{Param{"dir", "js"}, Param{"filepath", "/inc/framework.js"}}}, - {"/info/gordon/public", false, "/info/:user/public", Params{Param{"user", "gordon"}}}, - {"/info/gordon/project/go", false, "/info/:user/project/:project", Params{Param{"user", "gordon"}, Param{"project", "go"}}}, - }) - - checkPriorities(t, tree) - checkMaxParams(t, tree) -} - -func catchPanic(testFunc func()) (recv interface{}) { - defer func() { - recv = recover() - }() - - testFunc() - return -} - -type testRoute struct { - path string - conflict bool -} - -func testRoutes(t *testing.T, routes []testRoute) { - tree := &node{} - - for _, route := range routes { - recv := catchPanic(func() { - tree.addRoute(route.path, nil) - }) - - if route.conflict { - if recv == nil { - t.Errorf("no panic for conflicting route '%s'", route.path) - } - } else if recv != nil { - t.Errorf("unexpected panic for route '%s': %v", route.path, recv) - } - } - - //printChildren(tree, "") -} - -func TestTreeWildcardConflict(t *testing.T) { - routes := []testRoute{ - {"/cmd/:tool/:sub", false}, - {"/cmd/vet", true}, - {"/src/*filepath", false}, - {"/src/*filepathx", true}, - {"/src/", true}, - {"/src1/", false}, - {"/src1/*filepath", true}, - {"/src2*filepath", true}, - {"/search/:query", false}, - {"/search/invalid", true}, - {"/user_:name", false}, - {"/user_x", true}, - {"/user_:name", false}, - {"/id:id", false}, - {"/id/:id", true}, - } - testRoutes(t, routes) -} - -func TestTreeChildConflict(t *testing.T) { - routes := []testRoute{ - {"/cmd/vet", false}, - {"/cmd/:tool/:sub", true}, - {"/src/AUTHORS", false}, - {"/src/*filepath", true}, - {"/user_x", false}, - {"/user_:name", true}, - {"/id/:id", false}, - {"/id:id", true}, - {"/:id", true}, - {"/*filepath", true}, - } - testRoutes(t, routes) -} - -func TestTreeDupliatePath(t *testing.T) { - tree := &node{} - - routes := [...]string{ - "/", - "/doc/", - "/src/*filepath", - "/search/:query", - "/user_:name", - } - for _, route := range routes { - recv := catchPanic(func() { - tree.addRoute(route, fakeHandler(route)) - }) - if recv != nil { - t.Fatalf("panic inserting route '%s': %v", route, recv) - } - - // Add again - recv = catchPanic(func() { - tree.addRoute(route, nil) - }) - if recv == nil { - t.Fatalf("no panic while inserting duplicate route '%s", route) - } - } - - //printChildren(tree, "") - - checkRequests(t, tree, testRequests{ - {"/", false, "/", nil}, - {"/doc/", false, "/doc/", nil}, - {"/src/some/file.png", false, "/src/*filepath", Params{Param{"filepath", "/some/file.png"}}}, - {"/search/someth!ng+in+ünìcodé", false, "/search/:query", Params{Param{"query", "someth!ng+in+ünìcodé"}}}, - {"/user_gopher", false, "/user_:name", Params{Param{"name", "gopher"}}}, - }) -} - -func TestEmptyWildcardName(t *testing.T) { - tree := &node{} - - routes := [...]string{ - "/user:", - "/user:/", - "/cmd/:/", - "/src/*", - } - for _, route := range routes { - recv := catchPanic(func() { - tree.addRoute(route, nil) - }) - if recv == nil { - t.Fatalf("no panic while inserting route with empty wildcard name '%s", route) - } - } -} - -func TestTreeCatchAllConflict(t *testing.T) { - routes := []testRoute{ - {"/src/*filepath/x", true}, - {"/src2/", false}, - {"/src2/*filepath/x", true}, - } - testRoutes(t, routes) -} - -func TestTreeCatchAllConflictRoot(t *testing.T) { - routes := []testRoute{ - {"/", false}, - {"/*filepath", true}, - } - testRoutes(t, routes) -} - -func TestTreeDoubleWildcard(t *testing.T) { - const panicMsg = "only one wildcard per path segment is allowed" - - routes := [...]string{ - "/:foo:bar", - "/:foo:bar/", - "/:foo*bar", - } - - for _, route := range routes { - tree := &node{} - recv := catchPanic(func() { - tree.addRoute(route, nil) - }) - - if rs, ok := recv.(string); !ok || !strings.HasPrefix(rs, panicMsg) { - t.Fatalf(`"Expected panic "%s" for route '%s', got "%v"`, panicMsg, route, recv) - } - } -} - -/*func TestTreeDuplicateWildcard(t *testing.T) { - tree := &node{} - - routes := [...]string{ - "/:id/:name/:id", - } - for _, route := range routes { - ... - } -}*/ - -func TestTreeTrailingSlashRedirect(t *testing.T) { - tree := &node{} - - routes := [...]string{ - "/hi", - "/b/", - "/search/:query", - "/cmd/:tool/", - "/src/*filepath", - "/x", - "/x/y", - "/y/", - "/y/z", - "/0/:id", - "/0/:id/1", - "/1/:id/", - "/1/:id/2", - "/aa", - "/a/", - "/doc", - "/doc/go_faq.html", - "/doc/go1.html", - "/no/a", - "/no/b", - "/api/hello/:name", - } - for _, route := range routes { - recv := catchPanic(func() { - tree.addRoute(route, fakeHandler(route)) - }) - if recv != nil { - t.Fatalf("panic inserting route '%s': %v", route, recv) - } - } - - //printChildren(tree, "") - - tsrRoutes := [...]string{ - "/hi/", - "/b", - "/search/gopher/", - "/cmd/vet", - "/src", - "/x/", - "/y", - "/0/go/", - "/1/go", - "/a", - "/doc/", - } - for _, route := range tsrRoutes { - handler, _, tsr := tree.getValue(route, nil) - if handler != nil { - t.Fatalf("non-nil handler for TSR route '%s", route) - } else if !tsr { - t.Errorf("expected TSR recommendation for route '%s'", route) - } - } - - noTsrRoutes := [...]string{ - "/", - "/no", - "/no/", - "/_", - "/_/", - "/api/world/abc", - } - for _, route := range noTsrRoutes { - handler, _, tsr := tree.getValue(route, nil) - if handler != nil { - t.Fatalf("non-nil handler for No-TSR route '%s", route) - } else if tsr { - t.Errorf("expected no TSR recommendation for route '%s'", route) - } - } -} - -func TestTreeFindCaseInsensitivePath(t *testing.T) { - tree := &node{} - - routes := [...]string{ - "/hi", - "/b/", - "/ABC/", - "/search/:query", - "/cmd/:tool/", - "/src/*filepath", - "/x", - "/x/y", - "/y/", - "/y/z", - "/0/:id", - "/0/:id/1", - "/1/:id/", - "/1/:id/2", - "/aa", - "/a/", - "/doc", - "/doc/go_faq.html", - "/doc/go1.html", - "/doc/go/away", - "/no/a", - "/no/b", - } - - for _, route := range routes { - recv := catchPanic(func() { - tree.addRoute(route, fakeHandler(route)) - }) - if recv != nil { - t.Fatalf("panic inserting route '%s': %v", route, recv) - } - } - - // Check out == in for all registered routes - // With fixTrailingSlash = true - for _, route := range routes { - out, found := tree.findCaseInsensitivePath(route, true) - if !found { - t.Errorf("Route '%s' not found!", route) - } else if string(out) != route { - t.Errorf("Wrong result for route '%s': %s", route, string(out)) - } - } - // With fixTrailingSlash = false - for _, route := range routes { - out, found := tree.findCaseInsensitivePath(route, false) - if !found { - t.Errorf("Route '%s' not found!", route) - } else if string(out) != route { - t.Errorf("Wrong result for route '%s': %s", route, string(out)) - } - } - - tests := []struct { - in string - out string - found bool - slash bool - }{ - {"/HI", "/hi", true, false}, - {"/HI/", "/hi", true, true}, - {"/B", "/b/", true, true}, - {"/B/", "/b/", true, false}, - {"/abc", "/ABC/", true, true}, - {"/abc/", "/ABC/", true, false}, - {"/aBc", "/ABC/", true, true}, - {"/aBc/", "/ABC/", true, false}, - {"/abC", "/ABC/", true, true}, - {"/abC/", "/ABC/", true, false}, - {"/SEARCH/QUERY", "/search/QUERY", true, false}, - {"/SEARCH/QUERY/", "/search/QUERY", true, true}, - {"/CMD/TOOL/", "/cmd/TOOL/", true, false}, - {"/CMD/TOOL", "/cmd/TOOL/", true, true}, - {"/SRC/FILE/PATH", "/src/FILE/PATH", true, false}, - {"/x/Y", "/x/y", true, false}, - {"/x/Y/", "/x/y", true, true}, - {"/X/y", "/x/y", true, false}, - {"/X/y/", "/x/y", true, true}, - {"/X/Y", "/x/y", true, false}, - {"/X/Y/", "/x/y", true, true}, - {"/Y/", "/y/", true, false}, - {"/Y", "/y/", true, true}, - {"/Y/z", "/y/z", true, false}, - {"/Y/z/", "/y/z", true, true}, - {"/Y/Z", "/y/z", true, false}, - {"/Y/Z/", "/y/z", true, true}, - {"/y/Z", "/y/z", true, false}, - {"/y/Z/", "/y/z", true, true}, - {"/Aa", "/aa", true, false}, - {"/Aa/", "/aa", true, true}, - {"/AA", "/aa", true, false}, - {"/AA/", "/aa", true, true}, - {"/aA", "/aa", true, false}, - {"/aA/", "/aa", true, true}, - {"/A/", "/a/", true, false}, - {"/A", "/a/", true, true}, - {"/DOC", "/doc", true, false}, - {"/DOC/", "/doc", true, true}, - {"/NO", "", false, true}, - {"/DOC/GO", "", false, true}, - } - // With fixTrailingSlash = true - for _, test := range tests { - out, found := tree.findCaseInsensitivePath(test.in, true) - if found != test.found || (found && (string(out) != test.out)) { - t.Errorf("Wrong result for '%s': got %s, %t; want %s, %t", - test.in, string(out), found, test.out, test.found) - return - } - } - // With fixTrailingSlash = false - for _, test := range tests { - out, found := tree.findCaseInsensitivePath(test.in, false) - if test.slash { - if found { // test needs a trailingSlash fix. It must not be found! - t.Errorf("Found without fixTrailingSlash: %s; got %s", test.in, string(out)) - } - } else { - if found != test.found || (found && (string(out) != test.out)) { - t.Errorf("Wrong result for '%s': got %s, %t; want %s, %t", - test.in, string(out), found, test.out, test.found) - return - } - } - } -} - -func TestTreeInvalidNodeType(t *testing.T) { - tree := &node{} - tree.addRoute("/", fakeHandler("/")) - tree.addRoute("/:page", fakeHandler("/:page")) - - // set invalid node type - tree.children[0].nType = 42 - - // normal lookup - recv := catchPanic(func() { - tree.getValue("/test", nil) - }) - if rs, ok := recv.(string); !ok || rs != "invalid node type" { - t.Fatalf(`Expected panic "invalid node type", got "%v"`, recv) - } - - // case-insensitive lookup - recv = catchPanic(func() { - tree.findCaseInsensitivePath("/test", true) - }) - if rs, ok := recv.(string); !ok || rs != "invalid node type" { - t.Fatalf(`Expected panic "invalid node type", got "%v"`, recv) - } -} diff --git a/vendor/github.com/gin-gonic/gin/utils.go b/vendor/github.com/gin-gonic/gin/utils.go index 533888d1e..2814791fb 100644 --- a/vendor/github.com/gin-gonic/gin/utils.go +++ b/vendor/github.com/gin-gonic/gin/utils.go @@ -71,6 +71,12 @@ func (h H) MarshalXML(e *xml.Encoder, start xml.StartElement) error { return nil } +func assert1(guard bool, text string) { + if !guard { + panic(text) + } +} + func filterFlags(content string) string { for i, char := range content { if char == ' ' || char == ';' { diff --git a/vendor/github.com/gin-gonic/gin/utils_test.go b/vendor/github.com/gin-gonic/gin/utils_test.go deleted file mode 100644 index 11a5b6848..000000000 --- a/vendor/github.com/gin-gonic/gin/utils_test.go +++ /dev/null @@ -1,126 +0,0 @@ -// Copyright 2014 Manu Martinez-Almeida. All rights reserved. -// Use of this source code is governed by a MIT style -// license that can be found in the LICENSE file. - -package gin - -import ( - "fmt" - "net/http" - "testing" - - "github.com/stretchr/testify/assert" -) - -func init() { - SetMode(TestMode) -} - -type testStruct struct { - T *testing.T -} - -func (t *testStruct) ServeHTTP(w http.ResponseWriter, req *http.Request) { - assert.Equal(t.T, req.Method, "POST") - assert.Equal(t.T, req.URL.Path, "/path") - w.WriteHeader(500) - fmt.Fprint(w, "hello") -} - -func TestWrap(t *testing.T) { - router := New() - router.POST("/path", WrapH(&testStruct{t})) - router.GET("/path2", WrapF(func(w http.ResponseWriter, req *http.Request) { - assert.Equal(t, req.Method, "GET") - assert.Equal(t, req.URL.Path, "/path2") - w.WriteHeader(400) - fmt.Fprint(w, "hola!") - })) - - w := performRequest(router, "POST", "/path") - assert.Equal(t, w.Code, 500) - assert.Equal(t, w.Body.String(), "hello") - - w = performRequest(router, "GET", "/path2") - assert.Equal(t, w.Code, 400) - assert.Equal(t, w.Body.String(), "hola!") -} - -func TestLastChar(t *testing.T) { - assert.Equal(t, lastChar("hola"), uint8('a')) - assert.Equal(t, lastChar("adios"), uint8('s')) - assert.Panics(t, func() { lastChar("") }) -} - -func TestParseAccept(t *testing.T) { - parts := parseAccept("text/html , application/xhtml+xml,application/xml;q=0.9, */* ;q=0.8") - assert.Len(t, parts, 4) - assert.Equal(t, parts[0], "text/html") - assert.Equal(t, parts[1], "application/xhtml+xml") - assert.Equal(t, parts[2], "application/xml") - assert.Equal(t, parts[3], "*/*") -} - -func TestChooseData(t *testing.T) { - A := "a" - B := "b" - assert.Equal(t, chooseData(A, B), A) - assert.Equal(t, chooseData(nil, B), B) - assert.Panics(t, func() { chooseData(nil, nil) }) -} - -func TestFilterFlags(t *testing.T) { - result := filterFlags("text/html ") - assert.Equal(t, result, "text/html") - - result = filterFlags("text/html;") - assert.Equal(t, result, "text/html") -} - -func TestFunctionName(t *testing.T) { - assert.Equal(t, nameOfFunction(somefunction), "github.com/gin-gonic/gin.somefunction") -} - -func somefunction() { - // this empty function is used by TestFunctionName() -} - -func TestJoinPaths(t *testing.T) { - assert.Equal(t, joinPaths("", ""), "") - assert.Equal(t, joinPaths("", "/"), "/") - assert.Equal(t, joinPaths("/a", ""), "/a") - assert.Equal(t, joinPaths("/a/", ""), "/a/") - assert.Equal(t, joinPaths("/a/", "/"), "/a/") - assert.Equal(t, joinPaths("/a", "/"), "/a/") - assert.Equal(t, joinPaths("/a", "/hola"), "/a/hola") - assert.Equal(t, joinPaths("/a/", "/hola"), "/a/hola") - assert.Equal(t, joinPaths("/a/", "/hola/"), "/a/hola/") - assert.Equal(t, joinPaths("/a/", "/hola//"), "/a/hola/") -} - -type bindTestStruct struct { - Foo string `form:"foo" binding:"required"` - Bar int `form:"bar" binding:"min=4"` -} - -func TestBindMiddleware(t *testing.T) { - var value *bindTestStruct - var called bool - router := New() - router.GET("/", Bind(bindTestStruct{}), func(c *Context) { - called = true - value = c.MustGet(BindKey).(*bindTestStruct) - }) - performRequest(router, "GET", "/?foo=hola&bar=10") - assert.True(t, called) - assert.Equal(t, value.Foo, "hola") - assert.Equal(t, value.Bar, 10) - - called = false - performRequest(router, "GET", "/?foo=hola&bar=1") - assert.False(t, called) - - assert.Panics(t, func() { - Bind(&bindTestStruct{}) - }) -} diff --git a/vendor/github.com/go-sql-driver/mysql/benchmark_test.go b/vendor/github.com/go-sql-driver/mysql/benchmark_test.go deleted file mode 100644 index d72a4183f..000000000 --- a/vendor/github.com/go-sql-driver/mysql/benchmark_test.go +++ /dev/null @@ -1,208 +0,0 @@ -// Go MySQL Driver - A MySQL-Driver for Go's database/sql package -// -// Copyright 2013 The Go-MySQL-Driver Authors. All rights reserved. -// -// This Source Code Form is subject to the terms of the Mozilla Public -// License, v. 2.0. If a copy of the MPL was not distributed with this file, -// You can obtain one at http://mozilla.org/MPL/2.0/. - -package mysql - -import ( - "bytes" - "database/sql" - "strings" - "sync" - "sync/atomic" - "testing" -) - -type TB testing.B - -func (tb *TB) check(err error) { - if err != nil { - tb.Fatal(err) - } -} - -func (tb *TB) checkDB(db *sql.DB, err error) *sql.DB { - tb.check(err) - return db -} - -func (tb *TB) checkRows(rows *sql.Rows, err error) *sql.Rows { - tb.check(err) - return rows -} - -func (tb *TB) checkStmt(stmt *sql.Stmt, err error) *sql.Stmt { - tb.check(err) - return stmt -} - -func initDB(b *testing.B, queries ...string) *sql.DB { - tb := (*TB)(b) - db := tb.checkDB(sql.Open("mysql", dsn)) - for _, query := range queries { - if _, err := db.Exec(query); err != nil { - b.Fatalf("Error on %q: %v", query, err) - } - } - return db -} - -const concurrencyLevel = 10 - -func BenchmarkQuery(b *testing.B) { - tb := (*TB)(b) - b.StopTimer() - b.ReportAllocs() - db := initDB(b, - "DROP TABLE IF EXISTS foo", - "CREATE TABLE foo (id INT PRIMARY KEY, val CHAR(50))", - `INSERT INTO foo VALUES (1, "one")`, - `INSERT INTO foo VALUES (2, "two")`, - ) - db.SetMaxIdleConns(concurrencyLevel) - defer db.Close() - - stmt := tb.checkStmt(db.Prepare("SELECT val FROM foo WHERE id=?")) - defer stmt.Close() - - remain := int64(b.N) - var wg sync.WaitGroup - wg.Add(concurrencyLevel) - defer wg.Wait() - b.StartTimer() - - for i := 0; i < concurrencyLevel; i++ { - go func() { - for { - if atomic.AddInt64(&remain, -1) < 0 { - wg.Done() - return - } - - var got string - tb.check(stmt.QueryRow(1).Scan(&got)) - if got != "one" { - b.Errorf("query = %q; want one", got) - wg.Done() - return - } - } - }() - } -} - -func BenchmarkExec(b *testing.B) { - tb := (*TB)(b) - b.StopTimer() - b.ReportAllocs() - db := tb.checkDB(sql.Open("mysql", dsn)) - db.SetMaxIdleConns(concurrencyLevel) - defer db.Close() - - stmt := tb.checkStmt(db.Prepare("DO 1")) - defer stmt.Close() - - remain := int64(b.N) - var wg sync.WaitGroup - wg.Add(concurrencyLevel) - defer wg.Wait() - b.StartTimer() - - for i := 0; i < concurrencyLevel; i++ { - go func() { - for { - if atomic.AddInt64(&remain, -1) < 0 { - wg.Done() - return - } - - if _, err := stmt.Exec(); err != nil { - b.Fatal(err.Error()) - } - } - }() - } -} - -// data, but no db writes -var roundtripSample []byte - -func initRoundtripBenchmarks() ([]byte, int, int) { - if roundtripSample == nil { - roundtripSample = []byte(strings.Repeat("0123456789abcdef", 1024*1024)) - } - return roundtripSample, 16, len(roundtripSample) -} - -func BenchmarkRoundtripTxt(b *testing.B) { - b.StopTimer() - sample, min, max := initRoundtripBenchmarks() - sampleString := string(sample) - b.ReportAllocs() - tb := (*TB)(b) - db := tb.checkDB(sql.Open("mysql", dsn)) - defer db.Close() - b.StartTimer() - var result string - for i := 0; i < b.N; i++ { - length := min + i - if length > max { - length = max - } - test := sampleString[0:length] - rows := tb.checkRows(db.Query(`SELECT "` + test + `"`)) - if !rows.Next() { - rows.Close() - b.Fatalf("crashed") - } - err := rows.Scan(&result) - if err != nil { - rows.Close() - b.Fatalf("crashed") - } - if result != test { - rows.Close() - b.Errorf("mismatch") - } - rows.Close() - } -} - -func BenchmarkRoundtripBin(b *testing.B) { - b.StopTimer() - sample, min, max := initRoundtripBenchmarks() - b.ReportAllocs() - tb := (*TB)(b) - db := tb.checkDB(sql.Open("mysql", dsn)) - defer db.Close() - stmt := tb.checkStmt(db.Prepare("SELECT ?")) - defer stmt.Close() - b.StartTimer() - var result sql.RawBytes - for i := 0; i < b.N; i++ { - length := min + i - if length > max { - length = max - } - test := sample[0:length] - rows := tb.checkRows(stmt.Query(test)) - if !rows.Next() { - rows.Close() - b.Fatalf("crashed") - } - err := rows.Scan(&result) - if err != nil { - rows.Close() - b.Fatalf("crashed") - } - if !bytes.Equal(result, test) { - rows.Close() - b.Errorf("mismatch") - } - rows.Close() - } -} diff --git a/vendor/github.com/go-sql-driver/mysql/driver_test.go b/vendor/github.com/go-sql-driver/mysql/driver_test.go deleted file mode 100644 index 854eec2d6..000000000 --- a/vendor/github.com/go-sql-driver/mysql/driver_test.go +++ /dev/null @@ -1,1259 +0,0 @@ -// Go MySQL Driver - A MySQL-Driver for Go's database/sql package -// -// Copyright 2013 The Go-MySQL-Driver Authors. All rights reserved. -// -// This Source Code Form is subject to the terms of the Mozilla Public -// License, v. 2.0. If a copy of the MPL was not distributed with this file, -// You can obtain one at http://mozilla.org/MPL/2.0/. - -package mysql - -import ( - "crypto/tls" - "database/sql" - "database/sql/driver" - "fmt" - "io" - "io/ioutil" - "net" - "net/url" - "os" - "strings" - "testing" - "time" -) - -var ( - dsn string - netAddr string - available bool -) - -var ( - tDate = time.Date(2012, 6, 14, 0, 0, 0, 0, time.UTC) - sDate = "2012-06-14" - tDateTime = time.Date(2011, 11, 20, 21, 27, 37, 0, time.UTC) - sDateTime = "2011-11-20 21:27:37" - tDate0 = time.Time{} - sDate0 = "0000-00-00" - sDateTime0 = "0000-00-00 00:00:00" -) - -// See https://github.com/go-sql-driver/mysql/wiki/Testing -func init() { - env := func(key, defaultValue string) string { - if value := os.Getenv(key); value != "" { - return value - } - return defaultValue - } - user := env("MYSQL_TEST_USER", "root") - pass := env("MYSQL_TEST_PASS", "") - prot := env("MYSQL_TEST_PROT", "tcp") - addr := env("MYSQL_TEST_ADDR", "localhost:3306") - dbname := env("MYSQL_TEST_DBNAME", "gotest") - netAddr = fmt.Sprintf("%s(%s)", prot, addr) - dsn = fmt.Sprintf("%s:%s@%s/%s?timeout=30s&strict=true", user, pass, netAddr, dbname) - c, err := net.Dial(prot, addr) - if err == nil { - available = true - c.Close() - } -} - -type DBTest struct { - *testing.T - db *sql.DB -} - -func runTests(t *testing.T, dsn string, tests ...func(dbt *DBTest)) { - if !available { - t.Skipf("MySQL-Server not running on %s", netAddr) - } - - db, err := sql.Open("mysql", dsn) - if err != nil { - t.Fatalf("Error connecting: %s", err.Error()) - } - defer db.Close() - - db.Exec("DROP TABLE IF EXISTS test") - - dbt := &DBTest{t, db} - for _, test := range tests { - test(dbt) - dbt.db.Exec("DROP TABLE IF EXISTS test") - } -} - -func (dbt *DBTest) fail(method, query string, err error) { - if len(query) > 300 { - query = "[query too large to print]" - } - dbt.Fatalf("Error on %s %s: %s", method, query, err.Error()) -} - -func (dbt *DBTest) mustExec(query string, args ...interface{}) (res sql.Result) { - res, err := dbt.db.Exec(query, args...) - if err != nil { - dbt.fail("Exec", query, err) - } - return res -} - -func (dbt *DBTest) mustQuery(query string, args ...interface{}) (rows *sql.Rows) { - rows, err := dbt.db.Query(query, args...) - if err != nil { - dbt.fail("Query", query, err) - } - return rows -} - -func TestCRUD(t *testing.T) { - runTests(t, dsn, func(dbt *DBTest) { - // Create Table - dbt.mustExec("CREATE TABLE test (value BOOL)") - - // Test for unexpected data - var out bool - rows := dbt.mustQuery("SELECT * FROM test") - if rows.Next() { - dbt.Error("unexpected data in empty table") - } - - // Create Data - res := dbt.mustExec("INSERT INTO test VALUES (1)") - count, err := res.RowsAffected() - if err != nil { - dbt.Fatalf("res.RowsAffected() returned error: %s", err.Error()) - } - if count != 1 { - dbt.Fatalf("Expected 1 affected row, got %d", count) - } - - id, err := res.LastInsertId() - if err != nil { - dbt.Fatalf("res.LastInsertId() returned error: %s", err.Error()) - } - if id != 0 { - dbt.Fatalf("Expected InsertID 0, got %d", id) - } - - // Read - rows = dbt.mustQuery("SELECT value FROM test") - if rows.Next() { - rows.Scan(&out) - if true != out { - dbt.Errorf("true != %t", out) - } - - if rows.Next() { - dbt.Error("unexpected data") - } - } else { - dbt.Error("no data") - } - - // Update - res = dbt.mustExec("UPDATE test SET value = ? WHERE value = ?", false, true) - count, err = res.RowsAffected() - if err != nil { - dbt.Fatalf("res.RowsAffected() returned error: %s", err.Error()) - } - if count != 1 { - dbt.Fatalf("Expected 1 affected row, got %d", count) - } - - // Check Update - rows = dbt.mustQuery("SELECT value FROM test") - if rows.Next() { - rows.Scan(&out) - if false != out { - dbt.Errorf("false != %t", out) - } - - if rows.Next() { - dbt.Error("unexpected data") - } - } else { - dbt.Error("no data") - } - - // Delete - res = dbt.mustExec("DELETE FROM test WHERE value = ?", false) - count, err = res.RowsAffected() - if err != nil { - dbt.Fatalf("res.RowsAffected() returned error: %s", err.Error()) - } - if count != 1 { - dbt.Fatalf("Expected 1 affected row, got %d", count) - } - - // Check for unexpected rows - res = dbt.mustExec("DELETE FROM test") - count, err = res.RowsAffected() - if err != nil { - dbt.Fatalf("res.RowsAffected() returned error: %s", err.Error()) - } - if count != 0 { - dbt.Fatalf("Expected 0 affected row, got %d", count) - } - }) -} - -func TestInt(t *testing.T) { - runTests(t, dsn, func(dbt *DBTest) { - types := [5]string{"TINYINT", "SMALLINT", "MEDIUMINT", "INT", "BIGINT"} - in := int64(42) - var out int64 - var rows *sql.Rows - - // SIGNED - for _, v := range types { - dbt.mustExec("CREATE TABLE test (value " + v + ")") - - dbt.mustExec("INSERT INTO test VALUES (?)", in) - - rows = dbt.mustQuery("SELECT value FROM test") - if rows.Next() { - rows.Scan(&out) - if in != out { - dbt.Errorf("%s: %d != %d", v, in, out) - } - } else { - dbt.Errorf("%s: no data", v) - } - - dbt.mustExec("DROP TABLE IF EXISTS test") - } - - // UNSIGNED ZEROFILL - for _, v := range types { - dbt.mustExec("CREATE TABLE test (value " + v + " ZEROFILL)") - - dbt.mustExec("INSERT INTO test VALUES (?)", in) - - rows = dbt.mustQuery("SELECT value FROM test") - if rows.Next() { - rows.Scan(&out) - if in != out { - dbt.Errorf("%s ZEROFILL: %d != %d", v, in, out) - } - } else { - dbt.Errorf("%s ZEROFILL: no data", v) - } - - dbt.mustExec("DROP TABLE IF EXISTS test") - } - }) -} - -func TestFloat(t *testing.T) { - runTests(t, dsn, func(dbt *DBTest) { - types := [2]string{"FLOAT", "DOUBLE"} - in := float32(42.23) - var out float32 - var rows *sql.Rows - for _, v := range types { - dbt.mustExec("CREATE TABLE test (value " + v + ")") - dbt.mustExec("INSERT INTO test VALUES (?)", in) - rows = dbt.mustQuery("SELECT value FROM test") - if rows.Next() { - rows.Scan(&out) - if in != out { - dbt.Errorf("%s: %g != %g", v, in, out) - } - } else { - dbt.Errorf("%s: no data", v) - } - dbt.mustExec("DROP TABLE IF EXISTS test") - } - }) -} - -func TestString(t *testing.T) { - runTests(t, dsn, func(dbt *DBTest) { - types := [6]string{"CHAR(255)", "VARCHAR(255)", "TINYTEXT", "TEXT", "MEDIUMTEXT", "LONGTEXT"} - in := "κόσμε üöäßñóùéàâÿœ'îë Árvíztűrő いろはにほへとちりぬるを イロハニホヘト דג סקרן чащах น่าฟังเอย" - var out string - var rows *sql.Rows - - for _, v := range types { - dbt.mustExec("CREATE TABLE test (value " + v + ") CHARACTER SET utf8") - - dbt.mustExec("INSERT INTO test VALUES (?)", in) - - rows = dbt.mustQuery("SELECT value FROM test") - if rows.Next() { - rows.Scan(&out) - if in != out { - dbt.Errorf("%s: %s != %s", v, in, out) - } - } else { - dbt.Errorf("%s: no data", v) - } - - dbt.mustExec("DROP TABLE IF EXISTS test") - } - - // BLOB - dbt.mustExec("CREATE TABLE test (id int, value BLOB) CHARACTER SET utf8") - - id := 2 - in = "Lorem ipsum dolor sit amet, consetetur sadipscing elitr, " + - "sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, " + - "sed diam voluptua. At vero eos et accusam et justo duo dolores et ea rebum. " + - "Stet clita kasd gubergren, no sea takimata sanctus est Lorem ipsum dolor sit amet. " + - "Lorem ipsum dolor sit amet, consetetur sadipscing elitr, " + - "sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, " + - "sed diam voluptua. At vero eos et accusam et justo duo dolores et ea rebum. " + - "Stet clita kasd gubergren, no sea takimata sanctus est Lorem ipsum dolor sit amet." - dbt.mustExec("INSERT INTO test VALUES (?, ?)", id, in) - - err := dbt.db.QueryRow("SELECT value FROM test WHERE id = ?", id).Scan(&out) - if err != nil { - dbt.Fatalf("Error on BLOB-Query: %s", err.Error()) - } else if out != in { - dbt.Errorf("BLOB: %s != %s", in, out) - } - }) -} - -func TestDateTime(t *testing.T) { - type testmode struct { - selectSuffix string - args []interface{} - } - type timetest struct { - in interface{} - sOut string - tOut time.Time - tIsZero bool - } - type tester func(dbt *DBTest, rows *sql.Rows, - test *timetest, sqltype, resulttype, mode string) - type setup struct { - vartype string - dsnSuffix string - test tester - } - var ( - modes = map[string]*testmode{ - "text": &testmode{}, - "binary": &testmode{" WHERE 1 = ?", []interface{}{1}}, - } - timetests = map[string][]*timetest{ - "DATE": { - {sDate, sDate, tDate, false}, - {sDate0, sDate0, tDate0, true}, - {tDate, sDate, tDate, false}, - {tDate0, sDate0, tDate0, true}, - }, - "DATETIME": { - {sDateTime, sDateTime, tDateTime, false}, - {sDateTime0, sDateTime0, tDate0, true}, - {tDateTime, sDateTime, tDateTime, false}, - {tDate0, sDateTime0, tDate0, true}, - }, - } - setups = []*setup{ - {"string", "&parseTime=false", func( - dbt *DBTest, rows *sql.Rows, test *timetest, sqltype, resulttype, mode string) { - var sOut string - if err := rows.Scan(&sOut); err != nil { - dbt.Errorf("%s (%s %s): %s", sqltype, resulttype, mode, err.Error()) - } else if test.sOut != sOut { - dbt.Errorf("%s (%s %s): %s != %s", sqltype, resulttype, mode, test.sOut, sOut) - } - }}, - {"time.Time", "&parseTime=true", func( - dbt *DBTest, rows *sql.Rows, test *timetest, sqltype, resulttype, mode string) { - var tOut time.Time - if err := rows.Scan(&tOut); err != nil { - dbt.Errorf("%s (%s %s): %s", sqltype, resulttype, mode, err.Error()) - } else if test.tOut != tOut || test.tIsZero != tOut.IsZero() { - dbt.Errorf("%s (%s %s): %s [%t] != %s [%t]", sqltype, resulttype, mode, test.tOut, test.tIsZero, tOut, tOut.IsZero()) - } - }}, - } - ) - - var s *setup - testTime := func(dbt *DBTest) { - var rows *sql.Rows - for sqltype, tests := range timetests { - dbt.mustExec("CREATE TABLE test (value " + sqltype + ")") - for _, test := range tests { - for mode, q := range modes { - dbt.mustExec("TRUNCATE test") - dbt.mustExec("INSERT INTO test VALUES (?)", test.in) - rows = dbt.mustQuery("SELECT value FROM test"+q.selectSuffix, q.args...) - if rows.Next() { - s.test(dbt, rows, test, sqltype, s.vartype, mode) - } else { - if err := rows.Err(); err != nil { - dbt.Errorf("%s (%s %s): %s", - sqltype, s.vartype, mode, err.Error()) - } else { - dbt.Errorf("%s (%s %s): no data", - sqltype, s.vartype, mode) - } - } - } - } - dbt.mustExec("DROP TABLE IF EXISTS test") - } - } - - timeDsn := dsn + "&sql_mode=ALLOW_INVALID_DATES" - for _, v := range setups { - s = v - runTests(t, timeDsn+s.dsnSuffix, testTime) - } -} - -func TestNULL(t *testing.T) { - runTests(t, dsn, func(dbt *DBTest) { - nullStmt, err := dbt.db.Prepare("SELECT NULL") - if err != nil { - dbt.Fatal(err) - } - defer nullStmt.Close() - - nonNullStmt, err := dbt.db.Prepare("SELECT 1") - if err != nil { - dbt.Fatal(err) - } - defer nonNullStmt.Close() - - // NullBool - var nb sql.NullBool - // Invalid - if err = nullStmt.QueryRow().Scan(&nb); err != nil { - dbt.Fatal(err) - } - if nb.Valid { - dbt.Error("Valid NullBool which should be invalid") - } - // Valid - if err = nonNullStmt.QueryRow().Scan(&nb); err != nil { - dbt.Fatal(err) - } - if !nb.Valid { - dbt.Error("Invalid NullBool which should be valid") - } else if nb.Bool != true { - dbt.Errorf("Unexpected NullBool value: %t (should be true)", nb.Bool) - } - - // NullFloat64 - var nf sql.NullFloat64 - // Invalid - if err = nullStmt.QueryRow().Scan(&nf); err != nil { - dbt.Fatal(err) - } - if nf.Valid { - dbt.Error("Valid NullFloat64 which should be invalid") - } - // Valid - if err = nonNullStmt.QueryRow().Scan(&nf); err != nil { - dbt.Fatal(err) - } - if !nf.Valid { - dbt.Error("Invalid NullFloat64 which should be valid") - } else if nf.Float64 != float64(1) { - dbt.Errorf("Unexpected NullFloat64 value: %f (should be 1.0)", nf.Float64) - } - - // NullInt64 - var ni sql.NullInt64 - // Invalid - if err = nullStmt.QueryRow().Scan(&ni); err != nil { - dbt.Fatal(err) - } - if ni.Valid { - dbt.Error("Valid NullInt64 which should be invalid") - } - // Valid - if err = nonNullStmt.QueryRow().Scan(&ni); err != nil { - dbt.Fatal(err) - } - if !ni.Valid { - dbt.Error("Invalid NullInt64 which should be valid") - } else if ni.Int64 != int64(1) { - dbt.Errorf("Unexpected NullInt64 value: %d (should be 1)", ni.Int64) - } - - // NullString - var ns sql.NullString - // Invalid - if err = nullStmt.QueryRow().Scan(&ns); err != nil { - dbt.Fatal(err) - } - if ns.Valid { - dbt.Error("Valid NullString which should be invalid") - } - // Valid - if err = nonNullStmt.QueryRow().Scan(&ns); err != nil { - dbt.Fatal(err) - } - if !ns.Valid { - dbt.Error("Invalid NullString which should be valid") - } else if ns.String != `1` { - dbt.Error("Unexpected NullString value:" + ns.String + " (should be `1`)") - } - - // nil-bytes - var b []byte - // Read nil - if err = nullStmt.QueryRow().Scan(&b); err != nil { - dbt.Fatal(err) - } - if b != nil { - dbt.Error("Non-nil []byte wich should be nil") - } - // Read non-nil - if err = nonNullStmt.QueryRow().Scan(&b); err != nil { - dbt.Fatal(err) - } - if b == nil { - dbt.Error("Nil []byte wich should be non-nil") - } - // Insert nil - b = nil - success := false - if err = dbt.db.QueryRow("SELECT ? IS NULL", b).Scan(&success); err != nil { - dbt.Fatal(err) - } - if !success { - dbt.Error("Inserting []byte(nil) as NULL failed") - } - // Check input==output with input==nil - b = nil - if err = dbt.db.QueryRow("SELECT ?", b).Scan(&b); err != nil { - dbt.Fatal(err) - } - if b != nil { - dbt.Error("Non-nil echo from nil input") - } - // Check input==output with input!=nil - b = []byte("") - if err = dbt.db.QueryRow("SELECT ?", b).Scan(&b); err != nil { - dbt.Fatal(err) - } - if b == nil { - dbt.Error("nil echo from non-nil input") - } - - // Insert NULL - dbt.mustExec("CREATE TABLE test (dummmy1 int, value int, dummy2 int)") - - dbt.mustExec("INSERT INTO test VALUES (?, ?, ?)", 1, nil, 2) - - var out interface{} - rows := dbt.mustQuery("SELECT * FROM test") - if rows.Next() { - rows.Scan(&out) - if out != nil { - dbt.Errorf("%v != nil", out) - } - } else { - dbt.Error("no data") - } - }) -} - -func TestLongData(t *testing.T) { - runTests(t, dsn, func(dbt *DBTest) { - var maxAllowedPacketSize int - err := dbt.db.QueryRow("select @@max_allowed_packet").Scan(&maxAllowedPacketSize) - if err != nil { - dbt.Fatal(err) - } - maxAllowedPacketSize-- - - // don't get too ambitious - if maxAllowedPacketSize > 1<<25 { - maxAllowedPacketSize = 1 << 25 - } - - dbt.mustExec("CREATE TABLE test (value LONGBLOB)") - - in := strings.Repeat(`a`, maxAllowedPacketSize+1) - var out string - var rows *sql.Rows - - // Long text data - const nonDataQueryLen = 28 // length query w/o value - inS := in[:maxAllowedPacketSize-nonDataQueryLen] - dbt.mustExec("INSERT INTO test VALUES('" + inS + "')") - rows = dbt.mustQuery("SELECT value FROM test") - if rows.Next() { - rows.Scan(&out) - if inS != out { - dbt.Fatalf("LONGBLOB: length in: %d, length out: %d", len(inS), len(out)) - } - if rows.Next() { - dbt.Error("LONGBLOB: unexpexted row") - } - } else { - dbt.Fatalf("LONGBLOB: no data") - } - - // Empty table - dbt.mustExec("TRUNCATE TABLE test") - - // Long binary data - dbt.mustExec("INSERT INTO test VALUES(?)", in) - rows = dbt.mustQuery("SELECT value FROM test WHERE 1=?", 1) - if rows.Next() { - rows.Scan(&out) - if in != out { - dbt.Fatalf("LONGBLOB: length in: %d, length out: %d", len(in), len(out)) - } - if rows.Next() { - dbt.Error("LONGBLOB: unexpexted row") - } - } else { - if err = rows.Err(); err != nil { - dbt.Fatalf("LONGBLOB: no data (err: %s)", err.Error()) - } else { - dbt.Fatal("LONGBLOB: no data (err: )") - } - } - }) -} - -func TestLoadData(t *testing.T) { - runTests(t, dsn, func(dbt *DBTest) { - verifyLoadDataResult := func() { - rows, err := dbt.db.Query("SELECT * FROM test") - if err != nil { - dbt.Fatal(err.Error()) - } - - i := 0 - values := [4]string{ - "a string", - "a string containing a \t", - "a string containing a \n", - "a string containing both \t\n", - } - - var id int - var value string - - for rows.Next() { - i++ - err = rows.Scan(&id, &value) - if err != nil { - dbt.Fatal(err.Error()) - } - if i != id { - dbt.Fatalf("%d != %d", i, id) - } - if values[i-1] != value { - dbt.Fatalf("%s != %s", values[i-1], value) - } - } - err = rows.Err() - if err != nil { - dbt.Fatal(err.Error()) - } - - if i != 4 { - dbt.Fatalf("Rows count mismatch. Got %d, want 4", i) - } - } - file, err := ioutil.TempFile("", "gotest") - defer os.Remove(file.Name()) - if err != nil { - dbt.Fatal(err) - } - file.WriteString("1\ta string\n2\ta string containing a \\t\n3\ta string containing a \\n\n4\ta string containing both \\t\\n\n") - file.Close() - - dbt.db.Exec("DROP TABLE IF EXISTS test") - dbt.mustExec("CREATE TABLE test (id INT NOT NULL PRIMARY KEY, value TEXT NOT NULL) CHARACTER SET utf8") - - // Local File - RegisterLocalFile(file.Name()) - dbt.mustExec(fmt.Sprintf("LOAD DATA LOCAL INFILE '%q' INTO TABLE test", file.Name())) - verifyLoadDataResult() - // negative test - _, err = dbt.db.Exec("LOAD DATA LOCAL INFILE 'doesnotexist' INTO TABLE test") - if err == nil { - dbt.Fatal("Load non-existent file didn't fail") - } else if err.Error() != "Local File 'doesnotexist' is not registered. Use the DSN parameter 'allowAllFiles=true' to allow all files" { - dbt.Fatal(err.Error()) - } - - // Empty table - dbt.mustExec("TRUNCATE TABLE test") - - // Reader - RegisterReaderHandler("test", func() io.Reader { - file, err = os.Open(file.Name()) - if err != nil { - dbt.Fatal(err) - } - return file - }) - dbt.mustExec("LOAD DATA LOCAL INFILE 'Reader::test' INTO TABLE test") - verifyLoadDataResult() - // negative test - _, err = dbt.db.Exec("LOAD DATA LOCAL INFILE 'Reader::doesnotexist' INTO TABLE test") - if err == nil { - dbt.Fatal("Load non-existent Reader didn't fail") - } else if err.Error() != "Reader 'doesnotexist' is not registered" { - dbt.Fatal(err.Error()) - } - }) -} - -func TestFoundRows(t *testing.T) { - runTests(t, dsn, func(dbt *DBTest) { - dbt.mustExec("CREATE TABLE test (id INT NOT NULL ,data INT NOT NULL)") - dbt.mustExec("INSERT INTO test (id, data) VALUES (0, 0),(0, 0),(1, 0),(1, 0),(1, 1)") - - res := dbt.mustExec("UPDATE test SET data = 1 WHERE id = 0") - count, err := res.RowsAffected() - if err != nil { - dbt.Fatalf("res.RowsAffected() returned error: %s", err.Error()) - } - if count != 2 { - dbt.Fatalf("Expected 2 affected rows, got %d", count) - } - res = dbt.mustExec("UPDATE test SET data = 1 WHERE id = 1") - count, err = res.RowsAffected() - if err != nil { - dbt.Fatalf("res.RowsAffected() returned error: %s", err.Error()) - } - if count != 2 { - dbt.Fatalf("Expected 2 affected rows, got %d", count) - } - }) - runTests(t, dsn+"&clientFoundRows=true", func(dbt *DBTest) { - dbt.mustExec("CREATE TABLE test (id INT NOT NULL ,data INT NOT NULL)") - dbt.mustExec("INSERT INTO test (id, data) VALUES (0, 0),(0, 0),(1, 0),(1, 0),(1, 1)") - - res := dbt.mustExec("UPDATE test SET data = 1 WHERE id = 0") - count, err := res.RowsAffected() - if err != nil { - dbt.Fatalf("res.RowsAffected() returned error: %s", err.Error()) - } - if count != 2 { - dbt.Fatalf("Expected 2 matched rows, got %d", count) - } - res = dbt.mustExec("UPDATE test SET data = 1 WHERE id = 1") - count, err = res.RowsAffected() - if err != nil { - dbt.Fatalf("res.RowsAffected() returned error: %s", err.Error()) - } - if count != 3 { - dbt.Fatalf("Expected 3 matched rows, got %d", count) - } - }) -} - -func TestStrict(t *testing.T) { - // ALLOW_INVALID_DATES to get rid of stricter modes - we want to test for warnings, not errors - relaxedDsn := dsn + "&sql_mode=ALLOW_INVALID_DATES" - runTests(t, relaxedDsn, func(dbt *DBTest) { - dbt.mustExec("CREATE TABLE test (a TINYINT NOT NULL, b CHAR(4))") - - var queries = [...]struct { - in string - codes []string - }{ - {"DROP TABLE IF EXISTS no_such_table", []string{"1051"}}, - {"INSERT INTO test VALUES(10,'mysql'),(NULL,'test'),(300,'Open Source')", []string{"1265", "1048", "1264", "1265"}}, - } - var err error - - var checkWarnings = func(err error, mode string, idx int) { - if err == nil { - dbt.Errorf("Expected STRICT error on query [%s] %s", mode, queries[idx].in) - } - - if warnings, ok := err.(MySQLWarnings); ok { - var codes = make([]string, len(warnings)) - for i := range warnings { - codes[i] = warnings[i].Code - } - if len(codes) != len(queries[idx].codes) { - dbt.Errorf("Unexpected STRICT error count on query [%s] %s: Wanted %v, Got %v", mode, queries[idx].in, queries[idx].codes, codes) - } - - for i := range warnings { - if codes[i] != queries[idx].codes[i] { - dbt.Errorf("Unexpected STRICT error codes on query [%s] %s: Wanted %v, Got %v", mode, queries[idx].in, queries[idx].codes, codes) - return - } - } - - } else { - dbt.Errorf("Unexpected error on query [%s] %s: %s", mode, queries[idx].in, err.Error()) - } - } - - // text protocol - for i := range queries { - _, err = dbt.db.Exec(queries[i].in) - checkWarnings(err, "text", i) - } - - var stmt *sql.Stmt - - // binary protocol - for i := range queries { - stmt, err = dbt.db.Prepare(queries[i].in) - if err != nil { - dbt.Errorf("Error on preparing query %s: %s", queries[i].in, err.Error()) - } - - _, err = stmt.Exec() - checkWarnings(err, "binary", i) - - err = stmt.Close() - if err != nil { - dbt.Errorf("Error on closing stmt for query %s: %s", queries[i].in, err.Error()) - } - } - }) -} - -func TestTLS(t *testing.T) { - tlsTest := func(dbt *DBTest) { - if err := dbt.db.Ping(); err != nil { - if err == errNoTLS { - dbt.Skip("Server does not support TLS") - } else { - dbt.Fatalf("Error on Ping: %s", err.Error()) - } - } - - rows := dbt.mustQuery("SHOW STATUS LIKE 'Ssl_cipher'") - - var variable, value *sql.RawBytes - for rows.Next() { - if err := rows.Scan(&variable, &value); err != nil { - dbt.Fatal(err.Error()) - } - - if value == nil { - dbt.Fatal("No Cipher") - } - } - } - - runTests(t, dsn+"&tls=skip-verify", tlsTest) - - // Verify that registering / using a custom cfg works - RegisterTLSConfig("custom-skip-verify", &tls.Config{ - InsecureSkipVerify: true, - }) - runTests(t, dsn+"&tls=custom-skip-verify", tlsTest) -} - -func TestReuseClosedConnection(t *testing.T) { - // this test does not use sql.database, it uses the driver directly - if !available { - t.Skipf("MySQL-Server not running on %s", netAddr) - } - - md := &MySQLDriver{} - conn, err := md.Open(dsn) - if err != nil { - t.Fatalf("Error connecting: %s", err.Error()) - } - stmt, err := conn.Prepare("DO 1") - if err != nil { - t.Fatalf("Error preparing statement: %s", err.Error()) - } - _, err = stmt.Exec(nil) - if err != nil { - t.Fatalf("Error executing statement: %s", err.Error()) - } - err = conn.Close() - if err != nil { - t.Fatalf("Error closing connection: %s", err.Error()) - } - - defer func() { - if err := recover(); err != nil { - t.Errorf("Panic after reusing a closed connection: %v", err) - } - }() - _, err = stmt.Exec(nil) - if err != nil && err != driver.ErrBadConn { - t.Errorf("Unexpected error '%s', expected '%s'", - err.Error(), driver.ErrBadConn.Error()) - } -} - -func TestCharset(t *testing.T) { - if !available { - t.Skipf("MySQL-Server not running on %s", netAddr) - } - - mustSetCharset := func(charsetParam, expected string) { - runTests(t, dsn+"&"+charsetParam, func(dbt *DBTest) { - rows := dbt.mustQuery("SELECT @@character_set_connection") - defer rows.Close() - - if !rows.Next() { - dbt.Fatalf("Error getting connection charset: %s", rows.Err()) - } - - var got string - rows.Scan(&got) - - if got != expected { - dbt.Fatalf("Expected connection charset %s but got %s", expected, got) - } - }) - } - - // non utf8 test - mustSetCharset("charset=ascii", "ascii") - - // when the first charset is invalid, use the second - mustSetCharset("charset=none,utf8", "utf8") - - // when the first charset is valid, use it - mustSetCharset("charset=ascii,utf8", "ascii") - mustSetCharset("charset=utf8,ascii", "utf8") -} - -func TestFailingCharset(t *testing.T) { - runTests(t, dsn+"&charset=none", func(dbt *DBTest) { - // run query to really establish connection... - _, err := dbt.db.Exec("SELECT 1") - if err == nil { - dbt.db.Close() - t.Fatalf("Connection must not succeed without a valid charset") - } - }) -} - -func TestRawBytesResultExceedsBuffer(t *testing.T) { - runTests(t, dsn, func(dbt *DBTest) { - // defaultBufSize from buffer.go - expected := strings.Repeat("abc", defaultBufSize) - - rows := dbt.mustQuery("SELECT '" + expected + "'") - defer rows.Close() - if !rows.Next() { - dbt.Error("expected result, got none") - } - var result sql.RawBytes - rows.Scan(&result) - if expected != string(result) { - dbt.Error("result did not match expected value") - } - }) -} - -func TestTimezoneConversion(t *testing.T) { - zones := []string{"UTC", "US/Central", "US/Pacific", "Local"} - - // Regression test for timezone handling - tzTest := func(dbt *DBTest) { - - // Create table - dbt.mustExec("CREATE TABLE test (ts TIMESTAMP)") - - // Insert local time into database (should be converted) - usCentral, _ := time.LoadLocation("US/Central") - now := time.Now().In(usCentral) - dbt.mustExec("INSERT INTO test VALUE (?)", now) - - // Retrieve time from DB - rows := dbt.mustQuery("SELECT ts FROM test") - if !rows.Next() { - dbt.Fatal("Didn't get any rows out") - } - - var nowDB time.Time - err := rows.Scan(&nowDB) - if err != nil { - dbt.Fatal("Err", err) - } - - // Check that dates match - if now.Unix() != nowDB.Unix() { - dbt.Errorf("Times don't match.\n") - dbt.Errorf(" Now(%v)=%v\n", usCentral, now) - dbt.Errorf(" Now(UTC)=%v\n", nowDB) - } - } - - for _, tz := range zones { - runTests(t, dsn+"&parseTime=true&loc="+url.QueryEscape(tz), tzTest) - } -} - -// This tests for https://github.com/go-sql-driver/mysql/pull/139 -// -// An extra (invisible) nil byte was being added to the beginning of positive -// time strings. -func TestTimeSign(t *testing.T) { - runTests(t, dsn, func(dbt *DBTest) { - var sTimes = []struct { - value string - fieldType string - }{ - {"12:34:56", "TIME"}, - {"-12:34:56", "TIME"}, - // As described in http://dev.mysql.com/doc/refman/5.6/en/fractional-seconds.html - // they *should* work, but only in 5.6+. - // { "12:34:56.789", "TIME(3)" }, - // { "-12:34:56.789", "TIME(3)" }, - } - - for _, sTime := range sTimes { - dbt.db.Exec("DROP TABLE IF EXISTS test") - dbt.mustExec("CREATE TABLE test (id INT, time_field " + sTime.fieldType + ")") - dbt.mustExec("INSERT INTO test (id, time_field) VALUES(1, '" + sTime.value + "')") - rows := dbt.mustQuery("SELECT time_field FROM test WHERE id = ?", 1) - if rows.Next() { - var oTime string - rows.Scan(&oTime) - if oTime != sTime.value { - dbt.Errorf(`time values differ: got %q, expected %q.`, oTime, sTime.value) - } - } else { - dbt.Error("expecting at least one row.") - } - } - }) -} - -// Special cases - -func TestRowsClose(t *testing.T) { - runTests(t, dsn, func(dbt *DBTest) { - rows, err := dbt.db.Query("SELECT 1") - if err != nil { - dbt.Fatal(err) - } - - err = rows.Close() - if err != nil { - dbt.Fatal(err) - } - - if rows.Next() { - dbt.Fatal("Unexpected row after rows.Close()") - } - - err = rows.Err() - if err != nil { - dbt.Fatal(err) - } - }) -} - -// dangling statements -// http://code.google.com/p/go/issues/detail?id=3865 -func TestCloseStmtBeforeRows(t *testing.T) { - runTests(t, dsn, func(dbt *DBTest) { - stmt, err := dbt.db.Prepare("SELECT 1") - if err != nil { - dbt.Fatal(err) - } - - rows, err := stmt.Query() - if err != nil { - stmt.Close() - dbt.Fatal(err) - } - defer rows.Close() - - err = stmt.Close() - if err != nil { - dbt.Fatal(err) - } - - if !rows.Next() { - dbt.Fatal("Getting row failed") - } else { - err = rows.Err() - if err != nil { - dbt.Fatal(err) - } - - var out bool - err = rows.Scan(&out) - if err != nil { - dbt.Fatalf("Error on rows.Scan(): %s", err.Error()) - } - if out != true { - dbt.Errorf("true != %t", out) - } - } - }) -} - -// It is valid to have multiple Rows for the same Stmt -// http://code.google.com/p/go/issues/detail?id=3734 -func TestStmtMultiRows(t *testing.T) { - runTests(t, dsn, func(dbt *DBTest) { - stmt, err := dbt.db.Prepare("SELECT 1 UNION SELECT 0") - if err != nil { - dbt.Fatal(err) - } - - rows1, err := stmt.Query() - if err != nil { - stmt.Close() - dbt.Fatal(err) - } - defer rows1.Close() - - rows2, err := stmt.Query() - if err != nil { - stmt.Close() - dbt.Fatal(err) - } - defer rows2.Close() - - var out bool - - // 1 - if !rows1.Next() { - dbt.Fatal("1st rows1.Next failed") - } else { - err = rows1.Err() - if err != nil { - dbt.Fatal(err) - } - - err = rows1.Scan(&out) - if err != nil { - dbt.Fatalf("Error on rows.Scan(): %s", err.Error()) - } - if out != true { - dbt.Errorf("true != %t", out) - } - } - - if !rows2.Next() { - dbt.Fatal("1st rows2.Next failed") - } else { - err = rows2.Err() - if err != nil { - dbt.Fatal(err) - } - - err = rows2.Scan(&out) - if err != nil { - dbt.Fatalf("Error on rows.Scan(): %s", err.Error()) - } - if out != true { - dbt.Errorf("true != %t", out) - } - } - - // 2 - if !rows1.Next() { - dbt.Fatal("2nd rows1.Next failed") - } else { - err = rows1.Err() - if err != nil { - dbt.Fatal(err) - } - - err = rows1.Scan(&out) - if err != nil { - dbt.Fatalf("Error on rows.Scan(): %s", err.Error()) - } - if out != false { - dbt.Errorf("false != %t", out) - } - - if rows1.Next() { - dbt.Fatal("Unexpected row on rows1") - } - err = rows1.Close() - if err != nil { - dbt.Fatal(err) - } - } - - if !rows2.Next() { - dbt.Fatal("2nd rows2.Next failed") - } else { - err = rows2.Err() - if err != nil { - dbt.Fatal(err) - } - - err = rows2.Scan(&out) - if err != nil { - dbt.Fatalf("Error on rows.Scan(): %s", err.Error()) - } - if out != false { - dbt.Errorf("false != %t", out) - } - - if rows2.Next() { - dbt.Fatal("Unexpected row on rows2") - } - err = rows2.Close() - if err != nil { - dbt.Fatal(err) - } - } - }) -} - -func TestConcurrent(t *testing.T) { - if enabled, _ := readBool(os.Getenv("MYSQL_TEST_CONCURRENT")); !enabled { - t.Skip("MYSQL_TEST_CONCURRENT env var not set") - } - - runTests(t, dsn, func(dbt *DBTest) { - var max int - err := dbt.db.QueryRow("SELECT @@max_connections").Scan(&max) - if err != nil { - dbt.Fatalf("%s", err.Error()) - } - dbt.Logf("Testing up to %d concurrent connections \r\n", max) - canStop := false - c := make(chan struct{}, max) - for i := 0; i < max; i++ { - go func(id int) { - tx, err := dbt.db.Begin() - if err != nil { - canStop = true - if err.Error() == "Error 1040: Too many connections" { - max-- - return - } else { - dbt.Fatalf("Error on Con %d: %s", id, err.Error()) - } - } - c <- struct{}{} - for !canStop { - _, err = tx.Exec("SELECT 1") - if err != nil { - canStop = true - dbt.Fatalf("Error on Con %d: %s", id, err.Error()) - } - } - err = tx.Commit() - if err != nil { - canStop = true - dbt.Fatalf("Error on Con %d: %s", id, err.Error()) - } - }(i) - } - for i := 0; i < max; i++ { - <-c - } - canStop = true - - dbt.Logf("Reached %d concurrent connections \r\n", max) - }) -} diff --git a/vendor/github.com/go-sql-driver/mysql/utils_test.go b/vendor/github.com/go-sql-driver/mysql/utils_test.go deleted file mode 100644 index d19c92731..000000000 --- a/vendor/github.com/go-sql-driver/mysql/utils_test.go +++ /dev/null @@ -1,124 +0,0 @@ -// Go MySQL Driver - A MySQL-Driver for Go's database/sql package -// -// Copyright 2013 The Go-MySQL-Driver Authors. All rights reserved. -// -// This Source Code Form is subject to the terms of the Mozilla Public -// License, v. 2.0. If a copy of the MPL was not distributed with this file, -// You can obtain one at http://mozilla.org/MPL/2.0/. - -package mysql - -import ( - "fmt" - "testing" - "time" -) - -var testDSNs = []struct { - in string - out string - loc *time.Location -}{ - {"username:password@protocol(address)/dbname?param=value", "&{user:username passwd:password net:protocol addr:address dbname:dbname params:map[param:value] loc:%p timeout:0 tls: allowAllFiles:false allowOldPasswords:false clientFoundRows:false}", time.UTC}, - {"user@unix(/path/to/socket)/dbname?charset=utf8", "&{user:user passwd: net:unix addr:/path/to/socket dbname:dbname params:map[charset:utf8] loc:%p timeout:0 tls: allowAllFiles:false allowOldPasswords:false clientFoundRows:false}", time.UTC}, - {"user:password@tcp(localhost:5555)/dbname?charset=utf8&tls=true", "&{user:user passwd:password net:tcp addr:localhost:5555 dbname:dbname params:map[charset:utf8] loc:%p timeout:0 tls: allowAllFiles:false allowOldPasswords:false clientFoundRows:false}", time.UTC}, - {"user:password@tcp(localhost:5555)/dbname?charset=utf8mb4,utf8&tls=skip-verify", "&{user:user passwd:password net:tcp addr:localhost:5555 dbname:dbname params:map[charset:utf8mb4,utf8] loc:%p timeout:0 tls: allowAllFiles:false allowOldPasswords:false clientFoundRows:false}", time.UTC}, - {"user:password@/dbname?loc=UTC&timeout=30s&allowAllFiles=1&clientFoundRows=true&allowOldPasswords=TRUE", "&{user:user passwd:password net:tcp addr:127.0.0.1:3306 dbname:dbname params:map[] loc:%p timeout:30000000000 tls: allowAllFiles:true allowOldPasswords:true clientFoundRows:true}", time.UTC}, - {"user:p@ss(word)@tcp([de:ad:be:ef::ca:fe]:80)/dbname?loc=Local", "&{user:user passwd:p@ss(word) net:tcp addr:[de:ad:be:ef::ca:fe]:80 dbname:dbname params:map[] loc:%p timeout:0 tls: allowAllFiles:false allowOldPasswords:false clientFoundRows:false}", time.Local}, - {"/dbname", "&{user: passwd: net:tcp addr:127.0.0.1:3306 dbname:dbname params:map[] loc:%p timeout:0 tls: allowAllFiles:false allowOldPasswords:false clientFoundRows:false}", time.UTC}, - {"@/", "&{user: passwd: net:tcp addr:127.0.0.1:3306 dbname: params:map[] loc:%p timeout:0 tls: allowAllFiles:false allowOldPasswords:false clientFoundRows:false}", time.UTC}, - {"/", "&{user: passwd: net:tcp addr:127.0.0.1:3306 dbname: params:map[] loc:%p timeout:0 tls: allowAllFiles:false allowOldPasswords:false clientFoundRows:false}", time.UTC}, - {"", "&{user: passwd: net:tcp addr:127.0.0.1:3306 dbname: params:map[] loc:%p timeout:0 tls: allowAllFiles:false allowOldPasswords:false clientFoundRows:false}", time.UTC}, - {"user:p@/ssword@/", "&{user:user passwd:p@/ssword net:tcp addr:127.0.0.1:3306 dbname: params:map[] loc:%p timeout:0 tls: allowAllFiles:false allowOldPasswords:false clientFoundRows:false}", time.UTC}, - {"unix/?arg=%2Fsome%2Fpath.ext", "&{user: passwd: net:unix addr:/tmp/mysql.sock dbname: params:map[arg:/some/path.ext] loc:%p timeout:0 tls: allowAllFiles:false allowOldPasswords:false clientFoundRows:false}", time.UTC}, -} - -func TestDSNParser(t *testing.T) { - var cfg *config - var err error - var res string - - for i, tst := range testDSNs { - cfg, err = parseDSN(tst.in) - if err != nil { - t.Error(err.Error()) - } - - // pointer not static - cfg.tls = nil - - res = fmt.Sprintf("%+v", cfg) - if res != fmt.Sprintf(tst.out, tst.loc) { - t.Errorf("%d. parseDSN(%q) => %q, want %q", i, tst.in, res, fmt.Sprintf(tst.out, tst.loc)) - } - } -} - -func TestDSNParserInvalid(t *testing.T) { - var invalidDSNs = []string{ - "@net(addr/", // no closing brace - "@tcp(/", // no closing brace - "tcp(/", // no closing brace - "(/", // no closing brace - "net(addr)//", // unescaped - //"/dbname?arg=/some/unescaped/path", - } - - for i, tst := range invalidDSNs { - if _, err := parseDSN(tst); err == nil { - t.Errorf("invalid DSN #%d. (%s) didn't error!", i, tst) - } - } -} - -func BenchmarkParseDSN(b *testing.B) { - b.ReportAllocs() - - for i := 0; i < b.N; i++ { - for _, tst := range testDSNs { - if _, err := parseDSN(tst.in); err != nil { - b.Error(err.Error()) - } - } - } -} - -func TestScanNullTime(t *testing.T) { - var scanTests = []struct { - in interface{} - error bool - valid bool - time time.Time - }{ - {tDate, false, true, tDate}, - {sDate, false, true, tDate}, - {[]byte(sDate), false, true, tDate}, - {tDateTime, false, true, tDateTime}, - {sDateTime, false, true, tDateTime}, - {[]byte(sDateTime), false, true, tDateTime}, - {tDate0, false, true, tDate0}, - {sDate0, false, true, tDate0}, - {[]byte(sDate0), false, true, tDate0}, - {sDateTime0, false, true, tDate0}, - {[]byte(sDateTime0), false, true, tDate0}, - {"", true, false, tDate0}, - {"1234", true, false, tDate0}, - {0, true, false, tDate0}, - } - - var nt = NullTime{} - var err error - - for _, tst := range scanTests { - err = nt.Scan(tst.in) - if (err != nil) != tst.error { - t.Errorf("%v: expected error status %t, got %t", tst.in, tst.error, (err != nil)) - } - if nt.Valid != tst.valid { - t.Errorf("%v: expected valid status %t, got %t", tst.in, tst.valid, nt.Valid) - } - if nt.Time != tst.time { - t.Errorf("%v: expected time %v, got %v", tst.in, tst.time, nt.Time) - } - } -} diff --git a/vendor/github.com/gogits/go-gogs-client/gogs.go b/vendor/github.com/gogits/go-gogs-client/gogs.go index dba1328d9..8ec21d12e 100644 --- a/vendor/github.com/gogits/go-gogs-client/gogs.go +++ b/vendor/github.com/gogits/go-gogs-client/gogs.go @@ -14,7 +14,7 @@ import ( ) func Version() string { - return "0.7.2" + return "0.7.3" } // Client represents a Gogs API client. diff --git a/vendor/github.com/gogits/go-gogs-client/repo_branch.go b/vendor/github.com/gogits/go-gogs-client/repo_branch.go new file mode 100644 index 000000000..1e5811212 --- /dev/null +++ b/vendor/github.com/gogits/go-gogs-client/repo_branch.go @@ -0,0 +1,25 @@ +// Copyright 2016 The Gogs Authors. All rights reserved. +// Use of this source code is governed by a MIT-style +// license that can be found in the LICENSE file. + +package gogs + +import ( + "fmt" +) + +// Branch represents a repository branch. +type Branch struct { + Name string `json:"name"` + Commit *PayloadCommit `json:"commit"` +} + +func (c *Client) ListRepoBranches(user, repo string) ([]*Branch, error) { + branches := make([]*Branch, 0, 10) + return branches, c.getParsedResponse("GET", fmt.Sprintf("/repos/%s/%s/branches", user, repo), nil, nil, &branches) +} + +func (c *Client) GetRepoBranch(user, repo, branch string) (*Branch, error) { + b := new(Branch) + return b, c.getParsedResponse("GET", fmt.Sprintf("/repos/%s/%s/branches/%s", user, repo, branch), nil, nil, &b) +} diff --git a/vendor/github.com/gogits/go-gogs-client/repo_hooks.go b/vendor/github.com/gogits/go-gogs-client/repo_hooks.go index fa3a1e68b..06c968735 100644 --- a/vendor/github.com/gogits/go-gogs-client/repo_hooks.go +++ b/vendor/github.com/gogits/go-gogs-client/repo_hooks.go @@ -92,16 +92,17 @@ type PayloadCommit struct { } type PayloadRepo struct { - ID int64 `json:"id"` - Name string `json:"name"` - URL string `json:"url"` - SSHURL string `json:"ssh_url"` - CloneURL string `json:"clone_url"` - Description string `json:"description"` - Website string `json:"website"` - Watchers int `json:"watchers"` - Owner *PayloadAuthor `json:"owner"` - Private bool `json:"private"` + ID int64 `json:"id"` + Name string `json:"name"` + URL string `json:"url"` + SSHURL string `json:"ssh_url"` + CloneURL string `json:"clone_url"` + Description string `json:"description"` + Website string `json:"website"` + Watchers int `json:"watchers"` + Owner *PayloadAuthor `json:"owner"` + Private bool `json:"private"` + DefaultBranch string `json:"default_branch"` } // _________ __ diff --git a/vendor/github.com/golang/protobuf/LICENSE b/vendor/github.com/golang/protobuf/LICENSE new file mode 100644 index 000000000..1b1b1921e --- /dev/null +++ b/vendor/github.com/golang/protobuf/LICENSE @@ -0,0 +1,31 @@ +Go support for Protocol Buffers - Google's data interchange format + +Copyright 2010 The Go Authors. All rights reserved. +https://github.com/golang/protobuf + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are +met: + + * Redistributions of source code must retain the above copyright +notice, this list of conditions and the following disclaimer. + * Redistributions in binary form must reproduce the above +copyright notice, this list of conditions and the following disclaimer +in the documentation and/or other materials provided with the +distribution. + * Neither the name of Google Inc. nor the names of its +contributors may be used to endorse or promote products derived from +this software without specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + diff --git a/vendor/github.com/golang/protobuf/proto/Makefile b/vendor/github.com/golang/protobuf/proto/Makefile new file mode 100644 index 000000000..f1f06564a --- /dev/null +++ b/vendor/github.com/golang/protobuf/proto/Makefile @@ -0,0 +1,43 @@ +# Go support for Protocol Buffers - Google's data interchange format +# +# Copyright 2010 The Go Authors. All rights reserved. +# https://github.com/golang/protobuf +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions are +# met: +# +# * Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# * Redistributions in binary form must reproduce the above +# copyright notice, this list of conditions and the following disclaimer +# in the documentation and/or other materials provided with the +# distribution. +# * Neither the name of Google Inc. nor the names of its +# contributors may be used to endorse or promote products derived from +# this software without specific prior written permission. +# +# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +# A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +# OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +install: + go install + +test: install generate-test-pbs + go test + + +generate-test-pbs: + make install + make -C testdata + protoc --go_out=Mtestdata/test.proto=github.com/golang/protobuf/proto/testdata:. proto3_proto/proto3.proto + make diff --git a/vendor/github.com/golang/protobuf/proto/clone.go b/vendor/github.com/golang/protobuf/proto/clone.go new file mode 100644 index 000000000..e98ddec98 --- /dev/null +++ b/vendor/github.com/golang/protobuf/proto/clone.go @@ -0,0 +1,223 @@ +// Go support for Protocol Buffers - Google's data interchange format +// +// Copyright 2011 The Go Authors. All rights reserved. +// https://github.com/golang/protobuf +// +// Redistribution and use in source and binary forms, with or without +// modification, are permitted provided that the following conditions are +// met: +// +// * Redistributions of source code must retain the above copyright +// notice, this list of conditions and the following disclaimer. +// * Redistributions in binary form must reproduce the above +// copyright notice, this list of conditions and the following disclaimer +// in the documentation and/or other materials provided with the +// distribution. +// * Neither the name of Google Inc. nor the names of its +// contributors may be used to endorse or promote products derived from +// this software without specific prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +// Protocol buffer deep copy and merge. +// TODO: RawMessage. + +package proto + +import ( + "log" + "reflect" + "strings" +) + +// Clone returns a deep copy of a protocol buffer. +func Clone(pb Message) Message { + in := reflect.ValueOf(pb) + if in.IsNil() { + return pb + } + + out := reflect.New(in.Type().Elem()) + // out is empty so a merge is a deep copy. + mergeStruct(out.Elem(), in.Elem()) + return out.Interface().(Message) +} + +// Merge merges src into dst. +// Required and optional fields that are set in src will be set to that value in dst. +// Elements of repeated fields will be appended. +// Merge panics if src and dst are not the same type, or if dst is nil. +func Merge(dst, src Message) { + in := reflect.ValueOf(src) + out := reflect.ValueOf(dst) + if out.IsNil() { + panic("proto: nil destination") + } + if in.Type() != out.Type() { + // Explicit test prior to mergeStruct so that mistyped nils will fail + panic("proto: type mismatch") + } + if in.IsNil() { + // Merging nil into non-nil is a quiet no-op + return + } + mergeStruct(out.Elem(), in.Elem()) +} + +func mergeStruct(out, in reflect.Value) { + sprop := GetProperties(in.Type()) + for i := 0; i < in.NumField(); i++ { + f := in.Type().Field(i) + if strings.HasPrefix(f.Name, "XXX_") { + continue + } + mergeAny(out.Field(i), in.Field(i), false, sprop.Prop[i]) + } + + if emIn, ok := in.Addr().Interface().(extendableProto); ok { + emOut := out.Addr().Interface().(extendableProto) + mergeExtension(emOut.ExtensionMap(), emIn.ExtensionMap()) + } + + uf := in.FieldByName("XXX_unrecognized") + if !uf.IsValid() { + return + } + uin := uf.Bytes() + if len(uin) > 0 { + out.FieldByName("XXX_unrecognized").SetBytes(append([]byte(nil), uin...)) + } +} + +// mergeAny performs a merge between two values of the same type. +// viaPtr indicates whether the values were indirected through a pointer (implying proto2). +// prop is set if this is a struct field (it may be nil). +func mergeAny(out, in reflect.Value, viaPtr bool, prop *Properties) { + if in.Type() == protoMessageType { + if !in.IsNil() { + if out.IsNil() { + out.Set(reflect.ValueOf(Clone(in.Interface().(Message)))) + } else { + Merge(out.Interface().(Message), in.Interface().(Message)) + } + } + return + } + switch in.Kind() { + case reflect.Bool, reflect.Float32, reflect.Float64, reflect.Int32, reflect.Int64, + reflect.String, reflect.Uint32, reflect.Uint64: + if !viaPtr && isProto3Zero(in) { + return + } + out.Set(in) + case reflect.Interface: + // Probably a oneof field; copy non-nil values. + if in.IsNil() { + return + } + // Allocate destination if it is not set, or set to a different type. + // Otherwise we will merge as normal. + if out.IsNil() || out.Elem().Type() != in.Elem().Type() { + out.Set(reflect.New(in.Elem().Elem().Type())) // interface -> *T -> T -> new(T) + } + mergeAny(out.Elem(), in.Elem(), false, nil) + case reflect.Map: + if in.Len() == 0 { + return + } + if out.IsNil() { + out.Set(reflect.MakeMap(in.Type())) + } + // For maps with value types of *T or []byte we need to deep copy each value. + elemKind := in.Type().Elem().Kind() + for _, key := range in.MapKeys() { + var val reflect.Value + switch elemKind { + case reflect.Ptr: + val = reflect.New(in.Type().Elem().Elem()) + mergeAny(val, in.MapIndex(key), false, nil) + case reflect.Slice: + val = in.MapIndex(key) + val = reflect.ValueOf(append([]byte{}, val.Bytes()...)) + default: + val = in.MapIndex(key) + } + out.SetMapIndex(key, val) + } + case reflect.Ptr: + if in.IsNil() { + return + } + if out.IsNil() { + out.Set(reflect.New(in.Elem().Type())) + } + mergeAny(out.Elem(), in.Elem(), true, nil) + case reflect.Slice: + if in.IsNil() { + return + } + if in.Type().Elem().Kind() == reflect.Uint8 { + // []byte is a scalar bytes field, not a repeated field. + + // Edge case: if this is in a proto3 message, a zero length + // bytes field is considered the zero value, and should not + // be merged. + if prop != nil && prop.proto3 && in.Len() == 0 { + return + } + + // Make a deep copy. + // Append to []byte{} instead of []byte(nil) so that we never end up + // with a nil result. + out.SetBytes(append([]byte{}, in.Bytes()...)) + return + } + n := in.Len() + if out.IsNil() { + out.Set(reflect.MakeSlice(in.Type(), 0, n)) + } + switch in.Type().Elem().Kind() { + case reflect.Bool, reflect.Float32, reflect.Float64, reflect.Int32, reflect.Int64, + reflect.String, reflect.Uint32, reflect.Uint64: + out.Set(reflect.AppendSlice(out, in)) + default: + for i := 0; i < n; i++ { + x := reflect.Indirect(reflect.New(in.Type().Elem())) + mergeAny(x, in.Index(i), false, nil) + out.Set(reflect.Append(out, x)) + } + } + case reflect.Struct: + mergeStruct(out, in) + default: + // unknown type, so not a protocol buffer + log.Printf("proto: don't know how to copy %v", in) + } +} + +func mergeExtension(out, in map[int32]Extension) { + for extNum, eIn := range in { + eOut := Extension{desc: eIn.desc} + if eIn.value != nil { + v := reflect.New(reflect.TypeOf(eIn.value)).Elem() + mergeAny(v, reflect.ValueOf(eIn.value), false, nil) + eOut.value = v.Interface() + } + if eIn.enc != nil { + eOut.enc = make([]byte, len(eIn.enc)) + copy(eOut.enc, eIn.enc) + } + + out[extNum] = eOut + } +} diff --git a/vendor/github.com/golang/protobuf/proto/decode.go b/vendor/github.com/golang/protobuf/proto/decode.go new file mode 100644 index 000000000..5810782fd --- /dev/null +++ b/vendor/github.com/golang/protobuf/proto/decode.go @@ -0,0 +1,867 @@ +// Go support for Protocol Buffers - Google's data interchange format +// +// Copyright 2010 The Go Authors. All rights reserved. +// https://github.com/golang/protobuf +// +// Redistribution and use in source and binary forms, with or without +// modification, are permitted provided that the following conditions are +// met: +// +// * Redistributions of source code must retain the above copyright +// notice, this list of conditions and the following disclaimer. +// * Redistributions in binary form must reproduce the above +// copyright notice, this list of conditions and the following disclaimer +// in the documentation and/or other materials provided with the +// distribution. +// * Neither the name of Google Inc. nor the names of its +// contributors may be used to endorse or promote products derived from +// this software without specific prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +package proto + +/* + * Routines for decoding protocol buffer data to construct in-memory representations. + */ + +import ( + "errors" + "fmt" + "io" + "os" + "reflect" +) + +// errOverflow is returned when an integer is too large to be represented. +var errOverflow = errors.New("proto: integer overflow") + +// ErrInternalBadWireType is returned by generated code when an incorrect +// wire type is encountered. It does not get returned to user code. +var ErrInternalBadWireType = errors.New("proto: internal error: bad wiretype for oneof") + +// The fundamental decoders that interpret bytes on the wire. +// Those that take integer types all return uint64 and are +// therefore of type valueDecoder. + +// DecodeVarint reads a varint-encoded integer from the slice. +// It returns the integer and the number of bytes consumed, or +// zero if there is not enough. +// This is the format for the +// int32, int64, uint32, uint64, bool, and enum +// protocol buffer types. +func DecodeVarint(buf []byte) (x uint64, n int) { + // x, n already 0 + for shift := uint(0); shift < 64; shift += 7 { + if n >= len(buf) { + return 0, 0 + } + b := uint64(buf[n]) + n++ + x |= (b & 0x7F) << shift + if (b & 0x80) == 0 { + return x, n + } + } + + // The number is too large to represent in a 64-bit value. + return 0, 0 +} + +// DecodeVarint reads a varint-encoded integer from the Buffer. +// This is the format for the +// int32, int64, uint32, uint64, bool, and enum +// protocol buffer types. +func (p *Buffer) DecodeVarint() (x uint64, err error) { + // x, err already 0 + + i := p.index + l := len(p.buf) + + for shift := uint(0); shift < 64; shift += 7 { + if i >= l { + err = io.ErrUnexpectedEOF + return + } + b := p.buf[i] + i++ + x |= (uint64(b) & 0x7F) << shift + if b < 0x80 { + p.index = i + return + } + } + + // The number is too large to represent in a 64-bit value. + err = errOverflow + return +} + +// DecodeFixed64 reads a 64-bit integer from the Buffer. +// This is the format for the +// fixed64, sfixed64, and double protocol buffer types. +func (p *Buffer) DecodeFixed64() (x uint64, err error) { + // x, err already 0 + i := p.index + 8 + if i < 0 || i > len(p.buf) { + err = io.ErrUnexpectedEOF + return + } + p.index = i + + x = uint64(p.buf[i-8]) + x |= uint64(p.buf[i-7]) << 8 + x |= uint64(p.buf[i-6]) << 16 + x |= uint64(p.buf[i-5]) << 24 + x |= uint64(p.buf[i-4]) << 32 + x |= uint64(p.buf[i-3]) << 40 + x |= uint64(p.buf[i-2]) << 48 + x |= uint64(p.buf[i-1]) << 56 + return +} + +// DecodeFixed32 reads a 32-bit integer from the Buffer. +// This is the format for the +// fixed32, sfixed32, and float protocol buffer types. +func (p *Buffer) DecodeFixed32() (x uint64, err error) { + // x, err already 0 + i := p.index + 4 + if i < 0 || i > len(p.buf) { + err = io.ErrUnexpectedEOF + return + } + p.index = i + + x = uint64(p.buf[i-4]) + x |= uint64(p.buf[i-3]) << 8 + x |= uint64(p.buf[i-2]) << 16 + x |= uint64(p.buf[i-1]) << 24 + return +} + +// DecodeZigzag64 reads a zigzag-encoded 64-bit integer +// from the Buffer. +// This is the format used for the sint64 protocol buffer type. +func (p *Buffer) DecodeZigzag64() (x uint64, err error) { + x, err = p.DecodeVarint() + if err != nil { + return + } + x = (x >> 1) ^ uint64((int64(x&1)<<63)>>63) + return +} + +// DecodeZigzag32 reads a zigzag-encoded 32-bit integer +// from the Buffer. +// This is the format used for the sint32 protocol buffer type. +func (p *Buffer) DecodeZigzag32() (x uint64, err error) { + x, err = p.DecodeVarint() + if err != nil { + return + } + x = uint64((uint32(x) >> 1) ^ uint32((int32(x&1)<<31)>>31)) + return +} + +// These are not ValueDecoders: they produce an array of bytes or a string. +// bytes, embedded messages + +// DecodeRawBytes reads a count-delimited byte buffer from the Buffer. +// This is the format used for the bytes protocol buffer +// type and for embedded messages. +func (p *Buffer) DecodeRawBytes(alloc bool) (buf []byte, err error) { + n, err := p.DecodeVarint() + if err != nil { + return nil, err + } + + nb := int(n) + if nb < 0 { + return nil, fmt.Errorf("proto: bad byte length %d", nb) + } + end := p.index + nb + if end < p.index || end > len(p.buf) { + return nil, io.ErrUnexpectedEOF + } + + if !alloc { + // todo: check if can get more uses of alloc=false + buf = p.buf[p.index:end] + p.index += nb + return + } + + buf = make([]byte, nb) + copy(buf, p.buf[p.index:]) + p.index += nb + return +} + +// DecodeStringBytes reads an encoded string from the Buffer. +// This is the format used for the proto2 string type. +func (p *Buffer) DecodeStringBytes() (s string, err error) { + buf, err := p.DecodeRawBytes(false) + if err != nil { + return + } + return string(buf), nil +} + +// Skip the next item in the buffer. Its wire type is decoded and presented as an argument. +// If the protocol buffer has extensions, and the field matches, add it as an extension. +// Otherwise, if the XXX_unrecognized field exists, append the skipped data there. +func (o *Buffer) skipAndSave(t reflect.Type, tag, wire int, base structPointer, unrecField field) error { + oi := o.index + + err := o.skip(t, tag, wire) + if err != nil { + return err + } + + if !unrecField.IsValid() { + return nil + } + + ptr := structPointer_Bytes(base, unrecField) + + // Add the skipped field to struct field + obuf := o.buf + + o.buf = *ptr + o.EncodeVarint(uint64(tag<<3 | wire)) + *ptr = append(o.buf, obuf[oi:o.index]...) + + o.buf = obuf + + return nil +} + +// Skip the next item in the buffer. Its wire type is decoded and presented as an argument. +func (o *Buffer) skip(t reflect.Type, tag, wire int) error { + + var u uint64 + var err error + + switch wire { + case WireVarint: + _, err = o.DecodeVarint() + case WireFixed64: + _, err = o.DecodeFixed64() + case WireBytes: + _, err = o.DecodeRawBytes(false) + case WireFixed32: + _, err = o.DecodeFixed32() + case WireStartGroup: + for { + u, err = o.DecodeVarint() + if err != nil { + break + } + fwire := int(u & 0x7) + if fwire == WireEndGroup { + break + } + ftag := int(u >> 3) + err = o.skip(t, ftag, fwire) + if err != nil { + break + } + } + default: + err = fmt.Errorf("proto: can't skip unknown wire type %d for %s", wire, t) + } + return err +} + +// Unmarshaler is the interface representing objects that can +// unmarshal themselves. The method should reset the receiver before +// decoding starts. The argument points to data that may be +// overwritten, so implementations should not keep references to the +// buffer. +type Unmarshaler interface { + Unmarshal([]byte) error +} + +// Unmarshal parses the protocol buffer representation in buf and places the +// decoded result in pb. If the struct underlying pb does not match +// the data in buf, the results can be unpredictable. +// +// Unmarshal resets pb before starting to unmarshal, so any +// existing data in pb is always removed. Use UnmarshalMerge +// to preserve and append to existing data. +func Unmarshal(buf []byte, pb Message) error { + pb.Reset() + return UnmarshalMerge(buf, pb) +} + +// UnmarshalMerge parses the protocol buffer representation in buf and +// writes the decoded result to pb. If the struct underlying pb does not match +// the data in buf, the results can be unpredictable. +// +// UnmarshalMerge merges into existing data in pb. +// Most code should use Unmarshal instead. +func UnmarshalMerge(buf []byte, pb Message) error { + // If the object can unmarshal itself, let it. + if u, ok := pb.(Unmarshaler); ok { + return u.Unmarshal(buf) + } + return NewBuffer(buf).Unmarshal(pb) +} + +// DecodeMessage reads a count-delimited message from the Buffer. +func (p *Buffer) DecodeMessage(pb Message) error { + enc, err := p.DecodeRawBytes(false) + if err != nil { + return err + } + return NewBuffer(enc).Unmarshal(pb) +} + +// DecodeGroup reads a tag-delimited group from the Buffer. +func (p *Buffer) DecodeGroup(pb Message) error { + typ, base, err := getbase(pb) + if err != nil { + return err + } + return p.unmarshalType(typ.Elem(), GetProperties(typ.Elem()), true, base) +} + +// Unmarshal parses the protocol buffer representation in the +// Buffer and places the decoded result in pb. If the struct +// underlying pb does not match the data in the buffer, the results can be +// unpredictable. +func (p *Buffer) Unmarshal(pb Message) error { + // If the object can unmarshal itself, let it. + if u, ok := pb.(Unmarshaler); ok { + err := u.Unmarshal(p.buf[p.index:]) + p.index = len(p.buf) + return err + } + + typ, base, err := getbase(pb) + if err != nil { + return err + } + + err = p.unmarshalType(typ.Elem(), GetProperties(typ.Elem()), false, base) + + if collectStats { + stats.Decode++ + } + + return err +} + +// unmarshalType does the work of unmarshaling a structure. +func (o *Buffer) unmarshalType(st reflect.Type, prop *StructProperties, is_group bool, base structPointer) error { + var state errorState + required, reqFields := prop.reqCount, uint64(0) + + var err error + for err == nil && o.index < len(o.buf) { + oi := o.index + var u uint64 + u, err = o.DecodeVarint() + if err != nil { + break + } + wire := int(u & 0x7) + if wire == WireEndGroup { + if is_group { + return nil // input is satisfied + } + return fmt.Errorf("proto: %s: wiretype end group for non-group", st) + } + tag := int(u >> 3) + if tag <= 0 { + return fmt.Errorf("proto: %s: illegal tag %d (wire type %d)", st, tag, wire) + } + fieldnum, ok := prop.decoderTags.get(tag) + if !ok { + // Maybe it's an extension? + if prop.extendable { + if e := structPointer_Interface(base, st).(extendableProto); isExtensionField(e, int32(tag)) { + if err = o.skip(st, tag, wire); err == nil { + ext := e.ExtensionMap()[int32(tag)] // may be missing + ext.enc = append(ext.enc, o.buf[oi:o.index]...) + e.ExtensionMap()[int32(tag)] = ext + } + continue + } + } + // Maybe it's a oneof? + if prop.oneofUnmarshaler != nil { + m := structPointer_Interface(base, st).(Message) + // First return value indicates whether tag is a oneof field. + ok, err = prop.oneofUnmarshaler(m, tag, wire, o) + if err == ErrInternalBadWireType { + // Map the error to something more descriptive. + // Do the formatting here to save generated code space. + err = fmt.Errorf("bad wiretype for oneof field in %T", m) + } + if ok { + continue + } + } + err = o.skipAndSave(st, tag, wire, base, prop.unrecField) + continue + } + p := prop.Prop[fieldnum] + + if p.dec == nil { + fmt.Fprintf(os.Stderr, "proto: no protobuf decoder for %s.%s\n", st, st.Field(fieldnum).Name) + continue + } + dec := p.dec + if wire != WireStartGroup && wire != p.WireType { + if wire == WireBytes && p.packedDec != nil { + // a packable field + dec = p.packedDec + } else { + err = fmt.Errorf("proto: bad wiretype for field %s.%s: got wiretype %d, want %d", st, st.Field(fieldnum).Name, wire, p.WireType) + continue + } + } + decErr := dec(o, p, base) + if decErr != nil && !state.shouldContinue(decErr, p) { + err = decErr + } + if err == nil && p.Required { + // Successfully decoded a required field. + if tag <= 64 { + // use bitmap for fields 1-64 to catch field reuse. + var mask uint64 = 1 << uint64(tag-1) + if reqFields&mask == 0 { + // new required field + reqFields |= mask + required-- + } + } else { + // This is imprecise. It can be fooled by a required field + // with a tag > 64 that is encoded twice; that's very rare. + // A fully correct implementation would require allocating + // a data structure, which we would like to avoid. + required-- + } + } + } + if err == nil { + if is_group { + return io.ErrUnexpectedEOF + } + if state.err != nil { + return state.err + } + if required > 0 { + // Not enough information to determine the exact field. If we use extra + // CPU, we could determine the field only if the missing required field + // has a tag <= 64 and we check reqFields. + return &RequiredNotSetError{"{Unknown}"} + } + } + return err +} + +// Individual type decoders +// For each, +// u is the decoded value, +// v is a pointer to the field (pointer) in the struct + +// Sizes of the pools to allocate inside the Buffer. +// The goal is modest amortization and allocation +// on at least 16-byte boundaries. +const ( + boolPoolSize = 16 + uint32PoolSize = 8 + uint64PoolSize = 4 +) + +// Decode a bool. +func (o *Buffer) dec_bool(p *Properties, base structPointer) error { + u, err := p.valDec(o) + if err != nil { + return err + } + if len(o.bools) == 0 { + o.bools = make([]bool, boolPoolSize) + } + o.bools[0] = u != 0 + *structPointer_Bool(base, p.field) = &o.bools[0] + o.bools = o.bools[1:] + return nil +} + +func (o *Buffer) dec_proto3_bool(p *Properties, base structPointer) error { + u, err := p.valDec(o) + if err != nil { + return err + } + *structPointer_BoolVal(base, p.field) = u != 0 + return nil +} + +// Decode an int32. +func (o *Buffer) dec_int32(p *Properties, base structPointer) error { + u, err := p.valDec(o) + if err != nil { + return err + } + word32_Set(structPointer_Word32(base, p.field), o, uint32(u)) + return nil +} + +func (o *Buffer) dec_proto3_int32(p *Properties, base structPointer) error { + u, err := p.valDec(o) + if err != nil { + return err + } + word32Val_Set(structPointer_Word32Val(base, p.field), uint32(u)) + return nil +} + +// Decode an int64. +func (o *Buffer) dec_int64(p *Properties, base structPointer) error { + u, err := p.valDec(o) + if err != nil { + return err + } + word64_Set(structPointer_Word64(base, p.field), o, u) + return nil +} + +func (o *Buffer) dec_proto3_int64(p *Properties, base structPointer) error { + u, err := p.valDec(o) + if err != nil { + return err + } + word64Val_Set(structPointer_Word64Val(base, p.field), o, u) + return nil +} + +// Decode a string. +func (o *Buffer) dec_string(p *Properties, base structPointer) error { + s, err := o.DecodeStringBytes() + if err != nil { + return err + } + *structPointer_String(base, p.field) = &s + return nil +} + +func (o *Buffer) dec_proto3_string(p *Properties, base structPointer) error { + s, err := o.DecodeStringBytes() + if err != nil { + return err + } + *structPointer_StringVal(base, p.field) = s + return nil +} + +// Decode a slice of bytes ([]byte). +func (o *Buffer) dec_slice_byte(p *Properties, base structPointer) error { + b, err := o.DecodeRawBytes(true) + if err != nil { + return err + } + *structPointer_Bytes(base, p.field) = b + return nil +} + +// Decode a slice of bools ([]bool). +func (o *Buffer) dec_slice_bool(p *Properties, base structPointer) error { + u, err := p.valDec(o) + if err != nil { + return err + } + v := structPointer_BoolSlice(base, p.field) + *v = append(*v, u != 0) + return nil +} + +// Decode a slice of bools ([]bool) in packed format. +func (o *Buffer) dec_slice_packed_bool(p *Properties, base structPointer) error { + v := structPointer_BoolSlice(base, p.field) + + nn, err := o.DecodeVarint() + if err != nil { + return err + } + nb := int(nn) // number of bytes of encoded bools + fin := o.index + nb + if fin < o.index { + return errOverflow + } + + y := *v + for o.index < fin { + u, err := p.valDec(o) + if err != nil { + return err + } + y = append(y, u != 0) + } + + *v = y + return nil +} + +// Decode a slice of int32s ([]int32). +func (o *Buffer) dec_slice_int32(p *Properties, base structPointer) error { + u, err := p.valDec(o) + if err != nil { + return err + } + structPointer_Word32Slice(base, p.field).Append(uint32(u)) + return nil +} + +// Decode a slice of int32s ([]int32) in packed format. +func (o *Buffer) dec_slice_packed_int32(p *Properties, base structPointer) error { + v := structPointer_Word32Slice(base, p.field) + + nn, err := o.DecodeVarint() + if err != nil { + return err + } + nb := int(nn) // number of bytes of encoded int32s + + fin := o.index + nb + if fin < o.index { + return errOverflow + } + for o.index < fin { + u, err := p.valDec(o) + if err != nil { + return err + } + v.Append(uint32(u)) + } + return nil +} + +// Decode a slice of int64s ([]int64). +func (o *Buffer) dec_slice_int64(p *Properties, base structPointer) error { + u, err := p.valDec(o) + if err != nil { + return err + } + + structPointer_Word64Slice(base, p.field).Append(u) + return nil +} + +// Decode a slice of int64s ([]int64) in packed format. +func (o *Buffer) dec_slice_packed_int64(p *Properties, base structPointer) error { + v := structPointer_Word64Slice(base, p.field) + + nn, err := o.DecodeVarint() + if err != nil { + return err + } + nb := int(nn) // number of bytes of encoded int64s + + fin := o.index + nb + if fin < o.index { + return errOverflow + } + for o.index < fin { + u, err := p.valDec(o) + if err != nil { + return err + } + v.Append(u) + } + return nil +} + +// Decode a slice of strings ([]string). +func (o *Buffer) dec_slice_string(p *Properties, base structPointer) error { + s, err := o.DecodeStringBytes() + if err != nil { + return err + } + v := structPointer_StringSlice(base, p.field) + *v = append(*v, s) + return nil +} + +// Decode a slice of slice of bytes ([][]byte). +func (o *Buffer) dec_slice_slice_byte(p *Properties, base structPointer) error { + b, err := o.DecodeRawBytes(true) + if err != nil { + return err + } + v := structPointer_BytesSlice(base, p.field) + *v = append(*v, b) + return nil +} + +// Decode a map field. +func (o *Buffer) dec_new_map(p *Properties, base structPointer) error { + raw, err := o.DecodeRawBytes(false) + if err != nil { + return err + } + oi := o.index // index at the end of this map entry + o.index -= len(raw) // move buffer back to start of map entry + + mptr := structPointer_NewAt(base, p.field, p.mtype) // *map[K]V + if mptr.Elem().IsNil() { + mptr.Elem().Set(reflect.MakeMap(mptr.Type().Elem())) + } + v := mptr.Elem() // map[K]V + + // Prepare addressable doubly-indirect placeholders for the key and value types. + // See enc_new_map for why. + keyptr := reflect.New(reflect.PtrTo(p.mtype.Key())).Elem() // addressable *K + keybase := toStructPointer(keyptr.Addr()) // **K + + var valbase structPointer + var valptr reflect.Value + switch p.mtype.Elem().Kind() { + case reflect.Slice: + // []byte + var dummy []byte + valptr = reflect.ValueOf(&dummy) // *[]byte + valbase = toStructPointer(valptr) // *[]byte + case reflect.Ptr: + // message; valptr is **Msg; need to allocate the intermediate pointer + valptr = reflect.New(reflect.PtrTo(p.mtype.Elem())).Elem() // addressable *V + valptr.Set(reflect.New(valptr.Type().Elem())) + valbase = toStructPointer(valptr) + default: + // everything else + valptr = reflect.New(reflect.PtrTo(p.mtype.Elem())).Elem() // addressable *V + valbase = toStructPointer(valptr.Addr()) // **V + } + + // Decode. + // This parses a restricted wire format, namely the encoding of a message + // with two fields. See enc_new_map for the format. + for o.index < oi { + // tagcode for key and value properties are always a single byte + // because they have tags 1 and 2. + tagcode := o.buf[o.index] + o.index++ + switch tagcode { + case p.mkeyprop.tagcode[0]: + if err := p.mkeyprop.dec(o, p.mkeyprop, keybase); err != nil { + return err + } + case p.mvalprop.tagcode[0]: + if err := p.mvalprop.dec(o, p.mvalprop, valbase); err != nil { + return err + } + default: + // TODO: Should we silently skip this instead? + return fmt.Errorf("proto: bad map data tag %d", raw[0]) + } + } + keyelem, valelem := keyptr.Elem(), valptr.Elem() + if !keyelem.IsValid() || !valelem.IsValid() { + // We did not decode the key or the value in the map entry. + // Either way, it's an invalid map entry. + return fmt.Errorf("proto: bad map data: missing key/val") + } + + v.SetMapIndex(keyelem, valelem) + return nil +} + +// Decode a group. +func (o *Buffer) dec_struct_group(p *Properties, base structPointer) error { + bas := structPointer_GetStructPointer(base, p.field) + if structPointer_IsNil(bas) { + // allocate new nested message + bas = toStructPointer(reflect.New(p.stype)) + structPointer_SetStructPointer(base, p.field, bas) + } + return o.unmarshalType(p.stype, p.sprop, true, bas) +} + +// Decode an embedded message. +func (o *Buffer) dec_struct_message(p *Properties, base structPointer) (err error) { + raw, e := o.DecodeRawBytes(false) + if e != nil { + return e + } + + bas := structPointer_GetStructPointer(base, p.field) + if structPointer_IsNil(bas) { + // allocate new nested message + bas = toStructPointer(reflect.New(p.stype)) + structPointer_SetStructPointer(base, p.field, bas) + } + + // If the object can unmarshal itself, let it. + if p.isUnmarshaler { + iv := structPointer_Interface(bas, p.stype) + return iv.(Unmarshaler).Unmarshal(raw) + } + + obuf := o.buf + oi := o.index + o.buf = raw + o.index = 0 + + err = o.unmarshalType(p.stype, p.sprop, false, bas) + o.buf = obuf + o.index = oi + + return err +} + +// Decode a slice of embedded messages. +func (o *Buffer) dec_slice_struct_message(p *Properties, base structPointer) error { + return o.dec_slice_struct(p, false, base) +} + +// Decode a slice of embedded groups. +func (o *Buffer) dec_slice_struct_group(p *Properties, base structPointer) error { + return o.dec_slice_struct(p, true, base) +} + +// Decode a slice of structs ([]*struct). +func (o *Buffer) dec_slice_struct(p *Properties, is_group bool, base structPointer) error { + v := reflect.New(p.stype) + bas := toStructPointer(v) + structPointer_StructPointerSlice(base, p.field).Append(bas) + + if is_group { + err := o.unmarshalType(p.stype, p.sprop, is_group, bas) + return err + } + + raw, err := o.DecodeRawBytes(false) + if err != nil { + return err + } + + // If the object can unmarshal itself, let it. + if p.isUnmarshaler { + iv := v.Interface() + return iv.(Unmarshaler).Unmarshal(raw) + } + + obuf := o.buf + oi := o.index + o.buf = raw + o.index = 0 + + err = o.unmarshalType(p.stype, p.sprop, is_group, bas) + + o.buf = obuf + o.index = oi + + return err +} diff --git a/vendor/github.com/golang/protobuf/proto/encode.go b/vendor/github.com/golang/protobuf/proto/encode.go new file mode 100644 index 000000000..231b07401 --- /dev/null +++ b/vendor/github.com/golang/protobuf/proto/encode.go @@ -0,0 +1,1325 @@ +// Go support for Protocol Buffers - Google's data interchange format +// +// Copyright 2010 The Go Authors. All rights reserved. +// https://github.com/golang/protobuf +// +// Redistribution and use in source and binary forms, with or without +// modification, are permitted provided that the following conditions are +// met: +// +// * Redistributions of source code must retain the above copyright +// notice, this list of conditions and the following disclaimer. +// * Redistributions in binary form must reproduce the above +// copyright notice, this list of conditions and the following disclaimer +// in the documentation and/or other materials provided with the +// distribution. +// * Neither the name of Google Inc. nor the names of its +// contributors may be used to endorse or promote products derived from +// this software without specific prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +package proto + +/* + * Routines for encoding data into the wire format for protocol buffers. + */ + +import ( + "errors" + "fmt" + "reflect" + "sort" +) + +// RequiredNotSetError is the error returned if Marshal is called with +// a protocol buffer struct whose required fields have not +// all been initialized. It is also the error returned if Unmarshal is +// called with an encoded protocol buffer that does not include all the +// required fields. +// +// When printed, RequiredNotSetError reports the first unset required field in a +// message. If the field cannot be precisely determined, it is reported as +// "{Unknown}". +type RequiredNotSetError struct { + field string +} + +func (e *RequiredNotSetError) Error() string { + return fmt.Sprintf("proto: required field %q not set", e.field) +} + +var ( + // errRepeatedHasNil is the error returned if Marshal is called with + // a struct with a repeated field containing a nil element. + errRepeatedHasNil = errors.New("proto: repeated field has nil element") + + // ErrNil is the error returned if Marshal is called with nil. + ErrNil = errors.New("proto: Marshal called with nil") +) + +// The fundamental encoders that put bytes on the wire. +// Those that take integer types all accept uint64 and are +// therefore of type valueEncoder. + +const maxVarintBytes = 10 // maximum length of a varint + +// EncodeVarint returns the varint encoding of x. +// This is the format for the +// int32, int64, uint32, uint64, bool, and enum +// protocol buffer types. +// Not used by the package itself, but helpful to clients +// wishing to use the same encoding. +func EncodeVarint(x uint64) []byte { + var buf [maxVarintBytes]byte + var n int + for n = 0; x > 127; n++ { + buf[n] = 0x80 | uint8(x&0x7F) + x >>= 7 + } + buf[n] = uint8(x) + n++ + return buf[0:n] +} + +// EncodeVarint writes a varint-encoded integer to the Buffer. +// This is the format for the +// int32, int64, uint32, uint64, bool, and enum +// protocol buffer types. +func (p *Buffer) EncodeVarint(x uint64) error { + for x >= 1<<7 { + p.buf = append(p.buf, uint8(x&0x7f|0x80)) + x >>= 7 + } + p.buf = append(p.buf, uint8(x)) + return nil +} + +// SizeVarint returns the varint encoding size of an integer. +func SizeVarint(x uint64) int { + return sizeVarint(x) +} + +func sizeVarint(x uint64) (n int) { + for { + n++ + x >>= 7 + if x == 0 { + break + } + } + return n +} + +// EncodeFixed64 writes a 64-bit integer to the Buffer. +// This is the format for the +// fixed64, sfixed64, and double protocol buffer types. +func (p *Buffer) EncodeFixed64(x uint64) error { + p.buf = append(p.buf, + uint8(x), + uint8(x>>8), + uint8(x>>16), + uint8(x>>24), + uint8(x>>32), + uint8(x>>40), + uint8(x>>48), + uint8(x>>56)) + return nil +} + +func sizeFixed64(x uint64) int { + return 8 +} + +// EncodeFixed32 writes a 32-bit integer to the Buffer. +// This is the format for the +// fixed32, sfixed32, and float protocol buffer types. +func (p *Buffer) EncodeFixed32(x uint64) error { + p.buf = append(p.buf, + uint8(x), + uint8(x>>8), + uint8(x>>16), + uint8(x>>24)) + return nil +} + +func sizeFixed32(x uint64) int { + return 4 +} + +// EncodeZigzag64 writes a zigzag-encoded 64-bit integer +// to the Buffer. +// This is the format used for the sint64 protocol buffer type. +func (p *Buffer) EncodeZigzag64(x uint64) error { + // use signed number to get arithmetic right shift. + return p.EncodeVarint(uint64((x << 1) ^ uint64((int64(x) >> 63)))) +} + +func sizeZigzag64(x uint64) int { + return sizeVarint(uint64((x << 1) ^ uint64((int64(x) >> 63)))) +} + +// EncodeZigzag32 writes a zigzag-encoded 32-bit integer +// to the Buffer. +// This is the format used for the sint32 protocol buffer type. +func (p *Buffer) EncodeZigzag32(x uint64) error { + // use signed number to get arithmetic right shift. + return p.EncodeVarint(uint64((uint32(x) << 1) ^ uint32((int32(x) >> 31)))) +} + +func sizeZigzag32(x uint64) int { + return sizeVarint(uint64((uint32(x) << 1) ^ uint32((int32(x) >> 31)))) +} + +// EncodeRawBytes writes a count-delimited byte buffer to the Buffer. +// This is the format used for the bytes protocol buffer +// type and for embedded messages. +func (p *Buffer) EncodeRawBytes(b []byte) error { + p.EncodeVarint(uint64(len(b))) + p.buf = append(p.buf, b...) + return nil +} + +func sizeRawBytes(b []byte) int { + return sizeVarint(uint64(len(b))) + + len(b) +} + +// EncodeStringBytes writes an encoded string to the Buffer. +// This is the format used for the proto2 string type. +func (p *Buffer) EncodeStringBytes(s string) error { + p.EncodeVarint(uint64(len(s))) + p.buf = append(p.buf, s...) + return nil +} + +func sizeStringBytes(s string) int { + return sizeVarint(uint64(len(s))) + + len(s) +} + +// Marshaler is the interface representing objects that can marshal themselves. +type Marshaler interface { + Marshal() ([]byte, error) +} + +// Marshal takes the protocol buffer +// and encodes it into the wire format, returning the data. +func Marshal(pb Message) ([]byte, error) { + // Can the object marshal itself? + if m, ok := pb.(Marshaler); ok { + return m.Marshal() + } + p := NewBuffer(nil) + err := p.Marshal(pb) + var state errorState + if err != nil && !state.shouldContinue(err, nil) { + return nil, err + } + if p.buf == nil && err == nil { + // Return a non-nil slice on success. + return []byte{}, nil + } + return p.buf, err +} + +// EncodeMessage writes the protocol buffer to the Buffer, +// prefixed by a varint-encoded length. +func (p *Buffer) EncodeMessage(pb Message) error { + t, base, err := getbase(pb) + if structPointer_IsNil(base) { + return ErrNil + } + if err == nil { + var state errorState + err = p.enc_len_struct(GetProperties(t.Elem()), base, &state) + } + return err +} + +// Marshal takes the protocol buffer +// and encodes it into the wire format, writing the result to the +// Buffer. +func (p *Buffer) Marshal(pb Message) error { + // Can the object marshal itself? + if m, ok := pb.(Marshaler); ok { + data, err := m.Marshal() + if err != nil { + return err + } + p.buf = append(p.buf, data...) + return nil + } + + t, base, err := getbase(pb) + if structPointer_IsNil(base) { + return ErrNil + } + if err == nil { + err = p.enc_struct(GetProperties(t.Elem()), base) + } + + if collectStats { + stats.Encode++ + } + + return err +} + +// Size returns the encoded size of a protocol buffer. +func Size(pb Message) (n int) { + // Can the object marshal itself? If so, Size is slow. + // TODO: add Size to Marshaler, or add a Sizer interface. + if m, ok := pb.(Marshaler); ok { + b, _ := m.Marshal() + return len(b) + } + + t, base, err := getbase(pb) + if structPointer_IsNil(base) { + return 0 + } + if err == nil { + n = size_struct(GetProperties(t.Elem()), base) + } + + if collectStats { + stats.Size++ + } + + return +} + +// Individual type encoders. + +// Encode a bool. +func (o *Buffer) enc_bool(p *Properties, base structPointer) error { + v := *structPointer_Bool(base, p.field) + if v == nil { + return ErrNil + } + x := 0 + if *v { + x = 1 + } + o.buf = append(o.buf, p.tagcode...) + p.valEnc(o, uint64(x)) + return nil +} + +func (o *Buffer) enc_proto3_bool(p *Properties, base structPointer) error { + v := *structPointer_BoolVal(base, p.field) + if !v { + return ErrNil + } + o.buf = append(o.buf, p.tagcode...) + p.valEnc(o, 1) + return nil +} + +func size_bool(p *Properties, base structPointer) int { + v := *structPointer_Bool(base, p.field) + if v == nil { + return 0 + } + return len(p.tagcode) + 1 // each bool takes exactly one byte +} + +func size_proto3_bool(p *Properties, base structPointer) int { + v := *structPointer_BoolVal(base, p.field) + if !v && !p.oneof { + return 0 + } + return len(p.tagcode) + 1 // each bool takes exactly one byte +} + +// Encode an int32. +func (o *Buffer) enc_int32(p *Properties, base structPointer) error { + v := structPointer_Word32(base, p.field) + if word32_IsNil(v) { + return ErrNil + } + x := int32(word32_Get(v)) // permit sign extension to use full 64-bit range + o.buf = append(o.buf, p.tagcode...) + p.valEnc(o, uint64(x)) + return nil +} + +func (o *Buffer) enc_proto3_int32(p *Properties, base structPointer) error { + v := structPointer_Word32Val(base, p.field) + x := int32(word32Val_Get(v)) // permit sign extension to use full 64-bit range + if x == 0 { + return ErrNil + } + o.buf = append(o.buf, p.tagcode...) + p.valEnc(o, uint64(x)) + return nil +} + +func size_int32(p *Properties, base structPointer) (n int) { + v := structPointer_Word32(base, p.field) + if word32_IsNil(v) { + return 0 + } + x := int32(word32_Get(v)) // permit sign extension to use full 64-bit range + n += len(p.tagcode) + n += p.valSize(uint64(x)) + return +} + +func size_proto3_int32(p *Properties, base structPointer) (n int) { + v := structPointer_Word32Val(base, p.field) + x := int32(word32Val_Get(v)) // permit sign extension to use full 64-bit range + if x == 0 && !p.oneof { + return 0 + } + n += len(p.tagcode) + n += p.valSize(uint64(x)) + return +} + +// Encode a uint32. +// Exactly the same as int32, except for no sign extension. +func (o *Buffer) enc_uint32(p *Properties, base structPointer) error { + v := structPointer_Word32(base, p.field) + if word32_IsNil(v) { + return ErrNil + } + x := word32_Get(v) + o.buf = append(o.buf, p.tagcode...) + p.valEnc(o, uint64(x)) + return nil +} + +func (o *Buffer) enc_proto3_uint32(p *Properties, base structPointer) error { + v := structPointer_Word32Val(base, p.field) + x := word32Val_Get(v) + if x == 0 { + return ErrNil + } + o.buf = append(o.buf, p.tagcode...) + p.valEnc(o, uint64(x)) + return nil +} + +func size_uint32(p *Properties, base structPointer) (n int) { + v := structPointer_Word32(base, p.field) + if word32_IsNil(v) { + return 0 + } + x := word32_Get(v) + n += len(p.tagcode) + n += p.valSize(uint64(x)) + return +} + +func size_proto3_uint32(p *Properties, base structPointer) (n int) { + v := structPointer_Word32Val(base, p.field) + x := word32Val_Get(v) + if x == 0 && !p.oneof { + return 0 + } + n += len(p.tagcode) + n += p.valSize(uint64(x)) + return +} + +// Encode an int64. +func (o *Buffer) enc_int64(p *Properties, base structPointer) error { + v := structPointer_Word64(base, p.field) + if word64_IsNil(v) { + return ErrNil + } + x := word64_Get(v) + o.buf = append(o.buf, p.tagcode...) + p.valEnc(o, x) + return nil +} + +func (o *Buffer) enc_proto3_int64(p *Properties, base structPointer) error { + v := structPointer_Word64Val(base, p.field) + x := word64Val_Get(v) + if x == 0 { + return ErrNil + } + o.buf = append(o.buf, p.tagcode...) + p.valEnc(o, x) + return nil +} + +func size_int64(p *Properties, base structPointer) (n int) { + v := structPointer_Word64(base, p.field) + if word64_IsNil(v) { + return 0 + } + x := word64_Get(v) + n += len(p.tagcode) + n += p.valSize(x) + return +} + +func size_proto3_int64(p *Properties, base structPointer) (n int) { + v := structPointer_Word64Val(base, p.field) + x := word64Val_Get(v) + if x == 0 && !p.oneof { + return 0 + } + n += len(p.tagcode) + n += p.valSize(x) + return +} + +// Encode a string. +func (o *Buffer) enc_string(p *Properties, base structPointer) error { + v := *structPointer_String(base, p.field) + if v == nil { + return ErrNil + } + x := *v + o.buf = append(o.buf, p.tagcode...) + o.EncodeStringBytes(x) + return nil +} + +func (o *Buffer) enc_proto3_string(p *Properties, base structPointer) error { + v := *structPointer_StringVal(base, p.field) + if v == "" { + return ErrNil + } + o.buf = append(o.buf, p.tagcode...) + o.EncodeStringBytes(v) + return nil +} + +func size_string(p *Properties, base structPointer) (n int) { + v := *structPointer_String(base, p.field) + if v == nil { + return 0 + } + x := *v + n += len(p.tagcode) + n += sizeStringBytes(x) + return +} + +func size_proto3_string(p *Properties, base structPointer) (n int) { + v := *structPointer_StringVal(base, p.field) + if v == "" && !p.oneof { + return 0 + } + n += len(p.tagcode) + n += sizeStringBytes(v) + return +} + +// All protocol buffer fields are nillable, but be careful. +func isNil(v reflect.Value) bool { + switch v.Kind() { + case reflect.Interface, reflect.Map, reflect.Ptr, reflect.Slice: + return v.IsNil() + } + return false +} + +// Encode a message struct. +func (o *Buffer) enc_struct_message(p *Properties, base structPointer) error { + var state errorState + structp := structPointer_GetStructPointer(base, p.field) + if structPointer_IsNil(structp) { + return ErrNil + } + + // Can the object marshal itself? + if p.isMarshaler { + m := structPointer_Interface(structp, p.stype).(Marshaler) + data, err := m.Marshal() + if err != nil && !state.shouldContinue(err, nil) { + return err + } + o.buf = append(o.buf, p.tagcode...) + o.EncodeRawBytes(data) + return state.err + } + + o.buf = append(o.buf, p.tagcode...) + return o.enc_len_struct(p.sprop, structp, &state) +} + +func size_struct_message(p *Properties, base structPointer) int { + structp := structPointer_GetStructPointer(base, p.field) + if structPointer_IsNil(structp) { + return 0 + } + + // Can the object marshal itself? + if p.isMarshaler { + m := structPointer_Interface(structp, p.stype).(Marshaler) + data, _ := m.Marshal() + n0 := len(p.tagcode) + n1 := sizeRawBytes(data) + return n0 + n1 + } + + n0 := len(p.tagcode) + n1 := size_struct(p.sprop, structp) + n2 := sizeVarint(uint64(n1)) // size of encoded length + return n0 + n1 + n2 +} + +// Encode a group struct. +func (o *Buffer) enc_struct_group(p *Properties, base structPointer) error { + var state errorState + b := structPointer_GetStructPointer(base, p.field) + if structPointer_IsNil(b) { + return ErrNil + } + + o.EncodeVarint(uint64((p.Tag << 3) | WireStartGroup)) + err := o.enc_struct(p.sprop, b) + if err != nil && !state.shouldContinue(err, nil) { + return err + } + o.EncodeVarint(uint64((p.Tag << 3) | WireEndGroup)) + return state.err +} + +func size_struct_group(p *Properties, base structPointer) (n int) { + b := structPointer_GetStructPointer(base, p.field) + if structPointer_IsNil(b) { + return 0 + } + + n += sizeVarint(uint64((p.Tag << 3) | WireStartGroup)) + n += size_struct(p.sprop, b) + n += sizeVarint(uint64((p.Tag << 3) | WireEndGroup)) + return +} + +// Encode a slice of bools ([]bool). +func (o *Buffer) enc_slice_bool(p *Properties, base structPointer) error { + s := *structPointer_BoolSlice(base, p.field) + l := len(s) + if l == 0 { + return ErrNil + } + for _, x := range s { + o.buf = append(o.buf, p.tagcode...) + v := uint64(0) + if x { + v = 1 + } + p.valEnc(o, v) + } + return nil +} + +func size_slice_bool(p *Properties, base structPointer) int { + s := *structPointer_BoolSlice(base, p.field) + l := len(s) + if l == 0 { + return 0 + } + return l * (len(p.tagcode) + 1) // each bool takes exactly one byte +} + +// Encode a slice of bools ([]bool) in packed format. +func (o *Buffer) enc_slice_packed_bool(p *Properties, base structPointer) error { + s := *structPointer_BoolSlice(base, p.field) + l := len(s) + if l == 0 { + return ErrNil + } + o.buf = append(o.buf, p.tagcode...) + o.EncodeVarint(uint64(l)) // each bool takes exactly one byte + for _, x := range s { + v := uint64(0) + if x { + v = 1 + } + p.valEnc(o, v) + } + return nil +} + +func size_slice_packed_bool(p *Properties, base structPointer) (n int) { + s := *structPointer_BoolSlice(base, p.field) + l := len(s) + if l == 0 { + return 0 + } + n += len(p.tagcode) + n += sizeVarint(uint64(l)) + n += l // each bool takes exactly one byte + return +} + +// Encode a slice of bytes ([]byte). +func (o *Buffer) enc_slice_byte(p *Properties, base structPointer) error { + s := *structPointer_Bytes(base, p.field) + if s == nil { + return ErrNil + } + o.buf = append(o.buf, p.tagcode...) + o.EncodeRawBytes(s) + return nil +} + +func (o *Buffer) enc_proto3_slice_byte(p *Properties, base structPointer) error { + s := *structPointer_Bytes(base, p.field) + if len(s) == 0 { + return ErrNil + } + o.buf = append(o.buf, p.tagcode...) + o.EncodeRawBytes(s) + return nil +} + +func size_slice_byte(p *Properties, base structPointer) (n int) { + s := *structPointer_Bytes(base, p.field) + if s == nil && !p.oneof { + return 0 + } + n += len(p.tagcode) + n += sizeRawBytes(s) + return +} + +func size_proto3_slice_byte(p *Properties, base structPointer) (n int) { + s := *structPointer_Bytes(base, p.field) + if len(s) == 0 && !p.oneof { + return 0 + } + n += len(p.tagcode) + n += sizeRawBytes(s) + return +} + +// Encode a slice of int32s ([]int32). +func (o *Buffer) enc_slice_int32(p *Properties, base structPointer) error { + s := structPointer_Word32Slice(base, p.field) + l := s.Len() + if l == 0 { + return ErrNil + } + for i := 0; i < l; i++ { + o.buf = append(o.buf, p.tagcode...) + x := int32(s.Index(i)) // permit sign extension to use full 64-bit range + p.valEnc(o, uint64(x)) + } + return nil +} + +func size_slice_int32(p *Properties, base structPointer) (n int) { + s := structPointer_Word32Slice(base, p.field) + l := s.Len() + if l == 0 { + return 0 + } + for i := 0; i < l; i++ { + n += len(p.tagcode) + x := int32(s.Index(i)) // permit sign extension to use full 64-bit range + n += p.valSize(uint64(x)) + } + return +} + +// Encode a slice of int32s ([]int32) in packed format. +func (o *Buffer) enc_slice_packed_int32(p *Properties, base structPointer) error { + s := structPointer_Word32Slice(base, p.field) + l := s.Len() + if l == 0 { + return ErrNil + } + // TODO: Reuse a Buffer. + buf := NewBuffer(nil) + for i := 0; i < l; i++ { + x := int32(s.Index(i)) // permit sign extension to use full 64-bit range + p.valEnc(buf, uint64(x)) + } + + o.buf = append(o.buf, p.tagcode...) + o.EncodeVarint(uint64(len(buf.buf))) + o.buf = append(o.buf, buf.buf...) + return nil +} + +func size_slice_packed_int32(p *Properties, base structPointer) (n int) { + s := structPointer_Word32Slice(base, p.field) + l := s.Len() + if l == 0 { + return 0 + } + var bufSize int + for i := 0; i < l; i++ { + x := int32(s.Index(i)) // permit sign extension to use full 64-bit range + bufSize += p.valSize(uint64(x)) + } + + n += len(p.tagcode) + n += sizeVarint(uint64(bufSize)) + n += bufSize + return +} + +// Encode a slice of uint32s ([]uint32). +// Exactly the same as int32, except for no sign extension. +func (o *Buffer) enc_slice_uint32(p *Properties, base structPointer) error { + s := structPointer_Word32Slice(base, p.field) + l := s.Len() + if l == 0 { + return ErrNil + } + for i := 0; i < l; i++ { + o.buf = append(o.buf, p.tagcode...) + x := s.Index(i) + p.valEnc(o, uint64(x)) + } + return nil +} + +func size_slice_uint32(p *Properties, base structPointer) (n int) { + s := structPointer_Word32Slice(base, p.field) + l := s.Len() + if l == 0 { + return 0 + } + for i := 0; i < l; i++ { + n += len(p.tagcode) + x := s.Index(i) + n += p.valSize(uint64(x)) + } + return +} + +// Encode a slice of uint32s ([]uint32) in packed format. +// Exactly the same as int32, except for no sign extension. +func (o *Buffer) enc_slice_packed_uint32(p *Properties, base structPointer) error { + s := structPointer_Word32Slice(base, p.field) + l := s.Len() + if l == 0 { + return ErrNil + } + // TODO: Reuse a Buffer. + buf := NewBuffer(nil) + for i := 0; i < l; i++ { + p.valEnc(buf, uint64(s.Index(i))) + } + + o.buf = append(o.buf, p.tagcode...) + o.EncodeVarint(uint64(len(buf.buf))) + o.buf = append(o.buf, buf.buf...) + return nil +} + +func size_slice_packed_uint32(p *Properties, base structPointer) (n int) { + s := structPointer_Word32Slice(base, p.field) + l := s.Len() + if l == 0 { + return 0 + } + var bufSize int + for i := 0; i < l; i++ { + bufSize += p.valSize(uint64(s.Index(i))) + } + + n += len(p.tagcode) + n += sizeVarint(uint64(bufSize)) + n += bufSize + return +} + +// Encode a slice of int64s ([]int64). +func (o *Buffer) enc_slice_int64(p *Properties, base structPointer) error { + s := structPointer_Word64Slice(base, p.field) + l := s.Len() + if l == 0 { + return ErrNil + } + for i := 0; i < l; i++ { + o.buf = append(o.buf, p.tagcode...) + p.valEnc(o, s.Index(i)) + } + return nil +} + +func size_slice_int64(p *Properties, base structPointer) (n int) { + s := structPointer_Word64Slice(base, p.field) + l := s.Len() + if l == 0 { + return 0 + } + for i := 0; i < l; i++ { + n += len(p.tagcode) + n += p.valSize(s.Index(i)) + } + return +} + +// Encode a slice of int64s ([]int64) in packed format. +func (o *Buffer) enc_slice_packed_int64(p *Properties, base structPointer) error { + s := structPointer_Word64Slice(base, p.field) + l := s.Len() + if l == 0 { + return ErrNil + } + // TODO: Reuse a Buffer. + buf := NewBuffer(nil) + for i := 0; i < l; i++ { + p.valEnc(buf, s.Index(i)) + } + + o.buf = append(o.buf, p.tagcode...) + o.EncodeVarint(uint64(len(buf.buf))) + o.buf = append(o.buf, buf.buf...) + return nil +} + +func size_slice_packed_int64(p *Properties, base structPointer) (n int) { + s := structPointer_Word64Slice(base, p.field) + l := s.Len() + if l == 0 { + return 0 + } + var bufSize int + for i := 0; i < l; i++ { + bufSize += p.valSize(s.Index(i)) + } + + n += len(p.tagcode) + n += sizeVarint(uint64(bufSize)) + n += bufSize + return +} + +// Encode a slice of slice of bytes ([][]byte). +func (o *Buffer) enc_slice_slice_byte(p *Properties, base structPointer) error { + ss := *structPointer_BytesSlice(base, p.field) + l := len(ss) + if l == 0 { + return ErrNil + } + for i := 0; i < l; i++ { + o.buf = append(o.buf, p.tagcode...) + o.EncodeRawBytes(ss[i]) + } + return nil +} + +func size_slice_slice_byte(p *Properties, base structPointer) (n int) { + ss := *structPointer_BytesSlice(base, p.field) + l := len(ss) + if l == 0 { + return 0 + } + n += l * len(p.tagcode) + for i := 0; i < l; i++ { + n += sizeRawBytes(ss[i]) + } + return +} + +// Encode a slice of strings ([]string). +func (o *Buffer) enc_slice_string(p *Properties, base structPointer) error { + ss := *structPointer_StringSlice(base, p.field) + l := len(ss) + for i := 0; i < l; i++ { + o.buf = append(o.buf, p.tagcode...) + o.EncodeStringBytes(ss[i]) + } + return nil +} + +func size_slice_string(p *Properties, base structPointer) (n int) { + ss := *structPointer_StringSlice(base, p.field) + l := len(ss) + n += l * len(p.tagcode) + for i := 0; i < l; i++ { + n += sizeStringBytes(ss[i]) + } + return +} + +// Encode a slice of message structs ([]*struct). +func (o *Buffer) enc_slice_struct_message(p *Properties, base structPointer) error { + var state errorState + s := structPointer_StructPointerSlice(base, p.field) + l := s.Len() + + for i := 0; i < l; i++ { + structp := s.Index(i) + if structPointer_IsNil(structp) { + return errRepeatedHasNil + } + + // Can the object marshal itself? + if p.isMarshaler { + m := structPointer_Interface(structp, p.stype).(Marshaler) + data, err := m.Marshal() + if err != nil && !state.shouldContinue(err, nil) { + return err + } + o.buf = append(o.buf, p.tagcode...) + o.EncodeRawBytes(data) + continue + } + + o.buf = append(o.buf, p.tagcode...) + err := o.enc_len_struct(p.sprop, structp, &state) + if err != nil && !state.shouldContinue(err, nil) { + if err == ErrNil { + return errRepeatedHasNil + } + return err + } + } + return state.err +} + +func size_slice_struct_message(p *Properties, base structPointer) (n int) { + s := structPointer_StructPointerSlice(base, p.field) + l := s.Len() + n += l * len(p.tagcode) + for i := 0; i < l; i++ { + structp := s.Index(i) + if structPointer_IsNil(structp) { + return // return the size up to this point + } + + // Can the object marshal itself? + if p.isMarshaler { + m := structPointer_Interface(structp, p.stype).(Marshaler) + data, _ := m.Marshal() + n += len(p.tagcode) + n += sizeRawBytes(data) + continue + } + + n0 := size_struct(p.sprop, structp) + n1 := sizeVarint(uint64(n0)) // size of encoded length + n += n0 + n1 + } + return +} + +// Encode a slice of group structs ([]*struct). +func (o *Buffer) enc_slice_struct_group(p *Properties, base structPointer) error { + var state errorState + s := structPointer_StructPointerSlice(base, p.field) + l := s.Len() + + for i := 0; i < l; i++ { + b := s.Index(i) + if structPointer_IsNil(b) { + return errRepeatedHasNil + } + + o.EncodeVarint(uint64((p.Tag << 3) | WireStartGroup)) + + err := o.enc_struct(p.sprop, b) + + if err != nil && !state.shouldContinue(err, nil) { + if err == ErrNil { + return errRepeatedHasNil + } + return err + } + + o.EncodeVarint(uint64((p.Tag << 3) | WireEndGroup)) + } + return state.err +} + +func size_slice_struct_group(p *Properties, base structPointer) (n int) { + s := structPointer_StructPointerSlice(base, p.field) + l := s.Len() + + n += l * sizeVarint(uint64((p.Tag<<3)|WireStartGroup)) + n += l * sizeVarint(uint64((p.Tag<<3)|WireEndGroup)) + for i := 0; i < l; i++ { + b := s.Index(i) + if structPointer_IsNil(b) { + return // return size up to this point + } + + n += size_struct(p.sprop, b) + } + return +} + +// Encode an extension map. +func (o *Buffer) enc_map(p *Properties, base structPointer) error { + v := *structPointer_ExtMap(base, p.field) + if err := encodeExtensionMap(v); err != nil { + return err + } + // Fast-path for common cases: zero or one extensions. + if len(v) <= 1 { + for _, e := range v { + o.buf = append(o.buf, e.enc...) + } + return nil + } + + // Sort keys to provide a deterministic encoding. + keys := make([]int, 0, len(v)) + for k := range v { + keys = append(keys, int(k)) + } + sort.Ints(keys) + + for _, k := range keys { + o.buf = append(o.buf, v[int32(k)].enc...) + } + return nil +} + +func size_map(p *Properties, base structPointer) int { + v := *structPointer_ExtMap(base, p.field) + return sizeExtensionMap(v) +} + +// Encode a map field. +func (o *Buffer) enc_new_map(p *Properties, base structPointer) error { + var state errorState // XXX: or do we need to plumb this through? + + /* + A map defined as + map map_field = N; + is encoded in the same way as + message MapFieldEntry { + key_type key = 1; + value_type value = 2; + } + repeated MapFieldEntry map_field = N; + */ + + v := structPointer_NewAt(base, p.field, p.mtype).Elem() // map[K]V + if v.Len() == 0 { + return nil + } + + keycopy, valcopy, keybase, valbase := mapEncodeScratch(p.mtype) + + enc := func() error { + if err := p.mkeyprop.enc(o, p.mkeyprop, keybase); err != nil { + return err + } + if err := p.mvalprop.enc(o, p.mvalprop, valbase); err != nil { + return err + } + return nil + } + + // Don't sort map keys. It is not required by the spec, and C++ doesn't do it. + for _, key := range v.MapKeys() { + val := v.MapIndex(key) + + // The only illegal map entry values are nil message pointers. + if val.Kind() == reflect.Ptr && val.IsNil() { + return errors.New("proto: map has nil element") + } + + keycopy.Set(key) + valcopy.Set(val) + + o.buf = append(o.buf, p.tagcode...) + if err := o.enc_len_thing(enc, &state); err != nil { + return err + } + } + return nil +} + +func size_new_map(p *Properties, base structPointer) int { + v := structPointer_NewAt(base, p.field, p.mtype).Elem() // map[K]V + + keycopy, valcopy, keybase, valbase := mapEncodeScratch(p.mtype) + + n := 0 + for _, key := range v.MapKeys() { + val := v.MapIndex(key) + keycopy.Set(key) + valcopy.Set(val) + + // Tag codes for key and val are the responsibility of the sub-sizer. + keysize := p.mkeyprop.size(p.mkeyprop, keybase) + valsize := p.mvalprop.size(p.mvalprop, valbase) + entry := keysize + valsize + // Add on tag code and length of map entry itself. + n += len(p.tagcode) + sizeVarint(uint64(entry)) + entry + } + return n +} + +// mapEncodeScratch returns a new reflect.Value matching the map's value type, +// and a structPointer suitable for passing to an encoder or sizer. +func mapEncodeScratch(mapType reflect.Type) (keycopy, valcopy reflect.Value, keybase, valbase structPointer) { + // Prepare addressable doubly-indirect placeholders for the key and value types. + // This is needed because the element-type encoders expect **T, but the map iteration produces T. + + keycopy = reflect.New(mapType.Key()).Elem() // addressable K + keyptr := reflect.New(reflect.PtrTo(keycopy.Type())).Elem() // addressable *K + keyptr.Set(keycopy.Addr()) // + keybase = toStructPointer(keyptr.Addr()) // **K + + // Value types are more varied and require special handling. + switch mapType.Elem().Kind() { + case reflect.Slice: + // []byte + var dummy []byte + valcopy = reflect.ValueOf(&dummy).Elem() // addressable []byte + valbase = toStructPointer(valcopy.Addr()) + case reflect.Ptr: + // message; the generated field type is map[K]*Msg (so V is *Msg), + // so we only need one level of indirection. + valcopy = reflect.New(mapType.Elem()).Elem() // addressable V + valbase = toStructPointer(valcopy.Addr()) + default: + // everything else + valcopy = reflect.New(mapType.Elem()).Elem() // addressable V + valptr := reflect.New(reflect.PtrTo(valcopy.Type())).Elem() // addressable *V + valptr.Set(valcopy.Addr()) // + valbase = toStructPointer(valptr.Addr()) // **V + } + return +} + +// Encode a struct. +func (o *Buffer) enc_struct(prop *StructProperties, base structPointer) error { + var state errorState + // Encode fields in tag order so that decoders may use optimizations + // that depend on the ordering. + // https://developers.google.com/protocol-buffers/docs/encoding#order + for _, i := range prop.order { + p := prop.Prop[i] + if p.enc != nil { + err := p.enc(o, p, base) + if err != nil { + if err == ErrNil { + if p.Required && state.err == nil { + state.err = &RequiredNotSetError{p.Name} + } + } else if err == errRepeatedHasNil { + // Give more context to nil values in repeated fields. + return errors.New("repeated field " + p.OrigName + " has nil element") + } else if !state.shouldContinue(err, p) { + return err + } + } + } + } + + // Do oneof fields. + if prop.oneofMarshaler != nil { + m := structPointer_Interface(base, prop.stype).(Message) + if err := prop.oneofMarshaler(m, o); err != nil { + return err + } + } + + // Add unrecognized fields at the end. + if prop.unrecField.IsValid() { + v := *structPointer_Bytes(base, prop.unrecField) + if len(v) > 0 { + o.buf = append(o.buf, v...) + } + } + + return state.err +} + +func size_struct(prop *StructProperties, base structPointer) (n int) { + for _, i := range prop.order { + p := prop.Prop[i] + if p.size != nil { + n += p.size(p, base) + } + } + + // Add unrecognized fields at the end. + if prop.unrecField.IsValid() { + v := *structPointer_Bytes(base, prop.unrecField) + n += len(v) + } + + // Factor in any oneof fields. + if prop.oneofSizer != nil { + m := structPointer_Interface(base, prop.stype).(Message) + n += prop.oneofSizer(m) + } + + return +} + +var zeroes [20]byte // longer than any conceivable sizeVarint + +// Encode a struct, preceded by its encoded length (as a varint). +func (o *Buffer) enc_len_struct(prop *StructProperties, base structPointer, state *errorState) error { + return o.enc_len_thing(func() error { return o.enc_struct(prop, base) }, state) +} + +// Encode something, preceded by its encoded length (as a varint). +func (o *Buffer) enc_len_thing(enc func() error, state *errorState) error { + iLen := len(o.buf) + o.buf = append(o.buf, 0, 0, 0, 0) // reserve four bytes for length + iMsg := len(o.buf) + err := enc() + if err != nil && !state.shouldContinue(err, nil) { + return err + } + lMsg := len(o.buf) - iMsg + lLen := sizeVarint(uint64(lMsg)) + switch x := lLen - (iMsg - iLen); { + case x > 0: // actual length is x bytes larger than the space we reserved + // Move msg x bytes right. + o.buf = append(o.buf, zeroes[:x]...) + copy(o.buf[iMsg+x:], o.buf[iMsg:iMsg+lMsg]) + case x < 0: // actual length is x bytes smaller than the space we reserved + // Move msg x bytes left. + copy(o.buf[iMsg+x:], o.buf[iMsg:iMsg+lMsg]) + o.buf = o.buf[:len(o.buf)+x] // x is negative + } + // Encode the length in the reserved space. + o.buf = o.buf[:iLen] + o.EncodeVarint(uint64(lMsg)) + o.buf = o.buf[:len(o.buf)+lMsg] + return state.err +} + +// errorState maintains the first error that occurs and updates that error +// with additional context. +type errorState struct { + err error +} + +// shouldContinue reports whether encoding should continue upon encountering the +// given error. If the error is RequiredNotSetError, shouldContinue returns true +// and, if this is the first appearance of that error, remembers it for future +// reporting. +// +// If prop is not nil, it may update any error with additional context about the +// field with the error. +func (s *errorState) shouldContinue(err error, prop *Properties) bool { + // Ignore unset required fields. + reqNotSet, ok := err.(*RequiredNotSetError) + if !ok { + return false + } + if s.err == nil { + if prop != nil { + err = &RequiredNotSetError{prop.Name + "." + reqNotSet.field} + } + s.err = err + } + return true +} diff --git a/vendor/github.com/golang/protobuf/proto/equal.go b/vendor/github.com/golang/protobuf/proto/equal.go new file mode 100644 index 000000000..f5db1def3 --- /dev/null +++ b/vendor/github.com/golang/protobuf/proto/equal.go @@ -0,0 +1,276 @@ +// Go support for Protocol Buffers - Google's data interchange format +// +// Copyright 2011 The Go Authors. All rights reserved. +// https://github.com/golang/protobuf +// +// Redistribution and use in source and binary forms, with or without +// modification, are permitted provided that the following conditions are +// met: +// +// * Redistributions of source code must retain the above copyright +// notice, this list of conditions and the following disclaimer. +// * Redistributions in binary form must reproduce the above +// copyright notice, this list of conditions and the following disclaimer +// in the documentation and/or other materials provided with the +// distribution. +// * Neither the name of Google Inc. nor the names of its +// contributors may be used to endorse or promote products derived from +// this software without specific prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +// Protocol buffer comparison. + +package proto + +import ( + "bytes" + "log" + "reflect" + "strings" +) + +/* +Equal returns true iff protocol buffers a and b are equal. +The arguments must both be pointers to protocol buffer structs. + +Equality is defined in this way: + - Two messages are equal iff they are the same type, + corresponding fields are equal, unknown field sets + are equal, and extensions sets are equal. + - Two set scalar fields are equal iff their values are equal. + If the fields are of a floating-point type, remember that + NaN != x for all x, including NaN. If the message is defined + in a proto3 .proto file, fields are not "set"; specifically, + zero length proto3 "bytes" fields are equal (nil == {}). + - Two repeated fields are equal iff their lengths are the same, + and their corresponding elements are equal (a "bytes" field, + although represented by []byte, is not a repeated field) + - Two unset fields are equal. + - Two unknown field sets are equal if their current + encoded state is equal. + - Two extension sets are equal iff they have corresponding + elements that are pairwise equal. + - Every other combination of things are not equal. + +The return value is undefined if a and b are not protocol buffers. +*/ +func Equal(a, b Message) bool { + if a == nil || b == nil { + return a == b + } + v1, v2 := reflect.ValueOf(a), reflect.ValueOf(b) + if v1.Type() != v2.Type() { + return false + } + if v1.Kind() == reflect.Ptr { + if v1.IsNil() { + return v2.IsNil() + } + if v2.IsNil() { + return false + } + v1, v2 = v1.Elem(), v2.Elem() + } + if v1.Kind() != reflect.Struct { + return false + } + return equalStruct(v1, v2) +} + +// v1 and v2 are known to have the same type. +func equalStruct(v1, v2 reflect.Value) bool { + sprop := GetProperties(v1.Type()) + for i := 0; i < v1.NumField(); i++ { + f := v1.Type().Field(i) + if strings.HasPrefix(f.Name, "XXX_") { + continue + } + f1, f2 := v1.Field(i), v2.Field(i) + if f.Type.Kind() == reflect.Ptr { + if n1, n2 := f1.IsNil(), f2.IsNil(); n1 && n2 { + // both unset + continue + } else if n1 != n2 { + // set/unset mismatch + return false + } + b1, ok := f1.Interface().(raw) + if ok { + b2 := f2.Interface().(raw) + // RawMessage + if !bytes.Equal(b1.Bytes(), b2.Bytes()) { + return false + } + continue + } + f1, f2 = f1.Elem(), f2.Elem() + } + if !equalAny(f1, f2, sprop.Prop[i]) { + return false + } + } + + if em1 := v1.FieldByName("XXX_extensions"); em1.IsValid() { + em2 := v2.FieldByName("XXX_extensions") + if !equalExtensions(v1.Type(), em1.Interface().(map[int32]Extension), em2.Interface().(map[int32]Extension)) { + return false + } + } + + uf := v1.FieldByName("XXX_unrecognized") + if !uf.IsValid() { + return true + } + + u1 := uf.Bytes() + u2 := v2.FieldByName("XXX_unrecognized").Bytes() + if !bytes.Equal(u1, u2) { + return false + } + + return true +} + +// v1 and v2 are known to have the same type. +// prop may be nil. +func equalAny(v1, v2 reflect.Value, prop *Properties) bool { + if v1.Type() == protoMessageType { + m1, _ := v1.Interface().(Message) + m2, _ := v2.Interface().(Message) + return Equal(m1, m2) + } + switch v1.Kind() { + case reflect.Bool: + return v1.Bool() == v2.Bool() + case reflect.Float32, reflect.Float64: + return v1.Float() == v2.Float() + case reflect.Int32, reflect.Int64: + return v1.Int() == v2.Int() + case reflect.Interface: + // Probably a oneof field; compare the inner values. + n1, n2 := v1.IsNil(), v2.IsNil() + if n1 || n2 { + return n1 == n2 + } + e1, e2 := v1.Elem(), v2.Elem() + if e1.Type() != e2.Type() { + return false + } + return equalAny(e1, e2, nil) + case reflect.Map: + if v1.Len() != v2.Len() { + return false + } + for _, key := range v1.MapKeys() { + val2 := v2.MapIndex(key) + if !val2.IsValid() { + // This key was not found in the second map. + return false + } + if !equalAny(v1.MapIndex(key), val2, nil) { + return false + } + } + return true + case reflect.Ptr: + return equalAny(v1.Elem(), v2.Elem(), prop) + case reflect.Slice: + if v1.Type().Elem().Kind() == reflect.Uint8 { + // short circuit: []byte + + // Edge case: if this is in a proto3 message, a zero length + // bytes field is considered the zero value. + if prop != nil && prop.proto3 && v1.Len() == 0 && v2.Len() == 0 { + return true + } + if v1.IsNil() != v2.IsNil() { + return false + } + return bytes.Equal(v1.Interface().([]byte), v2.Interface().([]byte)) + } + + if v1.Len() != v2.Len() { + return false + } + for i := 0; i < v1.Len(); i++ { + if !equalAny(v1.Index(i), v2.Index(i), prop) { + return false + } + } + return true + case reflect.String: + return v1.Interface().(string) == v2.Interface().(string) + case reflect.Struct: + return equalStruct(v1, v2) + case reflect.Uint32, reflect.Uint64: + return v1.Uint() == v2.Uint() + } + + // unknown type, so not a protocol buffer + log.Printf("proto: don't know how to compare %v", v1) + return false +} + +// base is the struct type that the extensions are based on. +// em1 and em2 are extension maps. +func equalExtensions(base reflect.Type, em1, em2 map[int32]Extension) bool { + if len(em1) != len(em2) { + return false + } + + for extNum, e1 := range em1 { + e2, ok := em2[extNum] + if !ok { + return false + } + + m1, m2 := e1.value, e2.value + + if m1 != nil && m2 != nil { + // Both are unencoded. + if !equalAny(reflect.ValueOf(m1), reflect.ValueOf(m2), nil) { + return false + } + continue + } + + // At least one is encoded. To do a semantically correct comparison + // we need to unmarshal them first. + var desc *ExtensionDesc + if m := extensionMaps[base]; m != nil { + desc = m[extNum] + } + if desc == nil { + log.Printf("proto: don't know how to compare extension %d of %v", extNum, base) + continue + } + var err error + if m1 == nil { + m1, err = decodeExtension(e1.enc, desc) + } + if m2 == nil && err == nil { + m2, err = decodeExtension(e2.enc, desc) + } + if err != nil { + // The encoded form is invalid. + log.Printf("proto: badly encoded extension %d of %v: %v", extNum, base, err) + return false + } + if !equalAny(reflect.ValueOf(m1), reflect.ValueOf(m2), nil) { + return false + } + } + + return true +} diff --git a/vendor/github.com/golang/protobuf/proto/extensions.go b/vendor/github.com/golang/protobuf/proto/extensions.go new file mode 100644 index 000000000..054f4f1df --- /dev/null +++ b/vendor/github.com/golang/protobuf/proto/extensions.go @@ -0,0 +1,399 @@ +// Go support for Protocol Buffers - Google's data interchange format +// +// Copyright 2010 The Go Authors. All rights reserved. +// https://github.com/golang/protobuf +// +// Redistribution and use in source and binary forms, with or without +// modification, are permitted provided that the following conditions are +// met: +// +// * Redistributions of source code must retain the above copyright +// notice, this list of conditions and the following disclaimer. +// * Redistributions in binary form must reproduce the above +// copyright notice, this list of conditions and the following disclaimer +// in the documentation and/or other materials provided with the +// distribution. +// * Neither the name of Google Inc. nor the names of its +// contributors may be used to endorse or promote products derived from +// this software without specific prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +package proto + +/* + * Types and routines for supporting protocol buffer extensions. + */ + +import ( + "errors" + "fmt" + "reflect" + "strconv" + "sync" +) + +// ErrMissingExtension is the error returned by GetExtension if the named extension is not in the message. +var ErrMissingExtension = errors.New("proto: missing extension") + +// ExtensionRange represents a range of message extensions for a protocol buffer. +// Used in code generated by the protocol compiler. +type ExtensionRange struct { + Start, End int32 // both inclusive +} + +// extendableProto is an interface implemented by any protocol buffer that may be extended. +type extendableProto interface { + Message + ExtensionRangeArray() []ExtensionRange + ExtensionMap() map[int32]Extension +} + +var extendableProtoType = reflect.TypeOf((*extendableProto)(nil)).Elem() + +// ExtensionDesc represents an extension specification. +// Used in generated code from the protocol compiler. +type ExtensionDesc struct { + ExtendedType Message // nil pointer to the type that is being extended + ExtensionType interface{} // nil pointer to the extension type + Field int32 // field number + Name string // fully-qualified name of extension, for text formatting + Tag string // protobuf tag style +} + +func (ed *ExtensionDesc) repeated() bool { + t := reflect.TypeOf(ed.ExtensionType) + return t.Kind() == reflect.Slice && t.Elem().Kind() != reflect.Uint8 +} + +// Extension represents an extension in a message. +type Extension struct { + // When an extension is stored in a message using SetExtension + // only desc and value are set. When the message is marshaled + // enc will be set to the encoded form of the message. + // + // When a message is unmarshaled and contains extensions, each + // extension will have only enc set. When such an extension is + // accessed using GetExtension (or GetExtensions) desc and value + // will be set. + desc *ExtensionDesc + value interface{} + enc []byte +} + +// SetRawExtension is for testing only. +func SetRawExtension(base extendableProto, id int32, b []byte) { + base.ExtensionMap()[id] = Extension{enc: b} +} + +// isExtensionField returns true iff the given field number is in an extension range. +func isExtensionField(pb extendableProto, field int32) bool { + for _, er := range pb.ExtensionRangeArray() { + if er.Start <= field && field <= er.End { + return true + } + } + return false +} + +// checkExtensionTypes checks that the given extension is valid for pb. +func checkExtensionTypes(pb extendableProto, extension *ExtensionDesc) error { + // Check the extended type. + if a, b := reflect.TypeOf(pb), reflect.TypeOf(extension.ExtendedType); a != b { + return errors.New("proto: bad extended type; " + b.String() + " does not extend " + a.String()) + } + // Check the range. + if !isExtensionField(pb, extension.Field) { + return errors.New("proto: bad extension number; not in declared ranges") + } + return nil +} + +// extPropKey is sufficient to uniquely identify an extension. +type extPropKey struct { + base reflect.Type + field int32 +} + +var extProp = struct { + sync.RWMutex + m map[extPropKey]*Properties +}{ + m: make(map[extPropKey]*Properties), +} + +func extensionProperties(ed *ExtensionDesc) *Properties { + key := extPropKey{base: reflect.TypeOf(ed.ExtendedType), field: ed.Field} + + extProp.RLock() + if prop, ok := extProp.m[key]; ok { + extProp.RUnlock() + return prop + } + extProp.RUnlock() + + extProp.Lock() + defer extProp.Unlock() + // Check again. + if prop, ok := extProp.m[key]; ok { + return prop + } + + prop := new(Properties) + prop.Init(reflect.TypeOf(ed.ExtensionType), "unknown_name", ed.Tag, nil) + extProp.m[key] = prop + return prop +} + +// encodeExtensionMap encodes any unmarshaled (unencoded) extensions in m. +func encodeExtensionMap(m map[int32]Extension) error { + for k, e := range m { + if e.value == nil || e.desc == nil { + // Extension is only in its encoded form. + continue + } + + // We don't skip extensions that have an encoded form set, + // because the extension value may have been mutated after + // the last time this function was called. + + et := reflect.TypeOf(e.desc.ExtensionType) + props := extensionProperties(e.desc) + + p := NewBuffer(nil) + // If e.value has type T, the encoder expects a *struct{ X T }. + // Pass a *T with a zero field and hope it all works out. + x := reflect.New(et) + x.Elem().Set(reflect.ValueOf(e.value)) + if err := props.enc(p, props, toStructPointer(x)); err != nil { + return err + } + e.enc = p.buf + m[k] = e + } + return nil +} + +func sizeExtensionMap(m map[int32]Extension) (n int) { + for _, e := range m { + if e.value == nil || e.desc == nil { + // Extension is only in its encoded form. + n += len(e.enc) + continue + } + + // We don't skip extensions that have an encoded form set, + // because the extension value may have been mutated after + // the last time this function was called. + + et := reflect.TypeOf(e.desc.ExtensionType) + props := extensionProperties(e.desc) + + // If e.value has type T, the encoder expects a *struct{ X T }. + // Pass a *T with a zero field and hope it all works out. + x := reflect.New(et) + x.Elem().Set(reflect.ValueOf(e.value)) + n += props.size(props, toStructPointer(x)) + } + return +} + +// HasExtension returns whether the given extension is present in pb. +func HasExtension(pb extendableProto, extension *ExtensionDesc) bool { + // TODO: Check types, field numbers, etc.? + _, ok := pb.ExtensionMap()[extension.Field] + return ok +} + +// ClearExtension removes the given extension from pb. +func ClearExtension(pb extendableProto, extension *ExtensionDesc) { + // TODO: Check types, field numbers, etc.? + delete(pb.ExtensionMap(), extension.Field) +} + +// GetExtension parses and returns the given extension of pb. +// If the extension is not present and has no default value it returns ErrMissingExtension. +func GetExtension(pb extendableProto, extension *ExtensionDesc) (interface{}, error) { + if err := checkExtensionTypes(pb, extension); err != nil { + return nil, err + } + + emap := pb.ExtensionMap() + e, ok := emap[extension.Field] + if !ok { + // defaultExtensionValue returns the default value or + // ErrMissingExtension if there is no default. + return defaultExtensionValue(extension) + } + + if e.value != nil { + // Already decoded. Check the descriptor, though. + if e.desc != extension { + // This shouldn't happen. If it does, it means that + // GetExtension was called twice with two different + // descriptors with the same field number. + return nil, errors.New("proto: descriptor conflict") + } + return e.value, nil + } + + v, err := decodeExtension(e.enc, extension) + if err != nil { + return nil, err + } + + // Remember the decoded version and drop the encoded version. + // That way it is safe to mutate what we return. + e.value = v + e.desc = extension + e.enc = nil + emap[extension.Field] = e + return e.value, nil +} + +// defaultExtensionValue returns the default value for extension. +// If no default for an extension is defined ErrMissingExtension is returned. +func defaultExtensionValue(extension *ExtensionDesc) (interface{}, error) { + t := reflect.TypeOf(extension.ExtensionType) + props := extensionProperties(extension) + + sf, _, err := fieldDefault(t, props) + if err != nil { + return nil, err + } + + if sf == nil || sf.value == nil { + // There is no default value. + return nil, ErrMissingExtension + } + + if t.Kind() != reflect.Ptr { + // We do not need to return a Ptr, we can directly return sf.value. + return sf.value, nil + } + + // We need to return an interface{} that is a pointer to sf.value. + value := reflect.New(t).Elem() + value.Set(reflect.New(value.Type().Elem())) + if sf.kind == reflect.Int32 { + // We may have an int32 or an enum, but the underlying data is int32. + // Since we can't set an int32 into a non int32 reflect.value directly + // set it as a int32. + value.Elem().SetInt(int64(sf.value.(int32))) + } else { + value.Elem().Set(reflect.ValueOf(sf.value)) + } + return value.Interface(), nil +} + +// decodeExtension decodes an extension encoded in b. +func decodeExtension(b []byte, extension *ExtensionDesc) (interface{}, error) { + o := NewBuffer(b) + + t := reflect.TypeOf(extension.ExtensionType) + + props := extensionProperties(extension) + + // t is a pointer to a struct, pointer to basic type or a slice. + // Allocate a "field" to store the pointer/slice itself; the + // pointer/slice will be stored here. We pass + // the address of this field to props.dec. + // This passes a zero field and a *t and lets props.dec + // interpret it as a *struct{ x t }. + value := reflect.New(t).Elem() + + for { + // Discard wire type and field number varint. It isn't needed. + if _, err := o.DecodeVarint(); err != nil { + return nil, err + } + + if err := props.dec(o, props, toStructPointer(value.Addr())); err != nil { + return nil, err + } + + if o.index >= len(o.buf) { + break + } + } + return value.Interface(), nil +} + +// GetExtensions returns a slice of the extensions present in pb that are also listed in es. +// The returned slice has the same length as es; missing extensions will appear as nil elements. +func GetExtensions(pb Message, es []*ExtensionDesc) (extensions []interface{}, err error) { + epb, ok := pb.(extendableProto) + if !ok { + err = errors.New("proto: not an extendable proto") + return + } + extensions = make([]interface{}, len(es)) + for i, e := range es { + extensions[i], err = GetExtension(epb, e) + if err == ErrMissingExtension { + err = nil + } + if err != nil { + return + } + } + return +} + +// SetExtension sets the specified extension of pb to the specified value. +func SetExtension(pb extendableProto, extension *ExtensionDesc, value interface{}) error { + if err := checkExtensionTypes(pb, extension); err != nil { + return err + } + typ := reflect.TypeOf(extension.ExtensionType) + if typ != reflect.TypeOf(value) { + return errors.New("proto: bad extension value type") + } + // nil extension values need to be caught early, because the + // encoder can't distinguish an ErrNil due to a nil extension + // from an ErrNil due to a missing field. Extensions are + // always optional, so the encoder would just swallow the error + // and drop all the extensions from the encoded message. + if reflect.ValueOf(value).IsNil() { + return fmt.Errorf("proto: SetExtension called with nil value of type %T", value) + } + + pb.ExtensionMap()[extension.Field] = Extension{desc: extension, value: value} + return nil +} + +// A global registry of extensions. +// The generated code will register the generated descriptors by calling RegisterExtension. + +var extensionMaps = make(map[reflect.Type]map[int32]*ExtensionDesc) + +// RegisterExtension is called from the generated code. +func RegisterExtension(desc *ExtensionDesc) { + st := reflect.TypeOf(desc.ExtendedType).Elem() + m := extensionMaps[st] + if m == nil { + m = make(map[int32]*ExtensionDesc) + extensionMaps[st] = m + } + if _, ok := m[desc.Field]; ok { + panic("proto: duplicate extension registered: " + st.String() + " " + strconv.Itoa(int(desc.Field))) + } + m[desc.Field] = desc +} + +// RegisteredExtensions returns a map of the registered extensions of a +// protocol buffer struct, indexed by the extension number. +// The argument pb should be a nil pointer to the struct type. +func RegisteredExtensions(pb Message) map[int32]*ExtensionDesc { + return extensionMaps[reflect.TypeOf(pb).Elem()] +} diff --git a/vendor/github.com/golang/protobuf/proto/lib.go b/vendor/github.com/golang/protobuf/proto/lib.go new file mode 100644 index 000000000..0de8f8dff --- /dev/null +++ b/vendor/github.com/golang/protobuf/proto/lib.go @@ -0,0 +1,894 @@ +// Go support for Protocol Buffers - Google's data interchange format +// +// Copyright 2010 The Go Authors. All rights reserved. +// https://github.com/golang/protobuf +// +// Redistribution and use in source and binary forms, with or without +// modification, are permitted provided that the following conditions are +// met: +// +// * Redistributions of source code must retain the above copyright +// notice, this list of conditions and the following disclaimer. +// * Redistributions in binary form must reproduce the above +// copyright notice, this list of conditions and the following disclaimer +// in the documentation and/or other materials provided with the +// distribution. +// * Neither the name of Google Inc. nor the names of its +// contributors may be used to endorse or promote products derived from +// this software without specific prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +/* +Package proto converts data structures to and from the wire format of +protocol buffers. It works in concert with the Go source code generated +for .proto files by the protocol compiler. + +A summary of the properties of the protocol buffer interface +for a protocol buffer variable v: + + - Names are turned from camel_case to CamelCase for export. + - There are no methods on v to set fields; just treat + them as structure fields. + - There are getters that return a field's value if set, + and return the field's default value if unset. + The getters work even if the receiver is a nil message. + - The zero value for a struct is its correct initialization state. + All desired fields must be set before marshaling. + - A Reset() method will restore a protobuf struct to its zero state. + - Non-repeated fields are pointers to the values; nil means unset. + That is, optional or required field int32 f becomes F *int32. + - Repeated fields are slices. + - Helper functions are available to aid the setting of fields. + msg.Foo = proto.String("hello") // set field + - Constants are defined to hold the default values of all fields that + have them. They have the form Default_StructName_FieldName. + Because the getter methods handle defaulted values, + direct use of these constants should be rare. + - Enums are given type names and maps from names to values. + Enum values are prefixed by the enclosing message's name, or by the + enum's type name if it is a top-level enum. Enum types have a String + method, and a Enum method to assist in message construction. + - Nested messages, groups and enums have type names prefixed with the name of + the surrounding message type. + - Extensions are given descriptor names that start with E_, + followed by an underscore-delimited list of the nested messages + that contain it (if any) followed by the CamelCased name of the + extension field itself. HasExtension, ClearExtension, GetExtension + and SetExtension are functions for manipulating extensions. + - Oneof field sets are given a single field in their message, + with distinguished wrapper types for each possible field value. + - Marshal and Unmarshal are functions to encode and decode the wire format. + +When the .proto file specifies `syntax="proto3"`, there are some differences: + + - Non-repeated fields of non-message type are values instead of pointers. + - Getters are only generated for message and oneof fields. + - Enum types do not get an Enum method. + +The simplest way to describe this is to see an example. +Given file test.proto, containing + + package example; + + enum FOO { X = 17; } + + message Test { + required string label = 1; + optional int32 type = 2 [default=77]; + repeated int64 reps = 3; + optional group OptionalGroup = 4 { + required string RequiredField = 5; + } + oneof union { + int32 number = 6; + string name = 7; + } + } + +The resulting file, test.pb.go, is: + + package example + + import proto "github.com/golang/protobuf/proto" + import math "math" + + type FOO int32 + const ( + FOO_X FOO = 17 + ) + var FOO_name = map[int32]string{ + 17: "X", + } + var FOO_value = map[string]int32{ + "X": 17, + } + + func (x FOO) Enum() *FOO { + p := new(FOO) + *p = x + return p + } + func (x FOO) String() string { + return proto.EnumName(FOO_name, int32(x)) + } + func (x *FOO) UnmarshalJSON(data []byte) error { + value, err := proto.UnmarshalJSONEnum(FOO_value, data) + if err != nil { + return err + } + *x = FOO(value) + return nil + } + + type Test struct { + Label *string `protobuf:"bytes,1,req,name=label" json:"label,omitempty"` + Type *int32 `protobuf:"varint,2,opt,name=type,def=77" json:"type,omitempty"` + Reps []int64 `protobuf:"varint,3,rep,name=reps" json:"reps,omitempty"` + Optionalgroup *Test_OptionalGroup `protobuf:"group,4,opt,name=OptionalGroup" json:"optionalgroup,omitempty"` + // Types that are valid to be assigned to Union: + // *Test_Number + // *Test_Name + Union isTest_Union `protobuf_oneof:"union"` + XXX_unrecognized []byte `json:"-"` + } + func (m *Test) Reset() { *m = Test{} } + func (m *Test) String() string { return proto.CompactTextString(m) } + func (*Test) ProtoMessage() {} + + type isTest_Union interface { + isTest_Union() + } + + type Test_Number struct { + Number int32 `protobuf:"varint,6,opt,name=number"` + } + type Test_Name struct { + Name string `protobuf:"bytes,7,opt,name=name"` + } + + func (*Test_Number) isTest_Union() {} + func (*Test_Name) isTest_Union() {} + + func (m *Test) GetUnion() isTest_Union { + if m != nil { + return m.Union + } + return nil + } + const Default_Test_Type int32 = 77 + + func (m *Test) GetLabel() string { + if m != nil && m.Label != nil { + return *m.Label + } + return "" + } + + func (m *Test) GetType() int32 { + if m != nil && m.Type != nil { + return *m.Type + } + return Default_Test_Type + } + + func (m *Test) GetOptionalgroup() *Test_OptionalGroup { + if m != nil { + return m.Optionalgroup + } + return nil + } + + type Test_OptionalGroup struct { + RequiredField *string `protobuf:"bytes,5,req" json:"RequiredField,omitempty"` + } + func (m *Test_OptionalGroup) Reset() { *m = Test_OptionalGroup{} } + func (m *Test_OptionalGroup) String() string { return proto.CompactTextString(m) } + + func (m *Test_OptionalGroup) GetRequiredField() string { + if m != nil && m.RequiredField != nil { + return *m.RequiredField + } + return "" + } + + func (m *Test) GetNumber() int32 { + if x, ok := m.GetUnion().(*Test_Number); ok { + return x.Number + } + return 0 + } + + func (m *Test) GetName() string { + if x, ok := m.GetUnion().(*Test_Name); ok { + return x.Name + } + return "" + } + + func init() { + proto.RegisterEnum("example.FOO", FOO_name, FOO_value) + } + +To create and play with a Test object: + + package main + + import ( + "log" + + "github.com/golang/protobuf/proto" + pb "./example.pb" + ) + + func main() { + test := &pb.Test{ + Label: proto.String("hello"), + Type: proto.Int32(17), + Reps: []int64{1, 2, 3}, + Optionalgroup: &pb.Test_OptionalGroup{ + RequiredField: proto.String("good bye"), + }, + Union: &pb.Test_Name{"fred"}, + } + data, err := proto.Marshal(test) + if err != nil { + log.Fatal("marshaling error: ", err) + } + newTest := &pb.Test{} + err = proto.Unmarshal(data, newTest) + if err != nil { + log.Fatal("unmarshaling error: ", err) + } + // Now test and newTest contain the same data. + if test.GetLabel() != newTest.GetLabel() { + log.Fatalf("data mismatch %q != %q", test.GetLabel(), newTest.GetLabel()) + } + // Use a type switch to determine which oneof was set. + switch u := test.Union.(type) { + case *pb.Test_Number: // u.Number contains the number. + case *pb.Test_Name: // u.Name contains the string. + } + // etc. + } +*/ +package proto + +import ( + "encoding/json" + "fmt" + "log" + "reflect" + "sort" + "strconv" + "sync" +) + +// Message is implemented by generated protocol buffer messages. +type Message interface { + Reset() + String() string + ProtoMessage() +} + +// Stats records allocation details about the protocol buffer encoders +// and decoders. Useful for tuning the library itself. +type Stats struct { + Emalloc uint64 // mallocs in encode + Dmalloc uint64 // mallocs in decode + Encode uint64 // number of encodes + Decode uint64 // number of decodes + Chit uint64 // number of cache hits + Cmiss uint64 // number of cache misses + Size uint64 // number of sizes +} + +// Set to true to enable stats collection. +const collectStats = false + +var stats Stats + +// GetStats returns a copy of the global Stats structure. +func GetStats() Stats { return stats } + +// A Buffer is a buffer manager for marshaling and unmarshaling +// protocol buffers. It may be reused between invocations to +// reduce memory usage. It is not necessary to use a Buffer; +// the global functions Marshal and Unmarshal create a +// temporary Buffer and are fine for most applications. +type Buffer struct { + buf []byte // encode/decode byte stream + index int // write point + + // pools of basic types to amortize allocation. + bools []bool + uint32s []uint32 + uint64s []uint64 + + // extra pools, only used with pointer_reflect.go + int32s []int32 + int64s []int64 + float32s []float32 + float64s []float64 +} + +// NewBuffer allocates a new Buffer and initializes its internal data to +// the contents of the argument slice. +func NewBuffer(e []byte) *Buffer { + return &Buffer{buf: e} +} + +// Reset resets the Buffer, ready for marshaling a new protocol buffer. +func (p *Buffer) Reset() { + p.buf = p.buf[0:0] // for reading/writing + p.index = 0 // for reading +} + +// SetBuf replaces the internal buffer with the slice, +// ready for unmarshaling the contents of the slice. +func (p *Buffer) SetBuf(s []byte) { + p.buf = s + p.index = 0 +} + +// Bytes returns the contents of the Buffer. +func (p *Buffer) Bytes() []byte { return p.buf } + +/* + * Helper routines for simplifying the creation of optional fields of basic type. + */ + +// Bool is a helper routine that allocates a new bool value +// to store v and returns a pointer to it. +func Bool(v bool) *bool { + return &v +} + +// Int32 is a helper routine that allocates a new int32 value +// to store v and returns a pointer to it. +func Int32(v int32) *int32 { + return &v +} + +// Int is a helper routine that allocates a new int32 value +// to store v and returns a pointer to it, but unlike Int32 +// its argument value is an int. +func Int(v int) *int32 { + p := new(int32) + *p = int32(v) + return p +} + +// Int64 is a helper routine that allocates a new int64 value +// to store v and returns a pointer to it. +func Int64(v int64) *int64 { + return &v +} + +// Float32 is a helper routine that allocates a new float32 value +// to store v and returns a pointer to it. +func Float32(v float32) *float32 { + return &v +} + +// Float64 is a helper routine that allocates a new float64 value +// to store v and returns a pointer to it. +func Float64(v float64) *float64 { + return &v +} + +// Uint32 is a helper routine that allocates a new uint32 value +// to store v and returns a pointer to it. +func Uint32(v uint32) *uint32 { + return &v +} + +// Uint64 is a helper routine that allocates a new uint64 value +// to store v and returns a pointer to it. +func Uint64(v uint64) *uint64 { + return &v +} + +// String is a helper routine that allocates a new string value +// to store v and returns a pointer to it. +func String(v string) *string { + return &v +} + +// EnumName is a helper function to simplify printing protocol buffer enums +// by name. Given an enum map and a value, it returns a useful string. +func EnumName(m map[int32]string, v int32) string { + s, ok := m[v] + if ok { + return s + } + return strconv.Itoa(int(v)) +} + +// UnmarshalJSONEnum is a helper function to simplify recovering enum int values +// from their JSON-encoded representation. Given a map from the enum's symbolic +// names to its int values, and a byte buffer containing the JSON-encoded +// value, it returns an int32 that can be cast to the enum type by the caller. +// +// The function can deal with both JSON representations, numeric and symbolic. +func UnmarshalJSONEnum(m map[string]int32, data []byte, enumName string) (int32, error) { + if data[0] == '"' { + // New style: enums are strings. + var repr string + if err := json.Unmarshal(data, &repr); err != nil { + return -1, err + } + val, ok := m[repr] + if !ok { + return 0, fmt.Errorf("unrecognized enum %s value %q", enumName, repr) + } + return val, nil + } + // Old style: enums are ints. + var val int32 + if err := json.Unmarshal(data, &val); err != nil { + return 0, fmt.Errorf("cannot unmarshal %#q into enum %s", data, enumName) + } + return val, nil +} + +// DebugPrint dumps the encoded data in b in a debugging format with a header +// including the string s. Used in testing but made available for general debugging. +func (p *Buffer) DebugPrint(s string, b []byte) { + var u uint64 + + obuf := p.buf + index := p.index + p.buf = b + p.index = 0 + depth := 0 + + fmt.Printf("\n--- %s ---\n", s) + +out: + for { + for i := 0; i < depth; i++ { + fmt.Print(" ") + } + + index := p.index + if index == len(p.buf) { + break + } + + op, err := p.DecodeVarint() + if err != nil { + fmt.Printf("%3d: fetching op err %v\n", index, err) + break out + } + tag := op >> 3 + wire := op & 7 + + switch wire { + default: + fmt.Printf("%3d: t=%3d unknown wire=%d\n", + index, tag, wire) + break out + + case WireBytes: + var r []byte + + r, err = p.DecodeRawBytes(false) + if err != nil { + break out + } + fmt.Printf("%3d: t=%3d bytes [%d]", index, tag, len(r)) + if len(r) <= 6 { + for i := 0; i < len(r); i++ { + fmt.Printf(" %.2x", r[i]) + } + } else { + for i := 0; i < 3; i++ { + fmt.Printf(" %.2x", r[i]) + } + fmt.Printf(" ..") + for i := len(r) - 3; i < len(r); i++ { + fmt.Printf(" %.2x", r[i]) + } + } + fmt.Printf("\n") + + case WireFixed32: + u, err = p.DecodeFixed32() + if err != nil { + fmt.Printf("%3d: t=%3d fix32 err %v\n", index, tag, err) + break out + } + fmt.Printf("%3d: t=%3d fix32 %d\n", index, tag, u) + + case WireFixed64: + u, err = p.DecodeFixed64() + if err != nil { + fmt.Printf("%3d: t=%3d fix64 err %v\n", index, tag, err) + break out + } + fmt.Printf("%3d: t=%3d fix64 %d\n", index, tag, u) + + case WireVarint: + u, err = p.DecodeVarint() + if err != nil { + fmt.Printf("%3d: t=%3d varint err %v\n", index, tag, err) + break out + } + fmt.Printf("%3d: t=%3d varint %d\n", index, tag, u) + + case WireStartGroup: + fmt.Printf("%3d: t=%3d start\n", index, tag) + depth++ + + case WireEndGroup: + depth-- + fmt.Printf("%3d: t=%3d end\n", index, tag) + } + } + + if depth != 0 { + fmt.Printf("%3d: start-end not balanced %d\n", p.index, depth) + } + fmt.Printf("\n") + + p.buf = obuf + p.index = index +} + +// SetDefaults sets unset protocol buffer fields to their default values. +// It only modifies fields that are both unset and have defined defaults. +// It recursively sets default values in any non-nil sub-messages. +func SetDefaults(pb Message) { + setDefaults(reflect.ValueOf(pb), true, false) +} + +// v is a pointer to a struct. +func setDefaults(v reflect.Value, recur, zeros bool) { + v = v.Elem() + + defaultMu.RLock() + dm, ok := defaults[v.Type()] + defaultMu.RUnlock() + if !ok { + dm = buildDefaultMessage(v.Type()) + defaultMu.Lock() + defaults[v.Type()] = dm + defaultMu.Unlock() + } + + for _, sf := range dm.scalars { + f := v.Field(sf.index) + if !f.IsNil() { + // field already set + continue + } + dv := sf.value + if dv == nil && !zeros { + // no explicit default, and don't want to set zeros + continue + } + fptr := f.Addr().Interface() // **T + // TODO: Consider batching the allocations we do here. + switch sf.kind { + case reflect.Bool: + b := new(bool) + if dv != nil { + *b = dv.(bool) + } + *(fptr.(**bool)) = b + case reflect.Float32: + f := new(float32) + if dv != nil { + *f = dv.(float32) + } + *(fptr.(**float32)) = f + case reflect.Float64: + f := new(float64) + if dv != nil { + *f = dv.(float64) + } + *(fptr.(**float64)) = f + case reflect.Int32: + // might be an enum + if ft := f.Type(); ft != int32PtrType { + // enum + f.Set(reflect.New(ft.Elem())) + if dv != nil { + f.Elem().SetInt(int64(dv.(int32))) + } + } else { + // int32 field + i := new(int32) + if dv != nil { + *i = dv.(int32) + } + *(fptr.(**int32)) = i + } + case reflect.Int64: + i := new(int64) + if dv != nil { + *i = dv.(int64) + } + *(fptr.(**int64)) = i + case reflect.String: + s := new(string) + if dv != nil { + *s = dv.(string) + } + *(fptr.(**string)) = s + case reflect.Uint8: + // exceptional case: []byte + var b []byte + if dv != nil { + db := dv.([]byte) + b = make([]byte, len(db)) + copy(b, db) + } else { + b = []byte{} + } + *(fptr.(*[]byte)) = b + case reflect.Uint32: + u := new(uint32) + if dv != nil { + *u = dv.(uint32) + } + *(fptr.(**uint32)) = u + case reflect.Uint64: + u := new(uint64) + if dv != nil { + *u = dv.(uint64) + } + *(fptr.(**uint64)) = u + default: + log.Printf("proto: can't set default for field %v (sf.kind=%v)", f, sf.kind) + } + } + + for _, ni := range dm.nested { + f := v.Field(ni) + // f is *T or []*T or map[T]*T + switch f.Kind() { + case reflect.Ptr: + if f.IsNil() { + continue + } + setDefaults(f, recur, zeros) + + case reflect.Slice: + for i := 0; i < f.Len(); i++ { + e := f.Index(i) + if e.IsNil() { + continue + } + setDefaults(e, recur, zeros) + } + + case reflect.Map: + for _, k := range f.MapKeys() { + e := f.MapIndex(k) + if e.IsNil() { + continue + } + setDefaults(e, recur, zeros) + } + } + } +} + +var ( + // defaults maps a protocol buffer struct type to a slice of the fields, + // with its scalar fields set to their proto-declared non-zero default values. + defaultMu sync.RWMutex + defaults = make(map[reflect.Type]defaultMessage) + + int32PtrType = reflect.TypeOf((*int32)(nil)) +) + +// defaultMessage represents information about the default values of a message. +type defaultMessage struct { + scalars []scalarField + nested []int // struct field index of nested messages +} + +type scalarField struct { + index int // struct field index + kind reflect.Kind // element type (the T in *T or []T) + value interface{} // the proto-declared default value, or nil +} + +// t is a struct type. +func buildDefaultMessage(t reflect.Type) (dm defaultMessage) { + sprop := GetProperties(t) + for _, prop := range sprop.Prop { + fi, ok := sprop.decoderTags.get(prop.Tag) + if !ok { + // XXX_unrecognized + continue + } + ft := t.Field(fi).Type + + sf, nested, err := fieldDefault(ft, prop) + switch { + case err != nil: + log.Print(err) + case nested: + dm.nested = append(dm.nested, fi) + case sf != nil: + sf.index = fi + dm.scalars = append(dm.scalars, *sf) + } + } + + return dm +} + +// fieldDefault returns the scalarField for field type ft. +// sf will be nil if the field can not have a default. +// nestedMessage will be true if this is a nested message. +// Note that sf.index is not set on return. +func fieldDefault(ft reflect.Type, prop *Properties) (sf *scalarField, nestedMessage bool, err error) { + var canHaveDefault bool + switch ft.Kind() { + case reflect.Ptr: + if ft.Elem().Kind() == reflect.Struct { + nestedMessage = true + } else { + canHaveDefault = true // proto2 scalar field + } + + case reflect.Slice: + switch ft.Elem().Kind() { + case reflect.Ptr: + nestedMessage = true // repeated message + case reflect.Uint8: + canHaveDefault = true // bytes field + } + + case reflect.Map: + if ft.Elem().Kind() == reflect.Ptr { + nestedMessage = true // map with message values + } + } + + if !canHaveDefault { + if nestedMessage { + return nil, true, nil + } + return nil, false, nil + } + + // We now know that ft is a pointer or slice. + sf = &scalarField{kind: ft.Elem().Kind()} + + // scalar fields without defaults + if !prop.HasDefault { + return sf, false, nil + } + + // a scalar field: either *T or []byte + switch ft.Elem().Kind() { + case reflect.Bool: + x, err := strconv.ParseBool(prop.Default) + if err != nil { + return nil, false, fmt.Errorf("proto: bad default bool %q: %v", prop.Default, err) + } + sf.value = x + case reflect.Float32: + x, err := strconv.ParseFloat(prop.Default, 32) + if err != nil { + return nil, false, fmt.Errorf("proto: bad default float32 %q: %v", prop.Default, err) + } + sf.value = float32(x) + case reflect.Float64: + x, err := strconv.ParseFloat(prop.Default, 64) + if err != nil { + return nil, false, fmt.Errorf("proto: bad default float64 %q: %v", prop.Default, err) + } + sf.value = x + case reflect.Int32: + x, err := strconv.ParseInt(prop.Default, 10, 32) + if err != nil { + return nil, false, fmt.Errorf("proto: bad default int32 %q: %v", prop.Default, err) + } + sf.value = int32(x) + case reflect.Int64: + x, err := strconv.ParseInt(prop.Default, 10, 64) + if err != nil { + return nil, false, fmt.Errorf("proto: bad default int64 %q: %v", prop.Default, err) + } + sf.value = x + case reflect.String: + sf.value = prop.Default + case reflect.Uint8: + // []byte (not *uint8) + sf.value = []byte(prop.Default) + case reflect.Uint32: + x, err := strconv.ParseUint(prop.Default, 10, 32) + if err != nil { + return nil, false, fmt.Errorf("proto: bad default uint32 %q: %v", prop.Default, err) + } + sf.value = uint32(x) + case reflect.Uint64: + x, err := strconv.ParseUint(prop.Default, 10, 64) + if err != nil { + return nil, false, fmt.Errorf("proto: bad default uint64 %q: %v", prop.Default, err) + } + sf.value = x + default: + return nil, false, fmt.Errorf("proto: unhandled def kind %v", ft.Elem().Kind()) + } + + return sf, false, nil +} + +// Map fields may have key types of non-float scalars, strings and enums. +// The easiest way to sort them in some deterministic order is to use fmt. +// If this turns out to be inefficient we can always consider other options, +// such as doing a Schwartzian transform. + +func mapKeys(vs []reflect.Value) sort.Interface { + s := mapKeySorter{ + vs: vs, + // default Less function: textual comparison + less: func(a, b reflect.Value) bool { + return fmt.Sprint(a.Interface()) < fmt.Sprint(b.Interface()) + }, + } + + // Type specialization per https://developers.google.com/protocol-buffers/docs/proto#maps; + // numeric keys are sorted numerically. + if len(vs) == 0 { + return s + } + switch vs[0].Kind() { + case reflect.Int32, reflect.Int64: + s.less = func(a, b reflect.Value) bool { return a.Int() < b.Int() } + case reflect.Uint32, reflect.Uint64: + s.less = func(a, b reflect.Value) bool { return a.Uint() < b.Uint() } + } + + return s +} + +type mapKeySorter struct { + vs []reflect.Value + less func(a, b reflect.Value) bool +} + +func (s mapKeySorter) Len() int { return len(s.vs) } +func (s mapKeySorter) Swap(i, j int) { s.vs[i], s.vs[j] = s.vs[j], s.vs[i] } +func (s mapKeySorter) Less(i, j int) bool { + return s.less(s.vs[i], s.vs[j]) +} + +// isProto3Zero reports whether v is a zero proto3 value. +func isProto3Zero(v reflect.Value) bool { + switch v.Kind() { + case reflect.Bool: + return !v.Bool() + case reflect.Int32, reflect.Int64: + return v.Int() == 0 + case reflect.Uint32, reflect.Uint64: + return v.Uint() == 0 + case reflect.Float32, reflect.Float64: + return v.Float() == 0 + case reflect.String: + return v.String() == "" + } + return false +} + +// ProtoPackageIsVersion1 is referenced from generated protocol buffer files +// to assert that that code is compatible with this version of the proto package. +const ProtoPackageIsVersion1 = true diff --git a/vendor/github.com/golang/protobuf/proto/message_set.go b/vendor/github.com/golang/protobuf/proto/message_set.go new file mode 100644 index 000000000..e25e01e63 --- /dev/null +++ b/vendor/github.com/golang/protobuf/proto/message_set.go @@ -0,0 +1,280 @@ +// Go support for Protocol Buffers - Google's data interchange format +// +// Copyright 2010 The Go Authors. All rights reserved. +// https://github.com/golang/protobuf +// +// Redistribution and use in source and binary forms, with or without +// modification, are permitted provided that the following conditions are +// met: +// +// * Redistributions of source code must retain the above copyright +// notice, this list of conditions and the following disclaimer. +// * Redistributions in binary form must reproduce the above +// copyright notice, this list of conditions and the following disclaimer +// in the documentation and/or other materials provided with the +// distribution. +// * Neither the name of Google Inc. nor the names of its +// contributors may be used to endorse or promote products derived from +// this software without specific prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +package proto + +/* + * Support for message sets. + */ + +import ( + "bytes" + "encoding/json" + "errors" + "fmt" + "reflect" + "sort" +) + +// errNoMessageTypeID occurs when a protocol buffer does not have a message type ID. +// A message type ID is required for storing a protocol buffer in a message set. +var errNoMessageTypeID = errors.New("proto does not have a message type ID") + +// The first two types (_MessageSet_Item and messageSet) +// model what the protocol compiler produces for the following protocol message: +// message MessageSet { +// repeated group Item = 1 { +// required int32 type_id = 2; +// required string message = 3; +// }; +// } +// That is the MessageSet wire format. We can't use a proto to generate these +// because that would introduce a circular dependency between it and this package. + +type _MessageSet_Item struct { + TypeId *int32 `protobuf:"varint,2,req,name=type_id"` + Message []byte `protobuf:"bytes,3,req,name=message"` +} + +type messageSet struct { + Item []*_MessageSet_Item `protobuf:"group,1,rep"` + XXX_unrecognized []byte + // TODO: caching? +} + +// Make sure messageSet is a Message. +var _ Message = (*messageSet)(nil) + +// messageTypeIder is an interface satisfied by a protocol buffer type +// that may be stored in a MessageSet. +type messageTypeIder interface { + MessageTypeId() int32 +} + +func (ms *messageSet) find(pb Message) *_MessageSet_Item { + mti, ok := pb.(messageTypeIder) + if !ok { + return nil + } + id := mti.MessageTypeId() + for _, item := range ms.Item { + if *item.TypeId == id { + return item + } + } + return nil +} + +func (ms *messageSet) Has(pb Message) bool { + if ms.find(pb) != nil { + return true + } + return false +} + +func (ms *messageSet) Unmarshal(pb Message) error { + if item := ms.find(pb); item != nil { + return Unmarshal(item.Message, pb) + } + if _, ok := pb.(messageTypeIder); !ok { + return errNoMessageTypeID + } + return nil // TODO: return error instead? +} + +func (ms *messageSet) Marshal(pb Message) error { + msg, err := Marshal(pb) + if err != nil { + return err + } + if item := ms.find(pb); item != nil { + // reuse existing item + item.Message = msg + return nil + } + + mti, ok := pb.(messageTypeIder) + if !ok { + return errNoMessageTypeID + } + + mtid := mti.MessageTypeId() + ms.Item = append(ms.Item, &_MessageSet_Item{ + TypeId: &mtid, + Message: msg, + }) + return nil +} + +func (ms *messageSet) Reset() { *ms = messageSet{} } +func (ms *messageSet) String() string { return CompactTextString(ms) } +func (*messageSet) ProtoMessage() {} + +// Support for the message_set_wire_format message option. + +func skipVarint(buf []byte) []byte { + i := 0 + for ; buf[i]&0x80 != 0; i++ { + } + return buf[i+1:] +} + +// MarshalMessageSet encodes the extension map represented by m in the message set wire format. +// It is called by generated Marshal methods on protocol buffer messages with the message_set_wire_format option. +func MarshalMessageSet(m map[int32]Extension) ([]byte, error) { + if err := encodeExtensionMap(m); err != nil { + return nil, err + } + + // Sort extension IDs to provide a deterministic encoding. + // See also enc_map in encode.go. + ids := make([]int, 0, len(m)) + for id := range m { + ids = append(ids, int(id)) + } + sort.Ints(ids) + + ms := &messageSet{Item: make([]*_MessageSet_Item, 0, len(m))} + for _, id := range ids { + e := m[int32(id)] + // Remove the wire type and field number varint, as well as the length varint. + msg := skipVarint(skipVarint(e.enc)) + + ms.Item = append(ms.Item, &_MessageSet_Item{ + TypeId: Int32(int32(id)), + Message: msg, + }) + } + return Marshal(ms) +} + +// UnmarshalMessageSet decodes the extension map encoded in buf in the message set wire format. +// It is called by generated Unmarshal methods on protocol buffer messages with the message_set_wire_format option. +func UnmarshalMessageSet(buf []byte, m map[int32]Extension) error { + ms := new(messageSet) + if err := Unmarshal(buf, ms); err != nil { + return err + } + for _, item := range ms.Item { + id := *item.TypeId + msg := item.Message + + // Restore wire type and field number varint, plus length varint. + // Be careful to preserve duplicate items. + b := EncodeVarint(uint64(id)<<3 | WireBytes) + if ext, ok := m[id]; ok { + // Existing data; rip off the tag and length varint + // so we join the new data correctly. + // We can assume that ext.enc is set because we are unmarshaling. + o := ext.enc[len(b):] // skip wire type and field number + _, n := DecodeVarint(o) // calculate length of length varint + o = o[n:] // skip length varint + msg = append(o, msg...) // join old data and new data + } + b = append(b, EncodeVarint(uint64(len(msg)))...) + b = append(b, msg...) + + m[id] = Extension{enc: b} + } + return nil +} + +// MarshalMessageSetJSON encodes the extension map represented by m in JSON format. +// It is called by generated MarshalJSON methods on protocol buffer messages with the message_set_wire_format option. +func MarshalMessageSetJSON(m map[int32]Extension) ([]byte, error) { + var b bytes.Buffer + b.WriteByte('{') + + // Process the map in key order for deterministic output. + ids := make([]int32, 0, len(m)) + for id := range m { + ids = append(ids, id) + } + sort.Sort(int32Slice(ids)) // int32Slice defined in text.go + + for i, id := range ids { + ext := m[id] + if i > 0 { + b.WriteByte(',') + } + + msd, ok := messageSetMap[id] + if !ok { + // Unknown type; we can't render it, so skip it. + continue + } + fmt.Fprintf(&b, `"[%s]":`, msd.name) + + x := ext.value + if x == nil { + x = reflect.New(msd.t.Elem()).Interface() + if err := Unmarshal(ext.enc, x.(Message)); err != nil { + return nil, err + } + } + d, err := json.Marshal(x) + if err != nil { + return nil, err + } + b.Write(d) + } + b.WriteByte('}') + return b.Bytes(), nil +} + +// UnmarshalMessageSetJSON decodes the extension map encoded in buf in JSON format. +// It is called by generated UnmarshalJSON methods on protocol buffer messages with the message_set_wire_format option. +func UnmarshalMessageSetJSON(buf []byte, m map[int32]Extension) error { + // Common-case fast path. + if len(buf) == 0 || bytes.Equal(buf, []byte("{}")) { + return nil + } + + // This is fairly tricky, and it's not clear that it is needed. + return errors.New("TODO: UnmarshalMessageSetJSON not yet implemented") +} + +// A global registry of types that can be used in a MessageSet. + +var messageSetMap = make(map[int32]messageSetDesc) + +type messageSetDesc struct { + t reflect.Type // pointer to struct + name string +} + +// RegisterMessageSetType is called from the generated code. +func RegisterMessageSetType(m Message, fieldNum int32, name string) { + messageSetMap[fieldNum] = messageSetDesc{ + t: reflect.TypeOf(m), + name: name, + } +} diff --git a/vendor/github.com/golang/protobuf/proto/pointer_reflect.go b/vendor/github.com/golang/protobuf/proto/pointer_reflect.go new file mode 100644 index 000000000..749919d25 --- /dev/null +++ b/vendor/github.com/golang/protobuf/proto/pointer_reflect.go @@ -0,0 +1,479 @@ +// Go support for Protocol Buffers - Google's data interchange format +// +// Copyright 2012 The Go Authors. All rights reserved. +// https://github.com/golang/protobuf +// +// Redistribution and use in source and binary forms, with or without +// modification, are permitted provided that the following conditions are +// met: +// +// * Redistributions of source code must retain the above copyright +// notice, this list of conditions and the following disclaimer. +// * Redistributions in binary form must reproduce the above +// copyright notice, this list of conditions and the following disclaimer +// in the documentation and/or other materials provided with the +// distribution. +// * Neither the name of Google Inc. nor the names of its +// contributors may be used to endorse or promote products derived from +// this software without specific prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +// +build appengine + +// This file contains an implementation of proto field accesses using package reflect. +// It is slower than the code in pointer_unsafe.go but it avoids package unsafe and can +// be used on App Engine. + +package proto + +import ( + "math" + "reflect" +) + +// A structPointer is a pointer to a struct. +type structPointer struct { + v reflect.Value +} + +// toStructPointer returns a structPointer equivalent to the given reflect value. +// The reflect value must itself be a pointer to a struct. +func toStructPointer(v reflect.Value) structPointer { + return structPointer{v} +} + +// IsNil reports whether p is nil. +func structPointer_IsNil(p structPointer) bool { + return p.v.IsNil() +} + +// Interface returns the struct pointer as an interface value. +func structPointer_Interface(p structPointer, _ reflect.Type) interface{} { + return p.v.Interface() +} + +// A field identifies a field in a struct, accessible from a structPointer. +// In this implementation, a field is identified by the sequence of field indices +// passed to reflect's FieldByIndex. +type field []int + +// toField returns a field equivalent to the given reflect field. +func toField(f *reflect.StructField) field { + return f.Index +} + +// invalidField is an invalid field identifier. +var invalidField = field(nil) + +// IsValid reports whether the field identifier is valid. +func (f field) IsValid() bool { return f != nil } + +// field returns the given field in the struct as a reflect value. +func structPointer_field(p structPointer, f field) reflect.Value { + // Special case: an extension map entry with a value of type T + // passes a *T to the struct-handling code with a zero field, + // expecting that it will be treated as equivalent to *struct{ X T }, + // which has the same memory layout. We have to handle that case + // specially, because reflect will panic if we call FieldByIndex on a + // non-struct. + if f == nil { + return p.v.Elem() + } + + return p.v.Elem().FieldByIndex(f) +} + +// ifield returns the given field in the struct as an interface value. +func structPointer_ifield(p structPointer, f field) interface{} { + return structPointer_field(p, f).Addr().Interface() +} + +// Bytes returns the address of a []byte field in the struct. +func structPointer_Bytes(p structPointer, f field) *[]byte { + return structPointer_ifield(p, f).(*[]byte) +} + +// BytesSlice returns the address of a [][]byte field in the struct. +func structPointer_BytesSlice(p structPointer, f field) *[][]byte { + return structPointer_ifield(p, f).(*[][]byte) +} + +// Bool returns the address of a *bool field in the struct. +func structPointer_Bool(p structPointer, f field) **bool { + return structPointer_ifield(p, f).(**bool) +} + +// BoolVal returns the address of a bool field in the struct. +func structPointer_BoolVal(p structPointer, f field) *bool { + return structPointer_ifield(p, f).(*bool) +} + +// BoolSlice returns the address of a []bool field in the struct. +func structPointer_BoolSlice(p structPointer, f field) *[]bool { + return structPointer_ifield(p, f).(*[]bool) +} + +// String returns the address of a *string field in the struct. +func structPointer_String(p structPointer, f field) **string { + return structPointer_ifield(p, f).(**string) +} + +// StringVal returns the address of a string field in the struct. +func structPointer_StringVal(p structPointer, f field) *string { + return structPointer_ifield(p, f).(*string) +} + +// StringSlice returns the address of a []string field in the struct. +func structPointer_StringSlice(p structPointer, f field) *[]string { + return structPointer_ifield(p, f).(*[]string) +} + +// ExtMap returns the address of an extension map field in the struct. +func structPointer_ExtMap(p structPointer, f field) *map[int32]Extension { + return structPointer_ifield(p, f).(*map[int32]Extension) +} + +// NewAt returns the reflect.Value for a pointer to a field in the struct. +func structPointer_NewAt(p structPointer, f field, typ reflect.Type) reflect.Value { + return structPointer_field(p, f).Addr() +} + +// SetStructPointer writes a *struct field in the struct. +func structPointer_SetStructPointer(p structPointer, f field, q structPointer) { + structPointer_field(p, f).Set(q.v) +} + +// GetStructPointer reads a *struct field in the struct. +func structPointer_GetStructPointer(p structPointer, f field) structPointer { + return structPointer{structPointer_field(p, f)} +} + +// StructPointerSlice the address of a []*struct field in the struct. +func structPointer_StructPointerSlice(p structPointer, f field) structPointerSlice { + return structPointerSlice{structPointer_field(p, f)} +} + +// A structPointerSlice represents the address of a slice of pointers to structs +// (themselves messages or groups). That is, v.Type() is *[]*struct{...}. +type structPointerSlice struct { + v reflect.Value +} + +func (p structPointerSlice) Len() int { return p.v.Len() } +func (p structPointerSlice) Index(i int) structPointer { return structPointer{p.v.Index(i)} } +func (p structPointerSlice) Append(q structPointer) { + p.v.Set(reflect.Append(p.v, q.v)) +} + +var ( + int32Type = reflect.TypeOf(int32(0)) + uint32Type = reflect.TypeOf(uint32(0)) + float32Type = reflect.TypeOf(float32(0)) + int64Type = reflect.TypeOf(int64(0)) + uint64Type = reflect.TypeOf(uint64(0)) + float64Type = reflect.TypeOf(float64(0)) +) + +// A word32 represents a field of type *int32, *uint32, *float32, or *enum. +// That is, v.Type() is *int32, *uint32, *float32, or *enum and v is assignable. +type word32 struct { + v reflect.Value +} + +// IsNil reports whether p is nil. +func word32_IsNil(p word32) bool { + return p.v.IsNil() +} + +// Set sets p to point at a newly allocated word with bits set to x. +func word32_Set(p word32, o *Buffer, x uint32) { + t := p.v.Type().Elem() + switch t { + case int32Type: + if len(o.int32s) == 0 { + o.int32s = make([]int32, uint32PoolSize) + } + o.int32s[0] = int32(x) + p.v.Set(reflect.ValueOf(&o.int32s[0])) + o.int32s = o.int32s[1:] + return + case uint32Type: + if len(o.uint32s) == 0 { + o.uint32s = make([]uint32, uint32PoolSize) + } + o.uint32s[0] = x + p.v.Set(reflect.ValueOf(&o.uint32s[0])) + o.uint32s = o.uint32s[1:] + return + case float32Type: + if len(o.float32s) == 0 { + o.float32s = make([]float32, uint32PoolSize) + } + o.float32s[0] = math.Float32frombits(x) + p.v.Set(reflect.ValueOf(&o.float32s[0])) + o.float32s = o.float32s[1:] + return + } + + // must be enum + p.v.Set(reflect.New(t)) + p.v.Elem().SetInt(int64(int32(x))) +} + +// Get gets the bits pointed at by p, as a uint32. +func word32_Get(p word32) uint32 { + elem := p.v.Elem() + switch elem.Kind() { + case reflect.Int32: + return uint32(elem.Int()) + case reflect.Uint32: + return uint32(elem.Uint()) + case reflect.Float32: + return math.Float32bits(float32(elem.Float())) + } + panic("unreachable") +} + +// Word32 returns a reference to a *int32, *uint32, *float32, or *enum field in the struct. +func structPointer_Word32(p structPointer, f field) word32 { + return word32{structPointer_field(p, f)} +} + +// A word32Val represents a field of type int32, uint32, float32, or enum. +// That is, v.Type() is int32, uint32, float32, or enum and v is assignable. +type word32Val struct { + v reflect.Value +} + +// Set sets *p to x. +func word32Val_Set(p word32Val, x uint32) { + switch p.v.Type() { + case int32Type: + p.v.SetInt(int64(x)) + return + case uint32Type: + p.v.SetUint(uint64(x)) + return + case float32Type: + p.v.SetFloat(float64(math.Float32frombits(x))) + return + } + + // must be enum + p.v.SetInt(int64(int32(x))) +} + +// Get gets the bits pointed at by p, as a uint32. +func word32Val_Get(p word32Val) uint32 { + elem := p.v + switch elem.Kind() { + case reflect.Int32: + return uint32(elem.Int()) + case reflect.Uint32: + return uint32(elem.Uint()) + case reflect.Float32: + return math.Float32bits(float32(elem.Float())) + } + panic("unreachable") +} + +// Word32Val returns a reference to a int32, uint32, float32, or enum field in the struct. +func structPointer_Word32Val(p structPointer, f field) word32Val { + return word32Val{structPointer_field(p, f)} +} + +// A word32Slice is a slice of 32-bit values. +// That is, v.Type() is []int32, []uint32, []float32, or []enum. +type word32Slice struct { + v reflect.Value +} + +func (p word32Slice) Append(x uint32) { + n, m := p.v.Len(), p.v.Cap() + if n < m { + p.v.SetLen(n + 1) + } else { + t := p.v.Type().Elem() + p.v.Set(reflect.Append(p.v, reflect.Zero(t))) + } + elem := p.v.Index(n) + switch elem.Kind() { + case reflect.Int32: + elem.SetInt(int64(int32(x))) + case reflect.Uint32: + elem.SetUint(uint64(x)) + case reflect.Float32: + elem.SetFloat(float64(math.Float32frombits(x))) + } +} + +func (p word32Slice) Len() int { + return p.v.Len() +} + +func (p word32Slice) Index(i int) uint32 { + elem := p.v.Index(i) + switch elem.Kind() { + case reflect.Int32: + return uint32(elem.Int()) + case reflect.Uint32: + return uint32(elem.Uint()) + case reflect.Float32: + return math.Float32bits(float32(elem.Float())) + } + panic("unreachable") +} + +// Word32Slice returns a reference to a []int32, []uint32, []float32, or []enum field in the struct. +func structPointer_Word32Slice(p structPointer, f field) word32Slice { + return word32Slice{structPointer_field(p, f)} +} + +// word64 is like word32 but for 64-bit values. +type word64 struct { + v reflect.Value +} + +func word64_Set(p word64, o *Buffer, x uint64) { + t := p.v.Type().Elem() + switch t { + case int64Type: + if len(o.int64s) == 0 { + o.int64s = make([]int64, uint64PoolSize) + } + o.int64s[0] = int64(x) + p.v.Set(reflect.ValueOf(&o.int64s[0])) + o.int64s = o.int64s[1:] + return + case uint64Type: + if len(o.uint64s) == 0 { + o.uint64s = make([]uint64, uint64PoolSize) + } + o.uint64s[0] = x + p.v.Set(reflect.ValueOf(&o.uint64s[0])) + o.uint64s = o.uint64s[1:] + return + case float64Type: + if len(o.float64s) == 0 { + o.float64s = make([]float64, uint64PoolSize) + } + o.float64s[0] = math.Float64frombits(x) + p.v.Set(reflect.ValueOf(&o.float64s[0])) + o.float64s = o.float64s[1:] + return + } + panic("unreachable") +} + +func word64_IsNil(p word64) bool { + return p.v.IsNil() +} + +func word64_Get(p word64) uint64 { + elem := p.v.Elem() + switch elem.Kind() { + case reflect.Int64: + return uint64(elem.Int()) + case reflect.Uint64: + return elem.Uint() + case reflect.Float64: + return math.Float64bits(elem.Float()) + } + panic("unreachable") +} + +func structPointer_Word64(p structPointer, f field) word64 { + return word64{structPointer_field(p, f)} +} + +// word64Val is like word32Val but for 64-bit values. +type word64Val struct { + v reflect.Value +} + +func word64Val_Set(p word64Val, o *Buffer, x uint64) { + switch p.v.Type() { + case int64Type: + p.v.SetInt(int64(x)) + return + case uint64Type: + p.v.SetUint(x) + return + case float64Type: + p.v.SetFloat(math.Float64frombits(x)) + return + } + panic("unreachable") +} + +func word64Val_Get(p word64Val) uint64 { + elem := p.v + switch elem.Kind() { + case reflect.Int64: + return uint64(elem.Int()) + case reflect.Uint64: + return elem.Uint() + case reflect.Float64: + return math.Float64bits(elem.Float()) + } + panic("unreachable") +} + +func structPointer_Word64Val(p structPointer, f field) word64Val { + return word64Val{structPointer_field(p, f)} +} + +type word64Slice struct { + v reflect.Value +} + +func (p word64Slice) Append(x uint64) { + n, m := p.v.Len(), p.v.Cap() + if n < m { + p.v.SetLen(n + 1) + } else { + t := p.v.Type().Elem() + p.v.Set(reflect.Append(p.v, reflect.Zero(t))) + } + elem := p.v.Index(n) + switch elem.Kind() { + case reflect.Int64: + elem.SetInt(int64(int64(x))) + case reflect.Uint64: + elem.SetUint(uint64(x)) + case reflect.Float64: + elem.SetFloat(float64(math.Float64frombits(x))) + } +} + +func (p word64Slice) Len() int { + return p.v.Len() +} + +func (p word64Slice) Index(i int) uint64 { + elem := p.v.Index(i) + switch elem.Kind() { + case reflect.Int64: + return uint64(elem.Int()) + case reflect.Uint64: + return uint64(elem.Uint()) + case reflect.Float64: + return math.Float64bits(float64(elem.Float())) + } + panic("unreachable") +} + +func structPointer_Word64Slice(p structPointer, f field) word64Slice { + return word64Slice{structPointer_field(p, f)} +} diff --git a/vendor/github.com/golang/protobuf/proto/pointer_unsafe.go b/vendor/github.com/golang/protobuf/proto/pointer_unsafe.go new file mode 100644 index 000000000..e9be0fe92 --- /dev/null +++ b/vendor/github.com/golang/protobuf/proto/pointer_unsafe.go @@ -0,0 +1,266 @@ +// Go support for Protocol Buffers - Google's data interchange format +// +// Copyright 2012 The Go Authors. All rights reserved. +// https://github.com/golang/protobuf +// +// Redistribution and use in source and binary forms, with or without +// modification, are permitted provided that the following conditions are +// met: +// +// * Redistributions of source code must retain the above copyright +// notice, this list of conditions and the following disclaimer. +// * Redistributions in binary form must reproduce the above +// copyright notice, this list of conditions and the following disclaimer +// in the documentation and/or other materials provided with the +// distribution. +// * Neither the name of Google Inc. nor the names of its +// contributors may be used to endorse or promote products derived from +// this software without specific prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +// +build !appengine + +// This file contains the implementation of the proto field accesses using package unsafe. + +package proto + +import ( + "reflect" + "unsafe" +) + +// NOTE: These type_Foo functions would more idiomatically be methods, +// but Go does not allow methods on pointer types, and we must preserve +// some pointer type for the garbage collector. We use these +// funcs with clunky names as our poor approximation to methods. +// +// An alternative would be +// type structPointer struct { p unsafe.Pointer } +// but that does not registerize as well. + +// A structPointer is a pointer to a struct. +type structPointer unsafe.Pointer + +// toStructPointer returns a structPointer equivalent to the given reflect value. +func toStructPointer(v reflect.Value) structPointer { + return structPointer(unsafe.Pointer(v.Pointer())) +} + +// IsNil reports whether p is nil. +func structPointer_IsNil(p structPointer) bool { + return p == nil +} + +// Interface returns the struct pointer, assumed to have element type t, +// as an interface value. +func structPointer_Interface(p structPointer, t reflect.Type) interface{} { + return reflect.NewAt(t, unsafe.Pointer(p)).Interface() +} + +// A field identifies a field in a struct, accessible from a structPointer. +// In this implementation, a field is identified by its byte offset from the start of the struct. +type field uintptr + +// toField returns a field equivalent to the given reflect field. +func toField(f *reflect.StructField) field { + return field(f.Offset) +} + +// invalidField is an invalid field identifier. +const invalidField = ^field(0) + +// IsValid reports whether the field identifier is valid. +func (f field) IsValid() bool { + return f != ^field(0) +} + +// Bytes returns the address of a []byte field in the struct. +func structPointer_Bytes(p structPointer, f field) *[]byte { + return (*[]byte)(unsafe.Pointer(uintptr(p) + uintptr(f))) +} + +// BytesSlice returns the address of a [][]byte field in the struct. +func structPointer_BytesSlice(p structPointer, f field) *[][]byte { + return (*[][]byte)(unsafe.Pointer(uintptr(p) + uintptr(f))) +} + +// Bool returns the address of a *bool field in the struct. +func structPointer_Bool(p structPointer, f field) **bool { + return (**bool)(unsafe.Pointer(uintptr(p) + uintptr(f))) +} + +// BoolVal returns the address of a bool field in the struct. +func structPointer_BoolVal(p structPointer, f field) *bool { + return (*bool)(unsafe.Pointer(uintptr(p) + uintptr(f))) +} + +// BoolSlice returns the address of a []bool field in the struct. +func structPointer_BoolSlice(p structPointer, f field) *[]bool { + return (*[]bool)(unsafe.Pointer(uintptr(p) + uintptr(f))) +} + +// String returns the address of a *string field in the struct. +func structPointer_String(p structPointer, f field) **string { + return (**string)(unsafe.Pointer(uintptr(p) + uintptr(f))) +} + +// StringVal returns the address of a string field in the struct. +func structPointer_StringVal(p structPointer, f field) *string { + return (*string)(unsafe.Pointer(uintptr(p) + uintptr(f))) +} + +// StringSlice returns the address of a []string field in the struct. +func structPointer_StringSlice(p structPointer, f field) *[]string { + return (*[]string)(unsafe.Pointer(uintptr(p) + uintptr(f))) +} + +// ExtMap returns the address of an extension map field in the struct. +func structPointer_ExtMap(p structPointer, f field) *map[int32]Extension { + return (*map[int32]Extension)(unsafe.Pointer(uintptr(p) + uintptr(f))) +} + +// NewAt returns the reflect.Value for a pointer to a field in the struct. +func structPointer_NewAt(p structPointer, f field, typ reflect.Type) reflect.Value { + return reflect.NewAt(typ, unsafe.Pointer(uintptr(p)+uintptr(f))) +} + +// SetStructPointer writes a *struct field in the struct. +func structPointer_SetStructPointer(p structPointer, f field, q structPointer) { + *(*structPointer)(unsafe.Pointer(uintptr(p) + uintptr(f))) = q +} + +// GetStructPointer reads a *struct field in the struct. +func structPointer_GetStructPointer(p structPointer, f field) structPointer { + return *(*structPointer)(unsafe.Pointer(uintptr(p) + uintptr(f))) +} + +// StructPointerSlice the address of a []*struct field in the struct. +func structPointer_StructPointerSlice(p structPointer, f field) *structPointerSlice { + return (*structPointerSlice)(unsafe.Pointer(uintptr(p) + uintptr(f))) +} + +// A structPointerSlice represents a slice of pointers to structs (themselves submessages or groups). +type structPointerSlice []structPointer + +func (v *structPointerSlice) Len() int { return len(*v) } +func (v *structPointerSlice) Index(i int) structPointer { return (*v)[i] } +func (v *structPointerSlice) Append(p structPointer) { *v = append(*v, p) } + +// A word32 is the address of a "pointer to 32-bit value" field. +type word32 **uint32 + +// IsNil reports whether *v is nil. +func word32_IsNil(p word32) bool { + return *p == nil +} + +// Set sets *v to point at a newly allocated word set to x. +func word32_Set(p word32, o *Buffer, x uint32) { + if len(o.uint32s) == 0 { + o.uint32s = make([]uint32, uint32PoolSize) + } + o.uint32s[0] = x + *p = &o.uint32s[0] + o.uint32s = o.uint32s[1:] +} + +// Get gets the value pointed at by *v. +func word32_Get(p word32) uint32 { + return **p +} + +// Word32 returns the address of a *int32, *uint32, *float32, or *enum field in the struct. +func structPointer_Word32(p structPointer, f field) word32 { + return word32((**uint32)(unsafe.Pointer(uintptr(p) + uintptr(f)))) +} + +// A word32Val is the address of a 32-bit value field. +type word32Val *uint32 + +// Set sets *p to x. +func word32Val_Set(p word32Val, x uint32) { + *p = x +} + +// Get gets the value pointed at by p. +func word32Val_Get(p word32Val) uint32 { + return *p +} + +// Word32Val returns the address of a *int32, *uint32, *float32, or *enum field in the struct. +func structPointer_Word32Val(p structPointer, f field) word32Val { + return word32Val((*uint32)(unsafe.Pointer(uintptr(p) + uintptr(f)))) +} + +// A word32Slice is a slice of 32-bit values. +type word32Slice []uint32 + +func (v *word32Slice) Append(x uint32) { *v = append(*v, x) } +func (v *word32Slice) Len() int { return len(*v) } +func (v *word32Slice) Index(i int) uint32 { return (*v)[i] } + +// Word32Slice returns the address of a []int32, []uint32, []float32, or []enum field in the struct. +func structPointer_Word32Slice(p structPointer, f field) *word32Slice { + return (*word32Slice)(unsafe.Pointer(uintptr(p) + uintptr(f))) +} + +// word64 is like word32 but for 64-bit values. +type word64 **uint64 + +func word64_Set(p word64, o *Buffer, x uint64) { + if len(o.uint64s) == 0 { + o.uint64s = make([]uint64, uint64PoolSize) + } + o.uint64s[0] = x + *p = &o.uint64s[0] + o.uint64s = o.uint64s[1:] +} + +func word64_IsNil(p word64) bool { + return *p == nil +} + +func word64_Get(p word64) uint64 { + return **p +} + +func structPointer_Word64(p structPointer, f field) word64 { + return word64((**uint64)(unsafe.Pointer(uintptr(p) + uintptr(f)))) +} + +// word64Val is like word32Val but for 64-bit values. +type word64Val *uint64 + +func word64Val_Set(p word64Val, o *Buffer, x uint64) { + *p = x +} + +func word64Val_Get(p word64Val) uint64 { + return *p +} + +func structPointer_Word64Val(p structPointer, f field) word64Val { + return word64Val((*uint64)(unsafe.Pointer(uintptr(p) + uintptr(f)))) +} + +// word64Slice is like word32Slice but for 64-bit values. +type word64Slice []uint64 + +func (v *word64Slice) Append(x uint64) { *v = append(*v, x) } +func (v *word64Slice) Len() int { return len(*v) } +func (v *word64Slice) Index(i int) uint64 { return (*v)[i] } + +func structPointer_Word64Slice(p structPointer, f field) *word64Slice { + return (*word64Slice)(unsafe.Pointer(uintptr(p) + uintptr(f))) +} diff --git a/vendor/github.com/golang/protobuf/proto/properties.go b/vendor/github.com/golang/protobuf/proto/properties.go new file mode 100644 index 000000000..4fe2ec22e --- /dev/null +++ b/vendor/github.com/golang/protobuf/proto/properties.go @@ -0,0 +1,846 @@ +// Go support for Protocol Buffers - Google's data interchange format +// +// Copyright 2010 The Go Authors. All rights reserved. +// https://github.com/golang/protobuf +// +// Redistribution and use in source and binary forms, with or without +// modification, are permitted provided that the following conditions are +// met: +// +// * Redistributions of source code must retain the above copyright +// notice, this list of conditions and the following disclaimer. +// * Redistributions in binary form must reproduce the above +// copyright notice, this list of conditions and the following disclaimer +// in the documentation and/or other materials provided with the +// distribution. +// * Neither the name of Google Inc. nor the names of its +// contributors may be used to endorse or promote products derived from +// this software without specific prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +package proto + +/* + * Routines for encoding data into the wire format for protocol buffers. + */ + +import ( + "fmt" + "log" + "os" + "reflect" + "sort" + "strconv" + "strings" + "sync" +) + +const debug bool = false + +// Constants that identify the encoding of a value on the wire. +const ( + WireVarint = 0 + WireFixed64 = 1 + WireBytes = 2 + WireStartGroup = 3 + WireEndGroup = 4 + WireFixed32 = 5 +) + +const startSize = 10 // initial slice/string sizes + +// Encoders are defined in encode.go +// An encoder outputs the full representation of a field, including its +// tag and encoder type. +type encoder func(p *Buffer, prop *Properties, base structPointer) error + +// A valueEncoder encodes a single integer in a particular encoding. +type valueEncoder func(o *Buffer, x uint64) error + +// Sizers are defined in encode.go +// A sizer returns the encoded size of a field, including its tag and encoder +// type. +type sizer func(prop *Properties, base structPointer) int + +// A valueSizer returns the encoded size of a single integer in a particular +// encoding. +type valueSizer func(x uint64) int + +// Decoders are defined in decode.go +// A decoder creates a value from its wire representation. +// Unrecognized subelements are saved in unrec. +type decoder func(p *Buffer, prop *Properties, base structPointer) error + +// A valueDecoder decodes a single integer in a particular encoding. +type valueDecoder func(o *Buffer) (x uint64, err error) + +// A oneofMarshaler does the marshaling for all oneof fields in a message. +type oneofMarshaler func(Message, *Buffer) error + +// A oneofUnmarshaler does the unmarshaling for a oneof field in a message. +type oneofUnmarshaler func(Message, int, int, *Buffer) (bool, error) + +// A oneofSizer does the sizing for all oneof fields in a message. +type oneofSizer func(Message) int + +// tagMap is an optimization over map[int]int for typical protocol buffer +// use-cases. Encoded protocol buffers are often in tag order with small tag +// numbers. +type tagMap struct { + fastTags []int + slowTags map[int]int +} + +// tagMapFastLimit is the upper bound on the tag number that will be stored in +// the tagMap slice rather than its map. +const tagMapFastLimit = 1024 + +func (p *tagMap) get(t int) (int, bool) { + if t > 0 && t < tagMapFastLimit { + if t >= len(p.fastTags) { + return 0, false + } + fi := p.fastTags[t] + return fi, fi >= 0 + } + fi, ok := p.slowTags[t] + return fi, ok +} + +func (p *tagMap) put(t int, fi int) { + if t > 0 && t < tagMapFastLimit { + for len(p.fastTags) < t+1 { + p.fastTags = append(p.fastTags, -1) + } + p.fastTags[t] = fi + return + } + if p.slowTags == nil { + p.slowTags = make(map[int]int) + } + p.slowTags[t] = fi +} + +// StructProperties represents properties for all the fields of a struct. +// decoderTags and decoderOrigNames should only be used by the decoder. +type StructProperties struct { + Prop []*Properties // properties for each field + reqCount int // required count + decoderTags tagMap // map from proto tag to struct field number + decoderOrigNames map[string]int // map from original name to struct field number + order []int // list of struct field numbers in tag order + unrecField field // field id of the XXX_unrecognized []byte field + extendable bool // is this an extendable proto + + oneofMarshaler oneofMarshaler + oneofUnmarshaler oneofUnmarshaler + oneofSizer oneofSizer + stype reflect.Type + + // OneofTypes contains information about the oneof fields in this message. + // It is keyed by the original name of a field. + OneofTypes map[string]*OneofProperties +} + +// OneofProperties represents information about a specific field in a oneof. +type OneofProperties struct { + Type reflect.Type // pointer to generated struct type for this oneof field + Field int // struct field number of the containing oneof in the message + Prop *Properties +} + +// Implement the sorting interface so we can sort the fields in tag order, as recommended by the spec. +// See encode.go, (*Buffer).enc_struct. + +func (sp *StructProperties) Len() int { return len(sp.order) } +func (sp *StructProperties) Less(i, j int) bool { + return sp.Prop[sp.order[i]].Tag < sp.Prop[sp.order[j]].Tag +} +func (sp *StructProperties) Swap(i, j int) { sp.order[i], sp.order[j] = sp.order[j], sp.order[i] } + +// Properties represents the protocol-specific behavior of a single struct field. +type Properties struct { + Name string // name of the field, for error messages + OrigName string // original name before protocol compiler (always set) + JSONName string // name to use for JSON; determined by protoc + Wire string + WireType int + Tag int + Required bool + Optional bool + Repeated bool + Packed bool // relevant for repeated primitives only + Enum string // set for enum types only + proto3 bool // whether this is known to be a proto3 field; set for []byte only + oneof bool // whether this is a oneof field + + Default string // default value + HasDefault bool // whether an explicit default was provided + def_uint64 uint64 + + enc encoder + valEnc valueEncoder // set for bool and numeric types only + field field + tagcode []byte // encoding of EncodeVarint((Tag<<3)|WireType) + tagbuf [8]byte + stype reflect.Type // set for struct types only + sprop *StructProperties // set for struct types only + isMarshaler bool + isUnmarshaler bool + + mtype reflect.Type // set for map types only + mkeyprop *Properties // set for map types only + mvalprop *Properties // set for map types only + + size sizer + valSize valueSizer // set for bool and numeric types only + + dec decoder + valDec valueDecoder // set for bool and numeric types only + + // If this is a packable field, this will be the decoder for the packed version of the field. + packedDec decoder +} + +// String formats the properties in the protobuf struct field tag style. +func (p *Properties) String() string { + s := p.Wire + s = "," + s += strconv.Itoa(p.Tag) + if p.Required { + s += ",req" + } + if p.Optional { + s += ",opt" + } + if p.Repeated { + s += ",rep" + } + if p.Packed { + s += ",packed" + } + s += ",name=" + p.OrigName + if p.JSONName != p.OrigName { + s += ",json=" + p.JSONName + } + if p.proto3 { + s += ",proto3" + } + if p.oneof { + s += ",oneof" + } + if len(p.Enum) > 0 { + s += ",enum=" + p.Enum + } + if p.HasDefault { + s += ",def=" + p.Default + } + return s +} + +// Parse populates p by parsing a string in the protobuf struct field tag style. +func (p *Properties) Parse(s string) { + // "bytes,49,opt,name=foo,def=hello!" + fields := strings.Split(s, ",") // breaks def=, but handled below. + if len(fields) < 2 { + fmt.Fprintf(os.Stderr, "proto: tag has too few fields: %q\n", s) + return + } + + p.Wire = fields[0] + switch p.Wire { + case "varint": + p.WireType = WireVarint + p.valEnc = (*Buffer).EncodeVarint + p.valDec = (*Buffer).DecodeVarint + p.valSize = sizeVarint + case "fixed32": + p.WireType = WireFixed32 + p.valEnc = (*Buffer).EncodeFixed32 + p.valDec = (*Buffer).DecodeFixed32 + p.valSize = sizeFixed32 + case "fixed64": + p.WireType = WireFixed64 + p.valEnc = (*Buffer).EncodeFixed64 + p.valDec = (*Buffer).DecodeFixed64 + p.valSize = sizeFixed64 + case "zigzag32": + p.WireType = WireVarint + p.valEnc = (*Buffer).EncodeZigzag32 + p.valDec = (*Buffer).DecodeZigzag32 + p.valSize = sizeZigzag32 + case "zigzag64": + p.WireType = WireVarint + p.valEnc = (*Buffer).EncodeZigzag64 + p.valDec = (*Buffer).DecodeZigzag64 + p.valSize = sizeZigzag64 + case "bytes", "group": + p.WireType = WireBytes + // no numeric converter for non-numeric types + default: + fmt.Fprintf(os.Stderr, "proto: tag has unknown wire type: %q\n", s) + return + } + + var err error + p.Tag, err = strconv.Atoi(fields[1]) + if err != nil { + return + } + + for i := 2; i < len(fields); i++ { + f := fields[i] + switch { + case f == "req": + p.Required = true + case f == "opt": + p.Optional = true + case f == "rep": + p.Repeated = true + case f == "packed": + p.Packed = true + case strings.HasPrefix(f, "name="): + p.OrigName = f[5:] + case strings.HasPrefix(f, "json="): + p.JSONName = f[5:] + case strings.HasPrefix(f, "enum="): + p.Enum = f[5:] + case f == "proto3": + p.proto3 = true + case f == "oneof": + p.oneof = true + case strings.HasPrefix(f, "def="): + p.HasDefault = true + p.Default = f[4:] // rest of string + if i+1 < len(fields) { + // Commas aren't escaped, and def is always last. + p.Default += "," + strings.Join(fields[i+1:], ",") + break + } + } + } +} + +func logNoSliceEnc(t1, t2 reflect.Type) { + fmt.Fprintf(os.Stderr, "proto: no slice oenc for %T = []%T\n", t1, t2) +} + +var protoMessageType = reflect.TypeOf((*Message)(nil)).Elem() + +// Initialize the fields for encoding and decoding. +func (p *Properties) setEncAndDec(typ reflect.Type, f *reflect.StructField, lockGetProp bool) { + p.enc = nil + p.dec = nil + p.size = nil + + switch t1 := typ; t1.Kind() { + default: + fmt.Fprintf(os.Stderr, "proto: no coders for %v\n", t1) + + // proto3 scalar types + + case reflect.Bool: + p.enc = (*Buffer).enc_proto3_bool + p.dec = (*Buffer).dec_proto3_bool + p.size = size_proto3_bool + case reflect.Int32: + p.enc = (*Buffer).enc_proto3_int32 + p.dec = (*Buffer).dec_proto3_int32 + p.size = size_proto3_int32 + case reflect.Uint32: + p.enc = (*Buffer).enc_proto3_uint32 + p.dec = (*Buffer).dec_proto3_int32 // can reuse + p.size = size_proto3_uint32 + case reflect.Int64, reflect.Uint64: + p.enc = (*Buffer).enc_proto3_int64 + p.dec = (*Buffer).dec_proto3_int64 + p.size = size_proto3_int64 + case reflect.Float32: + p.enc = (*Buffer).enc_proto3_uint32 // can just treat them as bits + p.dec = (*Buffer).dec_proto3_int32 + p.size = size_proto3_uint32 + case reflect.Float64: + p.enc = (*Buffer).enc_proto3_int64 // can just treat them as bits + p.dec = (*Buffer).dec_proto3_int64 + p.size = size_proto3_int64 + case reflect.String: + p.enc = (*Buffer).enc_proto3_string + p.dec = (*Buffer).dec_proto3_string + p.size = size_proto3_string + + case reflect.Ptr: + switch t2 := t1.Elem(); t2.Kind() { + default: + fmt.Fprintf(os.Stderr, "proto: no encoder function for %v -> %v\n", t1, t2) + break + case reflect.Bool: + p.enc = (*Buffer).enc_bool + p.dec = (*Buffer).dec_bool + p.size = size_bool + case reflect.Int32: + p.enc = (*Buffer).enc_int32 + p.dec = (*Buffer).dec_int32 + p.size = size_int32 + case reflect.Uint32: + p.enc = (*Buffer).enc_uint32 + p.dec = (*Buffer).dec_int32 // can reuse + p.size = size_uint32 + case reflect.Int64, reflect.Uint64: + p.enc = (*Buffer).enc_int64 + p.dec = (*Buffer).dec_int64 + p.size = size_int64 + case reflect.Float32: + p.enc = (*Buffer).enc_uint32 // can just treat them as bits + p.dec = (*Buffer).dec_int32 + p.size = size_uint32 + case reflect.Float64: + p.enc = (*Buffer).enc_int64 // can just treat them as bits + p.dec = (*Buffer).dec_int64 + p.size = size_int64 + case reflect.String: + p.enc = (*Buffer).enc_string + p.dec = (*Buffer).dec_string + p.size = size_string + case reflect.Struct: + p.stype = t1.Elem() + p.isMarshaler = isMarshaler(t1) + p.isUnmarshaler = isUnmarshaler(t1) + if p.Wire == "bytes" { + p.enc = (*Buffer).enc_struct_message + p.dec = (*Buffer).dec_struct_message + p.size = size_struct_message + } else { + p.enc = (*Buffer).enc_struct_group + p.dec = (*Buffer).dec_struct_group + p.size = size_struct_group + } + } + + case reflect.Slice: + switch t2 := t1.Elem(); t2.Kind() { + default: + logNoSliceEnc(t1, t2) + break + case reflect.Bool: + if p.Packed { + p.enc = (*Buffer).enc_slice_packed_bool + p.size = size_slice_packed_bool + } else { + p.enc = (*Buffer).enc_slice_bool + p.size = size_slice_bool + } + p.dec = (*Buffer).dec_slice_bool + p.packedDec = (*Buffer).dec_slice_packed_bool + case reflect.Int32: + if p.Packed { + p.enc = (*Buffer).enc_slice_packed_int32 + p.size = size_slice_packed_int32 + } else { + p.enc = (*Buffer).enc_slice_int32 + p.size = size_slice_int32 + } + p.dec = (*Buffer).dec_slice_int32 + p.packedDec = (*Buffer).dec_slice_packed_int32 + case reflect.Uint32: + if p.Packed { + p.enc = (*Buffer).enc_slice_packed_uint32 + p.size = size_slice_packed_uint32 + } else { + p.enc = (*Buffer).enc_slice_uint32 + p.size = size_slice_uint32 + } + p.dec = (*Buffer).dec_slice_int32 + p.packedDec = (*Buffer).dec_slice_packed_int32 + case reflect.Int64, reflect.Uint64: + if p.Packed { + p.enc = (*Buffer).enc_slice_packed_int64 + p.size = size_slice_packed_int64 + } else { + p.enc = (*Buffer).enc_slice_int64 + p.size = size_slice_int64 + } + p.dec = (*Buffer).dec_slice_int64 + p.packedDec = (*Buffer).dec_slice_packed_int64 + case reflect.Uint8: + p.enc = (*Buffer).enc_slice_byte + p.dec = (*Buffer).dec_slice_byte + p.size = size_slice_byte + // This is a []byte, which is either a bytes field, + // or the value of a map field. In the latter case, + // we always encode an empty []byte, so we should not + // use the proto3 enc/size funcs. + // f == nil iff this is the key/value of a map field. + if p.proto3 && f != nil { + p.enc = (*Buffer).enc_proto3_slice_byte + p.size = size_proto3_slice_byte + } + case reflect.Float32, reflect.Float64: + switch t2.Bits() { + case 32: + // can just treat them as bits + if p.Packed { + p.enc = (*Buffer).enc_slice_packed_uint32 + p.size = size_slice_packed_uint32 + } else { + p.enc = (*Buffer).enc_slice_uint32 + p.size = size_slice_uint32 + } + p.dec = (*Buffer).dec_slice_int32 + p.packedDec = (*Buffer).dec_slice_packed_int32 + case 64: + // can just treat them as bits + if p.Packed { + p.enc = (*Buffer).enc_slice_packed_int64 + p.size = size_slice_packed_int64 + } else { + p.enc = (*Buffer).enc_slice_int64 + p.size = size_slice_int64 + } + p.dec = (*Buffer).dec_slice_int64 + p.packedDec = (*Buffer).dec_slice_packed_int64 + default: + logNoSliceEnc(t1, t2) + break + } + case reflect.String: + p.enc = (*Buffer).enc_slice_string + p.dec = (*Buffer).dec_slice_string + p.size = size_slice_string + case reflect.Ptr: + switch t3 := t2.Elem(); t3.Kind() { + default: + fmt.Fprintf(os.Stderr, "proto: no ptr oenc for %T -> %T -> %T\n", t1, t2, t3) + break + case reflect.Struct: + p.stype = t2.Elem() + p.isMarshaler = isMarshaler(t2) + p.isUnmarshaler = isUnmarshaler(t2) + if p.Wire == "bytes" { + p.enc = (*Buffer).enc_slice_struct_message + p.dec = (*Buffer).dec_slice_struct_message + p.size = size_slice_struct_message + } else { + p.enc = (*Buffer).enc_slice_struct_group + p.dec = (*Buffer).dec_slice_struct_group + p.size = size_slice_struct_group + } + } + case reflect.Slice: + switch t2.Elem().Kind() { + default: + fmt.Fprintf(os.Stderr, "proto: no slice elem oenc for %T -> %T -> %T\n", t1, t2, t2.Elem()) + break + case reflect.Uint8: + p.enc = (*Buffer).enc_slice_slice_byte + p.dec = (*Buffer).dec_slice_slice_byte + p.size = size_slice_slice_byte + } + } + + case reflect.Map: + p.enc = (*Buffer).enc_new_map + p.dec = (*Buffer).dec_new_map + p.size = size_new_map + + p.mtype = t1 + p.mkeyprop = &Properties{} + p.mkeyprop.init(reflect.PtrTo(p.mtype.Key()), "Key", f.Tag.Get("protobuf_key"), nil, lockGetProp) + p.mvalprop = &Properties{} + vtype := p.mtype.Elem() + if vtype.Kind() != reflect.Ptr && vtype.Kind() != reflect.Slice { + // The value type is not a message (*T) or bytes ([]byte), + // so we need encoders for the pointer to this type. + vtype = reflect.PtrTo(vtype) + } + p.mvalprop.init(vtype, "Value", f.Tag.Get("protobuf_val"), nil, lockGetProp) + } + + // precalculate tag code + wire := p.WireType + if p.Packed { + wire = WireBytes + } + x := uint32(p.Tag)<<3 | uint32(wire) + i := 0 + for i = 0; x > 127; i++ { + p.tagbuf[i] = 0x80 | uint8(x&0x7F) + x >>= 7 + } + p.tagbuf[i] = uint8(x) + p.tagcode = p.tagbuf[0 : i+1] + + if p.stype != nil { + if lockGetProp { + p.sprop = GetProperties(p.stype) + } else { + p.sprop = getPropertiesLocked(p.stype) + } + } +} + +var ( + marshalerType = reflect.TypeOf((*Marshaler)(nil)).Elem() + unmarshalerType = reflect.TypeOf((*Unmarshaler)(nil)).Elem() +) + +// isMarshaler reports whether type t implements Marshaler. +func isMarshaler(t reflect.Type) bool { + // We're checking for (likely) pointer-receiver methods + // so if t is not a pointer, something is very wrong. + // The calls above only invoke isMarshaler on pointer types. + if t.Kind() != reflect.Ptr { + panic("proto: misuse of isMarshaler") + } + return t.Implements(marshalerType) +} + +// isUnmarshaler reports whether type t implements Unmarshaler. +func isUnmarshaler(t reflect.Type) bool { + // We're checking for (likely) pointer-receiver methods + // so if t is not a pointer, something is very wrong. + // The calls above only invoke isUnmarshaler on pointer types. + if t.Kind() != reflect.Ptr { + panic("proto: misuse of isUnmarshaler") + } + return t.Implements(unmarshalerType) +} + +// Init populates the properties from a protocol buffer struct tag. +func (p *Properties) Init(typ reflect.Type, name, tag string, f *reflect.StructField) { + p.init(typ, name, tag, f, true) +} + +func (p *Properties) init(typ reflect.Type, name, tag string, f *reflect.StructField, lockGetProp bool) { + // "bytes,49,opt,def=hello!" + p.Name = name + p.OrigName = name + if f != nil { + p.field = toField(f) + } + if tag == "" { + return + } + p.Parse(tag) + p.setEncAndDec(typ, f, lockGetProp) +} + +var ( + propertiesMu sync.RWMutex + propertiesMap = make(map[reflect.Type]*StructProperties) +) + +// GetProperties returns the list of properties for the type represented by t. +// t must represent a generated struct type of a protocol message. +func GetProperties(t reflect.Type) *StructProperties { + if t.Kind() != reflect.Struct { + panic("proto: type must have kind struct") + } + + // Most calls to GetProperties in a long-running program will be + // retrieving details for types we have seen before. + propertiesMu.RLock() + sprop, ok := propertiesMap[t] + propertiesMu.RUnlock() + if ok { + if collectStats { + stats.Chit++ + } + return sprop + } + + propertiesMu.Lock() + sprop = getPropertiesLocked(t) + propertiesMu.Unlock() + return sprop +} + +// getPropertiesLocked requires that propertiesMu is held. +func getPropertiesLocked(t reflect.Type) *StructProperties { + if prop, ok := propertiesMap[t]; ok { + if collectStats { + stats.Chit++ + } + return prop + } + if collectStats { + stats.Cmiss++ + } + + prop := new(StructProperties) + // in case of recursive protos, fill this in now. + propertiesMap[t] = prop + + // build properties + prop.extendable = reflect.PtrTo(t).Implements(extendableProtoType) + prop.unrecField = invalidField + prop.Prop = make([]*Properties, t.NumField()) + prop.order = make([]int, t.NumField()) + + for i := 0; i < t.NumField(); i++ { + f := t.Field(i) + p := new(Properties) + name := f.Name + p.init(f.Type, name, f.Tag.Get("protobuf"), &f, false) + + if f.Name == "XXX_extensions" { // special case + p.enc = (*Buffer).enc_map + p.dec = nil // not needed + p.size = size_map + } + if f.Name == "XXX_unrecognized" { // special case + prop.unrecField = toField(&f) + } + oneof := f.Tag.Get("protobuf_oneof") != "" // special case + prop.Prop[i] = p + prop.order[i] = i + if debug { + print(i, " ", f.Name, " ", t.String(), " ") + if p.Tag > 0 { + print(p.String()) + } + print("\n") + } + if p.enc == nil && !strings.HasPrefix(f.Name, "XXX_") && !oneof { + fmt.Fprintln(os.Stderr, "proto: no encoder for", f.Name, f.Type.String(), "[GetProperties]") + } + } + + // Re-order prop.order. + sort.Sort(prop) + + type oneofMessage interface { + XXX_OneofFuncs() (func(Message, *Buffer) error, func(Message, int, int, *Buffer) (bool, error), func(Message) int, []interface{}) + } + if om, ok := reflect.Zero(reflect.PtrTo(t)).Interface().(oneofMessage); ok { + var oots []interface{} + prop.oneofMarshaler, prop.oneofUnmarshaler, prop.oneofSizer, oots = om.XXX_OneofFuncs() + prop.stype = t + + // Interpret oneof metadata. + prop.OneofTypes = make(map[string]*OneofProperties) + for _, oot := range oots { + oop := &OneofProperties{ + Type: reflect.ValueOf(oot).Type(), // *T + Prop: new(Properties), + } + sft := oop.Type.Elem().Field(0) + oop.Prop.Name = sft.Name + oop.Prop.Parse(sft.Tag.Get("protobuf")) + // There will be exactly one interface field that + // this new value is assignable to. + for i := 0; i < t.NumField(); i++ { + f := t.Field(i) + if f.Type.Kind() != reflect.Interface { + continue + } + if !oop.Type.AssignableTo(f.Type) { + continue + } + oop.Field = i + break + } + prop.OneofTypes[oop.Prop.OrigName] = oop + } + } + + // build required counts + // build tags + reqCount := 0 + prop.decoderOrigNames = make(map[string]int) + for i, p := range prop.Prop { + if strings.HasPrefix(p.Name, "XXX_") { + // Internal fields should not appear in tags/origNames maps. + // They are handled specially when encoding and decoding. + continue + } + if p.Required { + reqCount++ + } + prop.decoderTags.put(p.Tag, i) + prop.decoderOrigNames[p.OrigName] = i + } + prop.reqCount = reqCount + + return prop +} + +// Return the Properties object for the x[0]'th field of the structure. +func propByIndex(t reflect.Type, x []int) *Properties { + if len(x) != 1 { + fmt.Fprintf(os.Stderr, "proto: field index dimension %d (not 1) for type %s\n", len(x), t) + return nil + } + prop := GetProperties(t) + return prop.Prop[x[0]] +} + +// Get the address and type of a pointer to a struct from an interface. +func getbase(pb Message) (t reflect.Type, b structPointer, err error) { + if pb == nil { + err = ErrNil + return + } + // get the reflect type of the pointer to the struct. + t = reflect.TypeOf(pb) + // get the address of the struct. + value := reflect.ValueOf(pb) + b = toStructPointer(value) + return +} + +// A global registry of enum types. +// The generated code will register the generated maps by calling RegisterEnum. + +var enumValueMaps = make(map[string]map[string]int32) + +// RegisterEnum is called from the generated code to install the enum descriptor +// maps into the global table to aid parsing text format protocol buffers. +func RegisterEnum(typeName string, unusedNameMap map[int32]string, valueMap map[string]int32) { + if _, ok := enumValueMaps[typeName]; ok { + panic("proto: duplicate enum registered: " + typeName) + } + enumValueMaps[typeName] = valueMap +} + +// EnumValueMap returns the mapping from names to integers of the +// enum type enumType, or a nil if not found. +func EnumValueMap(enumType string) map[string]int32 { + return enumValueMaps[enumType] +} + +// A registry of all linked message types. +// The string is a fully-qualified proto name ("pkg.Message"). +var ( + protoTypes = make(map[string]reflect.Type) + revProtoTypes = make(map[reflect.Type]string) +) + +// RegisterType is called from generated code and maps from the fully qualified +// proto name to the type (pointer to struct) of the protocol buffer. +func RegisterType(x Message, name string) { + if _, ok := protoTypes[name]; ok { + // TODO: Some day, make this a panic. + log.Printf("proto: duplicate proto type registered: %s", name) + return + } + t := reflect.TypeOf(x) + protoTypes[name] = t + revProtoTypes[t] = name +} + +// MessageName returns the fully-qualified proto name for the given message type. +func MessageName(x Message) string { return revProtoTypes[reflect.TypeOf(x)] } + +// MessageType returns the message type (pointer to struct) for a named message. +func MessageType(name string) reflect.Type { return protoTypes[name] } diff --git a/vendor/github.com/golang/protobuf/proto/text.go b/vendor/github.com/golang/protobuf/proto/text.go new file mode 100644 index 000000000..1cbaf86d3 --- /dev/null +++ b/vendor/github.com/golang/protobuf/proto/text.go @@ -0,0 +1,762 @@ +// Go support for Protocol Buffers - Google's data interchange format +// +// Copyright 2010 The Go Authors. All rights reserved. +// https://github.com/golang/protobuf +// +// Redistribution and use in source and binary forms, with or without +// modification, are permitted provided that the following conditions are +// met: +// +// * Redistributions of source code must retain the above copyright +// notice, this list of conditions and the following disclaimer. +// * Redistributions in binary form must reproduce the above +// copyright notice, this list of conditions and the following disclaimer +// in the documentation and/or other materials provided with the +// distribution. +// * Neither the name of Google Inc. nor the names of its +// contributors may be used to endorse or promote products derived from +// this software without specific prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +package proto + +// Functions for writing the text protocol buffer format. + +import ( + "bufio" + "bytes" + "encoding" + "errors" + "fmt" + "io" + "log" + "math" + "reflect" + "sort" + "strings" +) + +var ( + newline = []byte("\n") + spaces = []byte(" ") + gtNewline = []byte(">\n") + endBraceNewline = []byte("}\n") + backslashN = []byte{'\\', 'n'} + backslashR = []byte{'\\', 'r'} + backslashT = []byte{'\\', 't'} + backslashDQ = []byte{'\\', '"'} + backslashBS = []byte{'\\', '\\'} + posInf = []byte("inf") + negInf = []byte("-inf") + nan = []byte("nan") +) + +type writer interface { + io.Writer + WriteByte(byte) error +} + +// textWriter is an io.Writer that tracks its indentation level. +type textWriter struct { + ind int + complete bool // if the current position is a complete line + compact bool // whether to write out as a one-liner + w writer +} + +func (w *textWriter) WriteString(s string) (n int, err error) { + if !strings.Contains(s, "\n") { + if !w.compact && w.complete { + w.writeIndent() + } + w.complete = false + return io.WriteString(w.w, s) + } + // WriteString is typically called without newlines, so this + // codepath and its copy are rare. We copy to avoid + // duplicating all of Write's logic here. + return w.Write([]byte(s)) +} + +func (w *textWriter) Write(p []byte) (n int, err error) { + newlines := bytes.Count(p, newline) + if newlines == 0 { + if !w.compact && w.complete { + w.writeIndent() + } + n, err = w.w.Write(p) + w.complete = false + return n, err + } + + frags := bytes.SplitN(p, newline, newlines+1) + if w.compact { + for i, frag := range frags { + if i > 0 { + if err := w.w.WriteByte(' '); err != nil { + return n, err + } + n++ + } + nn, err := w.w.Write(frag) + n += nn + if err != nil { + return n, err + } + } + return n, nil + } + + for i, frag := range frags { + if w.complete { + w.writeIndent() + } + nn, err := w.w.Write(frag) + n += nn + if err != nil { + return n, err + } + if i+1 < len(frags) { + if err := w.w.WriteByte('\n'); err != nil { + return n, err + } + n++ + } + } + w.complete = len(frags[len(frags)-1]) == 0 + return n, nil +} + +func (w *textWriter) WriteByte(c byte) error { + if w.compact && c == '\n' { + c = ' ' + } + if !w.compact && w.complete { + w.writeIndent() + } + err := w.w.WriteByte(c) + w.complete = c == '\n' + return err +} + +func (w *textWriter) indent() { w.ind++ } + +func (w *textWriter) unindent() { + if w.ind == 0 { + log.Printf("proto: textWriter unindented too far") + return + } + w.ind-- +} + +func writeName(w *textWriter, props *Properties) error { + if _, err := w.WriteString(props.OrigName); err != nil { + return err + } + if props.Wire != "group" { + return w.WriteByte(':') + } + return nil +} + +// raw is the interface satisfied by RawMessage. +type raw interface { + Bytes() []byte +} + +func writeStruct(w *textWriter, sv reflect.Value) error { + st := sv.Type() + sprops := GetProperties(st) + for i := 0; i < sv.NumField(); i++ { + fv := sv.Field(i) + props := sprops.Prop[i] + name := st.Field(i).Name + + if strings.HasPrefix(name, "XXX_") { + // There are two XXX_ fields: + // XXX_unrecognized []byte + // XXX_extensions map[int32]proto.Extension + // The first is handled here; + // the second is handled at the bottom of this function. + if name == "XXX_unrecognized" && !fv.IsNil() { + if err := writeUnknownStruct(w, fv.Interface().([]byte)); err != nil { + return err + } + } + continue + } + if fv.Kind() == reflect.Ptr && fv.IsNil() { + // Field not filled in. This could be an optional field or + // a required field that wasn't filled in. Either way, there + // isn't anything we can show for it. + continue + } + if fv.Kind() == reflect.Slice && fv.IsNil() { + // Repeated field that is empty, or a bytes field that is unused. + continue + } + + if props.Repeated && fv.Kind() == reflect.Slice { + // Repeated field. + for j := 0; j < fv.Len(); j++ { + if err := writeName(w, props); err != nil { + return err + } + if !w.compact { + if err := w.WriteByte(' '); err != nil { + return err + } + } + v := fv.Index(j) + if v.Kind() == reflect.Ptr && v.IsNil() { + // A nil message in a repeated field is not valid, + // but we can handle that more gracefully than panicking. + if _, err := w.Write([]byte("\n")); err != nil { + return err + } + continue + } + if err := writeAny(w, v, props); err != nil { + return err + } + if err := w.WriteByte('\n'); err != nil { + return err + } + } + continue + } + if fv.Kind() == reflect.Map { + // Map fields are rendered as a repeated struct with key/value fields. + keys := fv.MapKeys() + sort.Sort(mapKeys(keys)) + for _, key := range keys { + val := fv.MapIndex(key) + if err := writeName(w, props); err != nil { + return err + } + if !w.compact { + if err := w.WriteByte(' '); err != nil { + return err + } + } + // open struct + if err := w.WriteByte('<'); err != nil { + return err + } + if !w.compact { + if err := w.WriteByte('\n'); err != nil { + return err + } + } + w.indent() + // key + if _, err := w.WriteString("key:"); err != nil { + return err + } + if !w.compact { + if err := w.WriteByte(' '); err != nil { + return err + } + } + if err := writeAny(w, key, props.mkeyprop); err != nil { + return err + } + if err := w.WriteByte('\n'); err != nil { + return err + } + // nil values aren't legal, but we can avoid panicking because of them. + if val.Kind() != reflect.Ptr || !val.IsNil() { + // value + if _, err := w.WriteString("value:"); err != nil { + return err + } + if !w.compact { + if err := w.WriteByte(' '); err != nil { + return err + } + } + if err := writeAny(w, val, props.mvalprop); err != nil { + return err + } + if err := w.WriteByte('\n'); err != nil { + return err + } + } + // close struct + w.unindent() + if err := w.WriteByte('>'); err != nil { + return err + } + if err := w.WriteByte('\n'); err != nil { + return err + } + } + continue + } + if props.proto3 && fv.Kind() == reflect.Slice && fv.Len() == 0 { + // empty bytes field + continue + } + if fv.Kind() != reflect.Ptr && fv.Kind() != reflect.Slice { + // proto3 non-repeated scalar field; skip if zero value + if isProto3Zero(fv) { + continue + } + } + + if fv.Kind() == reflect.Interface { + // Check if it is a oneof. + if st.Field(i).Tag.Get("protobuf_oneof") != "" { + // fv is nil, or holds a pointer to generated struct. + // That generated struct has exactly one field, + // which has a protobuf struct tag. + if fv.IsNil() { + continue + } + inner := fv.Elem().Elem() // interface -> *T -> T + tag := inner.Type().Field(0).Tag.Get("protobuf") + props = new(Properties) // Overwrite the outer props var, but not its pointee. + props.Parse(tag) + // Write the value in the oneof, not the oneof itself. + fv = inner.Field(0) + + // Special case to cope with malformed messages gracefully: + // If the value in the oneof is a nil pointer, don't panic + // in writeAny. + if fv.Kind() == reflect.Ptr && fv.IsNil() { + // Use errors.New so writeAny won't render quotes. + msg := errors.New("/* nil */") + fv = reflect.ValueOf(&msg).Elem() + } + } + } + + if err := writeName(w, props); err != nil { + return err + } + if !w.compact { + if err := w.WriteByte(' '); err != nil { + return err + } + } + if b, ok := fv.Interface().(raw); ok { + if err := writeRaw(w, b.Bytes()); err != nil { + return err + } + continue + } + + // Enums have a String method, so writeAny will work fine. + if err := writeAny(w, fv, props); err != nil { + return err + } + + if err := w.WriteByte('\n'); err != nil { + return err + } + } + + // Extensions (the XXX_extensions field). + pv := sv.Addr() + if pv.Type().Implements(extendableProtoType) { + if err := writeExtensions(w, pv); err != nil { + return err + } + } + + return nil +} + +// writeRaw writes an uninterpreted raw message. +func writeRaw(w *textWriter, b []byte) error { + if err := w.WriteByte('<'); err != nil { + return err + } + if !w.compact { + if err := w.WriteByte('\n'); err != nil { + return err + } + } + w.indent() + if err := writeUnknownStruct(w, b); err != nil { + return err + } + w.unindent() + if err := w.WriteByte('>'); err != nil { + return err + } + return nil +} + +// writeAny writes an arbitrary field. +func writeAny(w *textWriter, v reflect.Value, props *Properties) error { + v = reflect.Indirect(v) + + // Floats have special cases. + if v.Kind() == reflect.Float32 || v.Kind() == reflect.Float64 { + x := v.Float() + var b []byte + switch { + case math.IsInf(x, 1): + b = posInf + case math.IsInf(x, -1): + b = negInf + case math.IsNaN(x): + b = nan + } + if b != nil { + _, err := w.Write(b) + return err + } + // Other values are handled below. + } + + // We don't attempt to serialise every possible value type; only those + // that can occur in protocol buffers. + switch v.Kind() { + case reflect.Slice: + // Should only be a []byte; repeated fields are handled in writeStruct. + if err := writeString(w, string(v.Interface().([]byte))); err != nil { + return err + } + case reflect.String: + if err := writeString(w, v.String()); err != nil { + return err + } + case reflect.Struct: + // Required/optional group/message. + var bra, ket byte = '<', '>' + if props != nil && props.Wire == "group" { + bra, ket = '{', '}' + } + if err := w.WriteByte(bra); err != nil { + return err + } + if !w.compact { + if err := w.WriteByte('\n'); err != nil { + return err + } + } + w.indent() + if tm, ok := v.Interface().(encoding.TextMarshaler); ok { + text, err := tm.MarshalText() + if err != nil { + return err + } + if _, err = w.Write(text); err != nil { + return err + } + } else if err := writeStruct(w, v); err != nil { + return err + } + w.unindent() + if err := w.WriteByte(ket); err != nil { + return err + } + default: + _, err := fmt.Fprint(w, v.Interface()) + return err + } + return nil +} + +// equivalent to C's isprint. +func isprint(c byte) bool { + return c >= 0x20 && c < 0x7f +} + +// writeString writes a string in the protocol buffer text format. +// It is similar to strconv.Quote except we don't use Go escape sequences, +// we treat the string as a byte sequence, and we use octal escapes. +// These differences are to maintain interoperability with the other +// languages' implementations of the text format. +func writeString(w *textWriter, s string) error { + // use WriteByte here to get any needed indent + if err := w.WriteByte('"'); err != nil { + return err + } + // Loop over the bytes, not the runes. + for i := 0; i < len(s); i++ { + var err error + // Divergence from C++: we don't escape apostrophes. + // There's no need to escape them, and the C++ parser + // copes with a naked apostrophe. + switch c := s[i]; c { + case '\n': + _, err = w.w.Write(backslashN) + case '\r': + _, err = w.w.Write(backslashR) + case '\t': + _, err = w.w.Write(backslashT) + case '"': + _, err = w.w.Write(backslashDQ) + case '\\': + _, err = w.w.Write(backslashBS) + default: + if isprint(c) { + err = w.w.WriteByte(c) + } else { + _, err = fmt.Fprintf(w.w, "\\%03o", c) + } + } + if err != nil { + return err + } + } + return w.WriteByte('"') +} + +func writeUnknownStruct(w *textWriter, data []byte) (err error) { + if !w.compact { + if _, err := fmt.Fprintf(w, "/* %d unknown bytes */\n", len(data)); err != nil { + return err + } + } + b := NewBuffer(data) + for b.index < len(b.buf) { + x, err := b.DecodeVarint() + if err != nil { + _, err := fmt.Fprintf(w, "/* %v */\n", err) + return err + } + wire, tag := x&7, x>>3 + if wire == WireEndGroup { + w.unindent() + if _, err := w.Write(endBraceNewline); err != nil { + return err + } + continue + } + if _, err := fmt.Fprint(w, tag); err != nil { + return err + } + if wire != WireStartGroup { + if err := w.WriteByte(':'); err != nil { + return err + } + } + if !w.compact || wire == WireStartGroup { + if err := w.WriteByte(' '); err != nil { + return err + } + } + switch wire { + case WireBytes: + buf, e := b.DecodeRawBytes(false) + if e == nil { + _, err = fmt.Fprintf(w, "%q", buf) + } else { + _, err = fmt.Fprintf(w, "/* %v */", e) + } + case WireFixed32: + x, err = b.DecodeFixed32() + err = writeUnknownInt(w, x, err) + case WireFixed64: + x, err = b.DecodeFixed64() + err = writeUnknownInt(w, x, err) + case WireStartGroup: + err = w.WriteByte('{') + w.indent() + case WireVarint: + x, err = b.DecodeVarint() + err = writeUnknownInt(w, x, err) + default: + _, err = fmt.Fprintf(w, "/* unknown wire type %d */", wire) + } + if err != nil { + return err + } + if err = w.WriteByte('\n'); err != nil { + return err + } + } + return nil +} + +func writeUnknownInt(w *textWriter, x uint64, err error) error { + if err == nil { + _, err = fmt.Fprint(w, x) + } else { + _, err = fmt.Fprintf(w, "/* %v */", err) + } + return err +} + +type int32Slice []int32 + +func (s int32Slice) Len() int { return len(s) } +func (s int32Slice) Less(i, j int) bool { return s[i] < s[j] } +func (s int32Slice) Swap(i, j int) { s[i], s[j] = s[j], s[i] } + +// writeExtensions writes all the extensions in pv. +// pv is assumed to be a pointer to a protocol message struct that is extendable. +func writeExtensions(w *textWriter, pv reflect.Value) error { + emap := extensionMaps[pv.Type().Elem()] + ep := pv.Interface().(extendableProto) + + // Order the extensions by ID. + // This isn't strictly necessary, but it will give us + // canonical output, which will also make testing easier. + m := ep.ExtensionMap() + ids := make([]int32, 0, len(m)) + for id := range m { + ids = append(ids, id) + } + sort.Sort(int32Slice(ids)) + + for _, extNum := range ids { + ext := m[extNum] + var desc *ExtensionDesc + if emap != nil { + desc = emap[extNum] + } + if desc == nil { + // Unknown extension. + if err := writeUnknownStruct(w, ext.enc); err != nil { + return err + } + continue + } + + pb, err := GetExtension(ep, desc) + if err != nil { + return fmt.Errorf("failed getting extension: %v", err) + } + + // Repeated extensions will appear as a slice. + if !desc.repeated() { + if err := writeExtension(w, desc.Name, pb); err != nil { + return err + } + } else { + v := reflect.ValueOf(pb) + for i := 0; i < v.Len(); i++ { + if err := writeExtension(w, desc.Name, v.Index(i).Interface()); err != nil { + return err + } + } + } + } + return nil +} + +func writeExtension(w *textWriter, name string, pb interface{}) error { + if _, err := fmt.Fprintf(w, "[%s]:", name); err != nil { + return err + } + if !w.compact { + if err := w.WriteByte(' '); err != nil { + return err + } + } + if err := writeAny(w, reflect.ValueOf(pb), nil); err != nil { + return err + } + if err := w.WriteByte('\n'); err != nil { + return err + } + return nil +} + +func (w *textWriter) writeIndent() { + if !w.complete { + return + } + remain := w.ind * 2 + for remain > 0 { + n := remain + if n > len(spaces) { + n = len(spaces) + } + w.w.Write(spaces[:n]) + remain -= n + } + w.complete = false +} + +// TextMarshaler is a configurable text format marshaler. +type TextMarshaler struct { + Compact bool // use compact text format (one line). +} + +// Marshal writes a given protocol buffer in text format. +// The only errors returned are from w. +func (m *TextMarshaler) Marshal(w io.Writer, pb Message) error { + val := reflect.ValueOf(pb) + if pb == nil || val.IsNil() { + w.Write([]byte("")) + return nil + } + var bw *bufio.Writer + ww, ok := w.(writer) + if !ok { + bw = bufio.NewWriter(w) + ww = bw + } + aw := &textWriter{ + w: ww, + complete: true, + compact: m.Compact, + } + + if tm, ok := pb.(encoding.TextMarshaler); ok { + text, err := tm.MarshalText() + if err != nil { + return err + } + if _, err = aw.Write(text); err != nil { + return err + } + if bw != nil { + return bw.Flush() + } + return nil + } + // Dereference the received pointer so we don't have outer < and >. + v := reflect.Indirect(val) + if err := writeStruct(aw, v); err != nil { + return err + } + if bw != nil { + return bw.Flush() + } + return nil +} + +// Text is the same as Marshal, but returns the string directly. +func (m *TextMarshaler) Text(pb Message) string { + var buf bytes.Buffer + m.Marshal(&buf, pb) + return buf.String() +} + +var ( + defaultTextMarshaler = TextMarshaler{} + compactTextMarshaler = TextMarshaler{Compact: true} +) + +// TODO: consider removing some of the Marshal functions below. + +// MarshalText writes a given protocol buffer in text format. +// The only errors returned are from w. +func MarshalText(w io.Writer, pb Message) error { return defaultTextMarshaler.Marshal(w, pb) } + +// MarshalTextString is the same as MarshalText, but returns the string directly. +func MarshalTextString(pb Message) string { return defaultTextMarshaler.Text(pb) } + +// CompactText writes a given protocol buffer in compact text format (one line). +func CompactText(w io.Writer, pb Message) error { return compactTextMarshaler.Marshal(w, pb) } + +// CompactTextString is the same as CompactText, but returns the string directly. +func CompactTextString(pb Message) string { return compactTextMarshaler.Text(pb) } diff --git a/vendor/github.com/golang/protobuf/proto/text_parser.go b/vendor/github.com/golang/protobuf/proto/text_parser.go new file mode 100644 index 000000000..451323262 --- /dev/null +++ b/vendor/github.com/golang/protobuf/proto/text_parser.go @@ -0,0 +1,806 @@ +// Go support for Protocol Buffers - Google's data interchange format +// +// Copyright 2010 The Go Authors. All rights reserved. +// https://github.com/golang/protobuf +// +// Redistribution and use in source and binary forms, with or without +// modification, are permitted provided that the following conditions are +// met: +// +// * Redistributions of source code must retain the above copyright +// notice, this list of conditions and the following disclaimer. +// * Redistributions in binary form must reproduce the above +// copyright notice, this list of conditions and the following disclaimer +// in the documentation and/or other materials provided with the +// distribution. +// * Neither the name of Google Inc. nor the names of its +// contributors may be used to endorse or promote products derived from +// this software without specific prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +package proto + +// Functions for parsing the Text protocol buffer format. +// TODO: message sets. + +import ( + "encoding" + "errors" + "fmt" + "reflect" + "strconv" + "strings" + "unicode/utf8" +) + +type ParseError struct { + Message string + Line int // 1-based line number + Offset int // 0-based byte offset from start of input +} + +func (p *ParseError) Error() string { + if p.Line == 1 { + // show offset only for first line + return fmt.Sprintf("line 1.%d: %v", p.Offset, p.Message) + } + return fmt.Sprintf("line %d: %v", p.Line, p.Message) +} + +type token struct { + value string + err *ParseError + line int // line number + offset int // byte number from start of input, not start of line + unquoted string // the unquoted version of value, if it was a quoted string +} + +func (t *token) String() string { + if t.err == nil { + return fmt.Sprintf("%q (line=%d, offset=%d)", t.value, t.line, t.offset) + } + return fmt.Sprintf("parse error: %v", t.err) +} + +type textParser struct { + s string // remaining input + done bool // whether the parsing is finished (success or error) + backed bool // whether back() was called + offset, line int + cur token +} + +func newTextParser(s string) *textParser { + p := new(textParser) + p.s = s + p.line = 1 + p.cur.line = 1 + return p +} + +func (p *textParser) errorf(format string, a ...interface{}) *ParseError { + pe := &ParseError{fmt.Sprintf(format, a...), p.cur.line, p.cur.offset} + p.cur.err = pe + p.done = true + return pe +} + +// Numbers and identifiers are matched by [-+._A-Za-z0-9] +func isIdentOrNumberChar(c byte) bool { + switch { + case 'A' <= c && c <= 'Z', 'a' <= c && c <= 'z': + return true + case '0' <= c && c <= '9': + return true + } + switch c { + case '-', '+', '.', '_': + return true + } + return false +} + +func isWhitespace(c byte) bool { + switch c { + case ' ', '\t', '\n', '\r': + return true + } + return false +} + +func isQuote(c byte) bool { + switch c { + case '"', '\'': + return true + } + return false +} + +func (p *textParser) skipWhitespace() { + i := 0 + for i < len(p.s) && (isWhitespace(p.s[i]) || p.s[i] == '#') { + if p.s[i] == '#' { + // comment; skip to end of line or input + for i < len(p.s) && p.s[i] != '\n' { + i++ + } + if i == len(p.s) { + break + } + } + if p.s[i] == '\n' { + p.line++ + } + i++ + } + p.offset += i + p.s = p.s[i:len(p.s)] + if len(p.s) == 0 { + p.done = true + } +} + +func (p *textParser) advance() { + // Skip whitespace + p.skipWhitespace() + if p.done { + return + } + + // Start of non-whitespace + p.cur.err = nil + p.cur.offset, p.cur.line = p.offset, p.line + p.cur.unquoted = "" + switch p.s[0] { + case '<', '>', '{', '}', ':', '[', ']', ';', ',': + // Single symbol + p.cur.value, p.s = p.s[0:1], p.s[1:len(p.s)] + case '"', '\'': + // Quoted string + i := 1 + for i < len(p.s) && p.s[i] != p.s[0] && p.s[i] != '\n' { + if p.s[i] == '\\' && i+1 < len(p.s) { + // skip escaped char + i++ + } + i++ + } + if i >= len(p.s) || p.s[i] != p.s[0] { + p.errorf("unmatched quote") + return + } + unq, err := unquoteC(p.s[1:i], rune(p.s[0])) + if err != nil { + p.errorf("invalid quoted string %s: %v", p.s[0:i+1], err) + return + } + p.cur.value, p.s = p.s[0:i+1], p.s[i+1:len(p.s)] + p.cur.unquoted = unq + default: + i := 0 + for i < len(p.s) && isIdentOrNumberChar(p.s[i]) { + i++ + } + if i == 0 { + p.errorf("unexpected byte %#x", p.s[0]) + return + } + p.cur.value, p.s = p.s[0:i], p.s[i:len(p.s)] + } + p.offset += len(p.cur.value) +} + +var ( + errBadUTF8 = errors.New("proto: bad UTF-8") + errBadHex = errors.New("proto: bad hexadecimal") +) + +func unquoteC(s string, quote rune) (string, error) { + // This is based on C++'s tokenizer.cc. + // Despite its name, this is *not* parsing C syntax. + // For instance, "\0" is an invalid quoted string. + + // Avoid allocation in trivial cases. + simple := true + for _, r := range s { + if r == '\\' || r == quote { + simple = false + break + } + } + if simple { + return s, nil + } + + buf := make([]byte, 0, 3*len(s)/2) + for len(s) > 0 { + r, n := utf8.DecodeRuneInString(s) + if r == utf8.RuneError && n == 1 { + return "", errBadUTF8 + } + s = s[n:] + if r != '\\' { + if r < utf8.RuneSelf { + buf = append(buf, byte(r)) + } else { + buf = append(buf, string(r)...) + } + continue + } + + ch, tail, err := unescape(s) + if err != nil { + return "", err + } + buf = append(buf, ch...) + s = tail + } + return string(buf), nil +} + +func unescape(s string) (ch string, tail string, err error) { + r, n := utf8.DecodeRuneInString(s) + if r == utf8.RuneError && n == 1 { + return "", "", errBadUTF8 + } + s = s[n:] + switch r { + case 'a': + return "\a", s, nil + case 'b': + return "\b", s, nil + case 'f': + return "\f", s, nil + case 'n': + return "\n", s, nil + case 'r': + return "\r", s, nil + case 't': + return "\t", s, nil + case 'v': + return "\v", s, nil + case '?': + return "?", s, nil // trigraph workaround + case '\'', '"', '\\': + return string(r), s, nil + case '0', '1', '2', '3', '4', '5', '6', '7', 'x', 'X': + if len(s) < 2 { + return "", "", fmt.Errorf(`\%c requires 2 following digits`, r) + } + base := 8 + ss := s[:2] + s = s[2:] + if r == 'x' || r == 'X' { + base = 16 + } else { + ss = string(r) + ss + } + i, err := strconv.ParseUint(ss, base, 8) + if err != nil { + return "", "", err + } + return string([]byte{byte(i)}), s, nil + case 'u', 'U': + n := 4 + if r == 'U' { + n = 8 + } + if len(s) < n { + return "", "", fmt.Errorf(`\%c requires %d digits`, r, n) + } + + bs := make([]byte, n/2) + for i := 0; i < n; i += 2 { + a, ok1 := unhex(s[i]) + b, ok2 := unhex(s[i+1]) + if !ok1 || !ok2 { + return "", "", errBadHex + } + bs[i/2] = a<<4 | b + } + s = s[n:] + return string(bs), s, nil + } + return "", "", fmt.Errorf(`unknown escape \%c`, r) +} + +// Adapted from src/pkg/strconv/quote.go. +func unhex(b byte) (v byte, ok bool) { + switch { + case '0' <= b && b <= '9': + return b - '0', true + case 'a' <= b && b <= 'f': + return b - 'a' + 10, true + case 'A' <= b && b <= 'F': + return b - 'A' + 10, true + } + return 0, false +} + +// Back off the parser by one token. Can only be done between calls to next(). +// It makes the next advance() a no-op. +func (p *textParser) back() { p.backed = true } + +// Advances the parser and returns the new current token. +func (p *textParser) next() *token { + if p.backed || p.done { + p.backed = false + return &p.cur + } + p.advance() + if p.done { + p.cur.value = "" + } else if len(p.cur.value) > 0 && isQuote(p.cur.value[0]) { + // Look for multiple quoted strings separated by whitespace, + // and concatenate them. + cat := p.cur + for { + p.skipWhitespace() + if p.done || !isQuote(p.s[0]) { + break + } + p.advance() + if p.cur.err != nil { + return &p.cur + } + cat.value += " " + p.cur.value + cat.unquoted += p.cur.unquoted + } + p.done = false // parser may have seen EOF, but we want to return cat + p.cur = cat + } + return &p.cur +} + +func (p *textParser) consumeToken(s string) error { + tok := p.next() + if tok.err != nil { + return tok.err + } + if tok.value != s { + p.back() + return p.errorf("expected %q, found %q", s, tok.value) + } + return nil +} + +// Return a RequiredNotSetError indicating which required field was not set. +func (p *textParser) missingRequiredFieldError(sv reflect.Value) *RequiredNotSetError { + st := sv.Type() + sprops := GetProperties(st) + for i := 0; i < st.NumField(); i++ { + if !isNil(sv.Field(i)) { + continue + } + + props := sprops.Prop[i] + if props.Required { + return &RequiredNotSetError{fmt.Sprintf("%v.%v", st, props.OrigName)} + } + } + return &RequiredNotSetError{fmt.Sprintf("%v.", st)} // should not happen +} + +// Returns the index in the struct for the named field, as well as the parsed tag properties. +func structFieldByName(sprops *StructProperties, name string) (int, *Properties, bool) { + i, ok := sprops.decoderOrigNames[name] + if ok { + return i, sprops.Prop[i], true + } + return -1, nil, false +} + +// Consume a ':' from the input stream (if the next token is a colon), +// returning an error if a colon is needed but not present. +func (p *textParser) checkForColon(props *Properties, typ reflect.Type) *ParseError { + tok := p.next() + if tok.err != nil { + return tok.err + } + if tok.value != ":" { + // Colon is optional when the field is a group or message. + needColon := true + switch props.Wire { + case "group": + needColon = false + case "bytes": + // A "bytes" field is either a message, a string, or a repeated field; + // those three become *T, *string and []T respectively, so we can check for + // this field being a pointer to a non-string. + if typ.Kind() == reflect.Ptr { + // *T or *string + if typ.Elem().Kind() == reflect.String { + break + } + } else if typ.Kind() == reflect.Slice { + // []T or []*T + if typ.Elem().Kind() != reflect.Ptr { + break + } + } else if typ.Kind() == reflect.String { + // The proto3 exception is for a string field, + // which requires a colon. + break + } + needColon = false + } + if needColon { + return p.errorf("expected ':', found %q", tok.value) + } + p.back() + } + return nil +} + +func (p *textParser) readStruct(sv reflect.Value, terminator string) error { + st := sv.Type() + sprops := GetProperties(st) + reqCount := sprops.reqCount + var reqFieldErr error + fieldSet := make(map[string]bool) + // A struct is a sequence of "name: value", terminated by one of + // '>' or '}', or the end of the input. A name may also be + // "[extension]". + for { + tok := p.next() + if tok.err != nil { + return tok.err + } + if tok.value == terminator { + break + } + if tok.value == "[" { + // Looks like an extension. + // + // TODO: Check whether we need to handle + // namespace rooted names (e.g. ".something.Foo"). + tok = p.next() + if tok.err != nil { + return tok.err + } + var desc *ExtensionDesc + // This could be faster, but it's functional. + // TODO: Do something smarter than a linear scan. + for _, d := range RegisteredExtensions(reflect.New(st).Interface().(Message)) { + if d.Name == tok.value { + desc = d + break + } + } + if desc == nil { + return p.errorf("unrecognized extension %q", tok.value) + } + // Check the extension terminator. + tok = p.next() + if tok.err != nil { + return tok.err + } + if tok.value != "]" { + return p.errorf("unrecognized extension terminator %q", tok.value) + } + + props := &Properties{} + props.Parse(desc.Tag) + + typ := reflect.TypeOf(desc.ExtensionType) + if err := p.checkForColon(props, typ); err != nil { + return err + } + + rep := desc.repeated() + + // Read the extension structure, and set it in + // the value we're constructing. + var ext reflect.Value + if !rep { + ext = reflect.New(typ).Elem() + } else { + ext = reflect.New(typ.Elem()).Elem() + } + if err := p.readAny(ext, props); err != nil { + if _, ok := err.(*RequiredNotSetError); !ok { + return err + } + reqFieldErr = err + } + ep := sv.Addr().Interface().(extendableProto) + if !rep { + SetExtension(ep, desc, ext.Interface()) + } else { + old, err := GetExtension(ep, desc) + var sl reflect.Value + if err == nil { + sl = reflect.ValueOf(old) // existing slice + } else { + sl = reflect.MakeSlice(typ, 0, 1) + } + sl = reflect.Append(sl, ext) + SetExtension(ep, desc, sl.Interface()) + } + if err := p.consumeOptionalSeparator(); err != nil { + return err + } + continue + } + + // This is a normal, non-extension field. + name := tok.value + var dst reflect.Value + fi, props, ok := structFieldByName(sprops, name) + if ok { + dst = sv.Field(fi) + } else if oop, ok := sprops.OneofTypes[name]; ok { + // It is a oneof. + props = oop.Prop + nv := reflect.New(oop.Type.Elem()) + dst = nv.Elem().Field(0) + sv.Field(oop.Field).Set(nv) + } + if !dst.IsValid() { + return p.errorf("unknown field name %q in %v", name, st) + } + + if dst.Kind() == reflect.Map { + // Consume any colon. + if err := p.checkForColon(props, dst.Type()); err != nil { + return err + } + + // Construct the map if it doesn't already exist. + if dst.IsNil() { + dst.Set(reflect.MakeMap(dst.Type())) + } + key := reflect.New(dst.Type().Key()).Elem() + val := reflect.New(dst.Type().Elem()).Elem() + + // The map entry should be this sequence of tokens: + // < key : KEY value : VALUE > + // Technically the "key" and "value" could come in any order, + // but in practice they won't. + + tok := p.next() + var terminator string + switch tok.value { + case "<": + terminator = ">" + case "{": + terminator = "}" + default: + return p.errorf("expected '{' or '<', found %q", tok.value) + } + if err := p.consumeToken("key"); err != nil { + return err + } + if err := p.consumeToken(":"); err != nil { + return err + } + if err := p.readAny(key, props.mkeyprop); err != nil { + return err + } + if err := p.consumeOptionalSeparator(); err != nil { + return err + } + if err := p.consumeToken("value"); err != nil { + return err + } + if err := p.checkForColon(props.mvalprop, dst.Type().Elem()); err != nil { + return err + } + if err := p.readAny(val, props.mvalprop); err != nil { + return err + } + if err := p.consumeOptionalSeparator(); err != nil { + return err + } + if err := p.consumeToken(terminator); err != nil { + return err + } + + dst.SetMapIndex(key, val) + continue + } + + // Check that it's not already set if it's not a repeated field. + if !props.Repeated && fieldSet[name] { + return p.errorf("non-repeated field %q was repeated", name) + } + + if err := p.checkForColon(props, dst.Type()); err != nil { + return err + } + + // Parse into the field. + fieldSet[name] = true + if err := p.readAny(dst, props); err != nil { + if _, ok := err.(*RequiredNotSetError); !ok { + return err + } + reqFieldErr = err + } else if props.Required { + reqCount-- + } + + if err := p.consumeOptionalSeparator(); err != nil { + return err + } + + } + + if reqCount > 0 { + return p.missingRequiredFieldError(sv) + } + return reqFieldErr +} + +// consumeOptionalSeparator consumes an optional semicolon or comma. +// It is used in readStruct to provide backward compatibility. +func (p *textParser) consumeOptionalSeparator() error { + tok := p.next() + if tok.err != nil { + return tok.err + } + if tok.value != ";" && tok.value != "," { + p.back() + } + return nil +} + +func (p *textParser) readAny(v reflect.Value, props *Properties) error { + tok := p.next() + if tok.err != nil { + return tok.err + } + if tok.value == "" { + return p.errorf("unexpected EOF") + } + + switch fv := v; fv.Kind() { + case reflect.Slice: + at := v.Type() + if at.Elem().Kind() == reflect.Uint8 { + // Special case for []byte + if tok.value[0] != '"' && tok.value[0] != '\'' { + // Deliberately written out here, as the error after + // this switch statement would write "invalid []byte: ...", + // which is not as user-friendly. + return p.errorf("invalid string: %v", tok.value) + } + bytes := []byte(tok.unquoted) + fv.Set(reflect.ValueOf(bytes)) + return nil + } + // Repeated field. + if tok.value == "[" { + // Repeated field with list notation, like [1,2,3]. + for { + fv.Set(reflect.Append(fv, reflect.New(at.Elem()).Elem())) + err := p.readAny(fv.Index(fv.Len()-1), props) + if err != nil { + return err + } + tok := p.next() + if tok.err != nil { + return tok.err + } + if tok.value == "]" { + break + } + if tok.value != "," { + return p.errorf("Expected ']' or ',' found %q", tok.value) + } + } + return nil + } + // One value of the repeated field. + p.back() + fv.Set(reflect.Append(fv, reflect.New(at.Elem()).Elem())) + return p.readAny(fv.Index(fv.Len()-1), props) + case reflect.Bool: + // Either "true", "false", 1 or 0. + switch tok.value { + case "true", "1": + fv.SetBool(true) + return nil + case "false", "0": + fv.SetBool(false) + return nil + } + case reflect.Float32, reflect.Float64: + v := tok.value + // Ignore 'f' for compatibility with output generated by C++, but don't + // remove 'f' when the value is "-inf" or "inf". + if strings.HasSuffix(v, "f") && tok.value != "-inf" && tok.value != "inf" { + v = v[:len(v)-1] + } + if f, err := strconv.ParseFloat(v, fv.Type().Bits()); err == nil { + fv.SetFloat(f) + return nil + } + case reflect.Int32: + if x, err := strconv.ParseInt(tok.value, 0, 32); err == nil { + fv.SetInt(x) + return nil + } + + if len(props.Enum) == 0 { + break + } + m, ok := enumValueMaps[props.Enum] + if !ok { + break + } + x, ok := m[tok.value] + if !ok { + break + } + fv.SetInt(int64(x)) + return nil + case reflect.Int64: + if x, err := strconv.ParseInt(tok.value, 0, 64); err == nil { + fv.SetInt(x) + return nil + } + + case reflect.Ptr: + // A basic field (indirected through pointer), or a repeated message/group + p.back() + fv.Set(reflect.New(fv.Type().Elem())) + return p.readAny(fv.Elem(), props) + case reflect.String: + if tok.value[0] == '"' || tok.value[0] == '\'' { + fv.SetString(tok.unquoted) + return nil + } + case reflect.Struct: + var terminator string + switch tok.value { + case "{": + terminator = "}" + case "<": + terminator = ">" + default: + return p.errorf("expected '{' or '<', found %q", tok.value) + } + // TODO: Handle nested messages which implement encoding.TextUnmarshaler. + return p.readStruct(fv, terminator) + case reflect.Uint32: + if x, err := strconv.ParseUint(tok.value, 0, 32); err == nil { + fv.SetUint(uint64(x)) + return nil + } + case reflect.Uint64: + if x, err := strconv.ParseUint(tok.value, 0, 64); err == nil { + fv.SetUint(x) + return nil + } + } + return p.errorf("invalid %v: %v", v.Type(), tok.value) +} + +// UnmarshalText reads a protocol buffer in Text format. UnmarshalText resets pb +// before starting to unmarshal, so any existing data in pb is always removed. +// If a required field is not set and no other error occurs, +// UnmarshalText returns *RequiredNotSetError. +func UnmarshalText(s string, pb Message) error { + if um, ok := pb.(encoding.TextUnmarshaler); ok { + err := um.UnmarshalText([]byte(s)) + return err + } + pb.Reset() + v := reflect.ValueOf(pb) + if pe := newTextParser(s).readStruct(v.Elem(), ""); pe != nil { + return pe + } + return nil +} diff --git a/vendor/github.com/google/go-github/LICENSE b/vendor/github.com/google/go-github/LICENSE new file mode 100644 index 000000000..3a3a8ec0e --- /dev/null +++ b/vendor/github.com/google/go-github/LICENSE @@ -0,0 +1,340 @@ +Copyright (c) 2013 The go-github AUTHORS. All rights reserved. + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are +met: + + * Redistributions of source code must retain the above copyright +notice, this list of conditions and the following disclaimer. + * Redistributions in binary form must reproduce the above +copyright notice, this list of conditions and the following disclaimer +in the documentation and/or other materials provided with the +distribution. + * Neither the name of Google Inc. nor the names of its +contributors may be used to endorse or promote products derived from +this software without specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +---------- + +Some documentation is taken from the GitHub Developer site +, which is available under a Creative Commons +Attribution 3.0 License: + +THE WORK (AS DEFINED BELOW) IS PROVIDED UNDER THE TERMS OF THIS CREATIVE +COMMONS PUBLIC LICENSE ("CCPL" OR "LICENSE"). THE WORK IS PROTECTED BY +COPYRIGHT AND/OR OTHER APPLICABLE LAW. ANY USE OF THE WORK OTHER THAN AS +AUTHORIZED UNDER THIS LICENSE OR COPYRIGHT LAW IS PROHIBITED. + +BY EXERCISING ANY RIGHTS TO THE WORK PROVIDED HERE, YOU ACCEPT AND AGREE +TO BE BOUND BY THE TERMS OF THIS LICENSE. TO THE EXTENT THIS LICENSE MAY +BE CONSIDERED TO BE A CONTRACT, THE LICENSOR GRANTS YOU THE RIGHTS +CONTAINED HERE IN CONSIDERATION OF YOUR ACCEPTANCE OF SUCH TERMS AND +CONDITIONS. + +1. Definitions + + a. "Adaptation" means a work based upon the Work, or upon the Work and + other pre-existing works, such as a translation, adaptation, + derivative work, arrangement of music or other alterations of a + literary or artistic work, or phonogram or performance and includes + cinematographic adaptations or any other form in which the Work may be + recast, transformed, or adapted including in any form recognizably + derived from the original, except that a work that constitutes a + Collection will not be considered an Adaptation for the purpose of + this License. For the avoidance of doubt, where the Work is a musical + work, performance or phonogram, the synchronization of the Work in + timed-relation with a moving image ("synching") will be considered an + Adaptation for the purpose of this License. + b. "Collection" means a collection of literary or artistic works, such as + encyclopedias and anthologies, or performances, phonograms or + broadcasts, or other works or subject matter other than works listed + in Section 1(f) below, which, by reason of the selection and + arrangement of their contents, constitute intellectual creations, in + which the Work is included in its entirety in unmodified form along + with one or more other contributions, each constituting separate and + independent works in themselves, which together are assembled into a + collective whole. A work that constitutes a Collection will not be + considered an Adaptation (as defined above) for the purposes of this + License. + c. "Distribute" means to make available to the public the original and + copies of the Work or Adaptation, as appropriate, through sale or + other transfer of ownership. + d. "Licensor" means the individual, individuals, entity or entities that + offer(s) the Work under the terms of this License. + e. "Original Author" means, in the case of a literary or artistic work, + the individual, individuals, entity or entities who created the Work + or if no individual or entity can be identified, the publisher; and in + addition (i) in the case of a performance the actors, singers, + musicians, dancers, and other persons who act, sing, deliver, declaim, + play in, interpret or otherwise perform literary or artistic works or + expressions of folklore; (ii) in the case of a phonogram the producer + being the person or legal entity who first fixes the sounds of a + performance or other sounds; and, (iii) in the case of broadcasts, the + organization that transmits the broadcast. + f. "Work" means the literary and/or artistic work offered under the terms + of this License including without limitation any production in the + literary, scientific and artistic domain, whatever may be the mode or + form of its expression including digital form, such as a book, + pamphlet and other writing; a lecture, address, sermon or other work + of the same nature; a dramatic or dramatico-musical work; a + choreographic work or entertainment in dumb show; a musical + composition with or without words; a cinematographic work to which are + assimilated works expressed by a process analogous to cinematography; + a work of drawing, painting, architecture, sculpture, engraving or + lithography; a photographic work to which are assimilated works + expressed by a process analogous to photography; a work of applied + art; an illustration, map, plan, sketch or three-dimensional work + relative to geography, topography, architecture or science; a + performance; a broadcast; a phonogram; a compilation of data to the + extent it is protected as a copyrightable work; or a work performed by + a variety or circus performer to the extent it is not otherwise + considered a literary or artistic work. + g. "You" means an individual or entity exercising rights under this + License who has not previously violated the terms of this License with + respect to the Work, or who has received express permission from the + Licensor to exercise rights under this License despite a previous + violation. + h. "Publicly Perform" means to perform public recitations of the Work and + to communicate to the public those public recitations, by any means or + process, including by wire or wireless means or public digital + performances; to make available to the public Works in such a way that + members of the public may access these Works from a place and at a + place individually chosen by them; to perform the Work to the public + by any means or process and the communication to the public of the + performances of the Work, including by public digital performance; to + broadcast and rebroadcast the Work by any means including signs, + sounds or images. + i. "Reproduce" means to make copies of the Work by any means including + without limitation by sound or visual recordings and the right of + fixation and reproducing fixations of the Work, including storage of a + protected performance or phonogram in digital form or other electronic + medium. + +2. Fair Dealing Rights. Nothing in this License is intended to reduce, +limit, or restrict any uses free from copyright or rights arising from +limitations or exceptions that are provided for in connection with the +copyright protection under copyright law or other applicable laws. + +3. License Grant. Subject to the terms and conditions of this License, +Licensor hereby grants You a worldwide, royalty-free, non-exclusive, +perpetual (for the duration of the applicable copyright) license to +exercise the rights in the Work as stated below: + + a. to Reproduce the Work, to incorporate the Work into one or more + Collections, and to Reproduce the Work as incorporated in the + Collections; + b. to create and Reproduce Adaptations provided that any such Adaptation, + including any translation in any medium, takes reasonable steps to + clearly label, demarcate or otherwise identify that changes were made + to the original Work. For example, a translation could be marked "The + original work was translated from English to Spanish," or a + modification could indicate "The original work has been modified."; + c. to Distribute and Publicly Perform the Work including as incorporated + in Collections; and, + d. to Distribute and Publicly Perform Adaptations. + e. For the avoidance of doubt: + + i. Non-waivable Compulsory License Schemes. In those jurisdictions in + which the right to collect royalties through any statutory or + compulsory licensing scheme cannot be waived, the Licensor + reserves the exclusive right to collect such royalties for any + exercise by You of the rights granted under this License; + ii. Waivable Compulsory License Schemes. In those jurisdictions in + which the right to collect royalties through any statutory or + compulsory licensing scheme can be waived, the Licensor waives the + exclusive right to collect such royalties for any exercise by You + of the rights granted under this License; and, + iii. Voluntary License Schemes. The Licensor waives the right to + collect royalties, whether individually or, in the event that the + Licensor is a member of a collecting society that administers + voluntary licensing schemes, via that society, from any exercise + by You of the rights granted under this License. + +The above rights may be exercised in all media and formats whether now +known or hereafter devised. The above rights include the right to make +such modifications as are technically necessary to exercise the rights in +other media and formats. Subject to Section 8(f), all rights not expressly +granted by Licensor are hereby reserved. + +4. Restrictions. The license granted in Section 3 above is expressly made +subject to and limited by the following restrictions: + + a. You may Distribute or Publicly Perform the Work only under the terms + of this License. You must include a copy of, or the Uniform Resource + Identifier (URI) for, this License with every copy of the Work You + Distribute or Publicly Perform. You may not offer or impose any terms + on the Work that restrict the terms of this License or the ability of + the recipient of the Work to exercise the rights granted to that + recipient under the terms of the License. You may not sublicense the + Work. You must keep intact all notices that refer to this License and + to the disclaimer of warranties with every copy of the Work You + Distribute or Publicly Perform. When You Distribute or Publicly + Perform the Work, You may not impose any effective technological + measures on the Work that restrict the ability of a recipient of the + Work from You to exercise the rights granted to that recipient under + the terms of the License. This Section 4(a) applies to the Work as + incorporated in a Collection, but this does not require the Collection + apart from the Work itself to be made subject to the terms of this + License. If You create a Collection, upon notice from any Licensor You + must, to the extent practicable, remove from the Collection any credit + as required by Section 4(b), as requested. If You create an + Adaptation, upon notice from any Licensor You must, to the extent + practicable, remove from the Adaptation any credit as required by + Section 4(b), as requested. + b. If You Distribute, or Publicly Perform the Work or any Adaptations or + Collections, You must, unless a request has been made pursuant to + Section 4(a), keep intact all copyright notices for the Work and + provide, reasonable to the medium or means You are utilizing: (i) the + name of the Original Author (or pseudonym, if applicable) if supplied, + and/or if the Original Author and/or Licensor designate another party + or parties (e.g., a sponsor institute, publishing entity, journal) for + attribution ("Attribution Parties") in Licensor's copyright notice, + terms of service or by other reasonable means, the name of such party + or parties; (ii) the title of the Work if supplied; (iii) to the + extent reasonably practicable, the URI, if any, that Licensor + specifies to be associated with the Work, unless such URI does not + refer to the copyright notice or licensing information for the Work; + and (iv) , consistent with Section 3(b), in the case of an Adaptation, + a credit identifying the use of the Work in the Adaptation (e.g., + "French translation of the Work by Original Author," or "Screenplay + based on original Work by Original Author"). The credit required by + this Section 4 (b) may be implemented in any reasonable manner; + provided, however, that in the case of a Adaptation or Collection, at + a minimum such credit will appear, if a credit for all contributing + authors of the Adaptation or Collection appears, then as part of these + credits and in a manner at least as prominent as the credits for the + other contributing authors. For the avoidance of doubt, You may only + use the credit required by this Section for the purpose of attribution + in the manner set out above and, by exercising Your rights under this + License, You may not implicitly or explicitly assert or imply any + connection with, sponsorship or endorsement by the Original Author, + Licensor and/or Attribution Parties, as appropriate, of You or Your + use of the Work, without the separate, express prior written + permission of the Original Author, Licensor and/or Attribution + Parties. + c. Except as otherwise agreed in writing by the Licensor or as may be + otherwise permitted by applicable law, if You Reproduce, Distribute or + Publicly Perform the Work either by itself or as part of any + Adaptations or Collections, You must not distort, mutilate, modify or + take other derogatory action in relation to the Work which would be + prejudicial to the Original Author's honor or reputation. Licensor + agrees that in those jurisdictions (e.g. Japan), in which any exercise + of the right granted in Section 3(b) of this License (the right to + make Adaptations) would be deemed to be a distortion, mutilation, + modification or other derogatory action prejudicial to the Original + Author's honor and reputation, the Licensor will waive or not assert, + as appropriate, this Section, to the fullest extent permitted by the + applicable national law, to enable You to reasonably exercise Your + right under Section 3(b) of this License (right to make Adaptations) + but not otherwise. + +5. Representations, Warranties and Disclaimer + +UNLESS OTHERWISE MUTUALLY AGREED TO BY THE PARTIES IN WRITING, LICENSOR +OFFERS THE WORK AS-IS AND MAKES NO REPRESENTATIONS OR WARRANTIES OF ANY +KIND CONCERNING THE WORK, EXPRESS, IMPLIED, STATUTORY OR OTHERWISE, +INCLUDING, WITHOUT LIMITATION, WARRANTIES OF TITLE, MERCHANTIBILITY, +FITNESS FOR A PARTICULAR PURPOSE, NONINFRINGEMENT, OR THE ABSENCE OF +LATENT OR OTHER DEFECTS, ACCURACY, OR THE PRESENCE OF ABSENCE OF ERRORS, +WHETHER OR NOT DISCOVERABLE. SOME JURISDICTIONS DO NOT ALLOW THE EXCLUSION +OF IMPLIED WARRANTIES, SO SUCH EXCLUSION MAY NOT APPLY TO YOU. + +6. Limitation on Liability. EXCEPT TO THE EXTENT REQUIRED BY APPLICABLE +LAW, IN NO EVENT WILL LICENSOR BE LIABLE TO YOU ON ANY LEGAL THEORY FOR +ANY SPECIAL, INCIDENTAL, CONSEQUENTIAL, PUNITIVE OR EXEMPLARY DAMAGES +ARISING OUT OF THIS LICENSE OR THE USE OF THE WORK, EVEN IF LICENSOR HAS +BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. + +7. Termination + + a. This License and the rights granted hereunder will terminate + automatically upon any breach by You of the terms of this License. + Individuals or entities who have received Adaptations or Collections + from You under this License, however, will not have their licenses + terminated provided such individuals or entities remain in full + compliance with those licenses. Sections 1, 2, 5, 6, 7, and 8 will + survive any termination of this License. + b. Subject to the above terms and conditions, the license granted here is + perpetual (for the duration of the applicable copyright in the Work). + Notwithstanding the above, Licensor reserves the right to release the + Work under different license terms or to stop distributing the Work at + any time; provided, however that any such election will not serve to + withdraw this License (or any other license that has been, or is + required to be, granted under the terms of this License), and this + License will continue in full force and effect unless terminated as + stated above. + +8. Miscellaneous + + a. Each time You Distribute or Publicly Perform the Work or a Collection, + the Licensor offers to the recipient a license to the Work on the same + terms and conditions as the license granted to You under this License. + b. Each time You Distribute or Publicly Perform an Adaptation, Licensor + offers to the recipient a license to the original Work on the same + terms and conditions as the license granted to You under this License. + c. If any provision of this License is invalid or unenforceable under + applicable law, it shall not affect the validity or enforceability of + the remainder of the terms of this License, and without further action + by the parties to this agreement, such provision shall be reformed to + the minimum extent necessary to make such provision valid and + enforceable. + d. No term or provision of this License shall be deemed waived and no + breach consented to unless such waiver or consent shall be in writing + and signed by the party to be charged with such waiver or consent. + e. This License constitutes the entire agreement between the parties with + respect to the Work licensed here. There are no understandings, + agreements or representations with respect to the Work not specified + here. Licensor shall not be bound by any additional provisions that + may appear in any communication from You. This License may not be + modified without the mutual written agreement of the Licensor and You. + f. The rights granted under, and the subject matter referenced, in this + License were drafted utilizing the terminology of the Berne Convention + for the Protection of Literary and Artistic Works (as amended on + September 28, 1979), the Rome Convention of 1961, the WIPO Copyright + Treaty of 1996, the WIPO Performances and Phonograms Treaty of 1996 + and the Universal Copyright Convention (as revised on July 24, 1971). + These rights and subject matter take effect in the relevant + jurisdiction in which the License terms are sought to be enforced + according to the corresponding provisions of the implementation of + those treaty provisions in the applicable national law. If the + standard suite of rights granted under applicable copyright law + includes additional rights not granted under this License, such + additional rights are deemed to be included in the License; this + License is not intended to restrict the license of any rights under + applicable law. + + +Creative Commons Notice + + Creative Commons is not a party to this License, and makes no warranty + whatsoever in connection with the Work. Creative Commons will not be + liable to You or any party on any legal theory for any damages + whatsoever, including without limitation any general, special, + incidental or consequential damages arising in connection to this + license. Notwithstanding the foregoing two (2) sentences, if Creative + Commons has expressly identified itself as the Licensor hereunder, it + shall have all rights and obligations of Licensor. + + Except for the limited purpose of indicating to the public that the + Work is licensed under the CCPL, Creative Commons does not authorize + the use by either party of the trademark "Creative Commons" or any + related trademark or logo of Creative Commons without the prior + written consent of Creative Commons. Any permitted use will be in + compliance with Creative Commons' then-current trademark usage + guidelines, as may be published on its website or otherwise made + available upon request from time to time. For the avoidance of doubt, + this trademark restriction does not form part of this License. + + Creative Commons may be contacted at http://creativecommons.org/. diff --git a/vendor/github.com/google/go-github/github/activity_events.go b/vendor/github.com/google/go-github/github/activity_events.go index b8a5e66b9..2a40d3e00 100644 --- a/vendor/github.com/google/go-github/github/activity_events.go +++ b/vendor/github.com/google/go-github/github/activity_events.go @@ -249,11 +249,11 @@ func (s *ActivityService) ListEventsPerformedByUser(user string, publicOnly bool return *events, resp, err } -// ListEventsRecievedByUser lists the events recieved by a user. If publicOnly is +// ListEventsReceivedByUser lists the events received by a user. If publicOnly is // true, only public events will be returned. // // GitHub API docs: http://developer.github.com/v3/activity/events/#list-events-that-a-user-has-received -func (s *ActivityService) ListEventsRecievedByUser(user string, publicOnly bool, opt *ListOptions) ([]Event, *Response, error) { +func (s *ActivityService) ListEventsReceivedByUser(user string, publicOnly bool, opt *ListOptions) ([]Event, *Response, error) { var u string if publicOnly { u = fmt.Sprintf("users/%v/received_events/public", user) diff --git a/vendor/github.com/google/go-github/github/activity_events_test.go b/vendor/github.com/google/go-github/github/activity_events_test.go deleted file mode 100644 index 1541f5e9f..000000000 --- a/vendor/github.com/google/go-github/github/activity_events_test.go +++ /dev/null @@ -1,305 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestActivityService_ListEvents(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/events", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "page": "2", - }) - fmt.Fprint(w, `[{"id":"1"},{"id":"2"}]`) - }) - - opt := &ListOptions{Page: 2} - events, _, err := client.Activity.ListEvents(opt) - if err != nil { - t.Errorf("Activities.ListEvents returned error: %v", err) - } - - want := []Event{{ID: String("1")}, {ID: String("2")}} - if !reflect.DeepEqual(events, want) { - t.Errorf("Activities.ListEvents returned %+v, want %+v", events, want) - } -} - -func TestActivityService_ListRepositoryEvents(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/events", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "page": "2", - }) - fmt.Fprint(w, `[{"id":"1"},{"id":"2"}]`) - }) - - opt := &ListOptions{Page: 2} - events, _, err := client.Activity.ListRepositoryEvents("o", "r", opt) - if err != nil { - t.Errorf("Activities.ListRepositoryEvents returned error: %v", err) - } - - want := []Event{{ID: String("1")}, {ID: String("2")}} - if !reflect.DeepEqual(events, want) { - t.Errorf("Activities.ListRepositoryEvents returned %+v, want %+v", events, want) - } -} - -func TestActivityService_ListRepositoryEvents_invalidOwner(t *testing.T) { - _, _, err := client.Activity.ListRepositoryEvents("%", "%", nil) - testURLParseError(t, err) -} - -func TestActivityService_ListIssueEventsForRepository(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/issues/events", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "page": "2", - }) - fmt.Fprint(w, `[{"id":"1"},{"id":"2"}]`) - }) - - opt := &ListOptions{Page: 2} - events, _, err := client.Activity.ListIssueEventsForRepository("o", "r", opt) - if err != nil { - t.Errorf("Activities.ListIssueEventsForRepository returned error: %v", err) - } - - want := []Event{{ID: String("1")}, {ID: String("2")}} - if !reflect.DeepEqual(events, want) { - t.Errorf("Activities.ListIssueEventsForRepository returned %+v, want %+v", events, want) - } -} - -func TestActivityService_ListIssueEventsForRepository_invalidOwner(t *testing.T) { - _, _, err := client.Activity.ListIssueEventsForRepository("%", "%", nil) - testURLParseError(t, err) -} - -func TestActivityService_ListEventsForRepoNetwork(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/networks/o/r/events", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "page": "2", - }) - fmt.Fprint(w, `[{"id":"1"},{"id":"2"}]`) - }) - - opt := &ListOptions{Page: 2} - events, _, err := client.Activity.ListEventsForRepoNetwork("o", "r", opt) - if err != nil { - t.Errorf("Activities.ListEventsForRepoNetwork returned error: %v", err) - } - - want := []Event{{ID: String("1")}, {ID: String("2")}} - if !reflect.DeepEqual(events, want) { - t.Errorf("Activities.ListEventsForRepoNetwork returned %+v, want %+v", events, want) - } -} - -func TestActivityService_ListEventsForRepoNetwork_invalidOwner(t *testing.T) { - _, _, err := client.Activity.ListEventsForRepoNetwork("%", "%", nil) - testURLParseError(t, err) -} - -func TestActivityService_ListEventsForOrganization(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/orgs/o/events", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "page": "2", - }) - fmt.Fprint(w, `[{"id":"1"},{"id":"2"}]`) - }) - - opt := &ListOptions{Page: 2} - events, _, err := client.Activity.ListEventsForOrganization("o", opt) - if err != nil { - t.Errorf("Activities.ListEventsForOrganization returned error: %v", err) - } - - want := []Event{{ID: String("1")}, {ID: String("2")}} - if !reflect.DeepEqual(events, want) { - t.Errorf("Activities.ListEventsForOrganization returned %+v, want %+v", events, want) - } -} - -func TestActivityService_ListEventsForOrganization_invalidOrg(t *testing.T) { - _, _, err := client.Activity.ListEventsForOrganization("%", nil) - testURLParseError(t, err) -} - -func TestActivityService_ListEventsPerformedByUser_all(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/users/u/events", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "page": "2", - }) - fmt.Fprint(w, `[{"id":"1"},{"id":"2"}]`) - }) - - opt := &ListOptions{Page: 2} - events, _, err := client.Activity.ListEventsPerformedByUser("u", false, opt) - if err != nil { - t.Errorf("Events.ListPerformedByUser returned error: %v", err) - } - - want := []Event{{ID: String("1")}, {ID: String("2")}} - if !reflect.DeepEqual(events, want) { - t.Errorf("Events.ListPerformedByUser returned %+v, want %+v", events, want) - } -} - -func TestActivityService_ListEventsPerformedByUser_publicOnly(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/users/u/events/public", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `[{"id":"1"},{"id":"2"}]`) - }) - - events, _, err := client.Activity.ListEventsPerformedByUser("u", true, nil) - if err != nil { - t.Errorf("Events.ListPerformedByUser returned error: %v", err) - } - - want := []Event{{ID: String("1")}, {ID: String("2")}} - if !reflect.DeepEqual(events, want) { - t.Errorf("Events.ListPerformedByUser returned %+v, want %+v", events, want) - } -} - -func TestActivityService_ListEventsPerformedByUser_invalidUser(t *testing.T) { - _, _, err := client.Activity.ListEventsPerformedByUser("%", false, nil) - testURLParseError(t, err) -} - -func TestActivityService_ListEventsRecievedByUser_all(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/users/u/received_events", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "page": "2", - }) - fmt.Fprint(w, `[{"id":"1"},{"id":"2"}]`) - }) - - opt := &ListOptions{Page: 2} - events, _, err := client.Activity.ListEventsRecievedByUser("u", false, opt) - if err != nil { - t.Errorf("Events.ListRecievedByUser returned error: %v", err) - } - - want := []Event{{ID: String("1")}, {ID: String("2")}} - if !reflect.DeepEqual(events, want) { - t.Errorf("Events.ListRecievedUser returned %+v, want %+v", events, want) - } -} - -func TestActivityService_ListEventsRecievedByUser_publicOnly(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/users/u/received_events/public", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `[{"id":"1"},{"id":"2"}]`) - }) - - events, _, err := client.Activity.ListEventsRecievedByUser("u", true, nil) - if err != nil { - t.Errorf("Events.ListRecievedByUser returned error: %v", err) - } - - want := []Event{{ID: String("1")}, {ID: String("2")}} - if !reflect.DeepEqual(events, want) { - t.Errorf("Events.ListRecievedByUser returned %+v, want %+v", events, want) - } -} - -func TestActivityService_ListEventsRecievedByUser_invalidUser(t *testing.T) { - _, _, err := client.Activity.ListEventsRecievedByUser("%", false, nil) - testURLParseError(t, err) -} - -func TestActivityService_ListUserEventsForOrganization(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/users/u/events/orgs/o", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "page": "2", - }) - fmt.Fprint(w, `[{"id":"1"},{"id":"2"}]`) - }) - - opt := &ListOptions{Page: 2} - events, _, err := client.Activity.ListUserEventsForOrganization("o", "u", opt) - if err != nil { - t.Errorf("Activities.ListUserEventsForOrganization returned error: %v", err) - } - - want := []Event{{ID: String("1")}, {ID: String("2")}} - if !reflect.DeepEqual(events, want) { - t.Errorf("Activities.ListUserEventsForOrganization returned %+v, want %+v", events, want) - } -} - -func TestActivity_EventPayload_typed(t *testing.T) { - raw := []byte(`{"type": "PushEvent","payload":{"push_id": 1}}`) - var event *Event - if err := json.Unmarshal(raw, &event); err != nil { - t.Fatalf("Unmarshal Event returned error: %v", err) - } - - want := &PushEvent{PushID: Int(1)} - if !reflect.DeepEqual(event.Payload(), want) { - t.Errorf("Event Payload returned %+v, want %+v", event.Payload(), want) - } -} - -// TestEvent_Payload_untyped checks that unrecognized events are parsed to an -// interface{} value (instead of being discarded or throwing an error), for -// forward compatibility with new event types. -func TestActivity_EventPayload_untyped(t *testing.T) { - raw := []byte(`{"type": "UnrecognizedEvent","payload":{"field": "val"}}`) - var event *Event - if err := json.Unmarshal(raw, &event); err != nil { - t.Fatalf("Unmarshal Event returned error: %v", err) - } - - want := map[string]interface{}{"field": "val"} - if !reflect.DeepEqual(event.Payload(), want) { - t.Errorf("Event Payload returned %+v, want %+v", event.Payload(), want) - } -} diff --git a/vendor/github.com/google/go-github/github/activity_notifications.go b/vendor/github.com/google/go-github/github/activity_notifications.go index 786df98a9..290b95427 100644 --- a/vendor/github.com/google/go-github/github/activity_notifications.go +++ b/vendor/github.com/google/go-github/github/activity_notifications.go @@ -41,6 +41,7 @@ type NotificationListOptions struct { All bool `url:"all,omitempty"` Participating bool `url:"participating,omitempty"` Since time.Time `url:"since,omitempty"` + Before time.Time `url:"before,omitempty"` } // ListNotifications lists all notifications for the authenticated user. diff --git a/vendor/github.com/google/go-github/github/activity_notifications_test.go b/vendor/github.com/google/go-github/github/activity_notifications_test.go deleted file mode 100644 index 829e118e9..000000000 --- a/vendor/github.com/google/go-github/github/activity_notifications_test.go +++ /dev/null @@ -1,203 +0,0 @@ -// Copyright 2014 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" - "time" -) - -func TestActivityService_ListNotification(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/notifications", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "all": "true", - "participating": "true", - "since": "2006-01-02T15:04:05Z", - }) - - fmt.Fprint(w, `[{"id":"1", "subject":{"title":"t"}}]`) - }) - - opt := &NotificationListOptions{ - All: true, - Participating: true, - Since: time.Date(2006, 01, 02, 15, 04, 05, 0, time.UTC), - } - notifications, _, err := client.Activity.ListNotifications(opt) - if err != nil { - t.Errorf("Activity.ListNotifications returned error: %v", err) - } - - want := []Notification{{ID: String("1"), Subject: &NotificationSubject{Title: String("t")}}} - if !reflect.DeepEqual(notifications, want) { - t.Errorf("Activity.ListNotifications returned %+v, want %+v", notifications, want) - } -} - -func TestActivityService_ListRepositoryNotification(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/notifications", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `[{"id":"1"}]`) - }) - - notifications, _, err := client.Activity.ListRepositoryNotifications("o", "r", nil) - if err != nil { - t.Errorf("Activity.ListRepositoryNotifications returned error: %v", err) - } - - want := []Notification{{ID: String("1")}} - if !reflect.DeepEqual(notifications, want) { - t.Errorf("Activity.ListRepositoryNotifications returned %+v, want %+v", notifications, want) - } -} - -func TestActivityService_MarkNotificationsRead(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/notifications", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "PUT") - testFormValues(t, r, values{ - "last_read_at": "2006-01-02T15:04:05Z", - }) - - w.WriteHeader(http.StatusResetContent) - }) - - _, err := client.Activity.MarkNotificationsRead(time.Date(2006, 01, 02, 15, 04, 05, 0, time.UTC)) - if err != nil { - t.Errorf("Activity.MarkNotificationsRead returned error: %v", err) - } -} - -func TestActivityService_MarkRepositoryNotificationsRead(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/notifications", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "PUT") - testFormValues(t, r, values{ - "last_read_at": "2006-01-02T15:04:05Z", - }) - - w.WriteHeader(http.StatusResetContent) - }) - - _, err := client.Activity.MarkRepositoryNotificationsRead("o", "r", time.Date(2006, 01, 02, 15, 04, 05, 0, time.UTC)) - if err != nil { - t.Errorf("Activity.MarkRepositoryNotificationsRead returned error: %v", err) - } -} - -func TestActivityService_GetThread(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/notifications/threads/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"id":"1"}`) - }) - - notification, _, err := client.Activity.GetThread("1") - if err != nil { - t.Errorf("Activity.GetThread returned error: %v", err) - } - - want := &Notification{ID: String("1")} - if !reflect.DeepEqual(notification, want) { - t.Errorf("Activity.GetThread returned %+v, want %+v", notification, want) - } -} - -func TestActivityService_MarkThreadRead(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/notifications/threads/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "PATCH") - w.WriteHeader(http.StatusResetContent) - }) - - _, err := client.Activity.MarkThreadRead("1") - if err != nil { - t.Errorf("Activity.MarkThreadRead returned error: %v", err) - } -} - -func TestActivityService_GetThreadSubscription(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/notifications/threads/1/subscription", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"subscribed":true}`) - }) - - sub, _, err := client.Activity.GetThreadSubscription("1") - if err != nil { - t.Errorf("Activity.GetThreadSubscription returned error: %v", err) - } - - want := &Subscription{Subscribed: Bool(true)} - if !reflect.DeepEqual(sub, want) { - t.Errorf("Activity.GetThreadSubscription returned %+v, want %+v", sub, want) - } -} - -func TestActivityService_SetThreadSubscription(t *testing.T) { - setup() - defer teardown() - - input := &Subscription{Subscribed: Bool(true)} - - mux.HandleFunc("/notifications/threads/1/subscription", func(w http.ResponseWriter, r *http.Request) { - v := new(Subscription) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "PUT") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"ignored":true}`) - }) - - sub, _, err := client.Activity.SetThreadSubscription("1", input) - if err != nil { - t.Errorf("Activity.SetThreadSubscription returned error: %v", err) - } - - want := &Subscription{Ignored: Bool(true)} - if !reflect.DeepEqual(sub, want) { - t.Errorf("Activity.SetThreadSubscription returned %+v, want %+v", sub, want) - } -} - -func TestActivityService_DeleteThreadSubscription(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/notifications/threads/1/subscription", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - w.WriteHeader(http.StatusNoContent) - }) - - _, err := client.Activity.DeleteThreadSubscription("1") - if err != nil { - t.Errorf("Activity.DeleteThreadSubscription returned error: %v", err) - } -} diff --git a/vendor/github.com/google/go-github/github/activity_star.go b/vendor/github.com/google/go-github/github/activity_star.go index 982f24d71..fac4f41d2 100644 --- a/vendor/github.com/google/go-github/github/activity_star.go +++ b/vendor/github.com/google/go-github/github/activity_star.go @@ -7,6 +7,12 @@ package github import "fmt" +// StarredRepository is returned by ListStarred. +type StarredRepository struct { + StarredAt *Timestamp `json:"starred_at,omitempty"` + Repository *Repository `json:"repo,omitempty"` +} + // ListStargazers lists people who have starred the specified repo. // // GitHub API Docs: https://developer.github.com/v3/activity/starring/#list-stargazers @@ -49,7 +55,7 @@ type ActivityListStarredOptions struct { // will list the starred repositories for the authenticated user. // // GitHub API docs: http://developer.github.com/v3/activity/starring/#list-repositories-being-starred -func (s *ActivityService) ListStarred(user string, opt *ActivityListStarredOptions) ([]Repository, *Response, error) { +func (s *ActivityService) ListStarred(user string, opt *ActivityListStarredOptions) ([]StarredRepository, *Response, error) { var u string if user != "" { u = fmt.Sprintf("users/%v/starred", user) @@ -66,7 +72,10 @@ func (s *ActivityService) ListStarred(user string, opt *ActivityListStarredOptio return nil, nil, err } - repos := new([]Repository) + // TODO: remove custom Accept header when this API fully launches + req.Header.Set("Accept", mediaTypeStarringPreview) + + repos := new([]StarredRepository) resp, err := s.client.Do(req, repos) if err != nil { return nil, resp, err diff --git a/vendor/github.com/google/go-github/github/activity_star_test.go b/vendor/github.com/google/go-github/github/activity_star_test.go deleted file mode 100644 index ae33b93cf..000000000 --- a/vendor/github.com/google/go-github/github/activity_star_test.go +++ /dev/null @@ -1,167 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestActivityService_ListStargazers(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/stargazers", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "page": "2", - }) - - fmt.Fprint(w, `[{"id":1}]`) - }) - - stargazers, _, err := client.Activity.ListStargazers("o", "r", &ListOptions{Page: 2}) - if err != nil { - t.Errorf("Activity.ListStargazers returned error: %v", err) - } - - want := []User{{ID: Int(1)}} - if !reflect.DeepEqual(stargazers, want) { - t.Errorf("Activity.ListStargazers returned %+v, want %+v", stargazers, want) - } -} - -func TestActivityService_ListStarred_authenticatedUser(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/user/starred", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `[{"id":1}]`) - }) - - repos, _, err := client.Activity.ListStarred("", nil) - if err != nil { - t.Errorf("Activity.ListStarred returned error: %v", err) - } - - want := []Repository{{ID: Int(1)}} - if !reflect.DeepEqual(repos, want) { - t.Errorf("Activity.ListStarred returned %+v, want %+v", repos, want) - } -} - -func TestActivityService_ListStarred_specifiedUser(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/users/u/starred", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "sort": "created", - "direction": "asc", - "page": "2", - }) - fmt.Fprint(w, `[{"id":2}]`) - }) - - opt := &ActivityListStarredOptions{"created", "asc", ListOptions{Page: 2}} - repos, _, err := client.Activity.ListStarred("u", opt) - if err != nil { - t.Errorf("Activity.ListStarred returned error: %v", err) - } - - want := []Repository{{ID: Int(2)}} - if !reflect.DeepEqual(repos, want) { - t.Errorf("Activity.ListStarred returned %+v, want %+v", repos, want) - } -} - -func TestActivityService_ListStarred_invalidUser(t *testing.T) { - _, _, err := client.Activity.ListStarred("%", nil) - testURLParseError(t, err) -} - -func TestActivityService_IsStarred_hasStar(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/user/starred/o/r", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - w.WriteHeader(http.StatusNoContent) - }) - - star, _, err := client.Activity.IsStarred("o", "r") - if err != nil { - t.Errorf("Activity.IsStarred returned error: %v", err) - } - if want := true; star != want { - t.Errorf("Activity.IsStarred returned %+v, want %+v", star, want) - } -} - -func TestActivityService_IsStarred_noStar(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/user/starred/o/r", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - w.WriteHeader(http.StatusNotFound) - }) - - star, _, err := client.Activity.IsStarred("o", "r") - if err != nil { - t.Errorf("Activity.IsStarred returned error: %v", err) - } - if want := false; star != want { - t.Errorf("Activity.IsStarred returned %+v, want %+v", star, want) - } -} - -func TestActivityService_IsStarred_invalidID(t *testing.T) { - _, _, err := client.Activity.IsStarred("%", "%") - testURLParseError(t, err) -} - -func TestActivityService_Star(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/user/starred/o/r", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "PUT") - }) - - _, err := client.Activity.Star("o", "r") - if err != nil { - t.Errorf("Activity.Star returned error: %v", err) - } -} - -func TestActivityService_Star_invalidID(t *testing.T) { - _, err := client.Activity.Star("%", "%") - testURLParseError(t, err) -} - -func TestActivityService_Unstar(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/user/starred/o/r", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - }) - - _, err := client.Activity.Unstar("o", "r") - if err != nil { - t.Errorf("Activity.Unstar returned error: %v", err) - } -} - -func TestActivityService_Unstar_invalidID(t *testing.T) { - _, err := client.Activity.Unstar("%", "%") - testURLParseError(t, err) -} diff --git a/vendor/github.com/google/go-github/github/activity_watching_test.go b/vendor/github.com/google/go-github/github/activity_watching_test.go deleted file mode 100644 index 8046ee217..000000000 --- a/vendor/github.com/google/go-github/github/activity_watching_test.go +++ /dev/null @@ -1,177 +0,0 @@ -// Copyright 2014 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestActivityService_ListWatchers(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/subscribers", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "page": "2", - }) - - fmt.Fprint(w, `[{"id":1}]`) - }) - - watchers, _, err := client.Activity.ListWatchers("o", "r", &ListOptions{Page: 2}) - if err != nil { - t.Errorf("Activity.ListWatchers returned error: %v", err) - } - - want := []User{{ID: Int(1)}} - if !reflect.DeepEqual(watchers, want) { - t.Errorf("Activity.ListWatchers returned %+v, want %+v", watchers, want) - } -} - -func TestActivityService_ListWatched_authenticatedUser(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/user/subscriptions", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `[{"id":1}]`) - }) - - watched, _, err := client.Activity.ListWatched("") - if err != nil { - t.Errorf("Activity.ListWatched returned error: %v", err) - } - - want := []Repository{{ID: Int(1)}} - if !reflect.DeepEqual(watched, want) { - t.Errorf("Activity.ListWatched returned %+v, want %+v", watched, want) - } -} - -func TestActivityService_ListWatched_specifiedUser(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/users/u/subscriptions", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `[{"id":1}]`) - }) - - watched, _, err := client.Activity.ListWatched("u") - if err != nil { - t.Errorf("Activity.ListWatched returned error: %v", err) - } - - want := []Repository{{ID: Int(1)}} - if !reflect.DeepEqual(watched, want) { - t.Errorf("Activity.ListWatched returned %+v, want %+v", watched, want) - } -} - -func TestActivityService_GetRepositorySubscription_true(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/subscription", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"subscribed":true}`) - }) - - sub, _, err := client.Activity.GetRepositorySubscription("o", "r") - if err != nil { - t.Errorf("Activity.GetRepositorySubscription returned error: %v", err) - } - - want := &Subscription{Subscribed: Bool(true)} - if !reflect.DeepEqual(sub, want) { - t.Errorf("Activity.GetRepositorySubscription returned %+v, want %+v", sub, want) - } -} - -func TestActivityService_GetRepositorySubscription_false(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/subscription", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - w.WriteHeader(http.StatusNotFound) - }) - - sub, _, err := client.Activity.GetRepositorySubscription("o", "r") - if err != nil { - t.Errorf("Activity.GetRepositorySubscription returned error: %v", err) - } - - var want *Subscription - if !reflect.DeepEqual(sub, want) { - t.Errorf("Activity.GetRepositorySubscription returned %+v, want %+v", sub, want) - } -} - -func TestActivityService_GetRepositorySubscription_error(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/subscription", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - w.WriteHeader(http.StatusBadRequest) - }) - - _, _, err := client.Activity.GetRepositorySubscription("o", "r") - if err == nil { - t.Errorf("Expected HTTP 400 response") - } -} - -func TestActivityService_SetRepositorySubscription(t *testing.T) { - setup() - defer teardown() - - input := &Subscription{Subscribed: Bool(true)} - - mux.HandleFunc("/repos/o/r/subscription", func(w http.ResponseWriter, r *http.Request) { - v := new(Subscription) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "PUT") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"ignored":true}`) - }) - - sub, _, err := client.Activity.SetRepositorySubscription("o", "r", input) - if err != nil { - t.Errorf("Activity.SetRepositorySubscription returned error: %v", err) - } - - want := &Subscription{Ignored: Bool(true)} - if !reflect.DeepEqual(sub, want) { - t.Errorf("Activity.SetRepositorySubscription returned %+v, want %+v", sub, want) - } -} - -func TestActivityService_DeleteRepositorySubscription(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/subscription", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - w.WriteHeader(http.StatusNoContent) - }) - - _, err := client.Activity.DeleteRepositorySubscription("o", "r") - if err != nil { - t.Errorf("Activity.DeleteRepositorySubscription returned error: %v", err) - } -} diff --git a/vendor/github.com/google/go-github/github/doc.go b/vendor/github.com/google/go-github/github/doc.go index 8dee02633..b4ac8e640 100644 --- a/vendor/github.com/google/go-github/github/doc.go +++ b/vendor/github.com/google/go-github/github/doc.go @@ -28,24 +28,25 @@ Authentication The go-github library does not directly handle authentication. Instead, when creating a new client, pass an http.Client that can handle authentication for -you. The easiest and recommended way to do this is using the goauth2 library, -but you can always use any other library that provides an http.Client. If you -have an OAuth2 access token (for example, a personal API token), you can use it -with the goauth2 using: +you. The easiest and recommended way to do this is using the golang.org/x/oauth2 +library, but you can always use any other library that provides an http.Client. +If you have an OAuth2 access token (for example, a personal API token), you can +use it with the oauth2 library using: - import "code.google.com/p/goauth2/oauth" + import "golang.org/x/oauth2" - // simple OAuth transport if you already have an access token; - // see goauth2 library for full usage - t := &oauth.Transport{ - Token: &oauth.Token{AccessToken: "..."}, + func main() { + ts := oauth2.StaticTokenSource( + &oauth2.Token{AccessToken: "... your access token ..."}, + ) + tc := oauth2.NewClient(oauth2.NoContext, ts) + + client := github.NewClient(tc) + + // list all repositories for the authenticated user + repos, _, err := client.Repositories.List("", nil) } - client := github.NewClient(t.Client()) - - // list all repositories for the authenticated user - repos, _, err := client.Repositories.List("", nil) - Note that when using an authenticated Client, all calls made by the client will include the specified OAuth token. Therefore, authenticated clients should almost never be shared between different users. diff --git a/vendor/github.com/google/go-github/github/gists.go b/vendor/github.com/google/go-github/github/gists.go index 20c3536c1..a662d3548 100644 --- a/vendor/github.com/google/go-github/github/gists.go +++ b/vendor/github.com/google/go-github/github/gists.go @@ -157,6 +157,24 @@ func (s *GistsService) Get(id string) (*Gist, *Response, error) { return gist, resp, err } +// GetRevision gets a specific revision of a gist. +// +// GitHub API docs: https://developer.github.com/v3/gists/#get-a-specific-revision-of-a-gist +func (s *GistsService) GetRevision(id, sha string) (*Gist, *Response, error) { + u := fmt.Sprintf("gists/%v/%v", id, sha) + req, err := s.client.NewRequest("GET", u, nil) + if err != nil { + return nil, nil, err + } + gist := new(Gist) + resp, err := s.client.Do(req, gist) + if err != nil { + return nil, resp, err + } + + return gist, resp, err +} + // Create a gist for authenticated user. // // GitHub API docs: http://developer.github.com/v3/gists/#create-a-gist diff --git a/vendor/github.com/google/go-github/github/gists_comments_test.go b/vendor/github.com/google/go-github/github/gists_comments_test.go deleted file mode 100644 index b2bbf23f7..000000000 --- a/vendor/github.com/google/go-github/github/gists_comments_test.go +++ /dev/null @@ -1,155 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestGistsService_ListComments(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/gists/1/comments", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `[{"id": 1}]`) - }) - - opt := &ListOptions{Page: 2} - comments, _, err := client.Gists.ListComments("1", opt) - - if err != nil { - t.Errorf("Gists.Comments returned error: %v", err) - } - - want := []GistComment{{ID: Int(1)}} - if !reflect.DeepEqual(comments, want) { - t.Errorf("Gists.ListComments returned %+v, want %+v", comments, want) - } -} - -func TestGistsService_ListComments_invalidID(t *testing.T) { - _, _, err := client.Gists.ListComments("%", nil) - testURLParseError(t, err) -} - -func TestGistsService_GetComment(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/gists/1/comments/2", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"id": 1}`) - }) - - comment, _, err := client.Gists.GetComment("1", 2) - - if err != nil { - t.Errorf("Gists.GetComment returned error: %v", err) - } - - want := &GistComment{ID: Int(1)} - if !reflect.DeepEqual(comment, want) { - t.Errorf("Gists.GetComment returned %+v, want %+v", comment, want) - } -} - -func TestGistsService_GetComment_invalidID(t *testing.T) { - _, _, err := client.Gists.GetComment("%", 1) - testURLParseError(t, err) -} - -func TestGistsService_CreateComment(t *testing.T) { - setup() - defer teardown() - - input := &GistComment{ID: Int(1), Body: String("b")} - - mux.HandleFunc("/gists/1/comments", func(w http.ResponseWriter, r *http.Request) { - v := new(GistComment) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "POST") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"id":1}`) - }) - - comment, _, err := client.Gists.CreateComment("1", input) - if err != nil { - t.Errorf("Gists.CreateComment returned error: %v", err) - } - - want := &GistComment{ID: Int(1)} - if !reflect.DeepEqual(comment, want) { - t.Errorf("Gists.CreateComment returned %+v, want %+v", comment, want) - } -} - -func TestGistsService_CreateComment_invalidID(t *testing.T) { - _, _, err := client.Gists.CreateComment("%", nil) - testURLParseError(t, err) -} - -func TestGistsService_EditComment(t *testing.T) { - setup() - defer teardown() - - input := &GistComment{ID: Int(1), Body: String("b")} - - mux.HandleFunc("/gists/1/comments/2", func(w http.ResponseWriter, r *http.Request) { - v := new(GistComment) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "PATCH") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"id":1}`) - }) - - comment, _, err := client.Gists.EditComment("1", 2, input) - if err != nil { - t.Errorf("Gists.EditComment returned error: %v", err) - } - - want := &GistComment{ID: Int(1)} - if !reflect.DeepEqual(comment, want) { - t.Errorf("Gists.EditComment returned %+v, want %+v", comment, want) - } -} - -func TestGistsService_EditComment_invalidID(t *testing.T) { - _, _, err := client.Gists.EditComment("%", 1, nil) - testURLParseError(t, err) -} - -func TestGistsService_DeleteComment(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/gists/1/comments/2", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - }) - - _, err := client.Gists.DeleteComment("1", 2) - if err != nil { - t.Errorf("Gists.Delete returned error: %v", err) - } -} - -func TestGistsService_DeleteComment_invalidID(t *testing.T) { - _, err := client.Gists.DeleteComment("%", 1) - testURLParseError(t, err) -} diff --git a/vendor/github.com/google/go-github/github/gists_test.go b/vendor/github.com/google/go-github/github/gists_test.go deleted file mode 100644 index bd755da0d..000000000 --- a/vendor/github.com/google/go-github/github/gists_test.go +++ /dev/null @@ -1,385 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" - "time" -) - -func TestGistsService_List_specifiedUser(t *testing.T) { - setup() - defer teardown() - - since := "2013-01-01T00:00:00Z" - - mux.HandleFunc("/users/u/gists", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "since": since, - }) - fmt.Fprint(w, `[{"id": "1"}]`) - }) - - opt := &GistListOptions{Since: time.Date(2013, time.January, 1, 0, 0, 0, 0, time.UTC)} - gists, _, err := client.Gists.List("u", opt) - - if err != nil { - t.Errorf("Gists.List returned error: %v", err) - } - - want := []Gist{{ID: String("1")}} - if !reflect.DeepEqual(gists, want) { - t.Errorf("Gists.List returned %+v, want %+v", gists, want) - } -} - -func TestGistsService_List_authenticatedUser(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/gists", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `[{"id": "1"}]`) - }) - - gists, _, err := client.Gists.List("", nil) - if err != nil { - t.Errorf("Gists.List returned error: %v", err) - } - - want := []Gist{{ID: String("1")}} - if !reflect.DeepEqual(gists, want) { - t.Errorf("Gists.List returned %+v, want %+v", gists, want) - } -} - -func TestGistsService_List_invalidUser(t *testing.T) { - _, _, err := client.Gists.List("%", nil) - testURLParseError(t, err) -} - -func TestGistsService_ListAll(t *testing.T) { - setup() - defer teardown() - - since := "2013-01-01T00:00:00Z" - - mux.HandleFunc("/gists/public", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "since": since, - }) - fmt.Fprint(w, `[{"id": "1"}]`) - }) - - opt := &GistListOptions{Since: time.Date(2013, time.January, 1, 0, 0, 0, 0, time.UTC)} - gists, _, err := client.Gists.ListAll(opt) - - if err != nil { - t.Errorf("Gists.ListAll returned error: %v", err) - } - - want := []Gist{{ID: String("1")}} - if !reflect.DeepEqual(gists, want) { - t.Errorf("Gists.ListAll returned %+v, want %+v", gists, want) - } -} - -func TestGistsService_ListStarred(t *testing.T) { - setup() - defer teardown() - - since := "2013-01-01T00:00:00Z" - - mux.HandleFunc("/gists/starred", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "since": since, - }) - fmt.Fprint(w, `[{"id": "1"}]`) - }) - - opt := &GistListOptions{Since: time.Date(2013, time.January, 1, 0, 0, 0, 0, time.UTC)} - gists, _, err := client.Gists.ListStarred(opt) - - if err != nil { - t.Errorf("Gists.ListStarred returned error: %v", err) - } - - want := []Gist{{ID: String("1")}} - if !reflect.DeepEqual(gists, want) { - t.Errorf("Gists.ListStarred returned %+v, want %+v", gists, want) - } -} - -func TestGistsService_Get(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/gists/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"id": "1"}`) - }) - - gist, _, err := client.Gists.Get("1") - - if err != nil { - t.Errorf("Gists.Get returned error: %v", err) - } - - want := &Gist{ID: String("1")} - if !reflect.DeepEqual(gist, want) { - t.Errorf("Gists.Get returned %+v, want %+v", gist, want) - } -} - -func TestGistsService_Get_invalidID(t *testing.T) { - _, _, err := client.Gists.Get("%") - testURLParseError(t, err) -} - -func TestGistsService_Create(t *testing.T) { - setup() - defer teardown() - - input := &Gist{ - Description: String("Gist description"), - Public: Bool(false), - Files: map[GistFilename]GistFile{ - "test.txt": {Content: String("Gist file content")}, - }, - } - - mux.HandleFunc("/gists", func(w http.ResponseWriter, r *http.Request) { - v := new(Gist) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "POST") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, - ` - { - "id": "1", - "description": "Gist description", - "public": false, - "files": { - "test.txt": { - "filename": "test.txt" - } - } - }`) - }) - - gist, _, err := client.Gists.Create(input) - if err != nil { - t.Errorf("Gists.Create returned error: %v", err) - } - - want := &Gist{ - ID: String("1"), - Description: String("Gist description"), - Public: Bool(false), - Files: map[GistFilename]GistFile{ - "test.txt": {Filename: String("test.txt")}, - }, - } - if !reflect.DeepEqual(gist, want) { - t.Errorf("Gists.Create returned %+v, want %+v", gist, want) - } -} - -func TestGistsService_Edit(t *testing.T) { - setup() - defer teardown() - - input := &Gist{ - Description: String("New description"), - Files: map[GistFilename]GistFile{ - "new.txt": {Content: String("new file content")}, - }, - } - - mux.HandleFunc("/gists/1", func(w http.ResponseWriter, r *http.Request) { - v := new(Gist) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "PATCH") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, - ` - { - "id": "1", - "description": "new description", - "public": false, - "files": { - "test.txt": { - "filename": "test.txt" - }, - "new.txt": { - "filename": "new.txt" - } - } - }`) - }) - - gist, _, err := client.Gists.Edit("1", input) - if err != nil { - t.Errorf("Gists.Edit returned error: %v", err) - } - - want := &Gist{ - ID: String("1"), - Description: String("new description"), - Public: Bool(false), - Files: map[GistFilename]GistFile{ - "test.txt": {Filename: String("test.txt")}, - "new.txt": {Filename: String("new.txt")}, - }, - } - if !reflect.DeepEqual(gist, want) { - t.Errorf("Gists.Edit returned %+v, want %+v", gist, want) - } -} - -func TestGistsService_Edit_invalidID(t *testing.T) { - _, _, err := client.Gists.Edit("%", nil) - testURLParseError(t, err) -} - -func TestGistsService_Delete(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/gists/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - }) - - _, err := client.Gists.Delete("1") - if err != nil { - t.Errorf("Gists.Delete returned error: %v", err) - } -} - -func TestGistsService_Delete_invalidID(t *testing.T) { - _, err := client.Gists.Delete("%") - testURLParseError(t, err) -} - -func TestGistsService_Star(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/gists/1/star", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "PUT") - }) - - _, err := client.Gists.Star("1") - if err != nil { - t.Errorf("Gists.Star returned error: %v", err) - } -} - -func TestGistsService_Star_invalidID(t *testing.T) { - _, err := client.Gists.Star("%") - testURLParseError(t, err) -} - -func TestGistsService_Unstar(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/gists/1/star", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - }) - - _, err := client.Gists.Unstar("1") - if err != nil { - t.Errorf("Gists.Unstar returned error: %v", err) - } -} - -func TestGistsService_Unstar_invalidID(t *testing.T) { - _, err := client.Gists.Unstar("%") - testURLParseError(t, err) -} - -func TestGistsService_IsStarred_hasStar(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/gists/1/star", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - w.WriteHeader(http.StatusNoContent) - }) - - star, _, err := client.Gists.IsStarred("1") - if err != nil { - t.Errorf("Gists.Starred returned error: %v", err) - } - if want := true; star != want { - t.Errorf("Gists.Starred returned %+v, want %+v", star, want) - } -} - -func TestGistsService_IsStarred_noStar(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/gists/1/star", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - w.WriteHeader(http.StatusNotFound) - }) - - star, _, err := client.Gists.IsStarred("1") - if err != nil { - t.Errorf("Gists.Starred returned error: %v", err) - } - if want := false; star != want { - t.Errorf("Gists.Starred returned %+v, want %+v", star, want) - } -} - -func TestGistsService_IsStarred_invalidID(t *testing.T) { - _, _, err := client.Gists.IsStarred("%") - testURLParseError(t, err) -} - -func TestGistsService_Fork(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/gists/1/forks", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "POST") - fmt.Fprint(w, `{"id": "2"}`) - }) - - gist, _, err := client.Gists.Fork("1") - - if err != nil { - t.Errorf("Gists.Fork returned error: %v", err) - } - - want := &Gist{ID: String("2")} - if !reflect.DeepEqual(gist, want) { - t.Errorf("Gists.Fork returned %+v, want %+v", gist, want) - } -} - -func TestGistsService_Fork_invalidID(t *testing.T) { - _, _, err := client.Gists.Fork("%") - testURLParseError(t, err) -} diff --git a/vendor/github.com/google/go-github/github/git_blobs_test.go b/vendor/github.com/google/go-github/github/git_blobs_test.go deleted file mode 100644 index 994549f2c..000000000 --- a/vendor/github.com/google/go-github/github/git_blobs_test.go +++ /dev/null @@ -1,92 +0,0 @@ -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestGitService_GetBlob(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/git/blobs/s", func(w http.ResponseWriter, r *http.Request) { - if m := "GET"; m != r.Method { - t.Errorf("Request method = %v, want %v", r.Method, m) - } - fmt.Fprint(w, `{ - "sha": "s", - "content": "blob content" - }`) - }) - - blob, _, err := client.Git.GetBlob("o", "r", "s") - if err != nil { - t.Errorf("Git.GetBlob returned error: %v", err) - } - - want := Blob{ - SHA: String("s"), - Content: String("blob content"), - } - - if !reflect.DeepEqual(*blob, want) { - t.Errorf("Blob.Get returned %+v, want %+v", *blob, want) - } -} - -func TestGitService_GetBlob_invalidOwner(t *testing.T) { - _, _, err := client.Git.GetBlob("%", "%", "%") - testURLParseError(t, err) -} - -func TestGitService_CreateBlob(t *testing.T) { - setup() - defer teardown() - - input := &Blob{ - SHA: String("s"), - Content: String("blob content"), - Encoding: String("utf-8"), - Size: Int(12), - } - - mux.HandleFunc("/repos/o/r/git/blobs", func(w http.ResponseWriter, r *http.Request) { - v := new(Blob) - json.NewDecoder(r.Body).Decode(v) - - if m := "POST"; m != r.Method { - t.Errorf("Request method = %v, want %v", r.Method, m) - } - - want := input - if !reflect.DeepEqual(v, want) { - t.Errorf("Git.CreateBlob request body: %+v, want %+v", v, want) - } - - fmt.Fprint(w, `{ - "sha": "s", - "content": "blob content", - "encoding": "utf-8", - "size": 12 - }`) - }) - - blob, _, err := client.Git.CreateBlob("o", "r", input) - if err != nil { - t.Errorf("Git.CreateBlob returned error: %v", err) - } - - want := input - - if !reflect.DeepEqual(*blob, *want) { - t.Errorf("Git.CreateBlob returned %+v, want %+v", *blob, *want) - } -} - -func TestGitService_CreateBlob_invalidOwner(t *testing.T) { - _, _, err := client.Git.CreateBlob("%", "%", &Blob{}) - testURLParseError(t, err) -} diff --git a/vendor/github.com/google/go-github/github/git_commits_test.go b/vendor/github.com/google/go-github/github/git_commits_test.go deleted file mode 100644 index 538f52360..000000000 --- a/vendor/github.com/google/go-github/github/git_commits_test.go +++ /dev/null @@ -1,82 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestGitService_GetCommit(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/git/commits/s", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"sha":"s","message":"m","author":{"name":"n"}}`) - }) - - commit, _, err := client.Git.GetCommit("o", "r", "s") - if err != nil { - t.Errorf("Git.GetCommit returned error: %v", err) - } - - want := &Commit{SHA: String("s"), Message: String("m"), Author: &CommitAuthor{Name: String("n")}} - if !reflect.DeepEqual(commit, want) { - t.Errorf("Git.GetCommit returned %+v, want %+v", commit, want) - } -} - -func TestGitService_GetCommit_invalidOwner(t *testing.T) { - _, _, err := client.Git.GetCommit("%", "%", "%") - testURLParseError(t, err) -} - -func TestGitService_CreateCommit(t *testing.T) { - setup() - defer teardown() - - input := &Commit{ - Message: String("m"), - Tree: &Tree{SHA: String("t")}, - Parents: []Commit{{SHA: String("p")}}, - } - - mux.HandleFunc("/repos/o/r/git/commits", func(w http.ResponseWriter, r *http.Request) { - v := new(createCommit) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "POST") - - want := &createCommit{ - Message: input.Message, - Tree: String("t"), - Parents: []string{"p"}, - } - if !reflect.DeepEqual(v, want) { - t.Errorf("Request body = %+v, want %+v", v, want) - } - fmt.Fprint(w, `{"sha":"s"}`) - }) - - commit, _, err := client.Git.CreateCommit("o", "r", input) - if err != nil { - t.Errorf("Git.CreateCommit returned error: %v", err) - } - - want := &Commit{SHA: String("s")} - if !reflect.DeepEqual(commit, want) { - t.Errorf("Git.CreateCommit returned %+v, want %+v", commit, want) - } -} - -func TestGitService_CreateCommit_invalidOwner(t *testing.T) { - _, _, err := client.Git.CreateCommit("%", "%", nil) - testURLParseError(t, err) -} diff --git a/vendor/github.com/google/go-github/github/git_refs_test.go b/vendor/github.com/google/go-github/github/git_refs_test.go deleted file mode 100644 index e66bf54af..000000000 --- a/vendor/github.com/google/go-github/github/git_refs_test.go +++ /dev/null @@ -1,280 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestGitService_GetRef(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/git/refs/heads/b", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, ` - { - "ref": "refs/heads/b", - "url": "https://api.github.com/repos/o/r/git/refs/heads/b", - "object": { - "type": "commit", - "sha": "aa218f56b14c9653891f9e74264a383fa43fefbd", - "url": "https://api.github.com/repos/o/r/git/commits/aa218f56b14c9653891f9e74264a383fa43fefbd" - } - }`) - }) - - ref, _, err := client.Git.GetRef("o", "r", "refs/heads/b") - if err != nil { - t.Errorf("Git.GetRef returned error: %v", err) - } - - want := &Reference{ - Ref: String("refs/heads/b"), - URL: String("https://api.github.com/repos/o/r/git/refs/heads/b"), - Object: &GitObject{ - Type: String("commit"), - SHA: String("aa218f56b14c9653891f9e74264a383fa43fefbd"), - URL: String("https://api.github.com/repos/o/r/git/commits/aa218f56b14c9653891f9e74264a383fa43fefbd"), - }, - } - if !reflect.DeepEqual(ref, want) { - t.Errorf("Git.GetRef returned %+v, want %+v", ref, want) - } - - // without 'refs/' prefix - if _, _, err := client.Git.GetRef("o", "r", "heads/b"); err != nil { - t.Errorf("Git.GetRef returned error: %v", err) - } -} - -func TestGitService_ListRefs(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/git/refs", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, ` - [ - { - "ref": "refs/heads/branchA", - "url": "https://api.github.com/repos/o/r/git/refs/heads/branchA", - "object": { - "type": "commit", - "sha": "aa218f56b14c9653891f9e74264a383fa43fefbd", - "url": "https://api.github.com/repos/o/r/git/commits/aa218f56b14c9653891f9e74264a383fa43fefbd" - } - }, - { - "ref": "refs/heads/branchB", - "url": "https://api.github.com/repos/o/r/git/refs/heads/branchB", - "object": { - "type": "commit", - "sha": "aa218f56b14c9653891f9e74264a383fa43fefbd", - "url": "https://api.github.com/repos/o/r/git/commits/aa218f56b14c9653891f9e74264a383fa43fefbd" - } - } - ]`) - }) - - refs, _, err := client.Git.ListRefs("o", "r", nil) - if err != nil { - t.Errorf("Git.ListRefs returned error: %v", err) - } - - want := []Reference{ - { - Ref: String("refs/heads/branchA"), - URL: String("https://api.github.com/repos/o/r/git/refs/heads/branchA"), - Object: &GitObject{ - Type: String("commit"), - SHA: String("aa218f56b14c9653891f9e74264a383fa43fefbd"), - URL: String("https://api.github.com/repos/o/r/git/commits/aa218f56b14c9653891f9e74264a383fa43fefbd"), - }, - }, - { - Ref: String("refs/heads/branchB"), - URL: String("https://api.github.com/repos/o/r/git/refs/heads/branchB"), - Object: &GitObject{ - Type: String("commit"), - SHA: String("aa218f56b14c9653891f9e74264a383fa43fefbd"), - URL: String("https://api.github.com/repos/o/r/git/commits/aa218f56b14c9653891f9e74264a383fa43fefbd"), - }, - }, - } - if !reflect.DeepEqual(refs, want) { - t.Errorf("Git.ListRefs returned %+v, want %+v", refs, want) - } -} - -func TestGitService_ListRefs_options(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/git/refs/t", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `[{"ref": "r"}]`) - }) - - opt := &ReferenceListOptions{Type: "t", ListOptions: ListOptions{Page: 2}} - refs, _, err := client.Git.ListRefs("o", "r", opt) - if err != nil { - t.Errorf("Git.ListRefs returned error: %v", err) - } - - want := []Reference{{Ref: String("r")}} - if !reflect.DeepEqual(refs, want) { - t.Errorf("Git.ListRefs returned %+v, want %+v", refs, want) - } -} - -func TestGitService_CreateRef(t *testing.T) { - setup() - defer teardown() - - args := &createRefRequest{ - Ref: String("refs/heads/b"), - SHA: String("aa218f56b14c9653891f9e74264a383fa43fefbd"), - } - - mux.HandleFunc("/repos/o/r/git/refs", func(w http.ResponseWriter, r *http.Request) { - v := new(createRefRequest) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "POST") - if !reflect.DeepEqual(v, args) { - t.Errorf("Request body = %+v, want %+v", v, args) - } - fmt.Fprint(w, ` - { - "ref": "refs/heads/b", - "url": "https://api.github.com/repos/o/r/git/refs/heads/b", - "object": { - "type": "commit", - "sha": "aa218f56b14c9653891f9e74264a383fa43fefbd", - "url": "https://api.github.com/repos/o/r/git/commits/aa218f56b14c9653891f9e74264a383fa43fefbd" - } - }`) - }) - - ref, _, err := client.Git.CreateRef("o", "r", &Reference{ - Ref: String("refs/heads/b"), - Object: &GitObject{ - SHA: String("aa218f56b14c9653891f9e74264a383fa43fefbd"), - }, - }) - if err != nil { - t.Errorf("Git.CreateRef returned error: %v", err) - } - - want := &Reference{ - Ref: String("refs/heads/b"), - URL: String("https://api.github.com/repos/o/r/git/refs/heads/b"), - Object: &GitObject{ - Type: String("commit"), - SHA: String("aa218f56b14c9653891f9e74264a383fa43fefbd"), - URL: String("https://api.github.com/repos/o/r/git/commits/aa218f56b14c9653891f9e74264a383fa43fefbd"), - }, - } - if !reflect.DeepEqual(ref, want) { - t.Errorf("Git.CreateRef returned %+v, want %+v", ref, want) - } - - // without 'refs/' prefix - _, _, err = client.Git.CreateRef("o", "r", &Reference{ - Ref: String("heads/b"), - Object: &GitObject{ - SHA: String("aa218f56b14c9653891f9e74264a383fa43fefbd"), - }, - }) - if err != nil { - t.Errorf("Git.CreateRef returned error: %v", err) - } -} - -func TestGitService_UpdateRef(t *testing.T) { - setup() - defer teardown() - - args := &updateRefRequest{ - SHA: String("aa218f56b14c9653891f9e74264a383fa43fefbd"), - Force: Bool(true), - } - - mux.HandleFunc("/repos/o/r/git/refs/heads/b", func(w http.ResponseWriter, r *http.Request) { - v := new(updateRefRequest) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "PATCH") - if !reflect.DeepEqual(v, args) { - t.Errorf("Request body = %+v, want %+v", v, args) - } - fmt.Fprint(w, ` - { - "ref": "refs/heads/b", - "url": "https://api.github.com/repos/o/r/git/refs/heads/b", - "object": { - "type": "commit", - "sha": "aa218f56b14c9653891f9e74264a383fa43fefbd", - "url": "https://api.github.com/repos/o/r/git/commits/aa218f56b14c9653891f9e74264a383fa43fefbd" - } - }`) - }) - - ref, _, err := client.Git.UpdateRef("o", "r", &Reference{ - Ref: String("refs/heads/b"), - Object: &GitObject{SHA: String("aa218f56b14c9653891f9e74264a383fa43fefbd")}, - }, true) - if err != nil { - t.Errorf("Git.UpdateRef returned error: %v", err) - } - - want := &Reference{ - Ref: String("refs/heads/b"), - URL: String("https://api.github.com/repos/o/r/git/refs/heads/b"), - Object: &GitObject{ - Type: String("commit"), - SHA: String("aa218f56b14c9653891f9e74264a383fa43fefbd"), - URL: String("https://api.github.com/repos/o/r/git/commits/aa218f56b14c9653891f9e74264a383fa43fefbd"), - }, - } - if !reflect.DeepEqual(ref, want) { - t.Errorf("Git.UpdateRef returned %+v, want %+v", ref, want) - } - - // without 'refs/' prefix - _, _, err = client.Git.UpdateRef("o", "r", &Reference{ - Ref: String("heads/b"), - Object: &GitObject{SHA: String("aa218f56b14c9653891f9e74264a383fa43fefbd")}, - }, true) - if err != nil { - t.Errorf("Git.UpdateRef returned error: %v", err) - } -} - -func TestGitService_DeleteRef(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/git/refs/heads/b", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - }) - - _, err := client.Git.DeleteRef("o", "r", "refs/heads/b") - if err != nil { - t.Errorf("Git.DeleteRef returned error: %v", err) - } - - // without 'refs/' prefix - if _, err := client.Git.DeleteRef("o", "r", "heads/b"); err != nil { - t.Errorf("Git.DeleteRef returned error: %v", err) - } -} diff --git a/vendor/github.com/google/go-github/github/git_tags_test.go b/vendor/github.com/google/go-github/github/git_tags_test.go deleted file mode 100644 index fb41bf38e..000000000 --- a/vendor/github.com/google/go-github/github/git_tags_test.go +++ /dev/null @@ -1,68 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestGitService_GetTag(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/git/tags/s", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - - fmt.Fprint(w, `{"tag": "t"}`) - }) - - tag, _, err := client.Git.GetTag("o", "r", "s") - - if err != nil { - t.Errorf("Git.GetTag returned error: %v", err) - } - - want := &Tag{Tag: String("t")} - if !reflect.DeepEqual(tag, want) { - t.Errorf("Git.GetTag returned %+v, want %+v", tag, want) - } -} - -func TestGitService_CreateTag(t *testing.T) { - setup() - defer teardown() - - input := &createTagRequest{Tag: String("t"), Object: String("s")} - - mux.HandleFunc("/repos/o/r/git/tags", func(w http.ResponseWriter, r *http.Request) { - v := new(createTagRequest) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "POST") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"tag": "t"}`) - }) - - tag, _, err := client.Git.CreateTag("o", "r", &Tag{ - Tag: input.Tag, - Object: &GitObject{SHA: input.Object}, - }) - if err != nil { - t.Errorf("Git.CreateTag returned error: %v", err) - } - - want := &Tag{Tag: String("t")} - if !reflect.DeepEqual(tag, want) { - t.Errorf("Git.GetTag returned %+v, want %+v", tag, want) - } -} diff --git a/vendor/github.com/google/go-github/github/git_trees_test.go b/vendor/github.com/google/go-github/github/git_trees_test.go deleted file mode 100644 index 99ec4f34c..000000000 --- a/vendor/github.com/google/go-github/github/git_trees_test.go +++ /dev/null @@ -1,189 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestGitService_GetTree(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/git/trees/s", func(w http.ResponseWriter, r *http.Request) { - if m := "GET"; m != r.Method { - t.Errorf("Request method = %v, want %v", r.Method, m) - } - fmt.Fprint(w, `{ - "sha": "s", - "tree": [ { "type": "blob" } ] - }`) - }) - - tree, _, err := client.Git.GetTree("o", "r", "s", true) - if err != nil { - t.Errorf("Git.GetTree returned error: %v", err) - } - - want := Tree{ - SHA: String("s"), - Entries: []TreeEntry{ - { - Type: String("blob"), - }, - }, - } - if !reflect.DeepEqual(*tree, want) { - t.Errorf("Tree.Get returned %+v, want %+v", *tree, want) - } -} - -func TestGitService_GetTree_invalidOwner(t *testing.T) { - _, _, err := client.Git.GetTree("%", "%", "%", false) - testURLParseError(t, err) -} - -func TestGitService_CreateTree(t *testing.T) { - setup() - defer teardown() - - input := []TreeEntry{ - { - Path: String("file.rb"), - Mode: String("100644"), - Type: String("blob"), - SHA: String("7c258a9869f33c1e1e1f74fbb32f07c86cb5a75b"), - }, - } - - mux.HandleFunc("/repos/o/r/git/trees", func(w http.ResponseWriter, r *http.Request) { - v := new(createTree) - json.NewDecoder(r.Body).Decode(v) - - if m := "POST"; m != r.Method { - t.Errorf("Request method = %v, want %v", r.Method, m) - } - - want := &createTree{ - BaseTree: "b", - Entries: input, - } - if !reflect.DeepEqual(v, want) { - t.Errorf("Git.CreateTree request body: %+v, want %+v", v, want) - } - - fmt.Fprint(w, `{ - "sha": "cd8274d15fa3ae2ab983129fb037999f264ba9a7", - "tree": [ - { - "path": "file.rb", - "mode": "100644", - "type": "blob", - "size": 132, - "sha": "7c258a9869f33c1e1e1f74fbb32f07c86cb5a75b" - } - ] - }`) - }) - - tree, _, err := client.Git.CreateTree("o", "r", "b", input) - if err != nil { - t.Errorf("Git.CreateTree returned error: %v", err) - } - - want := Tree{ - String("cd8274d15fa3ae2ab983129fb037999f264ba9a7"), - []TreeEntry{ - { - Path: String("file.rb"), - Mode: String("100644"), - Type: String("blob"), - Size: Int(132), - SHA: String("7c258a9869f33c1e1e1f74fbb32f07c86cb5a75b"), - }, - }, - } - - if !reflect.DeepEqual(*tree, want) { - t.Errorf("Git.CreateTree returned %+v, want %+v", *tree, want) - } -} - -func TestGitService_CreateTree_Content(t *testing.T) { - setup() - defer teardown() - - input := []TreeEntry{ - { - Path: String("content.md"), - Mode: String("100644"), - Content: String("file content"), - }, - } - - mux.HandleFunc("/repos/o/r/git/trees", func(w http.ResponseWriter, r *http.Request) { - v := new(createTree) - json.NewDecoder(r.Body).Decode(v) - - if m := "POST"; m != r.Method { - t.Errorf("Request method = %v, want %v", r.Method, m) - } - - want := &createTree{ - BaseTree: "b", - Entries: input, - } - if !reflect.DeepEqual(v, want) { - t.Errorf("Git.CreateTree request body: %+v, want %+v", v, want) - } - - fmt.Fprint(w, `{ - "sha": "5c6780ad2c68743383b740fd1dab6f6a33202b11", - "url": "https://api.github.com/repos/o/r/git/trees/5c6780ad2c68743383b740fd1dab6f6a33202b11", - "tree": [ - { - "mode": "100644", - "type": "blob", - "sha": "aad8feacf6f8063150476a7b2bd9770f2794c08b", - "path": "content.md", - "size": 12, - "url": "https://api.github.com/repos/o/r/git/blobs/aad8feacf6f8063150476a7b2bd9770f2794c08b" - } - ] - }`) - }) - - tree, _, err := client.Git.CreateTree("o", "r", "b", input) - if err != nil { - t.Errorf("Git.CreateTree returned error: %v", err) - } - - want := Tree{ - String("5c6780ad2c68743383b740fd1dab6f6a33202b11"), - []TreeEntry{ - { - Path: String("content.md"), - Mode: String("100644"), - Type: String("blob"), - Size: Int(12), - SHA: String("aad8feacf6f8063150476a7b2bd9770f2794c08b"), - }, - }, - } - - if !reflect.DeepEqual(*tree, want) { - t.Errorf("Git.CreateTree returned %+v, want %+v", *tree, want) - } -} - -func TestGitService_CreateTree_invalidOwner(t *testing.T) { - _, _, err := client.Git.CreateTree("%", "%", "", nil) - testURLParseError(t, err) -} diff --git a/vendor/github.com/google/go-github/github/github.go b/vendor/github.com/google/go-github/github/github.go index fced10769..30b839059 100644 --- a/vendor/github.com/google/go-github/github/github.go +++ b/vendor/github.com/google/go-github/github/github.go @@ -37,11 +37,15 @@ const ( // Media Type values to access preview APIs - // https://developer.github.com/changes/2014-08-05-team-memberships-api/ - mediaTypeMembershipPreview = "application/vnd.github.the-wasp-preview+json" + // https://developer.github.com/changes/2015-03-09-licenses-api/ + mediaTypeLicensesPreview = "application/vnd.github.drax-preview+json" - // https://developer.github.com/changes/2014-01-09-preview-the-new-deployments-api/ - mediaTypeDeploymentPreview = "application/vnd.github.cannonball-preview+json" + // https://developer.github.com/changes/2014-12-09-new-attributes-for-stars-api/ + mediaTypeStarringPreview = "application/vnd.github.v3.star+json" + + // https://developer.github.com/changes/2015-06-24-api-enhancements-for-working-with-organization-permissions/ + mediaTypeOrgPermissionPreview = "application/vnd.github.ironman-preview+json" + mediaTypeOrgPermissionRepoPreview = "application/vnd.github.ironman-preview.repository+json" ) // A Client manages communication with the GitHub API. @@ -62,7 +66,7 @@ type Client struct { // Rate specifies the current rate limit for the client as determined by the // most recent API call. If the client is used in a multi-user application, - // this rate may not always be up-to-date. Call RateLimit() to check the + // this rate may not always be up-to-date. Call RateLimits() to check the // current rate. Rate Rate @@ -77,6 +81,7 @@ type Client struct { Repositories *RepositoriesService Search *SearchService Users *UsersService + Licenses *LicensesService } // ListOptions specifies the optional parameters to various List methods that @@ -119,7 +124,7 @@ func addOptions(s string, opt interface{}) (string, error) { // NewClient returns a new GitHub API client. If a nil httpClient is // provided, http.DefaultClient will be used. To use API methods which require // authentication, provide an http.Client that will perform the authentication -// for you (such as that provided by the goauth2 library). +// for you (such as that provided by the golang.org/x/oauth2 library). func NewClient(httpClient *http.Client) *Client { if httpClient == nil { httpClient = http.DefaultClient @@ -138,6 +143,7 @@ func NewClient(httpClient *http.Client) *Client { c.Repositories = &RepositoriesService{client: c} c.Search = &SearchService{client: c} c.Users = &UsersService{client: c} + c.Licenses = &LicensesService{client: c} return c } @@ -219,7 +225,7 @@ type Response struct { Rate } -// newResponse creats a new Response for the provided http.Response. +// newResponse creates a new Response for the provided http.Response. func newResponse(r *http.Response) *Response { response := &Response{Response: r} response.populatePageValues() @@ -333,10 +339,24 @@ type ErrorResponse struct { func (r *ErrorResponse) Error() string { return fmt.Sprintf("%v %v: %d %v %+v", - r.Response.Request.Method, r.Response.Request.URL, + r.Response.Request.Method, sanitizeURL(r.Response.Request.URL), r.Response.StatusCode, r.Message, r.Errors) } +// sanitizeURL redacts the client_id and client_secret tokens from the URL which +// may be exposed to the user, specifically in the ErrorResponse error message. +func sanitizeURL(uri *url.URL) *url.URL { + if uri == nil { + return nil + } + params := uri.Query() + if len(params.Get("client_secret")) > 0 { + params.Set("client_secret", "REDACTED") + uri.RawQuery = params.Encode() + } + return uri +} + /* An Error reports more details on an individual error in an ErrorResponse. These are the possible validation error codes: diff --git a/vendor/github.com/google/go-github/github/github_test.go b/vendor/github.com/google/go-github/github/github_test.go deleted file mode 100644 index 0fb2c18a1..000000000 --- a/vendor/github.com/google/go-github/github/github_test.go +++ /dev/null @@ -1,660 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "bytes" - "encoding/json" - "fmt" - "io/ioutil" - "net/http" - "net/http/httptest" - "net/url" - "os" - "path" - "reflect" - "strings" - "testing" - "time" -) - -var ( - // mux is the HTTP request multiplexer used with the test server. - mux *http.ServeMux - - // client is the GitHub client being tested. - client *Client - - // server is a test HTTP server used to provide mock API responses. - server *httptest.Server -) - -// setup sets up a test HTTP server along with a github.Client that is -// configured to talk to that test server. Tests should register handlers on -// mux which provide mock responses for the API method being tested. -func setup() { - // test server - mux = http.NewServeMux() - server = httptest.NewServer(mux) - - // github client configured to use test server - client = NewClient(nil) - url, _ := url.Parse(server.URL) - client.BaseURL = url - client.UploadURL = url -} - -// teardown closes the test HTTP server. -func teardown() { - server.Close() -} - -// openTestFile creates a new file with the given name and content for testing. -// In order to ensure the exact file name, this function will create a new temp -// directory, and create the file in that directory. It is the caller's -// responsibility to remove the directy and its contents when no longer needed. -func openTestFile(name, content string) (file *os.File, dir string, err error) { - dir, err = ioutil.TempDir("", "go-github") - if err != nil { - return nil, dir, err - } - - file, err = os.OpenFile(path.Join(dir, name), os.O_RDWR|os.O_CREATE|os.O_EXCL, 0600) - if err != nil { - return nil, dir, err - } - - fmt.Fprint(file, content) - - // close and re-open the file to keep file.Stat() happy - file.Close() - file, err = os.Open(file.Name()) - if err != nil { - return nil, dir, err - } - - return file, dir, err -} - -func testMethod(t *testing.T, r *http.Request, want string) { - if got := r.Method; got != want { - t.Errorf("Request method: %v, want %v", got, want) - } -} - -type values map[string]string - -func testFormValues(t *testing.T, r *http.Request, values values) { - want := url.Values{} - for k, v := range values { - want.Add(k, v) - } - - r.ParseForm() - if got := r.Form; !reflect.DeepEqual(got, want) { - t.Errorf("Request parameters: %v, want %v", got, want) - } -} - -func testHeader(t *testing.T, r *http.Request, header string, want string) { - if got := r.Header.Get(header); got != want { - t.Errorf("Header.Get(%q) returned %s, want %s", header, got, want) - } -} - -func testURLParseError(t *testing.T, err error) { - if err == nil { - t.Errorf("Expected error to be returned") - } - if err, ok := err.(*url.Error); !ok || err.Op != "parse" { - t.Errorf("Expected URL parse error, got %+v", err) - } -} - -func testBody(t *testing.T, r *http.Request, want string) { - b, err := ioutil.ReadAll(r.Body) - if err != nil { - t.Errorf("Error reading request body: %v", err) - } - if got := string(b); got != want { - t.Errorf("request Body is %s, want %s", got, want) - } -} - -// Helper function to test that a value is marshalled to JSON as expected. -func testJSONMarshal(t *testing.T, v interface{}, want string) { - j, err := json.Marshal(v) - if err != nil { - t.Errorf("Unable to marshal JSON for %v", v) - } - - w := new(bytes.Buffer) - err = json.Compact(w, []byte(want)) - if err != nil { - t.Errorf("String is not valid json: %s", want) - } - - if w.String() != string(j) { - t.Errorf("json.Marshal(%q) returned %s, want %s", v, j, w) - } - - // now go the other direction and make sure things unmarshal as expected - u := reflect.ValueOf(v).Interface() - if err := json.Unmarshal([]byte(want), u); err != nil { - t.Errorf("Unable to unmarshal JSON for %v", want) - } - - if !reflect.DeepEqual(v, u) { - t.Errorf("json.Unmarshal(%q) returned %s, want %s", want, u, v) - } -} - -func TestNewClient(t *testing.T) { - c := NewClient(nil) - - if got, want := c.BaseURL.String(), defaultBaseURL; got != want { - t.Errorf("NewClient BaseURL is %v, want %v", got, want) - } - if got, want := c.UserAgent, userAgent; got != want { - t.Errorf("NewClient UserAgent is %v, want %v", got, want) - } -} - -func TestNewRequest(t *testing.T) { - c := NewClient(nil) - - inURL, outURL := "/foo", defaultBaseURL+"foo" - inBody, outBody := &User{Login: String("l")}, `{"login":"l"}`+"\n" - req, _ := c.NewRequest("GET", inURL, inBody) - - // test that relative URL was expanded - if got, want := req.URL.String(), outURL; got != want { - t.Errorf("NewRequest(%q) URL is %v, want %v", inURL, got, want) - } - - // test that body was JSON encoded - body, _ := ioutil.ReadAll(req.Body) - if got, want := string(body), outBody; got != want { - t.Errorf("NewRequest(%q) Body is %v, want %v", inBody, got, want) - } - - // test that default user-agent is attached to the request - if got, want := req.Header.Get("User-Agent"), c.UserAgent; got != want { - t.Errorf("NewRequest() User-Agent is %v, want %v", got, want) - } -} - -func TestNewRequest_invalidJSON(t *testing.T) { - c := NewClient(nil) - - type T struct { - A map[int]interface{} - } - _, err := c.NewRequest("GET", "/", &T{}) - - if err == nil { - t.Error("Expected error to be returned.") - } - if err, ok := err.(*json.UnsupportedTypeError); !ok { - t.Errorf("Expected a JSON error; got %#v.", err) - } -} - -func TestNewRequest_badURL(t *testing.T) { - c := NewClient(nil) - _, err := c.NewRequest("GET", ":", nil) - testURLParseError(t, err) -} - -// ensure that no User-Agent header is set if the client's UserAgent is empty. -// This caused a problem with Google's internal http client. -func TestNewRequest_emptyUserAgent(t *testing.T) { - c := NewClient(nil) - c.UserAgent = "" - req, err := c.NewRequest("GET", "/", nil) - if err != nil { - t.Fatalf("NewRequest returned unexpected error: %v", err) - } - if _, ok := req.Header["User-Agent"]; ok { - t.Fatal("constructed request contains unexpected User-Agent header") - } -} - -// If a nil body is passed to github.NewRequest, make sure that nil is also -// passed to http.NewRequest. In most cases, passing an io.Reader that returns -// no content is fine, since there is no difference between an HTTP request -// body that is an empty string versus one that is not set at all. However in -// certain cases, intermediate systems may treat these differently resulting in -// subtle errors. -func TestNewRequest_emptyBody(t *testing.T) { - c := NewClient(nil) - req, err := c.NewRequest("GET", "/", nil) - if err != nil { - t.Fatalf("NewRequest returned unexpected error: %v", err) - } - if req.Body != nil { - t.Fatalf("constructed request contains a non-nil Body") - } -} - -func TestResponse_populatePageValues(t *testing.T) { - r := http.Response{ - Header: http.Header{ - "Link": {`; rel="first",` + - ` ; rel="prev",` + - ` ; rel="next",` + - ` ; rel="last"`, - }, - }, - } - - response := newResponse(&r) - if got, want := response.FirstPage, 1; got != want { - t.Errorf("response.FirstPage: %v, want %v", got, want) - } - if got, want := response.PrevPage, 2; want != got { - t.Errorf("response.PrevPage: %v, want %v", got, want) - } - if got, want := response.NextPage, 4; want != got { - t.Errorf("response.NextPage: %v, want %v", got, want) - } - if got, want := response.LastPage, 5; want != got { - t.Errorf("response.LastPage: %v, want %v", got, want) - } -} - -func TestResponse_populatePageValues_invalid(t *testing.T) { - r := http.Response{ - Header: http.Header{ - "Link": {`,` + - `; rel="first",` + - `https://api.github.com/?page=2; rel="prev",` + - `; rel="next",` + - `; rel="last"`, - }, - }, - } - - response := newResponse(&r) - if got, want := response.FirstPage, 0; got != want { - t.Errorf("response.FirstPage: %v, want %v", got, want) - } - if got, want := response.PrevPage, 0; got != want { - t.Errorf("response.PrevPage: %v, want %v", got, want) - } - if got, want := response.NextPage, 0; got != want { - t.Errorf("response.NextPage: %v, want %v", got, want) - } - if got, want := response.LastPage, 0; got != want { - t.Errorf("response.LastPage: %v, want %v", got, want) - } - - // more invalid URLs - r = http.Response{ - Header: http.Header{ - "Link": {`; rel="first"`}, - }, - } - - response = newResponse(&r) - if got, want := response.FirstPage, 0; got != want { - t.Errorf("response.FirstPage: %v, want %v", got, want) - } -} - -func TestDo(t *testing.T) { - setup() - defer teardown() - - type foo struct { - A string - } - - mux.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) { - if m := "GET"; m != r.Method { - t.Errorf("Request method = %v, want %v", r.Method, m) - } - fmt.Fprint(w, `{"A":"a"}`) - }) - - req, _ := client.NewRequest("GET", "/", nil) - body := new(foo) - client.Do(req, body) - - want := &foo{"a"} - if !reflect.DeepEqual(body, want) { - t.Errorf("Response body = %v, want %v", body, want) - } -} - -func TestDo_httpError(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) { - http.Error(w, "Bad Request", 400) - }) - - req, _ := client.NewRequest("GET", "/", nil) - _, err := client.Do(req, nil) - - if err == nil { - t.Error("Expected HTTP 400 error.") - } -} - -// Test handling of an error caused by the internal http client's Do() -// function. A redirect loop is pretty unlikely to occur within the GitHub -// API, but does allow us to exercise the right code path. -func TestDo_redirectLoop(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) { - http.Redirect(w, r, "/", http.StatusFound) - }) - - req, _ := client.NewRequest("GET", "/", nil) - _, err := client.Do(req, nil) - - if err == nil { - t.Error("Expected error to be returned.") - } - if err, ok := err.(*url.Error); !ok { - t.Errorf("Expected a URL error; got %#v.", err) - } -} - -func TestDo_rateLimit(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) { - w.Header().Add(headerRateLimit, "60") - w.Header().Add(headerRateRemaining, "59") - w.Header().Add(headerRateReset, "1372700873") - }) - - if got, want := client.Rate.Limit, 0; got != want { - t.Errorf("Client rate limit = %v, want %v", got, want) - } - if got, want := client.Rate.Limit, 0; got != want { - t.Errorf("Client rate remaining = %v, got %v", got, want) - } - if !client.Rate.Reset.IsZero() { - t.Errorf("Client rate reset not initialized to zero value") - } - - req, _ := client.NewRequest("GET", "/", nil) - client.Do(req, nil) - - if got, want := client.Rate.Limit, 60; got != want { - t.Errorf("Client rate limit = %v, want %v", got, want) - } - if got, want := client.Rate.Remaining, 59; got != want { - t.Errorf("Client rate remaining = %v, want %v", got, want) - } - reset := time.Date(2013, 7, 1, 17, 47, 53, 0, time.UTC) - if client.Rate.Reset.UTC() != reset { - t.Errorf("Client rate reset = %v, want %v", client.Rate.Reset, reset) - } -} - -// ensure rate limit is still parsed, even for error responses -func TestDo_rateLimit_errorResponse(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) { - w.Header().Add(headerRateLimit, "60") - w.Header().Add(headerRateRemaining, "59") - w.Header().Add(headerRateReset, "1372700873") - http.Error(w, "Bad Request", 400) - }) - - req, _ := client.NewRequest("GET", "/", nil) - client.Do(req, nil) - - if got, want := client.Rate.Limit, 60; got != want { - t.Errorf("Client rate limit = %v, want %v", got, want) - } - if got, want := client.Rate.Remaining, 59; got != want { - t.Errorf("Client rate remaining = %v, want %v", got, want) - } - reset := time.Date(2013, 7, 1, 17, 47, 53, 0, time.UTC) - if client.Rate.Reset.UTC() != reset { - t.Errorf("Client rate reset = %v, want %v", client.Rate.Reset, reset) - } -} - -func TestCheckResponse(t *testing.T) { - res := &http.Response{ - Request: &http.Request{}, - StatusCode: http.StatusBadRequest, - Body: ioutil.NopCloser(strings.NewReader(`{"message":"m", - "errors": [{"resource": "r", "field": "f", "code": "c"}]}`)), - } - err := CheckResponse(res).(*ErrorResponse) - - if err == nil { - t.Errorf("Expected error response.") - } - - want := &ErrorResponse{ - Response: res, - Message: "m", - Errors: []Error{{Resource: "r", Field: "f", Code: "c"}}, - } - if !reflect.DeepEqual(err, want) { - t.Errorf("Error = %#v, want %#v", err, want) - } -} - -// ensure that we properly handle API errors that do not contain a response body -func TestCheckResponse_noBody(t *testing.T) { - res := &http.Response{ - Request: &http.Request{}, - StatusCode: http.StatusBadRequest, - Body: ioutil.NopCloser(strings.NewReader("")), - } - err := CheckResponse(res).(*ErrorResponse) - - if err == nil { - t.Errorf("Expected error response.") - } - - want := &ErrorResponse{ - Response: res, - } - if !reflect.DeepEqual(err, want) { - t.Errorf("Error = %#v, want %#v", err, want) - } -} - -func TestParseBooleanResponse_true(t *testing.T) { - result, err := parseBoolResponse(nil) - - if err != nil { - t.Errorf("parseBoolResponse returned error: %+v", err) - } - - if want := true; result != want { - t.Errorf("parseBoolResponse returned %+v, want: %+v", result, want) - } -} - -func TestParseBooleanResponse_false(t *testing.T) { - v := &ErrorResponse{Response: &http.Response{StatusCode: http.StatusNotFound}} - result, err := parseBoolResponse(v) - - if err != nil { - t.Errorf("parseBoolResponse returned error: %+v", err) - } - - if want := false; result != want { - t.Errorf("parseBoolResponse returned %+v, want: %+v", result, want) - } -} - -func TestParseBooleanResponse_error(t *testing.T) { - v := &ErrorResponse{Response: &http.Response{StatusCode: http.StatusBadRequest}} - result, err := parseBoolResponse(v) - - if err == nil { - t.Errorf("Expected error to be returned.") - } - - if want := false; result != want { - t.Errorf("parseBoolResponse returned %+v, want: %+v", result, want) - } -} - -func TestErrorResponse_Error(t *testing.T) { - res := &http.Response{Request: &http.Request{}} - err := ErrorResponse{Message: "m", Response: res} - if err.Error() == "" { - t.Errorf("Expected non-empty ErrorResponse.Error()") - } -} - -func TestError_Error(t *testing.T) { - err := Error{} - if err.Error() == "" { - t.Errorf("Expected non-empty Error.Error()") - } -} - -func TestRateLimit(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/rate_limit", func(w http.ResponseWriter, r *http.Request) { - if m := "GET"; m != r.Method { - t.Errorf("Request method = %v, want %v", r.Method, m) - } - //fmt.Fprint(w, `{"resources":{"core": {"limit":2,"remaining":1,"reset":1372700873}}}`) - fmt.Fprint(w, `{"resources":{ - "core": {"limit":2,"remaining":1,"reset":1372700873}, - "search": {"limit":3,"remaining":2,"reset":1372700874} - }}`) - }) - - rate, _, err := client.RateLimit() - if err != nil { - t.Errorf("Rate limit returned error: %v", err) - } - - want := &Rate{ - Limit: 2, - Remaining: 1, - Reset: Timestamp{time.Date(2013, 7, 1, 17, 47, 53, 0, time.UTC).Local()}, - } - if !reflect.DeepEqual(rate, want) { - t.Errorf("RateLimit returned %+v, want %+v", rate, want) - } -} - -func TestRateLimits(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/rate_limit", func(w http.ResponseWriter, r *http.Request) { - if m := "GET"; m != r.Method { - t.Errorf("Request method = %v, want %v", r.Method, m) - } - fmt.Fprint(w, `{"resources":{ - "core": {"limit":2,"remaining":1,"reset":1372700873}, - "search": {"limit":3,"remaining":2,"reset":1372700874} - }}`) - }) - - rate, _, err := client.RateLimits() - if err != nil { - t.Errorf("RateLimits returned error: %v", err) - } - - want := &RateLimits{ - Core: &Rate{ - Limit: 2, - Remaining: 1, - Reset: Timestamp{time.Date(2013, 7, 1, 17, 47, 53, 0, time.UTC).Local()}, - }, - Search: &Rate{ - Limit: 3, - Remaining: 2, - Reset: Timestamp{time.Date(2013, 7, 1, 17, 47, 54, 0, time.UTC).Local()}, - }, - } - if !reflect.DeepEqual(rate, want) { - t.Errorf("RateLimits returned %+v, want %+v", rate, want) - } -} - -func TestUnauthenticatedRateLimitedTransport(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) { - var v, want string - q := r.URL.Query() - if v, want = q.Get("client_id"), "id"; v != want { - t.Errorf("OAuth Client ID = %v, want %v", v, want) - } - if v, want = q.Get("client_secret"), "secret"; v != want { - t.Errorf("OAuth Client Secret = %v, want %v", v, want) - } - }) - - tp := &UnauthenticatedRateLimitedTransport{ - ClientID: "id", - ClientSecret: "secret", - } - unauthedClient := NewClient(tp.Client()) - unauthedClient.BaseURL = client.BaseURL - req, _ := unauthedClient.NewRequest("GET", "/", nil) - unauthedClient.Do(req, nil) -} - -func TestUnauthenticatedRateLimitedTransport_missingFields(t *testing.T) { - // missing ClientID - tp := &UnauthenticatedRateLimitedTransport{ - ClientSecret: "secret", - } - _, err := tp.RoundTrip(nil) - if err == nil { - t.Errorf("Expected error to be returned") - } - - // missing ClientSecret - tp = &UnauthenticatedRateLimitedTransport{ - ClientID: "id", - } - _, err = tp.RoundTrip(nil) - if err == nil { - t.Errorf("Expected error to be returned") - } -} - -func TestUnauthenticatedRateLimitedTransport_transport(t *testing.T) { - // default transport - tp := &UnauthenticatedRateLimitedTransport{ - ClientID: "id", - ClientSecret: "secret", - } - if tp.transport() != http.DefaultTransport { - t.Errorf("Expected http.DefaultTransport to be used.") - } - - // custom transport - tp = &UnauthenticatedRateLimitedTransport{ - ClientID: "id", - ClientSecret: "secret", - Transport: &http.Transport{}, - } - if tp.transport() == http.DefaultTransport { - t.Errorf("Expected custom transport to be used.") - } -} diff --git a/vendor/github.com/google/go-github/github/gitignore_test.go b/vendor/github.com/google/go-github/github/gitignore_test.go deleted file mode 100644 index 6d49d00fa..000000000 --- a/vendor/github.com/google/go-github/github/gitignore_test.go +++ /dev/null @@ -1,58 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestGitignoresService_List(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/gitignore/templates", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `["C", "Go"]`) - }) - - available, _, err := client.Gitignores.List() - if err != nil { - t.Errorf("Gitignores.List returned error: %v", err) - } - - want := []string{"C", "Go"} - if !reflect.DeepEqual(available, want) { - t.Errorf("Gitignores.List returned %+v, want %+v", available, want) - } -} - -func TestGitignoresService_Get(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/gitignore/templates/name", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"name":"Name","source":"template source"}`) - }) - - gitignore, _, err := client.Gitignores.Get("name") - if err != nil { - t.Errorf("Gitignores.List returned error: %v", err) - } - - want := &Gitignore{Name: String("Name"), Source: String("template source")} - if !reflect.DeepEqual(gitignore, want) { - t.Errorf("Gitignores.Get returned %+v, want %+v", gitignore, want) - } -} - -func TestGitignoresService_Get_invalidTemplate(t *testing.T) { - _, _, err := client.Gitignores.Get("%") - testURLParseError(t, err) -} diff --git a/vendor/github.com/google/go-github/github/issues.go b/vendor/github.com/google/go-github/github/issues.go index f92df6b56..34807aa65 100644 --- a/vendor/github.com/google/go-github/github/issues.go +++ b/vendor/github.com/google/go-github/github/issues.go @@ -49,12 +49,12 @@ func (i Issue) String() string { // It is separate from Issue above because otherwise Labels // and Assignee fail to serialize to the correct JSON. type IssueRequest struct { - Title *string `json:"title,omitempty"` - Body *string `json:"body,omitempty"` - Labels []string `json:"labels,omitempty"` - Assignee *string `json:"assignee,omitempty"` - State *string `json:"state,omitempty"` - Milestone *int `json:"milestone,omitempty"` + Title *string `json:"title,omitempty"` + Body *string `json:"body,omitempty"` + Labels *[]string `json:"labels,omitempty"` + Assignee *string `json:"assignee,omitempty"` + State *string `json:"state,omitempty"` + Milestone *int `json:"milestone,omitempty"` } // IssueListOptions specifies the optional parameters to the IssuesService.List @@ -72,7 +72,7 @@ type IssueListOptions struct { Labels []string `url:"labels,comma,omitempty"` // Sort specifies how to sort issues. Possible values are: created, updated, - // and comments. Default value is "assigned". + // and comments. Default value is "created". Sort string `url:"sort,omitempty"` // Direction in which to sort issues. Possible values are: asc, desc. @@ -156,17 +156,17 @@ type IssueListByRepoOptions struct { // any assigned user. Assignee string `url:"assignee,omitempty"` - // Assignee filters issues based on their creator. + // Creator filters issues based on their creator. Creator string `url:"creator,omitempty"` - // Assignee filters issues to those mentioned a specific user. + // Mentioned filters issues to those mentioned a specific user. Mentioned string `url:"mentioned,omitempty"` // Labels filters issues based on their label. Labels []string `url:"labels,omitempty,comma"` // Sort specifies how to sort issues. Possible values are: created, updated, - // and comments. Default value is "assigned". + // and comments. Default value is "created". Sort string `url:"sort,omitempty"` // Direction in which to sort issues. Possible values are: asc, desc. diff --git a/vendor/github.com/google/go-github/github/issues_assignees_test.go b/vendor/github.com/google/go-github/github/issues_assignees_test.go deleted file mode 100644 index 63e024d31..000000000 --- a/vendor/github.com/google/go-github/github/issues_assignees_test.go +++ /dev/null @@ -1,98 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestIssuesService_ListAssignees(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/assignees", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `[{"id":1}]`) - }) - - opt := &ListOptions{Page: 2} - assignees, _, err := client.Issues.ListAssignees("o", "r", opt) - if err != nil { - t.Errorf("Issues.List returned error: %v", err) - } - - want := []User{{ID: Int(1)}} - if !reflect.DeepEqual(assignees, want) { - t.Errorf("Issues.ListAssignees returned %+v, want %+v", assignees, want) - } -} - -func TestIssuesService_ListAssignees_invalidOwner(t *testing.T) { - _, _, err := client.Issues.ListAssignees("%", "r", nil) - testURLParseError(t, err) -} - -func TestIssuesService_IsAssignee_true(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/assignees/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - }) - - assignee, _, err := client.Issues.IsAssignee("o", "r", "u") - if err != nil { - t.Errorf("Issues.IsAssignee returned error: %v", err) - } - if want := true; assignee != want { - t.Errorf("Issues.IsAssignee returned %+v, want %+v", assignee, want) - } -} - -func TestIssuesService_IsAssignee_false(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/assignees/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - w.WriteHeader(http.StatusNotFound) - }) - - assignee, _, err := client.Issues.IsAssignee("o", "r", "u") - if err != nil { - t.Errorf("Issues.IsAssignee returned error: %v", err) - } - if want := false; assignee != want { - t.Errorf("Issues.IsAssignee returned %+v, want %+v", assignee, want) - } -} - -func TestIssuesService_IsAssignee_error(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/assignees/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - http.Error(w, "BadRequest", http.StatusBadRequest) - }) - - assignee, _, err := client.Issues.IsAssignee("o", "r", "u") - if err == nil { - t.Errorf("Expected HTTP 400 response") - } - if want := false; assignee != want { - t.Errorf("Issues.IsAssignee returned %+v, want %+v", assignee, want) - } -} - -func TestIssuesService_IsAssignee_invalidOwner(t *testing.T) { - _, _, err := client.Issues.IsAssignee("%", "r", "u") - testURLParseError(t, err) -} diff --git a/vendor/github.com/google/go-github/github/issues_comments_test.go b/vendor/github.com/google/go-github/github/issues_comments_test.go deleted file mode 100644 index 697f4380f..000000000 --- a/vendor/github.com/google/go-github/github/issues_comments_test.go +++ /dev/null @@ -1,184 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" - "time" -) - -func TestIssuesService_ListComments_allIssues(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/issues/comments", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "sort": "updated", - "direction": "desc", - "since": "2002-02-10T15:30:00Z", - "page": "2", - }) - fmt.Fprint(w, `[{"id":1}]`) - }) - - opt := &IssueListCommentsOptions{ - Sort: "updated", - Direction: "desc", - Since: time.Date(2002, time.February, 10, 15, 30, 0, 0, time.UTC), - ListOptions: ListOptions{Page: 2}, - } - comments, _, err := client.Issues.ListComments("o", "r", 0, opt) - if err != nil { - t.Errorf("Issues.ListComments returned error: %v", err) - } - - want := []IssueComment{{ID: Int(1)}} - if !reflect.DeepEqual(comments, want) { - t.Errorf("Issues.ListComments returned %+v, want %+v", comments, want) - } -} - -func TestIssuesService_ListComments_specificIssue(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/issues/1/comments", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `[{"id":1}]`) - }) - - comments, _, err := client.Issues.ListComments("o", "r", 1, nil) - if err != nil { - t.Errorf("Issues.ListComments returned error: %v", err) - } - - want := []IssueComment{{ID: Int(1)}} - if !reflect.DeepEqual(comments, want) { - t.Errorf("Issues.ListComments returned %+v, want %+v", comments, want) - } -} - -func TestIssuesService_ListComments_invalidOwner(t *testing.T) { - _, _, err := client.Issues.ListComments("%", "r", 1, nil) - testURLParseError(t, err) -} - -func TestIssuesService_GetComment(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/issues/comments/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"id":1}`) - }) - - comment, _, err := client.Issues.GetComment("o", "r", 1) - if err != nil { - t.Errorf("Issues.GetComment returned error: %v", err) - } - - want := &IssueComment{ID: Int(1)} - if !reflect.DeepEqual(comment, want) { - t.Errorf("Issues.GetComment returned %+v, want %+v", comment, want) - } -} - -func TestIssuesService_GetComment_invalidOrg(t *testing.T) { - _, _, err := client.Issues.GetComment("%", "r", 1) - testURLParseError(t, err) -} - -func TestIssuesService_CreateComment(t *testing.T) { - setup() - defer teardown() - - input := &IssueComment{Body: String("b")} - - mux.HandleFunc("/repos/o/r/issues/1/comments", func(w http.ResponseWriter, r *http.Request) { - v := new(IssueComment) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "POST") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"id":1}`) - }) - - comment, _, err := client.Issues.CreateComment("o", "r", 1, input) - if err != nil { - t.Errorf("Issues.CreateComment returned error: %v", err) - } - - want := &IssueComment{ID: Int(1)} - if !reflect.DeepEqual(comment, want) { - t.Errorf("Issues.CreateComment returned %+v, want %+v", comment, want) - } -} - -func TestIssuesService_CreateComment_invalidOrg(t *testing.T) { - _, _, err := client.Issues.CreateComment("%", "r", 1, nil) - testURLParseError(t, err) -} - -func TestIssuesService_EditComment(t *testing.T) { - setup() - defer teardown() - - input := &IssueComment{Body: String("b")} - - mux.HandleFunc("/repos/o/r/issues/comments/1", func(w http.ResponseWriter, r *http.Request) { - v := new(IssueComment) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "PATCH") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"id":1}`) - }) - - comment, _, err := client.Issues.EditComment("o", "r", 1, input) - if err != nil { - t.Errorf("Issues.EditComment returned error: %v", err) - } - - want := &IssueComment{ID: Int(1)} - if !reflect.DeepEqual(comment, want) { - t.Errorf("Issues.EditComment returned %+v, want %+v", comment, want) - } -} - -func TestIssuesService_EditComment_invalidOwner(t *testing.T) { - _, _, err := client.Issues.EditComment("%", "r", 1, nil) - testURLParseError(t, err) -} - -func TestIssuesService_DeleteComment(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/issues/comments/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - }) - - _, err := client.Issues.DeleteComment("o", "r", 1) - if err != nil { - t.Errorf("Issues.DeleteComments returned error: %v", err) - } -} - -func TestIssuesService_DeleteComment_invalidOwner(t *testing.T) { - _, err := client.Issues.DeleteComment("%", "r", 1) - testURLParseError(t, err) -} diff --git a/vendor/github.com/google/go-github/github/issues_events.go b/vendor/github.com/google/go-github/github/issues_events.go index 0c720aa15..9062d4da1 100644 --- a/vendor/github.com/google/go-github/github/issues_events.go +++ b/vendor/github.com/google/go-github/github/issues_events.go @@ -22,40 +22,52 @@ type IssueEvent struct { // values are: // // closed - // The issue was closed by the actor. When the commit_id is - // present, it identifies the commit that closed the issue using - // “closes / fixes #NN” syntax. - // - // reopened - // The issue was reopened by the actor. - // - // subscribed - // The actor subscribed to receive notifications for an issue. + // The Actor closed the issue. + // If the issue was closed by commit message, CommitID holds the SHA1 hash of the commit. // // merged - // The issue was merged by the actor. The commit_id attribute is the SHA1 of the HEAD commit that was merged. + // The Actor merged into master a branch containing a commit mentioning the issue. + // CommitID holds the SHA1 of the merge commit. // // referenced - // The issue was referenced from a commit message. The commit_id attribute is the commit SHA1 of where that happened. + // The Actor committed to master a commit mentioning the issue in its commit message. + // CommitID holds the SHA1 of the commit. + // + // reopened, locked, unlocked + // The Actor did that to the issue. + // + // renamed + // The Actor changed the issue title from Rename.From to Rename.To. // // mentioned - // The actor was @mentioned in an issue body. + // Someone unspecified @mentioned the Actor [sic] in an issue comment body. // - // assigned - // The issue was assigned to the actor. + // assigned, unassigned + // The Actor assigned the issue to or removed the assignment from the Assignee. // - // head_ref_deleted - // The pull request’s branch was deleted. + // labeled, unlabeled + // The Actor added or removed the Label from the issue. + // + // milestoned, demilestoned + // The Actor added or removed the issue from the Milestone. + // + // subscribed, unsubscribed + // The Actor subscribed to or unsubscribed from notifications for an issue. + // + // head_ref_deleted, head_ref_restored + // The pull request’s branch was deleted or restored. // - // head_ref_restored - // The pull request’s branch was restored. Event *string `json:"event,omitempty"` - // The SHA of the commit that referenced this commit, if applicable. - CommitID *string `json:"commit_id,omitempty"` - CreatedAt *time.Time `json:"created_at,omitempty"` Issue *Issue `json:"issue,omitempty"` + + // Only present on certain events; see above. + Assignee *User `json:"assignee,omitempty"` + CommitID *string `json:"commit_id,omitempty"` + Milestone *Milestone `json:"milestone,omitempty"` + Label *Label `json:"label,omitempty"` + Rename *Rename `json:"rename,omitempty"` } // ListIssueEvents lists events for the specified issue. @@ -125,3 +137,13 @@ func (s *IssuesService) GetEvent(owner, repo string, id int) (*IssueEvent, *Resp return event, resp, err } + +// Rename contains details for 'renamed' events. +type Rename struct { + From *string `json:"from,omitempty"` + To *string `json:"to,omitempty"` +} + +func (r Rename) String() string { + return Stringify(r) +} diff --git a/vendor/github.com/google/go-github/github/issues_events_test.go b/vendor/github.com/google/go-github/github/issues_events_test.go deleted file mode 100644 index f90b64a71..000000000 --- a/vendor/github.com/google/go-github/github/issues_events_test.go +++ /dev/null @@ -1,86 +0,0 @@ -// Copyright 2014 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestIssuesService_ListIssueEvents(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/issues/1/events", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "page": "1", - "per_page": "2", - }) - fmt.Fprint(w, `[{"id":1}]`) - }) - - opt := &ListOptions{Page: 1, PerPage: 2} - events, _, err := client.Issues.ListIssueEvents("o", "r", 1, opt) - - if err != nil { - t.Errorf("Issues.ListIssueEvents returned error: %v", err) - } - - want := []IssueEvent{{ID: Int(1)}} - if !reflect.DeepEqual(events, want) { - t.Errorf("Issues.ListIssueEvents returned %+v, want %+v", events, want) - } -} - -func TestIssuesService_ListRepositoryEvents(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/issues/events", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "page": "1", - "per_page": "2", - }) - fmt.Fprint(w, `[{"id":1}]`) - }) - - opt := &ListOptions{Page: 1, PerPage: 2} - events, _, err := client.Issues.ListRepositoryEvents("o", "r", opt) - - if err != nil { - t.Errorf("Issues.ListRepositoryEvents returned error: %v", err) - } - - want := []IssueEvent{{ID: Int(1)}} - if !reflect.DeepEqual(events, want) { - t.Errorf("Issues.ListRepositoryEvents returned %+v, want %+v", events, want) - } -} - -func TestIssuesService_GetEvent(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/issues/events/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"id":1}`) - }) - - event, _, err := client.Issues.GetEvent("o", "r", 1) - - if err != nil { - t.Errorf("Issues.GetEvent returned error: %v", err) - } - - want := &IssueEvent{ID: Int(1)} - if !reflect.DeepEqual(event, want) { - t.Errorf("Issues.GetEvent returned %+v, want %+v", event, want) - } -} diff --git a/vendor/github.com/google/go-github/github/issues_labels.go b/vendor/github.com/google/go-github/github/issues_labels.go index 5ad25c1bb..88f9f3ff9 100644 --- a/vendor/github.com/google/go-github/github/issues_labels.go +++ b/vendor/github.com/google/go-github/github/issues_labels.go @@ -7,7 +7,7 @@ package github import "fmt" -// Label represents a GitHib label on an Issue +// Label represents a GitHub label on an Issue type Label struct { URL *string `json:"url,omitempty"` Name *string `json:"name,omitempty"` diff --git a/vendor/github.com/google/go-github/github/issues_labels_test.go b/vendor/github.com/google/go-github/github/issues_labels_test.go deleted file mode 100644 index 2243eb0ee..000000000 --- a/vendor/github.com/google/go-github/github/issues_labels_test.go +++ /dev/null @@ -1,313 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestIssuesService_ListLabels(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/labels", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `[{"name": "a"},{"name": "b"}]`) - }) - - opt := &ListOptions{Page: 2} - labels, _, err := client.Issues.ListLabels("o", "r", opt) - if err != nil { - t.Errorf("Issues.ListLabels returned error: %v", err) - } - - want := []Label{{Name: String("a")}, {Name: String("b")}} - if !reflect.DeepEqual(labels, want) { - t.Errorf("Issues.ListLabels returned %+v, want %+v", labels, want) - } -} - -func TestIssuesService_ListLabels_invalidOwner(t *testing.T) { - _, _, err := client.Issues.ListLabels("%", "%", nil) - testURLParseError(t, err) -} - -func TestIssuesService_GetLabel(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/labels/n", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"url":"u", "name": "n", "color": "c"}`) - }) - - label, _, err := client.Issues.GetLabel("o", "r", "n") - if err != nil { - t.Errorf("Issues.GetLabel returned error: %v", err) - } - - want := &Label{URL: String("u"), Name: String("n"), Color: String("c")} - if !reflect.DeepEqual(label, want) { - t.Errorf("Issues.GetLabel returned %+v, want %+v", label, want) - } -} - -func TestIssuesService_GetLabel_invalidOwner(t *testing.T) { - _, _, err := client.Issues.GetLabel("%", "%", "%") - testURLParseError(t, err) -} - -func TestIssuesService_CreateLabel(t *testing.T) { - setup() - defer teardown() - - input := &Label{Name: String("n")} - - mux.HandleFunc("/repos/o/r/labels", func(w http.ResponseWriter, r *http.Request) { - v := new(Label) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "POST") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"url":"u"}`) - }) - - label, _, err := client.Issues.CreateLabel("o", "r", input) - if err != nil { - t.Errorf("Issues.CreateLabel returned error: %v", err) - } - - want := &Label{URL: String("u")} - if !reflect.DeepEqual(label, want) { - t.Errorf("Issues.CreateLabel returned %+v, want %+v", label, want) - } -} - -func TestIssuesService_CreateLabel_invalidOwner(t *testing.T) { - _, _, err := client.Issues.CreateLabel("%", "%", nil) - testURLParseError(t, err) -} - -func TestIssuesService_EditLabel(t *testing.T) { - setup() - defer teardown() - - input := &Label{Name: String("z")} - - mux.HandleFunc("/repos/o/r/labels/n", func(w http.ResponseWriter, r *http.Request) { - v := new(Label) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "PATCH") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"url":"u"}`) - }) - - label, _, err := client.Issues.EditLabel("o", "r", "n", input) - if err != nil { - t.Errorf("Issues.EditLabel returned error: %v", err) - } - - want := &Label{URL: String("u")} - if !reflect.DeepEqual(label, want) { - t.Errorf("Issues.EditLabel returned %+v, want %+v", label, want) - } -} - -func TestIssuesService_EditLabel_invalidOwner(t *testing.T) { - _, _, err := client.Issues.EditLabel("%", "%", "%", nil) - testURLParseError(t, err) -} - -func TestIssuesService_DeleteLabel(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/labels/n", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - }) - - _, err := client.Issues.DeleteLabel("o", "r", "n") - if err != nil { - t.Errorf("Issues.DeleteLabel returned error: %v", err) - } -} - -func TestIssuesService_DeleteLabel_invalidOwner(t *testing.T) { - _, err := client.Issues.DeleteLabel("%", "%", "%") - testURLParseError(t, err) -} - -func TestIssuesService_ListLabelsByIssue(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/issues/1/labels", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `[{"name": "a"},{"name": "b"}]`) - }) - - opt := &ListOptions{Page: 2} - labels, _, err := client.Issues.ListLabelsByIssue("o", "r", 1, opt) - if err != nil { - t.Errorf("Issues.ListLabelsByIssue returned error: %v", err) - } - - want := []Label{{Name: String("a")}, {Name: String("b")}} - if !reflect.DeepEqual(labels, want) { - t.Errorf("Issues.ListLabelsByIssue returned %+v, want %+v", labels, want) - } -} - -func TestIssuesService_ListLabelsByIssue_invalidOwner(t *testing.T) { - _, _, err := client.Issues.ListLabelsByIssue("%", "%", 1, nil) - testURLParseError(t, err) -} - -func TestIssuesService_AddLabelsToIssue(t *testing.T) { - setup() - defer teardown() - - input := []string{"a", "b"} - - mux.HandleFunc("/repos/o/r/issues/1/labels", func(w http.ResponseWriter, r *http.Request) { - v := new([]string) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "POST") - if !reflect.DeepEqual(*v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `[{"url":"u"}]`) - }) - - labels, _, err := client.Issues.AddLabelsToIssue("o", "r", 1, input) - if err != nil { - t.Errorf("Issues.AddLabelsToIssue returned error: %v", err) - } - - want := []Label{{URL: String("u")}} - if !reflect.DeepEqual(labels, want) { - t.Errorf("Issues.AddLabelsToIssue returned %+v, want %+v", labels, want) - } -} - -func TestIssuesService_AddLabelsToIssue_invalidOwner(t *testing.T) { - _, _, err := client.Issues.AddLabelsToIssue("%", "%", 1, nil) - testURLParseError(t, err) -} - -func TestIssuesService_RemoveLabelForIssue(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/issues/1/labels/l", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - }) - - _, err := client.Issues.RemoveLabelForIssue("o", "r", 1, "l") - if err != nil { - t.Errorf("Issues.RemoveLabelForIssue returned error: %v", err) - } -} - -func TestIssuesService_RemoveLabelForIssue_invalidOwner(t *testing.T) { - _, err := client.Issues.RemoveLabelForIssue("%", "%", 1, "%") - testURLParseError(t, err) -} - -func TestIssuesService_ReplaceLabelsForIssue(t *testing.T) { - setup() - defer teardown() - - input := []string{"a", "b"} - - mux.HandleFunc("/repos/o/r/issues/1/labels", func(w http.ResponseWriter, r *http.Request) { - v := new([]string) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "PUT") - if !reflect.DeepEqual(*v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `[{"url":"u"}]`) - }) - - labels, _, err := client.Issues.ReplaceLabelsForIssue("o", "r", 1, input) - if err != nil { - t.Errorf("Issues.ReplaceLabelsForIssue returned error: %v", err) - } - - want := []Label{{URL: String("u")}} - if !reflect.DeepEqual(labels, want) { - t.Errorf("Issues.ReplaceLabelsForIssue returned %+v, want %+v", labels, want) - } -} - -func TestIssuesService_ReplaceLabelsForIssue_invalidOwner(t *testing.T) { - _, _, err := client.Issues.ReplaceLabelsForIssue("%", "%", 1, nil) - testURLParseError(t, err) -} - -func TestIssuesService_RemoveLabelsForIssue(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/issues/1/labels", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - }) - - _, err := client.Issues.RemoveLabelsForIssue("o", "r", 1) - if err != nil { - t.Errorf("Issues.RemoveLabelsForIssue returned error: %v", err) - } -} - -func TestIssuesService_RemoveLabelsForIssue_invalidOwner(t *testing.T) { - _, err := client.Issues.RemoveLabelsForIssue("%", "%", 1) - testURLParseError(t, err) -} - -func TestIssuesService_ListLabelsForMilestone(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/milestones/1/labels", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `[{"name": "a"},{"name": "b"}]`) - }) - - opt := &ListOptions{Page: 2} - labels, _, err := client.Issues.ListLabelsForMilestone("o", "r", 1, opt) - if err != nil { - t.Errorf("Issues.ListLabelsForMilestone returned error: %v", err) - } - - want := []Label{{Name: String("a")}, {Name: String("b")}} - if !reflect.DeepEqual(labels, want) { - t.Errorf("Issues.ListLabelsForMilestone returned %+v, want %+v", labels, want) - } -} - -func TestIssuesService_ListLabelsForMilestone_invalidOwner(t *testing.T) { - _, _, err := client.Issues.ListLabelsForMilestone("%", "%", 1, nil) - testURLParseError(t, err) -} diff --git a/vendor/github.com/google/go-github/github/issues_milestones.go b/vendor/github.com/google/go-github/github/issues_milestones.go index d5fd8aecc..cbd79200e 100644 --- a/vendor/github.com/google/go-github/github/issues_milestones.go +++ b/vendor/github.com/google/go-github/github/issues_milestones.go @@ -49,7 +49,7 @@ type MilestoneListOptions struct { // // GitHub API docs: https://developer.github.com/v3/issues/milestones/#list-milestones-for-a-repository func (s *IssuesService) ListMilestones(owner string, repo string, opt *MilestoneListOptions) ([]Milestone, *Response, error) { - u := fmt.Sprintf("/repos/%v/%v/milestones", owner, repo) + u := fmt.Sprintf("repos/%v/%v/milestones", owner, repo) u, err := addOptions(u, opt) if err != nil { return nil, nil, err @@ -73,7 +73,7 @@ func (s *IssuesService) ListMilestones(owner string, repo string, opt *Milestone // // GitHub API docs: https://developer.github.com/v3/issues/milestones/#get-a-single-milestone func (s *IssuesService) GetMilestone(owner string, repo string, number int) (*Milestone, *Response, error) { - u := fmt.Sprintf("/repos/%v/%v/milestones/%d", owner, repo, number) + u := fmt.Sprintf("repos/%v/%v/milestones/%d", owner, repo, number) req, err := s.client.NewRequest("GET", u, nil) if err != nil { return nil, nil, err @@ -92,7 +92,7 @@ func (s *IssuesService) GetMilestone(owner string, repo string, number int) (*Mi // // GitHub API docs: https://developer.github.com/v3/issues/milestones/#create-a-milestone func (s *IssuesService) CreateMilestone(owner string, repo string, milestone *Milestone) (*Milestone, *Response, error) { - u := fmt.Sprintf("/repos/%v/%v/milestones", owner, repo) + u := fmt.Sprintf("repos/%v/%v/milestones", owner, repo) req, err := s.client.NewRequest("POST", u, milestone) if err != nil { return nil, nil, err diff --git a/vendor/github.com/google/go-github/github/issues_milestones_test.go b/vendor/github.com/google/go-github/github/issues_milestones_test.go deleted file mode 100644 index 817fffedd..000000000 --- a/vendor/github.com/google/go-github/github/issues_milestones_test.go +++ /dev/null @@ -1,157 +0,0 @@ -// Copyright 2014 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestIssuesService_ListMilestones(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/milestones", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "state": "closed", - "sort": "due_date", - "direction": "asc", - }) - fmt.Fprint(w, `[{"number":1}]`) - }) - - opt := &MilestoneListOptions{"closed", "due_date", "asc"} - milestones, _, err := client.Issues.ListMilestones("o", "r", opt) - if err != nil { - t.Errorf("IssuesService.ListMilestones returned error: %v", err) - } - - want := []Milestone{{Number: Int(1)}} - if !reflect.DeepEqual(milestones, want) { - t.Errorf("IssuesService.ListMilestones returned %+v, want %+v", milestones, want) - } -} - -func TestIssuesService_ListMilestones_invalidOwner(t *testing.T) { - _, _, err := client.Issues.ListMilestones("%", "r", nil) - testURLParseError(t, err) -} - -func TestIssuesService_GetMilestone(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/milestones/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"number":1}`) - }) - - milestone, _, err := client.Issues.GetMilestone("o", "r", 1) - if err != nil { - t.Errorf("IssuesService.GetMilestone returned error: %v", err) - } - - want := &Milestone{Number: Int(1)} - if !reflect.DeepEqual(milestone, want) { - t.Errorf("IssuesService.GetMilestone returned %+v, want %+v", milestone, want) - } -} - -func TestIssuesService_GetMilestone_invalidOwner(t *testing.T) { - _, _, err := client.Issues.GetMilestone("%", "r", 1) - testURLParseError(t, err) -} - -func TestIssuesService_CreateMilestone(t *testing.T) { - setup() - defer teardown() - - input := &Milestone{Title: String("t")} - - mux.HandleFunc("/repos/o/r/milestones", func(w http.ResponseWriter, r *http.Request) { - v := new(Milestone) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "POST") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"number":1}`) - }) - - milestone, _, err := client.Issues.CreateMilestone("o", "r", input) - if err != nil { - t.Errorf("IssuesService.CreateMilestone returned error: %v", err) - } - - want := &Milestone{Number: Int(1)} - if !reflect.DeepEqual(milestone, want) { - t.Errorf("IssuesService.CreateMilestone returned %+v, want %+v", milestone, want) - } -} - -func TestIssuesService_CreateMilestone_invalidOwner(t *testing.T) { - _, _, err := client.Issues.CreateMilestone("%", "r", nil) - testURLParseError(t, err) -} - -func TestIssuesService_EditMilestone(t *testing.T) { - setup() - defer teardown() - - input := &Milestone{Title: String("t")} - - mux.HandleFunc("/repos/o/r/milestones/1", func(w http.ResponseWriter, r *http.Request) { - v := new(Milestone) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "PATCH") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"number":1}`) - }) - - milestone, _, err := client.Issues.EditMilestone("o", "r", 1, input) - if err != nil { - t.Errorf("IssuesService.EditMilestone returned error: %v", err) - } - - want := &Milestone{Number: Int(1)} - if !reflect.DeepEqual(milestone, want) { - t.Errorf("IssuesService.EditMilestone returned %+v, want %+v", milestone, want) - } -} - -func TestIssuesService_EditMilestone_invalidOwner(t *testing.T) { - _, _, err := client.Issues.EditMilestone("%", "r", 1, nil) - testURLParseError(t, err) -} - -func TestIssuesService_DeleteMilestone(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/milestones/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - }) - - _, err := client.Issues.DeleteMilestone("o", "r", 1) - if err != nil { - t.Errorf("IssuesService.DeleteMilestone returned error: %v", err) - } -} - -func TestIssuesService_DeleteMilestone_invalidOwner(t *testing.T) { - _, err := client.Issues.DeleteMilestone("%", "r", 1) - testURLParseError(t, err) -} diff --git a/vendor/github.com/google/go-github/github/issues_test.go b/vendor/github.com/google/go-github/github/issues_test.go deleted file mode 100644 index 090cf1b1a..000000000 --- a/vendor/github.com/google/go-github/github/issues_test.go +++ /dev/null @@ -1,242 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" - "time" -) - -func TestIssuesService_List_all(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/issues", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "filter": "all", - "state": "closed", - "labels": "a,b", - "sort": "updated", - "direction": "asc", - "since": "2002-02-10T15:30:00Z", - "page": "1", - "per_page": "2", - }) - fmt.Fprint(w, `[{"number":1}]`) - }) - - opt := &IssueListOptions{ - "all", "closed", []string{"a", "b"}, "updated", "asc", - time.Date(2002, time.February, 10, 15, 30, 0, 0, time.UTC), - ListOptions{Page: 1, PerPage: 2}, - } - issues, _, err := client.Issues.List(true, opt) - - if err != nil { - t.Errorf("Issues.List returned error: %v", err) - } - - want := []Issue{{Number: Int(1)}} - if !reflect.DeepEqual(issues, want) { - t.Errorf("Issues.List returned %+v, want %+v", issues, want) - } -} - -func TestIssuesService_List_owned(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/user/issues", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `[{"number":1}]`) - }) - - issues, _, err := client.Issues.List(false, nil) - if err != nil { - t.Errorf("Issues.List returned error: %v", err) - } - - want := []Issue{{Number: Int(1)}} - if !reflect.DeepEqual(issues, want) { - t.Errorf("Issues.List returned %+v, want %+v", issues, want) - } -} - -func TestIssuesService_ListByOrg(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/orgs/o/issues", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `[{"number":1}]`) - }) - - issues, _, err := client.Issues.ListByOrg("o", nil) - if err != nil { - t.Errorf("Issues.ListByOrg returned error: %v", err) - } - - want := []Issue{{Number: Int(1)}} - if !reflect.DeepEqual(issues, want) { - t.Errorf("Issues.List returned %+v, want %+v", issues, want) - } -} - -func TestIssuesService_ListByOrg_invalidOrg(t *testing.T) { - _, _, err := client.Issues.ListByOrg("%", nil) - testURLParseError(t, err) -} - -func TestIssuesService_ListByRepo(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/issues", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "milestone": "*", - "state": "closed", - "assignee": "a", - "creator": "c", - "mentioned": "m", - "labels": "a,b", - "sort": "updated", - "direction": "asc", - "since": "2002-02-10T15:30:00Z", - }) - fmt.Fprint(w, `[{"number":1}]`) - }) - - opt := &IssueListByRepoOptions{ - "*", "closed", "a", "c", "m", []string{"a", "b"}, "updated", "asc", - time.Date(2002, time.February, 10, 15, 30, 0, 0, time.UTC), - ListOptions{0, 0}, - } - issues, _, err := client.Issues.ListByRepo("o", "r", opt) - if err != nil { - t.Errorf("Issues.ListByOrg returned error: %v", err) - } - - want := []Issue{{Number: Int(1)}} - if !reflect.DeepEqual(issues, want) { - t.Errorf("Issues.List returned %+v, want %+v", issues, want) - } -} - -func TestIssuesService_ListByRepo_invalidOwner(t *testing.T) { - _, _, err := client.Issues.ListByRepo("%", "r", nil) - testURLParseError(t, err) -} - -func TestIssuesService_Get(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/issues/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"number":1, "labels": [{"url": "u", "name": "n", "color": "c"}]}`) - }) - - issue, _, err := client.Issues.Get("o", "r", 1) - if err != nil { - t.Errorf("Issues.Get returned error: %v", err) - } - - want := &Issue{ - Number: Int(1), - Labels: []Label{{ - URL: String("u"), - Name: String("n"), - Color: String("c"), - }}, - } - if !reflect.DeepEqual(issue, want) { - t.Errorf("Issues.Get returned %+v, want %+v", issue, want) - } -} - -func TestIssuesService_Get_invalidOwner(t *testing.T) { - _, _, err := client.Issues.Get("%", "r", 1) - testURLParseError(t, err) -} - -func TestIssuesService_Create(t *testing.T) { - setup() - defer teardown() - - input := &IssueRequest{ - Title: String("t"), - Body: String("b"), - Assignee: String("a"), - Labels: []string{"l1", "l2"}, - } - - mux.HandleFunc("/repos/o/r/issues", func(w http.ResponseWriter, r *http.Request) { - v := new(IssueRequest) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "POST") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"number":1}`) - }) - - issue, _, err := client.Issues.Create("o", "r", input) - if err != nil { - t.Errorf("Issues.Create returned error: %v", err) - } - - want := &Issue{Number: Int(1)} - if !reflect.DeepEqual(issue, want) { - t.Errorf("Issues.Create returned %+v, want %+v", issue, want) - } -} - -func TestIssuesService_Create_invalidOwner(t *testing.T) { - _, _, err := client.Issues.Create("%", "r", nil) - testURLParseError(t, err) -} - -func TestIssuesService_Edit(t *testing.T) { - setup() - defer teardown() - - input := &IssueRequest{Title: String("t")} - - mux.HandleFunc("/repos/o/r/issues/1", func(w http.ResponseWriter, r *http.Request) { - v := new(IssueRequest) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "PATCH") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"number":1}`) - }) - - issue, _, err := client.Issues.Edit("o", "r", 1, input) - if err != nil { - t.Errorf("Issues.Edit returned error: %v", err) - } - - want := &Issue{Number: Int(1)} - if !reflect.DeepEqual(issue, want) { - t.Errorf("Issues.Edit returned %+v, want %+v", issue, want) - } -} - -func TestIssuesService_Edit_invalidOwner(t *testing.T) { - _, _, err := client.Issues.Edit("%", "r", 1, nil) - testURLParseError(t, err) -} diff --git a/vendor/github.com/google/go-github/github/licenses.go b/vendor/github.com/google/go-github/github/licenses.go new file mode 100644 index 000000000..fb2fb5af2 --- /dev/null +++ b/vendor/github.com/google/go-github/github/licenses.go @@ -0,0 +1,81 @@ +// Copyright 2013 The go-github AUTHORS. All rights reserved. +// +// Use of this source code is governed by a BSD-style +// license that can be found in the LICENSE file. + +package github + +import "fmt" + +// LicensesService handles communication with the license related +// methods of the GitHub API. +// +// GitHub API docs: http://developer.github.com/v3/pulls/ +type LicensesService struct { + client *Client +} + +// License represents an open source license. +type License struct { + Key *string `json:"key,omitempty"` + Name *string `json:"name,omitempty"` + URL *string `json:"url,omitempty"` + + HTMLURL *string `json:"html_url,omitempty"` + Featured *bool `json:"featured,omitempty"` + Description *string `json:"description,omitempty"` + Category *string `json:"category,omitempty"` + Implementation *string `json:"implementation,omitempty"` + Required *[]string `json:"required,omitempty"` + Permitted *[]string `json:"permitted,omitempty"` + Forbidden *[]string `json:"forbidden,omitempty"` + Body *string `json:"body,omitempty"` +} + +func (l License) String() string { + return Stringify(l) +} + +// List popular open source licenses. +// +// GitHub API docs: https://developer.github.com/v3/licenses/#list-all-licenses +func (s *LicensesService) List() ([]License, *Response, error) { + req, err := s.client.NewRequest("GET", "licenses", nil) + if err != nil { + return nil, nil, err + } + + // TODO: remove custom Accept header when this API fully launches + req.Header.Set("Accept", mediaTypeLicensesPreview) + + licenses := new([]License) + resp, err := s.client.Do(req, licenses) + if err != nil { + return nil, resp, err + } + + return *licenses, resp, err +} + +// Get extended metadata for one license. +// +// GitHub API docs: https://developer.github.com/v3/licenses/#get-an-individual-license +func (s *LicensesService) Get(licenseName string) (*License, *Response, error) { + u := fmt.Sprintf("licenses/%s", licenseName) + + req, err := s.client.NewRequest("GET", u, nil) + if err != nil { + return nil, nil, err + } + + // TODO: remove custom Accept header when this API fully launches + req.Header.Set("Accept", mediaTypeLicensesPreview) + + license := new(License) + resp, err := s.client.Do(req, license) + if err != nil { + return nil, resp, err + } + + return license, resp, err +} diff --git a/vendor/github.com/google/go-github/github/misc.go b/vendor/github.com/google/go-github/github/misc.go index 4a9bb99ef..66e7f5239 100644 --- a/vendor/github.com/google/go-github/github/misc.go +++ b/vendor/github.com/google/go-github/github/misc.go @@ -98,6 +98,10 @@ type APIMeta struct { // username and password, sudo mode, and two-factor authentication are // not supported on these servers.) VerifiablePasswordAuthentication *bool `json:"verifiable_password_authentication,omitempty"` + + // An array of IP addresses in CIDR format specifying the addresses + // which serve GitHub Pages websites. + Pages []string `json:"pages,omitempty"` } // APIMeta returns information about GitHub.com, the service. Or, if you access @@ -159,3 +163,35 @@ func (c *Client) Zen() (string, *Response, error) { return buf.String(), resp, nil } + +// ServiceHook represents a hook that has configuration settings, a list of +// available events, and default events. +type ServiceHook struct { + Name *string `json:"name,omitempty"` + Events []string `json:"events,omitempty"` + SupportedEvents []string `json:"supported_events,omitempty"` + Schema [][]string `json:"schema,omitempty"` +} + +func (s *ServiceHook) String() string { + return Stringify(s) +} + +// ListServiceHooks lists all of the available service hooks. +// +// GitHub API docs: https://developer.github.com/webhooks/#services +func (c *Client) ListServiceHooks() ([]ServiceHook, *Response, error) { + u := "hooks" + req, err := c.NewRequest("GET", u, nil) + if err != nil { + return nil, nil, err + } + + hooks := new([]ServiceHook) + resp, err := c.Do(req, hooks) + if err != nil { + return nil, resp, err + } + + return *hooks, resp, err +} diff --git a/vendor/github.com/google/go-github/github/misc_test.go b/vendor/github.com/google/go-github/github/misc_test.go deleted file mode 100644 index 33c3db63d..000000000 --- a/vendor/github.com/google/go-github/github/misc_test.go +++ /dev/null @@ -1,137 +0,0 @@ -// Copyright 2014 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestMarkdown(t *testing.T) { - setup() - defer teardown() - - input := &markdownRequest{ - Text: String("# text #"), - Mode: String("gfm"), - Context: String("google/go-github"), - } - mux.HandleFunc("/markdown", func(w http.ResponseWriter, r *http.Request) { - v := new(markdownRequest) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "POST") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - fmt.Fprint(w, `

text

`) - }) - - md, _, err := client.Markdown("# text #", &MarkdownOptions{ - Mode: "gfm", - Context: "google/go-github", - }) - if err != nil { - t.Errorf("Markdown returned error: %v", err) - } - - if want := "

text

"; want != md { - t.Errorf("Markdown returned %+v, want %+v", md, want) - } -} - -func TestListEmojis(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/emojis", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"+1": "+1.png"}`) - }) - - emoji, _, err := client.ListEmojis() - if err != nil { - t.Errorf("ListEmojis returned error: %v", err) - } - - want := map[string]string{"+1": "+1.png"} - if !reflect.DeepEqual(want, emoji) { - t.Errorf("ListEmojis returned %+v, want %+v", emoji, want) - } -} - -func TestAPIMeta(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/meta", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"hooks":["h"], "git":["g"], "verifiable_password_authentication": true}`) - }) - - meta, _, err := client.APIMeta() - if err != nil { - t.Errorf("APIMeta returned error: %v", err) - } - - want := &APIMeta{ - Hooks: []string{"h"}, - Git: []string{"g"}, - VerifiablePasswordAuthentication: Bool(true), - } - if !reflect.DeepEqual(want, meta) { - t.Errorf("APIMeta returned %+v, want %+v", meta, want) - } -} - -func TestOctocat(t *testing.T) { - setup() - defer teardown() - - input := "input" - output := "sample text" - - mux.HandleFunc("/octocat", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"s": input}) - w.Header().Set("Content-Type", "application/octocat-stream") - fmt.Fprint(w, output) - }) - - got, _, err := client.Octocat(input) - if err != nil { - t.Errorf("Octocat returned error: %v", err) - } - - if want := output; got != want { - t.Errorf("Octocat returned %+v, want %+v", got, want) - } -} - -func TestZen(t *testing.T) { - setup() - defer teardown() - - output := "sample text" - - mux.HandleFunc("/zen", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - w.Header().Set("Content-Type", "text/plain;charset=utf-8") - fmt.Fprint(w, output) - }) - - got, _, err := client.Zen() - if err != nil { - t.Errorf("Zen returned error: %v", err) - } - - if want := output; got != want { - t.Errorf("Zen returned %+v, want %+v", got, want) - } -} diff --git a/vendor/github.com/google/go-github/github/orgs_hooks.go b/vendor/github.com/google/go-github/github/orgs_hooks.go new file mode 100644 index 000000000..3e7ad40ff --- /dev/null +++ b/vendor/github.com/google/go-github/github/orgs_hooks.go @@ -0,0 +1,104 @@ +// Copyright 2015 The go-github AUTHORS. All rights reserved. +// +// Use of this source code is governed by a BSD-style +// license that can be found in the LICENSE file. + +package github + +import "fmt" + +// ListHooks lists all Hooks for the specified organization. +// +// GitHub API docs: https://developer.github.com/v3/orgs/hooks/#list-hooks +func (s *OrganizationsService) ListHooks(org string, opt *ListOptions) ([]Hook, *Response, error) { + u := fmt.Sprintf("orgs/%v/hooks", org) + u, err := addOptions(u, opt) + if err != nil { + return nil, nil, err + } + + req, err := s.client.NewRequest("GET", u, nil) + if err != nil { + return nil, nil, err + } + + hooks := new([]Hook) + resp, err := s.client.Do(req, hooks) + if err != nil { + return nil, resp, err + } + + return *hooks, resp, err +} + +// GetHook returns a single specified Hook. +// +// GitHub API docs: https://developer.github.com/v3/orgs/hooks/#get-single-hook +func (s *OrganizationsService) GetHook(org string, id int) (*Hook, *Response, error) { + u := fmt.Sprintf("orgs/%v/hooks/%d", org, id) + req, err := s.client.NewRequest("GET", u, nil) + if err != nil { + return nil, nil, err + } + hook := new(Hook) + resp, err := s.client.Do(req, hook) + return hook, resp, err +} + +// CreateHook creates a Hook for the specified org. +// Name and Config are required fields. +// +// GitHub API docs: https://developer.github.com/v3/orgs/hooks/#create-a-hook +func (s *OrganizationsService) CreateHook(org string, hook *Hook) (*Hook, *Response, error) { + u := fmt.Sprintf("orgs/%v/hooks", org) + req, err := s.client.NewRequest("POST", u, hook) + if err != nil { + return nil, nil, err + } + + h := new(Hook) + resp, err := s.client.Do(req, h) + if err != nil { + return nil, resp, err + } + + return h, resp, err +} + +// EditHook updates a specified Hook. +// +// GitHub API docs: https://developer.github.com/v3/orgs/hooks/#edit-a-hook +func (s *OrganizationsService) EditHook(org string, id int, hook *Hook) (*Hook, *Response, error) { + u := fmt.Sprintf("orgs/%v/hooks/%d", org, id) + req, err := s.client.NewRequest("PATCH", u, hook) + if err != nil { + return nil, nil, err + } + h := new(Hook) + resp, err := s.client.Do(req, h) + return h, resp, err +} + +// PingHook triggers a 'ping' event to be sent to the Hook. +// +// GitHub API docs: https://developer.github.com/v3/orgs/hooks/#ping-a-hook +func (s *OrganizationsService) PingHook(org string, id int) (*Response, error) { + u := fmt.Sprintf("orgs/%v/hooks/%d/pings", org, id) + req, err := s.client.NewRequest("POST", u, nil) + if err != nil { + return nil, err + } + return s.client.Do(req, nil) +} + +// DeleteHook deletes a specified Hook. +// +// GitHub API docs: https://developer.github.com/v3/orgs/hooks/#delete-a-hook +func (s *OrganizationsService) DeleteHook(org string, id int) (*Response, error) { + u := fmt.Sprintf("orgs/%v/hooks/%d", org, id) + req, err := s.client.NewRequest("DELETE", u, nil) + if err != nil { + return nil, err + } + return s.client.Do(req, nil) +} diff --git a/vendor/github.com/google/go-github/github/orgs_members.go b/vendor/github.com/google/go-github/github/orgs_members.go index ae6f57943..c326ff8a3 100644 --- a/vendor/github.com/google/go-github/github/orgs_members.go +++ b/vendor/github.com/google/go-github/github/orgs_members.go @@ -15,7 +15,16 @@ type Membership struct { // Possible values are: "active", "pending" State *string `json:"state,omitempty"` - // TODO(willnorris): add docs + // Role identifies the user's role within the organization or team. + // Possible values for organization membership: + // member - non-owner organization member + // admin - organization owner + // + // Possible values for team membership are: + // member - a normal member of the team + // maintainer - a team maintainer. Able to add/remove other team + // members, promote other team members to team + // maintainer, and edit the team’s name and description Role *string `json:"role,omitempty"` // For organization membership, the API URL of the organization. @@ -43,6 +52,15 @@ type ListMembersOptions struct { // 2fa_disabled, all. Default is "all". Filter string `url:"filter,omitempty"` + // Role filters memebers returned by their role in the organization. + // Possible values are: + // all - all members of the organization, regardless of role + // admin - organization owners + // member - non-organization members + // + // Default is "all". + Role string `url:"role,omitempty"` + ListOptions } @@ -68,6 +86,10 @@ func (s *OrganizationsService) ListMembers(org string, opt *ListMembersOptions) return nil, nil, err } + if opt != nil && opt.Role != "" { + req.Header.Set("Accept", mediaTypeOrgPermissionPreview) + } + members := new([]User) resp, err := s.client.Do(req, members) if err != nil { @@ -120,7 +142,8 @@ func (s *OrganizationsService) RemoveMember(org, user string) (*Response, error) return s.client.Do(req, nil) } -// PublicizeMembership publicizes a user's membership in an organization. +// PublicizeMembership publicizes a user's membership in an organization. (A +// user cannot publicize the membership for another user.) // // GitHub API docs: http://developer.github.com/v3/orgs/members/#publicize-a-users-membership func (s *OrganizationsService) PublicizeMembership(org, user string) (*Response, error) { @@ -149,7 +172,7 @@ func (s *OrganizationsService) ConcealMembership(org, user string) (*Response, e // ListOrgMembershipsOptions specifies optional parameters to the // OrganizationsService.ListOrgMemberships method. type ListOrgMembershipsOptions struct { - // Filter memberships to include only those withe the specified state. + // Filter memberships to include only those with the specified state. // Possible values are: "active", "pending". State string `url:"state,omitempty"` @@ -171,9 +194,6 @@ func (s *OrganizationsService) ListOrgMemberships(opt *ListOrgMembershipsOptions return nil, nil, err } - // TODO: remove custom Accept header when this API fully launches - req.Header.Set("Accept", mediaTypeMembershipPreview) - var memberships []Membership resp, err := s.client.Do(req, &memberships) if err != nil { @@ -183,20 +203,25 @@ func (s *OrganizationsService) ListOrgMemberships(opt *ListOrgMembershipsOptions return memberships, resp, err } -// GetOrgMembership gets the membership for the authenticated user for the -// specified organization. +// GetOrgMembership gets the membership for a user in a specified organization. +// Passing an empty string for user will get the membership for the +// authenticated user. // +// GitHub API docs: https://developer.github.com/v3/orgs/members/#get-organization-membership // GitHub API docs: https://developer.github.com/v3/orgs/members/#get-your-organization-membership -func (s *OrganizationsService) GetOrgMembership(org string) (*Membership, *Response, error) { - u := fmt.Sprintf("user/memberships/orgs/%v", org) +func (s *OrganizationsService) GetOrgMembership(user, org string) (*Membership, *Response, error) { + var u string + if user != "" { + u = fmt.Sprintf("orgs/%v/memberships/%v", org, user) + } else { + u = fmt.Sprintf("user/memberships/orgs/%v", org) + } + req, err := s.client.NewRequest("GET", u, nil) if err != nil { return nil, nil, err } - // TODO: remove custom Accept header when this API fully launches - req.Header.Set("Accept", mediaTypeMembershipPreview) - membership := new(Membership) resp, err := s.client.Do(req, membership) if err != nil { @@ -206,20 +231,27 @@ func (s *OrganizationsService) GetOrgMembership(org string) (*Membership, *Respo return membership, resp, err } -// EditOrgMembership edits the membership for the authenticated user for the -// specified organization. +// EditOrgMembership edits the membership for user in specified organization. +// Passing an empty string for user will edit the membership for the +// authenticated user. // +// GitHub API docs: https://developer.github.com/v3/orgs/members/#add-or-update-organization-membership // GitHub API docs: https://developer.github.com/v3/orgs/members/#edit-your-organization-membership -func (s *OrganizationsService) EditOrgMembership(org string, membership *Membership) (*Membership, *Response, error) { - u := fmt.Sprintf("user/memberships/orgs/%v", org) - req, err := s.client.NewRequest("PATCH", u, membership) +func (s *OrganizationsService) EditOrgMembership(user, org string, membership *Membership) (*Membership, *Response, error) { + var u, method string + if user != "" { + u = fmt.Sprintf("orgs/%v/memberships/%v", org, user) + method = "PUT" + } else { + u = fmt.Sprintf("user/memberships/orgs/%v", org) + method = "PATCH" + } + + req, err := s.client.NewRequest(method, u, membership) if err != nil { return nil, nil, err } - // TODO: remove custom Accept header when this API fully launches - req.Header.Set("Accept", mediaTypeMembershipPreview) - m := new(Membership) resp, err := s.client.Do(req, m) if err != nil { @@ -228,3 +260,17 @@ func (s *OrganizationsService) EditOrgMembership(org string, membership *Members return m, resp, err } + +// RemoveOrgMembership removes user from the specified organization. If the +// user has been invited to the organization, this will cancel their invitation. +// +// GitHub API docs: https://developer.github.com/v3/orgs/members/#remove-organization-membership +func (s *OrganizationsService) RemoveOrgMembership(user, org string) (*Response, error) { + u := fmt.Sprintf("orgs/%v/memberships/%v", org, user) + req, err := s.client.NewRequest("DELETE", u, nil) + if err != nil { + return nil, err + } + + return s.client.Do(req, nil) +} diff --git a/vendor/github.com/google/go-github/github/orgs_members_test.go b/vendor/github.com/google/go-github/github/orgs_members_test.go deleted file mode 100644 index 85cb98718..000000000 --- a/vendor/github.com/google/go-github/github/orgs_members_test.go +++ /dev/null @@ -1,292 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestOrganizationsService_ListMembers(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/orgs/o/members", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "filter": "2fa_disabled", - "page": "2", - }) - fmt.Fprint(w, `[{"id":1}]`) - }) - - opt := &ListMembersOptions{ - PublicOnly: false, - Filter: "2fa_disabled", - ListOptions: ListOptions{Page: 2}, - } - members, _, err := client.Organizations.ListMembers("o", opt) - if err != nil { - t.Errorf("Organizations.ListMembers returned error: %v", err) - } - - want := []User{{ID: Int(1)}} - if !reflect.DeepEqual(members, want) { - t.Errorf("Organizations.ListMembers returned %+v, want %+v", members, want) - } -} - -func TestOrganizationsService_ListMembers_invalidOrg(t *testing.T) { - _, _, err := client.Organizations.ListMembers("%", nil) - testURLParseError(t, err) -} - -func TestOrganizationsService_ListMembers_public(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/orgs/o/public_members", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `[{"id":1}]`) - }) - - opt := &ListMembersOptions{PublicOnly: true} - members, _, err := client.Organizations.ListMembers("o", opt) - if err != nil { - t.Errorf("Organizations.ListMembers returned error: %v", err) - } - - want := []User{{ID: Int(1)}} - if !reflect.DeepEqual(members, want) { - t.Errorf("Organizations.ListMembers returned %+v, want %+v", members, want) - } -} - -func TestOrganizationsService_IsMember(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/orgs/o/members/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - w.WriteHeader(http.StatusNoContent) - }) - - member, _, err := client.Organizations.IsMember("o", "u") - if err != nil { - t.Errorf("Organizations.IsMember returned error: %v", err) - } - if want := true; member != want { - t.Errorf("Organizations.IsMember returned %+v, want %+v", member, want) - } -} - -// ensure that a 404 response is interpreted as "false" and not an error -func TestOrganizationsService_IsMember_notMember(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/orgs/o/members/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - w.WriteHeader(http.StatusNotFound) - }) - - member, _, err := client.Organizations.IsMember("o", "u") - if err != nil { - t.Errorf("Organizations.IsMember returned error: %+v", err) - } - if want := false; member != want { - t.Errorf("Organizations.IsMember returned %+v, want %+v", member, want) - } -} - -// ensure that a 400 response is interpreted as an actual error, and not simply -// as "false" like the above case of a 404 -func TestOrganizationsService_IsMember_error(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/orgs/o/members/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - http.Error(w, "BadRequest", http.StatusBadRequest) - }) - - member, _, err := client.Organizations.IsMember("o", "u") - if err == nil { - t.Errorf("Expected HTTP 400 response") - } - if want := false; member != want { - t.Errorf("Organizations.IsMember returned %+v, want %+v", member, want) - } -} - -func TestOrganizationsService_IsMember_invalidOrg(t *testing.T) { - _, _, err := client.Organizations.IsMember("%", "u") - testURLParseError(t, err) -} - -func TestOrganizationsService_IsPublicMember(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/orgs/o/public_members/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - w.WriteHeader(http.StatusNoContent) - }) - - member, _, err := client.Organizations.IsPublicMember("o", "u") - if err != nil { - t.Errorf("Organizations.IsPublicMember returned error: %v", err) - } - if want := true; member != want { - t.Errorf("Organizations.IsPublicMember returned %+v, want %+v", member, want) - } -} - -// ensure that a 404 response is interpreted as "false" and not an error -func TestOrganizationsService_IsPublicMember_notMember(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/orgs/o/public_members/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - w.WriteHeader(http.StatusNotFound) - }) - - member, _, err := client.Organizations.IsPublicMember("o", "u") - if err != nil { - t.Errorf("Organizations.IsPublicMember returned error: %v", err) - } - if want := false; member != want { - t.Errorf("Organizations.IsPublicMember returned %+v, want %+v", member, want) - } -} - -// ensure that a 400 response is interpreted as an actual error, and not simply -// as "false" like the above case of a 404 -func TestOrganizationsService_IsPublicMember_error(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/orgs/o/public_members/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - http.Error(w, "BadRequest", http.StatusBadRequest) - }) - - member, _, err := client.Organizations.IsPublicMember("o", "u") - if err == nil { - t.Errorf("Expected HTTP 400 response") - } - if want := false; member != want { - t.Errorf("Organizations.IsPublicMember returned %+v, want %+v", member, want) - } -} - -func TestOrganizationsService_IsPublicMember_invalidOrg(t *testing.T) { - _, _, err := client.Organizations.IsPublicMember("%", "u") - testURLParseError(t, err) -} - -func TestOrganizationsService_RemoveMember(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/orgs/o/members/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - }) - - _, err := client.Organizations.RemoveMember("o", "u") - if err != nil { - t.Errorf("Organizations.RemoveMember returned error: %v", err) - } -} - -func TestOrganizationsService_RemoveMember_invalidOrg(t *testing.T) { - _, err := client.Organizations.RemoveMember("%", "u") - testURLParseError(t, err) -} - -func TestOrganizationsService_ListOrgMemberships(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/user/memberships/orgs", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testHeader(t, r, "Accept", mediaTypeMembershipPreview) - testFormValues(t, r, values{ - "state": "active", - "page": "2", - }) - fmt.Fprint(w, `[{"url":"u"}]`) - }) - - opt := &ListOrgMembershipsOptions{ - State: "active", - ListOptions: ListOptions{Page: 2}, - } - memberships, _, err := client.Organizations.ListOrgMemberships(opt) - if err != nil { - t.Errorf("Organizations.ListOrgMemberships returned error: %v", err) - } - - want := []Membership{{URL: String("u")}} - if !reflect.DeepEqual(memberships, want) { - t.Errorf("Organizations.ListOrgMemberships returned %+v, want %+v", memberships, want) - } -} - -func TestOrganizationsService_GetOrgMembership(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/user/memberships/orgs/o", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testHeader(t, r, "Accept", mediaTypeMembershipPreview) - fmt.Fprint(w, `{"url":"u"}`) - }) - - membership, _, err := client.Organizations.GetOrgMembership("o") - if err != nil { - t.Errorf("Organizations.GetOrgMembership returned error: %v", err) - } - - want := &Membership{URL: String("u")} - if !reflect.DeepEqual(membership, want) { - t.Errorf("Organizations.GetOrgMembership returned %+v, want %+v", membership, want) - } -} - -func TestOrganizationsService_EditOrgMembership(t *testing.T) { - setup() - defer teardown() - - input := &Membership{State: String("active")} - - mux.HandleFunc("/user/memberships/orgs/o", func(w http.ResponseWriter, r *http.Request) { - v := new(Membership) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "PATCH") - testHeader(t, r, "Accept", mediaTypeMembershipPreview) - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"url":"u"}`) - }) - - membership, _, err := client.Organizations.EditOrgMembership("o", input) - if err != nil { - t.Errorf("Organizations.EditOrgMembership returned error: %v", err) - } - - want := &Membership{URL: String("u")} - if !reflect.DeepEqual(membership, want) { - t.Errorf("Organizations.EditOrgMembership returned %+v, want %+v", membership, want) - } -} diff --git a/vendor/github.com/google/go-github/github/orgs_teams.go b/vendor/github.com/google/go-github/github/orgs_teams.go index 0c0f7dbd9..858c54510 100644 --- a/vendor/github.com/google/go-github/github/orgs_teams.go +++ b/vendor/github.com/google/go-github/github/orgs_teams.go @@ -10,11 +10,25 @@ import "fmt" // Team represents a team within a GitHub organization. Teams are used to // manage access to an organization's repositories. type Team struct { - ID *int `json:"id,omitempty"` - Name *string `json:"name,omitempty"` - URL *string `json:"url,omitempty"` - Slug *string `json:"slug,omitempty"` - Permission *string `json:"permission,omitempty"` + ID *int `json:"id,omitempty"` + Name *string `json:"name,omitempty"` + URL *string `json:"url,omitempty"` + Slug *string `json:"slug,omitempty"` + + // Permission is deprecated when creating or editing a team in an org + // using the new GitHub permission model. It no longer identifies the + // permission a team has on its repos, but only specifies the default + // permission a repo is initially added with. Avoid confusion by + // specifying a permission value when calling AddTeamRepo. + Permission *string `json:"permission,omitempty"` + + // Privacy identifies the level of privacy this team should have. + // Possible values are: + // secret - only visible to organization owners and members of this team + // closed - visible to all members of this organization + // Default is "secret". + Privacy *string `json:"privacy,omitempty"` + MembersCount *int `json:"members_count,omitempty"` ReposCount *int `json:"repos_count,omitempty"` Organization *Organization `json:"organization,omitempty"` @@ -77,6 +91,10 @@ func (s *OrganizationsService) CreateTeam(org string, team *Team) (*Team, *Respo return nil, nil, err } + if team.Privacy != nil { + req.Header.Set("Accept", mediaTypeOrgPermissionPreview) + } + t := new(Team) resp, err := s.client.Do(req, t) if err != nil { @@ -96,6 +114,10 @@ func (s *OrganizationsService) EditTeam(id int, team *Team) (*Team, *Response, e return nil, nil, err } + if team.Privacy != nil { + req.Header.Set("Accept", mediaTypeOrgPermissionPreview) + } + t := new(Team) resp, err := s.client.Do(req, t) if err != nil { @@ -118,11 +140,21 @@ func (s *OrganizationsService) DeleteTeam(team int) (*Response, error) { return s.client.Do(req, nil) } +// OrganizationListTeamMembersOptions specifies the optional parameters to the +// OrganizationsService.ListTeamMembers method. +type OrganizationListTeamMembersOptions struct { + // Role filters members returned by their role in the team. Possible + // values are "all", "member", "maintainer". Default is "all". + Role string `url:"role,omitempty"` + + ListOptions +} + // ListTeamMembers lists all of the users who are members of the specified // team. // // GitHub API docs: http://developer.github.com/v3/orgs/teams/#list-team-members -func (s *OrganizationsService) ListTeamMembers(team int, opt *ListOptions) ([]User, *Response, error) { +func (s *OrganizationsService) ListTeamMembers(team int, opt *OrganizationListTeamMembersOptions) ([]User, *Response, error) { u := fmt.Sprintf("teams/%v/members", team) u, err := addOptions(u, opt) if err != nil { @@ -134,6 +166,10 @@ func (s *OrganizationsService) ListTeamMembers(team int, opt *ListOptions) ([]Us return nil, nil, err } + if opt != nil && opt.Role != "" { + req.Header.Set("Accept", mediaTypeOrgPermissionPreview) + } + members := new([]User) resp, err := s.client.Do(req, members) if err != nil { @@ -158,32 +194,6 @@ func (s *OrganizationsService) IsTeamMember(team int, user string) (bool, *Respo return member, resp, err } -// AddTeamMember adds a user to a team. -// -// GitHub API docs: http://developer.github.com/v3/orgs/teams/#add-team-member -func (s *OrganizationsService) AddTeamMember(team int, user string) (*Response, error) { - u := fmt.Sprintf("teams/%v/members/%v", team, user) - req, err := s.client.NewRequest("PUT", u, nil) - if err != nil { - return nil, err - } - - return s.client.Do(req, nil) -} - -// RemoveTeamMember removes a user from a team. -// -// GitHub API docs: http://developer.github.com/v3/orgs/teams/#remove-team-member -func (s *OrganizationsService) RemoveTeamMember(team int, user string) (*Response, error) { - u := fmt.Sprintf("teams/%v/members/%v", team, user) - req, err := s.client.NewRequest("DELETE", u, nil) - if err != nil { - return nil, err - } - - return s.client.Do(req, nil) -} - // ListTeamRepos lists the repositories that the specified team has access to. // // GitHub API docs: http://developer.github.com/v3/orgs/teams/#list-team-repos @@ -208,19 +218,40 @@ func (s *OrganizationsService) ListTeamRepos(team int, opt *ListOptions) ([]Repo return *repos, resp, err } -// IsTeamRepo checks if a team manages the specified repository. +// IsTeamRepo checks if a team manages the specified repository. If the +// repository is managed by team, a Repository is returned which includes the +// permissions team has for that repo. // // GitHub API docs: http://developer.github.com/v3/orgs/teams/#get-team-repo -func (s *OrganizationsService) IsTeamRepo(team int, owner string, repo string) (bool, *Response, error) { +func (s *OrganizationsService) IsTeamRepo(team int, owner string, repo string) (*Repository, *Response, error) { u := fmt.Sprintf("teams/%v/repos/%v/%v", team, owner, repo) req, err := s.client.NewRequest("GET", u, nil) if err != nil { - return false, nil, err + return nil, nil, err } - resp, err := s.client.Do(req, nil) - manages, err := parseBoolResponse(err) - return manages, resp, err + req.Header.Set("Accept", mediaTypeOrgPermissionRepoPreview) + + repository := new(Repository) + resp, err := s.client.Do(req, repository) + if err != nil { + return nil, resp, err + } + + return repository, resp, err +} + +// OrganizationAddTeamRepoOptions specifies the optional parameters to the +// OrganizationsService.AddTeamRepo method. +type OrganizationAddTeamRepoOptions struct { + // Permission specifies the permission to grant the team on this repository. + // Possible values are: + // pull - team members can pull, but not push to or administer this repository + // push - team members can pull and push, but not administer this repository + // admin - team members can pull, push and administer this repository + // + // If not specified, the team's permission attribute will be used. + Permission string `json:"permission,omitempty"` } // AddTeamRepo adds a repository to be managed by the specified team. The @@ -228,13 +259,17 @@ func (s *OrganizationsService) IsTeamRepo(team int, owner string, repo string) ( // belongs, or a direct fork of a repository owned by the organization. // // GitHub API docs: http://developer.github.com/v3/orgs/teams/#add-team-repo -func (s *OrganizationsService) AddTeamRepo(team int, owner string, repo string) (*Response, error) { +func (s *OrganizationsService) AddTeamRepo(team int, owner string, repo string, opt *OrganizationAddTeamRepoOptions) (*Response, error) { u := fmt.Sprintf("teams/%v/repos/%v/%v", team, owner, repo) - req, err := s.client.NewRequest("PUT", u, nil) + req, err := s.client.NewRequest("PUT", u, opt) if err != nil { return nil, err } + if opt != nil { + req.Header.Set("Accept", mediaTypeOrgPermissionPreview) + } + return s.client.Do(req, nil) } @@ -286,9 +321,6 @@ func (s *OrganizationsService) GetTeamMembership(team int, user string) (*Member return nil, nil, err } - // TODO: remove custom Accept header when this API fully launches - req.Header.Set("Accept", mediaTypeMembershipPreview) - t := new(Membership) resp, err := s.client.Do(req, t) if err != nil { @@ -298,6 +330,20 @@ func (s *OrganizationsService) GetTeamMembership(team int, user string) (*Member return t, resp, err } +// OrganizationAddTeamMembershipOptions does stuff specifies the optional +// parameters to the OrganizationsService.AddTeamMembership method. +type OrganizationAddTeamMembershipOptions struct { + // Role specifies the role the user should have in the team. Possible + // values are: + // member - a normal member of the team + // maintainer - a team maintainer. Able to add/remove other team + // members, promote other team members to team + // maintainer, and edit the team’s name and description + // + // Default value is "member". + Role string `json:"role,omitempty"` +} + // AddTeamMembership adds or invites a user to a team. // // In order to add a membership between a user and a team, the authenticated @@ -316,15 +362,16 @@ func (s *OrganizationsService) GetTeamMembership(team int, user string) (*Member // added as a member of the team. // // GitHub API docs: https://developer.github.com/v3/orgs/teams/#add-team-membership -func (s *OrganizationsService) AddTeamMembership(team int, user string) (*Membership, *Response, error) { +func (s *OrganizationsService) AddTeamMembership(team int, user string, opt *OrganizationAddTeamMembershipOptions) (*Membership, *Response, error) { u := fmt.Sprintf("teams/%v/memberships/%v", team, user) - req, err := s.client.NewRequest("PUT", u, nil) + req, err := s.client.NewRequest("PUT", u, opt) if err != nil { return nil, nil, err } - // TODO: remove custom Accept header when this API fully launches - req.Header.Set("Accept", mediaTypeMembershipPreview) + if opt != nil { + req.Header.Set("Accept", mediaTypeOrgPermissionPreview) + } t := new(Membership) resp, err := s.client.Do(req, t) @@ -345,8 +392,5 @@ func (s *OrganizationsService) RemoveTeamMembership(team int, user string) (*Res return nil, err } - // TODO: remove custom Accept header when this API fully launches - req.Header.Set("Accept", mediaTypeMembershipPreview) - return s.client.Do(req, nil) } diff --git a/vendor/github.com/google/go-github/github/orgs_teams_test.go b/vendor/github.com/google/go-github/github/orgs_teams_test.go deleted file mode 100644 index 1f45e8c1b..000000000 --- a/vendor/github.com/google/go-github/github/orgs_teams_test.go +++ /dev/null @@ -1,517 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestOrganizationsService_ListTeams(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/orgs/o/teams", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `[{"id":1}]`) - }) - - opt := &ListOptions{Page: 2} - teams, _, err := client.Organizations.ListTeams("o", opt) - if err != nil { - t.Errorf("Organizations.ListTeams returned error: %v", err) - } - - want := []Team{{ID: Int(1)}} - if !reflect.DeepEqual(teams, want) { - t.Errorf("Organizations.ListTeams returned %+v, want %+v", teams, want) - } -} - -func TestOrganizationsService_ListTeams_invalidOrg(t *testing.T) { - _, _, err := client.Organizations.ListTeams("%", nil) - testURLParseError(t, err) -} - -func TestOrganizationsService_GetTeam(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/teams/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"id":1, "name":"n", "url":"u", "slug": "s", "permission":"p"}`) - }) - - team, _, err := client.Organizations.GetTeam(1) - if err != nil { - t.Errorf("Organizations.GetTeam returned error: %v", err) - } - - want := &Team{ID: Int(1), Name: String("n"), URL: String("u"), Slug: String("s"), Permission: String("p")} - if !reflect.DeepEqual(team, want) { - t.Errorf("Organizations.GetTeam returned %+v, want %+v", team, want) - } -} - -func TestOrganizationsService_CreateTeam(t *testing.T) { - setup() - defer teardown() - - input := &Team{Name: String("n")} - - mux.HandleFunc("/orgs/o/teams", func(w http.ResponseWriter, r *http.Request) { - v := new(Team) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "POST") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"id":1}`) - }) - - team, _, err := client.Organizations.CreateTeam("o", input) - if err != nil { - t.Errorf("Organizations.CreateTeam returned error: %v", err) - } - - want := &Team{ID: Int(1)} - if !reflect.DeepEqual(team, want) { - t.Errorf("Organizations.CreateTeam returned %+v, want %+v", team, want) - } -} - -func TestOrganizationsService_CreateTeam_invalidOrg(t *testing.T) { - _, _, err := client.Organizations.CreateTeam("%", nil) - testURLParseError(t, err) -} - -func TestOrganizationsService_EditTeam(t *testing.T) { - setup() - defer teardown() - - input := &Team{Name: String("n")} - - mux.HandleFunc("/teams/1", func(w http.ResponseWriter, r *http.Request) { - v := new(Team) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "PATCH") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"id":1}`) - }) - - team, _, err := client.Organizations.EditTeam(1, input) - if err != nil { - t.Errorf("Organizations.EditTeam returned error: %v", err) - } - - want := &Team{ID: Int(1)} - if !reflect.DeepEqual(team, want) { - t.Errorf("Organizations.EditTeam returned %+v, want %+v", team, want) - } -} - -func TestOrganizationsService_DeleteTeam(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/teams/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - }) - - _, err := client.Organizations.DeleteTeam(1) - if err != nil { - t.Errorf("Organizations.DeleteTeam returned error: %v", err) - } -} - -func TestOrganizationsService_ListTeamMembers(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/teams/1/members", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `[{"id":1}]`) - }) - - opt := &ListOptions{Page: 2} - members, _, err := client.Organizations.ListTeamMembers(1, opt) - if err != nil { - t.Errorf("Organizations.ListTeamMembers returned error: %v", err) - } - - want := []User{{ID: Int(1)}} - if !reflect.DeepEqual(members, want) { - t.Errorf("Organizations.ListTeamMembers returned %+v, want %+v", members, want) - } -} - -func TestOrganizationsService_IsTeamMember_true(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/teams/1/members/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - }) - - member, _, err := client.Organizations.IsTeamMember(1, "u") - if err != nil { - t.Errorf("Organizations.IsTeamMember returned error: %v", err) - } - if want := true; member != want { - t.Errorf("Organizations.IsTeamMember returned %+v, want %+v", member, want) - } -} - -// ensure that a 404 response is interpreted as "false" and not an error -func TestOrganizationsService_IsTeamMember_false(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/teams/1/members/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - w.WriteHeader(http.StatusNotFound) - }) - - member, _, err := client.Organizations.IsTeamMember(1, "u") - if err != nil { - t.Errorf("Organizations.IsTeamMember returned error: %+v", err) - } - if want := false; member != want { - t.Errorf("Organizations.IsTeamMember returned %+v, want %+v", member, want) - } -} - -// ensure that a 400 response is interpreted as an actual error, and not simply -// as "false" like the above case of a 404 -func TestOrganizationsService_IsTeamMember_error(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/teams/1/members/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - http.Error(w, "BadRequest", http.StatusBadRequest) - }) - - member, _, err := client.Organizations.IsTeamMember(1, "u") - if err == nil { - t.Errorf("Expected HTTP 400 response") - } - if want := false; member != want { - t.Errorf("Organizations.IsTeamMember returned %+v, want %+v", member, want) - } -} - -func TestOrganizationsService_IsTeamMember_invalidUser(t *testing.T) { - _, _, err := client.Organizations.IsTeamMember(1, "%") - testURLParseError(t, err) -} - -func TestOrganizationsService_AddTeamMember(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/teams/1/members/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "PUT") - w.WriteHeader(http.StatusNoContent) - }) - - _, err := client.Organizations.AddTeamMember(1, "u") - if err != nil { - t.Errorf("Organizations.AddTeamMember returned error: %v", err) - } -} - -func TestOrganizationsService_AddTeamMember_invalidUser(t *testing.T) { - _, err := client.Organizations.AddTeamMember(1, "%") - testURLParseError(t, err) -} - -func TestOrganizationsService_RemoveTeamMember(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/teams/1/members/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - w.WriteHeader(http.StatusNoContent) - }) - - _, err := client.Organizations.RemoveTeamMember(1, "u") - if err != nil { - t.Errorf("Organizations.RemoveTeamMember returned error: %v", err) - } -} - -func TestOrganizationsService_RemoveTeamMember_invalidUser(t *testing.T) { - _, err := client.Organizations.RemoveTeamMember(1, "%") - testURLParseError(t, err) -} - -func TestOrganizationsService_PublicizeMembership(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/orgs/o/public_members/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "PUT") - w.WriteHeader(http.StatusNoContent) - }) - - _, err := client.Organizations.PublicizeMembership("o", "u") - if err != nil { - t.Errorf("Organizations.PublicizeMembership returned error: %v", err) - } -} - -func TestOrganizationsService_PublicizeMembership_invalidOrg(t *testing.T) { - _, err := client.Organizations.PublicizeMembership("%", "u") - testURLParseError(t, err) -} - -func TestOrganizationsService_ConcealMembership(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/orgs/o/public_members/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - w.WriteHeader(http.StatusNoContent) - }) - - _, err := client.Organizations.ConcealMembership("o", "u") - if err != nil { - t.Errorf("Organizations.ConcealMembership returned error: %v", err) - } -} - -func TestOrganizationsService_ConcealMembership_invalidOrg(t *testing.T) { - _, err := client.Organizations.ConcealMembership("%", "u") - testURLParseError(t, err) -} - -func TestOrganizationsService_ListTeamRepos(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/teams/1/repos", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `[{"id":1}]`) - }) - - opt := &ListOptions{Page: 2} - members, _, err := client.Organizations.ListTeamRepos(1, opt) - if err != nil { - t.Errorf("Organizations.ListTeamRepos returned error: %v", err) - } - - want := []Repository{{ID: Int(1)}} - if !reflect.DeepEqual(members, want) { - t.Errorf("Organizations.ListTeamRepos returned %+v, want %+v", members, want) - } -} - -func TestOrganizationsService_IsTeamRepo_true(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/teams/1/repos/o/r", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - w.WriteHeader(http.StatusNoContent) - }) - - managed, _, err := client.Organizations.IsTeamRepo(1, "o", "r") - if err != nil { - t.Errorf("Organizations.IsTeamRepo returned error: %v", err) - } - if want := true; managed != want { - t.Errorf("Organizations.IsTeamRepo returned %+v, want %+v", managed, want) - } -} - -func TestOrganizationsService_IsTeamRepo_false(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/teams/1/repos/o/r", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - w.WriteHeader(http.StatusNotFound) - }) - - managed, _, err := client.Organizations.IsTeamRepo(1, "o", "r") - if err != nil { - t.Errorf("Organizations.IsTeamRepo returned error: %v", err) - } - if want := false; managed != want { - t.Errorf("Organizations.IsTeamRepo returned %+v, want %+v", managed, want) - } -} - -func TestOrganizationsService_IsTeamRepo_error(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/teams/1/repos/o/r", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - http.Error(w, "BadRequest", http.StatusBadRequest) - }) - - managed, _, err := client.Organizations.IsTeamRepo(1, "o", "r") - if err == nil { - t.Errorf("Expected HTTP 400 response") - } - if want := false; managed != want { - t.Errorf("Organizations.IsTeamRepo returned %+v, want %+v", managed, want) - } -} - -func TestOrganizationsService_IsTeamRepo_invalidOwner(t *testing.T) { - _, _, err := client.Organizations.IsTeamRepo(1, "%", "r") - testURLParseError(t, err) -} - -func TestOrganizationsService_AddTeamRepo(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/teams/1/repos/o/r", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "PUT") - w.WriteHeader(http.StatusNoContent) - }) - - _, err := client.Organizations.AddTeamRepo(1, "o", "r") - if err != nil { - t.Errorf("Organizations.AddTeamRepo returned error: %v", err) - } -} - -func TestOrganizationsService_AddTeamRepo_noAccess(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/teams/1/repos/o/r", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "PUT") - w.WriteHeader(422) - }) - - _, err := client.Organizations.AddTeamRepo(1, "o", "r") - if err == nil { - t.Errorf("Expcted error to be returned") - } -} - -func TestOrganizationsService_AddTeamRepo_invalidOwner(t *testing.T) { - _, err := client.Organizations.AddTeamRepo(1, "%", "r") - testURLParseError(t, err) -} - -func TestOrganizationsService_RemoveTeamRepo(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/teams/1/repos/o/r", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - w.WriteHeader(http.StatusNoContent) - }) - - _, err := client.Organizations.RemoveTeamRepo(1, "o", "r") - if err != nil { - t.Errorf("Organizations.RemoveTeamRepo returned error: %v", err) - } -} - -func TestOrganizationsService_RemoveTeamRepo_invalidOwner(t *testing.T) { - _, err := client.Organizations.RemoveTeamRepo(1, "%", "r") - testURLParseError(t, err) -} - -func TestOrganizationsService_GetTeamMembership(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/teams/1/memberships/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testHeader(t, r, "Accept", mediaTypeMembershipPreview) - fmt.Fprint(w, `{"url":"u", "state":"active"}`) - }) - - membership, _, err := client.Organizations.GetTeamMembership(1, "u") - if err != nil { - t.Errorf("Organizations.GetTeamMembership returned error: %v", err) - } - - want := &Membership{URL: String("u"), State: String("active")} - if !reflect.DeepEqual(membership, want) { - t.Errorf("Organizations.GetTeamMembership returned %+v, want %+v", membership, want) - } -} - -func TestOrganizationsService_AddTeamMembership(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/teams/1/memberships/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "PUT") - testHeader(t, r, "Accept", mediaTypeMembershipPreview) - fmt.Fprint(w, `{"url":"u", "state":"pending"}`) - }) - - membership, _, err := client.Organizations.AddTeamMembership(1, "u") - if err != nil { - t.Errorf("Organizations.AddTeamMembership returned error: %v", err) - } - - want := &Membership{URL: String("u"), State: String("pending")} - if !reflect.DeepEqual(membership, want) { - t.Errorf("Organizations.AddTeamMembership returned %+v, want %+v", membership, want) - } -} - -func TestOrganizationsService_RemoveTeamMembership(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/teams/1/memberships/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - testHeader(t, r, "Accept", mediaTypeMembershipPreview) - w.WriteHeader(http.StatusNoContent) - }) - - _, err := client.Organizations.RemoveTeamMembership(1, "u") - if err != nil { - t.Errorf("Organizations.RemoveTeamMembership returned error: %v", err) - } -} - -func TestOrganizationsService_ListUserTeams(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/user/teams", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "1"}) - fmt.Fprint(w, `[{"id":1}]`) - }) - - opt := &ListOptions{Page: 1} - teams, _, err := client.Organizations.ListUserTeams(opt) - if err != nil { - t.Errorf("Organizations.ListUserTeams returned error: %v", err) - } - - want := []Team{{ID: Int(1)}} - if !reflect.DeepEqual(teams, want) { - t.Errorf("Organizations.ListUserTeams returned %+v, want %+v", teams, want) - } -} diff --git a/vendor/github.com/google/go-github/github/orgs_test.go b/vendor/github.com/google/go-github/github/orgs_test.go deleted file mode 100644 index 84ebc5468..000000000 --- a/vendor/github.com/google/go-github/github/orgs_test.go +++ /dev/null @@ -1,120 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestOrganizationsService_List_authenticatedUser(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/user/orgs", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `[{"id":1},{"id":2}]`) - }) - - orgs, _, err := client.Organizations.List("", nil) - if err != nil { - t.Errorf("Organizations.List returned error: %v", err) - } - - want := []Organization{{ID: Int(1)}, {ID: Int(2)}} - if !reflect.DeepEqual(orgs, want) { - t.Errorf("Organizations.List returned %+v, want %+v", orgs, want) - } -} - -func TestOrganizationsService_List_specifiedUser(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/users/u/orgs", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `[{"id":1},{"id":2}]`) - }) - - opt := &ListOptions{Page: 2} - orgs, _, err := client.Organizations.List("u", opt) - if err != nil { - t.Errorf("Organizations.List returned error: %v", err) - } - - want := []Organization{{ID: Int(1)}, {ID: Int(2)}} - if !reflect.DeepEqual(orgs, want) { - t.Errorf("Organizations.List returned %+v, want %+v", orgs, want) - } -} - -func TestOrganizationsService_List_invalidUser(t *testing.T) { - _, _, err := client.Organizations.List("%", nil) - testURLParseError(t, err) -} - -func TestOrganizationsService_Get(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/orgs/o", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"id":1, "login":"l", "url":"u", "avatar_url": "a", "location":"l"}`) - }) - - org, _, err := client.Organizations.Get("o") - if err != nil { - t.Errorf("Organizations.Get returned error: %v", err) - } - - want := &Organization{ID: Int(1), Login: String("l"), URL: String("u"), AvatarURL: String("a"), Location: String("l")} - if !reflect.DeepEqual(org, want) { - t.Errorf("Organizations.Get returned %+v, want %+v", org, want) - } -} - -func TestOrganizationsService_Get_invalidOrg(t *testing.T) { - _, _, err := client.Organizations.Get("%") - testURLParseError(t, err) -} - -func TestOrganizationsService_Edit(t *testing.T) { - setup() - defer teardown() - - input := &Organization{Login: String("l")} - - mux.HandleFunc("/orgs/o", func(w http.ResponseWriter, r *http.Request) { - v := new(Organization) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "PATCH") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"id":1}`) - }) - - org, _, err := client.Organizations.Edit("o", input) - if err != nil { - t.Errorf("Organizations.Edit returned error: %v", err) - } - - want := &Organization{ID: Int(1)} - if !reflect.DeepEqual(org, want) { - t.Errorf("Organizations.Edit returned %+v, want %+v", org, want) - } -} - -func TestOrganizationsService_Edit_invalidOrg(t *testing.T) { - _, _, err := client.Organizations.Edit("%", nil) - testURLParseError(t, err) -} diff --git a/vendor/github.com/google/go-github/github/pulls.go b/vendor/github.com/google/go-github/github/pulls.go index 307562d70..71cf2e248 100644 --- a/vendor/github.com/google/go-github/github/pulls.go +++ b/vendor/github.com/google/go-github/github/pulls.go @@ -41,6 +41,8 @@ type PullRequest struct { HTMLURL *string `json:"html_url,omitempty"` IssueURL *string `json:"issue_url,omitempty"` StatusesURL *string `json:"statuses_url,omitempty"` + DiffURL *string `json:"diff_url,omitempty"` + PatchURL *string `json:"patch_url,omitempty"` Head *PullRequestBranch `json:"head,omitempty"` Base *PullRequestBranch `json:"base,omitempty"` @@ -73,6 +75,15 @@ type PullRequestListOptions struct { // Base filters pull requests by base branch name. Base string `url:"base,omitempty"` + // Sort specifies how to sort pull requests. Possible values are: created, + // updated, popularity, long-running. Default is "created". + Sort string `url:"sort,omitempty"` + + // Direction in which to sort pull requests. Possible values are: asc, desc. + // If Sort is "created" or not specified, Default is "desc", otherwise Default + // is "asc" + Direction string `url:"direction,omitempty"` + ListOptions } diff --git a/vendor/github.com/google/go-github/github/pulls_comments.go b/vendor/github.com/google/go-github/github/pulls_comments.go index bfbad9af2..f165d5fc6 100644 --- a/vendor/github.com/google/go-github/github/pulls_comments.go +++ b/vendor/github.com/google/go-github/github/pulls_comments.go @@ -12,14 +12,17 @@ import ( // PullRequestComment represents a comment left on a pull request. type PullRequestComment struct { - ID *int `json:"id,omitempty"` - Body *string `json:"body,omitempty"` - Path *string `json:"path,omitempty"` - Position *int `json:"position,omitempty"` - CommitID *string `json:"commit_id,omitempty"` - User *User `json:"user,omitempty"` - CreatedAt *time.Time `json:"created_at,omitempty"` - UpdatedAt *time.Time `json:"updated_at,omitempty"` + ID *int `json:"id,omitempty"` + Body *string `json:"body,omitempty"` + Path *string `json:"path,omitempty"` + DiffHunk *string `json:"diff_hunk,omitempty"` + Position *int `json:"position,omitempty"` + OriginalPosition *int `json:"original_position,omitempty"` + CommitID *string `json:"commit_id,omitempty"` + OriginalCommitID *string `json:"original_commit_id,omitempty"` + User *User `json:"user,omitempty"` + CreatedAt *time.Time `json:"created_at,omitempty"` + UpdatedAt *time.Time `json:"updated_at,omitempty"` } func (p PullRequestComment) String() string { @@ -93,7 +96,7 @@ func (s *PullRequestsService) GetComment(owner string, repo string, number int) // CreateComment creates a new comment on the specified pull request. // -// GitHub API docs: https://developer.github.com/v3/pulls/comments/#get-a-single-comment +// GitHub API docs: https://developer.github.com/v3/pulls/comments/#create-a-comment func (s *PullRequestsService) CreateComment(owner string, repo string, number int, comment *PullRequestComment) (*PullRequestComment, *Response, error) { u := fmt.Sprintf("repos/%v/%v/pulls/%d/comments", owner, repo, number) req, err := s.client.NewRequest("POST", u, comment) diff --git a/vendor/github.com/google/go-github/github/pulls_comments_test.go b/vendor/github.com/google/go-github/github/pulls_comments_test.go deleted file mode 100644 index 7885ab158..000000000 --- a/vendor/github.com/google/go-github/github/pulls_comments_test.go +++ /dev/null @@ -1,189 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" - "time" -) - -func TestPullRequestsService_ListComments_allPulls(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/pulls/comments", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "sort": "updated", - "direction": "desc", - "since": "2002-02-10T15:30:00Z", - "page": "2", - }) - fmt.Fprint(w, `[{"id":1}]`) - }) - - opt := &PullRequestListCommentsOptions{ - Sort: "updated", - Direction: "desc", - Since: time.Date(2002, time.February, 10, 15, 30, 0, 0, time.UTC), - ListOptions: ListOptions{Page: 2}, - } - pulls, _, err := client.PullRequests.ListComments("o", "r", 0, opt) - - if err != nil { - t.Errorf("PullRequests.ListComments returned error: %v", err) - } - - want := []PullRequestComment{{ID: Int(1)}} - if !reflect.DeepEqual(pulls, want) { - t.Errorf("PullRequests.ListComments returned %+v, want %+v", pulls, want) - } -} - -func TestPullRequestsService_ListComments_specificPull(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/pulls/1/comments", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `[{"id":1}]`) - }) - - pulls, _, err := client.PullRequests.ListComments("o", "r", 1, nil) - - if err != nil { - t.Errorf("PullRequests.ListComments returned error: %v", err) - } - - want := []PullRequestComment{{ID: Int(1)}} - if !reflect.DeepEqual(pulls, want) { - t.Errorf("PullRequests.ListComments returned %+v, want %+v", pulls, want) - } -} - -func TestPullRequestsService_ListComments_invalidOwner(t *testing.T) { - _, _, err := client.PullRequests.ListComments("%", "r", 1, nil) - testURLParseError(t, err) -} - -func TestPullRequestsService_GetComment(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/pulls/comments/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"id":1}`) - }) - - comment, _, err := client.PullRequests.GetComment("o", "r", 1) - - if err != nil { - t.Errorf("PullRequests.GetComment returned error: %v", err) - } - - want := &PullRequestComment{ID: Int(1)} - if !reflect.DeepEqual(comment, want) { - t.Errorf("PullRequests.GetComment returned %+v, want %+v", comment, want) - } -} - -func TestPullRequestsService_GetComment_invalidOwner(t *testing.T) { - _, _, err := client.PullRequests.GetComment("%", "r", 1) - testURLParseError(t, err) -} - -func TestPullRequestsService_CreateComment(t *testing.T) { - setup() - defer teardown() - - input := &PullRequestComment{Body: String("b")} - - mux.HandleFunc("/repos/o/r/pulls/1/comments", func(w http.ResponseWriter, r *http.Request) { - v := new(PullRequestComment) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "POST") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"id":1}`) - }) - - comment, _, err := client.PullRequests.CreateComment("o", "r", 1, input) - - if err != nil { - t.Errorf("PullRequests.CreateComment returned error: %v", err) - } - - want := &PullRequestComment{ID: Int(1)} - if !reflect.DeepEqual(comment, want) { - t.Errorf("PullRequests.CreateComment returned %+v, want %+v", comment, want) - } -} - -func TestPullRequestsService_CreateComment_invalidOwner(t *testing.T) { - _, _, err := client.PullRequests.CreateComment("%", "r", 1, nil) - testURLParseError(t, err) -} - -func TestPullRequestsService_EditComment(t *testing.T) { - setup() - defer teardown() - - input := &PullRequestComment{Body: String("b")} - - mux.HandleFunc("/repos/o/r/pulls/comments/1", func(w http.ResponseWriter, r *http.Request) { - v := new(PullRequestComment) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "PATCH") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"id":1}`) - }) - - comment, _, err := client.PullRequests.EditComment("o", "r", 1, input) - - if err != nil { - t.Errorf("PullRequests.EditComment returned error: %v", err) - } - - want := &PullRequestComment{ID: Int(1)} - if !reflect.DeepEqual(comment, want) { - t.Errorf("PullRequests.EditComment returned %+v, want %+v", comment, want) - } -} - -func TestPullRequestsService_EditComment_invalidOwner(t *testing.T) { - _, _, err := client.PullRequests.EditComment("%", "r", 1, nil) - testURLParseError(t, err) -} - -func TestPullRequestsService_DeleteComment(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/pulls/comments/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - }) - - _, err := client.PullRequests.DeleteComment("o", "r", 1) - if err != nil { - t.Errorf("PullRequests.DeleteComment returned error: %v", err) - } -} - -func TestPullRequestsService_DeleteComment_invalidOwner(t *testing.T) { - _, err := client.PullRequests.DeleteComment("%", "r", 1) - testURLParseError(t, err) -} diff --git a/vendor/github.com/google/go-github/github/pulls_test.go b/vendor/github.com/google/go-github/github/pulls_test.go deleted file mode 100644 index d0e976bc3..000000000 --- a/vendor/github.com/google/go-github/github/pulls_test.go +++ /dev/null @@ -1,340 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestPullRequestsService_List(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/pulls", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "state": "closed", - "head": "h", - "base": "b", - "page": "2", - }) - fmt.Fprint(w, `[{"number":1}]`) - }) - - opt := &PullRequestListOptions{"closed", "h", "b", ListOptions{Page: 2}} - pulls, _, err := client.PullRequests.List("o", "r", opt) - - if err != nil { - t.Errorf("PullRequests.List returned error: %v", err) - } - - want := []PullRequest{{Number: Int(1)}} - if !reflect.DeepEqual(pulls, want) { - t.Errorf("PullRequests.List returned %+v, want %+v", pulls, want) - } -} - -func TestPullRequestsService_List_invalidOwner(t *testing.T) { - _, _, err := client.PullRequests.List("%", "r", nil) - testURLParseError(t, err) -} - -func TestPullRequestsService_Get(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/pulls/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"number":1}`) - }) - - pull, _, err := client.PullRequests.Get("o", "r", 1) - - if err != nil { - t.Errorf("PullRequests.Get returned error: %v", err) - } - - want := &PullRequest{Number: Int(1)} - if !reflect.DeepEqual(pull, want) { - t.Errorf("PullRequests.Get returned %+v, want %+v", pull, want) - } -} - -func TestPullRequestsService_Get_headAndBase(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/pulls/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"number":1,"head":{"ref":"r2","repo":{"id":2}},"base":{"ref":"r1","repo":{"id":1}}}`) - }) - - pull, _, err := client.PullRequests.Get("o", "r", 1) - - if err != nil { - t.Errorf("PullRequests.Get returned error: %v", err) - } - - want := &PullRequest{ - Number: Int(1), - Head: &PullRequestBranch{ - Ref: String("r2"), - Repo: &Repository{ID: Int(2)}, - }, - Base: &PullRequestBranch{ - Ref: String("r1"), - Repo: &Repository{ID: Int(1)}, - }, - } - if !reflect.DeepEqual(pull, want) { - t.Errorf("PullRequests.Get returned %+v, want %+v", pull, want) - } -} - -func TestPullRequestsService_Get_invalidOwner(t *testing.T) { - _, _, err := client.PullRequests.Get("%", "r", 1) - testURLParseError(t, err) -} - -func TestPullRequestsService_Create(t *testing.T) { - setup() - defer teardown() - - input := &NewPullRequest{Title: String("t")} - - mux.HandleFunc("/repos/o/r/pulls", func(w http.ResponseWriter, r *http.Request) { - v := new(NewPullRequest) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "POST") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"number":1}`) - }) - - pull, _, err := client.PullRequests.Create("o", "r", input) - if err != nil { - t.Errorf("PullRequests.Create returned error: %v", err) - } - - want := &PullRequest{Number: Int(1)} - if !reflect.DeepEqual(pull, want) { - t.Errorf("PullRequests.Create returned %+v, want %+v", pull, want) - } -} - -func TestPullRequestsService_Create_invalidOwner(t *testing.T) { - _, _, err := client.PullRequests.Create("%", "r", nil) - testURLParseError(t, err) -} - -func TestPullRequestsService_Edit(t *testing.T) { - setup() - defer teardown() - - input := &PullRequest{Title: String("t")} - - mux.HandleFunc("/repos/o/r/pulls/1", func(w http.ResponseWriter, r *http.Request) { - v := new(PullRequest) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "PATCH") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"number":1}`) - }) - - pull, _, err := client.PullRequests.Edit("o", "r", 1, input) - if err != nil { - t.Errorf("PullRequests.Edit returned error: %v", err) - } - - want := &PullRequest{Number: Int(1)} - if !reflect.DeepEqual(pull, want) { - t.Errorf("PullRequests.Edit returned %+v, want %+v", pull, want) - } -} - -func TestPullRequestsService_Edit_invalidOwner(t *testing.T) { - _, _, err := client.PullRequests.Edit("%", "r", 1, nil) - testURLParseError(t, err) -} - -func TestPullRequestsService_ListCommits(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/pulls/1/commits", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, ` - [ - { - "sha": "3", - "parents": [ - { - "sha": "2" - } - ] - }, - { - "sha": "2", - "parents": [ - { - "sha": "1" - } - ] - } - ]`) - }) - - opt := &ListOptions{Page: 2} - commits, _, err := client.PullRequests.ListCommits("o", "r", 1, opt) - if err != nil { - t.Errorf("PullRequests.ListCommits returned error: %v", err) - } - - want := []RepositoryCommit{ - { - SHA: String("3"), - Parents: []Commit{ - { - SHA: String("2"), - }, - }, - }, - { - SHA: String("2"), - Parents: []Commit{ - { - SHA: String("1"), - }, - }, - }, - } - if !reflect.DeepEqual(commits, want) { - t.Errorf("PullRequests.ListCommits returned %+v, want %+v", commits, want) - } -} - -func TestPullRequestsService_ListFiles(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/pulls/1/files", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, ` - [ - { - "sha": "6dcb09b5b57875f334f61aebed695e2e4193db5e", - "filename": "file1.txt", - "status": "added", - "additions": 103, - "deletions": 21, - "changes": 124, - "patch": "@@ -132,7 +132,7 @@ module Test @@ -1000,7 +1000,7 @@ module Test" - }, - { - "sha": "f61aebed695e2e4193db5e6dcb09b5b57875f334", - "filename": "file2.txt", - "status": "modified", - "additions": 5, - "deletions": 3, - "changes": 103, - "patch": "@@ -132,7 +132,7 @@ module Test @@ -1000,7 +1000,7 @@ module Test" - } - ]`) - }) - - opt := &ListOptions{Page: 2} - commitFiles, _, err := client.PullRequests.ListFiles("o", "r", 1, opt) - if err != nil { - t.Errorf("PullRequests.ListFiles returned error: %v", err) - } - - want := []CommitFile{ - { - SHA: String("6dcb09b5b57875f334f61aebed695e2e4193db5e"), - Filename: String("file1.txt"), - Additions: Int(103), - Deletions: Int(21), - Changes: Int(124), - Status: String("added"), - Patch: String("@@ -132,7 +132,7 @@ module Test @@ -1000,7 +1000,7 @@ module Test"), - }, - { - SHA: String("f61aebed695e2e4193db5e6dcb09b5b57875f334"), - Filename: String("file2.txt"), - Additions: Int(5), - Deletions: Int(3), - Changes: Int(103), - Status: String("modified"), - Patch: String("@@ -132,7 +132,7 @@ module Test @@ -1000,7 +1000,7 @@ module Test"), - }, - } - - if !reflect.DeepEqual(commitFiles, want) { - t.Errorf("PullRequests.ListFiles returned %+v, want %+v", commitFiles, want) - } -} - -func TestPullRequestsService_IsMerged(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/pulls/1/merge", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - w.WriteHeader(http.StatusNoContent) - }) - - isMerged, _, err := client.PullRequests.IsMerged("o", "r", 1) - if err != nil { - t.Errorf("PullRequests.IsMerged returned error: %v", err) - } - - want := true - if !reflect.DeepEqual(isMerged, want) { - t.Errorf("PullRequests.IsMerged returned %+v, want %+v", isMerged, want) - } -} - -func TestPullRequestsService_Merge(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/pulls/1/merge", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "PUT") - fmt.Fprint(w, ` - { - "sha": "6dcb09b5b57875f334f61aebed695e2e4193db5e", - "merged": true, - "message": "Pull Request successfully merged" - }`) - }) - - merge, _, err := client.PullRequests.Merge("o", "r", 1, "merging pull request") - if err != nil { - t.Errorf("PullRequests.Merge returned error: %v", err) - } - - want := &PullRequestMergeResult{ - SHA: String("6dcb09b5b57875f334f61aebed695e2e4193db5e"), - Merged: Bool(true), - Message: String("Pull Request successfully merged"), - } - if !reflect.DeepEqual(merge, want) { - t.Errorf("PullRequests.Merge returned %+v, want %+v", merge, want) - } -} diff --git a/vendor/github.com/google/go-github/github/repos.go b/vendor/github.com/google/go-github/github/repos.go index 8d8d40fc1..2e9b29eec 100644 --- a/vendor/github.com/google/go-github/github/repos.go +++ b/vendor/github.com/google/go-github/github/repos.go @@ -49,6 +49,9 @@ type Repository struct { Organization *Organization `json:"organization,omitempty"` Permissions *map[string]bool `json:"permissions,omitempty"` + // Only provided when using RepositoriesService.Get while in preview + License *License `json:"license,omitempty"` + // Additional mutable fields when creating and editing a repository Private *bool `json:"private"` HasIssues *bool `json:"has_issues"` @@ -143,6 +146,9 @@ func (s *RepositoriesService) List(user string, opt *RepositoryListOptions) ([]R return nil, nil, err } + // TODO: remove custom Accept header when license support fully launches + req.Header.Set("Accept", mediaTypeLicensesPreview) + repos := new([]Repository) resp, err := s.client.Do(req, repos) if err != nil { @@ -177,6 +183,9 @@ func (s *RepositoriesService) ListByOrg(org string, opt *RepositoryListByOrgOpti return nil, nil, err } + // TODO: remove custom Accept header when license support fully launches + req.Header.Set("Accept", mediaTypeLicensesPreview) + repos := new([]Repository) resp, err := s.client.Do(req, repos) if err != nil { @@ -255,6 +264,10 @@ func (s *RepositoriesService) Get(owner, repo string) (*Repository, *Response, e return nil, nil, err } + // TODO: remove custom Accept header when the license support fully launches + // https://developer.github.com/v3/licenses/#get-a-repositorys-license + req.Header.Set("Accept", mediaTypeLicensesPreview) + repository := new(Repository) resp, err := s.client.Do(req, repository) if err != nil { diff --git a/vendor/github.com/google/go-github/github/repos_collaborators.go b/vendor/github.com/google/go-github/github/repos_collaborators.go index 3ad61622a..61dc4ef20 100644 --- a/vendor/github.com/google/go-github/github/repos_collaborators.go +++ b/vendor/github.com/google/go-github/github/repos_collaborators.go @@ -22,6 +22,8 @@ func (s *RepositoriesService) ListCollaborators(owner, repo string, opt *ListOpt return nil, nil, err } + req.Header.Set("Accept", mediaTypeOrgPermissionPreview) + users := new([]User) resp, err := s.client.Do(req, users) if err != nil { @@ -49,15 +51,33 @@ func (s *RepositoriesService) IsCollaborator(owner, repo, user string) (bool, *R return isCollab, resp, err } +// RepositoryAddCollaboratorOptions specifies the optional parameters to the +// RepositoriesService.AddCollaborator method. +type RepositoryAddCollaboratorOptions struct { + // Permission specifies the permission to grant the user on this repository. + // Possible values are: + // pull - team members can pull, but not push to or administer this repository + // push - team members can pull and push, but not administer this repository + // admin - team members can pull, push and administer this repository + // + // Default value is "pull". This option is only valid for organization-owned repositories. + Permission string `json:"permission,omitempty"` +} + // AddCollaborator adds the specified Github user as collaborator to the given repo. // // GitHub API docs: http://developer.github.com/v3/repos/collaborators/#add-collaborator -func (s *RepositoriesService) AddCollaborator(owner, repo, user string) (*Response, error) { +func (s *RepositoriesService) AddCollaborator(owner, repo, user string, opt *RepositoryAddCollaboratorOptions) (*Response, error) { u := fmt.Sprintf("repos/%v/%v/collaborators/%v", owner, repo, user) - req, err := s.client.NewRequest("PUT", u, nil) + req, err := s.client.NewRequest("PUT", u, opt) if err != nil { return nil, err } + + if opt != nil { + req.Header.Set("Accept", mediaTypeOrgPermissionPreview) + } + return s.client.Do(req, nil) } diff --git a/vendor/github.com/google/go-github/github/repos_collaborators_test.go b/vendor/github.com/google/go-github/github/repos_collaborators_test.go deleted file mode 100644 index de26ba970..000000000 --- a/vendor/github.com/google/go-github/github/repos_collaborators_test.go +++ /dev/null @@ -1,123 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestRepositoriesService_ListCollaborators(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/collaborators", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprintf(w, `[{"id":1}, {"id":2}]`) - }) - - opt := &ListOptions{Page: 2} - users, _, err := client.Repositories.ListCollaborators("o", "r", opt) - if err != nil { - t.Errorf("Repositories.ListCollaborators returned error: %v", err) - } - - want := []User{{ID: Int(1)}, {ID: Int(2)}} - if !reflect.DeepEqual(users, want) { - t.Errorf("Repositories.ListCollaborators returned %+v, want %+v", users, want) - } -} - -func TestRepositoriesService_ListCollaborators_invalidOwner(t *testing.T) { - _, _, err := client.Repositories.ListCollaborators("%", "%", nil) - testURLParseError(t, err) -} - -func TestRepositoriesService_IsCollaborator_True(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/collaborators/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - w.WriteHeader(http.StatusNoContent) - }) - - isCollab, _, err := client.Repositories.IsCollaborator("o", "r", "u") - if err != nil { - t.Errorf("Repositories.IsCollaborator returned error: %v", err) - } - - if !isCollab { - t.Errorf("Repositories.IsCollaborator returned false, want true") - } -} - -func TestRepositoriesService_IsCollaborator_False(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/collaborators/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - w.WriteHeader(http.StatusNotFound) - }) - - isCollab, _, err := client.Repositories.IsCollaborator("o", "r", "u") - if err != nil { - t.Errorf("Repositories.IsCollaborator returned error: %v", err) - } - - if isCollab { - t.Errorf("Repositories.IsCollaborator returned true, want false") - } -} - -func TestRepositoriesService_IsCollaborator_invalidUser(t *testing.T) { - _, _, err := client.Repositories.IsCollaborator("%", "%", "%") - testURLParseError(t, err) -} - -func TestRepositoriesService_AddCollaborator(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/collaborators/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "PUT") - w.WriteHeader(http.StatusNoContent) - }) - - _, err := client.Repositories.AddCollaborator("o", "r", "u") - if err != nil { - t.Errorf("Repositories.AddCollaborator returned error: %v", err) - } -} - -func TestRepositoriesService_AddCollaborator_invalidUser(t *testing.T) { - _, err := client.Repositories.AddCollaborator("%", "%", "%") - testURLParseError(t, err) -} - -func TestRepositoriesService_RemoveCollaborator(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/collaborators/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - w.WriteHeader(http.StatusNoContent) - }) - - _, err := client.Repositories.RemoveCollaborator("o", "r", "u") - if err != nil { - t.Errorf("Repositories.RemoveCollaborator returned error: %v", err) - } -} - -func TestRepositoriesService_RemoveCollaborator_invalidUser(t *testing.T) { - _, err := client.Repositories.RemoveCollaborator("%", "%", "%") - testURLParseError(t, err) -} diff --git a/vendor/github.com/google/go-github/github/repos_comments_test.go b/vendor/github.com/google/go-github/github/repos_comments_test.go deleted file mode 100644 index b5a8786a9..000000000 --- a/vendor/github.com/google/go-github/github/repos_comments_test.go +++ /dev/null @@ -1,180 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestRepositoriesService_ListComments(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/comments", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `[{"id":1}, {"id":2}]`) - }) - - opt := &ListOptions{Page: 2} - comments, _, err := client.Repositories.ListComments("o", "r", opt) - if err != nil { - t.Errorf("Repositories.ListComments returned error: %v", err) - } - - want := []RepositoryComment{{ID: Int(1)}, {ID: Int(2)}} - if !reflect.DeepEqual(comments, want) { - t.Errorf("Repositories.ListComments returned %+v, want %+v", comments, want) - } -} - -func TestRepositoriesService_ListComments_invalidOwner(t *testing.T) { - _, _, err := client.Repositories.ListComments("%", "%", nil) - testURLParseError(t, err) -} - -func TestRepositoriesService_ListCommitComments(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/commits/s/comments", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `[{"id":1}, {"id":2}]`) - }) - - opt := &ListOptions{Page: 2} - comments, _, err := client.Repositories.ListCommitComments("o", "r", "s", opt) - if err != nil { - t.Errorf("Repositories.ListCommitComments returned error: %v", err) - } - - want := []RepositoryComment{{ID: Int(1)}, {ID: Int(2)}} - if !reflect.DeepEqual(comments, want) { - t.Errorf("Repositories.ListCommitComments returned %+v, want %+v", comments, want) - } -} - -func TestRepositoriesService_ListCommitComments_invalidOwner(t *testing.T) { - _, _, err := client.Repositories.ListCommitComments("%", "%", "%", nil) - testURLParseError(t, err) -} - -func TestRepositoriesService_CreateComment(t *testing.T) { - setup() - defer teardown() - - input := &RepositoryComment{Body: String("b")} - - mux.HandleFunc("/repos/o/r/commits/s/comments", func(w http.ResponseWriter, r *http.Request) { - v := new(RepositoryComment) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "POST") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"id":1}`) - }) - - comment, _, err := client.Repositories.CreateComment("o", "r", "s", input) - if err != nil { - t.Errorf("Repositories.CreateComment returned error: %v", err) - } - - want := &RepositoryComment{ID: Int(1)} - if !reflect.DeepEqual(comment, want) { - t.Errorf("Repositories.CreateComment returned %+v, want %+v", comment, want) - } -} - -func TestRepositoriesService_CreateComment_invalidOwner(t *testing.T) { - _, _, err := client.Repositories.CreateComment("%", "%", "%", nil) - testURLParseError(t, err) -} - -func TestRepositoriesService_GetComment(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/comments/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"id":1}`) - }) - - comment, _, err := client.Repositories.GetComment("o", "r", 1) - if err != nil { - t.Errorf("Repositories.GetComment returned error: %v", err) - } - - want := &RepositoryComment{ID: Int(1)} - if !reflect.DeepEqual(comment, want) { - t.Errorf("Repositories.GetComment returned %+v, want %+v", comment, want) - } -} - -func TestRepositoriesService_GetComment_invalidOwner(t *testing.T) { - _, _, err := client.Repositories.GetComment("%", "%", 1) - testURLParseError(t, err) -} - -func TestRepositoriesService_UpdateComment(t *testing.T) { - setup() - defer teardown() - - input := &RepositoryComment{Body: String("b")} - - mux.HandleFunc("/repos/o/r/comments/1", func(w http.ResponseWriter, r *http.Request) { - v := new(RepositoryComment) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "PATCH") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"id":1}`) - }) - - comment, _, err := client.Repositories.UpdateComment("o", "r", 1, input) - if err != nil { - t.Errorf("Repositories.UpdateComment returned error: %v", err) - } - - want := &RepositoryComment{ID: Int(1)} - if !reflect.DeepEqual(comment, want) { - t.Errorf("Repositories.UpdateComment returned %+v, want %+v", comment, want) - } -} - -func TestRepositoriesService_UpdateComment_invalidOwner(t *testing.T) { - _, _, err := client.Repositories.UpdateComment("%", "%", 1, nil) - testURLParseError(t, err) -} - -func TestRepositoriesService_DeleteComment(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/comments/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - }) - - _, err := client.Repositories.DeleteComment("o", "r", 1) - if err != nil { - t.Errorf("Repositories.DeleteComment returned error: %v", err) - } -} - -func TestRepositoriesService_DeleteComment_invalidOwner(t *testing.T) { - _, err := client.Repositories.DeleteComment("%", "%", 1) - testURLParseError(t, err) -} diff --git a/vendor/github.com/google/go-github/github/repos_commits.go b/vendor/github.com/google/go-github/github/repos_commits.go index 5a5914690..6401cb4ab 100644 --- a/vendor/github.com/google/go-github/github/repos_commits.go +++ b/vendor/github.com/google/go-github/github/repos_commits.go @@ -61,7 +61,8 @@ func (c CommitFile) String() string { // CommitsComparison is the result of comparing two commits. // See CompareCommits() for details. type CommitsComparison struct { - BaseCommit *RepositoryCommit `json:"base_commit,omitempty"` + BaseCommit *RepositoryCommit `json:"base_commit,omitempty"` + MergeBaseCommit *RepositoryCommit `json:"merge_base_commit,omitempty"` // Head can be 'behind' or 'ahead' Status *string `json:"status,omitempty"` diff --git a/vendor/github.com/google/go-github/github/repos_commits_test.go b/vendor/github.com/google/go-github/github/repos_commits_test.go deleted file mode 100644 index 56ba8a5e0..000000000 --- a/vendor/github.com/google/go-github/github/repos_commits_test.go +++ /dev/null @@ -1,191 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "fmt" - "net/http" - "reflect" - "testing" - "time" -) - -func TestRepositoriesService_ListCommits(t *testing.T) { - setup() - defer teardown() - - // given - mux.HandleFunc("/repos/o/r/commits", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, - values{ - "sha": "s", - "path": "p", - "author": "a", - "since": "2013-08-01T00:00:00Z", - "until": "2013-09-03T00:00:00Z", - }) - fmt.Fprintf(w, `[{"sha": "s"}]`) - }) - - opt := &CommitsListOptions{ - SHA: "s", - Path: "p", - Author: "a", - Since: time.Date(2013, time.August, 1, 0, 0, 0, 0, time.UTC), - Until: time.Date(2013, time.September, 3, 0, 0, 0, 0, time.UTC), - } - commits, _, err := client.Repositories.ListCommits("o", "r", opt) - if err != nil { - t.Errorf("Repositories.ListCommits returned error: %v", err) - } - - want := []RepositoryCommit{{SHA: String("s")}} - if !reflect.DeepEqual(commits, want) { - t.Errorf("Repositories.ListCommits returned %+v, want %+v", commits, want) - } -} - -func TestRepositoriesService_GetCommit(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/commits/s", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprintf(w, `{ - "sha": "s", - "commit": { "message": "m" }, - "author": { "login": "l" }, - "committer": { "login": "l" }, - "parents": [ { "sha": "s" } ], - "stats": { "additions": 104, "deletions": 4, "total": 108 }, - "files": [ - { - "filename": "f", - "additions": 10, - "deletions": 2, - "changes": 12, - "status": "s", - "raw_url": "r", - "blob_url": "b", - "patch": "p" - } - ] - }`) - }) - - commit, _, err := client.Repositories.GetCommit("o", "r", "s") - if err != nil { - t.Errorf("Repositories.GetCommit returned error: %v", err) - } - - want := &RepositoryCommit{ - SHA: String("s"), - Commit: &Commit{ - Message: String("m"), - }, - Author: &User{ - Login: String("l"), - }, - Committer: &User{ - Login: String("l"), - }, - Parents: []Commit{ - { - SHA: String("s"), - }, - }, - Stats: &CommitStats{ - Additions: Int(104), - Deletions: Int(4), - Total: Int(108), - }, - Files: []CommitFile{ - { - Filename: String("f"), - Additions: Int(10), - Deletions: Int(2), - Changes: Int(12), - Status: String("s"), - Patch: String("p"), - }, - }, - } - if !reflect.DeepEqual(commit, want) { - t.Errorf("Repositories.GetCommit returned \n%+v, want \n%+v", commit, want) - } -} - -func TestRepositoriesService_CompareCommits(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/compare/b...h", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprintf(w, `{ - "base_commit": { - "sha": "s", - "commit": { - "author": { "name": "n" }, - "committer": { "name": "n" }, - "message": "m", - "tree": { "sha": "t" } - }, - "author": { "login": "n" }, - "committer": { "login": "l" }, - "parents": [ { "sha": "s" } ] - }, - "status": "s", - "ahead_by": 1, - "behind_by": 2, - "total_commits": 1, - "commits": [ - { - "sha": "s", - "commit": { "author": { "name": "n" } }, - "author": { "login": "l" }, - "committer": { "login": "l" }, - "parents": [ { "sha": "s" } ] - } - ], - "files": [ { "filename": "f" } ] - }`) - }) - - got, _, err := client.Repositories.CompareCommits("o", "r", "b", "h") - if err != nil { - t.Errorf("Repositories.CompareCommits returned error: %v", err) - } - - want := &CommitsComparison{ - Status: String("s"), - AheadBy: Int(1), - BehindBy: Int(2), - TotalCommits: Int(1), - BaseCommit: &RepositoryCommit{ - Commit: &Commit{ - Author: &CommitAuthor{Name: String("n")}, - }, - Author: &User{Login: String("l")}, - Committer: &User{Login: String("l")}, - Message: String("m"), - }, - Commits: []RepositoryCommit{ - { - SHA: String("s"), - }, - }, - Files: []CommitFile{ - { - Filename: String("f"), - }, - }, - } - - if reflect.DeepEqual(got, want) { - t.Errorf("Repositories.CompareCommits returned \n%+v, want \n%+v", got, want) - } -} diff --git a/vendor/github.com/google/go-github/github/repos_contents.go b/vendor/github.com/google/go-github/github/repos_contents.go index d17c63e8c..80776f2da 100644 --- a/vendor/github.com/google/go-github/github/repos_contents.go +++ b/vendor/github.com/google/go-github/github/repos_contents.go @@ -13,22 +13,25 @@ import ( "encoding/json" "errors" "fmt" + "io" "net/http" "net/url" + "path" ) // RepositoryContent represents a file or directory in a github repository. type RepositoryContent struct { - Type *string `json:"type,omitempty"` - Encoding *string `json:"encoding,omitempty"` - Size *int `json:"size,omitempty"` - Name *string `json:"name,omitempty"` - Path *string `json:"path,omitempty"` - Content *string `json:"content,omitempty"` - SHA *string `json:"sha,omitempty"` - URL *string `json:"url,omitempty"` - GitURL *string `json:"giturl,omitempty"` - HTMLURL *string `json:"htmlurl,omitempty"` + Type *string `json:"type,omitempty"` + Encoding *string `json:"encoding,omitempty"` + Size *int `json:"size,omitempty"` + Name *string `json:"name,omitempty"` + Path *string `json:"path,omitempty"` + Content *string `json:"content,omitempty"` + SHA *string `json:"sha,omitempty"` + URL *string `json:"url,omitempty"` + GitURL *string `json:"git_url,omitempty"` + HTMLURL *string `json:"html_url,omitempty"` + DownloadURL *string `json:"download_url,omitempty"` } // RepositoryContentResponse holds the parsed response from CreateFile, UpdateFile, and DeleteFile. @@ -90,6 +93,32 @@ func (s *RepositoriesService) GetReadme(owner, repo string, opt *RepositoryConte return readme, resp, err } +// DownloadContents returns an io.ReadCloser that reads the contents of the +// specified file. This function will work with files of any size, as opposed +// to GetContents which is limited to 1 Mb files. It is the caller's +// responsibility to close the ReadCloser. +func (s *RepositoriesService) DownloadContents(owner, repo, filepath string, opt *RepositoryContentGetOptions) (io.ReadCloser, error) { + dir := path.Dir(filepath) + filename := path.Base(filepath) + _, dirContents, _, err := s.GetContents(owner, repo, dir, opt) + if err != nil { + return nil, err + } + for _, contents := range dirContents { + if *contents.Name == filename { + if contents.DownloadURL == nil || *contents.DownloadURL == "" { + return nil, fmt.Errorf("No download link found for %s", filepath) + } + resp, err := s.client.client.Get(*contents.DownloadURL) + if err != nil { + return nil, err + } + return resp.Body, nil + } + } + return nil, fmt.Errorf("No file named %s found in %s", filename, dir) +} + // GetContents can return either the metadata and content of a single file // (when path references a file) or the metadata of all the files and/or // subdirectories of a directory (when path references a directory). To make it diff --git a/vendor/github.com/google/go-github/github/repos_contents_test.go b/vendor/github.com/google/go-github/github/repos_contents_test.go deleted file mode 100644 index 7376aea57..000000000 --- a/vendor/github.com/google/go-github/github/repos_contents_test.go +++ /dev/null @@ -1,240 +0,0 @@ -package github - -import ( - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestDecode(t *testing.T) { - setup() - defer teardown() - r := RepositoryContent{Encoding: String("base64"), Content: String("aGVsbG8=")} - o, err := r.Decode() - if err != nil { - t.Errorf("Failed to decode content.") - } - want := "hello" - if string(o) != want { - t.Errorf("RepositoryContent.Decode returned %+v, want %+v", string(o), want) - } -} - -func TestDecodeBadEncoding(t *testing.T) { - setup() - defer teardown() - r := RepositoryContent{Encoding: String("bad")} - _, err := r.Decode() - if err == nil { - t.Errorf("Should fail to decode non-base64") - } -} - -func TestRepositoriesService_GetReadme(t *testing.T) { - setup() - defer teardown() - mux.HandleFunc("/repos/o/r/readme", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{ - "type": "file", - "encoding": "base64", - "size": 5362, - "name": "README.md", - "path": "README.md" - }`) - }) - readme, _, err := client.Repositories.GetReadme("o", "r", &RepositoryContentGetOptions{}) - if err != nil { - t.Errorf("Repositories.GetReadme returned error: %v", err) - } - want := &RepositoryContent{Type: String("file"), Name: String("README.md"), Size: Int(5362), Encoding: String("base64"), Path: String("README.md")} - if !reflect.DeepEqual(readme, want) { - t.Errorf("Repositories.GetReadme returned %+v, want %+v", readme, want) - } -} - -func TestRepositoriesService_GetContent_File(t *testing.T) { - setup() - defer teardown() - mux.HandleFunc("/repos/o/r/contents/p", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{ - "type": "file", - "encoding": "base64", - "size": 20678, - "name": "LICENSE", - "path": "LICENSE" - }`) - }) - fileContents, _, _, err := client.Repositories.GetContents("o", "r", "p", &RepositoryContentGetOptions{}) - if err != nil { - t.Errorf("Repositories.GetContents_File returned error: %v", err) - } - want := &RepositoryContent{Type: String("file"), Name: String("LICENSE"), Size: Int(20678), Encoding: String("base64"), Path: String("LICENSE")} - if !reflect.DeepEqual(fileContents, want) { - t.Errorf("Repositories.GetContents returned %+v, want %+v", fileContents, want) - } -} - -func TestRepositoriesService_GetContent_Directory(t *testing.T) { - setup() - defer teardown() - mux.HandleFunc("/repos/o/r/contents/p", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `[{ - "type": "dir", - "name": "lib", - "path": "lib" - }, - { - "type": "file", - "size": 20678, - "name": "LICENSE", - "path": "LICENSE" - }]`) - }) - _, directoryContents, _, err := client.Repositories.GetContents("o", "r", "p", &RepositoryContentGetOptions{}) - if err != nil { - t.Errorf("Repositories.GetContents_Directory returned error: %v", err) - } - want := []*RepositoryContent{{Type: String("dir"), Name: String("lib"), Path: String("lib")}, - {Type: String("file"), Name: String("LICENSE"), Size: Int(20678), Path: String("LICENSE")}} - if !reflect.DeepEqual(directoryContents, want) { - t.Errorf("Repositories.GetContents_Directory returned %+v, want %+v", directoryContents, want) - } -} - -func TestRepositoriesService_CreateFile(t *testing.T) { - setup() - defer teardown() - mux.HandleFunc("/repos/o/r/contents/p", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "PUT") - fmt.Fprint(w, `{ - "content":{ - "name":"p" - }, - "commit":{ - "message":"m", - "sha":"f5f369044773ff9c6383c087466d12adb6fa0828" - } - }`) - }) - message := "m" - content := []byte("c") - repositoryContentsOptions := &RepositoryContentFileOptions{ - Message: &message, - Content: content, - Committer: &CommitAuthor{Name: String("n"), Email: String("e")}, - } - createResponse, _, err := client.Repositories.CreateFile("o", "r", "p", repositoryContentsOptions) - if err != nil { - t.Errorf("Repositories.CreateFile returned error: %v", err) - } - want := &RepositoryContentResponse{ - Content: &RepositoryContent{Name: String("p")}, - Commit: Commit{ - Message: String("m"), - SHA: String("f5f369044773ff9c6383c087466d12adb6fa0828"), - }, - } - if !reflect.DeepEqual(createResponse, want) { - t.Errorf("Repositories.CreateFile returned %+v, want %+v", createResponse, want) - } -} - -func TestRepositoriesService_UpdateFile(t *testing.T) { - setup() - defer teardown() - mux.HandleFunc("/repos/o/r/contents/p", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "PUT") - fmt.Fprint(w, `{ - "content":{ - "name":"p" - }, - "commit":{ - "message":"m", - "sha":"f5f369044773ff9c6383c087466d12adb6fa0828" - } - }`) - }) - message := "m" - content := []byte("c") - sha := "f5f369044773ff9c6383c087466d12adb6fa0828" - repositoryContentsOptions := &RepositoryContentFileOptions{ - Message: &message, - Content: content, - SHA: &sha, - Committer: &CommitAuthor{Name: String("n"), Email: String("e")}, - } - updateResponse, _, err := client.Repositories.UpdateFile("o", "r", "p", repositoryContentsOptions) - if err != nil { - t.Errorf("Repositories.UpdateFile returned error: %v", err) - } - want := &RepositoryContentResponse{ - Content: &RepositoryContent{Name: String("p")}, - Commit: Commit{ - Message: String("m"), - SHA: String("f5f369044773ff9c6383c087466d12adb6fa0828"), - }, - } - if !reflect.DeepEqual(updateResponse, want) { - t.Errorf("Repositories.UpdateFile returned %+v, want %+v", updateResponse, want) - } -} - -func TestRepositoriesService_DeleteFile(t *testing.T) { - setup() - defer teardown() - mux.HandleFunc("/repos/o/r/contents/p", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - fmt.Fprint(w, `{ - "content": null, - "commit":{ - "message":"m", - "sha":"f5f369044773ff9c6383c087466d12adb6fa0828" - } - }`) - }) - message := "m" - sha := "f5f369044773ff9c6383c087466d12adb6fa0828" - repositoryContentsOptions := &RepositoryContentFileOptions{ - Message: &message, - SHA: &sha, - Committer: &CommitAuthor{Name: String("n"), Email: String("e")}, - } - deleteResponse, _, err := client.Repositories.DeleteFile("o", "r", "p", repositoryContentsOptions) - if err != nil { - t.Errorf("Repositories.DeleteFile returned error: %v", err) - } - want := &RepositoryContentResponse{ - Content: nil, - Commit: Commit{ - Message: String("m"), - SHA: String("f5f369044773ff9c6383c087466d12adb6fa0828"), - }, - } - if !reflect.DeepEqual(deleteResponse, want) { - t.Errorf("Repositories.DeleteFile returned %+v, want %+v", deleteResponse, want) - } -} - -func TestRepositoriesService_GetArchiveLink(t *testing.T) { - setup() - defer teardown() - mux.HandleFunc("/repos/o/r/tarball", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - http.Redirect(w, r, "http://github.com/a", http.StatusFound) - }) - url, resp, err := client.Repositories.GetArchiveLink("o", "r", Tarball, &RepositoryContentGetOptions{}) - if err != nil { - t.Errorf("Repositories.GetArchiveLink returned error: %v", err) - } - if resp.StatusCode != http.StatusFound { - t.Errorf("Repositories.GetArchiveLink returned status: %d, want %d", resp.StatusCode, http.StatusFound) - } - want := "http://github.com/a" - if url.String() != want { - t.Errorf("Repositories.GetArchiveLink returned %+v, want %+v", url.String(), want) - } -} diff --git a/vendor/github.com/google/go-github/github/repos_deployments.go b/vendor/github.com/google/go-github/github/repos_deployments.go index 2fdf15a76..77c79491d 100644 --- a/vendor/github.com/google/go-github/github/repos_deployments.go +++ b/vendor/github.com/google/go-github/github/repos_deployments.go @@ -27,13 +27,13 @@ type Deployment struct { // DeploymentRequest represents a deployment request type DeploymentRequest struct { - Ref *string `json:"ref,omitempty"` - Task *string `json:"task,omitempty"` - AutoMerge *bool `json:"auto_merge,omitempty"` - RequiredContexts []string `json:"required_contexts,omitempty"` - Payload *string `json:"payload,omitempty"` - Environment *string `json:"environment,omitempty"` - Description *string `json:"description,omitempty"` + Ref *string `json:"ref,omitempty"` + Task *string `json:"task,omitempty"` + AutoMerge *bool `json:"auto_merge,omitempty"` + RequiredContexts *[]string `json:"required_contexts,omitempty"` + Payload *string `json:"payload,omitempty"` + Environment *string `json:"environment,omitempty"` + Description *string `json:"description,omitempty"` } // DeploymentsListOptions specifies the optional parameters to the @@ -69,9 +69,6 @@ func (s *RepositoriesService) ListDeployments(owner, repo string, opt *Deploymen return nil, nil, err } - // TODO: remove custom Accept header when this API fully launches - req.Header.Set("Accept", mediaTypeDeploymentPreview) - deployments := new([]Deployment) resp, err := s.client.Do(req, deployments) if err != nil { @@ -92,9 +89,6 @@ func (s *RepositoriesService) CreateDeployment(owner, repo string, request *Depl return nil, nil, err } - // TODO: remove custom Accept header when this API fully launches - req.Header.Set("Accept", mediaTypeDeploymentPreview) - d := new(Deployment) resp, err := s.client.Do(req, d) if err != nil { @@ -138,9 +132,6 @@ func (s *RepositoriesService) ListDeploymentStatuses(owner, repo string, deploym return nil, nil, err } - // TODO: remove custom Accept header when this API fully launches - req.Header.Set("Accept", mediaTypeDeploymentPreview) - statuses := new([]DeploymentStatus) resp, err := s.client.Do(req, statuses) if err != nil { @@ -161,9 +152,6 @@ func (s *RepositoriesService) CreateDeploymentStatus(owner, repo string, deploym return nil, nil, err } - // TODO: remove custom Accept header when this API fully launches - req.Header.Set("Accept", mediaTypeDeploymentPreview) - d := new(DeploymentStatus) resp, err := s.client.Do(req, d) if err != nil { diff --git a/vendor/github.com/google/go-github/github/repos_deployments_test.go b/vendor/github.com/google/go-github/github/repos_deployments_test.go deleted file mode 100644 index 161a07ccd..000000000 --- a/vendor/github.com/google/go-github/github/repos_deployments_test.go +++ /dev/null @@ -1,87 +0,0 @@ -// Copyright 2014 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestRepositoriesService_ListDeployments(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/deployments", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"environment": "test"}) - fmt.Fprint(w, `[{"id":1}, {"id":2}]`) - }) - - opt := &DeploymentsListOptions{Environment: "test"} - deployments, _, err := client.Repositories.ListDeployments("o", "r", opt) - if err != nil { - t.Errorf("Repositories.ListDeployments returned error: %v", err) - } - - want := []Deployment{{ID: Int(1)}, {ID: Int(2)}} - if !reflect.DeepEqual(deployments, want) { - t.Errorf("Repositories.ListDeployments returned %+v, want %+v", deployments, want) - } -} - -func TestRepositoriesService_CreateDeployment(t *testing.T) { - setup() - defer teardown() - - input := &DeploymentRequest{Ref: String("1111"), Task: String("deploy")} - - mux.HandleFunc("/repos/o/r/deployments", func(w http.ResponseWriter, r *http.Request) { - v := new(DeploymentRequest) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "POST") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"ref": "1111", "task": "deploy"}`) - }) - - deployment, _, err := client.Repositories.CreateDeployment("o", "r", input) - if err != nil { - t.Errorf("Repositories.CreateDeployment returned error: %v", err) - } - - want := &Deployment{Ref: String("1111"), Task: String("deploy")} - if !reflect.DeepEqual(deployment, want) { - t.Errorf("Repositories.CreateDeployment returned %+v, want %+v", deployment, want) - } -} - -func TestRepositoriesService_ListDeploymentStatuses(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/deployments/1/statuses", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `[{"id":1}, {"id":2}]`) - }) - - opt := &ListOptions{Page: 2} - statutses, _, err := client.Repositories.ListDeploymentStatuses("o", "r", 1, opt) - if err != nil { - t.Errorf("Repositories.ListDeploymentStatuses returned error: %v", err) - } - - want := []DeploymentStatus{{ID: Int(1)}, {ID: Int(2)}} - if !reflect.DeepEqual(statutses, want) { - t.Errorf("Repositories.ListDeploymentStatuses returned %+v, want %+v", statutses, want) - } -} diff --git a/vendor/github.com/google/go-github/github/repos_forks_test.go b/vendor/github.com/google/go-github/github/repos_forks_test.go deleted file mode 100644 index 965a06639..000000000 --- a/vendor/github.com/google/go-github/github/repos_forks_test.go +++ /dev/null @@ -1,73 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestRepositoriesService_ListForks(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/forks", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "sort": "newest", - "page": "3", - }) - fmt.Fprint(w, `[{"id":1},{"id":2}]`) - }) - - opt := &RepositoryListForksOptions{ - Sort: "newest", - ListOptions: ListOptions{Page: 3}, - } - repos, _, err := client.Repositories.ListForks("o", "r", opt) - if err != nil { - t.Errorf("Repositories.ListForks returned error: %v", err) - } - - want := []Repository{{ID: Int(1)}, {ID: Int(2)}} - if !reflect.DeepEqual(repos, want) { - t.Errorf("Repositories.ListForks returned %+v, want %+v", repos, want) - } -} - -func TestRepositoriesService_ListForks_invalidOwner(t *testing.T) { - _, _, err := client.Repositories.ListForks("%", "r", nil) - testURLParseError(t, err) -} - -func TestRepositoriesService_CreateFork(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/forks", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "POST") - testFormValues(t, r, values{"organization": "o"}) - fmt.Fprint(w, `{"id":1}`) - }) - - opt := &RepositoryCreateForkOptions{Organization: "o"} - repo, _, err := client.Repositories.CreateFork("o", "r", opt) - if err != nil { - t.Errorf("Repositories.CreateFork returned error: %v", err) - } - - want := &Repository{ID: Int(1)} - if !reflect.DeepEqual(repo, want) { - t.Errorf("Repositories.CreateFork returned %+v, want %+v", repo, want) - } -} - -func TestRepositoriesService_CreateFork_invalidOwner(t *testing.T) { - _, _, err := client.Repositories.CreateFork("%", "r", nil) - testURLParseError(t, err) -} diff --git a/vendor/github.com/google/go-github/github/repos_hooks.go b/vendor/github.com/google/go-github/github/repos_hooks.go index 846867285..bc4c8c5dd 100644 --- a/vendor/github.com/google/go-github/github/repos_hooks.go +++ b/vendor/github.com/google/go-github/github/repos_hooks.go @@ -164,6 +164,18 @@ func (s *RepositoriesService) DeleteHook(owner, repo string, id int) (*Response, return s.client.Do(req, nil) } +// PingHook triggers a 'ping' event to be sent to the Hook. +// +// GitHub API docs: https://developer.github.com/v3/repos/hooks/#ping-a-hook +func (s *RepositoriesService) PingHook(owner, repo string, id int) (*Response, error) { + u := fmt.Sprintf("repos/%v/%v/hooks/%d/pings", owner, repo, id) + req, err := s.client.NewRequest("POST", u, nil) + if err != nil { + return nil, err + } + return s.client.Do(req, nil) +} + // TestHook triggers a test Hook by github. // // GitHub API docs: http://developer.github.com/v3/repos/hooks/#test-a-push-hook @@ -176,34 +188,7 @@ func (s *RepositoriesService) TestHook(owner, repo string, id int) (*Response, e return s.client.Do(req, nil) } -// ServiceHook represents a hook that has configuration settings, a list of -// available events, and default events. -type ServiceHook struct { - Name *string `json:"name,omitempty"` - Events []string `json:"events,omitempty"` - SupportedEvents []string `json:"supported_events,omitempty"` - Schema [][]string `json:"schema,omitempty"` -} - -func (s *ServiceHook) String() string { - return Stringify(s) -} - -// ListServiceHooks lists all of the available service hooks. -// -// GitHub API docs: https://developer.github.com/webhooks/#services +// ListServiceHooks is deprecated. Use Client.ListServiceHooks instead. func (s *RepositoriesService) ListServiceHooks() ([]ServiceHook, *Response, error) { - u := "hooks" - req, err := s.client.NewRequest("GET", u, nil) - if err != nil { - return nil, nil, err - } - - hooks := new([]ServiceHook) - resp, err := s.client.Do(req, hooks) - if err != nil { - return nil, resp, err - } - - return *hooks, resp, err + return s.client.ListServiceHooks() } diff --git a/vendor/github.com/google/go-github/github/repos_hooks_test.go b/vendor/github.com/google/go-github/github/repos_hooks_test.go deleted file mode 100644 index b322e17ea..000000000 --- a/vendor/github.com/google/go-github/github/repos_hooks_test.go +++ /dev/null @@ -1,205 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestRepositoriesService_CreateHook(t *testing.T) { - setup() - defer teardown() - - input := &Hook{Name: String("t")} - - mux.HandleFunc("/repos/o/r/hooks", func(w http.ResponseWriter, r *http.Request) { - v := new(Hook) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "POST") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"id":1}`) - }) - - hook, _, err := client.Repositories.CreateHook("o", "r", input) - if err != nil { - t.Errorf("Repositories.CreateHook returned error: %v", err) - } - - want := &Hook{ID: Int(1)} - if !reflect.DeepEqual(hook, want) { - t.Errorf("Repositories.CreateHook returned %+v, want %+v", hook, want) - } -} - -func TestRepositoriesService_CreateHook_invalidOwner(t *testing.T) { - _, _, err := client.Repositories.CreateHook("%", "%", nil) - testURLParseError(t, err) -} - -func TestRepositoriesService_ListHooks(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/hooks", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `[{"id":1}, {"id":2}]`) - }) - - opt := &ListOptions{Page: 2} - - hooks, _, err := client.Repositories.ListHooks("o", "r", opt) - if err != nil { - t.Errorf("Repositories.ListHooks returned error: %v", err) - } - - want := []Hook{{ID: Int(1)}, {ID: Int(2)}} - if !reflect.DeepEqual(hooks, want) { - t.Errorf("Repositories.ListHooks returned %+v, want %+v", hooks, want) - } -} - -func TestRepositoriesService_ListHooks_invalidOwner(t *testing.T) { - _, _, err := client.Repositories.ListHooks("%", "%", nil) - testURLParseError(t, err) -} - -func TestRepositoriesService_GetHook(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/hooks/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"id":1}`) - }) - - hook, _, err := client.Repositories.GetHook("o", "r", 1) - if err != nil { - t.Errorf("Repositories.GetHook returned error: %v", err) - } - - want := &Hook{ID: Int(1)} - if !reflect.DeepEqual(hook, want) { - t.Errorf("Repositories.GetHook returned %+v, want %+v", hook, want) - } -} - -func TestRepositoriesService_GetHook_invalidOwner(t *testing.T) { - _, _, err := client.Repositories.GetHook("%", "%", 1) - testURLParseError(t, err) -} - -func TestRepositoriesService_EditHook(t *testing.T) { - setup() - defer teardown() - - input := &Hook{Name: String("t")} - - mux.HandleFunc("/repos/o/r/hooks/1", func(w http.ResponseWriter, r *http.Request) { - v := new(Hook) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "PATCH") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"id":1}`) - }) - - hook, _, err := client.Repositories.EditHook("o", "r", 1, input) - if err != nil { - t.Errorf("Repositories.EditHook returned error: %v", err) - } - - want := &Hook{ID: Int(1)} - if !reflect.DeepEqual(hook, want) { - t.Errorf("Repositories.EditHook returned %+v, want %+v", hook, want) - } -} - -func TestRepositoriesService_EditHook_invalidOwner(t *testing.T) { - _, _, err := client.Repositories.EditHook("%", "%", 1, nil) - testURLParseError(t, err) -} - -func TestRepositoriesService_DeleteHook(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/hooks/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - }) - - _, err := client.Repositories.DeleteHook("o", "r", 1) - if err != nil { - t.Errorf("Repositories.DeleteHook returned error: %v", err) - } -} - -func TestRepositoriesService_DeleteHook_invalidOwner(t *testing.T) { - _, err := client.Repositories.DeleteHook("%", "%", 1) - testURLParseError(t, err) -} - -func TestRepositoriesService_TestHook(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/hooks/1/tests", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "POST") - }) - - _, err := client.Repositories.TestHook("o", "r", 1) - if err != nil { - t.Errorf("Repositories.TestHook returned error: %v", err) - } -} - -func TestRepositoriesService_TestHook_invalidOwner(t *testing.T) { - _, err := client.Repositories.TestHook("%", "%", 1) - testURLParseError(t, err) -} - -func TestRepositoriesService_ListServiceHooks(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/hooks", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `[{ - "name":"n", - "events":["e"], - "supported_events":["s"], - "schema":[ - ["a", "b"] - ] - }]`) - }) - - hooks, _, err := client.Repositories.ListServiceHooks() - if err != nil { - t.Errorf("Repositories.ListHooks returned error: %v", err) - } - - want := []ServiceHook{{ - Name: String("n"), - Events: []string{"e"}, - SupportedEvents: []string{"s"}, - Schema: [][]string{{"a", "b"}}, - }} - if !reflect.DeepEqual(hooks, want) { - t.Errorf("Repositories.ListServiceHooks returned %+v, want %+v", hooks, want) - } -} diff --git a/vendor/github.com/google/go-github/github/repos_keys_test.go b/vendor/github.com/google/go-github/github/repos_keys_test.go deleted file mode 100644 index dcf6c55e4..000000000 --- a/vendor/github.com/google/go-github/github/repos_keys_test.go +++ /dev/null @@ -1,153 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestRepositoriesService_ListKeys(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/keys", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `[{"id":1}]`) - }) - - opt := &ListOptions{Page: 2} - keys, _, err := client.Repositories.ListKeys("o", "r", opt) - if err != nil { - t.Errorf("Repositories.ListKeys returned error: %v", err) - } - - want := []Key{{ID: Int(1)}} - if !reflect.DeepEqual(keys, want) { - t.Errorf("Repositories.ListKeys returned %+v, want %+v", keys, want) - } -} - -func TestRepositoriesService_ListKeys_invalidOwner(t *testing.T) { - _, _, err := client.Repositories.ListKeys("%", "%", nil) - testURLParseError(t, err) -} - -func TestRepositoriesService_GetKey(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/keys/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"id":1}`) - }) - - key, _, err := client.Repositories.GetKey("o", "r", 1) - if err != nil { - t.Errorf("Repositories.GetKey returned error: %v", err) - } - - want := &Key{ID: Int(1)} - if !reflect.DeepEqual(key, want) { - t.Errorf("Repositories.GetKey returned %+v, want %+v", key, want) - } -} - -func TestRepositoriesService_GetKey_invalidOwner(t *testing.T) { - _, _, err := client.Repositories.GetKey("%", "%", 1) - testURLParseError(t, err) -} - -func TestRepositoriesService_CreateKey(t *testing.T) { - setup() - defer teardown() - - input := &Key{Key: String("k"), Title: String("t")} - - mux.HandleFunc("/repos/o/r/keys", func(w http.ResponseWriter, r *http.Request) { - v := new(Key) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "POST") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"id":1}`) - }) - - key, _, err := client.Repositories.CreateKey("o", "r", input) - if err != nil { - t.Errorf("Repositories.GetKey returned error: %v", err) - } - - want := &Key{ID: Int(1)} - if !reflect.DeepEqual(key, want) { - t.Errorf("Repositories.GetKey returned %+v, want %+v", key, want) - } -} - -func TestRepositoriesService_CreateKey_invalidOwner(t *testing.T) { - _, _, err := client.Repositories.CreateKey("%", "%", nil) - testURLParseError(t, err) -} - -func TestRepositoriesService_EditKey(t *testing.T) { - setup() - defer teardown() - - input := &Key{Key: String("k"), Title: String("t")} - - mux.HandleFunc("/repos/o/r/keys/1", func(w http.ResponseWriter, r *http.Request) { - v := new(Key) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "PATCH") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"id":1}`) - }) - - key, _, err := client.Repositories.EditKey("o", "r", 1, input) - if err != nil { - t.Errorf("Repositories.EditKey returned error: %v", err) - } - - want := &Key{ID: Int(1)} - if !reflect.DeepEqual(key, want) { - t.Errorf("Repositories.EditKey returned %+v, want %+v", key, want) - } -} - -func TestRepositoriesService_EditKey_invalidOwner(t *testing.T) { - _, _, err := client.Repositories.EditKey("%", "%", 1, nil) - testURLParseError(t, err) -} - -func TestRepositoriesService_DeleteKey(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/keys/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - }) - - _, err := client.Repositories.DeleteKey("o", "r", 1) - if err != nil { - t.Errorf("Repositories.DeleteKey returned error: %v", err) - } -} - -func TestRepositoriesService_DeleteKey_invalidOwner(t *testing.T) { - _, err := client.Repositories.DeleteKey("%", "%", 1) - testURLParseError(t, err) -} diff --git a/vendor/github.com/google/go-github/github/repos_merging_test.go b/vendor/github.com/google/go-github/github/repos_merging_test.go deleted file mode 100644 index 166c5e520..000000000 --- a/vendor/github.com/google/go-github/github/repos_merging_test.go +++ /dev/null @@ -1,47 +0,0 @@ -// Copyright 2014 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestRepositoriesService_Merge(t *testing.T) { - setup() - defer teardown() - - input := &RepositoryMergeRequest{ - Base: String("b"), - Head: String("h"), - CommitMessage: String("c"), - } - - mux.HandleFunc("/repos/o/r/merges", func(w http.ResponseWriter, r *http.Request) { - v := new(RepositoryMergeRequest) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "POST") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"sha":"s"}`) - }) - - commit, _, err := client.Repositories.Merge("o", "r", input) - if err != nil { - t.Errorf("Repositories.Merge returned error: %v", err) - } - - want := &RepositoryCommit{SHA: String("s")} - if !reflect.DeepEqual(commit, want) { - t.Errorf("Repositories.Merge returned %+v, want %+v", commit, want) - } -} diff --git a/vendor/github.com/google/go-github/github/repos_pages_test.go b/vendor/github.com/google/go-github/github/repos_pages_test.go deleted file mode 100644 index 4cbc43a17..000000000 --- a/vendor/github.com/google/go-github/github/repos_pages_test.go +++ /dev/null @@ -1,73 +0,0 @@ -// Copyright 2014 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestRepositoriesService_GetPagesInfo(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/pages", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"url":"u","status":"s","cname":"c","custom_404":false}`) - }) - - page, _, err := client.Repositories.GetPagesInfo("o", "r") - if err != nil { - t.Errorf("Repositories.GetPagesInfo returned error: %v", err) - } - - want := &Pages{URL: String("u"), Status: String("s"), CNAME: String("c"), Custom404: Bool(false)} - if !reflect.DeepEqual(page, want) { - t.Errorf("Repositories.GetPagesInfo returned %+v, want %+v", page, want) - } -} - -func TestRepositoriesService_ListPagesBuilds(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/pages/builds", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `[{"url":"u","status":"s","commit":"c"}]`) - }) - - pages, _, err := client.Repositories.ListPagesBuilds("o", "r") - if err != nil { - t.Errorf("Repositories.ListPagesBuilds returned error: %v", err) - } - - want := []PagesBuild{{URL: String("u"), Status: String("s"), Commit: String("c")}} - if !reflect.DeepEqual(pages, want) { - t.Errorf("Repositories.ListPagesBuilds returned %+v, want %+v", pages, want) - } -} - -func TestRepositoriesService_GetLatestPagesBuild(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/pages/builds/latest", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"url":"u","status":"s","commit":"c"}`) - }) - - build, _, err := client.Repositories.GetLatestPagesBuild("o", "r") - if err != nil { - t.Errorf("Repositories.GetLatestPagesBuild returned error: %v", err) - } - - want := &PagesBuild{URL: String("u"), Status: String("s"), Commit: String("c")} - if !reflect.DeepEqual(build, want) { - t.Errorf("Repositories.GetLatestPagesBuild returned %+v, want %+v", build, want) - } -} diff --git a/vendor/github.com/google/go-github/github/repos_releases.go b/vendor/github.com/google/go-github/github/repos_releases.go index 140011441..4e4e2abbf 100644 --- a/vendor/github.com/google/go-github/github/repos_releases.go +++ b/vendor/github.com/google/go-github/github/repos_releases.go @@ -8,6 +8,7 @@ package github import ( "errors" "fmt" + "io" "mime" "os" "path/filepath" @@ -85,8 +86,27 @@ func (s *RepositoriesService) ListReleases(owner, repo string, opt *ListOptions) // GitHub API docs: http://developer.github.com/v3/repos/releases/#get-a-single-release func (s *RepositoriesService) GetRelease(owner, repo string, id int) (*RepositoryRelease, *Response, error) { u := fmt.Sprintf("repos/%s/%s/releases/%d", owner, repo, id) + return s.getSingleRelease(u) +} - req, err := s.client.NewRequest("GET", u, nil) +// GetLatestRelease fetches the latest published release for the repository. +// +// GitHub API docs: https://developer.github.com/v3/repos/releases/#get-the-latest-release +func (s *RepositoriesService) GetLatestRelease(owner, repo string) (*RepositoryRelease, *Response, error) { + u := fmt.Sprintf("repos/%s/%s/releases/latest", owner, repo) + return s.getSingleRelease(u) +} + +// GetReleaseByTag fetches a release with the specified tag. +// +// GitHub API docs: https://developer.github.com/v3/repos/releases/#get-a-release-by-tag-name +func (s *RepositoriesService) GetReleaseByTag(owner, repo, tag string) (*RepositoryRelease, *Response, error) { + u := fmt.Sprintf("repos/%s/%s/releases/tags/%s", owner, repo, tag) + return s.getSingleRelease(u) +} + +func (s *RepositoriesService) getSingleRelease(url string) (*RepositoryRelease, *Response, error) { + req, err := s.client.NewRequest("GET", url, nil) if err != nil { return nil, nil, err } @@ -192,6 +212,29 @@ func (s *RepositoriesService) GetReleaseAsset(owner, repo string, id int) (*Rele return asset, resp, err } +// DownloadReleaseAsset downloads a release asset. +// +// DownloadReleaseAsset returns an io.ReadCloser that reads the contents of the +// specified release asset. It is the caller's responsibility to close the ReadCloser. +// +// GitHub API docs : http://developer.github.com/v3/repos/releases/#get-a-single-release-asset +func (s *RepositoriesService) DownloadReleaseAsset(owner, repo string, id int) (io.ReadCloser, error) { + u := fmt.Sprintf("repos/%s/%s/releases/assets/%d", owner, repo, id) + + req, err := s.client.NewRequest("GET", u, nil) + if err != nil { + return nil, err + } + req.Header.Set("Accept", defaultMediaType) + + resp, err := s.client.client.Do(req) + if err != nil { + return nil, err + } + + return resp.Body, nil +} + // EditReleaseAsset edits a repository release asset. // // GitHub API docs : http://developer.github.com/v3/repos/releases/#edit-a-release-asset diff --git a/vendor/github.com/google/go-github/github/repos_releases_test.go b/vendor/github.com/google/go-github/github/repos_releases_test.go deleted file mode 100644 index 17c670235..000000000 --- a/vendor/github.com/google/go-github/github/repos_releases_test.go +++ /dev/null @@ -1,237 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "os" - "reflect" - "testing" -) - -func TestRepositoriesService_ListReleases(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/releases", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `[{"id":1}]`) - }) - - opt := &ListOptions{Page: 2} - releases, _, err := client.Repositories.ListReleases("o", "r", opt) - if err != nil { - t.Errorf("Repositories.ListReleases returned error: %v", err) - } - want := []RepositoryRelease{{ID: Int(1)}} - if !reflect.DeepEqual(releases, want) { - t.Errorf("Repositories.ListReleases returned %+v, want %+v", releases, want) - } -} - -func TestRepositoriesService_GetRelease(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/releases/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"id":1}`) - }) - - release, resp, err := client.Repositories.GetRelease("o", "r", 1) - if err != nil { - t.Errorf("Repositories.GetRelease returned error: %v\n%v", err, resp.Body) - } - - want := &RepositoryRelease{ID: Int(1)} - if !reflect.DeepEqual(release, want) { - t.Errorf("Repositories.GetRelease returned %+v, want %+v", release, want) - } -} - -func TestRepositoriesService_CreateRelease(t *testing.T) { - setup() - defer teardown() - - input := &RepositoryRelease{Name: String("v1.0")} - - mux.HandleFunc("/repos/o/r/releases", func(w http.ResponseWriter, r *http.Request) { - v := new(RepositoryRelease) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "POST") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - fmt.Fprint(w, `{"id":1}`) - }) - - release, _, err := client.Repositories.CreateRelease("o", "r", input) - if err != nil { - t.Errorf("Repositories.CreateRelease returned error: %v", err) - } - - want := &RepositoryRelease{ID: Int(1)} - if !reflect.DeepEqual(release, want) { - t.Errorf("Repositories.CreateRelease returned %+v, want %+v", release, want) - } -} - -func TestRepositoriesService_EditRelease(t *testing.T) { - setup() - defer teardown() - - input := &RepositoryRelease{Name: String("n")} - - mux.HandleFunc("/repos/o/r/releases/1", func(w http.ResponseWriter, r *http.Request) { - v := new(RepositoryRelease) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "PATCH") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - fmt.Fprint(w, `{"id":1}`) - }) - - release, _, err := client.Repositories.EditRelease("o", "r", 1, input) - if err != nil { - t.Errorf("Repositories.EditRelease returned error: %v", err) - } - want := &RepositoryRelease{ID: Int(1)} - if !reflect.DeepEqual(release, want) { - t.Errorf("Repositories.EditRelease returned = %+v, want %+v", release, want) - } -} - -func TestRepositoriesService_DeleteRelease(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/releases/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - }) - - _, err := client.Repositories.DeleteRelease("o", "r", 1) - if err != nil { - t.Errorf("Repositories.DeleteRelease returned error: %v", err) - } -} - -func TestRepositoriesService_ListReleaseAssets(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/releases/1/assets", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `[{"id":1}]`) - }) - - opt := &ListOptions{Page: 2} - assets, _, err := client.Repositories.ListReleaseAssets("o", "r", 1, opt) - if err != nil { - t.Errorf("Repositories.ListReleaseAssets returned error: %v", err) - } - want := []ReleaseAsset{{ID: Int(1)}} - if !reflect.DeepEqual(assets, want) { - t.Errorf("Repositories.ListReleaseAssets returned %+v, want %+v", assets, want) - } -} - -func TestRepositoriesService_GetReleaseAsset(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/releases/assets/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"id":1}`) - }) - - asset, _, err := client.Repositories.GetReleaseAsset("o", "r", 1) - if err != nil { - t.Errorf("Repositories.GetReleaseAsset returned error: %v", err) - } - want := &ReleaseAsset{ID: Int(1)} - if !reflect.DeepEqual(asset, want) { - t.Errorf("Repositories.GetReleaseAsset returned %+v, want %+v", asset, want) - } -} - -func TestRepositoriesService_EditReleaseAsset(t *testing.T) { - setup() - defer teardown() - - input := &ReleaseAsset{Name: String("n")} - - mux.HandleFunc("/repos/o/r/releases/assets/1", func(w http.ResponseWriter, r *http.Request) { - v := new(ReleaseAsset) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "PATCH") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - fmt.Fprint(w, `{"id":1}`) - }) - - asset, _, err := client.Repositories.EditReleaseAsset("o", "r", 1, input) - if err != nil { - t.Errorf("Repositories.EditReleaseAsset returned error: %v", err) - } - want := &ReleaseAsset{ID: Int(1)} - if !reflect.DeepEqual(asset, want) { - t.Errorf("Repositories.EditReleaseAsset returned = %+v, want %+v", asset, want) - } -} - -func TestRepositoriesService_DeleteReleaseAsset(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/releases/assets/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - }) - - _, err := client.Repositories.DeleteReleaseAsset("o", "r", 1) - if err != nil { - t.Errorf("Repositories.DeleteReleaseAsset returned error: %v", err) - } -} - -func TestRepositoriesService_UploadReleaseAsset(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/releases/1/assets", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "POST") - testHeader(t, r, "Content-Type", "text/plain; charset=utf-8") - testHeader(t, r, "Content-Length", "12") - testFormValues(t, r, values{"name": "n"}) - testBody(t, r, "Upload me !\n") - - fmt.Fprintf(w, `{"id":1}`) - }) - - file, dir, err := openTestFile("upload.txt", "Upload me !\n") - if err != nil { - t.Fatalf("Unable to create temp file: %v", err) - } - defer os.RemoveAll(dir) - - opt := &UploadOptions{Name: "n"} - asset, _, err := client.Repositories.UploadReleaseAsset("o", "r", 1, opt, file) - if err != nil { - t.Errorf("Repositories.UploadReleaseAssert returned error: %v", err) - } - want := &ReleaseAsset{ID: Int(1)} - if !reflect.DeepEqual(asset, want) { - t.Errorf("Repositories.UploadReleaseAssert returned %+v, want %+v", asset, want) - } -} diff --git a/vendor/github.com/google/go-github/github/repos_stats_test.go b/vendor/github.com/google/go-github/github/repos_stats_test.go deleted file mode 100644 index 3f9fab5ca..000000000 --- a/vendor/github.com/google/go-github/github/repos_stats_test.go +++ /dev/null @@ -1,210 +0,0 @@ -// Copyright 2014 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "fmt" - "net/http" - "reflect" - "testing" - "time" -) - -func TestRepositoriesService_ListContributorsStats(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/stats/contributors", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - - fmt.Fprint(w, ` -[ - { - "author": { - "id": 1 - }, - "total": 135, - "weeks": [ - { - "w": 1367712000, - "a": 6898, - "d": 77, - "c": 10 - } - ] - } -] -`) - }) - - stats, _, err := client.Repositories.ListContributorsStats("o", "r") - if err != nil { - t.Errorf("RepositoriesService.ListContributorsStats returned error: %v", err) - } - - want := []ContributorStats{ - { - Author: &Contributor{ - ID: Int(1), - }, - Total: Int(135), - Weeks: []WeeklyStats{ - { - Week: &Timestamp{time.Date(2013, 05, 05, 00, 00, 00, 0, time.UTC).Local()}, - Additions: Int(6898), - Deletions: Int(77), - Commits: Int(10), - }, - }, - }, - } - - if !reflect.DeepEqual(stats, want) { - t.Errorf("RepositoriesService.ListContributorsStats returned %+v, want %+v", stats, want) - } -} - -func TestRepositoriesService_ListCommitActivity(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/stats/commit_activity", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - - fmt.Fprint(w, ` -[ - { - "days": [0, 3, 26, 20, 39, 1, 0], - "total": 89, - "week": 1336280400 - } -] -`) - }) - - activity, _, err := client.Repositories.ListCommitActivity("o", "r") - if err != nil { - t.Errorf("RepositoriesService.ListCommitActivity returned error: %v", err) - } - - want := []WeeklyCommitActivity{ - { - Days: []int{0, 3, 26, 20, 39, 1, 0}, - Total: Int(89), - Week: &Timestamp{time.Date(2012, 05, 06, 05, 00, 00, 0, time.UTC).Local()}, - }, - } - - if !reflect.DeepEqual(activity, want) { - t.Errorf("RepositoriesService.ListCommitActivity returned %+v, want %+v", activity, want) - } -} - -func TestRepositoriesService_ListCodeFrequency(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/stats/code_frequency", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - - fmt.Fprint(w, `[[1302998400, 1124, -435]]`) - }) - - code, _, err := client.Repositories.ListCodeFrequency("o", "r") - if err != nil { - t.Errorf("RepositoriesService.ListCodeFrequency returned error: %v", err) - } - - want := []WeeklyStats{{ - Week: &Timestamp{time.Date(2011, 04, 17, 00, 00, 00, 0, time.UTC).Local()}, - Additions: Int(1124), - Deletions: Int(-435), - }} - - if !reflect.DeepEqual(code, want) { - t.Errorf("RepositoriesService.ListCodeFrequency returned %+v, want %+v", code, want) - } -} - -func TestRepositoriesService_Participation(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/stats/participation", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - - fmt.Fprint(w, ` -{ - "all": [ - 11,21,15,2,8,1,8,23,17,21,11,10,33, - 91,38,34,22,23,32,3,43,87,71,18,13,5, - 13,16,66,27,12,45,110,117,13,8,18,9,19, - 26,39,12,20,31,46,91,45,10,24,9,29,7 - ], - "owner": [ - 3,2,3,0,2,0,5,14,7,9,1,5,0, - 48,19,2,0,1,10,2,23,40,35,8,8,2, - 10,6,30,0,2,9,53,104,3,3,10,4,7, - 11,21,4,4,22,26,63,11,2,14,1,10,3 - ] -} -`) - }) - - participation, _, err := client.Repositories.ListParticipation("o", "r") - if err != nil { - t.Errorf("RepositoriesService.ListParticipation returned error: %v", err) - } - - want := &RepositoryParticipation{ - All: []int{ - 11, 21, 15, 2, 8, 1, 8, 23, 17, 21, 11, 10, 33, - 91, 38, 34, 22, 23, 32, 3, 43, 87, 71, 18, 13, 5, - 13, 16, 66, 27, 12, 45, 110, 117, 13, 8, 18, 9, 19, - 26, 39, 12, 20, 31, 46, 91, 45, 10, 24, 9, 29, 7, - }, - Owner: []int{ - 3, 2, 3, 0, 2, 0, 5, 14, 7, 9, 1, 5, 0, - 48, 19, 2, 0, 1, 10, 2, 23, 40, 35, 8, 8, 2, - 10, 6, 30, 0, 2, 9, 53, 104, 3, 3, 10, 4, 7, - 11, 21, 4, 4, 22, 26, 63, 11, 2, 14, 1, 10, 3, - }, - } - - if !reflect.DeepEqual(participation, want) { - t.Errorf("RepositoriesService.ListParticipation returned %+v, want %+v", participation, want) - } -} - -func TestRepositoriesService_ListPunchCard(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/stats/punch_card", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - - fmt.Fprint(w, `[ - [0, 0, 5], - [0, 1, 43], - [0, 2, 21] - ]`) - }) - - card, _, err := client.Repositories.ListPunchCard("o", "r") - if err != nil { - t.Errorf("RepositoriesService.ListPunchCard returned error: %v", err) - } - - want := []PunchCard{ - {Day: Int(0), Hour: Int(0), Commits: Int(5)}, - {Day: Int(0), Hour: Int(1), Commits: Int(43)}, - {Day: Int(0), Hour: Int(2), Commits: Int(21)}, - } - - if !reflect.DeepEqual(card, want) { - t.Errorf("RepositoriesService.ListPunchCard returned %+v, want %+v", card, want) - } -} diff --git a/vendor/github.com/google/go-github/github/repos_statuses_test.go b/vendor/github.com/google/go-github/github/repos_statuses_test.go deleted file mode 100644 index 8b230528c..000000000 --- a/vendor/github.com/google/go-github/github/repos_statuses_test.go +++ /dev/null @@ -1,96 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestRepositoriesService_ListStatuses(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/commits/r/statuses", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `[{"id":1}]`) - }) - - opt := &ListOptions{Page: 2} - statuses, _, err := client.Repositories.ListStatuses("o", "r", "r", opt) - if err != nil { - t.Errorf("Repositories.ListStatuses returned error: %v", err) - } - - want := []RepoStatus{{ID: Int(1)}} - if !reflect.DeepEqual(statuses, want) { - t.Errorf("Repositories.ListStatuses returned %+v, want %+v", statuses, want) - } -} - -func TestRepositoriesService_ListStatuses_invalidOwner(t *testing.T) { - _, _, err := client.Repositories.ListStatuses("%", "r", "r", nil) - testURLParseError(t, err) -} - -func TestRepositoriesService_CreateStatus(t *testing.T) { - setup() - defer teardown() - - input := &RepoStatus{State: String("s"), TargetURL: String("t"), Description: String("d")} - - mux.HandleFunc("/repos/o/r/statuses/r", func(w http.ResponseWriter, r *http.Request) { - v := new(RepoStatus) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "POST") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - fmt.Fprint(w, `{"id":1}`) - }) - - status, _, err := client.Repositories.CreateStatus("o", "r", "r", input) - if err != nil { - t.Errorf("Repositories.CreateStatus returned error: %v", err) - } - - want := &RepoStatus{ID: Int(1)} - if !reflect.DeepEqual(status, want) { - t.Errorf("Repositories.CreateStatus returned %+v, want %+v", status, want) - } -} - -func TestRepositoriesService_CreateStatus_invalidOwner(t *testing.T) { - _, _, err := client.Repositories.CreateStatus("%", "r", "r", nil) - testURLParseError(t, err) -} - -func TestRepositoriesService_GetCombinedStatus(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/commits/r/status", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `{"state":"success", "statuses":[{"id":1}]}`) - }) - - opt := &ListOptions{Page: 2} - status, _, err := client.Repositories.GetCombinedStatus("o", "r", "r", opt) - if err != nil { - t.Errorf("Repositories.GetCombinedStatus returned error: %v", err) - } - - want := &CombinedStatus{State: String("success"), Statuses: []RepoStatus{{ID: Int(1)}}} - if !reflect.DeepEqual(status, want) { - t.Errorf("Repositories.GetCombinedStatus returned %+v, want %+v", status, want) - } -} diff --git a/vendor/github.com/google/go-github/github/repos_test.go b/vendor/github.com/google/go-github/github/repos_test.go deleted file mode 100644 index def211975..000000000 --- a/vendor/github.com/google/go-github/github/repos_test.go +++ /dev/null @@ -1,406 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestRepositoriesService_List_authenticatedUser(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/user/repos", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `[{"id":1},{"id":2}]`) - }) - - repos, _, err := client.Repositories.List("", nil) - if err != nil { - t.Errorf("Repositories.List returned error: %v", err) - } - - want := []Repository{{ID: Int(1)}, {ID: Int(2)}} - if !reflect.DeepEqual(repos, want) { - t.Errorf("Repositories.List returned %+v, want %+v", repos, want) - } -} - -func TestRepositoriesService_List_specifiedUser(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/users/u/repos", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "type": "owner", - "sort": "created", - "direction": "asc", - "page": "2", - }) - - fmt.Fprint(w, `[{"id":1}]`) - }) - - opt := &RepositoryListOptions{"owner", "created", "asc", ListOptions{Page: 2}} - repos, _, err := client.Repositories.List("u", opt) - if err != nil { - t.Errorf("Repositories.List returned error: %v", err) - } - - want := []Repository{{ID: Int(1)}} - if !reflect.DeepEqual(repos, want) { - t.Errorf("Repositories.List returned %+v, want %+v", repos, want) - } -} - -func TestRepositoriesService_List_invalidUser(t *testing.T) { - _, _, err := client.Repositories.List("%", nil) - testURLParseError(t, err) -} - -func TestRepositoriesService_ListByOrg(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/orgs/o/repos", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "type": "forks", - "page": "2", - }) - fmt.Fprint(w, `[{"id":1}]`) - }) - - opt := &RepositoryListByOrgOptions{"forks", ListOptions{Page: 2}} - repos, _, err := client.Repositories.ListByOrg("o", opt) - if err != nil { - t.Errorf("Repositories.ListByOrg returned error: %v", err) - } - - want := []Repository{{ID: Int(1)}} - if !reflect.DeepEqual(repos, want) { - t.Errorf("Repositories.ListByOrg returned %+v, want %+v", repos, want) - } -} - -func TestRepositoriesService_ListByOrg_invalidOrg(t *testing.T) { - _, _, err := client.Repositories.ListByOrg("%", nil) - testURLParseError(t, err) -} - -func TestRepositoriesService_ListAll(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repositories", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "since": "1", - "page": "2", - "per_page": "3", - }) - fmt.Fprint(w, `[{"id":1}]`) - }) - - opt := &RepositoryListAllOptions{1, ListOptions{2, 3}} - repos, _, err := client.Repositories.ListAll(opt) - if err != nil { - t.Errorf("Repositories.ListAll returned error: %v", err) - } - - want := []Repository{{ID: Int(1)}} - if !reflect.DeepEqual(repos, want) { - t.Errorf("Repositories.ListAll returned %+v, want %+v", repos, want) - } -} - -func TestRepositoriesService_Create_user(t *testing.T) { - setup() - defer teardown() - - input := &Repository{Name: String("n")} - - mux.HandleFunc("/user/repos", func(w http.ResponseWriter, r *http.Request) { - v := new(Repository) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "POST") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"id":1}`) - }) - - repo, _, err := client.Repositories.Create("", input) - if err != nil { - t.Errorf("Repositories.Create returned error: %v", err) - } - - want := &Repository{ID: Int(1)} - if !reflect.DeepEqual(repo, want) { - t.Errorf("Repositories.Create returned %+v, want %+v", repo, want) - } -} - -func TestRepositoriesService_Create_org(t *testing.T) { - setup() - defer teardown() - - input := &Repository{Name: String("n")} - - mux.HandleFunc("/orgs/o/repos", func(w http.ResponseWriter, r *http.Request) { - v := new(Repository) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "POST") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"id":1}`) - }) - - repo, _, err := client.Repositories.Create("o", input) - if err != nil { - t.Errorf("Repositories.Create returned error: %v", err) - } - - want := &Repository{ID: Int(1)} - if !reflect.DeepEqual(repo, want) { - t.Errorf("Repositories.Create returned %+v, want %+v", repo, want) - } -} - -func TestRepositoriesService_Create_invalidOrg(t *testing.T) { - _, _, err := client.Repositories.Create("%", nil) - testURLParseError(t, err) -} - -func TestRepositoriesService_Get(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"id":1,"name":"n","description":"d","owner":{"login":"l"}}`) - }) - - repo, _, err := client.Repositories.Get("o", "r") - if err != nil { - t.Errorf("Repositories.Get returned error: %v", err) - } - - want := &Repository{ID: Int(1), Name: String("n"), Description: String("d"), Owner: &User{Login: String("l")}} - if !reflect.DeepEqual(repo, want) { - t.Errorf("Repositories.Get returned %+v, want %+v", repo, want) - } -} - -func TestRepositoriesService_Edit(t *testing.T) { - setup() - defer teardown() - - i := true - input := &Repository{HasIssues: &i} - - mux.HandleFunc("/repos/o/r", func(w http.ResponseWriter, r *http.Request) { - v := new(Repository) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "PATCH") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - fmt.Fprint(w, `{"id":1}`) - }) - - repo, _, err := client.Repositories.Edit("o", "r", input) - if err != nil { - t.Errorf("Repositories.Edit returned error: %v", err) - } - - want := &Repository{ID: Int(1)} - if !reflect.DeepEqual(repo, want) { - t.Errorf("Repositories.Edit returned %+v, want %+v", repo, want) - } -} - -func TestRepositoriesService_Delete(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - }) - - _, err := client.Repositories.Delete("o", "r") - if err != nil { - t.Errorf("Repositories.Delete returned error: %v", err) - } -} - -func TestRepositoriesService_Get_invalidOwner(t *testing.T) { - _, _, err := client.Repositories.Get("%", "r") - testURLParseError(t, err) -} - -func TestRepositoriesService_Edit_invalidOwner(t *testing.T) { - _, _, err := client.Repositories.Edit("%", "r", nil) - testURLParseError(t, err) -} - -func TestRepositoriesService_ListContributors(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/contributors", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "anon": "true", - "page": "2", - }) - fmt.Fprint(w, `[{"contributions":42}]`) - }) - - opts := &ListContributorsOptions{Anon: "true", ListOptions: ListOptions{Page: 2}} - contributors, _, err := client.Repositories.ListContributors("o", "r", opts) - - if err != nil { - t.Errorf("Repositories.ListContributors returned error: %v", err) - } - - want := []Contributor{{Contributions: Int(42)}} - if !reflect.DeepEqual(contributors, want) { - t.Errorf("Repositories.ListContributors returned %+v, want %+v", contributors, want) - } -} - -func TestRepositoriesService_ListLanguages(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/languages", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"go":1}`) - }) - - languages, _, err := client.Repositories.ListLanguages("o", "r") - if err != nil { - t.Errorf("Repositories.ListLanguages returned error: %v", err) - } - - want := map[string]int{"go": 1} - if !reflect.DeepEqual(languages, want) { - t.Errorf("Repositories.ListLanguages returned %+v, want %+v", languages, want) - } -} - -func TestRepositoriesService_ListTeams(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/teams", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `[{"id":1}]`) - }) - - opt := &ListOptions{Page: 2} - teams, _, err := client.Repositories.ListTeams("o", "r", opt) - if err != nil { - t.Errorf("Repositories.ListTeams returned error: %v", err) - } - - want := []Team{{ID: Int(1)}} - if !reflect.DeepEqual(teams, want) { - t.Errorf("Repositories.ListTeams returned %+v, want %+v", teams, want) - } -} - -func TestRepositoriesService_ListTags(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/tags", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `[{"name":"n", "commit" : {"sha" : "s", "url" : "u"}, "zipball_url": "z", "tarball_url": "t"}]`) - }) - - opt := &ListOptions{Page: 2} - tags, _, err := client.Repositories.ListTags("o", "r", opt) - if err != nil { - t.Errorf("Repositories.ListTags returned error: %v", err) - } - - want := []RepositoryTag{ - { - Name: String("n"), - Commit: &Commit{ - SHA: String("s"), - URL: String("u"), - }, - ZipballURL: String("z"), - TarballURL: String("t"), - }, - } - if !reflect.DeepEqual(tags, want) { - t.Errorf("Repositories.ListTags returned %+v, want %+v", tags, want) - } -} - -func TestRepositoriesService_ListBranches(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/branches", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `[{"name":"master", "commit" : {"sha" : "a57781", "url" : "https://api.github.com/repos/o/r/commits/a57781"}}]`) - }) - - opt := &ListOptions{Page: 2} - branches, _, err := client.Repositories.ListBranches("o", "r", opt) - if err != nil { - t.Errorf("Repositories.ListBranches returned error: %v", err) - } - - want := []Branch{{Name: String("master"), Commit: &Commit{SHA: String("a57781"), URL: String("https://api.github.com/repos/o/r/commits/a57781")}}} - if !reflect.DeepEqual(branches, want) { - t.Errorf("Repositories.ListBranches returned %+v, want %+v", branches, want) - } -} - -func TestRepositoriesService_GetBranch(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/repos/o/r/branches/b", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"name":"n", "commit":{"sha":"s"}}`) - }) - - branch, _, err := client.Repositories.GetBranch("o", "r", "b") - if err != nil { - t.Errorf("Repositories.GetBranch returned error: %v", err) - } - - want := &Branch{Name: String("n"), Commit: &Commit{SHA: String("s")}} - if !reflect.DeepEqual(branch, want) { - t.Errorf("Repositories.GetBranch returned %+v, want %+v", branch, want) - } -} - -func TestRepositoriesService_ListLanguages_invalidOwner(t *testing.T) { - _, _, err := client.Repositories.ListLanguages("%", "%") - testURLParseError(t, err) -} diff --git a/vendor/github.com/google/go-github/github/search_test.go b/vendor/github.com/google/go-github/github/search_test.go deleted file mode 100644 index 3cfd16243..000000000 --- a/vendor/github.com/google/go-github/github/search_test.go +++ /dev/null @@ -1,196 +0,0 @@ -package github - -import ( - "fmt" - "net/http" - "reflect" - - "testing" -) - -func TestSearchService_Repositories(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/search/repositories", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "q": "blah", - "sort": "forks", - "order": "desc", - "page": "2", - "per_page": "2", - }) - - fmt.Fprint(w, `{"total_count": 4, "items": [{"id":1},{"id":2}]}`) - }) - - opts := &SearchOptions{Sort: "forks", Order: "desc", ListOptions: ListOptions{Page: 2, PerPage: 2}} - result, _, err := client.Search.Repositories("blah", opts) - if err != nil { - t.Errorf("Search.Repositories returned error: %v", err) - } - - want := &RepositoriesSearchResult{ - Total: Int(4), - Repositories: []Repository{{ID: Int(1)}, {ID: Int(2)}}, - } - if !reflect.DeepEqual(result, want) { - t.Errorf("Search.Repositories returned %+v, want %+v", result, want) - } -} - -func TestSearchService_Issues(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/search/issues", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "q": "blah", - "sort": "forks", - "order": "desc", - "page": "2", - "per_page": "2", - }) - - fmt.Fprint(w, `{"total_count": 4, "items": [{"number":1},{"number":2}]}`) - }) - - opts := &SearchOptions{Sort: "forks", Order: "desc", ListOptions: ListOptions{Page: 2, PerPage: 2}} - result, _, err := client.Search.Issues("blah", opts) - if err != nil { - t.Errorf("Search.Issues returned error: %v", err) - } - - want := &IssuesSearchResult{ - Total: Int(4), - Issues: []Issue{{Number: Int(1)}, {Number: Int(2)}}, - } - if !reflect.DeepEqual(result, want) { - t.Errorf("Search.Issues returned %+v, want %+v", result, want) - } -} - -func TestSearchService_Users(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/search/users", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "q": "blah", - "sort": "forks", - "order": "desc", - "page": "2", - "per_page": "2", - }) - - fmt.Fprint(w, `{"total_count": 4, "items": [{"id":1},{"id":2}]}`) - }) - - opts := &SearchOptions{Sort: "forks", Order: "desc", ListOptions: ListOptions{Page: 2, PerPage: 2}} - result, _, err := client.Search.Users("blah", opts) - if err != nil { - t.Errorf("Search.Issues returned error: %v", err) - } - - want := &UsersSearchResult{ - Total: Int(4), - Users: []User{{ID: Int(1)}, {ID: Int(2)}}, - } - if !reflect.DeepEqual(result, want) { - t.Errorf("Search.Users returned %+v, want %+v", result, want) - } -} - -func TestSearchService_Code(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/search/code", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{ - "q": "blah", - "sort": "forks", - "order": "desc", - "page": "2", - "per_page": "2", - }) - - fmt.Fprint(w, `{"total_count": 4, "items": [{"name":"1"},{"name":"2"}]}`) - }) - - opts := &SearchOptions{Sort: "forks", Order: "desc", ListOptions: ListOptions{Page: 2, PerPage: 2}} - result, _, err := client.Search.Code("blah", opts) - if err != nil { - t.Errorf("Search.Code returned error: %v", err) - } - - want := &CodeSearchResult{ - Total: Int(4), - CodeResults: []CodeResult{{Name: String("1")}, {Name: String("2")}}, - } - if !reflect.DeepEqual(result, want) { - t.Errorf("Search.Code returned %+v, want %+v", result, want) - } -} - -func TestSearchService_CodeTextMatch(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/search/code", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - - textMatchResponse := ` - { - "total_count": 1, - "items": [ - { - "name":"gopher1", - "text_matches": [ - { - "fragment": "I'm afraid my friend what you have found\nIs a gopher who lives to feed", - "matches": [ - { - "text": "gopher", - "indices": [ - 14, - 21 - ] - } - ] - } - ] - } - ] - } - ` - - fmt.Fprint(w, textMatchResponse) - }) - - opts := &SearchOptions{Sort: "forks", Order: "desc", ListOptions: ListOptions{Page: 2, PerPage: 2}, TextMatch: true} - result, _, err := client.Search.Code("blah", opts) - if err != nil { - t.Errorf("Search.Code returned error: %v", err) - } - - wantedCodeResult := CodeResult{ - Name: String("gopher1"), - TextMatches: []TextMatch{{ - Fragment: String("I'm afraid my friend what you have found\nIs a gopher who lives to feed"), - Matches: []Match{{Text: String("gopher"), Indices: []int{14, 21}}}, - }, - }, - } - - want := &CodeSearchResult{ - Total: Int(1), - CodeResults: []CodeResult{wantedCodeResult}, - } - if !reflect.DeepEqual(result, want) { - t.Errorf("Search.Code returned %+v, want %+v", result, want) - } -} diff --git a/vendor/github.com/google/go-github/github/strings_test.go b/vendor/github.com/google/go-github/github/strings_test.go deleted file mode 100644 index a393eb6cf..000000000 --- a/vendor/github.com/google/go-github/github/strings_test.go +++ /dev/null @@ -1,137 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "fmt" - "testing" - "time" -) - -func TestStringify(t *testing.T) { - var nilPointer *string - - var tests = []struct { - in interface{} - out string - }{ - // basic types - {"foo", `"foo"`}, - {123, `123`}, - {1.5, `1.5`}, - {false, `false`}, - { - []string{"a", "b"}, - `["a" "b"]`, - }, - { - struct { - A []string - }{nil}, - // nil slice is skipped - `{}`, - }, - { - struct { - A string - }{"foo"}, - // structs not of a named type get no prefix - `{A:"foo"}`, - }, - - // pointers - {nilPointer, ``}, - {String("foo"), `"foo"`}, - {Int(123), `123`}, - {Bool(false), `false`}, - { - []*string{String("a"), String("b")}, - `["a" "b"]`, - }, - - // actual GitHub structs - { - Timestamp{time.Date(2006, 01, 02, 15, 04, 05, 0, time.UTC)}, - `github.Timestamp{2006-01-02 15:04:05 +0000 UTC}`, - }, - { - &Timestamp{time.Date(2006, 01, 02, 15, 04, 05, 0, time.UTC)}, - `github.Timestamp{2006-01-02 15:04:05 +0000 UTC}`, - }, - { - User{ID: Int(123), Name: String("n")}, - `github.User{ID:123, Name:"n"}`, - }, - { - Repository{Owner: &User{ID: Int(123)}}, - `github.Repository{Owner:github.User{ID:123}}`, - }, - } - - for i, tt := range tests { - s := Stringify(tt.in) - if s != tt.out { - t.Errorf("%d. Stringify(%q) => %q, want %q", i, tt.in, s, tt.out) - } - } -} - -// Directly test the String() methods on various GitHub types. We don't do an -// exaustive test of all the various field types, since TestStringify() above -// takes care of that. Rather, we just make sure that Stringify() is being -// used to build the strings, which we do by verifying that pointers are -// stringified as their underlying value. -func TestString(t *testing.T) { - var tests = []struct { - in interface{} - out string - }{ - {CodeResult{Name: String("n")}, `github.CodeResult{Name:"n"}`}, - {CommitAuthor{Name: String("n")}, `github.CommitAuthor{Name:"n"}`}, - {CommitFile{SHA: String("s")}, `github.CommitFile{SHA:"s"}`}, - {CommitStats{Total: Int(1)}, `github.CommitStats{Total:1}`}, - {CommitsComparison{TotalCommits: Int(1)}, `github.CommitsComparison{TotalCommits:1}`}, - {Commit{SHA: String("s")}, `github.Commit{SHA:"s"}`}, - {Event{ID: String("1")}, `github.Event{ID:"1"}`}, - {GistComment{ID: Int(1)}, `github.GistComment{ID:1}`}, - {GistFile{Size: Int(1)}, `github.GistFile{Size:1}`}, - {Gist{ID: String("1")}, `github.Gist{ID:"1", Files:map[]}`}, - {GitObject{SHA: String("s")}, `github.GitObject{SHA:"s"}`}, - {Gitignore{Name: String("n")}, `github.Gitignore{Name:"n"}`}, - {Hook{ID: Int(1)}, `github.Hook{Config:map[], ID:1}`}, - {IssueComment{ID: Int(1)}, `github.IssueComment{ID:1}`}, - {Issue{Number: Int(1)}, `github.Issue{Number:1}`}, - {Key{ID: Int(1)}, `github.Key{ID:1}`}, - {Label{Name: String("l")}, "l"}, - {Organization{ID: Int(1)}, `github.Organization{ID:1}`}, - {PullRequestComment{ID: Int(1)}, `github.PullRequestComment{ID:1}`}, - {PullRequest{Number: Int(1)}, `github.PullRequest{Number:1}`}, - {PushEventCommit{SHA: String("s")}, `github.PushEventCommit{SHA:"s"}`}, - {PushEvent{PushID: Int(1)}, `github.PushEvent{PushID:1}`}, - {Reference{Ref: String("r")}, `github.Reference{Ref:"r"}`}, - {ReleaseAsset{ID: Int(1)}, `github.ReleaseAsset{ID:1}`}, - {RepoStatus{ID: Int(1)}, `github.RepoStatus{ID:1}`}, - {RepositoryComment{ID: Int(1)}, `github.RepositoryComment{ID:1}`}, - {RepositoryCommit{SHA: String("s")}, `github.RepositoryCommit{SHA:"s"}`}, - {RepositoryContent{Name: String("n")}, `github.RepositoryContent{Name:"n"}`}, - {RepositoryRelease{ID: Int(1)}, `github.RepositoryRelease{ID:1}`}, - {Repository{ID: Int(1)}, `github.Repository{ID:1}`}, - {Team{ID: Int(1)}, `github.Team{ID:1}`}, - {TreeEntry{SHA: String("s")}, `github.TreeEntry{SHA:"s"}`}, - {Tree{SHA: String("s")}, `github.Tree{SHA:"s"}`}, - {User{ID: Int(1)}, `github.User{ID:1}`}, - {WebHookAuthor{Name: String("n")}, `github.WebHookAuthor{Name:"n"}`}, - {WebHookCommit{ID: String("1")}, `github.WebHookCommit{ID:"1"}`}, - {WebHookPayload{Ref: String("r")}, `github.WebHookPayload{Ref:"r"}`}, - } - - for i, tt := range tests { - s := tt.in.(fmt.Stringer).String() - if s != tt.out { - t.Errorf("%d. String() => %q, want %q", i, tt.in, tt.out) - } - } -} diff --git a/vendor/github.com/google/go-github/github/timestamp_test.go b/vendor/github.com/google/go-github/github/timestamp_test.go deleted file mode 100644 index 12376c51a..000000000 --- a/vendor/github.com/google/go-github/github/timestamp_test.go +++ /dev/null @@ -1,181 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "testing" - "time" -) - -const ( - emptyTimeStr = `"0001-01-01T00:00:00Z"` - referenceTimeStr = `"2006-01-02T15:04:05Z"` - referenceUnixTimeStr = `1136214245` -) - -var ( - referenceTime = time.Date(2006, 01, 02, 15, 04, 05, 0, time.UTC) - unixOrigin = time.Unix(0, 0).In(time.UTC) -) - -func TestTimestamp_Marshal(t *testing.T) { - testCases := []struct { - desc string - data Timestamp - want string - wantErr bool - equal bool - }{ - {"Reference", Timestamp{referenceTime}, referenceTimeStr, false, true}, - {"Empty", Timestamp{}, emptyTimeStr, false, true}, - {"Mismatch", Timestamp{}, referenceTimeStr, false, false}, - } - for _, tc := range testCases { - out, err := json.Marshal(tc.data) - if gotErr := err != nil; gotErr != tc.wantErr { - t.Errorf("%s: gotErr=%v, wantErr=%v, err=%v", tc.desc, gotErr, tc.wantErr, err) - } - got := string(out) - equal := got == tc.want - if (got == tc.want) != tc.equal { - t.Errorf("%s: got=%s, want=%s, equal=%v, want=%v", tc.desc, got, tc.want, equal, tc.equal) - } - } -} - -func TestTimestamp_Unmarshal(t *testing.T) { - testCases := []struct { - desc string - data string - want Timestamp - wantErr bool - equal bool - }{ - {"Reference", referenceTimeStr, Timestamp{referenceTime}, false, true}, - {"ReferenceUnix", `1136214245`, Timestamp{referenceTime}, false, true}, - {"Empty", emptyTimeStr, Timestamp{}, false, true}, - {"UnixStart", `0`, Timestamp{unixOrigin}, false, true}, - {"Mismatch", referenceTimeStr, Timestamp{}, false, false}, - {"MismatchUnix", `0`, Timestamp{}, false, false}, - {"Invalid", `"asdf"`, Timestamp{referenceTime}, true, false}, - } - for _, tc := range testCases { - var got Timestamp - err := json.Unmarshal([]byte(tc.data), &got) - if gotErr := err != nil; gotErr != tc.wantErr { - t.Errorf("%s: gotErr=%v, wantErr=%v, err=%v", tc.desc, gotErr, tc.wantErr, err) - continue - } - equal := got.Equal(tc.want) - if equal != tc.equal { - t.Errorf("%s: got=%#v, want=%#v, equal=%v, want=%v", tc.desc, got, tc.want, equal, tc.equal) - } - } -} - -func TestTimstamp_MarshalReflexivity(t *testing.T) { - testCases := []struct { - desc string - data Timestamp - }{ - {"Reference", Timestamp{referenceTime}}, - {"Empty", Timestamp{}}, - } - for _, tc := range testCases { - data, err := json.Marshal(tc.data) - if err != nil { - t.Errorf("%s: Marshal err=%v", tc.desc, err) - } - var got Timestamp - err = json.Unmarshal(data, &got) - if !got.Equal(tc.data) { - t.Errorf("%s: %+v != %+v", tc.desc, got, data) - } - } -} - -type WrappedTimestamp struct { - A int - Time Timestamp -} - -func TestWrappedTimstamp_Marshal(t *testing.T) { - testCases := []struct { - desc string - data WrappedTimestamp - want string - wantErr bool - equal bool - }{ - {"Reference", WrappedTimestamp{0, Timestamp{referenceTime}}, fmt.Sprintf(`{"A":0,"Time":%s}`, referenceTimeStr), false, true}, - {"Empty", WrappedTimestamp{}, fmt.Sprintf(`{"A":0,"Time":%s}`, emptyTimeStr), false, true}, - {"Mismatch", WrappedTimestamp{}, fmt.Sprintf(`{"A":0,"Time":%s}`, referenceTimeStr), false, false}, - } - for _, tc := range testCases { - out, err := json.Marshal(tc.data) - if gotErr := err != nil; gotErr != tc.wantErr { - t.Errorf("%s: gotErr=%v, wantErr=%v, err=%v", tc.desc, gotErr, tc.wantErr, err) - } - got := string(out) - equal := got == tc.want - if equal != tc.equal { - t.Errorf("%s: got=%s, want=%s, equal=%v, want=%v", tc.desc, got, tc.want, equal, tc.equal) - } - } -} - -func TestWrappedTimstamp_Unmarshal(t *testing.T) { - testCases := []struct { - desc string - data string - want WrappedTimestamp - wantErr bool - equal bool - }{ - {"Reference", referenceTimeStr, WrappedTimestamp{0, Timestamp{referenceTime}}, false, true}, - {"ReferenceUnix", referenceUnixTimeStr, WrappedTimestamp{0, Timestamp{referenceTime}}, false, true}, - {"Empty", emptyTimeStr, WrappedTimestamp{0, Timestamp{}}, false, true}, - {"UnixStart", `0`, WrappedTimestamp{0, Timestamp{unixOrigin}}, false, true}, - {"Mismatch", referenceTimeStr, WrappedTimestamp{0, Timestamp{}}, false, false}, - {"MismatchUnix", `0`, WrappedTimestamp{0, Timestamp{}}, false, false}, - {"Invalid", `"asdf"`, WrappedTimestamp{0, Timestamp{referenceTime}}, true, false}, - } - for _, tc := range testCases { - var got Timestamp - err := json.Unmarshal([]byte(tc.data), &got) - if gotErr := err != nil; gotErr != tc.wantErr { - t.Errorf("%s: gotErr=%v, wantErr=%v, err=%v", tc.desc, gotErr, tc.wantErr, err) - continue - } - equal := got.Time.Equal(tc.want.Time.Time) - if equal != tc.equal { - t.Errorf("%s: got=%#v, want=%#v, equal=%v, want=%v", tc.desc, got, tc.want, equal, tc.equal) - } - } -} - -func TestWrappedTimstamp_MarshalReflexivity(t *testing.T) { - testCases := []struct { - desc string - data WrappedTimestamp - }{ - {"Reference", WrappedTimestamp{0, Timestamp{referenceTime}}}, - {"Empty", WrappedTimestamp{0, Timestamp{}}}, - } - for _, tc := range testCases { - bytes, err := json.Marshal(tc.data) - if err != nil { - t.Errorf("%s: Marshal err=%v", tc.desc, err) - } - var got WrappedTimestamp - err = json.Unmarshal(bytes, &got) - if !got.Time.Equal(tc.data.Time) { - t.Errorf("%s: %+v != %+v", tc.desc, got, tc.data) - } - } -} diff --git a/vendor/github.com/google/go-github/github/users.go b/vendor/github.com/google/go-github/github/users.go index bd68ac202..a041bbf98 100644 --- a/vendor/github.com/google/go-github/github/users.go +++ b/vendor/github.com/google/go-github/github/users.go @@ -59,6 +59,10 @@ type User struct { // TextMatches is only populated from search results that request text matches // See: search.go and https://developer.github.com/v3/search/#text-match-metadata TextMatches []TextMatch `json:"text_matches,omitempty"` + + // Permissions identifies the permissions that a user has on a given + // repository. This is only populated when calling Repositories.ListCollaborators. + Permissions *map[string]bool `json:"permissions,omitempty"` } func (u User) String() string { @@ -109,7 +113,7 @@ func (s *UsersService) Edit(user *User) (*User, *Response, error) { return uResp, resp, err } -// UserListOptions specifies optional parameters to the UsersService.List +// UserListOptions specifies optional parameters to the UsersService.ListAll // method. type UserListOptions struct { // ID of the last user seen diff --git a/vendor/github.com/google/go-github/github/users_administration_test.go b/vendor/github.com/google/go-github/github/users_administration_test.go deleted file mode 100644 index d415f4d4a..000000000 --- a/vendor/github.com/google/go-github/github/users_administration_test.go +++ /dev/null @@ -1,71 +0,0 @@ -// Copyright 2014 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "net/http" - "testing" -) - -func TestUsersService_PromoteSiteAdmin(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/users/u/site_admin", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "PUT") - w.WriteHeader(http.StatusNoContent) - }) - - _, err := client.Users.PromoteSiteAdmin("u") - if err != nil { - t.Errorf("Users.PromoteSiteAdmin returned error: %v", err) - } -} - -func TestUsersService_DemoteSiteAdmin(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/users/u/site_admin", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - w.WriteHeader(http.StatusNoContent) - }) - - _, err := client.Users.DemoteSiteAdmin("u") - if err != nil { - t.Errorf("Users.DemoteSiteAdmin returned error: %v", err) - } -} - -func TestUsersService_Suspend(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/users/u/suspended", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "PUT") - w.WriteHeader(http.StatusNoContent) - }) - - _, err := client.Users.Suspend("u") - if err != nil { - t.Errorf("Users.Suspend returned error: %v", err) - } -} - -func TestUsersService_Unsuspend(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/users/u/suspended", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - w.WriteHeader(http.StatusNoContent) - }) - - _, err := client.Users.Unsuspend("u") - if err != nil { - t.Errorf("Users.Unsuspend returned error: %v", err) - } -} diff --git a/vendor/github.com/google/go-github/github/users_emails_test.go b/vendor/github.com/google/go-github/github/users_emails_test.go deleted file mode 100644 index 7eb650860..000000000 --- a/vendor/github.com/google/go-github/github/users_emails_test.go +++ /dev/null @@ -1,94 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestUsersService_ListEmails(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/user/emails", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `[{ - "email": "user@example.com", - "verified": false, - "primary": true - }]`) - }) - - opt := &ListOptions{Page: 2} - emails, _, err := client.Users.ListEmails(opt) - if err != nil { - t.Errorf("Users.ListEmails returned error: %v", err) - } - - want := []UserEmail{{Email: String("user@example.com"), Verified: Bool(false), Primary: Bool(true)}} - if !reflect.DeepEqual(emails, want) { - t.Errorf("Users.ListEmails returned %+v, want %+v", emails, want) - } -} - -func TestUsersService_AddEmails(t *testing.T) { - setup() - defer teardown() - - input := []string{"new@example.com"} - - mux.HandleFunc("/user/emails", func(w http.ResponseWriter, r *http.Request) { - v := new([]string) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "POST") - if !reflect.DeepEqual(*v, input) { - t.Errorf("Request body = %+v, want %+v", *v, input) - } - - fmt.Fprint(w, `[{"email":"old@example.com"}, {"email":"new@example.com"}]`) - }) - - emails, _, err := client.Users.AddEmails(input) - if err != nil { - t.Errorf("Users.AddEmails returned error: %v", err) - } - - want := []UserEmail{ - {Email: String("old@example.com")}, - {Email: String("new@example.com")}, - } - if !reflect.DeepEqual(emails, want) { - t.Errorf("Users.AddEmails returned %+v, want %+v", emails, want) - } -} - -func TestUsersService_DeleteEmails(t *testing.T) { - setup() - defer teardown() - - input := []string{"user@example.com"} - - mux.HandleFunc("/user/emails", func(w http.ResponseWriter, r *http.Request) { - v := new([]string) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "DELETE") - if !reflect.DeepEqual(*v, input) { - t.Errorf("Request body = %+v, want %+v", *v, input) - } - }) - - _, err := client.Users.DeleteEmails(input) - if err != nil { - t.Errorf("Users.DeleteEmails returned error: %v", err) - } -} diff --git a/vendor/github.com/google/go-github/github/users_followers_test.go b/vendor/github.com/google/go-github/github/users_followers_test.go deleted file mode 100644 index f4d24578e..000000000 --- a/vendor/github.com/google/go-github/github/users_followers_test.go +++ /dev/null @@ -1,222 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestUsersService_ListFollowers_authenticatedUser(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/user/followers", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `[{"id":1}]`) - }) - - opt := &ListOptions{Page: 2} - users, _, err := client.Users.ListFollowers("", opt) - if err != nil { - t.Errorf("Users.ListFollowers returned error: %v", err) - } - - want := []User{{ID: Int(1)}} - if !reflect.DeepEqual(users, want) { - t.Errorf("Users.ListFollowers returned %+v, want %+v", users, want) - } -} - -func TestUsersService_ListFollowers_specifiedUser(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/users/u/followers", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `[{"id":1}]`) - }) - - users, _, err := client.Users.ListFollowers("u", nil) - if err != nil { - t.Errorf("Users.ListFollowers returned error: %v", err) - } - - want := []User{{ID: Int(1)}} - if !reflect.DeepEqual(users, want) { - t.Errorf("Users.ListFollowers returned %+v, want %+v", users, want) - } -} - -func TestUsersService_ListFollowers_invalidUser(t *testing.T) { - _, _, err := client.Users.ListFollowers("%", nil) - testURLParseError(t, err) -} - -func TestUsersService_ListFollowing_authenticatedUser(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/user/following", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `[{"id":1}]`) - }) - - opts := &ListOptions{Page: 2} - users, _, err := client.Users.ListFollowing("", opts) - if err != nil { - t.Errorf("Users.ListFollowing returned error: %v", err) - } - - want := []User{{ID: Int(1)}} - if !reflect.DeepEqual(users, want) { - t.Errorf("Users.ListFollowing returned %+v, want %+v", users, want) - } -} - -func TestUsersService_ListFollowing_specifiedUser(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/users/u/following", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `[{"id":1}]`) - }) - - users, _, err := client.Users.ListFollowing("u", nil) - if err != nil { - t.Errorf("Users.ListFollowing returned error: %v", err) - } - - want := []User{{ID: Int(1)}} - if !reflect.DeepEqual(users, want) { - t.Errorf("Users.ListFollowing returned %+v, want %+v", users, want) - } -} - -func TestUsersService_ListFollowing_invalidUser(t *testing.T) { - _, _, err := client.Users.ListFollowing("%", nil) - testURLParseError(t, err) -} - -func TestUsersService_IsFollowing_authenticatedUser(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/user/following/t", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - w.WriteHeader(http.StatusNoContent) - }) - - following, _, err := client.Users.IsFollowing("", "t") - if err != nil { - t.Errorf("Users.IsFollowing returned error: %v", err) - } - if want := true; following != want { - t.Errorf("Users.IsFollowing returned %+v, want %+v", following, want) - } -} - -func TestUsersService_IsFollowing_specifiedUser(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/users/u/following/t", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - w.WriteHeader(http.StatusNoContent) - }) - - following, _, err := client.Users.IsFollowing("u", "t") - if err != nil { - t.Errorf("Users.IsFollowing returned error: %v", err) - } - if want := true; following != want { - t.Errorf("Users.IsFollowing returned %+v, want %+v", following, want) - } -} - -func TestUsersService_IsFollowing_false(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/users/u/following/t", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - w.WriteHeader(http.StatusNotFound) - }) - - following, _, err := client.Users.IsFollowing("u", "t") - if err != nil { - t.Errorf("Users.IsFollowing returned error: %v", err) - } - if want := false; following != want { - t.Errorf("Users.IsFollowing returned %+v, want %+v", following, want) - } -} - -func TestUsersService_IsFollowing_error(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/users/u/following/t", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - http.Error(w, "BadRequest", http.StatusBadRequest) - }) - - following, _, err := client.Users.IsFollowing("u", "t") - if err == nil { - t.Errorf("Expected HTTP 400 response") - } - if want := false; following != want { - t.Errorf("Users.IsFollowing returned %+v, want %+v", following, want) - } -} - -func TestUsersService_IsFollowing_invalidUser(t *testing.T) { - _, _, err := client.Users.IsFollowing("%", "%") - testURLParseError(t, err) -} - -func TestUsersService_Follow(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/user/following/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "PUT") - }) - - _, err := client.Users.Follow("u") - if err != nil { - t.Errorf("Users.Follow returned error: %v", err) - } -} - -func TestUsersService_Follow_invalidUser(t *testing.T) { - _, err := client.Users.Follow("%") - testURLParseError(t, err) -} - -func TestUsersService_Unfollow(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/user/following/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - }) - - _, err := client.Users.Unfollow("u") - if err != nil { - t.Errorf("Users.Follow returned error: %v", err) - } -} - -func TestUsersService_Unfollow_invalidUser(t *testing.T) { - _, err := client.Users.Unfollow("%") - testURLParseError(t, err) -} diff --git a/vendor/github.com/google/go-github/github/users_keys_test.go b/vendor/github.com/google/go-github/github/users_keys_test.go deleted file mode 100644 index e47afd71d..000000000 --- a/vendor/github.com/google/go-github/github/users_keys_test.go +++ /dev/null @@ -1,124 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestUsersService_ListKeys_authenticatedUser(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/user/keys", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"page": "2"}) - fmt.Fprint(w, `[{"id":1}]`) - }) - - opt := &ListOptions{Page: 2} - keys, _, err := client.Users.ListKeys("", opt) - if err != nil { - t.Errorf("Users.ListKeys returned error: %v", err) - } - - want := []Key{{ID: Int(1)}} - if !reflect.DeepEqual(keys, want) { - t.Errorf("Users.ListKeys returned %+v, want %+v", keys, want) - } -} - -func TestUsersService_ListKeys_specifiedUser(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/users/u/keys", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `[{"id":1}]`) - }) - - keys, _, err := client.Users.ListKeys("u", nil) - if err != nil { - t.Errorf("Users.ListKeys returned error: %v", err) - } - - want := []Key{{ID: Int(1)}} - if !reflect.DeepEqual(keys, want) { - t.Errorf("Users.ListKeys returned %+v, want %+v", keys, want) - } -} - -func TestUsersService_ListKeys_invalidUser(t *testing.T) { - _, _, err := client.Users.ListKeys("%", nil) - testURLParseError(t, err) -} - -func TestUsersService_GetKey(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/user/keys/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"id":1}`) - }) - - key, _, err := client.Users.GetKey(1) - if err != nil { - t.Errorf("Users.GetKey returned error: %v", err) - } - - want := &Key{ID: Int(1)} - if !reflect.DeepEqual(key, want) { - t.Errorf("Users.GetKey returned %+v, want %+v", key, want) - } -} - -func TestUsersService_CreateKey(t *testing.T) { - setup() - defer teardown() - - input := &Key{Key: String("k"), Title: String("t")} - - mux.HandleFunc("/user/keys", func(w http.ResponseWriter, r *http.Request) { - v := new(Key) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "POST") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"id":1}`) - }) - - key, _, err := client.Users.CreateKey(input) - if err != nil { - t.Errorf("Users.GetKey returned error: %v", err) - } - - want := &Key{ID: Int(1)} - if !reflect.DeepEqual(key, want) { - t.Errorf("Users.GetKey returned %+v, want %+v", key, want) - } -} - -func TestUsersService_DeleteKey(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/user/keys/1", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "DELETE") - }) - - _, err := client.Users.DeleteKey(1) - if err != nil { - t.Errorf("Users.DeleteKey returned error: %v", err) - } -} diff --git a/vendor/github.com/google/go-github/github/users_test.go b/vendor/github.com/google/go-github/github/users_test.go deleted file mode 100644 index 15ea3e83a..000000000 --- a/vendor/github.com/google/go-github/github/users_test.go +++ /dev/null @@ -1,150 +0,0 @@ -// Copyright 2013 The go-github AUTHORS. All rights reserved. -// -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package github - -import ( - "encoding/json" - "fmt" - "net/http" - "reflect" - "testing" -) - -func TestUser_marshall(t *testing.T) { - testJSONMarshal(t, &User{}, "{}") - - u := &User{ - Login: String("l"), - ID: Int(1), - URL: String("u"), - AvatarURL: String("a"), - GravatarID: String("g"), - Name: String("n"), - Company: String("c"), - Blog: String("b"), - Location: String("l"), - Email: String("e"), - Hireable: Bool(true), - PublicRepos: Int(1), - Followers: Int(1), - Following: Int(1), - CreatedAt: &Timestamp{referenceTime}, - } - want := `{ - "login": "l", - "id": 1, - "avatar_url": "a", - "gravatar_id": "g", - "name": "n", - "company": "c", - "blog": "b", - "location": "l", - "email": "e", - "hireable": true, - "public_repos": 1, - "followers": 1, - "following": 1, - "created_at": ` + referenceTimeStr + `, - "url": "u" - }` - testJSONMarshal(t, u, want) -} - -func TestUsersService_Get_authenticatedUser(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/user", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"id":1}`) - }) - - user, _, err := client.Users.Get("") - if err != nil { - t.Errorf("Users.Get returned error: %v", err) - } - - want := &User{ID: Int(1)} - if !reflect.DeepEqual(user, want) { - t.Errorf("Users.Get returned %+v, want %+v", user, want) - } -} - -func TestUsersService_Get_specifiedUser(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/users/u", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - fmt.Fprint(w, `{"id":1}`) - }) - - user, _, err := client.Users.Get("u") - if err != nil { - t.Errorf("Users.Get returned error: %v", err) - } - - want := &User{ID: Int(1)} - if !reflect.DeepEqual(user, want) { - t.Errorf("Users.Get returned %+v, want %+v", user, want) - } -} - -func TestUsersService_Get_invalidUser(t *testing.T) { - _, _, err := client.Users.Get("%") - testURLParseError(t, err) -} - -func TestUsersService_Edit(t *testing.T) { - setup() - defer teardown() - - input := &User{Name: String("n")} - - mux.HandleFunc("/user", func(w http.ResponseWriter, r *http.Request) { - v := new(User) - json.NewDecoder(r.Body).Decode(v) - - testMethod(t, r, "PATCH") - if !reflect.DeepEqual(v, input) { - t.Errorf("Request body = %+v, want %+v", v, input) - } - - fmt.Fprint(w, `{"id":1}`) - }) - - user, _, err := client.Users.Edit(input) - if err != nil { - t.Errorf("Users.Edit returned error: %v", err) - } - - want := &User{ID: Int(1)} - if !reflect.DeepEqual(user, want) { - t.Errorf("Users.Edit returned %+v, want %+v", user, want) - } -} - -func TestUsersService_ListAll(t *testing.T) { - setup() - defer teardown() - - mux.HandleFunc("/users", func(w http.ResponseWriter, r *http.Request) { - testMethod(t, r, "GET") - testFormValues(t, r, values{"since": "1"}) - fmt.Fprint(w, `[{"id":2}]`) - }) - - opt := &UserListOptions{1} - users, _, err := client.Users.ListAll(opt) - if err != nil { - t.Errorf("Users.Get returned error: %v", err) - } - - want := []User{{ID: Int(2)}} - if !reflect.DeepEqual(users, want) { - t.Errorf("Users.ListAll returned %+v, want %+v", users, want) - } -} diff --git a/vendor/github.com/google/go-querystring/LICENSE b/vendor/github.com/google/go-querystring/LICENSE new file mode 100644 index 000000000..ae121a1e4 --- /dev/null +++ b/vendor/github.com/google/go-querystring/LICENSE @@ -0,0 +1,27 @@ +Copyright (c) 2013 Google. All rights reserved. + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are +met: + + * Redistributions of source code must retain the above copyright +notice, this list of conditions and the following disclaimer. + * Redistributions in binary form must reproduce the above +copyright notice, this list of conditions and the following disclaimer +in the documentation and/or other materials provided with the +distribution. + * Neither the name of Google Inc. nor the names of its +contributors may be used to endorse or promote products derived from +this software without specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. diff --git a/vendor/github.com/google/go-querystring/query/encode_test.go b/vendor/github.com/google/go-querystring/query/encode_test.go deleted file mode 100644 index 8afbd0bed..000000000 --- a/vendor/github.com/google/go-querystring/query/encode_test.go +++ /dev/null @@ -1,238 +0,0 @@ -// Copyright 2013 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package query - -import ( - "fmt" - "net/url" - "reflect" - "testing" - "time" -) - -func TestValues_types(t *testing.T) { - str := "string" - strPtr := &str - - tests := []struct { - in interface{} - want url.Values - }{ - { - // basic primitives - struct { - A string - B int - C uint - D float32 - E bool - }{}, - url.Values{ - "A": {""}, - "B": {"0"}, - "C": {"0"}, - "D": {"0"}, - "E": {"false"}, - }, - }, - { - // pointers - struct { - A *string - B *int - C **string - }{A: strPtr, C: &strPtr}, - url.Values{ - "A": {str}, - "B": {""}, - "C": {str}, - }, - }, - { - // slices and arrays - struct { - A []string - B []string `url:",comma"` - C []string `url:",space"` - D [2]string - E [2]string `url:",comma"` - F [2]string `url:",space"` - G []*string `url:",space"` - H []bool `url:",int,space"` - }{ - A: []string{"a", "b"}, - B: []string{"a", "b"}, - C: []string{"a", "b"}, - D: [2]string{"a", "b"}, - E: [2]string{"a", "b"}, - F: [2]string{"a", "b"}, - G: []*string{&str, &str}, - H: []bool{true, false}, - }, - url.Values{ - "A": {"a", "b"}, - "B": {"a,b"}, - "C": {"a b"}, - "D": {"a", "b"}, - "E": {"a,b"}, - "F": {"a b"}, - "G": {"string string"}, - "H": {"1 0"}, - }, - }, - { - // other types - struct { - A time.Time - B time.Time `url:",unix"` - C bool `url:",int"` - D bool `url:",int"` - }{ - A: time.Date(2000, 1, 1, 12, 34, 56, 0, time.UTC), - B: time.Date(2000, 1, 1, 12, 34, 56, 0, time.UTC), - C: true, - D: false, - }, - url.Values{ - "A": {"2000-01-01T12:34:56Z"}, - "B": {"946730096"}, - "C": {"1"}, - "D": {"0"}, - }, - }, - } - - for i, tt := range tests { - v, err := Values(tt.in) - if err != nil { - t.Errorf("%d. Values(%q) returned error: %v", i, tt.in, err) - } - - if !reflect.DeepEqual(tt.want, v) { - t.Errorf("%d. Values(%q) returned %v, want %v", i, tt.in, v, tt.want) - } - } -} - -func TestValues_omitEmpty(t *testing.T) { - str := "" - s := struct { - a string - A string - B string `url:",omitempty"` - C string `url:"-"` - D string `url:"omitempty"` // actually named omitempty, not an option - E *string `url:",omitempty"` - }{E: &str} - - v, err := Values(s) - if err != nil { - t.Errorf("Values(%q) returned error: %v", s, err) - } - - want := url.Values{ - "A": {""}, - "omitempty": {""}, - "E": {""}, // E is included because the pointer is not empty, even though the string being pointed to is - } - if !reflect.DeepEqual(want, v) { - t.Errorf("Values(%q) returned %v, want %v", s, v, want) - } -} - -type A struct { - B -} - -type B struct { - C string -} - -type D struct { - B - C string -} - -func TestValues_embeddedStructs(t *testing.T) { - tests := []struct { - in interface{} - want url.Values - }{ - { - A{B{C: "foo"}}, - url.Values{"C": {"foo"}}, - }, - { - D{B: B{C: "bar"}, C: "foo"}, - url.Values{"C": {"foo", "bar"}}, - }, - } - - for i, tt := range tests { - v, err := Values(tt.in) - if err != nil { - t.Errorf("%d. Values(%q) returned error: %v", i, tt.in, err) - } - - if !reflect.DeepEqual(tt.want, v) { - t.Errorf("%d. Values(%q) returned %v, want %v", i, tt.in, v, tt.want) - } - } -} - -func TestValues_invalidInput(t *testing.T) { - _, err := Values("") - if err == nil { - t.Errorf("expected Values() to return an error on invalid input") - } -} - -type EncodedArgs []string - -func (m EncodedArgs) EncodeValues(key string, v *url.Values) error { - for i, arg := range m { - v.Set(fmt.Sprintf("%s.%d", key, i), arg) - } - return nil -} - -func TestValues_Marshaler(t *testing.T) { - s := struct { - Args EncodedArgs `url:"arg"` - }{[]string{"a", "b", "c"}} - v, err := Values(s) - if err != nil { - t.Errorf("Values(%q) returned error: %v", s, err) - } - - want := url.Values{ - "arg.0": {"a"}, - "arg.1": {"b"}, - "arg.2": {"c"}, - } - if !reflect.DeepEqual(want, v) { - t.Errorf("Values(%q) returned %v, want %v", s, v, want) - } -} - -func TestTagParsing(t *testing.T) { - name, opts := parseTag("field,foobar,foo") - if name != "field" { - t.Fatalf("name = %q, want field", name) - } - for _, tt := range []struct { - opt string - want bool - }{ - {"foobar", true}, - {"foo", true}, - {"bar", false}, - {"field", false}, - } { - if opts.Contains(tt.opt) != tt.want { - t.Errorf("Contains(%q) = %v", tt.opt, !tt.want) - } - } -} diff --git a/vendor/github.com/gorilla/securecookie/securecookie_test.go b/vendor/github.com/gorilla/securecookie/securecookie_test.go deleted file mode 100644 index fe0cdb109..000000000 --- a/vendor/github.com/gorilla/securecookie/securecookie_test.go +++ /dev/null @@ -1,178 +0,0 @@ -// Copyright 2012 The Gorilla Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package securecookie - -import ( - "crypto/aes" - "crypto/hmac" - "crypto/sha256" - "errors" - "fmt" - "strings" - "testing" -) - -var testCookies = []interface{}{ - map[string]string{"foo": "bar"}, - map[string]string{"baz": "ding"}, -} - -var testStrings = []string{"foo", "bar", "baz"} - -func TestSecureCookie(t *testing.T) { - // TODO test too old / too new timestamps - compareMaps := func(m1, m2 map[string]interface{}) error { - if len(m1) != len(m2) { - return errors.New("different maps") - } - for k, v := range m1 { - if m2[k] != v { - return fmt.Errorf("Different value for key %v: expected %v, got %v", k, m2[k], v) - } - } - return nil - } - - s1 := New([]byte("12345"), []byte("1234567890123456")) - s2 := New([]byte("54321"), []byte("6543210987654321")) - value := map[string]interface{}{ - "foo": "bar", - "baz": 128, - } - - for i := 0; i < 50; i++ { - // Running this multiple times to check if any special character - // breaks encoding/decoding. - encoded, err1 := s1.Encode("sid", value) - if err1 != nil { - t.Error(err1) - continue - } - dst := make(map[string]interface{}) - err2 := s1.Decode("sid", encoded, &dst) - if err2 != nil { - t.Fatalf("%v: %v", err2, encoded) - } - if err := compareMaps(dst, value); err != nil { - t.Fatalf("Expected %v, got %v.", value, dst) - } - dst2 := make(map[string]interface{}) - err3 := s2.Decode("sid", encoded, &dst2) - if err3 == nil { - t.Fatalf("Expected failure decoding.") - } - } -} - -func TestAuthentication(t *testing.T) { - hash := hmac.New(sha256.New, []byte("secret-key")) - for _, value := range testStrings { - hash.Reset() - signed := createMac(hash, []byte(value)) - hash.Reset() - err := verifyMac(hash, []byte(value), signed) - if err != nil { - t.Error(err) - } - } -} - -func TestEncription(t *testing.T) { - block, err := aes.NewCipher([]byte("1234567890123456")) - if err != nil { - t.Fatalf("Block could not be created") - } - var encrypted, decrypted []byte - for _, value := range testStrings { - if encrypted, err = encrypt(block, []byte(value)); err != nil { - t.Error(err) - } else { - if decrypted, err = decrypt(block, encrypted); err != nil { - t.Error(err) - } - if string(decrypted) != value { - t.Errorf("Expected %v, got %v.", value, string(decrypted)) - } - } - } -} - -func TestSerialization(t *testing.T) { - var ( - serialized []byte - deserialized map[string]string - err error - ) - for _, value := range testCookies { - if serialized, err = serialize(value); err != nil { - t.Error(err) - } else { - deserialized = make(map[string]string) - if err = deserialize(serialized, &deserialized); err != nil { - t.Error(err) - } - if fmt.Sprintf("%v", deserialized) != fmt.Sprintf("%v", value) { - t.Errorf("Expected %v, got %v.", value, deserialized) - } - } - } -} - -func TestEncoding(t *testing.T) { - for _, value := range testStrings { - encoded := encode([]byte(value)) - decoded, err := decode(encoded) - if err != nil { - t.Error(err) - } else if string(decoded) != value { - t.Errorf("Expected %v, got %s.", value, string(decoded)) - } - } -} - -func TestMultiError(t *testing.T) { - s1, s2 := New(nil, nil), New(nil, nil) - _, err := EncodeMulti("sid", "value", s1, s2) - if len(err.(MultiError)) != 2 { - t.Errorf("Expected 2 errors, got %s.", err) - } else { - if strings.Index(err.Error(), "hash key is not set") == -1 { - t.Errorf("Expected missing hash key error, got %s.", err.Error()) - } - } -} - -func TestMultiNoCodecs(t *testing.T) { - _, err := EncodeMulti("foo", "bar") - if err != errNoCodecs { - t.Errorf("EncodeMulti: bad value for error, got: %v", err) - } - - var dst []byte - err = DecodeMulti("foo", "bar", &dst) - if err != errNoCodecs { - t.Errorf("DecodeMulti: bad value for error, got: %v", err) - } -} - -// ---------------------------------------------------------------------------- - -type FooBar struct { - Foo int - Bar string -} - -func TestCustomType(t *testing.T) { - s1 := New([]byte("12345"), []byte("1234567890123456")) - // Type is not registered in gob. (!!!) - src := &FooBar{42, "bar"} - encoded, _ := s1.Encode("sid", src) - - dst := &FooBar{} - _ = s1.Decode("sid", encoded, dst) - if dst.Foo != 42 || dst.Bar != "bar" { - t.Fatalf("Expected %#v, got %#v", src, dst) - } -} diff --git a/vendor/github.com/hashicorp/golang-lru/LICENSE b/vendor/github.com/hashicorp/golang-lru/LICENSE deleted file mode 100644 index be2cc4dfb..000000000 --- a/vendor/github.com/hashicorp/golang-lru/LICENSE +++ /dev/null @@ -1,362 +0,0 @@ -Mozilla Public License, version 2.0 - -1. Definitions - -1.1. "Contributor" - - means each individual or legal entity that creates, contributes to the - creation of, or owns Covered Software. - -1.2. "Contributor Version" - - means the combination of the Contributions of others (if any) used by a - Contributor and that particular Contributor's Contribution. - -1.3. "Contribution" - - means Covered Software of a particular Contributor. - -1.4. "Covered Software" - - means Source Code Form to which the initial Contributor has attached the - notice in Exhibit A, the Executable Form of such Source Code Form, and - Modifications of such Source Code Form, in each case including portions - thereof. - -1.5. "Incompatible With Secondary Licenses" - means - - a. that the initial Contributor has attached the notice described in - Exhibit B to the Covered Software; or - - b. that the Covered Software was made available under the terms of - version 1.1 or earlier of the License, but not also under the terms of - a Secondary License. - -1.6. "Executable Form" - - means any form of the work other than Source Code Form. - -1.7. "Larger Work" - - means a work that combines Covered Software with other material, in a - separate file or files, that is not Covered Software. - -1.8. "License" - - means this document. - -1.9. "Licensable" - - means having the right to grant, to the maximum extent possible, whether - at the time of the initial grant or subsequently, any and all of the - rights conveyed by this License. - -1.10. "Modifications" - - means any of the following: - - a. any file in Source Code Form that results from an addition to, - deletion from, or modification of the contents of Covered Software; or - - b. any new file in Source Code Form that contains any Covered Software. - -1.11. "Patent Claims" of a Contributor - - means any patent claim(s), including without limitation, method, - process, and apparatus claims, in any patent Licensable by such - Contributor that would be infringed, but for the grant of the License, - by the making, using, selling, offering for sale, having made, import, - or transfer of either its Contributions or its Contributor Version. - -1.12. "Secondary License" - - means either the GNU General Public License, Version 2.0, the GNU Lesser - General Public License, Version 2.1, the GNU Affero General Public - License, Version 3.0, or any later versions of those licenses. - -1.13. "Source Code Form" - - means the form of the work preferred for making modifications. - -1.14. "You" (or "Your") - - means an individual or a legal entity exercising rights under this - License. For legal entities, "You" includes any entity that controls, is - controlled by, or is under common control with You. For purposes of this - definition, "control" means (a) the power, direct or indirect, to cause - the direction or management of such entity, whether by contract or - otherwise, or (b) ownership of more than fifty percent (50%) of the - outstanding shares or beneficial ownership of such entity. - - -2. License Grants and Conditions - -2.1. Grants - - Each Contributor hereby grants You a world-wide, royalty-free, - non-exclusive license: - - a. under intellectual property rights (other than patent or trademark) - Licensable by such Contributor to use, reproduce, make available, - modify, display, perform, distribute, and otherwise exploit its - Contributions, either on an unmodified basis, with Modifications, or - as part of a Larger Work; and - - b. under Patent Claims of such Contributor to make, use, sell, offer for - sale, have made, import, and otherwise transfer either its - Contributions or its Contributor Version. - -2.2. Effective Date - - The licenses granted in Section 2.1 with respect to any Contribution - become effective for each Contribution on the date the Contributor first - distributes such Contribution. - -2.3. Limitations on Grant Scope - - The licenses granted in this Section 2 are the only rights granted under - this License. No additional rights or licenses will be implied from the - distribution or licensing of Covered Software under this License. - Notwithstanding Section 2.1(b) above, no patent license is granted by a - Contributor: - - a. for any code that a Contributor has removed from Covered Software; or - - b. for infringements caused by: (i) Your and any other third party's - modifications of Covered Software, or (ii) the combination of its - Contributions with other software (except as part of its Contributor - Version); or - - c. under Patent Claims infringed by Covered Software in the absence of - its Contributions. - - This License does not grant any rights in the trademarks, service marks, - or logos of any Contributor (except as may be necessary to comply with - the notice requirements in Section 3.4). - -2.4. Subsequent Licenses - - No Contributor makes additional grants as a result of Your choice to - distribute the Covered Software under a subsequent version of this - License (see Section 10.2) or under the terms of a Secondary License (if - permitted under the terms of Section 3.3). - -2.5. Representation - - Each Contributor represents that the Contributor believes its - Contributions are its original creation(s) or it has sufficient rights to - grant the rights to its Contributions conveyed by this License. - -2.6. Fair Use - - This License is not intended to limit any rights You have under - applicable copyright doctrines of fair use, fair dealing, or other - equivalents. - -2.7. Conditions - - Sections 3.1, 3.2, 3.3, and 3.4 are conditions of the licenses granted in - Section 2.1. - - -3. Responsibilities - -3.1. Distribution of Source Form - - All distribution of Covered Software in Source Code Form, including any - Modifications that You create or to which You contribute, must be under - the terms of this License. You must inform recipients that the Source - Code Form of the Covered Software is governed by the terms of this - License, and how they can obtain a copy of this License. You may not - attempt to alter or restrict the recipients' rights in the Source Code - Form. - -3.2. Distribution of Executable Form - - If You distribute Covered Software in Executable Form then: - - a. such Covered Software must also be made available in Source Code Form, - as described in Section 3.1, and You must inform recipients of the - Executable Form how they can obtain a copy of such Source Code Form by - reasonable means in a timely manner, at a charge no more than the cost - of distribution to the recipient; and - - b. You may distribute such Executable Form under the terms of this - License, or sublicense it under different terms, provided that the - license for the Executable Form does not attempt to limit or alter the - recipients' rights in the Source Code Form under this License. - -3.3. Distribution of a Larger Work - - You may create and distribute a Larger Work under terms of Your choice, - provided that You also comply with the requirements of this License for - the Covered Software. If the Larger Work is a combination of Covered - Software with a work governed by one or more Secondary Licenses, and the - Covered Software is not Incompatible With Secondary Licenses, this - License permits You to additionally distribute such Covered Software - under the terms of such Secondary License(s), so that the recipient of - the Larger Work may, at their option, further distribute the Covered - Software under the terms of either this License or such Secondary - License(s). - -3.4. Notices - - You may not remove or alter the substance of any license notices - (including copyright notices, patent notices, disclaimers of warranty, or - limitations of liability) contained within the Source Code Form of the - Covered Software, except that You may alter any license notices to the - extent required to remedy known factual inaccuracies. - -3.5. Application of Additional Terms - - You may choose to offer, and to charge a fee for, warranty, support, - indemnity or liability obligations to one or more recipients of Covered - Software. However, You may do so only on Your own behalf, and not on - behalf of any Contributor. You must make it absolutely clear that any - such warranty, support, indemnity, or liability obligation is offered by - You alone, and You hereby agree to indemnify every Contributor for any - liability incurred by such Contributor as a result of warranty, support, - indemnity or liability terms You offer. You may include additional - disclaimers of warranty and limitations of liability specific to any - jurisdiction. - -4. Inability to Comply Due to Statute or Regulation - - If it is impossible for You to comply with any of the terms of this License - with respect to some or all of the Covered Software due to statute, - judicial order, or regulation then You must: (a) comply with the terms of - this License to the maximum extent possible; and (b) describe the - limitations and the code they affect. Such description must be placed in a - text file included with all distributions of the Covered Software under - this License. Except to the extent prohibited by statute or regulation, - such description must be sufficiently detailed for a recipient of ordinary - skill to be able to understand it. - -5. Termination - -5.1. The rights granted under this License will terminate automatically if You - fail to comply with any of its terms. However, if You become compliant, - then the rights granted under this License from a particular Contributor - are reinstated (a) provisionally, unless and until such Contributor - explicitly and finally terminates Your grants, and (b) on an ongoing - basis, if such Contributor fails to notify You of the non-compliance by - some reasonable means prior to 60 days after You have come back into - compliance. Moreover, Your grants from a particular Contributor are - reinstated on an ongoing basis if such Contributor notifies You of the - non-compliance by some reasonable means, this is the first time You have - received notice of non-compliance with this License from such - Contributor, and You become compliant prior to 30 days after Your receipt - of the notice. - -5.2. If You initiate litigation against any entity by asserting a patent - infringement claim (excluding declaratory judgment actions, - counter-claims, and cross-claims) alleging that a Contributor Version - directly or indirectly infringes any patent, then the rights granted to - You by any and all Contributors for the Covered Software under Section - 2.1 of this License shall terminate. - -5.3. In the event of termination under Sections 5.1 or 5.2 above, all end user - license agreements (excluding distributors and resellers) which have been - validly granted by You or Your distributors under this License prior to - termination shall survive termination. - -6. Disclaimer of Warranty - - Covered Software is provided under this License on an "as is" basis, - without warranty of any kind, either expressed, implied, or statutory, - including, without limitation, warranties that the Covered Software is free - of defects, merchantable, fit for a particular purpose or non-infringing. - The entire risk as to the quality and performance of the Covered Software - is with You. Should any Covered Software prove defective in any respect, - You (not any Contributor) assume the cost of any necessary servicing, - repair, or correction. This disclaimer of warranty constitutes an essential - part of this License. No use of any Covered Software is authorized under - this License except under this disclaimer. - -7. Limitation of Liability - - Under no circumstances and under no legal theory, whether tort (including - negligence), contract, or otherwise, shall any Contributor, or anyone who - distributes Covered Software as permitted above, be liable to You for any - direct, indirect, special, incidental, or consequential damages of any - character including, without limitation, damages for lost profits, loss of - goodwill, work stoppage, computer failure or malfunction, or any and all - other commercial damages or losses, even if such party shall have been - informed of the possibility of such damages. This limitation of liability - shall not apply to liability for death or personal injury resulting from - such party's negligence to the extent applicable law prohibits such - limitation. Some jurisdictions do not allow the exclusion or limitation of - incidental or consequential damages, so this exclusion and limitation may - not apply to You. - -8. Litigation - - Any litigation relating to this License may be brought only in the courts - of a jurisdiction where the defendant maintains its principal place of - business and such litigation shall be governed by laws of that - jurisdiction, without reference to its conflict-of-law provisions. Nothing - in this Section shall prevent a party's ability to bring cross-claims or - counter-claims. - -9. Miscellaneous - - This License represents the complete agreement concerning the subject - matter hereof. If any provision of this License is held to be - unenforceable, such provision shall be reformed only to the extent - necessary to make it enforceable. Any law or regulation which provides that - the language of a contract shall be construed against the drafter shall not - be used to construe this License against a Contributor. - - -10. Versions of the License - -10.1. New Versions - - Mozilla Foundation is the license steward. Except as provided in Section - 10.3, no one other than the license steward has the right to modify or - publish new versions of this License. Each version will be given a - distinguishing version number. - -10.2. Effect of New Versions - - You may distribute the Covered Software under the terms of the version - of the License under which You originally received the Covered Software, - or under the terms of any subsequent version published by the license - steward. - -10.3. Modified Versions - - If you create software not governed by this License, and you want to - create a new license for such software, you may create and use a - modified version of this License if you rename the license and remove - any references to the name of the license steward (except to note that - such modified license differs from this License). - -10.4. Distributing Source Code Form that is Incompatible With Secondary - Licenses If You choose to distribute Source Code Form that is - Incompatible With Secondary Licenses under the terms of this version of - the License, the notice described in Exhibit B of this License must be - attached. - -Exhibit A - Source Code Form License Notice - - This Source Code Form is subject to the - terms of the Mozilla Public License, v. - 2.0. If a copy of the MPL was not - distributed with this file, You can - obtain one at - http://mozilla.org/MPL/2.0/. - -If it is not possible or desirable to put the notice in a particular file, -then You may include the notice in a location (such as a LICENSE file in a -relevant directory) where a recipient would be likely to look for such a -notice. - -You may add additional accurate notices of copyright ownership. - -Exhibit B - "Incompatible With Secondary Licenses" Notice - - This Source Code Form is "Incompatible - With Secondary Licenses", as defined by - the Mozilla Public License, v. 2.0. diff --git a/vendor/github.com/hashicorp/golang-lru/README.md b/vendor/github.com/hashicorp/golang-lru/README.md deleted file mode 100644 index 37fa54d42..000000000 --- a/vendor/github.com/hashicorp/golang-lru/README.md +++ /dev/null @@ -1,25 +0,0 @@ -golang-lru -========== - -This provides the `lru` package which implements a fixed-size -thread safe LRU cache. It is based on the cache in Groupcache. - -Documentation -============= - -Full docs are available on [Godoc](http://godoc.org/github.com/hashicorp/golang-lru) - -Example -======= - -Using the LRU is very simple: - -```go -l, _ := New(128) -for i := 0; i < 256; i++ { - l.Add(i, nil) -} -if l.Len() != 128 { - panic("bad len: %v", l.Len()) -} -``` diff --git a/vendor/github.com/hashicorp/golang-lru/lru.go b/vendor/github.com/hashicorp/golang-lru/lru.go deleted file mode 100644 index 8ccb72979..000000000 --- a/vendor/github.com/hashicorp/golang-lru/lru.go +++ /dev/null @@ -1,119 +0,0 @@ -// This package provides a simple LRU cache. It is based on the -// LRU implementation in groupcache: -// https://github.com/golang/groupcache/tree/master/lru -package lru - -import ( - "container/list" - "errors" - "sync" -) - -// Cache is a thread-safe fixed size LRU cache. -type Cache struct { - size int - evictList *list.List - items map[interface{}]*list.Element - lock sync.Mutex -} - -// entry is used to hold a value in the evictList -type entry struct { - key interface{} - value interface{} -} - -// New creates an LRU of the given size -func New(size int) (*Cache, error) { - if size <= 0 { - return nil, errors.New("Must provide a positive size") - } - c := &Cache{ - size: size, - evictList: list.New(), - items: make(map[interface{}]*list.Element, size), - } - return c, nil -} - -// Purge is used to completely clear the cache -func (c *Cache) Purge() { - c.lock.Lock() - defer c.lock.Unlock() - c.evictList = list.New() - c.items = make(map[interface{}]*list.Element, c.size) -} - -// Add adds a value to the cache. -func (c *Cache) Add(key, value interface{}) { - c.lock.Lock() - defer c.lock.Unlock() - - // Check for existing item - if ent, ok := c.items[key]; ok { - c.evictList.MoveToFront(ent) - ent.Value.(*entry).value = value - return - } - - // Add new item - ent := &entry{key, value} - entry := c.evictList.PushFront(ent) - c.items[key] = entry - - // Verify size not exceeded - if c.evictList.Len() > c.size { - c.removeOldest() - } -} - -// Get looks up a key's value from the cache. -func (c *Cache) Get(key interface{}) (value interface{}, ok bool) { - c.lock.Lock() - defer c.lock.Unlock() - - if ent, ok := c.items[key]; ok { - c.evictList.MoveToFront(ent) - return ent.Value.(*entry).value, true - } - return -} - -// Remove removes the provided key from the cache. -func (c *Cache) Remove(key interface{}) { - c.lock.Lock() - defer c.lock.Unlock() - - if ent, ok := c.items[key]; ok { - c.removeElement(ent) - } -} - -// RemoveOldest removes the oldest item from the cache. -func (c *Cache) RemoveOldest() { - c.lock.Lock() - defer c.lock.Unlock() - c.removeOldest() -} - -// removeOldest removes the oldest item from the cache. -func (c *Cache) removeOldest() { - ent := c.evictList.Back() - if ent != nil { - c.removeElement(ent) - } -} - -// removeElement is used to remove a given list element from the cache -func (c *Cache) removeElement(e *list.Element) { - c.evictList.Remove(e) - kv := e.Value.(*entry) - delete(c.items, kv.key) -} - -// Len returns the number of items in the cache. -func (c *Cache) Len() int { - c.lock.Lock() - defer c.lock.Unlock() - return c.evictList.Len() -} diff --git a/vendor/github.com/hashicorp/golang-lru/lru_test.go b/vendor/github.com/hashicorp/golang-lru/lru_test.go deleted file mode 100644 index 9c1063f92..000000000 --- a/vendor/github.com/hashicorp/golang-lru/lru_test.go +++ /dev/null @@ -1,45 +0,0 @@ -package lru - -import ( - "testing" -) - -func TestLRU(t *testing.T) { - l, err := New(128) - if err != nil { - t.Fatalf("err: %v", err) - } - for i := 0; i < 256; i++ { - l.Add(i, i) - } - if l.Len() != 128 { - t.Fatalf("bad len: %v", l.Len()) - } - for i := 0; i < 128; i++ { - _, ok := l.Get(i) - if ok { - t.Fatalf("should be evicted") - } - } - for i := 128; i < 256; i++ { - _, ok := l.Get(i) - if !ok { - t.Fatalf("should not be evicted") - } - } - for i := 128; i < 192; i++ { - l.Remove(i) - _, ok := l.Get(i) - if ok { - t.Fatalf("should be deleted") - } - } - - l.Purge() - if l.Len() != 0 { - t.Fatalf("bad len: %v", l.Len()) - } - if _, ok := l.Get(200); ok { - t.Fatalf("should contain nothing") - } -} diff --git a/vendor/github.com/koding/cache/helper_test.go b/vendor/github.com/koding/cache/helper_test.go deleted file mode 100644 index be2c67994..000000000 --- a/vendor/github.com/koding/cache/helper_test.go +++ /dev/null @@ -1,83 +0,0 @@ -package cache - -import "testing" - -func testCacheGetSet(t *testing.T, cache Cache) { - err := cache.Set("test_key", "test_data") - if err != nil { - t.Fatal("should not give err while setting item") - } - - err = cache.Set("test_key2", "test_data2") - if err != nil { - t.Fatal("should not give err while setting item") - } - - data, err := cache.Get("test_key") - if err != nil { - t.Fatal("test_key should be in the cache") - } - - if data != "test_data" { - t.Fatal("data is not \"test_data\"") - } - - data, err = cache.Get("test_key2") - if err != nil { - t.Fatal("test_key2 should be in the cache") - } - - if data != "test_data2" { - t.Fatal("data is not \"test_data2\"") - } -} - -func testCacheNilValue(t *testing.T, cache Cache) { - err := cache.Set("test_key", nil) - if err != nil { - t.Fatal("should not give err while setting item") - } - - data, err := cache.Get("test_key") - if err != nil { - t.Fatal("test_key should be in the cache") - } - - if data != nil { - t.Fatal("data is not nil") - } - - err = cache.Delete("test_key") - if err != nil { - t.Fatal("should not give err while setting item") - } - - data, err = cache.Get("test_key") - if err == nil { - t.Fatal("test_key should not be in the cache") - } -} - -func testCacheDelete(t *testing.T, cache Cache) { - cache.Set("test_key", "test_data") - cache.Set("test_key2", "test_data2") - - err := cache.Delete("test_key3") - if err != nil { - t.Fatal("non-exiting item should not give error") - } - - err = cache.Delete("test_key") - if err != nil { - t.Fatal("exiting item should not give error") - } - - data, err := cache.Get("test_key") - if err != ErrNotFound { - t.Fatal("test_key should not be in the cache") - } - - if data != nil { - t.Fatal("data should be nil") - } -} diff --git a/vendor/github.com/koding/cache/lru_nots_test.go b/vendor/github.com/koding/cache/lru_nots_test.go deleted file mode 100644 index 2103369bb..000000000 --- a/vendor/github.com/koding/cache/lru_nots_test.go +++ /dev/null @@ -1,33 +0,0 @@ -package cache - -import "testing" - -func TestLRUNoTSGetSet(t *testing.T) { - cache := NewLRUNoTS(2) - testCacheGetSet(t, cache) -} - -func TestLRUNoTSEviction(t *testing.T) { - cache := NewLRUNoTS(2) - testCacheGetSet(t, cache) - - err := cache.Set("test_key3", "test_data3") - if err != nil { - t.Fatal("should not give err while setting item") - } - - _, err = cache.Get("test_key") - if err == nil { - t.Fatal("test_key should not be in the cache") - } -} - -func TestLRUNoTSDelete(t *testing.T) { - cache := NewLRUNoTS(2) - testCacheDelete(t, cache) -} - -func TestLRUNoTSNilValue(t *testing.T) { - cache := NewLRUNoTS(2) - testCacheNilValue(t, cache) -} diff --git a/vendor/github.com/koding/cache/lru_test.go b/vendor/github.com/koding/cache/lru_test.go deleted file mode 100644 index 2bae93db5..000000000 --- a/vendor/github.com/koding/cache/lru_test.go +++ /dev/null @@ -1,33 +0,0 @@ -package cache - -import "testing" - -func TestLRUGetSet(t *testing.T) { - cache := NewLRU(2) - testCacheGetSet(t, cache) -} - -func TestLRUEviction(t *testing.T) { - cache := NewLRU(2) - testCacheGetSet(t, cache) - - err := cache.Set("test_key3", "test_data3") - if err != nil { - t.Fatal("should not give err while setting item") - } - - _, err = cache.Get("test_key") - if err == nil { - t.Fatal("test_key should not be in the cache") - } -} - -func TestLRUDelete(t *testing.T) { - cache := NewLRU(2) - testCacheDelete(t, cache) -} - -func TestLRUNilValue(t *testing.T) { - cache := NewLRU(2) - testCacheNilValue(t, cache) -} diff --git a/vendor/github.com/koding/cache/memory_nots_test.go b/vendor/github.com/koding/cache/memory_nots_test.go deleted file mode 100644 index 1dc1e563b..000000000 --- a/vendor/github.com/koding/cache/memory_nots_test.go +++ /dev/null @@ -1,18 +0,0 @@ -package cache - -import "testing" - -func TestMemoryCacheNoTSGetSet(t *testing.T) { - cache := NewMemoryNoTS() - testCacheGetSet(t, cache) -} - -func TestMemoryCacheNoTSDelete(t *testing.T) { - cache := NewMemoryNoTS() - testCacheDelete(t, cache) -} - -func TestMemoryCacheNoTSNilValue(t *testing.T) { - cache := NewMemoryNoTS() - testCacheNilValue(t, cache) -} diff --git a/vendor/github.com/koding/cache/memory_test.go b/vendor/github.com/koding/cache/memory_test.go deleted file mode 100644 index 6b4b74443..000000000 --- a/vendor/github.com/koding/cache/memory_test.go +++ /dev/null @@ -1,18 +0,0 @@ -package cache - -import "testing" - -func TestMemoryGetSet(t *testing.T) { - cache := NewMemory() - testCacheGetSet(t, cache) -} - -func TestMemoryDelete(t *testing.T) { - cache := NewMemory() - testCacheDelete(t, cache) -} - -func TestMemoryNilValue(t *testing.T) { - cache := NewMemory() - testCacheNilValue(t, cache) -} diff --git a/vendor/github.com/koding/cache/memory_ttl_test.go b/vendor/github.com/koding/cache/memory_ttl_test.go deleted file mode 100644 index f19150d48..000000000 --- a/vendor/github.com/koding/cache/memory_ttl_test.go +++ /dev/null @@ -1,43 +0,0 @@ -package cache - -import ( - "testing" - "time" -) - -func TestMemoryCacheGetSet(t *testing.T) { - cache := NewMemoryWithTTL(2 * time.Second) - cache.StartGC(time.Millisecond * 10) - cache.Set("test_key", "test_data") - data, err := cache.Get("test_key") - if err != nil { - t.Fatal("data not found") - } - if data != "test_data" { - t.Fatal("data is not \"test_data\"") - } -} - -func TestMemoryCacheTTL(t *testing.T) { - cache := NewMemoryWithTTL(100 * time.Millisecond) - cache.StartGC(time.Millisecond * 10) - cache.Set("test_key", "test_data") - time.Sleep(200 * time.Millisecond) - _, err := cache.Get("test_key") - if err == nil { - t.Fatal("data found") - } -} - -func TestMemoryCacheTTLNilValue(t *testing.T) { - cache := NewMemoryWithTTL(100 * time.Millisecond) - cache.StartGC(time.Millisecond * 10) - cache.Set("test_key", nil) - data, err := cache.Get("test_key") - if err != nil { - t.Fatal("data found") - } - if data != nil { - t.Fatal("data is not null") - } -} diff --git a/vendor/github.com/lib/pq/bench_test.go b/vendor/github.com/lib/pq/bench_test.go deleted file mode 100644 index e71f41d06..000000000 --- a/vendor/github.com/lib/pq/bench_test.go +++ /dev/null @@ -1,435 +0,0 @@ -// +build go1.1 - -package pq - -import ( - "bufio" - "bytes" - "database/sql" - "database/sql/driver" - "io" - "math/rand" - "net" - "runtime" - "strconv" - "strings" - "sync" - "testing" - "time" - - "github.com/lib/pq/oid" -) - -var ( - selectStringQuery = "SELECT '" + strings.Repeat("0123456789", 10) + "'" - selectSeriesQuery = "SELECT generate_series(1, 100)" -) - -func BenchmarkSelectString(b *testing.B) { - var result string - benchQuery(b, selectStringQuery, &result) -} - -func BenchmarkSelectSeries(b *testing.B) { - var result int - benchQuery(b, selectSeriesQuery, &result) -} - -func benchQuery(b *testing.B, query string, result interface{}) { - b.StopTimer() - db := openTestConn(b) - defer db.Close() - b.StartTimer() - - for i := 0; i < b.N; i++ { - benchQueryLoop(b, db, query, result) - } -} - -func benchQueryLoop(b *testing.B, db *sql.DB, query string, result interface{}) { - rows, err := db.Query(query) - if err != nil { - b.Fatal(err) - } - defer rows.Close() - for rows.Next() { - err = rows.Scan(result) - if err != nil { - b.Fatal("failed to scan", err) - } - } -} - -// reading from circularConn yields content[:prefixLen] once, followed by -// content[prefixLen:] over and over again. It never returns EOF. -type circularConn struct { - content string - prefixLen int - pos int - net.Conn // for all other net.Conn methods that will never be called -} - -func (r *circularConn) Read(b []byte) (n int, err error) { - n = copy(b, r.content[r.pos:]) - r.pos += n - if r.pos >= len(r.content) { - r.pos = r.prefixLen - } - return -} - -func (r *circularConn) Write(b []byte) (n int, err error) { return len(b), nil } - -func (r *circularConn) Close() error { return nil } - -func fakeConn(content string, prefixLen int) *conn { - c := &circularConn{content: content, prefixLen: prefixLen} - return &conn{buf: bufio.NewReader(c), c: c} -} - -// This benchmark is meant to be the same as BenchmarkSelectString, but takes -// out some of the factors this package can't control. The numbers are less noisy, -// but also the costs of network communication aren't accurately represented. -func BenchmarkMockSelectString(b *testing.B) { - b.StopTimer() - // taken from a recorded run of BenchmarkSelectString - // See: http://www.postgresql.org/docs/current/static/protocol-message-formats.html - const response = "1\x00\x00\x00\x04" + - "t\x00\x00\x00\x06\x00\x00" + - "T\x00\x00\x00!\x00\x01?column?\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\xc1\xff\xfe\xff\xff\xff\xff\x00\x00" + - "Z\x00\x00\x00\x05I" + - "2\x00\x00\x00\x04" + - "D\x00\x00\x00n\x00\x01\x00\x00\x00d0123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789" + - "C\x00\x00\x00\rSELECT 1\x00" + - "Z\x00\x00\x00\x05I" + - "3\x00\x00\x00\x04" + - "Z\x00\x00\x00\x05I" - c := fakeConn(response, 0) - b.StartTimer() - - for i := 0; i < b.N; i++ { - benchMockQuery(b, c, selectStringQuery) - } -} - -var seriesRowData = func() string { - var buf bytes.Buffer - for i := 1; i <= 100; i++ { - digits := byte(2) - if i >= 100 { - digits = 3 - } else if i < 10 { - digits = 1 - } - buf.WriteString("D\x00\x00\x00") - buf.WriteByte(10 + digits) - buf.WriteString("\x00\x01\x00\x00\x00") - buf.WriteByte(digits) - buf.WriteString(strconv.Itoa(i)) - } - return buf.String() -}() - -func BenchmarkMockSelectSeries(b *testing.B) { - b.StopTimer() - var response = "1\x00\x00\x00\x04" + - "t\x00\x00\x00\x06\x00\x00" + - "T\x00\x00\x00!\x00\x01?column?\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\xc1\xff\xfe\xff\xff\xff\xff\x00\x00" + - "Z\x00\x00\x00\x05I" + - "2\x00\x00\x00\x04" + - seriesRowData + - "C\x00\x00\x00\x0fSELECT 100\x00" + - "Z\x00\x00\x00\x05I" + - "3\x00\x00\x00\x04" + - "Z\x00\x00\x00\x05I" - c := fakeConn(response, 0) - b.StartTimer() - - for i := 0; i < b.N; i++ { - benchMockQuery(b, c, selectSeriesQuery) - } -} - -func benchMockQuery(b *testing.B, c *conn, query string) { - stmt, err := c.Prepare(query) - if err != nil { - b.Fatal(err) - } - defer stmt.Close() - rows, err := stmt.Query(nil) - if err != nil { - b.Fatal(err) - } - defer rows.Close() - var dest [1]driver.Value - for { - if err := rows.Next(dest[:]); err != nil { - if err == io.EOF { - break - } - b.Fatal(err) - } - } -} - -func BenchmarkPreparedSelectString(b *testing.B) { - var result string - benchPreparedQuery(b, selectStringQuery, &result) -} - -func BenchmarkPreparedSelectSeries(b *testing.B) { - var result int - benchPreparedQuery(b, selectSeriesQuery, &result) -} - -func benchPreparedQuery(b *testing.B, query string, result interface{}) { - b.StopTimer() - db := openTestConn(b) - defer db.Close() - stmt, err := db.Prepare(query) - if err != nil { - b.Fatal(err) - } - defer stmt.Close() - b.StartTimer() - - for i := 0; i < b.N; i++ { - benchPreparedQueryLoop(b, db, stmt, result) - } -} - -func benchPreparedQueryLoop(b *testing.B, db *sql.DB, stmt *sql.Stmt, result interface{}) { - rows, err := stmt.Query() - if err != nil { - b.Fatal(err) - } - if !rows.Next() { - rows.Close() - b.Fatal("no rows") - } - defer rows.Close() - for rows.Next() { - err = rows.Scan(&result) - if err != nil { - b.Fatal("failed to scan") - } - } -} - -// See the comment for BenchmarkMockSelectString. -func BenchmarkMockPreparedSelectString(b *testing.B) { - b.StopTimer() - const parseResponse = "1\x00\x00\x00\x04" + - "t\x00\x00\x00\x06\x00\x00" + - "T\x00\x00\x00!\x00\x01?column?\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\xc1\xff\xfe\xff\xff\xff\xff\x00\x00" + - "Z\x00\x00\x00\x05I" - const responses = parseResponse + - "2\x00\x00\x00\x04" + - "D\x00\x00\x00n\x00\x01\x00\x00\x00d0123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789" + - "C\x00\x00\x00\rSELECT 1\x00" + - "Z\x00\x00\x00\x05I" - c := fakeConn(responses, len(parseResponse)) - - stmt, err := c.Prepare(selectStringQuery) - if err != nil { - b.Fatal(err) - } - b.StartTimer() - - for i := 0; i < b.N; i++ { - benchPreparedMockQuery(b, c, stmt) - } -} - -func BenchmarkMockPreparedSelectSeries(b *testing.B) { - b.StopTimer() - const parseResponse = "1\x00\x00\x00\x04" + - "t\x00\x00\x00\x06\x00\x00" + - "T\x00\x00\x00!\x00\x01?column?\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\xc1\xff\xfe\xff\xff\xff\xff\x00\x00" + - "Z\x00\x00\x00\x05I" - var responses = parseResponse + - "2\x00\x00\x00\x04" + - seriesRowData + - "C\x00\x00\x00\x0fSELECT 100\x00" + - "Z\x00\x00\x00\x05I" - c := fakeConn(responses, len(parseResponse)) - - stmt, err := c.Prepare(selectSeriesQuery) - if err != nil { - b.Fatal(err) - } - b.StartTimer() - - for i := 0; i < b.N; i++ { - benchPreparedMockQuery(b, c, stmt) - } -} - -func benchPreparedMockQuery(b *testing.B, c *conn, stmt driver.Stmt) { - rows, err := stmt.Query(nil) - if err != nil { - b.Fatal(err) - } - defer rows.Close() - var dest [1]driver.Value - for { - if err := rows.Next(dest[:]); err != nil { - if err == io.EOF { - break - } - b.Fatal(err) - } - } -} - -func BenchmarkEncodeInt64(b *testing.B) { - for i := 0; i < b.N; i++ { - encode(¶meterStatus{}, int64(1234), oid.T_int8) - } -} - -func BenchmarkEncodeFloat64(b *testing.B) { - for i := 0; i < b.N; i++ { - encode(¶meterStatus{}, 3.14159, oid.T_float8) - } -} - -var testByteString = []byte("abcdefghijklmnopqrstuvwxyz") - -func BenchmarkEncodeByteaHex(b *testing.B) { - for i := 0; i < b.N; i++ { - encode(¶meterStatus{serverVersion: 90000}, testByteString, oid.T_bytea) - } -} -func BenchmarkEncodeByteaEscape(b *testing.B) { - for i := 0; i < b.N; i++ { - encode(¶meterStatus{serverVersion: 84000}, testByteString, oid.T_bytea) - } -} - -func BenchmarkEncodeBool(b *testing.B) { - for i := 0; i < b.N; i++ { - encode(¶meterStatus{}, true, oid.T_bool) - } -} - -var testTimestamptz = time.Date(2001, time.January, 1, 0, 0, 0, 0, time.Local) - -func BenchmarkEncodeTimestamptz(b *testing.B) { - for i := 0; i < b.N; i++ { - encode(¶meterStatus{}, testTimestamptz, oid.T_timestamptz) - } -} - -var testIntBytes = []byte("1234") - -func BenchmarkDecodeInt64(b *testing.B) { - for i := 0; i < b.N; i++ { - decode(¶meterStatus{}, testIntBytes, oid.T_int8, formatText) - } -} - -var testFloatBytes = []byte("3.14159") - -func BenchmarkDecodeFloat64(b *testing.B) { - for i := 0; i < b.N; i++ { - decode(¶meterStatus{}, testFloatBytes, oid.T_float8, formatText) - } -} - -var testBoolBytes = []byte{'t'} - -func BenchmarkDecodeBool(b *testing.B) { - for i := 0; i < b.N; i++ { - decode(¶meterStatus{}, testBoolBytes, oid.T_bool, formatText) - } -} - -func TestDecodeBool(t *testing.T) { - db := openTestConn(t) - rows, err := db.Query("select true") - if err != nil { - t.Fatal(err) - } - rows.Close() -} - -var testTimestamptzBytes = []byte("2013-09-17 22:15:32.360754-07") - -func BenchmarkDecodeTimestamptz(b *testing.B) { - for i := 0; i < b.N; i++ { - decode(¶meterStatus{}, testTimestamptzBytes, oid.T_timestamptz, formatText) - } -} - -func BenchmarkDecodeTimestamptzMultiThread(b *testing.B) { - oldProcs := runtime.GOMAXPROCS(0) - defer runtime.GOMAXPROCS(oldProcs) - runtime.GOMAXPROCS(runtime.NumCPU()) - globalLocationCache = newLocationCache() - - f := func(wg *sync.WaitGroup, loops int) { - defer wg.Done() - for i := 0; i < loops; i++ { - decode(¶meterStatus{}, testTimestamptzBytes, oid.T_timestamptz, formatText) - } - } - - wg := &sync.WaitGroup{} - b.ResetTimer() - for j := 0; j < 10; j++ { - wg.Add(1) - go f(wg, b.N/10) - } - wg.Wait() -} - -func BenchmarkLocationCache(b *testing.B) { - globalLocationCache = newLocationCache() - for i := 0; i < b.N; i++ { - globalLocationCache.getLocation(rand.Intn(10000)) - } -} - -func BenchmarkLocationCacheMultiThread(b *testing.B) { - oldProcs := runtime.GOMAXPROCS(0) - defer runtime.GOMAXPROCS(oldProcs) - runtime.GOMAXPROCS(runtime.NumCPU()) - globalLocationCache = newLocationCache() - - f := func(wg *sync.WaitGroup, loops int) { - defer wg.Done() - for i := 0; i < loops; i++ { - globalLocationCache.getLocation(rand.Intn(10000)) - } - } - - wg := &sync.WaitGroup{} - b.ResetTimer() - for j := 0; j < 10; j++ { - wg.Add(1) - go f(wg, b.N/10) - } - wg.Wait() -} - -// Stress test the performance of parsing results from the wire. -func BenchmarkResultParsing(b *testing.B) { - b.StopTimer() - - db := openTestConn(b) - defer db.Close() - _, err := db.Exec("BEGIN") - if err != nil { - b.Fatal(err) - } - - b.StartTimer() - for i := 0; i < b.N; i++ { - res, err := db.Query("SELECT generate_series(1, 50000)") - if err != nil { - b.Fatal(err) - } - res.Close() - } -} diff --git a/vendor/github.com/lib/pq/certs/README b/vendor/github.com/lib/pq/certs/README deleted file mode 100644 index 24ab7b256..000000000 --- a/vendor/github.com/lib/pq/certs/README +++ /dev/null @@ -1,3 +0,0 @@ -This directory contains certificates and private keys for testing some -SSL-related functionality in Travis. Do NOT use these certificates for -anything other than testing. diff --git a/vendor/github.com/lib/pq/certs/postgresql.crt b/vendor/github.com/lib/pq/certs/postgresql.crt deleted file mode 100644 index 6e6b4284a..000000000 --- a/vendor/github.com/lib/pq/certs/postgresql.crt +++ /dev/null @@ -1,69 +0,0 @@ -Certificate: - Data: - Version: 3 (0x2) - Serial Number: 2 (0x2) - Signature Algorithm: sha256WithRSAEncryption - Issuer: C=US, ST=Nevada, L=Las Vegas, O=github.com/lib/pq, CN=pq CA - Validity - Not Before: Oct 11 15:10:11 2014 GMT - Not After : Oct 8 15:10:11 2024 GMT - Subject: C=US, ST=Nevada, L=Las Vegas, O=github.com/lib/pq, CN=pqgosslcert - Subject Public Key Info: - Public Key Algorithm: rsaEncryption - RSA Public Key: (1024 bit) - Modulus (1024 bit): - 00:e3:8c:06:9a:70:54:51:d1:34:34:83:39:cd:a2: - 59:0f:05:ed:8d:d8:0e:34:d0:92:f4:09:4d:ee:8c: - 78:55:49:24:f8:3c:e0:34:58:02:b2:e7:94:58:c1: - e8:e5:bb:d1:af:f6:54:c1:40:b1:90:70:79:0d:35: - 54:9c:8f:16:e9:c2:f0:92:e6:64:49:38:c1:76:f8: - 47:66:c4:5b:4a:b6:a9:43:ce:c8:be:6c:4d:2b:94: - 97:3c:55:bc:d1:d0:6e:b7:53:ae:89:5c:4b:6b:86: - 40:be:c1:ae:1e:64:ce:9c:ae:87:0a:69:e5:c8:21: - 12:be:ae:1d:f6:45:df:16:a7 - Exponent: 65537 (0x10001) - X509v3 extensions: - X509v3 Subject Key Identifier: - 9B:25:31:63:A2:D8:06:FF:CB:E3:E9:96:FF:0D:BA:DC:12:7D:04:CF - X509v3 Authority Key Identifier: - keyid:52:93:ED:1E:76:0A:9F:65:4F:DE:19:66:C1:D5:22:40:35:CB:A0:72 - - X509v3 Basic Constraints: - CA:FALSE - X509v3 Key Usage: - Digital Signature, Non Repudiation, Key Encipherment - Signature Algorithm: sha256WithRSAEncryption - 3e:f5:f8:0b:4e:11:bd:00:86:1f:ce:dc:97:02:98:91:11:f5: - 65:f6:f2:8a:b2:3e:47:92:05:69:28:c9:e9:b4:f7:cf:93:d1: - 2d:81:5d:00:3c:23:be:da:70:ea:59:e1:2c:d3:25:49:ae:a6: - 95:54:c1:10:df:23:e3:fe:d6:e4:76:c7:6b:73:ad:1b:34:7c: - e2:56:cc:c0:37:ae:c5:7a:11:20:6c:3d:05:0e:99:cd:22:6c: - cf:59:a1:da:28:d4:65:ba:7d:2f:2b:3d:69:6d:a6:c1:ae:57: - bf:56:64:13:79:f8:48:46:65:eb:81:67:28:0b:7b:de:47:10: - b3:80:3c:31:d1:58:94:01:51:4a:c7:c8:1a:01:a8:af:c4:cd: - bb:84:a5:d9:8b:b4:b9:a1:64:3e:95:d9:90:1d:d5:3f:67:cc: - 3b:ba:f5:b4:d1:33:77:ee:c2:d2:3e:7e:c5:66:6e:b7:35:4c: - 60:57:b0:b8:be:36:c8:f3:d3:95:8c:28:4a:c9:f7:27:a4:0d: - e5:96:99:eb:f5:c8:bd:f3:84:6d:ef:02:f9:8a:36:7d:6b:5f: - 36:68:37:41:d9:74:ae:c6:78:2e:44:86:a1:ad:43:ca:fb:b5: - 3e:ba:10:23:09:02:ac:62:d1:d0:83:c8:95:b9:e3:5e:30:ff: - 5b:2b:38:fa ------BEGIN CERTIFICATE----- -MIIDEzCCAfugAwIBAgIBAjANBgkqhkiG9w0BAQsFADBeMQswCQYDVQQGEwJVUzEP -MA0GA1UECBMGTmV2YWRhMRIwEAYDVQQHEwlMYXMgVmVnYXMxGjAYBgNVBAoTEWdp -dGh1Yi5jb20vbGliL3BxMQ4wDAYDVQQDEwVwcSBDQTAeFw0xNDEwMTExNTEwMTFa -Fw0yNDEwMDgxNTEwMTFaMGQxCzAJBgNVBAYTAlVTMQ8wDQYDVQQIEwZOZXZhZGEx -EjAQBgNVBAcTCUxhcyBWZWdhczEaMBgGA1UEChMRZ2l0aHViLmNvbS9saWIvcHEx -FDASBgNVBAMTC3BxZ29zc2xjZXJ0MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKB -gQDjjAaacFRR0TQ0gznNolkPBe2N2A400JL0CU3ujHhVSST4POA0WAKy55RYwejl -u9Gv9lTBQLGQcHkNNVScjxbpwvCS5mRJOMF2+EdmxFtKtqlDzsi+bE0rlJc8VbzR -0G63U66JXEtrhkC+wa4eZM6crocKaeXIIRK+rh32Rd8WpwIDAQABo1owWDAdBgNV -HQ4EFgQUmyUxY6LYBv/L4+mW/w263BJ9BM8wHwYDVR0jBBgwFoAUUpPtHnYKn2VP -3hlmwdUiQDXLoHIwCQYDVR0TBAIwADALBgNVHQ8EBAMCBeAwDQYJKoZIhvcNAQEL -BQADggEBAD71+AtOEb0Ahh/O3JcCmJER9WX28oqyPkeSBWkoyem098+T0S2BXQA8 -I77acOpZ4SzTJUmuppVUwRDfI+P+1uR2x2tzrRs0fOJWzMA3rsV6ESBsPQUOmc0i -bM9Zodoo1GW6fS8rPWltpsGuV79WZBN5+EhGZeuBZygLe95HELOAPDHRWJQBUUrH -yBoBqK/EzbuEpdmLtLmhZD6V2ZAd1T9nzDu69bTRM3fuwtI+fsVmbrc1TGBXsLi+ -Nsjz05WMKErJ9yekDeWWmev1yL3zhG3vAvmKNn1rXzZoN0HZdK7GeC5EhqGtQ8r7 -tT66ECMJAqxi0dCDyJW5414w/1srOPo= ------END CERTIFICATE----- diff --git a/vendor/github.com/lib/pq/certs/postgresql.key b/vendor/github.com/lib/pq/certs/postgresql.key deleted file mode 100644 index eb8b20be9..000000000 --- a/vendor/github.com/lib/pq/certs/postgresql.key +++ /dev/null @@ -1,15 +0,0 @@ ------BEGIN RSA PRIVATE KEY----- -MIICWwIBAAKBgQDjjAaacFRR0TQ0gznNolkPBe2N2A400JL0CU3ujHhVSST4POA0 -WAKy55RYwejlu9Gv9lTBQLGQcHkNNVScjxbpwvCS5mRJOMF2+EdmxFtKtqlDzsi+ -bE0rlJc8VbzR0G63U66JXEtrhkC+wa4eZM6crocKaeXIIRK+rh32Rd8WpwIDAQAB -AoGAM5dM6/kp9P700i8qjOgRPym96Zoh5nGfz/rIE5z/r36NBkdvIg8OVZfR96nH -b0b9TOMR5lsPp0sI9yivTWvX6qyvLJRWy2vvx17hXK9NxXUNTAm0PYZUTvCtcPeX -RnJpzQKNZQPkFzF0uXBc4CtPK2Vz0+FGvAelrhYAxnw1dIkCQQD+9qaW5QhXjsjb -Nl85CmXgxPmGROcgLQCO+omfrjf9UXrituU9Dz6auym5lDGEdMFnkzfr+wpasEy9 -mf5ZZOhDAkEA5HjXfVGaCtpydOt6hDon/uZsyssCK2lQ7NSuE3vP+sUsYMzIpEoy -t3VWXqKbo+g9KNDTP4WEliqp1aiSIylzzQJANPeqzihQnlgEdD4MdD4rwhFJwVIp -Le8Lcais1KaN7StzOwxB/XhgSibd2TbnPpw+3bSg5n5lvUdo+e62/31OHwJAU1jS -I+F09KikQIr28u3UUWT2IzTT4cpVv1AHAQyV3sG3YsjSGT0IK20eyP9BEBZU2WL0 -7aNjrvR5aHxKc5FXsQJABsFtyGpgI5X4xufkJZVZ+Mklz2n7iXa+XPatMAHFxAtb -EEMt60rngwMjXAzBSC6OYuYogRRAY3UCacNC5VhLYQ== ------END RSA PRIVATE KEY----- diff --git a/vendor/github.com/lib/pq/certs/root.crt b/vendor/github.com/lib/pq/certs/root.crt deleted file mode 100644 index aecf8f621..000000000 --- a/vendor/github.com/lib/pq/certs/root.crt +++ /dev/null @@ -1,24 +0,0 @@ ------BEGIN CERTIFICATE----- -MIIEAzCCAuugAwIBAgIJANmheROCdW1NMA0GCSqGSIb3DQEBBQUAMF4xCzAJBgNV -BAYTAlVTMQ8wDQYDVQQIEwZOZXZhZGExEjAQBgNVBAcTCUxhcyBWZWdhczEaMBgG -A1UEChMRZ2l0aHViLmNvbS9saWIvcHExDjAMBgNVBAMTBXBxIENBMB4XDTE0MTAx -MTE1MDQyOVoXDTI0MTAwODE1MDQyOVowXjELMAkGA1UEBhMCVVMxDzANBgNVBAgT -Bk5ldmFkYTESMBAGA1UEBxMJTGFzIFZlZ2FzMRowGAYDVQQKExFnaXRodWIuY29t -L2xpYi9wcTEOMAwGA1UEAxMFcHEgQ0EwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAw -ggEKAoIBAQCV4PxP7ShzWBzUCThcKk3qZtOLtHmszQVtbqhvgTpm1kTRtKBdVMu0 -pLAHQ3JgJCnAYgH0iZxVGoMP16T3irdgsdC48+nNTFM2T0cCdkfDURGIhSFN47cb -Pgy306BcDUD2q7ucW33+dlFSRuGVewocoh4BWM/vMtMvvWzdi4Ag/L/jhb+5wZxZ -sWymsadOVSDePEMKOvlCa3EdVwVFV40TVyDb+iWBUivDAYsS2a3KajuJrO6MbZiE -Sp2RCIkZS2zFmzWxVRi9ZhzIZhh7EVF9JAaNC3T52jhGUdlRq3YpBTMnd89iOh74 -6jWXG7wSuPj3haFzyNhmJ0ZUh+2Ynoh1AgMBAAGjgcMwgcAwHQYDVR0OBBYEFFKT -7R52Cp9lT94ZZsHVIkA1y6ByMIGQBgNVHSMEgYgwgYWAFFKT7R52Cp9lT94ZZsHV -IkA1y6ByoWKkYDBeMQswCQYDVQQGEwJVUzEPMA0GA1UECBMGTmV2YWRhMRIwEAYD -VQQHEwlMYXMgVmVnYXMxGjAYBgNVBAoTEWdpdGh1Yi5jb20vbGliL3BxMQ4wDAYD -VQQDEwVwcSBDQYIJANmheROCdW1NMAwGA1UdEwQFMAMBAf8wDQYJKoZIhvcNAQEF -BQADggEBAAEhCLWkqJNMI8b4gkbmj5fqQ/4+oO83bZ3w2Oqf6eZ8I8BC4f2NOyE6 -tRUlq5+aU7eqC1cOAvGjO+YHN/bF/DFpwLlzvUSXt+JP/pYcUjL7v+pIvwqec9hD -ndvM4iIbkD/H/OYQ3L+N3W+G1x7AcFIX+bGCb3PzYVQAjxreV6//wgKBosMGFbZo -HPxT9RPMun61SViF04H5TNs0derVn1+5eiiYENeAhJzQNyZoOOUuX1X/Inx9bEPh -C5vFBtSMgIytPgieRJVWAiMLYsfpIAStrHztRAbBs2DU01LmMgRvHdxgFEKinC/d -UHZZQDP+6pT+zADrGhQGXe4eThaO6f0= ------END CERTIFICATE----- diff --git a/vendor/github.com/lib/pq/certs/server.crt b/vendor/github.com/lib/pq/certs/server.crt deleted file mode 100644 index ddc995a6d..000000000 --- a/vendor/github.com/lib/pq/certs/server.crt +++ /dev/null @@ -1,81 +0,0 @@ -Certificate: - Data: - Version: 3 (0x2) - Serial Number: 1 (0x1) - Signature Algorithm: sha256WithRSAEncryption - Issuer: C=US, ST=Nevada, L=Las Vegas, O=github.com/lib/pq, CN=pq CA - Validity - Not Before: Oct 11 15:05:15 2014 GMT - Not After : Oct 8 15:05:15 2024 GMT - Subject: C=US, ST=Nevada, L=Las Vegas, O=github.com/lib/pq, CN=postgres - Subject Public Key Info: - Public Key Algorithm: rsaEncryption - RSA Public Key: (2048 bit) - Modulus (2048 bit): - 00:d7:8a:4c:85:fb:17:a5:3c:8f:e0:72:11:29:ce: - 3f:b0:1f:3f:7d:c6:ee:7f:a7:fc:02:2b:35:47:08: - a6:3d:90:df:5c:56:14:94:00:c7:6d:d1:d2:e2:61: - 95:77:b8:e3:a6:66:31:f9:1f:21:7d:62:e1:27:da: - 94:37:61:4a:ea:63:53:a0:61:b8:9c:bb:a5:e2:e7: - b7:a6:d8:0f:05:04:c7:29:e2:ea:49:2b:7f:de:15: - 00:a6:18:70:50:c7:0c:de:9a:f9:5a:96:b0:e1:94: - 06:c6:6d:4a:21:3b:b4:0f:a5:6d:92:86:34:b2:4e: - d7:0e:a7:19:c0:77:0b:7b:87:c8:92:de:42:ff:86: - d2:b7:9a:a4:d4:15:23:ca:ad:a5:69:21:b8:ce:7e: - 66:cb:85:5d:b9:ed:8b:2d:09:8d:94:e4:04:1e:72: - ec:ef:d0:76:90:15:5a:a4:f7:91:4b:e9:ce:4e:9d: - 5d:9a:70:17:9c:d8:e9:73:83:ea:3d:61:99:a6:cd: - ac:91:40:5a:88:77:e5:4e:2a:8e:3d:13:f3:f9:38: - 6f:81:6b:8a:95:ca:0e:07:ab:6f:da:b4:8c:d9:ff: - aa:78:03:aa:c7:c2:cf:6f:64:92:d3:d8:83:d5:af: - f1:23:18:a7:2e:7b:17:0b:e7:7d:f1:fa:a8:41:a3: - 04:57 - Exponent: 65537 (0x10001) - X509v3 extensions: - X509v3 Subject Key Identifier: - EE:F0:B3:46:DC:C7:09:EB:0E:B6:2F:E5:FE:62:60:45:44:9F:59:CC - X509v3 Authority Key Identifier: - keyid:52:93:ED:1E:76:0A:9F:65:4F:DE:19:66:C1:D5:22:40:35:CB:A0:72 - - X509v3 Basic Constraints: - CA:FALSE - X509v3 Key Usage: - Digital Signature, Non Repudiation, Key Encipherment - Signature Algorithm: sha256WithRSAEncryption - 7e:5a:6e:be:bf:d2:6c:c1:d6:fa:b6:fb:3f:06:53:36:08:87: - 9d:95:b1:39:af:9e:f6:47:38:17:39:da:25:7c:f2:ad:0c:e3: - ab:74:19:ca:fb:8c:a0:50:c0:1d:19:8a:9c:21:ed:0f:3a:d1: - 96:54:2e:10:09:4f:b8:70:f7:2b:99:43:d2:c6:15:bc:3f:24: - 7d:28:39:32:3f:8d:a4:4f:40:75:7f:3e:0d:1c:d1:69:f2:4e: - 98:83:47:97:d2:25:ac:c9:36:86:2f:04:a6:c4:86:c7:c4:00: - 5f:7f:b9:ad:fc:bf:e9:f5:78:d7:82:1a:51:0d:fc:ab:9e:92: - 1d:5f:0c:18:d1:82:e0:14:c9:ce:91:89:71:ff:49:49:ff:35: - bf:7b:44:78:42:c1:d0:66:65:bb:28:2e:60:ca:9b:20:12:a9: - 90:61:b1:96:ec:15:46:c9:37:f7:07:90:8a:89:45:2a:3f:37: - ec:dc:e3:e5:8f:c3:3a:57:80:a5:54:60:0c:e1:b2:26:99:2b: - 40:7e:36:d1:9a:70:02:ec:63:f4:3b:72:ae:81:fb:30:20:6d: - cb:48:46:c6:b5:8f:39:b1:84:05:25:55:8d:f5:62:f6:1b:46: - 2e:da:a3:4c:26:12:44:d7:56:b6:b8:a9:ca:d3:ab:71:45:7c: - 9f:48:6d:1e ------BEGIN CERTIFICATE----- -MIIDlDCCAnygAwIBAgIBATANBgkqhkiG9w0BAQsFADBeMQswCQYDVQQGEwJVUzEP -MA0GA1UECBMGTmV2YWRhMRIwEAYDVQQHEwlMYXMgVmVnYXMxGjAYBgNVBAoTEWdp -dGh1Yi5jb20vbGliL3BxMQ4wDAYDVQQDEwVwcSBDQTAeFw0xNDEwMTExNTA1MTVa -Fw0yNDEwMDgxNTA1MTVaMGExCzAJBgNVBAYTAlVTMQ8wDQYDVQQIEwZOZXZhZGEx -EjAQBgNVBAcTCUxhcyBWZWdhczEaMBgGA1UEChMRZ2l0aHViLmNvbS9saWIvcHEx -ETAPBgNVBAMTCHBvc3RncmVzMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKC -AQEA14pMhfsXpTyP4HIRKc4/sB8/fcbuf6f8Ais1RwimPZDfXFYUlADHbdHS4mGV -d7jjpmYx+R8hfWLhJ9qUN2FK6mNToGG4nLul4ue3ptgPBQTHKeLqSSt/3hUAphhw -UMcM3pr5Wpaw4ZQGxm1KITu0D6VtkoY0sk7XDqcZwHcLe4fIkt5C/4bSt5qk1BUj -yq2laSG4zn5my4Vdue2LLQmNlOQEHnLs79B2kBVapPeRS+nOTp1dmnAXnNjpc4Pq -PWGZps2skUBaiHflTiqOPRPz+ThvgWuKlcoOB6tv2rSM2f+qeAOqx8LPb2SS09iD -1a/xIxinLnsXC+d98fqoQaMEVwIDAQABo1owWDAdBgNVHQ4EFgQU7vCzRtzHCesO -ti/l/mJgRUSfWcwwHwYDVR0jBBgwFoAUUpPtHnYKn2VP3hlmwdUiQDXLoHIwCQYD -VR0TBAIwADALBgNVHQ8EBAMCBeAwDQYJKoZIhvcNAQELBQADggEBAH5abr6/0mzB -1vq2+z8GUzYIh52VsTmvnvZHOBc52iV88q0M46t0Gcr7jKBQwB0Zipwh7Q860ZZU -LhAJT7hw9yuZQ9LGFbw/JH0oOTI/jaRPQHV/Pg0c0WnyTpiDR5fSJazJNoYvBKbE -hsfEAF9/ua38v+n1eNeCGlEN/Kuekh1fDBjRguAUyc6RiXH/SUn/Nb97RHhCwdBm -ZbsoLmDKmyASqZBhsZbsFUbJN/cHkIqJRSo/N+zc4+WPwzpXgKVUYAzhsiaZK0B+ -NtGacALsY/Q7cq6B+zAgbctIRsa1jzmxhAUlVY31YvYbRi7ao0wmEkTXVra4qcrT -q3FFfJ9IbR4= ------END CERTIFICATE----- diff --git a/vendor/github.com/lib/pq/certs/server.key b/vendor/github.com/lib/pq/certs/server.key deleted file mode 100644 index bd7b019b6..000000000 --- a/vendor/github.com/lib/pq/certs/server.key +++ /dev/null @@ -1,27 +0,0 @@ ------BEGIN RSA PRIVATE KEY----- -MIIEogIBAAKCAQEA14pMhfsXpTyP4HIRKc4/sB8/fcbuf6f8Ais1RwimPZDfXFYU -lADHbdHS4mGVd7jjpmYx+R8hfWLhJ9qUN2FK6mNToGG4nLul4ue3ptgPBQTHKeLq -SSt/3hUAphhwUMcM3pr5Wpaw4ZQGxm1KITu0D6VtkoY0sk7XDqcZwHcLe4fIkt5C -/4bSt5qk1BUjyq2laSG4zn5my4Vdue2LLQmNlOQEHnLs79B2kBVapPeRS+nOTp1d -mnAXnNjpc4PqPWGZps2skUBaiHflTiqOPRPz+ThvgWuKlcoOB6tv2rSM2f+qeAOq -x8LPb2SS09iD1a/xIxinLnsXC+d98fqoQaMEVwIDAQABAoIBAF3ZoihUhJ82F4+r -Gz4QyDpv4L1reT2sb1aiabhcU8ZK5nbWJG+tRyjSS/i2dNaEcttpdCj9HR/zhgZM -bm0OuAgG58rVwgS80CZUruq++Qs+YVojq8/gWPTiQD4SNhV2Fmx3HkwLgUk3oxuT -SsvdqzGE3okGVrutCIcgy126eA147VPMoej1Bb3fO6npqK0pFPhZfAc0YoqJuM+k -obRm5pAnGUipyLCFXjA9HYPKwYZw2RtfdA3CiImHeanSdqS+ctrC9y8BV40Th7gZ -haXdKUNdjmIxV695QQ1mkGqpKLZFqhzKioGQ2/Ly2d1iaKN9fZltTusu8unepWJ2 -tlT9qMECgYEA9uHaF1t2CqE+AJvWTihHhPIIuLxoOQXYea1qvxfcH/UMtaLKzCNm -lQ5pqCGsPvp+10f36yttO1ZehIvlVNXuJsjt0zJmPtIolNuJY76yeussfQ9jHheB -5uPEzCFlHzxYbBUyqgWaF6W74okRGzEGJXjYSP0yHPPdU4ep2q3bGiUCgYEA34Af -wBSuQSK7uLxArWHvQhyuvi43ZGXls6oRGl+Ysj54s8BP6XGkq9hEJ6G4yxgyV+BR -DUOs5X8/TLT8POuIMYvKTQthQyCk0eLv2FLdESDuuKx0kBVY3s8lK3/z5HhrdOiN -VMNZU+xDKgKc3hN9ypkk8vcZe6EtH7Y14e0rVcsCgYBTgxi8F/M5K0wG9rAqphNz -VFBA9XKn/2M33cKjO5X5tXIEKzpAjaUQvNxexG04rJGljzG8+mar0M6ONahw5yD1 -O7i/XWgazgpuOEkkVYiYbd8RutfDgR4vFVMn3hAP3eDnRtBplRWH9Ec3HTiNIys6 -F8PKBOQjyRZQQC7jyzW3hQKBgACe5HeuFwXLSOYsb6mLmhR+6+VPT4wR1F95W27N -USk9jyxAnngxfpmTkiziABdgS9N+pfr5cyN4BP77ia/Jn6kzkC5Cl9SN5KdIkA3z -vPVtN/x/ThuQU5zaymmig1ThGLtMYggYOslG4LDfLPxY5YKIhle+Y+259twdr2yf -Mf2dAoGAaGv3tWMgnIdGRk6EQL/yb9PKHo7ShN+tKNlGaK7WwzBdKs+Fe8jkgcr7 -pz4Ne887CmxejdISzOCcdT+Zm9Bx6I/uZwWOtDvWpIgIxVX9a9URj/+D1MxTE/y4 -d6H+c89yDY62I2+drMpdjCd3EtCaTlxpTbRS+s1eAHMH7aEkcCE= ------END RSA PRIVATE KEY----- diff --git a/vendor/github.com/lib/pq/conn_test.go b/vendor/github.com/lib/pq/conn_test.go deleted file mode 100644 index af07e5596..000000000 --- a/vendor/github.com/lib/pq/conn_test.go +++ /dev/null @@ -1,1306 +0,0 @@ -package pq - -import ( - "database/sql" - "database/sql/driver" - "fmt" - "io" - "os" - "reflect" - "strings" - "testing" - "time" -) - -type Fatalistic interface { - Fatal(args ...interface{}) -} - -func forceBinaryParameters() bool { - bp := os.Getenv("PQTEST_BINARY_PARAMETERS") - if bp == "yes" { - return true - } else if bp == "" || bp == "no" { - return false - } else { - panic("unexpected value for PQTEST_BINARY_PARAMETERS") - } -} - -func openTestConnConninfo(conninfo string) (*sql.DB, error) { - defaultTo := func(envvar string, value string) { - if os.Getenv(envvar) == "" { - os.Setenv(envvar, value) - } - } - defaultTo("PGDATABASE", "pqgotest") - defaultTo("PGSSLMODE", "disable") - defaultTo("PGCONNECT_TIMEOUT", "20") - - if forceBinaryParameters() && - !strings.HasPrefix(conninfo, "postgres://") && - !strings.HasPrefix(conninfo, "postgresql://") { - conninfo = conninfo + " binary_parameters=yes" - } - - return sql.Open("postgres", conninfo) -} - -func openTestConn(t Fatalistic) *sql.DB { - conn, err := openTestConnConninfo("") - if err != nil { - t.Fatal(err) - } - - return conn -} - -func getServerVersion(t *testing.T, db *sql.DB) int { - var version int - err := db.QueryRow("SHOW server_version_num").Scan(&version) - if err != nil { - t.Fatal(err) - } - return version -} - -func TestReconnect(t *testing.T) { - db1 := openTestConn(t) - defer db1.Close() - tx, err := db1.Begin() - if err != nil { - t.Fatal(err) - } - var pid1 int - err = tx.QueryRow("SELECT pg_backend_pid()").Scan(&pid1) - if err != nil { - t.Fatal(err) - } - db2 := openTestConn(t) - defer db2.Close() - _, err = db2.Exec("SELECT pg_terminate_backend($1)", pid1) - if err != nil { - t.Fatal(err) - } - // The rollback will probably "fail" because we just killed - // its connection above - _ = tx.Rollback() - - const expected int = 42 - var result int - err = db1.QueryRow(fmt.Sprintf("SELECT %d", expected)).Scan(&result) - if err != nil { - t.Fatal(err) - } - if result != expected { - t.Errorf("got %v; expected %v", result, expected) - } -} - -func TestCommitInFailedTransaction(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - txn, err := db.Begin() - if err != nil { - t.Fatal(err) - } - rows, err := txn.Query("SELECT error") - if err == nil { - rows.Close() - t.Fatal("expected failure") - } - err = txn.Commit() - if err != ErrInFailedTransaction { - t.Fatalf("expected ErrInFailedTransaction; got %#v", err) - } -} - -func TestOpenURL(t *testing.T) { - testURL := func(url string) { - db, err := openTestConnConninfo(url) - if err != nil { - t.Fatal(err) - } - defer db.Close() - // database/sql might not call our Open at all unless we do something with - // the connection - txn, err := db.Begin() - if err != nil { - t.Fatal(err) - } - txn.Rollback() - } - testURL("postgres://") - testURL("postgresql://") -} - -func TestExec(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - _, err := db.Exec("CREATE TEMP TABLE temp (a int)") - if err != nil { - t.Fatal(err) - } - - r, err := db.Exec("INSERT INTO temp VALUES (1)") - if err != nil { - t.Fatal(err) - } - - if n, _ := r.RowsAffected(); n != 1 { - t.Fatalf("expected 1 row affected, not %d", n) - } - - r, err = db.Exec("INSERT INTO temp VALUES ($1), ($2), ($3)", 1, 2, 3) - if err != nil { - t.Fatal(err) - } - - if n, _ := r.RowsAffected(); n != 3 { - t.Fatalf("expected 3 rows affected, not %d", n) - } - - // SELECT doesn't send the number of returned rows in the command tag - // before 9.0 - if getServerVersion(t, db) >= 90000 { - r, err = db.Exec("SELECT g FROM generate_series(1, 2) g") - if err != nil { - t.Fatal(err) - } - if n, _ := r.RowsAffected(); n != 2 { - t.Fatalf("expected 2 rows affected, not %d", n) - } - - r, err = db.Exec("SELECT g FROM generate_series(1, $1) g", 3) - if err != nil { - t.Fatal(err) - } - if n, _ := r.RowsAffected(); n != 3 { - t.Fatalf("expected 3 rows affected, not %d", n) - } - } -} - -func TestStatment(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - st, err := db.Prepare("SELECT 1") - if err != nil { - t.Fatal(err) - } - - st1, err := db.Prepare("SELECT 2") - if err != nil { - t.Fatal(err) - } - - r, err := st.Query() - if err != nil { - t.Fatal(err) - } - defer r.Close() - - if !r.Next() { - t.Fatal("expected row") - } - - var i int - err = r.Scan(&i) - if err != nil { - t.Fatal(err) - } - - if i != 1 { - t.Fatalf("expected 1, got %d", i) - } - - // st1 - - r1, err := st1.Query() - if err != nil { - t.Fatal(err) - } - defer r1.Close() - - if !r1.Next() { - if r.Err() != nil { - t.Fatal(r1.Err()) - } - t.Fatal("expected row") - } - - err = r1.Scan(&i) - if err != nil { - t.Fatal(err) - } - - if i != 2 { - t.Fatalf("expected 2, got %d", i) - } -} - -func TestRowsCloseBeforeDone(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - r, err := db.Query("SELECT 1") - if err != nil { - t.Fatal(err) - } - - err = r.Close() - if err != nil { - t.Fatal(err) - } - - if r.Next() { - t.Fatal("unexpected row") - } - - if r.Err() != nil { - t.Fatal(r.Err()) - } -} - -func TestParameterCountMismatch(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - var notused int - err := db.QueryRow("SELECT false", 1).Scan(¬used) - if err == nil { - t.Fatal("expected err") - } - // make sure we clean up correctly - err = db.QueryRow("SELECT 1").Scan(¬used) - if err != nil { - t.Fatal(err) - } - - err = db.QueryRow("SELECT $1").Scan(¬used) - if err == nil { - t.Fatal("expected err") - } - // make sure we clean up correctly - err = db.QueryRow("SELECT 1").Scan(¬used) - if err != nil { - t.Fatal(err) - } -} - -// Test that EmptyQueryResponses are handled correctly. -func TestEmptyQuery(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - _, err := db.Exec("") - if err != nil { - t.Fatal(err) - } - rows, err := db.Query("") - if err != nil { - t.Fatal(err) - } - cols, err := rows.Columns() - if err != nil { - t.Fatal(err) - } - if len(cols) != 0 { - t.Fatalf("unexpected number of columns %d in response to an empty query", len(cols)) - } - if rows.Next() { - t.Fatal("unexpected row") - } - if rows.Err() != nil { - t.Fatal(rows.Err()) - } - - stmt, err := db.Prepare("") - if err != nil { - t.Fatal(err) - } - _, err = stmt.Exec() - if err != nil { - t.Fatal(err) - } - rows, err = stmt.Query() - if err != nil { - t.Fatal(err) - } - cols, err = rows.Columns() - if err != nil { - t.Fatal(err) - } - if len(cols) != 0 { - t.Fatalf("unexpected number of columns %d in response to an empty query", len(cols)) - } - if rows.Next() { - t.Fatal("unexpected row") - } - if rows.Err() != nil { - t.Fatal(rows.Err()) - } -} - -func TestEncodeDecode(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - q := ` - SELECT - E'\\000\\001\\002'::bytea, - 'foobar'::text, - NULL::integer, - '2000-1-1 01:02:03.04-7'::timestamptz, - 0::boolean, - 123, - -321, - 3.14::float8 - WHERE - E'\\000\\001\\002'::bytea = $1 - AND 'foobar'::text = $2 - AND $3::integer is NULL - ` - // AND '2000-1-1 12:00:00.000000-7'::timestamp = $3 - - exp1 := []byte{0, 1, 2} - exp2 := "foobar" - - r, err := db.Query(q, exp1, exp2, nil) - if err != nil { - t.Fatal(err) - } - defer r.Close() - - if !r.Next() { - if r.Err() != nil { - t.Fatal(r.Err()) - } - t.Fatal("expected row") - } - - var got1 []byte - var got2 string - var got3 = sql.NullInt64{Valid: true} - var got4 time.Time - var got5, got6, got7, got8 interface{} - - err = r.Scan(&got1, &got2, &got3, &got4, &got5, &got6, &got7, &got8) - if err != nil { - t.Fatal(err) - } - - if !reflect.DeepEqual(exp1, got1) { - t.Errorf("expected %q byte: %q", exp1, got1) - } - - if !reflect.DeepEqual(exp2, got2) { - t.Errorf("expected %q byte: %q", exp2, got2) - } - - if got3.Valid { - t.Fatal("expected invalid") - } - - if got4.Year() != 2000 { - t.Fatal("wrong year") - } - - if got5 != false { - t.Fatalf("expected false, got %q", got5) - } - - if got6 != int64(123) { - t.Fatalf("expected 123, got %d", got6) - } - - if got7 != int64(-321) { - t.Fatalf("expected -321, got %d", got7) - } - - if got8 != float64(3.14) { - t.Fatalf("expected 3.14, got %f", got8) - } -} - -func TestNoData(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - st, err := db.Prepare("SELECT 1 WHERE true = false") - if err != nil { - t.Fatal(err) - } - defer st.Close() - - r, err := st.Query() - if err != nil { - t.Fatal(err) - } - defer r.Close() - - if r.Next() { - if r.Err() != nil { - t.Fatal(r.Err()) - } - t.Fatal("unexpected row") - } - - _, err = db.Query("SELECT * FROM nonexistenttable WHERE age=$1", 20) - if err == nil { - t.Fatal("Should have raised an error on non existent table") - } - - _, err = db.Query("SELECT * FROM nonexistenttable") - if err == nil { - t.Fatal("Should have raised an error on non existent table") - } -} - -func TestErrorDuringStartup(t *testing.T) { - // Don't use the normal connection setup, this is intended to - // blow up in the startup packet from a non-existent user. - db, err := openTestConnConninfo("user=thisuserreallydoesntexist") - if err != nil { - t.Fatal(err) - } - defer db.Close() - - _, err = db.Begin() - if err == nil { - t.Fatal("expected error") - } - - e, ok := err.(*Error) - if !ok { - t.Fatalf("expected Error, got %#v", err) - } else if e.Code.Name() != "invalid_authorization_specification" && e.Code.Name() != "invalid_password" { - t.Fatalf("expected invalid_authorization_specification or invalid_password, got %s (%+v)", e.Code.Name(), err) - } -} - -func TestBadConn(t *testing.T) { - var err error - - cn := conn{} - func() { - defer cn.errRecover(&err) - panic(io.EOF) - }() - if err != driver.ErrBadConn { - t.Fatalf("expected driver.ErrBadConn, got: %#v", err) - } - if !cn.bad { - t.Fatalf("expected cn.bad") - } - - cn = conn{} - func() { - defer cn.errRecover(&err) - e := &Error{Severity: Efatal} - panic(e) - }() - if err != driver.ErrBadConn { - t.Fatalf("expected driver.ErrBadConn, got: %#v", err) - } - if !cn.bad { - t.Fatalf("expected cn.bad") - } -} - -func TestErrorOnExec(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - txn, err := db.Begin() - if err != nil { - t.Fatal(err) - } - defer txn.Rollback() - - _, err = txn.Exec("CREATE TEMPORARY TABLE foo(f1 int PRIMARY KEY)") - if err != nil { - t.Fatal(err) - } - - _, err = txn.Exec("INSERT INTO foo VALUES (0), (0)") - if err == nil { - t.Fatal("Should have raised error") - } - - e, ok := err.(*Error) - if !ok { - t.Fatalf("expected Error, got %#v", err) - } else if e.Code.Name() != "unique_violation" { - t.Fatalf("expected unique_violation, got %s (%+v)", e.Code.Name(), err) - } -} - -func TestErrorOnQuery(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - txn, err := db.Begin() - if err != nil { - t.Fatal(err) - } - defer txn.Rollback() - - _, err = txn.Exec("CREATE TEMPORARY TABLE foo(f1 int PRIMARY KEY)") - if err != nil { - t.Fatal(err) - } - - _, err = txn.Query("INSERT INTO foo VALUES (0), (0)") - if err == nil { - t.Fatal("Should have raised error") - } - - e, ok := err.(*Error) - if !ok { - t.Fatalf("expected Error, got %#v", err) - } else if e.Code.Name() != "unique_violation" { - t.Fatalf("expected unique_violation, got %s (%+v)", e.Code.Name(), err) - } -} - -func TestErrorOnQueryRowSimpleQuery(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - txn, err := db.Begin() - if err != nil { - t.Fatal(err) - } - defer txn.Rollback() - - _, err = txn.Exec("CREATE TEMPORARY TABLE foo(f1 int PRIMARY KEY)") - if err != nil { - t.Fatal(err) - } - - var v int - err = txn.QueryRow("INSERT INTO foo VALUES (0), (0)").Scan(&v) - if err == nil { - t.Fatal("Should have raised error") - } - - e, ok := err.(*Error) - if !ok { - t.Fatalf("expected Error, got %#v", err) - } else if e.Code.Name() != "unique_violation" { - t.Fatalf("expected unique_violation, got %s (%+v)", e.Code.Name(), err) - } -} - -// Test the QueryRow bug workarounds in stmt.exec() and simpleQuery() -func TestQueryRowBugWorkaround(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - // stmt.exec() - _, err := db.Exec("CREATE TEMP TABLE notnulltemp (a varchar(10) not null)") - if err != nil { - t.Fatal(err) - } - - var a string - err = db.QueryRow("INSERT INTO notnulltemp(a) values($1) RETURNING a", nil).Scan(&a) - if err == sql.ErrNoRows { - t.Fatalf("expected constraint violation error; got: %v", err) - } - pge, ok := err.(*Error) - if !ok { - t.Fatalf("expected *Error; got: %#v", err) - } - if pge.Code.Name() != "not_null_violation" { - t.Fatalf("expected not_null_violation; got: %s (%+v)", pge.Code.Name(), err) - } - - // Test workaround in simpleQuery() - tx, err := db.Begin() - if err != nil { - t.Fatalf("unexpected error %s in Begin", err) - } - defer tx.Rollback() - - _, err = tx.Exec("SET LOCAL check_function_bodies TO FALSE") - if err != nil { - t.Fatalf("could not disable check_function_bodies: %s", err) - } - _, err = tx.Exec(` -CREATE OR REPLACE FUNCTION bad_function() -RETURNS integer --- hack to prevent the function from being inlined -SET check_function_bodies TO TRUE -AS $$ - SELECT text 'bad' -$$ LANGUAGE sql`) - if err != nil { - t.Fatalf("could not create function: %s", err) - } - - err = tx.QueryRow("SELECT * FROM bad_function()").Scan(&a) - if err == nil { - t.Fatalf("expected error") - } - pge, ok = err.(*Error) - if !ok { - t.Fatalf("expected *Error; got: %#v", err) - } - if pge.Code.Name() != "invalid_function_definition" { - t.Fatalf("expected invalid_function_definition; got: %s (%+v)", pge.Code.Name(), err) - } - - err = tx.Rollback() - if err != nil { - t.Fatalf("unexpected error %s in Rollback", err) - } - - // Also test that simpleQuery()'s workaround works when the query fails - // after a row has been received. - rows, err := db.Query(` -select - (select generate_series(1, ss.i)) -from (select gs.i - from generate_series(1, 2) gs(i) - order by gs.i limit 2) ss`) - if err != nil { - t.Fatalf("query failed: %s", err) - } - if !rows.Next() { - t.Fatalf("expected at least one result row; got %s", rows.Err()) - } - var i int - err = rows.Scan(&i) - if err != nil { - t.Fatalf("rows.Scan() failed: %s", err) - } - if i != 1 { - t.Fatalf("unexpected value for i: %d", i) - } - if rows.Next() { - t.Fatalf("unexpected row") - } - pge, ok = rows.Err().(*Error) - if !ok { - t.Fatalf("expected *Error; got: %#v", err) - } - if pge.Code.Name() != "cardinality_violation" { - t.Fatalf("expected cardinality_violation; got: %s (%+v)", pge.Code.Name(), rows.Err()) - } -} - -func TestSimpleQuery(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - r, err := db.Query("select 1") - if err != nil { - t.Fatal(err) - } - defer r.Close() - - if !r.Next() { - t.Fatal("expected row") - } -} - -func TestBindError(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - _, err := db.Exec("create temp table test (i integer)") - if err != nil { - t.Fatal(err) - } - - _, err = db.Query("select * from test where i=$1", "hhh") - if err == nil { - t.Fatal("expected an error") - } - - // Should not get error here - r, err := db.Query("select * from test where i=$1", 1) - if err != nil { - t.Fatal(err) - } - defer r.Close() -} - -func TestParseErrorInExtendedQuery(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - rows, err := db.Query("PARSE_ERROR $1", 1) - if err == nil { - t.Fatal("expected error") - } - - rows, err = db.Query("SELECT 1") - if err != nil { - t.Fatal(err) - } - rows.Close() -} - -// TestReturning tests that an INSERT query using the RETURNING clause returns a row. -func TestReturning(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - _, err := db.Exec("CREATE TEMP TABLE distributors (did integer default 0, dname text)") - if err != nil { - t.Fatal(err) - } - - rows, err := db.Query("INSERT INTO distributors (did, dname) VALUES (DEFAULT, 'XYZ Widgets') " + - "RETURNING did;") - if err != nil { - t.Fatal(err) - } - if !rows.Next() { - t.Fatal("no rows") - } - var did int - err = rows.Scan(&did) - if err != nil { - t.Fatal(err) - } - if did != 0 { - t.Fatalf("bad value for did: got %d, want %d", did, 0) - } - - if rows.Next() { - t.Fatal("unexpected next row") - } - err = rows.Err() - if err != nil { - t.Fatal(err) - } -} - -func TestIssue186(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - // Exec() a query which returns results - _, err := db.Exec("VALUES (1), (2), (3)") - if err != nil { - t.Fatal(err) - } - - _, err = db.Exec("VALUES ($1), ($2), ($3)", 1, 2, 3) - if err != nil { - t.Fatal(err) - } - - // Query() a query which doesn't return any results - txn, err := db.Begin() - if err != nil { - t.Fatal(err) - } - defer txn.Rollback() - - rows, err := txn.Query("CREATE TEMP TABLE foo(f1 int)") - if err != nil { - t.Fatal(err) - } - if err = rows.Close(); err != nil { - t.Fatal(err) - } - - // small trick to get NoData from a parameterized query - _, err = txn.Exec("CREATE RULE nodata AS ON INSERT TO foo DO INSTEAD NOTHING") - if err != nil { - t.Fatal(err) - } - rows, err = txn.Query("INSERT INTO foo VALUES ($1)", 1) - if err != nil { - t.Fatal(err) - } - if err = rows.Close(); err != nil { - t.Fatal(err) - } -} - -func TestIssue196(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - row := db.QueryRow("SELECT float4 '0.10000122' = $1, float8 '35.03554004971999' = $2", - float32(0.10000122), float64(35.03554004971999)) - - var float4match, float8match bool - err := row.Scan(&float4match, &float8match) - if err != nil { - t.Fatal(err) - } - if !float4match { - t.Errorf("Expected float4 fidelity to be maintained; got no match") - } - if !float8match { - t.Errorf("Expected float8 fidelity to be maintained; got no match") - } -} - -// Test that any CommandComplete messages sent before the query results are -// ignored. -func TestIssue282(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - var search_path string - err := db.QueryRow(` - SET LOCAL search_path TO pg_catalog; - SET LOCAL search_path TO pg_catalog; - SHOW search_path`).Scan(&search_path) - if err != nil { - t.Fatal(err) - } - if search_path != "pg_catalog" { - t.Fatalf("unexpected search_path %s", search_path) - } -} - -func TestReadFloatPrecision(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - row := db.QueryRow("SELECT float4 '0.10000122', float8 '35.03554004971999'") - var float4val float32 - var float8val float64 - err := row.Scan(&float4val, &float8val) - if err != nil { - t.Fatal(err) - } - if float4val != float32(0.10000122) { - t.Errorf("Expected float4 fidelity to be maintained; got no match") - } - if float8val != float64(35.03554004971999) { - t.Errorf("Expected float8 fidelity to be maintained; got no match") - } -} - -func TestXactMultiStmt(t *testing.T) { - // minified test case based on bug reports from - // pico303@gmail.com and rangelspam@gmail.com - t.Skip("Skipping failing test") - db := openTestConn(t) - defer db.Close() - - tx, err := db.Begin() - if err != nil { - t.Fatal(err) - } - defer tx.Commit() - - rows, err := tx.Query("select 1") - if err != nil { - t.Fatal(err) - } - - if rows.Next() { - var val int32 - if err = rows.Scan(&val); err != nil { - t.Fatal(err) - } - } else { - t.Fatal("Expected at least one row in first query in xact") - } - - rows2, err := tx.Query("select 2") - if err != nil { - t.Fatal(err) - } - - if rows2.Next() { - var val2 int32 - if err := rows2.Scan(&val2); err != nil { - t.Fatal(err) - } - } else { - t.Fatal("Expected at least one row in second query in xact") - } - - if err = rows.Err(); err != nil { - t.Fatal(err) - } - - if err = rows2.Err(); err != nil { - t.Fatal(err) - } - - if err = tx.Commit(); err != nil { - t.Fatal(err) - } -} - -var envParseTests = []struct { - Expected map[string]string - Env []string -}{ - { - Env: []string{"PGDATABASE=hello", "PGUSER=goodbye"}, - Expected: map[string]string{"dbname": "hello", "user": "goodbye"}, - }, - { - Env: []string{"PGDATESTYLE=ISO, MDY"}, - Expected: map[string]string{"datestyle": "ISO, MDY"}, - }, - { - Env: []string{"PGCONNECT_TIMEOUT=30"}, - Expected: map[string]string{"connect_timeout": "30"}, - }, -} - -func TestParseEnviron(t *testing.T) { - for i, tt := range envParseTests { - results := parseEnviron(tt.Env) - if !reflect.DeepEqual(tt.Expected, results) { - t.Errorf("%d: Expected: %#v Got: %#v", i, tt.Expected, results) - } - } -} - -func TestParseComplete(t *testing.T) { - tpc := func(commandTag string, command string, affectedRows int64, shouldFail bool) { - defer func() { - if p := recover(); p != nil { - if !shouldFail { - t.Error(p) - } - } - }() - cn := &conn{} - res, c := cn.parseComplete(commandTag) - if c != command { - t.Errorf("Expected %v, got %v", command, c) - } - n, err := res.RowsAffected() - if err != nil { - t.Fatal(err) - } - if n != affectedRows { - t.Errorf("Expected %d, got %d", affectedRows, n) - } - } - - tpc("ALTER TABLE", "ALTER TABLE", 0, false) - tpc("INSERT 0 1", "INSERT", 1, false) - tpc("UPDATE 100", "UPDATE", 100, false) - tpc("SELECT 100", "SELECT", 100, false) - tpc("FETCH 100", "FETCH", 100, false) - // allow COPY (and others) without row count - tpc("COPY", "COPY", 0, false) - // don't fail on command tags we don't recognize - tpc("UNKNOWNCOMMANDTAG", "UNKNOWNCOMMANDTAG", 0, false) - - // failure cases - tpc("INSERT 1", "", 0, true) // missing oid - tpc("UPDATE 0 1", "", 0, true) // too many numbers - tpc("SELECT foo", "", 0, true) // invalid row count -} - -func TestExecerInterface(t *testing.T) { - // Gin up a straw man private struct just for the type check - cn := &conn{c: nil} - var cni interface{} = cn - - _, ok := cni.(driver.Execer) - if !ok { - t.Fatal("Driver doesn't implement Execer") - } -} - -func TestNullAfterNonNull(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - r, err := db.Query("SELECT 9::integer UNION SELECT NULL::integer") - if err != nil { - t.Fatal(err) - } - - var n sql.NullInt64 - - if !r.Next() { - if r.Err() != nil { - t.Fatal(err) - } - t.Fatal("expected row") - } - - if err := r.Scan(&n); err != nil { - t.Fatal(err) - } - - if n.Int64 != 9 { - t.Fatalf("expected 2, not %d", n.Int64) - } - - if !r.Next() { - if r.Err() != nil { - t.Fatal(err) - } - t.Fatal("expected row") - } - - if err := r.Scan(&n); err != nil { - t.Fatal(err) - } - - if n.Valid { - t.Fatal("expected n to be invalid") - } - - if n.Int64 != 0 { - t.Fatalf("expected n to 2, not %d", n.Int64) - } -} - -func Test64BitErrorChecking(t *testing.T) { - defer func() { - if err := recover(); err != nil { - t.Fatal("panic due to 0xFFFFFFFF != -1 " + - "when int is 64 bits") - } - }() - - db := openTestConn(t) - defer db.Close() - - r, err := db.Query(`SELECT * -FROM (VALUES (0::integer, NULL::text), (1, 'test string')) AS t;`) - - if err != nil { - t.Fatal(err) - } - - defer r.Close() - - for r.Next() { - } -} - -func TestCommit(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - _, err := db.Exec("CREATE TEMP TABLE temp (a int)") - if err != nil { - t.Fatal(err) - } - sqlInsert := "INSERT INTO temp VALUES (1)" - sqlSelect := "SELECT * FROM temp" - tx, err := db.Begin() - if err != nil { - t.Fatal(err) - } - _, err = tx.Exec(sqlInsert) - if err != nil { - t.Fatal(err) - } - err = tx.Commit() - if err != nil { - t.Fatal(err) - } - var i int - err = db.QueryRow(sqlSelect).Scan(&i) - if err != nil { - t.Fatal(err) - } - if i != 1 { - t.Fatalf("expected 1, got %d", i) - } -} - -func TestErrorClass(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - _, err := db.Query("SELECT int 'notint'") - if err == nil { - t.Fatal("expected error") - } - pge, ok := err.(*Error) - if !ok { - t.Fatalf("expected *pq.Error, got %#+v", err) - } - if pge.Code.Class() != "22" { - t.Fatalf("expected class 28, got %v", pge.Code.Class()) - } - if pge.Code.Class().Name() != "data_exception" { - t.Fatalf("expected data_exception, got %v", pge.Code.Class().Name()) - } -} - -func TestParseOpts(t *testing.T) { - tests := []struct { - in string - expected values - valid bool - }{ - {"dbname=hello user=goodbye", values{"dbname": "hello", "user": "goodbye"}, true}, - {"dbname=hello user=goodbye ", values{"dbname": "hello", "user": "goodbye"}, true}, - {"dbname = hello user=goodbye", values{"dbname": "hello", "user": "goodbye"}, true}, - {"dbname=hello user =goodbye", values{"dbname": "hello", "user": "goodbye"}, true}, - {"dbname=hello user= goodbye", values{"dbname": "hello", "user": "goodbye"}, true}, - {"host=localhost password='correct horse battery staple'", values{"host": "localhost", "password": "correct horse battery staple"}, true}, - {"dbname=データベース password=パスワード", values{"dbname": "データベース", "password": "パスワード"}, true}, - {"dbname=hello user=''", values{"dbname": "hello", "user": ""}, true}, - {"user='' dbname=hello", values{"dbname": "hello", "user": ""}, true}, - // The last option value is an empty string if there's no non-whitespace after its = - {"dbname=hello user= ", values{"dbname": "hello", "user": ""}, true}, - - // The parser ignores spaces after = and interprets the next set of non-whitespace characters as the value. - {"user= password=foo", values{"user": "password=foo"}, true}, - - // Backslash escapes next char - {`user=a\ \'\\b`, values{"user": `a '\b`}, true}, - {`user='a \'b'`, values{"user": `a 'b`}, true}, - - // Incomplete escape - {`user=x\`, values{}, false}, - - // No '=' after the key - {"postgre://marko@internet", values{}, false}, - {"dbname user=goodbye", values{}, false}, - {"user=foo blah", values{}, false}, - {"user=foo blah ", values{}, false}, - - // Unterminated quoted value - {"dbname=hello user='unterminated", values{}, false}, - } - - for _, test := range tests { - o := make(values) - err := parseOpts(test.in, o) - - switch { - case err != nil && test.valid: - t.Errorf("%q got unexpected error: %s", test.in, err) - case err == nil && test.valid && !reflect.DeepEqual(test.expected, o): - t.Errorf("%q got: %#v want: %#v", test.in, o, test.expected) - case err == nil && !test.valid: - t.Errorf("%q expected an error", test.in) - } - } -} - -func TestRuntimeParameters(t *testing.T) { - type RuntimeTestResult int - const ( - ResultUnknown RuntimeTestResult = iota - ResultSuccess - ResultError // other error - ) - - tests := []struct { - conninfo string - param string - expected string - expectedOutcome RuntimeTestResult - }{ - // invalid parameter - {"DOESNOTEXIST=foo", "", "", ResultError}, - // we can only work with a specific value for these two - {"client_encoding=SQL_ASCII", "", "", ResultError}, - {"datestyle='ISO, YDM'", "", "", ResultError}, - // "options" should work exactly as it does in libpq - {"options='-c search_path=pqgotest'", "search_path", "pqgotest", ResultSuccess}, - // pq should override client_encoding in this case - {"options='-c client_encoding=SQL_ASCII'", "client_encoding", "UTF8", ResultSuccess}, - // allow client_encoding to be set explicitly - {"client_encoding=UTF8", "client_encoding", "UTF8", ResultSuccess}, - // test a runtime parameter not supported by libpq - {"work_mem='139kB'", "work_mem", "139kB", ResultSuccess}, - // test fallback_application_name - {"application_name=foo fallback_application_name=bar", "application_name", "foo", ResultSuccess}, - {"application_name='' fallback_application_name=bar", "application_name", "", ResultSuccess}, - {"fallback_application_name=bar", "application_name", "bar", ResultSuccess}, - } - - for _, test := range tests { - db, err := openTestConnConninfo(test.conninfo) - if err != nil { - t.Fatal(err) - } - - // application_name didn't exist before 9.0 - if test.param == "application_name" && getServerVersion(t, db) < 90000 { - db.Close() - continue - } - - tryGetParameterValue := func() (value string, outcome RuntimeTestResult) { - defer db.Close() - row := db.QueryRow("SELECT current_setting($1)", test.param) - err = row.Scan(&value) - if err != nil { - return "", ResultError - } - return value, ResultSuccess - } - - value, outcome := tryGetParameterValue() - if outcome != test.expectedOutcome && outcome == ResultError { - t.Fatalf("%v: unexpected error: %v", test.conninfo, err) - } - if outcome != test.expectedOutcome { - t.Fatalf("unexpected outcome %v (was expecting %v) for conninfo \"%s\"", - outcome, test.expectedOutcome, test.conninfo) - } - if value != test.expected { - t.Fatalf("bad value for %s: got %s, want %s with conninfo \"%s\"", - test.param, value, test.expected, test.conninfo) - } - } -} - -func TestIsUTF8(t *testing.T) { - var cases = []struct { - name string - want bool - }{ - {"unicode", true}, - {"utf-8", true}, - {"utf_8", true}, - {"UTF-8", true}, - {"UTF8", true}, - {"utf8", true}, - {"u n ic_ode", true}, - {"ut_f%8", true}, - {"ubf8", false}, - {"punycode", false}, - } - - for _, test := range cases { - if g := isUTF8(test.name); g != test.want { - t.Errorf("isUTF8(%q) = %v want %v", test.name, g, test.want) - } - } -} - -func TestQuoteIdentifier(t *testing.T) { - var cases = []struct { - input string - want string - }{ - {`foo`, `"foo"`}, - {`foo bar baz`, `"foo bar baz"`}, - {`foo"bar`, `"foo""bar"`}, - {"foo\x00bar", `"foo"`}, - {"\x00foo", `""`}, - } - - for _, test := range cases { - got := QuoteIdentifier(test.input) - if got != test.want { - t.Errorf("QuoteIdentifier(%q) = %v want %v", test.input, got, test.want) - } - } -} diff --git a/vendor/github.com/lib/pq/copy_test.go b/vendor/github.com/lib/pq/copy_test.go deleted file mode 100644 index 6af4c9c76..000000000 --- a/vendor/github.com/lib/pq/copy_test.go +++ /dev/null @@ -1,462 +0,0 @@ -package pq - -import ( - "bytes" - "database/sql" - "strings" - "testing" -) - -func TestCopyInStmt(t *testing.T) { - var stmt string - stmt = CopyIn("table name") - if stmt != `COPY "table name" () FROM STDIN` { - t.Fatal(stmt) - } - - stmt = CopyIn("table name", "column 1", "column 2") - if stmt != `COPY "table name" ("column 1", "column 2") FROM STDIN` { - t.Fatal(stmt) - } - - stmt = CopyIn(`table " name """`, `co"lumn""`) - if stmt != `COPY "table "" name """"""" ("co""lumn""""") FROM STDIN` { - t.Fatal(stmt) - } -} - -func TestCopyInSchemaStmt(t *testing.T) { - var stmt string - stmt = CopyInSchema("schema name", "table name") - if stmt != `COPY "schema name"."table name" () FROM STDIN` { - t.Fatal(stmt) - } - - stmt = CopyInSchema("schema name", "table name", "column 1", "column 2") - if stmt != `COPY "schema name"."table name" ("column 1", "column 2") FROM STDIN` { - t.Fatal(stmt) - } - - stmt = CopyInSchema(`schema " name """`, `table " name """`, `co"lumn""`) - if stmt != `COPY "schema "" name """"""".`+ - `"table "" name """"""" ("co""lumn""""") FROM STDIN` { - t.Fatal(stmt) - } -} - -func TestCopyInMultipleValues(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - txn, err := db.Begin() - if err != nil { - t.Fatal(err) - } - defer txn.Rollback() - - _, err = txn.Exec("CREATE TEMP TABLE temp (a int, b varchar)") - if err != nil { - t.Fatal(err) - } - - stmt, err := txn.Prepare(CopyIn("temp", "a", "b")) - if err != nil { - t.Fatal(err) - } - - longString := strings.Repeat("#", 500) - - for i := 0; i < 500; i++ { - _, err = stmt.Exec(int64(i), longString) - if err != nil { - t.Fatal(err) - } - } - - _, err = stmt.Exec() - if err != nil { - t.Fatal(err) - } - - err = stmt.Close() - if err != nil { - t.Fatal(err) - } - - var num int - err = txn.QueryRow("SELECT COUNT(*) FROM temp").Scan(&num) - if err != nil { - t.Fatal(err) - } - - if num != 500 { - t.Fatalf("expected 500 items, not %d", num) - } -} - -func TestCopyInRaiseStmtTrigger(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - if getServerVersion(t, db) < 90000 { - var exists int - err := db.QueryRow("SELECT 1 FROM pg_language WHERE lanname = 'plpgsql'").Scan(&exists) - if err == sql.ErrNoRows { - t.Skip("language PL/PgSQL does not exist; skipping TestCopyInRaiseStmtTrigger") - } else if err != nil { - t.Fatal(err) - } - } - - txn, err := db.Begin() - if err != nil { - t.Fatal(err) - } - defer txn.Rollback() - - _, err = txn.Exec("CREATE TEMP TABLE temp (a int, b varchar)") - if err != nil { - t.Fatal(err) - } - - _, err = txn.Exec(` - CREATE OR REPLACE FUNCTION pg_temp.temptest() - RETURNS trigger AS - $BODY$ begin - raise notice 'Hello world'; - return new; - end $BODY$ - LANGUAGE plpgsql`) - if err != nil { - t.Fatal(err) - } - - _, err = txn.Exec(` - CREATE TRIGGER temptest_trigger - BEFORE INSERT - ON temp - FOR EACH ROW - EXECUTE PROCEDURE pg_temp.temptest()`) - if err != nil { - t.Fatal(err) - } - - stmt, err := txn.Prepare(CopyIn("temp", "a", "b")) - if err != nil { - t.Fatal(err) - } - - longString := strings.Repeat("#", 500) - - _, err = stmt.Exec(int64(1), longString) - if err != nil { - t.Fatal(err) - } - - _, err = stmt.Exec() - if err != nil { - t.Fatal(err) - } - - err = stmt.Close() - if err != nil { - t.Fatal(err) - } - - var num int - err = txn.QueryRow("SELECT COUNT(*) FROM temp").Scan(&num) - if err != nil { - t.Fatal(err) - } - - if num != 1 { - t.Fatalf("expected 1 items, not %d", num) - } -} - -func TestCopyInTypes(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - txn, err := db.Begin() - if err != nil { - t.Fatal(err) - } - defer txn.Rollback() - - _, err = txn.Exec("CREATE TEMP TABLE temp (num INTEGER, text VARCHAR, blob BYTEA, nothing VARCHAR)") - if err != nil { - t.Fatal(err) - } - - stmt, err := txn.Prepare(CopyIn("temp", "num", "text", "blob", "nothing")) - if err != nil { - t.Fatal(err) - } - - _, err = stmt.Exec(int64(1234567890), "Héllö\n ☃!\r\t\\", []byte{0, 255, 9, 10, 13}, nil) - if err != nil { - t.Fatal(err) - } - - _, err = stmt.Exec() - if err != nil { - t.Fatal(err) - } - - err = stmt.Close() - if err != nil { - t.Fatal(err) - } - - var num int - var text string - var blob []byte - var nothing sql.NullString - - err = txn.QueryRow("SELECT * FROM temp").Scan(&num, &text, &blob, ¬hing) - if err != nil { - t.Fatal(err) - } - - if num != 1234567890 { - t.Fatal("unexpected result", num) - } - if text != "Héllö\n ☃!\r\t\\" { - t.Fatal("unexpected result", text) - } - if bytes.Compare(blob, []byte{0, 255, 9, 10, 13}) != 0 { - t.Fatal("unexpected result", blob) - } - if nothing.Valid { - t.Fatal("unexpected result", nothing.String) - } -} - -func TestCopyInWrongType(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - txn, err := db.Begin() - if err != nil { - t.Fatal(err) - } - defer txn.Rollback() - - _, err = txn.Exec("CREATE TEMP TABLE temp (num INTEGER)") - if err != nil { - t.Fatal(err) - } - - stmt, err := txn.Prepare(CopyIn("temp", "num")) - if err != nil { - t.Fatal(err) - } - defer stmt.Close() - - _, err = stmt.Exec("Héllö\n ☃!\r\t\\") - if err != nil { - t.Fatal(err) - } - - _, err = stmt.Exec() - if err == nil { - t.Fatal("expected error") - } - if pge := err.(*Error); pge.Code.Name() != "invalid_text_representation" { - t.Fatalf("expected 'invalid input syntax for integer' error, got %s (%+v)", pge.Code.Name(), pge) - } -} - -func TestCopyOutsideOfTxnError(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - _, err := db.Prepare(CopyIn("temp", "num")) - if err == nil { - t.Fatal("COPY outside of transaction did not return an error") - } - if err != errCopyNotSupportedOutsideTxn { - t.Fatalf("expected %s, got %s", err, err.Error()) - } -} - -func TestCopyInBinaryError(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - txn, err := db.Begin() - if err != nil { - t.Fatal(err) - } - defer txn.Rollback() - - _, err = txn.Exec("CREATE TEMP TABLE temp (num INTEGER)") - if err != nil { - t.Fatal(err) - } - _, err = txn.Prepare("COPY temp (num) FROM STDIN WITH binary") - if err != errBinaryCopyNotSupported { - t.Fatalf("expected %s, got %+v", errBinaryCopyNotSupported, err) - } - // check that the protocol is in a valid state - err = txn.Rollback() - if err != nil { - t.Fatal(err) - } -} - -func TestCopyFromError(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - txn, err := db.Begin() - if err != nil { - t.Fatal(err) - } - defer txn.Rollback() - - _, err = txn.Exec("CREATE TEMP TABLE temp (num INTEGER)") - if err != nil { - t.Fatal(err) - } - _, err = txn.Prepare("COPY temp (num) TO STDOUT") - if err != errCopyToNotSupported { - t.Fatalf("expected %s, got %+v", errCopyToNotSupported, err) - } - // check that the protocol is in a valid state - err = txn.Rollback() - if err != nil { - t.Fatal(err) - } -} - -func TestCopySyntaxError(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - txn, err := db.Begin() - if err != nil { - t.Fatal(err) - } - defer txn.Rollback() - - _, err = txn.Prepare("COPY ") - if err == nil { - t.Fatal("expected error") - } - if pge := err.(*Error); pge.Code.Name() != "syntax_error" { - t.Fatalf("expected syntax error, got %s (%+v)", pge.Code.Name(), pge) - } - // check that the protocol is in a valid state - err = txn.Rollback() - if err != nil { - t.Fatal(err) - } -} - -// Tests for connection errors in copyin.resploop() -func TestCopyRespLoopConnectionError(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - txn, err := db.Begin() - if err != nil { - t.Fatal(err) - } - defer txn.Rollback() - - var pid int - err = txn.QueryRow("SELECT pg_backend_pid()").Scan(&pid) - if err != nil { - t.Fatal(err) - } - - _, err = txn.Exec("CREATE TEMP TABLE temp (a int)") - if err != nil { - t.Fatal(err) - } - - stmt, err := txn.Prepare(CopyIn("temp", "a")) - if err != nil { - t.Fatal(err) - } - - _, err = db.Exec("SELECT pg_terminate_backend($1)", pid) - if err != nil { - t.Fatal(err) - } - - if getServerVersion(t, db) < 90500 { - // We have to try and send something over, since postgres before - // version 9.5 won't process SIGTERMs while it's waiting for - // CopyData/CopyEnd messages; see tcop/postgres.c. - _, err = stmt.Exec(1) - if err != nil { - t.Fatal(err) - } - } - _, err = stmt.Exec() - if err == nil { - t.Fatalf("expected error") - } - pge, ok := err.(*Error) - if !ok { - t.Fatalf("expected *pq.Error, got %+#v", err) - } else if pge.Code.Name() != "admin_shutdown" { - t.Fatalf("expected admin_shutdown, got %s", pge.Code.Name()) - } - - err = stmt.Close() - if err != nil { - t.Fatal(err) - } -} - -func BenchmarkCopyIn(b *testing.B) { - db := openTestConn(b) - defer db.Close() - - txn, err := db.Begin() - if err != nil { - b.Fatal(err) - } - defer txn.Rollback() - - _, err = txn.Exec("CREATE TEMP TABLE temp (a int, b varchar)") - if err != nil { - b.Fatal(err) - } - - stmt, err := txn.Prepare(CopyIn("temp", "a", "b")) - if err != nil { - b.Fatal(err) - } - - for i := 0; i < b.N; i++ { - _, err = stmt.Exec(int64(i), "hello world!") - if err != nil { - b.Fatal(err) - } - } - - _, err = stmt.Exec() - if err != nil { - b.Fatal(err) - } - - err = stmt.Close() - if err != nil { - b.Fatal(err) - } - - var num int - err = txn.QueryRow("SELECT COUNT(*) FROM temp").Scan(&num) - if err != nil { - b.Fatal(err) - } - - if num != b.N { - b.Fatalf("expected %d items, not %d", b.N, num) - } -} diff --git a/vendor/github.com/lib/pq/encode_test.go b/vendor/github.com/lib/pq/encode_test.go deleted file mode 100644 index 97b663886..000000000 --- a/vendor/github.com/lib/pq/encode_test.go +++ /dev/null @@ -1,719 +0,0 @@ -package pq - -import ( - "bytes" - "database/sql" - "fmt" - "testing" - "time" - - "github.com/lib/pq/oid" -) - -func TestScanTimestamp(t *testing.T) { - var nt NullTime - tn := time.Now() - nt.Scan(tn) - if !nt.Valid { - t.Errorf("Expected Valid=false") - } - if nt.Time != tn { - t.Errorf("Time value mismatch") - } -} - -func TestScanNilTimestamp(t *testing.T) { - var nt NullTime - nt.Scan(nil) - if nt.Valid { - t.Errorf("Expected Valid=false") - } -} - -var timeTests = []struct { - str string - timeval time.Time -}{ - {"22001-02-03", time.Date(22001, time.February, 3, 0, 0, 0, 0, time.FixedZone("", 0))}, - {"2001-02-03", time.Date(2001, time.February, 3, 0, 0, 0, 0, time.FixedZone("", 0))}, - {"2001-02-03 04:05:06", time.Date(2001, time.February, 3, 4, 5, 6, 0, time.FixedZone("", 0))}, - {"2001-02-03 04:05:06.000001", time.Date(2001, time.February, 3, 4, 5, 6, 1000, time.FixedZone("", 0))}, - {"2001-02-03 04:05:06.00001", time.Date(2001, time.February, 3, 4, 5, 6, 10000, time.FixedZone("", 0))}, - {"2001-02-03 04:05:06.0001", time.Date(2001, time.February, 3, 4, 5, 6, 100000, time.FixedZone("", 0))}, - {"2001-02-03 04:05:06.001", time.Date(2001, time.February, 3, 4, 5, 6, 1000000, time.FixedZone("", 0))}, - {"2001-02-03 04:05:06.01", time.Date(2001, time.February, 3, 4, 5, 6, 10000000, time.FixedZone("", 0))}, - {"2001-02-03 04:05:06.1", time.Date(2001, time.February, 3, 4, 5, 6, 100000000, time.FixedZone("", 0))}, - {"2001-02-03 04:05:06.12", time.Date(2001, time.February, 3, 4, 5, 6, 120000000, time.FixedZone("", 0))}, - {"2001-02-03 04:05:06.123", time.Date(2001, time.February, 3, 4, 5, 6, 123000000, time.FixedZone("", 0))}, - {"2001-02-03 04:05:06.1234", time.Date(2001, time.February, 3, 4, 5, 6, 123400000, time.FixedZone("", 0))}, - {"2001-02-03 04:05:06.12345", time.Date(2001, time.February, 3, 4, 5, 6, 123450000, time.FixedZone("", 0))}, - {"2001-02-03 04:05:06.123456", time.Date(2001, time.February, 3, 4, 5, 6, 123456000, time.FixedZone("", 0))}, - {"2001-02-03 04:05:06.123-07", time.Date(2001, time.February, 3, 4, 5, 6, 123000000, - time.FixedZone("", -7*60*60))}, - {"2001-02-03 04:05:06-07", time.Date(2001, time.February, 3, 4, 5, 6, 0, - time.FixedZone("", -7*60*60))}, - {"2001-02-03 04:05:06-07:42", time.Date(2001, time.February, 3, 4, 5, 6, 0, - time.FixedZone("", -(7*60*60+42*60)))}, - {"2001-02-03 04:05:06-07:30:09", time.Date(2001, time.February, 3, 4, 5, 6, 0, - time.FixedZone("", -(7*60*60+30*60+9)))}, - {"2001-02-03 04:05:06+07", time.Date(2001, time.February, 3, 4, 5, 6, 0, - time.FixedZone("", 7*60*60))}, - {"0011-02-03 04:05:06 BC", time.Date(-10, time.February, 3, 4, 5, 6, 0, time.FixedZone("", 0))}, - {"0011-02-03 04:05:06.123 BC", time.Date(-10, time.February, 3, 4, 5, 6, 123000000, time.FixedZone("", 0))}, - {"0011-02-03 04:05:06.123-07 BC", time.Date(-10, time.February, 3, 4, 5, 6, 123000000, - time.FixedZone("", -7*60*60))}, - {"0001-02-03 04:05:06.123", time.Date(1, time.February, 3, 4, 5, 6, 123000000, time.FixedZone("", 0))}, - {"0001-02-03 04:05:06.123 BC", time.Date(1, time.February, 3, 4, 5, 6, 123000000, time.FixedZone("", 0)).AddDate(-1, 0, 0)}, - {"0001-02-03 04:05:06.123 BC", time.Date(0, time.February, 3, 4, 5, 6, 123000000, time.FixedZone("", 0))}, - {"0002-02-03 04:05:06.123 BC", time.Date(0, time.February, 3, 4, 5, 6, 123000000, time.FixedZone("", 0)).AddDate(-1, 0, 0)}, - {"0002-02-03 04:05:06.123 BC", time.Date(-1, time.February, 3, 4, 5, 6, 123000000, time.FixedZone("", 0))}, - {"12345-02-03 04:05:06.1", time.Date(12345, time.February, 3, 4, 5, 6, 100000000, time.FixedZone("", 0))}, - {"123456-02-03 04:05:06.1", time.Date(123456, time.February, 3, 4, 5, 6, 100000000, time.FixedZone("", 0))}, -} - -// Helper function for the two tests below -func tryParse(str string) (t time.Time, err error) { - defer func() { - if p := recover(); p != nil { - err = fmt.Errorf("%v", p) - return - } - }() - i := parseTs(nil, str) - t, ok := i.(time.Time) - if !ok { - err = fmt.Errorf("Not a time.Time type, got %#v", i) - } - return -} - -// Test that parsing the string results in the expected value. -func TestParseTs(t *testing.T) { - for i, tt := range timeTests { - val, err := tryParse(tt.str) - if err != nil { - t.Errorf("%d: got error: %v", i, err) - } else if val.String() != tt.timeval.String() { - t.Errorf("%d: expected to parse %q into %q; got %q", - i, tt.str, tt.timeval, val) - } - } -} - -// Now test that sending the value into the database and parsing it back -// returns the same time.Time value. -func TestEncodeAndParseTs(t *testing.T) { - db, err := openTestConnConninfo("timezone='Etc/UTC'") - if err != nil { - t.Fatal(err) - } - defer db.Close() - - for i, tt := range timeTests { - var dbstr string - err = db.QueryRow("SELECT ($1::timestamptz)::text", tt.timeval).Scan(&dbstr) - if err != nil { - t.Errorf("%d: could not send value %q to the database: %s", i, tt.timeval, err) - continue - } - - val, err := tryParse(dbstr) - if err != nil { - t.Errorf("%d: could not parse value %q: %s", i, dbstr, err) - continue - } - val = val.In(tt.timeval.Location()) - if val.String() != tt.timeval.String() { - t.Errorf("%d: expected to parse %q into %q; got %q", i, dbstr, tt.timeval, val) - } - } -} - -var formatTimeTests = []struct { - time time.Time - expected string -}{ - {time.Time{}, "0001-01-01T00:00:00Z"}, - {time.Date(2001, time.February, 3, 4, 5, 6, 123456789, time.FixedZone("", 0)), "2001-02-03T04:05:06.123456789Z"}, - {time.Date(2001, time.February, 3, 4, 5, 6, 123456789, time.FixedZone("", 2*60*60)), "2001-02-03T04:05:06.123456789+02:00"}, - {time.Date(2001, time.February, 3, 4, 5, 6, 123456789, time.FixedZone("", -6*60*60)), "2001-02-03T04:05:06.123456789-06:00"}, - {time.Date(2001, time.February, 3, 4, 5, 6, 0, time.FixedZone("", -(7*60*60+30*60+9))), "2001-02-03T04:05:06-07:30:09"}, - - {time.Date(1, time.February, 3, 4, 5, 6, 123456789, time.FixedZone("", 0)), "0001-02-03T04:05:06.123456789Z"}, - {time.Date(1, time.February, 3, 4, 5, 6, 123456789, time.FixedZone("", 2*60*60)), "0001-02-03T04:05:06.123456789+02:00"}, - {time.Date(1, time.February, 3, 4, 5, 6, 123456789, time.FixedZone("", -6*60*60)), "0001-02-03T04:05:06.123456789-06:00"}, - - {time.Date(0, time.February, 3, 4, 5, 6, 123456789, time.FixedZone("", 0)), "0001-02-03T04:05:06.123456789Z BC"}, - {time.Date(0, time.February, 3, 4, 5, 6, 123456789, time.FixedZone("", 2*60*60)), "0001-02-03T04:05:06.123456789+02:00 BC"}, - {time.Date(0, time.February, 3, 4, 5, 6, 123456789, time.FixedZone("", -6*60*60)), "0001-02-03T04:05:06.123456789-06:00 BC"}, - - {time.Date(1, time.February, 3, 4, 5, 6, 0, time.FixedZone("", -(7*60*60+30*60+9))), "0001-02-03T04:05:06-07:30:09"}, - {time.Date(0, time.February, 3, 4, 5, 6, 0, time.FixedZone("", -(7*60*60+30*60+9))), "0001-02-03T04:05:06-07:30:09 BC"}, -} - -func TestFormatTs(t *testing.T) { - for i, tt := range formatTimeTests { - val := string(formatTs(tt.time)) - if val != tt.expected { - t.Errorf("%d: incorrect time format %q, want %q", i, val, tt.expected) - } - } -} - -func TestTimestampWithTimeZone(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - tx, err := db.Begin() - if err != nil { - t.Fatal(err) - } - defer tx.Rollback() - - // try several different locations, all included in Go's zoneinfo.zip - for _, locName := range []string{ - "UTC", - "America/Chicago", - "America/New_York", - "Australia/Darwin", - "Australia/Perth", - } { - loc, err := time.LoadLocation(locName) - if err != nil { - t.Logf("Could not load time zone %s - skipping", locName) - continue - } - - // Postgres timestamps have a resolution of 1 microsecond, so don't - // use the full range of the Nanosecond argument - refTime := time.Date(2012, 11, 6, 10, 23, 42, 123456000, loc) - - for _, pgTimeZone := range []string{"US/Eastern", "Australia/Darwin"} { - // Switch Postgres's timezone to test different output timestamp formats - _, err = tx.Exec(fmt.Sprintf("set time zone '%s'", pgTimeZone)) - if err != nil { - t.Fatal(err) - } - - var gotTime time.Time - row := tx.QueryRow("select $1::timestamp with time zone", refTime) - err = row.Scan(&gotTime) - if err != nil { - t.Fatal(err) - } - - if !refTime.Equal(gotTime) { - t.Errorf("timestamps not equal: %s != %s", refTime, gotTime) - } - - // check that the time zone is set correctly based on TimeZone - pgLoc, err := time.LoadLocation(pgTimeZone) - if err != nil { - t.Logf("Could not load time zone %s - skipping", pgLoc) - continue - } - translated := refTime.In(pgLoc) - if translated.String() != gotTime.String() { - t.Errorf("timestamps not equal: %s != %s", translated, gotTime) - } - } - } -} - -func TestTimestampWithOutTimezone(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - test := func(ts, pgts string) { - r, err := db.Query("SELECT $1::timestamp", pgts) - if err != nil { - t.Fatalf("Could not run query: %v", err) - } - - n := r.Next() - - if n != true { - t.Fatal("Expected at least one row") - } - - var result time.Time - err = r.Scan(&result) - if err != nil { - t.Fatalf("Did not expect error scanning row: %v", err) - } - - expected, err := time.Parse(time.RFC3339, ts) - if err != nil { - t.Fatalf("Could not parse test time literal: %v", err) - } - - if !result.Equal(expected) { - t.Fatalf("Expected time to match %v: got mismatch %v", - expected, result) - } - - n = r.Next() - if n != false { - t.Fatal("Expected only one row") - } - } - - test("2000-01-01T00:00:00Z", "2000-01-01T00:00:00") - - // Test higher precision time - test("2013-01-04T20:14:58.80033Z", "2013-01-04 20:14:58.80033") -} - -func TestInfinityTimestamp(t *testing.T) { - db := openTestConn(t) - defer db.Close() - var err error - var resultT time.Time - - expectedError := fmt.Errorf(`sql: Scan error on column index 0: unsupported driver -> Scan pair: []uint8 -> *time.Time`) - type testCases []struct { - Query string - Param string - ExpectedErr error - ExpectedVal interface{} - } - tc := testCases{ - {"SELECT $1::timestamp", "-infinity", expectedError, "-infinity"}, - {"SELECT $1::timestamptz", "-infinity", expectedError, "-infinity"}, - {"SELECT $1::timestamp", "infinity", expectedError, "infinity"}, - {"SELECT $1::timestamptz", "infinity", expectedError, "infinity"}, - } - // try to assert []byte to time.Time - for _, q := range tc { - err = db.QueryRow(q.Query, q.Param).Scan(&resultT) - if err.Error() != q.ExpectedErr.Error() { - t.Errorf("Scanning -/+infinity, expected error, %q, got %q", q.ExpectedErr, err) - } - } - // yield []byte - for _, q := range tc { - var resultI interface{} - err = db.QueryRow(q.Query, q.Param).Scan(&resultI) - if err != nil { - t.Errorf("Scanning -/+infinity, expected no error, got %q", err) - } - result, ok := resultI.([]byte) - if !ok { - t.Errorf("Scanning -/+infinity, expected []byte, got %#v", resultI) - } - if string(result) != q.ExpectedVal { - t.Errorf("Scanning -/+infinity, expected %q, got %q", q.ExpectedVal, result) - } - } - - y1500 := time.Date(1500, time.January, 1, 0, 0, 0, 0, time.UTC) - y2500 := time.Date(2500, time.January, 1, 0, 0, 0, 0, time.UTC) - EnableInfinityTs(y1500, y2500) - - err = db.QueryRow("SELECT $1::timestamp", "infinity").Scan(&resultT) - if err != nil { - t.Errorf("Scanning infinity, expected no error, got %q", err) - } - if !resultT.Equal(y2500) { - t.Errorf("Scanning infinity, expected %q, got %q", y2500, resultT) - } - - err = db.QueryRow("SELECT $1::timestamptz", "infinity").Scan(&resultT) - if err != nil { - t.Errorf("Scanning infinity, expected no error, got %q", err) - } - if !resultT.Equal(y2500) { - t.Errorf("Scanning Infinity, expected time %q, got %q", y2500, resultT.String()) - } - - err = db.QueryRow("SELECT $1::timestamp", "-infinity").Scan(&resultT) - if err != nil { - t.Errorf("Scanning -infinity, expected no error, got %q", err) - } - if !resultT.Equal(y1500) { - t.Errorf("Scanning -infinity, expected time %q, got %q", y1500, resultT.String()) - } - - err = db.QueryRow("SELECT $1::timestamptz", "-infinity").Scan(&resultT) - if err != nil { - t.Errorf("Scanning -infinity, expected no error, got %q", err) - } - if !resultT.Equal(y1500) { - t.Errorf("Scanning -infinity, expected time %q, got %q", y1500, resultT.String()) - } - - y_1500 := time.Date(-1500, time.January, 1, 0, 0, 0, 0, time.UTC) - y11500 := time.Date(11500, time.January, 1, 0, 0, 0, 0, time.UTC) - var s string - err = db.QueryRow("SELECT $1::timestamp::text", y_1500).Scan(&s) - if err != nil { - t.Errorf("Encoding -infinity, expected no error, got %q", err) - } - if s != "-infinity" { - t.Errorf("Encoding -infinity, expected %q, got %q", "-infinity", s) - } - err = db.QueryRow("SELECT $1::timestamptz::text", y_1500).Scan(&s) - if err != nil { - t.Errorf("Encoding -infinity, expected no error, got %q", err) - } - if s != "-infinity" { - t.Errorf("Encoding -infinity, expected %q, got %q", "-infinity", s) - } - - err = db.QueryRow("SELECT $1::timestamp::text", y11500).Scan(&s) - if err != nil { - t.Errorf("Encoding infinity, expected no error, got %q", err) - } - if s != "infinity" { - t.Errorf("Encoding infinity, expected %q, got %q", "infinity", s) - } - err = db.QueryRow("SELECT $1::timestamptz::text", y11500).Scan(&s) - if err != nil { - t.Errorf("Encoding infinity, expected no error, got %q", err) - } - if s != "infinity" { - t.Errorf("Encoding infinity, expected %q, got %q", "infinity", s) - } - - disableInfinityTs() - - var panicErrorString string - func() { - defer func() { - panicErrorString, _ = recover().(string) - }() - EnableInfinityTs(y2500, y1500) - }() - if panicErrorString != infinityTsNegativeMustBeSmaller { - t.Errorf("Expected error, %q, got %q", infinityTsNegativeMustBeSmaller, panicErrorString) - } -} - -func TestStringWithNul(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - hello0world := string("hello\x00world") - _, err := db.Query("SELECT $1::text", &hello0world) - if err == nil { - t.Fatal("Postgres accepts a string with nul in it; " + - "injection attacks may be plausible") - } -} - -func TestByteSliceToText(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - b := []byte("hello world") - row := db.QueryRow("SELECT $1::text", b) - - var result []byte - err := row.Scan(&result) - if err != nil { - t.Fatal(err) - } - - if string(result) != string(b) { - t.Fatalf("expected %v but got %v", b, result) - } -} - -func TestStringToBytea(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - b := "hello world" - row := db.QueryRow("SELECT $1::bytea", b) - - var result []byte - err := row.Scan(&result) - if err != nil { - t.Fatal(err) - } - - if !bytes.Equal(result, []byte(b)) { - t.Fatalf("expected %v but got %v", b, result) - } -} - -func TestTextByteSliceToUUID(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - b := []byte("a0eebc99-9c0b-4ef8-bb6d-6bb9bd380a11") - row := db.QueryRow("SELECT $1::uuid", b) - - var result string - err := row.Scan(&result) - if forceBinaryParameters() { - pqErr := err.(*Error) - if pqErr == nil { - t.Errorf("Expected to get error") - } else if pqErr.Code != "22P03" { - t.Fatalf("Expected to get invalid binary encoding error (22P03), got %s", pqErr.Code) - } - } else { - if err != nil { - t.Fatal(err) - } - - if result != string(b) { - t.Fatalf("expected %v but got %v", b, result) - } - } -} - -func TestBinaryByteSlicetoUUID(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - b := []byte{'\xa0','\xee','\xbc','\x99', - '\x9c', '\x0b', - '\x4e', '\xf8', - '\xbb', '\x00', '\x6b', - '\xb9', '\xbd', '\x38', '\x0a', '\x11'} - row := db.QueryRow("SELECT $1::uuid", b) - - var result string - err := row.Scan(&result) - if forceBinaryParameters() { - if err != nil { - t.Fatal(err) - } - - if result != string("a0eebc99-9c0b-4ef8-bb00-6bb9bd380a11") { - t.Fatalf("expected %v but got %v", b, result) - } - } else { - pqErr := err.(*Error) - if pqErr == nil { - t.Errorf("Expected to get error") - } else if pqErr.Code != "22021" { - t.Fatalf("Expected to get invalid byte sequence for encoding error (22021), got %s", pqErr.Code) - } - } -} - -func TestStringToUUID(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - s := "a0eebc99-9c0b-4ef8-bb00-6bb9bd380a11" - row := db.QueryRow("SELECT $1::uuid", s) - - var result string - err := row.Scan(&result) - if err != nil { - t.Fatal(err) - } - - if result != s { - t.Fatalf("expected %v but got %v", s, result) - } -} - -func TestTextByteSliceToInt(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - expected := 12345678 - b := []byte(fmt.Sprintf("%d", expected)) - row := db.QueryRow("SELECT $1::int", b) - - var result int - err := row.Scan(&result) - if forceBinaryParameters() { - pqErr := err.(*Error) - if pqErr == nil { - t.Errorf("Expected to get error") - } else if pqErr.Code != "22P03" { - t.Fatalf("Expected to get invalid binary encoding error (22P03), got %s", pqErr.Code) - } - } else { - if err != nil { - t.Fatal(err) - } - if result != expected { - t.Fatalf("expected %v but got %v", expected, result) - } - } -} - -func TestBinaryByteSliceToInt(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - expected := 12345678 - b := []byte{'\x00', '\xbc', '\x61', '\x4e'} - row := db.QueryRow("SELECT $1::int", b) - - var result int - err := row.Scan(&result) - if forceBinaryParameters() { - if err != nil { - t.Fatal(err) - } - if result != expected { - t.Fatalf("expected %v but got %v", expected, result) - } - } else { - pqErr := err.(*Error) - if pqErr == nil { - t.Errorf("Expected to get error") - } else if pqErr.Code != "22021" { - t.Fatalf("Expected to get invalid byte sequence for encoding error (22021), got %s", pqErr.Code) - } - } -} - -func TestByteaOutputFormatEncoding(t *testing.T) { - input := []byte("\\x\x00\x01\x02\xFF\xFEabcdefg0123") - want := []byte("\\x5c78000102fffe6162636465666730313233") - got := encode(¶meterStatus{serverVersion: 90000}, input, oid.T_bytea) - if !bytes.Equal(want, got) { - t.Errorf("invalid hex bytea output, got %v but expected %v", got, want) - } - - want = []byte("\\\\x\\000\\001\\002\\377\\376abcdefg0123") - got = encode(¶meterStatus{serverVersion: 84000}, input, oid.T_bytea) - if !bytes.Equal(want, got) { - t.Errorf("invalid escape bytea output, got %v but expected %v", got, want) - } -} - -func TestByteaOutputFormats(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - if getServerVersion(t, db) < 90000 { - // skip - return - } - - testByteaOutputFormat := func(f string, usePrepared bool) { - expectedData := []byte("\x5c\x78\x00\xff\x61\x62\x63\x01\x08") - sqlQuery := "SELECT decode('5c7800ff6162630108', 'hex')" - - var data []byte - - // use a txn to avoid relying on getting the same connection - txn, err := db.Begin() - if err != nil { - t.Fatal(err) - } - defer txn.Rollback() - - _, err = txn.Exec("SET LOCAL bytea_output TO " + f) - if err != nil { - t.Fatal(err) - } - var rows *sql.Rows - var stmt *sql.Stmt - if usePrepared { - stmt, err = txn.Prepare(sqlQuery) - if err != nil { - t.Fatal(err) - } - rows, err = stmt.Query() - } else { - // use Query; QueryRow would hide the actual error - rows, err = txn.Query(sqlQuery) - } - if err != nil { - t.Fatal(err) - } - if !rows.Next() { - if rows.Err() != nil { - t.Fatal(rows.Err()) - } - t.Fatal("shouldn't happen") - } - err = rows.Scan(&data) - if err != nil { - t.Fatal(err) - } - err = rows.Close() - if err != nil { - t.Fatal(err) - } - if stmt != nil { - err = stmt.Close() - if err != nil { - t.Fatal(err) - } - } - if !bytes.Equal(data, expectedData) { - t.Errorf("unexpected bytea value %v for format %s; expected %v", data, f, expectedData) - } - } - - testByteaOutputFormat("hex", false) - testByteaOutputFormat("escape", false) - testByteaOutputFormat("hex", true) - testByteaOutputFormat("escape", true) -} - -func TestAppendEncodedText(t *testing.T) { - var buf []byte - - buf = appendEncodedText(¶meterStatus{serverVersion: 90000}, buf, int64(10)) - buf = append(buf, '\t') - buf = appendEncodedText(¶meterStatus{serverVersion: 90000}, buf, 42.0000000001) - buf = append(buf, '\t') - buf = appendEncodedText(¶meterStatus{serverVersion: 90000}, buf, "hello\tworld") - buf = append(buf, '\t') - buf = appendEncodedText(¶meterStatus{serverVersion: 90000}, buf, []byte{0, 128, 255}) - - if string(buf) != "10\t42.0000000001\thello\\tworld\t\\\\x0080ff" { - t.Fatal(string(buf)) - } -} - -func TestAppendEscapedText(t *testing.T) { - if esc := appendEscapedText(nil, "hallo\tescape"); string(esc) != "hallo\\tescape" { - t.Fatal(string(esc)) - } - if esc := appendEscapedText(nil, "hallo\\tescape\n"); string(esc) != "hallo\\\\tescape\\n" { - t.Fatal(string(esc)) - } - if esc := appendEscapedText(nil, "\n\r\t\f"); string(esc) != "\\n\\r\\t\f" { - t.Fatal(string(esc)) - } -} - -func TestAppendEscapedTextExistingBuffer(t *testing.T) { - var buf []byte - buf = []byte("123\t") - if esc := appendEscapedText(buf, "hallo\tescape"); string(esc) != "123\thallo\\tescape" { - t.Fatal(string(esc)) - } - buf = []byte("123\t") - if esc := appendEscapedText(buf, "hallo\\tescape\n"); string(esc) != "123\thallo\\\\tescape\\n" { - t.Fatal(string(esc)) - } - buf = []byte("123\t") - if esc := appendEscapedText(buf, "\n\r\t\f"); string(esc) != "123\t\\n\\r\\t\f" { - t.Fatal(string(esc)) - } -} - -func BenchmarkAppendEscapedText(b *testing.B) { - longString := "" - for i := 0; i < 100; i++ { - longString += "123456789\n" - } - for i := 0; i < b.N; i++ { - appendEscapedText(nil, longString) - } -} - -func BenchmarkAppendEscapedTextNoEscape(b *testing.B) { - longString := "" - for i := 0; i < 100; i++ { - longString += "1234567890" - } - for i := 0; i < b.N; i++ { - appendEscapedText(nil, longString) - } -} diff --git a/vendor/github.com/lib/pq/hstore/hstore.go b/vendor/github.com/lib/pq/hstore/hstore.go deleted file mode 100644 index 72d5abf51..000000000 --- a/vendor/github.com/lib/pq/hstore/hstore.go +++ /dev/null @@ -1,118 +0,0 @@ -package hstore - -import ( - "database/sql" - "database/sql/driver" - "strings" -) - -// A wrapper for transferring Hstore values back and forth easily. -type Hstore struct { - Map map[string]sql.NullString -} - -// escapes and quotes hstore keys/values -// s should be a sql.NullString or string -func hQuote(s interface{}) string { - var str string - switch v := s.(type) { - case sql.NullString: - if !v.Valid { - return "NULL" - } - str = v.String - case string: - str = v - default: - panic("not a string or sql.NullString") - } - - str = strings.Replace(str, "\\", "\\\\", -1) - return `"` + strings.Replace(str, "\"", "\\\"", -1) + `"` -} - -// Scan implements the Scanner interface. -// -// Note h.Map is reallocated before the scan to clear existing values. If the -// hstore column's database value is NULL, then h.Map is set to nil instead. -func (h *Hstore) Scan(value interface{}) error { - if value == nil { - h.Map = nil - return nil - } - h.Map = make(map[string]sql.NullString) - var b byte - pair := [][]byte{{}, {}} - pi := 0 - inQuote := false - didQuote := false - sawSlash := false - bindex := 0 - for bindex, b = range value.([]byte) { - if sawSlash { - pair[pi] = append(pair[pi], b) - sawSlash = false - continue - } - - switch b { - case '\\': - sawSlash = true - continue - case '"': - inQuote = !inQuote - if !didQuote { - didQuote = true - } - continue - default: - if !inQuote { - switch b { - case ' ', '\t', '\n', '\r': - continue - case '=': - continue - case '>': - pi = 1 - didQuote = false - continue - case ',': - s := string(pair[1]) - if !didQuote && len(s) == 4 && strings.ToLower(s) == "null" { - h.Map[string(pair[0])] = sql.NullString{String: "", Valid: false} - } else { - h.Map[string(pair[0])] = sql.NullString{String: string(pair[1]), Valid: true} - } - pair[0] = []byte{} - pair[1] = []byte{} - pi = 0 - continue - } - } - } - pair[pi] = append(pair[pi], b) - } - if bindex > 0 { - s := string(pair[1]) - if !didQuote && len(s) == 4 && strings.ToLower(s) == "null" { - h.Map[string(pair[0])] = sql.NullString{String: "", Valid: false} - } else { - h.Map[string(pair[0])] = sql.NullString{String: string(pair[1]), Valid: true} - } - } - return nil -} - -// Value implements the driver Valuer interface. Note if h.Map is nil, the -// database column value will be set to NULL. -func (h Hstore) Value() (driver.Value, error) { - if h.Map == nil { - return nil, nil - } - parts := []string{} - for key, val := range h.Map { - thispart := hQuote(key) + "=>" + hQuote(val) - parts = append(parts, thispart) - } - return []byte(strings.Join(parts, ",")), nil -} diff --git a/vendor/github.com/lib/pq/hstore/hstore_test.go b/vendor/github.com/lib/pq/hstore/hstore_test.go deleted file mode 100644 index c9c108fc3..000000000 --- a/vendor/github.com/lib/pq/hstore/hstore_test.go +++ /dev/null @@ -1,148 +0,0 @@ -package hstore - -import ( - "database/sql" - "os" - "testing" - - _ "github.com/lib/pq" -) - -type Fatalistic interface { - Fatal(args ...interface{}) -} - -func openTestConn(t Fatalistic) *sql.DB { - datname := os.Getenv("PGDATABASE") - sslmode := os.Getenv("PGSSLMODE") - - if datname == "" { - os.Setenv("PGDATABASE", "pqgotest") - } - - if sslmode == "" { - os.Setenv("PGSSLMODE", "disable") - } - - conn, err := sql.Open("postgres", "") - if err != nil { - t.Fatal(err) - } - - return conn -} - -func TestHstore(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - // quitely create hstore if it doesn't exist - _, err := db.Exec("CREATE EXTENSION IF NOT EXISTS hstore") - if err != nil { - t.Skipf("Skipping hstore tests - hstore extension create failed: %s", err.Error()) - } - - hs := Hstore{} - - // test for null-valued hstores - err = db.QueryRow("SELECT NULL::hstore").Scan(&hs) - if err != nil { - t.Fatal(err) - } - if hs.Map != nil { - t.Fatalf("expected null map") - } - - err = db.QueryRow("SELECT $1::hstore", hs).Scan(&hs) - if err != nil { - t.Fatalf("re-query null map failed: %s", err.Error()) - } - if hs.Map != nil { - t.Fatalf("expected null map") - } - - // test for empty hstores - err = db.QueryRow("SELECT ''::hstore").Scan(&hs) - if err != nil { - t.Fatal(err) - } - if hs.Map == nil { - t.Fatalf("expected empty map, got null map") - } - if len(hs.Map) != 0 { - t.Fatalf("expected empty map, got len(map)=%d", len(hs.Map)) - } - - err = db.QueryRow("SELECT $1::hstore", hs).Scan(&hs) - if err != nil { - t.Fatalf("re-query empty map failed: %s", err.Error()) - } - if hs.Map == nil { - t.Fatalf("expected empty map, got null map") - } - if len(hs.Map) != 0 { - t.Fatalf("expected empty map, got len(map)=%d", len(hs.Map)) - } - - // a few example maps to test out - hsOnePair := Hstore{ - Map: map[string]sql.NullString{ - "key1": {"value1", true}, - }, - } - - hsThreePairs := Hstore{ - Map: map[string]sql.NullString{ - "key1": {"value1", true}, - "key2": {"value2", true}, - "key3": {"value3", true}, - }, - } - - hsSmorgasbord := Hstore{ - Map: map[string]sql.NullString{ - "nullstring": {"NULL", true}, - "actuallynull": {"", false}, - "NULL": {"NULL string key", true}, - "withbracket": {"value>42", true}, - "withequal": {"value=42", true}, - `"withquotes1"`: {`this "should" be fine`, true}, - `"withquotes"2"`: {`this "should\" also be fine`, true}, - "embedded1": {"value1=>x1", true}, - "embedded2": {`"value2"=>x2`, true}, - "withnewlines": {"\n\nvalue\t=>2", true}, - "<>": {`this, "should,\" also, => be fine`, true}, - }, - } - - // test encoding in query params, then decoding during Scan - testBidirectional := func(h Hstore) { - err = db.QueryRow("SELECT $1::hstore", h).Scan(&hs) - if err != nil { - t.Fatalf("re-query %d-pair map failed: %s", len(h.Map), err.Error()) - } - if hs.Map == nil { - t.Fatalf("expected %d-pair map, got null map", len(h.Map)) - } - if len(hs.Map) != len(h.Map) { - t.Fatalf("expected %d-pair map, got len(map)=%d", len(h.Map), len(hs.Map)) - } - - for key, val := range hs.Map { - otherval, found := h.Map[key] - if !found { - t.Fatalf(" key '%v' not found in %d-pair map", key, len(h.Map)) - } - if otherval.Valid != val.Valid { - t.Fatalf(" value %v <> %v in %d-pair map", otherval, val, len(h.Map)) - } - if otherval.String != val.String { - t.Fatalf(" value '%v' <> '%v' in %d-pair map", otherval.String, val.String, len(h.Map)) - } - } - } - - testBidirectional(hsOnePair) - testBidirectional(hsThreePairs) - testBidirectional(hsSmorgasbord) -} diff --git a/vendor/github.com/lib/pq/listen_example/doc.go b/vendor/github.com/lib/pq/listen_example/doc.go deleted file mode 100644 index 5bc99f5c1..000000000 --- a/vendor/github.com/lib/pq/listen_example/doc.go +++ /dev/null @@ -1,102 +0,0 @@ -/* - -Below you will find a self-contained Go program which uses the LISTEN / NOTIFY -mechanism to avoid polling the database while waiting for more work to arrive. - - // - // You can see the program in action by defining a function similar to - // the following: - // - // CREATE OR REPLACE FUNCTION public.get_work() - // RETURNS bigint - // LANGUAGE sql - // AS $$ - // SELECT CASE WHEN random() >= 0.2 THEN int8 '1' END - // $$ - // ; - - package main - - import ( - "database/sql" - "fmt" - "time" - - "github.com/lib/pq" - ) - - func doWork(db *sql.DB, work int64) { - // work here - } - - func getWork(db *sql.DB) { - for { - // get work from the database here - var work sql.NullInt64 - err := db.QueryRow("SELECT get_work()").Scan(&work) - if err != nil { - fmt.Println("call to get_work() failed: ", err) - time.Sleep(10 * time.Second) - continue - } - if !work.Valid { - // no more work to do - fmt.Println("ran out of work") - return - } - - fmt.Println("starting work on ", work.Int64) - go doWork(db, work.Int64) - } - } - - func waitForNotification(l *pq.Listener) { - for { - select { - case <-l.Notify: - fmt.Println("received notification, new work available") - return - case <-time.After(90 * time.Second): - go func() { - l.Ping() - }() - // Check if there's more work available, just in case it takes - // a while for the Listener to notice connection loss and - // reconnect. - fmt.Println("received no work for 90 seconds, checking for new work") - return - } - } - } - - func main() { - var conninfo string = "" - - db, err := sql.Open("postgres", conninfo) - if err != nil { - panic(err) - } - - reportProblem := func(ev pq.ListenerEventType, err error) { - if err != nil { - fmt.Println(err.Error()) - } - } - - listener := pq.NewListener(conninfo, 10 * time.Second, time.Minute, reportProblem) - err = listener.Listen("getwork") - if err != nil { - panic(err) - } - - fmt.Println("entering main loop") - for { - // process all available work before waiting for notifications - getWork(db) - waitForNotification(listener) - } - } - - -*/ -package listen_example diff --git a/vendor/github.com/lib/pq/notify_test.go b/vendor/github.com/lib/pq/notify_test.go deleted file mode 100644 index fe8941a4e..000000000 --- a/vendor/github.com/lib/pq/notify_test.go +++ /dev/null @@ -1,574 +0,0 @@ -package pq - -import ( - "errors" - "fmt" - "io" - "os" - "runtime" - "sync" - "sync/atomic" - "testing" - "time" -) - -var errNilNotification = errors.New("nil notification") - -func expectNotification(t *testing.T, ch <-chan *Notification, relname string, extra string) error { - select { - case n := <-ch: - if n == nil { - return errNilNotification - } - if n.Channel != relname || n.Extra != extra { - return fmt.Errorf("unexpected notification %v", n) - } - return nil - case <-time.After(1500 * time.Millisecond): - return fmt.Errorf("timeout") - } -} - -func expectNoNotification(t *testing.T, ch <-chan *Notification) error { - select { - case n := <-ch: - return fmt.Errorf("unexpected notification %v", n) - case <-time.After(100 * time.Millisecond): - return nil - } -} - -func expectEvent(t *testing.T, eventch <-chan ListenerEventType, et ListenerEventType) error { - select { - case e := <-eventch: - if e != et { - return fmt.Errorf("unexpected event %v", e) - } - return nil - case <-time.After(1500 * time.Millisecond): - panic("expectEvent timeout") - } -} - -func expectNoEvent(t *testing.T, eventch <-chan ListenerEventType) error { - select { - case e := <-eventch: - return fmt.Errorf("unexpected event %v", e) - case <-time.After(100 * time.Millisecond): - return nil - } -} - -func newTestListenerConn(t *testing.T) (*ListenerConn, <-chan *Notification) { - datname := os.Getenv("PGDATABASE") - sslmode := os.Getenv("PGSSLMODE") - - if datname == "" { - os.Setenv("PGDATABASE", "pqgotest") - } - - if sslmode == "" { - os.Setenv("PGSSLMODE", "disable") - } - - notificationChan := make(chan *Notification) - l, err := NewListenerConn("", notificationChan) - if err != nil { - t.Fatal(err) - } - - return l, notificationChan -} - -func TestNewListenerConn(t *testing.T) { - l, _ := newTestListenerConn(t) - - defer l.Close() -} - -func TestConnListen(t *testing.T) { - l, channel := newTestListenerConn(t) - - defer l.Close() - - db := openTestConn(t) - defer db.Close() - - ok, err := l.Listen("notify_test") - if !ok || err != nil { - t.Fatal(err) - } - - _, err = db.Exec("NOTIFY notify_test") - if err != nil { - t.Fatal(err) - } - - err = expectNotification(t, channel, "notify_test", "") - if err != nil { - t.Fatal(err) - } -} - -func TestConnUnlisten(t *testing.T) { - l, channel := newTestListenerConn(t) - - defer l.Close() - - db := openTestConn(t) - defer db.Close() - - ok, err := l.Listen("notify_test") - if !ok || err != nil { - t.Fatal(err) - } - - _, err = db.Exec("NOTIFY notify_test") - - err = expectNotification(t, channel, "notify_test", "") - if err != nil { - t.Fatal(err) - } - - ok, err = l.Unlisten("notify_test") - if !ok || err != nil { - t.Fatal(err) - } - - _, err = db.Exec("NOTIFY notify_test") - if err != nil { - t.Fatal(err) - } - - err = expectNoNotification(t, channel) - if err != nil { - t.Fatal(err) - } -} - -func TestConnUnlistenAll(t *testing.T) { - l, channel := newTestListenerConn(t) - - defer l.Close() - - db := openTestConn(t) - defer db.Close() - - ok, err := l.Listen("notify_test") - if !ok || err != nil { - t.Fatal(err) - } - - _, err = db.Exec("NOTIFY notify_test") - - err = expectNotification(t, channel, "notify_test", "") - if err != nil { - t.Fatal(err) - } - - ok, err = l.UnlistenAll() - if !ok || err != nil { - t.Fatal(err) - } - - _, err = db.Exec("NOTIFY notify_test") - if err != nil { - t.Fatal(err) - } - - err = expectNoNotification(t, channel) - if err != nil { - t.Fatal(err) - } -} - -func TestConnClose(t *testing.T) { - l, _ := newTestListenerConn(t) - defer l.Close() - - err := l.Close() - if err != nil { - t.Fatal(err) - } - err = l.Close() - if err != errListenerConnClosed { - t.Fatalf("expected errListenerConnClosed; got %v", err) - } -} - -func TestConnPing(t *testing.T) { - l, _ := newTestListenerConn(t) - defer l.Close() - err := l.Ping() - if err != nil { - t.Fatal(err) - } - err = l.Close() - if err != nil { - t.Fatal(err) - } - err = l.Ping() - if err != errListenerConnClosed { - t.Fatalf("expected errListenerConnClosed; got %v", err) - } -} - -// Test for deadlock where a query fails while another one is queued -func TestConnExecDeadlock(t *testing.T) { - l, _ := newTestListenerConn(t) - defer l.Close() - - var wg sync.WaitGroup - wg.Add(2) - - go func() { - l.ExecSimpleQuery("SELECT pg_sleep(60)") - wg.Done() - }() - runtime.Gosched() - go func() { - l.ExecSimpleQuery("SELECT 1") - wg.Done() - }() - // give the two goroutines some time to get into position - runtime.Gosched() - // calls Close on the net.Conn; equivalent to a network failure - l.Close() - - var done int32 = 0 - go func() { - time.Sleep(10 * time.Second) - if atomic.LoadInt32(&done) != 1 { - panic("timed out") - } - }() - wg.Wait() - atomic.StoreInt32(&done, 1) -} - -// Test for ListenerConn being closed while a slow query is executing -func TestListenerConnCloseWhileQueryIsExecuting(t *testing.T) { - l, _ := newTestListenerConn(t) - defer l.Close() - - var wg sync.WaitGroup - wg.Add(1) - - go func() { - sent, err := l.ExecSimpleQuery("SELECT pg_sleep(60)") - if sent { - panic("expected sent=false") - } - // could be any of a number of errors - if err == nil { - panic("expected error") - } - wg.Done() - }() - // give the above goroutine some time to get into position - runtime.Gosched() - err := l.Close() - if err != nil { - t.Fatal(err) - } - var done int32 = 0 - go func() { - time.Sleep(10 * time.Second) - if atomic.LoadInt32(&done) != 1 { - panic("timed out") - } - }() - wg.Wait() - atomic.StoreInt32(&done, 1) -} - -func TestNotifyExtra(t *testing.T) { - db := openTestConn(t) - defer db.Close() - - if getServerVersion(t, db) < 90000 { - t.Skip("skipping NOTIFY payload test since the server does not appear to support it") - } - - l, channel := newTestListenerConn(t) - defer l.Close() - - ok, err := l.Listen("notify_test") - if !ok || err != nil { - t.Fatal(err) - } - - _, err = db.Exec("NOTIFY notify_test, 'something'") - if err != nil { - t.Fatal(err) - } - - err = expectNotification(t, channel, "notify_test", "something") - if err != nil { - t.Fatal(err) - } -} - -// create a new test listener and also set the timeouts -func newTestListenerTimeout(t *testing.T, min time.Duration, max time.Duration) (*Listener, <-chan ListenerEventType) { - datname := os.Getenv("PGDATABASE") - sslmode := os.Getenv("PGSSLMODE") - - if datname == "" { - os.Setenv("PGDATABASE", "pqgotest") - } - - if sslmode == "" { - os.Setenv("PGSSLMODE", "disable") - } - - eventch := make(chan ListenerEventType, 16) - l := NewListener("", min, max, func(t ListenerEventType, err error) { eventch <- t }) - err := expectEvent(t, eventch, ListenerEventConnected) - if err != nil { - t.Fatal(err) - } - return l, eventch -} - -func newTestListener(t *testing.T) (*Listener, <-chan ListenerEventType) { - return newTestListenerTimeout(t, time.Hour, time.Hour) -} - -func TestListenerListen(t *testing.T) { - l, _ := newTestListener(t) - defer l.Close() - - db := openTestConn(t) - defer db.Close() - - err := l.Listen("notify_listen_test") - if err != nil { - t.Fatal(err) - } - - _, err = db.Exec("NOTIFY notify_listen_test") - if err != nil { - t.Fatal(err) - } - - err = expectNotification(t, l.Notify, "notify_listen_test", "") - if err != nil { - t.Fatal(err) - } -} - -func TestListenerUnlisten(t *testing.T) { - l, _ := newTestListener(t) - defer l.Close() - - db := openTestConn(t) - defer db.Close() - - err := l.Listen("notify_listen_test") - if err != nil { - t.Fatal(err) - } - - _, err = db.Exec("NOTIFY notify_listen_test") - if err != nil { - t.Fatal(err) - } - - err = l.Unlisten("notify_listen_test") - if err != nil { - t.Fatal(err) - } - - err = expectNotification(t, l.Notify, "notify_listen_test", "") - if err != nil { - t.Fatal(err) - } - - _, err = db.Exec("NOTIFY notify_listen_test") - if err != nil { - t.Fatal(err) - } - - err = expectNoNotification(t, l.Notify) - if err != nil { - t.Fatal(err) - } -} - -func TestListenerUnlistenAll(t *testing.T) { - l, _ := newTestListener(t) - defer l.Close() - - db := openTestConn(t) - defer db.Close() - - err := l.Listen("notify_listen_test") - if err != nil { - t.Fatal(err) - } - - _, err = db.Exec("NOTIFY notify_listen_test") - if err != nil { - t.Fatal(err) - } - - err = l.UnlistenAll() - if err != nil { - t.Fatal(err) - } - - err = expectNotification(t, l.Notify, "notify_listen_test", "") - if err != nil { - t.Fatal(err) - } - - _, err = db.Exec("NOTIFY notify_listen_test") - if err != nil { - t.Fatal(err) - } - - err = expectNoNotification(t, l.Notify) - if err != nil { - t.Fatal(err) - } -} - -func TestListenerFailedQuery(t *testing.T) { - l, eventch := newTestListener(t) - defer l.Close() - - db := openTestConn(t) - defer db.Close() - - err := l.Listen("notify_listen_test") - if err != nil { - t.Fatal(err) - } - - _, err = db.Exec("NOTIFY notify_listen_test") - if err != nil { - t.Fatal(err) - } - - err = expectNotification(t, l.Notify, "notify_listen_test", "") - if err != nil { - t.Fatal(err) - } - - // shouldn't cause a disconnect - ok, err := l.cn.ExecSimpleQuery("SELECT error") - if !ok { - t.Fatalf("could not send query to server: %v", err) - } - _, ok = err.(PGError) - if !ok { - t.Fatalf("unexpected error %v", err) - } - err = expectNoEvent(t, eventch) - if err != nil { - t.Fatal(err) - } - - // should still work - _, err = db.Exec("NOTIFY notify_listen_test") - if err != nil { - t.Fatal(err) - } - - err = expectNotification(t, l.Notify, "notify_listen_test", "") - if err != nil { - t.Fatal(err) - } -} - -func TestListenerReconnect(t *testing.T) { - l, eventch := newTestListenerTimeout(t, 20*time.Millisecond, time.Hour) - defer l.Close() - - db := openTestConn(t) - defer db.Close() - - err := l.Listen("notify_listen_test") - if err != nil { - t.Fatal(err) - } - - _, err = db.Exec("NOTIFY notify_listen_test") - if err != nil { - t.Fatal(err) - } - - err = expectNotification(t, l.Notify, "notify_listen_test", "") - if err != nil { - t.Fatal(err) - } - - // kill the connection and make sure it comes back up - ok, err := l.cn.ExecSimpleQuery("SELECT pg_terminate_backend(pg_backend_pid())") - if ok { - t.Fatalf("could not kill the connection: %v", err) - } - if err != io.EOF { - t.Fatalf("unexpected error %v", err) - } - err = expectEvent(t, eventch, ListenerEventDisconnected) - if err != nil { - t.Fatal(err) - } - err = expectEvent(t, eventch, ListenerEventReconnected) - if err != nil { - t.Fatal(err) - } - - // should still work - _, err = db.Exec("NOTIFY notify_listen_test") - if err != nil { - t.Fatal(err) - } - - // should get nil after Reconnected - err = expectNotification(t, l.Notify, "", "") - if err != errNilNotification { - t.Fatal(err) - } - - err = expectNotification(t, l.Notify, "notify_listen_test", "") - if err != nil { - t.Fatal(err) - } -} - -func TestListenerClose(t *testing.T) { - l, _ := newTestListenerTimeout(t, 20*time.Millisecond, time.Hour) - defer l.Close() - - err := l.Close() - if err != nil { - t.Fatal(err) - } - err = l.Close() - if err != errListenerClosed { - t.Fatalf("expected errListenerClosed; got %v", err) - } -} - -func TestListenerPing(t *testing.T) { - l, _ := newTestListenerTimeout(t, 20*time.Millisecond, time.Hour) - defer l.Close() - - err := l.Ping() - if err != nil { - t.Fatal(err) - } - - err = l.Close() - if err != nil { - t.Fatal(err) - } - - err = l.Ping() - if err != errListenerClosed { - t.Fatalf("expected errListenerClosed; got %v", err) - } -} diff --git a/vendor/github.com/lib/pq/ssl_test.go b/vendor/github.com/lib/pq/ssl_test.go deleted file mode 100644 index 932b336f5..000000000 --- a/vendor/github.com/lib/pq/ssl_test.go +++ /dev/null @@ -1,226 +0,0 @@ -package pq - -// This file contains SSL tests - -import ( - _ "crypto/sha256" - "crypto/x509" - "database/sql" - "fmt" - "os" - "path/filepath" - "testing" -) - -func maybeSkipSSLTests(t *testing.T) { - // Require some special variables for testing certificates - if os.Getenv("PQSSLCERTTEST_PATH") == "" { - t.Skip("PQSSLCERTTEST_PATH not set, skipping SSL tests") - } - - value := os.Getenv("PQGOSSLTESTS") - if value == "" || value == "0" { - t.Skip("PQGOSSLTESTS not enabled, skipping SSL tests") - } else if value != "1" { - t.Fatalf("unexpected value %q for PQGOSSLTESTS", value) - } -} - -func openSSLConn(t *testing.T, conninfo string) (*sql.DB, error) { - db, err := openTestConnConninfo(conninfo) - if err != nil { - // should never fail - t.Fatal(err) - } - // Do something with the connection to see whether it's working or not. - tx, err := db.Begin() - if err == nil { - return db, tx.Rollback() - } - _ = db.Close() - return nil, err -} - -func checkSSLSetup(t *testing.T, conninfo string) { - db, err := openSSLConn(t, conninfo) - if err == nil { - db.Close() - t.Fatalf("expected error with conninfo=%q", conninfo) - } -} - -// Connect over SSL and run a simple query to test the basics -func TestSSLConnection(t *testing.T) { - maybeSkipSSLTests(t) - // Environment sanity check: should fail without SSL - checkSSLSetup(t, "sslmode=disable user=pqgossltest") - - db, err := openSSLConn(t, "sslmode=require user=pqgossltest") - if err != nil { - t.Fatal(err) - } - rows, err := db.Query("SELECT 1") - if err != nil { - t.Fatal(err) - } - rows.Close() -} - -// Test sslmode=verify-full -func TestSSLVerifyFull(t *testing.T) { - maybeSkipSSLTests(t) - // Environment sanity check: should fail without SSL - checkSSLSetup(t, "sslmode=disable user=pqgossltest") - - // Not OK according to the system CA - _, err := openSSLConn(t, "host=postgres sslmode=verify-full user=pqgossltest") - if err == nil { - t.Fatal("expected error") - } - _, ok := err.(x509.UnknownAuthorityError) - if !ok { - t.Fatalf("expected x509.UnknownAuthorityError, got %#+v", err) - } - - rootCertPath := filepath.Join(os.Getenv("PQSSLCERTTEST_PATH"), "root.crt") - rootCert := "sslrootcert=" + rootCertPath + " " - // No match on Common Name - _, err = openSSLConn(t, rootCert+"host=127.0.0.1 sslmode=verify-full user=pqgossltest") - if err == nil { - t.Fatal("expected error") - } - _, ok = err.(x509.HostnameError) - if !ok { - t.Fatalf("expected x509.HostnameError, got %#+v", err) - } - // OK - _, err = openSSLConn(t, rootCert+"host=postgres sslmode=verify-full user=pqgossltest") - if err != nil { - t.Fatal(err) - } -} - -// Test sslmode=verify-ca -func TestSSLVerifyCA(t *testing.T) { - maybeSkipSSLTests(t) - // Environment sanity check: should fail without SSL - checkSSLSetup(t, "sslmode=disable user=pqgossltest") - - // Not OK according to the system CA - _, err := openSSLConn(t, "host=postgres sslmode=verify-ca user=pqgossltest") - if err == nil { - t.Fatal("expected error") - } - _, ok := err.(x509.UnknownAuthorityError) - if !ok { - t.Fatalf("expected x509.UnknownAuthorityError, got %#+v", err) - } - - rootCertPath := filepath.Join(os.Getenv("PQSSLCERTTEST_PATH"), "root.crt") - rootCert := "sslrootcert=" + rootCertPath + " " - // No match on Common Name, but that's OK - _, err = openSSLConn(t, rootCert+"host=127.0.0.1 sslmode=verify-ca user=pqgossltest") - if err != nil { - t.Fatal(err) - } - // Everything OK - _, err = openSSLConn(t, rootCert+"host=postgres sslmode=verify-ca user=pqgossltest") - if err != nil { - t.Fatal(err) - } -} - -func getCertConninfo(t *testing.T, source string) string { - var sslkey string - var sslcert string - - certpath := os.Getenv("PQSSLCERTTEST_PATH") - - switch source { - case "missingkey": - sslkey = "/tmp/filedoesnotexist" - sslcert = filepath.Join(certpath, "postgresql.crt") - case "missingcert": - sslkey = filepath.Join(certpath, "postgresql.key") - sslcert = "/tmp/filedoesnotexist" - case "certtwice": - sslkey = filepath.Join(certpath, "postgresql.crt") - sslcert = filepath.Join(certpath, "postgresql.crt") - case "valid": - sslkey = filepath.Join(certpath, "postgresql.key") - sslcert = filepath.Join(certpath, "postgresql.crt") - default: - t.Fatalf("invalid source %q", source) - } - return fmt.Sprintf("sslmode=require user=pqgosslcert sslkey=%s sslcert=%s", sslkey, sslcert) -} - -// Authenticate over SSL using client certificates -func TestSSLClientCertificates(t *testing.T) { - maybeSkipSSLTests(t) - // Environment sanity check: should fail without SSL - checkSSLSetup(t, "sslmode=disable user=pqgossltest") - - // Should also fail without a valid certificate - db, err := openSSLConn(t, "sslmode=require user=pqgosslcert") - if err == nil { - db.Close() - t.Fatal("expected error") - } - pge, ok := err.(*Error) - if !ok { - t.Fatal("expected pq.Error") - } - if pge.Code.Name() != "invalid_authorization_specification" { - t.Fatalf("unexpected error code %q", pge.Code.Name()) - } - - // Should work - db, err = openSSLConn(t, getCertConninfo(t, "valid")) - if err != nil { - t.Fatal(err) - } - rows, err := db.Query("SELECT 1") - if err != nil { - t.Fatal(err) - } - rows.Close() -} - -// Test errors with ssl certificates -func TestSSLClientCertificatesMissingFiles(t *testing.T) { - maybeSkipSSLTests(t) - // Environment sanity check: should fail without SSL - checkSSLSetup(t, "sslmode=disable user=pqgossltest") - - // Key missing, should fail - _, err := openSSLConn(t, getCertConninfo(t, "missingkey")) - if err == nil { - t.Fatal("expected error") - } - // should be a PathError - _, ok := err.(*os.PathError) - if !ok { - t.Fatalf("expected PathError, got %#+v", err) - } - - // Cert missing, should fail - _, err = openSSLConn(t, getCertConninfo(t, "missingcert")) - if err == nil { - t.Fatal("expected error") - } - // should be a PathError - _, ok = err.(*os.PathError) - if !ok { - t.Fatalf("expected PathError, got %#+v", err) - } - - // Key has wrong permissions, should fail - _, err = openSSLConn(t, getCertConninfo(t, "certtwice")) - if err == nil { - t.Fatal("expected error") - } - if err != ErrSSLKeyHasWorldPermissions { - t.Fatalf("expected ErrSSLKeyHasWorldPermissions, got %#+v", err) - } -} diff --git a/vendor/github.com/lib/pq/url_test.go b/vendor/github.com/lib/pq/url_test.go deleted file mode 100644 index 29f4a7c75..000000000 --- a/vendor/github.com/lib/pq/url_test.go +++ /dev/null @@ -1,54 +0,0 @@ -package pq - -import ( - "testing" -) - -func TestSimpleParseURL(t *testing.T) { - expected := "host=hostname.remote" - str, err := ParseURL("postgres://hostname.remote") - if err != nil { - t.Fatal(err) - } - - if str != expected { - t.Fatalf("unexpected result from ParseURL:\n+ %v\n- %v", str, expected) - } -} - -func TestFullParseURL(t *testing.T) { - expected := `dbname=database host=hostname.remote password=top\ secret port=1234 user=username` - str, err := ParseURL("postgres://username:top%20secret@hostname.remote:1234/database") - if err != nil { - t.Fatal(err) - } - - if str != expected { - t.Fatalf("unexpected result from ParseURL:\n+ %s\n- %s", str, expected) - } -} - -func TestInvalidProtocolParseURL(t *testing.T) { - _, err := ParseURL("http://hostname.remote") - switch err { - case nil: - t.Fatal("Expected an error from parsing invalid protocol") - default: - msg := "invalid connection protocol: http" - if err.Error() != msg { - t.Fatalf("Unexpected error message:\n+ %s\n- %s", - err.Error(), msg) - } - } -} - -func TestMinimalURL(t *testing.T) { - cs, err := ParseURL("postgres://") - if err != nil { - t.Fatal(err) - } - - if cs != "" { - t.Fatalf("expected blank connection string, got: %q", cs) - } -} diff --git a/vendor/github.com/manucorporat/sse/sse-decoder.go b/vendor/github.com/manucorporat/sse/sse-decoder.go index e1afc6f36..fd49b9c37 100644 --- a/vendor/github.com/manucorporat/sse/sse-decoder.go +++ b/vendor/github.com/manucorporat/sse/sse-decoder.go @@ -109,6 +109,7 @@ func (d *decoder) decode(r io.Reader) ([]Event, error) { continue } } + // Once the end of the file is reached, the user agent must dispatch the event one final time. d.dispatchEvent(currentEvent, dataBuffer.String()) return d.events, nil diff --git a/vendor/github.com/manucorporat/sse/sse-decoder_test.go b/vendor/github.com/manucorporat/sse/sse-decoder_test.go deleted file mode 100644 index 068107b64..000000000 --- a/vendor/github.com/manucorporat/sse/sse-decoder_test.go +++ /dev/null @@ -1,116 +0,0 @@ -// Copyright 2014 Manu Martinez-Almeida. All rights reserved. -// Use of this source code is governed by a MIT style -// license that can be found in the LICENSE file. - -package sse - -import ( - "bytes" - "testing" - - "github.com/stretchr/testify/assert" -) - -func TestDecodeSingle1(t *testing.T) { - events, err := Decode(bytes.NewBufferString( - `data: this is a text -event: message -fake: -id: 123456789010 -: we can append data -: and multiple comments should not break it -data: a very nice one`)) - - assert.NoError(t, err) - assert.Len(t, events, 1) - assert.Equal(t, events[0].Event, "message") - assert.Equal(t, events[0].Id, "123456789010") -} - -func TestDecodeSingle2(t *testing.T) { - events, err := Decode(bytes.NewBufferString( - `: starting with a comment -fake: - -data:this is a \ntext -event:a message\n\n -fake -:and multiple comments\n should not break it\n\n -id:1234567890\n10 -:we can append data -data:a very nice one\n! - - -`)) - assert.NoError(t, err) - assert.Len(t, events, 1) - assert.Equal(t, events[0].Event, "a message\\n\\n") - assert.Equal(t, events[0].Id, "1234567890\\n10") -} - -func TestDecodeSingle3(t *testing.T) { - events, err := Decode(bytes.NewBufferString( - ` -id:123456ABCabc789010 -event: message123 -: we can append data -data:this is a text -data: a very nice one -data: -data -: ending with a comment`)) - - assert.NoError(t, err) - assert.Len(t, events, 1) - assert.Equal(t, events[0].Event, "message123") - assert.Equal(t, events[0].Id, "123456ABCabc789010") -} - -func TestDecodeMulti1(t *testing.T) { - events, err := Decode(bytes.NewBufferString( - ` -id: -event: weird event -data:this is a text -:data: this should NOT APER -data: second line - -: a comment -event: message -id:123 -data:this is a text -:data: this should NOT APER -data: second line - - -: a comment -event: message -id:123 -data:this is a text -data: second line - -:hola - -data - -event: - -id`)) - assert.NoError(t, err) - assert.Len(t, events, 3) - assert.Equal(t, events[0].Event, "weird event") - assert.Equal(t, events[0].Id, "") -} - -func TestDecodeW3C(t *testing.T) { - events, err := Decode(bytes.NewBufferString( - `data - -data -data - -data: -`)) - assert.NoError(t, err) - assert.Len(t, events, 1) -} diff --git a/vendor/github.com/manucorporat/sse/sse_test.go b/vendor/github.com/manucorporat/sse/sse_test.go deleted file mode 100644 index 61b685b0e..000000000 --- a/vendor/github.com/manucorporat/sse/sse_test.go +++ /dev/null @@ -1,255 +0,0 @@ -// Copyright 2014 Manu Martinez-Almeida. All rights reserved. -// Use of this source code is governed by a MIT style -// license that can be found in the LICENSE file. - -package sse - -import ( - "bytes" - "net/http/httptest" - "testing" - - "github.com/stretchr/testify/assert" -) - -func TestEncodeOnlyData(t *testing.T) { - w := new(bytes.Buffer) - event := Event{ - Data: "junk\n\njk\nid:fake", - } - err := Encode(w, event) - assert.NoError(t, err) - assert.Equal(t, w.String(), - `data:junk -data: -data:jk -data:id:fake - -`) - - decoded, _ := Decode(w) - assert.Equal(t, decoded, []Event{event}) -} - -func TestEncodeWithEvent(t *testing.T) { - w := new(bytes.Buffer) - event := Event{ - Event: "t\n:<>\r\test", - Data: "junk\n\njk\nid:fake", - } - err := Encode(w, event) - assert.NoError(t, err) - assert.Equal(t, w.String(), - `event:t\n:<>\r est -data:junk -data: -data:jk -data:id:fake - -`) - - decoded, _ := Decode(w) - assert.Equal(t, decoded, []Event{event}) -} - -func TestEncodeWithId(t *testing.T) { - w := new(bytes.Buffer) - err := Encode(w, Event{ - Id: "t\n:<>\r\test", - Data: "junk\n\njk\nid:fa\rke", - }) - assert.NoError(t, err) - assert.Equal(t, w.String(), - `id:t\n:<>\r est -data:junk -data: -data:jk -data:id:fa\rke - -`) -} - -func TestEncodeWithRetry(t *testing.T) { - w := new(bytes.Buffer) - err := Encode(w, Event{ - Retry: 11, - Data: "junk\n\njk\nid:fake\n", - }) - assert.NoError(t, err) - assert.Equal(t, w.String(), - `retry:11 -data:junk -data: -data:jk -data:id:fake -data: - -`) -} - -func TestEncodeWithEverything(t *testing.T) { - w := new(bytes.Buffer) - err := Encode(w, Event{ - Event: "abc", - Id: "12345", - Retry: 10, - Data: "some data", - }) - assert.NoError(t, err) - assert.Equal(t, w.String(), "id:12345\nevent:abc\nretry:10\ndata:some data\n\n") -} - -func TestEncodeMap(t *testing.T) { - w := new(bytes.Buffer) - err := Encode(w, Event{ - Event: "a map", - Data: map[string]interface{}{ - "foo": "b\n\rar", - "bar": "id: 2", - }, - }) - assert.NoError(t, err) - assert.Equal(t, w.String(), "event:a map\ndata:{\"bar\":\"id: 2\",\"foo\":\"b\\n\\rar\"}\n\n") -} - -func TestEncodeSlice(t *testing.T) { - w := new(bytes.Buffer) - err := Encode(w, Event{ - Event: "a slice", - Data: []interface{}{1, "text", map[string]interface{}{"foo": "bar"}}, - }) - assert.NoError(t, err) - assert.Equal(t, w.String(), "event:a slice\ndata:[1,\"text\",{\"foo\":\"bar\"}]\n\n") -} - -func TestEncodeStruct(t *testing.T) { - myStruct := struct { - A int - B string `json:"value"` - }{1, "number"} - - w := new(bytes.Buffer) - err := Encode(w, Event{ - Event: "a struct", - Data: myStruct, - }) - assert.NoError(t, err) - assert.Equal(t, w.String(), "event:a struct\ndata:{\"A\":1,\"value\":\"number\"}\n\n") - - w.Reset() - err = Encode(w, Event{ - Event: "a struct", - Data: &myStruct, - }) - assert.NoError(t, err) - assert.Equal(t, w.String(), "event:a struct\ndata:{\"A\":1,\"value\":\"number\"}\n\n") -} - -func TestEncodeInteger(t *testing.T) { - w := new(bytes.Buffer) - err := Encode(w, Event{ - Event: "an integer", - Data: 1, - }) - assert.NoError(t, err) - assert.Equal(t, w.String(), "event:an integer\ndata:1\n\n") -} - -func TestEncodeFloat(t *testing.T) { - w := new(bytes.Buffer) - err := Encode(w, Event{ - Event: "Float", - Data: 1.5, - }) - assert.NoError(t, err) - assert.Equal(t, w.String(), "event:Float\ndata:1.5\n\n") -} - -func TestEncodeStream(t *testing.T) { - w := new(bytes.Buffer) - - Encode(w, Event{ - Event: "float", - Data: 1.5, - }) - - Encode(w, Event{ - Id: "123", - Data: map[string]interface{}{"foo": "bar", "bar": "foo"}, - }) - - Encode(w, Event{ - Id: "124", - Event: "chat", - Data: "hi! dude", - }) - assert.Equal(t, w.String(), "event:float\ndata:1.5\n\nid:123\ndata:{\"bar\":\"foo\",\"foo\":\"bar\"}\n\nid:124\nevent:chat\ndata:hi! dude\n\n") -} - -func TestRenderSSE(t *testing.T) { - w := httptest.NewRecorder() - - err := (Event{ - Event: "msg", - Data: "hi! how are you?", - }).Render(w) - - assert.NoError(t, err) - assert.Equal(t, w.Body.String(), "event:msg\ndata:hi! how are you?\n\n") - assert.Equal(t, w.Header().Get("Content-Type"), "text/event-stream") - assert.Equal(t, w.Header().Get("Cache-Control"), "no-cache") -} - -func BenchmarkResponseWriter(b *testing.B) { - w := httptest.NewRecorder() - b.ResetTimer() - b.ReportAllocs() - for i := 0; i < b.N; i++ { - (Event{ - Event: "new_message", - Data: "hi! how are you? I am fine. this is a long stupid message!!!", - }).Render(w) - } -} - -func BenchmarkFullSSE(b *testing.B) { - buf := new(bytes.Buffer) - b.ResetTimer() - b.ReportAllocs() - for i := 0; i < b.N; i++ { - Encode(buf, Event{ - Event: "new_message", - Id: "13435", - Retry: 10, - Data: "hi! how are you? I am fine. this is a long stupid message!!!", - }) - buf.Reset() - } -} - -func BenchmarkNoRetrySSE(b *testing.B) { - buf := new(bytes.Buffer) - b.ResetTimer() - b.ReportAllocs() - for i := 0; i < b.N; i++ { - Encode(buf, Event{ - Event: "new_message", - Id: "13435", - Data: "hi! how are you? I am fine. this is a long stupid message!!!", - }) - buf.Reset() - } -} - -func BenchmarkSimpleSSE(b *testing.B) { - buf := new(bytes.Buffer) - b.ResetTimer() - b.ReportAllocs() - for i := 0; i < b.N; i++ { - Encode(buf, Event{ - Event: "new_message", - Data: "hi! how are you? I am fine. this is a long stupid message!!!", - }) - buf.Reset() - } -} diff --git a/vendor/github.com/manucorporat/stats/stats.go b/vendor/github.com/manucorporat/stats/stats.go deleted file mode 100644 index 250e5416e..000000000 --- a/vendor/github.com/manucorporat/stats/stats.go +++ /dev/null @@ -1,87 +0,0 @@ -package stats - -import "sync" - -type ValueType float64 -type StatsType map[string]ValueType - -type StatsCollector struct { - lock sync.RWMutex - stats StatsType -} - -func New() *StatsCollector { - s := new(StatsCollector) - s.Reset() - return s -} - -func (s *StatsCollector) Reset() { - s.lock.Lock() - s.stats = make(StatsType) - s.lock.Unlock() -} - -func (s *StatsCollector) Set(key string, value ValueType) { - s.lock.Lock() - s.stats[key] = value - s.lock.Unlock() -} - -func (s *StatsCollector) Add(key string, delta ValueType) (v ValueType) { - s.lock.Lock() - v = s.stats[key] - v += delta - s.stats[key] = v - s.lock.Unlock() - return -} - -func (s *StatsCollector) Get(key string) (v ValueType) { - s.lock.RLock() - v = s.stats[key] - s.lock.RUnlock() - return -} - -func (s *StatsCollector) Del(key string) { - s.lock.Lock() - delete(s.stats, key) - s.lock.Unlock() -} - -func (s *StatsCollector) Data() StatsType { - cp := make(StatsType) - s.lock.RLock() - for key, value := range s.stats { - cp[key] = value - } - s.lock.RUnlock() - return cp -} - -var defaultCollector = New() - -func Reset() { - defaultCollector.Reset() -} - -func Set(key string, value ValueType) { - defaultCollector.Set(key, value) -} - -func Del(key string) { - defaultCollector.Del(key) -} - -func Add(key string, delta ValueType) ValueType { - return defaultCollector.Add(key, delta) -} - -func Get(key string) ValueType { - return defaultCollector.Get(key) -} - -func Data() StatsType { - return defaultCollector.Data() -} diff --git a/vendor/github.com/mattn/go-colorable/README.md b/vendor/github.com/mattn/go-colorable/README.md deleted file mode 100644 index e84226a73..000000000 --- a/vendor/github.com/mattn/go-colorable/README.md +++ /dev/null @@ -1,43 +0,0 @@ -# go-colorable - -Colorable writer for windows. - -For example, most of logger packages doesn't show colors on windows. (I know we can do it with ansicon. But I don't want.) -This package is possible to handle escape sequence for ansi color on windows. - -## Too Bad! - -![](https://raw.githubusercontent.com/mattn/go-colorable/gh-pages/bad.png) - - -## So Good! - -![](https://raw.githubusercontent.com/mattn/go-colorable/gh-pages/good.png) - -## Usage - -```go -logrus.SetFormatter(&logrus.TextFormatter{ForceColors: true}) -logrus.SetOutput(colorable.NewColorableStdout()) - -logrus.Info("succeeded") -logrus.Warn("not correct") -logrus.Error("something error") -logrus.Fatal("panic") -``` - -You can compile above code on non-windows OSs. - -## Installation - -``` -$ go get github.com/mattn/go-colorable -``` - -# License - -MIT - -# Author - -Yasuhiro Matsumoto (a.k.a mattn) diff --git a/vendor/github.com/mattn/go-colorable/colorable_others.go b/vendor/github.com/mattn/go-colorable/colorable_others.go deleted file mode 100644 index 219f02f62..000000000 --- a/vendor/github.com/mattn/go-colorable/colorable_others.go +++ /dev/null @@ -1,16 +0,0 @@ -// +build !windows - -package colorable - -import ( - "io" - "os" -) - -func NewColorableStdout() io.Writer { - return os.Stdout -} - -func NewColorableStderr() io.Writer { - return os.Stderr -} diff --git a/vendor/github.com/mattn/go-colorable/colorable_windows.go b/vendor/github.com/mattn/go-colorable/colorable_windows.go deleted file mode 100644 index 6a2787808..000000000 --- a/vendor/github.com/mattn/go-colorable/colorable_windows.go +++ /dev/null @@ -1,594 +0,0 @@ -package colorable - -import ( - "bytes" - "fmt" - "io" - "os" - "strconv" - "strings" - "syscall" - "unsafe" - - "github.com/mattn/go-isatty" -) - -const ( - foregroundBlue = 0x1 - foregroundGreen = 0x2 - foregroundRed = 0x4 - foregroundIntensity = 0x8 - foregroundMask = (foregroundRed | foregroundBlue | foregroundGreen | foregroundIntensity) - backgroundBlue = 0x10 - backgroundGreen = 0x20 - backgroundRed = 0x40 - backgroundIntensity = 0x80 - backgroundMask = (backgroundRed | backgroundBlue | backgroundGreen | backgroundIntensity) -) - -type wchar uint16 -type short int16 -type dword uint32 -type word uint16 - -type coord struct { - x short - y short -} - -type smallRect struct { - left short - top short - right short - bottom short -} - -type consoleScreenBufferInfo struct { - size coord - cursorPosition coord - attributes word - window smallRect - maximumWindowSize coord -} - -var ( - kernel32 = syscall.NewLazyDLL("kernel32.dll") - procGetConsoleScreenBufferInfo = kernel32.NewProc("GetConsoleScreenBufferInfo") - procSetConsoleTextAttribute = kernel32.NewProc("SetConsoleTextAttribute") -) - -type Writer struct { - out io.Writer - handle syscall.Handle - lastbuf bytes.Buffer - oldattr word -} - -func NewColorableStdout() io.Writer { - var csbi consoleScreenBufferInfo - out := os.Stdout - if !isatty.IsTerminal(out.Fd()) { - return out - } - handle := syscall.Handle(out.Fd()) - procGetConsoleScreenBufferInfo.Call(uintptr(handle), uintptr(unsafe.Pointer(&csbi))) - return &Writer{out: out, handle: handle, oldattr: csbi.attributes} -} - -func NewColorableStderr() io.Writer { - var csbi consoleScreenBufferInfo - out := os.Stderr - if !isatty.IsTerminal(out.Fd()) { - return out - } - handle := syscall.Handle(out.Fd()) - procGetConsoleScreenBufferInfo.Call(uintptr(handle), uintptr(unsafe.Pointer(&csbi))) - return &Writer{out: out, handle: handle, oldattr: csbi.attributes} -} - -var color256 = map[int]int{ - 0: 0x000000, - 1: 0x800000, - 2: 0x008000, - 3: 0x808000, - 4: 0x000080, - 5: 0x800080, - 6: 0x008080, - 7: 0xc0c0c0, - 8: 0x808080, - 9: 0xff0000, - 10: 0x00ff00, - 11: 0xffff00, - 12: 0x0000ff, - 13: 0xff00ff, - 14: 0x00ffff, - 15: 0xffffff, - 16: 0x000000, - 17: 0x00005f, - 18: 0x000087, - 19: 0x0000af, - 20: 0x0000d7, - 21: 0x0000ff, - 22: 0x005f00, - 23: 0x005f5f, - 24: 0x005f87, - 25: 0x005faf, - 26: 0x005fd7, - 27: 0x005fff, - 28: 0x008700, - 29: 0x00875f, - 30: 0x008787, - 31: 0x0087af, - 32: 0x0087d7, - 33: 0x0087ff, - 34: 0x00af00, - 35: 0x00af5f, - 36: 0x00af87, - 37: 0x00afaf, - 38: 0x00afd7, - 39: 0x00afff, - 40: 0x00d700, - 41: 0x00d75f, - 42: 0x00d787, - 43: 0x00d7af, - 44: 0x00d7d7, - 45: 0x00d7ff, - 46: 0x00ff00, - 47: 0x00ff5f, - 48: 0x00ff87, - 49: 0x00ffaf, - 50: 0x00ffd7, - 51: 0x00ffff, - 52: 0x5f0000, - 53: 0x5f005f, - 54: 0x5f0087, - 55: 0x5f00af, - 56: 0x5f00d7, - 57: 0x5f00ff, - 58: 0x5f5f00, - 59: 0x5f5f5f, - 60: 0x5f5f87, - 61: 0x5f5faf, - 62: 0x5f5fd7, - 63: 0x5f5fff, - 64: 0x5f8700, - 65: 0x5f875f, - 66: 0x5f8787, - 67: 0x5f87af, - 68: 0x5f87d7, - 69: 0x5f87ff, - 70: 0x5faf00, - 71: 0x5faf5f, - 72: 0x5faf87, - 73: 0x5fafaf, - 74: 0x5fafd7, - 75: 0x5fafff, - 76: 0x5fd700, - 77: 0x5fd75f, - 78: 0x5fd787, - 79: 0x5fd7af, - 80: 0x5fd7d7, - 81: 0x5fd7ff, - 82: 0x5fff00, - 83: 0x5fff5f, - 84: 0x5fff87, - 85: 0x5fffaf, - 86: 0x5fffd7, - 87: 0x5fffff, - 88: 0x870000, - 89: 0x87005f, - 90: 0x870087, - 91: 0x8700af, - 92: 0x8700d7, - 93: 0x8700ff, - 94: 0x875f00, - 95: 0x875f5f, - 96: 0x875f87, - 97: 0x875faf, - 98: 0x875fd7, - 99: 0x875fff, - 100: 0x878700, - 101: 0x87875f, - 102: 0x878787, - 103: 0x8787af, - 104: 0x8787d7, - 105: 0x8787ff, - 106: 0x87af00, - 107: 0x87af5f, - 108: 0x87af87, - 109: 0x87afaf, - 110: 0x87afd7, - 111: 0x87afff, - 112: 0x87d700, - 113: 0x87d75f, - 114: 0x87d787, - 115: 0x87d7af, - 116: 0x87d7d7, - 117: 0x87d7ff, - 118: 0x87ff00, - 119: 0x87ff5f, - 120: 0x87ff87, - 121: 0x87ffaf, - 122: 0x87ffd7, - 123: 0x87ffff, - 124: 0xaf0000, - 125: 0xaf005f, - 126: 0xaf0087, - 127: 0xaf00af, - 128: 0xaf00d7, - 129: 0xaf00ff, - 130: 0xaf5f00, - 131: 0xaf5f5f, - 132: 0xaf5f87, - 133: 0xaf5faf, - 134: 0xaf5fd7, - 135: 0xaf5fff, - 136: 0xaf8700, - 137: 0xaf875f, - 138: 0xaf8787, - 139: 0xaf87af, - 140: 0xaf87d7, - 141: 0xaf87ff, - 142: 0xafaf00, - 143: 0xafaf5f, - 144: 0xafaf87, - 145: 0xafafaf, - 146: 0xafafd7, - 147: 0xafafff, - 148: 0xafd700, - 149: 0xafd75f, - 150: 0xafd787, - 151: 0xafd7af, - 152: 0xafd7d7, - 153: 0xafd7ff, - 154: 0xafff00, - 155: 0xafff5f, - 156: 0xafff87, - 157: 0xafffaf, - 158: 0xafffd7, - 159: 0xafffff, - 160: 0xd70000, - 161: 0xd7005f, - 162: 0xd70087, - 163: 0xd700af, - 164: 0xd700d7, - 165: 0xd700ff, - 166: 0xd75f00, - 167: 0xd75f5f, - 168: 0xd75f87, - 169: 0xd75faf, - 170: 0xd75fd7, - 171: 0xd75fff, - 172: 0xd78700, - 173: 0xd7875f, - 174: 0xd78787, - 175: 0xd787af, - 176: 0xd787d7, - 177: 0xd787ff, - 178: 0xd7af00, - 179: 0xd7af5f, - 180: 0xd7af87, - 181: 0xd7afaf, - 182: 0xd7afd7, - 183: 0xd7afff, - 184: 0xd7d700, - 185: 0xd7d75f, - 186: 0xd7d787, - 187: 0xd7d7af, - 188: 0xd7d7d7, - 189: 0xd7d7ff, - 190: 0xd7ff00, - 191: 0xd7ff5f, - 192: 0xd7ff87, - 193: 0xd7ffaf, - 194: 0xd7ffd7, - 195: 0xd7ffff, - 196: 0xff0000, - 197: 0xff005f, - 198: 0xff0087, - 199: 0xff00af, - 200: 0xff00d7, - 201: 0xff00ff, - 202: 0xff5f00, - 203: 0xff5f5f, - 204: 0xff5f87, - 205: 0xff5faf, - 206: 0xff5fd7, - 207: 0xff5fff, - 208: 0xff8700, - 209: 0xff875f, - 210: 0xff8787, - 211: 0xff87af, - 212: 0xff87d7, - 213: 0xff87ff, - 214: 0xffaf00, - 215: 0xffaf5f, - 216: 0xffaf87, - 217: 0xffafaf, - 218: 0xffafd7, - 219: 0xffafff, - 220: 0xffd700, - 221: 0xffd75f, - 222: 0xffd787, - 223: 0xffd7af, - 224: 0xffd7d7, - 225: 0xffd7ff, - 226: 0xffff00, - 227: 0xffff5f, - 228: 0xffff87, - 229: 0xffffaf, - 230: 0xffffd7, - 231: 0xffffff, - 232: 0x080808, - 233: 0x121212, - 234: 0x1c1c1c, - 235: 0x262626, - 236: 0x303030, - 237: 0x3a3a3a, - 238: 0x444444, - 239: 0x4e4e4e, - 240: 0x585858, - 241: 0x626262, - 242: 0x6c6c6c, - 243: 0x767676, - 244: 0x808080, - 245: 0x8a8a8a, - 246: 0x949494, - 247: 0x9e9e9e, - 248: 0xa8a8a8, - 249: 0xb2b2b2, - 250: 0xbcbcbc, - 251: 0xc6c6c6, - 252: 0xd0d0d0, - 253: 0xdadada, - 254: 0xe4e4e4, - 255: 0xeeeeee, -} - -func (w *Writer) Write(data []byte) (n int, err error) { - var csbi consoleScreenBufferInfo - procGetConsoleScreenBufferInfo.Call(uintptr(w.handle), uintptr(unsafe.Pointer(&csbi))) - - er := bytes.NewBuffer(data) -loop: - for { - r1, _, err := procGetConsoleScreenBufferInfo.Call(uintptr(w.handle), uintptr(unsafe.Pointer(&csbi))) - if r1 == 0 { - break loop - } - - c1, _, err := er.ReadRune() - if err != nil { - break loop - } - if c1 != 0x1b { - fmt.Fprint(w.out, string(c1)) - continue - } - c2, _, err := er.ReadRune() - if err != nil { - w.lastbuf.WriteRune(c1) - break loop - } - if c2 != 0x5b { - w.lastbuf.WriteRune(c1) - w.lastbuf.WriteRune(c2) - continue - } - - var buf bytes.Buffer - var m rune - for { - c, _, err := er.ReadRune() - if err != nil { - w.lastbuf.WriteRune(c1) - w.lastbuf.WriteRune(c2) - w.lastbuf.Write(buf.Bytes()) - break loop - } - if ('a' <= c && c <= 'z') || ('A' <= c && c <= 'Z') || c == '@' { - m = c - break - } - buf.Write([]byte(string(c))) - } - - switch m { - case 'm': - attr := csbi.attributes - cs := buf.String() - if cs == "" { - procSetConsoleTextAttribute.Call(uintptr(w.handle), uintptr(w.oldattr)) - continue - } - token := strings.Split(cs, ";") - for i, ns := range token { - if n, err = strconv.Atoi(ns); err == nil { - switch { - case n == 0 || n == 100: - attr = w.oldattr - case 1 <= n && n <= 5: - attr |= foregroundIntensity - case n == 7: - attr = ((attr & foregroundMask) << 4) | ((attr & backgroundMask) >> 4) - case 22 == n || n == 25 || n == 25: - attr |= foregroundIntensity - case n == 27: - attr = ((attr & foregroundMask) << 4) | ((attr & backgroundMask) >> 4) - case 30 <= n && n <= 37: - attr = (attr & backgroundMask) - if (n-30)&1 != 0 { - attr |= foregroundRed - } - if (n-30)&2 != 0 { - attr |= foregroundGreen - } - if (n-30)&4 != 0 { - attr |= foregroundBlue - } - case n == 38: // set foreground color. - if i < len(token)-2 && token[i+1] == "5" { - if n256, err := strconv.Atoi(token[i+2]); err == nil { - if n256foreAttr == nil { - n256setup() - } - attr &= backgroundMask - attr |= n256foreAttr[n256] - i += 2 - } - } else { - attr = attr & (w.oldattr & backgroundMask) - } - case n == 39: // reset foreground color. - attr &= backgroundMask - attr |= w.oldattr & foregroundMask - case 40 <= n && n <= 47: - attr = (attr & foregroundMask) - if (n-40)&1 != 0 { - attr |= backgroundRed - } - if (n-40)&2 != 0 { - attr |= backgroundGreen - } - if (n-40)&4 != 0 { - attr |= backgroundBlue - } - case n == 48: // set background color. - if i < len(token)-2 && token[i+1] == "5" { - if n256, err := strconv.Atoi(token[i+2]); err == nil { - if n256backAttr == nil { - n256setup() - } - attr &= foregroundMask - attr |= n256backAttr[n256] - i += 2 - } - } else { - attr = attr & (w.oldattr & foregroundMask) - } - case n == 49: // reset foreground color. - attr &= foregroundMask - attr |= w.oldattr & backgroundMask - } - procSetConsoleTextAttribute.Call(uintptr(w.handle), uintptr(attr)) - } - } - } - } - return len(data) - w.lastbuf.Len(), nil -} - -type consoleColor struct { - red bool - green bool - blue bool - intensity bool -} - -func minmax3(a, b, c int) (min, max int) { - if a < b { - if b < c { - return a, c - } else if a < c { - return a, b - } else { - return c, b - } - } else { - if a < c { - return b, c - } else if b < c { - return b, a - } else { - return c, a - } - } -} - -func toConsoleColor(rgb int) (c consoleColor) { - r, g, b := (rgb&0xFF0000)>>16, (rgb&0x00FF00)>>8, rgb&0x0000FF - min, max := minmax3(r, g, b) - a := (min + max) / 2 - if r < 128 && g < 128 && b < 128 { - if r >= a { - c.red = true - } - if g >= a { - c.green = true - } - if b >= a { - c.blue = true - } - // non-intensed white is lighter than intensed black, so swap those. - if c.red && c.green && c.blue { - c.red, c.green, c.blue = false, false, false - c.intensity = true - } - } else { - if min < 128 { - min = 128 - a = (min + max) / 2 - } - if r >= a { - c.red = true - } - if g >= a { - c.green = true - } - if b >= a { - c.blue = true - } - c.intensity = true - // intensed black is darker than non-intensed white, so swap those. - if !c.red && !c.green && !c.blue { - c.red, c.green, c.blue = true, true, true - c.intensity = false - } - } - return c -} - -func (c consoleColor) foregroundAttr() (attr word) { - if c.red { - attr |= foregroundRed - } - if c.green { - attr |= foregroundGreen - } - if c.blue { - attr |= foregroundBlue - } - if c.intensity { - attr |= foregroundIntensity - } - return -} - -func (c consoleColor) backgroundAttr() (attr word) { - if c.red { - attr |= backgroundRed - } - if c.green { - attr |= backgroundGreen - } - if c.blue { - attr |= backgroundBlue - } - if c.intensity { - attr |= backgroundIntensity - } - return -} - -var n256foreAttr []word -var n256backAttr []word - -func n256setup() { - n256foreAttr = make([]word, 256) - n256backAttr = make([]word, 256) - for i, rgb := range color256 { - c := toConsoleColor(rgb) - n256foreAttr[i] = c.foregroundAttr() - n256backAttr[i] = c.backgroundAttr() - } -} diff --git a/vendor/github.com/mattn/go-sqlite3/README.md b/vendor/github.com/mattn/go-sqlite3/README.md index 9d04745fa..d69e30580 100644 --- a/vendor/github.com/mattn/go-sqlite3/README.md +++ b/vendor/github.com/mattn/go-sqlite3/README.md @@ -1,8 +1,9 @@ go-sqlite3 ========== -[![Build Status](https://travis-ci.org/mattn/go-sqlite3.png?branch=master)](https://travis-ci.org/mattn/go-sqlite3) -[![Coverage Status](https://coveralls.io/repos/mattn/go-sqlite3/badge.png?branch=master)](https://coveralls.io/r/mattn/go-sqlite3?branch=master) +[![Build Status](https://travis-ci.org/mattn/go-sqlite3.svg?branch=master)](https://travis-ci.org/mattn/go-sqlite3) +[![Coverage Status](https://coveralls.io/repos/mattn/go-sqlite3/badge.svg?branch=master)](https://coveralls.io/r/mattn/go-sqlite3?branch=master) +[![GoDoc](https://godoc.org/github.com/mattn/go-sqlite3?status.svg)](http://godoc.org/github.com/mattn/go-sqlite3) Description ----------- @@ -16,6 +17,10 @@ This package can be installed with the go get command: go get github.com/mattn/go-sqlite3 +_go-sqlite3_ is *cgo* package. +If you want to build your app using go-sqlite3, you need gcc. +However, if you install _go-sqlite3_ with `go install github.com/mattn/go-sqlite3`, you don't need gcc to build your app anymore. + Documentation ------------- @@ -26,6 +31,14 @@ Examples can be found under the `./_example` directory FAQ --- +* Want to build go-sqlite3 with libsqlite3 on my linux. + + Use `go build --tags "libsqlite3 linux"` + +* Want to build go-sqlite3 with icu extension. + + Use `go build --tags "icu"` + * Can't build go-sqlite3 on windows 64bit. > Probably, you are using go 1.0, go1.0 has a problem when it comes to compiling/linking on windows 64bit. @@ -36,19 +49,25 @@ FAQ > You can pass some arguments into the connection string, for example, a URI. > See: https://github.com/mattn/go-sqlite3/issues/39 -* Do you want cross compiling? mingw on Linux or Mac? +* Do you want to cross compile? mingw on Linux or Mac? > See: https://github.com/mattn/go-sqlite3/issues/106 > See also: http://www.limitlessfx.com/cross-compile-golang-app-for-windows-from-linux.html +* Want to get time.Time with current locale + + Use `loc=auto` in SQLite3 filename schema like `file:foo.db?loc=auto`. + License ------- MIT: http://mattn.mit-license.org/2012 -sqlite.c, sqlite3.h, sqlite3ext.h +sqlite3-binding.c, sqlite3-binding.h, sqlite3ext.h -In this repository, those files are amalgamation code that copied from SQLite3. The license of those codes are depend on the license of SQLite3. +The -binding suffix was added to avoid build failures under gccgo. + +In this repository, those files are an amalgamation of code that was copied from SQLite3. The license of that code is the same as the license of SQLite3. Author ------ diff --git a/vendor/github.com/mattn/go-sqlite3/backup.go b/vendor/github.com/mattn/go-sqlite3/backup.go index 270446aa7..3807c606b 100644 --- a/vendor/github.com/mattn/go-sqlite3/backup.go +++ b/vendor/github.com/mattn/go-sqlite3/backup.go @@ -6,7 +6,7 @@ package sqlite3 /* -#include +#include #include */ import "C" diff --git a/vendor/github.com/mattn/go-sqlite3/callback.go b/vendor/github.com/mattn/go-sqlite3/callback.go new file mode 100644 index 000000000..e2bf3c6a2 --- /dev/null +++ b/vendor/github.com/mattn/go-sqlite3/callback.go @@ -0,0 +1,336 @@ +// Copyright (C) 2014 Yasuhiro Matsumoto . +// +// Use of this source code is governed by an MIT-style +// license that can be found in the LICENSE file. + +package sqlite3 + +// You can't export a Go function to C and have definitions in the C +// preamble in the same file, so we have to have callbackTrampoline in +// its own file. Because we need a separate file anyway, the support +// code for SQLite custom functions is in here. + +/* +#include +#include + +void _sqlite3_result_text(sqlite3_context* ctx, const char* s); +void _sqlite3_result_blob(sqlite3_context* ctx, const void* b, int l); +*/ +import "C" + +import ( + "errors" + "fmt" + "math" + "reflect" + "sync" + "unsafe" +) + +//export callbackTrampoline +func callbackTrampoline(ctx *C.sqlite3_context, argc int, argv **C.sqlite3_value) { + args := (*[(math.MaxInt32 - 1) / unsafe.Sizeof((*C.sqlite3_value)(nil))]*C.sqlite3_value)(unsafe.Pointer(argv))[:argc:argc] + fi := lookupHandle(uintptr(C.sqlite3_user_data(ctx))).(*functionInfo) + fi.Call(ctx, args) +} + +//export stepTrampoline +func stepTrampoline(ctx *C.sqlite3_context, argc int, argv **C.sqlite3_value) { + args := (*[(math.MaxInt32 - 1) / unsafe.Sizeof((*C.sqlite3_value)(nil))]*C.sqlite3_value)(unsafe.Pointer(argv))[:argc:argc] + ai := lookupHandle(uintptr(C.sqlite3_user_data(ctx))).(*aggInfo) + ai.Step(ctx, args) +} + +//export doneTrampoline +func doneTrampoline(ctx *C.sqlite3_context) { + handle := uintptr(C.sqlite3_user_data(ctx)) + ai := lookupHandle(handle).(*aggInfo) + ai.Done(ctx) +} + +// Use handles to avoid passing Go pointers to C. + +type handleVal struct { + db *SQLiteConn + val interface{} +} + +var handleLock sync.Mutex +var handleVals = make(map[uintptr]handleVal) +var handleIndex uintptr = 100 + +func newHandle(db *SQLiteConn, v interface{}) uintptr { + handleLock.Lock() + defer handleLock.Unlock() + i := handleIndex + handleIndex++ + handleVals[i] = handleVal{db, v} + return i +} + +func lookupHandle(handle uintptr) interface{} { + handleLock.Lock() + defer handleLock.Unlock() + r, ok := handleVals[handle] + if !ok { + if handle >= 100 && handle < handleIndex { + panic("deleted handle") + } else { + panic("invalid handle") + } + } + return r.val +} + +func deleteHandles(db *SQLiteConn) { + handleLock.Lock() + defer handleLock.Unlock() + for handle, val := range handleVals { + if val.db == db { + delete(handleVals, handle) + } + } +} + +// This is only here so that tests can refer to it. +type callbackArgRaw C.sqlite3_value + +type callbackArgConverter func(*C.sqlite3_value) (reflect.Value, error) + +type callbackArgCast struct { + f callbackArgConverter + typ reflect.Type +} + +func (c callbackArgCast) Run(v *C.sqlite3_value) (reflect.Value, error) { + val, err := c.f(v) + if err != nil { + return reflect.Value{}, err + } + if !val.Type().ConvertibleTo(c.typ) { + return reflect.Value{}, fmt.Errorf("cannot convert %s to %s", val.Type(), c.typ) + } + return val.Convert(c.typ), nil +} + +func callbackArgInt64(v *C.sqlite3_value) (reflect.Value, error) { + if C.sqlite3_value_type(v) != C.SQLITE_INTEGER { + return reflect.Value{}, fmt.Errorf("argument must be an INTEGER") + } + return reflect.ValueOf(int64(C.sqlite3_value_int64(v))), nil +} + +func callbackArgBool(v *C.sqlite3_value) (reflect.Value, error) { + if C.sqlite3_value_type(v) != C.SQLITE_INTEGER { + return reflect.Value{}, fmt.Errorf("argument must be an INTEGER") + } + i := int64(C.sqlite3_value_int64(v)) + val := false + if i != 0 { + val = true + } + return reflect.ValueOf(val), nil +} + +func callbackArgFloat64(v *C.sqlite3_value) (reflect.Value, error) { + if C.sqlite3_value_type(v) != C.SQLITE_FLOAT { + return reflect.Value{}, fmt.Errorf("argument must be a FLOAT") + } + return reflect.ValueOf(float64(C.sqlite3_value_double(v))), nil +} + +func callbackArgBytes(v *C.sqlite3_value) (reflect.Value, error) { + switch C.sqlite3_value_type(v) { + case C.SQLITE_BLOB: + l := C.sqlite3_value_bytes(v) + p := C.sqlite3_value_blob(v) + return reflect.ValueOf(C.GoBytes(p, l)), nil + case C.SQLITE_TEXT: + l := C.sqlite3_value_bytes(v) + c := unsafe.Pointer(C.sqlite3_value_text(v)) + return reflect.ValueOf(C.GoBytes(c, l)), nil + default: + return reflect.Value{}, fmt.Errorf("argument must be BLOB or TEXT") + } +} + +func callbackArgString(v *C.sqlite3_value) (reflect.Value, error) { + switch C.sqlite3_value_type(v) { + case C.SQLITE_BLOB: + l := C.sqlite3_value_bytes(v) + p := (*C.char)(C.sqlite3_value_blob(v)) + return reflect.ValueOf(C.GoStringN(p, l)), nil + case C.SQLITE_TEXT: + c := (*C.char)(unsafe.Pointer(C.sqlite3_value_text(v))) + return reflect.ValueOf(C.GoString(c)), nil + default: + return reflect.Value{}, fmt.Errorf("argument must be BLOB or TEXT") + } +} + +func callbackArgGeneric(v *C.sqlite3_value) (reflect.Value, error) { + switch C.sqlite3_value_type(v) { + case C.SQLITE_INTEGER: + return callbackArgInt64(v) + case C.SQLITE_FLOAT: + return callbackArgFloat64(v) + case C.SQLITE_TEXT: + return callbackArgString(v) + case C.SQLITE_BLOB: + return callbackArgBytes(v) + case C.SQLITE_NULL: + // Interpret NULL as a nil byte slice. + var ret []byte + return reflect.ValueOf(ret), nil + default: + panic("unreachable") + } +} + +func callbackArg(typ reflect.Type) (callbackArgConverter, error) { + switch typ.Kind() { + case reflect.Interface: + if typ.NumMethod() != 0 { + return nil, errors.New("the only supported interface type is interface{}") + } + return callbackArgGeneric, nil + case reflect.Slice: + if typ.Elem().Kind() != reflect.Uint8 { + return nil, errors.New("the only supported slice type is []byte") + } + return callbackArgBytes, nil + case reflect.String: + return callbackArgString, nil + case reflect.Bool: + return callbackArgBool, nil + case reflect.Int64: + return callbackArgInt64, nil + case reflect.Int8, reflect.Int16, reflect.Int32, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Int, reflect.Uint: + c := callbackArgCast{callbackArgInt64, typ} + return c.Run, nil + case reflect.Float64: + return callbackArgFloat64, nil + case reflect.Float32: + c := callbackArgCast{callbackArgFloat64, typ} + return c.Run, nil + default: + return nil, fmt.Errorf("don't know how to convert to %s", typ) + } +} + +func callbackConvertArgs(argv []*C.sqlite3_value, converters []callbackArgConverter, variadic callbackArgConverter) ([]reflect.Value, error) { + var args []reflect.Value + + if len(argv) < len(converters) { + return nil, fmt.Errorf("function requires at least %d arguments", len(converters)) + } + + for i, arg := range argv[:len(converters)] { + v, err := converters[i](arg) + if err != nil { + return nil, err + } + args = append(args, v) + } + + if variadic != nil { + for _, arg := range argv[len(converters):] { + v, err := variadic(arg) + if err != nil { + return nil, err + } + args = append(args, v) + } + } + return args, nil +} + +type callbackRetConverter func(*C.sqlite3_context, reflect.Value) error + +func callbackRetInteger(ctx *C.sqlite3_context, v reflect.Value) error { + switch v.Type().Kind() { + case reflect.Int64: + case reflect.Int8, reflect.Int16, reflect.Int32, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Int, reflect.Uint: + v = v.Convert(reflect.TypeOf(int64(0))) + case reflect.Bool: + b := v.Interface().(bool) + if b { + v = reflect.ValueOf(int64(1)) + } else { + v = reflect.ValueOf(int64(0)) + } + default: + return fmt.Errorf("cannot convert %s to INTEGER", v.Type()) + } + + C.sqlite3_result_int64(ctx, C.sqlite3_int64(v.Interface().(int64))) + return nil +} + +func callbackRetFloat(ctx *C.sqlite3_context, v reflect.Value) error { + switch v.Type().Kind() { + case reflect.Float64: + case reflect.Float32: + v = v.Convert(reflect.TypeOf(float64(0))) + default: + return fmt.Errorf("cannot convert %s to FLOAT", v.Type()) + } + + C.sqlite3_result_double(ctx, C.double(v.Interface().(float64))) + return nil +} + +func callbackRetBlob(ctx *C.sqlite3_context, v reflect.Value) error { + if v.Type().Kind() != reflect.Slice || v.Type().Elem().Kind() != reflect.Uint8 { + return fmt.Errorf("cannot convert %s to BLOB", v.Type()) + } + i := v.Interface() + if i == nil || len(i.([]byte)) == 0 { + C.sqlite3_result_null(ctx) + } else { + bs := i.([]byte) + C._sqlite3_result_blob(ctx, unsafe.Pointer(&bs[0]), C.int(len(bs))) + } + return nil +} + +func callbackRetText(ctx *C.sqlite3_context, v reflect.Value) error { + if v.Type().Kind() != reflect.String { + return fmt.Errorf("cannot convert %s to TEXT", v.Type()) + } + C._sqlite3_result_text(ctx, C.CString(v.Interface().(string))) + return nil +} + +func callbackRet(typ reflect.Type) (callbackRetConverter, error) { + switch typ.Kind() { + case reflect.Slice: + if typ.Elem().Kind() != reflect.Uint8 { + return nil, errors.New("the only supported slice type is []byte") + } + return callbackRetBlob, nil + case reflect.String: + return callbackRetText, nil + case reflect.Bool, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Int, reflect.Uint: + return callbackRetInteger, nil + case reflect.Float32, reflect.Float64: + return callbackRetFloat, nil + default: + return nil, fmt.Errorf("don't know how to convert to %s", typ) + } +} + +func callbackError(ctx *C.sqlite3_context, err error) { + cstr := C.CString(err.Error()) + defer C.free(unsafe.Pointer(cstr)) + C.sqlite3_result_error(ctx, cstr, -1) +} + +// Test support code. Tests are not allowed to import "C", so we can't +// declare any functions that use C.sqlite3_value. +func callbackSyntheticForTests(v reflect.Value, err error) callbackArgConverter { + return func(*C.sqlite3_value) (reflect.Value, error) { + return v, err + } +} diff --git a/vendor/github.com/mattn/go-sqlite3/sqlite3.c b/vendor/github.com/mattn/go-sqlite3/code/sqlite3-binding.c similarity index 73% rename from vendor/github.com/mattn/go-sqlite3/sqlite3.c rename to vendor/github.com/mattn/go-sqlite3/code/sqlite3-binding.c index 9228d249c..c0ab2337e 100644 --- a/vendor/github.com/mattn/go-sqlite3/sqlite3.c +++ b/vendor/github.com/mattn/go-sqlite3/code/sqlite3-binding.c @@ -1,6 +1,6 @@ /****************************************************************************** ** This file is an amalgamation of many separate C source files from SQLite -** version 3.8.5. By combining all the individual C code files into this +** version 3.10.2. By combining all the individual C code files into this ** single large file, the entire code can be compiled as a single translation ** unit. This allows many compilers to do optimizations that would not be ** possible if the files were compiled separately. Performance improvements @@ -22,9 +22,6 @@ #ifndef SQLITE_PRIVATE # define SQLITE_PRIVATE static #endif -#ifndef SQLITE_API -# define SQLITE_API -#endif /************** Begin file sqliteInt.h ***************************************/ /* ** 2001 September 15 @@ -43,6 +40,92 @@ #ifndef _SQLITEINT_H_ #define _SQLITEINT_H_ +/* +** Include the header file used to customize the compiler options for MSVC. +** This should be done first so that it can successfully prevent spurious +** compiler warnings due to subsequent content in this file and other files +** that are included by this file. +*/ +/************** Include msvc.h in the middle of sqliteInt.h ******************/ +/************** Begin file msvc.h ********************************************/ +/* +** 2015 January 12 +** +** The author disclaims copyright to this source code. In place of +** a legal notice, here is a blessing: +** +** May you do good and not evil. +** May you find forgiveness for yourself and forgive others. +** May you share freely, never taking more than you give. +** +****************************************************************************** +** +** This file contains code that is specific to MSVC. +*/ +#ifndef _MSVC_H_ +#define _MSVC_H_ + +#if defined(_MSC_VER) +#pragma warning(disable : 4054) +#pragma warning(disable : 4055) +#pragma warning(disable : 4100) +#pragma warning(disable : 4127) +#pragma warning(disable : 4130) +#pragma warning(disable : 4152) +#pragma warning(disable : 4189) +#pragma warning(disable : 4206) +#pragma warning(disable : 4210) +#pragma warning(disable : 4232) +#pragma warning(disable : 4244) +#pragma warning(disable : 4305) +#pragma warning(disable : 4306) +#pragma warning(disable : 4702) +#pragma warning(disable : 4706) +#endif /* defined(_MSC_VER) */ + +#endif /* _MSVC_H_ */ + +/************** End of msvc.h ************************************************/ +/************** Continuing where we left off in sqliteInt.h ******************/ + +/* +** Special setup for VxWorks +*/ +/************** Include vxworks.h in the middle of sqliteInt.h ***************/ +/************** Begin file vxworks.h *****************************************/ +/* +** 2015-03-02 +** +** The author disclaims copyright to this source code. In place of +** a legal notice, here is a blessing: +** +** May you do good and not evil. +** May you find forgiveness for yourself and forgive others. +** May you share freely, never taking more than you give. +** +****************************************************************************** +** +** This file contains code that is specific to Wind River's VxWorks +*/ +#if defined(__RTP__) || defined(_WRS_KERNEL) +/* This is VxWorks. Set up things specially for that OS +*/ +#include +#include /* amalgamator: dontcache */ +#define OS_VXWORKS 1 +#define SQLITE_OS_OTHER 0 +#define SQLITE_HOMEGROWN_RECURSIVE_MUTEX 1 +#define SQLITE_OMIT_LOAD_EXTENSION 1 +#define SQLITE_ENABLE_LOCKING_STYLE 0 +#define HAVE_UTIME 1 +#else +/* This is not VxWorks. */ +#define OS_VXWORKS 0 +#endif /* defined(_WRS_KERNEL) */ + +/************** End of vxworks.h *********************************************/ +/************** Continuing where we left off in sqliteInt.h ******************/ + /* ** These #defines should enable >2GB file support on POSIX if the ** underlying operating system supports it. If the OS lacks @@ -75,6 +158,22 @@ # define _LARGEFILE_SOURCE 1 #endif +/* What version of GCC is being used. 0 means GCC is not being used */ +#ifdef __GNUC__ +# define GCC_VERSION (__GNUC__*1000000+__GNUC_MINOR__*1000+__GNUC_PATCHLEVEL__) +#else +# define GCC_VERSION 0 +#endif + +/* Needed for various definitions... */ +#if defined(__GNUC__) && !defined(_GNU_SOURCE) +# define _GNU_SOURCE +#endif + +#if defined(__OpenBSD__) && !defined(_BSD_SOURCE) +# define _BSD_SOURCE +#endif + /* ** For MinGW, check to see if we can include the header file containing its ** version information, among other things. Normally, this internal MinGW @@ -138,7 +237,7 @@ ** ** The official C-language API documentation for SQLite is derived ** from comments in this file. This file is the authoritative source -** on how SQLite interfaces are suppose to operate. +** on how SQLite interfaces are supposed to operate. ** ** The name of this file under configuration management is "sqlite.h.in". ** The makefile makes some minor changes to this file (such as inserting @@ -158,21 +257,25 @@ extern "C" { /* -** Add the ability to override 'extern' +** Provide the ability to override linkage features of the interface. */ #ifndef SQLITE_EXTERN # define SQLITE_EXTERN extern #endif - #ifndef SQLITE_API # define SQLITE_API #endif - +#ifndef SQLITE_CDECL +# define SQLITE_CDECL +#endif +#ifndef SQLITE_STDCALL +# define SQLITE_STDCALL +#endif /* ** These no-op macros are used in front of interfaces to mark those ** interfaces as either deprecated or experimental. New applications -** should not use deprecated interfaces - they are support for backwards +** should not use deprecated interfaces - they are supported for backwards ** compatibility only. Application writers should be aware that ** experimental interfaces are subject to change in point releases. ** @@ -222,9 +325,9 @@ extern "C" { ** [sqlite3_libversion_number()], [sqlite3_sourceid()], ** [sqlite_version()] and [sqlite_source_id()]. */ -#define SQLITE_VERSION "3.8.5" -#define SQLITE_VERSION_NUMBER 3008005 -#define SQLITE_SOURCE_ID "2014-06-04 14:06:34 b1ed4f2a34ba66c29b130f8d13e9092758019212" +#define SQLITE_VERSION "3.10.2" +#define SQLITE_VERSION_NUMBER 3010002 +#define SQLITE_SOURCE_ID "2016-01-20 15:27:19 17efb4209f97fb4971656086b138599a91a75ff9" /* ** CAPI3REF: Run-Time Library Version Numbers @@ -235,7 +338,7 @@ extern "C" { ** but are associated with the library instead of the header file. ^(Cautious ** programmers might include assert() statements in their application to ** verify that values returned by these interfaces match the macros in -** the header, and thus insure that the application is +** the header, and thus ensure that the application is ** compiled with matching library and header files. ** **
@@ -257,9 +360,9 @@ extern "C" {
 ** See also: [sqlite_version()] and [sqlite_source_id()].
 */
 SQLITE_API const char sqlite3_version[] = SQLITE_VERSION;
-SQLITE_API const char *sqlite3_libversion(void);
-SQLITE_API const char *sqlite3_sourceid(void);
-SQLITE_API int sqlite3_libversion_number(void);
+SQLITE_API const char *SQLITE_STDCALL sqlite3_libversion(void);
+SQLITE_API const char *SQLITE_STDCALL sqlite3_sourceid(void);
+SQLITE_API int SQLITE_STDCALL sqlite3_libversion_number(void);
 
 /*
 ** CAPI3REF: Run-Time Library Compilation Options Diagnostics
@@ -284,8 +387,8 @@ SQLITE_API int sqlite3_libversion_number(void);
 ** [sqlite_compileoption_get()] and the [compile_options pragma].
 */
 #ifndef SQLITE_OMIT_COMPILEOPTION_DIAGS
-SQLITE_API int sqlite3_compileoption_used(const char *zOptName);
-SQLITE_API const char *sqlite3_compileoption_get(int N);
+SQLITE_API int SQLITE_STDCALL sqlite3_compileoption_used(const char *zOptName);
+SQLITE_API const char *SQLITE_STDCALL sqlite3_compileoption_get(int N);
 #endif
 
 /*
@@ -316,7 +419,7 @@ SQLITE_API const char *sqlite3_compileoption_get(int N);
 ** SQLITE_THREADSAFE=1 or =2 then mutexes are enabled by default but
 ** can be fully or partially disabled using a call to [sqlite3_config()]
 ** with the verbs [SQLITE_CONFIG_SINGLETHREAD], [SQLITE_CONFIG_MULTITHREAD],
-** or [SQLITE_CONFIG_MUTEX].  ^(The return value of the
+** or [SQLITE_CONFIG_SERIALIZED].  ^(The return value of the
 ** sqlite3_threadsafe() function shows only the compile-time setting of
 ** thread safety, not any run-time changes to that setting made by
 ** sqlite3_config(). In other words, the return value from sqlite3_threadsafe()
@@ -324,7 +427,7 @@ SQLITE_API const char *sqlite3_compileoption_get(int N);
 **
 ** See the [threading mode] documentation for additional information.
 */
-SQLITE_API int sqlite3_threadsafe(void);
+SQLITE_API int SQLITE_STDCALL sqlite3_threadsafe(void);
 
 /*
 ** CAPI3REF: Database Connection Handle
@@ -381,10 +484,11 @@ typedef sqlite_uint64 sqlite3_uint64;
 
 /*
 ** CAPI3REF: Closing A Database Connection
+** DESTRUCTOR: sqlite3
 **
 ** ^The sqlite3_close() and sqlite3_close_v2() routines are destructors
 ** for the [sqlite3] object.
-** ^Calls to sqlite3_close() and sqlite3_close_v2() return SQLITE_OK if
+** ^Calls to sqlite3_close() and sqlite3_close_v2() return [SQLITE_OK] if
 ** the [sqlite3] object is successfully destroyed and all associated
 ** resources are deallocated.
 **
@@ -392,7 +496,7 @@ typedef sqlite_uint64 sqlite3_uint64;
 ** statements or unfinished sqlite3_backup objects then sqlite3_close()
 ** will leave the database connection open and return [SQLITE_BUSY].
 ** ^If sqlite3_close_v2() is called with unfinalized prepared statements
-** and unfinished sqlite3_backups, then the database connection becomes
+** and/or unfinished sqlite3_backups, then the database connection becomes
 ** an unusable "zombie" which will automatically be deallocated when the
 ** last prepared statement is finalized or the last sqlite3_backup is
 ** finished.  The sqlite3_close_v2() interface is intended for use with
@@ -405,7 +509,7 @@ typedef sqlite_uint64 sqlite3_uint64;
 ** with the [sqlite3] object prior to attempting to close the object.  ^If
 ** sqlite3_close_v2() is called on a [database connection] that still has
 ** outstanding [prepared statements], [BLOB handles], and/or
-** [sqlite3_backup] objects then it returns SQLITE_OK but the deallocation
+** [sqlite3_backup] objects then it returns [SQLITE_OK] and the deallocation
 ** of resources is deferred until all [prepared statements], [BLOB handles],
 ** and [sqlite3_backup] objects are also destroyed.
 **
@@ -420,8 +524,8 @@ typedef sqlite_uint64 sqlite3_uint64;
 ** ^Calling sqlite3_close() or sqlite3_close_v2() with a NULL pointer
 ** argument is a harmless no-op.
 */
-SQLITE_API int sqlite3_close(sqlite3*);
-SQLITE_API int sqlite3_close_v2(sqlite3*);
+SQLITE_API int SQLITE_STDCALL sqlite3_close(sqlite3*);
+SQLITE_API int SQLITE_STDCALL sqlite3_close_v2(sqlite3*);
 
 /*
 ** The type for a callback function.
@@ -432,6 +536,7 @@ typedef int (*sqlite3_callback)(void*,int,char**, char**);
 
 /*
 ** CAPI3REF: One-Step Query Execution Interface
+** METHOD: sqlite3
 **
 ** The sqlite3_exec() interface is a convenience wrapper around
 ** [sqlite3_prepare_v2()], [sqlite3_step()], and [sqlite3_finalize()],
@@ -483,7 +588,7 @@ typedef int (*sqlite3_callback)(void*,int,char**, char**);
 ** Restrictions:
 **
 ** 
    -**
  • The application must insure that the 1st parameter to sqlite3_exec() +**
  • The application must ensure that the 1st parameter to sqlite3_exec() ** is a valid and open [database connection]. **
  • The application must not close the [database connection] specified by ** the 1st parameter to sqlite3_exec() while sqlite3_exec() is running. @@ -491,7 +596,7 @@ typedef int (*sqlite3_callback)(void*,int,char**, char**); ** the 2nd parameter of sqlite3_exec() while sqlite3_exec() is running. **
*/ -SQLITE_API int sqlite3_exec( +SQLITE_API int SQLITE_STDCALL sqlite3_exec( sqlite3*, /* An open database */ const char *sql, /* SQL to be evaluated */ int (*callback)(void*,int,char**,char**), /* Callback function */ @@ -501,16 +606,14 @@ SQLITE_API int sqlite3_exec( /* ** CAPI3REF: Result Codes -** KEYWORDS: SQLITE_OK {error code} {error codes} -** KEYWORDS: {result code} {result codes} +** KEYWORDS: {result code definitions} ** ** Many SQLite functions return an integer result code from the set shown ** here in order to indicate success or failure. ** ** New error codes may be added in future versions of SQLite. ** -** See also: [SQLITE_IOERR_READ | extended result codes], -** [sqlite3_vtab_on_conflict()] [SQLITE_ROLLBACK | result codes]. +** See also: [extended result code definitions] */ #define SQLITE_OK 0 /* Successful result */ /* beginning-of-error-codes */ @@ -548,26 +651,19 @@ SQLITE_API int sqlite3_exec( /* ** CAPI3REF: Extended Result Codes -** KEYWORDS: {extended error code} {extended error codes} -** KEYWORDS: {extended result code} {extended result codes} +** KEYWORDS: {extended result code definitions} ** -** In its default configuration, SQLite API routines return one of 26 integer -** [SQLITE_OK | result codes]. However, experience has shown that many of +** In its default configuration, SQLite API routines return one of 30 integer +** [result codes]. However, experience has shown that many of ** these result codes are too coarse-grained. They do not provide as ** much information about problems as programmers might like. In an effort to ** address this, newer versions of SQLite (version 3.3.8 and later) include ** support for additional result codes that provide more detailed information -** about errors. The extended result codes are enabled or disabled +** about errors. These [extended result codes] are enabled or disabled ** on a per database connection basis using the -** [sqlite3_extended_result_codes()] API. -** -** Some of the available extended result codes are listed here. -** One may expect the number of extended result codes will increase -** over time. Software that uses extended result codes should expect -** to see new result codes in future releases of SQLite. -** -** The SQLITE_OK result code will never be extended. It will always -** be exactly zero. +** [sqlite3_extended_result_codes()] API. Or, the extended code for +** the most recent error can be obtained using +** [sqlite3_extended_errcode()]. */ #define SQLITE_IOERR_READ (SQLITE_IOERR | (1<<8)) #define SQLITE_IOERR_SHORT_READ (SQLITE_IOERR | (2<<8)) @@ -595,6 +691,8 @@ SQLITE_API int sqlite3_exec( #define SQLITE_IOERR_MMAP (SQLITE_IOERR | (24<<8)) #define SQLITE_IOERR_GETTEMPPATH (SQLITE_IOERR | (25<<8)) #define SQLITE_IOERR_CONVPATH (SQLITE_IOERR | (26<<8)) +#define SQLITE_IOERR_VNODE (SQLITE_IOERR | (27<<8)) +#define SQLITE_IOERR_AUTH (SQLITE_IOERR | (28<<8)) #define SQLITE_LOCKED_SHAREDCACHE (SQLITE_LOCKED | (1<<8)) #define SQLITE_BUSY_RECOVERY (SQLITE_BUSY | (1<<8)) #define SQLITE_BUSY_SNAPSHOT (SQLITE_BUSY | (2<<8)) @@ -621,6 +719,7 @@ SQLITE_API int sqlite3_exec( #define SQLITE_NOTICE_RECOVER_WAL (SQLITE_NOTICE | (1<<8)) #define SQLITE_NOTICE_RECOVER_ROLLBACK (SQLITE_NOTICE | (2<<8)) #define SQLITE_WARNING_AUTOINDEX (SQLITE_WARNING | (1<<8)) +#define SQLITE_AUTH_USER (SQLITE_AUTH | (1<<8)) /* ** CAPI3REF: Flags For File Open Operations @@ -800,7 +899,7 @@ struct sqlite3_file { ** locking strategy (for example to use dot-file locks), to inquire ** about the status of a lock, or to break stale locks. The SQLite ** core reserves all opcodes less than 100 for its own use. -** A [SQLITE_FCNTL_LOCKSTATE | list of opcodes] less than 100 is available. +** A [file control opcodes | list of opcodes] less than 100 is available. ** Applications that define a custom xFileControl method should use opcodes ** greater than 100 to avoid conflicts. VFS implementations should ** return [SQLITE_NOTFOUND] for file control opcodes that they do not @@ -873,19 +972,22 @@ struct sqlite3_io_methods { /* ** CAPI3REF: Standard File Control Opcodes +** KEYWORDS: {file control opcodes} {file control opcode} ** ** These integer constants are opcodes for the xFileControl method ** of the [sqlite3_io_methods] object and for the [sqlite3_file_control()] ** interface. ** +**
    +**
  • [[SQLITE_FCNTL_LOCKSTATE]] ** The [SQLITE_FCNTL_LOCKSTATE] opcode is used for debugging. This ** opcode causes the xFileControl method to write the current state of ** the lock (one of [SQLITE_LOCK_NONE], [SQLITE_LOCK_SHARED], ** [SQLITE_LOCK_RESERVED], [SQLITE_LOCK_PENDING], or [SQLITE_LOCK_EXCLUSIVE]) ** into an integer that the pArg argument points to. This capability -** is used during testing and only needs to be supported when SQLITE_TEST -** is defined. -**
      +** is used during testing and is only available when the SQLITE_TEST +** compile-time option is used. +** **
    • [[SQLITE_FCNTL_SIZE_HINT]] ** The [SQLITE_FCNTL_SIZE_HINT] opcode is used by SQLite to give the VFS ** layer a hint of how large the database file will grow to be during the @@ -906,8 +1008,13 @@ struct sqlite3_io_methods { **
    • [[SQLITE_FCNTL_FILE_POINTER]] ** The [SQLITE_FCNTL_FILE_POINTER] opcode is used to obtain a pointer ** to the [sqlite3_file] object associated with a particular database -** connection. See the [sqlite3_file_control()] documentation for -** additional information. +** connection. See also [SQLITE_FCNTL_JOURNAL_POINTER]. +** +**
    • [[SQLITE_FCNTL_JOURNAL_POINTER]] +** The [SQLITE_FCNTL_JOURNAL_POINTER] opcode is used to obtain a pointer +** to the [sqlite3_file] object associated with the journal file (either +** the [rollback journal] or the [write-ahead log]) for a particular database +** connection. See also [SQLITE_FCNTL_FILE_POINTER]. ** **
    • [[SQLITE_FCNTL_SYNC_OMITTED]] ** No longer in use. @@ -994,6 +1101,15 @@ struct sqlite3_io_methods { ** pointer in case this file-control is not implemented. This file-control ** is intended for diagnostic use only. ** +**
    • [[SQLITE_FCNTL_VFS_POINTER]] +** ^The [SQLITE_FCNTL_VFS_POINTER] opcode finds a pointer to the top-level +** [VFSes] currently in use. ^(The argument X in +** sqlite3_file_control(db,SQLITE_FCNTL_VFS_POINTER,X) must be +** of type "[sqlite3_vfs] **". This opcodes will set *X +** to a pointer to the top-level VFS.)^ +** ^When there are multiple VFS shims in the stack, this opcode finds the +** upper-most shim only. +** **
    • [[SQLITE_FCNTL_PRAGMA]] ** ^Whenever a [PRAGMA] statement is parsed, an [SQLITE_FCNTL_PRAGMA] ** file control is sent to the open [sqlite3_file] object corresponding @@ -1010,7 +1126,9 @@ struct sqlite3_io_methods { ** [PRAGMA] processing continues. ^If the [SQLITE_FCNTL_PRAGMA] ** file control returns [SQLITE_OK], then the parser assumes that the ** VFS has handled the PRAGMA itself and the parser generates a no-op -** prepared statement. ^If the [SQLITE_FCNTL_PRAGMA] file control returns +** prepared statement if result string is NULL, or that returns a copy +** of the result string if the string is non-NULL. +** ^If the [SQLITE_FCNTL_PRAGMA] file control returns ** any result code other than [SQLITE_OK] or [SQLITE_NOTFOUND], that means ** that the VFS encountered an error while handling the [PRAGMA] and the ** compilation of the PRAGMA fails with an error. ^The [SQLITE_FCNTL_PRAGMA] @@ -1068,12 +1186,27 @@ struct sqlite3_io_methods { ** pointed to by the pArg argument. This capability is used during testing ** and only needs to be supported when SQLITE_TEST is defined. ** +**
    • [[SQLITE_FCNTL_WAL_BLOCK]] +** The [SQLITE_FCNTL_WAL_BLOCK] is a signal to the VFS layer that it might +** be advantageous to block on the next WAL lock if the lock is not immediately +** available. The WAL subsystem issues this signal during rare +** circumstances in order to fix a problem with priority inversion. +** Applications should not use this file-control. +** +**
    • [[SQLITE_FCNTL_ZIPVFS]] +** The [SQLITE_FCNTL_ZIPVFS] opcode is implemented by zipvfs only. All other +** VFS should return SQLITE_NOTFOUND for this opcode. +** +**
    • [[SQLITE_FCNTL_RBU]] +** The [SQLITE_FCNTL_RBU] opcode is implemented by the special VFS used by +** the RBU extension only. All other VFS should return SQLITE_NOTFOUND for +** this opcode. **
    */ #define SQLITE_FCNTL_LOCKSTATE 1 -#define SQLITE_GET_LOCKPROXYFILE 2 -#define SQLITE_SET_LOCKPROXYFILE 3 -#define SQLITE_LAST_ERRNO 4 +#define SQLITE_FCNTL_GET_LOCKPROXYFILE 2 +#define SQLITE_FCNTL_SET_LOCKPROXYFILE 3 +#define SQLITE_FCNTL_LAST_ERRNO 4 #define SQLITE_FCNTL_SIZE_HINT 5 #define SQLITE_FCNTL_CHUNK_SIZE 6 #define SQLITE_FCNTL_FILE_POINTER 7 @@ -1092,6 +1225,17 @@ struct sqlite3_io_methods { #define SQLITE_FCNTL_SYNC 21 #define SQLITE_FCNTL_COMMIT_PHASETWO 22 #define SQLITE_FCNTL_WIN32_SET_HANDLE 23 +#define SQLITE_FCNTL_WAL_BLOCK 24 +#define SQLITE_FCNTL_ZIPVFS 25 +#define SQLITE_FCNTL_RBU 26 +#define SQLITE_FCNTL_VFS_POINTER 27 +#define SQLITE_FCNTL_JOURNAL_POINTER 28 + +/* deprecated names */ +#define SQLITE_GET_LOCKPROXYFILE SQLITE_FCNTL_GET_LOCKPROXYFILE +#define SQLITE_SET_LOCKPROXYFILE SQLITE_FCNTL_SET_LOCKPROXYFILE +#define SQLITE_LAST_ERRNO SQLITE_FCNTL_LAST_ERRNO + /* ** CAPI3REF: Mutex Handle @@ -1343,7 +1487,7 @@ struct sqlite3_vfs { **
** ** When unlocking, the same SHARED or EXCLUSIVE flag must be supplied as -** was given no the corresponding lock. +** was given on the corresponding lock. ** ** The xShmLock method can transition between unlocked and SHARED or ** between unlocked and EXCLUSIVE. It cannot transition between SHARED @@ -1440,10 +1584,10 @@ struct sqlite3_vfs { ** must return [SQLITE_OK] on success and some other [error code] upon ** failure. */ -SQLITE_API int sqlite3_initialize(void); -SQLITE_API int sqlite3_shutdown(void); -SQLITE_API int sqlite3_os_init(void); -SQLITE_API int sqlite3_os_end(void); +SQLITE_API int SQLITE_STDCALL sqlite3_initialize(void); +SQLITE_API int SQLITE_STDCALL sqlite3_shutdown(void); +SQLITE_API int SQLITE_STDCALL sqlite3_os_init(void); +SQLITE_API int SQLITE_STDCALL sqlite3_os_end(void); /* ** CAPI3REF: Configuring The SQLite Library @@ -1454,9 +1598,11 @@ SQLITE_API int sqlite3_os_end(void); ** applications and so this routine is usually not necessary. It is ** provided to support rare applications with unusual needs. ** -** The sqlite3_config() interface is not threadsafe. The application -** must insure that no other SQLite interfaces are invoked by other -** threads while sqlite3_config() is running. Furthermore, sqlite3_config() +** The sqlite3_config() interface is not threadsafe. The application +** must ensure that no other SQLite interfaces are invoked by other +** threads while sqlite3_config() is running. +** +** The sqlite3_config() interface ** may only be invoked prior to library initialization using ** [sqlite3_initialize()] or after shutdown by [sqlite3_shutdown()]. ** ^If sqlite3_config() is called after [sqlite3_initialize()] and before @@ -1474,10 +1620,11 @@ SQLITE_API int sqlite3_os_end(void); ** ^If the option is unknown or SQLite is unable to set the option ** then this routine returns a non-zero [error code]. */ -SQLITE_API int sqlite3_config(int, ...); +SQLITE_API int SQLITE_CDECL sqlite3_config(int, ...); /* ** CAPI3REF: Configure database connections +** METHOD: sqlite3 ** ** The sqlite3_db_config() interface is used to make configuration ** changes to a [database connection]. The interface is similar to @@ -1492,7 +1639,7 @@ SQLITE_API int sqlite3_config(int, ...); ** ^Calls to sqlite3_db_config() return SQLITE_OK if and only if ** the call is considered successful. */ -SQLITE_API int sqlite3_db_config(sqlite3*, int op, ...); +SQLITE_API int SQLITE_CDECL sqlite3_db_config(sqlite3*, int op, ...); /* ** CAPI3REF: Memory Allocation Routines @@ -1626,31 +1773,33 @@ struct sqlite3_mem_methods { ** SQLITE_CONFIG_SERIALIZED configuration option. ** ** [[SQLITE_CONFIG_MALLOC]]
SQLITE_CONFIG_MALLOC
-**
^(This option takes a single argument which is a pointer to an -** instance of the [sqlite3_mem_methods] structure. The argument specifies +**
^(The SQLITE_CONFIG_MALLOC option takes a single argument which is +** a pointer to an instance of the [sqlite3_mem_methods] structure. +** The argument specifies ** alternative low-level memory allocation routines to be used in place of ** the memory allocation routines built into SQLite.)^ ^SQLite makes ** its own private copy of the content of the [sqlite3_mem_methods] structure ** before the [sqlite3_config()] call returns.
** ** [[SQLITE_CONFIG_GETMALLOC]]
SQLITE_CONFIG_GETMALLOC
-**
^(This option takes a single argument which is a pointer to an -** instance of the [sqlite3_mem_methods] structure. The [sqlite3_mem_methods] +**
^(The SQLITE_CONFIG_GETMALLOC option takes a single argument which +** is a pointer to an instance of the [sqlite3_mem_methods] structure. +** The [sqlite3_mem_methods] ** structure is filled with the currently defined memory allocation routines.)^ ** This option can be used to overload the default memory allocation ** routines with a wrapper that simulations memory allocation failure or ** tracks memory usage, for example.
** ** [[SQLITE_CONFIG_MEMSTATUS]]
SQLITE_CONFIG_MEMSTATUS
-**
^This option takes single argument of type int, interpreted as a -** boolean, which enables or disables the collection of memory allocation -** statistics. ^(When memory allocation statistics are disabled, the -** following SQLite interfaces become non-operational: +**
^The SQLITE_CONFIG_MEMSTATUS option takes single argument of type int, +** interpreted as a boolean, which enables or disables the collection of +** memory allocation statistics. ^(When memory allocation statistics are +** disabled, the following SQLite interfaces become non-operational: **
    **
  • [sqlite3_memory_used()] **
  • [sqlite3_memory_highwater()] **
  • [sqlite3_soft_heap_limit64()] -**
  • [sqlite3_status()] +**
  • [sqlite3_status64()] **
)^ ** ^Memory allocation statistics are enabled by default unless SQLite is ** compiled with [SQLITE_DEFAULT_MEMSTATUS]=0 in which case memory @@ -1658,53 +1807,72 @@ struct sqlite3_mem_methods { **
** ** [[SQLITE_CONFIG_SCRATCH]]
SQLITE_CONFIG_SCRATCH
-**
^This option specifies a static memory buffer that SQLite can use for -** scratch memory. There are three arguments: A pointer an 8-byte +**
^The SQLITE_CONFIG_SCRATCH option specifies a static memory buffer +** that SQLite can use for scratch memory. ^(There are three arguments +** to SQLITE_CONFIG_SCRATCH: A pointer an 8-byte ** aligned memory buffer from which the scratch allocations will be ** drawn, the size of each scratch allocation (sz), -** and the maximum number of scratch allocations (N). The sz -** argument must be a multiple of 16. +** and the maximum number of scratch allocations (N).)^ ** The first argument must be a pointer to an 8-byte aligned buffer ** of at least sz*N bytes of memory. -** ^SQLite will use no more than two scratch buffers per thread. So -** N should be set to twice the expected maximum number of threads. -** ^SQLite will never require a scratch buffer that is more than 6 -** times the database page size. ^If SQLite needs needs additional +** ^SQLite will not use more than one scratch buffers per thread. +** ^SQLite will never request a scratch buffer that is more than 6 +** times the database page size. +** ^If SQLite needs needs additional ** scratch memory beyond what is provided by this configuration option, then -** [sqlite3_malloc()] will be used to obtain the memory needed.
+** [sqlite3_malloc()] will be used to obtain the memory needed.

+** ^When the application provides any amount of scratch memory using +** SQLITE_CONFIG_SCRATCH, SQLite avoids unnecessary large +** [sqlite3_malloc|heap allocations]. +** This can help [Robson proof|prevent memory allocation failures] due to heap +** fragmentation in low-memory embedded systems. +** ** ** [[SQLITE_CONFIG_PAGECACHE]]

SQLITE_CONFIG_PAGECACHE
-**
^This option specifies a static memory buffer that SQLite can use for -** the database page cache with the default page cache implementation. -** This configuration should not be used if an application-define page -** cache implementation is loaded using the SQLITE_CONFIG_PCACHE2 option. -** There are three arguments to this option: A pointer to 8-byte aligned -** memory, the size of each page buffer (sz), and the number of pages (N). +**
^The SQLITE_CONFIG_PAGECACHE option specifies a memory pool +** that SQLite can use for the database page cache with the default page +** cache implementation. +** This configuration option is a no-op if an application-define page +** cache implementation is loaded using the [SQLITE_CONFIG_PCACHE2]. +** ^There are three arguments to SQLITE_CONFIG_PAGECACHE: A pointer to +** 8-byte aligned memory (pMem), the size of each page cache line (sz), +** and the number of cache lines (N). ** The sz argument should be the size of the largest database page -** (a power of two between 512 and 32768) plus a little extra for each -** page header. ^The page header size is 20 to 40 bytes depending on -** the host architecture. ^It is harmless, apart from the wasted memory, -** to make sz a little too large. The first -** argument should point to an allocation of at least sz*N bytes of memory. -** ^SQLite will use the memory provided by the first argument to satisfy its -** memory needs for the first N pages that it adds to cache. ^If additional -** page cache memory is needed beyond what is provided by this option, then -** SQLite goes to [sqlite3_malloc()] for the additional storage space. -** The pointer in the first argument must -** be aligned to an 8-byte boundary or subsequent behavior of SQLite -** will be undefined.
+** (a power of two between 512 and 65536) plus some extra bytes for each +** page header. ^The number of extra bytes needed by the page header +** can be determined using [SQLITE_CONFIG_PCACHE_HDRSZ]. +** ^It is harmless, apart from the wasted memory, +** for the sz parameter to be larger than necessary. The pMem +** argument must be either a NULL pointer or a pointer to an 8-byte +** aligned block of memory of at least sz*N bytes, otherwise +** subsequent behavior is undefined. +** ^When pMem is not NULL, SQLite will strive to use the memory provided +** to satisfy page cache needs, falling back to [sqlite3_malloc()] if +** a page cache line is larger than sz bytes or if all of the pMem buffer +** is exhausted. +** ^If pMem is NULL and N is non-zero, then each database connection +** does an initial bulk allocation for page cache memory +** from [sqlite3_malloc()] sufficient for N cache lines if N is positive or +** of -1024*N bytes if N is negative, . ^If additional +** page cache memory is needed beyond what is provided by the initial +** allocation, then SQLite goes to [sqlite3_malloc()] separately for each +** additional cache line. ** ** [[SQLITE_CONFIG_HEAP]]
SQLITE_CONFIG_HEAP
-**
^This option specifies a static memory buffer that SQLite will use -** for all of its dynamic memory allocation needs beyond those provided -** for by [SQLITE_CONFIG_SCRATCH] and [SQLITE_CONFIG_PAGECACHE]. -** There are three arguments: An 8-byte aligned pointer to the memory, +**
^The SQLITE_CONFIG_HEAP option specifies a static memory buffer +** that SQLite will use for all of its dynamic memory allocation needs +** beyond those provided for by [SQLITE_CONFIG_SCRATCH] and +** [SQLITE_CONFIG_PAGECACHE]. +** ^The SQLITE_CONFIG_HEAP option is only available if SQLite is compiled +** with either [SQLITE_ENABLE_MEMSYS3] or [SQLITE_ENABLE_MEMSYS5] and returns +** [SQLITE_ERROR] if invoked otherwise. +** ^There are three arguments to SQLITE_CONFIG_HEAP: +** An 8-byte aligned pointer to the memory, ** the number of bytes in the memory buffer, and the minimum allocation size. ** ^If the first pointer (the memory pointer) is NULL, then SQLite reverts ** to using its default memory allocator (the system malloc() implementation), ** undoing any prior invocation of [SQLITE_CONFIG_MALLOC]. ^If the -** memory pointer is not NULL and either [SQLITE_ENABLE_MEMSYS3] or -** [SQLITE_ENABLE_MEMSYS5] are defined, then the alternative memory +** memory pointer is not NULL then the alternative memory ** allocator is engaged to handle all of SQLites memory allocation needs. ** The first pointer (the memory pointer) must be aligned to an 8-byte ** boundary or subsequent behavior of SQLite will be undefined. @@ -1712,11 +1880,11 @@ struct sqlite3_mem_methods { ** for the minimum allocation size are 2**5 through 2**8.
** ** [[SQLITE_CONFIG_MUTEX]]
SQLITE_CONFIG_MUTEX
-**
^(This option takes a single argument which is a pointer to an -** instance of the [sqlite3_mutex_methods] structure. The argument specifies -** alternative low-level mutex routines to be used in place -** the mutex routines built into SQLite.)^ ^SQLite makes a copy of the -** content of the [sqlite3_mutex_methods] structure before the call to +**
^(The SQLITE_CONFIG_MUTEX option takes a single argument which is a +** pointer to an instance of the [sqlite3_mutex_methods] structure. +** The argument specifies alternative low-level mutex routines to be used +** in place the mutex routines built into SQLite.)^ ^SQLite makes a copy of +** the content of the [sqlite3_mutex_methods] structure before the call to ** [sqlite3_config()] returns. ^If SQLite is compiled with ** the [SQLITE_THREADSAFE | SQLITE_THREADSAFE=0] compile-time option then ** the entire mutexing subsystem is omitted from the build and hence calls to @@ -1724,8 +1892,8 @@ struct sqlite3_mem_methods { ** return [SQLITE_ERROR].
** ** [[SQLITE_CONFIG_GETMUTEX]]
SQLITE_CONFIG_GETMUTEX
-**
^(This option takes a single argument which is a pointer to an -** instance of the [sqlite3_mutex_methods] structure. The +**
^(The SQLITE_CONFIG_GETMUTEX option takes a single argument which +** is a pointer to an instance of the [sqlite3_mutex_methods] structure. The ** [sqlite3_mutex_methods] ** structure is filled with the currently defined mutex routines.)^ ** This option can be used to overload the default mutex allocation @@ -1737,25 +1905,25 @@ struct sqlite3_mem_methods { ** return [SQLITE_ERROR].
** ** [[SQLITE_CONFIG_LOOKASIDE]]
SQLITE_CONFIG_LOOKASIDE
-**
^(This option takes two arguments that determine the default -** memory allocation for the lookaside memory allocator on each -** [database connection]. The first argument is the +**
^(The SQLITE_CONFIG_LOOKASIDE option takes two arguments that determine +** the default size of lookaside memory on each [database connection]. +** The first argument is the ** size of each lookaside buffer slot and the second is the number of -** slots allocated to each database connection.)^ ^(This option sets the -** default lookaside size. The [SQLITE_DBCONFIG_LOOKASIDE] -** verb to [sqlite3_db_config()] can be used to change the lookaside +** slots allocated to each database connection.)^ ^(SQLITE_CONFIG_LOOKASIDE +** sets the default lookaside size. The [SQLITE_DBCONFIG_LOOKASIDE] +** option to [sqlite3_db_config()] can be used to change the lookaside ** configuration on individual connections.)^
** ** [[SQLITE_CONFIG_PCACHE2]]
SQLITE_CONFIG_PCACHE2
-**
^(This option takes a single argument which is a pointer to -** an [sqlite3_pcache_methods2] object. This object specifies the interface -** to a custom page cache implementation.)^ ^SQLite makes a copy of the -** object and uses it for page cache memory allocations.
+**
^(The SQLITE_CONFIG_PCACHE2 option takes a single argument which is +** a pointer to an [sqlite3_pcache_methods2] object. This object specifies +** the interface to a custom page cache implementation.)^ +** ^SQLite makes a copy of the [sqlite3_pcache_methods2] object.
** ** [[SQLITE_CONFIG_GETPCACHE2]]
SQLITE_CONFIG_GETPCACHE2
-**
^(This option takes a single argument which is a pointer to an -** [sqlite3_pcache_methods2] object. SQLite copies of the current -** page cache implementation into that object.)^
+**
^(The SQLITE_CONFIG_GETPCACHE2 option takes a single argument which +** is a pointer to an [sqlite3_pcache_methods2] object. SQLite copies of +** the current page cache implementation into that object.)^
** ** [[SQLITE_CONFIG_LOG]]
SQLITE_CONFIG_LOG
**
The SQLITE_CONFIG_LOG option is used to configure the SQLite @@ -1778,10 +1946,11 @@ struct sqlite3_mem_methods { ** function must be threadsafe.
** ** [[SQLITE_CONFIG_URI]]
SQLITE_CONFIG_URI -**
^(This option takes a single argument of type int. If non-zero, then -** URI handling is globally enabled. If the parameter is zero, then URI handling -** is globally disabled.)^ ^If URI handling is globally enabled, all filenames -** passed to [sqlite3_open()], [sqlite3_open_v2()], [sqlite3_open16()] or +**
^(The SQLITE_CONFIG_URI option takes a single argument of type int. +** If non-zero, then URI handling is globally enabled. If the parameter is zero, +** then URI handling is globally disabled.)^ ^If URI handling is globally +** enabled, all filenames passed to [sqlite3_open()], [sqlite3_open_v2()], +** [sqlite3_open16()] or ** specified as part of [ATTACH] commands are interpreted as URIs, regardless ** of whether or not the [SQLITE_OPEN_URI] flag is set when the database ** connection is opened. ^If it is globally disabled, filenames are @@ -1791,9 +1960,10 @@ struct sqlite3_mem_methods { ** [SQLITE_USE_URI] symbol defined.)^ ** ** [[SQLITE_CONFIG_COVERING_INDEX_SCAN]]
SQLITE_CONFIG_COVERING_INDEX_SCAN -**
^This option takes a single integer argument which is interpreted as -** a boolean in order to enable or disable the use of covering indices for -** full table scans in the query optimizer. ^The default setting is determined +**
^The SQLITE_CONFIG_COVERING_INDEX_SCAN option takes a single integer +** argument which is interpreted as a boolean in order to enable or disable +** the use of covering indices for full table scans in the query optimizer. +** ^The default setting is determined ** by the [SQLITE_ALLOW_COVERING_INDEX_SCAN] compile-time option, or is "on" ** if that compile-time option is omitted. ** The ability to disable the use of covering indices for full table scans @@ -1833,18 +2003,37 @@ struct sqlite3_mem_methods { ** ^The default setting can be overridden by each database connection using ** either the [PRAGMA mmap_size] command, or by using the ** [SQLITE_FCNTL_MMAP_SIZE] file control. ^(The maximum allowed mmap size -** cannot be changed at run-time. Nor may the maximum allowed mmap size -** exceed the compile-time maximum mmap size set by the +** will be silently truncated if necessary so that it does not exceed the +** compile-time maximum mmap size set by the ** [SQLITE_MAX_MMAP_SIZE] compile-time option.)^ ** ^If either argument to this option is negative, then that argument is ** changed to its compile-time default. ** ** [[SQLITE_CONFIG_WIN32_HEAPSIZE]] **
SQLITE_CONFIG_WIN32_HEAPSIZE -**
^This option is only available if SQLite is compiled for Windows -** with the [SQLITE_WIN32_MALLOC] pre-processor macro defined. -** SQLITE_CONFIG_WIN32_HEAPSIZE takes a 32-bit unsigned integer value +**
^The SQLITE_CONFIG_WIN32_HEAPSIZE option is only available if SQLite is +** compiled for Windows with the [SQLITE_WIN32_MALLOC] pre-processor macro +** defined. ^SQLITE_CONFIG_WIN32_HEAPSIZE takes a 32-bit unsigned integer value ** that specifies the maximum size of the created heap. +** +** [[SQLITE_CONFIG_PCACHE_HDRSZ]] +**
SQLITE_CONFIG_PCACHE_HDRSZ +**
^The SQLITE_CONFIG_PCACHE_HDRSZ option takes a single parameter which +** is a pointer to an integer and writes into that integer the number of extra +** bytes per page required for each page in [SQLITE_CONFIG_PAGECACHE]. +** The amount of extra space required can change depending on the compiler, +** target platform, and SQLite version. +** +** [[SQLITE_CONFIG_PMASZ]] +**
SQLITE_CONFIG_PMASZ +**
^The SQLITE_CONFIG_PMASZ option takes a single parameter which +** is an unsigned integer and sets the "Minimum PMA Size" for the multithreaded +** sorter to that integer. The default minimum PMA Size is set by the +** [SQLITE_SORTER_PMASZ] compile-time option. New threads are launched +** to help with sort operations when multithreaded sorting +** is enabled (using the [PRAGMA threads] command) and the amount of content +** to be sorted exceeds the page size times the minimum of the +** [PRAGMA cache_size] setting and this value. ** */ #define SQLITE_CONFIG_SINGLETHREAD 1 /* nil */ @@ -1870,6 +2059,8 @@ struct sqlite3_mem_methods { #define SQLITE_CONFIG_SQLLOG 21 /* xSqllog, void* */ #define SQLITE_CONFIG_MMAP_SIZE 22 /* sqlite3_int64, sqlite3_int64 */ #define SQLITE_CONFIG_WIN32_HEAPSIZE 23 /* int nByte */ +#define SQLITE_CONFIG_PCACHE_HDRSZ 24 /* int *psz */ +#define SQLITE_CONFIG_PMASZ 25 /* unsigned int szPma */ /* ** CAPI3REF: Database Connection Configuration Options @@ -1936,15 +2127,17 @@ struct sqlite3_mem_methods { /* ** CAPI3REF: Enable Or Disable Extended Result Codes +** METHOD: sqlite3 ** ** ^The sqlite3_extended_result_codes() routine enables or disables the ** [extended result codes] feature of SQLite. ^The extended result ** codes are disabled by default for historical compatibility. */ -SQLITE_API int sqlite3_extended_result_codes(sqlite3*, int onoff); +SQLITE_API int SQLITE_STDCALL sqlite3_extended_result_codes(sqlite3*, int onoff); /* ** CAPI3REF: Last Insert Rowid +** METHOD: sqlite3 ** ** ^Each entry in most SQLite tables (except for [WITHOUT ROWID] tables) ** has a unique 64-bit signed @@ -1992,52 +2185,51 @@ SQLITE_API int sqlite3_extended_result_codes(sqlite3*, int onoff); ** unpredictable and might not equal either the old or the new ** last insert [rowid]. */ -SQLITE_API sqlite3_int64 sqlite3_last_insert_rowid(sqlite3*); +SQLITE_API sqlite3_int64 SQLITE_STDCALL sqlite3_last_insert_rowid(sqlite3*); /* ** CAPI3REF: Count The Number Of Rows Modified +** METHOD: sqlite3 ** -** ^This function returns the number of database rows that were changed -** or inserted or deleted by the most recently completed SQL statement -** on the [database connection] specified by the first parameter. -** ^(Only changes that are directly specified by the [INSERT], [UPDATE], -** or [DELETE] statement are counted. Auxiliary changes caused by -** triggers or [foreign key actions] are not counted.)^ Use the -** [sqlite3_total_changes()] function to find the total number of changes -** including changes caused by triggers and foreign key actions. +** ^This function returns the number of rows modified, inserted or +** deleted by the most recently completed INSERT, UPDATE or DELETE +** statement on the database connection specified by the only parameter. +** ^Executing any other type of SQL statement does not modify the value +** returned by this function. ** -** ^Changes to a view that are simulated by an [INSTEAD OF trigger] -** are not counted. Only real table changes are counted. +** ^Only changes made directly by the INSERT, UPDATE or DELETE statement are +** considered - auxiliary changes caused by [CREATE TRIGGER | triggers], +** [foreign key actions] or [REPLACE] constraint resolution are not counted. +** +** Changes to a view that are intercepted by +** [INSTEAD OF trigger | INSTEAD OF triggers] are not counted. ^The value +** returned by sqlite3_changes() immediately after an INSERT, UPDATE or +** DELETE statement run on a view is always zero. Only changes made to real +** tables are counted. ** -** ^(A "row change" is a change to a single row of a single table -** caused by an INSERT, DELETE, or UPDATE statement. Rows that -** are changed as side effects of [REPLACE] constraint resolution, -** rollback, ABORT processing, [DROP TABLE], or by any other -** mechanisms do not count as direct row changes.)^ -** -** A "trigger context" is a scope of execution that begins and -** ends with the script of a [CREATE TRIGGER | trigger]. -** Most SQL statements are -** evaluated outside of any trigger. This is the "top level" -** trigger context. If a trigger fires from the top level, a -** new trigger context is entered for the duration of that one -** trigger. Subtriggers create subcontexts for their duration. -** -** ^Calling [sqlite3_exec()] or [sqlite3_step()] recursively does -** not create a new trigger context. -** -** ^This function returns the number of direct row changes in the -** most recent INSERT, UPDATE, or DELETE statement within the same -** trigger context. -** -** ^Thus, when called from the top level, this function returns the -** number of changes in the most recent INSERT, UPDATE, or DELETE -** that also occurred at the top level. ^(Within the body of a trigger, -** the sqlite3_changes() interface can be called to find the number of -** changes in the most recently completed INSERT, UPDATE, or DELETE -** statement within the body of the same trigger. -** However, the number returned does not include changes -** caused by subtriggers since those have their own context.)^ +** Things are more complicated if the sqlite3_changes() function is +** executed while a trigger program is running. This may happen if the +** program uses the [changes() SQL function], or if some other callback +** function invokes sqlite3_changes() directly. Essentially: +** +**
    +**
  • ^(Before entering a trigger program the value returned by +** sqlite3_changes() function is saved. After the trigger program +** has finished, the original value is restored.)^ +** +**
  • ^(Within a trigger program each INSERT, UPDATE and DELETE +** statement sets the value returned by sqlite3_changes() +** upon completion as normal. Of course, this value will not include +** any changes performed by sub-triggers, as the sqlite3_changes() +** value will be saved and restored after each sub-trigger has run.)^ +**
+** +** ^This means that if the changes() SQL function (or similar) is used +** by the first INSERT, UPDATE or DELETE statement within a trigger, it +** returns the value as set when the calling statement began executing. +** ^If it is used by the second or subsequent such statement within a trigger +** program, the value returned reflects the number of rows modified by the +** previous INSERT, UPDATE or DELETE statement within the same trigger. ** ** See also the [sqlite3_total_changes()] interface, the ** [count_changes pragma], and the [changes() SQL function]. @@ -2046,25 +2238,23 @@ SQLITE_API sqlite3_int64 sqlite3_last_insert_rowid(sqlite3*); ** while [sqlite3_changes()] is running then the value returned ** is unpredictable and not meaningful. */ -SQLITE_API int sqlite3_changes(sqlite3*); +SQLITE_API int SQLITE_STDCALL sqlite3_changes(sqlite3*); /* ** CAPI3REF: Total Number Of Rows Modified +** METHOD: sqlite3 ** -** ^This function returns the number of row changes caused by [INSERT], -** [UPDATE] or [DELETE] statements since the [database connection] was opened. -** ^(The count returned by sqlite3_total_changes() includes all changes -** from all [CREATE TRIGGER | trigger] contexts and changes made by -** [foreign key actions]. However, -** the count does not include changes used to implement [REPLACE] constraints, -** do rollbacks or ABORT processing, or [DROP TABLE] processing. The -** count does not include rows of views that fire an [INSTEAD OF trigger], -** though if the INSTEAD OF trigger makes changes of its own, those changes -** are counted.)^ -** ^The sqlite3_total_changes() function counts the changes as soon as -** the statement that makes them is completed (when the statement handle -** is passed to [sqlite3_reset()] or [sqlite3_finalize()]). -** +** ^This function returns the total number of rows inserted, modified or +** deleted by all [INSERT], [UPDATE] or [DELETE] statements completed +** since the database connection was opened, including those executed as +** part of trigger programs. ^Executing any other type of SQL statement +** does not affect the value returned by sqlite3_total_changes(). +** +** ^Changes made as part of [foreign key actions] are included in the +** count, but those made as part of REPLACE constraint resolution are +** not. ^Changes to a view that are intercepted by INSTEAD OF triggers +** are not counted. +** ** See also the [sqlite3_changes()] interface, the ** [count_changes pragma], and the [total_changes() SQL function]. ** @@ -2072,10 +2262,11 @@ SQLITE_API int sqlite3_changes(sqlite3*); ** while [sqlite3_total_changes()] is running then the value ** returned is unpredictable and not meaningful. */ -SQLITE_API int sqlite3_total_changes(sqlite3*); +SQLITE_API int SQLITE_STDCALL sqlite3_total_changes(sqlite3*); /* ** CAPI3REF: Interrupt A Long-Running Query +** METHOD: sqlite3 ** ** ^This function causes any pending database operation to abort and ** return at its earliest opportunity. This routine is typically @@ -2111,7 +2302,7 @@ SQLITE_API int sqlite3_total_changes(sqlite3*); ** If the database connection closes while [sqlite3_interrupt()] ** is running then bad things will likely happen. */ -SQLITE_API void sqlite3_interrupt(sqlite3*); +SQLITE_API void SQLITE_STDCALL sqlite3_interrupt(sqlite3*); /* ** CAPI3REF: Determine If An SQL Statement Is Complete @@ -2146,33 +2337,41 @@ SQLITE_API void sqlite3_interrupt(sqlite3*); ** The input to [sqlite3_complete16()] must be a zero-terminated ** UTF-16 string in native byte order. */ -SQLITE_API int sqlite3_complete(const char *sql); -SQLITE_API int sqlite3_complete16(const void *sql); +SQLITE_API int SQLITE_STDCALL sqlite3_complete(const char *sql); +SQLITE_API int SQLITE_STDCALL sqlite3_complete16(const void *sql); /* ** CAPI3REF: Register A Callback To Handle SQLITE_BUSY Errors +** KEYWORDS: {busy-handler callback} {busy handler} +** METHOD: sqlite3 ** -** ^This routine sets a callback function that might be invoked whenever -** an attempt is made to open a database table that another thread -** or process has locked. +** ^The sqlite3_busy_handler(D,X,P) routine sets a callback function X +** that might be invoked with argument P whenever +** an attempt is made to access a database table associated with +** [database connection] D when another thread +** or process has the table locked. +** The sqlite3_busy_handler() interface is used to implement +** [sqlite3_busy_timeout()] and [PRAGMA busy_timeout]. ** -** ^If the busy callback is NULL, then [SQLITE_BUSY] or [SQLITE_IOERR_BLOCKED] +** ^If the busy callback is NULL, then [SQLITE_BUSY] ** is returned immediately upon encountering the lock. ^If the busy callback ** is not NULL, then the callback might be invoked with two arguments. ** ** ^The first argument to the busy handler is a copy of the void* pointer which ** is the third argument to sqlite3_busy_handler(). ^The second argument to ** the busy handler callback is the number of times that the busy handler has -** been invoked for this locking event. ^If the +** been invoked previously for the same locking event. ^If the ** busy callback returns 0, then no additional attempts are made to -** access the database and [SQLITE_BUSY] or [SQLITE_IOERR_BLOCKED] is returned. +** access the database and [SQLITE_BUSY] is returned +** to the application. ** ^If the callback returns non-zero, then another attempt -** is made to open the database for reading and the cycle repeats. +** is made to access the database and the cycle repeats. ** ** The presence of a busy handler does not guarantee that it will be invoked ** when there is lock contention. ^If SQLite determines that invoking the busy ** handler could result in a deadlock, it will go ahead and return [SQLITE_BUSY] -** or [SQLITE_IOERR_BLOCKED] instead of invoking the busy handler. +** to the application instead of invoking the +** busy handler. ** Consider a scenario where one process is holding a read lock that ** it is trying to promote to a reserved lock and ** a second process is holding a reserved lock that it is trying @@ -2186,57 +2385,48 @@ SQLITE_API int sqlite3_complete16(const void *sql); ** ** ^The default busy callback is NULL. ** -** ^The [SQLITE_BUSY] error is converted to [SQLITE_IOERR_BLOCKED] -** when SQLite is in the middle of a large transaction where all the -** changes will not fit into the in-memory cache. SQLite will -** already hold a RESERVED lock on the database file, but it needs -** to promote this lock to EXCLUSIVE so that it can spill cache -** pages into the database file without harm to concurrent -** readers. ^If it is unable to promote the lock, then the in-memory -** cache will be left in an inconsistent state and so the error -** code is promoted from the relatively benign [SQLITE_BUSY] to -** the more severe [SQLITE_IOERR_BLOCKED]. ^This error code promotion -** forces an automatic rollback of the changes. See the -** -** CorruptionFollowingBusyError wiki page for a discussion of why -** this is important. -** ** ^(There can only be a single busy handler defined for each ** [database connection]. Setting a new busy handler clears any ** previously set handler.)^ ^Note that calling [sqlite3_busy_timeout()] -** will also set or clear the busy handler. +** or evaluating [PRAGMA busy_timeout=N] will change the +** busy handler and thus clear any previously set busy handler. ** ** The busy callback should not take any actions which modify the -** database connection that invoked the busy handler. Any such actions +** database connection that invoked the busy handler. In other words, +** the busy handler is not reentrant. Any such actions ** result in undefined behavior. ** ** A busy handler must not close the database connection ** or [prepared statement] that invoked the busy handler. */ -SQLITE_API int sqlite3_busy_handler(sqlite3*, int(*)(void*,int), void*); +SQLITE_API int SQLITE_STDCALL sqlite3_busy_handler(sqlite3*, int(*)(void*,int), void*); /* ** CAPI3REF: Set A Busy Timeout +** METHOD: sqlite3 ** ** ^This routine sets a [sqlite3_busy_handler | busy handler] that sleeps ** for a specified amount of time when a table is locked. ^The handler ** will sleep multiple times until at least "ms" milliseconds of sleeping ** have accumulated. ^After at least "ms" milliseconds of sleeping, ** the handler returns 0 which causes [sqlite3_step()] to return -** [SQLITE_BUSY] or [SQLITE_IOERR_BLOCKED]. +** [SQLITE_BUSY]. ** ** ^Calling this routine with an argument less than or equal to zero ** turns off all busy handlers. ** ** ^(There can only be a single busy handler for a particular -** [database connection] any any given moment. If another busy handler +** [database connection] at any given moment. If another busy handler ** was defined (using [sqlite3_busy_handler()]) prior to calling ** this routine, that other busy handler is cleared.)^ +** +** See also: [PRAGMA busy_timeout] */ -SQLITE_API int sqlite3_busy_timeout(sqlite3*, int ms); +SQLITE_API int SQLITE_STDCALL sqlite3_busy_timeout(sqlite3*, int ms); /* ** CAPI3REF: Convenience Routines For Running Queries +** METHOD: sqlite3 ** ** This is a legacy interface that is preserved for backwards compatibility. ** Use of this interface is not recommended. @@ -2307,7 +2497,7 @@ SQLITE_API int sqlite3_busy_timeout(sqlite3*, int ms); ** reflected in subsequent calls to [sqlite3_errcode()] or ** [sqlite3_errmsg()]. */ -SQLITE_API int sqlite3_get_table( +SQLITE_API int SQLITE_STDCALL sqlite3_get_table( sqlite3 *db, /* An open database */ const char *zSql, /* SQL to be evaluated */ char ***pazResult, /* Results of the query */ @@ -2315,13 +2505,17 @@ SQLITE_API int sqlite3_get_table( int *pnColumn, /* Number of result columns written here */ char **pzErrmsg /* Error msg written here */ ); -SQLITE_API void sqlite3_free_table(char **result); +SQLITE_API void SQLITE_STDCALL sqlite3_free_table(char **result); /* ** CAPI3REF: Formatted String Printing Functions ** ** These routines are work-alikes of the "printf()" family of functions ** from the standard C library. +** These routines understand most of the common K&R formatting options, +** plus some additional non-standard formats, detailed below. +** Note that some of the more obscure formatting options from recent +** C-library standards are omitted from this implementation. ** ** ^The sqlite3_mprintf() and sqlite3_vmprintf() routines write their ** results into memory obtained from [sqlite3_malloc()]. @@ -2354,7 +2548,7 @@ SQLITE_API void sqlite3_free_table(char **result); ** These routines all implement some additional formatting ** options that are useful for constructing SQL statements. ** All of the usual printf() formatting options apply. In addition, there -** is are "%q", "%Q", and "%z" options. +** is are "%q", "%Q", "%w" and "%z" options. ** ** ^(The %q option works like %s in that it substitutes a nul-terminated ** string from the argument list. But %q also doubles every '\'' character. @@ -2407,14 +2601,20 @@ SQLITE_API void sqlite3_free_table(char **result); ** The code above will render a correct SQL statement in the zSQL ** variable even if the zText variable is a NULL pointer. ** +** ^(The "%w" formatting option is like "%q" except that it expects to +** be contained within double-quotes instead of single quotes, and it +** escapes the double-quote character instead of the single-quote +** character.)^ The "%w" formatting option is intended for safely inserting +** table and column names into a constructed SQL statement. +** ** ^(The "%z" formatting option works like "%s" but with the ** addition that after the string has been read and copied into ** the result, [sqlite3_free()] is called on the input string.)^ */ -SQLITE_API char *sqlite3_mprintf(const char*,...); -SQLITE_API char *sqlite3_vmprintf(const char*, va_list); -SQLITE_API char *sqlite3_snprintf(int,char*,const char*, ...); -SQLITE_API char *sqlite3_vsnprintf(int,char*,const char*, va_list); +SQLITE_API char *SQLITE_CDECL sqlite3_mprintf(const char*,...); +SQLITE_API char *SQLITE_STDCALL sqlite3_vmprintf(const char*, va_list); +SQLITE_API char *SQLITE_CDECL sqlite3_snprintf(int,char*,const char*, ...); +SQLITE_API char *SQLITE_STDCALL sqlite3_vsnprintf(int,char*,const char*, va_list); /* ** CAPI3REF: Memory Allocation Subsystem @@ -2431,6 +2631,10 @@ SQLITE_API char *sqlite3_vsnprintf(int,char*,const char*, va_list); ** sqlite3_malloc() is zero or negative then sqlite3_malloc() returns ** a NULL pointer. ** +** ^The sqlite3_malloc64(N) routine works just like +** sqlite3_malloc(N) except that N is an unsigned 64-bit integer instead +** of a signed 32-bit integer. +** ** ^Calling sqlite3_free() with a pointer previously returned ** by sqlite3_malloc() or sqlite3_realloc() releases that memory so ** that it might be reused. ^The sqlite3_free() routine is @@ -2442,24 +2646,38 @@ SQLITE_API char *sqlite3_vsnprintf(int,char*,const char*, va_list); ** might result if sqlite3_free() is called with a non-NULL pointer that ** was not obtained from sqlite3_malloc() or sqlite3_realloc(). ** -** ^(The sqlite3_realloc() interface attempts to resize a -** prior memory allocation to be at least N bytes, where N is the -** second parameter. The memory allocation to be resized is the first -** parameter.)^ ^ If the first parameter to sqlite3_realloc() +** ^The sqlite3_realloc(X,N) interface attempts to resize a +** prior memory allocation X to be at least N bytes. +** ^If the X parameter to sqlite3_realloc(X,N) ** is a NULL pointer then its behavior is identical to calling -** sqlite3_malloc(N) where N is the second parameter to sqlite3_realloc(). -** ^If the second parameter to sqlite3_realloc() is zero or +** sqlite3_malloc(N). +** ^If the N parameter to sqlite3_realloc(X,N) is zero or ** negative then the behavior is exactly the same as calling -** sqlite3_free(P) where P is the first parameter to sqlite3_realloc(). -** ^sqlite3_realloc() returns a pointer to a memory allocation -** of at least N bytes in size or NULL if sufficient memory is unavailable. +** sqlite3_free(X). +** ^sqlite3_realloc(X,N) returns a pointer to a memory allocation +** of at least N bytes in size or NULL if insufficient memory is available. ** ^If M is the size of the prior allocation, then min(N,M) bytes ** of the prior allocation are copied into the beginning of buffer returned -** by sqlite3_realloc() and the prior allocation is freed. -** ^If sqlite3_realloc() returns NULL, then the prior allocation -** is not freed. +** by sqlite3_realloc(X,N) and the prior allocation is freed. +** ^If sqlite3_realloc(X,N) returns NULL and N is positive, then the +** prior allocation is not freed. ** -** ^The memory returned by sqlite3_malloc() and sqlite3_realloc() +** ^The sqlite3_realloc64(X,N) interfaces works the same as +** sqlite3_realloc(X,N) except that N is a 64-bit unsigned integer instead +** of a 32-bit signed integer. +** +** ^If X is a memory allocation previously obtained from sqlite3_malloc(), +** sqlite3_malloc64(), sqlite3_realloc(), or sqlite3_realloc64(), then +** sqlite3_msize(X) returns the size of that memory allocation in bytes. +** ^The value returned by sqlite3_msize(X) might be larger than the number +** of bytes requested when X was allocated. ^If X is a NULL pointer then +** sqlite3_msize(X) returns zero. If X points to something that is not +** the beginning of memory allocation, or if it points to a formerly +** valid memory allocation that has now been freed, then the behavior +** of sqlite3_msize(X) is undefined and possibly harmful. +** +** ^The memory returned by sqlite3_malloc(), sqlite3_realloc(), +** sqlite3_malloc64(), and sqlite3_realloc64() ** is always aligned to at least an 8 byte boundary, or to a ** 4 byte boundary if the [SQLITE_4_BYTE_ALIGNED_MALLOC] compile-time ** option is used. @@ -2486,9 +2704,12 @@ SQLITE_API char *sqlite3_vsnprintf(int,char*,const char*, va_list); ** a block of memory after it has been released using ** [sqlite3_free()] or [sqlite3_realloc()]. */ -SQLITE_API void *sqlite3_malloc(int); -SQLITE_API void *sqlite3_realloc(void*, int); -SQLITE_API void sqlite3_free(void*); +SQLITE_API void *SQLITE_STDCALL sqlite3_malloc(int); +SQLITE_API void *SQLITE_STDCALL sqlite3_malloc64(sqlite3_uint64); +SQLITE_API void *SQLITE_STDCALL sqlite3_realloc(void*, int); +SQLITE_API void *SQLITE_STDCALL sqlite3_realloc64(void*, sqlite3_uint64); +SQLITE_API void SQLITE_STDCALL sqlite3_free(void*); +SQLITE_API sqlite3_uint64 SQLITE_STDCALL sqlite3_msize(void*); /* ** CAPI3REF: Memory Allocator Statistics @@ -2513,8 +2734,8 @@ SQLITE_API void sqlite3_free(void*); ** by [sqlite3_memory_highwater(1)] is the high-water mark ** prior to the reset. */ -SQLITE_API sqlite3_int64 sqlite3_memory_used(void); -SQLITE_API sqlite3_int64 sqlite3_memory_highwater(int resetFlag); +SQLITE_API sqlite3_int64 SQLITE_STDCALL sqlite3_memory_used(void); +SQLITE_API sqlite3_int64 SQLITE_STDCALL sqlite3_memory_highwater(int resetFlag); /* ** CAPI3REF: Pseudo-Random Number Generator @@ -2526,20 +2747,22 @@ SQLITE_API sqlite3_int64 sqlite3_memory_highwater(int resetFlag); ** applications to access the same PRNG for other purposes. ** ** ^A call to this routine stores N bytes of randomness into buffer P. -** ^If N is less than one, then P can be a NULL pointer. +** ^The P parameter can be a NULL pointer. ** ** ^If this routine has not been previously called or if the previous -** call had N less than one, then the PRNG is seeded using randomness -** obtained from the xRandomness method of the default [sqlite3_vfs] object. -** ^If the previous call to this routine had an N of 1 or more then -** the pseudo-randomness is generated +** call had N less than one or a NULL pointer for P, then the PRNG is +** seeded using randomness obtained from the xRandomness method of +** the default [sqlite3_vfs] object. +** ^If the previous call to this routine had an N of 1 or more and a +** non-NULL P then the pseudo-randomness is generated ** internally and without recourse to the [sqlite3_vfs] xRandomness ** method. */ -SQLITE_API void sqlite3_randomness(int N, void *P); +SQLITE_API void SQLITE_STDCALL sqlite3_randomness(int N, void *P); /* ** CAPI3REF: Compile-Time Authorization Callbacks +** METHOD: sqlite3 ** ** ^This routine registers an authorizer callback with a particular ** [database connection], supplied in the first argument. @@ -2618,7 +2841,7 @@ SQLITE_API void sqlite3_randomness(int N, void *P); ** as stated in the previous paragraph, sqlite3_step() invokes ** sqlite3_prepare_v2() to reprepare a statement after a schema change. */ -SQLITE_API int sqlite3_set_authorizer( +SQLITE_API int SQLITE_STDCALL sqlite3_set_authorizer( sqlite3*, int (*xAuth)(void*,int,const char*,const char*,const char*,const char*), void *pUserData @@ -2633,8 +2856,8 @@ SQLITE_API int sqlite3_set_authorizer( ** [sqlite3_set_authorizer | authorizer documentation] for additional ** information. ** -** Note that SQLITE_IGNORE is also used as a [SQLITE_ROLLBACK | return code] -** from the [sqlite3_vtab_on_conflict()] interface. +** Note that SQLITE_IGNORE is also used as a [conflict resolution mode] +** returned from the [sqlite3_vtab_on_conflict()] interface. */ #define SQLITE_DENY 1 /* Abort the SQL statement with an error */ #define SQLITE_IGNORE 2 /* Don't allow access, but don't generate an error */ @@ -2696,6 +2919,7 @@ SQLITE_API int sqlite3_set_authorizer( /* ** CAPI3REF: Tracing And Profiling Functions +** METHOD: sqlite3 ** ** These routines register callback functions that can be used for ** tracing and profiling the execution of SQL statements. @@ -2722,12 +2946,13 @@ SQLITE_API int sqlite3_set_authorizer( ** sqlite3_profile() function is considered experimental and is ** subject to change in future versions of SQLite. */ -SQLITE_API void *sqlite3_trace(sqlite3*, void(*xTrace)(void*,const char*), void*); -SQLITE_API SQLITE_EXPERIMENTAL void *sqlite3_profile(sqlite3*, +SQLITE_API void *SQLITE_STDCALL sqlite3_trace(sqlite3*, void(*xTrace)(void*,const char*), void*); +SQLITE_API SQLITE_EXPERIMENTAL void *SQLITE_STDCALL sqlite3_profile(sqlite3*, void(*xProfile)(void*,const char*,sqlite3_uint64), void*); /* ** CAPI3REF: Query Progress Callbacks +** METHOD: sqlite3 ** ** ^The sqlite3_progress_handler(D,N,X,P) interface causes the callback ** function X to be invoked periodically during long running calls to @@ -2757,10 +2982,11 @@ SQLITE_API SQLITE_EXPERIMENTAL void *sqlite3_profile(sqlite3*, ** database connections for the meaning of "modify" in this paragraph. ** */ -SQLITE_API void sqlite3_progress_handler(sqlite3*, int, int(*)(void*), void*); +SQLITE_API void SQLITE_STDCALL sqlite3_progress_handler(sqlite3*, int, int(*)(void*), void*); /* ** CAPI3REF: Opening A New Database Connection +** CONSTRUCTOR: sqlite3 ** ** ^These routines open an SQLite database file as specified by the ** filename argument. ^The filename argument is interpreted as UTF-8 for @@ -2775,9 +3001,9 @@ SQLITE_API void sqlite3_progress_handler(sqlite3*, int, int(*)(void*), void*); ** an English language description of the error following a failure of any ** of the sqlite3_open() routines. ** -** ^The default encoding for the database will be UTF-8 if -** sqlite3_open() or sqlite3_open_v2() is called and -** UTF-16 in the native byte order if sqlite3_open16() is used. +** ^The default encoding will be UTF-8 for databases created using +** sqlite3_open() or sqlite3_open_v2(). ^The default encoding for databases +** created using sqlite3_open16() will be UTF-16 in the native byte order. ** ** Whether or not an error occurs when it is opened, resources ** associated with the [database connection] handle should be released by @@ -2865,13 +3091,14 @@ SQLITE_API void sqlite3_progress_handler(sqlite3*, int, int(*)(void*), void*); ** then it is interpreted as an absolute path. ^If the path does not begin ** with a '/' (meaning that the authority section is omitted from the URI) ** then the path is interpreted as a relative path. -** ^On windows, the first component of an absolute path -** is a drive specification (e.g. "C:"). +** ^(On windows, the first component of an absolute path +** is a drive specification (e.g. "C:").)^ ** ** [[core URI query parameters]] ** The query component of a URI may contain parameters that are interpreted ** either by SQLite itself, or by a [VFS | custom VFS implementation]. -** SQLite interprets the following three query parameters: +** SQLite and its built-in [VFSes] interpret the +** following query parameters: ** **
    **
  • vfs: ^The "vfs" parameter may be used to specify the name of @@ -2906,11 +3133,9 @@ SQLITE_API void sqlite3_progress_handler(sqlite3*, int, int(*)(void*), void*); ** a URI filename, its value overrides any behavior requested by setting ** SQLITE_OPEN_PRIVATECACHE or SQLITE_OPEN_SHAREDCACHE flag. ** -**
  • psow: ^The psow parameter may be "true" (or "on" or "yes" or -** "1") or "false" (or "off" or "no" or "0") to indicate that the +**
  • psow: ^The psow parameter indicates whether or not the ** [powersafe overwrite] property does or does not apply to the -** storage media on which the database file resides. ^The psow query -** parameter only works for the built-in unix and Windows VFSes. +** storage media on which the database file resides. ** **
  • nolock: ^The nolock parameter is a boolean query parameter ** which if set disables file locking in rollback journal modes. This @@ -2986,15 +3211,15 @@ SQLITE_API void sqlite3_progress_handler(sqlite3*, int, int(*)(void*), void*); ** ** See also: [sqlite3_temp_directory] */ -SQLITE_API int sqlite3_open( +SQLITE_API int SQLITE_STDCALL sqlite3_open( const char *filename, /* Database filename (UTF-8) */ sqlite3 **ppDb /* OUT: SQLite db handle */ ); -SQLITE_API int sqlite3_open16( +SQLITE_API int SQLITE_STDCALL sqlite3_open16( const void *filename, /* Database filename (UTF-16) */ sqlite3 **ppDb /* OUT: SQLite db handle */ ); -SQLITE_API int sqlite3_open_v2( +SQLITE_API int SQLITE_STDCALL sqlite3_open_v2( const char *filename, /* Database filename (UTF-8) */ sqlite3 **ppDb, /* OUT: SQLite db handle */ int flags, /* Flags */ @@ -3040,19 +3265,22 @@ SQLITE_API int sqlite3_open_v2( ** VFS method, then the behavior of this routine is undefined and probably ** undesirable. */ -SQLITE_API const char *sqlite3_uri_parameter(const char *zFilename, const char *zParam); -SQLITE_API int sqlite3_uri_boolean(const char *zFile, const char *zParam, int bDefault); -SQLITE_API sqlite3_int64 sqlite3_uri_int64(const char*, const char*, sqlite3_int64); +SQLITE_API const char *SQLITE_STDCALL sqlite3_uri_parameter(const char *zFilename, const char *zParam); +SQLITE_API int SQLITE_STDCALL sqlite3_uri_boolean(const char *zFile, const char *zParam, int bDefault); +SQLITE_API sqlite3_int64 SQLITE_STDCALL sqlite3_uri_int64(const char*, const char*, sqlite3_int64); /* ** CAPI3REF: Error Codes And Messages +** METHOD: sqlite3 ** -** ^The sqlite3_errcode() interface returns the numeric [result code] or -** [extended result code] for the most recent failed sqlite3_* API call -** associated with a [database connection]. If a prior API call failed -** but the most recent API call succeeded, the return value from -** sqlite3_errcode() is undefined. ^The sqlite3_extended_errcode() +** ^If the most recent sqlite3_* API call associated with +** [database connection] D failed, then the sqlite3_errcode(D) interface +** returns the numeric [result code] or [extended result code] for that +** API call. +** If the most recent API call was successful, +** then the return value from sqlite3_errcode() is undefined. +** ^The sqlite3_extended_errcode() ** interface is the same except that it always returns the ** [extended result code] even when extended result codes are ** disabled. @@ -3083,40 +3311,41 @@ SQLITE_API sqlite3_int64 sqlite3_uri_int64(const char*, const char*, sqlite3_int ** was invoked incorrectly by the application. In that case, the ** error code and message may or may not be set. */ -SQLITE_API int sqlite3_errcode(sqlite3 *db); -SQLITE_API int sqlite3_extended_errcode(sqlite3 *db); -SQLITE_API const char *sqlite3_errmsg(sqlite3*); -SQLITE_API const void *sqlite3_errmsg16(sqlite3*); -SQLITE_API const char *sqlite3_errstr(int); +SQLITE_API int SQLITE_STDCALL sqlite3_errcode(sqlite3 *db); +SQLITE_API int SQLITE_STDCALL sqlite3_extended_errcode(sqlite3 *db); +SQLITE_API const char *SQLITE_STDCALL sqlite3_errmsg(sqlite3*); +SQLITE_API const void *SQLITE_STDCALL sqlite3_errmsg16(sqlite3*); +SQLITE_API const char *SQLITE_STDCALL sqlite3_errstr(int); /* -** CAPI3REF: SQL Statement Object +** CAPI3REF: Prepared Statement Object ** KEYWORDS: {prepared statement} {prepared statements} ** -** An instance of this object represents a single SQL statement. -** This object is variously known as a "prepared statement" or a -** "compiled SQL statement" or simply as a "statement". +** An instance of this object represents a single SQL statement that +** has been compiled into binary form and is ready to be evaluated. ** -** The life of a statement object goes something like this: +** Think of each SQL statement as a separate computer program. The +** original SQL text is source code. A prepared statement object +** is the compiled object code. All SQL must be converted into a +** prepared statement before it can be run. +** +** The life-cycle of a prepared statement object usually goes like this: ** **
      -**
    1. Create the object using [sqlite3_prepare_v2()] or a related -** function. -**
    2. Bind values to [host parameters] using the sqlite3_bind_*() +**
    3. Create the prepared statement object using [sqlite3_prepare_v2()]. +**
    4. Bind values to [parameters] using the sqlite3_bind_*() ** interfaces. **
    5. Run the SQL by calling [sqlite3_step()] one or more times. -**
    6. Reset the statement using [sqlite3_reset()] then go back +**
    7. Reset the prepared statement using [sqlite3_reset()] then go back ** to step 2. Do this zero or more times. **
    8. Destroy the object using [sqlite3_finalize()]. **
    -** -** Refer to documentation on individual methods above for additional -** information. */ typedef struct sqlite3_stmt sqlite3_stmt; /* ** CAPI3REF: Run-time Limits +** METHOD: sqlite3 ** ** ^(This interface allows the size of various constructs to be limited ** on a connection by connection basis. The first parameter is the @@ -3154,7 +3383,7 @@ typedef struct sqlite3_stmt sqlite3_stmt; ** ** New run-time limit categories may be added in future releases. */ -SQLITE_API int sqlite3_limit(sqlite3*, int id, int newVal); +SQLITE_API int SQLITE_STDCALL sqlite3_limit(sqlite3*, int id, int newVal); /* ** CAPI3REF: Run-Time Limit Categories @@ -3206,6 +3435,10 @@ SQLITE_API int sqlite3_limit(sqlite3*, int id, int newVal); ** ** [[SQLITE_LIMIT_TRIGGER_DEPTH]] ^(
    SQLITE_LIMIT_TRIGGER_DEPTH
    **
    The maximum depth of recursion for triggers.
    )^ +** +** [[SQLITE_LIMIT_WORKER_THREADS]] ^(
    SQLITE_LIMIT_WORKER_THREADS
    +**
    The maximum number of auxiliary worker threads that a single +** [prepared statement] may start.
    )^ ** */ #define SQLITE_LIMIT_LENGTH 0 @@ -3219,10 +3452,13 @@ SQLITE_API int sqlite3_limit(sqlite3*, int id, int newVal); #define SQLITE_LIMIT_LIKE_PATTERN_LENGTH 8 #define SQLITE_LIMIT_VARIABLE_NUMBER 9 #define SQLITE_LIMIT_TRIGGER_DEPTH 10 +#define SQLITE_LIMIT_WORKER_THREADS 11 /* ** CAPI3REF: Compiling An SQL Statement ** KEYWORDS: {SQL statement compiler} +** METHOD: sqlite3 +** CONSTRUCTOR: sqlite3_stmt ** ** To execute an SQL query, it must first be compiled into a byte-code ** program using one of these routines. @@ -3236,16 +3472,14 @@ SQLITE_API int sqlite3_limit(sqlite3*, int id, int newVal); ** interfaces use UTF-8, and sqlite3_prepare16() and sqlite3_prepare16_v2() ** use UTF-16. ** -** ^If the nByte argument is less than zero, then zSql is read up to the -** first zero terminator. ^If nByte is non-negative, then it is the maximum -** number of bytes read from zSql. ^When nByte is non-negative, the -** zSql string ends at either the first '\000' or '\u0000' character or -** the nByte-th byte, whichever comes first. If the caller knows -** that the supplied string is nul-terminated, then there is a small -** performance advantage to be gained by passing an nByte parameter that -** is equal to the number of bytes in the input string including -** the nul-terminator bytes as this saves SQLite from having to -** make a copy of the input string. +** ^If the nByte argument is negative, then zSql is read up to the +** first zero terminator. ^If nByte is positive, then it is the +** number of bytes read from zSql. ^If nByte is zero, then no prepared +** statement is generated. +** If the caller knows that the supplied string is nul-terminated, then +** there is a small performance advantage to passing an nByte parameter that +** is the number of bytes in the input string including +** the nul-terminator. ** ** ^If pzTail is not NULL then *pzTail is made to point to the first byte ** past the end of the first SQL statement in zSql. These routines only @@ -3301,28 +3535,28 @@ SQLITE_API int sqlite3_limit(sqlite3*, int id, int newVal); **
  • ** */ -SQLITE_API int sqlite3_prepare( +SQLITE_API int SQLITE_STDCALL sqlite3_prepare( sqlite3 *db, /* Database handle */ const char *zSql, /* SQL statement, UTF-8 encoded */ int nByte, /* Maximum length of zSql in bytes. */ sqlite3_stmt **ppStmt, /* OUT: Statement handle */ const char **pzTail /* OUT: Pointer to unused portion of zSql */ ); -SQLITE_API int sqlite3_prepare_v2( +SQLITE_API int SQLITE_STDCALL sqlite3_prepare_v2( sqlite3 *db, /* Database handle */ const char *zSql, /* SQL statement, UTF-8 encoded */ int nByte, /* Maximum length of zSql in bytes. */ sqlite3_stmt **ppStmt, /* OUT: Statement handle */ const char **pzTail /* OUT: Pointer to unused portion of zSql */ ); -SQLITE_API int sqlite3_prepare16( +SQLITE_API int SQLITE_STDCALL sqlite3_prepare16( sqlite3 *db, /* Database handle */ const void *zSql, /* SQL statement, UTF-16 encoded */ int nByte, /* Maximum length of zSql in bytes. */ sqlite3_stmt **ppStmt, /* OUT: Statement handle */ const void **pzTail /* OUT: Pointer to unused portion of zSql */ ); -SQLITE_API int sqlite3_prepare16_v2( +SQLITE_API int SQLITE_STDCALL sqlite3_prepare16_v2( sqlite3 *db, /* Database handle */ const void *zSql, /* SQL statement, UTF-16 encoded */ int nByte, /* Maximum length of zSql in bytes. */ @@ -3332,15 +3566,17 @@ SQLITE_API int sqlite3_prepare16_v2( /* ** CAPI3REF: Retrieving Statement SQL +** METHOD: sqlite3_stmt ** ** ^This interface can be used to retrieve a saved copy of the original ** SQL text used to create a [prepared statement] if that statement was ** compiled using either [sqlite3_prepare_v2()] or [sqlite3_prepare16_v2()]. */ -SQLITE_API const char *sqlite3_sql(sqlite3_stmt *pStmt); +SQLITE_API const char *SQLITE_STDCALL sqlite3_sql(sqlite3_stmt *pStmt); /* ** CAPI3REF: Determine If An SQL Statement Writes The Database +** METHOD: sqlite3_stmt ** ** ^The sqlite3_stmt_readonly(X) interface returns true (non-zero) if ** and only if the [prepared statement] X makes no direct changes to @@ -3368,14 +3604,16 @@ SQLITE_API const char *sqlite3_sql(sqlite3_stmt *pStmt); ** change the configuration of a database connection, they do not make ** changes to the content of the database files on disk. */ -SQLITE_API int sqlite3_stmt_readonly(sqlite3_stmt *pStmt); +SQLITE_API int SQLITE_STDCALL sqlite3_stmt_readonly(sqlite3_stmt *pStmt); /* ** CAPI3REF: Determine If A Prepared Statement Has Been Reset +** METHOD: sqlite3_stmt ** ** ^The sqlite3_stmt_busy(S) interface returns true (non-zero) if the ** [prepared statement] S has been stepped at least once using -** [sqlite3_step(S)] but has not run to completion and/or has not +** [sqlite3_step(S)] but has neither run to completion (returned +** [SQLITE_DONE] from [sqlite3_step(S)]) nor ** been reset using [sqlite3_reset(S)]. ^The sqlite3_stmt_busy(S) ** interface returns false if S is a NULL pointer. If S is not a ** NULL pointer and is not a pointer to a valid [prepared statement] @@ -3387,7 +3625,7 @@ SQLITE_API int sqlite3_stmt_readonly(sqlite3_stmt *pStmt); ** for example, in diagnostic routines to search for prepared ** statements that are holding a transaction open. */ -SQLITE_API int sqlite3_stmt_busy(sqlite3_stmt*); +SQLITE_API int SQLITE_STDCALL sqlite3_stmt_busy(sqlite3_stmt*); /* ** CAPI3REF: Dynamically Typed Value Object @@ -3402,7 +3640,9 @@ SQLITE_API int sqlite3_stmt_busy(sqlite3_stmt*); ** Some interfaces require a protected sqlite3_value. Other interfaces ** will accept either a protected or an unprotected sqlite3_value. ** Every interface that accepts sqlite3_value arguments specifies -** whether or not it requires a protected sqlite3_value. +** whether or not it requires a protected sqlite3_value. The +** [sqlite3_value_dup()] interface can be used to construct a new +** protected sqlite3_value from an unprotected sqlite3_value. ** ** The terms "protected" and "unprotected" refer to whether or not ** a mutex is held. An internal mutex is held for a protected @@ -3446,6 +3686,7 @@ typedef struct sqlite3_context sqlite3_context; ** CAPI3REF: Binding Values To Prepared Statements ** KEYWORDS: {host parameter} {host parameters} {host parameter name} ** KEYWORDS: {SQL parameter} {SQL parameters} {parameter binding} +** METHOD: sqlite3_stmt ** ** ^(In the SQL statement text input to [sqlite3_prepare_v2()] and its variants, ** literals may be replaced by a [parameter] that matches one of following @@ -3492,18 +3733,18 @@ typedef struct sqlite3_context sqlite3_context; ** If the fourth parameter to sqlite3_bind_blob() is negative, then ** the behavior is undefined. ** If a non-negative fourth parameter is provided to sqlite3_bind_text() -** or sqlite3_bind_text16() then that parameter must be the byte offset +** or sqlite3_bind_text16() or sqlite3_bind_text64() then +** that parameter must be the byte offset ** where the NUL terminator would occur assuming the string were NUL ** terminated. If any NUL characters occur at byte offsets less than ** the value of the fourth parameter then the resulting string value will ** contain embedded NULs. The result of expressions involving strings ** with embedded NULs is undefined. ** -** ^The fifth argument to sqlite3_bind_blob(), sqlite3_bind_text(), and -** sqlite3_bind_text16() is a destructor used to dispose of the BLOB or +** ^The fifth argument to the BLOB and string binding interfaces +** is a destructor used to dispose of the BLOB or ** string after SQLite has finished with it. ^The destructor is called -** to dispose of the BLOB or string even if the call to sqlite3_bind_blob(), -** sqlite3_bind_text(), or sqlite3_bind_text16() fails. +** to dispose of the BLOB or string even if the call to bind API fails. ** ^If the fifth argument is ** the special value [SQLITE_STATIC], then SQLite assumes that the ** information is in static, unmanaged space and does not need to be freed. @@ -3511,6 +3752,14 @@ typedef struct sqlite3_context sqlite3_context; ** SQLite makes its own private copy of the data immediately, before ** the sqlite3_bind_*() routine returns. ** +** ^The sixth argument to sqlite3_bind_text64() must be one of +** [SQLITE_UTF8], [SQLITE_UTF16], [SQLITE_UTF16BE], or [SQLITE_UTF16LE] +** to specify the encoding of the text in the third parameter. If +** the sixth argument to sqlite3_bind_text64() is not one of the +** allowed values shown above, or if the text encoding is different +** from the encoding specified by the sixth parameter, then the behavior +** is undefined. +** ** ^The sqlite3_bind_zeroblob() routine binds a BLOB of length N that ** is filled with zeroes. ^A zeroblob uses a fixed amount of memory ** (just an integer to hold its size) while it is being processed. @@ -3531,24 +3780,33 @@ typedef struct sqlite3_context sqlite3_context; ** ** ^The sqlite3_bind_* routines return [SQLITE_OK] on success or an ** [error code] if anything goes wrong. +** ^[SQLITE_TOOBIG] might be returned if the size of a string or BLOB +** exceeds limits imposed by [sqlite3_limit]([SQLITE_LIMIT_LENGTH]) or +** [SQLITE_MAX_LENGTH]. ** ^[SQLITE_RANGE] is returned if the parameter ** index is out of range. ^[SQLITE_NOMEM] is returned if malloc() fails. ** ** See also: [sqlite3_bind_parameter_count()], ** [sqlite3_bind_parameter_name()], and [sqlite3_bind_parameter_index()]. */ -SQLITE_API int sqlite3_bind_blob(sqlite3_stmt*, int, const void*, int n, void(*)(void*)); -SQLITE_API int sqlite3_bind_double(sqlite3_stmt*, int, double); -SQLITE_API int sqlite3_bind_int(sqlite3_stmt*, int, int); -SQLITE_API int sqlite3_bind_int64(sqlite3_stmt*, int, sqlite3_int64); -SQLITE_API int sqlite3_bind_null(sqlite3_stmt*, int); -SQLITE_API int sqlite3_bind_text(sqlite3_stmt*, int, const char*, int n, void(*)(void*)); -SQLITE_API int sqlite3_bind_text16(sqlite3_stmt*, int, const void*, int, void(*)(void*)); -SQLITE_API int sqlite3_bind_value(sqlite3_stmt*, int, const sqlite3_value*); -SQLITE_API int sqlite3_bind_zeroblob(sqlite3_stmt*, int, int n); +SQLITE_API int SQLITE_STDCALL sqlite3_bind_blob(sqlite3_stmt*, int, const void*, int n, void(*)(void*)); +SQLITE_API int SQLITE_STDCALL sqlite3_bind_blob64(sqlite3_stmt*, int, const void*, sqlite3_uint64, + void(*)(void*)); +SQLITE_API int SQLITE_STDCALL sqlite3_bind_double(sqlite3_stmt*, int, double); +SQLITE_API int SQLITE_STDCALL sqlite3_bind_int(sqlite3_stmt*, int, int); +SQLITE_API int SQLITE_STDCALL sqlite3_bind_int64(sqlite3_stmt*, int, sqlite3_int64); +SQLITE_API int SQLITE_STDCALL sqlite3_bind_null(sqlite3_stmt*, int); +SQLITE_API int SQLITE_STDCALL sqlite3_bind_text(sqlite3_stmt*,int,const char*,int,void(*)(void*)); +SQLITE_API int SQLITE_STDCALL sqlite3_bind_text16(sqlite3_stmt*, int, const void*, int, void(*)(void*)); +SQLITE_API int SQLITE_STDCALL sqlite3_bind_text64(sqlite3_stmt*, int, const char*, sqlite3_uint64, + void(*)(void*), unsigned char encoding); +SQLITE_API int SQLITE_STDCALL sqlite3_bind_value(sqlite3_stmt*, int, const sqlite3_value*); +SQLITE_API int SQLITE_STDCALL sqlite3_bind_zeroblob(sqlite3_stmt*, int, int n); +SQLITE_API int SQLITE_STDCALL sqlite3_bind_zeroblob64(sqlite3_stmt*, int, sqlite3_uint64); /* ** CAPI3REF: Number Of SQL Parameters +** METHOD: sqlite3_stmt ** ** ^This routine can be used to find the number of [SQL parameters] ** in a [prepared statement]. SQL parameters are tokens of the @@ -3565,10 +3823,11 @@ SQLITE_API int sqlite3_bind_zeroblob(sqlite3_stmt*, int, int n); ** [sqlite3_bind_parameter_name()], and ** [sqlite3_bind_parameter_index()]. */ -SQLITE_API int sqlite3_bind_parameter_count(sqlite3_stmt*); +SQLITE_API int SQLITE_STDCALL sqlite3_bind_parameter_count(sqlite3_stmt*); /* ** CAPI3REF: Name Of A Host Parameter +** METHOD: sqlite3_stmt ** ** ^The sqlite3_bind_parameter_name(P,N) interface returns ** the name of the N-th [SQL parameter] in the [prepared statement] P. @@ -3592,10 +3851,11 @@ SQLITE_API int sqlite3_bind_parameter_count(sqlite3_stmt*); ** [sqlite3_bind_parameter_count()], and ** [sqlite3_bind_parameter_index()]. */ -SQLITE_API const char *sqlite3_bind_parameter_name(sqlite3_stmt*, int); +SQLITE_API const char *SQLITE_STDCALL sqlite3_bind_parameter_name(sqlite3_stmt*, int); /* ** CAPI3REF: Index Of A Parameter With A Given Name +** METHOD: sqlite3_stmt ** ** ^Return the index of an SQL parameter given its name. ^The ** index value returned is suitable for use as the second @@ -3606,21 +3866,23 @@ SQLITE_API const char *sqlite3_bind_parameter_name(sqlite3_stmt*, int); ** ** See also: [sqlite3_bind_blob|sqlite3_bind()], ** [sqlite3_bind_parameter_count()], and -** [sqlite3_bind_parameter_index()]. +** [sqlite3_bind_parameter_name()]. */ -SQLITE_API int sqlite3_bind_parameter_index(sqlite3_stmt*, const char *zName); +SQLITE_API int SQLITE_STDCALL sqlite3_bind_parameter_index(sqlite3_stmt*, const char *zName); /* ** CAPI3REF: Reset All Bindings On A Prepared Statement +** METHOD: sqlite3_stmt ** ** ^Contrary to the intuition of many, [sqlite3_reset()] does not reset ** the [sqlite3_bind_blob | bindings] on a [prepared statement]. ** ^Use this routine to reset all host parameters to NULL. */ -SQLITE_API int sqlite3_clear_bindings(sqlite3_stmt*); +SQLITE_API int SQLITE_STDCALL sqlite3_clear_bindings(sqlite3_stmt*); /* ** CAPI3REF: Number Of Columns In A Result Set +** METHOD: sqlite3_stmt ** ** ^Return the number of columns in the result set returned by the ** [prepared statement]. ^This routine returns 0 if pStmt is an SQL @@ -3628,10 +3890,11 @@ SQLITE_API int sqlite3_clear_bindings(sqlite3_stmt*); ** ** See also: [sqlite3_data_count()] */ -SQLITE_API int sqlite3_column_count(sqlite3_stmt *pStmt); +SQLITE_API int SQLITE_STDCALL sqlite3_column_count(sqlite3_stmt *pStmt); /* ** CAPI3REF: Column Names In A Result Set +** METHOD: sqlite3_stmt ** ** ^These routines return the name assigned to a particular column ** in the result set of a [SELECT] statement. ^The sqlite3_column_name() @@ -3656,11 +3919,12 @@ SQLITE_API int sqlite3_column_count(sqlite3_stmt *pStmt); ** then the name of the column is unspecified and may change from ** one release of SQLite to the next. */ -SQLITE_API const char *sqlite3_column_name(sqlite3_stmt*, int N); -SQLITE_API const void *sqlite3_column_name16(sqlite3_stmt*, int N); +SQLITE_API const char *SQLITE_STDCALL sqlite3_column_name(sqlite3_stmt*, int N); +SQLITE_API const void *SQLITE_STDCALL sqlite3_column_name16(sqlite3_stmt*, int N); /* ** CAPI3REF: Source Of Data In A Query Result +** METHOD: sqlite3_stmt ** ** ^These routines provide a means to determine the database, table, and ** table column that is the origin of a particular result column in @@ -3704,15 +3968,16 @@ SQLITE_API const void *sqlite3_column_name16(sqlite3_stmt*, int N); ** for the same [prepared statement] and result column ** at the same time then the results are undefined. */ -SQLITE_API const char *sqlite3_column_database_name(sqlite3_stmt*,int); -SQLITE_API const void *sqlite3_column_database_name16(sqlite3_stmt*,int); -SQLITE_API const char *sqlite3_column_table_name(sqlite3_stmt*,int); -SQLITE_API const void *sqlite3_column_table_name16(sqlite3_stmt*,int); -SQLITE_API const char *sqlite3_column_origin_name(sqlite3_stmt*,int); -SQLITE_API const void *sqlite3_column_origin_name16(sqlite3_stmt*,int); +SQLITE_API const char *SQLITE_STDCALL sqlite3_column_database_name(sqlite3_stmt*,int); +SQLITE_API const void *SQLITE_STDCALL sqlite3_column_database_name16(sqlite3_stmt*,int); +SQLITE_API const char *SQLITE_STDCALL sqlite3_column_table_name(sqlite3_stmt*,int); +SQLITE_API const void *SQLITE_STDCALL sqlite3_column_table_name16(sqlite3_stmt*,int); +SQLITE_API const char *SQLITE_STDCALL sqlite3_column_origin_name(sqlite3_stmt*,int); +SQLITE_API const void *SQLITE_STDCALL sqlite3_column_origin_name16(sqlite3_stmt*,int); /* ** CAPI3REF: Declared Datatype Of A Query Result +** METHOD: sqlite3_stmt ** ** ^(The first parameter is a [prepared statement]. ** If this statement is a [SELECT] statement and the Nth column of the @@ -3740,11 +4005,12 @@ SQLITE_API const void *sqlite3_column_origin_name16(sqlite3_stmt*,int); ** is associated with individual values, not with the containers ** used to hold those values. */ -SQLITE_API const char *sqlite3_column_decltype(sqlite3_stmt*,int); -SQLITE_API const void *sqlite3_column_decltype16(sqlite3_stmt*,int); +SQLITE_API const char *SQLITE_STDCALL sqlite3_column_decltype(sqlite3_stmt*,int); +SQLITE_API const void *SQLITE_STDCALL sqlite3_column_decltype16(sqlite3_stmt*,int); /* ** CAPI3REF: Evaluate An SQL Statement +** METHOD: sqlite3_stmt ** ** After a [prepared statement] has been prepared using either ** [sqlite3_prepare_v2()] or [sqlite3_prepare16_v2()] or one of the legacy @@ -3820,10 +4086,11 @@ SQLITE_API const void *sqlite3_column_decltype16(sqlite3_stmt*,int); ** then the more specific [error codes] are returned directly ** by sqlite3_step(). The use of the "v2" interface is recommended. */ -SQLITE_API int sqlite3_step(sqlite3_stmt*); +SQLITE_API int SQLITE_STDCALL sqlite3_step(sqlite3_stmt*); /* ** CAPI3REF: Number of columns in a result set +** METHOD: sqlite3_stmt ** ** ^The sqlite3_data_count(P) interface returns the number of columns in the ** current row of the result set of [prepared statement] P. @@ -3840,7 +4107,7 @@ SQLITE_API int sqlite3_step(sqlite3_stmt*); ** ** See also: [sqlite3_column_count()] */ -SQLITE_API int sqlite3_data_count(sqlite3_stmt *pStmt); +SQLITE_API int SQLITE_STDCALL sqlite3_data_count(sqlite3_stmt *pStmt); /* ** CAPI3REF: Fundamental Datatypes @@ -3877,8 +4144,7 @@ SQLITE_API int sqlite3_data_count(sqlite3_stmt *pStmt); /* ** CAPI3REF: Result Values From A Query ** KEYWORDS: {column access functions} -** -** These routines form the "result set" interface. +** METHOD: sqlite3_stmt ** ** ^These routines return information about a single column of the current ** result row of a query. ^In every case the first argument is a pointer @@ -3939,13 +4205,14 @@ SQLITE_API int sqlite3_data_count(sqlite3_stmt *pStmt); ** even empty strings, are always zero-terminated. ^The return ** value from sqlite3_column_blob() for a zero-length BLOB is a NULL pointer. ** -** ^The object returned by [sqlite3_column_value()] is an -** [unprotected sqlite3_value] object. An unprotected sqlite3_value object -** may only be used with [sqlite3_bind_value()] and [sqlite3_result_value()]. +** Warning: ^The object returned by [sqlite3_column_value()] is an +** [unprotected sqlite3_value] object. In a multithreaded environment, +** an unprotected sqlite3_value object may only be used safely with +** [sqlite3_bind_value()] and [sqlite3_result_value()]. ** If the [unprotected sqlite3_value] object returned by ** [sqlite3_column_value()] is used in any other way, including calls ** to routines like [sqlite3_value_int()], [sqlite3_value_text()], -** or [sqlite3_value_bytes()], then the behavior is undefined. +** or [sqlite3_value_bytes()], the behavior is not threadsafe. ** ** These routines attempt to convert the value where appropriate. ^For ** example, if the internal representation is FLOAT and a text result @@ -3976,12 +4243,6 @@ SQLITE_API int sqlite3_data_count(sqlite3_stmt *pStmt); ** **
)^ ** -** The table above makes reference to standard C library functions atoi() -** and atof(). SQLite does not really use these functions. It has its -** own equivalent internal routines. The atoi() and atof() names are -** used in the table for brevity and because they are familiar to most -** C programmers. -** ** Note that when type conversions occur, pointers returned by prior ** calls to sqlite3_column_blob(), sqlite3_column_text(), and/or ** sqlite3_column_text16() may be invalidated. @@ -4006,7 +4267,7 @@ SQLITE_API int sqlite3_data_count(sqlite3_stmt *pStmt); ** of conversion are done in place when it is possible, but sometimes they ** are not possible and in those cases prior pointers are invalidated. ** -** The safest and easiest to remember policy is to invoke these routines +** The safest policy is to invoke these routines ** in one of the following ways: ** **
    @@ -4026,7 +4287,7 @@ SQLITE_API int sqlite3_data_count(sqlite3_stmt *pStmt); ** ^The pointers returned are valid until a type conversion occurs as ** described above, or until [sqlite3_step()] or [sqlite3_reset()] or ** [sqlite3_finalize()] is called. ^The memory space used to hold strings -** and BLOBs is freed automatically. Do not pass the pointers returned +** and BLOBs is freed automatically. Do not pass the pointers returned ** from [sqlite3_column_blob()], [sqlite3_column_text()], etc. into ** [sqlite3_free()]. ** @@ -4036,19 +4297,20 @@ SQLITE_API int sqlite3_data_count(sqlite3_stmt *pStmt); ** pointer. Subsequent calls to [sqlite3_errcode()] will return ** [SQLITE_NOMEM].)^ */ -SQLITE_API const void *sqlite3_column_blob(sqlite3_stmt*, int iCol); -SQLITE_API int sqlite3_column_bytes(sqlite3_stmt*, int iCol); -SQLITE_API int sqlite3_column_bytes16(sqlite3_stmt*, int iCol); -SQLITE_API double sqlite3_column_double(sqlite3_stmt*, int iCol); -SQLITE_API int sqlite3_column_int(sqlite3_stmt*, int iCol); -SQLITE_API sqlite3_int64 sqlite3_column_int64(sqlite3_stmt*, int iCol); -SQLITE_API const unsigned char *sqlite3_column_text(sqlite3_stmt*, int iCol); -SQLITE_API const void *sqlite3_column_text16(sqlite3_stmt*, int iCol); -SQLITE_API int sqlite3_column_type(sqlite3_stmt*, int iCol); -SQLITE_API sqlite3_value *sqlite3_column_value(sqlite3_stmt*, int iCol); +SQLITE_API const void *SQLITE_STDCALL sqlite3_column_blob(sqlite3_stmt*, int iCol); +SQLITE_API int SQLITE_STDCALL sqlite3_column_bytes(sqlite3_stmt*, int iCol); +SQLITE_API int SQLITE_STDCALL sqlite3_column_bytes16(sqlite3_stmt*, int iCol); +SQLITE_API double SQLITE_STDCALL sqlite3_column_double(sqlite3_stmt*, int iCol); +SQLITE_API int SQLITE_STDCALL sqlite3_column_int(sqlite3_stmt*, int iCol); +SQLITE_API sqlite3_int64 SQLITE_STDCALL sqlite3_column_int64(sqlite3_stmt*, int iCol); +SQLITE_API const unsigned char *SQLITE_STDCALL sqlite3_column_text(sqlite3_stmt*, int iCol); +SQLITE_API const void *SQLITE_STDCALL sqlite3_column_text16(sqlite3_stmt*, int iCol); +SQLITE_API int SQLITE_STDCALL sqlite3_column_type(sqlite3_stmt*, int iCol); +SQLITE_API sqlite3_value *SQLITE_STDCALL sqlite3_column_value(sqlite3_stmt*, int iCol); /* ** CAPI3REF: Destroy A Prepared Statement Object +** DESTRUCTOR: sqlite3_stmt ** ** ^The sqlite3_finalize() function is called to delete a [prepared statement]. ** ^If the most recent evaluation of the statement encountered no errors @@ -4072,10 +4334,11 @@ SQLITE_API sqlite3_value *sqlite3_column_value(sqlite3_stmt*, int iCol); ** statement after it has been finalized can result in undefined and ** undesirable behavior such as segfaults and heap corruption. */ -SQLITE_API int sqlite3_finalize(sqlite3_stmt *pStmt); +SQLITE_API int SQLITE_STDCALL sqlite3_finalize(sqlite3_stmt *pStmt); /* ** CAPI3REF: Reset A Prepared Statement Object +** METHOD: sqlite3_stmt ** ** The sqlite3_reset() function is called to reset a [prepared statement] ** object back to its initial state, ready to be re-executed. @@ -4098,13 +4361,14 @@ SQLITE_API int sqlite3_finalize(sqlite3_stmt *pStmt); ** ^The [sqlite3_reset(S)] interface does not change the values ** of any [sqlite3_bind_blob|bindings] on the [prepared statement] S. */ -SQLITE_API int sqlite3_reset(sqlite3_stmt *pStmt); +SQLITE_API int SQLITE_STDCALL sqlite3_reset(sqlite3_stmt *pStmt); /* ** CAPI3REF: Create Or Redefine SQL Functions ** KEYWORDS: {function creation routines} ** KEYWORDS: {application-defined SQL function} ** KEYWORDS: {application-defined SQL functions} +** METHOD: sqlite3 ** ** ^These functions (collectively known as "function creation routines") ** are used to add SQL functions or aggregates or to redefine the behavior @@ -4197,7 +4461,7 @@ SQLITE_API int sqlite3_reset(sqlite3_stmt *pStmt); ** close the database connection nor finalize or reset the prepared ** statement in which the function is running. */ -SQLITE_API int sqlite3_create_function( +SQLITE_API int SQLITE_STDCALL sqlite3_create_function( sqlite3 *db, const char *zFunctionName, int nArg, @@ -4207,7 +4471,7 @@ SQLITE_API int sqlite3_create_function( void (*xStep)(sqlite3_context*,int,sqlite3_value**), void (*xFinal)(sqlite3_context*) ); -SQLITE_API int sqlite3_create_function16( +SQLITE_API int SQLITE_STDCALL sqlite3_create_function16( sqlite3 *db, const void *zFunctionName, int nArg, @@ -4217,7 +4481,7 @@ SQLITE_API int sqlite3_create_function16( void (*xStep)(sqlite3_context*,int,sqlite3_value**), void (*xFinal)(sqlite3_context*) ); -SQLITE_API int sqlite3_create_function_v2( +SQLITE_API int SQLITE_STDCALL sqlite3_create_function_v2( sqlite3 *db, const char *zFunctionName, int nArg, @@ -4235,9 +4499,9 @@ SQLITE_API int sqlite3_create_function_v2( ** These constant define integer codes that represent the various ** text encodings supported by SQLite. */ -#define SQLITE_UTF8 1 -#define SQLITE_UTF16LE 2 -#define SQLITE_UTF16BE 3 +#define SQLITE_UTF8 1 /* IMP: R-37514-35566 */ +#define SQLITE_UTF16LE 2 /* IMP: R-03371-37637 */ +#define SQLITE_UTF16BE 3 /* IMP: R-51971-34154 */ #define SQLITE_UTF16 4 /* Use native byte order */ #define SQLITE_ANY 5 /* Deprecated */ #define SQLITE_UTF16_ALIGNED 8 /* sqlite3_create_collation only */ @@ -4259,25 +4523,26 @@ SQLITE_API int sqlite3_create_function_v2( ** These functions are [deprecated]. In order to maintain ** backwards compatibility with older code, these functions continue ** to be supported. However, new applications should avoid -** the use of these functions. To help encourage people to avoid -** using these functions, we are not going to tell you what they do. +** the use of these functions. To encourage programmers to avoid +** these functions, we will not explain what they do. */ #ifndef SQLITE_OMIT_DEPRECATED -SQLITE_API SQLITE_DEPRECATED int sqlite3_aggregate_count(sqlite3_context*); -SQLITE_API SQLITE_DEPRECATED int sqlite3_expired(sqlite3_stmt*); -SQLITE_API SQLITE_DEPRECATED int sqlite3_transfer_bindings(sqlite3_stmt*, sqlite3_stmt*); -SQLITE_API SQLITE_DEPRECATED int sqlite3_global_recover(void); -SQLITE_API SQLITE_DEPRECATED void sqlite3_thread_cleanup(void); -SQLITE_API SQLITE_DEPRECATED int sqlite3_memory_alarm(void(*)(void*,sqlite3_int64,int), +SQLITE_API SQLITE_DEPRECATED int SQLITE_STDCALL sqlite3_aggregate_count(sqlite3_context*); +SQLITE_API SQLITE_DEPRECATED int SQLITE_STDCALL sqlite3_expired(sqlite3_stmt*); +SQLITE_API SQLITE_DEPRECATED int SQLITE_STDCALL sqlite3_transfer_bindings(sqlite3_stmt*, sqlite3_stmt*); +SQLITE_API SQLITE_DEPRECATED int SQLITE_STDCALL sqlite3_global_recover(void); +SQLITE_API SQLITE_DEPRECATED void SQLITE_STDCALL sqlite3_thread_cleanup(void); +SQLITE_API SQLITE_DEPRECATED int SQLITE_STDCALL sqlite3_memory_alarm(void(*)(void*,sqlite3_int64,int), void*,sqlite3_int64); #endif /* -** CAPI3REF: Obtaining SQL Function Parameter Values +** CAPI3REF: Obtaining SQL Values +** METHOD: sqlite3_value ** ** The C-language implementation of SQL functions and aggregates uses ** this set of interface routines to access the parameter values on -** the function or aggregate. +** the function or aggregate. ** ** The xFunc (for scalar functions) or xStep (for aggregates) parameters ** to [sqlite3_create_function()] and [sqlite3_create_function16()] @@ -4292,7 +4557,7 @@ SQLITE_API SQLITE_DEPRECATED int sqlite3_memory_alarm(void(*)(void*,sqlite3_int6 ** object results in undefined behavior. ** ** ^These routines work just like the corresponding [column access functions] -** except that these routines take a single [protected sqlite3_value] object +** except that these routines take a single [protected sqlite3_value] object ** pointer instead of a [sqlite3_stmt*] pointer and an integer column number. ** ** ^The sqlite3_value_text16() interface extracts a UTF-16 string @@ -4317,21 +4582,55 @@ SQLITE_API SQLITE_DEPRECATED int sqlite3_memory_alarm(void(*)(void*,sqlite3_int6 ** These routines must be called from the same thread as ** the SQL function that supplied the [sqlite3_value*] parameters. */ -SQLITE_API const void *sqlite3_value_blob(sqlite3_value*); -SQLITE_API int sqlite3_value_bytes(sqlite3_value*); -SQLITE_API int sqlite3_value_bytes16(sqlite3_value*); -SQLITE_API double sqlite3_value_double(sqlite3_value*); -SQLITE_API int sqlite3_value_int(sqlite3_value*); -SQLITE_API sqlite3_int64 sqlite3_value_int64(sqlite3_value*); -SQLITE_API const unsigned char *sqlite3_value_text(sqlite3_value*); -SQLITE_API const void *sqlite3_value_text16(sqlite3_value*); -SQLITE_API const void *sqlite3_value_text16le(sqlite3_value*); -SQLITE_API const void *sqlite3_value_text16be(sqlite3_value*); -SQLITE_API int sqlite3_value_type(sqlite3_value*); -SQLITE_API int sqlite3_value_numeric_type(sqlite3_value*); +SQLITE_API const void *SQLITE_STDCALL sqlite3_value_blob(sqlite3_value*); +SQLITE_API int SQLITE_STDCALL sqlite3_value_bytes(sqlite3_value*); +SQLITE_API int SQLITE_STDCALL sqlite3_value_bytes16(sqlite3_value*); +SQLITE_API double SQLITE_STDCALL sqlite3_value_double(sqlite3_value*); +SQLITE_API int SQLITE_STDCALL sqlite3_value_int(sqlite3_value*); +SQLITE_API sqlite3_int64 SQLITE_STDCALL sqlite3_value_int64(sqlite3_value*); +SQLITE_API const unsigned char *SQLITE_STDCALL sqlite3_value_text(sqlite3_value*); +SQLITE_API const void *SQLITE_STDCALL sqlite3_value_text16(sqlite3_value*); +SQLITE_API const void *SQLITE_STDCALL sqlite3_value_text16le(sqlite3_value*); +SQLITE_API const void *SQLITE_STDCALL sqlite3_value_text16be(sqlite3_value*); +SQLITE_API int SQLITE_STDCALL sqlite3_value_type(sqlite3_value*); +SQLITE_API int SQLITE_STDCALL sqlite3_value_numeric_type(sqlite3_value*); + +/* +** CAPI3REF: Finding The Subtype Of SQL Values +** METHOD: sqlite3_value +** +** The sqlite3_value_subtype(V) function returns the subtype for +** an [application-defined SQL function] argument V. The subtype +** information can be used to pass a limited amount of context from +** one SQL function to another. Use the [sqlite3_result_subtype()] +** routine to set the subtype for the return value of an SQL function. +** +** SQLite makes no use of subtype itself. It merely passes the subtype +** from the result of one [application-defined SQL function] into the +** input of another. +*/ +SQLITE_API unsigned int SQLITE_STDCALL sqlite3_value_subtype(sqlite3_value*); + +/* +** CAPI3REF: Copy And Free SQL Values +** METHOD: sqlite3_value +** +** ^The sqlite3_value_dup(V) interface makes a copy of the [sqlite3_value] +** object D and returns a pointer to that copy. ^The [sqlite3_value] returned +** is a [protected sqlite3_value] object even if the input is not. +** ^The sqlite3_value_dup(V) interface returns NULL if V is NULL or if a +** memory allocation fails. +** +** ^The sqlite3_value_free(V) interface frees an [sqlite3_value] object +** previously obtained from [sqlite3_value_dup()]. ^If V is a NULL pointer +** then sqlite3_value_free(V) is a harmless no-op. +*/ +SQLITE_API sqlite3_value *SQLITE_STDCALL sqlite3_value_dup(const sqlite3_value*); +SQLITE_API void SQLITE_STDCALL sqlite3_value_free(sqlite3_value*); /* ** CAPI3REF: Obtain Aggregate Function Context +** METHOD: sqlite3_context ** ** Implementations of aggregate SQL functions use this ** routine to allocate memory for storing their state. @@ -4372,10 +4671,11 @@ SQLITE_API int sqlite3_value_numeric_type(sqlite3_value*); ** This routine must be called from the same thread in which ** the aggregate SQL function is running. */ -SQLITE_API void *sqlite3_aggregate_context(sqlite3_context*, int nBytes); +SQLITE_API void *SQLITE_STDCALL sqlite3_aggregate_context(sqlite3_context*, int nBytes); /* ** CAPI3REF: User Data For Functions +** METHOD: sqlite3_context ** ** ^The sqlite3_user_data() interface returns a copy of ** the pointer that was the pUserData parameter (the 5th parameter) @@ -4386,10 +4686,11 @@ SQLITE_API void *sqlite3_aggregate_context(sqlite3_context*, int nBytes); ** This routine must be called from the same thread in which ** the application-defined function is running. */ -SQLITE_API void *sqlite3_user_data(sqlite3_context*); +SQLITE_API void *SQLITE_STDCALL sqlite3_user_data(sqlite3_context*); /* ** CAPI3REF: Database Connection For Functions +** METHOD: sqlite3_context ** ** ^The sqlite3_context_db_handle() interface returns a copy of ** the pointer to the [database connection] (the 1st parameter) @@ -4397,10 +4698,11 @@ SQLITE_API void *sqlite3_user_data(sqlite3_context*); ** and [sqlite3_create_function16()] routines that originally ** registered the application defined function. */ -SQLITE_API sqlite3 *sqlite3_context_db_handle(sqlite3_context*); +SQLITE_API sqlite3 *SQLITE_STDCALL sqlite3_context_db_handle(sqlite3_context*); /* ** CAPI3REF: Function Auxiliary Data +** METHOD: sqlite3_context ** ** These functions may be used by (non-aggregate) SQL functions to ** associate metadata with argument values. If the same value is passed to @@ -4449,8 +4751,8 @@ SQLITE_API sqlite3 *sqlite3_context_db_handle(sqlite3_context*); ** These routines must be called from the same thread in which ** the SQL function is running. */ -SQLITE_API void *sqlite3_get_auxdata(sqlite3_context*, int N); -SQLITE_API void sqlite3_set_auxdata(sqlite3_context*, int N, void*, void (*)(void*)); +SQLITE_API void *SQLITE_STDCALL sqlite3_get_auxdata(sqlite3_context*, int N); +SQLITE_API void SQLITE_STDCALL sqlite3_set_auxdata(sqlite3_context*, int N, void*, void (*)(void*)); /* @@ -4473,6 +4775,7 @@ typedef void (*sqlite3_destructor_type)(void*); /* ** CAPI3REF: Setting The Result Of An SQL Function +** METHOD: sqlite3_context ** ** These routines are used by the xFunc or xFinal callbacks that ** implement SQL functions and aggregates. See @@ -4488,9 +4791,9 @@ typedef void (*sqlite3_destructor_type)(void*); ** to by the second parameter and which is N bytes long where N is the ** third parameter. ** -** ^The sqlite3_result_zeroblob() interfaces set the result of -** the application-defined function to be a BLOB containing all zero -** bytes and N bytes in size, where N is the value of the 2nd parameter. +** ^The sqlite3_result_zeroblob(C,N) and sqlite3_result_zeroblob64(C,N) +** interfaces set the result of the application-defined function to be +** a BLOB containing all zero bytes and N bytes in size. ** ** ^The sqlite3_result_double() interface sets the result from ** an application-defined function to be a floating point value specified @@ -4539,6 +4842,10 @@ typedef void (*sqlite3_destructor_type)(void*); ** set the return value of the application-defined function to be ** a text string which is represented as UTF-8, UTF-16 native byte order, ** UTF-16 little endian, or UTF-16 big endian, respectively. +** ^The sqlite3_result_text64() interface sets the return value of an +** application-defined function to be a text string in an encoding +** specified by the fifth (and last) parameter, which must be one +** of [SQLITE_UTF8], [SQLITE_UTF16], [SQLITE_UTF16BE], or [SQLITE_UTF16LE]. ** ^SQLite takes the text result from the application from ** the 2nd parameter of the sqlite3_result_text* interfaces. ** ^If the 3rd parameter to the sqlite3_result_text* interfaces @@ -4568,7 +4875,7 @@ typedef void (*sqlite3_destructor_type)(void*); ** from [sqlite3_malloc()] before it returns. ** ** ^The sqlite3_result_value() interface sets the result of -** the application-defined function to be a copy the +** the application-defined function to be a copy of the ** [unprotected sqlite3_value] object specified by the 2nd parameter. ^The ** sqlite3_result_value() interface makes a copy of the [sqlite3_value] ** so that the [sqlite3_value] specified in the parameter may change or @@ -4581,25 +4888,46 @@ typedef void (*sqlite3_destructor_type)(void*); ** than the one containing the application-defined function that received ** the [sqlite3_context] pointer, the results are undefined. */ -SQLITE_API void sqlite3_result_blob(sqlite3_context*, const void*, int, void(*)(void*)); -SQLITE_API void sqlite3_result_double(sqlite3_context*, double); -SQLITE_API void sqlite3_result_error(sqlite3_context*, const char*, int); -SQLITE_API void sqlite3_result_error16(sqlite3_context*, const void*, int); -SQLITE_API void sqlite3_result_error_toobig(sqlite3_context*); -SQLITE_API void sqlite3_result_error_nomem(sqlite3_context*); -SQLITE_API void sqlite3_result_error_code(sqlite3_context*, int); -SQLITE_API void sqlite3_result_int(sqlite3_context*, int); -SQLITE_API void sqlite3_result_int64(sqlite3_context*, sqlite3_int64); -SQLITE_API void sqlite3_result_null(sqlite3_context*); -SQLITE_API void sqlite3_result_text(sqlite3_context*, const char*, int, void(*)(void*)); -SQLITE_API void sqlite3_result_text16(sqlite3_context*, const void*, int, void(*)(void*)); -SQLITE_API void sqlite3_result_text16le(sqlite3_context*, const void*, int,void(*)(void*)); -SQLITE_API void sqlite3_result_text16be(sqlite3_context*, const void*, int,void(*)(void*)); -SQLITE_API void sqlite3_result_value(sqlite3_context*, sqlite3_value*); -SQLITE_API void sqlite3_result_zeroblob(sqlite3_context*, int n); +SQLITE_API void SQLITE_STDCALL sqlite3_result_blob(sqlite3_context*, const void*, int, void(*)(void*)); +SQLITE_API void SQLITE_STDCALL sqlite3_result_blob64(sqlite3_context*,const void*, + sqlite3_uint64,void(*)(void*)); +SQLITE_API void SQLITE_STDCALL sqlite3_result_double(sqlite3_context*, double); +SQLITE_API void SQLITE_STDCALL sqlite3_result_error(sqlite3_context*, const char*, int); +SQLITE_API void SQLITE_STDCALL sqlite3_result_error16(sqlite3_context*, const void*, int); +SQLITE_API void SQLITE_STDCALL sqlite3_result_error_toobig(sqlite3_context*); +SQLITE_API void SQLITE_STDCALL sqlite3_result_error_nomem(sqlite3_context*); +SQLITE_API void SQLITE_STDCALL sqlite3_result_error_code(sqlite3_context*, int); +SQLITE_API void SQLITE_STDCALL sqlite3_result_int(sqlite3_context*, int); +SQLITE_API void SQLITE_STDCALL sqlite3_result_int64(sqlite3_context*, sqlite3_int64); +SQLITE_API void SQLITE_STDCALL sqlite3_result_null(sqlite3_context*); +SQLITE_API void SQLITE_STDCALL sqlite3_result_text(sqlite3_context*, const char*, int, void(*)(void*)); +SQLITE_API void SQLITE_STDCALL sqlite3_result_text64(sqlite3_context*, const char*,sqlite3_uint64, + void(*)(void*), unsigned char encoding); +SQLITE_API void SQLITE_STDCALL sqlite3_result_text16(sqlite3_context*, const void*, int, void(*)(void*)); +SQLITE_API void SQLITE_STDCALL sqlite3_result_text16le(sqlite3_context*, const void*, int,void(*)(void*)); +SQLITE_API void SQLITE_STDCALL sqlite3_result_text16be(sqlite3_context*, const void*, int,void(*)(void*)); +SQLITE_API void SQLITE_STDCALL sqlite3_result_value(sqlite3_context*, sqlite3_value*); +SQLITE_API void SQLITE_STDCALL sqlite3_result_zeroblob(sqlite3_context*, int n); +SQLITE_API int SQLITE_STDCALL sqlite3_result_zeroblob64(sqlite3_context*, sqlite3_uint64 n); + + +/* +** CAPI3REF: Setting The Subtype Of An SQL Function +** METHOD: sqlite3_context +** +** The sqlite3_result_subtype(C,T) function causes the subtype of +** the result from the [application-defined SQL function] with +** [sqlite3_context] C to be the value T. Only the lower 8 bits +** of the subtype T are preserved in current versions of SQLite; +** higher order bits are discarded. +** The number of subtype bytes preserved by SQLite might increase +** in future releases of SQLite. +*/ +SQLITE_API void SQLITE_STDCALL sqlite3_result_subtype(sqlite3_context*,unsigned int); /* ** CAPI3REF: Define New Collating Sequences +** METHOD: sqlite3 ** ** ^These functions add, remove, or modify a [collation] associated ** with the [database connection] specified as the first argument. @@ -4677,14 +5005,14 @@ SQLITE_API void sqlite3_result_zeroblob(sqlite3_context*, int n); ** ** See also: [sqlite3_collation_needed()] and [sqlite3_collation_needed16()]. */ -SQLITE_API int sqlite3_create_collation( +SQLITE_API int SQLITE_STDCALL sqlite3_create_collation( sqlite3*, const char *zName, int eTextRep, void *pArg, int(*xCompare)(void*,int,const void*,int,const void*) ); -SQLITE_API int sqlite3_create_collation_v2( +SQLITE_API int SQLITE_STDCALL sqlite3_create_collation_v2( sqlite3*, const char *zName, int eTextRep, @@ -4692,7 +5020,7 @@ SQLITE_API int sqlite3_create_collation_v2( int(*xCompare)(void*,int,const void*,int,const void*), void(*xDestroy)(void*) ); -SQLITE_API int sqlite3_create_collation16( +SQLITE_API int SQLITE_STDCALL sqlite3_create_collation16( sqlite3*, const void *zName, int eTextRep, @@ -4702,6 +5030,7 @@ SQLITE_API int sqlite3_create_collation16( /* ** CAPI3REF: Collation Needed Callbacks +** METHOD: sqlite3 ** ** ^To avoid having to register all collation sequences before a database ** can be used, a single callback function may be registered with the @@ -4726,12 +5055,12 @@ SQLITE_API int sqlite3_create_collation16( ** [sqlite3_create_collation()], [sqlite3_create_collation16()], or ** [sqlite3_create_collation_v2()]. */ -SQLITE_API int sqlite3_collation_needed( +SQLITE_API int SQLITE_STDCALL sqlite3_collation_needed( sqlite3*, void*, void(*)(void*,sqlite3*,int eTextRep,const char*) ); -SQLITE_API int sqlite3_collation_needed16( +SQLITE_API int SQLITE_STDCALL sqlite3_collation_needed16( sqlite3*, void*, void(*)(void*,sqlite3*,int eTextRep,const void*) @@ -4745,11 +5074,11 @@ SQLITE_API int sqlite3_collation_needed16( ** The code to implement this API is not available in the public release ** of SQLite. */ -SQLITE_API int sqlite3_key( +SQLITE_API int SQLITE_STDCALL sqlite3_key( sqlite3 *db, /* Database to be rekeyed */ const void *pKey, int nKey /* The key */ ); -SQLITE_API int sqlite3_key_v2( +SQLITE_API int SQLITE_STDCALL sqlite3_key_v2( sqlite3 *db, /* Database to be rekeyed */ const char *zDbName, /* Name of the database */ const void *pKey, int nKey /* The key */ @@ -4763,11 +5092,11 @@ SQLITE_API int sqlite3_key_v2( ** The code to implement this API is not available in the public release ** of SQLite. */ -SQLITE_API int sqlite3_rekey( +SQLITE_API int SQLITE_STDCALL sqlite3_rekey( sqlite3 *db, /* Database to be rekeyed */ const void *pKey, int nKey /* The new key */ ); -SQLITE_API int sqlite3_rekey_v2( +SQLITE_API int SQLITE_STDCALL sqlite3_rekey_v2( sqlite3 *db, /* Database to be rekeyed */ const char *zDbName, /* Name of the database */ const void *pKey, int nKey /* The new key */ @@ -4777,7 +5106,7 @@ SQLITE_API int sqlite3_rekey_v2( ** Specify the activation key for a SEE database. Unless ** activated, none of the SEE routines will work. */ -SQLITE_API void sqlite3_activate_see( +SQLITE_API void SQLITE_STDCALL sqlite3_activate_see( const char *zPassPhrase /* Activation phrase */ ); #endif @@ -4787,7 +5116,7 @@ SQLITE_API void sqlite3_activate_see( ** Specify the activation key for a CEROD database. Unless ** activated, none of the CEROD routines will work. */ -SQLITE_API void sqlite3_activate_cerod( +SQLITE_API void SQLITE_STDCALL sqlite3_activate_cerod( const char *zPassPhrase /* Activation phrase */ ); #endif @@ -4809,7 +5138,7 @@ SQLITE_API void sqlite3_activate_cerod( ** all, then the behavior of sqlite3_sleep() may deviate from the description ** in the previous paragraphs. */ -SQLITE_API int sqlite3_sleep(int); +SQLITE_API int SQLITE_STDCALL sqlite3_sleep(int); /* ** CAPI3REF: Name Of The Folder Holding Temporary Files @@ -4821,6 +5150,13 @@ SQLITE_API int sqlite3_sleep(int); ** is a NULL pointer, then SQLite performs a search for an appropriate ** temporary file directory. ** +** Applications are strongly discouraged from using this global variable. +** It is required to set a temporary folder on Windows Runtime (WinRT). +** But for all other platforms, it is highly recommended that applications +** neither read nor write this variable. This global variable is a relic +** that exists for backwards compatibility of legacy applications and should +** be avoided in new projects. +** ** It is not safe to read or modify this variable in more than one ** thread at a time. It is not safe to read or modify this variable ** if a [database connection] is being used at the same time in a separate @@ -4839,6 +5175,11 @@ SQLITE_API int sqlite3_sleep(int); ** Hence, if this variable is modified directly, either it should be ** made NULL or made to point to memory obtained from [sqlite3_malloc] ** or else the use of the [temp_store_directory pragma] should be avoided. +** Except when requested by the [temp_store_directory pragma], SQLite +** does not free the memory that sqlite3_temp_directory points to. If +** the application wants that memory to be freed, it must do +** so itself, taking care to only do so after all [database connection] +** objects have been destroyed. ** ** Note to Windows Runtime users: The temporary directory must be set ** prior to calling [sqlite3_open] or [sqlite3_open_v2]. Otherwise, various @@ -4897,6 +5238,7 @@ SQLITE_API char *sqlite3_data_directory; /* ** CAPI3REF: Test For Auto-Commit Mode ** KEYWORDS: {autocommit mode} +** METHOD: sqlite3 ** ** ^The sqlite3_get_autocommit() interface returns non-zero or ** zero if the given database connection is or is not in autocommit mode, @@ -4915,10 +5257,11 @@ SQLITE_API char *sqlite3_data_directory; ** connection while this routine is running, then the return value ** is undefined. */ -SQLITE_API int sqlite3_get_autocommit(sqlite3*); +SQLITE_API int SQLITE_STDCALL sqlite3_get_autocommit(sqlite3*); /* ** CAPI3REF: Find The Database Handle Of A Prepared Statement +** METHOD: sqlite3_stmt ** ** ^The sqlite3_db_handle interface returns the [database connection] handle ** to which a [prepared statement] belongs. ^The [database connection] @@ -4927,10 +5270,11 @@ SQLITE_API int sqlite3_get_autocommit(sqlite3*); ** to the [sqlite3_prepare_v2()] call (or its variants) that was used to ** create the statement in the first place. */ -SQLITE_API sqlite3 *sqlite3_db_handle(sqlite3_stmt*); +SQLITE_API sqlite3 *SQLITE_STDCALL sqlite3_db_handle(sqlite3_stmt*); /* ** CAPI3REF: Return The Filename For A Database Connection +** METHOD: sqlite3 ** ** ^The sqlite3_db_filename(D,N) interface returns a pointer to a filename ** associated with database N of connection D. ^The main database file @@ -4943,19 +5287,21 @@ SQLITE_API sqlite3 *sqlite3_db_handle(sqlite3_stmt*); ** will be an absolute pathname, even if the filename used ** to open the database originally was a URI or relative pathname. */ -SQLITE_API const char *sqlite3_db_filename(sqlite3 *db, const char *zDbName); +SQLITE_API const char *SQLITE_STDCALL sqlite3_db_filename(sqlite3 *db, const char *zDbName); /* ** CAPI3REF: Determine if a database is read-only +** METHOD: sqlite3 ** ** ^The sqlite3_db_readonly(D,N) interface returns 1 if the database N ** of connection D is read-only, 0 if it is read/write, or -1 if N is not ** the name of a database on connection D. */ -SQLITE_API int sqlite3_db_readonly(sqlite3 *db, const char *zDbName); +SQLITE_API int SQLITE_STDCALL sqlite3_db_readonly(sqlite3 *db, const char *zDbName); /* ** CAPI3REF: Find the next prepared statement +** METHOD: sqlite3 ** ** ^This interface returns a pointer to the next [prepared statement] after ** pStmt associated with the [database connection] pDb. ^If pStmt is NULL @@ -4967,10 +5313,11 @@ SQLITE_API int sqlite3_db_readonly(sqlite3 *db, const char *zDbName); ** [sqlite3_next_stmt(D,S)] must refer to an open database ** connection and in particular must not be a NULL pointer. */ -SQLITE_API sqlite3_stmt *sqlite3_next_stmt(sqlite3 *pDb, sqlite3_stmt *pStmt); +SQLITE_API sqlite3_stmt *SQLITE_STDCALL sqlite3_next_stmt(sqlite3 *pDb, sqlite3_stmt *pStmt); /* ** CAPI3REF: Commit And Rollback Notification Callbacks +** METHOD: sqlite3 ** ** ^The sqlite3_commit_hook() interface registers a callback ** function to be invoked whenever a transaction is [COMMIT | committed]. @@ -5015,11 +5362,12 @@ SQLITE_API sqlite3_stmt *sqlite3_next_stmt(sqlite3 *pDb, sqlite3_stmt *pStmt); ** ** See also the [sqlite3_update_hook()] interface. */ -SQLITE_API void *sqlite3_commit_hook(sqlite3*, int(*)(void*), void*); -SQLITE_API void *sqlite3_rollback_hook(sqlite3*, void(*)(void *), void*); +SQLITE_API void *SQLITE_STDCALL sqlite3_commit_hook(sqlite3*, int(*)(void*), void*); +SQLITE_API void *SQLITE_STDCALL sqlite3_rollback_hook(sqlite3*, void(*)(void *), void*); /* ** CAPI3REF: Data Change Notification Callbacks +** METHOD: sqlite3 ** ** ^The sqlite3_update_hook() interface registers a callback function ** with the [database connection] identified by the first argument @@ -5066,7 +5414,7 @@ SQLITE_API void *sqlite3_rollback_hook(sqlite3*, void(*)(void *), void*); ** See also the [sqlite3_commit_hook()] and [sqlite3_rollback_hook()] ** interfaces. */ -SQLITE_API void *sqlite3_update_hook( +SQLITE_API void *SQLITE_STDCALL sqlite3_update_hook( sqlite3*, void(*)(void *,int ,char const *,char const *,sqlite3_int64), void* @@ -5096,12 +5444,17 @@ SQLITE_API void *sqlite3_update_hook( ** future releases of SQLite. Applications that care about shared ** cache setting should set it explicitly. ** +** Note: This method is disabled on MacOS X 10.7 and iOS version 5.0 +** and will always return SQLITE_MISUSE. On those systems, +** shared cache mode should be enabled per-database connection via +** [sqlite3_open_v2()] with [SQLITE_OPEN_SHAREDCACHE]. +** ** This interface is threadsafe on processors where writing a ** 32-bit integer is atomic. ** ** See Also: [SQLite Shared-Cache Mode] */ -SQLITE_API int sqlite3_enable_shared_cache(int); +SQLITE_API int SQLITE_STDCALL sqlite3_enable_shared_cache(int); /* ** CAPI3REF: Attempt To Free Heap Memory @@ -5117,10 +5470,11 @@ SQLITE_API int sqlite3_enable_shared_cache(int); ** ** See also: [sqlite3_db_release_memory()] */ -SQLITE_API int sqlite3_release_memory(int); +SQLITE_API int SQLITE_STDCALL sqlite3_release_memory(int); /* ** CAPI3REF: Free Memory Used By A Database Connection +** METHOD: sqlite3 ** ** ^The sqlite3_db_release_memory(D) interface attempts to free as much heap ** memory as possible from database connection D. Unlike the @@ -5130,7 +5484,7 @@ SQLITE_API int sqlite3_release_memory(int); ** ** See also: [sqlite3_release_memory()] */ -SQLITE_API int sqlite3_db_release_memory(sqlite3*); +SQLITE_API int SQLITE_STDCALL sqlite3_db_release_memory(sqlite3*); /* ** CAPI3REF: Impose A Limit On Heap Size @@ -5182,7 +5536,7 @@ SQLITE_API int sqlite3_db_release_memory(sqlite3*); ** The circumstances under which SQLite will enforce the soft heap limit may ** changes in future releases of SQLite. */ -SQLITE_API sqlite3_int64 sqlite3_soft_heap_limit64(sqlite3_int64 N); +SQLITE_API sqlite3_int64 SQLITE_STDCALL sqlite3_soft_heap_limit64(sqlite3_int64 N); /* ** CAPI3REF: Deprecated Soft Heap Limit Interface @@ -5193,26 +5547,34 @@ SQLITE_API sqlite3_int64 sqlite3_soft_heap_limit64(sqlite3_int64 N); ** only. All new applications should use the ** [sqlite3_soft_heap_limit64()] interface rather than this one. */ -SQLITE_API SQLITE_DEPRECATED void sqlite3_soft_heap_limit(int N); +SQLITE_API SQLITE_DEPRECATED void SQLITE_STDCALL sqlite3_soft_heap_limit(int N); /* ** CAPI3REF: Extract Metadata About A Column Of A Table +** METHOD: sqlite3 ** -** ^This routine returns metadata about a specific column of a specific -** database table accessible using the [database connection] handle -** passed as the first function argument. +** ^(The sqlite3_table_column_metadata(X,D,T,C,....) routine returns +** information about column C of table T in database D +** on [database connection] X.)^ ^The sqlite3_table_column_metadata() +** interface returns SQLITE_OK and fills in the non-NULL pointers in +** the final five arguments with appropriate values if the specified +** column exists. ^The sqlite3_table_column_metadata() interface returns +** SQLITE_ERROR and if the specified column does not exist. +** ^If the column-name parameter to sqlite3_table_column_metadata() is a +** NULL pointer, then this routine simply checks for the existance of the +** table and returns SQLITE_OK if the table exists and SQLITE_ERROR if it +** does not. ** ** ^The column is identified by the second, third and fourth parameters to -** this function. ^The second parameter is either the name of the database +** this function. ^(The second parameter is either the name of the database ** (i.e. "main", "temp", or an attached database) containing the specified -** table or NULL. ^If it is NULL, then all attached databases are searched +** table or NULL.)^ ^If it is NULL, then all attached databases are searched ** for the table using the same algorithm used by the database engine to ** resolve unqualified table references. ** ** ^The third and fourth parameters to this function are the table and column -** name of the desired column, respectively. Neither of these parameters -** may be NULL. +** name of the desired column, respectively. ** ** ^Metadata is returned by writing to the memory locations passed as the 5th ** and subsequent parameters to this function. ^Any of these arguments may be @@ -5231,16 +5593,17 @@ SQLITE_API SQLITE_DEPRECATED void sqlite3_soft_heap_limit(int N); ** )^ ** ** ^The memory pointed to by the character pointers returned for the -** declaration type and collation sequence is valid only until the next +** declaration type and collation sequence is valid until the next ** call to any SQLite API function. ** ** ^If the specified table is actually a view, an [error code] is returned. ** -** ^If the specified column is "rowid", "oid" or "_rowid_" and an +** ^If the specified column is "rowid", "oid" or "_rowid_" and the table +** is not a [WITHOUT ROWID] table and an ** [INTEGER PRIMARY KEY] column has been explicitly declared, then the output ** parameters are set for the explicitly declared column. ^(If there is no -** explicitly declared [INTEGER PRIMARY KEY] column, then the output -** parameters are set as follows: +** [INTEGER PRIMARY KEY] column, then the outputs +** for the [rowid] are set as follows: ** **
     **     data type: "INTEGER"
    @@ -5250,15 +5613,11 @@ SQLITE_API SQLITE_DEPRECATED void sqlite3_soft_heap_limit(int N);
     **     auto increment: 0
     ** 
    )^ ** -** ^(This function may load one or more schemas from database files. If an -** error occurs during this process, or if the requested table or column -** cannot be found, an [error code] is returned and an error message left -** in the [database connection] (to be retrieved using sqlite3_errmsg()).)^ -** -** ^This API is only available if the library was compiled with the -** [SQLITE_ENABLE_COLUMN_METADATA] C-preprocessor symbol defined. +** ^This function causes all database schemas to be read from disk and +** parsed, if that has not already been done, and returns an error if +** any errors are encountered while loading the schema. */ -SQLITE_API int sqlite3_table_column_metadata( +SQLITE_API int SQLITE_STDCALL sqlite3_table_column_metadata( sqlite3 *db, /* Connection handle */ const char *zDbName, /* Database name or NULL */ const char *zTableName, /* Table name */ @@ -5272,6 +5631,7 @@ SQLITE_API int sqlite3_table_column_metadata( /* ** CAPI3REF: Load An Extension +** METHOD: sqlite3 ** ** ^This interface loads an SQLite extension library from the named file. ** @@ -5304,7 +5664,7 @@ SQLITE_API int sqlite3_table_column_metadata( ** ** See also the [load_extension() SQL function]. */ -SQLITE_API int sqlite3_load_extension( +SQLITE_API int SQLITE_STDCALL sqlite3_load_extension( sqlite3 *db, /* Load the extension into this database connection */ const char *zFile, /* Name of the shared library containing extension */ const char *zProc, /* Entry point. Derived from zFile if 0 */ @@ -5313,6 +5673,7 @@ SQLITE_API int sqlite3_load_extension( /* ** CAPI3REF: Enable Or Disable Extension Loading +** METHOD: sqlite3 ** ** ^So as not to open security holes in older applications that are ** unprepared to deal with [extension loading], and as a means of disabling @@ -5324,7 +5685,7 @@ SQLITE_API int sqlite3_load_extension( ** to turn extension loading on and call it with onoff==0 to turn ** it back off again. */ -SQLITE_API int sqlite3_enable_load_extension(sqlite3 *db, int onoff); +SQLITE_API int SQLITE_STDCALL sqlite3_enable_load_extension(sqlite3 *db, int onoff); /* ** CAPI3REF: Automatically Load Statically Linked Extensions @@ -5362,7 +5723,7 @@ SQLITE_API int sqlite3_enable_load_extension(sqlite3 *db, int onoff); ** See also: [sqlite3_reset_auto_extension()] ** and [sqlite3_cancel_auto_extension()] */ -SQLITE_API int sqlite3_auto_extension(void (*xEntryPoint)(void)); +SQLITE_API int SQLITE_STDCALL sqlite3_auto_extension(void (*xEntryPoint)(void)); /* ** CAPI3REF: Cancel Automatic Extension Loading @@ -5374,7 +5735,7 @@ SQLITE_API int sqlite3_auto_extension(void (*xEntryPoint)(void)); ** unregistered and it returns 0 if X was not on the list of initialization ** routines. */ -SQLITE_API int sqlite3_cancel_auto_extension(void (*xEntryPoint)(void)); +SQLITE_API int SQLITE_STDCALL sqlite3_cancel_auto_extension(void (*xEntryPoint)(void)); /* ** CAPI3REF: Reset Automatic Extension Loading @@ -5382,7 +5743,7 @@ SQLITE_API int sqlite3_cancel_auto_extension(void (*xEntryPoint)(void)); ** ^This interface disables all automatic extensions previously ** registered using [sqlite3_auto_extension()]. */ -SQLITE_API void sqlite3_reset_auto_extension(void); +SQLITE_API void SQLITE_STDCALL sqlite3_reset_auto_extension(void); /* ** The interface to the virtual-table mechanism is currently considered @@ -5484,6 +5845,17 @@ struct sqlite3_module { ** ^Information about the ORDER BY clause is stored in aOrderBy[]. ** ^Each term of aOrderBy records a column of the ORDER BY clause. ** +** The colUsed field indicates which columns of the virtual table may be +** required by the current scan. Virtual table columns are numbered from +** zero in the order in which they appear within the CREATE TABLE statement +** passed to sqlite3_declare_vtab(). For the first 63 columns (columns 0-62), +** the corresponding bit is set within the colUsed mask if the column may be +** required by SQLite. If the table has at least 64 columns and any column +** to the right of the first 63 is required, then bit 63 of colUsed is also +** set. In other words, column iCol may be required if the expression +** (colUsed & ((sqlite3_uint64)1 << (iCol>=63 ? 63 : iCol))) evaluates to +** non-zero. +** ** The [xBestIndex] method must fill aConstraintUsage[] with information ** about what parameters to pass to xFilter. ^If argvIndex>0 then ** the right-hand side of the corresponding aConstraint[] is evaluated @@ -5509,13 +5881,31 @@ struct sqlite3_module { ** ^The estimatedRows value is an estimate of the number of rows that ** will be returned by the strategy. ** +** The xBestIndex method may optionally populate the idxFlags field with a +** mask of SQLITE_INDEX_SCAN_* flags. Currently there is only one such flag - +** SQLITE_INDEX_SCAN_UNIQUE. If the xBestIndex method sets this flag, SQLite +** assumes that the strategy may visit at most one row. +** +** Additionally, if xBestIndex sets the SQLITE_INDEX_SCAN_UNIQUE flag, then +** SQLite also assumes that if a call to the xUpdate() method is made as +** part of the same statement to delete or update a virtual table row and the +** implementation returns SQLITE_CONSTRAINT, then there is no need to rollback +** any database changes. In other words, if the xUpdate() returns +** SQLITE_CONSTRAINT, the database contents must be exactly as they were +** before xUpdate was called. By contrast, if SQLITE_INDEX_SCAN_UNIQUE is not +** set and xUpdate returns SQLITE_CONSTRAINT, any database changes made by +** the xUpdate method are automatically rolled back by SQLite. +** ** IMPORTANT: The estimatedRows field was added to the sqlite3_index_info ** structure for SQLite version 3.8.2. If a virtual table extension is ** used with an SQLite version earlier than 3.8.2, the results of attempting ** to read or write the estimatedRows field are undefined (but are likely ** to included crashing the application). The estimatedRows field should ** therefore only be used if [sqlite3_libversion_number()] returns a -** value greater than or equal to 3008002. +** value greater than or equal to 3008002. Similarly, the idxFlags field +** was added for version 3.9.0. It may therefore only be used if +** sqlite3_libversion_number() returns a value greater than or equal to +** 3009000. */ struct sqlite3_index_info { /* Inputs */ @@ -5543,8 +5933,17 @@ struct sqlite3_index_info { double estimatedCost; /* Estimated cost of using this index */ /* Fields below are only available in SQLite 3.8.2 and later */ sqlite3_int64 estimatedRows; /* Estimated number of rows returned */ + /* Fields below are only available in SQLite 3.9.0 and later */ + int idxFlags; /* Mask of SQLITE_INDEX_SCAN_* flags */ + /* Fields below are only available in SQLite 3.10.0 and later */ + sqlite3_uint64 colUsed; /* Input: Mask of columns used by statement */ }; +/* +** CAPI3REF: Virtual Table Scan Flags +*/ +#define SQLITE_INDEX_SCAN_UNIQUE 1 /* Scan visits at most 1 row */ + /* ** CAPI3REF: Virtual Table Constraint Operator Codes ** @@ -5553,15 +5952,19 @@ struct sqlite3_index_info { ** an operator that is part of a constraint term in the wHERE clause of ** a query that uses a [virtual table]. */ -#define SQLITE_INDEX_CONSTRAINT_EQ 2 -#define SQLITE_INDEX_CONSTRAINT_GT 4 -#define SQLITE_INDEX_CONSTRAINT_LE 8 -#define SQLITE_INDEX_CONSTRAINT_LT 16 -#define SQLITE_INDEX_CONSTRAINT_GE 32 -#define SQLITE_INDEX_CONSTRAINT_MATCH 64 +#define SQLITE_INDEX_CONSTRAINT_EQ 2 +#define SQLITE_INDEX_CONSTRAINT_GT 4 +#define SQLITE_INDEX_CONSTRAINT_LE 8 +#define SQLITE_INDEX_CONSTRAINT_LT 16 +#define SQLITE_INDEX_CONSTRAINT_GE 32 +#define SQLITE_INDEX_CONSTRAINT_MATCH 64 +#define SQLITE_INDEX_CONSTRAINT_LIKE 65 +#define SQLITE_INDEX_CONSTRAINT_GLOB 66 +#define SQLITE_INDEX_CONSTRAINT_REGEXP 67 /* ** CAPI3REF: Register A Virtual Table Implementation +** METHOD: sqlite3 ** ** ^These routines are used to register a new [virtual table module] name. ** ^Module names must be registered before @@ -5585,13 +5988,13 @@ struct sqlite3_index_info { ** interface is equivalent to sqlite3_create_module_v2() with a NULL ** destructor. */ -SQLITE_API int sqlite3_create_module( +SQLITE_API int SQLITE_STDCALL sqlite3_create_module( sqlite3 *db, /* SQLite connection to register module with */ const char *zName, /* Name of the module */ const sqlite3_module *p, /* Methods for the module */ void *pClientData /* Client data for xCreate/xConnect */ ); -SQLITE_API int sqlite3_create_module_v2( +SQLITE_API int SQLITE_STDCALL sqlite3_create_module_v2( sqlite3 *db, /* SQLite connection to register module with */ const char *zName, /* Name of the module */ const sqlite3_module *p, /* Methods for the module */ @@ -5619,7 +6022,7 @@ SQLITE_API int sqlite3_create_module_v2( */ struct sqlite3_vtab { const sqlite3_module *pModule; /* The module for this virtual table */ - int nRef; /* NO LONGER USED */ + int nRef; /* Number of open cursors */ char *zErrMsg; /* Error message from sqlite3_mprintf() */ /* Virtual table implementations will typically add additional fields */ }; @@ -5654,10 +6057,11 @@ struct sqlite3_vtab_cursor { ** to declare the format (the names and datatypes of the columns) of ** the virtual tables they implement. */ -SQLITE_API int sqlite3_declare_vtab(sqlite3*, const char *zSQL); +SQLITE_API int SQLITE_STDCALL sqlite3_declare_vtab(sqlite3*, const char *zSQL); /* ** CAPI3REF: Overload A Function For A Virtual Table +** METHOD: sqlite3 ** ** ^(Virtual tables can provide alternative implementations of functions ** using the [xFindFunction] method of the [virtual table module]. @@ -5672,7 +6076,7 @@ SQLITE_API int sqlite3_declare_vtab(sqlite3*, const char *zSQL); ** purpose is to be a placeholder function that can be overloaded ** by a [virtual table]. */ -SQLITE_API int sqlite3_overload_function(sqlite3*, const char *zFuncName, int nArg); +SQLITE_API int SQLITE_STDCALL sqlite3_overload_function(sqlite3*, const char *zFuncName, int nArg); /* ** The interface to the virtual-table mechanism defined above (back up @@ -5700,6 +6104,8 @@ typedef struct sqlite3_blob sqlite3_blob; /* ** CAPI3REF: Open A BLOB For Incremental I/O +** METHOD: sqlite3 +** CONSTRUCTOR: sqlite3_blob ** ** ^(This interfaces opens a [BLOB handle | handle] to the BLOB located ** in row iRow, column zColumn, table zTable in database zDb; @@ -5709,26 +6115,42 @@ typedef struct sqlite3_blob sqlite3_blob; ** SELECT zColumn FROM zDb.zTable WHERE [rowid] = iRow; ** )^ ** +** ^(Parameter zDb is not the filename that contains the database, but +** rather the symbolic name of the database. For attached databases, this is +** the name that appears after the AS keyword in the [ATTACH] statement. +** For the main database file, the database name is "main". For TEMP +** tables, the database name is "temp".)^ +** ** ^If the flags parameter is non-zero, then the BLOB is opened for read -** and write access. ^If it is zero, the BLOB is opened for read access. -** ^It is not possible to open a column that is part of an index or primary -** key for writing. ^If [foreign key constraints] are enabled, it is -** not possible to open a column that is part of a [child key] for writing. +** and write access. ^If the flags parameter is zero, the BLOB is opened for +** read-only access. ** -** ^Note that the database name is not the filename that contains -** the database but rather the symbolic name of the database that -** appears after the AS keyword when the database is connected using [ATTACH]. -** ^For the main database file, the database name is "main". -** ^For TEMP tables, the database name is "temp". +** ^(On success, [SQLITE_OK] is returned and the new [BLOB handle] is stored +** in *ppBlob. Otherwise an [error code] is returned and, unless the error +** code is SQLITE_MISUSE, *ppBlob is set to NULL.)^ ^This means that, provided +** the API is not misused, it is always safe to call [sqlite3_blob_close()] +** on *ppBlob after this function it returns. +** +** This function fails with SQLITE_ERROR if any of the following are true: +**
      +**
    • ^(Database zDb does not exist)^, +**
    • ^(Table zTable does not exist within database zDb)^, +**
    • ^(Table zTable is a WITHOUT ROWID table)^, +**
    • ^(Column zColumn does not exist)^, +**
    • ^(Row iRow is not present in the table)^, +**
    • ^(The specified column of row iRow contains a value that is not +** a TEXT or BLOB value)^, +**
    • ^(Column zColumn is part of an index, PRIMARY KEY or UNIQUE +** constraint and the blob is being opened for read/write access)^, +**
    • ^([foreign key constraints | Foreign key constraints] are enabled, +** column zColumn is part of a [child key] definition and the blob is +** being opened for read/write access)^. +**
    +** +** ^Unless it returns SQLITE_MISUSE, this function sets the +** [database connection] error code and message accessible via +** [sqlite3_errcode()] and [sqlite3_errmsg()] and related functions. ** -** ^(On success, [SQLITE_OK] is returned and the new [BLOB handle] is written -** to *ppBlob. Otherwise an [error code] is returned and *ppBlob is set -** to be a null pointer.)^ -** ^This function sets the [database connection] error code and message -** accessible via [sqlite3_errcode()] and [sqlite3_errmsg()] and related -** functions. ^Note that the *ppBlob variable is always initialized in a -** way that makes it safe to invoke [sqlite3_blob_close()] on *ppBlob -** regardless of the success or failure of this routine. ** ** ^(If the row that a BLOB handle points to is modified by an ** [UPDATE], [DELETE], or by [ON CONFLICT] side-effects @@ -5746,18 +6168,14 @@ typedef struct sqlite3_blob sqlite3_blob; ** interface. Use the [UPDATE] SQL command to change the size of a ** blob. ** -** ^The [sqlite3_blob_open()] interface will fail for a [WITHOUT ROWID] -** table. Incremental BLOB I/O is not possible on [WITHOUT ROWID] tables. -** ** ^The [sqlite3_bind_zeroblob()] and [sqlite3_result_zeroblob()] interfaces -** and the built-in [zeroblob] SQL function can be used, if desired, -** to create an empty, zero-filled blob in which to read or write using -** this interface. +** and the built-in [zeroblob] SQL function may be used to create a +** zero-filled blob to read or write using the incremental-blob interface. ** ** To avoid a resource leak, every open [BLOB handle] should eventually ** be released by a call to [sqlite3_blob_close()]. */ -SQLITE_API int sqlite3_blob_open( +SQLITE_API int SQLITE_STDCALL sqlite3_blob_open( sqlite3*, const char *zDb, const char *zTable, @@ -5769,6 +6187,7 @@ SQLITE_API int sqlite3_blob_open( /* ** CAPI3REF: Move a BLOB Handle to a New Row +** METHOD: sqlite3_blob ** ** ^This function is used to move an existing blob handle so that it points ** to a different row of the same database table. ^The new row is identified @@ -5789,34 +6208,34 @@ SQLITE_API int sqlite3_blob_open( ** ** ^This function sets the database handle error code and message. */ -SQLITE_API SQLITE_EXPERIMENTAL int sqlite3_blob_reopen(sqlite3_blob *, sqlite3_int64); +SQLITE_API int SQLITE_STDCALL sqlite3_blob_reopen(sqlite3_blob *, sqlite3_int64); /* ** CAPI3REF: Close A BLOB Handle +** DESTRUCTOR: sqlite3_blob ** -** ^Closes an open [BLOB handle]. +** ^This function closes an open [BLOB handle]. ^(The BLOB handle is closed +** unconditionally. Even if this routine returns an error code, the +** handle is still closed.)^ ** -** ^Closing a BLOB shall cause the current transaction to commit -** if there are no other BLOBs, no pending prepared statements, and the -** database connection is in [autocommit mode]. -** ^If any writes were made to the BLOB, they might be held in cache -** until the close operation if they will fit. +** ^If the blob handle being closed was opened for read-write access, and if +** the database is in auto-commit mode and there are no other open read-write +** blob handles or active write statements, the current transaction is +** committed. ^If an error occurs while committing the transaction, an error +** code is returned and the transaction rolled back. ** -** ^(Closing the BLOB often forces the changes -** out to disk and so if any I/O errors occur, they will likely occur -** at the time when the BLOB is closed. Any errors that occur during -** closing are reported as a non-zero return value.)^ -** -** ^(The BLOB is closed unconditionally. Even if this routine returns -** an error code, the BLOB is still closed.)^ -** -** ^Calling this routine with a null pointer (such as would be returned -** by a failed call to [sqlite3_blob_open()]) is a harmless no-op. +** Calling this function with an argument that is not a NULL pointer or an +** open blob handle results in undefined behaviour. ^Calling this routine +** with a null pointer (such as would be returned by a failed call to +** [sqlite3_blob_open()]) is a harmless no-op. ^Otherwise, if this function +** is passed a valid open blob handle, the values returned by the +** sqlite3_errcode() and sqlite3_errmsg() functions are set before returning. */ -SQLITE_API int sqlite3_blob_close(sqlite3_blob *); +SQLITE_API int SQLITE_STDCALL sqlite3_blob_close(sqlite3_blob *); /* ** CAPI3REF: Return The Size Of An Open BLOB +** METHOD: sqlite3_blob ** ** ^Returns the size in bytes of the BLOB accessible via the ** successfully opened [BLOB handle] in its only argument. ^The @@ -5828,10 +6247,11 @@ SQLITE_API int sqlite3_blob_close(sqlite3_blob *); ** been closed by [sqlite3_blob_close()]. Passing any other pointer in ** to this routine results in undefined and probably undesirable behavior. */ -SQLITE_API int sqlite3_blob_bytes(sqlite3_blob *); +SQLITE_API int SQLITE_STDCALL sqlite3_blob_bytes(sqlite3_blob *); /* ** CAPI3REF: Read Data From A BLOB Incrementally +** METHOD: sqlite3_blob ** ** ^(This function is used to read data from an open [BLOB handle] into a ** caller-supplied buffer. N bytes of data are copied into buffer Z @@ -5856,26 +6276,33 @@ SQLITE_API int sqlite3_blob_bytes(sqlite3_blob *); ** ** See also: [sqlite3_blob_write()]. */ -SQLITE_API int sqlite3_blob_read(sqlite3_blob *, void *Z, int N, int iOffset); +SQLITE_API int SQLITE_STDCALL sqlite3_blob_read(sqlite3_blob *, void *Z, int N, int iOffset); /* ** CAPI3REF: Write Data Into A BLOB Incrementally +** METHOD: sqlite3_blob ** -** ^This function is used to write data into an open [BLOB handle] from a -** caller-supplied buffer. ^N bytes of data are copied from the buffer Z -** into the open BLOB, starting at offset iOffset. +** ^(This function is used to write data into an open [BLOB handle] from a +** caller-supplied buffer. N bytes of data are copied from the buffer Z +** into the open BLOB, starting at offset iOffset.)^ +** +** ^(On success, sqlite3_blob_write() returns SQLITE_OK. +** Otherwise, an [error code] or an [extended error code] is returned.)^ +** ^Unless SQLITE_MISUSE is returned, this function sets the +** [database connection] error code and message accessible via +** [sqlite3_errcode()] and [sqlite3_errmsg()] and related functions. ** ** ^If the [BLOB handle] passed as the first argument was not opened for ** writing (the flags parameter to [sqlite3_blob_open()] was zero), ** this function returns [SQLITE_READONLY]. ** -** ^This function may only modify the contents of the BLOB; it is +** This function may only modify the contents of the BLOB; it is ** not possible to increase the size of a BLOB using this API. ** ^If offset iOffset is less than N bytes from the end of the BLOB, -** [SQLITE_ERROR] is returned and no data is written. ^If N is -** less than zero [SQLITE_ERROR] is returned and no data is written. -** The size of the BLOB (and hence the maximum value of N+iOffset) -** can be determined using the [sqlite3_blob_bytes()] interface. +** [SQLITE_ERROR] is returned and no data is written. The size of the +** BLOB (and hence the maximum value of N+iOffset) can be determined +** using the [sqlite3_blob_bytes()] interface. ^If N or iOffset are less +** than zero [SQLITE_ERROR] is returned and no data is written. ** ** ^An attempt to write to an expired [BLOB handle] fails with an ** error code of [SQLITE_ABORT]. ^Writes to the BLOB that occurred @@ -5884,9 +6311,6 @@ SQLITE_API int sqlite3_blob_read(sqlite3_blob *, void *Z, int N, int iOffset); ** have been overwritten by the statement that expired the BLOB handle ** or by other independent statements. ** -** ^(On success, sqlite3_blob_write() returns SQLITE_OK. -** Otherwise, an [error code] or an [extended error code] is returned.)^ -** ** This routine only works on a [BLOB handle] which has been created ** by a prior successful call to [sqlite3_blob_open()] and which has not ** been closed by [sqlite3_blob_close()]. Passing any other pointer in @@ -5894,7 +6318,7 @@ SQLITE_API int sqlite3_blob_read(sqlite3_blob *, void *Z, int N, int iOffset); ** ** See also: [sqlite3_blob_read()]. */ -SQLITE_API int sqlite3_blob_write(sqlite3_blob *, const void *z, int n, int iOffset); +SQLITE_API int SQLITE_STDCALL sqlite3_blob_write(sqlite3_blob *, const void *z, int n, int iOffset); /* ** CAPI3REF: Virtual File System Objects @@ -5925,9 +6349,9 @@ SQLITE_API int sqlite3_blob_write(sqlite3_blob *, const void *z, int n, int iOff ** ^(If the default VFS is unregistered, another VFS is chosen as ** the default. The choice for the new VFS is arbitrary.)^ */ -SQLITE_API sqlite3_vfs *sqlite3_vfs_find(const char *zVfsName); -SQLITE_API int sqlite3_vfs_register(sqlite3_vfs*, int makeDflt); -SQLITE_API int sqlite3_vfs_unregister(sqlite3_vfs*); +SQLITE_API sqlite3_vfs *SQLITE_STDCALL sqlite3_vfs_find(const char *zVfsName); +SQLITE_API int SQLITE_STDCALL sqlite3_vfs_register(sqlite3_vfs*, int makeDflt); +SQLITE_API int SQLITE_STDCALL sqlite3_vfs_unregister(sqlite3_vfs*); /* ** CAPI3REF: Mutexes @@ -5939,45 +6363,51 @@ SQLITE_API int sqlite3_vfs_unregister(sqlite3_vfs*); ** ** The SQLite source code contains multiple implementations ** of these mutex routines. An appropriate implementation -** is selected automatically at compile-time. ^(The following +** is selected automatically at compile-time. The following ** implementations are available in the SQLite core: ** **
      **
    • SQLITE_MUTEX_PTHREADS **
    • SQLITE_MUTEX_W32 **
    • SQLITE_MUTEX_NOOP -**
    )^ +**
** -** ^The SQLITE_MUTEX_NOOP implementation is a set of routines +** The SQLITE_MUTEX_NOOP implementation is a set of routines ** that does no real locking and is appropriate for use in -** a single-threaded application. ^The SQLITE_MUTEX_PTHREADS and +** a single-threaded application. The SQLITE_MUTEX_PTHREADS and ** SQLITE_MUTEX_W32 implementations are appropriate for use on Unix ** and Windows. ** -** ^(If SQLite is compiled with the SQLITE_MUTEX_APPDEF preprocessor +** If SQLite is compiled with the SQLITE_MUTEX_APPDEF preprocessor ** macro defined (with "-DSQLITE_MUTEX_APPDEF=1"), then no mutex ** implementation is included with the library. In this case the ** application must supply a custom mutex implementation using the ** [SQLITE_CONFIG_MUTEX] option of the sqlite3_config() function ** before calling sqlite3_initialize() or any other public sqlite3_ -** function that calls sqlite3_initialize().)^ +** function that calls sqlite3_initialize(). ** ** ^The sqlite3_mutex_alloc() routine allocates a new -** mutex and returns a pointer to it. ^If it returns NULL -** that means that a mutex could not be allocated. ^SQLite -** will unwind its stack and return an error. ^(The argument -** to sqlite3_mutex_alloc() is one of these integer constants: +** mutex and returns a pointer to it. ^The sqlite3_mutex_alloc() +** routine returns NULL if it is unable to allocate the requested +** mutex. The argument to sqlite3_mutex_alloc() must one of these +** integer constants: ** **
    **
  • SQLITE_MUTEX_FAST **
  • SQLITE_MUTEX_RECURSIVE **
  • SQLITE_MUTEX_STATIC_MASTER **
  • SQLITE_MUTEX_STATIC_MEM -**
  • SQLITE_MUTEX_STATIC_MEM2 +**
  • SQLITE_MUTEX_STATIC_OPEN **
  • SQLITE_MUTEX_STATIC_PRNG **
  • SQLITE_MUTEX_STATIC_LRU -**
  • SQLITE_MUTEX_STATIC_LRU2 -**
)^ +**
  • SQLITE_MUTEX_STATIC_PMEM +**
  • SQLITE_MUTEX_STATIC_APP1 +**
  • SQLITE_MUTEX_STATIC_APP2 +**
  • SQLITE_MUTEX_STATIC_APP3 +**
  • SQLITE_MUTEX_STATIC_VFS1 +**
  • SQLITE_MUTEX_STATIC_VFS2 +**
  • SQLITE_MUTEX_STATIC_VFS3 +** ** ** ^The first two constants (SQLITE_MUTEX_FAST and SQLITE_MUTEX_RECURSIVE) ** cause sqlite3_mutex_alloc() to create @@ -5985,14 +6415,14 @@ SQLITE_API int sqlite3_vfs_unregister(sqlite3_vfs*); ** is used but not necessarily so when SQLITE_MUTEX_FAST is used. ** The mutex implementation does not need to make a distinction ** between SQLITE_MUTEX_RECURSIVE and SQLITE_MUTEX_FAST if it does -** not want to. ^SQLite will only request a recursive mutex in -** cases where it really needs one. ^If a faster non-recursive mutex +** not want to. SQLite will only request a recursive mutex in +** cases where it really needs one. If a faster non-recursive mutex ** implementation is available on the host platform, the mutex subsystem ** might return such a mutex in response to SQLITE_MUTEX_FAST. ** ** ^The other allowed parameters to sqlite3_mutex_alloc() (anything other ** than SQLITE_MUTEX_FAST and SQLITE_MUTEX_RECURSIVE) each return -** a pointer to a static preexisting mutex. ^Six static mutexes are +** a pointer to a static preexisting mutex. ^Nine static mutexes are ** used by the current version of SQLite. Future versions of SQLite ** may add additional static mutexes. Static mutexes are for internal ** use by SQLite only. Applications that use SQLite mutexes should @@ -6001,16 +6431,13 @@ SQLITE_API int sqlite3_vfs_unregister(sqlite3_vfs*); ** ** ^Note that if one of the dynamic mutex parameters (SQLITE_MUTEX_FAST ** or SQLITE_MUTEX_RECURSIVE) is used then sqlite3_mutex_alloc() -** returns a different mutex on every call. ^But for the static +** returns a different mutex on every call. ^For the static ** mutex types, the same mutex is returned on every call that has ** the same type number. ** ** ^The sqlite3_mutex_free() routine deallocates a previously -** allocated dynamic mutex. ^SQLite is careful to deallocate every -** dynamic mutex that it allocates. The dynamic mutexes must not be in -** use when they are deallocated. Attempting to deallocate a static -** mutex results in undefined behavior. ^SQLite never deallocates -** a static mutex. +** allocated dynamic mutex. Attempting to deallocate a static +** mutex results in undefined behavior. ** ** ^The sqlite3_mutex_enter() and sqlite3_mutex_try() routines attempt ** to enter a mutex. ^If another thread is already within the mutex, @@ -6018,23 +6445,21 @@ SQLITE_API int sqlite3_vfs_unregister(sqlite3_vfs*); ** SQLITE_BUSY. ^The sqlite3_mutex_try() interface returns [SQLITE_OK] ** upon successful entry. ^(Mutexes created using ** SQLITE_MUTEX_RECURSIVE can be entered multiple times by the same thread. -** In such cases the, +** In such cases, the ** mutex must be exited an equal number of times before another thread -** can enter.)^ ^(If the same thread tries to enter any other -** kind of mutex more than once, the behavior is undefined. -** SQLite will never exhibit -** such behavior in its own use of mutexes.)^ +** can enter.)^ If the same thread tries to enter any mutex other +** than an SQLITE_MUTEX_RECURSIVE more than once, the behavior is undefined. ** ** ^(Some systems (for example, Windows 95) do not support the operation ** implemented by sqlite3_mutex_try(). On those systems, sqlite3_mutex_try() -** will always return SQLITE_BUSY. The SQLite core only ever uses -** sqlite3_mutex_try() as an optimization so this is acceptable behavior.)^ +** will always return SQLITE_BUSY. The SQLite core only ever uses +** sqlite3_mutex_try() as an optimization so this is acceptable +** behavior.)^ ** ** ^The sqlite3_mutex_leave() routine exits a mutex that was -** previously entered by the same thread. ^(The behavior +** previously entered by the same thread. The behavior ** is undefined if the mutex is not currently entered by the -** calling thread or is not currently allocated. SQLite will -** never do either.)^ +** calling thread or is not currently allocated. ** ** ^If the argument to sqlite3_mutex_enter(), sqlite3_mutex_try(), or ** sqlite3_mutex_leave() is a NULL pointer, then all three routines @@ -6042,11 +6467,11 @@ SQLITE_API int sqlite3_vfs_unregister(sqlite3_vfs*); ** ** See also: [sqlite3_mutex_held()] and [sqlite3_mutex_notheld()]. */ -SQLITE_API sqlite3_mutex *sqlite3_mutex_alloc(int); -SQLITE_API void sqlite3_mutex_free(sqlite3_mutex*); -SQLITE_API void sqlite3_mutex_enter(sqlite3_mutex*); -SQLITE_API int sqlite3_mutex_try(sqlite3_mutex*); -SQLITE_API void sqlite3_mutex_leave(sqlite3_mutex*); +SQLITE_API sqlite3_mutex *SQLITE_STDCALL sqlite3_mutex_alloc(int); +SQLITE_API void SQLITE_STDCALL sqlite3_mutex_free(sqlite3_mutex*); +SQLITE_API void SQLITE_STDCALL sqlite3_mutex_enter(sqlite3_mutex*); +SQLITE_API int SQLITE_STDCALL sqlite3_mutex_try(sqlite3_mutex*); +SQLITE_API void SQLITE_STDCALL sqlite3_mutex_leave(sqlite3_mutex*); /* ** CAPI3REF: Mutex Methods Object @@ -6055,9 +6480,9 @@ SQLITE_API void sqlite3_mutex_leave(sqlite3_mutex*); ** used to allocate and use mutexes. ** ** Usually, the default mutex implementations provided by SQLite are -** sufficient, however the user has the option of substituting a custom +** sufficient, however the application has the option of substituting a custom ** implementation for specialized deployments or systems for which SQLite -** does not provide a suitable implementation. In this case, the user +** does not provide a suitable implementation. In this case, the application ** creates and populates an instance of this structure to pass ** to sqlite3_config() along with the [SQLITE_CONFIG_MUTEX] option. ** Additionally, an instance of this structure can be used as an @@ -6098,13 +6523,13 @@ SQLITE_API void sqlite3_mutex_leave(sqlite3_mutex*); ** (i.e. it is acceptable to provide an implementation that segfaults if ** it is passed a NULL pointer). ** -** The xMutexInit() method must be threadsafe. ^It must be harmless to +** The xMutexInit() method must be threadsafe. It must be harmless to ** invoke xMutexInit() multiple times within the same process and without ** intervening calls to xMutexEnd(). Second and subsequent calls to ** xMutexInit() must be no-ops. ** -** ^xMutexInit() must not use SQLite memory allocation ([sqlite3_malloc()] -** and its associates). ^Similarly, xMutexAlloc() must not use SQLite memory +** xMutexInit() must not use SQLite memory allocation ([sqlite3_malloc()] +** and its associates). Similarly, xMutexAlloc() must not use SQLite memory ** allocation for a static mutex. ^However xMutexAlloc() may use SQLite ** memory allocation for a fast or recursive mutex. ** @@ -6130,34 +6555,34 @@ struct sqlite3_mutex_methods { ** CAPI3REF: Mutex Verification Routines ** ** The sqlite3_mutex_held() and sqlite3_mutex_notheld() routines -** are intended for use inside assert() statements. ^The SQLite core +** are intended for use inside assert() statements. The SQLite core ** never uses these routines except inside an assert() and applications -** are advised to follow the lead of the core. ^The SQLite core only +** are advised to follow the lead of the core. The SQLite core only ** provides implementations for these routines when it is compiled -** with the SQLITE_DEBUG flag. ^External mutex implementations +** with the SQLITE_DEBUG flag. External mutex implementations ** are only required to provide these routines if SQLITE_DEBUG is ** defined and if NDEBUG is not defined. ** -** ^These routines should return true if the mutex in their argument +** These routines should return true if the mutex in their argument ** is held or not held, respectively, by the calling thread. ** -** ^The implementation is not required to provide versions of these +** The implementation is not required to provide versions of these ** routines that actually work. If the implementation does not provide working ** versions of these routines, it should at least provide stubs that always ** return true so that one does not get spurious assertion failures. ** -** ^If the argument to sqlite3_mutex_held() is a NULL pointer then +** If the argument to sqlite3_mutex_held() is a NULL pointer then ** the routine should return 1. This seems counter-intuitive since ** clearly the mutex cannot be held if it does not exist. But ** the reason the mutex does not exist is because the build is not ** using mutexes. And we do not want the assert() containing the ** call to sqlite3_mutex_held() to fail, so a non-zero return is -** the appropriate thing to do. ^The sqlite3_mutex_notheld() +** the appropriate thing to do. The sqlite3_mutex_notheld() ** interface should also return 1 when given a NULL pointer. */ #ifndef NDEBUG -SQLITE_API int sqlite3_mutex_held(sqlite3_mutex*); -SQLITE_API int sqlite3_mutex_notheld(sqlite3_mutex*); +SQLITE_API int SQLITE_STDCALL sqlite3_mutex_held(sqlite3_mutex*); +SQLITE_API int SQLITE_STDCALL sqlite3_mutex_notheld(sqlite3_mutex*); #endif /* @@ -6180,9 +6605,16 @@ SQLITE_API int sqlite3_mutex_notheld(sqlite3_mutex*); #define SQLITE_MUTEX_STATIC_LRU 6 /* lru page list */ #define SQLITE_MUTEX_STATIC_LRU2 7 /* NOT USED */ #define SQLITE_MUTEX_STATIC_PMEM 7 /* sqlite3PageMalloc() */ +#define SQLITE_MUTEX_STATIC_APP1 8 /* For use by application */ +#define SQLITE_MUTEX_STATIC_APP2 9 /* For use by application */ +#define SQLITE_MUTEX_STATIC_APP3 10 /* For use by application */ +#define SQLITE_MUTEX_STATIC_VFS1 11 /* For use by built-in VFS */ +#define SQLITE_MUTEX_STATIC_VFS2 12 /* For use by extension VFS */ +#define SQLITE_MUTEX_STATIC_VFS3 13 /* For use by application VFS */ /* ** CAPI3REF: Retrieve the mutex for a database connection +** METHOD: sqlite3 ** ** ^This interface returns a pointer the [sqlite3_mutex] object that ** serializes access to the [database connection] given in the argument @@ -6190,10 +6622,11 @@ SQLITE_API int sqlite3_mutex_notheld(sqlite3_mutex*); ** ^If the [threading mode] is Single-thread or Multi-thread then this ** routine returns a NULL pointer. */ -SQLITE_API sqlite3_mutex *sqlite3_db_mutex(sqlite3*); +SQLITE_API sqlite3_mutex *SQLITE_STDCALL sqlite3_db_mutex(sqlite3*); /* ** CAPI3REF: Low-Level Control Of Database Files +** METHOD: sqlite3 ** ** ^The [sqlite3_file_control()] interface makes a direct call to the ** xFileControl method for the [sqlite3_io_methods] object associated @@ -6224,7 +6657,7 @@ SQLITE_API sqlite3_mutex *sqlite3_db_mutex(sqlite3*); ** ** See also: [SQLITE_FCNTL_LOCKSTATE] */ -SQLITE_API int sqlite3_file_control(sqlite3*, const char *zDbName, int op, void*); +SQLITE_API int SQLITE_STDCALL sqlite3_file_control(sqlite3*, const char *zDbName, int op, void*); /* ** CAPI3REF: Testing Interface @@ -6243,7 +6676,7 @@ SQLITE_API int sqlite3_file_control(sqlite3*, const char *zDbName, int op, void* ** Unlike most of the SQLite API, this function is not guaranteed to ** operate consistently from one release to the next. */ -SQLITE_API int sqlite3_test_control(int op, ...); +SQLITE_API int SQLITE_CDECL sqlite3_test_control(int op, ...); /* ** CAPI3REF: Testing Interface Operation Codes @@ -6271,16 +6704,19 @@ SQLITE_API int sqlite3_test_control(int op, ...); #define SQLITE_TESTCTRL_ISKEYWORD 16 #define SQLITE_TESTCTRL_SCRATCHMALLOC 17 #define SQLITE_TESTCTRL_LOCALTIME_FAULT 18 -#define SQLITE_TESTCTRL_EXPLAIN_STMT 19 +#define SQLITE_TESTCTRL_EXPLAIN_STMT 19 /* NOT USED */ #define SQLITE_TESTCTRL_NEVER_CORRUPT 20 #define SQLITE_TESTCTRL_VDBE_COVERAGE 21 #define SQLITE_TESTCTRL_BYTEORDER 22 -#define SQLITE_TESTCTRL_LAST 22 +#define SQLITE_TESTCTRL_ISINIT 23 +#define SQLITE_TESTCTRL_SORTER_MMAP 24 +#define SQLITE_TESTCTRL_IMPOSTER 25 +#define SQLITE_TESTCTRL_LAST 25 /* ** CAPI3REF: SQLite Runtime Status ** -** ^This interface is used to retrieve runtime status information +** ^These interfaces are used to retrieve runtime status information ** about the performance of SQLite, and optionally to reset various ** highwater marks. ^The first argument is an integer code for ** the specific parameter to measure. ^(Recognized integer codes @@ -6294,19 +6730,22 @@ SQLITE_API int sqlite3_test_control(int op, ...); ** ^(Other parameters record only the highwater mark and not the current ** value. For these latter parameters nothing is written into *pCurrent.)^ ** -** ^The sqlite3_status() routine returns SQLITE_OK on success and a -** non-zero [error code] on failure. +** ^The sqlite3_status() and sqlite3_status64() routines return +** SQLITE_OK on success and a non-zero [error code] on failure. ** -** This routine is threadsafe but is not atomic. This routine can be -** called while other threads are running the same or different SQLite -** interfaces. However the values returned in *pCurrent and -** *pHighwater reflect the status of SQLite at different points in time -** and it is possible that another thread might change the parameter -** in between the times when *pCurrent and *pHighwater are written. +** If either the current value or the highwater mark is too large to +** be represented by a 32-bit integer, then the values returned by +** sqlite3_status() are undefined. ** ** See also: [sqlite3_db_status()] */ -SQLITE_API int sqlite3_status(int op, int *pCurrent, int *pHighwater, int resetFlag); +SQLITE_API int SQLITE_STDCALL sqlite3_status(int op, int *pCurrent, int *pHighwater, int resetFlag); +SQLITE_API int SQLITE_STDCALL sqlite3_status64( + int op, + sqlite3_int64 *pCurrent, + sqlite3_int64 *pHighwater, + int resetFlag +); /* @@ -6385,7 +6824,8 @@ SQLITE_API int sqlite3_status(int op, int *pCurrent, int *pHighwater, int resetF ** The value written into the *pCurrent parameter is undefined.)^ ** ** [[SQLITE_STATUS_PARSER_STACK]] ^(
    SQLITE_STATUS_PARSER_STACK
    -**
    This parameter records the deepest parser stack. It is only +**
    The *pHighwater parameter records the deepest parser stack. +** The *pCurrent value is undefined. The *pHighwater value is only ** meaningful if SQLite is compiled with [YYTRACKMAXSTACKDEPTH].
    )^ ** ** @@ -6404,6 +6844,7 @@ SQLITE_API int sqlite3_status(int op, int *pCurrent, int *pHighwater, int resetF /* ** CAPI3REF: Database Connection Status +** METHOD: sqlite3 ** ** ^This interface is used to retrieve runtime status information ** about a single [database connection]. ^The first argument is the @@ -6424,7 +6865,7 @@ SQLITE_API int sqlite3_status(int op, int *pCurrent, int *pHighwater, int resetF ** ** See also: [sqlite3_status()] and [sqlite3_stmt_status()]. */ -SQLITE_API int sqlite3_db_status(sqlite3*, int op, int *pCur, int *pHiwtr, int resetFlg); +SQLITE_API int SQLITE_STDCALL sqlite3_db_status(sqlite3*, int op, int *pCur, int *pHiwtr, int resetFlg); /* ** CAPI3REF: Status Parameters for database connections @@ -6466,12 +6907,12 @@ SQLITE_API int sqlite3_db_status(sqlite3*, int op, int *pCur, int *pHiwtr, int r ** the current value is always zero.)^ ** ** [[SQLITE_DBSTATUS_CACHE_USED]] ^(
    SQLITE_DBSTATUS_CACHE_USED
    -**
    This parameter returns the approximate number of of bytes of heap +**
    This parameter returns the approximate number of bytes of heap ** memory used by all pager caches associated with the database connection.)^ ** ^The highwater mark associated with SQLITE_DBSTATUS_CACHE_USED is always 0. ** ** [[SQLITE_DBSTATUS_SCHEMA_USED]] ^(
    SQLITE_DBSTATUS_SCHEMA_USED
    -**
    This parameter returns the approximate number of of bytes of heap +**
    This parameter returns the approximate number of bytes of heap ** memory used to store the schema for all databases associated ** with the connection - main, temp, and any [ATTACH]-ed databases.)^ ** ^The full amount of memory used by the schemas is reported, even if the @@ -6480,7 +6921,7 @@ SQLITE_API int sqlite3_db_status(sqlite3*, int op, int *pCur, int *pHiwtr, int r ** ^The highwater mark associated with SQLITE_DBSTATUS_SCHEMA_USED is always 0. ** ** [[SQLITE_DBSTATUS_STMT_USED]] ^(
    SQLITE_DBSTATUS_STMT_USED
    -**
    This parameter returns the approximate number of of bytes of heap +**
    This parameter returns the approximate number of bytes of heap ** and lookaside memory used by all prepared statements associated with ** the database connection.)^ ** ^The highwater mark associated with SQLITE_DBSTATUS_STMT_USED is always 0. @@ -6532,6 +6973,7 @@ SQLITE_API int sqlite3_db_status(sqlite3*, int op, int *pCur, int *pHiwtr, int r /* ** CAPI3REF: Prepared Statement Status +** METHOD: sqlite3_stmt ** ** ^(Each prepared statement maintains various ** [SQLITE_STMTSTATUS counters] that measure the number @@ -6553,7 +6995,7 @@ SQLITE_API int sqlite3_db_status(sqlite3*, int op, int *pCur, int *pHiwtr, int r ** ** See also: [sqlite3_status()] and [sqlite3_db_status()]. */ -SQLITE_API int sqlite3_stmt_status(sqlite3_stmt*, int op,int resetFlg); +SQLITE_API int SQLITE_STDCALL sqlite3_stmt_status(sqlite3_stmt*, int op,int resetFlg); /* ** CAPI3REF: Status Parameters for prepared statements @@ -6880,6 +7322,10 @@ typedef struct sqlite3_backup sqlite3_backup; ** must be different or else sqlite3_backup_init(D,N,S,M) will fail with ** an error. ** +** ^A call to sqlite3_backup_init() will fail, returning SQLITE_ERROR, if +** there is already a read or read-write transaction open on the +** destination database. +** ** ^If an error occurs within sqlite3_backup_init(D,N,S,M), then NULL is ** returned and an error code and error message are stored in the ** destination [database connection] D. @@ -6972,20 +7418,20 @@ typedef struct sqlite3_backup sqlite3_backup; ** is not a permanent error and does not affect the return value of ** sqlite3_backup_finish(). ** -** [[sqlite3_backup__remaining()]] [[sqlite3_backup_pagecount()]] +** [[sqlite3_backup_remaining()]] [[sqlite3_backup_pagecount()]] ** sqlite3_backup_remaining() and sqlite3_backup_pagecount() ** -** ^Each call to sqlite3_backup_step() sets two values inside -** the [sqlite3_backup] object: the number of pages still to be backed -** up and the total number of pages in the source database file. -** The sqlite3_backup_remaining() and sqlite3_backup_pagecount() interfaces -** retrieve these two values, respectively. -** -** ^The values returned by these functions are only updated by -** sqlite3_backup_step(). ^If the source database is modified during a backup -** operation, then the values are not updated to account for any extra -** pages that need to be updated or the size of the source database file -** changing. +** ^The sqlite3_backup_remaining() routine returns the number of pages still +** to be backed up at the conclusion of the most recent sqlite3_backup_step(). +** ^The sqlite3_backup_pagecount() routine returns the total number of pages +** in the source database at the conclusion of the most recent +** sqlite3_backup_step(). +** ^(The values returned by these functions are only updated by +** sqlite3_backup_step(). If the source database is modified in a way that +** changes the size of the source database or the number of pages remaining, +** those changes are not reflected in the output of sqlite3_backup_pagecount() +** and sqlite3_backup_remaining() until after the next +** sqlite3_backup_step().)^ ** ** Concurrent Usage of Database Handles ** @@ -7018,19 +7464,20 @@ typedef struct sqlite3_backup sqlite3_backup; ** same time as another thread is invoking sqlite3_backup_step() it is ** possible that they return invalid values. */ -SQLITE_API sqlite3_backup *sqlite3_backup_init( +SQLITE_API sqlite3_backup *SQLITE_STDCALL sqlite3_backup_init( sqlite3 *pDest, /* Destination database handle */ const char *zDestName, /* Destination database name */ sqlite3 *pSource, /* Source database handle */ const char *zSourceName /* Source database name */ ); -SQLITE_API int sqlite3_backup_step(sqlite3_backup *p, int nPage); -SQLITE_API int sqlite3_backup_finish(sqlite3_backup *p); -SQLITE_API int sqlite3_backup_remaining(sqlite3_backup *p); -SQLITE_API int sqlite3_backup_pagecount(sqlite3_backup *p); +SQLITE_API int SQLITE_STDCALL sqlite3_backup_step(sqlite3_backup *p, int nPage); +SQLITE_API int SQLITE_STDCALL sqlite3_backup_finish(sqlite3_backup *p); +SQLITE_API int SQLITE_STDCALL sqlite3_backup_remaining(sqlite3_backup *p); +SQLITE_API int SQLITE_STDCALL sqlite3_backup_pagecount(sqlite3_backup *p); /* ** CAPI3REF: Unlock Notification +** METHOD: sqlite3 ** ** ^When running in shared-cache mode, a database operation may fail with ** an [SQLITE_LOCKED] error if the required locks on the shared-cache or @@ -7143,7 +7590,7 @@ SQLITE_API int sqlite3_backup_pagecount(sqlite3_backup *p); ** the special "DROP TABLE/INDEX" case, the extended error code is just ** SQLITE_LOCKED.)^ */ -SQLITE_API int sqlite3_unlock_notify( +SQLITE_API int SQLITE_STDCALL sqlite3_unlock_notify( sqlite3 *pBlocked, /* Waiting connection */ void (*xNotify)(void **apArg, int nArg), /* Callback function to invoke */ void *pNotifyArg /* Argument to pass to xNotify */ @@ -7158,23 +7605,48 @@ SQLITE_API int sqlite3_unlock_notify( ** strings in a case-independent fashion, using the same definition of "case ** independence" that SQLite uses internally when comparing identifiers. */ -SQLITE_API int sqlite3_stricmp(const char *, const char *); -SQLITE_API int sqlite3_strnicmp(const char *, const char *, int); +SQLITE_API int SQLITE_STDCALL sqlite3_stricmp(const char *, const char *); +SQLITE_API int SQLITE_STDCALL sqlite3_strnicmp(const char *, const char *, int); /* ** CAPI3REF: String Globbing * -** ^The [sqlite3_strglob(P,X)] interface returns zero if string X matches -** the glob pattern P, and it returns non-zero if string X does not match -** the glob pattern P. ^The definition of glob pattern matching used in +** ^The [sqlite3_strglob(P,X)] interface returns zero if and only if +** string X matches the [GLOB] pattern P. +** ^The definition of [GLOB] pattern matching used in ** [sqlite3_strglob(P,X)] is the same as for the "X GLOB P" operator in the -** SQL dialect used by SQLite. ^The sqlite3_strglob(P,X) function is case -** sensitive. +** SQL dialect understood by SQLite. ^The [sqlite3_strglob(P,X)] function +** is case sensitive. ** ** Note that this routine returns zero on a match and non-zero if the strings ** do not match, the same as [sqlite3_stricmp()] and [sqlite3_strnicmp()]. +** +** See also: [sqlite3_strlike()]. */ -SQLITE_API int sqlite3_strglob(const char *zGlob, const char *zStr); +SQLITE_API int SQLITE_STDCALL sqlite3_strglob(const char *zGlob, const char *zStr); + +/* +** CAPI3REF: String LIKE Matching +* +** ^The [sqlite3_strlike(P,X,E)] interface returns zero if and only if +** string X matches the [LIKE] pattern P with escape character E. +** ^The definition of [LIKE] pattern matching used in +** [sqlite3_strlike(P,X,E)] is the same as for the "X LIKE P ESCAPE E" +** operator in the SQL dialect understood by SQLite. ^For "X LIKE P" without +** the ESCAPE clause, set the E parameter of [sqlite3_strlike(P,X,E)] to 0. +** ^As with the LIKE operator, the [sqlite3_strlike(P,X,E)] function is case +** insensitive - equivalent upper and lower case ASCII characters match +** one another. +** +** ^The [sqlite3_strlike(P,X,E)] function matches Unicode characters, though +** only ASCII characters are case folded. +** +** Note that this routine returns zero on a match and non-zero if the strings +** do not match, the same as [sqlite3_stricmp()] and [sqlite3_strnicmp()]. +** +** See also: [sqlite3_strglob()]. +*/ +SQLITE_API int SQLITE_STDCALL sqlite3_strlike(const char *zGlob, const char *zStr, unsigned int cEsc); /* ** CAPI3REF: Error Logging Interface @@ -7197,18 +7669,17 @@ SQLITE_API int sqlite3_strglob(const char *zGlob, const char *zStr); ** a few hundred characters, it will be truncated to the length of the ** buffer. */ -SQLITE_API void sqlite3_log(int iErrCode, const char *zFormat, ...); +SQLITE_API void SQLITE_CDECL sqlite3_log(int iErrCode, const char *zFormat, ...); /* ** CAPI3REF: Write-Ahead Log Commit Hook +** METHOD: sqlite3 ** ** ^The [sqlite3_wal_hook()] function is used to register a callback that -** will be invoked each time a database connection commits data to a -** [write-ahead log] (i.e. whenever a transaction is committed in -** [journal_mode | journal_mode=WAL mode]). +** is invoked each time data is committed to a database in wal mode. ** -** ^The callback is invoked by SQLite after the commit has taken place and -** the associated write-lock on the database released, so the implementation +** ^(The callback is invoked by SQLite after the commit has taken place and +** the associated write-lock on the database released)^, so the implementation ** may read, write or [checkpoint] the database as required. ** ** ^The first parameter passed to the callback function when it is invoked @@ -7234,7 +7705,7 @@ SQLITE_API void sqlite3_log(int iErrCode, const char *zFormat, ...); ** [wal_autocheckpoint pragma] both invoke [sqlite3_wal_hook()] and will ** those overwrite any prior [sqlite3_wal_hook()] settings. */ -SQLITE_API void *sqlite3_wal_hook( +SQLITE_API void *SQLITE_STDCALL sqlite3_wal_hook( sqlite3*, int(*)(void *,sqlite3*,const char*,int), void* @@ -7242,6 +7713,7 @@ SQLITE_API void *sqlite3_wal_hook( /* ** CAPI3REF: Configure an auto-checkpoint +** METHOD: sqlite3 ** ** ^The [sqlite3_wal_autocheckpoint(D,N)] is a wrapper around ** [sqlite3_wal_hook()] that causes any database on [database connection] D @@ -7259,103 +7731,132 @@ SQLITE_API void *sqlite3_wal_hook( ** ^The [wal_autocheckpoint pragma] can be used to invoke this interface ** from SQL. ** +** ^Checkpoints initiated by this mechanism are +** [sqlite3_wal_checkpoint_v2|PASSIVE]. +** ** ^Every new [database connection] defaults to having the auto-checkpoint ** enabled with a threshold of 1000 or [SQLITE_DEFAULT_WAL_AUTOCHECKPOINT] ** pages. The use of this interface ** is only necessary if the default setting is found to be suboptimal ** for a particular application. */ -SQLITE_API int sqlite3_wal_autocheckpoint(sqlite3 *db, int N); +SQLITE_API int SQLITE_STDCALL sqlite3_wal_autocheckpoint(sqlite3 *db, int N); /* ** CAPI3REF: Checkpoint a database +** METHOD: sqlite3 ** -** ^The [sqlite3_wal_checkpoint(D,X)] interface causes database named X -** on [database connection] D to be [checkpointed]. ^If X is NULL or an -** empty string, then a checkpoint is run on all databases of -** connection D. ^If the database connection D is not in -** [WAL | write-ahead log mode] then this interface is a harmless no-op. +** ^(The sqlite3_wal_checkpoint(D,X) is equivalent to +** [sqlite3_wal_checkpoint_v2](D,X,[SQLITE_CHECKPOINT_PASSIVE],0,0).)^ ** -** ^The [wal_checkpoint pragma] can be used to invoke this interface -** from SQL. ^The [sqlite3_wal_autocheckpoint()] interface and the -** [wal_autocheckpoint pragma] can be used to cause this interface to be -** run whenever the WAL reaches a certain size threshold. +** In brief, sqlite3_wal_checkpoint(D,X) causes the content in the +** [write-ahead log] for database X on [database connection] D to be +** transferred into the database file and for the write-ahead log to +** be reset. See the [checkpointing] documentation for addition +** information. ** -** See also: [sqlite3_wal_checkpoint_v2()] +** This interface used to be the only way to cause a checkpoint to +** occur. But then the newer and more powerful [sqlite3_wal_checkpoint_v2()] +** interface was added. This interface is retained for backwards +** compatibility and as a convenience for applications that need to manually +** start a callback but which do not need the full power (and corresponding +** complication) of [sqlite3_wal_checkpoint_v2()]. */ -SQLITE_API int sqlite3_wal_checkpoint(sqlite3 *db, const char *zDb); +SQLITE_API int SQLITE_STDCALL sqlite3_wal_checkpoint(sqlite3 *db, const char *zDb); /* ** CAPI3REF: Checkpoint a database +** METHOD: sqlite3 ** -** Run a checkpoint operation on WAL database zDb attached to database -** handle db. The specific operation is determined by the value of the -** eMode parameter: +** ^(The sqlite3_wal_checkpoint_v2(D,X,M,L,C) interface runs a checkpoint +** operation on database X of [database connection] D in mode M. Status +** information is written back into integers pointed to by L and C.)^ +** ^(The M parameter must be a valid [checkpoint mode]:)^ ** **
    **
    SQLITE_CHECKPOINT_PASSIVE
    -** Checkpoint as many frames as possible without waiting for any database -** readers or writers to finish. Sync the db file if all frames in the log -** are checkpointed. This mode is the same as calling -** sqlite3_wal_checkpoint(). The busy-handler callback is never invoked. +** ^Checkpoint as many frames as possible without waiting for any database +** readers or writers to finish, then sync the database file if all frames +** in the log were checkpointed. ^The [busy-handler callback] +** is never invoked in the SQLITE_CHECKPOINT_PASSIVE mode. +** ^On the other hand, passive mode might leave the checkpoint unfinished +** if there are concurrent readers or writers. ** **
    SQLITE_CHECKPOINT_FULL
    -** This mode blocks (calls the busy-handler callback) until there is no +** ^This mode blocks (it invokes the +** [sqlite3_busy_handler|busy-handler callback]) until there is no ** database writer and all readers are reading from the most recent database -** snapshot. It then checkpoints all frames in the log file and syncs the -** database file. This call blocks database writers while it is running, -** but not database readers. +** snapshot. ^It then checkpoints all frames in the log file and syncs the +** database file. ^This mode blocks new database writers while it is pending, +** but new database readers are allowed to continue unimpeded. ** **
    SQLITE_CHECKPOINT_RESTART
    -** This mode works the same way as SQLITE_CHECKPOINT_FULL, except after -** checkpointing the log file it blocks (calls the busy-handler callback) -** until all readers are reading from the database file only. This ensures -** that the next client to write to the database file restarts the log file -** from the beginning. This call blocks database writers while it is running, -** but not database readers. +** ^This mode works the same way as SQLITE_CHECKPOINT_FULL with the addition +** that after checkpointing the log file it blocks (calls the +** [busy-handler callback]) +** until all readers are reading from the database file only. ^This ensures +** that the next writer will restart the log file from the beginning. +** ^Like SQLITE_CHECKPOINT_FULL, this mode blocks new +** database writer attempts while it is pending, but does not impede readers. +** +**
    SQLITE_CHECKPOINT_TRUNCATE
    +** ^This mode works the same way as SQLITE_CHECKPOINT_RESTART with the +** addition that it also truncates the log file to zero bytes just prior +** to a successful return. **
    ** -** If pnLog is not NULL, then *pnLog is set to the total number of frames in -** the log file before returning. If pnCkpt is not NULL, then *pnCkpt is set to -** the total number of checkpointed frames (including any that were already -** checkpointed when this function is called). *pnLog and *pnCkpt may be -** populated even if sqlite3_wal_checkpoint_v2() returns other than SQLITE_OK. -** If no values are available because of an error, they are both set to -1 -** before returning to communicate this to the caller. +** ^If pnLog is not NULL, then *pnLog is set to the total number of frames in +** the log file or to -1 if the checkpoint could not run because +** of an error or because the database is not in [WAL mode]. ^If pnCkpt is not +** NULL,then *pnCkpt is set to the total number of checkpointed frames in the +** log file (including any that were already checkpointed before the function +** was called) or to -1 if the checkpoint could not run due to an error or +** because the database is not in WAL mode. ^Note that upon successful +** completion of an SQLITE_CHECKPOINT_TRUNCATE, the log file will have been +** truncated to zero bytes and so both *pnLog and *pnCkpt will be set to zero. ** -** All calls obtain an exclusive "checkpoint" lock on the database file. If +** ^All calls obtain an exclusive "checkpoint" lock on the database file. ^If ** any other process is running a checkpoint operation at the same time, the -** lock cannot be obtained and SQLITE_BUSY is returned. Even if there is a +** lock cannot be obtained and SQLITE_BUSY is returned. ^Even if there is a ** busy-handler configured, it will not be invoked in this case. ** -** The SQLITE_CHECKPOINT_FULL and RESTART modes also obtain the exclusive -** "writer" lock on the database file. If the writer lock cannot be obtained -** immediately, and a busy-handler is configured, it is invoked and the writer -** lock retried until either the busy-handler returns 0 or the lock is -** successfully obtained. The busy-handler is also invoked while waiting for -** database readers as described above. If the busy-handler returns 0 before +** ^The SQLITE_CHECKPOINT_FULL, RESTART and TRUNCATE modes also obtain the +** exclusive "writer" lock on the database file. ^If the writer lock cannot be +** obtained immediately, and a busy-handler is configured, it is invoked and +** the writer lock retried until either the busy-handler returns 0 or the lock +** is successfully obtained. ^The busy-handler is also invoked while waiting for +** database readers as described above. ^If the busy-handler returns 0 before ** the writer lock is obtained or while waiting for database readers, the ** checkpoint operation proceeds from that point in the same way as ** SQLITE_CHECKPOINT_PASSIVE - checkpointing as many frames as possible -** without blocking any further. SQLITE_BUSY is returned in this case. +** without blocking any further. ^SQLITE_BUSY is returned in this case. ** -** If parameter zDb is NULL or points to a zero length string, then the -** specified operation is attempted on all WAL databases. In this case the -** values written to output parameters *pnLog and *pnCkpt are undefined. If +** ^If parameter zDb is NULL or points to a zero length string, then the +** specified operation is attempted on all WAL databases [attached] to +** [database connection] db. In this case the +** values written to output parameters *pnLog and *pnCkpt are undefined. ^If ** an SQLITE_BUSY error is encountered when processing one or more of the ** attached WAL databases, the operation is still attempted on any remaining -** attached databases and SQLITE_BUSY is returned to the caller. If any other +** attached databases and SQLITE_BUSY is returned at the end. ^If any other ** error occurs while processing an attached database, processing is abandoned -** and the error code returned to the caller immediately. If no error +** and the error code is returned to the caller immediately. ^If no error ** (SQLITE_BUSY or otherwise) is encountered while processing the attached ** databases, SQLITE_OK is returned. ** -** If database zDb is the name of an attached database that is not in WAL -** mode, SQLITE_OK is returned and both *pnLog and *pnCkpt set to -1. If +** ^If database zDb is the name of an attached database that is not in WAL +** mode, SQLITE_OK is returned and both *pnLog and *pnCkpt set to -1. ^If ** zDb is not NULL (or a zero length string) and is not the name of any ** attached database, SQLITE_ERROR is returned to the caller. +** +** ^Unless it returns SQLITE_MISUSE, +** the sqlite3_wal_checkpoint_v2() interface +** sets the error information that is queried by +** [sqlite3_errcode()] and [sqlite3_errmsg()]. +** +** ^The [PRAGMA wal_checkpoint] command can be used to invoke this interface +** from SQL. */ -SQLITE_API int sqlite3_wal_checkpoint_v2( +SQLITE_API int SQLITE_STDCALL sqlite3_wal_checkpoint_v2( sqlite3 *db, /* Database handle */ const char *zDb, /* Name of attached database (or NULL) */ int eMode, /* SQLITE_CHECKPOINT_* value */ @@ -7364,16 +7865,18 @@ SQLITE_API int sqlite3_wal_checkpoint_v2( ); /* -** CAPI3REF: Checkpoint operation parameters +** CAPI3REF: Checkpoint Mode Values +** KEYWORDS: {checkpoint mode} ** -** These constants can be used as the 3rd parameter to -** [sqlite3_wal_checkpoint_v2()]. See the [sqlite3_wal_checkpoint_v2()] -** documentation for additional information about the meaning and use of -** each of these values. +** These constants define all valid values for the "checkpoint mode" passed +** as the third parameter to the [sqlite3_wal_checkpoint_v2()] interface. +** See the [sqlite3_wal_checkpoint_v2()] documentation for details on the +** meaning of each of these checkpoint modes. */ -#define SQLITE_CHECKPOINT_PASSIVE 0 -#define SQLITE_CHECKPOINT_FULL 1 -#define SQLITE_CHECKPOINT_RESTART 2 +#define SQLITE_CHECKPOINT_PASSIVE 0 /* Do as much as possible w/o blocking */ +#define SQLITE_CHECKPOINT_FULL 1 /* Wait for writers, then checkpoint */ +#define SQLITE_CHECKPOINT_RESTART 2 /* Like FULL but wait for for readers */ +#define SQLITE_CHECKPOINT_TRUNCATE 3 /* Like RESTART but also truncate WAL */ /* ** CAPI3REF: Virtual Table Interface Configuration @@ -7389,7 +7892,7 @@ SQLITE_API int sqlite3_wal_checkpoint_v2( ** this function. (See [SQLITE_VTAB_CONSTRAINT_SUPPORT].) Further options ** may be added in the future. */ -SQLITE_API int sqlite3_vtab_config(sqlite3*, int op, ...); +SQLITE_API int SQLITE_CDECL sqlite3_vtab_config(sqlite3*, int op, ...); /* ** CAPI3REF: Virtual Table Configuration Options @@ -7442,10 +7945,11 @@ SQLITE_API int sqlite3_vtab_config(sqlite3*, int op, ...); ** of the SQL statement that triggered the call to the [xUpdate] method of the ** [virtual table]. */ -SQLITE_API int sqlite3_vtab_on_conflict(sqlite3 *); +SQLITE_API int SQLITE_STDCALL sqlite3_vtab_on_conflict(sqlite3 *); /* ** CAPI3REF: Conflict resolution modes +** KEYWORDS: {conflict resolution mode} ** ** These constants are returned by [sqlite3_vtab_on_conflict()] to ** inform a [virtual table] implementation what the [ON CONFLICT] mode @@ -7461,7 +7965,232 @@ SQLITE_API int sqlite3_vtab_on_conflict(sqlite3 *); /* #define SQLITE_ABORT 4 // Also an error code */ #define SQLITE_REPLACE 5 +/* +** CAPI3REF: Prepared Statement Scan Status Opcodes +** KEYWORDS: {scanstatus options} +** +** The following constants can be used for the T parameter to the +** [sqlite3_stmt_scanstatus(S,X,T,V)] interface. Each constant designates a +** different metric for sqlite3_stmt_scanstatus() to return. +** +** When the value returned to V is a string, space to hold that string is +** managed by the prepared statement S and will be automatically freed when +** S is finalized. +** +**
    +** [[SQLITE_SCANSTAT_NLOOP]]
    SQLITE_SCANSTAT_NLOOP
    +**
    ^The [sqlite3_int64] variable pointed to by the T parameter will be +** set to the total number of times that the X-th loop has run.
    +** +** [[SQLITE_SCANSTAT_NVISIT]]
    SQLITE_SCANSTAT_NVISIT
    +**
    ^The [sqlite3_int64] variable pointed to by the T parameter will be set +** to the total number of rows examined by all iterations of the X-th loop.
    +** +** [[SQLITE_SCANSTAT_EST]]
    SQLITE_SCANSTAT_EST
    +**
    ^The "double" variable pointed to by the T parameter will be set to the +** query planner's estimate for the average number of rows output from each +** iteration of the X-th loop. If the query planner's estimates was accurate, +** then this value will approximate the quotient NVISIT/NLOOP and the +** product of this value for all prior loops with the same SELECTID will +** be the NLOOP value for the current loop. +** +** [[SQLITE_SCANSTAT_NAME]]
    SQLITE_SCANSTAT_NAME
    +**
    ^The "const char *" variable pointed to by the T parameter will be set +** to a zero-terminated UTF-8 string containing the name of the index or table +** used for the X-th loop. +** +** [[SQLITE_SCANSTAT_EXPLAIN]]
    SQLITE_SCANSTAT_EXPLAIN
    +**
    ^The "const char *" variable pointed to by the T parameter will be set +** to a zero-terminated UTF-8 string containing the [EXPLAIN QUERY PLAN] +** description for the X-th loop. +** +** [[SQLITE_SCANSTAT_SELECTID]]
    SQLITE_SCANSTAT_SELECT
    +**
    ^The "int" variable pointed to by the T parameter will be set to the +** "select-id" for the X-th loop. The select-id identifies which query or +** subquery the loop is part of. The main query has a select-id of zero. +** The select-id is the same value as is output in the first column +** of an [EXPLAIN QUERY PLAN] query. +**
    +*/ +#define SQLITE_SCANSTAT_NLOOP 0 +#define SQLITE_SCANSTAT_NVISIT 1 +#define SQLITE_SCANSTAT_EST 2 +#define SQLITE_SCANSTAT_NAME 3 +#define SQLITE_SCANSTAT_EXPLAIN 4 +#define SQLITE_SCANSTAT_SELECTID 5 +/* +** CAPI3REF: Prepared Statement Scan Status +** METHOD: sqlite3_stmt +** +** This interface returns information about the predicted and measured +** performance for pStmt. Advanced applications can use this +** interface to compare the predicted and the measured performance and +** issue warnings and/or rerun [ANALYZE] if discrepancies are found. +** +** Since this interface is expected to be rarely used, it is only +** available if SQLite is compiled using the [SQLITE_ENABLE_STMT_SCANSTATUS] +** compile-time option. +** +** The "iScanStatusOp" parameter determines which status information to return. +** The "iScanStatusOp" must be one of the [scanstatus options] or the behavior +** of this interface is undefined. +** ^The requested measurement is written into a variable pointed to by +** the "pOut" parameter. +** Parameter "idx" identifies the specific loop to retrieve statistics for. +** Loops are numbered starting from zero. ^If idx is out of range - less than +** zero or greater than or equal to the total number of loops used to implement +** the statement - a non-zero value is returned and the variable that pOut +** points to is unchanged. +** +** ^Statistics might not be available for all loops in all statements. ^In cases +** where there exist loops with no available statistics, this function behaves +** as if the loop did not exist - it returns non-zero and leave the variable +** that pOut points to unchanged. +** +** See also: [sqlite3_stmt_scanstatus_reset()] +*/ +SQLITE_API int SQLITE_STDCALL sqlite3_stmt_scanstatus( + sqlite3_stmt *pStmt, /* Prepared statement for which info desired */ + int idx, /* Index of loop to report on */ + int iScanStatusOp, /* Information desired. SQLITE_SCANSTAT_* */ + void *pOut /* Result written here */ +); + +/* +** CAPI3REF: Zero Scan-Status Counters +** METHOD: sqlite3_stmt +** +** ^Zero all [sqlite3_stmt_scanstatus()] related event counters. +** +** This API is only available if the library is built with pre-processor +** symbol [SQLITE_ENABLE_STMT_SCANSTATUS] defined. +*/ +SQLITE_API void SQLITE_STDCALL sqlite3_stmt_scanstatus_reset(sqlite3_stmt*); + +/* +** CAPI3REF: Flush caches to disk mid-transaction +** +** ^If a write-transaction is open on [database connection] D when the +** [sqlite3_db_cacheflush(D)] interface invoked, any dirty +** pages in the pager-cache that are not currently in use are written out +** to disk. A dirty page may be in use if a database cursor created by an +** active SQL statement is reading from it, or if it is page 1 of a database +** file (page 1 is always "in use"). ^The [sqlite3_db_cacheflush(D)] +** interface flushes caches for all schemas - "main", "temp", and +** any [attached] databases. +** +** ^If this function needs to obtain extra database locks before dirty pages +** can be flushed to disk, it does so. ^If those locks cannot be obtained +** immediately and there is a busy-handler callback configured, it is invoked +** in the usual manner. ^If the required lock still cannot be obtained, then +** the database is skipped and an attempt made to flush any dirty pages +** belonging to the next (if any) database. ^If any databases are skipped +** because locks cannot be obtained, but no other error occurs, this +** function returns SQLITE_BUSY. +** +** ^If any other error occurs while flushing dirty pages to disk (for +** example an IO error or out-of-memory condition), then processing is +** abandoned and an SQLite [error code] is returned to the caller immediately. +** +** ^Otherwise, if no error occurs, [sqlite3_db_cacheflush()] returns SQLITE_OK. +** +** ^This function does not set the database handle error code or message +** returned by the [sqlite3_errcode()] and [sqlite3_errmsg()] functions. +*/ +SQLITE_API int SQLITE_STDCALL sqlite3_db_cacheflush(sqlite3*); + +/* +** CAPI3REF: Database Snapshot +** KEYWORDS: {snapshot} +** EXPERIMENTAL +** +** An instance of the snapshot object records the state of a [WAL mode] +** database for some specific point in history. +** +** In [WAL mode], multiple [database connections] that are open on the +** same database file can each be reading a different historical version +** of the database file. When a [database connection] begins a read +** transaction, that connection sees an unchanging copy of the database +** as it existed for the point in time when the transaction first started. +** Subsequent changes to the database from other connections are not seen +** by the reader until a new read transaction is started. +** +** The sqlite3_snapshot object records state information about an historical +** version of the database file so that it is possible to later open a new read +** transaction that sees that historical version of the database rather than +** the most recent version. +** +** The constructor for this object is [sqlite3_snapshot_get()]. The +** [sqlite3_snapshot_open()] method causes a fresh read transaction to refer +** to an historical snapshot (if possible). The destructor for +** sqlite3_snapshot objects is [sqlite3_snapshot_free()]. +*/ +typedef struct sqlite3_snapshot sqlite3_snapshot; + +/* +** CAPI3REF: Record A Database Snapshot +** EXPERIMENTAL +** +** ^The [sqlite3_snapshot_get(D,S,P)] interface attempts to make a +** new [sqlite3_snapshot] object that records the current state of +** schema S in database connection D. ^On success, the +** [sqlite3_snapshot_get(D,S,P)] interface writes a pointer to the newly +** created [sqlite3_snapshot] object into *P and returns SQLITE_OK. +** ^If schema S of [database connection] D is not a [WAL mode] database +** that is in a read transaction, then [sqlite3_snapshot_get(D,S,P)] +** leaves the *P value unchanged and returns an appropriate [error code]. +** +** The [sqlite3_snapshot] object returned from a successful call to +** [sqlite3_snapshot_get()] must be freed using [sqlite3_snapshot_free()] +** to avoid a memory leak. +** +** The [sqlite3_snapshot_get()] interface is only available when the +** SQLITE_ENABLE_SNAPSHOT compile-time option is used. +*/ +SQLITE_API SQLITE_EXPERIMENTAL int SQLITE_STDCALL sqlite3_snapshot_get( + sqlite3 *db, + const char *zSchema, + sqlite3_snapshot **ppSnapshot +); + +/* +** CAPI3REF: Start a read transaction on an historical snapshot +** EXPERIMENTAL +** +** ^The [sqlite3_snapshot_open(D,S,P)] interface attempts to move the +** read transaction that is currently open on schema S of +** [database connection] D so that it refers to historical [snapshot] P. +** ^The [sqlite3_snapshot_open()] interface returns SQLITE_OK on success +** or an appropriate [error code] if it fails. +** +** ^In order to succeed, a call to [sqlite3_snapshot_open(D,S,P)] must be +** the first operation, apart from other sqlite3_snapshot_open() calls, +** following the [BEGIN] that starts a new read transaction. +** ^A [snapshot] will fail to open if it has been overwritten by a +** [checkpoint]. +** +** The [sqlite3_snapshot_open()] interface is only available when the +** SQLITE_ENABLE_SNAPSHOT compile-time option is used. +*/ +SQLITE_API SQLITE_EXPERIMENTAL int SQLITE_STDCALL sqlite3_snapshot_open( + sqlite3 *db, + const char *zSchema, + sqlite3_snapshot *pSnapshot +); + +/* +** CAPI3REF: Destroy a snapshot +** EXPERIMENTAL +** +** ^The [sqlite3_snapshot_free(P)] interface destroys [sqlite3_snapshot] P. +** The application must eventually free every [sqlite3_snapshot] object +** using this routine to avoid a memory leak. +** +** The [sqlite3_snapshot_free()] interface is only available when the +** SQLITE_ENABLE_SNAPSHOT compile-time option is used. +*/ +SQLITE_API SQLITE_EXPERIMENTAL void SQLITE_STDCALL sqlite3_snapshot_free(sqlite3_snapshot*); /* ** Undo the hack that converts floating point types to integer for @@ -7515,7 +8244,7 @@ typedef struct sqlite3_rtree_query_info sqlite3_rtree_query_info; ** ** SELECT ... FROM WHERE MATCH $zGeom(... params ...) */ -SQLITE_API int sqlite3_rtree_geometry_callback( +SQLITE_API int SQLITE_STDCALL sqlite3_rtree_geometry_callback( sqlite3 *db, const char *zGeom, int (*xGeom)(sqlite3_rtree_geometry*, int, sqlite3_rtree_dbl*,int*), @@ -7541,7 +8270,7 @@ struct sqlite3_rtree_geometry { ** ** SELECT ... FROM WHERE MATCH $zQueryFunc(... params ...) */ -SQLITE_API int sqlite3_rtree_query_callback( +SQLITE_API int SQLITE_STDCALL sqlite3_rtree_query_callback( sqlite3 *db, const char *zQueryFunc, int (*xQueryFunc)(sqlite3_rtree_query_info*), @@ -7575,6 +8304,8 @@ struct sqlite3_rtree_query_info { int eParentWithin; /* Visibility of parent node */ int eWithin; /* OUT: Visiblity */ sqlite3_rtree_dbl rScore; /* OUT: Write the score here */ + /* The following fields are only available in 3.8.11 and later */ + sqlite3_value **apSqlParam; /* Original SQL values of parameters */ }; /* @@ -7591,6 +8322,526 @@ struct sqlite3_rtree_query_info { #endif /* ifndef _SQLITE3RTREE_H_ */ +/* +** 2014 May 31 +** +** The author disclaims copyright to this source code. In place of +** a legal notice, here is a blessing: +** +** May you do good and not evil. +** May you find forgiveness for yourself and forgive others. +** May you share freely, never taking more than you give. +** +****************************************************************************** +** +** Interfaces to extend FTS5. Using the interfaces defined in this file, +** FTS5 may be extended with: +** +** * custom tokenizers, and +** * custom auxiliary functions. +*/ + + +#ifndef _FTS5_H +#define _FTS5_H + + +#if 0 +extern "C" { +#endif + +/************************************************************************* +** CUSTOM AUXILIARY FUNCTIONS +** +** Virtual table implementations may overload SQL functions by implementing +** the sqlite3_module.xFindFunction() method. +*/ + +typedef struct Fts5ExtensionApi Fts5ExtensionApi; +typedef struct Fts5Context Fts5Context; +typedef struct Fts5PhraseIter Fts5PhraseIter; + +typedef void (*fts5_extension_function)( + const Fts5ExtensionApi *pApi, /* API offered by current FTS version */ + Fts5Context *pFts, /* First arg to pass to pApi functions */ + sqlite3_context *pCtx, /* Context for returning result/error */ + int nVal, /* Number of values in apVal[] array */ + sqlite3_value **apVal /* Array of trailing arguments */ +); + +struct Fts5PhraseIter { + const unsigned char *a; + const unsigned char *b; +}; + +/* +** EXTENSION API FUNCTIONS +** +** xUserData(pFts): +** Return a copy of the context pointer the extension function was +** registered with. +** +** xColumnTotalSize(pFts, iCol, pnToken): +** If parameter iCol is less than zero, set output variable *pnToken +** to the total number of tokens in the FTS5 table. Or, if iCol is +** non-negative but less than the number of columns in the table, return +** the total number of tokens in column iCol, considering all rows in +** the FTS5 table. +** +** If parameter iCol is greater than or equal to the number of columns +** in the table, SQLITE_RANGE is returned. Or, if an error occurs (e.g. +** an OOM condition or IO error), an appropriate SQLite error code is +** returned. +** +** xColumnCount(pFts): +** Return the number of columns in the table. +** +** xColumnSize(pFts, iCol, pnToken): +** If parameter iCol is less than zero, set output variable *pnToken +** to the total number of tokens in the current row. Or, if iCol is +** non-negative but less than the number of columns in the table, set +** *pnToken to the number of tokens in column iCol of the current row. +** +** If parameter iCol is greater than or equal to the number of columns +** in the table, SQLITE_RANGE is returned. Or, if an error occurs (e.g. +** an OOM condition or IO error), an appropriate SQLite error code is +** returned. +** +** xColumnText: +** This function attempts to retrieve the text of column iCol of the +** current document. If successful, (*pz) is set to point to a buffer +** containing the text in utf-8 encoding, (*pn) is set to the size in bytes +** (not characters) of the buffer and SQLITE_OK is returned. Otherwise, +** if an error occurs, an SQLite error code is returned and the final values +** of (*pz) and (*pn) are undefined. +** +** xPhraseCount: +** Returns the number of phrases in the current query expression. +** +** xPhraseSize: +** Returns the number of tokens in phrase iPhrase of the query. Phrases +** are numbered starting from zero. +** +** xInstCount: +** Set *pnInst to the total number of occurrences of all phrases within +** the query within the current row. Return SQLITE_OK if successful, or +** an error code (i.e. SQLITE_NOMEM) if an error occurs. +** +** xInst: +** Query for the details of phrase match iIdx within the current row. +** Phrase matches are numbered starting from zero, so the iIdx argument +** should be greater than or equal to zero and smaller than the value +** output by xInstCount(). +** +** Returns SQLITE_OK if successful, or an error code (i.e. SQLITE_NOMEM) +** if an error occurs. +** +** xRowid: +** Returns the rowid of the current row. +** +** xTokenize: +** Tokenize text using the tokenizer belonging to the FTS5 table. +** +** xQueryPhrase(pFts5, iPhrase, pUserData, xCallback): +** This API function is used to query the FTS table for phrase iPhrase +** of the current query. Specifically, a query equivalent to: +** +** ... FROM ftstable WHERE ftstable MATCH $p ORDER BY rowid +** +** with $p set to a phrase equivalent to the phrase iPhrase of the +** current query is executed. For each row visited, the callback function +** passed as the fourth argument is invoked. The context and API objects +** passed to the callback function may be used to access the properties of +** each matched row. Invoking Api.xUserData() returns a copy of the pointer +** passed as the third argument to pUserData. +** +** If the callback function returns any value other than SQLITE_OK, the +** query is abandoned and the xQueryPhrase function returns immediately. +** If the returned value is SQLITE_DONE, xQueryPhrase returns SQLITE_OK. +** Otherwise, the error code is propagated upwards. +** +** If the query runs to completion without incident, SQLITE_OK is returned. +** Or, if some error occurs before the query completes or is aborted by +** the callback, an SQLite error code is returned. +** +** +** xSetAuxdata(pFts5, pAux, xDelete) +** +** Save the pointer passed as the second argument as the extension functions +** "auxiliary data". The pointer may then be retrieved by the current or any +** future invocation of the same fts5 extension function made as part of +** of the same MATCH query using the xGetAuxdata() API. +** +** Each extension function is allocated a single auxiliary data slot for +** each FTS query (MATCH expression). If the extension function is invoked +** more than once for a single FTS query, then all invocations share a +** single auxiliary data context. +** +** If there is already an auxiliary data pointer when this function is +** invoked, then it is replaced by the new pointer. If an xDelete callback +** was specified along with the original pointer, it is invoked at this +** point. +** +** The xDelete callback, if one is specified, is also invoked on the +** auxiliary data pointer after the FTS5 query has finished. +** +** If an error (e.g. an OOM condition) occurs within this function, an +** the auxiliary data is set to NULL and an error code returned. If the +** xDelete parameter was not NULL, it is invoked on the auxiliary data +** pointer before returning. +** +** +** xGetAuxdata(pFts5, bClear) +** +** Returns the current auxiliary data pointer for the fts5 extension +** function. See the xSetAuxdata() method for details. +** +** If the bClear argument is non-zero, then the auxiliary data is cleared +** (set to NULL) before this function returns. In this case the xDelete, +** if any, is not invoked. +** +** +** xRowCount(pFts5, pnRow) +** +** This function is used to retrieve the total number of rows in the table. +** In other words, the same value that would be returned by: +** +** SELECT count(*) FROM ftstable; +** +** xPhraseFirst() +** This function is used, along with type Fts5PhraseIter and the xPhraseNext +** method, to iterate through all instances of a single query phrase within +** the current row. This is the same information as is accessible via the +** xInstCount/xInst APIs. While the xInstCount/xInst APIs are more convenient +** to use, this API may be faster under some circumstances. To iterate +** through instances of phrase iPhrase, use the following code: +** +** Fts5PhraseIter iter; +** int iCol, iOff; +** for(pApi->xPhraseFirst(pFts, iPhrase, &iter, &iCol, &iOff); +** iOff>=0; +** pApi->xPhraseNext(pFts, &iter, &iCol, &iOff) +** ){ +** // An instance of phrase iPhrase at offset iOff of column iCol +** } +** +** The Fts5PhraseIter structure is defined above. Applications should not +** modify this structure directly - it should only be used as shown above +** with the xPhraseFirst() and xPhraseNext() API methods. +** +** xPhraseNext() +** See xPhraseFirst above. +*/ +struct Fts5ExtensionApi { + int iVersion; /* Currently always set to 1 */ + + void *(*xUserData)(Fts5Context*); + + int (*xColumnCount)(Fts5Context*); + int (*xRowCount)(Fts5Context*, sqlite3_int64 *pnRow); + int (*xColumnTotalSize)(Fts5Context*, int iCol, sqlite3_int64 *pnToken); + + int (*xTokenize)(Fts5Context*, + const char *pText, int nText, /* Text to tokenize */ + void *pCtx, /* Context passed to xToken() */ + int (*xToken)(void*, int, const char*, int, int, int) /* Callback */ + ); + + int (*xPhraseCount)(Fts5Context*); + int (*xPhraseSize)(Fts5Context*, int iPhrase); + + int (*xInstCount)(Fts5Context*, int *pnInst); + int (*xInst)(Fts5Context*, int iIdx, int *piPhrase, int *piCol, int *piOff); + + sqlite3_int64 (*xRowid)(Fts5Context*); + int (*xColumnText)(Fts5Context*, int iCol, const char **pz, int *pn); + int (*xColumnSize)(Fts5Context*, int iCol, int *pnToken); + + int (*xQueryPhrase)(Fts5Context*, int iPhrase, void *pUserData, + int(*)(const Fts5ExtensionApi*,Fts5Context*,void*) + ); + int (*xSetAuxdata)(Fts5Context*, void *pAux, void(*xDelete)(void*)); + void *(*xGetAuxdata)(Fts5Context*, int bClear); + + void (*xPhraseFirst)(Fts5Context*, int iPhrase, Fts5PhraseIter*, int*, int*); + void (*xPhraseNext)(Fts5Context*, Fts5PhraseIter*, int *piCol, int *piOff); +}; + +/* +** CUSTOM AUXILIARY FUNCTIONS +*************************************************************************/ + +/************************************************************************* +** CUSTOM TOKENIZERS +** +** Applications may also register custom tokenizer types. A tokenizer +** is registered by providing fts5 with a populated instance of the +** following structure. All structure methods must be defined, setting +** any member of the fts5_tokenizer struct to NULL leads to undefined +** behaviour. The structure methods are expected to function as follows: +** +** xCreate: +** This function is used to allocate and inititalize a tokenizer instance. +** A tokenizer instance is required to actually tokenize text. +** +** The first argument passed to this function is a copy of the (void*) +** pointer provided by the application when the fts5_tokenizer object +** was registered with FTS5 (the third argument to xCreateTokenizer()). +** The second and third arguments are an array of nul-terminated strings +** containing the tokenizer arguments, if any, specified following the +** tokenizer name as part of the CREATE VIRTUAL TABLE statement used +** to create the FTS5 table. +** +** The final argument is an output variable. If successful, (*ppOut) +** should be set to point to the new tokenizer handle and SQLITE_OK +** returned. If an error occurs, some value other than SQLITE_OK should +** be returned. In this case, fts5 assumes that the final value of *ppOut +** is undefined. +** +** xDelete: +** This function is invoked to delete a tokenizer handle previously +** allocated using xCreate(). Fts5 guarantees that this function will +** be invoked exactly once for each successful call to xCreate(). +** +** xTokenize: +** This function is expected to tokenize the nText byte string indicated +** by argument pText. pText may or may not be nul-terminated. The first +** argument passed to this function is a pointer to an Fts5Tokenizer object +** returned by an earlier call to xCreate(). +** +** The second argument indicates the reason that FTS5 is requesting +** tokenization of the supplied text. This is always one of the following +** four values: +** +**
    • FTS5_TOKENIZE_DOCUMENT - A document is being inserted into +** or removed from the FTS table. The tokenizer is being invoked to +** determine the set of tokens to add to (or delete from) the +** FTS index. +** +**
    • FTS5_TOKENIZE_QUERY - A MATCH query is being executed +** against the FTS index. The tokenizer is being called to tokenize +** a bareword or quoted string specified as part of the query. +** +**
    • (FTS5_TOKENIZE_QUERY | FTS5_TOKENIZE_PREFIX) - Same as +** FTS5_TOKENIZE_QUERY, except that the bareword or quoted string is +** followed by a "*" character, indicating that the last token +** returned by the tokenizer will be treated as a token prefix. +** +**
    • FTS5_TOKENIZE_AUX - The tokenizer is being invoked to +** satisfy an fts5_api.xTokenize() request made by an auxiliary +** function. Or an fts5_api.xColumnSize() request made by the same +** on a columnsize=0 database. +**
    +** +** For each token in the input string, the supplied callback xToken() must +** be invoked. The first argument to it should be a copy of the pointer +** passed as the second argument to xTokenize(). The third and fourth +** arguments are a pointer to a buffer containing the token text, and the +** size of the token in bytes. The 4th and 5th arguments are the byte offsets +** of the first byte of and first byte immediately following the text from +** which the token is derived within the input. +** +** The second argument passed to the xToken() callback ("tflags") should +** normally be set to 0. The exception is if the tokenizer supports +** synonyms. In this case see the discussion below for details. +** +** FTS5 assumes the xToken() callback is invoked for each token in the +** order that they occur within the input text. +** +** If an xToken() callback returns any value other than SQLITE_OK, then +** the tokenization should be abandoned and the xTokenize() method should +** immediately return a copy of the xToken() return value. Or, if the +** input buffer is exhausted, xTokenize() should return SQLITE_OK. Finally, +** if an error occurs with the xTokenize() implementation itself, it +** may abandon the tokenization and return any error code other than +** SQLITE_OK or SQLITE_DONE. +** +** SYNONYM SUPPORT +** +** Custom tokenizers may also support synonyms. Consider a case in which a +** user wishes to query for a phrase such as "first place". Using the +** built-in tokenizers, the FTS5 query 'first + place' will match instances +** of "first place" within the document set, but not alternative forms +** such as "1st place". In some applications, it would be better to match +** all instances of "first place" or "1st place" regardless of which form +** the user specified in the MATCH query text. +** +** There are several ways to approach this in FTS5: +** +**
    1. By mapping all synonyms to a single token. In this case, the +** In the above example, this means that the tokenizer returns the +** same token for inputs "first" and "1st". Say that token is in +** fact "first", so that when the user inserts the document "I won +** 1st place" entries are added to the index for tokens "i", "won", +** "first" and "place". If the user then queries for '1st + place', +** the tokenizer substitutes "first" for "1st" and the query works +** as expected. +** +**
    2. By adding multiple synonyms for a single term to the FTS index. +** In this case, when tokenizing query text, the tokenizer may +** provide multiple synonyms for a single term within the document. +** FTS5 then queries the index for each synonym individually. For +** example, faced with the query: +** +** +** ... MATCH 'first place' +** +** the tokenizer offers both "1st" and "first" as synonyms for the +** first token in the MATCH query and FTS5 effectively runs a query +** similar to: +** +** +** ... MATCH '(first OR 1st) place' +** +** except that, for the purposes of auxiliary functions, the query +** still appears to contain just two phrases - "(first OR 1st)" +** being treated as a single phrase. +** +**
    3. By adding multiple synonyms for a single term to the FTS index. +** Using this method, when tokenizing document text, the tokenizer +** provides multiple synonyms for each token. So that when a +** document such as "I won first place" is tokenized, entries are +** added to the FTS index for "i", "won", "first", "1st" and +** "place". +** +** This way, even if the tokenizer does not provide synonyms +** when tokenizing query text (it should not - to do would be +** inefficient), it doesn't matter if the user queries for +** 'first + place' or '1st + place', as there are entires in the +** FTS index corresponding to both forms of the first token. +**
    +** +** Whether it is parsing document or query text, any call to xToken that +** specifies a tflags argument with the FTS5_TOKEN_COLOCATED bit +** is considered to supply a synonym for the previous token. For example, +** when parsing the document "I won first place", a tokenizer that supports +** synonyms would call xToken() 5 times, as follows: +** +** +** xToken(pCtx, 0, "i", 1, 0, 1); +** xToken(pCtx, 0, "won", 3, 2, 5); +** xToken(pCtx, 0, "first", 5, 6, 11); +** xToken(pCtx, FTS5_TOKEN_COLOCATED, "1st", 3, 6, 11); +** xToken(pCtx, 0, "place", 5, 12, 17); +** +** +** It is an error to specify the FTS5_TOKEN_COLOCATED flag the first time +** xToken() is called. Multiple synonyms may be specified for a single token +** by making multiple calls to xToken(FTS5_TOKEN_COLOCATED) in sequence. +** There is no limit to the number of synonyms that may be provided for a +** single token. +** +** In many cases, method (1) above is the best approach. It does not add +** extra data to the FTS index or require FTS5 to query for multiple terms, +** so it is efficient in terms of disk space and query speed. However, it +** does not support prefix queries very well. If, as suggested above, the +** token "first" is subsituted for "1st" by the tokenizer, then the query: +** +** +** ... MATCH '1s*' +** +** will not match documents that contain the token "1st" (as the tokenizer +** will probably not map "1s" to any prefix of "first"). +** +** For full prefix support, method (3) may be preferred. In this case, +** because the index contains entries for both "first" and "1st", prefix +** queries such as 'fi*' or '1s*' will match correctly. However, because +** extra entries are added to the FTS index, this method uses more space +** within the database. +** +** Method (2) offers a midpoint between (1) and (3). Using this method, +** a query such as '1s*' will match documents that contain the literal +** token "1st", but not "first" (assuming the tokenizer is not able to +** provide synonyms for prefixes). However, a non-prefix query like '1st' +** will match against "1st" and "first". This method does not require +** extra disk space, as no extra entries are added to the FTS index. +** On the other hand, it may require more CPU cycles to run MATCH queries, +** as separate queries of the FTS index are required for each synonym. +** +** When using methods (2) or (3), it is important that the tokenizer only +** provide synonyms when tokenizing document text (method (2)) or query +** text (method (3)), not both. Doing so will not cause any errors, but is +** inefficient. +*/ +typedef struct Fts5Tokenizer Fts5Tokenizer; +typedef struct fts5_tokenizer fts5_tokenizer; +struct fts5_tokenizer { + int (*xCreate)(void*, const char **azArg, int nArg, Fts5Tokenizer **ppOut); + void (*xDelete)(Fts5Tokenizer*); + int (*xTokenize)(Fts5Tokenizer*, + void *pCtx, + int flags, /* Mask of FTS5_TOKENIZE_* flags */ + const char *pText, int nText, + int (*xToken)( + void *pCtx, /* Copy of 2nd argument to xTokenize() */ + int tflags, /* Mask of FTS5_TOKEN_* flags */ + const char *pToken, /* Pointer to buffer containing token */ + int nToken, /* Size of token in bytes */ + int iStart, /* Byte offset of token within input text */ + int iEnd /* Byte offset of end of token within input text */ + ) + ); +}; + +/* Flags that may be passed as the third argument to xTokenize() */ +#define FTS5_TOKENIZE_QUERY 0x0001 +#define FTS5_TOKENIZE_PREFIX 0x0002 +#define FTS5_TOKENIZE_DOCUMENT 0x0004 +#define FTS5_TOKENIZE_AUX 0x0008 + +/* Flags that may be passed by the tokenizer implementation back to FTS5 +** as the third argument to the supplied xToken callback. */ +#define FTS5_TOKEN_COLOCATED 0x0001 /* Same position as prev. token */ + +/* +** END OF CUSTOM TOKENIZERS +*************************************************************************/ + +/************************************************************************* +** FTS5 EXTENSION REGISTRATION API +*/ +typedef struct fts5_api fts5_api; +struct fts5_api { + int iVersion; /* Currently always set to 2 */ + + /* Create a new tokenizer */ + int (*xCreateTokenizer)( + fts5_api *pApi, + const char *zName, + void *pContext, + fts5_tokenizer *pTokenizer, + void (*xDestroy)(void*) + ); + + /* Find an existing tokenizer */ + int (*xFindTokenizer)( + fts5_api *pApi, + const char *zName, + void **ppContext, + fts5_tokenizer *pTokenizer + ); + + /* Create a new auxiliary function */ + int (*xCreateFunction)( + fts5_api *pApi, + const char *zName, + void *pContext, + fts5_extension_function xFunction, + void (*xDestroy)(void*) + ); +}; + +/* +** END OF REGISTRATION API +*************************************************************************/ + +#if 0 +} /* end of the 'extern "C"' block */ +#endif + +#endif /* _FTS5_H */ + + /************** End of sqlite3.h *********************************************/ /************** Continuing where we left off in sqliteInt.h ******************/ @@ -7705,15 +8956,17 @@ struct sqlite3_rtree_query_info { #endif /* -** The maximum number of in-memory pages to use for the main database -** table and for temporary tables. The SQLITE_DEFAULT_CACHE_SIZE +** The suggested maximum number of in-memory pages to use for +** the main database table and for temporary tables. +** +** IMPLEMENTATION-OF: R-31093-59126 The default suggested cache size +** is 2000 pages. +** IMPLEMENTATION-OF: R-48205-43578 The default suggested cache size can be +** altered using the SQLITE_DEFAULT_CACHE_SIZE compile-time options. */ #ifndef SQLITE_DEFAULT_CACHE_SIZE # define SQLITE_DEFAULT_CACHE_SIZE 2000 #endif -#ifndef SQLITE_DEFAULT_TEMP_CACHE_SIZE -# define SQLITE_DEFAULT_TEMP_CACHE_SIZE 500 -#endif /* ** The default number of frames to accumulate in the log file before @@ -7826,15 +9079,6 @@ struct sqlite3_rtree_query_info { #pragma warn -spa /* Suspicious pointer arithmetic */ #endif -/* Needed for various definitions... */ -#ifndef _GNU_SOURCE -# define _GNU_SOURCE -#endif - -#if defined(__OpenBSD__) && !defined(_BSD_SOURCE) -# define _BSD_SOURCE -#endif - /* ** Include standard header files as necessary */ @@ -7875,6 +9119,51 @@ struct sqlite3_rtree_query_info { # define SQLITE_PTR_TO_INT(X) ((int)(X)) #endif +/* +** The SQLITE_WITHIN(P,S,E) macro checks to see if pointer P points to +** something between S (inclusive) and E (exclusive). +** +** In other words, S is a buffer and E is a pointer to the first byte after +** the end of buffer S. This macro returns true if P points to something +** contained within the buffer S. +*/ +#if defined(HAVE_STDINT_H) +# define SQLITE_WITHIN(P,S,E) \ + ((uintptr_t)(P)>=(uintptr_t)(S) && (uintptr_t)(P)<(uintptr_t)(E)) +#else +# define SQLITE_WITHIN(P,S,E) ((P)>=(S) && (P)<(E)) +#endif + +/* +** A macro to hint to the compiler that a function should not be +** inlined. +*/ +#if defined(__GNUC__) +# define SQLITE_NOINLINE __attribute__((noinline)) +#elif defined(_MSC_VER) && _MSC_VER>=1310 +# define SQLITE_NOINLINE __declspec(noinline) +#else +# define SQLITE_NOINLINE +#endif + +/* +** Make sure that the compiler intrinsics we desire are enabled when +** compiling with an appropriate version of MSVC unless prevented by +** the SQLITE_DISABLE_INTRINSIC define. +*/ +#if !defined(SQLITE_DISABLE_INTRINSIC) +# if defined(_MSC_VER) && _MSC_VER>=1300 +# if !defined(_WIN32_WCE) +# include +# pragma intrinsic(_byteswap_ushort) +# pragma intrinsic(_byteswap_ulong) +# pragma intrinsic(_ReadWriteBarrier) +# else +# include +# endif +# endif +#endif + /* ** The SQLITE_THREADSAFE macro must be defined as 0, 1, or 2. ** 0 means mutexes are permanently disable and the library is never @@ -7903,10 +9192,9 @@ struct sqlite3_rtree_query_info { #endif /* -** The SQLITE_DEFAULT_MEMSTATUS macro must be defined as either 0 or 1. -** It determines whether or not the features related to -** SQLITE_CONFIG_MEMSTATUS are available by default or not. This value can -** be overridden at runtime using the sqlite3_config() API. +** EVIDENCE-OF: R-25715-37072 Memory allocation statistics are enabled by +** default unless SQLite is compiled with SQLITE_DEFAULT_MEMSTATUS=0 in +** which case memory allocation statistics are disabled by default. */ #if !defined(SQLITE_DEFAULT_MEMSTATUS) # define SQLITE_DEFAULT_MEMSTATUS 1 @@ -8061,7 +9349,33 @@ SQLITE_PRIVATE void sqlite3Coverage(int); #endif /* -** Return true (non-zero) if the input is a integer that is too large +** Declarations used for tracing the operating system interfaces. +*/ +#if defined(SQLITE_FORCE_OS_TRACE) || defined(SQLITE_TEST) || \ + (defined(SQLITE_DEBUG) && SQLITE_OS_WIN) + extern int sqlite3OSTrace; +# define OSTRACE(X) if( sqlite3OSTrace ) sqlite3DebugPrintf X +# define SQLITE_HAVE_OS_TRACE +#else +# define OSTRACE(X) +# undef SQLITE_HAVE_OS_TRACE +#endif + +/* +** Is the sqlite3ErrName() function needed in the build? Currently, +** it is needed by "mutex_w32.c" (when debugging), "os_win.c" (when +** OSTRACE is enabled), and by several "test*.c" files (which are +** compiled using SQLITE_TEST). +*/ +#if defined(SQLITE_HAVE_OS_TRACE) || defined(SQLITE_TEST) || \ + (defined(SQLITE_DEBUG) && SQLITE_OS_WIN) +# define SQLITE_NEED_ERR_NAME +#else +# undef SQLITE_NEED_ERR_NAME +#endif + +/* +** Return true (non-zero) if the input is an integer that is too large ** to fit in 32-bits. This macro is used inside of various testcase() ** macros to verify that we have tested SQLite for large-file support. */ @@ -8140,15 +9454,15 @@ struct Hash { struct HashElem { HashElem *next, *prev; /* Next and previous elements in the table */ void *data; /* Data associated with this element */ - const char *pKey; int nKey; /* Key associated with this element */ + const char *pKey; /* Key associated with this element */ }; /* ** Access routines. To delete, insert a NULL pointer. */ SQLITE_PRIVATE void sqlite3HashInit(Hash*); -SQLITE_PRIVATE void *sqlite3HashInsert(Hash*, const char *pKey, int nKey, void *pData); -SQLITE_PRIVATE void *sqlite3HashFind(const Hash*, const char *pKey, int nKey); +SQLITE_PRIVATE void *sqlite3HashInsert(Hash*, const char *pKey, void *pData); +SQLITE_PRIVATE void *sqlite3HashFind(const Hash*, const char *pKey); SQLITE_PRIVATE void sqlite3HashClear(Hash*); /* @@ -8329,16 +9643,24 @@ SQLITE_PRIVATE void sqlite3HashClear(Hash*); #define TK_TO_REAL 147 #define TK_ISNOT 148 #define TK_END_OF_FILE 149 -#define TK_ILLEGAL 150 -#define TK_SPACE 151 -#define TK_UNCLOSED_STRING 152 -#define TK_FUNCTION 153 -#define TK_COLUMN 154 -#define TK_AGG_FUNCTION 155 -#define TK_AGG_COLUMN 156 -#define TK_UMINUS 157 -#define TK_UPLUS 158 -#define TK_REGISTER 159 +#define TK_UNCLOSED_STRING 150 +#define TK_FUNCTION 151 +#define TK_COLUMN 152 +#define TK_AGG_FUNCTION 153 +#define TK_AGG_COLUMN 154 +#define TK_UMINUS 155 +#define TK_UPLUS 156 +#define TK_REGISTER 157 +#define TK_ASTERISK 158 +#define TK_SPACE 159 +#define TK_ILLEGAL 160 + +/* The token codes above must all fit in 8 bits */ +#define TKFLG_MASK 0xff + +/* Flags that can be added to a token code when it is not +** being stored in a u8: */ +#define TKFLG_DONTFOLD 0x100 /* Omit constant folding optimizations */ /************** End of parse.h ***********************************************/ /************** Continuing where we left off in sqliteInt.h ******************/ @@ -8407,6 +9729,36 @@ SQLITE_PRIVATE void sqlite3HashClear(Hash*); # define SQLITE_TEMP_STORE_xc 1 /* Exclude from ctime.c */ #endif +/* +** If no value has been provided for SQLITE_MAX_WORKER_THREADS, or if +** SQLITE_TEMP_STORE is set to 3 (never use temporary files), set it +** to zero. +*/ +#if SQLITE_TEMP_STORE==3 || SQLITE_THREADSAFE==0 +# undef SQLITE_MAX_WORKER_THREADS +# define SQLITE_MAX_WORKER_THREADS 0 +#endif +#ifndef SQLITE_MAX_WORKER_THREADS +# define SQLITE_MAX_WORKER_THREADS 8 +#endif +#ifndef SQLITE_DEFAULT_WORKER_THREADS +# define SQLITE_DEFAULT_WORKER_THREADS 0 +#endif +#if SQLITE_DEFAULT_WORKER_THREADS>SQLITE_MAX_WORKER_THREADS +# undef SQLITE_MAX_WORKER_THREADS +# define SQLITE_MAX_WORKER_THREADS SQLITE_DEFAULT_WORKER_THREADS +#endif + +/* +** The default initial allocation for the pagecache when using separate +** pagecaches for each database connection. A positive number is the +** number of pages. A negative number N translations means that a buffer +** of -1024*N bytes is allocated and used for as many pages as it will hold. +*/ +#ifndef SQLITE_DEFAULT_PCACHE_INITSZ +# define SQLITE_DEFAULT_PCACHE_INITSZ 100 +#endif + /* ** GCC does not define the offsetof() macro so we'll have to do it ** ourselves. @@ -8421,6 +9773,11 @@ SQLITE_PRIVATE void sqlite3HashClear(Hash*); #define MIN(A,B) ((A)<(B)?(A):(B)) #define MAX(A,B) ((A)>(B)?(A):(B)) +/* +** Swap two objects of type TYPE. +*/ +#define SWAP(TYPE,A,B) {TYPE t=A; A=B; B=t;} + /* ** Check to see if this machine uses EBCDIC. (Yes, believe it or ** not, there are still machines out there that use EBCDIC.) @@ -8510,7 +9867,7 @@ typedef INT8_TYPE i8; /* 1-byte signed integer */ ** gives a possible range of values of approximately 1.0e986 to 1e-986. ** But the allowed values are "grainy". Not every value is representable. ** For example, quantities 16 and 17 are both represented by a LogEst -** of 40. However, since LogEst quantaties are suppose to be estimates, +** of 40. However, since LogEst quantities are suppose to be estimates, ** not exact values, this imprecision is not a problem. ** ** "LogEst" is short for "Logarithmic Estimate". @@ -8529,6 +9886,20 @@ typedef INT8_TYPE i8; /* 1-byte signed integer */ */ typedef INT16_TYPE LogEst; +/* +** Set the SQLITE_PTRSIZE macro to the number of bytes in a pointer +*/ +#ifndef SQLITE_PTRSIZE +# if defined(__SIZEOF_POINTER__) +# define SQLITE_PTRSIZE __SIZEOF_POINTER__ +# elif defined(i386) || defined(__i386__) || defined(_M_IX86) || \ + defined(_M_ARM) || defined(__arm__) || defined(__x86) +# define SQLITE_PTRSIZE 4 +# else +# define SQLITE_PTRSIZE 8 +# endif +#endif + /* ** Macros to determine whether the machine is big or little endian, ** and whether or not that determination is run-time or compile-time. @@ -8538,11 +9909,6 @@ typedef INT16_TYPE LogEst; ** -DSQLITE_RUNTIME_BYTEORDER=1 is set, then byte-order is determined ** at run-time. */ -#ifdef SQLITE_AMALGAMATION -SQLITE_PRIVATE const int sqlite3one = 1; -#else -SQLITE_PRIVATE const int sqlite3one; -#endif #if (defined(i386) || defined(__i386__) || defined(_M_IX86) || \ defined(__x86_64) || defined(__x86_64__) || defined(_M_X64) || \ defined(_M_AMD64) || defined(_M_ARM) || defined(__x86) || \ @@ -8560,6 +9926,11 @@ SQLITE_PRIVATE const int sqlite3one; # define SQLITE_UTF16NATIVE SQLITE_UTF16BE #endif #if !defined(SQLITE_BYTEORDER) +# ifdef SQLITE_AMALGAMATION + const int sqlite3one = 1; +# else + extern const int sqlite3one; +# endif # define SQLITE_BYTEORDER 0 /* 0 means "unknown at compile-time" */ # define SQLITE_BIGENDIAN (*(char *)(&sqlite3one)==0) # define SQLITE_LITTLEENDIAN (*(char *)(&sqlite3one)==1) @@ -8591,7 +9962,7 @@ SQLITE_PRIVATE const int sqlite3one; ** all alignment restrictions correct. ** ** Except, if SQLITE_4_BYTE_ALIGNED_MALLOC is defined, then the -** underlying malloc() implemention might return us 4-byte aligned +** underlying malloc() implementation might return us 4-byte aligned ** pointers. In that case, only verify 4-byte alignment. */ #ifdef SQLITE_4_BYTE_ALIGNED_MALLOC @@ -8622,7 +9993,9 @@ SQLITE_PRIVATE const int sqlite3one; # if defined(__linux__) \ || defined(_WIN32) \ || (defined(__APPLE__) && defined(__MACH__)) \ - || defined(__sun) + || defined(__sun) \ + || defined(__FreeBSD__) \ + || defined(__DragonFly__) # define SQLITE_MAX_MMAP_SIZE 0x7fff0000 /* 2147418112 */ # else # define SQLITE_MAX_MMAP_SIZE 0 @@ -8658,6 +10031,16 @@ SQLITE_PRIVATE const int sqlite3one; # undef SQLITE_ENABLE_STAT3_OR_STAT4 #endif +/* +** SELECTTRACE_ENABLED will be either 1 or 0 depending on whether or not +** the Select query generator tracing logic is turned on. +*/ +#if defined(SQLITE_DEBUG) || defined(SQLITE_ENABLE_SELECTTRACE) +# define SELECTTRACE_ENABLED 1 +#else +# define SELECTTRACE_ENABLED 0 +#endif + /* ** An instance of the following structure is used to store the busy-handler ** callback for a given sqlite handle. @@ -8731,8 +10114,8 @@ struct BusyHandler { #define SQLITE_WSD const #define GLOBAL(t,v) (*(t*)sqlite3_wsd_find((void*)&(v), sizeof(v))) #define sqlite3GlobalConfig GLOBAL(struct Sqlite3Config, sqlite3Config) -SQLITE_API int sqlite3_wsd_init(int N, int J); -SQLITE_API void *sqlite3_wsd_find(void *K, int L); +SQLITE_API int SQLITE_STDCALL sqlite3_wsd_init(int N, int J); +SQLITE_API void *SQLITE_STDCALL sqlite3_wsd_find(void *K, int L); #else #define SQLITE_WSD #define GLOBAL(t,v) v @@ -8790,12 +10173,14 @@ typedef struct PrintfArguments PrintfArguments; typedef struct RowSet RowSet; typedef struct Savepoint Savepoint; typedef struct Select Select; +typedef struct SQLiteThread SQLiteThread; typedef struct SelectDest SelectDest; typedef struct SrcList SrcList; typedef struct StrAccum StrAccum; typedef struct Table Table; typedef struct TableLock TableLock; typedef struct Token Token; +typedef struct TreeView TreeView; typedef struct Trigger Trigger; typedef struct TriggerPrg TriggerPrg; typedef struct TriggerStep TriggerStep; @@ -8834,7 +10219,7 @@ typedef struct With With; /* TODO: This definition is just included so other modules compile. It ** needs to be revisited. */ -#define SQLITE_N_BTREE_META 10 +#define SQLITE_N_BTREE_META 16 /* ** If defined as non-zero, auto-vacuum is enabled by default. Otherwise @@ -8878,6 +10263,7 @@ SQLITE_PRIVATE int sqlite3BtreeOpen( SQLITE_PRIVATE int sqlite3BtreeClose(Btree*); SQLITE_PRIVATE int sqlite3BtreeSetCacheSize(Btree*,int); +SQLITE_PRIVATE int sqlite3BtreeSetSpillSize(Btree*,int); #if SQLITE_MAX_MMAP_SIZE>0 SQLITE_PRIVATE int sqlite3BtreeSetMmapLimit(Btree*,sqlite3_int64); #endif @@ -8888,17 +10274,15 @@ SQLITE_PRIVATE int sqlite3BtreeGetPageSize(Btree*); SQLITE_PRIVATE int sqlite3BtreeMaxPageCount(Btree*,int); SQLITE_PRIVATE u32 sqlite3BtreeLastPage(Btree*); SQLITE_PRIVATE int sqlite3BtreeSecureDelete(Btree*,int); -SQLITE_PRIVATE int sqlite3BtreeGetReserve(Btree*); -#if defined(SQLITE_HAS_CODEC) || defined(SQLITE_DEBUG) +SQLITE_PRIVATE int sqlite3BtreeGetOptimalReserve(Btree*); SQLITE_PRIVATE int sqlite3BtreeGetReserveNoMutex(Btree *p); -#endif SQLITE_PRIVATE int sqlite3BtreeSetAutoVacuum(Btree *, int); SQLITE_PRIVATE int sqlite3BtreeGetAutoVacuum(Btree *); SQLITE_PRIVATE int sqlite3BtreeBeginTrans(Btree*,int); SQLITE_PRIVATE int sqlite3BtreeCommitPhaseOne(Btree*, const char *zMaster); SQLITE_PRIVATE int sqlite3BtreeCommitPhaseTwo(Btree*, int); SQLITE_PRIVATE int sqlite3BtreeCommit(Btree*); -SQLITE_PRIVATE int sqlite3BtreeRollback(Btree*,int); +SQLITE_PRIVATE int sqlite3BtreeRollback(Btree*,int,int); SQLITE_PRIVATE int sqlite3BtreeBeginStmt(Btree*,int); SQLITE_PRIVATE int sqlite3BtreeCreateTable(Btree*, int*, int flags); SQLITE_PRIVATE int sqlite3BtreeIsInTrans(Btree*); @@ -8931,7 +10315,7 @@ SQLITE_PRIVATE int sqlite3BtreeIncrVacuum(Btree *); SQLITE_PRIVATE int sqlite3BtreeDropTable(Btree*, int, int*); SQLITE_PRIVATE int sqlite3BtreeClearTable(Btree*, int, int*); SQLITE_PRIVATE int sqlite3BtreeClearTableOfCursor(BtCursor*); -SQLITE_PRIVATE void sqlite3BtreeTripAllCursors(Btree*, int); +SQLITE_PRIVATE int sqlite3BtreeTripAllCursors(Btree*, int, int); SQLITE_PRIVATE void sqlite3BtreeGetMeta(Btree *pBtree, int idx, u32 *pValue); SQLITE_PRIVATE int sqlite3BtreeUpdateMeta(Btree*, int idx, u32 value); @@ -8949,6 +10333,11 @@ SQLITE_PRIVATE int sqlite3BtreeNewDb(Btree *p); ** For example, the free-page-count field is located at byte offset 36 of ** the database file header. The incr-vacuum-flag field is located at ** byte offset 64 (== 36+4*7). +** +** The BTREE_DATA_VERSION value is not really a value stored in the header. +** It is a read-only number computed by the pager. But we merge it with +** the header value access routines since its access pattern is the same. +** Call it a "virtual meta value". */ #define BTREE_FREE_PAGE_COUNT 0 #define BTREE_SCHEMA_VERSION 1 @@ -8959,12 +10348,68 @@ SQLITE_PRIVATE int sqlite3BtreeNewDb(Btree *p); #define BTREE_USER_VERSION 6 #define BTREE_INCR_VACUUM 7 #define BTREE_APPLICATION_ID 8 +#define BTREE_DATA_VERSION 15 /* A virtual meta-value */ /* -** Values that may be OR'd together to form the second argument of an -** sqlite3BtreeCursorHints() call. +** Kinds of hints that can be passed into the sqlite3BtreeCursorHint() +** interface. +** +** BTREE_HINT_RANGE (arguments: Expr*, Mem*) +** +** The first argument is an Expr* (which is guaranteed to be constant for +** the lifetime of the cursor) that defines constraints on which rows +** might be fetched with this cursor. The Expr* tree may contain +** TK_REGISTER nodes that refer to values stored in the array of registers +** passed as the second parameter. In other words, if Expr.op==TK_REGISTER +** then the value of the node is the value in Mem[pExpr.iTable]. Any +** TK_COLUMN node in the expression tree refers to the Expr.iColumn-th +** column of the b-tree of the cursor. The Expr tree will not contain +** any function calls nor subqueries nor references to b-trees other than +** the cursor being hinted. +** +** The design of the _RANGE hint is aid b-tree implementations that try +** to prefetch content from remote machines - to provide those +** implementations with limits on what needs to be prefetched and thereby +** reduce network bandwidth. +** +** Note that BTREE_HINT_FLAGS with BTREE_BULKLOAD is the only hint used by +** standard SQLite. The other hints are provided for extentions that use +** the SQLite parser and code generator but substitute their own storage +** engine. */ -#define BTREE_BULKLOAD 0x00000001 +#define BTREE_HINT_RANGE 0 /* Range constraints on queries */ + +/* +** Values that may be OR'd together to form the argument to the +** BTREE_HINT_FLAGS hint for sqlite3BtreeCursorHint(): +** +** The BTREE_BULKLOAD flag is set on index cursors when the index is going +** to be filled with content that is already in sorted order. +** +** The BTREE_SEEK_EQ flag is set on cursors that will get OP_SeekGE or +** OP_SeekLE opcodes for a range search, but where the range of entries +** selected will all have the same key. In other words, the cursor will +** be used only for equality key searches. +** +*/ +#define BTREE_BULKLOAD 0x00000001 /* Used to full index in sorted order */ +#define BTREE_SEEK_EQ 0x00000002 /* EQ seeks only - no range seeks */ + +/* +** Flags passed as the third argument to sqlite3BtreeCursor(). +** +** For read-only cursors the wrFlag argument is always zero. For read-write +** cursors it may be set to either (BTREE_WRCSR|BTREE_FORDELETE) or +** (BTREE_WRCSR). If the BTREE_FORDELETE flag is set, then the cursor will +** only be used by SQLite for the following: +** +** * to seek to and delete specific entries, and/or +** +** * to read values that will be used to create keys that other +** BTREE_FORDELETE cursors will seek to and delete. +*/ +#define BTREE_WRCSR 0x00000004 /* read-write cursor */ +#define BTREE_FORDELETE 0x00000008 /* Cursor is for seek/delete only */ SQLITE_PRIVATE int sqlite3BtreeCursor( Btree*, /* BTree containing table to open */ @@ -8975,6 +10420,10 @@ SQLITE_PRIVATE int sqlite3BtreeCursor( ); SQLITE_PRIVATE int sqlite3BtreeCursorSize(void); SQLITE_PRIVATE void sqlite3BtreeCursorZero(BtCursor*); +SQLITE_PRIVATE void sqlite3BtreeCursorHintFlags(BtCursor*, unsigned); +#ifdef SQLITE_ENABLE_CURSOR_HINTS +SQLITE_PRIVATE void sqlite3BtreeCursorHint(BtCursor*, int, ...); +#endif SQLITE_PRIVATE int sqlite3BtreeCloseCursor(BtCursor*); SQLITE_PRIVATE int sqlite3BtreeMovetoUnpacked( @@ -8984,8 +10433,9 @@ SQLITE_PRIVATE int sqlite3BtreeMovetoUnpacked( int bias, int *pRes ); -SQLITE_PRIVATE int sqlite3BtreeCursorHasMoved(BtCursor*, int*); -SQLITE_PRIVATE int sqlite3BtreeDelete(BtCursor*); +SQLITE_PRIVATE int sqlite3BtreeCursorHasMoved(BtCursor*); +SQLITE_PRIVATE int sqlite3BtreeCursorRestore(BtCursor*, int*); +SQLITE_PRIVATE int sqlite3BtreeDelete(BtCursor*, int); SQLITE_PRIVATE int sqlite3BtreeInsert(BtCursor*, const void *pKey, i64 nKey, const void *pData, int nData, int nZero, int bias, int seekResult); @@ -9008,8 +10458,9 @@ SQLITE_PRIVATE int sqlite3BtreePutData(BtCursor*, u32 offset, u32 amt, void*); SQLITE_PRIVATE void sqlite3BtreeIncrblobCursor(BtCursor *); SQLITE_PRIVATE void sqlite3BtreeClearCursor(BtCursor *); SQLITE_PRIVATE int sqlite3BtreeSetVersion(Btree *pBt, int iVersion); -SQLITE_PRIVATE void sqlite3BtreeCursorHints(BtCursor *, unsigned int mask); +SQLITE_PRIVATE int sqlite3BtreeCursorHasHint(BtCursor*, unsigned int mask); SQLITE_PRIVATE int sqlite3BtreeIsReadonly(Btree *pBt); +SQLITE_PRIVATE int sqlite3HeaderSizeBtree(void); #ifndef NDEBUG SQLITE_PRIVATE int sqlite3BtreeCursorIsValid(BtCursor*); @@ -9121,19 +10572,23 @@ struct VdbeOp { int p1; /* First operand */ int p2; /* Second parameter (often the jump destination) */ int p3; /* The third parameter */ - union { /* fourth parameter */ + union p4union { /* fourth parameter */ int i; /* Integer value if p4type==P4_INT32 */ void *p; /* Generic pointer */ char *z; /* Pointer to data for string (char array) types */ i64 *pI64; /* Used when p4type is P4_INT64 */ double *pReal; /* Used when p4type is P4_REAL */ FuncDef *pFunc; /* Used when p4type is P4_FUNCDEF */ + sqlite3_context *pCtx; /* Used when p4type is P4_FUNCCTX */ CollSeq *pColl; /* Used when p4type is P4_COLLSEQ */ Mem *pMem; /* Used when p4type is P4_MEM */ VTable *pVtab; /* Used when p4type is P4_VTAB */ KeyInfo *pKeyInfo; /* Used when p4type is P4_KEYINFO */ int *ai; /* Used when p4type is P4_INTARRAY */ SubProgram *pProgram; /* Used when p4type is P4_SUBPROGRAM */ +#ifdef SQLITE_ENABLE_CURSOR_HINTS + Expr *pExpr; /* Used when p4type is P4_EXPR */ +#endif int (*xAdvance)(BtCursor *, int *); } p4; #ifdef SQLITE_ENABLE_EXPLAIN_COMMENTS @@ -9184,6 +10639,7 @@ typedef struct VdbeOpList VdbeOpList; #define P4_COLLSEQ (-4) /* P4 is a pointer to a CollSeq structure */ #define P4_FUNCDEF (-5) /* P4 is a pointer to a FuncDef structure */ #define P4_KEYINFO (-6) /* P4 is a pointer to a KeyInfo structure */ +#define P4_EXPR (-7) /* P4 is a pointer to an Expr tree */ #define P4_MEM (-8) /* P4 is a pointer to a Mem* structure */ #define P4_TRANSIENT 0 /* P4 is a pointer to a transient string */ #define P4_VTAB (-10) /* P4 is a pointer to an sqlite3_vtab structure */ @@ -9194,6 +10650,7 @@ typedef struct VdbeOpList VdbeOpList; #define P4_INTARRAY (-15) /* P4 is a vector of 32-bit integers */ #define P4_SUBPROGRAM (-18) /* P4 is a pointer to a SubProgram structure */ #define P4_ADVANCE (-19) /* P4 is a pointer to BtreeNext() or BtreePrev() */ +#define P4_FUNCCTX (-20) /* P4 is a pointer to an sqlite3_context object */ /* Error message codes for OP_Halt */ #define P5_ConstraintNotNull 1 @@ -9235,82 +10692,82 @@ typedef struct VdbeOpList VdbeOpList; /************** Include opcodes.h in the middle of vdbe.h ********************/ /************** Begin file opcodes.h *****************************************/ /* Automatically generated. Do not edit */ -/* See the mkopcodeh.awk script for details */ -#define OP_Function 1 /* synopsis: r[P3]=func(r[P2@P5]) */ -#define OP_Savepoint 2 -#define OP_AutoCommit 3 -#define OP_Transaction 4 -#define OP_SorterNext 5 -#define OP_PrevIfOpen 6 -#define OP_NextIfOpen 7 -#define OP_Prev 8 -#define OP_Next 9 -#define OP_AggStep 10 /* synopsis: accum=r[P3] step(r[P2@P5]) */ -#define OP_Checkpoint 11 -#define OP_JournalMode 12 -#define OP_Vacuum 13 -#define OP_VFilter 14 /* synopsis: iplan=r[P3] zplan='P4' */ -#define OP_VUpdate 15 /* synopsis: data=r[P3@P2] */ -#define OP_Goto 16 -#define OP_Gosub 17 -#define OP_Return 18 +/* See the tool/mkopcodeh.tcl script for details */ +#define OP_Savepoint 1 +#define OP_AutoCommit 2 +#define OP_Transaction 3 +#define OP_SorterNext 4 +#define OP_PrevIfOpen 5 +#define OP_NextIfOpen 6 +#define OP_Prev 7 +#define OP_Next 8 +#define OP_Checkpoint 9 +#define OP_JournalMode 10 +#define OP_Vacuum 11 +#define OP_VFilter 12 /* synopsis: iplan=r[P3] zplan='P4' */ +#define OP_VUpdate 13 /* synopsis: data=r[P3@P2] */ +#define OP_Goto 14 +#define OP_Gosub 15 +#define OP_Return 16 +#define OP_InitCoroutine 17 +#define OP_EndCoroutine 18 #define OP_Not 19 /* same as TK_NOT, synopsis: r[P2]= !r[P1] */ -#define OP_InitCoroutine 20 -#define OP_EndCoroutine 21 -#define OP_Yield 22 -#define OP_HaltIfNull 23 /* synopsis: if r[P3]=null halt */ -#define OP_Halt 24 -#define OP_Integer 25 /* synopsis: r[P2]=P1 */ -#define OP_Int64 26 /* synopsis: r[P2]=P4 */ -#define OP_String 27 /* synopsis: r[P2]='P4' (len=P1) */ -#define OP_Null 28 /* synopsis: r[P2..P3]=NULL */ -#define OP_SoftNull 29 /* synopsis: r[P1]=NULL */ -#define OP_Blob 30 /* synopsis: r[P2]=P4 (len=P1) */ -#define OP_Variable 31 /* synopsis: r[P2]=parameter(P1,P4) */ -#define OP_Move 32 /* synopsis: r[P2@P3]=r[P1@P3] */ -#define OP_Copy 33 /* synopsis: r[P2@P3+1]=r[P1@P3+1] */ -#define OP_SCopy 34 /* synopsis: r[P2]=r[P1] */ -#define OP_ResultRow 35 /* synopsis: output=r[P1@P2] */ -#define OP_CollSeq 36 -#define OP_AddImm 37 /* synopsis: r[P1]=r[P1]+P2 */ -#define OP_MustBeInt 38 -#define OP_RealAffinity 39 -#define OP_Permutation 40 -#define OP_Compare 41 /* synopsis: r[P1@P3] <-> r[P2@P3] */ -#define OP_Jump 42 -#define OP_Once 43 -#define OP_If 44 -#define OP_IfNot 45 -#define OP_Column 46 /* synopsis: r[P3]=PX */ -#define OP_Affinity 47 /* synopsis: affinity(r[P1@P2]) */ -#define OP_MakeRecord 48 /* synopsis: r[P3]=mkrec(r[P1@P2]) */ -#define OP_Count 49 /* synopsis: r[P2]=count() */ -#define OP_ReadCookie 50 -#define OP_SetCookie 51 -#define OP_OpenRead 52 /* synopsis: root=P2 iDb=P3 */ -#define OP_OpenWrite 53 /* synopsis: root=P2 iDb=P3 */ -#define OP_OpenAutoindex 54 /* synopsis: nColumn=P2 */ -#define OP_OpenEphemeral 55 /* synopsis: nColumn=P2 */ -#define OP_SorterOpen 56 -#define OP_OpenPseudo 57 /* synopsis: P3 columns in r[P2] */ -#define OP_Close 58 -#define OP_SeekLT 59 -#define OP_SeekLE 60 -#define OP_SeekGE 61 -#define OP_SeekGT 62 -#define OP_Seek 63 /* synopsis: intkey=r[P2] */ -#define OP_NoConflict 64 /* synopsis: key=r[P3@P4] */ -#define OP_NotFound 65 /* synopsis: key=r[P3@P4] */ -#define OP_Found 66 /* synopsis: key=r[P3@P4] */ -#define OP_NotExists 67 /* synopsis: intkey=r[P3] */ -#define OP_Sequence 68 /* synopsis: r[P2]=cursor[P1].ctr++ */ -#define OP_NewRowid 69 /* synopsis: r[P2]=rowid */ -#define OP_Insert 70 /* synopsis: intkey=r[P3] data=r[P2] */ +#define OP_Yield 20 +#define OP_HaltIfNull 21 /* synopsis: if r[P3]=null halt */ +#define OP_Halt 22 +#define OP_Integer 23 /* synopsis: r[P2]=P1 */ +#define OP_Int64 24 /* synopsis: r[P2]=P4 */ +#define OP_String 25 /* synopsis: r[P2]='P4' (len=P1) */ +#define OP_Null 26 /* synopsis: r[P2..P3]=NULL */ +#define OP_SoftNull 27 /* synopsis: r[P1]=NULL */ +#define OP_Blob 28 /* synopsis: r[P2]=P4 (len=P1) */ +#define OP_Variable 29 /* synopsis: r[P2]=parameter(P1,P4) */ +#define OP_Move 30 /* synopsis: r[P2@P3]=r[P1@P3] */ +#define OP_Copy 31 /* synopsis: r[P2@P3+1]=r[P1@P3+1] */ +#define OP_SCopy 32 /* synopsis: r[P2]=r[P1] */ +#define OP_IntCopy 33 /* synopsis: r[P2]=r[P1] */ +#define OP_ResultRow 34 /* synopsis: output=r[P1@P2] */ +#define OP_CollSeq 35 +#define OP_Function0 36 /* synopsis: r[P3]=func(r[P2@P5]) */ +#define OP_Function 37 /* synopsis: r[P3]=func(r[P2@P5]) */ +#define OP_AddImm 38 /* synopsis: r[P1]=r[P1]+P2 */ +#define OP_MustBeInt 39 +#define OP_RealAffinity 40 +#define OP_Cast 41 /* synopsis: affinity(r[P1]) */ +#define OP_Permutation 42 +#define OP_Compare 43 /* synopsis: r[P1@P3] <-> r[P2@P3] */ +#define OP_Jump 44 +#define OP_Once 45 +#define OP_If 46 +#define OP_IfNot 47 +#define OP_Column 48 /* synopsis: r[P3]=PX */ +#define OP_Affinity 49 /* synopsis: affinity(r[P1@P2]) */ +#define OP_MakeRecord 50 /* synopsis: r[P3]=mkrec(r[P1@P2]) */ +#define OP_Count 51 /* synopsis: r[P2]=count() */ +#define OP_ReadCookie 52 +#define OP_SetCookie 53 +#define OP_ReopenIdx 54 /* synopsis: root=P2 iDb=P3 */ +#define OP_OpenRead 55 /* synopsis: root=P2 iDb=P3 */ +#define OP_OpenWrite 56 /* synopsis: root=P2 iDb=P3 */ +#define OP_OpenAutoindex 57 /* synopsis: nColumn=P2 */ +#define OP_OpenEphemeral 58 /* synopsis: nColumn=P2 */ +#define OP_SorterOpen 59 +#define OP_SequenceTest 60 /* synopsis: if( cursor[P1].ctr++ ) pc = P2 */ +#define OP_OpenPseudo 61 /* synopsis: P3 columns in r[P2] */ +#define OP_Close 62 +#define OP_ColumnsUsed 63 +#define OP_SeekLT 64 /* synopsis: key=r[P3@P4] */ +#define OP_SeekLE 65 /* synopsis: key=r[P3@P4] */ +#define OP_SeekGE 66 /* synopsis: key=r[P3@P4] */ +#define OP_SeekGT 67 /* synopsis: key=r[P3@P4] */ +#define OP_Seek 68 /* synopsis: intkey=r[P2] */ +#define OP_NoConflict 69 /* synopsis: key=r[P3@P4] */ +#define OP_NotFound 70 /* synopsis: key=r[P3@P4] */ #define OP_Or 71 /* same as TK_OR, synopsis: r[P3]=(r[P1] || r[P2]) */ #define OP_And 72 /* same as TK_AND, synopsis: r[P3]=(r[P1] && r[P2]) */ -#define OP_InsertInt 73 /* synopsis: intkey=P3 data=r[P2] */ -#define OP_Delete 74 -#define OP_ResetCount 75 +#define OP_Found 73 /* synopsis: key=r[P3@P4] */ +#define OP_NotExists 74 /* synopsis: intkey=r[P3] */ +#define OP_Sequence 75 /* synopsis: r[P2]=cursor[P1].ctr++ */ #define OP_IsNull 76 /* same as TK_ISNULL, synopsis: if r[P1]==NULL goto P2 */ #define OP_NotNull 77 /* same as TK_NOTNULL, synopsis: if r[P1]!=NULL goto P2 */ #define OP_Ne 78 /* same as TK_NE, synopsis: if r[P1]!=r[P3] goto P2 */ @@ -9319,7 +10776,7 @@ typedef struct VdbeOpList VdbeOpList; #define OP_Le 81 /* same as TK_LE, synopsis: if r[P1]<=r[P3] goto P2 */ #define OP_Lt 82 /* same as TK_LT, synopsis: if r[P1]=r[P3] goto P2 */ -#define OP_SorterCompare 84 /* synopsis: if key(P1)!=rtrim(r[P3],P4) goto P2 */ +#define OP_NewRowid 84 /* synopsis: r[P2]=rowid */ #define OP_BitAnd 85 /* same as TK_BITAND, synopsis: r[P3]=r[P1]&r[P2] */ #define OP_BitOr 86 /* same as TK_BITOR, synopsis: r[P3]=r[P1]|r[P2] */ #define OP_ShiftLeft 87 /* same as TK_LSHIFT, synopsis: r[P3]=r[P2]<0 goto P2 */ -#define OP_IfNeg 135 /* synopsis: if r[P1]<0 goto P2 */ -#define OP_IfZero 136 /* synopsis: r[P1]+=P3, if r[P1]==0 goto P2 */ -#define OP_AggFinal 137 /* synopsis: accum=r[P1] N=P2 */ -#define OP_IncrVacuum 138 -#define OP_Expire 139 -#define OP_TableLock 140 /* synopsis: iDb=P1 root=P2 write=P3 */ -#define OP_VBegin 141 -#define OP_VCreate 142 -#define OP_ToText 143 /* same as TK_TO_TEXT */ -#define OP_ToBlob 144 /* same as TK_TO_BLOB */ -#define OP_ToNumeric 145 /* same as TK_TO_NUMERIC */ -#define OP_ToInt 146 /* same as TK_TO_INT */ -#define OP_ToReal 147 /* same as TK_TO_REAL */ -#define OP_VDestroy 148 -#define OP_VOpen 149 -#define OP_VColumn 150 /* synopsis: r[P3]=vcolumn(P2) */ -#define OP_VNext 151 -#define OP_VRename 152 -#define OP_Pagecount 153 -#define OP_MaxPgcnt 154 -#define OP_Init 155 /* synopsis: Start at P2 */ -#define OP_Noop 156 -#define OP_Explain 157 - +#define OP_Program 134 +#define OP_Param 135 +#define OP_FkCounter 136 /* synopsis: fkctr[P1]+=P2 */ +#define OP_FkIfZero 137 /* synopsis: if fkctr[P1]==0 goto P2 */ +#define OP_MemMax 138 /* synopsis: r[P1]=max(r[P1],r[P2]) */ +#define OP_IfPos 139 /* synopsis: if r[P1]>0 then r[P1]-=P3, goto P2 */ +#define OP_SetIfNotPos 140 /* synopsis: if r[P1]<=0 then r[P2]=P3 */ +#define OP_IfNotZero 141 /* synopsis: if r[P1]!=0 then r[P1]-=P3, goto P2 */ +#define OP_DecrJumpZero 142 /* synopsis: if (--r[P1])==0 goto P2 */ +#define OP_JumpZeroIncr 143 /* synopsis: if (r[P1]++)==0 ) goto P2 */ +#define OP_AggStep0 144 /* synopsis: accum=r[P3] step(r[P2@P5]) */ +#define OP_AggStep 145 /* synopsis: accum=r[P3] step(r[P2@P5]) */ +#define OP_AggFinal 146 /* synopsis: accum=r[P1] N=P2 */ +#define OP_IncrVacuum 147 +#define OP_Expire 148 +#define OP_TableLock 149 /* synopsis: iDb=P1 root=P2 write=P3 */ +#define OP_VBegin 150 +#define OP_VCreate 151 +#define OP_VDestroy 152 +#define OP_VOpen 153 +#define OP_VColumn 154 /* synopsis: r[P3]=vcolumn(P2) */ +#define OP_VNext 155 +#define OP_VRename 156 +#define OP_Pagecount 157 +#define OP_MaxPgcnt 158 +#define OP_Init 159 /* synopsis: Start at P2 */ +#define OP_CursorHint 160 +#define OP_Noop 161 +#define OP_Explain 162 /* Properties such as "out2" or "jump" that are specified in ** comments following the "case" for each opcode in the vdbe.c ** are encoded into bitvectors as follows: */ #define OPFLG_JUMP 0x0001 /* jump: P2 holds jmp target */ -#define OPFLG_OUT2_PRERELEASE 0x0002 /* out2-prerelease: */ -#define OPFLG_IN1 0x0004 /* in1: P1 is an input */ -#define OPFLG_IN2 0x0008 /* in2: P2 is an input */ -#define OPFLG_IN3 0x0010 /* in3: P3 is an input */ -#define OPFLG_OUT2 0x0020 /* out2: P2 is an output */ -#define OPFLG_OUT3 0x0040 /* out3: P3 is an output */ +#define OPFLG_IN1 0x0002 /* in1: P1 is an input */ +#define OPFLG_IN2 0x0004 /* in2: P2 is an input */ +#define OPFLG_IN3 0x0008 /* in3: P3 is an input */ +#define OPFLG_OUT2 0x0010 /* out2: P2 is an output */ +#define OPFLG_OUT3 0x0020 /* out3: P3 is an output */ #define OPFLG_INITIALIZER {\ -/* 0 */ 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x01, 0x01,\ -/* 8 */ 0x01, 0x01, 0x00, 0x00, 0x02, 0x00, 0x01, 0x00,\ -/* 16 */ 0x01, 0x01, 0x04, 0x24, 0x01, 0x04, 0x05, 0x10,\ -/* 24 */ 0x00, 0x02, 0x02, 0x02, 0x02, 0x00, 0x02, 0x02,\ -/* 32 */ 0x00, 0x00, 0x20, 0x00, 0x00, 0x04, 0x05, 0x04,\ -/* 40 */ 0x00, 0x00, 0x01, 0x01, 0x05, 0x05, 0x00, 0x00,\ -/* 48 */ 0x00, 0x02, 0x02, 0x10, 0x00, 0x00, 0x00, 0x00,\ -/* 56 */ 0x00, 0x00, 0x00, 0x11, 0x11, 0x11, 0x11, 0x08,\ -/* 64 */ 0x11, 0x11, 0x11, 0x11, 0x02, 0x02, 0x00, 0x4c,\ -/* 72 */ 0x4c, 0x00, 0x00, 0x00, 0x05, 0x05, 0x15, 0x15,\ -/* 80 */ 0x15, 0x15, 0x15, 0x15, 0x00, 0x4c, 0x4c, 0x4c,\ -/* 88 */ 0x4c, 0x4c, 0x4c, 0x4c, 0x4c, 0x4c, 0x4c, 0x00,\ -/* 96 */ 0x24, 0x02, 0x00, 0x00, 0x02, 0x00, 0x01, 0x01,\ -/* 104 */ 0x01, 0x01, 0x08, 0x08, 0x00, 0x02, 0x01, 0x01,\ -/* 112 */ 0x01, 0x01, 0x02, 0x00, 0x00, 0x02, 0x02, 0x00,\ -/* 120 */ 0x00, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x45, 0x15,\ -/* 128 */ 0x01, 0x02, 0x00, 0x01, 0x08, 0x02, 0x05, 0x05,\ -/* 136 */ 0x05, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x04,\ -/* 144 */ 0x04, 0x04, 0x04, 0x04, 0x00, 0x00, 0x00, 0x01,\ -/* 152 */ 0x00, 0x02, 0x02, 0x01, 0x00, 0x00,} +/* 0 */ 0x00, 0x00, 0x00, 0x00, 0x01, 0x01, 0x01, 0x01,\ +/* 8 */ 0x01, 0x00, 0x10, 0x00, 0x01, 0x00, 0x01, 0x01,\ +/* 16 */ 0x02, 0x01, 0x02, 0x12, 0x03, 0x08, 0x00, 0x10,\ +/* 24 */ 0x10, 0x10, 0x10, 0x00, 0x10, 0x10, 0x00, 0x00,\ +/* 32 */ 0x10, 0x10, 0x00, 0x00, 0x00, 0x00, 0x02, 0x03,\ +/* 40 */ 0x02, 0x02, 0x00, 0x00, 0x01, 0x01, 0x03, 0x03,\ +/* 48 */ 0x00, 0x00, 0x00, 0x10, 0x10, 0x08, 0x00, 0x00,\ +/* 56 */ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,\ +/* 64 */ 0x09, 0x09, 0x09, 0x09, 0x04, 0x09, 0x09, 0x26,\ +/* 72 */ 0x26, 0x09, 0x09, 0x10, 0x03, 0x03, 0x0b, 0x0b,\ +/* 80 */ 0x0b, 0x0b, 0x0b, 0x0b, 0x10, 0x26, 0x26, 0x26,\ +/* 88 */ 0x26, 0x26, 0x26, 0x26, 0x26, 0x26, 0x26, 0x00,\ +/* 96 */ 0x12, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,\ +/* 104 */ 0x00, 0x10, 0x00, 0x01, 0x01, 0x01, 0x01, 0x04,\ +/* 112 */ 0x04, 0x00, 0x10, 0x01, 0x01, 0x01, 0x01, 0x10,\ +/* 120 */ 0x00, 0x00, 0x10, 0x10, 0x00, 0x00, 0x00, 0x00,\ +/* 128 */ 0x00, 0x00, 0x06, 0x23, 0x0b, 0x10, 0x01, 0x10,\ +/* 136 */ 0x00, 0x01, 0x04, 0x03, 0x06, 0x03, 0x03, 0x03,\ +/* 144 */ 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00,\ +/* 152 */ 0x00, 0x00, 0x00, 0x01, 0x00, 0x10, 0x10, 0x01,\ +/* 160 */ 0x00, 0x00, 0x00,} /************** End of opcodes.h *********************************************/ /************** Continuing where we left off in vdbe.h ***********************/ @@ -9439,11 +10900,16 @@ SQLITE_PRIVATE Vdbe *sqlite3VdbeCreate(Parse*); SQLITE_PRIVATE int sqlite3VdbeAddOp0(Vdbe*,int); SQLITE_PRIVATE int sqlite3VdbeAddOp1(Vdbe*,int,int); SQLITE_PRIVATE int sqlite3VdbeAddOp2(Vdbe*,int,int,int); +SQLITE_PRIVATE int sqlite3VdbeGoto(Vdbe*,int); +SQLITE_PRIVATE int sqlite3VdbeLoadString(Vdbe*,int,const char*); +SQLITE_PRIVATE void sqlite3VdbeMultiLoad(Vdbe*,int,const char*,...); SQLITE_PRIVATE int sqlite3VdbeAddOp3(Vdbe*,int,int,int,int); SQLITE_PRIVATE int sqlite3VdbeAddOp4(Vdbe*,int,int,int,int,const char *zP4,int); +SQLITE_PRIVATE int sqlite3VdbeAddOp4Dup8(Vdbe*,int,int,int,int,const u8*,int); SQLITE_PRIVATE int sqlite3VdbeAddOp4Int(Vdbe*,int,int,int,int,int); SQLITE_PRIVATE int sqlite3VdbeAddOpList(Vdbe*, int nOp, VdbeOpList const *aOp, int iLineno); SQLITE_PRIVATE void sqlite3VdbeAddParseSchemaOp(Vdbe*,int,char*); +SQLITE_PRIVATE void sqlite3VdbeChangeOpcode(Vdbe*, u32 addr, u8); SQLITE_PRIVATE void sqlite3VdbeChangeP1(Vdbe*, u32 addr, int P1); SQLITE_PRIVATE void sqlite3VdbeChangeP2(Vdbe*, u32 addr, int P2); SQLITE_PRIVATE void sqlite3VdbeChangeP3(Vdbe*, u32 addr, int P3); @@ -9481,12 +10947,14 @@ SQLITE_PRIVATE void sqlite3VdbeSetVarmask(Vdbe*, int); #ifndef SQLITE_OMIT_TRACE SQLITE_PRIVATE char *sqlite3VdbeExpandSql(Vdbe*, const char*); #endif +SQLITE_PRIVATE int sqlite3MemCompare(const Mem*, const Mem*, const CollSeq*); SQLITE_PRIVATE void sqlite3VdbeRecordUnpack(KeyInfo*,int,const void*,UnpackedRecord*); -SQLITE_PRIVATE int sqlite3VdbeRecordCompare(int,const void*,UnpackedRecord*,int); +SQLITE_PRIVATE int sqlite3VdbeRecordCompare(int,const void*,UnpackedRecord*); +SQLITE_PRIVATE int sqlite3VdbeRecordCompareWithSkip(int, const void *, UnpackedRecord *, int); SQLITE_PRIVATE UnpackedRecord *sqlite3VdbeAllocUnpackedRecord(KeyInfo *, char *, int, char **); -typedef int (*RecordCompare)(int,const void*,UnpackedRecord*,int); +typedef int (*RecordCompare)(int,const void*,UnpackedRecord*); SQLITE_PRIVATE RecordCompare sqlite3VdbeFindCompare(UnpackedRecord*); #ifndef SQLITE_OMIT_TRIGGER @@ -9553,6 +11021,12 @@ SQLITE_PRIVATE void sqlite3VdbeSetLineNumber(Vdbe*,int); # define VDBE_OFFSET_LINENO(x) 0 #endif +#ifdef SQLITE_ENABLE_STMT_SCANSTATUS +SQLITE_PRIVATE void sqlite3VdbeScanStatus(Vdbe*, int, int, int, LogEst, const char*); +#else +# define sqlite3VdbeScanStatus(a,b,c,d,e) +#endif + #endif /************** End of vdbe.h ************************************************/ @@ -9640,7 +11114,7 @@ typedef struct PgHdr DbPage; #define PAGER_JOURNALMODE_WAL 5 /* Use write-ahead logging */ /* -** Flags that make up the mask passed to sqlite3PagerAcquire(). +** Flags that make up the mask passed to sqlite3PagerGet(). */ #define PAGER_GET_NOCONTENT 0x01 /* Do not load data from disk */ #define PAGER_GET_READONLY 0x02 /* Read-only page is acceptable */ @@ -9679,8 +11153,12 @@ SQLITE_PRIVATE int sqlite3PagerReadFileheader(Pager*, int, unsigned char*); /* Functions used to configure a Pager object. */ SQLITE_PRIVATE void sqlite3PagerSetBusyhandler(Pager*, int(*)(void *), void *); SQLITE_PRIVATE int sqlite3PagerSetPagesize(Pager*, u32*, int); +#ifdef SQLITE_HAS_CODEC +SQLITE_PRIVATE void sqlite3PagerAlignReserve(Pager*,Pager*); +#endif SQLITE_PRIVATE int sqlite3PagerMaxPageCount(Pager*, int); SQLITE_PRIVATE void sqlite3PagerSetCachesize(Pager*, int); +SQLITE_PRIVATE int sqlite3PagerSetSpillsize(Pager*, int); SQLITE_PRIVATE void sqlite3PagerSetMmapLimit(Pager *, sqlite3_int64); SQLITE_PRIVATE void sqlite3PagerShrink(Pager*); SQLITE_PRIVATE void sqlite3PagerSetFlags(Pager*,unsigned); @@ -9690,10 +11168,10 @@ SQLITE_PRIVATE int sqlite3PagerGetJournalMode(Pager*); SQLITE_PRIVATE int sqlite3PagerOkToChangeJournalMode(Pager*); SQLITE_PRIVATE i64 sqlite3PagerJournalSizeLimit(Pager *, i64); SQLITE_PRIVATE sqlite3_backup **sqlite3PagerBackupPtr(Pager*); +SQLITE_PRIVATE int sqlite3PagerFlush(Pager*); /* Functions used to obtain and release page references. */ -SQLITE_PRIVATE int sqlite3PagerAcquire(Pager *pPager, Pgno pgno, DbPage **ppPage, int clrFlag); -#define sqlite3PagerGet(A,B,C) sqlite3PagerAcquire(A,B,C,0) +SQLITE_PRIVATE int sqlite3PagerGet(Pager *pPager, Pgno pgno, DbPage **ppPage, int clrFlag); SQLITE_PRIVATE DbPage *sqlite3PagerLookup(Pager *pPager, Pgno pgno); SQLITE_PRIVATE void sqlite3PagerRef(DbPage*); SQLITE_PRIVATE void sqlite3PagerUnref(DbPage*); @@ -9725,6 +11203,10 @@ SQLITE_PRIVATE int sqlite3PagerWalSupported(Pager *pPager); SQLITE_PRIVATE int sqlite3PagerWalCallback(Pager *pPager); SQLITE_PRIVATE int sqlite3PagerOpenWal(Pager *pPager, int *pisOpen); SQLITE_PRIVATE int sqlite3PagerCloseWal(Pager *pPager); +# ifdef SQLITE_ENABLE_SNAPSHOT +SQLITE_PRIVATE int sqlite3PagerSnapshotGet(Pager *pPager, sqlite3_snapshot **ppSnapshot); +SQLITE_PRIVATE int sqlite3PagerSnapshotOpen(Pager *pPager, sqlite3_snapshot *pSnapshot); +# endif #endif #ifdef SQLITE_ENABLE_ZIPVFS @@ -9733,11 +11215,15 @@ SQLITE_PRIVATE int sqlite3PagerWalFramesize(Pager *pPager); /* Functions used to query pager state and configuration. */ SQLITE_PRIVATE u8 sqlite3PagerIsreadonly(Pager*); -SQLITE_PRIVATE int sqlite3PagerRefcount(Pager*); +SQLITE_PRIVATE u32 sqlite3PagerDataVersion(Pager*); +#ifdef SQLITE_DEBUG +SQLITE_PRIVATE int sqlite3PagerRefcount(Pager*); +#endif SQLITE_PRIVATE int sqlite3PagerMemUsed(Pager*); SQLITE_PRIVATE const char *sqlite3PagerFilename(Pager*, int); -SQLITE_PRIVATE const sqlite3_vfs *sqlite3PagerVfs(Pager*); +SQLITE_PRIVATE sqlite3_vfs *sqlite3PagerVfs(Pager*); SQLITE_PRIVATE sqlite3_file *sqlite3PagerFile(Pager*); +SQLITE_PRIVATE sqlite3_file *sqlite3PagerJrnlFile(Pager*); SQLITE_PRIVATE const char *sqlite3PagerJournalname(Pager*); SQLITE_PRIVATE int sqlite3PagerNosync(Pager*); SQLITE_PRIVATE void *sqlite3PagerTempSpace(Pager*); @@ -9749,6 +11235,8 @@ SQLITE_PRIVATE int sqlite3SectorSize(sqlite3_file *); /* Functions used to truncate the database file. */ SQLITE_PRIVATE void sqlite3PagerTruncateImage(Pager*,Pgno); +SQLITE_PRIVATE void sqlite3PagerRekey(DbPage*, Pgno, u16); + #if defined(SQLITE_HAS_CODEC) && !defined(SQLITE_OMIT_WAL) SQLITE_PRIVATE void *sqlite3PagerCodec(DbPage *); #endif @@ -9822,14 +11310,14 @@ struct PgHdr { }; /* Bit values for PgHdr.flags */ -#define PGHDR_DIRTY 0x002 /* Page has changed */ -#define PGHDR_NEED_SYNC 0x004 /* Fsync the rollback journal before - ** writing this page to the database */ -#define PGHDR_NEED_READ 0x008 /* Content is unread */ -#define PGHDR_REUSE_UNLIKELY 0x010 /* A hint that reuse is unlikely */ -#define PGHDR_DONT_WRITE 0x020 /* Do not write content to disk */ - -#define PGHDR_MMAP 0x040 /* This is an mmap page object */ +#define PGHDR_CLEAN 0x001 /* Page not on the PCache.pDirty list */ +#define PGHDR_DIRTY 0x002 /* Page is on the PCache.pDirty list */ +#define PGHDR_WRITEABLE 0x004 /* Journaled and ready to modify */ +#define PGHDR_NEED_SYNC 0x008 /* Fsync the rollback journal before + ** writing this page to the database */ +#define PGHDR_NEED_READ 0x010 /* Content is unread */ +#define PGHDR_DONT_WRITE 0x020 /* Do not write content to disk */ +#define PGHDR_MMAP 0x040 /* This is an mmap page object */ /* Initialize and shutdown the page cache subsystem */ SQLITE_PRIVATE int sqlite3PcacheInitialize(void); @@ -9844,7 +11332,7 @@ SQLITE_PRIVATE void sqlite3PCacheBufferSetup(void *, int sz, int n); ** Under memory stress, invoke xStress to try to make pages clean. ** Only clean and unpinned pages can be reclaimed. */ -SQLITE_PRIVATE void sqlite3PcacheOpen( +SQLITE_PRIVATE int sqlite3PcacheOpen( int szPage, /* Size of every page */ int szExtra, /* Extra space associated with each page */ int bPurgeable, /* True if pages are on backing store */ @@ -9854,7 +11342,7 @@ SQLITE_PRIVATE void sqlite3PcacheOpen( ); /* Modify the page-size after the cache has been created. */ -SQLITE_PRIVATE void sqlite3PcacheSetPageSize(PCache *, int); +SQLITE_PRIVATE int sqlite3PcacheSetPageSize(PCache *, int); /* Return the size in bytes of a PCache object. Used to preallocate ** storage space. @@ -9864,7 +11352,9 @@ SQLITE_PRIVATE int sqlite3PcacheSize(void); /* One release per successful fetch. Page is pinned until released. ** Reference counted. */ -SQLITE_PRIVATE int sqlite3PcacheFetch(PCache*, Pgno, int createFlag, PgHdr**); +SQLITE_PRIVATE sqlite3_pcache_page *sqlite3PcacheFetch(PCache*, Pgno, int createFlag); +SQLITE_PRIVATE int sqlite3PcacheFetchStress(PCache*, Pgno, sqlite3_pcache_page**); +SQLITE_PRIVATE PgHdr *sqlite3PcacheFetchFinish(PCache*, Pgno, sqlite3_pcache_page *pPage); SQLITE_PRIVATE void sqlite3PcacheRelease(PgHdr*); SQLITE_PRIVATE void sqlite3PcacheDrop(PgHdr*); /* Remove page from cache */ @@ -9920,6 +11410,13 @@ SQLITE_PRIVATE void sqlite3PcacheSetCachesize(PCache *, int); SQLITE_PRIVATE int sqlite3PcacheGetCachesize(PCache *); #endif +/* Set or get the suggested spill-size for the specified pager-cache. +** +** The spill-size is the minimum number of pages in cache before the cache +** will attempt to spill dirty pages by calling xStress. +*/ +SQLITE_PRIVATE int sqlite3PcacheSetSpillsize(PCache *, int); + /* Free up as much memory as possible from the page cache */ SQLITE_PRIVATE void sqlite3PcacheShrink(PCache*); @@ -9934,6 +11431,10 @@ SQLITE_PRIVATE void sqlite3PcacheStats(int*,int*,int*,int*); SQLITE_PRIVATE void sqlite3PCacheSetDefault(void); +/* Return the header size */ +SQLITE_PRIVATE int sqlite3HeaderSizePcache(void); +SQLITE_PRIVATE int sqlite3HeaderSizePcache1(void); + #endif /* _PCACHE_H_ */ /************** End of pcache.h **********************************************/ @@ -10124,7 +11625,7 @@ SQLITE_PRIVATE void sqlite3PCacheSetDefault(void); ** shared locks begins at SHARED_FIRST. ** ** The same locking strategy and -** byte ranges are used for Unix. This leaves open the possiblity of having +** byte ranges are used for Unix. This leaves open the possibility of having ** clients on win95, winNT, and unix all talking to the same shared file ** and all locking correctly. To do so would require that samba (or whatever ** tool is being used for file sharing) implements locks correctly between @@ -10243,7 +11744,7 @@ SQLITE_PRIVATE int sqlite3OsCloseFree(sqlite3_file *); ** Figure out what version of the code to use. The choices are ** ** SQLITE_MUTEX_OMIT No mutex logic. Not even stubs. The -** mutexes implemention cannot be overridden +** mutexes implementation cannot be overridden ** at start-time. ** ** SQLITE_MUTEX_NOOP For single-threaded applications. No @@ -10332,7 +11833,7 @@ struct Schema { Table *pSeqTab; /* The sqlite_sequence table used by AUTOINCREMENT */ u8 file_format; /* Schema format version for this file */ u8 enc; /* Text encoding used by this database */ - u16 flags; /* Flags associated with this schema */ + u16 schemaFlags; /* Flags associated with this schema */ int cache_size; /* Number of pages to use in the cache */ }; @@ -10340,10 +11841,10 @@ struct Schema { ** These macros can be used to test, set, or clear bits in the ** Db.pSchema->flags field. */ -#define DbHasProperty(D,I,P) (((D)->aDb[I].pSchema->flags&(P))==(P)) -#define DbHasAnyProperty(D,I,P) (((D)->aDb[I].pSchema->flags&(P))!=0) -#define DbSetProperty(D,I,P) (D)->aDb[I].pSchema->flags|=(P) -#define DbClearProperty(D,I,P) (D)->aDb[I].pSchema->flags&=~(P) +#define DbHasProperty(D,I,P) (((D)->aDb[I].pSchema->schemaFlags&(P))==(P)) +#define DbHasAnyProperty(D,I,P) (((D)->aDb[I].pSchema->schemaFlags&(P))!=0) +#define DbSetProperty(D,I,P) (D)->aDb[I].pSchema->schemaFlags|=(P) +#define DbClearProperty(D,I,P) (D)->aDb[I].pSchema->schemaFlags&=~(P) /* ** Allowed values for the DB.pSchema->flags field. @@ -10363,7 +11864,7 @@ struct Schema { ** The number of different kinds of things that can be limited ** using the sqlite3_limit() interface. */ -#define SQLITE_N_LIMIT (SQLITE_LIMIT_TRIGGER_DEPTH+1) +#define SQLITE_N_LIMIT (SQLITE_LIMIT_WORKER_THREADS+1) /* ** Lookaside malloc is a set of fixed-size buffers that can be used @@ -10410,6 +11911,45 @@ struct FuncDefHash { FuncDef *a[23]; /* Hash table for functions */ }; +#ifdef SQLITE_USER_AUTHENTICATION +/* +** Information held in the "sqlite3" database connection object and used +** to manage user authentication. +*/ +typedef struct sqlite3_userauth sqlite3_userauth; +struct sqlite3_userauth { + u8 authLevel; /* Current authentication level */ + int nAuthPW; /* Size of the zAuthPW in bytes */ + char *zAuthPW; /* Password used to authenticate */ + char *zAuthUser; /* User name used to authenticate */ +}; + +/* Allowed values for sqlite3_userauth.authLevel */ +#define UAUTH_Unknown 0 /* Authentication not yet checked */ +#define UAUTH_Fail 1 /* User authentication failed */ +#define UAUTH_User 2 /* Authenticated as a normal user */ +#define UAUTH_Admin 3 /* Authenticated as an administrator */ + +/* Functions used only by user authorization logic */ +SQLITE_PRIVATE int sqlite3UserAuthTable(const char*); +SQLITE_PRIVATE int sqlite3UserAuthCheckLogin(sqlite3*,const char*,u8*); +SQLITE_PRIVATE void sqlite3UserAuthInit(sqlite3*); +SQLITE_PRIVATE void sqlite3CryptFunc(sqlite3_context*,int,sqlite3_value**); + +#endif /* SQLITE_USER_AUTHENTICATION */ + +/* +** typedef for the authorization callback function. +*/ +#ifdef SQLITE_USER_AUTHENTICATION + typedef int (*sqlite3_xauth)(void*,int,const char*,const char*,const char*, + const char*, const char*); +#else + typedef int (*sqlite3_xauth)(void*,int,const char*,const char*,const char*, + const char*); +#endif + + /* ** Each database connection is an instance of the following structure. */ @@ -10427,6 +11967,7 @@ struct sqlite3 { int errCode; /* Most recent error code (SQLITE_*) */ int errMask; /* & result codes with this before returning */ u16 dbOptFlags; /* Flags to enable/disable optimizations */ + u8 enc; /* Text encoding */ u8 autoCommit; /* The auto-commit flag. */ u8 temp_store; /* 1: file 2: memory 0: default */ u8 mallocFailed; /* True if we have seen a malloc failure */ @@ -10440,16 +11981,19 @@ struct sqlite3 { int nChange; /* Value returned by sqlite3_changes() */ int nTotalChange; /* Value returned by sqlite3_total_changes() */ int aLimit[SQLITE_N_LIMIT]; /* Limits */ + int nMaxSorterMmap; /* Maximum size of regions mapped by sorter */ struct sqlite3InitInfo { /* Information used during initialization */ int newTnum; /* Rootpage of table being initialized */ u8 iDb; /* Which db file is being initialized */ u8 busy; /* TRUE if currently initializing */ u8 orphanTrigger; /* Last statement is orphaned TEMP trigger */ + u8 imposterTable; /* Building an imposter table */ } init; int nVdbeActive; /* Number of VDBEs currently running */ int nVdbeRead; /* Number of active VDBEs that read or write */ int nVdbeWrite; /* Number of active VDBEs that read and write */ int nVdbeExec; /* Number of nested calls to VdbeExec() */ + int nVDestroy; /* Number of active OP_VDestroy operations */ int nExtension; /* Number of loaded extensions */ void **aExtension; /* Array of shared library handles */ void (*xTrace)(void*,const char*); /* Trace function */ @@ -10476,8 +12020,7 @@ struct sqlite3 { } u1; Lookaside lookaside; /* Lookaside malloc configuration */ #ifndef SQLITE_OMIT_AUTHORIZATION - int (*xAuth)(void*,int,const char*,const char*,const char*,const char*); - /* Access authorization function */ + sqlite3_xauth xAuth; /* Access authorization function */ void *pAuthArg; /* 1st argument to the access auth function */ #endif #ifndef SQLITE_OMIT_PROGRESS_CALLBACK @@ -10503,7 +12046,6 @@ struct sqlite3 { i64 nDeferredCons; /* Net deferred constraints this transaction. */ i64 nDeferredImmCons; /* Net deferred immediate constraints */ int *pnBytesFreed; /* If not NULL, increment this in DbFree() */ - #ifdef SQLITE_ENABLE_UNLOCK_NOTIFY /* The following variables are all protected by the STATIC_MASTER ** mutex, not by sqlite3.mutex. They are used by code in notify.c. @@ -10521,12 +12063,16 @@ struct sqlite3 { void (*xUnlockNotify)(void **, int); /* Unlock notify callback */ sqlite3 *pNextBlocked; /* Next in list of all blocked connections */ #endif +#ifdef SQLITE_USER_AUTHENTICATION + sqlite3_userauth auth; /* User authentication information */ +#endif }; /* ** A macro to discover the encoding of a database. */ -#define ENC(db) ((db)->aDb[0].pSchema->enc) +#define SCHEMA_ENC(db) ((db)->aDb[0].pSchema->enc) +#define ENC(db) ((db)->enc) /* ** Possible values for the sqlite3.flags. @@ -10561,6 +12107,8 @@ struct sqlite3 { #define SQLITE_DeferFKs 0x01000000 /* Defer all FK constraints */ #define SQLITE_QueryOnly 0x02000000 /* Disable database changes */ #define SQLITE_VdbeEQP 0x04000000 /* Debug EXPLAIN QUERY PLAN */ +#define SQLITE_Vacuum 0x08000000 /* Currently in a VACUUM */ +#define SQLITE_CellSizeCk 0x10000000 /* Check btree cell sizes on load */ /* @@ -10579,8 +12127,8 @@ struct sqlite3 { #define SQLITE_SubqCoroutine 0x0100 /* Evaluate subqueries as coroutines */ #define SQLITE_Transitive 0x0200 /* Transitive constraints */ #define SQLITE_OmitNoopJoin 0x0400 /* Omit unused tables in joins */ -#define SQLITE_Stat3 0x0800 /* Use the SQLITE_STAT3 table */ -#define SQLITE_AdjustOutEst 0x1000 /* Adjust output estimates using WHERE */ +#define SQLITE_Stat34 0x0800 /* Use STAT3 or STAT4 data */ +#define SQLITE_CursorHints 0x2000 /* Add OP_CursorHint opcodes */ #define SQLITE_AllOpts 0xffff /* All optimizations */ /* @@ -10653,20 +12201,24 @@ struct FuncDestructor { /* ** Possible values for FuncDef.flags. Note that the _LENGTH and _TYPEOF -** values must correspond to OPFLAG_LENGTHARG and OPFLAG_TYPEOFARG. There +** values must correspond to OPFLAG_LENGTHARG and OPFLAG_TYPEOFARG. And +** SQLITE_FUNC_CONSTANT must be the same as SQLITE_DETERMINISTIC. There ** are assert() statements in the code to verify this. */ -#define SQLITE_FUNC_ENCMASK 0x003 /* SQLITE_UTF8, SQLITE_UTF16BE or UTF16LE */ -#define SQLITE_FUNC_LIKE 0x004 /* Candidate for the LIKE optimization */ -#define SQLITE_FUNC_CASE 0x008 /* Case-sensitive LIKE-type function */ -#define SQLITE_FUNC_EPHEM 0x010 /* Ephemeral. Delete with VDBE */ -#define SQLITE_FUNC_NEEDCOLL 0x020 /* sqlite3GetFuncCollSeq() might be called */ -#define SQLITE_FUNC_LENGTH 0x040 /* Built-in length() function */ -#define SQLITE_FUNC_TYPEOF 0x080 /* Built-in typeof() function */ -#define SQLITE_FUNC_COUNT 0x100 /* Built-in count(*) aggregate */ -#define SQLITE_FUNC_COALESCE 0x200 /* Built-in coalesce() or ifnull() */ -#define SQLITE_FUNC_UNLIKELY 0x400 /* Built-in unlikely() function */ -#define SQLITE_FUNC_CONSTANT 0x800 /* Constant inputs give a constant output */ +#define SQLITE_FUNC_ENCMASK 0x0003 /* SQLITE_UTF8, SQLITE_UTF16BE or UTF16LE */ +#define SQLITE_FUNC_LIKE 0x0004 /* Candidate for the LIKE optimization */ +#define SQLITE_FUNC_CASE 0x0008 /* Case-sensitive LIKE-type function */ +#define SQLITE_FUNC_EPHEM 0x0010 /* Ephemeral. Delete with VDBE */ +#define SQLITE_FUNC_NEEDCOLL 0x0020 /* sqlite3GetFuncCollSeq() might be called*/ +#define SQLITE_FUNC_LENGTH 0x0040 /* Built-in length() function */ +#define SQLITE_FUNC_TYPEOF 0x0080 /* Built-in typeof() function */ +#define SQLITE_FUNC_COUNT 0x0100 /* Built-in count(*) aggregate */ +#define SQLITE_FUNC_COALESCE 0x0200 /* Built-in coalesce() or ifnull() */ +#define SQLITE_FUNC_UNLIKELY 0x0400 /* Built-in unlikely() function */ +#define SQLITE_FUNC_CONSTANT 0x0800 /* Constant inputs give a constant output */ +#define SQLITE_FUNC_MINMAX 0x1000 /* True for min() and max() aggregates */ +#define SQLITE_FUNC_SLOCHNG 0x2000 /* "Slow Change". Value constant during a + ** single query - might change over time */ /* ** The following three macros, FUNCTION(), LIKEFUNC() and AGGREGATE() are @@ -10682,6 +12234,12 @@ struct FuncDestructor { ** VFUNCTION(zName, nArg, iArg, bNC, xFunc) ** Like FUNCTION except it omits the SQLITE_FUNC_CONSTANT flag. ** +** DFUNCTION(zName, nArg, iArg, bNC, xFunc) +** Like FUNCTION except it omits the SQLITE_FUNC_CONSTANT flag and +** adds the SQLITE_FUNC_SLOCHNG flag. Used for date & time functions +** and functions like sqlite_version() that can change, but not during +** a single query. +** ** AGGREGATE(zName, nArg, iArg, bNC, xStep, xFinal) ** Used to create an aggregate function definition implemented by ** the C functions xStep and xFinal. The first four parameters @@ -10702,11 +12260,14 @@ struct FuncDestructor { #define VFUNCTION(zName, nArg, iArg, bNC, xFunc) \ {nArg, SQLITE_UTF8|(bNC*SQLITE_FUNC_NEEDCOLL), \ SQLITE_INT_TO_PTR(iArg), 0, xFunc, 0, 0, #zName, 0, 0} +#define DFUNCTION(zName, nArg, iArg, bNC, xFunc) \ + {nArg, SQLITE_FUNC_SLOCHNG|SQLITE_UTF8|(bNC*SQLITE_FUNC_NEEDCOLL), \ + SQLITE_INT_TO_PTR(iArg), 0, xFunc, 0, 0, #zName, 0, 0} #define FUNCTION2(zName, nArg, iArg, bNC, xFunc, extraFlags) \ {nArg,SQLITE_FUNC_CONSTANT|SQLITE_UTF8|(bNC*SQLITE_FUNC_NEEDCOLL)|extraFlags,\ SQLITE_INT_TO_PTR(iArg), 0, xFunc, 0, 0, #zName, 0, 0} #define STR_FUNCTION(zName, nArg, pArg, bNC, xFunc) \ - {nArg, SQLITE_FUNC_CONSTANT|SQLITE_UTF8|(bNC*SQLITE_FUNC_NEEDCOLL), \ + {nArg, SQLITE_FUNC_SLOCHNG|SQLITE_UTF8|(bNC*SQLITE_FUNC_NEEDCOLL), \ pArg, 0, xFunc, 0, 0, #zName, 0, 0} #define LIKEFUNC(zName, nArg, arg, flags) \ {nArg, SQLITE_FUNC_CONSTANT|SQLITE_UTF8|flags, \ @@ -10714,6 +12275,9 @@ struct FuncDestructor { #define AGGREGATE(zName, nArg, arg, nc, xStep, xFinal) \ {nArg, SQLITE_UTF8|(nc*SQLITE_FUNC_NEEDCOLL), \ SQLITE_INT_TO_PTR(arg), 0, 0, xStep,xFinal,#zName,0,0} +#define AGGREGATE2(zName, nArg, arg, nc, xStep, xFinal, extraFlags) \ + {nArg, SQLITE_UTF8|(nc*SQLITE_FUNC_NEEDCOLL)|extraFlags, \ + SQLITE_INT_TO_PTR(arg), 0, 0, xStep,xFinal,#zName,0,0} /* ** All current savepoints are stored in a linked list starting at @@ -10747,6 +12311,7 @@ struct Module { const char *zName; /* Name passed to create_module() */ void *pAux; /* pAux passed to create_module() */ void (*xDestroy)(void *); /* Module destructor function */ + Table *pEpoTab; /* Eponymous table for this module */ }; /* @@ -10761,7 +12326,7 @@ struct Column { char *zColl; /* Collating sequence. If NULL, use the default */ u8 notNull; /* An OE_ code for handling a NOT NULL constraint */ char affinity; /* One of the SQLITE_AFF_... values */ - u8 szEst; /* Estimated size of this column. INT==1 */ + u8 szEst; /* Estimated size of value in this column. sizeof(INT)==1 */ u8 colFlags; /* Boolean properties. See COLFLAG_ defines below */ }; @@ -10792,6 +12357,7 @@ struct CollSeq { */ #define SQLITE_SO_ASC 0 /* Sort in ascending order */ #define SQLITE_SO_DESC 1 /* Sort in ascending order */ +#define SQLITE_SO_UNDEFINED -1 /* No sort order specified */ /* ** Column affinity types. @@ -10800,18 +12366,18 @@ struct CollSeq { ** 't' for SQLITE_AFF_TEXT. But we can save a little space and improve ** the speed a little by numbering the values consecutively. ** -** But rather than start with 0 or 1, we begin with 'a'. That way, +** But rather than start with 0 or 1, we begin with 'A'. That way, ** when multiple affinity types are concatenated into a string and ** used as the P4 operand, they will be more readable. ** ** Note also that the numeric types are grouped together so that testing -** for a numeric type is a single comparison. +** for a numeric type is a single comparison. And the BLOB type is first. */ -#define SQLITE_AFF_TEXT 'a' -#define SQLITE_AFF_NONE 'b' -#define SQLITE_AFF_NUMERIC 'c' -#define SQLITE_AFF_INTEGER 'd' -#define SQLITE_AFF_REAL 'e' +#define SQLITE_AFF_BLOB 'A' +#define SQLITE_AFF_TEXT 'B' +#define SQLITE_AFF_NUMERIC 'C' +#define SQLITE_AFF_INTEGER 'D' +#define SQLITE_AFF_REAL 'E' #define sqlite3IsNumericAffinity(X) ((X)>=SQLITE_AFF_NUMERIC) @@ -10819,7 +12385,7 @@ struct CollSeq { ** The SQLITE_AFF_MASK values masks off the significant bits of an ** affinity value. */ -#define SQLITE_AFF_MASK 0x67 +#define SQLITE_AFF_MASK 0x47 /* ** Additional bit values that can be ORed with an affinity without @@ -10830,10 +12396,10 @@ struct CollSeq { ** operator is NULL. It is added to certain comparison operators to ** prove that the operands are always NOT NULL. */ -#define SQLITE_JUMPIFNULL 0x08 /* jumps if either operand is NULL */ -#define SQLITE_STOREP2 0x10 /* Store result in reg[P2] rather than jump */ +#define SQLITE_JUMPIFNULL 0x10 /* jumps if either operand is NULL */ +#define SQLITE_STOREP2 0x20 /* Store result in reg[P2] rather than jump */ #define SQLITE_NULLEQ 0x80 /* NULL=NULL */ -#define SQLITE_NOTNULL 0x88 /* Assert that operands are never NULL */ +#define SQLITE_NOTNULL 0x90 /* Assert that operands are never NULL */ /* ** An object of this type is created for each virtual table present in @@ -10888,34 +12454,8 @@ struct VTable { }; /* -** Each SQL table is represented in memory by an instance of the -** following structure. -** -** Table.zName is the name of the table. The case of the original -** CREATE TABLE statement is stored, but case is not significant for -** comparisons. -** -** Table.nCol is the number of columns in this table. Table.aCol is a -** pointer to an array of Column structures, one for each column. -** -** If the table has an INTEGER PRIMARY KEY, then Table.iPKey is the index of -** the column that is that key. Otherwise Table.iPKey is negative. Note -** that the datatype of the PRIMARY KEY must be INTEGER for this field to -** be set. An INTEGER PRIMARY KEY is used as the rowid for each row of -** the table. If a table has no INTEGER PRIMARY KEY, then a random rowid -** is generated for each row of the table. TF_HasPrimaryKey is set if -** the table has any PRIMARY KEY, INTEGER or otherwise. -** -** Table.tnum is the page number for the root BTree page of the table in the -** database file. If Table.iDb is the index of the database table backend -** in sqlite.aDb[]. 0 is for the main database and 1 is for the file that -** holds temporary tables and indices. If TF_Ephemeral is set -** then the table is stored in a file that is automatically deleted -** when the VDBE cursor to the table is closed. In this case Table.tnum -** refers VDBE cursor number that holds the table open, not to the root -** page number. Transient tables are used to hold the results of a -** sub-query that appears instead of a real table name in the FROM clause -** of a SELECT statement. +** The schema for each SQL table and view is represented in memory +** by an instance of the following structure. */ struct Table { char *zName; /* Name of the table or view */ @@ -10924,15 +12464,17 @@ struct Table { Select *pSelect; /* NULL for tables. Points to definition if a view. */ FKey *pFKey; /* Linked list of all foreign keys in this table */ char *zColAff; /* String defining the affinity of each column */ -#ifndef SQLITE_OMIT_CHECK ExprList *pCheck; /* All CHECK constraints */ -#endif - LogEst nRowLogEst; /* Estimated rows in table - from sqlite_stat1 table */ - int tnum; /* Root BTree node for this table (see note above) */ - i16 iPKey; /* If not negative, use aCol[iPKey] as the primary key */ + /* ... also used as column name list in a VIEW */ + int tnum; /* Root BTree page for this table */ + i16 iPKey; /* If not negative, use aCol[iPKey] as the rowid */ i16 nCol; /* Number of columns in this table */ u16 nRef; /* Number of pointers to this Table */ + LogEst nRowLogEst; /* Estimated rows in table - from sqlite_stat1 table */ LogEst szTabRow; /* Estimated size of each table row in bytes */ +#ifdef SQLITE_ENABLE_COSTMULT + LogEst costMult; /* Cost multiplier for using this table */ +#endif u8 tabFlags; /* Mask of TF_* values */ u8 keyConf; /* What to do in case of uniqueness conflict on iPKey */ #ifndef SQLITE_OMIT_ALTERTABLE @@ -10940,7 +12482,7 @@ struct Table { #endif #ifndef SQLITE_OMIT_VIRTUALTABLE int nModuleArg; /* Number of arguments to the module */ - char **azModuleArg; /* Text of all module args. [0] is module name */ + char **azModuleArg; /* 0: module 1: schema 2: vtab name 3...: args */ VTable *pVTable; /* List of VTable objects. */ #endif Trigger *pTrigger; /* List of triggers stored in pSchema */ @@ -10950,13 +12492,21 @@ struct Table { /* ** Allowed values for Table.tabFlags. +** +** TF_OOOHidden applies to tables or view that have hidden columns that are +** followed by non-hidden columns. Example: "CREATE VIRTUAL TABLE x USING +** vtab1(a HIDDEN, b);". Since "b" is a non-hidden column but "a" is hidden, +** the TF_OOOHidden attribute would apply in this case. Such tables require +** special handling during INSERT processing. */ #define TF_Readonly 0x01 /* Read-only system table */ #define TF_Ephemeral 0x02 /* An ephemeral table */ #define TF_HasPrimaryKey 0x04 /* Table has a primary key */ #define TF_Autoincrement 0x08 /* Integer primary key is autoincrement */ #define TF_Virtual 0x10 /* Is a virtual table */ -#define TF_WithoutRowid 0x20 /* No rowid used. PRIMARY KEY is the key */ +#define TF_WithoutRowid 0x20 /* No rowid. PRIMARY KEY is the key */ +#define TF_NoVisibleRowid 0x40 /* No user-visible "rowid" column */ +#define TF_OOOHidden 0x80 /* Out-of-Order hidden columns */ /* @@ -10966,14 +12516,31 @@ struct Table { */ #ifndef SQLITE_OMIT_VIRTUALTABLE # define IsVirtual(X) (((X)->tabFlags & TF_Virtual)!=0) -# define IsHiddenColumn(X) (((X)->colFlags & COLFLAG_HIDDEN)!=0) #else # define IsVirtual(X) 0 -# define IsHiddenColumn(X) 0 #endif +/* +** Macros to determine if a column is hidden. IsOrdinaryHiddenColumn() +** only works for non-virtual tables (ordinary tables and views) and is +** always false unless SQLITE_ENABLE_HIDDEN_COLUMNS is defined. The +** IsHiddenColumn() macro is general purpose. +*/ +#if defined(SQLITE_ENABLE_HIDDEN_COLUMNS) +# define IsHiddenColumn(X) (((X)->colFlags & COLFLAG_HIDDEN)!=0) +# define IsOrdinaryHiddenColumn(X) (((X)->colFlags & COLFLAG_HIDDEN)!=0) +#elif !defined(SQLITE_OMIT_VIRTUALTABLE) +# define IsHiddenColumn(X) (((X)->colFlags & COLFLAG_HIDDEN)!=0) +# define IsOrdinaryHiddenColumn(X) 0 +#else +# define IsHiddenColumn(X) 0 +# define IsOrdinaryHiddenColumn(X) 0 +#endif + + /* Does the table have a rowid */ #define HasRowid(X) (((X)->tabFlags & TF_WithoutRowid)==0) +#define VisibleRowid(X) (((X)->tabFlags & TF_NoVisibleRowid)==0) /* ** Each foreign key constraint is an instance of the following structure. @@ -11080,9 +12647,8 @@ struct KeyInfo { }; /* -** An instance of the following structure holds information about a -** single index record that has already been parsed out into individual -** values. +** This object holds a record which has been parsed out into individual +** fields, for the purposes of doing a comparison. ** ** A record is an object that contains one or more fields of data. ** Records are used to store the content of a table row and to store @@ -11090,20 +12656,40 @@ struct KeyInfo { ** the OP_MakeRecord opcode of the VDBE and is disassembled by the ** OP_Column opcode. ** -** This structure holds a record that has already been disassembled -** into its constituent fields. +** An instance of this object serves as a "key" for doing a search on +** an index b+tree. The goal of the search is to find the entry that +** is closed to the key described by this object. This object might hold +** just a prefix of the key. The number of fields is given by +** pKeyInfo->nField. ** -** The r1 and r2 member variables are only used by the optimized comparison -** functions vdbeRecordCompareInt() and vdbeRecordCompareString(). +** The r1 and r2 fields are the values to return if this key is less than +** or greater than a key in the btree, respectively. These are normally +** -1 and +1 respectively, but might be inverted to +1 and -1 if the b-tree +** is in DESC order. +** +** The key comparison functions actually return default_rc when they find +** an equals comparison. default_rc can be -1, 0, or +1. If there are +** multiple entries in the b-tree with the same key (when only looking +** at the first pKeyInfo->nFields,) then default_rc can be set to -1 to +** cause the search to find the last match, or +1 to cause the search to +** find the first match. +** +** The key comparison functions will set eqSeen to true if they ever +** get and equal results when comparing this structure to a b-tree record. +** When default_rc!=0, the search might end up on the record immediately +** before the first match or immediately after the last match. The +** eqSeen field will indicate whether or not an exact match exists in the +** b-tree. */ struct UnpackedRecord { KeyInfo *pKeyInfo; /* Collation and sort-order information */ + Mem *aMem; /* Values */ u16 nField; /* Number of entries in apMem[] */ i8 default_rc; /* Comparison result if keys are equal */ - u8 isCorrupt; /* Corruption detected by xRecordCompare() */ - Mem *aMem; /* Values */ - int r1; /* Value to return if (lhs > rhs) */ - int r2; /* Value to return if (rhs < lhs) */ + u8 errCode; /* Error detected by xRecordCompare (CORRUPT or NOMEM) */ + i8 r1; /* Value to return if (lhs > rhs) */ + i8 r2; /* Value to return if (rhs < lhs) */ + u8 eqSeen; /* True if an equality comparison has been seen */ }; @@ -11132,6 +12718,14 @@ struct UnpackedRecord { ** and the value of Index.onError indicate the which conflict resolution ** algorithm to employ whenever an attempt is made to insert a non-unique ** element. +** +** While parsing a CREATE TABLE or CREATE INDEX statement in order to +** generate VDBE code (as opposed to parsing one read from an sqlite_master +** table as part of parsing an existing database schema), transient instances +** of this structure may be created. In this case the Index.tnum variable is +** used to store the address of a VDBE instruction, not a database page +** number (it cannot - the database page is not allocated until the VDBE +** program is executed). See convertToWithoutRowidTable() for details. */ struct Index { char *zName; /* Name of this index */ @@ -11142,9 +12736,9 @@ struct Index { Index *pNext; /* The next index associated with the same table */ Schema *pSchema; /* Schema containing this index */ u8 *aSortOrder; /* for each column: True==DESC, False==ASC */ - char **azColl; /* Array of collation sequence names for index */ + const char **azColl; /* Array of collation sequence names for index */ Expr *pPartIdxWhere; /* WHERE clause for partial indices */ - KeyInfo *pKeyInfo; /* A KeyInfo object suitable for this index */ + ExprList *aColExpr; /* Column expressions */ int tnum; /* DB Page containing root of this index */ LogEst szIdxRow; /* Estimated average row size in bytes */ u16 nKeyCol; /* Number of columns forming the key */ @@ -11155,11 +12749,14 @@ struct Index { unsigned uniqNotNull:1; /* True if UNIQUE and NOT NULL for all columns */ unsigned isResized:1; /* True if resizeIndexObject() has been called */ unsigned isCovering:1; /* True if this is a covering index */ + unsigned noSkipScan:1; /* Do not try to use skip-scan if true */ #ifdef SQLITE_ENABLE_STAT3_OR_STAT4 int nSample; /* Number of elements in aSample[] */ int nSampleCol; /* Size of IndexSample.anEq[] and so on */ tRowcnt *aAvgEq; /* Average nEq values for keys not in aSample */ IndexSample *aSample; /* Samples of the left-most key */ + tRowcnt *aiRowEst; /* Non-logarithmic stat1 data for this index */ + tRowcnt nRowEst0; /* Non-logarithmic number of rows in the index */ #endif }; @@ -11173,6 +12770,15 @@ struct Index { /* Return true if index X is a PRIMARY KEY index */ #define IsPrimaryKeyIndex(X) ((X)->idxType==SQLITE_IDXTYPE_PRIMARYKEY) +/* Return true if index X is a UNIQUE index */ +#define IsUniqueIndex(X) ((X)->onError!=OE_None) + +/* The Index.aiColumn[] values are normally positive integer. But +** there are some negative values that have special meaning: +*/ +#define XN_ROWID (-1) /* Indexed column is the rowid */ +#define XN_EXPR (-2) /* Indexed column is an expression */ + /* ** Each sample stored in the sqlite_stat3 table is represented in memory ** using a structure of this type. See documentation at the top of the @@ -11354,7 +12960,7 @@ struct Expr { int iTable; /* TK_COLUMN: cursor number of table holding column ** TK_REGISTER: register number ** TK_TRIGGER: 1 -> new, 0 -> old - ** EP_Unlikely: 1000 times likelihood */ + ** EP_Unlikely: 134217728 times likelihood */ ynVar iColumn; /* TK_COLUMN: column index. -1 for rowid. ** TK_VARIABLE: variable number (always >= 1). */ i16 iAgg; /* Which entry in pAggInfo->aCol[] or ->aFunc[] */ @@ -11369,7 +12975,7 @@ struct Expr { /* ** The following are the meanings of bits in the Expr.flags field. */ -#define EP_FromJoin 0x000001 /* Originated in ON or USING clause of a join */ +#define EP_FromJoin 0x000001 /* Originates in ON/USING clause of outer join */ #define EP_Agg 0x000002 /* Contains one or more aggregate functions */ #define EP_Resolved 0x000004 /* IDs have been resolved to COLUMNs */ #define EP_Error 0x000008 /* Expression contains one or more errors */ @@ -11388,7 +12994,15 @@ struct Expr { #define EP_MemToken 0x010000 /* Need to sqlite3DbFree() Expr.zToken */ #define EP_NoReduce 0x020000 /* Cannot EXPRDUP_REDUCE this Expr */ #define EP_Unlikely 0x040000 /* unlikely() or likelihood() function */ -#define EP_Constant 0x080000 /* Node is a constant */ +#define EP_ConstFunc 0x080000 /* A SQLITE_FUNC_CONSTANT or _SLOCHNG function */ +#define EP_CanBeNull 0x100000 /* Can be null despite NOT NULL constraint */ +#define EP_Subquery 0x200000 /* Tree contains a TK_SELECT operator */ +#define EP_Alias 0x400000 /* Is an alias for a result set column */ + +/* +** Combinations of two or more EP_* flags +*/ +#define EP_Propagate (EP_Collate|EP_Subquery) /* Propagate these bits up tree */ /* ** These macros can be used to test, set, or clear bits in the @@ -11546,11 +13160,15 @@ struct SrcList { int addrFillSub; /* Address of subroutine to manifest a subquery */ int regReturn; /* Register holding return address of addrFillSub */ int regResult; /* Registers holding results of a co-routine */ - u8 jointype; /* Type of join between this able and the previous */ - unsigned notIndexed :1; /* True if there is a NOT INDEXED clause */ - unsigned isCorrelated :1; /* True if sub-query is correlated */ - unsigned viaCoroutine :1; /* Implemented as a co-routine */ - unsigned isRecursive :1; /* True for recursive reference in WITH */ + struct { + u8 jointype; /* Type of join between this able and the previous */ + unsigned notIndexed :1; /* True if there is a NOT INDEXED clause */ + unsigned isIndexedBy :1; /* True if there is an INDEXED BY clause */ + unsigned isTabFunc :1; /* True if table-valued-function syntax */ + unsigned isCorrelated :1; /* True if sub-query is correlated */ + unsigned viaCoroutine :1; /* Implemented as a co-routine */ + unsigned isRecursive :1; /* True for recursive reference in WITH */ + } fg; #ifndef SQLITE_OMIT_EXPLAIN u8 iSelectId; /* If pSelect!=0, the id of the sub-select in EQP */ #endif @@ -11558,8 +13176,11 @@ struct SrcList { Expr *pOn; /* The ON clause of a join */ IdList *pUsing; /* The USING clause of a join */ Bitmask colUsed; /* Bit N (1<" clause */ - Index *pIndex; /* Index structure corresponding to zIndex, if any */ + union { + char *zIndexedBy; /* Identifier from "INDEXED BY " clause */ + ExprList *pFuncArg; /* Arguments to table-valued-function */ + } u1; + Index *pIBIndex; /* Index structure corresponding to u1.zIndexedBy */ } a[1]; /* One entry for each identifier on the list */ }; @@ -11587,11 +13208,13 @@ struct SrcList { #define WHERE_OMIT_OPEN_CLOSE 0x0010 /* Table cursors are already open */ #define WHERE_FORCE_TABLE 0x0020 /* Do not use an index-only search */ #define WHERE_ONETABLE_ONLY 0x0040 /* Only code the 1st table in pTabList */ -#define WHERE_AND_ONLY 0x0080 /* Don't use indices for OR terms */ +#define WHERE_NO_AUTOINDEX 0x0080 /* Disallow automatic indexes */ #define WHERE_GROUPBY 0x0100 /* pOrderBy is really a GROUP BY */ #define WHERE_DISTINCTBY 0x0200 /* pOrderby is really a DISTINCT clause */ #define WHERE_WANT_DISTINCT 0x0400 /* All output needs to be distinct */ #define WHERE_SORTBYGROUP 0x0800 /* Support sqlite3WhereIsSorted() */ +#define WHERE_REOPEN_IDX 0x1000 /* Try to use OP_ReopenIdx */ +#define WHERE_ONEPASS_MULTIROW 0x2000 /* ONEPASS is ok with multiple rows */ /* Allowed return values from sqlite3WhereIsDistinct() */ @@ -11629,17 +13252,23 @@ struct NameContext { NameContext *pNext; /* Next outer name context. NULL for outermost */ int nRef; /* Number of names resolved by this context */ int nErr; /* Number of errors encountered while resolving names */ - u8 ncFlags; /* Zero or more NC_* flags defined below */ + u16 ncFlags; /* Zero or more NC_* flags defined below */ }; /* ** Allowed values for the NameContext, ncFlags field. +** +** Note: NC_MinMaxAgg must have the same value as SF_MinMaxAgg and +** SQLITE_FUNC_MINMAX. +** */ -#define NC_AllowAgg 0x01 /* Aggregate functions are allowed here */ -#define NC_HasAgg 0x02 /* One or more aggregate functions seen */ -#define NC_IsCheck 0x04 /* True if resolving names in a CHECK constraint */ -#define NC_InAggFunc 0x08 /* True if analyzing arguments to an agg func */ -#define NC_PartIdx 0x10 /* True if resolving a partial index WHERE */ +#define NC_AllowAgg 0x0001 /* Aggregate functions are allowed here */ +#define NC_HasAgg 0x0002 /* One or more aggregate functions seen */ +#define NC_IsCheck 0x0004 /* True if resolving names in a CHECK constraint */ +#define NC_InAggFunc 0x0008 /* True if analyzing arguments to an agg func */ +#define NC_PartIdx 0x0010 /* True if resolving a partial index WHERE */ +#define NC_IdxExpr 0x0020 /* True if resolving columns of CREATE INDEX */ +#define NC_MinMaxAgg 0x1000 /* min/max aggregates seen. See note above */ /* ** An instance of the following structure contains all information @@ -11666,6 +13295,9 @@ struct Select { u8 op; /* One of: TK_UNION TK_ALL TK_INTERSECT TK_EXCEPT */ u16 selFlags; /* Various SF_* values */ int iLimit, iOffset; /* Memory registers holding LIMIT & OFFSET counters */ +#if SELECTTRACE_ENABLED + char zSelName[12]; /* Symbolic name of this SELECT use for debugging */ +#endif int addrOpenEphm[2]; /* OP_OpenEphem opcodes related to this select */ u64 nSelectRow; /* Estimated number of result rows */ SrcList *pSrc; /* The FROM clause */ @@ -11685,18 +13317,21 @@ struct Select { ** "Select Flag". */ #define SF_Distinct 0x0001 /* Output should be DISTINCT */ -#define SF_Resolved 0x0002 /* Identifiers have been resolved */ -#define SF_Aggregate 0x0004 /* Contains aggregate functions */ -#define SF_UsesEphemeral 0x0008 /* Uses the OpenEphemeral opcode */ -#define SF_Expanded 0x0010 /* sqlite3SelectExpand() called on this */ -#define SF_HasTypeInfo 0x0020 /* FROM subqueries have Table metadata */ - /* 0x0040 NOT USED */ -#define SF_Values 0x0080 /* Synthesized from VALUES clause */ - /* 0x0100 NOT USED */ -#define SF_NestedFrom 0x0200 /* Part of a parenthesized FROM clause */ -#define SF_MaybeConvert 0x0400 /* Need convertCompoundSelectToSubquery() */ -#define SF_Recursive 0x0800 /* The recursive part of a recursive CTE */ -#define SF_Compound 0x1000 /* Part of a compound query */ +#define SF_All 0x0002 /* Includes the ALL keyword */ +#define SF_Resolved 0x0004 /* Identifiers have been resolved */ +#define SF_Aggregate 0x0008 /* Contains aggregate functions */ +#define SF_UsesEphemeral 0x0010 /* Uses the OpenEphemeral opcode */ +#define SF_Expanded 0x0020 /* sqlite3SelectExpand() called on this */ +#define SF_HasTypeInfo 0x0040 /* FROM subqueries have Table metadata */ +#define SF_Compound 0x0080 /* Part of a compound query */ +#define SF_Values 0x0100 /* Synthesized from VALUES clause */ +#define SF_MultiValue 0x0200 /* Single VALUES term with multiple rows */ +#define SF_NestedFrom 0x0400 /* Part of a parenthesized FROM clause */ +#define SF_MaybeConvert 0x0800 /* Need convertCompoundSelectToSubquery() */ +#define SF_MinMaxAgg 0x1000 /* Aggregate containing min() or max() */ +#define SF_Recursive 0x2000 /* The recursive part of a recursive CTE */ +#define SF_Converted 0x4000 /* By convertCompoundSelectToSubquery() */ +#define SF_IncludeHidden 0x8000 /* Include hidden columns in output */ /* @@ -11848,9 +13483,19 @@ struct TriggerPrg { ** The yDbMask datatype for the bitmask of all attached databases. */ #if SQLITE_MAX_ATTACHED>30 - typedef sqlite3_uint64 yDbMask; + typedef unsigned char yDbMask[(SQLITE_MAX_ATTACHED+9)/8]; +# define DbMaskTest(M,I) (((M)[(I)/8]&(1<<((I)&7)))!=0) +# define DbMaskZero(M) memset((M),0,sizeof(M)) +# define DbMaskSet(M,I) (M)[(I)/8]|=(1<<((I)&7)) +# define DbMaskAllZero(M) sqlite3DbMaskAllZero(M) +# define DbMaskNonZero(M) (sqlite3DbMaskAllZero(M)==0) #else typedef unsigned int yDbMask; +# define DbMaskTest(M,I) (((M)&(((yDbMask)1)<<(I)))!=0) +# define DbMaskZero(M) (M)=0 +# define DbMaskSet(M,I) (M)|=(((yDbMask)1)<<(I)) +# define DbMaskAllZero(M) (M)==0 +# define DbMaskNonZero(M) (M)!=0 #endif /* @@ -11891,9 +13536,10 @@ struct Parse { int nSet; /* Number of sets used so far */ int nOnce; /* Number of OP_Once instructions so far */ int nOpAlloc; /* Number of slots allocated for Vdbe.aOp[] */ + int szOpAlloc; /* Bytes of memory space allocated for Vdbe.aOp[] */ int iFixedOp; /* Never back out opcodes iFixedOp-1 or earlier */ int ckBase; /* Base register of data during check constraints */ - int iPartIdxTab; /* Table corresponding to a partial index */ + int iSelfTab; /* Table of an index whose exprs are being coded */ int iCacheLevel; /* ColCache valid when aColCache[].iLevel<=iCacheLevel */ int iCacheCnt; /* Counter used to generate aColCache[].lru values */ int nLabel; /* Number of labels used */ @@ -11914,6 +13560,10 @@ struct Parse { int regRowid; /* Register holding rowid of CREATE TABLE entry */ int regRoot; /* Register holding root page number for new objects */ int nMaxArg; /* Max args passed to user function by sub-program */ +#if SELECTTRACE_ENABLED + int nSelect; /* Number of SELECT statements seen */ + int nSelectIndent; /* How far to indent SELECTTRACE() output */ +#endif #ifndef SQLITE_OMIT_SHARED_CACHE int nTableLock; /* Number of locks in aTableLock */ TableLock *aTableLock; /* Required table locks for shared-cache mode */ @@ -11924,7 +13574,6 @@ struct Parse { Parse *pToplevel; /* Parse structure for main program (or NULL) */ Table *pTriggerTab; /* Table triggers are being coded for */ int addrCrTab; /* Address of OP_CreateTable opcode on CREATE TABLE */ - int addrSkipPK; /* Address of instruction to skip PRIMARY KEY index */ u32 nQueryLoop; /* Est number of iterations of a query (10*log2(N)) */ u32 oldmask; /* Mask of old.* columns referenced */ u32 newmask; /* Mask of new.* columns referenced */ @@ -11942,7 +13591,6 @@ struct Parse { int nVar; /* Number of '?' variables seen in the SQL so far */ int nzVar; /* Number of available slots in azVar[] */ u8 iPkSortOrder; /* ASC or DESC for INTEGER PRIMARY KEY */ - u8 bFreeWith; /* True if pWith should be freed with parser */ u8 explain; /* True if the EXPLAIN flag is found on the query */ #ifndef SQLITE_OMIT_VIRTUALTABLE u8 declareVtab; /* True if inside sqlite3_declare_vtab() */ @@ -11969,6 +13617,7 @@ struct Parse { Table *pZombieTab; /* List of Table objects to delete after code gen */ TriggerPrg *pTriggerPrg; /* Linked list of coded triggers */ With *pWith; /* Current WITH clause, or NULL */ + With *pWithToFree; /* Free this WITH object at the end of the parse */ }; /* @@ -11993,15 +13642,17 @@ struct AuthContext { ** Bitfield flags for P5 value in various opcodes. */ #define OPFLAG_NCHANGE 0x01 /* Set to update db->nChange */ +#define OPFLAG_EPHEM 0x01 /* OP_Column: Ephemeral output is ok */ #define OPFLAG_LASTROWID 0x02 /* Set to update db->lastRowid */ #define OPFLAG_ISUPDATE 0x04 /* This OP_Insert is an sql UPDATE */ #define OPFLAG_APPEND 0x08 /* This is likely to be an append */ #define OPFLAG_USESEEKRESULT 0x10 /* Try to avoid a seek in BtreeInsert() */ -#define OPFLAG_CLEARCACHE 0x20 /* Clear pseudo-table cache in OP_Column */ #define OPFLAG_LENGTHARG 0x40 /* OP_Column only used for length() */ #define OPFLAG_TYPEOFARG 0x80 /* OP_Column only used for typeof() */ #define OPFLAG_BULKCSR 0x01 /* OP_Open** used to open bulk cursor */ -#define OPFLAG_P2ISREG 0x02 /* P2 to OP_Open** is a register number */ +#define OPFLAG_SEEKEQ 0x02 /* OP_Open** cursor uses EQ seek only */ +#define OPFLAG_FORDELETE 0x08 /* OP_Open is opening for-delete csr */ +#define OPFLAG_P2ISREG 0x10 /* P2 to OP_Open** is a register number */ #define OPFLAG_PERMUTE 0x01 /* OP_Compare: use the permutation */ /* @@ -12060,7 +13711,7 @@ struct Trigger { * orconf -> stores the ON CONFLICT algorithm * pSelect -> If this is an INSERT INTO ... SELECT ... statement, then * this stores a pointer to the SELECT statement. Otherwise NULL. - * target -> A token holding the quoted name of the table to insert into. + * zTarget -> Dequoted name of the table to insert into. * pExprList -> If this is an INSERT INTO ... VALUES ... statement, then * this stores values to be inserted. Otherwise NULL. * pIdList -> If this is an INSERT INTO ... () VALUES ... @@ -12068,12 +13719,12 @@ struct Trigger { * inserted into. * * (op == TK_DELETE) - * target -> A token holding the quoted name of the table to delete from. + * zTarget -> Dequoted name of the table to delete from. * pWhere -> The WHERE clause of the DELETE statement if one is specified. * Otherwise NULL. * * (op == TK_UPDATE) - * target -> A token holding the quoted name of the table to update rows of. + * zTarget -> Dequoted name of the table to update. * pWhere -> The WHERE clause of the UPDATE statement if one is specified. * Otherwise NULL. * pExprList -> A list of the columns to update and the expressions to update @@ -12085,8 +13736,8 @@ struct TriggerStep { u8 op; /* One of TK_DELETE, TK_UPDATE, TK_INSERT, TK_SELECT */ u8 orconf; /* OE_Rollback etc. */ Trigger *pTrig; /* The trigger that this step is a part of */ - Select *pSelect; /* SELECT statment or RHS of INSERT INTO .. SELECT ... */ - Token target; /* Target table for DELETE, UPDATE, INSERT */ + Select *pSelect; /* SELECT statement or RHS of INSERT INTO SELECT ... */ + char *zTarget; /* Target table for DELETE, UPDATE, INSERT */ Expr *pWhere; /* The WHERE clause for DELETE or UPDATE steps */ ExprList *pExprList; /* SET clause for UPDATE. */ IdList *pIdList; /* Column names for INSERT */ @@ -12117,11 +13768,11 @@ struct StrAccum { sqlite3 *db; /* Optional database for lookaside. Can be NULL */ char *zBase; /* A base allocation. Not from malloc. */ char *zText; /* The string collected so far */ - int nChar; /* Length of the string so far */ - int nAlloc; /* Amount of space allocated in zText */ - int mxAlloc; /* Maximum allowed string length */ - u8 useMalloc; /* 0: none, 1: sqlite3DbMalloc, 2: sqlite3_malloc */ + u32 nChar; /* Length of the string so far */ + u32 nAlloc; /* Amount of space allocated in zText */ + u32 mxAlloc; /* Maximum allowed allocation. 0 for no malloc usage */ u8 accError; /* STRACCUM_NOMEM or STRACCUM_TOOBIG */ + u8 bMalloced; /* zText points to allocated space */ }; #define STRACCUM_NOMEM 1 #define STRACCUM_TOOBIG 2 @@ -12168,6 +13819,7 @@ struct Sqlite3Config { int nPage; /* Number of pages in pPage[] */ int mxParserStack; /* maximum depth of the parser stack */ int sharedCacheEnabled; /* true if shared-cache mode enabled */ + u32 szPma; /* Maximum Sorter PMA size */ /* The above might be initialized to non-zero. The following need to always ** initially be zero, however. */ int isInit; /* True after initialization has finished */ @@ -12223,11 +13875,14 @@ struct Walker { void (*xSelectCallback2)(Walker*,Select*);/* Second callback for SELECTs */ Parse *pParse; /* Parser context. */ int walkerDepth; /* Number of subqueries */ + u8 eCode; /* A small processing code */ union { /* Extra data for callback */ NameContext *pNC; /* Naming context */ - int i; /* Integer value */ + int n; /* A counter */ + int iCur; /* A cursor number */ SrcList *pSrcList; /* FROM clause */ struct SrcCount *pSrcCount; /* Counting column references */ + struct CCurHint *pCCurHint; /* Used by codeCursorHint() */ } u; }; @@ -12237,6 +13892,7 @@ SQLITE_PRIVATE int sqlite3WalkExprList(Walker*, ExprList*); SQLITE_PRIVATE int sqlite3WalkSelect(Walker*, Select*); SQLITE_PRIVATE int sqlite3WalkSelectExpr(Walker*, Select*); SQLITE_PRIVATE int sqlite3WalkSelectFrom(Walker*, Select*); +SQLITE_PRIVATE int sqlite3ExprWalkNoop(Walker*, Expr*); /* ** Return code from the parse-tree walking primitives and their @@ -12257,10 +13913,21 @@ struct With { char *zName; /* Name of this CTE */ ExprList *pCols; /* List of explicit column names, or NULL */ Select *pSelect; /* The definition of this CTE */ - const char *zErr; /* Error message for circular references */ + const char *zCteErr; /* Error message for circular references */ } a[1]; }; +#ifdef SQLITE_DEBUG +/* +** An instance of the TreeView object is used for printing the content of +** data structures on sqlite3DebugPrintf() using a tree-like view. +*/ +struct TreeView { + int iLevel; /* Which level of the tree we are on */ + u8 bLine[100]; /* Draw vertical in column i if bLine[i] is true */ +}; +#endif /* SQLITE_DEBUG */ + /* ** Assuming zIn points to the first byte of a UTF-8 character, ** advance zIn to point to the first byte of the next UTF-8 character. @@ -12288,11 +13955,11 @@ SQLITE_PRIVATE int sqlite3CantopenError(int); /* ** FTS4 is really an extension for FTS3. It is enabled using the -** SQLITE_ENABLE_FTS3 macro. But to avoid confusion we also all -** the SQLITE_ENABLE_FTS4 macro to serve as an alisse for SQLITE_ENABLE_FTS3. +** SQLITE_ENABLE_FTS3 macro. But to avoid confusion we also call +** the SQLITE_ENABLE_FTS4 macro to serve as an alias for SQLITE_ENABLE_FTS3. */ #if defined(SQLITE_ENABLE_FTS4) && !defined(SQLITE_ENABLE_FTS3) -# define SQLITE_ENABLE_FTS3 +# define SQLITE_ENABLE_FTS3 1 #endif /* @@ -12326,6 +13993,9 @@ SQLITE_PRIVATE int sqlite3CantopenError(int); # define sqlite3Isxdigit(x) isxdigit((unsigned char)(x)) # define sqlite3Tolower(x) tolower((unsigned char)(x)) #endif +#ifndef SQLITE_OMIT_COMPILEOPTION_DIAGS +SQLITE_PRIVATE int sqlite3IsIdChar(u8); +#endif /* ** Internal function prototypes @@ -12336,15 +14006,15 @@ SQLITE_PRIVATE int sqlite3Strlen30(const char*); SQLITE_PRIVATE int sqlite3MallocInit(void); SQLITE_PRIVATE void sqlite3MallocEnd(void); -SQLITE_PRIVATE void *sqlite3Malloc(int); -SQLITE_PRIVATE void *sqlite3MallocZero(int); -SQLITE_PRIVATE void *sqlite3DbMallocZero(sqlite3*, int); -SQLITE_PRIVATE void *sqlite3DbMallocRaw(sqlite3*, int); +SQLITE_PRIVATE void *sqlite3Malloc(u64); +SQLITE_PRIVATE void *sqlite3MallocZero(u64); +SQLITE_PRIVATE void *sqlite3DbMallocZero(sqlite3*, u64); +SQLITE_PRIVATE void *sqlite3DbMallocRaw(sqlite3*, u64); SQLITE_PRIVATE char *sqlite3DbStrDup(sqlite3*,const char*); -SQLITE_PRIVATE char *sqlite3DbStrNDup(sqlite3*,const char*, int); -SQLITE_PRIVATE void *sqlite3Realloc(void*, int); -SQLITE_PRIVATE void *sqlite3DbReallocOrFree(sqlite3 *, void *, int); -SQLITE_PRIVATE void *sqlite3DbRealloc(sqlite3 *, void *, int); +SQLITE_PRIVATE char *sqlite3DbStrNDup(sqlite3*,const char*, u64); +SQLITE_PRIVATE void *sqlite3Realloc(void*, u64); +SQLITE_PRIVATE void *sqlite3DbReallocOrFree(sqlite3 *, void *, u64); +SQLITE_PRIVATE void *sqlite3DbRealloc(sqlite3 *, void *, u64); SQLITE_PRIVATE void sqlite3DbFree(sqlite3*, void*); SQLITE_PRIVATE int sqlite3MallocSize(void*); SQLITE_PRIVATE int sqlite3DbMallocSize(sqlite3*, void*); @@ -12353,7 +14023,9 @@ SQLITE_PRIVATE void sqlite3ScratchFree(void*); SQLITE_PRIVATE void *sqlite3PageMalloc(int); SQLITE_PRIVATE void sqlite3PageFree(void*); SQLITE_PRIVATE void sqlite3MemSetDefault(void); +#ifndef SQLITE_OMIT_BUILTIN_TEST SQLITE_PRIVATE void sqlite3BenignMallocHooks(void (*)(void), void (*)(void)); +#endif SQLITE_PRIVATE int sqlite3HeapNearlyFull(void); /* @@ -12389,10 +14061,20 @@ SQLITE_PRIVATE sqlite3_mutex *sqlite3MutexAlloc(int); SQLITE_PRIVATE int sqlite3MutexInit(void); SQLITE_PRIVATE int sqlite3MutexEnd(void); #endif +#if !defined(SQLITE_MUTEX_OMIT) && !defined(SQLITE_MUTEX_NOOP) +SQLITE_PRIVATE void sqlite3MemoryBarrier(void); +#else +# define sqlite3MemoryBarrier() +#endif -SQLITE_PRIVATE int sqlite3StatusValue(int); -SQLITE_PRIVATE void sqlite3StatusAdd(int, int); -SQLITE_PRIVATE void sqlite3StatusSet(int, int); +SQLITE_PRIVATE sqlite3_int64 sqlite3StatusValue(int); +SQLITE_PRIVATE void sqlite3StatusUp(int, int); +SQLITE_PRIVATE void sqlite3StatusDown(int, int); +SQLITE_PRIVATE void sqlite3StatusHighwater(int, int); + +/* Access to mutexes used by sqlite3_status() */ +SQLITE_PRIVATE sqlite3_mutex *sqlite3Pcache1Mutex(void); +SQLITE_PRIVATE sqlite3_mutex *sqlite3MallocMutex(void); #ifndef SQLITE_OMIT_FLOATING_POINT SQLITE_PRIVATE int sqlite3IsNaN(double); @@ -12416,37 +14098,22 @@ SQLITE_PRIVATE void sqlite3VXPrintf(StrAccum*, u32, const char*, va_list); SQLITE_PRIVATE void sqlite3XPrintf(StrAccum*, u32, const char*, ...); SQLITE_PRIVATE char *sqlite3MPrintf(sqlite3*,const char*, ...); SQLITE_PRIVATE char *sqlite3VMPrintf(sqlite3*,const char*, va_list); -SQLITE_PRIVATE char *sqlite3MAppendf(sqlite3*,char*,const char*,...); -#if defined(SQLITE_TEST) || defined(SQLITE_DEBUG) +#if defined(SQLITE_DEBUG) || defined(SQLITE_HAVE_OS_TRACE) SQLITE_PRIVATE void sqlite3DebugPrintf(const char*, ...); #endif #if defined(SQLITE_TEST) SQLITE_PRIVATE void *sqlite3TestTextToPtr(const char*); #endif -/* Output formatting for SQLITE_TESTCTRL_EXPLAIN */ -#if defined(SQLITE_ENABLE_TREE_EXPLAIN) -SQLITE_PRIVATE void sqlite3ExplainBegin(Vdbe*); -SQLITE_PRIVATE void sqlite3ExplainPrintf(Vdbe*, const char*, ...); -SQLITE_PRIVATE void sqlite3ExplainNL(Vdbe*); -SQLITE_PRIVATE void sqlite3ExplainPush(Vdbe*); -SQLITE_PRIVATE void sqlite3ExplainPop(Vdbe*); -SQLITE_PRIVATE void sqlite3ExplainFinish(Vdbe*); -SQLITE_PRIVATE void sqlite3ExplainSelect(Vdbe*, Select*); -SQLITE_PRIVATE void sqlite3ExplainExpr(Vdbe*, Expr*); -SQLITE_PRIVATE void sqlite3ExplainExprList(Vdbe*, ExprList*); -SQLITE_PRIVATE const char *sqlite3VdbeExplanation(Vdbe*); -#else -# define sqlite3ExplainBegin(X) -# define sqlite3ExplainSelect(A,B) -# define sqlite3ExplainExpr(A,B) -# define sqlite3ExplainExprList(A,B) -# define sqlite3ExplainFinish(X) -# define sqlite3VdbeExplanation(X) 0 +#if defined(SQLITE_DEBUG) +SQLITE_PRIVATE void sqlite3TreeViewExpr(TreeView*, const Expr*, u8); +SQLITE_PRIVATE void sqlite3TreeViewExprList(TreeView*, const ExprList*, u8, const char*); +SQLITE_PRIVATE void sqlite3TreeViewSelect(TreeView*, const Select*, u8); +SQLITE_PRIVATE void sqlite3TreeViewWith(TreeView*, const With*, u8); #endif -SQLITE_PRIVATE void sqlite3SetString(char **, sqlite3*, const char*, ...); +SQLITE_PRIVATE void sqlite3SetString(char **, sqlite3*, const char*); SQLITE_PRIVATE void sqlite3ErrorMsg(Parse*, const char*, ...); SQLITE_PRIVATE int sqlite3Dequote(char*); SQLITE_PRIVATE int sqlite3KeywordCode(const unsigned char*, int); @@ -12466,9 +14133,11 @@ SQLITE_PRIVATE Expr *sqlite3ExprFunction(Parse*,ExprList*, Token*); SQLITE_PRIVATE void sqlite3ExprAssignVarNumber(Parse*, Expr*); SQLITE_PRIVATE void sqlite3ExprDelete(sqlite3*, Expr*); SQLITE_PRIVATE ExprList *sqlite3ExprListAppend(Parse*,ExprList*,Expr*); +SQLITE_PRIVATE void sqlite3ExprListSetSortOrder(ExprList*,int); SQLITE_PRIVATE void sqlite3ExprListSetName(Parse*,ExprList*,Token*,int); SQLITE_PRIVATE void sqlite3ExprListSetSpan(Parse*,ExprList*,ExprSpan*); SQLITE_PRIVATE void sqlite3ExprListDelete(sqlite3*, ExprList*); +SQLITE_PRIVATE u32 sqlite3ExprListFlags(const ExprList*); SQLITE_PRIVATE int sqlite3Init(sqlite3*, char**); SQLITE_PRIVATE int sqlite3InitCallback(void*, int, char**, char**); SQLITE_PRIVATE void sqlite3Pragma(Parse*,Token*,Token*,Token*,int); @@ -12477,11 +14146,18 @@ SQLITE_PRIVATE void sqlite3ResetOneSchema(sqlite3*,int); SQLITE_PRIVATE void sqlite3CollapseDatabaseArray(sqlite3*); SQLITE_PRIVATE void sqlite3BeginParse(Parse*,int); SQLITE_PRIVATE void sqlite3CommitInternalChanges(sqlite3*); +SQLITE_PRIVATE void sqlite3DeleteColumnNames(sqlite3*,Table*); +SQLITE_PRIVATE int sqlite3ColumnsFromExprList(Parse*,ExprList*,i16*,Column**); SQLITE_PRIVATE Table *sqlite3ResultSetOfSelect(Parse*,Select*); SQLITE_PRIVATE void sqlite3OpenMasterTable(Parse *, int); SQLITE_PRIVATE Index *sqlite3PrimaryKeyIndex(Table*); SQLITE_PRIVATE i16 sqlite3ColumnOfIndex(Index*, i16); SQLITE_PRIVATE void sqlite3StartTable(Parse*,Token*,Token*,int,int,int,int); +#if SQLITE_ENABLE_HIDDEN_COLUMNS +SQLITE_PRIVATE void sqlite3ColumnPropertiesFromName(Table*, Column*); +#else +# define sqlite3ColumnPropertiesFromName(T,C) /* no-op */ +#endif SQLITE_PRIVATE void sqlite3AddColumn(Parse*,Token*); SQLITE_PRIVATE void sqlite3AddNotNull(Parse*, int); SQLITE_PRIVATE void sqlite3AddPrimaryKey(Parse*, ExprList*, int, int, int); @@ -12503,11 +14179,14 @@ SQLITE_PRIVATE int sqlite3FaultSim(int); SQLITE_PRIVATE Bitvec *sqlite3BitvecCreate(u32); SQLITE_PRIVATE int sqlite3BitvecTest(Bitvec*, u32); +SQLITE_PRIVATE int sqlite3BitvecTestNotNull(Bitvec*, u32); SQLITE_PRIVATE int sqlite3BitvecSet(Bitvec*, u32); SQLITE_PRIVATE void sqlite3BitvecClear(Bitvec*, u32, void*); SQLITE_PRIVATE void sqlite3BitvecDestroy(Bitvec*); SQLITE_PRIVATE u32 sqlite3BitvecSize(Bitvec*); +#ifndef SQLITE_OMIT_BUILTIN_TEST SQLITE_PRIVATE int sqlite3BitvecBuiltinTest(int,int*); +#endif SQLITE_PRIVATE RowSet *sqlite3RowSetInit(sqlite3*, void*, unsigned int); SQLITE_PRIVATE void sqlite3RowSetClear(RowSet*); @@ -12515,7 +14194,7 @@ SQLITE_PRIVATE void sqlite3RowSetInsert(RowSet*, i64); SQLITE_PRIVATE int sqlite3RowSetTest(RowSet*, int iBatch, i64); SQLITE_PRIVATE int sqlite3RowSetNext(RowSet*, i64*); -SQLITE_PRIVATE void sqlite3CreateView(Parse*,Token*,Token*,Token*,Select*,int,int); +SQLITE_PRIVATE void sqlite3CreateView(Parse*,Token*,Token*,Token*,ExprList*,Select*,int,int); #if !defined(SQLITE_OMIT_VIEW) || !defined(SQLITE_OMIT_VIRTUALTABLE) SQLITE_PRIVATE int sqlite3ViewGetColumnNames(Parse*,Table*); @@ -12523,6 +14202,9 @@ SQLITE_PRIVATE int sqlite3ViewGetColumnNames(Parse*,Table*); # define sqlite3ViewGetColumnNames(A,B) 0 #endif +#if SQLITE_MAX_ATTACHED>30 +SQLITE_PRIVATE int sqlite3DbMaskAllZero(yDbMask); +#endif SQLITE_PRIVATE void sqlite3DropTable(Parse*, SrcList*, int, int); SQLITE_PRIVATE void sqlite3CodeDropTable(Parse*, Table*, int, int); SQLITE_PRIVATE void sqlite3DeleteTable(sqlite3*, Table*); @@ -12542,6 +14224,7 @@ SQLITE_PRIVATE SrcList *sqlite3SrcListAppend(sqlite3*, SrcList*, Token*, Token*) SQLITE_PRIVATE SrcList *sqlite3SrcListAppendFromTerm(Parse*, SrcList*, Token*, Token*, Token*, Select*, Expr*, IdList*); SQLITE_PRIVATE void sqlite3SrcListIndexedBy(Parse *, SrcList *, Token *); +SQLITE_PRIVATE void sqlite3SrcListFuncArgs(Parse*, SrcList*, ExprList*); SQLITE_PRIVATE int sqlite3IndexedByLookup(Parse *, struct SrcList_item *); SQLITE_PRIVATE void sqlite3SrcListShiftJoinType(SrcList*); SQLITE_PRIVATE void sqlite3SrcListAssignCursors(Parse*, SrcList*); @@ -12572,7 +14255,12 @@ SQLITE_PRIVATE int sqlite3WhereIsSorted(WhereInfo*); SQLITE_PRIVATE int sqlite3WhereContinueLabel(WhereInfo*); SQLITE_PRIVATE int sqlite3WhereBreakLabel(WhereInfo*); SQLITE_PRIVATE int sqlite3WhereOkOnePass(WhereInfo*, int*); +#define ONEPASS_OFF 0 /* Use of ONEPASS not allowed */ +#define ONEPASS_SINGLE 1 /* ONEPASS valid for a single row update */ +#define ONEPASS_MULTI 2 /* ONEPASS is valid for multiple rows */ +SQLITE_PRIVATE void sqlite3ExprCodeLoadIndexColumn(Parse*, Index*, int, int, int); SQLITE_PRIVATE int sqlite3ExprCodeGetColumn(Parse*, Table*, int, int, int, u8); +SQLITE_PRIVATE void sqlite3ExprCodeGetColumnToReg(Parse*, Table*, int, int, int); SQLITE_PRIVATE void sqlite3ExprCodeGetColumnOfTable(Vdbe*, Table*, int, int, int); SQLITE_PRIVATE void sqlite3ExprCodeMove(Parse*, int, int, int); SQLITE_PRIVATE void sqlite3ExprCacheStore(Parse*, int, int, int); @@ -12582,16 +14270,19 @@ SQLITE_PRIVATE void sqlite3ExprCacheRemove(Parse*, int, int); SQLITE_PRIVATE void sqlite3ExprCacheClear(Parse*); SQLITE_PRIVATE void sqlite3ExprCacheAffinityChange(Parse*, int, int); SQLITE_PRIVATE void sqlite3ExprCode(Parse*, Expr*, int); +SQLITE_PRIVATE void sqlite3ExprCodeCopy(Parse*, Expr*, int); SQLITE_PRIVATE void sqlite3ExprCodeFactorable(Parse*, Expr*, int); SQLITE_PRIVATE void sqlite3ExprCodeAtInit(Parse*, Expr*, int, u8); SQLITE_PRIVATE int sqlite3ExprCodeTemp(Parse*, Expr*, int*); SQLITE_PRIVATE int sqlite3ExprCodeTarget(Parse*, Expr*, int); SQLITE_PRIVATE void sqlite3ExprCodeAndCache(Parse*, Expr*, int); -SQLITE_PRIVATE int sqlite3ExprCodeExprList(Parse*, ExprList*, int, u8); +SQLITE_PRIVATE int sqlite3ExprCodeExprList(Parse*, ExprList*, int, int, u8); #define SQLITE_ECEL_DUP 0x01 /* Deep, not shallow copies */ #define SQLITE_ECEL_FACTOR 0x02 /* Factor out constant terms */ +#define SQLITE_ECEL_REF 0x04 /* Use ExprList.u.x.iOrderByCol */ SQLITE_PRIVATE void sqlite3ExprIfTrue(Parse*, Expr*, int, int); SQLITE_PRIVATE void sqlite3ExprIfFalse(Parse*, Expr*, int, int); +SQLITE_PRIVATE void sqlite3ExprIfFalseDup(Parse*, Expr*, int, int); SQLITE_PRIVATE Table *sqlite3FindTable(sqlite3*,const char*, const char*); SQLITE_PRIVATE Table *sqlite3LocateTable(Parse*,int isView,const char*, const char*); SQLITE_PRIVATE Table *sqlite3LocateTableItem(Parse*,int isView,struct SrcList_item *); @@ -12608,8 +14299,10 @@ SQLITE_PRIVATE void sqlite3ExprAnalyzeAggregates(NameContext*, Expr*); SQLITE_PRIVATE void sqlite3ExprAnalyzeAggList(NameContext*,ExprList*); SQLITE_PRIVATE int sqlite3FunctionUsesThisSrc(Expr*, SrcList*); SQLITE_PRIVATE Vdbe *sqlite3GetVdbe(Parse*); +#ifndef SQLITE_OMIT_BUILTIN_TEST SQLITE_PRIVATE void sqlite3PrngSaveState(void); SQLITE_PRIVATE void sqlite3PrngRestoreState(void); +#endif SQLITE_PRIVATE void sqlite3RollbackAll(sqlite3*,int); SQLITE_PRIVATE void sqlite3CodeVerifySchema(Parse*, int); SQLITE_PRIVATE void sqlite3CodeVerifyNamedSchema(Parse*, const char *zDb); @@ -12621,19 +14314,24 @@ SQLITE_PRIVATE void sqlite3CloseSavepoints(sqlite3 *); SQLITE_PRIVATE void sqlite3LeaveMutexAndCloseZombie(sqlite3*); SQLITE_PRIVATE int sqlite3ExprIsConstant(Expr*); SQLITE_PRIVATE int sqlite3ExprIsConstantNotJoin(Expr*); -SQLITE_PRIVATE int sqlite3ExprIsConstantOrFunction(Expr*); +SQLITE_PRIVATE int sqlite3ExprIsConstantOrFunction(Expr*, u8); +SQLITE_PRIVATE int sqlite3ExprIsTableConstant(Expr*,int); +#ifdef SQLITE_ENABLE_CURSOR_HINTS +SQLITE_PRIVATE int sqlite3ExprContainsSubquery(Expr*); +#endif SQLITE_PRIVATE int sqlite3ExprIsInteger(Expr*, int*); SQLITE_PRIVATE int sqlite3ExprCanBeNull(const Expr*); SQLITE_PRIVATE int sqlite3ExprNeedsNoAffinityChange(const Expr*, char); SQLITE_PRIVATE int sqlite3IsRowid(const char*); -SQLITE_PRIVATE void sqlite3GenerateRowDelete(Parse*,Table*,Trigger*,int,int,int,i16,u8,u8,u8); -SQLITE_PRIVATE void sqlite3GenerateRowIndexDelete(Parse*, Table*, int, int, int*); +SQLITE_PRIVATE void sqlite3GenerateRowDelete( + Parse*,Table*,Trigger*,int,int,int,i16,u8,u8,u8,int); +SQLITE_PRIVATE void sqlite3GenerateRowIndexDelete(Parse*, Table*, int, int, int*, int); SQLITE_PRIVATE int sqlite3GenerateIndexKey(Parse*, Index*, int, int, int, int*,Index*,int); SQLITE_PRIVATE void sqlite3ResolvePartIdxLabel(Parse*,int); SQLITE_PRIVATE void sqlite3GenerateConstraintChecks(Parse*,Table*,int*,int,int,int,int, u8,u8,int,int*); SQLITE_PRIVATE void sqlite3CompleteInsertion(Parse*,Table*,int,int,int,int*,int,int,int); -SQLITE_PRIVATE int sqlite3OpenTableAndIndices(Parse*, Table*, int, int, u8*, int*, int*); +SQLITE_PRIVATE int sqlite3OpenTableAndIndices(Parse*, Table*, int, u8, int, u8*, int*, int*); SQLITE_PRIVATE void sqlite3BeginWriteOperation(Parse*, int, int); SQLITE_PRIVATE void sqlite3MultiWrite(Parse*); SQLITE_PRIVATE void sqlite3MayAbort(Parse*); @@ -12645,6 +14343,11 @@ SQLITE_PRIVATE ExprList *sqlite3ExprListDup(sqlite3*,ExprList*,int); SQLITE_PRIVATE SrcList *sqlite3SrcListDup(sqlite3*,SrcList*,int); SQLITE_PRIVATE IdList *sqlite3IdListDup(sqlite3*,IdList*); SQLITE_PRIVATE Select *sqlite3SelectDup(sqlite3*,Select*,int); +#if SELECTTRACE_ENABLED +SQLITE_PRIVATE void sqlite3SelectSetName(Select*,const char*); +#else +# define sqlite3SelectSetName(A,B) +#endif SQLITE_PRIVATE void sqlite3FuncDefInsert(FuncDefHash*, FuncDef*); SQLITE_PRIVATE FuncDef *sqlite3FindFunction(sqlite3*,const char*,int,int,u8,u8); SQLITE_PRIVATE void sqlite3RegisterBuiltinFunctions(sqlite3*); @@ -12680,6 +14383,7 @@ SQLITE_PRIVATE void sqlite3DeleteTrigger(sqlite3*, Trigger*); SQLITE_PRIVATE void sqlite3UnlinkAndDeleteTrigger(sqlite3*,int,const char*); SQLITE_PRIVATE u32 sqlite3TriggerColmask(Parse*,Trigger*,ExprList*,int,int,Table*,int); # define sqlite3ParseToplevel(p) ((p)->pToplevel ? (p)->pToplevel : (p)) +# define sqlite3IsToplevel(p) ((p)->pToplevel==0) #else # define sqlite3TriggersExist(B,C,D,E,F) 0 # define sqlite3DeleteTrigger(A,B) @@ -12689,6 +14393,7 @@ SQLITE_PRIVATE u32 sqlite3TriggerColmask(Parse*,Trigger*,ExprList*,int,int,Tab # define sqlite3CodeRowTriggerDirect(A,B,C,D,E,F) # define sqlite3TriggerList(X, Y) 0 # define sqlite3ParseToplevel(p) p +# define sqlite3IsToplevel(p) 1 # define sqlite3TriggerColmask(A,B,C,D,E,F,G) 0 #endif @@ -12731,54 +14436,41 @@ SQLITE_PRIVATE u64 sqlite3LogEstToInt(LogEst); /* ** Routines to read and write variable-length integers. These used to ** be defined locally, but now we use the varint routines in the util.c -** file. Code should use the MACRO forms below, as the Varint32 versions -** are coded to assume the single byte case is already handled (which -** the MACRO form does). +** file. */ SQLITE_PRIVATE int sqlite3PutVarint(unsigned char*, u64); -SQLITE_PRIVATE int sqlite3PutVarint32(unsigned char*, u32); SQLITE_PRIVATE u8 sqlite3GetVarint(const unsigned char *, u64 *); SQLITE_PRIVATE u8 sqlite3GetVarint32(const unsigned char *, u32 *); SQLITE_PRIVATE int sqlite3VarintLen(u64 v); /* -** The header of a record consists of a sequence variable-length integers. -** These integers are almost always small and are encoded as a single byte. -** The following macros take advantage this fact to provide a fast encode -** and decode of the integers in a record header. It is faster for the common -** case where the integer is a single byte. It is a little slower when the -** integer is two or more bytes. But overall it is faster. -** -** The following expressions are equivalent: -** -** x = sqlite3GetVarint32( A, &B ); -** x = sqlite3PutVarint32( A, B ); -** -** x = getVarint32( A, B ); -** x = putVarint32( A, B ); -** +** The common case is for a varint to be a single byte. They following +** macros handle the common case without a procedure call, but then call +** the procedure for larger varints. */ #define getVarint32(A,B) \ (u8)((*(A)<(u8)0x80)?((B)=(u32)*(A)),1:sqlite3GetVarint32((A),(u32 *)&(B))) #define putVarint32(A,B) \ (u8)(((u32)(B)<(u32)0x80)?(*(A)=(unsigned char)(B)),1:\ - sqlite3PutVarint32((A),(B))) + sqlite3PutVarint((A),(B))) #define getVarint sqlite3GetVarint #define putVarint sqlite3PutVarint -SQLITE_PRIVATE const char *sqlite3IndexAffinityStr(Vdbe *, Index *); +SQLITE_PRIVATE const char *sqlite3IndexAffinityStr(sqlite3*, Index*); SQLITE_PRIVATE void sqlite3TableAffinity(Vdbe*, Table*, int); SQLITE_PRIVATE char sqlite3CompareAffinity(Expr *pExpr, char aff2); SQLITE_PRIVATE int sqlite3IndexAffinityOk(Expr *pExpr, char idx_affinity); SQLITE_PRIVATE char sqlite3ExprAffinity(Expr *pExpr); SQLITE_PRIVATE int sqlite3Atoi64(const char*, i64*, int, u8); -SQLITE_PRIVATE void sqlite3Error(sqlite3*, int, const char*,...); +SQLITE_PRIVATE int sqlite3DecOrHexToI64(const char*, i64*); +SQLITE_PRIVATE void sqlite3ErrorWithMsg(sqlite3*, int, const char*,...); +SQLITE_PRIVATE void sqlite3Error(sqlite3*,int); SQLITE_PRIVATE void *sqlite3HexToBlob(sqlite3*, const char *z, int n); SQLITE_PRIVATE u8 sqlite3HexToInt(int h); SQLITE_PRIVATE int sqlite3TwoPartName(Parse *, Token *, Token *, Token **); -#if defined(SQLITE_TEST) +#if defined(SQLITE_NEED_ERR_NAME) SQLITE_PRIVATE const char *sqlite3ErrName(int); #endif @@ -12787,7 +14479,7 @@ SQLITE_PRIVATE int sqlite3ReadSchema(Parse *pParse); SQLITE_PRIVATE CollSeq *sqlite3FindCollSeq(sqlite3*,u8 enc, const char*,int); SQLITE_PRIVATE CollSeq *sqlite3LocateCollSeq(Parse *pParse, const char*zName); SQLITE_PRIVATE CollSeq *sqlite3ExprCollSeq(Parse *pParse, Expr *pExpr); -SQLITE_PRIVATE Expr *sqlite3ExprAddCollateToken(Parse *pParse, Expr*, const Token*); +SQLITE_PRIVATE Expr *sqlite3ExprAddCollateToken(Parse *pParse, Expr*, const Token*, int); SQLITE_PRIVATE Expr *sqlite3ExprAddCollateString(Parse*,Expr*,const char*); SQLITE_PRIVATE Expr *sqlite3ExprSkipCollate(Expr*); SQLITE_PRIVATE int sqlite3CheckCollSeq(Parse *, CollSeq *); @@ -12802,7 +14494,7 @@ SQLITE_PRIVATE void sqlite3FileSuffix3(const char*, char*); #else # define sqlite3FileSuffix3(X,Y) #endif -SQLITE_PRIVATE u8 sqlite3GetBoolean(const char *z,int); +SQLITE_PRIVATE u8 sqlite3GetBoolean(const char *z,u8); SQLITE_PRIVATE const void *sqlite3ValueText(sqlite3_value*, u8); SQLITE_PRIVATE int sqlite3ValueBytes(sqlite3_value*, u8); @@ -12816,6 +14508,7 @@ SQLITE_PRIVATE int sqlite3ValueFromExpr(sqlite3 *, Expr *, u8, u8, sqlite3_value SQLITE_PRIVATE void sqlite3ValueApplyAffinity(sqlite3_value *, u8, u8); #ifndef SQLITE_AMALGAMATION SQLITE_PRIVATE const unsigned char sqlite3OpcodeProperty[]; +SQLITE_PRIVATE const char sqlite3StrBINARY[]; SQLITE_PRIVATE const unsigned char sqlite3UpperToLower[]; SQLITE_PRIVATE const unsigned char sqlite3CtypeMap[]; SQLITE_PRIVATE const Token sqlite3IntTokens[]; @@ -12834,8 +14527,10 @@ SQLITE_PRIVATE void sqlite3NestedParse(Parse*, const char*, ...); SQLITE_PRIVATE void sqlite3ExpirePreparedStatements(sqlite3*); SQLITE_PRIVATE int sqlite3CodeSubselect(Parse *, Expr *, int, int); SQLITE_PRIVATE void sqlite3SelectPrep(Parse*, Select*, NameContext*); +SQLITE_PRIVATE void sqlite3SelectWrongNumTermsError(Parse *pParse, Select *p); SQLITE_PRIVATE int sqlite3MatchSpanName(const char*, const char*, const char*, const char*); SQLITE_PRIVATE int sqlite3ResolveExprNames(NameContext*, Expr*); +SQLITE_PRIVATE int sqlite3ResolveExprListNames(NameContext*, ExprList*); SQLITE_PRIVATE void sqlite3ResolveSelectNames(Parse*, Select*, NameContext*); SQLITE_PRIVATE void sqlite3ResolveSelfReference(Parse*,Table*,int,Expr*,ExprList*); SQLITE_PRIVATE int sqlite3ResolveOrderGroupBy(Parse*, Select*, ExprList*, const char*); @@ -12872,10 +14567,10 @@ SQLITE_PRIVATE int sqlite3CreateFunc(sqlite3 *, const char *, int, int, void *, SQLITE_PRIVATE int sqlite3ApiExit(sqlite3 *db, int); SQLITE_PRIVATE int sqlite3OpenTempDatabase(Parse *); -SQLITE_PRIVATE void sqlite3StrAccumInit(StrAccum*, char*, int, int); +SQLITE_PRIVATE void sqlite3StrAccumInit(StrAccum*, sqlite3*, char*, int, int); SQLITE_PRIVATE void sqlite3StrAccumAppend(StrAccum*,const char*,int); SQLITE_PRIVATE void sqlite3StrAccumAppendAll(StrAccum*,const char*); -SQLITE_PRIVATE void sqlite3AppendSpace(StrAccum*,int); +SQLITE_PRIVATE void sqlite3AppendChar(StrAccum*,int,char); SQLITE_PRIVATE char *sqlite3StrAccumFinish(StrAccum*); SQLITE_PRIVATE void sqlite3StrAccumReset(StrAccum*); SQLITE_PRIVATE void sqlite3SelectDestInit(SelectDest*,int,int); @@ -12887,13 +14582,15 @@ SQLITE_PRIVATE void sqlite3BackupUpdate(sqlite3_backup *, Pgno, const u8 *); #ifdef SQLITE_ENABLE_STAT3_OR_STAT4 SQLITE_PRIVATE void sqlite3AnalyzeFunctions(void); SQLITE_PRIVATE int sqlite3Stat4ProbeSetValue(Parse*,Index*,UnpackedRecord**,Expr*,u8,int,int*); +SQLITE_PRIVATE int sqlite3Stat4ValueFromExpr(Parse*, Expr*, u8, sqlite3_value**); SQLITE_PRIVATE void sqlite3Stat4ProbeFree(UnpackedRecord*); +SQLITE_PRIVATE int sqlite3Stat4Column(sqlite3*, const void*, int, int, sqlite3_value**); #endif /* ** The interface to the LEMON-generated parser */ -SQLITE_PRIVATE void *sqlite3ParserAlloc(void*(*)(size_t)); +SQLITE_PRIVATE void *sqlite3ParserAlloc(void*(*)(u64)); SQLITE_PRIVATE void sqlite3ParserFree(void*, void(*)(void*)); SQLITE_PRIVATE void sqlite3Parser(void*, int, Token, Parse*); #ifdef YYTRACKMAXSTACKDEPTH @@ -12942,6 +14639,8 @@ SQLITE_PRIVATE void sqlite3VtabImportErrmsg(Vdbe*, sqlite3_vtab*); SQLITE_PRIVATE VTable *sqlite3GetVTable(sqlite3*, Table*); # define sqlite3VtabInSync(db) ((db)->nVTrans>0 && (db)->aVTrans==0) #endif +SQLITE_PRIVATE int sqlite3VtabEponymousTableInit(Parse*,Module*); +SQLITE_PRIVATE void sqlite3VtabEponymousTableClear(sqlite3*,Module*); SQLITE_PRIVATE void sqlite3VtabMakeWritable(Parse*,Table*); SQLITE_PRIVATE void sqlite3VtabBeginParse(Parse*, Token*, Token*, Token*, int); SQLITE_PRIVATE void sqlite3VtabFinishParse(Parse*, Token*); @@ -13024,11 +14723,21 @@ SQLITE_PRIVATE void sqlite3EndBenignMalloc(void); #define sqlite3EndBenignMalloc() #endif -#define IN_INDEX_ROWID 1 -#define IN_INDEX_EPH 2 -#define IN_INDEX_INDEX_ASC 3 -#define IN_INDEX_INDEX_DESC 4 -SQLITE_PRIVATE int sqlite3FindInIndex(Parse *, Expr *, int*); +/* +** Allowed return values from sqlite3FindInIndex() +*/ +#define IN_INDEX_ROWID 1 /* Search the rowid of the table */ +#define IN_INDEX_EPH 2 /* Search an ephemeral b-tree */ +#define IN_INDEX_INDEX_ASC 3 /* Existing index ASCENDING */ +#define IN_INDEX_INDEX_DESC 4 /* Existing index DESCENDING */ +#define IN_INDEX_NOOP 5 /* No table available. Use comparisons */ +/* +** Allowed flags for the 3rd parameter to sqlite3FindInIndex(). +*/ +#define IN_INDEX_NOOP_OK 0x0001 /* OK to return IN_INDEX_NOOP */ +#define IN_INDEX_MEMBERSHIP 0x0002 /* IN operator used for membership test */ +#define IN_INDEX_LOOP 0x0004 /* IN operator used as a loop */ +SQLITE_PRIVATE int sqlite3FindInIndex(Parse *, Expr *, u32, int*); #ifdef SQLITE_ENABLE_ATOMIC_WRITE SQLITE_PRIVATE int sqlite3JournalOpen(sqlite3_vfs *, const char *, sqlite3_file *, int, int); @@ -13044,12 +14753,11 @@ SQLITE_PRIVATE void sqlite3MemJournalOpen(sqlite3_file *); SQLITE_PRIVATE int sqlite3MemJournalSize(void); SQLITE_PRIVATE int sqlite3IsMemJournal(sqlite3_file *); +SQLITE_PRIVATE void sqlite3ExprSetHeightAndFlags(Parse *pParse, Expr *p); #if SQLITE_MAX_EXPR_DEPTH>0 -SQLITE_PRIVATE void sqlite3ExprSetHeight(Parse *pParse, Expr *p); SQLITE_PRIVATE int sqlite3SelectExprHeight(Select *); SQLITE_PRIVATE int sqlite3ExprCheckHeight(Parse*, int); #else - #define sqlite3ExprSetHeight(x,y) #define sqlite3SelectExprHeight(x) 0 #define sqlite3ExprCheckHeight(x,y) #endif @@ -13079,7 +14787,7 @@ SQLITE_PRIVATE void sqlite3ParserTrace(FILE*, char *); #ifdef SQLITE_ENABLE_IOTRACE # define IOTRACE(A) if( sqlite3IoTrace ){ sqlite3IoTrace A; } SQLITE_PRIVATE void sqlite3VdbeIOTraceSql(Vdbe*); -SQLITE_PRIVATE void (*sqlite3IoTrace)(const char*,...); +SQLITE_API SQLITE_EXTERN void (SQLITE_CDECL *sqlite3IoTrace)(const char*,...); #else # define IOTRACE(A) # define sqlite3VdbeIOTraceSql(X) @@ -13123,10 +14831,21 @@ SQLITE_PRIVATE int sqlite3MemdebugNoType(void*,u8); # define sqlite3MemdebugNoType(X,Y) 1 #endif #define MEMTYPE_HEAP 0x01 /* General heap allocations */ -#define MEMTYPE_LOOKASIDE 0x02 /* Might have been lookaside memory */ +#define MEMTYPE_LOOKASIDE 0x02 /* Heap that might have been lookaside */ #define MEMTYPE_SCRATCH 0x04 /* Scratch allocations */ #define MEMTYPE_PCACHE 0x08 /* Page cache allocations */ -#define MEMTYPE_DB 0x10 /* Uses sqlite3DbMalloc, not sqlite_malloc */ + +/* +** Threading interface +*/ +#if SQLITE_MAX_WORKER_THREADS>0 +SQLITE_PRIVATE int sqlite3ThreadCreate(SQLiteThread**,void*(*)(void*),void*); +SQLITE_PRIVATE int sqlite3ThreadJoin(SQLiteThread*, void**); +#endif + +#if defined(SQLITE_ENABLE_DBSTAT_VTAB) || defined(SQLITE_TEST) +SQLITE_PRIVATE int sqlite3DbstatRegister(sqlite3*); +#endif #endif /* _SQLITEINT_H_ */ @@ -13144,8 +14863,9 @@ SQLITE_PRIVATE int sqlite3MemdebugNoType(void*,u8); ** ************************************************************************* ** -** This file contains definitions of global variables and contants. +** This file contains definitions of global variables and constants. */ +/* #include "sqliteInt.h" */ /* An array to map all upper-case characters into their corresponding ** lower-case character. @@ -13179,16 +14899,16 @@ SQLITE_PRIVATE const unsigned char sqlite3UpperToLower[] = { 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, /* 3x */ 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, /* 4x */ 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, /* 5x */ - 96, 97, 66, 67, 68, 69, 70, 71, 72, 73,106,107,108,109,110,111, /* 6x */ - 112, 81, 82, 83, 84, 85, 86, 87, 88, 89,122,123,124,125,126,127, /* 7x */ + 96, 97, 98, 99,100,101,102,103,104,105,106,107,108,109,110,111, /* 6x */ + 112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127, /* 7x */ 128,129,130,131,132,133,134,135,136,137,138,139,140,141,142,143, /* 8x */ - 144,145,146,147,148,149,150,151,152,153,154,155,156,157,156,159, /* 9x */ + 144,145,146,147,148,149,150,151,152,153,154,155,156,157,158,159, /* 9x */ 160,161,162,163,164,165,166,167,168,169,170,171,140,141,142,175, /* Ax */ 176,177,178,179,180,181,182,183,184,185,186,187,188,189,190,191, /* Bx */ 192,129,130,131,132,133,134,135,136,137,202,203,204,205,206,207, /* Cx */ 208,145,146,147,148,149,150,151,152,153,218,219,220,221,222,223, /* Dx */ - 224,225,162,163,164,165,166,167,168,169,232,203,204,205,206,207, /* Ex */ - 239,240,241,242,243,244,245,246,247,248,249,219,220,221,222,255, /* Fx */ + 224,225,162,163,164,165,166,167,168,169,234,235,236,237,238,239, /* Ex */ + 240,241,242,243,244,245,246,247,248,249,250,251,252,253,254,255, /* Fx */ #endif }; @@ -13262,14 +14982,36 @@ SQLITE_PRIVATE const unsigned char sqlite3CtypeMap[256] = { }; #endif +/* EVIDENCE-OF: R-02982-34736 In order to maintain full backwards +** compatibility for legacy applications, the URI filename capability is +** disabled by default. +** +** EVIDENCE-OF: R-38799-08373 URI filenames can be enabled or disabled +** using the SQLITE_USE_URI=1 or SQLITE_USE_URI=0 compile-time options. +** +** EVIDENCE-OF: R-43642-56306 By default, URI handling is globally +** disabled. The default value may be changed by compiling with the +** SQLITE_USE_URI symbol defined. +*/ #ifndef SQLITE_USE_URI # define SQLITE_USE_URI 0 #endif +/* EVIDENCE-OF: R-38720-18127 The default setting is determined by the +** SQLITE_ALLOW_COVERING_INDEX_SCAN compile-time option, or is "on" if +** that compile-time option is omitted. +*/ #ifndef SQLITE_ALLOW_COVERING_INDEX_SCAN # define SQLITE_ALLOW_COVERING_INDEX_SCAN 1 #endif +/* The minimum PMA size is set to this value multiplied by the database +** page size in bytes. +*/ +#ifndef SQLITE_SORTER_PMASZ +# define SQLITE_SORTER_PMASZ 250 +#endif + /* ** The following singleton contains the global configuration for ** the SQLite library. @@ -13297,9 +15039,10 @@ SQLITE_PRIVATE SQLITE_WSD struct Sqlite3Config sqlite3Config = { 0, /* nScratch */ (void*)0, /* pPage */ 0, /* szPage */ - 0, /* nPage */ + SQLITE_DEFAULT_PCACHE_INITSZ, /* nPage */ 0, /* mxParserStack */ 0, /* sharedCacheEnabled */ + SQLITE_SORTER_PMASZ, /* szPma */ /* All the rest should always be initialized to zero */ 0, /* isInit */ 0, /* inProgress */ @@ -13355,13 +15098,14 @@ SQLITE_PRIVATE const Token sqlite3IntTokens[] = { ** ** IMPORTANT: Changing the pending byte to any value other than ** 0x40000000 results in an incompatible database file format! -** Changing the pending byte during operating results in undefined -** and dileterious behavior. +** Changing the pending byte during operation will result in undefined +** and incorrect behavior. */ #ifndef SQLITE_OMIT_WSD SQLITE_PRIVATE int sqlite3PendingByte = 0x40000000; #endif +/* #include "opcodes.h" */ /* ** Properties of opcodes. The OPFLG_INITIALIZER macro is ** created by mkopcodeh.awk during compilation. Data is obtained @@ -13370,6 +15114,11 @@ SQLITE_PRIVATE int sqlite3PendingByte = 0x40000000; */ SQLITE_PRIVATE const unsigned char sqlite3OpcodeProperty[] = OPFLG_INITIALIZER; +/* +** Name of the default collating sequence +*/ +SQLITE_PRIVATE const char sqlite3StrBINARY[] = "BINARY"; + /************** End of global.c **********************************************/ /************** Begin file ctime.c *******************************************/ /* @@ -13390,6 +15139,7 @@ SQLITE_PRIVATE const unsigned char sqlite3OpcodeProperty[] = OPFLG_INITIALIZER; #ifndef SQLITE_OMIT_COMPILEOPTION_DIAGS +/* #include "sqliteInt.h" */ /* ** An array of names of all compile-time options. This array should @@ -13406,88 +15156,103 @@ static const char * const azCompileOpt[] = { #define CTIMEOPT_VAL_(opt) #opt #define CTIMEOPT_VAL(opt) CTIMEOPT_VAL_(opt) -#ifdef SQLITE_32BIT_ROWID +#if SQLITE_32BIT_ROWID "32BIT_ROWID", #endif -#ifdef SQLITE_4_BYTE_ALIGNED_MALLOC +#if SQLITE_4_BYTE_ALIGNED_MALLOC "4_BYTE_ALIGNED_MALLOC", #endif -#ifdef SQLITE_CASE_SENSITIVE_LIKE +#if SQLITE_CASE_SENSITIVE_LIKE "CASE_SENSITIVE_LIKE", #endif -#ifdef SQLITE_CHECK_PAGES +#if SQLITE_CHECK_PAGES "CHECK_PAGES", #endif -#ifdef SQLITE_COVERAGE_TEST +#if SQLITE_COVERAGE_TEST "COVERAGE_TEST", #endif -#ifdef SQLITE_DEBUG +#if SQLITE_DEBUG "DEBUG", #endif -#ifdef SQLITE_DEFAULT_LOCKING_MODE +#if SQLITE_DEFAULT_LOCKING_MODE "DEFAULT_LOCKING_MODE=" CTIMEOPT_VAL(SQLITE_DEFAULT_LOCKING_MODE), #endif #if defined(SQLITE_DEFAULT_MMAP_SIZE) && !defined(SQLITE_DEFAULT_MMAP_SIZE_xc) "DEFAULT_MMAP_SIZE=" CTIMEOPT_VAL(SQLITE_DEFAULT_MMAP_SIZE), #endif -#ifdef SQLITE_DISABLE_DIRSYNC +#if SQLITE_DISABLE_DIRSYNC "DISABLE_DIRSYNC", #endif -#ifdef SQLITE_DISABLE_LFS +#if SQLITE_DISABLE_LFS "DISABLE_LFS", #endif -#ifdef SQLITE_ENABLE_ATOMIC_WRITE +#if SQLITE_ENABLE_8_3_NAMES + "ENABLE_8_3_NAMES", +#endif +#if SQLITE_ENABLE_API_ARMOR + "ENABLE_API_ARMOR", +#endif +#if SQLITE_ENABLE_ATOMIC_WRITE "ENABLE_ATOMIC_WRITE", #endif -#ifdef SQLITE_ENABLE_CEROD +#if SQLITE_ENABLE_CEROD "ENABLE_CEROD", #endif -#ifdef SQLITE_ENABLE_COLUMN_METADATA +#if SQLITE_ENABLE_COLUMN_METADATA "ENABLE_COLUMN_METADATA", #endif -#ifdef SQLITE_ENABLE_EXPENSIVE_ASSERT +#if SQLITE_ENABLE_DBSTAT_VTAB + "ENABLE_DBSTAT_VTAB", +#endif +#if SQLITE_ENABLE_EXPENSIVE_ASSERT "ENABLE_EXPENSIVE_ASSERT", #endif -#ifdef SQLITE_ENABLE_FTS1 +#if SQLITE_ENABLE_FTS1 "ENABLE_FTS1", #endif -#ifdef SQLITE_ENABLE_FTS2 +#if SQLITE_ENABLE_FTS2 "ENABLE_FTS2", #endif -#ifdef SQLITE_ENABLE_FTS3 +#if SQLITE_ENABLE_FTS3 "ENABLE_FTS3", #endif -#ifdef SQLITE_ENABLE_FTS3_PARENTHESIS +#if SQLITE_ENABLE_FTS3_PARENTHESIS "ENABLE_FTS3_PARENTHESIS", #endif -#ifdef SQLITE_ENABLE_FTS4 +#if SQLITE_ENABLE_FTS4 "ENABLE_FTS4", #endif -#ifdef SQLITE_ENABLE_ICU +#if SQLITE_ENABLE_FTS5 + "ENABLE_FTS5", +#endif +#if SQLITE_ENABLE_ICU "ENABLE_ICU", #endif -#ifdef SQLITE_ENABLE_IOTRACE +#if SQLITE_ENABLE_IOTRACE "ENABLE_IOTRACE", #endif -#ifdef SQLITE_ENABLE_LOAD_EXTENSION +#if SQLITE_ENABLE_JSON1 + "ENABLE_JSON1", +#endif +#if SQLITE_ENABLE_LOAD_EXTENSION "ENABLE_LOAD_EXTENSION", #endif -#ifdef SQLITE_ENABLE_LOCKING_STYLE +#if SQLITE_ENABLE_LOCKING_STYLE "ENABLE_LOCKING_STYLE=" CTIMEOPT_VAL(SQLITE_ENABLE_LOCKING_STYLE), #endif -#ifdef SQLITE_ENABLE_MEMORY_MANAGEMENT +#if SQLITE_ENABLE_MEMORY_MANAGEMENT "ENABLE_MEMORY_MANAGEMENT", #endif -#ifdef SQLITE_ENABLE_MEMSYS3 +#if SQLITE_ENABLE_MEMSYS3 "ENABLE_MEMSYS3", #endif -#ifdef SQLITE_ENABLE_MEMSYS5 +#if SQLITE_ENABLE_MEMSYS5 "ENABLE_MEMSYS5", #endif -#ifdef SQLITE_ENABLE_OVERSIZE_CELL_CHECK +#if SQLITE_ENABLE_OVERSIZE_CELL_CHECK "ENABLE_OVERSIZE_CELL_CHECK", #endif -#ifdef SQLITE_ENABLE_RTREE +#if SQLITE_ENABLE_RTREE "ENABLE_RTREE", #endif #if defined(SQLITE_ENABLE_STAT4) @@ -13495,31 +15260,34 @@ static const char * const azCompileOpt[] = { #elif defined(SQLITE_ENABLE_STAT3) "ENABLE_STAT3", #endif -#ifdef SQLITE_ENABLE_UNLOCK_NOTIFY +#if SQLITE_ENABLE_UNLOCK_NOTIFY "ENABLE_UNLOCK_NOTIFY", #endif -#ifdef SQLITE_ENABLE_UPDATE_DELETE_LIMIT +#if SQLITE_ENABLE_UPDATE_DELETE_LIMIT "ENABLE_UPDATE_DELETE_LIMIT", #endif -#ifdef SQLITE_HAS_CODEC +#if SQLITE_HAS_CODEC "HAS_CODEC", #endif -#ifdef SQLITE_HAVE_ISNAN +#if HAVE_ISNAN || SQLITE_HAVE_ISNAN "HAVE_ISNAN", #endif -#ifdef SQLITE_HOMEGROWN_RECURSIVE_MUTEX +#if SQLITE_HOMEGROWN_RECURSIVE_MUTEX "HOMEGROWN_RECURSIVE_MUTEX", #endif -#ifdef SQLITE_IGNORE_AFP_LOCK_ERRORS +#if SQLITE_IGNORE_AFP_LOCK_ERRORS "IGNORE_AFP_LOCK_ERRORS", #endif -#ifdef SQLITE_IGNORE_FLOCK_LOCK_ERRORS +#if SQLITE_IGNORE_FLOCK_LOCK_ERRORS "IGNORE_FLOCK_LOCK_ERRORS", #endif #ifdef SQLITE_INT64_TYPE "INT64_TYPE", #endif -#ifdef SQLITE_LOCK_TRACE +#ifdef SQLITE_LIKE_DOESNT_MATCH_BLOBS + "LIKE_DOESNT_MATCH_BLOBS", +#endif +#if SQLITE_LOCK_TRACE "LOCK_TRACE", #endif #if defined(SQLITE_MAX_MMAP_SIZE) && !defined(SQLITE_MAX_MMAP_SIZE_xc) @@ -13528,223 +15296,226 @@ static const char * const azCompileOpt[] = { #ifdef SQLITE_MAX_SCHEMA_RETRY "MAX_SCHEMA_RETRY=" CTIMEOPT_VAL(SQLITE_MAX_SCHEMA_RETRY), #endif -#ifdef SQLITE_MEMDEBUG +#if SQLITE_MEMDEBUG "MEMDEBUG", #endif -#ifdef SQLITE_MIXED_ENDIAN_64BIT_FLOAT +#if SQLITE_MIXED_ENDIAN_64BIT_FLOAT "MIXED_ENDIAN_64BIT_FLOAT", #endif -#ifdef SQLITE_NO_SYNC +#if SQLITE_NO_SYNC "NO_SYNC", #endif -#ifdef SQLITE_OMIT_ALTERTABLE +#if SQLITE_OMIT_ALTERTABLE "OMIT_ALTERTABLE", #endif -#ifdef SQLITE_OMIT_ANALYZE +#if SQLITE_OMIT_ANALYZE "OMIT_ANALYZE", #endif -#ifdef SQLITE_OMIT_ATTACH +#if SQLITE_OMIT_ATTACH "OMIT_ATTACH", #endif -#ifdef SQLITE_OMIT_AUTHORIZATION +#if SQLITE_OMIT_AUTHORIZATION "OMIT_AUTHORIZATION", #endif -#ifdef SQLITE_OMIT_AUTOINCREMENT +#if SQLITE_OMIT_AUTOINCREMENT "OMIT_AUTOINCREMENT", #endif -#ifdef SQLITE_OMIT_AUTOINIT +#if SQLITE_OMIT_AUTOINIT "OMIT_AUTOINIT", #endif -#ifdef SQLITE_OMIT_AUTOMATIC_INDEX +#if SQLITE_OMIT_AUTOMATIC_INDEX "OMIT_AUTOMATIC_INDEX", #endif -#ifdef SQLITE_OMIT_AUTORESET +#if SQLITE_OMIT_AUTORESET "OMIT_AUTORESET", #endif -#ifdef SQLITE_OMIT_AUTOVACUUM +#if SQLITE_OMIT_AUTOVACUUM "OMIT_AUTOVACUUM", #endif -#ifdef SQLITE_OMIT_BETWEEN_OPTIMIZATION +#if SQLITE_OMIT_BETWEEN_OPTIMIZATION "OMIT_BETWEEN_OPTIMIZATION", #endif -#ifdef SQLITE_OMIT_BLOB_LITERAL +#if SQLITE_OMIT_BLOB_LITERAL "OMIT_BLOB_LITERAL", #endif -#ifdef SQLITE_OMIT_BTREECOUNT +#if SQLITE_OMIT_BTREECOUNT "OMIT_BTREECOUNT", #endif -#ifdef SQLITE_OMIT_BUILTIN_TEST +#if SQLITE_OMIT_BUILTIN_TEST "OMIT_BUILTIN_TEST", #endif -#ifdef SQLITE_OMIT_CAST +#if SQLITE_OMIT_CAST "OMIT_CAST", #endif -#ifdef SQLITE_OMIT_CHECK +#if SQLITE_OMIT_CHECK "OMIT_CHECK", #endif -#ifdef SQLITE_OMIT_COMPLETE +#if SQLITE_OMIT_COMPLETE "OMIT_COMPLETE", #endif -#ifdef SQLITE_OMIT_COMPOUND_SELECT +#if SQLITE_OMIT_COMPOUND_SELECT "OMIT_COMPOUND_SELECT", #endif -#ifdef SQLITE_OMIT_CTE +#if SQLITE_OMIT_CTE "OMIT_CTE", #endif -#ifdef SQLITE_OMIT_DATETIME_FUNCS +#if SQLITE_OMIT_DATETIME_FUNCS "OMIT_DATETIME_FUNCS", #endif -#ifdef SQLITE_OMIT_DECLTYPE +#if SQLITE_OMIT_DECLTYPE "OMIT_DECLTYPE", #endif -#ifdef SQLITE_OMIT_DEPRECATED +#if SQLITE_OMIT_DEPRECATED "OMIT_DEPRECATED", #endif -#ifdef SQLITE_OMIT_DISKIO +#if SQLITE_OMIT_DISKIO "OMIT_DISKIO", #endif -#ifdef SQLITE_OMIT_EXPLAIN +#if SQLITE_OMIT_EXPLAIN "OMIT_EXPLAIN", #endif -#ifdef SQLITE_OMIT_FLAG_PRAGMAS +#if SQLITE_OMIT_FLAG_PRAGMAS "OMIT_FLAG_PRAGMAS", #endif -#ifdef SQLITE_OMIT_FLOATING_POINT +#if SQLITE_OMIT_FLOATING_POINT "OMIT_FLOATING_POINT", #endif -#ifdef SQLITE_OMIT_FOREIGN_KEY +#if SQLITE_OMIT_FOREIGN_KEY "OMIT_FOREIGN_KEY", #endif -#ifdef SQLITE_OMIT_GET_TABLE +#if SQLITE_OMIT_GET_TABLE "OMIT_GET_TABLE", #endif -#ifdef SQLITE_OMIT_INCRBLOB +#if SQLITE_OMIT_INCRBLOB "OMIT_INCRBLOB", #endif -#ifdef SQLITE_OMIT_INTEGRITY_CHECK +#if SQLITE_OMIT_INTEGRITY_CHECK "OMIT_INTEGRITY_CHECK", #endif -#ifdef SQLITE_OMIT_LIKE_OPTIMIZATION +#if SQLITE_OMIT_LIKE_OPTIMIZATION "OMIT_LIKE_OPTIMIZATION", #endif -#ifdef SQLITE_OMIT_LOAD_EXTENSION +#if SQLITE_OMIT_LOAD_EXTENSION "OMIT_LOAD_EXTENSION", #endif -#ifdef SQLITE_OMIT_LOCALTIME +#if SQLITE_OMIT_LOCALTIME "OMIT_LOCALTIME", #endif -#ifdef SQLITE_OMIT_LOOKASIDE +#if SQLITE_OMIT_LOOKASIDE "OMIT_LOOKASIDE", #endif -#ifdef SQLITE_OMIT_MEMORYDB +#if SQLITE_OMIT_MEMORYDB "OMIT_MEMORYDB", #endif -#ifdef SQLITE_OMIT_OR_OPTIMIZATION +#if SQLITE_OMIT_OR_OPTIMIZATION "OMIT_OR_OPTIMIZATION", #endif -#ifdef SQLITE_OMIT_PAGER_PRAGMAS +#if SQLITE_OMIT_PAGER_PRAGMAS "OMIT_PAGER_PRAGMAS", #endif -#ifdef SQLITE_OMIT_PRAGMA +#if SQLITE_OMIT_PRAGMA "OMIT_PRAGMA", #endif -#ifdef SQLITE_OMIT_PROGRESS_CALLBACK +#if SQLITE_OMIT_PROGRESS_CALLBACK "OMIT_PROGRESS_CALLBACK", #endif -#ifdef SQLITE_OMIT_QUICKBALANCE +#if SQLITE_OMIT_QUICKBALANCE "OMIT_QUICKBALANCE", #endif -#ifdef SQLITE_OMIT_REINDEX +#if SQLITE_OMIT_REINDEX "OMIT_REINDEX", #endif -#ifdef SQLITE_OMIT_SCHEMA_PRAGMAS +#if SQLITE_OMIT_SCHEMA_PRAGMAS "OMIT_SCHEMA_PRAGMAS", #endif -#ifdef SQLITE_OMIT_SCHEMA_VERSION_PRAGMAS +#if SQLITE_OMIT_SCHEMA_VERSION_PRAGMAS "OMIT_SCHEMA_VERSION_PRAGMAS", #endif -#ifdef SQLITE_OMIT_SHARED_CACHE +#if SQLITE_OMIT_SHARED_CACHE "OMIT_SHARED_CACHE", #endif -#ifdef SQLITE_OMIT_SUBQUERY +#if SQLITE_OMIT_SUBQUERY "OMIT_SUBQUERY", #endif -#ifdef SQLITE_OMIT_TCL_VARIABLE +#if SQLITE_OMIT_TCL_VARIABLE "OMIT_TCL_VARIABLE", #endif -#ifdef SQLITE_OMIT_TEMPDB +#if SQLITE_OMIT_TEMPDB "OMIT_TEMPDB", #endif -#ifdef SQLITE_OMIT_TRACE +#if SQLITE_OMIT_TRACE "OMIT_TRACE", #endif -#ifdef SQLITE_OMIT_TRIGGER +#if SQLITE_OMIT_TRIGGER "OMIT_TRIGGER", #endif -#ifdef SQLITE_OMIT_TRUNCATE_OPTIMIZATION +#if SQLITE_OMIT_TRUNCATE_OPTIMIZATION "OMIT_TRUNCATE_OPTIMIZATION", #endif -#ifdef SQLITE_OMIT_UTF16 +#if SQLITE_OMIT_UTF16 "OMIT_UTF16", #endif -#ifdef SQLITE_OMIT_VACUUM +#if SQLITE_OMIT_VACUUM "OMIT_VACUUM", #endif -#ifdef SQLITE_OMIT_VIEW +#if SQLITE_OMIT_VIEW "OMIT_VIEW", #endif -#ifdef SQLITE_OMIT_VIRTUALTABLE +#if SQLITE_OMIT_VIRTUALTABLE "OMIT_VIRTUALTABLE", #endif -#ifdef SQLITE_OMIT_WAL +#if SQLITE_OMIT_WAL "OMIT_WAL", #endif -#ifdef SQLITE_OMIT_WSD +#if SQLITE_OMIT_WSD "OMIT_WSD", #endif -#ifdef SQLITE_OMIT_XFER_OPT +#if SQLITE_OMIT_XFER_OPT "OMIT_XFER_OPT", #endif -#ifdef SQLITE_PERFORMANCE_TRACE +#if SQLITE_PERFORMANCE_TRACE "PERFORMANCE_TRACE", #endif -#ifdef SQLITE_PROXY_DEBUG +#if SQLITE_PROXY_DEBUG "PROXY_DEBUG", #endif -#ifdef SQLITE_RTREE_INT_ONLY +#if SQLITE_RTREE_INT_ONLY "RTREE_INT_ONLY", #endif -#ifdef SQLITE_SECURE_DELETE +#if SQLITE_SECURE_DELETE "SECURE_DELETE", #endif -#ifdef SQLITE_SMALL_STACK +#if SQLITE_SMALL_STACK "SMALL_STACK", #endif -#ifdef SQLITE_SOUNDEX +#if SQLITE_SOUNDEX "SOUNDEX", #endif -#ifdef SQLITE_SYSTEM_MALLOC +#if SQLITE_SYSTEM_MALLOC "SYSTEM_MALLOC", #endif -#ifdef SQLITE_TCL +#if SQLITE_TCL "TCL", #endif #if defined(SQLITE_TEMP_STORE) && !defined(SQLITE_TEMP_STORE_xc) "TEMP_STORE=" CTIMEOPT_VAL(SQLITE_TEMP_STORE), #endif -#ifdef SQLITE_TEST +#if SQLITE_TEST "TEST", #endif #if defined(SQLITE_THREADSAFE) "THREADSAFE=" CTIMEOPT_VAL(SQLITE_THREADSAFE), #endif -#ifdef SQLITE_USE_ALLOCA +#if SQLITE_USE_ALLOCA "USE_ALLOCA", #endif -#ifdef SQLITE_WIN32_MALLOC +#if SQLITE_USER_AUTHENTICATION + "USER_AUTHENTICATION", +#endif +#if SQLITE_WIN32_MALLOC "WIN32_MALLOC", #endif -#ifdef SQLITE_ZERO_MALLOC +#if SQLITE_ZERO_MALLOC "ZERO_MALLOC" #endif }; @@ -13756,8 +15527,15 @@ static const char * const azCompileOpt[] = { ** The name can optionally begin with "SQLITE_" but the "SQLITE_" prefix ** is not required for a match. */ -SQLITE_API int sqlite3_compileoption_used(const char *zOptName){ +SQLITE_API int SQLITE_STDCALL sqlite3_compileoption_used(const char *zOptName){ int i, n; + +#if SQLITE_ENABLE_API_ARMOR + if( zOptName==0 ){ + (void)SQLITE_MISUSE_BKPT; + return 0; + } +#endif if( sqlite3StrNICmp(zOptName, "SQLITE_", 7)==0 ) zOptName += 7; n = sqlite3Strlen30(zOptName); @@ -13765,7 +15543,7 @@ SQLITE_API int sqlite3_compileoption_used(const char *zOptName){ ** linear search is adequate. No need for a binary search. */ for(i=0; i=0 && NaDb[] (or -1) */ + u8 nullRow; /* True if pointing to a row with no data */ + u8 deferredMoveto; /* A call to sqlite3BtreeMoveto() is needed */ + u8 isTable; /* True for rowid tables. False for indexes */ +#ifdef SQLITE_DEBUG + u8 seekOp; /* Most recent seek operation on this cursor */ +#endif + Bool isEphemeral:1; /* True for an ephemeral table */ + Bool useRandomRowid:1;/* Generate new record numbers semi-randomly */ + Bool isOrdered:1; /* True if the underlying table is BTREE_UNORDERED */ + Pgno pgnoRoot; /* Root page of the open btree cursor */ + i16 nField; /* Number of fields in the header */ + u16 nHdrParsed; /* Number of header fields parsed so far */ + union { + BtCursor *pCursor; /* CURTYPE_BTREE. Btree cursor */ + sqlite3_vtab_cursor *pVCur; /* CURTYPE_VTAB. Vtab cursor */ + int pseudoTableReg; /* CURTYPE_PSEUDO. Reg holding content. */ + VdbeSorter *pSorter; /* CURTYPE_SORTER. Sorter object */ + } uc; Btree *pBt; /* Separate file holding temporary table */ KeyInfo *pKeyInfo; /* Info about index keys needed by index cursors */ int seekResult; /* Result of previous sqlite3BtreeMoveto() */ - int pseudoTableReg; /* Register holding pseudotable content. */ - i16 nField; /* Number of fields in the header */ - u16 nHdrParsed; /* Number of header fields parsed so far */ - i8 iDb; /* Index of cursor database in db->aDb[] (or -1) */ - u8 nullRow; /* True if pointing to a row with no data */ - u8 rowidIsValid; /* True if lastRowid is valid */ - u8 deferredMoveto; /* A call to sqlite3BtreeMoveto() is needed */ - Bool isEphemeral:1; /* True for an ephemeral table */ - Bool useRandomRowid:1;/* Generate new record numbers semi-randomly */ - Bool isTable:1; /* True if a table requiring integer keys */ - Bool isOrdered:1; /* True if the underlying table is BTREE_UNORDERED */ - sqlite3_vtab_cursor *pVtabCursor; /* The cursor for a virtual table */ i64 seqCount; /* Sequence counter */ i64 movetoTarget; /* Argument to the deferred sqlite3BtreeMoveto() */ - i64 lastRowid; /* Rowid being deleted by OP_Delete */ - VdbeSorter *pSorter; /* Sorter object for OP_SorterOpen cursors */ +#ifdef SQLITE_ENABLE_COLUMN_USED_MASK + u64 maskUsed; /* Mask of columns used by this cursor */ +#endif /* Cached information about the header for the data record that the ** cursor is currently pointing to. Only valid if cacheStatus matches @@ -13903,6 +15704,7 @@ struct VdbeCursor { u32 szRow; /* Byte available in aRow */ u32 iHdrOffset; /* Offset to next unparsed byte of the header */ const u8 *aRow; /* Data for the current row, if all on one page */ + u32 *aOffset; /* Pointer to aType[nField] */ u32 aType[1]; /* Type values for all entries in the record */ /* 2*nField extra array elements allocated for aType[], beyond the one ** static element declared in the structure. nField total array slots for @@ -13936,6 +15738,7 @@ struct VdbeFrame { Vdbe *v; /* VM this frame belongs to */ VdbeFrame *pParent; /* Parent of this frame, or NULL if parent is main */ Op *aOp; /* Program instructions for parent frame */ + i64 *anExec; /* Event counters from parent frame */ Mem *aMem; /* Array of memory cells for parent frame */ u8 *aOnceFlag; /* Array of OP_Once flags for parent frame */ VdbeCursor **apCsr; /* Array of Vdbe cursors for parent frame */ @@ -13948,7 +15751,8 @@ struct VdbeFrame { int nOnceFlag; /* Number of entries in aOnceFlag */ int nChildMem; /* Number of memory cells for child frame */ int nChildCsr; /* Number of cursors for child frame */ - int nChange; /* Statement changes (Vdbe.nChanges) */ + int nChange; /* Statement changes (Vdbe.nChange) */ + int nDbChange; /* Value of db->nChange */ }; #define VdbeFrameMem(p) ((Mem *)&((u8 *)p)[ROUND8(sizeof(VdbeFrame))]) @@ -13964,27 +15768,37 @@ struct VdbeFrame { ** integer etc.) of the same value. */ struct Mem { - sqlite3 *db; /* The associated database connection */ - char *z; /* String or BLOB value */ - double r; /* Real value */ - union { + union MemValue { + double r; /* Real value used when MEM_Real is set in flags */ i64 i; /* Integer value used when MEM_Int is set in flags */ int nZero; /* Used when bit MEM_Zero is set in flags */ FuncDef *pDef; /* Used only when flags==MEM_Agg */ RowSet *pRowSet; /* Used only when flags==MEM_RowSet */ VdbeFrame *pFrame; /* Used when flags==MEM_Frame */ } u; - int n; /* Number of characters in string value, excluding '\0' */ u16 flags; /* Some combination of MEM_Null, MEM_Str, MEM_Dyn, etc. */ u8 enc; /* SQLITE_UTF8, SQLITE_UTF16BE, SQLITE_UTF16LE */ + u8 eSubtype; /* Subtype for this value */ + int n; /* Number of characters in string value, excluding '\0' */ + char *z; /* String or BLOB value */ + /* ShallowCopy only needs to copy the information above */ + char *zMalloc; /* Space to hold MEM_Str or MEM_Blob if szMalloc>0 */ + int szMalloc; /* Size of the zMalloc allocation */ + u32 uTemp; /* Transient storage for serial_type in OP_MakeRecord */ + sqlite3 *db; /* The associated database connection */ + void (*xDel)(void*);/* Destructor for Mem.z - only valid if MEM_Dyn */ #ifdef SQLITE_DEBUG Mem *pScopyFrom; /* This Mem is a shallow copy of pScopyFrom */ void *pFiller; /* So that sizeof(Mem) is a multiple of 8 */ #endif - void (*xDel)(void *); /* If not null, call this function to delete Mem.z */ - char *zMalloc; /* Dynamic buffer allocated by sqlite3_malloc() */ }; +/* +** Size of struct Mem not including the Mem.zMalloc member or anything that +** follows. +*/ +#define MEMCELLSIZE offsetof(Mem,zMalloc) + /* One or more of the following flags are set to indicate the validOK ** representations of the value stored in the Mem struct. ** @@ -14041,7 +15855,7 @@ struct Mem { #endif /* -** Each auxilliary data pointer stored by a user defined function +** Each auxiliary data pointer stored by a user defined function ** implementation calling sqlite3_set_auxdata() is stored in an instance ** of this structure. All such structures associated with a single VM ** are stored in a linked list headed at Vdbe.pAuxData. All are destroyed @@ -14056,7 +15870,7 @@ struct AuxData { }; /* -** The "context" argument for a installable function. A pointer to an +** The "context" argument for an installable function. A pointer to an ** instance of this structure is the first argument to the routines used ** implement the SQL functions. ** @@ -14069,15 +15883,16 @@ struct AuxData { ** (Mem) which are only defined there. */ struct sqlite3_context { - FuncDef *pFunc; /* Pointer to function information. MUST BE FIRST */ - Mem s; /* The return value is stored here */ - Mem *pMem; /* Memory cell used to store aggregate context */ - CollSeq *pColl; /* Collating sequence */ - Vdbe *pVdbe; /* The VM that owns this context */ - int iOp; /* Instruction number of OP_Function */ - int isError; /* Error code returned by the function. */ - u8 skipFlag; /* Skip skip accumulator loading if true */ - u8 fErrorOrAux; /* isError!=0 or pVdbe->pAuxData modified */ + Mem *pOut; /* The return value is stored here */ + FuncDef *pFunc; /* Pointer to function information */ + Mem *pMem; /* Memory cell used to store aggregate context */ + Vdbe *pVdbe; /* The VM that owns this context */ + int iOp; /* Instruction number of OP_Function */ + int isError; /* Error code returned by the function. */ + u8 skipFlag; /* Skip accumulator loading if true */ + u8 fErrorOrAux; /* isError!=0 or pVdbe->pAuxData modified */ + u8 argc; /* Number of arguments */ + sqlite3_value *argv[1]; /* Argument set */ }; /* @@ -14097,20 +15912,22 @@ struct Explain { */ typedef unsigned bft; /* Bit Field Type */ +typedef struct ScanStatus ScanStatus; +struct ScanStatus { + int addrExplain; /* OP_Explain for loop */ + int addrLoop; /* Address of "loops" counter */ + int addrVisit; /* Address of "rows visited" counter */ + int iSelectID; /* The "Select-ID" for this loop */ + LogEst nEst; /* Estimated output rows per loop */ + char *zName; /* Name of table or index */ +}; + /* ** An instance of the virtual machine. This structure contains the complete ** state of the virtual machine. ** ** The "sqlite3_stmt" structure pointer that is returned by sqlite3_prepare() ** is really a pointer to an instance of this structure. -** -** The Vdbe.inVtabMethod variable is set to non-zero for the duration of -** any virtual table method invocations made by the vdbe program. It is -** set to 2 for xDestroy method calls and 1 for all other methods. This -** variable is used for two purposes: to allow xDestroy methods to execute -** "DROP TABLE" statements and to prevent some nasty side effects of -** malloc failure when SQLite is invoked recursively by a virtual table -** method function. */ struct Vdbe { sqlite3 *db; /* The database connection that owns this statement */ @@ -14134,11 +15951,13 @@ struct Vdbe { u32 cacheCtr; /* VdbeCursor row cache generation counter */ int pc; /* The program counter */ int rc; /* Value to return */ +#ifdef SQLITE_DEBUG + int rcApp; /* errcode set by sqlite3_result_error_code() */ +#endif u16 nResColumn; /* Number of columns in one row of the result set */ u8 errorAction; /* Recovery action to do in case of an error */ u8 minWriteFileFormat; /* Minimum file format for writable database files */ bft explain:2; /* True if EXPLAIN present on SQL command */ - bft inVtabMethod:2; /* See comments above */ bft changeCntOn:1; /* True to update the change-counter */ bft expired:1; /* True if the VM needs to be recompiled */ bft runOnlyOnce:1; /* Automatically expire on reset */ @@ -14161,10 +15980,6 @@ struct Vdbe { i64 nStmtDefImmCons; /* Number of def. imm constraints when stmt started */ char *zSql; /* Text of the SQL statement that generated this */ void *pFree; /* Free this when deleting the vdbe */ -#ifdef SQLITE_ENABLE_TREE_EXPLAIN - Explain *pExplain; /* The explainer */ - char *zExplain; /* Explanation of data structures */ -#endif VdbeFrame *pFrame; /* Parent frame */ VdbeFrame *pDelFrame; /* List of frame objects to free on VM reset */ int nFrame; /* Number of frames in pFrame list */ @@ -14173,6 +15988,11 @@ struct Vdbe { int nOnceFlag; /* Size of array aOnceFlag[] */ u8 *aOnceFlag; /* Flags for OP_Once */ AuxData *pAuxData; /* Linked list of auxdata allocations */ +#ifdef SQLITE_ENABLE_STMT_SCANSTATUS + i64 *anExec; /* Number of times each op has been executed */ + int nScan; /* Entries in aScan[] */ + ScanStatus *aScan; /* Scan definitions for sqlite3_stmt_scanstatus() */ +#endif }; /* @@ -14186,22 +16006,24 @@ struct Vdbe { /* ** Function prototypes */ +SQLITE_PRIVATE void sqlite3VdbeError(Vdbe*, const char *, ...); SQLITE_PRIVATE void sqlite3VdbeFreeCursor(Vdbe *, VdbeCursor*); void sqliteVdbePopStack(Vdbe*,int); SQLITE_PRIVATE int sqlite3VdbeCursorMoveto(VdbeCursor*); +SQLITE_PRIVATE int sqlite3VdbeCursorRestore(VdbeCursor*); #if defined(SQLITE_DEBUG) || defined(VDBE_PROFILE) SQLITE_PRIVATE void sqlite3VdbePrintOp(FILE*, int, Op*); #endif SQLITE_PRIVATE u32 sqlite3VdbeSerialTypeLen(u32); -SQLITE_PRIVATE u32 sqlite3VdbeSerialType(Mem*, int); +SQLITE_PRIVATE u8 sqlite3VdbeOneByteSerialTypeLen(u8); +SQLITE_PRIVATE u32 sqlite3VdbeSerialType(Mem*, int, u32*); SQLITE_PRIVATE u32 sqlite3VdbeSerialPut(unsigned char*, Mem*, u32); SQLITE_PRIVATE u32 sqlite3VdbeSerialGet(const unsigned char*, u32, Mem*); SQLITE_PRIVATE void sqlite3VdbeDeleteAuxData(Vdbe*, int, int); int sqlite2BtreeKeyCompare(BtCursor *, const void *, int, int, int *); -SQLITE_PRIVATE int sqlite3VdbeIdxKeyCompare(VdbeCursor*,UnpackedRecord*,int*); -SQLITE_PRIVATE int sqlite3VdbeIdxRowid(sqlite3*, BtCursor *, i64 *); -SQLITE_PRIVATE int sqlite3MemCompare(const Mem*, const Mem*, const CollSeq*); +SQLITE_PRIVATE int sqlite3VdbeIdxKeyCompare(sqlite3*,VdbeCursor*,UnpackedRecord*,int*); +SQLITE_PRIVATE int sqlite3VdbeIdxRowid(sqlite3*, BtCursor*, i64*); SQLITE_PRIVATE int sqlite3VdbeExec(Vdbe*); SQLITE_PRIVATE int sqlite3VdbeList(Vdbe*); SQLITE_PRIVATE int sqlite3VdbeHalt(Vdbe*); @@ -14218,39 +16040,39 @@ SQLITE_PRIVATE void sqlite3VdbeMemSetInt64(Mem*, i64); #else SQLITE_PRIVATE void sqlite3VdbeMemSetDouble(Mem*, double); #endif +SQLITE_PRIVATE void sqlite3VdbeMemInit(Mem*,sqlite3*,u16); SQLITE_PRIVATE void sqlite3VdbeMemSetNull(Mem*); SQLITE_PRIVATE void sqlite3VdbeMemSetZeroBlob(Mem*,int); SQLITE_PRIVATE void sqlite3VdbeMemSetRowSet(Mem*); SQLITE_PRIVATE int sqlite3VdbeMemMakeWriteable(Mem*); -SQLITE_PRIVATE int sqlite3VdbeMemStringify(Mem*, int); +SQLITE_PRIVATE int sqlite3VdbeMemStringify(Mem*, u8, u8); SQLITE_PRIVATE i64 sqlite3VdbeIntValue(Mem*); SQLITE_PRIVATE int sqlite3VdbeMemIntegerify(Mem*); SQLITE_PRIVATE double sqlite3VdbeRealValue(Mem*); SQLITE_PRIVATE void sqlite3VdbeIntegerAffinity(Mem*); SQLITE_PRIVATE int sqlite3VdbeMemRealify(Mem*); SQLITE_PRIVATE int sqlite3VdbeMemNumerify(Mem*); +SQLITE_PRIVATE void sqlite3VdbeMemCast(Mem*,u8,u8); SQLITE_PRIVATE int sqlite3VdbeMemFromBtree(BtCursor*,u32,u32,int,Mem*); SQLITE_PRIVATE void sqlite3VdbeMemRelease(Mem *p); -SQLITE_PRIVATE void sqlite3VdbeMemReleaseExternal(Mem *p); #define VdbeMemDynamic(X) \ (((X)->flags&(MEM_Agg|MEM_Dyn|MEM_RowSet|MEM_Frame))!=0) -#define VdbeMemRelease(X) \ - if( VdbeMemDynamic(X) ) sqlite3VdbeMemReleaseExternal(X); SQLITE_PRIVATE int sqlite3VdbeMemFinalize(Mem*, FuncDef*); SQLITE_PRIVATE const char *sqlite3OpcodeName(int); SQLITE_PRIVATE int sqlite3VdbeMemGrow(Mem *pMem, int n, int preserve); +SQLITE_PRIVATE int sqlite3VdbeMemClearAndResize(Mem *pMem, int n); SQLITE_PRIVATE int sqlite3VdbeCloseStatement(Vdbe *, int); SQLITE_PRIVATE void sqlite3VdbeFrameDelete(VdbeFrame*); SQLITE_PRIVATE int sqlite3VdbeFrameRestore(VdbeFrame *); SQLITE_PRIVATE int sqlite3VdbeTransferError(Vdbe *p); -SQLITE_PRIVATE int sqlite3VdbeSorterInit(sqlite3 *, VdbeCursor *); +SQLITE_PRIVATE int sqlite3VdbeSorterInit(sqlite3 *, int, VdbeCursor *); SQLITE_PRIVATE void sqlite3VdbeSorterReset(sqlite3 *, VdbeSorter *); SQLITE_PRIVATE void sqlite3VdbeSorterClose(sqlite3 *, VdbeCursor *); SQLITE_PRIVATE int sqlite3VdbeSorterRowkey(const VdbeCursor *, Mem *); SQLITE_PRIVATE int sqlite3VdbeSorterNext(sqlite3 *, const VdbeCursor *, int *); -SQLITE_PRIVATE int sqlite3VdbeSorterRewind(sqlite3 *, const VdbeCursor *, int *); -SQLITE_PRIVATE int sqlite3VdbeSorterWrite(sqlite3 *, const VdbeCursor *, Mem *); +SQLITE_PRIVATE int sqlite3VdbeSorterRewind(const VdbeCursor *, int *); +SQLITE_PRIVATE int sqlite3VdbeSorterWrite(const VdbeCursor *, Mem *); SQLITE_PRIVATE int sqlite3VdbeSorterCompare(const VdbeCursor *, Mem *, int, int *); #if !defined(SQLITE_OMIT_SHARED_CACHE) && SQLITE_THREADSAFE>0 @@ -14295,12 +16117,34 @@ SQLITE_PRIVATE int sqlite3VdbeMemExpandBlob(Mem *); /* ** Variables in which to record status information. */ +#if SQLITE_PTRSIZE>4 +typedef sqlite3_int64 sqlite3StatValueType; +#else +typedef u32 sqlite3StatValueType; +#endif typedef struct sqlite3StatType sqlite3StatType; static SQLITE_WSD struct sqlite3StatType { - int nowValue[10]; /* Current value */ - int mxValue[10]; /* Maximum value */ + sqlite3StatValueType nowValue[10]; /* Current value */ + sqlite3StatValueType mxValue[10]; /* Maximum value */ } sqlite3Stat = { {0,}, {0,} }; +/* +** Elements of sqlite3Stat[] are protected by either the memory allocator +** mutex, or by the pcache1 mutex. The following array determines which. +*/ +static const char statMutex[] = { + 0, /* SQLITE_STATUS_MEMORY_USED */ + 1, /* SQLITE_STATUS_PAGECACHE_USED */ + 1, /* SQLITE_STATUS_PAGECACHE_OVERFLOW */ + 0, /* SQLITE_STATUS_SCRATCH_USED */ + 0, /* SQLITE_STATUS_SCRATCH_OVERFLOW */ + 0, /* SQLITE_STATUS_MALLOC_SIZE */ + 0, /* SQLITE_STATUS_PARSER_STACK */ + 1, /* SQLITE_STATUS_PAGECACHE_SIZE */ + 0, /* SQLITE_STATUS_SCRATCH_SIZE */ + 0, /* SQLITE_STATUS_MALLOC_COUNT */ +}; + /* The "wsdStat" macro will resolve to the status information ** state vector. If writable static data is unsupported on the target, @@ -14317,63 +16161,118 @@ static SQLITE_WSD struct sqlite3StatType { #endif /* -** Return the current value of a status parameter. +** Return the current value of a status parameter. The caller must +** be holding the appropriate mutex. */ -SQLITE_PRIVATE int sqlite3StatusValue(int op){ +SQLITE_PRIVATE sqlite3_int64 sqlite3StatusValue(int op){ wsdStatInit; assert( op>=0 && op=0 && op=0 && op=0 && opwsdStat.mxValue[op] ){ wsdStat.mxValue[op] = wsdStat.nowValue[op]; } } +SQLITE_PRIVATE void sqlite3StatusDown(int op, int N){ + wsdStatInit; + assert( N>=0 ); + assert( op>=0 && op=0 && op=0 ); + newValue = (sqlite3StatValueType)X; assert( op>=0 && opwsdStat.mxValue[op] ){ - wsdStat.mxValue[op] = wsdStat.nowValue[op]; + assert( op>=0 && opwsdStat.mxValue[op] ){ + wsdStat.mxValue[op] = newValue; } } /* ** Query status information. -** -** This implementation assumes that reading or writing an aligned -** 32-bit integer is an atomic operation. If that assumption is not true, -** then this routine is not threadsafe. */ -SQLITE_API int sqlite3_status(int op, int *pCurrent, int *pHighwater, int resetFlag){ +SQLITE_API int SQLITE_STDCALL sqlite3_status64( + int op, + sqlite3_int64 *pCurrent, + sqlite3_int64 *pHighwater, + int resetFlag +){ + sqlite3_mutex *pMutex; wsdStatInit; if( op<0 || op>=ArraySize(wsdStat.nowValue) ){ return SQLITE_MISUSE_BKPT; } +#ifdef SQLITE_ENABLE_API_ARMOR + if( pCurrent==0 || pHighwater==0 ) return SQLITE_MISUSE_BKPT; +#endif + pMutex = statMutex[op] ? sqlite3Pcache1Mutex() : sqlite3MallocMutex(); + sqlite3_mutex_enter(pMutex); *pCurrent = wsdStat.nowValue[op]; *pHighwater = wsdStat.mxValue[op]; if( resetFlag ){ wsdStat.mxValue[op] = wsdStat.nowValue[op]; } + sqlite3_mutex_leave(pMutex); + (void)pMutex; /* Prevent warning when SQLITE_THREADSAFE=0 */ return SQLITE_OK; } +SQLITE_API int SQLITE_STDCALL sqlite3_status(int op, int *pCurrent, int *pHighwater, int resetFlag){ + sqlite3_int64 iCur, iHwtr; + int rc; +#ifdef SQLITE_ENABLE_API_ARMOR + if( pCurrent==0 || pHighwater==0 ) return SQLITE_MISUSE_BKPT; +#endif + rc = sqlite3_status64(op, &iCur, &iHwtr, resetFlag); + if( rc==0 ){ + *pCurrent = (int)iCur; + *pHighwater = (int)iHwtr; + } + return rc; +} /* ** Query status information for a single database connection */ -SQLITE_API int sqlite3_db_status( +SQLITE_API int SQLITE_STDCALL sqlite3_db_status( sqlite3 *db, /* The database connection whose status is desired */ int op, /* Status verb */ int *pCurrent, /* Write current value here */ @@ -14381,6 +16280,11 @@ SQLITE_API int sqlite3_db_status( int resetFlag /* Reset high-water mark if true */ ){ int rc = SQLITE_OK; /* Return code */ +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) || pCurrent==0|| pHighwater==0 ){ + return SQLITE_MISUSE_BKPT; + } +#endif sqlite3_mutex_enter(db->mutex); switch( op ){ case SQLITE_DBSTATUS_LOOKASIDE_USED: { @@ -14452,10 +16356,10 @@ SQLITE_API int sqlite3_db_status( + pSchema->idxHash.count + pSchema->fkeyHash.count ); - nByte += sqlite3MallocSize(pSchema->tblHash.ht); - nByte += sqlite3MallocSize(pSchema->trigHash.ht); - nByte += sqlite3MallocSize(pSchema->idxHash.ht); - nByte += sqlite3MallocSize(pSchema->fkeyHash.ht); + nByte += sqlite3_msize(pSchema->tblHash.ht); + nByte += sqlite3_msize(pSchema->trigHash.ht); + nByte += sqlite3_msize(pSchema->idxHash.ht); + nByte += sqlite3_msize(pSchema->fkeyHash.ht); for(p=sqliteHashFirst(&pSchema->trigHash); p; p=sqliteHashNext(p)){ sqlite3DeleteTrigger(db, (Trigger*)sqliteHashData(p)); @@ -14489,7 +16393,7 @@ SQLITE_API int sqlite3_db_status( } db->pnBytesFreed = 0; - *pHighwater = 0; + *pHighwater = 0; /* IMP: R-64479-57858 */ *pCurrent = nByte; break; @@ -14514,7 +16418,9 @@ SQLITE_API int sqlite3_db_status( sqlite3PagerCacheStat(pPager, op, resetFlag, &nRet); } } - *pHighwater = 0; + *pHighwater = 0; /* IMP: R-42420-56072 */ + /* IMP: R-54100-20147 */ + /* IMP: R-29431-39229 */ *pCurrent = nRet; break; } @@ -14524,7 +16430,7 @@ SQLITE_API int sqlite3_db_status( ** have been satisfied. The *pHighwater is always set to zero. */ case SQLITE_DBSTATUS_DEFERRED_FKS: { - *pHighwater = 0; + *pHighwater = 0; /* IMP: R-11967-56545 */ *pCurrent = db->nDeferredImmCons>0 || db->nDeferredCons>0; break; } @@ -14557,7 +16463,7 @@ SQLITE_API int sqlite3_db_status( ** sqlite3RegisterDateTimeFunctions() found at the bottom of the file. ** All other code has file scope. ** -** SQLite processes all times and dates as Julian Day numbers. The +** SQLite processes all times and dates as julian day numbers. The ** dates and times are stored as the number of days since noon ** in Greenwich on November 24, 4714 B.C. according to the Gregorian ** calendar system. @@ -14565,14 +16471,14 @@ SQLITE_API int sqlite3_db_status( ** 1970-01-01 00:00:00 is JD 2440587.5 ** 2000-01-01 00:00:00 is JD 2451544.5 ** -** This implemention requires years to be expressed as a 4-digit number +** This implementation requires years to be expressed as a 4-digit number ** which means that only dates between 0000-01-01 and 9999-12-31 can ** be represented, even though julian day numbers allow a much wider ** range of dates. ** ** The Gregorian calendar system is used for all dates and times, ** even those that predate the Gregorian calendar. Historians usually -** use the Julian calendar for dates prior to 1582-10-15 and for some +** use the julian calendar for dates prior to 1582-10-15 and for some ** dates afterwards, depending on locale. Beware of this difference. ** ** The conversion algorithms are implemented based on descriptions @@ -14584,6 +16490,7 @@ SQLITE_API int sqlite3_db_status( ** Willmann-Bell, Inc ** Richmond, Virginia (USA) */ +/* #include "sqliteInt.h" */ /* #include */ /* #include */ #include @@ -14605,6 +16512,7 @@ struct DateTime { char validHMS; /* True (1) if h,m,s are valid */ char validJD; /* True (1) if iJD is valid */ char validTZ; /* True (1) if tz is valid */ + char tzSet; /* Timezone was set explicitly */ }; @@ -14698,6 +16606,7 @@ static int parseTimezone(const char *zDate, DateTime *p){ p->tz = sgn*(nMn + nHr*60); zulu_time: while( sqlite3Isspace(*zDate) ){ zDate++; } + p->tzSet = 1; return *zDate!=0; } @@ -14844,7 +16753,7 @@ static int setDateTimeToCurrent(sqlite3_context *context, DateTime *p){ } /* -** Attempt to parse the given string into a Julian Day Number. Return +** Attempt to parse the given string into a julian day number. Return ** the number of errors. ** ** The following are acceptable forms for the input string: @@ -14895,7 +16804,7 @@ static void computeYMD(DateTime *p){ A = Z + 1 + A - (A/4); B = A + 1524; C = (int)((B - 122.1)/365.25); - D = (36525*C)/100; + D = (36525*(C&32767))/100; E = (int)((B-D)/30.6001); X1 = (int)(30.6001*E); p->D = B - D - X1; @@ -14952,8 +16861,9 @@ static void clearYMD_HMS_TZ(DateTime *p){ ** already, check for an MSVC build environment that provides ** localtime_s(). */ -#if !defined(HAVE_LOCALTIME_R) && !defined(HAVE_LOCALTIME_S) && \ - defined(_MSC_VER) && defined(_CRT_INSECURE_DEPRECATE) +#if !HAVE_LOCALTIME_R && !HAVE_LOCALTIME_S \ + && defined(_MSC_VER) && defined(_CRT_INSECURE_DEPRECATE) +#undef HAVE_LOCALTIME_S #define HAVE_LOCALTIME_S 1 #endif @@ -14973,8 +16883,7 @@ static void clearYMD_HMS_TZ(DateTime *p){ */ static int osLocaltime(time_t *t, struct tm *pTm){ int rc; -#if (!defined(HAVE_LOCALTIME_R) || !HAVE_LOCALTIME_R) \ - && (!defined(HAVE_LOCALTIME_S) || !HAVE_LOCALTIME_S) +#if !HAVE_LOCALTIME_R && !HAVE_LOCALTIME_S struct tm *pX; #if SQLITE_THREADSAFE>0 sqlite3_mutex *mutex = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MASTER); @@ -14991,7 +16900,7 @@ static int osLocaltime(time_t *t, struct tm *pTm){ #ifndef SQLITE_OMIT_BUILTIN_TEST if( sqlite3GlobalConfig.bLocaltimeFault ) return 1; #endif -#if defined(HAVE_LOCALTIME_R) && HAVE_LOCALTIME_R +#if HAVE_LOCALTIME_R rc = localtime_r(t, pTm)==0; #else rc = localtime_s(pTm, t); @@ -15130,13 +17039,18 @@ static int parseModifier(sqlite3_context *pCtx, const char *zMod, DateTime *p){ } #ifndef SQLITE_OMIT_LOCALTIME else if( strcmp(z, "utc")==0 ){ - sqlite3_int64 c1; - computeJD(p); - c1 = localtimeOffset(p, pCtx, &rc); - if( rc==SQLITE_OK ){ - p->iJD -= c1; - clearYMD_HMS_TZ(p); - p->iJD += c1 - localtimeOffset(p, pCtx, &rc); + if( p->tzSet==0 ){ + sqlite3_int64 c1; + computeJD(p); + c1 = localtimeOffset(p, pCtx, &rc); + if( rc==SQLITE_OK ){ + p->iJD -= c1; + clearYMD_HMS_TZ(p); + p->iJD += c1 - localtimeOffset(p, pCtx, &rc); + } + p->tzSet = 1; + }else{ + rc = SQLITE_OK; } } #endif @@ -15415,7 +17329,7 @@ static void dateFunc( ** %f ** fractional seconds SS.SSS ** %H hour 00-24 ** %j day of year 000-366 -** %J ** Julian day number +** %J ** julian day number ** %m month 01-12 ** %M minute 00-59 ** %s seconds since 1970-01-01 @@ -15435,8 +17349,10 @@ static void strftimeFunc( size_t i,j; char *z; sqlite3 *db; - const char *zFmt = (const char*)sqlite3_value_text(argv[0]); + const char *zFmt; char zBuf[100]; + if( argc==0 ) return; + zFmt = (const char*)sqlite3_value_text(argv[0]); if( zFmt==0 || isDate(context, argc-1, argv+1, &x) ) return; db = sqlite3_context_db_handle(context); for(i=0, n=1; zFmt[i]; i++, n++){ @@ -15630,7 +17546,7 @@ static void currentTimeFunc( iT = sqlite3StmtCurrentTime(context); if( iT<=0 ) return; t = iT/1000 - 10000*(sqlite3_int64)21086676; -#ifdef HAVE_GMTIME_R +#if HAVE_GMTIME_R pTm = gmtime_r(&t, &sNow); #else sqlite3_mutex_enter(sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MASTER)); @@ -15653,14 +17569,14 @@ static void currentTimeFunc( SQLITE_PRIVATE void sqlite3RegisterDateTimeFunctions(void){ static SQLITE_WSD FuncDef aDateTimeFuncs[] = { #ifndef SQLITE_OMIT_DATETIME_FUNCS - FUNCTION(julianday, -1, 0, 0, juliandayFunc ), - FUNCTION(date, -1, 0, 0, dateFunc ), - FUNCTION(time, -1, 0, 0, timeFunc ), - FUNCTION(datetime, -1, 0, 0, datetimeFunc ), - FUNCTION(strftime, -1, 0, 0, strftimeFunc ), - FUNCTION(current_time, 0, 0, 0, ctimeFunc ), - FUNCTION(current_timestamp, 0, 0, 0, ctimestampFunc), - FUNCTION(current_date, 0, 0, 0, cdateFunc ), + DFUNCTION(julianday, -1, 0, 0, juliandayFunc ), + DFUNCTION(date, -1, 0, 0, dateFunc ), + DFUNCTION(time, -1, 0, 0, timeFunc ), + DFUNCTION(datetime, -1, 0, 0, datetimeFunc ), + DFUNCTION(strftime, -1, 0, 0, strftimeFunc ), + DFUNCTION(current_time, 0, 0, 0, ctimeFunc ), + DFUNCTION(current_timestamp, 0, 0, 0, ctimestampFunc), + DFUNCTION(current_date, 0, 0, 0, cdateFunc ), #else STR_FUNCTION(current_time, 0, "%H:%M:%S", 0, currentTimeFunc), STR_FUNCTION(current_date, 0, "%Y-%m-%d", 0, currentTimeFunc), @@ -15694,6 +17610,7 @@ SQLITE_PRIVATE void sqlite3RegisterDateTimeFunctions(void){ ** architectures. */ #define _SQLITE_OS_C_ 1 +/* #include "sqliteInt.h" */ #undef _SQLITE_OS_C_ /* @@ -15988,7 +17905,7 @@ static sqlite3_vfs * SQLITE_WSD vfsList = 0; ** Locate a VFS by name. If no name is given, simply return the ** first VFS on the list. */ -SQLITE_API sqlite3_vfs *sqlite3_vfs_find(const char *zVfs){ +SQLITE_API sqlite3_vfs *SQLITE_STDCALL sqlite3_vfs_find(const char *zVfs){ sqlite3_vfs *pVfs = 0; #if SQLITE_THREADSAFE sqlite3_mutex *mutex; @@ -16034,12 +17951,16 @@ static void vfsUnlink(sqlite3_vfs *pVfs){ ** VFS multiple times. The new VFS becomes the default if makeDflt is ** true. */ -SQLITE_API int sqlite3_vfs_register(sqlite3_vfs *pVfs, int makeDflt){ +SQLITE_API int SQLITE_STDCALL sqlite3_vfs_register(sqlite3_vfs *pVfs, int makeDflt){ MUTEX_LOGIC(sqlite3_mutex *mutex;) #ifndef SQLITE_OMIT_AUTOINIT int rc = sqlite3_initialize(); if( rc ) return rc; #endif +#ifdef SQLITE_ENABLE_API_ARMOR + if( pVfs==0 ) return SQLITE_MISUSE_BKPT; +#endif + MUTEX_LOGIC( mutex = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MASTER); ) sqlite3_mutex_enter(mutex); vfsUnlink(pVfs); @@ -16058,7 +17979,7 @@ SQLITE_API int sqlite3_vfs_register(sqlite3_vfs *pVfs, int makeDflt){ /* ** Unregister a VFS so that it is no longer accessible. */ -SQLITE_API int sqlite3_vfs_unregister(sqlite3_vfs *pVfs){ +SQLITE_API int SQLITE_STDCALL sqlite3_vfs_unregister(sqlite3_vfs *pVfs){ #if SQLITE_THREADSAFE sqlite3_mutex *mutex = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MASTER); #endif @@ -16096,6 +18017,7 @@ SQLITE_API int sqlite3_vfs_unregister(sqlite3_vfs *pVfs){ ** during a hash table resize is a benign fault. */ +/* #include "sqliteInt.h" */ #ifndef SQLITE_OMIT_BUILTIN_TEST @@ -16177,6 +18099,7 @@ SQLITE_PRIVATE void sqlite3EndBenignMalloc(void){ ** are merely placeholders. Real drivers must be substituted using ** sqlite3_config() before SQLite will operate. */ +/* #include "sqliteInt.h" */ /* ** This version of the memory allocator is the default. It is @@ -16263,6 +18186,7 @@ SQLITE_PRIVATE void sqlite3MemSetDefault(void){ ** be necessary when compiling for Delphi, ** for example. */ +/* #include "sqliteInt.h" */ /* ** This version of the memory allocator is the default. It is @@ -16300,9 +18224,9 @@ static malloc_zone_t* _sqliteZone_; ** The malloc.h header file is needed for malloc_usable_size() function ** on some systems (e.g. Linux). */ -#if defined(HAVE_MALLOC_H) && defined(HAVE_MALLOC_USABLE_SIZE) -# define SQLITE_USE_MALLOC_H -# define SQLITE_USE_MALLOC_USABLE_SIZE +#if HAVE_MALLOC_H && HAVE_MALLOC_USABLE_SIZE +# define SQLITE_USE_MALLOC_H 1 +# define SQLITE_USE_MALLOC_USABLE_SIZE 1 /* ** The MSVCRT has malloc_usable_size(), but it is called _msize(). The ** use of _msize() is automatic, but can be disabled by compiling with @@ -16393,10 +18317,11 @@ static void sqlite3MemFree(void *pPrior){ */ static int sqlite3MemSize(void *pPrior){ #ifdef SQLITE_MALLOCSIZE - return pPrior ? (int)SQLITE_MALLOCSIZE(pPrior) : 0; + assert( pPrior!=0 ); + return (int)SQLITE_MALLOCSIZE(pPrior); #else sqlite3_int64 *p; - if( pPrior==0 ) return 0; + assert( pPrior!=0 ); p = (sqlite3_int64*)pPrior; p--; return (int)p[0]; @@ -16409,7 +18334,7 @@ static int sqlite3MemSize(void *pPrior){ ** ** For this low-level interface, we know that pPrior!=0. Cases where ** pPrior==0 while have been intercepted by higher-level routine and -** redirected to xMalloc. Similarly, we know that nByte>0 becauses +** redirected to xMalloc. Similarly, we know that nByte>0 because ** cases where nByte<=0 will have been intercepted by higher-level ** routines and redirected to xFree. */ @@ -16538,6 +18463,7 @@ SQLITE_PRIVATE void sqlite3MemSetDefault(void){ ** This file contains implementations of the low-level memory allocation ** routines specified in the sqlite3_mem_methods object. */ +/* #include "sqliteInt.h" */ /* ** This version of the memory allocator is used only if the @@ -16912,7 +18838,7 @@ SQLITE_PRIVATE void sqlite3MemdebugSetType(void *p, u8 eType){ ** This routine is designed for use within an assert() statement, to ** verify the type of an allocation. For example: ** -** assert( sqlite3MemdebugHasType(p, MEMTYPE_DB) ); +** assert( sqlite3MemdebugHasType(p, MEMTYPE_HEAP) ); */ SQLITE_PRIVATE int sqlite3MemdebugHasType(void *p, u8 eType){ int rc = 1; @@ -16934,7 +18860,7 @@ SQLITE_PRIVATE int sqlite3MemdebugHasType(void *p, u8 eType){ ** This routine is designed for use within an assert() statement, to ** verify the type of an allocation. For example: ** -** assert( sqlite3MemdebugNoType(p, MEMTYPE_DB) ); +** assert( sqlite3MemdebugNoType(p, MEMTYPE_LOOKASIDE) ); */ SQLITE_PRIVATE int sqlite3MemdebugNoType(void *p, u8 eType){ int rc = 1; @@ -17072,6 +18998,7 @@ SQLITE_PRIVATE int sqlite3MemdebugMallocCount(){ ** This version of the memory allocation subsystem is included ** in the build only if SQLITE_ENABLE_MEMSYS3 is defined. */ +/* #include "sqliteInt.h" */ /* ** This version of the memory allocator is only built into the library @@ -17524,7 +19451,7 @@ static void memsys3FreeUnsafe(void *pOld){ */ static int memsys3Size(void *p){ Mem3Block *pBlock; - if( p==0 ) return 0; + assert( p!=0 ); pBlock = (Mem3Block*)p; assert( (pBlock[-1].u.hdr.size4x&1)!=0 ); return (pBlock[-1].u.hdr.size4x&~3)*2 - 4; @@ -17763,10 +19690,10 @@ SQLITE_PRIVATE const sqlite3_mem_methods *sqlite3MemGetMemsys3(void){ ** ** This memory allocator uses the following algorithm: ** -** 1. All memory allocations sizes are rounded up to a power of 2. +** 1. All memory allocation sizes are rounded up to a power of 2. ** ** 2. If two adjacent free blocks are the halves of a larger block, -** then the two blocks are coalesed into the single larger block. +** then the two blocks are coalesced into the single larger block. ** ** 3. New memory is allocated from the first available free block. ** @@ -17786,6 +19713,7 @@ SQLITE_PRIVATE const sqlite3_mem_methods *sqlite3MemGetMemsys3(void){ ** The sqlite3_status() logic tracks the maximum values of n and M so ** that an application can, at any time, verify this constraint. */ +/* #include "sqliteInt.h" */ /* ** This version of the memory allocator is used only when @@ -17854,7 +19782,7 @@ static SQLITE_WSD struct Mem5Global { /* ** Lists of free blocks. aiFreelist[0] is a list of free blocks of ** size mem5.szAtom. aiFreelist[1] holds blocks of size szAtom*2. - ** and so forth. + ** aiFreelist[2] holds free blocks of size szAtom*4. And so forth. */ int aiFreelist[LOGMAX+1]; @@ -17920,9 +19848,7 @@ static void memsys5Link(int i, int iLogsize){ } /* -** If the STATIC_MEM mutex is not already held, obtain it now. The mutex -** will already be held (obtained by code in malloc.c) if -** sqlite3GlobalConfig.bMemStat is true. +** Obtain or release the mutex needed to access global data structures. */ static void memsys5Enter(void){ sqlite3_mutex_enter(mem5.mutex); @@ -17932,17 +19858,15 @@ static void memsys5Leave(void){ } /* -** Return the size of an outstanding allocation, in bytes. The -** size returned omits the 8-byte header overhead. This only -** works for chunks that are currently checked out. +** Return the size of an outstanding allocation, in bytes. +** This only works for chunks that are currently checked out. */ static int memsys5Size(void *p){ - int iSize = 0; - if( p ){ - int i = (int)(((u8 *)p-mem5.zPool)/mem5.szAtom); - assert( i>=0 && i=0 && imem5.maxRequest ){ + /* Abort if the requested allocation size is larger than the largest + ** power of two that we can represent using 32-bit signed integers. */ + if( nByte > 0x40000000 ) return 0; mem5.maxRequest = nByte; } - /* Abort if the requested allocation size is larger than the largest - ** power of two that we can represent using 32-bit signed integers. - */ - if( nByte > 0x40000000 ){ - return 0; - } - /* Round nByte up to the next valid power of two */ - for(iFullSz=mem5.szAtom, iLogsize=0; iFullSzxMutexFree, &pFrom->xMutexFree, - sizeof(*pTo) - offsetof(sqlite3_mutex_methods, xMutexFree)); + pTo->xMutexInit = pFrom->xMutexInit; + pTo->xMutexEnd = pFrom->xMutexEnd; + pTo->xMutexFree = pFrom->xMutexFree; + pTo->xMutexEnter = pFrom->xMutexEnter; + pTo->xMutexTry = pFrom->xMutexTry; + pTo->xMutexLeave = pFrom->xMutexLeave; + pTo->xMutexHeld = pFrom->xMutexHeld; + pTo->xMutexNotheld = pFrom->xMutexNotheld; + sqlite3MemoryBarrier(); pTo->xMutexAlloc = pFrom->xMutexAlloc; } + assert( sqlite3GlobalConfig.mutex.xMutexInit ); rc = sqlite3GlobalConfig.mutex.xMutexInit(); #ifdef SQLITE_DEBUG @@ -18394,10 +20320,12 @@ SQLITE_PRIVATE int sqlite3MutexEnd(void){ /* ** Retrieve a pointer to a static mutex or allocate a new dynamic one. */ -SQLITE_API sqlite3_mutex *sqlite3_mutex_alloc(int id){ +SQLITE_API sqlite3_mutex *SQLITE_STDCALL sqlite3_mutex_alloc(int id){ #ifndef SQLITE_OMIT_AUTOINIT - if( sqlite3_initialize() ) return 0; + if( id<=SQLITE_MUTEX_RECURSIVE && sqlite3_initialize() ) return 0; + if( id>SQLITE_MUTEX_RECURSIVE && sqlite3MutexInit() ) return 0; #endif + assert( sqlite3GlobalConfig.mutex.xMutexAlloc ); return sqlite3GlobalConfig.mutex.xMutexAlloc(id); } @@ -18406,14 +20334,16 @@ SQLITE_PRIVATE sqlite3_mutex *sqlite3MutexAlloc(int id){ return 0; } assert( GLOBAL(int, mutexIsInit) ); + assert( sqlite3GlobalConfig.mutex.xMutexAlloc ); return sqlite3GlobalConfig.mutex.xMutexAlloc(id); } /* ** Free a dynamic mutex. */ -SQLITE_API void sqlite3_mutex_free(sqlite3_mutex *p){ +SQLITE_API void SQLITE_STDCALL sqlite3_mutex_free(sqlite3_mutex *p){ if( p ){ + assert( sqlite3GlobalConfig.mutex.xMutexFree ); sqlite3GlobalConfig.mutex.xMutexFree(p); } } @@ -18422,8 +20352,9 @@ SQLITE_API void sqlite3_mutex_free(sqlite3_mutex *p){ ** Obtain the mutex p. If some other thread already has the mutex, block ** until it can be obtained. */ -SQLITE_API void sqlite3_mutex_enter(sqlite3_mutex *p){ +SQLITE_API void SQLITE_STDCALL sqlite3_mutex_enter(sqlite3_mutex *p){ if( p ){ + assert( sqlite3GlobalConfig.mutex.xMutexEnter ); sqlite3GlobalConfig.mutex.xMutexEnter(p); } } @@ -18432,9 +20363,10 @@ SQLITE_API void sqlite3_mutex_enter(sqlite3_mutex *p){ ** Obtain the mutex p. If successful, return SQLITE_OK. Otherwise, if another ** thread holds the mutex and it cannot be obtained, return SQLITE_BUSY. */ -SQLITE_API int sqlite3_mutex_try(sqlite3_mutex *p){ +SQLITE_API int SQLITE_STDCALL sqlite3_mutex_try(sqlite3_mutex *p){ int rc = SQLITE_OK; if( p ){ + assert( sqlite3GlobalConfig.mutex.xMutexTry ); return sqlite3GlobalConfig.mutex.xMutexTry(p); } return rc; @@ -18446,8 +20378,9 @@ SQLITE_API int sqlite3_mutex_try(sqlite3_mutex *p){ ** is not currently entered. If a NULL pointer is passed as an argument ** this function is a no-op. */ -SQLITE_API void sqlite3_mutex_leave(sqlite3_mutex *p){ +SQLITE_API void SQLITE_STDCALL sqlite3_mutex_leave(sqlite3_mutex *p){ if( p ){ + assert( sqlite3GlobalConfig.mutex.xMutexLeave ); sqlite3GlobalConfig.mutex.xMutexLeave(p); } } @@ -18457,10 +20390,12 @@ SQLITE_API void sqlite3_mutex_leave(sqlite3_mutex *p){ ** The sqlite3_mutex_held() and sqlite3_mutex_notheld() routine are ** intended for use inside assert() statements. */ -SQLITE_API int sqlite3_mutex_held(sqlite3_mutex *p){ +SQLITE_API int SQLITE_STDCALL sqlite3_mutex_held(sqlite3_mutex *p){ + assert( p==0 || sqlite3GlobalConfig.mutex.xMutexHeld ); return p==0 || sqlite3GlobalConfig.mutex.xMutexHeld(p); } -SQLITE_API int sqlite3_mutex_notheld(sqlite3_mutex *p){ +SQLITE_API int SQLITE_STDCALL sqlite3_mutex_notheld(sqlite3_mutex *p){ + assert( p==0 || sqlite3GlobalConfig.mutex.xMutexNotheld ); return p==0 || sqlite3GlobalConfig.mutex.xMutexNotheld(p); } #endif @@ -18496,6 +20431,7 @@ SQLITE_API int sqlite3_mutex_notheld(sqlite3_mutex *p){ ** that does error checking on mutexes to make sure they are being ** called correctly. */ +/* #include "sqliteInt.h" */ #ifndef SQLITE_MUTEX_OMIT @@ -18577,7 +20513,7 @@ static int debugMutexEnd(void){ return SQLITE_OK; } ** that means that a mutex could not be allocated. */ static sqlite3_mutex *debugMutexAlloc(int id){ - static sqlite3_debug_mutex aStatic[6]; + static sqlite3_debug_mutex aStatic[SQLITE_MUTEX_STATIC_VFS3 - 1]; sqlite3_debug_mutex *pNew = 0; switch( id ){ case SQLITE_MUTEX_FAST: @@ -18590,8 +20526,12 @@ static sqlite3_mutex *debugMutexAlloc(int id){ break; } default: { - assert( id-2 >= 0 ); - assert( id-2 < (int)(sizeof(aStatic)/sizeof(aStatic[0])) ); +#ifdef SQLITE_ENABLE_API_ARMOR + if( id-2<0 || id-2>=ArraySize(aStatic) ){ + (void)SQLITE_MISUSE_BKPT; + return 0; + } +#endif pNew = &aStatic[id-2]; pNew->id = id; break; @@ -18606,8 +20546,13 @@ static sqlite3_mutex *debugMutexAlloc(int id){ static void debugMutexFree(sqlite3_mutex *pX){ sqlite3_debug_mutex *p = (sqlite3_debug_mutex*)pX; assert( p->cnt==0 ); - assert( p->id==SQLITE_MUTEX_FAST || p->id==SQLITE_MUTEX_RECURSIVE ); - sqlite3_free(p); + if( p->id==SQLITE_MUTEX_RECURSIVE || p->id==SQLITE_MUTEX_FAST ){ + sqlite3_free(p); + }else{ +#ifdef SQLITE_ENABLE_API_ARMOR + (void)SQLITE_MISUSE_BKPT; +#endif + } } /* @@ -18690,6 +20635,7 @@ SQLITE_PRIVATE sqlite3_mutex_methods const *sqlite3DefaultMutex(void){ ************************************************************************* ** This file contains the C functions that implement mutexes for pthreads */ +/* #include "sqliteInt.h" */ /* ** The code in this file is only used if we are compiling threadsafe @@ -18718,15 +20664,19 @@ SQLITE_PRIVATE sqlite3_mutex_methods const *sqlite3DefaultMutex(void){ */ struct sqlite3_mutex { pthread_mutex_t mutex; /* Mutex controlling the lock */ -#if SQLITE_MUTEX_NREF +#if SQLITE_MUTEX_NREF || defined(SQLITE_ENABLE_API_ARMOR) int id; /* Mutex type */ +#endif +#if SQLITE_MUTEX_NREF volatile int nRef; /* Number of entrances */ volatile pthread_t owner; /* Thread that is within this mutex */ int trace; /* True to trace changes */ #endif }; #if SQLITE_MUTEX_NREF -#define SQLITE3_MUTEX_INITIALIZER { PTHREAD_MUTEX_INITIALIZER, 0, 0, (pthread_t)0, 0 } +#define SQLITE3_MUTEX_INITIALIZER {PTHREAD_MUTEX_INITIALIZER,0,0,(pthread_t)0,0} +#elif defined(SQLITE_ENABLE_API_ARMOR) +#define SQLITE3_MUTEX_INITIALIZER { PTHREAD_MUTEX_INITIALIZER, 0 } #else #define SQLITE3_MUTEX_INITIALIZER { PTHREAD_MUTEX_INITIALIZER } #endif @@ -18756,6 +20706,19 @@ static int pthreadMutexNotheld(sqlite3_mutex *p){ } #endif +/* +** Try to provide a memory barrier operation, needed for initialization +** and also for the implementation of xShmBarrier in the VFS in cases +** where SQLite is compiled without mutexes. +*/ +SQLITE_PRIVATE void sqlite3MemoryBarrier(void){ +#if defined(SQLITE_MEMORY_BARRIER) + SQLITE_MEMORY_BARRIER; +#elif defined(__GNUC__) && GCC_VERSION>=4001000 + __sync_synchronize(); +#endif +} + /* ** Initialize and deinitialize the mutex subsystem. */ @@ -18774,10 +20737,16 @@ static int pthreadMutexEnd(void){ return SQLITE_OK; } **
  • SQLITE_MUTEX_RECURSIVE **
  • SQLITE_MUTEX_STATIC_MASTER **
  • SQLITE_MUTEX_STATIC_MEM -**
  • SQLITE_MUTEX_STATIC_MEM2 +**
  • SQLITE_MUTEX_STATIC_OPEN **
  • SQLITE_MUTEX_STATIC_PRNG **
  • SQLITE_MUTEX_STATIC_LRU **
  • SQLITE_MUTEX_STATIC_PMEM +**
  • SQLITE_MUTEX_STATIC_APP1 +**
  • SQLITE_MUTEX_STATIC_APP2 +**
  • SQLITE_MUTEX_STATIC_APP3 +**
  • SQLITE_MUTEX_STATIC_VFS1 +**
  • SQLITE_MUTEX_STATIC_VFS2 +**
  • SQLITE_MUTEX_STATIC_VFS3 ** ** ** The first two constants cause sqlite3_mutex_alloc() to create @@ -18806,6 +20775,12 @@ static int pthreadMutexEnd(void){ return SQLITE_OK; } */ static sqlite3_mutex *pthreadMutexAlloc(int iType){ static sqlite3_mutex staticMutexes[] = { + SQLITE3_MUTEX_INITIALIZER, + SQLITE3_MUTEX_INITIALIZER, + SQLITE3_MUTEX_INITIALIZER, + SQLITE3_MUTEX_INITIALIZER, + SQLITE3_MUTEX_INITIALIZER, + SQLITE3_MUTEX_INITIALIZER, SQLITE3_MUTEX_INITIALIZER, SQLITE3_MUTEX_INITIALIZER, SQLITE3_MUTEX_INITIALIZER, @@ -18829,9 +20804,6 @@ static sqlite3_mutex *pthreadMutexAlloc(int iType){ pthread_mutexattr_settype(&recursiveAttr, PTHREAD_MUTEX_RECURSIVE); pthread_mutex_init(&p->mutex, &recursiveAttr); pthread_mutexattr_destroy(&recursiveAttr); -#endif -#if SQLITE_MUTEX_NREF - p->id = iType; #endif } break; @@ -18839,23 +20811,24 @@ static sqlite3_mutex *pthreadMutexAlloc(int iType){ case SQLITE_MUTEX_FAST: { p = sqlite3MallocZero( sizeof(*p) ); if( p ){ -#if SQLITE_MUTEX_NREF - p->id = iType; -#endif pthread_mutex_init(&p->mutex, 0); } break; } default: { - assert( iType-2 >= 0 ); - assert( iType-2 < ArraySize(staticMutexes) ); - p = &staticMutexes[iType-2]; -#if SQLITE_MUTEX_NREF - p->id = iType; +#ifdef SQLITE_ENABLE_API_ARMOR + if( iType-2<0 || iType-2>=ArraySize(staticMutexes) ){ + (void)SQLITE_MISUSE_BKPT; + return 0; + } #endif + p = &staticMutexes[iType-2]; break; } } +#if SQLITE_MUTEX_NREF || defined(SQLITE_ENABLE_API_ARMOR) + if( p ) p->id = iType; +#endif return p; } @@ -18867,9 +20840,18 @@ static sqlite3_mutex *pthreadMutexAlloc(int iType){ */ static void pthreadMutexFree(sqlite3_mutex *p){ assert( p->nRef==0 ); - assert( p->id==SQLITE_MUTEX_FAST || p->id==SQLITE_MUTEX_RECURSIVE ); - pthread_mutex_destroy(&p->mutex); - sqlite3_free(p); +#if SQLITE_ENABLE_API_ARMOR + if( p->id==SQLITE_MUTEX_FAST || p->id==SQLITE_MUTEX_RECURSIVE ) +#endif + { + pthread_mutex_destroy(&p->mutex); + sqlite3_free(p); + } +#ifdef SQLITE_ENABLE_API_ARMOR + else{ + (void)SQLITE_MISUSE_BKPT; + } +#endif } /* @@ -19041,10 +21023,214 @@ SQLITE_PRIVATE sqlite3_mutex_methods const *sqlite3DefaultMutex(void){ ** May you share freely, never taking more than you give. ** ************************************************************************* -** This file contains the C functions that implement mutexes for win32 +** This file contains the C functions that implement mutexes for Win32. */ +/* #include "sqliteInt.h" */ #if SQLITE_OS_WIN +/* +** Include code that is common to all os_*.c files +*/ +/************** Include os_common.h in the middle of mutex_w32.c *************/ +/************** Begin file os_common.h ***************************************/ +/* +** 2004 May 22 +** +** The author disclaims copyright to this source code. In place of +** a legal notice, here is a blessing: +** +** May you do good and not evil. +** May you find forgiveness for yourself and forgive others. +** May you share freely, never taking more than you give. +** +****************************************************************************** +** +** This file contains macros and a little bit of code that is common to +** all of the platform-specific files (os_*.c) and is #included into those +** files. +** +** This file should be #included by the os_*.c files only. It is not a +** general purpose header file. +*/ +#ifndef _OS_COMMON_H_ +#define _OS_COMMON_H_ + +/* +** At least two bugs have slipped in because we changed the MEMORY_DEBUG +** macro to SQLITE_DEBUG and some older makefiles have not yet made the +** switch. The following code should catch this problem at compile-time. +*/ +#ifdef MEMORY_DEBUG +# error "The MEMORY_DEBUG macro is obsolete. Use SQLITE_DEBUG instead." +#endif + +/* +** Macros for performance tracing. Normally turned off. Only works +** on i486 hardware. +*/ +#ifdef SQLITE_PERFORMANCE_TRACE + +/* +** hwtime.h contains inline assembler code for implementing +** high-performance timing routines. +*/ +/************** Include hwtime.h in the middle of os_common.h ****************/ +/************** Begin file hwtime.h ******************************************/ +/* +** 2008 May 27 +** +** The author disclaims copyright to this source code. In place of +** a legal notice, here is a blessing: +** +** May you do good and not evil. +** May you find forgiveness for yourself and forgive others. +** May you share freely, never taking more than you give. +** +****************************************************************************** +** +** This file contains inline asm code for retrieving "high-performance" +** counters for x86 class CPUs. +*/ +#ifndef _HWTIME_H_ +#define _HWTIME_H_ + +/* +** The following routine only works on pentium-class (or newer) processors. +** It uses the RDTSC opcode to read the cycle count value out of the +** processor and returns that value. This can be used for high-res +** profiling. +*/ +#if (defined(__GNUC__) || defined(_MSC_VER)) && \ + (defined(i386) || defined(__i386__) || defined(_M_IX86)) + + #if defined(__GNUC__) + + __inline__ sqlite_uint64 sqlite3Hwtime(void){ + unsigned int lo, hi; + __asm__ __volatile__ ("rdtsc" : "=a" (lo), "=d" (hi)); + return (sqlite_uint64)hi << 32 | lo; + } + + #elif defined(_MSC_VER) + + __declspec(naked) __inline sqlite_uint64 __cdecl sqlite3Hwtime(void){ + __asm { + rdtsc + ret ; return value at EDX:EAX + } + } + + #endif + +#elif (defined(__GNUC__) && defined(__x86_64__)) + + __inline__ sqlite_uint64 sqlite3Hwtime(void){ + unsigned long val; + __asm__ __volatile__ ("rdtsc" : "=A" (val)); + return val; + } + +#elif (defined(__GNUC__) && defined(__ppc__)) + + __inline__ sqlite_uint64 sqlite3Hwtime(void){ + unsigned long long retval; + unsigned long junk; + __asm__ __volatile__ ("\n\ + 1: mftbu %1\n\ + mftb %L0\n\ + mftbu %0\n\ + cmpw %0,%1\n\ + bne 1b" + : "=r" (retval), "=r" (junk)); + return retval; + } + +#else + + #error Need implementation of sqlite3Hwtime() for your platform. + + /* + ** To compile without implementing sqlite3Hwtime() for your platform, + ** you can remove the above #error and use the following + ** stub function. You will lose timing support for many + ** of the debugging and testing utilities, but it should at + ** least compile and run. + */ +SQLITE_PRIVATE sqlite_uint64 sqlite3Hwtime(void){ return ((sqlite_uint64)0); } + +#endif + +#endif /* !defined(_HWTIME_H_) */ + +/************** End of hwtime.h **********************************************/ +/************** Continuing where we left off in os_common.h ******************/ + +static sqlite_uint64 g_start; +static sqlite_uint64 g_elapsed; +#define TIMER_START g_start=sqlite3Hwtime() +#define TIMER_END g_elapsed=sqlite3Hwtime()-g_start +#define TIMER_ELAPSED g_elapsed +#else +#define TIMER_START +#define TIMER_END +#define TIMER_ELAPSED ((sqlite_uint64)0) +#endif + +/* +** If we compile with the SQLITE_TEST macro set, then the following block +** of code will give us the ability to simulate a disk I/O error. This +** is used for testing the I/O recovery logic. +*/ +#ifdef SQLITE_TEST +SQLITE_API int sqlite3_io_error_hit = 0; /* Total number of I/O Errors */ +SQLITE_API int sqlite3_io_error_hardhit = 0; /* Number of non-benign errors */ +SQLITE_API int sqlite3_io_error_pending = 0; /* Count down to first I/O error */ +SQLITE_API int sqlite3_io_error_persist = 0; /* True if I/O errors persist */ +SQLITE_API int sqlite3_io_error_benign = 0; /* True if errors are benign */ +SQLITE_API int sqlite3_diskfull_pending = 0; +SQLITE_API int sqlite3_diskfull = 0; +#define SimulateIOErrorBenign(X) sqlite3_io_error_benign=(X) +#define SimulateIOError(CODE) \ + if( (sqlite3_io_error_persist && sqlite3_io_error_hit) \ + || sqlite3_io_error_pending-- == 1 ) \ + { local_ioerr(); CODE; } +static void local_ioerr(){ + IOTRACE(("IOERR\n")); + sqlite3_io_error_hit++; + if( !sqlite3_io_error_benign ) sqlite3_io_error_hardhit++; +} +#define SimulateDiskfullError(CODE) \ + if( sqlite3_diskfull_pending ){ \ + if( sqlite3_diskfull_pending == 1 ){ \ + local_ioerr(); \ + sqlite3_diskfull = 1; \ + sqlite3_io_error_hit = 1; \ + CODE; \ + }else{ \ + sqlite3_diskfull_pending--; \ + } \ + } +#else +#define SimulateIOErrorBenign(X) +#define SimulateIOError(A) +#define SimulateDiskfullError(A) +#endif + +/* +** When testing, keep a count of the number of open files. +*/ +#ifdef SQLITE_TEST +SQLITE_API int sqlite3_open_file_count = 0; +#define OpenCounter(X) sqlite3_open_file_count+=(X) +#else +#define OpenCounter(X) +#endif + +#endif /* !defined(_OS_COMMON_H_) */ + +/************** End of os_common.h *******************************************/ +/************** Continuing where we left off in mutex_w32.c ******************/ + /* ** Include the header file for the Windows VFS. */ @@ -19116,6 +21302,27 @@ SQLITE_PRIVATE sqlite3_mutex_methods const *sqlite3DefaultMutex(void){ # define SQLITE_OS_WINRT 0 #endif +/* +** For WinCE, some API function parameters do not appear to be declared as +** volatile. +*/ +#if SQLITE_OS_WINCE +# define SQLITE_WIN32_VOLATILE +#else +# define SQLITE_WIN32_VOLATILE volatile +#endif + +/* +** For some Windows sub-platforms, the _beginthreadex() / _endthreadex() +** functions are not available (e.g. those not using MSVC, Cygwin, etc). +*/ +#if SQLITE_OS_WIN && !SQLITE_OS_WINCE && !SQLITE_OS_WINRT && \ + SQLITE_THREADSAFE>0 && !defined(__CYGWIN__) +# define SQLITE_OS_WIN_THREADS 1 +#else +# define SQLITE_OS_WIN_THREADS 0 +#endif + #endif /* _OS_WIN_H_ */ /************** End of os_win.h **********************************************/ @@ -19124,7 +21331,7 @@ SQLITE_PRIVATE sqlite3_mutex_methods const *sqlite3DefaultMutex(void){ /* ** The code in this file is only used if we are compiling multithreaded -** on a win32 system. +** on a Win32 system. */ #ifdef SQLITE_MUTEX_W32 @@ -19137,48 +21344,22 @@ struct sqlite3_mutex { #ifdef SQLITE_DEBUG volatile int nRef; /* Number of enterances */ volatile DWORD owner; /* Thread holding this mutex */ - int trace; /* True to trace changes */ + volatile int trace; /* True to trace changes */ #endif }; -#define SQLITE_W32_MUTEX_INITIALIZER { 0 } -#ifdef SQLITE_DEBUG -#define SQLITE3_MUTEX_INITIALIZER { SQLITE_W32_MUTEX_INITIALIZER, 0, 0L, (DWORD)0, 0 } -#else -#define SQLITE3_MUTEX_INITIALIZER { SQLITE_W32_MUTEX_INITIALIZER, 0 } -#endif /* -** Return true (non-zero) if we are running under WinNT, Win2K, WinXP, -** or WinCE. Return false (zero) for Win95, Win98, or WinME. -** -** Here is an interesting observation: Win95, Win98, and WinME lack -** the LockFileEx() API. But we can still statically link against that -** API as long as we don't call it win running Win95/98/ME. A call to -** this routine is used to determine if the host is Win95/98/ME or -** WinNT/2K/XP so that we will know whether or not we can safely call -** the LockFileEx() API. -** -** mutexIsNT() is only used for the TryEnterCriticalSection() API call, -** which is only available if your application was compiled with -** _WIN32_WINNT defined to a value >= 0x0400. Currently, the only -** call to TryEnterCriticalSection() is #ifdef'ed out, so #ifdef -** this out as well. +** These are the initializer values used when declaring a "static" mutex +** on Win32. It should be noted that all mutexes require initialization +** on the Win32 platform. */ -#if 0 -#if SQLITE_OS_WINCE || SQLITE_OS_WINRT -# define mutexIsNT() (1) +#define SQLITE_W32_MUTEX_INITIALIZER { 0 } + +#ifdef SQLITE_DEBUG +#define SQLITE3_MUTEX_INITIALIZER { SQLITE_W32_MUTEX_INITIALIZER, 0, \ + 0L, (DWORD)0, 0 } #else - static int mutexIsNT(void){ - static int osType = 0; - if( osType==0 ){ - OSVERSIONINFO sInfo; - sInfo.dwOSVersionInfoSize = sizeof(sInfo); - GetVersionEx(&sInfo); - osType = sInfo.dwPlatformId==VER_PLATFORM_WIN32_NT ? 2 : 1; - } - return osType==2; - } -#endif /* SQLITE_OS_WINCE || SQLITE_OS_WINRT */ +#define SQLITE3_MUTEX_INITIALIZER { SQLITE_W32_MUTEX_INITIALIZER, 0 } #endif #ifdef SQLITE_DEBUG @@ -19189,20 +21370,45 @@ struct sqlite3_mutex { static int winMutexHeld(sqlite3_mutex *p){ return p->nRef!=0 && p->owner==GetCurrentThreadId(); } + static int winMutexNotheld2(sqlite3_mutex *p, DWORD tid){ return p->nRef==0 || p->owner!=tid; } + static int winMutexNotheld(sqlite3_mutex *p){ - DWORD tid = GetCurrentThreadId(); + DWORD tid = GetCurrentThreadId(); return winMutexNotheld2(p, tid); } #endif +/* +** Try to provide a memory barrier operation, needed for initialization +** and also for the xShmBarrier method of the VFS in cases when SQLite is +** compiled without mutexes (SQLITE_THREADSAFE=0). +*/ +SQLITE_PRIVATE void sqlite3MemoryBarrier(void){ +#if defined(SQLITE_MEMORY_BARRIER) + SQLITE_MEMORY_BARRIER; +#elif defined(__GNUC__) + __sync_synchronize(); +#elif !defined(SQLITE_DISABLE_INTRINSIC) && \ + defined(_MSC_VER) && _MSC_VER>=1300 + _ReadWriteBarrier(); +#elif defined(MemoryBarrier) + MemoryBarrier(); +#endif +} /* ** Initialize and deinitialize the mutex subsystem. */ -static sqlite3_mutex winMutex_staticMutexes[6] = { +static sqlite3_mutex winMutex_staticMutexes[] = { + SQLITE3_MUTEX_INITIALIZER, + SQLITE3_MUTEX_INITIALIZER, + SQLITE3_MUTEX_INITIALIZER, + SQLITE3_MUTEX_INITIALIZER, + SQLITE3_MUTEX_INITIALIZER, + SQLITE3_MUTEX_INITIALIZER, SQLITE3_MUTEX_INITIALIZER, SQLITE3_MUTEX_INITIALIZER, SQLITE3_MUTEX_INITIALIZER, @@ -19210,17 +21416,20 @@ static sqlite3_mutex winMutex_staticMutexes[6] = { SQLITE3_MUTEX_INITIALIZER, SQLITE3_MUTEX_INITIALIZER }; + static int winMutex_isInit = 0; -/* As winMutexInit() and winMutexEnd() are called as part -** of the sqlite3_initialize and sqlite3_shutdown() -** processing, the "interlocked" magic is probably not -** strictly necessary. +static int winMutex_isNt = -1; /* <0 means "need to query" */ + +/* As the winMutexInit() and winMutexEnd() functions are called as part +** of the sqlite3_initialize() and sqlite3_shutdown() processing, the +** "interlocked" magic used here is probably not strictly necessary. */ -static LONG winMutex_lock = 0; +static LONG SQLITE_WIN32_VOLATILE winMutex_lock = 0; -SQLITE_API void sqlite3_win32_sleep(DWORD milliseconds); /* os_win.c */ +SQLITE_API int SQLITE_STDCALL sqlite3_win32_is_nt(void); /* os_win.c */ +SQLITE_API void SQLITE_STDCALL sqlite3_win32_sleep(DWORD milliseconds); /* os_win.c */ -static int winMutexInit(void){ +static int winMutexInit(void){ /* The first to increment to 1 does actual initialization */ if( InterlockedCompareExchange(&winMutex_lock, 1, 0)==0 ){ int i; @@ -19233,16 +21442,17 @@ static int winMutexInit(void){ } winMutex_isInit = 1; }else{ - /* Someone else is in the process of initing the static mutexes */ + /* Another thread is (in the process of) initializing the static + ** mutexes */ while( !winMutex_isInit ){ sqlite3_win32_sleep(1); } } - return SQLITE_OK; + return SQLITE_OK; } -static int winMutexEnd(void){ - /* The first to decrement to 0 does actual shutdown +static int winMutexEnd(void){ + /* The first to decrement to 0 does actual shutdown ** (which should be the last to shutdown.) */ if( InterlockedCompareExchange(&winMutex_lock, 0, 1)==1 ){ if( winMutex_isInit==1 ){ @@ -19253,7 +21463,7 @@ static int winMutexEnd(void){ winMutex_isInit = 0; } } - return SQLITE_OK; + return SQLITE_OK; } /* @@ -19268,10 +21478,16 @@ static int winMutexEnd(void){ **
  • SQLITE_MUTEX_RECURSIVE **
  • SQLITE_MUTEX_STATIC_MASTER **
  • SQLITE_MUTEX_STATIC_MEM -**
  • SQLITE_MUTEX_STATIC_MEM2 +**
  • SQLITE_MUTEX_STATIC_OPEN **
  • SQLITE_MUTEX_STATIC_PRNG **
  • SQLITE_MUTEX_STATIC_LRU **
  • SQLITE_MUTEX_STATIC_PMEM +**
  • SQLITE_MUTEX_STATIC_APP1 +**
  • SQLITE_MUTEX_STATIC_APP2 +**
  • SQLITE_MUTEX_STATIC_APP3 +**
  • SQLITE_MUTEX_STATIC_VFS1 +**
  • SQLITE_MUTEX_STATIC_VFS2 +**
  • SQLITE_MUTEX_STATIC_VFS3 ** ** ** The first two constants cause sqlite3_mutex_alloc() to create @@ -19294,7 +21510,7 @@ static int winMutexEnd(void){ ** ** Note that if one of the dynamic mutex parameters (SQLITE_MUTEX_FAST ** or SQLITE_MUTEX_RECURSIVE) is used then sqlite3_mutex_alloc() -** returns a different mutex on every call. But for the static +** returns a different mutex on every call. But for the static ** mutex types, the same mutex is returned on every call that has ** the same type number. */ @@ -19305,9 +21521,12 @@ static sqlite3_mutex *winMutexAlloc(int iType){ case SQLITE_MUTEX_FAST: case SQLITE_MUTEX_RECURSIVE: { p = sqlite3MallocZero( sizeof(*p) ); - if( p ){ -#ifdef SQLITE_DEBUG + if( p ){ p->id = iType; +#ifdef SQLITE_DEBUG +#ifdef SQLITE_WIN32_MUTEX_TRACE_DYNAMIC + p->trace = 1; +#endif #endif #if SQLITE_OS_WINRT InitializeCriticalSectionEx(&p->mutex, 0, 0); @@ -19318,12 +21537,18 @@ static sqlite3_mutex *winMutexAlloc(int iType){ break; } default: { - assert( winMutex_isInit==1 ); - assert( iType-2 >= 0 ); - assert( iType-2 < ArraySize(winMutex_staticMutexes) ); +#ifdef SQLITE_ENABLE_API_ARMOR + if( iType-2<0 || iType-2>=ArraySize(winMutex_staticMutexes) ){ + (void)SQLITE_MISUSE_BKPT; + return 0; + } +#endif p = &winMutex_staticMutexes[iType-2]; -#ifdef SQLITE_DEBUG p->id = iType; +#ifdef SQLITE_DEBUG +#ifdef SQLITE_WIN32_MUTEX_TRACE_STATIC + p->trace = 1; +#endif #endif break; } @@ -19340,9 +21565,14 @@ static sqlite3_mutex *winMutexAlloc(int iType){ static void winMutexFree(sqlite3_mutex *p){ assert( p ); assert( p->nRef==0 && p->owner==0 ); - assert( p->id==SQLITE_MUTEX_FAST || p->id==SQLITE_MUTEX_RECURSIVE ); - DeleteCriticalSection(&p->mutex); - sqlite3_free(p); + if( p->id==SQLITE_MUTEX_FAST || p->id==SQLITE_MUTEX_RECURSIVE ){ + DeleteCriticalSection(&p->mutex); + sqlite3_free(p); + }else{ +#ifdef SQLITE_ENABLE_API_ARMOR + (void)SQLITE_MISUSE_BKPT; +#endif + } } /* @@ -19357,30 +21587,39 @@ static void winMutexFree(sqlite3_mutex *p){ ** more than once, the behavior is undefined. */ static void winMutexEnter(sqlite3_mutex *p){ -#ifdef SQLITE_DEBUG - DWORD tid = GetCurrentThreadId(); - assert( p->id==SQLITE_MUTEX_RECURSIVE || winMutexNotheld2(p, tid) ); +#if defined(SQLITE_DEBUG) || defined(SQLITE_TEST) + DWORD tid = GetCurrentThreadId(); #endif +#ifdef SQLITE_DEBUG + assert( p ); + assert( p->id==SQLITE_MUTEX_RECURSIVE || winMutexNotheld2(p, tid) ); +#else + assert( p ); +#endif + assert( winMutex_isInit==1 ); EnterCriticalSection(&p->mutex); #ifdef SQLITE_DEBUG assert( p->nRef>0 || p->owner==0 ); - p->owner = tid; + p->owner = tid; p->nRef++; if( p->trace ){ - printf("enter mutex %p (%d) with nRef=%d\n", p, p->trace, p->nRef); + OSTRACE(("ENTER-MUTEX tid=%lu, mutex=%p (%d), nRef=%d\n", + tid, p, p->trace, p->nRef)); } #endif } + static int winMutexTry(sqlite3_mutex *p){ -#ifndef NDEBUG - DWORD tid = GetCurrentThreadId(); +#if defined(SQLITE_DEBUG) || defined(SQLITE_TEST) + DWORD tid = GetCurrentThreadId(); #endif int rc = SQLITE_BUSY; + assert( p ); assert( p->id==SQLITE_MUTEX_RECURSIVE || winMutexNotheld2(p, tid) ); /* ** The sqlite3_mutex_try() routine is very rarely used, and when it ** is used it is merely an optimization. So it is OK for it to always - ** fail. + ** fail. ** ** The TryEnterCriticalSection() interface is only available on WinNT. ** And some windows compilers complain if you try to use it without @@ -19388,18 +21627,27 @@ static int winMutexTry(sqlite3_mutex *p){ ** For that reason, we will omit this optimization for now. See ** ticket #2685. */ -#if 0 - if( mutexIsNT() && TryEnterCriticalSection(&p->mutex) ){ +#if defined(_WIN32_WINNT) && _WIN32_WINNT >= 0x0400 + assert( winMutex_isInit==1 ); + assert( winMutex_isNt>=-1 && winMutex_isNt<=1 ); + if( winMutex_isNt<0 ){ + winMutex_isNt = sqlite3_win32_is_nt(); + } + assert( winMutex_isNt==0 || winMutex_isNt==1 ); + if( winMutex_isNt && TryEnterCriticalSection(&p->mutex) ){ +#ifdef SQLITE_DEBUG p->owner = tid; p->nRef++; +#endif rc = SQLITE_OK; } #else UNUSED_PARAMETER(p); #endif #ifdef SQLITE_DEBUG - if( rc==SQLITE_OK && p->trace ){ - printf("try mutex %p (%d) with nRef=%d\n", p, p->trace, p->nRef); + if( p->trace ){ + OSTRACE(("TRY-MUTEX tid=%lu, mutex=%p (%d), owner=%lu, nRef=%d, rc=%s\n", + tid, p, p->trace, p->owner, p->nRef, sqlite3ErrName(rc))); } #endif return rc; @@ -19412,18 +21660,23 @@ static int winMutexTry(sqlite3_mutex *p){ ** is not currently allocated. SQLite will never do either. */ static void winMutexLeave(sqlite3_mutex *p){ -#ifndef NDEBUG +#if defined(SQLITE_DEBUG) || defined(SQLITE_TEST) DWORD tid = GetCurrentThreadId(); +#endif + assert( p ); +#ifdef SQLITE_DEBUG assert( p->nRef>0 ); assert( p->owner==tid ); p->nRef--; if( p->nRef==0 ) p->owner = 0; assert( p->nRef==0 || p->id==SQLITE_MUTEX_RECURSIVE ); #endif + assert( winMutex_isInit==1 ); LeaveCriticalSection(&p->mutex); #ifdef SQLITE_DEBUG if( p->trace ){ - printf("leave mutex %p (%d) with nRef=%d\n", p, p->trace, p->nRef); + OSTRACE(("LEAVE-MUTEX tid=%lu, mutex=%p (%d), nRef=%d\n", + tid, p, p->trace, p->nRef)); } #endif } @@ -19445,9 +21698,9 @@ SQLITE_PRIVATE sqlite3_mutex_methods const *sqlite3DefaultMutex(void){ 0 #endif }; - return &sMutex; } + #endif /* SQLITE_MUTEX_W32 */ /************** End of mutex_w32.c *******************************************/ @@ -19466,6 +21719,7 @@ SQLITE_PRIVATE sqlite3_mutex_methods const *sqlite3DefaultMutex(void){ ** ** Memory allocation functions used throughout sqlite. */ +/* #include "sqliteInt.h" */ /* #include */ /* @@ -19473,7 +21727,7 @@ SQLITE_PRIVATE sqlite3_mutex_methods const *sqlite3DefaultMutex(void){ ** held by SQLite. An example of non-essential memory is memory used to ** cache database pages that are not currently in use. */ -SQLITE_API int sqlite3_release_memory(int n){ +SQLITE_API int SQLITE_STDCALL sqlite3_release_memory(int n){ #ifdef SQLITE_ENABLE_MEMORY_MANAGEMENT return sqlite3PcacheReleaseMemory(n); #else @@ -19498,16 +21752,7 @@ typedef struct ScratchFreeslot { */ static SQLITE_WSD struct Mem0Global { sqlite3_mutex *mutex; /* Mutex to serialize access */ - - /* - ** The alarm callback and its arguments. The mem0.mutex lock will - ** be held while the callback is running. Recursive calls into - ** the memory subsystem are allowed, but no new callbacks will be - ** issued. - */ - sqlite3_int64 alarmThreshold; - void (*alarmCallback)(void*, sqlite3_int64,int); - void *alarmArg; + sqlite3_int64 alarmThreshold; /* The soft heap limit */ /* ** Pointers to the end of sqlite3GlobalConfig.pScratch memory @@ -19524,54 +21769,32 @@ static SQLITE_WSD struct Mem0Global { ** sqlite3_soft_heap_limit() setting. */ int nearlyFull; -} mem0 = { 0, 0, 0, 0, 0, 0, 0, 0 }; +} mem0 = { 0, 0, 0, 0, 0, 0 }; #define mem0 GLOBAL(struct Mem0Global, mem0) /* -** This routine runs when the memory allocator sees that the -** total memory allocation is about to exceed the soft heap -** limit. +** Return the memory allocator mutex. sqlite3_status() needs it. */ -static void softHeapLimitEnforcer( - void *NotUsed, - sqlite3_int64 NotUsed2, - int allocSize -){ - UNUSED_PARAMETER2(NotUsed, NotUsed2); - sqlite3_release_memory(allocSize); -} - -/* -** Change the alarm callback -*/ -static int sqlite3MemoryAlarm( - void(*xCallback)(void *pArg, sqlite3_int64 used,int N), - void *pArg, - sqlite3_int64 iThreshold -){ - int nUsed; - sqlite3_mutex_enter(mem0.mutex); - mem0.alarmCallback = xCallback; - mem0.alarmArg = pArg; - mem0.alarmThreshold = iThreshold; - nUsed = sqlite3StatusValue(SQLITE_STATUS_MEMORY_USED); - mem0.nearlyFull = (iThreshold>0 && iThreshold<=nUsed); - sqlite3_mutex_leave(mem0.mutex); - return SQLITE_OK; +SQLITE_PRIVATE sqlite3_mutex *sqlite3MallocMutex(void){ + return mem0.mutex; } #ifndef SQLITE_OMIT_DEPRECATED /* -** Deprecated external interface. Internal/core SQLite code -** should call sqlite3MemoryAlarm. +** Deprecated external interface. It used to set an alarm callback +** that was invoked when memory usage grew too large. Now it is a +** no-op. */ -SQLITE_API int sqlite3_memory_alarm( +SQLITE_API int SQLITE_STDCALL sqlite3_memory_alarm( void(*xCallback)(void *pArg, sqlite3_int64 used,int N), void *pArg, sqlite3_int64 iThreshold ){ - return sqlite3MemoryAlarm(xCallback, pArg, iThreshold); + (void)xCallback; + (void)pArg; + (void)iThreshold; + return SQLITE_OK; } #endif @@ -19579,27 +21802,29 @@ SQLITE_API int sqlite3_memory_alarm( ** Set the soft heap-size limit for the library. Passing a zero or ** negative value indicates no limit. */ -SQLITE_API sqlite3_int64 sqlite3_soft_heap_limit64(sqlite3_int64 n){ +SQLITE_API sqlite3_int64 SQLITE_STDCALL sqlite3_soft_heap_limit64(sqlite3_int64 n){ sqlite3_int64 priorLimit; sqlite3_int64 excess; + sqlite3_int64 nUsed; #ifndef SQLITE_OMIT_AUTOINIT int rc = sqlite3_initialize(); if( rc ) return -1; #endif sqlite3_mutex_enter(mem0.mutex); priorLimit = mem0.alarmThreshold; - sqlite3_mutex_leave(mem0.mutex); - if( n<0 ) return priorLimit; - if( n>0 ){ - sqlite3MemoryAlarm(softHeapLimitEnforcer, 0, n); - }else{ - sqlite3MemoryAlarm(0, 0, 0); + if( n<0 ){ + sqlite3_mutex_leave(mem0.mutex); + return priorLimit; } + mem0.alarmThreshold = n; + nUsed = sqlite3StatusValue(SQLITE_STATUS_MEMORY_USED); + mem0.nearlyFull = (n>0 && n<=nUsed); + sqlite3_mutex_leave(mem0.mutex); excess = sqlite3_memory_used() - n; if( excess>0 ) sqlite3_release_memory((int)(excess & 0x7fffffff)); return priorLimit; } -SQLITE_API void sqlite3_soft_heap_limit(int n){ +SQLITE_API void SQLITE_STDCALL sqlite3_soft_heap_limit(int n){ if( n<0 ) n = 0; sqlite3_soft_heap_limit64(n); } @@ -19608,13 +21833,12 @@ SQLITE_API void sqlite3_soft_heap_limit(int n){ ** Initialize the memory allocation subsystem. */ SQLITE_PRIVATE int sqlite3MallocInit(void){ + int rc; if( sqlite3GlobalConfig.m.xMalloc==0 ){ sqlite3MemSetDefault(); } memset(&mem0, 0, sizeof(mem0)); - if( sqlite3GlobalConfig.bCoreMutex ){ - mem0.mutex = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MEM); - } + mem0.mutex = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MEM); if( sqlite3GlobalConfig.pScratch && sqlite3GlobalConfig.szScratch>=100 && sqlite3GlobalConfig.nScratch>0 ){ int i, n, sz; @@ -19638,12 +21862,13 @@ SQLITE_PRIVATE int sqlite3MallocInit(void){ sqlite3GlobalConfig.nScratch = 0; } if( sqlite3GlobalConfig.pPage==0 || sqlite3GlobalConfig.szPage<512 - || sqlite3GlobalConfig.nPage<1 ){ + || sqlite3GlobalConfig.nPage<=0 ){ sqlite3GlobalConfig.pPage = 0; sqlite3GlobalConfig.szPage = 0; - sqlite3GlobalConfig.nPage = 0; } - return sqlite3GlobalConfig.m.xInit(sqlite3GlobalConfig.m.pAppData); + rc = sqlite3GlobalConfig.m.xInit(sqlite3GlobalConfig.m.pAppData); + if( rc!=SQLITE_OK ) memset(&mem0, 0, sizeof(mem0)); + return rc; } /* @@ -19668,11 +21893,9 @@ SQLITE_PRIVATE void sqlite3MallocEnd(void){ /* ** Return the amount of memory currently checked out. */ -SQLITE_API sqlite3_int64 sqlite3_memory_used(void){ - int n, mx; - sqlite3_int64 res; - sqlite3_status(SQLITE_STATUS_MEMORY_USED, &n, &mx, 0); - res = (sqlite3_int64)n; /* Work around bug in Borland C. Ticket #3216 */ +SQLITE_API sqlite3_int64 SQLITE_STDCALL sqlite3_memory_used(void){ + sqlite3_int64 res, mx; + sqlite3_status64(SQLITE_STATUS_MEMORY_USED, &res, &mx, 0); return res; } @@ -19681,31 +21904,20 @@ SQLITE_API sqlite3_int64 sqlite3_memory_used(void){ ** checked out since either the beginning of this process ** or since the most recent reset. */ -SQLITE_API sqlite3_int64 sqlite3_memory_highwater(int resetFlag){ - int n, mx; - sqlite3_int64 res; - sqlite3_status(SQLITE_STATUS_MEMORY_USED, &n, &mx, resetFlag); - res = (sqlite3_int64)mx; /* Work around bug in Borland C. Ticket #3216 */ - return res; +SQLITE_API sqlite3_int64 SQLITE_STDCALL sqlite3_memory_highwater(int resetFlag){ + sqlite3_int64 res, mx; + sqlite3_status64(SQLITE_STATUS_MEMORY_USED, &res, &mx, resetFlag); + return mx; } /* ** Trigger the alarm */ static void sqlite3MallocAlarm(int nByte){ - void (*xCallback)(void*,sqlite3_int64,int); - sqlite3_int64 nowUsed; - void *pArg; - if( mem0.alarmCallback==0 ) return; - xCallback = mem0.alarmCallback; - nowUsed = sqlite3StatusValue(SQLITE_STATUS_MEMORY_USED); - pArg = mem0.alarmArg; - mem0.alarmCallback = 0; + if( mem0.alarmThreshold<=0 ) return; sqlite3_mutex_leave(mem0.mutex); - xCallback(pArg, nowUsed, nByte); + sqlite3_release_memory(nByte); sqlite3_mutex_enter(mem0.mutex); - mem0.alarmCallback = xCallback; - mem0.alarmArg = pArg; } /* @@ -19717,9 +21929,9 @@ static int mallocWithAlarm(int n, void **pp){ void *p; assert( sqlite3_mutex_held(mem0.mutex) ); nFull = sqlite3GlobalConfig.m.xRoundup(n); - sqlite3StatusSet(SQLITE_STATUS_MALLOC_SIZE, n); - if( mem0.alarmCallback!=0 ){ - int nUsed = sqlite3StatusValue(SQLITE_STATUS_MEMORY_USED); + sqlite3StatusHighwater(SQLITE_STATUS_MALLOC_SIZE, n); + if( mem0.alarmThreshold>0 ){ + sqlite3_int64 nUsed = sqlite3StatusValue(SQLITE_STATUS_MEMORY_USED); if( nUsed >= mem0.alarmThreshold - nFull ){ mem0.nearlyFull = 1; sqlite3MallocAlarm(nFull); @@ -19729,15 +21941,15 @@ static int mallocWithAlarm(int n, void **pp){ } p = sqlite3GlobalConfig.m.xMalloc(nFull); #ifdef SQLITE_ENABLE_MEMORY_MANAGEMENT - if( p==0 && mem0.alarmCallback ){ + if( p==0 && mem0.alarmThreshold>0 ){ sqlite3MallocAlarm(nFull); p = sqlite3GlobalConfig.m.xMalloc(nFull); } #endif if( p ){ nFull = sqlite3MallocSize(p); - sqlite3StatusAdd(SQLITE_STATUS_MEMORY_USED, nFull); - sqlite3StatusAdd(SQLITE_STATUS_MALLOC_COUNT, 1); + sqlite3StatusUp(SQLITE_STATUS_MEMORY_USED, nFull); + sqlite3StatusUp(SQLITE_STATUS_MALLOC_COUNT, 1); } *pp = p; return nFull; @@ -19747,11 +21959,9 @@ static int mallocWithAlarm(int n, void **pp){ ** Allocate memory. This routine is like sqlite3_malloc() except that it ** assumes the memory subsystem has already been initialized. */ -SQLITE_PRIVATE void *sqlite3Malloc(int n){ +SQLITE_PRIVATE void *sqlite3Malloc(u64 n){ void *p; - if( n<=0 /* IMP: R-65312-04917 */ - || n>=0x7fffff00 - ){ + if( n==0 || n>=0x7fffff00 ){ /* A memory allocation of a number of bytes which is near the maximum ** signed integer value might cause an integer overflow inside of the ** xMalloc(). Hence we limit the maximum size to 0x7fffff00, giving @@ -19760,12 +21970,12 @@ SQLITE_PRIVATE void *sqlite3Malloc(int n){ p = 0; }else if( sqlite3GlobalConfig.bMemstat ){ sqlite3_mutex_enter(mem0.mutex); - mallocWithAlarm(n, &p); + mallocWithAlarm((int)n, &p); sqlite3_mutex_leave(mem0.mutex); }else{ - p = sqlite3GlobalConfig.m.xMalloc(n); + p = sqlite3GlobalConfig.m.xMalloc((int)n); } - assert( EIGHT_BYTE_ALIGNMENT(p) ); /* IMP: R-04675-44850 */ + assert( EIGHT_BYTE_ALIGNMENT(p) ); /* IMP: R-11148-40995 */ return p; } @@ -19774,7 +21984,13 @@ SQLITE_PRIVATE void *sqlite3Malloc(int n){ ** First make sure the memory subsystem is initialized, then do the ** allocation. */ -SQLITE_API void *sqlite3_malloc(int n){ +SQLITE_API void *SQLITE_STDCALL sqlite3_malloc(int n){ +#ifndef SQLITE_OMIT_AUTOINIT + if( sqlite3_initialize() ) return 0; +#endif + return n<=0 ? 0 : sqlite3Malloc(n); +} +SQLITE_API void *SQLITE_STDCALL sqlite3_malloc64(sqlite3_uint64 n){ #ifndef SQLITE_OMIT_AUTOINIT if( sqlite3_initialize() ) return 0; #endif @@ -19805,22 +22021,20 @@ SQLITE_PRIVATE void *sqlite3ScratchMalloc(int n){ assert( n>0 ); sqlite3_mutex_enter(mem0.mutex); + sqlite3StatusHighwater(SQLITE_STATUS_SCRATCH_SIZE, n); if( mem0.nScratchFree && sqlite3GlobalConfig.szScratch>=n ){ p = mem0.pScratchFree; mem0.pScratchFree = mem0.pScratchFree->pNext; mem0.nScratchFree--; - sqlite3StatusAdd(SQLITE_STATUS_SCRATCH_USED, 1); - sqlite3StatusSet(SQLITE_STATUS_SCRATCH_SIZE, n); + sqlite3StatusUp(SQLITE_STATUS_SCRATCH_USED, 1); sqlite3_mutex_leave(mem0.mutex); }else{ - if( sqlite3GlobalConfig.bMemstat ){ - sqlite3StatusSet(SQLITE_STATUS_SCRATCH_SIZE, n); - n = mallocWithAlarm(n, &p); - if( p ) sqlite3StatusAdd(SQLITE_STATUS_SCRATCH_OVERFLOW, n); + sqlite3_mutex_leave(mem0.mutex); + p = sqlite3Malloc(n); + if( sqlite3GlobalConfig.bMemstat && p ){ + sqlite3_mutex_enter(mem0.mutex); + sqlite3StatusUp(SQLITE_STATUS_SCRATCH_OVERFLOW, sqlite3MallocSize(p)); sqlite3_mutex_leave(mem0.mutex); - }else{ - sqlite3_mutex_leave(mem0.mutex); - p = sqlite3GlobalConfig.m.xMalloc(n); } sqlite3MemdebugSetType(p, MEMTYPE_SCRATCH); } @@ -19828,11 +22042,12 @@ SQLITE_PRIVATE void *sqlite3ScratchMalloc(int n){ #if SQLITE_THREADSAFE==0 && !defined(NDEBUG) - /* Verify that no more than two scratch allocations per thread - ** are outstanding at one time. (This is only checked in the - ** single-threaded case since checking in the multi-threaded case - ** would be much more complicated.) */ - assert( scratchAllocOut<=1 ); + /* EVIDENCE-OF: R-12970-05880 SQLite will not use more than one scratch + ** buffers per thread. + ** + ** This can only be checked in single-threaded mode. + */ + assert( scratchAllocOut==0 ); if( p ) scratchAllocOut++; #endif @@ -19850,7 +22065,7 @@ SQLITE_PRIVATE void sqlite3ScratchFree(void *p){ scratchAllocOut--; #endif - if( p>=sqlite3GlobalConfig.pScratch && p=db->lookaside.pStart && plookaside.pEnd; + return SQLITE_WITHIN(p, db->lookaside.pStart, db->lookaside.pEnd); } #else #define isLookaside(A,B) 0 @@ -19898,33 +22113,43 @@ static int isLookaside(sqlite3 *db, void *p){ */ SQLITE_PRIVATE int sqlite3MallocSize(void *p){ assert( sqlite3MemdebugHasType(p, MEMTYPE_HEAP) ); - assert( sqlite3MemdebugNoType(p, MEMTYPE_DB) ); return sqlite3GlobalConfig.m.xSize(p); } SQLITE_PRIVATE int sqlite3DbMallocSize(sqlite3 *db, void *p){ - assert( db!=0 ); - assert( sqlite3_mutex_held(db->mutex) ); - if( isLookaside(db, p) ){ - return db->lookaside.sz; - }else{ - assert( sqlite3MemdebugHasType(p, MEMTYPE_DB) ); - assert( sqlite3MemdebugHasType(p, MEMTYPE_LOOKASIDE|MEMTYPE_HEAP) ); - assert( db!=0 || sqlite3MemdebugNoType(p, MEMTYPE_LOOKASIDE) ); + assert( p!=0 ); + if( db==0 || !isLookaside(db,p) ){ +#if SQLITE_DEBUG + if( db==0 ){ + assert( sqlite3MemdebugNoType(p, (u8)~MEMTYPE_HEAP) ); + assert( sqlite3MemdebugHasType(p, MEMTYPE_HEAP) ); + }else{ + assert( sqlite3MemdebugHasType(p, (MEMTYPE_LOOKASIDE|MEMTYPE_HEAP)) ); + assert( sqlite3MemdebugNoType(p, (u8)~(MEMTYPE_LOOKASIDE|MEMTYPE_HEAP)) ); + } +#endif return sqlite3GlobalConfig.m.xSize(p); + }else{ + assert( sqlite3_mutex_held(db->mutex) ); + return db->lookaside.sz; } } +SQLITE_API sqlite3_uint64 SQLITE_STDCALL sqlite3_msize(void *p){ + assert( sqlite3MemdebugNoType(p, (u8)~MEMTYPE_HEAP) ); + assert( sqlite3MemdebugHasType(p, MEMTYPE_HEAP) ); + return p ? sqlite3GlobalConfig.m.xSize(p) : 0; +} /* ** Free memory previously obtained from sqlite3Malloc(). */ -SQLITE_API void sqlite3_free(void *p){ +SQLITE_API void SQLITE_STDCALL sqlite3_free(void *p){ if( p==0 ) return; /* IMP: R-49053-54554 */ - assert( sqlite3MemdebugNoType(p, MEMTYPE_DB) ); assert( sqlite3MemdebugHasType(p, MEMTYPE_HEAP) ); + assert( sqlite3MemdebugNoType(p, (u8)~MEMTYPE_HEAP) ); if( sqlite3GlobalConfig.bMemstat ){ sqlite3_mutex_enter(mem0.mutex); - sqlite3StatusAdd(SQLITE_STATUS_MEMORY_USED, -sqlite3MallocSize(p)); - sqlite3StatusAdd(SQLITE_STATUS_MALLOC_COUNT, -1); + sqlite3StatusDown(SQLITE_STATUS_MEMORY_USED, sqlite3MallocSize(p)); + sqlite3StatusDown(SQLITE_STATUS_MALLOC_COUNT, 1); sqlite3GlobalConfig.m.xFree(p); sqlite3_mutex_leave(mem0.mutex); }else{ @@ -19932,6 +22157,14 @@ SQLITE_API void sqlite3_free(void *p){ } } +/* +** Add the size of memory allocation "p" to the count in +** *db->pnBytesFreed. +*/ +static SQLITE_NOINLINE void measureAllocationSize(sqlite3 *db, void *p){ + *db->pnBytesFreed += sqlite3DbMallocSize(db,p); +} + /* ** Free memory that might be associated with a particular database ** connection. @@ -19941,7 +22174,7 @@ SQLITE_PRIVATE void sqlite3DbFree(sqlite3 *db, void *p){ if( p==0 ) return; if( db ){ if( db->pnBytesFreed ){ - *db->pnBytesFreed += sqlite3DbMallocSize(db, p); + measureAllocationSize(db, p); return; } if( isLookaside(db, p) ){ @@ -19956,8 +22189,8 @@ SQLITE_PRIVATE void sqlite3DbFree(sqlite3 *db, void *p){ return; } } - assert( sqlite3MemdebugHasType(p, MEMTYPE_DB) ); - assert( sqlite3MemdebugHasType(p, MEMTYPE_LOOKASIDE|MEMTYPE_HEAP) ); + assert( sqlite3MemdebugHasType(p, (MEMTYPE_LOOKASIDE|MEMTYPE_HEAP)) ); + assert( sqlite3MemdebugNoType(p, (u8)~(MEMTYPE_LOOKASIDE|MEMTYPE_HEAP)) ); assert( db!=0 || sqlite3MemdebugNoType(p, MEMTYPE_LOOKASIDE) ); sqlite3MemdebugSetType(p, MEMTYPE_HEAP); sqlite3_free(p); @@ -19966,14 +22199,16 @@ SQLITE_PRIVATE void sqlite3DbFree(sqlite3 *db, void *p){ /* ** Change the size of an existing memory allocation */ -SQLITE_PRIVATE void *sqlite3Realloc(void *pOld, int nBytes){ +SQLITE_PRIVATE void *sqlite3Realloc(void *pOld, u64 nBytes){ int nOld, nNew, nDiff; void *pNew; + assert( sqlite3MemdebugHasType(pOld, MEMTYPE_HEAP) ); + assert( sqlite3MemdebugNoType(pOld, (u8)~MEMTYPE_HEAP) ); if( pOld==0 ){ - return sqlite3Malloc(nBytes); /* IMP: R-28354-25769 */ + return sqlite3Malloc(nBytes); /* IMP: R-04300-56712 */ } - if( nBytes<=0 ){ - sqlite3_free(pOld); /* IMP: R-31593-10574 */ + if( nBytes==0 ){ + sqlite3_free(pOld); /* IMP: R-26507-47431 */ return 0; } if( nBytes>=0x7fffff00 ){ @@ -19984,33 +22219,31 @@ SQLITE_PRIVATE void *sqlite3Realloc(void *pOld, int nBytes){ /* IMPLEMENTATION-OF: R-46199-30249 SQLite guarantees that the second ** argument to xRealloc is always a value returned by a prior call to ** xRoundup. */ - nNew = sqlite3GlobalConfig.m.xRoundup(nBytes); + nNew = sqlite3GlobalConfig.m.xRoundup((int)nBytes); if( nOld==nNew ){ pNew = pOld; }else if( sqlite3GlobalConfig.bMemstat ){ sqlite3_mutex_enter(mem0.mutex); - sqlite3StatusSet(SQLITE_STATUS_MALLOC_SIZE, nBytes); + sqlite3StatusHighwater(SQLITE_STATUS_MALLOC_SIZE, (int)nBytes); nDiff = nNew - nOld; if( sqlite3StatusValue(SQLITE_STATUS_MEMORY_USED) >= mem0.alarmThreshold-nDiff ){ sqlite3MallocAlarm(nDiff); } - assert( sqlite3MemdebugHasType(pOld, MEMTYPE_HEAP) ); - assert( sqlite3MemdebugNoType(pOld, ~MEMTYPE_HEAP) ); pNew = sqlite3GlobalConfig.m.xRealloc(pOld, nNew); - if( pNew==0 && mem0.alarmCallback ){ - sqlite3MallocAlarm(nBytes); + if( pNew==0 && mem0.alarmThreshold>0 ){ + sqlite3MallocAlarm((int)nBytes); pNew = sqlite3GlobalConfig.m.xRealloc(pOld, nNew); } if( pNew ){ nNew = sqlite3MallocSize(pNew); - sqlite3StatusAdd(SQLITE_STATUS_MEMORY_USED, nNew-nOld); + sqlite3StatusUp(SQLITE_STATUS_MEMORY_USED, nNew-nOld); } sqlite3_mutex_leave(mem0.mutex); }else{ pNew = sqlite3GlobalConfig.m.xRealloc(pOld, nNew); } - assert( EIGHT_BYTE_ALIGNMENT(pNew) ); /* IMP: R-04675-44850 */ + assert( EIGHT_BYTE_ALIGNMENT(pNew) ); /* IMP: R-11148-40995 */ return pNew; } @@ -20018,7 +22251,14 @@ SQLITE_PRIVATE void *sqlite3Realloc(void *pOld, int nBytes){ ** The public interface to sqlite3Realloc. Make sure that the memory ** subsystem is initialized prior to invoking sqliteRealloc. */ -SQLITE_API void *sqlite3_realloc(void *pOld, int n){ +SQLITE_API void *SQLITE_STDCALL sqlite3_realloc(void *pOld, int n){ +#ifndef SQLITE_OMIT_AUTOINIT + if( sqlite3_initialize() ) return 0; +#endif + if( n<0 ) n = 0; /* IMP: R-26507-47431 */ + return sqlite3Realloc(pOld, n); +} +SQLITE_API void *SQLITE_STDCALL sqlite3_realloc64(void *pOld, sqlite3_uint64 n){ #ifndef SQLITE_OMIT_AUTOINIT if( sqlite3_initialize() ) return 0; #endif @@ -20029,10 +22269,10 @@ SQLITE_API void *sqlite3_realloc(void *pOld, int n){ /* ** Allocate and zero memory. */ -SQLITE_PRIVATE void *sqlite3MallocZero(int n){ +SQLITE_PRIVATE void *sqlite3MallocZero(u64 n){ void *p = sqlite3Malloc(n); if( p ){ - memset(p, 0, n); + memset(p, 0, (size_t)n); } return p; } @@ -20041,10 +22281,10 @@ SQLITE_PRIVATE void *sqlite3MallocZero(int n){ ** Allocate and zero memory. If the allocation fails, make ** the mallocFailed flag in the connection pointer. */ -SQLITE_PRIVATE void *sqlite3DbMallocZero(sqlite3 *db, int n){ +SQLITE_PRIVATE void *sqlite3DbMallocZero(sqlite3 *db, u64 n){ void *p = sqlite3DbMallocRaw(db, n); if( p ){ - memset(p, 0, n); + memset(p, 0, (size_t)n); } return p; } @@ -20067,7 +22307,7 @@ SQLITE_PRIVATE void *sqlite3DbMallocZero(sqlite3 *db, int n){ ** In other words, if a subsequent malloc (ex: "b") worked, it is assumed ** that all prior mallocs (ex: "a") worked too. */ -SQLITE_PRIVATE void *sqlite3DbMallocRaw(sqlite3 *db, int n){ +SQLITE_PRIVATE void *sqlite3DbMallocRaw(sqlite3 *db, u64 n){ void *p; assert( db==0 || sqlite3_mutex_held(db->mutex) ); assert( db==0 || db->pnBytesFreed==0 ); @@ -20102,8 +22342,8 @@ SQLITE_PRIVATE void *sqlite3DbMallocRaw(sqlite3 *db, int n){ if( !p && db ){ db->mallocFailed = 1; } - sqlite3MemdebugSetType(p, MEMTYPE_DB | - ((db && db->lookaside.bEnabled) ? MEMTYPE_LOOKASIDE : MEMTYPE_HEAP)); + sqlite3MemdebugSetType(p, + (db && db->lookaside.bEnabled) ? MEMTYPE_LOOKASIDE : MEMTYPE_HEAP); return p; } @@ -20111,7 +22351,7 @@ SQLITE_PRIVATE void *sqlite3DbMallocRaw(sqlite3 *db, int n){ ** Resize the block of memory pointed to by p to n bytes. If the ** resize fails, set the mallocFailed flag in the connection object. */ -SQLITE_PRIVATE void *sqlite3DbRealloc(sqlite3 *db, void *p, int n){ +SQLITE_PRIVATE void *sqlite3DbRealloc(sqlite3 *db, void *p, u64 n){ void *pNew = 0; assert( db!=0 ); assert( sqlite3_mutex_held(db->mutex) ); @@ -20129,15 +22369,14 @@ SQLITE_PRIVATE void *sqlite3DbRealloc(sqlite3 *db, void *p, int n){ sqlite3DbFree(db, p); } }else{ - assert( sqlite3MemdebugHasType(p, MEMTYPE_DB) ); - assert( sqlite3MemdebugHasType(p, MEMTYPE_LOOKASIDE|MEMTYPE_HEAP) ); + assert( sqlite3MemdebugHasType(p, (MEMTYPE_LOOKASIDE|MEMTYPE_HEAP)) ); + assert( sqlite3MemdebugNoType(p, (u8)~(MEMTYPE_LOOKASIDE|MEMTYPE_HEAP)) ); sqlite3MemdebugSetType(p, MEMTYPE_HEAP); - pNew = sqlite3_realloc(p, n); + pNew = sqlite3_realloc64(p, n); if( !pNew ){ - sqlite3MemdebugSetType(p, MEMTYPE_DB|MEMTYPE_HEAP); db->mallocFailed = 1; } - sqlite3MemdebugSetType(pNew, MEMTYPE_DB | + sqlite3MemdebugSetType(pNew, (db->lookaside.bEnabled ? MEMTYPE_LOOKASIDE : MEMTYPE_HEAP)); } } @@ -20148,7 +22387,7 @@ SQLITE_PRIVATE void *sqlite3DbRealloc(sqlite3 *db, void *p, int n){ ** Attempt to reallocate p. If the reallocation fails, then free p ** and set the mallocFailed flag in the database connection. */ -SQLITE_PRIVATE void *sqlite3DbReallocOrFree(sqlite3 *db, void *p, int n){ +SQLITE_PRIVATE void *sqlite3DbReallocOrFree(sqlite3 *db, void *p, u64 n){ void *pNew; pNew = sqlite3DbRealloc(db, p, n); if( !pNew ){ @@ -20178,7 +22417,7 @@ SQLITE_PRIVATE char *sqlite3DbStrDup(sqlite3 *db, const char *z){ } return zNew; } -SQLITE_PRIVATE char *sqlite3DbStrNDup(sqlite3 *db, const char *z, int n){ +SQLITE_PRIVATE char *sqlite3DbStrNDup(sqlite3 *db, const char *z, u64 n){ char *zNew; if( z==0 ){ return 0; @@ -20186,28 +22425,28 @@ SQLITE_PRIVATE char *sqlite3DbStrNDup(sqlite3 *db, const char *z, int n){ assert( (n&0x7fffffff)==n ); zNew = sqlite3DbMallocRaw(db, n+1); if( zNew ){ - memcpy(zNew, z, n); + memcpy(zNew, z, (size_t)n); zNew[n] = 0; } return zNew; } /* -** Create a string from the zFromat argument and the va_list that follows. -** Store the string in memory obtained from sqliteMalloc() and make *pz -** point to that string. +** Free any prior content in *pz and replace it with a copy of zNew. */ -SQLITE_PRIVATE void sqlite3SetString(char **pz, sqlite3 *db, const char *zFormat, ...){ - va_list ap; - char *z; - - va_start(ap, zFormat); - z = sqlite3VMPrintf(db, zFormat, ap); - va_end(ap); +SQLITE_PRIVATE void sqlite3SetString(char **pz, sqlite3 *db, const char *zNew){ sqlite3DbFree(db, *pz); - *pz = z; + *pz = sqlite3DbStrDup(db, zNew); } +/* +** Take actions at the end of an API call to indicate an OOM error +*/ +static SQLITE_NOINLINE int apiOomError(sqlite3 *db){ + db->mallocFailed = 0; + sqlite3Error(db, SQLITE_NOMEM); + return SQLITE_NOMEM; +} /* ** This function must be called before exiting any API function (i.e. @@ -20218,40 +22457,36 @@ SQLITE_PRIVATE void sqlite3SetString(char **pz, sqlite3 *db, const char *zFormat ** function. However, if a malloc() failure has occurred since the previous ** invocation SQLITE_NOMEM is returned instead. ** -** If the first argument, db, is not NULL and a malloc() error has occurred, -** then the connection error-code (the value returned by sqlite3_errcode()) -** is set to SQLITE_NOMEM. +** If an OOM as occurred, then the connection error-code (the value +** returned by sqlite3_errcode()) is set to SQLITE_NOMEM. */ SQLITE_PRIVATE int sqlite3ApiExit(sqlite3* db, int rc){ - /* If the db handle is not NULL, then we must hold the connection handle - ** mutex here. Otherwise the read (and possible write) of db->mallocFailed + /* If the db handle must hold the connection handle mutex here. + ** Otherwise the read (and possible write) of db->mallocFailed ** is unsafe, as is the call to sqlite3Error(). */ - assert( !db || sqlite3_mutex_held(db->mutex) ); - if( db && (db->mallocFailed || rc==SQLITE_IOERR_NOMEM) ){ - sqlite3Error(db, SQLITE_NOMEM, 0); - db->mallocFailed = 0; - rc = SQLITE_NOMEM; + assert( db!=0 ); + assert( sqlite3_mutex_held(db->mutex) ); + if( db->mallocFailed || rc==SQLITE_IOERR_NOMEM ){ + return apiOomError(db); } - return rc & (db ? db->errMask : 0xff); + return rc & db->errMask; } /************** End of malloc.c **********************************************/ /************** Begin file printf.c ******************************************/ /* ** The "printf" code that follows dates from the 1980's. It is in -** the public domain. The original comments are included here for -** completeness. They are very out-of-date but might be useful as -** an historical reference. Most of the "enhancements" have been backed -** out so that the functionality is now the same as standard printf(). +** the public domain. ** ************************************************************************** ** ** This file contains code for a set of "printf"-like routines. These ** routines format strings much like the printf() from the standard C ** library, though the implementation here has enhancements to support -** SQLlite. +** SQLite. */ +/* #include "sqliteInt.h" */ /* ** Conversion types fall into various categories as defined by the @@ -20377,6 +22612,7 @@ static char et_getdigit(LONGDOUBLE_TYPE *val, int *cnt){ ** Set the StrAccum object to an error mode. */ static void setStrAccumError(StrAccum *p, u8 eError){ + assert( eError==STRACCUM_NOMEM || eError==STRACCUM_TOOBIG ); p->accError = eError; p->nAlloc = 0; } @@ -20440,7 +22676,7 @@ SQLITE_PRIVATE void sqlite3VXPrintf( const et_info *infop; /* Pointer to the appropriate info structure */ char *zOut; /* Rendering buffer */ int nOut; /* Size of the rendering buffer */ - char *zExtra; /* Malloced memory used by some conversion */ + char *zExtra = 0; /* Malloced memory used by some conversion */ #ifndef SQLITE_OMIT_FLOATING_POINT int exp, e2; /* exponent of real numbers */ int nsd; /* Number of significant digits returned */ @@ -20463,9 +22699,13 @@ SQLITE_PRIVATE void sqlite3VXPrintf( for(; (c=(*fmt))!=0; ++fmt){ if( c!='%' ){ bufpt = (char *)fmt; - while( (c=(*++fmt))!='%' && c!=0 ){}; +#if HAVE_STRCHRNUL + fmt = strchrnul(fmt, '%'); +#else + do{ fmt++; }while( *fmt && *fmt != '%' ); +#endif sqlite3StrAccumAppend(pAccum, bufpt, (int)(fmt - bufpt)); - if( c==0 ) break; + if( *fmt==0 ) break; } if( (c=(*++fmt))==0 ){ sqlite3StrAccumAppend(pAccum, "%", 1); @@ -20487,7 +22727,6 @@ SQLITE_PRIVATE void sqlite3VXPrintf( } }while( !done && (c=(*++fmt))!=0 ); /* Get the field width */ - width = 0; if( c=='*' ){ if( bArgList ){ width = (int)getIntArg(pArgList); @@ -20496,18 +22735,27 @@ SQLITE_PRIVATE void sqlite3VXPrintf( } if( width<0 ){ flag_leftjustify = 1; - width = -width; + width = width >= -2147483647 ? -width : 0; } c = *++fmt; }else{ + unsigned wx = 0; while( c>='0' && c<='9' ){ - width = width*10 + c - '0'; + wx = wx*10 + c - '0'; c = *++fmt; } + testcase( wx>0x7fffffff ); + width = wx & 0x7fffffff; } + assert( width>=0 ); +#ifdef SQLITE_PRINTF_PRECISION_LIMIT + if( width>SQLITE_PRINTF_PRECISION_LIMIT ){ + width = SQLITE_PRINTF_PRECISION_LIMIT; + } +#endif + /* Get the precision */ if( c=='.' ){ - precision = 0; c = *++fmt; if( c=='*' ){ if( bArgList ){ @@ -20515,17 +22763,30 @@ SQLITE_PRIVATE void sqlite3VXPrintf( }else{ precision = va_arg(ap,int); } - if( precision<0 ) precision = -precision; c = *++fmt; + if( precision<0 ){ + precision = precision >= -2147483647 ? -precision : -1; + } }else{ + unsigned px = 0; while( c>='0' && c<='9' ){ - precision = precision*10 + c - '0'; + px = px*10 + c - '0'; c = *++fmt; } + testcase( px>0x7fffffff ); + precision = px & 0x7fffffff; } }else{ precision = -1; } + assert( precision>=(-1) ); +#ifdef SQLITE_PRINTF_PRECISION_LIMIT + if( precision>SQLITE_PRINTF_PRECISION_LIMIT ){ + precision = SQLITE_PRINTF_PRECISION_LIMIT; + } +#endif + + /* Get the conversion type modifier */ if( c=='l' ){ flag_long = 1; @@ -20553,7 +22814,6 @@ SQLITE_PRIVATE void sqlite3VXPrintf( break; } } - zExtra = 0; /* ** At this point, variables are initialized as follows: @@ -20686,7 +22946,8 @@ SQLITE_PRIVATE void sqlite3VXPrintf( else prefix = 0; } if( xtype==etGENERIC && precision>0 ) precision--; - for(idx=precision, rounder=0.5; idx>0; idx--, rounder*=0.1){} + testcase( precision>0xfff ); + for(idx=precision&0xfff, rounder=0.5; idx>0; idx--, rounder*=0.1){} if( xtype==etFLOAT ) realvalue += rounder; /* Normalize realvalue to within 10.0 > realvalue >= 1.0 */ exp = 0; @@ -20698,21 +22959,16 @@ SQLITE_PRIVATE void sqlite3VXPrintf( if( realvalue>0.0 ){ LONGDOUBLE_TYPE scale = 1.0; while( realvalue>=1e100*scale && exp<=350 ){ scale *= 1e100;exp+=100;} - while( realvalue>=1e64*scale && exp<=350 ){ scale *= 1e64; exp+=64; } - while( realvalue>=1e8*scale && exp<=350 ){ scale *= 1e8; exp+=8; } + while( realvalue>=1e10*scale && exp<=350 ){ scale *= 1e10; exp+=10; } while( realvalue>=10.0*scale && exp<=350 ){ scale *= 10.0; exp++; } realvalue /= scale; while( realvalue<1e-8 ){ realvalue *= 1e8; exp-=8; } while( realvalue<1.0 ){ realvalue *= 10.0; exp--; } if( exp>350 ){ - if( prefix=='-' ){ - bufpt = "-Inf"; - }else if( prefix=='+' ){ - bufpt = "+Inf"; - }else{ - bufpt = "Inf"; - } - length = sqlite3Strlen30(bufpt); + bufpt = buf; + buf[0] = prefix; + memcpy(buf+(prefix!=0),"Inf",4); + length = 3+(prefix!=0); break; } } @@ -20741,8 +22997,9 @@ SQLITE_PRIVATE void sqlite3VXPrintf( }else{ e2 = exp; } - if( MAX(e2,0)+precision+width > etBUFSIZE - 15 ){ - bufpt = zExtra = sqlite3Malloc( MAX(e2,0)+precision+width+15 ); + if( MAX(e2,0)+(i64)precision+(i64)width > etBUFSIZE - 15 ){ + bufpt = zExtra + = sqlite3Malloc( MAX(e2,0)+(i64)precision+(i64)width+15 ); if( bufpt==0 ){ setStrAccumError(pAccum, STRACCUM_NOMEM); return; @@ -20844,25 +23101,29 @@ SQLITE_PRIVATE void sqlite3VXPrintf( }else{ c = va_arg(ap,int); } - buf[0] = (char)c; - if( precision>=0 ){ - for(idx=1; idx1 ){ + width -= precision-1; + if( width>1 && !flag_leftjustify ){ + sqlite3AppendChar(pAccum, width-1, ' '); + width = 0; + } + sqlite3AppendChar(pAccum, precision-1, c); } + length = 1; + buf[0] = c; bufpt = buf; break; case etSTRING: case etDYNSTRING: if( bArgList ){ bufpt = getTextArg(pArgList); + xtype = etSTRING; }else{ bufpt = va_arg(ap,char*); } if( bufpt==0 ){ bufpt = ""; - }else if( xtype==etDYNSTRING && !bArgList ){ + }else if( xtype==etDYNSTRING ){ zExtra = bufpt; } if( precision>=0 ){ @@ -20871,9 +23132,9 @@ SQLITE_PRIVATE void sqlite3VXPrintf( length = sqlite3Strlen30(bufpt); } break; - case etSQLESCAPE: - case etSQLESCAPE2: - case etSQLESCAPE3: { + case etSQLESCAPE: /* Escape ' characters */ + case etSQLESCAPE2: /* Escape ' and enclose in '...' */ + case etSQLESCAPE3: { /* Escape " characters */ int i, j, k, n, isnull; int needQuote; char ch; @@ -20892,7 +23153,7 @@ SQLITE_PRIVATE void sqlite3VXPrintf( if( ch==q ) n++; } needQuote = !isnull && xtype==etSQLESCAPE2; - n += i + 1 + needQuote*2; + n += i + 3; if( n>etBUFSIZE ){ bufpt = zExtra = sqlite3Malloc( n ); if( bufpt==0 ){ @@ -20951,11 +23212,14 @@ SQLITE_PRIVATE void sqlite3VXPrintf( ** the output. */ width -= length; - if( width>0 && !flag_leftjustify ) sqlite3AppendSpace(pAccum, width); + if( width>0 && !flag_leftjustify ) sqlite3AppendChar(pAccum, width, ' '); sqlite3StrAccumAppend(pAccum, bufpt, length); - if( width>0 && flag_leftjustify ) sqlite3AppendSpace(pAccum, width); + if( width>0 && flag_leftjustify ) sqlite3AppendChar(pAccum, width, ' '); - if( zExtra ) sqlite3_free(zExtra); + if( zExtra ){ + sqlite3DbFree(pAccum->db, zExtra); + zExtra = 0; + } }/* End for loop over the format string */ } /* End of function */ @@ -20968,20 +23232,26 @@ SQLITE_PRIVATE void sqlite3VXPrintf( */ static int sqlite3StrAccumEnlarge(StrAccum *p, int N){ char *zNew; - assert( p->nChar+N >= p->nAlloc ); /* Only called if really needed */ + assert( p->nChar+(i64)N >= p->nAlloc ); /* Only called if really needed */ if( p->accError ){ testcase(p->accError==STRACCUM_TOOBIG); testcase(p->accError==STRACCUM_NOMEM); return 0; } - if( !p->useMalloc ){ + if( p->mxAlloc==0 ){ N = p->nAlloc - p->nChar - 1; setStrAccumError(p, STRACCUM_TOOBIG); return N; }else{ - char *zOld = (p->zText==p->zBase ? 0 : p->zText); + char *zOld = p->bMalloced ? p->zText : 0; i64 szNew = p->nChar; + assert( (p->zText==0 || p->zText==p->zBase)==(p->bMalloced==0) ); szNew += N + 1; + if( szNew+p->nChar<=p->mxAlloc ){ + /* Force exponential buffer size growth as long as it does not overflow, + ** to avoid having to call this routine too often */ + szNew += p->nChar; + } if( szNew > p->mxAlloc ){ sqlite3StrAccumReset(p); setStrAccumError(p, STRACCUM_TOOBIG); @@ -20989,15 +23259,17 @@ static int sqlite3StrAccumEnlarge(StrAccum *p, int N){ }else{ p->nAlloc = (int)szNew; } - if( p->useMalloc==1 ){ + if( p->db ){ zNew = sqlite3DbRealloc(p->db, zOld, p->nAlloc); }else{ - zNew = sqlite3_realloc(zOld, p->nAlloc); + zNew = sqlite3_realloc64(zOld, p->nAlloc); } if( zNew ){ assert( p->zText!=0 || p->nChar==0 ); - if( zOld==0 && p->nChar>0 ) memcpy(zNew, p->zText, p->nChar); + if( !p->bMalloced && p->nChar>0 ) memcpy(zNew, p->zText, p->nChar); p->zText = zNew; + p->nAlloc = sqlite3DbMallocSize(p->db, zNew); + p->bMalloced = 1; }else{ sqlite3StrAccumReset(p); setStrAccumError(p, STRACCUM_NOMEM); @@ -21008,11 +23280,15 @@ static int sqlite3StrAccumEnlarge(StrAccum *p, int N){ } /* -** Append N space characters to the given string buffer. +** Append N copies of character c to the given string buffer. */ -SQLITE_PRIVATE void sqlite3AppendSpace(StrAccum *p, int N){ - if( p->nChar+N >= p->nAlloc && (N = sqlite3StrAccumEnlarge(p, N))<=0 ) return; - while( (N--)>0 ) p->zText[p->nChar++] = ' '; +SQLITE_PRIVATE void sqlite3AppendChar(StrAccum *p, int N, char c){ + testcase( p->nChar + (i64)N > 0x7fffffff ); + if( p->nChar+(i64)N >= p->nAlloc && (N = sqlite3StrAccumEnlarge(p, N))<=0 ){ + return; + } + assert( (p->zText==p->zBase)==(p->bMalloced==0) ); + while( (N--)>0 ) p->zText[p->nChar++] = c; } /* @@ -21023,12 +23299,13 @@ SQLITE_PRIVATE void sqlite3AppendSpace(StrAccum *p, int N){ ** work (enlarging the buffer) using tail recursion, so that the ** sqlite3StrAccumAppend() routine can use fast calling semantics. */ -static void enlargeAndAppend(StrAccum *p, const char *z, int N){ +static void SQLITE_NOINLINE enlargeAndAppend(StrAccum *p, const char *z, int N){ N = sqlite3StrAccumEnlarge(p, N); if( N>0 ){ memcpy(&p->zText[p->nChar], z, N); p->nChar += N; } + assert( (p->zText==0 || p->zText==p->zBase)==(p->bMalloced==0) ); } /* @@ -21036,17 +23313,17 @@ static void enlargeAndAppend(StrAccum *p, const char *z, int N){ ** size of the memory allocation for StrAccum if necessary. */ SQLITE_PRIVATE void sqlite3StrAccumAppend(StrAccum *p, const char *z, int N){ - assert( z!=0 ); + assert( z!=0 || N==0 ); assert( p->zText!=0 || p->nChar==0 || p->accError ); assert( N>=0 ); assert( p->accError==0 || p->nAlloc==0 ); if( p->nChar+N >= p->nAlloc ){ enlargeAndAppend(p,z,N); - return; + }else{ + assert( p->zText ); + p->nChar += N; + memcpy(&p->zText[p->nChar-N], z, N); } - assert( p->zText ); - memcpy(&p->zText[p->nChar], z, N); - p->nChar += N; } /* @@ -21064,15 +23341,13 @@ SQLITE_PRIVATE void sqlite3StrAccumAppendAll(StrAccum *p, const char *z){ */ SQLITE_PRIVATE char *sqlite3StrAccumFinish(StrAccum *p){ if( p->zText ){ + assert( (p->zText==p->zBase)==(p->bMalloced==0) ); p->zText[p->nChar] = 0; - if( p->useMalloc && p->zText==p->zBase ){ - if( p->useMalloc==1 ){ - p->zText = sqlite3DbMallocRaw(p->db, p->nChar+1 ); - }else{ - p->zText = sqlite3_malloc(p->nChar+1); - } + if( p->mxAlloc>0 && p->bMalloced==0 ){ + p->zText = sqlite3DbMallocRaw(p->db, p->nChar+1 ); if( p->zText ){ memcpy(p->zText, p->zBase, p->nChar+1); + p->bMalloced = 1; }else{ setStrAccumError(p, STRACCUM_NOMEM); } @@ -21085,27 +23360,36 @@ SQLITE_PRIVATE char *sqlite3StrAccumFinish(StrAccum *p){ ** Reset an StrAccum string. Reclaim all malloced memory. */ SQLITE_PRIVATE void sqlite3StrAccumReset(StrAccum *p){ - if( p->zText!=p->zBase ){ - if( p->useMalloc==1 ){ - sqlite3DbFree(p->db, p->zText); - }else{ - sqlite3_free(p->zText); - } + assert( (p->zText==0 || p->zText==p->zBase)==(p->bMalloced==0) ); + if( p->bMalloced ){ + sqlite3DbFree(p->db, p->zText); + p->bMalloced = 0; } p->zText = 0; } /* -** Initialize a string accumulator +** Initialize a string accumulator. +** +** p: The accumulator to be initialized. +** db: Pointer to a database connection. May be NULL. Lookaside +** memory is used if not NULL. db->mallocFailed is set appropriately +** when not NULL. +** zBase: An initial buffer. May be NULL in which case the initial buffer +** is malloced. +** n: Size of zBase in bytes. If total space requirements never exceed +** n then no memory allocations ever occur. +** mx: Maximum number of bytes to accumulate. If mx==0 then no memory +** allocations will ever occur. */ -SQLITE_PRIVATE void sqlite3StrAccumInit(StrAccum *p, char *zBase, int n, int mx){ +SQLITE_PRIVATE void sqlite3StrAccumInit(StrAccum *p, sqlite3 *db, char *zBase, int n, int mx){ p->zText = p->zBase = zBase; - p->db = 0; + p->db = db; p->nChar = 0; p->nAlloc = n; p->mxAlloc = mx; - p->useMalloc = 1; p->accError = 0; + p->bMalloced = 0; } /* @@ -21117,9 +23401,8 @@ SQLITE_PRIVATE char *sqlite3VMPrintf(sqlite3 *db, const char *zFormat, va_list a char zBase[SQLITE_PRINT_BUF_SIZE]; StrAccum acc; assert( db!=0 ); - sqlite3StrAccumInit(&acc, zBase, sizeof(zBase), + sqlite3StrAccumInit(&acc, db, zBase, sizeof(zBase), db->aLimit[SQLITE_LIMIT_LENGTH]); - acc.db = db; sqlite3VXPrintf(&acc, SQLITE_PRINTF_INTERNAL, zFormat, ap); z = sqlite3StrAccumFinish(&acc); if( acc.accError==STRACCUM_NOMEM ){ @@ -21141,37 +23424,25 @@ SQLITE_PRIVATE char *sqlite3MPrintf(sqlite3 *db, const char *zFormat, ...){ return z; } -/* -** Like sqlite3MPrintf(), but call sqlite3DbFree() on zStr after formatting -** the string and before returnning. This routine is intended to be used -** to modify an existing string. For example: -** -** x = sqlite3MPrintf(db, x, "prefix %s suffix", x); -** -*/ -SQLITE_PRIVATE char *sqlite3MAppendf(sqlite3 *db, char *zStr, const char *zFormat, ...){ - va_list ap; - char *z; - va_start(ap, zFormat); - z = sqlite3VMPrintf(db, zFormat, ap); - va_end(ap); - sqlite3DbFree(db, zStr); - return z; -} - /* ** Print into memory obtained from sqlite3_malloc(). Omit the internal ** %-conversion extensions. */ -SQLITE_API char *sqlite3_vmprintf(const char *zFormat, va_list ap){ +SQLITE_API char *SQLITE_STDCALL sqlite3_vmprintf(const char *zFormat, va_list ap){ char *z; char zBase[SQLITE_PRINT_BUF_SIZE]; StrAccum acc; + +#ifdef SQLITE_ENABLE_API_ARMOR + if( zFormat==0 ){ + (void)SQLITE_MISUSE_BKPT; + return 0; + } +#endif #ifndef SQLITE_OMIT_AUTOINIT if( sqlite3_initialize() ) return 0; #endif - sqlite3StrAccumInit(&acc, zBase, sizeof(zBase), SQLITE_MAX_LENGTH); - acc.useMalloc = 2; + sqlite3StrAccumInit(&acc, 0, zBase, sizeof(zBase), SQLITE_MAX_LENGTH); sqlite3VXPrintf(&acc, 0, zFormat, ap); z = sqlite3StrAccumFinish(&acc); return z; @@ -21181,7 +23452,7 @@ SQLITE_API char *sqlite3_vmprintf(const char *zFormat, va_list ap){ ** Print into memory obtained from sqlite3_malloc()(). Omit the internal ** %-conversion extensions. */ -SQLITE_API char *sqlite3_mprintf(const char *zFormat, ...){ +SQLITE_API char *SQLITE_CDECL sqlite3_mprintf(const char *zFormat, ...){ va_list ap; char *z; #ifndef SQLITE_OMIT_AUTOINIT @@ -21206,15 +23477,21 @@ SQLITE_API char *sqlite3_mprintf(const char *zFormat, ...){ ** ** sqlite3_vsnprintf() is the varargs version. */ -SQLITE_API char *sqlite3_vsnprintf(int n, char *zBuf, const char *zFormat, va_list ap){ +SQLITE_API char *SQLITE_STDCALL sqlite3_vsnprintf(int n, char *zBuf, const char *zFormat, va_list ap){ StrAccum acc; if( n<=0 ) return zBuf; - sqlite3StrAccumInit(&acc, zBuf, n, 0); - acc.useMalloc = 0; +#ifdef SQLITE_ENABLE_API_ARMOR + if( zBuf==0 || zFormat==0 ) { + (void)SQLITE_MISUSE_BKPT; + if( zBuf ) zBuf[0] = 0; + return zBuf; + } +#endif + sqlite3StrAccumInit(&acc, 0, zBuf, n, 0); sqlite3VXPrintf(&acc, 0, zFormat, ap); return sqlite3StrAccumFinish(&acc); } -SQLITE_API char *sqlite3_snprintf(int n, char *zBuf, const char *zFormat, ...){ +SQLITE_API char *SQLITE_CDECL sqlite3_snprintf(int n, char *zBuf, const char *zFormat, ...){ char *z; va_list ap; va_start(ap,zFormat); @@ -21231,13 +23508,17 @@ SQLITE_API char *sqlite3_snprintf(int n, char *zBuf, const char *zFormat, ...){ ** sqlite3_log() must render into a static buffer. It cannot dynamically ** allocate memory because it might be called while the memory allocator ** mutex is held. +** +** sqlite3VXPrintf() might ask for *temporary* memory allocations for +** certain format characters (%q) or for very large precisions or widths. +** Care must be taken that any sqlite3_log() calls that occur while the +** memory mutex is held do not use these mechanisms. */ static void renderLogMsg(int iErrCode, const char *zFormat, va_list ap){ StrAccum acc; /* String accumulator */ char zMsg[SQLITE_PRINT_BUF_SIZE*3]; /* Complete log message */ - sqlite3StrAccumInit(&acc, zMsg, sizeof(zMsg), 0); - acc.useMalloc = 0; + sqlite3StrAccumInit(&acc, 0, zMsg, sizeof(zMsg), 0); sqlite3VXPrintf(&acc, 0, zFormat, ap); sqlite3GlobalConfig.xLog(sqlite3GlobalConfig.pLogArg, iErrCode, sqlite3StrAccumFinish(&acc)); @@ -21246,7 +23527,7 @@ static void renderLogMsg(int iErrCode, const char *zFormat, va_list ap){ /* ** Format and write a message to the log if logging is enabled. */ -SQLITE_API void sqlite3_log(int iErrCode, const char *zFormat, ...){ +SQLITE_API void SQLITE_CDECL sqlite3_log(int iErrCode, const char *zFormat, ...){ va_list ap; /* Vararg list */ if( sqlite3GlobalConfig.xLog ){ va_start(ap, zFormat); @@ -21255,7 +23536,7 @@ SQLITE_API void sqlite3_log(int iErrCode, const char *zFormat, ...){ } } -#if defined(SQLITE_DEBUG) +#if defined(SQLITE_DEBUG) || defined(SQLITE_HAVE_OS_TRACE) /* ** A version of printf() that understands %lld. Used for debugging. ** The printf() built into some versions of windows does not understand %lld @@ -21265,8 +23546,7 @@ SQLITE_PRIVATE void sqlite3DebugPrintf(const char *zFormat, ...){ va_list ap; StrAccum acc; char zBuf[500]; - sqlite3StrAccumInit(&acc, zBuf, sizeof(zBuf), 0); - acc.useMalloc = 0; + sqlite3StrAccumInit(&acc, 0, zBuf, sizeof(zBuf), 0); va_start(ap,zFormat); sqlite3VXPrintf(&acc, 0, zFormat, ap); va_end(ap); @@ -21276,8 +23556,10 @@ SQLITE_PRIVATE void sqlite3DebugPrintf(const char *zFormat, ...){ } #endif + /* -** variable-argument wrapper around sqlite3VXPrintf(). +** variable-argument wrapper around sqlite3VXPrintf(). The bFlags argument +** can contain the bit SQLITE_PRINTF_INTERNAL enable internal formats. */ SQLITE_PRIVATE void sqlite3XPrintf(StrAccum *p, u32 bFlags, const char *zFormat, ...){ va_list ap; @@ -21287,6 +23569,495 @@ SQLITE_PRIVATE void sqlite3XPrintf(StrAccum *p, u32 bFlags, const char *zFormat, } /************** End of printf.c **********************************************/ +/************** Begin file treeview.c ****************************************/ +/* +** 2015-06-08 +** +** The author disclaims copyright to this source code. In place of +** a legal notice, here is a blessing: +** +** May you do good and not evil. +** May you find forgiveness for yourself and forgive others. +** May you share freely, never taking more than you give. +** +************************************************************************* +** +** This file contains C code to implement the TreeView debugging routines. +** These routines print a parse tree to standard output for debugging and +** analysis. +** +** The interfaces in this file is only available when compiling +** with SQLITE_DEBUG. +*/ +/* #include "sqliteInt.h" */ +#ifdef SQLITE_DEBUG + +/* +** Add a new subitem to the tree. The moreToFollow flag indicates that this +** is not the last item in the tree. +*/ +static TreeView *sqlite3TreeViewPush(TreeView *p, u8 moreToFollow){ + if( p==0 ){ + p = sqlite3_malloc64( sizeof(*p) ); + if( p==0 ) return 0; + memset(p, 0, sizeof(*p)); + }else{ + p->iLevel++; + } + assert( moreToFollow==0 || moreToFollow==1 ); + if( p->iLevelbLine) ) p->bLine[p->iLevel] = moreToFollow; + return p; +} + +/* +** Finished with one layer of the tree +*/ +static void sqlite3TreeViewPop(TreeView *p){ + if( p==0 ) return; + p->iLevel--; + if( p->iLevel<0 ) sqlite3_free(p); +} + +/* +** Generate a single line of output for the tree, with a prefix that contains +** all the appropriate tree lines +*/ +static void sqlite3TreeViewLine(TreeView *p, const char *zFormat, ...){ + va_list ap; + int i; + StrAccum acc; + char zBuf[500]; + sqlite3StrAccumInit(&acc, 0, zBuf, sizeof(zBuf), 0); + if( p ){ + for(i=0; iiLevel && ibLine)-1; i++){ + sqlite3StrAccumAppend(&acc, p->bLine[i] ? "| " : " ", 4); + } + sqlite3StrAccumAppend(&acc, p->bLine[i] ? "|-- " : "'-- ", 4); + } + va_start(ap, zFormat); + sqlite3VXPrintf(&acc, 0, zFormat, ap); + va_end(ap); + if( zBuf[acc.nChar-1]!='\n' ) sqlite3StrAccumAppend(&acc, "\n", 1); + sqlite3StrAccumFinish(&acc); + fprintf(stdout,"%s", zBuf); + fflush(stdout); +} + +/* +** Shorthand for starting a new tree item that consists of a single label +*/ +static void sqlite3TreeViewItem(TreeView *p, const char *zLabel,u8 moreFollows){ + p = sqlite3TreeViewPush(p, moreFollows); + sqlite3TreeViewLine(p, "%s", zLabel); +} + +/* +** Generate a human-readable description of a WITH clause. +*/ +SQLITE_PRIVATE void sqlite3TreeViewWith(TreeView *pView, const With *pWith, u8 moreToFollow){ + int i; + if( pWith==0 ) return; + if( pWith->nCte==0 ) return; + if( pWith->pOuter ){ + sqlite3TreeViewLine(pView, "WITH (0x%p, pOuter=0x%p)",pWith,pWith->pOuter); + }else{ + sqlite3TreeViewLine(pView, "WITH (0x%p)", pWith); + } + if( pWith->nCte>0 ){ + pView = sqlite3TreeViewPush(pView, 1); + for(i=0; inCte; i++){ + StrAccum x; + char zLine[1000]; + const struct Cte *pCte = &pWith->a[i]; + sqlite3StrAccumInit(&x, 0, zLine, sizeof(zLine), 0); + sqlite3XPrintf(&x, 0, "%s", pCte->zName); + if( pCte->pCols && pCte->pCols->nExpr>0 ){ + char cSep = '('; + int j; + for(j=0; jpCols->nExpr; j++){ + sqlite3XPrintf(&x, 0, "%c%s", cSep, pCte->pCols->a[j].zName); + cSep = ','; + } + sqlite3XPrintf(&x, 0, ")"); + } + sqlite3XPrintf(&x, 0, " AS"); + sqlite3StrAccumFinish(&x); + sqlite3TreeViewItem(pView, zLine, inCte-1); + sqlite3TreeViewSelect(pView, pCte->pSelect, 0); + sqlite3TreeViewPop(pView); + } + sqlite3TreeViewPop(pView); + } +} + + +/* +** Generate a human-readable description of a the Select object. +*/ +SQLITE_PRIVATE void sqlite3TreeViewSelect(TreeView *pView, const Select *p, u8 moreToFollow){ + int n = 0; + int cnt = 0; + pView = sqlite3TreeViewPush(pView, moreToFollow); + if( p->pWith ){ + sqlite3TreeViewWith(pView, p->pWith, 1); + cnt = 1; + sqlite3TreeViewPush(pView, 1); + } + do{ + sqlite3TreeViewLine(pView, "SELECT%s%s (0x%p) selFlags=0x%x", + ((p->selFlags & SF_Distinct) ? " DISTINCT" : ""), + ((p->selFlags & SF_Aggregate) ? " agg_flag" : ""), p, p->selFlags + ); + if( cnt++ ) sqlite3TreeViewPop(pView); + if( p->pPrior ){ + n = 1000; + }else{ + n = 0; + if( p->pSrc && p->pSrc->nSrc ) n++; + if( p->pWhere ) n++; + if( p->pGroupBy ) n++; + if( p->pHaving ) n++; + if( p->pOrderBy ) n++; + if( p->pLimit ) n++; + if( p->pOffset ) n++; + } + sqlite3TreeViewExprList(pView, p->pEList, (n--)>0, "result-set"); + if( p->pSrc && p->pSrc->nSrc ){ + int i; + pView = sqlite3TreeViewPush(pView, (n--)>0); + sqlite3TreeViewLine(pView, "FROM"); + for(i=0; ipSrc->nSrc; i++){ + struct SrcList_item *pItem = &p->pSrc->a[i]; + StrAccum x; + char zLine[100]; + sqlite3StrAccumInit(&x, 0, zLine, sizeof(zLine), 0); + sqlite3XPrintf(&x, 0, "{%d,*}", pItem->iCursor); + if( pItem->zDatabase ){ + sqlite3XPrintf(&x, 0, " %s.%s", pItem->zDatabase, pItem->zName); + }else if( pItem->zName ){ + sqlite3XPrintf(&x, 0, " %s", pItem->zName); + } + if( pItem->pTab ){ + sqlite3XPrintf(&x, 0, " tabname=%Q", pItem->pTab->zName); + } + if( pItem->zAlias ){ + sqlite3XPrintf(&x, 0, " (AS %s)", pItem->zAlias); + } + if( pItem->fg.jointype & JT_LEFT ){ + sqlite3XPrintf(&x, 0, " LEFT-JOIN"); + } + sqlite3StrAccumFinish(&x); + sqlite3TreeViewItem(pView, zLine, ipSrc->nSrc-1); + if( pItem->pSelect ){ + sqlite3TreeViewSelect(pView, pItem->pSelect, 0); + } + if( pItem->fg.isTabFunc ){ + sqlite3TreeViewExprList(pView, pItem->u1.pFuncArg, 0, "func-args:"); + } + sqlite3TreeViewPop(pView); + } + sqlite3TreeViewPop(pView); + } + if( p->pWhere ){ + sqlite3TreeViewItem(pView, "WHERE", (n--)>0); + sqlite3TreeViewExpr(pView, p->pWhere, 0); + sqlite3TreeViewPop(pView); + } + if( p->pGroupBy ){ + sqlite3TreeViewExprList(pView, p->pGroupBy, (n--)>0, "GROUPBY"); + } + if( p->pHaving ){ + sqlite3TreeViewItem(pView, "HAVING", (n--)>0); + sqlite3TreeViewExpr(pView, p->pHaving, 0); + sqlite3TreeViewPop(pView); + } + if( p->pOrderBy ){ + sqlite3TreeViewExprList(pView, p->pOrderBy, (n--)>0, "ORDERBY"); + } + if( p->pLimit ){ + sqlite3TreeViewItem(pView, "LIMIT", (n--)>0); + sqlite3TreeViewExpr(pView, p->pLimit, 0); + sqlite3TreeViewPop(pView); + } + if( p->pOffset ){ + sqlite3TreeViewItem(pView, "OFFSET", (n--)>0); + sqlite3TreeViewExpr(pView, p->pOffset, 0); + sqlite3TreeViewPop(pView); + } + if( p->pPrior ){ + const char *zOp = "UNION"; + switch( p->op ){ + case TK_ALL: zOp = "UNION ALL"; break; + case TK_INTERSECT: zOp = "INTERSECT"; break; + case TK_EXCEPT: zOp = "EXCEPT"; break; + } + sqlite3TreeViewItem(pView, zOp, 1); + } + p = p->pPrior; + }while( p!=0 ); + sqlite3TreeViewPop(pView); +} + +/* +** Generate a human-readable explanation of an expression tree. +*/ +SQLITE_PRIVATE void sqlite3TreeViewExpr(TreeView *pView, const Expr *pExpr, u8 moreToFollow){ + const char *zBinOp = 0; /* Binary operator */ + const char *zUniOp = 0; /* Unary operator */ + char zFlgs[30]; + pView = sqlite3TreeViewPush(pView, moreToFollow); + if( pExpr==0 ){ + sqlite3TreeViewLine(pView, "nil"); + sqlite3TreeViewPop(pView); + return; + } + if( pExpr->flags ){ + sqlite3_snprintf(sizeof(zFlgs),zFlgs," flags=0x%x",pExpr->flags); + }else{ + zFlgs[0] = 0; + } + switch( pExpr->op ){ + case TK_AGG_COLUMN: { + sqlite3TreeViewLine(pView, "AGG{%d:%d}%s", + pExpr->iTable, pExpr->iColumn, zFlgs); + break; + } + case TK_COLUMN: { + if( pExpr->iTable<0 ){ + /* This only happens when coding check constraints */ + sqlite3TreeViewLine(pView, "COLUMN(%d)%s", pExpr->iColumn, zFlgs); + }else{ + sqlite3TreeViewLine(pView, "{%d:%d}%s", + pExpr->iTable, pExpr->iColumn, zFlgs); + } + break; + } + case TK_INTEGER: { + if( pExpr->flags & EP_IntValue ){ + sqlite3TreeViewLine(pView, "%d", pExpr->u.iValue); + }else{ + sqlite3TreeViewLine(pView, "%s", pExpr->u.zToken); + } + break; + } +#ifndef SQLITE_OMIT_FLOATING_POINT + case TK_FLOAT: { + sqlite3TreeViewLine(pView,"%s", pExpr->u.zToken); + break; + } +#endif + case TK_STRING: { + sqlite3TreeViewLine(pView,"%Q", pExpr->u.zToken); + break; + } + case TK_NULL: { + sqlite3TreeViewLine(pView,"NULL"); + break; + } +#ifndef SQLITE_OMIT_BLOB_LITERAL + case TK_BLOB: { + sqlite3TreeViewLine(pView,"%s", pExpr->u.zToken); + break; + } +#endif + case TK_VARIABLE: { + sqlite3TreeViewLine(pView,"VARIABLE(%s,%d)", + pExpr->u.zToken, pExpr->iColumn); + break; + } + case TK_REGISTER: { + sqlite3TreeViewLine(pView,"REGISTER(%d)", pExpr->iTable); + break; + } + case TK_ID: { + sqlite3TreeViewLine(pView,"ID \"%w\"", pExpr->u.zToken); + break; + } +#ifndef SQLITE_OMIT_CAST + case TK_CAST: { + /* Expressions of the form: CAST(pLeft AS token) */ + sqlite3TreeViewLine(pView,"CAST %Q", pExpr->u.zToken); + sqlite3TreeViewExpr(pView, pExpr->pLeft, 0); + break; + } +#endif /* SQLITE_OMIT_CAST */ + case TK_LT: zBinOp = "LT"; break; + case TK_LE: zBinOp = "LE"; break; + case TK_GT: zBinOp = "GT"; break; + case TK_GE: zBinOp = "GE"; break; + case TK_NE: zBinOp = "NE"; break; + case TK_EQ: zBinOp = "EQ"; break; + case TK_IS: zBinOp = "IS"; break; + case TK_ISNOT: zBinOp = "ISNOT"; break; + case TK_AND: zBinOp = "AND"; break; + case TK_OR: zBinOp = "OR"; break; + case TK_PLUS: zBinOp = "ADD"; break; + case TK_STAR: zBinOp = "MUL"; break; + case TK_MINUS: zBinOp = "SUB"; break; + case TK_REM: zBinOp = "REM"; break; + case TK_BITAND: zBinOp = "BITAND"; break; + case TK_BITOR: zBinOp = "BITOR"; break; + case TK_SLASH: zBinOp = "DIV"; break; + case TK_LSHIFT: zBinOp = "LSHIFT"; break; + case TK_RSHIFT: zBinOp = "RSHIFT"; break; + case TK_CONCAT: zBinOp = "CONCAT"; break; + case TK_DOT: zBinOp = "DOT"; break; + + case TK_UMINUS: zUniOp = "UMINUS"; break; + case TK_UPLUS: zUniOp = "UPLUS"; break; + case TK_BITNOT: zUniOp = "BITNOT"; break; + case TK_NOT: zUniOp = "NOT"; break; + case TK_ISNULL: zUniOp = "ISNULL"; break; + case TK_NOTNULL: zUniOp = "NOTNULL"; break; + + case TK_COLLATE: { + sqlite3TreeViewLine(pView, "COLLATE %Q", pExpr->u.zToken); + sqlite3TreeViewExpr(pView, pExpr->pLeft, 0); + break; + } + + case TK_AGG_FUNCTION: + case TK_FUNCTION: { + ExprList *pFarg; /* List of function arguments */ + if( ExprHasProperty(pExpr, EP_TokenOnly) ){ + pFarg = 0; + }else{ + pFarg = pExpr->x.pList; + } + if( pExpr->op==TK_AGG_FUNCTION ){ + sqlite3TreeViewLine(pView, "AGG_FUNCTION%d %Q", + pExpr->op2, pExpr->u.zToken); + }else{ + sqlite3TreeViewLine(pView, "FUNCTION %Q", pExpr->u.zToken); + } + if( pFarg ){ + sqlite3TreeViewExprList(pView, pFarg, 0, 0); + } + break; + } +#ifndef SQLITE_OMIT_SUBQUERY + case TK_EXISTS: { + sqlite3TreeViewLine(pView, "EXISTS-expr"); + sqlite3TreeViewSelect(pView, pExpr->x.pSelect, 0); + break; + } + case TK_SELECT: { + sqlite3TreeViewLine(pView, "SELECT-expr"); + sqlite3TreeViewSelect(pView, pExpr->x.pSelect, 0); + break; + } + case TK_IN: { + sqlite3TreeViewLine(pView, "IN"); + sqlite3TreeViewExpr(pView, pExpr->pLeft, 1); + if( ExprHasProperty(pExpr, EP_xIsSelect) ){ + sqlite3TreeViewSelect(pView, pExpr->x.pSelect, 0); + }else{ + sqlite3TreeViewExprList(pView, pExpr->x.pList, 0, 0); + } + break; + } +#endif /* SQLITE_OMIT_SUBQUERY */ + + /* + ** x BETWEEN y AND z + ** + ** This is equivalent to + ** + ** x>=y AND x<=z + ** + ** X is stored in pExpr->pLeft. + ** Y is stored in pExpr->pList->a[0].pExpr. + ** Z is stored in pExpr->pList->a[1].pExpr. + */ + case TK_BETWEEN: { + Expr *pX = pExpr->pLeft; + Expr *pY = pExpr->x.pList->a[0].pExpr; + Expr *pZ = pExpr->x.pList->a[1].pExpr; + sqlite3TreeViewLine(pView, "BETWEEN"); + sqlite3TreeViewExpr(pView, pX, 1); + sqlite3TreeViewExpr(pView, pY, 1); + sqlite3TreeViewExpr(pView, pZ, 0); + break; + } + case TK_TRIGGER: { + /* If the opcode is TK_TRIGGER, then the expression is a reference + ** to a column in the new.* or old.* pseudo-tables available to + ** trigger programs. In this case Expr.iTable is set to 1 for the + ** new.* pseudo-table, or 0 for the old.* pseudo-table. Expr.iColumn + ** is set to the column of the pseudo-table to read, or to -1 to + ** read the rowid field. + */ + sqlite3TreeViewLine(pView, "%s(%d)", + pExpr->iTable ? "NEW" : "OLD", pExpr->iColumn); + break; + } + case TK_CASE: { + sqlite3TreeViewLine(pView, "CASE"); + sqlite3TreeViewExpr(pView, pExpr->pLeft, 1); + sqlite3TreeViewExprList(pView, pExpr->x.pList, 0, 0); + break; + } +#ifndef SQLITE_OMIT_TRIGGER + case TK_RAISE: { + const char *zType = "unk"; + switch( pExpr->affinity ){ + case OE_Rollback: zType = "rollback"; break; + case OE_Abort: zType = "abort"; break; + case OE_Fail: zType = "fail"; break; + case OE_Ignore: zType = "ignore"; break; + } + sqlite3TreeViewLine(pView, "RAISE %s(%Q)", zType, pExpr->u.zToken); + break; + } +#endif + default: { + sqlite3TreeViewLine(pView, "op=%d", pExpr->op); + break; + } + } + if( zBinOp ){ + sqlite3TreeViewLine(pView, "%s%s", zBinOp, zFlgs); + sqlite3TreeViewExpr(pView, pExpr->pLeft, 1); + sqlite3TreeViewExpr(pView, pExpr->pRight, 0); + }else if( zUniOp ){ + sqlite3TreeViewLine(pView, "%s%s", zUniOp, zFlgs); + sqlite3TreeViewExpr(pView, pExpr->pLeft, 0); + } + sqlite3TreeViewPop(pView); +} + +/* +** Generate a human-readable explanation of an expression list. +*/ +SQLITE_PRIVATE void sqlite3TreeViewExprList( + TreeView *pView, + const ExprList *pList, + u8 moreToFollow, + const char *zLabel +){ + int i; + pView = sqlite3TreeViewPush(pView, moreToFollow); + if( zLabel==0 || zLabel[0]==0 ) zLabel = "LIST"; + if( pList==0 ){ + sqlite3TreeViewLine(pView, "%s (empty)", zLabel); + }else{ + sqlite3TreeViewLine(pView, "%s", zLabel); + for(i=0; inExpr; i++){ + int j = pList->a[i].u.x.iOrderByCol; + if( j ){ + sqlite3TreeViewPush(pView, 0); + sqlite3TreeViewLine(pView, "iOrderByCol=%d", j); + } + sqlite3TreeViewExpr(pView, pList->a[i].pExpr, inExpr-1); + if( j ) sqlite3TreeViewPop(pView); + } + } + sqlite3TreeViewPop(pView); +} + +#endif /* SQLITE_DEBUG */ + +/************** End of treeview.c ********************************************/ /************** Begin file random.c ******************************************/ /* ** 2001 September 15 @@ -21305,6 +24076,7 @@ SQLITE_PRIVATE void sqlite3XPrintf(StrAccum *p, u32 bFlags, const char *zFormat, ** Random numbers are used by some of the database backends in order ** to generate random integer keys for tables or random filenames. */ +/* #include "sqliteInt.h" */ /* All threads share a single random number generator. @@ -21319,7 +24091,7 @@ static SQLITE_WSD struct sqlite3PrngType { /* ** Return N random bytes. */ -SQLITE_API void sqlite3_randomness(int N, void *pBuf){ +SQLITE_API void SQLITE_STDCALL sqlite3_randomness(int N, void *pBuf){ unsigned char t; unsigned char *zBuf = pBuf; @@ -21337,11 +24109,19 @@ SQLITE_API void sqlite3_randomness(int N, void *pBuf){ #endif #if SQLITE_THREADSAFE - sqlite3_mutex *mutex = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_PRNG); - sqlite3_mutex_enter(mutex); + sqlite3_mutex *mutex; #endif - if( N<=0 ){ +#ifndef SQLITE_OMIT_AUTOINIT + if( sqlite3_initialize() ) return; +#endif + +#if SQLITE_THREADSAFE + mutex = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_PRNG); +#endif + + sqlite3_mutex_enter(mutex); + if( N<=0 || pBuf==0 ){ wsdPrng.isInit = 0; sqlite3_mutex_leave(mutex); return; @@ -21415,6 +24195,283 @@ SQLITE_PRIVATE void sqlite3PrngRestoreState(void){ #endif /* SQLITE_OMIT_BUILTIN_TEST */ /************** End of random.c **********************************************/ +/************** Begin file threads.c *****************************************/ +/* +** 2012 July 21 +** +** The author disclaims copyright to this source code. In place of +** a legal notice, here is a blessing: +** +** May you do good and not evil. +** May you find forgiveness for yourself and forgive others. +** May you share freely, never taking more than you give. +** +****************************************************************************** +** +** This file presents a simple cross-platform threading interface for +** use internally by SQLite. +** +** A "thread" can be created using sqlite3ThreadCreate(). This thread +** runs independently of its creator until it is joined using +** sqlite3ThreadJoin(), at which point it terminates. +** +** Threads do not have to be real. It could be that the work of the +** "thread" is done by the main thread at either the sqlite3ThreadCreate() +** or sqlite3ThreadJoin() call. This is, in fact, what happens in +** single threaded systems. Nothing in SQLite requires multiple threads. +** This interface exists so that applications that want to take advantage +** of multiple cores can do so, while also allowing applications to stay +** single-threaded if desired. +*/ +/* #include "sqliteInt.h" */ +#if SQLITE_OS_WIN +/* # include "os_win.h" */ +#endif + +#if SQLITE_MAX_WORKER_THREADS>0 + +/********************************* Unix Pthreads ****************************/ +#if SQLITE_OS_UNIX && defined(SQLITE_MUTEX_PTHREADS) && SQLITE_THREADSAFE>0 + +#define SQLITE_THREADS_IMPLEMENTED 1 /* Prevent the single-thread code below */ +/* #include */ + +/* A running thread */ +struct SQLiteThread { + pthread_t tid; /* Thread ID */ + int done; /* Set to true when thread finishes */ + void *pOut; /* Result returned by the thread */ + void *(*xTask)(void*); /* The thread routine */ + void *pIn; /* Argument to the thread */ +}; + +/* Create a new thread */ +SQLITE_PRIVATE int sqlite3ThreadCreate( + SQLiteThread **ppThread, /* OUT: Write the thread object here */ + void *(*xTask)(void*), /* Routine to run in a separate thread */ + void *pIn /* Argument passed into xTask() */ +){ + SQLiteThread *p; + int rc; + + assert( ppThread!=0 ); + assert( xTask!=0 ); + /* This routine is never used in single-threaded mode */ + assert( sqlite3GlobalConfig.bCoreMutex!=0 ); + + *ppThread = 0; + p = sqlite3Malloc(sizeof(*p)); + if( p==0 ) return SQLITE_NOMEM; + memset(p, 0, sizeof(*p)); + p->xTask = xTask; + p->pIn = pIn; + /* If the SQLITE_TESTCTRL_FAULT_INSTALL callback is registered to a + ** function that returns SQLITE_ERROR when passed the argument 200, that + ** forces worker threads to run sequentially and deterministically + ** for testing purposes. */ + if( sqlite3FaultSim(200) ){ + rc = 1; + }else{ + rc = pthread_create(&p->tid, 0, xTask, pIn); + } + if( rc ){ + p->done = 1; + p->pOut = xTask(pIn); + } + *ppThread = p; + return SQLITE_OK; +} + +/* Get the results of the thread */ +SQLITE_PRIVATE int sqlite3ThreadJoin(SQLiteThread *p, void **ppOut){ + int rc; + + assert( ppOut!=0 ); + if( NEVER(p==0) ) return SQLITE_NOMEM; + if( p->done ){ + *ppOut = p->pOut; + rc = SQLITE_OK; + }else{ + rc = pthread_join(p->tid, ppOut) ? SQLITE_ERROR : SQLITE_OK; + } + sqlite3_free(p); + return rc; +} + +#endif /* SQLITE_OS_UNIX && defined(SQLITE_MUTEX_PTHREADS) */ +/******************************** End Unix Pthreads *************************/ + + +/********************************* Win32 Threads ****************************/ +#if SQLITE_OS_WIN_THREADS + +#define SQLITE_THREADS_IMPLEMENTED 1 /* Prevent the single-thread code below */ +#include + +/* A running thread */ +struct SQLiteThread { + void *tid; /* The thread handle */ + unsigned id; /* The thread identifier */ + void *(*xTask)(void*); /* The routine to run as a thread */ + void *pIn; /* Argument to xTask */ + void *pResult; /* Result of xTask */ +}; + +/* Thread procedure Win32 compatibility shim */ +static unsigned __stdcall sqlite3ThreadProc( + void *pArg /* IN: Pointer to the SQLiteThread structure */ +){ + SQLiteThread *p = (SQLiteThread *)pArg; + + assert( p!=0 ); +#if 0 + /* + ** This assert appears to trigger spuriously on certain + ** versions of Windows, possibly due to _beginthreadex() + ** and/or CreateThread() not fully setting their thread + ** ID parameter before starting the thread. + */ + assert( p->id==GetCurrentThreadId() ); +#endif + assert( p->xTask!=0 ); + p->pResult = p->xTask(p->pIn); + + _endthreadex(0); + return 0; /* NOT REACHED */ +} + +/* Create a new thread */ +SQLITE_PRIVATE int sqlite3ThreadCreate( + SQLiteThread **ppThread, /* OUT: Write the thread object here */ + void *(*xTask)(void*), /* Routine to run in a separate thread */ + void *pIn /* Argument passed into xTask() */ +){ + SQLiteThread *p; + + assert( ppThread!=0 ); + assert( xTask!=0 ); + *ppThread = 0; + p = sqlite3Malloc(sizeof(*p)); + if( p==0 ) return SQLITE_NOMEM; + /* If the SQLITE_TESTCTRL_FAULT_INSTALL callback is registered to a + ** function that returns SQLITE_ERROR when passed the argument 200, that + ** forces worker threads to run sequentially and deterministically + ** (via the sqlite3FaultSim() term of the conditional) for testing + ** purposes. */ + if( sqlite3GlobalConfig.bCoreMutex==0 || sqlite3FaultSim(200) ){ + memset(p, 0, sizeof(*p)); + }else{ + p->xTask = xTask; + p->pIn = pIn; + p->tid = (void*)_beginthreadex(0, 0, sqlite3ThreadProc, p, 0, &p->id); + if( p->tid==0 ){ + memset(p, 0, sizeof(*p)); + } + } + if( p->xTask==0 ){ + p->id = GetCurrentThreadId(); + p->pResult = xTask(pIn); + } + *ppThread = p; + return SQLITE_OK; +} + +SQLITE_PRIVATE DWORD sqlite3Win32Wait(HANDLE hObject); /* os_win.c */ + +/* Get the results of the thread */ +SQLITE_PRIVATE int sqlite3ThreadJoin(SQLiteThread *p, void **ppOut){ + DWORD rc; + BOOL bRc; + + assert( ppOut!=0 ); + if( NEVER(p==0) ) return SQLITE_NOMEM; + if( p->xTask==0 ){ + /* assert( p->id==GetCurrentThreadId() ); */ + rc = WAIT_OBJECT_0; + assert( p->tid==0 ); + }else{ + assert( p->id!=0 && p->id!=GetCurrentThreadId() ); + rc = sqlite3Win32Wait((HANDLE)p->tid); + assert( rc!=WAIT_IO_COMPLETION ); + bRc = CloseHandle((HANDLE)p->tid); + assert( bRc ); + } + if( rc==WAIT_OBJECT_0 ) *ppOut = p->pResult; + sqlite3_free(p); + return (rc==WAIT_OBJECT_0) ? SQLITE_OK : SQLITE_ERROR; +} + +#endif /* SQLITE_OS_WIN_THREADS */ +/******************************** End Win32 Threads *************************/ + + +/********************************* Single-Threaded **************************/ +#ifndef SQLITE_THREADS_IMPLEMENTED +/* +** This implementation does not actually create a new thread. It does the +** work of the thread in the main thread, when either the thread is created +** or when it is joined +*/ + +/* A running thread */ +struct SQLiteThread { + void *(*xTask)(void*); /* The routine to run as a thread */ + void *pIn; /* Argument to xTask */ + void *pResult; /* Result of xTask */ +}; + +/* Create a new thread */ +SQLITE_PRIVATE int sqlite3ThreadCreate( + SQLiteThread **ppThread, /* OUT: Write the thread object here */ + void *(*xTask)(void*), /* Routine to run in a separate thread */ + void *pIn /* Argument passed into xTask() */ +){ + SQLiteThread *p; + + assert( ppThread!=0 ); + assert( xTask!=0 ); + *ppThread = 0; + p = sqlite3Malloc(sizeof(*p)); + if( p==0 ) return SQLITE_NOMEM; + if( (SQLITE_PTR_TO_INT(p)/17)&1 ){ + p->xTask = xTask; + p->pIn = pIn; + }else{ + p->xTask = 0; + p->pResult = xTask(pIn); + } + *ppThread = p; + return SQLITE_OK; +} + +/* Get the results of the thread */ +SQLITE_PRIVATE int sqlite3ThreadJoin(SQLiteThread *p, void **ppOut){ + + assert( ppOut!=0 ); + if( NEVER(p==0) ) return SQLITE_NOMEM; + if( p->xTask ){ + *ppOut = p->xTask(p->pIn); + }else{ + *ppOut = p->pResult; + } + sqlite3_free(p); + +#if defined(SQLITE_TEST) + { + void *pTstAlloc = sqlite3Malloc(10); + if (!pTstAlloc) return SQLITE_NOMEM; + sqlite3_free(pTstAlloc); + } +#endif + + return SQLITE_OK; +} + +#endif /* !defined(SQLITE_THREADS_IMPLEMENTED) */ +/****************************** End Single-Threaded *************************/ +#endif /* SQLITE_MAX_WORKER_THREADS>0 */ + +/************** End of threads.c *********************************************/ /************** Begin file utf.c *********************************************/ /* ** 2004 April 13 @@ -21451,15 +24508,17 @@ SQLITE_PRIVATE void sqlite3PrngRestoreState(void){ ** 0xfe 0xff big-endian utf-16 follows ** */ +/* #include "sqliteInt.h" */ /* #include */ +/* #include "vdbeInt.h" */ -#ifndef SQLITE_AMALGAMATION +#if !defined(SQLITE_AMALGAMATION) && SQLITE_BYTEORDER==0 /* ** The following constant value is used by the SQLITE_BIGENDIAN and ** SQLITE_LITTLEENDIAN macros. */ SQLITE_PRIVATE const int sqlite3one = 1; -#endif /* SQLITE_AMALGAMATION */ +#endif /* SQLITE_AMALGAMATION && SQLITE_BYTEORDER==0 */ /* ** This lookup table is used to help decode the first byte of @@ -21564,8 +24623,8 @@ static const unsigned char sqlite3Utf8Trans1[] = { ** and rendered as themselves even though they are technically ** invalid characters. ** -** * This routine accepts an infinite number of different UTF8 encodings -** for unicode values 0x80 and greater. It do not change over-length +** * This routine accepts over-length UTF8 encodings +** for unicode values 0x80 and greater. It does not change over-length ** encodings to 0xfffd as some systems recommend. */ #define READ_UTF8(zIn, zTerm, c) \ @@ -21615,7 +24674,7 @@ SQLITE_PRIVATE u32 sqlite3Utf8Read( ** desiredEnc. It is an error if the string is already of the desired ** encoding, or if *pMem does not contain a string value. */ -SQLITE_PRIVATE int sqlite3VdbeMemTranslate(Mem *pMem, u8 desiredEnc){ +SQLITE_PRIVATE SQLITE_NOINLINE int sqlite3VdbeMemTranslate(Mem *pMem, u8 desiredEnc){ int len; /* Maximum length of output string in bytes */ unsigned char *zOut; /* Output buffer */ unsigned char *zIn; /* Input iterator */ @@ -21730,12 +24789,13 @@ SQLITE_PRIVATE int sqlite3VdbeMemTranslate(Mem *pMem, u8 desiredEnc){ *z = 0; assert( (pMem->n+(desiredEnc==SQLITE_UTF8?1:2))<=len ); + c = pMem->flags; sqlite3VdbeMemRelease(pMem); - pMem->flags &= ~(MEM_Static|MEM_Dyn|MEM_Ephem); + pMem->flags = MEM_Str|MEM_Term|(c&MEM_AffMask); pMem->enc = desiredEnc; - pMem->flags |= (MEM_Term); pMem->z = (char*)zOut; pMem->zMalloc = pMem->z; + pMem->szMalloc = sqlite3DbMallocSize(pMem->db, pMem->z); translate_out: #if defined(TRANSLATE_TRACE) && defined(SQLITE_DEBUG) @@ -21963,8 +25023,9 @@ SQLITE_PRIVATE void sqlite3UtfSelfTest(void){ ** strings, and stuff like that. ** */ +/* #include "sqliteInt.h" */ /* #include */ -#ifdef SQLITE_HAVE_ISNAN +#if HAVE_ISNAN || SQLITE_HAVE_ISNAN # include #endif @@ -22005,7 +25066,7 @@ SQLITE_PRIVATE int sqlite3FaultSim(int iTest){ */ SQLITE_PRIVATE int sqlite3IsNaN(double x){ int rc; /* The value return */ -#if !defined(SQLITE_HAVE_ISNAN) +#if !SQLITE_HAVE_ISNAN && !HAVE_ISNAN /* ** Systems that support the isnan() library function should probably ** make use of it by compiling with -DSQLITE_HAVE_ISNAN. But we have @@ -22035,9 +25096,9 @@ SQLITE_PRIVATE int sqlite3IsNaN(double x){ volatile double y = x; volatile double z = y; rc = (y!=z); -#else /* if defined(SQLITE_HAVE_ISNAN) */ +#else /* if HAVE_ISNAN */ rc = isnan(x); -#endif /* SQLITE_HAVE_ISNAN */ +#endif /* HAVE_ISNAN */ testcase( rc ); return rc; } @@ -22052,10 +25113,17 @@ SQLITE_PRIVATE int sqlite3IsNaN(double x){ ** than 1GiB) the value returned might be less than the true string length. */ SQLITE_PRIVATE int sqlite3Strlen30(const char *z){ - const char *z2 = z; if( z==0 ) return 0; - while( *z2 ){ z2++; } - return 0x3fffffff & (int)(z2 - z); + return 0x3fffffff & (int)strlen(z); +} + +/* +** Set the current error code to err_code and clear any prior error message. +*/ +SQLITE_PRIVATE void sqlite3Error(sqlite3 *db, int err_code){ + assert( db!=0 ); + db->errCode = err_code; + if( db->pErr ) sqlite3ValueSetNull(db->pErr); } /* @@ -22079,18 +25147,18 @@ SQLITE_PRIVATE int sqlite3Strlen30(const char *z){ ** should be called with err_code set to SQLITE_OK and zFormat set ** to NULL. */ -SQLITE_PRIVATE void sqlite3Error(sqlite3 *db, int err_code, const char *zFormat, ...){ +SQLITE_PRIVATE void sqlite3ErrorWithMsg(sqlite3 *db, int err_code, const char *zFormat, ...){ assert( db!=0 ); db->errCode = err_code; - if( zFormat && (db->pErr || (db->pErr = sqlite3ValueNew(db))!=0) ){ + if( zFormat==0 ){ + sqlite3Error(db, err_code); + }else if( db->pErr || (db->pErr = sqlite3ValueNew(db))!=0 ){ char *z; va_list ap; va_start(ap, zFormat); z = sqlite3VMPrintf(db, zFormat, ap); va_end(ap); sqlite3ValueSetStr(db->pErr, -1, z, SQLITE_UTF8, SQLITE_DYNAMIC); - }else if( db->pErr ){ - sqlite3ValueSetNull(db->pErr); } } @@ -22104,12 +25172,12 @@ SQLITE_PRIVATE void sqlite3Error(sqlite3 *db, int err_code, const char *zFormat, ** %T Insert a token ** %S Insert the first element of a SrcList ** -** This function should be used to report any error that occurs whilst +** This function should be used to report any error that occurs while ** compiling an SQL statement (i.e. within sqlite3_prepare()). The ** last thing the sqlite3_prepare() function does is copy the error ** stored by this function into the database handle using sqlite3Error(). -** Function sqlite3Error() should be used during statement execution -** (sqlite3_step() etc.). +** Functions sqlite3Error() or sqlite3ErrorWithMsg() should be used +** during statement execution (sqlite3_step() etc.). */ SQLITE_PRIVATE void sqlite3ErrorMsg(Parse *pParse, const char *zFormat, ...){ char *zMsg; @@ -22142,7 +25210,7 @@ SQLITE_PRIVATE void sqlite3ErrorMsg(Parse *pParse, const char *zFormat, ...){ ** occur. ** ** 2002-Feb-14: This routine is extended to remove MS-Access style -** brackets from around identifers. For example: "[a-b-c]" becomes +** brackets from around identifiers. For example: "[a-b-c]" becomes ** "a-b-c". */ SQLITE_PRIVATE int sqlite3Dequote(char *z){ @@ -22187,15 +25255,25 @@ SQLITE_PRIVATE int sqlite3Dequote(char *z){ ** case-independent fashion, using the same definition of "case ** independence" that SQLite uses internally when comparing identifiers. */ -SQLITE_API int sqlite3_stricmp(const char *zLeft, const char *zRight){ +SQLITE_API int SQLITE_STDCALL sqlite3_stricmp(const char *zLeft, const char *zRight){ register unsigned char *a, *b; + if( zLeft==0 ){ + return zRight ? -1 : 0; + }else if( zRight==0 ){ + return 1; + } a = (unsigned char *)zLeft; b = (unsigned char *)zRight; while( *a!=0 && UpperToLower[*a]==UpperToLower[*b]){ a++; b++; } return UpperToLower[*a] - UpperToLower[*b]; } -SQLITE_API int sqlite3_strnicmp(const char *zLeft, const char *zRight, int N){ +SQLITE_API int SQLITE_STDCALL sqlite3_strnicmp(const char *zLeft, const char *zRight, int N){ register unsigned char *a, *b; + if( zLeft==0 ){ + return zRight ? -1 : 0; + }else if( zRight==0 ){ + return 1; + } a = (unsigned char *)zLeft; b = (unsigned char *)zRight; while( N-- > 0 && *a!=0 && UpperToLower[*a]==UpperToLower[*b]){ a++; b++; } @@ -22422,9 +25500,9 @@ static int compare2pow63(const char *zNum, int incr){ return c; } - /* -** Convert zNum to a 64-bit signed integer. +** Convert zNum to a 64-bit signed integer. zNum must be decimal. This +** routine does *not* accept hexadecimal notation. ** ** If the zNum value is representable as a 64-bit twos-complement ** integer, then write that value into *pNum and return 0. @@ -22485,7 +25563,8 @@ SQLITE_PRIVATE int sqlite3Atoi64(const char *zNum, i64 *pNum, int length, u8 enc testcase( i==18 ); testcase( i==19 ); testcase( i==20 ); - if( (c!=0 && &zNum[i]19*incr || nonNum ){ + if( (c!=0 && &zNum[i]19*incr || nonNum ){ /* zNum is empty or contains non-numeric text or is longer ** than 19 digits (thus guaranteeing that it is too large) */ return 1; @@ -22512,10 +25591,44 @@ SQLITE_PRIVATE int sqlite3Atoi64(const char *zNum, i64 *pNum, int length, u8 enc } } +/* +** Transform a UTF-8 integer literal, in either decimal or hexadecimal, +** into a 64-bit signed integer. This routine accepts hexadecimal literals, +** whereas sqlite3Atoi64() does not. +** +** Returns: +** +** 0 Successful transformation. Fits in a 64-bit signed integer. +** 1 Integer too large for a 64-bit signed integer or is malformed +** 2 Special case of 9223372036854775808 +*/ +SQLITE_PRIVATE int sqlite3DecOrHexToI64(const char *z, i64 *pOut){ +#ifndef SQLITE_OMIT_HEX_INTEGER + if( z[0]=='0' + && (z[1]=='x' || z[1]=='X') + && sqlite3Isxdigit(z[2]) + ){ + u64 u = 0; + int i, k; + for(i=2; z[i]=='0'; i++){} + for(k=i; sqlite3Isxdigit(z[k]); k++){ + u = u*16 + sqlite3HexToInt(z[k]); + } + memcpy(pOut, &u, 8); + return (z[k]==0 && k-i<=16) ? 0 : 1; + }else +#endif /* SQLITE_OMIT_HEX_INTEGER */ + { + return sqlite3Atoi64(z, pOut, sqlite3Strlen30(z), SQLITE_UTF8); + } +} + /* ** If zNum represents an integer that will fit in 32-bits, then set ** *pValue to that integer and return true. Otherwise return false. ** +** This routine accepts both decimal and hexadecimal notation for integers. +** ** Any non-numeric characters that following zNum are ignored. ** This is different from sqlite3Atoi64() which requires the ** input number to be zero-terminated. @@ -22530,6 +25643,25 @@ SQLITE_PRIVATE int sqlite3GetInt32(const char *zNum, int *pValue){ }else if( zNum[0]=='+' ){ zNum++; } +#ifndef SQLITE_OMIT_HEX_INTEGER + else if( zNum[0]=='0' + && (zNum[1]=='x' || zNum[1]=='X') + && sqlite3Isxdigit(zNum[2]) + ){ + u32 u = 0; + zNum += 2; + while( zNum[0]=='0' ) zNum++; + for(i=0; sqlite3Isxdigit(zNum[i]) && i<8; i++){ + u = u*16 + sqlite3HexToInt(zNum[i]); + } + if( (u&0x80000000)==0 && sqlite3Isxdigit(zNum[i])==0 ){ + memcpy(pValue, &u, 4); + return 1; + }else{ + return 0; + } + } +#endif while( zNum[0]=='0' ) zNum++; for(i=0; i<11 && (c = zNum[i] - '0')>=0 && c<=9; i++){ v = v*10 + c; @@ -22594,7 +25726,7 @@ SQLITE_PRIVATE int sqlite3Atoi(const char *z){ ** bit clear. Except, if we get to the 9th byte, it stores the full ** 8 bits and is the last byte. */ -SQLITE_PRIVATE int sqlite3PutVarint(unsigned char *p, u64 v){ +static int SQLITE_NOINLINE putVarint64(unsigned char *p, u64 v){ int i, j, n; u8 buf[10]; if( v & (((u64)0xff000000)<<32) ){ @@ -22618,28 +25750,17 @@ SQLITE_PRIVATE int sqlite3PutVarint(unsigned char *p, u64 v){ } return n; } - -/* -** This routine is a faster version of sqlite3PutVarint() that only -** works for 32-bit positive integers and which is optimized for -** the common case of small integers. A MACRO version, putVarint32, -** is provided which inlines the single-byte case. All code should use -** the MACRO version as this function assumes the single-byte case has -** already been handled. -*/ -SQLITE_PRIVATE int sqlite3PutVarint32(unsigned char *p, u32 v){ -#ifndef putVarint32 - if( (v & ~0x7f)==0 ){ - p[0] = v; +SQLITE_PRIVATE int sqlite3PutVarint(unsigned char *p, u64 v){ + if( v<=0x7f ){ + p[0] = v&0x7f; return 1; } -#endif - if( (v & ~0x3fff)==0 ){ - p[0] = (u8)((v>>7) | 0x80); - p[1] = (u8)(v & 0x7f); + if( v<=0x3fff ){ + p[0] = ((v>>7)&0x7f)|0x80; + p[1] = v&0x7f; return 2; } - return sqlite3PutVarint(p, v); + return putVarint64(p,v); } /* @@ -22732,7 +25853,8 @@ SQLITE_PRIVATE u8 sqlite3GetVarint(const unsigned char *p, u64 *v){ /* a: p0<<28 | p2<<14 | p4 (unmasked) */ if (!(a&0x80)) { - /* we can skip these cause they were (effectively) done above in calc'ing s */ + /* we can skip these cause they were (effectively) done above + ** while calculating s */ /* a &= (0x7f<<28)|(0x7f<<14)|(0x7f); */ /* b &= (0x7f<<14)|(0x7f); */ b = b<<7; @@ -22953,11 +26075,8 @@ SQLITE_PRIVATE u8 sqlite3GetVarint32(const unsigned char *p, u32 *v){ ** 64-bit integer. */ SQLITE_PRIVATE int sqlite3VarintLen(u64 v){ - int i = 0; - do{ - i++; - v >>= 7; - }while( v!=0 && ALWAYS(i<9) ); + int i; + for(i=1; (v >>= 7)!=0; i++){ assert( i<9 ); } return i; } @@ -22966,14 +26085,40 @@ SQLITE_PRIVATE int sqlite3VarintLen(u64 v){ ** Read or write a four-byte big-endian integer value. */ SQLITE_PRIVATE u32 sqlite3Get4byte(const u8 *p){ +#if SQLITE_BYTEORDER==4321 + u32 x; + memcpy(&x,p,4); + return x; +#elif SQLITE_BYTEORDER==1234 && !defined(SQLITE_DISABLE_INTRINSIC) \ + && defined(__GNUC__) && GCC_VERSION>=4003000 + u32 x; + memcpy(&x,p,4); + return __builtin_bswap32(x); +#elif SQLITE_BYTEORDER==1234 && !defined(SQLITE_DISABLE_INTRINSIC) \ + && defined(_MSC_VER) && _MSC_VER>=1300 + u32 x; + memcpy(&x,p,4); + return _byteswap_ulong(x); +#else testcase( p[0]&0x80 ); return ((unsigned)p[0]<<24) | (p[1]<<16) | (p[2]<<8) | p[3]; +#endif } SQLITE_PRIVATE void sqlite3Put4byte(unsigned char *p, u32 v){ +#if SQLITE_BYTEORDER==4321 + memcpy(p,&v,4); +#elif SQLITE_BYTEORDER==1234 && defined(__GNUC__) && GCC_VERSION>=4003000 + u32 x = __builtin_bswap32(v); + memcpy(p,&x,4); +#elif SQLITE_BYTEORDER==1234 && defined(_MSC_VER) && _MSC_VER>=1300 + u32 x = _byteswap_ulong(v); + memcpy(p,&x,4); +#else p[0] = (u8)(v>>24); p[1] = (u8)(v>>16); p[2] = (u8)(v>>8); p[3] = (u8)v; +#endif } @@ -23276,6 +26421,7 @@ SQLITE_PRIVATE u64 sqlite3LogEstToInt(LogEst x){ ** This is the implementation of generic hash-tables ** used in SQLite. */ +/* #include "sqliteInt.h" */ /* #include */ /* Turn bulk memory into a hash table object by initializing the @@ -23315,12 +26461,11 @@ SQLITE_PRIVATE void sqlite3HashClear(Hash *pH){ /* ** The hashing function. */ -static unsigned int strHash(const char *z, int nKey){ +static unsigned int strHash(const char *z){ unsigned int h = 0; - assert( nKey>=0 ); - while( nKey > 0 ){ - h = (h<<3) ^ h ^ sqlite3UpperToLower[(unsigned char)*z++]; - nKey--; + unsigned char c; + while( (c = (unsigned char)*z++)!=0 ){ + h = (h<<3) ^ h ^ sqlite3UpperToLower[c]; } return h; } @@ -23392,7 +26537,7 @@ static int rehash(Hash *pH, unsigned int new_size){ pH->htsize = new_size = sqlite3MallocSize(new_ht)/sizeof(struct _ht); memset(new_ht, 0, new_size*sizeof(struct _ht)); for(elem=pH->first, pH->first=0; elem; elem = next_elem){ - unsigned int h = strHash(elem->pKey, elem->nKey) % new_size; + unsigned int h = strHash(elem->pKey) % new_size; next_elem = elem->next; insertElement(pH, &new_ht[h], elem); } @@ -23400,28 +26545,33 @@ static int rehash(Hash *pH, unsigned int new_size){ } /* This function (for internal use only) locates an element in an -** hash table that matches the given key. The hash for this key has -** already been computed and is passed as the 4th parameter. +** hash table that matches the given key. The hash for this key is +** also computed and returned in the *pH parameter. */ -static HashElem *findElementGivenHash( +static HashElem *findElementWithHash( const Hash *pH, /* The pH to be searched */ const char *pKey, /* The key we are searching for */ - int nKey, /* Bytes in key (not counting zero terminator) */ - unsigned int h /* The hash for this key. */ + unsigned int *pHash /* Write the hash value here */ ){ HashElem *elem; /* Used to loop thru the element list */ int count; /* Number of elements left to test */ + unsigned int h; /* The computed hash */ if( pH->ht ){ - struct _ht *pEntry = &pH->ht[h]; + struct _ht *pEntry; + h = strHash(pKey) % pH->htsize; + pEntry = &pH->ht[h]; elem = pEntry->chain; count = pEntry->count; }else{ + h = 0; elem = pH->first; count = pH->count; } - while( count-- && ALWAYS(elem) ){ - if( elem->nKey==nKey && sqlite3StrNICmp(elem->pKey,pKey,nKey)==0 ){ + *pHash = h; + while( count-- ){ + assert( elem!=0 ); + if( sqlite3StrICmp(elem->pKey,pKey)==0 ){ return elem; } elem = elem->next; @@ -23464,26 +26614,20 @@ static void removeElementGivenHash( } /* Attempt to locate an element of the hash table pH with a key -** that matches pKey,nKey. Return the data for this element if it is +** that matches pKey. Return the data for this element if it is ** found, or NULL if there is no match. */ -SQLITE_PRIVATE void *sqlite3HashFind(const Hash *pH, const char *pKey, int nKey){ +SQLITE_PRIVATE void *sqlite3HashFind(const Hash *pH, const char *pKey){ HashElem *elem; /* The element that matches key */ unsigned int h; /* A hash on key */ assert( pH!=0 ); assert( pKey!=0 ); - assert( nKey>=0 ); - if( pH->ht ){ - h = strHash(pKey, nKey) % pH->htsize; - }else{ - h = 0; - } - elem = findElementGivenHash(pH, pKey, nKey, h); + elem = findElementWithHash(pH, pKey, &h); return elem ? elem->data : 0; } -/* Insert an element into the hash table pH. The key is pKey,nKey +/* Insert an element into the hash table pH. The key is pKey ** and the data is "data". ** ** If no element exists with a matching key, then a new @@ -23497,20 +26641,14 @@ SQLITE_PRIVATE void *sqlite3HashFind(const Hash *pH, const char *pKey, int nKey) ** If the "data" parameter to this function is NULL, then the ** element corresponding to "key" is removed from the hash table. */ -SQLITE_PRIVATE void *sqlite3HashInsert(Hash *pH, const char *pKey, int nKey, void *data){ +SQLITE_PRIVATE void *sqlite3HashInsert(Hash *pH, const char *pKey, void *data){ unsigned int h; /* the hash of the key modulo hash table size */ HashElem *elem; /* Used to loop thru the element list */ HashElem *new_elem; /* New element added to the pH */ assert( pH!=0 ); assert( pKey!=0 ); - assert( nKey>=0 ); - if( pH->htsize ){ - h = strHash(pKey, nKey) % pH->htsize; - }else{ - h = 0; - } - elem = findElementGivenHash(pH,pKey,nKey,h); + elem = findElementWithHash(pH,pKey,&h); if( elem ){ void *old_data = elem->data; if( data==0 ){ @@ -23518,7 +26656,6 @@ SQLITE_PRIVATE void *sqlite3HashInsert(Hash *pH, const char *pKey, int nKey, voi }else{ elem->data = data; elem->pKey = pKey; - assert(nKey==elem->nKey); } return old_data; } @@ -23526,28 +26663,25 @@ SQLITE_PRIVATE void *sqlite3HashInsert(Hash *pH, const char *pKey, int nKey, voi new_elem = (HashElem*)sqlite3Malloc( sizeof(HashElem) ); if( new_elem==0 ) return data; new_elem->pKey = pKey; - new_elem->nKey = nKey; new_elem->data = data; pH->count++; if( pH->count>=10 && pH->count > 2*pH->htsize ){ if( rehash(pH, pH->count*2) ){ assert( pH->htsize>0 ); - h = strHash(pKey, nKey) % pH->htsize; + h = strHash(pKey) % pH->htsize; } } - if( pH->ht ){ - insertElement(pH, &pH->ht[h], new_elem); - }else{ - insertElement(pH, 0, new_elem); - } + insertElement(pH, pH->ht ? &pH->ht[h] : 0, new_elem); return 0; } /************** End of hash.c ************************************************/ /************** Begin file opcodes.c *****************************************/ /* Automatically generated. Do not edit */ -/* See the mkopcodec.awk script for details. */ -#if !defined(SQLITE_OMIT_EXPLAIN) || defined(VDBE_PROFILE) || defined(SQLITE_DEBUG) +/* See the tool/mkopcodec.tcl script for details. */ +#if !defined(SQLITE_OMIT_EXPLAIN) \ + || defined(VDBE_PROFILE) \ + || defined(SQLITE_DEBUG) #if defined(SQLITE_ENABLE_EXPLAIN_COMMENTS) || defined(SQLITE_DEBUG) # define OpHelp(X) "\0" X #else @@ -23555,163 +26689,168 @@ SQLITE_PRIVATE void *sqlite3HashInsert(Hash *pH, const char *pKey, int nKey, voi #endif SQLITE_PRIVATE const char *sqlite3OpcodeName(int i){ static const char *const azName[] = { "?", - /* 1 */ "Function" OpHelp("r[P3]=func(r[P2@P5])"), - /* 2 */ "Savepoint" OpHelp(""), - /* 3 */ "AutoCommit" OpHelp(""), - /* 4 */ "Transaction" OpHelp(""), - /* 5 */ "SorterNext" OpHelp(""), - /* 6 */ "PrevIfOpen" OpHelp(""), - /* 7 */ "NextIfOpen" OpHelp(""), - /* 8 */ "Prev" OpHelp(""), - /* 9 */ "Next" OpHelp(""), - /* 10 */ "AggStep" OpHelp("accum=r[P3] step(r[P2@P5])"), - /* 11 */ "Checkpoint" OpHelp(""), - /* 12 */ "JournalMode" OpHelp(""), - /* 13 */ "Vacuum" OpHelp(""), - /* 14 */ "VFilter" OpHelp("iplan=r[P3] zplan='P4'"), - /* 15 */ "VUpdate" OpHelp("data=r[P3@P2]"), - /* 16 */ "Goto" OpHelp(""), - /* 17 */ "Gosub" OpHelp(""), - /* 18 */ "Return" OpHelp(""), - /* 19 */ "Not" OpHelp("r[P2]= !r[P1]"), - /* 20 */ "InitCoroutine" OpHelp(""), - /* 21 */ "EndCoroutine" OpHelp(""), - /* 22 */ "Yield" OpHelp(""), - /* 23 */ "HaltIfNull" OpHelp("if r[P3]=null halt"), - /* 24 */ "Halt" OpHelp(""), - /* 25 */ "Integer" OpHelp("r[P2]=P1"), - /* 26 */ "Int64" OpHelp("r[P2]=P4"), - /* 27 */ "String" OpHelp("r[P2]='P4' (len=P1)"), - /* 28 */ "Null" OpHelp("r[P2..P3]=NULL"), - /* 29 */ "SoftNull" OpHelp("r[P1]=NULL"), - /* 30 */ "Blob" OpHelp("r[P2]=P4 (len=P1)"), - /* 31 */ "Variable" OpHelp("r[P2]=parameter(P1,P4)"), - /* 32 */ "Move" OpHelp("r[P2@P3]=r[P1@P3]"), - /* 33 */ "Copy" OpHelp("r[P2@P3+1]=r[P1@P3+1]"), - /* 34 */ "SCopy" OpHelp("r[P2]=r[P1]"), - /* 35 */ "ResultRow" OpHelp("output=r[P1@P2]"), - /* 36 */ "CollSeq" OpHelp(""), - /* 37 */ "AddImm" OpHelp("r[P1]=r[P1]+P2"), - /* 38 */ "MustBeInt" OpHelp(""), - /* 39 */ "RealAffinity" OpHelp(""), - /* 40 */ "Permutation" OpHelp(""), - /* 41 */ "Compare" OpHelp("r[P1@P3] <-> r[P2@P3]"), - /* 42 */ "Jump" OpHelp(""), - /* 43 */ "Once" OpHelp(""), - /* 44 */ "If" OpHelp(""), - /* 45 */ "IfNot" OpHelp(""), - /* 46 */ "Column" OpHelp("r[P3]=PX"), - /* 47 */ "Affinity" OpHelp("affinity(r[P1@P2])"), - /* 48 */ "MakeRecord" OpHelp("r[P3]=mkrec(r[P1@P2])"), - /* 49 */ "Count" OpHelp("r[P2]=count()"), - /* 50 */ "ReadCookie" OpHelp(""), - /* 51 */ "SetCookie" OpHelp(""), - /* 52 */ "OpenRead" OpHelp("root=P2 iDb=P3"), - /* 53 */ "OpenWrite" OpHelp("root=P2 iDb=P3"), - /* 54 */ "OpenAutoindex" OpHelp("nColumn=P2"), - /* 55 */ "OpenEphemeral" OpHelp("nColumn=P2"), - /* 56 */ "SorterOpen" OpHelp(""), - /* 57 */ "OpenPseudo" OpHelp("P3 columns in r[P2]"), - /* 58 */ "Close" OpHelp(""), - /* 59 */ "SeekLT" OpHelp(""), - /* 60 */ "SeekLE" OpHelp(""), - /* 61 */ "SeekGE" OpHelp(""), - /* 62 */ "SeekGT" OpHelp(""), - /* 63 */ "Seek" OpHelp("intkey=r[P2]"), - /* 64 */ "NoConflict" OpHelp("key=r[P3@P4]"), - /* 65 */ "NotFound" OpHelp("key=r[P3@P4]"), - /* 66 */ "Found" OpHelp("key=r[P3@P4]"), - /* 67 */ "NotExists" OpHelp("intkey=r[P3]"), - /* 68 */ "Sequence" OpHelp("r[P2]=cursor[P1].ctr++"), - /* 69 */ "NewRowid" OpHelp("r[P2]=rowid"), - /* 70 */ "Insert" OpHelp("intkey=r[P3] data=r[P2]"), - /* 71 */ "Or" OpHelp("r[P3]=(r[P1] || r[P2])"), - /* 72 */ "And" OpHelp("r[P3]=(r[P1] && r[P2])"), - /* 73 */ "InsertInt" OpHelp("intkey=P3 data=r[P2]"), - /* 74 */ "Delete" OpHelp(""), - /* 75 */ "ResetCount" OpHelp(""), - /* 76 */ "IsNull" OpHelp("if r[P1]==NULL goto P2"), - /* 77 */ "NotNull" OpHelp("if r[P1]!=NULL goto P2"), - /* 78 */ "Ne" OpHelp("if r[P1]!=r[P3] goto P2"), - /* 79 */ "Eq" OpHelp("if r[P1]==r[P3] goto P2"), - /* 80 */ "Gt" OpHelp("if r[P1]>r[P3] goto P2"), - /* 81 */ "Le" OpHelp("if r[P1]<=r[P3] goto P2"), - /* 82 */ "Lt" OpHelp("if r[P1]=r[P3] goto P2"), - /* 84 */ "SorterCompare" OpHelp("if key(P1)!=rtrim(r[P3],P4) goto P2"), - /* 85 */ "BitAnd" OpHelp("r[P3]=r[P1]&r[P2]"), - /* 86 */ "BitOr" OpHelp("r[P3]=r[P1]|r[P2]"), - /* 87 */ "ShiftLeft" OpHelp("r[P3]=r[P2]<>r[P1]"), - /* 89 */ "Add" OpHelp("r[P3]=r[P1]+r[P2]"), - /* 90 */ "Subtract" OpHelp("r[P3]=r[P2]-r[P1]"), - /* 91 */ "Multiply" OpHelp("r[P3]=r[P1]*r[P2]"), - /* 92 */ "Divide" OpHelp("r[P3]=r[P2]/r[P1]"), - /* 93 */ "Remainder" OpHelp("r[P3]=r[P2]%r[P1]"), - /* 94 */ "Concat" OpHelp("r[P3]=r[P2]+r[P1]"), - /* 95 */ "SorterData" OpHelp("r[P2]=data"), - /* 96 */ "BitNot" OpHelp("r[P1]= ~r[P1]"), - /* 97 */ "String8" OpHelp("r[P2]='P4'"), - /* 98 */ "RowKey" OpHelp("r[P2]=key"), - /* 99 */ "RowData" OpHelp("r[P2]=data"), - /* 100 */ "Rowid" OpHelp("r[P2]=rowid"), - /* 101 */ "NullRow" OpHelp(""), - /* 102 */ "Last" OpHelp(""), - /* 103 */ "SorterSort" OpHelp(""), - /* 104 */ "Sort" OpHelp(""), - /* 105 */ "Rewind" OpHelp(""), - /* 106 */ "SorterInsert" OpHelp(""), - /* 107 */ "IdxInsert" OpHelp("key=r[P2]"), - /* 108 */ "IdxDelete" OpHelp("key=r[P2@P3]"), - /* 109 */ "IdxRowid" OpHelp("r[P2]=rowid"), - /* 110 */ "IdxLE" OpHelp("key=r[P3@P4]"), - /* 111 */ "IdxGT" OpHelp("key=r[P3@P4]"), - /* 112 */ "IdxLT" OpHelp("key=r[P3@P4]"), - /* 113 */ "IdxGE" OpHelp("key=r[P3@P4]"), - /* 114 */ "Destroy" OpHelp(""), - /* 115 */ "Clear" OpHelp(""), - /* 116 */ "ResetSorter" OpHelp(""), - /* 117 */ "CreateIndex" OpHelp("r[P2]=root iDb=P1"), - /* 118 */ "CreateTable" OpHelp("r[P2]=root iDb=P1"), - /* 119 */ "ParseSchema" OpHelp(""), - /* 120 */ "LoadAnalysis" OpHelp(""), - /* 121 */ "DropTable" OpHelp(""), - /* 122 */ "DropIndex" OpHelp(""), - /* 123 */ "DropTrigger" OpHelp(""), - /* 124 */ "IntegrityCk" OpHelp(""), - /* 125 */ "RowSetAdd" OpHelp("rowset(P1)=r[P2]"), - /* 126 */ "RowSetRead" OpHelp("r[P3]=rowset(P1)"), - /* 127 */ "RowSetTest" OpHelp("if r[P3] in rowset(P1) goto P2"), - /* 128 */ "Program" OpHelp(""), - /* 129 */ "Param" OpHelp(""), - /* 130 */ "FkCounter" OpHelp("fkctr[P1]+=P2"), - /* 131 */ "FkIfZero" OpHelp("if fkctr[P1]==0 goto P2"), - /* 132 */ "MemMax" OpHelp("r[P1]=max(r[P1],r[P2])"), - /* 133 */ "Real" OpHelp("r[P2]=P4"), - /* 134 */ "IfPos" OpHelp("if r[P1]>0 goto P2"), - /* 135 */ "IfNeg" OpHelp("if r[P1]<0 goto P2"), - /* 136 */ "IfZero" OpHelp("r[P1]+=P3, if r[P1]==0 goto P2"), - /* 137 */ "AggFinal" OpHelp("accum=r[P1] N=P2"), - /* 138 */ "IncrVacuum" OpHelp(""), - /* 139 */ "Expire" OpHelp(""), - /* 140 */ "TableLock" OpHelp("iDb=P1 root=P2 write=P3"), - /* 141 */ "VBegin" OpHelp(""), - /* 142 */ "VCreate" OpHelp(""), - /* 143 */ "ToText" OpHelp(""), - /* 144 */ "ToBlob" OpHelp(""), - /* 145 */ "ToNumeric" OpHelp(""), - /* 146 */ "ToInt" OpHelp(""), - /* 147 */ "ToReal" OpHelp(""), - /* 148 */ "VDestroy" OpHelp(""), - /* 149 */ "VOpen" OpHelp(""), - /* 150 */ "VColumn" OpHelp("r[P3]=vcolumn(P2)"), - /* 151 */ "VNext" OpHelp(""), - /* 152 */ "VRename" OpHelp(""), - /* 153 */ "Pagecount" OpHelp(""), - /* 154 */ "MaxPgcnt" OpHelp(""), - /* 155 */ "Init" OpHelp("Start at P2"), - /* 156 */ "Noop" OpHelp(""), - /* 157 */ "Explain" OpHelp(""), + /* 1 */ "Savepoint" OpHelp(""), + /* 2 */ "AutoCommit" OpHelp(""), + /* 3 */ "Transaction" OpHelp(""), + /* 4 */ "SorterNext" OpHelp(""), + /* 5 */ "PrevIfOpen" OpHelp(""), + /* 6 */ "NextIfOpen" OpHelp(""), + /* 7 */ "Prev" OpHelp(""), + /* 8 */ "Next" OpHelp(""), + /* 9 */ "Checkpoint" OpHelp(""), + /* 10 */ "JournalMode" OpHelp(""), + /* 11 */ "Vacuum" OpHelp(""), + /* 12 */ "VFilter" OpHelp("iplan=r[P3] zplan='P4'"), + /* 13 */ "VUpdate" OpHelp("data=r[P3@P2]"), + /* 14 */ "Goto" OpHelp(""), + /* 15 */ "Gosub" OpHelp(""), + /* 16 */ "Return" OpHelp(""), + /* 17 */ "InitCoroutine" OpHelp(""), + /* 18 */ "EndCoroutine" OpHelp(""), + /* 19 */ "Not" OpHelp("r[P2]= !r[P1]"), + /* 20 */ "Yield" OpHelp(""), + /* 21 */ "HaltIfNull" OpHelp("if r[P3]=null halt"), + /* 22 */ "Halt" OpHelp(""), + /* 23 */ "Integer" OpHelp("r[P2]=P1"), + /* 24 */ "Int64" OpHelp("r[P2]=P4"), + /* 25 */ "String" OpHelp("r[P2]='P4' (len=P1)"), + /* 26 */ "Null" OpHelp("r[P2..P3]=NULL"), + /* 27 */ "SoftNull" OpHelp("r[P1]=NULL"), + /* 28 */ "Blob" OpHelp("r[P2]=P4 (len=P1)"), + /* 29 */ "Variable" OpHelp("r[P2]=parameter(P1,P4)"), + /* 30 */ "Move" OpHelp("r[P2@P3]=r[P1@P3]"), + /* 31 */ "Copy" OpHelp("r[P2@P3+1]=r[P1@P3+1]"), + /* 32 */ "SCopy" OpHelp("r[P2]=r[P1]"), + /* 33 */ "IntCopy" OpHelp("r[P2]=r[P1]"), + /* 34 */ "ResultRow" OpHelp("output=r[P1@P2]"), + /* 35 */ "CollSeq" OpHelp(""), + /* 36 */ "Function0" OpHelp("r[P3]=func(r[P2@P5])"), + /* 37 */ "Function" OpHelp("r[P3]=func(r[P2@P5])"), + /* 38 */ "AddImm" OpHelp("r[P1]=r[P1]+P2"), + /* 39 */ "MustBeInt" OpHelp(""), + /* 40 */ "RealAffinity" OpHelp(""), + /* 41 */ "Cast" OpHelp("affinity(r[P1])"), + /* 42 */ "Permutation" OpHelp(""), + /* 43 */ "Compare" OpHelp("r[P1@P3] <-> r[P2@P3]"), + /* 44 */ "Jump" OpHelp(""), + /* 45 */ "Once" OpHelp(""), + /* 46 */ "If" OpHelp(""), + /* 47 */ "IfNot" OpHelp(""), + /* 48 */ "Column" OpHelp("r[P3]=PX"), + /* 49 */ "Affinity" OpHelp("affinity(r[P1@P2])"), + /* 50 */ "MakeRecord" OpHelp("r[P3]=mkrec(r[P1@P2])"), + /* 51 */ "Count" OpHelp("r[P2]=count()"), + /* 52 */ "ReadCookie" OpHelp(""), + /* 53 */ "SetCookie" OpHelp(""), + /* 54 */ "ReopenIdx" OpHelp("root=P2 iDb=P3"), + /* 55 */ "OpenRead" OpHelp("root=P2 iDb=P3"), + /* 56 */ "OpenWrite" OpHelp("root=P2 iDb=P3"), + /* 57 */ "OpenAutoindex" OpHelp("nColumn=P2"), + /* 58 */ "OpenEphemeral" OpHelp("nColumn=P2"), + /* 59 */ "SorterOpen" OpHelp(""), + /* 60 */ "SequenceTest" OpHelp("if( cursor[P1].ctr++ ) pc = P2"), + /* 61 */ "OpenPseudo" OpHelp("P3 columns in r[P2]"), + /* 62 */ "Close" OpHelp(""), + /* 63 */ "ColumnsUsed" OpHelp(""), + /* 64 */ "SeekLT" OpHelp("key=r[P3@P4]"), + /* 65 */ "SeekLE" OpHelp("key=r[P3@P4]"), + /* 66 */ "SeekGE" OpHelp("key=r[P3@P4]"), + /* 67 */ "SeekGT" OpHelp("key=r[P3@P4]"), + /* 68 */ "Seek" OpHelp("intkey=r[P2]"), + /* 69 */ "NoConflict" OpHelp("key=r[P3@P4]"), + /* 70 */ "NotFound" OpHelp("key=r[P3@P4]"), + /* 71 */ "Or" OpHelp("r[P3]=(r[P1] || r[P2])"), + /* 72 */ "And" OpHelp("r[P3]=(r[P1] && r[P2])"), + /* 73 */ "Found" OpHelp("key=r[P3@P4]"), + /* 74 */ "NotExists" OpHelp("intkey=r[P3]"), + /* 75 */ "Sequence" OpHelp("r[P2]=cursor[P1].ctr++"), + /* 76 */ "IsNull" OpHelp("if r[P1]==NULL goto P2"), + /* 77 */ "NotNull" OpHelp("if r[P1]!=NULL goto P2"), + /* 78 */ "Ne" OpHelp("if r[P1]!=r[P3] goto P2"), + /* 79 */ "Eq" OpHelp("if r[P1]==r[P3] goto P2"), + /* 80 */ "Gt" OpHelp("if r[P1]>r[P3] goto P2"), + /* 81 */ "Le" OpHelp("if r[P1]<=r[P3] goto P2"), + /* 82 */ "Lt" OpHelp("if r[P1]=r[P3] goto P2"), + /* 84 */ "NewRowid" OpHelp("r[P2]=rowid"), + /* 85 */ "BitAnd" OpHelp("r[P3]=r[P1]&r[P2]"), + /* 86 */ "BitOr" OpHelp("r[P3]=r[P1]|r[P2]"), + /* 87 */ "ShiftLeft" OpHelp("r[P3]=r[P2]<>r[P1]"), + /* 89 */ "Add" OpHelp("r[P3]=r[P1]+r[P2]"), + /* 90 */ "Subtract" OpHelp("r[P3]=r[P2]-r[P1]"), + /* 91 */ "Multiply" OpHelp("r[P3]=r[P1]*r[P2]"), + /* 92 */ "Divide" OpHelp("r[P3]=r[P2]/r[P1]"), + /* 93 */ "Remainder" OpHelp("r[P3]=r[P2]%r[P1]"), + /* 94 */ "Concat" OpHelp("r[P3]=r[P2]+r[P1]"), + /* 95 */ "Insert" OpHelp("intkey=r[P3] data=r[P2]"), + /* 96 */ "BitNot" OpHelp("r[P1]= ~r[P1]"), + /* 97 */ "String8" OpHelp("r[P2]='P4'"), + /* 98 */ "InsertInt" OpHelp("intkey=P3 data=r[P2]"), + /* 99 */ "Delete" OpHelp(""), + /* 100 */ "ResetCount" OpHelp(""), + /* 101 */ "SorterCompare" OpHelp("if key(P1)!=trim(r[P3],P4) goto P2"), + /* 102 */ "SorterData" OpHelp("r[P2]=data"), + /* 103 */ "RowKey" OpHelp("r[P2]=key"), + /* 104 */ "RowData" OpHelp("r[P2]=data"), + /* 105 */ "Rowid" OpHelp("r[P2]=rowid"), + /* 106 */ "NullRow" OpHelp(""), + /* 107 */ "Last" OpHelp(""), + /* 108 */ "SorterSort" OpHelp(""), + /* 109 */ "Sort" OpHelp(""), + /* 110 */ "Rewind" OpHelp(""), + /* 111 */ "SorterInsert" OpHelp(""), + /* 112 */ "IdxInsert" OpHelp("key=r[P2]"), + /* 113 */ "IdxDelete" OpHelp("key=r[P2@P3]"), + /* 114 */ "IdxRowid" OpHelp("r[P2]=rowid"), + /* 115 */ "IdxLE" OpHelp("key=r[P3@P4]"), + /* 116 */ "IdxGT" OpHelp("key=r[P3@P4]"), + /* 117 */ "IdxLT" OpHelp("key=r[P3@P4]"), + /* 118 */ "IdxGE" OpHelp("key=r[P3@P4]"), + /* 119 */ "Destroy" OpHelp(""), + /* 120 */ "Clear" OpHelp(""), + /* 121 */ "ResetSorter" OpHelp(""), + /* 122 */ "CreateIndex" OpHelp("r[P2]=root iDb=P1"), + /* 123 */ "CreateTable" OpHelp("r[P2]=root iDb=P1"), + /* 124 */ "ParseSchema" OpHelp(""), + /* 125 */ "LoadAnalysis" OpHelp(""), + /* 126 */ "DropTable" OpHelp(""), + /* 127 */ "DropIndex" OpHelp(""), + /* 128 */ "DropTrigger" OpHelp(""), + /* 129 */ "IntegrityCk" OpHelp(""), + /* 130 */ "RowSetAdd" OpHelp("rowset(P1)=r[P2]"), + /* 131 */ "RowSetRead" OpHelp("r[P3]=rowset(P1)"), + /* 132 */ "RowSetTest" OpHelp("if r[P3] in rowset(P1) goto P2"), + /* 133 */ "Real" OpHelp("r[P2]=P4"), + /* 134 */ "Program" OpHelp(""), + /* 135 */ "Param" OpHelp(""), + /* 136 */ "FkCounter" OpHelp("fkctr[P1]+=P2"), + /* 137 */ "FkIfZero" OpHelp("if fkctr[P1]==0 goto P2"), + /* 138 */ "MemMax" OpHelp("r[P1]=max(r[P1],r[P2])"), + /* 139 */ "IfPos" OpHelp("if r[P1]>0 then r[P1]-=P3, goto P2"), + /* 140 */ "SetIfNotPos" OpHelp("if r[P1]<=0 then r[P2]=P3"), + /* 141 */ "IfNotZero" OpHelp("if r[P1]!=0 then r[P1]-=P3, goto P2"), + /* 142 */ "DecrJumpZero" OpHelp("if (--r[P1])==0 goto P2"), + /* 143 */ "JumpZeroIncr" OpHelp("if (r[P1]++)==0 ) goto P2"), + /* 144 */ "AggStep0" OpHelp("accum=r[P3] step(r[P2@P5])"), + /* 145 */ "AggStep" OpHelp("accum=r[P3] step(r[P2@P5])"), + /* 146 */ "AggFinal" OpHelp("accum=r[P1] N=P2"), + /* 147 */ "IncrVacuum" OpHelp(""), + /* 148 */ "Expire" OpHelp(""), + /* 149 */ "TableLock" OpHelp("iDb=P1 root=P2 write=P3"), + /* 150 */ "VBegin" OpHelp(""), + /* 151 */ "VCreate" OpHelp(""), + /* 152 */ "VDestroy" OpHelp(""), + /* 153 */ "VOpen" OpHelp(""), + /* 154 */ "VColumn" OpHelp("r[P3]=vcolumn(P2)"), + /* 155 */ "VNext" OpHelp(""), + /* 156 */ "VRename" OpHelp(""), + /* 157 */ "Pagecount" OpHelp(""), + /* 158 */ "MaxPgcnt" OpHelp(""), + /* 159 */ "Init" OpHelp("Start at P2"), + /* 160 */ "CursorHint" OpHelp(""), + /* 161 */ "Noop" OpHelp(""), + /* 162 */ "Explain" OpHelp(""), }; return azName[i]; } @@ -23764,6 +26903,7 @@ SQLITE_PRIVATE const char *sqlite3OpcodeName(int i){ ** * Definitions of sqlite3_vfs objects for all locking methods ** plus implementations of sqlite3_os_init() and sqlite3_os_end(). */ +/* #include "sqliteInt.h" */ #if SQLITE_OS_UNIX /* This file is used on unix only */ /* @@ -23791,18 +26931,6 @@ SQLITE_PRIVATE const char *sqlite3OpcodeName(int i){ # endif #endif -/* -** Define the OS_VXWORKS pre-processor macro to 1 if building on -** vxworks, or 0 otherwise. -*/ -#ifndef OS_VXWORKS -# if defined(__RTP__) || defined(_WRS_KERNEL) -# define OS_VXWORKS 1 -# else -# define OS_VXWORKS 0 -# endif -#endif - /* ** standard include files. */ @@ -23814,22 +26942,33 @@ SQLITE_PRIVATE const char *sqlite3OpcodeName(int i){ #include #include #if !defined(SQLITE_OMIT_WAL) || SQLITE_MAX_MMAP_SIZE>0 -#include +# include #endif - #if SQLITE_ENABLE_LOCKING_STYLE # include -# if OS_VXWORKS -# include -# include -# else -# include -# include -# endif +# include +# include #endif /* SQLITE_ENABLE_LOCKING_STYLE */ -#if defined(__APPLE__) || (SQLITE_ENABLE_LOCKING_STYLE && !OS_VXWORKS) +#if defined(__APPLE__) && ((__MAC_OS_X_VERSION_MIN_REQUIRED > 1050) || \ + (__IPHONE_OS_VERSION_MIN_REQUIRED > 2000)) +# if (!defined(TARGET_OS_EMBEDDED) || (TARGET_OS_EMBEDDED==0)) \ + && (!defined(TARGET_IPHONE_SIMULATOR) || (TARGET_IPHONE_SIMULATOR==0)) +# define HAVE_GETHOSTUUID 1 +# else +# warning "gethostuuid() is disabled." +# endif +#endif + + +#if OS_VXWORKS +/* # include */ +# include +# include +#endif /* OS_VXWORKS */ + +#if defined(__APPLE__) || SQLITE_ENABLE_LOCKING_STYLE # include #endif @@ -23870,6 +27009,10 @@ SQLITE_PRIVATE const char *sqlite3OpcodeName(int i){ */ #define MAX_PATHNAME 512 +/* Always cast the getpid() return type for compatibility with +** kernel modules in VxWorks. */ +#define osGetpid(X) (pid_t)getpid() + /* ** Only set the lastErrno if the error code is a real error and not ** a normal expected return code of SQLITE_BUSY or SQLITE_OK @@ -23958,7 +27101,7 @@ struct unixFile { ** method was called. If xOpen() is called from a different process id, ** indicating that a fork() has occurred, the PRNG will be reset. */ -static int randomnessPid = 0; +static pid_t randomnessPid = 0; /* ** Allowed values for the unixFile.ctrlFlags bitmask: @@ -23975,7 +27118,6 @@ static int randomnessPid = 0; #define UNIXFILE_DELETE 0x20 /* Delete on close */ #define UNIXFILE_URI 0x40 /* Filename might have query parameters */ #define UNIXFILE_NOLOCK 0x80 /* Do no file locking */ -#define UNIXFILE_WARNED 0x0100 /* verifyDbFile() warnings have been issued */ /* ** Include code that is common to all os_*.c files @@ -24013,16 +27155,6 @@ static int randomnessPid = 0; # error "The MEMORY_DEBUG macro is obsolete. Use SQLITE_DEBUG instead." #endif -#if defined(SQLITE_TEST) && defined(SQLITE_DEBUG) -# ifndef SQLITE_DEBUG_OS_TRACE -# define SQLITE_DEBUG_OS_TRACE 0 -# endif - int sqlite3OSTrace = SQLITE_DEBUG_OS_TRACE; -# define OSTRACE(X) if( sqlite3OSTrace ) sqlite3DebugPrintf X -#else -# define OSTRACE(X) -#endif - /* ** Macros for performance tracing. Normally turned off. Only works ** on i486 hardware. @@ -24228,6 +27360,14 @@ SQLITE_API int sqlite3_open_file_count = 0; # endif #endif +/* +** Explicitly call the 64-bit version of lseek() on Android. Otherwise, lseek() +** is the 32-bit version, even if _FILE_OFFSET_BITS=64 is defined. +*/ +#ifdef __ANDROID__ +# define lseek lseek64 +#endif + /* ** Different Unix systems declare open() in different ways. Same use ** open(const char*,int,mode_t). Others use open(const char*,int,...). @@ -24240,15 +27380,6 @@ static int posixOpen(const char *zFile, int flags, int mode){ return open(zFile, flags, mode); } -/* -** On some systems, calls to fchown() will trigger a message in a security -** log if they come from non-root processes. So avoid calling fchown() if -** we are not running as root. -*/ -static int posixFchown(int fd, uid_t uid, gid_t gid){ - return geteuid() ? 0 : fchown(fd,uid,gid); -} - /* Forward reference */ static int openDirectory(const char*, int*); static int unixGetpagesize(void); @@ -24335,7 +27466,7 @@ static struct unix_syscall { #define osPwrite64 ((ssize_t(*)(int,const void*,size_t,off_t))\ aSyscall[13].pCurrent) - { "fchmod", (sqlite3_syscall_ptr)fchmod, 0 }, + { "fchmod", (sqlite3_syscall_ptr)fchmod, 0 }, #define osFchmod ((int(*)(int,mode_t))aSyscall[14].pCurrent) #if defined(HAVE_POSIX_FALLOCATE) && HAVE_POSIX_FALLOCATE @@ -24357,29 +27488,50 @@ static struct unix_syscall { { "rmdir", (sqlite3_syscall_ptr)rmdir, 0 }, #define osRmdir ((int(*)(const char*))aSyscall[19].pCurrent) - { "fchown", (sqlite3_syscall_ptr)posixFchown, 0 }, + { "fchown", (sqlite3_syscall_ptr)fchown, 0 }, #define osFchown ((int(*)(int,uid_t,gid_t))aSyscall[20].pCurrent) + { "geteuid", (sqlite3_syscall_ptr)geteuid, 0 }, +#define osGeteuid ((uid_t(*)(void))aSyscall[21].pCurrent) + #if !defined(SQLITE_OMIT_WAL) || SQLITE_MAX_MMAP_SIZE>0 { "mmap", (sqlite3_syscall_ptr)mmap, 0 }, -#define osMmap ((void*(*)(void*,size_t,int,int,int,off_t))aSyscall[21].pCurrent) +#define osMmap ((void*(*)(void*,size_t,int,int,int,off_t))aSyscall[22].pCurrent) { "munmap", (sqlite3_syscall_ptr)munmap, 0 }, -#define osMunmap ((void*(*)(void*,size_t))aSyscall[22].pCurrent) +#define osMunmap ((void*(*)(void*,size_t))aSyscall[23].pCurrent) #if HAVE_MREMAP { "mremap", (sqlite3_syscall_ptr)mremap, 0 }, #else { "mremap", (sqlite3_syscall_ptr)0, 0 }, #endif -#define osMremap ((void*(*)(void*,size_t,size_t,int,...))aSyscall[23].pCurrent) -#endif +#define osMremap ((void*(*)(void*,size_t,size_t,int,...))aSyscall[24].pCurrent) { "getpagesize", (sqlite3_syscall_ptr)unixGetpagesize, 0 }, -#define osGetpagesize ((int(*)(void))aSyscall[24].pCurrent) +#define osGetpagesize ((int(*)(void))aSyscall[25].pCurrent) + + { "readlink", (sqlite3_syscall_ptr)readlink, 0 }, +#define osReadlink ((ssize_t(*)(const char*,char*,size_t))aSyscall[26].pCurrent) + +#endif }; /* End of the overrideable system calls */ + +/* +** On some systems, calls to fchown() will trigger a message in a security +** log if they come from non-root processes. So avoid calling fchown() if +** we are not running as root. +*/ +static int robustFchown(int fd, uid_t uid, gid_t gid){ +#if OS_VXWORKS + return 0; +#else + return osGeteuid() ? 0 : osFchown(fd,uid,gid); +#endif +} + /* ** This is the xSetSystemCall() method of sqlite3_vfs for all of the ** "unix" VFSes. Return SQLITE_OK opon successfully updating the @@ -24541,22 +27693,22 @@ static int robust_open(const char *z, int f, mode_t m){ ** unixEnterLeave() */ static void unixEnterMutex(void){ - sqlite3_mutex_enter(sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MASTER)); + sqlite3_mutex_enter(sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_VFS1)); } static void unixLeaveMutex(void){ - sqlite3_mutex_leave(sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MASTER)); + sqlite3_mutex_leave(sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_VFS1)); } #ifdef SQLITE_DEBUG static int unixMutexHeld(void) { - return sqlite3_mutex_held(sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MASTER)); + return sqlite3_mutex_held(sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_VFS1)); } #endif -#if defined(SQLITE_TEST) && defined(SQLITE_DEBUG) +#ifdef SQLITE_HAVE_OS_TRACE /* ** Helper function for printing out trace information from debugging -** binaries. This returns the string represetation of the supplied +** binaries. This returns the string representation of the supplied ** integer lock-type. */ static const char *azFileLock(int eFileLock){ @@ -24633,9 +27785,22 @@ static int lockTrace(int fd, int op, struct flock *p){ /* ** Retry ftruncate() calls that fail due to EINTR +** +** All calls to ftruncate() within this file should be made through +** this wrapper. On the Android platform, bypassing the logic below +** could lead to a corrupt database. */ static int robust_ftruncate(int h, sqlite3_int64 sz){ int rc; +#ifdef __ANDROID__ + /* On Android, ftruncate() always uses 32-bit offsets, even if + ** _FILE_OFFSET_BITS=64 is defined. This means it is unsafe to attempt to + ** truncate a file to any size larger than 2GiB. Silently ignore any + ** such attempts. */ + if( sz>(sqlite3_int64)0x7FFFFFFF ){ + rc = SQLITE_OK; + }else +#endif do{ rc = osFtruncate(h,sz); }while( rc<0 && errno==EINTR ); return rc; } @@ -24651,23 +27816,12 @@ static int robust_ftruncate(int h, sqlite3_int64 sz){ ** should handle ENOLCK, ENOTSUP, EOPNOTSUPP separately. */ static int sqliteErrorFromPosixError(int posixError, int sqliteIOErr) { + assert( (sqliteIOErr == SQLITE_IOERR_LOCK) || + (sqliteIOErr == SQLITE_IOERR_UNLOCK) || + (sqliteIOErr == SQLITE_IOERR_RDLOCK) || + (sqliteIOErr == SQLITE_IOERR_CHECKRESERVEDLOCK) ); switch (posixError) { -#if 0 - /* At one point this code was not commented out. In theory, this branch - ** should never be hit, as this function should only be called after - ** a locking-related function (i.e. fcntl()) has returned non-zero with - ** the value of errno as the first argument. Since a system call has failed, - ** errno should be non-zero. - ** - ** Despite this, if errno really is zero, we still don't want to return - ** SQLITE_OK. The system call failed, and *some* SQLite error should be - ** propagated back to the caller. Commenting this branch out means errno==0 - ** will be handled by the "default:" case below. - */ - case 0: - return SQLITE_OK; -#endif - + case EACCES: case EAGAIN: case ETIMEDOUT: case EBUSY: @@ -24677,51 +27831,9 @@ static int sqliteErrorFromPosixError(int posixError, int sqliteIOErr) { * introspection, in which it actually means what it says */ return SQLITE_BUSY; - case EACCES: - /* EACCES is like EAGAIN during locking operations, but not any other time*/ - if( (sqliteIOErr == SQLITE_IOERR_LOCK) || - (sqliteIOErr == SQLITE_IOERR_UNLOCK) || - (sqliteIOErr == SQLITE_IOERR_RDLOCK) || - (sqliteIOErr == SQLITE_IOERR_CHECKRESERVEDLOCK) ){ - return SQLITE_BUSY; - } - /* else fall through */ case EPERM: return SQLITE_PERM; - /* EDEADLK is only possible if a call to fcntl(F_SETLKW) is made. And - ** this module never makes such a call. And the code in SQLite itself - ** asserts that SQLITE_IOERR_BLOCKED is never returned. For these reasons - ** this case is also commented out. If the system does set errno to EDEADLK, - ** the default SQLITE_IOERR_XXX code will be returned. */ -#if 0 - case EDEADLK: - return SQLITE_IOERR_BLOCKED; -#endif - -#if EOPNOTSUPP!=ENOTSUP - case EOPNOTSUPP: - /* something went terribly awry, unless during file system support - * introspection, in which it actually means what it says */ -#endif -#ifdef ENOTSUP - case ENOTSUP: - /* invalid fd, unless during file system support introspection, in which - * it actually means what it says */ -#endif - case EIO: - case EBADF: - case EINVAL: - case ENOTCONN: - case ENODEV: - case ENXIO: - case ENOENT: -#ifdef ESTALE /* ESTALE is not defined on Interix systems */ - case ESTALE: -#endif - case ENOSYS: - /* these should force the client to close the file and reconnect */ - default: return sqliteIOErr; } @@ -24813,7 +27925,7 @@ static struct vxworksFileId *vxworksFindFileId(const char *zAbsoluteName){ assert( zAbsoluteName[0]=='/' ); n = (int)strlen(zAbsoluteName); - pNew = sqlite3_malloc( sizeof(*pNew) + (n+1) ); + pNew = sqlite3_malloc64( sizeof(*pNew) + (n+1) ); if( pNew==0 ) return 0; pNew->zCanonicalName = (char*)&pNew[1]; memcpy(pNew->zCanonicalName, zAbsoluteName, n+1); @@ -25005,7 +28117,7 @@ static unixInodeInfo *inodeList = 0; /* ** -** This function - unixLogError_x(), is only ever called via the macro +** This function - unixLogErrorAtLine(), is only ever called via the macro ** unixLogError(). ** ** It is invoked after an error occurs in an OS function and errno has been @@ -25092,6 +28204,14 @@ static void robust_close(unixFile *pFile, int h, int lineno){ } } +/* +** Set the pFile->lastErrno. Do this in a subroutine as that provides +** a convenient place to set a breakpoint. +*/ +static void storeLastErrno(unixFile *pFile, int error){ + pFile->lastErrno = error; +} + /* ** Close all file descriptors accumuated in the unixInodeInfo->pUnused list. */ @@ -25165,8 +28285,8 @@ static int findInodeInfo( fd = pFile->h; rc = osFstat(fd, &statbuf); if( rc!=0 ){ - pFile->lastErrno = errno; -#ifdef EOVERFLOW + storeLastErrno(pFile, errno); +#if defined(EOVERFLOW) && defined(SQLITE_DISABLE_LFS) if( pFile->lastErrno==EOVERFLOW ) return SQLITE_NOLFS; #endif return SQLITE_IOERR; @@ -25186,12 +28306,12 @@ static int findInodeInfo( if( statbuf.st_size==0 && (pFile->fsFlags & SQLITE_FSFLAGS_IS_MSDOS)!=0 ){ do{ rc = osWrite(fd, "S", 1); }while( rc<0 && errno==EINTR ); if( rc!=1 ){ - pFile->lastErrno = errno; + storeLastErrno(pFile, errno); return SQLITE_IOERR; } rc = osFstat(fd, &statbuf); if( rc!=0 ){ - pFile->lastErrno = errno; + storeLastErrno(pFile, errno); return SQLITE_IOERR; } } @@ -25209,7 +28329,7 @@ static int findInodeInfo( pInode = pInode->pNext; } if( pInode==0 ){ - pInode = sqlite3_malloc( sizeof(*pInode) ); + pInode = sqlite3_malloc64( sizeof(*pInode) ); if( pInode==0 ){ return SQLITE_NOMEM; } @@ -25231,9 +28351,13 @@ static int findInodeInfo( ** Return TRUE if pFile has been renamed or unlinked since it was first opened. */ static int fileHasMoved(unixFile *pFile){ +#if OS_VXWORKS + return pFile->pInode!=0 && pFile->pId!=pFile->pInode->fileId.pId; +#else struct stat buf; return pFile->pInode!=0 && - (osStat(pFile->zPath, &buf)!=0 || buf.st_ino!=pFile->pInode->fileId.ino); + (osStat(pFile->zPath, &buf)!=0 || buf.st_ino!=pFile->pInode->fileId.ino); +#endif } @@ -25249,30 +28373,21 @@ static int fileHasMoved(unixFile *pFile){ static void verifyDbFile(unixFile *pFile){ struct stat buf; int rc; - if( pFile->ctrlFlags & UNIXFILE_WARNED ){ - /* One or more of the following warnings have already been issued. Do not - ** repeat them so as not to clutter the error log */ - return; - } rc = osFstat(pFile->h, &buf); if( rc!=0 ){ sqlite3_log(SQLITE_WARNING, "cannot fstat db file %s", pFile->zPath); - pFile->ctrlFlags |= UNIXFILE_WARNED; return; } if( buf.st_nlink==0 && (pFile->ctrlFlags & UNIXFILE_DELETE)==0 ){ sqlite3_log(SQLITE_WARNING, "file unlinked while open: %s", pFile->zPath); - pFile->ctrlFlags |= UNIXFILE_WARNED; return; } if( buf.st_nlink>1 ){ sqlite3_log(SQLITE_WARNING, "multiple links to file: %s", pFile->zPath); - pFile->ctrlFlags |= UNIXFILE_WARNED; return; } if( fileHasMoved(pFile) ){ sqlite3_log(SQLITE_WARNING, "file renamed while open: %s", pFile->zPath); - pFile->ctrlFlags |= UNIXFILE_WARNED; return; } } @@ -25292,6 +28407,7 @@ static int unixCheckReservedLock(sqlite3_file *id, int *pResOut){ SimulateIOError( return SQLITE_IOERR_CHECKRESERVEDLOCK; ); assert( pFile ); + assert( pFile->eFileLock<=SHARED_LOCK ); unixEnterMutex(); /* Because pFile->pInode is shared across threads */ /* Check if a thread in this process holds such a lock */ @@ -25310,7 +28426,7 @@ static int unixCheckReservedLock(sqlite3_file *id, int *pResOut){ lock.l_type = F_WRLCK; if( osFcntl(pFile->h, F_GETLK, &lock) ){ rc = SQLITE_IOERR_CHECKRESERVEDLOCK; - pFile->lastErrno = errno; + storeLastErrno(pFile, errno); } else if( lock.l_type!=F_UNLCK ){ reserved = 1; } @@ -25348,9 +28464,7 @@ static int unixFileLock(unixFile *pFile, struct flock *pLock){ unixInodeInfo *pInode = pFile->pInode; assert( unixMutexHeld() ); assert( pInode!=0 ); - if( ((pFile->ctrlFlags & UNIXFILE_EXCL)!=0 || pInode->bProcessLock) - && ((pFile->ctrlFlags & UNIXFILE_RDONLY)==0) - ){ + if( (pFile->ctrlFlags & (UNIXFILE_EXCL|UNIXFILE_RDONLY))==UNIXFILE_EXCL ){ if( pInode->bProcessLock==0 ){ struct flock lock; assert( pInode->nLock==0 ); @@ -25443,7 +28557,8 @@ static int unixLock(sqlite3_file *id, int eFileLock){ assert( pFile ); OSTRACE(("LOCK %d %s was %s(%s,%d) pid=%d (unix)\n", pFile->h, azFileLock(eFileLock), azFileLock(pFile->eFileLock), - azFileLock(pFile->pInode->eFileLock), pFile->pInode->nShared , getpid())); + azFileLock(pFile->pInode->eFileLock), pFile->pInode->nShared, + osGetpid(0))); /* If there is already a lock of this type or more restrictive on the ** unixFile, do nothing. Don't use the end_lock: exit path, as @@ -25510,7 +28625,7 @@ static int unixLock(sqlite3_file *id, int eFileLock){ tErrno = errno; rc = sqliteErrorFromPosixError(tErrno, SQLITE_IOERR_LOCK); if( rc!=SQLITE_BUSY ){ - pFile->lastErrno = tErrno; + storeLastErrno(pFile, tErrno); } goto end_lock; } @@ -25545,7 +28660,7 @@ static int unixLock(sqlite3_file *id, int eFileLock){ if( rc ){ if( rc!=SQLITE_BUSY ){ - pFile->lastErrno = tErrno; + storeLastErrno(pFile, tErrno); } goto end_lock; }else{ @@ -25578,7 +28693,7 @@ static int unixLock(sqlite3_file *id, int eFileLock){ tErrno = errno; rc = sqliteErrorFromPosixError(tErrno, SQLITE_IOERR_LOCK); if( rc!=SQLITE_BUSY ){ - pFile->lastErrno = tErrno; + storeLastErrno(pFile, tErrno); } } } @@ -25651,7 +28766,7 @@ static int posixUnlock(sqlite3_file *id, int eFileLock, int handleNFSUnlock){ assert( pFile ); OSTRACE(("UNLOCK %d %d was %d(%d,%d) pid=%d (unix)\n", pFile->h, eFileLock, pFile->eFileLock, pFile->pInode->eFileLock, pFile->pInode->nShared, - getpid())); + osGetpid(0))); assert( eFileLock<=SHARED_LOCK ); if( pFile->eFileLock<=eFileLock ){ @@ -25685,7 +28800,6 @@ static int posixUnlock(sqlite3_file *id, int eFileLock, int handleNFSUnlock){ ** 4: [RRRR.] */ if( eFileLock==SHARED_LOCK ){ - #if !defined(__APPLE__) || !SQLITE_ENABLE_LOCKING_STYLE (void)handleNFSUnlock; assert( handleNFSUnlock==0 ); @@ -25702,9 +28816,7 @@ static int posixUnlock(sqlite3_file *id, int eFileLock, int handleNFSUnlock){ if( unixFileLock(pFile, &lock)==(-1) ){ tErrno = errno; rc = SQLITE_IOERR_UNLOCK; - if( IS_LOCK_ERROR(rc) ){ - pFile->lastErrno = tErrno; - } + storeLastErrno(pFile, tErrno); goto end_unlock; } lock.l_type = F_RDLCK; @@ -25715,7 +28827,7 @@ static int posixUnlock(sqlite3_file *id, int eFileLock, int handleNFSUnlock){ tErrno = errno; rc = sqliteErrorFromPosixError(tErrno, SQLITE_IOERR_RDLOCK); if( IS_LOCK_ERROR(rc) ){ - pFile->lastErrno = tErrno; + storeLastErrno(pFile, tErrno); } goto end_unlock; } @@ -25726,9 +28838,7 @@ static int posixUnlock(sqlite3_file *id, int eFileLock, int handleNFSUnlock){ if( unixFileLock(pFile, &lock)==(-1) ){ tErrno = errno; rc = SQLITE_IOERR_UNLOCK; - if( IS_LOCK_ERROR(rc) ){ - pFile->lastErrno = tErrno; - } + storeLastErrno(pFile, tErrno); goto end_unlock; } }else @@ -25746,7 +28856,7 @@ static int posixUnlock(sqlite3_file *id, int eFileLock, int handleNFSUnlock){ ** SQLITE_BUSY would confuse the upper layer (in practice it causes ** an assert to fail). */ rc = SQLITE_IOERR_RDLOCK; - pFile->lastErrno = errno; + storeLastErrno(pFile, errno); goto end_unlock; } } @@ -25759,7 +28869,7 @@ static int posixUnlock(sqlite3_file *id, int eFileLock, int handleNFSUnlock){ pInode->eFileLock = SHARED_LOCK; }else{ rc = SQLITE_IOERR_UNLOCK; - pFile->lastErrno = errno; + storeLastErrno(pFile, errno); goto end_unlock; } } @@ -25777,7 +28887,7 @@ static int posixUnlock(sqlite3_file *id, int eFileLock, int handleNFSUnlock){ pInode->eFileLock = NO_LOCK; }else{ rc = SQLITE_IOERR_UNLOCK; - pFile->lastErrno = errno; + storeLastErrno(pFile, errno); pInode->eFileLock = NO_LOCK; pFile->eFileLock = NO_LOCK; } @@ -25846,6 +28956,13 @@ static int closeUnixFile(sqlite3_file *id){ vxworksReleaseFileId(pFile->pId); pFile->pId = 0; } +#endif +#ifdef SQLITE_UNLINK_AFTER_CLOSE + if( pFile->ctrlFlags & UNIXFILE_DELETE ){ + osUnlink(pFile->zPath); + sqlite3_free(*(char**)&pFile->zPath); + pFile->zPath = 0; + } #endif OSTRACE(("CLOSE %-3d\n", pFile->h)); OpenCounter(-1); @@ -25972,17 +29089,7 @@ static int dotlockCheckReservedLock(sqlite3_file *id, int *pResOut) { SimulateIOError( return SQLITE_IOERR_CHECKRESERVEDLOCK; ); assert( pFile ); - - /* Check if a thread in this process holds such a lock */ - if( pFile->eFileLock>SHARED_LOCK ){ - /* Either this connection or some other connection in the same process - ** holds a lock on the file. No need to check further. */ - reserved = 1; - }else{ - /* The lock is held if and only if the lockfile exists */ - const char *zLockFile = (const char*)pFile->lockingContext; - reserved = osAccess(zLockFile, 0)==0; - } + reserved = osAccess((const char*)pFile->lockingContext, 0)==0; OSTRACE(("TEST WR-LOCK %d %d %d (dotlock)\n", pFile->h, rc, reserved)); *pResOut = reserved; return rc; @@ -26044,8 +29151,8 @@ static int dotlockLock(sqlite3_file *id, int eFileLock) { rc = SQLITE_BUSY; } else { rc = sqliteErrorFromPosixError(tErrno, SQLITE_IOERR_LOCK); - if( IS_LOCK_ERROR(rc) ){ - pFile->lastErrno = tErrno; + if( rc!=SQLITE_BUSY ){ + storeLastErrno(pFile, tErrno); } } return rc; @@ -26072,7 +29179,7 @@ static int dotlockUnlock(sqlite3_file *id, int eFileLock) { assert( pFile ); OSTRACE(("UNLOCK %d %d was %d pid=%d (dotlock)\n", pFile->h, eFileLock, - pFile->eFileLock, getpid())); + pFile->eFileLock, osGetpid(0))); assert( eFileLock<=SHARED_LOCK ); /* no-op if possible */ @@ -26091,15 +29198,13 @@ static int dotlockUnlock(sqlite3_file *id, int eFileLock) { /* To fully unlock the database, delete the lock file */ assert( eFileLock==NO_LOCK ); rc = osRmdir(zLockFile); - if( rc<0 && errno==ENOTDIR ) rc = osUnlink(zLockFile); if( rc<0 ){ int tErrno = errno; - rc = 0; - if( ENOENT != tErrno ){ + if( tErrno==ENOENT ){ + rc = SQLITE_OK; + }else{ rc = SQLITE_IOERR_UNLOCK; - } - if( IS_LOCK_ERROR(rc) ){ - pFile->lastErrno = tErrno; + storeLastErrno(pFile, tErrno); } return rc; } @@ -26111,14 +29216,11 @@ static int dotlockUnlock(sqlite3_file *id, int eFileLock) { ** Close a file. Make sure the lock has been released before closing. */ static int dotlockClose(sqlite3_file *id) { - int rc = SQLITE_OK; - if( id ){ - unixFile *pFile = (unixFile*)id; - dotlockUnlock(id, NO_LOCK); - sqlite3_free(pFile->lockingContext); - rc = closeUnixFile(id); - } - return rc; + unixFile *pFile = (unixFile*)id; + assert( id!=0 ); + dotlockUnlock(id, NO_LOCK); + sqlite3_free(pFile->lockingContext); + return closeUnixFile(id); } /****************** End of the dot-file lock implementation ******************* ******************************************************************************/ @@ -26135,10 +29237,9 @@ static int dotlockClose(sqlite3_file *id) { ** still works when you do this, but concurrency is reduced since ** only a single process can be reading the database at a time. ** -** Omit this section if SQLITE_ENABLE_LOCKING_STYLE is turned off or if -** compiling for VXWORKS. +** Omit this section if SQLITE_ENABLE_LOCKING_STYLE is turned off */ -#if SQLITE_ENABLE_LOCKING_STYLE && !OS_VXWORKS +#if SQLITE_ENABLE_LOCKING_STYLE /* ** Retry flock() calls that fail with EINTR @@ -26185,10 +29286,8 @@ static int flockCheckReservedLock(sqlite3_file *id, int *pResOut){ int tErrno = errno; /* unlock failed with an error */ lrc = SQLITE_IOERR_UNLOCK; - if( IS_LOCK_ERROR(lrc) ){ - pFile->lastErrno = tErrno; - rc = lrc; - } + storeLastErrno(pFile, tErrno); + rc = lrc; } } else { int tErrno = errno; @@ -26196,7 +29295,7 @@ static int flockCheckReservedLock(sqlite3_file *id, int *pResOut){ /* someone else might have it reserved */ lrc = sqliteErrorFromPosixError(tErrno, SQLITE_IOERR_LOCK); if( IS_LOCK_ERROR(lrc) ){ - pFile->lastErrno = tErrno; + storeLastErrno(pFile, tErrno); rc = lrc; } } @@ -26262,7 +29361,7 @@ static int flockLock(sqlite3_file *id, int eFileLock) { /* didn't get, must be busy */ rc = sqliteErrorFromPosixError(tErrno, SQLITE_IOERR_LOCK); if( IS_LOCK_ERROR(rc) ){ - pFile->lastErrno = tErrno; + storeLastErrno(pFile, tErrno); } } else { /* got it, set the type and return ok */ @@ -26291,7 +29390,7 @@ static int flockUnlock(sqlite3_file *id, int eFileLock) { assert( pFile ); OSTRACE(("UNLOCK %d %d was %d pid=%d (flock)\n", pFile->h, eFileLock, - pFile->eFileLock, getpid())); + pFile->eFileLock, osGetpid(0))); assert( eFileLock<=SHARED_LOCK ); /* no-op if possible */ @@ -26321,12 +29420,9 @@ static int flockUnlock(sqlite3_file *id, int eFileLock) { ** Close a file. */ static int flockClose(sqlite3_file *id) { - int rc = SQLITE_OK; - if( id ){ - flockUnlock(id, NO_LOCK); - rc = closeUnixFile(id); - } - return rc; + assert( id!=0 ); + flockUnlock(id, NO_LOCK); + return closeUnixFile(id); } #endif /* SQLITE_ENABLE_LOCKING_STYLE && !OS_VXWORK */ @@ -26352,7 +29448,7 @@ static int flockClose(sqlite3_file *id) { ** to a non-zero value otherwise *pResOut is set to zero. The return value ** is set to SQLITE_OK unless an I/O error occurs during lock checking. */ -static int semCheckReservedLock(sqlite3_file *id, int *pResOut) { +static int semXCheckReservedLock(sqlite3_file *id, int *pResOut) { int rc = SQLITE_OK; int reserved = 0; unixFile *pFile = (unixFile*)id; @@ -26369,13 +29465,12 @@ static int semCheckReservedLock(sqlite3_file *id, int *pResOut) { /* Otherwise see if some other process holds it. */ if( !reserved ){ sem_t *pSem = pFile->pInode->pSem; - struct stat statBuf; if( sem_trywait(pSem)==-1 ){ int tErrno = errno; if( EAGAIN != tErrno ){ rc = sqliteErrorFromPosixError(tErrno, SQLITE_IOERR_CHECKRESERVEDLOCK); - pFile->lastErrno = tErrno; + storeLastErrno(pFile, tErrno); } else { /* someone else has the lock when we are in NO_LOCK */ reserved = (pFile->eFileLock < SHARED_LOCK); @@ -26420,9 +29515,8 @@ static int semCheckReservedLock(sqlite3_file *id, int *pResOut) { ** This routine will only increase a lock. Use the sqlite3OsUnlock() ** routine to lower a locking level. */ -static int semLock(sqlite3_file *id, int eFileLock) { +static int semXLock(sqlite3_file *id, int eFileLock) { unixFile *pFile = (unixFile*)id; - int fd; sem_t *pSem = pFile->pInode->pSem; int rc = SQLITE_OK; @@ -26454,14 +29548,14 @@ static int semLock(sqlite3_file *id, int eFileLock) { ** If the locking level of the file descriptor is already at or below ** the requested locking level, this routine is a no-op. */ -static int semUnlock(sqlite3_file *id, int eFileLock) { +static int semXUnlock(sqlite3_file *id, int eFileLock) { unixFile *pFile = (unixFile*)id; sem_t *pSem = pFile->pInode->pSem; assert( pFile ); assert( pSem ); OSTRACE(("UNLOCK %d %d was %d pid=%d (sem)\n", pFile->h, eFileLock, - pFile->eFileLock, getpid())); + pFile->eFileLock, osGetpid(0))); assert( eFileLock<=SHARED_LOCK ); /* no-op if possible */ @@ -26480,7 +29574,7 @@ static int semUnlock(sqlite3_file *id, int eFileLock) { int rc, tErrno = errno; rc = sqliteErrorFromPosixError(tErrno, SQLITE_IOERR_UNLOCK); if( IS_LOCK_ERROR(rc) ){ - pFile->lastErrno = tErrno; + storeLastErrno(pFile, tErrno); } return rc; } @@ -26491,10 +29585,10 @@ static int semUnlock(sqlite3_file *id, int eFileLock) { /* ** Close a file. */ -static int semClose(sqlite3_file *id) { +static int semXClose(sqlite3_file *id) { if( id ){ unixFile *pFile = (unixFile*)id; - semUnlock(id, NO_LOCK); + semXUnlock(id, NO_LOCK); assert( pFile ); unixEnterMutex(); releaseInodeInfo(pFile); @@ -26582,7 +29676,7 @@ static int afpSetLock( setLockFlag ? SQLITE_IOERR_LOCK : SQLITE_IOERR_UNLOCK); #endif /* SQLITE_IGNORE_AFP_LOCK_ERRORS */ if( IS_LOCK_ERROR(rc) ){ - pFile->lastErrno = tErrno; + storeLastErrno(pFile, tErrno); } return rc; } else { @@ -26675,7 +29769,7 @@ static int afpLock(sqlite3_file *id, int eFileLock){ assert( pFile ); OSTRACE(("LOCK %d %s was %s(%s,%d) pid=%d (afp)\n", pFile->h, azFileLock(eFileLock), azFileLock(pFile->eFileLock), - azFileLock(pInode->eFileLock), pInode->nShared , getpid())); + azFileLock(pInode->eFileLock), pInode->nShared , osGetpid(0))); /* If there is already a lock of this type or more restrictive on the ** unixFile, do nothing. Don't use the afp_end_lock: exit path, as @@ -26765,7 +29859,7 @@ static int afpLock(sqlite3_file *id, int eFileLock){ lrc2 = afpSetLock(context->dbPath, pFile, PENDING_BYTE, 1, 0); if( IS_LOCK_ERROR(lrc1) ) { - pFile->lastErrno = lrc1Errno; + storeLastErrno(pFile, lrc1Errno); rc = lrc1; goto afp_end_lock; } else if( IS_LOCK_ERROR(lrc2) ){ @@ -26861,7 +29955,7 @@ static int afpUnlock(sqlite3_file *id, int eFileLock) { assert( pFile ); OSTRACE(("UNLOCK %d %d was %d(%d,%d) pid=%d (afp)\n", pFile->h, eFileLock, pFile->eFileLock, pFile->pInode->eFileLock, pFile->pInode->nShared, - getpid())); + osGetpid(0))); assert( eFileLock<=SHARED_LOCK ); if( pFile->eFileLock<=eFileLock ){ @@ -26953,23 +30047,22 @@ static int afpUnlock(sqlite3_file *id, int eFileLock) { */ static int afpClose(sqlite3_file *id) { int rc = SQLITE_OK; - if( id ){ - unixFile *pFile = (unixFile*)id; - afpUnlock(id, NO_LOCK); - unixEnterMutex(); - if( pFile->pInode && pFile->pInode->nLock ){ - /* If there are outstanding locks, do not actually close the file just - ** yet because that would clear those locks. Instead, add the file - ** descriptor to pInode->aPending. It will be automatically closed when - ** the last lock is cleared. - */ - setPendingFd(pFile); - } - releaseInodeInfo(pFile); - sqlite3_free(pFile->lockingContext); - rc = closeUnixFile(id); - unixLeaveMutex(); + unixFile *pFile = (unixFile*)id; + assert( id!=0 ); + afpUnlock(id, NO_LOCK); + unixEnterMutex(); + if( pFile->pInode && pFile->pInode->nLock ){ + /* If there are outstanding locks, do not actually close the file just + ** yet because that would clear those locks. Instead, add the file + ** descriptor to pInode->aPending. It will be automatically closed when + ** the last lock is cleared. + */ + setPendingFd(pFile); } + releaseInodeInfo(pFile); + sqlite3_free(pFile->lockingContext); + rc = closeUnixFile(id); + unixLeaveMutex(); return rc; } @@ -27024,7 +30117,7 @@ static int nfsUnlock(sqlite3_file *id, int eFileLock){ ** NB: If you define USE_PREAD or USE_PREAD64, then it might also ** be necessary to define _XOPEN_SOURCE to be 500. This varies from ** one system to another. Since SQLite does not define USE_PREAD -** any any form by default, we will not attempt to define _XOPEN_SOURCE. +** in any form by default, we will not attempt to define _XOPEN_SOURCE. ** See tickets #2741 and #2681. ** ** To avoid stomping the errno value on a failed read the lastErrno value @@ -27039,7 +30132,6 @@ static int seekAndRead(unixFile *id, sqlite3_int64 offset, void *pBuf, int cnt){ TIMER_START; assert( cnt==(cnt&0x1ffff) ); assert( id->h>2 ); - cnt &= 0x1ffff; do{ #if defined(USE_PREAD) got = osPread(id->h, pBuf, cnt, offset); @@ -27049,13 +30141,9 @@ static int seekAndRead(unixFile *id, sqlite3_int64 offset, void *pBuf, int cnt){ SimulateIOError( got = -1 ); #else newOffset = lseek(id->h, offset, SEEK_SET); - SimulateIOError( newOffset-- ); - if( newOffset!=offset ){ - if( newOffset == -1 ){ - ((unixFile*)id)->lastErrno = errno; - }else{ - ((unixFile*)id)->lastErrno = 0; - } + SimulateIOError( newOffset = -1 ); + if( newOffset<0 ){ + storeLastErrno((unixFile*)id, errno); return -1; } got = osRead(id->h, pBuf, cnt); @@ -27064,7 +30152,7 @@ static int seekAndRead(unixFile *id, sqlite3_int64 offset, void *pBuf, int cnt){ if( got<0 ){ if( errno==EINTR ){ got = 1; continue; } prior = 0; - ((unixFile*)id)->lastErrno = errno; + storeLastErrno((unixFile*)id, errno); break; }else if( got>0 ){ cnt -= got; @@ -27129,7 +30217,7 @@ static int unixRead( /* lastErrno set by seekAndRead */ return SQLITE_IOERR_READ; }else{ - pFile->lastErrno = 0; /* not a system error */ + storeLastErrno(pFile, 0); /* not a system error */ /* Unread parts of the buffer must be zero-filled */ memset(&((char*)pBuf)[got], 0, amt-got); return SQLITE_IOERR_SHORT_READ; @@ -27154,21 +30242,21 @@ static int seekAndWriteFd( assert( nBuf==(nBuf&0x1ffff) ); assert( fd>2 ); + assert( piErrno!=0 ); nBuf &= 0x1ffff; TIMER_START; #if defined(USE_PREAD) - do{ rc = osPwrite(fd, pBuf, nBuf, iOff); }while( rc<0 && errno==EINTR ); + do{ rc = (int)osPwrite(fd, pBuf, nBuf, iOff); }while( rc<0 && errno==EINTR ); #elif defined(USE_PREAD64) - do{ rc = osPwrite64(fd, pBuf, nBuf, iOff);}while( rc<0 && errno==EINTR); + do{ rc = (int)osPwrite64(fd, pBuf, nBuf, iOff);}while( rc<0 && errno==EINTR); #else do{ i64 iSeek = lseek(fd, iOff, SEEK_SET); - SimulateIOError( iSeek-- ); - - if( iSeek!=iOff ){ - if( piErrno ) *piErrno = (iSeek==-1 ? errno : 0); - return -1; + SimulateIOError( iSeek = -1 ); + if( iSeek<0 ){ + rc = -1; + break; } rc = osWrite(fd, pBuf, nBuf); }while( rc<0 && errno==EINTR ); @@ -27177,7 +30265,7 @@ static int seekAndWriteFd( TIMER_END; OSTRACE(("WRITE %-3d %5d %7lld %llu\n", fd, rc, iOff, TIMER_ELAPSED)); - if( rc<0 && piErrno ) *piErrno = errno; + if( rc<0 ) *piErrno = errno; return rc; } @@ -27240,7 +30328,7 @@ static int unixWrite( } #endif -#if SQLITE_MAX_MMAP_SIZE>0 +#if defined(SQLITE_MMAP_READWRITE) && SQLITE_MAX_MMAP_SIZE>0 /* Deal with as much of this write request as possible by transfering ** data from the memory mapping using memcpy(). */ if( offsetmmapSize ){ @@ -27256,8 +30344,8 @@ static int unixWrite( } } #endif - - while( amt>0 && (wrote = seekAndWrite(pFile, offset, pBuf, amt))>0 ){ + + while( (wrote = seekAndWrite(pFile, offset, pBuf, amt))0 ){ amt -= wrote; offset += wrote; pBuf = &((char*)pBuf)[wrote]; @@ -27265,12 +30353,12 @@ static int unixWrite( SimulateIOError(( wrote=(-1), amt=1 )); SimulateDiskfullError(( wrote=0, amt=1 )); - if( amt>0 ){ + if( amt>wrote ){ if( wrote<0 && pFile->lastErrno!=ENOSPC ){ /* lastErrno set by seekAndWrite */ return SQLITE_IOERR_WRITE; }else{ - pFile->lastErrno = 0; /* not a system error */ + storeLastErrno(pFile, 0); /* not a system error */ return SQLITE_FULL; } } @@ -27291,9 +30379,9 @@ SQLITE_API int sqlite3_fullsync_count = 0; ** We do not trust systems to provide a working fdatasync(). Some do. ** Others do no. To be safe, we will stick with the (slightly slower) ** fsync(). If you know that your system does support fdatasync() correctly, -** then simply compile with -Dfdatasync=fdatasync +** then simply compile with -Dfdatasync=fdatasync or -DHAVE_FDATASYNC */ -#if !defined(fdatasync) +#if !defined(fdatasync) && !HAVE_FDATASYNC # define fdatasync fsync #endif @@ -27361,10 +30449,15 @@ static int full_fsync(int fd, int fullSync, int dataOnly){ #endif /* If we compiled with the SQLITE_NO_SYNC flag, then syncing is a - ** no-op + ** no-op. But go ahead and call fstat() to validate the file + ** descriptor as we need a method to provoke a failure during + ** coverate testing. */ #ifdef SQLITE_NO_SYNC - rc = SQLITE_OK; + { + struct stat buf; + rc = osFstat(fd, &buf); + } #elif HAVE_FULLFSYNC if( fullSync ){ rc = osFcntl(fd, F_FULLFSYNC, 0); @@ -27430,16 +30523,20 @@ static int openDirectory(const char *zFilename, int *pFd){ char zDirname[MAX_PATHNAME+1]; sqlite3_snprintf(MAX_PATHNAME, zDirname, "%s", zFilename); - for(ii=(int)strlen(zDirname); ii>1 && zDirname[ii]!='/'; ii--); + for(ii=(int)strlen(zDirname); ii>0 && zDirname[ii]!='/'; ii--); if( ii>0 ){ zDirname[ii] = '\0'; - fd = robust_open(zDirname, O_RDONLY|O_BINARY, 0); - if( fd>=0 ){ - OSTRACE(("OPENDIR %-3d %s\n", fd, zDirname)); - } + }else{ + if( zDirname[0]!='/' ) zDirname[0] = '.'; + zDirname[1] = 0; + } + fd = robust_open(zDirname, O_RDONLY|O_BINARY, 0); + if( fd>=0 ){ + OSTRACE(("OPENDIR %-3d %s\n", fd, zDirname)); } *pFd = fd; - return (fd>=0?SQLITE_OK:unixLogError(SQLITE_CANTOPEN_BKPT, "open", zDirname)); + if( fd>=0 ) return SQLITE_OK; + return unixLogError(SQLITE_CANTOPEN_BKPT, "openDirectory", zDirname); } /* @@ -27479,7 +30576,7 @@ static int unixSync(sqlite3_file *id, int flags){ rc = full_fsync(pFile->h, isFullsync, isDataOnly); SimulateIOError( rc=1 ); if( rc ){ - pFile->lastErrno = errno; + storeLastErrno(pFile, errno); return unixLogError(SQLITE_IOERR_FSYNC, "full_fsync", pFile->zPath); } @@ -27492,10 +30589,11 @@ static int unixSync(sqlite3_file *id, int flags){ OSTRACE(("DIRSYNC %s (have_fullfsync=%d fullsync=%d)\n", pFile->zPath, HAVE_FULLFSYNC, isFullsync)); rc = osOpenDirectory(pFile->zPath, &dirfd); - if( rc==SQLITE_OK && dirfd>=0 ){ + if( rc==SQLITE_OK ){ full_fsync(dirfd, 0, 0); robust_close(pFile, dirfd, __LINE__); - }else if( rc==SQLITE_CANTOPEN ){ + }else{ + assert( rc==SQLITE_CANTOPEN ); rc = SQLITE_OK; } pFile->ctrlFlags &= ~UNIXFILE_DIRSYNC; @@ -27521,9 +30619,9 @@ static int unixTruncate(sqlite3_file *id, i64 nByte){ nByte = ((nByte + pFile->szChunk - 1)/pFile->szChunk) * pFile->szChunk; } - rc = robust_ftruncate(pFile->h, (off_t)nByte); + rc = robust_ftruncate(pFile->h, nByte); if( rc ){ - pFile->lastErrno = errno; + storeLastErrno(pFile, errno); return unixLogError(SQLITE_IOERR_TRUNCATE, "ftruncate", pFile->zPath); }else{ #ifdef SQLITE_DEBUG @@ -27563,7 +30661,7 @@ static int unixFileSize(sqlite3_file *id, i64 *pSize){ rc = osFstat(((unixFile*)id)->h, &buf); SimulateIOError( rc=1 ); if( rc!=0 ){ - ((unixFile*)id)->lastErrno = errno; + storeLastErrno((unixFile*)id, errno); return SQLITE_IOERR_FSTAT; } *pSize = buf.st_size; @@ -27599,7 +30697,9 @@ static int fcntlSizeHint(unixFile *pFile, i64 nByte){ i64 nSize; /* Required file size */ struct stat buf; /* Used to hold return values of fstat() */ - if( osFstat(pFile->h, &buf) ) return SQLITE_IOERR_FSTAT; + if( osFstat(pFile->h, &buf) ){ + return SQLITE_IOERR_FSTAT; + } nSize = ((nByte+pFile->szChunk-1) / pFile->szChunk) * pFile->szChunk; if( nSize>(i64)buf.st_size ){ @@ -27614,24 +30714,24 @@ static int fcntlSizeHint(unixFile *pFile, i64 nByte){ }while( err==EINTR ); if( err ) return SQLITE_IOERR_WRITE; #else - /* If the OS does not have posix_fallocate(), fake it. First use - ** ftruncate() to set the file size, then write a single byte to - ** the last byte in each block within the extended region. This - ** is the same technique used by glibc to implement posix_fallocate() - ** on systems that do not have a real fallocate() system call. + /* If the OS does not have posix_fallocate(), fake it. Write a + ** single byte to the last byte in each block that falls entirely + ** within the extended region. Then, if required, a single byte + ** at offset (nSize-1), to set the size of the file correctly. + ** This is a similar technique to that used by glibc on systems + ** that do not have a real fallocate() call. */ int nBlk = buf.st_blksize; /* File-system block size */ + int nWrite = 0; /* Number of bytes written by seekAndWrite */ i64 iWrite; /* Next offset to write to */ - if( robust_ftruncate(pFile->h, nSize) ){ - pFile->lastErrno = errno; - return unixLogError(SQLITE_IOERR_TRUNCATE, "ftruncate", pFile->zPath); - } - iWrite = ((buf.st_size + 2*nBlk - 1)/nBlk)*nBlk-1; - while( iWrite=buf.st_size ); + assert( ((iWrite+1)%nBlk)==0 ); + for(/*no-op*/; iWrite=nSize ) iWrite = nSize - 1; + nWrite = seekAndWrite(pFile, iWrite, "", 1); if( nWrite!=1 ) return SQLITE_IOERR_WRITE; - iWrite += nBlk; } #endif } @@ -27642,7 +30742,7 @@ static int fcntlSizeHint(unixFile *pFile, i64 nByte){ int rc; if( pFile->szChunk<=0 ){ if( robust_ftruncate(pFile->h, nByte) ){ - pFile->lastErrno = errno; + storeLastErrno(pFile, errno); return unixLogError(SQLITE_IOERR_TRUNCATE, "ftruncate", pFile->zPath); } } @@ -27656,7 +30756,7 @@ static int fcntlSizeHint(unixFile *pFile, i64 nByte){ } /* -** If *pArg is inititially negative then this is a query. Set *pArg to +** If *pArg is initially negative then this is a query. Set *pArg to ** 1 or 0 depending on whether or not bit mask of pFile->ctrlFlags is set. ** ** If *pArg is 0 or 1, then clear or set the mask bit of pFile->ctrlFlags. @@ -27684,7 +30784,7 @@ static int unixFileControl(sqlite3_file *id, int op, void *pArg){ *(int*)pArg = pFile->eFileLock; return SQLITE_OK; } - case SQLITE_LAST_ERRNO: { + case SQLITE_FCNTL_LAST_ERRNO: { *(int*)pArg = pFile->lastErrno; return SQLITE_OK; } @@ -27712,7 +30812,7 @@ static int unixFileControl(sqlite3_file *id, int op, void *pArg){ return SQLITE_OK; } case SQLITE_FCNTL_TEMPFILENAME: { - char *zTFile = sqlite3_malloc( pFile->pVfs->mxPathname ); + char *zTFile = sqlite3_malloc64( pFile->pVfs->mxPathname ); if( zTFile ){ unixGetTempname(pFile->pVfs->mxPathname, zTFile); *(char**)pArg = zTFile; @@ -27753,8 +30853,8 @@ static int unixFileControl(sqlite3_file *id, int op, void *pArg){ } #endif #if SQLITE_ENABLE_LOCKING_STYLE && defined(__APPLE__) - case SQLITE_SET_LOCKPROXYFILE: - case SQLITE_GET_LOCKPROXYFILE: { + case SQLITE_FCNTL_SET_LOCKPROXYFILE: + case SQLITE_FCNTL_GET_LOCKPROXYFILE: { return proxyFileControl(id,op,pArg); } #endif /* SQLITE_ENABLE_LOCKING_STYLE && defined(__APPLE__) */ @@ -27863,7 +30963,7 @@ static int unixSectorSize(sqlite3_file *id){ ** Return the device characteristics for the file. ** ** This VFS is set up to return SQLITE_IOCAP_POWERSAFE_OVERWRITE by default. -** However, that choice is contraversial since technically the underlying +** However, that choice is controversial since technically the underlying ** file system does not always provide powersafe overwrites. (In other ** words, after a power-loss event, parts of the file that were never ** written might end up being altered.) However, non-PSOW behavior is very, @@ -27885,8 +30985,27 @@ static int unixDeviceCharacteristics(sqlite3_file *id){ return rc; } -#ifndef SQLITE_OMIT_WAL +#if !defined(SQLITE_OMIT_WAL) || SQLITE_MAX_MMAP_SIZE>0 +/* +** Return the system page size. +** +** This function should not be called directly by other code in this file. +** Instead, it should be called via macro osGetpagesize(). +*/ +static int unixGetpagesize(void){ +#if OS_VXWORKS + return 1024; +#elif defined(_BSD_SOURCE) + return getpagesize(); +#else + return (int)sysconf(_SC_PAGESIZE); +#endif +} + +#endif /* !defined(SQLITE_OMIT_WAL) || SQLITE_MAX_MMAP_SIZE>0 */ + +#ifndef SQLITE_OMIT_WAL /* ** Object used to represent an shared memory buffer. @@ -27970,22 +31089,24 @@ struct unixShm { ** otherwise. */ static int unixShmSystemLock( - unixShmNode *pShmNode, /* Apply locks to this open shared-memory segment */ + unixFile *pFile, /* Open connection to the WAL file */ int lockType, /* F_UNLCK, F_RDLCK, or F_WRLCK */ int ofst, /* First byte of the locking range */ int n /* Number of bytes to lock */ ){ - struct flock f; /* The posix advisory locking structure */ - int rc = SQLITE_OK; /* Result code form fcntl() */ + unixShmNode *pShmNode; /* Apply locks to this open shared-memory segment */ + struct flock f; /* The posix advisory locking structure */ + int rc = SQLITE_OK; /* Result code form fcntl() */ /* Access to the unixShmNode object is serialized by the caller */ + pShmNode = pFile->pInode->pShmNode; assert( sqlite3_mutex_held(pShmNode->mutex) || pShmNode->nRef==0 ); /* Shared locks never span more than one byte */ assert( n==1 || lockType!=F_RDLCK ); /* Locks are within range */ - assert( n>=1 && n=1 && n<=SQLITE_SHM_NLOCK ); if( pShmNode->h>=0 ){ /* Initialize the locking parameters */ @@ -28037,20 +31158,6 @@ static int unixShmSystemLock( return rc; } -/* -** Return the system page size. -** -** This function should not be called directly by other code in this file. -** Instead, it should be called via macro osGetpagesize(). -*/ -static int unixGetpagesize(void){ -#if defined(_BSD_SOURCE) - return getpagesize(); -#else - return (int)sysconf(_SC_PAGESIZE); -#endif -} - /* ** Return the minimum number of 32KB shm regions that should be mapped at ** a time, assuming that each mapping must be an integer multiple of the @@ -28077,7 +31184,7 @@ static int unixShmRegionPerMap(void){ static void unixShmPurge(unixFile *pFd){ unixShmNode *p = pFd->pInode->pShmNode; assert( unixMutexHeld() ); - if( p && p->nRef==0 ){ + if( p && ALWAYS(p->nRef==0) ){ int nShmPerMap = unixShmRegionPerMap(); int i; assert( p->pInode==pFd->pInode ); @@ -28143,7 +31250,7 @@ static int unixOpenSharedMemory(unixFile *pDbFd){ int nShmFilename; /* Size of the SHM filename in bytes */ /* Allocate space for the new unixShm object. */ - p = sqlite3_malloc( sizeof(*p) ); + p = sqlite3_malloc64( sizeof(*p) ); if( p==0 ) return SQLITE_NOMEM; memset(p, 0, sizeof(*p)); assert( pDbFd->pShm==0 ); @@ -28156,12 +31263,15 @@ static int unixOpenSharedMemory(unixFile *pDbFd){ pShmNode = pInode->pShmNode; if( pShmNode==0 ){ struct stat sStat; /* fstat() info for database file */ +#ifndef SQLITE_SHM_DIRECTORY + const char *zBasePath = pDbFd->zPath; +#endif /* Call fstat() to figure out the permissions on the database file. If ** a new *-shm file is created, an attempt will be made to create it ** with the same permissions. */ - if( osFstat(pDbFd->h, &sStat) && pInode->bProcessLock==0 ){ + if( osFstat(pDbFd->h, &sStat) ){ rc = SQLITE_IOERR_FSTAT; goto shm_open_err; } @@ -28169,9 +31279,9 @@ static int unixOpenSharedMemory(unixFile *pDbFd){ #ifdef SQLITE_SHM_DIRECTORY nShmFilename = sizeof(SQLITE_SHM_DIRECTORY) + 31; #else - nShmFilename = 6 + (int)strlen(pDbFd->zPath); + nShmFilename = 6 + (int)strlen(zBasePath); #endif - pShmNode = sqlite3_malloc( sizeof(*pShmNode) + nShmFilename ); + pShmNode = sqlite3_malloc64( sizeof(*pShmNode) + nShmFilename ); if( pShmNode==0 ){ rc = SQLITE_NOMEM; goto shm_open_err; @@ -28183,7 +31293,7 @@ static int unixOpenSharedMemory(unixFile *pDbFd){ SQLITE_SHM_DIRECTORY "/sqlite-shm-%x-%x", (u32)sStat.st_ino, (u32)sStat.st_dev); #else - sqlite3_snprintf(nShmFilename, zShmFilename, "%s-shm", pDbFd->zPath); + sqlite3_snprintf(nShmFilename, zShmFilename, "%s-shm", zBasePath); sqlite3FileSuffix3(pDbFd->zPath, zShmFilename); #endif pShmNode->h = -1; @@ -28211,19 +31321,19 @@ static int unixOpenSharedMemory(unixFile *pDbFd){ ** is owned by the same user that owns the original database. Otherwise, ** the original owner will not be able to connect. */ - osFchown(pShmNode->h, sStat.st_uid, sStat.st_gid); + robustFchown(pShmNode->h, sStat.st_uid, sStat.st_gid); /* Check to see if another process is holding the dead-man switch. ** If not, truncate the file to zero length. */ rc = SQLITE_OK; - if( unixShmSystemLock(pShmNode, F_WRLCK, UNIX_SHM_DMS, 1)==SQLITE_OK ){ + if( unixShmSystemLock(pDbFd, F_WRLCK, UNIX_SHM_DMS, 1)==SQLITE_OK ){ if( robust_ftruncate(pShmNode->h, 0) ){ rc = unixLogError(SQLITE_IOERR_SHMOPEN, "ftruncate", zShmFilename); } } if( rc==SQLITE_OK ){ - rc = unixShmSystemLock(pShmNode, F_RDLCK, UNIX_SHM_DMS, 1); + rc = unixShmSystemLock(pDbFd, F_RDLCK, UNIX_SHM_DMS, 1); } if( rc ) goto shm_open_err; } @@ -28348,7 +31458,8 @@ static int unixShmMap( /* Write to the last byte of each newly allocated or extended page */ assert( (nByte % pgsz)==0 ); for(iPg=(sStat.st_size/pgsz); iPg<(nByte/pgsz); iPg++){ - if( seekAndWriteFd(pShmNode->h, iPg*pgsz + pgsz-1, "", 1, 0)!=1 ){ + int x = 0; + if( seekAndWriteFd(pShmNode->h, iPg*pgsz + pgsz-1, "", 1, &x)!=1 ){ const char *zFile = pShmNode->zFilename; rc = unixLogError(SQLITE_IOERR_SHMSIZE, "write", zFile); goto shmpage_out; @@ -28381,7 +31492,7 @@ static int unixShmMap( goto shmpage_out; } }else{ - pMem = sqlite3_malloc(szRegion); + pMem = sqlite3_malloc64(szRegion); if( pMem==0 ){ rc = SQLITE_NOMEM; goto shmpage_out; @@ -28455,7 +31566,7 @@ static int unixShmLock( /* Unlock the system-level locks */ if( (mask & allMask)==0 ){ - rc = unixShmSystemLock(pShmNode, F_UNLCK, ofst+UNIX_SHM_BASE, n); + rc = unixShmSystemLock(pDbFd, F_UNLCK, ofst+UNIX_SHM_BASE, n); }else{ rc = SQLITE_OK; } @@ -28483,7 +31594,7 @@ static int unixShmLock( /* Get shared locks at the system level, if necessary */ if( rc==SQLITE_OK ){ if( (allShared & mask)==0 ){ - rc = unixShmSystemLock(pShmNode, F_RDLCK, ofst+UNIX_SHM_BASE, n); + rc = unixShmSystemLock(pDbFd, F_RDLCK, ofst+UNIX_SHM_BASE, n); }else{ rc = SQLITE_OK; } @@ -28508,7 +31619,7 @@ static int unixShmLock( ** also mark the local connection as being locked. */ if( rc==SQLITE_OK ){ - rc = unixShmSystemLock(pShmNode, F_WRLCK, ofst+UNIX_SHM_BASE, n); + rc = unixShmSystemLock(pDbFd, F_WRLCK, ofst+UNIX_SHM_BASE, n); if( rc==SQLITE_OK ){ assert( (p->sharedMask & mask)==0 ); p->exclMask |= mask; @@ -28517,7 +31628,7 @@ static int unixShmLock( } sqlite3_mutex_leave(pShmNode->mutex); OSTRACE(("SHM-LOCK shmid-%d, pid-%d got %03x,%03x\n", - p->id, getpid(), p->sharedMask, p->exclMask)); + p->id, osGetpid(0), p->sharedMask, p->exclMask)); return rc; } @@ -28531,7 +31642,8 @@ static void unixShmBarrier( sqlite3_file *fd /* Database file holding the shared memory */ ){ UNUSED_PARAMETER(fd); - unixEnterMutex(); + sqlite3MemoryBarrier(); /* compiler-defined memory barrier */ + unixEnterMutex(); /* Also mutex, for redundancy */ unixLeaveMutex(); } @@ -28576,7 +31688,9 @@ static int unixShmUnmap( assert( pShmNode->nRef>0 ); pShmNode->nRef--; if( pShmNode->nRef==0 ){ - if( deleteFlag && pShmNode->h>=0 ) osUnlink(pShmNode->zFilename); + if( deleteFlag && pShmNode->h>=0 ){ + osUnlink(pShmNode->zFilename); + } unixShmPurge(pDbFd); } unixLeaveMutex(); @@ -28639,7 +31753,9 @@ static void unixRemapfile( assert( pFd->mmapSizeActual>=pFd->mmapSize ); assert( MAP_FAILED!=0 ); +#ifdef SQLITE_MMAP_READWRITE if( (pFd->ctrlFlags & UNIXFILE_RDONLY)==0 ) flags |= PROT_WRITE; +#endif if( pOrig ){ #if HAVE_MREMAP @@ -28711,17 +31827,14 @@ static void unixRemapfile( ** recreated as a result of outstanding references) or an SQLite error ** code otherwise. */ -static int unixMapfile(unixFile *pFd, i64 nByte){ - i64 nMap = nByte; - int rc; - +static int unixMapfile(unixFile *pFd, i64 nMap){ assert( nMap>=0 || pFd->nFetchOut==0 ); + assert( nMap>0 || (pFd->mmapSize==0 && pFd->pMapRegion==0) ); if( pFd->nFetchOut>0 ) return SQLITE_OK; if( nMap<0 ){ struct stat statbuf; /* Low-level file information */ - rc = osFstat(pFd->h, &statbuf); - if( rc!=SQLITE_OK ){ + if( osFstat(pFd->h, &statbuf) ){ return SQLITE_IOERR_FSTAT; } nMap = statbuf.st_size; @@ -28730,12 +31843,9 @@ static int unixMapfile(unixFile *pFd, i64 nByte){ nMap = pFd->mmapSizeMax; } + assert( nMap>0 || (pFd->mmapSize==0 && pFd->pMapRegion==0) ); if( nMap!=pFd->mmapSize ){ - if( nMap>0 ){ - unixRemapfile(pFd, nMap); - }else{ - unixUnmapfile(pFd); - } + unixRemapfile(pFd, nMap); } return SQLITE_OK; @@ -28832,7 +31942,7 @@ static int unixUnfetch(sqlite3_file *fd, i64 iOff, void *p){ ** looks at the filesystem type and tries to guess the best locking ** strategy from that. ** -** For finder-funtion F, two objects are created: +** For finder-function F, two objects are created: ** ** (1) The real finder-function named "FImpt()". ** @@ -28853,7 +31963,7 @@ static int unixUnfetch(sqlite3_file *fd, i64 iOff, void *p){ ** * An I/O method finder function called FINDER that returns a pointer ** to the METHOD object in the previous bullet. */ -#define IOMETHODS(FINDER, METHOD, VERSION, CLOSE, LOCK, UNLOCK, CKLOCK) \ +#define IOMETHODS(FINDER,METHOD,VERSION,CLOSE,LOCK,UNLOCK,CKLOCK,SHMMAP) \ static const sqlite3_io_methods METHOD = { \ VERSION, /* iVersion */ \ CLOSE, /* xClose */ \ @@ -28868,7 +31978,7 @@ static const sqlite3_io_methods METHOD = { \ unixFileControl, /* xFileControl */ \ unixSectorSize, /* xSectorSize */ \ unixDeviceCharacteristics, /* xDeviceCapabilities */ \ - unixShmMap, /* xShmMap */ \ + SHMMAP, /* xShmMap */ \ unixShmLock, /* xShmLock */ \ unixShmBarrier, /* xShmBarrier */ \ unixShmUnmap, /* xShmUnmap */ \ @@ -28894,16 +32004,18 @@ IOMETHODS( unixClose, /* xClose method */ unixLock, /* xLock method */ unixUnlock, /* xUnlock method */ - unixCheckReservedLock /* xCheckReservedLock method */ + unixCheckReservedLock, /* xCheckReservedLock method */ + unixShmMap /* xShmMap method */ ) IOMETHODS( nolockIoFinder, /* Finder function name */ nolockIoMethods, /* sqlite3_io_methods object name */ - 1, /* shared memory is disabled */ + 3, /* shared memory is disabled */ nolockClose, /* xClose method */ nolockLock, /* xLock method */ nolockUnlock, /* xUnlock method */ - nolockCheckReservedLock /* xCheckReservedLock method */ + nolockCheckReservedLock, /* xCheckReservedLock method */ + 0 /* xShmMap method */ ) IOMETHODS( dotlockIoFinder, /* Finder function name */ @@ -28912,10 +32024,11 @@ IOMETHODS( dotlockClose, /* xClose method */ dotlockLock, /* xLock method */ dotlockUnlock, /* xUnlock method */ - dotlockCheckReservedLock /* xCheckReservedLock method */ + dotlockCheckReservedLock, /* xCheckReservedLock method */ + 0 /* xShmMap method */ ) -#if SQLITE_ENABLE_LOCKING_STYLE && !OS_VXWORKS +#if SQLITE_ENABLE_LOCKING_STYLE IOMETHODS( flockIoFinder, /* Finder function name */ flockIoMethods, /* sqlite3_io_methods object name */ @@ -28923,7 +32036,8 @@ IOMETHODS( flockClose, /* xClose method */ flockLock, /* xLock method */ flockUnlock, /* xUnlock method */ - flockCheckReservedLock /* xCheckReservedLock method */ + flockCheckReservedLock, /* xCheckReservedLock method */ + 0 /* xShmMap method */ ) #endif @@ -28932,10 +32046,11 @@ IOMETHODS( semIoFinder, /* Finder function name */ semIoMethods, /* sqlite3_io_methods object name */ 1, /* shared memory is disabled */ - semClose, /* xClose method */ - semLock, /* xLock method */ - semUnlock, /* xUnlock method */ - semCheckReservedLock /* xCheckReservedLock method */ + semXClose, /* xClose method */ + semXLock, /* xLock method */ + semXUnlock, /* xUnlock method */ + semXCheckReservedLock, /* xCheckReservedLock method */ + 0 /* xShmMap method */ ) #endif @@ -28947,7 +32062,8 @@ IOMETHODS( afpClose, /* xClose method */ afpLock, /* xLock method */ afpUnlock, /* xUnlock method */ - afpCheckReservedLock /* xCheckReservedLock method */ + afpCheckReservedLock, /* xCheckReservedLock method */ + 0 /* xShmMap method */ ) #endif @@ -28972,7 +32088,8 @@ IOMETHODS( proxyClose, /* xClose method */ proxyLock, /* xLock method */ proxyUnlock, /* xUnlock method */ - proxyCheckReservedLock /* xCheckReservedLock method */ + proxyCheckReservedLock, /* xCheckReservedLock method */ + 0 /* xShmMap method */ ) #endif @@ -28985,7 +32102,8 @@ IOMETHODS( unixClose, /* xClose method */ unixLock, /* xLock method */ nfsUnlock, /* xUnlock method */ - unixCheckReservedLock /* xCheckReservedLock method */ + unixCheckReservedLock, /* xCheckReservedLock method */ + 0 /* xShmMap method */ ) #endif @@ -29055,15 +32173,13 @@ static const sqlite3_io_methods #endif /* defined(__APPLE__) && SQLITE_ENABLE_LOCKING_STYLE */ -#if OS_VXWORKS && SQLITE_ENABLE_LOCKING_STYLE -/* -** This "finder" function attempts to determine the best locking strategy -** for the database file "filePath". It then returns the sqlite3_io_methods -** object that implements that strategy. -** -** This is for VXWorks only. +#if OS_VXWORKS +/* +** This "finder" function for VxWorks checks to see if posix advisory +** locking works. If it does, then that is what is used. If it does not +** work, then fallback to named semaphore locking. */ -static const sqlite3_io_methods *autolockIoFinderImpl( +static const sqlite3_io_methods *vxworksIoFinderImpl( const char *filePath, /* name of the database file */ unixFile *pNew /* the open file object */ ){ @@ -29089,12 +32205,12 @@ static const sqlite3_io_methods *autolockIoFinderImpl( } } static const sqlite3_io_methods - *(*const autolockIoFinder)(const char*,unixFile*) = autolockIoFinderImpl; + *(*const vxworksIoFinder)(const char*,unixFile*) = vxworksIoFinderImpl; -#endif /* OS_VXWORKS && SQLITE_ENABLE_LOCKING_STYLE */ +#endif /* OS_VXWORKS */ /* -** An abstract type for a pointer to a IO method finder function: +** An abstract type for a pointer to an IO method finder function: */ typedef const sqlite3_io_methods *(*finder_type)(const char*,unixFile*); @@ -29210,7 +32326,7 @@ static int fillInUnixFile( ** the afpLockingContext. */ afpLockingContext *pCtx; - pNew->lockingContext = pCtx = sqlite3_malloc( sizeof(*pCtx) ); + pNew->lockingContext = pCtx = sqlite3_malloc64( sizeof(*pCtx) ); if( pCtx==0 ){ rc = SQLITE_NOMEM; }else{ @@ -29240,7 +32356,7 @@ static int fillInUnixFile( int nFilename; assert( zFilename!=0 ); nFilename = (int)strlen(zFilename) + 6; - zLockFile = (char *)sqlite3_malloc(nFilename); + zLockFile = (char *)sqlite3_malloc64(nFilename); if( zLockFile==0 ){ rc = SQLITE_NOMEM; }else{ @@ -29273,7 +32389,7 @@ static int fillInUnixFile( } #endif - pNew->lastErrno = 0; + storeLastErrno(pNew, 0); #if OS_VXWORKS if( rc!=SQLITE_OK ){ if( h>=0 ) robust_close(pNew, h, __LINE__); @@ -29298,21 +32414,19 @@ static int fillInUnixFile( */ static const char *unixTempFileDir(void){ static const char *azDirs[] = { - 0, 0, 0, "/var/tmp", "/usr/tmp", "/tmp", - 0 /* List terminator */ + "." }; unsigned int i; struct stat buf; - const char *zDir = 0; + const char *zDir = sqlite3_temp_directory; - azDirs[0] = sqlite3_temp_directory; - if( !azDirs[1] ) azDirs[1] = getenv("SQLITE_TMPDIR"); - if( !azDirs[2] ) azDirs[2] = getenv("TMPDIR"); + if( !azDirs[0] ) azDirs[0] = getenv("SQLITE_TMPDIR"); + if( !azDirs[1] ) azDirs[1] = getenv("TMPDIR"); for(i=0; imxPathname bytes. */ static int unixGetTempname(int nBuf, char *zBuf){ - static const unsigned char zChars[] = - "abcdefghijklmnopqrstuvwxyz" - "ABCDEFGHIJKLMNOPQRSTUVWXYZ" - "0123456789"; - unsigned int i, j; const char *zDir; + int iLimit = 0; /* It's odd to simulate an io-error here, but really this is just ** using the io-error infrastructure to test that SQLite handles this @@ -29343,24 +32453,14 @@ static int unixGetTempname(int nBuf, char *zBuf){ SimulateIOError( return SQLITE_IOERR ); zDir = unixTempFileDir(); - if( zDir==0 ) zDir = "."; - - /* Check that the output buffer is large enough for the temporary file - ** name. If it is not, return SQLITE_ERROR. - */ - if( (strlen(zDir) + strlen(SQLITE_TEMP_FILE_PREFIX) + 18) >= (size_t)nBuf ){ - return SQLITE_ERROR; - } - do{ - sqlite3_snprintf(nBuf-18, zBuf, "%s/"SQLITE_TEMP_FILE_PREFIX, zDir); - j = (int)strlen(zBuf); - sqlite3_randomness(15, &zBuf[j]); - for(i=0; i<15; i++, j++){ - zBuf[j] = (char)zChars[ ((unsigned char)zBuf[j])%(sizeof(zChars)-1) ]; - } - zBuf[j] = 0; - zBuf[j+1] = 0; + u64 r; + sqlite3_randomness(sizeof(r), &r); + assert( nBuf>2 ); + zBuf[nBuf-2] = 0; + sqlite3_snprintf(nBuf, zBuf, "%s/"SQLITE_TEMP_FILE_PREFIX"%llx%c", + zDir, r, 0); + if( zBuf[nBuf-2]!=0 || (iLimit++)>10 ) return SQLITE_ERROR; }while( osAccess(zBuf,0)==0 ); return SQLITE_OK; } @@ -29408,7 +32508,7 @@ static UnixUnusedFd *findReusableFd(const char *zPath, int flags){ ** descriptor on the same path, fail, and return an error to SQLite. ** ** Even if a subsequent open() call does succeed, the consequences of - ** not searching for a resusable file descriptor are not dire. */ + ** not searching for a reusable file descriptor are not dire. */ if( 0==osStat(zPath, &sStat) ){ unixInodeInfo *pInode; @@ -29439,7 +32539,7 @@ static UnixUnusedFd *findReusableFd(const char *zPath, int flags){ ** written to *pMode. If an IO error occurs, an SQLite error code is ** returned and the value of *pMode is not modified. ** -** In most cases cases, this routine sets *pMode to 0, which will become +** In most cases, this routine sets *pMode to 0, which will become ** an indication to robust_open() to create the file using ** SQLITE_DEFAULT_FILE_PERMISSIONS adjusted by the umask. ** But if the file being opened is a WAL or regular journal file, then @@ -29482,16 +32582,19 @@ static int findCreateFileMode( ** used by the test_multiplex.c module. */ nDb = sqlite3Strlen30(zPath) - 1; -#ifdef SQLITE_ENABLE_8_3_NAMES - while( nDb>0 && sqlite3Isalnum(zPath[nDb]) ) nDb--; - if( nDb==0 || zPath[nDb]!='-' ) return SQLITE_OK; -#else while( zPath[nDb]!='-' ){ +#ifndef SQLITE_ENABLE_8_3_NAMES + /* In the normal case (8+3 filenames disabled) the journal filename + ** is guaranteed to contain a '-' character. */ assert( nDb>0 ); - assert( zPath[nDb]!='\n' ); + assert( sqlite3Isalnum(zPath[nDb]) ); +#else + /* If 8+3 names are possible, then the journal file might not contain + ** a '-' character. So check for that case and return early. */ + if( nDb==0 || zPath[nDb]=='.' ) return SQLITE_OK; +#endif nDb--; } -#endif memcpy(zDb, zPath, nDb); zDb[nDb] = '\0'; @@ -29604,8 +32707,8 @@ static int unixOpen( ** the same instant might all reset the PRNG. But multiple resets ** are harmless. */ - if( randomnessPid!=getpid() ){ - randomnessPid = getpid(); + if( randomnessPid!=osGetpid(0) ){ + randomnessPid = osGetpid(0); sqlite3_randomness(0,0); } @@ -29617,7 +32720,7 @@ static int unixOpen( if( pUnused ){ fd = pUnused->fd; }else{ - pUnused = sqlite3_malloc(sizeof(*pUnused)); + pUnused = sqlite3_malloc64(sizeof(*pUnused)); if( !pUnused ){ return SQLITE_NOMEM; } @@ -29632,7 +32735,7 @@ static int unixOpen( }else if( !zName ){ /* If zName is NULL, the upper layer is requesting a temp file. */ assert(isDelete && !syncDir); - rc = unixGetTempname(MAX_PATHNAME+2, zTmpname); + rc = unixGetTempname(pVfs->mxPathname, zTmpname); if( rc!=SQLITE_OK ){ return rc; } @@ -29665,7 +32768,8 @@ static int unixOpen( } fd = robust_open(zName, openFlags, openMode); OSTRACE(("OPENX %-3d %s 0%o\n", fd, zName, openFlags)); - if( fd<0 && errno!=EISDIR && isReadWrite && !isExclusive ){ + assert( !isExclusive || (openFlags & O_CREAT)!=0 ); + if( fd<0 && errno!=EISDIR && isReadWrite ){ /* Failed to open the file for read/write access. Try read-only. */ flags &= ~(SQLITE_OPEN_READWRITE|SQLITE_OPEN_CREATE); openFlags &= ~(O_RDWR|O_CREAT); @@ -29684,7 +32788,7 @@ static int unixOpen( ** the same as the original database. */ if( flags & (SQLITE_OPEN_WAL|SQLITE_OPEN_MAIN_JOURNAL) ){ - osFchown(fd, uid, gid); + robustFchown(fd, uid, gid); } } assert( fd>=0 ); @@ -29700,6 +32804,12 @@ static int unixOpen( if( isDelete ){ #if OS_VXWORKS zPath = zName; +#elif defined(SQLITE_UNLINK_AFTER_CLOSE) + zPath = sqlite3_mprintf("%s", zName); + if( zPath==0 ){ + robust_close(p, fd, __LINE__); + return SQLITE_NOMEM; + } #else osUnlink(zName); #endif @@ -29715,13 +32825,16 @@ static int unixOpen( #if defined(__APPLE__) || SQLITE_ENABLE_LOCKING_STYLE if( fstatfs(fd, &fsInfo) == -1 ){ - ((unixFile*)pFile)->lastErrno = errno; + storeLastErrno(p, errno); robust_close(p, fd, __LINE__); return SQLITE_IOERR_ACCESS; } if (0 == strncmp("msdos", fsInfo.f_fstypename, 5)) { ((unixFile*)pFile)->fsFlags |= SQLITE_FSFLAGS_IS_MSDOS; } + if (0 == strncmp("exfat", fsInfo.f_fstypename, 5)) { + ((unixFile*)pFile)->fsFlags |= SQLITE_FSFLAGS_IS_MSDOS; + } #endif /* Set up appropriate ctrlFlags */ @@ -29744,19 +32857,6 @@ static int unixOpen( if( envforce!=NULL ){ useProxy = atoi(envforce)>0; }else{ - if( statfs(zPath, &fsInfo) == -1 ){ - /* In theory, the close(fd) call is sub-optimal. If the file opened - ** with fd is a database file, and there are other connections open - ** on that file that are currently holding advisory locks on it, - ** then the call to close() will cancel those locks. In practice, - ** we're assuming that statfs() doesn't fail very often. At least - ** not while other file descriptors opened by the same process on - ** the same file are working. */ - p->lastErrno = errno; - robust_close(p, fd, __LINE__); - rc = SQLITE_IOERR_ACCESS; - goto open_finished; - } useProxy = !(fsInfo.f_flags&MNT_LOCAL); } if( useProxy ){ @@ -29800,7 +32900,11 @@ static int unixDelete( UNUSED_PARAMETER(NotUsed); SimulateIOError(return SQLITE_IOERR_DELETE); if( osUnlink(zPath)==(-1) ){ - if( errno==ENOENT ){ + if( errno==ENOENT +#if OS_VXWORKS + || osAccess(zPath,0)!=0 +#endif + ){ rc = SQLITE_IOERR_DELETE_NOENT; }else{ rc = unixLogError(SQLITE_IOERR_DELETE, "unlink", zPath); @@ -29821,7 +32925,8 @@ static int unixDelete( rc = unixLogError(SQLITE_IOERR_DIR_FSYNC, "fsync", zPath); } robust_close(0, fd, __LINE__); - }else if( rc==SQLITE_CANTOPEN ){ + }else{ + assert( rc==SQLITE_CANTOPEN ); rc = SQLITE_OK; } } @@ -29845,29 +32950,19 @@ static int unixAccess( int flags, /* What do we want to learn about the zPath file? */ int *pResOut /* Write result boolean here */ ){ - int amode = 0; UNUSED_PARAMETER(NotUsed); SimulateIOError( return SQLITE_IOERR_ACCESS; ); - switch( flags ){ - case SQLITE_ACCESS_EXISTS: - amode = F_OK; - break; - case SQLITE_ACCESS_READWRITE: - amode = W_OK|R_OK; - break; - case SQLITE_ACCESS_READ: - amode = R_OK; - break; + assert( pResOut!=0 ); - default: - assert(!"Invalid flags argument"); - } - *pResOut = (osAccess(zPath, amode)==0); - if( flags==SQLITE_ACCESS_EXISTS && *pResOut ){ + /* The spec says there are three possible values for flags. But only + ** two of them are actually used */ + assert( flags==SQLITE_ACCESS_EXISTS || flags==SQLITE_ACCESS_READWRITE ); + + if( flags==SQLITE_ACCESS_EXISTS ){ struct stat buf; - if( 0==osStat(zPath, &buf) && buf.st_size==0 ){ - *pResOut = 0; - } + *pResOut = (0==osStat(zPath, &buf) && buf.st_size>0); + }else{ + *pResOut = osAccess(zPath, W_OK|R_OK)==0; } return SQLITE_OK; } @@ -29888,6 +32983,7 @@ static int unixFullPathname( int nOut, /* Size of output buffer in bytes */ char *zOut /* Output buffer */ ){ + int nByte; /* It's odd to simulate an io-error here, but really this is just ** using the io-error infrastructure to test that SQLite handles this @@ -29899,17 +32995,54 @@ static int unixFullPathname( assert( pVfs->mxPathname==MAX_PATHNAME ); UNUSED_PARAMETER(pVfs); - zOut[nOut-1] = '\0'; - if( zPath[0]=='/' ){ + /* Attempt to resolve the path as if it were a symbolic link. If it is + ** a symbolic link, the resolved path is stored in buffer zOut[]. Or, if + ** the identified file is not a symbolic link or does not exist, then + ** zPath is copied directly into zOut. Either way, nByte is left set to + ** the size of the string copied into zOut[] in bytes. */ + nByte = osReadlink(zPath, zOut, nOut-1); + if( nByte<0 ){ + if( errno!=EINVAL && errno!=ENOENT ){ + return unixLogError(SQLITE_CANTOPEN_BKPT, "readlink", zPath); + } sqlite3_snprintf(nOut, zOut, "%s", zPath); + nByte = sqlite3Strlen30(zOut); }else{ + zOut[nByte] = '\0'; + } + + /* If buffer zOut[] now contains an absolute path there is nothing more + ** to do. If it contains a relative path, do the following: + ** + ** * move the relative path string so that it is at the end of th + ** zOut[] buffer. + ** * Call getcwd() to read the path of the current working directory + ** into the start of the zOut[] buffer. + ** * Append a '/' character to the cwd string and move the + ** relative path back within the buffer so that it immediately + ** follows the '/'. + ** + ** This code is written so that if the combination of the CWD and relative + ** path are larger than the allocated size of zOut[] the CWD is silently + ** truncated to make it fit. This is Ok, as SQLite refuses to open any + ** file for which this function returns a full path larger than (nOut-8) + ** bytes in size. */ + testcase( nByte==nOut-5 ); + testcase( nByte==nOut-4 ); + if( zOut[0]!='/' && nByte | ":auto:"); -** sqlite3_file_control(db, dbname, SQLITE_GET_LOCKPROXYFILE, &); +** sqlite3_file_control(db, dbname, SQLITE_FCNTL_GET_LOCKPROXYFILE, +** &); ** ** ** SQL pragmas @@ -30221,7 +33360,7 @@ static int unixGetLastError(sqlite3_vfs *NotUsed, int NotUsed2, char *NotUsed3){ ** proxy path against the values stored in the conch. The conch file is ** stored in the same directory as the database file and the file name ** is patterned after the database file name as ".-conch". -** If the conch file does not exist, or it's contents do not match the +** If the conch file does not exist, or its contents do not match the ** host ID and/or proxy path, then the lock is escalated to an exclusive ** lock and the conch file contents is updated with the host ID and proxy ** path and the lock is downgraded to a shared lock again. If the conch @@ -30273,7 +33412,7 @@ static int unixGetLastError(sqlite3_vfs *NotUsed, int NotUsed2, char *NotUsed3){ ** setting the environment variable SQLITE_FORCE_PROXY_LOCKING to 1 will ** force proxy locking to be used for every database file opened, and 0 ** will force automatic proxy locking to be disabled for all database -** files (explicity calling the SQLITE_SET_LOCKPROXYFILE pragma or +** files (explicitly calling the SQLITE_FCNTL_SET_LOCKPROXYFILE pragma or ** sqlite_file_control API is not affected by SQLITE_FORCE_PROXY_LOCKING). */ @@ -30294,6 +33433,7 @@ struct proxyLockingContext { char *lockProxyPath; /* Name of the proxy lock file */ char *dbPath; /* Name of the open file */ int conchHeld; /* 1 if the conch is held, -1 if lockless */ + int nFails; /* Number of conch taking failures */ void *oldLockingContext; /* Original lockingcontext to restore on close */ sqlite3_io_methods const *pOldMethod; /* Original I/O methods for close */ }; @@ -30315,7 +33455,7 @@ static int proxyGetLockPath(const char *dbPath, char *lPath, size_t maxLen){ { if( !confstr(_CS_DARWIN_USER_TEMP_DIR, lPath, maxLen) ){ OSTRACE(("GETLOCKPATH failed %s errno=%d pid=%d\n", - lPath, errno, getpid())); + lPath, errno, osGetpid(0))); return SQLITE_IOERR_LOCK; } len = strlcat(lPath, "sqliteplocks", maxLen); @@ -30337,7 +33477,7 @@ static int proxyGetLockPath(const char *dbPath, char *lPath, size_t maxLen){ } lPath[i+len]='\0'; strlcat(lPath, ":auto:", maxLen); - OSTRACE(("GETLOCKPATH proxy lock path=%s pid=%d\n", lPath, getpid())); + OSTRACE(("GETLOCKPATH proxy lock path=%s pid=%d\n", lPath, osGetpid(0))); return SQLITE_OK; } @@ -30364,7 +33504,7 @@ static int proxyCreateLockPath(const char *lockPath){ if( err!=EEXIST ) { OSTRACE(("CREATELOCKPATH FAILED creating %s, " "'%s' proxy lock path=%s pid=%d\n", - buf, strerror(err), lockPath, getpid())); + buf, strerror(err), lockPath, osGetpid(0))); return err; } } @@ -30373,7 +33513,7 @@ static int proxyCreateLockPath(const char *lockPath){ } buf[i] = lockPath[i]; } - OSTRACE(("CREATELOCKPATH proxy lock path=%s pid=%d\n", lockPath, getpid())); + OSTRACE(("CREATELOCKPATH proxy lock path=%s pid=%d\n",lockPath,osGetpid(0))); return 0; } @@ -30407,7 +33547,7 @@ static int proxyCreateUnixFile( if( pUnused ){ fd = pUnused->fd; }else{ - pUnused = sqlite3_malloc(sizeof(*pUnused)); + pUnused = sqlite3_malloc64(sizeof(*pUnused)); if( !pUnused ){ return SQLITE_NOMEM; } @@ -30440,7 +33580,7 @@ static int proxyCreateUnixFile( } } - pNew = (unixFile *)sqlite3_malloc(sizeof(*pNew)); + pNew = (unixFile *)sqlite3_malloc64(sizeof(*pNew)); if( pNew==NULL ){ rc = SQLITE_NOMEM; goto end_create_proxy; @@ -30473,8 +33613,10 @@ SQLITE_API int sqlite3_hostid_num = 0; #define PROXY_HOSTIDLEN 16 /* conch file host id length */ +#ifdef HAVE_GETHOSTUUID /* Not always defined in the headers as it ought to be */ extern int gethostuuid(uuid_t id, const struct timespec *wait); +#endif /* get the host ID via gethostuuid(), pHostID must point to PROXY_HOSTIDLEN ** bytes of writable memory. @@ -30482,10 +33624,9 @@ extern int gethostuuid(uuid_t id, const struct timespec *wait); static int proxyGetHostID(unsigned char *pHostID, int *pError){ assert(PROXY_HOSTIDLEN == sizeof(uuid_t)); memset(pHostID, 0, PROXY_HOSTIDLEN); -#if defined(__MAX_OS_X_VERSION_MIN_REQUIRED)\ - && __MAC_OS_X_VERSION_MIN_REQUIRED<1050 +#ifdef HAVE_GETHOSTUUID { - static const struct timespec timeout = {1, 0}; /* 1 sec timeout */ + struct timespec timeout = {1, 0}; /* 1 sec timeout */ if( gethostuuid(pHostID, &timeout) ){ int err = errno; if( pError ){ @@ -30600,7 +33741,7 @@ static int proxyConchLock(unixFile *pFile, uuid_t myHostID, int lockType){ */ struct stat buf; if( osFstat(conchFile->h, &buf) ){ - pFile->lastErrno = errno; + storeLastErrno(pFile, errno); return SQLITE_IOERR_LOCK; } @@ -30620,7 +33761,7 @@ static int proxyConchLock(unixFile *pFile, uuid_t myHostID, int lockType){ char tBuf[PROXY_MAXCONCHLEN]; int len = osPread(conchFile->h, tBuf, PROXY_MAXCONCHLEN, 0); if( len<0 ){ - pFile->lastErrno = errno; + storeLastErrno(pFile, errno); return SQLITE_IOERR_LOCK; } if( len>PROXY_PATHINDEX && tBuf[0]==(char)PROXY_CONCHVERSION){ @@ -30640,7 +33781,7 @@ static int proxyConchLock(unixFile *pFile, uuid_t myHostID, int lockType){ if( 0==proxyBreakConchLock(pFile, myHostID) ){ rc = SQLITE_OK; if( lockType==EXCLUSIVE_LOCK ){ - rc = conchFile->pMethod->xLock((sqlite3_file*)conchFile, SHARED_LOCK); + rc = conchFile->pMethod->xLock((sqlite3_file*)conchFile, SHARED_LOCK); } if( !rc ){ rc = conchFile->pMethod->xLock((sqlite3_file*)conchFile, lockType); @@ -30678,11 +33819,12 @@ static int proxyTakeConch(unixFile *pFile){ int forceNewLockPath = 0; OSTRACE(("TAKECONCH %d for %s pid=%d\n", conchFile->h, - (pCtx->lockProxyPath ? pCtx->lockProxyPath : ":auto:"), getpid())); + (pCtx->lockProxyPath ? pCtx->lockProxyPath : ":auto:"), + osGetpid(0))); rc = proxyGetHostID(myHostID, &pError); if( (rc&0xff)==SQLITE_IOERR ){ - pFile->lastErrno = pError; + storeLastErrno(pFile, pError); goto end_takeconch; } rc = proxyConchLock(pFile, myHostID, SHARED_LOCK); @@ -30693,7 +33835,7 @@ static int proxyTakeConch(unixFile *pFile){ readLen = seekAndRead((unixFile*)conchFile, 0, readBuf, PROXY_MAXCONCHLEN); if( readLen<0 ){ /* I/O error: lastErrno set by seekAndRead */ - pFile->lastErrno = conchFile->lastErrno; + storeLastErrno(pFile, conchFile->lastErrno); rc = SQLITE_IOERR_READ; goto end_takeconch; }else if( readLen<=(PROXY_HEADERLEN+PROXY_HOSTIDLEN) || @@ -30766,7 +33908,7 @@ static int proxyTakeConch(unixFile *pFile){ rc = proxyConchLock(pFile, myHostID, EXCLUSIVE_LOCK); } }else{ - rc = conchFile->pMethod->xLock((sqlite3_file*)conchFile, EXCLUSIVE_LOCK); + rc = proxyConchLock(pFile, myHostID, EXCLUSIVE_LOCK); } if( rc==SQLITE_OK ){ char writeBuffer[PROXY_MAXCONCHLEN]; @@ -30775,7 +33917,8 @@ static int proxyTakeConch(unixFile *pFile){ writeBuffer[0] = (char)PROXY_CONCHVERSION; memcpy(&writeBuffer[PROXY_HEADERLEN], myHostID, PROXY_HOSTIDLEN); if( pCtx->lockProxyPath!=NULL ){ - strlcpy(&writeBuffer[PROXY_PATHINDEX], pCtx->lockProxyPath, MAXPATHLEN); + strlcpy(&writeBuffer[PROXY_PATHINDEX], pCtx->lockProxyPath, + MAXPATHLEN); }else{ strlcpy(&writeBuffer[PROXY_PATHINDEX], tempLockPath, MAXPATHLEN); } @@ -30887,7 +34030,7 @@ static int proxyReleaseConch(unixFile *pFile){ conchFile = pCtx->conchFile; OSTRACE(("RELEASECONCH %d for %s pid=%d\n", conchFile->h, (pCtx->lockProxyPath ? pCtx->lockProxyPath : ":auto:"), - getpid())); + osGetpid(0))); if( pCtx->conchHeld>0 ){ rc = conchFile->pMethod->xUnlock((sqlite3_file*)conchFile, NO_LOCK); } @@ -30899,7 +34042,7 @@ static int proxyReleaseConch(unixFile *pFile){ /* ** Given the name of a database file, compute the name of its conch file. -** Store the conch filename in memory obtained from sqlite3_malloc(). +** Store the conch filename in memory obtained from sqlite3_malloc64(). ** Make *pConchPath point to the new name. Return SQLITE_OK on success ** or SQLITE_NOMEM if unable to obtain memory. ** @@ -30915,7 +34058,7 @@ static int proxyCreateConchPathname(char *dbPath, char **pConchPath){ /* Allocate space for the conch filename and initialize the name to ** the name of the original database file. */ - *pConchPath = conchPath = (char *)sqlite3_malloc(len + 8); + *pConchPath = conchPath = (char *)sqlite3_malloc64(len + 8); if( conchPath==0 ){ return SQLITE_NOMEM; } @@ -30987,7 +34130,8 @@ static int proxyGetDbPathForUnixFile(unixFile *pFile, char *dbPath){ /* afp style keeps a reference to the db path in the filePath field ** of the struct */ assert( (int)strlen((char*)pFile->lockingContext)<=MAXPATHLEN ); - strlcpy(dbPath, ((afpLockingContext *)pFile->lockingContext)->dbPath, MAXPATHLEN); + strlcpy(dbPath, ((afpLockingContext *)pFile->lockingContext)->dbPath, + MAXPATHLEN); } else #endif if( pFile->pMethod == &dotlockIoMethods ){ @@ -31028,9 +34172,9 @@ static int proxyTransformUnixFile(unixFile *pFile, const char *path) { } OSTRACE(("TRANSPROXY %d for %s pid=%d\n", pFile->h, - (lockPath ? lockPath : ":auto:"), getpid())); + (lockPath ? lockPath : ":auto:"), osGetpid(0))); - pCtx = sqlite3_malloc( sizeof(*pCtx) ); + pCtx = sqlite3_malloc64( sizeof(*pCtx) ); if( pCtx==0 ){ return SQLITE_NOMEM; } @@ -31100,7 +34244,7 @@ static int proxyTransformUnixFile(unixFile *pFile, const char *path) { */ static int proxyFileControl(sqlite3_file *id, int op, void *pArg){ switch( op ){ - case SQLITE_GET_LOCKPROXYFILE: { + case SQLITE_FCNTL_GET_LOCKPROXYFILE: { unixFile *pFile = (unixFile*)id; if( pFile->pMethod == &proxyIoMethods ){ proxyLockingContext *pCtx = (proxyLockingContext*)pFile->lockingContext; @@ -31115,13 +34259,16 @@ static int proxyFileControl(sqlite3_file *id, int op, void *pArg){ } return SQLITE_OK; } - case SQLITE_SET_LOCKPROXYFILE: { + case SQLITE_FCNTL_SET_LOCKPROXYFILE: { unixFile *pFile = (unixFile*)id; int rc = SQLITE_OK; int isProxyStyle = (pFile->pMethod == &proxyIoMethods); if( pArg==NULL || (const char *)pArg==0 ){ if( isProxyStyle ){ - /* turn off proxy locking - not supported */ + /* turn off proxy locking - not supported. If support is added for + ** switching proxy locking mode off then it will need to fail if + ** the journal mode is WAL mode. + */ rc = SQLITE_ERROR /*SQLITE_PROTOCOL? SQLITE_MISUSE?*/; }else{ /* turn off proxy locking - already off - NOOP */ @@ -31251,7 +34398,7 @@ static int proxyUnlock(sqlite3_file *id, int eFileLock) { ** Close a file that uses proxy locks. */ static int proxyClose(sqlite3_file *id) { - if( id ){ + if( ALWAYS(id) ){ unixFile *pFile = (unixFile*)id; proxyLockingContext *pCtx = (proxyLockingContext *)pFile->lockingContext; unixFile *lockProxy = pCtx->lockProxy; @@ -31312,7 +34459,7 @@ static int proxyClose(sqlite3_file *id) { ** necessarily been initialized when this routine is called, and so they ** should not be used. */ -SQLITE_API int sqlite3_os_init(void){ +SQLITE_API int SQLITE_STDCALL sqlite3_os_init(void){ /* ** The following macro defines an initializer for an sqlite3_vfs object. ** The name of the VFS is NAME. The pAppData is a pointer to a pointer @@ -31366,8 +34513,10 @@ SQLITE_API int sqlite3_os_init(void){ ** array cannot be const. */ static sqlite3_vfs aVfs[] = { -#if SQLITE_ENABLE_LOCKING_STYLE && (OS_VXWORKS || defined(__APPLE__)) +#if SQLITE_ENABLE_LOCKING_STYLE && defined(__APPLE__) UNIXVFS("unix", autolockIoFinder ), +#elif OS_VXWORKS + UNIXVFS("unix", vxworksIoFinder ), #else UNIXVFS("unix", posixIoFinder ), #endif @@ -31377,11 +34526,11 @@ SQLITE_API int sqlite3_os_init(void){ #if OS_VXWORKS UNIXVFS("unix-namedsem", semIoFinder ), #endif -#if SQLITE_ENABLE_LOCKING_STYLE +#if SQLITE_ENABLE_LOCKING_STYLE || OS_VXWORKS UNIXVFS("unix-posix", posixIoFinder ), -#if !OS_VXWORKS - UNIXVFS("unix-flock", flockIoFinder ), #endif +#if SQLITE_ENABLE_LOCKING_STYLE + UNIXVFS("unix-flock", flockIoFinder ), #endif #if SQLITE_ENABLE_LOCKING_STYLE && defined(__APPLE__) UNIXVFS("unix-afp", afpIoFinder ), @@ -31393,7 +34542,7 @@ SQLITE_API int sqlite3_os_init(void){ /* Double-check that the aSyscall[] array has been constructed ** correctly. See ticket [bb3a86e890c8e96ab] */ - assert( ArraySize(aSyscall)==25 ); + assert( ArraySize(aSyscall)==27 ); /* Register all VFSes defined in the aVfs[] array */ for(i=0; i<(sizeof(aVfs)/sizeof(sqlite3_vfs)); i++){ @@ -31409,7 +34558,7 @@ SQLITE_API int sqlite3_os_init(void){ ** to release dynamically allocated objects. But not on unix. ** This routine is a no-op for unix. */ -SQLITE_API int sqlite3_os_end(void){ +SQLITE_API int SQLITE_STDCALL sqlite3_os_end(void){ return SQLITE_OK; } @@ -31431,6 +34580,7 @@ SQLITE_API int sqlite3_os_end(void){ ** ** This file contains code that is specific to Windows. */ +/* #include "sqliteInt.h" */ #if SQLITE_OS_WIN /* This file is used for Windows only */ /* @@ -31469,16 +34619,6 @@ SQLITE_API int sqlite3_os_end(void){ # error "The MEMORY_DEBUG macro is obsolete. Use SQLITE_DEBUG instead." #endif -#if defined(SQLITE_TEST) && defined(SQLITE_DEBUG) -# ifndef SQLITE_DEBUG_OS_TRACE -# define SQLITE_DEBUG_OS_TRACE 0 -# endif - int sqlite3OSTrace = SQLITE_DEBUG_OS_TRACE; -# define OSTRACE(X) if( sqlite3OSTrace ) sqlite3DebugPrintf X -#else -# define OSTRACE(X) -#endif - /* ** Macros for performance tracing. Normally turned off. Only works ** on i486 hardware. @@ -31649,6 +34789,7 @@ SQLITE_API int sqlite3_open_file_count = 0; /* ** Include the header file for the Windows VFS. */ +/* #include "os_win.h" */ /* ** Compiling and using WAL mode requires several APIs that are only @@ -31659,6 +34800,11 @@ SQLITE_API int sqlite3_open_file_count = 0; with SQLITE_OMIT_WAL." #endif +#if !SQLITE_OS_WINNT && SQLITE_MAX_MMAP_SIZE>0 +# error "Memory mapped files require support from the Windows NT kernel,\ + compile with SQLITE_MAX_MMAP_SIZE=0." +#endif + /* ** Are most of the Win32 ANSI APIs available (i.e. with certain exceptions ** based on the sub-platform)? @@ -31697,18 +34843,14 @@ SQLITE_API int sqlite3_open_file_count = 0; #endif /* -** Check if the GetVersionEx[AW] functions should be considered deprecated -** and avoid using them in that case. It should be noted here that if the -** value of the SQLITE_WIN32_GETVERSIONEX pre-processor macro is zero -** (whether via this block or via being manually specified), that implies -** the underlying operating system will always be based on the Windows NT -** Kernel. +** Check to see if the GetVersionEx[AW] functions are deprecated on the +** target system. GetVersionEx was first deprecated in Win8.1. */ #ifndef SQLITE_WIN32_GETVERSIONEX # if defined(NTDDI_VERSION) && NTDDI_VERSION >= NTDDI_WINBLUE -# define SQLITE_WIN32_GETVERSIONEX 0 +# define SQLITE_WIN32_GETVERSIONEX 0 /* GetVersionEx() is deprecated */ # else -# define SQLITE_WIN32_GETVERSIONEX 1 +# define SQLITE_WIN32_GETVERSIONEX 1 /* GetVersionEx() is current */ # endif #endif @@ -31780,7 +34922,7 @@ SQLITE_API int sqlite3_open_file_count = 0; ** [sometimes] not used by the code (e.g. via conditional compilation). */ #ifndef UNUSED_VARIABLE_VALUE -# define UNUSED_VARIABLE_VALUE(x) (void)(x) +# define UNUSED_VARIABLE_VALUE(x) (void)(x) #endif /* @@ -31792,10 +34934,11 @@ SQLITE_API int sqlite3_open_file_count = 0; /* ** Do we need to manually define the Win32 file mapping APIs for use with WAL -** mode (e.g. these APIs are available in the Windows CE SDK; however, they -** are not present in the header file)? +** mode or memory mapped files (e.g. these APIs are available in the Windows +** CE SDK; however, they are not present in the header file)? */ -#if SQLITE_WIN32_FILEMAPPING_API && !defined(SQLITE_OMIT_WAL) +#if SQLITE_WIN32_FILEMAPPING_API && \ + (!defined(SQLITE_OMIT_WAL) || SQLITE_MAX_MMAP_SIZE>0) /* ** Two of the file mapping APIs are different under WinRT. Figure out which ** set we need. @@ -31820,16 +34963,18 @@ WINBASEAPI LPVOID WINAPI MapViewOfFile(HANDLE, DWORD, DWORD, DWORD, SIZE_T); #endif /* SQLITE_OS_WINRT */ /* -** This file mapping API is common to both Win32 and WinRT. +** These file mapping APIs are common to both Win32 and WinRT. */ + +WINBASEAPI BOOL WINAPI FlushViewOfFile(LPCVOID, SIZE_T); WINBASEAPI BOOL WINAPI UnmapViewOfFile(LPCVOID); -#endif /* SQLITE_WIN32_FILEMAPPING_API && !defined(SQLITE_OMIT_WAL) */ +#endif /* SQLITE_WIN32_FILEMAPPING_API */ /* ** Some Microsoft compilers lack this definition. */ #ifndef INVALID_FILE_ATTRIBUTES -# define INVALID_FILE_ATTRIBUTES ((DWORD)-1) +# define INVALID_FILE_ATTRIBUTES ((DWORD)-1) #endif #ifndef FILE_FLAG_MASK @@ -31879,7 +35024,7 @@ struct winFile { int szChunk; /* Chunk size configured by FCNTL_CHUNK_SIZE */ #if SQLITE_OS_WINCE LPWSTR zDeleteOnClose; /* Name of file to delete when closing */ - HANDLE hMutex; /* Mutex used to control access to shared lock */ + HANDLE hMutex; /* Mutex used to control access to shared lock */ HANDLE hShared; /* Shared memory segment used for locking */ winceLock local; /* Locks obtained by this instance of winFile */ winceLock *shared; /* Global shared lock memory for the file */ @@ -32039,10 +35184,9 @@ SQLITE_PRIVATE const sqlite3_mem_methods *sqlite3MemGetWin32(void); ** can manually set this value to 1 to emulate Win98 behavior. */ #ifdef SQLITE_TEST -SQLITE_API int sqlite3_os_type = 0; -#elif !SQLITE_OS_WINCE && !SQLITE_OS_WINRT && \ - defined(SQLITE_WIN32_HAS_ANSI) && defined(SQLITE_WIN32_HAS_WIDE) -static int sqlite3_os_type = 0; +SQLITE_API LONG SQLITE_WIN32_VOLATILE sqlite3_os_type = 0; +#else +static LONG SQLITE_WIN32_VOLATILE sqlite3_os_type = 0; #endif #ifndef SYSCALL @@ -32117,7 +35261,7 @@ static struct win_syscall { LPSECURITY_ATTRIBUTES,DWORD,DWORD,HANDLE))aSyscall[5].pCurrent) #if (!SQLITE_OS_WINRT && defined(SQLITE_WIN32_HAS_ANSI) && \ - !defined(SQLITE_OMIT_WAL)) + (!defined(SQLITE_OMIT_WAL) || SQLITE_MAX_MMAP_SIZE>0)) { "CreateFileMappingA", (SYSCALL)CreateFileMappingA, 0 }, #else { "CreateFileMappingA", (SYSCALL)0, 0 }, @@ -32127,7 +35271,7 @@ static struct win_syscall { DWORD,DWORD,DWORD,LPCSTR))aSyscall[6].pCurrent) #if SQLITE_OS_WINCE || (!SQLITE_OS_WINRT && defined(SQLITE_WIN32_HAS_WIDE) && \ - !defined(SQLITE_OMIT_WAL)) + (!defined(SQLITE_OMIT_WAL) || SQLITE_MAX_MMAP_SIZE>0)) { "CreateFileMappingW", (SYSCALL)CreateFileMappingW, 0 }, #else { "CreateFileMappingW", (SYSCALL)0, 0 }, @@ -32467,7 +35611,8 @@ static struct win_syscall { LPOVERLAPPED))aSyscall[48].pCurrent) #endif -#if SQLITE_OS_WINCE || (!SQLITE_OS_WINRT && !defined(SQLITE_OMIT_WAL)) +#if SQLITE_OS_WINCE || (!SQLITE_OS_WINRT && \ + (!defined(SQLITE_OMIT_WAL) || SQLITE_MAX_MMAP_SIZE>0)) { "MapViewOfFile", (SYSCALL)MapViewOfFile, 0 }, #else { "MapViewOfFile", (SYSCALL)0, 0 }, @@ -32537,7 +35682,7 @@ static struct win_syscall { #define osUnlockFileEx ((BOOL(WINAPI*)(HANDLE,DWORD,DWORD,DWORD, \ LPOVERLAPPED))aSyscall[58].pCurrent) -#if SQLITE_OS_WINCE || !defined(SQLITE_OMIT_WAL) +#if SQLITE_OS_WINCE || !defined(SQLITE_OMIT_WAL) || SQLITE_MAX_MMAP_SIZE>0 { "UnmapViewOfFile", (SYSCALL)UnmapViewOfFile, 0 }, #else { "UnmapViewOfFile", (SYSCALL)0, 0 }, @@ -32573,7 +35718,7 @@ static struct win_syscall { #define osWaitForSingleObject ((DWORD(WINAPI*)(HANDLE, \ DWORD))aSyscall[63].pCurrent) -#if SQLITE_OS_WINRT +#if !SQLITE_OS_WINCE { "WaitForSingleObjectEx", (SYSCALL)WaitForSingleObjectEx, 0 }, #else { "WaitForSingleObjectEx", (SYSCALL)0, 0 }, @@ -32600,7 +35745,7 @@ static struct win_syscall { #define osGetFileInformationByHandleEx ((BOOL(WINAPI*)(HANDLE, \ FILE_INFO_BY_HANDLE_CLASS,LPVOID,DWORD))aSyscall[66].pCurrent) -#if SQLITE_OS_WINRT && !defined(SQLITE_OMIT_WAL) +#if SQLITE_OS_WINRT && (!defined(SQLITE_OMIT_WAL) || SQLITE_MAX_MMAP_SIZE>0) { "MapViewOfFileFromApp", (SYSCALL)MapViewOfFileFromApp, 0 }, #else { "MapViewOfFileFromApp", (SYSCALL)0, 0 }, @@ -32664,7 +35809,7 @@ static struct win_syscall { #define osGetProcessHeap ((HANDLE(WINAPI*)(VOID))aSyscall[74].pCurrent) -#if SQLITE_OS_WINRT && !defined(SQLITE_OMIT_WAL) +#if SQLITE_OS_WINRT && (!defined(SQLITE_OMIT_WAL) || SQLITE_MAX_MMAP_SIZE>0) { "CreateFileMappingFromApp", (SYSCALL)CreateFileMappingFromApp, 0 }, #else { "CreateFileMappingFromApp", (SYSCALL)0, 0 }, @@ -32673,6 +35818,48 @@ static struct win_syscall { #define osCreateFileMappingFromApp ((HANDLE(WINAPI*)(HANDLE, \ LPSECURITY_ATTRIBUTES,ULONG,ULONG64,LPCWSTR))aSyscall[75].pCurrent) +/* +** NOTE: On some sub-platforms, the InterlockedCompareExchange "function" +** is really just a macro that uses a compiler intrinsic (e.g. x64). +** So do not try to make this is into a redefinable interface. +*/ +#if defined(InterlockedCompareExchange) + { "InterlockedCompareExchange", (SYSCALL)0, 0 }, + +#define osInterlockedCompareExchange InterlockedCompareExchange +#else + { "InterlockedCompareExchange", (SYSCALL)InterlockedCompareExchange, 0 }, + +#define osInterlockedCompareExchange ((LONG(WINAPI*)(LONG \ + SQLITE_WIN32_VOLATILE*, LONG,LONG))aSyscall[76].pCurrent) +#endif /* defined(InterlockedCompareExchange) */ + +#if !SQLITE_OS_WINCE && !SQLITE_OS_WINRT && SQLITE_WIN32_USE_UUID + { "UuidCreate", (SYSCALL)UuidCreate, 0 }, +#else + { "UuidCreate", (SYSCALL)0, 0 }, +#endif + +#define osUuidCreate ((RPC_STATUS(RPC_ENTRY*)(UUID*))aSyscall[77].pCurrent) + +#if !SQLITE_OS_WINCE && !SQLITE_OS_WINRT && SQLITE_WIN32_USE_UUID + { "UuidCreateSequential", (SYSCALL)UuidCreateSequential, 0 }, +#else + { "UuidCreateSequential", (SYSCALL)0, 0 }, +#endif + +#define osUuidCreateSequential \ + ((RPC_STATUS(RPC_ENTRY*)(UUID*))aSyscall[78].pCurrent) + +#if !defined(SQLITE_NO_SYNC) && SQLITE_MAX_MMAP_SIZE>0 + { "FlushViewOfFile", (SYSCALL)FlushViewOfFile, 0 }, +#else + { "FlushViewOfFile", (SYSCALL)0, 0 }, +#endif + +#define osFlushViewOfFile \ + ((BOOL(WINAPI*)(LPCVOID,SIZE_T))aSyscall[79].pCurrent) + }; /* End of the overrideable system calls */ /* @@ -32766,7 +35953,7 @@ static const char *winNextSystemCall(sqlite3_vfs *p, const char *zName){ ** "pnLargest" argument, if non-zero, will be used to return the size of the ** largest committed free block in the heap, in bytes. */ -SQLITE_API int sqlite3_win32_compact_heap(LPUINT pnLargest){ +SQLITE_API int SQLITE_STDCALL sqlite3_win32_compact_heap(LPUINT pnLargest){ int rc = SQLITE_OK; UINT nLargest = 0; HANDLE hHeap; @@ -32806,12 +35993,12 @@ SQLITE_API int sqlite3_win32_compact_heap(LPUINT pnLargest){ ** the sqlite3_memory_used() function does not return zero, SQLITE_BUSY will ** be returned and no changes will be made to the Win32 native heap. */ -SQLITE_API int sqlite3_win32_reset_heap(){ +SQLITE_API int SQLITE_STDCALL sqlite3_win32_reset_heap(){ int rc; MUTEX_LOGIC( sqlite3_mutex *pMaster; ) /* The main static mutex */ MUTEX_LOGIC( sqlite3_mutex *pMem; ) /* The memsys static mutex */ - MUTEX_LOGIC( pMaster = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MASTER); ) - MUTEX_LOGIC( pMem = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MEM); ) + MUTEX_LOGIC( pMaster = sqlite3_mutex_alloc(SQLITE_MUTEX_STATIC_MASTER); ) + MUTEX_LOGIC( pMem = sqlite3_mutex_alloc(SQLITE_MUTEX_STATIC_MEM); ) sqlite3_mutex_enter(pMaster); sqlite3_mutex_enter(pMem); winMemAssertMagic(); @@ -32851,7 +36038,7 @@ SQLITE_API int sqlite3_win32_reset_heap(){ ** (if available). */ -SQLITE_API void sqlite3_win32_write_debug(const char *zBuf, int nBuf){ +SQLITE_API void SQLITE_STDCALL sqlite3_win32_write_debug(const char *zBuf, int nBuf){ char zDbgBuf[SQLITE_WIN32_DBG_BUF_SIZE]; int nMin = MIN(nBuf, (SQLITE_WIN32_DBG_BUF_SIZE - 1)); /* may be negative. */ if( nMin<-1 ) nMin = -1; /* all negative values become -1. */ @@ -32891,7 +36078,7 @@ SQLITE_API void sqlite3_win32_write_debug(const char *zBuf, int nBuf){ static HANDLE sleepObj = NULL; #endif -SQLITE_API void sqlite3_win32_sleep(DWORD milliseconds){ +SQLITE_API void SQLITE_STDCALL sqlite3_win32_sleep(DWORD milliseconds){ #if SQLITE_OS_WINRT if ( sleepObj==NULL ){ sleepObj = osCreateEventExW(NULL, NULL, CREATE_EVENT_MANUAL_RESET, @@ -32904,6 +36091,16 @@ SQLITE_API void sqlite3_win32_sleep(DWORD milliseconds){ #endif } +#if SQLITE_MAX_WORKER_THREADS>0 && !SQLITE_OS_WINCE && !SQLITE_OS_WINRT && \ + SQLITE_THREADSAFE>0 +SQLITE_PRIVATE DWORD sqlite3Win32Wait(HANDLE hObject){ + DWORD rc; + while( (rc = osWaitForSingleObjectEx(hObject, INFINITE, + TRUE))==WAIT_IO_COMPLETION ){} + return rc; +} +#endif + /* ** Return true (non-zero) if we are running under WinNT, Win2K, WinXP, ** or WinCE. Return false (zero) for Win95, Win98, or WinME. @@ -32923,22 +36120,47 @@ SQLITE_API void sqlite3_win32_sleep(DWORD milliseconds){ #elif !defined(SQLITE_WIN32_HAS_WIDE) # define osIsNT() (0) #else - static int osIsNT(void){ - if( sqlite3_os_type==0 ){ -#if defined(NTDDI_VERSION) && NTDDI_VERSION >= NTDDI_WIN8 - OSVERSIONINFOW sInfo; - sInfo.dwOSVersionInfoSize = sizeof(sInfo); - osGetVersionExW(&sInfo); -#else - OSVERSIONINFOA sInfo; - sInfo.dwOSVersionInfoSize = sizeof(sInfo); - osGetVersionExA(&sInfo); +# define osIsNT() ((sqlite3_os_type==2) || sqlite3_win32_is_nt()) +#endif + +/* +** This function determines if the machine is running a version of Windows +** based on the NT kernel. +*/ +SQLITE_API int SQLITE_STDCALL sqlite3_win32_is_nt(void){ +#if SQLITE_OS_WINRT + /* + ** NOTE: The WinRT sub-platform is always assumed to be based on the NT + ** kernel. + */ + return 1; +#elif defined(SQLITE_WIN32_GETVERSIONEX) && SQLITE_WIN32_GETVERSIONEX + if( osInterlockedCompareExchange(&sqlite3_os_type, 0, 0)==0 ){ +#if defined(SQLITE_WIN32_HAS_ANSI) + OSVERSIONINFOA sInfo; + sInfo.dwOSVersionInfoSize = sizeof(sInfo); + osGetVersionExA(&sInfo); + osInterlockedCompareExchange(&sqlite3_os_type, + (sInfo.dwPlatformId == VER_PLATFORM_WIN32_NT) ? 2 : 1, 0); +#elif defined(SQLITE_WIN32_HAS_WIDE) + OSVERSIONINFOW sInfo; + sInfo.dwOSVersionInfoSize = sizeof(sInfo); + osGetVersionExW(&sInfo); + osInterlockedCompareExchange(&sqlite3_os_type, + (sInfo.dwPlatformId == VER_PLATFORM_WIN32_NT) ? 2 : 1, 0); #endif - sqlite3_os_type = sInfo.dwPlatformId==VER_PLATFORM_WIN32_NT ? 2 : 1; - } - return sqlite3_os_type==2; } + return osInterlockedCompareExchange(&sqlite3_os_type, 2, 2)==2; +#elif SQLITE_TEST + return osInterlockedCompareExchange(&sqlite3_os_type, 2, 2)==2; +#else + /* + ** NOTE: All sub-platforms where the GetVersionEx[AW] functions are + ** deprecated are always assumed to be based on the NT kernel. + */ + return 1; #endif +} #ifdef SQLITE_WIN32_MALLOC /* @@ -33146,7 +36368,7 @@ SQLITE_PRIVATE void sqlite3MemSetDefault(void){ #endif /* SQLITE_WIN32_MALLOC */ /* -** Convert a UTF-8 string to Microsoft Unicode (UTF-16?). +** Convert a UTF-8 string to Microsoft Unicode (UTF-16?). ** ** Space to hold the returned string is obtained from malloc. */ @@ -33199,7 +36421,7 @@ static char *winUnicodeToUtf8(LPCWSTR zWideFilename){ /* ** Convert an ANSI string to Microsoft Unicode, based on the ** current codepage settings for file apis. -** +** ** Space to hold the returned string is obtained ** from sqlite3_malloc. */ @@ -33259,7 +36481,7 @@ static char *winUnicodeToMbcs(LPCWSTR zWideFilename){ ** Convert multibyte character string to UTF-8. Space to hold the ** returned string is obtained from sqlite3_malloc(). */ -SQLITE_API char *sqlite3_win32_mbcs_to_utf8(const char *zFilename){ +SQLITE_API char *SQLITE_STDCALL sqlite3_win32_mbcs_to_utf8(const char *zFilename){ char *zFilenameUtf8; LPWSTR zTmpWide; @@ -33273,10 +36495,10 @@ SQLITE_API char *sqlite3_win32_mbcs_to_utf8(const char *zFilename){ } /* -** Convert UTF-8 to multibyte character string. Space to hold the +** Convert UTF-8 to multibyte character string. Space to hold the ** returned string is obtained from sqlite3_malloc(). */ -SQLITE_API char *sqlite3_win32_utf8_to_mbcs(const char *zFilename){ +SQLITE_API char *SQLITE_STDCALL sqlite3_win32_utf8_to_mbcs(const char *zFilename){ char *zFilenameMbcs; LPWSTR zTmpWide; @@ -33296,7 +36518,7 @@ SQLITE_API char *sqlite3_win32_utf8_to_mbcs(const char *zFilename){ ** argument is the name of the directory to use. The return value will be ** SQLITE_OK if successful. */ -SQLITE_API int sqlite3_win32_set_directory(DWORD type, LPCWSTR zValue){ +SQLITE_API int SQLITE_STDCALL sqlite3_win32_set_directory(DWORD type, LPCWSTR zValue){ char **ppDirectory = 0; #ifndef SQLITE_OMIT_AUTOINIT int rc = sqlite3_initialize(); @@ -33413,11 +36635,11 @@ static int winGetLastErrorMsg(DWORD lastErrno, int nBuf, char *zBuf){ ** ** This routine is invoked after an error occurs in an OS function. ** It logs a message using sqlite3_log() containing the current value of -** error code and, if possible, the human-readable equivalent from +** error code and, if possible, the human-readable equivalent from ** FormatMessage. ** ** The first argument passed to the macro should be the error code that -** will be returned to SQLite (e.g. SQLITE_IOERR_DELETE, SQLITE_CANTOPEN). +** will be returned to SQLite (e.g. SQLITE_IOERR_DELETE, SQLITE_CANTOPEN). ** The two subsequent arguments should be the name of the OS function that ** failed and the associated file-system path, if any. */ @@ -33448,7 +36670,7 @@ static int winLogErrorAtLine( /* ** The number of times that a ReadFile(), WriteFile(), and DeleteFile() -** will be retried following a locking error - probably caused by +** will be retried following a locking error - probably caused by ** antivirus software. Also the initial delay before the first retry. ** The delay increases linearly with each retry. */ @@ -33521,11 +36743,11 @@ static int winRetryIoerr(int *pnRetry, DWORD *pError){ /* ** Log a I/O error retry episode. */ -static void winLogIoerr(int nRetry){ +static void winLogIoerr(int nRetry, int lineno){ if( nRetry ){ - sqlite3_log(SQLITE_IOERR, - "delayed %dms for lock/sharing conflict", - winIoerrRetryDelay*nRetry*(nRetry+1)/2 + sqlite3_log(SQLITE_NOTICE, + "delayed %dms for lock/sharing conflict at line %d", + winIoerrRetryDelay*nRetry*(nRetry+1)/2, lineno ); } } @@ -33617,17 +36839,17 @@ static int winceCreateLock(const char *zFilename, winFile *pFile){ /* Acquire the mutex before continuing */ winceMutexAcquire(pFile->hMutex); - - /* Since the names of named mutexes, semaphores, file mappings etc are + + /* Since the names of named mutexes, semaphores, file mappings etc are ** case-sensitive, take advantage of that by uppercasing the mutex name ** and using that as the shared filemapping name. */ osCharUpperW(zName); pFile->hShared = osCreateFileMappingW(INVALID_HANDLE_VALUE, NULL, PAGE_READWRITE, 0, sizeof(winceLock), - zName); + zName); - /* Set a flag that indicates we're the first to create the memory so it + /* Set a flag that indicates we're the first to create the memory so it ** must be zero-initialized */ lastErrno = osGetLastError(); if (lastErrno == ERROR_ALREADY_EXISTS){ @@ -33638,7 +36860,7 @@ static int winceCreateLock(const char *zFilename, winFile *pFile){ /* If we succeeded in making the shared memory handle, map it. */ if( pFile->hShared ){ - pFile->shared = (winceLock*)osMapViewOfFile(pFile->hShared, + pFile->shared = (winceLock*)osMapViewOfFile(pFile->hShared, FILE_MAP_READ|FILE_MAP_WRITE, 0, 0, sizeof(winceLock)); /* If mapping failed, close the shared memory handle and erase it */ if( !pFile->shared ){ @@ -33664,7 +36886,7 @@ static int winceCreateLock(const char *zFilename, winFile *pFile){ pFile->hMutex = NULL; return SQLITE_IOERR; } - + /* Initialize the shared memory if we're supposed to */ if( bInit ){ memset(pFile->shared, 0, sizeof(winceLock)); @@ -33702,13 +36924,13 @@ static void winceDestroyLock(winFile *pFile){ osCloseHandle(pFile->hShared); /* Done with the mutex */ - winceMutexRelease(pFile->hMutex); + winceMutexRelease(pFile->hMutex); osCloseHandle(pFile->hMutex); pFile->hMutex = NULL; } } -/* +/* ** An implementation of the LockFile() API of Windows for CE */ static BOOL winceLockFile( @@ -33919,8 +37141,8 @@ static BOOL winUnlockFile( #endif /* -** Move the current position of the file handle passed as the first -** argument to offset iOffset within the file. If successful, return 0. +** Move the current position of the file handle passed as the first +** argument to offset iOffset within the file. If successful, return 0. ** Otherwise, set pFile->lastErrno and return non-zero. */ static int winSeekFile(winFile *pFile, sqlite3_int64 iOffset){ @@ -33935,11 +37157,11 @@ static int winSeekFile(winFile *pFile, sqlite3_int64 iOffset){ upperBits = (LONG)((iOffset>>32) & 0x7fffffff); lowerBits = (LONG)(iOffset & 0xffffffff); - /* API oddity: If successful, SetFilePointer() returns a dword + /* API oddity: If successful, SetFilePointer() returns a dword ** containing the lower 32-bits of the new file-offset. Or, if it fails, - ** it returns INVALID_SET_FILE_POINTER. However according to MSDN, - ** INVALID_SET_FILE_POINTER may also be a valid new offset. So to determine - ** whether an error has actually occurred, it is also necessary to call + ** it returns INVALID_SET_FILE_POINTER. However according to MSDN, + ** INVALID_SET_FILE_POINTER may also be a valid new offset. So to determine + ** whether an error has actually occurred, it is also necessary to call ** GetLastError(). */ dwRet = osSetFilePointer(pFile->h, lowerBits, &upperBits, FILE_BEGIN); @@ -34005,7 +37227,8 @@ static int winClose(sqlite3_file *id){ assert( pFile->pShm==0 ); #endif assert( pFile->h!=NULL && pFile->h!=INVALID_HANDLE_VALUE ); - OSTRACE(("CLOSE file=%p\n", pFile->h)); + OSTRACE(("CLOSE pid=%lu, pFile=%p, file=%p\n", + osGetCurrentProcessId(), pFile, pFile->h)); #if SQLITE_MAX_MMAP_SIZE>0 winUnmapfile(pFile); @@ -34022,7 +37245,7 @@ static int winClose(sqlite3_file *id){ int cnt = 0; while( osDeleteFileW(pFile->zDeleteOnClose)==0 - && osGetFileAttributesW(pFile->zDeleteOnClose)!=0xffffffff + && osGetFileAttributesW(pFile->zDeleteOnClose)!=0xffffffff && cnt++ < WINCE_DELETION_ATTEMPTS ){ sqlite3_win32_sleep(100); /* Wait a little before trying again */ @@ -34034,7 +37257,8 @@ static int winClose(sqlite3_file *id){ pFile->h = NULL; } OpenCounter(-1); - OSTRACE(("CLOSE file=%p, rc=%s\n", pFile->h, rc ? "ok" : "failed")); + OSTRACE(("CLOSE pid=%lu, pFile=%p, file=%p, rc=%s\n", + osGetCurrentProcessId(), pFile, pFile->h, rc ? "ok" : "failed")); return rc ? SQLITE_OK : winLogError(SQLITE_IOERR_CLOSE, osGetLastError(), "winClose", pFile->zPath); @@ -34051,7 +37275,7 @@ static int winRead( int amt, /* Number of bytes to read */ sqlite3_int64 offset /* Begin reading at this offset */ ){ -#if !SQLITE_OS_WINCE +#if !SQLITE_OS_WINCE && !defined(SQLITE_WIN32_NO_OVERLAPPED) OVERLAPPED overlapped; /* The offset for ReadFile. */ #endif winFile *pFile = (winFile*)id; /* file handle */ @@ -34062,7 +37286,8 @@ static int winRead( assert( amt>0 ); assert( offset>=0 ); SimulateIOError(return SQLITE_IOERR_READ); - OSTRACE(("READ file=%p, buffer=%p, amount=%d, offset=%lld, lock=%d\n", + OSTRACE(("READ pid=%lu, pFile=%p, file=%p, buffer=%p, amount=%d, " + "offset=%lld, lock=%d\n", osGetCurrentProcessId(), pFile, pFile->h, pBuf, amt, offset, pFile->locktype)); #if SQLITE_MAX_MMAP_SIZE>0 @@ -34071,7 +37296,8 @@ static int winRead( if( offsetmmapSize ){ if( offset+amt <= pFile->mmapSize ){ memcpy(pBuf, &((u8 *)(pFile->pMapRegion))[offset], amt); - OSTRACE(("READ-MMAP file=%p, rc=SQLITE_OK\n", pFile->h)); + OSTRACE(("READ-MMAP pid=%lu, pFile=%p, file=%p, rc=SQLITE_OK\n", + osGetCurrentProcessId(), pFile, pFile->h)); return SQLITE_OK; }else{ int nCopy = (int)(pFile->mmapSize - offset); @@ -34083,9 +37309,10 @@ static int winRead( } #endif -#if SQLITE_OS_WINCE +#if SQLITE_OS_WINCE || defined(SQLITE_WIN32_NO_OVERLAPPED) if( winSeekFile(pFile, offset) ){ - OSTRACE(("READ file=%p, rc=SQLITE_FULL\n", pFile->h)); + OSTRACE(("READ pid=%lu, pFile=%p, file=%p, rc=SQLITE_FULL\n", + osGetCurrentProcessId(), pFile, pFile->h)); return SQLITE_FULL; } while( !osReadFile(pFile->h, pBuf, amt, &nRead, 0) ){ @@ -34099,19 +37326,22 @@ static int winRead( DWORD lastErrno; if( winRetryIoerr(&nRetry, &lastErrno) ) continue; pFile->lastErrno = lastErrno; - OSTRACE(("READ file=%p, rc=SQLITE_IOERR_READ\n", pFile->h)); + OSTRACE(("READ pid=%lu, pFile=%p, file=%p, rc=SQLITE_IOERR_READ\n", + osGetCurrentProcessId(), pFile, pFile->h)); return winLogError(SQLITE_IOERR_READ, pFile->lastErrno, "winRead", pFile->zPath); } - winLogIoerr(nRetry); + winLogIoerr(nRetry, __LINE__); if( nRead<(DWORD)amt ){ /* Unread parts of the buffer must be zero-filled */ memset(&((char*)pBuf)[nRead], 0, amt-nRead); - OSTRACE(("READ file=%p, rc=SQLITE_IOERR_SHORT_READ\n", pFile->h)); + OSTRACE(("READ pid=%lu, pFile=%p, file=%p, rc=SQLITE_IOERR_SHORT_READ\n", + osGetCurrentProcessId(), pFile, pFile->h)); return SQLITE_IOERR_SHORT_READ; } - OSTRACE(("READ file=%p, rc=SQLITE_OK\n", pFile->h)); + OSTRACE(("READ pid=%lu, pFile=%p, file=%p, rc=SQLITE_OK\n", + osGetCurrentProcessId(), pFile, pFile->h)); return SQLITE_OK; } @@ -34134,16 +37364,18 @@ static int winWrite( SimulateIOError(return SQLITE_IOERR_WRITE); SimulateDiskfullError(return SQLITE_FULL); - OSTRACE(("WRITE file=%p, buffer=%p, amount=%d, offset=%lld, lock=%d\n", + OSTRACE(("WRITE pid=%lu, pFile=%p, file=%p, buffer=%p, amount=%d, " + "offset=%lld, lock=%d\n", osGetCurrentProcessId(), pFile, pFile->h, pBuf, amt, offset, pFile->locktype)); -#if SQLITE_MAX_MMAP_SIZE>0 +#if defined(SQLITE_MMAP_READWRITE) && SQLITE_MAX_MMAP_SIZE>0 /* Deal with as much of this write request as possible by transfering ** data from the memory mapping using memcpy(). */ if( offsetmmapSize ){ if( offset+amt <= pFile->mmapSize ){ memcpy(&((u8 *)(pFile->pMapRegion))[offset], pBuf, amt); - OSTRACE(("WRITE-MMAP file=%p, rc=SQLITE_OK\n", pFile->h)); + OSTRACE(("WRITE-MMAP pid=%lu, pFile=%p, file=%p, rc=SQLITE_OK\n", + osGetCurrentProcessId(), pFile, pFile->h)); return SQLITE_OK; }else{ int nCopy = (int)(pFile->mmapSize - offset); @@ -34155,13 +37387,13 @@ static int winWrite( } #endif -#if SQLITE_OS_WINCE +#if SQLITE_OS_WINCE || defined(SQLITE_WIN32_NO_OVERLAPPED) rc = winSeekFile(pFile, offset); if( rc==0 ){ #else { #endif -#if !SQLITE_OS_WINCE +#if !SQLITE_OS_WINCE && !defined(SQLITE_WIN32_NO_OVERLAPPED) OVERLAPPED overlapped; /* The offset for WriteFile. */ #endif u8 *aRem = (u8 *)pBuf; /* Data yet to be written */ @@ -34169,14 +37401,14 @@ static int winWrite( DWORD nWrite; /* Bytes written by each WriteFile() call */ DWORD lastErrno = NO_ERROR; /* Value returned by GetLastError() */ -#if !SQLITE_OS_WINCE +#if !SQLITE_OS_WINCE && !defined(SQLITE_WIN32_NO_OVERLAPPED) memset(&overlapped, 0, sizeof(OVERLAPPED)); overlapped.Offset = (LONG)(offset & 0xffffffff); overlapped.OffsetHigh = (LONG)((offset>>32) & 0x7fffffff); #endif while( nRem>0 ){ -#if SQLITE_OS_WINCE +#if SQLITE_OS_WINCE || defined(SQLITE_WIN32_NO_OVERLAPPED) if( !osWriteFile(pFile->h, aRem, nRem, &nWrite, 0) ){ #else if( !osWriteFile(pFile->h, aRem, nRem, &nWrite, &overlapped) ){ @@ -34189,7 +37421,7 @@ static int winWrite( lastErrno = osGetLastError(); break; } -#if !SQLITE_OS_WINCE +#if !SQLITE_OS_WINCE && !defined(SQLITE_WIN32_NO_OVERLAPPED) offset += nWrite; overlapped.Offset = (LONG)(offset & 0xffffffff); overlapped.OffsetHigh = (LONG)((offset>>32) & 0x7fffffff); @@ -34206,17 +37438,20 @@ static int winWrite( if( rc ){ if( ( pFile->lastErrno==ERROR_HANDLE_DISK_FULL ) || ( pFile->lastErrno==ERROR_DISK_FULL )){ - OSTRACE(("WRITE file=%p, rc=SQLITE_FULL\n", pFile->h)); + OSTRACE(("WRITE pid=%lu, pFile=%p, file=%p, rc=SQLITE_FULL\n", + osGetCurrentProcessId(), pFile, pFile->h)); return winLogError(SQLITE_FULL, pFile->lastErrno, "winWrite1", pFile->zPath); } - OSTRACE(("WRITE file=%p, rc=SQLITE_IOERR_WRITE\n", pFile->h)); + OSTRACE(("WRITE pid=%lu, pFile=%p, file=%p, rc=SQLITE_IOERR_WRITE\n", + osGetCurrentProcessId(), pFile, pFile->h)); return winLogError(SQLITE_IOERR_WRITE, pFile->lastErrno, "winWrite2", pFile->zPath); }else{ - winLogIoerr(nRetry); + winLogIoerr(nRetry, __LINE__); } - OSTRACE(("WRITE file=%p, rc=SQLITE_OK\n", pFile->h)); + OSTRACE(("WRITE pid=%lu, pFile=%p, file=%p, rc=SQLITE_OK\n", + osGetCurrentProcessId(), pFile, pFile->h)); return SQLITE_OK; } @@ -34230,8 +37465,8 @@ static int winTruncate(sqlite3_file *id, sqlite3_int64 nByte){ assert( pFile ); SimulateIOError(return SQLITE_IOERR_TRUNCATE); - OSTRACE(("TRUNCATE file=%p, size=%lld, lock=%d\n", - pFile->h, nByte, pFile->locktype)); + OSTRACE(("TRUNCATE pid=%lu, pFile=%p, file=%p, size=%lld, lock=%d\n", + osGetCurrentProcessId(), pFile, pFile->h, nByte, pFile->locktype)); /* If the user has configured a chunk-size for this file, truncate the ** file so that it consists of an integer number of chunks (i.e. the @@ -34263,7 +37498,8 @@ static int winTruncate(sqlite3_file *id, sqlite3_int64 nByte){ } #endif - OSTRACE(("TRUNCATE file=%p, rc=%s\n", pFile->h, sqlite3ErrName(rc))); + OSTRACE(("TRUNCATE pid=%lu, pFile=%p, file=%p, rc=%s\n", + osGetCurrentProcessId(), pFile, pFile->h, sqlite3ErrName(rc))); return rc; } @@ -34287,7 +37523,7 @@ static int winSync(sqlite3_file *id, int flags){ BOOL rc; #endif #if !defined(NDEBUG) || !defined(SQLITE_NO_SYNC) || \ - (defined(SQLITE_TEST) && defined(SQLITE_DEBUG)) + defined(SQLITE_HAVE_OS_TRACE) /* ** Used when SQLITE_NO_SYNC is not defined and by the assert() and/or ** OSTRACE() macros. @@ -34308,8 +37544,9 @@ static int winSync(sqlite3_file *id, int flags){ */ SimulateDiskfullError( return SQLITE_FULL ); - OSTRACE(("SYNC file=%p, flags=%x, lock=%d\n", - pFile->h, flags, pFile->locktype)); + OSTRACE(("SYNC pid=%lu, pFile=%p, file=%p, flags=%x, lock=%d\n", + osGetCurrentProcessId(), pFile, pFile->h, flags, + pFile->locktype)); #ifndef SQLITE_TEST UNUSED_PARAMETER(flags); @@ -34324,19 +37561,38 @@ static int winSync(sqlite3_file *id, int flags){ ** no-op */ #ifdef SQLITE_NO_SYNC - OSTRACE(("SYNC-NOP file=%p, rc=SQLITE_OK\n", pFile->h)); + OSTRACE(("SYNC-NOP pid=%lu, pFile=%p, file=%p, rc=SQLITE_OK\n", + osGetCurrentProcessId(), pFile, pFile->h)); return SQLITE_OK; #else +#if SQLITE_MAX_MMAP_SIZE>0 + if( pFile->pMapRegion ){ + if( osFlushViewOfFile(pFile->pMapRegion, 0) ){ + OSTRACE(("SYNC-MMAP pid=%lu, pFile=%p, pMapRegion=%p, " + "rc=SQLITE_OK\n", osGetCurrentProcessId(), + pFile, pFile->pMapRegion)); + }else{ + pFile->lastErrno = osGetLastError(); + OSTRACE(("SYNC-MMAP pid=%lu, pFile=%p, pMapRegion=%p, " + "rc=SQLITE_IOERR_MMAP\n", osGetCurrentProcessId(), + pFile, pFile->pMapRegion)); + return winLogError(SQLITE_IOERR_MMAP, pFile->lastErrno, + "winSync1", pFile->zPath); + } + } +#endif rc = osFlushFileBuffers(pFile->h); SimulateIOError( rc=FALSE ); if( rc ){ - OSTRACE(("SYNC file=%p, rc=SQLITE_OK\n", pFile->h)); + OSTRACE(("SYNC pid=%lu, pFile=%p, file=%p, rc=SQLITE_OK\n", + osGetCurrentProcessId(), pFile, pFile->h)); return SQLITE_OK; }else{ pFile->lastErrno = osGetLastError(); - OSTRACE(("SYNC file=%p, rc=SQLITE_IOERR_FSYNC\n", pFile->h)); + OSTRACE(("SYNC pid=%lu, pFile=%p, file=%p, rc=SQLITE_IOERR_FSYNC\n", + osGetCurrentProcessId(), pFile, pFile->h)); return winLogError(SQLITE_IOERR_FSYNC, pFile->lastErrno, - "winSync", pFile->zPath); + "winSync2", pFile->zPath); } #endif } @@ -34525,6 +37781,12 @@ static int winLock(sqlite3_file *id, int locktype){ return SQLITE_OK; } + /* Do not allow any kind of write-lock on a read-only database + */ + if( (pFile->ctrlFlags & WINFILE_RDONLY)!=0 && locktype>=RESERVED_LOCK ){ + return SQLITE_IOERR_LOCK; + } + /* Make sure the locking sequence is correct */ assert( pFile->locktype!=NO_LOCK || locktype==SHARED_LOCK ); @@ -34654,7 +37916,7 @@ static int winCheckReservedLock(sqlite3_file *id, int *pResOut){ res = 1; OSTRACE(("TEST-WR-LOCK file=%p, result=%d (local)\n", pFile->h, res)); }else{ - res = winLockFile(&pFile->h, SQLITE_LOCKFILEEX_FLAGS,RESERVED_BYTE, 0, 1, 0); + res = winLockFile(&pFile->h, SQLITE_LOCKFILEEX_FLAGS,RESERVED_BYTE,0,1,0); if( res ){ winUnlockFile(&pFile->h, RESERVED_BYTE, 0, 1, 0); } @@ -34712,7 +37974,7 @@ static int winUnlock(sqlite3_file *id, int locktype){ } /* -** If *pArg is inititially negative then this is a query. Set *pArg to +** If *pArg is initially negative then this is a query. Set *pArg to ** 1 or 0 depending on whether or not bit mask of pFile->ctrlFlags is set. ** ** If *pArg is 0 or 1, then clear or set the mask bit of pFile->ctrlFlags. @@ -34870,7 +38132,7 @@ static int winDeviceCharacteristics(sqlite3_file *id){ ((p->ctrlFlags & WINFILE_PSOW)?SQLITE_IOCAP_POWERSAFE_OVERWRITE:0); } -/* +/* ** Windows will only let you create file view mappings ** on allocation size granularity boundaries. ** During sqlite3_os_init() we do a GetSystemInfo() @@ -34882,11 +38144,11 @@ static SYSTEM_INFO winSysInfo; /* ** Helper functions to obtain and relinquish the global mutex. The -** global mutex is used to protect the winLockInfo objects used by +** global mutex is used to protect the winLockInfo objects used by ** this file, all of which may be shared by multiple threads. ** -** Function winShmMutexHeld() is used to assert() that the global mutex -** is held when required. This function is only used as part of assert() +** Function winShmMutexHeld() is used to assert() that the global mutex +** is held when required. This function is only used as part of assert() ** statements. e.g. ** ** winShmEnterMutex() @@ -34894,14 +38156,14 @@ static SYSTEM_INFO winSysInfo; ** winShmLeaveMutex() */ static void winShmEnterMutex(void){ - sqlite3_mutex_enter(sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MASTER)); + sqlite3_mutex_enter(sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_VFS1)); } static void winShmLeaveMutex(void){ - sqlite3_mutex_leave(sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MASTER)); + sqlite3_mutex_leave(sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_VFS1)); } #ifndef NDEBUG static int winShmMutexHeld(void) { - return sqlite3_mutex_held(sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MASTER)); + return sqlite3_mutex_held(sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_VFS1)); } #endif @@ -34916,10 +38178,10 @@ static int winShmMutexHeld(void) { ** this object or while reading or writing the following fields: ** ** nRef -** pNext +** pNext ** ** The following fields are read-only after the object is created: -** +** ** fid ** zFilename ** @@ -34944,7 +38206,7 @@ struct winShmNode { int nRef; /* Number of winShm objects pointing to this */ winShm *pFirst; /* All winShm objects pointing to this */ winShmNode *pNext; /* Next in list of all winShmNode objects */ -#ifdef SQLITE_DEBUG +#if defined(SQLITE_DEBUG) || defined(SQLITE_HAVE_OS_TRACE) u8 nextShmId; /* Next available winShm.id value */ #endif }; @@ -34975,7 +38237,7 @@ struct winShm { u8 hasMutex; /* True if holding the winShmNode mutex */ u16 sharedMask; /* Mask of shared locks held */ u16 exclMask; /* Mask of exclusive locks held */ -#ifdef SQLITE_DEBUG +#if defined(SQLITE_DEBUG) || defined(SQLITE_HAVE_OS_TRACE) u8 id; /* Id of this connection with its winShmNode */ #endif }; @@ -35015,7 +38277,7 @@ static int winShmSystemLock( if( lockType == _SHM_WRLCK ) dwFlags |= LOCKFILE_EXCLUSIVE_LOCK; rc = winLockFile(&pFile->hFile.h, dwFlags, ofst, 0, nByte, 0); } - + if( rc!= 0 ){ rc = SQLITE_OK; }else{ @@ -35111,7 +38373,7 @@ static int winOpenSharedMemory(winFile *pDbFd){ } pNew->zFilename = (char*)&pNew[1]; sqlite3_snprintf(nName+15, pNew->zFilename, "%s-shm", pDbFd->zPath); - sqlite3FileSuffix3(pDbFd->zPath, pNew->zFilename); + sqlite3FileSuffix3(pDbFd->zPath, pNew->zFilename); /* Look to see if there is an existing winShmNode that can be used. ** If no matching winShmNode currently exists, create a new one. @@ -35148,7 +38410,7 @@ static int winOpenSharedMemory(winFile *pDbFd){ } /* Check to see if another process is holding the dead-man switch. - ** If not, truncate the file to zero length. + ** If not, truncate the file to zero length. */ if( winShmSystemLock(pShmNode, _SHM_WRLCK, WIN_SHM_DMS, 1)==SQLITE_OK ){ rc = winTruncate((sqlite3_file *)&pShmNode->hFile, 0); @@ -35166,7 +38428,7 @@ static int winOpenSharedMemory(winFile *pDbFd){ /* Make the new connection a child of the winShmNode */ p->pShmNode = pShmNode; -#ifdef SQLITE_DEBUG +#if defined(SQLITE_DEBUG) || defined(SQLITE_HAVE_OS_TRACE) p->id = pShmNode->nextShmId++; #endif pShmNode->nRef++; @@ -35177,7 +38439,7 @@ static int winOpenSharedMemory(winFile *pDbFd){ ** the cover of the winShmEnterMutex() mutex and the pointer from the ** new (struct winShm) object to the pShmNode has been set. All that is ** left to do is to link the new object into the linked list starting - ** at pShmNode->pFirst. This must be done while holding the pShmNode->mutex + ** at pShmNode->pFirst. This must be done while holding the pShmNode->mutex ** mutex. */ sqlite3_mutex_enter(pShmNode->mutex); @@ -35197,7 +38459,7 @@ shm_open_err: } /* -** Close a connection to shared-memory. Delete the underlying +** Close a connection to shared-memory. Delete the underlying ** storage if deleteFlag is true. */ static int winShmUnmap( @@ -35286,7 +38548,7 @@ static int winShmLock( if( rc==SQLITE_OK ){ p->exclMask &= ~mask; p->sharedMask &= ~mask; - } + } }else if( flags & SQLITE_SHM_SHARED ){ u16 allShared = 0; /* Union of locks held by connections other than "p" */ @@ -35325,7 +38587,7 @@ static int winShmLock( break; } } - + /* Get the exclusive locks at the system level. Then if successful ** also mark the local connection as being locked. */ @@ -35345,7 +38607,7 @@ static int winShmLock( } /* -** Implement a memory barrier or memory fence on shared memory. +** Implement a memory barrier or memory fence on shared memory. ** ** All loads and stores begun before the barrier must complete before ** any load or store begun after the barrier. @@ -35354,28 +38616,28 @@ static void winShmBarrier( sqlite3_file *fd /* Database holding the shared memory */ ){ UNUSED_PARAMETER(fd); - /* MemoryBarrier(); // does not work -- do not know why not */ - winShmEnterMutex(); + sqlite3MemoryBarrier(); /* compiler-defined memory barrier */ + winShmEnterMutex(); /* Also mutex, for redundancy */ winShmLeaveMutex(); } /* -** This function is called to obtain a pointer to region iRegion of the -** shared-memory associated with the database file fd. Shared-memory regions -** are numbered starting from zero. Each shared-memory region is szRegion +** This function is called to obtain a pointer to region iRegion of the +** shared-memory associated with the database file fd. Shared-memory regions +** are numbered starting from zero. Each shared-memory region is szRegion ** bytes in size. ** ** If an error occurs, an error code is returned and *pp is set to NULL. ** ** Otherwise, if the isWrite parameter is 0 and the requested shared-memory ** region has not been allocated (by any client, including one running in a -** separate process), then *pp is set to NULL and SQLITE_OK returned. If -** isWrite is non-zero and the requested shared-memory region has not yet +** separate process), then *pp is set to NULL and SQLITE_OK returned. If +** isWrite is non-zero and the requested shared-memory region has not yet ** been allocated, it is allocated by this function. ** ** If the shared-memory region has already been allocated or is allocated by -** this call as described above, then it is mapped into this processes -** address space (if it is not already), *pp is set to point to the mapped +** this call as described above, then it is mapped into this processes +** address space (if it is not already), *pp is set to point to the mapped ** memory and SQLITE_OK returned. */ static int winShmMap( @@ -35386,16 +38648,16 @@ static int winShmMap( void volatile **pp /* OUT: Mapped memory */ ){ winFile *pDbFd = (winFile*)fd; - winShm *p = pDbFd->pShm; + winShm *pShm = pDbFd->pShm; winShmNode *pShmNode; int rc = SQLITE_OK; - if( !p ){ + if( !pShm ){ rc = winOpenSharedMemory(pDbFd); if( rc!=SQLITE_OK ) return rc; - p = pDbFd->pShm; + pShm = pDbFd->pShm; } - pShmNode = p->pShmNode; + pShmNode = pShm->pShmNode; sqlite3_mutex_enter(pShmNode->mutex); assert( szRegion==pShmNode->szRegion || pShmNode->nRegion==0 ); @@ -35435,7 +38697,7 @@ static int winShmMap( } /* Map the requested memory region into this processes address space. */ - apNew = (struct ShmRegion *)sqlite3_realloc( + apNew = (struct ShmRegion *)sqlite3_realloc64( pShmNode->aRegion, (iRegion+1)*sizeof(apNew[0]) ); if( !apNew ){ @@ -35447,17 +38709,17 @@ static int winShmMap( while( pShmNode->nRegion<=iRegion ){ HANDLE hMap = NULL; /* file-mapping handle */ void *pMap = 0; /* Mapped memory region */ - + #if SQLITE_OS_WINRT hMap = osCreateFileMappingFromApp(pShmNode->hFile.h, NULL, PAGE_READWRITE, nByte, NULL ); #elif defined(SQLITE_WIN32_HAS_WIDE) - hMap = osCreateFileMappingW(pShmNode->hFile.h, + hMap = osCreateFileMappingW(pShmNode->hFile.h, NULL, PAGE_READWRITE, 0, nByte, NULL ); #elif defined(SQLITE_WIN32_HAS_ANSI) - hMap = osCreateFileMappingA(pShmNode->hFile.h, + hMap = osCreateFileMappingA(pShmNode->hFile.h, NULL, PAGE_READWRITE, 0, nByte, NULL ); #endif @@ -35554,14 +38816,14 @@ static int winUnmapfile(winFile *pFile){ /* ** Memory map or remap the file opened by file-descriptor pFd (if the file -** is already mapped, the existing mapping is replaced by the new). Or, if -** there already exists a mapping for this file, and there are still +** is already mapped, the existing mapping is replaced by the new). Or, if +** there already exists a mapping for this file, and there are still ** outstanding xFetch() references to it, this function is a no-op. ** -** If parameter nByte is non-negative, then it is the requested size of -** the mapping to create. Otherwise, if nByte is less than zero, then the +** If parameter nByte is non-negative, then it is the requested size of +** the mapping to create. Otherwise, if nByte is less than zero, then the ** requested size is the size of the file on disk. The actual size of the -** created mapping is either the requested size or the value configured +** created mapping is either the requested size or the value configured ** using SQLITE_FCNTL_MMAP_SIZE, whichever is smaller. ** ** SQLITE_OK is returned if no error occurs (even if the mapping is not @@ -35590,7 +38852,7 @@ static int winMapfile(winFile *pFd, sqlite3_int64 nByte){ nMap = pFd->mmapSizeMax; } nMap &= ~(sqlite3_int64)(winSysInfo.dwPageSize - 1); - + if( nMap==0 && pFd->mmapSize>0 ){ winUnmapfile(pFd); } @@ -35600,10 +38862,12 @@ static int winMapfile(winFile *pFd, sqlite3_int64 nByte){ DWORD flags = FILE_MAP_READ; winUnmapfile(pFd); +#ifdef SQLITE_MMAP_READWRITE if( (pFd->ctrlFlags & WINFILE_RDONLY)==0 ){ protect = PAGE_READWRITE; flags |= FILE_MAP_WRITE; } +#endif #if SQLITE_OS_WINRT pFd->hMap = osCreateFileMappingFromApp(pFd->h, NULL, protect, nMap, NULL); #elif defined(SQLITE_WIN32_HAS_WIDE) @@ -35662,7 +38926,7 @@ static int winMapfile(winFile *pFd, sqlite3_int64 nByte){ ** Finally, if an error does occur, return an SQLite error code. The final ** value of *pp is undefined in this case. ** -** If this function does return a pointer, the caller must eventually +** If this function does return a pointer, the caller must eventually ** release the reference by calling winUnfetch(). */ static int winFetch(sqlite3_file *fd, i64 iOff, int nAmt, void **pp){ @@ -35697,20 +38961,20 @@ static int winFetch(sqlite3_file *fd, i64 iOff, int nAmt, void **pp){ } /* -** If the third argument is non-NULL, then this function releases a +** If the third argument is non-NULL, then this function releases a ** reference obtained by an earlier call to winFetch(). The second ** argument passed to this function must be the same as the corresponding -** argument that was passed to the winFetch() invocation. +** argument that was passed to the winFetch() invocation. ** -** Or, if the third argument is NULL, then this function is being called -** to inform the VFS layer that, according to POSIX, any existing mapping +** Or, if the third argument is NULL, then this function is being called +** to inform the VFS layer that, according to POSIX, any existing mapping ** may now be invalid and should be unmapped. */ static int winUnfetch(sqlite3_file *fd, i64 iOff, void *p){ #if SQLITE_MAX_MMAP_SIZE>0 winFile *pFd = (winFile*)fd; /* The underlying database file */ - /* If p==0 (unmap the entire file) then there must be no outstanding + /* If p==0 (unmap the entire file) then there must be no outstanding ** xFetch references. Or, if p!=0 (meaning it is an xFetch reference), ** then there must be at least one outstanding. */ assert( (p==0)==(pFd->nFetchOut==0) ); @@ -35726,7 +38990,7 @@ static int winUnfetch(sqlite3_file *fd, i64 iOff, void *p){ }else{ /* FIXME: If Windows truly always prevents truncating or deleting a ** file while a mapping is held, then the following winUnmapfile() call - ** is unnecessary can can be omitted - potentially improving + ** is unnecessary can be omitted - potentially improving ** performance. */ winUnmapfile(pFd); } @@ -35856,7 +39120,7 @@ static int winGetTempname(sqlite3_vfs *pVfs, char **pzBuf){ /* It's odd to simulate an io-error here, but really this is just ** using the io-error infrastructure to test that SQLite handles this - ** function failing. + ** function failing. */ SimulateIOError( return SQLITE_IOERR ); @@ -36038,7 +39302,7 @@ static int winGetTempname(sqlite3_vfs *pVfs, char **pzBuf){ } /* - ** Check that the output buffer is large enough for the temporary file + ** Check that the output buffer is large enough for the temporary file ** name in the following format: ** ** "/etilqs_XXXXXXXXXXXXXXX\0\0" @@ -36141,8 +39405,8 @@ static int winOpen( #ifndef NDEBUG int isOpenJournal = (isCreate && ( - eType==SQLITE_OPEN_MASTER_JOURNAL - || eType==SQLITE_OPEN_MAIN_JOURNAL + eType==SQLITE_OPEN_MASTER_JOURNAL + || eType==SQLITE_OPEN_MAIN_JOURNAL || eType==SQLITE_OPEN_WAL )); #endif @@ -36150,9 +39414,9 @@ static int winOpen( OSTRACE(("OPEN name=%s, pFile=%p, flags=%x, pOutFlags=%p\n", zUtf8Name, id, flags, pOutFlags)); - /* Check the following statements are true: + /* Check the following statements are true: ** - ** (a) Exactly one of the READWRITE and READONLY flags must be set, and + ** (a) Exactly one of the READWRITE and READONLY flags must be set, and ** (b) if CREATE is set, then READWRITE must also be set, and ** (c) if EXCLUSIVE is set, then CREATE must also be set. ** (d) if DELETEONCLOSE is set, then CREATE must also be set. @@ -36162,7 +39426,7 @@ static int winOpen( assert(isExclusive==0 || isCreate); assert(isDelete==0 || isCreate); - /* The main DB, main journal, WAL file and master journal are never + /* The main DB, main journal, WAL file and master journal are never ** automatically deleted. Nor are they ever temporary files. */ assert( (!isDelete && zName) || eType!=SQLITE_OPEN_MAIN_DB ); assert( (!isDelete && zName) || eType!=SQLITE_OPEN_MAIN_JOURNAL ); @@ -36170,9 +39434,9 @@ static int winOpen( assert( (!isDelete && zName) || eType!=SQLITE_OPEN_WAL ); /* Assert that the upper layer has set one of the "file-type" flags. */ - assert( eType==SQLITE_OPEN_MAIN_DB || eType==SQLITE_OPEN_TEMP_DB - || eType==SQLITE_OPEN_MAIN_JOURNAL || eType==SQLITE_OPEN_TEMP_JOURNAL - || eType==SQLITE_OPEN_SUBJOURNAL || eType==SQLITE_OPEN_MASTER_JOURNAL + assert( eType==SQLITE_OPEN_MAIN_DB || eType==SQLITE_OPEN_TEMP_DB + || eType==SQLITE_OPEN_MAIN_JOURNAL || eType==SQLITE_OPEN_TEMP_JOURNAL + || eType==SQLITE_OPEN_SUBJOURNAL || eType==SQLITE_OPEN_MASTER_JOURNAL || eType==SQLITE_OPEN_TRANSIENT_DB || eType==SQLITE_OPEN_WAL ); @@ -36187,8 +39451,8 @@ static int winOpen( } #endif - /* If the second argument to this function is NULL, generate a - ** temporary file name to use + /* If the second argument to this function is NULL, generate a + ** temporary file name to use */ if( !zUtf8Name ){ assert( isDelete && !isOpenJournal ); @@ -36228,8 +39492,8 @@ static int winOpen( dwDesiredAccess = GENERIC_READ; } - /* SQLITE_OPEN_EXCLUSIVE is used to make sure that a new file is - ** created. SQLite doesn't use it to indicate "exclusive access" + /* SQLITE_OPEN_EXCLUSIVE is used to make sure that a new file is + ** created. SQLite doesn't use it to indicate "exclusive access" ** as it is usually understood. */ if( isExclusive ){ @@ -36307,7 +39571,7 @@ static int winOpen( } } #endif - winLogIoerr(cnt); + winLogIoerr(cnt, __LINE__); OSTRACE(("OPEN file=%p, name=%s, access=%lx, rc=%s\n", h, zUtf8Name, dwDesiredAccess, (h==INVALID_HANDLE_VALUE) ? "failed" : "ok")); @@ -36318,7 +39582,7 @@ static int winOpen( sqlite3_free(zConverted); sqlite3_free(zTmpname); if( isReadWrite && !isExclusive ){ - return winOpen(pVfs, zName, id, + return winOpen(pVfs, zName, id, ((flags|SQLITE_OPEN_READONLY) & ~(SQLITE_OPEN_CREATE|SQLITE_OPEN_READWRITE)), pOutFlags); @@ -36491,7 +39755,7 @@ static int winDelete( if( rc && rc!=SQLITE_IOERR_DELETE_NOENT ){ rc = winLogError(SQLITE_IOERR_DELETE, lastErrno, "winDelete", zFilename); }else{ - winLogIoerr(cnt); + winLogIoerr(cnt, __LINE__); } sqlite3_free(zConverted); OSTRACE(("DELETE name=%s, rc=%s\n", zFilename, sqlite3ErrName(rc))); @@ -36527,21 +39791,21 @@ static int winAccess( WIN32_FILE_ATTRIBUTE_DATA sAttrData; memset(&sAttrData, 0, sizeof(sAttrData)); while( !(rc = osGetFileAttributesExW((LPCWSTR)zConverted, - GetFileExInfoStandard, + GetFileExInfoStandard, &sAttrData)) && winRetryIoerr(&cnt, &lastErrno) ){} if( rc ){ /* For an SQLITE_ACCESS_EXISTS query, treat a zero-length file ** as if it does not exist. */ if( flags==SQLITE_ACCESS_EXISTS - && sAttrData.nFileSizeHigh==0 + && sAttrData.nFileSizeHigh==0 && sAttrData.nFileSizeLow==0 ){ attr = INVALID_FILE_ATTRIBUTES; }else{ attr = sAttrData.dwFileAttributes; } }else{ - winLogIoerr(cnt); + winLogIoerr(cnt, __LINE__); if( lastErrno!=ERROR_FILE_NOT_FOUND && lastErrno!=ERROR_PATH_NOT_FOUND ){ sqlite3_free(zConverted); return winLogError(SQLITE_IOERR_ACCESS, lastErrno, "winAccess", @@ -36633,7 +39897,7 @@ static int winFullPathname( int nFull, /* Size of output buffer in bytes */ char *zFull /* Output buffer */ ){ - + #if defined(__CYGWIN__) SimulateIOError( return SQLITE_ERROR ); UNUSED_PARAMETER(nFull); @@ -36882,7 +40146,7 @@ static void winDlClose(sqlite3_vfs *pVfs, void *pHandle){ static int winRandomness(sqlite3_vfs *pVfs, int nBuf, char *zBuf){ int n = 0; UNUSED_PARAMETER(pVfs); -#if defined(SQLITE_TEST) +#if defined(SQLITE_TEST) || defined(SQLITE_OMIT_RANDOMNESS) n = nBuf; memset(zBuf, 0, nBuf); #else @@ -36916,7 +40180,23 @@ static int winRandomness(sqlite3_vfs *pVfs, int nBuf, char *zBuf){ memcpy(&zBuf[n], &i, sizeof(i)); n += sizeof(i); } +#if !SQLITE_OS_WINCE && !SQLITE_OS_WINRT && SQLITE_WIN32_USE_UUID + if( sizeof(UUID)<=nBuf-n ){ + UUID id; + memset(&id, 0, sizeof(UUID)); + osUuidCreate(&id); + memcpy(&zBuf[n], &id, sizeof(UUID)); + n += sizeof(UUID); + } + if( sizeof(UUID)<=nBuf-n ){ + UUID id; + memset(&id, 0, sizeof(UUID)); + osUuidCreateSequential(&id); + memcpy(&zBuf[n], &id, sizeof(UUID)); + n += sizeof(UUID); + } #endif +#endif /* defined(SQLITE_TEST) || defined(SQLITE_ZERO_PRNG_SEED) */ return n; } @@ -36946,12 +40226,12 @@ SQLITE_API int sqlite3_current_time = 0; /* Fake system time in seconds since 1 ** epoch of noon in Greenwich on November 24, 4714 B.C according to the ** proleptic Gregorian calendar. ** -** On success, return SQLITE_OK. Return SQLITE_ERROR if the time and date +** On success, return SQLITE_OK. Return SQLITE_ERROR if the time and date ** cannot be found. */ static int winCurrentTimeInt64(sqlite3_vfs *pVfs, sqlite3_int64 *piNow){ - /* FILETIME structure is a 64-bit value representing the number of - 100-nanosecond intervals since January 1, 1601 (= JD 2305813.5). + /* FILETIME structure is a 64-bit value representing the number of + 100-nanosecond intervals since January 1, 1601 (= JD 2305813.5). */ FILETIME ft; static const sqlite3_int64 winFiletimeEpoch = 23058135*(sqlite3_int64)8640000; @@ -36959,7 +40239,7 @@ static int winCurrentTimeInt64(sqlite3_vfs *pVfs, sqlite3_int64 *piNow){ static const sqlite3_int64 unixEpoch = 24405875*(sqlite3_int64)8640000; #endif /* 2^32 - to avoid use of LL and warnings in gcc */ - static const sqlite3_int64 max32BitValue = + static const sqlite3_int64 max32BitValue = (sqlite3_int64)2000000000 + (sqlite3_int64)2000000000 + (sqlite3_int64)294967296; @@ -36975,7 +40255,7 @@ static int winCurrentTimeInt64(sqlite3_vfs *pVfs, sqlite3_int64 *piNow){ #endif *piNow = winFiletimeEpoch + - ((((sqlite3_int64)ft.dwHighDateTime)*max32BitValue) + + ((((sqlite3_int64)ft.dwHighDateTime)*max32BitValue) + (sqlite3_int64)ft.dwLowDateTime)/(sqlite3_int64)10000; #ifdef SQLITE_TEST @@ -37040,7 +40320,7 @@ static int winGetLastError(sqlite3_vfs *pVfs, int nBuf, char *zBuf){ /* ** Initialize and deinitialize the operating system interface. */ -SQLITE_API int sqlite3_os_init(void){ +SQLITE_API int SQLITE_STDCALL sqlite3_os_init(void){ static sqlite3_vfs winVfs = { 3, /* iVersion */ sizeof(winFile), /* szOsFile */ @@ -37094,7 +40374,7 @@ SQLITE_API int sqlite3_os_init(void){ /* Double-check that the aSyscall[] array has been constructed ** correctly. See ticket [bb3a86e890c8e96ab] */ - assert( ArraySize(aSyscall)==76 ); + assert( ArraySize(aSyscall)==80 ); /* get memory map allocation granularity */ memset(&winSysInfo, 0, sizeof(SYSTEM_INFO)); @@ -37112,10 +40392,10 @@ SQLITE_API int sqlite3_os_init(void){ sqlite3_vfs_register(&winLongPathVfs, 0); #endif - return SQLITE_OK; + return SQLITE_OK; } -SQLITE_API int sqlite3_os_end(void){ +SQLITE_API int SQLITE_STDCALL sqlite3_os_end(void){ #if SQLITE_OS_WINRT if( sleepObj!=NULL ){ osCloseHandle(sleepObj); @@ -37165,13 +40445,15 @@ SQLITE_API int sqlite3_os_end(void){ ** start of a transaction, and is thus usually less than a few thousand, ** but can be as large as 2 billion for a really big database. */ +/* #include "sqliteInt.h" */ /* Size of the Bitvec structure in bytes. */ #define BITVEC_SZ 512 /* Round the union size down to the nearest pointer boundary, since that's how ** it will be aligned within the Bitvec struct. */ -#define BITVEC_USIZE (((BITVEC_SZ-(3*sizeof(u32)))/sizeof(Bitvec*))*sizeof(Bitvec*)) +#define BITVEC_USIZE \ + (((BITVEC_SZ-(3*sizeof(u32)))/sizeof(Bitvec*))*sizeof(Bitvec*)) /* Type of the array "element" for the bitmap representation. ** Should be a power of 2, and ideally, evenly divide into BITVEC_USIZE. @@ -37256,10 +40538,10 @@ SQLITE_PRIVATE Bitvec *sqlite3BitvecCreate(u32 iSize){ ** If p is NULL (if the bitmap has not been created) or if ** i is out of range, then return false. */ -SQLITE_PRIVATE int sqlite3BitvecTest(Bitvec *p, u32 i){ - if( p==0 ) return 0; - if( i>p->iSize || i==0 ) return 0; +SQLITE_PRIVATE int sqlite3BitvecTestNotNull(Bitvec *p, u32 i){ + assert( p!=0 ); i--; + if( i>=p->iSize ) return 0; while( p->iDivisor ){ u32 bin = i/p->iDivisor; i = i%p->iDivisor; @@ -37279,6 +40561,9 @@ SQLITE_PRIVATE int sqlite3BitvecTest(Bitvec *p, u32 i){ return 0; } } +SQLITE_PRIVATE int sqlite3BitvecTest(Bitvec *p, u32 i){ + return p!=0 && sqlite3BitvecTestNotNull(p,i); +} /* ** Set the i-th bit. Return 0 on success and an error code if @@ -37471,7 +40756,7 @@ SQLITE_PRIVATE int sqlite3BitvecBuiltinTest(int sz, int *aOp){ ** bits to act as the reference */ pBitvec = sqlite3BitvecCreate( sz ); pV = sqlite3MallocZero( (sz+7)/8 + 1 ); - pTmpSpace = sqlite3_malloc(BITVEC_SZ); + pTmpSpace = sqlite3_malloc64(BITVEC_SZ); if( pBitvec==0 || pV==0 || pTmpSpace==0 ) goto bitvec_end; /* NULL pBitvec tests */ @@ -37551,6 +40836,7 @@ bitvec_end: ************************************************************************* ** This file implements that page cache. */ +/* #include "sqliteInt.h" */ /* ** A complete page cache is an instance of this structure. @@ -37558,8 +40844,9 @@ bitvec_end: struct PCache { PgHdr *pDirty, *pDirtyTail; /* List of dirty pages in LRU order */ PgHdr *pSynced; /* Last synced page in dirty page list */ - int nRef; /* Number of referenced pages */ + int nRefSum; /* Sum of ref counts over all pages */ int szCache; /* Configured cache size */ + int szSpill; /* Size before spilling occurs */ int szPage; /* Size of every page in this cache */ int szExtra; /* Size of extra space for each page */ u8 bPurgeable; /* True if pages are on backing store */ @@ -37567,105 +40854,75 @@ struct PCache { int (*xStress)(void*,PgHdr*); /* Call to try make a page clean */ void *pStress; /* Argument to xStress */ sqlite3_pcache *pCache; /* Pluggable cache module */ - PgHdr *pPage1; /* Reference to page 1 */ }; -/* -** Some of the assert() macros in this code are too expensive to run -** even during normal debugging. Use them only rarely on long-running -** tests. Enable the expensive asserts using the -** -DSQLITE_ENABLE_EXPENSIVE_ASSERT=1 compile-time option. -*/ -#ifdef SQLITE_ENABLE_EXPENSIVE_ASSERT -# define expensive_assert(X) assert(X) -#else -# define expensive_assert(X) -#endif - /********************************** Linked List Management ********************/ -#if !defined(NDEBUG) && defined(SQLITE_ENABLE_EXPENSIVE_ASSERT) -/* -** Check that the pCache->pSynced variable is set correctly. If it -** is not, either fail an assert or return zero. Otherwise, return -** non-zero. This is only used in debugging builds, as follows: -** -** expensive_assert( pcacheCheckSynced(pCache) ); -*/ -static int pcacheCheckSynced(PCache *pCache){ - PgHdr *p; - for(p=pCache->pDirtyTail; p!=pCache->pSynced; p=p->pDirtyPrev){ - assert( p->nRef || (p->flags&PGHDR_NEED_SYNC) ); - } - return (p==0 || p->nRef || (p->flags&PGHDR_NEED_SYNC)==0); -} -#endif /* !NDEBUG && SQLITE_ENABLE_EXPENSIVE_ASSERT */ +/* Allowed values for second argument to pcacheManageDirtyList() */ +#define PCACHE_DIRTYLIST_REMOVE 1 /* Remove pPage from dirty list */ +#define PCACHE_DIRTYLIST_ADD 2 /* Add pPage to the dirty list */ +#define PCACHE_DIRTYLIST_FRONT 3 /* Move pPage to the front of the list */ /* -** Remove page pPage from the list of dirty pages. +** Manage pPage's participation on the dirty list. Bits of the addRemove +** argument determines what operation to do. The 0x01 bit means first +** remove pPage from the dirty list. The 0x02 means add pPage back to +** the dirty list. Doing both moves pPage to the front of the dirty list. */ -static void pcacheRemoveFromDirtyList(PgHdr *pPage){ +static void pcacheManageDirtyList(PgHdr *pPage, u8 addRemove){ PCache *p = pPage->pCache; - assert( pPage->pDirtyNext || pPage==p->pDirtyTail ); - assert( pPage->pDirtyPrev || pPage==p->pDirty ); - - /* Update the PCache1.pSynced variable if necessary. */ - if( p->pSynced==pPage ){ - PgHdr *pSynced = pPage->pDirtyPrev; - while( pSynced && (pSynced->flags&PGHDR_NEED_SYNC) ){ - pSynced = pSynced->pDirtyPrev; + if( addRemove & PCACHE_DIRTYLIST_REMOVE ){ + assert( pPage->pDirtyNext || pPage==p->pDirtyTail ); + assert( pPage->pDirtyPrev || pPage==p->pDirty ); + + /* Update the PCache1.pSynced variable if necessary. */ + if( p->pSynced==pPage ){ + PgHdr *pSynced = pPage->pDirtyPrev; + while( pSynced && (pSynced->flags&PGHDR_NEED_SYNC) ){ + pSynced = pSynced->pDirtyPrev; + } + p->pSynced = pSynced; } - p->pSynced = pSynced; + + if( pPage->pDirtyNext ){ + pPage->pDirtyNext->pDirtyPrev = pPage->pDirtyPrev; + }else{ + assert( pPage==p->pDirtyTail ); + p->pDirtyTail = pPage->pDirtyPrev; + } + if( pPage->pDirtyPrev ){ + pPage->pDirtyPrev->pDirtyNext = pPage->pDirtyNext; + }else{ + assert( pPage==p->pDirty ); + p->pDirty = pPage->pDirtyNext; + if( p->pDirty==0 && p->bPurgeable ){ + assert( p->eCreate==1 ); + p->eCreate = 2; + } + } + pPage->pDirtyNext = 0; + pPage->pDirtyPrev = 0; } - - if( pPage->pDirtyNext ){ - pPage->pDirtyNext->pDirtyPrev = pPage->pDirtyPrev; - }else{ - assert( pPage==p->pDirtyTail ); - p->pDirtyTail = pPage->pDirtyPrev; - } - if( pPage->pDirtyPrev ){ - pPage->pDirtyPrev->pDirtyNext = pPage->pDirtyNext; - }else{ - assert( pPage==p->pDirty ); - p->pDirty = pPage->pDirtyNext; - if( p->pDirty==0 && p->bPurgeable ){ - assert( p->eCreate==1 ); - p->eCreate = 2; + if( addRemove & PCACHE_DIRTYLIST_ADD ){ + assert( pPage->pDirtyNext==0 && pPage->pDirtyPrev==0 && p->pDirty!=pPage ); + + pPage->pDirtyNext = p->pDirty; + if( pPage->pDirtyNext ){ + assert( pPage->pDirtyNext->pDirtyPrev==0 ); + pPage->pDirtyNext->pDirtyPrev = pPage; + }else{ + p->pDirtyTail = pPage; + if( p->bPurgeable ){ + assert( p->eCreate==2 ); + p->eCreate = 1; + } + } + p->pDirty = pPage; + if( !p->pSynced && 0==(pPage->flags&PGHDR_NEED_SYNC) ){ + p->pSynced = pPage; } } - pPage->pDirtyNext = 0; - pPage->pDirtyPrev = 0; - - expensive_assert( pcacheCheckSynced(p) ); -} - -/* -** Add page pPage to the head of the dirty list (PCache1.pDirty is set to -** pPage). -*/ -static void pcacheAddToDirtyList(PgHdr *pPage){ - PCache *p = pPage->pCache; - - assert( pPage->pDirtyNext==0 && pPage->pDirtyPrev==0 && p->pDirty!=pPage ); - - pPage->pDirtyNext = p->pDirty; - if( pPage->pDirtyNext ){ - assert( pPage->pDirtyNext->pDirtyPrev==0 ); - pPage->pDirtyNext->pDirtyPrev = pPage; - }else if( p->bPurgeable ){ - assert( p->eCreate==2 ); - p->eCreate = 1; - } - p->pDirty = pPage; - if( !p->pDirtyTail ){ - p->pDirtyTail = pPage; - } - if( !p->pSynced && 0==(pPage->flags&PGHDR_NEED_SYNC) ){ - p->pSynced = pPage; - } - expensive_assert( pcacheCheckSynced(p) ); } /* @@ -37673,12 +40930,25 @@ static void pcacheAddToDirtyList(PgHdr *pPage){ ** being used for an in-memory database, this function is a no-op. */ static void pcacheUnpin(PgHdr *p){ - PCache *pCache = p->pCache; - if( pCache->bPurgeable ){ - if( p->pgno==1 ){ - pCache->pPage1 = 0; - } - sqlite3GlobalConfig.pcache2.xUnpin(pCache->pCache, p->pPage, 0); + if( p->pCache->bPurgeable ){ + sqlite3GlobalConfig.pcache2.xUnpin(p->pCache->pCache, p->pPage, 0); + } +} + +/* +** Compute the number of pages of cache requested. p->szCache is the +** cache size requested by the "PRAGMA cache_size" statement. +*/ +static int numberOfCachePages(PCache *p){ + if( p->szCache>=0 ){ + /* IMPLEMENTATION-OF: R-42059-47211 If the argument N is positive then the + ** suggested cache size is set to N. */ + return p->szCache; + }else{ + /* IMPLEMENTATION-OF: R-61436-13639 If the argument N is negative, then + ** the number of cache pages is adjusted to use approximately abs(N*1024) + ** bytes of memory. */ + return (int)((-1024*(i64)p->szCache)/(p->szPage+p->szExtra)); } } @@ -37714,7 +40984,7 @@ SQLITE_PRIVATE int sqlite3PcacheSize(void){ return sizeof(PCache); } ** The caller discovers how much space needs to be allocated by ** calling sqlite3PcacheSize(). */ -SQLITE_PRIVATE void sqlite3PcacheOpen( +SQLITE_PRIVATE int sqlite3PcacheOpen( int szPage, /* Size of every page */ int szExtra, /* Extra space associated with each page */ int bPurgeable, /* True if pages are on backing store */ @@ -37723,76 +40993,76 @@ SQLITE_PRIVATE void sqlite3PcacheOpen( PCache *p /* Preallocated space for the PCache */ ){ memset(p, 0, sizeof(PCache)); - p->szPage = szPage; + p->szPage = 1; p->szExtra = szExtra; p->bPurgeable = bPurgeable; p->eCreate = 2; p->xStress = xStress; p->pStress = pStress; p->szCache = 100; + p->szSpill = 1; + return sqlite3PcacheSetPageSize(p, szPage); } /* ** Change the page size for PCache object. The caller must ensure that there ** are no outstanding page references when this function is called. */ -SQLITE_PRIVATE void sqlite3PcacheSetPageSize(PCache *pCache, int szPage){ - assert( pCache->nRef==0 && pCache->pDirty==0 ); - if( pCache->pCache ){ - sqlite3GlobalConfig.pcache2.xDestroy(pCache->pCache); - pCache->pCache = 0; - pCache->pPage1 = 0; - } - pCache->szPage = szPage; -} - -/* -** Compute the number of pages of cache requested. -*/ -static int numberOfCachePages(PCache *p){ - if( p->szCache>=0 ){ - return p->szCache; - }else{ - return (int)((-1024*(i64)p->szCache)/(p->szPage+p->szExtra)); +SQLITE_PRIVATE int sqlite3PcacheSetPageSize(PCache *pCache, int szPage){ + assert( pCache->nRefSum==0 && pCache->pDirty==0 ); + if( pCache->szPage ){ + sqlite3_pcache *pNew; + pNew = sqlite3GlobalConfig.pcache2.xCreate( + szPage, pCache->szExtra + ROUND8(sizeof(PgHdr)), + pCache->bPurgeable + ); + if( pNew==0 ) return SQLITE_NOMEM; + sqlite3GlobalConfig.pcache2.xCachesize(pNew, numberOfCachePages(pCache)); + if( pCache->pCache ){ + sqlite3GlobalConfig.pcache2.xDestroy(pCache->pCache); + } + pCache->pCache = pNew; + pCache->szPage = szPage; } + return SQLITE_OK; } /* ** Try to obtain a page from the cache. +** +** This routine returns a pointer to an sqlite3_pcache_page object if +** such an object is already in cache, or if a new one is created. +** This routine returns a NULL pointer if the object was not in cache +** and could not be created. +** +** The createFlags should be 0 to check for existing pages and should +** be 3 (not 1, but 3) to try to create a new page. +** +** If the createFlag is 0, then NULL is always returned if the page +** is not already in the cache. If createFlag is 1, then a new page +** is created only if that can be done without spilling dirty pages +** and without exceeding the cache size limit. +** +** The caller needs to invoke sqlite3PcacheFetchFinish() to properly +** initialize the sqlite3_pcache_page object and convert it into a +** PgHdr object. The sqlite3PcacheFetch() and sqlite3PcacheFetchFinish() +** routines are split this way for performance reasons. When separated +** they can both (usually) operate without having to push values to +** the stack on entry and pop them back off on exit, which saves a +** lot of pushing and popping. */ -SQLITE_PRIVATE int sqlite3PcacheFetch( +SQLITE_PRIVATE sqlite3_pcache_page *sqlite3PcacheFetch( PCache *pCache, /* Obtain the page from this cache */ Pgno pgno, /* Page number to obtain */ - int createFlag, /* If true, create page if it does not exist already */ - PgHdr **ppPage /* Write the page here */ + int createFlag /* If true, create page if it does not exist already */ ){ - sqlite3_pcache_page *pPage; - PgHdr *pPgHdr = 0; int eCreate; assert( pCache!=0 ); - assert( createFlag==1 || createFlag==0 ); + assert( pCache->pCache!=0 ); + assert( createFlag==3 || createFlag==0 ); assert( pgno>0 ); - /* If the pluggable cache (sqlite3_pcache*) has not been allocated, - ** allocate it now. - */ - if( !pCache->pCache ){ - sqlite3_pcache *p; - if( !createFlag ){ - *ppPage = 0; - return SQLITE_OK; - } - p = sqlite3GlobalConfig.pcache2.xCreate( - pCache->szPage, pCache->szExtra + sizeof(PgHdr), pCache->bPurgeable - ); - if( !p ){ - return SQLITE_NOMEM; - } - sqlite3GlobalConfig.pcache2.xCachesize(p, numberOfCachePages(pCache)); - pCache->pCache = p; - } - /* eCreate defines what to do if the page does not exist. ** 0 Do not allocate a new page. (createFlag==0) ** 1 Allocate a new page if doing so is inexpensive. @@ -37800,18 +41070,38 @@ SQLITE_PRIVATE int sqlite3PcacheFetch( ** 2 Allocate a new page even it doing so is difficult. ** (createFlag==1 AND !(bPurgeable AND pDirty) */ - eCreate = createFlag==0 ? 0 : pCache->eCreate; - assert( (createFlag*(1+(!pCache->bPurgeable||!pCache->pDirty)))==eCreate ); - pPage = sqlite3GlobalConfig.pcache2.xFetch(pCache->pCache, pgno, eCreate); - if( !pPage && eCreate==1 ){ - PgHdr *pPg; + eCreate = createFlag & pCache->eCreate; + assert( eCreate==0 || eCreate==1 || eCreate==2 ); + assert( createFlag==0 || pCache->eCreate==eCreate ); + assert( createFlag==0 || eCreate==1+(!pCache->bPurgeable||!pCache->pDirty) ); + return sqlite3GlobalConfig.pcache2.xFetch(pCache->pCache, pgno, eCreate); +} +/* +** If the sqlite3PcacheFetch() routine is unable to allocate a new +** page because new clean pages are available for reuse and the cache +** size limit has been reached, then this routine can be invoked to +** try harder to allocate a page. This routine might invoke the stress +** callback to spill dirty pages to the journal. It will then try to +** allocate the new page and will only fail to allocate a new page on +** an OOM error. +** +** This routine should be invoked only after sqlite3PcacheFetch() fails. +*/ +SQLITE_PRIVATE int sqlite3PcacheFetchStress( + PCache *pCache, /* Obtain the page from this cache */ + Pgno pgno, /* Page number to obtain */ + sqlite3_pcache_page **ppPage /* Write result here */ +){ + PgHdr *pPg; + if( pCache->eCreate==2 ) return 0; + + if( sqlite3PcachePagecount(pCache)>pCache->szSpill ){ /* Find a dirty page to write-out and recycle. First try to find a ** page that does not require a journal-sync (one with PGHDR_NEED_SYNC ** cleared), but if that is not possible settle for any other ** unreferenced dirty page. */ - expensive_assert( pcacheCheckSynced(pCache) ); for(pPg=pCache->pSynced; pPg && (pPg->nRef || (pPg->flags&PGHDR_NEED_SYNC)); pPg=pPg->pDirtyPrev @@ -37827,62 +41117,84 @@ SQLITE_PRIVATE int sqlite3PcacheFetch( "spill page %d making room for %d - cache used: %d/%d", pPg->pgno, pgno, sqlite3GlobalConfig.pcache.xPagecount(pCache->pCache), - numberOfCachePages(pCache)); + numberOfCachePages(pCache)); #endif rc = pCache->xStress(pCache->pStress, pPg); if( rc!=SQLITE_OK && rc!=SQLITE_BUSY ){ return rc; } } - - pPage = sqlite3GlobalConfig.pcache2.xFetch(pCache->pCache, pgno, 2); } + *ppPage = sqlite3GlobalConfig.pcache2.xFetch(pCache->pCache, pgno, 2); + return *ppPage==0 ? SQLITE_NOMEM : SQLITE_OK; +} - if( pPage ){ - pPgHdr = (PgHdr *)pPage->pExtra; +/* +** This is a helper routine for sqlite3PcacheFetchFinish() +** +** In the uncommon case where the page being fetched has not been +** initialized, this routine is invoked to do the initialization. +** This routine is broken out into a separate function since it +** requires extra stack manipulation that can be avoided in the common +** case. +*/ +static SQLITE_NOINLINE PgHdr *pcacheFetchFinishWithInit( + PCache *pCache, /* Obtain the page from this cache */ + Pgno pgno, /* Page number obtained */ + sqlite3_pcache_page *pPage /* Page obtained by prior PcacheFetch() call */ +){ + PgHdr *pPgHdr; + assert( pPage!=0 ); + pPgHdr = (PgHdr*)pPage->pExtra; + assert( pPgHdr->pPage==0 ); + memset(pPgHdr, 0, sizeof(PgHdr)); + pPgHdr->pPage = pPage; + pPgHdr->pData = pPage->pBuf; + pPgHdr->pExtra = (void *)&pPgHdr[1]; + memset(pPgHdr->pExtra, 0, pCache->szExtra); + pPgHdr->pCache = pCache; + pPgHdr->pgno = pgno; + pPgHdr->flags = PGHDR_CLEAN; + return sqlite3PcacheFetchFinish(pCache,pgno,pPage); +} - if( !pPgHdr->pPage ){ - memset(pPgHdr, 0, sizeof(PgHdr)); - pPgHdr->pPage = pPage; - pPgHdr->pData = pPage->pBuf; - pPgHdr->pExtra = (void *)&pPgHdr[1]; - memset(pPgHdr->pExtra, 0, pCache->szExtra); - pPgHdr->pCache = pCache; - pPgHdr->pgno = pgno; - } - assert( pPgHdr->pCache==pCache ); - assert( pPgHdr->pgno==pgno ); - assert( pPgHdr->pData==pPage->pBuf ); - assert( pPgHdr->pExtra==(void *)&pPgHdr[1] ); +/* +** This routine converts the sqlite3_pcache_page object returned by +** sqlite3PcacheFetch() into an initialized PgHdr object. This routine +** must be called after sqlite3PcacheFetch() in order to get a usable +** result. +*/ +SQLITE_PRIVATE PgHdr *sqlite3PcacheFetchFinish( + PCache *pCache, /* Obtain the page from this cache */ + Pgno pgno, /* Page number obtained */ + sqlite3_pcache_page *pPage /* Page obtained by prior PcacheFetch() call */ +){ + PgHdr *pPgHdr; - if( 0==pPgHdr->nRef ){ - pCache->nRef++; - } - pPgHdr->nRef++; - if( pgno==1 ){ - pCache->pPage1 = pPgHdr; - } + assert( pPage!=0 ); + pPgHdr = (PgHdr *)pPage->pExtra; + + if( !pPgHdr->pPage ){ + return pcacheFetchFinishWithInit(pCache, pgno, pPage); } - *ppPage = pPgHdr; - return (pPgHdr==0 && eCreate) ? SQLITE_NOMEM : SQLITE_OK; + pCache->nRefSum++; + pPgHdr->nRef++; + return pPgHdr; } /* ** Decrement the reference count on a page. If the page is clean and the -** reference count drops to 0, then it is made elible for recycling. +** reference count drops to 0, then it is made eligible for recycling. */ -SQLITE_PRIVATE void sqlite3PcacheRelease(PgHdr *p){ +SQLITE_PRIVATE void SQLITE_NOINLINE sqlite3PcacheRelease(PgHdr *p){ assert( p->nRef>0 ); - p->nRef--; - if( p->nRef==0 ){ - PCache *pCache = p->pCache; - pCache->nRef--; - if( (p->flags&PGHDR_DIRTY)==0 ){ + p->pCache->nRefSum--; + if( (--p->nRef)==0 ){ + if( p->flags&PGHDR_CLEAN ){ pcacheUnpin(p); - }else{ + }else if( p->pDirtyPrev!=0 ){ /* Move the page to the head of the dirty list. */ - pcacheRemoveFromDirtyList(p); - pcacheAddToDirtyList(p); + pcacheManageDirtyList(p, PCACHE_DIRTYLIST_FRONT); } } } @@ -37893,6 +41205,7 @@ SQLITE_PRIVATE void sqlite3PcacheRelease(PgHdr *p){ SQLITE_PRIVATE void sqlite3PcacheRef(PgHdr *p){ assert(p->nRef>0); p->nRef++; + p->pCache->nRefSum++; } /* @@ -37901,17 +41214,12 @@ SQLITE_PRIVATE void sqlite3PcacheRef(PgHdr *p){ ** page pointed to by p is invalid. */ SQLITE_PRIVATE void sqlite3PcacheDrop(PgHdr *p){ - PCache *pCache; assert( p->nRef==1 ); if( p->flags&PGHDR_DIRTY ){ - pcacheRemoveFromDirtyList(p); + pcacheManageDirtyList(p, PCACHE_DIRTYLIST_REMOVE); } - pCache = p->pCache; - pCache->nRef--; - if( p->pgno==1 ){ - pCache->pPage1 = 0; - } - sqlite3GlobalConfig.pcache2.xUnpin(pCache->pCache, p->pPage, 1); + p->pCache->nRefSum--; + sqlite3GlobalConfig.pcache2.xUnpin(p->pCache->pCache, p->pPage, 1); } /* @@ -37919,11 +41227,14 @@ SQLITE_PRIVATE void sqlite3PcacheDrop(PgHdr *p){ ** make it so. */ SQLITE_PRIVATE void sqlite3PcacheMakeDirty(PgHdr *p){ - p->flags &= ~PGHDR_DONT_WRITE; assert( p->nRef>0 ); - if( 0==(p->flags & PGHDR_DIRTY) ){ - p->flags |= PGHDR_DIRTY; - pcacheAddToDirtyList( p); + if( p->flags & (PGHDR_CLEAN|PGHDR_DONT_WRITE) ){ + p->flags &= ~PGHDR_DONT_WRITE; + if( p->flags & PGHDR_CLEAN ){ + p->flags ^= (PGHDR_DIRTY|PGHDR_CLEAN); + assert( (p->flags & (PGHDR_DIRTY|PGHDR_CLEAN))==PGHDR_DIRTY ); + pcacheManageDirtyList(p, PCACHE_DIRTYLIST_ADD); + } } } @@ -37933,8 +41244,10 @@ SQLITE_PRIVATE void sqlite3PcacheMakeDirty(PgHdr *p){ */ SQLITE_PRIVATE void sqlite3PcacheMakeClean(PgHdr *p){ if( (p->flags & PGHDR_DIRTY) ){ - pcacheRemoveFromDirtyList(p); - p->flags &= ~(PGHDR_DIRTY|PGHDR_NEED_SYNC); + assert( (p->flags & PGHDR_CLEAN)==0 ); + pcacheManageDirtyList(p, PCACHE_DIRTYLIST_REMOVE); + p->flags &= ~(PGHDR_DIRTY|PGHDR_NEED_SYNC|PGHDR_WRITEABLE); + p->flags |= PGHDR_CLEAN; if( p->nRef==0 ){ pcacheUnpin(p); } @@ -37972,8 +41285,7 @@ SQLITE_PRIVATE void sqlite3PcacheMove(PgHdr *p, Pgno newPgno){ sqlite3GlobalConfig.pcache2.xRekey(pCache->pCache, p->pPage, p->pgno,newPgno); p->pgno = newPgno; if( (p->flags&PGHDR_DIRTY) && (p->flags&PGHDR_NEED_SYNC) ){ - pcacheRemoveFromDirtyList(p); - pcacheAddToDirtyList(p); + pcacheManageDirtyList(p, PCACHE_DIRTYLIST_FRONT); } } @@ -38002,9 +41314,14 @@ SQLITE_PRIVATE void sqlite3PcacheTruncate(PCache *pCache, Pgno pgno){ sqlite3PcacheMakeClean(p); } } - if( pgno==0 && pCache->pPage1 ){ - memset(pCache->pPage1->pData, 0, pCache->szPage); - pgno = 1; + if( pgno==0 && pCache->nRefSum ){ + sqlite3_pcache_page *pPage1; + pPage1 = sqlite3GlobalConfig.pcache2.xFetch(pCache->pCache,1,0); + if( ALWAYS(pPage1) ){ /* Page 1 is always available in cache, because + ** pCache->nRefSum>0 */ + memset(pPage1->pBuf, 0, pCache->szPage); + pgno = 1; + } } sqlite3GlobalConfig.pcache2.xTruncate(pCache->pCache, pgno+1); } @@ -38014,9 +41331,8 @@ SQLITE_PRIVATE void sqlite3PcacheTruncate(PCache *pCache, Pgno pgno){ ** Close a cache. */ SQLITE_PRIVATE void sqlite3PcacheClose(PCache *pCache){ - if( pCache->pCache ){ - sqlite3GlobalConfig.pcache2.xDestroy(pCache->pCache); - } + assert( pCache->pCache!=0 ); + sqlite3GlobalConfig.pcache2.xDestroy(pCache->pCache); } /* @@ -38108,10 +41424,13 @@ SQLITE_PRIVATE PgHdr *sqlite3PcacheDirtyList(PCache *pCache){ } /* -** Return the total number of referenced pages held by the cache. +** Return the total number of references to all pages held by the cache. +** +** This is not the total number of pages referenced, but the sum of the +** reference count for all pages. */ SQLITE_PRIVATE int sqlite3PcacheRefCount(PCache *pCache){ - return pCache->nRef; + return pCache->nRefSum; } /* @@ -38125,11 +41444,8 @@ SQLITE_PRIVATE int sqlite3PcachePageRefcount(PgHdr *p){ ** Return the total number of pages in the cache. */ SQLITE_PRIVATE int sqlite3PcachePagecount(PCache *pCache){ - int nPage = 0; - if( pCache->pCache ){ - nPage = sqlite3GlobalConfig.pcache2.xPagecount(pCache->pCache); - } - return nPage; + assert( pCache->pCache!=0 ); + return sqlite3GlobalConfig.pcache2.xPagecount(pCache->pCache); } #ifdef SQLITE_TEST @@ -38145,22 +41461,46 @@ SQLITE_PRIVATE int sqlite3PcacheGetCachesize(PCache *pCache){ ** Set the suggested cache-size value. */ SQLITE_PRIVATE void sqlite3PcacheSetCachesize(PCache *pCache, int mxPage){ + assert( pCache->pCache!=0 ); pCache->szCache = mxPage; - if( pCache->pCache ){ - sqlite3GlobalConfig.pcache2.xCachesize(pCache->pCache, - numberOfCachePages(pCache)); + sqlite3GlobalConfig.pcache2.xCachesize(pCache->pCache, + numberOfCachePages(pCache)); +} + +/* +** Set the suggested cache-spill value. Make no changes if if the +** argument is zero. Return the effective cache-spill size, which will +** be the larger of the szSpill and szCache. +*/ +SQLITE_PRIVATE int sqlite3PcacheSetSpillsize(PCache *p, int mxPage){ + int res; + assert( p->pCache!=0 ); + if( mxPage ){ + if( mxPage<0 ){ + mxPage = (int)((-1024*(i64)mxPage)/(p->szPage+p->szExtra)); + } + p->szSpill = mxPage; } + res = numberOfCachePages(p); + if( resszSpill ) res = p->szSpill; + return res; } /* ** Free up as much memory as possible from the page cache. */ SQLITE_PRIVATE void sqlite3PcacheShrink(PCache *pCache){ - if( pCache->pCache ){ - sqlite3GlobalConfig.pcache2.xShrink(pCache->pCache); - } + assert( pCache->pCache!=0 ); + sqlite3GlobalConfig.pcache2.xShrink(pCache->pCache); } +/* +** Return the size of the header added by this middleware layer +** in the page-cache hierarchy. +*/ +SQLITE_PRIVATE int sqlite3HeaderSizePcache(void){ return ROUND8(sizeof(PgHdr)); } + + #if defined(SQLITE_CHECK_PAGES) || defined(SQLITE_DEBUG) /* ** For all dirty pages currently in the cache, invoke the specified @@ -38192,18 +41532,100 @@ SQLITE_PRIVATE void sqlite3PcacheIterateDirty(PCache *pCache, void (*xIter)(PgHd ** This file implements the default page cache implementation (the ** sqlite3_pcache interface). It also contains part of the implementation ** of the SQLITE_CONFIG_PAGECACHE and sqlite3_release_memory() features. -** If the default page cache implementation is overriden, then neither of +** If the default page cache implementation is overridden, then neither of ** these two features are available. +** +** A Page cache line looks like this: +** +** ------------------------------------------------------------- +** | database page content | PgHdr1 | MemPage | PgHdr | +** ------------------------------------------------------------- +** +** The database page content is up front (so that buffer overreads tend to +** flow harmlessly into the PgHdr1, MemPage, and PgHdr extensions). MemPage +** is the extension added by the btree.c module containing information such +** as the database page number and how that database page is used. PgHdr +** is added by the pcache.c layer and contains information used to keep track +** of which pages are "dirty". PgHdr1 is an extension added by this +** module (pcache1.c). The PgHdr1 header is a subclass of sqlite3_pcache_page. +** PgHdr1 contains information needed to look up a page by its page number. +** The superclass sqlite3_pcache_page.pBuf points to the start of the +** database page content and sqlite3_pcache_page.pExtra points to PgHdr. +** +** The size of the extension (MemPage+PgHdr+PgHdr1) can be determined at +** runtime using sqlite3_config(SQLITE_CONFIG_PCACHE_HDRSZ, &size). The +** sizes of the extensions sum to 272 bytes on x64 for 3.8.10, but this +** size can vary according to architecture, compile-time options, and +** SQLite library version number. +** +** If SQLITE_PCACHE_SEPARATE_HEADER is defined, then the extension is obtained +** using a separate memory allocation from the database page content. This +** seeks to overcome the "clownshoe" problem (also called "internal +** fragmentation" in academic literature) of allocating a few bytes more +** than a power of two with the memory allocator rounding up to the next +** power of two, and leaving the rounded-up space unused. +** +** This module tracks pointers to PgHdr1 objects. Only pcache.c communicates +** with this module. Information is passed back and forth as PgHdr1 pointers. +** +** The pcache.c and pager.c modules deal pointers to PgHdr objects. +** The btree.c module deals with pointers to MemPage objects. +** +** SOURCE OF PAGE CACHE MEMORY: +** +** Memory for a page might come from any of three sources: +** +** (1) The general-purpose memory allocator - sqlite3Malloc() +** (2) Global page-cache memory provided using sqlite3_config() with +** SQLITE_CONFIG_PAGECACHE. +** (3) PCache-local bulk allocation. +** +** The third case is a chunk of heap memory (defaulting to 100 pages worth) +** that is allocated when the page cache is created. The size of the local +** bulk allocation can be adjusted using +** +** sqlite3_config(SQLITE_CONFIG_PAGECACHE, (void*)0, 0, N). +** +** If N is positive, then N pages worth of memory are allocated using a single +** sqlite3Malloc() call and that memory is used for the first N pages allocated. +** Or if N is negative, then -1024*N bytes of memory are allocated and used +** for as many pages as can be accomodated. +** +** Only one of (2) or (3) can be used. Once the memory available to (2) or +** (3) is exhausted, subsequent allocations fail over to the general-purpose +** memory allocator (1). +** +** Earlier versions of SQLite used only methods (1) and (2). But experiments +** show that method (3) with N==100 provides about a 5% performance boost for +** common workloads. */ - +/* #include "sqliteInt.h" */ typedef struct PCache1 PCache1; typedef struct PgHdr1 PgHdr1; typedef struct PgFreeslot PgFreeslot; typedef struct PGroup PGroup; +/* +** Each cache entry is represented by an instance of the following +** structure. Unless SQLITE_PCACHE_SEPARATE_HEADER is defined, a buffer of +** PgHdr1.pCache->szPage bytes is allocated directly before this structure +** in memory. +*/ +struct PgHdr1 { + sqlite3_pcache_page page; /* Base class. Must be first. pBuf & pExtra */ + unsigned int iKey; /* Key value (page number) */ + u8 isPinned; /* Page in use, not on the LRU list */ + u8 isBulkLocal; /* This page from bulk local storage */ + u8 isAnchor; /* This is the PGroup.lru element */ + PgHdr1 *pNext; /* Next in hash table chain */ + PCache1 *pCache; /* Cache that currently owns this page */ + PgHdr1 *pLruNext; /* Next in LRU list of unpinned pages */ + PgHdr1 *pLruPrev; /* Previous in LRU list of unpinned pages */ +}; + /* Each page cache (or PCache) belongs to a PGroup. A PGroup is a set -** of one or more PCaches that are able to recycle each others unpinned +** of one or more PCaches that are able to recycle each other's unpinned ** pages when they are under memory pressure. A PGroup is an instance of ** the following object. ** @@ -38230,7 +41652,7 @@ struct PGroup { unsigned int nMinPage; /* Sum of nMin for purgeable caches */ unsigned int mxPinned; /* nMaxpage + 10 - nMinPage */ unsigned int nCurrentPage; /* Number of purgeable pages allocated */ - PgHdr1 *pLruHead, *pLruTail; /* LRU list of unpinned pages */ + PgHdr1 lru; /* The beginning and end of the LRU list */ }; /* Each page cache is an instance of the following object. Every @@ -38248,8 +41670,9 @@ struct PCache1 { ** The PGroup mutex must be held when accessing nMax. */ PGroup *pGroup; /* PGroup this cache belongs to */ - int szPage; /* Size of allocated pages in bytes */ - int szExtra; /* Size of extra space in bytes */ + int szPage; /* Size of database content section */ + int szExtra; /* sizeof(MemPage)+sizeof(PgHdr) */ + int szAlloc; /* Total size of one pcache line */ int bPurgeable; /* True if cache is purgeable */ unsigned int nMin; /* Minimum number of pages reserved */ unsigned int nMax; /* Configured "cache_size" value */ @@ -38263,27 +41686,13 @@ struct PCache1 { unsigned int nPage; /* Total number of pages in apHash */ unsigned int nHash; /* Number of slots in apHash[] */ PgHdr1 **apHash; /* Hash table for fast lookup by key */ + PgHdr1 *pFree; /* List of unused pcache-local pages */ + void *pBulk; /* Bulk memory used by pcache-local */ }; /* -** Each cache entry is represented by an instance of the following -** structure. Unless SQLITE_PCACHE_SEPARATE_HEADER is defined, a buffer of -** PgHdr1.pCache->szPage bytes is allocated directly before this structure -** in memory. -*/ -struct PgHdr1 { - sqlite3_pcache_page page; - unsigned int iKey; /* Key value (page number) */ - u8 isPinned; /* Page in use, not on the LRU list */ - PgHdr1 *pNext; /* Next in hash table chain */ - PCache1 *pCache; /* Cache that currently owns this page */ - PgHdr1 *pLruNext; /* Next in LRU list of unpinned pages */ - PgHdr1 *pLruPrev; /* Previous in LRU list of unpinned pages */ -}; - -/* -** Free slots in the allocator used to divide up the buffer provided using -** the SQLITE_CONFIG_PAGECACHE mechanism. +** Free slots in the allocator used to divide up the global page cache +** buffer provided using the SQLITE_CONFIG_PAGECACHE mechanism. */ struct PgFreeslot { PgFreeslot *pNext; /* Next free slot */ @@ -38301,10 +41710,12 @@ static SQLITE_WSD struct PCacheGlobal { ** The nFreeSlot and pFree values do require mutex protection. */ int isInit; /* True if initialized */ + int separateCache; /* Use a new PGroup for each PCache */ + int nInitPage; /* Initial bulk allocation size */ int szSlot; /* Size of each free slot */ int nSlot; /* The number of pcache slots */ int nReserve; /* Try to keep nFreeSlot above this */ - void *pStart, *pEnd; /* Bounds of pagecache malloc range */ + void *pStart, *pEnd; /* Bounds of global page cache memory */ /* Above requires no mutex. Use mutex below for variable that follow. */ sqlite3_mutex *mutex; /* Mutex for accessing the following: */ PgFreeslot *pFree; /* Free page blocks */ @@ -38326,12 +41737,20 @@ static SQLITE_WSD struct PCacheGlobal { /* ** Macros to enter and leave the PCache LRU mutex. */ -#define pcache1EnterMutex(X) sqlite3_mutex_enter((X)->mutex) -#define pcache1LeaveMutex(X) sqlite3_mutex_leave((X)->mutex) +#if !defined(SQLITE_ENABLE_MEMORY_MANAGEMENT) || SQLITE_THREADSAFE==0 +# define pcache1EnterMutex(X) assert((X)->mutex==0) +# define pcache1LeaveMutex(X) assert((X)->mutex==0) +# define PCACHE1_MIGHT_USE_GROUP_MUTEX 0 +#else +# define pcache1EnterMutex(X) sqlite3_mutex_enter((X)->mutex) +# define pcache1LeaveMutex(X) sqlite3_mutex_leave((X)->mutex) +# define PCACHE1_MIGHT_USE_GROUP_MUTEX 1 +#endif /******************************************************************************/ /******** Page Allocation/SQLITE_CONFIG_PCACHE Related Functions **************/ + /* ** This function is called during initialization if a static buffer is ** supplied to use for the page-cache by passing the SQLITE_CONFIG_PAGECACHE @@ -38344,6 +41763,7 @@ static SQLITE_WSD struct PCacheGlobal { SQLITE_PRIVATE void sqlite3PCacheBufferSetup(void *pBuf, int sz, int n){ if( pcache1.isInit ){ PgFreeslot *p; + if( pBuf==0 ) sz = n = 0; sz = ROUNDDOWN8(sz); pcache1.szSlot = sz; pcache1.nSlot = pcache1.nFreeSlot = n; @@ -38361,6 +41781,44 @@ SQLITE_PRIVATE void sqlite3PCacheBufferSetup(void *pBuf, int sz, int n){ } } +/* +** Try to initialize the pCache->pFree and pCache->pBulk fields. Return +** true if pCache->pFree ends up containing one or more free pages. +*/ +static int pcache1InitBulk(PCache1 *pCache){ + i64 szBulk; + char *zBulk; + if( pcache1.nInitPage==0 ) return 0; + /* Do not bother with a bulk allocation if the cache size very small */ + if( pCache->nMax<3 ) return 0; + sqlite3BeginBenignMalloc(); + if( pcache1.nInitPage>0 ){ + szBulk = pCache->szAlloc * (i64)pcache1.nInitPage; + }else{ + szBulk = -1024 * (i64)pcache1.nInitPage; + } + if( szBulk > pCache->szAlloc*(i64)pCache->nMax ){ + szBulk = pCache->szAlloc*pCache->nMax; + } + zBulk = pCache->pBulk = sqlite3Malloc( szBulk ); + sqlite3EndBenignMalloc(); + if( zBulk ){ + int nBulk = sqlite3MallocSize(zBulk)/pCache->szAlloc; + int i; + for(i=0; iszPage]; + pX->page.pBuf = zBulk; + pX->page.pExtra = &pX[1]; + pX->isBulkLocal = 1; + pX->isAnchor = 0; + pX->pNext = pCache->pFree; + pCache->pFree = pX; + zBulk += pCache->szAlloc; + } + } + return pCache->pFree!=0; +} + /* ** Malloc function used within this file to allocate space from the buffer ** configured using sqlite3_config(SQLITE_CONFIG_PAGECACHE) option. If no @@ -38373,7 +41831,6 @@ SQLITE_PRIVATE void sqlite3PCacheBufferSetup(void *pBuf, int sz, int n){ static void *pcache1Alloc(int nByte){ void *p = 0; assert( sqlite3_mutex_notheld(pcache1.grp.mutex) ); - sqlite3StatusSet(SQLITE_STATUS_PAGECACHE_SIZE, nByte); if( nByte<=pcache1.szSlot ){ sqlite3_mutex_enter(pcache1.mutex); p = (PgHdr1 *)pcache1.pFree; @@ -38382,7 +41839,8 @@ static void *pcache1Alloc(int nByte){ pcache1.nFreeSlot--; pcache1.bUnderPressure = pcache1.nFreeSlot=0 ); - sqlite3StatusAdd(SQLITE_STATUS_PAGECACHE_USED, 1); + sqlite3StatusHighwater(SQLITE_STATUS_PAGECACHE_SIZE, nByte); + sqlite3StatusUp(SQLITE_STATUS_PAGECACHE_USED, 1); } sqlite3_mutex_leave(pcache1.mutex); } @@ -38395,7 +41853,8 @@ static void *pcache1Alloc(int nByte){ if( p ){ int sz = sqlite3MallocSize(p); sqlite3_mutex_enter(pcache1.mutex); - sqlite3StatusAdd(SQLITE_STATUS_PAGECACHE_OVERFLOW, sz); + sqlite3StatusHighwater(SQLITE_STATUS_PAGECACHE_SIZE, nByte); + sqlite3StatusUp(SQLITE_STATUS_PAGECACHE_OVERFLOW, sz); sqlite3_mutex_leave(pcache1.mutex); } #endif @@ -38407,13 +41866,13 @@ static void *pcache1Alloc(int nByte){ /* ** Free an allocated buffer obtained from pcache1Alloc(). */ -static int pcache1Free(void *p){ +static void pcache1Free(void *p){ int nFreed = 0; - if( p==0 ) return 0; - if( p>=pcache1.pStart && ppNext = pcache1.pFree; pcache1.pFree = pSlot; @@ -38424,15 +41883,14 @@ static int pcache1Free(void *p){ }else{ assert( sqlite3MemdebugHasType(p, MEMTYPE_PCACHE) ); sqlite3MemdebugSetType(p, MEMTYPE_HEAP); - nFreed = sqlite3MallocSize(p); #ifndef SQLITE_DISABLE_PAGECACHE_OVERFLOW_STATS + nFreed = sqlite3MallocSize(p); sqlite3_mutex_enter(pcache1.mutex); - sqlite3StatusAdd(SQLITE_STATUS_PAGECACHE_OVERFLOW, -nFreed); + sqlite3StatusDown(SQLITE_STATUS_PAGECACHE_OVERFLOW, nFreed); sqlite3_mutex_leave(pcache1.mutex); #endif sqlite3_free(p); } - return nFreed; } #ifdef SQLITE_ENABLE_MEMORY_MANAGEMENT @@ -38456,58 +41914,72 @@ static int pcache1MemSize(void *p){ /* ** Allocate a new page object initially associated with cache pCache. */ -static PgHdr1 *pcache1AllocPage(PCache1 *pCache){ +static PgHdr1 *pcache1AllocPage(PCache1 *pCache, int benignMalloc){ PgHdr1 *p = 0; void *pPg; - /* The group mutex must be released before pcache1Alloc() is called. This - ** is because it may call sqlite3_release_memory(), which assumes that - ** this mutex is not held. */ assert( sqlite3_mutex_held(pCache->pGroup->mutex) ); - pcache1LeaveMutex(pCache->pGroup); -#ifdef SQLITE_PCACHE_SEPARATE_HEADER - pPg = pcache1Alloc(pCache->szPage); - p = sqlite3Malloc(sizeof(PgHdr1) + pCache->szExtra); - if( !pPg || !p ){ - pcache1Free(pPg); - sqlite3_free(p); - pPg = 0; - } -#else - pPg = pcache1Alloc(sizeof(PgHdr1) + pCache->szPage + pCache->szExtra); - p = (PgHdr1 *)&((u8 *)pPg)[pCache->szPage]; + if( pCache->pFree || (pCache->nPage==0 && pcache1InitBulk(pCache)) ){ + p = pCache->pFree; + pCache->pFree = p->pNext; + p->pNext = 0; + }else{ +#ifdef SQLITE_ENABLE_MEMORY_MANAGEMENT + /* The group mutex must be released before pcache1Alloc() is called. This + ** is because it might call sqlite3_release_memory(), which assumes that + ** this mutex is not held. */ + assert( pcache1.separateCache==0 ); + assert( pCache->pGroup==&pcache1.grp ); + pcache1LeaveMutex(pCache->pGroup); #endif - pcache1EnterMutex(pCache->pGroup); - - if( pPg ){ + if( benignMalloc ){ sqlite3BeginBenignMalloc(); } +#ifdef SQLITE_PCACHE_SEPARATE_HEADER + pPg = pcache1Alloc(pCache->szPage); + p = sqlite3Malloc(sizeof(PgHdr1) + pCache->szExtra); + if( !pPg || !p ){ + pcache1Free(pPg); + sqlite3_free(p); + pPg = 0; + } +#else + pPg = pcache1Alloc(pCache->szAlloc); + p = (PgHdr1 *)&((u8 *)pPg)[pCache->szPage]; +#endif + if( benignMalloc ){ sqlite3EndBenignMalloc(); } +#ifdef SQLITE_ENABLE_MEMORY_MANAGEMENT + pcache1EnterMutex(pCache->pGroup); +#endif + if( pPg==0 ) return 0; p->page.pBuf = pPg; p->page.pExtra = &p[1]; - if( pCache->bPurgeable ){ - pCache->pGroup->nCurrentPage++; - } - return p; + p->isBulkLocal = 0; + p->isAnchor = 0; } - return 0; + if( pCache->bPurgeable ){ + pCache->pGroup->nCurrentPage++; + } + return p; } /* ** Free a page object allocated by pcache1AllocPage(). -** -** The pointer is allowed to be NULL, which is prudent. But it turns out -** that the current implementation happens to never call this routine -** with a NULL pointer, so we mark the NULL test with ALWAYS(). */ static void pcache1FreePage(PgHdr1 *p){ - if( ALWAYS(p) ){ - PCache1 *pCache = p->pCache; - assert( sqlite3_mutex_held(p->pCache->pGroup->mutex) ); + PCache1 *pCache; + assert( p!=0 ); + pCache = p->pCache; + assert( sqlite3_mutex_held(p->pCache->pGroup->mutex) ); + if( p->isBulkLocal ){ + p->pNext = pCache->pFree; + pCache->pFree = p; + }else{ pcache1Free(p->page.pBuf); #ifdef SQLITE_PCACHE_SEPARATE_HEADER sqlite3_free(p); #endif - if( pCache->bPurgeable ){ - pCache->pGroup->nCurrentPage--; - } + } + if( pCache->bPurgeable ){ + pCache->pGroup->nCurrentPage--; } } @@ -38561,7 +42033,7 @@ static int pcache1UnderMemoryPressure(PCache1 *pCache){ ** ** The PCache mutex must be held when this function is called. */ -static int pcache1ResizeHash(PCache1 *p){ +static void pcache1ResizeHash(PCache1 *p){ PgHdr1 **apNew; unsigned int nNew; unsigned int i; @@ -38593,8 +42065,6 @@ static int pcache1ResizeHash(PCache1 *p){ p->apHash = apNew; p->nHash = nNew; } - - return (p->apHash ? SQLITE_OK : SQLITE_NOMEM); } /* @@ -38604,41 +42074,35 @@ static int pcache1ResizeHash(PCache1 *p){ ** ** The PGroup mutex must be held when this function is called. */ -static void pcache1PinPage(PgHdr1 *pPage){ +static PgHdr1 *pcache1PinPage(PgHdr1 *pPage){ PCache1 *pCache; - PGroup *pGroup; assert( pPage!=0 ); assert( pPage->isPinned==0 ); pCache = pPage->pCache; - pGroup = pCache->pGroup; - assert( pPage->pLruNext || pPage==pGroup->pLruTail ); - assert( pPage->pLruPrev || pPage==pGroup->pLruHead ); - assert( sqlite3_mutex_held(pGroup->mutex) ); - if( pPage->pLruPrev ){ - pPage->pLruPrev->pLruNext = pPage->pLruNext; - }else{ - pGroup->pLruHead = pPage->pLruNext; - } - if( pPage->pLruNext ){ - pPage->pLruNext->pLruPrev = pPage->pLruPrev; - }else{ - pGroup->pLruTail = pPage->pLruPrev; - } + assert( pPage->pLruNext ); + assert( pPage->pLruPrev ); + assert( sqlite3_mutex_held(pCache->pGroup->mutex) ); + pPage->pLruPrev->pLruNext = pPage->pLruNext; + pPage->pLruNext->pLruPrev = pPage->pLruPrev; pPage->pLruNext = 0; pPage->pLruPrev = 0; pPage->isPinned = 1; + assert( pPage->isAnchor==0 ); + assert( pCache->pGroup->lru.isAnchor==1 ); pCache->nRecyclable--; + return pPage; } /* ** Remove the page supplied as an argument from the hash table ** (PCache1.apHash structure) that it is currently stored in. +** Also free the page if freePage is true. ** ** The PGroup mutex must be held when this function is called. */ -static void pcache1RemoveFromHash(PgHdr1 *pPage){ +static void pcache1RemoveFromHash(PgHdr1 *pPage, int freeFlag){ unsigned int h; PCache1 *pCache = pPage->pCache; PgHdr1 **pp; @@ -38649,21 +42113,28 @@ static void pcache1RemoveFromHash(PgHdr1 *pPage){ *pp = (*pp)->pNext; pCache->nPage--; + if( freeFlag ) pcache1FreePage(pPage); } /* ** If there are currently more than nMaxPage pages allocated, try ** to recycle pages to reduce the number allocated to nMaxPage. */ -static void pcache1EnforceMaxPage(PGroup *pGroup){ +static void pcache1EnforceMaxPage(PCache1 *pCache){ + PGroup *pGroup = pCache->pGroup; + PgHdr1 *p; assert( sqlite3_mutex_held(pGroup->mutex) ); - while( pGroup->nCurrentPage>pGroup->nMaxPage && pGroup->pLruTail ){ - PgHdr1 *p = pGroup->pLruTail; + while( pGroup->nCurrentPage>pGroup->nMaxPage + && (p=pGroup->lru.pLruPrev)->isAnchor==0 + ){ assert( p->pCache->pGroup==pGroup ); assert( p->isPinned==0 ); pcache1PinPage(p); - pcache1RemoveFromHash(p); - pcache1FreePage(p); + pcache1RemoveFromHash(p, 1); + } + if( pCache->nPage==0 && pCache->pBulk ){ + sqlite3_free(pCache->pBulk); + pCache->pBulk = pCache->pFree = 0; } } @@ -38709,10 +42180,45 @@ static int pcache1Init(void *NotUsed){ UNUSED_PARAMETER(NotUsed); assert( pcache1.isInit==0 ); memset(&pcache1, 0, sizeof(pcache1)); + + + /* + ** The pcache1.separateCache variable is true if each PCache has its own + ** private PGroup (mode-1). pcache1.separateCache is false if the single + ** PGroup in pcache1.grp is used for all page caches (mode-2). + ** + ** * Always use a unified cache (mode-2) if ENABLE_MEMORY_MANAGEMENT + ** + ** * Use a unified cache in single-threaded applications that have + ** configured a start-time buffer for use as page-cache memory using + ** sqlite3_config(SQLITE_CONFIG_PAGECACHE, pBuf, sz, N) with non-NULL + ** pBuf argument. + ** + ** * Otherwise use separate caches (mode-1) + */ +#if defined(SQLITE_ENABLE_MEMORY_MANAGEMENT) + pcache1.separateCache = 0; +#elif SQLITE_THREADSAFE + pcache1.separateCache = sqlite3GlobalConfig.pPage==0 + || sqlite3GlobalConfig.bCoreMutex>0; +#else + pcache1.separateCache = sqlite3GlobalConfig.pPage==0; +#endif + +#if SQLITE_THREADSAFE if( sqlite3GlobalConfig.bCoreMutex ){ pcache1.grp.mutex = sqlite3_mutex_alloc(SQLITE_MUTEX_STATIC_LRU); pcache1.mutex = sqlite3_mutex_alloc(SQLITE_MUTEX_STATIC_PMEM); } +#endif + if( pcache1.separateCache + && sqlite3GlobalConfig.nPage!=0 + && sqlite3GlobalConfig.pPage==0 + ){ + pcache1.nInitPage = sqlite3GlobalConfig.nPage; + }else{ + pcache1.nInitPage = 0; + } pcache1.grp.mxPinned = 10; pcache1.isInit = 1; return SQLITE_OK; @@ -38729,6 +42235,9 @@ static void pcache1Shutdown(void *NotUsed){ memset(&pcache1, 0, sizeof(pcache1)); } +/* forward declaration */ +static void pcache1Destroy(sqlite3_pcache *p); + /* ** Implementation of the sqlite3_pcache.xCreate method. ** @@ -38739,46 +42248,38 @@ static sqlite3_pcache *pcache1Create(int szPage, int szExtra, int bPurgeable){ PGroup *pGroup; /* The group the new page cache will belong to */ int sz; /* Bytes of memory required to allocate the new cache */ - /* - ** The separateCache variable is true if each PCache has its own private - ** PGroup. In other words, separateCache is true for mode (1) where no - ** mutexing is required. - ** - ** * Always use a unified cache (mode-2) if ENABLE_MEMORY_MANAGEMENT - ** - ** * Always use a unified cache in single-threaded applications - ** - ** * Otherwise (if multi-threaded and ENABLE_MEMORY_MANAGEMENT is off) - ** use separate caches (mode-1) - */ -#if defined(SQLITE_ENABLE_MEMORY_MANAGEMENT) || SQLITE_THREADSAFE==0 - const int separateCache = 0; -#else - int separateCache = sqlite3GlobalConfig.bCoreMutex>0; -#endif - assert( (szPage & (szPage-1))==0 && szPage>=512 && szPage<=65536 ); assert( szExtra < 300 ); - sz = sizeof(PCache1) + sizeof(PGroup)*separateCache; + sz = sizeof(PCache1) + sizeof(PGroup)*pcache1.separateCache; pCache = (PCache1 *)sqlite3MallocZero(sz); if( pCache ){ - if( separateCache ){ + if( pcache1.separateCache ){ pGroup = (PGroup*)&pCache[1]; pGroup->mxPinned = 10; }else{ pGroup = &pcache1.grp; } + if( pGroup->lru.isAnchor==0 ){ + pGroup->lru.isAnchor = 1; + pGroup->lru.pLruPrev = pGroup->lru.pLruNext = &pGroup->lru; + } pCache->pGroup = pGroup; pCache->szPage = szPage; pCache->szExtra = szExtra; + pCache->szAlloc = szPage + szExtra + ROUND8(sizeof(PgHdr1)); pCache->bPurgeable = (bPurgeable ? 1 : 0); + pcache1EnterMutex(pGroup); + pcache1ResizeHash(pCache); if( bPurgeable ){ pCache->nMin = 10; - pcache1EnterMutex(pGroup); pGroup->nMinPage += pCache->nMin; pGroup->mxPinned = pGroup->nMaxPage + 10 - pGroup->nMinPage; - pcache1LeaveMutex(pGroup); + } + pcache1LeaveMutex(pGroup); + if( pCache->nHash==0 ){ + pcache1Destroy((sqlite3_pcache*)pCache); + pCache = 0; } } return (sqlite3_pcache *)pCache; @@ -38798,7 +42299,7 @@ static void pcache1Cachesize(sqlite3_pcache *p, int nMax){ pGroup->mxPinned = pGroup->nMaxPage + 10 - pGroup->nMinPage; pCache->nMax = nMax; pCache->n90pct = pCache->nMax*9/10; - pcache1EnforceMaxPage(pGroup); + pcache1EnforceMaxPage(pCache); pcache1LeaveMutex(pGroup); } } @@ -38816,7 +42317,7 @@ static void pcache1Shrink(sqlite3_pcache *p){ pcache1EnterMutex(pGroup); savedMaxPage = pGroup->nMaxPage; pGroup->nMaxPage = 0; - pcache1EnforceMaxPage(pGroup); + pcache1EnforceMaxPage(pCache); pGroup->nMaxPage = savedMaxPage; pcache1LeaveMutex(pGroup); } @@ -38834,6 +42335,84 @@ static int pcache1Pagecount(sqlite3_pcache *p){ return n; } + +/* +** Implement steps 3, 4, and 5 of the pcache1Fetch() algorithm described +** in the header of the pcache1Fetch() procedure. +** +** This steps are broken out into a separate procedure because they are +** usually not needed, and by avoiding the stack initialization required +** for these steps, the main pcache1Fetch() procedure can run faster. +*/ +static SQLITE_NOINLINE PgHdr1 *pcache1FetchStage2( + PCache1 *pCache, + unsigned int iKey, + int createFlag +){ + unsigned int nPinned; + PGroup *pGroup = pCache->pGroup; + PgHdr1 *pPage = 0; + + /* Step 3: Abort if createFlag is 1 but the cache is nearly full */ + assert( pCache->nPage >= pCache->nRecyclable ); + nPinned = pCache->nPage - pCache->nRecyclable; + assert( pGroup->mxPinned == pGroup->nMaxPage + 10 - pGroup->nMinPage ); + assert( pCache->n90pct == pCache->nMax*9/10 ); + if( createFlag==1 && ( + nPinned>=pGroup->mxPinned + || nPinned>=pCache->n90pct + || (pcache1UnderMemoryPressure(pCache) && pCache->nRecyclablenPage>=pCache->nHash ) pcache1ResizeHash(pCache); + assert( pCache->nHash>0 && pCache->apHash ); + + /* Step 4. Try to recycle a page. */ + if( pCache->bPurgeable + && !pGroup->lru.pLruPrev->isAnchor + && ((pCache->nPage+1>=pCache->nMax) || pcache1UnderMemoryPressure(pCache)) + ){ + PCache1 *pOther; + pPage = pGroup->lru.pLruPrev; + assert( pPage->isPinned==0 ); + pcache1RemoveFromHash(pPage, 0); + pcache1PinPage(pPage); + pOther = pPage->pCache; + if( pOther->szAlloc != pCache->szAlloc ){ + pcache1FreePage(pPage); + pPage = 0; + }else{ + pGroup->nCurrentPage -= (pOther->bPurgeable - pCache->bPurgeable); + } + } + + /* Step 5. If a usable page buffer has still not been found, + ** attempt to allocate a new one. + */ + if( !pPage ){ + pPage = pcache1AllocPage(pCache, createFlag==1); + } + + if( pPage ){ + unsigned int h = iKey % pCache->nHash; + pCache->nPage++; + pPage->iKey = iKey; + pPage->pNext = pCache->apHash[h]; + pPage->pCache = pCache; + pPage->pLruPrev = 0; + pPage->pLruNext = 0; + pPage->isPinned = 1; + *(void **)pPage->page.pExtra = 0; + pCache->apHash[h] = pPage; + if( iKey>pCache->iMaxKey ){ + pCache->iMaxKey = iKey; + } + } + return pPage; +} + /* ** Implementation of the sqlite3_pcache.xFetch method. ** @@ -38887,124 +42466,80 @@ static int pcache1Pagecount(sqlite3_pcache *p){ ** proceed to step 5. ** ** 5. Otherwise, allocate and return a new page buffer. +** +** There are two versions of this routine. pcache1FetchWithMutex() is +** the general case. pcache1FetchNoMutex() is a faster implementation for +** the common case where pGroup->mutex is NULL. The pcache1Fetch() wrapper +** invokes the appropriate routine. */ +static PgHdr1 *pcache1FetchNoMutex( + sqlite3_pcache *p, + unsigned int iKey, + int createFlag +){ + PCache1 *pCache = (PCache1 *)p; + PgHdr1 *pPage = 0; + + /* Step 1: Search the hash table for an existing entry. */ + pPage = pCache->apHash[iKey % pCache->nHash]; + while( pPage && pPage->iKey!=iKey ){ pPage = pPage->pNext; } + + /* Step 2: If the page was found in the hash table, then return it. + ** If the page was not in the hash table and createFlag is 0, abort. + ** Otherwise (page not in hash and createFlag!=0) continue with + ** subsequent steps to try to create the page. */ + if( pPage ){ + if( !pPage->isPinned ){ + return pcache1PinPage(pPage); + }else{ + return pPage; + } + }else if( createFlag ){ + /* Steps 3, 4, and 5 implemented by this subroutine */ + return pcache1FetchStage2(pCache, iKey, createFlag); + }else{ + return 0; + } +} +#if PCACHE1_MIGHT_USE_GROUP_MUTEX +static PgHdr1 *pcache1FetchWithMutex( + sqlite3_pcache *p, + unsigned int iKey, + int createFlag +){ + PCache1 *pCache = (PCache1 *)p; + PgHdr1 *pPage; + + pcache1EnterMutex(pCache->pGroup); + pPage = pcache1FetchNoMutex(p, iKey, createFlag); + assert( pPage==0 || pCache->iMaxKey>=iKey ); + pcache1LeaveMutex(pCache->pGroup); + return pPage; +} +#endif static sqlite3_pcache_page *pcache1Fetch( sqlite3_pcache *p, unsigned int iKey, int createFlag ){ - unsigned int nPinned; +#if PCACHE1_MIGHT_USE_GROUP_MUTEX || defined(SQLITE_DEBUG) PCache1 *pCache = (PCache1 *)p; - PGroup *pGroup; - PgHdr1 *pPage = 0; +#endif assert( offsetof(PgHdr1,page)==0 ); assert( pCache->bPurgeable || createFlag!=1 ); assert( pCache->bPurgeable || pCache->nMin==0 ); assert( pCache->bPurgeable==0 || pCache->nMin==10 ); assert( pCache->nMin==0 || pCache->bPurgeable ); - pcache1EnterMutex(pGroup = pCache->pGroup); - - /* Step 1: Search the hash table for an existing entry. */ - if( pCache->nHash>0 ){ - unsigned int h = iKey % pCache->nHash; - for(pPage=pCache->apHash[h]; pPage&&pPage->iKey!=iKey; pPage=pPage->pNext); - } - - /* Step 2: Abort if no existing page is found and createFlag is 0 */ - if( pPage ){ - if( !pPage->isPinned ) pcache1PinPage(pPage); - goto fetch_out; - } - if( createFlag==0 ){ - goto fetch_out; - } - - /* The pGroup local variable will normally be initialized by the - ** pcache1EnterMutex() macro above. But if SQLITE_MUTEX_OMIT is defined, - ** then pcache1EnterMutex() is a no-op, so we have to initialize the - ** local variable here. Delaying the initialization of pGroup is an - ** optimization: The common case is to exit the module before reaching - ** this point. - */ -#ifdef SQLITE_MUTEX_OMIT - pGroup = pCache->pGroup; + assert( pCache->nHash>0 ); +#if PCACHE1_MIGHT_USE_GROUP_MUTEX + if( pCache->pGroup->mutex ){ + return (sqlite3_pcache_page*)pcache1FetchWithMutex(p, iKey, createFlag); + }else #endif - - /* Step 3: Abort if createFlag is 1 but the cache is nearly full */ - assert( pCache->nPage >= pCache->nRecyclable ); - nPinned = pCache->nPage - pCache->nRecyclable; - assert( pGroup->mxPinned == pGroup->nMaxPage + 10 - pGroup->nMinPage ); - assert( pCache->n90pct == pCache->nMax*9/10 ); - if( createFlag==1 && ( - nPinned>=pGroup->mxPinned - || nPinned>=pCache->n90pct - || pcache1UnderMemoryPressure(pCache) - )){ - goto fetch_out; + { + return (sqlite3_pcache_page*)pcache1FetchNoMutex(p, iKey, createFlag); } - - if( pCache->nPage>=pCache->nHash && pcache1ResizeHash(pCache) ){ - goto fetch_out; - } - assert( pCache->nHash>0 && pCache->apHash ); - - /* Step 4. Try to recycle a page. */ - if( pCache->bPurgeable && pGroup->pLruTail && ( - (pCache->nPage+1>=pCache->nMax) - || pGroup->nCurrentPage>=pGroup->nMaxPage - || pcache1UnderMemoryPressure(pCache) - )){ - PCache1 *pOther; - pPage = pGroup->pLruTail; - assert( pPage->isPinned==0 ); - pcache1RemoveFromHash(pPage); - pcache1PinPage(pPage); - pOther = pPage->pCache; - - /* We want to verify that szPage and szExtra are the same for pOther - ** and pCache. Assert that we can verify this by comparing sums. */ - assert( (pCache->szPage & (pCache->szPage-1))==0 && pCache->szPage>=512 ); - assert( pCache->szExtra<512 ); - assert( (pOther->szPage & (pOther->szPage-1))==0 && pOther->szPage>=512 ); - assert( pOther->szExtra<512 ); - - if( pOther->szPage+pOther->szExtra != pCache->szPage+pCache->szExtra ){ - pcache1FreePage(pPage); - pPage = 0; - }else{ - pGroup->nCurrentPage -= (pOther->bPurgeable - pCache->bPurgeable); - } - } - - /* Step 5. If a usable page buffer has still not been found, - ** attempt to allocate a new one. - */ - if( !pPage ){ - if( createFlag==1 ) sqlite3BeginBenignMalloc(); - pPage = pcache1AllocPage(pCache); - if( createFlag==1 ) sqlite3EndBenignMalloc(); - } - - if( pPage ){ - unsigned int h = iKey % pCache->nHash; - pCache->nPage++; - pPage->iKey = iKey; - pPage->pNext = pCache->apHash[h]; - pPage->pCache = pCache; - pPage->pLruPrev = 0; - pPage->pLruNext = 0; - pPage->isPinned = 1; - *(void **)pPage->page.pExtra = 0; - pCache->apHash[h] = pPage; - } - -fetch_out: - if( pPage && iKey>pCache->iMaxKey ){ - pCache->iMaxKey = iKey; - } - pcache1LeaveMutex(pGroup); - return (sqlite3_pcache_page*)pPage; } @@ -39029,22 +42564,16 @@ static void pcache1Unpin( ** part of the PGroup LRU list. */ assert( pPage->pLruPrev==0 && pPage->pLruNext==0 ); - assert( pGroup->pLruHead!=pPage && pGroup->pLruTail!=pPage ); assert( pPage->isPinned==1 ); if( reuseUnlikely || pGroup->nCurrentPage>pGroup->nMaxPage ){ - pcache1RemoveFromHash(pPage); - pcache1FreePage(pPage); + pcache1RemoveFromHash(pPage, 1); }else{ /* Add the page to the PGroup LRU list. */ - if( pGroup->pLruHead ){ - pGroup->pLruHead->pLruPrev = pPage; - pPage->pLruNext = pGroup->pLruHead; - pGroup->pLruHead = pPage; - }else{ - pGroup->pLruTail = pPage; - pGroup->pLruHead = pPage; - } + PgHdr1 **ppFirst = &pGroup->lru.pLruNext; + pPage->pLruPrev = &pGroup->lru; + (pPage->pLruNext = *ppFirst)->pLruPrev = pPage; + *ppFirst = pPage; pCache->nRecyclable++; pPage->isPinned = 0; } @@ -39121,8 +42650,9 @@ static void pcache1Destroy(sqlite3_pcache *p){ assert( pGroup->nMinPage >= pCache->nMin ); pGroup->nMinPage -= pCache->nMin; pGroup->mxPinned = pGroup->nMaxPage + 10 - pGroup->nMinPage; - pcache1EnforceMaxPage(pGroup); + pcache1EnforceMaxPage(pCache); pcache1LeaveMutex(pGroup); + sqlite3_free(pCache->pBulk); sqlite3_free(pCache->apHash); sqlite3_free(pCache); } @@ -39151,6 +42681,19 @@ SQLITE_PRIVATE void sqlite3PCacheSetDefault(void){ sqlite3_config(SQLITE_CONFIG_PCACHE2, &defaultMethods); } +/* +** Return the size of the header on each page of this PCACHE implementation. +*/ +SQLITE_PRIVATE int sqlite3HeaderSizePcache1(void){ return ROUND8(sizeof(PgHdr1)); } + +/* +** Return the global mutex used by this PCACHE implementation. The +** sqlite3_status() routine needs access to this mutex. +*/ +SQLITE_PRIVATE sqlite3_mutex *sqlite3Pcache1Mutex(void){ + return pcache1.mutex; +} + #ifdef SQLITE_ENABLE_MEMORY_MANAGEMENT /* ** This function is called to free superfluous dynamically allocated memory @@ -39165,18 +42708,20 @@ SQLITE_PRIVATE int sqlite3PcacheReleaseMemory(int nReq){ int nFree = 0; assert( sqlite3_mutex_notheld(pcache1.grp.mutex) ); assert( sqlite3_mutex_notheld(pcache1.mutex) ); - if( pcache1.pStart==0 ){ + if( sqlite3GlobalConfig.nPage==0 ){ PgHdr1 *p; pcache1EnterMutex(&pcache1.grp); - while( (nReq<0 || nFreeisAnchor==0 + ){ nFree += pcache1MemSize(p->page.pBuf); #ifdef SQLITE_PCACHE_SEPARATE_HEADER nFree += sqlite3MemSize(p); #endif assert( p->isPinned==0 ); pcache1PinPage(p); - pcache1RemoveFromHash(p); - pcache1FreePage(p); + pcache1RemoveFromHash(p, 1); } pcache1LeaveMutex(&pcache1.grp); } @@ -39197,7 +42742,7 @@ SQLITE_PRIVATE void sqlite3PcacheStats( ){ PgHdr1 *p; int nRecyclable = 0; - for(p=pcache1.grp.pLruHead; p; p=p->pLruNext){ + for(p=pcache1.grp.lru.pLruNext; p && !p->isAnchor; p=p->pLruNext){ assert( p->isPinned==0 ); nRecyclable++; } @@ -39262,7 +42807,7 @@ SQLITE_PRIVATE void sqlite3PcacheStats( ** No INSERTs may occurs after a SMALLEST. An assertion will fail if ** that is attempted. ** -** The cost of an INSERT is roughly constant. (Sometime new memory +** The cost of an INSERT is roughly constant. (Sometimes new memory ** has to be allocated on an INSERT.) The cost of a TEST with a new ** batch number is O(NlogN) where N is the number of elements in the RowSet. ** The cost of a TEST using the same batch number is O(logN). The cost @@ -39272,6 +42817,7 @@ SQLITE_PRIVATE void sqlite3PcacheStats( ** There is an added cost of O(N) when switching between TEST and ** SMALLEST primitives. */ +/* #include "sqliteInt.h" */ /* @@ -39654,8 +43200,8 @@ SQLITE_PRIVATE int sqlite3RowSetNext(RowSet *p, i64 *pRowid){ ** Check to see if element iRowid was inserted into the rowset as ** part of any insert batch prior to iBatch. Return 1 or 0. ** -** If this is the first test of a new batch and if there exist entires -** on pRowSet->pEntry, then sort those entires into the forest at +** If this is the first test of a new batch and if there exist entries +** on pRowSet->pEntry, then sort those entries into the forest at ** pRowSet->pForest so that they can be tested. */ SQLITE_PRIVATE int sqlite3RowSetTest(RowSet *pRowSet, int iBatch, sqlite3_int64 iRowid){ @@ -39741,6 +43287,7 @@ SQLITE_PRIVATE int sqlite3RowSetTest(RowSet *pRowSet, int iBatch, sqlite3_int64 ** another is writing. */ #ifndef SQLITE_OMIT_DISKIO +/* #include "sqliteInt.h" */ /************** Include wal.h in the middle of pager.c ***********************/ /************** Begin file wal.h *********************************************/ /* @@ -39762,6 +43309,7 @@ SQLITE_PRIVATE int sqlite3RowSetTest(RowSet *pRowSet, int iBatch, sqlite3_int64 #ifndef _WAL_H_ #define _WAL_H_ +/* #include "sqliteInt.h" */ /* Additional values that can be added to the sync_flags argument of ** sqlite3WalFrames(): @@ -39788,6 +43336,7 @@ SQLITE_PRIVATE int sqlite3RowSetTest(RowSet *pRowSet, int iBatch, sqlite3_int64 # define sqlite3WalHeapMemory(z) 0 # define sqlite3WalFramesize(z) 0 # define sqlite3WalFindFrame(x,y,z) 0 +# define sqlite3WalFile(x) 0 #else #define WAL_SAVEPOINT_NDATA 4 @@ -39870,6 +43419,11 @@ SQLITE_PRIVATE int sqlite3WalExclusiveMode(Wal *pWal, int op); */ SQLITE_PRIVATE int sqlite3WalHeapMemory(Wal *pWal); +#ifdef SQLITE_ENABLE_SNAPSHOT +SQLITE_PRIVATE int sqlite3WalSnapshotGet(Wal *pWal, sqlite3_snapshot **ppSnapshot); +SQLITE_PRIVATE void sqlite3WalSnapshotOpen(Wal *pWal, sqlite3_snapshot *pSnapshot); +#endif + #ifdef SQLITE_ENABLE_ZIPVFS /* If the WAL file is not empty, return the number of bytes of content ** stored in each frame (i.e. the db page-size when the WAL was created). @@ -39877,6 +43431,9 @@ SQLITE_PRIVATE int sqlite3WalHeapMemory(Wal *pWal); SQLITE_PRIVATE int sqlite3WalFramesize(Wal *pWal); #endif +/* Return the sqlite3_file object for the WAL file */ +SQLITE_PRIVATE sqlite3_file *sqlite3WalFile(Wal *pWal); + #endif /* ifndef SQLITE_OMIT_WAL */ #endif /* _WAL_H_ */ @@ -39937,12 +43494,12 @@ SQLITE_PRIVATE int sqlite3WalFramesize(Wal *pWal); ** Definition: Two databases (or the same database at two points it time) ** are said to be "logically equivalent" if they give the same answer to ** all queries. Note in particular the content of freelist leaf -** pages can be changed arbitarily without effecting the logical equivalence +** pages can be changed arbitrarily without affecting the logical equivalence ** of the database. ** ** (7) At any time, if any subset, including the empty set and the total set, ** of the unsynced changes to a rollback journal are removed and the -** journal is rolled back, the resulting database file will be logical +** journal is rolled back, the resulting database file will be logically ** equivalent to the database file at the beginning of the transaction. ** ** (8) When a transaction is rolled back, the xTruncate method of the VFS @@ -40239,7 +43796,7 @@ int sqlite3PagerTrace=1; /* True to enable tracing */ ** ** The exception is when the database file is unlocked as the pager moves ** from ERROR to OPEN state. At this point there may be a hot-journal file -** in the file-system that needs to be rolled back (as part of a OPEN->SHARED +** in the file-system that needs to be rolled back (as part of an OPEN->SHARED ** transition, by the same pager or any other). If the call to xUnlock() ** fails at this point and the pager is left holding an EXCLUSIVE lock, this ** can confuse the call to xCheckReservedLock() call made later as part @@ -40317,12 +43874,12 @@ struct PagerSavepoint { /* ** Bits of the Pager.doNotSpill flag. See further description below. */ -#define SPILLFLAG_OFF 0x01 /* Never spill cache. Set via pragma */ -#define SPILLFLAG_ROLLBACK 0x02 /* Current rolling back, so do not spill */ -#define SPILLFLAG_NOSYNC 0x04 /* Spill is ok, but do not sync */ +#define SPILLFLAG_OFF 0x01 /* Never spill cache. Set via pragma */ +#define SPILLFLAG_ROLLBACK 0x02 /* Current rolling back, so do not spill */ +#define SPILLFLAG_NOSYNC 0x04 /* Spill is ok, but do not sync */ /* -** A open page cache is an instance of struct Pager. A description of +** An open page cache is an instance of struct Pager. A description of ** some of the more important member variables follows: ** ** eState @@ -40401,11 +43958,11 @@ struct PagerSavepoint { ** while it is being traversed by code in pager_playback(). The SPILLFLAG_OFF ** case is a user preference. ** -** If the SPILLFLAG_NOSYNC bit is set, writing to the database from pagerStress() -** is permitted, but syncing the journal file is not. This flag is set -** by sqlite3PagerWrite() when the file-system sector-size is larger than -** the database page-size in order to prevent a journal sync from happening -** in between the journalling of two pages on the same sector. +** If the SPILLFLAG_NOSYNC bit is set, writing to the database from +** pagerStress() is permitted, but syncing the journal file is not. +** This flag is set by sqlite3PagerWrite() when the file-system sector-size +** is larger than the database page-size in order to prevent a journal sync +** from happening in between the journalling of two pages on the same sector. ** ** subjInMemory ** @@ -40494,7 +44051,7 @@ struct Pager { /************************************************************************** ** The following block contains those class members that change during - ** routine opertion. Class members not in this block are either fixed + ** routine operation. Class members not in this block are either fixed ** when the pager is first created or else only change when there is a ** significant mode change (such as changing the page_size, locking_mode, ** or the journal_mode). From another view, these class members describe @@ -40507,6 +44064,8 @@ struct Pager { u8 setMaster; /* True if a m-j name has been written to jrnl */ u8 doNotSpill; /* Do not spill the cache when non-zero */ u8 subjInMemory; /* True to use in-memory sub-journals */ + u8 bUseFetch; /* True to use xFetch() */ + u8 hasHeldSharedLock; /* True if a shared lock has ever been held */ Pgno dbSize; /* Number of pages in the database */ Pgno dbOrigSize; /* dbSize before the current transaction */ Pgno dbFileSize; /* Number of pages in the database file */ @@ -40524,9 +44083,9 @@ struct Pager { sqlite3_backup *pBackup; /* Pointer to list of ongoing backup processes */ PagerSavepoint *aSavepoint; /* Array of active savepoints */ int nSavepoint; /* Number of elements in aSavepoint[] */ + u32 iDataVersion; /* Changes whenever database content changes */ char dbFileVers[16]; /* Changes whenever database file changes */ - u8 bUseFetch; /* True to use xFetch() */ int nMmapOut; /* Number of mmap pages currently outstanding */ sqlite3_int64 szMmap; /* Desired maximum mmap size */ PgHdr *pMmapFreelist; /* List of free mmap page headers (pDirty) */ @@ -40667,7 +44226,7 @@ static const unsigned char aJournalMagic[] = { ** ** if( pPager->jfd->pMethods ){ ... */ -#define isOpen(pFd) ((pFd)->pMethods) +#define isOpen(pFd) ((pFd)->pMethods!=0) /* ** Return true if this pager uses a write-ahead log instead of the usual @@ -40890,19 +44449,21 @@ static int subjRequiresPage(PgHdr *pPg){ int i; for(i=0; inSavepoint; i++){ p = &pPager->aSavepoint[i]; - if( p->nOrig>=pgno && 0==sqlite3BitvecTest(p->pInSavepoint, pgno) ){ + if( p->nOrig>=pgno && 0==sqlite3BitvecTestNotNull(p->pInSavepoint, pgno) ){ return 1; } } return 0; } +#ifdef SQLITE_DEBUG /* ** Return true if the page is already in the journal file. */ static int pageInJournal(Pager *pPager, PgHdr *pPg){ return sqlite3BitvecTest(pPager->pInJournal, pPg->pgno); } +#endif /* ** Read a 32-bit integer from the given file descriptor. Store the integer @@ -41514,7 +45075,8 @@ static int writeMasterJournal(Pager *pPager, const char *zMaster){ || (0 != (rc = sqlite3OsWrite(pPager->jfd, zMaster, nMaster, iHdrOff+4))) || (0 != (rc = write32bits(pPager->jfd, iHdrOff+4+nMaster, nMaster))) || (0 != (rc = write32bits(pPager->jfd, iHdrOff+4+nMaster+4, cksum))) - || (0 != (rc = sqlite3OsWrite(pPager->jfd, aJournalMagic, 8, iHdrOff+4+nMaster+8))) + || (0 != (rc = sqlite3OsWrite(pPager->jfd, aJournalMagic, 8, + iHdrOff+4+nMaster+8))) ){ return rc; } @@ -41538,29 +45100,23 @@ static int writeMasterJournal(Pager *pPager, const char *zMaster){ return rc; } -/* -** Find a page in the hash table given its page number. Return -** a pointer to the page or NULL if the requested page is not -** already in memory. -*/ -static PgHdr *pager_lookup(Pager *pPager, Pgno pgno){ - PgHdr *p = 0; /* Return value */ - - /* It is not possible for a call to PcacheFetch() with createFlag==0 to - ** fail, since no attempt to allocate dynamic memory will be made. - */ - (void)sqlite3PcacheFetch(pPager->pPCache, pgno, 0, &p); - return p; -} - /* ** Discard the entire contents of the in-memory page-cache. */ static void pager_reset(Pager *pPager){ + pPager->iDataVersion++; sqlite3BackupRestart(pPager->pBackup); sqlite3PcacheClear(pPager->pPCache); } +/* +** Return the pPager->iDataVersion value +*/ +SQLITE_PRIVATE u32 sqlite3PagerDataVersion(Pager *pPager){ + assert( pPager->eState>PAGER_OPEN ); + return pPager->iDataVersion; +} + /* ** Free all structures in the Pager.aSavepoint[] array and set both ** Pager.aSavepoint and Pager.nSavepoint to zero. Close the sub-journal @@ -41817,6 +45373,14 @@ static int pager_end_transaction(Pager *pPager, int hasMaster, int bCommit){ rc = SQLITE_OK; }else{ rc = sqlite3OsTruncate(pPager->jfd, 0); + if( rc==SQLITE_OK && pPager->fullSync ){ + /* Make sure the new file size is written into the inode right away. + ** Otherwise the journal might resurrect following a power loss and + ** cause the last transaction to roll back. See + ** https://bugzilla.mozilla.org/show_bug.cgi?id=1072773 + */ + rc = sqlite3OsSync(pPager->jfd, pPager->syncFlags); + } } pPager->journalOff = 0; }else if( pPager->journalMode==PAGER_JOURNALMODE_PERSIST @@ -41845,7 +45409,7 @@ static int pager_end_transaction(Pager *pPager, int hasMaster, int bCommit){ #ifdef SQLITE_CHECK_PAGES sqlite3PcacheIterateDirty(pPager->pPCache, pager_set_pagehash); if( pPager->dbSize==0 && sqlite3PcacheRefCount(pPager->pPCache)>0 ){ - PgHdr *p = pager_lookup(pPager, 1); + PgHdr *p = sqlite3PagerLookup(pPager, 1); if( p ){ p->pageHash = 0; sqlite3PagerUnrefNotNull(p); @@ -41970,6 +45534,20 @@ static void pagerReportSize(Pager *pPager){ # define pagerReportSize(X) /* No-op if we do not support a codec */ #endif +#ifdef SQLITE_HAS_CODEC +/* +** Make sure the number of reserved bits is the same in the destination +** pager as it is in the source. This comes up when a VACUUM changes the +** number of reserved bits to the "optimal" amount. +*/ +SQLITE_PRIVATE void sqlite3PagerAlignReserve(Pager *pDest, Pager *pSrc){ + if( pDest->nReserve!=pSrc->nReserve ){ + pDest->nReserve = pSrc->nReserve; + pagerReportSize(pDest); + } +} +#endif + /* ** Read a single page from either the journal file (if isMainJrnl==1) or ** from the sub-journal (if isMainJrnl==0) and playback that page. @@ -42072,7 +45650,7 @@ static int pager_playback_one_page( } } - /* If this page has already been played by before during the current + /* If this page has already been played back before during the current ** rollback, then don't bother to play it back again. */ if( pDone && (rc = sqlite3BitvecSet(pDone, pgno))!=SQLITE_OK ){ @@ -42124,7 +45702,7 @@ static int pager_playback_one_page( if( pagerUseWal(pPager) ){ pPg = 0; }else{ - pPg = pager_lookup(pPager, pgno); + pPg = sqlite3PagerLookup(pPager, pgno); } assert( pPg || !MEMDB ); assert( pPager->eState!=PAGER_OPEN || pPg==0 ); @@ -42173,7 +45751,7 @@ static int pager_playback_one_page( assert( isSavepnt ); assert( (pPager->doNotSpill & SPILLFLAG_ROLLBACK)==0 ); pPager->doNotSpill |= SPILLFLAG_ROLLBACK; - rc = sqlite3PagerAcquire(pPager, pgno, &pPg, 1); + rc = sqlite3PagerGet(pPager, pgno, &pPg, 1); assert( (pPager->doNotSpill & SPILLFLAG_ROLLBACK)!=0 ); pPager->doNotSpill &= ~SPILLFLAG_ROLLBACK; if( rc!=SQLITE_OK ) return rc; @@ -42304,7 +45882,7 @@ static int pager_delmaster(Pager *pPager, const char *zMaster){ rc = sqlite3OsFileSize(pMaster, &nMasterJournal); if( rc!=SQLITE_OK ) goto delmaster_out; nMasterPtr = pVfs->mxPathname+1; - zMasterJournal = sqlite3Malloc((int)nMasterJournal + nMasterPtr + 1); + zMasterJournal = sqlite3Malloc(nMasterJournal + nMasterPtr + 1); if( !zMasterJournal ){ rc = SQLITE_NOMEM; goto delmaster_out; @@ -42373,7 +45951,7 @@ delmaster_out: ** If the file on disk is currently larger than nPage pages, then use the VFS ** xTruncate() method to truncate it. ** -** Or, it might might be the case that the file on disk is smaller than +** Or, it might be the case that the file on disk is smaller than ** nPage pages. Some operating system implementations can get confused if ** you try to truncate a file to some size that is larger than it ** currently is, so detect this case and write a single zero byte to @@ -42432,7 +46010,7 @@ SQLITE_PRIVATE int sqlite3SectorSize(sqlite3_file *pFile){ /* ** Set the value of the Pager.sectorSize variable for the given ** pager based on the value returned by the xSectorSize method -** of the open database file. The sector size will be used used +** of the open database file. The sector size will be used ** to determine the size and alignment of journal header and ** master journal pointers within created journal files. ** @@ -42767,7 +46345,7 @@ static int readDbPage(PgHdr *pPg, u32 iFrame){ ** ** For an encrypted database, the situation is more complex: bytes ** 24..39 of the database are white noise. But the probability of - ** white noising equaling 16 bytes of 0xff is vanishingly small so + ** white noise equaling 16 bytes of 0xff is vanishingly small so ** we should still be ok. */ memset(pPager->dbFileVers, 0xff, sizeof(pPager->dbFileVers)); @@ -42901,9 +46479,7 @@ static int pagerWalFrames( ){ int rc; /* Return code */ int nList; /* Number of pages in pList */ -#if defined(SQLITE_DEBUG) || defined(SQLITE_CHECK_PAGES) PgHdr *p; /* For looping over pages */ -#endif assert( pPager->pWal ); assert( pList ); @@ -42920,7 +46496,6 @@ static int pagerWalFrames( ** any pages with page numbers greater than nTruncate into the WAL file. ** They will never be read by any client. So remove them from the pDirty ** list here. */ - PgHdr *p; PgHdr **ppNext = &pList; nList = 0; for(p=pList; (*ppNext = p)!=0; p=p->pDirty){ @@ -42940,7 +46515,6 @@ static int pagerWalFrames( pPager->pageSize, pList, nTruncate, isCommit, pPager->walSyncFlags ); if( rc==SQLITE_OK && pPager->pBackup ){ - PgHdr *p; for(p=pList; p; p=p->pDirty){ sqlite3BackupUpdate(pPager->pBackup, p->pgno, (u8 *)p->pData); } @@ -43010,11 +46584,10 @@ static int pagerPagecount(Pager *pPager, Pgno *pnPage){ assert( pPager->eLock>=SHARED_LOCK ); nPage = sqlite3WalDbsize(pPager->pWal); - /* If the database size was not available from the WAL sub-system, - ** determine it based on the size of the database file. If the size - ** of the database file is not an integer multiple of the page-size, - ** round down to the nearest page. Except, any file larger than 0 - ** bytes in size is considered to contain at least one page. + /* If the number of pages in the database is not available from the + ** WAL sub-system, determine the page counte based on the size of + ** the database file. If the size of the database file is not an + ** integer multiple of the page-size, round up the result. */ if( nPage==0 ){ i64 n = 0; /* Size of db file in bytes */ @@ -43237,12 +46810,21 @@ static int pagerPlaybackSavepoint(Pager *pPager, PagerSavepoint *pSavepoint){ } /* -** Change the maximum number of in-memory pages that are allowed. +** Change the maximum number of in-memory pages that are allowed +** before attempting to recycle clean and unused pages. */ SQLITE_PRIVATE void sqlite3PagerSetCachesize(Pager *pPager, int mxPage){ sqlite3PcacheSetCachesize(pPager->pPCache, mxPage); } +/* +** Change the maximum number of in-memory pages that are allowed +** before attempting to spill pages to journal. +*/ +SQLITE_PRIVATE int sqlite3PagerSetSpillsize(Pager *pPager, int mxPage){ + return sqlite3PcacheSetSpillsize(pPager->pPCache, mxPage); +} + /* ** Invoke SQLITE_FCNTL_MMAP_SIZE based on the current value of szMmap. */ @@ -43494,11 +47076,15 @@ SQLITE_PRIVATE int sqlite3PagerSetPagesize(Pager *pPager, u32 *pPageSize, int nR if( rc==SQLITE_OK ){ pager_reset(pPager); - pPager->dbSize = (Pgno)((nByte+pageSize-1)/pageSize); - pPager->pageSize = pageSize; + rc = sqlite3PcacheSetPageSize(pPager->pPCache, pageSize); + } + if( rc==SQLITE_OK ){ sqlite3PageFree(pPager->pTmpSpace); pPager->pTmpSpace = pNew; - sqlite3PcacheSetPageSize(pPager->pPCache, pageSize); + pPager->dbSize = (Pgno)((nByte+pageSize-1)/pageSize); + pPager->pageSize = pageSize; + }else{ + sqlite3PageFree(pNew); } } @@ -43632,7 +47218,7 @@ static int pager_wait_on_lock(Pager *pPager, int locktype){ int rc; /* Return code */ /* Check that this is either a no-op (because the requested lock is - ** already held, or one of the transistions that the busy-handler + ** already held), or one of the transitions that the busy-handler ** may be invoked during, according to the comment above ** sqlite3PagerSetBusyhandler(). */ @@ -43751,7 +47337,7 @@ static int pagerAcquireMapPage( PgHdr **ppPage /* OUT: Acquired page object */ ){ PgHdr *p; /* Memory mapped page to return */ - + if( pPager->pMmapFreelist ){ *ppPage = p = pPager->pMmapFreelist; pPager->pMmapFreelist = p->pDirty; @@ -44175,8 +47761,6 @@ static int openSubJournal(Pager *pPager){ /* ** Append a record of the current state of page pPg to the sub-journal. -** It is the callers responsibility to use subjRequiresPage() to check -** that it is really required before calling this function. ** ** If successful, set the bit corresponding to pPg->pgno in the bitvecs ** for all open savepoints before returning. @@ -44223,6 +47807,13 @@ static int subjournalPage(PgHdr *pPg){ } return rc; } +static int subjournalPageIfRequired(PgHdr *pPg){ + if( subjRequiresPage(pPg) ){ + return subjournalPage(pPg); + }else{ + return SQLITE_OK; + } +} /* ** This function is called by the pcache layer when it has reached some @@ -44260,8 +47851,8 @@ static int pagerStress(void *p, PgHdr *pPg){ ** a rollback or by user request, respectively. ** ** Spilling is also prohibited when in an error state since that could - ** lead to database corruption. In the current implementaton it - ** is impossible for sqlite3PcacheFetch() to be called with createFlag==1 + ** lead to database corruption. In the current implementation it + ** is impossible for sqlite3PcacheFetch() to be called with createFlag==3 ** while in the error state, hence it is impossible for this routine to ** be called in the error state. Nevertheless, we include a NEVER() ** test for the error state as a safeguard against future changes. @@ -44280,9 +47871,7 @@ static int pagerStress(void *p, PgHdr *pPg){ pPg->pDirty = 0; if( pagerUseWal(pPager) ){ /* Write a single frame for this page to the log. */ - if( subjRequiresPage(pPg) ){ - rc = subjournalPage(pPg); - } + rc = subjournalPageIfRequired(pPg); if( rc==SQLITE_OK ){ rc = pagerWalFrames(pPager, pPg, 0, 0); } @@ -44295,39 +47884,6 @@ static int pagerStress(void *p, PgHdr *pPg){ rc = syncJournal(pPager, 1); } - /* If the page number of this page is larger than the current size of - ** the database image, it may need to be written to the sub-journal. - ** This is because the call to pager_write_pagelist() below will not - ** actually write data to the file in this case. - ** - ** Consider the following sequence of events: - ** - ** BEGIN; - ** - ** - ** SAVEPOINT sp; - ** - ** pagerStress(page X) - ** ROLLBACK TO sp; - ** - ** If (X>Y), then when pagerStress is called page X will not be written - ** out to the database file, but will be dropped from the cache. Then, - ** following the "ROLLBACK TO sp" statement, reading page X will read - ** data from the database file. This will be the copy of page X as it - ** was when the transaction started, not as it was when "SAVEPOINT sp" - ** was executed. - ** - ** The solution is to write the current data for page X into the - ** sub-journal file now (if it is not already there), so that it will - ** be restored to its current value when the "ROLLBACK TO sp" is - ** executed. - */ - if( NEVER( - rc==SQLITE_OK && pPg->pgno>pPager->dbSize && subjRequiresPage(pPg) - ) ){ - rc = subjournalPage(pPg); - } - /* Write the contents of the page out to the database file. */ if( rc==SQLITE_OK ){ assert( (pPg->flags&PGHDR_NEED_SYNC)==0 ); @@ -44344,6 +47900,25 @@ static int pagerStress(void *p, PgHdr *pPg){ return pager_error(pPager, rc); } +/* +** Flush all unreferenced dirty pages to disk. +*/ +SQLITE_PRIVATE int sqlite3PagerFlush(Pager *pPager){ + int rc = pPager->errCode; + if( !MEMDB ){ + PgHdr *pList = sqlite3PcacheDirtyList(pPager->pPCache); + assert( assert_pager_state(pPager) ); + while( rc==SQLITE_OK && pList ){ + PgHdr *pNext = pList->pDirty; + if( pList->nRef==0 ){ + rc = pagerStress((void*)pPager, pList); + } + pList = pNext; + } + } + + return rc; +} /* ** Allocate and initialize a new Pager object and put a pointer to it @@ -44583,7 +48158,7 @@ SQLITE_PRIVATE int sqlite3PagerOpen( act_like_temp_file: tempFile = 1; pPager->eState = PAGER_READER; /* Pretend we already have a lock */ - pPager->eLock = EXCLUSIVE_LOCK; /* Pretend we are in EXCLUSIVE locking mode */ + pPager->eLock = EXCLUSIVE_LOCK; /* Pretend we are in EXCLUSIVE mode */ pPager->noLock = 1; /* Do no locking */ readOnly = (vfsFlags&SQLITE_OPEN_READONLY); } @@ -44597,22 +48172,23 @@ act_like_temp_file: testcase( rc!=SQLITE_OK ); } - /* If an error occurred in either of the blocks above, free the - ** Pager structure and close the file. + /* Initialize the PCache object. */ + if( rc==SQLITE_OK ){ + assert( nExtra<1000 ); + nExtra = ROUND8(nExtra); + rc = sqlite3PcacheOpen(szPageDflt, nExtra, !memDb, + !memDb?pagerStress:0, (void *)pPager, pPager->pPCache); + } + + /* If an error occurred above, free the Pager structure and close the file. */ if( rc!=SQLITE_OK ){ - assert( !pPager->pTmpSpace ); sqlite3OsClose(pPager->fd); + sqlite3PageFree(pPager->pTmpSpace); sqlite3_free(pPager); return rc; } - /* Initialize the PCache object. */ - assert( nExtra<1000 ); - nExtra = ROUND8(nExtra); - sqlite3PcacheOpen(szPageDflt, nExtra, !memDb, - !memDb?pagerStress:0, (void *)pPager, pPager->pPCache); - PAGERTRACE(("OPEN %d %s\n", FILEHANDLEID(pPager->fd), pPager->zFilename)); IOTRACE(("OPEN %p %s\n", pPager, pPager->zFilename)) @@ -44799,7 +48375,7 @@ static int hasHotJournal(Pager *pPager, int *pExists){ *pExists = (first!=0); }else if( rc==SQLITE_CANTOPEN ){ /* If we cannot open the rollback journal file in order to see if - ** its has a zero header, that might be due to an I/O error, or + ** it has a zero header, that might be due to an I/O error, or ** it might be due to the race condition described above and in ** ticket #3883. Either way, assume that the journal is hot. ** This might be a false positive. But if it is, then the @@ -44820,7 +48396,7 @@ static int hasHotJournal(Pager *pPager, int *pExists){ /* ** This function is called to obtain a shared lock on the database file. -** It is illegal to call sqlite3PagerAcquire() until after this function +** It is illegal to call sqlite3PagerGet() until after this function ** has been successfully called. If a shared-lock is already held when ** this function is called, it is a no-op. ** @@ -44981,18 +48557,14 @@ SQLITE_PRIVATE int sqlite3PagerSharedLock(Pager *pPager){ ); } - if( !pPager->tempFile && ( - pPager->pBackup - || sqlite3PcachePagecount(pPager->pPCache)>0 - || USEFETCH(pPager) - )){ - /* The shared-lock has just been acquired on the database file - ** and there are already pages in the cache (from a previous - ** read or write transaction). Check to see if the database - ** has been modified. If the database has changed, flush the - ** cache. + if( !pPager->tempFile && pPager->hasHeldSharedLock ){ + /* The shared-lock has just been acquired then check to + ** see if the database has been modified. If the database has changed, + ** flush the cache. The hasHeldSharedLock flag prevents this from + ** occurring on the very first access to a file, in order to save a + ** single unnecessary sqlite3OsRead() call at the start-up. ** - ** Database changes is detected by looking at 15 bytes beginning + ** Database changes are detected by looking at 15 bytes beginning ** at offset 24 into the file. The first 4 of these 16 bytes are ** a 32-bit counter that is incremented with each change. The ** other bytes change randomly with each file change when @@ -45058,6 +48630,7 @@ SQLITE_PRIVATE int sqlite3PagerSharedLock(Pager *pPager){ assert( pPager->eState==PAGER_OPEN ); }else{ pPager->eState = PAGER_READER; + pPager->hasHeldSharedLock = 1; } return rc; } @@ -45126,7 +48699,7 @@ static void pagerUnlockIfUnused(Pager *pPager){ ** Since Lookup() never goes to disk, it never has to deal with locks ** or journal files. */ -SQLITE_PRIVATE int sqlite3PagerAcquire( +SQLITE_PRIVATE int sqlite3PagerGet( Pager *pPager, /* The pager open on the database file */ Pgno pgno, /* Page number to fetch */ DbPage **ppPage, /* Write a pointer to the page here */ @@ -45141,27 +48714,31 @@ SQLITE_PRIVATE int sqlite3PagerAcquire( ** page 1 if there is no write-transaction open or the ACQUIRE_READONLY ** flag was specified by the caller. And so long as the db is not a ** temporary or in-memory database. */ - const int bMmapOk = (pgno!=1 && USEFETCH(pPager) + const int bMmapOk = (pgno>1 && USEFETCH(pPager) && (pPager->eState==PAGER_READER || (flags & PAGER_GET_READONLY)) #ifdef SQLITE_HAS_CODEC && pPager->xCodec==0 #endif ); + /* Optimization note: Adding the "pgno<=1" term before "pgno==0" here + ** allows the compiler optimizer to reuse the results of the "pgno>1" + ** test in the previous statement, and avoid testing pgno==0 in the + ** common case where pgno is large. */ + if( pgno<=1 && pgno==0 ){ + return SQLITE_CORRUPT_BKPT; + } assert( pPager->eState>=PAGER_READER ); assert( assert_pager_state(pPager) ); assert( noContent==0 || bMmapOk==0 ); - if( pgno==0 ){ - return SQLITE_CORRUPT_BKPT; - } + assert( pPager->hasHeldSharedLock==1 ); /* If the pager is in the error state, return an error immediately. ** Otherwise, request the page from the PCache layer. */ if( pPager->errCode!=SQLITE_OK ){ rc = pPager->errCode; }else{ - if( bMmapOk && pagerUseWal(pPager) ){ rc = sqlite3WalFindFrame(pPager->pWal, pgno, &iFrame); if( rc!=SQLITE_OK ) goto pager_acquire_err; @@ -45176,7 +48753,7 @@ SQLITE_PRIVATE int sqlite3PagerAcquire( if( rc==SQLITE_OK && pData ){ if( pPager->eState>PAGER_READER ){ - (void)sqlite3PcacheFetch(pPager->pPCache, pgno, 0, &pPg); + pPg = sqlite3PagerLookup(pPager, pgno); } if( pPg==0 ){ rc = pagerAcquireMapPage(pPager, pgno, pData, &pPg); @@ -45194,7 +48771,21 @@ SQLITE_PRIVATE int sqlite3PagerAcquire( } } - rc = sqlite3PcacheFetch(pPager->pPCache, pgno, 1, ppPage); + { + sqlite3_pcache_page *pBase; + pBase = sqlite3PcacheFetch(pPager->pPCache, pgno, 3); + if( pBase==0 ){ + rc = sqlite3PcacheFetchStress(pPager->pPCache, pgno, &pBase); + if( rc!=SQLITE_OK ) goto pager_acquire_err; + if( pBase==0 ){ + pPg = *ppPage = 0; + rc = SQLITE_NOMEM; + goto pager_acquire_err; + } + } + pPg = *ppPage = sqlite3PcacheFetchFinish(pPager->pPCache, pgno, pBase); + assert( pPg!=0 ); + } } if( rc!=SQLITE_OK ){ @@ -45204,10 +48795,11 @@ SQLITE_PRIVATE int sqlite3PagerAcquire( pPg = 0; goto pager_acquire_err; } - assert( (*ppPage)->pgno==pgno ); - assert( (*ppPage)->pPager==pPager || (*ppPage)->pPager==0 ); + assert( pPg==(*ppPage) ); + assert( pPg->pgno==pgno ); + assert( pPg->pPager==pPager || pPg->pPager==0 ); - if( (*ppPage)->pPager && !noContent ){ + if( pPg->pPager && !noContent ){ /* In this case the pcache already contains an initialized copy of ** the page. Return without further ado. */ assert( pgno<=PAGER_MAX_PGNO && pgno!=PAGER_MJ_PGNO(pPager) ); @@ -45218,7 +48810,6 @@ SQLITE_PRIVATE int sqlite3PagerAcquire( /* The pager cache has created a new page. Its content needs to ** be initialized. */ - pPg = *ppPage; pPg->pPager = pPager; /* The maximum page number is 2^31. Return SQLITE_CORRUPT if a page @@ -45291,13 +48882,14 @@ pager_acquire_err: ** has ever happened. */ SQLITE_PRIVATE DbPage *sqlite3PagerLookup(Pager *pPager, Pgno pgno){ - PgHdr *pPg = 0; + sqlite3_pcache_page *pPage; assert( pPager!=0 ); assert( pgno!=0 ); assert( pPager->pPCache!=0 ); - assert( pPager->eState>=PAGER_READER && pPager->eState!=PAGER_ERROR ); - sqlite3PcacheFetch(pPager->pPCache, pgno, 0, &pPg); - return pPg; + pPage = sqlite3PcacheFetch(pPager->pPCache, pgno, 0); + assert( pPage==0 || pPager->hasHeldSharedLock ); + if( pPage==0 ) return 0; + return sqlite3PcacheFetchFinish(pPager->pPCache, pgno, pPage); } /* @@ -45453,7 +49045,7 @@ SQLITE_PRIVATE int sqlite3PagerBegin(Pager *pPager, int exFlag, int subjInMemory if( rc!=SQLITE_OK ){ return rc; } - sqlite3WalExclusiveMode(pPager->pWal, 1); + (void)sqlite3WalExclusiveMode(pPager->pWal, 1); } /* Grab the write lock on the log file. If successful, upgrade to @@ -45500,6 +49092,59 @@ SQLITE_PRIVATE int sqlite3PagerBegin(Pager *pPager, int exFlag, int subjInMemory return rc; } +/* +** Write page pPg onto the end of the rollback journal. +*/ +static SQLITE_NOINLINE int pagerAddPageToRollbackJournal(PgHdr *pPg){ + Pager *pPager = pPg->pPager; + int rc; + u32 cksum; + char *pData2; + i64 iOff = pPager->journalOff; + + /* We should never write to the journal file the page that + ** contains the database locks. The following assert verifies + ** that we do not. */ + assert( pPg->pgno!=PAGER_MJ_PGNO(pPager) ); + + assert( pPager->journalHdr<=pPager->journalOff ); + CODEC2(pPager, pPg->pData, pPg->pgno, 7, return SQLITE_NOMEM, pData2); + cksum = pager_cksum(pPager, (u8*)pData2); + + /* Even if an IO or diskfull error occurs while journalling the + ** page in the block above, set the need-sync flag for the page. + ** Otherwise, when the transaction is rolled back, the logic in + ** playback_one_page() will think that the page needs to be restored + ** in the database file. And if an IO error occurs while doing so, + ** then corruption may follow. + */ + pPg->flags |= PGHDR_NEED_SYNC; + + rc = write32bits(pPager->jfd, iOff, pPg->pgno); + if( rc!=SQLITE_OK ) return rc; + rc = sqlite3OsWrite(pPager->jfd, pData2, pPager->pageSize, iOff+4); + if( rc!=SQLITE_OK ) return rc; + rc = write32bits(pPager->jfd, iOff+pPager->pageSize+4, cksum); + if( rc!=SQLITE_OK ) return rc; + + IOTRACE(("JOUT %p %d %lld %d\n", pPager, pPg->pgno, + pPager->journalOff, pPager->pageSize)); + PAGER_INCR(sqlite3_pager_writej_count); + PAGERTRACE(("JOURNAL %d page %d needSync=%d hash(%08x)\n", + PAGERID(pPager), pPg->pgno, + ((pPg->flags&PGHDR_NEED_SYNC)?1:0), pager_pagehash(pPg))); + + pPager->journalOff += 8 + pPager->pageSize; + pPager->nRec++; + assert( pPager->pInJournal!=0 ); + rc = sqlite3BitvecSet(pPager->pInJournal, pPg->pgno); + testcase( rc==SQLITE_NOMEM ); + assert( rc==SQLITE_OK || rc==SQLITE_NOMEM ); + rc |= addToSavepointBitvecs(pPager, pPg->pgno); + assert( rc==SQLITE_OK || rc==SQLITE_NOMEM ); + return rc; +} + /* ** Mark a single data page as writeable. The page is written into the ** main journal or sub-journal as required. If the page is written into @@ -45510,7 +49155,6 @@ SQLITE_PRIVATE int sqlite3PagerBegin(Pager *pPager, int exFlag, int subjInMemory static int pager_write(PgHdr *pPg){ Pager *pPager = pPg->pPager; int rc = SQLITE_OK; - int inJournal; /* This routine is not called unless a write-transaction has already ** been started. The journal file may or may not be open at this point. @@ -45523,7 +49167,6 @@ static int pager_write(PgHdr *pPg){ assert( assert_pager_state(pPager) ); assert( pPager->errCode==0 ); assert( pPager->readOnly==0 ); - CHECK_PAGE(pPg); /* The journal file needs to be opened. Higher level routines have already @@ -45542,97 +49185,145 @@ static int pager_write(PgHdr *pPg){ assert( pPager->eState>=PAGER_WRITER_CACHEMOD ); assert( assert_pager_state(pPager) ); - /* Mark the page as dirty. If the page has already been written - ** to the journal then we can return right away. - */ + /* Mark the page that is about to be modified as dirty. */ sqlite3PcacheMakeDirty(pPg); - inJournal = pageInJournal(pPager, pPg); - if( inJournal && (pPager->nSavepoint==0 || !subjRequiresPage(pPg)) ){ - assert( !pagerUseWal(pPager) ); - }else{ - - /* The transaction journal now exists and we have a RESERVED or an - ** EXCLUSIVE lock on the main database file. Write the current page to - ** the transaction journal if it is not there already. - */ - if( !inJournal && !pagerUseWal(pPager) ){ - assert( pagerUseWal(pPager)==0 ); - if( pPg->pgno<=pPager->dbOrigSize && isOpen(pPager->jfd) ){ - u32 cksum; - char *pData2; - i64 iOff = pPager->journalOff; - /* We should never write to the journal file the page that - ** contains the database locks. The following assert verifies - ** that we do not. */ - assert( pPg->pgno!=PAGER_MJ_PGNO(pPager) ); - - assert( pPager->journalHdr<=pPager->journalOff ); - CODEC2(pPager, pPg->pData, pPg->pgno, 7, return SQLITE_NOMEM, pData2); - cksum = pager_cksum(pPager, (u8*)pData2); - - /* Even if an IO or diskfull error occurs while journalling the - ** page in the block above, set the need-sync flag for the page. - ** Otherwise, when the transaction is rolled back, the logic in - ** playback_one_page() will think that the page needs to be restored - ** in the database file. And if an IO error occurs while doing so, - ** then corruption may follow. - */ - pPg->flags |= PGHDR_NEED_SYNC; - - rc = write32bits(pPager->jfd, iOff, pPg->pgno); - if( rc!=SQLITE_OK ) return rc; - rc = sqlite3OsWrite(pPager->jfd, pData2, pPager->pageSize, iOff+4); - if( rc!=SQLITE_OK ) return rc; - rc = write32bits(pPager->jfd, iOff+pPager->pageSize+4, cksum); - if( rc!=SQLITE_OK ) return rc; - - IOTRACE(("JOUT %p %d %lld %d\n", pPager, pPg->pgno, - pPager->journalOff, pPager->pageSize)); - PAGER_INCR(sqlite3_pager_writej_count); - PAGERTRACE(("JOURNAL %d page %d needSync=%d hash(%08x)\n", - PAGERID(pPager), pPg->pgno, - ((pPg->flags&PGHDR_NEED_SYNC)?1:0), pager_pagehash(pPg))); - - pPager->journalOff += 8 + pPager->pageSize; - pPager->nRec++; - assert( pPager->pInJournal!=0 ); - rc = sqlite3BitvecSet(pPager->pInJournal, pPg->pgno); - testcase( rc==SQLITE_NOMEM ); - assert( rc==SQLITE_OK || rc==SQLITE_NOMEM ); - rc |= addToSavepointBitvecs(pPager, pPg->pgno); - if( rc!=SQLITE_OK ){ - assert( rc==SQLITE_NOMEM ); - return rc; - } - }else{ - if( pPager->eState!=PAGER_WRITER_DBMOD ){ - pPg->flags |= PGHDR_NEED_SYNC; - } - PAGERTRACE(("APPEND %d page %d needSync=%d\n", - PAGERID(pPager), pPg->pgno, - ((pPg->flags&PGHDR_NEED_SYNC)?1:0))); + /* If a rollback journal is in use, them make sure the page that is about + ** to change is in the rollback journal, or if the page is a new page off + ** then end of the file, make sure it is marked as PGHDR_NEED_SYNC. + */ + assert( (pPager->pInJournal!=0) == isOpen(pPager->jfd) ); + if( pPager->pInJournal!=0 + && sqlite3BitvecTestNotNull(pPager->pInJournal, pPg->pgno)==0 + ){ + assert( pagerUseWal(pPager)==0 ); + if( pPg->pgno<=pPager->dbOrigSize ){ + rc = pagerAddPageToRollbackJournal(pPg); + if( rc!=SQLITE_OK ){ + return rc; } - } - - /* If the statement journal is open and the page is not in it, - ** then write the current page to the statement journal. Note that - ** the statement journal format differs from the standard journal format - ** in that it omits the checksums and the header. - */ - if( pPager->nSavepoint>0 && subjRequiresPage(pPg) ){ - rc = subjournalPage(pPg); + }else{ + if( pPager->eState!=PAGER_WRITER_DBMOD ){ + pPg->flags |= PGHDR_NEED_SYNC; + } + PAGERTRACE(("APPEND %d page %d needSync=%d\n", + PAGERID(pPager), pPg->pgno, + ((pPg->flags&PGHDR_NEED_SYNC)?1:0))); } } - /* Update the database size and return. + /* The PGHDR_DIRTY bit is set above when the page was added to the dirty-list + ** and before writing the page into the rollback journal. Wait until now, + ** after the page has been successfully journalled, before setting the + ** PGHDR_WRITEABLE bit that indicates that the page can be safely modified. */ + pPg->flags |= PGHDR_WRITEABLE; + + /* If the statement journal is open and the page is not in it, + ** then write the page into the statement journal. + */ + if( pPager->nSavepoint>0 ){ + rc = subjournalPageIfRequired(pPg); + } + + /* Update the database size and return. */ if( pPager->dbSizepgno ){ pPager->dbSize = pPg->pgno; } return rc; } +/* +** This is a variant of sqlite3PagerWrite() that runs when the sector size +** is larger than the page size. SQLite makes the (reasonable) assumption that +** all bytes of a sector are written together by hardware. Hence, all bytes of +** a sector need to be journalled in case of a power loss in the middle of +** a write. +** +** Usually, the sector size is less than or equal to the page size, in which +** case pages can be individually written. This routine only runs in the +** exceptional case where the page size is smaller than the sector size. +*/ +static SQLITE_NOINLINE int pagerWriteLargeSector(PgHdr *pPg){ + int rc = SQLITE_OK; /* Return code */ + Pgno nPageCount; /* Total number of pages in database file */ + Pgno pg1; /* First page of the sector pPg is located on. */ + int nPage = 0; /* Number of pages starting at pg1 to journal */ + int ii; /* Loop counter */ + int needSync = 0; /* True if any page has PGHDR_NEED_SYNC */ + Pager *pPager = pPg->pPager; /* The pager that owns pPg */ + Pgno nPagePerSector = (pPager->sectorSize/pPager->pageSize); + + /* Set the doNotSpill NOSYNC bit to 1. This is because we cannot allow + ** a journal header to be written between the pages journaled by + ** this function. + */ + assert( !MEMDB ); + assert( (pPager->doNotSpill & SPILLFLAG_NOSYNC)==0 ); + pPager->doNotSpill |= SPILLFLAG_NOSYNC; + + /* This trick assumes that both the page-size and sector-size are + ** an integer power of 2. It sets variable pg1 to the identifier + ** of the first page of the sector pPg is located on. + */ + pg1 = ((pPg->pgno-1) & ~(nPagePerSector-1)) + 1; + + nPageCount = pPager->dbSize; + if( pPg->pgno>nPageCount ){ + nPage = (pPg->pgno - pg1)+1; + }else if( (pg1+nPagePerSector-1)>nPageCount ){ + nPage = nPageCount+1-pg1; + }else{ + nPage = nPagePerSector; + } + assert(nPage>0); + assert(pg1<=pPg->pgno); + assert((pg1+nPage)>pPg->pgno); + + for(ii=0; iipgno || !sqlite3BitvecTest(pPager->pInJournal, pg) ){ + if( pg!=PAGER_MJ_PGNO(pPager) ){ + rc = sqlite3PagerGet(pPager, pg, &pPage, 0); + if( rc==SQLITE_OK ){ + rc = pager_write(pPage); + if( pPage->flags&PGHDR_NEED_SYNC ){ + needSync = 1; + } + sqlite3PagerUnrefNotNull(pPage); + } + } + }else if( (pPage = sqlite3PagerLookup(pPager, pg))!=0 ){ + if( pPage->flags&PGHDR_NEED_SYNC ){ + needSync = 1; + } + sqlite3PagerUnrefNotNull(pPage); + } + } + + /* If the PGHDR_NEED_SYNC flag is set for any of the nPage pages + ** starting at pg1, then it needs to be set for all of them. Because + ** writing to any of these nPage pages may damage the others, the + ** journal file must contain sync()ed copies of all of them + ** before any of them can be written out to the database file. + */ + if( rc==SQLITE_OK && needSync ){ + assert( !MEMDB ); + for(ii=0; iiflags |= PGHDR_NEED_SYNC; + sqlite3PagerUnrefNotNull(pPage); + } + } + } + + assert( (pPager->doNotSpill & SPILLFLAG_NOSYNC)!=0 ); + pPager->doNotSpill &= ~SPILLFLAG_NOSYNC; + return rc; +} + /* ** Mark a data page as writeable. This routine must be called before ** making changes to a page. The caller must check the return value @@ -45647,96 +49338,21 @@ static int pager_write(PgHdr *pPg){ ** If an error occurs, SQLITE_NOMEM or an IO error code is returned ** as appropriate. Otherwise, SQLITE_OK. */ -SQLITE_PRIVATE int sqlite3PagerWrite(DbPage *pDbPage){ - int rc = SQLITE_OK; - - PgHdr *pPg = pDbPage; +SQLITE_PRIVATE int sqlite3PagerWrite(PgHdr *pPg){ Pager *pPager = pPg->pPager; - assert( (pPg->flags & PGHDR_MMAP)==0 ); assert( pPager->eState>=PAGER_WRITER_LOCKED ); - assert( pPager->eState!=PAGER_ERROR ); assert( assert_pager_state(pPager) ); - - if( pPager->sectorSize > (u32)pPager->pageSize ){ - Pgno nPageCount; /* Total number of pages in database file */ - Pgno pg1; /* First page of the sector pPg is located on. */ - int nPage = 0; /* Number of pages starting at pg1 to journal */ - int ii; /* Loop counter */ - int needSync = 0; /* True if any page has PGHDR_NEED_SYNC */ - Pgno nPagePerSector = (pPager->sectorSize/pPager->pageSize); - - /* Set the doNotSpill NOSYNC bit to 1. This is because we cannot allow - ** a journal header to be written between the pages journaled by - ** this function. - */ - assert( !MEMDB ); - assert( (pPager->doNotSpill & SPILLFLAG_NOSYNC)==0 ); - pPager->doNotSpill |= SPILLFLAG_NOSYNC; - - /* This trick assumes that both the page-size and sector-size are - ** an integer power of 2. It sets variable pg1 to the identifier - ** of the first page of the sector pPg is located on. - */ - pg1 = ((pPg->pgno-1) & ~(nPagePerSector-1)) + 1; - - nPageCount = pPager->dbSize; - if( pPg->pgno>nPageCount ){ - nPage = (pPg->pgno - pg1)+1; - }else if( (pg1+nPagePerSector-1)>nPageCount ){ - nPage = nPageCount+1-pg1; - }else{ - nPage = nPagePerSector; - } - assert(nPage>0); - assert(pg1<=pPg->pgno); - assert((pg1+nPage)>pPg->pgno); - - for(ii=0; iipgno || !sqlite3BitvecTest(pPager->pInJournal, pg) ){ - if( pg!=PAGER_MJ_PGNO(pPager) ){ - rc = sqlite3PagerGet(pPager, pg, &pPage); - if( rc==SQLITE_OK ){ - rc = pager_write(pPage); - if( pPage->flags&PGHDR_NEED_SYNC ){ - needSync = 1; - } - sqlite3PagerUnrefNotNull(pPage); - } - } - }else if( (pPage = pager_lookup(pPager, pg))!=0 ){ - if( pPage->flags&PGHDR_NEED_SYNC ){ - needSync = 1; - } - sqlite3PagerUnrefNotNull(pPage); - } - } - - /* If the PGHDR_NEED_SYNC flag is set for any of the nPage pages - ** starting at pg1, then it needs to be set for all of them. Because - ** writing to any of these nPage pages may damage the others, the - ** journal file must contain sync()ed copies of all of them - ** before any of them can be written out to the database file. - */ - if( rc==SQLITE_OK && needSync ){ - assert( !MEMDB ); - for(ii=0; iiflags |= PGHDR_NEED_SYNC; - sqlite3PagerUnrefNotNull(pPage); - } - } - } - - assert( (pPager->doNotSpill & SPILLFLAG_NOSYNC)!=0 ); - pPager->doNotSpill &= ~SPILLFLAG_NOSYNC; + if( pPager->errCode ){ + return pPager->errCode; + }else if( (pPg->flags & PGHDR_WRITEABLE)!=0 && pPager->dbSize>=pPg->pgno ){ + if( pPager->nSavepoint ) return subjournalPageIfRequired(pPg); + return SQLITE_OK; + }else if( pPager->sectorSize > (u32)pPager->pageSize ){ + return pagerWriteLargeSector(pPg); }else{ - rc = pager_write(pDbPage); + return pager_write(pPg); } - return rc; } /* @@ -45746,7 +49362,7 @@ SQLITE_PRIVATE int sqlite3PagerWrite(DbPage *pDbPage){ */ #ifndef NDEBUG SQLITE_PRIVATE int sqlite3PagerIswriteable(DbPage *pPg){ - return pPg->flags&PGHDR_DIRTY; + return pPg->flags & PGHDR_WRITEABLE; } #endif @@ -45770,6 +49386,7 @@ SQLITE_PRIVATE void sqlite3PagerDontWrite(PgHdr *pPg){ PAGERTRACE(("DONT_WRITE page %d of %d\n", pPg->pgno, PAGERID(pPager))); IOTRACE(("CLEAN %p %d\n", pPager, pPg->pgno)) pPg->flags |= PGHDR_DONT_WRITE; + pPg->flags &= ~PGHDR_WRITEABLE; pager_set_pagehash(pPg); } } @@ -45828,7 +49445,7 @@ static int pager_incr_changecounter(Pager *pPager, int isDirectMode){ assert( !pPager->tempFile && isOpen(pPager->fd) ); /* Open page 1 of the file for writing. */ - rc = sqlite3PagerGet(pPager, 1, &pPgHdr); + rc = sqlite3PagerGet(pPager, 1, &pPgHdr, 0); assert( pPgHdr==0 || rc==SQLITE_OK ); /* If page one was fetched successfully, and this function is not @@ -45906,14 +49523,17 @@ SQLITE_PRIVATE int sqlite3PagerSync(Pager *pPager, const char *zMaster){ ** returned. */ SQLITE_PRIVATE int sqlite3PagerExclusiveLock(Pager *pPager){ - int rc = SQLITE_OK; - assert( pPager->eState==PAGER_WRITER_CACHEMOD - || pPager->eState==PAGER_WRITER_DBMOD - || pPager->eState==PAGER_WRITER_LOCKED - ); + int rc = pPager->errCode; assert( assert_pager_state(pPager) ); - if( 0==pagerUseWal(pPager) ){ - rc = pager_wait_on_lock(pPager, EXCLUSIVE_LOCK); + if( rc==SQLITE_OK ){ + assert( pPager->eState==PAGER_WRITER_CACHEMOD + || pPager->eState==PAGER_WRITER_DBMOD + || pPager->eState==PAGER_WRITER_LOCKED + ); + assert( assert_pager_state(pPager) ); + if( 0==pagerUseWal(pPager) ){ + rc = pager_wait_on_lock(pPager, EXCLUSIVE_LOCK); + } } return rc; } @@ -45980,7 +49600,7 @@ SQLITE_PRIVATE int sqlite3PagerCommitPhaseOne( if( pList==0 ){ /* Must have at least one page for the WAL commit flag. ** Ticket [2d1a5c67dfc2363e44f29d9bbd57f] 2011-05-18 */ - rc = sqlite3PagerGet(pPager, 1, &pPageOne); + rc = sqlite3PagerGet(pPager, 1, &pPageOne, 0); pList = pPageOne; pList->pDirty = 0; } @@ -46152,6 +49772,7 @@ SQLITE_PRIVATE int sqlite3PagerCommitPhaseTwo(Pager *pPager){ } PAGERTRACE(("COMMIT %d\n", PAGERID(pPager))); + pPager->iDataVersion++; rc = pager_end_transaction(pPager, pPager->setMaster, 1); return pager_error(pPager, rc); } @@ -46235,12 +49856,14 @@ SQLITE_PRIVATE u8 sqlite3PagerIsreadonly(Pager *pPager){ return pPager->readOnly; } +#ifdef SQLITE_DEBUG /* -** Return the number of references to the pager. +** Return the sum of the reference counts for all pages held by pPager. */ SQLITE_PRIVATE int sqlite3PagerRefcount(Pager *pPager){ return sqlite3PcacheRefCount(pPager->pPCache); } +#endif /* ** Return the approximate number of bytes of memory currently @@ -46323,54 +49946,62 @@ SQLITE_PRIVATE int sqlite3PagerIsMemdb(Pager *pPager){ ** occurs while opening the sub-journal file, then an IO error code is ** returned. Otherwise, SQLITE_OK. */ -SQLITE_PRIVATE int sqlite3PagerOpenSavepoint(Pager *pPager, int nSavepoint){ +static SQLITE_NOINLINE int pagerOpenSavepoint(Pager *pPager, int nSavepoint){ int rc = SQLITE_OK; /* Return code */ int nCurrent = pPager->nSavepoint; /* Current number of savepoints */ + int ii; /* Iterator variable */ + PagerSavepoint *aNew; /* New Pager.aSavepoint array */ assert( pPager->eState>=PAGER_WRITER_LOCKED ); assert( assert_pager_state(pPager) ); + assert( nSavepoint>nCurrent && pPager->useJournal ); - if( nSavepoint>nCurrent && pPager->useJournal ){ - int ii; /* Iterator variable */ - PagerSavepoint *aNew; /* New Pager.aSavepoint array */ + /* Grow the Pager.aSavepoint array using realloc(). Return SQLITE_NOMEM + ** if the allocation fails. Otherwise, zero the new portion in case a + ** malloc failure occurs while populating it in the for(...) loop below. + */ + aNew = (PagerSavepoint *)sqlite3Realloc( + pPager->aSavepoint, sizeof(PagerSavepoint)*nSavepoint + ); + if( !aNew ){ + return SQLITE_NOMEM; + } + memset(&aNew[nCurrent], 0, (nSavepoint-nCurrent) * sizeof(PagerSavepoint)); + pPager->aSavepoint = aNew; - /* Grow the Pager.aSavepoint array using realloc(). Return SQLITE_NOMEM - ** if the allocation fails. Otherwise, zero the new portion in case a - ** malloc failure occurs while populating it in the for(...) loop below. - */ - aNew = (PagerSavepoint *)sqlite3Realloc( - pPager->aSavepoint, sizeof(PagerSavepoint)*nSavepoint - ); - if( !aNew ){ + /* Populate the PagerSavepoint structures just allocated. */ + for(ii=nCurrent; iidbSize; + if( isOpen(pPager->jfd) && pPager->journalOff>0 ){ + aNew[ii].iOffset = pPager->journalOff; + }else{ + aNew[ii].iOffset = JOURNAL_HDR_SZ(pPager); + } + aNew[ii].iSubRec = pPager->nSubRec; + aNew[ii].pInSavepoint = sqlite3BitvecCreate(pPager->dbSize); + if( !aNew[ii].pInSavepoint ){ return SQLITE_NOMEM; } - memset(&aNew[nCurrent], 0, (nSavepoint-nCurrent) * sizeof(PagerSavepoint)); - pPager->aSavepoint = aNew; - - /* Populate the PagerSavepoint structures just allocated. */ - for(ii=nCurrent; iidbSize; - if( isOpen(pPager->jfd) && pPager->journalOff>0 ){ - aNew[ii].iOffset = pPager->journalOff; - }else{ - aNew[ii].iOffset = JOURNAL_HDR_SZ(pPager); - } - aNew[ii].iSubRec = pPager->nSubRec; - aNew[ii].pInSavepoint = sqlite3BitvecCreate(pPager->dbSize); - if( !aNew[ii].pInSavepoint ){ - return SQLITE_NOMEM; - } - if( pagerUseWal(pPager) ){ - sqlite3WalSavepoint(pPager->pWal, aNew[ii].aWalData); - } - pPager->nSavepoint = ii+1; + if( pagerUseWal(pPager) ){ + sqlite3WalSavepoint(pPager->pWal, aNew[ii].aWalData); } - assert( pPager->nSavepoint==nSavepoint ); - assertTruncateConstraint(pPager); + pPager->nSavepoint = ii+1; } - + assert( pPager->nSavepoint==nSavepoint ); + assertTruncateConstraint(pPager); return rc; } +SQLITE_PRIVATE int sqlite3PagerOpenSavepoint(Pager *pPager, int nSavepoint){ + assert( pPager->eState>=PAGER_WRITER_LOCKED ); + assert( assert_pager_state(pPager) ); + + if( nSavepoint>pPager->nSavepoint && pPager->useJournal ){ + return pagerOpenSavepoint(pPager, nSavepoint); + }else{ + return SQLITE_OK; + } +} + /* ** This function is called to rollback or release (commit) a savepoint. @@ -46466,7 +50097,7 @@ SQLITE_PRIVATE const char *sqlite3PagerFilename(Pager *pPager, int nullIfMemDb){ /* ** Return the VFS structure for the pager. */ -SQLITE_PRIVATE const sqlite3_vfs *sqlite3PagerVfs(Pager *pPager){ +SQLITE_PRIVATE sqlite3_vfs *sqlite3PagerVfs(Pager *pPager){ return pPager->pVfs; } @@ -46479,6 +50110,18 @@ SQLITE_PRIVATE sqlite3_file *sqlite3PagerFile(Pager *pPager){ return pPager->fd; } +/* +** Return the file handle for the journal file (if it exists). +** This will be either the rollback journal or the WAL file. +*/ +SQLITE_PRIVATE sqlite3_file *sqlite3PagerJrnlFile(Pager *pPager){ +#if SQLITE_OMIT_WAL + return pPager->jfd; +#else + return pPager->pWal ? sqlite3WalFile(pPager->pWal) : pPager->jfd; +#endif +} + /* ** Return the full pathname of the journal file. */ @@ -46601,9 +50244,8 @@ SQLITE_PRIVATE int sqlite3PagerMovepage(Pager *pPager, DbPage *pPg, Pgno pgno, i ** one or more savepoint bitvecs. This is the reason this function ** may return SQLITE_NOMEM. */ - if( pPg->flags&PGHDR_DIRTY - && subjRequiresPage(pPg) - && SQLITE_OK!=(rc = subjournalPage(pPg)) + if( (pPg->flags & PGHDR_DIRTY)!=0 + && SQLITE_OK!=(rc = subjournalPageIfRequired(pPg)) ){ return rc; } @@ -46632,7 +50274,7 @@ SQLITE_PRIVATE int sqlite3PagerMovepage(Pager *pPager, DbPage *pPg, Pgno pgno, i ** for the page moved there. */ pPg->flags &= ~PGHDR_NEED_SYNC; - pPgOld = pager_lookup(pPager, pgno); + pPgOld = sqlite3PagerLookup(pPager, pgno); assert( !pPgOld || pPgOld->nRef==1 ); if( pPgOld ){ pPg->flags |= (pPgOld->flags&PGHDR_NEED_SYNC); @@ -46675,7 +50317,7 @@ SQLITE_PRIVATE int sqlite3PagerMovepage(Pager *pPager, DbPage *pPg, Pgno pgno, i ** the journal file twice, but that is not a problem. */ PgHdr *pPgHdr; - rc = sqlite3PagerGet(pPager, needSyncPgno, &pPgHdr); + rc = sqlite3PagerGet(pPager, needSyncPgno, &pPgHdr, 0); if( rc!=SQLITE_OK ){ if( needSyncPgno<=pPager->dbOrigSize ){ assert( pPager->pTmpSpace!=0 ); @@ -46692,6 +50334,18 @@ SQLITE_PRIVATE int sqlite3PagerMovepage(Pager *pPager, DbPage *pPg, Pgno pgno, i } #endif +/* +** The page handle passed as the first argument refers to a dirty page +** with a page number other than iNew. This function changes the page's +** page number to iNew and sets the value of the PgHdr.flags field to +** the value passed as the third parameter. +*/ +SQLITE_PRIVATE void sqlite3PagerRekey(DbPage *pPg, Pgno iNew, u16 flags){ + assert( pPg->pgno!=iNew ); + pPg->flags = flags; + sqlite3PcacheMove(pPg, iNew); +} + /* ** Return a pointer to the data for the specified page. */ @@ -46837,6 +50491,8 @@ SQLITE_PRIVATE int sqlite3PagerSetJournalMode(Pager *pPager, int eMode){ } assert( state==pPager->eState ); } + }else if( eMode==PAGER_JOURNALMODE_OFF ){ + sqlite3OsClose(pPager->jfd); } } @@ -46908,7 +50564,8 @@ SQLITE_PRIVATE int sqlite3PagerCheckpoint(Pager *pPager, int eMode, int *pnLog, int rc = SQLITE_OK; if( pPager->pWal ){ rc = sqlite3WalCheckpoint(pPager->pWal, eMode, - pPager->xBusyHandler, pPager->pBusyHandlerArg, + (eMode==SQLITE_CHECKPOINT_PASSIVE ? 0 : pPager->xBusyHandler), + pPager->pBusyHandlerArg, pPager->ckptSyncFlags, pPager->pageSize, (u8 *)pPager->pTmpSpace, pnLog, pnCkpt ); @@ -47074,6 +50731,34 @@ SQLITE_PRIVATE int sqlite3PagerCloseWal(Pager *pPager){ return rc; } +#ifdef SQLITE_ENABLE_SNAPSHOT +/* +** If this is a WAL database, obtain a snapshot handle for the snapshot +** currently open. Otherwise, return an error. +*/ +SQLITE_PRIVATE int sqlite3PagerSnapshotGet(Pager *pPager, sqlite3_snapshot **ppSnapshot){ + int rc = SQLITE_ERROR; + if( pPager->pWal ){ + rc = sqlite3WalSnapshotGet(pPager->pWal, ppSnapshot); + } + return rc; +} + +/* +** If this is a WAL database, store a pointer to pSnapshot. Next time a +** read transaction is opened, attempt to read from the snapshot it +** identifies. If this is not a WAL database, return an error. +*/ +SQLITE_PRIVATE int sqlite3PagerSnapshotOpen(Pager *pPager, sqlite3_snapshot *pSnapshot){ + int rc = SQLITE_OK; + if( pPager->pWal ){ + sqlite3WalSnapshotOpen(pPager->pWal, pSnapshot); + }else{ + rc = SQLITE_ERROR; + } + return rc; +} +#endif /* SQLITE_ENABLE_SNAPSHOT */ #endif /* !SQLITE_OMIT_WAL */ #ifdef SQLITE_ENABLE_ZIPVFS @@ -47085,11 +50770,12 @@ SQLITE_PRIVATE int sqlite3PagerCloseWal(Pager *pPager){ ** is empty, return 0. */ SQLITE_PRIVATE int sqlite3PagerWalFramesize(Pager *pPager){ - assert( pPager->eState==PAGER_READER ); + assert( pPager->eState>=PAGER_READER ); return sqlite3WalFramesize(pPager->pWal); } #endif + #endif /* SQLITE_OMIT_DISKIO */ /************** End of pager.c ***********************************************/ @@ -47338,6 +51024,7 @@ SQLITE_PRIVATE int sqlite3PagerWalFramesize(Pager *pPager){ */ #ifndef SQLITE_OMIT_WAL +/* #include "wal.h" */ /* ** Trace output macros @@ -47367,7 +51054,8 @@ SQLITE_PRIVATE int sqlite3WalTrace = 0; /* ** Indices of various locking bytes. WAL_NREADER is the number -** of available reader locks and should be at least 3. +** of available reader locks and should be at least 3. The default +** is SQLITE_SHM_NLOCK==8 and WAL_NREADER==5. */ #define WAL_WRITE_LOCK 0 #define WAL_ALL_BUT_WRITE 1 @@ -47387,7 +51075,10 @@ typedef struct WalCkptInfo WalCkptInfo; ** The following object holds a copy of the wal-index header content. ** ** The actual header in the wal-index consists of two copies of this -** object. +** object followed by one instance of the WalCkptInfo object. +** For all versions of SQLite through 3.10.0 and probably beyond, +** the locking bytes (WalCkptInfo.aLock) start at offset 120 and +** the total header size is 136 bytes. ** ** The szPage value can be any power of 2 between 512 and 32768, inclusive. ** Or it can be 1 to represent a 65536-byte page. The latter case was @@ -47420,6 +51111,16 @@ struct WalIndexHdr { ** However, a WAL_WRITE_LOCK thread can move the value of nBackfill from ** mxFrame back to zero when the WAL is reset. ** +** nBackfillAttempted is the largest value of nBackfill that a checkpoint +** has attempted to achieve. Normally nBackfill==nBackfillAtempted, however +** the nBackfillAttempted is set before any backfilling is done and the +** nBackfill is only set after all backfilling completes. So if a checkpoint +** crashes, nBackfillAttempted might be larger than nBackfill. The +** WalIndexHdr.mxFrame must never be less than nBackfillAttempted. +** +** The aLock[] field is a set of bytes used for locking. These bytes should +** never be read or written. +** ** There is one entry in aReadMark[] for each reader lock. If a reader ** holds read-lock K, then the value in aReadMark[K] is no greater than ** the mxFrame for that reader. The value READMARK_NOT_USED (0xffffffff) @@ -47459,6 +51160,9 @@ struct WalIndexHdr { struct WalCkptInfo { u32 nBackfill; /* Number of WAL frames backfilled into DB */ u32 aReadMark[WAL_NREADER]; /* Reader marks */ + u8 aLock[SQLITE_SHM_NLOCK]; /* Reserved space for locks */ + u32 nBackfillAttempted; /* WAL frames perhaps written, or maybe not */ + u32 notUsed0; /* Available for future enhancements */ }; #define READMARK_NOT_USED 0xffffffff @@ -47468,9 +51172,8 @@ struct WalCkptInfo { ** only support mandatory file-locks, we do not read or write data ** from the region of the file on which locks are applied. */ -#define WALINDEX_LOCK_OFFSET (sizeof(WalIndexHdr)*2 + sizeof(WalCkptInfo)) -#define WALINDEX_LOCK_RESERVED 16 -#define WALINDEX_HDR_SIZE (WALINDEX_LOCK_OFFSET+WALINDEX_LOCK_RESERVED) +#define WALINDEX_LOCK_OFFSET (sizeof(WalIndexHdr)*2+offsetof(WalCkptInfo,aLock)) +#define WALINDEX_HDR_SIZE (sizeof(WalIndexHdr)*2+sizeof(WalCkptInfo)) /* Size of header before each frame in wal */ #define WAL_FRAME_HDRSIZE 24 @@ -47523,11 +51226,15 @@ struct Wal { u8 syncHeader; /* Fsync the WAL header if true */ u8 padToSectorBoundary; /* Pad transactions out to the next sector */ WalIndexHdr hdr; /* Wal-index header for current transaction */ + u32 minFrame; /* Ignore wal frames before this one */ const char *zWalName; /* Name of WAL file */ u32 nCkpt; /* Checkpoint sequence counter in the wal-header */ #ifdef SQLITE_DEBUG u8 lockError; /* True if a locking error has occurred */ #endif +#ifdef SQLITE_ENABLE_SNAPSHOT + WalIndexHdr *pSnapshot; /* Start transaction here if not NULL */ +#endif }; /* @@ -47617,7 +51324,7 @@ static int walIndexPage(Wal *pWal, int iPage, volatile u32 **ppPage){ if( pWal->nWiData<=iPage ){ int nByte = sizeof(u32*)*(iPage+1); volatile u32 **apNew; - apNew = (volatile u32 **)sqlite3_realloc((void *)pWal->apWiData, nByte); + apNew = (volatile u32 **)sqlite3_realloc64((void *)pWal->apWiData, nByte); if( !apNew ){ *ppPage = 0; return SQLITE_NOMEM; @@ -47669,7 +51376,7 @@ static volatile WalIndexHdr *walIndexHdr(Wal *pWal){ ** The argument to this macro must be of type u32. On a little-endian ** architecture, it returns the u32 value that results from interpreting ** the 4 bytes as a big-endian value. On a big-endian architecture, it -** returns the value that would be produced by intepreting the 4 bytes +** returns the value that would be produced by interpreting the 4 bytes ** of the input value as a little-endian integer. */ #define BYTESWAP32(x) ( \ @@ -47743,9 +51450,9 @@ static void walIndexWriteHdr(Wal *pWal){ pWal->hdr.isInit = 1; pWal->hdr.iVersion = WALINDEX_MAX_VERSION; walChecksumBytes(1, (u8*)&pWal->hdr, nCksum, 0, pWal->hdr.aCksum); - memcpy((void *)&aHdr[1], (void *)&pWal->hdr, sizeof(WalIndexHdr)); + memcpy((void*)&aHdr[1], (const void*)&pWal->hdr, sizeof(WalIndexHdr)); walShmBarrier(pWal); - memcpy((void *)&aHdr[0], (void *)&pWal->hdr, sizeof(WalIndexHdr)); + memcpy((void*)&aHdr[0], (const void*)&pWal->hdr, sizeof(WalIndexHdr)); } /* @@ -48046,13 +51753,13 @@ static void walCleanupHash(Wal *pWal){ ** via the hash table even after the cleanup. */ if( iLimit ){ - int i; /* Loop counter */ + int j; /* Loop counter */ int iKey; /* Hash key */ - for(i=1; i<=iLimit; i++){ - for(iKey=walHash(aPgno[i]); aHash[iKey]; iKey=walNextHash(iKey)){ - if( aHash[iKey]==i ) break; + for(j=1; j<=iLimit; j++){ + for(iKey=walHash(aPgno[j]); aHash[iKey]; iKey=walNextHash(iKey)){ + if( aHash[iKey]==j ) break; } - assert( aHash[iKey]==i ); + assert( aHash[iKey]==j ); } } #endif /* SQLITE_ENABLE_EXPENSIVE_ASSERT */ @@ -48083,7 +51790,7 @@ static int walIndexAppend(Wal *pWal, u32 iFrame, u32 iPage){ assert( idx <= HASHTABLE_NSLOT/2 + 1 ); /* If this is the first entry to be added to this hash-table, zero the - ** entire hash table and aPgno[] array before proceding. + ** entire hash table and aPgno[] array before proceeding. */ if( idx==1 ){ int nByte = (int)((u8 *)&aHash[HASHTABLE_NSLOT] - (u8 *)&aPgno[1]); @@ -48241,7 +51948,7 @@ static int walIndexRecover(Wal *pWal){ /* Malloc a buffer to read frames into. */ szFrame = szPage + WAL_FRAME_HDRSIZE; - aFrame = (u8 *)sqlite3_malloc(szFrame); + aFrame = (u8 *)sqlite3_malloc64(szFrame); if( !aFrame ){ rc = SQLITE_NOMEM; goto recovery_error; @@ -48292,6 +51999,7 @@ finished: */ pInfo = walCkptInfo(pWal); pInfo->nBackfill = 0; + pInfo->nBackfillAttempted = pWal->hdr.mxFrame; pInfo->aReadMark[0] = 0; for(i=1; iaReadMark[i] = READMARK_NOT_USED; if( pWal->hdr.mxFrame ) pInfo->aReadMark[1] = pWal->hdr.mxFrame; @@ -48363,7 +52071,11 @@ SQLITE_PRIVATE int sqlite3WalOpen( /* In the amalgamation, the os_unix.c and os_win.c source files come before ** this source file. Verify that the #defines of the locking byte offsets ** in os_unix.c and os_win.c agree with the WALINDEX_LOCK_OFFSET value. + ** For that matter, if the lock offset ever changes from its initial design + ** value of 120, we need to know that so there is an assert() to check it. */ + assert( 120==WALINDEX_LOCK_OFFSET ); + assert( 136==WALINDEX_HDR_SIZE ); #ifdef WIN_SHM_BASE assert( WIN_SHM_BASE==WALINDEX_LOCK_OFFSET ); #endif @@ -48554,7 +52266,7 @@ static void walMergesort( int nMerge = 0; /* Number of elements in list aMerge */ ht_slot *aMerge = 0; /* List to be merged */ int iList; /* Index into input list */ - int iSub = 0; /* Index into aSub array */ + u32 iSub = 0; /* Index into aSub array */ struct Sublist aSub[13]; /* Array of sub-lists */ memset(aSub, 0, sizeof(aSub)); @@ -48565,7 +52277,9 @@ static void walMergesort( nMerge = 1; aMerge = &aList[iList]; for(iSub=0; iList & (1<aList && p->nList<=(1<aList==&aList[iList&~((2<aList, p->nList, &aMerge, &nMerge, aBuffer); @@ -48576,7 +52290,9 @@ static void walMergesort( for(iSub++; iSubnList<=(1<aList==&aList[nList&~((2<aList, p->nList, &aMerge, &nMerge, aBuffer); @@ -48599,7 +52315,7 @@ static void walMergesort( ** Free an iterator allocated by walIteratorInit(). */ static void walIteratorFree(WalIterator *p){ - sqlite3ScratchFree(p); + sqlite3_free(p); } /* @@ -48634,7 +52350,7 @@ static int walIteratorInit(Wal *pWal, WalIterator **pp){ nByte = sizeof(WalIterator) + (nSegment-1)*sizeof(struct WalSegment) + iLast*sizeof(ht_slot); - p = (WalIterator *)sqlite3ScratchMalloc(nByte); + p = (WalIterator *)sqlite3_malloc64(nByte); if( !p ){ return SQLITE_NOMEM; } @@ -48644,7 +52360,7 @@ static int walIteratorInit(Wal *pWal, WalIterator **pp){ /* Allocate temporary space used by the merge-sort routine. This block ** of memory will be freed before this function returns. */ - aTmp = (ht_slot *)sqlite3ScratchMalloc( + aTmp = (ht_slot *)sqlite3_malloc64( sizeof(ht_slot) * (iLast>HASHTABLE_NPAGE?HASHTABLE_NPAGE:iLast) ); if( !aTmp ){ @@ -48681,7 +52397,7 @@ static int walIteratorInit(Wal *pWal, WalIterator **pp){ p->aSegment[i].aPgno = (u32 *)aPgno; } } - sqlite3ScratchFree(aTmp); + sqlite3_free(aTmp); if( rc!=SQLITE_OK ){ walIteratorFree(p); @@ -48718,6 +52434,39 @@ static int walPagesize(Wal *pWal){ return (pWal->hdr.szPage&0xfe00) + ((pWal->hdr.szPage&0x0001)<<16); } +/* +** The following is guaranteed when this function is called: +** +** a) the WRITER lock is held, +** b) the entire log file has been checkpointed, and +** c) any existing readers are reading exclusively from the database +** file - there are no readers that may attempt to read a frame from +** the log file. +** +** This function updates the shared-memory structures so that the next +** client to write to the database (which may be this one) does so by +** writing frames into the start of the log file. +** +** The value of parameter salt1 is used as the aSalt[1] value in the +** new wal-index header. It should be passed a pseudo-random value (i.e. +** one obtained from sqlite3_randomness()). +*/ +static void walRestartHdr(Wal *pWal, u32 salt1){ + volatile WalCkptInfo *pInfo = walCkptInfo(pWal); + int i; /* Loop counter */ + u32 *aSalt = pWal->hdr.aSalt; /* Big-endian salt values */ + pWal->nCkpt++; + pWal->hdr.mxFrame = 0; + sqlite3Put4byte((u8*)&aSalt[0], 1 + sqlite3Get4byte((u8*)&aSalt[0])); + memcpy(&pWal->hdr.aSalt[1], &salt1, 4); + walIndexWriteHdr(pWal); + pInfo->nBackfill = 0; + pInfo->nBackfillAttempted = 0; + pInfo->aReadMark[1] = 0; + for(i=2; iaReadMark[i] = READMARK_NOT_USED; + assert( pInfo->aReadMark[0]==0 ); +} + /* ** Copy as much content as we can from the WAL back into the database file ** in response to an sqlite3_wal_checkpoint() request or the equivalent. @@ -48741,7 +52490,7 @@ static int walPagesize(Wal *pWal){ ** database file. ** ** This routine uses and updates the nBackfill field of the wal-index header. -** This is the only routine tha will increase the value of nBackfill. +** This is the only routine that will increase the value of nBackfill. ** (A WAL reset or recovery will revert nBackfill to zero, but not increase ** its value.) ** @@ -48752,12 +52501,12 @@ static int walPagesize(Wal *pWal){ static int walCheckpoint( Wal *pWal, /* Wal connection */ int eMode, /* One of PASSIVE, FULL or RESTART */ - int (*xBusyCall)(void*), /* Function to call when busy */ + int (*xBusy)(void*), /* Function to call when busy */ void *pBusyArg, /* Context argument for xBusyHandler */ int sync_flags, /* Flags for OsSync() (or 0) */ u8 *zBuf /* Temporary buffer to use */ ){ - int rc; /* Return code */ + int rc = SQLITE_OK; /* Return code */ int szPage; /* Database page-size */ WalIterator *pIter = 0; /* Wal iterator context */ u32 iDbpage = 0; /* Next database page to write */ @@ -48766,123 +52515,156 @@ static int walCheckpoint( u32 mxPage; /* Max database page to write */ int i; /* Loop counter */ volatile WalCkptInfo *pInfo; /* The checkpoint status information */ - int (*xBusy)(void*) = 0; /* Function to call when waiting for locks */ szPage = walPagesize(pWal); testcase( szPage<=32768 ); testcase( szPage>=65536 ); pInfo = walCkptInfo(pWal); - if( pInfo->nBackfill>=pWal->hdr.mxFrame ) return SQLITE_OK; + if( pInfo->nBackfillhdr.mxFrame ){ - /* Allocate the iterator */ - rc = walIteratorInit(pWal, &pIter); - if( rc!=SQLITE_OK ){ - return rc; - } - assert( pIter ); - - if( eMode!=SQLITE_CHECKPOINT_PASSIVE ) xBusy = xBusyCall; - - /* Compute in mxSafeFrame the index of the last frame of the WAL that is - ** safe to write into the database. Frames beyond mxSafeFrame might - ** overwrite database pages that are in use by active readers and thus - ** cannot be backfilled from the WAL. - */ - mxSafeFrame = pWal->hdr.mxFrame; - mxPage = pWal->hdr.nPage; - for(i=1; iaReadMark[i]; - if( mxSafeFrame>y ){ - assert( y<=pWal->hdr.mxFrame ); - rc = walBusyLock(pWal, xBusy, pBusyArg, WAL_READ_LOCK(i), 1); - if( rc==SQLITE_OK ){ - pInfo->aReadMark[i] = (i==1 ? mxSafeFrame : READMARK_NOT_USED); - walUnlockExclusive(pWal, WAL_READ_LOCK(i), 1); - }else if( rc==SQLITE_BUSY ){ - mxSafeFrame = y; - xBusy = 0; - }else{ - goto walcheckpoint_out; - } + /* Allocate the iterator */ + rc = walIteratorInit(pWal, &pIter); + if( rc!=SQLITE_OK ){ + return rc; } - } + assert( pIter ); - if( pInfo->nBackfillnBackfill; + /* EVIDENCE-OF: R-62920-47450 The busy-handler callback is never invoked + ** in the SQLITE_CHECKPOINT_PASSIVE mode. */ + assert( eMode!=SQLITE_CHECKPOINT_PASSIVE || xBusy==0 ); - /* Sync the WAL to disk */ - if( sync_flags ){ - rc = sqlite3OsSync(pWal->pWalFd, sync_flags); - } - - /* If the database may grow as a result of this checkpoint, hint - ** about the eventual size of the db file to the VFS layer. + /* Compute in mxSafeFrame the index of the last frame of the WAL that is + ** safe to write into the database. Frames beyond mxSafeFrame might + ** overwrite database pages that are in use by active readers and thus + ** cannot be backfilled from the WAL. */ - if( rc==SQLITE_OK ){ - i64 nReq = ((i64)mxPage * szPage); - rc = sqlite3OsFileSize(pWal->pDbFd, &nSize); - if( rc==SQLITE_OK && nSizepDbFd, SQLITE_FCNTL_SIZE_HINT, &nReq); - } - } - - - /* Iterate through the contents of the WAL, copying data to the db file. */ - while( rc==SQLITE_OK && 0==walIteratorNext(pIter, &iDbpage, &iFrame) ){ - i64 iOffset; - assert( walFramePgno(pWal, iFrame)==iDbpage ); - if( iFrame<=nBackfill || iFrame>mxSafeFrame || iDbpage>mxPage ) continue; - iOffset = walFrameOffset(iFrame, szPage) + WAL_FRAME_HDRSIZE; - /* testcase( IS_BIG_INT(iOffset) ); // requires a 4GiB WAL file */ - rc = sqlite3OsRead(pWal->pWalFd, zBuf, szPage, iOffset); - if( rc!=SQLITE_OK ) break; - iOffset = (iDbpage-1)*(i64)szPage; - testcase( IS_BIG_INT(iOffset) ); - rc = sqlite3OsWrite(pWal->pDbFd, zBuf, szPage, iOffset); - if( rc!=SQLITE_OK ) break; - } - - /* If work was actually accomplished... */ - if( rc==SQLITE_OK ){ - if( mxSafeFrame==walIndexHdr(pWal)->mxFrame ){ - i64 szDb = pWal->hdr.nPage*(i64)szPage; - testcase( IS_BIG_INT(szDb) ); - rc = sqlite3OsTruncate(pWal->pDbFd, szDb); - if( rc==SQLITE_OK && sync_flags ){ - rc = sqlite3OsSync(pWal->pDbFd, sync_flags); + mxSafeFrame = pWal->hdr.mxFrame; + mxPage = pWal->hdr.nPage; + for(i=1; iaReadMark[i]; + if( mxSafeFrame>y ){ + assert( y<=pWal->hdr.mxFrame ); + rc = walBusyLock(pWal, xBusy, pBusyArg, WAL_READ_LOCK(i), 1); + if( rc==SQLITE_OK ){ + pInfo->aReadMark[i] = (i==1 ? mxSafeFrame : READMARK_NOT_USED); + walUnlockExclusive(pWal, WAL_READ_LOCK(i), 1); + }else if( rc==SQLITE_BUSY ){ + mxSafeFrame = y; + xBusy = 0; + }else{ + goto walcheckpoint_out; } } - if( rc==SQLITE_OK ){ - pInfo->nBackfill = mxSafeFrame; - } } - /* Release the reader lock held while backfilling */ - walUnlockExclusive(pWal, WAL_READ_LOCK(0), 1); + if( pInfo->nBackfillnBackfill; + + pInfo->nBackfillAttempted = mxSafeFrame; + + /* Sync the WAL to disk */ + if( sync_flags ){ + rc = sqlite3OsSync(pWal->pWalFd, sync_flags); + } + + /* If the database may grow as a result of this checkpoint, hint + ** about the eventual size of the db file to the VFS layer. + */ + if( rc==SQLITE_OK ){ + i64 nReq = ((i64)mxPage * szPage); + rc = sqlite3OsFileSize(pWal->pDbFd, &nSize); + if( rc==SQLITE_OK && nSizepDbFd, SQLITE_FCNTL_SIZE_HINT, &nReq); + } + } + + + /* Iterate through the contents of the WAL, copying data to the db file */ + while( rc==SQLITE_OK && 0==walIteratorNext(pIter, &iDbpage, &iFrame) ){ + i64 iOffset; + assert( walFramePgno(pWal, iFrame)==iDbpage ); + if( iFrame<=nBackfill || iFrame>mxSafeFrame || iDbpage>mxPage ){ + continue; + } + iOffset = walFrameOffset(iFrame, szPage) + WAL_FRAME_HDRSIZE; + /* testcase( IS_BIG_INT(iOffset) ); // requires a 4GiB WAL file */ + rc = sqlite3OsRead(pWal->pWalFd, zBuf, szPage, iOffset); + if( rc!=SQLITE_OK ) break; + iOffset = (iDbpage-1)*(i64)szPage; + testcase( IS_BIG_INT(iOffset) ); + rc = sqlite3OsWrite(pWal->pDbFd, zBuf, szPage, iOffset); + if( rc!=SQLITE_OK ) break; + } + + /* If work was actually accomplished... */ + if( rc==SQLITE_OK ){ + if( mxSafeFrame==walIndexHdr(pWal)->mxFrame ){ + i64 szDb = pWal->hdr.nPage*(i64)szPage; + testcase( IS_BIG_INT(szDb) ); + rc = sqlite3OsTruncate(pWal->pDbFd, szDb); + if( rc==SQLITE_OK && sync_flags ){ + rc = sqlite3OsSync(pWal->pDbFd, sync_flags); + } + } + if( rc==SQLITE_OK ){ + pInfo->nBackfill = mxSafeFrame; + } + } + + /* Release the reader lock held while backfilling */ + walUnlockExclusive(pWal, WAL_READ_LOCK(0), 1); + } + + if( rc==SQLITE_BUSY ){ + /* Reset the return code so as not to report a checkpoint failure + ** just because there are active readers. */ + rc = SQLITE_OK; + } } - if( rc==SQLITE_BUSY ){ - /* Reset the return code so as not to report a checkpoint failure - ** just because there are active readers. */ - rc = SQLITE_OK; - } - - /* If this is an SQLITE_CHECKPOINT_RESTART operation, and the entire wal - ** file has been copied into the database file, then block until all - ** readers have finished using the wal file. This ensures that the next - ** process to write to the database restarts the wal file. + /* If this is an SQLITE_CHECKPOINT_RESTART or TRUNCATE operation, and the + ** entire wal file has been copied into the database file, then block + ** until all readers have finished using the wal file. This ensures that + ** the next process to write to the database restarts the wal file. */ if( rc==SQLITE_OK && eMode!=SQLITE_CHECKPOINT_PASSIVE ){ assert( pWal->writeLock ); if( pInfo->nBackfillhdr.mxFrame ){ rc = SQLITE_BUSY; - }else if( eMode==SQLITE_CHECKPOINT_RESTART ){ - assert( mxSafeFrame==pWal->hdr.mxFrame ); + }else if( eMode>=SQLITE_CHECKPOINT_RESTART ){ + u32 salt1; + sqlite3_randomness(4, &salt1); + assert( pInfo->nBackfill==pWal->hdr.mxFrame ); rc = walBusyLock(pWal, xBusy, pBusyArg, WAL_READ_LOCK(1), WAL_NREADER-1); if( rc==SQLITE_OK ){ + if( eMode==SQLITE_CHECKPOINT_TRUNCATE ){ + /* IMPLEMENTATION-OF: R-44699-57140 This mode works the same way as + ** SQLITE_CHECKPOINT_RESTART with the addition that it also + ** truncates the log file to zero bytes just prior to a + ** successful return. + ** + ** In theory, it might be safe to do this without updating the + ** wal-index header in shared memory, as all subsequent reader or + ** writer clients should see that the entire log file has been + ** checkpointed and behave accordingly. This seems unsafe though, + ** as it would leave the system in a state where the contents of + ** the wal-index header do not match the contents of the + ** file-system. To avoid this, update the wal-index header to + ** indicate that the log file contains zero valid frames. */ + walRestartHdr(pWal, salt1); + rc = sqlite3OsTruncate(pWal->pWalFd, 0); + } walUnlockExclusive(pWal, WAL_READ_LOCK(1), WAL_NREADER-1); } } @@ -49045,7 +52827,7 @@ static int walIndexTryHdr(Wal *pWal, int *pChanged){ ** wal-index from the WAL before returning. ** ** Set *pChanged to 1 if the wal-index header value in pWal->hdr is -** changed by this opertion. If pWal->hdr is unchanged, set *pChanged +** changed by this operation. If pWal->hdr is unchanged, set *pChanged ** to 0. ** ** If the wal-index header is successfully read, return SQLITE_OK. @@ -49174,6 +52956,7 @@ static int walTryBeginRead(Wal *pWal, int *pChanged, int useWal, int cnt){ int mxI; /* Index of largest aReadMark[] value */ int i; /* Loop counter */ int rc = SQLITE_OK; /* Return code */ + u32 mxFrame; /* Wal frame to lock to */ assert( pWal->readLock<0 ); /* Not currently locked */ @@ -49191,8 +52974,8 @@ static int walTryBeginRead(Wal *pWal, int *pChanged, int useWal, int cnt){ ** calls to sqlite3OsSleep() have a delay of 1 microsecond. Really this ** is more of a scheduler yield than an actual delay. But on the 10th ** an subsequent retries, the delays start becoming longer and longer, - ** so that on the 100th (and last) RETRY we delay for 21 milliseconds. - ** The total delay time before giving up is less than 1 second. + ** so that on the 100th (and last) RETRY we delay for 323 milliseconds. + ** The total delay time before giving up is less than 10 seconds. */ if( cnt>5 ){ int nDelay = 1; /* Pause time in microseconds */ @@ -49200,7 +52983,7 @@ static int walTryBeginRead(Wal *pWal, int *pChanged, int useWal, int cnt){ VVA_ONLY( pWal->lockError = 1; ) return SQLITE_PROTOCOL; } - if( cnt>=10 ) nDelay = (cnt-9)*238; /* Max delay 21ms. Total delay 996ms */ + if( cnt>=10 ) nDelay = (cnt-9)*(cnt-9)*39; sqlite3OsSleep(pWal->pVfs, nDelay); } @@ -49237,7 +53020,12 @@ static int walTryBeginRead(Wal *pWal, int *pChanged, int useWal, int cnt){ } pInfo = walCkptInfo(pWal); - if( !useWal && pInfo->nBackfill==pWal->hdr.mxFrame ){ + if( !useWal && pInfo->nBackfill==pWal->hdr.mxFrame +#ifdef SQLITE_ENABLE_SNAPSHOT + && (pWal->pSnapshot==0 || pWal->hdr.mxFrame==0 + || 0==memcmp(&pWal->hdr, pWal->pSnapshot, sizeof(WalIndexHdr))) +#endif + ){ /* The WAL has been completely backfilled (or it is empty). ** and can be safely ignored. */ @@ -49249,7 +53037,7 @@ static int walTryBeginRead(Wal *pWal, int *pChanged, int useWal, int cnt){ ** may have been appended to the log before READ_LOCK(0) was obtained. ** When holding READ_LOCK(0), the reader ignores the entire log file, ** which implies that the database file contains a trustworthy - ** snapshoT. Since holding READ_LOCK(0) prevents a checkpoint from + ** snapshot. Since holding READ_LOCK(0) prevents a checkpoint from ** happening, this is usually correct. ** ** However, if frames have been appended to the log (or if the log @@ -49275,70 +53063,88 @@ static int walTryBeginRead(Wal *pWal, int *pChanged, int useWal, int cnt){ */ mxReadMark = 0; mxI = 0; + mxFrame = pWal->hdr.mxFrame; +#ifdef SQLITE_ENABLE_SNAPSHOT + if( pWal->pSnapshot && pWal->pSnapshot->mxFramepSnapshot->mxFrame; + } +#endif for(i=1; iaReadMark[i]; - if( mxReadMark<=thisMark && thisMark<=pWal->hdr.mxFrame ){ + if( mxReadMark<=thisMark && thisMark<=mxFrame ){ assert( thisMark!=READMARK_NOT_USED ); mxReadMark = thisMark; mxI = i; } } - /* There was once an "if" here. The extra "{" is to preserve indentation. */ - { - if( (pWal->readOnly & WAL_SHM_RDONLY)==0 - && (mxReadMarkhdr.mxFrame || mxI==0) - ){ - for(i=1; iaReadMark[i] = pWal->hdr.mxFrame; - mxI = i; - walUnlockExclusive(pWal, WAL_READ_LOCK(i), 1); - break; - }else if( rc!=SQLITE_BUSY ){ - return rc; - } + if( (pWal->readOnly & WAL_SHM_RDONLY)==0 + && (mxReadMarkaReadMark[i] = mxFrame; + mxI = i; + walUnlockExclusive(pWal, WAL_READ_LOCK(i), 1); + break; + }else if( rc!=SQLITE_BUSY ){ + return rc; } } - if( mxI==0 ){ - assert( rc==SQLITE_BUSY || (pWal->readOnly & WAL_SHM_RDONLY)!=0 ); - return rc==SQLITE_BUSY ? WAL_RETRY : SQLITE_READONLY_CANTLOCK; - } + } + if( mxI==0 ){ + assert( rc==SQLITE_BUSY || (pWal->readOnly & WAL_SHM_RDONLY)!=0 ); + return rc==SQLITE_BUSY ? WAL_RETRY : SQLITE_READONLY_CANTLOCK; + } - rc = walLockShared(pWal, WAL_READ_LOCK(mxI)); - if( rc ){ - return rc==SQLITE_BUSY ? WAL_RETRY : rc; - } - /* Now that the read-lock has been obtained, check that neither the - ** value in the aReadMark[] array or the contents of the wal-index - ** header have changed. - ** - ** It is necessary to check that the wal-index header did not change - ** between the time it was read and when the shared-lock was obtained - ** on WAL_READ_LOCK(mxI) was obtained to account for the possibility - ** that the log file may have been wrapped by a writer, or that frames - ** that occur later in the log than pWal->hdr.mxFrame may have been - ** copied into the database by a checkpointer. If either of these things - ** happened, then reading the database with the current value of - ** pWal->hdr.mxFrame risks reading a corrupted snapshot. So, retry - ** instead. - ** - ** This does not guarantee that the copy of the wal-index header is up to - ** date before proceeding. That would not be possible without somehow - ** blocking writers. It only guarantees that a dangerous checkpoint or - ** log-wrap (either of which would require an exclusive lock on - ** WAL_READ_LOCK(mxI)) has not occurred since the snapshot was valid. - */ - walShmBarrier(pWal); - if( pInfo->aReadMark[mxI]!=mxReadMark - || memcmp((void *)walIndexHdr(pWal), &pWal->hdr, sizeof(WalIndexHdr)) - ){ - walUnlockShared(pWal, WAL_READ_LOCK(mxI)); - return WAL_RETRY; - }else{ - assert( mxReadMark<=pWal->hdr.mxFrame ); - pWal->readLock = (i16)mxI; - } + rc = walLockShared(pWal, WAL_READ_LOCK(mxI)); + if( rc ){ + return rc==SQLITE_BUSY ? WAL_RETRY : rc; + } + /* Now that the read-lock has been obtained, check that neither the + ** value in the aReadMark[] array or the contents of the wal-index + ** header have changed. + ** + ** It is necessary to check that the wal-index header did not change + ** between the time it was read and when the shared-lock was obtained + ** on WAL_READ_LOCK(mxI) was obtained to account for the possibility + ** that the log file may have been wrapped by a writer, or that frames + ** that occur later in the log than pWal->hdr.mxFrame may have been + ** copied into the database by a checkpointer. If either of these things + ** happened, then reading the database with the current value of + ** pWal->hdr.mxFrame risks reading a corrupted snapshot. So, retry + ** instead. + ** + ** Before checking that the live wal-index header has not changed + ** since it was read, set Wal.minFrame to the first frame in the wal + ** file that has not yet been checkpointed. This client will not need + ** to read any frames earlier than minFrame from the wal file - they + ** can be safely read directly from the database file. + ** + ** Because a ShmBarrier() call is made between taking the copy of + ** nBackfill and checking that the wal-header in shared-memory still + ** matches the one cached in pWal->hdr, it is guaranteed that the + ** checkpointer that set nBackfill was not working with a wal-index + ** header newer than that cached in pWal->hdr. If it were, that could + ** cause a problem. The checkpointer could omit to checkpoint + ** a version of page X that lies before pWal->minFrame (call that version + ** A) on the basis that there is a newer version (version B) of the same + ** page later in the wal file. But if version B happens to like past + ** frame pWal->hdr.mxFrame - then the client would incorrectly assume + ** that it can read version A from the database file. However, since + ** we can guarantee that the checkpointer that set nBackfill could not + ** see any pages past pWal->hdr.mxFrame, this problem does not come up. + */ + pWal->minFrame = pInfo->nBackfill+1; + walShmBarrier(pWal); + if( pInfo->aReadMark[mxI]!=mxReadMark + || memcmp((void *)walIndexHdr(pWal), &pWal->hdr, sizeof(WalIndexHdr)) + ){ + walUnlockShared(pWal, WAL_READ_LOCK(mxI)); + return WAL_RETRY; + }else{ + assert( mxReadMark<=pWal->hdr.mxFrame ); + pWal->readLock = (i16)mxI; } return rc; } @@ -49361,6 +53167,14 @@ SQLITE_PRIVATE int sqlite3WalBeginReadTransaction(Wal *pWal, int *pChanged){ int rc; /* Return code */ int cnt = 0; /* Number of TryBeginRead attempts */ +#ifdef SQLITE_ENABLE_SNAPSHOT + int bChanged = 0; + WalIndexHdr *pSnapshot = pWal->pSnapshot; + if( pSnapshot && memcmp(pSnapshot, &pWal->hdr, sizeof(WalIndexHdr))!=0 ){ + bChanged = 1; + } +#endif + do{ rc = walTryBeginRead(pWal, pChanged, 0, ++cnt); }while( rc==WAL_RETRY ); @@ -49368,6 +53182,66 @@ SQLITE_PRIVATE int sqlite3WalBeginReadTransaction(Wal *pWal, int *pChanged){ testcase( (rc&0xff)==SQLITE_IOERR ); testcase( rc==SQLITE_PROTOCOL ); testcase( rc==SQLITE_OK ); + +#ifdef SQLITE_ENABLE_SNAPSHOT + if( rc==SQLITE_OK ){ + if( pSnapshot && memcmp(pSnapshot, &pWal->hdr, sizeof(WalIndexHdr))!=0 ){ + /* At this point the client has a lock on an aReadMark[] slot holding + ** a value equal to or smaller than pSnapshot->mxFrame, but pWal->hdr + ** is populated with the wal-index header corresponding to the head + ** of the wal file. Verify that pSnapshot is still valid before + ** continuing. Reasons why pSnapshot might no longer be valid: + ** + ** (1) The WAL file has been reset since the snapshot was taken. + ** In this case, the salt will have changed. + ** + ** (2) A checkpoint as been attempted that wrote frames past + ** pSnapshot->mxFrame into the database file. Note that the + ** checkpoint need not have completed for this to cause problems. + */ + volatile WalCkptInfo *pInfo = walCkptInfo(pWal); + + assert( pWal->readLock>0 || pWal->hdr.mxFrame==0 ); + assert( pInfo->aReadMark[pWal->readLock]<=pSnapshot->mxFrame ); + + /* It is possible that there is a checkpointer thread running + ** concurrent with this code. If this is the case, it may be that the + ** checkpointer has already determined that it will checkpoint + ** snapshot X, where X is later in the wal file than pSnapshot, but + ** has not yet set the pInfo->nBackfillAttempted variable to indicate + ** its intent. To avoid the race condition this leads to, ensure that + ** there is no checkpointer process by taking a shared CKPT lock + ** before checking pInfo->nBackfillAttempted. */ + rc = walLockShared(pWal, WAL_CKPT_LOCK); + + if( rc==SQLITE_OK ){ + /* Check that the wal file has not been wrapped. Assuming that it has + ** not, also check that no checkpointer has attempted to checkpoint any + ** frames beyond pSnapshot->mxFrame. If either of these conditions are + ** true, return SQLITE_BUSY_SNAPSHOT. Otherwise, overwrite pWal->hdr + ** with *pSnapshot and set *pChanged as appropriate for opening the + ** snapshot. */ + if( !memcmp(pSnapshot->aSalt, pWal->hdr.aSalt, sizeof(pWal->hdr.aSalt)) + && pSnapshot->mxFrame>=pInfo->nBackfillAttempted + ){ + assert( pWal->readLock>0 ); + memcpy(&pWal->hdr, pSnapshot, sizeof(WalIndexHdr)); + *pChanged = bChanged; + }else{ + rc = SQLITE_BUSY_SNAPSHOT; + } + + /* Release the shared CKPT lock obtained above. */ + walUnlockShared(pWal, WAL_CKPT_LOCK); + } + + + if( rc!=SQLITE_OK ){ + sqlite3WalEndReadTransaction(pWal); + } + } + } +#endif return rc; } @@ -49399,6 +53273,7 @@ SQLITE_PRIVATE int sqlite3WalFindFrame( u32 iRead = 0; /* If !=0, WAL frame to return data from */ u32 iLast = pWal->hdr.mxFrame; /* Last page in WAL for this reader */ int iHash; /* Used to loop through N hash tables */ + int iMinHash; /* This routine is only be called from within a read transaction. */ assert( pWal->readLock>=0 || pWal->lockError ); @@ -49439,7 +53314,8 @@ SQLITE_PRIVATE int sqlite3WalFindFrame( ** This condition filters out entries that were added to the hash ** table after the current read-transaction had started. */ - for(iHash=walFramePage(iLast); iHash>=0 && iRead==0; iHash--){ + iMinHash = walFramePage(pWal->minFrame); + for(iHash=walFramePage(iLast); iHash>=iMinHash && iRead==0; iHash--){ volatile ht_slot *aHash; /* Pointer to hash table */ volatile u32 *aPgno; /* Pointer to array of page numbers */ u32 iZero; /* Frame number corresponding to aPgno[0] */ @@ -49454,8 +53330,8 @@ SQLITE_PRIVATE int sqlite3WalFindFrame( nCollide = HASHTABLE_NSLOT; for(iKey=walHash(pgno); aHash[iKey]; iKey=walNextHash(iKey)){ u32 iFrame = aHash[iKey] + iZero; - if( iFrame<=iLast && aPgno[aHash[iKey]]==pgno ){ - /* assert( iFrame>iRead ); -- not true if there is corruption */ + if( iFrame<=iLast && iFrame>=pWal->minFrame && aPgno[aHash[iKey]]==pgno ){ + assert( iFrame>iRead || CORRUPT_DB ); iRead = iFrame; } if( (nCollide--)==0 ){ @@ -49471,7 +53347,8 @@ SQLITE_PRIVATE int sqlite3WalFindFrame( { u32 iRead2 = 0; u32 iTest; - for(iTest=iLast; iTest>0; iTest--){ + assert( pWal->minFrame>0 ); + for(iTest=iLast; iTest>=pWal->minFrame; iTest--){ if( walFramePgno(pWal, iTest)==pgno ){ iRead2 = iTest; break; @@ -49620,7 +53497,6 @@ SQLITE_PRIVATE int sqlite3WalUndo(Wal *pWal, int (*xUndo)(void *, Pgno), void *p } if( iMax!=pWal->hdr.mxFrame ) walCleanupHash(pWal); } - assert( rc==SQLITE_OK ); return rc; } @@ -49669,7 +53545,6 @@ SQLITE_PRIVATE int sqlite3WalSavepointUndo(Wal *pWal, u32 *aWalData){ return rc; } - /* ** This function is called just before writing a set of frames to the log ** file (see sqlite3WalFrames()). It checks to see if, instead of appending @@ -49702,20 +53577,8 @@ static int walRestartLog(Wal *pWal){ ** In theory it would be Ok to update the cache of the header only ** at this point. But updating the actual wal-index header is also ** safe and means there is no special case for sqlite3WalUndo() - ** to handle if this transaction is rolled back. - */ - int i; /* Loop counter */ - u32 *aSalt = pWal->hdr.aSalt; /* Big-endian salt values */ - - pWal->nCkpt++; - pWal->hdr.mxFrame = 0; - sqlite3Put4byte((u8*)&aSalt[0], 1 + sqlite3Get4byte((u8*)&aSalt[0])); - aSalt[1] = salt1; - walIndexWriteHdr(pWal); - pInfo->nBackfill = 0; - pInfo->aReadMark[1] = 0; - for(i=2; iaReadMark[i] = READMARK_NOT_USED; - assert( pInfo->aReadMark[0]==0 ); + ** to handle if this transaction is rolled back. */ + walRestartHdr(pWal, salt1); walUnlockExclusive(pWal, WAL_READ_LOCK(1), WAL_NREADER-1); }else if( rc!=SQLITE_BUSY ){ return rc; @@ -49917,7 +53780,7 @@ SQLITE_PRIVATE int sqlite3WalFrames( ** ** Padding and syncing only occur if this set of frames complete a ** transaction and if PRAGMA synchronous=FULL. If synchronous==NORMAL - ** or synchonous==OFF, then no padding or syncing are needed. + ** or synchronous==OFF, then no padding or syncing are needed. ** ** If SQLITE_IOCAP_POWERSAFE_OVERWRITE is defined, then padding is not ** needed and only the sync is done. If padding is needed, then the @@ -50003,7 +53866,7 @@ SQLITE_PRIVATE int sqlite3WalFrames( */ SQLITE_PRIVATE int sqlite3WalCheckpoint( Wal *pWal, /* Wal connection */ - int eMode, /* PASSIVE, FULL or RESTART */ + int eMode, /* PASSIVE, FULL, RESTART, or TRUNCATE */ int (*xBusy)(void*), /* Function to call when busy */ void *pBusyArg, /* Context argument for xBusyHandler */ int sync_flags, /* Flags to sync db file with (or 0) */ @@ -50015,29 +53878,42 @@ SQLITE_PRIVATE int sqlite3WalCheckpoint( int rc; /* Return code */ int isChanged = 0; /* True if a new wal-index header is loaded */ int eMode2 = eMode; /* Mode to pass to walCheckpoint() */ + int (*xBusy2)(void*) = xBusy; /* Busy handler for eMode2 */ assert( pWal->ckptLock==0 ); assert( pWal->writeLock==0 ); + /* EVIDENCE-OF: R-62920-47450 The busy-handler callback is never invoked + ** in the SQLITE_CHECKPOINT_PASSIVE mode. */ + assert( eMode!=SQLITE_CHECKPOINT_PASSIVE || xBusy==0 ); + if( pWal->readOnly ) return SQLITE_READONLY; WALTRACE(("WAL%p: checkpoint begins\n", pWal)); + + /* IMPLEMENTATION-OF: R-62028-47212 All calls obtain an exclusive + ** "checkpoint" lock on the database file. */ rc = walLockExclusive(pWal, WAL_CKPT_LOCK, 1); if( rc ){ - /* Usually this is SQLITE_BUSY meaning that another thread or process - ** is already running a checkpoint, or maybe a recovery. But it might - ** also be SQLITE_IOERR. */ + /* EVIDENCE-OF: R-10421-19736 If any other process is running a + ** checkpoint operation at the same time, the lock cannot be obtained and + ** SQLITE_BUSY is returned. + ** EVIDENCE-OF: R-53820-33897 Even if there is a busy-handler configured, + ** it will not be invoked in this case. + */ + testcase( rc==SQLITE_BUSY ); + testcase( xBusy!=0 ); return rc; } pWal->ckptLock = 1; - /* If this is a blocking-checkpoint, then obtain the write-lock as well - ** to prevent any writers from running while the checkpoint is underway. - ** This has to be done before the call to walIndexReadHdr() below. + /* IMPLEMENTATION-OF: R-59782-36818 The SQLITE_CHECKPOINT_FULL, RESTART and + ** TRUNCATE modes also obtain the exclusive "writer" lock on the database + ** file. ** - ** If the writer lock cannot be obtained, then a passive checkpoint is - ** run instead. Since the checkpointer is not holding the writer lock, - ** there is no point in blocking waiting for any readers. Assuming no - ** other error occurs, this function will return SQLITE_BUSY to the caller. + ** EVIDENCE-OF: R-60642-04082 If the writer lock cannot be obtained + ** immediately, and a busy-handler is configured, it is invoked and the + ** writer lock retried until either the busy-handler returns 0 or the + ** lock is successfully obtained. */ if( eMode!=SQLITE_CHECKPOINT_PASSIVE ){ rc = walBusyLock(pWal, xBusy, pBusyArg, WAL_WRITE_LOCK, 1); @@ -50045,6 +53921,7 @@ SQLITE_PRIVATE int sqlite3WalCheckpoint( pWal->writeLock = 1; }else if( rc==SQLITE_BUSY ){ eMode2 = SQLITE_CHECKPOINT_PASSIVE; + xBusy2 = 0; rc = SQLITE_OK; } } @@ -50062,7 +53939,7 @@ SQLITE_PRIVATE int sqlite3WalCheckpoint( if( pWal->hdr.mxFrame && walPagesize(pWal)!=nBuf ){ rc = SQLITE_CORRUPT_BKPT; }else{ - rc = walCheckpoint(pWal, eMode2, xBusy, pBusyArg, sync_flags, zBuf); + rc = walCheckpoint(pWal, eMode2, xBusy2, pBusyArg, sync_flags, zBuf); } /* If no error occurred, set the output variables. */ @@ -50174,6 +54051,35 @@ SQLITE_PRIVATE int sqlite3WalHeapMemory(Wal *pWal){ return (pWal && pWal->exclusiveMode==WAL_HEAPMEMORY_MODE ); } +#ifdef SQLITE_ENABLE_SNAPSHOT +/* Create a snapshot object. The content of a snapshot is opaque to +** every other subsystem, so the WAL module can put whatever it needs +** in the object. +*/ +SQLITE_PRIVATE int sqlite3WalSnapshotGet(Wal *pWal, sqlite3_snapshot **ppSnapshot){ + int rc = SQLITE_OK; + WalIndexHdr *pRet; + + assert( pWal->readLock>=0 && pWal->writeLock==0 ); + + pRet = (WalIndexHdr*)sqlite3_malloc(sizeof(WalIndexHdr)); + if( pRet==0 ){ + rc = SQLITE_NOMEM; + }else{ + memcpy(pRet, &pWal->hdr, sizeof(WalIndexHdr)); + *ppSnapshot = (sqlite3_snapshot*)pRet; + } + + return rc; +} + +/* Try to open on pSnapshot when the next read-transaction starts +*/ +SQLITE_PRIVATE void sqlite3WalSnapshotOpen(Wal *pWal, sqlite3_snapshot *pSnapshot){ + pWal->pSnapshot = (WalIndexHdr*)pSnapshot; +} +#endif /* SQLITE_ENABLE_SNAPSHOT */ + #ifdef SQLITE_ENABLE_ZIPVFS /* ** If the argument is not NULL, it points to a Wal object that holds a @@ -50186,6 +54092,12 @@ SQLITE_PRIVATE int sqlite3WalFramesize(Wal *pWal){ } #endif +/* Return the sqlite3_file object for the WAL file +*/ +SQLITE_PRIVATE sqlite3_file *sqlite3WalFile(Wal *pWal){ + return pWal->pWalFd; +} + #endif /* #ifndef SQLITE_OMIT_WAL */ /************** End of wal.c *************************************************/ @@ -50220,7 +54132,7 @@ SQLITE_PRIVATE int sqlite3WalFramesize(Wal *pWal){ ** May you share freely, never taking more than you give. ** ************************************************************************* -** This file implements a external (disk-based) database using BTrees. +** This file implements an external (disk-based) database using BTrees. ** For a detailed discussion of BTrees, refer to ** ** Donald E. Knuth, THE ART OF COMPUTER PROGRAMMING, Volume 3: @@ -50346,7 +54258,7 @@ SQLITE_PRIVATE int sqlite3WalFramesize(Wal *pWal){ ** ** The flags define the format of this btree page. The leaf flag means that ** this page has no children. The zerodata flag means that this page carries -** only keys and no data. The intkey flag means that the key is a integer +** only keys and no data. The intkey flag means that the key is an integer ** which is stored in the key size entry of the cell header rather than in ** the payload area. ** @@ -50424,6 +54336,7 @@ SQLITE_PRIVATE int sqlite3WalFramesize(Wal *pWal){ ** 4 Number of leaf pointers on this page ** * zero or more pages numbers of leaves */ +/* #include "sqliteInt.h" */ /* The following value is the maximum cell size assuming a maximum page @@ -50441,6 +54354,7 @@ SQLITE_PRIVATE int sqlite3WalFramesize(Wal *pWal){ /* Forward declarations */ typedef struct MemPage MemPage; typedef struct BtLock BtLock; +typedef struct CellInfo CellInfo; /* ** This is a magic string that appears at the beginning of every @@ -50483,12 +54397,14 @@ typedef struct BtLock BtLock; struct MemPage { u8 isInit; /* True if previously initialized. MUST BE FIRST! */ u8 nOverflow; /* Number of overflow cell bodies in aCell[] */ - u8 intKey; /* True if intkey flag is set */ - u8 leaf; /* True if leaf flag is set */ - u8 hasData; /* True if this page stores data */ + u8 intKey; /* True if table b-trees. False for index b-trees */ + u8 intKeyLeaf; /* True if the leaf of an intKey table */ + u8 noPayload; /* True if internal intKey page (thus w/o data) */ + u8 leaf; /* True if a leaf page */ u8 hdrOffset; /* 100 for page 1. 0 otherwise */ u8 childPtrSize; /* 0 if leaf==1. 4 if leaf==0 */ u8 max1bytePayload; /* min(maxLocal,127) */ + u8 bBusy; /* Prevent endless loops on corrupt database files */ u16 maxLocal; /* Copy of BtShared.maxLocal or BtShared.maxLeaf */ u16 minLocal; /* Copy of BtShared.minLocal or BtShared.minLeaf */ u16 cellOffset; /* Index in aData of first cell pointer */ @@ -50502,7 +54418,10 @@ struct MemPage { u8 *aData; /* Pointer to disk image of the page data */ u8 *aDataEnd; /* One byte past the end of usable data */ u8 *aCellIdx; /* The cell index area */ + u8 *aDataOfst; /* Same as aData for leaves. aData+4 for interior */ DbPage *pDbPage; /* Pager page handle */ + u16 (*xCellSize)(MemPage*,u8*); /* cellSizePtr method */ + void (*xParseCell)(MemPage*,u8*,CellInfo*); /* btreeParseCell method */ Pgno pgno; /* Page number for this page */ }; @@ -50558,8 +54477,10 @@ struct Btree { u8 inTrans; /* TRANS_NONE, TRANS_READ or TRANS_WRITE */ u8 sharable; /* True if we can share pBt with another db */ u8 locked; /* True if db currently has pBt locked */ + u8 hasIncrblobCur; /* True if there are one or more Incrblob cursors */ int wantToLock; /* Number of nested calls to sqlite3BtreeEnter() */ int nBackup; /* Number of backup operations reading this btree */ + u32 iDataVersion; /* Combines with pBt->pPager->iDataVersion */ Btree *pNext; /* List of other sharable Btrees from the same db */ Btree *pPrev; /* Back pointer of the same list */ #ifndef SQLITE_OMIT_SHARED_CACHE @@ -50626,6 +54547,9 @@ struct BtShared { #endif u8 inTransaction; /* Transaction state */ u8 max1bytePayload; /* Maximum first byte of cell for a 1-byte payload */ +#ifdef SQLITE_HAS_CODEC + u8 optimalReserve; /* Desired amount of reserved space per page */ +#endif u16 btsFlags; /* Boolean parameters. See BTS_* macros below */ u16 maxLocal; /* Maximum local payload in non-LEAFDATA tables */ u16 minLocal; /* Minimum local payload in non-LEAFDATA tables */ @@ -50645,7 +54569,7 @@ struct BtShared { BtLock *pLock; /* List of locks held on this shared-btree struct */ Btree *pWriter; /* Btree with currently open write transaction */ #endif - u8 *pTmpSpace; /* BtShared.pageSize bytes of space for tmp use */ + u8 *pTmpSpace; /* Temp space sufficient to hold a single cell */ }; /* @@ -50664,15 +54588,11 @@ struct BtShared { ** about a cell. The parseCellPtr() function fills in this structure ** based on information extract from the raw disk page. */ -typedef struct CellInfo CellInfo; struct CellInfo { - i64 nKey; /* The key for INTKEY tables, or number of bytes in key */ - u8 *pCell; /* Pointer to the start of cell content */ - u32 nData; /* Number of bytes of data */ - u32 nPayload; /* Total amount of payload */ - u16 nHeader; /* Size of the cell content header in bytes */ - u16 nLocal; /* Amount of payload held locally */ - u16 iOverflow; /* Offset to overflow page number. Zero if no overflow */ + i64 nKey; /* The key for INTKEY tables, or nPayload otherwise */ + u8 *pPayload; /* Pointer to the start of payload */ + u32 nPayload; /* Bytes of payload */ + u16 nLocal; /* Amount of payload held locally, not on overflow */ u16 nSize; /* Size of the cell content on the main b-tree page */ }; @@ -50700,23 +54620,35 @@ struct CellInfo { ** ** Fields in this structure are accessed under the BtShared.mutex ** found at self->pBt->mutex. +** +** skipNext meaning: +** eState==SKIPNEXT && skipNext>0: Next sqlite3BtreeNext() is no-op. +** eState==SKIPNEXT && skipNext<0: Next sqlite3BtreePrevious() is no-op. +** eState==FAULT: Cursor fault with skipNext as error code. */ struct BtCursor { Btree *pBtree; /* The Btree to which this cursor belongs */ BtShared *pBt; /* The BtShared this cursor points to */ - BtCursor *pNext, *pPrev; /* Forms a linked list of all cursors */ - struct KeyInfo *pKeyInfo; /* Argument passed to comparison function */ + BtCursor *pNext; /* Forms a linked list of all cursors */ Pgno *aOverflow; /* Cache of overflow page locations */ CellInfo info; /* A parse of the cell we are pointing at */ i64 nKey; /* Size of pKey, or last integer key */ void *pKey; /* Saved key that was cursor last known position */ Pgno pgnoRoot; /* The root page of this tree */ int nOvflAlloc; /* Allocated size of aOverflow[] array */ - int skipNext; /* Prev() is noop if negative. Next() is noop if positive */ + int skipNext; /* Prev() is noop if negative. Next() is noop if positive. + ** Error code if eState==CURSOR_FAULT */ u8 curFlags; /* zero or more BTCF_* flags defined below */ + u8 curPagerFlags; /* Flags to send to sqlite3PagerGet() */ u8 eState; /* One of the CURSOR_XXX constants (see below) */ - u8 hints; /* As configured by CursorSetHints() */ - i16 iPage; /* Index of current page in apPage */ + u8 hints; /* As configured by CursorSetHints() */ + /* All fields above are zeroed when the cursor is allocated. See + ** sqlite3BtreeCursorZero(). Fields that follow must be manually + ** initialized. */ + i8 iPage; /* Index of current page in apPage */ + u8 curIntKey; /* Value of apPage[0]->intKey */ + struct KeyInfo *pKeyInfo; /* Argument passed to comparison function */ + void *padding1; /* Make object size a multiple of 16 */ u16 aiIdx[BTCURSOR_MAX_DEPTH]; /* Current index in apPage[i] */ MemPage *apPage[BTCURSOR_MAX_DEPTH]; /* Pages from root to current page */ }; @@ -50729,6 +54661,7 @@ struct BtCursor { #define BTCF_ValidOvfl 0x04 /* True if aOverflow is valid */ #define BTCF_AtLast 0x08 /* Cursor is pointing ot the last entry */ #define BTCF_Incrblob 0x10 /* True if an incremental I/O handle */ +#define BTCF_Multiple 0x20 /* Maybe another cursor on the same btree */ /* ** Potential values for BtCursor.eState. @@ -50754,11 +54687,11 @@ struct BtCursor { ** seek the cursor to the saved position. ** ** CURSOR_FAULT: -** A unrecoverable error (an I/O error or a malloc failure) has occurred +** An unrecoverable error (an I/O error or a malloc failure) has occurred ** on a different connection that shares the BtShared cache with this ** cursor. The error has left the cache in an inconsistent state. ** Do nothing else with this cursor. Any attempt to use the cursor -** should return the error code stored in BtCursor.skip +** should return the error code stored in BtCursor.skipNext */ #define CURSOR_INVALID 0 #define CURSOR_VALID 1 @@ -50868,7 +54801,10 @@ struct IntegrityCk { int mxErr; /* Stop accumulating errors when this reaches zero */ int nErr; /* Number of messages written to zErrMsg so far */ int mallocFailed; /* A memory allocation error has occurred */ + const char *zPfx; /* Error message prefix */ + int v1, v2; /* Values for up to two %d fields in zPfx */ StrAccum errMsg; /* Accumulate the error message text here */ + u32 *heap; /* Min-heap used for analyzing cell coverage */ }; /* @@ -50879,6 +54815,23 @@ struct IntegrityCk { #define get4byte sqlite3Get4byte #define put4byte sqlite3Put4byte +/* +** get2byteAligned(), unlike get2byte(), requires that its argument point to a +** two-byte aligned address. get2bytea() is only used for accessing the +** cell addresses in a btree header. +*/ +#if SQLITE_BYTEORDER==4321 +# define get2byteAligned(x) (*(u16*)(x)) +#elif SQLITE_BYTEORDER==1234 && !defined(SQLITE_DISABLE_INTRINSIC) \ + && GCC_VERSION>=4008000 +# define get2byteAligned(x) __builtin_bswap16(*(u16*)(x)) +#elif SQLITE_BYTEORDER==1234 && !defined(SQLITE_DISABLE_INTRINSIC) \ + && defined(_MSC_VER) && _MSC_VER>=1300 +# define get2byteAligned(x) _byteswap_ushort(*(u16*)(x)) +#else +# define get2byteAligned(x) ((x)[0]<<8 | (x)[1]) +#endif + /************** End of btreeInt.h ********************************************/ /************** Continuing where we left off in btmutex.c ********************/ #ifndef SQLITE_OMIT_SHARED_CACHE @@ -50903,7 +54856,7 @@ static void lockBtreeMutex(Btree *p){ ** Release the BtShared mutex associated with B-Tree handle p and ** clear the p->locked boolean. */ -static void unlockBtreeMutex(Btree *p){ +static void SQLITE_NOINLINE unlockBtreeMutex(Btree *p){ BtShared *pBt = p->pBt; assert( p->locked==1 ); assert( sqlite3_mutex_held(pBt->mutex) ); @@ -50914,6 +54867,9 @@ static void unlockBtreeMutex(Btree *p){ p->locked = 0; } +/* Forward reference */ +static void SQLITE_NOINLINE btreeLockCarefully(Btree *p); + /* ** Enter a mutex on the given BTree object. ** @@ -50931,8 +54887,6 @@ static void unlockBtreeMutex(Btree *p){ ** subsequent Btrees that desire a lock. */ SQLITE_PRIVATE void sqlite3BtreeEnter(Btree *p){ - Btree *pLater; - /* Some basic sanity checking on the Btree. The list of Btrees ** connected by pNext and pPrev should be in sorted order by ** Btree.pBt value. All elements of the list should belong to @@ -50957,9 +54911,20 @@ SQLITE_PRIVATE void sqlite3BtreeEnter(Btree *p){ if( !p->sharable ) return; p->wantToLock++; if( p->locked ) return; + btreeLockCarefully(p); +} + +/* This is a helper function for sqlite3BtreeLock(). By moving +** complex, but seldom used logic, out of sqlite3BtreeLock() and +** into this routine, we avoid unnecessary stack pointer changes +** and thus help the sqlite3BtreeLock() routine to run much faster +** in the common case. +*/ +static void SQLITE_NOINLINE btreeLockCarefully(Btree *p){ + Btree *pLater; /* In most cases, we should be able to acquire the lock we - ** want without having to go throught the ascending lock + ** want without having to go through the ascending lock ** procedure that follows. Just be sure not to block. */ if( sqlite3_mutex_try(p->pBt->mutex)==SQLITE_OK ){ @@ -50989,10 +54954,12 @@ SQLITE_PRIVATE void sqlite3BtreeEnter(Btree *p){ } } + /* ** Exit the recursive mutex on a Btree. */ SQLITE_PRIVATE void sqlite3BtreeLeave(Btree *p){ + assert( sqlite3_mutex_held(p->db->mutex) ); if( p->sharable ){ assert( p->wantToLock>0 ); p->wantToLock--; @@ -51164,10 +55131,11 @@ SQLITE_PRIVATE void sqlite3BtreeEnterAll(sqlite3 *db){ ** May you share freely, never taking more than you give. ** ************************************************************************* -** This file implements a external (disk-based) database using BTrees. +** This file implements an external (disk-based) database using BTrees. ** See the header comment on "btreeInt.h" for additional information. ** Including a description of file format and an overview of operation. */ +/* #include "btreeInt.h" */ /* ** The header string that appears at the beginning of every @@ -51240,7 +55208,7 @@ static BtShared *SQLITE_WSD sqlite3SharedCacheList = 0; ** The shared cache setting effects only future calls to ** sqlite3_open(), sqlite3_open16(), or sqlite3_open_v2(). */ -SQLITE_API int sqlite3_enable_shared_cache(int enable){ +SQLITE_API int SQLITE_STDCALL sqlite3_enable_shared_cache(int enable){ sqlite3GlobalConfig.sharedCacheEnabled = enable; return SQLITE_OK; } @@ -51316,7 +55284,7 @@ static int hasSharedCacheTableLock( ** the correct locks are held. So do not bother - just return true. ** This case does not come up very often anyhow. */ - if( isIndex && (!pSchema || (pSchema->flags&DB_SchemaLoaded)==0) ){ + if( isIndex && (!pSchema || (pSchema->schemaFlags&DB_SchemaLoaded)==0) ){ return 1; } @@ -51329,6 +55297,12 @@ static int hasSharedCacheTableLock( for(p=sqliteHashFirst(&pSchema->idxHash); p; p=sqliteHashNext(p)){ Index *pIdx = (Index *)sqliteHashData(p); if( pIdx->tnum==(int)iRoot ){ + if( iTab ){ + /* Two or more indexes share the same root page. There must + ** be imposter tables. So just return true. The assert is not + ** useful in that case. */ + return 1; + } iTab = pIdx->pTable->tnum; } } @@ -51638,11 +55612,15 @@ static void invalidateIncrblobCursors( int isClearTable /* True if all rows are being deleted */ ){ BtCursor *p; - BtShared *pBt = pBtree->pBt; + if( pBtree->hasIncrblobCur==0 ) return; assert( sqlite3BtreeHoldsMutex(pBtree) ); - for(p=pBt->pCursor; p; p=p->pNext){ - if( (p->curFlags & BTCF_Incrblob)!=0 && (isClearTable || p->info.nKey==iRow) ){ - p->eState = CURSOR_INVALID; + pBtree->hasIncrblobCur = 0; + for(p=pBtree->pBt->pCursor; p; p=p->pNext){ + if( (p->curFlags & BTCF_Incrblob)!=0 ){ + pBtree->hasIncrblobCur = 1; + if( isClearTable || p->info.nKey==iRow ){ + p->eState = CURSOR_INVALID; + } } } } @@ -51735,17 +55713,21 @@ static void btreeReleaseAllCursorPages(BtCursor *pCur){ pCur->iPage = -1; } - /* -** Save the current cursor position in the variables BtCursor.nKey -** and BtCursor.pKey. The cursor's state is set to CURSOR_REQUIRESEEK. +** The cursor passed as the only argument must point to a valid entry +** when this function is called (i.e. have eState==CURSOR_VALID). This +** function saves the current cursor key in variables pCur->nKey and +** pCur->pKey. SQLITE_OK is returned if successful or an SQLite error +** code otherwise. ** -** The caller must ensure that the cursor is valid (has eState==CURSOR_VALID) -** prior to calling this routine. +** If the cursor is open on an intkey table, then the integer key +** (the rowid) is stored in pCur->nKey and pCur->pKey is left set to +** NULL. If the cursor is open on a non-intkey table, then pCur->pKey is +** set to point to a malloced buffer pCur->nKey bytes in size containing +** the key. */ -static int saveCursorPosition(BtCursor *pCur){ +static int saveCursorKey(BtCursor *pCur){ int rc; - assert( CURSOR_VALID==pCur->eState ); assert( 0==pCur->pKey ); assert( cursorHoldsMutex(pCur) ); @@ -51757,10 +55739,9 @@ static int saveCursorPosition(BtCursor *pCur){ ** stores the integer key in pCur->nKey. In this case this value is ** all that is required. Otherwise, if pCur is not open on an intKey ** table, then malloc space for and store the pCur->nKey bytes of key - ** data. - */ - if( 0==pCur->apPage[0]->intKey ){ - void *pKey = sqlite3Malloc( (int)pCur->nKey ); + ** data. */ + if( 0==pCur->curIntKey ){ + void *pKey = sqlite3Malloc( pCur->nKey ); if( pKey ){ rc = sqlite3BtreeKey(pCur, 0, (int)pCur->nKey, pKey); if( rc==SQLITE_OK ){ @@ -51772,29 +55753,89 @@ static int saveCursorPosition(BtCursor *pCur){ rc = SQLITE_NOMEM; } } - assert( !pCur->apPage[0]->intKey || !pCur->pKey ); + assert( !pCur->curIntKey || !pCur->pKey ); + return rc; +} +/* +** Save the current cursor position in the variables BtCursor.nKey +** and BtCursor.pKey. The cursor's state is set to CURSOR_REQUIRESEEK. +** +** The caller must ensure that the cursor is valid (has eState==CURSOR_VALID) +** prior to calling this routine. +*/ +static int saveCursorPosition(BtCursor *pCur){ + int rc; + + assert( CURSOR_VALID==pCur->eState || CURSOR_SKIPNEXT==pCur->eState ); + assert( 0==pCur->pKey ); + assert( cursorHoldsMutex(pCur) ); + + if( pCur->eState==CURSOR_SKIPNEXT ){ + pCur->eState = CURSOR_VALID; + }else{ + pCur->skipNext = 0; + } + + rc = saveCursorKey(pCur); if( rc==SQLITE_OK ){ btreeReleaseAllCursorPages(pCur); pCur->eState = CURSOR_REQUIRESEEK; } - invalidateOverflowCache(pCur); + pCur->curFlags &= ~(BTCF_ValidNKey|BTCF_ValidOvfl|BTCF_AtLast); return rc; } +/* Forward reference */ +static int SQLITE_NOINLINE saveCursorsOnList(BtCursor*,Pgno,BtCursor*); + /* ** Save the positions of all cursors (except pExcept) that are open on -** the table with root-page iRoot. Usually, this is called just before cursor -** pExcept is used to modify the table (BtreeDelete() or BtreeInsert()). +** the table with root-page iRoot. "Saving the cursor position" means that +** the location in the btree is remembered in such a way that it can be +** moved back to the same spot after the btree has been modified. This +** routine is called just before cursor pExcept is used to modify the +** table, for example in BtreeDelete() or BtreeInsert(). +** +** If there are two or more cursors on the same btree, then all such +** cursors should have their BTCF_Multiple flag set. The btreeCursor() +** routine enforces that rule. This routine only needs to be called in +** the uncommon case when pExpect has the BTCF_Multiple flag set. +** +** If pExpect!=NULL and if no other cursors are found on the same root-page, +** then the BTCF_Multiple flag on pExpect is cleared, to avoid another +** pointless call to this routine. +** +** Implementation note: This routine merely checks to see if any cursors +** need to be saved. It calls out to saveCursorsOnList() in the (unusual) +** event that cursors are in need to being saved. */ static int saveAllCursors(BtShared *pBt, Pgno iRoot, BtCursor *pExcept){ BtCursor *p; assert( sqlite3_mutex_held(pBt->mutex) ); assert( pExcept==0 || pExcept->pBt==pBt ); for(p=pBt->pCursor; p; p=p->pNext){ + if( p!=pExcept && (0==iRoot || p->pgnoRoot==iRoot) ) break; + } + if( p ) return saveCursorsOnList(p, iRoot, pExcept); + if( pExcept ) pExcept->curFlags &= ~BTCF_Multiple; + return SQLITE_OK; +} + +/* This helper routine to saveAllCursors does the actual work of saving +** the cursors if and when a cursor is found that actually requires saving. +** The common case is that no cursors need to be saved, so this routine is +** broken out from its caller to avoid unnecessary stack pointer movement. +*/ +static int SQLITE_NOINLINE saveCursorsOnList( + BtCursor *p, /* The first cursor that needs saving */ + Pgno iRoot, /* Only save cursor with this iRoot. Save all if zero */ + BtCursor *pExcept /* Do not save this cursor */ +){ + do{ if( p!=pExcept && (0==iRoot || p->pgnoRoot==iRoot) ){ - if( p->eState==CURSOR_VALID ){ + if( p->eState==CURSOR_VALID || p->eState==CURSOR_SKIPNEXT ){ int rc = saveCursorPosition(p); if( SQLITE_OK!=rc ){ return rc; @@ -51804,7 +55845,8 @@ static int saveAllCursors(BtShared *pBt, Pgno iRoot, BtCursor *pExcept){ btreeReleaseAllCursorPages(p); } } - } + p = p->pNext; + }while( p ); return SQLITE_OK; } @@ -51865,17 +55907,19 @@ static int btreeMoveto( */ static int btreeRestoreCursorPosition(BtCursor *pCur){ int rc; + int skipNext; assert( cursorHoldsMutex(pCur) ); assert( pCur->eState>=CURSOR_REQUIRESEEK ); if( pCur->eState==CURSOR_FAULT ){ return pCur->skipNext; } pCur->eState = CURSOR_INVALID; - rc = btreeMoveto(pCur, pCur->pKey, pCur->nKey, 0, &pCur->skipNext); + rc = btreeMoveto(pCur, pCur->pKey, pCur->nKey, 0, &skipNext); if( rc==SQLITE_OK ){ sqlite3_free(pCur->pKey); pCur->pKey = 0; assert( pCur->eState==CURSOR_VALID || pCur->eState==CURSOR_INVALID ); + pCur->skipNext |= skipNext; if( pCur->skipNext && pCur->eState==CURSOR_VALID ){ pCur->eState = CURSOR_SKIPNEXT; } @@ -51889,41 +55933,73 @@ static int btreeRestoreCursorPosition(BtCursor *pCur){ SQLITE_OK) /* -** Determine whether or not a cursor has moved from the position it -** was last placed at. Cursors can move when the row they are pointing -** at is deleted out from under them. +** Determine whether or not a cursor has moved from the position where +** it was last placed, or has been invalidated for any other reason. +** Cursors can move when the row they are pointing at is deleted out +** from under them, for example. Cursor might also move if a btree +** is rebalanced. ** -** This routine returns an error code if something goes wrong. The -** integer *pHasMoved is set as follows: +** Calling this routine with a NULL cursor pointer returns false. ** -** 0: The cursor is unchanged -** 1: The cursor is still pointing at the same row, but the pointers -** returned by sqlite3BtreeKeyFetch() or sqlite3BtreeDataFetch() -** might now be invalid because of a balance() or other change to the -** b-tree. -** 2: The cursor is no longer pointing to the row. The row might have -** been deleted out from under the cursor. +** Use the separate sqlite3BtreeCursorRestore() routine to restore a cursor +** back to where it ought to be if this routine returns true. */ -SQLITE_PRIVATE int sqlite3BtreeCursorHasMoved(BtCursor *pCur, int *pHasMoved){ +SQLITE_PRIVATE int sqlite3BtreeCursorHasMoved(BtCursor *pCur){ + return pCur->eState!=CURSOR_VALID; +} + +/* +** This routine restores a cursor back to its original position after it +** has been moved by some outside activity (such as a btree rebalance or +** a row having been deleted out from under the cursor). +** +** On success, the *pDifferentRow parameter is false if the cursor is left +** pointing at exactly the same row. *pDifferntRow is the row the cursor +** was pointing to has been deleted, forcing the cursor to point to some +** nearby row. +** +** This routine should only be called for a cursor that just returned +** TRUE from sqlite3BtreeCursorHasMoved(). +*/ +SQLITE_PRIVATE int sqlite3BtreeCursorRestore(BtCursor *pCur, int *pDifferentRow){ int rc; - if( pCur->eState==CURSOR_VALID ){ - *pHasMoved = 0; - return SQLITE_OK; - } + assert( pCur!=0 ); + assert( pCur->eState!=CURSOR_VALID ); rc = restoreCursorPosition(pCur); if( rc ){ - *pHasMoved = 2; + *pDifferentRow = 1; return rc; } - if( pCur->eState!=CURSOR_VALID || NEVER(pCur->skipNext!=0) ){ - *pHasMoved = 2; + if( pCur->eState!=CURSOR_VALID ){ + *pDifferentRow = 1; }else{ - *pHasMoved = 1; + assert( pCur->skipNext==0 ); + *pDifferentRow = 0; } return SQLITE_OK; } +#ifdef SQLITE_ENABLE_CURSOR_HINTS +/* +** Provide hints to the cursor. The particular hint given (and the type +** and number of the varargs parameters) is determined by the eHintType +** parameter. See the definitions of the BTREE_HINT_* macros for details. +*/ +SQLITE_PRIVATE void sqlite3BtreeCursorHint(BtCursor *pCur, int eHintType, ...){ + /* Used only by system that substitute their own storage engine */ +} +#endif + +/* +** Provide flag hints to the cursor. +*/ +SQLITE_PRIVATE void sqlite3BtreeCursorHintFlags(BtCursor *pCur, unsigned x){ + assert( x==BTREE_SEEK_EQ || x==BTREE_BULKLOAD || x==0 ); + pCur->hints = x; +} + + #ifndef SQLITE_OMIT_AUTOVACUUM /* ** Given a page number of a regular database page, return the page @@ -51977,7 +56053,7 @@ static void ptrmapPut(BtShared *pBt, Pgno key, u8 eType, Pgno parent, int *pRC){ return; } iPtrmap = PTRMAP_PAGENO(pBt, key); - rc = sqlite3PagerGet(pBt->pPager, iPtrmap, &pDbPage); + rc = sqlite3PagerGet(pBt->pPager, iPtrmap, &pDbPage, 0); if( rc!=SQLITE_OK ){ *pRC = rc; return; @@ -52020,7 +56096,7 @@ static int ptrmapGet(BtShared *pBt, Pgno key, u8 *pEType, Pgno *pPgno){ assert( sqlite3_mutex_held(pBt->mutex) ); iPtrmap = PTRMAP_PAGENO(pBt, key); - rc = sqlite3PagerGet(pBt->pPager, iPtrmap, &pDbPage); + rc = sqlite3PagerGet(pBt->pPager, iPtrmap, &pDbPage, 0); if( rc!=0 ){ return rc; } @@ -52052,128 +56128,218 @@ static int ptrmapGet(BtShared *pBt, Pgno key, u8 *pEType, Pgno *pPgno){ ** the page, 1 means the second cell, and so forth) return a pointer ** to the cell content. ** +** findCellPastPtr() does the same except it skips past the initial +** 4-byte child pointer found on interior pages, if there is one. +** ** This routine works only for pages that do not contain overflow cells. */ #define findCell(P,I) \ - ((P)->aData + ((P)->maskPage & get2byte(&(P)->aCellIdx[2*(I)]))) -#define findCellv2(D,M,O,I) (D+(M&get2byte(D+(O+2*(I))))) + ((P)->aData + ((P)->maskPage & get2byteAligned(&(P)->aCellIdx[2*(I)]))) +#define findCellPastPtr(P,I) \ + ((P)->aDataOfst + ((P)->maskPage & get2byteAligned(&(P)->aCellIdx[2*(I)]))) /* -** This a more complex version of findCell() that works for -** pages that do contain overflow cells. +** This is common tail processing for btreeParseCellPtr() and +** btreeParseCellPtrIndex() for the case when the cell does not fit entirely +** on a single B-tree page. Make necessary adjustments to the CellInfo +** structure. */ -static u8 *findOverflowCell(MemPage *pPage, int iCell){ - int i; - assert( sqlite3_mutex_held(pPage->pBt->mutex) ); - for(i=pPage->nOverflow-1; i>=0; i--){ - int k; - k = pPage->aiOvfl[i]; - if( k<=iCell ){ - if( k==iCell ){ - return pPage->apOvfl[i]; - } - iCell--; - } +static SQLITE_NOINLINE void btreeParseCellAdjustSizeForOverflow( + MemPage *pPage, /* Page containing the cell */ + u8 *pCell, /* Pointer to the cell text. */ + CellInfo *pInfo /* Fill in this structure */ +){ + /* If the payload will not fit completely on the local page, we have + ** to decide how much to store locally and how much to spill onto + ** overflow pages. The strategy is to minimize the amount of unused + ** space on overflow pages while keeping the amount of local storage + ** in between minLocal and maxLocal. + ** + ** Warning: changing the way overflow payload is distributed in any + ** way will result in an incompatible file format. + */ + int minLocal; /* Minimum amount of payload held locally */ + int maxLocal; /* Maximum amount of payload held locally */ + int surplus; /* Overflow payload available for local storage */ + + minLocal = pPage->minLocal; + maxLocal = pPage->maxLocal; + surplus = minLocal + (pInfo->nPayload - minLocal)%(pPage->pBt->usableSize-4); + testcase( surplus==maxLocal ); + testcase( surplus==maxLocal+1 ); + if( surplus <= maxLocal ){ + pInfo->nLocal = (u16)surplus; + }else{ + pInfo->nLocal = (u16)minLocal; } - return findCell(pPage, iCell); + pInfo->nSize = (u16)(&pInfo->pPayload[pInfo->nLocal] - pCell) + 4; } /* -** Parse a cell content block and fill in the CellInfo structure. There -** are two versions of this function. btreeParseCell() takes a -** cell index as the second argument and btreeParseCellPtr() -** takes a pointer to the body of the cell as its second argument. +** The following routines are implementations of the MemPage.xParseCell() +** method. ** -** Within this file, the parseCell() macro can be called instead of -** btreeParseCellPtr(). Using some compilers, this will be faster. +** Parse a cell content block and fill in the CellInfo structure. +** +** btreeParseCellPtr() => table btree leaf nodes +** btreeParseCellNoPayload() => table btree internal nodes +** btreeParseCellPtrIndex() => index btree nodes +** +** There is also a wrapper function btreeParseCell() that works for +** all MemPage types and that references the cell by index rather than +** by pointer. */ +static void btreeParseCellPtrNoPayload( + MemPage *pPage, /* Page containing the cell */ + u8 *pCell, /* Pointer to the cell text. */ + CellInfo *pInfo /* Fill in this structure */ +){ + assert( sqlite3_mutex_held(pPage->pBt->mutex) ); + assert( pPage->leaf==0 ); + assert( pPage->noPayload ); + assert( pPage->childPtrSize==4 ); +#ifndef SQLITE_DEBUG + UNUSED_PARAMETER(pPage); +#endif + pInfo->nSize = 4 + getVarint(&pCell[4], (u64*)&pInfo->nKey); + pInfo->nPayload = 0; + pInfo->nLocal = 0; + pInfo->pPayload = 0; + return; +} static void btreeParseCellPtr( MemPage *pPage, /* Page containing the cell */ u8 *pCell, /* Pointer to the cell text. */ CellInfo *pInfo /* Fill in this structure */ ){ - u16 n; /* Number bytes in cell content header */ + u8 *pIter; /* For scanning through pCell */ u32 nPayload; /* Number of bytes of cell payload */ + u64 iKey; /* Extracted Key value */ assert( sqlite3_mutex_held(pPage->pBt->mutex) ); - - pInfo->pCell = pCell; assert( pPage->leaf==0 || pPage->leaf==1 ); - n = pPage->childPtrSize; - assert( n==4-4*pPage->leaf ); - if( pPage->intKey ){ - if( pPage->hasData ){ - assert( n==0 ); - n = getVarint32(pCell, nPayload); - }else{ - nPayload = 0; - } - n += getVarint(&pCell[n], (u64*)&pInfo->nKey); - pInfo->nData = nPayload; - }else{ - pInfo->nData = 0; - n += getVarint32(&pCell[n], nPayload); - pInfo->nKey = nPayload; + assert( pPage->intKeyLeaf || pPage->noPayload ); + assert( pPage->noPayload==0 ); + assert( pPage->intKeyLeaf ); + assert( pPage->childPtrSize==0 ); + pIter = pCell; + + /* The next block of code is equivalent to: + ** + ** pIter += getVarint32(pIter, nPayload); + ** + ** The code is inlined to avoid a function call. + */ + nPayload = *pIter; + if( nPayload>=0x80 ){ + u8 *pEnd = &pIter[8]; + nPayload &= 0x7f; + do{ + nPayload = (nPayload<<7) | (*++pIter & 0x7f); + }while( (*pIter)>=0x80 && pIternKey); + ** + ** The code is inlined to avoid a function call. + */ + iKey = *pIter; + if( iKey>=0x80 ){ + u8 *pEnd = &pIter[7]; + iKey &= 0x7f; + while(1){ + iKey = (iKey<<7) | (*++pIter & 0x7f); + if( (*pIter)<0x80 ) break; + if( pIter>=pEnd ){ + iKey = (iKey<<8) | *++pIter; + break; + } + } + } + pIter++; + + pInfo->nKey = *(i64*)&iKey; pInfo->nPayload = nPayload; - pInfo->nHeader = n; + pInfo->pPayload = pIter; testcase( nPayload==pPage->maxLocal ); testcase( nPayload==pPage->maxLocal+1 ); - if( likely(nPayload<=pPage->maxLocal) ){ + if( nPayload<=pPage->maxLocal ){ /* This is the (easy) common case where the entire payload fits ** on the local page. No overflow is required. */ - if( (pInfo->nSize = (u16)(n+nPayload))<4 ) pInfo->nSize = 4; + pInfo->nSize = nPayload + (u16)(pIter - pCell); + if( pInfo->nSize<4 ) pInfo->nSize = 4; pInfo->nLocal = (u16)nPayload; - pInfo->iOverflow = 0; }else{ - /* If the payload will not fit completely on the local page, we have - ** to decide how much to store locally and how much to spill onto - ** overflow pages. The strategy is to minimize the amount of unused - ** space on overflow pages while keeping the amount of local storage - ** in between minLocal and maxLocal. - ** - ** Warning: changing the way overflow payload is distributed in any - ** way will result in an incompatible file format. + btreeParseCellAdjustSizeForOverflow(pPage, pCell, pInfo); + } +} +static void btreeParseCellPtrIndex( + MemPage *pPage, /* Page containing the cell */ + u8 *pCell, /* Pointer to the cell text. */ + CellInfo *pInfo /* Fill in this structure */ +){ + u8 *pIter; /* For scanning through pCell */ + u32 nPayload; /* Number of bytes of cell payload */ + + assert( sqlite3_mutex_held(pPage->pBt->mutex) ); + assert( pPage->leaf==0 || pPage->leaf==1 ); + assert( pPage->intKeyLeaf==0 ); + assert( pPage->noPayload==0 ); + pIter = pCell + pPage->childPtrSize; + nPayload = *pIter; + if( nPayload>=0x80 ){ + u8 *pEnd = &pIter[8]; + nPayload &= 0x7f; + do{ + nPayload = (nPayload<<7) | (*++pIter & 0x7f); + }while( *(pIter)>=0x80 && pIternKey = nPayload; + pInfo->nPayload = nPayload; + pInfo->pPayload = pIter; + testcase( nPayload==pPage->maxLocal ); + testcase( nPayload==pPage->maxLocal+1 ); + if( nPayload<=pPage->maxLocal ){ + /* This is the (easy) common case where the entire payload fits + ** on the local page. No overflow is required. */ - int minLocal; /* Minimum amount of payload held locally */ - int maxLocal; /* Maximum amount of payload held locally */ - int surplus; /* Overflow payload available for local storage */ - - minLocal = pPage->minLocal; - maxLocal = pPage->maxLocal; - surplus = minLocal + (nPayload - minLocal)%(pPage->pBt->usableSize - 4); - testcase( surplus==maxLocal ); - testcase( surplus==maxLocal+1 ); - if( surplus <= maxLocal ){ - pInfo->nLocal = (u16)surplus; - }else{ - pInfo->nLocal = (u16)minLocal; - } - pInfo->iOverflow = (u16)(pInfo->nLocal + n); - pInfo->nSize = pInfo->iOverflow + 4; + pInfo->nSize = nPayload + (u16)(pIter - pCell); + if( pInfo->nSize<4 ) pInfo->nSize = 4; + pInfo->nLocal = (u16)nPayload; + }else{ + btreeParseCellAdjustSizeForOverflow(pPage, pCell, pInfo); } } -#define parseCell(pPage, iCell, pInfo) \ - btreeParseCellPtr((pPage), findCell((pPage), (iCell)), (pInfo)) static void btreeParseCell( MemPage *pPage, /* Page containing the cell */ int iCell, /* The cell index. First cell is 0 */ CellInfo *pInfo /* Fill in this structure */ ){ - parseCell(pPage, iCell, pInfo); + pPage->xParseCell(pPage, findCell(pPage, iCell), pInfo); } /* +** The following routines are implementations of the MemPage.xCellSize +** method. +** ** Compute the total number of bytes that a Cell needs in the cell ** data area of the btree-page. The return number includes the cell ** data header and the local payload, but not any overflow page or ** the space used by the cell pointer. +** +** cellSizePtrNoPayload() => table internal nodes +** cellSizePtr() => all index nodes & table leaf nodes */ static u16 cellSizePtr(MemPage *pPage, u8 *pCell){ - u8 *pIter = &pCell[pPage->childPtrSize]; - u32 nSize; + u8 *pIter = pCell + pPage->childPtrSize; /* For looping over bytes of pCell */ + u8 *pEnd; /* End mark for a varint */ + u32 nSize; /* Size value to return */ #ifdef SQLITE_DEBUG /* The value returned by this function should always be the same as @@ -52181,29 +56347,32 @@ static u16 cellSizePtr(MemPage *pPage, u8 *pCell){ ** cell. If SQLITE_DEBUG is defined, an assert() at the bottom of ** this function verifies that this invariant is not violated. */ CellInfo debuginfo; - btreeParseCellPtr(pPage, pCell, &debuginfo); + pPage->xParseCell(pPage, pCell, &debuginfo); #endif + assert( pPage->noPayload==0 ); + nSize = *pIter; + if( nSize>=0x80 ){ + pEnd = &pIter[8]; + nSize &= 0x7f; + do{ + nSize = (nSize<<7) | (*++pIter & 0x7f); + }while( *(pIter)>=0x80 && pIterintKey ){ - u8 *pEnd; - if( pPage->hasData ){ - pIter += getVarint32(pIter, nSize); - }else{ - nSize = 0; - } - /* pIter now points at the 64-bit integer key value, a variable length ** integer. The following block moves pIter to point at the first byte ** past the end of the key value. */ pEnd = &pIter[9]; while( (*pIter++)&0x80 && pItermaxLocal ); testcase( nSize==pPage->maxLocal+1 ); - if( nSize>pPage->maxLocal ){ + if( nSize<=pPage->maxLocal ){ + nSize += (u32)(pIter - pCell); + if( nSize<4 ) nSize = 4; + }else{ int minLocal = pPage->minLocal; nSize = minLocal + (nSize - minLocal) % (pPage->pBt->usableSize - 4); testcase( nSize==pPage->maxLocal ); @@ -52211,24 +56380,39 @@ static u16 cellSizePtr(MemPage *pPage, u8 *pCell){ if( nSize>pPage->maxLocal ){ nSize = minLocal; } - nSize += 4; + nSize += 4 + (u16)(pIter - pCell); } - nSize += (u32)(pIter - pCell); - - /* The minimum size of any cell is 4 bytes. */ - if( nSize<4 ){ - nSize = 4; - } - - assert( nSize==debuginfo.nSize ); + assert( nSize==debuginfo.nSize || CORRUPT_DB ); return (u16)nSize; } +static u16 cellSizePtrNoPayload(MemPage *pPage, u8 *pCell){ + u8 *pIter = pCell + 4; /* For looping over bytes of pCell */ + u8 *pEnd; /* End mark for a varint */ + +#ifdef SQLITE_DEBUG + /* The value returned by this function should always be the same as + ** the (CellInfo.nSize) value found by doing a full parse of the + ** cell. If SQLITE_DEBUG is defined, an assert() at the bottom of + ** this function verifies that this invariant is not violated. */ + CellInfo debuginfo; + pPage->xParseCell(pPage, pCell, &debuginfo); +#else + UNUSED_PARAMETER(pPage); +#endif + + assert( pPage->childPtrSize==4 ); + pEnd = pIter + 9; + while( (*pIter++)&0x80 && pIterxCellSize(pPage, findCell(pPage, iCell)); } #endif @@ -52242,10 +56426,9 @@ static void ptrmapPutOvflPtr(MemPage *pPage, u8 *pCell, int *pRC){ CellInfo info; if( *pRC ) return; assert( pCell!=0 ); - btreeParseCellPtr(pPage, pCell, &info); - assert( (info.nData+(pPage->intKey?0:info.nKey))==info.nPayload ); - if( info.iOverflow ){ - Pgno ovfl = get4byte(&pCell[info.iOverflow]); + pPage->xParseCell(pPage, pCell, &info); + if( info.nLocalpBt, ovfl, PTRMAP_OVERFLOW1, pPage->pgno, pRC); } } @@ -52257,10 +56440,15 @@ static void ptrmapPutOvflPtr(MemPage *pPage, u8 *pCell, int *pRC){ ** end of the page and all free space is collected into one ** big FreeBlk that occurs in between the header and cell ** pointer array and the cell content area. +** +** EVIDENCE-OF: R-44582-60138 SQLite may from time to time reorganize a +** b-tree page so that there are no freeblocks or fragment bytes, all +** unused bytes are contained in the unallocated space region, and all +** cells are packed tightly at the end of the page. */ static int defragmentPage(MemPage *pPage){ int i; /* Loop counter */ - int pc; /* Address of a i-th cell */ + int pc; /* Address of the i-th cell */ int hdr; /* Offset to the page header */ int size; /* Size of a cell */ int usableSize; /* Number of usable bytes on a page */ @@ -52269,6 +56457,7 @@ static int defragmentPage(MemPage *pPage){ int nCell; /* Number of cells on the page */ unsigned char *data; /* The page data */ unsigned char *temp; /* Temp area for cell content */ + unsigned char *src; /* Source of content */ int iCellFirst; /* First allowable cell index */ int iCellLast; /* Last possible cell index */ @@ -52278,15 +56467,13 @@ static int defragmentPage(MemPage *pPage){ assert( pPage->pBt->usableSize <= SQLITE_MAX_PAGE_SIZE ); assert( pPage->nOverflow==0 ); assert( sqlite3_mutex_held(pPage->pBt->mutex) ); - temp = sqlite3PagerTempSpace(pPage->pBt->pPager); - data = pPage->aData; + temp = 0; + src = data = pPage->aData; hdr = pPage->hdrOffset; cellOffset = pPage->cellOffset; nCell = pPage->nCell; assert( nCell==get2byte(&data[hdr+3]) ); usableSize = pPage->pBt->usableSize; - cbrk = get2byte(&data[hdr+5]); - memcpy(&temp[cbrk], &data[cbrk], usableSize - cbrk); cbrk = usableSize; iCellFirst = cellOffset + 2*nCell; iCellLast = usableSize - 4; @@ -52296,31 +56483,31 @@ static int defragmentPage(MemPage *pPage){ pc = get2byte(pAddr); testcase( pc==iCellFirst ); testcase( pc==iCellLast ); -#if !defined(SQLITE_ENABLE_OVERSIZE_CELL_CHECK) /* These conditions have already been verified in btreeInitPage() - ** if SQLITE_ENABLE_OVERSIZE_CELL_CHECK is defined + ** if PRAGMA cell_size_check=ON. */ if( pciCellLast ){ return SQLITE_CORRUPT_BKPT; } -#endif assert( pc>=iCellFirst && pc<=iCellLast ); - size = cellSizePtr(pPage, &temp[pc]); + size = pPage->xCellSize(pPage, &src[pc]); cbrk -= size; -#if defined(SQLITE_ENABLE_OVERSIZE_CELL_CHECK) - if( cbrkusableSize ){ return SQLITE_CORRUPT_BKPT; } -#endif assert( cbrk+size<=usableSize && cbrk>=iCellFirst ); testcase( cbrk+size==usableSize ); testcase( pc+size==usableSize ); - memcpy(&data[cbrk], &temp[pc], size); put2byte(pAddr, cbrk); + if( temp==0 ){ + int x; + if( cbrk==pc ) continue; + temp = sqlite3PagerTempSpace(pPage->pBt->pPager); + x = get2byte(&data[hdr+5]); + memcpy(&temp[x], &data[x], (cbrk+size) - x); + src = temp; + } + memcpy(&data[cbrk], &src[pc], size); } assert( cbrk>=iCellFirst ); put2byte(&data[hdr+5], cbrk); @@ -52335,6 +56522,70 @@ static int defragmentPage(MemPage *pPage){ return SQLITE_OK; } +/* +** Search the free-list on page pPg for space to store a cell nByte bytes in +** size. If one can be found, return a pointer to the space and remove it +** from the free-list. +** +** If no suitable space can be found on the free-list, return NULL. +** +** This function may detect corruption within pPg. If corruption is +** detected then *pRc is set to SQLITE_CORRUPT and NULL is returned. +** +** Slots on the free list that are between 1 and 3 bytes larger than nByte +** will be ignored if adding the extra space to the fragmentation count +** causes the fragmentation count to exceed 60. +*/ +static u8 *pageFindSlot(MemPage *pPg, int nByte, int *pRc){ + const int hdr = pPg->hdrOffset; + u8 * const aData = pPg->aData; + int iAddr = hdr + 1; + int pc = get2byte(&aData[iAddr]); + int x; + int usableSize = pPg->pBt->usableSize; + + assert( pc>0 ); + do{ + int size; /* Size of the free slot */ + /* EVIDENCE-OF: R-06866-39125 Freeblocks are always connected in order of + ** increasing offset. */ + if( pc>usableSize-4 || pc=0 ){ + testcase( x==4 ); + testcase( x==3 ); + if( pc < pPg->cellOffset+2*pPg->nCell || size+pc > usableSize ){ + *pRc = SQLITE_CORRUPT_BKPT; + return 0; + }else if( x<4 ){ + /* EVIDENCE-OF: R-11498-58022 In a well-formed b-tree page, the total + ** number of bytes in fragments may not exceed 60. */ + if( aData[hdr+7]>57 ) return 0; + + /* Remove the slot from the free-list. Update the number of + ** fragmented bytes within the page. */ + memcpy(&aData[iAddr], &aData[pc], 2); + aData[hdr+7] += (u8)x; + }else{ + /* The slot remains on the free-list. Reduce its size to account + ** for the portion used by the new allocation. */ + put2byte(&aData[pc+2], x); + } + return &aData[pc + x]; + } + iAddr = pc; + pc = get2byte(&aData[pc]); + }while( pc ); + + return 0; +} + /* ** Allocate nByte bytes of space from within the B-Tree page passed ** as the first argument. Write into *pIdx the index into pPage->aData[] @@ -52351,11 +56602,9 @@ static int defragmentPage(MemPage *pPage){ static int allocateSpace(MemPage *pPage, int nByte, int *pIdx){ const int hdr = pPage->hdrOffset; /* Local cache of pPage->hdrOffset */ u8 * const data = pPage->aData; /* Local cache of pPage->aData */ - int nFrag; /* Number of fragmented bytes on pPage */ int top; /* First byte of cell content area */ + int rc = SQLITE_OK; /* Integer return code */ int gap; /* First byte of gap between cell pointers and cell content */ - int rc; /* Integer return code */ - int usableSize; /* Usable size of the page */ assert( sqlite3PagerIswriteable(pPage->pDbPage) ); assert( pPage->pBt ); @@ -52363,62 +56612,50 @@ static int allocateSpace(MemPage *pPage, int nByte, int *pIdx){ assert( nByte>=0 ); /* Minimum cell size is 4 */ assert( pPage->nFree>=nByte ); assert( pPage->nOverflow==0 ); - usableSize = pPage->pBt->usableSize; - assert( nByte < usableSize-8 ); + assert( nByte < (int)(pPage->pBt->usableSize-8) ); - nFrag = data[hdr+7]; assert( pPage->cellOffset == hdr + 12 - 4*pPage->leaf ); gap = pPage->cellOffset + 2*pPage->nCell; - top = get2byteNotZero(&data[hdr+5]); - if( gap>top ) return SQLITE_CORRUPT_BKPT; - testcase( gap+2==top ); - testcase( gap+1==top ); - testcase( gap==top ); - - if( nFrag>=60 ){ - /* Always defragment highly fragmented pages */ - rc = defragmentPage(pPage); - if( rc ) return rc; - top = get2byteNotZero(&data[hdr+5]); - }else if( gap+2<=top ){ - /* Search the freelist looking for a free slot big enough to satisfy - ** the request. The allocation is made from the first free slot in - ** the list that is large enough to accommodate it. - */ - int pc, addr; - for(addr=hdr+1; (pc = get2byte(&data[addr]))>0; addr=pc){ - int size; /* Size of the free slot */ - if( pc>usableSize-4 || pc=nByte ){ - int x = size - nByte; - testcase( x==4 ); - testcase( x==3 ); - if( x<4 ){ - /* Remove the slot from the free-list. Update the number of - ** fragmented bytes within the page. */ - memcpy(&data[addr], &data[pc], 2); - data[hdr+7] = (u8)(nFrag + x); - }else if( size+pc > usableSize ){ - return SQLITE_CORRUPT_BKPT; - }else{ - /* The slot remains on the free-list. Reduce its size to account - ** for the portion used by the new allocation. */ - put2byte(&data[pc+2], x); - } - *pIdx = pc + x; - return SQLITE_OK; - } + assert( gap<=65536 ); + /* EVIDENCE-OF: R-29356-02391 If the database uses a 65536-byte page size + ** and the reserved space is zero (the usual value for reserved space) + ** then the cell content offset of an empty page wants to be 65536. + ** However, that integer is too large to be stored in a 2-byte unsigned + ** integer, so a value of 0 is used in its place. */ + top = get2byte(&data[hdr+5]); + assert( top<=(int)pPage->pBt->usableSize ); /* Prevent by getAndInitPage() */ + if( gap>top ){ + if( top==0 && pPage->pBt->usableSize==65536 ){ + top = 65536; + }else{ + return SQLITE_CORRUPT_BKPT; } } - /* Check to make sure there is enough space in the gap to satisfy - ** the allocation. If not, defragment. + /* If there is enough space between gap and top for one more cell pointer + ** array entry offset, and if the freelist is not empty, then search the + ** freelist looking for a free slot big enough to satisfy the request. + */ + testcase( gap+2==top ); + testcase( gap+1==top ); + testcase( gap==top ); + if( (data[hdr+2] || data[hdr+1]) && gap+2<=top ){ + u8 *pSpace = pageFindSlot(pPage, nByte, &rc); + if( pSpace ){ + assert( pSpace>=data && (pSpace - data)<65536 ); + *pIdx = (int)(pSpace - data); + return SQLITE_OK; + }else if( rc ){ + return rc; + } + } + + /* The request could not be fulfilled using a freelist slot. Check + ** to see if defragmentation is necessary. */ testcase( gap+2+nByte==top ); if( gap+2+nByte>top ){ + assert( pPage->nCell>0 || CORRUPT_DB ); rc = defragmentPage(pPage); if( rc ) return rc; top = get2byteNotZero(&data[hdr+5]); @@ -52441,90 +56678,101 @@ static int allocateSpace(MemPage *pPage, int nByte, int *pIdx){ /* ** Return a section of the pPage->aData to the freelist. -** The first byte of the new free block is pPage->aDisk[start] -** and the size of the block is "size" bytes. +** The first byte of the new free block is pPage->aData[iStart] +** and the size of the block is iSize bytes. ** -** Most of the effort here is involved in coalesing adjacent -** free blocks into a single big free block. +** Adjacent freeblocks are coalesced. +** +** Note that even though the freeblock list was checked by btreeInitPage(), +** that routine will not detect overlap between cells or freeblocks. Nor +** does it detect cells or freeblocks that encrouch into the reserved bytes +** at the end of the page. So do additional corruption checks inside this +** routine and return SQLITE_CORRUPT if any problems are found. */ -static int freeSpace(MemPage *pPage, int start, int size){ - int addr, pbegin, hdr; - int iLast; /* Largest possible freeblock offset */ - unsigned char *data = pPage->aData; +static int freeSpace(MemPage *pPage, u16 iStart, u16 iSize){ + u16 iPtr; /* Address of ptr to next freeblock */ + u16 iFreeBlk; /* Address of the next freeblock */ + u8 hdr; /* Page header size. 0 or 100 */ + u8 nFrag = 0; /* Reduction in fragmentation */ + u16 iOrigSize = iSize; /* Original value of iSize */ + u32 iLast = pPage->pBt->usableSize-4; /* Largest possible freeblock offset */ + u32 iEnd = iStart + iSize; /* First byte past the iStart buffer */ + unsigned char *data = pPage->aData; /* Page content */ assert( pPage->pBt!=0 ); assert( sqlite3PagerIswriteable(pPage->pDbPage) ); - assert( start>=pPage->hdrOffset+6+pPage->childPtrSize ); - assert( (start + size) <= (int)pPage->pBt->usableSize ); + assert( CORRUPT_DB || iStart>=pPage->hdrOffset+6+pPage->childPtrSize ); + assert( CORRUPT_DB || iEnd <= pPage->pBt->usableSize ); assert( sqlite3_mutex_held(pPage->pBt->mutex) ); - assert( size>=0 ); /* Minimum cell size is 4 */ + assert( iSize>=4 ); /* Minimum cell size is 4 */ + assert( iStart<=iLast ); + /* Overwrite deleted information with zeros when the secure_delete + ** option is enabled */ if( pPage->pBt->btsFlags & BTS_SECURE_DELETE ){ - /* Overwrite deleted information with zeros when the secure_delete - ** option is enabled */ - memset(&data[start], 0, size); + memset(&data[iStart], 0, iSize); } - /* Add the space back into the linked list of freeblocks. Note that - ** even though the freeblock list was checked by btreeInitPage(), - ** btreeInitPage() did not detect overlapping cells or - ** freeblocks that overlapped cells. Nor does it detect when the - ** cell content area exceeds the value in the page header. If these - ** situations arise, then subsequent insert operations might corrupt - ** the freelist. So we do need to check for corruption while scanning - ** the freelist. + /* The list of freeblocks must be in ascending order. Find the + ** spot on the list where iStart should be inserted. */ hdr = pPage->hdrOffset; - addr = hdr + 1; - iLast = pPage->pBt->usableSize - 4; - assert( start<=iLast ); - while( (pbegin = get2byte(&data[addr]))0 ){ - if( pbegin0 && iFreeBlkiLast ){ - return SQLITE_CORRUPT_BKPT; - } - assert( pbegin>addr || pbegin==0 ); - put2byte(&data[addr], start); - put2byte(&data[start], pbegin); - put2byte(&data[start+2], size); - pPage->nFree = pPage->nFree + (u16)size; - - /* Coalesce adjacent free blocks */ - addr = hdr + 1; - while( (pbegin = get2byte(&data[addr]))>0 ){ - int pnext, psize, x; - assert( pbegin>addr ); - assert( pbegin <= (int)pPage->pBt->usableSize-4 ); - pnext = get2byte(&data[pbegin]); - psize = get2byte(&data[pbegin+2]); - if( pbegin + psize + 3 >= pnext && pnext>0 ){ - int frag = pnext - (pbegin+psize); - if( (frag<0) || (frag>(int)data[hdr+7]) ){ - return SQLITE_CORRUPT_BKPT; + if( iFreeBlk>iLast ) return SQLITE_CORRUPT_BKPT; + assert( iFreeBlk>iPtr || iFreeBlk==0 ); + + /* At this point: + ** iFreeBlk: First freeblock after iStart, or zero if none + ** iPtr: The address of a pointer to iFreeBlk + ** + ** Check to see if iFreeBlk should be coalesced onto the end of iStart. + */ + if( iFreeBlk && iEnd+3>=iFreeBlk ){ + nFrag = iFreeBlk - iEnd; + if( iEnd>iFreeBlk ) return SQLITE_CORRUPT_BKPT; + iEnd = iFreeBlk + get2byte(&data[iFreeBlk+2]); + if( iEnd > pPage->pBt->usableSize ) return SQLITE_CORRUPT_BKPT; + iSize = iEnd - iStart; + iFreeBlk = get2byte(&data[iFreeBlk]); + } + + /* If iPtr is another freeblock (that is, if iPtr is not the freelist + ** pointer in the page header) then check to see if iStart should be + ** coalesced onto the end of iPtr. + */ + if( iPtr>hdr+1 ){ + int iPtrEnd = iPtr + get2byte(&data[iPtr+2]); + if( iPtrEnd+3>=iStart ){ + if( iPtrEnd>iStart ) return SQLITE_CORRUPT_BKPT; + nFrag += iStart - iPtrEnd; + iSize = iEnd - iPtr; + iStart = iPtr; } - data[hdr+7] -= (u8)frag; - x = get2byte(&data[pnext]); - put2byte(&data[pbegin], x); - x = pnext + get2byte(&data[pnext+2]) - pbegin; - put2byte(&data[pbegin+2], x); - }else{ - addr = pbegin; } + if( nFrag>data[hdr+7] ) return SQLITE_CORRUPT_BKPT; + data[hdr+7] -= nFrag; } - - /* If the cell content area begins with a freeblock, remove it. */ - if( data[hdr+1]==data[hdr+5] && data[hdr+2]==data[hdr+6] ){ - int top; - pbegin = get2byte(&data[hdr+1]); - memcpy(&data[hdr+1], &data[pbegin], 2); - top = get2byte(&data[hdr+5]) + get2byte(&data[pbegin+2]); - put2byte(&data[hdr+5], top); + if( iStart==get2byte(&data[hdr+5]) ){ + /* The new freeblock is at the beginning of the cell content area, + ** so just extend the cell content area rather than create another + ** freelist entry */ + if( iPtr!=hdr+1 ) return SQLITE_CORRUPT_BKPT; + put2byte(&data[hdr+1], iFreeBlk); + put2byte(&data[hdr+5], iEnd); + }else{ + /* Insert the new freeblock into the freelist */ + put2byte(&data[iPtr], iStart); + put2byte(&data[iStart], iFreeBlk); + put2byte(&data[iStart+2], iSize); } - assert( sqlite3PagerIswriteable(pPage->pDbPage) ); + pPage->nFree += iOrigSize; return SQLITE_OK; } @@ -52548,18 +56796,44 @@ static int decodeFlags(MemPage *pPage, int flagByte){ pPage->leaf = (u8)(flagByte>>3); assert( PTF_LEAF == 1<<3 ); flagByte &= ~PTF_LEAF; pPage->childPtrSize = 4-4*pPage->leaf; + pPage->xCellSize = cellSizePtr; pBt = pPage->pBt; if( flagByte==(PTF_LEAFDATA | PTF_INTKEY) ){ + /* EVIDENCE-OF: R-03640-13415 A value of 5 means the page is an interior + ** table b-tree page. */ + assert( (PTF_LEAFDATA|PTF_INTKEY)==5 ); + /* EVIDENCE-OF: R-20501-61796 A value of 13 means the page is a leaf + ** table b-tree page. */ + assert( (PTF_LEAFDATA|PTF_INTKEY|PTF_LEAF)==13 ); pPage->intKey = 1; - pPage->hasData = pPage->leaf; + if( pPage->leaf ){ + pPage->intKeyLeaf = 1; + pPage->noPayload = 0; + pPage->xParseCell = btreeParseCellPtr; + }else{ + pPage->intKeyLeaf = 0; + pPage->noPayload = 1; + pPage->xCellSize = cellSizePtrNoPayload; + pPage->xParseCell = btreeParseCellPtrNoPayload; + } pPage->maxLocal = pBt->maxLeaf; pPage->minLocal = pBt->minLeaf; }else if( flagByte==PTF_ZERODATA ){ + /* EVIDENCE-OF: R-27225-53936 A value of 2 means the page is an interior + ** index b-tree page. */ + assert( (PTF_ZERODATA)==2 ); + /* EVIDENCE-OF: R-16571-11615 A value of 10 means the page is a leaf + ** index b-tree page. */ + assert( (PTF_ZERODATA|PTF_LEAF)==10 ); pPage->intKey = 0; - pPage->hasData = 0; + pPage->intKeyLeaf = 0; + pPage->noPayload = 0; + pPage->xParseCell = btreeParseCellPtrIndex; pPage->maxLocal = pBt->maxLocal; pPage->minLocal = pBt->minLocal; }else{ + /* EVIDENCE-OF: R-47608-56469 Any other value for the b-tree page type is + ** an error. */ return SQLITE_CORRUPT_BKPT; } pPage->max1bytePayload = pBt->max1bytePayload; @@ -52578,6 +56852,7 @@ static int decodeFlags(MemPage *pPage, int flagByte){ static int btreeInitPage(MemPage *pPage){ assert( pPage->pBt!=0 ); + assert( pPage->pBt->db!=0 ); assert( sqlite3_mutex_held(pPage->pBt->mutex) ); assert( pPage->pgno==sqlite3PagerPagenumber(pPage->pDbPage) ); assert( pPage == sqlite3PagerGetExtra(pPage->pDbPage) ); @@ -52599,21 +56874,34 @@ static int btreeInitPage(MemPage *pPage){ hdr = pPage->hdrOffset; data = pPage->aData; + /* EVIDENCE-OF: R-28594-02890 The one-byte flag at offset 0 indicating + ** the b-tree page type. */ if( decodeFlags(pPage, data[hdr]) ) return SQLITE_CORRUPT_BKPT; assert( pBt->pageSize>=512 && pBt->pageSize<=65536 ); pPage->maskPage = (u16)(pBt->pageSize - 1); pPage->nOverflow = 0; usableSize = pBt->usableSize; - pPage->cellOffset = cellOffset = hdr + 12 - 4*pPage->leaf; + pPage->cellOffset = cellOffset = hdr + 8 + pPage->childPtrSize; pPage->aDataEnd = &data[usableSize]; pPage->aCellIdx = &data[cellOffset]; + pPage->aDataOfst = &data[pPage->childPtrSize]; + /* EVIDENCE-OF: R-58015-48175 The two-byte integer at offset 5 designates + ** the start of the cell content area. A zero value for this integer is + ** interpreted as 65536. */ top = get2byteNotZero(&data[hdr+5]); + /* EVIDENCE-OF: R-37002-32774 The two-byte integer at offset 3 gives the + ** number of cells on the page. */ pPage->nCell = get2byte(&data[hdr+3]); if( pPage->nCell>MX_CELL(pBt) ){ /* To many cells for a single page. The page must be corrupt */ return SQLITE_CORRUPT_BKPT; } testcase( pPage->nCell==MX_CELL(pBt) ); + /* EVIDENCE-OF: R-24089-57979 If a page contains no cells (which is only + ** possible for a root page of a table that contains no rows) then the + ** offset to the cell content area will equal the page size minus the + ** bytes of reserved space. */ + assert( pPage->nCell>0 || top==usableSize || CORRUPT_DB ); /* A malformed database page might cause us to read past the end ** of page when parsing a cell. @@ -52624,20 +56912,19 @@ static int btreeInitPage(MemPage *pPage){ */ iCellFirst = cellOffset + 2*pPage->nCell; iCellLast = usableSize - 4; -#if defined(SQLITE_ENABLE_OVERSIZE_CELL_CHECK) - { + if( pBt->db->flags & SQLITE_CellSizeCk ){ int i; /* Index into the cell pointer array */ int sz; /* Size of a cell */ if( !pPage->leaf ) iCellLast--; for(i=0; inCell; i++){ - pc = get2byte(&data[cellOffset+i*2]); + pc = get2byteAligned(&data[cellOffset+i*2]); testcase( pc==iCellFirst ); testcase( pc==iCellLast ); if( pciCellLast ){ return SQLITE_CORRUPT_BKPT; } - sz = cellSizePtr(pPage, &data[pc]); + sz = pPage->xCellSize(pPage, &data[pc]); testcase( pc+sz==usableSize ); if( pc+sz>usableSize ){ return SQLITE_CORRUPT_BKPT; @@ -52645,15 +56932,21 @@ static int btreeInitPage(MemPage *pPage){ } if( !pPage->leaf ) iCellLast++; } -#endif - /* Compute the total free space on the page */ + /* Compute the total free space on the page + ** EVIDENCE-OF: R-23588-34450 The two-byte integer at offset 1 gives the + ** start of the first freeblock on the page, or is zero if there are no + ** freeblocks. */ pc = get2byte(&data[hdr+1]); - nFree = data[hdr+7] + top; + nFree = data[hdr+7] + top; /* Init nFree to non-freeblock free space */ while( pc>0 ){ u16 next, size; if( pciCellLast ){ - /* Start of free block is off the page */ + /* EVIDENCE-OF: R-55530-52930 In a well-formed b-tree page, there will + ** always be at least one cell before the first freeblock. + ** + ** Or, the freeblock is off the end of the page + */ return SQLITE_CORRUPT_BKPT; } next = get2byte(&data[pc]); @@ -52711,6 +57004,7 @@ static void zeroPage(MemPage *pPage, int flags){ pPage->cellOffset = first; pPage->aDataEnd = &data[pBt->usableSize]; pPage->aCellIdx = &data[first]; + pPage->aDataOfst = &data[pPage->childPtrSize]; pPage->nOverflow = 0; assert( pBt->pageSize>=512 && pBt->pageSize<=65536 ); pPage->maskPage = (u16)(pBt->pageSize - 1); @@ -52725,20 +57019,23 @@ static void zeroPage(MemPage *pPage, int flags){ */ static MemPage *btreePageFromDbPage(DbPage *pDbPage, Pgno pgno, BtShared *pBt){ MemPage *pPage = (MemPage*)sqlite3PagerGetExtra(pDbPage); - pPage->aData = sqlite3PagerGetData(pDbPage); - pPage->pDbPage = pDbPage; - pPage->pBt = pBt; - pPage->pgno = pgno; - pPage->hdrOffset = pPage->pgno==1 ? 100 : 0; + if( pgno!=pPage->pgno ){ + pPage->aData = sqlite3PagerGetData(pDbPage); + pPage->pDbPage = pDbPage; + pPage->pBt = pBt; + pPage->pgno = pgno; + pPage->hdrOffset = pgno==1 ? 100 : 0; + } + assert( pPage->aData==sqlite3PagerGetData(pDbPage) ); return pPage; } /* ** Get a page from the pager. Initialize the MemPage.pBt and -** MemPage.aData elements if needed. +** MemPage.aData elements if needed. See also: btreeGetUnusedPage(). ** -** If the noContent flag is set, it means that we do not care about -** the content of the page at this time. So do not go to the disk +** If the PAGER_GET_NOCONTENT flag is set, it means that we do not care +** about the content of the page at this time. So do not go to the disk ** to fetch the content. Just fill in the content with zeros for now. ** If in the future we call sqlite3PagerWrite() on this page, that ** means we have started to be concerned about content and the disk @@ -52755,7 +57052,7 @@ static int btreeGetPage( assert( flags==0 || flags==PAGER_GET_NOCONTENT || flags==PAGER_GET_READONLY ); assert( sqlite3_mutex_held(pBt->mutex) ); - rc = sqlite3PagerAcquire(pBt->pPager, pgno, (DbPage**)&pDbPage, flags); + rc = sqlite3PagerGet(pBt->pPager, pgno, (DbPage**)&pDbPage, flags); if( rc ) return rc; *ppPage = btreePageFromDbPage(pDbPage, pgno, pBt); return SQLITE_OK; @@ -52786,39 +57083,67 @@ static Pgno btreePagecount(BtShared *pBt){ SQLITE_PRIVATE u32 sqlite3BtreeLastPage(Btree *p){ assert( sqlite3BtreeHoldsMutex(p) ); assert( ((p->pBt->nPage)&0x8000000)==0 ); - return (int)btreePagecount(p->pBt); + return btreePagecount(p->pBt); } /* -** Get a page from the pager and initialize it. This routine is just a -** convenience wrapper around separate calls to btreeGetPage() and -** btreeInitPage(). +** Get a page from the pager and initialize it. ** -** If an error occurs, then the value *ppPage is set to is undefined. It +** If pCur!=0 then the page is being fetched as part of a moveToChild() +** call. Do additional sanity checking on the page in this case. +** And if the fetch fails, this routine must decrement pCur->iPage. +** +** The page is fetched as read-write unless pCur is not NULL and is +** a read-only cursor. +** +** If an error occurs, then *ppPage is undefined. It ** may remain unchanged, or it may be set to an invalid value. */ static int getAndInitPage( BtShared *pBt, /* The database file */ Pgno pgno, /* Number of the page to get */ MemPage **ppPage, /* Write the page pointer here */ - int bReadonly /* PAGER_GET_READONLY or 0 */ + BtCursor *pCur, /* Cursor to receive the page, or NULL */ + int bReadOnly /* True for a read-only page */ ){ int rc; + DbPage *pDbPage; assert( sqlite3_mutex_held(pBt->mutex) ); - assert( bReadonly==PAGER_GET_READONLY || bReadonly==0 ); + assert( pCur==0 || ppPage==&pCur->apPage[pCur->iPage] ); + assert( pCur==0 || bReadOnly==pCur->curPagerFlags ); + assert( pCur==0 || pCur->iPage>0 ); if( pgno>btreePagecount(pBt) ){ rc = SQLITE_CORRUPT_BKPT; - }else{ - rc = btreeGetPage(pBt, pgno, ppPage, bReadonly); - if( rc==SQLITE_OK && (*ppPage)->isInit==0 ){ - rc = btreeInitPage(*ppPage); - if( rc!=SQLITE_OK ){ - releasePage(*ppPage); - } + goto getAndInitPage_error; + } + rc = sqlite3PagerGet(pBt->pPager, pgno, (DbPage**)&pDbPage, bReadOnly); + if( rc ){ + goto getAndInitPage_error; + } + *ppPage = (MemPage*)sqlite3PagerGetExtra(pDbPage); + if( (*ppPage)->isInit==0 ){ + btreePageFromDbPage(pDbPage, pgno, pBt); + rc = btreeInitPage(*ppPage); + if( rc!=SQLITE_OK ){ + releasePage(*ppPage); + goto getAndInitPage_error; } } + assert( (*ppPage)->pgno==pgno ); + assert( (*ppPage)->aData==sqlite3PagerGetData(pDbPage) ); + /* If obtaining a child page for a cursor, we must verify that the page is + ** compatible with the root page. */ + if( pCur && ((*ppPage)->nCell<1 || (*ppPage)->intKey!=pCur->curIntKey) ){ + rc = SQLITE_CORRUPT_BKPT; + releasePage(*ppPage); + goto getAndInitPage_error; + } + return SQLITE_OK; + +getAndInitPage_error: + if( pCur ) pCur->iPage--; testcase( pgno==0 ); assert( pgno!=0 || rc==SQLITE_CORRUPT ); return rc; @@ -52828,17 +57153,48 @@ static int getAndInitPage( ** Release a MemPage. This should be called once for each prior ** call to btreeGetPage. */ -static void releasePage(MemPage *pPage){ - if( pPage ){ - assert( pPage->aData ); - assert( pPage->pBt ); - assert( pPage->pDbPage!=0 ); - assert( sqlite3PagerGetExtra(pPage->pDbPage) == (void*)pPage ); - assert( sqlite3PagerGetData(pPage->pDbPage)==pPage->aData ); - assert( sqlite3_mutex_held(pPage->pBt->mutex) ); - sqlite3PagerUnrefNotNull(pPage->pDbPage); - } +static void releasePageNotNull(MemPage *pPage){ + assert( pPage->aData ); + assert( pPage->pBt ); + assert( pPage->pDbPage!=0 ); + assert( sqlite3PagerGetExtra(pPage->pDbPage) == (void*)pPage ); + assert( sqlite3PagerGetData(pPage->pDbPage)==pPage->aData ); + assert( sqlite3_mutex_held(pPage->pBt->mutex) ); + sqlite3PagerUnrefNotNull(pPage->pDbPage); } +static void releasePage(MemPage *pPage){ + if( pPage ) releasePageNotNull(pPage); +} + +/* +** Get an unused page. +** +** This works just like btreeGetPage() with the addition: +** +** * If the page is already in use for some other purpose, immediately +** release it and return an SQLITE_CURRUPT error. +** * Make sure the isInit flag is clear +*/ +static int btreeGetUnusedPage( + BtShared *pBt, /* The btree */ + Pgno pgno, /* Number of the page to fetch */ + MemPage **ppPage, /* Return the page in this parameter */ + int flags /* PAGER_GET_NOCONTENT or PAGER_GET_READONLY */ +){ + int rc = btreeGetPage(pBt, pgno, ppPage, flags); + if( rc==SQLITE_OK ){ + if( sqlite3PagerPageRefcount((*ppPage)->pDbPage)>1 ){ + releasePage(*ppPage); + *ppPage = 0; + return SQLITE_CORRUPT_BKPT; + } + (*ppPage)->isInit = 0; + }else{ + *ppPage = 0; + } + return rc; +} + /* ** During a rollback, when the pager reloads information into the cache @@ -52962,16 +57318,18 @@ SQLITE_PRIVATE int sqlite3BtreeOpen( */ if( isTempDb==0 && (isMemdb==0 || (vfsFlags&SQLITE_OPEN_URI)!=0) ){ if( vfsFlags & SQLITE_OPEN_SHAREDCACHE ){ + int nFilename = sqlite3Strlen30(zFilename)+1; int nFullPathname = pVfs->mxPathname+1; - char *zFullPathname = sqlite3Malloc(nFullPathname); + char *zFullPathname = sqlite3Malloc(MAX(nFullPathname,nFilename)); MUTEX_LOGIC( sqlite3_mutex *mutexShared; ) + p->sharable = 1; if( !zFullPathname ){ sqlite3_free(p); return SQLITE_NOMEM; } if( isMemdb ){ - memcpy(zFullPathname, zFilename, sqlite3Strlen30(zFilename)+1); + memcpy(zFullPathname, zFilename, nFilename); }else{ rc = sqlite3OsFullPathname(pVfs, zFilename, nFullPathname, zFullPathname); @@ -53028,8 +57386,8 @@ SQLITE_PRIVATE int sqlite3BtreeOpen( ** the right size. This is to guard against size changes that result ** when compiling on a different architecture. */ - assert( sizeof(i64)==8 || sizeof(i64)==4 ); - assert( sizeof(u64)==8 || sizeof(u64)==4 ); + assert( sizeof(i64)==8 ); + assert( sizeof(u64)==8 ); assert( sizeof(u32)==4 ); assert( sizeof(u16)==2 ); assert( sizeof(Pgno)==4 ); @@ -53059,6 +57417,9 @@ SQLITE_PRIVATE int sqlite3BtreeOpen( #ifdef SQLITE_SECURE_DELETE pBt->btsFlags |= BTS_SECURE_DELETE; #endif + /* EVIDENCE-OF: R-51873-39618 The page size for a database file is + ** determined by the 2-byte integer located at an offset of 16 bytes from + ** the beginning of the database file. */ pBt->pageSize = (zDbHeader[16]<<8) | (zDbHeader[17]<<16); if( pBt->pageSize<512 || pBt->pageSize>SQLITE_MAX_PAGE_SIZE || ((pBt->pageSize-1)&pBt->pageSize)!=0 ){ @@ -53077,6 +57438,9 @@ SQLITE_PRIVATE int sqlite3BtreeOpen( #endif nReserve = 0; }else{ + /* EVIDENCE-OF: R-37497-42412 The size of the reserved region is + ** determined by the one-byte unsigned integer found at an offset of 20 + ** into the database file header. */ nReserve = zDbHeader[20]; pBt->btsFlags |= BTS_PAGESIZE_FIXED; #ifndef SQLITE_OMIT_AUTOVACUUM @@ -53211,7 +57575,8 @@ static int removeFromSharingList(BtShared *pBt){ /* ** Make sure pBt->pTmpSpace points to an allocation of -** MX_CELL_SIZE(pBt) bytes. +** MX_CELL_SIZE(pBt) bytes with a 4-byte prefix for a left-child +** pointer. */ static void allocateTempSpace(BtShared *pBt){ if( !pBt->pTmpSpace ){ @@ -53226,8 +57591,16 @@ static void allocateTempSpace(BtShared *pBt){ ** it into a database page. This is not actually a problem, but it ** does cause a valgrind error when the 1 or 2 bytes of unitialized ** data is passed to system call write(). So to avoid this error, - ** zero the first 4 bytes of temp space here. */ - if( pBt->pTmpSpace ) memset(pBt->pTmpSpace, 0, 4); + ** zero the first 4 bytes of temp space here. + ** + ** Also: Provide four bytes of initialized space before the + ** beginning of pTmpSpace as an area available to prepend the + ** left-child pointer to the beginning of a cell. + */ + if( pBt->pTmpSpace ){ + memset(pBt->pTmpSpace, 0, 8); + pBt->pTmpSpace += 4; + } } } @@ -53235,8 +57608,11 @@ static void allocateTempSpace(BtShared *pBt){ ** Free the pBt->pTmpSpace allocation */ static void freeTempSpace(BtShared *pBt){ - sqlite3PageFree( pBt->pTmpSpace); - pBt->pTmpSpace = 0; + if( pBt->pTmpSpace ){ + pBt->pTmpSpace -= 4; + sqlite3PageFree(pBt->pTmpSpace); + pBt->pTmpSpace = 0; + } } /* @@ -53262,7 +57638,7 @@ SQLITE_PRIVATE int sqlite3BtreeClose(Btree *p){ ** The call to sqlite3BtreeRollback() drops any table-locks held by ** this handle. */ - sqlite3BtreeRollback(p, SQLITE_OK); + sqlite3BtreeRollback(p, SQLITE_OK, 0); sqlite3BtreeLeave(p); /* If there are still other outstanding references to the shared-btree @@ -53298,19 +57674,11 @@ SQLITE_PRIVATE int sqlite3BtreeClose(Btree *p){ } /* -** Change the limit on the number of pages allowed in the cache. -** -** The maximum number of cache pages is set to the absolute -** value of mxPage. If mxPage is negative, the pager will -** operate asynchronously - it will not stop to do fsync()s -** to insure data is written to the disk surface before -** continuing. Transactions still work if synchronous is off, -** and the database cannot be corrupted if this program -** crashes. But if the operating system crashes or there is -** an abrupt power failure when synchronous is off, the database -** could be left in an inconsistent and unrecoverable state. -** Synchronous is on by default so database corruption is not -** normally a worry. +** Change the "soft" limit on the number of pages in the cache. +** Unused and unmodified pages will be recycled when the number of +** pages in the cache exceeds this soft limit. But the size of the +** cache is allowed to grow larger than this limit if it contains +** dirty pages or pages still in active use. */ SQLITE_PRIVATE int sqlite3BtreeSetCacheSize(Btree *p, int mxPage){ BtShared *pBt = p->pBt; @@ -53321,6 +57689,26 @@ SQLITE_PRIVATE int sqlite3BtreeSetCacheSize(Btree *p, int mxPage){ return SQLITE_OK; } +/* +** Change the "spill" limit on the number of pages in the cache. +** If the number of pages exceeds this limit during a write transaction, +** the pager might attempt to "spill" pages to the journal early in +** order to free up memory. +** +** The value returned is the current spill size. If zero is passed +** as an argument, no changes are made to the spill size setting, so +** using mxPage of 0 is a way to query the current spill size. +*/ +SQLITE_PRIVATE int sqlite3BtreeSetSpillSize(Btree *p, int mxPage){ + BtShared *pBt = p->pBt; + int res; + assert( sqlite3_mutex_held(p->db->mutex) ); + sqlite3BtreeEnter(p); + res = sqlite3PagerSetSpillsize(pBt->pPager, mxPage); + sqlite3BtreeLeave(p); + return res; +} + #if SQLITE_MAX_MMAP_SIZE>0 /* ** Change the limit on the amount of the database file that may be @@ -53398,6 +57786,9 @@ SQLITE_PRIVATE int sqlite3BtreeSetPageSize(Btree *p, int pageSize, int nReserve, BtShared *pBt = p->pBt; assert( nReserve>=-1 && nReserve<=255 ); sqlite3BtreeEnter(p); +#if SQLITE_HAS_CODEC + if( nReserve>pBt->optimalReserve ) pBt->optimalReserve = (u8)nReserve; +#endif if( pBt->btsFlags & BTS_PAGESIZE_FIXED ){ sqlite3BtreeLeave(p); return SQLITE_READONLY; @@ -53409,7 +57800,7 @@ SQLITE_PRIVATE int sqlite3BtreeSetPageSize(Btree *p, int pageSize, int nReserve, if( pageSize>=512 && pageSize<=SQLITE_MAX_PAGE_SIZE && ((pageSize-1)&pageSize)==0 ){ assert( (pageSize & 7)==0 ); - assert( !pBt->pPage1 && !pBt->pCursor ); + assert( !pBt->pCursor ); pBt->pageSize = (u32)pageSize; freeTempSpace(pBt); } @@ -53427,7 +57818,6 @@ SQLITE_PRIVATE int sqlite3BtreeGetPageSize(Btree *p){ return p->pBt->pageSize; } -#if defined(SQLITE_HAS_CODEC) || defined(SQLITE_DEBUG) /* ** This function is similar to sqlite3BtreeGetReserve(), except that it ** may only be called if it is guaranteed that the b-tree mutex is already @@ -53440,25 +57830,33 @@ SQLITE_PRIVATE int sqlite3BtreeGetPageSize(Btree *p){ ** database handle that owns *p, causing undefined behavior. */ SQLITE_PRIVATE int sqlite3BtreeGetReserveNoMutex(Btree *p){ + int n; assert( sqlite3_mutex_held(p->pBt->mutex) ); - return p->pBt->pageSize - p->pBt->usableSize; + n = p->pBt->pageSize - p->pBt->usableSize; + return n; } -#endif /* SQLITE_HAS_CODEC || SQLITE_DEBUG */ -#if !defined(SQLITE_OMIT_PAGER_PRAGMAS) || !defined(SQLITE_OMIT_VACUUM) /* ** Return the number of bytes of space at the end of every page that ** are intentually left unused. This is the "reserved" space that is ** sometimes used by extensions. +** +** If SQLITE_HAS_MUTEX is defined then the number returned is the +** greater of the current reserved space and the maximum requested +** reserve space. */ -SQLITE_PRIVATE int sqlite3BtreeGetReserve(Btree *p){ +SQLITE_PRIVATE int sqlite3BtreeGetOptimalReserve(Btree *p){ int n; sqlite3BtreeEnter(p); - n = p->pBt->pageSize - p->pBt->usableSize; + n = sqlite3BtreeGetReserveNoMutex(p); +#ifdef SQLITE_HAS_CODEC + if( npBt->optimalReserve ) n = p->pBt->optimalReserve; +#endif sqlite3BtreeLeave(p); return n; } + /* ** Set the maximum page count for a database if mxPage is positive. ** No changes are made if mxPage is 0 or negative. @@ -53489,7 +57887,6 @@ SQLITE_PRIVATE int sqlite3BtreeSecureDelete(Btree *p, int newFlag){ sqlite3BtreeLeave(p); return b; } -#endif /* !defined(SQLITE_OMIT_PAGER_PRAGMAS) || !defined(SQLITE_OMIT_VACUUM) */ /* ** Change the 'auto-vacuum' property of the database. If the 'autoVacuum' @@ -53574,6 +57971,9 @@ static int lockBtree(BtShared *pBt){ u32 usableSize; u8 *page1 = pPage1->aData; rc = SQLITE_NOTADB; + /* EVIDENCE-OF: R-43737-39999 Every valid SQLite database file begins + ** with the following 16 bytes (in hex): 53 51 4c 69 74 65 20 66 6f 72 6d + ** 61 74 20 33 00. */ if( memcmp(page1, zMagicHeader, 16)!=0 ){ goto page1_init_failed; } @@ -53614,15 +58014,21 @@ static int lockBtree(BtShared *pBt){ } #endif - /* The maximum embedded fraction must be exactly 25%. And the minimum - ** embedded fraction must be 12.5% for both leaf-data and non-leaf-data. + /* EVIDENCE-OF: R-15465-20813 The maximum and minimum embedded payload + ** fractions and the leaf payload fraction values must be 64, 32, and 32. + ** ** The original design allowed these amounts to vary, but as of ** version 3.6.0, we require them to be fixed. */ if( memcmp(&page1[21], "\100\040\040",3)!=0 ){ goto page1_init_failed; } + /* EVIDENCE-OF: R-51873-39618 The page size for a database file is + ** determined by the 2-byte integer located at an offset of 16 bytes from + ** the beginning of the database file. */ pageSize = (page1[16]<<8) | (page1[17]<<16); + /* EVIDENCE-OF: R-25008-21688 The size of a page is a power of two + ** between 512 and 65536 inclusive. */ if( ((pageSize-1)&pageSize)!=0 || pageSize>SQLITE_MAX_PAGE_SIZE || pageSize<=256 @@ -53630,6 +58036,13 @@ static int lockBtree(BtShared *pBt){ goto page1_init_failed; } assert( (pageSize & 7)==0 ); + /* EVIDENCE-OF: R-59310-51205 The "reserved space" size in the 1-byte + ** integer at offset 20 is the number of bytes of space at the end of + ** each page to reserve for extensions. + ** + ** EVIDENCE-OF: R-37497-42412 The size of the reserved region is + ** determined by the one-byte unsigned integer found at an offset of 20 + ** into the database file header. */ usableSize = pageSize - page1[20]; if( (u32)pageSize!=pBt->pageSize ){ /* After reading the first page of the database assuming a page size @@ -53650,6 +58063,9 @@ static int lockBtree(BtShared *pBt){ rc = SQLITE_CORRUPT_BKPT; goto page1_init_failed; } + /* EVIDENCE-OF: R-28312-64704 However, the usable size is not allowed to + ** be less than 480. In other words, if the page size is 512, then the + ** reserved space size cannot exceed 32. */ if( usableSize<480 ){ goto page1_init_failed; } @@ -53704,7 +58120,7 @@ page1_init_failed: ** false then all cursors are counted. ** ** For the purposes of this routine, a cursor is any cursor that -** is capable of reading or writing to the databse. Cursors that +** is capable of reading or writing to the database. Cursors that ** have been tripped into the CURSOR_FAULT state are not counted. */ static int countValidCursors(BtShared *pBt, int wrOnly){ @@ -53730,11 +58146,11 @@ static void unlockBtreeIfUnused(BtShared *pBt){ assert( sqlite3_mutex_held(pBt->mutex) ); assert( countValidCursors(pBt,0)==0 || pBt->inTransaction>TRANS_NONE ); if( pBt->inTransaction==TRANS_NONE && pBt->pPage1!=0 ){ - assert( pBt->pPage1->aData ); + MemPage *pPage1 = pBt->pPage1; + assert( pPage1->aData ); assert( sqlite3PagerRefcount(pBt->pPager)==1 ); - assert( pBt->pPage1->aData ); - releasePage(pBt->pPage1); pBt->pPage1 = 0; + releasePageNotNull(pPage1); } } @@ -54039,20 +58455,22 @@ static int modifyPagePointer(MemPage *pPage, Pgno iFrom, Pgno iTo, u8 eType){ u8 isInitOrig = pPage->isInit; int i; int nCell; + int rc; - btreeInitPage(pPage); + rc = btreeInitPage(pPage); + if( rc ) return rc; nCell = pPage->nCell; for(i=0; iaData+pPage->maskPage - && iFrom==get4byte(&pCell[info.iOverflow]) + pPage->xParseCell(pPage, pCell, &info); + if( info.nLocalaData+pPage->maskPage + && iFrom==get4byte(pCell+info.nSize-4) ){ - put4byte(&pCell[info.iOverflow], iTo); + put4byte(pCell+info.nSize-4, iTo); break; } }else{ @@ -54168,7 +58586,7 @@ static int allocateBtreePage(BtShared *, MemPage **, Pgno *, Pgno, u8); ** calling this function again), return SQLITE_DONE. Or, if an error ** occurs, return some other error code. ** -** More specificly, this function attempts to re-organize the database so +** More specifically, this function attempts to re-organize the database so ** that the last page of the file currently in use is no longer in use. ** ** Parameter nFin is the number of pages that this database would contain @@ -54176,7 +58594,7 @@ static int allocateBtreePage(BtShared *, MemPage **, Pgno *, Pgno, u8); ** ** If the bCommit parameter is non-zero, this function assumes that the ** caller will keep calling incrVacuumStep() until it returns SQLITE_DONE -** or an error. bCommit is passed true for an auto-vacuum-on-commmit +** or an error. bCommit is passed true for an auto-vacuum-on-commit ** operation, or false for an incremental vacuum. */ static int incrVacuumStep(BtShared *pBt, Pgno nFin, Pgno iLastPg, int bCommit){ @@ -54346,7 +58764,7 @@ SQLITE_PRIVATE int sqlite3BtreeIncrVacuum(Btree *p){ static int autoVacuumCommit(BtShared *pBt){ int rc = SQLITE_OK; Pager *pPager = pBt->pPager; - VVA_ONLY( int nRef = sqlite3PagerRefcount(pPager) ); + VVA_ONLY( int nRef = sqlite3PagerRefcount(pPager); ) assert( sqlite3_mutex_held(pBt->mutex) ); invalidateAllOverflowCache(pBt); @@ -54530,6 +58948,7 @@ SQLITE_PRIVATE int sqlite3BtreeCommitPhaseTwo(Btree *p, int bCleanup){ sqlite3BtreeLeave(p); return rc; } + p->iDataVersion--; /* Compensate for pPager->iDataVersion++; */ pBt->inTransaction = TRANS_READ; btreeClearHasContent(pBt); } @@ -54555,60 +58974,91 @@ SQLITE_PRIVATE int sqlite3BtreeCommit(Btree *p){ /* ** This routine sets the state to CURSOR_FAULT and the error -** code to errCode for every cursor on BtShared that pBtree -** references. +** code to errCode for every cursor on any BtShared that pBtree +** references. Or if the writeOnly flag is set to 1, then only +** trip write cursors and leave read cursors unchanged. ** -** Every cursor is tripped, including cursors that belong -** to other database connections that happen to be sharing -** the cache with pBtree. +** Every cursor is a candidate to be tripped, including cursors +** that belong to other database connections that happen to be +** sharing the cache with pBtree. ** -** This routine gets called when a rollback occurs. -** All cursors using the same cache must be tripped -** to prevent them from trying to use the btree after -** the rollback. The rollback may have deleted tables -** or moved root pages, so it is not sufficient to -** save the state of the cursor. The cursor must be -** invalidated. +** This routine gets called when a rollback occurs. If the writeOnly +** flag is true, then only write-cursors need be tripped - read-only +** cursors save their current positions so that they may continue +** following the rollback. Or, if writeOnly is false, all cursors are +** tripped. In general, writeOnly is false if the transaction being +** rolled back modified the database schema. In this case b-tree root +** pages may be moved or deleted from the database altogether, making +** it unsafe for read cursors to continue. +** +** If the writeOnly flag is true and an error is encountered while +** saving the current position of a read-only cursor, all cursors, +** including all read-cursors are tripped. +** +** SQLITE_OK is returned if successful, or if an error occurs while +** saving a cursor position, an SQLite error code. */ -SQLITE_PRIVATE void sqlite3BtreeTripAllCursors(Btree *pBtree, int errCode){ +SQLITE_PRIVATE int sqlite3BtreeTripAllCursors(Btree *pBtree, int errCode, int writeOnly){ BtCursor *p; - if( pBtree==0 ) return; - sqlite3BtreeEnter(pBtree); - for(p=pBtree->pBt->pCursor; p; p=p->pNext){ - int i; - sqlite3BtreeClearCursor(p); - p->eState = CURSOR_FAULT; - p->skipNext = errCode; - for(i=0; i<=p->iPage; i++){ - releasePage(p->apPage[i]); - p->apPage[i] = 0; + int rc = SQLITE_OK; + + assert( (writeOnly==0 || writeOnly==1) && BTCF_WriteFlag==1 ); + if( pBtree ){ + sqlite3BtreeEnter(pBtree); + for(p=pBtree->pBt->pCursor; p; p=p->pNext){ + int i; + if( writeOnly && (p->curFlags & BTCF_WriteFlag)==0 ){ + if( p->eState==CURSOR_VALID || p->eState==CURSOR_SKIPNEXT ){ + rc = saveCursorPosition(p); + if( rc!=SQLITE_OK ){ + (void)sqlite3BtreeTripAllCursors(pBtree, rc, 0); + break; + } + } + }else{ + sqlite3BtreeClearCursor(p); + p->eState = CURSOR_FAULT; + p->skipNext = errCode; + } + for(i=0; i<=p->iPage; i++){ + releasePage(p->apPage[i]); + p->apPage[i] = 0; + } } + sqlite3BtreeLeave(pBtree); } - sqlite3BtreeLeave(pBtree); + return rc; } /* -** Rollback the transaction in progress. All cursors will be -** invalided by this operation. Any attempt to use a cursor -** that was open at the beginning of this operation will result -** in an error. +** Rollback the transaction in progress. +** +** If tripCode is not SQLITE_OK then cursors will be invalidated (tripped). +** Only write cursors are tripped if writeOnly is true but all cursors are +** tripped if writeOnly is false. Any attempt to use +** a tripped cursor will result in an error. ** ** This will release the write lock on the database file. If there ** are no active cursors, it also releases the read lock. */ -SQLITE_PRIVATE int sqlite3BtreeRollback(Btree *p, int tripCode){ +SQLITE_PRIVATE int sqlite3BtreeRollback(Btree *p, int tripCode, int writeOnly){ int rc; BtShared *pBt = p->pBt; MemPage *pPage1; + assert( writeOnly==1 || writeOnly==0 ); + assert( tripCode==SQLITE_ABORT_ROLLBACK || tripCode==SQLITE_OK ); sqlite3BtreeEnter(p); if( tripCode==SQLITE_OK ){ rc = tripCode = saveAllCursors(pBt, 0, 0); + if( rc ) writeOnly = 0; }else{ rc = SQLITE_OK; } if( tripCode ){ - sqlite3BtreeTripAllCursors(p, tripCode); + int rc2 = sqlite3BtreeTripAllCursors(p, tripCode, writeOnly); + assert( rc==SQLITE_OK || (writeOnly==0 && rc2==SQLITE_OK) ); + if( rc2!=SQLITE_OK ) rc = rc2; } btreeIntegrity(p); @@ -54643,7 +59093,7 @@ SQLITE_PRIVATE int sqlite3BtreeRollback(Btree *p, int tripCode){ } /* -** Start a statement subtransaction. The subtransaction can can be rolled +** Start a statement subtransaction. The subtransaction can be rolled ** back independently of the main transaction. You must start a transaction ** before starting a subtransaction. The subtransaction is ended automatically ** if the main transaction commits or rolls back. @@ -54756,24 +59206,30 @@ static int btreeCursor( BtCursor *pCur /* Space for new cursor */ ){ BtShared *pBt = p->pBt; /* Shared b-tree handle */ + BtCursor *pX; /* Looping over other all cursors */ assert( sqlite3BtreeHoldsMutex(p) ); - assert( wrFlag==0 || wrFlag==1 ); + assert( wrFlag==0 + || wrFlag==BTREE_WRCSR + || wrFlag==(BTREE_WRCSR|BTREE_FORDELETE) + ); /* The following assert statements verify that if this is a sharable ** b-tree database, the connection is holding the required table locks, ** and that no other connection has any open cursor that conflicts with ** this lock. */ - assert( hasSharedCacheTableLock(p, iTable, pKeyInfo!=0, wrFlag+1) ); + assert( hasSharedCacheTableLock(p, iTable, pKeyInfo!=0, (wrFlag?2:1)) ); assert( wrFlag==0 || !hasReadConflicts(p, iTable) ); /* Assert that the caller has opened the required transaction. */ assert( p->inTrans>TRANS_NONE ); assert( wrFlag==0 || p->inTrans==TRANS_WRITE ); assert( pBt->pPage1 && pBt->pPage1->aData ); + assert( wrFlag==0 || (pBt->btsFlags & BTS_READ_ONLY)==0 ); - if( NEVER(wrFlag && (pBt->btsFlags & BTS_READ_ONLY)!=0) ){ - return SQLITE_READONLY; + if( wrFlag ){ + allocateTempSpace(pBt); + if( pBt->pTmpSpace==0 ) return SQLITE_NOMEM; } if( iTable==1 && btreePagecount(pBt)==0 ){ assert( wrFlag==0 ); @@ -54787,12 +59243,17 @@ static int btreeCursor( pCur->pKeyInfo = pKeyInfo; pCur->pBtree = p; pCur->pBt = pBt; - assert( wrFlag==0 || wrFlag==BTCF_WriteFlag ); - pCur->curFlags = wrFlag; - pCur->pNext = pBt->pCursor; - if( pCur->pNext ){ - pCur->pNext->pPrev = pCur; + pCur->curFlags = wrFlag ? BTCF_WriteFlag : 0; + pCur->curPagerFlags = wrFlag ? 0 : PAGER_GET_READONLY; + /* If there are two or more cursors on the same btree, then all such + ** cursors *must* have the BTCF_Multiple flag set. */ + for(pX=pBt->pCursor; pX; pX=pX->pNext){ + if( pX->pgnoRoot==(Pgno)iTable ){ + pX->curFlags |= BTCF_Multiple; + pCur->curFlags |= BTCF_Multiple; + } } + pCur->pNext = pBt->pCursor; pBt->pCursor = pCur; pCur->eState = CURSOR_INVALID; return SQLITE_OK; @@ -54805,9 +59266,13 @@ SQLITE_PRIVATE int sqlite3BtreeCursor( BtCursor *pCur /* Write new cursor here */ ){ int rc; - sqlite3BtreeEnter(p); - rc = btreeCursor(p, iTable, wrFlag, pKeyInfo, pCur); - sqlite3BtreeLeave(p); + if( iTable<1 ){ + rc = SQLITE_CORRUPT_BKPT; + }else{ + sqlite3BtreeEnter(p); + rc = btreeCursor(p, iTable, wrFlag, pKeyInfo, pCur); + sqlite3BtreeLeave(p); + } return rc; } @@ -54846,19 +59311,24 @@ SQLITE_PRIVATE int sqlite3BtreeCloseCursor(BtCursor *pCur){ BtShared *pBt = pCur->pBt; sqlite3BtreeEnter(pBtree); sqlite3BtreeClearCursor(pCur); - if( pCur->pPrev ){ - pCur->pPrev->pNext = pCur->pNext; - }else{ + assert( pBt->pCursor!=0 ); + if( pBt->pCursor==pCur ){ pBt->pCursor = pCur->pNext; - } - if( pCur->pNext ){ - pCur->pNext->pPrev = pCur->pPrev; + }else{ + BtCursor *pPrev = pBt->pCursor; + do{ + if( pPrev->pNext==pCur ){ + pPrev->pNext = pCur->pNext; + break; + } + pPrev = pPrev->pNext; + }while( ALWAYS(pPrev) ); } for(i=0; i<=pCur->iPage; i++){ releasePage(pCur->apPage[i]); } unlockBtreeIfUnused(pBt); - sqlite3DbFree(pBtree->db, pCur->aOverflow); + sqlite3_free(pCur->aOverflow); /* sqlite3_free(pCur); */ sqlite3BtreeLeave(pBtree); } @@ -54872,13 +59342,6 @@ SQLITE_PRIVATE int sqlite3BtreeCloseCursor(BtCursor *pCur){ ** ** BtCursor.info is a cache of the information in the current cell. ** Using this cache reduces the number of calls to btreeParseCell(). -** -** 2007-06-25: There is a bug in some versions of MSVC that cause the -** compiler to crash when getCellInfo() is implemented as a macro. -** But there is a measureable speed advantage to using the macro on gcc -** (when less compiler optimizations like -Os or -O0 are used and the -** compiler is not doing agressive inlining.) So we use a real function -** for MSVC and a macro for everything else. Ticket #2457. */ #ifndef NDEBUG static void assertCellInfo(BtCursor *pCur){ @@ -54891,28 +59354,15 @@ SQLITE_PRIVATE int sqlite3BtreeCloseCursor(BtCursor *pCur){ #else #define assertCellInfo(x) #endif -#ifdef _MSC_VER - /* Use a real function in MSVC to work around bugs in that compiler. */ - static void getCellInfo(BtCursor *pCur){ - if( pCur->info.nSize==0 ){ - int iPage = pCur->iPage; - btreeParseCell(pCur->apPage[iPage],pCur->aiIdx[iPage],&pCur->info); - pCur->curFlags |= BTCF_ValidNKey; - }else{ - assertCellInfo(pCur); - } +static SQLITE_NOINLINE void getCellInfo(BtCursor *pCur){ + if( pCur->info.nSize==0 ){ + int iPage = pCur->iPage; + pCur->curFlags |= BTCF_ValidNKey; + btreeParseCell(pCur->apPage[iPage],pCur->aiIdx[iPage],&pCur->info); + }else{ + assertCellInfo(pCur); } -#else /* if not _MSC_VER */ - /* Use a macro in all other compilers so that the function is inlined */ -#define getCellInfo(pCur) \ - if( pCur->info.nSize==0 ){ \ - int iPage = pCur->iPage; \ - btreeParseCell(pCur->apPage[iPage],pCur->aiIdx[iPage],&pCur->info); \ - pCur->curFlags |= BTCF_ValidNKey; \ - }else{ \ - assertCellInfo(pCur); \ - } -#endif /* _MSC_VER */ +} #ifndef NDEBUG /* The next routine used only within assert() statements */ /* @@ -54939,13 +59389,9 @@ SQLITE_PRIVATE int sqlite3BtreeCursorIsValid(BtCursor *pCur){ */ SQLITE_PRIVATE int sqlite3BtreeKeySize(BtCursor *pCur, i64 *pSize){ assert( cursorHoldsMutex(pCur) ); - assert( pCur->eState==CURSOR_INVALID || pCur->eState==CURSOR_VALID ); - if( pCur->eState!=CURSOR_VALID ){ - *pSize = 0; - }else{ - getCellInfo(pCur); - *pSize = pCur->info.nKey; - } + assert( pCur->eState==CURSOR_VALID ); + getCellInfo(pCur); + *pSize = pCur->info.nKey; return SQLITE_OK; } @@ -54964,8 +59410,11 @@ SQLITE_PRIVATE int sqlite3BtreeKeySize(BtCursor *pCur, i64 *pSize){ SQLITE_PRIVATE int sqlite3BtreeDataSize(BtCursor *pCur, u32 *pSize){ assert( cursorHoldsMutex(pCur) ); assert( pCur->eState==CURSOR_VALID ); + assert( pCur->iPage>=0 ); + assert( pCur->iPageapPage[pCur->iPage]->intKeyLeaf==1 ); getCellInfo(pCur); - *pSize = pCur->info.nData; + *pSize = pCur->info.nPayload; return SQLITE_OK; } @@ -55094,7 +59543,7 @@ static int copyPayload( ** ** If the current cursor entry uses one or more overflow pages and the ** eOp argument is not 2, this function may allocate space for and lazily -** popluates the overflow page-list cache array (BtCursor.aOverflow). +** populates the overflow page-list cache array (BtCursor.aOverflow). ** Subsequent calls use this cache to make seeking to the supplied offset ** more efficient. ** @@ -55116,30 +59565,28 @@ static int accessPayload( ){ unsigned char *aPayload; int rc = SQLITE_OK; - u32 nKey; int iIdx = 0; MemPage *pPage = pCur->apPage[pCur->iPage]; /* Btree page of current entry */ BtShared *pBt = pCur->pBt; /* Btree this cursor belongs to */ #ifdef SQLITE_DIRECT_OVERFLOW_READ - int bEnd; /* True if reading to end of data */ + unsigned char * const pBufStart = pBuf; + int bEnd; /* True if reading to end of data */ #endif assert( pPage ); assert( pCur->eState==CURSOR_VALID ); assert( pCur->aiIdx[pCur->iPage]nCell ); assert( cursorHoldsMutex(pCur) ); - assert( eOp!=2 || offset==0 ); /* Always start from beginning for eOp==2 */ + assert( eOp!=2 || offset==0 ); /* Always start from beginning for eOp==2 */ getCellInfo(pCur); - aPayload = pCur->info.pCell + pCur->info.nHeader; - nKey = (pPage->intKey ? 0 : (int)pCur->info.nKey); + aPayload = pCur->info.pPayload; #ifdef SQLITE_DIRECT_OVERFLOW_READ - bEnd = (offset+amt==nKey+pCur->info.nData); + bEnd = offset+amt==pCur->info.nPayload; #endif + assert( offset+amt <= pCur->info.nPayload ); - if( NEVER(offset+amt > nKey+pCur->info.nData) - || &aPayload[pCur->info.nLocal] > &pPage->aData[pBt->usableSize] - ){ + if( &aPayload[pCur->info.nLocal] > &pPage->aData[pBt->usableSize] ){ /* Trying to read or write past the end of the data is an error */ return SQLITE_CORRUPT_BKPT; } @@ -55158,6 +59605,7 @@ static int accessPayload( offset -= pCur->info.nLocal; } + if( rc==SQLITE_OK && amt>0 ){ const u32 ovflSize = pBt->usableSize - 4; /* Bytes content per ovfl page */ Pgno nextPage; @@ -55175,8 +59623,8 @@ static int accessPayload( if( eOp!=2 && (pCur->curFlags & BTCF_ValidOvfl)==0 ){ int nOvfl = (pCur->info.nPayload-pCur->info.nLocal+ovflSize-1)/ovflSize; if( nOvfl>pCur->nOvflAlloc ){ - Pgno *aNew = (Pgno*)sqlite3DbRealloc( - pCur->pBtree->db, pCur->aOverflow, nOvfl*2*sizeof(Pgno) + Pgno *aNew = (Pgno*)sqlite3Realloc( + pCur->aOverflow, nOvfl*2*sizeof(Pgno) ); if( aNew==0 ){ rc = SQLITE_NOMEM; @@ -55195,7 +59643,9 @@ static int accessPayload( ** entry for the first required overflow page is valid, skip ** directly to it. */ - if( (pCur->curFlags & BTCF_ValidOvfl)!=0 && pCur->aOverflow[offset/ovflSize] ){ + if( (pCur->curFlags & BTCF_ValidOvfl)!=0 + && pCur->aOverflow[offset/ovflSize] + ){ iIdx = (offset/ovflSize); nextPage = pCur->aOverflow[iIdx]; offset = (offset%ovflSize); @@ -55205,7 +59655,9 @@ static int accessPayload( /* If required, populate the overflow page-list cache. */ if( (pCur->curFlags & BTCF_ValidOvfl)!=0 ){ - assert(!pCur->aOverflow[iIdx] || pCur->aOverflow[iIdx]==nextPage); + assert( pCur->aOverflow[iIdx]==0 + || pCur->aOverflow[iIdx]==nextPage + || CORRUPT_DB ); pCur->aOverflow[iIdx] = nextPage; } @@ -55221,6 +59673,7 @@ static int accessPayload( */ assert( eOp!=2 ); assert( pCur->curFlags & BTCF_ValidOvfl ); + assert( pCur->pBtree->db==pBt->db ); if( pCur->aOverflow[iIdx+1] ){ nextPage = pCur->aOverflow[iIdx+1]; }else{ @@ -55248,6 +59701,7 @@ static int accessPayload( ** 4) there is no open write-transaction, and ** 5) the database is not a WAL database, ** 6) all data from the page is being read. + ** 7) at least 4 bytes have already been read into the output buffer ** ** then data can be read directly from the database file into the ** output buffer, bypassing the page-cache altogether. This speeds @@ -55259,9 +59713,11 @@ static int accessPayload( && pBt->inTransaction==TRANS_READ /* (4) */ && (fd = sqlite3PagerFile(pBt->pPager))->pMethods /* (3) */ && pBt->pPage1->aData[19]==0x01 /* (5) */ + && &pBuf[-4]>=pBufStart /* (7) */ ){ u8 aSave[4]; u8 *aWrite = &pBuf[-4]; + assert( aWrite>=pBufStart ); /* hence (7) */ memcpy(aSave, aWrite, 4); rc = sqlite3OsRead(fd, aWrite, a+4, (i64)pBt->pageSize*(nextPage-1)); nextPage = get4byte(aWrite); @@ -55271,7 +59727,7 @@ static int accessPayload( { DbPage *pDbPage; - rc = sqlite3PagerAcquire(pBt->pPager, nextPage, &pDbPage, + rc = sqlite3PagerGet(pBt->pPager, nextPage, &pDbPage, ((eOp&0x01)==0 ? PAGER_GET_READONLY : 0) ); if( rc==SQLITE_OK ){ @@ -55296,7 +59752,7 @@ static int accessPayload( /* ** Read part of the key associated with cursor pCur. Exactly -** "amt" bytes will be transfered into pBuf[]. The transfer +** "amt" bytes will be transferred into pBuf[]. The transfer ** begins at "offset". ** ** The caller must ensure that pCur is pointing to a valid row @@ -55366,14 +59822,19 @@ static const void *fetchPayload( BtCursor *pCur, /* Cursor pointing to entry to read from */ u32 *pAmt /* Write the number of available bytes here */ ){ + u32 amt; assert( pCur!=0 && pCur->iPage>=0 && pCur->apPage[pCur->iPage]); assert( pCur->eState==CURSOR_VALID ); assert( sqlite3_mutex_held(pCur->pBtree->db->mutex) ); assert( cursorHoldsMutex(pCur) ); assert( pCur->aiIdx[pCur->iPage]apPage[pCur->iPage]->nCell ); assert( pCur->info.nSize>0 ); - *pAmt = pCur->info.nLocal; - return (void*)(pCur->info.pCell + pCur->info.nHeader); + assert( pCur->info.pPayload>pCur->apPage[pCur->iPage]->aData || CORRUPT_DB ); + assert( pCur->info.pPayloadapPage[pCur->iPage]->aDataEnd ||CORRUPT_DB); + amt = (int)(pCur->apPage[pCur->iPage]->aDataEnd - pCur->info.pPayload); + if( pCur->info.nLocalinfo.nLocal; + *pAmt = amt; + return (void*)pCur->info.pPayload; } @@ -55409,9 +59870,6 @@ SQLITE_PRIVATE const void *sqlite3BtreeDataFetch(BtCursor *pCur, u32 *pAmt){ ** vice-versa). */ static int moveToChild(BtCursor *pCur, u32 newPgno){ - int rc; - int i = pCur->iPage; - MemPage *pNewPage; BtShared *pBt = pCur->pBt; assert( cursorHoldsMutex(pCur) ); @@ -55421,22 +59879,15 @@ static int moveToChild(BtCursor *pCur, u32 newPgno){ if( pCur->iPage>=(BTCURSOR_MAX_DEPTH-1) ){ return SQLITE_CORRUPT_BKPT; } - rc = getAndInitPage(pBt, newPgno, &pNewPage, - (pCur->curFlags & BTCF_WriteFlag)==0 ? PAGER_GET_READONLY : 0); - if( rc ) return rc; - pCur->apPage[i+1] = pNewPage; - pCur->aiIdx[i+1] = 0; - pCur->iPage++; - pCur->info.nSize = 0; pCur->curFlags &= ~(BTCF_ValidNKey|BTCF_ValidOvfl); - if( pNewPage->nCell<1 || pNewPage->intKey!=pCur->apPage[i]->intKey ){ - return SQLITE_CORRUPT_BKPT; - } - return SQLITE_OK; + pCur->iPage++; + pCur->aiIdx[pCur->iPage] = 0; + return getAndInitPage(pBt, newPgno, &pCur->apPage[pCur->iPage], + pCur, pCur->curPagerFlags); } -#if 0 +#if SQLITE_DEBUG /* ** Page pParent is an internal (non-leaf) tree page. This function ** asserts that page number iChild is the left-child if the iIdx'th @@ -55445,6 +59896,8 @@ static int moveToChild(BtCursor *pCur, u32 newPgno){ ** the page. */ static void assertParentIndex(MemPage *pParent, int iIdx, Pgno iChild){ + if( CORRUPT_DB ) return; /* The conditions tested below might not be true + ** in a corrupt database */ assert( iIdx<=pParent->nCell ); if( iIdx==pParent->nCell ){ assert( get4byte(&pParent->aData[pParent->hdrOffset+8])==iChild ); @@ -55469,25 +59922,15 @@ static void moveToParent(BtCursor *pCur){ assert( pCur->eState==CURSOR_VALID ); assert( pCur->iPage>0 ); assert( pCur->apPage[pCur->iPage] ); - - /* UPDATE: It is actually possible for the condition tested by the assert - ** below to be untrue if the database file is corrupt. This can occur if - ** one cursor has modified page pParent while a reference to it is held - ** by a second cursor. Which can only happen if a single page is linked - ** into more than one b-tree structure in a corrupt database. */ -#if 0 assertParentIndex( pCur->apPage[pCur->iPage-1], pCur->aiIdx[pCur->iPage-1], pCur->apPage[pCur->iPage]->pgno ); -#endif testcase( pCur->aiIdx[pCur->iPage-1] > pCur->apPage[pCur->iPage-1]->nCell ); - - releasePage(pCur->apPage[pCur->iPage]); - pCur->iPage--; pCur->info.nSize = 0; pCur->curFlags &= ~(BTCF_ValidNKey|BTCF_ValidOvfl); + releasePageNotNull(pCur->apPage[pCur->iPage--]); } /* @@ -55528,18 +59971,23 @@ static int moveToRoot(BtCursor *pCur){ } if( pCur->iPage>=0 ){ - while( pCur->iPage ) releasePage(pCur->apPage[pCur->iPage--]); + while( pCur->iPage ){ + assert( pCur->apPage[pCur->iPage]!=0 ); + releasePageNotNull(pCur->apPage[pCur->iPage--]); + } }else if( pCur->pgnoRoot==0 ){ pCur->eState = CURSOR_INVALID; return SQLITE_OK; }else{ + assert( pCur->iPage==(-1) ); rc = getAndInitPage(pCur->pBtree->pBt, pCur->pgnoRoot, &pCur->apPage[0], - (pCur->curFlags & BTCF_WriteFlag)==0 ? PAGER_GET_READONLY : 0); + 0, pCur->curPagerFlags); if( rc!=SQLITE_OK ){ pCur->eState = CURSOR_INVALID; return rc; } pCur->iPage = 0; + pCur->curIntKey = pCur->apPage[0]->intKey; } pRoot = pCur->apPage[0]; assert( pRoot->pgno==pCur->pgnoRoot ); @@ -55616,17 +60064,16 @@ static int moveToRightmost(BtCursor *pCur){ assert( cursorHoldsMutex(pCur) ); assert( pCur->eState==CURSOR_VALID ); - while( rc==SQLITE_OK && !(pPage = pCur->apPage[pCur->iPage])->leaf ){ + while( !(pPage = pCur->apPage[pCur->iPage])->leaf ){ pgno = get4byte(&pPage->aData[pPage->hdrOffset+8]); pCur->aiIdx[pCur->iPage] = pPage->nCell; rc = moveToChild(pCur, pgno); + if( rc ) return rc; } - if( rc==SQLITE_OK ){ - pCur->aiIdx[pCur->iPage] = pPage->nCell-1; - pCur->info.nSize = 0; - pCur->curFlags &= ~BTCF_ValidNKey; - } - return rc; + pCur->aiIdx[pCur->iPage] = pPage->nCell-1; + assert( pCur->info.nSize==0 ); + assert( (pCur->curFlags & BTCF_ValidNKey)==0 ); + return SQLITE_OK; } /* Move the cursor to the first entry in the table. Return SQLITE_OK @@ -55724,6 +60171,8 @@ SQLITE_PRIVATE int sqlite3BtreeLast(BtCursor *pCur, int *pRes){ ** *pRes>0 The cursor is left pointing at an entry that ** is larger than intKey/pIdxKey. ** +** For index tables, the pIdxKey->eqSeen field is set to 1 if there +** exists an entry in the table that exactly matches pIdxKey. */ SQLITE_PRIVATE int sqlite3BtreeMovetoUnpacked( BtCursor *pCur, /* The cursor to be moved */ @@ -55743,7 +60192,7 @@ SQLITE_PRIVATE int sqlite3BtreeMovetoUnpacked( /* If the cursor is already positioned at the point we are trying ** to move to, then just return without doing any work */ if( pCur->eState==CURSOR_VALID && (pCur->curFlags & BTCF_ValidNKey)!=0 - && pCur->apPage[0]->intKey + && pCur->curIntKey ){ if( pCur->info.nKey==intKey ){ *pRes = 0; @@ -55757,7 +60206,7 @@ SQLITE_PRIVATE int sqlite3BtreeMovetoUnpacked( if( pIdxKey ){ xRecordCompare = sqlite3VdbeFindCompare(pIdxKey); - pIdxKey->isCorrupt = 0; + pIdxKey->errCode = 0; assert( pIdxKey->default_rc==1 || pIdxKey->default_rc==0 || pIdxKey->default_rc==-1 @@ -55778,7 +60227,8 @@ SQLITE_PRIVATE int sqlite3BtreeMovetoUnpacked( assert( pCur->pgnoRoot==0 || pCur->apPage[pCur->iPage]->nCell==0 ); return SQLITE_OK; } - assert( pCur->apPage[0]->intKey || pIdxKey ); + assert( pCur->apPage[0]->intKey==pCur->curIntKey ); + assert( pCur->curIntKey || pIdxKey ); for(;;){ int lwr, upr, idx, c; Pgno chldPg; @@ -55801,8 +60251,8 @@ SQLITE_PRIVATE int sqlite3BtreeMovetoUnpacked( if( xRecordCompare==0 ){ for(;;){ i64 nCellKey; - pCell = findCell(pPage, idx) + pPage->childPtrSize; - if( pPage->hasData ){ + pCell = findCellPastPtr(pPage, idx); + if( pPage->intKeyLeaf ){ while( 0x80 <= *(pCell++) ){ if( pCell>=pPage->aDataEnd ) return SQLITE_CORRUPT_BKPT; } @@ -55833,8 +60283,8 @@ SQLITE_PRIVATE int sqlite3BtreeMovetoUnpacked( } }else{ for(;;){ - int nCell; - pCell = findCell(pPage, idx) + pPage->childPtrSize; + int nCell; /* Size of the pCell cell in bytes */ + pCell = findCellPastPtr(pPage, idx); /* The maximum supported page-size is 65536 bytes. This means that ** the maximum number of record bytes stored on an index B-Tree @@ -55850,24 +60300,37 @@ SQLITE_PRIVATE int sqlite3BtreeMovetoUnpacked( ** single byte varint and the record fits entirely on the main ** b-tree page. */ testcase( pCell+nCell+1==pPage->aDataEnd ); - c = xRecordCompare(nCell, (void*)&pCell[1], pIdxKey, 0); + c = xRecordCompare(nCell, (void*)&pCell[1], pIdxKey); }else if( !(pCell[1] & 0x80) && (nCell = ((nCell&0x7f)<<7) + pCell[1])<=pPage->maxLocal ){ /* The record-size field is a 2 byte varint and the record ** fits entirely on the main b-tree page. */ testcase( pCell+nCell+2==pPage->aDataEnd ); - c = xRecordCompare(nCell, (void*)&pCell[2], pIdxKey, 0); + c = xRecordCompare(nCell, (void*)&pCell[2], pIdxKey); }else{ /* The record flows over onto one or more overflow pages. In ** this case the whole cell needs to be parsed, a buffer allocated ** and accessPayload() used to retrieve the record into the - ** buffer before VdbeRecordCompare() can be called. */ + ** buffer before VdbeRecordCompare() can be called. + ** + ** If the record is corrupt, the xRecordCompare routine may read + ** up to two varints past the end of the buffer. An extra 18 + ** bytes of padding is allocated at the end of the buffer in + ** case this happens. */ void *pCellKey; u8 * const pCellBody = pCell - pPage->childPtrSize; - btreeParseCellPtr(pPage, pCellBody, &pCur->info); + pPage->xParseCell(pPage, pCellBody, &pCur->info); nCell = (int)pCur->info.nKey; - pCellKey = sqlite3Malloc( nCell ); + testcase( nCell<0 ); /* True if key size is 2^32 or more */ + testcase( nCell==0 ); /* Invalid key size: 0x80 0x80 0x00 */ + testcase( nCell==1 ); /* Invalid key size: 0x80 0x80 0x01 */ + testcase( nCell==2 ); /* Minimum legal index key size */ + if( nCell<2 ){ + rc = SQLITE_CORRUPT_BKPT; + goto moveto_finish; + } + pCellKey = sqlite3Malloc( nCell+18 ); if( pCellKey==0 ){ rc = SQLITE_NOMEM; goto moveto_finish; @@ -55878,10 +60341,13 @@ SQLITE_PRIVATE int sqlite3BtreeMovetoUnpacked( sqlite3_free(pCellKey); goto moveto_finish; } - c = xRecordCompare(nCell, pCellKey, pIdxKey, 0); + c = xRecordCompare(nCell, pCellKey, pIdxKey); sqlite3_free(pCellKey); } - assert( pIdxKey->isCorrupt==0 || c==0 ); + assert( + (pIdxKey->errCode!=SQLITE_CORRUPT || c==0) + && (pIdxKey->errCode!=SQLITE_NOMEM || pCur->pBtree->db->mallocFailed) + ); if( c<0 ){ lwr = idx+1; }else if( c>0 ){ @@ -55891,7 +60357,7 @@ SQLITE_PRIVATE int sqlite3BtreeMovetoUnpacked( *pRes = 0; rc = SQLITE_OK; pCur->aiIdx[pCur->iPage] = (u16)idx; - if( pIdxKey->isCorrupt ) rc = SQLITE_CORRUPT; + if( pIdxKey->errCode ) rc = SQLITE_CORRUPT; goto moveto_finish; } if( lwr>upr ) break; @@ -55946,6 +60412,12 @@ SQLITE_PRIVATE int sqlite3BtreeEof(BtCursor *pCur){ ** was already pointing to the last entry in the database before ** this routine was called, then set *pRes=1. ** +** The main entry point is sqlite3BtreeNext(). That routine is optimized +** for the common case of merely incrementing the cell counter BtCursor.aiIdx +** to the next cell on the current page. The (slower) btreeNext() helper +** routine is called when it is necessary to move to a different page or +** to restore the cursor. +** ** The calling function will set *pRes to 0 or 1. The initial *pRes value ** will be 1 if the cursor being stepped corresponds to an SQL index and ** if this routine could have been skipped if that SQL index had been @@ -55955,20 +60427,18 @@ SQLITE_PRIVATE int sqlite3BtreeEof(BtCursor *pCur){ ** SQLite btree implementation does not. (Note that the comdb2 btree ** implementation does use this hint, however.) */ -SQLITE_PRIVATE int sqlite3BtreeNext(BtCursor *pCur, int *pRes){ +static SQLITE_NOINLINE int btreeNext(BtCursor *pCur, int *pRes){ int rc; int idx; MemPage *pPage; assert( cursorHoldsMutex(pCur) ); - assert( pRes!=0 ); - assert( *pRes==0 || *pRes==1 ); assert( pCur->skipNext==0 || pCur->eState!=CURSOR_VALID ); + assert( *pRes==0 ); if( pCur->eState!=CURSOR_VALID ){ - invalidateOverflowCache(pCur); + assert( (pCur->curFlags & BTCF_ValidOvfl)==0 ); rc = restoreCursorPosition(pCur); if( rc!=SQLITE_OK ){ - *pRes = 0; return rc; } if( CURSOR_INVALID==pCur->eState ){ @@ -55980,7 +60450,6 @@ SQLITE_PRIVATE int sqlite3BtreeNext(BtCursor *pCur, int *pRes){ pCur->eState = CURSOR_VALID; if( pCur->skipNext>0 ){ pCur->skipNext = 0; - *pRes = 0; return SQLITE_OK; } pCur->skipNext = 0; @@ -55998,18 +60467,11 @@ SQLITE_PRIVATE int sqlite3BtreeNext(BtCursor *pCur, int *pRes){ ** page into more than one b-tree structure. */ testcase( idx>pPage->nCell ); - pCur->info.nSize = 0; - pCur->curFlags &= ~(BTCF_ValidNKey|BTCF_ValidOvfl); if( idx>=pPage->nCell ){ if( !pPage->leaf ){ rc = moveToChild(pCur, get4byte(&pPage->aData[pPage->hdrOffset+8])); - if( rc ){ - *pRes = 0; - return rc; - } - rc = moveToLeftmost(pCur); - *pRes = 0; - return rc; + if( rc ) return rc; + return moveToLeftmost(pCur); } do{ if( pCur->iPage==0 ){ @@ -56020,22 +60482,39 @@ SQLITE_PRIVATE int sqlite3BtreeNext(BtCursor *pCur, int *pRes){ moveToParent(pCur); pPage = pCur->apPage[pCur->iPage]; }while( pCur->aiIdx[pCur->iPage]>=pPage->nCell ); - *pRes = 0; if( pPage->intKey ){ - rc = sqlite3BtreeNext(pCur, pRes); + return sqlite3BtreeNext(pCur, pRes); }else{ - rc = SQLITE_OK; + return SQLITE_OK; } - return rc; } - *pRes = 0; if( pPage->leaf ){ return SQLITE_OK; + }else{ + return moveToLeftmost(pCur); + } +} +SQLITE_PRIVATE int sqlite3BtreeNext(BtCursor *pCur, int *pRes){ + MemPage *pPage; + assert( cursorHoldsMutex(pCur) ); + assert( pRes!=0 ); + assert( *pRes==0 || *pRes==1 ); + assert( pCur->skipNext==0 || pCur->eState!=CURSOR_VALID ); + pCur->info.nSize = 0; + pCur->curFlags &= ~(BTCF_ValidNKey|BTCF_ValidOvfl); + *pRes = 0; + if( pCur->eState!=CURSOR_VALID ) return btreeNext(pCur, pRes); + pPage = pCur->apPage[pCur->iPage]; + if( (++pCur->aiIdx[pCur->iPage])>=pPage->nCell ){ + pCur->aiIdx[pCur->iPage]--; + return btreeNext(pCur, pRes); + } + if( pPage->leaf ){ + return SQLITE_OK; + }else{ + return moveToLeftmost(pCur); } - rc = moveToLeftmost(pCur); - return rc; } - /* ** Step the cursor to the back to the previous entry in the database. If @@ -56043,6 +60522,12 @@ SQLITE_PRIVATE int sqlite3BtreeNext(BtCursor *pCur, int *pRes){ ** was already pointing to the first entry in the database before ** this routine was called, then set *pRes=1. ** +** The main entry point is sqlite3BtreePrevious(). That routine is optimized +** for the common case of merely decrementing the cell counter BtCursor.aiIdx +** to the previous cell on the current page. The (slower) btreePrevious() +** helper routine is called when it is necessary to move to a different page +** or to restore the cursor. +** ** The calling function will set *pRes to 0 or 1. The initial *pRes value ** will be 1 if the cursor being stepped corresponds to an SQL index and ** if this routine could have been skipped if that SQL index had been @@ -56052,22 +60537,20 @@ SQLITE_PRIVATE int sqlite3BtreeNext(BtCursor *pCur, int *pRes){ ** SQLite btree implementation does not. (Note that the comdb2 btree ** implementation does use this hint, however.) */ -SQLITE_PRIVATE int sqlite3BtreePrevious(BtCursor *pCur, int *pRes){ +static SQLITE_NOINLINE int btreePrevious(BtCursor *pCur, int *pRes){ int rc; MemPage *pPage; assert( cursorHoldsMutex(pCur) ); assert( pRes!=0 ); - assert( *pRes==0 || *pRes==1 ); + assert( *pRes==0 ); assert( pCur->skipNext==0 || pCur->eState!=CURSOR_VALID ); - pCur->curFlags &= ~(BTCF_AtLast|BTCF_ValidOvfl); + assert( (pCur->curFlags & (BTCF_AtLast|BTCF_ValidOvfl|BTCF_ValidNKey))==0 ); + assert( pCur->info.nSize==0 ); if( pCur->eState!=CURSOR_VALID ){ - if( ALWAYS(pCur->eState>=CURSOR_REQUIRESEEK) ){ - rc = btreeRestoreCursorPosition(pCur); - if( rc!=SQLITE_OK ){ - *pRes = 0; - return rc; - } + rc = restoreCursorPosition(pCur); + if( rc!=SQLITE_OK ){ + return rc; } if( CURSOR_INVALID==pCur->eState ){ *pRes = 1; @@ -56078,7 +60561,6 @@ SQLITE_PRIVATE int sqlite3BtreePrevious(BtCursor *pCur, int *pRes){ pCur->eState = CURSOR_VALID; if( pCur->skipNext<0 ){ pCur->skipNext = 0; - *pRes = 0; return SQLITE_OK; } pCur->skipNext = 0; @@ -56090,10 +60572,7 @@ SQLITE_PRIVATE int sqlite3BtreePrevious(BtCursor *pCur, int *pRes){ if( !pPage->leaf ){ int idx = pCur->aiIdx[pCur->iPage]; rc = moveToChild(pCur, get4byte(findCell(pPage, idx))); - if( rc ){ - *pRes = 0; - return rc; - } + if( rc ) return rc; rc = moveToRightmost(pCur); }else{ while( pCur->aiIdx[pCur->iPage]==0 ){ @@ -56104,8 +60583,8 @@ SQLITE_PRIVATE int sqlite3BtreePrevious(BtCursor *pCur, int *pRes){ } moveToParent(pCur); } - pCur->info.nSize = 0; - pCur->curFlags &= ~(BTCF_ValidNKey|BTCF_ValidOvfl); + assert( pCur->info.nSize==0 ); + assert( (pCur->curFlags & (BTCF_ValidNKey|BTCF_ValidOvfl))==0 ); pCur->aiIdx[pCur->iPage]--; pPage = pCur->apPage[pCur->iPage]; @@ -56115,9 +60594,25 @@ SQLITE_PRIVATE int sqlite3BtreePrevious(BtCursor *pCur, int *pRes){ rc = SQLITE_OK; } } - *pRes = 0; return rc; } +SQLITE_PRIVATE int sqlite3BtreePrevious(BtCursor *pCur, int *pRes){ + assert( cursorHoldsMutex(pCur) ); + assert( pRes!=0 ); + assert( *pRes==0 || *pRes==1 ); + assert( pCur->skipNext==0 || pCur->eState!=CURSOR_VALID ); + *pRes = 0; + pCur->curFlags &= ~(BTCF_AtLast|BTCF_ValidOvfl|BTCF_ValidNKey); + pCur->info.nSize = 0; + if( pCur->eState!=CURSOR_VALID + || pCur->aiIdx[pCur->iPage]==0 + || pCur->apPage[pCur->iPage]->leaf==0 + ){ + return btreePrevious(pCur, pRes); + } + pCur->aiIdx[pCur->iPage]--; + return SQLITE_OK; +} /* ** Allocate a new page from the database file. @@ -56128,8 +60623,7 @@ SQLITE_PRIVATE int sqlite3BtreePrevious(BtCursor *pCur, int *pRes){ ** sqlite3PagerUnref() on the new page when it is done. ** ** SQLITE_OK is returned on success. Any other return value indicates -** an error. *ppPage and *pPgno are undefined in the event of an error. -** Do not invoke sqlite3PagerUnref() on *ppPage if an error is returned. +** an error. *ppPage is set to NULL in the event of an error. ** ** If the "nearby" parameter is not 0, then an effort is made to ** locate a page close to the page number "nearby". This can be used in an @@ -56161,6 +60655,8 @@ static int allocateBtreePage( assert( eMode==BTALLOC_ANY || (nearby>0 && IfNotOmitAV(pBt->autoVacuum)) ); pPage1 = pBt->pPage1; mxPage = btreePagecount(pBt); + /* EVIDENCE-OF: R-05119-02637 The 4-byte big-endian integer at offset 36 + ** stores stores the total number of pages on the freelist. */ n = get4byte(&pPage1->aData[36]); testcase( n==mxPage-1 ); if( n>=mxPage ){ @@ -56170,6 +60666,7 @@ static int allocateBtreePage( /* There are pages on the freelist. Reuse one of those pages. */ Pgno iTrunk; u8 searchList = 0; /* If the free-list must be searched for 'nearby' */ + u32 nSearch = 0; /* Count of the number of search attempts */ /* If eMode==BTALLOC_EXACT and a query of the pointer-map ** shows that the page 'nearby' is somewhere on the free-list, then @@ -56207,15 +60704,21 @@ static int allocateBtreePage( do { pPrevTrunk = pTrunk; if( pPrevTrunk ){ + /* EVIDENCE-OF: R-01506-11053 The first integer on a freelist trunk page + ** is the page number of the next freelist trunk page in the list or + ** zero if this is the last freelist trunk page. */ iTrunk = get4byte(&pPrevTrunk->aData[0]); }else{ + /* EVIDENCE-OF: R-59841-13798 The 4-byte big-endian integer at offset 32 + ** stores the page number of the first page of the freelist, or zero if + ** the freelist is empty. */ iTrunk = get4byte(&pPage1->aData[32]); } testcase( iTrunk==mxPage ); - if( iTrunk>mxPage ){ + if( iTrunk>mxPage || nSearch++ > n ){ rc = SQLITE_CORRUPT_BKPT; }else{ - rc = btreeGetPage(pBt, iTrunk, &pTrunk, 0); + rc = btreeGetUnusedPage(pBt, iTrunk, &pTrunk, 0); } if( rc ){ pTrunk = 0; @@ -56223,8 +60726,9 @@ static int allocateBtreePage( } assert( pTrunk!=0 ); assert( pTrunk->aData!=0 ); - - k = get4byte(&pTrunk->aData[4]); /* # of leaves on this trunk page */ + /* EVIDENCE-OF: R-13523-04394 The second integer on a freelist trunk page + ** is the number of leaf page pointers to follow. */ + k = get4byte(&pTrunk->aData[4]); if( k==0 && !searchList ){ /* The trunk has no leaves and the list is not being searched. ** So extract the trunk page itself and use it as the newly @@ -56279,7 +60783,7 @@ static int allocateBtreePage( goto end_allocate_page; } testcase( iNewTrunk==mxPage ); - rc = btreeGetPage(pBt, iNewTrunk, &pNewTrunk, 0); + rc = btreeGetUnusedPage(pBt, iNewTrunk, &pNewTrunk, 0); if( rc!=SQLITE_OK ){ goto end_allocate_page; } @@ -56358,12 +60862,13 @@ static int allocateBtreePage( memcpy(&aData[8+closest*4], &aData[4+k*4], 4); } put4byte(&aData[4], k-1); - noContent = !btreeGetHasContent(pBt, *pPgno) ? PAGER_GET_NOCONTENT : 0; - rc = btreeGetPage(pBt, *pPgno, ppPage, noContent); + noContent = !btreeGetHasContent(pBt, *pPgno)? PAGER_GET_NOCONTENT : 0; + rc = btreeGetUnusedPage(pBt, *pPgno, ppPage, noContent); if( rc==SQLITE_OK ){ rc = sqlite3PagerWrite((*ppPage)->pDbPage); if( rc!=SQLITE_OK ){ releasePage(*ppPage); + *ppPage = 0; } } searchList = 0; @@ -56391,7 +60896,7 @@ static int allocateBtreePage( ** here are confined to those pages that lie between the end of the ** database image and the end of the database file. */ - int bNoContent = (0==IfNotOmitAV(pBt->bDoTruncate)) ? PAGER_GET_NOCONTENT : 0; + int bNoContent = (0==IfNotOmitAV(pBt->bDoTruncate))? PAGER_GET_NOCONTENT:0; rc = sqlite3PagerWrite(pBt->pPage1->pDbPage); if( rc ) return rc; @@ -56407,7 +60912,7 @@ static int allocateBtreePage( MemPage *pPg = 0; TRACE(("ALLOCATE: %d from end of file (pointer-map page)\n", pBt->nPage)); assert( pBt->nPage!=PENDING_BYTE_PAGE(pBt) ); - rc = btreeGetPage(pBt, pBt->nPage, &pPg, bNoContent); + rc = btreeGetUnusedPage(pBt, pBt->nPage, &pPg, bNoContent); if( rc==SQLITE_OK ){ rc = sqlite3PagerWrite(pPg->pDbPage); releasePage(pPg); @@ -56421,11 +60926,12 @@ static int allocateBtreePage( *pPgno = pBt->nPage; assert( *pPgno!=PENDING_BYTE_PAGE(pBt) ); - rc = btreeGetPage(pBt, *pPgno, ppPage, bNoContent); + rc = btreeGetUnusedPage(pBt, *pPgno, ppPage, bNoContent); if( rc ) return rc; rc = sqlite3PagerWrite((*ppPage)->pDbPage); if( rc!=SQLITE_OK ){ releasePage(*ppPage); + *ppPage = 0; } TRACE(("ALLOCATE: %d from end of file\n", *pPgno)); } @@ -56435,17 +60941,8 @@ static int allocateBtreePage( end_allocate_page: releasePage(pTrunk); releasePage(pPrevTrunk); - if( rc==SQLITE_OK ){ - if( sqlite3PagerPageRefcount((*ppPage)->pDbPage)>1 ){ - releasePage(*ppPage); - *ppPage = 0; - return SQLITE_CORRUPT_BKPT; - } - (*ppPage)->isInit = 0; - }else{ - *ppPage = 0; - } - assert( rc!=SQLITE_OK || sqlite3PagerIswriteable((*ppPage)->pDbPage) ); + assert( rc!=SQLITE_OK || sqlite3PagerPageRefcount((*ppPage)->pDbPage)<=1 ); + assert( rc!=SQLITE_OK || (*ppPage)->isInit==0 ); return rc; } @@ -56470,9 +60967,10 @@ static int freePage2(BtShared *pBt, MemPage *pMemPage, Pgno iPage){ int nFree; /* Initial number of pages on free-list */ assert( sqlite3_mutex_held(pBt->mutex) ); - assert( iPage>1 ); + assert( CORRUPT_DB || iPage>1 ); assert( !pMemPage || pMemPage->pgno==iPage ); + if( iPage<2 ) return SQLITE_CORRUPT_BKPT; if( pMemPage ){ pPage = pMemPage; sqlite3PagerRef(pPage->pDbPage); @@ -56542,6 +61040,11 @@ static int freePage2(BtShared *pBt, MemPage *pMemPage, Pgno iPage){ ** for now. At some point in the future (once everyone has upgraded ** to 3.6.0 or later) we should consider fixing the conditional above ** to read "usableSize/4-2" instead of "usableSize/4-8". + ** + ** EVIDENCE-OF: R-19920-11576 However, newer versions of SQLite still + ** avoid using the last six entries in the freelist trunk page array in + ** order that database files created by newer versions of SQLite can be + ** read by older versions of SQLite. */ rc = sqlite3PagerWrite(pTrunk->pDbPage); if( rc==SQLITE_OK ){ @@ -56590,9 +61093,15 @@ static void freePage(MemPage *pPage, int *pRC){ } /* -** Free any overflow pages associated with the given Cell. +** Free any overflow pages associated with the given Cell. Write the +** local Cell size (the number of bytes on the original page, omitting +** overflow) into *pnSize. */ -static int clearCell(MemPage *pPage, unsigned char *pCell){ +static int clearCell( + MemPage *pPage, /* The page that contains the Cell */ + unsigned char *pCell, /* First byte of the Cell */ + u16 *pnSize /* Write the size of the Cell here */ +){ BtShared *pBt = pPage->pBt; CellInfo info; Pgno ovflPgno; @@ -56601,18 +61110,21 @@ static int clearCell(MemPage *pPage, unsigned char *pCell){ u32 ovflPageSize; assert( sqlite3_mutex_held(pPage->pBt->mutex) ); - btreeParseCellPtr(pPage, pCell, &info); - if( info.iOverflow==0 ){ + pPage->xParseCell(pPage, pCell, &info); + *pnSize = info.nSize; + if( info.nLocal==info.nPayload ){ return SQLITE_OK; /* No overflow pages. Return without doing anything */ } - if( pCell+info.iOverflow+3 > pPage->aData+pPage->maskPage ){ + if( pCell+info.nSize-1 > pPage->aData+pPage->maskPage ){ return SQLITE_CORRUPT_BKPT; /* Cell extends past end of page */ } - ovflPgno = get4byte(&pCell[info.iOverflow]); + ovflPgno = get4byte(pCell + info.nSize - 4); assert( pBt->usableSize > 4 ); ovflPageSize = pBt->usableSize - 4; nOvfl = (info.nPayload - info.nLocal + ovflPageSize - 1)/ovflPageSize; - assert( ovflPgno==0 || nOvfl>0 ); + assert( nOvfl>0 || + (CORRUPT_DB && (info.nPayload + ovflPageSize)pBt; Pgno pgnoOvfl = 0; int nHeader; - CellInfo info; assert( sqlite3_mutex_held(pPage->pBt->mutex) ); @@ -56695,40 +61206,71 @@ static int fillInCell( || sqlite3PagerIswriteable(pPage->pDbPage) ); /* Fill in the header. */ - nHeader = 0; - if( !pPage->leaf ){ - nHeader += 4; - } - if( pPage->hasData ){ - nHeader += putVarint32(&pCell[nHeader], nData+nZero); + nHeader = pPage->childPtrSize; + nPayload = nData + nZero; + if( pPage->intKeyLeaf ){ + nHeader += putVarint32(&pCell[nHeader], nPayload); }else{ - nData = nZero = 0; + assert( nData==0 ); + assert( nZero==0 ); } nHeader += putVarint(&pCell[nHeader], *(u64*)&nKey); - btreeParseCellPtr(pPage, pCell, &info); - assert( info.nHeader==nHeader ); - assert( info.nKey==nKey ); - assert( info.nData==(u32)(nData+nZero) ); - /* Fill in the payload */ - nPayload = nData + nZero; + /* Fill in the payload size */ if( pPage->intKey ){ pSrc = pData; nSrc = nData; nData = 0; }else{ - if( NEVER(nKey>0x7fffffff || pKey==0) ){ - return SQLITE_CORRUPT_BKPT; - } - nPayload += (int)nKey; + assert( nKey<=0x7fffffff && pKey!=0 ); + nPayload = (int)nKey; pSrc = pKey; nSrc = (int)nKey; } - *pnSize = info.nSize; - spaceLeft = info.nLocal; + if( nPayload<=pPage->maxLocal ){ + n = nHeader + nPayload; + testcase( n==3 ); + testcase( n==4 ); + if( n<4 ) n = 4; + *pnSize = n; + spaceLeft = nPayload; + pPrior = pCell; + }else{ + int mn = pPage->minLocal; + n = mn + (nPayload - mn) % (pPage->pBt->usableSize - 4); + testcase( n==pPage->maxLocal ); + testcase( n==pPage->maxLocal+1 ); + if( n > pPage->maxLocal ) n = mn; + spaceLeft = n; + *pnSize = n + nHeader + 4; + pPrior = &pCell[nHeader+n]; + } pPayload = &pCell[nHeader]; - pPrior = &pCell[info.iOverflow]; + /* At this point variables should be set as follows: + ** + ** nPayload Total payload size in bytes + ** pPayload Begin writing payload here + ** spaceLeft Space available at pPayload. If nPayload>spaceLeft, + ** that means content must spill into overflow pages. + ** *pnSize Size of the local cell (not counting overflow pages) + ** pPrior Where to write the pgno of the first overflow page + ** + ** Use a call to btreeParseCellPtr() to verify that the values above + ** were computed correctly. + */ +#if SQLITE_DEBUG + { + CellInfo info; + pPage->xParseCell(pPage, pCell, &info); + assert( nHeader=(int)(info.pPayload - pCell) ); + assert( info.nKey==nKey ); + assert( *pnSize == info.nSize ); + assert( spaceLeft == info.nLocal ); + } +#endif + + /* Write the payload into the local Cell and any extra into overflow pages */ while( nPayload>0 ){ if( spaceLeft==0 ){ #ifndef SQLITE_OMIT_AUTOVACUUM @@ -56834,7 +61376,7 @@ static void dropCell(MemPage *pPage, int idx, int sz, int *pRC){ if( *pRC ) return; assert( idx>=0 && idxnCell ); - assert( sz==cellSize(pPage, idx) ); + assert( CORRUPT_DB || sz==cellSize(pPage, idx) ); assert( sqlite3PagerIswriteable(pPage->pDbPage) ); assert( sqlite3_mutex_held(pPage->pBt->mutex) ); data = pPage->aData; @@ -56853,9 +61395,17 @@ static void dropCell(MemPage *pPage, int idx, int sz, int *pRC){ return; } pPage->nCell--; - memmove(ptr, ptr+2, 2*(pPage->nCell - idx)); - put2byte(&data[hdr+3], pPage->nCell); - pPage->nFree += 2; + if( pPage->nCell==0 ){ + memset(&data[hdr+1], 0, 4); + data[hdr+7] = 0; + put2byte(&data[hdr+5], pPage->pBt->usableSize); + pPage->nFree = pPage->pBt->usableSize - pPage->hdrOffset + - pPage->childPtrSize - 8; + }else{ + memmove(ptr, ptr+2, 2*(pPage->nCell - idx)); + put2byte(&data[hdr+3], pPage->nCell); + pPage->nFree += 2; + } } /* @@ -56869,11 +61419,6 @@ static void dropCell(MemPage *pPage, int idx, int sz, int *pRC){ ** in pTemp or the original pCell) and also record its index. ** Allocating a new entry in pPage->aCell[] implies that ** pPage->nOverflow is incremented. -** -** If nSkip is non-zero, then do not copy the first nSkip bytes of the -** cell. The caller will overwrite them after this function returns. If -** nSkip is non-zero, then pCell may not point to an invalid memory location -** (but pCell+nSkip is always valid). */ static void insertCell( MemPage *pPage, /* Page into which we are copying */ @@ -56886,16 +61431,14 @@ static void insertCell( ){ int idx = 0; /* Where to write new cell content in data[] */ int j; /* Loop counter */ - int end; /* First byte past the last cell pointer in data[] */ - int ins; /* Index in data[] where new cell pointer is inserted */ - int cellOffset; /* Address of first cell pointer in data[] */ u8 *data; /* The content of the whole page */ - int nSkip = (iChild ? 4 : 0); + u8 *pIns; /* The point in pPage->aCellIdx[] where no cell inserted */ if( *pRC ) return; assert( i>=0 && i<=pPage->nCell+pPage->nOverflow ); - assert( pPage->nCell<=MX_CELL(pPage->pBt) && MX_CELL(pPage->pBt)<=10921 ); + assert( MX_CELL(pPage->pBt)<=10921 ); + assert( pPage->nCell<=MX_CELL(pPage->pBt) || CORRUPT_DB ); assert( pPage->nOverflow<=ArraySize(pPage->apOvfl) ); assert( ArraySize(pPage->apOvfl)==ArraySize(pPage->aiOvfl) ); assert( sqlite3_mutex_held(pPage->pBt->mutex) ); @@ -56904,10 +61447,10 @@ static void insertCell( ** wanted to be less than 4 but got rounded up to 4 on the leaf, then size ** might be less than 8 (leaf-size + pointer) on the interior node. Hence ** the term after the || in the following assert(). */ - assert( sz==cellSizePtr(pPage, pCell) || (sz==8 && iChild>0) ); + assert( sz==pPage->xCellSize(pPage, pCell) || (sz==8 && iChild>0) ); if( pPage->nOverflow || sz+2>pPage->nFree ){ if( pTemp ){ - memcpy(pTemp+nSkip, pCell+nSkip, sz-nSkip); + memcpy(pTemp, pCell, sz); pCell = pTemp; } if( iChild ){ @@ -56917,6 +61460,14 @@ static void insertCell( assert( j<(int)(sizeof(pPage->apOvfl)/sizeof(pPage->apOvfl[0])) ); pPage->apOvfl[j] = pCell; pPage->aiOvfl[j] = (u16)i; + + /* When multiple overflows occur, they are always sequential and in + ** sorted order. This invariants arise because multiple overflows can + ** only occur when inserting divider cells into the parent page during + ** balancing, and the dividers are adjacent and sorted. + */ + assert( j==0 || pPage->aiOvfl[j-1]<(u16)i ); /* Overflows in sorted order */ + assert( j==0 || i==pPage->aiOvfl[j-1]+1 ); /* Overflows are sequential */ }else{ int rc = sqlite3PagerWrite(pPage->pDbPage); if( rc!=SQLITE_OK ){ @@ -56925,24 +61476,26 @@ static void insertCell( } assert( sqlite3PagerIswriteable(pPage->pDbPage) ); data = pPage->aData; - cellOffset = pPage->cellOffset; - end = cellOffset + 2*pPage->nCell; - ins = cellOffset + 2*i; + assert( &data[pPage->cellOffset]==pPage->aCellIdx ); rc = allocateSpace(pPage, sz, &idx); if( rc ){ *pRC = rc; return; } - /* The allocateSpace() routine guarantees the following two properties - ** if it returns success */ - assert( idx >= end+2 ); + /* The allocateSpace() routine guarantees the following properties + ** if it returns successfully */ + assert( idx >= 0 ); + assert( idx >= pPage->cellOffset+2*pPage->nCell+2 || CORRUPT_DB ); assert( idx+sz <= (int)pPage->pBt->usableSize ); - pPage->nCell++; pPage->nFree -= (u16)(2 + sz); - memcpy(&data[idx+nSkip], pCell+nSkip, sz-nSkip); + memcpy(&data[idx], pCell, sz); if( iChild ){ put4byte(&data[idx], iChild); } - memmove(&data[ins+2], &data[ins], end-ins); - put2byte(&data[ins], idx); - put2byte(&data[pPage->hdrOffset+3], pPage->nCell); + pIns = pPage->aCellIdx + i*2; + memmove(pIns+2, pIns, 2*(pPage->nCell - i)); + put2byte(pIns, idx); + pPage->nCell++; + /* increment the cell count */ + if( (++data[pPage->hdrOffset+4])==0 ) data[pPage->hdrOffset+3]++; + assert( get2byte(&data[pPage->hdrOffset+3])==pPage->nCell ); #ifndef SQLITE_OMIT_AUTOVACUUM if( pPage->pBt->autoVacuum ){ /* The cell may contain a pointer to an overflow page. If so, write @@ -56955,45 +61508,328 @@ static void insertCell( } /* -** Add a list of cells to a page. The page should be initially empty. -** The cells are guaranteed to fit on the page. +** A CellArray object contains a cache of pointers and sizes for a +** consecutive sequence of cells that might be held multiple pages. */ -static void assemblePage( - MemPage *pPage, /* The page to be assemblied */ - int nCell, /* The number of cells to add to this page */ - u8 **apCell, /* Pointers to cell bodies */ - u16 *aSize /* Sizes of the cells */ -){ - int i; /* Loop counter */ - u8 *pCellptr; /* Address of next cell pointer */ - int cellbody; /* Address of next cell body */ - u8 * const data = pPage->aData; /* Pointer to data for pPage */ - const int hdr = pPage->hdrOffset; /* Offset of header on pPage */ - const int nUsable = pPage->pBt->usableSize; /* Usable size of page */ +typedef struct CellArray CellArray; +struct CellArray { + int nCell; /* Number of cells in apCell[] */ + MemPage *pRef; /* Reference page */ + u8 **apCell; /* All cells begin balanced */ + u16 *szCell; /* Local size of all cells in apCell[] */ +}; - assert( pPage->nOverflow==0 ); - assert( sqlite3_mutex_held(pPage->pBt->mutex) ); - assert( nCell>=0 && nCell<=(int)MX_CELL(pPage->pBt) - && (int)MX_CELL(pPage->pBt)<=10921); - assert( sqlite3PagerIswriteable(pPage->pDbPage) ); - - /* Check that the page has just been zeroed by zeroPage() */ - assert( pPage->nCell==0 ); - assert( get2byteNotZero(&data[hdr+5])==nUsable ); - - pCellptr = &pPage->aCellIdx[nCell*2]; - cellbody = nUsable; - for(i=nCell-1; i>=0; i--){ - u16 sz = aSize[i]; - pCellptr -= 2; - cellbody -= sz; - put2byte(pCellptr, cellbody); - memcpy(&data[cellbody], apCell[i], sz); +/* +** Make sure the cell sizes at idx, idx+1, ..., idx+N-1 have been +** computed. +*/ +static void populateCellCache(CellArray *p, int idx, int N){ + assert( idx>=0 && idx+N<=p->nCell ); + while( N>0 ){ + assert( p->apCell[idx]!=0 ); + if( p->szCell[idx]==0 ){ + p->szCell[idx] = p->pRef->xCellSize(p->pRef, p->apCell[idx]); + }else{ + assert( CORRUPT_DB || + p->szCell[idx]==p->pRef->xCellSize(p->pRef, p->apCell[idx]) ); + } + idx++; + N--; } - put2byte(&data[hdr+3], nCell); - put2byte(&data[hdr+5], cellbody); - pPage->nFree -= (nCell*2 + nUsable - cellbody); - pPage->nCell = (u16)nCell; +} + +/* +** Return the size of the Nth element of the cell array +*/ +static SQLITE_NOINLINE u16 computeCellSize(CellArray *p, int N){ + assert( N>=0 && NnCell ); + assert( p->szCell[N]==0 ); + p->szCell[N] = p->pRef->xCellSize(p->pRef, p->apCell[N]); + return p->szCell[N]; +} +static u16 cachedCellSize(CellArray *p, int N){ + assert( N>=0 && NnCell ); + if( p->szCell[N] ) return p->szCell[N]; + return computeCellSize(p, N); +} + +/* +** Array apCell[] contains pointers to nCell b-tree page cells. The +** szCell[] array contains the size in bytes of each cell. This function +** replaces the current contents of page pPg with the contents of the cell +** array. +** +** Some of the cells in apCell[] may currently be stored in pPg. This +** function works around problems caused by this by making a copy of any +** such cells before overwriting the page data. +** +** The MemPage.nFree field is invalidated by this function. It is the +** responsibility of the caller to set it correctly. +*/ +static int rebuildPage( + MemPage *pPg, /* Edit this page */ + int nCell, /* Final number of cells on page */ + u8 **apCell, /* Array of cells */ + u16 *szCell /* Array of cell sizes */ +){ + const int hdr = pPg->hdrOffset; /* Offset of header on pPg */ + u8 * const aData = pPg->aData; /* Pointer to data for pPg */ + const int usableSize = pPg->pBt->usableSize; + u8 * const pEnd = &aData[usableSize]; + int i; + u8 *pCellptr = pPg->aCellIdx; + u8 *pTmp = sqlite3PagerTempSpace(pPg->pBt->pPager); + u8 *pData; + + i = get2byte(&aData[hdr+5]); + memcpy(&pTmp[i], &aData[i], usableSize - i); + + pData = pEnd; + for(i=0; ixCellSize(pPg, pCell) || CORRUPT_DB ); + testcase( szCell[i]!=pPg->xCellSize(pPg,pCell) ); + } + + /* The pPg->nFree field is now set incorrectly. The caller will fix it. */ + pPg->nCell = nCell; + pPg->nOverflow = 0; + + put2byte(&aData[hdr+1], 0); + put2byte(&aData[hdr+3], pPg->nCell); + put2byte(&aData[hdr+5], pData - aData); + aData[hdr+7] = 0x00; + return SQLITE_OK; +} + +/* +** Array apCell[] contains nCell pointers to b-tree cells. Array szCell +** contains the size in bytes of each such cell. This function attempts to +** add the cells stored in the array to page pPg. If it cannot (because +** the page needs to be defragmented before the cells will fit), non-zero +** is returned. Otherwise, if the cells are added successfully, zero is +** returned. +** +** Argument pCellptr points to the first entry in the cell-pointer array +** (part of page pPg) to populate. After cell apCell[0] is written to the +** page body, a 16-bit offset is written to pCellptr. And so on, for each +** cell in the array. It is the responsibility of the caller to ensure +** that it is safe to overwrite this part of the cell-pointer array. +** +** When this function is called, *ppData points to the start of the +** content area on page pPg. If the size of the content area is extended, +** *ppData is updated to point to the new start of the content area +** before returning. +** +** Finally, argument pBegin points to the byte immediately following the +** end of the space required by this page for the cell-pointer area (for +** all cells - not just those inserted by the current call). If the content +** area must be extended to before this point in order to accomodate all +** cells in apCell[], then the cells do not fit and non-zero is returned. +*/ +static int pageInsertArray( + MemPage *pPg, /* Page to add cells to */ + u8 *pBegin, /* End of cell-pointer array */ + u8 **ppData, /* IN/OUT: Page content -area pointer */ + u8 *pCellptr, /* Pointer to cell-pointer area */ + int iFirst, /* Index of first cell to add */ + int nCell, /* Number of cells to add to pPg */ + CellArray *pCArray /* Array of cells */ +){ + int i; + u8 *aData = pPg->aData; + u8 *pData = *ppData; + int iEnd = iFirst + nCell; + assert( CORRUPT_DB || pPg->hdrOffset==0 ); /* Never called on page 1 */ + for(i=iFirst; iapCell[i] will never overlap on a well-formed + ** database. But they might for a corrupt database. Hence use memmove() + ** since memcpy() sends SIGABORT with overlapping buffers on OpenBSD */ + assert( (pSlot+sz)<=pCArray->apCell[i] + || pSlot>=(pCArray->apCell[i]+sz) + || CORRUPT_DB ); + memmove(pSlot, pCArray->apCell[i], sz); + put2byte(pCellptr, (pSlot - aData)); + pCellptr += 2; + } + *ppData = pData; + return 0; +} + +/* +** Array apCell[] contains nCell pointers to b-tree cells. Array szCell +** contains the size in bytes of each such cell. This function adds the +** space associated with each cell in the array that is currently stored +** within the body of pPg to the pPg free-list. The cell-pointers and other +** fields of the page are not updated. +** +** This function returns the total number of cells added to the free-list. +*/ +static int pageFreeArray( + MemPage *pPg, /* Page to edit */ + int iFirst, /* First cell to delete */ + int nCell, /* Cells to delete */ + CellArray *pCArray /* Array of cells */ +){ + u8 * const aData = pPg->aData; + u8 * const pEnd = &aData[pPg->pBt->usableSize]; + u8 * const pStart = &aData[pPg->hdrOffset + 8 + pPg->childPtrSize]; + int nRet = 0; + int i; + int iEnd = iFirst + nCell; + u8 *pFree = 0; + int szFree = 0; + + for(i=iFirst; iapCell[i]; + if( SQLITE_WITHIN(pCell, pStart, pEnd) ){ + int sz; + /* No need to use cachedCellSize() here. The sizes of all cells that + ** are to be freed have already been computing while deciding which + ** cells need freeing */ + sz = pCArray->szCell[i]; assert( sz>0 ); + if( pFree!=(pCell + sz) ){ + if( pFree ){ + assert( pFree>aData && (pFree - aData)<65536 ); + freeSpace(pPg, (u16)(pFree - aData), szFree); + } + pFree = pCell; + szFree = sz; + if( pFree+sz>pEnd ) return 0; + }else{ + pFree = pCell; + szFree += sz; + } + nRet++; + } + } + if( pFree ){ + assert( pFree>aData && (pFree - aData)<65536 ); + freeSpace(pPg, (u16)(pFree - aData), szFree); + } + return nRet; +} + +/* +** apCell[] and szCell[] contains pointers to and sizes of all cells in the +** pages being balanced. The current page, pPg, has pPg->nCell cells starting +** with apCell[iOld]. After balancing, this page should hold nNew cells +** starting at apCell[iNew]. +** +** This routine makes the necessary adjustments to pPg so that it contains +** the correct cells after being balanced. +** +** The pPg->nFree field is invalid when this function returns. It is the +** responsibility of the caller to set it correctly. +*/ +static int editPage( + MemPage *pPg, /* Edit this page */ + int iOld, /* Index of first cell currently on page */ + int iNew, /* Index of new first cell on page */ + int nNew, /* Final number of cells on page */ + CellArray *pCArray /* Array of cells and sizes */ +){ + u8 * const aData = pPg->aData; + const int hdr = pPg->hdrOffset; + u8 *pBegin = &pPg->aCellIdx[nNew * 2]; + int nCell = pPg->nCell; /* Cells stored on pPg */ + u8 *pData; + u8 *pCellptr; + int i; + int iOldEnd = iOld + pPg->nCell + pPg->nOverflow; + int iNewEnd = iNew + nNew; + +#ifdef SQLITE_DEBUG + u8 *pTmp = sqlite3PagerTempSpace(pPg->pBt->pPager); + memcpy(pTmp, aData, pPg->pBt->usableSize); +#endif + + /* Remove cells from the start and end of the page */ + if( iOldaCellIdx, &pPg->aCellIdx[nShift*2], nCell*2); + nCell -= nShift; + } + if( iNewEnd < iOldEnd ){ + nCell -= pageFreeArray(pPg, iNewEnd, iOldEnd - iNewEnd, pCArray); + } + + pData = &aData[get2byteNotZero(&aData[hdr+5])]; + if( pDataaCellIdx; + memmove(&pCellptr[nAdd*2], pCellptr, nCell*2); + if( pageInsertArray( + pPg, pBegin, &pData, pCellptr, + iNew, nAdd, pCArray + ) ) goto editpage_fail; + nCell += nAdd; + } + + /* Add any overflow cells */ + for(i=0; inOverflow; i++){ + int iCell = (iOld + pPg->aiOvfl[i]) - iNew; + if( iCell>=0 && iCellaCellIdx[iCell * 2]; + memmove(&pCellptr[2], pCellptr, (nCell - iCell) * 2); + nCell++; + if( pageInsertArray( + pPg, pBegin, &pData, pCellptr, + iCell+iNew, 1, pCArray + ) ) goto editpage_fail; + } + } + + /* Append cells to the end of the page */ + pCellptr = &pPg->aCellIdx[nCell*2]; + if( pageInsertArray( + pPg, pBegin, &pData, pCellptr, + iNew+nCell, nNew-nCell, pCArray + ) ) goto editpage_fail; + + pPg->nCell = nNew; + pPg->nOverflow = 0; + + put2byte(&aData[hdr+3], pPg->nCell); + put2byte(&aData[hdr+5], pData - aData); + +#ifdef SQLITE_DEBUG + for(i=0; iapCell[i+iNew]; + int iOff = get2byteAligned(&pPg->aCellIdx[i*2]); + if( pCell>=aData && pCell<&aData[pPg->pBt->usableSize] ){ + pCell = &pTmp[pCell - aData]; + } + assert( 0==memcmp(pCell, &aData[iOff], + pCArray->pRef->xCellSize(pCArray->pRef, pCArray->apCell[i+iNew])) ); + } +#endif + + return SQLITE_OK; + editpage_fail: + /* Unable to edit this page. Rebuild it from scratch instead. */ + populateCellCache(pCArray, iNew, nNew); + return rebuildPage(pPg, nNew, &pCArray->apCell[iNew], &pCArray->szCell[iNew]); } /* @@ -57047,7 +61883,7 @@ static int balance_quick(MemPage *pParent, MemPage *pPage, u8 *pSpace){ assert( pPage->nOverflow==1 ); /* This error condition is now caught prior to reaching this function */ - if( pPage->nCell==0 ) return SQLITE_CORRUPT_BKPT; + if( NEVER(pPage->nCell==0) ) return SQLITE_CORRUPT_BKPT; /* Allocate a new page. This page will become the right-sibling of ** pPage. Make the parent page writable, so that the new divider cell @@ -57059,13 +61895,15 @@ static int balance_quick(MemPage *pParent, MemPage *pPage, u8 *pSpace){ u8 *pOut = &pSpace[4]; u8 *pCell = pPage->apOvfl[0]; - u16 szCell = cellSizePtr(pPage, pCell); + u16 szCell = pPage->xCellSize(pPage, pCell); u8 *pStop; assert( sqlite3PagerIswriteable(pNew->pDbPage) ); assert( pPage->aData[0]==(PTF_INTKEY|PTF_LEAFDATA|PTF_LEAF) ); zeroPage(pNew, PTF_INTKEY|PTF_LEAFDATA|PTF_LEAF); - assemblePage(pNew, 1, &pCell, &szCell); + rc = rebuildPage(pNew, 1, &pCell, &szCell); + if( NEVER(rc) ) return rc; + pNew->nFree = pBt->usableSize - pNew->cellOffset - 2 - szCell; /* If this is an auto-vacuum database, update the pointer map ** with entries for the new page, and any pointer from the @@ -57137,9 +61975,9 @@ static int ptrmapCheckPages(MemPage **apPage, int nPage){ u8 *z; z = findCell(pPage, j); - btreeParseCellPtr(pPage, z, &info); - if( info.iOverflow ){ - Pgno ovfl = get4byte(&z[info.iOverflow]); + pPage->xParseCell(pPage, z, &info); + if( info.nLocalpgno && e==PTRMAP_OVERFLOW1 ); } @@ -57257,9 +62095,6 @@ static void copyNodeContent(MemPage *pFrom, MemPage *pTo, int *pRC){ ** If aOvflSpace is set to a null pointer, this function returns ** SQLITE_NOMEM. */ -#if defined(_MSC_VER) && _MSC_VER >= 1700 && defined(_M_ARM) -#pragma optimize("", off) -#endif static int balance_nonroot( MemPage *pParent, /* Parent page of siblings being balanced */ int iParentIdx, /* Index of "the page" in pParent */ @@ -57268,7 +62103,6 @@ static int balance_nonroot( int bBulk /* True if this call is part of a bulk load */ ){ BtShared *pBt; /* The whole database */ - int nCell = 0; /* Number of cells in apCell[] */ int nMaxCells = 0; /* Allocated size of apCell, szCell, aFrom. */ int nNew = 0; /* Number of pages in apNew[] */ int nOld; /* Number of pages in apOld[] */ @@ -57279,22 +62113,27 @@ static int balance_nonroot( int leafData; /* True if pPage is a leaf of a LEAFDATA tree */ int usableSpace; /* Bytes in pPage beyond the header */ int pageFlags; /* Value of pPage->aData[0] */ - int subtotal; /* Subtotal of bytes in cells on one page */ int iSpace1 = 0; /* First unused byte of aSpace1[] */ int iOvflSpace = 0; /* First unused byte of aOvflSpace[] */ int szScratch; /* Size of scratch memory requested */ MemPage *apOld[NB]; /* pPage and up to two siblings */ - MemPage *apCopy[NB]; /* Private copies of apOld[] pages */ MemPage *apNew[NB+2]; /* pPage and up to NB siblings after balancing */ u8 *pRight; /* Location in parent of right-sibling pointer */ u8 *apDiv[NB-1]; /* Divider cells in pParent */ - int cntNew[NB+2]; /* Index in aCell[] of cell after i-th page */ - int szNew[NB+2]; /* Combined size of cells place on i-th page */ - u8 **apCell = 0; /* All cells begin balanced */ - u16 *szCell; /* Local size of all cells in apCell[] */ + int cntNew[NB+2]; /* Index in b.paCell[] of cell after i-th page */ + int cntOld[NB+2]; /* Old index in b.apCell[] */ + int szNew[NB+2]; /* Combined size of cells placed on i-th page */ u8 *aSpace1; /* Space for copies of dividers cells */ Pgno pgno; /* Temp var to store a page number in */ + u8 abDone[NB+2]; /* True after i'th new page is populated */ + Pgno aPgno[NB+2]; /* Page numbers of new pages before shuffling */ + Pgno aPgOrder[NB+2]; /* Copy of aPgno[] used for sorting pages */ + u16 aPgFlags[NB+2]; /* flags field of new pages before shuffling */ + CellArray b; /* Parsed information on cells being balanced */ + memset(abDone, 0, sizeof(abDone)); + b.nCell = 0; + b.apCell = 0; pBt = pParent->pBt; assert( sqlite3_mutex_held(pBt->mutex) ); assert( sqlite3PagerIswriteable(pParent->pDbPage) ); @@ -57336,7 +62175,6 @@ static int balance_nonroot( }else if( iParentIdx==i ){ nxDiv = i-2+bBulk; }else{ - assert( bBulk==0 ); nxDiv = iParentIdx-1; } i = 2-bBulk; @@ -57349,7 +62187,7 @@ static int balance_nonroot( } pgno = get4byte(pRight); while( 1 ){ - rc = getAndInitPage(pBt, pgno, &apOld[i], 0); + rc = getAndInitPage(pBt, pgno, &apOld[i], 0, 0); if( rc ){ memset(apOld, 0, (i+1)*sizeof(MemPage*)); goto balance_cleanup; @@ -57360,12 +62198,12 @@ static int balance_nonroot( if( i+nxDiv==pParent->aiOvfl[0] && pParent->nOverflow ){ apDiv[i] = pParent->apOvfl[0]; pgno = get4byte(apDiv[i]); - szNew[i] = cellSizePtr(pParent, apDiv[i]); + szNew[i] = pParent->xCellSize(pParent, apDiv[i]); pParent->nOverflow = 0; }else{ apDiv[i] = findCell(pParent, i+nxDiv-pParent->nOverflow); pgno = get4byte(apDiv[i]); - szNew[i] = cellSizePtr(pParent, apDiv[i]); + szNew[i] = pParent->xCellSize(pParent, apDiv[i]); /* Drop the cell from the parent page. apDiv[i] still points to ** the cell within the parent, even though it has been dropped. @@ -57403,138 +62241,209 @@ static int balance_nonroot( /* ** Allocate space for memory structures */ - k = pBt->pageSize + ROUND8(sizeof(MemPage)); szScratch = - nMaxCells*sizeof(u8*) /* apCell */ - + nMaxCells*sizeof(u16) /* szCell */ - + pBt->pageSize /* aSpace1 */ - + k*nOld; /* Page copies (apCopy) */ - apCell = sqlite3ScratchMalloc( szScratch ); - if( apCell==0 ){ + nMaxCells*sizeof(u8*) /* b.apCell */ + + nMaxCells*sizeof(u16) /* b.szCell */ + + pBt->pageSize; /* aSpace1 */ + + /* EVIDENCE-OF: R-28375-38319 SQLite will never request a scratch buffer + ** that is more than 6 times the database page size. */ + assert( szScratch<=6*(int)pBt->pageSize ); + b.apCell = sqlite3ScratchMalloc( szScratch ); + if( b.apCell==0 ){ rc = SQLITE_NOMEM; goto balance_cleanup; } - szCell = (u16*)&apCell[nMaxCells]; - aSpace1 = (u8*)&szCell[nMaxCells]; + b.szCell = (u16*)&b.apCell[nMaxCells]; + aSpace1 = (u8*)&b.szCell[nMaxCells]; assert( EIGHT_BYTE_ALIGNMENT(aSpace1) ); /* ** Load pointers to all cells on sibling pages and the divider cells - ** into the local apCell[] array. Make copies of the divider cells - ** into space obtained from aSpace1[] and remove the divider cells - ** from pParent. + ** into the local b.apCell[] array. Make copies of the divider cells + ** into space obtained from aSpace1[]. The divider cells have already + ** been removed from pParent. ** ** If the siblings are on leaf pages, then the child pointers of the ** divider cells are stripped from the cells before they are copied - ** into aSpace1[]. In this way, all cells in apCell[] are without + ** into aSpace1[]. In this way, all cells in b.apCell[] are without ** child pointers. If siblings are not leaves, then all cell in - ** apCell[] include child pointers. Either way, all cells in apCell[] + ** b.apCell[] include child pointers. Either way, all cells in b.apCell[] ** are alike. ** ** leafCorrection: 4 if pPage is a leaf. 0 if pPage is not a leaf. ** leafData: 1 if pPage holds key+data and pParent holds only keys. */ - leafCorrection = apOld[0]->leaf*4; - leafData = apOld[0]->hasData; + b.pRef = apOld[0]; + leafCorrection = b.pRef->leaf*4; + leafData = b.pRef->intKeyLeaf; for(i=0; ipageSize + k*i]; - memcpy(pOld, apOld[i], sizeof(MemPage)); - pOld->aData = (void*)&pOld[1]; - memcpy(pOld->aData, apOld[i]->aData, pBt->pageSize); + MemPage *pOld = apOld[i]; + int limit = pOld->nCell; + u8 *aData = pOld->aData; + u16 maskPage = pOld->maskPage; + u8 *piCell = aData + pOld->cellOffset; + u8 *piEnd; - limit = pOld->nCell+pOld->nOverflow; + /* Verify that all sibling pages are of the same "type" (table-leaf, + ** table-interior, index-leaf, or index-interior). + */ + if( pOld->aData[0]!=apOld[0]->aData[0] ){ + rc = SQLITE_CORRUPT_BKPT; + goto balance_cleanup; + } + + /* Load b.apCell[] with pointers to all cells in pOld. If pOld + ** constains overflow cells, include them in the b.apCell[] array + ** in the correct spot. + ** + ** Note that when there are multiple overflow cells, it is always the + ** case that they are sequential and adjacent. This invariant arises + ** because multiple overflows can only occurs when inserting divider + ** cells into a parent on a prior balance, and divider cells are always + ** adjacent and are inserted in order. There is an assert() tagged + ** with "NOTE 1" in the overflow cell insertion loop to prove this + ** invariant. + ** + ** This must be done in advance. Once the balance starts, the cell + ** offset section of the btree page will be overwritten and we will no + ** long be able to find the cells if a pointer to each cell is not saved + ** first. + */ + memset(&b.szCell[b.nCell], 0, sizeof(b.szCell[0])*limit); if( pOld->nOverflow>0 ){ + memset(&b.szCell[b.nCell+limit], 0, sizeof(b.szCell[0])*pOld->nOverflow); + limit = pOld->aiOvfl[0]; for(j=0; jaData; - u16 maskPage = pOld->maskPage; - u16 cellOffset = pOld->cellOffset; - for(j=0; jnOverflow; k++){ + assert( k==0 || pOld->aiOvfl[k-1]+1==pOld->aiOvfl[k] );/* NOTE 1 */ + b.apCell[b.nCell] = pOld->apOvfl[k]; + b.nCell++; } - } + } + piEnd = aData + pOld->cellOffset + 2*pOld->nCell; + while( piCellmaxLocal+23 ); assert( iSpace1 <= (int)pBt->pageSize ); memcpy(pTemp, apDiv[i], sz); - apCell[nCell] = pTemp+leafCorrection; + b.apCell[b.nCell] = pTemp+leafCorrection; assert( leafCorrection==0 || leafCorrection==4 ); - szCell[nCell] = szCell[nCell] - leafCorrection; + b.szCell[b.nCell] = b.szCell[b.nCell] - leafCorrection; if( !pOld->leaf ){ assert( leafCorrection==0 ); assert( pOld->hdrOffset==0 ); /* The right pointer of the child page pOld becomes the left ** pointer of the divider cell */ - memcpy(apCell[nCell], &pOld->aData[8], 4); + memcpy(b.apCell[b.nCell], &pOld->aData[8], 4); }else{ assert( leafCorrection==4 ); - if( szCell[nCell]<4 ){ - /* Do not allow any cells smaller than 4 bytes. */ - szCell[nCell] = 4; + while( b.szCell[b.nCell]<4 ){ + /* Do not allow any cells smaller than 4 bytes. If a smaller cell + ** does exist, pad it with 0x00 bytes. */ + assert( b.szCell[b.nCell]==3 || CORRUPT_DB ); + assert( b.apCell[b.nCell]==&aSpace1[iSpace1-3] || CORRUPT_DB ); + aSpace1[iSpace1++] = 0x00; + b.szCell[b.nCell]++; } } - nCell++; + b.nCell++; } } /* - ** Figure out the number of pages needed to hold all nCell cells. + ** Figure out the number of pages needed to hold all b.nCell cells. ** Store this number in "k". Also compute szNew[] which is the total ** size of all cells on the i-th page and cntNew[] which is the index - ** in apCell[] of the cell that divides page i from page i+1. - ** cntNew[k] should equal nCell. + ** in b.apCell[] of the cell that divides page i from page i+1. + ** cntNew[k] should equal b.nCell. ** ** Values computed by this block: ** ** k: The total number of sibling pages ** szNew[i]: Spaced used on the i-th sibling page. - ** cntNew[i]: Index in apCell[] and szCell[] for the first cell to + ** cntNew[i]: Index in b.apCell[] and b.szCell[] for the first cell to ** the right of the i-th sibling page. ** usableSpace: Number of bytes of space available on each sibling. ** */ usableSpace = pBt->usableSize - 12 + leafCorrection; - for(subtotal=k=i=0; i usableSpace ){ - szNew[k] = subtotal - szCell[i]; - cntNew[k] = i; - if( leafData ){ i--; } - subtotal = 0; - k++; - if( k>NB+1 ){ rc = SQLITE_CORRUPT_BKPT; goto balance_cleanup; } + for(i=0; inFree; + if( szNew[i]<0 ){ rc = SQLITE_CORRUPT_BKPT; goto balance_cleanup; } + for(j=0; jnOverflow; j++){ + szNew[i] += 2 + p->xCellSize(p, p->apOvfl[j]); + } + cntNew[i] = cntOld[i]; + } + k = nOld; + for(i=0; iusableSpace ){ + if( i+1>=k ){ + k = i+2; + if( k>NB+2 ){ rc = SQLITE_CORRUPT_BKPT; goto balance_cleanup; } + szNew[k-1] = 0; + cntNew[k-1] = b.nCell; + } + sz = 2 + cachedCellSize(&b, cntNew[i]-1); + szNew[i] -= sz; + if( !leafData ){ + if( cntNew[i]usableSpace ) break; + szNew[i] += sz; + cntNew[i]++; + if( !leafData ){ + if( cntNew[i]=b.nCell ){ + k = i+1; + }else if( cntNew[i] <= (i>0 ? cntNew[i-1] : 0) ){ + rc = SQLITE_CORRUPT_BKPT; + goto balance_cleanup; } } - szNew[k] = subtotal; - cntNew[k] = nCell; - k++; /* ** The packing computed by the previous block is biased toward the siblings - ** on the left side. The left siblings are always nearly full, while the - ** right-most sibling might be nearly empty. This block of code attempts - ** to adjust the packing of siblings to get a better balance. + ** on the left side (siblings with smaller keys). The left siblings are + ** always nearly full, while the right-most sibling might be nearly empty. + ** The next block of code attempts to adjust the packing of siblings to + ** get a better balance. ** ** This adjustment is more than an optimization. The packing above might ** be so out of balance as to be illegal. For example, the right-most @@ -57548,46 +62457,46 @@ static int balance_nonroot( r = cntNew[i-1] - 1; d = r + 1 - leafData; - assert( d szLeft-(b.szCell[r]+2)) ){ + break; + } + szRight += b.szCell[d] + 2; + szLeft -= b.szCell[r] + 2; + cntNew[i-1] = r; + r--; + d--; + }while( r>=0 ); szNew[i] = szRight; szNew[i-1] = szLeft; + if( cntNew[i-1] <= (i>1 ? cntNew[i-2] : 0) ){ + rc = SQLITE_CORRUPT_BKPT; + goto balance_cleanup; + } } - /* Either we found one or more cells (cntnew[0])>0) or pPage is - ** a virtual root page. A virtual root page is when the real root - ** page is page 1 and we are the only child of that page. - ** - ** UPDATE: The assert() below is not necessarily true if the database - ** file is corrupt. The corruption will be detected and reported later - ** in this procedure so there is no need to act upon it now. + /* Sanity check: For a non-corrupt database file one of the follwing + ** must be true: + ** (1) We found one or more cells (cntNew[0])>0), or + ** (2) pPage is a virtual root page. A virtual root page is when + ** the real root page is page 1 and we are the only child of + ** that page. */ -#if 0 - assert( cntNew[0]>0 || (pParent->pgno==1 && pParent->nCell==0) ); -#endif - - TRACE(("BALANCE: old: %d %d %d ", - apOld[0]->pgno, - nOld>=2 ? apOld[1]->pgno : 0, - nOld>=3 ? apOld[2]->pgno : 0 + assert( cntNew[0]>0 || (pParent->pgno==1 && pParent->nCell==0) || CORRUPT_DB); + TRACE(("BALANCE: old: %d(nc=%d) %d(nc=%d) %d(nc=%d)\n", + apOld[0]->pgno, apOld[0]->nCell, + nOld>=2 ? apOld[1]->pgno : 0, nOld>=2 ? apOld[1]->nCell : 0, + nOld>=3 ? apOld[2]->pgno : 0, nOld>=3 ? apOld[2]->nCell : 0 )); /* ** Allocate k new pages. Reuse old pages where possible. */ - if( apOld[0]->pgno<=1 ){ - rc = SQLITE_CORRUPT_BKPT; - goto balance_cleanup; - } pageFlags = apOld[0]->aData[0]; for(i=0; i0 ); rc = allocateBtreePage(pBt, &pNew, &pgno, (bBulk ? 1 : pgno), 0); if( rc ) goto balance_cleanup; + zeroPage(pNew, pageFlags); apNew[i] = pNew; nNew++; + cntOld[i] = b.nCell; /* Set the pointer-map entry for the new sibling page. */ if( ISAUTOVACUUM ){ @@ -57614,135 +62525,249 @@ static int balance_nonroot( } } - /* Free any old pages that were not reused as new pages. - */ - while( ipgno; - int minI = i; - for(j=i+1; jpgno<(unsigned)minV ){ - minI = j; - minV = apNew[j]->pgno; + for(i=0; ipgno; + aPgFlags[i] = apNew[i]->pDbPage->flags; + for(j=0; ji ){ - MemPage *pT; - pT = apNew[i]; - apNew[i] = apNew[minI]; - apNew[minI] = pT; + } + for(i=0; ii ){ + sqlite3PagerRekey(apNew[iBest]->pDbPage, pBt->nPage+iBest+1, 0); + } + sqlite3PagerRekey(apNew[i]->pDbPage, pgno, aPgFlags[iBest]); + apNew[i]->pgno = pgno; } } - TRACE(("new: %d(%d) %d(%d) %d(%d) %d(%d) %d(%d)\n", - apNew[0]->pgno, szNew[0], + + TRACE(("BALANCE: new: %d(%d nc=%d) %d(%d nc=%d) %d(%d nc=%d) " + "%d(%d nc=%d) %d(%d nc=%d)\n", + apNew[0]->pgno, szNew[0], cntNew[0], nNew>=2 ? apNew[1]->pgno : 0, nNew>=2 ? szNew[1] : 0, + nNew>=2 ? cntNew[1] - cntNew[0] - !leafData : 0, nNew>=3 ? apNew[2]->pgno : 0, nNew>=3 ? szNew[2] : 0, + nNew>=3 ? cntNew[2] - cntNew[1] - !leafData : 0, nNew>=4 ? apNew[3]->pgno : 0, nNew>=4 ? szNew[3] : 0, - nNew>=5 ? apNew[4]->pgno : 0, nNew>=5 ? szNew[4] : 0)); + nNew>=4 ? cntNew[3] - cntNew[2] - !leafData : 0, + nNew>=5 ? apNew[4]->pgno : 0, nNew>=5 ? szNew[4] : 0, + nNew>=5 ? cntNew[4] - cntNew[3] - !leafData : 0 + )); assert( sqlite3PagerIswriteable(pParent->pDbPage) ); put4byte(pRight, apNew[nNew-1]->pgno); - /* - ** Evenly distribute the data in apCell[] across the new pages. - ** Insert divider cells into pParent as necessary. + /* If the sibling pages are not leaves, ensure that the right-child pointer + ** of the right-most new sibling page is set to the value that was + ** originally in the same field of the right-most old sibling page. */ + if( (pageFlags & PTF_LEAF)==0 && nOld!=nNew ){ + MemPage *pOld = (nNew>nOld ? apNew : apOld)[nOld-1]; + memcpy(&apNew[nNew-1]->aData[8], &pOld->aData[8], 4); + } + + /* Make any required updates to pointer map entries associated with + ** cells stored on sibling pages following the balance operation. Pointer + ** map entries associated with divider cells are set by the insertCell() + ** routine. The associated pointer map entries are: + ** + ** a) if the cell contains a reference to an overflow chain, the + ** entry associated with the first page in the overflow chain, and + ** + ** b) if the sibling pages are not leaves, the child page associated + ** with the cell. + ** + ** If the sibling pages are not leaves, then the pointer map entry + ** associated with the right-child of each sibling may also need to be + ** updated. This happens below, after the sibling pages have been + ** populated, not here. */ - j = 0; - for(i=0; inCell>0 || (nNew==1 && cntNew[0]==0) ); - assert( pNew->nOverflow==0 ); + if( ISAUTOVACUUM ){ + MemPage *pNew = apNew[0]; + u8 *aOld = pNew->aData; + int cntOldNext = pNew->nCell + pNew->nOverflow; + int usableSize = pBt->usableSize; + int iNew = 0; + int iOld = 0; - j = cntNew[i]; - - /* If the sibling page assembled above was not the right-most sibling, - ** insert a divider cell into the parent page. - */ - assert( ileaf ){ - memcpy(&pNew->aData[8], pCell, 4); - }else if( leafData ){ - /* If the tree is a leaf-data tree, and the siblings are leaves, - ** then there is no divider cell in apCell[]. Instead, the divider - ** cell consists of the integer key for the right-most cell of - ** the sibling-page assembled above only. - */ - CellInfo info; - j--; - btreeParseCellPtr(pNew, apCell[j], &info); - pCell = pTemp; - sz = 4 + putVarint(&pCell[4], info.nKey); - pTemp = 0; - }else{ - pCell -= 4; - /* Obscure case for non-leaf-data trees: If the cell at pCell was - ** previously stored on a leaf node, and its reported size was 4 - ** bytes, then it may actually be smaller than this - ** (see btreeParseCellPtr(), 4 bytes is the minimum size of - ** any cell). But it is important to pass the correct size to - ** insertCell(), so reparse the cell now. - ** - ** Note that this can never happen in an SQLite data file, as all - ** cells are at least 4 bytes. It only happens in b-trees used - ** to evaluate "IN (SELECT ...)" and similar clauses. - */ - if( szCell[j]==4 ){ - assert(leafCorrection==4); - sz = cellSizePtr(pParent, pCell); - } + for(i=0; inCell + pOld->nOverflow + !leafData; + aOld = pOld->aData; + } + if( i==cntNew[iNew] ){ + pNew = apNew[++iNew]; + if( !leafData ) continue; } - iOvflSpace += sz; - assert( sz<=pBt->maxLocal+23 ); - assert( iOvflSpace <= (int)pBt->pageSize ); - insertCell(pParent, nxDiv, pCell, sz, pTemp, pNew->pgno, &rc); - if( rc!=SQLITE_OK ) goto balance_cleanup; - assert( sqlite3PagerIswriteable(pParent->pDbPage) ); - j++; - nxDiv++; + /* Cell pCell is destined for new sibling page pNew. Originally, it + ** was either part of sibling page iOld (possibly an overflow cell), + ** or else the divider cell to the left of sibling page iOld. So, + ** if sibling page iOld had the same page number as pNew, and if + ** pCell really was a part of sibling page iOld (not a divider or + ** overflow cell), we can skip updating the pointer map entries. */ + if( iOld>=nNew + || pNew->pgno!=aPgno[iOld] + || !SQLITE_WITHIN(pCell,aOld,&aOld[usableSize]) + ){ + if( !leafCorrection ){ + ptrmapPut(pBt, get4byte(pCell), PTRMAP_BTREE, pNew->pgno, &rc); + } + if( cachedCellSize(&b,i)>pNew->minLocal ){ + ptrmapPutOvflPtr(pNew, pCell, &rc); + } + if( rc ) goto balance_cleanup; + } } } - assert( j==nCell ); + + /* Insert new divider cells into pParent. */ + for(i=0; ileaf ){ + memcpy(&pNew->aData[8], pCell, 4); + }else if( leafData ){ + /* If the tree is a leaf-data tree, and the siblings are leaves, + ** then there is no divider cell in b.apCell[]. Instead, the divider + ** cell consists of the integer key for the right-most cell of + ** the sibling-page assembled above only. + */ + CellInfo info; + j--; + pNew->xParseCell(pNew, b.apCell[j], &info); + pCell = pTemp; + sz = 4 + putVarint(&pCell[4], info.nKey); + pTemp = 0; + }else{ + pCell -= 4; + /* Obscure case for non-leaf-data trees: If the cell at pCell was + ** previously stored on a leaf node, and its reported size was 4 + ** bytes, then it may actually be smaller than this + ** (see btreeParseCellPtr(), 4 bytes is the minimum size of + ** any cell). But it is important to pass the correct size to + ** insertCell(), so reparse the cell now. + ** + ** Note that this can never happen in an SQLite data file, as all + ** cells are at least 4 bytes. It only happens in b-trees used + ** to evaluate "IN (SELECT ...)" and similar clauses. + */ + if( b.szCell[j]==4 ){ + assert(leafCorrection==4); + sz = pParent->xCellSize(pParent, pCell); + } + } + iOvflSpace += sz; + assert( sz<=pBt->maxLocal+23 ); + assert( iOvflSpace <= (int)pBt->pageSize ); + insertCell(pParent, nxDiv+i, pCell, sz, pTemp, pNew->pgno, &rc); + if( rc!=SQLITE_OK ) goto balance_cleanup; + assert( sqlite3PagerIswriteable(pParent->pDbPage) ); + } + + /* Now update the actual sibling pages. The order in which they are updated + ** is important, as this code needs to avoid disrupting any page from which + ** cells may still to be read. In practice, this means: + ** + ** (1) If cells are moving left (from apNew[iPg] to apNew[iPg-1]) + ** then it is not safe to update page apNew[iPg] until after + ** the left-hand sibling apNew[iPg-1] has been updated. + ** + ** (2) If cells are moving right (from apNew[iPg] to apNew[iPg+1]) + ** then it is not safe to update page apNew[iPg] until after + ** the right-hand sibling apNew[iPg+1] has been updated. + ** + ** If neither of the above apply, the page is safe to update. + ** + ** The iPg value in the following loop starts at nNew-1 goes down + ** to 0, then back up to nNew-1 again, thus making two passes over + ** the pages. On the initial downward pass, only condition (1) above + ** needs to be tested because (2) will always be true from the previous + ** step. On the upward pass, both conditions are always true, so the + ** upwards pass simply processes pages that were missed on the downward + ** pass. + */ + for(i=1-nNew; i=0 && iPg=0 /* On the upwards pass, or... */ + || cntOld[iPg-1]>=cntNew[iPg-1] /* Condition (1) is true */ + ){ + int iNew; + int iOld; + int nNewCell; + + /* Verify condition (1): If cells are moving left, update iPg + ** only after iPg-1 has already been updated. */ + assert( iPg==0 || cntOld[iPg-1]>=cntNew[iPg-1] || abDone[iPg-1] ); + + /* Verify condition (2): If cells are moving right, update iPg + ** only after iPg+1 has already been updated. */ + assert( cntNew[iPg]>=cntOld[iPg] || abDone[iPg+1] ); + + if( iPg==0 ){ + iNew = iOld = 0; + nNewCell = cntNew[0]; + }else{ + iOld = iPgnFree = usableSpace-szNew[iPg]; + assert( apNew[iPg]->nOverflow==0 ); + assert( apNew[iPg]->nCell==nNewCell ); + } + } + + /* All pages have been processed exactly once */ + assert( memcmp(abDone, "\01\01\01\01\01", nNew)==0 ); + assert( nOld>0 ); assert( nNew>0 ); - if( (pageFlags & PTF_LEAF)==0 ){ - u8 *zChild = &apCopy[nOld-1]->aData[8]; - memcpy(&apNew[nNew-1]->aData[8], zChild, 4); - } if( isRoot && pParent->nCell==0 && pParent->hdrOffset<=apNew[0]->nFree ){ /* The root page of the b-tree now contains no cells. The only sibling @@ -57755,132 +62780,56 @@ static int balance_nonroot( ** sets all pointer-map entries corresponding to database image pages ** for which the pointer is stored within the content being copied. ** - ** The second assert below verifies that the child page is defragmented - ** (it must be, as it was just reconstructed using assemblePage()). This - ** is important if the parent page happens to be page 1 of the database - ** image. */ - assert( nNew==1 ); + ** It is critical that the child page be defragmented before being + ** copied into the parent, because if the parent is page 1 then it will + ** by smaller than the child due to the database header, and so all the + ** free space needs to be up front. + */ + assert( nNew==1 || CORRUPT_DB ); + rc = defragmentPage(apNew[0]); + testcase( rc!=SQLITE_OK ); assert( apNew[0]->nFree == - (get2byte(&apNew[0]->aData[5])-apNew[0]->cellOffset-apNew[0]->nCell*2) + (get2byte(&apNew[0]->aData[5])-apNew[0]->cellOffset-apNew[0]->nCell*2) + || rc!=SQLITE_OK ); copyNodeContent(apNew[0], pParent, &rc); freePage(apNew[0], &rc); - }else if( ISAUTOVACUUM ){ - /* Fix the pointer-map entries for all the cells that were shifted around. - ** There are several different types of pointer-map entries that need to - ** be dealt with by this routine. Some of these have been set already, but - ** many have not. The following is a summary: - ** - ** 1) The entries associated with new sibling pages that were not - ** siblings when this function was called. These have already - ** been set. We don't need to worry about old siblings that were - ** moved to the free-list - the freePage() code has taken care - ** of those. - ** - ** 2) The pointer-map entries associated with the first overflow - ** page in any overflow chains used by new divider cells. These - ** have also already been taken care of by the insertCell() code. - ** - ** 3) If the sibling pages are not leaves, then the child pages of - ** cells stored on the sibling pages may need to be updated. - ** - ** 4) If the sibling pages are not internal intkey nodes, then any - ** overflow pages used by these cells may need to be updated - ** (internal intkey nodes never contain pointers to overflow pages). - ** - ** 5) If the sibling pages are not leaves, then the pointer-map - ** entries for the right-child pages of each sibling may need - ** to be updated. - ** - ** Cases 1 and 2 are dealt with above by other code. The next - ** block deals with cases 3 and 4 and the one after that, case 5. Since - ** setting a pointer map entry is a relatively expensive operation, this - ** code only sets pointer map entries for child or overflow pages that have - ** actually moved between pages. */ - MemPage *pNew = apNew[0]; - MemPage *pOld = apCopy[0]; - int nOverflow = pOld->nOverflow; - int iNextOld = pOld->nCell + nOverflow; - int iOverflow = (nOverflow ? pOld->aiOvfl[0] : -1); - j = 0; /* Current 'old' sibling page */ - k = 0; /* Current 'new' sibling page */ - for(i=0; inCell + pOld->nOverflow; - if( pOld->nOverflow ){ - nOverflow = pOld->nOverflow; - iOverflow = i + !leafData + pOld->aiOvfl[0]; - } - isDivider = !leafData; - } - - assert(nOverflow>0 || iOverflowaiOvfl[0]==pOld->aiOvfl[1]-1); - assert(nOverflow<3 || pOld->aiOvfl[1]==pOld->aiOvfl[2]-1); - if( i==iOverflow ){ - isDivider = 1; - if( (--nOverflow)>0 ){ - iOverflow++; - } - } - - if( i==cntNew[k] ){ - /* Cell i is the cell immediately following the last cell on new - ** sibling page k. If the siblings are not leaf pages of an - ** intkey b-tree, then cell i is a divider cell. */ - pNew = apNew[++k]; - if( !leafData ) continue; - } - assert( jpgno!=pNew->pgno ){ - if( !leafCorrection ){ - ptrmapPut(pBt, get4byte(apCell[i]), PTRMAP_BTREE, pNew->pgno, &rc); - } - if( szCell[i]>pNew->minLocal ){ - ptrmapPutOvflPtr(pNew, apCell[i], &rc); - } - } + }else if( ISAUTOVACUUM && !leafCorrection ){ + /* Fix the pointer map entries associated with the right-child of each + ** sibling page. All other pointer map entries have already been taken + ** care of. */ + for(i=0; iaData[8]); + ptrmapPut(pBt, key, PTRMAP_BTREE, apNew[i]->pgno, &rc); } + } - if( !leafCorrection ){ - for(i=0; iaData[8]); - ptrmapPut(pBt, key, PTRMAP_BTREE, apNew[i]->pgno, &rc); - } - } + assert( pParent->isInit ); + TRACE(("BALANCE: finished: old=%d new=%d cells=%d\n", + nOld, nNew, b.nCell)); + + /* Free any old pages that were not reused as new pages. + */ + for(i=nNew; iisInit ){ /* The ptrmapCheckPages() contains assert() statements that verify that ** all pointer map pages are set correctly. This is helpful while ** debugging. This is usually disabled because a corrupt database may ** cause an assert() statement to fail. */ ptrmapCheckPages(apNew, nNew); ptrmapCheckPages(&pParent, 1); -#endif } - - assert( pParent->isInit ); - TRACE(("BALANCE: finished: old=%d new=%d cells=%d\n", - nOld, nNew, nCell)); +#endif /* ** Cleanup before returning. */ balance_cleanup: - sqlite3ScratchFree(apCell); + sqlite3ScratchFree(b.apCell); for(i=0; i= 1700 && defined(_M_ARM) -#pragma optimize("", on) -#endif /* @@ -58011,7 +62957,7 @@ static int balance(BtCursor *pCur){ rc = sqlite3PagerWrite(pParent->pDbPage); if( rc==SQLITE_OK ){ #ifndef SQLITE_OMIT_QUICKBALANCE - if( pPage->hasData + if( pPage->intKeyLeaf && pPage->nOverflow==1 && pPage->aiOvfl[0]==pPage->nCell && pParent->pgno!=1 @@ -58020,7 +62966,7 @@ static int balance(BtCursor *pCur){ /* Call balance_quick() to create a new sibling of pPage on which ** to store the overflow cell. balance_quick() inserts a new cell ** into pParent, which may cause pParent overflow. If this - ** happens, the next interation of the do-loop will balance pParent + ** happens, the next iteration of the do-loop will balance pParent ** use either balance_nonroot() or balance_deeper(). Until this ** happens, the overflow cell is stored in the aBalanceQuickSpace[] ** buffer. @@ -58053,7 +62999,8 @@ static int balance(BtCursor *pCur){ ** pSpace buffer passed to the latter call to balance_nonroot(). */ u8 *pSpace = sqlite3PageMalloc(pCur->pBt->pageSize); - rc = balance_nonroot(pParent, iIdx, pSpace, iPage==1, pCur->hints); + rc = balance_nonroot(pParent, iIdx, pSpace, iPage==1, + pCur->hints&BTREE_BULKLOAD); if( pFree ){ /* If pFree is not NULL, it points to the pSpace buffer used ** by a previous call to balance_nonroot(). Its contents are @@ -58074,6 +63021,7 @@ static int balance(BtCursor *pCur){ /* The next iteration of the do-loop balances the parent page. */ releasePage(pPage); pCur->iPage--; + assert( pCur->iPage>=0 ); } }while( rc==SQLITE_OK ); @@ -58097,7 +63045,7 @@ static int balance(BtCursor *pCur){ ** MovetoUnpacked() to seek cursor pCur to (pKey, nKey) has already ** been performed. seekResult is the search result returned (a negative ** number if pCur points at an entry that is smaller than (pKey, nKey), or -** a positive value if pCur points at an etry that is larger than +** a positive value if pCur points at an entry that is larger than ** (pKey, nKey)). ** ** If the seekResult parameter is non-zero, then the caller guarantees that @@ -58130,7 +63078,8 @@ SQLITE_PRIVATE int sqlite3BtreeInsert( } assert( cursorHoldsMutex(pCur) ); - assert( (pCur->curFlags & BTCF_WriteFlag)!=0 && pBt->inTransaction==TRANS_WRITE + assert( (pCur->curFlags & BTCF_WriteFlag)!=0 + && pBt->inTransaction==TRANS_WRITE && (pBt->btsFlags & BTS_READ_ONLY)==0 ); assert( hasSharedCacheTableLock(p, pCur->pgnoRoot, pCur->pKeyInfo!=0, 2) ); @@ -58152,23 +63101,28 @@ SQLITE_PRIVATE int sqlite3BtreeInsert( ** doing any work. To avoid thwarting these optimizations, it is important ** not to clear the cursor here. */ - rc = saveAllCursors(pBt, pCur->pgnoRoot, pCur); - if( rc ) return rc; + if( pCur->curFlags & BTCF_Multiple ){ + rc = saveAllCursors(pBt, pCur->pgnoRoot, pCur); + if( rc ) return rc; + } if( pCur->pKeyInfo==0 ){ + assert( pKey==0 ); /* If this is an insert into a table b-tree, invalidate any incrblob ** cursors open on the row being replaced */ invalidateIncrblobCursors(p, nKey, 0); /* If the cursor is currently on the last row and we are appending a - ** new row onto the end, set the "loc" to avoid an unnecessary btreeMoveto() - ** call */ - if( (pCur->curFlags&BTCF_ValidNKey)!=0 && nKey>0 && pCur->info.nKey==nKey-1 ){ - loc = -1; + ** new row onto the end, set the "loc" to avoid an unnecessary + ** btreeMoveto() call */ + if( (pCur->curFlags&BTCF_ValidNKey)!=0 && nKey>0 + && pCur->info.nKey==nKey-1 ){ + loc = -1; + }else if( loc==0 ){ + rc = sqlite3BtreeMovetoUnpacked(pCur, 0, nKey, appendBias, &loc); + if( rc ) return rc; } - } - - if( !loc ){ + }else if( loc==0 ){ rc = btreeMoveto(pCur, pKey, nKey, appendBias, &loc); if( rc ) return rc; } @@ -58182,12 +63136,11 @@ SQLITE_PRIVATE int sqlite3BtreeInsert( pCur->pgnoRoot, nKey, nData, pPage->pgno, loc==0 ? "overwrite" : "new entry")); assert( pPage->isInit ); - allocateTempSpace(pBt); newCell = pBt->pTmpSpace; - if( newCell==0 ) return SQLITE_NOMEM; + assert( newCell!=0 ); rc = fillInCell(pPage, newCell, pKey, nKey, pData, nData, nZero, &szNew); if( rc ) goto end_insert; - assert( szNew==cellSizePtr(pPage, newCell) ); + assert( szNew==pPage->xCellSize(pPage, newCell) ); assert( szNew <= MX_CELL_SIZE(pBt) ); idx = pCur->aiIdx[pCur->iPage]; if( loc==0 ){ @@ -58201,8 +63154,7 @@ SQLITE_PRIVATE int sqlite3BtreeInsert( if( !pPage->leaf ){ memcpy(newCell, oldCell, 4); } - szOld = cellSizePtr(pPage, oldCell); - rc = clearCell(pPage, oldCell); + rc = clearCell(pPage, oldCell, &szOld); dropCell(pPage, idx, szOld, &rc); if( rc ) goto end_insert; }else if( loc<0 && pPage->nCell>0 ){ @@ -58253,10 +63205,15 @@ end_insert: } /* -** Delete the entry that the cursor is pointing to. The cursor -** is left pointing at a arbitrary location. +** Delete the entry that the cursor is pointing to. +** +** If the second parameter is zero, then the cursor is left pointing at an +** arbitrary location after the delete. If it is non-zero, then the cursor +** is left in a state such that the next call to BtreeNext() or BtreePrev() +** moves it to the same row as it would if the call to BtreeDelete() had +** been omitted. */ -SQLITE_PRIVATE int sqlite3BtreeDelete(BtCursor *pCur){ +SQLITE_PRIVATE int sqlite3BtreeDelete(BtCursor *pCur, int bPreserve){ Btree *p = pCur->pBtree; BtShared *pBt = p->pBt; int rc; /* Return code */ @@ -58264,6 +63221,8 @@ SQLITE_PRIVATE int sqlite3BtreeDelete(BtCursor *pCur){ unsigned char *pCell; /* Pointer to cell to delete */ int iCellIdx; /* Index of cell to delete */ int iCellDepth; /* Depth of node containing pCell */ + u16 szCell; /* Size of the cell being deleted */ + int bSkipnext = 0; /* Leaf cursor in SKIPNEXT state */ assert( cursorHoldsMutex(pCur) ); assert( pBt->inTransaction==TRANS_WRITE ); @@ -58271,12 +63230,8 @@ SQLITE_PRIVATE int sqlite3BtreeDelete(BtCursor *pCur){ assert( pCur->curFlags & BTCF_WriteFlag ); assert( hasSharedCacheTableLock(p, pCur->pgnoRoot, pCur->pKeyInfo!=0, 2) ); assert( !hasReadConflicts(p, pCur->pgnoRoot) ); - - if( NEVER(pCur->aiIdx[pCur->iPage]>=pCur->apPage[pCur->iPage]->nCell) - || NEVER(pCur->eState!=CURSOR_VALID) - ){ - return SQLITE_ERROR; /* Something has gone awry. */ - } + assert( pCur->aiIdx[pCur->iPage]apPage[pCur->iPage]->nCell ); + assert( pCur->eState==CURSOR_VALID ); iCellDepth = pCur->iPage; iCellIdx = pCur->aiIdx[iCellDepth]; @@ -58297,12 +63252,11 @@ SQLITE_PRIVATE int sqlite3BtreeDelete(BtCursor *pCur){ } /* Save the positions of any other cursors open on this table before - ** making any modifications. Make the page containing the entry to be - ** deleted writable. Then free any overflow pages associated with the - ** entry and finally remove the cell itself from within the page. - */ - rc = saveAllCursors(pBt, pCur->pgnoRoot, pCur); - if( rc ) return rc; + ** making any modifications. */ + if( pCur->curFlags & BTCF_Multiple ){ + rc = saveAllCursors(pBt, pCur->pgnoRoot, pCur); + if( rc ) return rc; + } /* If this is a delete operation to remove a row from a table b-tree, ** invalidate any incrblob cursors open on the row being deleted. */ @@ -58310,10 +63264,35 @@ SQLITE_PRIVATE int sqlite3BtreeDelete(BtCursor *pCur){ invalidateIncrblobCursors(p, pCur->info.nKey, 0); } + /* If the bPreserve flag is set to true, then the cursor position must + ** be preserved following this delete operation. If the current delete + ** will cause a b-tree rebalance, then this is done by saving the cursor + ** key and leaving the cursor in CURSOR_REQUIRESEEK state before + ** returning. + ** + ** Or, if the current delete will not cause a rebalance, then the cursor + ** will be left in CURSOR_SKIPNEXT state pointing to the entry immediately + ** before or after the deleted entry. In this case set bSkipnext to true. */ + if( bPreserve ){ + if( !pPage->leaf + || (pPage->nFree+cellSizePtr(pPage,pCell)+2)>(int)(pBt->usableSize*2/3) + ){ + /* A b-tree rebalance will be required after deleting this entry. + ** Save the cursor key. */ + rc = saveCursorKey(pCur); + if( rc ) return rc; + }else{ + bSkipnext = 1; + } + } + + /* Make the page containing the entry to be deleted writable. Then free any + ** overflow pages associated with the entry and finally remove the cell + ** itself from within the page. */ rc = sqlite3PagerWrite(pPage->pDbPage); if( rc ) return rc; - rc = clearCell(pPage, pCell); - dropCell(pPage, iCellIdx, cellSizePtr(pPage, pCell), &rc); + rc = clearCell(pPage, pCell, &szCell); + dropCell(pPage, iCellIdx, szCell, &rc); if( rc ) return rc; /* If the cell deleted was not located on a leaf page, then the cursor @@ -58328,12 +63307,11 @@ SQLITE_PRIVATE int sqlite3BtreeDelete(BtCursor *pCur){ unsigned char *pTmp; pCell = findCell(pLeaf, pLeaf->nCell-1); - nCell = cellSizePtr(pLeaf, pCell); + if( pCell<&pLeaf->aData[4] ) return SQLITE_CORRUPT_BKPT; + nCell = pLeaf->xCellSize(pLeaf, pCell); assert( MX_CELL_SIZE(pBt) >= nCell ); - - allocateTempSpace(pBt); pTmp = pBt->pTmpSpace; - + assert( pTmp!=0 ); rc = sqlite3PagerWrite(pLeaf->pDbPage); insertCell(pPage, iCellIdx, pCell-4, nCell+4, pTmp, n, &rc); dropCell(pLeaf, pLeaf->nCell-1, nCell, &rc); @@ -58364,7 +63342,23 @@ SQLITE_PRIVATE int sqlite3BtreeDelete(BtCursor *pCur){ } if( rc==SQLITE_OK ){ - moveToRoot(pCur); + if( bSkipnext ){ + assert( bPreserve && (pCur->iPage==iCellDepth || CORRUPT_DB) ); + assert( pPage==pCur->apPage[pCur->iPage] ); + assert( (pPage->nCell>0 || CORRUPT_DB) && iCellIdx<=pPage->nCell ); + pCur->eState = CURSOR_SKIPNEXT; + if( iCellIdx>=pPage->nCell ){ + pCur->skipNext = -1; + pCur->aiIdx[iCellDepth] = pPage->nCell-1; + }else{ + pCur->skipNext = 1; + } + }else{ + rc = moveToRoot(pCur); + if( bPreserve ){ + pCur->eState = CURSOR_REQUIRESEEK; + } + } } return rc; } @@ -58422,7 +63416,8 @@ static int btreeCreateTable(Btree *p, int *piTable, int createTabFlags){ pgnoRoot==PENDING_BYTE_PAGE(pBt) ){ pgnoRoot++; } - assert( pgnoRoot>=3 ); + assert( pgnoRoot>=3 || CORRUPT_DB ); + testcase( pgnoRoot<3 ); /* Allocate a page. The page that currently resides at pgnoRoot will ** be moved to the allocated page (unless the allocated page happens @@ -58545,14 +63540,19 @@ static int clearDatabasePage( unsigned char *pCell; int i; int hdr; + u16 szCell; assert( sqlite3_mutex_held(pBt->mutex) ); if( pgno>btreePagecount(pBt) ){ return SQLITE_CORRUPT_BKPT; } - - rc = getAndInitPage(pBt, pgno, &pPage, 0); + rc = getAndInitPage(pBt, pgno, &pPage, 0, 0); if( rc ) return rc; + if( pPage->bBusy ){ + rc = SQLITE_CORRUPT_BKPT; + goto cleardatabasepage_out; + } + pPage->bBusy = 1; hdr = pPage->hdrOffset; for(i=0; inCell; i++){ pCell = findCell(pPage, i); @@ -58560,14 +63560,15 @@ static int clearDatabasePage( rc = clearDatabasePage(pBt, get4byte(pCell), 1, pnChange); if( rc ) goto cleardatabasepage_out; } - rc = clearCell(pPage, pCell); + rc = clearCell(pPage, pCell, &szCell); if( rc ) goto cleardatabasepage_out; } if( !pPage->leaf ){ rc = clearDatabasePage(pBt, get4byte(&pPage->aData[hdr+8]), 1, pnChange); if( rc ) goto cleardatabasepage_out; }else if( pnChange ){ - assert( pPage->intKey ); + assert( pPage->intKey || CORRUPT_DB ); + testcase( !pPage->intKey ); *pnChange += pPage->nCell; } if( freePageFlag ){ @@ -58577,6 +63578,7 @@ static int clearDatabasePage( } cleardatabasepage_out: + pPage->bBusy = 0; releasePage(pPage); return rc; } @@ -58766,6 +63768,13 @@ SQLITE_PRIVATE int sqlite3BtreeDropTable(Btree *p, int iTable, int *piMoved){ ** The schema layer numbers meta values differently. At the schema ** layer (and the SetCookie and ReadCookie opcodes) the number of ** free pages is not visible. So Cookie[0] is the same as Meta[1]. +** +** This routine treats Meta[BTREE_DATA_VERSION] as a special case. Instead +** of reading the value out of the header, it instead loads the "DataVersion" +** from the pager. The BTREE_DATA_VERSION value is not actually stored in the +** database file. It is a number computed by the pager. But its access +** pattern is the same as header meta values, and so it is convenient to +** read it from this routine. */ SQLITE_PRIVATE void sqlite3BtreeGetMeta(Btree *p, int idx, u32 *pMeta){ BtShared *pBt = p->pBt; @@ -58776,7 +63785,11 @@ SQLITE_PRIVATE void sqlite3BtreeGetMeta(Btree *p, int idx, u32 *pMeta){ assert( pBt->pPage1 ); assert( idx>=0 && idx<=15 ); - *pMeta = get4byte(&pBt->pPage1->aData[36 + idx*4]); + if( idx==BTREE_DATA_VERSION ){ + *pMeta = sqlite3PagerDataVersion(pBt->pPager) + p->iDataVersion; + }else{ + *pMeta = get4byte(&pBt->pPage1->aData[36 + idx*4]); + } /* If auto-vacuum is disabled in this build and this is an auto-vacuum ** database, mark the database as read-only. */ @@ -58867,7 +63880,7 @@ SQLITE_PRIVATE int sqlite3BtreeCount(BtCursor *pCur, i64 *pnEntry){ if( pCur->iPage==0 ){ /* All pages of the b-tree have been visited. Return successfully. */ *pnEntry = nEntry; - return SQLITE_OK; + return moveToRoot(pCur); } moveToParent(pCur); }while ( pCur->aiIdx[pCur->iPage]>=pCur->apPage[pCur->iPage]->nCell ); @@ -58906,7 +63919,6 @@ SQLITE_PRIVATE Pager *sqlite3BtreePager(Btree *p){ */ static void checkAppendMsg( IntegrityCk *pCheck, - char *zMsg1, const char *zFormat, ... ){ @@ -58918,8 +63930,8 @@ static void checkAppendMsg( if( pCheck->errMsg.nChar ){ sqlite3StrAccumAppend(&pCheck->errMsg, "\n", 1); } - if( zMsg1 ){ - sqlite3StrAccumAppendAll(&pCheck->errMsg, zMsg1); + if( pCheck->zPfx ){ + sqlite3XPrintf(&pCheck->errMsg, 0, pCheck->zPfx, pCheck->v1, pCheck->v2); } sqlite3VXPrintf(&pCheck->errMsg, 1, zFormat, ap); va_end(ap); @@ -58952,19 +63964,19 @@ static void setPageReferenced(IntegrityCk *pCheck, Pgno iPg){ /* ** Add 1 to the reference count for page iPage. If this is the second ** reference to the page, add an error message to pCheck->zErrMsg. -** Return 1 if there are 2 ore more references to the page and 0 if +** Return 1 if there are 2 or more references to the page and 0 if ** if this is the first reference to the page. ** ** Also check that the page number is in bounds. */ -static int checkRef(IntegrityCk *pCheck, Pgno iPage, char *zContext){ +static int checkRef(IntegrityCk *pCheck, Pgno iPage){ if( iPage==0 ) return 1; if( iPage>pCheck->nPage ){ - checkAppendMsg(pCheck, zContext, "invalid page number %d", iPage); + checkAppendMsg(pCheck, "invalid page number %d", iPage); return 1; } if( getPageReferenced(pCheck, iPage) ){ - checkAppendMsg(pCheck, zContext, "2nd reference to page %d", iPage); + checkAppendMsg(pCheck, "2nd reference to page %d", iPage); return 1; } setPageReferenced(pCheck, iPage); @@ -58981,8 +63993,7 @@ static void checkPtrmap( IntegrityCk *pCheck, /* Integrity check context */ Pgno iChild, /* Child page number */ u8 eType, /* Expected pointer map type */ - Pgno iParent, /* Expected pointer map parent page number */ - char *zContext /* Context description (used for error msg) */ + Pgno iParent /* Expected pointer map parent page number */ ){ int rc; u8 ePtrmapType; @@ -58991,12 +64002,12 @@ static void checkPtrmap( rc = ptrmapGet(pCheck->pBt, iChild, &ePtrmapType, &iPtrmapParent); if( rc!=SQLITE_OK ){ if( rc==SQLITE_NOMEM || rc==SQLITE_IOERR_NOMEM ) pCheck->mallocFailed = 1; - checkAppendMsg(pCheck, zContext, "Failed to read ptrmap key=%d", iChild); + checkAppendMsg(pCheck, "Failed to read ptrmap key=%d", iChild); return; } if( ePtrmapType!=eType || iPtrmapParent!=iParent ){ - checkAppendMsg(pCheck, zContext, + checkAppendMsg(pCheck, "Bad ptr map entry key=%d expected=(%d,%d) got=(%d,%d)", iChild, eType, iParent, ePtrmapType, iPtrmapParent); } @@ -59011,8 +64022,7 @@ static void checkList( IntegrityCk *pCheck, /* Integrity checking context */ int isFreeList, /* True for a freelist. False for overflow page list */ int iPage, /* Page number for first page in the list */ - int N, /* Expected number of pages in the list */ - char *zContext /* Context for error messages */ + int N /* Expected number of pages in the list */ ){ int i; int expected = N; @@ -59021,14 +64031,14 @@ static void checkList( DbPage *pOvflPage; unsigned char *pOvflData; if( iPage<1 ){ - checkAppendMsg(pCheck, zContext, + checkAppendMsg(pCheck, "%d of %d pages missing from overflow list starting at %d", N+1, expected, iFirst); break; } - if( checkRef(pCheck, iPage, zContext) ) break; - if( sqlite3PagerGet(pCheck->pPager, (Pgno)iPage, &pOvflPage) ){ - checkAppendMsg(pCheck, zContext, "failed to get page %d", iPage); + if( checkRef(pCheck, iPage) ) break; + if( sqlite3PagerGet(pCheck->pPager, (Pgno)iPage, &pOvflPage, 0) ){ + checkAppendMsg(pCheck, "failed to get page %d", iPage); break; } pOvflData = (unsigned char *)sqlite3PagerGetData(pOvflPage); @@ -59036,11 +64046,11 @@ static void checkList( int n = get4byte(&pOvflData[4]); #ifndef SQLITE_OMIT_AUTOVACUUM if( pCheck->pBt->autoVacuum ){ - checkPtrmap(pCheck, iPage, PTRMAP_FREEPAGE, 0, zContext); + checkPtrmap(pCheck, iPage, PTRMAP_FREEPAGE, 0); } #endif if( n>(int)pCheck->pBt->usableSize/4-2 ){ - checkAppendMsg(pCheck, zContext, + checkAppendMsg(pCheck, "freelist leaf count too big on page %d", iPage); N--; }else{ @@ -59048,10 +64058,10 @@ static void checkList( Pgno iFreePage = get4byte(&pOvflData[8+i*4]); #ifndef SQLITE_OMIT_AUTOVACUUM if( pCheck->pBt->autoVacuum ){ - checkPtrmap(pCheck, iFreePage, PTRMAP_FREEPAGE, 0, zContext); + checkPtrmap(pCheck, iFreePage, PTRMAP_FREEPAGE, 0); } #endif - checkRef(pCheck, iFreePage, zContext); + checkRef(pCheck, iFreePage); } N -= n; } @@ -59064,16 +64074,71 @@ static void checkList( */ if( pCheck->pBt->autoVacuum && N>0 ){ i = get4byte(pOvflData); - checkPtrmap(pCheck, i, PTRMAP_OVERFLOW2, iPage, zContext); + checkPtrmap(pCheck, i, PTRMAP_OVERFLOW2, iPage); } } #endif iPage = get4byte(pOvflData); sqlite3PagerUnref(pOvflPage); + + if( isFreeList && N<(iPage!=0) ){ + checkAppendMsg(pCheck, "free-page count in header is too small"); + } } } #endif /* SQLITE_OMIT_INTEGRITY_CHECK */ +/* +** An implementation of a min-heap. +** +** aHeap[0] is the number of elements on the heap. aHeap[1] is the +** root element. The daughter nodes of aHeap[N] are aHeap[N*2] +** and aHeap[N*2+1]. +** +** The heap property is this: Every node is less than or equal to both +** of its daughter nodes. A consequence of the heap property is that the +** root node aHeap[1] is always the minimum value currently in the heap. +** +** The btreeHeapInsert() routine inserts an unsigned 32-bit number onto +** the heap, preserving the heap property. The btreeHeapPull() routine +** removes the root element from the heap (the minimum value in the heap) +** and then moves other nodes around as necessary to preserve the heap +** property. +** +** This heap is used for cell overlap and coverage testing. Each u32 +** entry represents the span of a cell or freeblock on a btree page. +** The upper 16 bits are the index of the first byte of a range and the +** lower 16 bits are the index of the last byte of that range. +*/ +static void btreeHeapInsert(u32 *aHeap, u32 x){ + u32 j, i = ++aHeap[0]; + aHeap[i] = x; + while( (j = i/2)>0 && aHeap[j]>aHeap[i] ){ + x = aHeap[j]; + aHeap[j] = aHeap[i]; + aHeap[i] = x; + i = j; + } +} +static int btreeHeapPull(u32 *aHeap, u32 *pOut){ + u32 j, i, x; + if( (x = aHeap[0])==0 ) return 0; + *pOut = aHeap[1]; + aHeap[1] = aHeap[x]; + aHeap[x] = 0xffffffff; + aHeap[0]--; + i = 1; + while( (j = i*2)<=aHeap[0] ){ + if( aHeap[j]>aHeap[j+1] ) j++; + if( aHeap[i]zPfx; + int saved_v1 = pCheck->v1; + int saved_v2 = pCheck->v2; + u8 savedIsInit = 0; /* Check that the page exists */ pBt = pCheck->pBt; usableSize = pBt->usableSize; if( iPage==0 ) return 0; - if( checkRef(pCheck, iPage, zParentContext) ) return 0; + if( checkRef(pCheck, iPage) ) return 0; + pCheck->zPfx = "Page %d: "; + pCheck->v1 = iPage; if( (rc = btreeGetPage(pBt, (Pgno)iPage, &pPage, 0))!=0 ){ - checkAppendMsg(pCheck, zContext, + checkAppendMsg(pCheck, "unable to get the page. error code=%d", rc); - return 0; + goto end_of_check; } /* Clear MemPage.isInit to make sure the corruption detection code in ** btreeInitPage() is executed. */ + savedIsInit = pPage->isInit; pPage->isInit = 0; if( (rc = btreeInitPage(pPage))!=0 ){ assert( rc==SQLITE_CORRUPT ); /* The only possible error from InitPage */ - checkAppendMsg(pCheck, zContext, + checkAppendMsg(pCheck, "btreeInitPage() returns error code %d", rc); - releasePage(pPage); - return 0; + goto end_of_check; + } + data = pPage->aData; + hdr = pPage->hdrOffset; + + /* Set up for cell analysis */ + pCheck->zPfx = "On tree page %d cell %d: "; + contentOffset = get2byteNotZero(&data[hdr+5]); + assert( contentOffset<=usableSize ); /* Enforced by btreeInitPage() */ + + /* EVIDENCE-OF: R-37002-32774 The two-byte integer at offset 3 gives the + ** number of cells on the page. */ + nCell = get2byte(&data[hdr+3]); + assert( pPage->nCell==nCell ); + + /* EVIDENCE-OF: R-23882-45353 The cell pointer array of a b-tree page + ** immediately follows the b-tree page header. */ + cellStart = hdr + 12 - 4*pPage->leaf; + assert( pPage->aCellIdx==&data[cellStart] ); + pCellIdx = &data[cellStart + 2*(nCell-1)]; + + if( !pPage->leaf ){ + /* Analyze the right-child page of internal pages */ + pgno = get4byte(&data[hdr+8]); +#ifndef SQLITE_OMIT_AUTOVACUUM + if( pBt->autoVacuum ){ + pCheck->zPfx = "On page %d at right child: "; + checkPtrmap(pCheck, pgno, PTRMAP_BTREE, iPage); + } +#endif + depth = checkTreePage(pCheck, pgno, &maxKey, maxKey); + keyCanBeEqual = 0; + }else{ + /* For leaf pages, the coverage check will occur in the same loop + ** as the other cell checks, so initialize the heap. */ + heap = pCheck->heap; + heap[0] = 0; } - /* Check out all the cells. - */ - depth = 0; - for(i=0; inCell && pCheck->mxErr; i++){ - u8 *pCell; - u32 sz; + /* EVIDENCE-OF: R-02776-14802 The cell pointer array consists of K 2-byte + ** integer offsets to the cell contents. */ + for(i=nCell-1; i>=0 && pCheck->mxErr; i--){ CellInfo info; - /* Check payload overflow pages - */ - sqlite3_snprintf(sizeof(zContext), zContext, - "On tree page %d cell %d: ", iPage, i); - pCell = findCell(pPage,i); - btreeParseCellPtr(pPage, pCell, &info); - sz = info.nData; - if( !pPage->intKey ) sz += (int)info.nKey; - /* For intKey pages, check that the keys are in order. - */ - else if( i==0 ) nMinKey = nMaxKey = info.nKey; - else{ - if( info.nKey <= nMaxKey ){ - checkAppendMsg(pCheck, zContext, - "Rowid %lld out of order (previous was %lld)", info.nKey, nMaxKey); - } - nMaxKey = info.nKey; + /* Check cell size */ + pCheck->v2 = i; + assert( pCellIdx==&data[cellStart + i*2] ); + pc = get2byteAligned(pCellIdx); + pCellIdx -= 2; + if( pcusableSize-4 ){ + checkAppendMsg(pCheck, "Offset %d out of range %d..%d", + pc, contentOffset, usableSize-4); + doCoverageCheck = 0; + continue; } - assert( sz==info.nPayload ); - if( (sz>info.nLocal) - && (&pCell[info.iOverflow]<=&pPage->aData[pBt->usableSize]) - ){ - int nPage = (sz - info.nLocal + usableSize - 5)/(usableSize - 4); - Pgno pgnoOvfl = get4byte(&pCell[info.iOverflow]); + pCell = &data[pc]; + pPage->xParseCell(pPage, pCell, &info); + if( pc+info.nSize>usableSize ){ + checkAppendMsg(pCheck, "Extends off end of page"); + doCoverageCheck = 0; + continue; + } + + /* Check for integer primary key out of range */ + if( pPage->intKey ){ + if( keyCanBeEqual ? (info.nKey > maxKey) : (info.nKey >= maxKey) ){ + checkAppendMsg(pCheck, "Rowid %lld out of order", info.nKey); + } + maxKey = info.nKey; + } + + /* Check the content overflow list */ + if( info.nPayload>info.nLocal ){ + int nPage; /* Number of pages on the overflow chain */ + Pgno pgnoOvfl; /* First page of the overflow chain */ + assert( pc + info.nSize - 4 <= usableSize ); + nPage = (info.nPayload - info.nLocal + usableSize - 5)/(usableSize - 4); + pgnoOvfl = get4byte(&pCell[info.nSize - 4]); #ifndef SQLITE_OMIT_AUTOVACUUM if( pBt->autoVacuum ){ - checkPtrmap(pCheck, pgnoOvfl, PTRMAP_OVERFLOW1, iPage, zContext); + checkPtrmap(pCheck, pgnoOvfl, PTRMAP_OVERFLOW1, iPage); } #endif - checkList(pCheck, 0, pgnoOvfl, nPage, zContext); + checkList(pCheck, 0, pgnoOvfl, nPage); } - /* Check sanity of left child page. - */ if( !pPage->leaf ){ + /* Check sanity of left child page for internal pages */ pgno = get4byte(pCell); #ifndef SQLITE_OMIT_AUTOVACUUM if( pBt->autoVacuum ){ - checkPtrmap(pCheck, pgno, PTRMAP_BTREE, iPage, zContext); + checkPtrmap(pCheck, pgno, PTRMAP_BTREE, iPage); } #endif - d2 = checkTreePage(pCheck, pgno, zContext, &nMinKey, i==0 ? NULL : &nMaxKey); - if( i>0 && d2!=depth ){ - checkAppendMsg(pCheck, zContext, "Child page depth differs"); - } - depth = d2; - } - } - - if( !pPage->leaf ){ - pgno = get4byte(&pPage->aData[pPage->hdrOffset+8]); - sqlite3_snprintf(sizeof(zContext), zContext, - "On page %d at right child: ", iPage); -#ifndef SQLITE_OMIT_AUTOVACUUM - if( pBt->autoVacuum ){ - checkPtrmap(pCheck, pgno, PTRMAP_BTREE, iPage, zContext); - } -#endif - checkTreePage(pCheck, pgno, zContext, NULL, !pPage->nCell ? NULL : &nMaxKey); - } - - /* For intKey leaf pages, check that the min/max keys are in order - ** with any left/parent/right pages. - */ - if( pPage->leaf && pPage->intKey ){ - /* if we are a left child page */ - if( pnParentMinKey ){ - /* if we are the left most child page */ - if( !pnParentMaxKey ){ - if( nMaxKey > *pnParentMinKey ){ - checkAppendMsg(pCheck, zContext, - "Rowid %lld out of order (max larger than parent min of %lld)", - nMaxKey, *pnParentMinKey); - } - }else{ - if( nMinKey <= *pnParentMinKey ){ - checkAppendMsg(pCheck, zContext, - "Rowid %lld out of order (min less than parent min of %lld)", - nMinKey, *pnParentMinKey); - } - if( nMaxKey > *pnParentMaxKey ){ - checkAppendMsg(pCheck, zContext, - "Rowid %lld out of order (max larger than parent max of %lld)", - nMaxKey, *pnParentMaxKey); - } - *pnParentMinKey = nMaxKey; - } - /* else if we're a right child page */ - } else if( pnParentMaxKey ){ - if( nMinKey <= *pnParentMaxKey ){ - checkAppendMsg(pCheck, zContext, - "Rowid %lld out of order (min less than parent max of %lld)", - nMinKey, *pnParentMaxKey); + d2 = checkTreePage(pCheck, pgno, &maxKey, maxKey); + keyCanBeEqual = 0; + if( d2!=depth ){ + checkAppendMsg(pCheck, "Child page depth differs"); + depth = d2; } + }else{ + /* Populate the coverage-checking heap for leaf pages */ + btreeHeapInsert(heap, (pc<<16)|(pc+info.nSize-1)); } } + *piMinKey = maxKey; /* Check for complete coverage of the page */ - data = pPage->aData; - hdr = pPage->hdrOffset; - hit = sqlite3PageMalloc( pBt->pageSize ); - if( hit==0 ){ - pCheck->mallocFailed = 1; - }else{ - int contentOffset = get2byteNotZero(&data[hdr+5]); - assert( contentOffset<=usableSize ); /* Enforced by btreeInitPage() */ - memset(hit+contentOffset, 0, usableSize-contentOffset); - memset(hit, 1, contentOffset); - nCell = get2byte(&data[hdr+3]); - cellStart = hdr + 12 - 4*pPage->leaf; - for(i=0; i=usableSize ){ - checkAppendMsg(pCheck, 0, - "Corruption detected in cell %d on page %d",i,iPage); - }else{ - for(j=pc+size-1; j>=pc; j--) hit[j]++; + pCheck->zPfx = 0; + if( doCoverageCheck && pCheck->mxErr>0 ){ + /* For leaf pages, the min-heap has already been initialized and the + ** cells have already been inserted. But for internal pages, that has + ** not yet been done, so do it now */ + if( !pPage->leaf ){ + heap = pCheck->heap; + heap[0] = 0; + for(i=nCell-1; i>=0; i--){ + u32 size; + pc = get2byteAligned(&data[cellStart+i*2]); + size = pPage->xCellSize(pPage, &data[pc]); + btreeHeapInsert(heap, (pc<<16)|(pc+size-1)); } } + /* Add the freeblocks to the min-heap + ** + ** EVIDENCE-OF: R-20690-50594 The second field of the b-tree page header + ** is the offset of the first freeblock, or zero if there are no + ** freeblocks on the page. + */ i = get2byte(&data[hdr+1]); while( i>0 ){ int size, j; - assert( i<=usableSize-4 ); /* Enforced by btreeInitPage() */ + assert( (u32)i<=usableSize-4 ); /* Enforced by btreeInitPage() */ size = get2byte(&data[i+2]); - assert( i+size<=usableSize ); /* Enforced by btreeInitPage() */ - for(j=i+size-1; j>=i; j--) hit[j]++; + assert( (u32)(i+size)<=usableSize ); /* Enforced by btreeInitPage() */ + btreeHeapInsert(heap, (((u32)i)<<16)|(i+size-1)); + /* EVIDENCE-OF: R-58208-19414 The first 2 bytes of a freeblock are a + ** big-endian integer which is the offset in the b-tree page of the next + ** freeblock in the chain, or zero if the freeblock is the last on the + ** chain. */ j = get2byte(&data[i]); + /* EVIDENCE-OF: R-06866-39125 Freeblocks are always connected in order of + ** increasing offset. */ assert( j==0 || j>i+size ); /* Enforced by btreeInitPage() */ - assert( j<=usableSize-4 ); /* Enforced by btreeInitPage() */ + assert( (u32)j<=usableSize-4 ); /* Enforced by btreeInitPage() */ i = j; } - for(i=cnt=0; i1 ){ - checkAppendMsg(pCheck, 0, - "Multiple uses for byte %d of page %d", i, iPage); + /* Analyze the min-heap looking for overlap between cells and/or + ** freeblocks, and counting the number of untracked bytes in nFrag. + ** + ** Each min-heap entry is of the form: (start_address<<16)|end_address. + ** There is an implied first entry the covers the page header, the cell + ** pointer index, and the gap between the cell pointer index and the start + ** of cell content. + ** + ** The loop below pulls entries from the min-heap in order and compares + ** the start_address against the previous end_address. If there is an + ** overlap, that means bytes are used multiple times. If there is a gap, + ** that gap is added to the fragmentation count. + */ + nFrag = 0; + prev = contentOffset - 1; /* Implied first min-heap entry */ + while( btreeHeapPull(heap,&x) ){ + if( (prev&0xffff)>=(x>>16) ){ + checkAppendMsg(pCheck, + "Multiple uses for byte %u of page %d", x>>16, iPage); break; + }else{ + nFrag += (x>>16) - (prev&0xffff) - 1; + prev = x; } } - if( cnt!=data[hdr+7] ){ - checkAppendMsg(pCheck, 0, + nFrag += usableSize - (prev&0xffff) - 1; + /* EVIDENCE-OF: R-43263-13491 The total number of bytes in all fragments + ** is stored in the fifth field of the b-tree page header. + ** EVIDENCE-OF: R-07161-27322 The one-byte integer at offset 7 gives the + ** number of fragmented free bytes within the cell content area. + */ + if( heap[0]==0 && nFrag!=data[hdr+7] ){ + checkAppendMsg(pCheck, "Fragmentation of %d bytes reported as %d on page %d", - cnt, data[hdr+7], iPage); + nFrag, data[hdr+7], iPage); } } - sqlite3PageFree(hit); + +end_of_check: + if( !doCoverageCheck ) pPage->isInit = savedIsInit; releasePage(pPage); + pCheck->zPfx = saved_zPfx; + pCheck->v1 = saved_v1; + pCheck->v2 = saved_v2; return depth+1; } #endif /* SQLITE_OMIT_INTEGRITY_CHECK */ @@ -59325,60 +64426,74 @@ SQLITE_PRIVATE char *sqlite3BtreeIntegrityCheck( int *pnErr /* Write number of errors seen to this variable */ ){ Pgno i; - int nRef; IntegrityCk sCheck; BtShared *pBt = p->pBt; + int savedDbFlags = pBt->db->flags; char zErr[100]; + VVA_ONLY( int nRef ); sqlite3BtreeEnter(p); assert( p->inTrans>TRANS_NONE && pBt->inTransaction>TRANS_NONE ); - nRef = sqlite3PagerRefcount(pBt->pPager); + assert( (nRef = sqlite3PagerRefcount(pBt->pPager))>=0 ); sCheck.pBt = pBt; sCheck.pPager = pBt->pPager; sCheck.nPage = btreePagecount(sCheck.pBt); sCheck.mxErr = mxErr; sCheck.nErr = 0; sCheck.mallocFailed = 0; - *pnErr = 0; + sCheck.zPfx = 0; + sCheck.v1 = 0; + sCheck.v2 = 0; + sCheck.aPgRef = 0; + sCheck.heap = 0; + sqlite3StrAccumInit(&sCheck.errMsg, 0, zErr, sizeof(zErr), SQLITE_MAX_LENGTH); if( sCheck.nPage==0 ){ - sqlite3BtreeLeave(p); - return 0; + goto integrity_ck_cleanup; } sCheck.aPgRef = sqlite3MallocZero((sCheck.nPage / 8)+ 1); if( !sCheck.aPgRef ){ - *pnErr = 1; - sqlite3BtreeLeave(p); - return 0; + sCheck.mallocFailed = 1; + goto integrity_ck_cleanup; } + sCheck.heap = (u32*)sqlite3PageMalloc( pBt->pageSize ); + if( sCheck.heap==0 ){ + sCheck.mallocFailed = 1; + goto integrity_ck_cleanup; + } + i = PENDING_BYTE_PAGE(pBt); if( i<=sCheck.nPage ) setPageReferenced(&sCheck, i); - sqlite3StrAccumInit(&sCheck.errMsg, zErr, sizeof(zErr), SQLITE_MAX_LENGTH); - sCheck.errMsg.useMalloc = 2; /* Check the integrity of the freelist */ + sCheck.zPfx = "Main freelist: "; checkList(&sCheck, 1, get4byte(&pBt->pPage1->aData[32]), - get4byte(&pBt->pPage1->aData[36]), "Main freelist: "); + get4byte(&pBt->pPage1->aData[36])); + sCheck.zPfx = 0; /* Check all the tables. */ + testcase( pBt->db->flags & SQLITE_CellSizeCk ); + pBt->db->flags &= ~SQLITE_CellSizeCk; for(i=0; (int)iautoVacuum && aRoot[i]>1 ){ - checkPtrmap(&sCheck, aRoot[i], PTRMAP_ROOTPAGE, 0, 0); + checkPtrmap(&sCheck, aRoot[i], PTRMAP_ROOTPAGE, 0); } #endif - checkTreePage(&sCheck, aRoot[i], "List of tree roots: ", NULL, NULL); + checkTreePage(&sCheck, aRoot[i], ¬Used, LARGEST_INT64); } + pBt->db->flags = savedDbFlags; /* Make sure every page in the file is referenced */ for(i=1; i<=sCheck.nPage && sCheck.mxErr; i++){ #ifdef SQLITE_OMIT_AUTOVACUUM if( getPageReferenced(&sCheck, i)==0 ){ - checkAppendMsg(&sCheck, 0, "Page %d is never used", i); + checkAppendMsg(&sCheck, "Page %d is never used", i); } #else /* If the database supports auto-vacuum, make sure no tables contain @@ -59386,37 +64501,29 @@ SQLITE_PRIVATE char *sqlite3BtreeIntegrityCheck( */ if( getPageReferenced(&sCheck, i)==0 && (PTRMAP_PAGENO(pBt, i)!=i || !pBt->autoVacuum) ){ - checkAppendMsg(&sCheck, 0, "Page %d is never used", i); + checkAppendMsg(&sCheck, "Page %d is never used", i); } if( getPageReferenced(&sCheck, i)!=0 && (PTRMAP_PAGENO(pBt, i)==i && pBt->autoVacuum) ){ - checkAppendMsg(&sCheck, 0, "Pointer map page %d is referenced", i); + checkAppendMsg(&sCheck, "Pointer map page %d is referenced", i); } #endif } - /* Make sure this analysis did not leave any unref() pages. - ** This is an internal consistency check; an integrity check - ** of the integrity check. - */ - if( NEVER(nRef != sqlite3PagerRefcount(pBt->pPager)) ){ - checkAppendMsg(&sCheck, 0, - "Outstanding page count goes from %d to %d during this analysis", - nRef, sqlite3PagerRefcount(pBt->pPager) - ); - } - /* Clean up and report errors. */ - sqlite3BtreeLeave(p); +integrity_ck_cleanup: + sqlite3PageFree(sCheck.heap); sqlite3_free(sCheck.aPgRef); if( sCheck.mallocFailed ){ sqlite3StrAccumReset(&sCheck.errMsg); - *pnErr = sCheck.nErr+1; - return 0; + sCheck.nErr++; } *pnErr = sCheck.nErr; if( sCheck.nErr==0 ) sqlite3StrAccumReset(&sCheck.errMsg); + /* Make sure this analysis did not leave any unref() pages. */ + assert( nRef==sqlite3PagerRefcount(pBt->pPager) ); + sqlite3BtreeLeave(p); return sqlite3StrAccumFinish(&sCheck.errMsg); } #endif /* SQLITE_OMIT_INTEGRITY_CHECK */ @@ -59596,7 +64703,7 @@ SQLITE_PRIVATE int sqlite3BtreePutData(BtCursor *pCsr, u32 offset, u32 amt, void ** required in case any of them are holding references to an xFetch ** version of the b-tree page modified by the accessPayload call below. ** - ** Note that pCsr must be open on a BTREE_INTKEY table and saveCursorPosition() + ** Note that pCsr must be open on a INTKEY table and saveCursorPosition() ** and hence saveAllCursors() cannot fail on a BTREE_INTKEY table, hence ** saveAllCursors can only return SQLITE_OK. */ @@ -59627,6 +64734,7 @@ SQLITE_PRIVATE int sqlite3BtreePutData(BtCursor *pCsr, u32 offset, u32 amt, void */ SQLITE_PRIVATE void sqlite3BtreeIncrblobCursor(BtCursor *pCur){ pCur->curFlags |= BTCF_Incrblob; + pCur->pBtree->hasIncrblobCur = 1; } #endif @@ -59667,12 +64775,11 @@ SQLITE_PRIVATE int sqlite3BtreeSetVersion(Btree *pBtree, int iVersion){ } /* -** set the mask of hint flags for cursor pCsr. Currently the only valid -** values are 0 and BTREE_BULKLOAD. +** Return true if the cursor has a hint specified. This routine is +** only used from within assert() statements */ -SQLITE_PRIVATE void sqlite3BtreeCursorHints(BtCursor *pCsr, unsigned int mask){ - assert( mask==BTREE_BULKLOAD || mask==0 ); - pCsr->hints = mask; +SQLITE_PRIVATE int sqlite3BtreeCursorHasHint(BtCursor *pCsr, unsigned int mask){ + return (pCsr->hints & mask)!=0; } /* @@ -59682,6 +64789,11 @@ SQLITE_PRIVATE int sqlite3BtreeIsReadonly(Btree *p){ return (p->pBt->btsFlags & BTS_READ_ONLY)!=0; } +/* +** Return the size of the header added to each page by this module. +*/ +SQLITE_PRIVATE int sqlite3HeaderSizeBtree(void){ return ROUND8(sizeof(MemPage)); } + /************** End of btree.c ***********************************************/ /************** Begin file backup.c ******************************************/ /* @@ -59698,6 +64810,8 @@ SQLITE_PRIVATE int sqlite3BtreeIsReadonly(Btree *p){ ** This file contains the implementation of the sqlite3_backup_XXX() ** API functions and the related features. */ +/* #include "sqliteInt.h" */ +/* #include "btreeInt.h" */ /* ** Structure allocated for each backup operation. @@ -59771,12 +64885,12 @@ static Btree *findBtree(sqlite3 *pErrorDb, sqlite3 *pDb, const char *zDb){ int rc = 0; pParse = sqlite3StackAllocZero(pErrorDb, sizeof(*pParse)); if( pParse==0 ){ - sqlite3Error(pErrorDb, SQLITE_NOMEM, "out of memory"); + sqlite3ErrorWithMsg(pErrorDb, SQLITE_NOMEM, "out of memory"); rc = SQLITE_NOMEM; }else{ pParse->db = pDb; if( sqlite3OpenTempDatabase(pParse) ){ - sqlite3Error(pErrorDb, pParse->rc, "%s", pParse->zErrMsg); + sqlite3ErrorWithMsg(pErrorDb, pParse->rc, "%s", pParse->zErrMsg); rc = SQLITE_ERROR; } sqlite3DbFree(pErrorDb, pParse->zErrMsg); @@ -59789,7 +64903,7 @@ static Btree *findBtree(sqlite3 *pErrorDb, sqlite3 *pDb, const char *zDb){ } if( i<0 ){ - sqlite3Error(pErrorDb, SQLITE_ERROR, "unknown database %s", zDb); + sqlite3ErrorWithMsg(pErrorDb, SQLITE_ERROR, "unknown database %s", zDb); return 0; } @@ -59806,6 +64920,20 @@ static int setDestPgsz(sqlite3_backup *p){ return rc; } +/* +** Check that there is no open read-transaction on the b-tree passed as the +** second argument. If there is not, return SQLITE_OK. Otherwise, if there +** is an open read-transaction, return SQLITE_ERROR and leave an error +** message in database handle db. +*/ +static int checkReadTransaction(sqlite3 *db, Btree *p){ + if( sqlite3BtreeIsInReadTrans(p) ){ + sqlite3ErrorWithMsg(db, SQLITE_ERROR, "destination database is in use"); + return SQLITE_ERROR; + } + return SQLITE_OK; +} + /* ** Create an sqlite3_backup process to copy the contents of zSrcDb from ** connection handle pSrcDb to zDestDb in pDestDb. If successful, return @@ -59814,7 +64942,7 @@ static int setDestPgsz(sqlite3_backup *p){ ** If an error occurs, NULL is returned and an error code and error message ** stored in database handle pDestDb. */ -SQLITE_API sqlite3_backup *sqlite3_backup_init( +SQLITE_API sqlite3_backup *SQLITE_STDCALL sqlite3_backup_init( sqlite3* pDestDb, /* Database to write to */ const char *zDestDb, /* Name of database within pDestDb */ sqlite3* pSrcDb, /* Database connection to read from */ @@ -59822,6 +64950,13 @@ SQLITE_API sqlite3_backup *sqlite3_backup_init( ){ sqlite3_backup *p; /* Value to return */ +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(pSrcDb)||!sqlite3SafetyCheckOk(pDestDb) ){ + (void)SQLITE_MISUSE_BKPT; + return 0; + } +#endif + /* Lock the source database handle. The destination database ** handle is not locked in this routine, but it is locked in ** sqlite3_backup_step(). The user is required to ensure that no @@ -59834,7 +64969,7 @@ SQLITE_API sqlite3_backup *sqlite3_backup_init( sqlite3_mutex_enter(pDestDb->mutex); if( pSrcDb==pDestDb ){ - sqlite3Error( + sqlite3ErrorWithMsg( pDestDb, SQLITE_ERROR, "source and destination must be distinct" ); p = 0; @@ -59845,7 +64980,7 @@ SQLITE_API sqlite3_backup *sqlite3_backup_init( ** sqlite3_backup_finish(). */ p = (sqlite3_backup *)sqlite3MallocZero(sizeof(sqlite3_backup)); if( !p ){ - sqlite3Error(pDestDb, SQLITE_NOMEM, 0); + sqlite3Error(pDestDb, SQLITE_NOMEM); } } @@ -59858,12 +64993,15 @@ SQLITE_API sqlite3_backup *sqlite3_backup_init( p->iNext = 1; p->isAttached = 0; - if( 0==p->pSrc || 0==p->pDest || setDestPgsz(p)==SQLITE_NOMEM ){ + if( 0==p->pSrc || 0==p->pDest + || setDestPgsz(p)==SQLITE_NOMEM + || checkReadTransaction(pDestDb, p->pDest)!=SQLITE_OK + ){ /* One (or both) of the named databases did not exist or an OOM - ** error was hit. The error has already been written into the - ** pDestDb handle. All that is left to do here is free the - ** sqlite3_backup structure. - */ + ** error was hit. Or there is a transaction open on the destination + ** database. The error has already been written into the pDestDb + ** handle. All that is left to do here is free the sqlite3_backup + ** structure. */ sqlite3_free(p); p = 0; } @@ -59907,7 +65045,7 @@ static int backupOnePage( ** guaranteed that the shared-mutex is held by this thread, handle ** p->pSrc may not actually be the owner. */ int nSrcReserve = sqlite3BtreeGetReserveNoMutex(p->pSrc); - int nDestReserve = sqlite3BtreeGetReserve(p->pDest); + int nDestReserve = sqlite3BtreeGetOptimalReserve(p->pDest); #endif int rc = SQLITE_OK; i64 iOff; @@ -59953,7 +65091,7 @@ static int backupOnePage( DbPage *pDestPg = 0; Pgno iDest = (Pgno)(iOff/nDestPgsz)+1; if( iDest==PENDING_BYTE_PAGE(p->pDest->pBt) ) continue; - if( SQLITE_OK==(rc = sqlite3PagerGet(pDestPager, iDest, &pDestPg)) + if( SQLITE_OK==(rc = sqlite3PagerGet(pDestPager, iDest, &pDestPg, 0)) && SQLITE_OK==(rc = sqlite3PagerWrite(pDestPg)) ){ const u8 *zIn = &zSrcData[iOff%nSrcPgsz]; @@ -60012,12 +65150,15 @@ static void attachBackupObject(sqlite3_backup *p){ /* ** Copy nPage pages from the source b-tree to the destination. */ -SQLITE_API int sqlite3_backup_step(sqlite3_backup *p, int nPage){ +SQLITE_API int SQLITE_STDCALL sqlite3_backup_step(sqlite3_backup *p, int nPage){ int rc; int destMode; /* Destination journal mode */ int pgszSrc = 0; /* Source page size */ int pgszDest = 0; /* Destination page size */ +#ifdef SQLITE_ENABLE_API_ARMOR + if( p==0 ) return SQLITE_MISUSE_BKPT; +#endif sqlite3_mutex_enter(p->pSrcDb->mutex); sqlite3BtreeEnter(p->pSrc); if( p->pDestDb ){ @@ -60076,8 +65217,7 @@ SQLITE_API int sqlite3_backup_step(sqlite3_backup *p, int nPage){ const Pgno iSrcPg = p->iNext; /* Source page number */ if( iSrcPg!=PENDING_BYTE_PAGE(p->pSrc->pBt) ){ DbPage *pSrcPg; /* Source page object */ - rc = sqlite3PagerAcquire(pSrcPager, iSrcPg, &pSrcPg, - PAGER_GET_READONLY); + rc = sqlite3PagerGet(pSrcPager, iSrcPg, &pSrcPg,PAGER_GET_READONLY); if( rc==SQLITE_OK ){ rc = backupOnePage(p, iSrcPg, sqlite3PagerGetData(pSrcPg), 0); sqlite3PagerUnref(pSrcPg); @@ -60177,7 +65317,7 @@ SQLITE_API int sqlite3_backup_step(sqlite3_backup *p, int nPage){ for(iPg=nDestTruncate; rc==SQLITE_OK && iPg<=(Pgno)nDstPage; iPg++){ if( iPg!=PENDING_BYTE_PAGE(p->pDest->pBt) ){ DbPage *pPg; - rc = sqlite3PagerGet(pDestPager, iPg, &pPg); + rc = sqlite3PagerGet(pDestPager, iPg, &pPg, 0); if( rc==SQLITE_OK ){ rc = sqlite3PagerWrite(pPg); sqlite3PagerUnref(pPg); @@ -60197,7 +65337,7 @@ SQLITE_API int sqlite3_backup_step(sqlite3_backup *p, int nPage){ ){ PgHdr *pSrcPg = 0; const Pgno iSrcPg = (Pgno)((iOff/pgszSrc)+1); - rc = sqlite3PagerGet(pSrcPager, iSrcPg, &pSrcPg); + rc = sqlite3PagerGet(pSrcPager, iSrcPg, &pSrcPg, 0); if( rc==SQLITE_OK ){ u8 *zData = sqlite3PagerGetData(pSrcPg); rc = sqlite3OsWrite(pFile, zData, pgszSrc, iOff); @@ -60254,7 +65394,7 @@ SQLITE_API int sqlite3_backup_step(sqlite3_backup *p, int nPage){ /* ** Release all resources associated with an sqlite3_backup* handle. */ -SQLITE_API int sqlite3_backup_finish(sqlite3_backup *p){ +SQLITE_API int SQLITE_STDCALL sqlite3_backup_finish(sqlite3_backup *p){ sqlite3_backup **pp; /* Ptr to head of pagers backup list */ sqlite3 *pSrcDb; /* Source database connection */ int rc; /* Value to return */ @@ -60281,12 +65421,12 @@ SQLITE_API int sqlite3_backup_finish(sqlite3_backup *p){ } /* If a transaction is still open on the Btree, roll it back. */ - sqlite3BtreeRollback(p->pDest, SQLITE_OK); + sqlite3BtreeRollback(p->pDest, SQLITE_OK, 0); /* Set the error code of the destination database handle. */ rc = (p->rc==SQLITE_DONE) ? SQLITE_OK : p->rc; if( p->pDestDb ){ - sqlite3Error(p->pDestDb, rc, 0); + sqlite3Error(p->pDestDb, rc); /* Exit the mutexes and free the backup context structure. */ sqlite3LeaveMutexAndCloseZombie(p->pDestDb); @@ -60306,7 +65446,13 @@ SQLITE_API int sqlite3_backup_finish(sqlite3_backup *p){ ** Return the number of pages still to be backed up as of the most recent ** call to sqlite3_backup_step(). */ -SQLITE_API int sqlite3_backup_remaining(sqlite3_backup *p){ +SQLITE_API int SQLITE_STDCALL sqlite3_backup_remaining(sqlite3_backup *p){ +#ifdef SQLITE_ENABLE_API_ARMOR + if( p==0 ){ + (void)SQLITE_MISUSE_BKPT; + return 0; + } +#endif return p->nRemaining; } @@ -60314,7 +65460,13 @@ SQLITE_API int sqlite3_backup_remaining(sqlite3_backup *p){ ** Return the total number of pages in the source database as of the most ** recent call to sqlite3_backup_step(). */ -SQLITE_API int sqlite3_backup_pagecount(sqlite3_backup *p){ +SQLITE_API int SQLITE_STDCALL sqlite3_backup_pagecount(sqlite3_backup *p){ +#ifdef SQLITE_ENABLE_API_ARMOR + if( p==0 ){ + (void)SQLITE_MISUSE_BKPT; + return 0; + } +#endif return p->nPagecount; } @@ -60330,9 +65482,13 @@ SQLITE_API int sqlite3_backup_pagecount(sqlite3_backup *p){ ** corresponding to the source database is held when this function is ** called. */ -SQLITE_PRIVATE void sqlite3BackupUpdate(sqlite3_backup *pBackup, Pgno iPage, const u8 *aData){ - sqlite3_backup *p; /* Iterator variable */ - for(p=pBackup; p; p=p->pNext){ +static SQLITE_NOINLINE void backupUpdate( + sqlite3_backup *p, + Pgno iPage, + const u8 *aData +){ + assert( p!=0 ); + do{ assert( sqlite3_mutex_held(p->pSrc->pBt->mutex) ); if( !isFatalError(p->rc) && iPageiNext ){ /* The backup process p has already copied page iPage. But now it @@ -60349,7 +65505,10 @@ SQLITE_PRIVATE void sqlite3BackupUpdate(sqlite3_backup *pBackup, Pgno iPage, con p->rc = rc; } } - } + }while( (p = p->pNext)!=0 ); +} +SQLITE_PRIVATE void sqlite3BackupUpdate(sqlite3_backup *pBackup, Pgno iPage, const u8 *aData){ + if( pBackup ) backupUpdate(pBackup, iPage, aData); } /* @@ -60407,6 +65566,10 @@ SQLITE_PRIVATE int sqlite3BtreeCopyFile(Btree *pTo, Btree *pFrom){ b.pDest = pTo; b.iNext = 1; +#ifdef SQLITE_HAS_CODEC + sqlite3PagerAlignReserve(sqlite3BtreePager(pTo), sqlite3BtreePager(pFrom)); +#endif + /* 0x7FFFFFFF is the hard limit for the number of pages in a database ** file. By passing this as the number of pages to copy to ** sqlite3_backup_step(), we can guarantee that the copy finishes @@ -60450,6 +65613,8 @@ copy_finished: ** only within the VDBE. Interface routines refer to a Mem using the ** name sqlite_value */ +/* #include "sqliteInt.h" */ +/* #include "vdbeInt.h" */ #ifdef SQLITE_DEBUG /* @@ -60459,29 +65624,40 @@ copy_finished: ** this: assert( sqlite3VdbeCheckMemInvariants(pMem) ); */ SQLITE_PRIVATE int sqlite3VdbeCheckMemInvariants(Mem *p){ - /* The MEM_Dyn bit is set if and only if Mem.xDel is a non-NULL destructor - ** function for Mem.z + /* If MEM_Dyn is set then Mem.xDel!=0. + ** Mem.xDel is might not be initialized if MEM_Dyn is clear. */ assert( (p->flags & MEM_Dyn)==0 || p->xDel!=0 ); - assert( (p->flags & MEM_Dyn)!=0 || p->xDel==0 ); + + /* MEM_Dyn may only be set if Mem.szMalloc==0. In this way we + ** ensure that if Mem.szMalloc>0 then it is safe to do + ** Mem.z = Mem.zMalloc without having to check Mem.flags&MEM_Dyn. + ** That saves a few cycles in inner loops. */ + assert( (p->flags & MEM_Dyn)==0 || p->szMalloc==0 ); + + /* Cannot be both MEM_Int and MEM_Real at the same time */ + assert( (p->flags & (MEM_Int|MEM_Real))!=(MEM_Int|MEM_Real) ); + + /* The szMalloc field holds the correct memory allocation size */ + assert( p->szMalloc==0 + || p->szMalloc==sqlite3DbMallocSize(p->db,p->zMalloc) ); /* If p holds a string or blob, the Mem.z must point to exactly ** one of the following: ** ** (1) Memory in Mem.zMalloc and managed by the Mem object ** (2) Memory to be freed using Mem.xDel - ** (3) An ephermal string or blob + ** (3) An ephemeral string or blob ** (4) A static string or blob */ - if( (p->flags & (MEM_Str|MEM_Blob)) && p->z!=0 ){ + if( (p->flags & (MEM_Str|MEM_Blob)) && p->n>0 ){ assert( - ((p->z==p->zMalloc)? 1 : 0) + + ((p->szMalloc>0 && p->z==p->zMalloc)? 1 : 0) + ((p->flags&MEM_Dyn)!=0 ? 1 : 0) + ((p->flags&MEM_Ephem)!=0 ? 1 : 0) + ((p->flags&MEM_Static)!=0 ? 1 : 0) == 1 ); } - return 1; } #endif @@ -60535,7 +65711,7 @@ SQLITE_PRIVATE int sqlite3VdbeChangeEncoding(Mem *pMem, int desiredEnc){ ** blob if bPreserve is true. If bPreserve is false, any prior content ** in pMem->z is discarded. */ -SQLITE_PRIVATE int sqlite3VdbeMemGrow(Mem *pMem, int n, int bPreserve){ +SQLITE_PRIVATE SQLITE_NOINLINE int sqlite3VdbeMemGrow(Mem *pMem, int n, int bPreserve){ assert( sqlite3VdbeCheckMemInvariants(pMem) ); assert( (pMem->flags&MEM_RowSet)==0 ); @@ -60544,24 +65720,28 @@ SQLITE_PRIVATE int sqlite3VdbeMemGrow(Mem *pMem, int n, int bPreserve){ assert( bPreserve==0 || pMem->flags&(MEM_Blob|MEM_Str) ); testcase( bPreserve && pMem->z==0 ); - if( pMem->zMalloc==0 || sqlite3DbMallocSize(pMem->db, pMem->zMalloc)szMalloc==0 + || pMem->szMalloc==sqlite3DbMallocSize(pMem->db, pMem->zMalloc) ); + if( pMem->szMallocz==pMem->zMalloc ){ + if( bPreserve && pMem->szMalloc>0 && pMem->z==pMem->zMalloc ){ pMem->z = pMem->zMalloc = sqlite3DbReallocOrFree(pMem->db, pMem->z, n); bPreserve = 0; }else{ - sqlite3DbFree(pMem->db, pMem->zMalloc); + if( pMem->szMalloc>0 ) sqlite3DbFree(pMem->db, pMem->zMalloc); pMem->zMalloc = sqlite3DbMallocRaw(pMem->db, n); } if( pMem->zMalloc==0 ){ - VdbeMemRelease(pMem); + sqlite3VdbeMemSetNull(pMem); pMem->z = 0; - pMem->flags = MEM_Null; + pMem->szMalloc = 0; return SQLITE_NOMEM; + }else{ + pMem->szMalloc = sqlite3DbMallocSize(pMem->db, pMem->zMalloc); } } - if( pMem->z && bPreserve && pMem->z!=pMem->zMalloc ){ + if( bPreserve && pMem->z && pMem->z!=pMem->zMalloc ){ memcpy(pMem->zMalloc, pMem->z, pMem->n); } if( (pMem->flags&MEM_Dyn)!=0 ){ @@ -60571,15 +65751,37 @@ SQLITE_PRIVATE int sqlite3VdbeMemGrow(Mem *pMem, int n, int bPreserve){ pMem->z = pMem->zMalloc; pMem->flags &= ~(MEM_Dyn|MEM_Ephem|MEM_Static); - pMem->xDel = 0; return SQLITE_OK; } /* -** Make the given Mem object MEM_Dyn. In other words, make it so -** that any TEXT or BLOB content is stored in memory obtained from -** malloc(). In this way, we know that the memory is safe to be -** overwritten or altered. +** Change the pMem->zMalloc allocation to be at least szNew bytes. +** If pMem->zMalloc already meets or exceeds the requested size, this +** routine is a no-op. +** +** Any prior string or blob content in the pMem object may be discarded. +** The pMem->xDel destructor is called, if it exists. Though MEM_Str +** and MEM_Blob values may be discarded, MEM_Int, MEM_Real, and MEM_Null +** values are preserved. +** +** Return SQLITE_OK on success or an error code (probably SQLITE_NOMEM) +** if unable to complete the resizing. +*/ +SQLITE_PRIVATE int sqlite3VdbeMemClearAndResize(Mem *pMem, int szNew){ + assert( szNew>0 ); + assert( (pMem->flags & MEM_Dyn)==0 || pMem->szMalloc==0 ); + if( pMem->szMallocflags & MEM_Dyn)==0 ); + pMem->z = pMem->zMalloc; + pMem->flags &= (MEM_Null|MEM_Int|MEM_Real); + return SQLITE_OK; +} + +/* +** Change pMem so that its MEM_Str or MEM_Blob value is stored in +** MEM.zMalloc, where it can be safely written. ** ** Return SQLITE_OK on success or SQLITE_NOMEM if malloc fails. */ @@ -60589,17 +65791,18 @@ SQLITE_PRIVATE int sqlite3VdbeMemMakeWriteable(Mem *pMem){ assert( (pMem->flags&MEM_RowSet)==0 ); ExpandBlob(pMem); f = pMem->flags; - if( (f&(MEM_Str|MEM_Blob)) && pMem->z!=pMem->zMalloc ){ + if( (f&(MEM_Str|MEM_Blob)) && (pMem->szMalloc==0 || pMem->z!=pMem->zMalloc) ){ if( sqlite3VdbeMemGrow(pMem, pMem->n + 2, 1) ){ return SQLITE_NOMEM; } pMem->z[pMem->n] = 0; pMem->z[pMem->n+1] = 0; pMem->flags |= MEM_Term; -#ifdef SQLITE_DEBUG - pMem->pScopyFrom = 0; -#endif } + pMem->flags &= ~MEM_Ephem; +#ifdef SQLITE_DEBUG + pMem->pScopyFrom = 0; +#endif return SQLITE_OK; } @@ -60633,15 +65836,11 @@ SQLITE_PRIVATE int sqlite3VdbeMemExpandBlob(Mem *pMem){ } #endif - /* -** Make sure the given Mem is \u0000 terminated. +** It is already known that pMem contains an unterminated string. +** Add the zero terminator. */ -SQLITE_PRIVATE int sqlite3VdbeMemNulTerminate(Mem *pMem){ - assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) ); - if( (pMem->flags & MEM_Term)!=0 || (pMem->flags & MEM_Str)==0 ){ - return SQLITE_OK; /* Nothing to do */ - } +static SQLITE_NOINLINE int vdbeMemAddTerminator(Mem *pMem){ if( sqlite3VdbeMemGrow(pMem, pMem->n+2, 1) ){ return SQLITE_NOMEM; } @@ -60651,21 +65850,35 @@ SQLITE_PRIVATE int sqlite3VdbeMemNulTerminate(Mem *pMem){ return SQLITE_OK; } +/* +** Make sure the given Mem is \u0000 terminated. +*/ +SQLITE_PRIVATE int sqlite3VdbeMemNulTerminate(Mem *pMem){ + assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) ); + testcase( (pMem->flags & (MEM_Term|MEM_Str))==(MEM_Term|MEM_Str) ); + testcase( (pMem->flags & (MEM_Term|MEM_Str))==0 ); + if( (pMem->flags & (MEM_Term|MEM_Str))!=MEM_Str ){ + return SQLITE_OK; /* Nothing to do */ + }else{ + return vdbeMemAddTerminator(pMem); + } +} + /* ** Add MEM_Str to the set of representations for the given Mem. Numbers ** are converted using sqlite3_snprintf(). Converting a BLOB to a string ** is a no-op. ** -** Existing representations MEM_Int and MEM_Real are *not* invalidated. +** Existing representations MEM_Int and MEM_Real are invalidated if +** bForce is true but are retained if bForce is false. ** ** A MEM_Null value will never be passed to this function. This function is ** used for converting values to text for returning to the user (i.e. via ** sqlite3_value_text()), or for ensuring that values to be used as btree ** keys are strings. In the former case a NULL pointer is returned the -** user and the later is an internal programming error. +** user and the latter is an internal programming error. */ -SQLITE_PRIVATE int sqlite3VdbeMemStringify(Mem *pMem, int enc){ - int rc = SQLITE_OK; +SQLITE_PRIVATE int sqlite3VdbeMemStringify(Mem *pMem, u8 enc, u8 bForce){ int fg = pMem->flags; const int nByte = 32; @@ -60677,11 +65890,11 @@ SQLITE_PRIVATE int sqlite3VdbeMemStringify(Mem *pMem, int enc){ assert( EIGHT_BYTE_ALIGNMENT(pMem) ); - if( sqlite3VdbeMemGrow(pMem, nByte, 0) ){ + if( sqlite3VdbeMemClearAndResize(pMem, nByte) ){ return SQLITE_NOMEM; } - /* For a Real or Integer, use sqlite3_mprintf() to produce the UTF-8 + /* For a Real or Integer, use sqlite3_snprintf() to produce the UTF-8 ** string representation of the value. Then, if the required encoding ** is UTF-16le or UTF-16be do a translation. ** @@ -60691,13 +65904,14 @@ SQLITE_PRIVATE int sqlite3VdbeMemStringify(Mem *pMem, int enc){ sqlite3_snprintf(nByte, pMem->z, "%lld", pMem->u.i); }else{ assert( fg & MEM_Real ); - sqlite3_snprintf(nByte, pMem->z, "%!.15g", pMem->r); + sqlite3_snprintf(nByte, pMem->z, "%!.15g", pMem->u.r); } pMem->n = sqlite3Strlen30(pMem->z); pMem->enc = SQLITE_UTF8; pMem->flags |= MEM_Str|MEM_Term; + if( bForce ) pMem->flags &= ~(MEM_Int|MEM_Real); sqlite3VdbeChangeEncoding(pMem, enc); - return rc; + return SQLITE_OK; } /* @@ -60712,59 +65926,90 @@ SQLITE_PRIVATE int sqlite3VdbeMemFinalize(Mem *pMem, FuncDef *pFunc){ int rc = SQLITE_OK; if( ALWAYS(pFunc && pFunc->xFinalize) ){ sqlite3_context ctx; + Mem t; assert( (pMem->flags & MEM_Null)!=0 || pFunc==pMem->u.pDef ); assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) ); memset(&ctx, 0, sizeof(ctx)); - ctx.s.flags = MEM_Null; - ctx.s.db = pMem->db; + memset(&t, 0, sizeof(t)); + t.flags = MEM_Null; + t.db = pMem->db; + ctx.pOut = &t; ctx.pMem = pMem; ctx.pFunc = pFunc; pFunc->xFinalize(&ctx); /* IMP: R-24505-23230 */ - assert( 0==(pMem->flags&MEM_Dyn) && !pMem->xDel ); - sqlite3DbFree(pMem->db, pMem->zMalloc); - memcpy(pMem, &ctx.s, sizeof(ctx.s)); + assert( (pMem->flags & MEM_Dyn)==0 ); + if( pMem->szMalloc>0 ) sqlite3DbFree(pMem->db, pMem->zMalloc); + memcpy(pMem, &t, sizeof(t)); rc = ctx.isError; } return rc; } /* -** If the memory cell contains a string value that must be freed by -** invoking an external callback, free it now. Calling this function -** does not free any Mem.zMalloc buffer. +** If the memory cell contains a value that must be freed by +** invoking the external callback in Mem.xDel, then this routine +** will free that value. It also sets Mem.flags to MEM_Null. +** +** This is a helper routine for sqlite3VdbeMemSetNull() and +** for sqlite3VdbeMemRelease(). Use those other routines as the +** entry point for releasing Mem resources. */ -SQLITE_PRIVATE void sqlite3VdbeMemReleaseExternal(Mem *p){ +static SQLITE_NOINLINE void vdbeMemClearExternAndSetNull(Mem *p){ assert( p->db==0 || sqlite3_mutex_held(p->db->mutex) ); + assert( VdbeMemDynamic(p) ); if( p->flags&MEM_Agg ){ sqlite3VdbeMemFinalize(p, p->u.pDef); assert( (p->flags & MEM_Agg)==0 ); - sqlite3VdbeMemRelease(p); - }else if( p->flags&MEM_Dyn ){ + testcase( p->flags & MEM_Dyn ); + } + if( p->flags&MEM_Dyn ){ assert( (p->flags&MEM_RowSet)==0 ); assert( p->xDel!=SQLITE_DYNAMIC && p->xDel!=0 ); p->xDel((void *)p->z); - p->xDel = 0; }else if( p->flags&MEM_RowSet ){ sqlite3RowSetClear(p->u.pRowSet); }else if( p->flags&MEM_Frame ){ - sqlite3VdbeMemSetNull(p); + VdbeFrame *pFrame = p->u.pFrame; + pFrame->pParent = pFrame->v->pDelFrame; + pFrame->v->pDelFrame = pFrame; } + p->flags = MEM_Null; } /* -** Release any memory held by the Mem. This may leave the Mem in an -** inconsistent state, for example with (Mem.z==0) and -** (Mem.flags==MEM_Str). +** Release memory held by the Mem p, both external memory cleared +** by p->xDel and memory in p->zMalloc. +** +** This is a helper routine invoked by sqlite3VdbeMemRelease() in +** the unusual case where there really is memory in p that needs +** to be freed. +*/ +static SQLITE_NOINLINE void vdbeMemClear(Mem *p){ + if( VdbeMemDynamic(p) ){ + vdbeMemClearExternAndSetNull(p); + } + if( p->szMalloc ){ + sqlite3DbFree(p->db, p->zMalloc); + p->szMalloc = 0; + } + p->z = 0; +} + +/* +** Release any memory resources held by the Mem. Both the memory that is +** free by Mem.xDel and the Mem.zMalloc allocation are freed. +** +** Use this routine prior to clean up prior to abandoning a Mem, or to +** reset a Mem back to its minimum memory utilization. +** +** Use sqlite3VdbeMemSetNull() to release just the Mem.xDel space +** prior to inserting new content into the Mem. */ SQLITE_PRIVATE void sqlite3VdbeMemRelease(Mem *p){ assert( sqlite3VdbeCheckMemInvariants(p) ); - VdbeMemRelease(p); - if( p->zMalloc ){ - sqlite3DbFree(p->db, p->zMalloc); - p->zMalloc = 0; + if( VdbeMemDynamic(p) || p->szMalloc ){ + vdbeMemClear(p); } - p->z = 0; - assert( p->xDel==0 ); /* Zeroed by VdbeMemRelease() above */ } /* @@ -60803,7 +66048,7 @@ static i64 doubleToInt64(double r){ ** If pMem is an integer, then the value is exact. If pMem is ** a floating-point then the value returned is the integer part. ** If pMem is a string or blob, then we make an attempt to convert -** it into a integer and return that. If pMem represents an +** it into an integer and return that. If pMem represents an ** an SQL-NULL value, return 0. ** ** If pMem represents a string value, its encoding might be changed. @@ -60816,11 +66061,10 @@ SQLITE_PRIVATE i64 sqlite3VdbeIntValue(Mem *pMem){ if( flags & MEM_Int ){ return pMem->u.i; }else if( flags & MEM_Real ){ - return doubleToInt64(pMem->r); + return doubleToInt64(pMem->u.r); }else if( flags & (MEM_Str|MEM_Blob) ){ i64 value = 0; assert( pMem->z || pMem->n==0 ); - testcase( pMem->z==0 ); sqlite3Atoi64(pMem->z, &value, pMem->n, pMem->enc); return value; }else{ @@ -60838,7 +66082,7 @@ SQLITE_PRIVATE double sqlite3VdbeRealValue(Mem *pMem){ assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) ); assert( EIGHT_BYTE_ALIGNMENT(pMem) ); if( pMem->flags & MEM_Real ){ - return pMem->r; + return pMem->u.r; }else if( pMem->flags & MEM_Int ){ return (double)pMem->u.i; }else if( pMem->flags & (MEM_Str|MEM_Blob) ){ @@ -60857,12 +66101,13 @@ SQLITE_PRIVATE double sqlite3VdbeRealValue(Mem *pMem){ ** MEM_Int if we can. */ SQLITE_PRIVATE void sqlite3VdbeIntegerAffinity(Mem *pMem){ + i64 ix; assert( pMem->flags & MEM_Real ); assert( (pMem->flags & MEM_RowSet)==0 ); assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) ); assert( EIGHT_BYTE_ALIGNMENT(pMem) ); - pMem->u.i = doubleToInt64(pMem->r); + ix = doubleToInt64(pMem->u.r); /* Only mark the value as an integer if ** @@ -60874,11 +66119,9 @@ SQLITE_PRIVATE void sqlite3VdbeIntegerAffinity(Mem *pMem){ ** the second condition under the assumption that addition overflow causes ** values to wrap around. */ - if( pMem->r==(double)pMem->u.i - && pMem->u.i>SMALLEST_INT64 - && pMem->u.iflags |= MEM_Int; + if( pMem->u.r==ix && ix>SMALLEST_INT64 && ixu.i = ix; + MemSetTypeFlag(pMem, MEM_Int); } } @@ -60903,7 +66146,7 @@ SQLITE_PRIVATE int sqlite3VdbeMemRealify(Mem *pMem){ assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) ); assert( EIGHT_BYTE_ALIGNMENT(pMem) ); - pMem->r = sqlite3VdbeRealValue(pMem); + pMem->u.r = sqlite3VdbeRealValue(pMem); MemSetTypeFlag(pMem, MEM_Real); return SQLITE_OK; } @@ -60923,7 +66166,7 @@ SQLITE_PRIVATE int sqlite3VdbeMemNumerify(Mem *pMem){ if( 0==sqlite3Atoi64(pMem->z, &pMem->u.i, pMem->n, pMem->enc) ){ MemSetTypeFlag(pMem, MEM_Int); }else{ - pMem->r = sqlite3VdbeRealValue(pMem); + pMem->u.r = sqlite3VdbeRealValue(pMem); MemSetTypeFlag(pMem, MEM_Real); sqlite3VdbeIntegerAffinity(pMem); } @@ -60933,19 +66176,81 @@ SQLITE_PRIVATE int sqlite3VdbeMemNumerify(Mem *pMem){ return SQLITE_OK; } +/* +** Cast the datatype of the value in pMem according to the affinity +** "aff". Casting is different from applying affinity in that a cast +** is forced. In other words, the value is converted into the desired +** affinity even if that results in loss of data. This routine is +** used (for example) to implement the SQL "cast()" operator. +*/ +SQLITE_PRIVATE void sqlite3VdbeMemCast(Mem *pMem, u8 aff, u8 encoding){ + if( pMem->flags & MEM_Null ) return; + switch( aff ){ + case SQLITE_AFF_BLOB: { /* Really a cast to BLOB */ + if( (pMem->flags & MEM_Blob)==0 ){ + sqlite3ValueApplyAffinity(pMem, SQLITE_AFF_TEXT, encoding); + assert( pMem->flags & MEM_Str || pMem->db->mallocFailed ); + MemSetTypeFlag(pMem, MEM_Blob); + }else{ + pMem->flags &= ~(MEM_TypeMask&~MEM_Blob); + } + break; + } + case SQLITE_AFF_NUMERIC: { + sqlite3VdbeMemNumerify(pMem); + break; + } + case SQLITE_AFF_INTEGER: { + sqlite3VdbeMemIntegerify(pMem); + break; + } + case SQLITE_AFF_REAL: { + sqlite3VdbeMemRealify(pMem); + break; + } + default: { + assert( aff==SQLITE_AFF_TEXT ); + assert( MEM_Str==(MEM_Blob>>3) ); + pMem->flags |= (pMem->flags&MEM_Blob)>>3; + sqlite3ValueApplyAffinity(pMem, SQLITE_AFF_TEXT, encoding); + assert( pMem->flags & MEM_Str || pMem->db->mallocFailed ); + pMem->flags &= ~(MEM_Int|MEM_Real|MEM_Blob|MEM_Zero); + break; + } + } +} + +/* +** Initialize bulk memory to be a consistent Mem object. +** +** The minimum amount of initialization feasible is performed. +*/ +SQLITE_PRIVATE void sqlite3VdbeMemInit(Mem *pMem, sqlite3 *db, u16 flags){ + assert( (flags & ~MEM_TypeMask)==0 ); + pMem->flags = flags; + pMem->db = db; + pMem->szMalloc = 0; +} + + /* ** Delete any previous value and set the value stored in *pMem to NULL. +** +** This routine calls the Mem.xDel destructor to dispose of values that +** require the destructor. But it preserves the Mem.zMalloc memory allocation. +** To free all resources, use sqlite3VdbeMemRelease(), which both calls this +** routine to invoke the destructor and deallocates Mem.zMalloc. +** +** Use this routine to reset the Mem prior to insert a new value. +** +** Use sqlite3VdbeMemRelease() to complete erase the Mem prior to abandoning it. */ SQLITE_PRIVATE void sqlite3VdbeMemSetNull(Mem *pMem){ - if( pMem->flags & MEM_Frame ){ - VdbeFrame *pFrame = pMem->u.pFrame; - pFrame->pParent = pFrame->v->pDelFrame; - pFrame->v->pDelFrame = pFrame; + if( VdbeMemDynamic(pMem) ){ + vdbeMemClearExternAndSetNull(pMem); + }else{ + pMem->flags = MEM_Null; } - if( pMem->flags & MEM_RowSet ){ - sqlite3RowSetClear(pMem->u.pRowSet); - } - MemSetTypeFlag(pMem, MEM_Null); } SQLITE_PRIVATE void sqlite3ValueSetNull(sqlite3_value *p){ sqlite3VdbeMemSetNull((Mem*)p); @@ -60962,14 +66267,18 @@ SQLITE_PRIVATE void sqlite3VdbeMemSetZeroBlob(Mem *pMem, int n){ if( n<0 ) n = 0; pMem->u.nZero = n; pMem->enc = SQLITE_UTF8; + pMem->z = 0; +} -#ifdef SQLITE_OMIT_INCRBLOB - sqlite3VdbeMemGrow(pMem, n, 0); - if( pMem->z ){ - pMem->n = n; - memset(pMem->z, 0, n); - } -#endif +/* +** The pMem is known to contain content that needs to be destroyed prior +** to a value change. So invoke the destructor, then set the value to +** a 64-bit integer. +*/ +static SQLITE_NOINLINE void vdbeReleaseAndSetInt64(Mem *pMem, i64 val){ + sqlite3VdbeMemSetNull(pMem); + pMem->u.i = val; + pMem->flags = MEM_Int; } /* @@ -60977,9 +66286,12 @@ SQLITE_PRIVATE void sqlite3VdbeMemSetZeroBlob(Mem *pMem, int n){ ** manifest type INTEGER. */ SQLITE_PRIVATE void sqlite3VdbeMemSetInt64(Mem *pMem, i64 val){ - sqlite3VdbeMemRelease(pMem); - pMem->u.i = val; - pMem->flags = MEM_Int; + if( VdbeMemDynamic(pMem) ){ + vdbeReleaseAndSetInt64(pMem, val); + }else{ + pMem->u.i = val; + pMem->flags = MEM_Int; + } } #ifndef SQLITE_OMIT_FLOATING_POINT @@ -60988,11 +66300,9 @@ SQLITE_PRIVATE void sqlite3VdbeMemSetInt64(Mem *pMem, i64 val){ ** manifest type REAL. */ SQLITE_PRIVATE void sqlite3VdbeMemSetDouble(Mem *pMem, double val){ - if( sqlite3IsNaN(val) ){ - sqlite3VdbeMemSetNull(pMem); - }else{ - sqlite3VdbeMemRelease(pMem); - pMem->r = val; + sqlite3VdbeMemSetNull(pMem); + if( !sqlite3IsNaN(val) ){ + pMem->u.r = val; pMem->flags = MEM_Real; } } @@ -61010,10 +66320,11 @@ SQLITE_PRIVATE void sqlite3VdbeMemSetRowSet(Mem *pMem){ pMem->zMalloc = sqlite3DbMallocRaw(db, 64); if( db->mallocFailed ){ pMem->flags = MEM_Null; + pMem->szMalloc = 0; }else{ assert( pMem->zMalloc ); - pMem->u.pRowSet = sqlite3RowSetInit(db, pMem->zMalloc, - sqlite3DbMallocSize(db, pMem->zMalloc)); + pMem->szMalloc = sqlite3DbMallocSize(db, pMem->zMalloc); + pMem->u.pRowSet = sqlite3RowSetInit(db, pMem->zMalloc, pMem->szMalloc); assert( pMem->u.pRowSet!=0 ); pMem->flags = MEM_RowSet; } @@ -61037,7 +66348,7 @@ SQLITE_PRIVATE int sqlite3VdbeMemTooBig(Mem *p){ #ifdef SQLITE_DEBUG /* -** This routine prepares a memory cell for modication by breaking +** This routine prepares a memory cell for modification by breaking ** its link to a shallow copy and by marking any current shallow ** copies of this cell as invalid. ** @@ -61057,10 +66368,6 @@ SQLITE_PRIVATE void sqlite3VdbeMemAboutToChange(Vdbe *pVdbe, Mem *pMem){ } #endif /* SQLITE_DEBUG */ -/* -** Size of struct Mem not including the Mem.zMalloc member. -*/ -#define MEMCELLSIZE offsetof(Mem,zMalloc) /* ** Make an shallow copy of pFrom into pTo. Prior contents of @@ -61068,11 +66375,16 @@ SQLITE_PRIVATE void sqlite3VdbeMemAboutToChange(Vdbe *pVdbe, Mem *pMem){ ** pFrom->z is used, then pTo->z points to the same thing as pFrom->z ** and flags gets srcType (either MEM_Ephem or MEM_Static). */ +static SQLITE_NOINLINE void vdbeClrCopy(Mem *pTo, const Mem *pFrom, int eType){ + vdbeMemClearExternAndSetNull(pTo); + assert( !VdbeMemDynamic(pTo) ); + sqlite3VdbeMemShallowCopy(pTo, pFrom, eType); +} SQLITE_PRIVATE void sqlite3VdbeMemShallowCopy(Mem *pTo, const Mem *pFrom, int srcType){ assert( (pFrom->flags & MEM_RowSet)==0 ); - VdbeMemRelease(pTo); + assert( pTo->db==pFrom->db ); + if( VdbeMemDynamic(pTo) ){ vdbeClrCopy(pTo,pFrom,srcType); return; } memcpy(pTo, pFrom, MEMCELLSIZE); - pTo->xDel = 0; if( (pFrom->flags&MEM_Static)==0 ){ pTo->flags &= ~(MEM_Dyn|MEM_Static|MEM_Ephem); assert( srcType==MEM_Ephem || srcType==MEM_Static ); @@ -61087,12 +66399,14 @@ SQLITE_PRIVATE void sqlite3VdbeMemShallowCopy(Mem *pTo, const Mem *pFrom, int sr SQLITE_PRIVATE int sqlite3VdbeMemCopy(Mem *pTo, const Mem *pFrom){ int rc = SQLITE_OK; + /* The pFrom==0 case in the following assert() is when an sqlite3_value + ** from sqlite3_value_dup() is used as the argument + ** to sqlite3_result_value(). */ + assert( pTo->db==pFrom->db || pFrom->db==0 ); assert( (pFrom->flags & MEM_RowSet)==0 ); - VdbeMemRelease(pTo); + if( VdbeMemDynamic(pTo) ) vdbeMemClearExternAndSetNull(pTo); memcpy(pTo, pFrom, MEMCELLSIZE); pTo->flags &= ~MEM_Dyn; - pTo->xDel = 0; - if( pTo->flags&(MEM_Str|MEM_Blob) ){ if( 0==(pFrom->flags&MEM_Static) ){ pTo->flags |= MEM_Ephem; @@ -61117,8 +66431,7 @@ SQLITE_PRIVATE void sqlite3VdbeMemMove(Mem *pTo, Mem *pFrom){ sqlite3VdbeMemRelease(pTo); memcpy(pTo, pFrom, sizeof(Mem)); pFrom->flags = MEM_Null; - pFrom->xDel = 0; - pFrom->zMalloc = 0; + pFrom->szMalloc = 0; } /* @@ -61165,7 +66478,8 @@ SQLITE_PRIVATE int sqlite3VdbeMemSetStr( if( nByte<0 ){ assert( enc!=0 ); if( enc==SQLITE_UTF8 ){ - for(nByte=0; nByte<=iLimit && z[nByte]; nByte++){} + nByte = sqlite3Strlen30(z); + if( nByte>iLimit ) nByte = iLimit+1; }else{ for(nByte=0; nByte<=iLimit && (z[nByte] | z[nByte+1]); nByte+=2){} } @@ -61184,14 +66498,17 @@ SQLITE_PRIVATE int sqlite3VdbeMemSetStr( if( nByte>iLimit ){ return SQLITE_TOOBIG; } - if( sqlite3VdbeMemGrow(pMem, nAlloc, 0) ){ + testcase( nAlloc==0 ); + testcase( nAlloc==31 ); + testcase( nAlloc==32 ); + if( sqlite3VdbeMemClearAndResize(pMem, MAX(nAlloc,32)) ){ return SQLITE_NOMEM; } memcpy(pMem->z, z, nAlloc); }else if( xDel==SQLITE_DYNAMIC ){ sqlite3VdbeMemRelease(pMem); pMem->zMalloc = pMem->z = (char *)z; - pMem->xDel = 0; + pMem->szMalloc = sqlite3DbMallocSize(pMem->db, pMem->zMalloc); }else{ sqlite3VdbeMemRelease(pMem); pMem->z = (char *)z; @@ -61223,41 +66540,25 @@ SQLITE_PRIVATE int sqlite3VdbeMemSetStr( ** key is true to get the key or false to get data. The result is written ** into the pMem element. ** -** The pMem structure is assumed to be uninitialized. Any prior content -** is overwritten without being freed. +** The pMem object must have been initialized. This routine will use +** pMem->zMalloc to hold the content from the btree, if possible. New +** pMem->zMalloc space will be allocated if necessary. The calling routine +** is responsible for making sure that the pMem object is eventually +** destroyed. ** ** If this routine fails for any reason (malloc returns NULL or unable ** to read from the disk) then the pMem is left in an inconsistent state. */ -SQLITE_PRIVATE int sqlite3VdbeMemFromBtree( +static SQLITE_NOINLINE int vdbeMemFromBtreeResize( BtCursor *pCur, /* Cursor pointing at record to retrieve. */ u32 offset, /* Offset from the start of data to return bytes from. */ u32 amt, /* Number of bytes to return. */ int key, /* If true, retrieve from the btree key, not data. */ Mem *pMem /* OUT: Return data in this Mem structure. */ ){ - char *zData; /* Data from the btree layer */ - u32 available = 0; /* Number of bytes available on the local btree page */ - int rc = SQLITE_OK; /* Return code */ - - assert( sqlite3BtreeCursorIsValid(pCur) ); - - /* Note: the calls to BtreeKeyFetch() and DataFetch() below assert() - ** that both the BtShared and database handle mutexes are held. */ - assert( (pMem->flags & MEM_RowSet)==0 ); - if( key ){ - zData = (char *)sqlite3BtreeKeyFetch(pCur, &available); - }else{ - zData = (char *)sqlite3BtreeDataFetch(pCur, &available); - } - assert( zData!=0 ); - - if( offset+amt<=available ){ - sqlite3VdbeMemRelease(pMem); - pMem->z = &zData[offset]; - pMem->flags = MEM_Blob|MEM_Ephem; - pMem->n = (int)amt; - }else if( SQLITE_OK==(rc = sqlite3VdbeMemGrow(pMem, amt+2, 0)) ){ + int rc; + pMem->flags = MEM_Null; + if( SQLITE_OK==(rc = sqlite3VdbeMemClearAndResize(pMem, amt+2)) ){ if( key ){ rc = sqlite3BtreeKey(pCur, offset, amt, pMem->z); }else{ @@ -61272,10 +66573,82 @@ SQLITE_PRIVATE int sqlite3VdbeMemFromBtree( sqlite3VdbeMemRelease(pMem); } } + return rc; +} +SQLITE_PRIVATE int sqlite3VdbeMemFromBtree( + BtCursor *pCur, /* Cursor pointing at record to retrieve. */ + u32 offset, /* Offset from the start of data to return bytes from. */ + u32 amt, /* Number of bytes to return. */ + int key, /* If true, retrieve from the btree key, not data. */ + Mem *pMem /* OUT: Return data in this Mem structure. */ +){ + char *zData; /* Data from the btree layer */ + u32 available = 0; /* Number of bytes available on the local btree page */ + int rc = SQLITE_OK; /* Return code */ + + assert( sqlite3BtreeCursorIsValid(pCur) ); + assert( !VdbeMemDynamic(pMem) ); + + /* Note: the calls to BtreeKeyFetch() and DataFetch() below assert() + ** that both the BtShared and database handle mutexes are held. */ + assert( (pMem->flags & MEM_RowSet)==0 ); + if( key ){ + zData = (char *)sqlite3BtreeKeyFetch(pCur, &available); + }else{ + zData = (char *)sqlite3BtreeDataFetch(pCur, &available); + } + assert( zData!=0 ); + + if( offset+amt<=available ){ + pMem->z = &zData[offset]; + pMem->flags = MEM_Blob|MEM_Ephem; + pMem->n = (int)amt; + }else{ + rc = vdbeMemFromBtreeResize(pCur, offset, amt, key, pMem); + } return rc; } +/* +** The pVal argument is known to be a value other than NULL. +** Convert it into a string with encoding enc and return a pointer +** to a zero-terminated version of that string. +*/ +static SQLITE_NOINLINE const void *valueToText(sqlite3_value* pVal, u8 enc){ + assert( pVal!=0 ); + assert( pVal->db==0 || sqlite3_mutex_held(pVal->db->mutex) ); + assert( (enc&3)==(enc&~SQLITE_UTF16_ALIGNED) ); + assert( (pVal->flags & MEM_RowSet)==0 ); + assert( (pVal->flags & (MEM_Null))==0 ); + if( pVal->flags & (MEM_Blob|MEM_Str) ){ + pVal->flags |= MEM_Str; + if( pVal->flags & MEM_Zero ){ + sqlite3VdbeMemExpandBlob(pVal); + } + if( pVal->enc != (enc & ~SQLITE_UTF16_ALIGNED) ){ + sqlite3VdbeChangeEncoding(pVal, enc & ~SQLITE_UTF16_ALIGNED); + } + if( (enc & SQLITE_UTF16_ALIGNED)!=0 && 1==(1&SQLITE_PTR_TO_INT(pVal->z)) ){ + assert( (pVal->flags & (MEM_Ephem|MEM_Static))!=0 ); + if( sqlite3VdbeMemMakeWriteable(pVal)!=SQLITE_OK ){ + return 0; + } + } + sqlite3VdbeMemNulTerminate(pVal); /* IMP: R-31275-44060 */ + }else{ + sqlite3VdbeMemStringify(pVal, enc, 0); + assert( 0==(1&SQLITE_PTR_TO_INT(pVal->z)) ); + } + assert(pVal->enc==(enc & ~SQLITE_UTF16_ALIGNED) || pVal->db==0 + || pVal->db->mallocFailed ); + if( pVal->enc==(enc & ~SQLITE_UTF16_ALIGNED) ){ + return pVal->z; + }else{ + return 0; + } +} + /* This function is only available internally, it is not part of the ** external API. It works in a similar way to sqlite3_value_text(), ** except the data returned is in the encoding specified by the second @@ -61288,38 +66661,16 @@ SQLITE_PRIVATE int sqlite3VdbeMemFromBtree( */ SQLITE_PRIVATE const void *sqlite3ValueText(sqlite3_value* pVal, u8 enc){ if( !pVal ) return 0; - assert( pVal->db==0 || sqlite3_mutex_held(pVal->db->mutex) ); assert( (enc&3)==(enc&~SQLITE_UTF16_ALIGNED) ); assert( (pVal->flags & MEM_RowSet)==0 ); - + if( (pVal->flags&(MEM_Str|MEM_Term))==(MEM_Str|MEM_Term) && pVal->enc==enc ){ + return pVal->z; + } if( pVal->flags&MEM_Null ){ return 0; } - assert( (MEM_Blob>>3) == MEM_Str ); - pVal->flags |= (pVal->flags & MEM_Blob)>>3; - ExpandBlob(pVal); - if( pVal->flags&MEM_Str ){ - sqlite3VdbeChangeEncoding(pVal, enc & ~SQLITE_UTF16_ALIGNED); - if( (enc & SQLITE_UTF16_ALIGNED)!=0 && 1==(1&SQLITE_PTR_TO_INT(pVal->z)) ){ - assert( (pVal->flags & (MEM_Ephem|MEM_Static))!=0 ); - if( sqlite3VdbeMemMakeWriteable(pVal)!=SQLITE_OK ){ - return 0; - } - } - sqlite3VdbeMemNulTerminate(pVal); /* IMP: R-31275-44060 */ - }else{ - assert( (pVal->flags&MEM_Blob)==0 ); - sqlite3VdbeMemStringify(pVal, enc); - assert( 0==(1&SQLITE_PTR_TO_INT(pVal->z)) ); - } - assert(pVal->enc==(enc & ~SQLITE_UTF16_ALIGNED) || pVal->db==0 - || pVal->db->mallocFailed ); - if( pVal->enc==(enc & ~SQLITE_UTF16_ALIGNED) ){ - return pVal->z; - }else{ - return 0; - } + return valueToText(pVal, enc); } /* @@ -61353,7 +66704,7 @@ struct ValueNewStat4Ctx { ** Otherwise, if the second argument is non-zero, then this function is ** being called indirectly by sqlite3Stat4ProbeSetValue(). If it has not ** already been allocated, allocate the UnpackedRecord structure that -** that function will return to its caller here. Then return a pointer +** that function will return to its caller here. Then return a pointer to ** an sqlite3_value within the UnpackedRecord.a[] array. */ static sqlite3_value *valueNew(sqlite3 *db, struct ValueNewStat4Ctx *p){ @@ -61397,6 +66748,113 @@ static sqlite3_value *valueNew(sqlite3 *db, struct ValueNewStat4Ctx *p){ return sqlite3ValueNew(db); } +/* +** The expression object indicated by the second argument is guaranteed +** to be a scalar SQL function. If +** +** * all function arguments are SQL literals, +** * one of the SQLITE_FUNC_CONSTANT or _SLOCHNG function flags is set, and +** * the SQLITE_FUNC_NEEDCOLL function flag is not set, +** +** then this routine attempts to invoke the SQL function. Assuming no +** error occurs, output parameter (*ppVal) is set to point to a value +** object containing the result before returning SQLITE_OK. +** +** Affinity aff is applied to the result of the function before returning. +** If the result is a text value, the sqlite3_value object uses encoding +** enc. +** +** If the conditions above are not met, this function returns SQLITE_OK +** and sets (*ppVal) to NULL. Or, if an error occurs, (*ppVal) is set to +** NULL and an SQLite error code returned. +*/ +#ifdef SQLITE_ENABLE_STAT3_OR_STAT4 +static int valueFromFunction( + sqlite3 *db, /* The database connection */ + Expr *p, /* The expression to evaluate */ + u8 enc, /* Encoding to use */ + u8 aff, /* Affinity to use */ + sqlite3_value **ppVal, /* Write the new value here */ + struct ValueNewStat4Ctx *pCtx /* Second argument for valueNew() */ +){ + sqlite3_context ctx; /* Context object for function invocation */ + sqlite3_value **apVal = 0; /* Function arguments */ + int nVal = 0; /* Size of apVal[] array */ + FuncDef *pFunc = 0; /* Function definition */ + sqlite3_value *pVal = 0; /* New value */ + int rc = SQLITE_OK; /* Return code */ + int nName; /* Size of function name in bytes */ + ExprList *pList = 0; /* Function arguments */ + int i; /* Iterator variable */ + + assert( pCtx!=0 ); + assert( (p->flags & EP_TokenOnly)==0 ); + pList = p->x.pList; + if( pList ) nVal = pList->nExpr; + nName = sqlite3Strlen30(p->u.zToken); + pFunc = sqlite3FindFunction(db, p->u.zToken, nName, nVal, enc, 0); + assert( pFunc ); + if( (pFunc->funcFlags & (SQLITE_FUNC_CONSTANT|SQLITE_FUNC_SLOCHNG))==0 + || (pFunc->funcFlags & SQLITE_FUNC_NEEDCOLL) + ){ + return SQLITE_OK; + } + + if( pList ){ + apVal = (sqlite3_value**)sqlite3DbMallocZero(db, sizeof(apVal[0]) * nVal); + if( apVal==0 ){ + rc = SQLITE_NOMEM; + goto value_from_function_out; + } + for(i=0; ia[i].pExpr, enc, aff, &apVal[i]); + if( apVal[i]==0 || rc!=SQLITE_OK ) goto value_from_function_out; + } + } + + pVal = valueNew(db, pCtx); + if( pVal==0 ){ + rc = SQLITE_NOMEM; + goto value_from_function_out; + } + + assert( pCtx->pParse->rc==SQLITE_OK ); + memset(&ctx, 0, sizeof(ctx)); + ctx.pOut = pVal; + ctx.pFunc = pFunc; + pFunc->xFunc(&ctx, nVal, apVal); + if( ctx.isError ){ + rc = ctx.isError; + sqlite3ErrorMsg(pCtx->pParse, "%s", sqlite3_value_text(pVal)); + }else{ + sqlite3ValueApplyAffinity(pVal, aff, SQLITE_UTF8); + assert( rc==SQLITE_OK ); + rc = sqlite3VdbeChangeEncoding(pVal, enc); + if( rc==SQLITE_OK && sqlite3VdbeMemTooBig(pVal) ){ + rc = SQLITE_TOOBIG; + pCtx->pParse->nErr++; + } + } + pCtx->pParse->rc = rc; + + value_from_function_out: + if( rc!=SQLITE_OK ){ + pVal = 0; + } + if( apVal ){ + for(i=0; iop; + while( (op = pExpr->op)==TK_UPLUS ) pExpr = pExpr->pLeft; if( NEVER(op==TK_REGISTER) ) op = pExpr->op2; + /* Compressed expressions only appear when parsing the DEFAULT clause + ** on a table column definition, and hence only when pCtx==0. This + ** check ensures that an EP_TokenOnly expression is never passed down + ** into valueFromFunction(). */ + assert( (pExpr->flags & EP_TokenOnly)==0 || pCtx==0 ); + + if( op==TK_CAST ){ + u8 aff = sqlite3AffinityType(pExpr->u.zToken,0); + rc = valueFromExpr(db, pExpr->pLeft, enc, aff, ppVal, pCtx); + testcase( rc!=SQLITE_OK ); + if( *ppVal ){ + sqlite3VdbeMemCast(*ppVal, aff, SQLITE_UTF8); + sqlite3ValueApplyAffinity(*ppVal, affinity, SQLITE_UTF8); + } + return rc; + } + /* Handle negative integers in a single step. This is needed in the ** case when the value is -9223372036854775808. */ @@ -61450,7 +66925,7 @@ static int valueFromExpr( if( zVal==0 ) goto no_mem; sqlite3ValueSetStr(pVal, -1, zVal, SQLITE_UTF8, SQLITE_DYNAMIC); } - if( (op==TK_INTEGER || op==TK_FLOAT ) && affinity==SQLITE_AFF_NONE ){ + if( (op==TK_INTEGER || op==TK_FLOAT ) && affinity==SQLITE_AFF_BLOB ){ sqlite3ValueApplyAffinity(pVal, SQLITE_AFF_NUMERIC, SQLITE_UTF8); }else{ sqlite3ValueApplyAffinity(pVal, affinity, SQLITE_UTF8); @@ -61465,14 +66940,14 @@ static int valueFromExpr( && pVal!=0 ){ sqlite3VdbeMemNumerify(pVal); - if( pVal->u.i==SMALLEST_INT64 ){ - pVal->flags &= ~MEM_Int; - pVal->flags |= MEM_Real; - pVal->r = (double)SMALLEST_INT64; + if( pVal->flags & MEM_Real ){ + pVal->u.r = -pVal->u.r; + }else if( pVal->u.i==SMALLEST_INT64 ){ + pVal->u.r = -(double)SMALLEST_INT64; + MemSetTypeFlag(pVal, MEM_Real); }else{ pVal->u.i = -pVal->u.i; } - pVal->r = -pVal->r; sqlite3ValueApplyAffinity(pVal, affinity, enc); } }else if( op==TK_NULL ){ @@ -61494,6 +66969,12 @@ static int valueFromExpr( } #endif +#ifdef SQLITE_ENABLE_STAT3_OR_STAT4 + else if( op==TK_FUNCTION && pCtx!=0 ){ + rc = valueFromFunction(db, pExpr, enc, affinity, &pVal, pCtx); + } +#endif + *ppVal = pVal; return rc; @@ -61544,17 +67025,16 @@ static void recordFunc( sqlite3_value **argv ){ const int file_format = 1; - int iSerial; /* Serial type */ + u32 iSerial; /* Serial type */ int nSerial; /* Bytes of space for iSerial as varint */ - int nVal; /* Bytes of space required for argv[0] */ + u32 nVal; /* Bytes of space required for argv[0] */ int nRet; sqlite3 *db; u8 *aRet; UNUSED_PARAMETER( argc ); - iSerial = sqlite3VdbeSerialType(argv[0], file_format); + iSerial = sqlite3VdbeSerialType(argv[0], file_format, &nVal); nSerial = sqlite3VarintLen(iSerial); - nVal = sqlite3VdbeSerialTypeLen(iSerial); db = sqlite3_context_db_handle(context); nRet = 1 + nSerial + nVal; @@ -61563,7 +67043,7 @@ static void recordFunc( sqlite3_result_error_nomem(context); }else{ aRet[0] = nSerial+1; - sqlite3PutVarint(&aRet[1], iSerial); + putVarint32(&aRet[1], iSerial); sqlite3VdbeSerialPut(&aRet[1+nSerial], argv[0], iSerial); sqlite3_result_blob(context, aRet, nRet, SQLITE_TRANSIENT); sqlite3DbFree(db, aRet); @@ -61585,6 +67065,68 @@ SQLITE_PRIVATE void sqlite3AnalyzeFunctions(void){ } } +/* +** Attempt to extract a value from pExpr and use it to construct *ppVal. +** +** If pAlloc is not NULL, then an UnpackedRecord object is created for +** pAlloc if one does not exist and the new value is added to the +** UnpackedRecord object. +** +** A value is extracted in the following cases: +** +** * (pExpr==0). In this case the value is assumed to be an SQL NULL, +** +** * The expression is a bound variable, and this is a reprepare, or +** +** * The expression is a literal value. +** +** On success, *ppVal is made to point to the extracted value. The caller +** is responsible for ensuring that the value is eventually freed. +*/ +static int stat4ValueFromExpr( + Parse *pParse, /* Parse context */ + Expr *pExpr, /* The expression to extract a value from */ + u8 affinity, /* Affinity to use */ + struct ValueNewStat4Ctx *pAlloc,/* How to allocate space. Or NULL */ + sqlite3_value **ppVal /* OUT: New value object (or NULL) */ +){ + int rc = SQLITE_OK; + sqlite3_value *pVal = 0; + sqlite3 *db = pParse->db; + + /* Skip over any TK_COLLATE nodes */ + pExpr = sqlite3ExprSkipCollate(pExpr); + + if( !pExpr ){ + pVal = valueNew(db, pAlloc); + if( pVal ){ + sqlite3VdbeMemSetNull((Mem*)pVal); + } + }else if( pExpr->op==TK_VARIABLE + || NEVER(pExpr->op==TK_REGISTER && pExpr->op2==TK_VARIABLE) + ){ + Vdbe *v; + int iBindVar = pExpr->iColumn; + sqlite3VdbeSetVarmask(pParse->pVdbe, iBindVar); + if( (v = pParse->pReprepare)!=0 ){ + pVal = valueNew(db, pAlloc); + if( pVal ){ + rc = sqlite3VdbeMemCopy((Mem*)pVal, &v->aVar[iBindVar-1]); + if( rc==SQLITE_OK ){ + sqlite3ValueApplyAffinity(pVal, affinity, ENC(db)); + } + pVal->db = pParse->db; + } + } + }else{ + rc = valueFromExpr(db, pExpr, ENC(db), affinity, &pVal, pAlloc); + } + + assert( pVal==0 || pVal->db==db ); + *ppVal = pVal; + return rc; +} + /* ** This function is used to allocate and populate UnpackedRecord ** structures intended to be compared against sample index keys stored @@ -61624,50 +67166,88 @@ SQLITE_PRIVATE int sqlite3Stat4ProbeSetValue( int iVal, /* Array element to populate */ int *pbOk /* OUT: True if value was extracted */ ){ - int rc = SQLITE_OK; + int rc; sqlite3_value *pVal = 0; - sqlite3 *db = pParse->db; - - struct ValueNewStat4Ctx alloc; + alloc.pParse = pParse; alloc.pIdx = pIdx; alloc.ppRec = ppRec; alloc.iVal = iVal; - /* Skip over any TK_COLLATE nodes */ - pExpr = sqlite3ExprSkipCollate(pExpr); - - if( !pExpr ){ - pVal = valueNew(db, &alloc); - if( pVal ){ - sqlite3VdbeMemSetNull((Mem*)pVal); - } - }else if( pExpr->op==TK_VARIABLE - || NEVER(pExpr->op==TK_REGISTER && pExpr->op2==TK_VARIABLE) - ){ - Vdbe *v; - int iBindVar = pExpr->iColumn; - sqlite3VdbeSetVarmask(pParse->pVdbe, iBindVar); - if( (v = pParse->pReprepare)!=0 ){ - pVal = valueNew(db, &alloc); - if( pVal ){ - rc = sqlite3VdbeMemCopy((Mem*)pVal, &v->aVar[iBindVar-1]); - if( rc==SQLITE_OK ){ - sqlite3ValueApplyAffinity(pVal, affinity, ENC(db)); - } - pVal->db = pParse->db; - } - } - }else{ - rc = valueFromExpr(db, pExpr, ENC(db), affinity, &pVal, &alloc); - } + rc = stat4ValueFromExpr(pParse, pExpr, affinity, &alloc, &pVal); + assert( pVal==0 || pVal->db==pParse->db ); *pbOk = (pVal!=0); - - assert( pVal==0 || pVal->db==db ); return rc; } +/* +** Attempt to extract a value from expression pExpr using the methods +** as described for sqlite3Stat4ProbeSetValue() above. +** +** If successful, set *ppVal to point to a new value object and return +** SQLITE_OK. If no value can be extracted, but no other error occurs +** (e.g. OOM), return SQLITE_OK and set *ppVal to NULL. Or, if an error +** does occur, return an SQLite error code. The final value of *ppVal +** is undefined in this case. +*/ +SQLITE_PRIVATE int sqlite3Stat4ValueFromExpr( + Parse *pParse, /* Parse context */ + Expr *pExpr, /* The expression to extract a value from */ + u8 affinity, /* Affinity to use */ + sqlite3_value **ppVal /* OUT: New value object (or NULL) */ +){ + return stat4ValueFromExpr(pParse, pExpr, affinity, 0, ppVal); +} + +/* +** Extract the iCol-th column from the nRec-byte record in pRec. Write +** the column value into *ppVal. If *ppVal is initially NULL then a new +** sqlite3_value object is allocated. +** +** If *ppVal is initially NULL then the caller is responsible for +** ensuring that the value written into *ppVal is eventually freed. +*/ +SQLITE_PRIVATE int sqlite3Stat4Column( + sqlite3 *db, /* Database handle */ + const void *pRec, /* Pointer to buffer containing record */ + int nRec, /* Size of buffer pRec in bytes */ + int iCol, /* Column to extract */ + sqlite3_value **ppVal /* OUT: Extracted value */ +){ + u32 t; /* a column type code */ + int nHdr; /* Size of the header in the record */ + int iHdr; /* Next unread header byte */ + int iField; /* Next unread data byte */ + int szField; /* Size of the current data field */ + int i; /* Column index */ + u8 *a = (u8*)pRec; /* Typecast byte array */ + Mem *pMem = *ppVal; /* Write result into this Mem object */ + + assert( iCol>0 ); + iHdr = getVarint32(a, nHdr); + if( nHdr>nRec || iHdr>=nHdr ) return SQLITE_CORRUPT_BKPT; + iField = nHdr; + for(i=0; i<=iCol; i++){ + iHdr += getVarint32(&a[iHdr], t); + testcase( iHdr==nHdr ); + testcase( iHdr==nHdr+1 ); + if( iHdr>nHdr ) return SQLITE_CORRUPT_BKPT; + szField = sqlite3VdbeSerialTypeLen(t); + iField += szField; + } + testcase( iField==nRec ); + testcase( iField==nRec+1 ); + if( iField>nRec ) return SQLITE_CORRUPT_BKPT; + if( pMem==0 ){ + pMem = *ppVal = sqlite3ValueNew(db); + if( pMem==0 ) return SQLITE_NOMEM; + } + sqlite3VdbeSerialGet(&a[iField-szField], t, pMem); + pMem->enc = ENC(db); + return SQLITE_OK; +} + /* ** Unless it is NULL, the argument must be an UnpackedRecord object returned ** by an earlier call to sqlite3Stat4ProbeSetValue(). This call deletes @@ -61680,7 +67260,7 @@ SQLITE_PRIVATE void sqlite3Stat4ProbeFree(UnpackedRecord *pRec){ Mem *aMem = pRec->aMem; sqlite3 *db = aMem[0].db; for(i=0; ipKeyInfo); sqlite3DbFree(db, pRec); @@ -61711,19 +67291,28 @@ SQLITE_PRIVATE void sqlite3ValueFree(sqlite3_value *v){ } /* -** Return the number of bytes in the sqlite3_value object assuming -** that it uses the encoding "enc" +** The sqlite3ValueBytes() routine returns the number of bytes in the +** sqlite3_value object assuming that it uses the encoding "enc". +** The valueBytes() routine is a helper function. */ +static SQLITE_NOINLINE int valueBytes(sqlite3_value *pVal, u8 enc){ + return valueToText(pVal, enc)!=0 ? pVal->n : 0; +} SQLITE_PRIVATE int sqlite3ValueBytes(sqlite3_value *pVal, u8 enc){ Mem *p = (Mem*)pVal; - if( (p->flags & MEM_Blob)!=0 || sqlite3ValueText(pVal, enc) ){ + assert( (p->flags & MEM_Null)==0 || (p->flags & (MEM_Str|MEM_Blob))==0 ); + if( (p->flags & MEM_Str)!=0 && pVal->enc==enc ){ + return p->n; + } + if( (p->flags & MEM_Blob)!=0 ){ if( p->flags & MEM_Zero ){ return p->n + p->u.nZero; }else{ return p->n; } } - return 0; + if( p->flags & MEM_Null ) return 0; + return valueBytes(pVal, enc); } /************** End of vdbemem.c *********************************************/ @@ -61740,10 +67329,10 @@ SQLITE_PRIVATE int sqlite3ValueBytes(sqlite3_value *pVal, u8 enc){ ** ************************************************************************* ** This file contains code used for creating, destroying, and populating -** a VDBE (or an "sqlite3_stmt" as it is known to the outside world.) Prior -** to version 2.8.7, all this code was combined into the vdbe.c source file. -** But that file was getting too big so this subroutines were split out. +** a VDBE (or an "sqlite3_stmt" as it is known to the outside world.) */ +/* #include "sqliteInt.h" */ +/* #include "vdbeInt.h" */ /* ** Create a new virtual database engine. @@ -61765,9 +67354,21 @@ SQLITE_PRIVATE Vdbe *sqlite3VdbeCreate(Parse *pParse){ assert( pParse->aLabel==0 ); assert( pParse->nLabel==0 ); assert( pParse->nOpAlloc==0 ); + assert( pParse->szOpAlloc==0 ); return p; } +/* +** Change the error string stored in Vdbe.zErrMsg +*/ +SQLITE_PRIVATE void sqlite3VdbeError(Vdbe *p, const char *zFormat, ...){ + va_list ap; + sqlite3DbFree(p->db, p->zErrMsg); + va_start(ap, zFormat); + p->zErrMsg = sqlite3VMPrintf(p->db, zFormat, ap); + va_end(ap); +} + /* ** Remember the SQL string for a prepared statement. */ @@ -61785,9 +67386,9 @@ SQLITE_PRIVATE void sqlite3VdbeSetSql(Vdbe *p, const char *z, int n, int isPrepa /* ** Return the SQL associated with a prepared statement */ -SQLITE_API const char *sqlite3_sql(sqlite3_stmt *pStmt){ +SQLITE_API const char *SQLITE_STDCALL sqlite3_sql(sqlite3_stmt *pStmt){ Vdbe *p = (Vdbe *)pStmt; - return (p && p->isPrepareV2) ? p->zSql : 0; + return p ? p->zSql : 0; } /* @@ -61812,21 +67413,39 @@ SQLITE_PRIVATE void sqlite3VdbeSwap(Vdbe *pA, Vdbe *pB){ } /* -** Resize the Vdbe.aOp array so that it is at least one op larger than -** it was. +** Resize the Vdbe.aOp array so that it is at least nOp elements larger +** than its current size. nOp is guaranteed to be less than or equal +** to 1024/sizeof(Op). ** ** If an out-of-memory error occurs while resizing the array, return -** SQLITE_NOMEM. In this case Vdbe.aOp and Vdbe.nOpAlloc remain +** SQLITE_NOMEM. In this case Vdbe.aOp and Parse.nOpAlloc remain ** unchanged (this is so that any opcodes already allocated can be ** correctly deallocated along with the rest of the Vdbe). */ -static int growOpArray(Vdbe *v){ +static int growOpArray(Vdbe *v, int nOp){ VdbeOp *pNew; Parse *p = v->pParse; + + /* The SQLITE_TEST_REALLOC_STRESS compile-time option is designed to force + ** more frequent reallocs and hence provide more opportunities for + ** simulated OOM faults. SQLITE_TEST_REALLOC_STRESS is generally used + ** during testing only. With SQLITE_TEST_REALLOC_STRESS grow the op array + ** by the minimum* amount required until the size reaches 512. Normal + ** operation (without SQLITE_TEST_REALLOC_STRESS) is to double the current + ** size of the op array or add 1KB of space, whichever is smaller. */ +#ifdef SQLITE_TEST_REALLOC_STRESS + int nNew = (p->nOpAlloc>=512 ? p->nOpAlloc*2 : p->nOpAlloc+nOp); +#else int nNew = (p->nOpAlloc ? p->nOpAlloc*2 : (int)(1024/sizeof(Op))); + UNUSED_PARAMETER(nOp); +#endif + + assert( nOp<=(1024/sizeof(Op)) ); + assert( nNew>=(p->nOpAlloc+nOp) ); pNew = sqlite3DbRealloc(p->db, v->aOp, nNew*sizeof(Op)); if( pNew ){ - p->nOpAlloc = sqlite3DbMallocSize(p->db, pNew)/sizeof(Op); + p->szOpAlloc = sqlite3DbMallocSize(p->db, pNew); + p->nOpAlloc = p->szOpAlloc/sizeof(Op); v->aOp = pNew; } return (pNew ? SQLITE_OK : SQLITE_NOMEM); @@ -61859,6 +67478,12 @@ static void test_addop_breakpoint(void){ ** the sqlite3VdbeChangeP4() function to change the value of the P4 ** operand. */ +static SQLITE_NOINLINE int growOp3(Vdbe *p, int op, int p1, int p2, int p3){ + assert( p->pParse->nOpAlloc<=p->nOp ); + if( growOpArray(p, 1) ) return 1; + assert( p->pParse->nOpAlloc>p->nOp ); + return sqlite3VdbeAddOp3(p, op, p1, p2, p3); +} SQLITE_PRIVATE int sqlite3VdbeAddOp3(Vdbe *p, int op, int p1, int p2, int p3){ int i; VdbeOp *pOp; @@ -61867,9 +67492,7 @@ SQLITE_PRIVATE int sqlite3VdbeAddOp3(Vdbe *p, int op, int p1, int p2, int p3){ assert( p->magic==VDBE_MAGIC_INIT ); assert( op>0 && op<0xff ); if( p->pParse->nOpAlloc<=i ){ - if( growOpArray(p) ){ - return 1; - } + return growOp3(p, op, p1, p2, p3); } p->nOp++; pOp = &p->aOp[i]; @@ -61917,6 +67540,44 @@ SQLITE_PRIVATE int sqlite3VdbeAddOp2(Vdbe *p, int op, int p1, int p2){ return sqlite3VdbeAddOp3(p, op, p1, p2, 0); } +/* Generate code for an unconditional jump to instruction iDest +*/ +SQLITE_PRIVATE int sqlite3VdbeGoto(Vdbe *p, int iDest){ + return sqlite3VdbeAddOp3(p, OP_Goto, 0, iDest, 0); +} + +/* Generate code to cause the string zStr to be loaded into +** register iDest +*/ +SQLITE_PRIVATE int sqlite3VdbeLoadString(Vdbe *p, int iDest, const char *zStr){ + return sqlite3VdbeAddOp4(p, OP_String8, 0, iDest, 0, zStr, 0); +} + +/* +** Generate code that initializes multiple registers to string or integer +** constants. The registers begin with iDest and increase consecutively. +** One register is initialized for each characgter in zTypes[]. For each +** "s" character in zTypes[], the register is a string if the argument is +** not NULL, or OP_Null if the value is a null pointer. For each "i" character +** in zTypes[], the register is initialized to an integer. +*/ +SQLITE_PRIVATE void sqlite3VdbeMultiLoad(Vdbe *p, int iDest, const char *zTypes, ...){ + va_list ap; + int i; + char c; + va_start(ap, zTypes); + for(i=0; (c = zTypes[i])!=0; i++){ + if( c=='s' ){ + const char *z = va_arg(ap, const char*); + int addr = sqlite3VdbeAddOp2(p, z==0 ? OP_Null : OP_String8, 0, iDest++); + if( z ) sqlite3VdbeChangeP4(p, addr, z, 0); + }else{ + assert( c=='i' ); + sqlite3VdbeAddOp2(p, OP_Integer, va_arg(ap, int), iDest++); + } + } + va_end(ap); +} /* ** Add an opcode that includes the p4 value as a pointer. @@ -61935,6 +67596,24 @@ SQLITE_PRIVATE int sqlite3VdbeAddOp4( return addr; } +/* +** Add an opcode that includes the p4 value with a P4_INT64 or +** P4_REAL type. +*/ +SQLITE_PRIVATE int sqlite3VdbeAddOp4Dup8( + Vdbe *p, /* Add the opcode to this VM */ + int op, /* The new opcode */ + int p1, /* The P1 operand */ + int p2, /* The P2 operand */ + int p3, /* The P3 operand */ + const u8 *zP4, /* The P4 operand */ + int p4type /* P4 operand type */ +){ + char *p4copy = sqlite3DbMallocRaw(sqlite3VdbeDb(p), 8); + if( p4copy ) memcpy(p4copy, zP4, 8); + return sqlite3VdbeAddOp4(p, op, p1, p2, p3, p4copy, p4type); +} + /* ** Add an OP_ParseSchema opcode. This routine is broken out from ** sqlite3VdbeAddOp4() since it needs to also needs to mark all btrees @@ -61991,7 +67670,7 @@ SQLITE_PRIVATE int sqlite3VdbeMakeLabel(Vdbe *v){ if( p->aLabel ){ p->aLabel[i] = -1; } - return -1-i; + return ADDR(i); } /* @@ -62001,10 +67680,11 @@ SQLITE_PRIVATE int sqlite3VdbeMakeLabel(Vdbe *v){ */ SQLITE_PRIVATE void sqlite3VdbeResolveLabel(Vdbe *v, int x){ Parse *p = v->pParse; - int j = -1-x; + int j = ADDR(x); assert( v->magic==VDBE_MAGIC_INIT ); assert( jnLabel ); - if( ALWAYS(j>=0) && p->aLabel ){ + assert( j>=0 ); + if( p->aLabel ){ p->aLabel[j] = v->nOp; } p->iFixedOp = v->nOp - 1; @@ -62099,6 +67779,7 @@ static Op *opIterNext(VdbeOpIter *p){ ** * OP_VUpdate ** * OP_VRename ** * OP_FkCounter with P2==0 (immediate foreign key constraint) +** * OP_CreateTable and OP_InitCoroutine (for CREATE TABLE AS SELECT ...) ** ** Then check that the value of Parse.mayAbort is true if an ** ABORT may be thrown, or false otherwise. Return true if it does @@ -62109,6 +67790,9 @@ static Op *opIterNext(VdbeOpIter *p){ */ SQLITE_PRIVATE int sqlite3VdbeAssertMayAbort(Vdbe *v, int mayAbort){ int hasAbort = 0; + int hasFkCounter = 0; + int hasCreateTable = 0; + int hasInitCoroutine = 0; Op *pOp; VdbeOpIter sIter; memset(&sIter, 0, sizeof(sIter)); @@ -62117,15 +67801,19 @@ SQLITE_PRIVATE int sqlite3VdbeAssertMayAbort(Vdbe *v, int mayAbort){ while( (pOp = opIterNext(&sIter))!=0 ){ int opcode = pOp->opcode; if( opcode==OP_Destroy || opcode==OP_VUpdate || opcode==OP_VRename -#ifndef SQLITE_OMIT_FOREIGN_KEY - || (opcode==OP_FkCounter && pOp->p1==0 && pOp->p2==1) -#endif || ((opcode==OP_Halt || opcode==OP_HaltIfNull) && ((pOp->p1&0xff)==SQLITE_CONSTRAINT && pOp->p2==OE_Abort)) ){ hasAbort = 1; break; } + if( opcode==OP_CreateTable ) hasCreateTable = 1; + if( opcode==OP_InitCoroutine ) hasInitCoroutine = 1; +#ifndef SQLITE_OMIT_FOREIGN_KEY + if( opcode==OP_FkCounter && pOp->p1==0 && pOp->p2==1 ){ + hasFkCounter = 1; + } +#endif } sqlite3DbFree(v->db, sIter.apSub); @@ -62134,22 +67822,27 @@ SQLITE_PRIVATE int sqlite3VdbeAssertMayAbort(Vdbe *v, int mayAbort){ ** through all opcodes and hasAbort may be set incorrectly. Return ** true for this case to prevent the assert() in the callers frame ** from failing. */ - return ( v->db->mallocFailed || hasAbort==mayAbort ); + return ( v->db->mallocFailed || hasAbort==mayAbort || hasFkCounter + || (hasCreateTable && hasInitCoroutine) ); } #endif /* SQLITE_DEBUG - the sqlite3AssertMayAbort() function */ /* -** Loop through the program looking for P2 values that are negative -** on jump instructions. Each such value is a label. Resolve the -** label by setting the P2 value to its correct non-zero value. +** This routine is called after all opcodes have been inserted. It loops +** through all the opcodes and fixes up some details. ** -** This routine is called once after all opcodes have been inserted. +** (1) For each jump instruction with a negative P2 value (a label) +** resolve the P2 value to an actual address. ** -** Variable *pMaxFuncArgs is set to the maximum value of any P2 argument -** to an OP_Function, OP_AggStep or OP_VFilter opcode. This is used by -** sqlite3VdbeMakeReady() to size the Vdbe.apArg[] array. +** (2) Compute the maximum number of arguments used by any SQL function +** and store that value in *pMaxFuncArgs. ** -** The Op.opflags field is set on all opcodes. +** (3) Update the Vdbe.readOnly and Vdbe.bIsReader flags to accurately +** indicate what the prepared statement actually does. +** +** (4) Initialize the p4.xAdvance pointer on opcodes that use it. +** +** (5) Reclaim the memory allocated for storing labels. */ static void resolveP2Values(Vdbe *p, int *pMaxFuncArgs){ int i; @@ -62165,11 +67858,6 @@ static void resolveP2Values(Vdbe *p, int *pMaxFuncArgs){ /* NOTE: Be sure to update mkopcodeh.awk when adding or removing ** cases from this switch! */ switch( opcode ){ - case OP_Function: - case OP_AggStep: { - if( pOp->p5>nMaxArgs ) nMaxArgs = pOp->p5; - break; - } case OP_Transaction: { if( pOp->p2!=0 ) p->readOnly = 0; /* fall thru */ @@ -62219,15 +67907,15 @@ static void resolveP2Values(Vdbe *p, int *pMaxFuncArgs){ pOp->opflags = sqlite3OpcodeProperty[opcode]; if( (pOp->opflags & OPFLG_JUMP)!=0 && pOp->p2<0 ){ - assert( -1-pOp->p2nLabel ); - pOp->p2 = aLabel[-1-pOp->p2]; + assert( ADDR(pOp->p2)nLabel ); + pOp->p2 = aLabel[ADDR(pOp->p2)]; } } sqlite3DbFree(p->db, pParse->aLabel); pParse->aLabel = 0; pParse->nLabel = 0; *pMaxFuncArgs = nMaxArgs; - assert( p->bIsReader!=0 || p->btreeMask==0 ); + assert( p->bIsReader!=0 || DbMaskAllZero(p->btreeMask) ); } /* @@ -62254,7 +67942,7 @@ SQLITE_PRIVATE VdbeOp *sqlite3VdbeTakeOpArray(Vdbe *p, int *pnOp, int *pnMaxArg) assert( aOp && !p->db->mallocFailed ); /* Check that sqlite3VdbeUsesBtree() was not called on this VM */ - assert( p->btreeMask==0 ); + assert( DbMaskAllZero(p->btreeMask) ); resolveP2Values(p, pnMaxArg); *pnOp = p->nOp; @@ -62267,93 +67955,88 @@ SQLITE_PRIVATE VdbeOp *sqlite3VdbeTakeOpArray(Vdbe *p, int *pnOp, int *pnMaxArg) ** address of the first operation added. */ SQLITE_PRIVATE int sqlite3VdbeAddOpList(Vdbe *p, int nOp, VdbeOpList const *aOp, int iLineno){ - int addr; + int addr, i; + VdbeOp *pOut; + assert( nOp>0 ); assert( p->magic==VDBE_MAGIC_INIT ); - if( p->nOp + nOp > p->pParse->nOpAlloc && growOpArray(p) ){ + if( p->nOp + nOp > p->pParse->nOpAlloc && growOpArray(p, nOp) ){ return 0; } addr = p->nOp; - if( ALWAYS(nOp>0) ){ - int i; - VdbeOpList const *pIn = aOp; - for(i=0; ip2; - VdbeOp *pOut = &p->aOp[i+addr]; - pOut->opcode = pIn->opcode; - pOut->p1 = pIn->p1; - if( p2<0 ){ - assert( sqlite3OpcodeProperty[pOut->opcode] & OPFLG_JUMP ); - pOut->p2 = addr + ADDR(p2); - }else{ - pOut->p2 = p2; - } - pOut->p3 = pIn->p3; - pOut->p4type = P4_NOTUSED; - pOut->p4.p = 0; - pOut->p5 = 0; + pOut = &p->aOp[addr]; + for(i=0; iopcode = aOp->opcode; + pOut->p1 = aOp->p1; + pOut->p2 = aOp->p2; + assert( aOp->p2>=0 ); + pOut->p3 = aOp->p3; + pOut->p4type = P4_NOTUSED; + pOut->p4.p = 0; + pOut->p5 = 0; #ifdef SQLITE_ENABLE_EXPLAIN_COMMENTS - pOut->zComment = 0; + pOut->zComment = 0; #endif #ifdef SQLITE_VDBE_COVERAGE - pOut->iSrcLine = iLineno+i; + pOut->iSrcLine = iLineno+i; #else - (void)iLineno; + (void)iLineno; #endif #ifdef SQLITE_DEBUG - if( p->db->flags & SQLITE_VdbeAddopTrace ){ - sqlite3VdbePrintOp(0, i+addr, &p->aOp[i+addr]); - } -#endif + if( p->db->flags & SQLITE_VdbeAddopTrace ){ + sqlite3VdbePrintOp(0, i+addr, &p->aOp[i+addr]); } - p->nOp += nOp; +#endif } + p->nOp += nOp; return addr; } +#if defined(SQLITE_ENABLE_STMT_SCANSTATUS) /* -** Change the value of the P1 operand for a specific instruction. -** This routine is useful when a large program is loaded from a -** static array using sqlite3VdbeAddOpList but we want to make a -** few minor changes to the program. +** Add an entry to the array of counters managed by sqlite3_stmt_scanstatus(). */ +SQLITE_PRIVATE void sqlite3VdbeScanStatus( + Vdbe *p, /* VM to add scanstatus() to */ + int addrExplain, /* Address of OP_Explain (or 0) */ + int addrLoop, /* Address of loop counter */ + int addrVisit, /* Address of rows visited counter */ + LogEst nEst, /* Estimated number of output rows */ + const char *zName /* Name of table or index being scanned */ +){ + int nByte = (p->nScan+1) * sizeof(ScanStatus); + ScanStatus *aNew; + aNew = (ScanStatus*)sqlite3DbRealloc(p->db, p->aScan, nByte); + if( aNew ){ + ScanStatus *pNew = &aNew[p->nScan++]; + pNew->addrExplain = addrExplain; + pNew->addrLoop = addrLoop; + pNew->addrVisit = addrVisit; + pNew->nEst = nEst; + pNew->zName = sqlite3DbStrDup(p->db, zName); + p->aScan = aNew; + } +} +#endif + + +/* +** Change the value of the opcode, or P1, P2, P3, or P5 operands +** for a specific instruction. +*/ +SQLITE_PRIVATE void sqlite3VdbeChangeOpcode(Vdbe *p, u32 addr, u8 iNewOpcode){ + sqlite3VdbeGetOp(p,addr)->opcode = iNewOpcode; +} SQLITE_PRIVATE void sqlite3VdbeChangeP1(Vdbe *p, u32 addr, int val){ - assert( p!=0 ); - if( ((u32)p->nOp)>addr ){ - p->aOp[addr].p1 = val; - } + sqlite3VdbeGetOp(p,addr)->p1 = val; } - -/* -** Change the value of the P2 operand for a specific instruction. -** This routine is useful for setting a jump destination. -*/ SQLITE_PRIVATE void sqlite3VdbeChangeP2(Vdbe *p, u32 addr, int val){ - assert( p!=0 ); - if( ((u32)p->nOp)>addr ){ - p->aOp[addr].p2 = val; - } + sqlite3VdbeGetOp(p,addr)->p2 = val; } - -/* -** Change the value of the P3 operand for a specific instruction. -*/ SQLITE_PRIVATE void sqlite3VdbeChangeP3(Vdbe *p, u32 addr, int val){ - assert( p!=0 ); - if( ((u32)p->nOp)>addr ){ - p->aOp[addr].p3 = val; - } + sqlite3VdbeGetOp(p,addr)->p3 = val; } - -/* -** Change the value of the P5 operand for the most recently -** added operation. -*/ -SQLITE_PRIVATE void sqlite3VdbeChangeP5(Vdbe *p, u8 val){ - assert( p!=0 ); - if( p->aOp ){ - assert( p->nOp>0 ); - p->aOp[p->nOp-1].p5 = val; - } +SQLITE_PRIVATE void sqlite3VdbeChangeP5(Vdbe *p, u8 p5){ + sqlite3VdbeGetOp(p,-1)->p5 = p5; } /* @@ -62361,8 +68044,8 @@ SQLITE_PRIVATE void sqlite3VdbeChangeP5(Vdbe *p, u8 val){ ** the address of the next instruction to be coded. */ SQLITE_PRIVATE void sqlite3VdbeJumpHere(Vdbe *p, int addr){ - sqlite3VdbeChangeP2(p, addr, p->nOp); p->pParse->iFixedOp = p->nOp - 1; + sqlite3VdbeChangeP2(p, addr, p->nOp); } @@ -62385,6 +68068,10 @@ static void freeP4(sqlite3 *db, int p4type, void *p4){ if( p4 ){ assert( db ); switch( p4type ){ + case P4_FUNCCTX: { + freeEphemeralFunction(db, ((sqlite3_context*)p4)->pFunc); + /* Fall through into the next case */ + } case P4_REAL: case P4_INT64: case P4_DYNAMIC: @@ -62396,6 +68083,12 @@ static void freeP4(sqlite3 *db, int p4type, void *p4){ if( db->pnBytesFreed==0 ) sqlite3KeyInfoUnref((KeyInfo*)p4); break; } +#ifdef SQLITE_ENABLE_CURSOR_HINTS + case P4_EXPR: { + sqlite3ExprDelete(db, (Expr*)p4); + break; + } +#endif case P4_MPRINTF: { if( db->pnBytesFreed==0 ) sqlite3_free(p4); break; @@ -62409,7 +68102,7 @@ static void freeP4(sqlite3 *db, int p4type, void *p4){ sqlite3ValueFree((sqlite3_value*)p4); }else{ Mem *p = (Mem*)p4; - sqlite3DbFree(db, p->zMalloc); + if( p->szMalloc ) sqlite3DbFree(db, p->zMalloc); sqlite3DbFree(db, p); } break; @@ -62454,18 +68147,18 @@ SQLITE_PRIVATE void sqlite3VdbeLinkSubProgram(Vdbe *pVdbe, SubProgram *p){ ** Change the opcode at addr into OP_Noop */ SQLITE_PRIVATE void sqlite3VdbeChangeToNoop(Vdbe *p, int addr){ - if( p->aOp ){ + if( addrnOp ){ VdbeOp *pOp = &p->aOp[addr]; sqlite3 *db = p->db; freeP4(db, pOp->p4type, pOp->p4.p); memset(pOp, 0, sizeof(pOp[0])); pOp->opcode = OP_Noop; - if( addr==p->nOp-1 ) p->nOp--; } } /* -** Remove the last opcode inserted +** If the last opcode is "op" and it is not a jump destination, +** then remove it. Return true if and only if an opcode was removed. */ SQLITE_PRIVATE int sqlite3VdbeDeletePriorOpcode(Vdbe *p, u8 op){ if( (p->nOp-1)>(p->pParse->iFixedOp) && p->aOp[p->nOp-1].opcode==op ){ @@ -62527,6 +68220,15 @@ SQLITE_PRIVATE void sqlite3VdbeChangeP4(Vdbe *p, int addr, const char *zP4, int }else if( n==P4_KEYINFO ){ pOp->p4.p = (void*)zP4; pOp->p4type = P4_KEYINFO; +#ifdef SQLITE_ENABLE_CURSOR_HINTS + }else if( n==P4_EXPR ){ + /* Responsibility for deleting the Expr tree is handed over to the + ** VDBE by this operation. The caller should have already invoked + ** sqlite3ExprDup() or whatever other routine is needed to make a + ** private copy of the tree. */ + pOp->p4.pExpr = (Expr*)zP4; + pOp->p4type = P4_EXPR; +#endif }else if( n==P4_VTAB ){ pOp->p4.p = (void*)zP4; pOp->p4type = P4_VTAB; @@ -62606,7 +68308,7 @@ SQLITE_PRIVATE void sqlite3VdbeSetLineNumber(Vdbe *v, int iLine){ ** routine, then a pointer to a dummy VdbeOp will be returned. That opcode ** is readable but not writable, though it is cast to a writable value. ** The return of a dummy opcode allows the call to continue functioning -** after a OOM fault without having to check to see if the return from +** after an OOM fault without having to check to see if the return from ** this routine is a valid pointer. But because the dummy.opcode is 0, ** dummy will never be written to. This is verified by code inspection and ** by running with Valgrind. @@ -62717,9 +68419,84 @@ static int displayComment( } #endif /* SQLITE_DEBUG */ +#if VDBE_DISPLAY_P4 && defined(SQLITE_ENABLE_CURSOR_HINTS) +/* +** Translate the P4.pExpr value for an OP_CursorHint opcode into text +** that can be displayed in the P4 column of EXPLAIN output. +*/ +static int displayP4Expr(int nTemp, char *zTemp, Expr *pExpr){ + const char *zOp = 0; + int n; + switch( pExpr->op ){ + case TK_STRING: + sqlite3_snprintf(nTemp, zTemp, "%Q", pExpr->u.zToken); + break; + case TK_INTEGER: + sqlite3_snprintf(nTemp, zTemp, "%d", pExpr->u.iValue); + break; + case TK_NULL: + sqlite3_snprintf(nTemp, zTemp, "NULL"); + break; + case TK_REGISTER: { + sqlite3_snprintf(nTemp, zTemp, "r[%d]", pExpr->iTable); + break; + } + case TK_COLUMN: { + if( pExpr->iColumn<0 ){ + sqlite3_snprintf(nTemp, zTemp, "rowid"); + }else{ + sqlite3_snprintf(nTemp, zTemp, "c%d", (int)pExpr->iColumn); + } + break; + } + case TK_LT: zOp = "LT"; break; + case TK_LE: zOp = "LE"; break; + case TK_GT: zOp = "GT"; break; + case TK_GE: zOp = "GE"; break; + case TK_NE: zOp = "NE"; break; + case TK_EQ: zOp = "EQ"; break; + case TK_IS: zOp = "IS"; break; + case TK_ISNOT: zOp = "ISNOT"; break; + case TK_AND: zOp = "AND"; break; + case TK_OR: zOp = "OR"; break; + case TK_PLUS: zOp = "ADD"; break; + case TK_STAR: zOp = "MUL"; break; + case TK_MINUS: zOp = "SUB"; break; + case TK_REM: zOp = "REM"; break; + case TK_BITAND: zOp = "BITAND"; break; + case TK_BITOR: zOp = "BITOR"; break; + case TK_SLASH: zOp = "DIV"; break; + case TK_LSHIFT: zOp = "LSHIFT"; break; + case TK_RSHIFT: zOp = "RSHIFT"; break; + case TK_CONCAT: zOp = "CONCAT"; break; + case TK_UMINUS: zOp = "MINUS"; break; + case TK_UPLUS: zOp = "PLUS"; break; + case TK_BITNOT: zOp = "BITNOT"; break; + case TK_NOT: zOp = "NOT"; break; + case TK_ISNULL: zOp = "ISNULL"; break; + case TK_NOTNULL: zOp = "NOTNULL"; break; -#if !defined(SQLITE_OMIT_EXPLAIN) || !defined(NDEBUG) \ - || defined(VDBE_PROFILE) || defined(SQLITE_DEBUG) + default: + sqlite3_snprintf(nTemp, zTemp, "%s", "expr"); + break; + } + + if( zOp ){ + sqlite3_snprintf(nTemp, zTemp, "%s(", zOp); + n = sqlite3Strlen30(zTemp); + n += displayP4Expr(nTemp-n, zTemp+n, pExpr->pLeft); + if( npRight ){ + zTemp[n++] = ','; + n += displayP4Expr(nTemp-n, zTemp+n, pExpr->pRight); + } + sqlite3_snprintf(nTemp-n, zTemp+n, ")"); + } + return sqlite3Strlen30(zTemp); +} +#endif /* VDBE_DISPLAY_P4 && defined(SQLITE_ENABLE_CURSOR_HINTS) */ + + +#if VDBE_DISPLAY_P4 /* ** Compute a string that describes the P4 parameter for an opcode. ** Use zTemp for any required temporary buffer space. @@ -62742,8 +68519,9 @@ static char *displayP4(Op *pOp, char *zTemp, int nTemp){ zColl = "B"; n = 1; } - if( i+n>nTemp-6 ){ + if( i+n>nTemp-7 ){ memcpy(&zTemp[i],",...",4); + i += 4; break; } zTemp[i++] = ','; @@ -62758,6 +68536,12 @@ static char *displayP4(Op *pOp, char *zTemp, int nTemp){ assert( ip4.pExpr); + break; + } +#endif case P4_COLLSEQ: { CollSeq *pColl = pOp->p4.pColl; sqlite3_snprintf(nTemp, zTemp, "(%.20s)", pColl->zName); @@ -62768,6 +68552,13 @@ static char *displayP4(Op *pOp, char *zTemp, int nTemp){ sqlite3_snprintf(nTemp, zTemp, "%s(%d)", pDef->zName, pDef->nArg); break; } +#ifdef SQLITE_DEBUG + case P4_FUNCCTX: { + FuncDef *pDef = pOp->p4.pCtx->pFunc; + sqlite3_snprintf(nTemp, zTemp, "%s(%d)", pDef->zName, pDef->nArg); + break; + } +#endif case P4_INT64: { sqlite3_snprintf(nTemp, zTemp, "%lld", *pOp->p4.pI64); break; @@ -62787,7 +68578,7 @@ static char *displayP4(Op *pOp, char *zTemp, int nTemp){ }else if( pMem->flags & MEM_Int ){ sqlite3_snprintf(nTemp, zTemp, "%lld", pMem->u.i); }else if( pMem->flags & MEM_Real ){ - sqlite3_snprintf(nTemp, zTemp, "%.16g", pMem->r); + sqlite3_snprintf(nTemp, zTemp, "%.16g", pMem->u.r); }else if( pMem->flags & MEM_Null ){ sqlite3_snprintf(nTemp, zTemp, "NULL"); }else{ @@ -62799,7 +68590,7 @@ static char *displayP4(Op *pOp, char *zTemp, int nTemp){ #ifndef SQLITE_OMIT_VIRTUALTABLE case P4_VTAB: { sqlite3_vtab *pVtab = pOp->p4.pVtab->pVtab; - sqlite3_snprintf(nTemp, zTemp, "vtab:%p:%p", pVtab, pVtab->pModule); + sqlite3_snprintf(nTemp, zTemp, "vtab:%p", pVtab); break; } #endif @@ -62826,7 +68617,7 @@ static char *displayP4(Op *pOp, char *zTemp, int nTemp){ assert( zP4!=0 ); return zP4; } -#endif +#endif /* VDBE_DISPLAY_P4 */ /* ** Declare to the Vdbe that the BTree object at db->aDb[i] is used. @@ -62839,9 +68630,9 @@ static char *displayP4(Op *pOp, char *zTemp, int nTemp){ SQLITE_PRIVATE void sqlite3VdbeUsesBtree(Vdbe *p, int i){ assert( i>=0 && idb->nDb && i<(int)sizeof(yDbMask)*8 ); assert( i<(int)sizeof(p->btreeMask)*8 ); - p->btreeMask |= ((yDbMask)1)<btreeMask, i); if( i!=1 && sqlite3BtreeSharable(p->db->aDb[i].pBt) ){ - p->lockMask |= ((yDbMask)1)<lockMask, i); } } @@ -62869,16 +68660,15 @@ SQLITE_PRIVATE void sqlite3VdbeUsesBtree(Vdbe *p, int i){ */ SQLITE_PRIVATE void sqlite3VdbeEnter(Vdbe *p){ int i; - yDbMask mask; sqlite3 *db; Db *aDb; int nDb; - if( p->lockMask==0 ) return; /* The common case */ + if( DbMaskAllZero(p->lockMask) ) return; /* The common case */ db = p->db; aDb = db->aDb; nDb = db->nDb; - for(i=0, mask=1; ilockMask)!=0 && ALWAYS(aDb[i].pBt!=0) ){ + for(i=0; ilockMask,i) && ALWAYS(aDb[i].pBt!=0) ){ sqlite3BtreeEnter(aDb[i].pBt); } } @@ -62889,22 +68679,24 @@ SQLITE_PRIVATE void sqlite3VdbeEnter(Vdbe *p){ /* ** Unlock all of the btrees previously locked by a call to sqlite3VdbeEnter(). */ -SQLITE_PRIVATE void sqlite3VdbeLeave(Vdbe *p){ +static SQLITE_NOINLINE void vdbeLeave(Vdbe *p){ int i; - yDbMask mask; sqlite3 *db; Db *aDb; int nDb; - if( p->lockMask==0 ) return; /* The common case */ db = p->db; aDb = db->aDb; nDb = db->nDb; - for(i=0, mask=1; ilockMask)!=0 && ALWAYS(aDb[i].pBt!=0) ){ + for(i=0; ilockMask,i) && ALWAYS(aDb[i].pBt!=0) ){ sqlite3BtreeLeave(aDb[i].pBt); } } } +SQLITE_PRIVATE void sqlite3VdbeLeave(Vdbe *p){ + if( DbMaskAllZero(p->lockMask) ) return; /* The common case */ + vdbeLeave(p); +} #endif #if defined(VDBE_PROFILE) || defined(SQLITE_DEBUG) @@ -62939,16 +68731,16 @@ SQLITE_PRIVATE void sqlite3VdbePrintOp(FILE *pOut, int pc, Op *pOp){ */ static void releaseMemArray(Mem *p, int N){ if( p && N ){ - Mem *pEnd; + Mem *pEnd = &p[N]; sqlite3 *db = p->db; u8 malloc_failed = db->mallocFailed; if( db->pnBytesFreed ){ - for(pEnd=&p[N]; pzMalloc); - } + do{ + if( p->szMalloc ) sqlite3DbFree(db, p->zMalloc); + }while( (++p)flags & MEM_RowSet ); if( p->flags&(MEM_Agg|MEM_Dyn|MEM_Frame|MEM_RowSet) ){ sqlite3VdbeMemRelease(p); - }else if( p->zMalloc ){ + }else if( p->szMalloc ){ sqlite3DbFree(db, p->zMalloc); - p->zMalloc = 0; + p->szMalloc = 0; } p->flags = MEM_Undefined; - } + }while( (++p)mallocFailed = malloc_failed; } } @@ -63077,7 +68869,7 @@ SQLITE_PRIVATE int sqlite3VdbeList( }else if( db->u1.isInterrupted ){ p->rc = SQLITE_INTERRUPT; rc = SQLITE_ERROR; - sqlite3SetString(&p->zErrMsg, db, "%s", sqlite3ErrStr(p->rc)); + sqlite3VdbeError(p, sqlite3ErrStr(p->rc)); }else{ char *zP4; Op *pOp; @@ -63139,12 +68931,12 @@ SQLITE_PRIVATE int sqlite3VdbeList( pMem->u.i = pOp->p3; /* P3 */ pMem++; - if( sqlite3VdbeMemGrow(pMem, 32, 0) ){ /* P4 */ + if( sqlite3VdbeMemClearAndResize(pMem, 100) ){ /* P4 */ assert( p->db->mallocFailed ); return SQLITE_ERROR; } pMem->flags = MEM_Str|MEM_Term; - zP4 = displayP4(pOp, pMem->z, 32); + zP4 = displayP4(pOp, pMem->z, pMem->szMalloc); if( zP4!=pMem->z ){ sqlite3VdbeMemSetStr(pMem, zP4, -1, SQLITE_UTF8, 0); }else{ @@ -63155,7 +68947,7 @@ SQLITE_PRIVATE int sqlite3VdbeList( pMem++; if( p->explain==1 ){ - if( sqlite3VdbeMemGrow(pMem, 4, 0) ){ + if( sqlite3VdbeMemClearAndResize(pMem, 4) ){ assert( p->db->mallocFailed ); return SQLITE_ERROR; } @@ -63166,7 +68958,7 @@ SQLITE_PRIVATE int sqlite3VdbeList( pMem++; #ifdef SQLITE_ENABLE_EXPLAIN_COMMENTS - if( sqlite3VdbeMemGrow(pMem, 500, 0) ){ + if( sqlite3VdbeMemClearAndResize(pMem, 500) ){ assert( p->db->mallocFailed ); return SQLITE_ERROR; } @@ -63249,30 +69041,31 @@ SQLITE_PRIVATE void sqlite3VdbeIOTraceSql(Vdbe *p){ ** ** nByte is the number of bytes of space needed. ** -** *ppFrom points to available space and pEnd points to the end of the -** available space. When space is allocated, *ppFrom is advanced past -** the end of the allocated space. +** pFrom points to *pnFrom bytes of available space. New space is allocated +** from the end of the pFrom buffer and *pnFrom is decremented. ** -** *pnByte is a counter of the number of bytes of space that have failed -** to allocate. If there is insufficient space in *ppFrom to satisfy the -** request, then increment *pnByte by the amount of the request. +** *pnNeeded is a counter of the number of bytes of space that have failed +** to allocate. If there is insufficient space in pFrom to satisfy the +** request, then increment *pnNeeded by the amount of the request. */ static void *allocSpace( void *pBuf, /* Where return pointer will be stored */ int nByte, /* Number of bytes to allocate */ - u8 **ppFrom, /* IN/OUT: Allocate from *ppFrom */ - u8 *pEnd, /* Pointer to 1 byte past the end of *ppFrom buffer */ - int *pnByte /* If allocation cannot be made, increment *pnByte */ + u8 *pFrom, /* Memory available for allocation */ + int *pnFrom, /* IN/OUT: Space available at pFrom */ + int *pnNeeded /* If allocation cannot be made, increment *pnByte */ ){ - assert( EIGHT_BYTE_ALIGNMENT(*ppFrom) ); - if( pBuf ) return pBuf; - nByte = ROUND8(nByte); - if( &(*ppFrom)[nByte] <= pEnd ){ - pBuf = (void*)*ppFrom; - *ppFrom += nByte; - }else{ - *pnByte += nByte; + assert( EIGHT_BYTE_ALIGNMENT(pFrom) ); + if( pBuf==0 ){ + nByte = ROUND8(nByte); + if( nByte <= *pnFrom ){ + *pnFrom -= nByte; + pBuf = &pFrom[*pnFrom]; + }else{ + *pnNeeded += nByte; + } } + assert( EIGHT_BYTE_ALIGNMENT(pBuf) ); return pBuf; } @@ -63319,13 +69112,13 @@ SQLITE_PRIVATE void sqlite3VdbeRewind(Vdbe *p){ /* ** Prepare a virtual machine for execution for the first time after ** creating the virtual machine. This involves things such -** as allocating stack space and initializing the program counter. +** as allocating registers and initializing the program counter. ** After the VDBE has be prepped, it can be executed by one or more ** calls to sqlite3VdbeExec(). ** -** This function may be called exact once on a each virtual machine. +** This function may be called exactly once on each virtual machine. ** After this routine is called the VM has been "packaged" and is ready -** to run. After this routine is called, futher calls to +** to run. After this routine is called, further calls to ** sqlite3VdbeAddOp() functions are prohibited. This routine disconnects ** the Vdbe from the Parse object that helped generate it so that the ** the Vdbe becomes an independent entity and the Parse object can be @@ -63345,8 +69138,8 @@ SQLITE_PRIVATE void sqlite3VdbeMakeReady( int nArg; /* Number of arguments in subprograms */ int nOnce; /* Number of OP_Once instructions */ int n; /* Loop counter */ + int nFree; /* Available free space */ u8 *zCsr; /* Memory available for allocation */ - u8 *zEnd; /* First byte past allocated memory */ int nByte; /* How much extra memory is needed */ assert( p!=0 ); @@ -63374,20 +69167,27 @@ SQLITE_PRIVATE void sqlite3VdbeMakeReady( */ nMem += nCursor; - /* Allocate space for memory registers, SQL variables, VDBE cursors and - ** an array to marshal SQL function arguments in. + /* zCsr will initially point to nFree bytes of unused space at the + ** end of the opcode array, p->aOp. The computation of nFree is + ** conservative - it might be smaller than the true number of free + ** bytes, but never larger. nFree must be a multiple of 8 - it is + ** rounded down if is not. */ - zCsr = (u8*)&p->aOp[p->nOp]; /* Memory avaliable for allocation */ - zEnd = (u8*)&p->aOp[pParse->nOpAlloc]; /* First byte past end of zCsr[] */ + n = ROUND8(sizeof(Op)*p->nOp); /* Bytes of opcode space used */ + zCsr = &((u8*)p->aOp)[n]; /* Unused opcode space */ + assert( EIGHT_BYTE_ALIGNMENT(zCsr) ); + nFree = ROUNDDOWN8(pParse->szOpAlloc - n); /* Bytes of unused space */ + assert( nFree>=0 ); + if( nFree>0 ){ + memset(zCsr, 0, nFree); + assert( EIGHT_BYTE_ALIGNMENT(&zCsr[nFree]) ); + } resolveP2Values(p, &nArg); p->usesStmtJournal = (u8)(pParse->isMultiWrite && pParse->mayAbort); if( pParse->explain && nMem<10 ){ nMem = 10; } - memset(zCsr, 0, zEnd-zCsr); - zCsr += (zCsr - (u8*)0)&7; - assert( EIGHT_BYTE_ALIGNMENT(zCsr) ); p->expired = 0; /* Memory for registers, parameters, cursor, etc, is allocated in two @@ -63402,18 +69202,21 @@ SQLITE_PRIVATE void sqlite3VdbeMakeReady( */ do { nByte = 0; - p->aMem = allocSpace(p->aMem, nMem*sizeof(Mem), &zCsr, zEnd, &nByte); - p->aVar = allocSpace(p->aVar, nVar*sizeof(Mem), &zCsr, zEnd, &nByte); - p->apArg = allocSpace(p->apArg, nArg*sizeof(Mem*), &zCsr, zEnd, &nByte); - p->azVar = allocSpace(p->azVar, nVar*sizeof(char*), &zCsr, zEnd, &nByte); + p->aMem = allocSpace(p->aMem, nMem*sizeof(Mem), zCsr, &nFree, &nByte); + p->aVar = allocSpace(p->aVar, nVar*sizeof(Mem), zCsr, &nFree, &nByte); + p->apArg = allocSpace(p->apArg, nArg*sizeof(Mem*), zCsr, &nFree, &nByte); + p->azVar = allocSpace(p->azVar, nVar*sizeof(char*), zCsr, &nFree, &nByte); p->apCsr = allocSpace(p->apCsr, nCursor*sizeof(VdbeCursor*), - &zCsr, zEnd, &nByte); - p->aOnceFlag = allocSpace(p->aOnceFlag, nOnce, &zCsr, zEnd, &nByte); + zCsr, &nFree, &nByte); + p->aOnceFlag = allocSpace(p->aOnceFlag, nOnce, zCsr, &nFree, &nByte); +#ifdef SQLITE_ENABLE_STMT_SCANSTATUS + p->anExec = allocSpace(p->anExec, p->nOp*sizeof(i64), zCsr, &nFree, &nByte); +#endif if( nByte ){ p->pFree = sqlite3DbMallocZero(db, nByte); } zCsr = p->pFree; - zEnd = &zCsr[nByte]; + nFree = nByte; }while( nByte && !db->mallocFailed ); p->nCursor = nCursor; @@ -63425,7 +69228,7 @@ SQLITE_PRIVATE void sqlite3VdbeMakeReady( p->aVar[n].db = db; } } - if( p->azVar ){ + if( p->azVar && pParse->nzVar>0 ){ p->nzVar = pParse->nzVar; memcpy(p->azVar, pParse->azVar, p->nzVar*sizeof(p->azVar[0])); memset(pParse->azVar, 0, pParse->nzVar*sizeof(pParse->azVar[0])); @@ -63450,23 +69253,50 @@ SQLITE_PRIVATE void sqlite3VdbeFreeCursor(Vdbe *p, VdbeCursor *pCx){ if( pCx==0 ){ return; } - sqlite3VdbeSorterClose(p->db, pCx); - if( pCx->pBt ){ - sqlite3BtreeClose(pCx->pBt); - /* The pCx->pCursor will be close automatically, if it exists, by - ** the call above. */ - }else if( pCx->pCursor ){ - sqlite3BtreeCloseCursor(pCx->pCursor); - } + assert( pCx->pBt==0 || pCx->eCurType==CURTYPE_BTREE ); + switch( pCx->eCurType ){ + case CURTYPE_SORTER: { + sqlite3VdbeSorterClose(p->db, pCx); + break; + } + case CURTYPE_BTREE: { + if( pCx->pBt ){ + sqlite3BtreeClose(pCx->pBt); + /* The pCx->pCursor will be close automatically, if it exists, by + ** the call above. */ + }else{ + assert( pCx->uc.pCursor!=0 ); + sqlite3BtreeCloseCursor(pCx->uc.pCursor); + } + break; + } #ifndef SQLITE_OMIT_VIRTUALTABLE - if( pCx->pVtabCursor ){ - sqlite3_vtab_cursor *pVtabCursor = pCx->pVtabCursor; - const sqlite3_module *pModule = pVtabCursor->pVtab->pModule; - p->inVtabMethod = 1; - pModule->xClose(pVtabCursor); - p->inVtabMethod = 0; - } + case CURTYPE_VTAB: { + sqlite3_vtab_cursor *pVCur = pCx->uc.pVCur; + const sqlite3_module *pModule = pVCur->pVtab->pModule; + assert( pVCur->pVtab->nRef>0 ); + pVCur->pVtab->nRef--; + pModule->xClose(pVCur); + break; + } #endif + } +} + +/* +** Close all cursors in the current frame. +*/ +static void closeCursorsInFrame(Vdbe *p){ + if( p->apCsr ){ + int i; + for(i=0; inCursor; i++){ + VdbeCursor *pC = p->apCsr[i]; + if( pC ){ + sqlite3VdbeFreeCursor(p, pC); + p->apCsr[i] = 0; + } + } + } } /* @@ -63476,6 +69306,10 @@ SQLITE_PRIVATE void sqlite3VdbeFreeCursor(Vdbe *p, VdbeCursor *pCx){ */ SQLITE_PRIVATE int sqlite3VdbeFrameRestore(VdbeFrame *pFrame){ Vdbe *v = pFrame->v; + closeCursorsInFrame(v); +#ifdef SQLITE_ENABLE_STMT_SCANSTATUS + v->anExec = pFrame->anExec; +#endif v->aOnceFlag = pFrame->aOnceFlag; v->nOnceFlag = pFrame->nOnceFlag; v->aOp = pFrame->aOp; @@ -63486,6 +69320,7 @@ SQLITE_PRIVATE int sqlite3VdbeFrameRestore(VdbeFrame *pFrame){ v->nCursor = pFrame->nCursor; v->db->lastRowid = pFrame->lastRowid; v->nChange = pFrame->nChange; + v->db->nChange = pFrame->nDbChange; return pFrame->pc; } @@ -63502,20 +69337,11 @@ static void closeAllCursors(Vdbe *p){ VdbeFrame *pFrame; for(pFrame=p->pFrame; pFrame->pParent; pFrame=pFrame->pParent); sqlite3VdbeFrameRestore(pFrame); + p->pFrame = 0; + p->nFrame = 0; } - p->pFrame = 0; - p->nFrame = 0; - - if( p->apCsr ){ - int i; - for(i=0; inCursor; i++){ - VdbeCursor *pC = p->apCsr[i]; - if( pC ){ - sqlite3VdbeFreeCursor(p, pC); - p->apCsr[i] = 0; - } - } - } + assert( p->nFrame==0 ); + closeCursorsInFrame(p); if( p->aMem ){ releaseMemArray(&p->aMem[1], p->nMem); } @@ -63526,16 +69352,12 @@ static void closeAllCursors(Vdbe *p){ } /* Delete any auxdata allocations made by the VM */ - sqlite3VdbeDeleteAuxData(p, -1, 0); + if( p->pAuxData ) sqlite3VdbeDeleteAuxData(p, -1, 0); assert( p->pAuxData==0 ); } /* -** Clean up the VM after execution. -** -** This routine will automatically close any cursors, lists, and/or -** sorters that were left open. It also deletes the values of -** variables in the aVar[] array. +** Clean up the VM after a single run. */ static void Cleanup(Vdbe *p){ sqlite3 *db = p->db; @@ -63703,7 +69525,7 @@ static int vdbeCommit(sqlite3 *db, Vdbe *p){ /* The complex case - There is a multi-file write-transaction active. ** This requires a master journal file to ensure the transaction is - ** committed atomicly. + ** committed atomically. */ #ifndef SQLITE_OMIT_DISKIO else{ @@ -63822,7 +69644,7 @@ static int vdbeCommit(sqlite3 *db, Vdbe *p){ ** doing this the directory is synced again before any individual ** transaction files are deleted. */ - rc = sqlite3OsDelete(pVfs, zMaster, 1); + rc = sqlite3OsDelete(pVfs, zMaster, needSync); sqlite3DbFree(db, zMaster); zMaster = 0; if( rc ){ @@ -63871,7 +69693,7 @@ static void checkActiveVdbeCnt(sqlite3 *db){ int nRead = 0; p = db->pVdbe; while( p ){ - if( p->magic==VDBE_MAGIC_RUN && p->pc>=0 ){ + if( sqlite3_stmt_busy((sqlite3_stmt*)p) ){ cnt++; if( p->readOnly==0 ) nWrite++; if( p->bIsReader ) nRead++; @@ -63969,7 +69791,7 @@ SQLITE_PRIVATE int sqlite3VdbeCheckFk(Vdbe *p, int deferred){ ){ p->rc = SQLITE_CONSTRAINT_FOREIGNKEY; p->errorAction = OE_Abort; - sqlite3SetString(&p->zErrMsg, db, "FOREIGN KEY constraint failed"); + sqlite3VdbeError(p, "FOREIGN KEY constraint failed"); return SQLITE_ERROR; } return SQLITE_OK; @@ -64031,7 +69853,6 @@ SQLITE_PRIVATE int sqlite3VdbeHalt(Vdbe *p){ /* Check for one of the special errors */ mrc = p->rc & 0xff; - assert( p->rc!=SQLITE_IOERR_BLOCKED ); /* This error no longer exists */ isSpecialError = mrc==SQLITE_NOMEM || mrc==SQLITE_IOERR || mrc==SQLITE_INTERRUPT || mrc==SQLITE_FULL; if( isSpecialError ){ @@ -64057,6 +69878,7 @@ SQLITE_PRIVATE int sqlite3VdbeHalt(Vdbe *p){ sqlite3RollbackAll(db, SQLITE_ABORT_ROLLBACK); sqlite3CloseSavepoints(db); db->autoCommit = 1; + p->nChange = 0; } } } @@ -64097,6 +69919,7 @@ SQLITE_PRIVATE int sqlite3VdbeHalt(Vdbe *p){ }else if( rc!=SQLITE_OK ){ p->rc = rc; sqlite3RollbackAll(db, SQLITE_OK); + p->nChange = 0; }else{ db->nDeferredCons = 0; db->nDeferredImmCons = 0; @@ -64105,6 +69928,7 @@ SQLITE_PRIVATE int sqlite3VdbeHalt(Vdbe *p){ } }else{ sqlite3RollbackAll(db, SQLITE_OK); + p->nChange = 0; } db->nStatement = 0; }else if( eStatementOp==0 ){ @@ -64116,6 +69940,7 @@ SQLITE_PRIVATE int sqlite3VdbeHalt(Vdbe *p){ sqlite3RollbackAll(db, SQLITE_ABORT_ROLLBACK); sqlite3CloseSavepoints(db); db->autoCommit = 1; + p->nChange = 0; } } @@ -64136,6 +69961,7 @@ SQLITE_PRIVATE int sqlite3VdbeHalt(Vdbe *p){ sqlite3RollbackAll(db, SQLITE_ABORT_ROLLBACK); sqlite3CloseSavepoints(db); db->autoCommit = 1; + p->nChange = 0; } } @@ -64211,7 +70037,7 @@ SQLITE_PRIVATE int sqlite3VdbeTransferError(Vdbe *p){ db->mallocFailed = mallocFailed; db->errCode = rc; }else{ - sqlite3Error(db, rc, 0); + sqlite3Error(db, rc); } return rc; } @@ -64274,7 +70100,7 @@ SQLITE_PRIVATE int sqlite3VdbeReset(Vdbe *p){ ** to sqlite3_step(). For consistency (since sqlite3_step() was ** called), set the database error in this case as well. */ - sqlite3Error(db, p->rc, p->zErrMsg ? "%s" : 0, p->zErrMsg); + sqlite3ErrorWithMsg(db, p->rc, p->zErrMsg ? "%s" : 0, p->zErrMsg); sqlite3DbFree(db, p->zErrMsg); p->zErrMsg = 0; } @@ -64352,7 +70178,7 @@ SQLITE_PRIVATE int sqlite3VdbeFinalize(Vdbe *p){ ** from left to right), or ** ** * the corresponding bit in argument mask is clear (where the first -** function parameter corrsponds to bit 0 etc.). +** function parameter corresponds to bit 0 etc.). */ SQLITE_PRIVATE void sqlite3VdbeDeleteAuxData(Vdbe *pVdbe, int iOp, int mask){ AuxData **pp = &pVdbe->pAuxData; @@ -64397,9 +70223,11 @@ SQLITE_PRIVATE void sqlite3VdbeClearObject(sqlite3 *db, Vdbe *p){ sqlite3DbFree(db, p->aColName); sqlite3DbFree(db, p->zSql); sqlite3DbFree(db, p->pFree); -#if defined(SQLITE_ENABLE_TREE_EXPLAIN) - sqlite3DbFree(db, p->zExplain); - sqlite3DbFree(db, p->pExplain); +#ifdef SQLITE_ENABLE_STMT_SCANSTATUS + for(i=0; inScan; i++){ + sqlite3DbFree(db, p->aScan[i].zName); + } + sqlite3DbFree(db, p->aScan); #endif } @@ -64427,6 +70255,60 @@ SQLITE_PRIVATE void sqlite3VdbeDelete(Vdbe *p){ sqlite3DbFree(db, p); } +/* +** The cursor "p" has a pending seek operation that has not yet been +** carried out. Seek the cursor now. If an error occurs, return +** the appropriate error code. +*/ +static int SQLITE_NOINLINE handleDeferredMoveto(VdbeCursor *p){ + int res, rc; +#ifdef SQLITE_TEST + extern int sqlite3_search_count; +#endif + assert( p->deferredMoveto ); + assert( p->isTable ); + assert( p->eCurType==CURTYPE_BTREE ); + rc = sqlite3BtreeMovetoUnpacked(p->uc.pCursor, 0, p->movetoTarget, 0, &res); + if( rc ) return rc; + if( res!=0 ) return SQLITE_CORRUPT_BKPT; +#ifdef SQLITE_TEST + sqlite3_search_count++; +#endif + p->deferredMoveto = 0; + p->cacheStatus = CACHE_STALE; + return SQLITE_OK; +} + +/* +** Something has moved cursor "p" out of place. Maybe the row it was +** pointed to was deleted out from under it. Or maybe the btree was +** rebalanced. Whatever the cause, try to restore "p" to the place it +** is supposed to be pointing. If the row was deleted out from under the +** cursor, set the cursor to point to a NULL row. +*/ +static int SQLITE_NOINLINE handleMovedCursor(VdbeCursor *p){ + int isDifferentRow, rc; + assert( p->eCurType==CURTYPE_BTREE ); + assert( p->uc.pCursor!=0 ); + assert( sqlite3BtreeCursorHasMoved(p->uc.pCursor) ); + rc = sqlite3BtreeCursorRestore(p->uc.pCursor, &isDifferentRow); + p->cacheStatus = CACHE_STALE; + if( isDifferentRow ) p->nullRow = 1; + return rc; +} + +/* +** Check to ensure that the cursor is valid. Restore the cursor +** if need be. Return any I/O error from the restore operation. +*/ +SQLITE_PRIVATE int sqlite3VdbeCursorRestore(VdbeCursor *p){ + assert( p->eCurType==CURTYPE_BTREE ); + if( sqlite3BtreeCursorHasMoved(p->uc.pCursor) ){ + return handleMovedCursor(p); + } + return SQLITE_OK; +} + /* ** Make sure the cursor p is ready to read or write the row to which it ** was last positioned. Return an error code if an OOM fault or I/O error @@ -64441,29 +70323,12 @@ SQLITE_PRIVATE void sqlite3VdbeDelete(Vdbe *p){ ** not been deleted out from under the cursor, then this routine is a no-op. */ SQLITE_PRIVATE int sqlite3VdbeCursorMoveto(VdbeCursor *p){ - if( p->deferredMoveto ){ - int res, rc; -#ifdef SQLITE_TEST - extern int sqlite3_search_count; -#endif - assert( p->isTable ); - rc = sqlite3BtreeMovetoUnpacked(p->pCursor, 0, p->movetoTarget, 0, &res); - if( rc ) return rc; - p->lastRowid = p->movetoTarget; - if( res!=0 ) return SQLITE_CORRUPT_BKPT; - p->rowidIsValid = 1; -#ifdef SQLITE_TEST - sqlite3_search_count++; -#endif - p->deferredMoveto = 0; - p->cacheStatus = CACHE_STALE; - }else if( p->pCursor ){ - int hasMoved; - int rc = sqlite3BtreeCursorHasMoved(p->pCursor, &hasMoved); - if( rc ) return rc; - if( hasMoved ){ - p->cacheStatus = CACHE_STALE; - if( hasMoved==2 ) p->nullRow = 1; + if( p->eCurType==CURTYPE_BTREE ){ + if( p->deferredMoveto ){ + return handleDeferredMoveto(p); + } + if( sqlite3BtreeCursorHasMoved(p->uc.pCursor) ){ + return handleMovedCursor(p); } } return SQLITE_OK; @@ -64514,11 +70379,13 @@ SQLITE_PRIVATE int sqlite3VdbeCursorMoveto(VdbeCursor *p){ /* ** Return the serial-type for the value stored in pMem. */ -SQLITE_PRIVATE u32 sqlite3VdbeSerialType(Mem *pMem, int file_format){ +SQLITE_PRIVATE u32 sqlite3VdbeSerialType(Mem *pMem, int file_format, u32 *pLen){ int flags = pMem->flags; - int n; + u32 n; + assert( pLen!=0 ); if( flags&MEM_Null ){ + *pLen = 0; return 0; } if( flags&MEM_Int ){ @@ -64527,44 +70394,76 @@ SQLITE_PRIVATE u32 sqlite3VdbeSerialType(Mem *pMem, int file_format){ i64 i = pMem->u.i; u64 u; if( i<0 ){ - if( i<(-MAX_6BYTE) ) return 6; - /* Previous test prevents: u = -(-9223372036854775808) */ - u = -i; + u = ~i; }else{ u = i; } if( u<=127 ){ - return ((i&1)==i && file_format>=4) ? 8+(u32)u : 1; + if( (i&1)==i && file_format>=4 ){ + *pLen = 0; + return 8+(u32)u; + }else{ + *pLen = 1; + return 1; + } } - if( u<=32767 ) return 2; - if( u<=8388607 ) return 3; - if( u<=2147483647 ) return 4; - if( u<=MAX_6BYTE ) return 5; + if( u<=32767 ){ *pLen = 2; return 2; } + if( u<=8388607 ){ *pLen = 3; return 3; } + if( u<=2147483647 ){ *pLen = 4; return 4; } + if( u<=MAX_6BYTE ){ *pLen = 6; return 5; } + *pLen = 8; return 6; } if( flags&MEM_Real ){ + *pLen = 8; return 7; } assert( pMem->db->mallocFailed || flags&(MEM_Str|MEM_Blob) ); - n = pMem->n; + assert( pMem->n>=0 ); + n = (u32)pMem->n; if( flags & MEM_Zero ){ n += pMem->u.nZero; } - assert( n>=0 ); + *pLen = n; return ((n*2) + 12 + ((flags&MEM_Str)!=0)); } +/* +** The sizes for serial types less than 128 +*/ +static const u8 sqlite3SmallTypeSizes[] = { + /* 0 1 2 3 4 5 6 7 8 9 */ +/* 0 */ 0, 1, 2, 3, 4, 6, 8, 8, 0, 0, +/* 10 */ 0, 0, 0, 0, 1, 1, 2, 2, 3, 3, +/* 20 */ 4, 4, 5, 5, 6, 6, 7, 7, 8, 8, +/* 30 */ 9, 9, 10, 10, 11, 11, 12, 12, 13, 13, +/* 40 */ 14, 14, 15, 15, 16, 16, 17, 17, 18, 18, +/* 50 */ 19, 19, 20, 20, 21, 21, 22, 22, 23, 23, +/* 60 */ 24, 24, 25, 25, 26, 26, 27, 27, 28, 28, +/* 70 */ 29, 29, 30, 30, 31, 31, 32, 32, 33, 33, +/* 80 */ 34, 34, 35, 35, 36, 36, 37, 37, 38, 38, +/* 90 */ 39, 39, 40, 40, 41, 41, 42, 42, 43, 43, +/* 100 */ 44, 44, 45, 45, 46, 46, 47, 47, 48, 48, +/* 110 */ 49, 49, 50, 50, 51, 51, 52, 52, 53, 53, +/* 120 */ 54, 54, 55, 55, 56, 56, 57, 57 +}; + /* ** Return the length of the data corresponding to the supplied serial-type. */ SQLITE_PRIVATE u32 sqlite3VdbeSerialTypeLen(u32 serial_type){ - if( serial_type>=12 ){ + if( serial_type>=128 ){ return (serial_type-12)/2; }else{ - static const u8 aSize[] = { 0, 1, 2, 3, 4, 6, 8, 8, 0, 0, 0, 0 }; - return aSize[serial_type]; + assert( serial_type<12 + || sqlite3SmallTypeSizes[serial_type]==(serial_type - 12)/2 ); + return sqlite3SmallTypeSizes[serial_type]; } } +SQLITE_PRIVATE u8 sqlite3VdbeOneByteSerialTypeLen(u8 serial_type){ + assert( serial_type<128 ); + return sqlite3SmallTypeSizes[serial_type]; +} /* ** If we are on an architecture with mixed-endian floating @@ -64640,17 +70539,18 @@ SQLITE_PRIVATE u32 sqlite3VdbeSerialPut(u8 *buf, Mem *pMem, u32 serial_type){ u64 v; u32 i; if( serial_type==7 ){ - assert( sizeof(v)==sizeof(pMem->r) ); - memcpy(&v, &pMem->r, sizeof(v)); + assert( sizeof(v)==sizeof(pMem->u.r) ); + memcpy(&v, &pMem->u.r, sizeof(v)); swapMixedEndianFloat(v); }else{ v = pMem->u.i; } - len = i = sqlite3VdbeSerialTypeLen(serial_type); - while( i-- ){ - buf[i] = (u8)(v&0xFF); + len = i = sqlite3SmallTypeSizes[serial_type]; + assert( i>0 ); + do{ + buf[--i] = (u8)(v&0xFF); v >>= 8; - } + }while( i ); return len; } @@ -64659,7 +70559,7 @@ SQLITE_PRIVATE u32 sqlite3VdbeSerialPut(u8 *buf, Mem *pMem, u32 serial_type){ assert( pMem->n + ((pMem->flags & MEM_Zero)?pMem->u.nZero:0) == (int)sqlite3VdbeSerialTypeLen(serial_type) ); len = pMem->n; - memcpy(buf, pMem->z, len); + if( len>0 ) memcpy(buf, pMem->z, len); return len; } @@ -64674,51 +70574,105 @@ SQLITE_PRIVATE u32 sqlite3VdbeSerialPut(u8 *buf, Mem *pMem, u32 serial_type){ #define TWO_BYTE_INT(x) (256*(i8)((x)[0])|(x)[1]) #define THREE_BYTE_INT(x) (65536*(i8)((x)[0])|((x)[1]<<8)|(x)[2]) #define FOUR_BYTE_UINT(x) (((u32)(x)[0]<<24)|((x)[1]<<16)|((x)[2]<<8)|(x)[3]) +#define FOUR_BYTE_INT(x) (16777216*(i8)((x)[0])|((x)[1]<<16)|((x)[2]<<8)|(x)[3]) /* ** Deserialize the data blob pointed to by buf as serial type serial_type ** and store the result in pMem. Return the number of bytes read. +** +** This function is implemented as two separate routines for performance. +** The few cases that require local variables are broken out into a separate +** routine so that in most cases the overhead of moving the stack pointer +** is avoided. */ +static u32 SQLITE_NOINLINE serialGet( + const unsigned char *buf, /* Buffer to deserialize from */ + u32 serial_type, /* Serial type to deserialize */ + Mem *pMem /* Memory cell to write value into */ +){ + u64 x = FOUR_BYTE_UINT(buf); + u32 y = FOUR_BYTE_UINT(buf+4); + x = (x<<32) + y; + if( serial_type==6 ){ + /* EVIDENCE-OF: R-29851-52272 Value is a big-endian 64-bit + ** twos-complement integer. */ + pMem->u.i = *(i64*)&x; + pMem->flags = MEM_Int; + testcase( pMem->u.i<0 ); + }else{ + /* EVIDENCE-OF: R-57343-49114 Value is a big-endian IEEE 754-2008 64-bit + ** floating point number. */ +#if !defined(NDEBUG) && !defined(SQLITE_OMIT_FLOATING_POINT) + /* Verify that integers and floating point values use the same + ** byte order. Or, that if SQLITE_MIXED_ENDIAN_64BIT_FLOAT is + ** defined that 64-bit floating point values really are mixed + ** endian. + */ + static const u64 t1 = ((u64)0x3ff00000)<<32; + static const double r1 = 1.0; + u64 t2 = t1; + swapMixedEndianFloat(t2); + assert( sizeof(r1)==sizeof(t2) && memcmp(&r1, &t2, sizeof(r1))==0 ); +#endif + assert( sizeof(x)==8 && sizeof(pMem->u.r)==8 ); + swapMixedEndianFloat(x); + memcpy(&pMem->u.r, &x, sizeof(x)); + pMem->flags = sqlite3IsNaN(pMem->u.r) ? MEM_Null : MEM_Real; + } + return 8; +} SQLITE_PRIVATE u32 sqlite3VdbeSerialGet( const unsigned char *buf, /* Buffer to deserialize from */ u32 serial_type, /* Serial type to deserialize */ Mem *pMem /* Memory cell to write value into */ ){ - u64 x; - u32 y; switch( serial_type ){ case 10: /* Reserved for future use */ case 11: /* Reserved for future use */ - case 0: { /* NULL */ + case 0: { /* Null */ + /* EVIDENCE-OF: R-24078-09375 Value is a NULL. */ pMem->flags = MEM_Null; break; } - case 1: { /* 1-byte signed integer */ + case 1: { + /* EVIDENCE-OF: R-44885-25196 Value is an 8-bit twos-complement + ** integer. */ pMem->u.i = ONE_BYTE_INT(buf); pMem->flags = MEM_Int; testcase( pMem->u.i<0 ); return 1; } case 2: { /* 2-byte signed integer */ + /* EVIDENCE-OF: R-49794-35026 Value is a big-endian 16-bit + ** twos-complement integer. */ pMem->u.i = TWO_BYTE_INT(buf); pMem->flags = MEM_Int; testcase( pMem->u.i<0 ); return 2; } case 3: { /* 3-byte signed integer */ + /* EVIDENCE-OF: R-37839-54301 Value is a big-endian 24-bit + ** twos-complement integer. */ pMem->u.i = THREE_BYTE_INT(buf); pMem->flags = MEM_Int; testcase( pMem->u.i<0 ); return 3; } case 4: { /* 4-byte signed integer */ - y = FOUR_BYTE_UINT(buf); - pMem->u.i = (i64)*(int*)&y; + /* EVIDENCE-OF: R-01849-26079 Value is a big-endian 32-bit + ** twos-complement integer. */ + pMem->u.i = FOUR_BYTE_INT(buf); +#ifdef __HP_cc + /* Work around a sign-extension bug in the HP compiler for HP/UX */ + if( buf[0]&0x80 ) pMem->u.i |= 0xffffffff80000000LL; +#endif pMem->flags = MEM_Int; testcase( pMem->u.i<0 ); return 4; } case 5: { /* 6-byte signed integer */ + /* EVIDENCE-OF: R-50385-09674 Value is a big-endian 48-bit + ** twos-complement integer. */ pMem->u.i = FOUR_BYTE_UINT(buf+2) + (((i64)1)<<32)*TWO_BYTE_INT(buf); pMem->flags = MEM_Int; testcase( pMem->u.i<0 ); @@ -64726,52 +70680,32 @@ SQLITE_PRIVATE u32 sqlite3VdbeSerialGet( } case 6: /* 8-byte signed integer */ case 7: { /* IEEE floating point */ -#if !defined(NDEBUG) && !defined(SQLITE_OMIT_FLOATING_POINT) - /* Verify that integers and floating point values use the same - ** byte order. Or, that if SQLITE_MIXED_ENDIAN_64BIT_FLOAT is - ** defined that 64-bit floating point values really are mixed - ** endian. - */ - static const u64 t1 = ((u64)0x3ff00000)<<32; - static const double r1 = 1.0; - u64 t2 = t1; - swapMixedEndianFloat(t2); - assert( sizeof(r1)==sizeof(t2) && memcmp(&r1, &t2, sizeof(r1))==0 ); -#endif - x = FOUR_BYTE_UINT(buf); - y = FOUR_BYTE_UINT(buf+4); - x = (x<<32) | y; - if( serial_type==6 ){ - pMem->u.i = *(i64*)&x; - pMem->flags = MEM_Int; - testcase( pMem->u.i<0 ); - }else{ - assert( sizeof(x)==8 && sizeof(pMem->r)==8 ); - swapMixedEndianFloat(x); - memcpy(&pMem->r, &x, sizeof(x)); - pMem->flags = sqlite3IsNaN(pMem->r) ? MEM_Null : MEM_Real; - } - return 8; + /* These use local variables, so do them in a separate routine + ** to avoid having to move the frame pointer in the common case */ + return serialGet(buf,serial_type,pMem); } case 8: /* Integer 0 */ case 9: { /* Integer 1 */ + /* EVIDENCE-OF: R-12976-22893 Value is the integer 0. */ + /* EVIDENCE-OF: R-18143-12121 Value is the integer 1. */ pMem->u.i = serial_type-8; pMem->flags = MEM_Int; return 0; } default: { + /* EVIDENCE-OF: R-14606-31564 Value is a BLOB that is (N-12)/2 bytes in + ** length. + ** EVIDENCE-OF: R-28401-00140 Value is a string in the text encoding and + ** (N-13)/2 bytes in length. */ static const u16 aFlag[] = { MEM_Blob|MEM_Ephem, MEM_Str|MEM_Ephem }; - u32 len = (serial_type-12)/2; pMem->z = (char *)buf; - pMem->n = len; - pMem->xDel = 0; + pMem->n = (serial_type-12)/2; pMem->flags = aFlag[serial_type&1]; - return len; + return pMem->n; } } return 0; } - /* ** This routine is used to allocate sufficient space for an UnpackedRecord ** structure large enough to be used with sqlite3VdbeRecordUnpack() if @@ -64841,17 +70775,17 @@ SQLITE_PRIVATE void sqlite3VdbeRecordUnpack( idx = getVarint32(aKey, szHdr); d = szHdr; u = 0; - while( idxnField && d<=nKey ){ + while( idxenc = pKeyInfo->enc; pMem->db = pKeyInfo->db; /* pMem->flags = 0; // sqlite3VdbeSerialGet() will set this for us */ - pMem->zMalloc = 0; + pMem->szMalloc = 0; d += sqlite3VdbeSerialGet(&aKey[d], serial_type, pMem); pMem++; - u++; + if( (++u)>=p->nField ) break; } assert( u<=pKeyInfo->nField + 1 ); p->nField = u; @@ -64865,10 +70799,14 @@ SQLITE_PRIVATE void sqlite3VdbeRecordUnpack( ** sqlite3VdbeSerialGet() and sqlite3MemCompare() functions. It is used ** in assert() statements to ensure that the optimized code in ** sqlite3VdbeRecordCompare() returns results with these two primitives. +** +** Return true if the result of comparison is equivalent to desiredResult. +** Return false if there is a disagreement. */ static int vdbeRecordCompareDebug( int nKey1, const void *pKey1, /* Left key */ - const UnpackedRecord *pPKey2 /* Right key */ + const UnpackedRecord *pPKey2, /* Right key */ + int desiredResult /* Correct answer */ ){ u32 d1; /* Offset into aKey[] of next data element */ u32 idx1; /* Offset into aKey[] of next header element */ @@ -64880,10 +70818,11 @@ static int vdbeRecordCompareDebug( Mem mem1; pKeyInfo = pPKey2->pKeyInfo; + if( pKeyInfo->db==0 ) return 1; mem1.enc = pKeyInfo->enc; mem1.db = pKeyInfo->db; /* mem1.flags = 0; // Will be initialized by sqlite3VdbeSerialGet() */ - VVA_ONLY( mem1.zMalloc = 0; ) /* Only needed by assert() statements */ + VVA_ONLY( mem1.szMalloc = 0; ) /* Only needed by assert() statements */ /* Compilers may complain that mem1.u.i is potentially uninitialized. ** We could initialize it, as shown here, to silence those complaints. @@ -64895,6 +70834,7 @@ static int vdbeRecordCompareDebug( /* mem1.u.i = 0; // not needed, here to silence compiler warning */ idx1 = getVarint32(aKey1, szHdr1); + if( szHdr1>98307 ) return SQLITE_CORRUPT; d1 = szHdr1; assert( pKeyInfo->nField+pKeyInfo->nXField>=pPKey2->nField || CORRUPT_DB ); assert( pKeyInfo->aSortOrder!=0 ); @@ -64926,11 +70866,11 @@ static int vdbeRecordCompareDebug( */ rc = sqlite3MemCompare(&mem1, &pPKey2->aMem[i], pKeyInfo->aColl[i]); if( rc!=0 ){ - assert( mem1.zMalloc==0 ); /* See comment below */ + assert( mem1.szMalloc==0 ); /* See comment below */ if( pKeyInfo->aSortOrder[i] ){ rc = -rc; /* Invert the result for DESC sort order. */ } - return rc; + goto debugCompareEnd; } i++; }while( idx1nField ); @@ -64939,15 +70879,59 @@ static int vdbeRecordCompareDebug( ** the following assert(). If the assert() fails, it indicates a ** memory leak and a need to call sqlite3VdbeMemRelease(&mem1). */ - assert( mem1.zMalloc==0 ); + assert( mem1.szMalloc==0 ); /* rc==0 here means that one of the keys ran out of fields and - ** all the fields up to that point were equal. Return the the default_rc + ** all the fields up to that point were equal. Return the default_rc ** value. */ - return pPKey2->default_rc; + rc = pPKey2->default_rc; + +debugCompareEnd: + if( desiredResult==0 && rc==0 ) return 1; + if( desiredResult<0 && rc<0 ) return 1; + if( desiredResult>0 && rc>0 ) return 1; + if( CORRUPT_DB ) return 1; + if( pKeyInfo->db->mallocFailed ) return 1; + return 0; } #endif +#if SQLITE_DEBUG +/* +** Count the number of fields (a.k.a. columns) in the record given by +** pKey,nKey. The verify that this count is less than or equal to the +** limit given by pKeyInfo->nField + pKeyInfo->nXField. +** +** If this constraint is not satisfied, it means that the high-speed +** vdbeRecordCompareInt() and vdbeRecordCompareString() routines will +** not work correctly. If this assert() ever fires, it probably means +** that the KeyInfo.nField or KeyInfo.nXField values were computed +** incorrectly. +*/ +static void vdbeAssertFieldCountWithinLimits( + int nKey, const void *pKey, /* The record to verify */ + const KeyInfo *pKeyInfo /* Compare size with this KeyInfo */ +){ + int nField = 0; + u32 szHdr; + u32 idx; + u32 notUsed; + const unsigned char *aKey = (const unsigned char*)pKey; + + if( CORRUPT_DB ) return; + idx = getVarint32(aKey, szHdr); + assert( nKey>=0 ); + assert( szHdr<=(u32)nKey ); + while( idxnField+pKeyInfo->nXField ); +} +#else +# define vdbeAssertFieldCountWithinLimits(A,B,C) +#endif + /* ** Both *pMem1 and *pMem2 contain string values. Compare the two values ** using the collation sequence pColl. As usual, return a negative , zero @@ -64957,7 +70941,8 @@ static int vdbeRecordCompareDebug( static int vdbeCompareMemString( const Mem *pMem1, const Mem *pMem2, - const CollSeq *pColl + const CollSeq *pColl, + u8 *prcErr /* If an OOM occurs, set to SQLITE_NOMEM */ ){ if( pMem1->enc==pColl->enc ){ /* The strings are already in the correct encoding. Call the @@ -64969,8 +70954,8 @@ static int vdbeCompareMemString( int n1, n2; Mem c1; Mem c2; - memset(&c1, 0, sizeof(c1)); - memset(&c2, 0, sizeof(c2)); + sqlite3VdbeMemInit(&c1, pMem1->db, MEM_Null); + sqlite3VdbeMemInit(&c2, pMem1->db, MEM_Null); sqlite3VdbeMemShallowCopy(&c1, pMem1, MEM_Ephem); sqlite3VdbeMemShallowCopy(&c2, pMem2, MEM_Ephem); v1 = sqlite3ValueText((sqlite3_value*)&c1, pColl->enc); @@ -64980,10 +70965,51 @@ static int vdbeCompareMemString( rc = pColl->xCmp(pColl->pUser, n1, v1, n2, v2); sqlite3VdbeMemRelease(&c1); sqlite3VdbeMemRelease(&c2); + if( (v1==0 || v2==0) && prcErr ) *prcErr = SQLITE_NOMEM; return rc; } } +/* +** Compare two blobs. Return negative, zero, or positive if the first +** is less than, equal to, or greater than the second, respectively. +** If one blob is a prefix of the other, then the shorter is the lessor. +*/ +static SQLITE_NOINLINE int sqlite3BlobCompare(const Mem *pB1, const Mem *pB2){ + int c = memcmp(pB1->z, pB2->z, pB1->n>pB2->n ? pB2->n : pB1->n); + if( c ) return c; + return pB1->n - pB2->n; +} + +/* +** Do a comparison between a 64-bit signed integer and a 64-bit floating-point +** number. Return negative, zero, or positive if the first (i64) is less than, +** equal to, or greater than the second (double). +*/ +static int sqlite3IntFloatCompare(i64 i, double r){ + if( sizeof(LONGDOUBLE_TYPE)>8 ){ + LONGDOUBLE_TYPE x = (LONGDOUBLE_TYPE)i; + if( xr ) return +1; + return 0; + }else{ + i64 y; + double s; + if( r<-9223372036854775808.0 ) return +1; + if( r>9223372036854775807.0 ) return -1; + y = (i64)r; + if( iy ){ + if( y==SMALLEST_INT64 && r>0.0 ) return -1; + return +1; + } + s = (double)i; + if( sr ) return +1; + return 0; + } +} + /* ** Compare the values contained by the two memory cells, returning ** negative, zero or positive if pMem1 is less than, equal to, or greater @@ -64994,7 +71020,6 @@ static int vdbeCompareMemString( ** Two NULL values are considered equal by this function. */ SQLITE_PRIVATE int sqlite3MemCompare(const Mem *pMem1, const Mem *pMem2, const CollSeq *pColl){ - int rc; int f1, f2; int combined_flags; @@ -65010,34 +71035,34 @@ SQLITE_PRIVATE int sqlite3MemCompare(const Mem *pMem1, const Mem *pMem2, const C return (f2&MEM_Null) - (f1&MEM_Null); } - /* If one value is a number and the other is not, the number is less. - ** If both are numbers, compare as reals if one is a real, or as integers - ** if both values are integers. + /* At least one of the two values is a number */ if( combined_flags&(MEM_Int|MEM_Real) ){ - double r1, r2; if( (f1 & f2 & MEM_Int)!=0 ){ if( pMem1->u.i < pMem2->u.i ) return -1; - if( pMem1->u.i > pMem2->u.i ) return 1; + if( pMem1->u.i > pMem2->u.i ) return +1; return 0; } + if( (f1 & f2 & MEM_Real)!=0 ){ + if( pMem1->u.r < pMem2->u.r ) return -1; + if( pMem1->u.r > pMem2->u.r ) return +1; + return 0; + } + if( (f1&MEM_Int)!=0 ){ + if( (f2&MEM_Real)!=0 ){ + return sqlite3IntFloatCompare(pMem1->u.i, pMem2->u.r); + }else{ + return -1; + } + } if( (f1&MEM_Real)!=0 ){ - r1 = pMem1->r; - }else if( (f1&MEM_Int)!=0 ){ - r1 = (double)pMem1->u.i; - }else{ - return 1; + if( (f2&MEM_Int)!=0 ){ + return -sqlite3IntFloatCompare(pMem2->u.i, pMem1->u.r); + }else{ + return -1; + } } - if( (f2&MEM_Real)!=0 ){ - r2 = pMem2->r; - }else if( (f2&MEM_Int)!=0 ){ - r2 = (double)pMem2->u.i; - }else{ - return -1; - } - if( r1r2 ) return 1; - return 0; + return +1; } /* If one value is a string and the other is a blob, the string is less. @@ -65051,7 +71076,7 @@ SQLITE_PRIVATE int sqlite3MemCompare(const Mem *pMem1, const Mem *pMem2, const C return -1; } - assert( pMem1->enc==pMem2->enc ); + assert( pMem1->enc==pMem2->enc || pMem1->db->mallocFailed ); assert( pMem1->enc==SQLITE_UTF8 || pMem1->enc==SQLITE_UTF16LE || pMem1->enc==SQLITE_UTF16BE ); @@ -65062,18 +71087,14 @@ SQLITE_PRIVATE int sqlite3MemCompare(const Mem *pMem1, const Mem *pMem2, const C assert( !pColl || pColl->xCmp ); if( pColl ){ - return vdbeCompareMemString(pMem1, pMem2, pColl); + return vdbeCompareMemString(pMem1, pMem2, pColl, 0); } /* If a NULL pointer was passed as the collate function, fall through ** to the blob case and use memcmp(). */ } /* Both values must be blobs. Compare using memcmp(). */ - rc = memcmp(pMem1->z, pMem2->z, (pMem1->n>pMem2->n)?pMem2->n:pMem1->n); - if( rc==0 ){ - rc = pMem1->n - pMem2->n; - } - return rc; + return sqlite3BlobCompare(pMem1, pMem2); } @@ -65123,7 +71144,7 @@ static i64 vdbeRecordDecodeInt(u32 serial_type, const u8 *aKey){ ** specified by {nKey1, pKey1} and pPKey2. It returns a negative, zero ** or positive integer if key1 is less than, equal to or ** greater than key2. The {nKey1, pKey1} key must be a blob -** created by th OP_MakeRecord opcode of the VDBE. The pPKey2 +** created by the OP_MakeRecord opcode of the VDBE. The pPKey2 ** key must be a parsed key such as obtained from ** sqlite3VdbeParseRecord. ** @@ -65134,10 +71155,12 @@ static i64 vdbeRecordDecodeInt(u32 serial_type, const u8 *aKey){ ** fields that appear in both keys are equal, then pPKey2->default_rc is ** returned. ** -** If database corruption is discovered, set pPKey2->isCorrupt to non-zero -** and return 0. +** If database corruption is discovered, set pPKey2->errCode to +** SQLITE_CORRUPT and return 0. If an OOM error is encountered, +** pPKey2->errCode is set to SQLITE_NOMEM and, if it is not NULL, the +** malloc-failed flag set on database handle (pPKey2->pKeyInfo->db). */ -SQLITE_PRIVATE int sqlite3VdbeRecordCompare( +SQLITE_PRIVATE int sqlite3VdbeRecordCompareWithSkip( int nKey1, const void *pKey1, /* Left key */ UnpackedRecord *pPKey2, /* Right key */ int bSkip /* If true, skip the first field */ @@ -65166,13 +71189,13 @@ SQLITE_PRIVATE int sqlite3VdbeRecordCompare( idx1 = getVarint32(aKey1, szHdr1); d1 = szHdr1; if( d1>(unsigned)nKey1 ){ - pPKey2->isCorrupt = (u8)SQLITE_CORRUPT_BKPT; + pPKey2->errCode = (u8)SQLITE_CORRUPT_BKPT; return 0; /* Corruption */ } i = 0; } - VVA_ONLY( mem1.zMalloc = 0; ) /* Only needed by assert() statements */ + VVA_ONLY( mem1.szMalloc = 0; ) /* Only needed by assert() statements */ assert( pPKey2->pKeyInfo->nField+pPKey2->pKeyInfo->nXField>=pPKey2->nField || CORRUPT_DB ); assert( pPKey2->pKeyInfo->aSortOrder!=0 ); @@ -65185,18 +71208,13 @@ SQLITE_PRIVATE int sqlite3VdbeRecordCompare( if( pRhs->flags & MEM_Int ){ serial_type = aKey1[idx1]; testcase( serial_type==12 ); - if( serial_type>=12 ){ + if( serial_type>=10 ){ rc = +1; }else if( serial_type==0 ){ rc = -1; }else if( serial_type==7 ){ - double rhs = (double)pRhs->u.i; sqlite3VdbeSerialGet(&aKey1[d1], serial_type, &mem1); - if( mem1.rrhs ){ - rc = +1; - } + rc = -sqlite3IntFloatCompare(pRhs->u.i, mem1.u.r); }else{ i64 lhs = vdbeRecordDecodeInt(serial_type, &aKey1[d1]); i64 rhs = pRhs->u.i; @@ -65211,23 +71229,24 @@ SQLITE_PRIVATE int sqlite3VdbeRecordCompare( /* RHS is real */ else if( pRhs->flags & MEM_Real ){ serial_type = aKey1[idx1]; - if( serial_type>=12 ){ + if( serial_type>=10 ){ + /* Serial types 12 or greater are strings and blobs (greater than + ** numbers). Types 10 and 11 are currently "reserved for future + ** use", so it doesn't really matter what the results of comparing + ** them to numberic values are. */ rc = +1; }else if( serial_type==0 ){ rc = -1; }else{ - double rhs = pRhs->r; - double lhs; sqlite3VdbeSerialGet(&aKey1[d1], serial_type, &mem1); if( serial_type==7 ){ - lhs = mem1.r; + if( mem1.u.ru.r ){ + rc = -1; + }else if( mem1.u.r>pRhs->u.r ){ + rc = +1; + } }else{ - lhs = (double)mem1.u.i; - } - if( lhsrhs ){ - rc = +1; + rc = sqlite3IntFloatCompare(mem1.u.i, pRhs->u.r); } } } @@ -65245,14 +71264,16 @@ SQLITE_PRIVATE int sqlite3VdbeRecordCompare( testcase( (d1+mem1.n)==(unsigned)nKey1 ); testcase( (d1+mem1.n+1)==(unsigned)nKey1 ); if( (d1+mem1.n) > (unsigned)nKey1 ){ - pPKey2->isCorrupt = (u8)SQLITE_CORRUPT_BKPT; + pPKey2->errCode = (u8)SQLITE_CORRUPT_BKPT; return 0; /* Corruption */ }else if( pKeyInfo->aColl[i] ){ mem1.enc = pKeyInfo->enc; mem1.db = pKeyInfo->db; mem1.flags = MEM_Str; mem1.z = (char*)&aKey1[d1]; - rc = vdbeCompareMemString(&mem1, pRhs, pKeyInfo->aColl[i]); + rc = vdbeCompareMemString( + &mem1, pRhs, pKeyInfo->aColl[i], &pPKey2->errCode + ); }else{ int nCmp = MIN(mem1.n, pRhs->n); rc = memcmp(&aKey1[d1], pRhs->z, nCmp); @@ -65272,7 +71293,7 @@ SQLITE_PRIVATE int sqlite3VdbeRecordCompare( testcase( (d1+nStr)==(unsigned)nKey1 ); testcase( (d1+nStr+1)==(unsigned)nKey1 ); if( (d1+nStr) > (unsigned)nKey1 ){ - pPKey2->isCorrupt = (u8)SQLITE_CORRUPT_BKPT; + pPKey2->errCode = (u8)SQLITE_CORRUPT_BKPT; return 0; /* Corruption */ }else{ int nCmp = MIN(nStr, pRhs->n); @@ -65292,12 +71313,8 @@ SQLITE_PRIVATE int sqlite3VdbeRecordCompare( if( pKeyInfo->aSortOrder[i] ){ rc = -rc; } - assert( CORRUPT_DB - || (rc<0 && vdbeRecordCompareDebug(nKey1, pKey1, pPKey2)<0) - || (rc>0 && vdbeRecordCompareDebug(nKey1, pKey1, pPKey2)>0) - || pKeyInfo->db->mallocFailed - ); - assert( mem1.zMalloc==0 ); /* See comment below */ + assert( vdbeRecordCompareDebug(nKey1, pKey1, pPKey2, rc) ); + assert( mem1.szMalloc==0 ); /* See comment below */ return rc; } @@ -65310,16 +71327,25 @@ SQLITE_PRIVATE int sqlite3VdbeRecordCompare( /* No memory allocation is ever used on mem1. Prove this using ** the following assert(). If the assert() fails, it indicates a ** memory leak and a need to call sqlite3VdbeMemRelease(&mem1). */ - assert( mem1.zMalloc==0 ); + assert( mem1.szMalloc==0 ); /* rc==0 here means that one or both of the keys ran out of fields and - ** all the fields up to that point were equal. Return the the default_rc + ** all the fields up to that point were equal. Return the default_rc ** value. */ assert( CORRUPT_DB - || pPKey2->default_rc==vdbeRecordCompareDebug(nKey1, pKey1, pPKey2) + || vdbeRecordCompareDebug(nKey1, pKey1, pPKey2, pPKey2->default_rc) + || pKeyInfo->db->mallocFailed ); + pPKey2->eqSeen = 1; return pPKey2->default_rc; } +SQLITE_PRIVATE int sqlite3VdbeRecordCompare( + int nKey1, const void *pKey1, /* Left key */ + UnpackedRecord *pPKey2 /* Right key */ +){ + return sqlite3VdbeRecordCompareWithSkip(nKey1, pKey1, pPKey2, 0); +} + /* ** This function is an optimized version of sqlite3VdbeRecordCompare() @@ -65332,8 +71358,7 @@ SQLITE_PRIVATE int sqlite3VdbeRecordCompare( */ static int vdbeRecordCompareInt( int nKey1, const void *pKey1, /* Left key */ - UnpackedRecord *pPKey2, /* Right key */ - int bSkip /* Ignored */ + UnpackedRecord *pPKey2 /* Right key */ ){ const u8 *aKey = &((const u8*)pKey1)[*(const u8*)pKey1 & 0x3F]; int serial_type = ((const u8*)pKey1)[1]; @@ -65342,9 +71367,8 @@ static int vdbeRecordCompareInt( u64 x; i64 v = pPKey2->aMem[0].u.i; i64 lhs; - UNUSED_PARAMETER(bSkip); - assert( bSkip==0 ); + vdbeAssertFieldCountWithinLimits(nKey1, pKey1, pPKey2->pKeyInfo); assert( (*(u8*)pKey1)<=0x3F || CORRUPT_DB ); switch( serial_type ){ case 1: { /* 1-byte signed integer */ @@ -65394,10 +71418,10 @@ static int vdbeRecordCompareInt( ** (as gcc is clever enough to combine the two like cases). Other ** compilers might be similar. */ case 0: case 7: - return sqlite3VdbeRecordCompare(nKey1, pKey1, pPKey2, 0); + return sqlite3VdbeRecordCompare(nKey1, pKey1, pPKey2); default: - return sqlite3VdbeRecordCompare(nKey1, pKey1, pPKey2, 0); + return sqlite3VdbeRecordCompare(nKey1, pKey1, pPKey2); } if( v>lhs ){ @@ -65407,18 +71431,15 @@ static int vdbeRecordCompareInt( }else if( pPKey2->nField>1 ){ /* The first fields of the two keys are equal. Compare the trailing ** fields. */ - res = sqlite3VdbeRecordCompare(nKey1, pKey1, pPKey2, 1); + res = sqlite3VdbeRecordCompareWithSkip(nKey1, pKey1, pPKey2, 1); }else{ /* The first fields of the two keys are equal and there are no trailing ** fields. Return pPKey2->default_rc in this case. */ res = pPKey2->default_rc; + pPKey2->eqSeen = 1; } - assert( (res==0 && vdbeRecordCompareDebug(nKey1, pKey1, pPKey2)==0) - || (res<0 && vdbeRecordCompareDebug(nKey1, pKey1, pPKey2)<0) - || (res>0 && vdbeRecordCompareDebug(nKey1, pKey1, pPKey2)>0) - || CORRUPT_DB - ); + assert( vdbeRecordCompareDebug(nKey1, pKey1, pPKey2, res) ); return res; } @@ -65430,17 +71451,15 @@ static int vdbeRecordCompareInt( */ static int vdbeRecordCompareString( int nKey1, const void *pKey1, /* Left key */ - UnpackedRecord *pPKey2, /* Right key */ - int bSkip + UnpackedRecord *pPKey2 /* Right key */ ){ const u8 *aKey1 = (const u8*)pKey1; int serial_type; int res; - UNUSED_PARAMETER(bSkip); - assert( bSkip==0 ); + assert( pPKey2->aMem[0].flags & MEM_Str ); + vdbeAssertFieldCountWithinLimits(nKey1, pKey1, pPKey2->pKeyInfo); getVarint32(&aKey1[1], serial_type); - if( serial_type<12 ){ res = pPKey2->r1; /* (pKey1/nKey1) is a number or a null */ }else if( !(serial_type & 0x01) ){ @@ -65452,7 +71471,7 @@ static int vdbeRecordCompareString( nStr = (serial_type-12) / 2; if( (szHdr + nStr) > nKey1 ){ - pPKey2->isCorrupt = (u8)SQLITE_CORRUPT_BKPT; + pPKey2->errCode = (u8)SQLITE_CORRUPT_BKPT; return 0; /* Corruption */ } nCmp = MIN( pPKey2->aMem[0].n, nStr ); @@ -65462,9 +71481,10 @@ static int vdbeRecordCompareString( res = nStr - pPKey2->aMem[0].n; if( res==0 ){ if( pPKey2->nField>1 ){ - res = sqlite3VdbeRecordCompare(nKey1, pKey1, pPKey2, 1); + res = sqlite3VdbeRecordCompareWithSkip(nKey1, pKey1, pPKey2, 1); }else{ res = pPKey2->default_rc; + pPKey2->eqSeen = 1; } }else if( res>0 ){ res = pPKey2->r2; @@ -65478,10 +71498,9 @@ static int vdbeRecordCompareString( } } - assert( (res==0 && vdbeRecordCompareDebug(nKey1, pKey1, pPKey2)==0) - || (res<0 && vdbeRecordCompareDebug(nKey1, pKey1, pPKey2)<0) - || (res>0 && vdbeRecordCompareDebug(nKey1, pKey1, pPKey2)>0) + assert( vdbeRecordCompareDebug(nKey1, pKey1, pPKey2, res) || CORRUPT_DB + || pPKey2->pKeyInfo->db->mallocFailed ); return res; } @@ -65545,8 +71564,6 @@ SQLITE_PRIVATE int sqlite3VdbeIdxRowid(sqlite3 *db, BtCursor *pCur, i64 *rowid){ u32 lenRowid; /* Size of the rowid */ Mem m, v; - UNUSED_PARAMETER(db); - /* Get the size of the index entry. Only indices entries of less ** than 2GiB are support - anything large must be database corruption. ** Any corruption is detected in sqlite3BtreeParseCellPtr(), though, so @@ -65558,7 +71575,7 @@ SQLITE_PRIVATE int sqlite3VdbeIdxRowid(sqlite3 *db, BtCursor *pCur, i64 *rowid){ assert( (nCellKey & SQLITE_MAX_U32)==(u64)nCellKey ); /* Read in the complete content of the index entry */ - memset(&m, 0, sizeof(m)); + sqlite3VdbeMemInit(&m, db, 0); rc = sqlite3VdbeMemFromBtree(pCur, 0, (u32)nCellKey, 1, &m); if( rc ){ return rc; @@ -65586,7 +71603,7 @@ SQLITE_PRIVATE int sqlite3VdbeIdxRowid(sqlite3 *db, BtCursor *pCur, i64 *rowid){ if( unlikely(typeRowid<1 || typeRowid>9 || typeRowid==7) ){ goto idx_rowid_corruption; } - lenRowid = sqlite3VdbeSerialTypeLen(typeRowid); + lenRowid = sqlite3SmallTypeSizes[typeRowid]; testcase( (u32)m.n==szHdr+lenRowid ); if( unlikely((u32)m.npCursor; + BtCursor *pCur; Mem m; + assert( pC->eCurType==CURTYPE_BTREE ); + pCur = pC->uc.pCursor; assert( sqlite3BtreeCursorIsValid(pCur) ); VVA_ONLY(rc =) sqlite3BtreeKeySize(pCur, &nCellKey); assert( rc==SQLITE_OK ); /* pCur is always valid so KeySize cannot fail */ @@ -65636,12 +71656,12 @@ SQLITE_PRIVATE int sqlite3VdbeIdxKeyCompare( *res = 0; return SQLITE_CORRUPT_BKPT; } - memset(&m, 0, sizeof(m)); - rc = sqlite3VdbeMemFromBtree(pC->pCursor, 0, (u32)nCellKey, 1, &m); + sqlite3VdbeMemInit(&m, db, 0); + rc = sqlite3VdbeMemFromBtree(pCur, 0, (u32)nCellKey, 1, &m); if( rc ){ return rc; } - *res = sqlite3VdbeRecordCompare(m.n, m.z, pUnpacked, 0); + *res = sqlite3VdbeRecordCompare(m.n, m.z, pUnpacked); sqlite3VdbeMemRelease(&m); return SQLITE_OK; } @@ -65758,6 +71778,8 @@ SQLITE_PRIVATE void sqlite3VtabImportErrmsg(Vdbe *p, sqlite3_vtab *pVtab){ ** This file contains code use to implement APIs that are part of the ** VDBE. */ +/* #include "sqliteInt.h" */ +/* #include "vdbeInt.h" */ #ifndef SQLITE_OMIT_DEPRECATED /* @@ -65768,7 +71790,7 @@ SQLITE_PRIVATE void sqlite3VtabImportErrmsg(Vdbe *p, sqlite3_vtab *pVtab){ ** collating sequences are registered or if an authorizer function is ** added or changed. */ -SQLITE_API int sqlite3_expired(sqlite3_stmt *pStmt){ +SQLITE_API int SQLITE_STDCALL sqlite3_expired(sqlite3_stmt *pStmt){ Vdbe *p = (Vdbe*)pStmt; return p==0 || p->expired; } @@ -65796,6 +71818,31 @@ static int vdbeSafetyNotNull(Vdbe *p){ } } +#ifndef SQLITE_OMIT_TRACE +/* +** Invoke the profile callback. This routine is only called if we already +** know that the profile callback is defined and needs to be invoked. +*/ +static SQLITE_NOINLINE void invokeProfileCallback(sqlite3 *db, Vdbe *p){ + sqlite3_int64 iNow; + assert( p->startTime>0 ); + assert( db->xProfile!=0 ); + assert( db->init.busy==0 ); + assert( p->zSql!=0 ); + sqlite3OsCurrentTimeInt64(db->pVfs, &iNow); + db->xProfile(db->pProfileArg, p->zSql, (iNow - p->startTime)*1000000); + p->startTime = 0; +} +/* +** The checkProfileCallback(DB,P) macro checks to see if a profile callback +** is needed, and it invokes the callback if it is needed. +*/ +# define checkProfileCallback(DB,P) \ + if( ((P)->startTime)>0 ){ invokeProfileCallback(DB,P); } +#else +# define checkProfileCallback(DB,P) /*no-op*/ +#endif + /* ** The following routine destroys a virtual machine that is created by ** the sqlite3_compile() routine. The integer returned is an SQLITE_ @@ -65805,7 +71852,7 @@ static int vdbeSafetyNotNull(Vdbe *p){ ** This routine sets the error code and string returned by ** sqlite3_errcode(), sqlite3_errmsg() and sqlite3_errmsg16(). */ -SQLITE_API int sqlite3_finalize(sqlite3_stmt *pStmt){ +SQLITE_API int SQLITE_STDCALL sqlite3_finalize(sqlite3_stmt *pStmt){ int rc; if( pStmt==0 ){ /* IMPLEMENTATION-OF: R-57228-12904 Invoking sqlite3_finalize() on a NULL @@ -65816,6 +71863,7 @@ SQLITE_API int sqlite3_finalize(sqlite3_stmt *pStmt){ sqlite3 *db = v->db; if( vdbeSafety(v) ) return SQLITE_MISUSE_BKPT; sqlite3_mutex_enter(db->mutex); + checkProfileCallback(db, v); rc = sqlite3VdbeFinalize(v); rc = sqlite3ApiExit(db, rc); sqlite3LeaveMutexAndCloseZombie(db); @@ -65831,18 +71879,20 @@ SQLITE_API int sqlite3_finalize(sqlite3_stmt *pStmt){ ** This routine sets the error code and string returned by ** sqlite3_errcode(), sqlite3_errmsg() and sqlite3_errmsg16(). */ -SQLITE_API int sqlite3_reset(sqlite3_stmt *pStmt){ +SQLITE_API int SQLITE_STDCALL sqlite3_reset(sqlite3_stmt *pStmt){ int rc; if( pStmt==0 ){ rc = SQLITE_OK; }else{ Vdbe *v = (Vdbe*)pStmt; - sqlite3_mutex_enter(v->db->mutex); + sqlite3 *db = v->db; + sqlite3_mutex_enter(db->mutex); + checkProfileCallback(db, v); rc = sqlite3VdbeReset(v); sqlite3VdbeRewind(v); - assert( (rc & (v->db->errMask))==rc ); - rc = sqlite3ApiExit(v->db, rc); - sqlite3_mutex_leave(v->db->mutex); + assert( (rc & (db->errMask))==rc ); + rc = sqlite3ApiExit(db, rc); + sqlite3_mutex_leave(db->mutex); } return rc; } @@ -65850,7 +71900,7 @@ SQLITE_API int sqlite3_reset(sqlite3_stmt *pStmt){ /* ** Set all the parameters in the compiled SQL statement to NULL. */ -SQLITE_API int sqlite3_clear_bindings(sqlite3_stmt *pStmt){ +SQLITE_API int SQLITE_STDCALL sqlite3_clear_bindings(sqlite3_stmt *pStmt){ int i; int rc = SQLITE_OK; Vdbe *p = (Vdbe*)pStmt; @@ -65874,46 +71924,56 @@ SQLITE_API int sqlite3_clear_bindings(sqlite3_stmt *pStmt){ ** The following routines extract information from a Mem or sqlite3_value ** structure. */ -SQLITE_API const void *sqlite3_value_blob(sqlite3_value *pVal){ +SQLITE_API const void *SQLITE_STDCALL sqlite3_value_blob(sqlite3_value *pVal){ Mem *p = (Mem*)pVal; if( p->flags & (MEM_Blob|MEM_Str) ){ - sqlite3VdbeMemExpandBlob(p); + if( sqlite3VdbeMemExpandBlob(p)!=SQLITE_OK ){ + assert( p->flags==MEM_Null && p->z==0 ); + return 0; + } p->flags |= MEM_Blob; return p->n ? p->z : 0; }else{ return sqlite3_value_text(pVal); } } -SQLITE_API int sqlite3_value_bytes(sqlite3_value *pVal){ +SQLITE_API int SQLITE_STDCALL sqlite3_value_bytes(sqlite3_value *pVal){ return sqlite3ValueBytes(pVal, SQLITE_UTF8); } -SQLITE_API int sqlite3_value_bytes16(sqlite3_value *pVal){ +SQLITE_API int SQLITE_STDCALL sqlite3_value_bytes16(sqlite3_value *pVal){ return sqlite3ValueBytes(pVal, SQLITE_UTF16NATIVE); } -SQLITE_API double sqlite3_value_double(sqlite3_value *pVal){ +SQLITE_API double SQLITE_STDCALL sqlite3_value_double(sqlite3_value *pVal){ return sqlite3VdbeRealValue((Mem*)pVal); } -SQLITE_API int sqlite3_value_int(sqlite3_value *pVal){ +SQLITE_API int SQLITE_STDCALL sqlite3_value_int(sqlite3_value *pVal){ return (int)sqlite3VdbeIntValue((Mem*)pVal); } -SQLITE_API sqlite_int64 sqlite3_value_int64(sqlite3_value *pVal){ +SQLITE_API sqlite_int64 SQLITE_STDCALL sqlite3_value_int64(sqlite3_value *pVal){ return sqlite3VdbeIntValue((Mem*)pVal); } -SQLITE_API const unsigned char *sqlite3_value_text(sqlite3_value *pVal){ +SQLITE_API unsigned int SQLITE_STDCALL sqlite3_value_subtype(sqlite3_value *pVal){ + return ((Mem*)pVal)->eSubtype; +} +SQLITE_API const unsigned char *SQLITE_STDCALL sqlite3_value_text(sqlite3_value *pVal){ return (const unsigned char *)sqlite3ValueText(pVal, SQLITE_UTF8); } #ifndef SQLITE_OMIT_UTF16 -SQLITE_API const void *sqlite3_value_text16(sqlite3_value* pVal){ +SQLITE_API const void *SQLITE_STDCALL sqlite3_value_text16(sqlite3_value* pVal){ return sqlite3ValueText(pVal, SQLITE_UTF16NATIVE); } -SQLITE_API const void *sqlite3_value_text16be(sqlite3_value *pVal){ +SQLITE_API const void *SQLITE_STDCALL sqlite3_value_text16be(sqlite3_value *pVal){ return sqlite3ValueText(pVal, SQLITE_UTF16BE); } -SQLITE_API const void *sqlite3_value_text16le(sqlite3_value *pVal){ +SQLITE_API const void *SQLITE_STDCALL sqlite3_value_text16le(sqlite3_value *pVal){ return sqlite3ValueText(pVal, SQLITE_UTF16LE); } #endif /* SQLITE_OMIT_UTF16 */ -SQLITE_API int sqlite3_value_type(sqlite3_value* pVal){ +/* EVIDENCE-OF: R-12793-43283 Every value in SQLite has one of five +** fundamental datatypes: 64-bit signed integer 64-bit IEEE floating +** point number string BLOB NULL +*/ +SQLITE_API int SQLITE_STDCALL sqlite3_value_type(sqlite3_value* pVal){ static const u8 aType[] = { SQLITE_BLOB, /* 0x00 */ SQLITE_NULL, /* 0x01 */ @@ -65951,13 +72011,46 @@ SQLITE_API int sqlite3_value_type(sqlite3_value* pVal){ return aType[pVal->flags&MEM_AffMask]; } +/* Make a copy of an sqlite3_value object +*/ +SQLITE_API sqlite3_value *SQLITE_STDCALL sqlite3_value_dup(const sqlite3_value *pOrig){ + sqlite3_value *pNew; + if( pOrig==0 ) return 0; + pNew = sqlite3_malloc( sizeof(*pNew) ); + if( pNew==0 ) return 0; + memset(pNew, 0, sizeof(*pNew)); + memcpy(pNew, pOrig, MEMCELLSIZE); + pNew->flags &= ~MEM_Dyn; + pNew->db = 0; + if( pNew->flags&(MEM_Str|MEM_Blob) ){ + pNew->flags &= ~(MEM_Static|MEM_Dyn); + pNew->flags |= MEM_Ephem; + if( sqlite3VdbeMemMakeWriteable(pNew)!=SQLITE_OK ){ + sqlite3ValueFree(pNew); + pNew = 0; + } + } + return pNew; +} + +/* Destroy an sqlite3_value object previously obtained from +** sqlite3_value_dup(). +*/ +SQLITE_API void SQLITE_STDCALL sqlite3_value_free(sqlite3_value *pOld){ + sqlite3ValueFree(pOld); +} + + /**************************** sqlite3_result_ ******************************* ** The following routines are used by user-defined functions to specify ** the function result. ** -** The setStrOrError() funtion calls sqlite3VdbeMemSetStr() to store the +** The setStrOrError() function calls sqlite3VdbeMemSetStr() to store the ** result as a string or blob but if the string or blob is too large, it ** then sets the error code to SQLITE_TOOBIG +** +** The invokeValueDestructor(P,X) routine invokes destructor function X() +** on value P is not going to be used and need to be destroyed. */ static void setResultStrOrError( sqlite3_context *pCtx, /* Function context */ @@ -65966,121 +72059,183 @@ static void setResultStrOrError( u8 enc, /* Encoding of z. 0 for BLOBs */ void (*xDel)(void*) /* Destructor function */ ){ - if( sqlite3VdbeMemSetStr(&pCtx->s, z, n, enc, xDel)==SQLITE_TOOBIG ){ + if( sqlite3VdbeMemSetStr(pCtx->pOut, z, n, enc, xDel)==SQLITE_TOOBIG ){ sqlite3_result_error_toobig(pCtx); } } -SQLITE_API void sqlite3_result_blob( +static int invokeValueDestructor( + const void *p, /* Value to destroy */ + void (*xDel)(void*), /* The destructor */ + sqlite3_context *pCtx /* Set a SQLITE_TOOBIG error if no NULL */ +){ + assert( xDel!=SQLITE_DYNAMIC ); + if( xDel==0 ){ + /* noop */ + }else if( xDel==SQLITE_TRANSIENT ){ + /* noop */ + }else{ + xDel((void*)p); + } + if( pCtx ) sqlite3_result_error_toobig(pCtx); + return SQLITE_TOOBIG; +} +SQLITE_API void SQLITE_STDCALL sqlite3_result_blob( sqlite3_context *pCtx, const void *z, int n, void (*xDel)(void *) ){ assert( n>=0 ); - assert( sqlite3_mutex_held(pCtx->s.db->mutex) ); + assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) ); setResultStrOrError(pCtx, z, n, 0, xDel); } -SQLITE_API void sqlite3_result_double(sqlite3_context *pCtx, double rVal){ - assert( sqlite3_mutex_held(pCtx->s.db->mutex) ); - sqlite3VdbeMemSetDouble(&pCtx->s, rVal); +SQLITE_API void SQLITE_STDCALL sqlite3_result_blob64( + sqlite3_context *pCtx, + const void *z, + sqlite3_uint64 n, + void (*xDel)(void *) +){ + assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) ); + assert( xDel!=SQLITE_DYNAMIC ); + if( n>0x7fffffff ){ + (void)invokeValueDestructor(z, xDel, pCtx); + }else{ + setResultStrOrError(pCtx, z, (int)n, 0, xDel); + } } -SQLITE_API void sqlite3_result_error(sqlite3_context *pCtx, const char *z, int n){ - assert( sqlite3_mutex_held(pCtx->s.db->mutex) ); +SQLITE_API void SQLITE_STDCALL sqlite3_result_double(sqlite3_context *pCtx, double rVal){ + assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) ); + sqlite3VdbeMemSetDouble(pCtx->pOut, rVal); +} +SQLITE_API void SQLITE_STDCALL sqlite3_result_error(sqlite3_context *pCtx, const char *z, int n){ + assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) ); pCtx->isError = SQLITE_ERROR; pCtx->fErrorOrAux = 1; - sqlite3VdbeMemSetStr(&pCtx->s, z, n, SQLITE_UTF8, SQLITE_TRANSIENT); + sqlite3VdbeMemSetStr(pCtx->pOut, z, n, SQLITE_UTF8, SQLITE_TRANSIENT); } #ifndef SQLITE_OMIT_UTF16 -SQLITE_API void sqlite3_result_error16(sqlite3_context *pCtx, const void *z, int n){ - assert( sqlite3_mutex_held(pCtx->s.db->mutex) ); +SQLITE_API void SQLITE_STDCALL sqlite3_result_error16(sqlite3_context *pCtx, const void *z, int n){ + assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) ); pCtx->isError = SQLITE_ERROR; pCtx->fErrorOrAux = 1; - sqlite3VdbeMemSetStr(&pCtx->s, z, n, SQLITE_UTF16NATIVE, SQLITE_TRANSIENT); + sqlite3VdbeMemSetStr(pCtx->pOut, z, n, SQLITE_UTF16NATIVE, SQLITE_TRANSIENT); } #endif -SQLITE_API void sqlite3_result_int(sqlite3_context *pCtx, int iVal){ - assert( sqlite3_mutex_held(pCtx->s.db->mutex) ); - sqlite3VdbeMemSetInt64(&pCtx->s, (i64)iVal); +SQLITE_API void SQLITE_STDCALL sqlite3_result_int(sqlite3_context *pCtx, int iVal){ + assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) ); + sqlite3VdbeMemSetInt64(pCtx->pOut, (i64)iVal); } -SQLITE_API void sqlite3_result_int64(sqlite3_context *pCtx, i64 iVal){ - assert( sqlite3_mutex_held(pCtx->s.db->mutex) ); - sqlite3VdbeMemSetInt64(&pCtx->s, iVal); +SQLITE_API void SQLITE_STDCALL sqlite3_result_int64(sqlite3_context *pCtx, i64 iVal){ + assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) ); + sqlite3VdbeMemSetInt64(pCtx->pOut, iVal); } -SQLITE_API void sqlite3_result_null(sqlite3_context *pCtx){ - assert( sqlite3_mutex_held(pCtx->s.db->mutex) ); - sqlite3VdbeMemSetNull(&pCtx->s); +SQLITE_API void SQLITE_STDCALL sqlite3_result_null(sqlite3_context *pCtx){ + assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) ); + sqlite3VdbeMemSetNull(pCtx->pOut); } -SQLITE_API void sqlite3_result_text( +SQLITE_API void SQLITE_STDCALL sqlite3_result_subtype(sqlite3_context *pCtx, unsigned int eSubtype){ + assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) ); + pCtx->pOut->eSubtype = eSubtype & 0xff; +} +SQLITE_API void SQLITE_STDCALL sqlite3_result_text( sqlite3_context *pCtx, const char *z, int n, void (*xDel)(void *) ){ - assert( sqlite3_mutex_held(pCtx->s.db->mutex) ); + assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) ); setResultStrOrError(pCtx, z, n, SQLITE_UTF8, xDel); } +SQLITE_API void SQLITE_STDCALL sqlite3_result_text64( + sqlite3_context *pCtx, + const char *z, + sqlite3_uint64 n, + void (*xDel)(void *), + unsigned char enc +){ + assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) ); + assert( xDel!=SQLITE_DYNAMIC ); + if( enc==SQLITE_UTF16 ) enc = SQLITE_UTF16NATIVE; + if( n>0x7fffffff ){ + (void)invokeValueDestructor(z, xDel, pCtx); + }else{ + setResultStrOrError(pCtx, z, (int)n, enc, xDel); + } +} #ifndef SQLITE_OMIT_UTF16 -SQLITE_API void sqlite3_result_text16( +SQLITE_API void SQLITE_STDCALL sqlite3_result_text16( sqlite3_context *pCtx, const void *z, int n, void (*xDel)(void *) ){ - assert( sqlite3_mutex_held(pCtx->s.db->mutex) ); + assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) ); setResultStrOrError(pCtx, z, n, SQLITE_UTF16NATIVE, xDel); } -SQLITE_API void sqlite3_result_text16be( +SQLITE_API void SQLITE_STDCALL sqlite3_result_text16be( sqlite3_context *pCtx, const void *z, int n, void (*xDel)(void *) ){ - assert( sqlite3_mutex_held(pCtx->s.db->mutex) ); + assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) ); setResultStrOrError(pCtx, z, n, SQLITE_UTF16BE, xDel); } -SQLITE_API void sqlite3_result_text16le( +SQLITE_API void SQLITE_STDCALL sqlite3_result_text16le( sqlite3_context *pCtx, const void *z, int n, void (*xDel)(void *) ){ - assert( sqlite3_mutex_held(pCtx->s.db->mutex) ); + assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) ); setResultStrOrError(pCtx, z, n, SQLITE_UTF16LE, xDel); } #endif /* SQLITE_OMIT_UTF16 */ -SQLITE_API void sqlite3_result_value(sqlite3_context *pCtx, sqlite3_value *pValue){ - assert( sqlite3_mutex_held(pCtx->s.db->mutex) ); - sqlite3VdbeMemCopy(&pCtx->s, pValue); +SQLITE_API void SQLITE_STDCALL sqlite3_result_value(sqlite3_context *pCtx, sqlite3_value *pValue){ + assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) ); + sqlite3VdbeMemCopy(pCtx->pOut, pValue); } -SQLITE_API void sqlite3_result_zeroblob(sqlite3_context *pCtx, int n){ - assert( sqlite3_mutex_held(pCtx->s.db->mutex) ); - sqlite3VdbeMemSetZeroBlob(&pCtx->s, n); +SQLITE_API void SQLITE_STDCALL sqlite3_result_zeroblob(sqlite3_context *pCtx, int n){ + assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) ); + sqlite3VdbeMemSetZeroBlob(pCtx->pOut, n); } -SQLITE_API void sqlite3_result_error_code(sqlite3_context *pCtx, int errCode){ +SQLITE_API int SQLITE_STDCALL sqlite3_result_zeroblob64(sqlite3_context *pCtx, u64 n){ + Mem *pOut = pCtx->pOut; + assert( sqlite3_mutex_held(pOut->db->mutex) ); + if( n>(u64)pOut->db->aLimit[SQLITE_LIMIT_LENGTH] ){ + return SQLITE_TOOBIG; + } + sqlite3VdbeMemSetZeroBlob(pCtx->pOut, (int)n); + return SQLITE_OK; +} +SQLITE_API void SQLITE_STDCALL sqlite3_result_error_code(sqlite3_context *pCtx, int errCode){ pCtx->isError = errCode; pCtx->fErrorOrAux = 1; - if( pCtx->s.flags & MEM_Null ){ - sqlite3VdbeMemSetStr(&pCtx->s, sqlite3ErrStr(errCode), -1, +#ifdef SQLITE_DEBUG + if( pCtx->pVdbe ) pCtx->pVdbe->rcApp = errCode; +#endif + if( pCtx->pOut->flags & MEM_Null ){ + sqlite3VdbeMemSetStr(pCtx->pOut, sqlite3ErrStr(errCode), -1, SQLITE_UTF8, SQLITE_STATIC); } } /* Force an SQLITE_TOOBIG error. */ -SQLITE_API void sqlite3_result_error_toobig(sqlite3_context *pCtx){ - assert( sqlite3_mutex_held(pCtx->s.db->mutex) ); +SQLITE_API void SQLITE_STDCALL sqlite3_result_error_toobig(sqlite3_context *pCtx){ + assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) ); pCtx->isError = SQLITE_TOOBIG; pCtx->fErrorOrAux = 1; - sqlite3VdbeMemSetStr(&pCtx->s, "string or blob too big", -1, + sqlite3VdbeMemSetStr(pCtx->pOut, "string or blob too big", -1, SQLITE_UTF8, SQLITE_STATIC); } /* An SQLITE_NOMEM error. */ -SQLITE_API void sqlite3_result_error_nomem(sqlite3_context *pCtx){ - assert( sqlite3_mutex_held(pCtx->s.db->mutex) ); - sqlite3VdbeMemSetNull(&pCtx->s); +SQLITE_API void SQLITE_STDCALL sqlite3_result_error_nomem(sqlite3_context *pCtx){ + assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) ); + sqlite3VdbeMemSetNull(pCtx->pOut); pCtx->isError = SQLITE_NOMEM; pCtx->fErrorOrAux = 1; - pCtx->s.db->mallocFailed = 1; + pCtx->pOut->db->mallocFailed = 1; } /* @@ -66094,7 +72249,10 @@ static int doWalCallbacks(sqlite3 *db){ for(i=0; inDb; i++){ Btree *pBt = db->aDb[i].pBt; if( pBt ){ - int nEntry = sqlite3PagerWalCallback(sqlite3BtreePager(pBt)); + int nEntry; + sqlite3BtreeEnter(pBt); + nEntry = sqlite3PagerWalCallback(sqlite3BtreePager(pBt)); + sqlite3BtreeLeave(pBt); if( db->xWalCallback && nEntry>0 && rc==SQLITE_OK ){ rc = db->xWalCallback(db->pWalArg, db, db->aDb[i].zName, nEntry); } @@ -66104,6 +72262,7 @@ static int doWalCallbacks(sqlite3 *db){ return rc; } + /* ** Execute the statement pStmt, either until a row of data is ready, the ** statement is completely executed or an error occurs. @@ -66136,7 +72295,7 @@ static int sqlite3Step(Vdbe *p){ ** or SQLITE_BUSY error. */ #ifdef SQLITE_OMIT_AUTORESET - if( p->rc==SQLITE_BUSY || p->rc==SQLITE_LOCKED ){ + if( (rc = p->rc&0xff)==SQLITE_BUSY || rc==SQLITE_LOCKED ){ sqlite3_reset((sqlite3_stmt*)p); }else{ return SQLITE_MISUSE_BKPT; @@ -66172,8 +72331,10 @@ static int sqlite3Step(Vdbe *p){ ); #ifndef SQLITE_OMIT_TRACE - if( db->xProfile && !db->init.busy ){ + if( db->xProfile && !db->init.busy && p->zSql ){ sqlite3OsCurrentTimeInt64(db->pVfs, &p->startTime); + }else{ + assert( p->startTime==0 ); } #endif @@ -66182,6 +72343,9 @@ static int sqlite3Step(Vdbe *p){ if( p->bIsReader ) db->nVdbeRead++; p->pc = 0; } +#ifdef SQLITE_DEBUG + p->rcApp = SQLITE_OK; +#endif #ifndef SQLITE_OMIT_EXPLAIN if( p->explain ){ rc = sqlite3VdbeList(p); @@ -66194,13 +72358,8 @@ static int sqlite3Step(Vdbe *p){ } #ifndef SQLITE_OMIT_TRACE - /* Invoke the profile callback if there is one - */ - if( rc!=SQLITE_ROW && db->xProfile && !db->init.busy && p->zSql ){ - sqlite3_int64 iNow; - sqlite3OsCurrentTimeInt64(db->pVfs, &iNow); - db->xProfile(db->pProfileArg, p->zSql, (iNow - p->startTime)*1000000); - } + /* If the statement completed successfully, invoke the profile callback */ + if( rc!=SQLITE_ROW ) checkProfileCallback(db, p); #endif if( rc==SQLITE_DONE ){ @@ -66224,9 +72383,9 @@ end_of_step: ** were called on statement p. */ assert( rc==SQLITE_ROW || rc==SQLITE_DONE || rc==SQLITE_ERROR - || rc==SQLITE_BUSY || rc==SQLITE_MISUSE + || (rc&0xff)==SQLITE_BUSY || rc==SQLITE_MISUSE ); - assert( p->rc!=SQLITE_ROW && p->rc!=SQLITE_DONE ); + assert( (p->rc!=SQLITE_ROW && p->rc!=SQLITE_DONE) || p->rc==p->rcApp ); if( p->isPrepareV2 && rc!=SQLITE_ROW && rc!=SQLITE_DONE ){ /* If this statement was prepared using sqlite3_prepare_v2(), and an ** error has occurred, then return the error code in p->rc to the @@ -66242,7 +72401,7 @@ end_of_step: ** sqlite3Step() to do most of the work. If a schema error occurs, ** call sqlite3Reprepare() and try again. */ -SQLITE_API int sqlite3_step(sqlite3_stmt *pStmt){ +SQLITE_API int SQLITE_STDCALL sqlite3_step(sqlite3_stmt *pStmt){ int rc = SQLITE_OK; /* Result from sqlite3Step() */ int rc2 = SQLITE_OK; /* Result from sqlite3Reprepare() */ Vdbe *v = (Vdbe*)pStmt; /* the prepared statement */ @@ -66256,10 +72415,12 @@ SQLITE_API int sqlite3_step(sqlite3_stmt *pStmt){ sqlite3_mutex_enter(db->mutex); v->doingRerun = 0; while( (rc = sqlite3Step(v))==SQLITE_SCHEMA - && cnt++ < SQLITE_MAX_SCHEMA_RETRY - && (rc2 = rc = sqlite3Reprepare(v))==SQLITE_OK ){ + && cnt++ < SQLITE_MAX_SCHEMA_RETRY ){ + int savedPc = v->pc; + rc2 = rc = sqlite3Reprepare(v); + if( rc!=SQLITE_OK) break; sqlite3_reset(pStmt); - v->doingRerun = 1; + if( savedPc>=0 ) v->doingRerun = 1; assert( v->expired==0 ); } if( rc2!=SQLITE_OK ){ @@ -66272,7 +72433,6 @@ SQLITE_API int sqlite3_step(sqlite3_stmt *pStmt){ ** sqlite3_errmsg() and sqlite3_errcode(). */ const char *zErr = (const char *)sqlite3_value_text(db->pErr); - assert( zErr!=0 || db->mallocFailed ); sqlite3DbFree(db, v->zErrMsg); if( !db->mallocFailed ){ v->zErrMsg = sqlite3DbStrDup(db, zErr); @@ -66292,7 +72452,7 @@ SQLITE_API int sqlite3_step(sqlite3_stmt *pStmt){ ** Extract the user data from a sqlite3_context structure and return a ** pointer to it. */ -SQLITE_API void *sqlite3_user_data(sqlite3_context *p){ +SQLITE_API void *SQLITE_STDCALL sqlite3_user_data(sqlite3_context *p){ assert( p && p->pFunc ); return p->pFunc->pUserData; } @@ -66307,22 +72467,32 @@ SQLITE_API void *sqlite3_user_data(sqlite3_context *p){ ** sqlite3_create_function16() routines that originally registered the ** application defined function. */ -SQLITE_API sqlite3 *sqlite3_context_db_handle(sqlite3_context *p){ - assert( p && p->pFunc ); - return p->s.db; +SQLITE_API sqlite3 *SQLITE_STDCALL sqlite3_context_db_handle(sqlite3_context *p){ + assert( p && p->pOut ); + return p->pOut->db; } /* -** Return the current time for a statement +** Return the current time for a statement. If the current time +** is requested more than once within the same run of a single prepared +** statement, the exact same time is returned for each invocation regardless +** of the amount of time that elapses between invocations. In other words, +** the time returned is always the time of the first call. */ SQLITE_PRIVATE sqlite3_int64 sqlite3StmtCurrentTime(sqlite3_context *p){ - Vdbe *v = p->pVdbe; int rc; - if( v->iCurrentTime==0 ){ - rc = sqlite3OsCurrentTimeInt64(p->s.db->pVfs, &v->iCurrentTime); - if( rc ) v->iCurrentTime = 0; +#ifndef SQLITE_ENABLE_STAT3_OR_STAT4 + sqlite3_int64 *piTime = &p->pVdbe->iCurrentTime; + assert( p->pVdbe!=0 ); +#else + sqlite3_int64 iTime = 0; + sqlite3_int64 *piTime = p->pVdbe!=0 ? &p->pVdbe->iCurrentTime : &iTime; +#endif + if( *piTime==0 ){ + rc = sqlite3OsCurrentTimeInt64(p->pOut->db->pVfs, piTime); + if( rc ) *piTime = 0; } - return v->iCurrentTime; + return *piTime; } /* @@ -66348,41 +72518,55 @@ SQLITE_PRIVATE void sqlite3InvalidFunction( } /* -** Allocate or return the aggregate context for a user function. A new -** context is allocated on the first call. Subsequent calls return the -** same context that was returned on prior calls. +** Create a new aggregate context for p and return a pointer to +** its pMem->z element. */ -SQLITE_API void *sqlite3_aggregate_context(sqlite3_context *p, int nByte){ - Mem *pMem; - assert( p && p->pFunc && p->pFunc->xStep ); - assert( sqlite3_mutex_held(p->s.db->mutex) ); - pMem = p->pMem; - testcase( nByte<0 ); - if( (pMem->flags & MEM_Agg)==0 ){ - if( nByte<=0 ){ - sqlite3VdbeMemReleaseExternal(pMem); - pMem->flags = MEM_Null; - pMem->z = 0; - }else{ - sqlite3VdbeMemGrow(pMem, nByte, 0); - pMem->flags = MEM_Agg; - pMem->u.pDef = p->pFunc; - if( pMem->z ){ - memset(pMem->z, 0, nByte); - } +static SQLITE_NOINLINE void *createAggContext(sqlite3_context *p, int nByte){ + Mem *pMem = p->pMem; + assert( (pMem->flags & MEM_Agg)==0 ); + if( nByte<=0 ){ + sqlite3VdbeMemSetNull(pMem); + pMem->z = 0; + }else{ + sqlite3VdbeMemClearAndResize(pMem, nByte); + pMem->flags = MEM_Agg; + pMem->u.pDef = p->pFunc; + if( pMem->z ){ + memset(pMem->z, 0, nByte); } } return (void*)pMem->z; } /* -** Return the auxilary data pointer, if any, for the iArg'th argument to +** Allocate or return the aggregate context for a user function. A new +** context is allocated on the first call. Subsequent calls return the +** same context that was returned on prior calls. +*/ +SQLITE_API void *SQLITE_STDCALL sqlite3_aggregate_context(sqlite3_context *p, int nByte){ + assert( p && p->pFunc && p->pFunc->xStep ); + assert( sqlite3_mutex_held(p->pOut->db->mutex) ); + testcase( nByte<0 ); + if( (p->pMem->flags & MEM_Agg)==0 ){ + return createAggContext(p, nByte); + }else{ + return (void*)p->pMem->z; + } +} + +/* +** Return the auxiliary data pointer, if any, for the iArg'th argument to ** the user-function defined by pCtx. */ -SQLITE_API void *sqlite3_get_auxdata(sqlite3_context *pCtx, int iArg){ +SQLITE_API void *SQLITE_STDCALL sqlite3_get_auxdata(sqlite3_context *pCtx, int iArg){ AuxData *pAuxData; - assert( sqlite3_mutex_held(pCtx->s.db->mutex) ); + assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) ); +#if SQLITE_ENABLE_STAT3_OR_STAT4 + if( pCtx->pVdbe==0 ) return 0; +#else + assert( pCtx->pVdbe!=0 ); +#endif for(pAuxData=pCtx->pVdbe->pAuxData; pAuxData; pAuxData=pAuxData->pNext){ if( pAuxData->iOp==pCtx->iOp && pAuxData->iArg==iArg ) break; } @@ -66391,11 +72575,11 @@ SQLITE_API void *sqlite3_get_auxdata(sqlite3_context *pCtx, int iArg){ } /* -** Set the auxilary data pointer and delete function, for the iArg'th +** Set the auxiliary data pointer and delete function, for the iArg'th ** argument to the user-function defined by pCtx. Any previous value is ** deleted by calling the delete function specified when it was set. */ -SQLITE_API void sqlite3_set_auxdata( +SQLITE_API void SQLITE_STDCALL sqlite3_set_auxdata( sqlite3_context *pCtx, int iArg, void *pAux, @@ -66404,8 +72588,13 @@ SQLITE_API void sqlite3_set_auxdata( AuxData *pAuxData; Vdbe *pVdbe = pCtx->pVdbe; - assert( sqlite3_mutex_held(pCtx->s.db->mutex) ); + assert( sqlite3_mutex_held(pCtx->pOut->db->mutex) ); if( iArg<0 ) goto failed; +#ifdef SQLITE_ENABLE_STAT3_OR_STAT4 + if( pVdbe==0 ) goto failed; +#else + assert( pVdbe!=0 ); +#endif for(pAuxData=pVdbe->pAuxData; pAuxData; pAuxData=pAuxData->pNext){ if( pAuxData->iOp==pCtx->iOp && pAuxData->iArg==iArg ) break; @@ -66437,7 +72626,7 @@ failed: #ifndef SQLITE_OMIT_DEPRECATED /* -** Return the number of times the Step function of a aggregate has been +** Return the number of times the Step function of an aggregate has been ** called. ** ** This function is deprecated. Do not use it for new code. It is @@ -66445,7 +72634,7 @@ failed: ** implementations should keep their own counts within their aggregate ** context. */ -SQLITE_API int sqlite3_aggregate_count(sqlite3_context *p){ +SQLITE_API int SQLITE_STDCALL sqlite3_aggregate_count(sqlite3_context *p){ assert( p && p->pMem && p->pFunc && p->pFunc->xStep ); return p->pMem->n; } @@ -66454,7 +72643,7 @@ SQLITE_API int sqlite3_aggregate_count(sqlite3_context *p){ /* ** Return the number of columns in the result set for the statement pStmt. */ -SQLITE_API int sqlite3_column_count(sqlite3_stmt *pStmt){ +SQLITE_API int SQLITE_STDCALL sqlite3_column_count(sqlite3_stmt *pStmt){ Vdbe *pVm = (Vdbe *)pStmt; return pVm ? pVm->nResColumn : 0; } @@ -66463,7 +72652,7 @@ SQLITE_API int sqlite3_column_count(sqlite3_stmt *pStmt){ ** Return the number of values available from the current row of the ** currently executing statement pStmt. */ -SQLITE_API int sqlite3_data_count(sqlite3_stmt *pStmt){ +SQLITE_API int SQLITE_STDCALL sqlite3_data_count(sqlite3_stmt *pStmt){ Vdbe *pVm = (Vdbe *)pStmt; if( pVm==0 || pVm->pResultSet==0 ) return 0; return pVm->nResColumn; @@ -66486,11 +72675,23 @@ static const Mem *columnNullValue(void){ #if defined(SQLITE_DEBUG) && defined(__GNUC__) __attribute__((aligned(8))) #endif - = {0, "", (double)0, {0}, 0, MEM_Null, 0, + = { + /* .u = */ {0}, + /* .flags = */ (u16)MEM_Null, + /* .enc = */ (u8)0, + /* .eSubtype = */ (u8)0, + /* .n = */ (int)0, + /* .z = */ (char*)0, + /* .zMalloc = */ (char*)0, + /* .szMalloc = */ (int)0, + /* .uTemp = */ (u32)0, + /* .db = */ (sqlite3*)0, + /* .xDel = */ (void(*)(void*))0, #ifdef SQLITE_DEBUG - 0, 0, /* pScopyFrom, pFiller */ + /* .pScopyFrom = */ (Mem*)0, + /* .pFiller = */ (void*)0, #endif - 0, 0 }; + }; return &nullMem; } @@ -66511,7 +72712,7 @@ static Mem *columnMem(sqlite3_stmt *pStmt, int i){ }else{ if( pVm && ALWAYS(pVm->db) ){ sqlite3_mutex_enter(pVm->db->mutex); - sqlite3Error(pVm->db, SQLITE_RANGE, 0); + sqlite3Error(pVm->db, SQLITE_RANGE); } pOut = (Mem*)columnNullValue(); } @@ -66554,7 +72755,7 @@ static void columnMallocFailure(sqlite3_stmt *pStmt) ** The following routines are used to access elements of the current row ** in the result set. */ -SQLITE_API const void *sqlite3_column_blob(sqlite3_stmt *pStmt, int i){ +SQLITE_API const void *SQLITE_STDCALL sqlite3_column_blob(sqlite3_stmt *pStmt, int i){ const void *val; val = sqlite3_value_blob( columnMem(pStmt,i) ); /* Even though there is no encoding conversion, value_blob() might @@ -66564,37 +72765,37 @@ SQLITE_API const void *sqlite3_column_blob(sqlite3_stmt *pStmt, int i){ columnMallocFailure(pStmt); return val; } -SQLITE_API int sqlite3_column_bytes(sqlite3_stmt *pStmt, int i){ +SQLITE_API int SQLITE_STDCALL sqlite3_column_bytes(sqlite3_stmt *pStmt, int i){ int val = sqlite3_value_bytes( columnMem(pStmt,i) ); columnMallocFailure(pStmt); return val; } -SQLITE_API int sqlite3_column_bytes16(sqlite3_stmt *pStmt, int i){ +SQLITE_API int SQLITE_STDCALL sqlite3_column_bytes16(sqlite3_stmt *pStmt, int i){ int val = sqlite3_value_bytes16( columnMem(pStmt,i) ); columnMallocFailure(pStmt); return val; } -SQLITE_API double sqlite3_column_double(sqlite3_stmt *pStmt, int i){ +SQLITE_API double SQLITE_STDCALL sqlite3_column_double(sqlite3_stmt *pStmt, int i){ double val = sqlite3_value_double( columnMem(pStmt,i) ); columnMallocFailure(pStmt); return val; } -SQLITE_API int sqlite3_column_int(sqlite3_stmt *pStmt, int i){ +SQLITE_API int SQLITE_STDCALL sqlite3_column_int(sqlite3_stmt *pStmt, int i){ int val = sqlite3_value_int( columnMem(pStmt,i) ); columnMallocFailure(pStmt); return val; } -SQLITE_API sqlite_int64 sqlite3_column_int64(sqlite3_stmt *pStmt, int i){ +SQLITE_API sqlite_int64 SQLITE_STDCALL sqlite3_column_int64(sqlite3_stmt *pStmt, int i){ sqlite_int64 val = sqlite3_value_int64( columnMem(pStmt,i) ); columnMallocFailure(pStmt); return val; } -SQLITE_API const unsigned char *sqlite3_column_text(sqlite3_stmt *pStmt, int i){ +SQLITE_API const unsigned char *SQLITE_STDCALL sqlite3_column_text(sqlite3_stmt *pStmt, int i){ const unsigned char *val = sqlite3_value_text( columnMem(pStmt,i) ); columnMallocFailure(pStmt); return val; } -SQLITE_API sqlite3_value *sqlite3_column_value(sqlite3_stmt *pStmt, int i){ +SQLITE_API sqlite3_value *SQLITE_STDCALL sqlite3_column_value(sqlite3_stmt *pStmt, int i){ Mem *pOut = columnMem(pStmt, i); if( pOut->flags&MEM_Static ){ pOut->flags &= ~MEM_Static; @@ -66604,13 +72805,13 @@ SQLITE_API sqlite3_value *sqlite3_column_value(sqlite3_stmt *pStmt, int i){ return (sqlite3_value *)pOut; } #ifndef SQLITE_OMIT_UTF16 -SQLITE_API const void *sqlite3_column_text16(sqlite3_stmt *pStmt, int i){ +SQLITE_API const void *SQLITE_STDCALL sqlite3_column_text16(sqlite3_stmt *pStmt, int i){ const void *val = sqlite3_value_text16( columnMem(pStmt,i) ); columnMallocFailure(pStmt); return val; } #endif /* SQLITE_OMIT_UTF16 */ -SQLITE_API int sqlite3_column_type(sqlite3_stmt *pStmt, int i){ +SQLITE_API int SQLITE_STDCALL sqlite3_column_type(sqlite3_stmt *pStmt, int i){ int iType = sqlite3_value_type( columnMem(pStmt,i) ); columnMallocFailure(pStmt); return iType; @@ -66638,11 +72839,19 @@ static const void *columnName( const void *(*xFunc)(Mem*), int useType ){ - const void *ret = 0; - Vdbe *p = (Vdbe *)pStmt; + const void *ret; + Vdbe *p; int n; - sqlite3 *db = p->db; - + sqlite3 *db; +#ifdef SQLITE_ENABLE_API_ARMOR + if( pStmt==0 ){ + (void)SQLITE_MISUSE_BKPT; + return 0; + } +#endif + ret = 0; + p = (Vdbe *)pStmt; + db = p->db; assert( db!=0 ); n = sqlite3_column_count(pStmt); if( N=0 ){ @@ -66666,12 +72875,12 @@ static const void *columnName( ** Return the name of the Nth column of the result set returned by SQL ** statement pStmt. */ -SQLITE_API const char *sqlite3_column_name(sqlite3_stmt *pStmt, int N){ +SQLITE_API const char *SQLITE_STDCALL sqlite3_column_name(sqlite3_stmt *pStmt, int N){ return columnName( pStmt, N, (const void*(*)(Mem*))sqlite3_value_text, COLNAME_NAME); } #ifndef SQLITE_OMIT_UTF16 -SQLITE_API const void *sqlite3_column_name16(sqlite3_stmt *pStmt, int N){ +SQLITE_API const void *SQLITE_STDCALL sqlite3_column_name16(sqlite3_stmt *pStmt, int N){ return columnName( pStmt, N, (const void*(*)(Mem*))sqlite3_value_text16, COLNAME_NAME); } @@ -66691,12 +72900,12 @@ SQLITE_API const void *sqlite3_column_name16(sqlite3_stmt *pStmt, int N){ ** Return the column declaration type (if applicable) of the 'i'th column ** of the result set of SQL statement pStmt. */ -SQLITE_API const char *sqlite3_column_decltype(sqlite3_stmt *pStmt, int N){ +SQLITE_API const char *SQLITE_STDCALL sqlite3_column_decltype(sqlite3_stmt *pStmt, int N){ return columnName( pStmt, N, (const void*(*)(Mem*))sqlite3_value_text, COLNAME_DECLTYPE); } #ifndef SQLITE_OMIT_UTF16 -SQLITE_API const void *sqlite3_column_decltype16(sqlite3_stmt *pStmt, int N){ +SQLITE_API const void *SQLITE_STDCALL sqlite3_column_decltype16(sqlite3_stmt *pStmt, int N){ return columnName( pStmt, N, (const void*(*)(Mem*))sqlite3_value_text16, COLNAME_DECLTYPE); } @@ -66707,14 +72916,14 @@ SQLITE_API const void *sqlite3_column_decltype16(sqlite3_stmt *pStmt, int N){ /* ** Return the name of the database from which a result column derives. ** NULL is returned if the result column is an expression or constant or -** anything else which is not an unabiguous reference to a database column. +** anything else which is not an unambiguous reference to a database column. */ -SQLITE_API const char *sqlite3_column_database_name(sqlite3_stmt *pStmt, int N){ +SQLITE_API const char *SQLITE_STDCALL sqlite3_column_database_name(sqlite3_stmt *pStmt, int N){ return columnName( pStmt, N, (const void*(*)(Mem*))sqlite3_value_text, COLNAME_DATABASE); } #ifndef SQLITE_OMIT_UTF16 -SQLITE_API const void *sqlite3_column_database_name16(sqlite3_stmt *pStmt, int N){ +SQLITE_API const void *SQLITE_STDCALL sqlite3_column_database_name16(sqlite3_stmt *pStmt, int N){ return columnName( pStmt, N, (const void*(*)(Mem*))sqlite3_value_text16, COLNAME_DATABASE); } @@ -66723,14 +72932,14 @@ SQLITE_API const void *sqlite3_column_database_name16(sqlite3_stmt *pStmt, int N /* ** Return the name of the table from which a result column derives. ** NULL is returned if the result column is an expression or constant or -** anything else which is not an unabiguous reference to a database column. +** anything else which is not an unambiguous reference to a database column. */ -SQLITE_API const char *sqlite3_column_table_name(sqlite3_stmt *pStmt, int N){ +SQLITE_API const char *SQLITE_STDCALL sqlite3_column_table_name(sqlite3_stmt *pStmt, int N){ return columnName( pStmt, N, (const void*(*)(Mem*))sqlite3_value_text, COLNAME_TABLE); } #ifndef SQLITE_OMIT_UTF16 -SQLITE_API const void *sqlite3_column_table_name16(sqlite3_stmt *pStmt, int N){ +SQLITE_API const void *SQLITE_STDCALL sqlite3_column_table_name16(sqlite3_stmt *pStmt, int N){ return columnName( pStmt, N, (const void*(*)(Mem*))sqlite3_value_text16, COLNAME_TABLE); } @@ -66739,14 +72948,14 @@ SQLITE_API const void *sqlite3_column_table_name16(sqlite3_stmt *pStmt, int N){ /* ** Return the name of the table column from which a result column derives. ** NULL is returned if the result column is an expression or constant or -** anything else which is not an unabiguous reference to a database column. +** anything else which is not an unambiguous reference to a database column. */ -SQLITE_API const char *sqlite3_column_origin_name(sqlite3_stmt *pStmt, int N){ +SQLITE_API const char *SQLITE_STDCALL sqlite3_column_origin_name(sqlite3_stmt *pStmt, int N){ return columnName( pStmt, N, (const void*(*)(Mem*))sqlite3_value_text, COLNAME_COLUMN); } #ifndef SQLITE_OMIT_UTF16 -SQLITE_API const void *sqlite3_column_origin_name16(sqlite3_stmt *pStmt, int N){ +SQLITE_API const void *SQLITE_STDCALL sqlite3_column_origin_name16(sqlite3_stmt *pStmt, int N){ return columnName( pStmt, N, (const void*(*)(Mem*))sqlite3_value_text16, COLNAME_COLUMN); } @@ -66776,14 +72985,14 @@ static int vdbeUnbind(Vdbe *p, int i){ } sqlite3_mutex_enter(p->db->mutex); if( p->magic!=VDBE_MAGIC_RUN || p->pc>=0 ){ - sqlite3Error(p->db, SQLITE_MISUSE, 0); + sqlite3Error(p->db, SQLITE_MISUSE); sqlite3_mutex_leave(p->db->mutex); sqlite3_log(SQLITE_MISUSE, "bind on a busy prepared statement: [%s]", p->zSql); return SQLITE_MISUSE_BKPT; } if( i<1 || i>p->nVar ){ - sqlite3Error(p->db, SQLITE_RANGE, 0); + sqlite3Error(p->db, SQLITE_RANGE); sqlite3_mutex_leave(p->db->mutex); return SQLITE_RANGE; } @@ -66791,7 +73000,7 @@ static int vdbeUnbind(Vdbe *p, int i){ pVar = &p->aVar[i]; sqlite3VdbeMemRelease(pVar); pVar->flags = MEM_Null; - sqlite3Error(p->db, SQLITE_OK, 0); + sqlite3Error(p->db, SQLITE_OK); /* If the bit corresponding to this variable in Vdbe.expmask is set, then ** binding a new value to this variable invalidates the current query plan. @@ -66833,7 +73042,7 @@ static int bindText( if( rc==SQLITE_OK && encoding!=0 ){ rc = sqlite3VdbeChangeEncoding(pVar, ENC(p->db)); } - sqlite3Error(p->db, rc, 0); + sqlite3Error(p->db, rc); rc = sqlite3ApiExit(p->db, rc); } sqlite3_mutex_leave(p->db->mutex); @@ -66847,7 +73056,7 @@ static int bindText( /* ** Bind a blob value to an SQL statement variable. */ -SQLITE_API int sqlite3_bind_blob( +SQLITE_API int SQLITE_STDCALL sqlite3_bind_blob( sqlite3_stmt *pStmt, int i, const void *zData, @@ -66856,7 +73065,21 @@ SQLITE_API int sqlite3_bind_blob( ){ return bindText(pStmt, i, zData, nData, xDel, 0); } -SQLITE_API int sqlite3_bind_double(sqlite3_stmt *pStmt, int i, double rValue){ +SQLITE_API int SQLITE_STDCALL sqlite3_bind_blob64( + sqlite3_stmt *pStmt, + int i, + const void *zData, + sqlite3_uint64 nData, + void (*xDel)(void*) +){ + assert( xDel!=SQLITE_DYNAMIC ); + if( nData>0x7fffffff ){ + return invokeValueDestructor(zData, xDel, 0); + }else{ + return bindText(pStmt, i, zData, (int)nData, xDel, 0); + } +} +SQLITE_API int SQLITE_STDCALL sqlite3_bind_double(sqlite3_stmt *pStmt, int i, double rValue){ int rc; Vdbe *p = (Vdbe *)pStmt; rc = vdbeUnbind(p, i); @@ -66866,10 +73089,10 @@ SQLITE_API int sqlite3_bind_double(sqlite3_stmt *pStmt, int i, double rValue){ } return rc; } -SQLITE_API int sqlite3_bind_int(sqlite3_stmt *p, int i, int iValue){ +SQLITE_API int SQLITE_STDCALL sqlite3_bind_int(sqlite3_stmt *p, int i, int iValue){ return sqlite3_bind_int64(p, i, (i64)iValue); } -SQLITE_API int sqlite3_bind_int64(sqlite3_stmt *pStmt, int i, sqlite_int64 iValue){ +SQLITE_API int SQLITE_STDCALL sqlite3_bind_int64(sqlite3_stmt *pStmt, int i, sqlite_int64 iValue){ int rc; Vdbe *p = (Vdbe *)pStmt; rc = vdbeUnbind(p, i); @@ -66879,7 +73102,7 @@ SQLITE_API int sqlite3_bind_int64(sqlite3_stmt *pStmt, int i, sqlite_int64 iValu } return rc; } -SQLITE_API int sqlite3_bind_null(sqlite3_stmt *pStmt, int i){ +SQLITE_API int SQLITE_STDCALL sqlite3_bind_null(sqlite3_stmt *pStmt, int i){ int rc; Vdbe *p = (Vdbe*)pStmt; rc = vdbeUnbind(p, i); @@ -66888,7 +73111,7 @@ SQLITE_API int sqlite3_bind_null(sqlite3_stmt *pStmt, int i){ } return rc; } -SQLITE_API int sqlite3_bind_text( +SQLITE_API int SQLITE_STDCALL sqlite3_bind_text( sqlite3_stmt *pStmt, int i, const char *zData, @@ -66897,8 +73120,24 @@ SQLITE_API int sqlite3_bind_text( ){ return bindText(pStmt, i, zData, nData, xDel, SQLITE_UTF8); } +SQLITE_API int SQLITE_STDCALL sqlite3_bind_text64( + sqlite3_stmt *pStmt, + int i, + const char *zData, + sqlite3_uint64 nData, + void (*xDel)(void*), + unsigned char enc +){ + assert( xDel!=SQLITE_DYNAMIC ); + if( nData>0x7fffffff ){ + return invokeValueDestructor(zData, xDel, 0); + }else{ + if( enc==SQLITE_UTF16 ) enc = SQLITE_UTF16NATIVE; + return bindText(pStmt, i, zData, (int)nData, xDel, enc); + } +} #ifndef SQLITE_OMIT_UTF16 -SQLITE_API int sqlite3_bind_text16( +SQLITE_API int SQLITE_STDCALL sqlite3_bind_text16( sqlite3_stmt *pStmt, int i, const void *zData, @@ -66908,7 +73147,7 @@ SQLITE_API int sqlite3_bind_text16( return bindText(pStmt, i, zData, nData, xDel, SQLITE_UTF16NATIVE); } #endif /* SQLITE_OMIT_UTF16 */ -SQLITE_API int sqlite3_bind_value(sqlite3_stmt *pStmt, int i, const sqlite3_value *pValue){ +SQLITE_API int SQLITE_STDCALL sqlite3_bind_value(sqlite3_stmt *pStmt, int i, const sqlite3_value *pValue){ int rc; switch( sqlite3_value_type((sqlite3_value*)pValue) ){ case SQLITE_INTEGER: { @@ -66916,7 +73155,7 @@ SQLITE_API int sqlite3_bind_value(sqlite3_stmt *pStmt, int i, const sqlite3_valu break; } case SQLITE_FLOAT: { - rc = sqlite3_bind_double(pStmt, i, pValue->r); + rc = sqlite3_bind_double(pStmt, i, pValue->u.r); break; } case SQLITE_BLOB: { @@ -66939,7 +73178,7 @@ SQLITE_API int sqlite3_bind_value(sqlite3_stmt *pStmt, int i, const sqlite3_valu } return rc; } -SQLITE_API int sqlite3_bind_zeroblob(sqlite3_stmt *pStmt, int i, int n){ +SQLITE_API int SQLITE_STDCALL sqlite3_bind_zeroblob(sqlite3_stmt *pStmt, int i, int n){ int rc; Vdbe *p = (Vdbe *)pStmt; rc = vdbeUnbind(p, i); @@ -66949,12 +73188,26 @@ SQLITE_API int sqlite3_bind_zeroblob(sqlite3_stmt *pStmt, int i, int n){ } return rc; } +SQLITE_API int SQLITE_STDCALL sqlite3_bind_zeroblob64(sqlite3_stmt *pStmt, int i, sqlite3_uint64 n){ + int rc; + Vdbe *p = (Vdbe *)pStmt; + sqlite3_mutex_enter(p->db->mutex); + if( n>(u64)p->db->aLimit[SQLITE_LIMIT_LENGTH] ){ + rc = SQLITE_TOOBIG; + }else{ + assert( (n & 0x7FFFFFFF)==n ); + rc = sqlite3_bind_zeroblob(pStmt, i, n); + } + rc = sqlite3ApiExit(p->db, rc); + sqlite3_mutex_leave(p->db->mutex); + return rc; +} /* ** Return the number of wildcards that can be potentially bound to. ** This routine is added to support DBD::SQLite. */ -SQLITE_API int sqlite3_bind_parameter_count(sqlite3_stmt *pStmt){ +SQLITE_API int SQLITE_STDCALL sqlite3_bind_parameter_count(sqlite3_stmt *pStmt){ Vdbe *p = (Vdbe*)pStmt; return p ? p->nVar : 0; } @@ -66965,7 +73218,7 @@ SQLITE_API int sqlite3_bind_parameter_count(sqlite3_stmt *pStmt){ ** ** The result is always UTF-8. */ -SQLITE_API const char *sqlite3_bind_parameter_name(sqlite3_stmt *pStmt, int i){ +SQLITE_API const char *SQLITE_STDCALL sqlite3_bind_parameter_name(sqlite3_stmt *pStmt, int i){ Vdbe *p = (Vdbe*)pStmt; if( p==0 || i<1 || i>p->nzVar ){ return 0; @@ -66993,7 +73246,7 @@ SQLITE_PRIVATE int sqlite3VdbeParameterIndex(Vdbe *p, const char *zName, int nNa } return 0; } -SQLITE_API int sqlite3_bind_parameter_index(sqlite3_stmt *pStmt, const char *zName){ +SQLITE_API int SQLITE_STDCALL sqlite3_bind_parameter_index(sqlite3_stmt *pStmt, const char *zName){ return sqlite3VdbeParameterIndex((Vdbe*)pStmt, zName, sqlite3Strlen30(zName)); } @@ -67019,7 +73272,7 @@ SQLITE_PRIVATE int sqlite3TransferBindings(sqlite3_stmt *pFromStmt, sqlite3_stmt ** Deprecated external interface. Internal/core SQLite code ** should call sqlite3TransferBindings. ** -** Is is misuse to call this routine with statements from different +** It is misuse to call this routine with statements from different ** database connections. But as this is a deprecated interface, we ** will not bother to check for that condition. ** @@ -67027,7 +73280,7 @@ SQLITE_PRIVATE int sqlite3TransferBindings(sqlite3_stmt *pFromStmt, sqlite3_stmt ** an SQLITE_ERROR is returned. Nothing else can go wrong, so otherwise ** SQLITE_OK is returned. */ -SQLITE_API int sqlite3_transfer_bindings(sqlite3_stmt *pFromStmt, sqlite3_stmt *pToStmt){ +SQLITE_API int SQLITE_STDCALL sqlite3_transfer_bindings(sqlite3_stmt *pFromStmt, sqlite3_stmt *pToStmt){ Vdbe *pFrom = (Vdbe*)pFromStmt; Vdbe *pTo = (Vdbe*)pToStmt; if( pFrom->nVar!=pTo->nVar ){ @@ -67049,7 +73302,7 @@ SQLITE_API int sqlite3_transfer_bindings(sqlite3_stmt *pFromStmt, sqlite3_stmt * ** the first argument to the sqlite3_prepare() that was used to create ** the statement in the first place. */ -SQLITE_API sqlite3 *sqlite3_db_handle(sqlite3_stmt *pStmt){ +SQLITE_API sqlite3 *SQLITE_STDCALL sqlite3_db_handle(sqlite3_stmt *pStmt){ return pStmt ? ((Vdbe*)pStmt)->db : 0; } @@ -67057,16 +73310,16 @@ SQLITE_API sqlite3 *sqlite3_db_handle(sqlite3_stmt *pStmt){ ** Return true if the prepared statement is guaranteed to not modify the ** database. */ -SQLITE_API int sqlite3_stmt_readonly(sqlite3_stmt *pStmt){ +SQLITE_API int SQLITE_STDCALL sqlite3_stmt_readonly(sqlite3_stmt *pStmt){ return pStmt ? ((Vdbe*)pStmt)->readOnly : 1; } /* ** Return true if the prepared statement is in need of being reset. */ -SQLITE_API int sqlite3_stmt_busy(sqlite3_stmt *pStmt){ +SQLITE_API int SQLITE_STDCALL sqlite3_stmt_busy(sqlite3_stmt *pStmt){ Vdbe *v = (Vdbe*)pStmt; - return v!=0 && v->pc>0 && v->magic==VDBE_MAGIC_RUN; + return v!=0 && v->pc>=0 && v->magic==VDBE_MAGIC_RUN; } /* @@ -67075,8 +73328,14 @@ SQLITE_API int sqlite3_stmt_busy(sqlite3_stmt *pStmt){ ** prepared statement for the database connection. Return NULL if there ** are no more. */ -SQLITE_API sqlite3_stmt *sqlite3_next_stmt(sqlite3 *pDb, sqlite3_stmt *pStmt){ +SQLITE_API sqlite3_stmt *SQLITE_STDCALL sqlite3_next_stmt(sqlite3 *pDb, sqlite3_stmt *pStmt){ sqlite3_stmt *pNext; +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(pDb) ){ + (void)SQLITE_MISUSE_BKPT; + return 0; + } +#endif sqlite3_mutex_enter(pDb->mutex); if( pStmt==0 ){ pNext = (sqlite3_stmt*)pDb->pVdbe; @@ -67090,13 +73349,89 @@ SQLITE_API sqlite3_stmt *sqlite3_next_stmt(sqlite3 *pDb, sqlite3_stmt *pStmt){ /* ** Return the value of a status counter for a prepared statement */ -SQLITE_API int sqlite3_stmt_status(sqlite3_stmt *pStmt, int op, int resetFlag){ +SQLITE_API int SQLITE_STDCALL sqlite3_stmt_status(sqlite3_stmt *pStmt, int op, int resetFlag){ Vdbe *pVdbe = (Vdbe*)pStmt; - u32 v = pVdbe->aCounter[op]; + u32 v; +#ifdef SQLITE_ENABLE_API_ARMOR + if( !pStmt ){ + (void)SQLITE_MISUSE_BKPT; + return 0; + } +#endif + v = pVdbe->aCounter[op]; if( resetFlag ) pVdbe->aCounter[op] = 0; return (int)v; } +#ifdef SQLITE_ENABLE_STMT_SCANSTATUS +/* +** Return status data for a single loop within query pStmt. +*/ +SQLITE_API int SQLITE_STDCALL sqlite3_stmt_scanstatus( + sqlite3_stmt *pStmt, /* Prepared statement being queried */ + int idx, /* Index of loop to report on */ + int iScanStatusOp, /* Which metric to return */ + void *pOut /* OUT: Write the answer here */ +){ + Vdbe *p = (Vdbe*)pStmt; + ScanStatus *pScan; + if( idx<0 || idx>=p->nScan ) return 1; + pScan = &p->aScan[idx]; + switch( iScanStatusOp ){ + case SQLITE_SCANSTAT_NLOOP: { + *(sqlite3_int64*)pOut = p->anExec[pScan->addrLoop]; + break; + } + case SQLITE_SCANSTAT_NVISIT: { + *(sqlite3_int64*)pOut = p->anExec[pScan->addrVisit]; + break; + } + case SQLITE_SCANSTAT_EST: { + double r = 1.0; + LogEst x = pScan->nEst; + while( x<100 ){ + x += 10; + r *= 0.5; + } + *(double*)pOut = r*sqlite3LogEstToInt(x); + break; + } + case SQLITE_SCANSTAT_NAME: { + *(const char**)pOut = pScan->zName; + break; + } + case SQLITE_SCANSTAT_EXPLAIN: { + if( pScan->addrExplain ){ + *(const char**)pOut = p->aOp[ pScan->addrExplain ].p4.z; + }else{ + *(const char**)pOut = 0; + } + break; + } + case SQLITE_SCANSTAT_SELECTID: { + if( pScan->addrExplain ){ + *(int*)pOut = p->aOp[ pScan->addrExplain ].p1; + }else{ + *(int*)pOut = -1; + } + break; + } + default: { + return 1; + } + } + return 0; +} + +/* +** Zero all counters associated with the sqlite3_stmt_scanstatus() data. +*/ +SQLITE_API void SQLITE_STDCALL sqlite3_stmt_scanstatus_reset(sqlite3_stmt *pStmt){ + Vdbe *p = (Vdbe*)pStmt; + memset(p->anExec, 0, p->nOp * sizeof(i64)); +} +#endif /* SQLITE_ENABLE_STMT_SCANSTATUS */ + /************** End of vdbeapi.c *********************************************/ /************** Begin file vdbetrace.c ***************************************/ /* @@ -67116,6 +73451,8 @@ SQLITE_API int sqlite3_stmt_status(sqlite3_stmt *pStmt, int op, int resetFlag){ ** ** The Vdbe parse-tree explainer is also found here. */ +/* #include "sqliteInt.h" */ +/* #include "vdbeInt.h" */ #ifndef SQLITE_OMIT_TRACE @@ -67163,7 +73500,7 @@ static int findNextHostParameter(const char *zSql, int *pnToken){ ** ALGORITHM: Scan the input string looking for host parameters in any of ** these forms: ?, ?N, $A, @A, :A. Take care to avoid text within ** string literals, quoted identifier names, and comments. For text forms, -** the host parameter index is found by scanning the perpared +** the host parameter index is found by scanning the prepared ** statement for the corresponding OP_Variable opcode. Once the host ** parameter index is known, locate the value in p->aVar[]. Then render ** the value as a literal in place of the host parameter name. @@ -67183,9 +73520,8 @@ SQLITE_PRIVATE char *sqlite3VdbeExpandSql( char zBase[100]; /* Initial working space */ db = p->db; - sqlite3StrAccumInit(&out, zBase, sizeof(zBase), + sqlite3StrAccumInit(&out, db, zBase, sizeof(zBase), db->aLimit[SQLITE_LIMIT_LENGTH]); - out.db = db; if( db->nVdbeExec>1 ){ while( *zRawSql ){ const char *zStart = zRawSql; @@ -67194,6 +73530,8 @@ SQLITE_PRIVATE char *sqlite3VdbeExpandSql( assert( (zRawSql - zStart) > 0 ); sqlite3StrAccumAppend(&out, zStart, (int)(zRawSql-zStart)); } + }else if( p->nVar==0 ){ + sqlite3StrAccumAppend(&out, zRawSql, sqlite3Strlen30(zRawSql)); }else{ while( zRawSql[0] ){ n = findNextHostParameter(zRawSql, &nToken); @@ -67210,10 +73548,12 @@ SQLITE_PRIVATE char *sqlite3VdbeExpandSql( idx = nextIndex; } }else{ - assert( zRawSql[0]==':' || zRawSql[0]=='$' || zRawSql[0]=='@' ); + assert( zRawSql[0]==':' || zRawSql[0]=='$' || + zRawSql[0]=='@' || zRawSql[0]=='#' ); testcase( zRawSql[0]==':' ); testcase( zRawSql[0]=='$' ); testcase( zRawSql[0]=='@' ); + testcase( zRawSql[0]=='#' ); idx = sqlite3VdbeParameterIndex(p, zRawSql, nToken); assert( idx>0 ); } @@ -67226,7 +73566,7 @@ SQLITE_PRIVATE char *sqlite3VdbeExpandSql( }else if( pVar->flags & MEM_Int ){ sqlite3XPrintf(&out, 0, "%lld", pVar->u.i); }else if( pVar->flags & MEM_Real ){ - sqlite3XPrintf(&out, 0, "%!.15g", pVar->r); + sqlite3XPrintf(&out, 0, "%!.15g", pVar->u.r); }else if( pVar->flags & MEM_Str ){ int nOut; /* Number of bytes of the string text to include in output */ #ifndef SQLITE_OMIT_UTF16 @@ -67283,121 +73623,6 @@ SQLITE_PRIVATE char *sqlite3VdbeExpandSql( #endif /* #ifndef SQLITE_OMIT_TRACE */ -/***************************************************************************** -** The following code implements the data-structure explaining logic -** for the Vdbe. -*/ - -#if defined(SQLITE_ENABLE_TREE_EXPLAIN) - -/* -** Allocate a new Explain object -*/ -SQLITE_PRIVATE void sqlite3ExplainBegin(Vdbe *pVdbe){ - if( pVdbe ){ - Explain *p; - sqlite3BeginBenignMalloc(); - p = (Explain *)sqlite3MallocZero( sizeof(Explain) ); - if( p ){ - p->pVdbe = pVdbe; - sqlite3_free(pVdbe->pExplain); - pVdbe->pExplain = p; - sqlite3StrAccumInit(&p->str, p->zBase, sizeof(p->zBase), - SQLITE_MAX_LENGTH); - p->str.useMalloc = 2; - }else{ - sqlite3EndBenignMalloc(); - } - } -} - -/* -** Return true if the Explain ends with a new-line. -*/ -static int endsWithNL(Explain *p){ - return p && p->str.zText && p->str.nChar - && p->str.zText[p->str.nChar-1]=='\n'; -} - -/* -** Append text to the indentation -*/ -SQLITE_PRIVATE void sqlite3ExplainPrintf(Vdbe *pVdbe, const char *zFormat, ...){ - Explain *p; - if( pVdbe && (p = pVdbe->pExplain)!=0 ){ - va_list ap; - if( p->nIndent && endsWithNL(p) ){ - int n = p->nIndent; - if( n>ArraySize(p->aIndent) ) n = ArraySize(p->aIndent); - sqlite3AppendSpace(&p->str, p->aIndent[n-1]); - } - va_start(ap, zFormat); - sqlite3VXPrintf(&p->str, SQLITE_PRINTF_INTERNAL, zFormat, ap); - va_end(ap); - } -} - -/* -** Append a '\n' if there is not already one. -*/ -SQLITE_PRIVATE void sqlite3ExplainNL(Vdbe *pVdbe){ - Explain *p; - if( pVdbe && (p = pVdbe->pExplain)!=0 && !endsWithNL(p) ){ - sqlite3StrAccumAppend(&p->str, "\n", 1); - } -} - -/* -** Push a new indentation level. Subsequent lines will be indented -** so that they begin at the current cursor position. -*/ -SQLITE_PRIVATE void sqlite3ExplainPush(Vdbe *pVdbe){ - Explain *p; - if( pVdbe && (p = pVdbe->pExplain)!=0 ){ - if( p->str.zText && p->nIndentaIndent) ){ - const char *z = p->str.zText; - int i = p->str.nChar-1; - int x; - while( i>=0 && z[i]!='\n' ){ i--; } - x = (p->str.nChar - 1) - i; - if( p->nIndent && xaIndent[p->nIndent-1] ){ - x = p->aIndent[p->nIndent-1]; - } - p->aIndent[p->nIndent] = x; - } - p->nIndent++; - } -} - -/* -** Pop the indentation stack by one level. -*/ -SQLITE_PRIVATE void sqlite3ExplainPop(Vdbe *p){ - if( p && p->pExplain ) p->pExplain->nIndent--; -} - -/* -** Free the indentation structure -*/ -SQLITE_PRIVATE void sqlite3ExplainFinish(Vdbe *pVdbe){ - if( pVdbe && pVdbe->pExplain ){ - sqlite3_free(pVdbe->zExplain); - sqlite3ExplainNL(pVdbe); - pVdbe->zExplain = sqlite3StrAccumFinish(&pVdbe->pExplain->str); - sqlite3_free(pVdbe->pExplain); - pVdbe->pExplain = 0; - sqlite3EndBenignMalloc(); - } -} - -/* -** Return the explanation of a virtual machine. -*/ -SQLITE_PRIVATE const char *sqlite3VdbeExplanation(Vdbe *pVdbe){ - return (pVdbe && pVdbe->zExplain) ? pVdbe->zExplain : 0; -} -#endif /* defined(SQLITE_DEBUG) */ - /************** End of vdbetrace.c *******************************************/ /************** Begin file vdbe.c ********************************************/ /* @@ -67420,6 +73645,8 @@ SQLITE_PRIVATE const char *sqlite3VdbeExplanation(Vdbe *pVdbe){ ** in this file for details. If in doubt, do not deviate from existing ** commenting and indentation practices when changing or adding code. */ +/* #include "sqliteInt.h" */ +/* #include "vdbeInt.h" */ /* ** Invoke this macro on memory cells just prior to changing the @@ -67516,6 +73743,12 @@ SQLITE_API int sqlite3_found_count = 0; ** branch can go. It is usually 2. "I" is the direction the branch ** goes. 0 means falls through. 1 means branch is taken. 2 means the ** second alternative branch is taken. +** +** iSrcLine is the source code line (from the __LINE__ macro) that +** generated the VDBE instruction. This instrumentation assumes that all +** source code is in a single file (the amalgamation). Special values 1 +** and 2 for the iSrcLine parameter mean that this particular branch is +** always taken or never taken, respectively. */ #if !defined(SQLITE_VDBE_COVERAGE) # define VdbeBranchTaken(I,M) @@ -67540,7 +73773,7 @@ SQLITE_API int sqlite3_found_count = 0; ** already. Return non-zero if a malloc() fails. */ #define Stringify(P, enc) \ - if(((P)->flags&(MEM_Str|MEM_Blob))==0 && sqlite3VdbeMemStringify(P,enc)) \ + if(((P)->flags&(MEM_Str|MEM_Blob))==0 && sqlite3VdbeMemStringify(P,enc,0)) \ { goto no_mem; } /* @@ -67559,7 +73792,7 @@ SQLITE_API int sqlite3_found_count = 0; && sqlite3VdbeMemMakeWriteable(P) ){ goto no_mem;} /* Return true if the cursor was opened using the OP_OpenSorter opcode. */ -#define isSorter(x) ((x)->pSorter!=0) +#define isSorter(x) ((x)->eCurType==CURTYPE_SORTER) /* ** Allocate VdbeCursor number iCur. Return a pointer to it. Return NULL @@ -67570,7 +73803,7 @@ static VdbeCursor *allocateCursor( int iCur, /* Index of the new VdbeCursor */ int nField, /* Number of fields in the table or index */ int iDb, /* Database the cursor belongs to, or -1 */ - int isBtreeCursor /* True for B-Tree. False for pseudo-table or vtab */ + u8 eCurType /* Type of the new cursor */ ){ /* Find the memory cell that will be used to store the blob of memory ** required for this VdbeCursor structure. It is convenient to use a @@ -67596,22 +73829,24 @@ static VdbeCursor *allocateCursor( VdbeCursor *pCx = 0; nByte = ROUND8(sizeof(VdbeCursor)) + 2*sizeof(u32)*nField + - (isBtreeCursor?sqlite3BtreeCursorSize():0); + (eCurType==CURTYPE_BTREE?sqlite3BtreeCursorSize():0); assert( iCurnCursor ); if( p->apCsr[iCur] ){ sqlite3VdbeFreeCursor(p, p->apCsr[iCur]); p->apCsr[iCur] = 0; } - if( SQLITE_OK==sqlite3VdbeMemGrow(pMem, nByte, 0) ){ + if( SQLITE_OK==sqlite3VdbeMemClearAndResize(pMem, nByte) ){ p->apCsr[iCur] = pCx = (VdbeCursor*)pMem->z; memset(pCx, 0, sizeof(VdbeCursor)); + pCx->eCurType = eCurType; pCx->iDb = iDb; pCx->nField = nField; - if( isBtreeCursor ){ - pCx->pCursor = (BtCursor*) + pCx->aOffset = &pCx->aType[nField]; + if( eCurType==CURTYPE_BTREE ){ + pCx->uc.pCursor = (BtCursor*) &pMem->z[ROUND8(sizeof(VdbeCursor))+2*sizeof(u32)*nField]; - sqlite3BtreeCursorZero(pCx->pCursor); + sqlite3BtreeCursorZero(pCx->uc.pCursor); } } return pCx; @@ -67622,21 +73857,29 @@ static VdbeCursor *allocateCursor( ** do so without loss of information. In other words, if the string ** looks like a number, convert it into a number. If it does not ** look like a number, leave it alone. +** +** If the bTryForInt flag is true, then extra effort is made to give +** an integer representation. Strings that look like floating point +** values but which have no fractional component (example: '48.00') +** will have a MEM_Int representation when bTryForInt is true. +** +** If bTryForInt is false, then if the input string contains a decimal +** point or exponential notation, the result is only MEM_Real, even +** if there is an exact integer representation of the quantity. */ -static void applyNumericAffinity(Mem *pRec){ - if( (pRec->flags & (MEM_Real|MEM_Int))==0 ){ - double rValue; - i64 iValue; - u8 enc = pRec->enc; - if( (pRec->flags&MEM_Str)==0 ) return; - if( sqlite3AtoF(pRec->z, &rValue, pRec->n, enc)==0 ) return; - if( 0==sqlite3Atoi64(pRec->z, &iValue, pRec->n, enc) ){ - pRec->u.i = iValue; - pRec->flags |= MEM_Int; - }else{ - pRec->r = rValue; - pRec->flags |= MEM_Real; - } +static void applyNumericAffinity(Mem *pRec, int bTryForInt){ + double rValue; + i64 iValue; + u8 enc = pRec->enc; + assert( (pRec->flags & (MEM_Str|MEM_Int|MEM_Real))==MEM_Str ); + if( sqlite3AtoF(pRec->z, &rValue, pRec->n, enc)==0 ) return; + if( 0==sqlite3Atoi64(pRec->z, &iValue, pRec->n, enc) ){ + pRec->u.i = iValue; + pRec->flags |= MEM_Int; + }else{ + pRec->u.r = rValue; + pRec->flags |= MEM_Real; + if( bTryForInt ) sqlite3VdbeIntegerAffinity(pRec); } } @@ -67655,7 +73898,7 @@ static void applyNumericAffinity(Mem *pRec){ ** SQLITE_AFF_TEXT: ** Convert pRec to a text representation. ** -** SQLITE_AFF_NONE: +** SQLITE_AFF_BLOB: ** No-op. pRec is unchanged. */ static void applyAffinity( @@ -67663,22 +73906,25 @@ static void applyAffinity( char affinity, /* The affinity to be applied */ u8 enc /* Use this text encoding */ ){ - if( affinity==SQLITE_AFF_TEXT ){ + if( affinity>=SQLITE_AFF_NUMERIC ){ + assert( affinity==SQLITE_AFF_INTEGER || affinity==SQLITE_AFF_REAL + || affinity==SQLITE_AFF_NUMERIC ); + if( (pRec->flags & MEM_Int)==0 ){ + if( (pRec->flags & MEM_Real)==0 ){ + if( pRec->flags & MEM_Str ) applyNumericAffinity(pRec,1); + }else{ + sqlite3VdbeIntegerAffinity(pRec); + } + } + }else if( affinity==SQLITE_AFF_TEXT ){ /* Only attempt the conversion to TEXT if there is an integer or real ** representation (blob and NULL do not get converted) but no string ** representation. */ if( 0==(pRec->flags&MEM_Str) && (pRec->flags&(MEM_Real|MEM_Int)) ){ - sqlite3VdbeMemStringify(pRec, enc); + sqlite3VdbeMemStringify(pRec, enc, 1); } pRec->flags &= ~(MEM_Real|MEM_Int); - }else if( affinity!=SQLITE_AFF_NONE ){ - assert( affinity==SQLITE_AFF_INTEGER || affinity==SQLITE_AFF_REAL - || affinity==SQLITE_AFF_NUMERIC ); - applyNumericAffinity(pRec); - if( pRec->flags & MEM_Real ){ - sqlite3VdbeIntegerAffinity(pRec); - } } } @@ -67688,11 +73934,11 @@ static void applyAffinity( ** is appropriate. But only do the conversion if it is possible without ** loss of information and return the revised type of the argument. */ -SQLITE_API int sqlite3_value_numeric_type(sqlite3_value *pVal){ +SQLITE_API int SQLITE_STDCALL sqlite3_value_numeric_type(sqlite3_value *pVal){ int eType = sqlite3_value_type(pVal); if( eType==SQLITE_TEXT ){ Mem *pMem = (Mem*)pVal; - applyNumericAffinity(pMem); + applyNumericAffinity(pMem, 0); eType = sqlite3_value_type(pVal); } return eType; @@ -67710,25 +73956,37 @@ SQLITE_PRIVATE void sqlite3ValueApplyAffinity( applyAffinity((Mem *)pVal, affinity, enc); } +/* +** pMem currently only holds a string type (or maybe a BLOB that we can +** interpret as a string if we want to). Compute its corresponding +** numeric type, if has one. Set the pMem->u.r and pMem->u.i fields +** accordingly. +*/ +static u16 SQLITE_NOINLINE computeNumericType(Mem *pMem){ + assert( (pMem->flags & (MEM_Int|MEM_Real))==0 ); + assert( (pMem->flags & (MEM_Str|MEM_Blob))!=0 ); + if( sqlite3AtoF(pMem->z, &pMem->u.r, pMem->n, pMem->enc)==0 ){ + return 0; + } + if( sqlite3Atoi64(pMem->z, &pMem->u.i, pMem->n, pMem->enc)==SQLITE_OK ){ + return MEM_Int; + } + return MEM_Real; +} + /* ** Return the numeric type for pMem, either MEM_Int or MEM_Real or both or ** none. ** ** Unlike applyNumericAffinity(), this routine does not modify pMem->flags. -** But it does set pMem->r and pMem->u.i appropriately. +** But it does set pMem->u.r and pMem->u.i appropriately. */ static u16 numericType(Mem *pMem){ if( pMem->flags & (MEM_Int|MEM_Real) ){ return pMem->flags & (MEM_Int|MEM_Real); } if( pMem->flags & (MEM_Str|MEM_Blob) ){ - if( sqlite3AtoF(pMem->z, &pMem->r, pMem->n, pMem->enc)==0 ){ - return 0; - } - if( sqlite3Atoi64(pMem->z, &pMem->u.i, pMem->n, pMem->enc)==SQLITE_OK ){ - return MEM_Int; - } - return MEM_Real; + return computeNumericType(pMem); } return 0; } @@ -67831,7 +74089,7 @@ static void memTracePrint(Mem *p){ printf(" i:%lld", p->u.i); #ifndef SQLITE_OMIT_FLOATING_POINT }else if( p->flags & MEM_Real ){ - printf(" r:%g", p->r); + printf(" r:%g", p->u.r); #endif }else if( p->flags & MEM_RowSet ){ printf(" (rowset)"); @@ -67974,6 +74232,29 @@ static int checkSavepointCount(sqlite3 *db){ } #endif +/* +** Return the register of pOp->p2 after first preparing it to be +** overwritten with an integer value. +*/ +static SQLITE_NOINLINE Mem *out2PrereleaseWithClear(Mem *pOut){ + sqlite3VdbeMemSetNull(pOut); + pOut->flags = MEM_Int; + return pOut; +} +static Mem *out2Prerelease(Vdbe *p, VdbeOp *pOp){ + Mem *pOut; + assert( pOp->p2>0 ); + assert( pOp->p2<=(p->nMem-p->nCursor) ); + pOut = &p->aMem[pOp->p2]; + memAboutToChange(p, pOut); + if( VdbeMemDynamic(pOut) ){ + return out2PrereleaseWithClear(pOut); + }else{ + pOut->flags = MEM_Int; + return pOut; + } +} + /* ** Execute as much of a VDBE program as we can. @@ -67982,9 +74263,11 @@ static int checkSavepointCount(sqlite3 *db){ SQLITE_PRIVATE int sqlite3VdbeExec( Vdbe *p /* The VDBE */ ){ - int pc=0; /* The program counter */ Op *aOp = p->aOp; /* Copy of p->aOp */ - Op *pOp; /* Current operation */ + Op *pOp = aOp; /* Current operation */ +#if defined(SQLITE_DEBUG) || defined(VDBE_PROFILE) + Op *pOrigOp; /* Value of pOp at the top of the loop */ +#endif int rc = SQLITE_OK; /* Value to return */ sqlite3 *db = p->db; /* The database */ u8 resetSchemaOnFault = 0; /* Reset schema after an error if positive */ @@ -68013,7 +74296,7 @@ SQLITE_PRIVATE int sqlite3VdbeExec( ** sqlite3_column_text16() failed. */ goto no_mem; } - assert( p->rc==SQLITE_OK || p->rc==SQLITE_BUSY ); + assert( p->rc==SQLITE_OK || (p->rc&0xff)==SQLITE_BUSY ); assert( p->bIsReader || p->readOnly!=0 ); p->rc = SQLITE_OK; p->iCurrentTime = 0; @@ -68024,13 +74307,9 @@ SQLITE_PRIVATE int sqlite3VdbeExec( sqlite3VdbeIOTraceSql(p); #ifndef SQLITE_OMIT_PROGRESS_CALLBACK if( db->xProgress ){ + u32 iPrior = p->aCounter[SQLITE_STMTSTATUS_VM_STEP]; assert( 0 < db->nProgressOps ); - nProgressLimit = (unsigned)p->aCounter[SQLITE_STMTSTATUS_VM_STEP]; - if( nProgressLimit==0 ){ - nProgressLimit = db->nProgressOps; - }else{ - nProgressLimit %= (unsigned)db->nProgressOps; - } + nProgressLimit = db->nProgressOps - (iPrior % db->nProgressOps); } #endif #ifdef SQLITE_DEBUG @@ -68060,20 +74339,22 @@ SQLITE_PRIVATE int sqlite3VdbeExec( } sqlite3EndBenignMalloc(); #endif - for(pc=p->pc; rc==SQLITE_OK; pc++){ - assert( pc>=0 && pcnOp ); + for(pOp=&aOp[p->pc]; rc==SQLITE_OK; pOp++){ + assert( pOp>=aOp && pOp<&aOp[p->nOp]); if( db->mallocFailed ) goto no_mem; #ifdef VDBE_PROFILE start = sqlite3Hwtime(); #endif nVmStep++; - pOp = &aOp[pc]; +#ifdef SQLITE_ENABLE_STMT_SCANSTATUS + if( p->anExec ) p->anExec[(int)(pOp-aOp)]++; +#endif /* Only allow tracing if SQLITE_DEBUG is defined. */ #ifdef SQLITE_DEBUG if( db->flags & SQLITE_VdbeTrace ){ - sqlite3VdbePrintOp(stdout, pc, pOp); + sqlite3VdbePrintOp(stdout, (int)(pOp - aOp), pOp); } #endif @@ -68090,23 +74371,9 @@ SQLITE_PRIVATE int sqlite3VdbeExec( } #endif - /* On any opcode with the "out2-prerelease" tag, free any - ** external allocations out of mem[p2] and set mem[p2] to be - ** an undefined integer. Opcodes will either fill in the integer - ** value or convert mem[p2] to a different type. - */ - assert( pOp->opflags==sqlite3OpcodeProperty[pOp->opcode] ); - if( pOp->opflags & OPFLG_OUT2_PRERELEASE ){ - assert( pOp->p2>0 ); - assert( pOp->p2<=(p->nMem-p->nCursor) ); - pOut = &aMem[pOp->p2]; - memAboutToChange(p, pOut); - VdbeMemRelease(pOut); - pOut->flags = MEM_Int; - } - /* Sanity checking on other operands */ #ifdef SQLITE_DEBUG + assert( pOp->opflags==sqlite3OpcodeProperty[pOp->opcode] ); if( (pOp->opflags & OPFLG_IN1)!=0 ){ assert( pOp->p1>0 ); assert( pOp->p1<=(p->nMem-p->nCursor) ); @@ -68139,6 +74406,9 @@ SQLITE_PRIVATE int sqlite3VdbeExec( memAboutToChange(p, &aMem[pOp->p3]); } #endif +#if defined(SQLITE_DEBUG) || defined(VDBE_PROFILE) + pOrigOp = pOp; +#endif switch( pOp->opcode ){ @@ -68162,7 +74432,7 @@ SQLITE_PRIVATE int sqlite3VdbeExec( ** ** Other keywords in the comment that follows each case are used to ** construct the OPFLG_INITIALIZER value that initializes opcodeProperty[]. -** Keywords include: in1, in2, in3, out2_prerelease, out2, out3. See +** Keywords include: in1, in2, in3, out2, out3. See ** the mkopcodeh.awk script for additional information. ** ** Documentation about VDBE opcodes is generated by scanning this file @@ -68190,7 +74460,8 @@ SQLITE_PRIVATE int sqlite3VdbeExec( ** to the current line should be indented for EXPLAIN output. */ case OP_Goto: { /* jump */ - pc = pOp->p2 - 1; +jump_to_p2_and_check_for_interrupt: + pOp = &aOp[pOp->p2 - 1]; /* Opcodes that are used as the bottom of a loop (OP_Next, OP_Prev, ** OP_VNext, OP_RowSetNext, or OP_SorterNext) all jump here upon @@ -68235,9 +74506,13 @@ case OP_Gosub: { /* jump */ assert( VdbeMemDynamic(pIn1)==0 ); memAboutToChange(p, pIn1); pIn1->flags = MEM_Int; - pIn1->u.i = pc; + pIn1->u.i = (int)(pOp-aOp); REGISTER_TRACE(pOp->p1, pIn1); - pc = pOp->p2 - 1; + + /* Most jump operations do a goto to this spot in order to update + ** the pOp pointer. */ +jump_to_p2: + pOp = &aOp[pOp->p2 - 1]; break; } @@ -68249,19 +74524,21 @@ case OP_Gosub: { /* jump */ case OP_Return: { /* in1 */ pIn1 = &aMem[pOp->p1]; assert( pIn1->flags==MEM_Int ); - pc = (int)pIn1->u.i; + pOp = &aOp[pIn1->u.i]; pIn1->flags = MEM_Undefined; break; } /* Opcode: InitCoroutine P1 P2 P3 * * ** -** Set up register P1 so that it will OP_Yield to the co-routine +** Set up register P1 so that it will Yield to the coroutine ** located at address P3. ** -** If P2!=0 then the co-routine implementation immediately follows -** this opcode. So jump over the co-routine implementation to +** If P2!=0 then the coroutine implementation immediately follows +** this opcode. So jump over the coroutine implementation to ** address P2. +** +** See also: EndCoroutine */ case OP_InitCoroutine: { /* jump */ assert( pOp->p1>0 && pOp->p1<=(p->nMem-p->nCursor) ); @@ -68271,15 +74548,17 @@ case OP_InitCoroutine: { /* jump */ assert( !VdbeMemDynamic(pOut) ); pOut->u.i = pOp->p3 - 1; pOut->flags = MEM_Int; - if( pOp->p2 ) pc = pOp->p2 - 1; + if( pOp->p2 ) goto jump_to_p2; break; } /* Opcode: EndCoroutine P1 * * * * ** -** The instruction at the address in register P1 is an OP_Yield. -** Jump to the P2 parameter of that OP_Yield. +** The instruction at the address in register P1 is a Yield. +** Jump to the P2 parameter of that Yield. ** After the jump, register P1 becomes undefined. +** +** See also: InitCoroutine */ case OP_EndCoroutine: { /* in1 */ VdbeOp *pCaller; @@ -68289,18 +74568,23 @@ case OP_EndCoroutine: { /* in1 */ pCaller = &aOp[pIn1->u.i]; assert( pCaller->opcode==OP_Yield ); assert( pCaller->p2>=0 && pCaller->p2nOp ); - pc = pCaller->p2 - 1; + pOp = &aOp[pCaller->p2 - 1]; pIn1->flags = MEM_Undefined; break; } /* Opcode: Yield P1 P2 * * * ** -** Swap the program counter with the value in register P1. +** Swap the program counter with the value in register P1. This +** has the effect of yielding to a coroutine. ** -** If the co-routine ends with OP_Yield or OP_Return then continue -** to the next instruction. But if the co-routine ends with -** OP_EndCoroutine, jump immediately to P2. +** If the coroutine that is launched by this instruction ends with +** Yield or Return then continue to the next instruction. But if +** the coroutine launched by this instruction ends with +** EndCoroutine, then jump to P2 rather than continuing with the +** next instruction. +** +** See also: InitCoroutine */ case OP_Yield: { /* in1, jump */ int pcDest; @@ -68308,9 +74592,9 @@ case OP_Yield: { /* in1, jump */ assert( VdbeMemDynamic(pIn1)==0 ); pIn1->flags = MEM_Int; pcDest = (int)pIn1->u.i; - pIn1->u.i = pc; + pIn1->u.i = (int)(pOp - aOp); REGISTER_TRACE(pOp->p1, pIn1); - pc = pcDest; + pOp = &aOp[pcDest]; break; } @@ -68361,30 +74645,34 @@ case OP_HaltIfNull: { /* in3 */ case OP_Halt: { const char *zType; const char *zLogFmt; + VdbeFrame *pFrame; + int pcx; + pcx = (int)(pOp - aOp); if( pOp->p1==SQLITE_OK && p->pFrame ){ /* Halt the sub-program. Return control to the parent frame. */ - VdbeFrame *pFrame = p->pFrame; + pFrame = p->pFrame; p->pFrame = pFrame->pParent; p->nFrame--; sqlite3VdbeSetChanges(db, p->nChange); - pc = sqlite3VdbeFrameRestore(pFrame); + pcx = sqlite3VdbeFrameRestore(pFrame); lastRowid = db->lastRowid; if( pOp->p2==OE_Ignore ){ - /* Instruction pc is the OP_Program that invoked the sub-program + /* Instruction pcx is the OP_Program that invoked the sub-program ** currently being halted. If the p2 instruction of this OP_Halt ** instruction is set to OE_Ignore, then the sub-program is throwing ** an IGNORE exception. In this case jump to the address specified ** as the p2 of the calling OP_Program. */ - pc = p->aOp[pc].p2-1; + pcx = p->aOp[pcx].p2-1; } aOp = p->aOp; aMem = p->aMem; + pOp = &aOp[pcx]; break; } p->rc = pOp->p1; p->errorAction = (u8)pOp->p2; - p->pc = pc; + p->pc = pcx; if( p->rc ){ if( pOp->p5 ){ static const char * const azType[] = { "NOT NULL", "UNIQUE", "CHECK", @@ -68401,14 +74689,13 @@ case OP_Halt: { assert( zType!=0 || pOp->p4.z!=0 ); zLogFmt = "abort at %d in [%s]: %s"; if( zType && pOp->p4.z ){ - sqlite3SetString(&p->zErrMsg, db, "%s constraint failed: %s", - zType, pOp->p4.z); + sqlite3VdbeError(p, "%s constraint failed: %s", zType, pOp->p4.z); }else if( pOp->p4.z ){ - sqlite3SetString(&p->zErrMsg, db, "%s", pOp->p4.z); + sqlite3VdbeError(p, "%s", pOp->p4.z); }else{ - sqlite3SetString(&p->zErrMsg, db, "%s constraint failed", zType); + sqlite3VdbeError(p, "%s constraint failed", zType); } - sqlite3_log(pOp->p1, zLogFmt, pc, p->zSql, p->zErrMsg); + sqlite3_log(pOp->p1, zLogFmt, pcx, p->zSql, p->zErrMsg); } rc = sqlite3VdbeHalt(p); assert( rc==SQLITE_BUSY || rc==SQLITE_OK || rc==SQLITE_ERROR ); @@ -68427,7 +74714,8 @@ case OP_Halt: { ** ** The 32-bit integer value P1 is written into register P2. */ -case OP_Integer: { /* out2-prerelease */ +case OP_Integer: { /* out2 */ + pOut = out2Prerelease(p, pOp); pOut->u.i = pOp->p1; break; } @@ -68438,7 +74726,8 @@ case OP_Integer: { /* out2-prerelease */ ** P4 is a pointer to a 64-bit integer value. ** Write that value into register P2. */ -case OP_Int64: { /* out2-prerelease */ +case OP_Int64: { /* out2 */ + pOut = out2Prerelease(p, pOp); assert( pOp->p4.pI64!=0 ); pOut->u.i = *pOp->p4.pI64; break; @@ -68451,10 +74740,11 @@ case OP_Int64: { /* out2-prerelease */ ** P4 is a pointer to a 64-bit floating point value. ** Write that value into register P2. */ -case OP_Real: { /* same as TK_FLOAT, out2-prerelease */ +case OP_Real: { /* same as TK_FLOAT, out2 */ + pOut = out2Prerelease(p, pOp); pOut->flags = MEM_Real; assert( !sqlite3IsNaN(*pOp->p4.pReal) ); - pOut->r = *pOp->p4.pReal; + pOut->u.r = *pOp->p4.pReal; break; } #endif @@ -68463,12 +74753,13 @@ case OP_Real: { /* same as TK_FLOAT, out2-prerelease */ ** Synopsis: r[P2]='P4' ** ** P4 points to a nul terminated UTF-8 string. This opcode is transformed -** into an OP_String before it is executed for the first time. During +** into a String opcode before it is executed for the first time. During ** this transformation, the length of string P4 is computed and stored ** as the P1 parameter. */ -case OP_String8: { /* same as TK_STRING, out2-prerelease */ +case OP_String8: { /* same as TK_STRING, out2 */ assert( pOp->p4.z!=0 ); + pOut = out2Prerelease(p, pOp); pOp->opcode = OP_String; pOp->p1 = sqlite3Strlen30(pOp->p4.z); @@ -68477,9 +74768,9 @@ case OP_String8: { /* same as TK_STRING, out2-prerelease */ rc = sqlite3VdbeMemSetStr(pOut, pOp->p4.z, -1, SQLITE_UTF8, SQLITE_STATIC); if( rc==SQLITE_TOOBIG ) goto too_big; if( SQLITE_OK!=sqlite3VdbeChangeEncoding(pOut, encoding) ) goto no_mem; - assert( pOut->zMalloc==pOut->z ); + assert( pOut->szMalloc>0 && pOut->zMalloc==pOut->z ); assert( VdbeMemDynamic(pOut)==0 ); - pOut->zMalloc = 0; + pOut->szMalloc = 0; pOut->flags |= MEM_Static; if( pOp->p4type==P4_DYNAMIC ){ sqlite3DbFree(db, pOp->p4.z); @@ -68495,18 +74786,33 @@ case OP_String8: { /* same as TK_STRING, out2-prerelease */ /* Fall through to the next case, OP_String */ } -/* Opcode: String P1 P2 * P4 * +/* Opcode: String P1 P2 P3 P4 P5 ** Synopsis: r[P2]='P4' (len=P1) ** ** The string value P4 of length P1 (bytes) is stored in register P2. +** +** If P5!=0 and the content of register P3 is greater than zero, then +** the datatype of the register P2 is converted to BLOB. The content is +** the same sequence of bytes, it is merely interpreted as a BLOB instead +** of a string, as if it had been CAST. */ -case OP_String: { /* out2-prerelease */ +case OP_String: { /* out2 */ assert( pOp->p4.z!=0 ); + pOut = out2Prerelease(p, pOp); pOut->flags = MEM_Str|MEM_Static|MEM_Term; pOut->z = pOp->p4.z; pOut->n = pOp->p1; pOut->enc = encoding; UPDATE_MAX_BLOBSIZE(pOut); +#ifndef SQLITE_LIKE_DOESNT_MATCH_BLOBS + if( pOp->p5 ){ + assert( pOp->p3>0 ); + assert( pOp->p3<=(p->nMem-p->nCursor) ); + pIn3 = &aMem[pOp->p3]; + assert( pIn3->flags & MEM_Int ); + if( pIn3->u.i ) pOut->flags = MEM_Blob|MEM_Static|MEM_Term; + } +#endif break; } @@ -68522,16 +74828,17 @@ case OP_String: { /* out2-prerelease */ ** NULL values will not compare equal even if SQLITE_NULLEQ is set on ** OP_Ne or OP_Eq. */ -case OP_Null: { /* out2-prerelease */ +case OP_Null: { /* out2 */ int cnt; u16 nullFlag; + pOut = out2Prerelease(p, pOp); cnt = pOp->p3-pOp->p2; assert( pOp->p3<=(p->nMem-p->nCursor) ); pOut->flags = nullFlag = pOp->p1 ? (MEM_Null|MEM_Cleared) : MEM_Null; while( cnt>0 ){ pOut++; memAboutToChange(p, pOut); - VdbeMemRelease(pOut); + sqlite3VdbeMemSetNull(pOut); pOut->flags = nullFlag; cnt--; } @@ -68559,8 +74866,9 @@ case OP_SoftNull: { ** P4 points to a blob of data P1 bytes long. Store this ** blob in register P2. */ -case OP_Blob: { /* out2-prerelease */ +case OP_Blob: { /* out2 */ assert( pOp->p1 <= SQLITE_MAX_LENGTH ); + pOut = out2Prerelease(p, pOp); sqlite3VdbeMemSetStr(pOut, pOp->p4.z, pOp->p1, 0, 0); pOut->enc = encoding; UPDATE_MAX_BLOBSIZE(pOut); @@ -68575,7 +74883,7 @@ case OP_Blob: { /* out2-prerelease */ ** If the parameter is named, then its name appears in P4. ** The P4 value is used by sqlite3_bind_parameter_name(). */ -case OP_Variable: { /* out2-prerelease */ +case OP_Variable: { /* out2 */ Mem *pVar; /* Value being transferred */ assert( pOp->p1>0 && pOp->p1<=p->nVar ); @@ -68584,6 +74892,7 @@ case OP_Variable: { /* out2-prerelease */ if( sqlite3VdbeMemTooBig(pVar) ){ goto too_big; } + pOut = out2Prerelease(p, pOp); sqlite3VdbeMemShallowCopy(pOut, pVar, MEM_Static); UPDATE_MAX_BLOBSIZE(pOut); break; @@ -68599,7 +74908,6 @@ case OP_Variable: { /* out2-prerelease */ ** for P3 to be less than 1. */ case OP_Move: { - char *zMalloc; /* Holding variable for allocated memory */ int n; /* Number of registers left to copy */ int p1; /* Register to copy from */ int p2; /* Register to copy to */ @@ -68617,17 +74925,13 @@ case OP_Move: { assert( pIn1<=&aMem[(p->nMem-p->nCursor)] ); assert( memIsValid(pIn1) ); memAboutToChange(p, pOut); - VdbeMemRelease(pOut); - zMalloc = pOut->zMalloc; - memcpy(pOut, pIn1, sizeof(Mem)); + sqlite3VdbeMemMove(pOut, pIn1); #ifdef SQLITE_DEBUG - if( pOut->pScopyFrom>=&aMem[p1] && pOut->pScopyFrom<&aMem[p1+pOp->p3] ){ - pOut->pScopyFrom += p1 - pOp->p2; + if( pOut->pScopyFrom>=&aMem[p1] && pOut->pScopyFrompScopyFrom += pOp->p2 - p1; } #endif - pIn1->flags = MEM_Undefined; - pIn1->xDel = 0; - pIn1->zMalloc = zMalloc; + Deephemeralize(pOut); REGISTER_TRACE(p2++, pOut); pIn1++; pOut++; @@ -68688,6 +74992,22 @@ case OP_SCopy: { /* out2 */ break; } +/* Opcode: IntCopy P1 P2 * * * +** Synopsis: r[P2]=r[P1] +** +** Transfer the integer value held in register P1 into register P2. +** +** This is an optimized version of SCopy that works only for integer +** values. +*/ +case OP_IntCopy: { /* out2 */ + pIn1 = &aMem[pOp->p1]; + assert( (pIn1->flags & MEM_Int)!=0 ); + pOut = &aMem[pOp->p2]; + sqlite3VdbeMemSetInt64(pOut, pIn1->u.i); + break; +} + /* Opcode: ResultRow P1 P2 * * * ** Synopsis: output=r[P1@P2] ** @@ -68766,7 +75086,7 @@ case OP_ResultRow: { /* Return SQLITE_ROW */ - p->pc = pc + 1; + p->pc = (int)(pOp - aOp) + 1; rc = SQLITE_ROW; goto vdbe_return; } @@ -68932,7 +75252,7 @@ fp_math: if( sqlite3IsNaN(rB) ){ goto arithmetic_result_is_null; } - pOut->r = rB; + pOut->u.r = rB; MemSetTypeFlag(pOut, MEM_Real); if( ((type1|type2)&MEM_Real)==0 && !bIntint ){ sqlite3VdbeIntegerAffinity(pOut); @@ -68959,7 +75279,7 @@ arithmetic_result_is_null: ** ** The interface used by the implementation of the aforementioned functions ** to retrieve the collation sequence set by this opcode is not available -** publicly, only to user functions defined in func.c. +** publicly. Only built-in functions have access to this feature. */ case OP_CollSeq: { assert( pOp->p4type==P4_COLLSEQ ); @@ -68969,10 +75289,10 @@ case OP_CollSeq: { break; } -/* Opcode: Function P1 P2 P3 P4 P5 +/* Opcode: Function0 P1 P2 P3 P4 P5 ** Synopsis: r[P3]=func(r[P2@P5]) ** -** Invoke a user function (P4 is a pointer to a Function structure that +** Invoke a user function (P4 is a pointer to a FuncDef object that ** defines the function) with P5 arguments taken from register P2 and ** successors. The result of the function is stored in register P3. ** Register P3 must not be one of the function inputs. @@ -68984,95 +75304,100 @@ case OP_CollSeq: { ** sqlite3_set_auxdata() API may be safely retained until the next ** invocation of this opcode. ** -** See also: AggStep and AggFinal +** See also: Function, AggStep, AggFinal */ -case OP_Function: { - int i; - Mem *pArg; - sqlite3_context ctx; - sqlite3_value **apVal; +/* Opcode: Function P1 P2 P3 P4 P5 +** Synopsis: r[P3]=func(r[P2@P5]) +** +** Invoke a user function (P4 is a pointer to an sqlite3_context object that +** contains a pointer to the function to be run) with P5 arguments taken +** from register P2 and successors. The result of the function is stored +** in register P3. Register P3 must not be one of the function inputs. +** +** P1 is a 32-bit bitmask indicating whether or not each argument to the +** function was determined to be constant at compile time. If the first +** argument was constant then bit 0 of P1 is set. This is used to determine +** whether meta data associated with a user function argument using the +** sqlite3_set_auxdata() API may be safely retained until the next +** invocation of this opcode. +** +** SQL functions are initially coded as OP_Function0 with P4 pointing +** to a FuncDef object. But on first evaluation, the P4 operand is +** automatically converted into an sqlite3_context object and the operation +** changed to this OP_Function opcode. In this way, the initialization of +** the sqlite3_context object occurs only once, rather than once for each +** evaluation of the function. +** +** See also: Function0, AggStep, AggFinal +*/ +case OP_Function0: { int n; - - n = pOp->p5; - apVal = p->apArg; - assert( apVal || n==0 ); - assert( pOp->p3>0 && pOp->p3<=(p->nMem-p->nCursor) ); - pOut = &aMem[pOp->p3]; - memAboutToChange(p, pOut); - - assert( n==0 || (pOp->p2>0 && pOp->p2+n<=(p->nMem-p->nCursor)+1) ); - assert( pOp->p3p2 || pOp->p3>=pOp->p2+n ); - pArg = &aMem[pOp->p2]; - for(i=0; ip2+i, pArg); - } + sqlite3_context *pCtx; assert( pOp->p4type==P4_FUNCDEF ); - ctx.pFunc = pOp->p4.pFunc; - ctx.iOp = pc; - ctx.pVdbe = p; + n = pOp->p5; + assert( pOp->p3>0 && pOp->p3<=(p->nMem-p->nCursor) ); + assert( n==0 || (pOp->p2>0 && pOp->p2+n<=(p->nMem-p->nCursor)+1) ); + assert( pOp->p3p2 || pOp->p3>=pOp->p2+n ); + pCtx = sqlite3DbMallocRaw(db, sizeof(*pCtx) + (n-1)*sizeof(sqlite3_value*)); + if( pCtx==0 ) goto no_mem; + pCtx->pOut = 0; + pCtx->pFunc = pOp->p4.pFunc; + pCtx->iOp = (int)(pOp - aOp); + pCtx->pVdbe = p; + pCtx->argc = n; + pOp->p4type = P4_FUNCCTX; + pOp->p4.pCtx = pCtx; + pOp->opcode = OP_Function; + /* Fall through into OP_Function */ +} +case OP_Function: { + int i; + sqlite3_context *pCtx; - /* The output cell may already have a buffer allocated. Move - ** the pointer to ctx.s so in case the user-function can use - ** the already allocated buffer instead of allocating a new one. - */ - memcpy(&ctx.s, pOut, sizeof(Mem)); - pOut->flags = MEM_Null; - pOut->xDel = 0; - pOut->zMalloc = 0; - MemSetTypeFlag(&ctx.s, MEM_Null); + assert( pOp->p4type==P4_FUNCCTX ); + pCtx = pOp->p4.pCtx; - ctx.fErrorOrAux = 0; - if( ctx.pFunc->funcFlags & SQLITE_FUNC_NEEDCOLL ){ - assert( pOp>aOp ); - assert( pOp[-1].p4type==P4_COLLSEQ ); - assert( pOp[-1].opcode==OP_CollSeq ); - ctx.pColl = pOp[-1].p4.pColl; + /* If this function is inside of a trigger, the register array in aMem[] + ** might change from one evaluation to the next. The next block of code + ** checks to see if the register array has changed, and if so it + ** reinitializes the relavant parts of the sqlite3_context object */ + pOut = &aMem[pOp->p3]; + if( pCtx->pOut != pOut ){ + pCtx->pOut = pOut; + for(i=pCtx->argc-1; i>=0; i--) pCtx->argv[i] = &aMem[pOp->p2+i]; } + + memAboutToChange(p, pCtx->pOut); +#ifdef SQLITE_DEBUG + for(i=0; iargc; i++){ + assert( memIsValid(pCtx->argv[i]) ); + REGISTER_TRACE(pOp->p2+i, pCtx->argv[i]); + } +#endif + MemSetTypeFlag(pCtx->pOut, MEM_Null); + pCtx->fErrorOrAux = 0; db->lastRowid = lastRowid; - (*ctx.pFunc->xFunc)(&ctx, n, apVal); /* IMP: R-24505-23230 */ - lastRowid = db->lastRowid; - - if( db->mallocFailed ){ - /* Even though a malloc() has failed, the implementation of the - ** user function may have called an sqlite3_result_XXX() function - ** to return a value. The following call releases any resources - ** associated with such a value. - */ - sqlite3VdbeMemRelease(&ctx.s); - goto no_mem; - } + (*pCtx->pFunc->xFunc)(pCtx, pCtx->argc, pCtx->argv); /* IMP: R-24505-23230 */ + lastRowid = db->lastRowid; /* Remember rowid changes made by xFunc */ /* If the function returned an error, throw an exception */ - if( ctx.fErrorOrAux ){ - if( ctx.isError ){ - sqlite3SetString(&p->zErrMsg, db, "%s", sqlite3_value_text(&ctx.s)); - rc = ctx.isError; + if( pCtx->fErrorOrAux ){ + if( pCtx->isError ){ + sqlite3VdbeError(p, "%s", sqlite3_value_text(pCtx->pOut)); + rc = pCtx->isError; } - sqlite3VdbeDeleteAuxData(p, pc, pOp->p1); + sqlite3VdbeDeleteAuxData(p, pCtx->iOp, pOp->p1); } /* Copy the result of the function into register P3 */ - sqlite3VdbeChangeEncoding(&ctx.s, encoding); - assert( pOut->flags==MEM_Null ); - memcpy(pOut, &ctx.s, sizeof(Mem)); - if( sqlite3VdbeMemTooBig(pOut) ){ - goto too_big; + if( pOut->flags & (MEM_Str|MEM_Blob) ){ + sqlite3VdbeChangeEncoding(pCtx->pOut, encoding); + if( sqlite3VdbeMemTooBig(pCtx->pOut) ) goto too_big; } -#if 0 - /* The app-defined function has done something that as caused this - ** statement to expire. (Perhaps the function called sqlite3_exec() - ** with a CREATE TABLE statement.) - */ - if( p->expired ) rc = SQLITE_ABORT; -#endif - - REGISTER_TRACE(pOp->p3, pOut); - UPDATE_MAX_BLOBSIZE(pOut); + REGISTER_TRACE(pOp->p3, pCtx->pOut); + UPDATE_MAX_BLOBSIZE(pCtx->pOut); break; } @@ -69191,8 +75516,7 @@ case OP_MustBeInt: { /* jump, in1 */ rc = SQLITE_MISMATCH; goto abort_due_to_error; }else{ - pc = pOp->p2 - 1; - break; + goto jump_to_p2; } } } @@ -69220,106 +75544,37 @@ case OP_RealAffinity: { /* in1 */ #endif #ifndef SQLITE_OMIT_CAST -/* Opcode: ToText P1 * * * * +/* Opcode: Cast P1 P2 * * * +** Synopsis: affinity(r[P1]) ** -** Force the value in register P1 to be text. -** If the value is numeric, convert it to a string using the -** equivalent of sprintf(). Blob values are unchanged and -** are afterwards simply interpreted as text. +** Force the value in register P1 to be the type defined by P2. +** +**
      +**
    • TEXT +**
    • BLOB +**
    • NUMERIC +**
    • INTEGER +**
    • REAL +**
    ** ** A NULL value is not changed by this routine. It remains NULL. */ -case OP_ToText: { /* same as TK_TO_TEXT, in1 */ +case OP_Cast: { /* in1 */ + assert( pOp->p2>=SQLITE_AFF_BLOB && pOp->p2<=SQLITE_AFF_REAL ); + testcase( pOp->p2==SQLITE_AFF_TEXT ); + testcase( pOp->p2==SQLITE_AFF_BLOB ); + testcase( pOp->p2==SQLITE_AFF_NUMERIC ); + testcase( pOp->p2==SQLITE_AFF_INTEGER ); + testcase( pOp->p2==SQLITE_AFF_REAL ); pIn1 = &aMem[pOp->p1]; memAboutToChange(p, pIn1); - if( pIn1->flags & MEM_Null ) break; - assert( MEM_Str==(MEM_Blob>>3) ); - pIn1->flags |= (pIn1->flags&MEM_Blob)>>3; - applyAffinity(pIn1, SQLITE_AFF_TEXT, encoding); rc = ExpandBlob(pIn1); - assert( pIn1->flags & MEM_Str || db->mallocFailed ); - pIn1->flags &= ~(MEM_Int|MEM_Real|MEM_Blob|MEM_Zero); + sqlite3VdbeMemCast(pIn1, pOp->p2, encoding); UPDATE_MAX_BLOBSIZE(pIn1); break; } - -/* Opcode: ToBlob P1 * * * * -** -** Force the value in register P1 to be a BLOB. -** If the value is numeric, convert it to a string first. -** Strings are simply reinterpreted as blobs with no change -** to the underlying data. -** -** A NULL value is not changed by this routine. It remains NULL. -*/ -case OP_ToBlob: { /* same as TK_TO_BLOB, in1 */ - pIn1 = &aMem[pOp->p1]; - if( pIn1->flags & MEM_Null ) break; - if( (pIn1->flags & MEM_Blob)==0 ){ - applyAffinity(pIn1, SQLITE_AFF_TEXT, encoding); - assert( pIn1->flags & MEM_Str || db->mallocFailed ); - MemSetTypeFlag(pIn1, MEM_Blob); - }else{ - pIn1->flags &= ~(MEM_TypeMask&~MEM_Blob); - } - UPDATE_MAX_BLOBSIZE(pIn1); - break; -} - -/* Opcode: ToNumeric P1 * * * * -** -** Force the value in register P1 to be numeric (either an -** integer or a floating-point number.) -** If the value is text or blob, try to convert it to an using the -** equivalent of atoi() or atof() and store 0 if no such conversion -** is possible. -** -** A NULL value is not changed by this routine. It remains NULL. -*/ -case OP_ToNumeric: { /* same as TK_TO_NUMERIC, in1 */ - pIn1 = &aMem[pOp->p1]; - sqlite3VdbeMemNumerify(pIn1); - break; -} #endif /* SQLITE_OMIT_CAST */ -/* Opcode: ToInt P1 * * * * -** -** Force the value in register P1 to be an integer. If -** The value is currently a real number, drop its fractional part. -** If the value is text or blob, try to convert it to an integer using the -** equivalent of atoi() and store 0 if no such conversion is possible. -** -** A NULL value is not changed by this routine. It remains NULL. -*/ -case OP_ToInt: { /* same as TK_TO_INT, in1 */ - pIn1 = &aMem[pOp->p1]; - if( (pIn1->flags & MEM_Null)==0 ){ - sqlite3VdbeMemIntegerify(pIn1); - } - break; -} - -#if !defined(SQLITE_OMIT_CAST) && !defined(SQLITE_OMIT_FLOATING_POINT) -/* Opcode: ToReal P1 * * * * -** -** Force the value in register P1 to be a floating point number. -** If The value is currently an integer, convert it. -** If the value is text or blob, try to convert it to an integer using the -** equivalent of atoi() and store 0.0 if no such conversion is possible. -** -** A NULL value is not changed by this routine. It remains NULL. -*/ -case OP_ToReal: { /* same as TK_TO_REAL, in1 */ - pIn1 = &aMem[pOp->p1]; - memAboutToChange(p, pIn1); - if( (pIn1->flags & MEM_Null)==0 ){ - sqlite3VdbeMemRealify(pIn1); - } - break; -} -#endif /* !defined(SQLITE_OMIT_CAST) && !defined(SQLITE_OMIT_FLOATING_POINT) */ - /* Opcode: Lt P1 P2 P3 P4 P5 ** Synopsis: if r[P1]p5 & SQLITE_STOREP2 ){ pOut = &aMem[pOp->p2]; + memAboutToChange(p, pOut); MemSetTypeFlag(pOut, MEM_Null); REGISTER_TRACE(pOp->p2, pOut); }else{ VdbeBranchTaken(2,3); if( pOp->p5 & SQLITE_JUMPIFNULL ){ - pc = pOp->p2-1; + goto jump_to_p2; } } break; @@ -69455,15 +75711,38 @@ case OP_Ge: { /* same as TK_GE, jump, in1, in3 */ }else{ /* Neither operand is NULL. Do a comparison. */ affinity = pOp->p5 & SQLITE_AFF_MASK; - if( affinity ){ - applyAffinity(pIn1, affinity, encoding); - applyAffinity(pIn3, affinity, encoding); - if( db->mallocFailed ) goto no_mem; + if( affinity>=SQLITE_AFF_NUMERIC ){ + if( (flags1 & (MEM_Int|MEM_Real|MEM_Str))==MEM_Str ){ + applyNumericAffinity(pIn1,0); + } + if( (flags3 & (MEM_Int|MEM_Real|MEM_Str))==MEM_Str ){ + applyNumericAffinity(pIn3,0); + } + }else if( affinity==SQLITE_AFF_TEXT ){ + if( (flags1 & MEM_Str)==0 && (flags1 & (MEM_Int|MEM_Real))!=0 ){ + testcase( pIn1->flags & MEM_Int ); + testcase( pIn1->flags & MEM_Real ); + sqlite3VdbeMemStringify(pIn1, encoding, 1); + testcase( (flags1&MEM_Dyn) != (pIn1->flags&MEM_Dyn) ); + flags1 = (pIn1->flags & ~MEM_TypeMask) | (flags1 & MEM_TypeMask); + } + if( (flags3 & MEM_Str)==0 && (flags3 & (MEM_Int|MEM_Real))!=0 ){ + testcase( pIn3->flags & MEM_Int ); + testcase( pIn3->flags & MEM_Real ); + sqlite3VdbeMemStringify(pIn3, encoding, 1); + testcase( (flags3&MEM_Dyn) != (pIn3->flags&MEM_Dyn) ); + flags3 = (pIn3->flags & ~MEM_TypeMask) | (flags3 & MEM_TypeMask); + } } - assert( pOp->p4type==P4_COLLSEQ || pOp->p4.pColl==0 ); - ExpandBlob(pIn1); - ExpandBlob(pIn3); + if( flags1 & MEM_Zero ){ + sqlite3VdbeMemExpandBlob(pIn1); + flags1 &= ~MEM_Zero; + } + if( flags3 & MEM_Zero ){ + sqlite3VdbeMemExpandBlob(pIn3); + flags3 &= ~MEM_Zero; + } res = sqlite3MemCompare(pIn3, pIn1, pOp->p4.pColl); } switch( pOp->opcode ){ @@ -69475,6 +75754,12 @@ case OP_Ge: { /* same as TK_GE, jump, in1, in3 */ default: res = res>=0; break; } + /* Undo any changes made by applyAffinity() to the input registers. */ + assert( (pIn1->flags & MEM_Dyn) == (flags1 & MEM_Dyn) ); + pIn1->flags = flags1; + assert( (pIn3->flags & MEM_Dyn) == (flags3 & MEM_Dyn) ); + pIn3->flags = flags3; + if( pOp->p5 & SQLITE_STOREP2 ){ pOut = &aMem[pOp->p2]; memAboutToChange(p, pOut); @@ -69484,12 +75769,9 @@ case OP_Ge: { /* same as TK_GE, jump, in1, in3 */ }else{ VdbeBranchTaken(res!=0, (pOp->p5 & SQLITE_NULLEQ)?2:3); if( res ){ - pc = pOp->p2-1; + goto jump_to_p2; } } - /* Undo any changes made by applyAffinity() to the input registers. */ - pIn1->flags = (pIn1->flags&~MEM_TypeMask) | (flags1&MEM_TypeMask); - pIn3->flags = (pIn3->flags&~MEM_TypeMask) | (flags3&MEM_TypeMask); break; } @@ -69584,11 +75866,11 @@ case OP_Compare: { */ case OP_Jump: { /* jump */ if( iCompare<0 ){ - pc = pOp->p1 - 1; VdbeBranchTaken(0,3); + VdbeBranchTaken(0,3); pOp = &aOp[pOp->p1 - 1]; }else if( iCompare==0 ){ - pc = pOp->p2 - 1; VdbeBranchTaken(1,3); + VdbeBranchTaken(1,3); pOp = &aOp[pOp->p2 - 1]; }else{ - pc = pOp->p3 - 1; VdbeBranchTaken(2,3); + VdbeBranchTaken(2,3); pOp = &aOp[pOp->p3 - 1]; } break; } @@ -69657,10 +75939,10 @@ case OP_Or: { /* same as TK_OR, in1, in2, out3 */ case OP_Not: { /* same as TK_NOT, in1, out2 */ pIn1 = &aMem[pOp->p1]; pOut = &aMem[pOp->p2]; - if( pIn1->flags & MEM_Null ){ - sqlite3VdbeMemSetNull(pOut); - }else{ - sqlite3VdbeMemSetInt64(pOut, !sqlite3VdbeIntValue(pIn1)); + sqlite3VdbeMemSetNull(pOut); + if( (pIn1->flags & MEM_Null)==0 ){ + pOut->flags = MEM_Int; + pOut->u.i = !sqlite3VdbeIntValue(pIn1); } break; } @@ -69675,26 +75957,30 @@ case OP_Not: { /* same as TK_NOT, in1, out2 */ case OP_BitNot: { /* same as TK_BITNOT, in1, out2 */ pIn1 = &aMem[pOp->p1]; pOut = &aMem[pOp->p2]; - if( pIn1->flags & MEM_Null ){ - sqlite3VdbeMemSetNull(pOut); - }else{ - sqlite3VdbeMemSetInt64(pOut, ~sqlite3VdbeIntValue(pIn1)); + sqlite3VdbeMemSetNull(pOut); + if( (pIn1->flags & MEM_Null)==0 ){ + pOut->flags = MEM_Int; + pOut->u.i = ~sqlite3VdbeIntValue(pIn1); } break; } /* Opcode: Once P1 P2 * * * ** -** Check if OP_Once flag P1 is set. If so, jump to instruction P2. Otherwise, -** set the flag and fall through to the next instruction. In other words, -** this opcode causes all following opcodes up through P2 (but not including -** P2) to run just once and to be skipped on subsequent times through the loop. +** Check the "once" flag number P1. If it is set, jump to instruction P2. +** Otherwise, set the flag and fall through to the next instruction. +** In other words, this opcode causes all following opcodes up through P2 +** (but not including P2) to run just once and to be skipped on subsequent +** times through the loop. +** +** All "once" flags are initially cleared whenever a prepared statement +** first begins to run. */ case OP_Once: { /* jump */ assert( pOp->p1nOnceFlag ); VdbeBranchTaken(p->aOnceFlag[pOp->p1]!=0, 2); if( p->aOnceFlag[pOp->p1] ){ - pc = pOp->p2-1; + goto jump_to_p2; }else{ p->aOnceFlag[pOp->p1] = 1; } @@ -69705,13 +75991,13 @@ case OP_Once: { /* jump */ ** ** Jump to P2 if the value in register P1 is true. The value ** is considered true if it is numeric and non-zero. If the value -** in P1 is NULL then take the jump if P3 is non-zero. +** in P1 is NULL then take the jump if and only if P3 is non-zero. */ /* Opcode: IfNot P1 P2 P3 * * ** ** Jump to P2 if the value in register P1 is False. The value ** is considered false if it has a numeric value of zero. If the value -** in P1 is NULL then take the jump if P3 is zero. +** in P1 is NULL then take the jump if and only if P3 is non-zero. */ case OP_If: /* jump, in1 */ case OP_IfNot: { /* jump, in1 */ @@ -69729,7 +76015,7 @@ case OP_IfNot: { /* jump, in1 */ } VdbeBranchTaken(c!=0, 2); if( c ){ - pc = pOp->p2-1; + goto jump_to_p2; } break; } @@ -69743,7 +76029,7 @@ case OP_IsNull: { /* same as TK_ISNULL, jump, in1 */ pIn1 = &aMem[pOp->p1]; VdbeBranchTaken( (pIn1->flags & MEM_Null)!=0, 2); if( (pIn1->flags & MEM_Null)!=0 ){ - pc = pOp->p2 - 1; + goto jump_to_p2; } break; } @@ -69757,7 +76043,7 @@ case OP_NotNull: { /* same as TK_NOTNULL, jump, in1 */ pIn1 = &aMem[pOp->p1]; VdbeBranchTaken( (pIn1->flags & MEM_Null)==0, 2); if( (pIn1->flags & MEM_Null)==0 ){ - pc = pOp->p2 - 1; + goto jump_to_p2; } break; } @@ -69792,7 +76078,6 @@ case OP_Column: { int p2; /* column number to retrieve */ VdbeCursor *pC; /* The VDBE cursor */ BtCursor *pCrsr; /* The BTree cursor */ - u32 *aType; /* aType[i] holds the numeric type of the i-th column */ u32 *aOffset; /* aOffset[i] is offset to start of data for i-th column */ int len; /* The length of the serialized data for the column */ int i; /* Loop counter */ @@ -69802,9 +76087,10 @@ case OP_Column: { const u8 *zHdr; /* Next unparsed byte of the header */ const u8 *zEndHdr; /* Pointer to first byte after the header */ u32 offset; /* Offset into the data */ - u32 szField; /* Number of bytes in the content of a field */ + u64 offset64; /* 64-bit offset */ u32 avail; /* Number of bytes of available data */ u32 t; /* A type code from the record header */ + u16 fx; /* pDest->flags value */ Mem *pReg; /* PseudoTable input register */ p2 = pOp->p2; @@ -69815,32 +76101,30 @@ case OP_Column: { pC = p->apCsr[pOp->p1]; assert( pC!=0 ); assert( p2nField ); - aType = pC->aType; - aOffset = aType + pC->nField; -#ifndef SQLITE_OMIT_VIRTUALTABLE - assert( pC->pVtabCursor==0 ); /* OP_Column never called on virtual table */ -#endif - pCrsr = pC->pCursor; - assert( pCrsr!=0 || pC->pseudoTableReg>0 ); /* pCrsr NULL on PseudoTables */ - assert( pCrsr!=0 || pC->nullRow ); /* pC->nullRow on PseudoTables */ + aOffset = pC->aOffset; + assert( pC->eCurType!=CURTYPE_VTAB ); + assert( pC->eCurType!=CURTYPE_PSEUDO || pC->nullRow ); + assert( pC->eCurType!=CURTYPE_SORTER ); + pCrsr = pC->uc.pCursor; /* If the cursor cache is stale, bring it up-to-date */ rc = sqlite3VdbeCursorMoveto(pC); if( rc ) goto abort_due_to_error; - if( pC->cacheStatus!=p->cacheCtr || (pOp->p5&OPFLAG_CLEARCACHE)!=0 ){ + if( pC->cacheStatus!=p->cacheCtr ){ if( pC->nullRow ){ - if( pCrsr==0 ){ - assert( pC->pseudoTableReg>0 ); - pReg = &aMem[pC->pseudoTableReg]; + if( pC->eCurType==CURTYPE_PSEUDO ){ + assert( pC->uc.pseudoTableReg>0 ); + pReg = &aMem[pC->uc.pseudoTableReg]; assert( pReg->flags & MEM_Blob ); assert( memIsValid(pReg) ); pC->payloadSize = pC->szRow = avail = pReg->n; pC->aRow = (u8*)pReg->z; }else{ - MemSetTypeFlag(pDest, MEM_Null); + sqlite3VdbeMemSetNull(pDest); goto op_column_out; } }else{ + assert( pC->eCurType==CURTYPE_BTREE ); assert( pCrsr ); if( pC->isTable==0 ){ assert( sqlite3BtreeCursorIsValid(pCrsr) ); @@ -69861,17 +76145,18 @@ case OP_Column: { assert( avail<=65536 ); /* Maximum page size is 64KiB */ if( pC->payloadSize <= (u32)avail ){ pC->szRow = pC->payloadSize; + }else if( pC->payloadSize > (u32)db->aLimit[SQLITE_LIMIT_LENGTH] ){ + goto too_big; }else{ pC->szRow = avail; } - if( pC->payloadSize > (u32)db->aLimit[SQLITE_LIMIT_LENGTH] ){ - goto too_big; - } } pC->cacheStatus = p->cacheCtr; pC->iHdrOffset = getVarint32(pC->aRow, offset); pC->nHdrParsed = 0; aOffset[0] = offset; + + if( availaRow does not have to hold the entire row, but it does at least ** need to cover the header of the record. If pC->aRow does not contain @@ -69879,90 +76164,86 @@ case OP_Column: { ** dynamically allocated. */ pC->aRow = 0; pC->szRow = 0; - } - /* Make sure a corrupt database has not given us an oversize header. - ** Do this now to avoid an oversize memory allocation. - ** - ** Type entries can be between 1 and 5 bytes each. But 4 and 5 byte - ** types use so much data space that there can only be 4096 and 32 of - ** them, respectively. So the maximum header length results from a - ** 3-byte type for each of the maximum of 32768 columns plus three - ** extra bytes for the header length itself. 32768*3 + 3 = 98307. - */ - if( offset > 98307 || offset > pC->payloadSize ){ - rc = SQLITE_CORRUPT_BKPT; - goto op_column_error; - } - } - - /* Make sure at least the first p2+1 entries of the header have been - ** parsed and valid information is in aOffset[] and aType[]. - */ - if( pC->nHdrParsed<=p2 ){ - /* If there is more header available for parsing in the record, try - ** to extract additional fields up through the p2+1-th field - */ - if( pC->iHdrOffsetaRow==0 ){ - memset(&sMem, 0, sizeof(sMem)); - rc = sqlite3VdbeMemFromBtree(pCrsr, 0, aOffset[0], - !pC->isTable, &sMem); - if( rc!=SQLITE_OK ){ - goto op_column_error; - } - zData = (u8*)sMem.z; - }else{ - zData = pC->aRow; - } - - /* Fill in aType[i] and aOffset[i] values through the p2-th field. */ - i = pC->nHdrParsed; - offset = aOffset[i]; - zHdr = zData + pC->iHdrOffset; - zEndHdr = zData + aOffset[0]; - assert( i<=p2 && zHdrnHdrParsed = i; - pC->iHdrOffset = (u32)(zHdr - zData); - if( pC->aRow==0 ){ - sqlite3VdbeMemRelease(&sMem); - sMem.flags = MEM_Null; - } - - /* If we have read more header data than was contained in the header, - ** or if the end of the last field appears to be past the end of the - ** record, or if the end of the last field appears to be before the end - ** of the record (when all fields present), then we must be dealing - ** with a corrupt database. + /* Make sure a corrupt database has not given us an oversize header. + ** Do this now to avoid an oversize memory allocation. + ** + ** Type entries can be between 1 and 5 bytes each. But 4 and 5 byte + ** types use so much data space that there can only be 4096 and 32 of + ** them, respectively. So the maximum header length results from a + ** 3-byte type for each of the maximum of 32768 columns plus three + ** extra bytes for the header length itself. 32768*3 + 3 = 98307. */ - if( (zHdr > zEndHdr) - || (offset > pC->payloadSize) - || (zHdr==zEndHdr && offset!=pC->payloadSize) - ){ + if( offset > 98307 || offset > pC->payloadSize ){ rc = SQLITE_CORRUPT_BKPT; goto op_column_error; } } - /* If after trying to extra new entries from the header, nHdrParsed is + /* The following goto is an optimization. It can be omitted and + ** everything will still work. But OP_Column is measurably faster + ** by skipping the subsequent conditional, which is always true. + */ + assert( pC->nHdrParsed<=p2 ); /* Conditional skipped */ + goto op_column_read_header; + } + + /* Make sure at least the first p2+1 entries of the header have been + ** parsed and valid information is in aOffset[] and pC->aType[]. + */ + if( pC->nHdrParsed<=p2 ){ + /* If there is more header available for parsing in the record, try + ** to extract additional fields up through the p2+1-th field + */ + op_column_read_header: + if( pC->iHdrOffsetaRow==0 ){ + memset(&sMem, 0, sizeof(sMem)); + rc = sqlite3VdbeMemFromBtree(pCrsr, 0, aOffset[0], !pC->isTable, &sMem); + if( rc!=SQLITE_OK ) goto op_column_error; + zData = (u8*)sMem.z; + }else{ + zData = pC->aRow; + } + + /* Fill in pC->aType[i] and aOffset[i] values through the p2-th field. */ + i = pC->nHdrParsed; + offset64 = aOffset[i]; + zHdr = zData + pC->iHdrOffset; + zEndHdr = zData + aOffset[0]; + assert( i<=p2 && zHdraType[i++] = t; + aOffset[i] = (u32)(offset64 & 0xffffffff); + }while( i<=p2 && zHdrnHdrParsed = i; + pC->iHdrOffset = (u32)(zHdr - zData); + if( pC->aRow==0 ) sqlite3VdbeMemRelease(&sMem); + + /* The record is corrupt if any of the following are true: + ** (1) the bytes of the header extend past the declared header size + ** (2) the entire header was used but not all data was used + ** (3) the end of the data extends beyond the end of the record. + */ + if( (zHdr>=zEndHdr && (zHdr>zEndHdr || offset64!=pC->payloadSize)) + || (offset64 > pC->payloadSize) + ){ + rc = SQLITE_CORRUPT_BKPT; + goto op_column_error; + } + }else{ + t = 0; + } + + /* If after trying to extract new entries from the header, nHdrParsed is ** still not up to p2, that means that the record has fewer than p2 ** columns. So the result will be either the default value or a NULL. */ @@ -69970,68 +76251,70 @@ case OP_Column: { if( pOp->p4type==P4_MEM ){ sqlite3VdbeMemShallowCopy(pDest, pOp->p4.pMem, MEM_Static); }else{ - MemSetTypeFlag(pDest, MEM_Null); + sqlite3VdbeMemSetNull(pDest); } goto op_column_out; } + }else{ + t = pC->aType[p2]; } /* Extract the content for the p2+1-th column. Control can only - ** reach this point if aOffset[p2], aOffset[p2+1], and aType[p2] are + ** reach this point if aOffset[p2], aOffset[p2+1], and pC->aType[p2] are ** all valid. */ assert( p2nHdrParsed ); assert( rc==SQLITE_OK ); assert( sqlite3VdbeCheckMemInvariants(pDest) ); + if( VdbeMemDynamic(pDest) ) sqlite3VdbeMemSetNull(pDest); + assert( t==pC->aType[p2] ); if( pC->szRow>=aOffset[p2+1] ){ /* This is the common case where the desired content fits on the original ** page - where the content is not on an overflow page */ - VdbeMemRelease(pDest); - sqlite3VdbeSerialGet(pC->aRow+aOffset[p2], aType[p2], pDest); + sqlite3VdbeSerialGet(pC->aRow+aOffset[p2], t, pDest); }else{ /* This branch happens only when content is on overflow pages */ - t = aType[p2]; if( ((pOp->p5 & (OPFLAG_LENGTHARG|OPFLAG_TYPEOFARG))!=0 && ((t>=12 && (t&1)==0) || (pOp->p5 & OPFLAG_TYPEOFARG)!=0)) || (len = sqlite3VdbeSerialTypeLen(t))==0 ){ - /* Content is irrelevant for the typeof() function and for - ** the length(X) function if X is a blob. So we might as well use - ** bogus content rather than reading content from disk. NULL works - ** for text and blob and whatever is in the payloadSize64 variable - ** will work for everything else. Content is also irrelevant if - ** the content length is 0. */ - zData = t<=13 ? (u8*)&payloadSize64 : 0; - sMem.zMalloc = 0; + /* Content is irrelevant for + ** 1. the typeof() function, + ** 2. the length(X) function if X is a blob, and + ** 3. if the content length is zero. + ** So we might as well use bogus content rather than reading + ** content from disk. NULL will work for the value for strings + ** and blobs and whatever is in the payloadSize64 variable + ** will work for everything else. */ + sqlite3VdbeSerialGet(t<=13 ? (u8*)&payloadSize64 : 0, t, pDest); }else{ - memset(&sMem, 0, sizeof(sMem)); - sqlite3VdbeMemMove(&sMem, pDest); rc = sqlite3VdbeMemFromBtree(pCrsr, aOffset[p2], len, !pC->isTable, - &sMem); + pDest); if( rc!=SQLITE_OK ){ goto op_column_error; } - zData = (u8*)sMem.z; - } - sqlite3VdbeSerialGet(zData, t, pDest); - /* If we dynamically allocated space to hold the data (in the - ** sqlite3VdbeMemFromBtree() call above) then transfer control of that - ** dynamically allocated space over to the pDest structure. - ** This prevents a memory copy. */ - if( sMem.zMalloc ){ - assert( sMem.z==sMem.zMalloc ); - assert( VdbeMemDynamic(pDest)==0 ); - assert( (pDest->flags & (MEM_Blob|MEM_Str))==0 || pDest->z==sMem.z ); - pDest->flags &= ~(MEM_Ephem|MEM_Static); - pDest->flags |= MEM_Term; - pDest->z = sMem.z; - pDest->zMalloc = sMem.zMalloc; + sqlite3VdbeSerialGet((const u8*)pDest->z, t, pDest); + pDest->flags &= ~MEM_Ephem; } } pDest->enc = encoding; op_column_out: - Deephemeralize(pDest); + /* If the column value is an ephemeral string, go ahead and persist + ** that string in case the cursor moves before the column value is + ** used. The following code does the equivalent of Deephemeralize() + ** but does it faster. */ + if( (pDest->flags & MEM_Ephem)!=0 && pDest->z ){ + fx = pDest->flags & (MEM_Str|MEM_Blob); + assert( fx!=0 ); + zData = (const u8*)pDest->z; + len = pDest->n; + if( sqlite3VdbeMemClearAndResize(pDest, len+2) ) goto no_mem; + memcpy(pDest->z, zData, len); + pDest->z[len] = 0; + pDest->z[len+1] = 0; + pDest->flags = fx|MEM_Term; + } op_column_error: UPDATE_MAX_BLOBSIZE(pDest); REGISTER_TRACE(pOp->p3, pDest); @@ -70078,7 +76361,7 @@ case OP_Affinity: { ** The mapping from character to affinity is given by the SQLITE_AFF_ ** macros defined in sqliteInt.h. ** -** If P4 is NULL then all index fields have the affinity NONE. +** If P4 is NULL then all index fields have the affinity BLOB. */ case OP_MakeRecord: { u8 *zNewRecord; /* A buffer to hold the data for the new record */ @@ -70086,7 +76369,7 @@ case OP_MakeRecord: { u64 nData; /* Number of bytes of data space */ int nHdr; /* Number of bytes of header space */ i64 nByte; /* Data space required for this record */ - int nZero; /* Number of zero bytes at the end of the record */ + i64 nZero; /* Number of zero bytes at the end of the record */ int nVarint; /* Number of bytes in a varint */ u32 serial_type; /* Type field */ Mem *pData0; /* First field to be combined into the record */ @@ -70096,7 +76379,7 @@ case OP_MakeRecord: { int file_format; /* File format to use for encoding */ int i; /* Space used in zNewRecord[] header */ int j; /* Space used in zNewRecord[] content */ - int len; /* Length of a field */ + u32 len; /* Length of a field */ /* Assuming the record contains N fields, the record format looks ** like this: @@ -70106,7 +76389,7 @@ case OP_MakeRecord: { ** ------------------------------------------------------------------------ ** ** Data(0) is taken from register P1. Data(1) comes from register P1+1 - ** and so froth. + ** and so forth. ** ** Each type field is a varint representing the serial type of the ** corresponding data element (see sqlite3VdbeSerialType()). The @@ -70146,11 +76429,10 @@ case OP_MakeRecord: { pRec = pLast; do{ assert( memIsValid(pRec) ); - serial_type = sqlite3VdbeSerialType(pRec, file_format); - len = sqlite3VdbeSerialTypeLen(serial_type); + pRec->uTemp = serial_type = sqlite3VdbeSerialType(pRec, file_format, &len); if( pRec->flags & MEM_Zero ){ if( nData ){ - sqlite3VdbeMemExpandBlob(pRec); + if( sqlite3VdbeMemExpandBlob(pRec) ) goto no_mem; }else{ nZero += pRec->u.nZero; len -= pRec->u.nZero; @@ -70162,7 +76444,10 @@ case OP_MakeRecord: { nHdr += serial_type<=127 ? 1 : sqlite3VarintLen(serial_type); }while( (--pRec)>=pData0 ); - /* Add the initial header varint and total the size */ + /* EVIDENCE-OF: R-22564-11647 The header begins with a single varint + ** which determines the total number of bytes in the header. The varint + ** value is the size of the header in bytes including the size varint + ** itself. */ testcase( nHdr==126 ); testcase( nHdr==127 ); if( nHdr<=126 ){ @@ -70175,16 +76460,16 @@ case OP_MakeRecord: { if( nVarintdb->aLimit[SQLITE_LIMIT_LENGTH] ){ + if( nByte+nZero>db->aLimit[SQLITE_LIMIT_LENGTH] ){ goto too_big; } /* Make sure the output register has a buffer large enough to store ** the new record. The output register (pOp->p3) is not allowed to ** be one of the input registers (because the following call to - ** sqlite3VdbeMemGrow() could clobber the value before it is used). + ** sqlite3VdbeMemClearAndResize() could clobber the value before it is used). */ - if( sqlite3VdbeMemGrow(pOut, (int)nByte, 0) ){ + if( sqlite3VdbeMemClearAndResize(pOut, (int)nByte) ){ goto no_mem; } zNewRecord = (u8 *)pOut->z; @@ -70195,8 +76480,12 @@ case OP_MakeRecord: { assert( pData0<=pLast ); pRec = pData0; do{ - serial_type = sqlite3VdbeSerialType(pRec, file_format); + serial_type = pRec->uTemp; + /* EVIDENCE-OF: R-06529-47362 Following the size varint are one or more + ** additional varints, one per column. */ i += putVarint32(&zNewRecord[i], serial_type); /* serial type */ + /* EVIDENCE-OF: R-64536-51728 The values for each column in the record + ** immediately follow the header. */ j += sqlite3VdbeSerialPut(&zNewRecord[j], pRec, serial_type); /* content */ }while( (++pRec)<=pLast ); assert( i==nHdr ); @@ -70205,7 +76494,6 @@ case OP_MakeRecord: { assert( pOp->p3>0 && pOp->p3<=(p->nMem-p->nCursor) ); pOut->n = (int)nByte; pOut->flags = MEM_Blob; - pOut->xDel = 0; if( nZero ){ pOut->u.nZero = nZero; pOut->flags |= MEM_Zero; @@ -70223,14 +76511,16 @@ case OP_MakeRecord: { ** opened by cursor P1 in register P2 */ #ifndef SQLITE_OMIT_BTREECOUNT -case OP_Count: { /* out2-prerelease */ +case OP_Count: { /* out2 */ i64 nEntry; BtCursor *pCrsr; - pCrsr = p->apCsr[pOp->p1]->pCursor; + assert( p->apCsr[pOp->p1]->eCurType==CURTYPE_BTREE ); + pCrsr = p->apCsr[pOp->p1]->uc.pCursor; assert( pCrsr ); nEntry = 0; /* Not needed. Only used to silence a warning. */ rc = sqlite3BtreeCount(pCrsr, &nEntry); + pOut = out2Prerelease(p, pOp); pOut->u.i = nEntry; break; } @@ -70269,8 +76559,7 @@ case OP_Savepoint: { /* A new savepoint cannot be created if there are active write ** statements (i.e. open read/write incremental blob handles). */ - sqlite3SetString(&p->zErrMsg, db, "cannot open savepoint - " - "SQL statements in progress"); + sqlite3VdbeError(p, "cannot open savepoint - SQL statements in progress"); rc = SQLITE_BUSY; }else{ nName = sqlite3Strlen30(zName); @@ -70321,15 +76610,14 @@ case OP_Savepoint: { iSavepoint++; } if( !pSavepoint ){ - sqlite3SetString(&p->zErrMsg, db, "no such savepoint: %s", zName); + sqlite3VdbeError(p, "no such savepoint: %s", zName); rc = SQLITE_ERROR; }else if( db->nVdbeWrite>0 && p1==SAVEPOINT_RELEASE ){ /* It is not possible to release (commit) a savepoint if there are ** active write statements. */ - sqlite3SetString(&p->zErrMsg, db, - "cannot release savepoint - SQL statements in progress" - ); + sqlite3VdbeError(p, "cannot release savepoint - " + "SQL statements in progress"); rc = SQLITE_BUSY; }else{ @@ -70344,7 +76632,7 @@ case OP_Savepoint: { } db->autoCommit = 1; if( sqlite3VdbeHalt(p)==SQLITE_BUSY ){ - p->pc = pc; + p->pc = (int)(pOp - aOp); db->autoCommit = 0; p->rc = rc = SQLITE_BUSY; goto vdbe_return; @@ -70352,11 +76640,18 @@ case OP_Savepoint: { db->isTransactionSavepoint = 0; rc = p->rc; }else{ + int isSchemaChange; iSavepoint = db->nSavepoint - iSavepoint - 1; if( p1==SAVEPOINT_ROLLBACK ){ + isSchemaChange = (db->flags & SQLITE_InternChanges)!=0; for(ii=0; iinDb; ii++){ - sqlite3BtreeTripAllCursors(db->aDb[ii].pBt, SQLITE_ABORT); + rc = sqlite3BtreeTripAllCursors(db->aDb[ii].pBt, + SQLITE_ABORT_ROLLBACK, + isSchemaChange==0); + if( rc!=SQLITE_OK ) goto abort_due_to_error; } + }else{ + isSchemaChange = 0; } for(ii=0; iinDb; ii++){ rc = sqlite3BtreeSavepoint(db->aDb[ii].pBt, p1, iSavepoint); @@ -70364,7 +76659,7 @@ case OP_Savepoint: { goto abort_due_to_error; } } - if( p1==SAVEPOINT_ROLLBACK && (db->flags&SQLITE_InternChanges)!=0 ){ + if( isSchemaChange ){ sqlite3ExpirePreparedStatements(db); sqlite3ResetAllSchemasOfConnection(db); db->flags = (db->flags | SQLITE_InternChanges); @@ -70396,7 +76691,7 @@ case OP_Savepoint: { db->nDeferredImmCons = pSavepoint->nDeferredImmCons; } - if( !isTransaction ){ + if( !isTransaction || p1==SAVEPOINT_ROLLBACK ){ rc = sqlite3VtabSavepoint(db, p1, iSavepoint); if( rc!=SQLITE_OK ) goto abort_due_to_error; } @@ -70428,23 +76723,12 @@ case OP_AutoCommit: { assert( db->nVdbeActive>0 ); /* At least this one VM is active */ assert( p->bIsReader ); -#if 0 - if( turnOnAC && iRollback && db->nVdbeActive>1 ){ - /* If this instruction implements a ROLLBACK and other VMs are - ** still running, and a transaction is active, return an error indicating - ** that the other VMs must complete first. - */ - sqlite3SetString(&p->zErrMsg, db, "cannot rollback transaction - " - "SQL statements in progress"); - rc = SQLITE_BUSY; - }else -#endif if( turnOnAC && !iRollback && db->nVdbeWrite>0 ){ /* If this instruction implements a COMMIT and other VMs are writing ** return an error indicating that the other VMs must complete first. */ - sqlite3SetString(&p->zErrMsg, db, "cannot commit transaction - " - "SQL statements in progress"); + sqlite3VdbeError(p, "cannot commit transaction - " + "SQL statements in progress"); rc = SQLITE_BUSY; }else if( desiredAutoCommit!=db->autoCommit ){ if( iRollback ){ @@ -70455,12 +76739,12 @@ case OP_AutoCommit: { goto vdbe_return; }else{ db->autoCommit = (u8)desiredAutoCommit; - if( sqlite3VdbeHalt(p)==SQLITE_BUSY ){ - p->pc = pc; - db->autoCommit = (u8)(1-desiredAutoCommit); - p->rc = rc = SQLITE_BUSY; - goto vdbe_return; - } + } + if( sqlite3VdbeHalt(p)==SQLITE_BUSY ){ + p->pc = (int)(pOp - aOp); + db->autoCommit = (u8)(1-desiredAutoCommit); + p->rc = rc = SQLITE_BUSY; + goto vdbe_return; } assert( db->nStatement==0 ); sqlite3CloseSavepoints(db); @@ -70471,7 +76755,7 @@ case OP_AutoCommit: { } goto vdbe_return; }else{ - sqlite3SetString(&p->zErrMsg, db, + sqlite3VdbeError(p, (!desiredAutoCommit)?"cannot start a transaction within a transaction":( (iRollback)?"cannot rollback - no transaction is active": "cannot commit - no transaction is active")); @@ -70523,7 +76807,7 @@ case OP_Transaction: { assert( p->bIsReader ); assert( p->readOnly==0 || pOp->p2==0 ); assert( pOp->p1>=0 && pOp->p1nDb ); - assert( (p->btreeMask & (((yDbMask)1)<p1))!=0 ); + assert( DbMaskTest(p->btreeMask, pOp->p1) ); if( pOp->p2 && (db->flags & SQLITE_QueryOnly)!=0 ){ rc = SQLITE_READONLY; goto abort_due_to_error; @@ -70532,9 +76816,11 @@ case OP_Transaction: { if( pBt ){ rc = sqlite3BtreeBeginTrans(pBt, pOp->p2); - if( rc==SQLITE_BUSY ){ - p->pc = pc; - p->rc = rc = SQLITE_BUSY; + testcase( rc==SQLITE_BUSY_SNAPSHOT ); + testcase( rc==SQLITE_BUSY_RECOVERY ); + if( (rc&0xff)==SQLITE_BUSY ){ + p->pc = (int)(pOp - aOp); + p->rc = rc; goto vdbe_return; } if( rc!=SQLITE_OK ){ @@ -70563,7 +76849,12 @@ case OP_Transaction: { p->nStmtDefImmCons = db->nDeferredImmCons; } - /* Gather the schema version number for checking */ + /* Gather the schema version number for checking: + ** IMPLEMENTATION-OF: R-32195-19465 The schema version is used by SQLite + ** each time a query is executed to ensure that the internal cache of the + ** schema used when compiling the SQL query matches the schema of the + ** database against which the compiled query is actually executed. + */ sqlite3BtreeGetMeta(pBt, BTREE_SCHEMA_VERSION, (u32 *)&iMeta); iGen = db->aDb[pOp->p1].pSchema->iGeneration; }else{ @@ -70607,7 +76898,7 @@ case OP_Transaction: { ** must be started or there must be an open cursor) before ** executing this instruction. */ -case OP_ReadCookie: { /* out2-prerelease */ +case OP_ReadCookie: { /* out2 */ int iMeta; int iDb; int iCookie; @@ -70618,9 +76909,10 @@ case OP_ReadCookie: { /* out2-prerelease */ assert( pOp->p3=0 && iDbnDb ); assert( db->aDb[iDb].pBt!=0 ); - assert( (p->btreeMask & (((yDbMask)1)<btreeMask, iDb) ); sqlite3BtreeGetMeta(db->aDb[iDb].pBt, iCookie, (u32 *)&iMeta); + pOut = out2Prerelease(p, pOp); pOut->u.i = iMeta; break; } @@ -70639,7 +76931,7 @@ case OP_SetCookie: { /* in3 */ Db *pDb; assert( pOp->p2p1>=0 && pOp->p1nDb ); - assert( (p->btreeMask & (((yDbMask)1)<p1))!=0 ); + assert( DbMaskTest(p->btreeMask, pOp->p1) ); assert( p->readOnly==0 ); pDb = &db->aDb[pOp->p1]; assert( pDb->pBt!=0 ); @@ -70694,7 +76986,21 @@ case OP_SetCookie: { /* in3 */ ** sequence of the index being opened. Otherwise, if P4 is an integer ** value, it is set to the number of columns in the table. ** -** See also OpenWrite. +** See also: OpenWrite, ReopenIdx +*/ +/* Opcode: ReopenIdx P1 P2 P3 P4 P5 +** Synopsis: root=P2 iDb=P3 +** +** The ReopenIdx opcode works exactly like ReadOpen except that it first +** checks to see if the cursor on P1 is already open with a root page +** number of P2 and if it is this opcode becomes a no-op. In other words, +** if the cursor is already open, do not reopen it. +** +** The ReopenIdx opcode may only be used with P5==0 and with P4 being +** a P4_KEYINFO object. Furthermore, the P3 value must be the same as +** every other ReopenIdx or OpenRead for the same cursor number. +** +** See the OpenRead opcode documentation for additional information. */ /* Opcode: OpenWrite P1 P2 P3 P4 P5 ** Synopsis: root=P2 iDb=P3 @@ -70716,8 +77022,7 @@ case OP_SetCookie: { /* in3 */ ** ** See also OpenRead. */ -case OP_OpenRead: -case OP_OpenWrite: { +case OP_ReopenIdx: { int nField; KeyInfo *pKeyInfo; int p2; @@ -70727,13 +77032,25 @@ case OP_OpenWrite: { VdbeCursor *pCur; Db *pDb; - assert( (pOp->p5&(OPFLAG_P2ISREG|OPFLAG_BULKCSR))==pOp->p5 ); - assert( pOp->opcode==OP_OpenWrite || pOp->p5==0 ); + assert( pOp->p5==0 || pOp->p5==OPFLAG_SEEKEQ ); + assert( pOp->p4type==P4_KEYINFO ); + pCur = p->apCsr[pOp->p1]; + if( pCur && pCur->pgnoRoot==(u32)pOp->p2 ){ + assert( pCur->iDb==pOp->p3 ); /* Guaranteed by the code generator */ + goto open_cursor_set_hints; + } + /* If the cursor is not currently open or is open on a different + ** index, then fall through into OP_OpenRead to force a reopen */ +case OP_OpenRead: +case OP_OpenWrite: + + assert( pOp->opcode==OP_OpenWrite || pOp->p5==0 || pOp->p5==OPFLAG_SEEKEQ ); assert( p->bIsReader ); - assert( pOp->opcode==OP_OpenRead || p->readOnly==0 ); + assert( pOp->opcode==OP_OpenRead || pOp->opcode==OP_ReopenIdx + || p->readOnly==0 ); if( p->expired ){ - rc = SQLITE_ABORT; + rc = SQLITE_ABORT_ROLLBACK; break; } @@ -70742,12 +77059,13 @@ case OP_OpenWrite: { p2 = pOp->p2; iDb = pOp->p3; assert( iDb>=0 && iDbnDb ); - assert( (p->btreeMask & (((yDbMask)1)<btreeMask, iDb) ); pDb = &db->aDb[iDb]; pX = pDb->pBt; assert( pX!=0 ); if( pOp->opcode==OP_OpenWrite ){ - wrFlag = 1; + assert( OPFLAG_FORDELETE==BTREE_FORDELETE ); + wrFlag = BTREE_WRCSR | (pOp->p5 & OPFLAG_FORDELETE); assert( sqlite3SchemaMutexHeld(db, iDb, 0) ); if( pDb->pSchema->file_format < p->minWriteFileFormat ){ p->minWriteFileFormat = pDb->pSchema->file_format; @@ -70783,24 +77101,28 @@ case OP_OpenWrite: { assert( pOp->p1>=0 ); assert( nField>=0 ); testcase( nField==0 ); /* Table with INTEGER PRIMARY KEY and nothing else */ - pCur = allocateCursor(p, pOp->p1, nField, iDb, 1); + pCur = allocateCursor(p, pOp->p1, nField, iDb, CURTYPE_BTREE); if( pCur==0 ) goto no_mem; pCur->nullRow = 1; pCur->isOrdered = 1; - rc = sqlite3BtreeCursor(pX, p2, wrFlag, pKeyInfo, pCur->pCursor); + pCur->pgnoRoot = p2; + rc = sqlite3BtreeCursor(pX, p2, wrFlag, pKeyInfo, pCur->uc.pCursor); pCur->pKeyInfo = pKeyInfo; - assert( OPFLAG_BULKCSR==BTREE_BULKLOAD ); - sqlite3BtreeCursorHints(pCur->pCursor, (pOp->p5 & OPFLAG_BULKCSR)); - - /* Since it performs no memory allocation or IO, the only value that - ** sqlite3BtreeCursor() may return is SQLITE_OK. */ - assert( rc==SQLITE_OK ); - /* Set the VdbeCursor.isTable variable. Previous versions of ** SQLite used to check if the root-page flags were sane at this point ** and report database corruption if they were not, but this check has ** since moved into the btree layer. */ pCur->isTable = pOp->p4type!=P4_KEYINFO; + +open_cursor_set_hints: + assert( OPFLAG_BULKCSR==BTREE_BULKLOAD ); + assert( OPFLAG_SEEKEQ==BTREE_SEEK_EQ ); + testcase( pOp->p5 & OPFLAG_BULKCSR ); +#ifdef SQLITE_ENABLE_CURSOR_HINTS + testcase( pOp->p2 & OPFLAG_SEEKEQ ); +#endif + sqlite3BtreeCursorHintFlags(pCur->uc.pCursor, + (pOp->p5 & (OPFLAG_BULKCSR|OPFLAG_SEEKEQ))); break; } @@ -70843,7 +77165,7 @@ case OP_OpenEphemeral: { SQLITE_OPEN_TRANSIENT_DB; assert( pOp->p1>=0 ); assert( pOp->p2>=0 ); - pCx = allocateCursor(p, pOp->p1, pOp->p2, -1, 1); + pCx = allocateCursor(p, pOp->p1, pOp->p2, -1, CURTYPE_BTREE); if( pCx==0 ) goto no_mem; pCx->nullRow = 1; pCx->isEphemeral = 1; @@ -70867,11 +77189,13 @@ case OP_OpenEphemeral: { assert( pKeyInfo->db==db ); assert( pKeyInfo->enc==ENC(db) ); pCx->pKeyInfo = pKeyInfo; - rc = sqlite3BtreeCursor(pCx->pBt, pgno, 1, pKeyInfo, pCx->pCursor); + rc = sqlite3BtreeCursor(pCx->pBt, pgno, BTREE_WRCSR, + pKeyInfo, pCx->uc.pCursor); } pCx->isTable = 0; }else{ - rc = sqlite3BtreeCursor(pCx->pBt, MASTER_ROOT, 1, 0, pCx->pCursor); + rc = sqlite3BtreeCursor(pCx->pBt, MASTER_ROOT, BTREE_WRCSR, + 0, pCx->uc.pCursor); pCx->isTable = 1; } } @@ -70879,23 +77203,45 @@ case OP_OpenEphemeral: { break; } -/* Opcode: SorterOpen P1 P2 * P4 * +/* Opcode: SorterOpen P1 P2 P3 P4 * ** ** This opcode works like OP_OpenEphemeral except that it opens ** a transient index that is specifically designed to sort large ** tables using an external merge-sort algorithm. +** +** If argument P3 is non-zero, then it indicates that the sorter may +** assume that a stable sort considering the first P3 fields of each +** key is sufficient to produce the required results. */ case OP_SorterOpen: { VdbeCursor *pCx; assert( pOp->p1>=0 ); assert( pOp->p2>=0 ); - pCx = allocateCursor(p, pOp->p1, pOp->p2, -1, 1); + pCx = allocateCursor(p, pOp->p1, pOp->p2, -1, CURTYPE_SORTER); if( pCx==0 ) goto no_mem; pCx->pKeyInfo = pOp->p4.pKeyInfo; assert( pCx->pKeyInfo->db==db ); assert( pCx->pKeyInfo->enc==ENC(db) ); - rc = sqlite3VdbeSorterInit(db, pCx); + rc = sqlite3VdbeSorterInit(db, pOp->p3, pCx); + break; +} + +/* Opcode: SequenceTest P1 P2 * * * +** Synopsis: if( cursor[P1].ctr++ ) pc = P2 +** +** P1 is a sorter cursor. If the sequence counter is currently zero, jump +** to P2. Regardless of whether or not the jump is taken, increment the +** the sequence value. +*/ +case OP_SequenceTest: { + VdbeCursor *pC; + assert( pOp->p1>=0 && pOp->p1nCursor ); + pC = p->apCsr[pOp->p1]; + assert( isSorter(pC) ); + if( (pC->seqCount++)==0 ){ + goto jump_to_p2; + } break; } @@ -70920,10 +77266,10 @@ case OP_OpenPseudo: { assert( pOp->p1>=0 ); assert( pOp->p3>=0 ); - pCx = allocateCursor(p, pOp->p1, pOp->p3, -1, 0); + pCx = allocateCursor(p, pOp->p1, pOp->p3, -1, CURTYPE_PSEUDO); if( pCx==0 ) goto no_mem; pCx->nullRow = 1; - pCx->pseudoTableReg = pOp->p2; + pCx->uc.pseudoTableReg = pOp->p2; pCx->isTable = 1; assert( pOp->p5==0 ); break; @@ -70941,7 +77287,27 @@ case OP_Close: { break; } -/* Opcode: SeekGe P1 P2 P3 P4 * +#ifdef SQLITE_ENABLE_COLUMN_USED_MASK +/* Opcode: ColumnsUsed P1 * * P4 * +** +** This opcode (which only exists if SQLite was compiled with +** SQLITE_ENABLE_COLUMN_USED_MASK) identifies which columns of the +** table or index for cursor P1 are used. P4 is a 64-bit integer +** (P4_INT64) in which the first 63 bits are one for each of the +** first 63 columns of the table or index that are actually used +** by the cursor. The high-order bit is set if any column after +** the 64th is used. +*/ +case OP_ColumnsUsed: { + VdbeCursor *pC; + pC = p->apCsr[pOp->p1]; + assert( pC->eCurType==CURTYPE_BTREE ); + pC->maskUsed = *(u64*)pOp->p4.pI64; + break; +} +#endif + +/* Opcode: SeekGE P1 P2 P3 P4 * ** Synopsis: key=r[P3@P4] ** ** If cursor P1 refers to an SQL table (B-Tree that uses integer keys), @@ -70953,9 +77319,20 @@ case OP_Close: { ** is greater than or equal to the key value. If there are no records ** greater than or equal to the key and P2 is not zero, then jump to P2. ** +** If the cursor P1 was opened using the OPFLAG_SEEKEQ flag, then this +** opcode will always land on a record that equally equals the key, or +** else jump immediately to P2. When the cursor is OPFLAG_SEEKEQ, this +** opcode must be followed by an IdxLE opcode with the same arguments. +** The IdxLE opcode will be skipped if this opcode succeeds, but the +** IdxLE opcode will be used on subsequent loop iterations. +** +** This opcode leaves the cursor configured to move in forward order, +** from the beginning toward the end. In other words, the cursor is +** configured to use Next, not Prev. +** ** See also: Found, NotFound, SeekLt, SeekGt, SeekLe */ -/* Opcode: SeekGt P1 P2 P3 P4 * +/* Opcode: SeekGT P1 P2 P3 P4 * ** Synopsis: key=r[P3@P4] ** ** If cursor P1 refers to an SQL table (B-Tree that uses integer keys), @@ -70967,9 +77344,13 @@ case OP_Close: { ** is greater than the key value. If there are no records greater than ** the key and P2 is not zero, then jump to P2. ** +** This opcode leaves the cursor configured to move in forward order, +** from the beginning toward the end. In other words, the cursor is +** configured to use Next, not Prev. +** ** See also: Found, NotFound, SeekLt, SeekGe, SeekLe */ -/* Opcode: SeekLt P1 P2 P3 P4 * +/* Opcode: SeekLT P1 P2 P3 P4 * ** Synopsis: key=r[P3@P4] ** ** If cursor P1 refers to an SQL table (B-Tree that uses integer keys), @@ -70981,9 +77362,13 @@ case OP_Close: { ** is less than the key value. If there are no records less than ** the key and P2 is not zero, then jump to P2. ** +** This opcode leaves the cursor configured to move in reverse order, +** from the end toward the beginning. In other words, the cursor is +** configured to use Prev, not Next. +** ** See also: Found, NotFound, SeekGt, SeekGe, SeekLe */ -/* Opcode: SeekLe P1 P2 P3 P4 * +/* Opcode: SeekLE P1 P2 P3 P4 * ** Synopsis: key=r[P3@P4] ** ** If cursor P1 refers to an SQL table (B-Tree that uses integer keys), @@ -70995,39 +77380,60 @@ case OP_Close: { ** is less than or equal to the key value. If there are no records ** less than or equal to the key and P2 is not zero, then jump to P2. ** +** This opcode leaves the cursor configured to move in reverse order, +** from the end toward the beginning. In other words, the cursor is +** configured to use Prev, not Next. +** +** If the cursor P1 was opened using the OPFLAG_SEEKEQ flag, then this +** opcode will always land on a record that equally equals the key, or +** else jump immediately to P2. When the cursor is OPFLAG_SEEKEQ, this +** opcode must be followed by an IdxGE opcode with the same arguments. +** The IdxGE opcode will be skipped if this opcode succeeds, but the +** IdxGE opcode will be used on subsequent loop iterations. +** ** See also: Found, NotFound, SeekGt, SeekGe, SeekLt */ case OP_SeekLT: /* jump, in3 */ case OP_SeekLE: /* jump, in3 */ case OP_SeekGE: /* jump, in3 */ case OP_SeekGT: { /* jump, in3 */ - int res; - int oc; - VdbeCursor *pC; - UnpackedRecord r; - int nField; - i64 iKey; /* The rowid we are to seek to */ + int res; /* Comparison result */ + int oc; /* Opcode */ + VdbeCursor *pC; /* The cursor to seek */ + UnpackedRecord r; /* The key to seek for */ + int nField; /* Number of columns or fields in the key */ + i64 iKey; /* The rowid we are to seek to */ + int eqOnly; /* Only interested in == results */ assert( pOp->p1>=0 && pOp->p1nCursor ); assert( pOp->p2!=0 ); pC = p->apCsr[pOp->p1]; assert( pC!=0 ); - assert( pC->pseudoTableReg==0 ); + assert( pC->eCurType==CURTYPE_BTREE ); assert( OP_SeekLE == OP_SeekLT+1 ); assert( OP_SeekGE == OP_SeekLT+2 ); assert( OP_SeekGT == OP_SeekLT+3 ); assert( pC->isOrdered ); - assert( pC->pCursor!=0 ); + assert( pC->uc.pCursor!=0 ); oc = pOp->opcode; + eqOnly = 0; pC->nullRow = 0; +#ifdef SQLITE_DEBUG + pC->seekOp = pOp->opcode; +#endif + if( pC->isTable ){ + /* The BTREE_SEEK_EQ flag is only set on index cursors */ + assert( sqlite3BtreeCursorHasHint(pC->uc.pCursor, BTREE_SEEK_EQ)==0 ); + /* The input value in P3 might be of any type: integer, real, string, ** blob, or NULL. But it needs to be an integer before we can do - ** the seek, so covert it. */ + ** the seek, so convert it. */ pIn3 = &aMem[pOp->p3]; - applyNumericAffinity(pIn3); + if( (pIn3->flags & (MEM_Int|MEM_Real|MEM_Str))==MEM_Str ){ + applyNumericAffinity(pIn3, 0); + } iKey = sqlite3VdbeIntValue(pIn3); - pC->rowidIsValid = 0; /* If the P3 value could not be converted into an integer without ** loss of information, then special processing is required... */ @@ -71035,7 +77441,7 @@ case OP_SeekGT: { /* jump, in3 */ if( (pIn3->flags & MEM_Real)==0 ){ /* If the P3 value cannot be converted into any kind of a number, ** then the seek is not possible, so jump to P2 */ - pc = pOp->p2 - 1; VdbeBranchTaken(1,2); + VdbeBranchTaken(1,2); goto jump_to_p2; break; } @@ -71046,7 +77452,7 @@ case OP_SeekGT: { /* jump, in3 */ ** (x > 4.9) -> (x >= 5) ** (x <= 4.9) -> (x < 5) */ - if( pIn3->r<(double)iKey ){ + if( pIn3->u.r<(double)iKey ){ assert( OP_SeekGE==(OP_SeekGT-1) ); assert( OP_SeekLT==(OP_SeekLE-1) ); assert( (OP_SeekLE & 0x0001)==(OP_SeekGT & 0x0001) ); @@ -71055,22 +77461,33 @@ case OP_SeekGT: { /* jump, in3 */ /* If the approximation iKey is smaller than the actual real search ** term, substitute <= for < and > for >=. */ - else if( pIn3->r>(double)iKey ){ + else if( pIn3->u.r>(double)iKey ){ assert( OP_SeekLE==(OP_SeekLT+1) ); assert( OP_SeekGT==(OP_SeekGE+1) ); assert( (OP_SeekLT & 0x0001)==(OP_SeekGE & 0x0001) ); if( (oc & 0x0001)==(OP_SeekLT & 0x0001) ) oc++; } } - rc = sqlite3BtreeMovetoUnpacked(pC->pCursor, 0, (u64)iKey, 0, &res); + rc = sqlite3BtreeMovetoUnpacked(pC->uc.pCursor, 0, (u64)iKey, 0, &res); + pC->movetoTarget = iKey; /* Used by OP_Delete */ if( rc!=SQLITE_OK ){ goto abort_due_to_error; } - if( res==0 ){ - pC->rowidIsValid = 1; - pC->lastRowid = iKey; - } }else{ + /* For a cursor with the BTREE_SEEK_EQ hint, only the OP_SeekGE and + ** OP_SeekLE opcodes are allowed, and these must be immediately followed + ** by an OP_IdxGT or OP_IdxLT opcode, respectively, with the same key. + */ + if( sqlite3BtreeCursorHasHint(pC->uc.pCursor, BTREE_SEEK_EQ) ){ + eqOnly = 1; + assert( pOp->opcode==OP_SeekGE || pOp->opcode==OP_SeekLE ); + assert( pOp[1].opcode==OP_IdxLT || pOp[1].opcode==OP_IdxGT ); + assert( pOp[1].p1==pOp[0].p1 ); + assert( pOp[1].p2==pOp[0].p2 ); + assert( pOp[1].p3==pOp[0].p3 ); + assert( pOp[1].p4.i==pOp[0].p4.i ); + } + nField = pOp->p4.i; assert( pOp->p4type==P4_INT32 ); assert( nField>0 ); @@ -71095,11 +77512,15 @@ case OP_SeekGT: { /* jump, in3 */ { int i; for(i=0; ipCursor, &r, 0, 0, &res); + r.eqSeen = 0; + rc = sqlite3BtreeMovetoUnpacked(pC->uc.pCursor, &r, 0, 0, &res); if( rc!=SQLITE_OK ){ goto abort_due_to_error; } - pC->rowidIsValid = 0; + if( eqOnly && r.eqSeen==0 ){ + assert( res!=0 ); + goto seek_not_found; + } } pC->deferredMoveto = 0; pC->cacheStatus = CACHE_STALE; @@ -71109,9 +77530,8 @@ case OP_SeekGT: { /* jump, in3 */ if( oc>=OP_SeekGE ){ assert( oc==OP_SeekGE || oc==OP_SeekGT ); if( res<0 || (res==0 && oc==OP_SeekGT) ){ res = 0; - rc = sqlite3BtreeNext(pC->pCursor, &res); + rc = sqlite3BtreeNext(pC->uc.pCursor, &res); if( rc!=SQLITE_OK ) goto abort_due_to_error; - pC->rowidIsValid = 0; }else{ res = 0; } @@ -71119,20 +77539,23 @@ case OP_SeekGT: { /* jump, in3 */ assert( oc==OP_SeekLT || oc==OP_SeekLE ); if( res>0 || (res==0 && oc==OP_SeekLT) ){ res = 0; - rc = sqlite3BtreePrevious(pC->pCursor, &res); + rc = sqlite3BtreePrevious(pC->uc.pCursor, &res); if( rc!=SQLITE_OK ) goto abort_due_to_error; - pC->rowidIsValid = 0; }else{ /* res might be negative because the table is empty. Check to ** see if this is the case. */ - res = sqlite3BtreeEof(pC->pCursor); + res = sqlite3BtreeEof(pC->uc.pCursor); } } +seek_not_found: assert( pOp->p2>0 ); VdbeBranchTaken(res!=0,2); if( res ){ - pc = pOp->p2 - 1; + goto jump_to_p2; + }else if( eqOnly ){ + assert( pOp[1].opcode==OP_IdxLT || pOp[1].opcode==OP_IdxGT ); + pOp++; /* Skip the OP_IdxLt or OP_IdxGT that follows */ } break; } @@ -71153,12 +77576,12 @@ case OP_Seek: { /* in2 */ assert( pOp->p1>=0 && pOp->p1nCursor ); pC = p->apCsr[pOp->p1]; assert( pC!=0 ); - assert( pC->pCursor!=0 ); + assert( pC->eCurType==CURTYPE_BTREE ); + assert( pC->uc.pCursor!=0 ); assert( pC->isTable ); pC->nullRow = 0; pIn2 = &aMem[pOp->p2]; pC->movetoTarget = sqlite3VdbeIntValue(pIn2); - pC->rowidIsValid = 0; pC->deferredMoveto = 1; break; } @@ -71175,6 +77598,10 @@ case OP_Seek: { /* in2 */ ** is a prefix of any entry in P1 then a jump is made to P2 and ** P1 is left pointing at the matching entry. ** +** This operation leaves the cursor in a state where it can be +** advanced in the forward direction. The Next instruction will work, +** but not the Prev instruction. +** ** See also: NotFound, NoConflict, NotExists. SeekGe */ /* Opcode: NotFound P1 P2 P3 P4 * @@ -71190,6 +77617,10 @@ case OP_Seek: { /* in2 */ ** falls through to the next instruction and P1 is left pointing at the ** matching entry. ** +** This operation leaves the cursor in a state where it cannot be +** advanced in either direction. In other words, the Next and Prev +** opcodes do not work after this operation. +** ** See also: Found, NotExists, NoConflict */ /* Opcode: NoConflict P1 P2 P3 P4 * @@ -71209,12 +77640,17 @@ case OP_Seek: { /* in2 */ ** This opcode is similar to OP_NotFound with the exceptions that the ** branch is always taken if any part of the search key input is NULL. ** +** This operation leaves the cursor in a state where it cannot be +** advanced in either direction. In other words, the Next and Prev +** opcodes do not work after this operation. +** ** See also: NotFound, Found, NotExists */ case OP_NoConflict: /* jump, in3 */ case OP_NotFound: /* jump, in3 */ case OP_Found: { /* jump, in3 */ int alreadyExists; + int takeJump; int ii; VdbeCursor *pC; int res; @@ -71231,10 +77667,14 @@ case OP_Found: { /* jump, in3 */ assert( pOp->p4type==P4_INT32 ); pC = p->apCsr[pOp->p1]; assert( pC!=0 ); +#ifdef SQLITE_DEBUG + pC->seekOp = pOp->opcode; +#endif pIn3 = &aMem[pOp->p3]; - assert( pC->pCursor!=0 ); + assert( pC->eCurType==CURTYPE_BTREE ); + assert( pC->uc.pCursor!=0 ); assert( pC->isTable==0 ); - pFree = 0; /* Not needed. Only used to suppress a compiler warning. */ + pFree = 0; if( pOp->p4.i>0 ){ r.pKeyInfo = pC->pKeyInfo; r.nField = (u16)pOp->p4.i; @@ -71250,28 +77690,27 @@ case OP_Found: { /* jump, in3 */ }else{ pIdxKey = sqlite3VdbeAllocUnpackedRecord( pC->pKeyInfo, aTempRec, sizeof(aTempRec), &pFree - ); + ); if( pIdxKey==0 ) goto no_mem; assert( pIn3->flags & MEM_Blob ); - assert( (pIn3->flags & MEM_Zero)==0 ); /* zeroblobs already expanded */ + ExpandBlob(pIn3); sqlite3VdbeRecordUnpack(pC->pKeyInfo, pIn3->n, pIn3->z, pIdxKey); } pIdxKey->default_rc = 0; + takeJump = 0; if( pOp->opcode==OP_NoConflict ){ /* For the OP_NoConflict opcode, take the jump if any of the ** input fields are NULL, since any key with a NULL will not ** conflict */ - for(ii=0; iip2 - 1; VdbeBranchTaken(1,2); + for(ii=0; iinField; ii++){ + if( pIdxKey->aMem[ii].flags & MEM_Null ){ + takeJump = 1; break; } } } - rc = sqlite3BtreeMovetoUnpacked(pC->pCursor, pIdxKey, 0, 0, &res); - if( pOp->p4.i==0 ){ - sqlite3DbFree(db, pFree); - } + rc = sqlite3BtreeMovetoUnpacked(pC->uc.pCursor, pIdxKey, 0, 0, &res); + sqlite3DbFree(db, pFree); if( rc!=SQLITE_OK ){ break; } @@ -71282,10 +77721,10 @@ case OP_Found: { /* jump, in3 */ pC->cacheStatus = CACHE_STALE; if( pOp->opcode==OP_Found ){ VdbeBranchTaken(alreadyExists!=0,2); - if( alreadyExists ) pc = pOp->p2 - 1; + if( alreadyExists ) goto jump_to_p2; }else{ - VdbeBranchTaken(alreadyExists==0,2); - if( !alreadyExists ) pc = pOp->p2 - 1; + VdbeBranchTaken(takeJump||alreadyExists==0,2); + if( takeJump || !alreadyExists ) goto jump_to_p2; } break; } @@ -71295,13 +77734,18 @@ case OP_Found: { /* jump, in3 */ ** ** P1 is the index of a cursor open on an SQL table btree (with integer ** keys). P3 is an integer rowid. If P1 does not contain a record with -** rowid P3 then jump immediately to P2. If P1 does contain a record -** with rowid P3 then leave the cursor pointing at that record and fall -** through to the next instruction. +** rowid P3 then jump immediately to P2. Or, if P2 is 0, raise an +** SQLITE_CORRUPT error. If P1 does contain a record with rowid P3 then +** leave the cursor pointing at that record and fall through to the next +** instruction. ** ** The OP_NotFound opcode performs the same operation on index btrees ** (with arbitrary multi-value keys). ** +** This opcode leaves the cursor in a state where it cannot be advanced +** in either direction. In other words, the Next and Prev opcodes will +** not work following this opcode. +** ** See also: Found, NotFound, NoConflict */ case OP_NotExists: { /* jump, in3 */ @@ -71315,24 +77759,31 @@ case OP_NotExists: { /* jump, in3 */ assert( pOp->p1>=0 && pOp->p1nCursor ); pC = p->apCsr[pOp->p1]; assert( pC!=0 ); +#ifdef SQLITE_DEBUG + pC->seekOp = 0; +#endif assert( pC->isTable ); - assert( pC->pseudoTableReg==0 ); - pCrsr = pC->pCursor; + assert( pC->eCurType==CURTYPE_BTREE ); + pCrsr = pC->uc.pCursor; assert( pCrsr!=0 ); res = 0; iKey = pIn3->u.i; rc = sqlite3BtreeMovetoUnpacked(pCrsr, 0, iKey, 0, &res); - pC->lastRowid = pIn3->u.i; - pC->rowidIsValid = res==0 ?1:0; + assert( rc==SQLITE_OK || res==0 ); + pC->movetoTarget = iKey; /* Used by OP_Delete */ pC->nullRow = 0; pC->cacheStatus = CACHE_STALE; pC->deferredMoveto = 0; VdbeBranchTaken(res!=0,2); - if( res!=0 ){ - pc = pOp->p2 - 1; - assert( pC->rowidIsValid==0 ); - } pC->seekResult = res; + if( res!=0 ){ + assert( rc==SQLITE_OK ); + if( pOp->p2==0 ){ + rc = SQLITE_CORRUPT_BKPT; + }else{ + goto jump_to_p2; + } + } break; } @@ -71344,9 +77795,11 @@ case OP_NotExists: { /* jump, in3 */ ** The sequence number on the cursor is incremented after this ** instruction. */ -case OP_Sequence: { /* out2-prerelease */ +case OP_Sequence: { /* out2 */ assert( pOp->p1>=0 && pOp->p1nCursor ); assert( p->apCsr[pOp->p1]!=0 ); + assert( p->apCsr[pOp->p1]->eCurType!=CURTYPE_VTAB ); + pOut = out2Prerelease(p, pOp); pOut->u.i = p->apCsr[pOp->p1]->seqCount++; break; } @@ -71367,7 +77820,7 @@ case OP_Sequence: { /* out2-prerelease */ ** generated record number. This P3 mechanism is used to help implement the ** AUTOINCREMENT feature. */ -case OP_NewRowid: { /* out2-prerelease */ +case OP_NewRowid: { /* out2 */ i64 v; /* The new rowid */ VdbeCursor *pC; /* Cursor of table to get the new rowid */ int res; /* Result of an sqlite3BtreeLast() */ @@ -71377,12 +77830,13 @@ case OP_NewRowid: { /* out2-prerelease */ v = 0; res = 0; + pOut = out2Prerelease(p, pOp); assert( pOp->p1>=0 && pOp->p1nCursor ); pC = p->apCsr[pOp->p1]; assert( pC!=0 ); - if( NEVER(pC->pCursor==0) ){ - /* The zero initialization above is all that is needed */ - }else{ + assert( pC->eCurType==CURTYPE_BTREE ); + assert( pC->uc.pCursor!=0 ); + { /* The next rowid or record number (different terms for the same ** thing) is obtained in a two-step algorithm. ** @@ -71409,15 +77863,15 @@ case OP_NewRowid: { /* out2-prerelease */ #endif if( !pC->useRandomRowid ){ - rc = sqlite3BtreeLast(pC->pCursor, &res); + rc = sqlite3BtreeLast(pC->uc.pCursor, &res); if( rc!=SQLITE_OK ){ goto abort_due_to_error; } if( res ){ v = 1; /* IMP: R-61914-48074 */ }else{ - assert( sqlite3BtreeCursorIsValid(pC->pCursor) ); - rc = sqlite3BtreeKeySize(pC->pCursor, &v); + assert( sqlite3BtreeCursorIsValid(pC->uc.pCursor) ); + rc = sqlite3BtreeKeySize(pC->uc.pCursor, &v); assert( rc==SQLITE_OK ); /* Cannot fail following BtreeLast() */ if( v>=MAX_ROWID ){ pC->useRandomRowid = 1; @@ -71464,32 +77918,20 @@ case OP_NewRowid: { /* out2-prerelease */ ** it finds one that is not previously used. */ assert( pOp->p3==0 ); /* We cannot be in random rowid mode if this is ** an AUTOINCREMENT table. */ - /* on the first attempt, simply do one more than previous */ - v = lastRowid; - v &= (MAX_ROWID>>1); /* ensure doesn't go negative */ - v++; /* ensure non-zero */ cnt = 0; - while( ((rc = sqlite3BtreeMovetoUnpacked(pC->pCursor, 0, (u64)v, + do{ + sqlite3_randomness(sizeof(v), &v); + v &= (MAX_ROWID>>1); v++; /* Ensure that v is greater than zero */ + }while( ((rc = sqlite3BtreeMovetoUnpacked(pC->uc.pCursor, 0, (u64)v, 0, &res))==SQLITE_OK) && (res==0) - && (++cnt<100)){ - /* collision - try another random rowid */ - sqlite3_randomness(sizeof(v), &v); - if( cnt<5 ){ - /* try "small" random rowids for the initial attempts */ - v &= 0xffffff; - }else{ - v &= (MAX_ROWID>>1); /* ensure doesn't go negative */ - } - v++; /* ensure non-zero */ - } + && (++cnt<100)); if( rc==SQLITE_OK && res==0 ){ rc = SQLITE_FULL; /* IMP: R-38219-53002 */ goto abort_due_to_error; } assert( v>0 ); /* EV: R-40812-03570 */ } - pC->rowidIsValid = 0; pC->deferredMoveto = 0; pC->cacheStatus = CACHE_STALE; } @@ -71560,8 +78002,8 @@ case OP_InsertInt: { assert( memIsValid(pData) ); pC = p->apCsr[pOp->p1]; assert( pC!=0 ); - assert( pC->pCursor!=0 ); - assert( pC->pseudoTableReg==0 ); + assert( pC->eCurType==CURTYPE_BTREE ); + assert( pC->uc.pCursor!=0 ); assert( pC->isTable ); REGISTER_TRACE(pOp->p2, pData); @@ -71590,11 +78032,10 @@ case OP_InsertInt: { }else{ nZero = 0; } - rc = sqlite3BtreeInsert(pC->pCursor, 0, iKey, + rc = sqlite3BtreeInsert(pC->uc.pCursor, 0, iKey, pData->z, pData->n, nZero, (pOp->p5 & OPFLAG_APPEND)!=0, seekResult ); - pC->rowidIsValid = 0; pC->deferredMoveto = 0; pC->cacheStatus = CACHE_STALE; @@ -71610,14 +78051,15 @@ case OP_InsertInt: { break; } -/* Opcode: Delete P1 P2 * P4 * +/* Opcode: Delete P1 P2 * P4 P5 ** ** Delete the record at which the P1 cursor is currently pointing. ** -** The cursor will be left pointing at either the next or the previous -** record in the table. If it is left pointing at the next record, then -** the next Next instruction will be a no-op. Hence it is OK to delete -** a record from within an Next loop. +** If the P5 parameter is non-zero, the cursor will be left pointing at +** either the next or the previous record in the table. If it is left +** pointing at the next record, then the next Next instruction will be a +** no-op. As a result, in this case it is OK to delete a record from within a +** Next loop. If P5 is zero, then the cursor is left in an undefined state. ** ** If the OPFLAG_NCHANGE flag of P2 is set, then the row change count is ** incremented (otherwise not). @@ -71631,33 +78073,39 @@ case OP_InsertInt: { ** using OP_NotFound prior to invoking this opcode. */ case OP_Delete: { - i64 iKey; VdbeCursor *pC; + u8 hasUpdateCallback; assert( pOp->p1>=0 && pOp->p1nCursor ); pC = p->apCsr[pOp->p1]; assert( pC!=0 ); - assert( pC->pCursor!=0 ); /* Only valid for real tables, no pseudotables */ - iKey = pC->lastRowid; /* Only used for the update hook */ - - /* The OP_Delete opcode always follows an OP_NotExists or OP_Last or - ** OP_Column on the same table without any intervening operations that - ** might move or invalidate the cursor. Hence cursor pC is always pointing - ** to the row to be deleted and the sqlite3VdbeCursorMoveto() operation - ** below is always a no-op and cannot fail. We will run it anyhow, though, - ** to guard against future changes to the code generator. - **/ + assert( pC->eCurType==CURTYPE_BTREE ); + assert( pC->uc.pCursor!=0 ); assert( pC->deferredMoveto==0 ); - rc = sqlite3VdbeCursorMoveto(pC); - if( NEVER(rc!=SQLITE_OK) ) goto abort_due_to_error; - rc = sqlite3BtreeDelete(pC->pCursor); + hasUpdateCallback = db->xUpdateCallback && pOp->p4.z && pC->isTable; + if( pOp->p5 && hasUpdateCallback ){ + sqlite3BtreeKeySize(pC->uc.pCursor, &pC->movetoTarget); + } + +#ifdef SQLITE_DEBUG + /* The seek operation that positioned the cursor prior to OP_Delete will + ** have also set the pC->movetoTarget field to the rowid of the row that + ** is being deleted */ + if( pOp->p4.z && pC->isTable && pOp->p5==0 ){ + i64 iKey = 0; + sqlite3BtreeKeySize(pC->uc.pCursor, &iKey); + assert( pC->movetoTarget==iKey ); + } +#endif + + rc = sqlite3BtreeDelete(pC->uc.pCursor, pOp->p5); pC->cacheStatus = CACHE_STALE; /* Invoke the update-hook if required. */ - if( rc==SQLITE_OK && db->xUpdateCallback && pOp->p4.z && pC->isTable ){ + if( rc==SQLITE_OK && hasUpdateCallback ){ db->xUpdateCallback(db->pUpdateArg, SQLITE_DELETE, - db->aDb[pC->iDb].zName, pOp->p4.z, iKey); + db->aDb[pC->iDb].zName, pOp->p4.z, pC->movetoTarget); assert( pC->iDb>=0 ); } if( pOp->p2 & OPFLAG_NCHANGE ) p->nChange++; @@ -71677,12 +78125,12 @@ case OP_ResetCount: { } /* Opcode: SorterCompare P1 P2 P3 P4 -** Synopsis: if key(P1)!=rtrim(r[P3],P4) goto P2 +** Synopsis: if key(P1)!=trim(r[P3],P4) goto P2 ** ** P1 is a sorter cursor. This instruction compares a prefix of the -** the record blob in register P3 against a prefix of the entry that -** the sorter cursor currently points to. The final P4 fields of both -** the P3 and sorter record are ignored. +** record blob in register P3 against a prefix of the entry that +** the sorter cursor currently points to. Only the first P4 fields +** of r[P3] and the sorter record are compared. ** ** If either P3 or the sorter contains a NULL in one of their significant ** fields (not counting the P4 fields at the end which are ignored) then @@ -71694,25 +78142,31 @@ case OP_ResetCount: { case OP_SorterCompare: { VdbeCursor *pC; int res; - int nIgnore; + int nKeyCol; pC = p->apCsr[pOp->p1]; assert( isSorter(pC) ); assert( pOp->p4type==P4_INT32 ); pIn3 = &aMem[pOp->p3]; - nIgnore = pOp->p4.i; - rc = sqlite3VdbeSorterCompare(pC, pIn3, nIgnore, &res); + nKeyCol = pOp->p4.i; + res = 0; + rc = sqlite3VdbeSorterCompare(pC, pIn3, nKeyCol, &res); VdbeBranchTaken(res!=0,2); - if( res ){ - pc = pOp->p2-1; - } + if( res ) goto jump_to_p2; break; }; -/* Opcode: SorterData P1 P2 * * * +/* Opcode: SorterData P1 P2 P3 * * ** Synopsis: r[P2]=data ** ** Write into register P2 the current sorter data for sorter cursor P1. +** Then clear the column header cache on cursor P3. +** +** This opcode is normally use to move a record out of the sorter and into +** a register that is the source for a pseudo-table cursor created using +** OpenPseudo. That pseudo-table cursor is the one that is identified by +** parameter P3. Clearing the P3 column cache as part of this opcode saves +** us from having to issue a separate NullRow instruction to clear that cache. */ case OP_SorterData: { VdbeCursor *pC; @@ -71722,6 +78176,8 @@ case OP_SorterData: { assert( isSorter(pC) ); rc = sqlite3VdbeSorterRowkey(pC, pOut); assert( rc!=SQLITE_OK || (pOut->flags & MEM_Blob) ); + assert( pOp->p1>=0 && pOp->p1nCursor ); + p->apCsr[pOp->p3]->cacheStatus = CACHE_STALE; break; } @@ -71760,24 +78216,28 @@ case OP_RowData: { /* Note that RowKey and RowData are really exactly the same instruction */ assert( pOp->p1>=0 && pOp->p1nCursor ); pC = p->apCsr[pOp->p1]; + assert( pC!=0 ); + assert( pC->eCurType==CURTYPE_BTREE ); assert( isSorter(pC)==0 ); assert( pC->isTable || pOp->opcode!=OP_RowData ); assert( pC->isTable==0 || pOp->opcode==OP_RowData ); - assert( pC!=0 ); assert( pC->nullRow==0 ); - assert( pC->pseudoTableReg==0 ); - assert( pC->pCursor!=0 ); - pCrsr = pC->pCursor; - assert( sqlite3BtreeCursorIsValid(pCrsr) ); + assert( pC->uc.pCursor!=0 ); + pCrsr = pC->uc.pCursor; /* The OP_RowKey and OP_RowData opcodes always follow OP_NotExists or ** OP_Rewind/Op_Next with no intervening instructions that might invalidate - ** the cursor. Hence the following sqlite3VdbeCursorMoveto() call is always - ** a no-op and can never fail. But we leave it in place as a safety. + ** the cursor. If this where not the case, on of the following assert()s + ** would fail. Should this ever change (because of changes in the code + ** generator) then the fix would be to insert a call to + ** sqlite3VdbeCursorMoveto(). */ assert( pC->deferredMoveto==0 ); + assert( sqlite3BtreeCursorIsValid(pCrsr) ); +#if 0 /* Not required due to the previous to assert() statements */ rc = sqlite3VdbeCursorMoveto(pC); - if( NEVER(rc!=SQLITE_OK) ) goto abort_due_to_error; + if( rc!=SQLITE_OK ) goto abort_due_to_error; +#endif if( pC->isTable==0 ){ assert( !pC->isTable ); @@ -71794,7 +78254,8 @@ case OP_RowData: { goto too_big; } } - if( sqlite3VdbeMemGrow(pOut, n, 0) ){ + testcase( n==0 ); + if( sqlite3VdbeMemClearAndResize(pOut, MAX(n,32)) ){ goto no_mem; } pOut->n = n; @@ -71820,39 +78281,42 @@ case OP_RowData: { ** be a separate OP_VRowid opcode for use with virtual tables, but this ** one opcode now works for both table types. */ -case OP_Rowid: { /* out2-prerelease */ +case OP_Rowid: { /* out2 */ VdbeCursor *pC; i64 v; sqlite3_vtab *pVtab; const sqlite3_module *pModule; + pOut = out2Prerelease(p, pOp); assert( pOp->p1>=0 && pOp->p1nCursor ); pC = p->apCsr[pOp->p1]; assert( pC!=0 ); - assert( pC->pseudoTableReg==0 || pC->nullRow ); + assert( pC->eCurType!=CURTYPE_PSEUDO || pC->nullRow ); if( pC->nullRow ){ pOut->flags = MEM_Null; break; }else if( pC->deferredMoveto ){ v = pC->movetoTarget; #ifndef SQLITE_OMIT_VIRTUALTABLE - }else if( pC->pVtabCursor ){ - pVtab = pC->pVtabCursor->pVtab; + }else if( pC->eCurType==CURTYPE_VTAB ){ + assert( pC->uc.pVCur!=0 ); + pVtab = pC->uc.pVCur->pVtab; pModule = pVtab->pModule; assert( pModule->xRowid ); - rc = pModule->xRowid(pC->pVtabCursor, &v); + rc = pModule->xRowid(pC->uc.pVCur, &v); sqlite3VtabImportErrmsg(p, pVtab); #endif /* SQLITE_OMIT_VIRTUALTABLE */ }else{ - assert( pC->pCursor!=0 ); - rc = sqlite3VdbeCursorMoveto(pC); + assert( pC->eCurType==CURTYPE_BTREE ); + assert( pC->uc.pCursor!=0 ); + rc = sqlite3VdbeCursorRestore(pC); if( rc ) goto abort_due_to_error; - if( pC->rowidIsValid ){ - v = pC->lastRowid; - }else{ - rc = sqlite3BtreeKeySize(pC->pCursor, &v); - assert( rc==SQLITE_OK ); /* Always so because of CursorMoveto() above */ + if( pC->nullRow ){ + pOut->flags = MEM_Null; + break; } + rc = sqlite3BtreeKeySize(pC->uc.pCursor, &v); + assert( rc==SQLITE_OK ); /* Always so because of CursorRestore() above */ } pOut->u.i = v; break; @@ -71871,21 +78335,25 @@ case OP_NullRow: { pC = p->apCsr[pOp->p1]; assert( pC!=0 ); pC->nullRow = 1; - pC->rowidIsValid = 0; pC->cacheStatus = CACHE_STALE; - if( pC->pCursor ){ - sqlite3BtreeClearCursor(pC->pCursor); + if( pC->eCurType==CURTYPE_BTREE ){ + assert( pC->uc.pCursor!=0 ); + sqlite3BtreeClearCursor(pC->uc.pCursor); } break; } -/* Opcode: Last P1 P2 * * * +/* Opcode: Last P1 P2 P3 * * ** -** The next use of the Rowid or Column or Next instruction for P1 +** The next use of the Rowid or Column or Prev instruction for P1 ** will refer to the last entry in the database table or index. ** If the table or index is empty and P2>0, then jump immediately to P2. ** If P2 is 0 or if the table or index is not empty, fall through ** to the following instruction. +** +** This opcode leaves the cursor configured to move in reverse order, +** from the end toward the beginning. In other words, the cursor is +** configured to use Prev, not Next. */ case OP_Last: { /* jump */ VdbeCursor *pC; @@ -71895,17 +78363,21 @@ case OP_Last: { /* jump */ assert( pOp->p1>=0 && pOp->p1nCursor ); pC = p->apCsr[pOp->p1]; assert( pC!=0 ); - pCrsr = pC->pCursor; + assert( pC->eCurType==CURTYPE_BTREE ); + pCrsr = pC->uc.pCursor; res = 0; assert( pCrsr!=0 ); rc = sqlite3BtreeLast(pCrsr, &res); pC->nullRow = (u8)res; pC->deferredMoveto = 0; - pC->rowidIsValid = 0; pC->cacheStatus = CACHE_STALE; + pC->seekResult = pOp->p3; +#ifdef SQLITE_DEBUG + pC->seekOp = OP_Last; +#endif if( pOp->p2>0 ){ VdbeBranchTaken(res!=0,2); - if( res ) pc = pOp->p2 - 1; + if( res ) goto jump_to_p2; } break; } @@ -71936,9 +78408,13 @@ case OP_Sort: { /* jump */ ** ** The next use of the Rowid or Column or Next instruction for P1 ** will refer to the first entry in the database table or index. -** If the table or index is empty and P2>0, then jump immediately to P2. -** If P2 is 0 or if the table or index is not empty, fall through -** to the following instruction. +** If the table or index is empty, jump immediately to P2. +** If the table or index is not empty, fall through to the following +** instruction. +** +** This opcode leaves the cursor configured to move in forward order, +** from the beginning toward the end. In other words, the cursor is +** configured to use Next, not Prev. */ case OP_Rewind: { /* jump */ VdbeCursor *pC; @@ -71950,22 +78426,23 @@ case OP_Rewind: { /* jump */ assert( pC!=0 ); assert( isSorter(pC)==(pOp->opcode==OP_SorterSort) ); res = 1; +#ifdef SQLITE_DEBUG + pC->seekOp = OP_Rewind; +#endif if( isSorter(pC) ){ - rc = sqlite3VdbeSorterRewind(db, pC, &res); + rc = sqlite3VdbeSorterRewind(pC, &res); }else{ - pCrsr = pC->pCursor; + assert( pC->eCurType==CURTYPE_BTREE ); + pCrsr = pC->uc.pCursor; assert( pCrsr ); rc = sqlite3BtreeFirst(pCrsr, &res); pC->deferredMoveto = 0; pC->cacheStatus = CACHE_STALE; - pC->rowidIsValid = 0; } pC->nullRow = (u8)res; assert( pOp->p2>0 && pOp->p2nOp ); VdbeBranchTaken(res!=0,2); - if( res ){ - pc = pOp->p2 - 1; - } + if( res ) goto jump_to_p2; break; } @@ -71976,6 +78453,10 @@ case OP_Rewind: { /* jump */ ** to the following instruction. But if the cursor advance was successful, ** jump immediately to P2. ** +** The Next opcode is only valid following an SeekGT, SeekGE, or +** OP_Rewind opcode used to position the cursor. Next is not allowed +** to follow SeekLT, SeekLE, or OP_Last. +** ** The P1 cursor must be for a real table, not a pseudo-table. P1 must have ** been opened prior to this opcode or the program will segfault. ** @@ -71994,7 +78475,7 @@ case OP_Rewind: { /* jump */ */ /* Opcode: NextIfOpen P1 P2 P3 P4 P5 ** -** This opcode works just like OP_Next except that if cursor P1 is not +** This opcode works just like Next except that if cursor P1 is not ** open it behaves a no-op. */ /* Opcode: Prev P1 P2 P3 P4 P5 @@ -72004,6 +78485,11 @@ case OP_Rewind: { /* jump */ ** to the following instruction. But if the cursor backup was successful, ** jump immediately to P2. ** +** +** The Prev opcode is only valid following an SeekLT, SeekLE, or +** OP_Last opcode used to position the cursor. Prev is not allowed +** to follow SeekGT, SeekGE, or OP_Rewind. +** ** The P1 cursor must be for a real table, not a pseudo-table. If P1 is ** not open then the behavior is undefined. ** @@ -72020,7 +78506,7 @@ case OP_Rewind: { /* jump */ */ /* Opcode: PrevIfOpen P1 P2 P3 P4 P5 ** -** This opcode works just like OP_Prev except that if cursor P1 is not +** This opcode works just like Prev except that if cursor P1 is not ** open it behaves a no-op. */ case OP_SorterNext: { /* jump */ @@ -72044,28 +78530,37 @@ case OP_Next: /* jump */ res = pOp->p3; assert( pC!=0 ); assert( pC->deferredMoveto==0 ); - assert( pC->pCursor ); + assert( pC->eCurType==CURTYPE_BTREE ); assert( res==0 || (res==1 && pC->isTable==0) ); testcase( res==1 ); assert( pOp->opcode!=OP_Next || pOp->p4.xAdvance==sqlite3BtreeNext ); assert( pOp->opcode!=OP_Prev || pOp->p4.xAdvance==sqlite3BtreePrevious ); assert( pOp->opcode!=OP_NextIfOpen || pOp->p4.xAdvance==sqlite3BtreeNext ); assert( pOp->opcode!=OP_PrevIfOpen || pOp->p4.xAdvance==sqlite3BtreePrevious); - rc = pOp->p4.xAdvance(pC->pCursor, &res); + + /* The Next opcode is only used after SeekGT, SeekGE, and Rewind. + ** The Prev opcode is only used after SeekLT, SeekLE, and Last. */ + assert( pOp->opcode!=OP_Next || pOp->opcode!=OP_NextIfOpen + || pC->seekOp==OP_SeekGT || pC->seekOp==OP_SeekGE + || pC->seekOp==OP_Rewind || pC->seekOp==OP_Found); + assert( pOp->opcode!=OP_Prev || pOp->opcode!=OP_PrevIfOpen + || pC->seekOp==OP_SeekLT || pC->seekOp==OP_SeekLE + || pC->seekOp==OP_Last ); + + rc = pOp->p4.xAdvance(pC->uc.pCursor, &res); next_tail: pC->cacheStatus = CACHE_STALE; VdbeBranchTaken(res==0,2); if( res==0 ){ pC->nullRow = 0; - pc = pOp->p2 - 1; p->aCounter[pOp->p5]++; #ifdef SQLITE_TEST sqlite3_search_count++; #endif + goto jump_to_p2_and_check_for_interrupt; }else{ pC->nullRow = 1; } - pC->rowidIsValid = 0; goto check_for_interrupt; } @@ -72093,7 +78588,6 @@ next_tail: case OP_SorterInsert: /* in2 */ case OP_IdxInsert: { /* in2 */ VdbeCursor *pC; - BtCursor *pCrsr; int nKey; const char *zKey; @@ -72103,18 +78597,17 @@ case OP_IdxInsert: { /* in2 */ assert( isSorter(pC)==(pOp->opcode==OP_SorterInsert) ); pIn2 = &aMem[pOp->p2]; assert( pIn2->flags & MEM_Blob ); - pCrsr = pC->pCursor; if( pOp->p5 & OPFLAG_NCHANGE ) p->nChange++; - assert( pCrsr!=0 ); + assert( pC->eCurType==CURTYPE_BTREE || pOp->opcode==OP_SorterInsert ); assert( pC->isTable==0 ); rc = ExpandBlob(pIn2); if( rc==SQLITE_OK ){ - if( isSorter(pC) ){ - rc = sqlite3VdbeSorterWrite(db, pC, pIn2); + if( pOp->opcode==OP_SorterInsert ){ + rc = sqlite3VdbeSorterWrite(pC, pIn2); }else{ nKey = pIn2->n; zKey = pIn2->z; - rc = sqlite3BtreeInsert(pCrsr, zKey, nKey, "", 0, 0, pOp->p3, + rc = sqlite3BtreeInsert(pC->uc.pCursor, zKey, nKey, "", 0, 0, pOp->p3, ((pOp->p5 & OPFLAG_USESEEKRESULT) ? pC->seekResult : 0) ); assert( pC->deferredMoveto==0 ); @@ -72142,7 +78635,8 @@ case OP_IdxDelete: { assert( pOp->p1>=0 && pOp->p1nCursor ); pC = p->apCsr[pOp->p1]; assert( pC!=0 ); - pCrsr = pC->pCursor; + assert( pC->eCurType==CURTYPE_BTREE ); + pCrsr = pC->uc.pCursor; assert( pCrsr!=0 ); assert( pOp->p5==0 ); r.pKeyInfo = pC->pKeyInfo; @@ -72154,7 +78648,7 @@ case OP_IdxDelete: { #endif rc = sqlite3BtreeMovetoUnpacked(pCrsr, &r, 0, 0, &res); if( rc==SQLITE_OK && res==0 ){ - rc = sqlite3BtreeDelete(pCrsr); + rc = sqlite3BtreeDelete(pCrsr, 0); } assert( pC->deferredMoveto==0 ); pC->cacheStatus = CACHE_STALE; @@ -72170,21 +78664,29 @@ case OP_IdxDelete: { ** ** See also: Rowid, MakeRecord. */ -case OP_IdxRowid: { /* out2-prerelease */ +case OP_IdxRowid: { /* out2 */ BtCursor *pCrsr; VdbeCursor *pC; i64 rowid; + pOut = out2Prerelease(p, pOp); assert( pOp->p1>=0 && pOp->p1nCursor ); pC = p->apCsr[pOp->p1]; assert( pC!=0 ); - pCrsr = pC->pCursor; + assert( pC->eCurType==CURTYPE_BTREE ); + pCrsr = pC->uc.pCursor; assert( pCrsr!=0 ); pOut->flags = MEM_Null; - rc = sqlite3VdbeCursorMoveto(pC); - if( NEVER(rc) ) goto abort_due_to_error; - assert( pC->deferredMoveto==0 ); assert( pC->isTable==0 ); + assert( pC->deferredMoveto==0 ); + + /* sqlite3VbeCursorRestore() can only fail if the record has been deleted + ** out from under the cursor. That will never happend for an IdxRowid + ** opcode, hence the NEVER() arround the check of the return value. + */ + rc = sqlite3VdbeCursorRestore(pC); + if( NEVER(rc!=SQLITE_OK) ) goto abort_due_to_error; + if( !pC->nullRow ){ rowid = 0; /* Not needed. Only used to silence a warning. */ rc = sqlite3VdbeIdxRowid(db, pCrsr, &rowid); @@ -72253,7 +78755,8 @@ case OP_IdxGE: { /* jump */ pC = p->apCsr[pOp->p1]; assert( pC!=0 ); assert( pC->isOrdered ); - assert( pC->pCursor!=0); + assert( pC->eCurType==CURTYPE_BTREE ); + assert( pC->uc.pCursor!=0); assert( pC->deferredMoveto==0 ); assert( pOp->p5==0 || pOp->p5==1 ); assert( pOp->p4type==P4_INT32 ); @@ -72271,7 +78774,7 @@ case OP_IdxGE: { /* jump */ { int i; for(i=0; iopcode&1)==(OP_IdxLT&1) ){ assert( pOp->opcode==OP_IdxLE || pOp->opcode==OP_IdxLT ); @@ -72281,9 +78784,7 @@ case OP_IdxGE: { /* jump */ res++; } VdbeBranchTaken(res>0,2); - if( res>0 ){ - pc = pOp->p2 - 1 ; - } + if( res>0 ) goto jump_to_p2; break; } @@ -72307,33 +78808,19 @@ case OP_IdxGE: { /* jump */ ** ** See also: Clear */ -case OP_Destroy: { /* out2-prerelease */ +case OP_Destroy: { /* out2 */ int iMoved; - int iCnt; - Vdbe *pVdbe; int iDb; assert( p->readOnly==0 ); -#ifndef SQLITE_OMIT_VIRTUALTABLE - iCnt = 0; - for(pVdbe=db->pVdbe; pVdbe; pVdbe = pVdbe->pNext){ - if( pVdbe->magic==VDBE_MAGIC_RUN && pVdbe->bIsReader - && pVdbe->inVtabMethod<2 && pVdbe->pc>=0 - ){ - iCnt++; - } - } -#else - iCnt = db->nVdbeRead; -#endif + pOut = out2Prerelease(p, pOp); pOut->flags = MEM_Null; - if( iCnt>1 ){ + if( db->nVdbeRead > db->nVDestroy+1 ){ rc = SQLITE_LOCKED; p->errorAction = OE_Abort; }else{ iDb = pOp->p3; - assert( iCnt==1 ); - assert( (p->btreeMask & (((yDbMask)1)<btreeMask, iDb) ); iMoved = 0; /* Not needed. Only to silence a warning. */ rc = sqlite3BtreeDropTable(db->aDb[iDb].pBt, pOp->p1, &iMoved); pOut->flags = MEM_Int; @@ -72373,7 +78860,7 @@ case OP_Clear: { nChange = 0; assert( p->readOnly==0 ); - assert( (p->btreeMask & (((yDbMask)1)<p2))!=0 ); + assert( DbMaskTest(p->btreeMask, pOp->p2) ); rc = sqlite3BtreeClearTable( db->aDb[pOp->p2].pBt, pOp->p1, (pOp->p3 ? &nChange : 0) ); @@ -72402,11 +78889,12 @@ case OP_ResetSorter: { assert( pOp->p1>=0 && pOp->p1nCursor ); pC = p->apCsr[pOp->p1]; assert( pC!=0 ); - if( pC->pSorter ){ - sqlite3VdbeSorterReset(db, pC->pSorter); + if( isSorter(pC) ){ + sqlite3VdbeSorterReset(db, pC->uc.pSorter); }else{ + assert( pC->eCurType==CURTYPE_BTREE ); assert( pC->isEphemeral ); - rc = sqlite3BtreeClearTableOfCursor(pC->pCursor); + rc = sqlite3BtreeClearTableOfCursor(pC->uc.pCursor); } break; } @@ -72435,15 +78923,16 @@ case OP_ResetSorter: { ** ** See documentation on OP_CreateTable for additional information. */ -case OP_CreateIndex: /* out2-prerelease */ -case OP_CreateTable: { /* out2-prerelease */ +case OP_CreateIndex: /* out2 */ +case OP_CreateTable: { /* out2 */ int pgno; int flags; Db *pDb; + pOut = out2Prerelease(p, pOp); pgno = 0; assert( pOp->p1>=0 && pOp->p1nDb ); - assert( (p->btreeMask & (((yDbMask)1)<p1))!=0 ); + assert( DbMaskTest(p->btreeMask, pOp->p1) ); assert( p->readOnly==0 ); pDb = &db->aDb[pOp->p1]; assert( pDb->pBt!=0 ); @@ -72531,7 +79020,8 @@ case OP_LoadAnalysis: { ** ** Remove the internal (in-memory) data structures that describe ** the table named P4 in database P1. This is called after a table -** is dropped in order to keep the internal representation of the +** is dropped from disk (using the Destroy opcode) in order to keep +** the internal representation of the ** schema consistent with what is on disk. */ case OP_DropTable: { @@ -72543,7 +79033,8 @@ case OP_DropTable: { ** ** Remove the internal (in-memory) data structures that describe ** the index named P4 in database P1. This is called after an index -** is dropped in order to keep the internal representation of the +** is dropped from disk (using the Destroy opcode) +** in order to keep the internal representation of the ** schema consistent with what is on disk. */ case OP_DropIndex: { @@ -72555,7 +79046,8 @@ case OP_DropIndex: { ** ** Remove the internal (in-memory) data structures that describe ** the trigger named P4 in database P1. This is called after a trigger -** is dropped in order to keep the internal representation of the +** is dropped from disk (using the Destroy opcode) in order to keep +** the internal representation of the ** schema consistent with what is on disk. */ case OP_DropTrigger: { @@ -72608,7 +79100,7 @@ case OP_IntegrityCk: { } aRoot[j] = 0; assert( pOp->p5nDb ); - assert( (p->btreeMask & (((yDbMask)1)<p5))!=0 ); + assert( DbMaskTest(p->btreeMask, pOp->p5) ); z = sqlite3BtreeIntegrityCheck(db->aDb[pOp->p5].pBt, aRoot, nRoot, (int)pnErr->u.i, &nErr); sqlite3DbFree(db, aRoot); @@ -72663,12 +79155,12 @@ case OP_RowSetRead: { /* jump, in1, out3 */ ){ /* The boolean index is empty */ sqlite3VdbeMemSetNull(pIn1); - pc = pOp->p2 - 1; VdbeBranchTaken(1,2); + goto jump_to_p2_and_check_for_interrupt; }else{ /* A value was pulled from the index */ - sqlite3VdbeMemSetInt64(&aMem[pOp->p3], val); VdbeBranchTaken(0,2); + sqlite3VdbeMemSetInt64(&aMem[pOp->p3], val); } goto check_for_interrupt; } @@ -72719,10 +79211,7 @@ case OP_RowSetTest: { /* jump, in1, in3 */ if( iSet ){ exists = sqlite3RowSetTest(pIn1->u.pRowSet, iSet, pIn3->u.i); VdbeBranchTaken(exists!=0,2); - if( exists ){ - pc = pOp->p2 - 1; - break; - } + if( exists ) goto jump_to_p2; } if( iSet>=0 ){ sqlite3RowSetInsert(pIn1->u.pRowSet, pIn3->u.i); @@ -72781,7 +79270,7 @@ case OP_Program: { /* jump */ if( p->nFrame>=db->aLimit[SQLITE_LIMIT_TRIGGER_DEPTH] ){ rc = SQLITE_ERROR; - sqlite3SetString(&p->zErrMsg, db, "too many levels of trigger recursion"); + sqlite3VdbeError(p, "too many levels of trigger recursion"); break; } @@ -72811,7 +79300,7 @@ case OP_Program: { /* jump */ pFrame->v = p; pFrame->nChildMem = nMem; pFrame->nChildCsr = pProgram->nCsr; - pFrame->pc = pc; + pFrame->pc = (int)(pOp - aOp); pFrame->aMem = p->aMem; pFrame->nMem = p->nMem; pFrame->apCsr = p->apCsr; @@ -72821,6 +79310,9 @@ case OP_Program: { /* jump */ pFrame->token = pProgram->token; pFrame->aOnceFlag = p->aOnceFlag; pFrame->nOnceFlag = p->nOnceFlag; +#ifdef SQLITE_ENABLE_STMT_SCANSTATUS + pFrame->anExec = p->anExec; +#endif pEnd = &VdbeFrameMem(pFrame)[pFrame->nChildMem]; for(pMem=VdbeFrameMem(pFrame); pMem!=pEnd; pMem++){ @@ -72831,13 +79323,14 @@ case OP_Program: { /* jump */ pFrame = pRt->u.pFrame; assert( pProgram->nMem+pProgram->nCsr==pFrame->nChildMem ); assert( pProgram->nCsr==pFrame->nChildCsr ); - assert( pc==pFrame->pc ); + assert( (int)(pOp - aOp)==pFrame->pc ); } p->nFrame++; pFrame->pParent = p->pFrame; pFrame->lastRowid = lastRowid; pFrame->nChange = p->nChange; + pFrame->nDbChange = p->db->nChange; p->nChange = 0; p->pFrame = pFrame; p->aMem = aMem = &VdbeFrameMem(pFrame)[-1]; @@ -72848,7 +79341,10 @@ case OP_Program: { /* jump */ p->nOp = pProgram->nOp; p->aOnceFlag = (u8 *)&p->apCsr[p->nCursor]; p->nOnceFlag = pProgram->nOnce; - pc = -1; +#ifdef SQLITE_ENABLE_STMT_SCANSTATUS + p->anExec = 0; +#endif + pOp = &aOp[-1]; memset(p->aOnceFlag, 0, p->nOnceFlag); break; @@ -72866,9 +79362,10 @@ case OP_Program: { /* jump */ ** the value of the P1 argument to the value of the P1 argument to the ** calling OP_Program instruction. */ -case OP_Param: { /* out2-prerelease */ +case OP_Param: { /* out2 */ VdbeFrame *pFrame; Mem *pIn; + pOut = out2Prerelease(p, pOp); pFrame = p->pFrame; pIn = &pFrame->aMem[pOp->p1 + pFrame->aOp[pFrame->pc].p1]; sqlite3VdbeMemShallowCopy(pOut, pIn, MEM_Ephem); @@ -72912,10 +79409,10 @@ case OP_FkCounter: { case OP_FkIfZero: { /* jump */ if( pOp->p1 ){ VdbeBranchTaken(db->nDeferredCons==0 && db->nDeferredImmCons==0, 2); - if( db->nDeferredCons==0 && db->nDeferredImmCons==0 ) pc = pOp->p2-1; + if( db->nDeferredCons==0 && db->nDeferredImmCons==0 ) goto jump_to_p2; }else{ VdbeBranchTaken(p->nFkConstraint==0 && db->nDeferredImmCons==0, 2); - if( p->nFkConstraint==0 && db->nDeferredImmCons==0 ) pc = pOp->p2-1; + if( p->nFkConstraint==0 && db->nDeferredImmCons==0 ) goto jump_to_p2; } break; } @@ -72952,122 +79449,189 @@ case OP_MemMax: { /* in2 */ } #endif /* SQLITE_OMIT_AUTOINCREMENT */ -/* Opcode: IfPos P1 P2 * * * -** Synopsis: if r[P1]>0 goto P2 +/* Opcode: IfPos P1 P2 P3 * * +** Synopsis: if r[P1]>0 then r[P1]-=P3, goto P2 ** -** If the value of register P1 is 1 or greater, jump to P2. +** Register P1 must contain an integer. +** If the value of register P1 is 1 or greater, subtract P3 from the +** value in P1 and jump to P2. ** -** It is illegal to use this instruction on a register that does -** not contain an integer. An assertion fault will result if you try. +** If the initial value of register P1 is less than 1, then the +** value is unchanged and control passes through to the next instruction. */ case OP_IfPos: { /* jump, in1 */ pIn1 = &aMem[pOp->p1]; assert( pIn1->flags&MEM_Int ); VdbeBranchTaken( pIn1->u.i>0, 2); if( pIn1->u.i>0 ){ - pc = pOp->p2 - 1; + pIn1->u.i -= pOp->p3; + goto jump_to_p2; } break; } -/* Opcode: IfNeg P1 P2 * * * -** Synopsis: if r[P1]<0 goto P2 +/* Opcode: SetIfNotPos P1 P2 P3 * * +** Synopsis: if r[P1]<=0 then r[P2]=P3 ** -** If the value of register P1 is less than zero, jump to P2. -** -** It is illegal to use this instruction on a register that does -** not contain an integer. An assertion fault will result if you try. +** Register P1 must contain an integer. +** If the value of register P1 is not positive (if it is less than 1) then +** set the value of register P2 to be the integer P3. */ -case OP_IfNeg: { /* jump, in1 */ +case OP_SetIfNotPos: { /* in1, in2 */ + pIn1 = &aMem[pOp->p1]; + assert( pIn1->flags&MEM_Int ); + if( pIn1->u.i<=0 ){ + pOut = out2Prerelease(p, pOp); + pOut->u.i = pOp->p3; + } + break; +} + +/* Opcode: IfNotZero P1 P2 P3 * * +** Synopsis: if r[P1]!=0 then r[P1]-=P3, goto P2 +** +** Register P1 must contain an integer. If the content of register P1 is +** initially nonzero, then subtract P3 from the value in register P1 and +** jump to P2. If register P1 is initially zero, leave it unchanged +** and fall through. +*/ +case OP_IfNotZero: { /* jump, in1 */ pIn1 = &aMem[pOp->p1]; assert( pIn1->flags&MEM_Int ); VdbeBranchTaken(pIn1->u.i<0, 2); - if( pIn1->u.i<0 ){ - pc = pOp->p2 - 1; + if( pIn1->u.i ){ + pIn1->u.i -= pOp->p3; + goto jump_to_p2; } break; } -/* Opcode: IfZero P1 P2 P3 * * -** Synopsis: r[P1]+=P3, if r[P1]==0 goto P2 +/* Opcode: DecrJumpZero P1 P2 * * * +** Synopsis: if (--r[P1])==0 goto P2 ** -** The register P1 must contain an integer. Add literal P3 to the -** value in register P1. If the result is exactly 0, jump to P2. -** -** It is illegal to use this instruction on a register that does -** not contain an integer. An assertion fault will result if you try. +** Register P1 must hold an integer. Decrement the value in register P1 +** then jump to P2 if the new value is exactly zero. */ -case OP_IfZero: { /* jump, in1 */ +case OP_DecrJumpZero: { /* jump, in1 */ pIn1 = &aMem[pOp->p1]; assert( pIn1->flags&MEM_Int ); - pIn1->u.i += pOp->p3; + pIn1->u.i--; VdbeBranchTaken(pIn1->u.i==0, 2); - if( pIn1->u.i==0 ){ - pc = pOp->p2 - 1; - } + if( pIn1->u.i==0 ) goto jump_to_p2; break; } -/* Opcode: AggStep * P2 P3 P4 P5 + +/* Opcode: JumpZeroIncr P1 P2 * * * +** Synopsis: if (r[P1]++)==0 ) goto P2 +** +** The register P1 must contain an integer. If register P1 is initially +** zero, then jump to P2. Increment register P1 regardless of whether or +** not the jump is taken. +*/ +case OP_JumpZeroIncr: { /* jump, in1 */ + pIn1 = &aMem[pOp->p1]; + assert( pIn1->flags&MEM_Int ); + VdbeBranchTaken(pIn1->u.i==0, 2); + if( (pIn1->u.i++)==0 ) goto jump_to_p2; + break; +} + +/* Opcode: AggStep0 * P2 P3 P4 P5 ** Synopsis: accum=r[P3] step(r[P2@P5]) ** ** Execute the step function for an aggregate. The ** function has P5 arguments. P4 is a pointer to the FuncDef -** structure that specifies the function. Use register -** P3 as the accumulator. +** structure that specifies the function. Register P3 is the +** accumulator. ** ** The P5 arguments are taken from register P2 and its ** successors. */ -case OP_AggStep: { +/* Opcode: AggStep * P2 P3 P4 P5 +** Synopsis: accum=r[P3] step(r[P2@P5]) +** +** Execute the step function for an aggregate. The +** function has P5 arguments. P4 is a pointer to an sqlite3_context +** object that is used to run the function. Register P3 is +** as the accumulator. +** +** The P5 arguments are taken from register P2 and its +** successors. +** +** This opcode is initially coded as OP_AggStep0. On first evaluation, +** the FuncDef stored in P4 is converted into an sqlite3_context and +** the opcode is changed. In this way, the initialization of the +** sqlite3_context only happens once, instead of on each call to the +** step function. +*/ +case OP_AggStep0: { int n; - int i; - Mem *pMem; - Mem *pRec; - sqlite3_context ctx; - sqlite3_value **apVal; + sqlite3_context *pCtx; + assert( pOp->p4type==P4_FUNCDEF ); n = pOp->p5; - assert( n>=0 ); - pRec = &aMem[pOp->p2]; - apVal = p->apArg; - assert( apVal || n==0 ); - for(i=0; ip4.pFunc; assert( pOp->p3>0 && pOp->p3<=(p->nMem-p->nCursor) ); - ctx.pMem = pMem = &aMem[pOp->p3]; + assert( n==0 || (pOp->p2>0 && pOp->p2+n<=(p->nMem-p->nCursor)+1) ); + assert( pOp->p3p2 || pOp->p3>=pOp->p2+n ); + pCtx = sqlite3DbMallocRaw(db, sizeof(*pCtx) + (n-1)*sizeof(sqlite3_value*)); + if( pCtx==0 ) goto no_mem; + pCtx->pMem = 0; + pCtx->pFunc = pOp->p4.pFunc; + pCtx->iOp = (int)(pOp - aOp); + pCtx->pVdbe = p; + pCtx->argc = n; + pOp->p4type = P4_FUNCCTX; + pOp->p4.pCtx = pCtx; + pOp->opcode = OP_AggStep; + /* Fall through into OP_AggStep */ +} +case OP_AggStep: { + int i; + sqlite3_context *pCtx; + Mem *pMem; + Mem t; + + assert( pOp->p4type==P4_FUNCCTX ); + pCtx = pOp->p4.pCtx; + pMem = &aMem[pOp->p3]; + + /* If this function is inside of a trigger, the register array in aMem[] + ** might change from one evaluation to the next. The next block of code + ** checks to see if the register array has changed, and if so it + ** reinitializes the relavant parts of the sqlite3_context object */ + if( pCtx->pMem != pMem ){ + pCtx->pMem = pMem; + for(i=pCtx->argc-1; i>=0; i--) pCtx->argv[i] = &aMem[pOp->p2+i]; + } + +#ifdef SQLITE_DEBUG + for(i=0; iargc; i++){ + assert( memIsValid(pCtx->argv[i]) ); + REGISTER_TRACE(pOp->p2+i, pCtx->argv[i]); + } +#endif + pMem->n++; - ctx.s.flags = MEM_Null; - ctx.s.z = 0; - ctx.s.zMalloc = 0; - ctx.s.xDel = 0; - ctx.s.db = db; - ctx.isError = 0; - ctx.pColl = 0; - ctx.skipFlag = 0; - if( ctx.pFunc->funcFlags & SQLITE_FUNC_NEEDCOLL ){ - assert( pOp>p->aOp ); - assert( pOp[-1].p4type==P4_COLLSEQ ); - assert( pOp[-1].opcode==OP_CollSeq ); - ctx.pColl = pOp[-1].p4.pColl; + sqlite3VdbeMemInit(&t, db, MEM_Null); + pCtx->pOut = &t; + pCtx->fErrorOrAux = 0; + pCtx->skipFlag = 0; + (pCtx->pFunc->xStep)(pCtx,pCtx->argc,pCtx->argv); /* IMP: R-24505-23230 */ + if( pCtx->fErrorOrAux ){ + if( pCtx->isError ){ + sqlite3VdbeError(p, "%s", sqlite3_value_text(&t)); + rc = pCtx->isError; + } + sqlite3VdbeMemRelease(&t); + }else{ + assert( t.flags==MEM_Null ); } - (ctx.pFunc->xStep)(&ctx, n, apVal); /* IMP: R-24505-23230 */ - if( ctx.isError ){ - sqlite3SetString(&p->zErrMsg, db, "%s", sqlite3_value_text(&ctx.s)); - rc = ctx.isError; - } - if( ctx.skipFlag ){ + if( pCtx->skipFlag ){ assert( pOp[-1].opcode==OP_CollSeq ); i = pOp[-1].p1; if( i ) sqlite3VdbeMemSetInt64(&aMem[i], 1); } - - sqlite3VdbeMemRelease(&ctx.s); - break; } @@ -73091,7 +79655,7 @@ case OP_AggFinal: { assert( (pMem->flags & ~(MEM_Null|MEM_Agg))==0 ); rc = sqlite3VdbeMemFinalize(pMem, pOp->p4.pFunc); if( rc ){ - sqlite3SetString(&p->zErrMsg, db, "%s", sqlite3_value_text(pMem)); + sqlite3VdbeError(p, "%s", sqlite3_value_text(pMem)); } sqlite3VdbeChangeEncoding(pMem, encoding); UPDATE_MAX_BLOBSIZE(pMem); @@ -73105,8 +79669,8 @@ case OP_AggFinal: { /* Opcode: Checkpoint P1 P2 P3 * * ** ** Checkpoint database P1. This is a no-op if P1 is not currently in -** WAL mode. Parameter P2 is one of SQLITE_CHECKPOINT_PASSIVE, FULL -** or RESTART. Write 1 or 0 into mem[P3] if the checkpoint returns +** WAL mode. Parameter P2 is one of SQLITE_CHECKPOINT_PASSIVE, FULL, +** RESTART, or TRUNCATE. Write 1 or 0 into mem[P3] if the checkpoint returns ** SQLITE_BUSY or not, respectively. Write the number of pages in the ** WAL after the checkpoint into mem[P3+1] and the number of pages ** in the WAL that have been checkpointed after the checkpoint @@ -73124,6 +79688,7 @@ case OP_Checkpoint: { assert( pOp->p2==SQLITE_CHECKPOINT_PASSIVE || pOp->p2==SQLITE_CHECKPOINT_FULL || pOp->p2==SQLITE_CHECKPOINT_RESTART + || pOp->p2==SQLITE_CHECKPOINT_TRUNCATE ); rc = sqlite3Checkpoint(db, pOp->p1, pOp->p2, &aRes[1], &aRes[2]); if( rc==SQLITE_BUSY ){ @@ -73149,7 +79714,7 @@ case OP_Checkpoint: { ** ** Write a string containing the final journal-mode to register P2. */ -case OP_JournalMode: { /* out2-prerelease */ +case OP_JournalMode: { /* out2 */ Btree *pBt; /* Btree to change journal mode of */ Pager *pPager; /* Pager associated with pBt */ int eNew; /* New journal mode */ @@ -73158,6 +79723,7 @@ case OP_JournalMode: { /* out2-prerelease */ const char *zFilename; /* Name of database file for pPager */ #endif + pOut = out2Prerelease(p, pOp); eNew = pOp->p3; assert( eNew==PAGER_JOURNALMODE_DELETE || eNew==PAGER_JOURNALMODE_TRUNCATE @@ -73194,7 +79760,7 @@ case OP_JournalMode: { /* out2-prerelease */ ){ if( !db->autoCommit || db->nVdbeRead>1 ){ rc = SQLITE_ERROR; - sqlite3SetString(&p->zErrMsg, db, + sqlite3VdbeError(p, "cannot change %s wal mode from within a transaction", (eNew==PAGER_JOURNALMODE_WAL ? "into" : "out of") ); @@ -73233,7 +79799,6 @@ case OP_JournalMode: { /* out2-prerelease */ } eNew = sqlite3PagerSetJournalMode(pPager, eNew); - pOut = &aMem[pOp->p2]; pOut->flags = MEM_Str|MEM_Static|MEM_Term; pOut->z = (char *)sqlite3JournalModename(eNew); pOut->n = sqlite3Strlen30(pOut->z); @@ -73268,14 +79833,14 @@ case OP_IncrVacuum: { /* jump */ Btree *pBt; assert( pOp->p1>=0 && pOp->p1nDb ); - assert( (p->btreeMask & (((yDbMask)1)<p1))!=0 ); + assert( DbMaskTest(p->btreeMask, pOp->p1) ); assert( p->readOnly==0 ); pBt = db->aDb[pOp->p1].pBt; rc = sqlite3BtreeIncrVacuum(pBt); VdbeBranchTaken(rc==SQLITE_DONE,2); if( rc==SQLITE_DONE ){ - pc = pOp->p2 - 1; rc = SQLITE_OK; + goto jump_to_p2; } break; } @@ -73283,12 +79848,13 @@ case OP_IncrVacuum: { /* jump */ /* Opcode: Expire P1 * * * * ** -** Cause precompiled statements to become expired. An expired statement -** fails with an error code of SQLITE_SCHEMA if it is ever executed -** (via sqlite3_step()). +** Cause precompiled statements to expire. When an expired statement +** is executed using sqlite3_step() it will either automatically +** reprepare itself (if it was originally created using sqlite3_prepare_v2()) +** or it will fail with SQLITE_SCHEMA. ** ** If P1 is 0, then all SQL statements become expired. If P1 is non-zero, -** then only the currently executing statement is affected. +** then only the currently executing statement is expired. */ case OP_Expire: { if( !pOp->p1 ){ @@ -73320,12 +79886,12 @@ case OP_TableLock: { if( isWriteLock || 0==(db->flags&SQLITE_ReadUncommitted) ){ int p1 = pOp->p1; assert( p1>=0 && p1nDb ); - assert( (p->btreeMask & (((yDbMask)1)<btreeMask, p1) ); assert( isWriteLock==0 || isWriteLock==1 ); rc = sqlite3BtreeLockTable(db->aDb[p1].pBt, pOp->p2, isWriteLock); if( (rc&0xFF)==SQLITE_LOCKED ){ const char *z = pOp->p4.z; - sqlite3SetString(&p->zErrMsg, db, "database table is locked: %s", z); + sqlite3VdbeError(p, "database table is locked: %s", z); } } break; @@ -73352,13 +79918,29 @@ case OP_VBegin: { #endif /* SQLITE_OMIT_VIRTUALTABLE */ #ifndef SQLITE_OMIT_VIRTUALTABLE -/* Opcode: VCreate P1 * * P4 * +/* Opcode: VCreate P1 P2 * * * ** -** P4 is the name of a virtual table in database P1. Call the xCreate method -** for that table. +** P2 is a register that holds the name of a virtual table in database +** P1. Call the xCreate method for that table. */ case OP_VCreate: { - rc = sqlite3VtabCallCreate(db, pOp->p1, pOp->p4.z, &p->zErrMsg); + Mem sMem; /* For storing the record being decoded */ + const char *zTab; /* Name of the virtual table */ + + memset(&sMem, 0, sizeof(sMem)); + sMem.db = db; + /* Because P2 is always a static string, it is impossible for the + ** sqlite3VdbeMemCopy() to fail */ + assert( (aMem[pOp->p2].flags & MEM_Str)!=0 ); + assert( (aMem[pOp->p2].flags & MEM_Static)!=0 ); + rc = sqlite3VdbeMemCopy(&sMem, &aMem[pOp->p2]); + assert( rc==SQLITE_OK ); + zTab = (const char*)sqlite3_value_text(&sMem); + assert( zTab || db->mallocFailed ); + if( zTab ){ + rc = sqlite3VtabCallCreate(db, pOp->p1, zTab, &p->zErrMsg); + } + sqlite3VdbeMemRelease(&sMem); break; } #endif /* SQLITE_OMIT_VIRTUALTABLE */ @@ -73370,9 +79952,9 @@ case OP_VCreate: { ** of that table. */ case OP_VDestroy: { - p->inVtabMethod = 2; + db->nVDestroy++; rc = sqlite3VtabCallDestroy(db, pOp->p1, pOp->p4.z); - p->inVtabMethod = 0; + db->nVDestroy--; break; } #endif /* SQLITE_OMIT_VIRTUALTABLE */ @@ -73386,29 +79968,34 @@ case OP_VDestroy: { */ case OP_VOpen: { VdbeCursor *pCur; - sqlite3_vtab_cursor *pVtabCursor; + sqlite3_vtab_cursor *pVCur; sqlite3_vtab *pVtab; - sqlite3_module *pModule; + const sqlite3_module *pModule; assert( p->bIsReader ); pCur = 0; - pVtabCursor = 0; + pVCur = 0; pVtab = pOp->p4.pVtab->pVtab; - pModule = (sqlite3_module *)pVtab->pModule; - assert(pVtab && pModule); - rc = pModule->xOpen(pVtab, &pVtabCursor); + if( pVtab==0 || NEVER(pVtab->pModule==0) ){ + rc = SQLITE_LOCKED; + break; + } + pModule = pVtab->pModule; + rc = pModule->xOpen(pVtab, &pVCur); sqlite3VtabImportErrmsg(p, pVtab); if( SQLITE_OK==rc ){ /* Initialize sqlite3_vtab_cursor base class */ - pVtabCursor->pVtab = pVtab; + pVCur->pVtab = pVtab; /* Initialize vdbe cursor object */ - pCur = allocateCursor(p, pOp->p1, 0, -1, 0); + pCur = allocateCursor(p, pOp->p1, 0, -1, CURTYPE_VTAB); if( pCur ){ - pCur->pVtabCursor = pVtabCursor; + pCur->uc.pVCur = pVCur; + pVtab->nRef++; }else{ - db->mallocFailed = 1; - pModule->xClose(pVtabCursor); + assert( db->mallocFailed ); + pModule->xClose(pVCur); + goto no_mem; } } break; @@ -73441,7 +80028,7 @@ case OP_VFilter: { /* jump */ const sqlite3_module *pModule; Mem *pQuery; Mem *pArgc; - sqlite3_vtab_cursor *pVtabCursor; + sqlite3_vtab_cursor *pVCur; sqlite3_vtab *pVtab; VdbeCursor *pCur; int res; @@ -73453,9 +80040,9 @@ case OP_VFilter: { /* jump */ pCur = p->apCsr[pOp->p1]; assert( memIsValid(pQuery) ); REGISTER_TRACE(pOp->p3, pQuery); - assert( pCur->pVtabCursor ); - pVtabCursor = pCur->pVtabCursor; - pVtab = pVtabCursor->pVtab; + assert( pCur->eCurType==CURTYPE_VTAB ); + pVCur = pCur->uc.pVCur; + pVtab = pVCur->pVtab; pModule = pVtab->pModule; /* Grab the index number and argc parameters */ @@ -73464,27 +80051,19 @@ case OP_VFilter: { /* jump */ iQuery = (int)pQuery->u.i; /* Invoke the xFilter method */ - { - res = 0; - apArg = p->apArg; - for(i = 0; iinVtabMethod = 1; - rc = pModule->xFilter(pVtabCursor, iQuery, pOp->p4.z, nArg, apArg); - p->inVtabMethod = 0; - sqlite3VtabImportErrmsg(p, pVtab); - if( rc==SQLITE_OK ){ - res = pModule->xEof(pVtabCursor); - } - VdbeBranchTaken(res!=0,2); - if( res ){ - pc = pOp->p2 - 1; - } + res = 0; + apArg = p->apArg; + for(i = 0; ixFilter(pVCur, iQuery, pOp->p4.z, nArg, apArg); + sqlite3VtabImportErrmsg(p, pVtab); + if( rc==SQLITE_OK ){ + res = pModule->xEof(pVCur); } pCur->nullRow = 0; - + VdbeBranchTaken(res!=0,2); + if( res ) goto jump_to_p2; break; } #endif /* SQLITE_OMIT_VIRTUALTABLE */ @@ -73504,7 +80083,7 @@ case OP_VColumn: { sqlite3_context sContext; VdbeCursor *pCur = p->apCsr[pOp->p1]; - assert( pCur->pVtabCursor ); + assert( pCur->eCurType==CURTYPE_VTAB ); assert( pOp->p3>0 && pOp->p3<=(p->nMem-p->nCursor) ); pDest = &aMem[pOp->p3]; memAboutToChange(p, pDest); @@ -73512,31 +80091,18 @@ case OP_VColumn: { sqlite3VdbeMemSetNull(pDest); break; } - pVtab = pCur->pVtabCursor->pVtab; + pVtab = pCur->uc.pVCur->pVtab; pModule = pVtab->pModule; assert( pModule->xColumn ); memset(&sContext, 0, sizeof(sContext)); - - /* The output cell may already have a buffer allocated. Move - ** the current contents to sContext.s so in case the user-function - ** can use the already allocated buffer instead of allocating a - ** new one. - */ - sqlite3VdbeMemMove(&sContext.s, pDest); - MemSetTypeFlag(&sContext.s, MEM_Null); - - rc = pModule->xColumn(pCur->pVtabCursor, &sContext, pOp->p2); + sContext.pOut = pDest; + MemSetTypeFlag(pDest, MEM_Null); + rc = pModule->xColumn(pCur->uc.pVCur, &sContext, pOp->p2); sqlite3VtabImportErrmsg(p, pVtab); if( sContext.isError ){ rc = sContext.isError; } - - /* Copy the result of the function to the P3 register. We - ** do this regardless of whether or not an error occurred to ensure any - ** dynamic allocation in sContext.s (a Mem struct) is released. - */ - sqlite3VdbeChangeEncoding(&sContext.s, encoding); - sqlite3VdbeMemMove(pDest, &sContext.s); + sqlite3VdbeChangeEncoding(pDest, encoding); REGISTER_TRACE(pOp->p3, pDest); UPDATE_MAX_BLOBSIZE(pDest); @@ -73562,11 +80128,11 @@ case OP_VNext: { /* jump */ res = 0; pCur = p->apCsr[pOp->p1]; - assert( pCur->pVtabCursor ); + assert( pCur->eCurType==CURTYPE_VTAB ); if( pCur->nullRow ){ break; } - pVtab = pCur->pVtabCursor->pVtab; + pVtab = pCur->uc.pVCur->pVtab; pModule = pVtab->pModule; assert( pModule->xNext ); @@ -73576,17 +80142,15 @@ case OP_VNext: { /* jump */ ** data is available) and the error code returned when xColumn or ** some other method is next invoked on the save virtual table cursor. */ - p->inVtabMethod = 1; - rc = pModule->xNext(pCur->pVtabCursor); - p->inVtabMethod = 0; + rc = pModule->xNext(pCur->uc.pVCur); sqlite3VtabImportErrmsg(p, pVtab); if( rc==SQLITE_OK ){ - res = pModule->xEof(pCur->pVtabCursor); + res = pModule->xEof(pCur->uc.pVCur); } VdbeBranchTaken(!res,2); if( !res ){ /* If there is data, jump to P2 */ - pc = pOp->p2 - 1; + goto jump_to_p2_and_check_for_interrupt; } goto check_for_interrupt; } @@ -73653,7 +80217,7 @@ case OP_VRename: { */ case OP_VUpdate: { sqlite3_vtab *pVtab; - sqlite3_module *pModule; + const sqlite3_module *pModule; int nArg; int i; sqlite_int64 rowid; @@ -73665,7 +80229,11 @@ case OP_VUpdate: { ); assert( p->readOnly==0 ); pVtab = pOp->p4.pVtab->pVtab; - pModule = (sqlite3_module *)pVtab->pModule; + if( pVtab==0 || NEVER(pVtab->pModule==0) ){ + rc = SQLITE_LOCKED; + break; + } + pModule = pVtab->pModule; nArg = pOp->p2; assert( pOp->p4type==P4_VTAB ); if( ALWAYS(pModule->xUpdate) ){ @@ -73705,7 +80273,8 @@ case OP_VUpdate: { ** ** Write the current number of pages in database P1 to memory cell P2. */ -case OP_Pagecount: { /* out2-prerelease */ +case OP_Pagecount: { /* out2 */ + pOut = out2Prerelease(p, pOp); pOut->u.i = sqlite3BtreeLastPage(db->aDb[pOp->p1].pBt); break; } @@ -73721,10 +80290,11 @@ case OP_Pagecount: { /* out2-prerelease */ ** ** Store the maximum page count after the change in register P2. */ -case OP_MaxPgcnt: { /* out2-prerelease */ +case OP_MaxPgcnt: { /* out2 */ unsigned int newMax; Btree *pBt; + pOut = out2Prerelease(p, pOp); pBt = db->aDb[pOp->p1].pBt; newMax = 0; if( pOp->p3 ){ @@ -73753,9 +80323,6 @@ case OP_Init: { /* jump */ char *zTrace; char *z; - if( pOp->p2 ){ - pc = pOp->p2 - 1; - } #ifndef SQLITE_OMIT_TRACE if( db->xTrace && !p->doingRerun @@ -73770,7 +80337,7 @@ case OP_Init: { /* jump */ if( zTrace ){ int i; for(i=0; inDb; i++){ - if( (MASKBIT(i) & p->btreeMask)==0 ) continue; + if( DbMaskTest(p->btreeMask, i)==0 ) continue; sqlite3_file_control(db, db->aDb[i].zName, SQLITE_FCNTL_TRACE, zTrace); } } @@ -73783,9 +80350,32 @@ case OP_Init: { /* jump */ } #endif /* SQLITE_DEBUG */ #endif /* SQLITE_OMIT_TRACE */ + if( pOp->p2 ) goto jump_to_p2; break; } +#ifdef SQLITE_ENABLE_CURSOR_HINTS +/* Opcode: CursorHint P1 * * P4 * +** +** Provide a hint to cursor P1 that it only needs to return rows that +** satisfy the Expr in P4. TK_REGISTER terms in the P4 expression refer +** to values currently held in registers. TK_COLUMN terms in the P4 +** expression refer to columns in the b-tree to which cursor P1 is pointing. +*/ +case OP_CursorHint: { + VdbeCursor *pC; + + assert( pOp->p1>=0 && pOp->p1nCursor ); + assert( pOp->p4type==P4_EXPR ); + pC = p->apCsr[pOp->p1]; + if( pC ){ + assert( pC->eCurType==CURTYPE_BTREE ); + sqlite3BtreeCursorHint(pC->uc.pCursor, BTREE_HINT_RANGE, + pOp->p4.pExpr, aMem); + } + break; +} +#endif /* SQLITE_ENABLE_CURSOR_HINTS */ /* Opcode: Noop * * * * * ** @@ -73814,8 +80404,8 @@ default: { /* This is really OP_Noop and OP_Explain */ #ifdef VDBE_PROFILE { u64 endTime = sqlite3Hwtime(); - if( endTime>start ) pOp->cycles += endTime - start; - pOp->cnt++; + if( endTime>start ) pOrigOp->cycles += endTime - start; + pOrigOp->cnt++; } #endif @@ -73825,16 +80415,16 @@ default: { /* This is really OP_Noop and OP_Explain */ ** the evaluator loop. So we can leave it out when NDEBUG is defined. */ #ifndef NDEBUG - assert( pc>=-1 && pcnOp ); + assert( pOp>=&aOp[-1] && pOp<&aOp[p->nOp-1] ); #ifdef SQLITE_DEBUG if( db->flags & SQLITE_VdbeTrace ){ if( rc!=0 ) printf("rc=%d\n",rc); - if( pOp->opflags & (OPFLG_OUT2_PRERELEASE|OPFLG_OUT2) ){ - registerTrace(pOp->p2, &aMem[pOp->p2]); + if( pOrigOp->opflags & (OPFLG_OUT2) ){ + registerTrace(pOrigOp->p2, &aMem[pOrigOp->p2]); } - if( pOp->opflags & OPFLG_OUT3 ){ - registerTrace(pOp->p3, &aMem[pOp->p3]); + if( pOrigOp->opflags & OPFLG_OUT3 ){ + registerTrace(pOrigOp->p3, &aMem[pOrigOp->p3]); } } #endif /* SQLITE_DEBUG */ @@ -73849,7 +80439,7 @@ vdbe_error_halt: p->rc = rc; testcase( sqlite3GlobalConfig.xLog!=0 ); sqlite3_log(rc, "statement aborts at %d: [%s] %s", - pc, p->zSql, p->zErrMsg); + (int)(pOp - aOp), p->zSql, p->zErrMsg); sqlite3VdbeHalt(p); if( rc==SQLITE_IOERR_NOMEM ) db->mallocFailed = 1; rc = SQLITE_ERROR; @@ -73871,7 +80461,7 @@ vdbe_return: ** is encountered. */ too_big: - sqlite3SetString(&p->zErrMsg, db, "string or blob too big"); + sqlite3VdbeError(p, "string or blob too big"); rc = SQLITE_TOOBIG; goto vdbe_error_halt; @@ -73879,7 +80469,7 @@ too_big: */ no_mem: db->mallocFailed = 1; - sqlite3SetString(&p->zErrMsg, db, "out of memory"); + sqlite3VdbeError(p, "out of memory"); rc = SQLITE_NOMEM; goto vdbe_error_halt; @@ -73890,7 +80480,7 @@ abort_due_to_error: assert( p->zErrMsg==0 ); if( db->mallocFailed ) rc = SQLITE_NOMEM; if( rc!=SQLITE_IOERR_NOMEM ){ - sqlite3SetString(&p->zErrMsg, db, "%s", sqlite3ErrStr(rc)); + sqlite3VdbeError(p, "%s", sqlite3ErrStr(rc)); } goto vdbe_error_halt; @@ -73901,7 +80491,7 @@ abort_due_to_interrupt: assert( db->u1.isInterrupted ); rc = SQLITE_INTERRUPT; p->rc = rc; - sqlite3SetString(&p->zErrMsg, db, "%s", sqlite3ErrStr(rc)); + sqlite3VdbeError(p, "%s", sqlite3ErrStr(rc)); goto vdbe_error_halt; } @@ -73923,6 +80513,8 @@ abort_due_to_interrupt: ** This file contains code used to implement incremental BLOB I/O. */ +/* #include "sqliteInt.h" */ +/* #include "vdbeInt.h" */ #ifndef SQLITE_OMIT_INCRBLOB @@ -73984,7 +80576,7 @@ static int blobSeekToRow(Incrblob *p, sqlite3_int64 iRow, char **pzErr){ }else{ p->iOffset = pC->aType[p->iCol + pC->nField]; p->nByte = sqlite3VdbeSerialTypeLen(type); - p->pCsr = pC->pCursor; + p->pCsr = pC->uc.pCursor; sqlite3BtreeIncrblobCursor(p->pCsr); } } @@ -74012,7 +80604,7 @@ static int blobSeekToRow(Incrblob *p, sqlite3_int64 iRow, char **pzErr){ /* ** Open a blob handle. */ -SQLITE_API int sqlite3_blob_open( +SQLITE_API int SQLITE_STDCALL sqlite3_blob_open( sqlite3* db, /* The database connection */ const char *zDb, /* The attached database containing the blob */ const char *zTable, /* The table containing the blob */ @@ -74061,8 +80653,18 @@ SQLITE_API int sqlite3_blob_open( Parse *pParse = 0; Incrblob *pBlob = 0; - flags = !!flags; /* flags = (flags ? 1 : 0); */ +#ifdef SQLITE_ENABLE_API_ARMOR + if( ppBlob==0 ){ + return SQLITE_MISUSE_BKPT; + } +#endif *ppBlob = 0; +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) || zTable==0 ){ + return SQLITE_MISUSE_BKPT; + } +#endif + flags = !!flags; /* flags = (flags ? 1 : 0); */ sqlite3_mutex_enter(db->mutex); @@ -74145,7 +80747,8 @@ SQLITE_API int sqlite3_blob_open( for(pIdx=pTab->pIndex; pIdx; pIdx=pIdx->pNext){ int j; for(j=0; jnKeyCol; j++){ - if( pIdx->aiColumn[j]==iCol ){ + /* FIXME: Be smarter about indexes that use expressions */ + if( pIdx->aiColumn[j]==iCol || pIdx->aiColumn[j]==XN_EXPR ){ zFault = "indexed"; } } @@ -74226,7 +80829,7 @@ blob_open_out: if( pBlob && pBlob->pStmt ) sqlite3VdbeFinalize((Vdbe *)pBlob->pStmt); sqlite3DbFree(db, pBlob); } - sqlite3Error(db, rc, (zErr ? "%s" : 0), zErr); + sqlite3ErrorWithMsg(db, rc, (zErr ? "%s" : 0), zErr); sqlite3DbFree(db, zErr); sqlite3ParserReset(pParse); sqlite3StackFree(db, pParse); @@ -74239,7 +80842,7 @@ blob_open_out: ** Close a blob handle that was previously created using ** sqlite3_blob_open(). */ -SQLITE_API int sqlite3_blob_close(sqlite3_blob *pBlob){ +SQLITE_API int SQLITE_STDCALL sqlite3_blob_close(sqlite3_blob *pBlob){ Incrblob *p = (Incrblob *)pBlob; int rc; sqlite3 *db; @@ -74276,10 +80879,9 @@ static int blobReadWrite( sqlite3_mutex_enter(db->mutex); v = (Vdbe*)p->pStmt; - if( n<0 || iOffset<0 || (iOffset+n)>p->nByte ){ + if( n<0 || iOffset<0 || ((sqlite3_int64)iOffset+n)>p->nByte ){ /* Request is out of range. Return a transient error. */ rc = SQLITE_ERROR; - sqlite3Error(db, SQLITE_ERROR, 0); }else if( v==0 ){ /* If there is no statement handle, then the blob-handle has ** already been invalidated. Return SQLITE_ABORT in this case. @@ -74297,10 +80899,10 @@ static int blobReadWrite( sqlite3VdbeFinalize(v); p->pStmt = 0; }else{ - db->errCode = rc; v->rc = rc; } } + sqlite3Error(db, rc); rc = sqlite3ApiExit(db, rc); sqlite3_mutex_leave(db->mutex); return rc; @@ -74309,14 +80911,14 @@ static int blobReadWrite( /* ** Read data from a blob handle. */ -SQLITE_API int sqlite3_blob_read(sqlite3_blob *pBlob, void *z, int n, int iOffset){ +SQLITE_API int SQLITE_STDCALL sqlite3_blob_read(sqlite3_blob *pBlob, void *z, int n, int iOffset){ return blobReadWrite(pBlob, z, n, iOffset, sqlite3BtreeData); } /* ** Write data to a blob handle. */ -SQLITE_API int sqlite3_blob_write(sqlite3_blob *pBlob, const void *z, int n, int iOffset){ +SQLITE_API int SQLITE_STDCALL sqlite3_blob_write(sqlite3_blob *pBlob, const void *z, int n, int iOffset){ return blobReadWrite(pBlob, (void *)z, n, iOffset, sqlite3BtreePutData); } @@ -74326,7 +80928,7 @@ SQLITE_API int sqlite3_blob_write(sqlite3_blob *pBlob, const void *z, int n, int ** The Incrblob.nByte field is fixed for the lifetime of the Incrblob ** so no mutex is required for access. */ -SQLITE_API int sqlite3_blob_bytes(sqlite3_blob *pBlob){ +SQLITE_API int SQLITE_STDCALL sqlite3_blob_bytes(sqlite3_blob *pBlob){ Incrblob *p = (Incrblob *)pBlob; return (p && p->pStmt) ? p->nByte : 0; } @@ -74341,7 +80943,7 @@ SQLITE_API int sqlite3_blob_bytes(sqlite3_blob *pBlob){ ** subsequent calls to sqlite3_blob_xxx() functions (except blob_close()) ** immediately return SQLITE_ABORT. */ -SQLITE_API int sqlite3_blob_reopen(sqlite3_blob *pBlob, sqlite3_int64 iRow){ +SQLITE_API int SQLITE_STDCALL sqlite3_blob_reopen(sqlite3_blob *pBlob, sqlite3_int64 iRow){ int rc; Incrblob *p = (Incrblob *)pBlob; sqlite3 *db; @@ -74359,7 +80961,7 @@ SQLITE_API int sqlite3_blob_reopen(sqlite3_blob *pBlob, sqlite3_int64 iRow){ char *zErr; rc = blobSeekToRow(p, iRow, &zErr); if( rc!=SQLITE_OK ){ - sqlite3Error(db, rc, (zErr ? "%s" : 0), zErr); + sqlite3ErrorWithMsg(db, rc, (zErr ? "%s" : 0), zErr); sqlite3DbFree(db, zErr); } assert( rc!=SQLITE_SCHEMA ); @@ -74376,7 +80978,7 @@ SQLITE_API int sqlite3_blob_reopen(sqlite3_blob *pBlob, sqlite3_int64 iRow){ /************** End of vdbeblob.c ********************************************/ /************** Begin file vdbesort.c ****************************************/ /* -** 2011 July 9 +** 2011-07-09 ** ** The author disclaims copyright to this source code. In place of ** a legal notice, here is a blessing: @@ -74387,42 +80989,205 @@ SQLITE_API int sqlite3_blob_reopen(sqlite3_blob *pBlob, sqlite3_int64 iRow){ ** ************************************************************************* ** This file contains code for the VdbeSorter object, used in concert with -** a VdbeCursor to sort large numbers of keys (as may be required, for -** example, by CREATE INDEX statements on tables too large to fit in main -** memory). +** a VdbeCursor to sort large numbers of keys for CREATE INDEX statements +** or by SELECT statements with ORDER BY clauses that cannot be satisfied +** using indexes and without LIMIT clauses. +** +** The VdbeSorter object implements a multi-threaded external merge sort +** algorithm that is efficient even if the number of elements being sorted +** exceeds the available memory. +** +** Here is the (internal, non-API) interface between this module and the +** rest of the SQLite system: +** +** sqlite3VdbeSorterInit() Create a new VdbeSorter object. +** +** sqlite3VdbeSorterWrite() Add a single new row to the VdbeSorter +** object. The row is a binary blob in the +** OP_MakeRecord format that contains both +** the ORDER BY key columns and result columns +** in the case of a SELECT w/ ORDER BY, or +** the complete record for an index entry +** in the case of a CREATE INDEX. +** +** sqlite3VdbeSorterRewind() Sort all content previously added. +** Position the read cursor on the +** first sorted element. +** +** sqlite3VdbeSorterNext() Advance the read cursor to the next sorted +** element. +** +** sqlite3VdbeSorterRowkey() Return the complete binary blob for the +** row currently under the read cursor. +** +** sqlite3VdbeSorterCompare() Compare the binary blob for the row +** currently under the read cursor against +** another binary blob X and report if +** X is strictly less than the read cursor. +** Used to enforce uniqueness in a +** CREATE UNIQUE INDEX statement. +** +** sqlite3VdbeSorterClose() Close the VdbeSorter object and reclaim +** all resources. +** +** sqlite3VdbeSorterReset() Refurbish the VdbeSorter for reuse. This +** is like Close() followed by Init() only +** much faster. +** +** The interfaces above must be called in a particular order. Write() can +** only occur in between Init()/Reset() and Rewind(). Next(), Rowkey(), and +** Compare() can only occur in between Rewind() and Close()/Reset(). i.e. +** +** Init() +** for each record: Write() +** Rewind() +** Rowkey()/Compare() +** Next() +** Close() +** +** Algorithm: +** +** Records passed to the sorter via calls to Write() are initially held +** unsorted in main memory. Assuming the amount of memory used never exceeds +** a threshold, when Rewind() is called the set of records is sorted using +** an in-memory merge sort. In this case, no temporary files are required +** and subsequent calls to Rowkey(), Next() and Compare() read records +** directly from main memory. +** +** If the amount of space used to store records in main memory exceeds the +** threshold, then the set of records currently in memory are sorted and +** written to a temporary file in "Packed Memory Array" (PMA) format. +** A PMA created at this point is known as a "level-0 PMA". Higher levels +** of PMAs may be created by merging existing PMAs together - for example +** merging two or more level-0 PMAs together creates a level-1 PMA. +** +** The threshold for the amount of main memory to use before flushing +** records to a PMA is roughly the same as the limit configured for the +** page-cache of the main database. Specifically, the threshold is set to +** the value returned by "PRAGMA main.page_size" multipled by +** that returned by "PRAGMA main.cache_size", in bytes. +** +** If the sorter is running in single-threaded mode, then all PMAs generated +** are appended to a single temporary file. Or, if the sorter is running in +** multi-threaded mode then up to (N+1) temporary files may be opened, where +** N is the configured number of worker threads. In this case, instead of +** sorting the records and writing the PMA to a temporary file itself, the +** calling thread usually launches a worker thread to do so. Except, if +** there are already N worker threads running, the main thread does the work +** itself. +** +** The sorter is running in multi-threaded mode if (a) the library was built +** with pre-processor symbol SQLITE_MAX_WORKER_THREADS set to a value greater +** than zero, and (b) worker threads have been enabled at runtime by calling +** "PRAGMA threads=N" with some value of N greater than 0. +** +** When Rewind() is called, any data remaining in memory is flushed to a +** final PMA. So at this point the data is stored in some number of sorted +** PMAs within temporary files on disk. +** +** If there are fewer than SORTER_MAX_MERGE_COUNT PMAs in total and the +** sorter is running in single-threaded mode, then these PMAs are merged +** incrementally as keys are retreived from the sorter by the VDBE. The +** MergeEngine object, described in further detail below, performs this +** merge. +** +** Or, if running in multi-threaded mode, then a background thread is +** launched to merge the existing PMAs. Once the background thread has +** merged T bytes of data into a single sorted PMA, the main thread +** begins reading keys from that PMA while the background thread proceeds +** with merging the next T bytes of data. And so on. +** +** Parameter T is set to half the value of the memory threshold used +** by Write() above to determine when to create a new PMA. +** +** If there are more than SORTER_MAX_MERGE_COUNT PMAs in total when +** Rewind() is called, then a hierarchy of incremental-merges is used. +** First, T bytes of data from the first SORTER_MAX_MERGE_COUNT PMAs on +** disk are merged together. Then T bytes of data from the second set, and +** so on, such that no operation ever merges more than SORTER_MAX_MERGE_COUNT +** PMAs at a time. This done is to improve locality. +** +** If running in multi-threaded mode and there are more than +** SORTER_MAX_MERGE_COUNT PMAs on disk when Rewind() is called, then more +** than one background thread may be created. Specifically, there may be +** one background thread for each temporary file on disk, and one background +** thread to merge the output of each of the others to a single PMA for +** the main thread to read from. */ +/* #include "sqliteInt.h" */ +/* #include "vdbeInt.h" */ - - -typedef struct VdbeSorterIter VdbeSorterIter; -typedef struct SorterRecord SorterRecord; -typedef struct FileWriter FileWriter; +/* +** If SQLITE_DEBUG_SORTER_THREADS is defined, this module outputs various +** messages to stderr that may be helpful in understanding the performance +** characteristics of the sorter in multi-threaded mode. +*/ +#if 0 +# define SQLITE_DEBUG_SORTER_THREADS 1 +#endif /* -** NOTES ON DATA STRUCTURE USED FOR N-WAY MERGES: +** Hard-coded maximum amount of data to accumulate in memory before flushing +** to a level 0 PMA. The purpose of this limit is to prevent various integer +** overflows. 512MiB. +*/ +#define SQLITE_MAX_PMASZ (1<<29) + +/* +** Private objects used by the sorter +*/ +typedef struct MergeEngine MergeEngine; /* Merge PMAs together */ +typedef struct PmaReader PmaReader; /* Incrementally read one PMA */ +typedef struct PmaWriter PmaWriter; /* Incrementally write one PMA */ +typedef struct SorterRecord SorterRecord; /* A record being sorted */ +typedef struct SortSubtask SortSubtask; /* A sub-task in the sort process */ +typedef struct SorterFile SorterFile; /* Temporary file object wrapper */ +typedef struct SorterList SorterList; /* In-memory list of records */ +typedef struct IncrMerger IncrMerger; /* Read & merge multiple PMAs */ + +/* +** A container for a temp file handle and the current amount of data +** stored in the file. +*/ +struct SorterFile { + sqlite3_file *pFd; /* File handle */ + i64 iEof; /* Bytes of data stored in pFd */ +}; + +/* +** An in-memory list of objects to be sorted. ** -** As keys are added to the sorter, they are written to disk in a series -** of sorted packed-memory-arrays (PMAs). The size of each PMA is roughly -** the same as the cache-size allowed for temporary databases. In order -** to allow the caller to extract keys from the sorter in sorted order, -** all PMAs currently stored on disk must be merged together. This comment -** describes the data structure used to do so. The structure supports -** merging any number of arrays in a single pass with no redundant comparison -** operations. +** If aMemory==0 then each object is allocated separately and the objects +** are connected using SorterRecord.u.pNext. If aMemory!=0 then all objects +** are stored in the aMemory[] bulk memory, one right after the other, and +** are connected using SorterRecord.u.iNext. +*/ +struct SorterList { + SorterRecord *pList; /* Linked list of records */ + u8 *aMemory; /* If non-NULL, bulk memory to hold pList */ + int szPMA; /* Size of pList as PMA in bytes */ +}; + +/* +** The MergeEngine object is used to combine two or more smaller PMAs into +** one big PMA using a merge operation. Separate PMAs all need to be +** combined into one big PMA in order to be able to step through the sorted +** records in order. ** -** The aIter[] array contains an iterator for each of the PMAs being merged. -** An aIter[] iterator either points to a valid key or else is at EOF. For -** the purposes of the paragraphs below, we assume that the array is actually -** N elements in size, where N is the smallest power of 2 greater to or equal -** to the number of iterators being merged. The extra aIter[] elements are -** treated as if they are empty (always at EOF). +** The aReadr[] array contains a PmaReader object for each of the PMAs being +** merged. An aReadr[] object either points to a valid key or else is at EOF. +** ("EOF" means "End Of File". When aReadr[] is at EOF there is no more data.) +** For the purposes of the paragraphs below, we assume that the array is +** actually N elements in size, where N is the smallest power of 2 greater +** to or equal to the number of PMAs being merged. The extra aReadr[] elements +** are treated as if they are empty (always at EOF). ** ** The aTree[] array is also N elements in size. The value of N is stored in -** the VdbeSorter.nTree variable. +** the MergeEngine.nTree variable. ** ** The final (N/2) elements of aTree[] contain the results of comparing -** pairs of iterator keys together. Element i contains the result of -** comparing aIter[2*i-N] and aIter[2*i-N+1]. Whichever key is smaller, the +** pairs of PMA keys together. Element i contains the result of +** comparing aReadr[2*i-N] and aReadr[2*i-N+1]. Whichever key is smaller, the ** aTree element is set to the index of it. ** ** For the purposes of this comparison, EOF is considered greater than any @@ -74430,34 +81195,34 @@ typedef struct FileWriter FileWriter; ** values), it doesn't matter which index is stored. ** ** The (N/4) elements of aTree[] that precede the final (N/2) described -** above contains the index of the smallest of each block of 4 iterators. -** And so on. So that aTree[1] contains the index of the iterator that +** above contains the index of the smallest of each block of 4 PmaReaders +** And so on. So that aTree[1] contains the index of the PmaReader that ** currently points to the smallest key value. aTree[0] is unused. ** ** Example: ** -** aIter[0] -> Banana -** aIter[1] -> Feijoa -** aIter[2] -> Elderberry -** aIter[3] -> Currant -** aIter[4] -> Grapefruit -** aIter[5] -> Apple -** aIter[6] -> Durian -** aIter[7] -> EOF +** aReadr[0] -> Banana +** aReadr[1] -> Feijoa +** aReadr[2] -> Elderberry +** aReadr[3] -> Currant +** aReadr[4] -> Grapefruit +** aReadr[5] -> Apple +** aReadr[6] -> Durian +** aReadr[7] -> EOF ** ** aTree[] = { X, 5 0, 5 0, 3, 5, 6 } ** ** The current element is "Apple" (the value of the key indicated by -** iterator 5). When the Next() operation is invoked, iterator 5 will +** PmaReader 5). When the Next() operation is invoked, PmaReader 5 will ** be advanced to the next key in its segment. Say the next key is ** "Eggplant": ** -** aIter[5] -> Eggplant +** aReadr[5] -> Eggplant ** -** The contents of aTree[] are updated first by comparing the new iterator -** 5 key to the current key of iterator 4 (still "Grapefruit"). The iterator +** The contents of aTree[] are updated first by comparing the new PmaReader +** 5 key to the current key of PmaReader 4 (still "Grapefruit"). The PmaReader ** 5 value is still smaller, so aTree[6] is set to 5. And so on up the tree. -** The value of iterator 6 - "Durian" - is now smaller than that of iterator +** The value of PmaReader 6 - "Durian" - is now smaller than that of PmaReader ** 5, so aTree[3] is set to 6. Key 0 is smaller than key 6 (Bananafile2. And instead of using a +** background thread to prepare data for the PmaReader, with a single +** threaded IncrMerger the allocate part of pTask->file2 is "refilled" with +** keys from pMerger by the calling thread whenever the PmaReader runs out +** of data. */ -struct VdbeSorterIter { - i64 iReadOff; /* Current read offset */ - i64 iEof; /* 1 byte past EOF for this iterator */ - int nAlloc; /* Bytes of space at aAlloc */ - int nKey; /* Number of bytes in key */ - sqlite3_file *pFile; /* File iterator is reading from */ - u8 *aAlloc; /* Allocated space */ - u8 *aKey; /* Pointer to current key */ - u8 *aBuffer; /* Current read buffer */ - int nBuffer; /* Size of read buffer in bytes */ +struct IncrMerger { + SortSubtask *pTask; /* Task that owns this merger */ + MergeEngine *pMerger; /* Merge engine thread reads data from */ + i64 iStartOff; /* Offset to start writing file at */ + int mxSz; /* Maximum bytes of data to store */ + int bEof; /* Set to true when merge is finished */ + int bUseThread; /* True to use a bg thread for this object */ + SorterFile aFile[2]; /* aFile[0] for reading, [1] for writing */ }; /* -** An instance of this structure is used to organize the stream of records -** being written to files by the merge-sort code into aligned, page-sized -** blocks. Doing all I/O in aligned page-sized blocks helps I/O to go -** faster on many operating systems. +** An instance of this object is used for writing a PMA. +** +** The PMA is written one record at a time. Each record is of an arbitrary +** size. But I/O is more efficient if it occurs in page-sized blocks where +** each block is aligned on a page boundary. This object caches writes to +** the PMA so that aligned, page-size blocks are written. */ -struct FileWriter { +struct PmaWriter { int eFWErr; /* Non-zero if in an error state */ u8 *aBuffer; /* Pointer to write buffer */ int nBuffer; /* Size of write buffer in bytes */ int iBufStart; /* First byte of buffer to write */ int iBufEnd; /* Last byte of buffer to write */ i64 iWriteOff; /* Offset of start of buffer in file */ - sqlite3_file *pFile; /* File to write to */ + sqlite3_file *pFd; /* File handle to write to */ }; /* -** A structure to store a single record. All in-memory records are connected -** together into a linked list headed at VdbeSorter.pRecord using the -** SorterRecord.pNext pointer. +** This object is the header on a single record while that record is being +** held in memory and prior to being written out as part of a PMA. +** +** How the linked list is connected depends on how memory is being managed +** by this module. If using a separate allocation for each in-memory record +** (VdbeSorter.list.aMemory==0), then the list is always connected using the +** SorterRecord.u.pNext pointers. +** +** Or, if using the single large allocation method (VdbeSorter.list.aMemory!=0), +** then while records are being accumulated the list is linked using the +** SorterRecord.u.iNext offset. This is because the aMemory[] array may +** be sqlite3Realloc()ed while records are being accumulated. Once the VM +** has finished passing records to the sorter, or when the in-memory buffer +** is full, the list is sorted. As part of the sorting process, it is +** converted to use the SorterRecord.u.pNext pointers. See function +** vdbeSorterSort() for details. */ struct SorterRecord { - void *pVal; - int nVal; - SorterRecord *pNext; + int nVal; /* Size of the record in bytes */ + union { + SorterRecord *pNext; /* Pointer to next record in list */ + int iNext; /* Offset within aMemory of next record */ + } u; + /* The data for the record immediately follows this header */ }; -/* Minimum allowable value for the VdbeSorter.nWorking variable */ -#define SORTER_MIN_WORKING 10 +/* Return a pointer to the buffer containing the record data for SorterRecord +** object p. Should be used as if: +** +** void *SRVAL(SorterRecord *p) { return (void*)&p[1]; } +*/ +#define SRVAL(p) ((void*)((SorterRecord*)(p) + 1)) -/* Maximum number of segments to merge in a single pass. */ + +/* Maximum number of PMAs that a single MergeEngine can merge */ #define SORTER_MAX_MERGE_COUNT 16 +static int vdbeIncrSwap(IncrMerger*); +static void vdbeIncrFree(IncrMerger *); + /* -** Free all memory belonging to the VdbeSorterIter object passed as the second +** Free all memory belonging to the PmaReader object passed as the ** argument. All structure fields are set to zero before returning. */ -static void vdbeSorterIterZero(sqlite3 *db, VdbeSorterIter *pIter){ - sqlite3DbFree(db, pIter->aAlloc); - sqlite3DbFree(db, pIter->aBuffer); - memset(pIter, 0, sizeof(VdbeSorterIter)); +static void vdbePmaReaderClear(PmaReader *pReadr){ + sqlite3_free(pReadr->aAlloc); + sqlite3_free(pReadr->aBuffer); + if( pReadr->aMap ) sqlite3OsUnfetch(pReadr->pFd, 0, pReadr->aMap); + vdbeIncrFree(pReadr->pIncr); + memset(pReadr, 0, sizeof(PmaReader)); } /* -** Read nByte bytes of data from the stream of data iterated by object p. +** Read the next nByte bytes of data from the PMA p. ** If successful, set *ppOut to point to a buffer containing the data ** and return SQLITE_OK. Otherwise, if an error occurs, return an SQLite ** error code. ** -** The buffer indicated by *ppOut may only be considered valid until the +** The buffer returned in *ppOut is only valid until the ** next call to this function. */ -static int vdbeSorterIterRead( - sqlite3 *db, /* Database handle (for malloc) */ - VdbeSorterIter *p, /* Iterator */ +static int vdbePmaReadBlob( + PmaReader *p, /* PmaReader from which to take the blob */ int nByte, /* Bytes of data to read */ u8 **ppOut /* OUT: Pointer to buffer containing data */ ){ int iBuf; /* Offset within buffer to read from */ int nAvail; /* Bytes of data available in buffer */ + + if( p->aMap ){ + *ppOut = &p->aMap[p->iReadOff]; + p->iReadOff += nByte; + return SQLITE_OK; + } + assert( p->aBuffer ); /* If there is no more data to be read from the buffer, read the next @@ -74576,8 +81494,8 @@ static int vdbeSorterIterRead( } assert( nRead>0 ); - /* Read data from the file. Return early if an error occurs. */ - rc = sqlite3OsRead(p->pFile, p->aBuffer, nRead, p->iReadOff); + /* Readr data from the file. Return early if an error occurs. */ + rc = sqlite3OsRead(p->pFd, p->aBuffer, nRead, p->iReadOff); assert( rc!=SQLITE_IOERR_SHORT_READ ); if( rc!=SQLITE_OK ) return rc; } @@ -74597,11 +81515,13 @@ static int vdbeSorterIterRead( /* Extend the p->aAlloc[] allocation if required. */ if( p->nAllocnAlloc*2; + u8 *aNew; + int nNew = MAX(128, p->nAlloc*2); while( nByte>nNew ) nNew = nNew*2; - p->aAlloc = sqlite3DbReallocOrFree(db, p->aAlloc, nNew); - if( !p->aAlloc ) return SQLITE_NOMEM; + aNew = sqlite3Realloc(p->aAlloc, nNew); + if( !aNew ) return SQLITE_NOMEM; p->nAlloc = nNew; + p->aAlloc = aNew; } /* Copy as much data as is available in the buffer into the start of @@ -74613,13 +81533,13 @@ static int vdbeSorterIterRead( /* The following loop copies up to p->nBuffer bytes per iteration into ** the p->aAlloc[] buffer. */ while( nRem>0 ){ - int rc; /* vdbeSorterIterRead() return code */ + int rc; /* vdbePmaReadBlob() return code */ int nCopy; /* Number of bytes to copy */ u8 *aNext; /* Pointer to buffer to copy data from */ nCopy = nRem; if( nRem>p->nBuffer ) nCopy = p->nBuffer; - rc = vdbeSorterIterRead(db, p, nCopy, &aNext); + rc = vdbePmaReadBlob(p, nCopy, &aNext); if( rc!=SQLITE_OK ) return rc; assert( aNext!=p->aAlloc ); memcpy(&p->aAlloc[nByte - nRem], aNext, nCopy); @@ -74636,235 +81556,445 @@ static int vdbeSorterIterRead( ** Read a varint from the stream of data accessed by p. Set *pnOut to ** the value read. */ -static int vdbeSorterIterVarint(sqlite3 *db, VdbeSorterIter *p, u64 *pnOut){ +static int vdbePmaReadVarint(PmaReader *p, u64 *pnOut){ int iBuf; - iBuf = p->iReadOff % p->nBuffer; - if( iBuf && (p->nBuffer-iBuf)>=9 ){ - p->iReadOff += sqlite3GetVarint(&p->aBuffer[iBuf], pnOut); + if( p->aMap ){ + p->iReadOff += sqlite3GetVarint(&p->aMap[p->iReadOff], pnOut); }else{ - u8 aVarint[16], *a; - int i = 0, rc; - do{ - rc = vdbeSorterIterRead(db, p, 1, &a); - if( rc ) return rc; - aVarint[(i++)&0xf] = a[0]; - }while( (a[0]&0x80)!=0 ); - sqlite3GetVarint(aVarint, pnOut); + iBuf = p->iReadOff % p->nBuffer; + if( iBuf && (p->nBuffer-iBuf)>=9 ){ + p->iReadOff += sqlite3GetVarint(&p->aBuffer[iBuf], pnOut); + }else{ + u8 aVarint[16], *a; + int i = 0, rc; + do{ + rc = vdbePmaReadBlob(p, 1, &a); + if( rc ) return rc; + aVarint[(i++)&0xf] = a[0]; + }while( (a[0]&0x80)!=0 ); + sqlite3GetVarint(aVarint, pnOut); + } } return SQLITE_OK; } - /* -** Advance iterator pIter to the next key in its PMA. Return SQLITE_OK if -** no error occurs, or an SQLite error code if one does. +** Attempt to memory map file pFile. If successful, set *pp to point to the +** new mapping and return SQLITE_OK. If the mapping is not attempted +** (because the file is too large or the VFS layer is configured not to use +** mmap), return SQLITE_OK and set *pp to NULL. +** +** Or, if an error occurs, return an SQLite error code. The final value of +** *pp is undefined in this case. */ -static int vdbeSorterIterNext( - sqlite3 *db, /* Database handle (for sqlite3DbMalloc() ) */ - VdbeSorterIter *pIter /* Iterator to advance */ -){ - int rc; /* Return Code */ - u64 nRec = 0; /* Size of record in bytes */ - - if( pIter->iReadOff>=pIter->iEof ){ - /* This is an EOF condition */ - vdbeSorterIterZero(db, pIter); - return SQLITE_OK; +static int vdbeSorterMapFile(SortSubtask *pTask, SorterFile *pFile, u8 **pp){ + int rc = SQLITE_OK; + if( pFile->iEof<=(i64)(pTask->pSorter->db->nMaxSorterMmap) ){ + sqlite3_file *pFd = pFile->pFd; + if( pFd->pMethods->iVersion>=3 ){ + rc = sqlite3OsFetch(pFd, 0, (int)pFile->iEof, (void**)pp); + testcase( rc!=SQLITE_OK ); + } } - - rc = vdbeSorterIterVarint(db, pIter, &nRec); - if( rc==SQLITE_OK ){ - pIter->nKey = (int)nRec; - rc = vdbeSorterIterRead(db, pIter, (int)nRec, &pIter->aKey); - } - return rc; } /* -** Initialize iterator pIter to scan through the PMA stored in file pFile -** starting at offset iStart and ending at offset iEof-1. This function -** leaves the iterator pointing to the first key in the PMA (or EOF if the -** PMA is empty). +** Attach PmaReader pReadr to file pFile (if it is not already attached to +** that file) and seek it to offset iOff within the file. Return SQLITE_OK +** if successful, or an SQLite error code if an error occurs. */ -static int vdbeSorterIterInit( - sqlite3 *db, /* Database handle */ - const VdbeSorter *pSorter, /* Sorter object */ - i64 iStart, /* Start offset in pFile */ - VdbeSorterIter *pIter, /* Iterator to populate */ - i64 *pnByte /* IN/OUT: Increment this value by PMA size */ +static int vdbePmaReaderSeek( + SortSubtask *pTask, /* Task context */ + PmaReader *pReadr, /* Reader whose cursor is to be moved */ + SorterFile *pFile, /* Sorter file to read from */ + i64 iOff /* Offset in pFile */ ){ int rc = SQLITE_OK; - int nBuf; - nBuf = sqlite3BtreeGetPageSize(db->aDb[0].pBt); + assert( pReadr->pIncr==0 || pReadr->pIncr->bEof==0 ); - assert( pSorter->iWriteOff>iStart ); - assert( pIter->aAlloc==0 ); - assert( pIter->aBuffer==0 ); - pIter->pFile = pSorter->pTemp1; - pIter->iReadOff = iStart; - pIter->nAlloc = 128; - pIter->aAlloc = (u8 *)sqlite3DbMallocRaw(db, pIter->nAlloc); - pIter->nBuffer = nBuf; - pIter->aBuffer = (u8 *)sqlite3DbMallocRaw(db, nBuf); + if( sqlite3FaultSim(201) ) return SQLITE_IOERR_READ; + if( pReadr->aMap ){ + sqlite3OsUnfetch(pReadr->pFd, 0, pReadr->aMap); + pReadr->aMap = 0; + } + pReadr->iReadOff = iOff; + pReadr->iEof = pFile->iEof; + pReadr->pFd = pFile->pFd; - if( !pIter->aBuffer ){ - rc = SQLITE_NOMEM; - }else{ - int iBuf; - - iBuf = iStart % nBuf; - if( iBuf ){ - int nRead = nBuf - iBuf; - if( (iStart + nRead) > pSorter->iWriteOff ){ - nRead = (int)(pSorter->iWriteOff - iStart); + rc = vdbeSorterMapFile(pTask, pFile, &pReadr->aMap); + if( rc==SQLITE_OK && pReadr->aMap==0 ){ + int pgsz = pTask->pSorter->pgsz; + int iBuf = pReadr->iReadOff % pgsz; + if( pReadr->aBuffer==0 ){ + pReadr->aBuffer = (u8*)sqlite3Malloc(pgsz); + if( pReadr->aBuffer==0 ) rc = SQLITE_NOMEM; + pReadr->nBuffer = pgsz; + } + if( rc==SQLITE_OK && iBuf ){ + int nRead = pgsz - iBuf; + if( (pReadr->iReadOff + nRead) > pReadr->iEof ){ + nRead = (int)(pReadr->iEof - pReadr->iReadOff); } rc = sqlite3OsRead( - pSorter->pTemp1, &pIter->aBuffer[iBuf], nRead, iStart + pReadr->pFd, &pReadr->aBuffer[iBuf], nRead, pReadr->iReadOff ); + testcase( rc!=SQLITE_OK ); + } + } + + return rc; +} + +/* +** Advance PmaReader pReadr to the next key in its PMA. Return SQLITE_OK if +** no error occurs, or an SQLite error code if one does. +*/ +static int vdbePmaReaderNext(PmaReader *pReadr){ + int rc = SQLITE_OK; /* Return Code */ + u64 nRec = 0; /* Size of record in bytes */ + + + if( pReadr->iReadOff>=pReadr->iEof ){ + IncrMerger *pIncr = pReadr->pIncr; + int bEof = 1; + if( pIncr ){ + rc = vdbeIncrSwap(pIncr); + if( rc==SQLITE_OK && pIncr->bEof==0 ){ + rc = vdbePmaReaderSeek( + pIncr->pTask, pReadr, &pIncr->aFile[0], pIncr->iStartOff + ); + bEof = 0; + } } - if( rc==SQLITE_OK ){ - u64 nByte; /* Size of PMA in bytes */ - pIter->iEof = pSorter->iWriteOff; - rc = vdbeSorterIterVarint(db, pIter, &nByte); - pIter->iEof = pIter->iReadOff + nByte; - *pnByte += nByte; + if( bEof ){ + /* This is an EOF condition */ + vdbePmaReaderClear(pReadr); + testcase( rc!=SQLITE_OK ); + return rc; } } if( rc==SQLITE_OK ){ - rc = vdbeSorterIterNext(db, pIter); + rc = vdbePmaReadVarint(pReadr, &nRec); + } + if( rc==SQLITE_OK ){ + pReadr->nKey = (int)nRec; + rc = vdbePmaReadBlob(pReadr, (int)nRec, &pReadr->aKey); + testcase( rc!=SQLITE_OK ); + } + + return rc; +} + +/* +** Initialize PmaReader pReadr to scan through the PMA stored in file pFile +** starting at offset iStart and ending at offset iEof-1. This function +** leaves the PmaReader pointing to the first key in the PMA (or EOF if the +** PMA is empty). +** +** If the pnByte parameter is NULL, then it is assumed that the file +** contains a single PMA, and that that PMA omits the initial length varint. +*/ +static int vdbePmaReaderInit( + SortSubtask *pTask, /* Task context */ + SorterFile *pFile, /* Sorter file to read from */ + i64 iStart, /* Start offset in pFile */ + PmaReader *pReadr, /* PmaReader to populate */ + i64 *pnByte /* IN/OUT: Increment this value by PMA size */ +){ + int rc; + + assert( pFile->iEof>iStart ); + assert( pReadr->aAlloc==0 && pReadr->nAlloc==0 ); + assert( pReadr->aBuffer==0 ); + assert( pReadr->aMap==0 ); + + rc = vdbePmaReaderSeek(pTask, pReadr, pFile, iStart); + if( rc==SQLITE_OK ){ + u64 nByte; /* Size of PMA in bytes */ + rc = vdbePmaReadVarint(pReadr, &nByte); + pReadr->iEof = pReadr->iReadOff + nByte; + *pnByte += nByte; + } + + if( rc==SQLITE_OK ){ + rc = vdbePmaReaderNext(pReadr); } return rc; } +/* +** A version of vdbeSorterCompare() that assumes that it has already been +** determined that the first field of key1 is equal to the first field of +** key2. +*/ +static int vdbeSorterCompareTail( + SortSubtask *pTask, /* Subtask context (for pKeyInfo) */ + int *pbKey2Cached, /* True if pTask->pUnpacked is pKey2 */ + const void *pKey1, int nKey1, /* Left side of comparison */ + const void *pKey2, int nKey2 /* Right side of comparison */ +){ + UnpackedRecord *r2 = pTask->pUnpacked; + if( *pbKey2Cached==0 ){ + sqlite3VdbeRecordUnpack(pTask->pSorter->pKeyInfo, nKey2, pKey2, r2); + *pbKey2Cached = 1; + } + return sqlite3VdbeRecordCompareWithSkip(nKey1, pKey1, r2, 1); +} /* ** Compare key1 (buffer pKey1, size nKey1 bytes) with key2 (buffer pKey2, -** size nKey2 bytes). Argument pKeyInfo supplies the collation functions -** used by the comparison. If an error occurs, return an SQLite error code. -** Otherwise, return SQLITE_OK and set *pRes to a negative, zero or positive -** value, depending on whether key1 is smaller, equal to or larger than key2. +** size nKey2 bytes). Use (pTask->pKeyInfo) for the collation sequences +** used by the comparison. Return the result of the comparison. ** -** If the bOmitRowid argument is non-zero, assume both keys end in a rowid -** field. For the purposes of the comparison, ignore it. Also, if bOmitRowid -** is true and key1 contains even a single NULL value, it is considered to -** be less than key2. Even if key2 also contains NULL values. +** If IN/OUT parameter *pbKey2Cached is true when this function is called, +** it is assumed that (pTask->pUnpacked) contains the unpacked version +** of key2. If it is false, (pTask->pUnpacked) is populated with the unpacked +** version of key2 and *pbKey2Cached set to true before returning. ** -** If pKey2 is passed a NULL pointer, then it is assumed that the pCsr->aSpace -** has been allocated and contains an unpacked record that is used as key2. +** If an OOM error is encountered, (pTask->pUnpacked->error_rc) is set +** to SQLITE_NOMEM. */ -static void vdbeSorterCompare( - const VdbeCursor *pCsr, /* Cursor object (for pKeyInfo) */ - int nIgnore, /* Ignore the last nIgnore fields */ +static int vdbeSorterCompare( + SortSubtask *pTask, /* Subtask context (for pKeyInfo) */ + int *pbKey2Cached, /* True if pTask->pUnpacked is pKey2 */ const void *pKey1, int nKey1, /* Left side of comparison */ - const void *pKey2, int nKey2, /* Right side of comparison */ - int *pRes /* OUT: Result of comparison */ + const void *pKey2, int nKey2 /* Right side of comparison */ ){ - KeyInfo *pKeyInfo = pCsr->pKeyInfo; - VdbeSorter *pSorter = pCsr->pSorter; - UnpackedRecord *r2 = pSorter->pUnpacked; - int i; - - if( pKey2 ){ - sqlite3VdbeRecordUnpack(pKeyInfo, nKey2, pKey2, r2); + UnpackedRecord *r2 = pTask->pUnpacked; + if( !*pbKey2Cached ){ + sqlite3VdbeRecordUnpack(pTask->pSorter->pKeyInfo, nKey2, pKey2, r2); + *pbKey2Cached = 1; } - - if( nIgnore ){ - r2->nField = pKeyInfo->nField - nIgnore; - assert( r2->nField>0 ); - for(i=0; inField; i++){ - if( r2->aMem[i].flags & MEM_Null ){ - *pRes = -1; - return; - } - } - assert( r2->default_rc==0 ); - } - - *pRes = sqlite3VdbeRecordCompare(nKey1, pKey1, r2, 0); + return sqlite3VdbeRecordCompare(nKey1, pKey1, r2); } /* -** This function is called to compare two iterator keys when merging -** multiple b-tree segments. Parameter iOut is the index of the aTree[] -** value to recalculate. +** A specially optimized version of vdbeSorterCompare() that assumes that +** the first field of each key is a TEXT value and that the collation +** sequence to compare them with is BINARY. */ -static int vdbeSorterDoCompare(const VdbeCursor *pCsr, int iOut){ - VdbeSorter *pSorter = pCsr->pSorter; - int i1; - int i2; - int iRes; - VdbeSorterIter *p1; - VdbeSorterIter *p2; +static int vdbeSorterCompareText( + SortSubtask *pTask, /* Subtask context (for pKeyInfo) */ + int *pbKey2Cached, /* True if pTask->pUnpacked is pKey2 */ + const void *pKey1, int nKey1, /* Left side of comparison */ + const void *pKey2, int nKey2 /* Right side of comparison */ +){ + const u8 * const p1 = (const u8 * const)pKey1; + const u8 * const p2 = (const u8 * const)pKey2; + const u8 * const v1 = &p1[ p1[0] ]; /* Pointer to value 1 */ + const u8 * const v2 = &p2[ p2[0] ]; /* Pointer to value 2 */ - assert( iOutnTree && iOut>0 ); + int n1; + int n2; + int res; - if( iOut>=(pSorter->nTree/2) ){ - i1 = (iOut - pSorter->nTree/2) * 2; - i2 = i1 + 1; - }else{ - i1 = pSorter->aTree[iOut*2]; - i2 = pSorter->aTree[iOut*2+1]; + getVarint32(&p1[1], n1); n1 = (n1 - 13) / 2; + getVarint32(&p2[1], n2); n2 = (n2 - 13) / 2; + res = memcmp(v1, v2, MIN(n1, n2)); + if( res==0 ){ + res = n1 - n2; } - p1 = &pSorter->aIter[i1]; - p2 = &pSorter->aIter[i2]; - - if( p1->pFile==0 ){ - iRes = i2; - }else if( p2->pFile==0 ){ - iRes = i1; + if( res==0 ){ + if( pTask->pSorter->pKeyInfo->nField>1 ){ + res = vdbeSorterCompareTail( + pTask, pbKey2Cached, pKey1, nKey1, pKey2, nKey2 + ); + } }else{ - int res; - assert( pCsr->pSorter->pUnpacked!=0 ); /* allocated in vdbeSorterMerge() */ - vdbeSorterCompare( - pCsr, 0, p1->aKey, p1->nKey, p2->aKey, p2->nKey, &res - ); - if( res<=0 ){ - iRes = i1; - }else{ - iRes = i2; + if( pTask->pSorter->pKeyInfo->aSortOrder[0] ){ + res = res * -1; } } - pSorter->aTree[iOut] = iRes; - return SQLITE_OK; + return res; +} + +/* +** A specially optimized version of vdbeSorterCompare() that assumes that +** the first field of each key is an INTEGER value. +*/ +static int vdbeSorterCompareInt( + SortSubtask *pTask, /* Subtask context (for pKeyInfo) */ + int *pbKey2Cached, /* True if pTask->pUnpacked is pKey2 */ + const void *pKey1, int nKey1, /* Left side of comparison */ + const void *pKey2, int nKey2 /* Right side of comparison */ +){ + const u8 * const p1 = (const u8 * const)pKey1; + const u8 * const p2 = (const u8 * const)pKey2; + const int s1 = p1[1]; /* Left hand serial type */ + const int s2 = p2[1]; /* Right hand serial type */ + const u8 * const v1 = &p1[ p1[0] ]; /* Pointer to value 1 */ + const u8 * const v2 = &p2[ p2[0] ]; /* Pointer to value 2 */ + int res; /* Return value */ + + assert( (s1>0 && s1<7) || s1==8 || s1==9 ); + assert( (s2>0 && s2<7) || s2==8 || s2==9 ); + + if( s1>7 && s2>7 ){ + res = s1 - s2; + }else{ + if( s1==s2 ){ + if( (*v1 ^ *v2) & 0x80 ){ + /* The two values have different signs */ + res = (*v1 & 0x80) ? -1 : +1; + }else{ + /* The two values have the same sign. Compare using memcmp(). */ + static const u8 aLen[] = {0, 1, 2, 3, 4, 6, 8 }; + int i; + res = 0; + for(i=0; i7 ){ + res = +1; + }else if( s1>7 ){ + res = -1; + }else{ + res = s1 - s2; + } + assert( res!=0 ); + + if( res>0 ){ + if( *v1 & 0x80 ) res = -1; + }else{ + if( *v2 & 0x80 ) res = +1; + } + } + } + + if( res==0 ){ + if( pTask->pSorter->pKeyInfo->nField>1 ){ + res = vdbeSorterCompareTail( + pTask, pbKey2Cached, pKey1, nKey1, pKey2, nKey2 + ); + } + }else if( pTask->pSorter->pKeyInfo->aSortOrder[0] ){ + res = res * -1; + } + + return res; } /* ** Initialize the temporary index cursor just opened as a sorter cursor. +** +** Usually, the sorter module uses the value of (pCsr->pKeyInfo->nField) +** to determine the number of fields that should be compared from the +** records being sorted. However, if the value passed as argument nField +** is non-zero and the sorter is able to guarantee a stable sort, nField +** is used instead. This is used when sorting records for a CREATE INDEX +** statement. In this case, keys are always delivered to the sorter in +** order of the primary key, which happens to be make up the final part +** of the records being sorted. So if the sort is stable, there is never +** any reason to compare PK fields and they can be ignored for a small +** performance boost. +** +** The sorter can guarantee a stable sort when running in single-threaded +** mode, but not in multi-threaded mode. +** +** SQLITE_OK is returned if successful, or an SQLite error code otherwise. */ -SQLITE_PRIVATE int sqlite3VdbeSorterInit(sqlite3 *db, VdbeCursor *pCsr){ +SQLITE_PRIVATE int sqlite3VdbeSorterInit( + sqlite3 *db, /* Database connection (for malloc()) */ + int nField, /* Number of key fields in each record */ + VdbeCursor *pCsr /* Cursor that holds the new sorter */ +){ int pgsz; /* Page size of main database */ + int i; /* Used to iterate through aTask[] */ int mxCache; /* Cache size */ VdbeSorter *pSorter; /* The new sorter */ - char *d; /* Dummy */ + KeyInfo *pKeyInfo; /* Copy of pCsr->pKeyInfo with db==0 */ + int szKeyInfo; /* Size of pCsr->pKeyInfo in bytes */ + int sz; /* Size of pSorter in bytes */ + int rc = SQLITE_OK; +#if SQLITE_MAX_WORKER_THREADS==0 +# define nWorker 0 +#else + int nWorker; +#endif + + /* Initialize the upper limit on the number of worker threads */ +#if SQLITE_MAX_WORKER_THREADS>0 + if( sqlite3TempInMemory(db) || sqlite3GlobalConfig.bCoreMutex==0 ){ + nWorker = 0; + }else{ + nWorker = db->aLimit[SQLITE_LIMIT_WORKER_THREADS]; + } +#endif + + /* Do not allow the total number of threads (main thread + all workers) + ** to exceed the maximum merge count */ +#if SQLITE_MAX_WORKER_THREADS>=SORTER_MAX_MERGE_COUNT + if( nWorker>=SORTER_MAX_MERGE_COUNT ){ + nWorker = SORTER_MAX_MERGE_COUNT-1; + } +#endif assert( pCsr->pKeyInfo && pCsr->pBt==0 ); - pCsr->pSorter = pSorter = sqlite3DbMallocZero(db, sizeof(VdbeSorter)); + assert( pCsr->eCurType==CURTYPE_SORTER ); + szKeyInfo = sizeof(KeyInfo) + (pCsr->pKeyInfo->nField-1)*sizeof(CollSeq*); + sz = sizeof(VdbeSorter) + nWorker * sizeof(SortSubtask); + + pSorter = (VdbeSorter*)sqlite3DbMallocZero(db, sz + szKeyInfo); + pCsr->uc.pSorter = pSorter; if( pSorter==0 ){ - return SQLITE_NOMEM; - } - - pSorter->pUnpacked = sqlite3VdbeAllocUnpackedRecord(pCsr->pKeyInfo, 0, 0, &d); - if( pSorter->pUnpacked==0 ) return SQLITE_NOMEM; - assert( pSorter->pUnpacked==(UnpackedRecord *)d ); + rc = SQLITE_NOMEM; + }else{ + pSorter->pKeyInfo = pKeyInfo = (KeyInfo*)((u8*)pSorter + sz); + memcpy(pKeyInfo, pCsr->pKeyInfo, szKeyInfo); + pKeyInfo->db = 0; + if( nField && nWorker==0 ){ + pKeyInfo->nXField += (pKeyInfo->nField - nField); + pKeyInfo->nField = nField; + } + pSorter->pgsz = pgsz = sqlite3BtreeGetPageSize(db->aDb[0].pBt); + pSorter->nTask = nWorker + 1; + pSorter->iPrev = (u8)(nWorker - 1); + pSorter->bUseThreads = (pSorter->nTask>1); + pSorter->db = db; + for(i=0; inTask; i++){ + SortSubtask *pTask = &pSorter->aTask[i]; + pTask->pSorter = pSorter; + } - if( !sqlite3TempInMemory(db) ){ - pgsz = sqlite3BtreeGetPageSize(db->aDb[0].pBt); - pSorter->mnPmaSize = SORTER_MIN_WORKING * pgsz; - mxCache = db->aDb[0].pSchema->cache_size; - if( mxCachemxPmaSize = mxCache * pgsz; + if( !sqlite3TempInMemory(db) ){ + u32 szPma = sqlite3GlobalConfig.szPma; + pSorter->mnPmaSize = szPma * pgsz; + mxCache = db->aDb[0].pSchema->cache_size; + if( mxCache<(int)szPma ) mxCache = (int)szPma; + pSorter->mxPmaSize = MIN((i64)mxCache*pgsz, SQLITE_MAX_PMASZ); + + /* EVIDENCE-OF: R-26747-61719 When the application provides any amount of + ** scratch memory using SQLITE_CONFIG_SCRATCH, SQLite avoids unnecessary + ** large heap allocations. + */ + if( sqlite3GlobalConfig.pScratch==0 ){ + assert( pSorter->iMemory==0 ); + pSorter->nMemory = pgsz; + pSorter->list.aMemory = (u8*)sqlite3Malloc(pgsz); + if( !pSorter->list.aMemory ) rc = SQLITE_NOMEM; + } + } + + if( (pKeyInfo->nField+pKeyInfo->nXField)<13 + && (pKeyInfo->aColl[0]==0 || pKeyInfo->aColl[0]==db->pDfltColl) + ){ + pSorter->typeMask = SORTER_TYPE_INTEGER | SORTER_TYPE_TEXT; + } } - return SQLITE_OK; + return rc; } +#undef nWorker /* Defined at the top of this function */ /* ** Free the list of sorted records starting at pRecord. @@ -74873,93 +82003,343 @@ static void vdbeSorterRecordFree(sqlite3 *db, SorterRecord *pRecord){ SorterRecord *p; SorterRecord *pNext; for(p=pRecord; p; p=pNext){ - pNext = p->pNext; + pNext = p->u.pNext; sqlite3DbFree(db, p); } } +/* +** Free all resources owned by the object indicated by argument pTask. All +** fields of *pTask are zeroed before returning. +*/ +static void vdbeSortSubtaskCleanup(sqlite3 *db, SortSubtask *pTask){ + sqlite3DbFree(db, pTask->pUnpacked); +#if SQLITE_MAX_WORKER_THREADS>0 + /* pTask->list.aMemory can only be non-zero if it was handed memory + ** from the main thread. That only occurs SQLITE_MAX_WORKER_THREADS>0 */ + if( pTask->list.aMemory ){ + sqlite3_free(pTask->list.aMemory); + }else +#endif + { + assert( pTask->list.aMemory==0 ); + vdbeSorterRecordFree(0, pTask->list.pList); + } + if( pTask->file.pFd ){ + sqlite3OsCloseFree(pTask->file.pFd); + } + if( pTask->file2.pFd ){ + sqlite3OsCloseFree(pTask->file2.pFd); + } + memset(pTask, 0, sizeof(SortSubtask)); +} + +#ifdef SQLITE_DEBUG_SORTER_THREADS +static void vdbeSorterWorkDebug(SortSubtask *pTask, const char *zEvent){ + i64 t; + int iTask = (pTask - pTask->pSorter->aTask); + sqlite3OsCurrentTimeInt64(pTask->pSorter->db->pVfs, &t); + fprintf(stderr, "%lld:%d %s\n", t, iTask, zEvent); +} +static void vdbeSorterRewindDebug(const char *zEvent){ + i64 t; + sqlite3OsCurrentTimeInt64(sqlite3_vfs_find(0), &t); + fprintf(stderr, "%lld:X %s\n", t, zEvent); +} +static void vdbeSorterPopulateDebug( + SortSubtask *pTask, + const char *zEvent +){ + i64 t; + int iTask = (pTask - pTask->pSorter->aTask); + sqlite3OsCurrentTimeInt64(pTask->pSorter->db->pVfs, &t); + fprintf(stderr, "%lld:bg%d %s\n", t, iTask, zEvent); +} +static void vdbeSorterBlockDebug( + SortSubtask *pTask, + int bBlocked, + const char *zEvent +){ + if( bBlocked ){ + i64 t; + sqlite3OsCurrentTimeInt64(pTask->pSorter->db->pVfs, &t); + fprintf(stderr, "%lld:main %s\n", t, zEvent); + } +} +#else +# define vdbeSorterWorkDebug(x,y) +# define vdbeSorterRewindDebug(y) +# define vdbeSorterPopulateDebug(x,y) +# define vdbeSorterBlockDebug(x,y,z) +#endif + +#if SQLITE_MAX_WORKER_THREADS>0 +/* +** Join thread pTask->thread. +*/ +static int vdbeSorterJoinThread(SortSubtask *pTask){ + int rc = SQLITE_OK; + if( pTask->pThread ){ +#ifdef SQLITE_DEBUG_SORTER_THREADS + int bDone = pTask->bDone; +#endif + void *pRet = SQLITE_INT_TO_PTR(SQLITE_ERROR); + vdbeSorterBlockDebug(pTask, !bDone, "enter"); + (void)sqlite3ThreadJoin(pTask->pThread, &pRet); + vdbeSorterBlockDebug(pTask, !bDone, "exit"); + rc = SQLITE_PTR_TO_INT(pRet); + assert( pTask->bDone==1 ); + pTask->bDone = 0; + pTask->pThread = 0; + } + return rc; +} + +/* +** Launch a background thread to run xTask(pIn). +*/ +static int vdbeSorterCreateThread( + SortSubtask *pTask, /* Thread will use this task object */ + void *(*xTask)(void*), /* Routine to run in a separate thread */ + void *pIn /* Argument passed into xTask() */ +){ + assert( pTask->pThread==0 && pTask->bDone==0 ); + return sqlite3ThreadCreate(&pTask->pThread, xTask, pIn); +} + +/* +** Join all outstanding threads launched by SorterWrite() to create +** level-0 PMAs. +*/ +static int vdbeSorterJoinAll(VdbeSorter *pSorter, int rcin){ + int rc = rcin; + int i; + + /* This function is always called by the main user thread. + ** + ** If this function is being called after SorterRewind() has been called, + ** it is possible that thread pSorter->aTask[pSorter->nTask-1].pThread + ** is currently attempt to join one of the other threads. To avoid a race + ** condition where this thread also attempts to join the same object, join + ** thread pSorter->aTask[pSorter->nTask-1].pThread first. */ + for(i=pSorter->nTask-1; i>=0; i--){ + SortSubtask *pTask = &pSorter->aTask[i]; + int rc2 = vdbeSorterJoinThread(pTask); + if( rc==SQLITE_OK ) rc = rc2; + } + return rc; +} +#else +# define vdbeSorterJoinAll(x,rcin) (rcin) +# define vdbeSorterJoinThread(pTask) SQLITE_OK +#endif + +/* +** Allocate a new MergeEngine object capable of handling up to +** nReader PmaReader inputs. +** +** nReader is automatically rounded up to the next power of two. +** nReader may not exceed SORTER_MAX_MERGE_COUNT even after rounding up. +*/ +static MergeEngine *vdbeMergeEngineNew(int nReader){ + int N = 2; /* Smallest power of two >= nReader */ + int nByte; /* Total bytes of space to allocate */ + MergeEngine *pNew; /* Pointer to allocated object to return */ + + assert( nReader<=SORTER_MAX_MERGE_COUNT ); + + while( NnTree = N; + pNew->pTask = 0; + pNew->aReadr = (PmaReader*)&pNew[1]; + pNew->aTree = (int*)&pNew->aReadr[N]; + } + return pNew; +} + +/* +** Free the MergeEngine object passed as the only argument. +*/ +static void vdbeMergeEngineFree(MergeEngine *pMerger){ + int i; + if( pMerger ){ + for(i=0; inTree; i++){ + vdbePmaReaderClear(&pMerger->aReadr[i]); + } + } + sqlite3_free(pMerger); +} + +/* +** Free all resources associated with the IncrMerger object indicated by +** the first argument. +*/ +static void vdbeIncrFree(IncrMerger *pIncr){ + if( pIncr ){ +#if SQLITE_MAX_WORKER_THREADS>0 + if( pIncr->bUseThread ){ + vdbeSorterJoinThread(pIncr->pTask); + if( pIncr->aFile[0].pFd ) sqlite3OsCloseFree(pIncr->aFile[0].pFd); + if( pIncr->aFile[1].pFd ) sqlite3OsCloseFree(pIncr->aFile[1].pFd); + } +#endif + vdbeMergeEngineFree(pIncr->pMerger); + sqlite3_free(pIncr); + } +} + /* ** Reset a sorting cursor back to its original empty state. */ SQLITE_PRIVATE void sqlite3VdbeSorterReset(sqlite3 *db, VdbeSorter *pSorter){ - if( pSorter->aIter ){ - int i; - for(i=0; inTree; i++){ - vdbeSorterIterZero(db, &pSorter->aIter[i]); - } - sqlite3DbFree(db, pSorter->aIter); - pSorter->aIter = 0; + int i; + (void)vdbeSorterJoinAll(pSorter, SQLITE_OK); + assert( pSorter->bUseThreads || pSorter->pReader==0 ); +#if SQLITE_MAX_WORKER_THREADS>0 + if( pSorter->pReader ){ + vdbePmaReaderClear(pSorter->pReader); + sqlite3DbFree(db, pSorter->pReader); + pSorter->pReader = 0; } - if( pSorter->pTemp1 ){ - sqlite3OsCloseFree(pSorter->pTemp1); - pSorter->pTemp1 = 0; +#endif + vdbeMergeEngineFree(pSorter->pMerger); + pSorter->pMerger = 0; + for(i=0; inTask; i++){ + SortSubtask *pTask = &pSorter->aTask[i]; + vdbeSortSubtaskCleanup(db, pTask); + pTask->pSorter = pSorter; } - vdbeSorterRecordFree(db, pSorter->pRecord); - pSorter->pRecord = 0; - pSorter->iWriteOff = 0; - pSorter->iReadOff = 0; - pSorter->nInMemory = 0; - pSorter->nTree = 0; - pSorter->nPMA = 0; - pSorter->aTree = 0; + if( pSorter->list.aMemory==0 ){ + vdbeSorterRecordFree(0, pSorter->list.pList); + } + pSorter->list.pList = 0; + pSorter->list.szPMA = 0; + pSorter->bUsePMA = 0; + pSorter->iMemory = 0; + pSorter->mxKeysize = 0; + sqlite3DbFree(db, pSorter->pUnpacked); + pSorter->pUnpacked = 0; } - /* ** Free any cursor components allocated by sqlite3VdbeSorterXXX routines. */ SQLITE_PRIVATE void sqlite3VdbeSorterClose(sqlite3 *db, VdbeCursor *pCsr){ - VdbeSorter *pSorter = pCsr->pSorter; + VdbeSorter *pSorter; + assert( pCsr->eCurType==CURTYPE_SORTER ); + pSorter = pCsr->uc.pSorter; if( pSorter ){ sqlite3VdbeSorterReset(db, pSorter); - sqlite3DbFree(db, pSorter->pUnpacked); + sqlite3_free(pSorter->list.aMemory); sqlite3DbFree(db, pSorter); - pCsr->pSorter = 0; + pCsr->uc.pSorter = 0; } } +#if SQLITE_MAX_MMAP_SIZE>0 +/* +** The first argument is a file-handle open on a temporary file. The file +** is guaranteed to be nByte bytes or smaller in size. This function +** attempts to extend the file to nByte bytes in size and to ensure that +** the VFS has memory mapped it. +** +** Whether or not the file does end up memory mapped of course depends on +** the specific VFS implementation. +*/ +static void vdbeSorterExtendFile(sqlite3 *db, sqlite3_file *pFd, i64 nByte){ + if( nByte<=(i64)(db->nMaxSorterMmap) && pFd->pMethods->iVersion>=3 ){ + void *p = 0; + int chunksize = 4*1024; + sqlite3OsFileControlHint(pFd, SQLITE_FCNTL_CHUNK_SIZE, &chunksize); + sqlite3OsFileControlHint(pFd, SQLITE_FCNTL_SIZE_HINT, &nByte); + sqlite3OsFetch(pFd, 0, (int)nByte, &p); + sqlite3OsUnfetch(pFd, 0, p); + } +} +#else +# define vdbeSorterExtendFile(x,y,z) +#endif + /* ** Allocate space for a file-handle and open a temporary file. If successful, -** set *ppFile to point to the malloc'd file-handle and return SQLITE_OK. -** Otherwise, set *ppFile to 0 and return an SQLite error code. +** set *ppFd to point to the malloc'd file-handle and return SQLITE_OK. +** Otherwise, set *ppFd to 0 and return an SQLite error code. */ -static int vdbeSorterOpenTempFile(sqlite3 *db, sqlite3_file **ppFile){ - int dummy; - return sqlite3OsOpenMalloc(db->pVfs, 0, ppFile, +static int vdbeSorterOpenTempFile( + sqlite3 *db, /* Database handle doing sort */ + i64 nExtend, /* Attempt to extend file to this size */ + sqlite3_file **ppFd +){ + int rc; + if( sqlite3FaultSim(202) ) return SQLITE_IOERR_ACCESS; + rc = sqlite3OsOpenMalloc(db->pVfs, 0, ppFd, SQLITE_OPEN_TEMP_JOURNAL | SQLITE_OPEN_READWRITE | SQLITE_OPEN_CREATE | - SQLITE_OPEN_EXCLUSIVE | SQLITE_OPEN_DELETEONCLOSE, &dummy + SQLITE_OPEN_EXCLUSIVE | SQLITE_OPEN_DELETEONCLOSE, &rc ); + if( rc==SQLITE_OK ){ + i64 max = SQLITE_MAX_MMAP_SIZE; + sqlite3OsFileControlHint(*ppFd, SQLITE_FCNTL_MMAP_SIZE, (void*)&max); + if( nExtend>0 ){ + vdbeSorterExtendFile(db, *ppFd, nExtend); + } + } + return rc; } +/* +** If it has not already been allocated, allocate the UnpackedRecord +** structure at pTask->pUnpacked. Return SQLITE_OK if successful (or +** if no allocation was required), or SQLITE_NOMEM otherwise. +*/ +static int vdbeSortAllocUnpacked(SortSubtask *pTask){ + if( pTask->pUnpacked==0 ){ + char *pFree; + pTask->pUnpacked = sqlite3VdbeAllocUnpackedRecord( + pTask->pSorter->pKeyInfo, 0, 0, &pFree + ); + assert( pTask->pUnpacked==(UnpackedRecord*)pFree ); + if( pFree==0 ) return SQLITE_NOMEM; + pTask->pUnpacked->nField = pTask->pSorter->pKeyInfo->nField; + pTask->pUnpacked->errCode = 0; + } + return SQLITE_OK; +} + + /* ** Merge the two sorted lists p1 and p2 into a single list. ** Set *ppOut to the head of the new list. */ static void vdbeSorterMerge( - const VdbeCursor *pCsr, /* For pKeyInfo */ + SortSubtask *pTask, /* Calling thread context */ SorterRecord *p1, /* First list to merge */ SorterRecord *p2, /* Second list to merge */ SorterRecord **ppOut /* OUT: Head of merged list */ ){ SorterRecord *pFinal = 0; SorterRecord **pp = &pFinal; - void *pVal2 = p2 ? p2->pVal : 0; + int bCached = 0; while( p1 && p2 ){ int res; - vdbeSorterCompare(pCsr, 0, p1->pVal, p1->nVal, pVal2, p2->nVal, &res); + res = pTask->xCompare( + pTask, &bCached, SRVAL(p1), p1->nVal, SRVAL(p2), p2->nVal + ); + if( res<=0 ){ *pp = p1; - pp = &p1->pNext; - p1 = p1->pNext; - pVal2 = 0; + pp = &p1->u.pNext; + p1 = p1->u.pNext; }else{ *pp = p2; - pp = &p2->pNext; - p2 = p2->pNext; - if( p2==0 ) break; - pVal2 = p2->pVal; + pp = &p2->u.pNext; + p2 = p2->u.pNext; + bCached = 0; } } *pp = p1 ? p1 : p2; @@ -74967,27 +82347,56 @@ static void vdbeSorterMerge( } /* -** Sort the linked list of records headed at pCsr->pRecord. Return SQLITE_OK -** if successful, or an SQLite error code (i.e. SQLITE_NOMEM) if an error -** occurs. +** Return the SorterCompare function to compare values collected by the +** sorter object passed as the only argument. */ -static int vdbeSorterSort(const VdbeCursor *pCsr){ +static SorterCompare vdbeSorterGetCompare(VdbeSorter *p){ + if( p->typeMask==SORTER_TYPE_INTEGER ){ + return vdbeSorterCompareInt; + }else if( p->typeMask==SORTER_TYPE_TEXT ){ + return vdbeSorterCompareText; + } + return vdbeSorterCompare; +} + +/* +** Sort the linked list of records headed at pTask->pList. Return +** SQLITE_OK if successful, or an SQLite error code (i.e. SQLITE_NOMEM) if +** an error occurs. +*/ +static int vdbeSorterSort(SortSubtask *pTask, SorterList *pList){ int i; SorterRecord **aSlot; SorterRecord *p; - VdbeSorter *pSorter = pCsr->pSorter; + int rc; + + rc = vdbeSortAllocUnpacked(pTask); + if( rc!=SQLITE_OK ) return rc; + + p = pList->pList; + pTask->xCompare = vdbeSorterGetCompare(pTask->pSorter); aSlot = (SorterRecord **)sqlite3MallocZero(64 * sizeof(SorterRecord *)); if( !aSlot ){ return SQLITE_NOMEM; } - p = pSorter->pRecord; while( p ){ - SorterRecord *pNext = p->pNext; - p->pNext = 0; + SorterRecord *pNext; + if( pList->aMemory ){ + if( (u8*)p==pList->aMemory ){ + pNext = 0; + }else{ + assert( p->u.iNextaMemory) ); + pNext = (SorterRecord*)&pList->aMemory[p->u.iNext]; + } + }else{ + pNext = p->u.pNext; + } + + p->u.pNext = 0; for(i=0; aSlot[i]; i++){ - vdbeSorterMerge(pCsr, p, aSlot[i], &p); + vdbeSorterMerge(pTask, p, aSlot[i], &p); aSlot[i] = 0; } aSlot[i] = p; @@ -74996,42 +82405,43 @@ static int vdbeSorterSort(const VdbeCursor *pCsr){ p = 0; for(i=0; i<64; i++){ - vdbeSorterMerge(pCsr, p, aSlot[i], &p); + vdbeSorterMerge(pTask, p, aSlot[i], &p); } - pSorter->pRecord = p; + pList->pList = p; sqlite3_free(aSlot); - return SQLITE_OK; + assert( pTask->pUnpacked->errCode==SQLITE_OK + || pTask->pUnpacked->errCode==SQLITE_NOMEM + ); + return pTask->pUnpacked->errCode; } /* -** Initialize a file-writer object. +** Initialize a PMA-writer object. */ -static void fileWriterInit( - sqlite3 *db, /* Database (for malloc) */ - sqlite3_file *pFile, /* File to write to */ - FileWriter *p, /* Object to populate */ - i64 iStart /* Offset of pFile to begin writing at */ +static void vdbePmaWriterInit( + sqlite3_file *pFd, /* File handle to write to */ + PmaWriter *p, /* Object to populate */ + int nBuf, /* Buffer size */ + i64 iStart /* Offset of pFd to begin writing at */ ){ - int nBuf = sqlite3BtreeGetPageSize(db->aDb[0].pBt); - - memset(p, 0, sizeof(FileWriter)); - p->aBuffer = (u8 *)sqlite3DbMallocRaw(db, nBuf); + memset(p, 0, sizeof(PmaWriter)); + p->aBuffer = (u8*)sqlite3Malloc(nBuf); if( !p->aBuffer ){ p->eFWErr = SQLITE_NOMEM; }else{ p->iBufEnd = p->iBufStart = (iStart % nBuf); p->iWriteOff = iStart - p->iBufStart; p->nBuffer = nBuf; - p->pFile = pFile; + p->pFd = pFd; } } /* -** Write nData bytes of data to the file-write object. Return SQLITE_OK +** Write nData bytes of data to the PMA. Return SQLITE_OK ** if successful, or an SQLite error code if an error occurs. */ -static void fileWriterWrite(FileWriter *p, u8 *pData, int nData){ +static void vdbePmaWriteBlob(PmaWriter *p, u8 *pData, int nData){ int nRem = nData; while( nRem>0 && p->eFWErr==0 ){ int nCopy = nRem; @@ -75042,7 +82452,7 @@ static void fileWriterWrite(FileWriter *p, u8 *pData, int nData){ memcpy(&p->aBuffer[p->iBufEnd], &pData[nData-nRem], nCopy); p->iBufEnd += nCopy; if( p->iBufEnd==p->nBuffer ){ - p->eFWErr = sqlite3OsWrite(p->pFile, + p->eFWErr = sqlite3OsWrite(p->pFd, &p->aBuffer[p->iBufStart], p->iBufEnd - p->iBufStart, p->iWriteOff + p->iBufStart ); @@ -75056,43 +82466,44 @@ static void fileWriterWrite(FileWriter *p, u8 *pData, int nData){ } /* -** Flush any buffered data to disk and clean up the file-writer object. -** The results of using the file-writer after this call are undefined. +** Flush any buffered data to disk and clean up the PMA-writer object. +** The results of using the PMA-writer after this call are undefined. ** Return SQLITE_OK if flushing the buffered data succeeds or is not ** required. Otherwise, return an SQLite error code. ** ** Before returning, set *piEof to the offset immediately following the ** last byte written to the file. */ -static int fileWriterFinish(sqlite3 *db, FileWriter *p, i64 *piEof){ +static int vdbePmaWriterFinish(PmaWriter *p, i64 *piEof){ int rc; if( p->eFWErr==0 && ALWAYS(p->aBuffer) && p->iBufEnd>p->iBufStart ){ - p->eFWErr = sqlite3OsWrite(p->pFile, + p->eFWErr = sqlite3OsWrite(p->pFd, &p->aBuffer[p->iBufStart], p->iBufEnd - p->iBufStart, p->iWriteOff + p->iBufStart ); } *piEof = (p->iWriteOff + p->iBufEnd); - sqlite3DbFree(db, p->aBuffer); + sqlite3_free(p->aBuffer); rc = p->eFWErr; - memset(p, 0, sizeof(FileWriter)); + memset(p, 0, sizeof(PmaWriter)); return rc; } /* -** Write value iVal encoded as a varint to the file-write object. Return +** Write value iVal encoded as a varint to the PMA. Return ** SQLITE_OK if successful, or an SQLite error code if an error occurs. */ -static void fileWriterWriteVarint(FileWriter *p, u64 iVal){ +static void vdbePmaWriteVarint(PmaWriter *p, u64 iVal){ int nByte; u8 aByte[10]; nByte = sqlite3PutVarint(aByte, iVal); - fileWriterWrite(p, aByte, nByte); + vdbePmaWriteBlob(p, aByte, nByte); } /* -** Write the current contents of the in-memory linked-list to a PMA. Return -** SQLITE_OK if successful, or an SQLite error code otherwise. +** Write the current contents of in-memory linked-list pList to a level-0 +** PMA in the temp file belonging to sub-task pTask. Return SQLITE_OK if +** successful, or an SQLite error code otherwise. ** ** The format of a PMA is: ** @@ -75103,76 +82514,256 @@ static void fileWriterWriteVarint(FileWriter *p, u64 iVal){ ** Each record consists of a varint followed by a blob of data (the ** key). The varint is the number of bytes in the blob of data. */ -static int vdbeSorterListToPMA(sqlite3 *db, const VdbeCursor *pCsr){ +static int vdbeSorterListToPMA(SortSubtask *pTask, SorterList *pList){ + sqlite3 *db = pTask->pSorter->db; int rc = SQLITE_OK; /* Return code */ - VdbeSorter *pSorter = pCsr->pSorter; - FileWriter writer; + PmaWriter writer; /* Object used to write to the file */ - memset(&writer, 0, sizeof(FileWriter)); +#ifdef SQLITE_DEBUG + /* Set iSz to the expected size of file pTask->file after writing the PMA. + ** This is used by an assert() statement at the end of this function. */ + i64 iSz = pList->szPMA + sqlite3VarintLen(pList->szPMA) + pTask->file.iEof; +#endif - if( pSorter->nInMemory==0 ){ - assert( pSorter->pRecord==0 ); - return rc; - } - - rc = vdbeSorterSort(pCsr); + vdbeSorterWorkDebug(pTask, "enter"); + memset(&writer, 0, sizeof(PmaWriter)); + assert( pList->szPMA>0 ); /* If the first temporary PMA file has not been opened, open it now. */ - if( rc==SQLITE_OK && pSorter->pTemp1==0 ){ - rc = vdbeSorterOpenTempFile(db, &pSorter->pTemp1); - assert( rc!=SQLITE_OK || pSorter->pTemp1 ); - assert( pSorter->iWriteOff==0 ); - assert( pSorter->nPMA==0 ); + if( pTask->file.pFd==0 ){ + rc = vdbeSorterOpenTempFile(db, 0, &pTask->file.pFd); + assert( rc!=SQLITE_OK || pTask->file.pFd ); + assert( pTask->file.iEof==0 ); + assert( pTask->nPMA==0 ); + } + + /* Try to get the file to memory map */ + if( rc==SQLITE_OK ){ + vdbeSorterExtendFile(db, pTask->file.pFd, pTask->file.iEof+pList->szPMA+9); + } + + /* Sort the list */ + if( rc==SQLITE_OK ){ + rc = vdbeSorterSort(pTask, pList); } if( rc==SQLITE_OK ){ SorterRecord *p; SorterRecord *pNext = 0; - fileWriterInit(db, pSorter->pTemp1, &writer, pSorter->iWriteOff); - pSorter->nPMA++; - fileWriterWriteVarint(&writer, pSorter->nInMemory); - for(p=pSorter->pRecord; p; p=pNext){ - pNext = p->pNext; - fileWriterWriteVarint(&writer, p->nVal); - fileWriterWrite(&writer, p->pVal, p->nVal); - sqlite3DbFree(db, p); + vdbePmaWriterInit(pTask->file.pFd, &writer, pTask->pSorter->pgsz, + pTask->file.iEof); + pTask->nPMA++; + vdbePmaWriteVarint(&writer, pList->szPMA); + for(p=pList->pList; p; p=pNext){ + pNext = p->u.pNext; + vdbePmaWriteVarint(&writer, p->nVal); + vdbePmaWriteBlob(&writer, SRVAL(p), p->nVal); + if( pList->aMemory==0 ) sqlite3_free(p); + } + pList->pList = p; + rc = vdbePmaWriterFinish(&writer, &pTask->file.iEof); + } + + vdbeSorterWorkDebug(pTask, "exit"); + assert( rc!=SQLITE_OK || pList->pList==0 ); + assert( rc!=SQLITE_OK || pTask->file.iEof==iSz ); + return rc; +} + +/* +** Advance the MergeEngine to its next entry. +** Set *pbEof to true there is no next entry because +** the MergeEngine has reached the end of all its inputs. +** +** Return SQLITE_OK if successful or an error code if an error occurs. +*/ +static int vdbeMergeEngineStep( + MergeEngine *pMerger, /* The merge engine to advance to the next row */ + int *pbEof /* Set TRUE at EOF. Set false for more content */ +){ + int rc; + int iPrev = pMerger->aTree[1];/* Index of PmaReader to advance */ + SortSubtask *pTask = pMerger->pTask; + + /* Advance the current PmaReader */ + rc = vdbePmaReaderNext(&pMerger->aReadr[iPrev]); + + /* Update contents of aTree[] */ + if( rc==SQLITE_OK ){ + int i; /* Index of aTree[] to recalculate */ + PmaReader *pReadr1; /* First PmaReader to compare */ + PmaReader *pReadr2; /* Second PmaReader to compare */ + int bCached = 0; + + /* Find the first two PmaReaders to compare. The one that was just + ** advanced (iPrev) and the one next to it in the array. */ + pReadr1 = &pMerger->aReadr[(iPrev & 0xFFFE)]; + pReadr2 = &pMerger->aReadr[(iPrev | 0x0001)]; + + for(i=(pMerger->nTree+iPrev)/2; i>0; i=i/2){ + /* Compare pReadr1 and pReadr2. Store the result in variable iRes. */ + int iRes; + if( pReadr1->pFd==0 ){ + iRes = +1; + }else if( pReadr2->pFd==0 ){ + iRes = -1; + }else{ + iRes = pTask->xCompare(pTask, &bCached, + pReadr1->aKey, pReadr1->nKey, pReadr2->aKey, pReadr2->nKey + ); + } + + /* If pReadr1 contained the smaller value, set aTree[i] to its index. + ** Then set pReadr2 to the next PmaReader to compare to pReadr1. In this + ** case there is no cache of pReadr2 in pTask->pUnpacked, so set + ** pKey2 to point to the record belonging to pReadr2. + ** + ** Alternatively, if pReadr2 contains the smaller of the two values, + ** set aTree[i] to its index and update pReadr1. If vdbeSorterCompare() + ** was actually called above, then pTask->pUnpacked now contains + ** a value equivalent to pReadr2. So set pKey2 to NULL to prevent + ** vdbeSorterCompare() from decoding pReadr2 again. + ** + ** If the two values were equal, then the value from the oldest + ** PMA should be considered smaller. The VdbeSorter.aReadr[] array + ** is sorted from oldest to newest, so pReadr1 contains older values + ** than pReadr2 iff (pReadr1aTree[i] = (int)(pReadr1 - pMerger->aReadr); + pReadr2 = &pMerger->aReadr[ pMerger->aTree[i ^ 0x0001] ]; + bCached = 0; + }else{ + if( pReadr1->pFd ) bCached = 0; + pMerger->aTree[i] = (int)(pReadr2 - pMerger->aReadr); + pReadr1 = &pMerger->aReadr[ pMerger->aTree[i ^ 0x0001] ]; + } + } + *pbEof = (pMerger->aReadr[pMerger->aTree[1]].pFd==0); + } + + return (rc==SQLITE_OK ? pTask->pUnpacked->errCode : rc); +} + +#if SQLITE_MAX_WORKER_THREADS>0 +/* +** The main routine for background threads that write level-0 PMAs. +*/ +static void *vdbeSorterFlushThread(void *pCtx){ + SortSubtask *pTask = (SortSubtask*)pCtx; + int rc; /* Return code */ + assert( pTask->bDone==0 ); + rc = vdbeSorterListToPMA(pTask, &pTask->list); + pTask->bDone = 1; + return SQLITE_INT_TO_PTR(rc); +} +#endif /* SQLITE_MAX_WORKER_THREADS>0 */ + +/* +** Flush the current contents of VdbeSorter.list to a new PMA, possibly +** using a background thread. +*/ +static int vdbeSorterFlushPMA(VdbeSorter *pSorter){ +#if SQLITE_MAX_WORKER_THREADS==0 + pSorter->bUsePMA = 1; + return vdbeSorterListToPMA(&pSorter->aTask[0], &pSorter->list); +#else + int rc = SQLITE_OK; + int i; + SortSubtask *pTask = 0; /* Thread context used to create new PMA */ + int nWorker = (pSorter->nTask-1); + + /* Set the flag to indicate that at least one PMA has been written. + ** Or will be, anyhow. */ + pSorter->bUsePMA = 1; + + /* Select a sub-task to sort and flush the current list of in-memory + ** records to disk. If the sorter is running in multi-threaded mode, + ** round-robin between the first (pSorter->nTask-1) tasks. Except, if + ** the background thread from a sub-tasks previous turn is still running, + ** skip it. If the first (pSorter->nTask-1) sub-tasks are all still busy, + ** fall back to using the final sub-task. The first (pSorter->nTask-1) + ** sub-tasks are prefered as they use background threads - the final + ** sub-task uses the main thread. */ + for(i=0; iiPrev + i + 1) % nWorker; + pTask = &pSorter->aTask[iTest]; + if( pTask->bDone ){ + rc = vdbeSorterJoinThread(pTask); + } + if( rc!=SQLITE_OK || pTask->pThread==0 ) break; + } + + if( rc==SQLITE_OK ){ + if( i==nWorker ){ + /* Use the foreground thread for this operation */ + rc = vdbeSorterListToPMA(&pSorter->aTask[nWorker], &pSorter->list); + }else{ + /* Launch a background thread for this operation */ + u8 *aMem = pTask->list.aMemory; + void *pCtx = (void*)pTask; + + assert( pTask->pThread==0 && pTask->bDone==0 ); + assert( pTask->list.pList==0 ); + assert( pTask->list.aMemory==0 || pSorter->list.aMemory!=0 ); + + pSorter->iPrev = (u8)(pTask - pSorter->aTask); + pTask->list = pSorter->list; + pSorter->list.pList = 0; + pSorter->list.szPMA = 0; + if( aMem ){ + pSorter->list.aMemory = aMem; + pSorter->nMemory = sqlite3MallocSize(aMem); + }else if( pSorter->list.aMemory ){ + pSorter->list.aMemory = sqlite3Malloc(pSorter->nMemory); + if( !pSorter->list.aMemory ) return SQLITE_NOMEM; + } + + rc = vdbeSorterCreateThread(pTask, vdbeSorterFlushThread, pCtx); } - pSorter->pRecord = p; - rc = fileWriterFinish(db, &writer, &pSorter->iWriteOff); } return rc; +#endif /* SQLITE_MAX_WORKER_THREADS!=0 */ } /* ** Add a record to the sorter. */ SQLITE_PRIVATE int sqlite3VdbeSorterWrite( - sqlite3 *db, /* Database handle */ - const VdbeCursor *pCsr, /* Sorter cursor */ + const VdbeCursor *pCsr, /* Sorter cursor */ Mem *pVal /* Memory cell containing record */ ){ - VdbeSorter *pSorter = pCsr->pSorter; + VdbeSorter *pSorter; int rc = SQLITE_OK; /* Return Code */ SorterRecord *pNew; /* New list element */ + int bFlush; /* True to flush contents of memory to PMA */ + int nReq; /* Bytes of memory required */ + int nPMA; /* Bytes of PMA space required */ + int t; /* serial type of first record field */ - assert( pSorter ); - pSorter->nInMemory += sqlite3VarintLen(pVal->n) + pVal->n; - - pNew = (SorterRecord *)sqlite3DbMallocRaw(db, pVal->n + sizeof(SorterRecord)); - if( pNew==0 ){ - rc = SQLITE_NOMEM; + assert( pCsr->eCurType==CURTYPE_SORTER ); + pSorter = pCsr->uc.pSorter; + getVarint32((const u8*)&pVal->z[1], t); + if( t>0 && t<10 && t!=7 ){ + pSorter->typeMask &= SORTER_TYPE_INTEGER; + }else if( t>10 && (t & 0x01) ){ + pSorter->typeMask &= SORTER_TYPE_TEXT; }else{ - pNew->pVal = (void *)&pNew[1]; - memcpy(pNew->pVal, pVal->z, pVal->n); - pNew->nVal = pVal->n; - pNew->pNext = pSorter->pRecord; - pSorter->pRecord = pNew; + pSorter->typeMask = 0; } - /* See if the contents of the sorter should now be written out. They - ** are written out when either of the following are true: + assert( pSorter ); + + /* Figure out whether or not the current contents of memory should be + ** flushed to a PMA before continuing. If so, do so. + ** + ** If using the single large allocation mode (pSorter->aMemory!=0), then + ** flush the contents of memory to a new PMA if (a) at least one value is + ** already in memory and (b) the new value will not fit in memory. + ** + ** Or, if using separate allocations for each record, flush the contents + ** of memory to a PMA if either of the following are true: ** ** * The total memory allocated for the in-memory list is greater ** than (page-size * cache-size), or @@ -75180,161 +82771,811 @@ SQLITE_PRIVATE int sqlite3VdbeSorterWrite( ** * The total memory allocated for the in-memory list is greater ** than (page-size * 10) and sqlite3HeapNearlyFull() returns true. */ - if( rc==SQLITE_OK && pSorter->mxPmaSize>0 && ( - (pSorter->nInMemory>pSorter->mxPmaSize) - || (pSorter->nInMemory>pSorter->mnPmaSize && sqlite3HeapNearlyFull()) - )){ -#ifdef SQLITE_DEBUG - i64 nExpect = pSorter->iWriteOff - + sqlite3VarintLen(pSorter->nInMemory) - + pSorter->nInMemory; + nReq = pVal->n + sizeof(SorterRecord); + nPMA = pVal->n + sqlite3VarintLen(pVal->n); + if( pSorter->mxPmaSize ){ + if( pSorter->list.aMemory ){ + bFlush = pSorter->iMemory && (pSorter->iMemory+nReq) > pSorter->mxPmaSize; + }else{ + bFlush = ( + (pSorter->list.szPMA > pSorter->mxPmaSize) + || (pSorter->list.szPMA > pSorter->mnPmaSize && sqlite3HeapNearlyFull()) + ); + } + if( bFlush ){ + rc = vdbeSorterFlushPMA(pSorter); + pSorter->list.szPMA = 0; + pSorter->iMemory = 0; + assert( rc!=SQLITE_OK || pSorter->list.pList==0 ); + } + } + + pSorter->list.szPMA += nPMA; + if( nPMA>pSorter->mxKeysize ){ + pSorter->mxKeysize = nPMA; + } + + if( pSorter->list.aMemory ){ + int nMin = pSorter->iMemory + nReq; + + if( nMin>pSorter->nMemory ){ + u8 *aNew; + int nNew = pSorter->nMemory * 2; + while( nNew < nMin ) nNew = nNew*2; + if( nNew > pSorter->mxPmaSize ) nNew = pSorter->mxPmaSize; + if( nNew < nMin ) nNew = nMin; + + aNew = sqlite3Realloc(pSorter->list.aMemory, nNew); + if( !aNew ) return SQLITE_NOMEM; + pSorter->list.pList = (SorterRecord*)( + aNew + ((u8*)pSorter->list.pList - pSorter->list.aMemory) + ); + pSorter->list.aMemory = aNew; + pSorter->nMemory = nNew; + } + + pNew = (SorterRecord*)&pSorter->list.aMemory[pSorter->iMemory]; + pSorter->iMemory += ROUND8(nReq); + pNew->u.iNext = (int)((u8*)(pSorter->list.pList) - pSorter->list.aMemory); + }else{ + pNew = (SorterRecord *)sqlite3Malloc(nReq); + if( pNew==0 ){ + return SQLITE_NOMEM; + } + pNew->u.pNext = pSorter->list.pList; + } + + memcpy(SRVAL(pNew), pVal->z, pVal->n); + pNew->nVal = pVal->n; + pSorter->list.pList = pNew; + + return rc; +} + +/* +** Read keys from pIncr->pMerger and populate pIncr->aFile[1]. The format +** of the data stored in aFile[1] is the same as that used by regular PMAs, +** except that the number-of-bytes varint is omitted from the start. +*/ +static int vdbeIncrPopulate(IncrMerger *pIncr){ + int rc = SQLITE_OK; + int rc2; + i64 iStart = pIncr->iStartOff; + SorterFile *pOut = &pIncr->aFile[1]; + SortSubtask *pTask = pIncr->pTask; + MergeEngine *pMerger = pIncr->pMerger; + PmaWriter writer; + assert( pIncr->bEof==0 ); + + vdbeSorterPopulateDebug(pTask, "enter"); + + vdbePmaWriterInit(pOut->pFd, &writer, pTask->pSorter->pgsz, iStart); + while( rc==SQLITE_OK ){ + int dummy; + PmaReader *pReader = &pMerger->aReadr[ pMerger->aTree[1] ]; + int nKey = pReader->nKey; + i64 iEof = writer.iWriteOff + writer.iBufEnd; + + /* Check if the output file is full or if the input has been exhausted. + ** In either case exit the loop. */ + if( pReader->pFd==0 ) break; + if( (iEof + nKey + sqlite3VarintLen(nKey))>(iStart + pIncr->mxSz) ) break; + + /* Write the next key to the output. */ + vdbePmaWriteVarint(&writer, nKey); + vdbePmaWriteBlob(&writer, pReader->aKey, nKey); + assert( pIncr->pMerger->pTask==pTask ); + rc = vdbeMergeEngineStep(pIncr->pMerger, &dummy); + } + + rc2 = vdbePmaWriterFinish(&writer, &pOut->iEof); + if( rc==SQLITE_OK ) rc = rc2; + vdbeSorterPopulateDebug(pTask, "exit"); + return rc; +} + +#if SQLITE_MAX_WORKER_THREADS>0 +/* +** The main routine for background threads that populate aFile[1] of +** multi-threaded IncrMerger objects. +*/ +static void *vdbeIncrPopulateThread(void *pCtx){ + IncrMerger *pIncr = (IncrMerger*)pCtx; + void *pRet = SQLITE_INT_TO_PTR( vdbeIncrPopulate(pIncr) ); + pIncr->pTask->bDone = 1; + return pRet; +} + +/* +** Launch a background thread to populate aFile[1] of pIncr. +*/ +static int vdbeIncrBgPopulate(IncrMerger *pIncr){ + void *p = (void*)pIncr; + assert( pIncr->bUseThread ); + return vdbeSorterCreateThread(pIncr->pTask, vdbeIncrPopulateThread, p); +} #endif - rc = vdbeSorterListToPMA(db, pCsr); - pSorter->nInMemory = 0; - assert( rc!=SQLITE_OK || (nExpect==pSorter->iWriteOff) ); + +/* +** This function is called when the PmaReader corresponding to pIncr has +** finished reading the contents of aFile[0]. Its purpose is to "refill" +** aFile[0] such that the PmaReader should start rereading it from the +** beginning. +** +** For single-threaded objects, this is accomplished by literally reading +** keys from pIncr->pMerger and repopulating aFile[0]. +** +** For multi-threaded objects, all that is required is to wait until the +** background thread is finished (if it is not already) and then swap +** aFile[0] and aFile[1] in place. If the contents of pMerger have not +** been exhausted, this function also launches a new background thread +** to populate the new aFile[1]. +** +** SQLITE_OK is returned on success, or an SQLite error code otherwise. +*/ +static int vdbeIncrSwap(IncrMerger *pIncr){ + int rc = SQLITE_OK; + +#if SQLITE_MAX_WORKER_THREADS>0 + if( pIncr->bUseThread ){ + rc = vdbeSorterJoinThread(pIncr->pTask); + + if( rc==SQLITE_OK ){ + SorterFile f0 = pIncr->aFile[0]; + pIncr->aFile[0] = pIncr->aFile[1]; + pIncr->aFile[1] = f0; + } + + if( rc==SQLITE_OK ){ + if( pIncr->aFile[0].iEof==pIncr->iStartOff ){ + pIncr->bEof = 1; + }else{ + rc = vdbeIncrBgPopulate(pIncr); + } + } + }else +#endif + { + rc = vdbeIncrPopulate(pIncr); + pIncr->aFile[0] = pIncr->aFile[1]; + if( pIncr->aFile[0].iEof==pIncr->iStartOff ){ + pIncr->bEof = 1; + } } return rc; } /* -** Helper function for sqlite3VdbeSorterRewind(). +** Allocate and return a new IncrMerger object to read data from pMerger. +** +** If an OOM condition is encountered, return NULL. In this case free the +** pMerger argument before returning. */ -static int vdbeSorterInitMerge( - sqlite3 *db, /* Database handle */ - const VdbeCursor *pCsr, /* Cursor handle for this sorter */ - i64 *pnByte /* Sum of bytes in all opened PMAs */ +static int vdbeIncrMergerNew( + SortSubtask *pTask, /* The thread that will be using the new IncrMerger */ + MergeEngine *pMerger, /* The MergeEngine that the IncrMerger will control */ + IncrMerger **ppOut /* Write the new IncrMerger here */ +){ + int rc = SQLITE_OK; + IncrMerger *pIncr = *ppOut = (IncrMerger*) + (sqlite3FaultSim(100) ? 0 : sqlite3MallocZero(sizeof(*pIncr))); + if( pIncr ){ + pIncr->pMerger = pMerger; + pIncr->pTask = pTask; + pIncr->mxSz = MAX(pTask->pSorter->mxKeysize+9,pTask->pSorter->mxPmaSize/2); + pTask->file2.iEof += pIncr->mxSz; + }else{ + vdbeMergeEngineFree(pMerger); + rc = SQLITE_NOMEM; + } + return rc; +} + +#if SQLITE_MAX_WORKER_THREADS>0 +/* +** Set the "use-threads" flag on object pIncr. +*/ +static void vdbeIncrMergerSetThreads(IncrMerger *pIncr){ + pIncr->bUseThread = 1; + pIncr->pTask->file2.iEof -= pIncr->mxSz; +} +#endif /* SQLITE_MAX_WORKER_THREADS>0 */ + + + +/* +** Recompute pMerger->aTree[iOut] by comparing the next keys on the +** two PmaReaders that feed that entry. Neither of the PmaReaders +** are advanced. This routine merely does the comparison. +*/ +static void vdbeMergeEngineCompare( + MergeEngine *pMerger, /* Merge engine containing PmaReaders to compare */ + int iOut /* Store the result in pMerger->aTree[iOut] */ +){ + int i1; + int i2; + int iRes; + PmaReader *p1; + PmaReader *p2; + + assert( iOutnTree && iOut>0 ); + + if( iOut>=(pMerger->nTree/2) ){ + i1 = (iOut - pMerger->nTree/2) * 2; + i2 = i1 + 1; + }else{ + i1 = pMerger->aTree[iOut*2]; + i2 = pMerger->aTree[iOut*2+1]; + } + + p1 = &pMerger->aReadr[i1]; + p2 = &pMerger->aReadr[i2]; + + if( p1->pFd==0 ){ + iRes = i2; + }else if( p2->pFd==0 ){ + iRes = i1; + }else{ + SortSubtask *pTask = pMerger->pTask; + int bCached = 0; + int res; + assert( pTask->pUnpacked!=0 ); /* from vdbeSortSubtaskMain() */ + res = pTask->xCompare( + pTask, &bCached, p1->aKey, p1->nKey, p2->aKey, p2->nKey + ); + if( res<=0 ){ + iRes = i1; + }else{ + iRes = i2; + } + } + + pMerger->aTree[iOut] = iRes; +} + +/* +** Allowed values for the eMode parameter to vdbeMergeEngineInit() +** and vdbePmaReaderIncrMergeInit(). +** +** Only INCRINIT_NORMAL is valid in single-threaded builds (when +** SQLITE_MAX_WORKER_THREADS==0). The other values are only used +** when there exists one or more separate worker threads. +*/ +#define INCRINIT_NORMAL 0 +#define INCRINIT_TASK 1 +#define INCRINIT_ROOT 2 + +/* +** Forward reference required as the vdbeIncrMergeInit() and +** vdbePmaReaderIncrInit() routines are called mutually recursively when +** building a merge tree. +*/ +static int vdbePmaReaderIncrInit(PmaReader *pReadr, int eMode); + +/* +** Initialize the MergeEngine object passed as the second argument. Once this +** function returns, the first key of merged data may be read from the +** MergeEngine object in the usual fashion. +** +** If argument eMode is INCRINIT_ROOT, then it is assumed that any IncrMerge +** objects attached to the PmaReader objects that the merger reads from have +** already been populated, but that they have not yet populated aFile[0] and +** set the PmaReader objects up to read from it. In this case all that is +** required is to call vdbePmaReaderNext() on each PmaReader to point it at +** its first key. +** +** Otherwise, if eMode is any value other than INCRINIT_ROOT, then use +** vdbePmaReaderIncrMergeInit() to initialize each PmaReader that feeds data +** to pMerger. +** +** SQLITE_OK is returned if successful, or an SQLite error code otherwise. +*/ +static int vdbeMergeEngineInit( + SortSubtask *pTask, /* Thread that will run pMerger */ + MergeEngine *pMerger, /* MergeEngine to initialize */ + int eMode /* One of the INCRINIT_XXX constants */ ){ - VdbeSorter *pSorter = pCsr->pSorter; int rc = SQLITE_OK; /* Return code */ - int i; /* Used to iterator through aIter[] */ - i64 nByte = 0; /* Total bytes in all opened PMAs */ + int i; /* For looping over PmaReader objects */ + int nTree = pMerger->nTree; - /* Initialize the iterators. */ - for(i=0; iaIter[i]; - rc = vdbeSorterIterInit(db, pSorter, pSorter->iReadOff, pIter, &nByte); - pSorter->iReadOff = pIter->iEof; - assert( rc!=SQLITE_OK || pSorter->iReadOff<=pSorter->iWriteOff ); - if( rc!=SQLITE_OK || pSorter->iReadOff>=pSorter->iWriteOff ) break; + /* eMode is always INCRINIT_NORMAL in single-threaded mode */ + assert( SQLITE_MAX_WORKER_THREADS>0 || eMode==INCRINIT_NORMAL ); + + /* Verify that the MergeEngine is assigned to a single thread */ + assert( pMerger->pTask==0 ); + pMerger->pTask = pTask; + + for(i=0; i0 && eMode==INCRINIT_ROOT ){ + /* PmaReaders should be normally initialized in order, as if they are + ** reading from the same temp file this makes for more linear file IO. + ** However, in the INCRINIT_ROOT case, if PmaReader aReadr[nTask-1] is + ** in use it will block the vdbePmaReaderNext() call while it uses + ** the main thread to fill its buffer. So calling PmaReaderNext() + ** on this PmaReader before any of the multi-threaded PmaReaders takes + ** better advantage of multi-processor hardware. */ + rc = vdbePmaReaderNext(&pMerger->aReadr[nTree-i-1]); + }else{ + rc = vdbePmaReaderIncrInit(&pMerger->aReadr[i], INCRINIT_NORMAL); + } + if( rc!=SQLITE_OK ) return rc; } - /* Initialize the aTree[] array. */ - for(i=pSorter->nTree-1; rc==SQLITE_OK && i>0; i--){ - rc = vdbeSorterDoCompare(pCsr, i); + for(i=pMerger->nTree-1; i>0; i--){ + vdbeMergeEngineCompare(pMerger, i); + } + return pTask->pUnpacked->errCode; +} + +/* +** The PmaReader passed as the first argument is guaranteed to be an +** incremental-reader (pReadr->pIncr!=0). This function serves to open +** and/or initialize the temp file related fields of the IncrMerge +** object at (pReadr->pIncr). +** +** If argument eMode is set to INCRINIT_NORMAL, then all PmaReaders +** in the sub-tree headed by pReadr are also initialized. Data is then +** loaded into the buffers belonging to pReadr and it is set to point to +** the first key in its range. +** +** If argument eMode is set to INCRINIT_TASK, then pReadr is guaranteed +** to be a multi-threaded PmaReader and this function is being called in a +** background thread. In this case all PmaReaders in the sub-tree are +** initialized as for INCRINIT_NORMAL and the aFile[1] buffer belonging to +** pReadr is populated. However, pReadr itself is not set up to point +** to its first key. A call to vdbePmaReaderNext() is still required to do +** that. +** +** The reason this function does not call vdbePmaReaderNext() immediately +** in the INCRINIT_TASK case is that vdbePmaReaderNext() assumes that it has +** to block on thread (pTask->thread) before accessing aFile[1]. But, since +** this entire function is being run by thread (pTask->thread), that will +** lead to the current background thread attempting to join itself. +** +** Finally, if argument eMode is set to INCRINIT_ROOT, it may be assumed +** that pReadr->pIncr is a multi-threaded IncrMerge objects, and that all +** child-trees have already been initialized using IncrInit(INCRINIT_TASK). +** In this case vdbePmaReaderNext() is called on all child PmaReaders and +** the current PmaReader set to point to the first key in its range. +** +** SQLITE_OK is returned if successful, or an SQLite error code otherwise. +*/ +static int vdbePmaReaderIncrMergeInit(PmaReader *pReadr, int eMode){ + int rc = SQLITE_OK; + IncrMerger *pIncr = pReadr->pIncr; + SortSubtask *pTask = pIncr->pTask; + sqlite3 *db = pTask->pSorter->db; + + /* eMode is always INCRINIT_NORMAL in single-threaded mode */ + assert( SQLITE_MAX_WORKER_THREADS>0 || eMode==INCRINIT_NORMAL ); + + rc = vdbeMergeEngineInit(pTask, pIncr->pMerger, eMode); + + /* Set up the required files for pIncr. A multi-theaded IncrMerge object + ** requires two temp files to itself, whereas a single-threaded object + ** only requires a region of pTask->file2. */ + if( rc==SQLITE_OK ){ + int mxSz = pIncr->mxSz; +#if SQLITE_MAX_WORKER_THREADS>0 + if( pIncr->bUseThread ){ + rc = vdbeSorterOpenTempFile(db, mxSz, &pIncr->aFile[0].pFd); + if( rc==SQLITE_OK ){ + rc = vdbeSorterOpenTempFile(db, mxSz, &pIncr->aFile[1].pFd); + } + }else +#endif + /*if( !pIncr->bUseThread )*/{ + if( pTask->file2.pFd==0 ){ + assert( pTask->file2.iEof>0 ); + rc = vdbeSorterOpenTempFile(db, pTask->file2.iEof, &pTask->file2.pFd); + pTask->file2.iEof = 0; + } + if( rc==SQLITE_OK ){ + pIncr->aFile[1].pFd = pTask->file2.pFd; + pIncr->iStartOff = pTask->file2.iEof; + pTask->file2.iEof += mxSz; + } + } } - *pnByte = nByte; +#if SQLITE_MAX_WORKER_THREADS>0 + if( rc==SQLITE_OK && pIncr->bUseThread ){ + /* Use the current thread to populate aFile[1], even though this + ** PmaReader is multi-threaded. If this is an INCRINIT_TASK object, + ** then this function is already running in background thread + ** pIncr->pTask->thread. + ** + ** If this is the INCRINIT_ROOT object, then it is running in the + ** main VDBE thread. But that is Ok, as that thread cannot return + ** control to the VDBE or proceed with anything useful until the + ** first results are ready from this merger object anyway. + */ + assert( eMode==INCRINIT_ROOT || eMode==INCRINIT_TASK ); + rc = vdbeIncrPopulate(pIncr); + } +#endif + + if( rc==SQLITE_OK && (SQLITE_MAX_WORKER_THREADS==0 || eMode!=INCRINIT_TASK) ){ + rc = vdbePmaReaderNext(pReadr); + } + + return rc; +} + +#if SQLITE_MAX_WORKER_THREADS>0 +/* +** The main routine for vdbePmaReaderIncrMergeInit() operations run in +** background threads. +*/ +static void *vdbePmaReaderBgIncrInit(void *pCtx){ + PmaReader *pReader = (PmaReader*)pCtx; + void *pRet = SQLITE_INT_TO_PTR( + vdbePmaReaderIncrMergeInit(pReader,INCRINIT_TASK) + ); + pReader->pIncr->pTask->bDone = 1; + return pRet; +} +#endif + +/* +** If the PmaReader passed as the first argument is not an incremental-reader +** (if pReadr->pIncr==0), then this function is a no-op. Otherwise, it invokes +** the vdbePmaReaderIncrMergeInit() function with the parameters passed to +** this routine to initialize the incremental merge. +** +** If the IncrMerger object is multi-threaded (IncrMerger.bUseThread==1), +** then a background thread is launched to call vdbePmaReaderIncrMergeInit(). +** Or, if the IncrMerger is single threaded, the same function is called +** using the current thread. +*/ +static int vdbePmaReaderIncrInit(PmaReader *pReadr, int eMode){ + IncrMerger *pIncr = pReadr->pIncr; /* Incremental merger */ + int rc = SQLITE_OK; /* Return code */ + if( pIncr ){ +#if SQLITE_MAX_WORKER_THREADS>0 + assert( pIncr->bUseThread==0 || eMode==INCRINIT_TASK ); + if( pIncr->bUseThread ){ + void *pCtx = (void*)pReadr; + rc = vdbeSorterCreateThread(pIncr->pTask, vdbePmaReaderBgIncrInit, pCtx); + }else +#endif + { + rc = vdbePmaReaderIncrMergeInit(pReadr, eMode); + } + } return rc; } /* -** Once the sorter has been populated, this function is called to prepare -** for iterating through its contents in sorted order. +** Allocate a new MergeEngine object to merge the contents of nPMA level-0 +** PMAs from pTask->file. If no error occurs, set *ppOut to point to +** the new object and return SQLITE_OK. Or, if an error does occur, set *ppOut +** to NULL and return an SQLite error code. +** +** When this function is called, *piOffset is set to the offset of the +** first PMA to read from pTask->file. Assuming no error occurs, it is +** set to the offset immediately following the last byte of the last +** PMA before returning. If an error does occur, then the final value of +** *piOffset is undefined. */ -SQLITE_PRIVATE int sqlite3VdbeSorterRewind(sqlite3 *db, const VdbeCursor *pCsr, int *pbEof){ - VdbeSorter *pSorter = pCsr->pSorter; - int rc; /* Return code */ - sqlite3_file *pTemp2 = 0; /* Second temp file to use */ - i64 iWrite2 = 0; /* Write offset for pTemp2 */ - int nIter; /* Number of iterators used */ - int nByte; /* Bytes of space required for aIter/aTree */ - int N = 2; /* Power of 2 >= nIter */ +static int vdbeMergeEngineLevel0( + SortSubtask *pTask, /* Sorter task to read from */ + int nPMA, /* Number of PMAs to read */ + i64 *piOffset, /* IN/OUT: Readr offset in pTask->file */ + MergeEngine **ppOut /* OUT: New merge-engine */ +){ + MergeEngine *pNew; /* Merge engine to return */ + i64 iOff = *piOffset; + int i; + int rc = SQLITE_OK; + *ppOut = pNew = vdbeMergeEngineNew(nPMA); + if( pNew==0 ) rc = SQLITE_NOMEM; + + for(i=0; iaReadr[i]; + rc = vdbePmaReaderInit(pTask, &pTask->file, iOff, pReadr, &nDummy); + iOff = pReadr->iEof; + } + + if( rc!=SQLITE_OK ){ + vdbeMergeEngineFree(pNew); + *ppOut = 0; + } + *piOffset = iOff; + return rc; +} + +/* +** Return the depth of a tree comprising nPMA PMAs, assuming a fanout of +** SORTER_MAX_MERGE_COUNT. The returned value does not include leaf nodes. +** +** i.e. +** +** nPMA<=16 -> TreeDepth() == 0 +** nPMA<=256 -> TreeDepth() == 1 +** nPMA<=65536 -> TreeDepth() == 2 +*/ +static int vdbeSorterTreeDepth(int nPMA){ + int nDepth = 0; + i64 nDiv = SORTER_MAX_MERGE_COUNT; + while( nDiv < (i64)nPMA ){ + nDiv = nDiv * SORTER_MAX_MERGE_COUNT; + nDepth++; + } + return nDepth; +} + +/* +** pRoot is the root of an incremental merge-tree with depth nDepth (according +** to vdbeSorterTreeDepth()). pLeaf is the iSeq'th leaf to be added to the +** tree, counting from zero. This function adds pLeaf to the tree. +** +** If successful, SQLITE_OK is returned. If an error occurs, an SQLite error +** code is returned and pLeaf is freed. +*/ +static int vdbeSorterAddToTree( + SortSubtask *pTask, /* Task context */ + int nDepth, /* Depth of tree according to TreeDepth() */ + int iSeq, /* Sequence number of leaf within tree */ + MergeEngine *pRoot, /* Root of tree */ + MergeEngine *pLeaf /* Leaf to add to tree */ +){ + int rc = SQLITE_OK; + int nDiv = 1; + int i; + MergeEngine *p = pRoot; + IncrMerger *pIncr; + + rc = vdbeIncrMergerNew(pTask, pLeaf, &pIncr); + + for(i=1; iaReadr[iIter]; + + if( pReadr->pIncr==0 ){ + MergeEngine *pNew = vdbeMergeEngineNew(SORTER_MAX_MERGE_COUNT); + if( pNew==0 ){ + rc = SQLITE_NOMEM; + }else{ + rc = vdbeIncrMergerNew(pTask, pNew, &pReadr->pIncr); + } + } + if( rc==SQLITE_OK ){ + p = pReadr->pIncr->pMerger; + nDiv = nDiv / SORTER_MAX_MERGE_COUNT; + } + } + + if( rc==SQLITE_OK ){ + p->aReadr[iSeq % SORTER_MAX_MERGE_COUNT].pIncr = pIncr; + }else{ + vdbeIncrFree(pIncr); + } + return rc; +} + +/* +** This function is called as part of a SorterRewind() operation on a sorter +** that has already written two or more level-0 PMAs to one or more temp +** files. It builds a tree of MergeEngine/IncrMerger/PmaReader objects that +** can be used to incrementally merge all PMAs on disk. +** +** If successful, SQLITE_OK is returned and *ppOut set to point to the +** MergeEngine object at the root of the tree before returning. Or, if an +** error occurs, an SQLite error code is returned and the final value +** of *ppOut is undefined. +*/ +static int vdbeSorterMergeTreeBuild( + VdbeSorter *pSorter, /* The VDBE cursor that implements the sort */ + MergeEngine **ppOut /* Write the MergeEngine here */ +){ + MergeEngine *pMain = 0; + int rc = SQLITE_OK; + int iTask; + +#if SQLITE_MAX_WORKER_THREADS>0 + /* If the sorter uses more than one task, then create the top-level + ** MergeEngine here. This MergeEngine will read data from exactly + ** one PmaReader per sub-task. */ + assert( pSorter->bUseThreads || pSorter->nTask==1 ); + if( pSorter->nTask>1 ){ + pMain = vdbeMergeEngineNew(pSorter->nTask); + if( pMain==0 ) rc = SQLITE_NOMEM; + } +#endif + + for(iTask=0; rc==SQLITE_OK && iTasknTask; iTask++){ + SortSubtask *pTask = &pSorter->aTask[iTask]; + assert( pTask->nPMA>0 || SQLITE_MAX_WORKER_THREADS>0 ); + if( SQLITE_MAX_WORKER_THREADS==0 || pTask->nPMA ){ + MergeEngine *pRoot = 0; /* Root node of tree for this task */ + int nDepth = vdbeSorterTreeDepth(pTask->nPMA); + i64 iReadOff = 0; + + if( pTask->nPMA<=SORTER_MAX_MERGE_COUNT ){ + rc = vdbeMergeEngineLevel0(pTask, pTask->nPMA, &iReadOff, &pRoot); + }else{ + int i; + int iSeq = 0; + pRoot = vdbeMergeEngineNew(SORTER_MAX_MERGE_COUNT); + if( pRoot==0 ) rc = SQLITE_NOMEM; + for(i=0; inPMA && rc==SQLITE_OK; i += SORTER_MAX_MERGE_COUNT){ + MergeEngine *pMerger = 0; /* New level-0 PMA merger */ + int nReader; /* Number of level-0 PMAs to merge */ + + nReader = MIN(pTask->nPMA - i, SORTER_MAX_MERGE_COUNT); + rc = vdbeMergeEngineLevel0(pTask, nReader, &iReadOff, &pMerger); + if( rc==SQLITE_OK ){ + rc = vdbeSorterAddToTree(pTask, nDepth, iSeq++, pRoot, pMerger); + } + } + } + + if( rc==SQLITE_OK ){ +#if SQLITE_MAX_WORKER_THREADS>0 + if( pMain!=0 ){ + rc = vdbeIncrMergerNew(pTask, pRoot, &pMain->aReadr[iTask].pIncr); + }else +#endif + { + assert( pMain==0 ); + pMain = pRoot; + } + }else{ + vdbeMergeEngineFree(pRoot); + } + } + } + + if( rc!=SQLITE_OK ){ + vdbeMergeEngineFree(pMain); + pMain = 0; + } + *ppOut = pMain; + return rc; +} + +/* +** This function is called as part of an sqlite3VdbeSorterRewind() operation +** on a sorter that has written two or more PMAs to temporary files. It sets +** up either VdbeSorter.pMerger (for single threaded sorters) or pReader +** (for multi-threaded sorters) so that it can be used to iterate through +** all records stored in the sorter. +** +** SQLITE_OK is returned if successful, or an SQLite error code otherwise. +*/ +static int vdbeSorterSetupMerge(VdbeSorter *pSorter){ + int rc; /* Return code */ + SortSubtask *pTask0 = &pSorter->aTask[0]; + MergeEngine *pMain = 0; +#if SQLITE_MAX_WORKER_THREADS + sqlite3 *db = pTask0->pSorter->db; + int i; + SorterCompare xCompare = vdbeSorterGetCompare(pSorter); + for(i=0; inTask; i++){ + pSorter->aTask[i].xCompare = xCompare; + } +#endif + + rc = vdbeSorterMergeTreeBuild(pSorter, &pMain); + if( rc==SQLITE_OK ){ +#if SQLITE_MAX_WORKER_THREADS + assert( pSorter->bUseThreads==0 || pSorter->nTask>1 ); + if( pSorter->bUseThreads ){ + int iTask; + PmaReader *pReadr = 0; + SortSubtask *pLast = &pSorter->aTask[pSorter->nTask-1]; + rc = vdbeSortAllocUnpacked(pLast); + if( rc==SQLITE_OK ){ + pReadr = (PmaReader*)sqlite3DbMallocZero(db, sizeof(PmaReader)); + pSorter->pReader = pReadr; + if( pReadr==0 ) rc = SQLITE_NOMEM; + } + if( rc==SQLITE_OK ){ + rc = vdbeIncrMergerNew(pLast, pMain, &pReadr->pIncr); + if( rc==SQLITE_OK ){ + vdbeIncrMergerSetThreads(pReadr->pIncr); + for(iTask=0; iTask<(pSorter->nTask-1); iTask++){ + IncrMerger *pIncr; + if( (pIncr = pMain->aReadr[iTask].pIncr) ){ + vdbeIncrMergerSetThreads(pIncr); + assert( pIncr->pTask!=pLast ); + } + } + for(iTask=0; rc==SQLITE_OK && iTasknTask; iTask++){ + /* Check that: + ** + ** a) The incremental merge object is configured to use the + ** right task, and + ** b) If it is using task (nTask-1), it is configured to run + ** in single-threaded mode. This is important, as the + ** root merge (INCRINIT_ROOT) will be using the same task + ** object. + */ + PmaReader *p = &pMain->aReadr[iTask]; + assert( p->pIncr==0 || ( + (p->pIncr->pTask==&pSorter->aTask[iTask]) /* a */ + && (iTask!=pSorter->nTask-1 || p->pIncr->bUseThread==0) /* b */ + )); + rc = vdbePmaReaderIncrInit(p, INCRINIT_TASK); + } + } + pMain = 0; + } + if( rc==SQLITE_OK ){ + rc = vdbePmaReaderIncrMergeInit(pReadr, INCRINIT_ROOT); + } + }else +#endif + { + rc = vdbeMergeEngineInit(pTask0, pMain, INCRINIT_NORMAL); + pSorter->pMerger = pMain; + pMain = 0; + } + } + + if( rc!=SQLITE_OK ){ + vdbeMergeEngineFree(pMain); + } + return rc; +} + + +/* +** Once the sorter has been populated by calls to sqlite3VdbeSorterWrite, +** this function is called to prepare for iterating through the records +** in sorted order. +*/ +SQLITE_PRIVATE int sqlite3VdbeSorterRewind(const VdbeCursor *pCsr, int *pbEof){ + VdbeSorter *pSorter; + int rc = SQLITE_OK; /* Return code */ + + assert( pCsr->eCurType==CURTYPE_SORTER ); + pSorter = pCsr->uc.pSorter; assert( pSorter ); /* If no data has been written to disk, then do not do so now. Instead, ** sort the VdbeSorter.pRecord list. The vdbe layer will read data directly ** from the in-memory list. */ - if( pSorter->nPMA==0 ){ - *pbEof = !pSorter->pRecord; - assert( pSorter->aTree==0 ); - return vdbeSorterSort(pCsr); - } - - /* Write the current in-memory list to a PMA. */ - rc = vdbeSorterListToPMA(db, pCsr); - if( rc!=SQLITE_OK ) return rc; - - /* Allocate space for aIter[] and aTree[]. */ - nIter = pSorter->nPMA; - if( nIter>SORTER_MAX_MERGE_COUNT ) nIter = SORTER_MAX_MERGE_COUNT; - assert( nIter>0 ); - while( NaIter = (VdbeSorterIter *)sqlite3DbMallocZero(db, nByte); - if( !pSorter->aIter ) return SQLITE_NOMEM; - pSorter->aTree = (int *)&pSorter->aIter[N]; - pSorter->nTree = N; - - do { - int iNew; /* Index of new, merged, PMA */ - - for(iNew=0; - rc==SQLITE_OK && iNew*SORTER_MAX_MERGE_COUNTnPMA; - iNew++ - ){ - int rc2; /* Return code from fileWriterFinish() */ - FileWriter writer; /* Object used to write to disk */ - i64 nWrite; /* Number of bytes in new PMA */ - - memset(&writer, 0, sizeof(FileWriter)); - - /* If there are SORTER_MAX_MERGE_COUNT or less PMAs in file pTemp1, - ** initialize an iterator for each of them and break out of the loop. - ** These iterators will be incrementally merged as the VDBE layer calls - ** sqlite3VdbeSorterNext(). - ** - ** Otherwise, if pTemp1 contains more than SORTER_MAX_MERGE_COUNT PMAs, - ** initialize interators for SORTER_MAX_MERGE_COUNT of them. These PMAs - ** are merged into a single PMA that is written to file pTemp2. - */ - rc = vdbeSorterInitMerge(db, pCsr, &nWrite); - assert( rc!=SQLITE_OK || pSorter->aIter[ pSorter->aTree[1] ].pFile ); - if( rc!=SQLITE_OK || pSorter->nPMA<=SORTER_MAX_MERGE_COUNT ){ - break; - } - - /* Open the second temp file, if it is not already open. */ - if( pTemp2==0 ){ - assert( iWrite2==0 ); - rc = vdbeSorterOpenTempFile(db, &pTemp2); - } - - if( rc==SQLITE_OK ){ - int bEof = 0; - fileWriterInit(db, pTemp2, &writer, iWrite2); - fileWriterWriteVarint(&writer, nWrite); - while( rc==SQLITE_OK && bEof==0 ){ - VdbeSorterIter *pIter = &pSorter->aIter[ pSorter->aTree[1] ]; - assert( pIter->pFile ); - - fileWriterWriteVarint(&writer, pIter->nKey); - fileWriterWrite(&writer, pIter->aKey, pIter->nKey); - rc = sqlite3VdbeSorterNext(db, pCsr, &bEof); - } - rc2 = fileWriterFinish(db, &writer, &iWrite2); - if( rc==SQLITE_OK ) rc = rc2; - } - } - - if( pSorter->nPMA<=SORTER_MAX_MERGE_COUNT ){ - break; + if( pSorter->bUsePMA==0 ){ + if( pSorter->list.pList ){ + *pbEof = 0; + rc = vdbeSorterSort(&pSorter->aTask[0], &pSorter->list); }else{ - sqlite3_file *pTmp = pSorter->pTemp1; - pSorter->nPMA = iNew; - pSorter->pTemp1 = pTemp2; - pTemp2 = pTmp; - pSorter->iWriteOff = iWrite2; - pSorter->iReadOff = 0; - iWrite2 = 0; + *pbEof = 1; } - }while( rc==SQLITE_OK ); - - if( pTemp2 ){ - sqlite3OsCloseFree(pTemp2); + return rc; } - *pbEof = (pSorter->aIter[pSorter->aTree[1]].pFile==0); + + /* Write the current in-memory list to a PMA. When the VdbeSorterWrite() + ** function flushes the contents of memory to disk, it immediately always + ** creates a new list consisting of a single key immediately afterwards. + ** So the list is never empty at this point. */ + assert( pSorter->list.pList ); + rc = vdbeSorterFlushPMA(pSorter); + + /* Join all threads */ + rc = vdbeSorterJoinAll(pSorter, rc); + + vdbeSorterRewindDebug("rewind"); + + /* Assuming no errors have occurred, set up a merger structure to + ** incrementally read and merge all remaining PMAs. */ + assert( pSorter->pReader==0 ); + if( rc==SQLITE_OK ){ + rc = vdbeSorterSetupMerge(pSorter); + *pbEof = 0; + } + + vdbeSorterRewindDebug("rewinddone"); return rc; } @@ -75342,66 +83583,33 @@ SQLITE_PRIVATE int sqlite3VdbeSorterRewind(sqlite3 *db, const VdbeCursor *pCsr, ** Advance to the next element in the sorter. */ SQLITE_PRIVATE int sqlite3VdbeSorterNext(sqlite3 *db, const VdbeCursor *pCsr, int *pbEof){ - VdbeSorter *pSorter = pCsr->pSorter; + VdbeSorter *pSorter; int rc; /* Return code */ - if( pSorter->aTree ){ - int iPrev = pSorter->aTree[1];/* Index of iterator to advance */ - rc = vdbeSorterIterNext(db, &pSorter->aIter[iPrev]); - if( rc==SQLITE_OK ){ - int i; /* Index of aTree[] to recalculate */ - VdbeSorterIter *pIter1; /* First iterator to compare */ - VdbeSorterIter *pIter2; /* Second iterator to compare */ - u8 *pKey2; /* To pIter2->aKey, or 0 if record cached */ - - /* Find the first two iterators to compare. The one that was just - ** advanced (iPrev) and the one next to it in the array. */ - pIter1 = &pSorter->aIter[(iPrev & 0xFFFE)]; - pIter2 = &pSorter->aIter[(iPrev | 0x0001)]; - pKey2 = pIter2->aKey; - - for(i=(pSorter->nTree+iPrev)/2; i>0; i=i/2){ - /* Compare pIter1 and pIter2. Store the result in variable iRes. */ - int iRes; - if( pIter1->pFile==0 ){ - iRes = +1; - }else if( pIter2->pFile==0 ){ - iRes = -1; - }else{ - vdbeSorterCompare(pCsr, 0, - pIter1->aKey, pIter1->nKey, pKey2, pIter2->nKey, &iRes - ); - } - - /* If pIter1 contained the smaller value, set aTree[i] to its index. - ** Then set pIter2 to the next iterator to compare to pIter1. In this - ** case there is no cache of pIter2 in pSorter->pUnpacked, so set - ** pKey2 to point to the record belonging to pIter2. - ** - ** Alternatively, if pIter2 contains the smaller of the two values, - ** set aTree[i] to its index and update pIter1. If vdbeSorterCompare() - ** was actually called above, then pSorter->pUnpacked now contains - ** a value equivalent to pIter2. So set pKey2 to NULL to prevent - ** vdbeSorterCompare() from decoding pIter2 again. */ - if( iRes<=0 ){ - pSorter->aTree[i] = (int)(pIter1 - pSorter->aIter); - pIter2 = &pSorter->aIter[ pSorter->aTree[i ^ 0x0001] ]; - pKey2 = pIter2->aKey; - }else{ - if( pIter1->pFile ) pKey2 = 0; - pSorter->aTree[i] = (int)(pIter2 - pSorter->aIter); - pIter1 = &pSorter->aIter[ pSorter->aTree[i ^ 0x0001] ]; - } - - } - *pbEof = (pSorter->aIter[pSorter->aTree[1]].pFile==0); + assert( pCsr->eCurType==CURTYPE_SORTER ); + pSorter = pCsr->uc.pSorter; + assert( pSorter->bUsePMA || (pSorter->pReader==0 && pSorter->pMerger==0) ); + if( pSorter->bUsePMA ){ + assert( pSorter->pReader==0 || pSorter->pMerger==0 ); + assert( pSorter->bUseThreads==0 || pSorter->pReader ); + assert( pSorter->bUseThreads==1 || pSorter->pMerger ); +#if SQLITE_MAX_WORKER_THREADS>0 + if( pSorter->bUseThreads ){ + rc = vdbePmaReaderNext(pSorter->pReader); + *pbEof = (pSorter->pReader->pFd==0); + }else +#endif + /*if( !pSorter->bUseThreads )*/ { + assert( pSorter->pMerger!=0 ); + assert( pSorter->pMerger->pTask==(&pSorter->aTask[0]) ); + rc = vdbeMergeEngineStep(pSorter->pMerger, pbEof); } }else{ - SorterRecord *pFree = pSorter->pRecord; - pSorter->pRecord = pFree->pNext; - pFree->pNext = 0; - vdbeSorterRecordFree(db, pFree); - *pbEof = !pSorter->pRecord; + SorterRecord *pFree = pSorter->list.pList; + pSorter->list.pList = pFree->u.pNext; + pFree->u.pNext = 0; + if( pSorter->list.aMemory==0 ) vdbeSorterRecordFree(db, pFree); + *pbEof = !pSorter->list.pList; rc = SQLITE_OK; } return rc; @@ -75416,14 +83624,21 @@ static void *vdbeSorterRowkey( int *pnKey /* OUT: Size of current key in bytes */ ){ void *pKey; - if( pSorter->aTree ){ - VdbeSorterIter *pIter; - pIter = &pSorter->aIter[ pSorter->aTree[1] ]; - *pnKey = pIter->nKey; - pKey = pIter->aKey; + if( pSorter->bUsePMA ){ + PmaReader *pReader; +#if SQLITE_MAX_WORKER_THREADS>0 + if( pSorter->bUseThreads ){ + pReader = pSorter->pReader; + }else +#endif + /*if( !pSorter->bUseThreads )*/{ + pReader = &pSorter->pMerger->aReadr[pSorter->pMerger->aTree[1]]; + } + *pnKey = pReader->nKey; + pKey = pReader->aKey; }else{ - *pnKey = pSorter->pRecord->nVal; - pKey = pSorter->pRecord->pVal; + *pnKey = pSorter->list.pList->nVal; + pKey = SRVAL(pSorter->list.pList); } return pKey; } @@ -75432,11 +83647,13 @@ static void *vdbeSorterRowkey( ** Copy the current sorter key into the memory cell pOut. */ SQLITE_PRIVATE int sqlite3VdbeSorterRowkey(const VdbeCursor *pCsr, Mem *pOut){ - VdbeSorter *pSorter = pCsr->pSorter; + VdbeSorter *pSorter; void *pKey; int nKey; /* Sorter key to copy into pOut */ + assert( pCsr->eCurType==CURTYPE_SORTER ); + pSorter = pCsr->uc.pSorter; pKey = vdbeSorterRowkey(pSorter, &nKey); - if( sqlite3VdbeMemGrow(pOut, nKey, 0) ){ + if( sqlite3VdbeMemClearAndResize(pOut, nKey) ){ return SQLITE_NOMEM; } pOut->n = nKey; @@ -75451,22 +83668,52 @@ SQLITE_PRIVATE int sqlite3VdbeSorterRowkey(const VdbeCursor *pCsr, Mem *pOut){ ** passed as the first argument currently points to. For the purposes of ** the comparison, ignore the rowid field at the end of each record. ** +** If the sorter cursor key contains any NULL values, consider it to be +** less than pVal. Even if pVal also contains NULL values. +** ** If an error occurs, return an SQLite error code (i.e. SQLITE_NOMEM). ** Otherwise, set *pRes to a negative, zero or positive value if the ** key in pVal is smaller than, equal to or larger than the current sorter ** key. +** +** This routine forms the core of the OP_SorterCompare opcode, which in +** turn is used to verify uniqueness when constructing a UNIQUE INDEX. */ SQLITE_PRIVATE int sqlite3VdbeSorterCompare( const VdbeCursor *pCsr, /* Sorter cursor */ Mem *pVal, /* Value to compare to current sorter key */ - int nIgnore, /* Ignore this many fields at the end */ + int nKeyCol, /* Compare this many columns */ int *pRes /* OUT: Result of comparison */ ){ - VdbeSorter *pSorter = pCsr->pSorter; + VdbeSorter *pSorter; + UnpackedRecord *r2; + KeyInfo *pKeyInfo; + int i; void *pKey; int nKey; /* Sorter key to compare pVal with */ + assert( pCsr->eCurType==CURTYPE_SORTER ); + pSorter = pCsr->uc.pSorter; + r2 = pSorter->pUnpacked; + pKeyInfo = pCsr->pKeyInfo; + if( r2==0 ){ + char *p; + r2 = pSorter->pUnpacked = sqlite3VdbeAllocUnpackedRecord(pKeyInfo,0,0,&p); + assert( pSorter->pUnpacked==(UnpackedRecord*)p ); + if( r2==0 ) return SQLITE_NOMEM; + r2->nField = nKeyCol; + } + assert( r2->nField==nKeyCol ); + pKey = vdbeSorterRowkey(pSorter, &nKey); - vdbeSorterCompare(pCsr, nIgnore, pVal->z, pVal->n, pKey, nKey, pRes); + sqlite3VdbeRecordUnpack(pKeyInfo, nKey, pKey, r2); + for(i=0; iaMem[i].flags & MEM_Null ){ + *pRes = -1; + return SQLITE_OK; + } + } + + *pRes = sqlite3VdbeRecordCompare(pVal->n, pVal->z, r2); return SQLITE_OK; } @@ -75499,6 +83746,7 @@ SQLITE_PRIVATE int sqlite3VdbeSorterCompare( ** 2) The sqlite3JournalCreate() function is called. */ #ifdef SQLITE_ENABLE_ATOMIC_WRITE +/* #include "sqliteInt.h" */ /* @@ -75746,6 +83994,7 @@ SQLITE_PRIVATE int sqlite3JournalSize(sqlite3_vfs *pVfs){ ** The in-memory rollback journal is used to journal transactions for ** ":memory:" databases and when the journal_mode=MEMORY pragma is used. */ +/* #include "sqliteInt.h" */ /* Forward references to internal structures */ typedef struct MemJournal MemJournal; @@ -75757,7 +84006,7 @@ typedef struct FileChunk FileChunk; ** ** The size chosen is a little less than a power of two. That way, ** the FileChunk object will have a size that almost exactly fills -** a power-of-two allocation. This mimimizes wasted space in power-of-two +** a power-of-two allocation. This minimizes wasted space in power-of-two ** memory allocators. */ #define JOURNAL_CHUNKSIZE ((int)(1024-sizeof(FileChunk*))) @@ -76001,13 +84250,14 @@ SQLITE_PRIVATE int sqlite3MemJournalSize(void){ ** This file contains routines used for walking the parser tree for ** an SQL statement. */ +/* #include "sqliteInt.h" */ /* #include */ /* #include */ /* ** Walk an expression tree. Invoke the callback once for each node -** of the expression, while decending. (In other words, the callback +** of the expression, while descending. (In other words, the callback ** is invoked before visiting children.) ** ** The return value from the callback should be one of the WRC_* @@ -76093,6 +84343,11 @@ SQLITE_PRIVATE int sqlite3WalkSelectFrom(Walker *pWalker, Select *p){ if( sqlite3WalkSelect(pWalker, pItem->pSelect) ){ return WRC_Abort; } + if( pItem->fg.isTabFunc + && sqlite3WalkExprList(pWalker, pItem->u1.pFuncArg) + ){ + return WRC_Abort; + } } } return WRC_Continue; @@ -76159,6 +84414,7 @@ SQLITE_PRIVATE int sqlite3WalkSelect(Walker *pWalker, Select *p){ ** resolve all identifiers by associating them with a particular ** table and column. */ +/* #include "sqliteInt.h" */ /* #include */ /* #include */ @@ -76172,7 +84428,7 @@ SQLITE_PRIVATE int sqlite3WalkSelect(Walker *pWalker, Select *p){ ** is a helper function - a callback for the tree walker. */ static int incrAggDepth(Walker *pWalker, Expr *pExpr){ - if( pExpr->op==TK_AGG_FUNCTION ) pExpr->op2 += pWalker->u.i; + if( pExpr->op==TK_AGG_FUNCTION ) pExpr->op2 += pWalker->u.n; return WRC_Continue; } static void incrAggFunctionDepth(Expr *pExpr, int N){ @@ -76180,7 +84436,7 @@ static void incrAggFunctionDepth(Expr *pExpr, int N){ Walker w; memset(&w, 0, sizeof(w)); w.xExprCallback = incrAggDepth; - w.u.i = N; + w.u.n = N; sqlite3WalkExpr(&w, pExpr); } } @@ -76189,30 +84445,6 @@ static void incrAggFunctionDepth(Expr *pExpr, int N){ ** Turn the pExpr expression into an alias for the iCol-th column of the ** result set in pEList. ** -** If the result set column is a simple column reference, then this routine -** makes an exact copy. But for any other kind of expression, this -** routine make a copy of the result set column as the argument to the -** TK_AS operator. The TK_AS operator causes the expression to be -** evaluated just once and then reused for each alias. -** -** The reason for suppressing the TK_AS term when the expression is a simple -** column reference is so that the column reference will be recognized as -** usable by indices within the WHERE clause processing logic. -** -** The TK_AS operator is inhibited if zType[0]=='G'. This means -** that in a GROUP BY clause, the expression is evaluated twice. Hence: -** -** SELECT random()%5 AS x, count(*) FROM tab GROUP BY x -** -** Is equivalent to: -** -** SELECT random()%5 AS x, count(*) FROM tab GROUP BY random()%5 -** -** The result of random()%5 in the GROUP BY clause is probably different -** from the result in the result-set. On the other hand Standard SQL does -** not allow the GROUP BY clause to contain references to result-set columns. -** So this should never come up in well-formed queries. -** ** If the reference is followed by a COLLATE operator, then make sure ** the COLLATE operator is preserved. For example: ** @@ -76223,7 +84455,7 @@ static void incrAggFunctionDepth(Expr *pExpr, int N){ ** SELECT a+b, c+d FROM t1 ORDER BY (a+b) COLLATE nocase; ** ** The nSubquery parameter specifies how many levels of subquery the -** alias is removed from the original expression. The usually value is +** alias is removed from the original expression. The usual value is ** zero but it might be more if the alias is contained within a subquery ** of the original expression. The Expr.op2 field of TK_AGG_FUNCTION ** structures must be increased by the nSubquery amount. @@ -76243,23 +84475,14 @@ static void resolveAlias( assert( iCol>=0 && iColnExpr ); pOrig = pEList->a[iCol].pExpr; assert( pOrig!=0 ); - assert( pOrig->flags & EP_Resolved ); db = pParse->db; pDup = sqlite3ExprDup(db, pOrig, 0); if( pDup==0 ) return; - if( pOrig->op!=TK_COLUMN && zType[0]!='G' ){ - incrAggFunctionDepth(pDup, nSubquery); - pDup = sqlite3PExpr(pParse, TK_AS, pDup, 0, 0); - if( pDup==0 ) return; - ExprSetProperty(pDup, EP_Skip); - if( pEList->a[iCol].u.x.iAlias==0 ){ - pEList->a[iCol].u.x.iAlias = (u16)(++pParse->nAlias); - } - pDup->iTable = pEList->a[iCol].u.x.iAlias; - } + if( zType[0]!='G' ) incrAggFunctionDepth(pDup, nSubquery); if( pExpr->op==TK_COLLATE ){ pDup = sqlite3ExprAddCollateString(pParse, pDup, pExpr->u.zToken); } + ExprSetProperty(pDup, EP_Alias); /* Before calling sqlite3ExprDelete(), set the EP_Static flag. This ** prevents ExprDelete() from deleting the Expr structure itself, @@ -76391,9 +84614,10 @@ static int lookupName( testcase( pNC->ncFlags & NC_PartIdx ); testcase( pNC->ncFlags & NC_IsCheck ); if( (pNC->ncFlags & (NC_PartIdx|NC_IsCheck))!=0 ){ - /* Silently ignore database qualifiers inside CHECK constraints and partial - ** indices. Do not raise errors because that might break legacy and - ** because it does not hurt anything to just ignore the database name. */ + /* Silently ignore database qualifiers inside CHECK constraints and + ** partial indices. Do not raise errors because that might break + ** legacy and because it does not hurt anything to just ignore the + ** database name. */ zDb = 0; }else{ for(i=0; inDb; i++){ @@ -76450,7 +84674,7 @@ static int lookupName( ** USING clause, then skip this match. */ if( cnt==1 ){ - if( pItem->jointype & JT_NATURAL ) continue; + if( pItem->fg.jointype & JT_NATURAL ) continue; if( nameInUsingClause(pItem->pUsing, zCol) ) continue; } cnt++; @@ -76464,6 +84688,11 @@ static int lookupName( if( pMatch ){ pExpr->iTable = pMatch->iCursor; pExpr->pTab = pMatch->pTab; + /* RIGHT JOIN not (yet) supported */ + assert( (pMatch->fg.jointype & JT_RIGHT)==0 ); + if( (pMatch->fg.jointype & JT_LEFT)!=0 ){ + ExprSetProperty(pExpr, EP_CanBeNull); + } pSchema = pExpr->pTab->pSchema; } } /* if( pSrcList ) */ @@ -76497,9 +84726,8 @@ static int lookupName( break; } } - if( iCol>=pTab->nCol && sqlite3IsRowid(zCol) && HasRowid(pTab) ){ - /* IMP: R-24309-18625 */ - /* IMP: R-44911-55124 */ + if( iCol>=pTab->nCol && sqlite3IsRowid(zCol) && VisibleRowid(pTab) ){ + /* IMP: R-51414-32910 */ iCol = -1; } if( iColnCol ){ @@ -76526,10 +84754,15 @@ static int lookupName( /* ** Perhaps the name is a reference to the ROWID */ - if( cnt==0 && cntTab==1 && pMatch && sqlite3IsRowid(zCol) - && HasRowid(pMatch->pTab) ){ + if( cnt==0 + && cntTab==1 + && pMatch + && (pNC->ncFlags & NC_IdxExpr)==0 + && sqlite3IsRowid(zCol) + && VisibleRowid(pMatch->pTab) + ){ cnt = 1; - pExpr->iColumn = -1; /* IMP: R-44911-55124 */ + pExpr->iColumn = -1; pExpr->affinity = SQLITE_AFF_INTEGER; } @@ -76546,9 +84779,9 @@ static int lookupName( ** resolved by the time the WHERE clause is resolved. ** ** The ability to use an output result-set column in the WHERE, GROUP BY, - ** or HAVING clauses, or as part of a larger expression in the ORDRE BY + ** or HAVING clauses, or as part of a larger expression in the ORDER BY ** clause is not standard SQL. This is a (goofy) SQLite extension, that - ** is supported for backwards compatibility only. TO DO: Issue a warning + ** is supported for backwards compatibility only. Hence, we issue a warning ** on sqlite3_log() whenever the capability is used. */ if( (pEList = pNC->pEList)!=0 @@ -76645,7 +84878,7 @@ static int lookupName( lookupname_end: if( cnt==1 ){ assert( pNC!=0 ); - if( pExpr->op!=TK_AS ){ + if( !ExprHasProperty(pExpr, EP_Alias) ){ sqlite3AuthRead(pParse, pExpr, pSchema, pNC->pSrcList); } /* Increment the nRef value on all name contexts from TopNC up to @@ -76686,36 +84919,25 @@ SQLITE_PRIVATE Expr *sqlite3CreateColumnExpr(sqlite3 *db, SrcList *pSrc, int iSr } /* -** Report an error that an expression is not valid for a partial index WHERE -** clause. +** Report an error that an expression is not valid for some set of +** pNC->ncFlags values determined by validMask. */ -static void notValidPartIdxWhere( +static void notValid( Parse *pParse, /* Leave error message here */ NameContext *pNC, /* The name context */ - const char *zMsg /* Type of error */ + const char *zMsg, /* Type of error */ + int validMask /* Set of contexts for which prohibited */ ){ - if( (pNC->ncFlags & NC_PartIdx)!=0 ){ - sqlite3ErrorMsg(pParse, "%s prohibited in partial index WHERE clauses", - zMsg); - } -} - + assert( (validMask&~(NC_IsCheck|NC_PartIdx|NC_IdxExpr))==0 ); + if( (pNC->ncFlags & validMask)!=0 ){ + const char *zIn = "partial index WHERE clauses"; + if( pNC->ncFlags & NC_IdxExpr ) zIn = "index expressions"; #ifndef SQLITE_OMIT_CHECK -/* -** Report an error that an expression is not valid for a CHECK constraint. -*/ -static void notValidCheckConstraint( - Parse *pParse, /* Leave error message here */ - NameContext *pNC, /* The name context */ - const char *zMsg /* Type of error */ -){ - if( (pNC->ncFlags & NC_IsCheck)!=0 ){ - sqlite3ErrorMsg(pParse,"%s prohibited in CHECK constraints", zMsg); + else if( pNC->ncFlags & NC_IsCheck ) zIn = "CHECK constraints"; +#endif + sqlite3ErrorMsg(pParse, "%s prohibited in %s", zMsg, zIn); } } -#else -# define notValidCheckConstraint(P,N,M) -#endif /* ** Expression p should encode a floating point value between 1.0 and 0.0. @@ -76728,7 +84950,7 @@ static int exprProbability(Expr *p){ sqlite3AtoF(p->u.zToken, &r, sqlite3Strlen30(p->u.zToken), SQLITE_UTF8); assert( r>=0.0 ); if( r>1.0 ) return -1; - return (int)(r*1000.0); + return (int)(r*134217728.0); } /* @@ -76781,7 +85003,8 @@ static int resolveExprStep(Walker *pWalker, Expr *pExpr){ pExpr->affinity = SQLITE_AFF_INTEGER; break; } -#endif /* defined(SQLITE_ENABLE_UPDATE_DELETE_LIMIT) && !defined(SQLITE_OMIT_SUBQUERY) */ +#endif /* defined(SQLITE_ENABLE_UPDATE_DELETE_LIMIT) + && !defined(SQLITE_OMIT_SUBQUERY) */ /* A lone identifier is the name of a column. */ @@ -76799,6 +85022,8 @@ static int resolveExprStep(Walker *pWalker, Expr *pExpr){ Expr *pRight; /* if( pSrcList==0 ) break; */ + notValid(pParse, pNC, "the \".\" operator", NC_IdxExpr); + /*notValid(pParse, pNC, "the \".\" operator", NC_PartIdx|NC_IsCheck, 1);*/ pRight = pExpr->pRight; if( pRight->op==TK_ID ){ zDb = 0; @@ -76828,7 +85053,7 @@ static int resolveExprStep(Walker *pWalker, Expr *pExpr){ u8 enc = ENC(pParse->db); /* The database encoding */ assert( !ExprHasProperty(pExpr, EP_xIsSelect) ); - notValidPartIdxWhere(pParse, pNC, "functions"); + notValid(pParse, pNC, "functions", NC_PartIdx); zId = pExpr->u.zToken; nId = sqlite3Strlen30(zId); pDef = sqlite3FindFunction(pParse->db, zId, nId, n, enc, 0); @@ -76846,21 +85071,25 @@ static int resolveExprStep(Walker *pWalker, Expr *pExpr){ if( n==2 ){ pExpr->iTable = exprProbability(pList->a[1].pExpr); if( pExpr->iTable<0 ){ - sqlite3ErrorMsg(pParse, "second argument to likelihood() must be a " - "constant between 0.0 and 1.0"); + sqlite3ErrorMsg(pParse, + "second argument to likelihood() must be a " + "constant between 0.0 and 1.0"); pNC->nErr++; } }else{ - /* EVIDENCE-OF: R-61304-29449 The unlikely(X) function is equivalent to - ** likelihood(X, 0.0625). - ** EVIDENCE-OF: R-01283-11636 The unlikely(X) function is short-hand for - ** likelihood(X,0.0625). */ - pExpr->iTable = 62; /* TUNING: Default 2nd arg to unlikely() is 0.0625 */ + /* EVIDENCE-OF: R-61304-29449 The unlikely(X) function is + ** equivalent to likelihood(X, 0.0625). + ** EVIDENCE-OF: R-01283-11636 The unlikely(X) function is + ** short-hand for likelihood(X,0.0625). + ** EVIDENCE-OF: R-36850-34127 The likely(X) function is short-hand + ** for likelihood(X,0.9375). + ** EVIDENCE-OF: R-53436-40973 The likely(X) function is equivalent + ** to likelihood(X,0.9375). */ + /* TUNING: unlikely() probability is 0.0625. likely() is 0.9375 */ + pExpr->iTable = pDef->zName[0]=='u' ? 8388608 : 125829120; } } - } #ifndef SQLITE_OMIT_AUTHORIZATION - if( pDef ){ auth = sqlite3AuthCheck(pParse, SQLITE_FUNCTION, 0, pDef->zName, 0); if( auth!=SQLITE_OK ){ if( auth==SQLITE_DENY ){ @@ -76871,9 +85100,20 @@ static int resolveExprStep(Walker *pWalker, Expr *pExpr){ pExpr->op = TK_NULL; return WRC_Prune; } - if( pDef->funcFlags & SQLITE_FUNC_CONSTANT ) ExprSetProperty(pExpr,EP_Constant); - } #endif + if( pDef->funcFlags & (SQLITE_FUNC_CONSTANT|SQLITE_FUNC_SLOCHNG) ){ + /* For the purposes of the EP_ConstFunc flag, date and time + ** functions and other functions that change slowly are considered + ** constant because they are constant for the duration of one query */ + ExprSetProperty(pExpr,EP_ConstFunc); + } + if( (pDef->funcFlags & SQLITE_FUNC_CONSTANT)==0 ){ + /* Date/time functions that use 'now', and other functions like + ** sqlite_version() that might change over time cannot be used + ** in an index. */ + notValid(pParse, pNC, "non-deterministic functions", NC_IdxExpr); + } + } if( is_agg && (pNC->ncFlags & NC_AllowAgg)==0 ){ sqlite3ErrorMsg(pParse, "misuse of aggregate function %.*s()", nId,zId); pNC->nErr++; @@ -76896,7 +85136,13 @@ static int resolveExprStep(Walker *pWalker, Expr *pExpr){ pExpr->op2++; pNC2 = pNC2->pNext; } - if( pNC2 ) pNC2->ncFlags |= NC_HasAgg; + assert( pDef!=0 ); + if( pNC2 ){ + assert( SQLITE_FUNC_MINMAX==NC_MinMaxAgg ); + testcase( (pDef->funcFlags & SQLITE_FUNC_MINMAX)!=0 ); + pNC2->ncFlags |= NC_HasAgg | (pDef->funcFlags & SQLITE_FUNC_MINMAX); + + } pNC->ncFlags |= NC_AllowAgg; } /* FIX ME: Compute pExpr->affinity based on the expected return @@ -76912,8 +85158,7 @@ static int resolveExprStep(Walker *pWalker, Expr *pExpr){ testcase( pExpr->op==TK_IN ); if( ExprHasProperty(pExpr, EP_xIsSelect) ){ int nRef = pNC->nRef; - notValidCheckConstraint(pParse, pNC, "subqueries"); - notValidPartIdxWhere(pParse, pNC, "subqueries"); + notValid(pParse, pNC, "subqueries", NC_IsCheck|NC_PartIdx|NC_IdxExpr); sqlite3WalkSelect(pWalker, pExpr->x.pSelect); assert( pNC->nRef>=nRef ); if( nRef!=pNC->nRef ){ @@ -76923,8 +85168,7 @@ static int resolveExprStep(Walker *pWalker, Expr *pExpr){ break; } case TK_VARIABLE: { - notValidCheckConstraint(pParse, pNC, "parameters"); - notValidPartIdxWhere(pParse, pNC, "parameters"); + notValid(pParse, pNC, "parameters", NC_IsCheck|NC_PartIdx|NC_IdxExpr); break; } } @@ -77118,9 +85362,11 @@ static int resolveCompoundOrderBy( if( pItem->pExpr==pE ){ pItem->pExpr = pNew; }else{ - assert( pItem->pExpr->op==TK_COLLATE ); - assert( pItem->pExpr->pLeft==pE ); - pItem->pExpr->pLeft = pNew; + Expr *pParent = pItem->pExpr; + assert( pParent->op==TK_COLLATE ); + while( pParent->pLeft->op==TK_COLLATE ) pParent = pParent->pLeft; + assert( pParent->pLeft==pE ); + pParent->pLeft = pNew; } sqlite3ExprDelete(db, pE); pItem->u.x.iOrderByCol = (u16)iCol; @@ -77177,7 +85423,8 @@ SQLITE_PRIVATE int sqlite3ResolveOrderGroupBy( resolveOutOfRangeError(pParse, zType, i+1, pEList->nExpr); return 1; } - resolveAlias(pParse, pEList, pItem->u.x.iOrderByCol-1, pItem->pExpr, zType,0); + resolveAlias(pParse, pEList, pItem->u.x.iOrderByCol-1, pItem->pExpr, + zType,0); } } return 0; @@ -77257,7 +85504,7 @@ static int resolveOrderGroupBy( } /* -** Resolve names in the SELECT statement p and all of its descendents. +** Resolve names in the SELECT statement p and all of its descendants. */ static int resolveSelectStep(Walker *pWalker, Select *p){ NameContext *pOuterNC; /* Context that contains this SELECT */ @@ -77265,7 +85512,6 @@ static int resolveSelectStep(Walker *pWalker, Select *p){ int isCompound; /* True if p is a compound select */ int nCompound; /* Number of compound terms processed so far */ Parse *pParse; /* Parsing context */ - ExprList *pEList; /* Result set expression list */ int i; /* Loop counter */ ExprList *pGroupBy; /* The GROUP BY clause */ Select *pLeftmost; /* Left-most of SELECT of a compound */ @@ -77310,6 +85556,20 @@ static int resolveSelectStep(Walker *pWalker, Select *p){ sqlite3ResolveExprNames(&sNC, p->pOffset) ){ return WRC_Abort; } + + /* If the SF_Converted flags is set, then this Select object was + ** was created by the convertCompoundSelectToSubquery() function. + ** In this case the ORDER BY clause (p->pOrderBy) should be resolved + ** as if it were part of the sub-query, not the parent. This block + ** moves the pOrderBy down to the sub-query. It will be moved back + ** after the names have been resolved. */ + if( p->selFlags & SF_Converted ){ + Select *pSub = p->pSrc->a[0].pSelect; + assert( p->pSrc->nSrc==1 && p->pOrderBy ); + assert( pSub->pPrior && pSub->pOrderBy==0 ); + pSub->pOrderBy = p->pOrderBy; + p->pOrderBy = 0; + } /* Recursively resolve names in all subqueries */ @@ -77324,7 +85584,7 @@ static int resolveSelectStep(Walker *pWalker, Select *p){ ** parent contexts. After resolving references to expressions in ** pItem->pSelect, check if this value has changed. If so, then ** SELECT statement pItem->pSelect must be correlated. Set the - ** pItem->isCorrelated flag if this is the case. */ + ** pItem->fg.isCorrelated flag if this is the case. */ for(pNC=pOuterNC; pNC; pNC=pNC->pNext) nRef += pNC->nRef; if( pItem->zName ) pParse->zAuthContext = pItem->zName; @@ -77333,8 +85593,8 @@ static int resolveSelectStep(Walker *pWalker, Select *p){ if( pParse->nErr || db->mallocFailed ) return WRC_Abort; for(pNC=pOuterNC; pNC; pNC=pNC->pNext) nRef -= pNC->nRef; - assert( pItem->isCorrelated==0 && nRef<=0 ); - pItem->isCorrelated = (nRef!=0); + assert( pItem->fg.isCorrelated==0 && nRef<=0 ); + pItem->fg.isCorrelated = (nRef!=0); } } @@ -77346,14 +85606,7 @@ static int resolveSelectStep(Walker *pWalker, Select *p){ sNC.pNext = pOuterNC; /* Resolve names in the result set. */ - pEList = p->pEList; - assert( pEList!=0 ); - for(i=0; inExpr; i++){ - Expr *pX = pEList->a[i].pExpr; - if( sqlite3ResolveExprNames(&sNC, pX) ){ - return WRC_Abort; - } - } + if( sqlite3ResolveExprListNames(&sNC, p->pEList) ) return WRC_Abort; /* If there are no aggregate functions in the result-set, and no GROUP BY ** expression, do not allow aggregates in any of the other expressions. @@ -77361,7 +85614,8 @@ static int resolveSelectStep(Walker *pWalker, Select *p){ assert( (p->selFlags & SF_Aggregate)==0 ); pGroupBy = p->pGroupBy; if( pGroupBy || (sNC.ncFlags & NC_HasAgg)!=0 ){ - p->selFlags |= SF_Aggregate; + assert( NC_MinMaxAgg==SF_MinMaxAgg ); + p->selFlags |= SF_Aggregate | (sNC.ncFlags&NC_MinMaxAgg); }else{ sNC.ncFlags &= ~NC_AllowAgg; } @@ -77385,18 +85639,46 @@ static int resolveSelectStep(Walker *pWalker, Select *p){ if( sqlite3ResolveExprNames(&sNC, p->pHaving) ) return WRC_Abort; if( sqlite3ResolveExprNames(&sNC, p->pWhere) ) return WRC_Abort; + /* Resolve names in table-valued-function arguments */ + for(i=0; ipSrc->nSrc; i++){ + struct SrcList_item *pItem = &p->pSrc->a[i]; + if( pItem->fg.isTabFunc + && sqlite3ResolveExprListNames(&sNC, pItem->u1.pFuncArg) + ){ + return WRC_Abort; + } + } + /* The ORDER BY and GROUP BY clauses may not refer to terms in ** outer queries */ sNC.pNext = 0; sNC.ncFlags |= NC_AllowAgg; + /* If this is a converted compound query, move the ORDER BY clause from + ** the sub-query back to the parent query. At this point each term + ** within the ORDER BY clause has been transformed to an integer value. + ** These integers will be replaced by copies of the corresponding result + ** set expressions by the call to resolveOrderGroupBy() below. */ + if( p->selFlags & SF_Converted ){ + Select *pSub = p->pSrc->a[0].pSelect; + p->pOrderBy = pSub->pOrderBy; + pSub->pOrderBy = 0; + } + /* Process the ORDER BY clause for singleton SELECT statements. ** The ORDER BY clause for compounds SELECT statements is handled ** below, after all of the result-sets for all of the elements of ** the compound have been resolved. + ** + ** If there is an ORDER BY clause on a term of a compound-select other + ** than the right-most term, then that is a syntax error. But the error + ** is not detected until much later, and so we need to go ahead and + ** resolve those symbols on the incorrect ORDER BY for consistency. */ - if( !isCompound && resolveOrderGroupBy(&sNC, p, p->pOrderBy, "ORDER") ){ + if( isCompound<=nCompound /* Defer right-most ORDER BY of a compound */ + && resolveOrderGroupBy(&sNC, p, p->pOrderBy, "ORDER") + ){ return WRC_Abort; } if( db->mallocFailed ){ @@ -77421,6 +85703,13 @@ static int resolveSelectStep(Walker *pWalker, Select *p){ } } + /* If this is part of a compound SELECT, check that it has the right + ** number of expressions in the select list. */ + if( p->pNext && p->pEList->nExpr!=p->pNext->pEList->nExpr ){ + sqlite3SelectWrongNumTermsError(pParse, p->pNext); + return WRC_Abort; + } + /* Advance to the next term of the compound */ p = p->pPrior; @@ -77489,7 +85778,7 @@ SQLITE_PRIVATE int sqlite3ResolveExprNames( NameContext *pNC, /* Namespace to resolve expressions in. */ Expr *pExpr /* The expression to be analyzed. */ ){ - u8 savedHasAgg; + u16 savedHasAgg; Walker w; if( pExpr==0 ) return 0; @@ -77502,8 +85791,8 @@ SQLITE_PRIVATE int sqlite3ResolveExprNames( pParse->nHeight += pExpr->nHeight; } #endif - savedHasAgg = pNC->ncFlags & NC_HasAgg; - pNC->ncFlags &= ~NC_HasAgg; + savedHasAgg = pNC->ncFlags & (NC_HasAgg|NC_MinMaxAgg); + pNC->ncFlags &= ~(NC_HasAgg|NC_MinMaxAgg); memset(&w, 0, sizeof(w)); w.xExprCallback = resolveExprStep; w.xSelectCallback = resolveSelectStep; @@ -77518,12 +85807,28 @@ SQLITE_PRIVATE int sqlite3ResolveExprNames( } if( pNC->ncFlags & NC_HasAgg ){ ExprSetProperty(pExpr, EP_Agg); - }else if( savedHasAgg ){ - pNC->ncFlags |= NC_HasAgg; } + pNC->ncFlags |= savedHasAgg; return ExprHasProperty(pExpr, EP_Error); } +/* +** Resolve all names for all expression in an expression list. This is +** just like sqlite3ResolveExprNames() except that it works for an expression +** list rather than a single expression. +*/ +SQLITE_PRIVATE int sqlite3ResolveExprListNames( + NameContext *pNC, /* Namespace to resolve expressions in. */ + ExprList *pList /* The expression list to be analyzed. */ +){ + int i; + if( pList ){ + for(i=0; inExpr; i++){ + if( sqlite3ResolveExprNames(pNC, pList->a[i].pExpr) ) return WRC_Abort; + } + } + return WRC_Continue; +} /* ** Resolve all names in all expressions of a SELECT and in all @@ -77567,15 +85872,14 @@ SQLITE_PRIVATE void sqlite3ResolveSelectNames( SQLITE_PRIVATE void sqlite3ResolveSelfReference( Parse *pParse, /* Parsing context */ Table *pTab, /* The table being referenced */ - int type, /* NC_IsCheck or NC_PartIdx */ + int type, /* NC_IsCheck or NC_PartIdx or NC_IdxExpr */ Expr *pExpr, /* Expression to resolve. May be NULL. */ ExprList *pList /* Expression list to resolve. May be NUL. */ ){ SrcList sSrc; /* Fake SrcList for pParse->pNewTable */ NameContext sNC; /* Name context for pParse->pNewTable */ - int i; /* Loop counter */ - assert( type==NC_IsCheck || type==NC_PartIdx ); + assert( type==NC_IsCheck || type==NC_PartIdx || type==NC_IdxExpr ); memset(&sNC, 0, sizeof(sNC)); memset(&sSrc, 0, sizeof(sSrc)); sSrc.nSrc = 1; @@ -77586,13 +85890,7 @@ SQLITE_PRIVATE void sqlite3ResolveSelfReference( sNC.pSrcList = &sSrc; sNC.ncFlags = type; if( sqlite3ResolveExprNames(&sNC, pExpr) ) return; - if( pList ){ - for(i=0; inExpr; i++){ - if( sqlite3ResolveExprNames(&sNC, pList->a[i].pExpr) ){ - return; - } - } - } + if( pList ) sqlite3ResolveExprListNames(&sNC, pList); } /************** End of resolve.c *********************************************/ @@ -77611,6 +85909,7 @@ SQLITE_PRIVATE void sqlite3ResolveSelfReference( ** This file contains routines used for analyzing expressions and ** for generating VDBE code that evaluates expressions in SQLite. */ +/* #include "sqliteInt.h" */ /* ** Return the 'affinity' of the expression pExpr if any. @@ -77620,7 +85919,7 @@ SQLITE_PRIVATE void sqlite3ResolveSelfReference( ** affinity of that column is returned. Otherwise, 0x00 is returned, ** indicating no affinity for the expression. ** -** i.e. the WHERE clause expresssions in the following statements all +** i.e. the WHERE clause expressions in the following statements all ** have an affinity: ** ** CREATE TABLE t1(a); @@ -77631,7 +85930,7 @@ SQLITE_PRIVATE void sqlite3ResolveSelfReference( SQLITE_PRIVATE char sqlite3ExprAffinity(Expr *pExpr){ int op; pExpr = sqlite3ExprSkipCollate(pExpr); - if( pExpr->flags & EP_Generic ) return SQLITE_AFF_NONE; + if( pExpr->flags & EP_Generic ) return 0; op = pExpr->op; if( op==TK_SELECT ){ assert( pExpr->flags&EP_xIsSelect ); @@ -77667,10 +85966,11 @@ SQLITE_PRIVATE char sqlite3ExprAffinity(Expr *pExpr){ SQLITE_PRIVATE Expr *sqlite3ExprAddCollateToken( Parse *pParse, /* Parsing context */ Expr *pExpr, /* Add the "COLLATE" clause to this expression */ - const Token *pCollName /* Name of collating sequence */ + const Token *pCollName, /* Name of collating sequence */ + int dequote /* True to dequote pCollName */ ){ if( pCollName->n>0 ){ - Expr *pNew = sqlite3ExprAlloc(pParse->db, TK_COLLATE, pCollName, 1); + Expr *pNew = sqlite3ExprAlloc(pParse->db, TK_COLLATE, pCollName, dequote); if( pNew ){ pNew->pLeft = pExpr; pNew->flags |= EP_Collate|EP_Skip; @@ -77684,11 +85984,11 @@ SQLITE_PRIVATE Expr *sqlite3ExprAddCollateString(Parse *pParse, Expr *pExpr, con assert( zC!=0 ); s.z = zC; s.n = sqlite3Strlen30(s.z); - return sqlite3ExprAddCollateToken(pParse, pExpr, &s); + return sqlite3ExprAddCollateToken(pParse, pExpr, &s, 0); } /* -** Skip over any TK_COLLATE or TK_AS operators and any unlikely() +** Skip over any TK_COLLATE operators and any unlikely() ** or likelihood() function at the root of an expression. */ SQLITE_PRIVATE Expr *sqlite3ExprSkipCollate(Expr *pExpr){ @@ -77699,7 +85999,7 @@ SQLITE_PRIVATE Expr *sqlite3ExprSkipCollate(Expr *pExpr){ assert( pExpr->op==TK_FUNCTION ); pExpr = pExpr->x.pList->a[0].pExpr; }else{ - assert( pExpr->op==TK_COLLATE || pExpr->op==TK_AS ); + assert( pExpr->op==TK_COLLATE ); pExpr = pExpr->pLeft; } } @@ -77730,9 +86030,9 @@ SQLITE_PRIVATE CollSeq *sqlite3ExprCollSeq(Parse *pParse, Expr *pExpr){ pColl = sqlite3GetCollSeq(pParse, ENC(db), 0, p->u.zToken); break; } - if( p->pTab!=0 - && (op==TK_AGG_COLUMN || op==TK_COLUMN + if( (op==TK_AGG_COLUMN || op==TK_COLUMN || op==TK_REGISTER || op==TK_TRIGGER) + && p->pTab!=0 ){ /* op==TK_REGISTER && p->pTab!=0 happens when pExpr was originally ** a TK_COLUMN but was previously evaluated and cached in a register */ @@ -77744,10 +86044,25 @@ SQLITE_PRIVATE CollSeq *sqlite3ExprCollSeq(Parse *pParse, Expr *pExpr){ break; } if( p->flags & EP_Collate ){ - if( ALWAYS(p->pLeft) && (p->pLeft->flags & EP_Collate)!=0 ){ + if( p->pLeft && (p->pLeft->flags & EP_Collate)!=0 ){ p = p->pLeft; }else{ - p = p->pRight; + Expr *pNext = p->pRight; + /* The Expr.x union is never used at the same time as Expr.pRight */ + assert( p->x.pList==0 || p->pRight==0 ); + /* p->flags holds EP_Collate and p->pLeft->flags does not. And + ** p->x.pSelect cannot. So if p->x.pLeft exists, it must hold at + ** least one EP_Collate. Thus the following two ALWAYS. */ + if( p->x.pList!=0 && ALWAYS(!ExprHasProperty(p, EP_xIsSelect)) ){ + int i; + for(i=0; ALWAYS(ix.pList->nExpr); i++){ + if( ExprHasProperty(p->x.pList->a[i].pExpr, EP_Collate) ){ + pNext = p->x.pList->a[i].pExpr; + break; + } + } + } + p = pNext; } }else{ break; @@ -77773,13 +86088,13 @@ SQLITE_PRIVATE char sqlite3CompareAffinity(Expr *pExpr, char aff2){ if( sqlite3IsNumericAffinity(aff1) || sqlite3IsNumericAffinity(aff2) ){ return SQLITE_AFF_NUMERIC; }else{ - return SQLITE_AFF_NONE; + return SQLITE_AFF_BLOB; } }else if( !aff1 && !aff2 ){ /* Neither side of the comparison is a column. Compare the ** results directly. */ - return SQLITE_AFF_NONE; + return SQLITE_AFF_BLOB; }else{ /* One side is a column, the other is not. Use the columns affinity. */ assert( aff1==0 || aff2==0 ); @@ -77803,7 +86118,7 @@ static char comparisonAffinity(Expr *pExpr){ }else if( ExprHasProperty(pExpr, EP_xIsSelect) ){ aff = sqlite3CompareAffinity(pExpr->x.pSelect->pEList->a[0].pExpr, aff); }else if( !aff ){ - aff = SQLITE_AFF_NONE; + aff = SQLITE_AFF_BLOB; } return aff; } @@ -77817,7 +86132,7 @@ static char comparisonAffinity(Expr *pExpr){ SQLITE_PRIVATE int sqlite3IndexAffinityOk(Expr *pExpr, char idx_affinity){ char aff = comparisonAffinity(pExpr); switch( aff ){ - case SQLITE_AFF_NONE: + case SQLITE_AFF_BLOB: return 1; case SQLITE_AFF_TEXT: return idx_affinity==SQLITE_AFF_TEXT; @@ -77953,6 +86268,9 @@ static void heightOfSelect(Select *p, int *pnHeight){ ** Expr.pSelect member has a height of 1. Any other expression ** has a height equal to the maximum height of any other ** referenced Expr plus one. +** +** Also propagate EP_Propagate flags up from Expr.x.pList to Expr.flags, +** if appropriate. */ static void exprSetHeight(Expr *p){ int nHeight = 0; @@ -77960,8 +86278,9 @@ static void exprSetHeight(Expr *p){ heightOfExpr(p->pRight, &nHeight); if( ExprHasProperty(p, EP_xIsSelect) ){ heightOfSelect(p->x.pSelect, &nHeight); - }else{ + }else if( p->x.pList ){ heightOfExprList(p->x.pList, &nHeight); + p->flags |= EP_Propagate & sqlite3ExprListFlags(p->x.pList); } p->nHeight = nHeight + 1; } @@ -77970,8 +86289,12 @@ static void exprSetHeight(Expr *p){ ** Set the Expr.nHeight variable using the exprSetHeight() function. If ** the height is greater than the maximum allowed expression depth, ** leave an error in pParse. +** +** Also propagate all EP_Propagate flags from the Expr.x.pList into +** Expr.flags. */ -SQLITE_PRIVATE void sqlite3ExprSetHeight(Parse *pParse, Expr *p){ +SQLITE_PRIVATE void sqlite3ExprSetHeightAndFlags(Parse *pParse, Expr *p){ + if( pParse->nErr ) return; exprSetHeight(p); sqlite3ExprCheckHeight(pParse, p->nHeight); } @@ -77985,8 +86308,17 @@ SQLITE_PRIVATE int sqlite3SelectExprHeight(Select *p){ heightOfSelect(p, &nHeight); return nHeight; } -#else - #define exprSetHeight(y) +#else /* ABOVE: Height enforcement enabled. BELOW: Height enforcement off */ +/* +** Propagate all EP_Propagate flags from the Expr.x.pList into +** Expr.flags. +*/ +SQLITE_PRIVATE void sqlite3ExprSetHeightAndFlags(Parse *pParse, Expr *p){ + if( p && p->x.pList && !ExprHasProperty(p, EP_xIsSelect) ){ + p->flags |= EP_Propagate & sqlite3ExprListFlags(p->x.pList); + } +} +#define exprSetHeight(y) #endif /* SQLITE_MAX_EXPR_DEPTH>0 */ /* @@ -77998,7 +86330,7 @@ SQLITE_PRIVATE int sqlite3SelectExprHeight(Select *p){ ** is responsible for making sure the node eventually gets freed. ** ** If dequote is true, then the token (if it exists) is dequoted. -** If dequote is false, no dequoting is performance. The deQuote +** If dequote is false, no dequoting is performed. The deQuote ** parameter is ignored if pToken is NULL or if the token does not ** appear to be quoted. If the quotes were of the form "..." (double-quotes) ** then the EP_DblQuoted flag is set on the expression node. @@ -78088,18 +86420,18 @@ SQLITE_PRIVATE void sqlite3ExprAttachSubtrees( }else{ if( pRight ){ pRoot->pRight = pRight; - pRoot->flags |= EP_Collate & pRight->flags; + pRoot->flags |= EP_Propagate & pRight->flags; } if( pLeft ){ pRoot->pLeft = pLeft; - pRoot->flags |= EP_Collate & pLeft->flags; + pRoot->flags |= EP_Propagate & pLeft->flags; } exprSetHeight(pRoot); } } /* -** Allocate a Expr node which joins as many as two subtrees. +** Allocate an Expr node which joins as many as two subtrees. ** ** One or both of the subtrees can be NULL. Return a pointer to the new ** Expr node. Or, if an OOM error occurs, set pParse->db->mallocFailed, @@ -78113,11 +86445,11 @@ SQLITE_PRIVATE Expr *sqlite3PExpr( const Token *pToken /* Argument token */ ){ Expr *p; - if( op==TK_AND && pLeft && pRight ){ + if( op==TK_AND && pParse->nErr==0 ){ /* Take advantage of short-circuit false optimization for AND */ p = sqlite3ExprAnd(pParse->db, pLeft, pRight); }else{ - p = sqlite3ExprAlloc(pParse->db, op, pToken, 1); + p = sqlite3ExprAlloc(pParse->db, op & TKFLG_MASK, pToken, 1); sqlite3ExprAttachSubtrees(pParse->db, p, pLeft, pRight); } if( p ) { @@ -78192,7 +86524,7 @@ SQLITE_PRIVATE Expr *sqlite3ExprFunction(Parse *pParse, ExprList *pList, Token * } pNew->x.pList = pList; assert( !ExprHasProperty(pNew, EP_xIsSelect) ); - sqlite3ExprSetHeight(pParse, pNew); + sqlite3ExprSetHeightAndFlags(pParse, pNew); return pNew; } @@ -78209,7 +86541,7 @@ SQLITE_PRIVATE Expr *sqlite3ExprFunction(Parse *pParse, ExprList *pList, Token * ** ** Wildcards of the form ":aaa", "@aaa", or "$aaa" are assigned the same number ** as the previous instance of the same wildcard. Or if this is the first -** instance of the wildcard, the next sequenial variable number is +** instance of the wildcard, the next sequential variable number is ** assigned. */ SQLITE_PRIVATE void sqlite3ExprAssignVarNumber(Parse *pParse, Expr *pExpr){ @@ -78344,7 +86676,7 @@ static int exprStructSize(Expr *p){ ** During expression analysis, extra information is computed and moved into ** later parts of teh Expr object and that extra information might get chopped ** off if the expression is reduced. Note also that it does not work to -** make a EXPRDUP_REDUCE copy of a reduced expression. It is only legal +** make an EXPRDUP_REDUCE copy of a reduced expression. It is only legal ** to reduce a pristine expression tree from the parser. The implementation ** of dupedExprStructSize() contain multiple assert() statements that attempt ** to enforce this constraint. @@ -78413,11 +86745,12 @@ static int dupedExprSize(Expr *p, int flags){ ** is not NULL then *pzBuffer is assumed to point to a buffer large enough ** to store the copy of expression p, the copies of p->u.zToken ** (if applicable), and the copies of the p->pLeft and p->pRight expressions, -** if any. Before returning, *pzBuffer is set to the first byte passed the +** if any. Before returning, *pzBuffer is set to the first byte past the ** portion of the buffer copied into by this function. */ static Expr *exprDup(sqlite3 *db, Expr *p, int flags, u8 **pzBuffer){ Expr *pNew = 0; /* Value to return */ + assert( flags==0 || flags==EXPRDUP_REDUCE ); if( p ){ const int isReduced = (flags&EXPRDUP_REDUCE); u8 *zAlloc; @@ -78452,9 +86785,11 @@ static Expr *exprDup(sqlite3 *db, Expr *p, int flags, u8 **pzBuffer){ assert( ExprHasProperty(p, EP_Reduced)==0 ); memcpy(zAlloc, p, nNewSize); }else{ - int nSize = exprStructSize(p); + u32 nSize = (u32)exprStructSize(p); memcpy(zAlloc, p, nSize); - memset(&zAlloc[nSize], 0, EXPR_FULLSIZE-nSize); + if( nSizezDatabase = sqlite3DbStrDup(db, pOldItem->zDatabase); pNewItem->zName = sqlite3DbStrDup(db, pOldItem->zName); pNewItem->zAlias = sqlite3DbStrDup(db, pOldItem->zAlias); - pNewItem->jointype = pOldItem->jointype; + pNewItem->fg = pOldItem->fg; pNewItem->iCursor = pOldItem->iCursor; pNewItem->addrFillSub = pOldItem->addrFillSub; pNewItem->regReturn = pOldItem->regReturn; - pNewItem->isCorrelated = pOldItem->isCorrelated; - pNewItem->viaCoroutine = pOldItem->viaCoroutine; - pNewItem->isRecursive = pOldItem->isRecursive; - pNewItem->zIndex = sqlite3DbStrDup(db, pOldItem->zIndex); - pNewItem->notIndexed = pOldItem->notIndexed; - pNewItem->pIndex = pOldItem->pIndex; + if( pNewItem->fg.isIndexedBy ){ + pNewItem->u1.zIndexedBy = sqlite3DbStrDup(db, pOldItem->u1.zIndexedBy); + } + pNewItem->pIBIndex = pOldItem->pIBIndex; + if( pNewItem->fg.isTabFunc ){ + pNewItem->u1.pFuncArg = + sqlite3ExprListDup(db, pOldItem->u1.pFuncArg, flags); + } pTab = pNewItem->pTab = pOldItem->pTab; if( pTab ){ pTab->nRef++; @@ -78667,6 +87005,7 @@ SQLITE_PRIVATE Select *sqlite3SelectDup(sqlite3 *db, Select *p, int flags){ pNew->addrOpenEphm[1] = -1; pNew->nSelectRow = p->nSelectRow; pNew->pWith = withDup(db, p->pWith); + sqlite3SelectSetName(pNew, p->zSelName); return pNew; } #else @@ -78722,6 +87061,20 @@ no_mem: return 0; } +/* +** Set the sort order for the last element on the given ExprList. +*/ +SQLITE_PRIVATE void sqlite3ExprListSetSortOrder(ExprList *p, int iSortOrder){ + if( p==0 ) return; + assert( SQLITE_SO_UNDEFINED<0 && SQLITE_SO_ASC>=0 && SQLITE_SO_DESC>0 ); + assert( p->nExpr>0 ); + if( iSortOrder<0 ){ + assert( p->a[p->nExpr-1].sortOrder==SQLITE_SO_ASC ); + return; + } + p->a[p->nExpr-1].sortOrder = (u8)iSortOrder; +} + /* ** Set the ExprList.a[].zName element of the most recently added item ** on the expression list. @@ -78807,37 +87160,67 @@ SQLITE_PRIVATE void sqlite3ExprListDelete(sqlite3 *db, ExprList *pList){ } /* -** These routines are Walker callbacks. Walker.u.pi is a pointer -** to an integer. These routines are checking an expression to see -** if it is a constant. Set *Walker.u.pi to 0 if the expression is -** not constant. +** Return the bitwise-OR of all Expr.flags fields in the given +** ExprList. +*/ +SQLITE_PRIVATE u32 sqlite3ExprListFlags(const ExprList *pList){ + int i; + u32 m = 0; + if( pList ){ + for(i=0; inExpr; i++){ + Expr *pExpr = pList->a[i].pExpr; + if( ALWAYS(pExpr) ) m |= pExpr->flags; + } + } + return m; +} + +/* +** These routines are Walker callbacks used to check expressions to +** see if they are "constant" for some definition of constant. The +** Walker.eCode value determines the type of "constant" we are looking +** for. ** ** These callback routines are used to implement the following: ** -** sqlite3ExprIsConstant() -** sqlite3ExprIsConstantNotJoin() -** sqlite3ExprIsConstantOrFunction() +** sqlite3ExprIsConstant() pWalker->eCode==1 +** sqlite3ExprIsConstantNotJoin() pWalker->eCode==2 +** sqlite3ExprIsTableConstant() pWalker->eCode==3 +** sqlite3ExprIsConstantOrFunction() pWalker->eCode==4 or 5 ** +** In all cases, the callbacks set Walker.eCode=0 and abort if the expression +** is found to not be a constant. +** +** The sqlite3ExprIsConstantOrFunction() is used for evaluating expressions +** in a CREATE TABLE statement. The Walker.eCode value is 5 when parsing +** an existing schema and 4 when processing a new statement. A bound +** parameter raises an error for new statements, but is silently converted +** to NULL for existing schemas. This allows sqlite_master tables that +** contain a bound parameter because they were generated by older versions +** of SQLite to be parsed by newer versions of SQLite without raising a +** malformed schema error. */ static int exprNodeIsConstant(Walker *pWalker, Expr *pExpr){ - /* If pWalker->u.i is 3 then any term of the expression that comes from - ** the ON or USING clauses of a join disqualifies the expression + /* If pWalker->eCode is 2 then any term of the expression that comes from + ** the ON or USING clauses of a left join disqualifies the expression ** from being considered constant. */ - if( pWalker->u.i==3 && ExprHasProperty(pExpr, EP_FromJoin) ){ - pWalker->u.i = 0; + if( pWalker->eCode==2 && ExprHasProperty(pExpr, EP_FromJoin) ){ + pWalker->eCode = 0; return WRC_Abort; } switch( pExpr->op ){ /* Consider functions to be constant if all their arguments are constant - ** and either pWalker->u.i==2 or the function as the SQLITE_FUNC_CONST - ** flag. */ + ** and either pWalker->eCode==4 or 5 or the function has the + ** SQLITE_FUNC_CONST flag. */ case TK_FUNCTION: - if( pWalker->u.i==2 || ExprHasProperty(pExpr,EP_Constant) ){ + if( pWalker->eCode>=4 || ExprHasProperty(pExpr,EP_ConstFunc) ){ return WRC_Continue; + }else{ + pWalker->eCode = 0; + return WRC_Abort; } - /* Fall through */ case TK_ID: case TK_COLUMN: case TK_AGG_FUNCTION: @@ -78846,8 +87229,25 @@ static int exprNodeIsConstant(Walker *pWalker, Expr *pExpr){ testcase( pExpr->op==TK_COLUMN ); testcase( pExpr->op==TK_AGG_FUNCTION ); testcase( pExpr->op==TK_AGG_COLUMN ); - pWalker->u.i = 0; - return WRC_Abort; + if( pWalker->eCode==3 && pExpr->iTable==pWalker->u.iCur ){ + return WRC_Continue; + }else{ + pWalker->eCode = 0; + return WRC_Abort; + } + case TK_VARIABLE: + if( pWalker->eCode==5 ){ + /* Silently convert bound parameters that appear inside of CREATE + ** statements into a NULL when parsing the CREATE statement text out + ** of the sqlite_master table */ + pExpr->op = TK_NULL; + }else if( pWalker->eCode==4 ){ + /* A bound parameter in a CREATE statement that originates from + ** sqlite3_prepare() causes an error */ + pWalker->eCode = 0; + return WRC_Abort; + } + /* Fall through */ default: testcase( pExpr->op==TK_SELECT ); /* selectNodeIsConstant will disallow */ testcase( pExpr->op==TK_EXISTS ); /* selectNodeIsConstant will disallow */ @@ -78856,21 +87256,22 @@ static int exprNodeIsConstant(Walker *pWalker, Expr *pExpr){ } static int selectNodeIsConstant(Walker *pWalker, Select *NotUsed){ UNUSED_PARAMETER(NotUsed); - pWalker->u.i = 0; + pWalker->eCode = 0; return WRC_Abort; } -static int exprIsConst(Expr *p, int initFlag){ +static int exprIsConst(Expr *p, int initFlag, int iCur){ Walker w; memset(&w, 0, sizeof(w)); - w.u.i = initFlag; + w.eCode = initFlag; w.xExprCallback = exprNodeIsConstant; w.xSelectCallback = selectNodeIsConstant; + w.u.iCur = iCur; sqlite3WalkExpr(&w, p); - return w.u.i; + return w.eCode; } /* -** Walk an expression tree. Return 1 if the expression is constant +** Walk an expression tree. Return non-zero if the expression is constant ** and 0 if it involves variables or function calls. ** ** For the purposes of this function, a double-quoted string (ex: "abc") @@ -78878,21 +87279,31 @@ static int exprIsConst(Expr *p, int initFlag){ ** a constant. */ SQLITE_PRIVATE int sqlite3ExprIsConstant(Expr *p){ - return exprIsConst(p, 1); + return exprIsConst(p, 1, 0); } /* -** Walk an expression tree. Return 1 if the expression is constant +** Walk an expression tree. Return non-zero if the expression is constant ** that does no originate from the ON or USING clauses of a join. ** Return 0 if it involves variables or function calls or terms from ** an ON or USING clause. */ SQLITE_PRIVATE int sqlite3ExprIsConstantNotJoin(Expr *p){ - return exprIsConst(p, 3); + return exprIsConst(p, 2, 0); } /* -** Walk an expression tree. Return 1 if the expression is constant +** Walk an expression tree. Return non-zero if the expression is constant +** for any single row of the table with cursor iCur. In other words, the +** expression must not refer to any non-deterministic function nor any +** table other than iCur. +*/ +SQLITE_PRIVATE int sqlite3ExprIsTableConstant(Expr *p, int iCur){ + return exprIsConst(p, 3, iCur); +} + +/* +** Walk an expression tree. Return non-zero if the expression is constant ** or a function call with constant arguments. Return and 0 if there ** are any variables. ** @@ -78900,10 +87311,27 @@ SQLITE_PRIVATE int sqlite3ExprIsConstantNotJoin(Expr *p){ ** is considered a variable but a single-quoted string (ex: 'abc') is ** a constant. */ -SQLITE_PRIVATE int sqlite3ExprIsConstantOrFunction(Expr *p){ - return exprIsConst(p, 2); +SQLITE_PRIVATE int sqlite3ExprIsConstantOrFunction(Expr *p, u8 isInit){ + assert( isInit==0 || isInit==1 ); + return exprIsConst(p, 4+isInit, 0); } +#ifdef SQLITE_ENABLE_CURSOR_HINTS +/* +** Walk an expression tree. Return 1 if the expression contains a +** subquery of some kind. Return 0 if there are no subqueries. +*/ +SQLITE_PRIVATE int sqlite3ExprContainsSubquery(Expr *p){ + Walker w; + memset(&w, 0, sizeof(w)); + w.eCode = 1; + w.xExprCallback = sqlite3ExprWalkNoop; + w.xSelectCallback = selectNodeIsConstant; + sqlite3WalkExpr(&w, p); + return w.eCode==0; +} +#endif + /* ** If the expression p codes a constant integer that is small enough ** to fit in a 32-bit integer, return 1 and put the value of the integer @@ -78966,6 +87394,10 @@ SQLITE_PRIVATE int sqlite3ExprCanBeNull(const Expr *p){ case TK_FLOAT: case TK_BLOB: return 0; + case TK_COLUMN: + assert( p->pTab!=0 ); + return ExprHasProperty(p, EP_CanBeNull) || + (p->iColumn>=0 && p->pTab->aCol[p->iColumn].notNull==0); default: return 1; } @@ -78983,7 +87415,7 @@ SQLITE_PRIVATE int sqlite3ExprCanBeNull(const Expr *p){ */ SQLITE_PRIVATE int sqlite3ExprNeedsNoAffinityChange(const Expr *p, char aff){ u8 op; - if( aff==SQLITE_AFF_NONE ) return 1; + if( aff==SQLITE_AFF_BLOB ) return 1; while( p->op==TK_UPLUS || p->op==TK_UMINUS ){ p = p->pLeft; } op = p->op; if( op==TK_REGISTER ) op = p->op2; @@ -79073,6 +87505,40 @@ SQLITE_PRIVATE int sqlite3CodeOnce(Parse *pParse){ return sqlite3VdbeAddOp1(v, OP_Once, pParse->nOnce++); } +/* +** Generate code that checks the left-most column of index table iCur to see if +** it contains any NULL entries. Cause the register at regHasNull to be set +** to a non-NULL value if iCur contains no NULLs. Cause register regHasNull +** to be set to NULL if iCur contains one or more NULL values. +*/ +static void sqlite3SetHasNullFlag(Vdbe *v, int iCur, int regHasNull){ + int addr1; + sqlite3VdbeAddOp2(v, OP_Integer, 0, regHasNull); + addr1 = sqlite3VdbeAddOp1(v, OP_Rewind, iCur); VdbeCoverage(v); + sqlite3VdbeAddOp3(v, OP_Column, iCur, 0, regHasNull); + sqlite3VdbeChangeP5(v, OPFLAG_TYPEOFARG); + VdbeComment((v, "first_entry_in(%d)", iCur)); + sqlite3VdbeJumpHere(v, addr1); +} + + +#ifndef SQLITE_OMIT_SUBQUERY +/* +** The argument is an IN operator with a list (not a subquery) on the +** right-hand side. Return TRUE if that list is constant. +*/ +static int sqlite3InRhsIsConstant(Expr *pIn){ + Expr *pLHS; + int res; + assert( !ExprHasProperty(pIn, EP_xIsSelect) ); + pLHS = pIn->pLeft; + pIn->pLeft = 0; + res = sqlite3ExprIsConstant(pIn); + pIn->pLeft = pLHS; + return res; +} +#endif + /* ** This function is used by the implementation of the IN (...) operator. ** The pX parameter is the expression on the RHS of the IN operator, which @@ -79082,7 +87548,7 @@ SQLITE_PRIVATE int sqlite3CodeOnce(Parse *pParse){ ** be used either to test for membership in the RHS set or to iterate through ** all members of the RHS set, skipping duplicates. ** -** A cursor is opened on the b-tree object that the RHS of the IN operator +** A cursor is opened on the b-tree object that is the RHS of the IN operator ** and pX->iTable is set to the index of that cursor. ** ** The returned value of this function indicates the b-tree type, as follows: @@ -79092,6 +87558,8 @@ SQLITE_PRIVATE int sqlite3CodeOnce(Parse *pParse){ ** IN_INDEX_INDEX_DESC - The cursor was opened on a descending index. ** IN_INDEX_EPH - The cursor was opened on a specially created and ** populated epheremal table. +** IN_INDEX_NOOP - No cursor was allocated. The IN operator must be +** implemented as a sequence of comparisons. ** ** An existing b-tree might be used if the RHS expression pX is a simple ** subquery such as: @@ -79100,59 +87568,64 @@ SQLITE_PRIVATE int sqlite3CodeOnce(Parse *pParse){ ** ** If the RHS of the IN operator is a list or a more complex subquery, then ** an ephemeral table might need to be generated from the RHS and then -** pX->iTable made to point to the ephermeral table instead of an -** existing table. +** pX->iTable made to point to the ephemeral table instead of an +** existing table. ** -** If the prNotFound parameter is 0, then the b-tree will be used to iterate -** through the set members, skipping any duplicates. In this case an -** epheremal table must be used unless the selected is guaranteed +** The inFlags parameter must contain exactly one of the bits +** IN_INDEX_MEMBERSHIP or IN_INDEX_LOOP. If inFlags contains +** IN_INDEX_MEMBERSHIP, then the generated table will be used for a +** fast membership test. When the IN_INDEX_LOOP bit is set, the +** IN index will be used to loop over all values of the RHS of the +** IN operator. +** +** When IN_INDEX_LOOP is used (and the b-tree will be used to iterate +** through the set members) then the b-tree must not contain duplicates. +** An epheremal table must be used unless the selected is guaranteed ** to be unique - either because it is an INTEGER PRIMARY KEY or it ** has a UNIQUE constraint or UNIQUE index. ** -** If the prNotFound parameter is not 0, then the b-tree will be used -** for fast set membership tests. In this case an epheremal table must +** When IN_INDEX_MEMBERSHIP is used (and the b-tree will be used +** for fast set membership tests) then an epheremal table must ** be used unless is an INTEGER PRIMARY KEY or an index can ** be found with as its left-most column. ** +** If the IN_INDEX_NOOP_OK and IN_INDEX_MEMBERSHIP are both set and +** if the RHS of the IN operator is a list (not a subquery) then this +** routine might decide that creating an ephemeral b-tree for membership +** testing is too expensive and return IN_INDEX_NOOP. In that case, the +** calling routine should implement the IN operator using a sequence +** of Eq or Ne comparison operations. +** ** When the b-tree is being used for membership tests, the calling function -** needs to know whether or not the structure contains an SQL NULL -** value in order to correctly evaluate expressions like "X IN (Y, Z)". -** If there is any chance that the (...) might contain a NULL value at +** might need to know whether or not the RHS side of the IN operator +** contains a NULL. If prRhsHasNull is not a NULL pointer and +** if there is any chance that the (...) might contain a NULL value at ** runtime, then a register is allocated and the register number written -** to *prNotFound. If there is no chance that the (...) contains a -** NULL value, then *prNotFound is left unchanged. +** to *prRhsHasNull. If there is no chance that the (...) contains a +** NULL value, then *prRhsHasNull is left unchanged. ** -** If a register is allocated and its location stored in *prNotFound, then -** its initial value is NULL. If the (...) does not remain constant -** for the duration of the query (i.e. the SELECT within the (...) -** is a correlated subquery) then the value of the allocated register is -** reset to NULL each time the subquery is rerun. This allows the -** caller to use vdbe code equivalent to the following: -** -** if( register==NULL ){ -** has_null = -** register = 1 -** } -** -** in order to avoid running the -** test more often than is necessary. +** If a register is allocated and its location stored in *prRhsHasNull, then +** the value in that register will be NULL if the b-tree contains one or more +** NULL values, and it will be some non-NULL value if the b-tree contains no +** NULL values. */ #ifndef SQLITE_OMIT_SUBQUERY -SQLITE_PRIVATE int sqlite3FindInIndex(Parse *pParse, Expr *pX, int *prNotFound){ +SQLITE_PRIVATE int sqlite3FindInIndex(Parse *pParse, Expr *pX, u32 inFlags, int *prRhsHasNull){ Select *p; /* SELECT to the right of IN operator */ int eType = 0; /* Type of RHS table. IN_INDEX_* */ int iTab = pParse->nTab++; /* Cursor of the RHS table */ - int mustBeUnique = (prNotFound==0); /* True if RHS must be unique */ + int mustBeUnique; /* True if RHS must be unique */ Vdbe *v = sqlite3GetVdbe(pParse); /* Virtual machine being coded */ assert( pX->op==TK_IN ); + mustBeUnique = (inFlags & IN_INDEX_LOOP)!=0; /* Check to see if an existing table or index can be used to ** satisfy the query. This is preferable to generating a new ** ephemeral table. */ p = (ExprHasProperty(pX, EP_xIsSelect) ? pX->x.pSelect : 0); - if( ALWAYS(pParse->nErr==0) && isCandidateForInOpt(p) ){ + if( pParse->nErr==0 && isCandidateForInOpt(p) ){ sqlite3 *db = pParse->db; /* Database connection */ Table *pTab; /* Table . */ Expr *pExpr; /* Expression */ @@ -79202,7 +87675,7 @@ SQLITE_PRIVATE int sqlite3FindInIndex(Parse *pParse, Expr *pX, int *prNotFound){ for(pIdx=pTab->pIndex; pIdx && eType==0 && affinity_ok; pIdx=pIdx->pNext){ if( (pIdx->aiColumn[0]==iCol) && sqlite3FindCollSeq(db, ENC(db), pIdx->azColl[0], 0)==pReq - && (!mustBeUnique || (pIdx->nKeyCol==1 && pIdx->onError!=OE_None)) + && (!mustBeUnique || (pIdx->nKeyCol==1 && IsUniqueIndex(pIdx))) ){ int iAddr = sqlite3CodeOnce(pParse); VdbeCoverage(v); sqlite3VdbeAddOp3(v, OP_OpenRead, iTab, pIdx->tnum, iDb); @@ -79211,9 +87684,9 @@ SQLITE_PRIVATE int sqlite3FindInIndex(Parse *pParse, Expr *pX, int *prNotFound){ assert( IN_INDEX_INDEX_DESC == IN_INDEX_INDEX_ASC+1 ); eType = IN_INDEX_INDEX_ASC + pIdx->aSortOrder[0]; - if( prNotFound && !pTab->aCol[iCol].notNull ){ - *prNotFound = ++pParse->nMem; - sqlite3VdbeAddOp2(v, OP_Null, 0, *prNotFound); + if( prRhsHasNull && !pTab->aCol[iCol].notNull ){ + *prRhsHasNull = ++pParse->nMem; + sqlite3SetHasNullFlag(v, iTab, *prRhsHasNull); } sqlite3VdbeJumpHere(v, iAddr); } @@ -79221,21 +87694,36 @@ SQLITE_PRIVATE int sqlite3FindInIndex(Parse *pParse, Expr *pX, int *prNotFound){ } } + /* If no preexisting index is available for the IN clause + ** and IN_INDEX_NOOP is an allowed reply + ** and the RHS of the IN operator is a list, not a subquery + ** and the RHS is not contant or has two or fewer terms, + ** then it is not worth creating an ephemeral table to evaluate + ** the IN operator so return IN_INDEX_NOOP. + */ + if( eType==0 + && (inFlags & IN_INDEX_NOOP_OK) + && !ExprHasProperty(pX, EP_xIsSelect) + && (!sqlite3InRhsIsConstant(pX) || pX->x.pList->nExpr<=2) + ){ + eType = IN_INDEX_NOOP; + } + + if( eType==0 ){ - /* Could not found an existing table or index to use as the RHS b-tree. + /* Could not find an existing table or index to use as the RHS b-tree. ** We will have to generate an ephemeral table to do the job. */ u32 savedNQueryLoop = pParse->nQueryLoop; int rMayHaveNull = 0; eType = IN_INDEX_EPH; - if( prNotFound ){ - *prNotFound = rMayHaveNull = ++pParse->nMem; - sqlite3VdbeAddOp2(v, OP_Null, 0, *prNotFound); - }else{ + if( inFlags & IN_INDEX_LOOP ){ pParse->nQueryLoop = 0; if( pX->pLeft->iColumn<0 && !ExprHasProperty(pX, EP_xIsSelect) ){ eType = IN_INDEX_ROWID; } + }else if( prRhsHasNull ){ + *prRhsHasNull = rMayHaveNull = ++pParse->nMem; } sqlite3CodeSubselect(pParse, pX, rMayHaveNull, eType==IN_INDEX_ROWID); pParse->nQueryLoop = savedNQueryLoop; @@ -79266,15 +87754,9 @@ SQLITE_PRIVATE int sqlite3FindInIndex(Parse *pParse, Expr *pX, int *prNotFound){ ** ** If rMayHaveNull is non-zero, that means that the operation is an IN ** (not a SELECT or EXISTS) and that the RHS might contains NULLs. -** Furthermore, the IN is in a WHERE clause and that we really want -** to iterate over the RHS of the IN operator in order to quickly locate -** all corresponding LHS elements. All this routine does is initialize -** the register given by rMayHaveNull to NULL. Calling routines will take -** care of changing this register value to non-NULL if the RHS is NULL-free. -** -** If rMayHaveNull is zero, that means that the subquery is being used -** for membership testing only. There is no need to initialize any -** registers to indicate the presence or absence of NULLs on the RHS. +** All this routine does is initialize the register given by rMayHaveNull +** to NULL. Calling routines will take care of changing this register +** value to non-NULL if the RHS is NULL-free. ** ** For a SELECT or EXISTS operator, return the register that holds the ** result. For IN operators or if an error occurs, the return value is 0. @@ -79283,10 +87765,10 @@ SQLITE_PRIVATE int sqlite3FindInIndex(Parse *pParse, Expr *pX, int *prNotFound){ SQLITE_PRIVATE int sqlite3CodeSubselect( Parse *pParse, /* Parsing context */ Expr *pExpr, /* The IN, SELECT, or EXISTS operator */ - int rMayHaveNull, /* Register that records whether NULLs exist in RHS */ + int rHasNullFlag, /* Register that records whether NULLs exist in RHS */ int isRowid /* If true, LHS of IN operator is a rowid */ ){ - int testAddr = -1; /* One-time test address */ + int jmpIfDynamic = -1; /* One-time test address */ int rReg = 0; /* Register storing resulting */ Vdbe *v = sqlite3GetVdbe(pParse); if( NEVER(v==0) ) return 0; @@ -79303,14 +87785,15 @@ SQLITE_PRIVATE int sqlite3CodeSubselect( ** save the results, and reuse the same result on subsequent invocations. */ if( !ExprHasProperty(pExpr, EP_VarSelect) ){ - testAddr = sqlite3CodeOnce(pParse); VdbeCoverage(v); + jmpIfDynamic = sqlite3CodeOnce(pParse); VdbeCoverage(v); } #ifndef SQLITE_OMIT_EXPLAIN if( pParse->explain==2 ){ - char *zMsg = sqlite3MPrintf( - pParse->db, "EXECUTE %s%s SUBQUERY %d", testAddr>=0?"":"CORRELATED ", - pExpr->op==TK_IN?"LIST":"SCALAR", pParse->iNextSelectId + char *zMsg = sqlite3MPrintf(pParse->db, "EXECUTE %s%s SUBQUERY %d", + jmpIfDynamic>=0?"":"CORRELATED ", + pExpr->op==TK_IN?"LIST":"SCALAR", + pParse->iNextSelectId ); sqlite3VdbeAddOp4(v, OP_Explain, pParse->iSelectId, 0, 0, zMsg, P4_DYNAMIC); } @@ -79323,10 +87806,6 @@ SQLITE_PRIVATE int sqlite3CodeSubselect( Expr *pLeft = pExpr->pLeft; /* the LHS of the IN operator */ KeyInfo *pKeyInfo = 0; /* Key information */ - if( rMayHaveNull ){ - sqlite3VdbeAddOp2(v, OP_Null, 0, rMayHaveNull); - } - affinity = sqlite3ExprAffinity(pLeft); /* Whether this is an 'x IN(SELECT...)' or an 'x IN()' @@ -79352,6 +87831,7 @@ SQLITE_PRIVATE int sqlite3CodeSubselect( ** Generate code to write the results of the select into the temporary ** table allocated and opened above. */ + Select *pSelect = pExpr->x.pSelect; SelectDest dest; ExprList *pEList; @@ -79359,13 +87839,14 @@ SQLITE_PRIVATE int sqlite3CodeSubselect( sqlite3SelectDestInit(&dest, SRT_Set, pExpr->iTable); dest.affSdst = (u8)affinity; assert( (pExpr->iTable&0x0000FFFF)==pExpr->iTable ); - pExpr->x.pSelect->iLimit = 0; + pSelect->iLimit = 0; + testcase( pSelect->selFlags & SF_Distinct ); testcase( pKeyInfo==0 ); /* Caused by OOM in sqlite3KeyInfoAlloc() */ - if( sqlite3Select(pParse, pExpr->x.pSelect, &dest) ){ + if( sqlite3Select(pParse, pSelect, &dest) ){ sqlite3KeyInfoUnref(pKeyInfo); return 0; } - pEList = pExpr->x.pSelect->pEList; + pEList = pSelect->pEList; assert( pKeyInfo!=0 ); /* OOM will cause exit after sqlite3Select() */ assert( pEList!=0 ); assert( pEList->nExpr>0 ); @@ -79386,7 +87867,7 @@ SQLITE_PRIVATE int sqlite3CodeSubselect( int r1, r2, r3; if( !affinity ){ - affinity = SQLITE_AFF_NONE; + affinity = SQLITE_AFF_BLOB; } if( pKeyInfo ){ assert( sqlite3KeyInfoIsWriteable(pKeyInfo) ); @@ -79396,7 +87877,7 @@ SQLITE_PRIVATE int sqlite3CodeSubselect( /* Loop through each expression in . */ r1 = sqlite3GetTempReg(pParse); r2 = sqlite3GetTempReg(pParse); - sqlite3VdbeAddOp2(v, OP_Null, 0, r2); + if( isRowid ) sqlite3VdbeAddOp2(v, OP_Null, 0, r2); for(i=pList->nExpr, pItem=pList->a; i>0; i--, pItem++){ Expr *pE2 = pItem->pExpr; int iValToIns; @@ -79406,9 +87887,9 @@ SQLITE_PRIVATE int sqlite3CodeSubselect( ** this code only executes once. Because for a non-constant ** expression we need to rerun this code each time. */ - if( testAddr>=0 && !sqlite3ExprIsConstant(pE2) ){ - sqlite3VdbeChangeToNoop(v, testAddr); - testAddr = -1; + if( jmpIfDynamic>=0 && !sqlite3ExprIsConstant(pE2) ){ + sqlite3VdbeChangeToNoop(v, jmpIfDynamic); + jmpIfDynamic = -1; } /* Evaluate the expression and insert it into the temp table */ @@ -79458,6 +87939,7 @@ SQLITE_PRIVATE int sqlite3CodeSubselect( sqlite3SelectDestInit(&dest, 0, ++pParse->nMem); if( pExpr->op==TK_SELECT ){ dest.eDest = SRT_Mem; + dest.iSdst = dest.iSDParm; sqlite3VdbeAddOp2(v, OP_Null, 0, dest.iSDParm); VdbeComment((v, "Init subquery result")); }else{ @@ -79469,6 +87951,7 @@ SQLITE_PRIVATE int sqlite3CodeSubselect( pSel->pLimit = sqlite3PExpr(pParse, TK_INTEGER, 0, 0, &sqlite3IntTokens[1]); pSel->iLimit = 0; + pSel->selFlags &= ~SF_MultiValue; if( sqlite3Select(pParse, pSel, &dest) ){ return 0; } @@ -79478,8 +87961,12 @@ SQLITE_PRIVATE int sqlite3CodeSubselect( } } - if( testAddr>=0 ){ - sqlite3VdbeJumpHere(v, testAddr); + if( rHasNullFlag ){ + sqlite3SetHasNullFlag(v, pExpr->iTable, rHasNullFlag); + } + + if( jmpIfDynamic>=0 ){ + sqlite3VdbeJumpHere(v, jmpIfDynamic); } sqlite3ExprCachePop(pParse); @@ -79500,7 +87987,7 @@ SQLITE_PRIVATE int sqlite3CodeSubselect( ** if the LHS is NULL or if the LHS is not contained within the RHS and the ** RHS contains one or more NULL values. ** -** This routine generates code will jump to destIfFalse if the LHS is not +** This routine generates code that jumps to destIfFalse if the LHS is not ** contained within the RHS. If due to NULLs we cannot determine if the LHS ** is contained in the RHS then jump to destIfNull. If the LHS is contained ** within the RHS then fall through. @@ -79523,7 +88010,9 @@ static void sqlite3ExprCodeIN( v = pParse->pVdbe; assert( v!=0 ); /* OOM detected prior to this routine */ VdbeNoopComment((v, "begin IN expr")); - eType = sqlite3FindInIndex(pParse, pExpr, &rRhsHasNull); + eType = sqlite3FindInIndex(pParse, pExpr, + IN_INDEX_MEMBERSHIP | IN_INDEX_NOOP_OK, + destIfFalse==destIfNull ? 0 : &rRhsHasNull); /* Figure out the affinity to use to create a key from the results ** of the expression. affinityStr stores a static string suitable for @@ -79537,82 +88026,114 @@ static void sqlite3ExprCodeIN( r1 = sqlite3GetTempReg(pParse); sqlite3ExprCode(pParse, pExpr->pLeft, r1); - /* If the LHS is NULL, then the result is either false or NULL depending - ** on whether the RHS is empty or not, respectively. + /* If sqlite3FindInIndex() did not find or create an index that is + ** suitable for evaluating the IN operator, then evaluate using a + ** sequence of comparisons. */ - if( destIfNull==destIfFalse ){ - /* Shortcut for the common case where the false and NULL outcomes are - ** the same. */ - sqlite3VdbeAddOp2(v, OP_IsNull, r1, destIfNull); VdbeCoverage(v); + if( eType==IN_INDEX_NOOP ){ + ExprList *pList = pExpr->x.pList; + CollSeq *pColl = sqlite3ExprCollSeq(pParse, pExpr->pLeft); + int labelOk = sqlite3VdbeMakeLabel(v); + int r2, regToFree; + int regCkNull = 0; + int ii; + assert( !ExprHasProperty(pExpr, EP_xIsSelect) ); + if( destIfNull!=destIfFalse ){ + regCkNull = sqlite3GetTempReg(pParse); + sqlite3VdbeAddOp3(v, OP_BitAnd, r1, r1, regCkNull); + } + for(ii=0; iinExpr; ii++){ + r2 = sqlite3ExprCodeTemp(pParse, pList->a[ii].pExpr, ®ToFree); + if( regCkNull && sqlite3ExprCanBeNull(pList->a[ii].pExpr) ){ + sqlite3VdbeAddOp3(v, OP_BitAnd, regCkNull, r2, regCkNull); + } + if( iinExpr-1 || destIfNull!=destIfFalse ){ + sqlite3VdbeAddOp4(v, OP_Eq, r1, labelOk, r2, + (void*)pColl, P4_COLLSEQ); + VdbeCoverageIf(v, iinExpr-1); + VdbeCoverageIf(v, ii==pList->nExpr-1); + sqlite3VdbeChangeP5(v, affinity); + }else{ + assert( destIfNull==destIfFalse ); + sqlite3VdbeAddOp4(v, OP_Ne, r1, destIfFalse, r2, + (void*)pColl, P4_COLLSEQ); VdbeCoverage(v); + sqlite3VdbeChangeP5(v, affinity | SQLITE_JUMPIFNULL); + } + sqlite3ReleaseTempReg(pParse, regToFree); + } + if( regCkNull ){ + sqlite3VdbeAddOp2(v, OP_IsNull, regCkNull, destIfNull); VdbeCoverage(v); + sqlite3VdbeGoto(v, destIfFalse); + } + sqlite3VdbeResolveLabel(v, labelOk); + sqlite3ReleaseTempReg(pParse, regCkNull); }else{ - int addr1 = sqlite3VdbeAddOp1(v, OP_NotNull, r1); VdbeCoverage(v); - sqlite3VdbeAddOp2(v, OP_Rewind, pExpr->iTable, destIfFalse); - VdbeCoverage(v); - sqlite3VdbeAddOp2(v, OP_Goto, 0, destIfNull); - sqlite3VdbeJumpHere(v, addr1); - } - - if( eType==IN_INDEX_ROWID ){ - /* In this case, the RHS is the ROWID of table b-tree + + /* If the LHS is NULL, then the result is either false or NULL depending + ** on whether the RHS is empty or not, respectively. */ - sqlite3VdbeAddOp2(v, OP_MustBeInt, r1, destIfFalse); VdbeCoverage(v); - sqlite3VdbeAddOp3(v, OP_NotExists, pExpr->iTable, destIfFalse, r1); - VdbeCoverage(v); - }else{ - /* In this case, the RHS is an index b-tree. - */ - sqlite3VdbeAddOp4(v, OP_Affinity, r1, 1, 0, &affinity, 1); - - /* If the set membership test fails, then the result of the - ** "x IN (...)" expression must be either 0 or NULL. If the set - ** contains no NULL values, then the result is 0. If the set - ** contains one or more NULL values, then the result of the - ** expression is also NULL. - */ - if( rRhsHasNull==0 || destIfFalse==destIfNull ){ - /* This branch runs if it is known at compile time that the RHS - ** cannot contain NULL values. This happens as the result - ** of a "NOT NULL" constraint in the database schema. - ** - ** Also run this branch if NULL is equivalent to FALSE - ** for this particular IN operator. + if( sqlite3ExprCanBeNull(pExpr->pLeft) ){ + if( destIfNull==destIfFalse ){ + /* Shortcut for the common case where the false and NULL outcomes are + ** the same. */ + sqlite3VdbeAddOp2(v, OP_IsNull, r1, destIfNull); VdbeCoverage(v); + }else{ + int addr1 = sqlite3VdbeAddOp1(v, OP_NotNull, r1); VdbeCoverage(v); + sqlite3VdbeAddOp2(v, OP_Rewind, pExpr->iTable, destIfFalse); + VdbeCoverage(v); + sqlite3VdbeGoto(v, destIfNull); + sqlite3VdbeJumpHere(v, addr1); + } + } + + if( eType==IN_INDEX_ROWID ){ + /* In this case, the RHS is the ROWID of table b-tree */ - sqlite3VdbeAddOp4Int(v, OP_NotFound, pExpr->iTable, destIfFalse, r1, 1); + sqlite3VdbeAddOp2(v, OP_MustBeInt, r1, destIfFalse); VdbeCoverage(v); + sqlite3VdbeAddOp3(v, OP_NotExists, pExpr->iTable, destIfFalse, r1); VdbeCoverage(v); }else{ - /* In this branch, the RHS of the IN might contain a NULL and - ** the presence of a NULL on the RHS makes a difference in the - ** outcome. + /* In this case, the RHS is an index b-tree. */ - int j1, j2; - - /* First check to see if the LHS is contained in the RHS. If so, - ** then the presence of NULLs in the RHS does not matter, so jump - ** over all of the code that follows. + sqlite3VdbeAddOp4(v, OP_Affinity, r1, 1, 0, &affinity, 1); + + /* If the set membership test fails, then the result of the + ** "x IN (...)" expression must be either 0 or NULL. If the set + ** contains no NULL values, then the result is 0. If the set + ** contains one or more NULL values, then the result of the + ** expression is also NULL. */ - j1 = sqlite3VdbeAddOp4Int(v, OP_Found, pExpr->iTable, 0, r1, 1); - VdbeCoverage(v); - - /* Here we begin generating code that runs if the LHS is not - ** contained within the RHS. Generate additional code that - ** tests the RHS for NULLs. If the RHS contains a NULL then - ** jump to destIfNull. If there are no NULLs in the RHS then - ** jump to destIfFalse. - */ - sqlite3VdbeAddOp2(v, OP_If, rRhsHasNull, destIfNull); VdbeCoverage(v); - sqlite3VdbeAddOp2(v, OP_IfNot, rRhsHasNull, destIfFalse); VdbeCoverage(v); - j2 = sqlite3VdbeAddOp4Int(v, OP_Found, pExpr->iTable, 0, rRhsHasNull, 1); - VdbeCoverage(v); - sqlite3VdbeAddOp2(v, OP_Integer, 0, rRhsHasNull); - sqlite3VdbeAddOp2(v, OP_Goto, 0, destIfFalse); - sqlite3VdbeJumpHere(v, j2); - sqlite3VdbeAddOp2(v, OP_Integer, 1, rRhsHasNull); - sqlite3VdbeAddOp2(v, OP_Goto, 0, destIfNull); - - /* The OP_Found at the top of this branch jumps here when true, - ** causing the overall IN expression evaluation to fall through. - */ - sqlite3VdbeJumpHere(v, j1); + assert( destIfFalse!=destIfNull || rRhsHasNull==0 ); + if( rRhsHasNull==0 ){ + /* This branch runs if it is known at compile time that the RHS + ** cannot contain NULL values. This happens as the result + ** of a "NOT NULL" constraint in the database schema. + ** + ** Also run this branch if NULL is equivalent to FALSE + ** for this particular IN operator. + */ + sqlite3VdbeAddOp4Int(v, OP_NotFound, pExpr->iTable, destIfFalse, r1, 1); + VdbeCoverage(v); + }else{ + /* In this branch, the RHS of the IN might contain a NULL and + ** the presence of a NULL on the RHS makes a difference in the + ** outcome. + */ + int addr1; + + /* First check to see if the LHS is contained in the RHS. If so, + ** then the answer is TRUE the presence of NULLs in the RHS does + ** not matter. If the LHS is not contained in the RHS, then the + ** answer is NULL if the RHS contains NULLs and the answer is + ** FALSE if the RHS is NULL-free. + */ + addr1 = sqlite3VdbeAddOp4Int(v, OP_Found, pExpr->iTable, 0, r1, 1); + VdbeCoverage(v); + sqlite3VdbeAddOp2(v, OP_IsNull, rRhsHasNull, destIfNull); + VdbeCoverage(v); + sqlite3VdbeGoto(v, destIfFalse); + sqlite3VdbeJumpHere(v, addr1); + } } } sqlite3ReleaseTempReg(pParse, r1); @@ -79621,17 +88142,6 @@ static void sqlite3ExprCodeIN( } #endif /* SQLITE_OMIT_SUBQUERY */ -/* -** Duplicate an 8-byte value -*/ -static char *dup8bytes(Vdbe *v, const char *in){ - char *out = sqlite3DbMallocRaw(sqlite3VdbeDb(v), 8); - if( out ){ - memcpy(out, in, 8); - } - return out; -} - #ifndef SQLITE_OMIT_FLOATING_POINT /* ** Generate an instruction that will put the floating point @@ -79644,12 +88154,10 @@ static char *dup8bytes(Vdbe *v, const char *in){ static void codeReal(Vdbe *v, const char *z, int negateFlag, int iMem){ if( ALWAYS(z!=0) ){ double value; - char *zV; sqlite3AtoF(z, &value, sqlite3Strlen30(z), SQLITE_UTF8); assert( !sqlite3IsNaN(value) ); /* The new AtoF never returns NaN */ if( negateFlag ) value = -value; - zV = dup8bytes(v, (char*)&value); - sqlite3VdbeAddOp4(v, OP_Real, 0, iMem, 0, zV, P4_REAL); + sqlite3VdbeAddOp4Dup8(v, OP_Real, 0, iMem, 0, (u8*)&value, P4_REAL); } } #endif @@ -79673,17 +88181,22 @@ static void codeInteger(Parse *pParse, Expr *pExpr, int negFlag, int iMem){ i64 value; const char *z = pExpr->u.zToken; assert( z!=0 ); - c = sqlite3Atoi64(z, &value, sqlite3Strlen30(z), SQLITE_UTF8); + c = sqlite3DecOrHexToI64(z, &value); if( c==0 || (c==2 && negFlag) ){ - char *zV; if( negFlag ){ value = c==2 ? SMALLEST_INT64 : -value; } - zV = dup8bytes(v, (char*)&value); - sqlite3VdbeAddOp4(v, OP_Int64, 0, iMem, 0, zV, P4_INT64); + sqlite3VdbeAddOp4Dup8(v, OP_Int64, 0, iMem, 0, (u8*)&value, P4_INT64); }else{ #ifdef SQLITE_OMIT_FLOATING_POINT sqlite3ErrorMsg(pParse, "oversized integer: %s%s", negFlag ? "-" : "", z); #else - codeReal(v, z, negFlag, iMem); +#ifndef SQLITE_OMIT_HEX_INTEGER + if( sqlite3_strnicmp(z,"0x",2)==0 ){ + sqlite3ErrorMsg(pParse, "hex literal too big: %s", z); + }else +#endif + { + codeReal(v, z, negFlag, iMem); + } #endif } } @@ -79712,7 +88225,8 @@ SQLITE_PRIVATE void sqlite3ExprCacheStore(Parse *pParse, int iTab, int iCol, int int idxLru; struct yColCache *p; - assert( iReg>0 ); /* Register numbers are always positive */ + /* Unless an error has occurred, register numbers are always positive. */ + assert( iReg>0 || pParse->nErr || pParse->db->mallocFailed ); assert( iCol>=-1 && iCol<32768 ); /* Finite column numbers */ /* The SQLITE_ColumnCache flag disables the column cache. This is used @@ -79836,6 +88350,28 @@ static void sqlite3ExprCachePinRegister(Parse *pParse, int iReg){ } } +/* Generate code that will load into register regOut a value that is +** appropriate for the iIdxCol-th column of index pIdx. +*/ +SQLITE_PRIVATE void sqlite3ExprCodeLoadIndexColumn( + Parse *pParse, /* The parsing context */ + Index *pIdx, /* The index whose column is to be loaded */ + int iTabCur, /* Cursor pointing to a table row */ + int iIdxCol, /* The column of the index to be loaded */ + int regOut /* Store the index column value in this register */ +){ + i16 iTabCol = pIdx->aiColumn[iIdxCol]; + if( iTabCol==XN_EXPR ){ + assert( pIdx->aColExpr ); + assert( pIdx->aColExpr->nExpr>iIdxCol ); + pParse->iSelfTab = iTabCur; + sqlite3ExprCodeCopy(pParse, pIdx->aColExpr->a[iIdxCol].pExpr, regOut); + }else{ + sqlite3ExprCodeGetColumnOfTable(pParse->pVdbe, pIdx->pTable, iTabCur, + iTabCol, regOut); + } +} + /* ** Generate code to extract the value of the iCol-th column of a table. */ @@ -79863,9 +88399,12 @@ SQLITE_PRIVATE void sqlite3ExprCodeGetColumnOfTable( /* ** Generate code that will extract the iColumn-th column from -** table pTab and store the column value in a register. An effort -** is made to store the column value in register iReg, but this is -** not guaranteed. The location of the column value is returned. +** table pTab and store the column value in a register. +** +** An effort is made to store the column value in register iReg. This +** is not garanteeed for GetColumn() - the result can be stored in +** any register. But the result is guaranteed to land in register iReg +** for GetColumnToReg(). ** ** There must be an open cursor to pTab in iTable when this routine ** is called. If iColumn<0 then code is generated that extracts the rowid. @@ -79876,7 +88415,7 @@ SQLITE_PRIVATE int sqlite3ExprCodeGetColumn( int iColumn, /* Index of the table column */ int iTable, /* The cursor pointing to the table */ int iReg, /* Store results here */ - u8 p5 /* P5 value for OP_Column */ + u8 p5 /* P5 value for OP_Column + FLAGS */ ){ Vdbe *v = pParse->pVdbe; int i; @@ -79898,6 +88437,17 @@ SQLITE_PRIVATE int sqlite3ExprCodeGetColumn( } return iReg; } +SQLITE_PRIVATE void sqlite3ExprCodeGetColumnToReg( + Parse *pParse, /* Parsing and code generating context */ + Table *pTab, /* Description of the table we are reading from */ + int iColumn, /* Index of the table column */ + int iTable, /* The cursor pointing to the table */ + int iReg /* Store results here */ +){ + int r1 = sqlite3ExprCodeGetColumn(pParse, pTab, iColumn, iTable, iReg, 0); + if( r1!=iReg ) sqlite3VdbeAddOp2(pParse->pVdbe, OP_SCopy, r1, iReg); +} + /* ** Clear all column cache entries. @@ -79932,16 +88482,9 @@ SQLITE_PRIVATE void sqlite3ExprCacheAffinityChange(Parse *pParse, int iStart, in ** over to iTo..iTo+nReg-1. Keep the column cache up-to-date. */ SQLITE_PRIVATE void sqlite3ExprCodeMove(Parse *pParse, int iFrom, int iTo, int nReg){ - int i; - struct yColCache *p; assert( iFrom>=iTo+nReg || iFrom+nReg<=iTo ); sqlite3VdbeAddOp3(pParse->pVdbe, OP_Move, iFrom, iTo, nReg); - for(i=0, p=pParse->aColCache; iiReg; - if( x>=iFrom && xiReg += iTo-iFrom; - } - } + sqlite3ExprCacheRemove(pParse, iFrom, nReg); } #if defined(SQLITE_DEBUG) || defined(SQLITE_COVERAGE_TEST) @@ -80028,8 +88571,9 @@ SQLITE_PRIVATE int sqlite3ExprCodeTarget(Parse *pParse, Expr *pExpr, int target) inReg = pExpr->iColumn + pParse->ckBase; break; }else{ - /* Deleting from a partial index */ - iTab = pParse->iPartIdxTab; + /* Coding an expression that is part of an index where column names + ** in the index refer to the table to which the index belongs */ + iTab = pParse->iSelfTab; } } inReg = sqlite3ExprCodeGetColumn(pParse, pExpr->pTab, @@ -80050,7 +88594,7 @@ SQLITE_PRIVATE int sqlite3ExprCodeTarget(Parse *pParse, Expr *pExpr, int target) #endif case TK_STRING: { assert( !ExprHasProperty(pExpr, EP_IntValue) ); - sqlite3VdbeAddOp4(v, OP_String8, 0, target, 0, pExpr->u.zToken, 0); + sqlite3VdbeLoadString(v, target, pExpr->u.zToken); break; } case TK_NULL: { @@ -80089,33 +88633,16 @@ SQLITE_PRIVATE int sqlite3ExprCodeTarget(Parse *pParse, Expr *pExpr, int target) inReg = pExpr->iTable; break; } - case TK_AS: { - inReg = sqlite3ExprCodeTarget(pParse, pExpr->pLeft, target); - break; - } #ifndef SQLITE_OMIT_CAST case TK_CAST: { /* Expressions of the form: CAST(pLeft AS token) */ - int aff, to_op; inReg = sqlite3ExprCodeTarget(pParse, pExpr->pLeft, target); - assert( !ExprHasProperty(pExpr, EP_IntValue) ); - aff = sqlite3AffinityType(pExpr->u.zToken, 0); - to_op = aff - SQLITE_AFF_TEXT + OP_ToText; - assert( to_op==OP_ToText || aff!=SQLITE_AFF_TEXT ); - assert( to_op==OP_ToBlob || aff!=SQLITE_AFF_NONE ); - assert( to_op==OP_ToNumeric || aff!=SQLITE_AFF_NUMERIC ); - assert( to_op==OP_ToInt || aff!=SQLITE_AFF_INTEGER ); - assert( to_op==OP_ToReal || aff!=SQLITE_AFF_REAL ); - testcase( to_op==OP_ToText ); - testcase( to_op==OP_ToBlob ); - testcase( to_op==OP_ToNumeric ); - testcase( to_op==OP_ToInt ); - testcase( to_op==OP_ToReal ); if( inReg!=target ){ sqlite3VdbeAddOp2(v, OP_SCopy, inReg, target); inReg = target; } - sqlite3VdbeAddOp1(v, to_op, inReg); + sqlite3VdbeAddOp2(v, OP_Cast, target, + sqlite3AffinityType(pExpr->u.zToken, 0)); testcase( usedAsColumnCache(pParse, inReg, inReg) ); sqlite3ExprCacheAffinityChange(pParse, inReg, 1); break; @@ -80229,7 +88756,7 @@ SQLITE_PRIVATE int sqlite3ExprCodeTarget(Parse *pParse, Expr *pExpr, int target) addr = sqlite3VdbeAddOp1(v, op, r1); VdbeCoverageIf(v, op==TK_ISNULL); VdbeCoverageIf(v, op==TK_NOTNULL); - sqlite3VdbeAddOp2(v, OP_AddImm, target, -1); + sqlite3VdbeAddOp2(v, OP_Integer, 0, target); sqlite3VdbeJumpHere(v, addr); break; } @@ -80265,13 +88792,13 @@ SQLITE_PRIVATE int sqlite3ExprCodeTarget(Parse *pParse, Expr *pExpr, int target) zId = pExpr->u.zToken; nId = sqlite3Strlen30(zId); pDef = sqlite3FindFunction(db, zId, nId, nFarg, enc, 0); - if( pDef==0 ){ + if( pDef==0 || pDef->xFunc==0 ){ sqlite3ErrorMsg(pParse, "unknown function: %.*s()", nId, zId); break; } /* Attempt a direct implementation of the built-in COALESCE() and - ** IFNULL() functions. This avoids unnecessary evalation of + ** IFNULL() functions. This avoids unnecessary evaluation of ** arguments past the first non-NULL argument. */ if( pDef->funcFlags & SQLITE_FUNC_COALESCE ){ @@ -80295,7 +88822,7 @@ SQLITE_PRIVATE int sqlite3ExprCodeTarget(Parse *pParse, Expr *pExpr, int target) */ if( pDef->funcFlags & SQLITE_FUNC_UNLIKELY ){ assert( nFarg>=1 ); - sqlite3ExprCode(pParse, pFarg->a[0].pExpr, target); + inReg = sqlite3ExprCodeTarget(pParse, pFarg->a[0].pExpr, target); break; } @@ -80336,7 +88863,7 @@ SQLITE_PRIVATE int sqlite3ExprCodeTarget(Parse *pParse, Expr *pExpr, int target) } sqlite3ExprCachePush(pParse); /* Ticket 2ea2425d34be */ - sqlite3ExprCodeExprList(pParse, pFarg, r1, + sqlite3ExprCodeExprList(pParse, pFarg, r1, 0, SQLITE_ECEL_DUP|SQLITE_ECEL_FACTOR); sqlite3ExprCachePop(pParse); /* Ticket 2ea2425d34be */ }else{ @@ -80365,7 +88892,7 @@ SQLITE_PRIVATE int sqlite3ExprCodeTarget(Parse *pParse, Expr *pExpr, int target) if( !pColl ) pColl = db->pDfltColl; sqlite3VdbeAddOp4(v, OP_CollSeq, 0, 0, 0, (char *)pColl, P4_COLLSEQ); } - sqlite3VdbeAddOp4(v, OP_Function, constMask, r1, target, + sqlite3VdbeAddOp4(v, OP_Function0, constMask, r1, target, (char*)pDef, P4_FUNCDEF); sqlite3VdbeChangeP5(v, (u8)nFarg); if( nFarg && constMask==0 ){ @@ -80480,7 +89007,10 @@ SQLITE_PRIVATE int sqlite3ExprCodeTarget(Parse *pParse, Expr *pExpr, int target) #ifndef SQLITE_OMIT_FLOATING_POINT /* If the column has REAL affinity, it may currently be stored as an - ** integer. Use OP_RealAffinity to make sure it is really real. */ + ** integer. Use OP_RealAffinity to make sure it is really real. + ** + ** EVIDENCE-OF: R-60985-57662 SQLite will convert the value back to + ** floating point when extracting it from the record. */ if( pExpr->iColumn>=0 && pTab->aCol[pExpr->iColumn].affinity==SQLITE_AFF_REAL ){ @@ -80557,7 +89087,7 @@ SQLITE_PRIVATE int sqlite3ExprCodeTarget(Parse *pParse, Expr *pExpr, int target) sqlite3ExprIfFalse(pParse, pTest, nextCase, SQLITE_JUMPIFNULL); testcase( aListelem[i+1].pExpr->op==TK_COLUMN ); sqlite3ExprCode(pParse, aListelem[i+1].pExpr, target); - sqlite3VdbeAddOp2(v, OP_Goto, 0, endLabel); + sqlite3VdbeGoto(v, endLabel); sqlite3ExprCachePop(pParse); sqlite3VdbeResolveLabel(v, nextCase); } @@ -80688,13 +89218,25 @@ SQLITE_PRIVATE void sqlite3ExprCode(Parse *pParse, Expr *pExpr, int target){ sqlite3VdbeAddOp2(pParse->pVdbe, OP_Copy, pExpr->iTable, target); }else{ inReg = sqlite3ExprCodeTarget(pParse, pExpr, target); - assert( pParse->pVdbe || pParse->db->mallocFailed ); + assert( pParse->pVdbe!=0 || pParse->db->mallocFailed ); if( inReg!=target && pParse->pVdbe ){ sqlite3VdbeAddOp2(pParse->pVdbe, OP_SCopy, inReg, target); } } } +/* +** Make a transient copy of expression pExpr and then code it using +** sqlite3ExprCode(). This routine works just like sqlite3ExprCode() +** except that the input expression is guaranteed to be unchanged. +*/ +SQLITE_PRIVATE void sqlite3ExprCodeCopy(Parse *pParse, Expr *pExpr, int target){ + sqlite3 *db = pParse->db; + pExpr = sqlite3ExprDup(db, pExpr, 0); + if( !db->mallocFailed ) sqlite3ExprCode(pParse, pExpr, target); + sqlite3ExprDelete(db, pExpr); +} + /* ** Generate code that will evaluate expression pExpr and store the ** results in register target. The results are guaranteed to appear @@ -80710,7 +89252,7 @@ SQLITE_PRIVATE void sqlite3ExprCodeFactorable(Parse *pParse, Expr *pExpr, int ta } /* -** Generate code that evalutes the given expression and puts the result +** Generate code that evaluates the given expression and puts the result ** in register target. ** ** Also make a copy of the expression results into another "cache" register @@ -80733,278 +89275,6 @@ SQLITE_PRIVATE void sqlite3ExprCodeAndCache(Parse *pParse, Expr *pExpr, int targ exprToRegister(pExpr, iMem); } -#if defined(SQLITE_ENABLE_TREE_EXPLAIN) -/* -** Generate a human-readable explanation of an expression tree. -*/ -SQLITE_PRIVATE void sqlite3ExplainExpr(Vdbe *pOut, Expr *pExpr){ - int op; /* The opcode being coded */ - const char *zBinOp = 0; /* Binary operator */ - const char *zUniOp = 0; /* Unary operator */ - if( pExpr==0 ){ - op = TK_NULL; - }else{ - op = pExpr->op; - } - switch( op ){ - case TK_AGG_COLUMN: { - sqlite3ExplainPrintf(pOut, "AGG{%d:%d}", - pExpr->iTable, pExpr->iColumn); - break; - } - case TK_COLUMN: { - if( pExpr->iTable<0 ){ - /* This only happens when coding check constraints */ - sqlite3ExplainPrintf(pOut, "COLUMN(%d)", pExpr->iColumn); - }else{ - sqlite3ExplainPrintf(pOut, "{%d:%d}", - pExpr->iTable, pExpr->iColumn); - } - break; - } - case TK_INTEGER: { - if( pExpr->flags & EP_IntValue ){ - sqlite3ExplainPrintf(pOut, "%d", pExpr->u.iValue); - }else{ - sqlite3ExplainPrintf(pOut, "%s", pExpr->u.zToken); - } - break; - } -#ifndef SQLITE_OMIT_FLOATING_POINT - case TK_FLOAT: { - sqlite3ExplainPrintf(pOut,"%s", pExpr->u.zToken); - break; - } -#endif - case TK_STRING: { - sqlite3ExplainPrintf(pOut,"%Q", pExpr->u.zToken); - break; - } - case TK_NULL: { - sqlite3ExplainPrintf(pOut,"NULL"); - break; - } -#ifndef SQLITE_OMIT_BLOB_LITERAL - case TK_BLOB: { - sqlite3ExplainPrintf(pOut,"%s", pExpr->u.zToken); - break; - } -#endif - case TK_VARIABLE: { - sqlite3ExplainPrintf(pOut,"VARIABLE(%s,%d)", - pExpr->u.zToken, pExpr->iColumn); - break; - } - case TK_REGISTER: { - sqlite3ExplainPrintf(pOut,"REGISTER(%d)", pExpr->iTable); - break; - } - case TK_AS: { - sqlite3ExplainExpr(pOut, pExpr->pLeft); - break; - } -#ifndef SQLITE_OMIT_CAST - case TK_CAST: { - /* Expressions of the form: CAST(pLeft AS token) */ - const char *zAff = "unk"; - switch( sqlite3AffinityType(pExpr->u.zToken, 0) ){ - case SQLITE_AFF_TEXT: zAff = "TEXT"; break; - case SQLITE_AFF_NONE: zAff = "NONE"; break; - case SQLITE_AFF_NUMERIC: zAff = "NUMERIC"; break; - case SQLITE_AFF_INTEGER: zAff = "INTEGER"; break; - case SQLITE_AFF_REAL: zAff = "REAL"; break; - } - sqlite3ExplainPrintf(pOut, "CAST-%s(", zAff); - sqlite3ExplainExpr(pOut, pExpr->pLeft); - sqlite3ExplainPrintf(pOut, ")"); - break; - } -#endif /* SQLITE_OMIT_CAST */ - case TK_LT: zBinOp = "LT"; break; - case TK_LE: zBinOp = "LE"; break; - case TK_GT: zBinOp = "GT"; break; - case TK_GE: zBinOp = "GE"; break; - case TK_NE: zBinOp = "NE"; break; - case TK_EQ: zBinOp = "EQ"; break; - case TK_IS: zBinOp = "IS"; break; - case TK_ISNOT: zBinOp = "ISNOT"; break; - case TK_AND: zBinOp = "AND"; break; - case TK_OR: zBinOp = "OR"; break; - case TK_PLUS: zBinOp = "ADD"; break; - case TK_STAR: zBinOp = "MUL"; break; - case TK_MINUS: zBinOp = "SUB"; break; - case TK_REM: zBinOp = "REM"; break; - case TK_BITAND: zBinOp = "BITAND"; break; - case TK_BITOR: zBinOp = "BITOR"; break; - case TK_SLASH: zBinOp = "DIV"; break; - case TK_LSHIFT: zBinOp = "LSHIFT"; break; - case TK_RSHIFT: zBinOp = "RSHIFT"; break; - case TK_CONCAT: zBinOp = "CONCAT"; break; - - case TK_UMINUS: zUniOp = "UMINUS"; break; - case TK_UPLUS: zUniOp = "UPLUS"; break; - case TK_BITNOT: zUniOp = "BITNOT"; break; - case TK_NOT: zUniOp = "NOT"; break; - case TK_ISNULL: zUniOp = "ISNULL"; break; - case TK_NOTNULL: zUniOp = "NOTNULL"; break; - - case TK_COLLATE: { - sqlite3ExplainExpr(pOut, pExpr->pLeft); - sqlite3ExplainPrintf(pOut,".COLLATE(%s)",pExpr->u.zToken); - break; - } - - case TK_AGG_FUNCTION: - case TK_FUNCTION: { - ExprList *pFarg; /* List of function arguments */ - if( ExprHasProperty(pExpr, EP_TokenOnly) ){ - pFarg = 0; - }else{ - pFarg = pExpr->x.pList; - } - if( op==TK_AGG_FUNCTION ){ - sqlite3ExplainPrintf(pOut, "AGG_FUNCTION%d:%s(", - pExpr->op2, pExpr->u.zToken); - }else{ - sqlite3ExplainPrintf(pOut, "FUNCTION:%s(", pExpr->u.zToken); - } - if( pFarg ){ - sqlite3ExplainExprList(pOut, pFarg); - } - sqlite3ExplainPrintf(pOut, ")"); - break; - } -#ifndef SQLITE_OMIT_SUBQUERY - case TK_EXISTS: { - sqlite3ExplainPrintf(pOut, "EXISTS("); - sqlite3ExplainSelect(pOut, pExpr->x.pSelect); - sqlite3ExplainPrintf(pOut,")"); - break; - } - case TK_SELECT: { - sqlite3ExplainPrintf(pOut, "("); - sqlite3ExplainSelect(pOut, pExpr->x.pSelect); - sqlite3ExplainPrintf(pOut, ")"); - break; - } - case TK_IN: { - sqlite3ExplainPrintf(pOut, "IN("); - sqlite3ExplainExpr(pOut, pExpr->pLeft); - sqlite3ExplainPrintf(pOut, ","); - if( ExprHasProperty(pExpr, EP_xIsSelect) ){ - sqlite3ExplainSelect(pOut, pExpr->x.pSelect); - }else{ - sqlite3ExplainExprList(pOut, pExpr->x.pList); - } - sqlite3ExplainPrintf(pOut, ")"); - break; - } -#endif /* SQLITE_OMIT_SUBQUERY */ - - /* - ** x BETWEEN y AND z - ** - ** This is equivalent to - ** - ** x>=y AND x<=z - ** - ** X is stored in pExpr->pLeft. - ** Y is stored in pExpr->pList->a[0].pExpr. - ** Z is stored in pExpr->pList->a[1].pExpr. - */ - case TK_BETWEEN: { - Expr *pX = pExpr->pLeft; - Expr *pY = pExpr->x.pList->a[0].pExpr; - Expr *pZ = pExpr->x.pList->a[1].pExpr; - sqlite3ExplainPrintf(pOut, "BETWEEN("); - sqlite3ExplainExpr(pOut, pX); - sqlite3ExplainPrintf(pOut, ","); - sqlite3ExplainExpr(pOut, pY); - sqlite3ExplainPrintf(pOut, ","); - sqlite3ExplainExpr(pOut, pZ); - sqlite3ExplainPrintf(pOut, ")"); - break; - } - case TK_TRIGGER: { - /* If the opcode is TK_TRIGGER, then the expression is a reference - ** to a column in the new.* or old.* pseudo-tables available to - ** trigger programs. In this case Expr.iTable is set to 1 for the - ** new.* pseudo-table, or 0 for the old.* pseudo-table. Expr.iColumn - ** is set to the column of the pseudo-table to read, or to -1 to - ** read the rowid field. - */ - sqlite3ExplainPrintf(pOut, "%s(%d)", - pExpr->iTable ? "NEW" : "OLD", pExpr->iColumn); - break; - } - case TK_CASE: { - sqlite3ExplainPrintf(pOut, "CASE("); - sqlite3ExplainExpr(pOut, pExpr->pLeft); - sqlite3ExplainPrintf(pOut, ","); - sqlite3ExplainExprList(pOut, pExpr->x.pList); - break; - } -#ifndef SQLITE_OMIT_TRIGGER - case TK_RAISE: { - const char *zType = "unk"; - switch( pExpr->affinity ){ - case OE_Rollback: zType = "rollback"; break; - case OE_Abort: zType = "abort"; break; - case OE_Fail: zType = "fail"; break; - case OE_Ignore: zType = "ignore"; break; - } - sqlite3ExplainPrintf(pOut, "RAISE-%s(%s)", zType, pExpr->u.zToken); - break; - } -#endif - } - if( zBinOp ){ - sqlite3ExplainPrintf(pOut,"%s(", zBinOp); - sqlite3ExplainExpr(pOut, pExpr->pLeft); - sqlite3ExplainPrintf(pOut,","); - sqlite3ExplainExpr(pOut, pExpr->pRight); - sqlite3ExplainPrintf(pOut,")"); - }else if( zUniOp ){ - sqlite3ExplainPrintf(pOut,"%s(", zUniOp); - sqlite3ExplainExpr(pOut, pExpr->pLeft); - sqlite3ExplainPrintf(pOut,")"); - } -} -#endif /* defined(SQLITE_ENABLE_TREE_EXPLAIN) */ - -#if defined(SQLITE_ENABLE_TREE_EXPLAIN) -/* -** Generate a human-readable explanation of an expression list. -*/ -SQLITE_PRIVATE void sqlite3ExplainExprList(Vdbe *pOut, ExprList *pList){ - int i; - if( pList==0 || pList->nExpr==0 ){ - sqlite3ExplainPrintf(pOut, "(empty-list)"); - return; - }else if( pList->nExpr==1 ){ - sqlite3ExplainExpr(pOut, pList->a[0].pExpr); - }else{ - sqlite3ExplainPush(pOut); - for(i=0; inExpr; i++){ - sqlite3ExplainPrintf(pOut, "item[%d] = ", i); - sqlite3ExplainPush(pOut); - sqlite3ExplainExpr(pOut, pList->a[i].pExpr); - sqlite3ExplainPop(pOut); - if( pList->a[i].zName ){ - sqlite3ExplainPrintf(pOut, " AS %s", pList->a[i].zName); - } - if( pList->a[i].bSpanIsTab ){ - sqlite3ExplainPrintf(pOut, " (%s)", pList->a[i].zSpan); - } - if( inExpr-1 ){ - sqlite3ExplainNL(pOut); - } - } - sqlite3ExplainPop(pOut); - } -} -#endif /* SQLITE_DEBUG */ - /* ** Generate code that pushes the value of every element of the given ** expression list into a sequence of registers beginning at target. @@ -81016,16 +89286,22 @@ SQLITE_PRIVATE void sqlite3ExplainExprList(Vdbe *pOut, ExprList *pList){ ** ** The SQLITE_ECEL_FACTOR argument allows constant arguments to be ** factored out into initialization code. +** +** The SQLITE_ECEL_REF flag means that expressions in the list with +** ExprList.a[].u.x.iOrderByCol>0 have already been evaluated and stored +** in registers at srcReg, and so the value can be copied from there. */ SQLITE_PRIVATE int sqlite3ExprCodeExprList( Parse *pParse, /* Parsing context */ ExprList *pList, /* The expression list to be coded */ int target, /* Where to write results */ + int srcReg, /* Source registers if SQLITE_ECEL_REF */ u8 flags /* SQLITE_ECEL_* flags */ ){ struct ExprList_item *pItem; - int i, n; + int i, j, n; u8 copyOp = (flags & SQLITE_ECEL_DUP) ? OP_Copy : OP_SCopy; + Vdbe *v = pParse->pVdbe; assert( pList!=0 ); assert( target>0 ); assert( pParse->pVdbe!=0 ); /* Never gets this far otherwise */ @@ -81033,13 +89309,14 @@ SQLITE_PRIVATE int sqlite3ExprCodeExprList( if( !ConstFactorOk(pParse) ) flags &= ~SQLITE_ECEL_FACTOR; for(pItem=pList->a, i=0; ipExpr; - if( (flags & SQLITE_ECEL_FACTOR)!=0 && sqlite3ExprIsConstant(pExpr) ){ + if( (flags & SQLITE_ECEL_REF)!=0 && (j = pList->a[i].u.x.iOrderByCol)>0 ){ + sqlite3VdbeAddOp2(v, copyOp, j+srcReg-1, target+i); + }else if( (flags & SQLITE_ECEL_FACTOR)!=0 && sqlite3ExprIsConstant(pExpr) ){ sqlite3ExprCodeAtInit(pParse, pExpr, target+i, 0); }else{ int inReg = sqlite3ExprCodeTarget(pParse, pExpr, target+i); if( inReg!=target+i ){ VdbeOp *pOp; - Vdbe *v = pParse->pVdbe; if( copyOp==OP_Copy && (pOp=sqlite3VdbeGetOp(v, -1))->opcode==OP_Copy && pOp->p1+pOp->p3+1==inReg @@ -81065,7 +89342,7 @@ SQLITE_PRIVATE int sqlite3ExprCodeExprList( ** x>=y AND x<=z ** ** Code it as such, taking care to do the common subexpression -** elementation of x. +** elimination of x. */ static void exprCodeBetween( Parse *pParse, /* Parsing and code generating context */ @@ -81216,14 +89493,14 @@ SQLITE_PRIVATE void sqlite3ExprIfTrue(Parse *pParse, Expr *pExpr, int dest, int int destIfFalse = sqlite3VdbeMakeLabel(v); int destIfNull = jumpIfNull ? dest : destIfFalse; sqlite3ExprCodeIN(pParse, pExpr, destIfFalse, destIfNull); - sqlite3VdbeAddOp2(v, OP_Goto, 0, dest); + sqlite3VdbeGoto(v, dest); sqlite3VdbeResolveLabel(v, destIfFalse); break; } #endif default: { if( exprAlwaysTrue(pExpr) ){ - sqlite3VdbeAddOp2(v, OP_Goto, 0, dest); + sqlite3VdbeGoto(v, dest); }else if( exprAlwaysFalse(pExpr) ){ /* No-op */ }else{ @@ -81379,7 +89656,7 @@ SQLITE_PRIVATE void sqlite3ExprIfFalse(Parse *pParse, Expr *pExpr, int dest, int #endif default: { if( exprAlwaysFalse(pExpr) ){ - sqlite3VdbeAddOp2(v, OP_Goto, 0, dest); + sqlite3VdbeGoto(v, dest); }else if( exprAlwaysTrue(pExpr) ){ /* no-op */ }else{ @@ -81396,6 +89673,21 @@ SQLITE_PRIVATE void sqlite3ExprIfFalse(Parse *pParse, Expr *pExpr, int dest, int sqlite3ReleaseTempReg(pParse, regFree2); } +/* +** Like sqlite3ExprIfFalse() except that a copy is made of pExpr before +** code generation, and that copy is deleted after code generation. This +** ensures that the original pExpr is unchanged. +*/ +SQLITE_PRIVATE void sqlite3ExprIfFalseDup(Parse *pParse, Expr *pExpr, int dest,int jumpIfNull){ + sqlite3 *db = pParse->db; + Expr *pCopy = sqlite3ExprDup(db, pExpr, 0); + if( db->mallocFailed==0 ){ + sqlite3ExprIfFalse(pParse, pCopy, dest, jumpIfNull); + } + sqlite3ExprDelete(db, pCopy); +} + + /* ** Do a deep comparison of two expression trees. Return 0 if the two ** expressions are completely identical. Return 1 if they differ only @@ -81439,8 +89731,10 @@ SQLITE_PRIVATE int sqlite3ExprCompare(Expr *pA, Expr *pB, int iTab){ } return 2; } - if( pA->op!=TK_COLUMN && ALWAYS(pA->op!=TK_AGG_COLUMN) && pA->u.zToken ){ - if( strcmp(pA->u.zToken,pB->u.zToken)!=0 ){ + if( pA->op!=TK_COLUMN && pA->op!=TK_AGG_COLUMN && pA->u.zToken ){ + if( pA->op==TK_FUNCTION ){ + if( sqlite3StrICmp(pA->u.zToken,pB->u.zToken)!=0 ) return 2; + }else if( strcmp(pA->u.zToken,pB->u.zToken)!=0 ){ return pA->op==TK_COLLATE ? 1 : 2; } } @@ -81450,7 +89744,7 @@ SQLITE_PRIVATE int sqlite3ExprCompare(Expr *pA, Expr *pB, int iTab){ if( sqlite3ExprCompare(pA->pLeft, pB->pLeft, iTab) ) return 2; if( sqlite3ExprCompare(pA->pRight, pB->pRight, iTab) ) return 2; if( sqlite3ExprListCompare(pA->x.pList, pB->x.pList, iTab) ) return 2; - if( ALWAYS((combinedFlags & EP_Reduced)==0) ){ + if( ALWAYS((combinedFlags & EP_Reduced)==0) && pA->op!=TK_STRING ){ if( pA->iColumn!=pB->iColumn ) return 2; if( pA->iTable!=pB->iTable && (pA->iTable!=iTab || NEVER(pB->iTable>=0)) ) return 2; @@ -81552,10 +89846,11 @@ static int exprSrcCount(Walker *pWalker, Expr *pExpr){ int i; struct SrcCount *p = pWalker->u.pSrcCount; SrcList *pSrc = p->pSrc; - for(i=0; inSrc; i++){ + int nSrc = pSrc ? pSrc->nSrc : 0; + for(i=0; iiTable==pSrc->a[i].iCursor ) break; } - if( inSrc ){ + if( inThis++; }else{ p->nOther++; @@ -81802,7 +90097,7 @@ SQLITE_PRIVATE int sqlite3GetTempReg(Parse *pParse){ ** purpose. ** ** If a register is currently being used by the column cache, then -** the dallocation is deferred until the column cache line that uses +** the deallocation is deferred until the column cache line that uses ** the register becomes stale. */ SQLITE_PRIVATE void sqlite3ReleaseTempReg(Parse *pParse, int iReg){ @@ -81868,6 +90163,7 @@ SQLITE_PRIVATE void sqlite3ClearTempRegCache(Parse *pParse){ ** This file contains C code routines that used to generate VDBE code ** that implements the ALTER TABLE command. */ +/* #include "sqliteInt.h" */ /* ** The code in this file only exists if we are not omitting the @@ -81981,6 +90277,7 @@ static void renameParentFunc( n = sqlite3GetToken(z, &token); }while( token==TK_SPACE ); + if( token==TK_ILLEGAL ) break; zParent = sqlite3DbStrNDup(db, (const char *)z, n); if( zParent==0 ) break; sqlite3Dequote(zParent); @@ -82029,8 +90326,8 @@ static void renameTriggerFunc( UNUSED_PARAMETER(NotUsed); /* The principle used to locate the table name in the CREATE TRIGGER - ** statement is that the table name is the first token that is immediatedly - ** preceded by either TK_ON or TK_DOT and immediatedly followed by one + ** statement is that the table name is the first token that is immediately + ** preceded by either TK_ON or TK_DOT and immediately followed by one ** of TK_WHEN, TK_BEGIN or TK_FOR. */ if( zSql ){ @@ -82345,7 +90642,7 @@ SQLITE_PRIVATE void sqlite3AlterRenameTable( #ifndef SQLITE_OMIT_VIRTUALTABLE if( pVTab ){ int i = ++pParse->nMem; - sqlite3VdbeAddOp4(v, OP_String8, 0, i, 0, zName, 0); + sqlite3VdbeLoadString(v, i, zName); sqlite3VdbeAddOp4(v, OP_VRename, i, 0, 0,(const char*)pVTab, P4_VTAB); sqlite3MayAbort(pParse); } @@ -82456,14 +90753,14 @@ SQLITE_PRIVATE void sqlite3MinimumFileFormat(Parse *pParse, int iDb, int minForm if( ALWAYS(v) ){ int r1 = sqlite3GetTempReg(pParse); int r2 = sqlite3GetTempReg(pParse); - int j1; + int addr1; sqlite3VdbeAddOp3(v, OP_ReadCookie, iDb, r1, BTREE_FILE_FORMAT); sqlite3VdbeUsesBtree(v, iDb); sqlite3VdbeAddOp2(v, OP_Integer, minFormat, r2); - j1 = sqlite3VdbeAddOp3(v, OP_Ge, r2, 0, r1); + addr1 = sqlite3VdbeAddOp3(v, OP_Ge, r2, 0, r1); sqlite3VdbeChangeP5(v, SQLITE_NOTNULL); VdbeCoverage(v); sqlite3VdbeAddOp3(v, OP_SetCookie, iDb, BTREE_FILE_FORMAT, r2); - sqlite3VdbeJumpHere(v, j1); + sqlite3VdbeJumpHere(v, addr1); sqlite3ReleaseTempReg(pParse, r1); sqlite3ReleaseTempReg(pParse, r2); } @@ -82545,7 +90842,10 @@ SQLITE_PRIVATE void sqlite3AlterFinishAddColumn(Parse *pParse, Token *pColDef){ */ if( pDflt ){ sqlite3_value *pVal = 0; - if( sqlite3ValueFromExpr(db, pDflt, SQLITE_UTF8, SQLITE_AFF_NONE, &pVal) ){ + int rc; + rc = sqlite3ValueFromExpr(db, pDflt, SQLITE_UTF8, SQLITE_AFF_BLOB, &pVal); + assert( rc==SQLITE_OK || rc==SQLITE_NOMEM ); + if( rc!=SQLITE_OK ){ db->mallocFailed = 1; return; } @@ -82721,7 +91021,7 @@ exit_begin_add_column: ** not possible to enable both STAT3 and STAT4 at the same time. If they ** are both enabled, then STAT4 takes precedence. ** -** For most applications, sqlite_stat1 provides all the statisics required +** For most applications, sqlite_stat1 provides all the statistics required ** for the query planner to make good choices. ** ** Format of sqlite_stat1: @@ -82826,6 +91126,7 @@ exit_begin_add_column: ** integer in the equivalent columns in sqlite_stat4. */ #ifndef SQLITE_OMIT_ANALYZE +/* #include "sqliteInt.h" */ #if defined(SQLITE_ENABLE_STAT4) # define IsStat4 1 @@ -82931,6 +91232,7 @@ static void openStatTable( assert( i1 ); /* >1 because it includes the rowid column */ + assert( nCol>0 ); nColUp = sizeof(tRowcnt)<8 ? (nCol+1)&~1 : nCol; + nKeyCol = sqlite3_value_int(argv[1]); + assert( nKeyCol<=nCol ); + assert( nKeyCol>0 ); /* Allocate the space required for the Stat4Accum object */ n = sizeof(*p) @@ -83100,6 +91421,7 @@ static void statInit( p->db = db; p->nRow = 0; p->nCol = nCol; + p->nKeyCol = nKeyCol; p->current.anDLt = (tRowcnt*)&p[1]; p->current.anEq = &p->current.anDLt[nColUp]; @@ -83110,9 +91432,9 @@ static void statInit( p->iGet = -1; p->mxSample = mxSample; - p->nPSample = (tRowcnt)(sqlite3_value_int64(argv[1])/(mxSample/3+1) + 1); + p->nPSample = (tRowcnt)(sqlite3_value_int64(argv[2])/(mxSample/3+1) + 1); p->current.anLt = &p->current.anEq[nColUp]; - p->iPrn = nCol*0x689e962d ^ sqlite3_value_int(argv[1])*0xd0944565; + p->iPrn = 0x689e962d*(u32)nCol ^ 0xd0944565*(u32)sqlite3_value_int(argv[2]); /* Set up the Stat4Accum.a[] and aBest[] arrays */ p->a = (struct Stat4Sample*)&p->current.anLt[nColUp]; @@ -83131,11 +91453,14 @@ static void statInit( } #endif - /* Return a pointer to the allocated object to the caller */ - sqlite3_result_blob(context, p, sizeof(p), stat4Destructor); + /* Return a pointer to the allocated object to the caller. Note that + ** only the pointer (the 2nd parameter) matters. The size of the object + ** (given by the 3rd parameter) is never used and can be any positive + ** value. */ + sqlite3_result_blob(context, p, sizeof(*p), stat4Destructor); } static const FuncDef statInitFuncdef = { - 1+IsStat34, /* nArg */ + 2+IsStat34, /* nArg */ SQLITE_UTF8, /* funcFlags */ 0, /* pUserData */ 0, /* pNext */ @@ -83359,7 +91684,10 @@ static void samplePushPrevious(Stat4Accum *p, int iChng){ ** R Rowid for the current row. Might be a key record for ** WITHOUT ROWID tables. ** -** The SQL function always returns NULL. +** This SQL function always returns NULL. It's purpose it to accumulate +** statistical data and/or samples in the Stat4Accum object about the +** index being analyzed. The stat_get() SQL function will later be used to +** extract relevant information for constructing the sqlite_statN tables. ** ** The R parameter is only used for STAT3 and STAT4 */ @@ -83376,7 +91704,7 @@ static void statPush( UNUSED_PARAMETER( argc ); UNUSED_PARAMETER( context ); - assert( p->nCol>1 ); /* Includes rowid field */ + assert( p->nCol>0 ); assert( iChngnCol ); if( p->nRow==0 ){ @@ -83453,7 +91781,10 @@ static const FuncDef statPushFuncdef = { /* ** Implementation of the stat_get(P,J) SQL function. This routine is -** used to query the results. Content is returned for parameter J +** used to query statistical information that has been gathered into +** the Stat4Accum object by prior calls to stat_push(). The P parameter +** has type BLOB but it is really just a pointer to the Stat4Accum object. +** The content to returned is determined by the parameter J ** which is one of the STAT_GET_xxxx values defined above. ** ** If neither STAT3 nor STAT4 are enabled, then J is always @@ -83504,7 +91835,7 @@ static void statGet( char *z; int i; - char *zRet = sqlite3MallocZero(p->nCol * 25); + char *zRet = sqlite3MallocZero( (p->nKeyCol+1)*25 ); if( zRet==0 ){ sqlite3_result_error_nomem(context); return; @@ -83512,7 +91843,7 @@ static void statGet( sqlite3_snprintf(24, zRet, "%llu", (u64)p->nRow); z = zRet + sqlite3Strlen30(zRet); - for(i=0; i<(p->nCol-1); i++){ + for(i=0; inKeyCol; i++){ u64 nDistinct = p->current.anDLt[i] + 1; u64 iVal = (p->nRow + nDistinct - 1) / nDistinct; sqlite3_snprintf(24, z, " %llu", iVal); @@ -83598,7 +91929,7 @@ static void callStatGet(Vdbe *v, int regStat4, int iParam, int regOut){ #else UNUSED_PARAMETER( iParam ); #endif - sqlite3VdbeAddOp3(v, OP_Function, 0, regStat4, regOut); + sqlite3VdbeAddOp3(v, OP_Function0, 0, regStat4, regOut); sqlite3VdbeChangeP4(v, -1, (char*)&statGetFuncdef, P4_FUNCDEF); sqlite3VdbeChangeP5(v, 1 + IsStat34); } @@ -83645,7 +91976,7 @@ static void analyzeOneTable( /* Do not gather statistics on views or virtual tables */ return; } - if( sqlite3_strnicmp(pTab->zName, "sqlite_", 7)==0 ){ + if( sqlite3_strlike("sqlite_%", pTab->zName, 0)==0 ){ /* Do not gather statistics on system tables */ return; } @@ -83669,30 +92000,30 @@ static void analyzeOneTable( iIdxCur = iTab++; pParse->nTab = MAX(pParse->nTab, iTab); sqlite3OpenTable(pParse, iTabCur, iDb, pTab, OP_OpenRead); - sqlite3VdbeAddOp4(v, OP_String8, 0, regTabname, 0, pTab->zName, 0); + sqlite3VdbeLoadString(v, regTabname, pTab->zName); for(pIdx=pTab->pIndex; pIdx; pIdx=pIdx->pNext){ - int nCol; /* Number of columns indexed by pIdx */ - int *aGotoChng; /* Array of jump instruction addresses */ + int nCol; /* Number of columns in pIdx. "N" */ int addrRewind; /* Address of "OP_Rewind iIdxCur" */ - int addrGotoChng0; /* Address of "Goto addr_chng_0" */ int addrNextRow; /* Address of "next_row:" */ const char *zIdxName; /* Name of the index */ + int nColTest; /* Number of columns to test for changes */ if( pOnlyIdx && pOnlyIdx!=pIdx ) continue; if( pIdx->pPartIdxWhere==0 ) needTableCnt = 0; - VdbeNoopComment((v, "Begin analysis of %s", pIdx->zName)); - nCol = pIdx->nKeyCol; - aGotoChng = sqlite3DbMallocRaw(db, sizeof(int)*(nCol+1)); - if( aGotoChng==0 ) continue; + if( !HasRowid(pTab) && IsPrimaryKeyIndex(pIdx) ){ + nCol = pIdx->nKeyCol; + zIdxName = pTab->zName; + nColTest = nCol - 1; + }else{ + nCol = pIdx->nColumn; + zIdxName = pIdx->zName; + nColTest = pIdx->uniqNotNull ? pIdx->nKeyCol-1 : nCol-1; + } /* Populate the register containing the index name. */ - if( IsPrimaryKeyIndex(pIdx) && !HasRowid(pTab) ){ - zIdxName = pTab->zName; - }else{ - zIdxName = pIdx->zName; - } - sqlite3VdbeAddOp4(v, OP_String8, 0, regIdxname, 0, zIdxName, 0); + sqlite3VdbeLoadString(v, regIdxname, zIdxName); + VdbeComment((v, "Analysis for %s.%s", pTab->zName, zIdxName)); /* ** Pseudo-code for loop that calls stat_push(): @@ -83717,7 +92048,7 @@ static void analyzeOneTable( ** regPrev(1) = idx(1) ** ... ** - ** chng_addr_N: + ** endDistinctTest: ** regRowid = idx(rowid) ** stat_push(P, regChng, regRowid) ** Next csr @@ -83730,7 +92061,7 @@ static void analyzeOneTable( ** the regPrev array and a trailing rowid (the rowid slot is required ** when building a record to insert into the sample column of ** the sqlite_stat4 table. */ - pParse->nMem = MAX(pParse->nMem, regPrev+nCol); + pParse->nMem = MAX(pParse->nMem, regPrev+nColTest); /* Open a read-only cursor on the index being analyzed. */ assert( iDb==sqlite3SchemaToIndex(db, pIdx->pSchema) ); @@ -83740,18 +92071,22 @@ static void analyzeOneTable( /* Invoke the stat_init() function. The arguments are: ** - ** (1) the number of columns in the index including the rowid, - ** (2) the number of rows in the index, + ** (1) the number of columns in the index including the rowid + ** (or for a WITHOUT ROWID table, the number of PK columns), + ** (2) the number of columns in the key without the rowid/pk + ** (3) the number of rows in the index, ** - ** The second argument is only used for STAT3 and STAT4 + ** + ** The third argument is only used for STAT3 and STAT4 */ #ifdef SQLITE_ENABLE_STAT3_OR_STAT4 - sqlite3VdbeAddOp2(v, OP_Count, iIdxCur, regStat4+2); + sqlite3VdbeAddOp2(v, OP_Count, iIdxCur, regStat4+3); #endif - sqlite3VdbeAddOp2(v, OP_Integer, nCol+1, regStat4+1); - sqlite3VdbeAddOp3(v, OP_Function, 0, regStat4+1, regStat4); + sqlite3VdbeAddOp2(v, OP_Integer, nCol, regStat4+1); + sqlite3VdbeAddOp2(v, OP_Integer, pIdx->nKeyCol, regStat4+2); + sqlite3VdbeAddOp3(v, OP_Function0, 0, regStat4+1, regStat4); sqlite3VdbeChangeP4(v, -1, (char*)&statInitFuncdef, P4_FUNCDEF); - sqlite3VdbeChangeP5(v, 1+IsStat34); + sqlite3VdbeChangeP5(v, 2+IsStat34); /* Implementation of the following: ** @@ -83764,44 +92099,62 @@ static void analyzeOneTable( addrRewind = sqlite3VdbeAddOp1(v, OP_Rewind, iIdxCur); VdbeCoverage(v); sqlite3VdbeAddOp2(v, OP_Integer, 0, regChng); - addrGotoChng0 = sqlite3VdbeAddOp0(v, OP_Goto); - - /* - ** next_row: - ** regChng = 0 - ** if( idx(0) != regPrev(0) ) goto chng_addr_0 - ** regChng = 1 - ** if( idx(1) != regPrev(1) ) goto chng_addr_1 - ** ... - ** regChng = N - ** goto chng_addr_N - */ addrNextRow = sqlite3VdbeCurrentAddr(v); - for(i=0; iazColl[i]); - sqlite3VdbeAddOp2(v, OP_Integer, i, regChng); - sqlite3VdbeAddOp3(v, OP_Column, iIdxCur, i, regTemp); - aGotoChng[i] = - sqlite3VdbeAddOp4(v, OP_Ne, regTemp, 0, regPrev+i, pColl, P4_COLLSEQ); - sqlite3VdbeChangeP5(v, SQLITE_NULLEQ); - VdbeCoverage(v); - } - sqlite3VdbeAddOp2(v, OP_Integer, nCol, regChng); - aGotoChng[nCol] = sqlite3VdbeAddOp0(v, OP_Goto); - /* - ** chng_addr_0: - ** regPrev(0) = idx(0) - ** chng_addr_1: - ** regPrev(1) = idx(1) - ** ... - */ - sqlite3VdbeJumpHere(v, addrGotoChng0); - for(i=0; i0 ){ + int endDistinctTest = sqlite3VdbeMakeLabel(v); + int *aGotoChng; /* Array of jump instruction addresses */ + aGotoChng = sqlite3DbMallocRaw(db, sizeof(int)*nColTest); + if( aGotoChng==0 ) continue; + /* + ** next_row: + ** regChng = 0 + ** if( idx(0) != regPrev(0) ) goto chng_addr_0 + ** regChng = 1 + ** if( idx(1) != regPrev(1) ) goto chng_addr_1 + ** ... + ** regChng = N + ** goto endDistinctTest + */ + sqlite3VdbeAddOp0(v, OP_Goto); + addrNextRow = sqlite3VdbeCurrentAddr(v); + if( nColTest==1 && pIdx->nKeyCol==1 && IsUniqueIndex(pIdx) ){ + /* For a single-column UNIQUE index, once we have found a non-NULL + ** row, we know that all the rest will be distinct, so skip + ** subsequent distinctness tests. */ + sqlite3VdbeAddOp2(v, OP_NotNull, regPrev, endDistinctTest); + VdbeCoverage(v); + } + for(i=0; iazColl[i]); + sqlite3VdbeAddOp2(v, OP_Integer, i, regChng); + sqlite3VdbeAddOp3(v, OP_Column, iIdxCur, i, regTemp); + aGotoChng[i] = + sqlite3VdbeAddOp4(v, OP_Ne, regTemp, 0, regPrev+i, pColl, P4_COLLSEQ); + sqlite3VdbeChangeP5(v, SQLITE_NULLEQ); + VdbeCoverage(v); + } + sqlite3VdbeAddOp2(v, OP_Integer, nColTest, regChng); + sqlite3VdbeGoto(v, endDistinctTest); + + + /* + ** chng_addr_0: + ** regPrev(0) = idx(0) + ** chng_addr_1: + ** regPrev(1) = idx(1) + ** ... + */ + sqlite3VdbeJumpHere(v, addrNextRow-1); + for(i=0; inKeyCol); for(j=0; jnKeyCol; j++){ k = sqlite3ColumnOfIndex(pIdx, pPk->aiColumn[j]); + assert( k>=0 && knCol ); sqlite3VdbeAddOp3(v, OP_Column, iIdxCur, k, regKey+j); VdbeComment((v, "%s", pTab->aCol[pPk->aiColumn[j]].zName)); } @@ -83828,14 +92181,15 @@ static void analyzeOneTable( } #endif assert( regChng==(regStat4+1) ); - sqlite3VdbeAddOp3(v, OP_Function, 1, regStat4, regTemp); + sqlite3VdbeAddOp3(v, OP_Function0, 1, regStat4, regTemp); sqlite3VdbeChangeP4(v, -1, (char*)&statPushFuncdef, P4_FUNCDEF); sqlite3VdbeChangeP5(v, 2+IsStat34); sqlite3VdbeAddOp2(v, OP_Next, iIdxCur, addrNextRow); VdbeCoverage(v); /* Add the entry to the stat1 table. */ callStatGet(v, regStat4, STAT_GET_STAT1, regStat1); - sqlite3VdbeAddOp4(v, OP_MakeRecord, regTabname, 3, regTemp, "aaa", 0); + assert( "BBB"[0]==SQLITE_AFF_TEXT ); + sqlite3VdbeAddOp4(v, OP_MakeRecord, regTabname, 3, regTemp, "BBB", 0); sqlite3VdbeAddOp2(v, OP_NewRowid, iStatCur, regNewRowid); sqlite3VdbeAddOp3(v, OP_Insert, iStatCur, regTemp, regNewRowid); sqlite3VdbeChangeP5(v, OPFLAG_APPEND); @@ -83853,7 +92207,7 @@ static void analyzeOneTable( int addrIsNull; u8 seekOp = HasRowid(pTab) ? OP_NotExists : OP_NotFound; - pParse->nMem = MAX(pParse->nMem, regCol+nCol+1); + pParse->nMem = MAX(pParse->nMem, regCol+nCol); addrNext = sqlite3VdbeCurrentAddr(v); callStatGet(v, regStat4, STAT_GET_ROWID, regSampleRowid); @@ -83868,14 +92222,12 @@ static void analyzeOneTable( ** be taken */ VdbeCoverageNeverTaken(v); #ifdef SQLITE_ENABLE_STAT3 - sqlite3ExprCodeGetColumnOfTable(v, pTab, iTabCur, - pIdx->aiColumn[0], regSample); + sqlite3ExprCodeLoadIndexColumn(pParse, pIdx, iTabCur, 0, regSample); #else for(i=0; iaiColumn[i]; - sqlite3ExprCodeGetColumnOfTable(v, pTab, iTabCur, iCol, regCol+i); + sqlite3ExprCodeLoadIndexColumn(pParse, pIdx, iTabCur, i, regCol+i); } - sqlite3VdbeAddOp3(v, OP_MakeRecord, regCol, nCol+1, regSample); + sqlite3VdbeAddOp3(v, OP_MakeRecord, regCol, nCol, regSample); #endif sqlite3VdbeAddOp3(v, OP_MakeRecord, regTabname, 6, regTemp); sqlite3VdbeAddOp2(v, OP_NewRowid, iStatCur+1, regNewRowid); @@ -83887,7 +92239,6 @@ static void analyzeOneTable( /* End of analysis */ sqlite3VdbeJumpHere(v, addrRewind); - sqlite3DbFree(db, aGotoChng); } @@ -83899,7 +92250,8 @@ static void analyzeOneTable( sqlite3VdbeAddOp2(v, OP_Count, iTabCur, regStat1); jZeroRows = sqlite3VdbeAddOp1(v, OP_IfNot, regStat1); VdbeCoverage(v); sqlite3VdbeAddOp2(v, OP_Null, 0, regIdxname); - sqlite3VdbeAddOp4(v, OP_MakeRecord, regTabname, 3, regTemp, "aaa", 0); + assert( "BBB"[0]==SQLITE_AFF_TEXT ); + sqlite3VdbeAddOp4(v, OP_MakeRecord, regTabname, 3, regTemp, "BBB", 0); sqlite3VdbeAddOp2(v, OP_NewRowid, iStatCur, regNewRowid); sqlite3VdbeAddOp3(v, OP_Insert, iStatCur, regTemp, regNewRowid); sqlite3VdbeChangeP5(v, OPFLAG_APPEND); @@ -83988,6 +92340,7 @@ SQLITE_PRIVATE void sqlite3Analyze(Parse *pParse, Token *pName1, Token *pName2){ Table *pTab; Index *pIdx; Token *pTableName; + Vdbe *v; /* Read the database schema. If an error occurs, leave an error message ** and code in pParse and return NULL. */ @@ -84035,6 +92388,8 @@ SQLITE_PRIVATE void sqlite3Analyze(Parse *pParse, Token *pName1, Token *pName2){ } } } + v = sqlite3GetVdbe(pParse); + if( v ) sqlite3VdbeAddOp0(v, OP_Expire); } /* @@ -84067,7 +92422,7 @@ static void decodeIntArray( #ifdef SQLITE_ENABLE_STAT3_OR_STAT4 if( z==0 ) z = ""; #else - if( NEVER(z==0) ) z = ""; + assert( z!=0 ); #endif for(i=0; *z && ibUnordered = 1; - }else if( sqlite3_strglob("sz=[0-9]*", z)==0 ){ - int v32 = 0; - sqlite3GetInt32(z+3, &v32); - pIndex->szIdxRow = sqlite3LogEst(v32); + pIndex->bUnordered = 0; + pIndex->noSkipScan = 0; + while( z[0] ){ + if( sqlite3_strglob("unordered*", z)==0 ){ + pIndex->bUnordered = 1; + }else if( sqlite3_strglob("sz=[0-9]*", z)==0 ){ + pIndex->szIdxRow = sqlite3LogEst(sqlite3Atoi(z+3)); + }else if( sqlite3_strglob("noskipscan*", z)==0 ){ + pIndex->noSkipScan = 1; + } +#ifdef SQLITE_ENABLE_COSTMULT + else if( sqlite3_strglob("costmult=[0-9]*",z)==0 ){ + pIndex->pTable->costMult = sqlite3LogEst(sqlite3Atoi(z+9)); + } +#endif + while( z[0]!=0 && z[0]!=' ' ) z++; + while( z[0]==' ' ) z++; } } } @@ -84141,11 +92504,27 @@ static int analysisLoader(void *pData, int argc, char **argv, char **NotUsed){ z = argv[2]; if( pIndex ){ - decodeIntArray((char*)z, pIndex->nKeyCol+1, 0, pIndex->aiRowLogEst, pIndex); + tRowcnt *aiRowEst = 0; + int nCol = pIndex->nKeyCol+1; +#ifdef SQLITE_ENABLE_STAT3_OR_STAT4 + /* Index.aiRowEst may already be set here if there are duplicate + ** sqlite_stat1 entries for this index. In that case just clobber + ** the old data with the new instead of allocating a new array. */ + if( pIndex->aiRowEst==0 ){ + pIndex->aiRowEst = (tRowcnt*)sqlite3MallocZero(sizeof(tRowcnt) * nCol); + if( pIndex->aiRowEst==0 ) pInfo->db->mallocFailed = 1; + } + aiRowEst = pIndex->aiRowEst; +#endif + pIndex->bUnordered = 0; + decodeIntArray((char*)z, nCol, aiRowEst, pIndex->aiRowLogEst, pIndex); if( pIndex->pPartIdxWhere==0 ) pTable->nRowLogEst = pIndex->aiRowLogEst[0]; }else{ Index fakeIdx; fakeIdx.szIdxRow = pTable->szTabRow; +#ifdef SQLITE_ENABLE_COSTMULT + fakeIdx.pTable = pTable; +#endif decodeIntArray((char*)z, 1, 0, &pTable->nRowLogEst, &fakeIdx); pTable->szTabRow = fakeIdx.szIdxRow; } @@ -84187,30 +92566,52 @@ static void initAvgEq(Index *pIdx){ IndexSample *aSample = pIdx->aSample; IndexSample *pFinal = &aSample[pIdx->nSample-1]; int iCol; - for(iCol=0; iColnKeyCol; iCol++){ + int nCol = 1; + if( pIdx->nSampleCol>1 ){ + /* If this is stat4 data, then calculate aAvgEq[] values for all + ** sample columns except the last. The last is always set to 1, as + ** once the trailing PK fields are considered all index keys are + ** unique. */ + nCol = pIdx->nSampleCol-1; + pIdx->aAvgEq[nCol] = 1; + } + for(iCol=0; iColnSample; int i; /* Used to iterate through samples */ tRowcnt sumEq = 0; /* Sum of the nEq values */ - tRowcnt nSum = 0; /* Number of terms contributing to sumEq */ tRowcnt avgEq = 0; - tRowcnt nDLt = pFinal->anDLt[iCol]; + tRowcnt nRow; /* Number of rows in index */ + i64 nSum100 = 0; /* Number of terms contributing to sumEq */ + i64 nDist100; /* Number of distinct values in index */ + + if( !pIdx->aiRowEst || iCol>=pIdx->nKeyCol || pIdx->aiRowEst[iCol+1]==0 ){ + nRow = pFinal->anLt[iCol]; + nDist100 = (i64)100 * pFinal->anDLt[iCol]; + nSample--; + }else{ + nRow = pIdx->aiRowEst[0]; + nDist100 = ((i64)100 * pIdx->aiRowEst[0]) / pIdx->aiRowEst[iCol+1]; + } + pIdx->nRowEst0 = nRow; /* Set nSum to the number of distinct (iCol+1) field prefixes that - ** occur in the stat4 table for this index before pFinal. Set - ** sumEq to the sum of the nEq values for column iCol for the same - ** set (adding the value only once where there exist dupicate - ** prefixes). */ - for(i=0; i<(pIdx->nSample-1); i++){ - if( aSample[i].anDLt[iCol]!=aSample[i+1].anDLt[iCol] ){ + ** occur in the stat4 table for this index. Set sumEq to the sum of + ** the nEq values for column iCol for the same set (adding the value + ** only once where there exist duplicate prefixes). */ + for(i=0; inSample-1) + || aSample[i].anDLt[iCol]!=aSample[i+1].anDLt[iCol] + ){ sumEq += aSample[i].anEq[iCol]; - nSum++; + nSum100 += 100; } } - if( nDLt>nSum ){ - avgEq = (pFinal->anLt[iCol] - sumEq)/(nDLt - nSum); + + if( nDist100>nSum100 ){ + avgEq = ((i64)100 * (nRow - sumEq))/(nDist100 - nSum100); } if( avgEq==0 ) avgEq = 1; pIdx->aAvgEq[iCol] = avgEq; - if( pIdx->nSampleCol==1 ) break; } } } @@ -84269,7 +92670,6 @@ static int loadStatTbl( while( sqlite3_step(pStmt)==SQLITE_ROW ){ int nIdxCol = 1; /* Number of columns in stat4 records */ - int nAvgCol = 1; /* Number of entries in Index.aAvgEq */ char *zIndex; /* Index name */ Index *pIdx; /* Pointer to the index object */ @@ -84287,13 +92687,17 @@ static int loadStatTbl( ** loaded from the stat4 table. In this case ignore stat3 data. */ if( pIdx==0 || pIdx->nSample ) continue; if( bStat3==0 ){ - nIdxCol = pIdx->nKeyCol+1; - nAvgCol = pIdx->nKeyCol; + assert( !HasRowid(pIdx->pTable) || pIdx->nColumn==pIdx->nKeyCol+1 ); + if( !HasRowid(pIdx->pTable) && IsPrimaryKeyIndex(pIdx) ){ + nIdxCol = pIdx->nKeyCol; + }else{ + nIdxCol = pIdx->nColumn; + } } pIdx->nSampleCol = nIdxCol; nByte = sizeof(IndexSample) * nSample; nByte += sizeof(tRowcnt) * nIdxCol * 3 * nSample; - nByte += nAvgCol * sizeof(tRowcnt); /* Space for Index.aAvgEq[] */ + nByte += nIdxCol * sizeof(tRowcnt); /* Space for Index.aAvgEq[] */ pIdx->aSample = sqlite3DbMallocZero(db, nByte); if( pIdx->aSample==0 ){ @@ -84301,7 +92705,7 @@ static int loadStatTbl( return SQLITE_NOMEM; } pSpace = (tRowcnt*)&pIdx->aSample[nSample]; - pIdx->aAvgEq = pSpace; pSpace += nAvgCol; + pIdx->aAvgEq = pSpace; pSpace += nIdxCol; for(i=0; iaSample[i].anEq = pSpace; pSpace += nIdxCol; pIdx->aSample[i].anLt = pSpace; pSpace += nIdxCol; @@ -84450,12 +92854,17 @@ SQLITE_PRIVATE int sqlite3AnalysisLoad(sqlite3 *db, int iDb){ /* Load the statistics from the sqlite_stat4 table. */ #ifdef SQLITE_ENABLE_STAT3_OR_STAT4 - if( rc==SQLITE_OK ){ + if( rc==SQLITE_OK && OptimizationEnabled(db, SQLITE_Stat34) ){ int lookasideEnabled = db->lookaside.bEnabled; db->lookaside.bEnabled = 0; rc = loadStat4(db, sInfo.zDatabase); db->lookaside.bEnabled = lookasideEnabled; } + for(i=sqliteHashFirst(&db->aDb[iDb].pSchema->idxHash);i;i=sqliteHashNext(i)){ + Index *pIdx = sqliteHashData(i); + sqlite3_free(pIdx->aiRowEst); + pIdx->aiRowEst = 0; + } #endif if( rc==SQLITE_NOMEM ){ @@ -84482,6 +92891,7 @@ SQLITE_PRIVATE int sqlite3AnalysisLoad(sqlite3 *db, int iDb){ ************************************************************************* ** This file contains code used to implement the ATTACH and DETACH commands. */ +/* #include "sqliteInt.h" */ #ifndef SQLITE_OMIT_ATTACH /* @@ -84620,6 +93030,7 @@ static void attachFunc( "attached databases must use the same text encoding as main database"); rc = SQLITE_ERROR; } + sqlite3BtreeEnter(aNew->pBt); pPager = sqlite3BtreePager(aNew->pBt); sqlite3PagerLockingMode(pPager, db->dfltLockMode); sqlite3BtreeSecureDelete(aNew->pBt, @@ -84627,6 +93038,7 @@ static void attachFunc( #ifndef SQLITE_OMIT_PAGER_PRAGMAS sqlite3BtreeSetPagerFlags(aNew->pBt, 3 | (db->flags & PAGER_FLAGS_MASK)); #endif + sqlite3BtreeLeave(aNew->pBt); } aNew->safety_level = 3; aNew->zName = sqlite3DbStrDup(db, zName); @@ -84659,7 +93071,7 @@ static void attachFunc( case SQLITE_NULL: /* No key specified. Use the key from the main database */ sqlite3CodecGetKey(db, 0, (void**)&zKey, &nKey); - if( nKey>0 || sqlite3BtreeGetReserve(db->aDb[0].pBt)>0 ){ + if( nKey>0 || sqlite3BtreeGetOptimalReserve(db->aDb[0].pBt)>0 ){ rc = sqlite3CodecAttach(db, db->nDb-1, zKey, nKey); } break; @@ -84677,6 +93089,15 @@ static void attachFunc( rc = sqlite3Init(db, &zErrDyn); sqlite3BtreeLeaveAll(db); } +#ifdef SQLITE_USER_AUTHENTICATION + if( rc==SQLITE_OK ){ + u8 newAuth = 0; + rc = sqlite3UserAuthCheckLogin(db, zName, &newAuth); + if( newAuthauth.authLevel ){ + rc = SQLITE_AUTH_USER; + } + } +#endif if( rc ){ int iDb = db->nDb - 1; assert( iDb>=2 ); @@ -84757,7 +93178,7 @@ static void detachFunc( sqlite3BtreeClose(pDb->pBt); pDb->pBt = 0; pDb->pSchema = 0; - sqlite3ResetAllSchemasOfConnection(db); + sqlite3CollapseDatabaseArray(db); return; detach_error: @@ -84791,7 +93212,6 @@ static void codeAttach( SQLITE_OK!=(rc = resolveAttachExpr(&sName, pDbname)) || SQLITE_OK!=(rc = resolveAttachExpr(&sName, pKey)) ){ - pParse->nErr++; goto attach_end; } @@ -84819,7 +93239,7 @@ static void codeAttach( assert( v || db->mallocFailed ); if( v ){ - sqlite3VdbeAddOp3(v, OP_Function, 0, regArgs+3-pFunc->nArg, regArgs+3); + sqlite3VdbeAddOp3(v, OP_Function0, 0, regArgs+3-pFunc->nArg, regArgs+3); assert( pFunc->nArg==-1 || (pFunc->nArg&0xff)==pFunc->nArg ); sqlite3VdbeChangeP5(v, (u8)(pFunc->nArg)); sqlite3VdbeChangeP4(v, -1, (char *)pFunc, P4_FUNCDEF); @@ -85061,6 +93481,7 @@ SQLITE_PRIVATE int sqlite3FixTriggerStep( ** systems that do not need this facility may omit it by recompiling ** the library with -DSQLITE_OMIT_AUTHORIZATION=1 */ +/* #include "sqliteInt.h" */ /* ** All of the code in this file may be omitted by defining a single @@ -85113,13 +93534,16 @@ SQLITE_PRIVATE int sqlite3FixTriggerStep( ** Setting the auth function to NULL disables this hook. The default ** setting of the auth function is NULL. */ -SQLITE_API int sqlite3_set_authorizer( +SQLITE_API int SQLITE_STDCALL sqlite3_set_authorizer( sqlite3 *db, int (*xAuth)(void*,int,const char*,const char*,const char*,const char*), void *pArg ){ +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ) return SQLITE_MISUSE_BKPT; +#endif sqlite3_mutex_enter(db->mutex); - db->xAuth = xAuth; + db->xAuth = (sqlite3_xauth)xAuth; db->pAuthArg = pArg; sqlite3ExpirePreparedStatements(db); sqlite3_mutex_leave(db->mutex); @@ -85154,7 +93578,11 @@ SQLITE_PRIVATE int sqlite3AuthReadCol( char *zDb = db->aDb[iDb].zName; /* Name of attached database */ int rc; /* Auth callback return code */ - rc = db->xAuth(db->pAuthArg, SQLITE_READ, zTab,zCol,zDb,pParse->zAuthContext); + rc = db->xAuth(db->pAuthArg, SQLITE_READ, zTab,zCol,zDb,pParse->zAuthContext +#ifdef SQLITE_USER_AUTHENTICATION + ,db->auth.zAuthUser +#endif + ); if( rc==SQLITE_DENY ){ if( db->nDb>2 || iDb!=0 ){ sqlite3ErrorMsg(pParse, "access to %s.%s.%s is prohibited",zDb,zTab,zCol); @@ -85254,7 +93682,11 @@ SQLITE_PRIVATE int sqlite3AuthCheck( if( db->xAuth==0 ){ return SQLITE_OK; } - rc = db->xAuth(db->pAuthArg, code, zArg1, zArg2, zArg3, pParse->zAuthContext); + rc = db->xAuth(db->pAuthArg, code, zArg1, zArg2, zArg3, pParse->zAuthContext +#ifdef SQLITE_USER_AUTHENTICATION + ,db->auth.zAuthUser +#endif + ); if( rc==SQLITE_DENY ){ sqlite3ErrorMsg(pParse, "not authorized"); pParse->rc = SQLITE_AUTH; @@ -85320,6 +93752,7 @@ SQLITE_PRIVATE void sqlite3AuthContextPop(AuthContext *pContext){ ** COMMIT ** ROLLBACK */ +/* #include "sqliteInt.h" */ /* ** This routine is called when a new SQL statement is beginning to @@ -85410,6 +93843,19 @@ static void codeTableLocks(Parse *pParse){ #define codeTableLocks(x) #endif +/* +** Return TRUE if the given yDbMask object is empty - if it contains no +** 1 bits. This routine is used by the DbMaskAllZero() and DbMaskNotZero() +** macros when SQLITE_MAX_ATTACHED is greater than 30. +*/ +#if SQLITE_MAX_ATTACHED>30 +SQLITE_PRIVATE int sqlite3DbMaskAllZero(yDbMask m){ + int i; + for(i=0; ipToplevel==0 ); db = pParse->db; - if( db->mallocFailed ) return; if( pParse->nested ) return; - if( pParse->nErr ) return; + if( db->mallocFailed || pParse->nErr ){ + if( pParse->rc==SQLITE_OK ) pParse->rc = SQLITE_ERROR; + return; + } /* Begin by generating some termination code at the end of the ** vdbe program @@ -85440,28 +93888,42 @@ SQLITE_PRIVATE void sqlite3FinishCoding(Parse *pParse){ while( sqlite3VdbeDeletePriorOpcode(v, OP_Close) ){} sqlite3VdbeAddOp0(v, OP_Halt); +#if SQLITE_USER_AUTHENTICATION + if( pParse->nTableLock>0 && db->init.busy==0 ){ + sqlite3UserAuthInit(db); + if( db->auth.authLevelrc = SQLITE_AUTH_USER; + sqlite3ErrorMsg(pParse, "user not authenticated"); + return; + } + } +#endif + /* The cookie mask contains one bit for each database file open. ** (Bit 0 is for main, bit 1 is for temp, and so forth.) Bits are ** set for each database that is used. Generate code to start a ** transaction on each used database and to verify the schema cookie ** on each used database. */ - if( db->mallocFailed==0 && (pParse->cookieMask || pParse->pConstExpr) ){ - yDbMask mask; + if( db->mallocFailed==0 + && (DbMaskNonZero(pParse->cookieMask) || pParse->pConstExpr) + ){ int iDb, i; assert( sqlite3VdbeGetOp(v, 0)->opcode==OP_Init ); sqlite3VdbeJumpHere(v, 0); - for(iDb=0, mask=1; iDbnDb; mask<<=1, iDb++){ - if( (mask & pParse->cookieMask)==0 ) continue; + for(iDb=0; iDbnDb; iDb++){ + if( DbMaskTest(pParse->cookieMask, iDb)==0 ) continue; sqlite3VdbeUsesBtree(v, iDb); sqlite3VdbeAddOp4Int(v, OP_Transaction, /* Opcode */ iDb, /* P1 */ - (mask & pParse->writeMask)!=0, /* P2 */ + DbMaskTest(pParse->writeMask,iDb), /* P2 */ pParse->cookieValue[iDb], /* P3 */ db->aDb[iDb].pSchema->iGeneration /* P4 */ ); if( db->init.busy==0 ) sqlite3VdbeChangeP5(v, 1); + VdbeComment((v, + "usesStmtJournal=%d", pParse->mayAbort && pParse->isMultiWrite)); } #ifndef SQLITE_OMIT_VIRTUALTABLE for(i=0; inVtabLock; i++){ @@ -85491,14 +93953,14 @@ SQLITE_PRIVATE void sqlite3FinishCoding(Parse *pParse){ } /* Finally, jump back to the beginning of the executable code. */ - sqlite3VdbeAddOp2(v, OP_Goto, 0, 1); + sqlite3VdbeGoto(v, 1); } } /* Get the VDBE program ready for execution */ - if( v && ALWAYS(pParse->nErr==0) && !db->mallocFailed ){ + if( v && pParse->nErr==0 && !db->mallocFailed ){ assert( pParse->iCacheLevel==0 ); /* Disables and re-enables match */ /* A minimum of one cursor is required if autoincrement is used * See ticket [a696379c1f08866] */ @@ -85513,7 +93975,7 @@ SQLITE_PRIVATE void sqlite3FinishCoding(Parse *pParse){ pParse->nMem = 0; pParse->nSet = 0; pParse->nVar = 0; - pParse->cookieMask = 0; + DbMaskZero(pParse->cookieMask); } /* @@ -85554,6 +94016,16 @@ SQLITE_PRIVATE void sqlite3NestedParse(Parse *pParse, const char *zFormat, ...){ pParse->nested--; } +#if SQLITE_USER_AUTHENTICATION +/* +** Return TRUE if zTable is the name of the system table that stores the +** list of users and their access credentials. +*/ +SQLITE_PRIVATE int sqlite3UserAuthTable(const char *zTable){ + return sqlite3_stricmp(zTable, "sqlite_user")==0; +} +#endif + /* ** Locate the in-memory structure that describes a particular database ** table given the name of that table and (optionally) the name of the @@ -85569,16 +94041,21 @@ SQLITE_PRIVATE void sqlite3NestedParse(Parse *pParse, const char *zFormat, ...){ SQLITE_PRIVATE Table *sqlite3FindTable(sqlite3 *db, const char *zName, const char *zDatabase){ Table *p = 0; int i; - int nName; - assert( zName!=0 ); - nName = sqlite3Strlen30(zName); + /* All mutexes are required for schema access. Make sure we hold them. */ assert( zDatabase!=0 || sqlite3BtreeHoldsAllMutexes(db) ); +#if SQLITE_USER_AUTHENTICATION + /* Only the admin user is allowed to know that the sqlite_user table + ** exists */ + if( db->auth.authLevelnDb; i++){ int j = (i<2) ? i^1 : i; /* Search TEMP before MAIN */ if( zDatabase!=0 && sqlite3StrICmp(zDatabase, db->aDb[j].zName) ) continue; assert( sqlite3SchemaMutexHeld(db, j, 0) ); - p = sqlite3HashFind(&db->aDb[j].pSchema->tblHash, zName, nName); + p = sqlite3HashFind(&db->aDb[j].pSchema->tblHash, zName); if( p ) break; } return p; @@ -85611,6 +94088,17 @@ SQLITE_PRIVATE Table *sqlite3LocateTable( p = sqlite3FindTable(pParse->db, zName, zDbase); if( p==0 ){ const char *zMsg = isView ? "no such view" : "no such table"; +#ifndef SQLITE_OMIT_VIRTUALTABLE + if( sqlite3FindDbName(pParse->db, zDbase)<1 ){ + /* If zName is the not the name of a table in the schema created using + ** CREATE, then check to see if it is the name of an virtual table that + ** can be an eponymous virtual table. */ + Module *pMod = (Module*)sqlite3HashFind(&pParse->db->aModule, zName); + if( pMod && sqlite3VtabEponymousTableInit(pParse, pMod) ){ + return pMod->pEpoTab; + } + } +#endif if( zDbase ){ sqlite3ErrorMsg(pParse, "%s: %s.%s", zMsg, zDbase, zName); }else{ @@ -85618,6 +94106,7 @@ SQLITE_PRIVATE Table *sqlite3LocateTable( } pParse->checkSchema = 1; } + return p; } @@ -85661,7 +94150,6 @@ SQLITE_PRIVATE Table *sqlite3LocateTableItem( SQLITE_PRIVATE Index *sqlite3FindIndex(sqlite3 *db, const char *zName, const char *zDb){ Index *p = 0; int i; - int nName = sqlite3Strlen30(zName); /* All mutexes are required for schema access. Make sure we hold them. */ assert( zDb!=0 || sqlite3BtreeHoldsAllMutexes(db) ); for(i=OMIT_TEMPDB; inDb; i++){ @@ -85670,7 +94158,7 @@ SQLITE_PRIVATE Index *sqlite3FindIndex(sqlite3 *db, const char *zName, const cha assert( pSchema ); if( zDb && sqlite3StrICmp(zDb, db->aDb[j].zName) ) continue; assert( sqlite3SchemaMutexHeld(db, j, 0) ); - p = sqlite3HashFind(&pSchema->idxHash, zName, nName); + p = sqlite3HashFind(&pSchema->idxHash, zName); if( p ) break; } return p; @@ -85683,10 +94171,13 @@ static void freeIndex(sqlite3 *db, Index *p){ #ifndef SQLITE_OMIT_ANALYZE sqlite3DeleteIndexSamples(db, p); #endif - if( db==0 || db->pnBytesFreed==0 ) sqlite3KeyInfoUnref(p->pKeyInfo); sqlite3ExprDelete(db, p->pPartIdxWhere); + sqlite3ExprListDelete(db, p->aColExpr); sqlite3DbFree(db, p->zColAff); - if( p->isResized ) sqlite3DbFree(db, p->azColl); + if( p->isResized ) sqlite3DbFree(db, (void *)p->azColl); +#ifdef SQLITE_ENABLE_STAT3_OR_STAT4 + sqlite3_free(p->aiRowEst); +#endif sqlite3DbFree(db, p); } @@ -85698,13 +94189,11 @@ static void freeIndex(sqlite3 *db, Index *p){ */ SQLITE_PRIVATE void sqlite3UnlinkAndDeleteIndex(sqlite3 *db, int iDb, const char *zIdxName){ Index *pIndex; - int len; Hash *pHash; assert( sqlite3SchemaMutexHeld(db, iDb, 0) ); pHash = &db->aDb[iDb].pSchema->idxHash; - len = sqlite3Strlen30(zIdxName); - pIndex = sqlite3HashInsert(pHash, zIdxName, len, 0); + pIndex = sqlite3HashInsert(pHash, zIdxName, 0); if( ALWAYS(pIndex) ){ if( pIndex->pTable->pIndex==pIndex ){ pIndex->pTable->pIndex = pIndex->pNext; @@ -85810,7 +94299,7 @@ SQLITE_PRIVATE void sqlite3CommitInternalChanges(sqlite3 *db){ ** Delete memory allocated for the column names of a table or view (the ** Table.aCol[] array). */ -static void sqliteDeleteColumnNames(sqlite3 *db, Table *pTable){ +SQLITE_PRIVATE void sqlite3DeleteColumnNames(sqlite3 *db, Table *pTable){ int i; Column *pCol; assert( pTable!=0 ); @@ -85864,7 +94353,7 @@ SQLITE_PRIVATE void sqlite3DeleteTable(sqlite3 *db, Table *pTable){ if( !db || db->pnBytesFreed==0 ){ char *zName = pIndex->zName; TESTONLY ( Index *pOld = ) sqlite3HashInsert( - &pIndex->pSchema->idxHash, zName, sqlite3Strlen30(zName), 0 + &pIndex->pSchema->idxHash, zName, 0 ); assert( db==0 || sqlite3SchemaMutexHeld(db, 0, pIndex->pSchema) ); assert( pOld==pIndex || pOld==0 ); @@ -85877,13 +94366,11 @@ SQLITE_PRIVATE void sqlite3DeleteTable(sqlite3 *db, Table *pTable){ /* Delete the Table structure itself. */ - sqliteDeleteColumnNames(db, pTable); + sqlite3DeleteColumnNames(db, pTable); sqlite3DbFree(db, pTable->zName); sqlite3DbFree(db, pTable->zColAff); sqlite3SelectDelete(db, pTable->pSelect); -#ifndef SQLITE_OMIT_CHECK sqlite3ExprListDelete(db, pTable->pCheck); -#endif #ifndef SQLITE_OMIT_VIRTUALTABLE sqlite3VtabClear(db, pTable); #endif @@ -85907,8 +94394,7 @@ SQLITE_PRIVATE void sqlite3UnlinkAndDeleteTable(sqlite3 *db, int iDb, const char assert( sqlite3SchemaMutexHeld(db, iDb, 0) ); testcase( zTabName[0]==0 ); /* Zero-length table names are allowed */ pDb = &db->aDb[iDb]; - p = sqlite3HashInsert(&pDb->pSchema->tblHash, zTabName, - sqlite3Strlen30(zTabName),0); + p = sqlite3HashInsert(&pDb->pSchema->tblHash, zTabName, 0); sqlite3DeleteTable(db, p); db->flags |= SQLITE_InternChanges; } @@ -86014,14 +94500,12 @@ SQLITE_PRIVATE int sqlite3TwoPartName( if( ALWAYS(pName2!=0) && pName2->n>0 ){ if( db->init.busy ) { sqlite3ErrorMsg(pParse, "corrupt database"); - pParse->nErr++; return -1; } *pUnqual = pName2; iDb = sqlite3FindDb(db, pName1); if( iDb<0 ){ sqlite3ErrorMsg(pParse, "unknown database %T", pName1); - pParse->nErr++; return -1; } }else{ @@ -86180,7 +94664,7 @@ SQLITE_PRIVATE void sqlite3StartTable( if( !noErr ){ sqlite3ErrorMsg(pParse, "table %T already exists", pName); }else{ - assert( !db->init.busy ); + assert( !db->init.busy || CORRUPT_DB ); sqlite3CodeVerifySchema(pParse, iDb); } goto begin_table_error; @@ -86226,10 +94710,12 @@ SQLITE_PRIVATE void sqlite3StartTable( ** now. */ if( !db->init.busy && (v = sqlite3GetVdbe(pParse))!=0 ){ - int j1; + int addr1; int fileFormat; int reg1, reg2, reg3; - sqlite3BeginWriteOperation(pParse, 0, iDb); + /* nullRow[] is an OP_Record encoding of a row containing 5 NULLs */ + static const char nullRow[] = { 6, 0, 0, 0, 0, 0 }; + sqlite3BeginWriteOperation(pParse, 1, iDb); #ifndef SQLITE_OMIT_VIRTUALTABLE if( isVirtual ){ @@ -86245,14 +94731,14 @@ SQLITE_PRIVATE void sqlite3StartTable( reg3 = ++pParse->nMem; sqlite3VdbeAddOp3(v, OP_ReadCookie, iDb, reg3, BTREE_FILE_FORMAT); sqlite3VdbeUsesBtree(v, iDb); - j1 = sqlite3VdbeAddOp1(v, OP_If, reg3); VdbeCoverage(v); + addr1 = sqlite3VdbeAddOp1(v, OP_If, reg3); VdbeCoverage(v); fileFormat = (db->flags & SQLITE_LegacyFileFmt)!=0 ? 1 : SQLITE_MAX_FILE_FORMAT; sqlite3VdbeAddOp2(v, OP_Integer, fileFormat, reg3); sqlite3VdbeAddOp3(v, OP_SetCookie, iDb, BTREE_FILE_FORMAT, reg3); sqlite3VdbeAddOp2(v, OP_Integer, ENC(db), reg3); sqlite3VdbeAddOp3(v, OP_SetCookie, iDb, BTREE_TEXT_ENCODING, reg3); - sqlite3VdbeJumpHere(v, j1); + sqlite3VdbeJumpHere(v, addr1); /* This just creates a place-holder record in the sqlite_master table. ** The record created does not contain anything yet. It will be replaced @@ -86273,7 +94759,7 @@ SQLITE_PRIVATE void sqlite3StartTable( } sqlite3OpenMasterTable(pParse, iDb); sqlite3VdbeAddOp2(v, OP_NewRowid, 0, reg1); - sqlite3VdbeAddOp2(v, OP_Null, 0, reg3); + sqlite3VdbeAddOp4(v, OP_Blob, 6, reg3, 0, nullRow, P4_STATIC); sqlite3VdbeAddOp3(v, OP_Insert, 0, reg3, reg1); sqlite3VdbeChangeP5(v, OPFLAG_APPEND); sqlite3VdbeAddOp0(v, OP_Close); @@ -86288,18 +94774,19 @@ begin_table_error: return; } -/* -** This macro is used to compare two strings in a case-insensitive manner. -** It is slightly faster than calling sqlite3StrICmp() directly, but -** produces larger code. -** -** WARNING: This macro is not compatible with the strcmp() family. It -** returns true if the two strings are equal, otherwise false. +/* Set properties of a table column based on the (magical) +** name of the column. */ -#define STRICMP(x, y) (\ -sqlite3UpperToLower[*(unsigned char *)(x)]== \ -sqlite3UpperToLower[*(unsigned char *)(y)] \ -&& sqlite3StrICmp((x)+1,(y)+1)==0 ) +#if SQLITE_ENABLE_HIDDEN_COLUMNS +SQLITE_PRIVATE void sqlite3ColumnPropertiesFromName(Table *pTab, Column *pCol){ + if( sqlite3_strnicmp(pCol->zName, "__hidden__", 10)==0 ){ + pCol->colFlags |= COLFLAG_HIDDEN; + }else if( pTab && pCol!=pTab->aCol && (pCol[-1].colFlags & COLFLAG_HIDDEN) ){ + pTab->tabFlags |= TF_OOOHidden; + } +} +#endif + /* ** Add a new column to the table currently being constructed. @@ -86325,7 +94812,7 @@ SQLITE_PRIVATE void sqlite3AddColumn(Parse *pParse, Token *pName){ z = sqlite3NameFromToken(db, pName); if( z==0 ) return; for(i=0; inCol; i++){ - if( STRICMP(z, p->aCol[i].zName) ){ + if( sqlite3_stricmp(z, p->aCol[i].zName)==0 ){ sqlite3ErrorMsg(pParse, "duplicate column name: %s", z); sqlite3DbFree(db, z); return; @@ -86343,12 +94830,13 @@ SQLITE_PRIVATE void sqlite3AddColumn(Parse *pParse, Token *pName){ pCol = &p->aCol[p->nCol]; memset(pCol, 0, sizeof(p->aCol[0])); pCol->zName = z; + sqlite3ColumnPropertiesFromName(p, pCol); /* If there is no type specified, columns have the default affinity - ** 'NONE'. If there is a type specified, then sqlite3AddColumnType() will + ** 'BLOB'. If there is a type specified, then sqlite3AddColumnType() will ** be called next to set pCol->affinity correctly. */ - pCol->affinity = SQLITE_AFF_NONE; + pCol->affinity = SQLITE_AFF_BLOB; pCol->szEst = 1; p->nCol++; } @@ -86383,7 +94871,7 @@ SQLITE_PRIVATE void sqlite3AddNotNull(Parse *pParse, int onError){ ** 'CHAR' | SQLITE_AFF_TEXT ** 'CLOB' | SQLITE_AFF_TEXT ** 'TEXT' | SQLITE_AFF_TEXT -** 'BLOB' | SQLITE_AFF_NONE +** 'BLOB' | SQLITE_AFF_BLOB ** 'REAL' | SQLITE_AFF_REAL ** 'FLOA' | SQLITE_AFF_REAL ** 'DOUB' | SQLITE_AFF_REAL @@ -86409,7 +94897,7 @@ SQLITE_PRIVATE char sqlite3AffinityType(const char *zIn, u8 *pszEst){ aff = SQLITE_AFF_TEXT; }else if( h==(('b'<<24)+('l'<<16)+('o'<<8)+'b') /* BLOB */ && (aff==SQLITE_AFF_NUMERIC || aff==SQLITE_AFF_REAL) ){ - aff = SQLITE_AFF_NONE; + aff = SQLITE_AFF_BLOB; if( zIn[0]=='(' ) zChar = zIn; #ifndef SQLITE_OMIT_FLOATING_POINT }else if( h==(('r'<<24)+('e'<<16)+('a'<<8)+'l') /* REAL */ @@ -86432,7 +94920,7 @@ SQLITE_PRIVATE char sqlite3AffinityType(const char *zIn, u8 *pszEst){ ** estimate is scaled so that the size of an integer is 1. */ if( pszEst ){ *pszEst = 1; /* default size is approx 4 bytes */ - if( aff<=SQLITE_AFF_NONE ){ + if( affpNewTable; if( p==0 || NEVER(p->nCol<1) ) return; pCol = &p->aCol[p->nCol-1]; - assert( pCol->zType==0 ); + assert( pCol->zType==0 || CORRUPT_DB ); + sqlite3DbFree(pParse->db, pCol->zType); pCol->zType = sqlite3NameFromToken(pParse->db, pType); pCol->affinity = sqlite3AffinityType(pCol->zType, &pCol->szEst); } @@ -86491,7 +94980,7 @@ SQLITE_PRIVATE void sqlite3AddDefaultValue(Parse *pParse, ExprSpan *pSpan){ p = pParse->pNewTable; if( p!=0 ){ pCol = &(p->aCol[p->nCol-1]); - if( !sqlite3ExprIsConstantOrFunction(pSpan->pExpr) ){ + if( !sqlite3ExprIsConstantOrFunction(pSpan->pExpr, db->init.busy) ){ sqlite3ErrorMsg(pParse, "default value of column [%s] is not constant", pCol->zName); }else{ @@ -86509,6 +94998,30 @@ SQLITE_PRIVATE void sqlite3AddDefaultValue(Parse *pParse, ExprSpan *pSpan){ sqlite3ExprDelete(db, pSpan->pExpr); } +/* +** Backwards Compatibility Hack: +** +** Historical versions of SQLite accepted strings as column names in +** indexes and PRIMARY KEY constraints and in UNIQUE constraints. Example: +** +** CREATE TABLE xyz(a,b,c,d,e,PRIMARY KEY('a'),UNIQUE('b','c' COLLATE trim) +** CREATE INDEX abc ON xyz('c','d' DESC,'e' COLLATE nocase DESC); +** +** This is goofy. But to preserve backwards compatibility we continue to +** accept it. This routine does the necessary conversion. It converts +** the expression given in its argument from a TK_STRING into a TK_ID +** if the expression is just a TK_STRING with an optional COLLATE clause. +** If the epxression is anything other than TK_STRING, the expression is +** unchanged. +*/ +static void sqlite3StringToId(Expr *p){ + if( p->op==TK_STRING ){ + p->op = TK_ID; + }else if( p->op==TK_COLLATE && p->pLeft->op==TK_STRING ){ + p->pLeft->op = TK_ID; + } +} + /* ** Designate the PRIMARY KEY for the table. pList is a list of names ** of columns that form the primary key. If pList is NULL, then the @@ -86553,18 +95066,24 @@ SQLITE_PRIVATE void sqlite3AddPrimaryKey( }else{ nTerm = pList->nExpr; for(i=0; inCol; iCol++){ - if( sqlite3StrICmp(pList->a[i].zName, pTab->aCol[iCol].zName)==0 ){ - pTab->aCol[iCol].colFlags |= COLFLAG_PRIMKEY; - zType = pTab->aCol[iCol].zType; - break; + Expr *pCExpr = sqlite3ExprSkipCollate(pList->a[i].pExpr); + assert( pCExpr!=0 ); + sqlite3StringToId(pCExpr); + if( pCExpr->op==TK_ID ){ + const char *zCName = pCExpr->u.zToken; + for(iCol=0; iColnCol; iCol++){ + if( sqlite3StrICmp(zCName, pTab->aCol[iCol].zName)==0 ){ + pTab->aCol[iCol].colFlags |= COLFLAG_PRIMKEY; + zType = pTab->aCol[iCol].zType; + break; + } } } } } if( nTerm==1 && zType && sqlite3StrICmp(zType, "INTEGER")==0 - && sortOrder==SQLITE_SO_ASC + && sortOrder!=SQLITE_SO_DESC ){ pTab->iPKey = iCol; pTab->keyConf = (u8)onError; @@ -86577,14 +95096,11 @@ SQLITE_PRIVATE void sqlite3AddPrimaryKey( "INTEGER PRIMARY KEY"); #endif }else{ - Vdbe *v = pParse->pVdbe; Index *p; - if( v ) pParse->addrSkipPK = sqlite3VdbeAddOp0(v, OP_Noop); p = sqlite3CreateIndex(pParse, 0, 0, 0, pList, onError, 0, 0, sortOrder, 0); if( p ){ p->idxType = SQLITE_IDXTYPE_PRIMARYKEY; - if( v ) sqlite3VdbeJumpHere(v, pParse->addrSkipPK); } pList = 0; } @@ -86803,8 +95319,8 @@ static char *createTableStmt(sqlite3 *db, Table *p){ zStmt[k++] = '('; for(pCol=p->aCol, i=0; inCol; i++, pCol++){ static const char * const azType[] = { + /* SQLITE_AFF_BLOB */ "", /* SQLITE_AFF_TEXT */ " TEXT", - /* SQLITE_AFF_NONE */ "", /* SQLITE_AFF_NUMERIC */ " NUM", /* SQLITE_AFF_INTEGER */ " INT", /* SQLITE_AFF_REAL */ " REAL" @@ -86816,17 +95332,17 @@ static char *createTableStmt(sqlite3 *db, Table *p){ k += sqlite3Strlen30(&zStmt[k]); zSep = zSep2; identPut(zStmt, &k, pCol->zName); - assert( pCol->affinity-SQLITE_AFF_TEXT >= 0 ); - assert( pCol->affinity-SQLITE_AFF_TEXT < ArraySize(azType) ); + assert( pCol->affinity-SQLITE_AFF_BLOB >= 0 ); + assert( pCol->affinity-SQLITE_AFF_BLOB < ArraySize(azType) ); + testcase( pCol->affinity==SQLITE_AFF_BLOB ); testcase( pCol->affinity==SQLITE_AFF_TEXT ); - testcase( pCol->affinity==SQLITE_AFF_NONE ); testcase( pCol->affinity==SQLITE_AFF_NUMERIC ); testcase( pCol->affinity==SQLITE_AFF_INTEGER ); testcase( pCol->affinity==SQLITE_AFF_REAL ); - zType = azType[pCol->affinity - SQLITE_AFF_TEXT]; + zType = azType[pCol->affinity - SQLITE_AFF_BLOB]; len = sqlite3Strlen30(zType); - assert( pCol->affinity==SQLITE_AFF_NONE + assert( pCol->affinity==SQLITE_AFF_BLOB || pCol->affinity==sqlite3AffinityType(zType, 0) ); memcpy(&zStmt[k], zType, len); k += len; @@ -86849,7 +95365,7 @@ static int resizeIndexObject(sqlite3 *db, Index *pIdx, int N){ zExtra = sqlite3DbMallocZero(db, nByte); if( zExtra==0 ) return SQLITE_NOMEM; memcpy(zExtra, pIdx->azColl, sizeof(char*)*pIdx->nColumn); - pIdx->azColl = (char**)zExtra; + pIdx->azColl = (const char**)zExtra; zExtra += sizeof(char*)*N; memcpy(zExtra, pIdx->aiColumn, sizeof(i16)*pIdx->nColumn); pIdx->aiColumn = (i16*)zExtra; @@ -86908,7 +95424,7 @@ static int hasColumn(const i16 *aiCol, int nCol, int x){ ** no rowid btree for a WITHOUT ROWID. Instead, the canonical ** data storage is a covering index btree. ** (2) Bypass the creation of the sqlite_master table entry -** for the PRIMARY KEY as the the primary key index is now +** for the PRIMARY KEY as the primary key index is now ** identified by the sqlite_master table entry of the table itself. ** (3) Set the Index.tnum of the PRIMARY KEY Index object in the ** schema to the rootpage from the main table. @@ -86929,20 +95445,12 @@ static void convertToWithoutRowidTable(Parse *pParse, Table *pTab){ Vdbe *v = pParse->pVdbe; /* Convert the OP_CreateTable opcode that would normally create the - ** root-page for the table into a OP_CreateIndex opcode. The index + ** root-page for the table into an OP_CreateIndex opcode. The index ** created will become the PRIMARY KEY index. */ if( pParse->addrCrTab ){ assert( v ); - sqlite3VdbeGetOp(v, pParse->addrCrTab)->opcode = OP_CreateIndex; - } - - /* Bypass the creation of the PRIMARY KEY btree and the sqlite_master - ** table entry. - */ - if( pParse->addrSkipPK ){ - assert( v ); - sqlite3VdbeGetOp(v, pParse->addrSkipPK)->opcode = OP_Goto; + sqlite3VdbeChangeOpcode(v, pParse->addrCrTab, OP_CreateIndex); } /* Locate the PRIMARY KEY index. Or, if this table was originally @@ -86950,10 +95458,12 @@ static void convertToWithoutRowidTable(Parse *pParse, Table *pTab){ */ if( pTab->iPKey>=0 ){ ExprList *pList; - pList = sqlite3ExprListAppend(pParse, 0, 0); + Token ipkToken; + ipkToken.z = pTab->aCol[pTab->iPKey].zName; + ipkToken.n = sqlite3Strlen30(ipkToken.z); + pList = sqlite3ExprListAppend(pParse, 0, + sqlite3ExprAlloc(db, TK_ID, &ipkToken, 0)); if( pList==0 ) return; - pList->a[0].zName = sqlite3DbStrDup(pParse->db, - pTab->aCol[pTab->iPKey].zName); pList->a[0].sortOrder = pParse->iPkSortOrder; assert( pParse->pNewTable==pTab ); pPk = sqlite3CreateIndex(pParse, 0, 0, 0, pList, pTab->keyConf, 0, 0, 0, 0); @@ -86962,16 +95472,42 @@ static void convertToWithoutRowidTable(Parse *pParse, Table *pTab){ pTab->iPKey = -1; }else{ pPk = sqlite3PrimaryKeyIndex(pTab); + + /* Bypass the creation of the PRIMARY KEY btree and the sqlite_master + ** table entry. This is only required if currently generating VDBE + ** code for a CREATE TABLE (not when parsing one as part of reading + ** a database schema). */ + if( v ){ + assert( db->init.busy==0 ); + sqlite3VdbeChangeOpcode(v, pPk->tnum, OP_Goto); + } + + /* + ** Remove all redundant columns from the PRIMARY KEY. For example, change + ** "PRIMARY KEY(a,b,a,b,c,b,c,d)" into just "PRIMARY KEY(a,b,c,d)". Later + ** code assumes the PRIMARY KEY contains no repeated columns. + */ + for(i=j=1; inKeyCol; i++){ + if( hasColumn(pPk->aiColumn, j, pPk->aiColumn[i]) ){ + pPk->nColumn--; + }else{ + pPk->aiColumn[j++] = pPk->aiColumn[i]; + } + } + pPk->nKeyCol = j; } pPk->isCovering = 1; assert( pPk!=0 ); nPk = pPk->nKeyCol; - /* Make sure every column of the PRIMARY KEY is NOT NULL */ - for(i=0; iaCol[pPk->aiColumn[i]].notNull = 1; + /* Make sure every column of the PRIMARY KEY is NOT NULL. (Except, + ** do not enforce this for imposter tables.) */ + if( !db->init.imposterTable ){ + for(i=0; iaCol[pPk->aiColumn[i]].notNull = OE_Abort; + } + pPk->uniqNotNull = 1; } - pPk->uniqNotNull = 1; /* The root page of the PRIMARY KEY is the table root page */ pPk->tnum = pTab->tnum; @@ -87010,7 +95546,7 @@ static void convertToWithoutRowidTable(Parse *pParse, Table *pTab){ if( !hasColumn(pPk->aiColumn, j, i) ){ assert( jnColumn ); pPk->aiColumn[j] = i; - pPk->azColl[j] = "BINARY"; + pPk->azColl[j] = sqlite3StrBINARY; j++; } } @@ -87053,9 +95589,10 @@ SQLITE_PRIVATE void sqlite3EndTable( int iDb; /* Database in which the table lives */ Index *pIdx; /* An implied index of the table */ - if( (pEnd==0 && pSelect==0) || db->mallocFailed ){ + if( pEnd==0 && pSelect==0 ){ return; } + assert( !db->mallocFailed ); p = pParse->pNewTable; if( p==0 ) return; @@ -87081,7 +95618,7 @@ SQLITE_PRIVATE void sqlite3EndTable( if( (p->tabFlags & TF_HasPrimaryKey)==0 ){ sqlite3ErrorMsg(pParse, "PRIMARY KEY missing on table %s", p->zName); }else{ - p->tabFlags |= TF_WithoutRowid; + p->tabFlags |= TF_WithoutRowid | TF_NoVisibleRowid; convertToWithoutRowidTable(pParse, p); } } @@ -87149,26 +95686,46 @@ SQLITE_PRIVATE void sqlite3EndTable( ** be redundant. */ if( pSelect ){ - SelectDest dest; - Table *pSelTab; + SelectDest dest; /* Where the SELECT should store results */ + int regYield; /* Register holding co-routine entry-point */ + int addrTop; /* Top of the co-routine */ + int regRec; /* A record to be insert into the new table */ + int regRowid; /* Rowid of the next row to insert */ + int addrInsLoop; /* Top of the loop for inserting rows */ + Table *pSelTab; /* A table that describes the SELECT results */ + regYield = ++pParse->nMem; + regRec = ++pParse->nMem; + regRowid = ++pParse->nMem; assert(pParse->nTab==1); + sqlite3MayAbort(pParse); sqlite3VdbeAddOp3(v, OP_OpenWrite, 1, pParse->regRoot, iDb); sqlite3VdbeChangeP5(v, OPFLAG_P2ISREG); pParse->nTab = 2; - sqlite3SelectDestInit(&dest, SRT_Table, 1); + addrTop = sqlite3VdbeCurrentAddr(v) + 1; + sqlite3VdbeAddOp3(v, OP_InitCoroutine, regYield, 0, addrTop); + sqlite3SelectDestInit(&dest, SRT_Coroutine, regYield); sqlite3Select(pParse, pSelect, &dest); + sqlite3VdbeAddOp1(v, OP_EndCoroutine, regYield); + sqlite3VdbeJumpHere(v, addrTop - 1); + if( pParse->nErr ) return; + pSelTab = sqlite3ResultSetOfSelect(pParse, pSelect); + if( pSelTab==0 ) return; + assert( p->aCol==0 ); + p->nCol = pSelTab->nCol; + p->aCol = pSelTab->aCol; + pSelTab->nCol = 0; + pSelTab->aCol = 0; + sqlite3DeleteTable(db, pSelTab); + addrInsLoop = sqlite3VdbeAddOp1(v, OP_Yield, dest.iSDParm); + VdbeCoverage(v); + sqlite3VdbeAddOp3(v, OP_MakeRecord, dest.iSdst, dest.nSdst, regRec); + sqlite3TableAffinity(v, p, 0); + sqlite3VdbeAddOp2(v, OP_NewRowid, 1, regRowid); + sqlite3VdbeAddOp3(v, OP_Insert, 1, regRec, regRowid); + sqlite3VdbeGoto(v, addrInsLoop); + sqlite3VdbeJumpHere(v, addrInsLoop); sqlite3VdbeAddOp1(v, OP_Close, 1); - if( pParse->nErr==0 ){ - pSelTab = sqlite3ResultSetOfSelect(pParse, pSelect); - if( pSelTab==0 ) return; - assert( p->aCol==0 ); - p->nCol = pSelTab->nCol; - p->aCol = pSelTab->aCol; - pSelTab->nCol = 0; - pSelTab->aCol = 0; - sqlite3DeleteTable(db, pSelTab); - } } /* Compute the complete text of the CREATE statement */ @@ -87230,8 +95787,7 @@ SQLITE_PRIVATE void sqlite3EndTable( Table *pOld; Schema *pSchema = p->pSchema; assert( sqlite3SchemaMutexHeld(db, iDb, 0) ); - pOld = sqlite3HashInsert(&pSchema->tblHash, p->zName, - sqlite3Strlen30(p->zName),p); + pOld = sqlite3HashInsert(&pSchema->tblHash, p->zName, p); if( pOld ){ assert( p==pOld ); /* Malloc must have failed inside HashInsert() */ db->mallocFailed = 1; @@ -87264,6 +95820,7 @@ SQLITE_PRIVATE void sqlite3CreateView( Token *pBegin, /* The CREATE token that begins the statement */ Token *pName1, /* The token that holds the name of the view */ Token *pName2, /* The token that holds the name of the view */ + ExprList *pCNames, /* Optional list of view column names */ Select *pSelect, /* A SELECT statement that will become the new view */ int isTemp, /* TRUE for a TEMPORARY view */ int noErr /* Suppress error messages if VIEW already exists */ @@ -87279,22 +95836,15 @@ SQLITE_PRIVATE void sqlite3CreateView( if( pParse->nVar>0 ){ sqlite3ErrorMsg(pParse, "parameters are not allowed in views"); - sqlite3SelectDelete(db, pSelect); - return; + goto create_view_fail; } sqlite3StartTable(pParse, pName1, pName2, isTemp, 1, 0, noErr); p = pParse->pNewTable; - if( p==0 || pParse->nErr ){ - sqlite3SelectDelete(db, pSelect); - return; - } + if( p==0 || pParse->nErr ) goto create_view_fail; sqlite3TwoPartName(pParse, pName1, pName2, &pName); iDb = sqlite3SchemaToIndex(db, p->pSchema); sqlite3FixInit(&sFix, pParse, iDb, "view", pName); - if( sqlite3FixSelect(&sFix, pSelect) ){ - sqlite3SelectDelete(db, pSelect); - return; - } + if( sqlite3FixSelect(&sFix, pSelect) ) goto create_view_fail; /* Make a copy of the entire SELECT statement that defines the view. ** This will force all the Expr.token.z values to be dynamically @@ -87302,30 +95852,31 @@ SQLITE_PRIVATE void sqlite3CreateView( ** they will persist after the current sqlite3_exec() call returns. */ p->pSelect = sqlite3SelectDup(db, pSelect, EXPRDUP_REDUCE); - sqlite3SelectDelete(db, pSelect); - if( db->mallocFailed ){ - return; - } - if( !db->init.busy ){ - sqlite3ViewGetColumnNames(pParse, p); - } + p->pCheck = sqlite3ExprListDup(db, pCNames, EXPRDUP_REDUCE); + if( db->mallocFailed ) goto create_view_fail; /* Locate the end of the CREATE VIEW statement. Make sEnd point to ** the end. */ sEnd = pParse->sLastToken; - if( ALWAYS(sEnd.z[0]!=0) && sEnd.z[0]!=';' ){ + assert( sEnd.z[0]!=0 ); + if( sEnd.z[0]!=';' ){ sEnd.z += sEnd.n; } sEnd.n = 0; n = (int)(sEnd.z - pBegin->z); + assert( n>0 ); z = pBegin->z; - while( ALWAYS(n>0) && sqlite3Isspace(z[n-1]) ){ n--; } + while( sqlite3Isspace(z[n-1]) ){ n--; } sEnd.z = &z[n-1]; sEnd.n = 1; /* Use sqlite3EndTable() to add the view to the SQLITE_MASTER table */ sqlite3EndTable(pParse, 0, &sEnd, 0, 0); + +create_view_fail: + sqlite3SelectDelete(db, pSelect); + sqlite3ExprListDelete(db, pCNames); return; } #endif /* SQLITE_OMIT_VIEW */ @@ -87342,7 +95893,8 @@ SQLITE_PRIVATE int sqlite3ViewGetColumnNames(Parse *pParse, Table *pTable){ int nErr = 0; /* Number of errors encountered */ int n; /* Temporarily holds the number of cursors assigned */ sqlite3 *db = pParse->db; /* Database connection for malloc errors */ - int (*xAuth)(void*,int,const char*,const char*,const char*,const char*); + sqlite3_xauth xAuth; /* Saved xAuth pointer */ + u8 bEnabledLA; /* Saved db->lookaside.bEnabled state */ assert( pTable ); @@ -87388,40 +95940,46 @@ SQLITE_PRIVATE int sqlite3ViewGetColumnNames(Parse *pParse, Table *pTable){ ** statement that defines the view. */ assert( pTable->pSelect ); - pSel = sqlite3SelectDup(db, pTable->pSelect, 0); - if( pSel ){ - u8 enableLookaside = db->lookaside.bEnabled; - n = pParse->nTab; - sqlite3SrcListAssignCursors(pParse, pSel->pSrc); - pTable->nCol = -1; + bEnabledLA = db->lookaside.bEnabled; + if( pTable->pCheck ){ db->lookaside.bEnabled = 0; + sqlite3ColumnsFromExprList(pParse, pTable->pCheck, + &pTable->nCol, &pTable->aCol); + }else{ + pSel = sqlite3SelectDup(db, pTable->pSelect, 0); + if( pSel ){ + n = pParse->nTab; + sqlite3SrcListAssignCursors(pParse, pSel->pSrc); + pTable->nCol = -1; + db->lookaside.bEnabled = 0; #ifndef SQLITE_OMIT_AUTHORIZATION - xAuth = db->xAuth; - db->xAuth = 0; - pSelTab = sqlite3ResultSetOfSelect(pParse, pSel); - db->xAuth = xAuth; + xAuth = db->xAuth; + db->xAuth = 0; + pSelTab = sqlite3ResultSetOfSelect(pParse, pSel); + db->xAuth = xAuth; #else - pSelTab = sqlite3ResultSetOfSelect(pParse, pSel); + pSelTab = sqlite3ResultSetOfSelect(pParse, pSel); #endif - db->lookaside.bEnabled = enableLookaside; - pParse->nTab = n; - if( pSelTab ){ - assert( pTable->aCol==0 ); - pTable->nCol = pSelTab->nCol; - pTable->aCol = pSelTab->aCol; - pSelTab->nCol = 0; - pSelTab->aCol = 0; - sqlite3DeleteTable(db, pSelTab); - assert( sqlite3SchemaMutexHeld(db, 0, pTable->pSchema) ); - pTable->pSchema->flags |= DB_UnresetViews; - }else{ - pTable->nCol = 0; + pParse->nTab = n; + if( pSelTab ){ + assert( pTable->aCol==0 ); + pTable->nCol = pSelTab->nCol; + pTable->aCol = pSelTab->aCol; + pSelTab->nCol = 0; + pSelTab->aCol = 0; + sqlite3DeleteTable(db, pSelTab); + assert( sqlite3SchemaMutexHeld(db, 0, pTable->pSchema) ); + }else{ + pTable->nCol = 0; + nErr++; + } + sqlite3SelectDelete(db, pSel); + } else { nErr++; } - sqlite3SelectDelete(db, pSel); - } else { - nErr++; } + db->lookaside.bEnabled = bEnabledLA; + pTable->pSchema->schemaFlags |= DB_UnresetViews; #endif /* SQLITE_OMIT_VIEW */ return nErr; } @@ -87438,7 +95996,7 @@ static void sqliteViewResetAll(sqlite3 *db, int idx){ for(i=sqliteHashFirst(&db->aDb[idx].pSchema->tblHash); i;i=sqliteHashNext(i)){ Table *pTab = sqliteHashData(i); if( pTab->pSelect ){ - sqliteDeleteColumnNames(db, pTab); + sqlite3DeleteColumnNames(db, pTab); pTab->aCol = 0; pTab->nCol = 0; } @@ -87688,6 +96246,7 @@ SQLITE_PRIVATE void sqlite3DropTable(Parse *pParse, SrcList *pName, int isView, } assert( pParse->nErr==0 ); assert( pName->nSrc==1 ); + if( sqlite3ReadSchema(pParse) ) goto exit_drop_table; if( noErr ) db->suppressErr++; pTab = sqlite3LocateTableItem(pParse, isView, &pName->a[0]); if( noErr ) db->suppressErr--; @@ -87881,7 +96440,7 @@ SQLITE_PRIVATE void sqlite3CreateForeignKey( assert( sqlite3SchemaMutexHeld(db, 0, p->pSchema) ); pNextTo = (FKey *)sqlite3HashInsert(&p->pSchema->fkeyHash, - pFKey->zTo, sqlite3Strlen30(pFKey->zTo), (void *)pFKey + pFKey->zTo, (void *)pFKey ); if( pNextTo==pFKey ){ db->mallocFailed = 1; @@ -87944,7 +96503,7 @@ static void sqlite3RefillIndex(Parse *pParse, Index *pIndex, int memRootPage){ int iPartIdxLabel; /* Jump to this label to skip a row */ Vdbe *v; /* Generate code into this virtual machine */ KeyInfo *pKey; /* KeyInfo for index */ - int regRecord; /* Register holding assemblied index record */ + int regRecord; /* Register holding assembled index record */ sqlite3 *db = pParse->db; /* The database connection */ int iDb = sqlite3SchemaToIndex(db, pIndex->pSchema); @@ -87969,7 +96528,7 @@ static void sqlite3RefillIndex(Parse *pParse, Index *pIndex, int memRootPage){ /* Open the sorter cursor if we are to use one. */ iSorter = pParse->nTab++; - sqlite3VdbeAddOp4(v, OP_SorterOpen, iSorter, 0, 0, (char*) + sqlite3VdbeAddOp4(v, OP_SorterOpen, iSorter, 0, pIndex->nKeyCol, (char*) sqlite3KeyInfoRef(pKey), P4_KEYINFO); /* Open the table. Loop through all rows of the table, inserting index @@ -87990,18 +96549,19 @@ static void sqlite3RefillIndex(Parse *pParse, Index *pIndex, int memRootPage){ addr1 = sqlite3VdbeAddOp2(v, OP_SorterSort, iSorter, 0); VdbeCoverage(v); assert( pKey!=0 || db->mallocFailed || pParse->nErr ); - if( pIndex->onError!=OE_None && pKey!=0 ){ + if( IsUniqueIndex(pIndex) && pKey!=0 ){ int j2 = sqlite3VdbeCurrentAddr(v) + 3; - sqlite3VdbeAddOp2(v, OP_Goto, 0, j2); + sqlite3VdbeGoto(v, j2); addr2 = sqlite3VdbeCurrentAddr(v); sqlite3VdbeAddOp4Int(v, OP_SorterCompare, iSorter, j2, regRecord, - pKey->nField - pIndex->nKeyCol); VdbeCoverage(v); + pIndex->nKeyCol); VdbeCoverage(v); sqlite3UniqueConstraint(pParse, OE_Abort, pIndex); }else{ addr2 = sqlite3VdbeCurrentAddr(v); } - sqlite3VdbeAddOp2(v, OP_SorterData, iSorter, regRecord); - sqlite3VdbeAddOp3(v, OP_IdxInsert, iIdx, regRecord, 1); + sqlite3VdbeAddOp3(v, OP_SorterData, iSorter, regRecord, iIdx); + sqlite3VdbeAddOp3(v, OP_Last, iIdx, 0, -1); + sqlite3VdbeAddOp3(v, OP_IdxInsert, iIdx, regRecord, 0); sqlite3VdbeChangeP5(v, OPFLAG_USESEEKRESULT); sqlite3ReleaseTempReg(pParse, regRecord); sqlite3VdbeAddOp2(v, OP_SorterNext, iSorter, addr2); VdbeCoverage(v); @@ -88036,7 +96596,7 @@ SQLITE_PRIVATE Index *sqlite3AllocateIndexObject( p = sqlite3DbMallocZero(db, nByte + nExtra); if( p ){ char *pExtra = ((char*)p)+ROUND8(sizeof(Index)); - p->azColl = (char**)pExtra; pExtra += ROUND8(sizeof(char*)*nCol); + p->azColl = (const char**)pExtra; pExtra += ROUND8(sizeof(char*)*nCol); p->aiRowLogEst = (LogEst*)pExtra; pExtra += sizeof(LogEst)*(nCol+1); p->aiColumn = (i16*)pExtra; pExtra += sizeof(i16)*nCol; p->aSortOrder = (u8*)pExtra; @@ -88088,14 +96648,12 @@ SQLITE_PRIVATE Index *sqlite3CreateIndex( int iDb; /* Index of the database that is being written */ Token *pName = 0; /* Unqualified name of the index to create */ struct ExprList_item *pListItem; /* For looping over pList */ - const Column *pTabCol; /* A column in the table */ int nExtra = 0; /* Space allocated for zExtra[] */ int nExtraCol; /* Number of extra columns needed */ char *zExtra = 0; /* Extra space after the Index object */ Index *pPk = 0; /* PRIMARY KEY index for WITHOUT ROWID tables */ - assert( pParse->nErr==0 ); /* Never called with prior errors */ - if( db->mallocFailed || IN_DECLARE_VTAB ){ + if( db->mallocFailed || IN_DECLARE_VTAB || pParse->nErr>0 ){ goto exit_create_index; } if( SQLITE_OK!=sqlite3ReadSchema(pParse) ){ @@ -88157,6 +96715,10 @@ SQLITE_PRIVATE Index *sqlite3CreateIndex( assert( pTab!=0 ); assert( pParse->nErr==0 ); if( sqlite3StrNICmp(pTab->zName, "sqlite_", 7)==0 + && db->init.busy==0 +#if SQLITE_USER_AUTHENTICATION + && sqlite3UserAuthTable(pTab->zName)==0 +#endif && sqlite3StrNICmp(&pTab->zName[7],"altertab_",9)!=0 ){ sqlite3ErrorMsg(pParse, "table %s may not be indexed", pTab->zName); goto exit_create_index; @@ -88240,11 +96802,16 @@ SQLITE_PRIVATE Index *sqlite3CreateIndex( ** So create a fake list to simulate this. */ if( pList==0 ){ - pList = sqlite3ExprListAppend(pParse, 0, 0); + Token prevCol; + prevCol.z = pTab->aCol[pTab->nCol-1].zName; + prevCol.n = sqlite3Strlen30(prevCol.z); + pList = sqlite3ExprListAppend(pParse, 0, + sqlite3ExprAlloc(db, TK_ID, &prevCol, 0)); if( pList==0 ) goto exit_create_index; - pList->a[0].zName = sqlite3DbStrDup(pParse->db, - pTab->aCol[pTab->nCol-1].zName); - pList->a[0].sortOrder = (u8)sortOrder; + assert( pList->nExpr==1 ); + sqlite3ExprListSetSortOrder(pList, sortOrder); + }else{ + sqlite3ExprListCheckLength(pParse, pList, "index"); } /* Figure out how many bytes of space are required to store explicitly @@ -88252,8 +96819,8 @@ SQLITE_PRIVATE Index *sqlite3CreateIndex( */ for(i=0; inExpr; i++){ Expr *pExpr = pList->a[i].pExpr; - if( pExpr ){ - assert( pExpr->op==TK_COLLATE ); + assert( pExpr!=0 ); + if( pExpr->op==TK_COLLATE ){ nExtra += (1 + sqlite3Strlen30(pExpr->u.zToken)); } } @@ -88294,35 +96861,54 @@ SQLITE_PRIVATE Index *sqlite3CreateIndex( sortOrderMask = 0; /* Ignore DESC */ } - /* Scan the names of the columns of the table to be indexed and - ** load the column indices into the Index structure. Report an error - ** if any column is not found. + /* Analyze the list of expressions that form the terms of the index and + ** report any errors. In the common case where the expression is exactly + ** a table column, store that column in aiColumn[]. For general expressions, + ** populate pIndex->aColExpr and store XN_EXPR (-2) in aiColumn[]. ** - ** TODO: Add a test to make sure that the same column is not named - ** more than once within the same index. Only the first instance of - ** the column will ever be used by the optimizer. Note that using the - ** same column more than once cannot be an error because that would - ** break backwards compatibility - it needs to be a warning. + ** TODO: Issue a warning if two or more columns of the index are identical. + ** TODO: Issue a warning if the table primary key is used as part of the + ** index key. */ for(i=0, pListItem=pList->a; inExpr; i++, pListItem++){ - const char *zColName = pListItem->zName; - int requestedSortOrder; - char *zColl; /* Collation sequence name */ + Expr *pCExpr; /* The i-th index expression */ + int requestedSortOrder; /* ASC or DESC on the i-th expression */ + const char *zColl; /* Collation sequence name */ - for(j=0, pTabCol=pTab->aCol; jnCol; j++, pTabCol++){ - if( sqlite3StrICmp(zColName, pTabCol->zName)==0 ) break; + sqlite3StringToId(pListItem->pExpr); + sqlite3ResolveSelfReference(pParse, pTab, NC_IdxExpr, pListItem->pExpr, 0); + if( pParse->nErr ) goto exit_create_index; + pCExpr = sqlite3ExprSkipCollate(pListItem->pExpr); + if( pCExpr->op!=TK_COLUMN ){ + if( pTab==pParse->pNewTable ){ + sqlite3ErrorMsg(pParse, "expressions prohibited in PRIMARY KEY and " + "UNIQUE constraints"); + goto exit_create_index; + } + if( pIndex->aColExpr==0 ){ + ExprList *pCopy = sqlite3ExprListDup(db, pList, 0); + pIndex->aColExpr = pCopy; + if( !db->mallocFailed ){ + assert( pCopy!=0 ); + pListItem = &pCopy->a[i]; + } + } + j = XN_EXPR; + pIndex->aiColumn[i] = XN_EXPR; + pIndex->uniqNotNull = 0; + }else{ + j = pCExpr->iColumn; + assert( j<=0x7fff ); + if( j<0 ){ + j = pTab->iPKey; + }else if( pTab->aCol[j].notNull==0 ){ + pIndex->uniqNotNull = 0; + } + pIndex->aiColumn[i] = (i16)j; } - if( j>=pTab->nCol ){ - sqlite3ErrorMsg(pParse, "table %s has no column named %s", - pTab->zName, zColName); - pParse->checkSchema = 1; - goto exit_create_index; - } - assert( pTab->nCol<=0x7fff && j<=0x7fff ); - pIndex->aiColumn[i] = (i16)j; - if( pListItem->pExpr ){ + zColl = 0; + if( pListItem->pExpr->op==TK_COLLATE ){ int nColl; - assert( pListItem->pExpr->op==TK_COLLATE ); zColl = pListItem->pExpr->u.zToken; nColl = sqlite3Strlen30(zColl) + 1; assert( nExtra>=nColl ); @@ -88330,21 +96916,26 @@ SQLITE_PRIVATE Index *sqlite3CreateIndex( zColl = zExtra; zExtra += nColl; nExtra -= nColl; - }else{ + }else if( j>=0 ){ zColl = pTab->aCol[j].zColl; - if( !zColl ) zColl = "BINARY"; } + if( !zColl ) zColl = sqlite3StrBINARY; if( !db->init.busy && !sqlite3LocateCollSeq(pParse, zColl) ){ goto exit_create_index; } pIndex->azColl[i] = zColl; requestedSortOrder = pListItem->sortOrder & sortOrderMask; pIndex->aSortOrder[i] = (u8)requestedSortOrder; - if( pTab->aCol[j].notNull==0 ) pIndex->uniqNotNull = 0; } + + /* Append the table key to the end of the index. For WITHOUT ROWID + ** tables (when pPk!=0) this will be the declared PRIMARY KEY. For + ** normal tables (when pPk==0) this will be the rowid. + */ if( pPk ){ for(j=0; jnKeyCol; j++){ int x = pPk->aiColumn[j]; + assert( x>=0 ); if( hasColumn(pIndex->aiColumn, pIndex->nKeyCol, x) ){ pIndex->nColumn--; }else{ @@ -88356,8 +96947,8 @@ SQLITE_PRIVATE Index *sqlite3CreateIndex( } assert( i==pIndex->nColumn ); }else{ - pIndex->aiColumn[i] = -1; - pIndex->azColl[i] = "BINARY"; + pIndex->aiColumn[i] = XN_ROWID; + pIndex->azColl[i] = sqlite3StrBINARY; } sqlite3DefaultRowEst(pIndex); if( pParse->pNewTable==0 ) estimateIndexWidth(pIndex); @@ -88387,14 +96978,15 @@ SQLITE_PRIVATE Index *sqlite3CreateIndex( Index *pIdx; for(pIdx=pTab->pIndex; pIdx; pIdx=pIdx->pNext){ int k; - assert( pIdx->onError!=OE_None ); + assert( IsUniqueIndex(pIdx) ); assert( pIdx->idxType!=SQLITE_IDXTYPE_APPDEF ); - assert( pIndex->onError!=OE_None ); + assert( IsUniqueIndex(pIndex) ); if( pIdx->nKeyCol!=pIndex->nKeyCol ) continue; for(k=0; knKeyCol; k++){ const char *z1; const char *z2; + assert( pIdx->aiColumn[k]>=0 ); if( pIdx->aiColumn[k]!=pIndex->aiColumn[k] ) break; z1 = pIdx->azColl[k]; z2 = pIndex->azColl[k]; @@ -88417,6 +97009,7 @@ SQLITE_PRIVATE Index *sqlite3CreateIndex( pIdx->onError = pIndex->onError; } } + pRet = pIdx; goto exit_create_index; } } @@ -88425,12 +97018,12 @@ SQLITE_PRIVATE Index *sqlite3CreateIndex( /* Link the new Index structure to its table and to the other ** in-memory database structures. */ + assert( pParse->nErr==0 ); if( db->init.busy ){ Index *p; assert( sqlite3SchemaMutexHeld(db, 0, pIndex->pSchema) ); p = sqlite3HashInsert(&pIndex->pSchema->idxHash, - pIndex->zName, sqlite3Strlen30(pIndex->zName), - pIndex); + pIndex->zName, pIndex); if( p ){ assert( p==pIndex ); /* Malloc must have failed */ db->mallocFailed = 1; @@ -88455,7 +97048,7 @@ SQLITE_PRIVATE Index *sqlite3CreateIndex( ** has just been created, it contains no data and the index initialization ** step can be skipped. */ - else if( pParse->nErr==0 && (HasRowid(pTab) || pTblName!=0) ){ + else if( HasRowid(pTab) || pTblName!=0 ){ Vdbe *v; char *zStmt; int iMem = ++pParse->nMem; @@ -88463,10 +97056,15 @@ SQLITE_PRIVATE Index *sqlite3CreateIndex( v = sqlite3GetVdbe(pParse); if( v==0 ) goto exit_create_index; - - /* Create the rootpage for the index - */ sqlite3BeginWriteOperation(pParse, 1, iDb); + + /* Create the rootpage for the index using CreateIndex. But before + ** doing so, code a Noop instruction and store its address in + ** Index.tnum. This is required in case this index is actually a + ** PRIMARY KEY and the table is actually a WITHOUT ROWID table. In + ** that case the convertToWithoutRowidTable() routine will replace + ** the Noop with a Goto to jump over the VDBE code generated below. */ + pIndex->tnum = sqlite3VdbeAddOp0(v, OP_Noop); sqlite3VdbeAddOp2(v, OP_CreateIndex, iDb, iMem); /* Gather the complete text of the CREATE INDEX statement into @@ -88506,6 +97104,8 @@ SQLITE_PRIVATE Index *sqlite3CreateIndex( sqlite3MPrintf(db, "name='%q' AND type='index'", pIndex->zName)); sqlite3VdbeAddOp1(v, OP_Expire, 0); } + + sqlite3VdbeJumpHere(v, pIndex->tnum); } /* When adding an index to the list of indices for a table, make @@ -88545,7 +97145,7 @@ exit_create_index: ** Fill the Index.aiRowEst[] array with default information - information ** to be used when we have not run the ANALYZE command. ** -** aiRowEst[0] is suppose to contain the number of elements in the index. +** aiRowEst[0] is supposed to contain the number of elements in the index. ** Since we do not know, guess 1 million. aiRowEst[1] is an estimate of the ** number of rows in the table that match any particular value of the ** first column of the index. aiRowEst[2] is an estimate of the number @@ -88580,7 +97180,7 @@ SQLITE_PRIVATE void sqlite3DefaultRowEst(Index *pIdx){ } assert( 0==sqlite3LogEst(1) ); - if( pIdx->onError!=OE_None ) a[pIdx->nKeyCol] = 0; + if( IsUniqueIndex(pIdx) ) a[pIdx->nKeyCol] = 0; } /* @@ -88908,7 +97508,8 @@ SQLITE_PRIVATE void sqlite3SrcListDelete(sqlite3 *db, SrcList *pList){ sqlite3DbFree(db, pItem->zDatabase); sqlite3DbFree(db, pItem->zName); sqlite3DbFree(db, pItem->zAlias); - sqlite3DbFree(db, pItem->zIndex); + if( pItem->fg.isIndexedBy ) sqlite3DbFree(db, pItem->u1.zIndexedBy); + if( pItem->fg.isTabFunc ) sqlite3ExprListDelete(db, pItem->u1.pFuncArg); sqlite3DeleteTable(db, pItem->pTab); sqlite3SelectDelete(db, pItem->pSelect); sqlite3ExprDelete(db, pItem->pOn); @@ -88924,7 +97525,7 @@ SQLITE_PRIVATE void sqlite3SrcListDelete(sqlite3 *db, SrcList *pList){ ** if this is the first term of the FROM clause. pTable and pDatabase ** are the name of the table and database named in the FROM clause term. ** pDatabase is NULL if the database name qualifier is missing - the -** usual case. If the term has a alias, then pAlias points to the +** usual case. If the term has an alias, then pAlias points to the ** alias token. If the term is a subquery, then pSubquery is the ** SELECT statement that the subquery encodes. The pTable and ** pDatabase parameters are NULL for subqueries. The pOn and pUsing @@ -88981,17 +97582,37 @@ SQLITE_PRIVATE void sqlite3SrcListIndexedBy(Parse *pParse, SrcList *p, Token *pI assert( pIndexedBy!=0 ); if( p && ALWAYS(p->nSrc>0) ){ struct SrcList_item *pItem = &p->a[p->nSrc-1]; - assert( pItem->notIndexed==0 && pItem->zIndex==0 ); + assert( pItem->fg.notIndexed==0 ); + assert( pItem->fg.isIndexedBy==0 ); + assert( pItem->fg.isTabFunc==0 ); if( pIndexedBy->n==1 && !pIndexedBy->z ){ /* A "NOT INDEXED" clause was supplied. See parse.y ** construct "indexed_opt" for details. */ - pItem->notIndexed = 1; + pItem->fg.notIndexed = 1; }else{ - pItem->zIndex = sqlite3NameFromToken(pParse->db, pIndexedBy); + pItem->u1.zIndexedBy = sqlite3NameFromToken(pParse->db, pIndexedBy); + pItem->fg.isIndexedBy = (pItem->u1.zIndexedBy!=0); } } } +/* +** Add the list of function arguments to the SrcList entry for a +** table-valued-function. +*/ +SQLITE_PRIVATE void sqlite3SrcListFuncArgs(Parse *pParse, SrcList *p, ExprList *pList){ + if( p ){ + struct SrcList_item *pItem = &p->a[p->nSrc-1]; + assert( pItem->fg.notIndexed==0 ); + assert( pItem->fg.isIndexedBy==0 ); + assert( pItem->fg.isTabFunc==0 ); + pItem->u1.pFuncArg = pList; + pItem->fg.isTabFunc = 1; + }else{ + sqlite3ExprListDelete(pParse->db, pList); + } +} + /* ** When building up a FROM clause in the parser, the join operator ** is initially attached to the left operand. But the code generator @@ -89010,11 +97631,10 @@ SQLITE_PRIVATE void sqlite3SrcListIndexedBy(Parse *pParse, SrcList *p, Token *pI SQLITE_PRIVATE void sqlite3SrcListShiftJoinType(SrcList *p){ if( p ){ int i; - assert( p->a || p->nSrc==0 ); for(i=p->nSrc-1; i>0; i--){ - p->a[i].jointype = p->a[i-1].jointype; + p->a[i].fg.jointype = p->a[i-1].fg.jointype; } - p->a[0].jointype = 0; + p->a[0].fg.jointype = 0; } } @@ -89140,15 +97760,13 @@ SQLITE_PRIVATE int sqlite3OpenTempDatabase(Parse *pParse){ SQLITE_PRIVATE void sqlite3CodeVerifySchema(Parse *pParse, int iDb){ Parse *pToplevel = sqlite3ParseToplevel(pParse); sqlite3 *db = pToplevel->db; - yDbMask mask; assert( iDb>=0 && iDbnDb ); assert( db->aDb[iDb].pBt!=0 || iDb==1 ); assert( iDbcookieMask & mask)==0 ){ - pToplevel->cookieMask |= mask; + if( DbMaskTest(pToplevel->cookieMask, iDb)==0 ){ + DbMaskSet(pToplevel->cookieMask, iDb); pToplevel->cookieValue[iDb] = db->aDb[iDb].pSchema->schema_cookie; if( !OMIT_TEMPDB && iDb==1 ){ sqlite3OpenTempDatabase(pToplevel); @@ -89187,7 +97805,7 @@ SQLITE_PRIVATE void sqlite3CodeVerifyNamedSchema(Parse *pParse, const char *zDb) SQLITE_PRIVATE void sqlite3BeginWriteOperation(Parse *pParse, int setStatement, int iDb){ Parse *pToplevel = sqlite3ParseToplevel(pParse); sqlite3CodeVerifySchema(pParse, iDb); - pToplevel->writeMask |= ((yDbMask)1)<writeMask, iDb); pToplevel->isMultiWrite |= setStatement; } @@ -89259,14 +97877,17 @@ SQLITE_PRIVATE void sqlite3UniqueConstraint( StrAccum errMsg; Table *pTab = pIdx->pTable; - sqlite3StrAccumInit(&errMsg, 0, 0, 200); - errMsg.db = pParse->db; - for(j=0; jnKeyCol; j++){ - char *zCol = pTab->aCol[pIdx->aiColumn[j]].zName; - if( j ) sqlite3StrAccumAppend(&errMsg, ", ", 2); - sqlite3StrAccumAppendAll(&errMsg, pTab->zName); - sqlite3StrAccumAppend(&errMsg, ".", 1); - sqlite3StrAccumAppendAll(&errMsg, zCol); + sqlite3StrAccumInit(&errMsg, pParse->db, 0, 0, 200); + if( pIdx->aColExpr ){ + sqlite3XPrintf(&errMsg, 0, "index '%q'", pIdx->zName); + }else{ + for(j=0; jnKeyCol; j++){ + char *zCol; + assert( pIdx->aiColumn[j]>=0 ); + zCol = pTab->aCol[pIdx->aiColumn[j]].zName; + if( j ) sqlite3StrAccumAppend(&errMsg, ", ", 2); + sqlite3XPrintf(&errMsg, 0, "%s.%s", pTab->zName, zCol); + } } zErr = sqlite3StrAccumFinish(&errMsg); sqlite3HaltConstraint(pParse, @@ -89438,40 +98059,30 @@ SQLITE_PRIVATE void sqlite3Reindex(Parse *pParse, Token *pName1, Token *pName2){ ** when it has finished using it. */ SQLITE_PRIVATE KeyInfo *sqlite3KeyInfoOfIndex(Parse *pParse, Index *pIdx){ + int i; + int nCol = pIdx->nColumn; + int nKey = pIdx->nKeyCol; + KeyInfo *pKey; if( pParse->nErr ) return 0; -#ifndef SQLITE_OMIT_SHARED_CACHE - if( pIdx->pKeyInfo && pIdx->pKeyInfo->db!=pParse->db ){ - sqlite3KeyInfoUnref(pIdx->pKeyInfo); - pIdx->pKeyInfo = 0; + if( pIdx->uniqNotNull ){ + pKey = sqlite3KeyInfoAlloc(pParse->db, nKey, nCol-nKey); + }else{ + pKey = sqlite3KeyInfoAlloc(pParse->db, nCol, 0); } -#endif - if( pIdx->pKeyInfo==0 ){ - int i; - int nCol = pIdx->nColumn; - int nKey = pIdx->nKeyCol; - KeyInfo *pKey; - if( pIdx->uniqNotNull ){ - pKey = sqlite3KeyInfoAlloc(pParse->db, nKey, nCol-nKey); - }else{ - pKey = sqlite3KeyInfoAlloc(pParse->db, nCol, 0); + if( pKey ){ + assert( sqlite3KeyInfoIsWriteable(pKey) ); + for(i=0; iazColl[i]; + pKey->aColl[i] = zColl==sqlite3StrBINARY ? 0 : + sqlite3LocateCollSeq(pParse, zColl); + pKey->aSortOrder[i] = pIdx->aSortOrder[i]; } - if( pKey ){ - assert( sqlite3KeyInfoIsWriteable(pKey) ); - for(i=0; iazColl[i]; - assert( zColl!=0 ); - pKey->aColl[i] = strcmp(zColl,"BINARY")==0 ? 0 : - sqlite3LocateCollSeq(pParse, zColl); - pKey->aSortOrder[i] = pIdx->aSortOrder[i]; - } - if( pParse->nErr ){ - sqlite3KeyInfoUnref(pKey); - }else{ - pIdx->pKeyInfo = pKey; - } + if( pParse->nErr ){ + sqlite3KeyInfoUnref(pKey); + pKey = 0; } } - return sqlite3KeyInfoRef(pIdx->pKeyInfo); + return pKey; } #ifndef SQLITE_OMIT_CTE @@ -89520,7 +98131,7 @@ SQLITE_PRIVATE With *sqlite3WithAdd( pNew->a[pNew->nCte].pSelect = pQuery; pNew->a[pNew->nCte].pCols = pArglist; pNew->a[pNew->nCte].zName = zName; - pNew->a[pNew->nCte].zErr = 0; + pNew->a[pNew->nCte].zCteErr = 0; pNew->nCte++; } @@ -89562,6 +98173,7 @@ SQLITE_PRIVATE void sqlite3WithDelete(sqlite3 *db, With *pWith){ ** of user defined functions and collation sequences. */ +/* #include "sqliteInt.h" */ /* ** Invoke the 'collation needed' callback to request a collation sequence @@ -89689,7 +98301,7 @@ SQLITE_PRIVATE int sqlite3CheckCollSeq(Parse *pParse, CollSeq *pColl){ ** ** Each pointer stored in the sqlite3.aCollSeq hash table contains an ** array of three CollSeq structures. The first is the collation sequence -** prefferred for UTF-8, the second UTF-16le, and the third UTF-16be. +** preferred for UTF-8, the second UTF-16le, and the third UTF-16be. ** ** Stored immediately after the three collation sequences is a copy of ** the collation sequence name. A pointer to this string is stored in @@ -89701,11 +98313,11 @@ static CollSeq *findCollSeqEntry( int create /* Create a new entry if true */ ){ CollSeq *pColl; - int nName = sqlite3Strlen30(zName); - pColl = sqlite3HashFind(&db->aCollSeq, zName, nName); + pColl = sqlite3HashFind(&db->aCollSeq, zName); if( 0==pColl && create ){ - pColl = sqlite3DbMallocZero(db, 3*sizeof(*pColl) + nName + 1 ); + int nName = sqlite3Strlen30(zName); + pColl = sqlite3DbMallocZero(db, 3*sizeof(*pColl) + nName + 1); if( pColl ){ CollSeq *pDel = 0; pColl[0].zName = (char*)&pColl[3]; @@ -89716,7 +98328,7 @@ static CollSeq *findCollSeqEntry( pColl[2].enc = SQLITE_UTF16BE; memcpy(pColl[0].zName, zName, nName); pColl[0].zName[nName] = 0; - pDel = sqlite3HashInsert(&db->aCollSeq, pColl[0].zName, nName, pColl); + pDel = sqlite3HashInsert(&db->aCollSeq, pColl[0].zName, pColl); /* If a malloc() failure occurred in sqlite3HashInsert(), it will ** return the pColl pointer to be deleted (because it wasn't added @@ -89994,9 +98606,9 @@ SQLITE_PRIVATE void sqlite3SchemaClear(void *p){ sqlite3HashClear(&temp1); sqlite3HashClear(&pSchema->fkeyHash); pSchema->pSeqTab = 0; - if( pSchema->flags & DB_SchemaLoaded ){ + if( pSchema->schemaFlags & DB_SchemaLoaded ){ pSchema->iGeneration++; - pSchema->flags &= ~DB_SchemaLoaded; + pSchema->schemaFlags &= ~DB_SchemaLoaded; } } @@ -90039,6 +98651,7 @@ SQLITE_PRIVATE Schema *sqlite3SchemaGet(sqlite3 *db, Btree *pBt){ ** This file contains C code routines that are called by the parser ** in order to generate code for DELETE FROM statements. */ +/* #include "sqliteInt.h" */ /* ** While a SrcList can in general represent multiple tables and subqueries @@ -90116,7 +98729,7 @@ SQLITE_PRIVATE void sqlite3MaterializeView( Parse *pParse, /* Parsing context */ Table *pView, /* View definition */ Expr *pWhere, /* Optional WHERE clause to be added */ - int iCur /* Cursor number for ephemerial table */ + int iCur /* Cursor number for ephemeral table */ ){ SelectDest dest; Select *pSel; @@ -90132,7 +98745,8 @@ SQLITE_PRIVATE void sqlite3MaterializeView( assert( pFrom->a[0].pOn==0 ); assert( pFrom->a[0].pUsing==0 ); } - pSel = sqlite3SelectNew(pParse, 0, pFrom, pWhere, 0, 0, 0, 0, 0, 0); + pSel = sqlite3SelectNew(pParse, 0, pFrom, pWhere, 0, 0, 0, + SF_IncludeHidden, 0, 0); sqlite3SelectDestInit(&dest, SRT_EphemTab, iCur); sqlite3Select(pParse, pSel, &dest); sqlite3SelectDelete(db, pSel); @@ -90215,7 +98829,7 @@ SQLITE_PRIVATE Expr *sqlite3LimitWhere( pInClause->x.pSelect = pSelect; pInClause->flags |= EP_xIsSelect; - sqlite3ExprSetHeight(pParse, pInClause); + sqlite3ExprSetHeightAndFlags(pParse, pInClause); return pInClause; /* something went wrong. clean up anything allocated. */ @@ -90252,8 +98866,8 @@ SQLITE_PRIVATE void sqlite3DeleteFrom( WhereInfo *pWInfo; /* Information about the WHERE clause */ Index *pIdx; /* For looping over indices of the table */ int iTabCur; /* Cursor number for the table */ - int iDataCur; /* VDBE cursor for the canonical data source */ - int iIdxCur; /* Cursor number of the first index */ + int iDataCur = 0; /* VDBE cursor for the canonical data source */ + int iIdxCur = 0; /* Cursor number of the first index */ int nIdx; /* Number of indices */ sqlite3 *db; /* Main database structure */ AuthContext sContext; /* Authorization context */ @@ -90261,7 +98875,7 @@ SQLITE_PRIVATE void sqlite3DeleteFrom( int iDb; /* Database number */ int memCnt = -1; /* Memory cell used for change counting */ int rcauth; /* Value returned by authorization callback */ - int okOnePass; /* True for one-pass algorithm without the FIFO */ + int eOnePass; /* ONEPASS_OFF or _SINGLE or _MULTI */ int aiCurOnePass[2]; /* The write cursors opened by WHERE_ONEPASS */ u8 *aToOpen = 0; /* Open cursor iTabCur+j if aToOpen[j] is true */ Index *pPk; /* The PRIMARY KEY index on the table */ @@ -90273,12 +98887,12 @@ SQLITE_PRIVATE void sqlite3DeleteFrom( int iRowSet = 0; /* Register for rowset of rows to delete */ int addrBypass = 0; /* Address of jump over the delete logic */ int addrLoop = 0; /* Top of the delete loop */ - int addrDelete = 0; /* Jump directly to the delete logic */ - int addrEphOpen = 0; /* Instruction to open the Ephermeral table */ + int addrEphOpen = 0; /* Instruction to open the Ephemeral table */ #ifndef SQLITE_OMIT_TRIGGER int isView; /* True if attempting to delete from a view */ Trigger *pTrigger; /* List of table triggers, if required */ + int bComplex; /* True if there are either triggers or FKs */ #endif memset(&sContext, 0, sizeof(sContext)); @@ -90302,9 +98916,11 @@ SQLITE_PRIVATE void sqlite3DeleteFrom( #ifndef SQLITE_OMIT_TRIGGER pTrigger = sqlite3TriggersExist(pParse, pTab, TK_DELETE, 0, 0); isView = pTab->pSelect!=0; + bComplex = pTrigger || sqlite3FkRequired(pParse, pTab, 0, 0); #else # define pTrigger 0 # define isView 0 +# define bComplex 0 #endif #ifdef SQLITE_OMIT_VIEW # undef isView @@ -90354,7 +98970,7 @@ SQLITE_PRIVATE void sqlite3DeleteFrom( sqlite3BeginWriteOperation(pParse, 1, iDb); /* If we are trying to delete from a view, realize that view into - ** a ephemeral table. + ** an ephemeral table. */ #if !defined(SQLITE_OMIT_VIEW) && !defined(SQLITE_OMIT_TRIGGER) if( isView ){ @@ -90385,8 +99001,10 @@ SQLITE_PRIVATE void sqlite3DeleteFrom( ** It is easier just to erase the whole table. Prior to version 3.6.5, ** this optimization caused the row change count (the value returned by ** API function sqlite3_count_changes) to be set incorrectly. */ - if( rcauth==SQLITE_OK && pWhere==0 && !pTrigger && !IsVirtual(pTab) - && 0==sqlite3FkRequired(pParse, pTab, 0, 0) + if( rcauth==SQLITE_OK + && pWhere==0 + && !bComplex + && !IsVirtual(pTab) ){ assert( !isView ); sqlite3TableLock(pParse, iDb, pTab->tnum, 1, pTab->zName); @@ -90401,6 +99019,8 @@ SQLITE_PRIVATE void sqlite3DeleteFrom( }else #endif /* SQLITE_OMIT_TRUNCATE_OPTIMIZATION */ { + u16 wcf = WHERE_ONEPASS_DESIRED|WHERE_DUPLICATES_OK; + wcf |= (bComplex ? 0 : WHERE_ONEPASS_MULTIROW); if( HasRowid(pTab) ){ /* For a rowid table, initialize the RowSet to an empty set */ pPk = 0; @@ -90408,7 +99028,7 @@ SQLITE_PRIVATE void sqlite3DeleteFrom( iRowSet = ++pParse->nMem; sqlite3VdbeAddOp2(v, OP_Null, 0, iRowSet); }else{ - /* For a WITHOUT ROWID table, create an ephermeral table used to + /* For a WITHOUT ROWID table, create an ephemeral table used to ** hold all primary keys for rows to be deleted. */ pPk = sqlite3PrimaryKeyIndex(pTab); assert( pPk!=0 ); @@ -90421,13 +99041,18 @@ SQLITE_PRIVATE void sqlite3DeleteFrom( } /* Construct a query to find the rowid or primary key for every row - ** to be deleted, based on the WHERE clause. + ** to be deleted, based on the WHERE clause. Set variable eOnePass + ** to indicate the strategy used to implement this delete: + ** + ** ONEPASS_OFF: Two-pass approach - use a FIFO for rowids/PK values. + ** ONEPASS_SINGLE: One-pass approach - at most one row deleted. + ** ONEPASS_MULTI: One-pass approach - any number of rows may be deleted. */ - pWInfo = sqlite3WhereBegin(pParse, pTabList, pWhere, 0, 0, - WHERE_ONEPASS_DESIRED|WHERE_DUPLICATES_OK, - iTabCur+1); + pWInfo = sqlite3WhereBegin(pParse, pTabList, pWhere, 0, 0, wcf, iTabCur+1); if( pWInfo==0 ) goto delete_from_cleanup; - okOnePass = sqlite3WhereOkOnePass(pWInfo, aiCurOnePass); + eOnePass = sqlite3WhereOkOnePass(pWInfo, aiCurOnePass); + assert( IsVirtual(pTab)==0 || eOnePass!=ONEPASS_MULTI ); + assert( IsVirtual(pTab) || bComplex || eOnePass!=ONEPASS_OFF ); /* Keep track of the number of rows to be deleted */ if( db->flags & SQLITE_CountRows ){ @@ -90437,6 +99062,7 @@ SQLITE_PRIVATE void sqlite3DeleteFrom( /* Extract the rowid or primary key for the current row */ if( pPk ){ for(i=0; iaiColumn[i]>=0 ); sqlite3ExprCodeGetColumnOfTable(v, pTab, iTabCur, pPk->aiColumn[i], iPk+i); } @@ -90447,11 +99073,10 @@ SQLITE_PRIVATE void sqlite3DeleteFrom( if( iKey>pParse->nMem ) pParse->nMem = iKey; } - if( okOnePass ){ - /* For ONEPASS, no need to store the rowid/primary-key. There is only + if( eOnePass!=ONEPASS_OFF ){ + /* For ONEPASS, no need to store the rowid/primary-key. There is only ** one, so just keep it in its register(s) and fall through to the - ** delete code. - */ + ** delete code. */ nKey = nPk; /* OP_Found will use an unpacked key */ aToOpen = sqlite3DbMallocRaw(db, nIdx+2); if( aToOpen==0 ){ @@ -90463,27 +99088,27 @@ SQLITE_PRIVATE void sqlite3DeleteFrom( if( aiCurOnePass[0]>=0 ) aToOpen[aiCurOnePass[0]-iTabCur] = 0; if( aiCurOnePass[1]>=0 ) aToOpen[aiCurOnePass[1]-iTabCur] = 0; if( addrEphOpen ) sqlite3VdbeChangeToNoop(v, addrEphOpen); - addrDelete = sqlite3VdbeAddOp0(v, OP_Goto); /* Jump to DELETE logic */ - }else if( pPk ){ - /* Construct a composite key for the row to be deleted and remember it */ - iKey = ++pParse->nMem; - nKey = 0; /* Zero tells OP_Found to use a composite key */ - sqlite3VdbeAddOp4(v, OP_MakeRecord, iPk, nPk, iKey, - sqlite3IndexAffinityStr(v, pPk), nPk); - sqlite3VdbeAddOp2(v, OP_IdxInsert, iEphCur, iKey); }else{ - /* Get the rowid of the row to be deleted and remember it in the RowSet */ - nKey = 1; /* OP_Seek always uses a single rowid */ - sqlite3VdbeAddOp2(v, OP_RowSetAdd, iRowSet, iKey); + if( pPk ){ + /* Add the PK key for this row to the temporary table */ + iKey = ++pParse->nMem; + nKey = 0; /* Zero tells OP_Found to use a composite key */ + sqlite3VdbeAddOp4(v, OP_MakeRecord, iPk, nPk, iKey, + sqlite3IndexAffinityStr(pParse->db, pPk), nPk); + sqlite3VdbeAddOp2(v, OP_IdxInsert, iEphCur, iKey); + }else{ + /* Add the rowid of the row to be deleted to the RowSet */ + nKey = 1; /* OP_Seek always uses a single rowid */ + sqlite3VdbeAddOp2(v, OP_RowSetAdd, iRowSet, iKey); + } } - /* End of the WHERE loop */ - sqlite3WhereEnd(pWInfo); - if( okOnePass ){ - /* Bypass the delete logic below if the WHERE loop found zero rows */ + /* If this DELETE cannot use the ONEPASS strategy, this is the + ** end of the WHERE loop */ + if( eOnePass!=ONEPASS_OFF ){ addrBypass = sqlite3VdbeMakeLabel(v); - sqlite3VdbeAddOp2(v, OP_Goto, 0, addrBypass); - sqlite3VdbeJumpHere(v, addrDelete); + }else{ + sqlite3WhereEnd(pWInfo); } /* Unless this is a view, open cursors for the table we are @@ -90492,20 +99117,26 @@ SQLITE_PRIVATE void sqlite3DeleteFrom( ** triggers. */ if( !isView ){ - sqlite3OpenTableAndIndices(pParse, pTab, OP_OpenWrite, iTabCur, aToOpen, - &iDataCur, &iIdxCur); - assert( pPk || iDataCur==iTabCur ); - assert( pPk || iIdxCur==iDataCur+1 ); + int iAddrOnce = 0; + u8 p5 = (eOnePass==ONEPASS_OFF ? 0 : OPFLAG_FORDELETE); + if( eOnePass==ONEPASS_MULTI ){ + iAddrOnce = sqlite3CodeOnce(pParse); VdbeCoverage(v); + } + testcase( IsVirtual(pTab) ); + sqlite3OpenTableAndIndices(pParse, pTab, OP_OpenWrite, p5, iTabCur, + aToOpen, &iDataCur, &iIdxCur); + assert( pPk || IsVirtual(pTab) || iDataCur==iTabCur ); + assert( pPk || IsVirtual(pTab) || iIdxCur==iDataCur+1 ); + if( eOnePass==ONEPASS_MULTI ) sqlite3VdbeJumpHere(v, iAddrOnce); } /* Set up a loop over the rowids/primary-keys that were found in the ** where-clause loop above. */ - if( okOnePass ){ - /* Just one row. Hence the top-of-loop is a no-op */ - assert( nKey==nPk ); /* OP_Found will use an unpacked key */ - if( aToOpen[iDataCur-iTabCur] ){ - assert( pPk!=0 ); + if( eOnePass!=ONEPASS_OFF ){ + assert( nKey==nPk ); /* OP_Found will use an unpacked key */ + if( !IsVirtual(pTab) && aToOpen[iDataCur-iTabCur] ){ + assert( pPk!=0 || pTab->pSelect!=0 ); sqlite3VdbeAddOp4Int(v, OP_NotFound, iDataCur, addrBypass, iKey, nKey); VdbeCoverage(v); } @@ -90526,23 +99157,32 @@ SQLITE_PRIVATE void sqlite3DeleteFrom( sqlite3VtabMakeWritable(pParse, pTab); sqlite3VdbeAddOp4(v, OP_VUpdate, 0, 1, iKey, pVTab, P4_VTAB); sqlite3VdbeChangeP5(v, OE_Abort); + assert( eOnePass==ONEPASS_OFF || eOnePass==ONEPASS_SINGLE ); sqlite3MayAbort(pParse); + if( eOnePass==ONEPASS_SINGLE && sqlite3IsToplevel(pParse) ){ + pParse->isMultiWrite = 0; + } }else #endif { int count = (pParse->nested==0); /* True to count changes */ + int iIdxNoSeek = -1; + if( bComplex==0 && aiCurOnePass[1]!=iDataCur ){ + iIdxNoSeek = aiCurOnePass[1]; + } sqlite3GenerateRowDelete(pParse, pTab, pTrigger, iDataCur, iIdxCur, - iKey, nKey, count, OE_Default, okOnePass); + iKey, nKey, count, OE_Default, eOnePass, iIdxNoSeek); } /* End of the loop over all rowids/primary-keys. */ - if( okOnePass ){ + if( eOnePass!=ONEPASS_OFF ){ sqlite3VdbeResolveLabel(v, addrBypass); + sqlite3WhereEnd(pWInfo); }else if( pPk ){ sqlite3VdbeAddOp2(v, OP_Next, iEphCur, addrLoop+1); VdbeCoverage(v); sqlite3VdbeJumpHere(v, addrLoop); }else{ - sqlite3VdbeAddOp2(v, OP_Goto, 0, addrLoop); + sqlite3VdbeGoto(v, addrLoop); sqlite3VdbeJumpHere(v, addrLoop); } @@ -90581,7 +99221,7 @@ delete_from_cleanup: return; } /* Make sure "isView" and other macros defined above are undefined. Otherwise -** thely may interfere with compilation of other functions in this file +** they may interfere with compilation of other functions in this file ** (or in another file, if this file becomes part of the amalgamation). */ #ifdef isView #undef isView @@ -90609,6 +99249,25 @@ delete_from_cleanup: ** sequence of nPk memory cells starting at iPk. If nPk==0 that means ** that a search record formed from OP_MakeRecord is contained in the ** single memory location iPk. +** +** eMode: +** Parameter eMode may be passed either ONEPASS_OFF (0), ONEPASS_SINGLE, or +** ONEPASS_MULTI. If eMode is not ONEPASS_OFF, then the cursor +** iDataCur already points to the row to delete. If eMode is ONEPASS_OFF +** then this function must seek iDataCur to the entry identified by iPk +** and nPk before reading from it. +** +** If eMode is ONEPASS_MULTI, then this call is being made as part +** of a ONEPASS delete that affects multiple rows. In this case, if +** iIdxNoSeek is a valid cursor number (>=0), then its position should +** be preserved following the delete operation. Or, if iIdxNoSeek is not +** a valid cursor number, the position of iDataCur should be preserved +** instead. +** +** iIdxNoSeek: +** If iIdxNoSeek is a valid cursor number (>=0), then it identifies an +** index cursor (from within array of cursors starting at iIdxCur) that +** already points to the index entry to be deleted. */ SQLITE_PRIVATE void sqlite3GenerateRowDelete( Parse *pParse, /* Parsing context */ @@ -90620,7 +99279,8 @@ SQLITE_PRIVATE void sqlite3GenerateRowDelete( i16 nPk, /* Number of PRIMARY KEY memory cells */ u8 count, /* If non-zero, increment the row change counter */ u8 onconf, /* Default ON CONFLICT policy for triggers */ - u8 bNoSeek /* iDataCur is already pointing to the row to delete */ + u8 eMode, /* ONEPASS_OFF, _SINGLE, or _MULTI. See above */ + int iIdxNoSeek /* Cursor number of cursor that does not need seeking */ ){ Vdbe *v = pParse->pVdbe; /* Vdbe */ int iOld = 0; /* First register in OLD.* array */ @@ -90637,7 +99297,7 @@ SQLITE_PRIVATE void sqlite3GenerateRowDelete( ** not attempt to delete it or fire any DELETE triggers. */ iLabel = sqlite3VdbeMakeLabel(v); opSeek = HasRowid(pTab) ? OP_NotExists : OP_NotFound; - if( !bNoSeek ){ + if( eMode==ONEPASS_OFF ){ sqlite3VdbeAddOp4Int(v, opSeek, iDataCur, iLabel, iPk, nPk); VdbeCoverageIf(v, opSeek==OP_NotExists); VdbeCoverageIf(v, opSeek==OP_NotFound); @@ -90697,11 +99357,15 @@ SQLITE_PRIVATE void sqlite3GenerateRowDelete( ** a view (in which case the only effect of the DELETE statement is to ** fire the INSTEAD OF triggers). */ if( pTab->pSelect==0 ){ - sqlite3GenerateRowIndexDelete(pParse, pTab, iDataCur, iIdxCur, 0); + sqlite3GenerateRowIndexDelete(pParse, pTab, iDataCur, iIdxCur,0,iIdxNoSeek); sqlite3VdbeAddOp2(v, OP_Delete, iDataCur, (count?OPFLAG_NCHANGE:0)); if( count ){ sqlite3VdbeChangeP4(v, -1, pTab->zName, P4_TRANSIENT); } + if( iIdxNoSeek>=0 ){ + sqlite3VdbeAddOp1(v, OP_Delete, iIdxNoSeek); + } + sqlite3VdbeChangeP5(v, eMode==ONEPASS_MULTI); } /* Do any ON CASCADE, SET NULL or SET DEFAULT operations required to @@ -90744,7 +99408,8 @@ SQLITE_PRIVATE void sqlite3GenerateRowIndexDelete( Table *pTab, /* Table containing the row to be deleted */ int iDataCur, /* Cursor of table holding data. */ int iIdxCur, /* First index cursor */ - int *aRegIdx /* Only delete if aRegIdx!=0 && aRegIdx[i]>0 */ + int *aRegIdx, /* Only delete if aRegIdx!=0 && aRegIdx[i]>0 */ + int iIdxNoSeek /* Do not delete from this cursor */ ){ int i; /* Index loop counter */ int r1 = -1; /* Register holding an index key */ @@ -90760,11 +99425,12 @@ SQLITE_PRIVATE void sqlite3GenerateRowIndexDelete( assert( iIdxCur+i!=iDataCur || pPk==pIdx ); if( aRegIdx!=0 && aRegIdx[i]==0 ) continue; if( pIdx==pPk ) continue; + if( iIdxCur+i==iIdxNoSeek ) continue; VdbeModuleComment((v, "GenRowIdxDel for %s", pIdx->zName)); r1 = sqlite3GenerateIndexKey(pParse, pIdx, iDataCur, 0, 1, - &iPartIdxLabel, pPrior, r1); + &iPartIdxLabel, pPrior, r1); sqlite3VdbeAddOp3(v, OP_IdxDelete, iIdxCur+i, r1, - pIdx->uniqNotNull ? pIdx->nKeyCol : pIdx->nColumn); + pIdx->uniqNotNull ? pIdx->nKeyCol : pIdx->nColumn); sqlite3ResolvePartIdxLabel(pParse, iPartIdxLabel); pPrior = pIdx; } @@ -90813,17 +99479,16 @@ SQLITE_PRIVATE int sqlite3GenerateIndexKey( ){ Vdbe *v = pParse->pVdbe; int j; - Table *pTab = pIdx->pTable; int regBase; int nCol; if( piPartIdxLabel ){ if( pIdx->pPartIdxWhere ){ *piPartIdxLabel = sqlite3VdbeMakeLabel(v); - pParse->iPartIdxTab = iDataCur; + pParse->iSelfTab = iDataCur; sqlite3ExprCachePush(pParse); - sqlite3ExprIfFalse(pParse, pIdx->pPartIdxWhere, *piPartIdxLabel, - SQLITE_JUMPIFNULL); + sqlite3ExprIfFalseDup(pParse, pIdx->pPartIdxWhere, *piPartIdxLabel, + SQLITE_JUMPIFNULL); }else{ *piPartIdxLabel = 0; } @@ -90832,9 +99497,14 @@ SQLITE_PRIVATE int sqlite3GenerateIndexKey( regBase = sqlite3GetTempRange(pParse, nCol); if( pPrior && (regBase!=regPrior || pPrior->pPartIdxWhere) ) pPrior = 0; for(j=0; jaiColumn[j]==pIdx->aiColumn[j] ) continue; - sqlite3ExprCodeGetColumnOfTable(v, pTab, iDataCur, pIdx->aiColumn[j], - regBase+j); + if( pPrior + && pPrior->aiColumn[j]==pIdx->aiColumn[j] + && pPrior->aiColumn[j]!=XN_EXPR + ){ + /* This column was already computed by the previous index */ + continue; + } + sqlite3ExprCodeLoadIndexColumn(pParse, pIdx, iDataCur, j, regBase+j); /* If the column affinity is REAL but the number is an integer, then it ** might be stored in the table as an integer (using a compact ** representation) then converted to REAL by an OP_RealAffinity opcode. @@ -90875,21 +99545,25 @@ SQLITE_PRIVATE void sqlite3ResolvePartIdxLabel(Parse *pParse, int iLabel){ ** May you share freely, never taking more than you give. ** ************************************************************************* -** This file contains the C functions that implement various SQL -** functions of SQLite. -** -** There is only one exported symbol in this file - the function -** sqliteRegisterBuildinFunctions() found at the bottom of the file. -** All other code has file scope. +** This file contains the C-language implementations for many of the SQL +** functions of SQLite. (Some function, and in particular the date and +** time functions, are implemented separately.) */ +/* #include "sqliteInt.h" */ /* #include */ /* #include */ +/* #include "vdbeInt.h" */ /* ** Return the collating function associated with a function. */ static CollSeq *sqlite3GetFuncCollSeq(sqlite3_context *context){ - return context->pColl; + VdbeOp *pOp; + assert( context->pVdbe!=0 ); + pOp = &context->pVdbe->aOp[context->iOp-1]; + assert( pOp->opcode==OP_CollSeq ); + assert( pOp->p4type==P4_COLLSEQ ); + return pOp->p4.pColl; } /* @@ -91021,8 +99695,8 @@ static void absFunc(sqlite3_context *context, int argc, sqlite3_value **argv){ default: { /* Because sqlite3_value_double() returns 0.0 if the argument is not ** something that can be converted into a number, we have: - ** IMP: R-57326-31541 Abs(X) return 0.0 if X is a string or blob that - ** cannot be converted to a numeric value. + ** IMP: R-01992-00519 Abs(X) returns 0.0 if X is a string or blob + ** that cannot be converted to a numeric value. */ double rVal = sqlite3_value_double(argv[0]); if( rVal<0 ) rVal = -rVal; @@ -91094,13 +99768,13 @@ static void printfFunc( StrAccum str; const char *zFormat; int n; + sqlite3 *db = sqlite3_context_db_handle(context); if( argc>=1 && (zFormat = (const char*)sqlite3_value_text(argv[0]))!=0 ){ x.nArg = argc-1; x.nUsed = 0; x.apArg = argv+1; - sqlite3StrAccumInit(&str, 0, 0, SQLITE_MAX_LENGTH); - str.db = sqlite3_context_db_handle(context); + sqlite3StrAccumInit(&str, db, 0, 0, db->aLimit[SQLITE_LIMIT_LENGTH]); sqlite3XPrintf(&str, SQLITE_PRINTF_SQLFUNC, zFormat, &x); n = str.nChar; sqlite3_result_text(context, sqlite3StrAccumFinish(&str), n, @@ -91155,6 +99829,14 @@ static void substrFunc( } } } +#ifdef SQLITE_SUBSTR_COMPATIBILITY + /* If SUBSTR_COMPATIBILITY is defined then substr(X,0,N) work the same as + ** as substr(X,1,N) - it returns the first N characters of X. This + ** is essentially a back-out of the bug-fix in check-in [5fc125d362df4b8] + ** from 2009-02-02 for compatibility of applications that exploited the + ** old buggy behavior. */ + if( p1==0 ) p1 = 1; /* */ +#endif if( argc==3 ){ p2 = sqlite3_value_int(argv[2]); if( p2<0 ){ @@ -91192,13 +99874,14 @@ static void substrFunc( for(z2=z; *z2 && p2; p2--){ SQLITE_SKIP_UTF8(z2); } - sqlite3_result_text(context, (char*)z, (int)(z2-z), SQLITE_TRANSIENT); + sqlite3_result_text64(context, (char*)z, z2-z, SQLITE_TRANSIENT, + SQLITE_UTF8); }else{ if( p1+p2>len ){ p2 = len-p1; if( p2<0 ) p2 = 0; } - sqlite3_result_blob(context, (char*)&z[p1], (int)p2, SQLITE_TRANSIENT); + sqlite3_result_blob64(context, (char*)&z[p1], (u64)p2, SQLITE_TRANSIENT); } } @@ -91241,7 +99924,7 @@ static void roundFunc(sqlite3_context *context, int argc, sqlite3_value **argv){ #endif /* -** Allocate nByte bytes of space using sqlite3_malloc(). If the +** Allocate nByte bytes of space using sqlite3Malloc(). If the ** allocation fails, call sqlite3_result_error_nomem() to notify ** the database handle that malloc() has failed and return NULL. ** If nByte is larger than the maximum string or blob length, then @@ -91257,7 +99940,7 @@ static void *contextMalloc(sqlite3_context *context, i64 nByte){ sqlite3_result_error_toobig(context); z = 0; }else{ - z = sqlite3Malloc((int)nByte); + z = sqlite3Malloc(nByte); if( !z ){ sqlite3_result_error_nomem(context); } @@ -91428,15 +100111,15 @@ struct compareInfo { /* ** For LIKE and GLOB matching on EBCDIC machines, assume that every -** character is exactly one byte in size. Also, all characters are -** able to participate in upper-case-to-lower-case mappings in EBCDIC -** whereas only characters less than 0x80 do in ASCII. +** character is exactly one byte in size. Also, provde the Utf8Read() +** macro for fast reading of the next character in the common case where +** the next character is ASCII. */ #if defined(SQLITE_EBCDIC) -# define sqlite3Utf8Read(A) (*((*A)++)) -# define GlobUpperToLower(A) A = sqlite3UpperToLower[A] +# define sqlite3Utf8Read(A) (*((*A)++)) +# define Utf8Read(A) (*(A++)) #else -# define GlobUpperToLower(A) if( !((A)&~0x7f) ){ A = sqlite3UpperToLower[A]; } +# define Utf8Read(A) (A[0]<0x80?*(A++):sqlite3Utf8Read(&A)) #endif static const struct compareInfo globInfo = { '*', '?', '[', 0 }; @@ -91449,7 +100132,7 @@ static const struct compareInfo likeInfoAlt = { '%', '_', 0, 0 }; /* ** Compare two UTF-8 strings for equality where the first string can -** potentially be a "glob" expression. Return true (1) if they +** potentially be a "glob" or "like" expression. Return true (1) if they ** are the same and false (0) if they are different. ** ** Globbing rules: @@ -91469,11 +100152,18 @@ static const struct compareInfo likeInfoAlt = { '%', '_', 0, 0 }; ** "[a-z]" matches any single lower-case letter. To match a '-', make ** it the last character in the list. ** +** Like matching rules: +** +** '%' Matches any sequence of zero or more characters +** +*** '_' Matches any one character +** +** Ec Where E is the "esc" character and c is any other +** character, including '%', '_', and esc, match exactly c. +** +** The comments within this routine usually assume glob matching. +** ** This routine is usually quick, but can be N**2 in the worst case. -** -** Hints: to match '*' or '?', put them in "[]". Like this: -** -** abc[*]xyz Matches "abc*xyz" only */ static int patternCompare( const u8 *zPattern, /* The glob pattern */ @@ -91481,104 +100171,123 @@ static int patternCompare( const struct compareInfo *pInfo, /* Information about how to do the compare */ u32 esc /* The escape character */ ){ - u32 c, c2; - int invert; - int seen; - u8 matchOne = pInfo->matchOne; - u8 matchAll = pInfo->matchAll; - u8 matchSet = pInfo->matchSet; - u8 noCase = pInfo->noCase; - int prevEscape = 0; /* True if the previous character was 'escape' */ + u32 c, c2; /* Next pattern and input string chars */ + u32 matchOne = pInfo->matchOne; /* "?" or "_" */ + u32 matchAll = pInfo->matchAll; /* "*" or "%" */ + u32 matchOther; /* "[" or the escape character */ + u8 noCase = pInfo->noCase; /* True if uppercase==lowercase */ + const u8 *zEscaped = 0; /* One past the last escaped input char */ + + /* The GLOB operator does not have an ESCAPE clause. And LIKE does not + ** have the matchSet operator. So we either have to look for one or + ** the other, never both. Hence the single variable matchOther is used + ** to store the one we have to look for. + */ + matchOther = esc ? esc : pInfo->matchSet; - while( (c = sqlite3Utf8Read(&zPattern))!=0 ){ - if( c==matchAll && !prevEscape ){ - while( (c=sqlite3Utf8Read(&zPattern)) == matchAll - || c == matchOne ){ + while( (c = Utf8Read(zPattern))!=0 ){ + if( c==matchAll ){ /* Match "*" */ + /* Skip over multiple "*" characters in the pattern. If there + ** are also "?" characters, skip those as well, but consume a + ** single character of the input string for each "?" skipped */ + while( (c=Utf8Read(zPattern)) == matchAll || c == matchOne ){ if( c==matchOne && sqlite3Utf8Read(&zString)==0 ){ return 0; } } if( c==0 ){ - return 1; - }else if( c==esc ){ - c = sqlite3Utf8Read(&zPattern); - if( c==0 ){ - return 0; - } - }else if( c==matchSet ){ - assert( esc==0 ); /* This is GLOB, not LIKE */ - assert( matchSet<0x80 ); /* '[' is a single-byte character */ - while( *zString && patternCompare(&zPattern[-1],zString,pInfo,esc)==0 ){ - SQLITE_SKIP_UTF8(zString); - } - return *zString!=0; - } - while( (c2 = sqlite3Utf8Read(&zString))!=0 ){ - if( noCase ){ - GlobUpperToLower(c2); - GlobUpperToLower(c); - while( c2 != 0 && c2 != c ){ - c2 = sqlite3Utf8Read(&zString); - GlobUpperToLower(c2); - } + return 1; /* "*" at the end of the pattern matches */ + }else if( c==matchOther ){ + if( esc ){ + c = sqlite3Utf8Read(&zPattern); + if( c==0 ) return 0; }else{ - while( c2 != 0 && c2 != c ){ - c2 = sqlite3Utf8Read(&zString); + /* "[...]" immediately follows the "*". We have to do a slow + ** recursive search in this case, but it is an unusual case. */ + assert( matchOther<0x80 ); /* '[' is a single-byte character */ + while( *zString + && patternCompare(&zPattern[-1],zString,pInfo,esc)==0 ){ + SQLITE_SKIP_UTF8(zString); } + return *zString!=0; + } + } + + /* At this point variable c contains the first character of the + ** pattern string past the "*". Search in the input string for the + ** first matching character and recursively contine the match from + ** that point. + ** + ** For a case-insensitive search, set variable cx to be the same as + ** c but in the other case and search the input string for either + ** c or cx. + */ + if( c<=0x80 ){ + u32 cx; + if( noCase ){ + cx = sqlite3Toupper(c); + c = sqlite3Tolower(c); + }else{ + cx = c; + } + while( (c2 = *(zString++))!=0 ){ + if( c2!=c && c2!=cx ) continue; + if( patternCompare(zPattern,zString,pInfo,esc) ) return 1; + } + }else{ + while( (c2 = Utf8Read(zString))!=0 ){ + if( c2!=c ) continue; + if( patternCompare(zPattern,zString,pInfo,esc) ) return 1; } - if( c2==0 ) return 0; - if( patternCompare(zPattern,zString,pInfo,esc) ) return 1; } return 0; - }else if( c==matchOne && !prevEscape ){ - if( sqlite3Utf8Read(&zString)==0 ){ - return 0; - } - }else if( c==matchSet ){ - u32 prior_c = 0; - assert( esc==0 ); /* This only occurs for GLOB, not LIKE */ - seen = 0; - invert = 0; - c = sqlite3Utf8Read(&zString); - if( c==0 ) return 0; - c2 = sqlite3Utf8Read(&zPattern); - if( c2=='^' ){ - invert = 1; - c2 = sqlite3Utf8Read(&zPattern); - } - if( c2==']' ){ - if( c==']' ) seen = 1; - c2 = sqlite3Utf8Read(&zPattern); - } - while( c2 && c2!=']' ){ - if( c2=='-' && zPattern[0]!=']' && zPattern[0]!=0 && prior_c>0 ){ - c2 = sqlite3Utf8Read(&zPattern); - if( c>=prior_c && c<=c2 ) seen = 1; - prior_c = 0; - }else{ - if( c==c2 ){ - seen = 1; - } - prior_c = c2; - } - c2 = sqlite3Utf8Read(&zPattern); - } - if( c2==0 || (seen ^ invert)==0 ){ - return 0; - } - }else if( esc==c && !prevEscape ){ - prevEscape = 1; - }else{ - c2 = sqlite3Utf8Read(&zString); - if( noCase ){ - GlobUpperToLower(c); - GlobUpperToLower(c2); - } - if( c!=c2 ){ - return 0; - } - prevEscape = 0; } + if( c==matchOther ){ + if( esc ){ + c = sqlite3Utf8Read(&zPattern); + if( c==0 ) return 0; + zEscaped = zPattern; + }else{ + u32 prior_c = 0; + int seen = 0; + int invert = 0; + c = sqlite3Utf8Read(&zString); + if( c==0 ) return 0; + c2 = sqlite3Utf8Read(&zPattern); + if( c2=='^' ){ + invert = 1; + c2 = sqlite3Utf8Read(&zPattern); + } + if( c2==']' ){ + if( c==']' ) seen = 1; + c2 = sqlite3Utf8Read(&zPattern); + } + while( c2 && c2!=']' ){ + if( c2=='-' && zPattern[0]!=']' && zPattern[0]!=0 && prior_c>0 ){ + c2 = sqlite3Utf8Read(&zPattern); + if( c>=prior_c && c<=c2 ) seen = 1; + prior_c = 0; + }else{ + if( c==c2 ){ + seen = 1; + } + prior_c = c2; + } + c2 = sqlite3Utf8Read(&zPattern); + } + if( c2==0 || (seen ^ invert)==0 ){ + return 0; + } + continue; + } + } + c2 = Utf8Read(zString); + if( c==c2 ) continue; + if( noCase && c<0x80 && c2<0x80 && sqlite3Tolower(c)==sqlite3Tolower(c2) ){ + continue; + } + if( c==matchOne && zPattern!=zEscaped && c2!=0 ) continue; + return 0; } return *zString==0; } @@ -91586,10 +100295,17 @@ static int patternCompare( /* ** The sqlite3_strglob() interface. */ -SQLITE_API int sqlite3_strglob(const char *zGlobPattern, const char *zString){ +SQLITE_API int SQLITE_STDCALL sqlite3_strglob(const char *zGlobPattern, const char *zString){ return patternCompare((u8*)zGlobPattern, (u8*)zString, &globInfo, 0)==0; } +/* +** The sqlite3_strlike() interface. +*/ +SQLITE_API int SQLITE_STDCALL sqlite3_strlike(const char *zPattern, const char *zStr, unsigned int esc){ + return patternCompare((u8*)zPattern, (u8*)zStr, &likeInfoNorm, esc)==0; +} + /* ** Count the number of times that the LIKE operator (or GLOB which is ** just a variation of LIKE) gets called. This is used for testing @@ -91622,6 +100338,17 @@ static void likeFunc( int nPat; sqlite3 *db = sqlite3_context_db_handle(context); +#ifdef SQLITE_LIKE_DOESNT_MATCH_BLOBS + if( sqlite3_value_type(argv[0])==SQLITE_BLOB + || sqlite3_value_type(argv[1])==SQLITE_BLOB + ){ +#ifdef SQLITE_TEST + sqlite3_like_count++; +#endif + sqlite3_result_int(context, 0); + return; + } +#endif zB = sqlite3_value_text(argv[0]); zA = sqlite3_value_text(argv[1]); @@ -91881,7 +100608,7 @@ static void charFunc( ){ unsigned char *z, *zOut; int i; - zOut = z = sqlite3_malloc( argc*4+1 ); + zOut = z = sqlite3_malloc64( argc*4+1 ); if( z==0 ){ sqlite3_result_error_nomem(context); return; @@ -91908,7 +100635,7 @@ static void charFunc( *zOut++ = 0x80 + (u8)(c & 0x3F); } \ } - sqlite3_result_text(context, (char*)z, (int)(zOut-z), sqlite3_free); + sqlite3_result_text64(context, (char*)z, zOut-z, sqlite3_free, SQLITE_UTF8); } /* @@ -91949,16 +100676,14 @@ static void zeroblobFunc( sqlite3_value **argv ){ i64 n; - sqlite3 *db = sqlite3_context_db_handle(context); + int rc; assert( argc==1 ); UNUSED_PARAMETER(argc); n = sqlite3_value_int64(argv[0]); - testcase( n==db->aLimit[SQLITE_LIMIT_LENGTH] ); - testcase( n==db->aLimit[SQLITE_LIMIT_LENGTH]+1 ); - if( n>db->aLimit[SQLITE_LIMIT_LENGTH] ){ - sqlite3_result_error_toobig(context); - }else{ - sqlite3_result_zeroblob(context, (int)n); /* IMP: R-00293-64994 */ + if( n<0 ) n = 0; + rc = sqlite3_result_zeroblob64(context, n); /* IMP: R-00293-64994 */ + if( rc ){ + sqlite3_result_error_code(context, rc); } } @@ -92029,7 +100754,7 @@ static void replaceFunc( return; } zOld = zOut; - zOut = sqlite3_realloc(zOut, (int)nOut); + zOut = sqlite3_realloc64(zOut, (int)nOut); if( zOut==0 ){ sqlite3_result_error_nomem(context); sqlite3_free(zOld); @@ -92358,6 +101083,7 @@ static void minmaxStep( sqlite3SkipAccumulatorLoad(context); } }else{ + pBest->db = sqlite3_context_db_handle(context); sqlite3VdbeMemCopy(pBest, pArg); } } @@ -92390,8 +101116,7 @@ static void groupConcatStep( if( pAccum ){ sqlite3 *db = sqlite3_context_db_handle(context); - int firstTerm = pAccum->useMalloc==0; - pAccum->useMalloc = 2; + int firstTerm = pAccum->mxAlloc==0; pAccum->mxAlloc = db->aLimit[SQLITE_LIMIT_LENGTH]; if( !firstTerm ){ if( argc==2 ){ @@ -92475,6 +101200,11 @@ SQLITE_PRIVATE void sqlite3RegisterLikeFunctions(sqlite3 *db, int caseSensitive) ** then set aWc[0] through aWc[2] to the wildcard characters and ** return TRUE. If the function is not a LIKE-style function then ** return FALSE. +** +** *pIsNocase is set to true if uppercase and lowercase are equivalent for +** the function (default for LIKE). If the function makes the distinction +** between uppercase and lowercase (as does GLOB) then *pIsNocase is set to +** false. */ SQLITE_PRIVATE int sqlite3IsLikeFunction(sqlite3 *db, Expr *pExpr, int *pIsNocase, char *aWc){ FuncDef *pDef; @@ -92505,7 +101235,7 @@ SQLITE_PRIVATE int sqlite3IsLikeFunction(sqlite3 *db, Expr *pExpr, int *pIsNocas } /* -** All all of the FuncDef structures in the aBuiltinFunc[] array above +** All of the FuncDef structures in the aBuiltinFunc[] array above ** to the global function hash table. This occurs at start-time (as ** a consequence of calling sqlite3_initialize()). ** @@ -92529,10 +101259,12 @@ SQLITE_PRIVATE void sqlite3RegisterGlobalFunctions(void){ FUNCTION(trim, 2, 3, 0, trimFunc ), FUNCTION(min, -1, 0, 1, minmaxFunc ), FUNCTION(min, 0, 0, 1, 0 ), - AGGREGATE(min, 1, 0, 1, minmaxStep, minMaxFinalize ), + AGGREGATE2(min, 1, 0, 1, minmaxStep, minMaxFinalize, + SQLITE_FUNC_MINMAX ), FUNCTION(max, -1, 1, 1, minmaxFunc ), FUNCTION(max, 0, 1, 1, 0 ), - AGGREGATE(max, 1, 1, 1, minmaxStep, minMaxFinalize ), + AGGREGATE2(max, 1, 1, 1, minmaxStep, minMaxFinalize, + SQLITE_FUNC_MINMAX ), FUNCTION2(typeof, 1, 0, 0, typeofFunc, SQLITE_FUNC_TYPEOF), FUNCTION2(length, 1, 0, 0, lengthFunc, SQLITE_FUNC_LENGTH), FUNCTION(instr, 2, 0, 0, instrFunc ), @@ -92555,15 +101287,19 @@ SQLITE_PRIVATE void sqlite3RegisterGlobalFunctions(void){ FUNCTION2(ifnull, 2, 0, 0, noopFunc, SQLITE_FUNC_COALESCE), FUNCTION2(unlikely, 1, 0, 0, noopFunc, SQLITE_FUNC_UNLIKELY), FUNCTION2(likelihood, 2, 0, 0, noopFunc, SQLITE_FUNC_UNLIKELY), + FUNCTION2(likely, 1, 0, 0, noopFunc, SQLITE_FUNC_UNLIKELY), VFUNCTION(random, 0, 0, 0, randomFunc ), VFUNCTION(randomblob, 1, 0, 0, randomBlob ), FUNCTION(nullif, 2, 0, 1, nullifFunc ), - FUNCTION(sqlite_version, 0, 0, 0, versionFunc ), - FUNCTION(sqlite_source_id, 0, 0, 0, sourceidFunc ), + DFUNCTION(sqlite_version, 0, 0, 0, versionFunc ), + DFUNCTION(sqlite_source_id, 0, 0, 0, sourceidFunc ), FUNCTION(sqlite_log, 2, 0, 0, errlogFunc ), +#if SQLITE_USER_AUTHENTICATION + FUNCTION(sqlite_crypt, 2, 0, 0, sqlite3CryptFunc ), +#endif #ifndef SQLITE_OMIT_COMPILEOPTION_DIAGS - FUNCTION(sqlite_compileoption_used,1, 0, 0, compileoptionusedFunc ), - FUNCTION(sqlite_compileoption_get, 1, 0, 0, compileoptiongetFunc ), + DFUNCTION(sqlite_compileoption_used,1, 0, 0, compileoptionusedFunc ), + DFUNCTION(sqlite_compileoption_get, 1, 0, 0, compileoptiongetFunc ), #endif /* SQLITE_OMIT_COMPILEOPTION_DIAGS */ FUNCTION(quote, 1, 0, 0, quoteFunc ), VFUNCTION(last_insert_rowid, 0, 0, 0, last_insert_rowid), @@ -92575,14 +101311,14 @@ SQLITE_PRIVATE void sqlite3RegisterGlobalFunctions(void){ FUNCTION(soundex, 1, 0, 0, soundexFunc ), #endif #ifndef SQLITE_OMIT_LOAD_EXTENSION - FUNCTION(load_extension, 1, 0, 0, loadExt ), - FUNCTION(load_extension, 2, 0, 0, loadExt ), + VFUNCTION(load_extension, 1, 0, 0, loadExt ), + VFUNCTION(load_extension, 2, 0, 0, loadExt ), #endif AGGREGATE(sum, 1, 0, 0, sumStep, sumFinalize ), AGGREGATE(total, 1, 0, 0, sumStep, totalFinalize ), AGGREGATE(avg, 1, 0, 0, sumStep, avgFinalize ), - /* AGGREGATE(count, 0, 0, 0, countStep, countFinalize ), */ - {0,SQLITE_UTF8|SQLITE_FUNC_COUNT,0,0,0,countStep,countFinalize,"count",0,0}, + AGGREGATE2(count, 0, 0, 0, countStep, countFinalize, + SQLITE_FUNC_COUNT ), AGGREGATE(count, 1, 0, 0, countStep, countFinalize ), AGGREGATE(group_concat, 1, 0, 0, groupConcatStep, groupConcatFinalize), AGGREGATE(group_concat, 2, 0, 0, groupConcatStep, groupConcatFinalize), @@ -92628,6 +101364,7 @@ SQLITE_PRIVATE void sqlite3RegisterGlobalFunctions(void){ ** This file contains code used by the compiler to add foreign key ** support to compiled SQL statements. */ +/* #include "sqliteInt.h" */ #ifndef SQLITE_OMIT_FOREIGN_KEY #ifndef SQLITE_OMIT_TRIGGER @@ -92789,7 +101526,7 @@ SQLITE_PRIVATE void sqlite3RegisterGlobalFunctions(void){ ** ** 4) No parent key columns were provided explicitly as part of the ** foreign key definition, and the PRIMARY KEY of the parent table -** consists of a a different number of columns to the child key in +** consists of a different number of columns to the child key in ** the child table. ** ** then non-zero is returned, and a "foreign key mismatch" error loaded @@ -92841,7 +101578,7 @@ SQLITE_PRIVATE int sqlite3FkLocateIndex( } for(pIdx=pParent->pIndex; pIdx; pIdx=pIdx->pNext){ - if( pIdx->nKeyCol==nCol && pIdx->onError!=OE_None ){ + if( pIdx->nKeyCol==nCol && IsUniqueIndex(pIdx) ){ /* pIdx is a UNIQUE index (or a PRIMARY KEY) and has the right number ** of columns. If each indexed column corresponds to a foreign key ** column of pFKey, then this index is a winner. */ @@ -92865,16 +101602,16 @@ SQLITE_PRIVATE int sqlite3FkLocateIndex( int i, j; for(i=0; iaiColumn[i]; /* Index of column in parent tbl */ - char *zDfltColl; /* Def. collation for column */ + const char *zDfltColl; /* Def. collation for column */ char *zIdxCol; /* Name of indexed column */ + if( iCol<0 ) break; /* No foreign keys against expression indexes */ + /* If the index uses a collation sequence that is different from ** the default collation sequence for the column, this index is ** unusable. Bail out early in this case. */ zDfltColl = pParent->aCol[iCol].zColl; - if( !zDfltColl ){ - zDfltColl = "BINARY"; - } + if( !zDfltColl ) zDfltColl = sqlite3StrBINARY; if( sqlite3StrICmp(pIdx->azColl[i], zDfltColl) ) break; zIdxCol = pParent->aCol[iCol].zName; @@ -92990,7 +101727,7 @@ static void fkLookupParent( sqlite3OpenTable(pParse, iCur, iDb, pTab, OP_OpenRead); sqlite3VdbeAddOp3(v, OP_NotExists, iCur, 0, regTemp); VdbeCoverage(v); - sqlite3VdbeAddOp2(v, OP_Goto, 0, iOk); + sqlite3VdbeGoto(v, iOk); sqlite3VdbeJumpHere(v, sqlite3VdbeCurrentAddr(v)-2); sqlite3VdbeJumpHere(v, iMustBeInt); sqlite3ReleaseTempReg(pParse, regTemp); @@ -93020,6 +101757,7 @@ static void fkLookupParent( for(i=0; iaiColumn[i]+1+regData; + assert( pIdx->aiColumn[i]>=0 ); assert( aiCol[i]!=pTab->iPKey ); if( pIdx->aiColumn[i]==pTab->iPKey ){ /* The parent key is a composite key that includes the IPK column */ @@ -93028,11 +101766,11 @@ static void fkLookupParent( sqlite3VdbeAddOp3(v, OP_Ne, iChild, iJump, iParent); VdbeCoverage(v); sqlite3VdbeChangeP5(v, SQLITE_JUMPIFNULL); } - sqlite3VdbeAddOp2(v, OP_Goto, 0, iOk); + sqlite3VdbeGoto(v, iOk); } sqlite3VdbeAddOp4(v, OP_MakeRecord, regTemp, nCol, regRec, - sqlite3IndexAffinityStr(v,pIdx), nCol); + sqlite3IndexAffinityStr(pParse->db,pIdx), nCol); sqlite3VdbeAddOp4Int(v, OP_Found, iCur, iOk, regRec, 0); VdbeCoverage(v); sqlite3ReleaseTempReg(pParse, regRec); @@ -93053,7 +101791,7 @@ static void fkLookupParent( OE_Abort, 0, P4_STATIC, P5_ConstraintFK); }else{ if( nIncr>0 && pFKey->isDeferred==0 ){ - sqlite3ParseToplevel(pParse)->mayAbort = 1; + sqlite3MayAbort(pParse); } sqlite3VdbeAddOp2(v, OP_FkCounter, pFKey->isDeferred, nIncr); } @@ -93125,6 +101863,10 @@ static Expr *exprTableColumn( ** code for an SQL UPDATE operation, this function may be called twice - ** once to "delete" the old row and once to "insert" the new row. ** +** Parameter nIncr is passed -1 when inserting a row (as this may decrease +** the number of FK violations in the db) or +1 when deleting one (as this +** may increase the number of FK constraint problems). +** ** The code generated by this function scans through the rows in the child ** table that correspond to the parent table row being deleted or inserted. ** For each child row found, one of the following actions is taken: @@ -93224,6 +101966,7 @@ static void fkScanChildren( assert( pIdx!=0 ); for(i=0; inKeyCol; i++){ i16 iCol = pIdx->aiColumn[i]; + assert( iCol>=0 ); pLeft = exprTableRegister(pParse, pTab, regData, iCol); pRight = exprTableColumn(db, pTab, pSrc->a[0].iCursor, iCol); pEq = sqlite3PExpr(pParse, TK_EQ, pLeft, pRight, 0); @@ -93241,13 +101984,9 @@ static void fkScanChildren( sqlite3ResolveExprNames(&sNameContext, pWhere); /* Create VDBE to loop through the entries in pSrc that match the WHERE - ** clause. If the constraint is not deferred, throw an exception for - ** each row found. Otherwise, for deferred constraints, increment the - ** deferred constraint counter by nIncr for each row selected. */ + ** clause. For each row found, increment either the deferred or immediate + ** foreign key constraint counter. */ pWInfo = sqlite3WhereBegin(pParse, pSrc, pWhere, 0, 0, 0, 0); - if( nIncr>0 && pFKey->isDeferred==0 ){ - sqlite3ParseToplevel(pParse)->mayAbort = 1; - } sqlite3VdbeAddOp2(v, OP_FkCounter, pFKey->isDeferred, nIncr); if( pWInfo ){ sqlite3WhereEnd(pWInfo); @@ -93275,8 +102014,7 @@ static void fkScanChildren( ** table). */ SQLITE_PRIVATE FKey *sqlite3FkReferences(Table *pTab){ - int nName = sqlite3Strlen30(pTab->zName); - return (FKey *)sqlite3HashFind(&pTab->pSchema->fkeyHash, pTab->zName, nName); + return (FKey *)sqlite3HashFind(&pTab->pSchema->fkeyHash, pTab->zName); } /* @@ -93427,6 +102165,24 @@ static int fkParentIsModified( return 0; } +/* +** Return true if the parser passed as the first argument is being +** used to code a trigger that is really a "SET NULL" action belonging +** to trigger pFKey. +*/ +static int isSetNullAction(Parse *pParse, FKey *pFKey){ + Parse *pTop = sqlite3ParseToplevel(pParse); + if( pTop->pTriggerPrg ){ + Trigger *p = pTop->pTriggerPrg->pTrigger; + if( (p==pFKey->apTrigger[0] && pFKey->aAction[0]==OE_SetNull) + || (p==pFKey->apTrigger[1] && pFKey->aAction[1]==OE_SetNull) + ){ + return 1; + } + } + return 0; +} + /* ** This function is called when inserting, deleting or updating a row of ** table pTab to generate VDBE code to perform foreign key constraint @@ -93479,7 +102235,7 @@ SQLITE_PRIVATE void sqlite3FkCheck( int *aiCol; int iCol; int i; - int isIgnore = 0; + int bIgnore = 0; if( aChange && sqlite3_stricmp(pTab->zName, pFKey->zTo)!=0 @@ -93530,6 +102286,7 @@ SQLITE_PRIVATE void sqlite3FkCheck( if( aiCol[i]==pTab->iPKey ){ aiCol[i] = -1; } + assert( pIdx==0 || pIdx->aiColumn[i]>=0 ); #ifndef SQLITE_OMIT_AUTHORIZATION /* Request permission to read the parent key columns. If the ** authorization callback returns SQLITE_IGNORE, behave as if any @@ -93538,7 +102295,7 @@ SQLITE_PRIVATE void sqlite3FkCheck( int rcauth; char *zCol = pTo->aCol[pIdx ? pIdx->aiColumn[i] : pTo->iPKey].zName; rcauth = sqlite3AuthReadCol(pParse, pTo->zName, zCol, iDb); - isIgnore = (rcauth==SQLITE_IGNORE); + bIgnore = (rcauth==SQLITE_IGNORE); } #endif } @@ -93553,12 +102310,18 @@ SQLITE_PRIVATE void sqlite3FkCheck( /* A row is being removed from the child table. Search for the parent. ** If the parent does not exist, removing the child row resolves an ** outstanding foreign key constraint violation. */ - fkLookupParent(pParse, iDb, pTo, pIdx, pFKey, aiCol, regOld, -1,isIgnore); + fkLookupParent(pParse, iDb, pTo, pIdx, pFKey, aiCol, regOld, -1, bIgnore); } - if( regNew!=0 ){ + if( regNew!=0 && !isSetNullAction(pParse, pFKey) ){ /* A row is being added to the child table. If a parent row cannot - ** be found, adding the child row has violated the FK constraint. */ - fkLookupParent(pParse, iDb, pTo, pIdx, pFKey, aiCol, regNew, +1,isIgnore); + ** be found, adding the child row has violated the FK constraint. + ** + ** If this operation is being performed as part of a trigger program + ** that is actually a "SET NULL" action belonging to this very + ** foreign key, then omit this scan altogether. As all child key + ** values are guaranteed to be NULL, it is not possible for adding + ** this row to cause an FK violation. */ + fkLookupParent(pParse, iDb, pTo, pIdx, pFKey, aiCol, regNew, +1, bIgnore); } sqlite3DbFree(db, aiFree); @@ -93579,8 +102342,8 @@ SQLITE_PRIVATE void sqlite3FkCheck( && !pParse->pToplevel && !pParse->isMultiWrite ){ assert( regOld==0 && regNew!=0 ); - /* Inserting a single row into a parent table cannot cause an immediate - ** foreign key violation. So do nothing in this case. */ + /* Inserting a single row into a parent table cannot cause (or fix) + ** an immediate foreign key violation. So do nothing in this case. */ continue; } @@ -93604,13 +102367,28 @@ SQLITE_PRIVATE void sqlite3FkCheck( fkScanChildren(pParse, pSrc, pTab, pIdx, pFKey, aiCol, regNew, -1); } if( regOld!=0 ){ - /* If there is a RESTRICT action configured for the current operation - ** on the parent table of this FK, then throw an exception - ** immediately if the FK constraint is violated, even if this is a - ** deferred trigger. That's what RESTRICT means. To defer checking - ** the constraint, the FK should specify NO ACTION (represented - ** using OE_None). NO ACTION is the default. */ + int eAction = pFKey->aAction[aChange!=0]; fkScanChildren(pParse, pSrc, pTab, pIdx, pFKey, aiCol, regOld, 1); + /* If this is a deferred FK constraint, or a CASCADE or SET NULL + ** action applies, then any foreign key violations caused by + ** removing the parent key will be rectified by the action trigger. + ** So do not set the "may-abort" flag in this case. + ** + ** Note 1: If the FK is declared "ON UPDATE CASCADE", then the + ** may-abort flag will eventually be set on this statement anyway + ** (when this function is called as part of processing the UPDATE + ** within the action trigger). + ** + ** Note 2: At first glance it may seem like SQLite could simply omit + ** all OP_FkCounter related scans when either CASCADE or SET NULL + ** applies. The trouble starts if the CASCADE or SET NULL action + ** trigger causes other triggers or action rules attached to the + ** child table to fire. In these cases the fk constraint counters + ** might be set incorrectly if any OP_FkCounter related scans are + ** omitted. */ + if( !pFKey->isDeferred && eAction!=OE_Cascade && eAction!=OE_SetNull ){ + sqlite3MayAbort(pParse); + } } pItem->zName = 0; sqlite3SrcListDelete(db, pSrc); @@ -93640,7 +102418,10 @@ SQLITE_PRIVATE u32 sqlite3FkOldmask( Index *pIdx = 0; sqlite3FkLocateIndex(pParse, pTab, p, &pIdx, 0); if( pIdx ){ - for(i=0; inKeyCol; i++) mask |= COLUMN_MASK(pIdx->aiColumn[i]); + for(i=0; inKeyCol; i++){ + assert( pIdx->aiColumn[i]>=0 ); + mask |= COLUMN_MASK(pIdx->aiColumn[i]); + } } } } @@ -93762,7 +102543,9 @@ static Trigger *fkActionTrigger( iFromCol = aiCol ? aiCol[i] : pFKey->aCol[0].iFrom; assert( iFromCol>=0 ); - tToCol.z = pIdx ? pTab->aCol[pIdx->aiColumn[i]].zName : "oid"; + assert( pIdx!=0 || (pTab->iPKey>=0 && pTab->iPKeynCol) ); + assert( pIdx==0 || pIdx->aiColumn[i]>=0 ); + tToCol.z = pTab->aCol[pIdx ? pIdx->aiColumn[i] : pTab->iPKey].zName; tFromCol.z = pFKey->pFrom->aCol[iFromCol].zName; tToCol.n = sqlite3Strlen30(tToCol.z); @@ -93774,10 +102557,10 @@ static Trigger *fkActionTrigger( ** parent table are used for the comparison. */ pEq = sqlite3PExpr(pParse, TK_EQ, sqlite3PExpr(pParse, TK_DOT, - sqlite3PExpr(pParse, TK_ID, 0, 0, &tOld), - sqlite3PExpr(pParse, TK_ID, 0, 0, &tToCol) + sqlite3ExprAlloc(db, TK_ID, &tOld, 0), + sqlite3ExprAlloc(db, TK_ID, &tToCol, 0) , 0), - sqlite3PExpr(pParse, TK_ID, 0, 0, &tFromCol) + sqlite3ExprAlloc(db, TK_ID, &tFromCol, 0) , 0); pWhere = sqlite3ExprAnd(db, pWhere, pEq); @@ -93789,12 +102572,12 @@ static Trigger *fkActionTrigger( if( pChanges ){ pEq = sqlite3PExpr(pParse, TK_IS, sqlite3PExpr(pParse, TK_DOT, - sqlite3PExpr(pParse, TK_ID, 0, 0, &tOld), - sqlite3PExpr(pParse, TK_ID, 0, 0, &tToCol), + sqlite3ExprAlloc(db, TK_ID, &tOld, 0), + sqlite3ExprAlloc(db, TK_ID, &tToCol, 0), 0), sqlite3PExpr(pParse, TK_DOT, - sqlite3PExpr(pParse, TK_ID, 0, 0, &tNew), - sqlite3PExpr(pParse, TK_ID, 0, 0, &tToCol), + sqlite3ExprAlloc(db, TK_ID, &tNew, 0), + sqlite3ExprAlloc(db, TK_ID, &tToCol, 0), 0), 0); pWhen = sqlite3ExprAnd(db, pWhen, pEq); @@ -93804,8 +102587,8 @@ static Trigger *fkActionTrigger( Expr *pNew; if( action==OE_Cascade ){ pNew = sqlite3PExpr(pParse, TK_DOT, - sqlite3PExpr(pParse, TK_ID, 0, 0, &tNew), - sqlite3PExpr(pParse, TK_ID, 0, 0, &tToCol) + sqlite3ExprAlloc(db, TK_ID, &tNew, 0), + sqlite3ExprAlloc(db, TK_ID, &tToCol, 0) , 0); }else if( action==OE_SetDflt ){ Expr *pDflt = pFKey->pFrom->aCol[iFromCol].pDflt; @@ -93852,13 +102635,12 @@ static Trigger *fkActionTrigger( pTrigger = (Trigger *)sqlite3DbMallocZero(db, sizeof(Trigger) + /* struct Trigger */ sizeof(TriggerStep) + /* Single step in trigger program */ - nFrom + 1 /* Space for pStep->target.z */ + nFrom + 1 /* Space for pStep->zTarget */ ); if( pTrigger ){ pStep = pTrigger->step_list = (TriggerStep *)&pTrigger[1]; - pStep->target.z = (char *)&pStep[1]; - pStep->target.n = nFrom; - memcpy((char *)pStep->target.z, zFrom, nFrom); + pStep->zTarget = (char *)&pStep[1]; + memcpy((char *)pStep->zTarget, zFrom, nFrom); pStep->pWhere = sqlite3ExprDup(db, pWhere, EXPRDUP_REDUCE); pStep->pExprList = sqlite3ExprListDup(db, pList, EXPRDUP_REDUCE); @@ -93954,7 +102736,7 @@ SQLITE_PRIVATE void sqlite3FkDelete(sqlite3 *db, Table *pTab){ }else{ void *p = (void *)pFKey->pNextTo; const char *z = (p ? pFKey->pNextTo->zTo : pFKey->zTo); - sqlite3HashInsert(&pTab->pSchema->fkeyHash, z, sqlite3Strlen30(z), p); + sqlite3HashInsert(&pTab->pSchema->fkeyHash, z, p); } if( pFKey->pNextTo ){ pFKey->pNextTo->pPrevTo = pFKey->pPrevTo; @@ -93994,6 +102776,7 @@ SQLITE_PRIVATE void sqlite3FkDelete(sqlite3 *db, Table *pTab){ ** This file contains C code routines that are called by the parser ** to handle INSERT statements in SQLite. */ +/* #include "sqliteInt.h" */ /* ** Generate code that will @@ -94023,7 +102806,7 @@ SQLITE_PRIVATE void sqlite3OpenTable( }else{ Index *pPk = sqlite3PrimaryKeyIndex(pTab); assert( pPk!=0 ); - assert( pPk->tnum=pTab->tnum ); + assert( pPk->tnum==pTab->tnum ); sqlite3VdbeAddOp3(v, opcode, iCur, pPk->tnum, iDb); sqlite3VdbeSetP4KeyInfo(pParse, pPk); VdbeComment((v, "%s", pTab->zName)); @@ -94037,20 +102820,20 @@ SQLITE_PRIVATE void sqlite3OpenTable( ** ** Character Column affinity ** ------------------------------ -** 'a' TEXT -** 'b' NONE -** 'c' NUMERIC -** 'd' INTEGER -** 'e' REAL +** 'A' BLOB +** 'B' TEXT +** 'C' NUMERIC +** 'D' INTEGER +** 'F' REAL ** -** An extra 'd' is appended to the end of the string to cover the +** An extra 'D' is appended to the end of the string to cover the ** rowid that appears as the last column in every index. ** ** Memory for the buffer containing the column index affinity string ** is managed along with the rest of the Index structure. It will be ** released when sqlite3DeleteIndex() is called. */ -SQLITE_PRIVATE const char *sqlite3IndexAffinityStr(Vdbe *v, Index *pIdx){ +SQLITE_PRIVATE const char *sqlite3IndexAffinityStr(sqlite3 *db, Index *pIdx){ if( !pIdx->zColAff ){ /* The first time a column affinity string for a particular index is ** required, it is allocated and populated here. It is then stored as @@ -94062,7 +102845,6 @@ SQLITE_PRIVATE const char *sqlite3IndexAffinityStr(Vdbe *v, Index *pIdx){ */ int n; Table *pTab = pIdx->pTable; - sqlite3 *db = sqlite3VdbeDb(v); pIdx->zColAff = (char *)sqlite3DbMallocRaw(0, pIdx->nColumn+1); if( !pIdx->zColAff ){ db->mallocFailed = 1; @@ -94070,7 +102852,18 @@ SQLITE_PRIVATE const char *sqlite3IndexAffinityStr(Vdbe *v, Index *pIdx){ } for(n=0; nnColumn; n++){ i16 x = pIdx->aiColumn[n]; - pIdx->zColAff[n] = x<0 ? SQLITE_AFF_INTEGER : pTab->aCol[x].affinity; + if( x>=0 ){ + pIdx->zColAff[n] = pTab->aCol[x].affinity; + }else if( x==XN_ROWID ){ + pIdx->zColAff[n] = SQLITE_AFF_INTEGER; + }else{ + char aff; + assert( x==XN_EXPR ); + assert( pIdx->aColExpr!=0 ); + aff = sqlite3ExprAffinity(pIdx->aColExpr->a[n].pExpr); + if( aff==0 ) aff = SQLITE_AFF_BLOB; + pIdx->zColAff[n] = aff; + } } pIdx->zColAff[n] = 0; } @@ -94080,9 +102873,9 @@ SQLITE_PRIVATE const char *sqlite3IndexAffinityStr(Vdbe *v, Index *pIdx){ /* ** Compute the affinity string for table pTab, if it has not already been -** computed. As an optimization, omit trailing SQLITE_AFF_NONE affinities. +** computed. As an optimization, omit trailing SQLITE_AFF_BLOB affinities. ** -** If the affinity exists (if it is no entirely SQLITE_AFF_NONE values) and +** If the affinity exists (if it is no entirely SQLITE_AFF_BLOB values) and ** if iReg>0 then code an OP_Affinity opcode that will set the affinities ** for register iReg and following. Or if affinities exists and iReg==0, ** then just set the P4 operand of the previous opcode (which should be @@ -94092,11 +102885,11 @@ SQLITE_PRIVATE const char *sqlite3IndexAffinityStr(Vdbe *v, Index *pIdx){ ** ** Character Column affinity ** ------------------------------ -** 'a' TEXT -** 'b' NONE -** 'c' NUMERIC -** 'd' INTEGER -** 'e' REAL +** 'A' BLOB +** 'B' TEXT +** 'C' NUMERIC +** 'D' INTEGER +** 'E' REAL */ SQLITE_PRIVATE void sqlite3TableAffinity(Vdbe *v, Table *pTab, int iReg){ int i; @@ -94114,7 +102907,7 @@ SQLITE_PRIVATE void sqlite3TableAffinity(Vdbe *v, Table *pTab, int iReg){ } do{ zColAff[i--] = 0; - }while( i>=0 && zColAff[i]==SQLITE_AFF_NONE ); + }while( i>=0 && zColAff[i]==SQLITE_AFF_BLOB ); pTab->zColAff = zColAff; } i = sqlite3Strlen30(zColAff); @@ -94231,7 +103024,7 @@ SQLITE_PRIVATE void sqlite3AutoincrementBegin(Parse *pParse){ /* This routine is never called during trigger-generation. It is ** only called from the top-level */ assert( pParse->pTriggerTab==0 ); - assert( pParse==sqlite3ParseToplevel(pParse) ); + assert( sqlite3IsToplevel(pParse) ); assert( v ); /* We failed long ago if this is not so */ for(p = pParse->pAinc; p; p = p->pNext){ @@ -94241,14 +103034,14 @@ SQLITE_PRIVATE void sqlite3AutoincrementBegin(Parse *pParse){ sqlite3OpenTable(pParse, 0, p->iDb, pDb->pSchema->pSeqTab, OP_OpenRead); sqlite3VdbeAddOp3(v, OP_Null, 0, memId, memId+1); addr = sqlite3VdbeCurrentAddr(v); - sqlite3VdbeAddOp4(v, OP_String8, 0, memId-1, 0, p->pTab->zName, 0); + sqlite3VdbeLoadString(v, memId-1, p->pTab->zName); sqlite3VdbeAddOp2(v, OP_Rewind, 0, addr+9); VdbeCoverage(v); sqlite3VdbeAddOp3(v, OP_Column, 0, 0, memId); sqlite3VdbeAddOp3(v, OP_Ne, memId-1, addr+7, memId); VdbeCoverage(v); sqlite3VdbeChangeP5(v, SQLITE_JUMPIFNULL); sqlite3VdbeAddOp2(v, OP_Rowid, 0, memId+1); sqlite3VdbeAddOp3(v, OP_Column, 0, 1, memId); - sqlite3VdbeAddOp2(v, OP_Goto, 0, addr+9); + sqlite3VdbeGoto(v, addr+9); sqlite3VdbeAddOp2(v, OP_Next, 0, addr+2); VdbeCoverage(v); sqlite3VdbeAddOp2(v, OP_Integer, 0, memId); sqlite3VdbeAddOp0(v, OP_Close); @@ -94284,16 +103077,16 @@ SQLITE_PRIVATE void sqlite3AutoincrementEnd(Parse *pParse){ assert( v ); for(p = pParse->pAinc; p; p = p->pNext){ Db *pDb = &db->aDb[p->iDb]; - int j1; + int addr1; int iRec; int memId = p->regCtr; iRec = sqlite3GetTempReg(pParse); assert( sqlite3SchemaMutexHeld(db, 0, pDb->pSchema) ); sqlite3OpenTable(pParse, 0, p->iDb, pDb->pSchema->pSeqTab, OP_OpenWrite); - j1 = sqlite3VdbeAddOp1(v, OP_NotNull, memId+1); VdbeCoverage(v); + addr1 = sqlite3VdbeAddOp1(v, OP_NotNull, memId+1); VdbeCoverage(v); sqlite3VdbeAddOp2(v, OP_NewRowid, 0, memId+1); - sqlite3VdbeJumpHere(v, j1); + sqlite3VdbeJumpHere(v, addr1); sqlite3VdbeAddOp3(v, OP_MakeRecord, memId-1, 2, iRec); sqlite3VdbeAddOp3(v, OP_Insert, 0, iRec, memId+1); sqlite3VdbeChangeP5(v, OPFLAG_APPEND); @@ -94323,20 +103116,23 @@ static int xferOptimization( /* ** This routine is called to handle SQL of the following forms: ** -** insert into TABLE (IDLIST) values(EXPRLIST) +** insert into TABLE (IDLIST) values(EXPRLIST),(EXPRLIST),... ** insert into TABLE (IDLIST) select +** insert into TABLE (IDLIST) default values ** ** The IDLIST following the table name is always optional. If omitted, -** then a list of all columns for the table is substituted. The IDLIST -** appears in the pColumn parameter. pColumn is NULL if IDLIST is omitted. +** then a list of all (non-hidden) columns for the table is substituted. +** The IDLIST appears in the pColumn parameter. pColumn is NULL if IDLIST +** is omitted. ** -** The pList parameter holds EXPRLIST in the first form of the INSERT -** statement above, and pSelect is NULL. For the second form, pList is -** NULL and pSelect is a pointer to the select statement used to generate -** data for the insert. +** For the pSelect parameter holds the values to be inserted for the +** first two forms shown above. A VALUES clause is really just short-hand +** for a SELECT statement that omits the FROM clause and everything else +** that follows. If the pSelect parameter is NULL, that means that the +** DEFAULT VALUES form of the INSERT statement is intended. ** ** The code generated follows one of four templates. For a simple -** insert with data coming from a VALUES clause, the code executes +** insert with data coming from a single-row VALUES clause, the code executes ** once straight down through. Pseudo-code follows (we call this ** the "1st template"): ** @@ -94391,7 +103187,7 @@ static int xferOptimization( ** The 4th template is used if the insert statement takes its ** values from a SELECT but the data is being inserted into a table ** that is also read as part of the SELECT. In the third form, -** we have to use a intermediate table to store the results of +** we have to use an intermediate table to store the results of ** the select. The template is like this: ** ** X <- A @@ -94443,7 +103239,7 @@ SQLITE_PRIVATE void sqlite3Insert( u8 useTempTable = 0; /* Store SELECT results in intermediate table */ u8 appendFlag = 0; /* True if the insert is likely to be an append */ u8 withoutRowid; /* 0 for normal table. 1 for WITHOUT ROWID table */ - u8 bIdListInOrder = 1; /* True if IDLIST is in table order */ + u8 bIdListInOrder; /* True if IDLIST is in table order */ ExprList *pList = 0; /* List of VALUES() to be inserted */ /* Register allocations */ @@ -94468,8 +103264,8 @@ SQLITE_PRIVATE void sqlite3Insert( } /* If the Select object is really just a simple VALUES() list with a - ** single row values (the common case) then keep that one row of values - ** and go ahead and discard the Select object + ** single row (the common case) then keep that one row of values + ** and discard the other (unused) parts of the pSelect object */ if( pSelect && (pSelect->selFlags & SF_Values)!=0 && pSelect->pPrior==0 ){ pList = pSelect->pEList; @@ -94556,7 +103352,7 @@ SQLITE_PRIVATE void sqlite3Insert( regAutoinc = autoIncBegin(pParse, iDb, pTab); /* Allocate registers for holding the rowid of the new row, - ** the content of the new row, and the assemblied row record. + ** the content of the new row, and the assembled row record. */ regRowid = regIns = pParse->nMem+1; pParse->nMem += pTab->nCol + 1; @@ -94577,6 +103373,7 @@ SQLITE_PRIVATE void sqlite3Insert( ** is appears in the original table. (The index of the INTEGER ** PRIMARY KEY in the original table is pTab->iPKey.) */ + bIdListInOrder = (pTab->tabFlags & TF_OOOHidden)==0; if( pColumn ){ for(i=0; inId; i++){ pColumn->a[i].idx = -1; @@ -94612,7 +103409,8 @@ SQLITE_PRIVATE void sqlite3Insert( ** co-routine is the common header to the 3rd and 4th templates. */ if( pSelect ){ - /* Data is coming from a SELECT. Generate a co-routine to run the SELECT */ + /* Data is coming from a SELECT or from a multi-row VALUES clause. + ** Generate a co-routine to run the SELECT. */ int regYield; /* Register holding co-routine entry-point */ int addrTop; /* Top of the co-routine */ int rc; /* Result code */ @@ -94625,8 +103423,7 @@ SQLITE_PRIVATE void sqlite3Insert( dest.nSdst = pTab->nCol; rc = sqlite3Select(pParse, pSelect, &dest); regFromSelect = dest.iSdst; - assert( pParse->nErr==0 || rc ); - if( rc || db->mallocFailed ) goto insert_cleanup; + if( rc || db->mallocFailed || pParse->nErr ) goto insert_cleanup; sqlite3VdbeAddOp1(v, OP_EndCoroutine, regYield); sqlite3VdbeJumpHere(v, addrTop - 1); /* label B: */ assert( pSelect->pEList ); @@ -94668,25 +103465,27 @@ SQLITE_PRIVATE void sqlite3Insert( sqlite3VdbeAddOp3(v, OP_MakeRecord, regFromSelect, nColumn, regRec); sqlite3VdbeAddOp2(v, OP_NewRowid, srcTab, regTempRowid); sqlite3VdbeAddOp3(v, OP_Insert, srcTab, regRec, regTempRowid); - sqlite3VdbeAddOp2(v, OP_Goto, 0, addrL); + sqlite3VdbeGoto(v, addrL); sqlite3VdbeJumpHere(v, addrL); sqlite3ReleaseTempReg(pParse, regRec); sqlite3ReleaseTempReg(pParse, regTempRowid); } }else{ - /* This is the case if the data for the INSERT is coming from a VALUES - ** clause + /* This is the case if the data for the INSERT is coming from a + ** single-row VALUES clause */ NameContext sNC; memset(&sNC, 0, sizeof(sNC)); sNC.pParse = pParse; srcTab = -1; assert( useTempTable==0 ); - nColumn = pList ? pList->nExpr : 0; - for(i=0; ia[i].pExpr) ){ + if( pList ){ + nColumn = pList->nExpr; + if( sqlite3ResolveExprListNames(&sNC, pList) ){ goto insert_cleanup; } + }else{ + nColumn = 0; } } @@ -94701,10 +103500,8 @@ SQLITE_PRIVATE void sqlite3Insert( /* Make sure the number of columns in the source data matches the number ** of columns to be inserted into the table. */ - if( IsVirtual(pTab) ){ - for(i=0; inCol; i++){ - nHidden += (IsHiddenColumn(&pTab->aCol[i]) ? 1 : 0); - } + for(i=0; inCol; i++){ + nHidden += (IsHiddenColumn(&pTab->aCol[i]) ? 1 : 0); } if( pColumn==0 && nColumn && nColumn!=(pTab->nCol-nHidden) ){ sqlite3ErrorMsg(pParse, @@ -94727,7 +103524,7 @@ SQLITE_PRIVATE void sqlite3Insert( /* If this is not a view, open the table and and all indices */ if( !isView ){ int nIdx; - nIdx = sqlite3OpenTableAndIndices(pParse, pTab, OP_OpenWrite, -1, 0, + nIdx = sqlite3OpenTableAndIndices(pParse, pTab, OP_OpenWrite, 0, -1, 0, &iDataCur, &iIdxCur); aRegIdx = sqlite3DbMallocRaw(db, sizeof(int)*(nIdx+1)); if( aRegIdx==0 ){ @@ -94779,7 +103576,7 @@ SQLITE_PRIVATE void sqlite3Insert( if( ipkColumn<0 ){ sqlite3VdbeAddOp2(v, OP_Integer, -1, regCols); }else{ - int j1; + int addr1; assert( !withoutRowid ); if( useTempTable ){ sqlite3VdbeAddOp3(v, OP_Column, srcTab, ipkColumn, regCols); @@ -94787,9 +103584,9 @@ SQLITE_PRIVATE void sqlite3Insert( assert( pSelect==0 ); /* Otherwise useTempTable is true */ sqlite3ExprCode(pParse, pList->a[ipkColumn].pExpr, regCols); } - j1 = sqlite3VdbeAddOp1(v, OP_NotNull, regCols); VdbeCoverage(v); + addr1 = sqlite3VdbeAddOp1(v, OP_NotNull, regCols); VdbeCoverage(v); sqlite3VdbeAddOp2(v, OP_Integer, -1, regCols); - sqlite3VdbeJumpHere(v, j1); + sqlite3VdbeJumpHere(v, addr1); sqlite3VdbeAddOp1(v, OP_MustBeInt, regCols); VdbeCoverage(v); } @@ -94800,15 +103597,14 @@ SQLITE_PRIVATE void sqlite3Insert( /* Create the new column data */ - for(i=0; inCol; i++){ - if( pColumn==0 ){ - j = i; - }else{ + for(i=j=0; inCol; i++){ + if( pColumn ){ for(j=0; jnId; j++){ if( pColumn->a[j].idx==i ) break; } } - if( (!useTempTable && !pList) || (pColumn && j>=pColumn->nId) ){ + if( (!useTempTable && !pList) || (pColumn && j>=pColumn->nId) + || (pColumn==0 && IsOrdinaryHiddenColumn(&pTab->aCol[i])) ){ sqlite3ExprCode(pParse, pTab->aCol[i].pDflt, regCols+i+1); }else if( useTempTable ){ sqlite3VdbeAddOp3(v, OP_Column, srcTab, j, regCols+i+1); @@ -94816,6 +103612,7 @@ SQLITE_PRIVATE void sqlite3Insert( assert( pSelect==0 ); /* Otherwise useTempTable is true */ sqlite3ExprCodeAndCache(pParse, pList->a[j].pExpr, regCols+i+1); } + if( pColumn==0 && !IsOrdinaryHiddenColumn(&pTab->aCol[i]) ) j++; } /* If this is an INSERT on a view with an INSTEAD OF INSERT trigger, @@ -94863,14 +103660,14 @@ SQLITE_PRIVATE void sqlite3Insert( ** to generate a unique primary key value. */ if( !appendFlag ){ - int j1; + int addr1; if( !IsVirtual(pTab) ){ - j1 = sqlite3VdbeAddOp1(v, OP_NotNull, regRowid); VdbeCoverage(v); + addr1 = sqlite3VdbeAddOp1(v, OP_NotNull, regRowid); VdbeCoverage(v); sqlite3VdbeAddOp3(v, OP_NewRowid, iDataCur, regRowid, regAutoinc); - sqlite3VdbeJumpHere(v, j1); + sqlite3VdbeJumpHere(v, addr1); }else{ - j1 = sqlite3VdbeCurrentAddr(v); - sqlite3VdbeAddOp2(v, OP_IsNull, regRowid, j1+2); VdbeCoverage(v); + addr1 = sqlite3VdbeCurrentAddr(v); + sqlite3VdbeAddOp2(v, OP_IsNull, regRowid, addr1+2); VdbeCoverage(v); } sqlite3VdbeAddOp1(v, OP_MustBeInt, regRowid); VdbeCoverage(v); } @@ -94899,7 +103696,6 @@ SQLITE_PRIVATE void sqlite3Insert( } if( pColumn==0 ){ if( IsHiddenColumn(&pTab->aCol[i]) ){ - assert( IsVirtual(pTab) ); j = -1; nHidden++; }else{ @@ -94967,7 +103763,7 @@ SQLITE_PRIVATE void sqlite3Insert( sqlite3VdbeJumpHere(v, addrInsTop); sqlite3VdbeAddOp1(v, OP_Close, srcTab); }else if( pSelect ){ - sqlite3VdbeAddOp2(v, OP_Goto, 0, addrCont); + sqlite3VdbeGoto(v, addrCont); sqlite3VdbeJumpHere(v, addrInsTop); } @@ -95008,7 +103804,7 @@ insert_cleanup: } /* Make sure "isView" and other macros defined above are undefined. Otherwise -** thely may interfere with compilation of other functions in this file +** they may interfere with compilation of other functions in this file ** (or in another file, if this file becomes part of the amalgamation). */ #ifdef isView #undef isView @@ -95124,7 +103920,7 @@ SQLITE_PRIVATE void sqlite3GenerateConstraintChecks( int ix; /* Index loop counter */ int nCol; /* Number of columns */ int onError; /* Conflict resolution strategy */ - int j1; /* Addresss of jump instruction */ + int addr1; /* Address of jump instruction */ int seenReplace = 0; /* True if REPLACE is used to resolve INT PK conflict */ int nPkField; /* Number of fields in PRIMARY KEY. 1 for ROWID tables */ int ipkTop = 0; /* Top of the rowid change constraint check */ @@ -95195,9 +103991,10 @@ SQLITE_PRIVATE void sqlite3GenerateConstraintChecks( } default: { assert( onError==OE_Replace ); - j1 = sqlite3VdbeAddOp1(v, OP_NotNull, regNewData+1+i); VdbeCoverage(v); + addr1 = sqlite3VdbeAddOp1(v, OP_NotNull, regNewData+1+i); + VdbeCoverage(v); sqlite3ExprCode(pParse, pTab->aCol[i].pDflt, regNewData+1+i); - sqlite3VdbeJumpHere(v, j1); + sqlite3VdbeJumpHere(v, addr1); break; } } @@ -95214,7 +104011,7 @@ SQLITE_PRIVATE void sqlite3GenerateConstraintChecks( int allOk = sqlite3VdbeMakeLabel(v); sqlite3ExprIfTrue(pParse, pCheck->a[i].pExpr, allOk, SQLITE_JUMPIFNULL); if( onError==OE_Ignore ){ - sqlite3VdbeAddOp2(v, OP_Goto, 0, ignoreDest); + sqlite3VdbeGoto(v, ignoreDest); }else{ char *zName = pCheck->a[i].zName; if( zName==0 ) zName = pTab->zName; @@ -95312,17 +104109,20 @@ SQLITE_PRIVATE void sqlite3GenerateConstraintChecks( if( pTrigger || sqlite3FkRequired(pParse, pTab, 0, 0) ){ sqlite3MultiWrite(pParse); sqlite3GenerateRowDelete(pParse, pTab, pTrigger, iDataCur, iIdxCur, - regNewData, 1, 0, OE_Replace, 1); - }else if( pTab->pIndex ){ - sqlite3MultiWrite(pParse); - sqlite3GenerateRowIndexDelete(pParse, pTab, iDataCur, iIdxCur, 0); + regNewData, 1, 0, OE_Replace, + ONEPASS_SINGLE, -1); + }else{ + if( pTab->pIndex ){ + sqlite3MultiWrite(pParse); + sqlite3GenerateRowIndexDelete(pParse, pTab, iDataCur, iIdxCur,0,-1); + } } seenReplace = 1; break; } case OE_Ignore: { /*assert( seenReplace==0 );*/ - sqlite3VdbeAddOp2(v, OP_Goto, 0, ignoreDest); + sqlite3VdbeGoto(v, ignoreDest); break; } } @@ -95358,8 +104158,8 @@ SQLITE_PRIVATE void sqlite3GenerateConstraintChecks( if( pIdx->pPartIdxWhere ){ sqlite3VdbeAddOp2(v, OP_Null, 0, aRegIdx[ix]); pParse->ckBase = regNewData+1; - sqlite3ExprIfFalse(pParse, pIdx->pPartIdxWhere, addrUniqueOk, - SQLITE_JUMPIFNULL); + sqlite3ExprIfFalseDup(pParse, pIdx->pPartIdxWhere, addrUniqueOk, + SQLITE_JUMPIFNULL); pParse->ckBase = 0; } @@ -95370,15 +104170,22 @@ SQLITE_PRIVATE void sqlite3GenerateConstraintChecks( for(i=0; inColumn; i++){ int iField = pIdx->aiColumn[i]; int x; - if( iField<0 || iField==pTab->iPKey ){ - if( regRowid==regIdx+i ) continue; /* ROWID already in regIdx+i */ - x = regNewData; - regRowid = pIdx->pPartIdxWhere ? -1 : regIdx+i; + if( iField==XN_EXPR ){ + pParse->ckBase = regNewData+1; + sqlite3ExprCodeCopy(pParse, pIdx->aColExpr->a[i].pExpr, regIdx+i); + pParse->ckBase = 0; + VdbeComment((v, "%s column %d", pIdx->zName, i)); }else{ - x = iField + regNewData + 1; + if( iField==XN_ROWID || iField==pTab->iPKey ){ + if( regRowid==regIdx+i ) continue; /* ROWID already in regIdx+i */ + x = regNewData; + regRowid = pIdx->pPartIdxWhere ? -1 : regIdx+i; + }else{ + x = iField + regNewData + 1; + } + sqlite3VdbeAddOp2(v, iField<0 ? OP_IntCopy : OP_SCopy, x, regIdx+i); + VdbeComment((v, "%s", iField<0 ? "rowid" : pTab->aCol[iField].zName)); } - sqlite3VdbeAddOp2(v, OP_SCopy, x, regIdx+i); - VdbeComment((v, "%s", iField<0 ? "rowid" : pTab->aCol[iField].zName)); } sqlite3VdbeAddOp3(v, OP_MakeRecord, regIdx, pIdx->nColumn, aRegIdx[ix]); VdbeComment((v, "for %s", pIdx->zName)); @@ -95428,6 +104235,7 @@ SQLITE_PRIVATE void sqlite3GenerateConstraintChecks( ** store it in registers regR..regR+nPk-1 */ if( pIdx!=pPk ){ for(i=0; inKeyCol; i++){ + assert( pPk->aiColumn[i]>=0 ); x = sqlite3ColumnOfIndex(pIdx, pPk->aiColumn[i]); sqlite3VdbeAddOp3(v, OP_Column, iThisCur, x, regR+i); VdbeComment((v, "%s.%s", pTab->zName, @@ -95449,6 +104257,7 @@ SQLITE_PRIVATE void sqlite3GenerateConstraintChecks( for(i=0; inKeyCol; i++){ char *p4 = (char*)sqlite3LocateCollSeq(pParse, pPk->azColl[i]); x = pPk->aiColumn[i]; + assert( x>=0 ); if( i==(pPk->nKeyCol-1) ){ addrJump = addrUniqueOk; op = OP_Eq; @@ -95475,7 +104284,7 @@ SQLITE_PRIVATE void sqlite3GenerateConstraintChecks( break; } case OE_Ignore: { - sqlite3VdbeAddOp2(v, OP_Goto, 0, ignoreDest); + sqlite3VdbeGoto(v, ignoreDest); break; } default: { @@ -95486,7 +104295,8 @@ SQLITE_PRIVATE void sqlite3GenerateConstraintChecks( pTrigger = sqlite3TriggersExist(pParse, pTab, TK_DELETE, 0, 0); } sqlite3GenerateRowDelete(pParse, pTab, pTrigger, iDataCur, iIdxCur, - regR, nPkField, 0, OE_Replace, pIdx==pPk); + regR, nPkField, 0, OE_Replace, + (pIdx==pPk ? ONEPASS_SINGLE : ONEPASS_OFF), -1); seenReplace = 1; break; } @@ -95496,7 +104306,7 @@ SQLITE_PRIVATE void sqlite3GenerateConstraintChecks( if( regR!=regIdx ) sqlite3ReleaseTempRange(pParse, regR, nPkField); } if( ipkTop ){ - sqlite3VdbeAddOp2(v, OP_Goto, 0, ipkTop+1); + sqlite3VdbeGoto(v, ipkTop+1); sqlite3VdbeJumpHere(v, ipkBottom); } @@ -95528,7 +104338,7 @@ SQLITE_PRIVATE void sqlite3CompleteInsertion( Index *pIdx; /* An index being inserted or updated */ u8 pik_flags; /* flag values passed to the btree insert */ int regData; /* Content registers (after the rowid) */ - int regRec; /* Register holding assemblied record for the table */ + int regRec; /* Register holding assembled record for the table */ int i; /* Loop counter */ u8 bAffinityDone = 0; /* True if OP_Affinity has been run already */ @@ -95593,11 +104403,15 @@ SQLITE_PRIVATE void sqlite3CompleteInsertion( ** For a WITHOUT ROWID table, *piDataCur will be somewhere in the range ** of *piIdxCurs, depending on where the PRIMARY KEY index appears on the ** pTab->pIndex list. +** +** If pTab is a virtual table, then this routine is a no-op and the +** *piDataCur and *piIdxCur values are left uninitialized. */ SQLITE_PRIVATE int sqlite3OpenTableAndIndices( Parse *pParse, /* Parsing context */ Table *pTab, /* Table to be opened */ int op, /* OP_OpenRead or OP_OpenWrite */ + u8 p5, /* P5 value for OP_Open* instructions */ int iBase, /* Use this for the table cursor, if there is one */ u8 *aToOpen, /* If not NULL: boolean for each table and index */ int *piDataCur, /* Write the database source cursor number here */ @@ -95610,10 +104424,11 @@ SQLITE_PRIVATE int sqlite3OpenTableAndIndices( Vdbe *v; assert( op==OP_OpenRead || op==OP_OpenWrite ); + assert( op==OP_OpenWrite || p5==0 ); if( IsVirtual(pTab) ){ - assert( aToOpen==0 ); - *piDataCur = 0; - *piIdxCur = 1; + /* This routine is a no-op for virtual tables. Leave the output + ** variables *piDataCur and *piIdxCur uninitialized so that valgrind + ** can detect if they are used by mistake in the caller. */ return 0; } iDb = sqlite3SchemaToIndex(pParse->db, pTab->pSchema); @@ -95637,6 +104452,7 @@ SQLITE_PRIVATE int sqlite3OpenTableAndIndices( if( aToOpen==0 || aToOpen[i+1] ){ sqlite3VdbeAddOp3(v, op, iIdxCur, pIdx->tnum, iDb); sqlite3VdbeSetP4KeyInfo(pParse, pIdx); + sqlite3VdbeChangeP5(v, p5); VdbeComment((v, "%s", pIdx->zName)); } } @@ -95650,27 +104466,13 @@ SQLITE_PRIVATE int sqlite3OpenTableAndIndices( ** The following global variable is incremented whenever the ** transfer optimization is used. This is used for testing ** purposes only - to make sure the transfer optimization really -** is happening when it is suppose to. +** is happening when it is supposed to. */ SQLITE_API int sqlite3_xferopt_count; #endif /* SQLITE_TEST */ #ifndef SQLITE_OMIT_XFER_OPT -/* -** Check to collation names to see if they are compatible. -*/ -static int xferCompatibleCollation(const char *z1, const char *z2){ - if( z1==0 ){ - return z2==0; - } - if( z2==0 ){ - return 0; - } - return sqlite3StrICmp(z1, z2)==0; -} - - /* ** Check to see if index pSrc is compatible as a source of data ** for index pDest in an insert transfer optimization. The rules @@ -95696,10 +104498,17 @@ static int xferCompatibleIndex(Index *pDest, Index *pSrc){ if( pSrc->aiColumn[i]!=pDest->aiColumn[i] ){ return 0; /* Different columns indexed */ } + if( pSrc->aiColumn[i]==XN_EXPR ){ + assert( pSrc->aColExpr!=0 && pDest->aColExpr!=0 ); + if( sqlite3ExprCompare(pSrc->aColExpr->a[i].pExpr, + pDest->aColExpr->a[i].pExpr, -1)!=0 ){ + return 0; /* Different expressions in the index */ + } + } if( pSrc->aSortOrder[i]!=pDest->aSortOrder[i] ){ return 0; /* Different sort orders */ } - if( !xferCompatibleCollation(pSrc->azColl[i],pDest->azColl[i]) ){ + if( sqlite3_stricmp(pSrc->azColl[i],pDest->azColl[i])!=0 ){ return 0; /* Different collating sequences */ } } @@ -95717,7 +104526,7 @@ static int xferCompatibleIndex(Index *pDest, Index *pSrc){ ** INSERT INTO tab1 SELECT * FROM tab2; ** ** The xfer optimization transfers raw records from tab2 over to tab1. -** Columns are not decoded and reassemblied, which greatly improves +** Columns are not decoded and reassembled, which greatly improves ** performance. Raw index records are transferred in the same way. ** ** The xfer optimization is only attempted if tab1 and tab2 are compatible. @@ -95743,6 +104552,7 @@ static int xferOptimization( int onError, /* How to handle constraint errors */ int iDbDest /* The database of pDest */ ){ + sqlite3 *db = pParse->db; ExprList *pEList; /* The result set of the SELECT */ Table *pSrc; /* The table in the FROM clause of SELECT */ Index *pSrcIdx, *pDestIdx; /* Source and destination indices */ @@ -95813,7 +104623,7 @@ static int xferOptimization( return 0; /* The result set must have exactly one column */ } assert( pEList->a[0].pExpr ); - if( pEList->a[0].pExpr->op!=TK_ALL ){ + if( pEList->a[0].pExpr->op!=TK_ASTERISK ){ return 0; /* The result set must be the special operator "*" */ } @@ -95849,10 +104659,17 @@ static int xferOptimization( for(i=0; inCol; i++){ Column *pDestCol = &pDest->aCol[i]; Column *pSrcCol = &pSrc->aCol[i]; +#ifdef SQLITE_ENABLE_HIDDEN_COLUMNS + if( (db->flags & SQLITE_Vacuum)==0 + && (pDestCol->colFlags | pSrcCol->colFlags) & COLFLAG_HIDDEN + ){ + return 0; /* Neither table may have __hidden__ columns */ + } +#endif if( pDestCol->affinity!=pSrcCol->affinity ){ return 0; /* Affinity must be the same on all columns */ } - if( !xferCompatibleCollation(pDestCol->zColl, pSrcCol->zColl) ){ + if( sqlite3_stricmp(pDestCol->zColl, pSrcCol->zColl)!=0 ){ return 0; /* Collating sequence must be the same on all columns */ } if( pDestCol->notNull && !pSrcCol->notNull ){ @@ -95867,7 +104684,7 @@ static int xferOptimization( } } for(pDestIdx=pDest->pIndex; pDestIdx; pDestIdx=pDestIdx->pNext){ - if( pDestIdx->onError!=OE_None ){ + if( IsUniqueIndex(pDestIdx) ){ destHasUniqueIdx = 1; } for(pSrcIdx=pSrc->pIndex; pSrcIdx; pSrcIdx=pSrcIdx->pNext){ @@ -95890,11 +104707,11 @@ static int xferOptimization( ** the extra complication to make this rule less restrictive is probably ** not worth the effort. Ticket [6284df89debdfa61db8073e062908af0c9b6118e] */ - if( (pParse->db->flags & SQLITE_ForeignKeys)!=0 && pDest->pFKey!=0 ){ + if( (db->flags & SQLITE_ForeignKeys)!=0 && pDest->pFKey!=0 ){ return 0; } #endif - if( (pParse->db->flags & SQLITE_CountRows)!=0 ){ + if( (db->flags & SQLITE_CountRows)!=0 ){ return 0; /* xfer opt does not play well with PRAGMA count_changes */ } @@ -95905,7 +104722,7 @@ static int xferOptimization( #ifdef SQLITE_TEST sqlite3_xferopt_count++; #endif - iDbSrc = sqlite3SchemaToIndex(pParse->db, pSrc->pSchema); + iDbSrc = sqlite3SchemaToIndex(db, pSrc->pSchema); v = sqlite3GetVdbe(pParse); sqlite3CodeVerifySchema(pParse, iDbSrc); iSrc = pParse->nTab++; @@ -95915,14 +104732,18 @@ static int xferOptimization( regRowid = sqlite3GetTempReg(pParse); sqlite3OpenTable(pParse, iDest, iDbDest, pDest, OP_OpenWrite); assert( HasRowid(pDest) || destHasUniqueIdx ); - if( (pDest->iPKey<0 && pDest->pIndex!=0) /* (1) */ + if( (db->flags & SQLITE_Vacuum)==0 && ( + (pDest->iPKey<0 && pDest->pIndex!=0) /* (1) */ || destHasUniqueIdx /* (2) */ || (onError!=OE_Abort && onError!=OE_Rollback) /* (3) */ - ){ + )){ /* In some circumstances, we are able to run the xfer optimization - ** only if the destination table is initially empty. This code makes - ** that determination. Conditions under which the destination must - ** be empty: + ** only if the destination table is initially empty. Unless the + ** SQLITE_Vacuum flag is set, this block generates code to make + ** that determination. If SQLITE_Vacuum is set, then the destination + ** table is always empty. + ** + ** Conditions under which the destination must be empty: ** ** (1) There is no INTEGER PRIMARY KEY but there are indices. ** (If the destination is not initially empty, the rowid fields @@ -95934,7 +104755,7 @@ static int xferOptimization( ** (3) onError is something other than OE_Abort and OE_Rollback. */ addr1 = sqlite3VdbeAddOp2(v, OP_Rewind, iDest, 0); VdbeCoverage(v); - emptyDestTest = sqlite3VdbeAddOp2(v, OP_Goto, 0, 0); + emptyDestTest = sqlite3VdbeAddOp0(v, OP_Goto); sqlite3VdbeJumpHere(v, addr1); } if( HasRowid(pSrc) ){ @@ -95965,6 +104786,7 @@ static int xferOptimization( sqlite3TableLock(pParse, iDbSrc, pSrc->tnum, 0, pSrc->zName); } for(pDestIdx=pDest->pIndex; pDestIdx; pDestIdx=pDestIdx->pNext){ + u8 idxInsFlags = 0; for(pSrcIdx=pSrc->pIndex; ALWAYS(pSrcIdx); pSrcIdx=pSrcIdx->pNext){ if( xferCompatibleIndex(pDestIdx, pSrcIdx) ) break; } @@ -95978,7 +104800,37 @@ static int xferOptimization( VdbeComment((v, "%s", pDestIdx->zName)); addr1 = sqlite3VdbeAddOp2(v, OP_Rewind, iSrc, 0); VdbeCoverage(v); sqlite3VdbeAddOp2(v, OP_RowKey, iSrc, regData); + if( db->flags & SQLITE_Vacuum ){ + /* This INSERT command is part of a VACUUM operation, which guarantees + ** that the destination table is empty. If all indexed columns use + ** collation sequence BINARY, then it can also be assumed that the + ** index will be populated by inserting keys in strictly sorted + ** order. In this case, instead of seeking within the b-tree as part + ** of every OP_IdxInsert opcode, an OP_Last is added before the + ** OP_IdxInsert to seek to the point within the b-tree where each key + ** should be inserted. This is faster. + ** + ** If any of the indexed columns use a collation sequence other than + ** BINARY, this optimization is disabled. This is because the user + ** might change the definition of a collation sequence and then run + ** a VACUUM command. In that case keys may not be written in strictly + ** sorted order. */ + for(i=0; inColumn; i++){ + const char *zColl = pSrcIdx->azColl[i]; + assert( sqlite3_stricmp(sqlite3StrBINARY, zColl)!=0 + || sqlite3StrBINARY==zColl ); + if( sqlite3_stricmp(sqlite3StrBINARY, zColl) ) break; + } + if( i==pSrcIdx->nColumn ){ + idxInsFlags = OPFLAG_USESEEKRESULT; + sqlite3VdbeAddOp3(v, OP_Last, iDest, 0, -1); + } + } + if( !HasRowid(pSrc) && pDestIdx->idxType==2 ){ + idxInsFlags |= OPFLAG_NCHANGE; + } sqlite3VdbeAddOp3(v, OP_IdxInsert, iDest, regData, 1); + sqlite3VdbeChangeP5(v, idxInsFlags); sqlite3VdbeAddOp2(v, OP_Next, iSrc, addr1+1); VdbeCoverage(v); sqlite3VdbeJumpHere(v, addr1); sqlite3VdbeAddOp2(v, OP_Close, iSrc, 0); @@ -96017,6 +104869,7 @@ static int xferOptimization( ** accessed by users of the library. */ +/* #include "sqliteInt.h" */ /* ** Execute SQL code. Return one of the SQLITE_ success/failure @@ -96028,7 +104881,7 @@ static int xferOptimization( ** argument to xCallback(). If xCallback=NULL then no callback ** is invoked, even for queries. */ -SQLITE_API int sqlite3_exec( +SQLITE_API int SQLITE_STDCALL sqlite3_exec( sqlite3 *db, /* The database on which the SQL executes */ const char *zSql, /* The SQL to be executed */ sqlite3_callback xCallback, /* Invoke this callback routine */ @@ -96045,7 +104898,7 @@ SQLITE_API int sqlite3_exec( if( zSql==0 ) zSql = ""; sqlite3_mutex_enter(db->mutex); - sqlite3Error(db, SQLITE_OK, 0); + sqlite3Error(db, SQLITE_OK); while( rc==SQLITE_OK && zSql[0] ){ int nCol; char **azVals = 0; @@ -96097,10 +104950,13 @@ SQLITE_API int sqlite3_exec( } } if( xCallback(pArg, nCol, azVals, azCols) ){ + /* EVIDENCE-OF: R-38229-40159 If the callback function to + ** sqlite3_exec() returns non-zero, then sqlite3_exec() will + ** return SQLITE_ABORT. */ rc = SQLITE_ABORT; sqlite3VdbeFinalize((Vdbe *)pStmt); pStmt = 0; - sqlite3Error(db, SQLITE_ABORT, 0); + sqlite3Error(db, SQLITE_ABORT); goto exec_out; } } @@ -96123,14 +104979,14 @@ exec_out: sqlite3DbFree(db, azCols); rc = sqlite3ApiExit(db, rc); - if( rc!=SQLITE_OK && ALWAYS(rc==sqlite3_errcode(db)) && pzErrMsg ){ + if( rc!=SQLITE_OK && pzErrMsg ){ int nErrMsg = 1 + sqlite3Strlen30(sqlite3_errmsg(db)); *pzErrMsg = sqlite3Malloc(nErrMsg); if( *pzErrMsg ){ memcpy(*pzErrMsg, sqlite3_errmsg(db), nErrMsg); }else{ rc = SQLITE_NOMEM; - sqlite3Error(db, SQLITE_NOMEM, 0); + sqlite3Error(db, SQLITE_NOMEM); } }else if( pzErrMsg ){ *pzErrMsg = 0; @@ -96182,6 +105038,7 @@ exec_out: */ #ifndef _SQLITE3EXT_H_ #define _SQLITE3EXT_H_ +/* #include "sqlite3.h" */ typedef struct sqlite3_api_routines sqlite3_api_routines; @@ -96192,7 +105049,7 @@ typedef struct sqlite3_api_routines sqlite3_api_routines; ** WARNING: In order to maintain backwards compatibility, add new ** interfaces to the end of this structure only. If you insert new ** interfaces in the middle of this structure, then older different -** versions of SQLite will not be able to load each others' shared +** versions of SQLite will not be able to load each other's shared ** libraries! */ struct sqlite3_api_routines { @@ -96414,11 +105271,40 @@ struct sqlite3_api_routines { const char *(*uri_parameter)(const char*,const char*); char *(*vsnprintf)(int,char*,const char*,va_list); int (*wal_checkpoint_v2)(sqlite3*,const char*,int,int*,int*); + /* Version 3.8.7 and later */ + int (*auto_extension)(void(*)(void)); + int (*bind_blob64)(sqlite3_stmt*,int,const void*,sqlite3_uint64, + void(*)(void*)); + int (*bind_text64)(sqlite3_stmt*,int,const char*,sqlite3_uint64, + void(*)(void*),unsigned char); + int (*cancel_auto_extension)(void(*)(void)); + int (*load_extension)(sqlite3*,const char*,const char*,char**); + void *(*malloc64)(sqlite3_uint64); + sqlite3_uint64 (*msize)(void*); + void *(*realloc64)(void*,sqlite3_uint64); + void (*reset_auto_extension)(void); + void (*result_blob64)(sqlite3_context*,const void*,sqlite3_uint64, + void(*)(void*)); + void (*result_text64)(sqlite3_context*,const char*,sqlite3_uint64, + void(*)(void*), unsigned char); + int (*strglob)(const char*,const char*); + /* Version 3.8.11 and later */ + sqlite3_value *(*value_dup)(const sqlite3_value*); + void (*value_free)(sqlite3_value*); + int (*result_zeroblob64)(sqlite3_context*,sqlite3_uint64); + int (*bind_zeroblob64)(sqlite3_stmt*, int, sqlite3_uint64); + /* Version 3.9.0 and later */ + unsigned int (*value_subtype)(sqlite3_value*); + void (*result_subtype)(sqlite3_context*,unsigned int); + /* Version 3.10.0 and later */ + int (*status64)(int,sqlite3_int64*,sqlite3_int64*,int); + int (*strlike)(const char*,const char*,unsigned int); + int (*db_cacheflush)(sqlite3*); }; /* ** The following macros redefine the API routines so that they are -** redirected throught the global sqlite3_api structure. +** redirected through the global sqlite3_api structure. ** ** This header file is also used by the loadext.c source file ** (part of the main SQLite library - not an extension) so that @@ -96427,7 +105313,7 @@ struct sqlite3_api_routines { ** the API. So the redefinition macros are only valid if the ** SQLITE_CORE macros is undefined. */ -#ifndef SQLITE_CORE +#if !defined(SQLITE_CORE) && !defined(SQLITE_OMIT_LOAD_EXTENSION) #define sqlite3_aggregate_context sqlite3_api->aggregate_context #ifndef SQLITE_OMIT_DEPRECATED #define sqlite3_aggregate_count sqlite3_api->aggregate_count @@ -96554,6 +105440,7 @@ struct sqlite3_api_routines { #define sqlite3_value_text16le sqlite3_api->value_text16le #define sqlite3_value_type sqlite3_api->value_type #define sqlite3_vmprintf sqlite3_api->vmprintf +#define sqlite3_vsnprintf sqlite3_api->vsnprintf #define sqlite3_overload_function sqlite3_api->overload_function #define sqlite3_prepare_v2 sqlite3_api->prepare_v2 #define sqlite3_prepare16_v2 sqlite3_api->prepare16_v2 @@ -96631,9 +105518,34 @@ struct sqlite3_api_routines { #define sqlite3_uri_parameter sqlite3_api->uri_parameter #define sqlite3_uri_vsnprintf sqlite3_api->vsnprintf #define sqlite3_wal_checkpoint_v2 sqlite3_api->wal_checkpoint_v2 -#endif /* SQLITE_CORE */ +/* Version 3.8.7 and later */ +#define sqlite3_auto_extension sqlite3_api->auto_extension +#define sqlite3_bind_blob64 sqlite3_api->bind_blob64 +#define sqlite3_bind_text64 sqlite3_api->bind_text64 +#define sqlite3_cancel_auto_extension sqlite3_api->cancel_auto_extension +#define sqlite3_load_extension sqlite3_api->load_extension +#define sqlite3_malloc64 sqlite3_api->malloc64 +#define sqlite3_msize sqlite3_api->msize +#define sqlite3_realloc64 sqlite3_api->realloc64 +#define sqlite3_reset_auto_extension sqlite3_api->reset_auto_extension +#define sqlite3_result_blob64 sqlite3_api->result_blob64 +#define sqlite3_result_text64 sqlite3_api->result_text64 +#define sqlite3_strglob sqlite3_api->strglob +/* Version 3.8.11 and later */ +#define sqlite3_value_dup sqlite3_api->value_dup +#define sqlite3_value_free sqlite3_api->value_free +#define sqlite3_result_zeroblob64 sqlite3_api->result_zeroblob64 +#define sqlite3_bind_zeroblob64 sqlite3_api->bind_zeroblob64 +/* Version 3.9.0 and later */ +#define sqlite3_value_subtype sqlite3_api->value_subtype +#define sqlite3_result_subtype sqlite3_api->result_subtype +/* Version 3.10.0 and later */ +#define sqlite3_status64 sqlite3_api->status64 +#define sqlite3_strlike sqlite3_api->strlike +#define sqlite3_db_cacheflush sqlite3_api->db_cacheflush +#endif /* !defined(SQLITE_CORE) && !defined(SQLITE_OMIT_LOAD_EXTENSION) */ -#ifndef SQLITE_CORE +#if !defined(SQLITE_CORE) && !defined(SQLITE_OMIT_LOAD_EXTENSION) /* This case when the file really is being compiled as a loadable ** extension */ # define SQLITE_EXTENSION_INIT1 const sqlite3_api_routines *sqlite3_api=0; @@ -96652,6 +105564,7 @@ struct sqlite3_api_routines { /************** End of sqlite3ext.h ******************************************/ /************** Continuing where we left off in loadext.c ********************/ +/* #include "sqliteInt.h" */ /* #include */ #ifndef SQLITE_OMIT_LOAD_EXTENSION @@ -96668,7 +105581,6 @@ struct sqlite3_api_routines { # define sqlite3_column_table_name16 0 # define sqlite3_column_origin_name 0 # define sqlite3_column_origin_name16 0 -# define sqlite3_table_column_metadata 0 #endif #ifdef SQLITE_OMIT_AUTHORIZATION @@ -97024,7 +105936,32 @@ static const sqlite3_api_routines sqlite3Apis = { sqlite3_uri_int64, sqlite3_uri_parameter, sqlite3_vsnprintf, - sqlite3_wal_checkpoint_v2 + sqlite3_wal_checkpoint_v2, + /* Version 3.8.7 and later */ + sqlite3_auto_extension, + sqlite3_bind_blob64, + sqlite3_bind_text64, + sqlite3_cancel_auto_extension, + sqlite3_load_extension, + sqlite3_malloc64, + sqlite3_msize, + sqlite3_realloc64, + sqlite3_reset_auto_extension, + sqlite3_result_blob64, + sqlite3_result_text64, + sqlite3_strglob, + /* Version 3.8.11 and later */ + (sqlite3_value*(*)(const sqlite3_value*))sqlite3_value_dup, + sqlite3_value_free, + sqlite3_result_zeroblob64, + sqlite3_bind_zeroblob64, + /* Version 3.9.0 and later */ + sqlite3_value_subtype, + sqlite3_result_subtype, + /* Version 3.10.0 and later */ + sqlite3_status64, + sqlite3_strlike, + sqlite3_db_cacheflush }; /* @@ -97052,7 +105989,7 @@ static int sqlite3LoadExtension( const char *zEntry; char *zAltEntry = 0; void **aHandle; - int nMsg = 300 + sqlite3Strlen30(zFile); + u64 nMsg = 300 + sqlite3Strlen30(zFile); int ii; /* Shared library endings to try if zFile cannot be loaded as written */ @@ -97095,7 +106032,7 @@ static int sqlite3LoadExtension( #endif if( handle==0 ){ if( pzErrMsg ){ - *pzErrMsg = zErrmsg = sqlite3_malloc(nMsg); + *pzErrMsg = zErrmsg = sqlite3_malloc64(nMsg); if( zErrmsg ){ sqlite3_snprintf(nMsg, zErrmsg, "unable to open shared library [%s]", zFile); @@ -97121,7 +106058,7 @@ static int sqlite3LoadExtension( if( xInit==0 && zProc==0 ){ int iFile, iEntry, c; int ncFile = sqlite3Strlen30(zFile); - zAltEntry = sqlite3_malloc(ncFile+30); + zAltEntry = sqlite3_malloc64(ncFile+30); if( zAltEntry==0 ){ sqlite3OsDlClose(pVfs, handle); return SQLITE_NOMEM; @@ -97143,7 +106080,7 @@ static int sqlite3LoadExtension( if( xInit==0 ){ if( pzErrMsg ){ nMsg += sqlite3Strlen30(zEntry); - *pzErrMsg = zErrmsg = sqlite3_malloc(nMsg); + *pzErrMsg = zErrmsg = sqlite3_malloc64(nMsg); if( zErrmsg ){ sqlite3_snprintf(nMsg, zErrmsg, "no entry point [%s] in shared library [%s]", zEntry, zFile); @@ -97178,7 +106115,7 @@ static int sqlite3LoadExtension( db->aExtension[db->nExtension++] = handle; return SQLITE_OK; } -SQLITE_API int sqlite3_load_extension( +SQLITE_API int SQLITE_STDCALL sqlite3_load_extension( sqlite3 *db, /* Load the extension into this database connection */ const char *zFile, /* Name of the shared library containing extension */ const char *zProc, /* Entry point. Use "sqlite3_extension_init" if 0 */ @@ -97209,7 +106146,7 @@ SQLITE_PRIVATE void sqlite3CloseExtensions(sqlite3 *db){ ** Enable or disable extension loading. Extension loading is disabled by ** default so as not to open security holes in older applications. */ -SQLITE_API int sqlite3_enable_load_extension(sqlite3 *db, int onoff){ +SQLITE_API int SQLITE_STDCALL sqlite3_enable_load_extension(sqlite3 *db, int onoff){ sqlite3_mutex_enter(db->mutex); if( onoff ){ db->flags |= SQLITE_LoadExtension; @@ -97242,7 +106179,7 @@ static const sqlite3_api_routines sqlite3Apis = { 0 }; */ typedef struct sqlite3AutoExtList sqlite3AutoExtList; static SQLITE_WSD struct sqlite3AutoExtList { - int nExt; /* Number of entries in aExt[] */ + u32 nExt; /* Number of entries in aExt[] */ void (**aExt)(void); /* Pointers to the extension init functions */ } sqlite3Autoext = { 0, 0 }; @@ -97266,7 +106203,7 @@ static SQLITE_WSD struct sqlite3AutoExtList { ** Register a statically linked extension that is automatically ** loaded by every new database connection. */ -SQLITE_API int sqlite3_auto_extension(void (*xInit)(void)){ +SQLITE_API int SQLITE_STDCALL sqlite3_auto_extension(void (*xInit)(void)){ int rc = SQLITE_OK; #ifndef SQLITE_OMIT_AUTOINIT rc = sqlite3_initialize(); @@ -97275,7 +106212,7 @@ SQLITE_API int sqlite3_auto_extension(void (*xInit)(void)){ }else #endif { - int i; + u32 i; #if SQLITE_THREADSAFE sqlite3_mutex *mutex = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MASTER); #endif @@ -97285,9 +106222,9 @@ SQLITE_API int sqlite3_auto_extension(void (*xInit)(void)){ if( wsdAutoext.aExt[i]==xInit ) break; } if( i==wsdAutoext.nExt ){ - int nByte = (wsdAutoext.nExt+1)*sizeof(wsdAutoext.aExt[0]); + u64 nByte = (wsdAutoext.nExt+1)*sizeof(wsdAutoext.aExt[0]); void (**aNew)(void); - aNew = sqlite3_realloc(wsdAutoext.aExt, nByte); + aNew = sqlite3_realloc64(wsdAutoext.aExt, nByte); if( aNew==0 ){ rc = SQLITE_NOMEM; }else{ @@ -97311,7 +106248,7 @@ SQLITE_API int sqlite3_auto_extension(void (*xInit)(void)){ ** Return 1 if xInit was found on the list and removed. Return 0 if xInit ** was not on the list. */ -SQLITE_API int sqlite3_cancel_auto_extension(void (*xInit)(void)){ +SQLITE_API int SQLITE_STDCALL sqlite3_cancel_auto_extension(void (*xInit)(void)){ #if SQLITE_THREADSAFE sqlite3_mutex *mutex = sqlite3MutexAlloc(SQLITE_MUTEX_STATIC_MASTER); #endif @@ -97319,7 +106256,7 @@ SQLITE_API int sqlite3_cancel_auto_extension(void (*xInit)(void)){ int n = 0; wsdAutoextInit; sqlite3_mutex_enter(mutex); - for(i=wsdAutoext.nExt-1; i>=0; i--){ + for(i=(int)wsdAutoext.nExt-1; i>=0; i--){ if( wsdAutoext.aExt[i]==xInit ){ wsdAutoext.nExt--; wsdAutoext.aExt[i] = wsdAutoext.aExt[wsdAutoext.nExt]; @@ -97334,7 +106271,7 @@ SQLITE_API int sqlite3_cancel_auto_extension(void (*xInit)(void)){ /* ** Reset the automatic extension loading mechanism. */ -SQLITE_API void sqlite3_reset_auto_extension(void){ +SQLITE_API void SQLITE_STDCALL sqlite3_reset_auto_extension(void){ #ifndef SQLITE_OMIT_AUTOINIT if( sqlite3_initialize()==SQLITE_OK ) #endif @@ -97357,7 +106294,7 @@ SQLITE_API void sqlite3_reset_auto_extension(void){ ** If anything goes wrong, set an error in the database connection. */ SQLITE_PRIVATE void sqlite3AutoLoadExtensions(sqlite3 *db){ - int i; + u32 i; int go = 1; int rc; int (*xInit)(sqlite3*,char**,const sqlite3_api_routines*); @@ -97383,7 +106320,7 @@ SQLITE_PRIVATE void sqlite3AutoLoadExtensions(sqlite3 *db){ sqlite3_mutex_leave(mutex); zErrmsg = 0; if( xInit && (rc = xInit(db, &zErrmsg, &sqlite3Apis))!=0 ){ - sqlite3Error(db, rc, + sqlite3ErrorWithMsg(db, rc, "automatic extension loading failed: %s", zErrmsg); go = 0; } @@ -97406,6 +106343,7 @@ SQLITE_PRIVATE void sqlite3AutoLoadExtensions(sqlite3 *db){ ************************************************************************* ** This file contains code used to implement the PRAGMA command. */ +/* #include "sqliteInt.h" */ #if !defined(SQLITE_ENABLE_LOCKING_STYLE) # if defined(__APPLE__) @@ -97416,54 +106354,64 @@ SQLITE_PRIVATE void sqlite3AutoLoadExtensions(sqlite3 *db){ #endif /*************************************************************************** -** The next block of code, including the PragTyp_XXXX macro definitions and -** the aPragmaName[] object is composed of generated code. DO NOT EDIT. -** -** To add new pragmas, edit the code in ../tool/mkpragmatab.tcl and rerun -** that script. Then copy/paste the output in place of the following: +** The "pragma.h" include file is an automatically generated file that +** that includes the PragType_XXXX macro definitions and the aPragmaName[] +** object. This ensures that the aPragmaName[] table is arranged in +** lexicographical order to facility a binary search of the pragma name. +** Do not edit pragma.h directly. Edit and rerun the script in at +** ../tool/mkpragmatab.tcl. */ +/************** Include pragma.h in the middle of pragma.c *******************/ +/************** Begin file pragma.h ******************************************/ +/* DO NOT EDIT! +** This file is automatically generated by the script at +** ../tool/mkpragmatab.tcl. To update the set of pragmas, edit +** that script and rerun it. */ #define PragTyp_HEADER_VALUE 0 #define PragTyp_AUTO_VACUUM 1 #define PragTyp_FLAG 2 #define PragTyp_BUSY_TIMEOUT 3 #define PragTyp_CACHE_SIZE 4 -#define PragTyp_CASE_SENSITIVE_LIKE 5 -#define PragTyp_COLLATION_LIST 6 -#define PragTyp_COMPILE_OPTIONS 7 -#define PragTyp_DATA_STORE_DIRECTORY 8 -#define PragTyp_DATABASE_LIST 9 -#define PragTyp_DEFAULT_CACHE_SIZE 10 -#define PragTyp_ENCODING 11 -#define PragTyp_FOREIGN_KEY_CHECK 12 -#define PragTyp_FOREIGN_KEY_LIST 13 -#define PragTyp_INCREMENTAL_VACUUM 14 -#define PragTyp_INDEX_INFO 15 -#define PragTyp_INDEX_LIST 16 -#define PragTyp_INTEGRITY_CHECK 17 -#define PragTyp_JOURNAL_MODE 18 -#define PragTyp_JOURNAL_SIZE_LIMIT 19 -#define PragTyp_LOCK_PROXY_FILE 20 -#define PragTyp_LOCKING_MODE 21 -#define PragTyp_PAGE_COUNT 22 -#define PragTyp_MMAP_SIZE 23 -#define PragTyp_PAGE_SIZE 24 -#define PragTyp_SECURE_DELETE 25 -#define PragTyp_SHRINK_MEMORY 26 -#define PragTyp_SOFT_HEAP_LIMIT 27 -#define PragTyp_STATS 28 -#define PragTyp_SYNCHRONOUS 29 -#define PragTyp_TABLE_INFO 30 -#define PragTyp_TEMP_STORE 31 -#define PragTyp_TEMP_STORE_DIRECTORY 32 -#define PragTyp_WAL_AUTOCHECKPOINT 33 -#define PragTyp_WAL_CHECKPOINT 34 -#define PragTyp_ACTIVATE_EXTENSIONS 35 -#define PragTyp_HEXKEY 36 -#define PragTyp_KEY 37 -#define PragTyp_REKEY 38 -#define PragTyp_LOCK_STATUS 39 -#define PragTyp_PARSER_TRACE 40 +#define PragTyp_CACHE_SPILL 5 +#define PragTyp_CASE_SENSITIVE_LIKE 6 +#define PragTyp_COLLATION_LIST 7 +#define PragTyp_COMPILE_OPTIONS 8 +#define PragTyp_DATA_STORE_DIRECTORY 9 +#define PragTyp_DATABASE_LIST 10 +#define PragTyp_DEFAULT_CACHE_SIZE 11 +#define PragTyp_ENCODING 12 +#define PragTyp_FOREIGN_KEY_CHECK 13 +#define PragTyp_FOREIGN_KEY_LIST 14 +#define PragTyp_INCREMENTAL_VACUUM 15 +#define PragTyp_INDEX_INFO 16 +#define PragTyp_INDEX_LIST 17 +#define PragTyp_INTEGRITY_CHECK 18 +#define PragTyp_JOURNAL_MODE 19 +#define PragTyp_JOURNAL_SIZE_LIMIT 20 +#define PragTyp_LOCK_PROXY_FILE 21 +#define PragTyp_LOCKING_MODE 22 +#define PragTyp_PAGE_COUNT 23 +#define PragTyp_MMAP_SIZE 24 +#define PragTyp_PAGE_SIZE 25 +#define PragTyp_SECURE_DELETE 26 +#define PragTyp_SHRINK_MEMORY 27 +#define PragTyp_SOFT_HEAP_LIMIT 28 +#define PragTyp_STATS 29 +#define PragTyp_SYNCHRONOUS 30 +#define PragTyp_TABLE_INFO 31 +#define PragTyp_TEMP_STORE 32 +#define PragTyp_TEMP_STORE_DIRECTORY 33 +#define PragTyp_THREADS 34 +#define PragTyp_WAL_AUTOCHECKPOINT 35 +#define PragTyp_WAL_CHECKPOINT 36 +#define PragTyp_ACTIVATE_EXTENSIONS 37 +#define PragTyp_HEXKEY 38 +#define PragTyp_KEY 39 +#define PragTyp_REKEY 40 +#define PragTyp_LOCK_STATUS 41 +#define PragTyp_PARSER_TRACE 42 #define PragFlag_NeedSchema 0x01 +#define PragFlag_ReadOnly 0x02 static const struct sPragmaNames { const char *const zName; /* Name of pragma */ u8 ePragTyp; /* PragTyp_XXX value */ @@ -97480,7 +106428,7 @@ static const struct sPragmaNames { { /* zName: */ "application_id", /* ePragTyp: */ PragTyp_HEADER_VALUE, /* ePragFlag: */ 0, - /* iArg: */ 0 }, + /* iArg: */ BTREE_APPLICATION_ID }, #endif #if !defined(SQLITE_OMIT_AUTOVACUUM) { /* zName: */ "auto_vacuum", @@ -97508,14 +106456,18 @@ static const struct sPragmaNames { #endif #if !defined(SQLITE_OMIT_FLAG_PRAGMAS) { /* zName: */ "cache_spill", - /* ePragTyp: */ PragTyp_FLAG, + /* ePragTyp: */ PragTyp_CACHE_SPILL, /* ePragFlag: */ 0, - /* iArg: */ SQLITE_CacheSpill }, + /* iArg: */ 0 }, #endif { /* zName: */ "case_sensitive_like", /* ePragTyp: */ PragTyp_CASE_SENSITIVE_LIKE, /* ePragFlag: */ 0, /* iArg: */ 0 }, + { /* zName: */ "cell_size_check", + /* ePragTyp: */ PragTyp_FLAG, + /* ePragFlag: */ 0, + /* iArg: */ SQLITE_CellSizeCk }, #if !defined(SQLITE_OMIT_FLAG_PRAGMAS) { /* zName: */ "checkpoint_fullfsync", /* ePragTyp: */ PragTyp_FLAG, @@ -97546,6 +106498,12 @@ static const struct sPragmaNames { /* ePragFlag: */ 0, /* iArg: */ 0 }, #endif +#if !defined(SQLITE_OMIT_SCHEMA_VERSION_PRAGMAS) + { /* zName: */ "data_version", + /* ePragTyp: */ PragTyp_HEADER_VALUE, + /* ePragFlag: */ PragFlag_ReadOnly, + /* iArg: */ BTREE_DATA_VERSION }, +#endif #if !defined(SQLITE_OMIT_SCHEMA_PRAGMAS) { /* zName: */ "database_list", /* ePragTyp: */ PragTyp_DATABASE_LIST, @@ -97601,8 +106559,8 @@ static const struct sPragmaNames { #if !defined(SQLITE_OMIT_SCHEMA_VERSION_PRAGMAS) { /* zName: */ "freelist_count", /* ePragTyp: */ PragTyp_HEADER_VALUE, - /* ePragFlag: */ 0, - /* iArg: */ 0 }, + /* ePragFlag: */ PragFlag_ReadOnly, + /* iArg: */ BTREE_FREE_PAGE_COUNT }, #endif #if !defined(SQLITE_OMIT_FLAG_PRAGMAS) { /* zName: */ "full_column_names", @@ -97647,6 +106605,10 @@ static const struct sPragmaNames { /* ePragTyp: */ PragTyp_INDEX_LIST, /* ePragFlag: */ PragFlag_NeedSchema, /* iArg: */ 0 }, + { /* zName: */ "index_xinfo", + /* ePragTyp: */ PragTyp_INDEX_INFO, + /* ePragFlag: */ PragFlag_NeedSchema, + /* iArg: */ 1 }, #endif #if !defined(SQLITE_OMIT_INTEGRITY_CHECK) { /* zName: */ "integrity_check", @@ -97710,7 +106672,7 @@ static const struct sPragmaNames { /* ePragFlag: */ 0, /* iArg: */ 0 }, #endif -#if defined(SQLITE_DEBUG) +#if defined(SQLITE_DEBUG) && !defined(SQLITE_OMIT_PARSER_TRACE) { /* zName: */ "parser_trace", /* ePragTyp: */ PragTyp_PARSER_TRACE, /* ePragFlag: */ 0, @@ -97754,7 +106716,7 @@ static const struct sPragmaNames { { /* zName: */ "schema_version", /* ePragTyp: */ PragTyp_HEADER_VALUE, /* ePragFlag: */ 0, - /* iArg: */ 0 }, + /* iArg: */ BTREE_SCHEMA_VERSION }, #endif #if !defined(SQLITE_OMIT_PAGER_PRAGMAS) { /* zName: */ "secure_delete", @@ -97812,11 +106774,15 @@ static const struct sPragmaNames { /* ePragFlag: */ 0, /* iArg: */ 0 }, #endif + { /* zName: */ "threads", + /* ePragTyp: */ PragTyp_THREADS, + /* ePragFlag: */ 0, + /* iArg: */ 0 }, #if !defined(SQLITE_OMIT_SCHEMA_VERSION_PRAGMAS) { /* zName: */ "user_version", /* ePragTyp: */ PragTyp_HEADER_VALUE, /* ePragFlag: */ 0, - /* iArg: */ 0 }, + /* iArg: */ BTREE_USER_VERSION }, #endif #if !defined(SQLITE_OMIT_FLAG_PRAGMAS) #if defined(SQLITE_DEBUG) @@ -97859,9 +106825,10 @@ static const struct sPragmaNames { /* iArg: */ SQLITE_WriteSchema|SQLITE_RecoveryMode }, #endif }; -/* Number of pragmas: 56 on by default, 69 total. */ -/* End of the automatically generated pragma table. -***************************************************************************/ +/* Number of pragmas: 60 on by default, 73 total. */ + +/************** End of pragma.h **********************************************/ +/************** Continuing where we left off in pragma.c *********************/ /* ** Interpret the given string as a safety level. Return 0 for OFF, @@ -97874,7 +106841,7 @@ static const struct sPragmaNames { ** to support legacy SQL code. The safety level used to be boolean ** and older scripts may have used numbers 0 for OFF and 1 for ON. */ -static u8 getSafetyLevel(const char *z, int omitFull, int dflt){ +static u8 getSafetyLevel(const char *z, int omitFull, u8 dflt){ /* 123456789 123456789 */ static const char zText[] = "onoffalseyestruefull"; static const u8 iOffset[] = {0, 1, 2, 4, 9, 12, 16}; @@ -97896,7 +106863,7 @@ static u8 getSafetyLevel(const char *z, int omitFull, int dflt){ /* ** Interpret the given string as a boolean value. */ -SQLITE_PRIVATE u8 sqlite3GetBoolean(const char *z, int dflt){ +SQLITE_PRIVATE u8 sqlite3GetBoolean(const char *z, u8 dflt){ return getSafetyLevel(z,1,dflt)!=0; } @@ -97992,20 +106959,46 @@ static int changeTempStorage(Parse *pParse, const char *zStorageType){ } #endif /* SQLITE_PAGER_PRAGMAS */ +/* +** Set the names of the first N columns to the values in azCol[] +*/ +static void setAllColumnNames( + Vdbe *v, /* The query under construction */ + int N, /* Number of columns */ + const char **azCol /* Names of columns */ +){ + int i; + sqlite3VdbeSetNumCols(v, N); + for(i=0; inMem; - i64 *pI64 = sqlite3DbMallocRaw(pParse->db, sizeof(value)); - if( pI64 ){ - memcpy(pI64, &value, sizeof(value)); +static void returnSingleInt(Vdbe *v, const char *zLabel, i64 value){ + sqlite3VdbeAddOp4Dup8(v, OP_Int64, 0, 1, 0, (const u8*)&value, P4_INT64); + setOneColumnName(v, zLabel); + sqlite3VdbeAddOp2(v, OP_ResultRow, 1, 1); +} + +/* +** Generate code to return a single text value. +*/ +static void returnSingleText( + Vdbe *v, /* Prepared statement under construction */ + const char *zLabel, /* Name of the result column */ + const char *zValue /* Value to be returned */ +){ + if( zValue ){ + sqlite3VdbeLoadString(v, 1, (const char*)zValue); + setOneColumnName(v, zLabel); + sqlite3VdbeAddOp2(v, OP_ResultRow, 1, 1); } - sqlite3VdbeAddOp4(v, OP_Int64, 0, mem, 0, (char*)pI64, P4_INT64); - sqlite3VdbeSetNumCols(v, 1); - sqlite3VdbeSetColName(v, 0, COLNAME_NAME, zLabel, SQLITE_STATIC); - sqlite3VdbeAddOp2(v, OP_ResultRow, mem, 1); } @@ -98086,7 +107079,7 @@ SQLITE_PRIVATE const char *sqlite3JournalModename(int eMode){ ** ** Pragmas are of this form: ** -** PRAGMA [database.]id [= value] +** PRAGMA [schema.]id [= value] ** ** The identifier might also be a string. The value is a string, and ** identifier, or a number. If minusFlag is true, then the value is @@ -98098,8 +107091,8 @@ SQLITE_PRIVATE const char *sqlite3JournalModename(int eMode){ */ SQLITE_PRIVATE void sqlite3Pragma( Parse *pParse, - Token *pId1, /* First part of [database.]id field */ - Token *pId2, /* Second part of [database.]id field, or NULL */ + Token *pId1, /* First part of [schema.]id field */ + Token *pId2, /* Second part of [schema.]id field, or NULL */ Token *pValue, /* Token for , or NULL */ int minusFlag /* True if a '-' sign preceded */ ){ @@ -98109,17 +107102,18 @@ SQLITE_PRIVATE void sqlite3Pragma( Token *pId; /* Pointer to token */ char *aFcntl[4]; /* Argument to SQLITE_FCNTL_PRAGMA */ int iDb; /* Database index for */ - int lwr, upr, mid; /* Binary search bounds */ + int lwr, upr, mid = 0; /* Binary search bounds */ int rc; /* return value form SQLITE_FCNTL_PRAGMA */ sqlite3 *db = pParse->db; /* The database connection */ Db *pDb; /* The specific database being pragmaed */ Vdbe *v = sqlite3GetVdbe(pParse); /* Prepared statement */ + const struct sPragmaNames *pPragma; if( v==0 ) return; sqlite3VdbeRunOnlyOnce(v); pParse->nMem = 2; - /* Interpret the [database.] part of the pragma statement. iDb is the + /* Interpret the [schema.] part of the pragma statement. iDb is the ** index of the database this pragma is being applied to in db.aDb[]. */ iDb = sqlite3TwoPartName(pParse, pId1, pId2, &pId); if( iDb<0 ) return; @@ -98149,6 +107143,17 @@ SQLITE_PRIVATE void sqlite3Pragma( /* Send an SQLITE_FCNTL_PRAGMA file-control to the underlying VFS ** connection. If it returns SQLITE_OK, then assume that the VFS ** handled the pragma and generate a no-op prepared statement. + ** + ** IMPLEMENTATION-OF: R-12238-55120 Whenever a PRAGMA statement is parsed, + ** an SQLITE_FCNTL_PRAGMA file control is sent to the open sqlite3_file + ** object corresponding to the database file to which the pragma + ** statement refers. + ** + ** IMPLEMENTATION-OF: R-29875-31678 The argument to the SQLITE_FCNTL_PRAGMA + ** file control is an array of pointers to strings (char**) in which the + ** second element of the array is the name of the pragma and the third + ** element is the argument to the pragma or NULL if the pragma has no + ** argument. */ aFcntl[0] = 0; aFcntl[1] = zLeft; @@ -98157,14 +107162,8 @@ SQLITE_PRIVATE void sqlite3Pragma( db->busyHandler.nBusy = 0; rc = sqlite3_file_control(db, zDb, SQLITE_FCNTL_PRAGMA, (void*)aFcntl); if( rc==SQLITE_OK ){ - if( aFcntl[0] ){ - int mem = ++pParse->nMem; - sqlite3VdbeAddOp4(v, OP_String8, 0, mem, 0, aFcntl[0], 0); - sqlite3VdbeSetNumCols(v, 1); - sqlite3VdbeSetColName(v, 0, COLNAME_NAME, "result", SQLITE_STATIC); - sqlite3VdbeAddOp2(v, OP_ResultRow, mem, 1); - sqlite3_free(aFcntl[0]); - } + returnSingleText(v, "result", aFcntl[0]); + sqlite3_free(aFcntl[0]); goto pragma_out; } if( rc!=SQLITE_NOTFOUND ){ @@ -98191,19 +107190,20 @@ SQLITE_PRIVATE void sqlite3Pragma( } } if( lwr>upr ) goto pragma_out; + pPragma = &aPragmaNames[mid]; /* Make sure the database schema is loaded if the pragma requires that */ - if( (aPragmaNames[mid].mPragFlag & PragFlag_NeedSchema)!=0 ){ + if( (pPragma->mPragFlag & PragFlag_NeedSchema)!=0 ){ if( sqlite3ReadSchema(pParse) ) goto pragma_out; } /* Jump to the appropriate pragma handler */ - switch( aPragmaNames[mid].ePragTyp ){ + switch( pPragma->ePragTyp ){ #if !defined(SQLITE_OMIT_PAGER_PRAGMAS) && !defined(SQLITE_OMIT_DEPRECATED) /* - ** PRAGMA [database.]default_cache_size - ** PRAGMA [database.]default_cache_size=N + ** PRAGMA [schema.]default_cache_size + ** PRAGMA [schema.]default_cache_size=N ** ** The first form reports the current persistent setting for the ** page cache size. The value returned is the maximum number of @@ -98233,8 +107233,7 @@ SQLITE_PRIVATE void sqlite3Pragma( int addr; sqlite3VdbeUsesBtree(v, iDb); if( !zRight ){ - sqlite3VdbeSetNumCols(v, 1); - sqlite3VdbeSetColName(v, 0, COLNAME_NAME, "cache_size", SQLITE_STATIC); + setOneColumnName(v, "cache_size"); pParse->nMem += 2; addr = sqlite3VdbeAddOpList(v, ArraySize(getCacheSize), getCacheSize,iLn); sqlite3VdbeChangeP1(v, addr, iDb); @@ -98255,8 +107254,8 @@ SQLITE_PRIVATE void sqlite3Pragma( #if !defined(SQLITE_OMIT_PAGER_PRAGMAS) /* - ** PRAGMA [database.]page_size - ** PRAGMA [database.]page_size=N + ** PRAGMA [schema.]page_size + ** PRAGMA [schema.]page_size=N ** ** The first form reports the current setting for the ** database page size in bytes. The second form sets the @@ -98268,7 +107267,7 @@ SQLITE_PRIVATE void sqlite3Pragma( assert( pBt!=0 ); if( !zRight ){ int size = ALWAYS(pBt) ? sqlite3BtreeGetPageSize(pBt) : 0; - returnSingleInt(pParse, "page_size", size); + returnSingleInt(v, "page_size", size); }else{ /* Malloc may fail when setting the page-size, as there is an internal ** buffer that the pager module resizes using sqlite3_realloc(). @@ -98282,8 +107281,8 @@ SQLITE_PRIVATE void sqlite3Pragma( } /* - ** PRAGMA [database.]secure_delete - ** PRAGMA [database.]secure_delete=ON/OFF + ** PRAGMA [schema.]secure_delete + ** PRAGMA [schema.]secure_delete=ON/OFF ** ** The first form reports the current setting for the ** secure_delete flag. The second form changes the secure_delete @@ -98303,13 +107302,13 @@ SQLITE_PRIVATE void sqlite3Pragma( } } b = sqlite3BtreeSecureDelete(pBt, b); - returnSingleInt(pParse, "secure_delete", b); + returnSingleInt(v, "secure_delete", b); break; } /* - ** PRAGMA [database.]max_page_count - ** PRAGMA [database.]max_page_count=N + ** PRAGMA [schema.]max_page_count + ** PRAGMA [schema.]max_page_count=N ** ** The first form reports the current setting for the ** maximum number of pages in the database file. The @@ -98320,7 +107319,7 @@ SQLITE_PRIVATE void sqlite3Pragma( ** change. The only purpose is to provide an easy way to test ** the sqlite3AbsInt32() function. ** - ** PRAGMA [database.]page_count + ** PRAGMA [schema.]page_count ** ** Return the number of pages in the specified database. */ @@ -98341,8 +107340,8 @@ SQLITE_PRIVATE void sqlite3Pragma( } /* - ** PRAGMA [database.]locking_mode - ** PRAGMA [database.]locking_mode = (normal|exclusive) + ** PRAGMA [schema.]locking_mode + ** PRAGMA [schema.]locking_mode = (normal|exclusive) */ case PragTyp_LOCKING_MODE: { const char *zRet = "normal"; @@ -98382,25 +107381,20 @@ SQLITE_PRIVATE void sqlite3Pragma( if( eMode==PAGER_LOCKINGMODE_EXCLUSIVE ){ zRet = "exclusive"; } - sqlite3VdbeSetNumCols(v, 1); - sqlite3VdbeSetColName(v, 0, COLNAME_NAME, "locking_mode", SQLITE_STATIC); - sqlite3VdbeAddOp4(v, OP_String8, 0, 1, 0, zRet, 0); - sqlite3VdbeAddOp2(v, OP_ResultRow, 1, 1); + returnSingleText(v, "locking_mode", zRet); break; } /* - ** PRAGMA [database.]journal_mode - ** PRAGMA [database.]journal_mode = + ** PRAGMA [schema.]journal_mode + ** PRAGMA [schema.]journal_mode = ** (delete|persist|off|truncate|memory|wal|off) */ case PragTyp_JOURNAL_MODE: { int eMode; /* One of the PAGER_JOURNALMODE_XXX symbols */ int ii; /* Loop counter */ - sqlite3VdbeSetNumCols(v, 1); - sqlite3VdbeSetColName(v, 0, COLNAME_NAME, "journal_mode", SQLITE_STATIC); - + setOneColumnName(v, "journal_mode"); if( zRight==0 ){ /* If there is no "=MODE" part of the pragma, do a query for the ** current mode */ @@ -98433,8 +107427,8 @@ SQLITE_PRIVATE void sqlite3Pragma( } /* - ** PRAGMA [database.]journal_size_limit - ** PRAGMA [database.]journal_size_limit=N + ** PRAGMA [schema.]journal_size_limit + ** PRAGMA [schema.]journal_size_limit=N ** ** Get or set the size limit on rollback journal files. */ @@ -98442,19 +107436,19 @@ SQLITE_PRIVATE void sqlite3Pragma( Pager *pPager = sqlite3BtreePager(pDb->pBt); i64 iLimit = -2; if( zRight ){ - sqlite3Atoi64(zRight, &iLimit, sqlite3Strlen30(zRight), SQLITE_UTF8); + sqlite3DecOrHexToI64(zRight, &iLimit); if( iLimit<-1 ) iLimit = -1; } iLimit = sqlite3PagerJournalSizeLimit(pPager, iLimit); - returnSingleInt(pParse, "journal_size_limit", iLimit); + returnSingleInt(v, "journal_size_limit", iLimit); break; } #endif /* SQLITE_OMIT_PAGER_PRAGMAS */ /* - ** PRAGMA [database.]auto_vacuum - ** PRAGMA [database.]auto_vacuum=N + ** PRAGMA [schema.]auto_vacuum + ** PRAGMA [schema.]auto_vacuum=N ** ** Get or set the value of the database 'auto-vacuum' parameter. ** The value is one of: 0 NONE 1 FULL 2 INCREMENTAL @@ -98464,7 +107458,7 @@ SQLITE_PRIVATE void sqlite3Pragma( Btree *pBt = pDb->pBt; assert( pBt!=0 ); if( !zRight ){ - returnSingleInt(pParse, "auto_vacuum", sqlite3BtreeGetAutoVacuum(pBt)); + returnSingleInt(v, "auto_vacuum", sqlite3BtreeGetAutoVacuum(pBt)); }else{ int eAuto = getAutoVacuum(zRight); assert( eAuto>=0 && eAuto<=2 ); @@ -98505,7 +107499,7 @@ SQLITE_PRIVATE void sqlite3Pragma( #endif /* - ** PRAGMA [database.]incremental_vacuum(N) + ** PRAGMA [schema.]incremental_vacuum(N) ** ** Do N steps of incremental vacuuming on a database. */ @@ -98528,8 +107522,8 @@ SQLITE_PRIVATE void sqlite3Pragma( #ifndef SQLITE_OMIT_PAGER_PRAGMAS /* - ** PRAGMA [database.]cache_size - ** PRAGMA [database.]cache_size=N + ** PRAGMA [schema.]cache_size + ** PRAGMA [schema.]cache_size=N ** ** The first form reports the current local setting for the ** page cache size. The second form sets the local @@ -98541,7 +107535,7 @@ SQLITE_PRIVATE void sqlite3Pragma( case PragTyp_CACHE_SIZE: { assert( sqlite3SchemaMutexHeld(db, iDb, 0) ); if( !zRight ){ - returnSingleInt(pParse, "cache_size", pDb->pSchema->cache_size); + returnSingleInt(v, "cache_size", pDb->pSchema->cache_size); }else{ int size = sqlite3Atoi(zRight); pDb->pSchema->cache_size = size; @@ -98551,7 +107545,50 @@ SQLITE_PRIVATE void sqlite3Pragma( } /* - ** PRAGMA [database.]mmap_size(N) + ** PRAGMA [schema.]cache_spill + ** PRAGMA cache_spill=BOOLEAN + ** PRAGMA [schema.]cache_spill=N + ** + ** The first form reports the current local setting for the + ** page cache spill size. The second form turns cache spill on + ** or off. When turnning cache spill on, the size is set to the + ** current cache_size. The third form sets a spill size that + ** may be different form the cache size. + ** If N is positive then that is the + ** number of pages in the cache. If N is negative, then the + ** number of pages is adjusted so that the cache uses -N kibibytes + ** of memory. + ** + ** If the number of cache_spill pages is less then the number of + ** cache_size pages, no spilling occurs until the page count exceeds + ** the number of cache_size pages. + ** + ** The cache_spill=BOOLEAN setting applies to all attached schemas, + ** not just the schema specified. + */ + case PragTyp_CACHE_SPILL: { + assert( sqlite3SchemaMutexHeld(db, iDb, 0) ); + if( !zRight ){ + returnSingleInt(v, "cache_spill", + (db->flags & SQLITE_CacheSpill)==0 ? 0 : + sqlite3BtreeSetSpillSize(pDb->pBt,0)); + }else{ + int size = 1; + if( sqlite3GetInt32(zRight, &size) ){ + sqlite3BtreeSetSpillSize(pDb->pBt, size); + } + if( sqlite3GetBoolean(zRight, size!=0) ){ + db->flags |= SQLITE_CacheSpill; + }else{ + db->flags &= ~SQLITE_CacheSpill; + } + setAllPagerFlags(db); + } + break; + } + + /* + ** PRAGMA [schema.]mmap_size(N) ** ** Used to set mapping size limit. The mapping size limit is ** used to limit the aggregate size of all memory mapped regions of the @@ -98570,7 +107607,7 @@ SQLITE_PRIVATE void sqlite3Pragma( assert( sqlite3SchemaMutexHeld(db, iDb, 0) ); if( zRight ){ int ii; - sqlite3Atoi64(zRight, &sz, sqlite3Strlen30(zRight), SQLITE_UTF8); + sqlite3DecOrHexToI64(zRight, &sz); if( sz<0 ) sz = sqlite3GlobalConfig.szMmap; if( pId2->n==0 ) db->szMmap = sz; for(ii=db->nDb-1; ii>=0; ii--){ @@ -98586,7 +107623,7 @@ SQLITE_PRIVATE void sqlite3Pragma( rc = SQLITE_OK; #endif if( rc==SQLITE_OK ){ - returnSingleInt(pParse, "mmap_size", sz); + returnSingleInt(v, "mmap_size", sz); }else if( rc!=SQLITE_NOTFOUND ){ pParse->nErr++; pParse->rc = rc; @@ -98607,7 +107644,7 @@ SQLITE_PRIVATE void sqlite3Pragma( */ case PragTyp_TEMP_STORE: { if( !zRight ){ - returnSingleInt(pParse, "temp_store", db->temp_store); + returnSingleInt(v, "temp_store", db->temp_store); }else{ changeTempStorage(pParse, zRight); } @@ -98626,13 +107663,7 @@ SQLITE_PRIVATE void sqlite3Pragma( */ case PragTyp_TEMP_STORE_DIRECTORY: { if( !zRight ){ - if( sqlite3_temp_directory ){ - sqlite3VdbeSetNumCols(v, 1); - sqlite3VdbeSetColName(v, 0, COLNAME_NAME, - "temp_store_directory", SQLITE_STATIC); - sqlite3VdbeAddOp4(v, OP_String8, 0, 1, 0, sqlite3_temp_directory, 0); - sqlite3VdbeAddOp2(v, OP_ResultRow, 1, 1); - } + returnSingleText(v, "temp_store_directory", sqlite3_temp_directory); }else{ #ifndef SQLITE_OMIT_WSD if( zRight[0] ){ @@ -98676,13 +107707,7 @@ SQLITE_PRIVATE void sqlite3Pragma( */ case PragTyp_DATA_STORE_DIRECTORY: { if( !zRight ){ - if( sqlite3_data_directory ){ - sqlite3VdbeSetNumCols(v, 1); - sqlite3VdbeSetColName(v, 0, COLNAME_NAME, - "data_store_directory", SQLITE_STATIC); - sqlite3VdbeAddOp4(v, OP_String8, 0, 1, 0, sqlite3_data_directory, 0); - sqlite3VdbeAddOp2(v, OP_ResultRow, 1, 1); - } + returnSingleText(v, "data_store_directory", sqlite3_data_directory); }else{ #ifndef SQLITE_OMIT_WSD if( zRight[0] ){ @@ -98707,8 +107732,8 @@ SQLITE_PRIVATE void sqlite3Pragma( #if SQLITE_ENABLE_LOCKING_STYLE /* - ** PRAGMA [database.]lock_proxy_file - ** PRAGMA [database.]lock_proxy_file = ":auto:"|"lock_file_path" + ** PRAGMA [schema.]lock_proxy_file + ** PRAGMA [schema.]lock_proxy_file = ":auto:"|"lock_file_path" ** ** Return or set the value of the lock_proxy_file flag. Changing ** the value sets a specific file to be used for database access locks. @@ -98721,14 +107746,7 @@ SQLITE_PRIVATE void sqlite3Pragma( sqlite3_file *pFile = sqlite3PagerFile(pPager); sqlite3OsFileControlHint(pFile, SQLITE_GET_LOCKPROXYFILE, &proxy_file_path); - - if( proxy_file_path ){ - sqlite3VdbeSetNumCols(v, 1); - sqlite3VdbeSetColName(v, 0, COLNAME_NAME, - "lock_proxy_file", SQLITE_STATIC); - sqlite3VdbeAddOp4(v, OP_String8, 0, 1, 0, proxy_file_path, 0); - sqlite3VdbeAddOp2(v, OP_ResultRow, 1, 1); - } + returnSingleText(v, "lock_proxy_file", proxy_file_path); }else{ Pager *pPager = sqlite3BtreePager(pDb->pBt); sqlite3_file *pFile = sqlite3PagerFile(pPager); @@ -98750,8 +107768,8 @@ SQLITE_PRIVATE void sqlite3Pragma( #endif /* SQLITE_ENABLE_LOCKING_STYLE */ /* - ** PRAGMA [database.]synchronous - ** PRAGMA [database.]synchronous=OFF|ON|NORMAL|FULL + ** PRAGMA [schema.]synchronous + ** PRAGMA [schema.]synchronous=OFF|ON|NORMAL|FULL ** ** Return or set the local value of the synchronous flag. Changing ** the local value does not make changes to the disk file and the @@ -98760,13 +107778,15 @@ SQLITE_PRIVATE void sqlite3Pragma( */ case PragTyp_SYNCHRONOUS: { if( !zRight ){ - returnSingleInt(pParse, "synchronous", pDb->safety_level-1); + returnSingleInt(v, "synchronous", pDb->safety_level-1); }else{ if( !db->autoCommit ){ sqlite3ErrorMsg(pParse, "Safety level may not be changed inside a transaction"); }else{ - pDb->safety_level = getSafetyLevel(zRight,0,1)+1; + int iLevel = (getSafetyLevel(zRight,0,1)+1) & PAGER_SYNCHRONOUS_MASK; + if( iLevel==0 ) iLevel = 1; + pDb->safety_level = iLevel; setAllPagerFlags(db); } } @@ -98777,15 +107797,20 @@ SQLITE_PRIVATE void sqlite3Pragma( #ifndef SQLITE_OMIT_FLAG_PRAGMAS case PragTyp_FLAG: { if( zRight==0 ){ - returnSingleInt(pParse, aPragmaNames[mid].zName, - (db->flags & aPragmaNames[mid].iArg)!=0 ); + returnSingleInt(v, pPragma->zName, (db->flags & pPragma->iArg)!=0 ); }else{ - int mask = aPragmaNames[mid].iArg; /* Mask of bits to set or clear. */ + int mask = pPragma->iArg; /* Mask of bits to set or clear. */ if( db->autoCommit==0 ){ /* Foreign key support may not be enabled or disabled while not ** in auto-commit mode. */ mask &= ~(SQLITE_ForeignKeys); } +#if SQLITE_USER_AUTHENTICATION + if( db->auth.authLevel==UAUTH_User ){ + /* Do not allow non-admin users to modify the schema arbitrarily */ + mask &= ~(SQLITE_WriteSchema); + } +#endif if( sqlite3GetBoolean(zRight, 0) ){ db->flags |= mask; @@ -98822,43 +107847,36 @@ SQLITE_PRIVATE void sqlite3Pragma( Table *pTab; pTab = sqlite3FindTable(db, zRight, zDb); if( pTab ){ + static const char *azCol[] = { + "cid", "name", "type", "notnull", "dflt_value", "pk" + }; int i, k; int nHidden = 0; Column *pCol; Index *pPk = sqlite3PrimaryKeyIndex(pTab); - sqlite3VdbeSetNumCols(v, 6); pParse->nMem = 6; sqlite3CodeVerifySchema(pParse, iDb); - sqlite3VdbeSetColName(v, 0, COLNAME_NAME, "cid", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 1, COLNAME_NAME, "name", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 2, COLNAME_NAME, "type", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 3, COLNAME_NAME, "notnull", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 4, COLNAME_NAME, "dflt_value", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 5, COLNAME_NAME, "pk", SQLITE_STATIC); + setAllColumnNames(v, 6, azCol); assert( 6==ArraySize(azCol) ); sqlite3ViewGetColumnNames(pParse, pTab); for(i=0, pCol=pTab->aCol; inCol; i++, pCol++){ if( IsHiddenColumn(pCol) ){ nHidden++; continue; } - sqlite3VdbeAddOp2(v, OP_Integer, i-nHidden, 1); - sqlite3VdbeAddOp4(v, OP_String8, 0, 2, 0, pCol->zName, 0); - sqlite3VdbeAddOp4(v, OP_String8, 0, 3, 0, - pCol->zType ? pCol->zType : "", 0); - sqlite3VdbeAddOp2(v, OP_Integer, (pCol->notNull ? 1 : 0), 4); - if( pCol->zDflt ){ - sqlite3VdbeAddOp4(v, OP_String8, 0, 5, 0, (char*)pCol->zDflt, 0); - }else{ - sqlite3VdbeAddOp2(v, OP_Null, 0, 5); - } if( (pCol->colFlags & COLFLAG_PRIMKEY)==0 ){ k = 0; }else if( pPk==0 ){ k = 1; }else{ - for(k=1; ALWAYS(k<=pTab->nCol) && pPk->aiColumn[k-1]!=i; k++){} + for(k=1; k<=pTab->nCol && pPk->aiColumn[k-1]!=i; k++){} } - sqlite3VdbeAddOp2(v, OP_Integer, k, 6); + sqlite3VdbeMultiLoad(v, 1, "issisi", + i-nHidden, + pCol->zName, + pCol->zType ? pCol->zType : "", + pCol->notNull ? 1 : 0, + pCol->zDflt, + k); sqlite3VdbeAddOp2(v, OP_ResultRow, 1, 6); } } @@ -98866,31 +107884,26 @@ SQLITE_PRIVATE void sqlite3Pragma( break; case PragTyp_STATS: { + static const char *azCol[] = { "table", "index", "width", "height" }; Index *pIdx; HashElem *i; v = sqlite3GetVdbe(pParse); - sqlite3VdbeSetNumCols(v, 4); pParse->nMem = 4; sqlite3CodeVerifySchema(pParse, iDb); - sqlite3VdbeSetColName(v, 0, COLNAME_NAME, "table", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 1, COLNAME_NAME, "index", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 2, COLNAME_NAME, "width", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 3, COLNAME_NAME, "height", SQLITE_STATIC); + setAllColumnNames(v, 4, azCol); assert( 4==ArraySize(azCol) ); for(i=sqliteHashFirst(&pDb->pSchema->tblHash); i; i=sqliteHashNext(i)){ Table *pTab = sqliteHashData(i); - sqlite3VdbeAddOp4(v, OP_String8, 0, 1, 0, pTab->zName, 0); - sqlite3VdbeAddOp2(v, OP_Null, 0, 2); - sqlite3VdbeAddOp2(v, OP_Integer, - (int)sqlite3LogEstToInt(pTab->szTabRow), 3); - sqlite3VdbeAddOp2(v, OP_Integer, - (int)sqlite3LogEstToInt(pTab->nRowLogEst), 4); + sqlite3VdbeMultiLoad(v, 1, "ssii", + pTab->zName, + 0, + (int)sqlite3LogEstToInt(pTab->szTabRow), + (int)sqlite3LogEstToInt(pTab->nRowLogEst)); sqlite3VdbeAddOp2(v, OP_ResultRow, 1, 4); for(pIdx=pTab->pIndex; pIdx; pIdx=pIdx->pNext){ - sqlite3VdbeAddOp4(v, OP_String8, 0, 2, 0, pIdx->zName, 0); - sqlite3VdbeAddOp2(v, OP_Integer, - (int)sqlite3LogEstToInt(pIdx->szIdxRow), 3); - sqlite3VdbeAddOp2(v, OP_Integer, - (int)sqlite3LogEstToInt(pIdx->aiRowLogEst[0]), 4); + sqlite3VdbeMultiLoad(v, 2, "sii", + pIdx->zName, + (int)sqlite3LogEstToInt(pIdx->szIdxRow), + (int)sqlite3LogEstToInt(pIdx->aiRowLogEst[0])); sqlite3VdbeAddOp2(v, OP_ResultRow, 1, 4); } } @@ -98902,21 +107915,35 @@ SQLITE_PRIVATE void sqlite3Pragma( Table *pTab; pIdx = sqlite3FindIndex(db, zRight, zDb); if( pIdx ){ + static const char *azCol[] = { + "seqno", "cid", "name", "desc", "coll", "key" + }; int i; + int mx; + if( pPragma->iArg ){ + /* PRAGMA index_xinfo (newer version with more rows and columns) */ + mx = pIdx->nColumn; + pParse->nMem = 6; + }else{ + /* PRAGMA index_info (legacy version) */ + mx = pIdx->nKeyCol; + pParse->nMem = 3; + } pTab = pIdx->pTable; - sqlite3VdbeSetNumCols(v, 3); - pParse->nMem = 3; sqlite3CodeVerifySchema(pParse, iDb); - sqlite3VdbeSetColName(v, 0, COLNAME_NAME, "seqno", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 1, COLNAME_NAME, "cid", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 2, COLNAME_NAME, "name", SQLITE_STATIC); - for(i=0; inKeyCol; i++){ + assert( pParse->nMem<=ArraySize(azCol) ); + setAllColumnNames(v, pParse->nMem, azCol); + for(i=0; iaiColumn[i]; - sqlite3VdbeAddOp2(v, OP_Integer, i, 1); - sqlite3VdbeAddOp2(v, OP_Integer, cnum, 2); - assert( pTab->nCol>cnum ); - sqlite3VdbeAddOp4(v, OP_String8, 0, 3, 0, pTab->aCol[cnum].zName, 0); - sqlite3VdbeAddOp2(v, OP_ResultRow, 1, 3); + sqlite3VdbeMultiLoad(v, 1, "iis", i, cnum, + cnum<0 ? 0 : pTab->aCol[cnum].zName); + if( pPragma->iArg ){ + sqlite3VdbeMultiLoad(v, 4, "isi", + pIdx->aSortOrder[i], + pIdx->azColl[i], + inKeyCol); + } + sqlite3VdbeAddOp2(v, OP_ResultRow, 1, pParse->nMem); } } } @@ -98928,53 +107955,53 @@ SQLITE_PRIVATE void sqlite3Pragma( int i; pTab = sqlite3FindTable(db, zRight, zDb); if( pTab ){ + static const char *azCol[] = { + "seq", "name", "unique", "origin", "partial" + }; v = sqlite3GetVdbe(pParse); - sqlite3VdbeSetNumCols(v, 3); - pParse->nMem = 3; + pParse->nMem = 5; sqlite3CodeVerifySchema(pParse, iDb); - sqlite3VdbeSetColName(v, 0, COLNAME_NAME, "seq", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 1, COLNAME_NAME, "name", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 2, COLNAME_NAME, "unique", SQLITE_STATIC); + setAllColumnNames(v, 5, azCol); assert( 5==ArraySize(azCol) ); for(pIdx=pTab->pIndex, i=0; pIdx; pIdx=pIdx->pNext, i++){ - sqlite3VdbeAddOp2(v, OP_Integer, i, 1); - sqlite3VdbeAddOp4(v, OP_String8, 0, 2, 0, pIdx->zName, 0); - sqlite3VdbeAddOp2(v, OP_Integer, pIdx->onError!=OE_None, 3); - sqlite3VdbeAddOp2(v, OP_ResultRow, 1, 3); + const char *azOrigin[] = { "c", "u", "pk" }; + sqlite3VdbeMultiLoad(v, 1, "isisi", + i, + pIdx->zName, + IsUniqueIndex(pIdx), + azOrigin[pIdx->idxType], + pIdx->pPartIdxWhere!=0); + sqlite3VdbeAddOp2(v, OP_ResultRow, 1, 5); } } } break; case PragTyp_DATABASE_LIST: { + static const char *azCol[] = { "seq", "name", "file" }; int i; - sqlite3VdbeSetNumCols(v, 3); pParse->nMem = 3; - sqlite3VdbeSetColName(v, 0, COLNAME_NAME, "seq", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 1, COLNAME_NAME, "name", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 2, COLNAME_NAME, "file", SQLITE_STATIC); + setAllColumnNames(v, 3, azCol); assert( 3==ArraySize(azCol) ); for(i=0; inDb; i++){ if( db->aDb[i].pBt==0 ) continue; assert( db->aDb[i].zName!=0 ); - sqlite3VdbeAddOp2(v, OP_Integer, i, 1); - sqlite3VdbeAddOp4(v, OP_String8, 0, 2, 0, db->aDb[i].zName, 0); - sqlite3VdbeAddOp4(v, OP_String8, 0, 3, 0, - sqlite3BtreeGetFilename(db->aDb[i].pBt), 0); + sqlite3VdbeMultiLoad(v, 1, "iss", + i, + db->aDb[i].zName, + sqlite3BtreeGetFilename(db->aDb[i].pBt)); sqlite3VdbeAddOp2(v, OP_ResultRow, 1, 3); } } break; case PragTyp_COLLATION_LIST: { + static const char *azCol[] = { "seq", "name" }; int i = 0; HashElem *p; - sqlite3VdbeSetNumCols(v, 2); pParse->nMem = 2; - sqlite3VdbeSetColName(v, 0, COLNAME_NAME, "seq", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 1, COLNAME_NAME, "name", SQLITE_STATIC); + setAllColumnNames(v, 2, azCol); assert( 2==ArraySize(azCol) ); for(p=sqliteHashFirst(&db->aCollSeq); p; p=sqliteHashNext(p)){ CollSeq *pColl = (CollSeq *)sqliteHashData(p); - sqlite3VdbeAddOp2(v, OP_Integer, i++, 1); - sqlite3VdbeAddOp4(v, OP_String8, 0, 2, 0, pColl->zName, 0); + sqlite3VdbeMultiLoad(v, 1, "is", i++, pColl->zName); sqlite3VdbeAddOp2(v, OP_ResultRow, 1, 2); } } @@ -98990,33 +108017,26 @@ SQLITE_PRIVATE void sqlite3Pragma( v = sqlite3GetVdbe(pParse); pFK = pTab->pFKey; if( pFK ){ + static const char *azCol[] = { + "id", "seq", "table", "from", "to", "on_update", "on_delete", + "match" + }; int i = 0; - sqlite3VdbeSetNumCols(v, 8); pParse->nMem = 8; sqlite3CodeVerifySchema(pParse, iDb); - sqlite3VdbeSetColName(v, 0, COLNAME_NAME, "id", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 1, COLNAME_NAME, "seq", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 2, COLNAME_NAME, "table", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 3, COLNAME_NAME, "from", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 4, COLNAME_NAME, "to", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 5, COLNAME_NAME, "on_update", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 6, COLNAME_NAME, "on_delete", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 7, COLNAME_NAME, "match", SQLITE_STATIC); + setAllColumnNames(v, 8, azCol); assert( 8==ArraySize(azCol) ); while(pFK){ int j; for(j=0; jnCol; j++){ - char *zCol = pFK->aCol[j].zCol; - char *zOnDelete = (char *)actionName(pFK->aAction[0]); - char *zOnUpdate = (char *)actionName(pFK->aAction[1]); - sqlite3VdbeAddOp2(v, OP_Integer, i, 1); - sqlite3VdbeAddOp2(v, OP_Integer, j, 2); - sqlite3VdbeAddOp4(v, OP_String8, 0, 3, 0, pFK->zTo, 0); - sqlite3VdbeAddOp4(v, OP_String8, 0, 4, 0, - pTab->aCol[pFK->aCol[j].iFrom].zName, 0); - sqlite3VdbeAddOp4(v, zCol ? OP_String8 : OP_Null, 0, 5, 0, zCol, 0); - sqlite3VdbeAddOp4(v, OP_String8, 0, 6, 0, zOnUpdate, 0); - sqlite3VdbeAddOp4(v, OP_String8, 0, 7, 0, zOnDelete, 0); - sqlite3VdbeAddOp4(v, OP_String8, 0, 8, 0, "NONE", 0); + sqlite3VdbeMultiLoad(v, 1, "iissssss", + i, + j, + pFK->zTo, + pTab->aCol[pFK->aCol[j].iFrom].zName, + pFK->aCol[j].zCol, + actionName(pFK->aAction[1]), /* ON UPDATE */ + actionName(pFK->aAction[0]), /* ON DELETE */ + "NONE"); sqlite3VdbeAddOp2(v, OP_ResultRow, 1, 8); } ++i; @@ -99045,17 +108065,14 @@ SQLITE_PRIVATE void sqlite3Pragma( int addrTop; /* Top of a loop checking foreign keys */ int addrOk; /* Jump here if the key is OK */ int *aiCols; /* child to parent column mapping */ + static const char *azCol[] = { "table", "rowid", "parent", "fkid" }; regResult = pParse->nMem+1; pParse->nMem += 4; regKey = ++pParse->nMem; regRow = ++pParse->nMem; v = sqlite3GetVdbe(pParse); - sqlite3VdbeSetNumCols(v, 4); - sqlite3VdbeSetColName(v, 0, COLNAME_NAME, "table", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 1, COLNAME_NAME, "rowid", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 2, COLNAME_NAME, "parent", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 3, COLNAME_NAME, "fkid", SQLITE_STATIC); + setAllColumnNames(v, 4, azCol); assert( 4==ArraySize(azCol) ); sqlite3CodeVerifySchema(pParse, iDb); k = sqliteHashFirst(&db->aDb[iDb].pSchema->tblHash); while( k ){ @@ -99070,8 +108087,7 @@ SQLITE_PRIVATE void sqlite3Pragma( sqlite3TableLock(pParse, iDb, pTab->tnum, 0, pTab->zName); if( pTab->nCol+regRow>pParse->nMem ) pParse->nMem = pTab->nCol + regRow; sqlite3OpenTable(pParse, 0, iDb, pTab, OP_OpenRead); - sqlite3VdbeAddOp4(v, OP_String8, 0, regResult, 0, pTab->zName, - P4_TRANSIENT); + sqlite3VdbeLoadString(v, regResult, pTab->zName); for(i=1, pFK=pTab->pFKey; pFK; i++, pFK=pFK->pNextFrom){ pParent = sqlite3FindTable(db, pFK->zTo, zDb); if( pParent==0 ) continue; @@ -99116,7 +108132,7 @@ SQLITE_PRIVATE void sqlite3Pragma( sqlite3VdbeAddOp2(v, OP_Rowid, 0, regRow); } sqlite3VdbeAddOp3(v, OP_NotExists, i, 0, regRow); VdbeCoverage(v); - sqlite3VdbeAddOp2(v, OP_Goto, 0, addrOk); + sqlite3VdbeGoto(v, addrOk); sqlite3VdbeJumpHere(v, sqlite3VdbeCurrentAddr(v)-2); }else{ for(j=0; jnCol; j++){ @@ -99126,15 +108142,13 @@ SQLITE_PRIVATE void sqlite3Pragma( } if( pParent ){ sqlite3VdbeAddOp4(v, OP_MakeRecord, regRow, pFK->nCol, regKey, - sqlite3IndexAffinityStr(v,pIdx), pFK->nCol); + sqlite3IndexAffinityStr(db,pIdx), pFK->nCol); sqlite3VdbeAddOp4Int(v, OP_Found, i, addrOk, regKey, 0); VdbeCoverage(v); } } sqlite3VdbeAddOp2(v, OP_Rowid, 0, regResult+1); - sqlite3VdbeAddOp4(v, OP_String8, 0, regResult+2, 0, - pFK->zTo, P4_TRANSIENT); - sqlite3VdbeAddOp2(v, OP_Integer, i-1, regResult+3); + sqlite3VdbeMultiLoad(v, regResult+2, "si", pFK->zTo, i-1); sqlite3VdbeAddOp2(v, OP_ResultRow, regResult, 4); sqlite3VdbeResolveLabel(v, addrOk); sqlite3DbFree(db, aiCols); @@ -99151,7 +108165,7 @@ SQLITE_PRIVATE void sqlite3Pragma( case PragTyp_PARSER_TRACE: { if( zRight ){ if( sqlite3GetBoolean(zRight, 0) ){ - sqlite3ParserTrace(stderr, "parser: "); + sqlite3ParserTrace(stdout, "parser: "); }else{ sqlite3ParserTrace(0, 0); } @@ -99189,7 +108203,7 @@ SQLITE_PRIVATE void sqlite3Pragma( static const int iLn = VDBE_OFFSET_LINENO(2); static const VdbeOpList endCode[] = { { OP_AddImm, 1, 0, 0}, /* 0 */ - { OP_IfNeg, 1, 0, 0}, /* 1 */ + { OP_If, 1, 0, 0}, /* 1 */ { OP_String8, 0, 3, 0}, /* 2 */ { OP_ResultRow, 3, 1, 0}, }; @@ -99211,8 +108225,7 @@ SQLITE_PRIVATE void sqlite3Pragma( /* Initialize the VDBE program */ pParse->nMem = 6; - sqlite3VdbeSetNumCols(v, 1); - sqlite3VdbeSetColName(v, 0, COLNAME_NAME, "integrity_check", SQLITE_STATIC); + setOneColumnName(v, "integrity_check"); /* Set the maximum error count */ mxErr = SQLITE_INTEGRITY_CHECK_ERROR_MAX; @@ -99293,7 +108306,7 @@ SQLITE_PRIVATE void sqlite3Pragma( sqlite3VdbeAddOp2(v, OP_Halt, 0, 0); sqlite3VdbeJumpHere(v, addr); sqlite3ExprCacheClear(pParse); - sqlite3OpenTableAndIndices(pParse, pTab, OP_OpenRead, + sqlite3OpenTableAndIndices(pParse, pTab, OP_OpenRead, 0, 1, 0, &iDataCur, &iIdxCur); sqlite3VdbeAddOp2(v, OP_Integer, 0, 7); for(j=0, pIdx=pTab->pIndex; pIdx; pIdx=pIdx->pNext, j++){ @@ -99302,35 +108315,79 @@ SQLITE_PRIVATE void sqlite3Pragma( pParse->nMem = MAX(pParse->nMem, 8+j); sqlite3VdbeAddOp2(v, OP_Rewind, iDataCur, 0); VdbeCoverage(v); loopTop = sqlite3VdbeAddOp2(v, OP_AddImm, 7, 1); + /* Verify that all NOT NULL columns really are NOT NULL */ + for(j=0; jnCol; j++){ + char *zErr; + int jmp2, jmp3; + if( j==pTab->iPKey ) continue; + if( pTab->aCol[j].notNull==0 ) continue; + sqlite3ExprCodeGetColumnOfTable(v, pTab, iDataCur, j, 3); + sqlite3VdbeChangeP5(v, OPFLAG_TYPEOFARG); + jmp2 = sqlite3VdbeAddOp1(v, OP_NotNull, 3); VdbeCoverage(v); + sqlite3VdbeAddOp2(v, OP_AddImm, 1, -1); /* Decrement error limit */ + zErr = sqlite3MPrintf(db, "NULL value in %s.%s", pTab->zName, + pTab->aCol[j].zName); + sqlite3VdbeAddOp4(v, OP_String8, 0, 3, 0, zErr, P4_DYNAMIC); + sqlite3VdbeAddOp2(v, OP_ResultRow, 3, 1); + jmp3 = sqlite3VdbeAddOp1(v, OP_IfPos, 1); VdbeCoverage(v); + sqlite3VdbeAddOp0(v, OP_Halt); + sqlite3VdbeJumpHere(v, jmp2); + sqlite3VdbeJumpHere(v, jmp3); + } + /* Validate index entries for the current row */ for(j=0, pIdx=pTab->pIndex; pIdx; pIdx=pIdx->pNext, j++){ - int jmp2, jmp3, jmp4; + int jmp2, jmp3, jmp4, jmp5; + int ckUniq = sqlite3VdbeMakeLabel(v); if( pPk==pIdx ) continue; r1 = sqlite3GenerateIndexKey(pParse, pIdx, iDataCur, 0, 0, &jmp3, pPrior, r1); pPrior = pIdx; sqlite3VdbeAddOp2(v, OP_AddImm, 8+j, 1); /* increment entry count */ - jmp2 = sqlite3VdbeAddOp4Int(v, OP_Found, iIdxCur+j, 0, r1, + /* Verify that an index entry exists for the current table row */ + jmp2 = sqlite3VdbeAddOp4Int(v, OP_Found, iIdxCur+j, ckUniq, r1, pIdx->nColumn); VdbeCoverage(v); sqlite3VdbeAddOp2(v, OP_AddImm, 1, -1); /* Decrement error limit */ - sqlite3VdbeAddOp4(v, OP_String8, 0, 3, 0, "row ", P4_STATIC); + sqlite3VdbeLoadString(v, 3, "row "); sqlite3VdbeAddOp3(v, OP_Concat, 7, 3, 3); - sqlite3VdbeAddOp4(v, OP_String8, 0, 4, 0, " missing from index ", - P4_STATIC); + sqlite3VdbeLoadString(v, 4, " missing from index "); sqlite3VdbeAddOp3(v, OP_Concat, 4, 3, 3); - sqlite3VdbeAddOp4(v, OP_String8, 0, 4, 0, pIdx->zName, P4_TRANSIENT); + jmp5 = sqlite3VdbeLoadString(v, 4, pIdx->zName); sqlite3VdbeAddOp3(v, OP_Concat, 4, 3, 3); sqlite3VdbeAddOp2(v, OP_ResultRow, 3, 1); jmp4 = sqlite3VdbeAddOp1(v, OP_IfPos, 1); VdbeCoverage(v); sqlite3VdbeAddOp0(v, OP_Halt); - sqlite3VdbeJumpHere(v, jmp4); sqlite3VdbeJumpHere(v, jmp2); + /* For UNIQUE indexes, verify that only one entry exists with the + ** current key. The entry is unique if (1) any column is NULL + ** or (2) the next entry has a different key */ + if( IsUniqueIndex(pIdx) ){ + int uniqOk = sqlite3VdbeMakeLabel(v); + int jmp6; + int kk; + for(kk=0; kknKeyCol; kk++){ + int iCol = pIdx->aiColumn[kk]; + assert( iCol!=XN_ROWID && iColnCol ); + if( iCol>=0 && pTab->aCol[iCol].notNull ) continue; + sqlite3VdbeAddOp2(v, OP_IsNull, r1+kk, uniqOk); + VdbeCoverage(v); + } + jmp6 = sqlite3VdbeAddOp1(v, OP_Next, iIdxCur+j); VdbeCoverage(v); + sqlite3VdbeGoto(v, uniqOk); + sqlite3VdbeJumpHere(v, jmp6); + sqlite3VdbeAddOp4Int(v, OP_IdxGT, iIdxCur+j, uniqOk, r1, + pIdx->nKeyCol); VdbeCoverage(v); + sqlite3VdbeAddOp2(v, OP_AddImm, 1, -1); /* Decrement error limit */ + sqlite3VdbeLoadString(v, 3, "non-unique entry in index "); + sqlite3VdbeGoto(v, jmp5); + sqlite3VdbeResolveLabel(v, uniqOk); + } + sqlite3VdbeJumpHere(v, jmp4); sqlite3ResolvePartIdxLabel(pParse, jmp3); } sqlite3VdbeAddOp2(v, OP_Next, iDataCur, loopTop); VdbeCoverage(v); sqlite3VdbeJumpHere(v, loopTop-1); #ifndef SQLITE_OMIT_BTREECOUNT - sqlite3VdbeAddOp4(v, OP_String8, 0, 2, 0, - "wrong # of entries in index ", P4_STATIC); + sqlite3VdbeLoadString(v, 2, "wrong # of entries in index "); for(j=0, pIdx=pTab->pIndex; pIdx; pIdx=pIdx->pNext, j++){ if( pPk==pIdx ) continue; addr = sqlite3VdbeCurrentAddr(v); @@ -99340,7 +108397,7 @@ SQLITE_PRIVATE void sqlite3Pragma( sqlite3VdbeAddOp3(v, OP_Eq, 8+j, addr+8, 3); VdbeCoverage(v); sqlite3VdbeChangeP5(v, SQLITE_NOTNULL); sqlite3VdbeAddOp2(v, OP_AddImm, 1, -1); - sqlite3VdbeAddOp4(v, OP_String8, 0, 3, 0, pIdx->zName, P4_TRANSIENT); + sqlite3VdbeLoadString(v, 3, pIdx->zName); sqlite3VdbeAddOp3(v, OP_Concat, 3, 2, 7); sqlite3VdbeAddOp2(v, OP_ResultRow, 7, 1); } @@ -99396,14 +108453,10 @@ SQLITE_PRIVATE void sqlite3Pragma( const struct EncName *pEnc; if( !zRight ){ /* "PRAGMA encoding" */ if( sqlite3ReadSchema(pParse) ) goto pragma_out; - sqlite3VdbeSetNumCols(v, 1); - sqlite3VdbeSetColName(v, 0, COLNAME_NAME, "encoding", SQLITE_STATIC); - sqlite3VdbeAddOp2(v, OP_String8, 0, 1); assert( encnames[SQLITE_UTF8].enc==SQLITE_UTF8 ); assert( encnames[SQLITE_UTF16LE].enc==SQLITE_UTF16LE ); assert( encnames[SQLITE_UTF16BE].enc==SQLITE_UTF16BE ); - sqlite3VdbeChangeP4(v, -1, encnames[ENC(pParse->db)].zName, P4_STATIC); - sqlite3VdbeAddOp2(v, OP_ResultRow, 1, 1); + returnSingleText(v, "encoding", encnames[ENC(pParse->db)].zName); }else{ /* "PRAGMA encoding = XXX" */ /* Only change the value of sqlite.enc if the database handle is not ** initialized. If the main database exists, the new sqlite.enc value @@ -99416,7 +108469,8 @@ SQLITE_PRIVATE void sqlite3Pragma( ){ for(pEnc=&encnames[0]; pEnc->zName; pEnc++){ if( 0==sqlite3StrICmp(zRight, pEnc->zName) ){ - ENC(pParse->db) = pEnc->enc ? pEnc->enc : SQLITE_UTF16NATIVE; + SCHEMA_ENC(db) = ENC(db) = + pEnc->enc ? pEnc->enc : SQLITE_UTF16NATIVE; break; } } @@ -99431,16 +108485,16 @@ SQLITE_PRIVATE void sqlite3Pragma( #ifndef SQLITE_OMIT_SCHEMA_VERSION_PRAGMAS /* - ** PRAGMA [database.]schema_version - ** PRAGMA [database.]schema_version = + ** PRAGMA [schema.]schema_version + ** PRAGMA [schema.]schema_version = ** - ** PRAGMA [database.]user_version - ** PRAGMA [database.]user_version = + ** PRAGMA [schema.]user_version + ** PRAGMA [schema.]user_version = ** - ** PRAGMA [database.]freelist_count = + ** PRAGMA [schema.]freelist_count = ** - ** PRAGMA [database.]application_id - ** PRAGMA [database.]application_id = + ** PRAGMA [schema.]application_id + ** PRAGMA [schema.]application_id = ** ** The pragma's schema_version and user_version are used to set or get ** the value of the schema-version and user-version, respectively. Both @@ -99461,24 +108515,9 @@ SQLITE_PRIVATE void sqlite3Pragma( ** applications for any purpose. */ case PragTyp_HEADER_VALUE: { - int iCookie; /* Cookie index. 1 for schema-cookie, 6 for user-cookie. */ + int iCookie = pPragma->iArg; /* Which cookie to read or write */ sqlite3VdbeUsesBtree(v, iDb); - switch( zLeft[0] ){ - case 'a': case 'A': - iCookie = BTREE_APPLICATION_ID; - break; - case 'f': case 'F': - iCookie = BTREE_FREE_PAGE_COUNT; - break; - case 's': case 'S': - iCookie = BTREE_SCHEMA_VERSION; - break; - default: - iCookie = BTREE_USER_VERSION; - break; - } - - if( zRight && iCookie!=BTREE_FREE_PAGE_COUNT ){ + if( zRight && (pPragma->mPragFlag & PragFlag_ReadOnly)==0 ){ /* Write the specified cookie value */ static const VdbeOpList setCookie[] = { { OP_Transaction, 0, 1, 0}, /* 0 */ @@ -99518,11 +108557,10 @@ SQLITE_PRIVATE void sqlite3Pragma( case PragTyp_COMPILE_OPTIONS: { int i = 0; const char *zOpt; - sqlite3VdbeSetNumCols(v, 1); pParse->nMem = 1; - sqlite3VdbeSetColName(v, 0, COLNAME_NAME, "compile_option", SQLITE_STATIC); + setOneColumnName(v, "compile_option"); while( (zOpt = sqlite3_compileoption_get(i++))!=0 ){ - sqlite3VdbeAddOp4(v, OP_String8, 0, 1, 0, zOpt, 0); + sqlite3VdbeLoadString(v, 1, zOpt); sqlite3VdbeAddOp2(v, OP_ResultRow, 1, 1); } } @@ -99531,11 +108569,12 @@ SQLITE_PRIVATE void sqlite3Pragma( #ifndef SQLITE_OMIT_WAL /* - ** PRAGMA [database.]wal_checkpoint = passive|full|restart + ** PRAGMA [schema.]wal_checkpoint = passive|full|restart|truncate ** ** Checkpoint the database. */ case PragTyp_WAL_CHECKPOINT: { + static const char *azCol[] = { "busy", "log", "checkpointed" }; int iBt = (pId2->z?iDb:SQLITE_MAX_ATTACHED); int eMode = SQLITE_CHECKPOINT_PASSIVE; if( zRight ){ @@ -99543,14 +108582,12 @@ SQLITE_PRIVATE void sqlite3Pragma( eMode = SQLITE_CHECKPOINT_FULL; }else if( sqlite3StrICmp(zRight, "restart")==0 ){ eMode = SQLITE_CHECKPOINT_RESTART; + }else if( sqlite3StrICmp(zRight, "truncate")==0 ){ + eMode = SQLITE_CHECKPOINT_TRUNCATE; } } - sqlite3VdbeSetNumCols(v, 3); + setAllColumnNames(v, 3, azCol); assert( 3==ArraySize(azCol) ); pParse->nMem = 3; - sqlite3VdbeSetColName(v, 0, COLNAME_NAME, "busy", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 1, COLNAME_NAME, "log", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 2, COLNAME_NAME, "checkpointed", SQLITE_STATIC); - sqlite3VdbeAddOp3(v, OP_Checkpoint, iBt, eMode, 1); sqlite3VdbeAddOp2(v, OP_ResultRow, 1, 3); } @@ -99568,7 +108605,7 @@ SQLITE_PRIVATE void sqlite3Pragma( if( zRight ){ sqlite3_wal_autocheckpoint(db, sqlite3Atoi(zRight)); } - returnSingleInt(pParse, "wal_autocheckpoint", + returnSingleInt(v, "wal_autocheckpoint", db->xWalCallback==sqlite3WalDefaultHook ? SQLITE_PTR_TO_INT(db->pWalArg) : 0); } @@ -99578,8 +108615,9 @@ SQLITE_PRIVATE void sqlite3Pragma( /* ** PRAGMA shrink_memory ** - ** This pragma attempts to free as much memory as possible from the - ** current database connection. + ** IMPLEMENTATION-OF: R-23445-46109 This pragma causes the database + ** connection on which it is invoked to free up as much memory as it + ** can, by calling sqlite3_db_release_memory(). */ case PragTyp_SHRINK_MEMORY: { sqlite3_db_release_memory(db); @@ -99596,11 +108634,11 @@ SQLITE_PRIVATE void sqlite3Pragma( ** disables the timeout. */ /*case PragTyp_BUSY_TIMEOUT*/ default: { - assert( aPragmaNames[mid].ePragTyp==PragTyp_BUSY_TIMEOUT ); + assert( pPragma->ePragTyp==PragTyp_BUSY_TIMEOUT ); if( zRight ){ sqlite3_busy_timeout(db, sqlite3Atoi(zRight)); } - returnSingleInt(pParse, "timeout", db->busyTimeout); + returnSingleInt(v, "timeout", db->busyTimeout); break; } @@ -99608,15 +108646,39 @@ SQLITE_PRIVATE void sqlite3Pragma( ** PRAGMA soft_heap_limit ** PRAGMA soft_heap_limit = N ** - ** Call sqlite3_soft_heap_limit64(N). Return the result. If N is omitted, - ** use -1. + ** IMPLEMENTATION-OF: R-26343-45930 This pragma invokes the + ** sqlite3_soft_heap_limit64() interface with the argument N, if N is + ** specified and is a non-negative integer. + ** IMPLEMENTATION-OF: R-64451-07163 The soft_heap_limit pragma always + ** returns the same integer that would be returned by the + ** sqlite3_soft_heap_limit64(-1) C-language function. */ case PragTyp_SOFT_HEAP_LIMIT: { sqlite3_int64 N; - if( zRight && sqlite3Atoi64(zRight, &N, 1000000, SQLITE_UTF8)==SQLITE_OK ){ + if( zRight && sqlite3DecOrHexToI64(zRight, &N)==SQLITE_OK ){ sqlite3_soft_heap_limit64(N); } - returnSingleInt(pParse, "soft_heap_limit", sqlite3_soft_heap_limit64(-1)); + returnSingleInt(v, "soft_heap_limit", sqlite3_soft_heap_limit64(-1)); + break; + } + + /* + ** PRAGMA threads + ** PRAGMA threads = N + ** + ** Configure the maximum number of worker threads. Return the new + ** maximum, which might be less than requested. + */ + case PragTyp_THREADS: { + sqlite3_int64 N; + if( zRight + && sqlite3DecOrHexToI64(zRight, &N)==SQLITE_OK + && N>=0 + ){ + sqlite3_limit(db, SQLITE_LIMIT_WORKER_THREADS, (int)(N&0x7fffffff)); + } + returnSingleInt(v, "threads", + sqlite3_limit(db, SQLITE_LIMIT_WORKER_THREADS, -1)); break; } @@ -99628,17 +108690,15 @@ SQLITE_PRIVATE void sqlite3Pragma( static const char *const azLockName[] = { "unlocked", "shared", "reserved", "pending", "exclusive" }; + static const char *azCol[] = { "database", "status" }; int i; - sqlite3VdbeSetNumCols(v, 2); + setAllColumnNames(v, 2, azCol); assert( 2==ArraySize(azCol) ); pParse->nMem = 2; - sqlite3VdbeSetColName(v, 0, COLNAME_NAME, "database", SQLITE_STATIC); - sqlite3VdbeSetColName(v, 1, COLNAME_NAME, "status", SQLITE_STATIC); for(i=0; inDb; i++){ Btree *pBt; const char *zState = "unknown"; int j; if( db->aDb[i].zName==0 ) continue; - sqlite3VdbeAddOp4(v, OP_String8, 0, 1, 0, db->aDb[i].zName, P4_STATIC); pBt = db->aDb[i].pBt; if( pBt==0 || sqlite3BtreePager(pBt)==0 ){ zState = "closed"; @@ -99646,7 +108706,7 @@ SQLITE_PRIVATE void sqlite3Pragma( SQLITE_FCNTL_LOCKSTATE, &j)==SQLITE_OK ){ zState = azLockName[j]; } - sqlite3VdbeAddOp4(v, OP_String8, 0, 2, 0, zState, P4_STATIC); + sqlite3VdbeMultiLoad(v, 1, "ss", db->aDb[i].zName, zState); sqlite3VdbeAddOp2(v, OP_ResultRow, 1, 2); } break; @@ -99722,6 +108782,7 @@ pragma_out: ** interface, and routines that contribute to loading the database schema ** from disk. */ +/* #include "sqliteInt.h" */ /* ** Fill the InitData structure with an error message that indicates @@ -99734,13 +108795,13 @@ static void corruptSchema( ){ sqlite3 *db = pData->db; if( !db->mallocFailed && (db->flags & SQLITE_RecoveryMode)==0 ){ + char *z; if( zObj==0 ) zObj = "?"; - sqlite3SetString(pData->pzErrMsg, db, - "malformed database schema (%s)", zObj); - if( zExtra ){ - *pData->pzErrMsg = sqlite3MAppendf(db, *pData->pzErrMsg, - "%s - %s", *pData->pzErrMsg, zExtra); - } + z = sqlite3_mprintf("malformed database schema (%s)", zObj); + if( z && zExtra ) z = sqlite3_mprintf("%z - %s", z, zExtra); + sqlite3DbFree(db, *pData->pzErrMsg); + *pData->pzErrMsg = z; + if( z==0 ) db->mallocFailed = 1; } pData->rc = db->mallocFailed ? SQLITE_NOMEM : SQLITE_CORRUPT_BKPT; } @@ -99775,7 +108836,7 @@ SQLITE_PRIVATE int sqlite3InitCallback(void *pInit, int argc, char **argv, char if( argv==0 ) return 0; /* Might happen if EMPTY_RESULT_CALLBACKS are on */ if( argv[1]==0 ){ corruptSchema(pData, argv[0], 0); - }else if( argv[2] && argv[2][0] ){ + }else if( sqlite3_strnicmp(argv[2],"create ",7)==0 ){ /* Call the parser to process a CREATE TABLE, INDEX or VIEW. ** But because db->init.busy is set to 1, no VDBE code is generated ** or executed. All the parser does is build the internal data @@ -99806,8 +108867,8 @@ SQLITE_PRIVATE int sqlite3InitCallback(void *pInit, int argc, char **argv, char } } sqlite3_finalize(pStmt); - }else if( argv[0]==0 ){ - corruptSchema(pData, 0, 0); + }else if( argv[0]==0 || (argv[2]!=0 && argv[2][0]!=0) ){ + corruptSchema(pData, argv[0], 0); }else{ /* If the SQL column is blank it means this is an index that ** was created to be the PRIMARY KEY or to fulfill a UNIQUE @@ -99932,7 +108993,7 @@ static int sqlite3InitOne(sqlite3 *db, int iDb, char **pzErrMsg){ if( !sqlite3BtreeIsInReadTrans(pDb->pBt) ){ rc = sqlite3BtreeBeginTrans(pDb->pBt, 0); if( rc!=SQLITE_OK ){ - sqlite3SetString(pzErrMsg, db, "%s", sqlite3ErrStr(rc)); + sqlite3SetString(pzErrMsg, db, sqlite3ErrStr(rc)); goto initone_error_out; } openedTransaction = 1; @@ -100036,7 +109097,7 @@ static int sqlite3InitOne(sqlite3 *db, int iDb, char **pzErrMsg){ db->aDb[iDb].zName, zMasterName); #ifndef SQLITE_OMIT_AUTHORIZATION { - int (*xAuth)(void*,int,const char*,const char*,const char*,const char*); + sqlite3_xauth xAuth; xAuth = db->xAuth; db->xAuth = 0; #endif @@ -100102,8 +109163,11 @@ SQLITE_PRIVATE int sqlite3Init(sqlite3 *db, char **pzErrMsg){ int commit_internal = !(db->flags&SQLITE_InternChanges); assert( sqlite3_mutex_held(db->mutex) ); + assert( sqlite3BtreeHoldsMutex(db->aDb[0].pBt) ); + assert( db->init.busy==0 ); rc = SQLITE_OK; db->init.busy = 1; + ENC(db) = SCHEMA_ENC(db); for(i=0; rc==SQLITE_OK && inDb; i++){ if( DbHasProperty(db, i, DB_SchemaLoaded) || i==1 ) continue; rc = sqlite3InitOne(db, i, pzErrMsg); @@ -100117,8 +109181,8 @@ SQLITE_PRIVATE int sqlite3Init(sqlite3 *db, char **pzErrMsg){ ** schema may contain references to objects in other databases. */ #ifndef SQLITE_OMIT_TEMPDB - if( rc==SQLITE_OK && ALWAYS(db->nDb>1) - && !DbHasProperty(db, 1, DB_SchemaLoaded) ){ + assert( db->nDb>1 ); + if( rc==SQLITE_OK && !DbHasProperty(db, 1, DB_SchemaLoaded) ){ rc = sqlite3InitOne(db, 1, pzErrMsg); if( rc ){ sqlite3ResetOneSchema(db, 1); @@ -100301,7 +109365,7 @@ static int sqlite3Prepare( rc = sqlite3BtreeSchemaLocked(pBt); if( rc ){ const char *zDb = db->aDb[i].zName; - sqlite3Error(db, rc, "database schema is locked: %s", zDb); + sqlite3ErrorWithMsg(db, rc, "database schema is locked: %s", zDb); testcase( db->flags & SQLITE_ReadUncommitted ); goto end_prepare; } @@ -100318,7 +109382,7 @@ static int sqlite3Prepare( testcase( nBytes==mxLen ); testcase( nBytes==mxLen+1 ); if( nBytes>mxLen ){ - sqlite3Error(db, SQLITE_TOOBIG, "statement too long"); + sqlite3ErrorWithMsg(db, SQLITE_TOOBIG, "statement too long"); rc = sqlite3ApiExit(db, SQLITE_TOOBIG); goto end_prepare; } @@ -100385,10 +109449,10 @@ static int sqlite3Prepare( } if( zErrMsg ){ - sqlite3Error(db, rc, "%s", zErrMsg); + sqlite3ErrorWithMsg(db, rc, "%s", zErrMsg); sqlite3DbFree(db, zErrMsg); }else{ - sqlite3Error(db, rc, 0); + sqlite3Error(db, rc); } /* Delete any TriggerPrg structures allocated while parsing this statement. */ @@ -100416,9 +109480,12 @@ static int sqlite3LockAndPrepare( const char **pzTail /* OUT: End of parsed string */ ){ int rc; - assert( ppStmt!=0 ); + +#ifdef SQLITE_ENABLE_API_ARMOR + if( ppStmt==0 ) return SQLITE_MISUSE_BKPT; +#endif *ppStmt = 0; - if( !sqlite3SafetyCheckOk(db) ){ + if( !sqlite3SafetyCheckOk(db)||zSql==0 ){ return SQLITE_MISUSE_BKPT; } sqlite3_mutex_enter(db->mutex); @@ -100479,7 +109546,7 @@ SQLITE_PRIVATE int sqlite3Reprepare(Vdbe *p){ ** and the statement is automatically recompiled if an schema change ** occurs. */ -SQLITE_API int sqlite3_prepare( +SQLITE_API int SQLITE_STDCALL sqlite3_prepare( sqlite3 *db, /* Database handle. */ const char *zSql, /* UTF-8 encoded SQL statement. */ int nBytes, /* Length of zSql in bytes. */ @@ -100491,7 +109558,7 @@ SQLITE_API int sqlite3_prepare( assert( rc==SQLITE_OK || ppStmt==0 || *ppStmt==0 ); /* VERIFY: F13021 */ return rc; } -SQLITE_API int sqlite3_prepare_v2( +SQLITE_API int SQLITE_STDCALL sqlite3_prepare_v2( sqlite3 *db, /* Database handle. */ const char *zSql, /* UTF-8 encoded SQL statement. */ int nBytes, /* Length of zSql in bytes. */ @@ -100525,9 +109592,11 @@ static int sqlite3Prepare16( const char *zTail8 = 0; int rc = SQLITE_OK; - assert( ppStmt ); +#ifdef SQLITE_ENABLE_API_ARMOR + if( ppStmt==0 ) return SQLITE_MISUSE_BKPT; +#endif *ppStmt = 0; - if( !sqlite3SafetyCheckOk(db) ){ + if( !sqlite3SafetyCheckOk(db)||zSql==0 ){ return SQLITE_MISUSE_BKPT; } if( nBytes>=0 ){ @@ -100565,7 +109634,7 @@ static int sqlite3Prepare16( ** and the statement is automatically recompiled if an schema change ** occurs. */ -SQLITE_API int sqlite3_prepare16( +SQLITE_API int SQLITE_STDCALL sqlite3_prepare16( sqlite3 *db, /* Database handle. */ const void *zSql, /* UTF-16 encoded SQL statement. */ int nBytes, /* Length of zSql in bytes. */ @@ -100577,7 +109646,7 @@ SQLITE_API int sqlite3_prepare16( assert( rc==SQLITE_OK || ppStmt==0 || *ppStmt==0 ); /* VERIFY: F13021 */ return rc; } -SQLITE_API int sqlite3_prepare16_v2( +SQLITE_API int SQLITE_STDCALL sqlite3_prepare16_v2( sqlite3 *db, /* Database handle. */ const void *zSql, /* UTF-16 encoded SQL statement. */ int nBytes, /* Length of zSql in bytes. */ @@ -100608,6 +109677,22 @@ SQLITE_API int sqlite3_prepare16_v2( ** This file contains C code routines that are called by the parser ** to handle SELECT statements in SQLite. */ +/* #include "sqliteInt.h" */ + +/* +** Trace output macros +*/ +#if SELECTTRACE_ENABLED +/***/ int sqlite3SelectTrace = 0; +# define SELECTTRACE(K,P,S,X) \ + if(sqlite3SelectTrace&(K)) \ + sqlite3DebugPrintf("%*s%s.%p: ",(P)->nSelectIndent*2-2,"",\ + (S)->zSelName,(S)),\ + sqlite3DebugPrintf X +#else +# define SELECTTRACE(K,P,S,X) +#endif + /* ** An instance of the following object is used to record information about @@ -100634,25 +109719,31 @@ struct SortCtx { int regReturn; /* Register holding block-output return address */ int labelBkOut; /* Start label for the block-output subroutine */ int addrSortIndex; /* Address of the OP_SorterOpen or OP_OpenEphemeral */ + int labelDone; /* Jump here when done, ex: LIMIT reached */ u8 sortFlags; /* Zero or more SORTFLAG_* bits */ }; #define SORTFLAG_UseSorter 0x01 /* Use SorterOpen instead of OpenEphemeral */ /* -** Delete all the content of a Select structure but do not deallocate -** the select structure itself. +** Delete all the content of a Select structure. Deallocate the structure +** itself only if bFree is true. */ -static void clearSelect(sqlite3 *db, Select *p){ - sqlite3ExprListDelete(db, p->pEList); - sqlite3SrcListDelete(db, p->pSrc); - sqlite3ExprDelete(db, p->pWhere); - sqlite3ExprListDelete(db, p->pGroupBy); - sqlite3ExprDelete(db, p->pHaving); - sqlite3ExprListDelete(db, p->pOrderBy); - sqlite3SelectDelete(db, p->pPrior); - sqlite3ExprDelete(db, p->pLimit); - sqlite3ExprDelete(db, p->pOffset); - sqlite3WithDelete(db, p->pWith); +static void clearSelect(sqlite3 *db, Select *p, int bFree){ + while( p ){ + Select *pPrior = p->pPrior; + sqlite3ExprListDelete(db, p->pEList); + sqlite3SrcListDelete(db, p->pSrc); + sqlite3ExprDelete(db, p->pWhere); + sqlite3ExprListDelete(db, p->pGroupBy); + sqlite3ExprDelete(db, p->pHaving); + sqlite3ExprListDelete(db, p->pOrderBy); + sqlite3ExprDelete(db, p->pLimit); + sqlite3ExprDelete(db, p->pOffset); + sqlite3WithDelete(db, p->pWith); + if( bFree ) sqlite3DbFree(db, p); + p = pPrior; + bFree = 1; + } } /* @@ -100687,14 +109778,13 @@ SQLITE_PRIVATE Select *sqlite3SelectNew( Select standin; sqlite3 *db = pParse->db; pNew = sqlite3DbMallocZero(db, sizeof(*pNew) ); - assert( db->mallocFailed || !pOffset || pLimit ); /* OFFSET implies LIMIT */ if( pNew==0 ){ assert( db->mallocFailed ); pNew = &standin; memset(pNew, 0, sizeof(*pNew)); } if( pEList==0 ){ - pEList = sqlite3ExprListAppend(pParse, 0, sqlite3Expr(db,TK_ALL,0)); + pEList = sqlite3ExprListAppend(pParse, 0, sqlite3Expr(db,TK_ASTERISK,0)); } pNew->pEList = pEList; if( pSrc==0 ) pSrc = sqlite3DbMallocZero(db, sizeof(*pSrc)); @@ -100707,12 +109797,11 @@ SQLITE_PRIVATE Select *sqlite3SelectNew( pNew->op = TK_SELECT; pNew->pLimit = pLimit; pNew->pOffset = pOffset; - assert( pOffset==0 || pLimit!=0 ); + assert( pOffset==0 || pLimit!=0 || pParse->nErr>0 || db->mallocFailed!=0 ); pNew->addrOpenEphm[0] = -1; pNew->addrOpenEphm[1] = -1; if( db->mallocFailed ) { - clearSelect(db, pNew); - if( pNew!=&standin ) sqlite3DbFree(db, pNew); + clearSelect(db, pNew, pNew!=&standin); pNew = 0; }else{ assert( pNew->pSrc!=0 || pParse->nErr>0 ); @@ -100721,14 +109810,23 @@ SQLITE_PRIVATE Select *sqlite3SelectNew( return pNew; } +#if SELECTTRACE_ENABLED +/* +** Set the name of a Select object +*/ +SQLITE_PRIVATE void sqlite3SelectSetName(Select *p, const char *zName){ + if( p && zName ){ + sqlite3_snprintf(sizeof(p->zSelName), p->zSelName, "%s", zName); + } +} +#endif + + /* ** Delete the given Select structure and all of its substructures. */ SQLITE_PRIVATE void sqlite3SelectDelete(sqlite3 *db, Select *p){ - if( p ){ - clearSelect(db, p); - sqlite3DbFree(db, p); - } + clearSelect(db, p, 1); } /* @@ -100934,6 +110032,12 @@ static void setJoinExpr(Expr *p, int iTable){ assert( !ExprHasProperty(p, EP_TokenOnly|EP_Reduced) ); ExprSetVVAProperty(p, EP_NoReduce); p->iRightJoinTable = (i16)iTable; + if( p->op==TK_FUNCTION && p->x.pList ){ + int i; + for(i=0; ix.pList->nExpr; i++){ + setJoinExpr(p->x.pList->a[i].pExpr, iTable); + } + } setJoinExpr(p->pLeft, iTable); p = p->pRight; } @@ -100968,12 +110072,12 @@ static int sqliteProcessJoin(Parse *pParse, Select *p){ int isOuter; if( NEVER(pLeftTab==0 || pRightTab==0) ) continue; - isOuter = (pRight->jointype & JT_OUTER)!=0; + isOuter = (pRight->fg.jointype & JT_OUTER)!=0; /* When the NATURAL keyword is present, add WHERE clause terms for ** every column that the two tables have in common. */ - if( pRight->jointype & JT_NATURAL ){ + if( pRight->fg.jointype & JT_NATURAL ){ if( pRight->pOn || pRight->pUsing ){ sqlite3ErrorMsg(pParse, "a NATURAL join may not have " "an ON or USING clause", 0); @@ -101050,28 +110154,49 @@ static KeyInfo *keyInfoFromExprList( ); /* -** Insert code into "v" that will push the record in register regData -** into the sorter. +** Generate code that will push the record in registers regData +** through regData+nData-1 onto the sorter. */ static void pushOntoSorter( Parse *pParse, /* Parser context */ SortCtx *pSort, /* Information about the ORDER BY clause */ Select *pSelect, /* The whole SELECT statement */ - int regData /* Register holding data to be sorted */ + int regData, /* First register holding data to be sorted */ + int regOrigData, /* First register holding data before packing */ + int nData, /* Number of elements in the data array */ + int nPrefixReg /* No. of reg prior to regData available for use */ ){ - Vdbe *v = pParse->pVdbe; - int nExpr = pSort->pOrderBy->nExpr; - int regRecord = ++pParse->nMem; - int regBase = pParse->nMem+1; - int nOBSat = pSort->nOBSat; - int op; + Vdbe *v = pParse->pVdbe; /* Stmt under construction */ + int bSeq = ((pSort->sortFlags & SORTFLAG_UseSorter)==0); + int nExpr = pSort->pOrderBy->nExpr; /* No. of ORDER BY terms */ + int nBase = nExpr + bSeq + nData; /* Fields in sorter record */ + int regBase; /* Regs for sorter record */ + int regRecord = ++pParse->nMem; /* Assembled sorter record */ + int nOBSat = pSort->nOBSat; /* ORDER BY terms to skip */ + int op; /* Opcode to add sorter record to sorter */ + int iLimit; /* LIMIT counter */ - pParse->nMem += nExpr+2; /* nExpr+2 registers allocated at regBase */ - sqlite3ExprCacheClear(pParse); - sqlite3ExprCodeExprList(pParse, pSort->pOrderBy, regBase, 0); - sqlite3VdbeAddOp2(v, OP_Sequence, pSort->iECursor, regBase+nExpr); - sqlite3ExprCodeMove(pParse, regData, regBase+nExpr+1, 1); - sqlite3VdbeAddOp3(v, OP_MakeRecord, regBase+nOBSat, nExpr+2-nOBSat,regRecord); + assert( bSeq==0 || bSeq==1 ); + assert( nData==1 || regData==regOrigData ); + if( nPrefixReg ){ + assert( nPrefixReg==nExpr+bSeq ); + regBase = regData - nExpr - bSeq; + }else{ + regBase = pParse->nMem + 1; + pParse->nMem += nBase; + } + assert( pSelect->iOffset==0 || pSelect->iLimit!=0 ); + iLimit = pSelect->iOffset ? pSelect->iOffset+1 : pSelect->iLimit; + pSort->labelDone = sqlite3VdbeMakeLabel(v); + sqlite3ExprCodeExprList(pParse, pSort->pOrderBy, regBase, regOrigData, + SQLITE_ECEL_DUP|SQLITE_ECEL_REF); + if( bSeq ){ + sqlite3VdbeAddOp2(v, OP_Sequence, pSort->iECursor, regBase+nExpr); + } + if( nPrefixReg==0 ){ + sqlite3ExprCodeMove(pParse, regData, regBase+nExpr+bSeq, nData); + } + sqlite3VdbeAddOp3(v, OP_MakeRecord, regBase+nOBSat, nBase-nOBSat, regRecord); if( nOBSat>0 ){ int regPrevKey; /* The first nOBSat columns of the previous row */ int addrFirst; /* Address of the OP_IfNot opcode */ @@ -101082,24 +110207,35 @@ static void pushOntoSorter( regPrevKey = pParse->nMem+1; pParse->nMem += pSort->nOBSat; - nKey = nExpr - pSort->nOBSat + 1; - addrFirst = sqlite3VdbeAddOp1(v, OP_IfNot, regBase+nExpr); VdbeCoverage(v); + nKey = nExpr - pSort->nOBSat + bSeq; + if( bSeq ){ + addrFirst = sqlite3VdbeAddOp1(v, OP_IfNot, regBase+nExpr); + }else{ + addrFirst = sqlite3VdbeAddOp1(v, OP_SequenceTest, pSort->iECursor); + } + VdbeCoverage(v); sqlite3VdbeAddOp3(v, OP_Compare, regPrevKey, regBase, pSort->nOBSat); pOp = sqlite3VdbeGetOp(v, pSort->addrSortIndex); if( pParse->db->mallocFailed ) return; - pOp->p2 = nKey + 1; + pOp->p2 = nKey + nData; pKI = pOp->p4.pKeyInfo; memset(pKI->aSortOrder, 0, pKI->nField); /* Makes OP_Jump below testable */ sqlite3VdbeChangeP4(v, -1, (char*)pKI, P4_KEYINFO); - pOp->p4.pKeyInfo = keyInfoFromExprList(pParse, pSort->pOrderBy, nOBSat, 1); + testcase( pKI->nXField>2 ); + pOp->p4.pKeyInfo = keyInfoFromExprList(pParse, pSort->pOrderBy, nOBSat, + pKI->nXField-1); addrJmp = sqlite3VdbeCurrentAddr(v); sqlite3VdbeAddOp3(v, OP_Jump, addrJmp+1, 0, addrJmp+1); VdbeCoverage(v); pSort->labelBkOut = sqlite3VdbeMakeLabel(v); pSort->regReturn = ++pParse->nMem; sqlite3VdbeAddOp2(v, OP_Gosub, pSort->regReturn, pSort->labelBkOut); sqlite3VdbeAddOp1(v, OP_ResetSorter, pSort->iECursor); + if( iLimit ){ + sqlite3VdbeAddOp2(v, OP_IfNot, iLimit, pSort->labelDone); + VdbeCoverage(v); + } sqlite3VdbeJumpHere(v, addrFirst); - sqlite3VdbeAddOp3(v, OP_Move, regBase, regPrevKey, pSort->nOBSat); + sqlite3ExprCodeMove(pParse, regBase, regPrevKey, pSort->nOBSat); sqlite3VdbeJumpHere(v, addrJmp); } if( pSort->sortFlags & SORTFLAG_UseSorter ){ @@ -101108,21 +110244,12 @@ static void pushOntoSorter( op = OP_IdxInsert; } sqlite3VdbeAddOp2(v, op, pSort->iECursor, regRecord); - if( pSelect->iLimit ){ - int addr1, addr2; - int iLimit; - if( pSelect->iOffset ){ - iLimit = pSelect->iOffset+1; - }else{ - iLimit = pSelect->iLimit; - } - addr1 = sqlite3VdbeAddOp1(v, OP_IfZero, iLimit); VdbeCoverage(v); - sqlite3VdbeAddOp2(v, OP_AddImm, iLimit, -1); - addr2 = sqlite3VdbeAddOp0(v, OP_Goto); - sqlite3VdbeJumpHere(v, addr1); + if( iLimit ){ + int addr; + addr = sqlite3VdbeAddOp3(v, OP_IfNotZero, iLimit, 0, 1); VdbeCoverage(v); sqlite3VdbeAddOp1(v, OP_Last, pSort->iECursor); sqlite3VdbeAddOp1(v, OP_Delete, pSort->iECursor); - sqlite3VdbeJumpHere(v, addr2); + sqlite3VdbeJumpHere(v, addr); } } @@ -101135,12 +110262,8 @@ static void codeOffset( int iContinue /* Jump here to skip the current record */ ){ if( iOffset>0 ){ - int addr; - sqlite3VdbeAddOp2(v, OP_AddImm, iOffset, -1); - addr = sqlite3VdbeAddOp1(v, OP_IfNeg, iOffset); VdbeCoverage(v); - sqlite3VdbeAddOp2(v, OP_Goto, 0, iContinue); - VdbeComment((v, "skip OFFSET records")); - sqlite3VdbeJumpHere(v, addr); + sqlite3VdbeAddOp3(v, OP_IfPos, iOffset, iContinue, 1); VdbeCoverage(v); + VdbeComment((v, "OFFSET")); } } @@ -101222,6 +110345,7 @@ static void selectInnerLoop( int eDest = pDest->eDest; /* How to dispose of results */ int iParm = pDest->iSDParm; /* First argument to disposal method */ int nResultCol; /* Number of result columns */ + int nPrefixReg = 0; /* Number of extra registers before regResult */ assert( v ); assert( pEList!=0 ); @@ -101237,6 +110361,11 @@ static void selectInnerLoop( nResultCol = pEList->nExpr; if( pDest->iSdst==0 ){ + if( pSort ){ + nPrefixReg = pSort->pOrderBy->nExpr; + if( !(pSort->sortFlags & SORTFLAG_UseSorter) ) nPrefixReg++; + pParse->nMem += nPrefixReg; + } pDest->iSdst = pParse->nMem+1; pParse->nMem += nResultCol; }else if( pDest->iSdst+nResultCol > pParse->nMem ){ @@ -101258,8 +110387,13 @@ static void selectInnerLoop( /* If the destination is an EXISTS(...) expression, the actual ** values returned by the SELECT are not required. */ - sqlite3ExprCodeExprList(pParse, pEList, regResult, - (eDest==SRT_Output||eDest==SRT_Coroutine)?SQLITE_ECEL_DUP:0); + u8 ecelFlags; + if( eDest==SRT_Mem || eDest==SRT_Output || eDest==SRT_Coroutine ){ + ecelFlags = SQLITE_ECEL_DUP; + }else{ + ecelFlags = 0; + } + sqlite3ExprCodeExprList(pParse, pEList, regResult, 0, ecelFlags); } /* If the DISTINCT keyword was present on the SELECT statement @@ -101302,7 +110436,7 @@ static void selectInnerLoop( sqlite3VdbeChangeP4(v, -1, (const char *)pColl, P4_COLLSEQ); sqlite3VdbeChangeP5(v, SQLITE_NULLEQ); } - assert( sqlite3VdbeCurrentAddr(v)==iJump ); + assert( sqlite3VdbeCurrentAddr(v)==iJump || pParse->db->mallocFailed ); sqlite3VdbeAddOp3(v, OP_Copy, regResult, regPrev, nResultCol-1); break; } @@ -101314,7 +110448,8 @@ static void selectInnerLoop( default: { assert( pDistinct->eTnctType==WHERE_DISTINCT_UNORDERED ); - codeDistinct(pParse, pDistinct->tabTnct, iContinue, nResultCol, regResult); + codeDistinct(pParse, pDistinct->tabTnct, iContinue, nResultCol, + regResult); break; } } @@ -101353,10 +110488,12 @@ static void selectInnerLoop( case SRT_DistFifo: case SRT_Table: case SRT_EphemTab: { - int r1 = sqlite3GetTempReg(pParse); + int r1 = sqlite3GetTempRange(pParse, nPrefixReg+1); testcase( eDest==SRT_Table ); testcase( eDest==SRT_EphemTab ); - sqlite3VdbeAddOp3(v, OP_MakeRecord, regResult, nResultCol, r1); + testcase( eDest==SRT_Fifo ); + testcase( eDest==SRT_DistFifo ); + sqlite3VdbeAddOp3(v, OP_MakeRecord, regResult, nResultCol, r1+nPrefixReg); #ifndef SQLITE_OMIT_CTE if( eDest==SRT_DistFifo ){ /* If the destination is DistFifo, then cursor (iParm+1) is open @@ -101365,13 +110502,14 @@ static void selectInnerLoop( ** current row to the index and proceed with writing it to the ** output table as well. */ int addr = sqlite3VdbeCurrentAddr(v) + 4; - sqlite3VdbeAddOp4Int(v, OP_Found, iParm+1, addr, r1, 0); VdbeCoverage(v); + sqlite3VdbeAddOp4Int(v, OP_Found, iParm+1, addr, r1, 0); + VdbeCoverage(v); sqlite3VdbeAddOp2(v, OP_IdxInsert, iParm+1, r1); assert( pSort==0 ); } #endif if( pSort ){ - pushOntoSorter(pParse, pSort, p, r1); + pushOntoSorter(pParse, pSort, p, r1+nPrefixReg,regResult,1,nPrefixReg); }else{ int r2 = sqlite3GetTempReg(pParse); sqlite3VdbeAddOp2(v, OP_NewRowid, iParm, r2); @@ -101379,7 +110517,7 @@ static void selectInnerLoop( sqlite3VdbeChangeP5(v, OPFLAG_APPEND); sqlite3ReleaseTempReg(pParse, r2); } - sqlite3ReleaseTempReg(pParse, r1); + sqlite3ReleaseTempRange(pParse, r1, nPrefixReg+1); break; } @@ -101397,7 +110535,7 @@ static void selectInnerLoop( ** ORDER BY in this case since the order of entries in the set ** does not matter. But there might be a LIMIT clause, in which ** case the order does matter */ - pushOntoSorter(pParse, pSort, p, regResult); + pushOntoSorter(pParse, pSort, p, regResult, regResult, 1, nPrefixReg); }else{ int r1 = sqlite3GetTempReg(pParse); sqlite3VdbeAddOp4(v, OP_MakeRecord, regResult,1,r1, &pDest->affSdst, 1); @@ -101423,9 +110561,9 @@ static void selectInnerLoop( case SRT_Mem: { assert( nResultCol==1 ); if( pSort ){ - pushOntoSorter(pParse, pSort, p, regResult); + pushOntoSorter(pParse, pSort, p, regResult, regResult, 1, nPrefixReg); }else{ - sqlite3ExprCodeMove(pParse, regResult, iParm, 1); + assert( regResult==iParm ); /* The LIMIT clause will jump out of the loop for us */ } break; @@ -101437,10 +110575,8 @@ static void selectInnerLoop( testcase( eDest==SRT_Coroutine ); testcase( eDest==SRT_Output ); if( pSort ){ - int r1 = sqlite3GetTempReg(pParse); - sqlite3VdbeAddOp3(v, OP_MakeRecord, regResult, nResultCol, r1); - pushOntoSorter(pParse, pSort, p, r1); - sqlite3ReleaseTempReg(pParse, r1); + pushOntoSorter(pParse, pSort, p, regResult, regResult, nResultCol, + nPrefixReg); }else if( eDest==SRT_Coroutine ){ sqlite3VdbeAddOp1(v, OP_Yield, pDest->iSDParm); }else{ @@ -101517,7 +110653,7 @@ static void selectInnerLoop( ** the output for us. */ if( pSort==0 && p->iLimit ){ - sqlite3VdbeAddOp3(v, OP_IfZero, p->iLimit, iBreak, -1); VdbeCoverage(v); + sqlite3VdbeAddOp2(v, OP_DecrJumpZero, p->iLimit, iBreak); VdbeCoverage(v); } } @@ -101583,7 +110719,7 @@ SQLITE_PRIVATE int sqlite3KeyInfoIsWriteable(KeyInfo *p){ return p->nRef==1; } ** then the KeyInfo structure is appropriate for initializing a virtual ** index to implement a DISTINCT test. ** -** Space to hold the KeyInfo structure is obtain from malloc. The calling +** Space to hold the KeyInfo structure is obtained from malloc. The calling ** function is responsible for seeing that this structure is eventually ** freed. */ @@ -101600,7 +110736,7 @@ static KeyInfo *keyInfoFromExprList( int i; nExpr = pList->nExpr; - pInfo = sqlite3KeyInfoAlloc(db, nExpr+nExtra-iStart, 1); + pInfo = sqlite3KeyInfoAlloc(db, nExpr-iStart, nExtra+1); if( pInfo ){ assert( sqlite3KeyInfoIsWriteable(pInfo) ); for(i=iStart, pItem=pList->a+iStart; ipVdbe; /* The prepared statement */ - int addrBreak = sqlite3VdbeMakeLabel(v); /* Jump here to exit loop */ + int addrBreak = pSort->labelDone; /* Jump here to exit loop */ int addrContinue = sqlite3VdbeMakeLabel(v); /* Jump here for next cycle */ int addr; int addrOnce = 0; int iTab; - int pseudoTab = 0; ExprList *pOrderBy = pSort->pOrderBy; int eDest = pDest->eDest; int iParm = pDest->iSDParm; int regRow; int regRowid; int nKey; + int iSortTab; /* Sorter cursor to read from */ + int nSortData; /* Trailing values to read from sorter */ + int i; + int bSeq; /* True if sorter record includes seq. no. */ +#ifdef SQLITE_ENABLE_EXPLAIN_COMMENTS + struct ExprList_item *aOutEx = p->pEList->a; +#endif + assert( addrBreak<0 ); if( pSort->labelBkOut ){ sqlite3VdbeAddOp2(v, OP_Gosub, pSort->regReturn, pSort->labelBkOut); - sqlite3VdbeAddOp2(v, OP_Goto, 0, addrBreak); + sqlite3VdbeGoto(v, addrBreak); sqlite3VdbeResolveLabel(v, pSort->labelBkOut); - addrOnce = sqlite3CodeOnce(pParse); VdbeCoverage(v); } iTab = pSort->iECursor; - regRow = sqlite3GetTempReg(pParse); if( eDest==SRT_Output || eDest==SRT_Coroutine ){ - pseudoTab = pParse->nTab++; - sqlite3VdbeAddOp3(v, OP_OpenPseudo, pseudoTab, regRow, nColumn); regRowid = 0; + regRow = pDest->iSdst; + nSortData = nColumn; }else{ regRowid = sqlite3GetTempReg(pParse); + regRow = sqlite3GetTempReg(pParse); + nSortData = 1; } nKey = pOrderBy->nExpr - pSort->nOBSat; if( pSort->sortFlags & SORTFLAG_UseSorter ){ int regSortOut = ++pParse->nMem; - int ptab2 = pParse->nTab++; - sqlite3VdbeAddOp3(v, OP_OpenPseudo, ptab2, regSortOut, nKey+2); + iSortTab = pParse->nTab++; + if( pSort->labelBkOut ){ + addrOnce = sqlite3CodeOnce(pParse); VdbeCoverage(v); + } + sqlite3VdbeAddOp3(v, OP_OpenPseudo, iSortTab, regSortOut, nKey+1+nSortData); if( addrOnce ) sqlite3VdbeJumpHere(v, addrOnce); addr = 1 + sqlite3VdbeAddOp2(v, OP_SorterSort, iTab, addrBreak); VdbeCoverage(v); codeOffset(v, p->iOffset, addrContinue); - sqlite3VdbeAddOp2(v, OP_SorterData, iTab, regSortOut); - sqlite3VdbeAddOp3(v, OP_Column, ptab2, nKey+1, regRow); - sqlite3VdbeChangeP5(v, OPFLAG_CLEARCACHE); + sqlite3VdbeAddOp3(v, OP_SorterData, iTab, regSortOut, iSortTab); + bSeq = 0; }else{ - if( addrOnce ) sqlite3VdbeJumpHere(v, addrOnce); addr = 1 + sqlite3VdbeAddOp2(v, OP_Sort, iTab, addrBreak); VdbeCoverage(v); codeOffset(v, p->iOffset, addrContinue); - sqlite3VdbeAddOp3(v, OP_Column, iTab, nKey+1, regRow); + iSortTab = iTab; + bSeq = 1; + } + for(i=0; iiSdst+i ); - sqlite3VdbeAddOp3(v, OP_Column, pseudoTab, i, pDest->iSdst+i); - if( i==0 ){ - sqlite3VdbeChangeP5(v, OPFLAG_CLEARCACHE); - } - } if( eDest==SRT_Output ){ sqlite3VdbeAddOp2(v, OP_ResultRow, pDest->iSdst, nColumn); sqlite3ExprCacheAffinityChange(pParse, pDest->iSdst, nColumn); @@ -101808,9 +110944,10 @@ static void generateSortTail( break; } } - sqlite3ReleaseTempReg(pParse, regRow); - sqlite3ReleaseTempReg(pParse, regRowid); - + if( regRowid ){ + sqlite3ReleaseTempReg(pParse, regRow); + sqlite3ReleaseTempReg(pParse, regRowid); + } /* The bottom of the loop */ sqlite3VdbeResolveLabel(v, addrContinue); @@ -101849,30 +110986,30 @@ static void generateSortTail( */ #ifdef SQLITE_ENABLE_COLUMN_METADATA # define columnType(A,B,C,D,E,F) columnTypeImpl(A,B,C,D,E,F) +#else /* if !defined(SQLITE_ENABLE_COLUMN_METADATA) */ +# define columnType(A,B,C,D,E,F) columnTypeImpl(A,B,F) +#endif static const char *columnTypeImpl( NameContext *pNC, Expr *pExpr, +#ifdef SQLITE_ENABLE_COLUMN_METADATA const char **pzOrigDb, const char **pzOrigTab, const char **pzOrigCol, +#endif u8 *pEstWidth ){ - char const *zOrigDb = 0; - char const *zOrigTab = 0; - char const *zOrigCol = 0; -#else /* if !defined(SQLITE_ENABLE_COLUMN_METADATA) */ -# define columnType(A,B,C,D,E,F) columnTypeImpl(A,B,F) -static const char *columnTypeImpl( - NameContext *pNC, - Expr *pExpr, - u8 *pEstWidth -){ -#endif /* !defined(SQLITE_ENABLE_COLUMN_METADATA) */ char const *zType = 0; int j; u8 estWidth = 1; +#ifdef SQLITE_ENABLE_COLUMN_METADATA + char const *zOrigDb = 0; + char const *zOrigTab = 0; + char const *zOrigCol = 0; +#endif - if( NEVER(pExpr==0) || pNC->pSrcList==0 ) return 0; + assert( pExpr!=0 ); + assert( pNC->pSrcList!=0 ); switch( pExpr->op ){ case TK_AGG_COLUMN: case TK_COLUMN: { @@ -101927,6 +111064,9 @@ static const char *columnTypeImpl( /* If iCol is less than zero, then the expression requests the ** rowid of the sub-select or view. This expression is legal (see ** test case misc2.2.2) - it always evaluates to NULL. + ** + ** The ALWAYS() is because iCol>=pS->pEList->nExpr will have been + ** caught already by name resolution. */ NameContext sNC; Expr *p = pS->pEList->a[iCol].pExpr; @@ -102057,7 +111197,9 @@ static void generateColumnNames( } #endif - if( pParse->colNamesSet || NEVER(v==0) || db->mallocFailed ) return; + if( pParse->colNamesSet || db->mallocFailed ) return; + assert( v!=0 ); + assert( pTabList!=0 ); pParse->colNamesSet = 1; fullNames = (db->flags & SQLITE_FullColNames)!=0; shortNames = (db->flags & SQLITE_ShortColNames)!=0; @@ -102069,7 +111211,7 @@ static void generateColumnNames( if( pEList->a[i].zName ){ char *zName = pEList->a[i].zName; sqlite3VdbeSetColName(v, i, COLNAME_NAME, zName, SQLITE_TRANSIENT); - }else if( (p->op==TK_COLUMN || p->op==TK_AGG_COLUMN) && pTabList ){ + }else if( p->op==TK_COLUMN || p->op==TK_AGG_COLUMN ){ Table *pTab; char *zCol; int iCol = p->iColumn; @@ -102105,7 +111247,7 @@ static void generateColumnNames( } /* -** Given a an expression list (which is really the list of expressions +** Given an expression list (which is really the list of expressions ** that form the result set of a SELECT statement) compute appropriate ** column names for a table that would hold the expression list. ** @@ -102117,7 +111259,7 @@ static void generateColumnNames( ** Return SQLITE_OK on success. If a memory allocation error occurs, ** store NULL in *paCol and 0 in *pnCol and return SQLITE_NOMEM. */ -static int selectColumnsFromExprList( +SQLITE_PRIVATE int sqlite3ColumnsFromExprList( Parse *pParse, /* Parsing context */ ExprList *pEList, /* Expr list from which to derive column names */ i16 *pnCol, /* Write the number of columns here */ @@ -102125,13 +111267,15 @@ static int selectColumnsFromExprList( ){ sqlite3 *db = pParse->db; /* Database connection */ int i, j; /* Loop counters */ - int cnt; /* Index added to make the name unique */ + u32 cnt; /* Index added to make the name unique */ Column *aCol, *pCol; /* For looping over result columns */ int nCol; /* Number of columns in the result set */ Expr *p; /* Expression for a single result column */ char *zName; /* Column name */ int nName; /* Size of name in zName[] */ + Hash ht; /* Hash table of column names */ + sqlite3HashInit(&ht); if( pEList ){ nCol = pEList->nExpr; aCol = sqlite3DbMallocZero(db, sizeof(aCol[0])*nCol); @@ -102140,16 +111284,16 @@ static int selectColumnsFromExprList( nCol = 0; aCol = 0; } + assert( nCol==(i16)nCol ); *pnCol = nCol; *paCol = aCol; - for(i=0, pCol=aCol; imallocFailed; i++, pCol++){ /* Get an appropriate name for the column */ p = sqlite3ExprSkipCollate(pEList->a[i].pExpr); if( (zName = pEList->a[i].zName)!=0 ){ /* If the column contains an "AS " phrase, use as the name */ - zName = sqlite3DbStrDup(db, zName); }else{ Expr *pColExpr = p; /* The expression that is the result column name */ Table *pTab; /* Table associated with this expression */ @@ -102162,41 +111306,37 @@ static int selectColumnsFromExprList( int iCol = pColExpr->iColumn; pTab = pColExpr->pTab; if( iCol<0 ) iCol = pTab->iPKey; - zName = sqlite3MPrintf(db, "%s", - iCol>=0 ? pTab->aCol[iCol].zName : "rowid"); + zName = iCol>=0 ? pTab->aCol[iCol].zName : "rowid"; }else if( pColExpr->op==TK_ID ){ assert( !ExprHasProperty(pColExpr, EP_IntValue) ); - zName = sqlite3MPrintf(db, "%s", pColExpr->u.zToken); + zName = pColExpr->u.zToken; }else{ /* Use the original text of the column expression as its name */ - zName = sqlite3MPrintf(db, "%s", pEList->a[i].zSpan); + zName = pEList->a[i].zSpan; } } - if( db->mallocFailed ){ - sqlite3DbFree(db, zName); - break; - } + zName = sqlite3MPrintf(db, "%s", zName); /* Make sure the column name is unique. If the name is not unique, - ** append a integer to the name so that it becomes unique. + ** append an integer to the name so that it becomes unique. */ - nName = sqlite3Strlen30(zName); - for(j=cnt=0; j1 && sqlite3Isdigit(zName[k]); k--){} - if( k>=0 && zName[k]==':' ) nName = k; - zName[nName] = 0; - zNewName = sqlite3MPrintf(db, "%s:%d", zName, ++cnt); - sqlite3DbFree(db, zName); - zName = zNewName; - j = -1; - if( zName==0 ) break; + cnt = 0; + while( zName && sqlite3HashFind(&ht, zName)!=0 ){ + nName = sqlite3Strlen30(zName); + if( nName>0 ){ + for(j=nName-1; j>0 && sqlite3Isdigit(zName[j]); j--){} + if( zName[j]==':' ) nName = j; } + zName = sqlite3MPrintf(db, "%.*z:%u", nName, zName, ++cnt); + if( cnt>3 ) sqlite3_randomness(sizeof(cnt), &cnt); } pCol->zName = zName; + sqlite3ColumnPropertiesFromName(0, pCol); + if( zName && sqlite3HashInsert(&ht, zName, pCol)==pCol ){ + db->mallocFailed = 1; + } } + sqlite3HashClear(&ht); if( db->mallocFailed ){ for(j=0; jpEList->a; for(i=0, pCol=pTab->aCol; inCol; i++, pCol++){ p = a[i].pExpr; - pCol->zType = sqlite3DbStrDup(db, columnType(&sNC, p,0,0,0, &pCol->szEst)); + if( pCol->zType==0 ){ + pCol->zType = sqlite3DbStrDup(db, + columnType(&sNC, p,0,0,0, &pCol->szEst)); + } szAll += pCol->szEst; pCol->affinity = sqlite3ExprAffinity(p); - if( pCol->affinity==0 ) pCol->affinity = SQLITE_AFF_NONE; + if( pCol->affinity==0 ) pCol->affinity = SQLITE_AFF_BLOB; pColl = sqlite3ExprCollSeq(pParse, p); - if( pColl ){ + if( pColl && pCol->zColl==0 ){ pCol->zColl = sqlite3DbStrDup(db, pColl->zName); } } @@ -102281,7 +111424,7 @@ SQLITE_PRIVATE Table *sqlite3ResultSetOfSelect(Parse *pParse, Select *pSelect){ pTab->nRef = 1; pTab->zName = 0; pTab->nRowLogEst = 200; assert( 200==sqlite3LogEst(1048576) ); - selectColumnsFromExprList(pParse, pSelect->pEList, &pTab->nCol, &pTab->aCol); + sqlite3ColumnsFromExprList(pParse, pSelect->pEList, &pTab->nCol, &pTab->aCol); selectAddColumnTypeAndCollation(pParse, pTab, pSelect); pTab->iPKey = -1; if( db->mallocFailed ){ @@ -102338,7 +111481,7 @@ static void computeLimitRegisters(Parse *pParse, Select *p, int iBreak){ Vdbe *v = 0; int iLimit = 0; int iOffset; - int addr1, n; + int n; if( p->iLimit ) return; /* @@ -102357,7 +111500,7 @@ static void computeLimitRegisters(Parse *pParse, Select *p, int iBreak){ sqlite3VdbeAddOp2(v, OP_Integer, n, iLimit); VdbeComment((v, "LIMIT counter")); if( n==0 ){ - sqlite3VdbeAddOp2(v, OP_Goto, 0, iBreak); + sqlite3VdbeGoto(v, iBreak); }else if( n>=0 && p->nSelectRow>(u64)n ){ p->nSelectRow = n; } @@ -102365,7 +111508,7 @@ static void computeLimitRegisters(Parse *pParse, Select *p, int iBreak){ sqlite3ExprCode(pParse, p->pLimit, iLimit); sqlite3VdbeAddOp1(v, OP_MustBeInt, iLimit); VdbeCoverage(v); VdbeComment((v, "LIMIT counter")); - sqlite3VdbeAddOp2(v, OP_IfZero, iLimit, iBreak); VdbeCoverage(v); + sqlite3VdbeAddOp2(v, OP_IfNot, iLimit, iBreak); VdbeCoverage(v); } if( p->pOffset ){ p->iOffset = iOffset = ++pParse->nMem; @@ -102373,14 +111516,10 @@ static void computeLimitRegisters(Parse *pParse, Select *p, int iBreak){ sqlite3ExprCode(pParse, p->pOffset, iOffset); sqlite3VdbeAddOp1(v, OP_MustBeInt, iOffset); VdbeCoverage(v); VdbeComment((v, "OFFSET counter")); - addr1 = sqlite3VdbeAddOp1(v, OP_IfPos, iOffset); VdbeCoverage(v); - sqlite3VdbeAddOp2(v, OP_Integer, 0, iOffset); - sqlite3VdbeJumpHere(v, addr1); + sqlite3VdbeAddOp3(v, OP_SetIfNotPos, iOffset, iOffset, 0); sqlite3VdbeAddOp3(v, OP_Add, iLimit, iOffset, iOffset+1); VdbeComment((v, "LIMIT+OFFSET")); - addr1 = sqlite3VdbeAddOp1(v, OP_IfPos, iLimit); VdbeCoverage(v); - sqlite3VdbeAddOp2(v, OP_Integer, -1, iOffset+1); - sqlite3VdbeJumpHere(v, addr1); + sqlite3VdbeAddOp3(v, OP_SetIfNotPos, iLimit, iOffset+1, -1); } } } @@ -102402,7 +111541,10 @@ static CollSeq *multiSelectCollSeq(Parse *pParse, Select *p, int iCol){ pRet = 0; } assert( iCol>=0 ); - if( pRet==0 && iColpEList->nExpr ){ + /* iCol must be less than p->pEList->nExpr. Otherwise an error would + ** have been thrown during name resolution and we would not have gotten + ** this far */ + if( pRet==0 && ALWAYS(iColpEList->nExpr) ){ pRet = sqlite3ExprCollSeq(pParse, p->pEList->a[iCol].pExpr); } return pRet; @@ -102457,7 +111599,7 @@ static KeyInfo *multiSelectOrderByKeyInfo(Parse *pParse, Select *p, int nExtra){ ** ** ** There is exactly one reference to the recursive-table in the FROM clause -** of recursive-query, marked with the SrcList->a[].isRecursive flag. +** of recursive-query, marked with the SrcList->a[].fg.isRecursive flag. ** ** The setup-query runs once to generate an initial set of rows that go ** into a Queue table. Rows are extracted from the Queue table one by @@ -102522,7 +111664,7 @@ static void generateWithRecursiveQuery( /* Locate the cursor number of the Current table */ for(i=0; ALWAYS(inSrc); i++){ - if( pSrc->a[i].isRecursive ){ + if( pSrc->a[i].fg.isRecursive ){ iCurrent = pSrc->a[i].iCursor; break; } @@ -102584,7 +111726,7 @@ static void generateWithRecursiveQuery( selectInnerLoop(pParse, p, p->pEList, iCurrent, 0, 0, pDest, addrCont, addrBreak); if( regLimit ){ - sqlite3VdbeAddOp3(v, OP_IfZero, regLimit, addrBreak, -1); + sqlite3VdbeAddOp2(v, OP_DecrJumpZero, regLimit, addrBreak); VdbeCoverage(v); } sqlite3VdbeResolveLabel(v, addrCont); @@ -102592,13 +111734,17 @@ static void generateWithRecursiveQuery( /* Execute the recursive SELECT taking the single row in Current as ** the value for the recursive-table. Store the results in the Queue. */ - p->pPrior = 0; - sqlite3Select(pParse, p, &destQueue); - assert( p->pPrior==0 ); - p->pPrior = pSetup; + if( p->selFlags & SF_Aggregate ){ + sqlite3ErrorMsg(pParse, "recursive aggregate queries not supported"); + }else{ + p->pPrior = 0; + sqlite3Select(pParse, p, &destQueue); + assert( p->pPrior==0 ); + p->pPrior = pSetup; + } /* Keep running the loop until the Queue is empty */ - sqlite3VdbeAddOp2(v, OP_Goto, 0, addrTop); + sqlite3VdbeGoto(v, addrTop); sqlite3VdbeResolveLabel(v, addrBreak); end_of_recursive_query: @@ -102617,6 +111763,48 @@ static int multiSelectOrderBy( SelectDest *pDest /* What to do with query results */ ); +/* +** Handle the special case of a compound-select that originates from a +** VALUES clause. By handling this as a special case, we avoid deep +** recursion, and thus do not need to enforce the SQLITE_LIMIT_COMPOUND_SELECT +** on a VALUES clause. +** +** Because the Select object originates from a VALUES clause: +** (1) It has no LIMIT or OFFSET +** (2) All terms are UNION ALL +** (3) There is no ORDER BY clause +*/ +static int multiSelectValues( + Parse *pParse, /* Parsing context */ + Select *p, /* The right-most of SELECTs to be coded */ + SelectDest *pDest /* What to do with query results */ +){ + Select *pPrior; + int nRow = 1; + int rc = 0; + assert( p->selFlags & SF_MultiValue ); + do{ + assert( p->selFlags & SF_Values ); + assert( p->op==TK_ALL || (p->op==TK_SELECT && p->pPrior==0) ); + assert( p->pLimit==0 ); + assert( p->pOffset==0 ); + assert( p->pNext==0 || p->pEList->nExpr==p->pNext->pEList->nExpr ); + if( p->pPrior==0 ) break; + assert( p->pPrior->pNext==p ); + p = p->pPrior; + nRow++; + }while(1); + while( p ){ + pPrior = p->pPrior; + p->pPrior = 0; + rc = sqlite3Select(pParse, p, pDest); + p->pPrior = pPrior; + if( rc ) break; + p->nSelectRow = nRow; + p = p->pNext; + } + return rc; +} /* ** This routine is called to process a compound query form from @@ -102698,20 +111886,18 @@ static int multiSelect( dest.eDest = SRT_Table; } + /* Special handling for a compound-select that originates as a VALUES clause. + */ + if( p->selFlags & SF_MultiValue ){ + rc = multiSelectValues(pParse, p, &dest); + goto multi_select_end; + } + /* Make sure all SELECTs in the statement have the same number of elements ** in their result sets. */ assert( p->pEList && pPrior->pEList ); - if( p->pEList->nExpr!=pPrior->pEList->nExpr ){ - if( p->selFlags & SF_Values ){ - sqlite3ErrorMsg(pParse, "all VALUES must have the same number of terms"); - }else{ - sqlite3ErrorMsg(pParse, "SELECTs to the left and right of %s" - " do not have the same number of result columns", selectOpName(p->op)); - } - rc = 1; - goto multi_select_end; - } + assert( p->pEList->nExpr==pPrior->pEList->nExpr ); #ifndef SQLITE_OMIT_CTE if( p->selFlags & SF_Recursive ){ @@ -102747,8 +111933,13 @@ static int multiSelect( p->iLimit = pPrior->iLimit; p->iOffset = pPrior->iOffset; if( p->iLimit ){ - addr = sqlite3VdbeAddOp1(v, OP_IfZero, p->iLimit); VdbeCoverage(v); + addr = sqlite3VdbeAddOp1(v, OP_IfNot, p->iLimit); VdbeCoverage(v); VdbeComment((v, "Jump ahead if LIMIT reached")); + if( p->iOffset ){ + sqlite3VdbeAddOp3(v, OP_SetIfNotPos, p->iOffset, p->iOffset, 0); + sqlite3VdbeAddOp3(v, OP_Add, p->iLimit, p->iOffset, p->iOffset+1); + sqlite3VdbeAddOp3(v, OP_SetIfNotPos, p->iLimit, p->iOffset+1, -1); + } } explainSetInteger(iSub2, pParse->iNextSelectId); rc = sqlite3Select(pParse, p, &dest); @@ -102849,7 +112040,7 @@ static int multiSelect( if( dest.eDest==SRT_Output ){ Select *pFirst = p; while( pFirst->pPrior ) pFirst = pFirst->pPrior; - generateColumnNames(pParse, 0, pFirst->pEList); + generateColumnNames(pParse, pFirst->pSrc, pFirst->pEList); } iBreak = sqlite3VdbeMakeLabel(v); iCont = sqlite3VdbeMakeLabel(v); @@ -102924,7 +112115,7 @@ static int multiSelect( if( dest.eDest==SRT_Output ){ Select *pFirst = p; while( pFirst->pPrior ) pFirst = pFirst->pPrior; - generateColumnNames(pParse, 0, pFirst->pEList); + generateColumnNames(pParse, pFirst->pSrc, pFirst->pEList); } iBreak = sqlite3VdbeMakeLabel(v); iCont = sqlite3VdbeMakeLabel(v); @@ -103003,6 +112194,19 @@ multi_select_end: } #endif /* SQLITE_OMIT_COMPOUND_SELECT */ +/* +** Error message for when two or more terms of a compound select have different +** size result sets. +*/ +SQLITE_PRIVATE void sqlite3SelectWrongNumTermsError(Parse *pParse, Select *p){ + if( p->selFlags & SF_Values ){ + sqlite3ErrorMsg(pParse, "all VALUES must have the same number of terms"); + }else{ + sqlite3ErrorMsg(pParse, "SELECTs to the left and right of %s" + " do not have the same number of result columns", selectOpName(p->op)); + } +} + /* ** Code an output subroutine for a coroutine implementation of a ** SELECT statment. @@ -103043,12 +112247,12 @@ static int generateOutputSubroutine( /* Suppress duplicates for UNION, EXCEPT, and INTERSECT */ if( regPrev ){ - int j1, j2; - j1 = sqlite3VdbeAddOp1(v, OP_IfNot, regPrev); VdbeCoverage(v); - j2 = sqlite3VdbeAddOp4(v, OP_Compare, pIn->iSdst, regPrev+1, pIn->nSdst, + int addr1, addr2; + addr1 = sqlite3VdbeAddOp1(v, OP_IfNot, regPrev); VdbeCoverage(v); + addr2 = sqlite3VdbeAddOp4(v, OP_Compare, pIn->iSdst, regPrev+1, pIn->nSdst, (char*)sqlite3KeyInfoRef(pKeyInfo), P4_KEYINFO); - sqlite3VdbeAddOp3(v, OP_Jump, j2+2, iContinue, j2+2); VdbeCoverage(v); - sqlite3VdbeJumpHere(v, j1); + sqlite3VdbeAddOp3(v, OP_Jump, addr2+2, iContinue, addr2+2); VdbeCoverage(v); + sqlite3VdbeJumpHere(v, addr1); sqlite3VdbeAddOp3(v, OP_Copy, pIn->iSdst, regPrev+1, pIn->nSdst-1); sqlite3VdbeAddOp2(v, OP_Integer, 1, regPrev); } @@ -103058,15 +112262,14 @@ static int generateOutputSubroutine( */ codeOffset(v, p->iOffset, iContinue); + assert( pDest->eDest!=SRT_Exists ); + assert( pDest->eDest!=SRT_Table ); switch( pDest->eDest ){ /* Store the result as data using a unique key. */ - case SRT_Table: case SRT_EphemTab: { int r1 = sqlite3GetTempReg(pParse); int r2 = sqlite3GetTempReg(pParse); - testcase( pDest->eDest==SRT_Table ); - testcase( pDest->eDest==SRT_EphemTab ); sqlite3VdbeAddOp3(v, OP_MakeRecord, pIn->iSdst, pIn->nSdst, r1); sqlite3VdbeAddOp2(v, OP_NewRowid, pDest->iSDParm, r2); sqlite3VdbeAddOp3(v, OP_Insert, pDest->iSDParm, r1, r2); @@ -103083,7 +112286,7 @@ static int generateOutputSubroutine( */ case SRT_Set: { int r1; - assert( pIn->nSdst==1 ); + assert( pIn->nSdst==1 || pParse->nErr>0 ); pDest->affSdst = sqlite3CompareAffinity(p->pEList->a[0].pExpr, pDest->affSdst); r1 = sqlite3GetTempReg(pParse); @@ -103094,22 +112297,12 @@ static int generateOutputSubroutine( break; } -#if 0 /* Never occurs on an ORDER BY query */ - /* If any row exist in the result set, record that fact and abort. - */ - case SRT_Exists: { - sqlite3VdbeAddOp2(v, OP_Integer, 1, pDest->iSDParm); - /* The LIMIT clause will terminate the loop for us */ - break; - } -#endif - /* If this is a scalar select that is part of an expression, then ** store the results in the appropriate memory cell and break out ** of the scan loop. */ case SRT_Mem: { - assert( pIn->nSdst==1 ); + assert( pIn->nSdst==1 || pParse->nErr>0 ); testcase( pIn->nSdst!=1 ); sqlite3ExprCodeMove(pParse, pIn->iSdst, pDest->iSDParm, 1); /* The LIMIT clause will jump out of the loop for us */ break; @@ -103124,7 +112317,7 @@ static int generateOutputSubroutine( pDest->iSdst = sqlite3GetTempRange(pParse, pIn->nSdst); pDest->nSdst = pIn->nSdst; } - sqlite3ExprCodeMove(pParse, pIn->iSdst, pDest->iSdst, pDest->nSdst); + sqlite3ExprCodeMove(pParse, pIn->iSdst, pDest->iSdst, pIn->nSdst); sqlite3VdbeAddOp1(v, OP_Yield, pDest->iSDParm); break; } @@ -103148,7 +112341,7 @@ static int generateOutputSubroutine( /* Jump to the end of the loop if the LIMIT is reached. */ if( p->iLimit ){ - sqlite3VdbeAddOp3(v, OP_IfZero, p->iLimit, iBreak, -1); VdbeCoverage(v); + sqlite3VdbeAddOp2(v, OP_DecrJumpZero, p->iLimit, iBreak); VdbeCoverage(v); } /* Generate the subroutine return @@ -103276,7 +112469,7 @@ static int multiSelectOrderBy( int savedOffset; /* Saved value of p->iOffset */ int labelCmpr; /* Label for the start of the merge algorithm */ int labelEnd; /* Label for the end of the overall SELECT stmt */ - int j1; /* Jump instructions that get retargetted */ + int addr1; /* Jump instructions that get retargetted */ int op; /* One of TK_ALL, TK_UNION, TK_EXCEPT, TK_INTERSECT */ KeyInfo *pKeyDup = 0; /* Comparison information for duplicate removal */ KeyInfo *pKeyMerge; /* Comparison information for merging rows */ @@ -103340,8 +112533,8 @@ static int multiSelectOrderBy( if( aPermute ){ struct ExprList_item *pItem; for(i=0, pItem=pOrderBy->a; iu.x.iOrderByCol>0 - && pItem->u.x.iOrderByCol<=p->pEList->nExpr ); + assert( pItem->u.x.iOrderByCol>0 ); + assert( pItem->u.x.iOrderByCol<=p->pEList->nExpr ); aPermute[i] = pItem->u.x.iOrderByCol - 1; } pKeyMerge = multiSelectOrderByKeyInfo(pParse, p, 1); @@ -103412,19 +112605,19 @@ static int multiSelectOrderBy( ** left of the compound operator - the "A" select. */ addrSelectA = sqlite3VdbeCurrentAddr(v) + 1; - j1 = sqlite3VdbeAddOp3(v, OP_InitCoroutine, regAddrA, 0, addrSelectA); + addr1 = sqlite3VdbeAddOp3(v, OP_InitCoroutine, regAddrA, 0, addrSelectA); VdbeComment((v, "left SELECT")); pPrior->iLimit = regLimitA; explainSetInteger(iSub1, pParse->iNextSelectId); sqlite3Select(pParse, pPrior, &destA); sqlite3VdbeAddOp1(v, OP_EndCoroutine, regAddrA); - sqlite3VdbeJumpHere(v, j1); + sqlite3VdbeJumpHere(v, addr1); /* Generate a coroutine to evaluate the SELECT statement on ** the right - the "B" select */ addrSelectB = sqlite3VdbeCurrentAddr(v) + 1; - j1 = sqlite3VdbeAddOp3(v, OP_InitCoroutine, regAddrB, 0, addrSelectB); + addr1 = sqlite3VdbeAddOp3(v, OP_InitCoroutine, regAddrB, 0, addrSelectB); VdbeComment((v, "right SELECT")); savedLimit = p->iLimit; savedOffset = p->iOffset; @@ -103465,7 +112658,7 @@ static int multiSelectOrderBy( addrEofA = sqlite3VdbeAddOp2(v, OP_Gosub, regOutB, addrOutB); addrEofA_noB = sqlite3VdbeAddOp2(v, OP_Yield, regAddrB, labelEnd); VdbeCoverage(v); - sqlite3VdbeAddOp2(v, OP_Goto, 0, addrEofA); + sqlite3VdbeGoto(v, addrEofA); p->nSelectRow += pPrior->nSelectRow; } @@ -103479,7 +112672,7 @@ static int multiSelectOrderBy( VdbeNoopComment((v, "eof-B subroutine")); addrEofB = sqlite3VdbeAddOp2(v, OP_Gosub, regOutA, addrOutA); sqlite3VdbeAddOp2(v, OP_Yield, regAddrA, labelEnd); VdbeCoverage(v); - sqlite3VdbeAddOp2(v, OP_Goto, 0, addrEofB); + sqlite3VdbeGoto(v, addrEofB); } /* Generate code to handle the case of AB @@ -103511,11 +112704,11 @@ static int multiSelectOrderBy( sqlite3VdbeAddOp2(v, OP_Gosub, regOutB, addrOutB); } sqlite3VdbeAddOp2(v, OP_Yield, regAddrB, addrEofB); VdbeCoverage(v); - sqlite3VdbeAddOp2(v, OP_Goto, 0, labelCmpr); + sqlite3VdbeGoto(v, labelCmpr); /* This code runs once to initialize everything. */ - sqlite3VdbeJumpHere(v, j1); + sqlite3VdbeJumpHere(v, addr1); sqlite3VdbeAddOp2(v, OP_Yield, regAddrA, addrEofA_noB); VdbeCoverage(v); sqlite3VdbeAddOp2(v, OP_Yield, regAddrB, addrEofB); VdbeCoverage(v); @@ -103537,7 +112730,7 @@ static int multiSelectOrderBy( if( pDest->eDest==SRT_Output ){ Select *pFirst = pPrior; while( pFirst->pPrior ) pFirst = pFirst->pPrior; - generateColumnNames(pParse, 0, pFirst->pEList); + generateColumnNames(pParse, pFirst->pSrc, pFirst->pEList); } /* Reassembly the compound query so that it will be freed correctly @@ -103551,14 +112744,14 @@ static int multiSelectOrderBy( /*** TBD: Insert subroutine calls to close cursors on incomplete **** subqueries ****/ explainComposite(pParse, p->op, iSub1, iSub2, 0); - return SQLITE_OK; + return pParse->nErr!=0; } #endif #if !defined(SQLITE_OMIT_SUBQUERY) || !defined(SQLITE_OMIT_VIEW) /* Forward Declarations */ static void substExprList(sqlite3*, ExprList*, int, ExprList*); -static void substSelect(sqlite3*, Select *, int, ExprList *); +static void substSelect(sqlite3*, Select *, int, ExprList*, int); /* ** Scan through the expression pExpr. Replace every reference to @@ -103595,7 +112788,7 @@ static Expr *substExpr( pExpr->pLeft = substExpr(db, pExpr->pLeft, iTable, pEList); pExpr->pRight = substExpr(db, pExpr->pRight, iTable, pEList); if( ExprHasProperty(pExpr, EP_xIsSelect) ){ - substSelect(db, pExpr->x.pSelect, iTable, pEList); + substSelect(db, pExpr->x.pSelect, iTable, pEList, 1); }else{ substExprList(db, pExpr->x.pList, iTable, pEList); } @@ -103618,25 +112811,28 @@ static void substSelect( sqlite3 *db, /* Report malloc errors here */ Select *p, /* SELECT statement in which to make substitutions */ int iTable, /* Table to be replaced */ - ExprList *pEList /* Substitute values */ + ExprList *pEList, /* Substitute values */ + int doPrior /* Do substitutes on p->pPrior too */ ){ SrcList *pSrc; struct SrcList_item *pItem; int i; if( !p ) return; - substExprList(db, p->pEList, iTable, pEList); - substExprList(db, p->pGroupBy, iTable, pEList); - substExprList(db, p->pOrderBy, iTable, pEList); - p->pHaving = substExpr(db, p->pHaving, iTable, pEList); - p->pWhere = substExpr(db, p->pWhere, iTable, pEList); - substSelect(db, p->pPrior, iTable, pEList); - pSrc = p->pSrc; - assert( pSrc ); /* Even for (SELECT 1) we have: pSrc!=0 but pSrc->nSrc==0 */ - if( ALWAYS(pSrc) ){ + do{ + substExprList(db, p->pEList, iTable, pEList); + substExprList(db, p->pGroupBy, iTable, pEList); + substExprList(db, p->pOrderBy, iTable, pEList); + p->pHaving = substExpr(db, p->pHaving, iTable, pEList); + p->pWhere = substExpr(db, p->pWhere, iTable, pEList); + pSrc = p->pSrc; + assert( pSrc!=0 ); for(i=pSrc->nSrc, pItem=pSrc->a; i>0; i--, pItem++){ - substSelect(db, pItem->pSelect, iTable, pEList); + substSelect(db, pItem->pSelect, iTable, pEList, 1); + if( pItem->fg.isTabFunc ){ + substExprList(db, pItem->u1.pFuncArg, iTable, pEList); + } } - } + }while( doPrior && (p = p->pPrior)!=0 ); } #endif /* !defined(SQLITE_OMIT_SUBQUERY) || !defined(SQLITE_OMIT_VIEW) */ @@ -103662,7 +112858,7 @@ static void substSelect( ** ** SELECT x+y AS a FROM t1 WHERE z<100 AND a>5 ** -** The code generated for this simpification gives the same result +** The code generated for this simplification gives the same result ** but only has to scan the data once. And because indices might ** exist on the table t1, a complete scan of the data might be ** avoided. @@ -103671,7 +112867,10 @@ static void substSelect( ** ** (1) The subquery and the outer query do not both use aggregates. ** -** (2) The subquery is not an aggregate or the outer query is not a join. +** (2) The subquery is not an aggregate or (2a) the outer query is not a join +** and (2b) the outer query does not use subqueries other than the one +** FROM-clause subquery that is a candidate for flattening. (2b is +** due to ticket [2f7170d73bf9abf80] from 2015-02-09.) ** ** (3) The subquery is not the right operand of a left outer join ** (Originally ticket #306. Strengthened by ticket #3300) @@ -103695,8 +112894,10 @@ static void substSelect( ** (9) The subquery does not use LIMIT or the outer query does not use ** aggregates. ** -** (10) The subquery does not use aggregates or the outer query does not -** use LIMIT. +** (**) Restriction (10) was removed from the code on 2005-02-05 but we +** accidently carried the comment forward until 2014-09-15. Original +** text: "The subquery does not use aggregates or the outer query +** does not use LIMIT." ** ** (11) The subquery and the outer query do not both have ORDER BY clauses. ** @@ -103759,6 +112960,11 @@ static void substSelect( ** parent to a compound query confuses the code that handles ** recursive queries in multiSelect(). ** +** (24) The subquery is not an aggregate that uses the built-in min() or +** or max() functions. (Without this restriction, a query like: +** "SELECT x FROM (SELECT max(y), x FROM t1)" would not necessarily +** return the value X for which Y was maximal.) +** ** ** In this routine, the "p" parameter is a pointer to the outer query. ** The subquery is p->pSrc->a[iFrom]. isAgg is true if the outer query @@ -103778,7 +112984,7 @@ static int flattenSubquery( int subqueryIsAgg /* True if the subquery uses aggregate functions */ ){ const char *zSavedAuthContext = pParse->zAuthContext; - Select *pParent; + Select *pParent; /* Current UNION ALL term of the other query */ Select *pSub; /* The inner query or "subquery" */ Select *pSub1; /* Pointer to the rightmost select in sub-query */ SrcList *pSrc; /* The FROM clause of the outer query */ @@ -103801,12 +113007,21 @@ static int flattenSubquery( iParent = pSubitem->iCursor; pSub = pSubitem->pSelect; assert( pSub!=0 ); - if( isAgg && subqueryIsAgg ) return 0; /* Restriction (1) */ - if( subqueryIsAgg && pSrc->nSrc>1 ) return 0; /* Restriction (2) */ + if( subqueryIsAgg ){ + if( isAgg ) return 0; /* Restriction (1) */ + if( pSrc->nSrc>1 ) return 0; /* Restriction (2a) */ + if( (p->pWhere && ExprHasProperty(p->pWhere,EP_Subquery)) + || (sqlite3ExprListFlags(p->pEList) & EP_Subquery)!=0 + || (sqlite3ExprListFlags(p->pOrderBy) & EP_Subquery)!=0 + ){ + return 0; /* Restriction (2b) */ + } + } + pSubSrc = pSub->pSrc; assert( pSubSrc ); /* Prior to version 3.1.2, when LIMIT and OFFSET had to be simple constants, - ** not arbitrary expresssions, we allowed some combining of LIMIT and OFFSET + ** not arbitrary expressions, we allowed some combining of LIMIT and OFFSET ** because they could be computed at compile-time. But when LIMIT and OFFSET ** became arbitrary expressions, we were forced to add restrictions (13) ** and (14). */ @@ -103831,8 +113046,14 @@ static int flattenSubquery( if( pSub->pLimit && (p->selFlags & SF_Distinct)!=0 ){ return 0; /* Restriction (21) */ } - if( pSub->selFlags & SF_Recursive ) return 0; /* Restriction (22) */ - if( (p->selFlags & SF_Recursive) && pSub->pPrior ) return 0; /* (23) */ + testcase( pSub->selFlags & SF_Recursive ); + testcase( pSub->selFlags & SF_MinMaxAgg ); + if( pSub->selFlags & (SF_Recursive|SF_MinMaxAgg) ){ + return 0; /* Restrictions (22) and (24) */ + } + if( (p->selFlags & SF_Recursive) && pSub->pPrior ){ + return 0; /* Restriction (23) */ + } /* OBSOLETE COMMENT 1: ** Restriction 3: If the subquery is a join, make sure the subquery is @@ -103866,7 +113087,7 @@ static int flattenSubquery( ** is fraught with danger. Best to avoid the whole thing. If the ** subquery is the right term of a LEFT JOIN, then do not flatten. */ - if( (pSubitem->jointype & JT_OUTER)!=0 ){ + if( (pSubitem->fg.jointype & JT_OUTER)!=0 ){ return 0; } @@ -103886,10 +113107,10 @@ static int flattenSubquery( testcase( (pSub1->selFlags & (SF_Distinct|SF_Aggregate))==SF_Distinct ); testcase( (pSub1->selFlags & (SF_Distinct|SF_Aggregate))==SF_Aggregate ); assert( pSub->pSrc!=0 ); + assert( pSub->pEList->nExpr==pSub1->pEList->nExpr ); if( (pSub1->selFlags & (SF_Distinct|SF_Aggregate))!=0 || (pSub1->pPrior && pSub1->op!=TK_ALL) || pSub1->pSrc->nSrc<1 - || pSub->pEList->nExpr!=pSub1->pEList->nExpr ){ return 0; } @@ -103906,6 +113127,8 @@ static int flattenSubquery( } /***** If we reach this point, flattening is permitted. *****/ + SELECTTRACE(1,pParse,p,("flatten %s.%p from term %d\n", + pSub->zSelName, pSub, iFrom)); /* Authorize the subquery */ pParse->zAuthContext = pSubitem->zName; @@ -103958,6 +113181,7 @@ static int flattenSubquery( p->pLimit = 0; p->pOffset = 0; pNew = sqlite3SelectDup(db, p, 0); + sqlite3SelectSetName(pNew, pSub->zSelName); p->pOffset = pOffset; p->pLimit = pLimit; p->pOrderBy = pOrderBy; @@ -103970,6 +113194,9 @@ static int flattenSubquery( if( pPrior ) pPrior->pNext = pNew; pNew->pNext = p; p->pPrior = pNew; + SELECTTRACE(2,pParse,p, + ("compound-subquery flattener creates %s.%p as peer\n", + pNew->zSelName, pNew)); } if( db->mallocFailed ) return 1; } @@ -104031,7 +113258,7 @@ static int flattenSubquery( if( pSrc ){ assert( pParent==p ); /* First time through the loop */ - jointype = pSubitem->jointype; + jointype = pSubitem->fg.jointype; }else{ assert( pParent!=p ); /* 2nd and subsequent times through the loop */ pSrc = pParent->pSrc = sqlite3SrcListAppend(db, 0, 0, 0); @@ -104052,9 +113279,9 @@ static int flattenSubquery( ** ** The outer query has 3 slots in its FROM clause. One slot of the ** outer query (the middle slot) is used by the subquery. The next - ** block of code will expand the out query to 4 slots. The middle - ** slot is expanded to two slots in order to make space for the - ** two elements in the FROM clause of the subquery. + ** block of code will expand the outer query FROM clause to 4 slots. + ** The middle slot is expanded to two slots in order to make space + ** for the two elements in the FROM clause of the subquery. */ if( nSubSrc>1 ){ pParent->pSrc = pSrc = sqlite3SrcListEnlarge(db, pSrc, nSubSrc-1,iFrom+1); @@ -104068,10 +113295,11 @@ static int flattenSubquery( */ for(i=0; ia[i+iFrom].pUsing); + assert( pSrc->a[i+iFrom].fg.isTabFunc==0 ); pSrc->a[i+iFrom] = pSubSrc->a[i]; memset(&pSubSrc->a[i], 0, sizeof(pSubSrc->a[i])); } - pSrc->a[iFrom].jointype = jointype; + pSrc->a[iFrom].fg.jointype = jointype; /* Now begin substituting subquery result set expressions for ** references to the iParent in the outer query. @@ -104093,36 +113321,39 @@ static int flattenSubquery( pList->a[i].zName = zName; } } - substExprList(db, pParent->pEList, iParent, pSub->pEList); - if( isAgg ){ - substExprList(db, pParent->pGroupBy, iParent, pSub->pEList); - pParent->pHaving = substExpr(db, pParent->pHaving, iParent, pSub->pEList); - } if( pSub->pOrderBy ){ + /* At this point, any non-zero iOrderByCol values indicate that the + ** ORDER BY column expression is identical to the iOrderByCol'th + ** expression returned by SELECT statement pSub. Since these values + ** do not necessarily correspond to columns in SELECT statement pParent, + ** zero them before transfering the ORDER BY clause. + ** + ** Not doing this may cause an error if a subsequent call to this + ** function attempts to flatten a compound sub-query into pParent + ** (the only way this can happen is if the compound sub-query is + ** currently part of pSub->pSrc). See ticket [d11a6e908f]. */ + ExprList *pOrderBy = pSub->pOrderBy; + for(i=0; inExpr; i++){ + pOrderBy->a[i].u.x.iOrderByCol = 0; + } assert( pParent->pOrderBy==0 ); - pParent->pOrderBy = pSub->pOrderBy; + assert( pSub->pPrior==0 ); + pParent->pOrderBy = pOrderBy; pSub->pOrderBy = 0; - }else if( pParent->pOrderBy ){ - substExprList(db, pParent->pOrderBy, iParent, pSub->pEList); - } - if( pSub->pWhere ){ - pWhere = sqlite3ExprDup(db, pSub->pWhere, 0); - }else{ - pWhere = 0; } + pWhere = sqlite3ExprDup(db, pSub->pWhere, 0); if( subqueryIsAgg ){ assert( pParent->pHaving==0 ); pParent->pHaving = pParent->pWhere; pParent->pWhere = pWhere; - pParent->pHaving = substExpr(db, pParent->pHaving, iParent, pSub->pEList); pParent->pHaving = sqlite3ExprAnd(db, pParent->pHaving, sqlite3ExprDup(db, pSub->pHaving, 0)); assert( pParent->pGroupBy==0 ); pParent->pGroupBy = sqlite3ExprListDup(db, pSub->pGroupBy, 0); }else{ - pParent->pWhere = substExpr(db, pParent->pWhere, iParent, pSub->pEList); pParent->pWhere = sqlite3ExprAnd(db, pParent->pWhere, pWhere); } + substSelect(db, pParent, iParent, pSub->pEList, 0); /* The flattened query is distinct if either the inner or the ** outer query is distinct. @@ -104146,10 +113377,88 @@ static int flattenSubquery( */ sqlite3SelectDelete(db, pSub1); +#if SELECTTRACE_ENABLED + if( sqlite3SelectTrace & 0x100 ){ + SELECTTRACE(0x100,pParse,p,("After flattening:\n")); + sqlite3TreeViewSelect(0, p, 0); + } +#endif + return 1; } #endif /* !defined(SQLITE_OMIT_SUBQUERY) || !defined(SQLITE_OMIT_VIEW) */ + + +#if !defined(SQLITE_OMIT_SUBQUERY) || !defined(SQLITE_OMIT_VIEW) +/* +** Make copies of relevant WHERE clause terms of the outer query into +** the WHERE clause of subquery. Example: +** +** SELECT * FROM (SELECT a AS x, c-d AS y FROM t1) WHERE x=5 AND y=10; +** +** Transformed into: +** +** SELECT * FROM (SELECT a AS x, c-d AS y FROM t1 WHERE a=5 AND c-d=10) +** WHERE x=5 AND y=10; +** +** The hope is that the terms added to the inner query will make it more +** efficient. +** +** Do not attempt this optimization if: +** +** (1) The inner query is an aggregate. (In that case, we'd really want +** to copy the outer WHERE-clause terms onto the HAVING clause of the +** inner query. But they probably won't help there so do not bother.) +** +** (2) The inner query is the recursive part of a common table expression. +** +** (3) The inner query has a LIMIT clause (since the changes to the WHERE +** close would change the meaning of the LIMIT). +** +** (4) The inner query is the right operand of a LEFT JOIN. (The caller +** enforces this restriction since this routine does not have enough +** information to know.) +** +** (5) The WHERE clause expression originates in the ON or USING clause +** of a LEFT JOIN. +** +** Return 0 if no changes are made and non-zero if one or more WHERE clause +** terms are duplicated into the subquery. +*/ +static int pushDownWhereTerms( + sqlite3 *db, /* The database connection (for malloc()) */ + Select *pSubq, /* The subquery whose WHERE clause is to be augmented */ + Expr *pWhere, /* The WHERE clause of the outer query */ + int iCursor /* Cursor number of the subquery */ +){ + Expr *pNew; + int nChng = 0; + if( pWhere==0 ) return 0; + if( (pSubq->selFlags & (SF_Aggregate|SF_Recursive))!=0 ){ + return 0; /* restrictions (1) and (2) */ + } + if( pSubq->pLimit!=0 ){ + return 0; /* restriction (3) */ + } + while( pWhere->op==TK_AND ){ + nChng += pushDownWhereTerms(db, pSubq, pWhere->pRight, iCursor); + pWhere = pWhere->pLeft; + } + if( ExprHasProperty(pWhere,EP_FromJoin) ) return 0; /* restriction 5 */ + if( sqlite3ExprIsTableConstant(pWhere, iCursor) ){ + nChng++; + while( pSubq ){ + pNew = sqlite3ExprDup(db, pWhere, 0); + pNew = substExpr(db, pNew, iCursor, pSubq->pEList); + pSubq->pWhere = sqlite3ExprAnd(db, pSubq->pWhere, pNew); + pSubq = pSubq->pPrior; + } + } + return nChng; +} +#endif /* !defined(SQLITE_OMIT_SUBQUERY) || !defined(SQLITE_OMIT_VIEW) */ + /* ** Based on the contents of the AggInfo structure indicated by the first ** argument, this function checks if the following are true: @@ -104192,7 +113501,7 @@ static u8 minMaxQuery(AggInfo *pAggInfo, ExprList **ppMinMax){ /* ** The select statement passed as the first argument is an aggregate query. -** The second argment is the associated aggregate-info object. This +** The second argument is the associated aggregate-info object. This ** function tests if the SELECT is of the form: ** ** SELECT count(*) FROM @@ -104233,20 +113542,20 @@ static Table *isSimpleCount(Select *p, AggInfo *pAggInfo){ ** pFrom->pIndex and return SQLITE_OK. */ SQLITE_PRIVATE int sqlite3IndexedByLookup(Parse *pParse, struct SrcList_item *pFrom){ - if( pFrom->pTab && pFrom->zIndex ){ + if( pFrom->pTab && pFrom->fg.isIndexedBy ){ Table *pTab = pFrom->pTab; - char *zIndex = pFrom->zIndex; + char *zIndexedBy = pFrom->u1.zIndexedBy; Index *pIdx; for(pIdx=pTab->pIndex; - pIdx && sqlite3StrICmp(pIdx->zName, zIndex); + pIdx && sqlite3StrICmp(pIdx->zName, zIndexedBy); pIdx=pIdx->pNext ); if( !pIdx ){ - sqlite3ErrorMsg(pParse, "no such index: %s", zIndex, 0); + sqlite3ErrorMsg(pParse, "no such index: %s", zIndexedBy, 0); pParse->checkSchema = 1; return SQLITE_ERROR; } - pFrom->pIndex = pIdx; + pFrom->pIBIndex = pIdx; } return SQLITE_OK; } @@ -104302,7 +113611,7 @@ static int convertCompoundSelectToSubquery(Walker *pWalker, Select *p){ if( pNewSrc==0 ) return WRC_Abort; *pNew = *p; p->pSrc = pNewSrc; - p->pEList = sqlite3ExprListAppend(pParse, 0, sqlite3Expr(db, TK_ALL, 0)); + p->pEList = sqlite3ExprListAppend(pParse, 0, sqlite3Expr(db, TK_ASTERISK, 0)); p->op = TK_SELECT; p->pWhere = 0; pNew->pGroupBy = 0; @@ -104310,7 +113619,10 @@ static int convertCompoundSelectToSubquery(Walker *pWalker, Select *p){ pNew->pOrderBy = 0; p->pPrior = 0; p->pNext = 0; + p->pWith = 0; p->selFlags &= ~SF_Compound; + assert( (p->selFlags & SF_Converted)==0 ); + p->selFlags |= SF_Converted; assert( pNew->pPrior!=0 ); pNew->pPrior->pNext = pNew; pNew->pLimit = 0; @@ -104318,6 +113630,19 @@ static int convertCompoundSelectToSubquery(Walker *pWalker, Select *p){ return WRC_Continue; } +/* +** Check to see if the FROM clause term pFrom has table-valued function +** arguments. If it does, leave an error message in pParse and return +** non-zero, since pFrom is not allowed to be a table-valued function. +*/ +static int cannotBeFunction(Parse *pParse, struct SrcList_item *pFrom){ + if( pFrom->fg.isTabFunc ){ + sqlite3ErrorMsg(pParse, "'%s' is not a function", pFrom->zName); + return 1; + } + return 0; +} + #ifndef SQLITE_OMIT_CTE /* ** Argument pWith (which may be NULL) points to a linked list of nested @@ -104330,7 +113655,7 @@ static int convertCompoundSelectToSubquery(Walker *pWalker, Select *p){ ** object that the returned CTE belongs to. */ static struct Cte *searchWith( - With *pWith, /* Current outermost WITH clause */ + With *pWith, /* Current innermost WITH clause */ struct SrcList_item *pItem, /* FROM clause element to resolve */ With **ppContext /* OUT: WITH clause return value belongs to */ ){ @@ -104361,11 +113686,12 @@ static struct Cte *searchWith( ** statement with which it is associated. */ SQLITE_PRIVATE void sqlite3WithPush(Parse *pParse, With *pWith, u8 bFree){ - assert( bFree==0 || pParse->pWith==0 ); + assert( bFree==0 || (pParse->pWith==0 && pParse->pWithToFree==0) ); if( pWith ){ + assert( pParse->pWith!=pWith ); pWith->pOuter = pParse->pWith; pParse->pWith = pWith; - pParse->bFreeWith = bFree; + if( bFree ) pParse->pWithToFree = pWith; } } @@ -104404,14 +113730,15 @@ static int withExpand( int bMayRecursive; /* True if compound joined by UNION [ALL] */ With *pSavedWith; /* Initial value of pParse->pWith */ - /* If pCte->zErr is non-NULL at this point, then this is an illegal + /* If pCte->zCteErr is non-NULL at this point, then this is an illegal ** recursive reference to CTE pCte. Leave an error in pParse and return - ** early. If pCte->zErr is NULL, then this is not a recursive reference. + ** early. If pCte->zCteErr is NULL, then this is not a recursive reference. ** In this case, proceed. */ - if( pCte->zErr ){ - sqlite3ErrorMsg(pParse, pCte->zErr, pCte->zName); + if( pCte->zCteErr ){ + sqlite3ErrorMsg(pParse, pCte->zCteErr, pCte->zName); return SQLITE_ERROR; } + if( cannotBeFunction(pParse, pFrom) ) return SQLITE_ERROR; assert( pFrom->pTab==0 ); pFrom->pTab = pTab = sqlite3DbMallocZero(db, sizeof(Table)); @@ -104420,7 +113747,7 @@ static int withExpand( pTab->zName = sqlite3DbStrDup(db, pCte->zName); pTab->iPKey = -1; pTab->nRowLogEst = 200; assert( 200==sqlite3LogEst(1048576) ); - pTab->tabFlags |= TF_Ephemeral; + pTab->tabFlags |= TF_Ephemeral | TF_NoVisibleRowid; pFrom->pSelect = sqlite3SelectDup(db, pCte->pSelect, 0); if( db->mallocFailed ) return SQLITE_NOMEM; assert( pFrom->pSelect ); @@ -104438,7 +113765,7 @@ static int withExpand( && 0==sqlite3StrICmp(pItem->zName, pCte->zName) ){ pItem->pTab = pTab; - pItem->isRecursive = 1; + pItem->fg.isRecursive = 1; pTab->nRef++; pSel->selFlags |= SF_Recursive; } @@ -104454,15 +113781,16 @@ static int withExpand( } assert( pTab->nRef==1 || ((pSel->selFlags&SF_Recursive) && pTab->nRef==2 )); - pCte->zErr = "circular reference: %s"; + pCte->zCteErr = "circular reference: %s"; pSavedWith = pParse->pWith; pParse->pWith = pWith; sqlite3WalkSelect(pWalker, bMayRecursive ? pSel->pPrior : pSel); + pParse->pWith = pWith; for(pLeft=pSel; pLeft->pPrior; pLeft=pLeft->pPrior); pEList = pLeft->pEList; if( pCte->pCols ){ - if( pEList->nExpr!=pCte->pCols->nExpr ){ + if( pEList && pEList->nExpr!=pCte->pCols->nExpr ){ sqlite3ErrorMsg(pParse, "table %s has %d values for %d columns", pCte->zName, pEList->nExpr, pCte->pCols->nExpr ); @@ -104472,16 +113800,16 @@ static int withExpand( pEList = pCte->pCols; } - selectColumnsFromExprList(pParse, pEList, &pTab->nCol, &pTab->aCol); + sqlite3ColumnsFromExprList(pParse, pEList, &pTab->nCol, &pTab->aCol); if( bMayRecursive ){ if( pSel->selFlags & SF_Recursive ){ - pCte->zErr = "multiple recursive references: %s"; + pCte->zCteErr = "multiple recursive references: %s"; }else{ - pCte->zErr = "recursive reference in a subquery: %s"; + pCte->zCteErr = "recursive reference in a subquery: %s"; } sqlite3WalkSelect(pWalker, pSel); } - pCte->zErr = 0; + pCte->zCteErr = 0; pParse->pWith = pSavedWith; } @@ -104522,10 +113850,10 @@ static void selectPopWith(Walker *pWalker, Select *p){ ** fill pTabList->a[].pSelect with a copy of the SELECT statement ** that implements the view. A copy is made of the view's SELECT ** statement so that we can freely modify or delete that statement -** without worrying about messing up the presistent representation +** without worrying about messing up the persistent representation ** of the view. ** -** (3) Add terms to the WHERE clause to accomodate the NATURAL keyword +** (3) Add terms to the WHERE clause to accommodate the NATURAL keyword ** on joins and the ON and USING clause of joins. ** ** (4) Scan the list of columns in the result set (pEList) looking @@ -104553,7 +113881,9 @@ static int selectExpander(Walker *pWalker, Select *p){ } pTabList = p->pSrc; pEList = p->pEList; - sqlite3WithPush(pParse, findRightmost(p)->pWith, 0); + if( pWalker->xSelectCallback2==selectPopWith ){ + sqlite3WithPush(pParse, findRightmost(p)->pWith, 0); + } /* Make sure cursor numbers have been assigned to all entries in ** the FROM clause of the SELECT statement. @@ -104566,17 +113896,9 @@ static int selectExpander(Walker *pWalker, Select *p){ */ for(i=0, pFrom=pTabList->a; inSrc; i++, pFrom++){ Table *pTab; - assert( pFrom->isRecursive==0 || pFrom->pTab ); - if( pFrom->isRecursive ) continue; - if( pFrom->pTab!=0 ){ - /* This statement has already been prepared. There is no need - ** to go further. */ - assert( i==0 ); -#ifndef SQLITE_OMIT_CTE - selectPopWith(pWalker, p); -#endif - return WRC_Prune; - } + assert( pFrom->fg.isRecursive==0 || pFrom->pTab!=0 ); + if( pFrom->fg.isRecursive ) continue; + assert( pFrom->pTab==0 ); #ifndef SQLITE_OMIT_CTE if( withExpand(pWalker, pFrom) ) return WRC_Abort; if( pFrom->pTab ) {} else @@ -104587,13 +113909,13 @@ static int selectExpander(Walker *pWalker, Select *p){ /* A sub-query in the FROM clause of a SELECT */ assert( pSel!=0 ); assert( pFrom->pTab==0 ); - sqlite3WalkSelect(pWalker, pSel); + if( sqlite3WalkSelect(pWalker, pSel) ) return WRC_Abort; pFrom->pTab = pTab = sqlite3DbMallocZero(db, sizeof(Table)); if( pTab==0 ) return WRC_Abort; pTab->nRef = 1; pTab->zName = sqlite3MPrintf(db, "sqlite_sq_%p", (void*)pTab); while( pSel->pPrior ){ pSel = pSel->pPrior; } - selectColumnsFromExprList(pParse, pSel->pEList, &pTab->nCol, &pTab->aCol); + sqlite3ColumnsFromExprList(pParse, pSel->pEList,&pTab->nCol,&pTab->aCol); pTab->iPKey = -1; pTab->nRowLogEst = 200; assert( 200==sqlite3LogEst(1048576) ); pTab->tabFlags |= TF_Ephemeral; @@ -104610,13 +113932,20 @@ static int selectExpander(Walker *pWalker, Select *p){ return WRC_Abort; } pTab->nRef++; + if( !IsVirtual(pTab) && cannotBeFunction(pParse, pFrom) ){ + return WRC_Abort; + } #if !defined(SQLITE_OMIT_VIEW) || !defined (SQLITE_OMIT_VIRTUALTABLE) - if( pTab->pSelect || IsVirtual(pTab) ){ - /* We reach here if the named table is a really a view */ + if( IsVirtual(pTab) || pTab->pSelect ){ + i16 nCol; if( sqlite3ViewGetColumnNames(pParse, pTab) ) return WRC_Abort; assert( pFrom->pSelect==0 ); pFrom->pSelect = sqlite3SelectDup(db, pTab->pSelect, 0); + sqlite3SelectSetName(pFrom->pSelect, pTab->zName); + nCol = pTab->nCol; + pTab->nCol = -1; sqlite3WalkSelect(pWalker, pFrom->pSelect); + pTab->nCol = nCol; } #endif } @@ -104636,19 +113965,20 @@ static int selectExpander(Walker *pWalker, Select *p){ /* For every "*" that occurs in the column list, insert the names of ** all columns in all tables. And for every TABLE.* insert the names ** of all columns in TABLE. The parser inserted a special expression - ** with the TK_ALL operator for each "*" that it found in the column list. - ** The following code just has to locate the TK_ALL expressions and expand - ** each one to the list of all columns in all tables. + ** with the TK_ASTERISK operator for each "*" that it found in the column + ** list. The following code just has to locate the TK_ASTERISK + ** expressions and expand each one to the list of all columns in + ** all tables. ** ** The first loop just checks to see if there are any "*" operators ** that need expanding. */ for(k=0; knExpr; k++){ pE = pEList->a[k].pExpr; - if( pE->op==TK_ALL ) break; + if( pE->op==TK_ASTERISK ) break; assert( pE->op!=TK_DOT || pE->pRight!=0 ); assert( pE->op!=TK_DOT || (pE->pLeft!=0 && pE->pLeft->op==TK_ID) ); - if( pE->op==TK_DOT && pE->pRight->op==TK_ALL ) break; + if( pE->op==TK_DOT && pE->pRight->op==TK_ASTERISK ) break; } if( knExpr ){ /* @@ -104662,18 +113992,13 @@ static int selectExpander(Walker *pWalker, Select *p){ int longNames = (flags & SQLITE_FullColNames)!=0 && (flags & SQLITE_ShortColNames)==0; - /* When processing FROM-clause subqueries, it is always the case - ** that full_column_names=OFF and short_column_names=ON. The - ** sqlite3ResultSetOfSelect() routine makes it so. */ - assert( (p->selFlags & SF_NestedFrom)==0 - || ((flags & SQLITE_FullColNames)==0 && - (flags & SQLITE_ShortColNames)!=0) ); - for(k=0; knExpr; k++){ pE = a[k].pExpr; pRight = pE->pRight; assert( pE->op!=TK_DOT || pRight!=0 ); - if( pE->op!=TK_ALL && (pE->op!=TK_DOT || pRight->op!=TK_ALL) ){ + if( pE->op!=TK_ASTERISK + && (pE->op!=TK_DOT || pRight->op!=TK_ASTERISK) + ){ /* This particular expression does not need to be expanded. */ pNew = sqlite3ExprListAppend(pParse, pNew, a[k].pExpr); @@ -104725,18 +114050,19 @@ static int selectExpander(Walker *pWalker, Select *p){ continue; } - /* If a column is marked as 'hidden' (currently only possible - ** for virtual tables), do not include it in the expanded - ** result-set list. + /* If a column is marked as 'hidden', omit it from the expanded + ** result-set list unless the SELECT has the SF_IncludeHidden + ** bit set. */ - if( IsHiddenColumn(&pTab->aCol[j]) ){ - assert(IsVirtual(pTab)); + if( (p->selFlags & SF_IncludeHidden)==0 + && IsHiddenColumn(&pTab->aCol[j]) + ){ continue; } tableSeen = 1; if( i>0 && zTName==0 ){ - if( (pFrom->jointype & JT_NATURAL)!=0 + if( (pFrom->fg.jointype & JT_NATURAL)!=0 && tableAndColumnIndex(pTabList, i, zName, 0, 0) ){ /* In a NATURAL join, omit the join columns from the @@ -104801,6 +114127,7 @@ static int selectExpander(Walker *pWalker, Select *p){ #if SQLITE_MAX_COLUMN if( p->pEList && p->pEList->nExpr>db->aLimit[SQLITE_LIMIT_COLUMN] ){ sqlite3ErrorMsg(pParse, "too many columns in result set"); + return WRC_Abort; } #endif return WRC_Continue; @@ -104815,7 +114142,7 @@ static int selectExpander(Walker *pWalker, Select *p){ ** Walker.xSelectCallback is set to do something useful for every ** subquery in the parser tree. */ -static int exprWalkNoop(Walker *NotUsed, Expr *NotUsed2){ +SQLITE_PRIVATE int sqlite3ExprWalkNoop(Walker *NotUsed, Expr *NotUsed2){ UNUSED_PARAMETER2(NotUsed, NotUsed2); return WRC_Continue; } @@ -104836,14 +114163,16 @@ static int exprWalkNoop(Walker *NotUsed, Expr *NotUsed2){ static void sqlite3SelectExpand(Parse *pParse, Select *pSelect){ Walker w; memset(&w, 0, sizeof(w)); - w.xExprCallback = exprWalkNoop; + w.xExprCallback = sqlite3ExprWalkNoop; w.pParse = pParse; if( pParse->hasCompound ){ w.xSelectCallback = convertCompoundSelectToSubquery; sqlite3WalkSelect(&w, pSelect); } w.xSelectCallback = selectExpander; - w.xSelectCallback2 = selectPopWith; + if( (pSelect->selFlags & SF_MultiValue)==0 ){ + w.xSelectCallback2 = selectPopWith; + } sqlite3WalkSelect(&w, pSelect); } @@ -104869,19 +114198,19 @@ static void selectAddSubqueryTypeInfo(Walker *pWalker, Select *p){ struct SrcList_item *pFrom; assert( p->selFlags & SF_Resolved ); - if( (p->selFlags & SF_HasTypeInfo)==0 ){ - p->selFlags |= SF_HasTypeInfo; - pParse = pWalker->pParse; - pTabList = p->pSrc; - for(i=0, pFrom=pTabList->a; inSrc; i++, pFrom++){ - Table *pTab = pFrom->pTab; - if( ALWAYS(pTab!=0) && (pTab->tabFlags & TF_Ephemeral)!=0 ){ - /* A sub-query in the FROM clause of a SELECT */ - Select *pSel = pFrom->pSelect; - if( pSel ){ - while( pSel->pPrior ) pSel = pSel->pPrior; - selectAddColumnTypeAndCollation(pParse, pTab, pSel); - } + assert( (p->selFlags & SF_HasTypeInfo)==0 ); + p->selFlags |= SF_HasTypeInfo; + pParse = pWalker->pParse; + pTabList = p->pSrc; + for(i=0, pFrom=pTabList->a; inSrc; i++, pFrom++){ + Table *pTab = pFrom->pTab; + assert( pTab!=0 ); + if( (pTab->tabFlags & TF_Ephemeral)!=0 ){ + /* A sub-query in the FROM clause of a SELECT */ + Select *pSel = pFrom->pSelect; + if( pSel ){ + while( pSel->pPrior ) pSel = pSel->pPrior; + selectAddColumnTypeAndCollation(pParse, pTab, pSel); } } } @@ -104901,7 +114230,7 @@ static void sqlite3SelectAddTypeInfo(Parse *pParse, Select *pSelect){ Walker w; memset(&w, 0, sizeof(w)); w.xSelectCallback2 = selectAddSubqueryTypeInfo; - w.xExprCallback = exprWalkNoop; + w.xExprCallback = sqlite3ExprWalkNoop; w.pParse = pParse; sqlite3WalkSelect(&w, pSelect); #endif @@ -105020,14 +114349,15 @@ static void updateAccumulator(Parse *pParse, AggInfo *pAggInfo){ if( pList ){ nArg = pList->nExpr; regAgg = sqlite3GetTempRange(pParse, nArg); - sqlite3ExprCodeExprList(pParse, pList, regAgg, SQLITE_ECEL_DUP); + sqlite3ExprCodeExprList(pParse, pList, regAgg, 0, SQLITE_ECEL_DUP); }else{ nArg = 0; regAgg = 0; } if( pF->iDistinct>=0 ){ addrNext = sqlite3VdbeMakeLabel(v); - assert( nArg==1 ); + testcase( nArg==0 ); /* Error condition */ + testcase( nArg>1 ); /* Also an error */ codeDistinct(pParse, pF->iDistinct, addrNext, 1, regAgg); } if( pF->pFunc->funcFlags & SQLITE_FUNC_NEEDCOLL ){ @@ -105044,7 +114374,7 @@ static void updateAccumulator(Parse *pParse, AggInfo *pAggInfo){ if( regHit==0 && pAggInfo->nAccumulator ) regHit = ++pParse->nMem; sqlite3VdbeAddOp4(v, OP_CollSeq, regHit, 0, 0, (char *)pColl, P4_COLLSEQ); } - sqlite3VdbeAddOp4(v, OP_AggStep, 0, regAgg, pF->iMem, + sqlite3VdbeAddOp4(v, OP_AggStep0, 0, regAgg, pF->iMem, (void*)pF->pFunc, P4_FUNCDEF); sqlite3VdbeChangeP5(v, (u8)nArg); sqlite3ExprCacheAffinityChange(pParse, regAgg, nArg); @@ -105127,7 +114457,7 @@ SQLITE_PRIVATE int sqlite3Select( WhereInfo *pWInfo; /* Return from sqlite3WhereBegin() */ Vdbe *v; /* The virtual machine under construction */ int isAgg; /* True for select lists like "count(*)" */ - ExprList *pEList; /* List of columns to extract. */ + ExprList *pEList = 0; /* List of columns to extract. */ SrcList *pTabList; /* List of tables to select from */ Expr *pWhere; /* The WHERE clause. May be NULL */ ExprList *pGroupBy; /* The GROUP BY clause. May be NULL */ @@ -105150,6 +114480,13 @@ SQLITE_PRIVATE int sqlite3Select( } if( sqlite3AuthCheck(pParse, SQLITE_SELECT, 0, 0, 0) ) return 1; memset(&sAggInfo, 0, sizeof(sAggInfo)); +#if SELECTTRACE_ENABLED + pParse->nSelectIndent++; + SELECTTRACE(1,pParse,p, ("begin processing:\n")); + if( sqlite3SelectTrace & 0x100 ){ + sqlite3TreeViewSelect(0, p, 0); + } +#endif assert( p->pOrderBy==0 || pDest->eDest!=SRT_DistFifo ); assert( p->pOrderBy==0 || pDest->eDest!=SRT_Fifo ); @@ -105170,36 +114507,90 @@ SQLITE_PRIVATE int sqlite3Select( memset(&sSort, 0, sizeof(sSort)); sSort.pOrderBy = p->pOrderBy; pTabList = p->pSrc; - pEList = p->pEList; if( pParse->nErr || db->mallocFailed ){ goto select_end; } + assert( p->pEList!=0 ); isAgg = (p->selFlags & SF_Aggregate)!=0; - assert( pEList!=0 ); +#if SELECTTRACE_ENABLED + if( sqlite3SelectTrace & 0x100 ){ + SELECTTRACE(0x100,pParse,p, ("after name resolution:\n")); + sqlite3TreeViewSelect(0, p, 0); + } +#endif - /* Begin generating code. - */ - v = sqlite3GetVdbe(pParse); - if( v==0 ) goto select_end; /* If writing to memory or generating a set ** only a single column may be output. */ #ifndef SQLITE_OMIT_SUBQUERY - if( checkForMultiColumnSelectError(pParse, pDest, pEList->nExpr) ){ + if( checkForMultiColumnSelectError(pParse, pDest, p->pEList->nExpr) ){ goto select_end; } #endif + /* Try to flatten subqueries in the FROM clause up into the main query + */ +#if !defined(SQLITE_OMIT_SUBQUERY) || !defined(SQLITE_OMIT_VIEW) + for(i=0; !p->pPrior && inSrc; i++){ + struct SrcList_item *pItem = &pTabList->a[i]; + Select *pSub = pItem->pSelect; + int isAggSub; + Table *pTab = pItem->pTab; + if( pSub==0 ) continue; + + /* Catch mismatch in the declared columns of a view and the number of + ** columns in the SELECT on the RHS */ + if( pTab->nCol!=pSub->pEList->nExpr ){ + sqlite3ErrorMsg(pParse, "expected %d columns for '%s' but got %d", + pTab->nCol, pTab->zName, pSub->pEList->nExpr); + goto select_end; + } + + isAggSub = (pSub->selFlags & SF_Aggregate)!=0; + if( flattenSubquery(pParse, p, i, isAgg, isAggSub) ){ + /* This subquery can be absorbed into its parent. */ + if( isAggSub ){ + isAgg = 1; + p->selFlags |= SF_Aggregate; + } + i = -1; + } + pTabList = p->pSrc; + if( db->mallocFailed ) goto select_end; + if( !IgnorableOrderby(pDest) ){ + sSort.pOrderBy = p->pOrderBy; + } + } +#endif + + /* Get a pointer the VDBE under construction, allocating a new VDBE if one + ** does not already exist */ + v = sqlite3GetVdbe(pParse); + if( v==0 ) goto select_end; + +#ifndef SQLITE_OMIT_COMPOUND_SELECT + /* Handle compound SELECT statements using the separate multiSelect() + ** procedure. + */ + if( p->pPrior ){ + rc = multiSelect(pParse, p, pDest); + explainSetInteger(pParse->iSelectId, iRestoreSelectId); +#if SELECTTRACE_ENABLED + SELECTTRACE(1,pParse,p,("end compound-select processing\n")); + pParse->nSelectIndent--; +#endif + return rc; + } +#endif + /* Generate code for all sub-queries in the FROM clause */ #if !defined(SQLITE_OMIT_SUBQUERY) || !defined(SQLITE_OMIT_VIEW) - for(i=0; !p->pPrior && inSrc; i++){ + for(i=0; inSrc; i++){ struct SrcList_item *pItem = &pTabList->a[i]; SelectDest dest; Select *pSub = pItem->pSelect; - int isAggSub; - if( pSub==0 ) continue; /* Sometimes the code for a subquery will be generated more than @@ -105209,7 +114600,7 @@ SQLITE_PRIVATE int sqlite3Select( ** is sufficient, though the subroutine to manifest the view does need ** to be invoked again. */ if( pItem->addrFillSub ){ - if( pItem->viaCoroutine==0 ){ + if( pItem->fg.viaCoroutine==0 ){ sqlite3VdbeAddOp2(v, OP_Gosub, pItem->regReturn, pItem->addrFillSub); } continue; @@ -105224,16 +114615,25 @@ SQLITE_PRIVATE int sqlite3Select( */ pParse->nHeight += sqlite3SelectExprHeight(p); - isAggSub = (pSub->selFlags & SF_Aggregate)!=0; - if( flattenSubquery(pParse, p, i, isAgg, isAggSub) ){ - /* This subquery can be absorbed into its parent. */ - if( isAggSub ){ - isAgg = 1; - p->selFlags |= SF_Aggregate; + /* Make copies of constant WHERE-clause terms in the outer query down + ** inside the subquery. This can help the subquery to run more efficiently. + */ + if( (pItem->fg.jointype & JT_OUTER)==0 + && pushDownWhereTerms(db, pSub, p->pWhere, pItem->iCursor) + ){ +#if SELECTTRACE_ENABLED + if( sqlite3SelectTrace & 0x100 ){ + SELECTTRACE(0x100,pParse,p,("After WHERE-clause push-down:\n")); + sqlite3TreeViewSelect(0, p, 0); } - i = -1; - }else if( pTabList->nSrc==1 - && OptimizationEnabled(db, SQLITE_SubqCoroutine) +#endif + } + + /* Generate code to implement the subquery + */ + if( pTabList->nSrc==1 + && (p->selFlags & SF_All)==0 + && OptimizationEnabled(db, SQLITE_SubqCoroutine) ){ /* Implement a co-routine that will return a single row of the result ** set on each invocation. @@ -105247,7 +114647,7 @@ SQLITE_PRIVATE int sqlite3Select( explainSetInteger(pItem->iSelectId, (u8)pParse->iNextSelectId); sqlite3Select(pParse, pSub, &dest); pItem->pTab->nRowLogEst = sqlite3LogEst(pSub->nSelectRow); - pItem->viaCoroutine = 1; + pItem->fg.viaCoroutine = 1; pItem->regResult = dest.iSdst; sqlite3VdbeAddOp1(v, OP_EndCoroutine, pItem->regReturn); sqlite3VdbeJumpHere(v, addrTop-1); @@ -105265,7 +114665,7 @@ SQLITE_PRIVATE int sqlite3Select( pItem->regReturn = ++pParse->nMem; topAddr = sqlite3VdbeAddOp2(v, OP_Integer, 0, pItem->regReturn); pItem->addrFillSub = topAddr+1; - if( pItem->isCorrelated==0 ){ + if( pItem->fg.isCorrelated==0 ){ /* If the subquery is not correlated and if we are not inside of ** a trigger, then we only need to compute the value of the subquery ** once. */ @@ -105284,29 +114684,23 @@ SQLITE_PRIVATE int sqlite3Select( sqlite3VdbeChangeP1(v, topAddr, retAddr); sqlite3ClearTempRegCache(pParse); } - if( /*pParse->nErr ||*/ db->mallocFailed ){ - goto select_end; - } + if( db->mallocFailed ) goto select_end; pParse->nHeight -= sqlite3SelectExprHeight(p); - pTabList = p->pSrc; - if( !IgnorableOrderby(pDest) ){ - sSort.pOrderBy = p->pOrderBy; - } } - pEList = p->pEList; #endif + + /* Various elements of the SELECT copied into local variables for + ** convenience */ + pEList = p->pEList; pWhere = p->pWhere; pGroupBy = p->pGroupBy; pHaving = p->pHaving; sDistinct.isTnct = (p->selFlags & SF_Distinct)!=0; -#ifndef SQLITE_OMIT_COMPOUND_SELECT - /* If there is are a sequence of queries, do the earlier ones first. - */ - if( p->pPrior ){ - rc = multiSelect(pParse, p, pDest); - explainSetInteger(pParse->iSelectId, iRestoreSelectId); - return rc; +#if SELECTTRACE_ENABLED + if( sqlite3SelectTrace & 0x400 ){ + SELECTTRACE(0x400,pParse,p,("After all FROM-clause analysis:\n")); + sqlite3TreeViewSelect(0, p, 0); } #endif @@ -105318,7 +114712,7 @@ SQLITE_PRIVATE int sqlite3Select( ** ** is transformed to: ** - ** SELECT xyz FROM ... GROUP BY xyz + ** SELECT xyz FROM ... GROUP BY xyz ORDER BY xyz ** ** The second form is preferred as a single index (or temp-table) may be ** used for both the ORDER BY and DISTINCT processing. As originally @@ -105326,33 +114720,33 @@ SQLITE_PRIVATE int sqlite3Select( ** BY and DISTINCT, and an index or separate temp-table for the other. */ if( (p->selFlags & (SF_Distinct|SF_Aggregate))==SF_Distinct - && sqlite3ExprListCompare(sSort.pOrderBy, p->pEList, -1)==0 + && sqlite3ExprListCompare(sSort.pOrderBy, pEList, -1)==0 ){ p->selFlags &= ~SF_Distinct; - p->pGroupBy = sqlite3ExprListDup(db, p->pEList, 0); - pGroupBy = p->pGroupBy; - sSort.pOrderBy = 0; + pGroupBy = p->pGroupBy = sqlite3ExprListDup(db, pEList, 0); /* Notice that even thought SF_Distinct has been cleared from p->selFlags, ** the sDistinct.isTnct is still set. Hence, isTnct represents the ** original setting of the SF_Distinct flag, not the current setting */ assert( sDistinct.isTnct ); } - /* If there is an ORDER BY clause, then this sorting - ** index might end up being unused if the data can be - ** extracted in pre-sorted order. If that is the case, then the - ** OP_OpenEphemeral instruction will be changed to an OP_Noop once - ** we figure out that the sorting index is not needed. The addrSortIndex - ** variable is used to facilitate that change. + /* If there is an ORDER BY clause, then create an ephemeral index to + ** do the sorting. But this sorting ephemeral index might end up + ** being unused if the data can be extracted in pre-sorted order. + ** If that is the case, then the OP_OpenEphemeral instruction will be + ** changed to an OP_Noop once we figure out that the sorting index is + ** not needed. The sSort.addrSortIndex variable is used to facilitate + ** that change. */ if( sSort.pOrderBy ){ KeyInfo *pKeyInfo; - pKeyInfo = keyInfoFromExprList(pParse, sSort.pOrderBy, 0, 0); + pKeyInfo = keyInfoFromExprList(pParse, sSort.pOrderBy, 0, pEList->nExpr); sSort.iECursor = pParse->nTab++; sSort.addrSortIndex = sqlite3VdbeAddOp4(v, OP_OpenEphemeral, - sSort.iECursor, sSort.pOrderBy->nExpr+2, 0, - (char*)pKeyInfo, P4_KEYINFO); + sSort.iECursor, sSort.pOrderBy->nExpr+1+pEList->nExpr, 0, + (char*)pKeyInfo, P4_KEYINFO + ); }else{ sSort.addrSortIndex = -1; } @@ -105369,18 +114763,18 @@ SQLITE_PRIVATE int sqlite3Select( p->nSelectRow = LARGEST_INT64; computeLimitRegisters(pParse, p, iEnd); if( p->iLimit==0 && sSort.addrSortIndex>=0 ){ - sqlite3VdbeGetOp(v, sSort.addrSortIndex)->opcode = OP_SorterOpen; + sqlite3VdbeChangeOpcode(v, sSort.addrSortIndex, OP_SorterOpen); sSort.sortFlags |= SORTFLAG_UseSorter; } - /* Open a virtual index to use for the distinct set. + /* Open an ephemeral index to use for the distinct set. */ if( p->selFlags & SF_Distinct ){ sDistinct.tabTnct = pParse->nTab++; sDistinct.addrTnct = sqlite3VdbeAddOp4(v, OP_OpenEphemeral, - sDistinct.tabTnct, 0, 0, - (char*)keyInfoFromExprList(pParse, p->pEList,0,0), - P4_KEYINFO); + sDistinct.tabTnct, 0, 0, + (char*)keyInfoFromExprList(pParse, p->pEList,0,0), + P4_KEYINFO); sqlite3VdbeChangeP5(v, BTREE_UNORDERED); sDistinct.eTnctType = WHERE_DISTINCT_UNORDERED; }else{ @@ -105458,11 +114852,10 @@ SQLITE_PRIVATE int sqlite3Select( p->nSelectRow = 1; } - /* If there is both a GROUP BY and an ORDER BY clause and they are ** identical, then it may be possible to disable the ORDER BY clause ** on the grounds that the GROUP BY will cause elements to come out - ** in the correct order. It also may not - the GROUP BY may use a + ** in the correct order. It also may not - the GROUP BY might use a ** database index that causes rows to be grouped together as required ** but not actually sorted. Either way, record the fact that the ** ORDER BY and GROUP BY clauses are the same by setting the orderByGrp @@ -105483,7 +114876,7 @@ SQLITE_PRIVATE int sqlite3Select( sNC.pSrcList = pTabList; sNC.pAggInfo = &sAggInfo; sAggInfo.mnReg = pParse->nMem+1; - sAggInfo.nSortingColumn = pGroupBy ? pGroupBy->nExpr+1 : 0; + sAggInfo.nSortingColumn = pGroupBy ? pGroupBy->nExpr : 0; sAggInfo.pGroupBy = pGroupBy; sqlite3ExprAnalyzeAggList(&sNC, pEList); sqlite3ExprAnalyzeAggList(&sNC, sSort.pOrderBy); @@ -105505,7 +114898,7 @@ SQLITE_PRIVATE int sqlite3Select( */ if( pGroupBy ){ KeyInfo *pKeyInfo; /* Keying information for the group by clause */ - int j1; /* A-vs-B comparision jump */ + int addr1; /* A-vs-B comparision jump */ int addrOutputRow; /* Start of subroutine that outputs a result row */ int regOutputRow; /* Return address register for output subroutine */ int addrSetAbort; /* Set the abort flag and return */ @@ -105520,7 +114913,7 @@ SQLITE_PRIVATE int sqlite3Select( ** will be converted into a Noop. */ sAggInfo.sortingIdx = pParse->nTab++; - pKeyInfo = keyInfoFromExprList(pParse, pGroupBy, 0, 0); + pKeyInfo = keyInfoFromExprList(pParse, pGroupBy, 0, sAggInfo.nColumn); addrSortingIdx = sqlite3VdbeAddOp4(v, OP_SorterOpen, sAggInfo.sortingIdx, sAggInfo.nSortingColumn, 0, (char*)pKeyInfo, P4_KEYINFO); @@ -105576,8 +114969,8 @@ SQLITE_PRIVATE int sqlite3Select( groupBySort = 1; nGroupBy = pGroupBy->nExpr; - nCol = nGroupBy + 1; - j = nGroupBy+1; + nCol = nGroupBy; + j = nGroupBy; for(i=0; i=j ){ nCol++; @@ -105586,20 +114979,14 @@ SQLITE_PRIVATE int sqlite3Select( } regBase = sqlite3GetTempRange(pParse, nCol); sqlite3ExprCacheClear(pParse); - sqlite3ExprCodeExprList(pParse, pGroupBy, regBase, 0); - sqlite3VdbeAddOp2(v, OP_Sequence, sAggInfo.sortingIdx,regBase+nGroupBy); - j = nGroupBy+1; + sqlite3ExprCodeExprList(pParse, pGroupBy, regBase, 0, 0); + j = nGroupBy; for(i=0; iiSorterColumn>=j ){ int r1 = j + regBase; - int r2; - - r2 = sqlite3ExprCodeGetColumn(pParse, - pCol->pTab, pCol->iColumn, pCol->iTable, r1, 0); - if( r1!=r2 ){ - sqlite3VdbeAddOp2(v, OP_SCopy, r2, r1); - } + sqlite3ExprCodeGetColumnToReg(pParse, + pCol->pTab, pCol->iColumn, pCol->iTable, r1); j++; } } @@ -105641,12 +115028,12 @@ SQLITE_PRIVATE int sqlite3Select( addrTopOfLoop = sqlite3VdbeCurrentAddr(v); sqlite3ExprCacheClear(pParse); if( groupBySort ){ - sqlite3VdbeAddOp2(v, OP_SorterData, sAggInfo.sortingIdx, sortOut); + sqlite3VdbeAddOp3(v, OP_SorterData, sAggInfo.sortingIdx, + sortOut, sortPTab); } for(j=0; jnExpr; j++){ if( groupBySort ){ sqlite3VdbeAddOp3(v, OP_Column, sortPTab, j, iBMem+j); - if( j==0 ) sqlite3VdbeChangeP5(v, OPFLAG_CLEARCACHE); }else{ sAggInfo.directMode = 1; sqlite3ExprCode(pParse, pGroupBy->a[j].pExpr, iBMem+j); @@ -105654,8 +115041,8 @@ SQLITE_PRIVATE int sqlite3Select( } sqlite3VdbeAddOp4(v, OP_Compare, iAMem, iBMem, pGroupBy->nExpr, (char*)sqlite3KeyInfoRef(pKeyInfo), P4_KEYINFO); - j1 = sqlite3VdbeCurrentAddr(v); - sqlite3VdbeAddOp3(v, OP_Jump, j1+1, 0, j1+1); VdbeCoverage(v); + addr1 = sqlite3VdbeCurrentAddr(v); + sqlite3VdbeAddOp3(v, OP_Jump, addr1+1, 0, addr1+1); VdbeCoverage(v); /* Generate code that runs whenever the GROUP BY changes. ** Changes in the GROUP BY are detected by the previous code @@ -105677,7 +115064,7 @@ SQLITE_PRIVATE int sqlite3Select( /* Update the aggregate accumulators based on the content of ** the current row */ - sqlite3VdbeJumpHere(v, j1); + sqlite3VdbeJumpHere(v, addr1); updateAccumulator(pParse, &sAggInfo); sqlite3VdbeAddOp2(v, OP_Integer, 1, iUseFlag); VdbeComment((v, "indicate data in accumulator")); @@ -105699,7 +115086,7 @@ SQLITE_PRIVATE int sqlite3Select( /* Jump over the subroutines */ - sqlite3VdbeAddOp2(v, OP_Goto, 0, addrEnd); + sqlite3VdbeGoto(v, addrEnd); /* Generate a subroutine that outputs a single row of the result ** set. This subroutine first looks at the iUseFlag. If iUseFlag @@ -105714,7 +115101,8 @@ SQLITE_PRIVATE int sqlite3Select( sqlite3VdbeAddOp1(v, OP_Return, regOutputRow); sqlite3VdbeResolveLabel(v, addrOutputRow); addrOutputRow = sqlite3VdbeCurrentAddr(v); - sqlite3VdbeAddOp2(v, OP_IfPos, iUseFlag, addrOutputRow+2); VdbeCoverage(v); + sqlite3VdbeAddOp2(v, OP_IfPos, iUseFlag, addrOutputRow+2); + VdbeCoverage(v); VdbeComment((v, "Groupby result generator entry point")); sqlite3VdbeAddOp1(v, OP_Return, regOutputRow); finalizeAggFunctions(pParse, &sAggInfo); @@ -105852,7 +115240,7 @@ SQLITE_PRIVATE int sqlite3Select( updateAccumulator(pParse, &sAggInfo); assert( pMinMax==0 || pMinMax->nExpr==1 ); if( sqlite3WhereIsOrdered(pWInfo)>0 ){ - sqlite3VdbeAddOp2(v, OP_Goto, 0, sqlite3WhereBreakLabel(pWInfo)); + sqlite3VdbeGoto(v, sqlite3WhereBreakLabel(pWInfo)); VdbeComment((v, "%s() by index", (flag==WHERE_ORDERBY_MIN?"min":"max"))); } @@ -105878,7 +115266,8 @@ SQLITE_PRIVATE int sqlite3Select( ** and send them to the callback one by one. */ if( sSort.pOrderBy ){ - explainTempTable(pParse, sSort.nOBSat>0 ? "RIGHT PART OF ORDER BY":"ORDER BY"); + explainTempTable(pParse, + sSort.nOBSat>0 ? "RIGHT PART OF ORDER BY":"ORDER BY"); generateSortTail(pParse, p, &sSort, pEList->nExpr, pDest); } @@ -105886,10 +115275,9 @@ SQLITE_PRIVATE int sqlite3Select( */ sqlite3VdbeResolveLabel(v, iEnd); - /* The SELECT was successfully coded. Set the return code to 0 - ** to indicate no errors. - */ - rc = 0; + /* The SELECT has been coded. If there is an error in the Parse structure, + ** set the return code to 1. Otherwise 0. */ + rc = (pParse->nErr>0); /* Control jumps to here if an error is encountered above, or upon ** successful coding of the SELECT. @@ -105905,104 +115293,13 @@ select_end: sqlite3DbFree(db, sAggInfo.aCol); sqlite3DbFree(db, sAggInfo.aFunc); +#if SELECTTRACE_ENABLED + SELECTTRACE(1,pParse,p,("end processing\n")); + pParse->nSelectIndent--; +#endif return rc; } -#if defined(SQLITE_ENABLE_TREE_EXPLAIN) -/* -** Generate a human-readable description of a the Select object. -*/ -static void explainOneSelect(Vdbe *pVdbe, Select *p){ - sqlite3ExplainPrintf(pVdbe, "SELECT "); - if( p->selFlags & (SF_Distinct|SF_Aggregate) ){ - if( p->selFlags & SF_Distinct ){ - sqlite3ExplainPrintf(pVdbe, "DISTINCT "); - } - if( p->selFlags & SF_Aggregate ){ - sqlite3ExplainPrintf(pVdbe, "agg_flag "); - } - sqlite3ExplainNL(pVdbe); - sqlite3ExplainPrintf(pVdbe, " "); - } - sqlite3ExplainExprList(pVdbe, p->pEList); - sqlite3ExplainNL(pVdbe); - if( p->pSrc && p->pSrc->nSrc ){ - int i; - sqlite3ExplainPrintf(pVdbe, "FROM "); - sqlite3ExplainPush(pVdbe); - for(i=0; ipSrc->nSrc; i++){ - struct SrcList_item *pItem = &p->pSrc->a[i]; - sqlite3ExplainPrintf(pVdbe, "{%d,*} = ", pItem->iCursor); - if( pItem->pSelect ){ - sqlite3ExplainSelect(pVdbe, pItem->pSelect); - if( pItem->pTab ){ - sqlite3ExplainPrintf(pVdbe, " (tabname=%s)", pItem->pTab->zName); - } - }else if( pItem->zName ){ - sqlite3ExplainPrintf(pVdbe, "%s", pItem->zName); - } - if( pItem->zAlias ){ - sqlite3ExplainPrintf(pVdbe, " (AS %s)", pItem->zAlias); - } - if( pItem->jointype & JT_LEFT ){ - sqlite3ExplainPrintf(pVdbe, " LEFT-JOIN"); - } - sqlite3ExplainNL(pVdbe); - } - sqlite3ExplainPop(pVdbe); - } - if( p->pWhere ){ - sqlite3ExplainPrintf(pVdbe, "WHERE "); - sqlite3ExplainExpr(pVdbe, p->pWhere); - sqlite3ExplainNL(pVdbe); - } - if( p->pGroupBy ){ - sqlite3ExplainPrintf(pVdbe, "GROUPBY "); - sqlite3ExplainExprList(pVdbe, p->pGroupBy); - sqlite3ExplainNL(pVdbe); - } - if( p->pHaving ){ - sqlite3ExplainPrintf(pVdbe, "HAVING "); - sqlite3ExplainExpr(pVdbe, p->pHaving); - sqlite3ExplainNL(pVdbe); - } - if( p->pOrderBy ){ - sqlite3ExplainPrintf(pVdbe, "ORDERBY "); - sqlite3ExplainExprList(pVdbe, p->pOrderBy); - sqlite3ExplainNL(pVdbe); - } - if( p->pLimit ){ - sqlite3ExplainPrintf(pVdbe, "LIMIT "); - sqlite3ExplainExpr(pVdbe, p->pLimit); - sqlite3ExplainNL(pVdbe); - } - if( p->pOffset ){ - sqlite3ExplainPrintf(pVdbe, "OFFSET "); - sqlite3ExplainExpr(pVdbe, p->pOffset); - sqlite3ExplainNL(pVdbe); - } -} -SQLITE_PRIVATE void sqlite3ExplainSelect(Vdbe *pVdbe, Select *p){ - if( p==0 ){ - sqlite3ExplainPrintf(pVdbe, "(null-select)"); - return; - } - sqlite3ExplainPush(pVdbe); - while( p ){ - explainOneSelect(pVdbe, p); - p = p->pNext; - if( p==0 ) break; - sqlite3ExplainNL(pVdbe); - sqlite3ExplainPrintf(pVdbe, "%s\n", selectOpName(p->op)); - } - sqlite3ExplainPrintf(pVdbe, "END"); - sqlite3ExplainPop(pVdbe); -} - -/* End of the structure debug printing code -*****************************************************************************/ -#endif /* defined(SQLITE_ENABLE_TREE_EXPLAIN) */ - /************** End of select.c **********************************************/ /************** Begin file table.c *******************************************/ /* @@ -106023,6 +115320,7 @@ SQLITE_PRIVATE void sqlite3ExplainSelect(Vdbe *pVdbe, Select *p){ ** These routines are in a separate files so that they will not be linked ** if they are not used. */ +/* #include "sqliteInt.h" */ /* #include */ /* #include */ @@ -106035,10 +115333,10 @@ SQLITE_PRIVATE void sqlite3ExplainSelect(Vdbe *pVdbe, Select *p){ typedef struct TabResult { char **azResult; /* Accumulated output */ char *zErrMsg; /* Error message text, if an error occurs */ - int nAlloc; /* Slots allocated for azResult[] */ - int nRow; /* Number of rows in the result */ - int nColumn; /* Number of columns in the result */ - int nData; /* Slots used in azResult[]. (nRow+1)*nColumn */ + u32 nAlloc; /* Slots allocated for azResult[] */ + u32 nRow; /* Number of rows in the result */ + u32 nColumn; /* Number of columns in the result */ + u32 nData; /* Slots used in azResult[]. (nRow+1)*nColumn */ int rc; /* Return code from sqlite3_exec() */ } TabResult; @@ -106064,7 +115362,7 @@ static int sqlite3_get_table_cb(void *pArg, int nCol, char **argv, char **colv){ if( p->nData + need > p->nAlloc ){ char **azNew; p->nAlloc = p->nAlloc*2 + need; - azNew = sqlite3_realloc( p->azResult, sizeof(char*)*p->nAlloc ); + azNew = sqlite3_realloc64( p->azResult, sizeof(char*)*p->nAlloc ); if( azNew==0 ) goto malloc_failed; p->azResult = azNew; } @@ -106079,7 +115377,7 @@ static int sqlite3_get_table_cb(void *pArg, int nCol, char **argv, char **colv){ if( z==0 ) goto malloc_failed; p->azResult[p->nData++] = z; } - }else if( p->nColumn!=nCol ){ + }else if( (int)p->nColumn!=nCol ){ sqlite3_free(p->zErrMsg); p->zErrMsg = sqlite3_mprintf( "sqlite3_get_table() called with two or more incompatible queries" @@ -106096,7 +115394,7 @@ static int sqlite3_get_table_cb(void *pArg, int nCol, char **argv, char **colv){ z = 0; }else{ int n = sqlite3Strlen30(argv[i])+1; - z = sqlite3_malloc( n ); + z = sqlite3_malloc64( n ); if( z==0 ) goto malloc_failed; memcpy(z, argv[i], n); } @@ -106121,7 +115419,7 @@ malloc_failed: ** Instead, the entire table should be passed to sqlite3_free_table() when ** the calling procedure is finished using it. */ -SQLITE_API int sqlite3_get_table( +SQLITE_API int SQLITE_STDCALL sqlite3_get_table( sqlite3 *db, /* The database on which the SQL executes */ const char *zSql, /* The SQL to be executed */ char ***pazResult, /* Write the result table here */ @@ -106132,6 +115430,9 @@ SQLITE_API int sqlite3_get_table( int rc; TabResult res; +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) || pazResult==0 ) return SQLITE_MISUSE_BKPT; +#endif *pazResult = 0; if( pnColumn ) *pnColumn = 0; if( pnRow ) *pnRow = 0; @@ -106142,7 +115443,7 @@ SQLITE_API int sqlite3_get_table( res.nData = 1; res.nAlloc = 20; res.rc = SQLITE_OK; - res.azResult = sqlite3_malloc(sizeof(char*)*res.nAlloc ); + res.azResult = sqlite3_malloc64(sizeof(char*)*res.nAlloc ); if( res.azResult==0 ){ db->errCode = SQLITE_NOMEM; return SQLITE_NOMEM; @@ -106170,7 +115471,7 @@ SQLITE_API int sqlite3_get_table( } if( res.nAlloc>res.nData ){ char **azNew; - azNew = sqlite3_realloc( res.azResult, sizeof(char*)*res.nData ); + azNew = sqlite3_realloc64( res.azResult, sizeof(char*)*res.nData ); if( azNew==0 ){ sqlite3_free_table(&res.azResult[1]); db->errCode = SQLITE_NOMEM; @@ -106187,8 +115488,8 @@ SQLITE_API int sqlite3_get_table( /* ** This routine frees the space the sqlite3_get_table() malloced. */ -SQLITE_API void sqlite3_free_table( - char **azResult /* Result returned from from sqlite3_get_table() */ +SQLITE_API void SQLITE_STDCALL sqlite3_free_table( + char **azResult /* Result returned from sqlite3_get_table() */ ){ if( azResult ){ int i, n; @@ -106216,6 +115517,7 @@ SQLITE_API void sqlite3_free_table( ************************************************************************* ** This file contains the implementation for TRIGGERs */ +/* #include "sqliteInt.h" */ #ifndef SQLITE_OMIT_TRIGGER /* @@ -106332,7 +115634,7 @@ SQLITE_PRIVATE void sqlite3BeginTrigger( ** ^^^^^^^^ ** ** To maintain backwards compatibility, ignore the database - ** name on pTableName if we are reparsing our of SQLITE_MASTER. + ** name on pTableName if we are reparsing out of SQLITE_MASTER. */ if( db->init.busy && iDb!=1 ){ sqlite3DbFree(db, pTableName->a[0].zDatabase); @@ -106385,8 +115687,7 @@ SQLITE_PRIVATE void sqlite3BeginTrigger( goto trigger_cleanup; } assert( sqlite3SchemaMutexHeld(db, iDb, 0) ); - if( sqlite3HashFind(&(db->aDb[iDb].pSchema->trigHash), - zName, sqlite3Strlen30(zName)) ){ + if( sqlite3HashFind(&(db->aDb[iDb].pSchema->trigHash),zName) ){ if( !noErr ){ sqlite3ErrorMsg(pParse, "trigger %T already exists", pName); }else{ @@ -106399,7 +115700,6 @@ SQLITE_PRIVATE void sqlite3BeginTrigger( /* Do not create a trigger on a system table */ if( sqlite3StrNICmp(pTab->zName, "sqlite_", 7)==0 ){ sqlite3ErrorMsg(pParse, "cannot create trigger on system table"); - pParse->nErr++; goto trigger_cleanup; } @@ -106529,13 +115829,12 @@ SQLITE_PRIVATE void sqlite3FinishTrigger( Trigger *pLink = pTrig; Hash *pHash = &db->aDb[iDb].pSchema->trigHash; assert( sqlite3SchemaMutexHeld(db, iDb, 0) ); - pTrig = sqlite3HashInsert(pHash, zName, sqlite3Strlen30(zName), pTrig); + pTrig = sqlite3HashInsert(pHash, zName, pTrig); if( pTrig ){ db->mallocFailed = 1; }else if( pLink->pSchema==pLink->pTabSchema ){ Table *pTab; - int n = sqlite3Strlen30(pLink->table); - pTab = sqlite3HashFind(&pLink->pTabSchema->tblHash, pLink->table, n); + pTab = sqlite3HashFind(&pLink->pTabSchema->tblHash, pLink->table); assert( pTab!=0 ); pLink->pNext = pTab->pTrigger; pTab->pTrigger = pLink; @@ -106580,12 +115879,12 @@ static TriggerStep *triggerStepAllocate( ){ TriggerStep *pTriggerStep; - pTriggerStep = sqlite3DbMallocZero(db, sizeof(TriggerStep) + pName->n); + pTriggerStep = sqlite3DbMallocZero(db, sizeof(TriggerStep) + pName->n + 1); if( pTriggerStep ){ char *z = (char*)&pTriggerStep[1]; memcpy(z, pName->z, pName->n); - pTriggerStep->target.z = z; - pTriggerStep->target.n = pName->n; + sqlite3Dequote(z); + pTriggerStep->zTarget = z; pTriggerStep->op = op; } return pTriggerStep; @@ -106694,7 +115993,6 @@ SQLITE_PRIVATE void sqlite3DropTrigger(Parse *pParse, SrcList *pName, int noErr) int i; const char *zDb; const char *zName; - int nName; sqlite3 *db = pParse->db; if( db->mallocFailed ) goto drop_trigger_cleanup; @@ -106705,13 +116003,12 @@ SQLITE_PRIVATE void sqlite3DropTrigger(Parse *pParse, SrcList *pName, int noErr) assert( pName->nSrc==1 ); zDb = pName->a[0].zDatabase; zName = pName->a[0].zName; - nName = sqlite3Strlen30(zName); assert( zDb!=0 || sqlite3BtreeHoldsAllMutexes(db) ); for(i=OMIT_TEMPDB; inDb; i++){ int j = (i<2) ? i^1 : i; /* Search TEMP before MAIN */ if( zDb && sqlite3StrICmp(db->aDb[j].zName, zDb) ) continue; assert( sqlite3SchemaMutexHeld(db, j, 0) ); - pTrigger = sqlite3HashFind(&(db->aDb[j].pSchema->trigHash), zName, nName); + pTrigger = sqlite3HashFind(&(db->aDb[j].pSchema->trigHash), zName); if( pTrigger ) break; } if( !pTrigger ){ @@ -106734,8 +116031,7 @@ drop_trigger_cleanup: ** is set on. */ static Table *tableOfTrigger(Trigger *pTrigger){ - int n = sqlite3Strlen30(pTrigger->table); - return sqlite3HashFind(&pTrigger->pTabSchema->tblHash, pTrigger->table, n); + return sqlite3HashFind(&pTrigger->pTabSchema->tblHash, pTrigger->table); } @@ -106770,31 +116066,12 @@ SQLITE_PRIVATE void sqlite3DropTriggerPtr(Parse *pParse, Trigger *pTrigger){ */ assert( pTable!=0 ); if( (v = sqlite3GetVdbe(pParse))!=0 ){ - int base; - static const int iLn = VDBE_OFFSET_LINENO(2); - static const VdbeOpList dropTrigger[] = { - { OP_Rewind, 0, ADDR(9), 0}, - { OP_String8, 0, 1, 0}, /* 1 */ - { OP_Column, 0, 1, 2}, - { OP_Ne, 2, ADDR(8), 1}, - { OP_String8, 0, 1, 0}, /* 4: "trigger" */ - { OP_Column, 0, 0, 2}, - { OP_Ne, 2, ADDR(8), 1}, - { OP_Delete, 0, 0, 0}, - { OP_Next, 0, ADDR(1), 0}, /* 8 */ - }; - - sqlite3BeginWriteOperation(pParse, 0, iDb); - sqlite3OpenMasterTable(pParse, iDb); - base = sqlite3VdbeAddOpList(v, ArraySize(dropTrigger), dropTrigger, iLn); - sqlite3VdbeChangeP4(v, base+1, pTrigger->zName, P4_TRANSIENT); - sqlite3VdbeChangeP4(v, base+4, "trigger", P4_STATIC); + sqlite3NestedParse(pParse, + "DELETE FROM %Q.%s WHERE name=%Q AND type='trigger'", + db->aDb[iDb].zName, SCHEMA_TABLE(iDb), pTrigger->zName + ); sqlite3ChangeCookie(pParse, iDb); - sqlite3VdbeAddOp2(v, OP_Close, 0, 0); sqlite3VdbeAddOp4(v, OP_DropTrigger, iDb, 0, 0, pTrigger->zName, 0); - if( pParse->nMem<3 ){ - pParse->nMem = 3; - } } } @@ -106807,7 +116084,7 @@ SQLITE_PRIVATE void sqlite3UnlinkAndDeleteTrigger(sqlite3 *db, int iDb, const ch assert( sqlite3SchemaMutexHeld(db, iDb, 0) ); pHash = &(db->aDb[iDb].pSchema->trigHash); - pTrigger = sqlite3HashInsert(pHash, zName, sqlite3Strlen30(zName), 0); + pTrigger = sqlite3HashInsert(pHash, zName, 0); if( ALWAYS(pTrigger) ){ if( pTrigger->pSchema==pTrigger->pTabSchema ){ Table *pTab = tableOfTrigger(pTrigger); @@ -106871,7 +116148,7 @@ SQLITE_PRIVATE Trigger *sqlite3TriggersExist( } /* -** Convert the pStep->target token into a SrcList and return a pointer +** Convert the pStep->zTarget string into a SrcList and return a pointer ** to that SrcList. ** ** This routine adds a specific database name, if needed, to the target when @@ -106884,17 +116161,17 @@ static SrcList *targetSrcList( Parse *pParse, /* The parsing context */ TriggerStep *pStep /* The trigger containing the target token */ ){ + sqlite3 *db = pParse->db; int iDb; /* Index of the database to use */ SrcList *pSrc; /* SrcList to be returned */ - pSrc = sqlite3SrcListAppend(pParse->db, 0, &pStep->target, 0); + pSrc = sqlite3SrcListAppend(db, 0, 0, 0); if( pSrc ){ assert( pSrc->nSrc>0 ); - assert( pSrc->a!=0 ); - iDb = sqlite3SchemaToIndex(pParse->db, pStep->pTrig->pSchema); + pSrc->a[pSrc->nSrc-1].zName = sqlite3DbStrDup(db, pStep->zTarget); + iDb = sqlite3SchemaToIndex(db, pStep->pTrig->pSchema); if( iDb==0 || iDb>=2 ){ - sqlite3 *db = pParse->db; - assert( iDbdb->nDb ); + assert( iDbnDb ); pSrc->a[pSrc->nSrc-1].zDatabase = sqlite3DbStrDup(db, db->aDb[iDb].zName); } } @@ -107006,6 +116283,7 @@ static void transferParseError(Parse *pTo, Parse *pFrom){ if( pTo->nErr==0 ){ pTo->zErrMsg = pFrom->zErrMsg; pTo->nErr = pFrom->nErr; + pTo->rc = pFrom->rc; }else{ sqlite3DbFree(pFrom->db, pFrom->zErrMsg); } @@ -107344,6 +116622,7 @@ SQLITE_PRIVATE u32 sqlite3TriggerColmask( ** This file contains C code routines that are called by the parser ** to handle UPDATE statements. */ +/* #include "sqliteInt.h" */ #ifndef SQLITE_OMIT_VIRTUALTABLE /* Forward declaration */ @@ -107465,9 +116744,9 @@ SQLITE_PRIVATE void sqlite3Update( /* Register Allocations */ int regRowCount = 0; /* A count of rows changed */ - int regOldRowid; /* The old rowid */ - int regNewRowid; /* The new rowid */ - int regNew; /* Content of the NEW.* table in triggers */ + int regOldRowid = 0; /* The old rowid */ + int regNewRowid = 0; /* The new rowid */ + int regNew = 0; /* Content of the NEW.* table in triggers */ int regOld = 0; /* Content of OLD.* table in triggers */ int regRowSet = 0; /* Rowset of rows to be updated */ int regKey = 0; /* composite PRIMARY KEY value */ @@ -107594,16 +116873,20 @@ SQLITE_PRIVATE void sqlite3Update( assert( chngPk==0 || chngPk==1 ); chngKey = chngRowid + chngPk; - /* The SET expressions are not actually used inside the WHERE loop. - ** So reset the colUsed mask + /* The SET expressions are not actually used inside the WHERE loop. + ** So reset the colUsed mask. Unless this is a virtual table. In that + ** case, set all bits of the colUsed mask (to ensure that the virtual + ** table implementation makes all columns available). */ - pTabList->a[0].colUsed = 0; + pTabList->a[0].colUsed = IsVirtual(pTab) ? (Bitmask)-1 : 0; hasFK = sqlite3FkRequired(pParse, pTab, aXRef, chngKey); /* There is one entry in the aRegIdx[] array for each index on the table ** being updated. Fill in aRegIdx[] with a register number that will hold - ** the key for accessing each index. + ** the key for accessing each index. + ** + ** FIXME: Be smarter about omitting indexes that use expressions. */ for(j=0, pIdx=pTab->pIndex; pIdx; pIdx=pIdx->pNext, j++){ int reg; @@ -107612,7 +116895,8 @@ SQLITE_PRIVATE void sqlite3Update( }else{ reg = 0; for(i=0; inKeyCol; i++){ - if( aXRef[pIdx->aiColumn[i]]>=0 ){ + i16 iIdxCol = pIdx->aiColumn[i]; + if( iIdxCol<0 || aXRef[iIdxCol]>=0 ){ reg = ++pParse->nMem; break; } @@ -107628,29 +116912,20 @@ SQLITE_PRIVATE void sqlite3Update( if( pParse->nested==0 ) sqlite3VdbeCountChanges(v); sqlite3BeginWriteOperation(pParse, 1, iDb); -#ifndef SQLITE_OMIT_VIRTUALTABLE - /* Virtual tables must be handled separately */ - if( IsVirtual(pTab) ){ - updateVirtualTable(pParse, pTabList, pTab, pChanges, pRowidExpr, aXRef, - pWhere, onError); - pWhere = 0; - pTabList = 0; - goto update_cleanup; - } -#endif - /* Allocate required registers. */ - regRowSet = ++pParse->nMem; - regOldRowid = regNewRowid = ++pParse->nMem; - if( chngPk || pTrigger || hasFK ){ - regOld = pParse->nMem + 1; + if( !IsVirtual(pTab) ){ + regRowSet = ++pParse->nMem; + regOldRowid = regNewRowid = ++pParse->nMem; + if( chngPk || pTrigger || hasFK ){ + regOld = pParse->nMem + 1; + pParse->nMem += pTab->nCol; + } + if( chngKey || pTrigger || hasFK ){ + regNewRowid = ++pParse->nMem; + } + regNew = pParse->nMem + 1; pParse->nMem += pTab->nCol; } - if( chngKey || pTrigger || hasFK ){ - regNewRowid = ++pParse->nMem; - } - regNew = pParse->nMem + 1; - pParse->nMem += pTab->nCol; /* Start the view context. */ if( isView ){ @@ -107658,7 +116933,7 @@ SQLITE_PRIVATE void sqlite3Update( } /* If we are trying to update a view, realize that view into - ** a ephemeral table. + ** an ephemeral table. */ #if !defined(SQLITE_OMIT_VIEW) && !defined(SQLITE_OMIT_TRIGGER) if( isView ){ @@ -107673,6 +116948,15 @@ SQLITE_PRIVATE void sqlite3Update( goto update_cleanup; } +#ifndef SQLITE_OMIT_VIRTUALTABLE + /* Virtual tables must be handled separately */ + if( IsVirtual(pTab) ){ + updateVirtualTable(pParse, pTabList, pTab, pChanges, pRowidExpr, aXRef, + pWhere, onError); + goto update_cleanup; + } +#endif + /* Begin the database scan */ if( HasRowid(pTab) ){ @@ -107712,6 +116996,7 @@ SQLITE_PRIVATE void sqlite3Update( if( pWInfo==0 ) goto update_cleanup; okOnePass = sqlite3WhereOkOnePass(pWInfo, aiCurOnePass); for(i=0; iaiColumn[i]>=0 ); sqlite3ExprCodeGetColumnOfTable(v, pTab, iDataCur, pPk->aiColumn[i], iPk+i); } @@ -107721,7 +117006,7 @@ SQLITE_PRIVATE void sqlite3Update( regKey = iPk; }else{ sqlite3VdbeAddOp4(v, OP_MakeRecord, iPk, nPk, regKey, - sqlite3IndexAffinityStr(v, pPk), nPk); + sqlite3IndexAffinityStr(db, pPk), nPk); sqlite3VdbeAddOp2(v, OP_IdxInsert, iEph, regKey); } sqlite3WhereEnd(pWInfo); @@ -107756,20 +117041,21 @@ SQLITE_PRIVATE void sqlite3Update( if( aiCurOnePass[0]>=0 ) aToOpen[aiCurOnePass[0]-iBaseCur] = 0; if( aiCurOnePass[1]>=0 ) aToOpen[aiCurOnePass[1]-iBaseCur] = 0; } - sqlite3OpenTableAndIndices(pParse, pTab, OP_OpenWrite, iBaseCur, aToOpen, + sqlite3OpenTableAndIndices(pParse, pTab, OP_OpenWrite, 0, iBaseCur, aToOpen, 0, 0); } /* Top of the update loop */ if( okOnePass ){ - if( aToOpen[iDataCur-iBaseCur] ){ - assert( pPk!=0 ); + if( aToOpen[iDataCur-iBaseCur] && !isView ){ + assert( pPk ); sqlite3VdbeAddOp4Int(v, OP_NotFound, iDataCur, labelBreak, regKey, nKey); VdbeCoverageNeverTaken(v); } labelContinue = labelBreak; sqlite3VdbeAddOp2(v, OP_IsNull, pPk ? regKey : regOldRowid, labelBreak); - VdbeCoverage(v); + VdbeCoverageIf(v, pPk==0); + VdbeCoverageIf(v, pPk!=0); }else if( pPk ){ labelContinue = sqlite3VdbeMakeLabel(v); sqlite3VdbeAddOp2(v, OP_Rewind, iEph, labelBreak); VdbeCoverage(v); @@ -107818,7 +117104,7 @@ SQLITE_PRIVATE void sqlite3Update( } /* Populate the array of registers beginning at regNew with the new - ** row data. This array is used to check constaints, create the new + ** row data. This array is used to check constants, create the new ** table and index records, and as the values for any new.* references ** made by triggers. ** @@ -107833,7 +117119,6 @@ SQLITE_PRIVATE void sqlite3Update( newmask = sqlite3TriggerColmask( pParse, pTrigger, pChanges, 1, TRIGGER_BEFORE, pTab, onError ); - /*sqlite3VdbeAddOp3(v, OP_Null, 0, regNew, regNew+pTab->nCol-1);*/ for(i=0; inCol; i++){ if( i==pTab->iPKey ){ sqlite3VdbeAddOp2(v, OP_Null, 0, regNew+i); @@ -107849,7 +117134,7 @@ SQLITE_PRIVATE void sqlite3Update( */ testcase( i==31 ); testcase( i==32 ); - sqlite3ExprCodeGetColumnOfTable(v, pTab, iDataCur, i, regNew+i); + sqlite3ExprCodeGetColumnToReg(pParse, pTab, i, iDataCur, regNew+i); }else{ sqlite3VdbeAddOp2(v, OP_Null, 0, regNew+i); } @@ -107891,7 +117176,7 @@ SQLITE_PRIVATE void sqlite3Update( } if( !isView ){ - int j1 = 0; /* Address of jump instruction */ + int addr1 = 0; /* Address of jump instruction */ int bReplace = 0; /* True if REPLACE conflict resolution might happen */ /* Do constraint checks. */ @@ -107907,20 +117192,20 @@ SQLITE_PRIVATE void sqlite3Update( /* Delete the index entries associated with the current record. */ if( bReplace || chngKey ){ if( pPk ){ - j1 = sqlite3VdbeAddOp4Int(v, OP_NotFound, iDataCur, 0, regKey, nKey); + addr1 = sqlite3VdbeAddOp4Int(v, OP_NotFound, iDataCur, 0, regKey, nKey); }else{ - j1 = sqlite3VdbeAddOp3(v, OP_NotExists, iDataCur, 0, regOldRowid); + addr1 = sqlite3VdbeAddOp3(v, OP_NotExists, iDataCur, 0, regOldRowid); } VdbeCoverageNeverTaken(v); } - sqlite3GenerateRowIndexDelete(pParse, pTab, iDataCur, iIdxCur, aRegIdx); + sqlite3GenerateRowIndexDelete(pParse, pTab, iDataCur, iIdxCur, aRegIdx, -1); /* If changing the record number, delete the old record. */ if( hasFK || chngKey || pPk!=0 ){ sqlite3VdbeAddOp2(v, OP_Delete, iDataCur, 0); } if( bReplace || chngKey ){ - sqlite3VdbeJumpHere(v, j1); + sqlite3VdbeJumpHere(v, addr1); } if( hasFK ){ @@ -107957,7 +117242,7 @@ SQLITE_PRIVATE void sqlite3Update( sqlite3VdbeResolveLabel(v, labelContinue); sqlite3VdbeAddOp2(v, OP_Next, iEph, addrTop); VdbeCoverage(v); }else{ - sqlite3VdbeAddOp2(v, OP_Goto, 0, labelContinue); + sqlite3VdbeGoto(v, labelContinue); } sqlite3VdbeResolveLabel(v, labelBreak); @@ -107998,7 +117283,7 @@ update_cleanup: return; } /* Make sure "isView" and other macros defined above are undefined. Otherwise -** thely may interfere with compilation of other functions in this file +** they may interfere with compilation of other functions in this file ** (or in another file, if this file becomes part of the amalgamation). */ #ifdef isView #undef isView @@ -108011,21 +117296,23 @@ update_cleanup: /* ** Generate code for an UPDATE of a virtual table. ** -** The strategy is that we create an ephemerial table that contains +** There are two possible strategies - the default and the special +** "onepass" strategy. Onepass is only used if the virtual table +** implementation indicates that pWhere may match at most one row. +** +** The default strategy is to create an ephemeral table that contains ** for each row to be changed: ** ** (A) The original rowid of that row. -** (B) The revised rowid for the row. (note1) +** (B) The revised rowid for the row. ** (C) The content of every column in the row. ** -** Then we loop over this ephemeral table and for each row in -** the ephermeral table call VUpdate. +** Then loop through the contents of this ephemeral table executing a +** VUpdate for each row. When finished, drop the ephemeral table. ** -** When finished, drop the ephemeral table. -** -** (note1) Actually, if we know in advance that (A) is always the same -** as (B) we only store (A), then duplicate (A) when pulling -** it out of the ephemeral table before calling VUpdate. +** The "onepass" strategy does not use an ephemeral table. Instead, it +** stores the same values (A, B and C above) in a register array and +** makes a single invocation of VUpdate. */ static void updateVirtualTable( Parse *pParse, /* The parsing context */ @@ -108038,68 +117325,96 @@ static void updateVirtualTable( int onError /* ON CONFLICT strategy */ ){ Vdbe *v = pParse->pVdbe; /* Virtual machine under construction */ - ExprList *pEList = 0; /* The result set of the SELECT statement */ - Select *pSelect = 0; /* The SELECT statement */ - Expr *pExpr; /* Temporary expression */ int ephemTab; /* Table holding the result of the SELECT */ int i; /* Loop counter */ - int addr; /* Address of top of loop */ - int iReg; /* First register in set passed to OP_VUpdate */ sqlite3 *db = pParse->db; /* Database connection */ const char *pVTab = (const char*)sqlite3GetVTable(db, pTab); - SelectDest dest; + WhereInfo *pWInfo; + int nArg = 2 + pTab->nCol; /* Number of arguments to VUpdate */ + int regArg; /* First register in VUpdate arg array */ + int regRec; /* Register in which to assemble record */ + int regRowid; /* Register for ephem table rowid */ + int iCsr = pSrc->a[0].iCursor; /* Cursor used for virtual table scan */ + int aDummy[2]; /* Unused arg for sqlite3WhereOkOnePass() */ + int bOnePass; /* True to use onepass strategy */ + int addr; /* Address of OP_OpenEphemeral */ - /* Construct the SELECT statement that will find the new values for - ** all updated rows. - */ - pEList = sqlite3ExprListAppend(pParse, 0, sqlite3Expr(db, TK_ID, "_rowid_")); - if( pRowid ){ - pEList = sqlite3ExprListAppend(pParse, pEList, - sqlite3ExprDup(db, pRowid, 0)); - } - assert( pTab->iPKey<0 ); - for(i=0; inCol; i++){ - if( aXRef[i]>=0 ){ - pExpr = sqlite3ExprDup(db, pChanges->a[aXRef[i]].pExpr, 0); - }else{ - pExpr = sqlite3Expr(db, TK_ID, pTab->aCol[i].zName); - } - pEList = sqlite3ExprListAppend(pParse, pEList, pExpr); - } - pSelect = sqlite3SelectNew(pParse, pEList, pSrc, pWhere, 0, 0, 0, 0, 0, 0); - - /* Create the ephemeral table into which the update results will - ** be stored. - */ + /* Allocate nArg registers to martial the arguments to VUpdate. Then + ** create and open the ephemeral table in which the records created from + ** these arguments will be temporarily stored. */ assert( v ); ephemTab = pParse->nTab++; - sqlite3VdbeAddOp2(v, OP_OpenEphemeral, ephemTab, pTab->nCol+1+(pRowid!=0)); - sqlite3VdbeChangeP5(v, BTREE_UNORDERED); + addr= sqlite3VdbeAddOp2(v, OP_OpenEphemeral, ephemTab, nArg); + regArg = pParse->nMem + 1; + pParse->nMem += nArg; + regRec = ++pParse->nMem; + regRowid = ++pParse->nMem; - /* fill the ephemeral table - */ - sqlite3SelectDestInit(&dest, SRT_Table, ephemTab); - sqlite3Select(pParse, pSelect, &dest); + /* Start scanning the virtual table */ + pWInfo = sqlite3WhereBegin(pParse, pSrc, pWhere, 0,0,WHERE_ONEPASS_DESIRED,0); + if( pWInfo==0 ) return; - /* Generate code to scan the ephemeral table and call VUpdate. */ - iReg = ++pParse->nMem; - pParse->nMem += pTab->nCol+1; - addr = sqlite3VdbeAddOp2(v, OP_Rewind, ephemTab, 0); VdbeCoverage(v); - sqlite3VdbeAddOp3(v, OP_Column, ephemTab, 0, iReg); - sqlite3VdbeAddOp3(v, OP_Column, ephemTab, (pRowid?1:0), iReg+1); + /* Populate the argument registers. */ + sqlite3VdbeAddOp2(v, OP_Rowid, iCsr, regArg); + if( pRowid ){ + sqlite3ExprCode(pParse, pRowid, regArg+1); + }else{ + sqlite3VdbeAddOp2(v, OP_Rowid, iCsr, regArg+1); + } for(i=0; inCol; i++){ - sqlite3VdbeAddOp3(v, OP_Column, ephemTab, i+1+(pRowid!=0), iReg+2+i); + if( aXRef[i]>=0 ){ + sqlite3ExprCode(pParse, pChanges->a[aXRef[i]].pExpr, regArg+2+i); + }else{ + sqlite3VdbeAddOp3(v, OP_VColumn, iCsr, i, regArg+2+i); + } + } + + bOnePass = sqlite3WhereOkOnePass(pWInfo, aDummy); + + if( bOnePass ){ + /* If using the onepass strategy, no-op out the OP_OpenEphemeral coded + ** above. Also, if this is a top-level parse (not a trigger), clear the + ** multi-write flag so that the VM does not open a statement journal */ + sqlite3VdbeChangeToNoop(v, addr); + if( sqlite3IsToplevel(pParse) ){ + pParse->isMultiWrite = 0; + } + }else{ + /* Create a record from the argument register contents and insert it into + ** the ephemeral table. */ + sqlite3VdbeAddOp3(v, OP_MakeRecord, regArg, nArg, regRec); + sqlite3VdbeAddOp2(v, OP_NewRowid, ephemTab, regRowid); + sqlite3VdbeAddOp3(v, OP_Insert, ephemTab, regRec, regRowid); + } + + + if( bOnePass==0 ){ + /* End the virtual table scan */ + sqlite3WhereEnd(pWInfo); + + /* Begin scannning through the ephemeral table. */ + addr = sqlite3VdbeAddOp1(v, OP_Rewind, ephemTab); VdbeCoverage(v); + + /* Extract arguments from the current row of the ephemeral table and + ** invoke the VUpdate method. */ + for(i=0; inCol+2, iReg, pVTab, P4_VTAB); + sqlite3VdbeAddOp4(v, OP_VUpdate, 0, nArg, regArg, pVTab, P4_VTAB); sqlite3VdbeChangeP5(v, onError==OE_Default ? OE_Abort : onError); sqlite3MayAbort(pParse); - sqlite3VdbeAddOp2(v, OP_Next, ephemTab, addr+1); VdbeCoverage(v); - sqlite3VdbeJumpHere(v, addr); - sqlite3VdbeAddOp2(v, OP_Close, ephemTab, 0); - /* Cleanup */ - sqlite3SelectDelete(db, pSelect); + /* End of the ephemeral table scan. Or, if using the onepass strategy, + ** jump to here if the scan visited zero rows. */ + if( bOnePass==0 ){ + sqlite3VdbeAddOp2(v, OP_Next, ephemTab, addr+1); VdbeCoverage(v); + sqlite3VdbeJumpHere(v, addr); + sqlite3VdbeAddOp2(v, OP_Close, ephemTab, 0); + }else{ + sqlite3WhereEnd(pWInfo); + } } #endif /* SQLITE_OMIT_VIRTUALTABLE */ @@ -108121,6 +117436,8 @@ static void updateVirtualTable( ** Most of the code in this file may be omitted by defining the ** SQLITE_OMIT_VACUUM macro. */ +/* #include "sqliteInt.h" */ +/* #include "vdbeInt.h" */ #if !defined(SQLITE_OMIT_VACUUM) && !defined(SQLITE_OMIT_ATTACH) /* @@ -108192,14 +117509,14 @@ static int execExecSql(sqlite3 *db, char **pzErrMsg, const char *zSql){ ** step (3) requires additional temporary disk space approximately equal ** to the size of the original database for the rollback journal. ** Hence, temporary disk space that is approximately 2x the size of the -** orginal database is required. Every page of the database is written +** original database is required. Every page of the database is written ** approximately 3 times: Once for step (2) and twice for step (3). ** Two writes per page are required in step (3) because the original ** database content must be written into the rollback journal prior to ** overwriting the database with the vacuumed content. ** ** Only 1x temporary space and only 1x writes would be required if -** the copy of step (3) were replace by deleting the original database +** the copy of step (3) were replaced by deleting the original database ** and renaming the transient database as the original. But that will ** not work if other processes are attached to the original database. ** And a power loss in between deleting the original and renaming the @@ -108289,7 +117606,7 @@ SQLITE_PRIVATE int sqlite3RunVacuum(char **pzErrMsg, sqlite3 *db){ ** cause problems for the call to BtreeSetPageSize() below. */ sqlite3BtreeCommit(pTemp); - nRes = sqlite3BtreeGetReserve(pMain); + nRes = sqlite3BtreeGetOptimalReserve(pMain); /* A VACUUM cannot change the pagesize of an encrypted database. */ #ifdef SQLITE_HAS_CODEC @@ -108355,6 +117672,8 @@ SQLITE_PRIVATE int sqlite3RunVacuum(char **pzErrMsg, sqlite3 *db){ ** an "INSERT INTO vacuum_db.xxx SELECT * FROM main.xxx;" to copy ** the contents to the temporary database. */ + assert( (db->flags & SQLITE_Vacuum)==0 ); + db->flags |= SQLITE_Vacuum; rc = execExecSql(db, pzErrMsg, "SELECT 'INSERT INTO vacuum_db.' || quote(name) " "|| ' SELECT * FROM main.' || quote(name) || ';'" @@ -108362,6 +117681,8 @@ SQLITE_PRIVATE int sqlite3RunVacuum(char **pzErrMsg, sqlite3 *db){ "WHERE type = 'table' AND name!='sqlite_sequence' " " AND coalesce(rootpage,1)>0" ); + assert( (db->flags & SQLITE_Vacuum)!=0 ); + db->flags &= ~SQLITE_Vacuum; if( rc!=SQLITE_OK ) goto end_of_vacuum; /* Copy over the sequence table @@ -108489,6 +117810,7 @@ end_of_vacuum: ** This file contains code used to help implement virtual tables. */ #ifndef SQLITE_OMIT_VIRTUALTABLE +/* #include "sqliteInt.h" */ /* ** Before a virtual table xCreate() or xConnect() method is invoked, the @@ -108500,6 +117822,8 @@ end_of_vacuum: struct VtabCtx { VTable *pVTable; /* The virtual table being constructed */ Table *pTab; /* The Table object to which the virtual table belongs */ + VtabCtx *pPrior; /* Parent context (if any) */ + int bDeclared; /* True after sqlite3_declare_vtab() is called */ }; /* @@ -108519,7 +117843,7 @@ static int createModule( sqlite3_mutex_enter(db->mutex); nName = sqlite3Strlen30(zName); - if( sqlite3HashFind(&db->aModule, zName, nName) ){ + if( sqlite3HashFind(&db->aModule, zName) ){ rc = SQLITE_MISUSE_BKPT; }else{ Module *pMod; @@ -108532,7 +117856,8 @@ static int createModule( pMod->pModule = pModule; pMod->pAux = pAux; pMod->xDestroy = xDestroy; - pDel = (Module *)sqlite3HashInsert(&db->aModule,zCopy,nName,(void*)pMod); + pMod->pEpoTab = 0; + pDel = (Module *)sqlite3HashInsert(&db->aModule,zCopy,(void*)pMod); assert( pDel==0 || pDel==pMod ); if( pDel ){ db->mallocFailed = 1; @@ -108551,25 +117876,31 @@ static int createModule( /* ** External API function used to create a new virtual-table module. */ -SQLITE_API int sqlite3_create_module( +SQLITE_API int SQLITE_STDCALL sqlite3_create_module( sqlite3 *db, /* Database in which module is registered */ const char *zName, /* Name assigned to this module */ const sqlite3_module *pModule, /* The definition of the module */ void *pAux /* Context pointer for xCreate/xConnect */ ){ +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) || zName==0 ) return SQLITE_MISUSE_BKPT; +#endif return createModule(db, zName, pModule, pAux, 0); } /* ** External API function used to create a new virtual-table module. */ -SQLITE_API int sqlite3_create_module_v2( +SQLITE_API int SQLITE_STDCALL sqlite3_create_module_v2( sqlite3 *db, /* Database in which module is registered */ const char *zName, /* Name assigned to this module */ const sqlite3_module *pModule, /* The definition of the module */ void *pAux, /* Context pointer for xCreate/xConnect */ void (*xDestroy)(void *) /* Module destructor function */ ){ +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) || zName==0 ) return SQLITE_MISUSE_BKPT; +#endif return createModule(db, zName, pModule, pAux, xDestroy); } @@ -108753,23 +118084,17 @@ SQLITE_PRIVATE void sqlite3VtabClear(sqlite3 *db, Table *p){ ** deleted. */ static void addModuleArgument(sqlite3 *db, Table *pTable, char *zArg){ - int i = pTable->nModuleArg++; - int nBytes = sizeof(char *)*(1+pTable->nModuleArg); + int nBytes = sizeof(char *)*(2+pTable->nModuleArg); char **azModuleArg; azModuleArg = sqlite3DbRealloc(db, pTable->azModuleArg, nBytes); if( azModuleArg==0 ){ - int j; - for(j=0; jazModuleArg[j]); - } sqlite3DbFree(db, zArg); - sqlite3DbFree(db, pTable->azModuleArg); - pTable->nModuleArg = 0; }else{ + int i = pTable->nModuleArg++; azModuleArg[i] = zArg; azModuleArg[i+1] = 0; + pTable->azModuleArg = azModuleArg; } - pTable->azModuleArg = azModuleArg; } /* @@ -108802,7 +118127,12 @@ SQLITE_PRIVATE void sqlite3VtabBeginParse( addModuleArgument(db, pTable, sqlite3NameFromToken(db, pModuleName)); addModuleArgument(db, pTable, 0); addModuleArgument(db, pTable, sqlite3DbStrDup(db, pTable->zName)); - pParse->sNameToken.n = (int)(&pModuleName->z[pModuleName->n] - pName1->z); + assert( (pParse->sNameToken.z==pName2->z && pName2->z!=0) + || (pParse->sNameToken.z==pName1->z && pName2->z==0) + ); + pParse->sNameToken.n = (int)( + &pModuleName->z[pModuleName->n] - pParse->sNameToken.z + ); #ifndef SQLITE_OMIT_AUTHORIZATION /* Creating a virtual table invokes the authorization callback twice. @@ -108854,6 +118184,7 @@ SQLITE_PRIVATE void sqlite3VtabFinishParse(Parse *pParse, Token *pEnd){ char *zStmt; char *zWhere; int iDb; + int iReg; Vdbe *v; /* Compute the complete text of the CREATE VIRTUAL TABLE statement */ @@ -108888,8 +118219,10 @@ SQLITE_PRIVATE void sqlite3VtabFinishParse(Parse *pParse, Token *pEnd){ sqlite3VdbeAddOp2(v, OP_Expire, 0, 0); zWhere = sqlite3MPrintf(db, "name='%q' AND type='table'", pTab->zName); sqlite3VdbeAddParseSchemaOp(v, iDb, zWhere); - sqlite3VdbeAddOp4(v, OP_VCreate, iDb, 0, 0, - pTab->zName, sqlite3Strlen30(pTab->zName) + 1); + + iReg = ++pParse->nMem; + sqlite3VdbeLoadString(v, iReg, pTab->zName); + sqlite3VdbeAddOp2(v, OP_VCreate, iDb, iReg); } /* If we are rereading the sqlite_master table create the in-memory @@ -108901,9 +118234,8 @@ SQLITE_PRIVATE void sqlite3VtabFinishParse(Parse *pParse, Token *pEnd){ Table *pOld; Schema *pSchema = pTab->pSchema; const char *zName = pTab->zName; - int nName = sqlite3Strlen30(zName); assert( sqlite3SchemaMutexHeld(db, 0, pSchema) ); - pOld = sqlite3HashInsert(&pSchema->tblHash, zName, nName, pTab); + pOld = sqlite3HashInsert(&pSchema->tblHash, zName, pTab); if( pOld ){ db->mallocFailed = 1; assert( pTab==pOld ); /* Malloc must have failed inside HashInsert() */ @@ -108933,7 +118265,7 @@ SQLITE_PRIVATE void sqlite3VtabArgExtend(Parse *pParse, Token *p){ pArg->z = p->z; pArg->n = p->n; }else{ - assert(pArg->z < p->z); + assert(pArg->z <= p->z); pArg->n = (int)(&p->z[p->n] - pArg->z); } } @@ -108950,15 +118282,27 @@ static int vtabCallConstructor( int (*xConstruct)(sqlite3*,void*,int,const char*const*,sqlite3_vtab**,char**), char **pzErr ){ - VtabCtx sCtx, *pPriorCtx; + VtabCtx sCtx; VTable *pVTable; int rc; const char *const*azArg = (const char *const*)pTab->azModuleArg; int nArg = pTab->nModuleArg; char *zErr = 0; - char *zModuleName = sqlite3MPrintf(db, "%s", pTab->zName); + char *zModuleName; int iDb; + VtabCtx *pCtx; + /* Check that the virtual-table is not already being initialized */ + for(pCtx=db->pVtabCtx; pCtx; pCtx=pCtx->pPrior){ + if( pCtx->pTab==pTab ){ + *pzErr = sqlite3MPrintf(db, + "vtable constructor called recursively: %s", pTab->zName + ); + return SQLITE_LOCKED; + } + } + + zModuleName = sqlite3MPrintf(db, "%s", pTab->zName); if( !zModuleName ){ return SQLITE_NOMEM; } @@ -108979,11 +118323,13 @@ static int vtabCallConstructor( assert( xConstruct ); sCtx.pTab = pTab; sCtx.pVTable = pVTable; - pPriorCtx = db->pVtabCtx; + sCtx.pPrior = db->pVtabCtx; + sCtx.bDeclared = 0; db->pVtabCtx = &sCtx; rc = xConstruct(db, pMod->pAux, nArg, azArg, &pVTable->pVtab, &zErr); - db->pVtabCtx = pPriorCtx; + db->pVtabCtx = sCtx.pPrior; if( rc==SQLITE_NOMEM ) db->mallocFailed = 1; + assert( sCtx.pTab==pTab ); if( SQLITE_OK!=rc ){ if( zErr==0 ){ @@ -108996,15 +118342,17 @@ static int vtabCallConstructor( }else if( ALWAYS(pVTable->pVtab) ){ /* Justification of ALWAYS(): A correct vtab constructor must allocate ** the sqlite3_vtab object if successful. */ + memset(pVTable->pVtab, 0, sizeof(pVTable->pVtab[0])); pVTable->pVtab->pModule = pMod->pModule; pVTable->nRef = 1; - if( sCtx.pTab ){ + if( sCtx.bDeclared==0 ){ const char *zFormat = "vtable constructor did not declare schema: %s"; *pzErr = sqlite3MPrintf(db, zFormat, pTab->zName); sqlite3VtabUnlock(pVTable); rc = SQLITE_ERROR; }else{ int iCol; + u8 oooHidden = 0; /* If everything went according to plan, link the new VTable structure ** into the linked list headed by pTab->pVTable. Then loop through the ** columns of the table to see if any of them contain the token "hidden". @@ -109017,7 +118365,10 @@ static int vtabCallConstructor( char *zType = pTab->aCol[iCol].zType; int nType; int i = 0; - if( !zType ) continue; + if( !zType ){ + pTab->tabFlags |= oooHidden; + continue; + } nType = sqlite3Strlen30(zType); if( sqlite3StrNICmp("hidden", zType, 6)||(zType[6] && zType[6]!=' ') ){ for(i=0; iaCol[iCol].colFlags |= COLFLAG_HIDDEN; + oooHidden = TF_OOOHidden; + }else{ + pTab->tabFlags |= oooHidden; } } } @@ -109069,7 +118423,7 @@ SQLITE_PRIVATE int sqlite3VtabCallConnect(Parse *pParse, Table *pTab){ /* Locate the required virtual table module */ zMod = pTab->azModuleArg[0]; - pMod = (Module*)sqlite3HashFind(&db->aModule, zMod, sqlite3Strlen30(zMod)); + pMod = (Module*)sqlite3HashFind(&db->aModule, zMod); if( !pMod ){ const char *zModule = pTab->azModuleArg[0]; @@ -109137,13 +118491,13 @@ SQLITE_PRIVATE int sqlite3VtabCallCreate(sqlite3 *db, int iDb, const char *zTab, /* Locate the required virtual table module */ zMod = pTab->azModuleArg[0]; - pMod = (Module*)sqlite3HashFind(&db->aModule, zMod, sqlite3Strlen30(zMod)); + pMod = (Module*)sqlite3HashFind(&db->aModule, zMod); /* If the module has been registered and includes a Create method, ** invoke it now. If the module has not been registered, return an ** error. Otherwise, do nothing. */ - if( !pMod ){ + if( pMod==0 || pMod->pModule->xCreate==0 || pMod->pModule->xDestroy==0 ){ *pzErr = sqlite3MPrintf(db, "no such module: %s", zMod); rc = SQLITE_ERROR; }else{ @@ -109167,19 +118521,26 @@ SQLITE_PRIVATE int sqlite3VtabCallCreate(sqlite3 *db, int iDb, const char *zTab, ** valid to call this function from within the xCreate() or xConnect() of a ** virtual table module. */ -SQLITE_API int sqlite3_declare_vtab(sqlite3 *db, const char *zCreateTable){ +SQLITE_API int SQLITE_STDCALL sqlite3_declare_vtab(sqlite3 *db, const char *zCreateTable){ + VtabCtx *pCtx; Parse *pParse; - int rc = SQLITE_OK; Table *pTab; char *zErr = 0; +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) || zCreateTable==0 ){ + return SQLITE_MISUSE_BKPT; + } +#endif sqlite3_mutex_enter(db->mutex); - if( !db->pVtabCtx || !(pTab = db->pVtabCtx->pTab) ){ - sqlite3Error(db, SQLITE_MISUSE, 0); + pCtx = db->pVtabCtx; + if( !pCtx || pCtx->bDeclared ){ + sqlite3Error(db, SQLITE_MISUSE); sqlite3_mutex_leave(db->mutex); return SQLITE_MISUSE_BKPT; } + pTab = pCtx->pTab; assert( (pTab->tabFlags & TF_Virtual)!=0 ); pParse = sqlite3StackAllocZero(db, sizeof(*pParse)); @@ -109202,9 +118563,9 @@ SQLITE_API int sqlite3_declare_vtab(sqlite3 *db, const char *zCreateTable){ pParse->pNewTable->nCol = 0; pParse->pNewTable->aCol = 0; } - db->pVtabCtx->pTab = 0; + pCtx->bDeclared = 1; }else{ - sqlite3Error(db, SQLITE_ERROR, (zErr ? "%s" : 0), zErr); + sqlite3ErrorWithMsg(db, SQLITE_ERROR, (zErr ? "%s" : 0), zErr); sqlite3DbFree(db, zErr); rc = SQLITE_ERROR; } @@ -109237,11 +118598,18 @@ SQLITE_PRIVATE int sqlite3VtabCallDestroy(sqlite3 *db, int iDb, const char *zTab pTab = sqlite3FindTable(db, zTab, db->aDb[iDb].zName); if( ALWAYS(pTab!=0 && pTab->pVTable!=0) ){ - VTable *p = vtabDisconnectAll(db, pTab); - - assert( rc==SQLITE_OK ); - rc = p->pMod->pModule->xDestroy(p->pVtab); - + VTable *p; + int (*xDestroy)(sqlite3_vtab *); + for(p=pTab->pVTable; p; p=p->pNext){ + assert( p->pVtab ); + if( p->pVtab->nRef>0 ){ + return SQLITE_LOCKED; + } + } + p = vtabDisconnectAll(db, pTab); + xDestroy = p->pMod->pModule->xDestroy; + assert( xDestroy!=0 ); /* Checked before the virtual table is created */ + rc = xDestroy(p->pVtab); /* Remove the sqlite3_vtab* from the aVTrans[] array, if applicable */ if( rc==SQLITE_OK ){ assert( pTab->pVTable==p && p->pNext==0 ); @@ -109265,8 +118633,10 @@ SQLITE_PRIVATE int sqlite3VtabCallDestroy(sqlite3 *db, int iDb, const char *zTab static void callFinaliser(sqlite3 *db, int offset){ int i; if( db->aVTrans ){ + VTable **aVTrans = db->aVTrans; + db->aVTrans = 0; for(i=0; inVTrans; i++){ - VTable *pVTab = db->aVTrans[i]; + VTable *pVTab = aVTrans[i]; sqlite3_vtab *p = pVTab->pVtab; if( p ){ int (*x)(sqlite3_vtab *); @@ -109276,9 +118646,8 @@ static void callFinaliser(sqlite3 *db, int offset){ pVTab->iSavepoint = 0; sqlite3VtabUnlock(pVTab); } - sqlite3DbFree(db, db->aVTrans); + sqlite3DbFree(db, aVTrans); db->nVTrans = 0; - db->aVTrans = 0; } } @@ -109366,7 +118735,9 @@ SQLITE_PRIVATE int sqlite3VtabBegin(sqlite3 *db, VTable *pVTab){ if( rc==SQLITE_OK ){ rc = pModule->xBegin(pVTab->pVtab); if( rc==SQLITE_OK ){ + int iSvpt = db->nStatement + db->nSavepoint; addToVTrans(db, pVTab); + if( iSvpt ) rc = sqlite3VtabSavepoint(db, SAVEPOINT_BEGIN, iSvpt-1); } } } @@ -109392,7 +118763,7 @@ SQLITE_PRIVATE int sqlite3VtabSavepoint(sqlite3 *db, int op, int iSavepoint){ int rc = SQLITE_OK; assert( op==SAVEPOINT_RELEASE||op==SAVEPOINT_ROLLBACK||op==SAVEPOINT_BEGIN ); - assert( iSavepoint>=0 ); + assert( iSavepoint>=-1 ); if( db->aVTrans ){ int i; for(i=0; rc==SQLITE_OK && inVTrans; i++){ @@ -109510,7 +118881,7 @@ SQLITE_PRIVATE void sqlite3VtabMakeWritable(Parse *pParse, Table *pTab){ if( pTab==pToplevel->apVtabLock[i] ) return; } n = (pToplevel->nVtabLock+1)*sizeof(pToplevel->apVtabLock[0]); - apVtabLock = sqlite3_realloc(pToplevel->apVtabLock, n); + apVtabLock = sqlite3_realloc64(pToplevel->apVtabLock, n); if( apVtabLock ){ pToplevel->apVtabLock = apVtabLock; pToplevel->apVtabLock[pToplevel->nVtabLock++] = pTab; @@ -109519,6 +118890,67 @@ SQLITE_PRIVATE void sqlite3VtabMakeWritable(Parse *pParse, Table *pTab){ } } +/* +** Check to see if virtual tale module pMod can be have an eponymous +** virtual table instance. If it can, create one if one does not already +** exist. Return non-zero if the eponymous virtual table instance exists +** when this routine returns, and return zero if it does not exist. +** +** An eponymous virtual table instance is one that is named after its +** module, and more importantly, does not require a CREATE VIRTUAL TABLE +** statement in order to come into existance. Eponymous virtual table +** instances always exist. They cannot be DROP-ed. +** +** Any virtual table module for which xConnect and xCreate are the same +** method can have an eponymous virtual table instance. +*/ +SQLITE_PRIVATE int sqlite3VtabEponymousTableInit(Parse *pParse, Module *pMod){ + const sqlite3_module *pModule = pMod->pModule; + Table *pTab; + char *zErr = 0; + int nName; + int rc; + sqlite3 *db = pParse->db; + if( pMod->pEpoTab ) return 1; + if( pModule->xCreate!=0 && pModule->xCreate!=pModule->xConnect ) return 0; + nName = sqlite3Strlen30(pMod->zName) + 1; + pTab = sqlite3DbMallocZero(db, sizeof(Table) + nName); + if( pTab==0 ) return 0; + pMod->pEpoTab = pTab; + pTab->zName = (char*)&pTab[1]; + memcpy(pTab->zName, pMod->zName, nName); + pTab->nRef = 1; + pTab->pSchema = db->aDb[0].pSchema; + pTab->tabFlags |= TF_Virtual; + pTab->nModuleArg = 0; + pTab->iPKey = -1; + addModuleArgument(db, pTab, sqlite3DbStrDup(db, pTab->zName)); + addModuleArgument(db, pTab, 0); + addModuleArgument(db, pTab, sqlite3DbStrDup(db, pTab->zName)); + rc = vtabCallConstructor(db, pTab, pMod, pModule->xConnect, &zErr); + if( rc ){ + sqlite3ErrorMsg(pParse, "%s", zErr); + sqlite3DbFree(db, zErr); + sqlite3VtabEponymousTableClear(db, pMod); + return 0; + } + return 1; +} + +/* +** Erase the eponymous virtual table instance associated with +** virtual table module pMod, if it exists. +*/ +SQLITE_PRIVATE void sqlite3VtabEponymousTableClear(sqlite3 *db, Module *pMod){ + Table *pTab = pMod->pEpoTab; + if( pTab!=0 ){ + sqlite3DeleteColumnNames(db, pTab); + sqlite3VtabClear(db, pTab); + sqlite3DbFree(db, pTab); + pMod->pEpoTab = 0; + } +} + /* ** Return the ON CONFLICT resolution mode in effect for the virtual ** table update operation currently in progress. @@ -109526,10 +118958,13 @@ SQLITE_PRIVATE void sqlite3VtabMakeWritable(Parse *pParse, Table *pTab){ ** The results of this routine are undefined unless it is called from ** within an xUpdate method. */ -SQLITE_API int sqlite3_vtab_on_conflict(sqlite3 *db){ +SQLITE_API int SQLITE_STDCALL sqlite3_vtab_on_conflict(sqlite3 *db){ static const unsigned char aMap[] = { SQLITE_ROLLBACK, SQLITE_ABORT, SQLITE_FAIL, SQLITE_IGNORE, SQLITE_REPLACE }; +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ) return SQLITE_MISUSE_BKPT; +#endif assert( OE_Rollback==1 && OE_Abort==2 && OE_Fail==3 ); assert( OE_Ignore==4 && OE_Replace==5 ); assert( db->vtabOnConflict>=1 && db->vtabOnConflict<=5 ); @@ -109541,12 +118976,14 @@ SQLITE_API int sqlite3_vtab_on_conflict(sqlite3 *db){ ** the SQLite core with additional information about the behavior ** of the virtual table being implemented. */ -SQLITE_API int sqlite3_vtab_config(sqlite3 *db, int op, ...){ +SQLITE_API int SQLITE_CDECL sqlite3_vtab_config(sqlite3 *db, int op, ...){ va_list ap; int rc = SQLITE_OK; +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ) return SQLITE_MISUSE_BKPT; +#endif sqlite3_mutex_enter(db->mutex); - va_start(ap, op); switch( op ){ case SQLITE_VTAB_CONSTRAINT_SUPPORT: { @@ -109565,7 +119002,7 @@ SQLITE_API int sqlite3_vtab_config(sqlite3 *db, int op, ...){ } va_end(ap); - if( rc!=SQLITE_OK ) sqlite3Error(db, rc, 0); + if( rc!=SQLITE_OK ) sqlite3Error(db, rc); sqlite3_mutex_leave(db->mutex); return rc; } @@ -109573,9 +119010,9 @@ SQLITE_API int sqlite3_vtab_config(sqlite3 *db, int op, ...){ #endif /* SQLITE_OMIT_VIRTUALTABLE */ /************** End of vtab.c ************************************************/ -/************** Begin file where.c *******************************************/ +/************** Begin file wherecode.c ***************************************/ /* -** 2001 September 15 +** 2015-06-06 ** ** The author disclaims copyright to this source code. In place of ** a legal notice, here is a blessing: @@ -109586,13 +119023,15 @@ SQLITE_API int sqlite3_vtab_config(sqlite3 *db, int op, ...){ ** ************************************************************************* ** This module contains C code that generates VDBE code used to process -** the WHERE clause of SQL statements. This module is responsible for -** generating the code that loops through a table looking for applicable -** rows. Indices are selected and used to speed the search when doing -** so is applicable. Because this module is responsible for selecting -** indices, you might also think of this module as the "query optimizer". +** the WHERE clause of SQL statements. +** +** This file was split off from where.c on 2015-06-06 in order to reduce the +** size of where.c and make it easier to edit. This file contains the routines +** that actually generate the bulk of the WHERE loop code. The original where.c +** file retains the code that does query planning and analysis. */ -/************** Include whereInt.h in the middle of where.c ******************/ +/* #include "sqliteInt.h" */ +/************** Include whereInt.h in the middle of wherecode.c **************/ /************** Begin file whereInt.h ****************************************/ /* ** 2013-11-12 @@ -109615,7 +119054,7 @@ SQLITE_API int sqlite3_vtab_config(sqlite3 *db, int op, ...){ ** Trace output macros */ #if defined(SQLITE_TEST) || defined(SQLITE_DEBUG) -/***/ int sqlite3WhereTrace = 0; +/***/ int sqlite3WhereTrace; #endif #if defined(SQLITE_DEBUG) \ && (defined(SQLITE_TEST) || defined(SQLITE_ENABLE_WHERETRACE)) @@ -109665,6 +119104,10 @@ struct WhereLevel { int addrCont; /* Jump here to continue with the next loop cycle */ int addrFirst; /* First instruction of interior of the loop */ int addrBody; /* Beginning of the body of this loop */ +#ifndef SQLITE_LIKE_DOESNT_MATCH_BLOBS + int iLikeRepCntr; /* LIKE range processing counter register */ + int addrLikeRep; /* LIKE range processing address */ +#endif u8 iFrom; /* Which entry in the FROM clause */ u8 op, p3, p5; /* Opcode, P3 & P5 of the opcode that ends the loop */ int p1, p2; /* Operands of the opcode used to ends the loop */ @@ -109681,6 +119124,9 @@ struct WhereLevel { } u; struct WhereLoop *pWLoop; /* The selected WhereLoop object */ Bitmask notReady; /* FROM entries not usable at this level */ +#ifdef SQLITE_ENABLE_STMT_SCANSTATUS + int addrVisit; /* Address at which row is visited */ +#endif }; /* @@ -109711,7 +119157,6 @@ struct WhereLoop { union { struct { /* Information for internal btree tables */ u16 nEq; /* Number of equality constraints */ - u16 nSkip; /* Number of initial index columns to skip */ Index *pIndex; /* Index used, or NULL */ } btree; struct { /* Information for virtual tables */ @@ -109724,12 +119169,13 @@ struct WhereLoop { } u; u32 wsFlags; /* WHERE_* flags describing the plan */ u16 nLTerm; /* Number of entries in aLTerm[] */ + u16 nSkip; /* Number of NULL aLTerm[] entries */ /**** whereLoopXfer() copies fields above ***********************/ # define WHERE_LOOP_XFER_SZ offsetof(WhereLoop,nLSlot) u16 nLSlot; /* Number of slots allocated for aLTerm[] */ WhereTerm **aLTerm; /* WhereTerms used */ WhereLoop *pNextLoop; /* Next WhereLoop object in the WhereClause */ - WhereTerm *aLTermSpace[4]; /* Initial aLTerm[] space */ + WhereTerm *aLTermSpace[3]; /* Initial aLTerm[] space */ }; /* This object holds the prerequisites and the cost of running a @@ -109752,10 +119198,6 @@ struct WhereOrSet { WhereOrCost a[N_OR_COST]; /* Set of best costs */ }; - -/* Forward declaration of methods */ -static int whereLoopResize(sqlite3*, WhereLoop*, int); - /* ** Each instance of this object holds a sequence of WhereLoop objects ** that implement some or all of a query plan. @@ -109772,13 +119214,14 @@ static int whereLoopResize(sqlite3*, WhereLoop*, int); ** 1. Then using those as a basis to compute the N best WherePath objects ** of length 2. And so forth until the length of WherePaths equals the ** number of nodes in the FROM clause. The best (lowest cost) WherePath -** at the end is the choosen query plan. +** at the end is the chosen query plan. */ struct WherePath { Bitmask maskLoop; /* Bitmask of all WhereLoop objects in this path */ Bitmask revLoop; /* aLoop[]s that should be reversed for ORDER BY */ LogEst nRow; /* Estimated number of rows generated by this path */ LogEst rCost; /* Total cost of this path */ + LogEst rUnsorted; /* Total cost of this path ignoring sorting costs */ i8 isOrdered; /* No. of ORDER BY terms satisfied. -1 for unknown */ WhereLoop **aLoop; /* Array of WhereLoop objects implementing this path */ }; @@ -109845,8 +119288,9 @@ struct WhereTerm { } u; LogEst truthProb; /* Probability of truth for this expression */ u16 eOperator; /* A WO_xx value describing */ - u8 wtFlags; /* TERM_xxx bit flags. See below */ + u16 wtFlags; /* TERM_xxx bit flags. See below */ u8 nChild; /* Number of children that must disable us */ + u8 eMatchOp; /* Op for vtab MATCH/LIKE/GLOB/REGEXP terms */ WhereClause *pWC; /* The clause this term is part of */ Bitmask prereqRight; /* Bitmask of tables used by pExpr->pRight */ Bitmask prereqAll; /* Bitmask of tables referenced by pExpr */ @@ -109867,6 +119311,10 @@ struct WhereTerm { #else # define TERM_VNULL 0x00 /* Disabled if not using stat3 */ #endif +#define TERM_LIKEOPT 0x100 /* Virtual terms from the LIKE optimization */ +#define TERM_LIKECOND 0x200 /* Conditionally this LIKE operator term */ +#define TERM_LIKE 0x400 /* The original LIKE operator */ +#define TERM_IS 0x800 /* Term.pExpr is an IS operator */ /* ** An instance of the WhereScan object is used as an iterator for locating @@ -109875,13 +119323,15 @@ struct WhereTerm { struct WhereScan { WhereClause *pOrigWC; /* Original, innermost WhereClause */ WhereClause *pWC; /* WhereClause currently being scanned */ - char *zCollName; /* Required collating sequence, if not NULL */ + const char *zCollName; /* Required collating sequence, if not NULL */ + Expr *pIdxExpr; /* Search for this index expression */ char idxaff; /* Must match this affinity, if zCollName!=NULL */ unsigned char nEquiv; /* Number of entries in aEquiv[] */ unsigned char iEquiv; /* Next unused slot in aEquiv[] */ u32 opMask; /* Acceptable operators */ int k; /* Resume scanning at this->pWC->a[this->k] */ - int aEquiv[22]; /* Cursor,Column pairs for equivalence classes */ + int aiCur[11]; /* Cursors in the equivalence class */ + i16 aiColumn[11]; /* Corresponding column number in the eq-class */ }; /* @@ -109958,6 +119408,11 @@ struct WhereMaskSet { int ix[BMS]; /* Cursor assigned to each bit */ }; +/* +** Initialize a WhereMaskSet object +*/ +#define initMaskSet(P) (P)->n=0 + /* ** This object is a convenience wrapper holding all information needed ** to construct WhereLoop objects for a particular query. @@ -109995,7 +119450,7 @@ struct WhereInfo { u16 wctrlFlags; /* Flags originally passed to sqlite3WhereBegin() */ i8 nOBSat; /* Number of ORDER BY terms satisfied by indices */ u8 sorted; /* True if really sorted (not just grouped) */ - u8 okOnePass; /* Ok to use one-pass algorithm for UPDATE/DELETE */ + u8 eOnePass; /* ONEPASS_OFF, or _SINGLE, or _MULTI */ u8 untestedTerms; /* Not all WHERE terms resolved by outer loop */ u8 eDistinct; /* One of the WHERE_DISTINCT_* values below */ u8 nLevel; /* Number of nested loop */ @@ -110009,27 +119464,85 @@ struct WhereInfo { WhereLevel a[1]; /* Information about each nest loop in WHERE */ }; +/* +** Private interfaces - callable only by other where.c routines. +** +** where.c: +*/ +SQLITE_PRIVATE Bitmask sqlite3WhereGetMask(WhereMaskSet*,int); +SQLITE_PRIVATE WhereTerm *sqlite3WhereFindTerm( + WhereClause *pWC, /* The WHERE clause to be searched */ + int iCur, /* Cursor number of LHS */ + int iColumn, /* Column number of LHS */ + Bitmask notReady, /* RHS must not overlap with this mask */ + u32 op, /* Mask of WO_xx values describing operator */ + Index *pIdx /* Must be compatible with this index, if not NULL */ +); + +/* wherecode.c: */ +#ifndef SQLITE_OMIT_EXPLAIN +SQLITE_PRIVATE int sqlite3WhereExplainOneScan( + Parse *pParse, /* Parse context */ + SrcList *pTabList, /* Table list this loop refers to */ + WhereLevel *pLevel, /* Scan to write OP_Explain opcode for */ + int iLevel, /* Value for "level" column of output */ + int iFrom, /* Value for "from" column of output */ + u16 wctrlFlags /* Flags passed to sqlite3WhereBegin() */ +); +#else +# define sqlite3WhereExplainOneScan(u,v,w,x,y,z) 0 +#endif /* SQLITE_OMIT_EXPLAIN */ +#ifdef SQLITE_ENABLE_STMT_SCANSTATUS +SQLITE_PRIVATE void sqlite3WhereAddScanStatus( + Vdbe *v, /* Vdbe to add scanstatus entry to */ + SrcList *pSrclist, /* FROM clause pLvl reads data from */ + WhereLevel *pLvl, /* Level to add scanstatus() entry for */ + int addrExplain /* Address of OP_Explain (or 0) */ +); +#else +# define sqlite3WhereAddScanStatus(a, b, c, d) ((void)d) +#endif +SQLITE_PRIVATE Bitmask sqlite3WhereCodeOneLoopStart( + WhereInfo *pWInfo, /* Complete information about the WHERE clause */ + int iLevel, /* Which level of pWInfo->a[] should be coded */ + Bitmask notReady /* Which tables are currently available */ +); + +/* whereexpr.c: */ +SQLITE_PRIVATE void sqlite3WhereClauseInit(WhereClause*,WhereInfo*); +SQLITE_PRIVATE void sqlite3WhereClauseClear(WhereClause*); +SQLITE_PRIVATE void sqlite3WhereSplit(WhereClause*,Expr*,u8); +SQLITE_PRIVATE Bitmask sqlite3WhereExprUsage(WhereMaskSet*, Expr*); +SQLITE_PRIVATE Bitmask sqlite3WhereExprListUsage(WhereMaskSet*, ExprList*); +SQLITE_PRIVATE void sqlite3WhereExprAnalyze(SrcList*, WhereClause*); +SQLITE_PRIVATE void sqlite3WhereTabFuncArgs(Parse*, struct SrcList_item*, WhereClause*); + + + + + /* ** Bitmasks for the operators on WhereTerm objects. These are all ** operators that are of interest to the query planner. An ** OR-ed combination of these values can be used when searching for ** particular WhereTerms within a WhereClause. */ -#define WO_IN 0x001 -#define WO_EQ 0x002 +#define WO_IN 0x0001 +#define WO_EQ 0x0002 #define WO_LT (WO_EQ<<(TK_LT-TK_EQ)) #define WO_LE (WO_EQ<<(TK_LE-TK_EQ)) #define WO_GT (WO_EQ<<(TK_GT-TK_EQ)) #define WO_GE (WO_EQ<<(TK_GE-TK_EQ)) -#define WO_MATCH 0x040 -#define WO_ISNULL 0x080 -#define WO_OR 0x100 /* Two or more OR-connected terms */ -#define WO_AND 0x200 /* Two or more AND-connected terms */ -#define WO_EQUIV 0x400 /* Of the form A==B, both columns */ -#define WO_NOOP 0x800 /* This term does not restrict search space */ +#define WO_MATCH 0x0040 +#define WO_IS 0x0080 +#define WO_ISNULL 0x0100 +#define WO_OR 0x0200 /* Two or more OR-connected terms */ +#define WO_AND 0x0400 /* Two or more AND-connected terms */ +#define WO_EQUIV 0x0800 /* Of the form A==B, both columns */ +#define WO_NOOP 0x1000 /* This term does not restrict search space */ -#define WO_ALL 0xfff /* Mask of all possible WO_* values */ -#define WO_SINGLE 0x0ff /* Mask of all non-compound WO_* values */ +#define WO_ALL 0x1fff /* Mask of all possible WO_* values */ +#define WO_SINGLE 0x01ff /* Mask of all non-compound WO_* values */ /* ** These are definitions of bits in the WhereLoop.wsFlags field. @@ -110054,2274 +119567,222 @@ struct WhereInfo { #define WHERE_AUTO_INDEX 0x00004000 /* Uses an ephemeral index */ #define WHERE_SKIPSCAN 0x00008000 /* Uses the skip-scan algorithm */ #define WHERE_UNQ_WANTED 0x00010000 /* WHERE_ONEROW would have been helpful*/ +#define WHERE_PARTIALIDX 0x00020000 /* The automatic index is partial */ /************** End of whereInt.h ********************************************/ -/************** Continuing where we left off in where.c **********************/ +/************** Continuing where we left off in wherecode.c ******************/ +#ifndef SQLITE_OMIT_EXPLAIN /* -** Return the estimated number of output rows from a WHERE clause -*/ -SQLITE_PRIVATE u64 sqlite3WhereOutputRowCount(WhereInfo *pWInfo){ - return sqlite3LogEstToInt(pWInfo->nRowOut); -} - -/* -** Return one of the WHERE_DISTINCT_xxxxx values to indicate how this -** WHERE clause returns outputs for DISTINCT processing. -*/ -SQLITE_PRIVATE int sqlite3WhereIsDistinct(WhereInfo *pWInfo){ - return pWInfo->eDistinct; -} - -/* -** Return TRUE if the WHERE clause returns rows in ORDER BY order. -** Return FALSE if the output needs to be sorted. -*/ -SQLITE_PRIVATE int sqlite3WhereIsOrdered(WhereInfo *pWInfo){ - return pWInfo->nOBSat; -} - -/* -** Return the VDBE address or label to jump to in order to continue -** immediately with the next row of a WHERE clause. -*/ -SQLITE_PRIVATE int sqlite3WhereContinueLabel(WhereInfo *pWInfo){ - assert( pWInfo->iContinue!=0 ); - return pWInfo->iContinue; -} - -/* -** Return the VDBE address or label to jump to in order to break -** out of a WHERE loop. -*/ -SQLITE_PRIVATE int sqlite3WhereBreakLabel(WhereInfo *pWInfo){ - return pWInfo->iBreak; -} - -/* -** Return TRUE if an UPDATE or DELETE statement can operate directly on -** the rowids returned by a WHERE clause. Return FALSE if doing an -** UPDATE or DELETE might change subsequent WHERE clause results. +** This routine is a helper for explainIndexRange() below ** -** If the ONEPASS optimization is used (if this routine returns true) -** then also write the indices of open cursors used by ONEPASS -** into aiCur[0] and aiCur[1]. iaCur[0] gets the cursor of the data -** table and iaCur[1] gets the cursor used by an auxiliary index. -** Either value may be -1, indicating that cursor is not used. -** Any cursors returned will have been opened for writing. -** -** aiCur[0] and aiCur[1] both get -1 if the where-clause logic is -** unable to use the ONEPASS optimization. +** pStr holds the text of an expression that we are building up one term +** at a time. This routine adds a new term to the end of the expression. +** Terms are separated by AND so add the "AND" text for second and subsequent +** terms only. */ -SQLITE_PRIVATE int sqlite3WhereOkOnePass(WhereInfo *pWInfo, int *aiCur){ - memcpy(aiCur, pWInfo->aiCurOnePass, sizeof(int)*2); - return pWInfo->okOnePass; -} - -/* -** Move the content of pSrc into pDest -*/ -static void whereOrMove(WhereOrSet *pDest, WhereOrSet *pSrc){ - pDest->n = pSrc->n; - memcpy(pDest->a, pSrc->a, pDest->n*sizeof(pDest->a[0])); -} - -/* -** Try to insert a new prerequisite/cost entry into the WhereOrSet pSet. -** -** The new entry might overwrite an existing entry, or it might be -** appended, or it might be discarded. Do whatever is the right thing -** so that pSet keeps the N_OR_COST best entries seen so far. -*/ -static int whereOrInsert( - WhereOrSet *pSet, /* The WhereOrSet to be updated */ - Bitmask prereq, /* Prerequisites of the new entry */ - LogEst rRun, /* Run-cost of the new entry */ - LogEst nOut /* Number of outputs for the new entry */ +static void explainAppendTerm( + StrAccum *pStr, /* The text expression being built */ + int iTerm, /* Index of this term. First is zero */ + const char *zColumn, /* Name of the column */ + const char *zOp /* Name of the operator */ ){ - u16 i; - WhereOrCost *p; - for(i=pSet->n, p=pSet->a; i>0; i--, p++){ - if( rRun<=p->rRun && (prereq & p->prereq)==prereq ){ - goto whereOrInsert_done; - } - if( p->rRun<=rRun && (p->prereq & prereq)==p->prereq ){ - return 0; - } - } - if( pSet->na[pSet->n++]; - p->nOut = nOut; - }else{ - p = pSet->a; - for(i=1; in; i++){ - if( p->rRun>pSet->a[i].rRun ) p = pSet->a + i; - } - if( p->rRun<=rRun ) return 0; - } -whereOrInsert_done: - p->prereq = prereq; - p->rRun = rRun; - if( p->nOut>nOut ) p->nOut = nOut; - return 1; + if( iTerm ) sqlite3StrAccumAppend(pStr, " AND ", 5); + sqlite3StrAccumAppendAll(pStr, zColumn); + sqlite3StrAccumAppend(pStr, zOp, 1); + sqlite3StrAccumAppend(pStr, "?", 1); } /* -** Initialize a preallocated WhereClause structure. +** Return the name of the i-th column of the pIdx index. */ -static void whereClauseInit( - WhereClause *pWC, /* The WhereClause to be initialized */ - WhereInfo *pWInfo /* The WHERE processing context */ -){ - pWC->pWInfo = pWInfo; - pWC->pOuter = 0; - pWC->nTerm = 0; - pWC->nSlot = ArraySize(pWC->aStatic); - pWC->a = pWC->aStatic; -} - -/* Forward reference */ -static void whereClauseClear(WhereClause*); - -/* -** Deallocate all memory associated with a WhereOrInfo object. -*/ -static void whereOrInfoDelete(sqlite3 *db, WhereOrInfo *p){ - whereClauseClear(&p->wc); - sqlite3DbFree(db, p); +static const char *explainIndexColumnName(Index *pIdx, int i){ + i = pIdx->aiColumn[i]; + if( i==XN_EXPR ) return ""; + if( i==XN_ROWID ) return "rowid"; + return pIdx->pTable->aCol[i].zName; } /* -** Deallocate all memory associated with a WhereAndInfo object. +** Argument pLevel describes a strategy for scanning table pTab. This +** function appends text to pStr that describes the subset of table +** rows scanned by the strategy in the form of an SQL expression. +** +** For example, if the query: +** +** SELECT * FROM t1 WHERE a=1 AND b>2; +** +** is run and there is an index on (a, b), then this function returns a +** string similar to: +** +** "a=? AND b>?" */ -static void whereAndInfoDelete(sqlite3 *db, WhereAndInfo *p){ - whereClauseClear(&p->wc); - sqlite3DbFree(db, p); -} - -/* -** Deallocate a WhereClause structure. The WhereClause structure -** itself is not freed. This routine is the inverse of whereClauseInit(). -*/ -static void whereClauseClear(WhereClause *pWC){ - int i; - WhereTerm *a; - sqlite3 *db = pWC->pWInfo->pParse->db; - for(i=pWC->nTerm-1, a=pWC->a; i>=0; i--, a++){ - if( a->wtFlags & TERM_DYNAMIC ){ - sqlite3ExprDelete(db, a->pExpr); - } - if( a->wtFlags & TERM_ORINFO ){ - whereOrInfoDelete(db, a->u.pOrInfo); - }else if( a->wtFlags & TERM_ANDINFO ){ - whereAndInfoDelete(db, a->u.pAndInfo); - } - } - if( pWC->a!=pWC->aStatic ){ - sqlite3DbFree(db, pWC->a); - } -} - -/* -** Add a single new WhereTerm entry to the WhereClause object pWC. -** The new WhereTerm object is constructed from Expr p and with wtFlags. -** The index in pWC->a[] of the new WhereTerm is returned on success. -** 0 is returned if the new WhereTerm could not be added due to a memory -** allocation error. The memory allocation failure will be recorded in -** the db->mallocFailed flag so that higher-level functions can detect it. -** -** This routine will increase the size of the pWC->a[] array as necessary. -** -** If the wtFlags argument includes TERM_DYNAMIC, then responsibility -** for freeing the expression p is assumed by the WhereClause object pWC. -** This is true even if this routine fails to allocate a new WhereTerm. -** -** WARNING: This routine might reallocate the space used to store -** WhereTerms. All pointers to WhereTerms should be invalidated after -** calling this routine. Such pointers may be reinitialized by referencing -** the pWC->a[] array. -*/ -static int whereClauseInsert(WhereClause *pWC, Expr *p, u8 wtFlags){ - WhereTerm *pTerm; - int idx; - testcase( wtFlags & TERM_VIRTUAL ); - if( pWC->nTerm>=pWC->nSlot ){ - WhereTerm *pOld = pWC->a; - sqlite3 *db = pWC->pWInfo->pParse->db; - pWC->a = sqlite3DbMallocRaw(db, sizeof(pWC->a[0])*pWC->nSlot*2 ); - if( pWC->a==0 ){ - if( wtFlags & TERM_DYNAMIC ){ - sqlite3ExprDelete(db, p); - } - pWC->a = pOld; - return 0; - } - memcpy(pWC->a, pOld, sizeof(pWC->a[0])*pWC->nTerm); - if( pOld!=pWC->aStatic ){ - sqlite3DbFree(db, pOld); - } - pWC->nSlot = sqlite3DbMallocSize(db, pWC->a)/sizeof(pWC->a[0]); - } - pTerm = &pWC->a[idx = pWC->nTerm++]; - if( p && ExprHasProperty(p, EP_Unlikely) ){ - pTerm->truthProb = sqlite3LogEst(p->iTable) - 99; - }else{ - pTerm->truthProb = 1; - } - pTerm->pExpr = sqlite3ExprSkipCollate(p); - pTerm->wtFlags = wtFlags; - pTerm->pWC = pWC; - pTerm->iParent = -1; - return idx; -} - -/* -** This routine identifies subexpressions in the WHERE clause where -** each subexpression is separated by the AND operator or some other -** operator specified in the op parameter. The WhereClause structure -** is filled with pointers to subexpressions. For example: -** -** WHERE a=='hello' AND coalesce(b,11)<10 AND (c+12!=d OR c==22) -** \________/ \_______________/ \________________/ -** slot[0] slot[1] slot[2] -** -** The original WHERE clause in pExpr is unaltered. All this routine -** does is make slot[] entries point to substructure within pExpr. -** -** In the previous sentence and in the diagram, "slot[]" refers to -** the WhereClause.a[] array. The slot[] array grows as needed to contain -** all terms of the WHERE clause. -*/ -static void whereSplit(WhereClause *pWC, Expr *pExpr, u8 op){ - pWC->op = op; - if( pExpr==0 ) return; - if( pExpr->op!=op ){ - whereClauseInsert(pWC, pExpr, 0); - }else{ - whereSplit(pWC, pExpr->pLeft, op); - whereSplit(pWC, pExpr->pRight, op); - } -} - -/* -** Initialize a WhereMaskSet object -*/ -#define initMaskSet(P) (P)->n=0 - -/* -** Return the bitmask for the given cursor number. Return 0 if -** iCursor is not in the set. -*/ -static Bitmask getMask(WhereMaskSet *pMaskSet, int iCursor){ - int i; - assert( pMaskSet->n<=(int)sizeof(Bitmask)*8 ); - for(i=0; in; i++){ - if( pMaskSet->ix[i]==iCursor ){ - return MASKBIT(i); - } - } - return 0; -} - -/* -** Create a new mask for cursor iCursor. -** -** There is one cursor per table in the FROM clause. The number of -** tables in the FROM clause is limited by a test early in the -** sqlite3WhereBegin() routine. So we know that the pMaskSet->ix[] -** array will never overflow. -*/ -static void createMask(WhereMaskSet *pMaskSet, int iCursor){ - assert( pMaskSet->n < ArraySize(pMaskSet->ix) ); - pMaskSet->ix[pMaskSet->n++] = iCursor; -} - -/* -** These routines walk (recursively) an expression tree and generate -** a bitmask indicating which tables are used in that expression -** tree. -*/ -static Bitmask exprListTableUsage(WhereMaskSet*, ExprList*); -static Bitmask exprSelectTableUsage(WhereMaskSet*, Select*); -static Bitmask exprTableUsage(WhereMaskSet *pMaskSet, Expr *p){ - Bitmask mask = 0; - if( p==0 ) return 0; - if( p->op==TK_COLUMN ){ - mask = getMask(pMaskSet, p->iTable); - return mask; - } - mask = exprTableUsage(pMaskSet, p->pRight); - mask |= exprTableUsage(pMaskSet, p->pLeft); - if( ExprHasProperty(p, EP_xIsSelect) ){ - mask |= exprSelectTableUsage(pMaskSet, p->x.pSelect); - }else{ - mask |= exprListTableUsage(pMaskSet, p->x.pList); - } - return mask; -} -static Bitmask exprListTableUsage(WhereMaskSet *pMaskSet, ExprList *pList){ - int i; - Bitmask mask = 0; - if( pList ){ - for(i=0; inExpr; i++){ - mask |= exprTableUsage(pMaskSet, pList->a[i].pExpr); - } - } - return mask; -} -static Bitmask exprSelectTableUsage(WhereMaskSet *pMaskSet, Select *pS){ - Bitmask mask = 0; - while( pS ){ - SrcList *pSrc = pS->pSrc; - mask |= exprListTableUsage(pMaskSet, pS->pEList); - mask |= exprListTableUsage(pMaskSet, pS->pGroupBy); - mask |= exprListTableUsage(pMaskSet, pS->pOrderBy); - mask |= exprTableUsage(pMaskSet, pS->pWhere); - mask |= exprTableUsage(pMaskSet, pS->pHaving); - if( ALWAYS(pSrc!=0) ){ - int i; - for(i=0; inSrc; i++){ - mask |= exprSelectTableUsage(pMaskSet, pSrc->a[i].pSelect); - mask |= exprTableUsage(pMaskSet, pSrc->a[i].pOn); - } - } - pS = pS->pPrior; - } - return mask; -} - -/* -** Return TRUE if the given operator is one of the operators that is -** allowed for an indexable WHERE clause term. The allowed operators are -** "=", "<", ">", "<=", ">=", "IN", and "IS NULL" -*/ -static int allowedOp(int op){ - assert( TK_GT>TK_EQ && TK_GTTK_EQ && TK_LTTK_EQ && TK_LE=TK_EQ && op<=TK_GE) || op==TK_ISNULL; -} - -/* -** Swap two objects of type TYPE. -*/ -#define SWAP(TYPE,A,B) {TYPE t=A; A=B; B=t;} - -/* -** Commute a comparison operator. Expressions of the form "X op Y" -** are converted into "Y op X". -** -** If left/right precedence rules come into play when determining the -** collating sequence, then COLLATE operators are adjusted to ensure -** that the collating sequence does not change. For example: -** "Y collate NOCASE op X" becomes "X op Y" because any collation sequence on -** the left hand side of a comparison overrides any collation sequence -** attached to the right. For the same reason the EP_Collate flag -** is not commuted. -*/ -static void exprCommute(Parse *pParse, Expr *pExpr){ - u16 expRight = (pExpr->pRight->flags & EP_Collate); - u16 expLeft = (pExpr->pLeft->flags & EP_Collate); - assert( allowedOp(pExpr->op) && pExpr->op!=TK_IN ); - if( expRight==expLeft ){ - /* Either X and Y both have COLLATE operator or neither do */ - if( expRight ){ - /* Both X and Y have COLLATE operators. Make sure X is always - ** used by clearing the EP_Collate flag from Y. */ - pExpr->pRight->flags &= ~EP_Collate; - }else if( sqlite3ExprCollSeq(pParse, pExpr->pLeft)!=0 ){ - /* Neither X nor Y have COLLATE operators, but X has a non-default - ** collating sequence. So add the EP_Collate marker on X to cause - ** it to be searched first. */ - pExpr->pLeft->flags |= EP_Collate; - } - } - SWAP(Expr*,pExpr->pRight,pExpr->pLeft); - if( pExpr->op>=TK_GT ){ - assert( TK_LT==TK_GT+2 ); - assert( TK_GE==TK_LE+2 ); - assert( TK_GT>TK_EQ ); - assert( TK_GTop>=TK_GT && pExpr->op<=TK_GE ); - pExpr->op = ((pExpr->op-TK_GT)^2)+TK_GT; - } -} - -/* -** Translate from TK_xx operator to WO_xx bitmask. -*/ -static u16 operatorMask(int op){ - u16 c; - assert( allowedOp(op) ); - if( op==TK_IN ){ - c = WO_IN; - }else if( op==TK_ISNULL ){ - c = WO_ISNULL; - }else{ - assert( (WO_EQ<<(op-TK_EQ)) < 0x7fff ); - c = (u16)(WO_EQ<<(op-TK_EQ)); - } - assert( op!=TK_ISNULL || c==WO_ISNULL ); - assert( op!=TK_IN || c==WO_IN ); - assert( op!=TK_EQ || c==WO_EQ ); - assert( op!=TK_LT || c==WO_LT ); - assert( op!=TK_LE || c==WO_LE ); - assert( op!=TK_GT || c==WO_GT ); - assert( op!=TK_GE || c==WO_GE ); - return c; -} - -/* -** Advance to the next WhereTerm that matches according to the criteria -** established when the pScan object was initialized by whereScanInit(). -** Return NULL if there are no more matching WhereTerms. -*/ -static WhereTerm *whereScanNext(WhereScan *pScan){ - int iCur; /* The cursor on the LHS of the term */ - int iColumn; /* The column on the LHS of the term. -1 for IPK */ - Expr *pX; /* An expression being tested */ - WhereClause *pWC; /* Shorthand for pScan->pWC */ - WhereTerm *pTerm; /* The term being tested */ - int k = pScan->k; /* Where to start scanning */ - - while( pScan->iEquiv<=pScan->nEquiv ){ - iCur = pScan->aEquiv[pScan->iEquiv-2]; - iColumn = pScan->aEquiv[pScan->iEquiv-1]; - while( (pWC = pScan->pWC)!=0 ){ - for(pTerm=pWC->a+k; knTerm; k++, pTerm++){ - if( pTerm->leftCursor==iCur - && pTerm->u.leftColumn==iColumn - && (pScan->iEquiv<=2 || !ExprHasProperty(pTerm->pExpr, EP_FromJoin)) - ){ - if( (pTerm->eOperator & WO_EQUIV)!=0 - && pScan->nEquivaEquiv) - ){ - int j; - pX = sqlite3ExprSkipCollate(pTerm->pExpr->pRight); - assert( pX->op==TK_COLUMN ); - for(j=0; jnEquiv; j+=2){ - if( pScan->aEquiv[j]==pX->iTable - && pScan->aEquiv[j+1]==pX->iColumn ){ - break; - } - } - if( j==pScan->nEquiv ){ - pScan->aEquiv[j] = pX->iTable; - pScan->aEquiv[j+1] = pX->iColumn; - pScan->nEquiv += 2; - } - } - if( (pTerm->eOperator & pScan->opMask)!=0 ){ - /* Verify the affinity and collating sequence match */ - if( pScan->zCollName && (pTerm->eOperator & WO_ISNULL)==0 ){ - CollSeq *pColl; - Parse *pParse = pWC->pWInfo->pParse; - pX = pTerm->pExpr; - if( !sqlite3IndexAffinityOk(pX, pScan->idxaff) ){ - continue; - } - assert(pX->pLeft); - pColl = sqlite3BinaryCompareCollSeq(pParse, - pX->pLeft, pX->pRight); - if( pColl==0 ) pColl = pParse->db->pDfltColl; - if( sqlite3StrICmp(pColl->zName, pScan->zCollName) ){ - continue; - } - } - if( (pTerm->eOperator & WO_EQ)!=0 - && (pX = pTerm->pExpr->pRight)->op==TK_COLUMN - && pX->iTable==pScan->aEquiv[0] - && pX->iColumn==pScan->aEquiv[1] - ){ - continue; - } - pScan->k = k+1; - return pTerm; - } - } - } - pScan->pWC = pScan->pWC->pOuter; - k = 0; - } - pScan->pWC = pScan->pOrigWC; - k = 0; - pScan->iEquiv += 2; - } - return 0; -} - -/* -** Initialize a WHERE clause scanner object. Return a pointer to the -** first match. Return NULL if there are no matches. -** -** The scanner will be searching the WHERE clause pWC. It will look -** for terms of the form "X " where X is column iColumn of table -** iCur. The must be one of the operators described by opMask. -** -** If the search is for X and the WHERE clause contains terms of the -** form X=Y then this routine might also return terms of the form -** "Y ". The number of levels of transitivity is limited, -** but is enough to handle most commonly occurring SQL statements. -** -** If X is not the INTEGER PRIMARY KEY then X must be compatible with -** index pIdx. -*/ -static WhereTerm *whereScanInit( - WhereScan *pScan, /* The WhereScan object being initialized */ - WhereClause *pWC, /* The WHERE clause to be scanned */ - int iCur, /* Cursor to scan for */ - int iColumn, /* Column to scan for */ - u32 opMask, /* Operator(s) to scan for */ - Index *pIdx /* Must be compatible with this index */ -){ - int j; - - /* memset(pScan, 0, sizeof(*pScan)); */ - pScan->pOrigWC = pWC; - pScan->pWC = pWC; - if( pIdx && iColumn>=0 ){ - pScan->idxaff = pIdx->pTable->aCol[iColumn].affinity; - for(j=0; pIdx->aiColumn[j]!=iColumn; j++){ - if( NEVER(j>=pIdx->nKeyCol) ) return 0; - } - pScan->zCollName = pIdx->azColl[j]; - }else{ - pScan->idxaff = 0; - pScan->zCollName = 0; - } - pScan->opMask = opMask; - pScan->k = 0; - pScan->aEquiv[0] = iCur; - pScan->aEquiv[1] = iColumn; - pScan->nEquiv = 2; - pScan->iEquiv = 2; - return whereScanNext(pScan); -} - -/* -** Search for a term in the WHERE clause that is of the form "X " -** where X is a reference to the iColumn of table iCur and is one of -** the WO_xx operator codes specified by the op parameter. -** Return a pointer to the term. Return 0 if not found. -** -** The term returned might by Y= if there is another constraint in -** the WHERE clause that specifies that X=Y. Any such constraints will be -** identified by the WO_EQUIV bit in the pTerm->eOperator field. The -** aEquiv[] array holds X and all its equivalents, with each SQL variable -** taking up two slots in aEquiv[]. The first slot is for the cursor number -** and the second is for the column number. There are 22 slots in aEquiv[] -** so that means we can look for X plus up to 10 other equivalent values. -** Hence a search for X will return if X=A1 and A1=A2 and A2=A3 -** and ... and A9=A10 and A10=. -** -** If there are multiple terms in the WHERE clause of the form "X " -** then try for the one with no dependencies on - in other words where -** is a constant expression of some kind. Only return entries of -** the form "X Y" where Y is a column in another table if no terms of -** the form "X " exist. If no terms with a constant RHS -** exist, try to return a term that does not use WO_EQUIV. -*/ -static WhereTerm *findTerm( - WhereClause *pWC, /* The WHERE clause to be searched */ - int iCur, /* Cursor number of LHS */ - int iColumn, /* Column number of LHS */ - Bitmask notReady, /* RHS must not overlap with this mask */ - u32 op, /* Mask of WO_xx values describing operator */ - Index *pIdx /* Must be compatible with this index, if not NULL */ -){ - WhereTerm *pResult = 0; - WhereTerm *p; - WhereScan scan; - - p = whereScanInit(&scan, pWC, iCur, iColumn, op, pIdx); - while( p ){ - if( (p->prereqRight & notReady)==0 ){ - if( p->prereqRight==0 && (p->eOperator&WO_EQ)!=0 ){ - return p; - } - if( pResult==0 ) pResult = p; - } - p = whereScanNext(&scan); - } - return pResult; -} - -/* Forward reference */ -static void exprAnalyze(SrcList*, WhereClause*, int); - -/* -** Call exprAnalyze on all terms in a WHERE clause. -*/ -static void exprAnalyzeAll( - SrcList *pTabList, /* the FROM clause */ - WhereClause *pWC /* the WHERE clause to be analyzed */ -){ - int i; - for(i=pWC->nTerm-1; i>=0; i--){ - exprAnalyze(pTabList, pWC, i); - } -} - -#ifndef SQLITE_OMIT_LIKE_OPTIMIZATION -/* -** Check to see if the given expression is a LIKE or GLOB operator that -** can be optimized using inequality constraints. Return TRUE if it is -** so and false if not. -** -** In order for the operator to be optimizible, the RHS must be a string -** literal that does not begin with a wildcard. -*/ -static int isLikeOrGlob( - Parse *pParse, /* Parsing and code generating context */ - Expr *pExpr, /* Test this expression */ - Expr **ppPrefix, /* Pointer to TK_STRING expression with pattern prefix */ - int *pisComplete, /* True if the only wildcard is % in the last character */ - int *pnoCase /* True if uppercase is equivalent to lowercase */ -){ - const char *z = 0; /* String on RHS of LIKE operator */ - Expr *pRight, *pLeft; /* Right and left size of LIKE operator */ - ExprList *pList; /* List of operands to the LIKE operator */ - int c; /* One character in z[] */ - int cnt; /* Number of non-wildcard prefix characters */ - char wc[3]; /* Wildcard characters */ - sqlite3 *db = pParse->db; /* Database connection */ - sqlite3_value *pVal = 0; - int op; /* Opcode of pRight */ - - if( !sqlite3IsLikeFunction(db, pExpr, pnoCase, wc) ){ - return 0; - } -#ifdef SQLITE_EBCDIC - if( *pnoCase ) return 0; -#endif - pList = pExpr->x.pList; - pLeft = pList->a[1].pExpr; - if( pLeft->op!=TK_COLUMN - || sqlite3ExprAffinity(pLeft)!=SQLITE_AFF_TEXT - || IsVirtual(pLeft->pTab) - ){ - /* IMP: R-02065-49465 The left-hand side of the LIKE or GLOB operator must - ** be the name of an indexed column with TEXT affinity. */ - return 0; - } - assert( pLeft->iColumn!=(-1) ); /* Because IPK never has AFF_TEXT */ - - pRight = sqlite3ExprSkipCollate(pList->a[0].pExpr); - op = pRight->op; - if( op==TK_VARIABLE ){ - Vdbe *pReprepare = pParse->pReprepare; - int iCol = pRight->iColumn; - pVal = sqlite3VdbeGetBoundValue(pReprepare, iCol, SQLITE_AFF_NONE); - if( pVal && sqlite3_value_type(pVal)==SQLITE_TEXT ){ - z = (char *)sqlite3_value_text(pVal); - } - sqlite3VdbeSetVarmask(pParse->pVdbe, iCol); - assert( pRight->op==TK_VARIABLE || pRight->op==TK_REGISTER ); - }else if( op==TK_STRING ){ - z = pRight->u.zToken; - } - if( z ){ - cnt = 0; - while( (c=z[cnt])!=0 && c!=wc[0] && c!=wc[1] && c!=wc[2] ){ - cnt++; - } - if( cnt!=0 && 255!=(u8)z[cnt-1] ){ - Expr *pPrefix; - *pisComplete = c==wc[0] && z[cnt+1]==0; - pPrefix = sqlite3Expr(db, TK_STRING, z); - if( pPrefix ) pPrefix->u.zToken[cnt] = 0; - *ppPrefix = pPrefix; - if( op==TK_VARIABLE ){ - Vdbe *v = pParse->pVdbe; - sqlite3VdbeSetVarmask(v, pRight->iColumn); - if( *pisComplete && pRight->u.zToken[1] ){ - /* If the rhs of the LIKE expression is a variable, and the current - ** value of the variable means there is no need to invoke the LIKE - ** function, then no OP_Variable will be added to the program. - ** This causes problems for the sqlite3_bind_parameter_name() - ** API. To workaround them, add a dummy OP_Variable here. - */ - int r1 = sqlite3GetTempReg(pParse); - sqlite3ExprCodeTarget(pParse, pRight, r1); - sqlite3VdbeChangeP3(v, sqlite3VdbeCurrentAddr(v)-1, 0); - sqlite3ReleaseTempReg(pParse, r1); - } - } - }else{ - z = 0; - } - } - - sqlite3ValueFree(pVal); - return (z!=0); -} -#endif /* SQLITE_OMIT_LIKE_OPTIMIZATION */ - - -#ifndef SQLITE_OMIT_VIRTUALTABLE -/* -** Check to see if the given expression is of the form -** -** column MATCH expr -** -** If it is then return TRUE. If not, return FALSE. -*/ -static int isMatchOfColumn( - Expr *pExpr /* Test this expression */ -){ - ExprList *pList; - - if( pExpr->op!=TK_FUNCTION ){ - return 0; - } - if( sqlite3StrICmp(pExpr->u.zToken,"match")!=0 ){ - return 0; - } - pList = pExpr->x.pList; - if( pList->nExpr!=2 ){ - return 0; - } - if( pList->a[1].pExpr->op != TK_COLUMN ){ - return 0; - } - return 1; -} -#endif /* SQLITE_OMIT_VIRTUALTABLE */ - -/* -** If the pBase expression originated in the ON or USING clause of -** a join, then transfer the appropriate markings over to derived. -*/ -static void transferJoinMarkings(Expr *pDerived, Expr *pBase){ - if( pDerived ){ - pDerived->flags |= pBase->flags & EP_FromJoin; - pDerived->iRightJoinTable = pBase->iRightJoinTable; - } -} - -#if !defined(SQLITE_OMIT_OR_OPTIMIZATION) && !defined(SQLITE_OMIT_SUBQUERY) -/* -** Analyze a term that consists of two or more OR-connected -** subterms. So in: -** -** ... WHERE (a=5) AND (b=7 OR c=9 OR d=13) AND (d=13) -** ^^^^^^^^^^^^^^^^^^^^ -** -** This routine analyzes terms such as the middle term in the above example. -** A WhereOrTerm object is computed and attached to the term under -** analysis, regardless of the outcome of the analysis. Hence: -** -** WhereTerm.wtFlags |= TERM_ORINFO -** WhereTerm.u.pOrInfo = a dynamically allocated WhereOrTerm object -** -** The term being analyzed must have two or more of OR-connected subterms. -** A single subterm might be a set of AND-connected sub-subterms. -** Examples of terms under analysis: -** -** (A) t1.x=t2.y OR t1.x=t2.z OR t1.y=15 OR t1.z=t3.a+5 -** (B) x=expr1 OR expr2=x OR x=expr3 -** (C) t1.x=t2.y OR (t1.x=t2.z AND t1.y=15) -** (D) x=expr1 OR (y>11 AND y<22 AND z LIKE '*hello*') -** (E) (p.a=1 AND q.b=2 AND r.c=3) OR (p.x=4 AND q.y=5 AND r.z=6) -** -** CASE 1: -** -** If all subterms are of the form T.C=expr for some single column of C and -** a single table T (as shown in example B above) then create a new virtual -** term that is an equivalent IN expression. In other words, if the term -** being analyzed is: -** -** x = expr1 OR expr2 = x OR x = expr3 -** -** then create a new virtual term like this: -** -** x IN (expr1,expr2,expr3) -** -** CASE 2: -** -** If all subterms are indexable by a single table T, then set -** -** WhereTerm.eOperator = WO_OR -** WhereTerm.u.pOrInfo->indexable |= the cursor number for table T -** -** A subterm is "indexable" if it is of the form -** "T.C " where C is any column of table T and -** is one of "=", "<", "<=", ">", ">=", "IS NULL", or "IN". -** A subterm is also indexable if it is an AND of two or more -** subsubterms at least one of which is indexable. Indexable AND -** subterms have their eOperator set to WO_AND and they have -** u.pAndInfo set to a dynamically allocated WhereAndTerm object. -** -** From another point of view, "indexable" means that the subterm could -** potentially be used with an index if an appropriate index exists. -** This analysis does not consider whether or not the index exists; that -** is decided elsewhere. This analysis only looks at whether subterms -** appropriate for indexing exist. -** -** All examples A through E above satisfy case 2. But if a term -** also statisfies case 1 (such as B) we know that the optimizer will -** always prefer case 1, so in that case we pretend that case 2 is not -** satisfied. -** -** It might be the case that multiple tables are indexable. For example, -** (E) above is indexable on tables P, Q, and R. -** -** Terms that satisfy case 2 are candidates for lookup by using -** separate indices to find rowids for each subterm and composing -** the union of all rowids using a RowSet object. This is similar -** to "bitmap indices" in other database engines. -** -** OTHERWISE: -** -** If neither case 1 nor case 2 apply, then leave the eOperator set to -** zero. This term is not useful for search. -*/ -static void exprAnalyzeOrTerm( - SrcList *pSrc, /* the FROM clause */ - WhereClause *pWC, /* the complete WHERE clause */ - int idxTerm /* Index of the OR-term to be analyzed */ -){ - WhereInfo *pWInfo = pWC->pWInfo; /* WHERE clause processing context */ - Parse *pParse = pWInfo->pParse; /* Parser context */ - sqlite3 *db = pParse->db; /* Database connection */ - WhereTerm *pTerm = &pWC->a[idxTerm]; /* The term to be analyzed */ - Expr *pExpr = pTerm->pExpr; /* The expression of the term */ - int i; /* Loop counters */ - WhereClause *pOrWc; /* Breakup of pTerm into subterms */ - WhereTerm *pOrTerm; /* A Sub-term within the pOrWc */ - WhereOrInfo *pOrInfo; /* Additional information associated with pTerm */ - Bitmask chngToIN; /* Tables that might satisfy case 1 */ - Bitmask indexable; /* Tables that are indexable, satisfying case 2 */ - - /* - ** Break the OR clause into its separate subterms. The subterms are - ** stored in a WhereClause structure containing within the WhereOrInfo - ** object that is attached to the original OR clause term. - */ - assert( (pTerm->wtFlags & (TERM_DYNAMIC|TERM_ORINFO|TERM_ANDINFO))==0 ); - assert( pExpr->op==TK_OR ); - pTerm->u.pOrInfo = pOrInfo = sqlite3DbMallocZero(db, sizeof(*pOrInfo)); - if( pOrInfo==0 ) return; - pTerm->wtFlags |= TERM_ORINFO; - pOrWc = &pOrInfo->wc; - whereClauseInit(pOrWc, pWInfo); - whereSplit(pOrWc, pExpr, TK_OR); - exprAnalyzeAll(pSrc, pOrWc); - if( db->mallocFailed ) return; - assert( pOrWc->nTerm>=2 ); - - /* - ** Compute the set of tables that might satisfy cases 1 or 2. - */ - indexable = ~(Bitmask)0; - chngToIN = ~(Bitmask)0; - for(i=pOrWc->nTerm-1, pOrTerm=pOrWc->a; i>=0 && indexable; i--, pOrTerm++){ - if( (pOrTerm->eOperator & WO_SINGLE)==0 ){ - WhereAndInfo *pAndInfo; - assert( (pOrTerm->wtFlags & (TERM_ANDINFO|TERM_ORINFO))==0 ); - chngToIN = 0; - pAndInfo = sqlite3DbMallocRaw(db, sizeof(*pAndInfo)); - if( pAndInfo ){ - WhereClause *pAndWC; - WhereTerm *pAndTerm; - int j; - Bitmask b = 0; - pOrTerm->u.pAndInfo = pAndInfo; - pOrTerm->wtFlags |= TERM_ANDINFO; - pOrTerm->eOperator = WO_AND; - pAndWC = &pAndInfo->wc; - whereClauseInit(pAndWC, pWC->pWInfo); - whereSplit(pAndWC, pOrTerm->pExpr, TK_AND); - exprAnalyzeAll(pSrc, pAndWC); - pAndWC->pOuter = pWC; - testcase( db->mallocFailed ); - if( !db->mallocFailed ){ - for(j=0, pAndTerm=pAndWC->a; jnTerm; j++, pAndTerm++){ - assert( pAndTerm->pExpr ); - if( allowedOp(pAndTerm->pExpr->op) ){ - b |= getMask(&pWInfo->sMaskSet, pAndTerm->leftCursor); - } - } - } - indexable &= b; - } - }else if( pOrTerm->wtFlags & TERM_COPIED ){ - /* Skip this term for now. We revisit it when we process the - ** corresponding TERM_VIRTUAL term */ - }else{ - Bitmask b; - b = getMask(&pWInfo->sMaskSet, pOrTerm->leftCursor); - if( pOrTerm->wtFlags & TERM_VIRTUAL ){ - WhereTerm *pOther = &pOrWc->a[pOrTerm->iParent]; - b |= getMask(&pWInfo->sMaskSet, pOther->leftCursor); - } - indexable &= b; - if( (pOrTerm->eOperator & WO_EQ)==0 ){ - chngToIN = 0; - }else{ - chngToIN &= b; - } - } - } - - /* - ** Record the set of tables that satisfy case 2. The set might be - ** empty. - */ - pOrInfo->indexable = indexable; - pTerm->eOperator = indexable==0 ? 0 : WO_OR; - - /* - ** chngToIN holds a set of tables that *might* satisfy case 1. But - ** we have to do some additional checking to see if case 1 really - ** is satisfied. - ** - ** chngToIN will hold either 0, 1, or 2 bits. The 0-bit case means - ** that there is no possibility of transforming the OR clause into an - ** IN operator because one or more terms in the OR clause contain - ** something other than == on a column in the single table. The 1-bit - ** case means that every term of the OR clause is of the form - ** "table.column=expr" for some single table. The one bit that is set - ** will correspond to the common table. We still need to check to make - ** sure the same column is used on all terms. The 2-bit case is when - ** the all terms are of the form "table1.column=table2.column". It - ** might be possible to form an IN operator with either table1.column - ** or table2.column as the LHS if either is common to every term of - ** the OR clause. - ** - ** Note that terms of the form "table.column1=table.column2" (the - ** same table on both sizes of the ==) cannot be optimized. - */ - if( chngToIN ){ - int okToChngToIN = 0; /* True if the conversion to IN is valid */ - int iColumn = -1; /* Column index on lhs of IN operator */ - int iCursor = -1; /* Table cursor common to all terms */ - int j = 0; /* Loop counter */ - - /* Search for a table and column that appears on one side or the - ** other of the == operator in every subterm. That table and column - ** will be recorded in iCursor and iColumn. There might not be any - ** such table and column. Set okToChngToIN if an appropriate table - ** and column is found but leave okToChngToIN false if not found. - */ - for(j=0; j<2 && !okToChngToIN; j++){ - pOrTerm = pOrWc->a; - for(i=pOrWc->nTerm-1; i>=0; i--, pOrTerm++){ - assert( pOrTerm->eOperator & WO_EQ ); - pOrTerm->wtFlags &= ~TERM_OR_OK; - if( pOrTerm->leftCursor==iCursor ){ - /* This is the 2-bit case and we are on the second iteration and - ** current term is from the first iteration. So skip this term. */ - assert( j==1 ); - continue; - } - if( (chngToIN & getMask(&pWInfo->sMaskSet, pOrTerm->leftCursor))==0 ){ - /* This term must be of the form t1.a==t2.b where t2 is in the - ** chngToIN set but t1 is not. This term will be either preceeded - ** or follwed by an inverted copy (t2.b==t1.a). Skip this term - ** and use its inversion. */ - testcase( pOrTerm->wtFlags & TERM_COPIED ); - testcase( pOrTerm->wtFlags & TERM_VIRTUAL ); - assert( pOrTerm->wtFlags & (TERM_COPIED|TERM_VIRTUAL) ); - continue; - } - iColumn = pOrTerm->u.leftColumn; - iCursor = pOrTerm->leftCursor; - break; - } - if( i<0 ){ - /* No candidate table+column was found. This can only occur - ** on the second iteration */ - assert( j==1 ); - assert( IsPowerOfTwo(chngToIN) ); - assert( chngToIN==getMask(&pWInfo->sMaskSet, iCursor) ); - break; - } - testcase( j==1 ); - - /* We have found a candidate table and column. Check to see if that - ** table and column is common to every term in the OR clause */ - okToChngToIN = 1; - for(; i>=0 && okToChngToIN; i--, pOrTerm++){ - assert( pOrTerm->eOperator & WO_EQ ); - if( pOrTerm->leftCursor!=iCursor ){ - pOrTerm->wtFlags &= ~TERM_OR_OK; - }else if( pOrTerm->u.leftColumn!=iColumn ){ - okToChngToIN = 0; - }else{ - int affLeft, affRight; - /* If the right-hand side is also a column, then the affinities - ** of both right and left sides must be such that no type - ** conversions are required on the right. (Ticket #2249) - */ - affRight = sqlite3ExprAffinity(pOrTerm->pExpr->pRight); - affLeft = sqlite3ExprAffinity(pOrTerm->pExpr->pLeft); - if( affRight!=0 && affRight!=affLeft ){ - okToChngToIN = 0; - }else{ - pOrTerm->wtFlags |= TERM_OR_OK; - } - } - } - } - - /* At this point, okToChngToIN is true if original pTerm satisfies - ** case 1. In that case, construct a new virtual term that is - ** pTerm converted into an IN operator. - */ - if( okToChngToIN ){ - Expr *pDup; /* A transient duplicate expression */ - ExprList *pList = 0; /* The RHS of the IN operator */ - Expr *pLeft = 0; /* The LHS of the IN operator */ - Expr *pNew; /* The complete IN operator */ - - for(i=pOrWc->nTerm-1, pOrTerm=pOrWc->a; i>=0; i--, pOrTerm++){ - if( (pOrTerm->wtFlags & TERM_OR_OK)==0 ) continue; - assert( pOrTerm->eOperator & WO_EQ ); - assert( pOrTerm->leftCursor==iCursor ); - assert( pOrTerm->u.leftColumn==iColumn ); - pDup = sqlite3ExprDup(db, pOrTerm->pExpr->pRight, 0); - pList = sqlite3ExprListAppend(pWInfo->pParse, pList, pDup); - pLeft = pOrTerm->pExpr->pLeft; - } - assert( pLeft!=0 ); - pDup = sqlite3ExprDup(db, pLeft, 0); - pNew = sqlite3PExpr(pParse, TK_IN, pDup, 0, 0); - if( pNew ){ - int idxNew; - transferJoinMarkings(pNew, pExpr); - assert( !ExprHasProperty(pNew, EP_xIsSelect) ); - pNew->x.pList = pList; - idxNew = whereClauseInsert(pWC, pNew, TERM_VIRTUAL|TERM_DYNAMIC); - testcase( idxNew==0 ); - exprAnalyze(pSrc, pWC, idxNew); - pTerm = &pWC->a[idxTerm]; - pWC->a[idxNew].iParent = idxTerm; - pTerm->nChild = 1; - }else{ - sqlite3ExprListDelete(db, pList); - } - pTerm->eOperator = WO_NOOP; /* case 1 trumps case 2 */ - } - } -} -#endif /* !SQLITE_OMIT_OR_OPTIMIZATION && !SQLITE_OMIT_SUBQUERY */ - -/* -** The input to this routine is an WhereTerm structure with only the -** "pExpr" field filled in. The job of this routine is to analyze the -** subexpression and populate all the other fields of the WhereTerm -** structure. -** -** If the expression is of the form " X" it gets commuted -** to the standard form of "X ". -** -** If the expression is of the form "X Y" where both X and Y are -** columns, then the original expression is unchanged and a new virtual -** term of the form "Y X" is added to the WHERE clause and -** analyzed separately. The original term is marked with TERM_COPIED -** and the new term is marked with TERM_DYNAMIC (because it's pExpr -** needs to be freed with the WhereClause) and TERM_VIRTUAL (because it -** is a commuted copy of a prior term.) The original term has nChild=1 -** and the copy has idxParent set to the index of the original term. -*/ -static void exprAnalyze( - SrcList *pSrc, /* the FROM clause */ - WhereClause *pWC, /* the WHERE clause */ - int idxTerm /* Index of the term to be analyzed */ -){ - WhereInfo *pWInfo = pWC->pWInfo; /* WHERE clause processing context */ - WhereTerm *pTerm; /* The term to be analyzed */ - WhereMaskSet *pMaskSet; /* Set of table index masks */ - Expr *pExpr; /* The expression to be analyzed */ - Bitmask prereqLeft; /* Prerequesites of the pExpr->pLeft */ - Bitmask prereqAll; /* Prerequesites of pExpr */ - Bitmask extraRight = 0; /* Extra dependencies on LEFT JOIN */ - Expr *pStr1 = 0; /* RHS of LIKE/GLOB operator */ - int isComplete = 0; /* RHS of LIKE/GLOB ends with wildcard */ - int noCase = 0; /* LIKE/GLOB distinguishes case */ - int op; /* Top-level operator. pExpr->op */ - Parse *pParse = pWInfo->pParse; /* Parsing context */ - sqlite3 *db = pParse->db; /* Database connection */ - - if( db->mallocFailed ){ - return; - } - pTerm = &pWC->a[idxTerm]; - pMaskSet = &pWInfo->sMaskSet; - pExpr = pTerm->pExpr; - assert( pExpr->op!=TK_AS && pExpr->op!=TK_COLLATE ); - prereqLeft = exprTableUsage(pMaskSet, pExpr->pLeft); - op = pExpr->op; - if( op==TK_IN ){ - assert( pExpr->pRight==0 ); - if( ExprHasProperty(pExpr, EP_xIsSelect) ){ - pTerm->prereqRight = exprSelectTableUsage(pMaskSet, pExpr->x.pSelect); - }else{ - pTerm->prereqRight = exprListTableUsage(pMaskSet, pExpr->x.pList); - } - }else if( op==TK_ISNULL ){ - pTerm->prereqRight = 0; - }else{ - pTerm->prereqRight = exprTableUsage(pMaskSet, pExpr->pRight); - } - prereqAll = exprTableUsage(pMaskSet, pExpr); - if( ExprHasProperty(pExpr, EP_FromJoin) ){ - Bitmask x = getMask(pMaskSet, pExpr->iRightJoinTable); - prereqAll |= x; - extraRight = x-1; /* ON clause terms may not be used with an index - ** on left table of a LEFT JOIN. Ticket #3015 */ - } - pTerm->prereqAll = prereqAll; - pTerm->leftCursor = -1; - pTerm->iParent = -1; - pTerm->eOperator = 0; - if( allowedOp(op) ){ - Expr *pLeft = sqlite3ExprSkipCollate(pExpr->pLeft); - Expr *pRight = sqlite3ExprSkipCollate(pExpr->pRight); - u16 opMask = (pTerm->prereqRight & prereqLeft)==0 ? WO_ALL : WO_EQUIV; - if( pLeft->op==TK_COLUMN ){ - pTerm->leftCursor = pLeft->iTable; - pTerm->u.leftColumn = pLeft->iColumn; - pTerm->eOperator = operatorMask(op) & opMask; - } - if( pRight && pRight->op==TK_COLUMN ){ - WhereTerm *pNew; - Expr *pDup; - u16 eExtraOp = 0; /* Extra bits for pNew->eOperator */ - if( pTerm->leftCursor>=0 ){ - int idxNew; - pDup = sqlite3ExprDup(db, pExpr, 0); - if( db->mallocFailed ){ - sqlite3ExprDelete(db, pDup); - return; - } - idxNew = whereClauseInsert(pWC, pDup, TERM_VIRTUAL|TERM_DYNAMIC); - if( idxNew==0 ) return; - pNew = &pWC->a[idxNew]; - pNew->iParent = idxTerm; - pTerm = &pWC->a[idxTerm]; - pTerm->nChild = 1; - pTerm->wtFlags |= TERM_COPIED; - if( pExpr->op==TK_EQ - && !ExprHasProperty(pExpr, EP_FromJoin) - && OptimizationEnabled(db, SQLITE_Transitive) - ){ - pTerm->eOperator |= WO_EQUIV; - eExtraOp = WO_EQUIV; - } - }else{ - pDup = pExpr; - pNew = pTerm; - } - exprCommute(pParse, pDup); - pLeft = sqlite3ExprSkipCollate(pDup->pLeft); - pNew->leftCursor = pLeft->iTable; - pNew->u.leftColumn = pLeft->iColumn; - testcase( (prereqLeft | extraRight) != prereqLeft ); - pNew->prereqRight = prereqLeft | extraRight; - pNew->prereqAll = prereqAll; - pNew->eOperator = (operatorMask(pDup->op) + eExtraOp) & opMask; - } - } - -#ifndef SQLITE_OMIT_BETWEEN_OPTIMIZATION - /* If a term is the BETWEEN operator, create two new virtual terms - ** that define the range that the BETWEEN implements. For example: - ** - ** a BETWEEN b AND c - ** - ** is converted into: - ** - ** (a BETWEEN b AND c) AND (a>=b) AND (a<=c) - ** - ** The two new terms are added onto the end of the WhereClause object. - ** The new terms are "dynamic" and are children of the original BETWEEN - ** term. That means that if the BETWEEN term is coded, the children are - ** skipped. Or, if the children are satisfied by an index, the original - ** BETWEEN term is skipped. - */ - else if( pExpr->op==TK_BETWEEN && pWC->op==TK_AND ){ - ExprList *pList = pExpr->x.pList; - int i; - static const u8 ops[] = {TK_GE, TK_LE}; - assert( pList!=0 ); - assert( pList->nExpr==2 ); - for(i=0; i<2; i++){ - Expr *pNewExpr; - int idxNew; - pNewExpr = sqlite3PExpr(pParse, ops[i], - sqlite3ExprDup(db, pExpr->pLeft, 0), - sqlite3ExprDup(db, pList->a[i].pExpr, 0), 0); - transferJoinMarkings(pNewExpr, pExpr); - idxNew = whereClauseInsert(pWC, pNewExpr, TERM_VIRTUAL|TERM_DYNAMIC); - testcase( idxNew==0 ); - exprAnalyze(pSrc, pWC, idxNew); - pTerm = &pWC->a[idxTerm]; - pWC->a[idxNew].iParent = idxTerm; - } - pTerm->nChild = 2; - } -#endif /* SQLITE_OMIT_BETWEEN_OPTIMIZATION */ - -#if !defined(SQLITE_OMIT_OR_OPTIMIZATION) && !defined(SQLITE_OMIT_SUBQUERY) - /* Analyze a term that is composed of two or more subterms connected by - ** an OR operator. - */ - else if( pExpr->op==TK_OR ){ - assert( pWC->op==TK_AND ); - exprAnalyzeOrTerm(pSrc, pWC, idxTerm); - pTerm = &pWC->a[idxTerm]; - } -#endif /* SQLITE_OMIT_OR_OPTIMIZATION */ - -#ifndef SQLITE_OMIT_LIKE_OPTIMIZATION - /* Add constraints to reduce the search space on a LIKE or GLOB - ** operator. - ** - ** A like pattern of the form "x LIKE 'abc%'" is changed into constraints - ** - ** x>='abc' AND x<'abd' AND x LIKE 'abc%' - ** - ** The last character of the prefix "abc" is incremented to form the - ** termination condition "abd". - */ - if( pWC->op==TK_AND - && isLikeOrGlob(pParse, pExpr, &pStr1, &isComplete, &noCase) - ){ - Expr *pLeft; /* LHS of LIKE/GLOB operator */ - Expr *pStr2; /* Copy of pStr1 - RHS of LIKE/GLOB operator */ - Expr *pNewExpr1; - Expr *pNewExpr2; - int idxNew1; - int idxNew2; - Token sCollSeqName; /* Name of collating sequence */ - - pLeft = pExpr->x.pList->a[1].pExpr; - pStr2 = sqlite3ExprDup(db, pStr1, 0); - if( !db->mallocFailed ){ - u8 c, *pC; /* Last character before the first wildcard */ - pC = (u8*)&pStr2->u.zToken[sqlite3Strlen30(pStr2->u.zToken)-1]; - c = *pC; - if( noCase ){ - /* The point is to increment the last character before the first - ** wildcard. But if we increment '@', that will push it into the - ** alphabetic range where case conversions will mess up the - ** inequality. To avoid this, make sure to also run the full - ** LIKE on all candidate expressions by clearing the isComplete flag - */ - if( c=='A'-1 ) isComplete = 0; - c = sqlite3UpperToLower[c]; - } - *pC = c + 1; - } - sCollSeqName.z = noCase ? "NOCASE" : "BINARY"; - sCollSeqName.n = 6; - pNewExpr1 = sqlite3ExprDup(db, pLeft, 0); - pNewExpr1 = sqlite3PExpr(pParse, TK_GE, - sqlite3ExprAddCollateToken(pParse,pNewExpr1,&sCollSeqName), - pStr1, 0); - transferJoinMarkings(pNewExpr1, pExpr); - idxNew1 = whereClauseInsert(pWC, pNewExpr1, TERM_VIRTUAL|TERM_DYNAMIC); - testcase( idxNew1==0 ); - exprAnalyze(pSrc, pWC, idxNew1); - pNewExpr2 = sqlite3ExprDup(db, pLeft, 0); - pNewExpr2 = sqlite3PExpr(pParse, TK_LT, - sqlite3ExprAddCollateToken(pParse,pNewExpr2,&sCollSeqName), - pStr2, 0); - transferJoinMarkings(pNewExpr2, pExpr); - idxNew2 = whereClauseInsert(pWC, pNewExpr2, TERM_VIRTUAL|TERM_DYNAMIC); - testcase( idxNew2==0 ); - exprAnalyze(pSrc, pWC, idxNew2); - pTerm = &pWC->a[idxTerm]; - if( isComplete ){ - pWC->a[idxNew1].iParent = idxTerm; - pWC->a[idxNew2].iParent = idxTerm; - pTerm->nChild = 2; - } - } -#endif /* SQLITE_OMIT_LIKE_OPTIMIZATION */ - -#ifndef SQLITE_OMIT_VIRTUALTABLE - /* Add a WO_MATCH auxiliary term to the constraint set if the - ** current expression is of the form: column MATCH expr. - ** This information is used by the xBestIndex methods of - ** virtual tables. The native query optimizer does not attempt - ** to do anything with MATCH functions. - */ - if( isMatchOfColumn(pExpr) ){ - int idxNew; - Expr *pRight, *pLeft; - WhereTerm *pNewTerm; - Bitmask prereqColumn, prereqExpr; - - pRight = pExpr->x.pList->a[0].pExpr; - pLeft = pExpr->x.pList->a[1].pExpr; - prereqExpr = exprTableUsage(pMaskSet, pRight); - prereqColumn = exprTableUsage(pMaskSet, pLeft); - if( (prereqExpr & prereqColumn)==0 ){ - Expr *pNewExpr; - pNewExpr = sqlite3PExpr(pParse, TK_MATCH, - 0, sqlite3ExprDup(db, pRight, 0), 0); - idxNew = whereClauseInsert(pWC, pNewExpr, TERM_VIRTUAL|TERM_DYNAMIC); - testcase( idxNew==0 ); - pNewTerm = &pWC->a[idxNew]; - pNewTerm->prereqRight = prereqExpr; - pNewTerm->leftCursor = pLeft->iTable; - pNewTerm->u.leftColumn = pLeft->iColumn; - pNewTerm->eOperator = WO_MATCH; - pNewTerm->iParent = idxTerm; - pTerm = &pWC->a[idxTerm]; - pTerm->nChild = 1; - pTerm->wtFlags |= TERM_COPIED; - pNewTerm->prereqAll = pTerm->prereqAll; - } - } -#endif /* SQLITE_OMIT_VIRTUALTABLE */ - -#ifdef SQLITE_ENABLE_STAT3_OR_STAT4 - /* When sqlite_stat3 histogram data is available an operator of the - ** form "x IS NOT NULL" can sometimes be evaluated more efficiently - ** as "x>NULL" if x is not an INTEGER PRIMARY KEY. So construct a - ** virtual term of that form. - ** - ** Note that the virtual term must be tagged with TERM_VNULL. This - ** TERM_VNULL tag will suppress the not-null check at the beginning - ** of the loop. Without the TERM_VNULL flag, the not-null check at - ** the start of the loop will prevent any results from being returned. - */ - if( pExpr->op==TK_NOTNULL - && pExpr->pLeft->op==TK_COLUMN - && pExpr->pLeft->iColumn>=0 - && OptimizationEnabled(db, SQLITE_Stat3) - ){ - Expr *pNewExpr; - Expr *pLeft = pExpr->pLeft; - int idxNew; - WhereTerm *pNewTerm; - - pNewExpr = sqlite3PExpr(pParse, TK_GT, - sqlite3ExprDup(db, pLeft, 0), - sqlite3PExpr(pParse, TK_NULL, 0, 0, 0), 0); - - idxNew = whereClauseInsert(pWC, pNewExpr, - TERM_VIRTUAL|TERM_DYNAMIC|TERM_VNULL); - if( idxNew ){ - pNewTerm = &pWC->a[idxNew]; - pNewTerm->prereqRight = 0; - pNewTerm->leftCursor = pLeft->iTable; - pNewTerm->u.leftColumn = pLeft->iColumn; - pNewTerm->eOperator = WO_GT; - pNewTerm->iParent = idxTerm; - pTerm = &pWC->a[idxTerm]; - pTerm->nChild = 1; - pTerm->wtFlags |= TERM_COPIED; - pNewTerm->prereqAll = pTerm->prereqAll; - } - } -#endif /* SQLITE_ENABLE_STAT3_OR_STAT4 */ - - /* Prevent ON clause terms of a LEFT JOIN from being used to drive - ** an index for tables to the left of the join. - */ - pTerm->prereqRight |= extraRight; -} - -/* -** This function searches pList for a entry that matches the iCol-th column -** of index pIdx. -** -** If such an expression is found, its index in pList->a[] is returned. If -** no expression is found, -1 is returned. -*/ -static int findIndexCol( - Parse *pParse, /* Parse context */ - ExprList *pList, /* Expression list to search */ - int iBase, /* Cursor for table associated with pIdx */ - Index *pIdx, /* Index to match column of */ - int iCol /* Column of index to match */ -){ - int i; - const char *zColl = pIdx->azColl[iCol]; - - for(i=0; inExpr; i++){ - Expr *p = sqlite3ExprSkipCollate(pList->a[i].pExpr); - if( p->op==TK_COLUMN - && p->iColumn==pIdx->aiColumn[iCol] - && p->iTable==iBase - ){ - CollSeq *pColl = sqlite3ExprCollSeq(pParse, pList->a[i].pExpr); - if( ALWAYS(pColl) && 0==sqlite3StrICmp(pColl->zName, zColl) ){ - return i; - } - } - } - - return -1; -} - -/* -** Return true if the DISTINCT expression-list passed as the third argument -** is redundant. -** -** A DISTINCT list is redundant if the database contains some subset of -** columns that are unique and non-null. -*/ -static int isDistinctRedundant( - Parse *pParse, /* Parsing context */ - SrcList *pTabList, /* The FROM clause */ - WhereClause *pWC, /* The WHERE clause */ - ExprList *pDistinct /* The result set that needs to be DISTINCT */ -){ - Table *pTab; - Index *pIdx; - int i; - int iBase; - - /* If there is more than one table or sub-select in the FROM clause of - ** this query, then it will not be possible to show that the DISTINCT - ** clause is redundant. */ - if( pTabList->nSrc!=1 ) return 0; - iBase = pTabList->a[0].iCursor; - pTab = pTabList->a[0].pTab; - - /* If any of the expressions is an IPK column on table iBase, then return - ** true. Note: The (p->iTable==iBase) part of this test may be false if the - ** current SELECT is a correlated sub-query. - */ - for(i=0; inExpr; i++){ - Expr *p = sqlite3ExprSkipCollate(pDistinct->a[i].pExpr); - if( p->op==TK_COLUMN && p->iTable==iBase && p->iColumn<0 ) return 1; - } - - /* Loop through all indices on the table, checking each to see if it makes - ** the DISTINCT qualifier redundant. It does so if: - ** - ** 1. The index is itself UNIQUE, and - ** - ** 2. All of the columns in the index are either part of the pDistinct - ** list, or else the WHERE clause contains a term of the form "col=X", - ** where X is a constant value. The collation sequences of the - ** comparison and select-list expressions must match those of the index. - ** - ** 3. All of those index columns for which the WHERE clause does not - ** contain a "col=X" term are subject to a NOT NULL constraint. - */ - for(pIdx=pTab->pIndex; pIdx; pIdx=pIdx->pNext){ - if( pIdx->onError==OE_None ) continue; - for(i=0; inKeyCol; i++){ - i16 iCol = pIdx->aiColumn[i]; - if( 0==findTerm(pWC, iBase, iCol, ~(Bitmask)0, WO_EQ, pIdx) ){ - int iIdxCol = findIndexCol(pParse, pDistinct, iBase, pIdx, i); - if( iIdxCol<0 || pTab->aCol[iCol].notNull==0 ){ - break; - } - } - } - if( i==pIdx->nKeyCol ){ - /* This index implies that the DISTINCT qualifier is redundant. */ - return 1; - } - } - - return 0; -} - - -/* -** Estimate the logarithm of the input value to base 2. -*/ -static LogEst estLog(LogEst N){ - LogEst x = sqlite3LogEst(N); - return x>33 ? x - 33 : 0; -} - -/* -** Two routines for printing the content of an sqlite3_index_info -** structure. Used for testing and debugging only. If neither -** SQLITE_TEST or SQLITE_DEBUG are defined, then these routines -** are no-ops. -*/ -#if !defined(SQLITE_OMIT_VIRTUALTABLE) && defined(WHERETRACE_ENABLED) -static void TRACE_IDX_INPUTS(sqlite3_index_info *p){ - int i; - if( !sqlite3WhereTrace ) return; - for(i=0; inConstraint; i++){ - sqlite3DebugPrintf(" constraint[%d]: col=%d termid=%d op=%d usabled=%d\n", - i, - p->aConstraint[i].iColumn, - p->aConstraint[i].iTermOffset, - p->aConstraint[i].op, - p->aConstraint[i].usable); - } - for(i=0; inOrderBy; i++){ - sqlite3DebugPrintf(" orderby[%d]: col=%d desc=%d\n", - i, - p->aOrderBy[i].iColumn, - p->aOrderBy[i].desc); - } -} -static void TRACE_IDX_OUTPUTS(sqlite3_index_info *p){ - int i; - if( !sqlite3WhereTrace ) return; - for(i=0; inConstraint; i++){ - sqlite3DebugPrintf(" usage[%d]: argvIdx=%d omit=%d\n", - i, - p->aConstraintUsage[i].argvIndex, - p->aConstraintUsage[i].omit); - } - sqlite3DebugPrintf(" idxNum=%d\n", p->idxNum); - sqlite3DebugPrintf(" idxStr=%s\n", p->idxStr); - sqlite3DebugPrintf(" orderByConsumed=%d\n", p->orderByConsumed); - sqlite3DebugPrintf(" estimatedCost=%g\n", p->estimatedCost); - sqlite3DebugPrintf(" estimatedRows=%lld\n", p->estimatedRows); -} -#else -#define TRACE_IDX_INPUTS(A) -#define TRACE_IDX_OUTPUTS(A) -#endif - -#ifndef SQLITE_OMIT_AUTOMATIC_INDEX -/* -** Return TRUE if the WHERE clause term pTerm is of a form where it -** could be used with an index to access pSrc, assuming an appropriate -** index existed. -*/ -static int termCanDriveIndex( - WhereTerm *pTerm, /* WHERE clause term to check */ - struct SrcList_item *pSrc, /* Table we are trying to access */ - Bitmask notReady /* Tables in outer loops of the join */ -){ - char aff; - if( pTerm->leftCursor!=pSrc->iCursor ) return 0; - if( (pTerm->eOperator & WO_EQ)==0 ) return 0; - if( (pTerm->prereqRight & notReady)!=0 ) return 0; - if( pTerm->u.leftColumn<0 ) return 0; - aff = pSrc->pTab->aCol[pTerm->u.leftColumn].affinity; - if( !sqlite3IndexAffinityOk(pTerm->pExpr, aff) ) return 0; - return 1; -} -#endif - - -#ifndef SQLITE_OMIT_AUTOMATIC_INDEX -/* -** Generate code to construct the Index object for an automatic index -** and to set up the WhereLevel object pLevel so that the code generator -** makes use of the automatic index. -*/ -static void constructAutomaticIndex( - Parse *pParse, /* The parsing context */ - WhereClause *pWC, /* The WHERE clause */ - struct SrcList_item *pSrc, /* The FROM clause term to get the next index */ - Bitmask notReady, /* Mask of cursors that are not available */ - WhereLevel *pLevel /* Write new index here */ -){ - int nKeyCol; /* Number of columns in the constructed index */ - WhereTerm *pTerm; /* A single term of the WHERE clause */ - WhereTerm *pWCEnd; /* End of pWC->a[] */ - Index *pIdx; /* Object describing the transient index */ - Vdbe *v; /* Prepared statement under construction */ - int addrInit; /* Address of the initialization bypass jump */ - Table *pTable; /* The table being indexed */ - int addrTop; /* Top of the index fill loop */ - int regRecord; /* Register holding an index record */ - int n; /* Column counter */ - int i; /* Loop counter */ - int mxBitCol; /* Maximum column in pSrc->colUsed */ - CollSeq *pColl; /* Collating sequence to on a column */ - WhereLoop *pLoop; /* The Loop object */ - char *zNotUsed; /* Extra space on the end of pIdx */ - Bitmask idxCols; /* Bitmap of columns used for indexing */ - Bitmask extraCols; /* Bitmap of additional columns */ - u8 sentWarning = 0; /* True if a warnning has been issued */ - - /* Generate code to skip over the creation and initialization of the - ** transient index on 2nd and subsequent iterations of the loop. */ - v = pParse->pVdbe; - assert( v!=0 ); - addrInit = sqlite3CodeOnce(pParse); VdbeCoverage(v); - - /* Count the number of columns that will be added to the index - ** and used to match WHERE clause constraints */ - nKeyCol = 0; - pTable = pSrc->pTab; - pWCEnd = &pWC->a[pWC->nTerm]; - pLoop = pLevel->pWLoop; - idxCols = 0; - for(pTerm=pWC->a; pTermu.leftColumn; - Bitmask cMask = iCol>=BMS ? MASKBIT(BMS-1) : MASKBIT(iCol); - testcase( iCol==BMS ); - testcase( iCol==BMS-1 ); - if( !sentWarning ){ - sqlite3_log(SQLITE_WARNING_AUTOINDEX, - "automatic index on %s(%s)", pTable->zName, - pTable->aCol[iCol].zName); - sentWarning = 1; - } - if( (idxCols & cMask)==0 ){ - if( whereLoopResize(pParse->db, pLoop, nKeyCol+1) ) return; - pLoop->aLTerm[nKeyCol++] = pTerm; - idxCols |= cMask; - } - } - } - assert( nKeyCol>0 ); - pLoop->u.btree.nEq = pLoop->nLTerm = nKeyCol; - pLoop->wsFlags = WHERE_COLUMN_EQ | WHERE_IDX_ONLY | WHERE_INDEXED - | WHERE_AUTO_INDEX; - - /* Count the number of additional columns needed to create a - ** covering index. A "covering index" is an index that contains all - ** columns that are needed by the query. With a covering index, the - ** original table never needs to be accessed. Automatic indices must - ** be a covering index because the index will not be updated if the - ** original table changes and the index and table cannot both be used - ** if they go out of sync. - */ - extraCols = pSrc->colUsed & (~idxCols | MASKBIT(BMS-1)); - mxBitCol = (pTable->nCol >= BMS-1) ? BMS-1 : pTable->nCol; - testcase( pTable->nCol==BMS-1 ); - testcase( pTable->nCol==BMS-2 ); - for(i=0; icolUsed & MASKBIT(BMS-1) ){ - nKeyCol += pTable->nCol - BMS + 1; - } - pLoop->wsFlags |= WHERE_COLUMN_EQ | WHERE_IDX_ONLY; - - /* Construct the Index object to describe this index */ - pIdx = sqlite3AllocateIndexObject(pParse->db, nKeyCol+1, 0, &zNotUsed); - if( pIdx==0 ) return; - pLoop->u.btree.pIndex = pIdx; - pIdx->zName = "auto-index"; - pIdx->pTable = pTable; - n = 0; - idxCols = 0; - for(pTerm=pWC->a; pTermu.leftColumn; - Bitmask cMask = iCol>=BMS ? MASKBIT(BMS-1) : MASKBIT(iCol); - testcase( iCol==BMS-1 ); - testcase( iCol==BMS ); - if( (idxCols & cMask)==0 ){ - Expr *pX = pTerm->pExpr; - idxCols |= cMask; - pIdx->aiColumn[n] = pTerm->u.leftColumn; - pColl = sqlite3BinaryCompareCollSeq(pParse, pX->pLeft, pX->pRight); - pIdx->azColl[n] = ALWAYS(pColl) ? pColl->zName : "BINARY"; - n++; - } - } - } - assert( (u32)n==pLoop->u.btree.nEq ); - - /* Add additional columns needed to make the automatic index into - ** a covering index */ - for(i=0; iaiColumn[n] = i; - pIdx->azColl[n] = "BINARY"; - n++; - } - } - if( pSrc->colUsed & MASKBIT(BMS-1) ){ - for(i=BMS-1; inCol; i++){ - pIdx->aiColumn[n] = i; - pIdx->azColl[n] = "BINARY"; - n++; - } - } - assert( n==nKeyCol ); - pIdx->aiColumn[n] = -1; - pIdx->azColl[n] = "BINARY"; - - /* Create the automatic index */ - assert( pLevel->iIdxCur>=0 ); - pLevel->iIdxCur = pParse->nTab++; - sqlite3VdbeAddOp2(v, OP_OpenAutoindex, pLevel->iIdxCur, nKeyCol+1); - sqlite3VdbeSetP4KeyInfo(pParse, pIdx); - VdbeComment((v, "for %s", pTable->zName)); - - /* Fill the automatic index with content */ - addrTop = sqlite3VdbeAddOp1(v, OP_Rewind, pLevel->iTabCur); VdbeCoverage(v); - regRecord = sqlite3GetTempReg(pParse); - sqlite3GenerateIndexKey(pParse, pIdx, pLevel->iTabCur, regRecord, 0, 0, 0, 0); - sqlite3VdbeAddOp2(v, OP_IdxInsert, pLevel->iIdxCur, regRecord); - sqlite3VdbeChangeP5(v, OPFLAG_USESEEKRESULT); - sqlite3VdbeAddOp2(v, OP_Next, pLevel->iTabCur, addrTop+1); VdbeCoverage(v); - sqlite3VdbeChangeP5(v, SQLITE_STMTSTATUS_AUTOINDEX); - sqlite3VdbeJumpHere(v, addrTop); - sqlite3ReleaseTempReg(pParse, regRecord); - - /* Jump here when skipping the initialization */ - sqlite3VdbeJumpHere(v, addrInit); -} -#endif /* SQLITE_OMIT_AUTOMATIC_INDEX */ - -#ifndef SQLITE_OMIT_VIRTUALTABLE -/* -** Allocate and populate an sqlite3_index_info structure. It is the -** responsibility of the caller to eventually release the structure -** by passing the pointer returned by this function to sqlite3_free(). -*/ -static sqlite3_index_info *allocateIndexInfo( - Parse *pParse, - WhereClause *pWC, - struct SrcList_item *pSrc, - ExprList *pOrderBy -){ +static void explainIndexRange(StrAccum *pStr, WhereLoop *pLoop){ + Index *pIndex = pLoop->u.btree.pIndex; + u16 nEq = pLoop->u.btree.nEq; + u16 nSkip = pLoop->nSkip; int i, j; - int nTerm; - struct sqlite3_index_constraint *pIdxCons; - struct sqlite3_index_orderby *pIdxOrderBy; - struct sqlite3_index_constraint_usage *pUsage; - WhereTerm *pTerm; - int nOrderBy; - sqlite3_index_info *pIdxInfo; - /* Count the number of possible WHERE clause constraints referring - ** to this virtual table */ - for(i=nTerm=0, pTerm=pWC->a; inTerm; i++, pTerm++){ - if( pTerm->leftCursor != pSrc->iCursor ) continue; - assert( IsPowerOfTwo(pTerm->eOperator & ~WO_EQUIV) ); - testcase( pTerm->eOperator & WO_IN ); - testcase( pTerm->eOperator & WO_ISNULL ); - testcase( pTerm->eOperator & WO_ALL ); - if( (pTerm->eOperator & ~(WO_ISNULL|WO_EQUIV))==0 ) continue; - if( pTerm->wtFlags & TERM_VNULL ) continue; - nTerm++; + if( nEq==0 && (pLoop->wsFlags&(WHERE_BTM_LIMIT|WHERE_TOP_LIMIT))==0 ) return; + sqlite3StrAccumAppend(pStr, " (", 2); + for(i=0; i=nSkip ? "%s=?" : "ANY(%s)", z); } - /* If the ORDER BY clause contains only columns in the current - ** virtual table then allocate space for the aOrderBy part of - ** the sqlite3_index_info structure. - */ - nOrderBy = 0; - if( pOrderBy ){ - int n = pOrderBy->nExpr; - for(i=0; ia[i].pExpr; - if( pExpr->op!=TK_COLUMN || pExpr->iTable!=pSrc->iCursor ) break; - } - if( i==n){ - nOrderBy = n; - } + j = i; + if( pLoop->wsFlags&WHERE_BTM_LIMIT ){ + const char *z = explainIndexColumnName(pIndex, i); + explainAppendTerm(pStr, i++, z, ">"); } - - /* Allocate the sqlite3_index_info structure - */ - pIdxInfo = sqlite3DbMallocZero(pParse->db, sizeof(*pIdxInfo) - + (sizeof(*pIdxCons) + sizeof(*pUsage))*nTerm - + sizeof(*pIdxOrderBy)*nOrderBy ); - if( pIdxInfo==0 ){ - sqlite3ErrorMsg(pParse, "out of memory"); - return 0; + if( pLoop->wsFlags&WHERE_TOP_LIMIT ){ + const char *z = explainIndexColumnName(pIndex, j); + explainAppendTerm(pStr, i, z, "<"); } - - /* Initialize the structure. The sqlite3_index_info structure contains - ** many fields that are declared "const" to prevent xBestIndex from - ** changing them. We have to do some funky casting in order to - ** initialize those fields. - */ - pIdxCons = (struct sqlite3_index_constraint*)&pIdxInfo[1]; - pIdxOrderBy = (struct sqlite3_index_orderby*)&pIdxCons[nTerm]; - pUsage = (struct sqlite3_index_constraint_usage*)&pIdxOrderBy[nOrderBy]; - *(int*)&pIdxInfo->nConstraint = nTerm; - *(int*)&pIdxInfo->nOrderBy = nOrderBy; - *(struct sqlite3_index_constraint**)&pIdxInfo->aConstraint = pIdxCons; - *(struct sqlite3_index_orderby**)&pIdxInfo->aOrderBy = pIdxOrderBy; - *(struct sqlite3_index_constraint_usage**)&pIdxInfo->aConstraintUsage = - pUsage; - - for(i=j=0, pTerm=pWC->a; inTerm; i++, pTerm++){ - u8 op; - if( pTerm->leftCursor != pSrc->iCursor ) continue; - assert( IsPowerOfTwo(pTerm->eOperator & ~WO_EQUIV) ); - testcase( pTerm->eOperator & WO_IN ); - testcase( pTerm->eOperator & WO_ISNULL ); - testcase( pTerm->eOperator & WO_ALL ); - if( (pTerm->eOperator & ~(WO_ISNULL|WO_EQUIV))==0 ) continue; - if( pTerm->wtFlags & TERM_VNULL ) continue; - pIdxCons[j].iColumn = pTerm->u.leftColumn; - pIdxCons[j].iTermOffset = i; - op = (u8)pTerm->eOperator & WO_ALL; - if( op==WO_IN ) op = WO_EQ; - pIdxCons[j].op = op; - /* The direct assignment in the previous line is possible only because - ** the WO_ and SQLITE_INDEX_CONSTRAINT_ codes are identical. The - ** following asserts verify this fact. */ - assert( WO_EQ==SQLITE_INDEX_CONSTRAINT_EQ ); - assert( WO_LT==SQLITE_INDEX_CONSTRAINT_LT ); - assert( WO_LE==SQLITE_INDEX_CONSTRAINT_LE ); - assert( WO_GT==SQLITE_INDEX_CONSTRAINT_GT ); - assert( WO_GE==SQLITE_INDEX_CONSTRAINT_GE ); - assert( WO_MATCH==SQLITE_INDEX_CONSTRAINT_MATCH ); - assert( pTerm->eOperator & (WO_IN|WO_EQ|WO_LT|WO_LE|WO_GT|WO_GE|WO_MATCH) ); - j++; - } - for(i=0; ia[i].pExpr; - pIdxOrderBy[i].iColumn = pExpr->iColumn; - pIdxOrderBy[i].desc = pOrderBy->a[i].sortOrder; - } - - return pIdxInfo; + sqlite3StrAccumAppend(pStr, ")", 1); } /* -** The table object reference passed as the second argument to this function -** must represent a virtual table. This function invokes the xBestIndex() -** method of the virtual table with the sqlite3_index_info object that -** comes in as the 3rd argument to this function. +** This function is a no-op unless currently processing an EXPLAIN QUERY PLAN +** command, or if either SQLITE_DEBUG or SQLITE_ENABLE_STMT_SCANSTATUS was +** defined at compile-time. If it is not a no-op, a single OP_Explain opcode +** is added to the output to describe the table scan strategy in pLevel. ** -** If an error occurs, pParse is populated with an error message and a -** non-zero value is returned. Otherwise, 0 is returned and the output -** part of the sqlite3_index_info structure is left populated. -** -** Whether or not an error is returned, it is the responsibility of the -** caller to eventually free p->idxStr if p->needToFreeIdxStr indicates -** that this is required. +** If an OP_Explain opcode is added to the VM, its address is returned. +** Otherwise, if no OP_Explain is coded, zero is returned. */ -static int vtabBestIndex(Parse *pParse, Table *pTab, sqlite3_index_info *p){ - sqlite3_vtab *pVtab = sqlite3GetVTable(pParse->db, pTab)->pVtab; - int i; - int rc; - - TRACE_IDX_INPUTS(p); - rc = pVtab->pModule->xBestIndex(pVtab, p); - TRACE_IDX_OUTPUTS(p); - - if( rc!=SQLITE_OK ){ - if( rc==SQLITE_NOMEM ){ - pParse->db->mallocFailed = 1; - }else if( !pVtab->zErrMsg ){ - sqlite3ErrorMsg(pParse, "%s", sqlite3ErrStr(rc)); - }else{ - sqlite3ErrorMsg(pParse, "%s", pVtab->zErrMsg); - } - } - sqlite3_free(pVtab->zErrMsg); - pVtab->zErrMsg = 0; - - for(i=0; inConstraint; i++){ - if( !p->aConstraint[i].usable && p->aConstraintUsage[i].argvIndex>0 ){ - sqlite3ErrorMsg(pParse, - "table %s: xBestIndex returned an invalid plan", pTab->zName); - } - } - - return pParse->nErr; -} -#endif /* !defined(SQLITE_OMIT_VIRTUALTABLE) */ - - -#ifdef SQLITE_ENABLE_STAT3_OR_STAT4 -/* -** Estimate the location of a particular key among all keys in an -** index. Store the results in aStat as follows: -** -** aStat[0] Est. number of rows less than pVal -** aStat[1] Est. number of rows equal to pVal -** -** Return SQLITE_OK on success. -*/ -static void whereKeyStats( - Parse *pParse, /* Database connection */ - Index *pIdx, /* Index to consider domain of */ - UnpackedRecord *pRec, /* Vector of values to consider */ - int roundUp, /* Round up if true. Round down if false */ - tRowcnt *aStat /* OUT: stats written here */ +SQLITE_PRIVATE int sqlite3WhereExplainOneScan( + Parse *pParse, /* Parse context */ + SrcList *pTabList, /* Table list this loop refers to */ + WhereLevel *pLevel, /* Scan to write OP_Explain opcode for */ + int iLevel, /* Value for "level" column of output */ + int iFrom, /* Value for "from" column of output */ + u16 wctrlFlags /* Flags passed to sqlite3WhereBegin() */ ){ - IndexSample *aSample = pIdx->aSample; - int iCol; /* Index of required stats in anEq[] etc. */ - int iMin = 0; /* Smallest sample not yet tested */ - int i = pIdx->nSample; /* Smallest sample larger than or equal to pRec */ - int iTest; /* Next sample to test */ - int res; /* Result of comparison operation */ - -#ifndef SQLITE_DEBUG - UNUSED_PARAMETER( pParse ); + int ret = 0; +#if !defined(SQLITE_DEBUG) && !defined(SQLITE_ENABLE_STMT_SCANSTATUS) + if( pParse->explain==2 ) #endif - assert( pRec!=0 ); - iCol = pRec->nField - 1; - assert( pIdx->nSample>0 ); - assert( pRec->nField>0 && iColnSampleCol ); - do{ - iTest = (iMin+i)/2; - res = sqlite3VdbeRecordCompare(aSample[iTest].n, aSample[iTest].p, pRec, 0); - if( res<0 ){ - iMin = iTest+1; + { + struct SrcList_item *pItem = &pTabList->a[pLevel->iFrom]; + Vdbe *v = pParse->pVdbe; /* VM being constructed */ + sqlite3 *db = pParse->db; /* Database handle */ + int iId = pParse->iSelectId; /* Select id (left-most output column) */ + int isSearch; /* True for a SEARCH. False for SCAN. */ + WhereLoop *pLoop; /* The controlling WhereLoop object */ + u32 flags; /* Flags that describe this loop */ + char *zMsg; /* Text to add to EQP output */ + StrAccum str; /* EQP output string */ + char zBuf[100]; /* Initial space for EQP output string */ + + pLoop = pLevel->pWLoop; + flags = pLoop->wsFlags; + if( (flags&WHERE_MULTI_OR) || (wctrlFlags&WHERE_ONETABLE_ONLY) ) return 0; + + isSearch = (flags&(WHERE_BTM_LIMIT|WHERE_TOP_LIMIT))!=0 + || ((flags&WHERE_VIRTUALTABLE)==0 && (pLoop->u.btree.nEq>0)) + || (wctrlFlags&(WHERE_ORDERBY_MIN|WHERE_ORDERBY_MAX)); + + sqlite3StrAccumInit(&str, db, zBuf, sizeof(zBuf), SQLITE_MAX_LENGTH); + sqlite3StrAccumAppendAll(&str, isSearch ? "SEARCH" : "SCAN"); + if( pItem->pSelect ){ + sqlite3XPrintf(&str, 0, " SUBQUERY %d", pItem->iSelectId); }else{ - i = iTest; - } - }while( res && iMinnSample ); - assert( 0==sqlite3VdbeRecordCompare(aSample[i].n, aSample[i].p, pRec, 0) - || pParse->db->mallocFailed ); - }else{ - /* Otherwise, pRec must be smaller than sample $i and larger than - ** sample ($i-1). */ - assert( i==pIdx->nSample - || sqlite3VdbeRecordCompare(aSample[i].n, aSample[i].p, pRec, 0)>0 - || pParse->db->mallocFailed ); - assert( i==0 - || sqlite3VdbeRecordCompare(aSample[i-1].n, aSample[i-1].p, pRec, 0)<0 - || pParse->db->mallocFailed ); - } -#endif /* ifdef SQLITE_DEBUG */ - - /* At this point, aSample[i] is the first sample that is greater than - ** or equal to pVal. Or if i==pIdx->nSample, then all samples are less - ** than pVal. If aSample[i]==pVal, then res==0. - */ - if( res==0 ){ - aStat[0] = aSample[i].anLt[iCol]; - aStat[1] = aSample[i].anEq[iCol]; - }else{ - tRowcnt iLower, iUpper, iGap; - if( i==0 ){ - iLower = 0; - iUpper = aSample[0].anLt[iCol]; - }else{ - i64 nRow0 = sqlite3LogEstToInt(pIdx->aiRowLogEst[0]); - iUpper = i>=pIdx->nSample ? nRow0 : aSample[i].anLt[iCol]; - iLower = aSample[i-1].anEq[iCol] + aSample[i-1].anLt[iCol]; - } - aStat[1] = (pIdx->nKeyCol>iCol ? pIdx->aAvgEq[iCol] : 1); - if( iLower>=iUpper ){ - iGap = 0; - }else{ - iGap = iUpper - iLower; - } - if( roundUp ){ - iGap = (iGap*2)/3; - }else{ - iGap = iGap/3; - } - aStat[0] = iLower + iGap; - } -} -#endif /* SQLITE_ENABLE_STAT3_OR_STAT4 */ - -/* -** If it is not NULL, pTerm is a term that provides an upper or lower -** bound on a range scan. Without considering pTerm, it is estimated -** that the scan will visit nNew rows. This function returns the number -** estimated to be visited after taking pTerm into account. -** -** If the user explicitly specified a likelihood() value for this term, -** then the return value is the likelihood multiplied by the number of -** input rows. Otherwise, this function assumes that an "IS NOT NULL" term -** has a likelihood of 0.50, and any other term a likelihood of 0.25. -*/ -static LogEst whereRangeAdjust(WhereTerm *pTerm, LogEst nNew){ - LogEst nRet = nNew; - if( pTerm ){ - if( pTerm->truthProb<=0 ){ - nRet += pTerm->truthProb; - }else if( (pTerm->wtFlags & TERM_VNULL)==0 ){ - nRet -= 20; assert( 20==sqlite3LogEst(4) ); - } - } - return nRet; -} - -/* -** This function is used to estimate the number of rows that will be visited -** by scanning an index for a range of values. The range may have an upper -** bound, a lower bound, or both. The WHERE clause terms that set the upper -** and lower bounds are represented by pLower and pUpper respectively. For -** example, assuming that index p is on t1(a): -** -** ... FROM t1 WHERE a > ? AND a < ? ... -** |_____| |_____| -** | | -** pLower pUpper -** -** If either of the upper or lower bound is not present, then NULL is passed in -** place of the corresponding WhereTerm. -** -** The value in (pBuilder->pNew->u.btree.nEq) is the index of the index -** column subject to the range constraint. Or, equivalently, the number of -** equality constraints optimized by the proposed index scan. For example, -** assuming index p is on t1(a, b), and the SQL query is: -** -** ... FROM t1 WHERE a = ? AND b > ? AND b < ? ... -** -** then nEq is set to 1 (as the range restricted column, b, is the second -** left-most column of the index). Or, if the query is: -** -** ... FROM t1 WHERE a > ? AND a < ? ... -** -** then nEq is set to 0. -** -** When this function is called, *pnOut is set to the sqlite3LogEst() of the -** number of rows that the index scan is expected to visit without -** considering the range constraints. If nEq is 0, this is the number of -** rows in the index. Assuming no error occurs, *pnOut is adjusted (reduced) -** to account for the range contraints pLower and pUpper. -** -** In the absence of sqlite_stat4 ANALYZE data, or if such data cannot be -** used, each range inequality reduces the search space by a factor of 4. -** Hence a pair of constraints (x>? AND x123" Might be NULL */ - WhereTerm *pUpper, /* Upper bound on the range. ex: "x<455" Might be NULL */ - WhereLoop *pLoop /* Modify the .nOut and maybe .rRun fields */ -){ - int rc = SQLITE_OK; - int nOut = pLoop->nOut; - LogEst nNew; - -#ifdef SQLITE_ENABLE_STAT3_OR_STAT4 - Index *p = pLoop->u.btree.pIndex; - int nEq = pLoop->u.btree.nEq; - - if( p->nSample>0 - && nEq==pBuilder->nRecValid - && nEqnSampleCol - && OptimizationEnabled(pParse->db, SQLITE_Stat3) - ){ - UnpackedRecord *pRec = pBuilder->pRec; - tRowcnt a[2]; - u8 aff; - - /* Variable iLower will be set to the estimate of the number of rows in - ** the index that are less than the lower bound of the range query. The - ** lower bound being the concatenation of $P and $L, where $P is the - ** key-prefix formed by the nEq values matched against the nEq left-most - ** columns of the index, and $L is the value in pLower. - ** - ** Or, if pLower is NULL or $L cannot be extracted from it (because it - ** is not a simple variable or literal value), the lower bound of the - ** range is $P. Due to a quirk in the way whereKeyStats() works, even - ** if $L is available, whereKeyStats() is called for both ($P) and - ** ($P:$L) and the larger of the two returned values used. - ** - ** Similarly, iUpper is to be set to the estimate of the number of rows - ** less than the upper bound of the range query. Where the upper bound - ** is either ($P) or ($P:$U). Again, even if $U is available, both values - ** of iUpper are requested of whereKeyStats() and the smaller used. - */ - tRowcnt iLower; - tRowcnt iUpper; - - if( nEq==p->nKeyCol ){ - aff = SQLITE_AFF_INTEGER; - }else{ - aff = p->pTable->aCol[p->aiColumn[nEq]].affinity; - } - /* Determine iLower and iUpper using ($P) only. */ - if( nEq==0 ){ - iLower = 0; - iUpper = sqlite3LogEstToInt(p->aiRowLogEst[0]); - }else{ - /* Note: this call could be optimized away - since the same values must - ** have been requested when testing key $P in whereEqualScanEst(). */ - whereKeyStats(pParse, p, pRec, 0, a); - iLower = a[0]; - iUpper = a[0] + a[1]; + sqlite3XPrintf(&str, 0, " TABLE %s", pItem->zName); } - /* If possible, improve on the iLower estimate using ($P:$L). */ - if( pLower ){ - int bOk; /* True if value is extracted from pExpr */ - Expr *pExpr = pLower->pExpr->pRight; - assert( (pLower->eOperator & (WO_GT|WO_GE))!=0 ); - rc = sqlite3Stat4ProbeSetValue(pParse, p, &pRec, pExpr, aff, nEq, &bOk); - if( rc==SQLITE_OK && bOk ){ - tRowcnt iNew; - whereKeyStats(pParse, p, pRec, 0, a); - iNew = a[0] + ((pLower->eOperator & WO_GT) ? a[1] : 0); - if( iNew>iLower ) iLower = iNew; - nOut--; - } + if( pItem->zAlias ){ + sqlite3XPrintf(&str, 0, " AS %s", pItem->zAlias); } + if( (flags & (WHERE_IPK|WHERE_VIRTUALTABLE))==0 ){ + const char *zFmt = 0; + Index *pIdx; - /* If possible, improve on the iUpper estimate using ($P:$U). */ - if( pUpper ){ - int bOk; /* True if value is extracted from pExpr */ - Expr *pExpr = pUpper->pExpr->pRight; - assert( (pUpper->eOperator & (WO_LT|WO_LE))!=0 ); - rc = sqlite3Stat4ProbeSetValue(pParse, p, &pRec, pExpr, aff, nEq, &bOk); - if( rc==SQLITE_OK && bOk ){ - tRowcnt iNew; - whereKeyStats(pParse, p, pRec, 1, a); - iNew = a[0] + ((pUpper->eOperator & WO_LE) ? a[1] : 0); - if( iNewpRec = pRec; - if( rc==SQLITE_OK ){ - if( iUpper>iLower ){ - nNew = sqlite3LogEst(iUpper - iLower); + assert( pLoop->u.btree.pIndex!=0 ); + pIdx = pLoop->u.btree.pIndex; + assert( !(flags&WHERE_AUTO_INDEX) || (flags&WHERE_IDX_ONLY) ); + if( !HasRowid(pItem->pTab) && IsPrimaryKeyIndex(pIdx) ){ + if( isSearch ){ + zFmt = "PRIMARY KEY"; + } + }else if( flags & WHERE_PARTIALIDX ){ + zFmt = "AUTOMATIC PARTIAL COVERING INDEX"; + }else if( flags & WHERE_AUTO_INDEX ){ + zFmt = "AUTOMATIC COVERING INDEX"; + }else if( flags & WHERE_IDX_ONLY ){ + zFmt = "COVERING INDEX %s"; }else{ - nNew = 10; assert( 10==sqlite3LogEst(2) ); + zFmt = "INDEX %s"; } - if( nNewzName); + explainIndexRange(&str, pLoop); } - pLoop->nOut = (LogEst)nOut; - WHERETRACE(0x10, ("range scan regions: %u..%u est=%d\n", - (u32)iLower, (u32)iUpper, nOut)); - return SQLITE_OK; + }else if( (flags & WHERE_IPK)!=0 && (flags & WHERE_CONSTRAINT)!=0 ){ + const char *zRangeOp; + if( flags&(WHERE_COLUMN_EQ|WHERE_COLUMN_IN) ){ + zRangeOp = "="; + }else if( (flags&WHERE_BOTH_LIMIT)==WHERE_BOTH_LIMIT ){ + zRangeOp = ">? AND rowid<"; + }else if( flags&WHERE_BTM_LIMIT ){ + zRangeOp = ">"; + }else{ + assert( flags&WHERE_TOP_LIMIT); + zRangeOp = "<"; + } + sqlite3XPrintf(&str, 0, " USING INTEGER PRIMARY KEY (rowid%s?)",zRangeOp); + } +#ifndef SQLITE_OMIT_VIRTUALTABLE + else if( (flags & WHERE_VIRTUALTABLE)!=0 ){ + sqlite3XPrintf(&str, 0, " VIRTUAL TABLE INDEX %d:%s", + pLoop->u.vtab.idxNum, pLoop->u.vtab.idxStr); } - } -#else - UNUSED_PARAMETER(pParse); - UNUSED_PARAMETER(pBuilder); #endif - assert( pLower || pUpper ); - assert( pUpper==0 || (pUpper->wtFlags & TERM_VNULL)==0 ); - nNew = whereRangeAdjust(pLower, nOut); - nNew = whereRangeAdjust(pUpper, nNew); - - /* TUNING: If there is both an upper and lower limit, assume the range is - ** reduced by an additional 75%. This means that, by default, an open-ended - ** range query (e.g. col > ?) is assumed to match 1/4 of the rows in the - ** index. While a closed range (e.g. col BETWEEN ? AND ?) is estimated to - ** match 1/64 of the index. */ - if( pLower && pUpper ) nNew -= 20; - - nOut -= (pLower!=0) + (pUpper!=0); - if( nNew<10 ) nNew = 10; - if( nNewnOut = (LogEst)nOut; - return rc; +#ifdef SQLITE_EXPLAIN_ESTIMATED_ROWS + if( pLoop->nOut>=10 ){ + sqlite3XPrintf(&str, 0, " (~%llu rows)", sqlite3LogEstToInt(pLoop->nOut)); + }else{ + sqlite3StrAccumAppend(&str, " (~1 row)", 9); + } +#endif + zMsg = sqlite3StrAccumFinish(&str); + ret = sqlite3VdbeAddOp4(v, OP_Explain, iId, iLevel, iFrom, zMsg,P4_DYNAMIC); + } + return ret; } +#endif /* SQLITE_OMIT_EXPLAIN */ -#ifdef SQLITE_ENABLE_STAT3_OR_STAT4 +#ifdef SQLITE_ENABLE_STMT_SCANSTATUS /* -** Estimate the number of rows that will be returned based on -** an equality constraint x=VALUE and where that VALUE occurs in -** the histogram data. This only works when x is the left-most -** column of an index and sqlite_stat3 histogram data is available -** for that index. When pExpr==NULL that means the constraint is -** "x IS NULL" instead of "x=VALUE". +** Configure the VM passed as the first argument with an +** sqlite3_stmt_scanstatus() entry corresponding to the scan used to +** implement level pLvl. Argument pSrclist is a pointer to the FROM +** clause that the scan reads data from. ** -** Write the estimated row count into *pnRow and return SQLITE_OK. -** If unable to make an estimate, leave *pnRow unchanged and return -** non-zero. -** -** This routine can fail if it is unable to load a collating sequence -** required for string comparison, or if unable to allocate memory -** for a UTF conversion required for comparison. The error is stored -** in the pParse structure. +** If argument addrExplain is not 0, it must be the address of an +** OP_Explain instruction that describes the same loop. */ -static int whereEqualScanEst( - Parse *pParse, /* Parsing & code generating context */ - WhereLoopBuilder *pBuilder, - Expr *pExpr, /* Expression for VALUE in the x=VALUE constraint */ - tRowcnt *pnRow /* Write the revised row estimate here */ +SQLITE_PRIVATE void sqlite3WhereAddScanStatus( + Vdbe *v, /* Vdbe to add scanstatus entry to */ + SrcList *pSrclist, /* FROM clause pLvl reads data from */ + WhereLevel *pLvl, /* Level to add scanstatus() entry for */ + int addrExplain /* Address of OP_Explain (or 0) */ ){ - Index *p = pBuilder->pNew->u.btree.pIndex; - int nEq = pBuilder->pNew->u.btree.nEq; - UnpackedRecord *pRec = pBuilder->pRec; - u8 aff; /* Column affinity */ - int rc; /* Subfunction return code */ - tRowcnt a[2]; /* Statistics */ - int bOk; - - assert( nEq>=1 ); - assert( nEq<=(p->nKeyCol+1) ); - assert( p->aSample!=0 ); - assert( p->nSample>0 ); - assert( pBuilder->nRecValidnRecValid<(nEq-1) ){ - return SQLITE_NOTFOUND; + const char *zObj = 0; + WhereLoop *pLoop = pLvl->pWLoop; + if( (pLoop->wsFlags & WHERE_VIRTUALTABLE)==0 && pLoop->u.btree.pIndex!=0 ){ + zObj = pLoop->u.btree.pIndex->zName; + }else{ + zObj = pSrclist->a[pLvl->iFrom].zName; } - - /* This is an optimization only. The call to sqlite3Stat4ProbeSetValue() - ** below would return the same value. */ - if( nEq>p->nKeyCol ){ - *pnRow = 1; - return SQLITE_OK; - } - - aff = p->pTable->aCol[p->aiColumn[nEq-1]].affinity; - rc = sqlite3Stat4ProbeSetValue(pParse, p, &pRec, pExpr, aff, nEq-1, &bOk); - pBuilder->pRec = pRec; - if( rc!=SQLITE_OK ) return rc; - if( bOk==0 ) return SQLITE_NOTFOUND; - pBuilder->nRecValid = nEq; - - whereKeyStats(pParse, p, pRec, 0, a); - WHERETRACE(0x10,("equality scan regions: %d\n", (int)a[1])); - *pnRow = a[1]; - - return rc; + sqlite3VdbeScanStatus( + v, addrExplain, pLvl->addrBody, pLvl->addrVisit, pLoop->nOut, zObj + ); } -#endif /* SQLITE_ENABLE_STAT3_OR_STAT4 */ +#endif -#ifdef SQLITE_ENABLE_STAT3_OR_STAT4 -/* -** Estimate the number of rows that will be returned based on -** an IN constraint where the right-hand side of the IN operator -** is a list of values. Example: -** -** WHERE x IN (1,2,3,4) -** -** Write the estimated row count into *pnRow and return SQLITE_OK. -** If unable to make an estimate, leave *pnRow unchanged and return -** non-zero. -** -** This routine can fail if it is unable to load a collating sequence -** required for string comparison, or if unable to allocate memory -** for a UTF conversion required for comparison. The error is stored -** in the pParse structure. -*/ -static int whereInScanEst( - Parse *pParse, /* Parsing & code generating context */ - WhereLoopBuilder *pBuilder, - ExprList *pList, /* The value list on the RHS of "x IN (v1,v2,v3,...)" */ - tRowcnt *pnRow /* Write the revised row estimate here */ -){ - Index *p = pBuilder->pNew->u.btree.pIndex; - i64 nRow0 = sqlite3LogEstToInt(p->aiRowLogEst[0]); - int nRecValid = pBuilder->nRecValid; - int rc = SQLITE_OK; /* Subfunction return code */ - tRowcnt nEst; /* Number of rows for a single term */ - tRowcnt nRowEst = 0; /* New estimate of the number of rows */ - int i; /* Loop counter */ - - assert( p->aSample!=0 ); - for(i=0; rc==SQLITE_OK && inExpr; i++){ - nEst = nRow0; - rc = whereEqualScanEst(pParse, pBuilder, pList->a[i].pExpr, &nEst); - nRowEst += nEst; - pBuilder->nRecValid = nRecValid; - } - - if( rc==SQLITE_OK ){ - if( nRowEst > nRow0 ) nRowEst = nRow0; - *pnRow = nRowEst; - WHERETRACE(0x10,("IN row estimate: est=%g\n", nRowEst)); - } - assert( pBuilder->nRecValid==nRecValid ); - return rc; -} -#endif /* SQLITE_ENABLE_STAT3_OR_STAT4 */ /* ** Disable a term in the WHERE clause. Except, do not disable the term @@ -112345,20 +119806,43 @@ static int whereInScanEst( ** but joins might run a little slower. The trick is to disable as much ** as we can without disabling too much. If we disabled in (1), we'd get ** the wrong answer. See ticket #813. +** +** If all the children of a term are disabled, then that term is also +** automatically disabled. In this way, terms get disabled if derived +** virtual terms are tested first. For example: +** +** x GLOB 'abc*' AND x>='abc' AND x<'acd' +** \___________/ \______/ \_____/ +** parent child1 child2 +** +** Only the parent term was in the original WHERE clause. The child1 +** and child2 terms were added by the LIKE optimization. If both of +** the virtual child terms are valid, then testing of the parent can be +** skipped. +** +** Usually the parent term is marked as TERM_CODED. But if the parent +** term was originally TERM_LIKE, then the parent gets TERM_LIKECOND instead. +** The TERM_LIKECOND marking indicates that the term should be coded inside +** a conditional such that is only evaluated on the second pass of a +** LIKE-optimization loop, when scanning BLOBs instead of strings. */ static void disableTerm(WhereLevel *pLevel, WhereTerm *pTerm){ - if( pTerm + int nLoop = 0; + while( pTerm && (pTerm->wtFlags & TERM_CODED)==0 && (pLevel->iLeftJoin==0 || ExprHasProperty(pTerm->pExpr, EP_FromJoin)) && (pLevel->notReady & pTerm->prereqAll)==0 ){ - pTerm->wtFlags |= TERM_CODED; - if( pTerm->iParent>=0 ){ - WhereTerm *pOther = &pTerm->pWC->a[pTerm->iParent]; - if( (--pOther->nChild)==0 ){ - disableTerm(pLevel, pOther); - } + if( nLoop && (pTerm->wtFlags & TERM_LIKE)!=0 ){ + pTerm->wtFlags |= TERM_LIKECOND; + }else{ + pTerm->wtFlags |= TERM_CODED; } + if( pTerm->iParent<0 ) break; + pTerm = &pTerm->pWC->a[pTerm->iParent]; + pTerm->nChild--; + if( pTerm->nChild!=0 ) break; + nLoop++; } } @@ -112366,9 +119850,9 @@ static void disableTerm(WhereLevel *pLevel, WhereTerm *pTerm){ ** Code an OP_Affinity opcode to apply the column affinity string zAff ** to the n registers starting at base. ** -** As an optimization, SQLITE_AFF_NONE entries (which are no-ops) at the +** As an optimization, SQLITE_AFF_BLOB entries (which are no-ops) at the ** beginning and end of zAff are ignored. If all entries in zAff are -** SQLITE_AFF_NONE, then no code gets generated. +** SQLITE_AFF_BLOB, then no code gets generated. ** ** This routine makes its own copy of zAff so that the caller is free ** to modify zAff after this routine returns. @@ -112381,15 +119865,15 @@ static void codeApplyAffinity(Parse *pParse, int base, int n, char *zAff){ } assert( v!=0 ); - /* Adjust base and n to skip over SQLITE_AFF_NONE entries at the beginning + /* Adjust base and n to skip over SQLITE_AFF_BLOB entries at the beginning ** and end of the affinity string. */ - while( n>0 && zAff[0]==SQLITE_AFF_NONE ){ + while( n>0 && zAff[0]==SQLITE_AFF_BLOB ){ n--; base++; zAff++; } - while( n>1 && zAff[n-1]==SQLITE_AFF_NONE ){ + while( n>1 && zAff[n-1]==SQLITE_AFF_BLOB ){ n--; } @@ -112426,7 +119910,7 @@ static int codeEqualityTerm( int iReg; /* Register holding results */ assert( iTarget>0 ); - if( pX->op==TK_EQ ){ + if( pX->op==TK_EQ || pX->op==TK_IS ){ iReg = sqlite3ExprCodeTarget(pParse, pX->pRight, iTarget); }else if( pX->op==TK_ISNULL ){ iReg = iTarget; @@ -112448,7 +119932,7 @@ static int codeEqualityTerm( } assert( pX->op==TK_IN ); iReg = iTarget; - eType = sqlite3FindInIndex(pParse, pX, 0); + eType = sqlite3FindInIndex(pParse, pX, IN_INDEX_LOOP, 0); if( eType==IN_INDEX_INDEX_DESC ){ testcase( bRev ); bRev = !bRev; @@ -112519,17 +120003,17 @@ static int codeEqualityTerm( ** Before returning, *pzAff is set to point to a buffer containing a ** copy of the column affinity string of the index allocated using ** sqlite3DbMalloc(). Except, entries in the copy of the string associated -** with equality constraints that use NONE affinity are set to -** SQLITE_AFF_NONE. This is to deal with SQL such as the following: +** with equality constraints that use BLOB or NONE affinity are set to +** SQLITE_AFF_BLOB. This is to deal with SQL such as the following: ** ** CREATE TABLE t1(a TEXT PRIMARY KEY, b); ** SELECT ... FROM t1 AS t2, t1 WHERE t1.a = t2.b; ** ** In the example above, the index on t1(a) has TEXT affinity. But since -** the right hand side of the equality constraint (t2.b) has NONE affinity, +** the right hand side of the equality constraint (t2.b) has BLOB/NONE affinity, ** no conversion should be attempted before using a t2.b value as part of ** a key to search the index. Hence the first byte in the returned affinity -** string in this example would be set to SQLITE_AFF_NONE. +** string in this example would be set to SQLITE_AFF_BLOB. */ static int codeAllEqualityTerms( Parse *pParse, /* Parsing context */ @@ -112553,7 +120037,7 @@ static int codeAllEqualityTerms( pLoop = pLevel->pWLoop; assert( (pLoop->wsFlags & WHERE_VIRTUALTABLE)==0 ); nEq = pLoop->u.btree.nEq; - nSkip = pLoop->u.btree.nSkip; + nSkip = pLoop->nSkip; pIdx = pLoop->u.btree.pIndex; assert( pIdx!=0 ); @@ -112563,7 +120047,7 @@ static int codeAllEqualityTerms( nReg = pLoop->u.btree.nEq + nExtraReg; pParse->nMem += nReg; - zAff = sqlite3DbStrDup(pParse->db, sqlite3IndexAffinityStr(v, pIdx)); + zAff = sqlite3DbStrDup(pParse->db,sqlite3IndexAffinityStr(pParse->db,pIdx)); if( !zAff ){ pParse->db->mallocFailed = 1; } @@ -112582,8 +120066,8 @@ static int codeAllEqualityTerms( sqlite3VdbeJumpHere(v, j); for(j=0; jaiColumn[j]>=0 ); - VdbeComment((v, "%s", pIdx->pTable->aCol[pIdx->aiColumn[j]].zName)); + testcase( pIdx->aiColumn[j]==XN_EXPR ); + VdbeComment((v, "%s", explainIndexColumnName(pIdx, j))); } } @@ -112611,16 +120095,16 @@ static int codeAllEqualityTerms( testcase( pTerm->eOperator & WO_IN ); if( (pTerm->eOperator & (WO_ISNULL|WO_IN))==0 ){ Expr *pRight = pTerm->pExpr->pRight; - if( sqlite3ExprCanBeNull(pRight) ){ + if( (pTerm->wtFlags & TERM_IS)==0 && sqlite3ExprCanBeNull(pRight) ){ sqlite3VdbeAddOp2(v, OP_IsNull, regBase+j, pLevel->addrBrk); VdbeCoverage(v); } if( zAff ){ - if( sqlite3CompareAffinity(pRight, zAff[j])==SQLITE_AFF_NONE ){ - zAff[j] = SQLITE_AFF_NONE; + if( sqlite3CompareAffinity(pRight, zAff[j])==SQLITE_AFF_BLOB ){ + zAff[j] = SQLITE_AFF_BLOB; } if( sqlite3ExprNeedsNoAffinityChange(pRight, zAff[j]) ){ - zAff[j] = SQLITE_AFF_NONE; + zAff[j] = SQLITE_AFF_BLOB; } } } @@ -112629,182 +120113,197 @@ static int codeAllEqualityTerms( return regBase; } -#ifndef SQLITE_OMIT_EXPLAIN +#ifndef SQLITE_LIKE_DOESNT_MATCH_BLOBS /* -** This routine is a helper for explainIndexRange() below +** If the most recently coded instruction is a constant range contraint +** that originated from the LIKE optimization, then change the P3 to be +** pLoop->iLikeRepCntr and set P5. ** -** pStr holds the text of an expression that we are building up one term -** at a time. This routine adds a new term to the end of the expression. -** Terms are separated by AND so add the "AND" text for second and subsequent -** terms only. +** The LIKE optimization trys to evaluate "x LIKE 'abc%'" as a range +** expression: "x>='ABC' AND x<'abd'". But this requires that the range +** scan loop run twice, once for strings and a second time for BLOBs. +** The OP_String opcodes on the second pass convert the upper and lower +** bound string contants to blobs. This routine makes the necessary changes +** to the OP_String opcodes for that to happen. +** +** Except, of course, if SQLITE_LIKE_DOESNT_MATCH_BLOBS is defined, then +** only the one pass through the string space is required, so this routine +** becomes a no-op. */ -static void explainAppendTerm( - StrAccum *pStr, /* The text expression being built */ - int iTerm, /* Index of this term. First is zero */ - const char *zColumn, /* Name of the column */ - const char *zOp /* Name of the operator */ +static void whereLikeOptimizationStringFixup( + Vdbe *v, /* prepared statement under construction */ + WhereLevel *pLevel, /* The loop that contains the LIKE operator */ + WhereTerm *pTerm /* The upper or lower bound just coded */ ){ - if( iTerm ) sqlite3StrAccumAppend(pStr, " AND ", 5); - sqlite3StrAccumAppendAll(pStr, zColumn); - sqlite3StrAccumAppend(pStr, zOp, 1); - sqlite3StrAccumAppend(pStr, "?", 1); -} - -/* -** Argument pLevel describes a strategy for scanning table pTab. This -** function returns a pointer to a string buffer containing a description -** of the subset of table rows scanned by the strategy in the form of an -** SQL expression. Or, if all rows are scanned, NULL is returned. -** -** For example, if the query: -** -** SELECT * FROM t1 WHERE a=1 AND b>2; -** -** is run and there is an index on (a, b), then this function returns a -** string similar to: -** -** "a=? AND b>?" -** -** The returned pointer points to memory obtained from sqlite3DbMalloc(). -** It is the responsibility of the caller to free the buffer when it is -** no longer required. -*/ -static char *explainIndexRange(sqlite3 *db, WhereLoop *pLoop, Table *pTab){ - Index *pIndex = pLoop->u.btree.pIndex; - u16 nEq = pLoop->u.btree.nEq; - u16 nSkip = pLoop->u.btree.nSkip; - int i, j; - Column *aCol = pTab->aCol; - i16 *aiColumn = pIndex->aiColumn; - StrAccum txt; - - if( nEq==0 && (pLoop->wsFlags & (WHERE_BTM_LIMIT|WHERE_TOP_LIMIT))==0 ){ - return 0; - } - sqlite3StrAccumInit(&txt, 0, 0, SQLITE_MAX_LENGTH); - txt.db = db; - sqlite3StrAccumAppend(&txt, " (", 2); - for(i=0; inKeyCol ) ? "rowid" : aCol[aiColumn[i]].zName; - if( i>=nSkip ){ - explainAppendTerm(&txt, i, z, "="); - }else{ - if( i ) sqlite3StrAccumAppend(&txt, " AND ", 5); - sqlite3StrAccumAppend(&txt, "ANY(", 4); - sqlite3StrAccumAppendAll(&txt, z); - sqlite3StrAccumAppend(&txt, ")", 1); - } - } - - j = i; - if( pLoop->wsFlags&WHERE_BTM_LIMIT ){ - char *z = (j==pIndex->nKeyCol ) ? "rowid" : aCol[aiColumn[j]].zName; - explainAppendTerm(&txt, i++, z, ">"); - } - if( pLoop->wsFlags&WHERE_TOP_LIMIT ){ - char *z = (j==pIndex->nKeyCol ) ? "rowid" : aCol[aiColumn[j]].zName; - explainAppendTerm(&txt, i, z, "<"); - } - sqlite3StrAccumAppend(&txt, ")", 1); - return sqlite3StrAccumFinish(&txt); -} - -/* -** This function is a no-op unless currently processing an EXPLAIN QUERY PLAN -** command. If the query being compiled is an EXPLAIN QUERY PLAN, a single -** record is added to the output to describe the table scan strategy in -** pLevel. -*/ -static void explainOneScan( - Parse *pParse, /* Parse context */ - SrcList *pTabList, /* Table list this loop refers to */ - WhereLevel *pLevel, /* Scan to write OP_Explain opcode for */ - int iLevel, /* Value for "level" column of output */ - int iFrom, /* Value for "from" column of output */ - u16 wctrlFlags /* Flags passed to sqlite3WhereBegin() */ -){ -#ifndef SQLITE_DEBUG - if( pParse->explain==2 ) -#endif - { - struct SrcList_item *pItem = &pTabList->a[pLevel->iFrom]; - Vdbe *v = pParse->pVdbe; /* VM being constructed */ - sqlite3 *db = pParse->db; /* Database handle */ - char *zMsg; /* Text to add to EQP output */ - int iId = pParse->iSelectId; /* Select id (left-most output column) */ - int isSearch; /* True for a SEARCH. False for SCAN. */ - WhereLoop *pLoop; /* The controlling WhereLoop object */ - u32 flags; /* Flags that describe this loop */ - - pLoop = pLevel->pWLoop; - flags = pLoop->wsFlags; - if( (flags&WHERE_MULTI_OR) || (wctrlFlags&WHERE_ONETABLE_ONLY) ) return; - - isSearch = (flags&(WHERE_BTM_LIMIT|WHERE_TOP_LIMIT))!=0 - || ((flags&WHERE_VIRTUALTABLE)==0 && (pLoop->u.btree.nEq>0)) - || (wctrlFlags&(WHERE_ORDERBY_MIN|WHERE_ORDERBY_MAX)); - - zMsg = sqlite3MPrintf(db, "%s", isSearch?"SEARCH":"SCAN"); - if( pItem->pSelect ){ - zMsg = sqlite3MAppendf(db, zMsg, "%s SUBQUERY %d", zMsg,pItem->iSelectId); - }else{ - zMsg = sqlite3MAppendf(db, zMsg, "%s TABLE %s", zMsg, pItem->zName); - } - - if( pItem->zAlias ){ - zMsg = sqlite3MAppendf(db, zMsg, "%s AS %s", zMsg, pItem->zAlias); - } - if( (flags & (WHERE_IPK|WHERE_VIRTUALTABLE))==0 - && ALWAYS(pLoop->u.btree.pIndex!=0) - ){ - const char *zFmt; - Index *pIdx = pLoop->u.btree.pIndex; - char *zWhere = explainIndexRange(db, pLoop, pItem->pTab); - assert( !(flags&WHERE_AUTO_INDEX) || (flags&WHERE_IDX_ONLY) ); - if( !HasRowid(pItem->pTab) && IsPrimaryKeyIndex(pIdx) ){ - zFmt = zWhere ? "%s USING PRIMARY KEY%.0s%s" : "%s%.0s%s"; - }else if( flags & WHERE_AUTO_INDEX ){ - zFmt = "%s USING AUTOMATIC COVERING INDEX%.0s%s"; - }else if( flags & WHERE_IDX_ONLY ){ - zFmt = "%s USING COVERING INDEX %s%s"; - }else{ - zFmt = "%s USING INDEX %s%s"; - } - zMsg = sqlite3MAppendf(db, zMsg, zFmt, zMsg, pIdx->zName, zWhere); - sqlite3DbFree(db, zWhere); - }else if( (flags & WHERE_IPK)!=0 && (flags & WHERE_CONSTRAINT)!=0 ){ - zMsg = sqlite3MAppendf(db, zMsg, "%s USING INTEGER PRIMARY KEY", zMsg); - - if( flags&(WHERE_COLUMN_EQ|WHERE_COLUMN_IN) ){ - zMsg = sqlite3MAppendf(db, zMsg, "%s (rowid=?)", zMsg); - }else if( (flags&WHERE_BOTH_LIMIT)==WHERE_BOTH_LIMIT ){ - zMsg = sqlite3MAppendf(db, zMsg, "%s (rowid>? AND rowid?)", zMsg); - }else if( ALWAYS(flags&WHERE_TOP_LIMIT) ){ - zMsg = sqlite3MAppendf(db, zMsg, "%s (rowidu.vtab.idxNum, pLoop->u.vtab.idxStr); - } -#endif - zMsg = sqlite3MAppendf(db, zMsg, "%s", zMsg); - sqlite3VdbeAddOp4(v, OP_Explain, iId, iLevel, iFrom, zMsg, P4_DYNAMIC); + if( pTerm->wtFlags & TERM_LIKEOPT ){ + VdbeOp *pOp; + assert( pLevel->iLikeRepCntr>0 ); + pOp = sqlite3VdbeGetOp(v, -1); + assert( pOp!=0 ); + assert( pOp->opcode==OP_String8 + || pTerm->pWC->pWInfo->pParse->db->mallocFailed ); + pOp->p3 = pLevel->iLikeRepCntr; + pOp->p5 = 1; } } #else -# define explainOneScan(u,v,w,x,y,z) -#endif /* SQLITE_OMIT_EXPLAIN */ +# define whereLikeOptimizationStringFixup(A,B,C) +#endif +#ifdef SQLITE_ENABLE_CURSOR_HINTS +/* +** Information is passed from codeCursorHint() down to individual nodes of +** the expression tree (by sqlite3WalkExpr()) using an instance of this +** structure. +*/ +struct CCurHint { + int iTabCur; /* Cursor for the main table */ + int iIdxCur; /* Cursor for the index, if pIdx!=0. Unused otherwise */ + Index *pIdx; /* The index used to access the table */ +}; + +/* +** This function is called for every node of an expression that is a candidate +** for a cursor hint on an index cursor. For TK_COLUMN nodes that reference +** the table CCurHint.iTabCur, verify that the same column can be +** accessed through the index. If it cannot, then set pWalker->eCode to 1. +*/ +static int codeCursorHintCheckExpr(Walker *pWalker, Expr *pExpr){ + struct CCurHint *pHint = pWalker->u.pCCurHint; + assert( pHint->pIdx!=0 ); + if( pExpr->op==TK_COLUMN + && pExpr->iTable==pHint->iTabCur + && sqlite3ColumnOfIndex(pHint->pIdx, pExpr->iColumn)<0 + ){ + pWalker->eCode = 1; + } + return WRC_Continue; +} + + +/* +** This function is called on every node of an expression tree used as an +** argument to the OP_CursorHint instruction. If the node is a TK_COLUMN +** that accesses any table other than the one identified by +** CCurHint.iTabCur, then do the following: +** +** 1) allocate a register and code an OP_Column instruction to read +** the specified column into the new register, and +** +** 2) transform the expression node to a TK_REGISTER node that reads +** from the newly populated register. +** +** Also, if the node is a TK_COLUMN that does access the table idenified +** by pCCurHint.iTabCur, and an index is being used (which we will +** know because CCurHint.pIdx!=0) then transform the TK_COLUMN into +** an access of the index rather than the original table. +*/ +static int codeCursorHintFixExpr(Walker *pWalker, Expr *pExpr){ + int rc = WRC_Continue; + struct CCurHint *pHint = pWalker->u.pCCurHint; + if( pExpr->op==TK_COLUMN ){ + if( pExpr->iTable!=pHint->iTabCur ){ + Vdbe *v = pWalker->pParse->pVdbe; + int reg = ++pWalker->pParse->nMem; /* Register for column value */ + sqlite3ExprCodeGetColumnOfTable( + v, pExpr->pTab, pExpr->iTable, pExpr->iColumn, reg + ); + pExpr->op = TK_REGISTER; + pExpr->iTable = reg; + }else if( pHint->pIdx!=0 ){ + pExpr->iTable = pHint->iIdxCur; + pExpr->iColumn = sqlite3ColumnOfIndex(pHint->pIdx, pExpr->iColumn); + assert( pExpr->iColumn>=0 ); + } + }else if( pExpr->op==TK_AGG_FUNCTION ){ + /* An aggregate function in the WHERE clause of a query means this must + ** be a correlated sub-query, and expression pExpr is an aggregate from + ** the parent context. Do not walk the function arguments in this case. + ** + ** todo: It should be possible to replace this node with a TK_REGISTER + ** expression, as the result of the expression must be stored in a + ** register at this point. The same holds for TK_AGG_COLUMN nodes. */ + rc = WRC_Prune; + } + return rc; +} + +/* +** Insert an OP_CursorHint instruction if it is appropriate to do so. +*/ +static void codeCursorHint( + WhereInfo *pWInfo, /* The where clause */ + WhereLevel *pLevel, /* Which loop to provide hints for */ + WhereTerm *pEndRange /* Hint this end-of-scan boundary term if not NULL */ +){ + Parse *pParse = pWInfo->pParse; + sqlite3 *db = pParse->db; + Vdbe *v = pParse->pVdbe; + Expr *pExpr = 0; + WhereLoop *pLoop = pLevel->pWLoop; + int iCur; + WhereClause *pWC; + WhereTerm *pTerm; + int i, j; + struct CCurHint sHint; + Walker sWalker; + + if( OptimizationDisabled(db, SQLITE_CursorHints) ) return; + iCur = pLevel->iTabCur; + assert( iCur==pWInfo->pTabList->a[pLevel->iFrom].iCursor ); + sHint.iTabCur = iCur; + sHint.iIdxCur = pLevel->iIdxCur; + sHint.pIdx = pLoop->u.btree.pIndex; + memset(&sWalker, 0, sizeof(sWalker)); + sWalker.pParse = pParse; + sWalker.u.pCCurHint = &sHint; + pWC = &pWInfo->sWC; + for(i=0; inTerm; i++){ + pTerm = &pWC->a[i]; + if( pTerm->wtFlags & (TERM_VIRTUAL|TERM_CODED) ) continue; + if( pTerm->prereqAll & pLevel->notReady ) continue; + if( ExprHasProperty(pTerm->pExpr, EP_FromJoin) ) continue; + + /* All terms in pWLoop->aLTerm[] except pEndRange are used to initialize + ** the cursor. These terms are not needed as hints for a pure range + ** scan (that has no == terms) so omit them. */ + if( pLoop->u.btree.nEq==0 && pTerm!=pEndRange ){ + for(j=0; jnLTerm && pLoop->aLTerm[j]!=pTerm; j++){} + if( jnLTerm ) continue; + } + + /* No subqueries or non-deterministic functions allowed */ + if( sqlite3ExprContainsSubquery(pTerm->pExpr) ) continue; + + /* For an index scan, make sure referenced columns are actually in + ** the index. */ + if( sHint.pIdx!=0 ){ + sWalker.eCode = 0; + sWalker.xExprCallback = codeCursorHintCheckExpr; + sqlite3WalkExpr(&sWalker, pTerm->pExpr); + if( sWalker.eCode ) continue; + } + + /* If we survive all prior tests, that means this term is worth hinting */ + pExpr = sqlite3ExprAnd(db, pExpr, sqlite3ExprDup(db, pTerm->pExpr, 0)); + } + if( pExpr!=0 ){ + sWalker.xExprCallback = codeCursorHintFixExpr; + sqlite3WalkExpr(&sWalker, pExpr); + sqlite3VdbeAddOp4(v, OP_CursorHint, + (sHint.pIdx ? sHint.iIdxCur : sHint.iTabCur), 0, 0, + (const char*)pExpr, P4_EXPR); + } +} +#else +# define codeCursorHint(A,B,C) /* No-op */ +#endif /* SQLITE_ENABLE_CURSOR_HINTS */ /* ** Generate code for the start of the iLevel-th loop in the WHERE clause ** implementation described by pWInfo. */ -static Bitmask codeOneLoopStart( +SQLITE_PRIVATE Bitmask sqlite3WhereCodeOneLoopStart( WhereInfo *pWInfo, /* Complete information about the WHERE clause */ int iLevel, /* Which level of pWInfo->a[] should be coded */ Bitmask notReady /* Which tables are currently available */ @@ -112835,7 +120334,7 @@ static Bitmask codeOneLoopStart( pLoop = pLevel->pWLoop; pTabItem = &pWInfo->pTabList->a[pLevel->iFrom]; iCur = pTabItem->iCursor; - pLevel->notReady = notReady & ~getMask(&pWInfo->sMaskSet, iCur); + pLevel->notReady = notReady & ~sqlite3WhereGetMask(&pWInfo->sMaskSet, iCur); bRev = (pWInfo->revMask>>iLevel)&1; omitTable = (pLoop->wsFlags & WHERE_IDX_ONLY)!=0 && (pWInfo->wctrlFlags & WHERE_FORCE_TABLE)==0; @@ -112858,14 +120357,14 @@ static Bitmask codeOneLoopStart( ** initialize a memory cell that records if this table matches any ** row of the left table of the join. */ - if( pLevel->iFrom>0 && (pTabItem[0].jointype & JT_LEFT)!=0 ){ + if( pLevel->iFrom>0 && (pTabItem[0].fg.jointype & JT_LEFT)!=0 ){ pLevel->iLeftJoin = ++pParse->nMem; sqlite3VdbeAddOp2(v, OP_Integer, 0, pLevel->iLeftJoin); VdbeComment((v, "init LEFT JOIN no-match flag")); } /* Special case of a FROM clause subquery implemented as a co-routine */ - if( pTabItem->viaCoroutine ){ + if( pTabItem->fg.viaCoroutine ){ int regYield = pTabItem->regReturn; sqlite3VdbeAddOp3(v, OP_InitCoroutine, regYield, 0, pTabItem->addrFillSub); pLevel->p2 = sqlite3VdbeAddOp2(v, OP_Yield, regYield, addrBrk); @@ -112909,8 +120408,8 @@ static Bitmask codeOneLoopStart( disableTerm(pLevel, pLoop->aLTerm[j]); } } - pLevel->op = OP_VNext; pLevel->p1 = iCur; + pLevel->op = pWInfo->eOnePass ? OP_Noop : OP_VNext; pLevel->p2 = sqlite3VdbeCurrentAddr(v); sqlite3ReleaseTempRange(pParse, iReg, nConstraint+2); sqlite3ExprCachePop(pParse); @@ -112963,6 +120462,7 @@ static Bitmask codeOneLoopStart( pStart = pEnd; pEnd = pTerm; } + codeCursorHint(pWInfo, pLevel, pEnd); if( pStart ){ Expr *pX; /* The expression that defines the start bound */ int r1, rTemp; /* Registers for holding the start boundary */ @@ -113099,7 +120599,7 @@ static Bitmask codeOneLoopStart( pIdx = pLoop->u.btree.pIndex; iIdxCur = pLevel->iIdxCur; - assert( nEq>=pLoop->u.btree.nSkip ); + assert( nEq>=pLoop->nSkip ); /* If this loop satisfies a sort order (pOrderBy) request that ** was passed to this function to implement a "SELECT min(x) ..." @@ -113116,7 +120616,7 @@ static Bitmask codeOneLoopStart( && pWInfo->nOBSat>0 && (pIdx->nKeyCol>nEq) ){ - assert( pLoop->u.btree.nSkip==0 ); + assert( pLoop->nSkip==0 ); bSeekPastNull = 1; nExtraReg = 1; } @@ -113128,10 +120628,27 @@ static Bitmask codeOneLoopStart( if( pLoop->wsFlags & WHERE_BTM_LIMIT ){ pRangeStart = pLoop->aLTerm[j++]; nExtraReg = 1; + /* Like optimization range constraints always occur in pairs */ + assert( (pRangeStart->wtFlags & TERM_LIKEOPT)==0 || + (pLoop->wsFlags & WHERE_TOP_LIMIT)!=0 ); } if( pLoop->wsFlags & WHERE_TOP_LIMIT ){ pRangeEnd = pLoop->aLTerm[j++]; nExtraReg = 1; +#ifndef SQLITE_LIKE_DOESNT_MATCH_BLOBS + if( (pRangeEnd->wtFlags & TERM_LIKEOPT)!=0 ){ + assert( pRangeStart!=0 ); /* LIKE opt constraints */ + assert( pRangeStart->wtFlags & TERM_LIKEOPT ); /* occur in pairs */ + pLevel->iLikeRepCntr = ++pParse->nMem; + testcase( bRev ); + testcase( pIdx->aSortOrder[nEq]==SQLITE_SO_DESC ); + sqlite3VdbeAddOp2(v, OP_Integer, + bRev ^ (pIdx->aSortOrder[nEq]==SQLITE_SO_DESC), + pLevel->iLikeRepCntr); + VdbeComment((v, "LIKE loop counter")); + pLevel->addrLikeRep = sqlite3VdbeCurrentAddr(v); + } +#endif if( pRangeStart==0 && (j = pIdx->aiColumn[nEq])>=0 && pIdx->pTable->aCol[j].notNull==0 @@ -113141,15 +120658,6 @@ static Bitmask codeOneLoopStart( } assert( pRangeEnd==0 || (pRangeEnd->wtFlags & TERM_VNULL)==0 ); - /* Generate code to evaluate all constraint terms using == or IN - ** and store the values of those terms in an array of registers - ** starting at regBase. - */ - regBase = codeAllEqualityTerms(pParse,pLevel,bRev,nExtraReg,&zStartAff); - assert( zStartAff==0 || sqlite3Strlen30(zStartAff)>=nEq ); - if( zStartAff ) cEndAff = zStartAff[nEq]; - addrNxt = pLevel->addrNxt; - /* If we are doing a reverse order scan on an ascending index, or ** a forward order scan on a descending index, interchange the ** start and end terms (pRangeStart and pRangeEnd). @@ -113161,6 +120669,16 @@ static Bitmask codeOneLoopStart( SWAP(u8, bSeekPastNull, bStopAtNull); } + /* Generate code to evaluate all constraint terms using == or IN + ** and store the values of those terms in an array of registers + ** starting at regBase. + */ + codeCursorHint(pWInfo, pLevel, pRangeEnd); + regBase = codeAllEqualityTerms(pParse,pLevel,bRev,nExtraReg,&zStartAff); + assert( zStartAff==0 || sqlite3Strlen30(zStartAff)>=nEq ); + if( zStartAff ) cEndAff = zStartAff[nEq]; + addrNxt = pLevel->addrNxt; + testcase( pRangeStart && (pRangeStart->eOperator & WO_LE)!=0 ); testcase( pRangeStart && (pRangeStart->eOperator & WO_GE)!=0 ); testcase( pRangeEnd && (pRangeEnd->eOperator & WO_LE)!=0 ); @@ -113174,6 +120692,7 @@ static Bitmask codeOneLoopStart( if( pRangeStart ){ Expr *pRight = pRangeStart->pExpr->pRight; sqlite3ExprCode(pParse, pRight, regBase+nEq); + whereLikeOptimizationStringFixup(v, pLevel, pRangeStart); if( (pRangeStart->wtFlags & TERM_VNULL)==0 && sqlite3ExprCanBeNull(pRight) ){ @@ -113181,14 +120700,14 @@ static Bitmask codeOneLoopStart( VdbeCoverage(v); } if( zStartAff ){ - if( sqlite3CompareAffinity(pRight, zStartAff[nEq])==SQLITE_AFF_NONE){ + if( sqlite3CompareAffinity(pRight, zStartAff[nEq])==SQLITE_AFF_BLOB){ /* Since the comparison is to be performed with no conversions ** applied to the operands, set the affinity to apply to pRight to - ** SQLITE_AFF_NONE. */ - zStartAff[nEq] = SQLITE_AFF_NONE; + ** SQLITE_AFF_BLOB. */ + zStartAff[nEq] = SQLITE_AFF_BLOB; } if( sqlite3ExprNeedsNoAffinityChange(pRight, zStartAff[nEq]) ){ - zStartAff[nEq] = SQLITE_AFF_NONE; + zStartAff[nEq] = SQLITE_AFF_BLOB; } } nConstraint++; @@ -113219,13 +120738,14 @@ static Bitmask codeOneLoopStart( Expr *pRight = pRangeEnd->pExpr->pRight; sqlite3ExprCacheRemove(pParse, regBase+nEq, 1); sqlite3ExprCode(pParse, pRight, regBase+nEq); + whereLikeOptimizationStringFixup(v, pLevel, pRangeEnd); if( (pRangeEnd->wtFlags & TERM_VNULL)==0 && sqlite3ExprCanBeNull(pRight) ){ sqlite3VdbeAddOp2(v, OP_IsNull, regBase+nEq, addrNxt); VdbeCoverage(v); } - if( sqlite3CompareAffinity(pRight, cEndAff)!=SQLITE_AFF_NONE + if( sqlite3CompareAffinity(pRight, cEndAff)!=SQLITE_AFF_BLOB && !sqlite3ExprNeedsNoAffinityChange(pRight, cEndAff) ){ codeApplyAffinity(pParse, regBase+nEq, 1, &cEndAff); @@ -113261,7 +120781,12 @@ static Bitmask codeOneLoopStart( iRowidReg = ++pParse->nMem; sqlite3VdbeAddOp2(v, OP_IdxRowid, iIdxCur, iRowidReg); sqlite3ExprCacheStore(pParse, iCur, -1, iRowidReg); - sqlite3VdbeAddOp2(v, OP_Seek, iCur, iRowidReg); /* Deferred seek */ + if( pWInfo->eOnePass!=ONEPASS_OFF ){ + sqlite3VdbeAddOp3(v, OP_NotExists, iCur, 0, iRowidReg); + VdbeCoverage(v); + }else{ + sqlite3VdbeAddOp2(v, OP_Seek, iCur, iRowidReg); /* Deferred seek */ + } }else if( iCur!=iIdxCur ){ Index *pPk = sqlite3PrimaryKeyIndex(pIdx->pTable); iRowidReg = sqlite3GetTempRange(pParse, pPk->nKeyCol); @@ -113333,7 +120858,7 @@ static Bitmask codeOneLoopStart( ** B: ** ** Added 2014-05-26: If the table is a WITHOUT ROWID table, then - ** use an ephermeral index instead of a RowSet to record the primary + ** use an ephemeral index instead of a RowSet to record the primary ** keys of the rows we have already seen. ** */ @@ -113349,6 +120874,7 @@ static Bitmask codeOneLoopStart( int iRetInit; /* Address of regReturn init */ int untestedTerms = 0; /* Some terms not completely tested */ int ii; /* Loop counter */ + u16 wctrlFlags; /* Flags for sub-WHERE clause */ Expr *pAndExpr = 0; /* An ".. AND (...)" expression */ Table *pTab = pTabItem->pTab; @@ -113383,7 +120909,7 @@ static Bitmask codeOneLoopStart( } /* Initialize the rowset register to contain NULL. An SQL NULL is - ** equivalent to an empty rowset. Or, create an ephermeral index + ** equivalent to an empty rowset. Or, create an ephemeral index ** capable of holding primary keys in the case of a WITHOUT ROWID. ** ** Also initialize regReturn to contain the address of the instruction @@ -113428,15 +120954,14 @@ static Bitmask codeOneLoopStart( Expr *pExpr = pWC->a[iTerm].pExpr; if( &pWC->a[iTerm] == pTerm ) continue; if( ExprHasProperty(pExpr, EP_FromJoin) ) continue; - testcase( pWC->a[iTerm].wtFlags & TERM_ORINFO ); - testcase( pWC->a[iTerm].wtFlags & TERM_VIRTUAL ); - if( pWC->a[iTerm].wtFlags & (TERM_ORINFO|TERM_VIRTUAL) ) continue; + if( (pWC->a[iTerm].wtFlags & TERM_VIRTUAL)!=0 ) continue; if( (pWC->a[iTerm].eOperator & WO_ALL)==0 ) continue; + testcase( pWC->a[iTerm].wtFlags & TERM_ORINFO ); pExpr = sqlite3ExprDup(db, pExpr, 0); pAndExpr = sqlite3ExprAnd(db, pAndExpr, pExpr); } if( pAndExpr ){ - pAndExpr = sqlite3PExpr(pParse, TK_AND, 0, pAndExpr, 0); + pAndExpr = sqlite3PExpr(pParse, TK_AND|TKFLG_DONTFOLD, 0, pAndExpr, 0); } } @@ -113444,26 +120969,32 @@ static Bitmask codeOneLoopStart( ** eliminating duplicates from other WHERE clauses, the action for each ** sub-WHERE clause is to to invoke the main loop body as a subroutine. */ + wctrlFlags = WHERE_OMIT_OPEN_CLOSE + | WHERE_FORCE_TABLE + | WHERE_ONETABLE_ONLY + | WHERE_NO_AUTOINDEX; for(ii=0; iinTerm; ii++){ WhereTerm *pOrTerm = &pOrWc->a[ii]; if( pOrTerm->leftCursor==iCur || (pOrTerm->eOperator & WO_AND)!=0 ){ WhereInfo *pSubWInfo; /* Info for single OR-term scan */ Expr *pOrExpr = pOrTerm->pExpr; /* Current OR clause term */ - int j1 = 0; /* Address of jump operation */ + int jmp1 = 0; /* Address of jump operation */ if( pAndExpr && !ExprHasProperty(pOrExpr, EP_FromJoin) ){ pAndExpr->pLeft = pOrExpr; pOrExpr = pAndExpr; } /* Loop through table entries that match term pOrTerm. */ + WHERETRACE(0xffff, ("Subplan for OR-clause:\n")); pSubWInfo = sqlite3WhereBegin(pParse, pOrTab, pOrExpr, 0, 0, - WHERE_OMIT_OPEN_CLOSE | WHERE_AND_ONLY | - WHERE_FORCE_TABLE | WHERE_ONETABLE_ONLY, iCovCur); + wctrlFlags, iCovCur); assert( pSubWInfo || pParse->nErr || db->mallocFailed ); if( pSubWInfo ){ WhereLoop *pSubLoop; - explainOneScan( + int addrExplain = sqlite3WhereExplainOneScan( pParse, pOrTab, &pSubWInfo->a[0], iLevel, pLevel->iFrom, 0 ); + sqlite3WhereAddScanStatus(v, pOrTab, &pSubWInfo->a[0], addrExplain); + /* This is the sub-WHERE clause body. First skip over ** duplicate rows from prior sub-WHERE clauses, and record the ** rowid (or PRIMARY KEY) for the current row so that the same @@ -113474,7 +121005,8 @@ static Bitmask codeOneLoopStart( int iSet = ((ii==pOrWc->nTerm-1)?-1:ii); if( HasRowid(pTab) ){ r = sqlite3ExprCodeGetColumn(pParse, pTab, -1, iCur, regRowid, 0); - j1 = sqlite3VdbeAddOp4Int(v, OP_RowSetTest, regRowset, 0, r,iSet); + jmp1 = sqlite3VdbeAddOp4Int(v, OP_RowSetTest, regRowset, 0, + r,iSet); VdbeCoverage(v); }else{ Index *pPk = sqlite3PrimaryKeyIndex(pTab); @@ -113485,7 +121017,7 @@ static Bitmask codeOneLoopStart( r = sqlite3GetTempRange(pParse, nPk); for(iPk=0; iPkaiColumn[iPk]; - sqlite3ExprCodeGetColumn(pParse, pTab, iCol, iCur, r+iPk, 0); + sqlite3ExprCodeGetColumnToReg(pParse, pTab, iCol, iCur, r+iPk); } /* Check if the temp table already contains this key. If so, @@ -113500,7 +121032,7 @@ static Bitmask codeOneLoopStart( ** need to insert the key into the temp table, as it will never ** be tested for. */ if( iSet ){ - j1 = sqlite3VdbeAddOp4Int(v, OP_Found, regRowset, 0, r, nPk); + jmp1 = sqlite3VdbeAddOp4Int(v, OP_Found, regRowset, 0, r, nPk); VdbeCoverage(v); } if( iSet>=0 ){ @@ -113519,7 +121051,7 @@ static Bitmask codeOneLoopStart( /* Jump here (skipping the main loop body subroutine) if the ** current sub-WHERE row is a duplicate from prior sub-WHEREs. */ - if( j1 ) sqlite3VdbeJumpHere(v, j1); + if( jmp1 ) sqlite3VdbeJumpHere(v, jmp1); /* The pSubWInfo->untestedTerms flag means that this OR term ** contained one or more AND term from a notReady table. The @@ -113548,6 +121080,7 @@ static Bitmask codeOneLoopStart( ){ assert( pSubWInfo->a[0].iIdxCur==iCovCur ); pCov = pSubLoop->u.btree.pIndex; + wctrlFlags |= WHERE_REOPEN_IDX; }else{ pCov = 0; } @@ -113564,7 +121097,7 @@ static Bitmask codeOneLoopStart( sqlite3ExprDelete(db, pAndExpr); } sqlite3VdbeChangeP1(v, iRetInit, sqlite3VdbeCurrentAddr(v)); - sqlite3VdbeAddOp2(v, OP_Goto, 0, pLevel->addrBrk); + sqlite3VdbeGoto(v, pLevel->addrBrk); sqlite3VdbeResolveLabel(v, iLoopBody); if( pWInfo->nLevel>1 ) sqlite3StackFree(db, pOrTab); @@ -113579,11 +121112,12 @@ static Bitmask codeOneLoopStart( static const u8 aStep[] = { OP_Next, OP_Prev }; static const u8 aStart[] = { OP_Rewind, OP_Last }; assert( bRev==0 || bRev==1 ); - if( pTabItem->isRecursive ){ + if( pTabItem->fg.isRecursive ){ /* Tables marked isRecursive have only a single row that is stored in ** a pseudo-cursor. No need to Rewind or Next such cursors. */ pLevel->op = OP_Noop; }else{ + codeCursorHint(pWInfo, pLevel, 0); pLevel->op = aStep[bRev]; pLevel->p1 = iCur; pLevel->p2 = 1 + sqlite3VdbeAddOp2(v, aStart[bRev], iCur, addrBrk); @@ -113593,11 +121127,16 @@ static Bitmask codeOneLoopStart( } } +#ifdef SQLITE_ENABLE_STMT_SCANSTATUS + pLevel->addrVisit = sqlite3VdbeCurrentAddr(v); +#endif + /* Insert code to test every subexpression that can be completely ** computed using the current set of tables. */ for(pTerm=pWC->a, j=pWC->nTerm; j>0; j--, pTerm++){ Expr *pE; + int skipLikeAddr = 0; testcase( pTerm->wtFlags & TERM_VIRTUAL ); testcase( pTerm->wtFlags & TERM_CODED ); if( pTerm->wtFlags & (TERM_VIRTUAL|TERM_CODED) ) continue; @@ -113612,7 +121151,17 @@ static Bitmask codeOneLoopStart( if( pLevel->iLeftJoin && !ExprHasProperty(pE, EP_FromJoin) ){ continue; } + if( pTerm->wtFlags & TERM_LIKECOND ){ +#ifdef SQLITE_LIKE_DOESNT_MATCH_BLOBS + continue; +#else + assert( pLevel->iLikeRepCntr>0 ); + skipLikeAddr = sqlite3VdbeAddOp1(v, OP_IfNot, pLevel->iLikeRepCntr); + VdbeCoverage(v); +#endif + } sqlite3ExprIfFalse(pParse, pE, addrCont, SQLITE_JUMPIFNULL); + if( skipLikeAddr ) sqlite3VdbeJumpHere(v, skipLikeAddr); pTerm->wtFlags |= TERM_CODED; } @@ -113628,16 +121177,19 @@ static Bitmask codeOneLoopStart( Expr *pE, *pEAlt; WhereTerm *pAlt; if( pTerm->wtFlags & (TERM_VIRTUAL|TERM_CODED) ) continue; - if( pTerm->eOperator!=(WO_EQUIV|WO_EQ) ) continue; + if( (pTerm->eOperator & (WO_EQ|WO_IS))==0 ) continue; + if( (pTerm->eOperator & WO_EQUIV)==0 ) continue; if( pTerm->leftCursor!=iCur ) continue; if( pLevel->iLeftJoin ) continue; pE = pTerm->pExpr; assert( !ExprHasProperty(pE, EP_FromJoin) ); assert( (pTerm->prereqRight & pLevel->notReady)!=0 ); - pAlt = findTerm(pWC, iCur, pTerm->u.leftColumn, notReady, WO_EQ|WO_IN, 0); + pAlt = sqlite3WhereFindTerm(pWC, iCur, pTerm->u.leftColumn, notReady, + WO_EQ|WO_IN|WO_IS, 0); if( pAlt==0 ) continue; if( pAlt->wtFlags & (TERM_CODED) ) continue; testcase( pAlt->eOperator & WO_EQ ); + testcase( pAlt->eOperator & WO_IS ); testcase( pAlt->eOperator & WO_IN ); VdbeModuleComment((v, "begin transitive constraint")); pEAlt = sqlite3StackAllocRaw(db, sizeof(*pEAlt)); @@ -113674,21 +121226,3010 @@ static Bitmask codeOneLoopStart( return pLevel->notReady; } -#if defined(WHERETRACE_ENABLED) && defined(SQLITE_ENABLE_TREE_EXPLAIN) +/************** End of wherecode.c *******************************************/ +/************** Begin file whereexpr.c ***************************************/ /* -** Generate "Explanation" text for a WhereTerm. +** 2015-06-08 +** +** The author disclaims copyright to this source code. In place of +** a legal notice, here is a blessing: +** +** May you do good and not evil. +** May you find forgiveness for yourself and forgive others. +** May you share freely, never taking more than you give. +** +************************************************************************* +** This module contains C code that generates VDBE code used to process +** the WHERE clause of SQL statements. +** +** This file was originally part of where.c but was split out to improve +** readability and editabiliity. This file contains utility routines for +** analyzing Expr objects in the WHERE clause. */ -static void whereExplainTerm(Vdbe *v, WhereTerm *pTerm){ - char zType[4]; - memcpy(zType, "...", 4); - if( pTerm->wtFlags & TERM_VIRTUAL ) zType[0] = 'V'; - if( pTerm->eOperator & WO_EQUIV ) zType[1] = 'E'; - if( ExprHasProperty(pTerm->pExpr, EP_FromJoin) ) zType[2] = 'L'; - sqlite3ExplainPrintf(v, "%s ", zType); - sqlite3ExplainExpr(v, pTerm->pExpr); -} -#endif /* WHERETRACE_ENABLED && SQLITE_ENABLE_TREE_EXPLAIN */ +/* #include "sqliteInt.h" */ +/* #include "whereInt.h" */ +/* Forward declarations */ +static void exprAnalyze(SrcList*, WhereClause*, int); + +/* +** Deallocate all memory associated with a WhereOrInfo object. +*/ +static void whereOrInfoDelete(sqlite3 *db, WhereOrInfo *p){ + sqlite3WhereClauseClear(&p->wc); + sqlite3DbFree(db, p); +} + +/* +** Deallocate all memory associated with a WhereAndInfo object. +*/ +static void whereAndInfoDelete(sqlite3 *db, WhereAndInfo *p){ + sqlite3WhereClauseClear(&p->wc); + sqlite3DbFree(db, p); +} + +/* +** Add a single new WhereTerm entry to the WhereClause object pWC. +** The new WhereTerm object is constructed from Expr p and with wtFlags. +** The index in pWC->a[] of the new WhereTerm is returned on success. +** 0 is returned if the new WhereTerm could not be added due to a memory +** allocation error. The memory allocation failure will be recorded in +** the db->mallocFailed flag so that higher-level functions can detect it. +** +** This routine will increase the size of the pWC->a[] array as necessary. +** +** If the wtFlags argument includes TERM_DYNAMIC, then responsibility +** for freeing the expression p is assumed by the WhereClause object pWC. +** This is true even if this routine fails to allocate a new WhereTerm. +** +** WARNING: This routine might reallocate the space used to store +** WhereTerms. All pointers to WhereTerms should be invalidated after +** calling this routine. Such pointers may be reinitialized by referencing +** the pWC->a[] array. +*/ +static int whereClauseInsert(WhereClause *pWC, Expr *p, u16 wtFlags){ + WhereTerm *pTerm; + int idx; + testcase( wtFlags & TERM_VIRTUAL ); + if( pWC->nTerm>=pWC->nSlot ){ + WhereTerm *pOld = pWC->a; + sqlite3 *db = pWC->pWInfo->pParse->db; + pWC->a = sqlite3DbMallocRaw(db, sizeof(pWC->a[0])*pWC->nSlot*2 ); + if( pWC->a==0 ){ + if( wtFlags & TERM_DYNAMIC ){ + sqlite3ExprDelete(db, p); + } + pWC->a = pOld; + return 0; + } + memcpy(pWC->a, pOld, sizeof(pWC->a[0])*pWC->nTerm); + if( pOld!=pWC->aStatic ){ + sqlite3DbFree(db, pOld); + } + pWC->nSlot = sqlite3DbMallocSize(db, pWC->a)/sizeof(pWC->a[0]); + memset(&pWC->a[pWC->nTerm], 0, sizeof(pWC->a[0])*(pWC->nSlot-pWC->nTerm)); + } + pTerm = &pWC->a[idx = pWC->nTerm++]; + if( p && ExprHasProperty(p, EP_Unlikely) ){ + pTerm->truthProb = sqlite3LogEst(p->iTable) - 270; + }else{ + pTerm->truthProb = 1; + } + pTerm->pExpr = sqlite3ExprSkipCollate(p); + pTerm->wtFlags = wtFlags; + pTerm->pWC = pWC; + pTerm->iParent = -1; + return idx; +} + +/* +** Return TRUE if the given operator is one of the operators that is +** allowed for an indexable WHERE clause term. The allowed operators are +** "=", "<", ">", "<=", ">=", "IN", and "IS NULL" +*/ +static int allowedOp(int op){ + assert( TK_GT>TK_EQ && TK_GTTK_EQ && TK_LTTK_EQ && TK_LE=TK_EQ && op<=TK_GE) || op==TK_ISNULL || op==TK_IS; +} + +/* +** Commute a comparison operator. Expressions of the form "X op Y" +** are converted into "Y op X". +** +** If left/right precedence rules come into play when determining the +** collating sequence, then COLLATE operators are adjusted to ensure +** that the collating sequence does not change. For example: +** "Y collate NOCASE op X" becomes "X op Y" because any collation sequence on +** the left hand side of a comparison overrides any collation sequence +** attached to the right. For the same reason the EP_Collate flag +** is not commuted. +*/ +static void exprCommute(Parse *pParse, Expr *pExpr){ + u16 expRight = (pExpr->pRight->flags & EP_Collate); + u16 expLeft = (pExpr->pLeft->flags & EP_Collate); + assert( allowedOp(pExpr->op) && pExpr->op!=TK_IN ); + if( expRight==expLeft ){ + /* Either X and Y both have COLLATE operator or neither do */ + if( expRight ){ + /* Both X and Y have COLLATE operators. Make sure X is always + ** used by clearing the EP_Collate flag from Y. */ + pExpr->pRight->flags &= ~EP_Collate; + }else if( sqlite3ExprCollSeq(pParse, pExpr->pLeft)!=0 ){ + /* Neither X nor Y have COLLATE operators, but X has a non-default + ** collating sequence. So add the EP_Collate marker on X to cause + ** it to be searched first. */ + pExpr->pLeft->flags |= EP_Collate; + } + } + SWAP(Expr*,pExpr->pRight,pExpr->pLeft); + if( pExpr->op>=TK_GT ){ + assert( TK_LT==TK_GT+2 ); + assert( TK_GE==TK_LE+2 ); + assert( TK_GT>TK_EQ ); + assert( TK_GTop>=TK_GT && pExpr->op<=TK_GE ); + pExpr->op = ((pExpr->op-TK_GT)^2)+TK_GT; + } +} + +/* +** Translate from TK_xx operator to WO_xx bitmask. +*/ +static u16 operatorMask(int op){ + u16 c; + assert( allowedOp(op) ); + if( op==TK_IN ){ + c = WO_IN; + }else if( op==TK_ISNULL ){ + c = WO_ISNULL; + }else if( op==TK_IS ){ + c = WO_IS; + }else{ + assert( (WO_EQ<<(op-TK_EQ)) < 0x7fff ); + c = (u16)(WO_EQ<<(op-TK_EQ)); + } + assert( op!=TK_ISNULL || c==WO_ISNULL ); + assert( op!=TK_IN || c==WO_IN ); + assert( op!=TK_EQ || c==WO_EQ ); + assert( op!=TK_LT || c==WO_LT ); + assert( op!=TK_LE || c==WO_LE ); + assert( op!=TK_GT || c==WO_GT ); + assert( op!=TK_GE || c==WO_GE ); + assert( op!=TK_IS || c==WO_IS ); + return c; +} + + +#ifndef SQLITE_OMIT_LIKE_OPTIMIZATION +/* +** Check to see if the given expression is a LIKE or GLOB operator that +** can be optimized using inequality constraints. Return TRUE if it is +** so and false if not. +** +** In order for the operator to be optimizible, the RHS must be a string +** literal that does not begin with a wildcard. The LHS must be a column +** that may only be NULL, a string, or a BLOB, never a number. (This means +** that virtual tables cannot participate in the LIKE optimization.) The +** collating sequence for the column on the LHS must be appropriate for +** the operator. +*/ +static int isLikeOrGlob( + Parse *pParse, /* Parsing and code generating context */ + Expr *pExpr, /* Test this expression */ + Expr **ppPrefix, /* Pointer to TK_STRING expression with pattern prefix */ + int *pisComplete, /* True if the only wildcard is % in the last character */ + int *pnoCase /* True if uppercase is equivalent to lowercase */ +){ + const char *z = 0; /* String on RHS of LIKE operator */ + Expr *pRight, *pLeft; /* Right and left size of LIKE operator */ + ExprList *pList; /* List of operands to the LIKE operator */ + int c; /* One character in z[] */ + int cnt; /* Number of non-wildcard prefix characters */ + char wc[3]; /* Wildcard characters */ + sqlite3 *db = pParse->db; /* Database connection */ + sqlite3_value *pVal = 0; + int op; /* Opcode of pRight */ + + if( !sqlite3IsLikeFunction(db, pExpr, pnoCase, wc) ){ + return 0; + } +#ifdef SQLITE_EBCDIC + if( *pnoCase ) return 0; +#endif + pList = pExpr->x.pList; + pLeft = pList->a[1].pExpr; + if( pLeft->op!=TK_COLUMN + || sqlite3ExprAffinity(pLeft)!=SQLITE_AFF_TEXT + || IsVirtual(pLeft->pTab) /* Value might be numeric */ + ){ + /* IMP: R-02065-49465 The left-hand side of the LIKE or GLOB operator must + ** be the name of an indexed column with TEXT affinity. */ + return 0; + } + assert( pLeft->iColumn!=(-1) ); /* Because IPK never has AFF_TEXT */ + + pRight = sqlite3ExprSkipCollate(pList->a[0].pExpr); + op = pRight->op; + if( op==TK_VARIABLE ){ + Vdbe *pReprepare = pParse->pReprepare; + int iCol = pRight->iColumn; + pVal = sqlite3VdbeGetBoundValue(pReprepare, iCol, SQLITE_AFF_BLOB); + if( pVal && sqlite3_value_type(pVal)==SQLITE_TEXT ){ + z = (char *)sqlite3_value_text(pVal); + } + sqlite3VdbeSetVarmask(pParse->pVdbe, iCol); + assert( pRight->op==TK_VARIABLE || pRight->op==TK_REGISTER ); + }else if( op==TK_STRING ){ + z = pRight->u.zToken; + } + if( z ){ + cnt = 0; + while( (c=z[cnt])!=0 && c!=wc[0] && c!=wc[1] && c!=wc[2] ){ + cnt++; + } + if( cnt!=0 && 255!=(u8)z[cnt-1] ){ + Expr *pPrefix; + *pisComplete = c==wc[0] && z[cnt+1]==0; + pPrefix = sqlite3Expr(db, TK_STRING, z); + if( pPrefix ) pPrefix->u.zToken[cnt] = 0; + *ppPrefix = pPrefix; + if( op==TK_VARIABLE ){ + Vdbe *v = pParse->pVdbe; + sqlite3VdbeSetVarmask(v, pRight->iColumn); + if( *pisComplete && pRight->u.zToken[1] ){ + /* If the rhs of the LIKE expression is a variable, and the current + ** value of the variable means there is no need to invoke the LIKE + ** function, then no OP_Variable will be added to the program. + ** This causes problems for the sqlite3_bind_parameter_name() + ** API. To work around them, add a dummy OP_Variable here. + */ + int r1 = sqlite3GetTempReg(pParse); + sqlite3ExprCodeTarget(pParse, pRight, r1); + sqlite3VdbeChangeP3(v, sqlite3VdbeCurrentAddr(v)-1, 0); + sqlite3ReleaseTempReg(pParse, r1); + } + } + }else{ + z = 0; + } + } + + sqlite3ValueFree(pVal); + return (z!=0); +} +#endif /* SQLITE_OMIT_LIKE_OPTIMIZATION */ + + +#ifndef SQLITE_OMIT_VIRTUALTABLE +/* +** Check to see if the given expression is of the form +** +** column OP expr +** +** where OP is one of MATCH, GLOB, LIKE or REGEXP and "column" is a +** column of a virtual table. +** +** If it is then return TRUE. If not, return FALSE. +*/ +static int isMatchOfColumn( + Expr *pExpr, /* Test this expression */ + unsigned char *peOp2 /* OUT: 0 for MATCH, or else an op2 value */ +){ + struct Op2 { + const char *zOp; + unsigned char eOp2; + } aOp[] = { + { "match", SQLITE_INDEX_CONSTRAINT_MATCH }, + { "glob", SQLITE_INDEX_CONSTRAINT_GLOB }, + { "like", SQLITE_INDEX_CONSTRAINT_LIKE }, + { "regexp", SQLITE_INDEX_CONSTRAINT_REGEXP } + }; + ExprList *pList; + Expr *pCol; /* Column reference */ + int i; + + if( pExpr->op!=TK_FUNCTION ){ + return 0; + } + pList = pExpr->x.pList; + if( pList==0 || pList->nExpr!=2 ){ + return 0; + } + pCol = pList->a[1].pExpr; + if( pCol->op!=TK_COLUMN || !IsVirtual(pCol->pTab) ){ + return 0; + } + for(i=0; iu.zToken, aOp[i].zOp)==0 ){ + *peOp2 = aOp[i].eOp2; + return 1; + } + } + return 0; +} +#endif /* SQLITE_OMIT_VIRTUALTABLE */ + +/* +** If the pBase expression originated in the ON or USING clause of +** a join, then transfer the appropriate markings over to derived. +*/ +static void transferJoinMarkings(Expr *pDerived, Expr *pBase){ + if( pDerived ){ + pDerived->flags |= pBase->flags & EP_FromJoin; + pDerived->iRightJoinTable = pBase->iRightJoinTable; + } +} + +/* +** Mark term iChild as being a child of term iParent +*/ +static void markTermAsChild(WhereClause *pWC, int iChild, int iParent){ + pWC->a[iChild].iParent = iParent; + pWC->a[iChild].truthProb = pWC->a[iParent].truthProb; + pWC->a[iParent].nChild++; +} + +/* +** Return the N-th AND-connected subterm of pTerm. Or if pTerm is not +** a conjunction, then return just pTerm when N==0. If N is exceeds +** the number of available subterms, return NULL. +*/ +static WhereTerm *whereNthSubterm(WhereTerm *pTerm, int N){ + if( pTerm->eOperator!=WO_AND ){ + return N==0 ? pTerm : 0; + } + if( Nu.pAndInfo->wc.nTerm ){ + return &pTerm->u.pAndInfo->wc.a[N]; + } + return 0; +} + +/* +** Subterms pOne and pTwo are contained within WHERE clause pWC. The +** two subterms are in disjunction - they are OR-ed together. +** +** If these two terms are both of the form: "A op B" with the same +** A and B values but different operators and if the operators are +** compatible (if one is = and the other is <, for example) then +** add a new virtual AND term to pWC that is the combination of the +** two. +** +** Some examples: +** +** x x<=y +** x=y OR x=y --> x=y +** x<=y OR x x<=y +** +** The following is NOT generated: +** +** xy --> x!=y +*/ +static void whereCombineDisjuncts( + SrcList *pSrc, /* the FROM clause */ + WhereClause *pWC, /* The complete WHERE clause */ + WhereTerm *pOne, /* First disjunct */ + WhereTerm *pTwo /* Second disjunct */ +){ + u16 eOp = pOne->eOperator | pTwo->eOperator; + sqlite3 *db; /* Database connection (for malloc) */ + Expr *pNew; /* New virtual expression */ + int op; /* Operator for the combined expression */ + int idxNew; /* Index in pWC of the next virtual term */ + + if( (pOne->eOperator & (WO_EQ|WO_LT|WO_LE|WO_GT|WO_GE))==0 ) return; + if( (pTwo->eOperator & (WO_EQ|WO_LT|WO_LE|WO_GT|WO_GE))==0 ) return; + if( (eOp & (WO_EQ|WO_LT|WO_LE))!=eOp + && (eOp & (WO_EQ|WO_GT|WO_GE))!=eOp ) return; + assert( pOne->pExpr->pLeft!=0 && pOne->pExpr->pRight!=0 ); + assert( pTwo->pExpr->pLeft!=0 && pTwo->pExpr->pRight!=0 ); + if( sqlite3ExprCompare(pOne->pExpr->pLeft, pTwo->pExpr->pLeft, -1) ) return; + if( sqlite3ExprCompare(pOne->pExpr->pRight, pTwo->pExpr->pRight, -1) )return; + /* If we reach this point, it means the two subterms can be combined */ + if( (eOp & (eOp-1))!=0 ){ + if( eOp & (WO_LT|WO_LE) ){ + eOp = WO_LE; + }else{ + assert( eOp & (WO_GT|WO_GE) ); + eOp = WO_GE; + } + } + db = pWC->pWInfo->pParse->db; + pNew = sqlite3ExprDup(db, pOne->pExpr, 0); + if( pNew==0 ) return; + for(op=TK_EQ; eOp!=(WO_EQ<<(op-TK_EQ)); op++){ assert( opop = op; + idxNew = whereClauseInsert(pWC, pNew, TERM_VIRTUAL|TERM_DYNAMIC); + exprAnalyze(pSrc, pWC, idxNew); +} + +#if !defined(SQLITE_OMIT_OR_OPTIMIZATION) && !defined(SQLITE_OMIT_SUBQUERY) +/* +** Analyze a term that consists of two or more OR-connected +** subterms. So in: +** +** ... WHERE (a=5) AND (b=7 OR c=9 OR d=13) AND (d=13) +** ^^^^^^^^^^^^^^^^^^^^ +** +** This routine analyzes terms such as the middle term in the above example. +** A WhereOrTerm object is computed and attached to the term under +** analysis, regardless of the outcome of the analysis. Hence: +** +** WhereTerm.wtFlags |= TERM_ORINFO +** WhereTerm.u.pOrInfo = a dynamically allocated WhereOrTerm object +** +** The term being analyzed must have two or more of OR-connected subterms. +** A single subterm might be a set of AND-connected sub-subterms. +** Examples of terms under analysis: +** +** (A) t1.x=t2.y OR t1.x=t2.z OR t1.y=15 OR t1.z=t3.a+5 +** (B) x=expr1 OR expr2=x OR x=expr3 +** (C) t1.x=t2.y OR (t1.x=t2.z AND t1.y=15) +** (D) x=expr1 OR (y>11 AND y<22 AND z LIKE '*hello*') +** (E) (p.a=1 AND q.b=2 AND r.c=3) OR (p.x=4 AND q.y=5 AND r.z=6) +** (F) x>A OR (x=A AND y>=B) +** +** CASE 1: +** +** If all subterms are of the form T.C=expr for some single column of C and +** a single table T (as shown in example B above) then create a new virtual +** term that is an equivalent IN expression. In other words, if the term +** being analyzed is: +** +** x = expr1 OR expr2 = x OR x = expr3 +** +** then create a new virtual term like this: +** +** x IN (expr1,expr2,expr3) +** +** CASE 2: +** +** If there are exactly two disjuncts and one side has x>A and the other side +** has x=A (for the same x and A) then add a new virtual conjunct term to the +** WHERE clause of the form "x>=A". Example: +** +** x>A OR (x=A AND y>B) adds: x>=A +** +** The added conjunct can sometimes be helpful in query planning. +** +** CASE 3: +** +** If all subterms are indexable by a single table T, then set +** +** WhereTerm.eOperator = WO_OR +** WhereTerm.u.pOrInfo->indexable |= the cursor number for table T +** +** A subterm is "indexable" if it is of the form +** "T.C " where C is any column of table T and +** is one of "=", "<", "<=", ">", ">=", "IS NULL", or "IN". +** A subterm is also indexable if it is an AND of two or more +** subsubterms at least one of which is indexable. Indexable AND +** subterms have their eOperator set to WO_AND and they have +** u.pAndInfo set to a dynamically allocated WhereAndTerm object. +** +** From another point of view, "indexable" means that the subterm could +** potentially be used with an index if an appropriate index exists. +** This analysis does not consider whether or not the index exists; that +** is decided elsewhere. This analysis only looks at whether subterms +** appropriate for indexing exist. +** +** All examples A through E above satisfy case 3. But if a term +** also satisfies case 1 (such as B) we know that the optimizer will +** always prefer case 1, so in that case we pretend that case 3 is not +** satisfied. +** +** It might be the case that multiple tables are indexable. For example, +** (E) above is indexable on tables P, Q, and R. +** +** Terms that satisfy case 3 are candidates for lookup by using +** separate indices to find rowids for each subterm and composing +** the union of all rowids using a RowSet object. This is similar +** to "bitmap indices" in other database engines. +** +** OTHERWISE: +** +** If none of cases 1, 2, or 3 apply, then leave the eOperator set to +** zero. This term is not useful for search. +*/ +static void exprAnalyzeOrTerm( + SrcList *pSrc, /* the FROM clause */ + WhereClause *pWC, /* the complete WHERE clause */ + int idxTerm /* Index of the OR-term to be analyzed */ +){ + WhereInfo *pWInfo = pWC->pWInfo; /* WHERE clause processing context */ + Parse *pParse = pWInfo->pParse; /* Parser context */ + sqlite3 *db = pParse->db; /* Database connection */ + WhereTerm *pTerm = &pWC->a[idxTerm]; /* The term to be analyzed */ + Expr *pExpr = pTerm->pExpr; /* The expression of the term */ + int i; /* Loop counters */ + WhereClause *pOrWc; /* Breakup of pTerm into subterms */ + WhereTerm *pOrTerm; /* A Sub-term within the pOrWc */ + WhereOrInfo *pOrInfo; /* Additional information associated with pTerm */ + Bitmask chngToIN; /* Tables that might satisfy case 1 */ + Bitmask indexable; /* Tables that are indexable, satisfying case 2 */ + + /* + ** Break the OR clause into its separate subterms. The subterms are + ** stored in a WhereClause structure containing within the WhereOrInfo + ** object that is attached to the original OR clause term. + */ + assert( (pTerm->wtFlags & (TERM_DYNAMIC|TERM_ORINFO|TERM_ANDINFO))==0 ); + assert( pExpr->op==TK_OR ); + pTerm->u.pOrInfo = pOrInfo = sqlite3DbMallocZero(db, sizeof(*pOrInfo)); + if( pOrInfo==0 ) return; + pTerm->wtFlags |= TERM_ORINFO; + pOrWc = &pOrInfo->wc; + sqlite3WhereClauseInit(pOrWc, pWInfo); + sqlite3WhereSplit(pOrWc, pExpr, TK_OR); + sqlite3WhereExprAnalyze(pSrc, pOrWc); + if( db->mallocFailed ) return; + assert( pOrWc->nTerm>=2 ); + + /* + ** Compute the set of tables that might satisfy cases 1 or 3. + */ + indexable = ~(Bitmask)0; + chngToIN = ~(Bitmask)0; + for(i=pOrWc->nTerm-1, pOrTerm=pOrWc->a; i>=0 && indexable; i--, pOrTerm++){ + if( (pOrTerm->eOperator & WO_SINGLE)==0 ){ + WhereAndInfo *pAndInfo; + assert( (pOrTerm->wtFlags & (TERM_ANDINFO|TERM_ORINFO))==0 ); + chngToIN = 0; + pAndInfo = sqlite3DbMallocRaw(db, sizeof(*pAndInfo)); + if( pAndInfo ){ + WhereClause *pAndWC; + WhereTerm *pAndTerm; + int j; + Bitmask b = 0; + pOrTerm->u.pAndInfo = pAndInfo; + pOrTerm->wtFlags |= TERM_ANDINFO; + pOrTerm->eOperator = WO_AND; + pAndWC = &pAndInfo->wc; + sqlite3WhereClauseInit(pAndWC, pWC->pWInfo); + sqlite3WhereSplit(pAndWC, pOrTerm->pExpr, TK_AND); + sqlite3WhereExprAnalyze(pSrc, pAndWC); + pAndWC->pOuter = pWC; + testcase( db->mallocFailed ); + if( !db->mallocFailed ){ + for(j=0, pAndTerm=pAndWC->a; jnTerm; j++, pAndTerm++){ + assert( pAndTerm->pExpr ); + if( allowedOp(pAndTerm->pExpr->op) ){ + b |= sqlite3WhereGetMask(&pWInfo->sMaskSet, pAndTerm->leftCursor); + } + } + } + indexable &= b; + } + }else if( pOrTerm->wtFlags & TERM_COPIED ){ + /* Skip this term for now. We revisit it when we process the + ** corresponding TERM_VIRTUAL term */ + }else{ + Bitmask b; + b = sqlite3WhereGetMask(&pWInfo->sMaskSet, pOrTerm->leftCursor); + if( pOrTerm->wtFlags & TERM_VIRTUAL ){ + WhereTerm *pOther = &pOrWc->a[pOrTerm->iParent]; + b |= sqlite3WhereGetMask(&pWInfo->sMaskSet, pOther->leftCursor); + } + indexable &= b; + if( (pOrTerm->eOperator & WO_EQ)==0 ){ + chngToIN = 0; + }else{ + chngToIN &= b; + } + } + } + + /* + ** Record the set of tables that satisfy case 3. The set might be + ** empty. + */ + pOrInfo->indexable = indexable; + pTerm->eOperator = indexable==0 ? 0 : WO_OR; + + /* For a two-way OR, attempt to implementation case 2. + */ + if( indexable && pOrWc->nTerm==2 ){ + int iOne = 0; + WhereTerm *pOne; + while( (pOne = whereNthSubterm(&pOrWc->a[0],iOne++))!=0 ){ + int iTwo = 0; + WhereTerm *pTwo; + while( (pTwo = whereNthSubterm(&pOrWc->a[1],iTwo++))!=0 ){ + whereCombineDisjuncts(pSrc, pWC, pOne, pTwo); + } + } + } + + /* + ** chngToIN holds a set of tables that *might* satisfy case 1. But + ** we have to do some additional checking to see if case 1 really + ** is satisfied. + ** + ** chngToIN will hold either 0, 1, or 2 bits. The 0-bit case means + ** that there is no possibility of transforming the OR clause into an + ** IN operator because one or more terms in the OR clause contain + ** something other than == on a column in the single table. The 1-bit + ** case means that every term of the OR clause is of the form + ** "table.column=expr" for some single table. The one bit that is set + ** will correspond to the common table. We still need to check to make + ** sure the same column is used on all terms. The 2-bit case is when + ** the all terms are of the form "table1.column=table2.column". It + ** might be possible to form an IN operator with either table1.column + ** or table2.column as the LHS if either is common to every term of + ** the OR clause. + ** + ** Note that terms of the form "table.column1=table.column2" (the + ** same table on both sizes of the ==) cannot be optimized. + */ + if( chngToIN ){ + int okToChngToIN = 0; /* True if the conversion to IN is valid */ + int iColumn = -1; /* Column index on lhs of IN operator */ + int iCursor = -1; /* Table cursor common to all terms */ + int j = 0; /* Loop counter */ + + /* Search for a table and column that appears on one side or the + ** other of the == operator in every subterm. That table and column + ** will be recorded in iCursor and iColumn. There might not be any + ** such table and column. Set okToChngToIN if an appropriate table + ** and column is found but leave okToChngToIN false if not found. + */ + for(j=0; j<2 && !okToChngToIN; j++){ + pOrTerm = pOrWc->a; + for(i=pOrWc->nTerm-1; i>=0; i--, pOrTerm++){ + assert( pOrTerm->eOperator & WO_EQ ); + pOrTerm->wtFlags &= ~TERM_OR_OK; + if( pOrTerm->leftCursor==iCursor ){ + /* This is the 2-bit case and we are on the second iteration and + ** current term is from the first iteration. So skip this term. */ + assert( j==1 ); + continue; + } + if( (chngToIN & sqlite3WhereGetMask(&pWInfo->sMaskSet, + pOrTerm->leftCursor))==0 ){ + /* This term must be of the form t1.a==t2.b where t2 is in the + ** chngToIN set but t1 is not. This term will be either preceded + ** or follwed by an inverted copy (t2.b==t1.a). Skip this term + ** and use its inversion. */ + testcase( pOrTerm->wtFlags & TERM_COPIED ); + testcase( pOrTerm->wtFlags & TERM_VIRTUAL ); + assert( pOrTerm->wtFlags & (TERM_COPIED|TERM_VIRTUAL) ); + continue; + } + iColumn = pOrTerm->u.leftColumn; + iCursor = pOrTerm->leftCursor; + break; + } + if( i<0 ){ + /* No candidate table+column was found. This can only occur + ** on the second iteration */ + assert( j==1 ); + assert( IsPowerOfTwo(chngToIN) ); + assert( chngToIN==sqlite3WhereGetMask(&pWInfo->sMaskSet, iCursor) ); + break; + } + testcase( j==1 ); + + /* We have found a candidate table and column. Check to see if that + ** table and column is common to every term in the OR clause */ + okToChngToIN = 1; + for(; i>=0 && okToChngToIN; i--, pOrTerm++){ + assert( pOrTerm->eOperator & WO_EQ ); + if( pOrTerm->leftCursor!=iCursor ){ + pOrTerm->wtFlags &= ~TERM_OR_OK; + }else if( pOrTerm->u.leftColumn!=iColumn ){ + okToChngToIN = 0; + }else{ + int affLeft, affRight; + /* If the right-hand side is also a column, then the affinities + ** of both right and left sides must be such that no type + ** conversions are required on the right. (Ticket #2249) + */ + affRight = sqlite3ExprAffinity(pOrTerm->pExpr->pRight); + affLeft = sqlite3ExprAffinity(pOrTerm->pExpr->pLeft); + if( affRight!=0 && affRight!=affLeft ){ + okToChngToIN = 0; + }else{ + pOrTerm->wtFlags |= TERM_OR_OK; + } + } + } + } + + /* At this point, okToChngToIN is true if original pTerm satisfies + ** case 1. In that case, construct a new virtual term that is + ** pTerm converted into an IN operator. + */ + if( okToChngToIN ){ + Expr *pDup; /* A transient duplicate expression */ + ExprList *pList = 0; /* The RHS of the IN operator */ + Expr *pLeft = 0; /* The LHS of the IN operator */ + Expr *pNew; /* The complete IN operator */ + + for(i=pOrWc->nTerm-1, pOrTerm=pOrWc->a; i>=0; i--, pOrTerm++){ + if( (pOrTerm->wtFlags & TERM_OR_OK)==0 ) continue; + assert( pOrTerm->eOperator & WO_EQ ); + assert( pOrTerm->leftCursor==iCursor ); + assert( pOrTerm->u.leftColumn==iColumn ); + pDup = sqlite3ExprDup(db, pOrTerm->pExpr->pRight, 0); + pList = sqlite3ExprListAppend(pWInfo->pParse, pList, pDup); + pLeft = pOrTerm->pExpr->pLeft; + } + assert( pLeft!=0 ); + pDup = sqlite3ExprDup(db, pLeft, 0); + pNew = sqlite3PExpr(pParse, TK_IN, pDup, 0, 0); + if( pNew ){ + int idxNew; + transferJoinMarkings(pNew, pExpr); + assert( !ExprHasProperty(pNew, EP_xIsSelect) ); + pNew->x.pList = pList; + idxNew = whereClauseInsert(pWC, pNew, TERM_VIRTUAL|TERM_DYNAMIC); + testcase( idxNew==0 ); + exprAnalyze(pSrc, pWC, idxNew); + pTerm = &pWC->a[idxTerm]; + markTermAsChild(pWC, idxNew, idxTerm); + }else{ + sqlite3ExprListDelete(db, pList); + } + pTerm->eOperator = WO_NOOP; /* case 1 trumps case 3 */ + } + } +} +#endif /* !SQLITE_OMIT_OR_OPTIMIZATION && !SQLITE_OMIT_SUBQUERY */ + +/* +** We already know that pExpr is a binary operator where both operands are +** column references. This routine checks to see if pExpr is an equivalence +** relation: +** 1. The SQLITE_Transitive optimization must be enabled +** 2. Must be either an == or an IS operator +** 3. Not originating in the ON clause of an OUTER JOIN +** 4. The affinities of A and B must be compatible +** 5a. Both operands use the same collating sequence OR +** 5b. The overall collating sequence is BINARY +** If this routine returns TRUE, that means that the RHS can be substituted +** for the LHS anyplace else in the WHERE clause where the LHS column occurs. +** This is an optimization. No harm comes from returning 0. But if 1 is +** returned when it should not be, then incorrect answers might result. +*/ +static int termIsEquivalence(Parse *pParse, Expr *pExpr){ + char aff1, aff2; + CollSeq *pColl; + const char *zColl1, *zColl2; + if( !OptimizationEnabled(pParse->db, SQLITE_Transitive) ) return 0; + if( pExpr->op!=TK_EQ && pExpr->op!=TK_IS ) return 0; + if( ExprHasProperty(pExpr, EP_FromJoin) ) return 0; + aff1 = sqlite3ExprAffinity(pExpr->pLeft); + aff2 = sqlite3ExprAffinity(pExpr->pRight); + if( aff1!=aff2 + && (!sqlite3IsNumericAffinity(aff1) || !sqlite3IsNumericAffinity(aff2)) + ){ + return 0; + } + pColl = sqlite3BinaryCompareCollSeq(pParse, pExpr->pLeft, pExpr->pRight); + if( pColl==0 || sqlite3StrICmp(pColl->zName, "BINARY")==0 ) return 1; + pColl = sqlite3ExprCollSeq(pParse, pExpr->pLeft); + /* Since pLeft and pRight are both a column references, their collating + ** sequence should always be defined. */ + zColl1 = ALWAYS(pColl) ? pColl->zName : 0; + pColl = sqlite3ExprCollSeq(pParse, pExpr->pRight); + zColl2 = ALWAYS(pColl) ? pColl->zName : 0; + return sqlite3StrICmp(zColl1, zColl2)==0; +} + +/* +** Recursively walk the expressions of a SELECT statement and generate +** a bitmask indicating which tables are used in that expression +** tree. +*/ +static Bitmask exprSelectUsage(WhereMaskSet *pMaskSet, Select *pS){ + Bitmask mask = 0; + while( pS ){ + SrcList *pSrc = pS->pSrc; + mask |= sqlite3WhereExprListUsage(pMaskSet, pS->pEList); + mask |= sqlite3WhereExprListUsage(pMaskSet, pS->pGroupBy); + mask |= sqlite3WhereExprListUsage(pMaskSet, pS->pOrderBy); + mask |= sqlite3WhereExprUsage(pMaskSet, pS->pWhere); + mask |= sqlite3WhereExprUsage(pMaskSet, pS->pHaving); + if( ALWAYS(pSrc!=0) ){ + int i; + for(i=0; inSrc; i++){ + mask |= exprSelectUsage(pMaskSet, pSrc->a[i].pSelect); + mask |= sqlite3WhereExprUsage(pMaskSet, pSrc->a[i].pOn); + } + } + pS = pS->pPrior; + } + return mask; +} + +/* +** Expression pExpr is one operand of a comparison operator that might +** be useful for indexing. This routine checks to see if pExpr appears +** in any index. Return TRUE (1) if pExpr is an indexed term and return +** FALSE (0) if not. If TRUE is returned, also set *piCur to the cursor +** number of the table that is indexed and *piColumn to the column number +** of the column that is indexed, or -2 if an expression is being indexed. +** +** If pExpr is a TK_COLUMN column reference, then this routine always returns +** true even if that particular column is not indexed, because the column +** might be added to an automatic index later. +*/ +static int exprMightBeIndexed( + SrcList *pFrom, /* The FROM clause */ + Bitmask mPrereq, /* Bitmask of FROM clause terms referenced by pExpr */ + Expr *pExpr, /* An operand of a comparison operator */ + int *piCur, /* Write the referenced table cursor number here */ + int *piColumn /* Write the referenced table column number here */ +){ + Index *pIdx; + int i; + int iCur; + if( pExpr->op==TK_COLUMN ){ + *piCur = pExpr->iTable; + *piColumn = pExpr->iColumn; + return 1; + } + if( mPrereq==0 ) return 0; /* No table references */ + if( (mPrereq&(mPrereq-1))!=0 ) return 0; /* Refs more than one table */ + for(i=0; mPrereq>1; i++, mPrereq>>=1){} + iCur = pFrom->a[i].iCursor; + for(pIdx=pFrom->a[i].pTab->pIndex; pIdx; pIdx=pIdx->pNext){ + if( pIdx->aColExpr==0 ) continue; + for(i=0; inKeyCol; i++){ + if( pIdx->aiColumn[i]!=(-2) ) continue; + if( sqlite3ExprCompare(pExpr, pIdx->aColExpr->a[i].pExpr, iCur)==0 ){ + *piCur = iCur; + *piColumn = -2; + return 1; + } + } + } + return 0; +} + +/* +** The input to this routine is an WhereTerm structure with only the +** "pExpr" field filled in. The job of this routine is to analyze the +** subexpression and populate all the other fields of the WhereTerm +** structure. +** +** If the expression is of the form " X" it gets commuted +** to the standard form of "X ". +** +** If the expression is of the form "X Y" where both X and Y are +** columns, then the original expression is unchanged and a new virtual +** term of the form "Y X" is added to the WHERE clause and +** analyzed separately. The original term is marked with TERM_COPIED +** and the new term is marked with TERM_DYNAMIC (because it's pExpr +** needs to be freed with the WhereClause) and TERM_VIRTUAL (because it +** is a commuted copy of a prior term.) The original term has nChild=1 +** and the copy has idxParent set to the index of the original term. +*/ +static void exprAnalyze( + SrcList *pSrc, /* the FROM clause */ + WhereClause *pWC, /* the WHERE clause */ + int idxTerm /* Index of the term to be analyzed */ +){ + WhereInfo *pWInfo = pWC->pWInfo; /* WHERE clause processing context */ + WhereTerm *pTerm; /* The term to be analyzed */ + WhereMaskSet *pMaskSet; /* Set of table index masks */ + Expr *pExpr; /* The expression to be analyzed */ + Bitmask prereqLeft; /* Prerequesites of the pExpr->pLeft */ + Bitmask prereqAll; /* Prerequesites of pExpr */ + Bitmask extraRight = 0; /* Extra dependencies on LEFT JOIN */ + Expr *pStr1 = 0; /* RHS of LIKE/GLOB operator */ + int isComplete = 0; /* RHS of LIKE/GLOB ends with wildcard */ + int noCase = 0; /* uppercase equivalent to lowercase */ + int op; /* Top-level operator. pExpr->op */ + Parse *pParse = pWInfo->pParse; /* Parsing context */ + sqlite3 *db = pParse->db; /* Database connection */ + unsigned char eOp2; /* op2 value for LIKE/REGEXP/GLOB */ + + if( db->mallocFailed ){ + return; + } + pTerm = &pWC->a[idxTerm]; + pMaskSet = &pWInfo->sMaskSet; + pExpr = pTerm->pExpr; + assert( pExpr->op!=TK_AS && pExpr->op!=TK_COLLATE ); + prereqLeft = sqlite3WhereExprUsage(pMaskSet, pExpr->pLeft); + op = pExpr->op; + if( op==TK_IN ){ + assert( pExpr->pRight==0 ); + if( ExprHasProperty(pExpr, EP_xIsSelect) ){ + pTerm->prereqRight = exprSelectUsage(pMaskSet, pExpr->x.pSelect); + }else{ + pTerm->prereqRight = sqlite3WhereExprListUsage(pMaskSet, pExpr->x.pList); + } + }else if( op==TK_ISNULL ){ + pTerm->prereqRight = 0; + }else{ + pTerm->prereqRight = sqlite3WhereExprUsage(pMaskSet, pExpr->pRight); + } + prereqAll = sqlite3WhereExprUsage(pMaskSet, pExpr); + if( ExprHasProperty(pExpr, EP_FromJoin) ){ + Bitmask x = sqlite3WhereGetMask(pMaskSet, pExpr->iRightJoinTable); + prereqAll |= x; + extraRight = x-1; /* ON clause terms may not be used with an index + ** on left table of a LEFT JOIN. Ticket #3015 */ + } + pTerm->prereqAll = prereqAll; + pTerm->leftCursor = -1; + pTerm->iParent = -1; + pTerm->eOperator = 0; + if( allowedOp(op) ){ + int iCur, iColumn; + Expr *pLeft = sqlite3ExprSkipCollate(pExpr->pLeft); + Expr *pRight = sqlite3ExprSkipCollate(pExpr->pRight); + u16 opMask = (pTerm->prereqRight & prereqLeft)==0 ? WO_ALL : WO_EQUIV; + if( exprMightBeIndexed(pSrc, prereqLeft, pLeft, &iCur, &iColumn) ){ + pTerm->leftCursor = iCur; + pTerm->u.leftColumn = iColumn; + pTerm->eOperator = operatorMask(op) & opMask; + } + if( op==TK_IS ) pTerm->wtFlags |= TERM_IS; + if( pRight + && exprMightBeIndexed(pSrc, pTerm->prereqRight, pRight, &iCur, &iColumn) + ){ + WhereTerm *pNew; + Expr *pDup; + u16 eExtraOp = 0; /* Extra bits for pNew->eOperator */ + if( pTerm->leftCursor>=0 ){ + int idxNew; + pDup = sqlite3ExprDup(db, pExpr, 0); + if( db->mallocFailed ){ + sqlite3ExprDelete(db, pDup); + return; + } + idxNew = whereClauseInsert(pWC, pDup, TERM_VIRTUAL|TERM_DYNAMIC); + if( idxNew==0 ) return; + pNew = &pWC->a[idxNew]; + markTermAsChild(pWC, idxNew, idxTerm); + if( op==TK_IS ) pNew->wtFlags |= TERM_IS; + pTerm = &pWC->a[idxTerm]; + pTerm->wtFlags |= TERM_COPIED; + + if( termIsEquivalence(pParse, pDup) ){ + pTerm->eOperator |= WO_EQUIV; + eExtraOp = WO_EQUIV; + } + }else{ + pDup = pExpr; + pNew = pTerm; + } + exprCommute(pParse, pDup); + pNew->leftCursor = iCur; + pNew->u.leftColumn = iColumn; + testcase( (prereqLeft | extraRight) != prereqLeft ); + pNew->prereqRight = prereqLeft | extraRight; + pNew->prereqAll = prereqAll; + pNew->eOperator = (operatorMask(pDup->op) + eExtraOp) & opMask; + } + } + +#ifndef SQLITE_OMIT_BETWEEN_OPTIMIZATION + /* If a term is the BETWEEN operator, create two new virtual terms + ** that define the range that the BETWEEN implements. For example: + ** + ** a BETWEEN b AND c + ** + ** is converted into: + ** + ** (a BETWEEN b AND c) AND (a>=b) AND (a<=c) + ** + ** The two new terms are added onto the end of the WhereClause object. + ** The new terms are "dynamic" and are children of the original BETWEEN + ** term. That means that if the BETWEEN term is coded, the children are + ** skipped. Or, if the children are satisfied by an index, the original + ** BETWEEN term is skipped. + */ + else if( pExpr->op==TK_BETWEEN && pWC->op==TK_AND ){ + ExprList *pList = pExpr->x.pList; + int i; + static const u8 ops[] = {TK_GE, TK_LE}; + assert( pList!=0 ); + assert( pList->nExpr==2 ); + for(i=0; i<2; i++){ + Expr *pNewExpr; + int idxNew; + pNewExpr = sqlite3PExpr(pParse, ops[i], + sqlite3ExprDup(db, pExpr->pLeft, 0), + sqlite3ExprDup(db, pList->a[i].pExpr, 0), 0); + transferJoinMarkings(pNewExpr, pExpr); + idxNew = whereClauseInsert(pWC, pNewExpr, TERM_VIRTUAL|TERM_DYNAMIC); + testcase( idxNew==0 ); + exprAnalyze(pSrc, pWC, idxNew); + pTerm = &pWC->a[idxTerm]; + markTermAsChild(pWC, idxNew, idxTerm); + } + } +#endif /* SQLITE_OMIT_BETWEEN_OPTIMIZATION */ + +#if !defined(SQLITE_OMIT_OR_OPTIMIZATION) && !defined(SQLITE_OMIT_SUBQUERY) + /* Analyze a term that is composed of two or more subterms connected by + ** an OR operator. + */ + else if( pExpr->op==TK_OR ){ + assert( pWC->op==TK_AND ); + exprAnalyzeOrTerm(pSrc, pWC, idxTerm); + pTerm = &pWC->a[idxTerm]; + } +#endif /* SQLITE_OMIT_OR_OPTIMIZATION */ + +#ifndef SQLITE_OMIT_LIKE_OPTIMIZATION + /* Add constraints to reduce the search space on a LIKE or GLOB + ** operator. + ** + ** A like pattern of the form "x LIKE 'aBc%'" is changed into constraints + ** + ** x>='ABC' AND x<'abd' AND x LIKE 'aBc%' + ** + ** The last character of the prefix "abc" is incremented to form the + ** termination condition "abd". If case is not significant (the default + ** for LIKE) then the lower-bound is made all uppercase and the upper- + ** bound is made all lowercase so that the bounds also work when comparing + ** BLOBs. + */ + if( pWC->op==TK_AND + && isLikeOrGlob(pParse, pExpr, &pStr1, &isComplete, &noCase) + ){ + Expr *pLeft; /* LHS of LIKE/GLOB operator */ + Expr *pStr2; /* Copy of pStr1 - RHS of LIKE/GLOB operator */ + Expr *pNewExpr1; + Expr *pNewExpr2; + int idxNew1; + int idxNew2; + const char *zCollSeqName; /* Name of collating sequence */ + const u16 wtFlags = TERM_LIKEOPT | TERM_VIRTUAL | TERM_DYNAMIC; + + pLeft = pExpr->x.pList->a[1].pExpr; + pStr2 = sqlite3ExprDup(db, pStr1, 0); + + /* Convert the lower bound to upper-case and the upper bound to + ** lower-case (upper-case is less than lower-case in ASCII) so that + ** the range constraints also work for BLOBs + */ + if( noCase && !pParse->db->mallocFailed ){ + int i; + char c; + pTerm->wtFlags |= TERM_LIKE; + for(i=0; (c = pStr1->u.zToken[i])!=0; i++){ + pStr1->u.zToken[i] = sqlite3Toupper(c); + pStr2->u.zToken[i] = sqlite3Tolower(c); + } + } + + if( !db->mallocFailed ){ + u8 c, *pC; /* Last character before the first wildcard */ + pC = (u8*)&pStr2->u.zToken[sqlite3Strlen30(pStr2->u.zToken)-1]; + c = *pC; + if( noCase ){ + /* The point is to increment the last character before the first + ** wildcard. But if we increment '@', that will push it into the + ** alphabetic range where case conversions will mess up the + ** inequality. To avoid this, make sure to also run the full + ** LIKE on all candidate expressions by clearing the isComplete flag + */ + if( c=='A'-1 ) isComplete = 0; + c = sqlite3UpperToLower[c]; + } + *pC = c + 1; + } + zCollSeqName = noCase ? "NOCASE" : "BINARY"; + pNewExpr1 = sqlite3ExprDup(db, pLeft, 0); + pNewExpr1 = sqlite3PExpr(pParse, TK_GE, + sqlite3ExprAddCollateString(pParse,pNewExpr1,zCollSeqName), + pStr1, 0); + transferJoinMarkings(pNewExpr1, pExpr); + idxNew1 = whereClauseInsert(pWC, pNewExpr1, wtFlags); + testcase( idxNew1==0 ); + exprAnalyze(pSrc, pWC, idxNew1); + pNewExpr2 = sqlite3ExprDup(db, pLeft, 0); + pNewExpr2 = sqlite3PExpr(pParse, TK_LT, + sqlite3ExprAddCollateString(pParse,pNewExpr2,zCollSeqName), + pStr2, 0); + transferJoinMarkings(pNewExpr2, pExpr); + idxNew2 = whereClauseInsert(pWC, pNewExpr2, wtFlags); + testcase( idxNew2==0 ); + exprAnalyze(pSrc, pWC, idxNew2); + pTerm = &pWC->a[idxTerm]; + if( isComplete ){ + markTermAsChild(pWC, idxNew1, idxTerm); + markTermAsChild(pWC, idxNew2, idxTerm); + } + } +#endif /* SQLITE_OMIT_LIKE_OPTIMIZATION */ + +#ifndef SQLITE_OMIT_VIRTUALTABLE + /* Add a WO_MATCH auxiliary term to the constraint set if the + ** current expression is of the form: column MATCH expr. + ** This information is used by the xBestIndex methods of + ** virtual tables. The native query optimizer does not attempt + ** to do anything with MATCH functions. + */ + if( isMatchOfColumn(pExpr, &eOp2) ){ + int idxNew; + Expr *pRight, *pLeft; + WhereTerm *pNewTerm; + Bitmask prereqColumn, prereqExpr; + + pRight = pExpr->x.pList->a[0].pExpr; + pLeft = pExpr->x.pList->a[1].pExpr; + prereqExpr = sqlite3WhereExprUsage(pMaskSet, pRight); + prereqColumn = sqlite3WhereExprUsage(pMaskSet, pLeft); + if( (prereqExpr & prereqColumn)==0 ){ + Expr *pNewExpr; + pNewExpr = sqlite3PExpr(pParse, TK_MATCH, + 0, sqlite3ExprDup(db, pRight, 0), 0); + idxNew = whereClauseInsert(pWC, pNewExpr, TERM_VIRTUAL|TERM_DYNAMIC); + testcase( idxNew==0 ); + pNewTerm = &pWC->a[idxNew]; + pNewTerm->prereqRight = prereqExpr; + pNewTerm->leftCursor = pLeft->iTable; + pNewTerm->u.leftColumn = pLeft->iColumn; + pNewTerm->eOperator = WO_MATCH; + pNewTerm->eMatchOp = eOp2; + markTermAsChild(pWC, idxNew, idxTerm); + pTerm = &pWC->a[idxTerm]; + pTerm->wtFlags |= TERM_COPIED; + pNewTerm->prereqAll = pTerm->prereqAll; + } + } +#endif /* SQLITE_OMIT_VIRTUALTABLE */ + +#ifdef SQLITE_ENABLE_STAT3_OR_STAT4 + /* When sqlite_stat3 histogram data is available an operator of the + ** form "x IS NOT NULL" can sometimes be evaluated more efficiently + ** as "x>NULL" if x is not an INTEGER PRIMARY KEY. So construct a + ** virtual term of that form. + ** + ** Note that the virtual term must be tagged with TERM_VNULL. + */ + if( pExpr->op==TK_NOTNULL + && pExpr->pLeft->op==TK_COLUMN + && pExpr->pLeft->iColumn>=0 + && OptimizationEnabled(db, SQLITE_Stat34) + ){ + Expr *pNewExpr; + Expr *pLeft = pExpr->pLeft; + int idxNew; + WhereTerm *pNewTerm; + + pNewExpr = sqlite3PExpr(pParse, TK_GT, + sqlite3ExprDup(db, pLeft, 0), + sqlite3PExpr(pParse, TK_NULL, 0, 0, 0), 0); + + idxNew = whereClauseInsert(pWC, pNewExpr, + TERM_VIRTUAL|TERM_DYNAMIC|TERM_VNULL); + if( idxNew ){ + pNewTerm = &pWC->a[idxNew]; + pNewTerm->prereqRight = 0; + pNewTerm->leftCursor = pLeft->iTable; + pNewTerm->u.leftColumn = pLeft->iColumn; + pNewTerm->eOperator = WO_GT; + markTermAsChild(pWC, idxNew, idxTerm); + pTerm = &pWC->a[idxTerm]; + pTerm->wtFlags |= TERM_COPIED; + pNewTerm->prereqAll = pTerm->prereqAll; + } + } +#endif /* SQLITE_ENABLE_STAT3_OR_STAT4 */ + + /* Prevent ON clause terms of a LEFT JOIN from being used to drive + ** an index for tables to the left of the join. + */ + pTerm->prereqRight |= extraRight; +} + +/*************************************************************************** +** Routines with file scope above. Interface to the rest of the where.c +** subsystem follows. +***************************************************************************/ + +/* +** This routine identifies subexpressions in the WHERE clause where +** each subexpression is separated by the AND operator or some other +** operator specified in the op parameter. The WhereClause structure +** is filled with pointers to subexpressions. For example: +** +** WHERE a=='hello' AND coalesce(b,11)<10 AND (c+12!=d OR c==22) +** \________/ \_______________/ \________________/ +** slot[0] slot[1] slot[2] +** +** The original WHERE clause in pExpr is unaltered. All this routine +** does is make slot[] entries point to substructure within pExpr. +** +** In the previous sentence and in the diagram, "slot[]" refers to +** the WhereClause.a[] array. The slot[] array grows as needed to contain +** all terms of the WHERE clause. +*/ +SQLITE_PRIVATE void sqlite3WhereSplit(WhereClause *pWC, Expr *pExpr, u8 op){ + Expr *pE2 = sqlite3ExprSkipCollate(pExpr); + pWC->op = op; + if( pE2==0 ) return; + if( pE2->op!=op ){ + whereClauseInsert(pWC, pExpr, 0); + }else{ + sqlite3WhereSplit(pWC, pE2->pLeft, op); + sqlite3WhereSplit(pWC, pE2->pRight, op); + } +} + +/* +** Initialize a preallocated WhereClause structure. +*/ +SQLITE_PRIVATE void sqlite3WhereClauseInit( + WhereClause *pWC, /* The WhereClause to be initialized */ + WhereInfo *pWInfo /* The WHERE processing context */ +){ + pWC->pWInfo = pWInfo; + pWC->pOuter = 0; + pWC->nTerm = 0; + pWC->nSlot = ArraySize(pWC->aStatic); + pWC->a = pWC->aStatic; +} + +/* +** Deallocate a WhereClause structure. The WhereClause structure +** itself is not freed. This routine is the inverse of +** sqlite3WhereClauseInit(). +*/ +SQLITE_PRIVATE void sqlite3WhereClauseClear(WhereClause *pWC){ + int i; + WhereTerm *a; + sqlite3 *db = pWC->pWInfo->pParse->db; + for(i=pWC->nTerm-1, a=pWC->a; i>=0; i--, a++){ + if( a->wtFlags & TERM_DYNAMIC ){ + sqlite3ExprDelete(db, a->pExpr); + } + if( a->wtFlags & TERM_ORINFO ){ + whereOrInfoDelete(db, a->u.pOrInfo); + }else if( a->wtFlags & TERM_ANDINFO ){ + whereAndInfoDelete(db, a->u.pAndInfo); + } + } + if( pWC->a!=pWC->aStatic ){ + sqlite3DbFree(db, pWC->a); + } +} + + +/* +** These routines walk (recursively) an expression tree and generate +** a bitmask indicating which tables are used in that expression +** tree. +*/ +SQLITE_PRIVATE Bitmask sqlite3WhereExprUsage(WhereMaskSet *pMaskSet, Expr *p){ + Bitmask mask = 0; + if( p==0 ) return 0; + if( p->op==TK_COLUMN ){ + mask = sqlite3WhereGetMask(pMaskSet, p->iTable); + return mask; + } + mask = sqlite3WhereExprUsage(pMaskSet, p->pRight); + mask |= sqlite3WhereExprUsage(pMaskSet, p->pLeft); + if( ExprHasProperty(p, EP_xIsSelect) ){ + mask |= exprSelectUsage(pMaskSet, p->x.pSelect); + }else{ + mask |= sqlite3WhereExprListUsage(pMaskSet, p->x.pList); + } + return mask; +} +SQLITE_PRIVATE Bitmask sqlite3WhereExprListUsage(WhereMaskSet *pMaskSet, ExprList *pList){ + int i; + Bitmask mask = 0; + if( pList ){ + for(i=0; inExpr; i++){ + mask |= sqlite3WhereExprUsage(pMaskSet, pList->a[i].pExpr); + } + } + return mask; +} + + +/* +** Call exprAnalyze on all terms in a WHERE clause. +** +** Note that exprAnalyze() might add new virtual terms onto the +** end of the WHERE clause. We do not want to analyze these new +** virtual terms, so start analyzing at the end and work forward +** so that the added virtual terms are never processed. +*/ +SQLITE_PRIVATE void sqlite3WhereExprAnalyze( + SrcList *pTabList, /* the FROM clause */ + WhereClause *pWC /* the WHERE clause to be analyzed */ +){ + int i; + for(i=pWC->nTerm-1; i>=0; i--){ + exprAnalyze(pTabList, pWC, i); + } +} + +/* +** For table-valued-functions, transform the function arguments into +** new WHERE clause terms. +** +** Each function argument translates into an equality constraint against +** a HIDDEN column in the table. +*/ +SQLITE_PRIVATE void sqlite3WhereTabFuncArgs( + Parse *pParse, /* Parsing context */ + struct SrcList_item *pItem, /* The FROM clause term to process */ + WhereClause *pWC /* Xfer function arguments to here */ +){ + Table *pTab; + int j, k; + ExprList *pArgs; + Expr *pColRef; + Expr *pTerm; + if( pItem->fg.isTabFunc==0 ) return; + pTab = pItem->pTab; + assert( pTab!=0 ); + pArgs = pItem->u1.pFuncArg; + if( pArgs==0 ) return; + for(j=k=0; jnExpr; j++){ + while( knCol && (pTab->aCol[k].colFlags & COLFLAG_HIDDEN)==0 ){k++;} + if( k>=pTab->nCol ){ + sqlite3ErrorMsg(pParse, "too many arguments on %s() - max %d", + pTab->zName, j); + return; + } + pColRef = sqlite3PExpr(pParse, TK_COLUMN, 0, 0, 0); + if( pColRef==0 ) return; + pColRef->iTable = pItem->iCursor; + pColRef->iColumn = k++; + pColRef->pTab = pTab; + pTerm = sqlite3PExpr(pParse, TK_EQ, pColRef, + sqlite3ExprDup(pParse->db, pArgs->a[j].pExpr, 0), 0); + whereClauseInsert(pWC, pTerm, TERM_DYNAMIC); + } +} + +/************** End of whereexpr.c *******************************************/ +/************** Begin file where.c *******************************************/ +/* +** 2001 September 15 +** +** The author disclaims copyright to this source code. In place of +** a legal notice, here is a blessing: +** +** May you do good and not evil. +** May you find forgiveness for yourself and forgive others. +** May you share freely, never taking more than you give. +** +************************************************************************* +** This module contains C code that generates VDBE code used to process +** the WHERE clause of SQL statements. This module is responsible for +** generating the code that loops through a table looking for applicable +** rows. Indices are selected and used to speed the search when doing +** so is applicable. Because this module is responsible for selecting +** indices, you might also think of this module as the "query optimizer". +*/ +/* #include "sqliteInt.h" */ +/* #include "whereInt.h" */ + +/* Forward declaration of methods */ +static int whereLoopResize(sqlite3*, WhereLoop*, int); + +/* Test variable that can be set to enable WHERE tracing */ +#if defined(SQLITE_TEST) || defined(SQLITE_DEBUG) +/***/ int sqlite3WhereTrace = 0; +#endif + + +/* +** Return the estimated number of output rows from a WHERE clause +*/ +SQLITE_PRIVATE u64 sqlite3WhereOutputRowCount(WhereInfo *pWInfo){ + return sqlite3LogEstToInt(pWInfo->nRowOut); +} + +/* +** Return one of the WHERE_DISTINCT_xxxxx values to indicate how this +** WHERE clause returns outputs for DISTINCT processing. +*/ +SQLITE_PRIVATE int sqlite3WhereIsDistinct(WhereInfo *pWInfo){ + return pWInfo->eDistinct; +} + +/* +** Return TRUE if the WHERE clause returns rows in ORDER BY order. +** Return FALSE if the output needs to be sorted. +*/ +SQLITE_PRIVATE int sqlite3WhereIsOrdered(WhereInfo *pWInfo){ + return pWInfo->nOBSat; +} + +/* +** Return the VDBE address or label to jump to in order to continue +** immediately with the next row of a WHERE clause. +*/ +SQLITE_PRIVATE int sqlite3WhereContinueLabel(WhereInfo *pWInfo){ + assert( pWInfo->iContinue!=0 ); + return pWInfo->iContinue; +} + +/* +** Return the VDBE address or label to jump to in order to break +** out of a WHERE loop. +*/ +SQLITE_PRIVATE int sqlite3WhereBreakLabel(WhereInfo *pWInfo){ + return pWInfo->iBreak; +} + +/* +** Return ONEPASS_OFF (0) if an UPDATE or DELETE statement is unable to +** operate directly on the rowis returned by a WHERE clause. Return +** ONEPASS_SINGLE (1) if the statement can operation directly because only +** a single row is to be changed. Return ONEPASS_MULTI (2) if the one-pass +** optimization can be used on multiple +** +** If the ONEPASS optimization is used (if this routine returns true) +** then also write the indices of open cursors used by ONEPASS +** into aiCur[0] and aiCur[1]. iaCur[0] gets the cursor of the data +** table and iaCur[1] gets the cursor used by an auxiliary index. +** Either value may be -1, indicating that cursor is not used. +** Any cursors returned will have been opened for writing. +** +** aiCur[0] and aiCur[1] both get -1 if the where-clause logic is +** unable to use the ONEPASS optimization. +*/ +SQLITE_PRIVATE int sqlite3WhereOkOnePass(WhereInfo *pWInfo, int *aiCur){ + memcpy(aiCur, pWInfo->aiCurOnePass, sizeof(int)*2); +#ifdef WHERETRACE_ENABLED + if( sqlite3WhereTrace && pWInfo->eOnePass!=ONEPASS_OFF ){ + sqlite3DebugPrintf("%s cursors: %d %d\n", + pWInfo->eOnePass==ONEPASS_SINGLE ? "ONEPASS_SINGLE" : "ONEPASS_MULTI", + aiCur[0], aiCur[1]); + } +#endif + return pWInfo->eOnePass; +} + +/* +** Move the content of pSrc into pDest +*/ +static void whereOrMove(WhereOrSet *pDest, WhereOrSet *pSrc){ + pDest->n = pSrc->n; + memcpy(pDest->a, pSrc->a, pDest->n*sizeof(pDest->a[0])); +} + +/* +** Try to insert a new prerequisite/cost entry into the WhereOrSet pSet. +** +** The new entry might overwrite an existing entry, or it might be +** appended, or it might be discarded. Do whatever is the right thing +** so that pSet keeps the N_OR_COST best entries seen so far. +*/ +static int whereOrInsert( + WhereOrSet *pSet, /* The WhereOrSet to be updated */ + Bitmask prereq, /* Prerequisites of the new entry */ + LogEst rRun, /* Run-cost of the new entry */ + LogEst nOut /* Number of outputs for the new entry */ +){ + u16 i; + WhereOrCost *p; + for(i=pSet->n, p=pSet->a; i>0; i--, p++){ + if( rRun<=p->rRun && (prereq & p->prereq)==prereq ){ + goto whereOrInsert_done; + } + if( p->rRun<=rRun && (p->prereq & prereq)==p->prereq ){ + return 0; + } + } + if( pSet->na[pSet->n++]; + p->nOut = nOut; + }else{ + p = pSet->a; + for(i=1; in; i++){ + if( p->rRun>pSet->a[i].rRun ) p = pSet->a + i; + } + if( p->rRun<=rRun ) return 0; + } +whereOrInsert_done: + p->prereq = prereq; + p->rRun = rRun; + if( p->nOut>nOut ) p->nOut = nOut; + return 1; +} + +/* +** Return the bitmask for the given cursor number. Return 0 if +** iCursor is not in the set. +*/ +SQLITE_PRIVATE Bitmask sqlite3WhereGetMask(WhereMaskSet *pMaskSet, int iCursor){ + int i; + assert( pMaskSet->n<=(int)sizeof(Bitmask)*8 ); + for(i=0; in; i++){ + if( pMaskSet->ix[i]==iCursor ){ + return MASKBIT(i); + } + } + return 0; +} + +/* +** Create a new mask for cursor iCursor. +** +** There is one cursor per table in the FROM clause. The number of +** tables in the FROM clause is limited by a test early in the +** sqlite3WhereBegin() routine. So we know that the pMaskSet->ix[] +** array will never overflow. +*/ +static void createMask(WhereMaskSet *pMaskSet, int iCursor){ + assert( pMaskSet->n < ArraySize(pMaskSet->ix) ); + pMaskSet->ix[pMaskSet->n++] = iCursor; +} + +/* +** Advance to the next WhereTerm that matches according to the criteria +** established when the pScan object was initialized by whereScanInit(). +** Return NULL if there are no more matching WhereTerms. +*/ +static WhereTerm *whereScanNext(WhereScan *pScan){ + int iCur; /* The cursor on the LHS of the term */ + i16 iColumn; /* The column on the LHS of the term. -1 for IPK */ + Expr *pX; /* An expression being tested */ + WhereClause *pWC; /* Shorthand for pScan->pWC */ + WhereTerm *pTerm; /* The term being tested */ + int k = pScan->k; /* Where to start scanning */ + + while( pScan->iEquiv<=pScan->nEquiv ){ + iCur = pScan->aiCur[pScan->iEquiv-1]; + iColumn = pScan->aiColumn[pScan->iEquiv-1]; + if( iColumn==XN_EXPR && pScan->pIdxExpr==0 ) return 0; + while( (pWC = pScan->pWC)!=0 ){ + for(pTerm=pWC->a+k; knTerm; k++, pTerm++){ + if( pTerm->leftCursor==iCur + && pTerm->u.leftColumn==iColumn + && (iColumn!=XN_EXPR + || sqlite3ExprCompare(pTerm->pExpr->pLeft,pScan->pIdxExpr,iCur)==0) + && (pScan->iEquiv<=1 || !ExprHasProperty(pTerm->pExpr, EP_FromJoin)) + ){ + if( (pTerm->eOperator & WO_EQUIV)!=0 + && pScan->nEquivaiCur) + && (pX = sqlite3ExprSkipCollate(pTerm->pExpr->pRight))->op==TK_COLUMN + ){ + int j; + for(j=0; jnEquiv; j++){ + if( pScan->aiCur[j]==pX->iTable + && pScan->aiColumn[j]==pX->iColumn ){ + break; + } + } + if( j==pScan->nEquiv ){ + pScan->aiCur[j] = pX->iTable; + pScan->aiColumn[j] = pX->iColumn; + pScan->nEquiv++; + } + } + if( (pTerm->eOperator & pScan->opMask)!=0 ){ + /* Verify the affinity and collating sequence match */ + if( pScan->zCollName && (pTerm->eOperator & WO_ISNULL)==0 ){ + CollSeq *pColl; + Parse *pParse = pWC->pWInfo->pParse; + pX = pTerm->pExpr; + if( !sqlite3IndexAffinityOk(pX, pScan->idxaff) ){ + continue; + } + assert(pX->pLeft); + pColl = sqlite3BinaryCompareCollSeq(pParse, + pX->pLeft, pX->pRight); + if( pColl==0 ) pColl = pParse->db->pDfltColl; + if( sqlite3StrICmp(pColl->zName, pScan->zCollName) ){ + continue; + } + } + if( (pTerm->eOperator & (WO_EQ|WO_IS))!=0 + && (pX = pTerm->pExpr->pRight)->op==TK_COLUMN + && pX->iTable==pScan->aiCur[0] + && pX->iColumn==pScan->aiColumn[0] + ){ + testcase( pTerm->eOperator & WO_IS ); + continue; + } + pScan->k = k+1; + return pTerm; + } + } + } + pScan->pWC = pScan->pWC->pOuter; + k = 0; + } + pScan->pWC = pScan->pOrigWC; + k = 0; + pScan->iEquiv++; + } + return 0; +} + +/* +** Initialize a WHERE clause scanner object. Return a pointer to the +** first match. Return NULL if there are no matches. +** +** The scanner will be searching the WHERE clause pWC. It will look +** for terms of the form "X " where X is column iColumn of table +** iCur. The must be one of the operators described by opMask. +** +** If the search is for X and the WHERE clause contains terms of the +** form X=Y then this routine might also return terms of the form +** "Y ". The number of levels of transitivity is limited, +** but is enough to handle most commonly occurring SQL statements. +** +** If X is not the INTEGER PRIMARY KEY then X must be compatible with +** index pIdx. +*/ +static WhereTerm *whereScanInit( + WhereScan *pScan, /* The WhereScan object being initialized */ + WhereClause *pWC, /* The WHERE clause to be scanned */ + int iCur, /* Cursor to scan for */ + int iColumn, /* Column to scan for */ + u32 opMask, /* Operator(s) to scan for */ + Index *pIdx /* Must be compatible with this index */ +){ + int j = 0; + + /* memset(pScan, 0, sizeof(*pScan)); */ + pScan->pOrigWC = pWC; + pScan->pWC = pWC; + pScan->pIdxExpr = 0; + if( pIdx ){ + j = iColumn; + iColumn = pIdx->aiColumn[j]; + if( iColumn==XN_EXPR ) pScan->pIdxExpr = pIdx->aColExpr->a[j].pExpr; + } + if( pIdx && iColumn>=0 ){ + pScan->idxaff = pIdx->pTable->aCol[iColumn].affinity; + pScan->zCollName = pIdx->azColl[j]; + }else{ + pScan->idxaff = 0; + pScan->zCollName = 0; + } + pScan->opMask = opMask; + pScan->k = 0; + pScan->aiCur[0] = iCur; + pScan->aiColumn[0] = iColumn; + pScan->nEquiv = 1; + pScan->iEquiv = 1; + return whereScanNext(pScan); +} + +/* +** Search for a term in the WHERE clause that is of the form "X " +** where X is a reference to the iColumn of table iCur and is one of +** the WO_xx operator codes specified by the op parameter. +** Return a pointer to the term. Return 0 if not found. +** +** If pIdx!=0 then search for terms matching the iColumn-th column of pIdx +** rather than the iColumn-th column of table iCur. +** +** The term returned might by Y= if there is another constraint in +** the WHERE clause that specifies that X=Y. Any such constraints will be +** identified by the WO_EQUIV bit in the pTerm->eOperator field. The +** aiCur[]/iaColumn[] arrays hold X and all its equivalents. There are 11 +** slots in aiCur[]/aiColumn[] so that means we can look for X plus up to 10 +** other equivalent values. Hence a search for X will return if X=A1 +** and A1=A2 and A2=A3 and ... and A9=A10 and A10=. +** +** If there are multiple terms in the WHERE clause of the form "X " +** then try for the one with no dependencies on - in other words where +** is a constant expression of some kind. Only return entries of +** the form "X Y" where Y is a column in another table if no terms of +** the form "X " exist. If no terms with a constant RHS +** exist, try to return a term that does not use WO_EQUIV. +*/ +SQLITE_PRIVATE WhereTerm *sqlite3WhereFindTerm( + WhereClause *pWC, /* The WHERE clause to be searched */ + int iCur, /* Cursor number of LHS */ + int iColumn, /* Column number of LHS */ + Bitmask notReady, /* RHS must not overlap with this mask */ + u32 op, /* Mask of WO_xx values describing operator */ + Index *pIdx /* Must be compatible with this index, if not NULL */ +){ + WhereTerm *pResult = 0; + WhereTerm *p; + WhereScan scan; + + p = whereScanInit(&scan, pWC, iCur, iColumn, op, pIdx); + op &= WO_EQ|WO_IS; + while( p ){ + if( (p->prereqRight & notReady)==0 ){ + if( p->prereqRight==0 && (p->eOperator&op)!=0 ){ + testcase( p->eOperator & WO_IS ); + return p; + } + if( pResult==0 ) pResult = p; + } + p = whereScanNext(&scan); + } + return pResult; +} + +/* +** This function searches pList for an entry that matches the iCol-th column +** of index pIdx. +** +** If such an expression is found, its index in pList->a[] is returned. If +** no expression is found, -1 is returned. +*/ +static int findIndexCol( + Parse *pParse, /* Parse context */ + ExprList *pList, /* Expression list to search */ + int iBase, /* Cursor for table associated with pIdx */ + Index *pIdx, /* Index to match column of */ + int iCol /* Column of index to match */ +){ + int i; + const char *zColl = pIdx->azColl[iCol]; + + for(i=0; inExpr; i++){ + Expr *p = sqlite3ExprSkipCollate(pList->a[i].pExpr); + if( p->op==TK_COLUMN + && p->iColumn==pIdx->aiColumn[iCol] + && p->iTable==iBase + ){ + CollSeq *pColl = sqlite3ExprCollSeq(pParse, pList->a[i].pExpr); + if( pColl && 0==sqlite3StrICmp(pColl->zName, zColl) ){ + return i; + } + } + } + + return -1; +} + +/* +** Return TRUE if the iCol-th column of index pIdx is NOT NULL +*/ +static int indexColumnNotNull(Index *pIdx, int iCol){ + int j; + assert( pIdx!=0 ); + assert( iCol>=0 && iColnColumn ); + j = pIdx->aiColumn[iCol]; + if( j>=0 ){ + return pIdx->pTable->aCol[j].notNull; + }else if( j==(-1) ){ + return 1; + }else{ + assert( j==(-2) ); + return 0; /* Assume an indexed expression can always yield a NULL */ + + } +} + +/* +** Return true if the DISTINCT expression-list passed as the third argument +** is redundant. +** +** A DISTINCT list is redundant if any subset of the columns in the +** DISTINCT list are collectively unique and individually non-null. +*/ +static int isDistinctRedundant( + Parse *pParse, /* Parsing context */ + SrcList *pTabList, /* The FROM clause */ + WhereClause *pWC, /* The WHERE clause */ + ExprList *pDistinct /* The result set that needs to be DISTINCT */ +){ + Table *pTab; + Index *pIdx; + int i; + int iBase; + + /* If there is more than one table or sub-select in the FROM clause of + ** this query, then it will not be possible to show that the DISTINCT + ** clause is redundant. */ + if( pTabList->nSrc!=1 ) return 0; + iBase = pTabList->a[0].iCursor; + pTab = pTabList->a[0].pTab; + + /* If any of the expressions is an IPK column on table iBase, then return + ** true. Note: The (p->iTable==iBase) part of this test may be false if the + ** current SELECT is a correlated sub-query. + */ + for(i=0; inExpr; i++){ + Expr *p = sqlite3ExprSkipCollate(pDistinct->a[i].pExpr); + if( p->op==TK_COLUMN && p->iTable==iBase && p->iColumn<0 ) return 1; + } + + /* Loop through all indices on the table, checking each to see if it makes + ** the DISTINCT qualifier redundant. It does so if: + ** + ** 1. The index is itself UNIQUE, and + ** + ** 2. All of the columns in the index are either part of the pDistinct + ** list, or else the WHERE clause contains a term of the form "col=X", + ** where X is a constant value. The collation sequences of the + ** comparison and select-list expressions must match those of the index. + ** + ** 3. All of those index columns for which the WHERE clause does not + ** contain a "col=X" term are subject to a NOT NULL constraint. + */ + for(pIdx=pTab->pIndex; pIdx; pIdx=pIdx->pNext){ + if( !IsUniqueIndex(pIdx) ) continue; + for(i=0; inKeyCol; i++){ + if( 0==sqlite3WhereFindTerm(pWC, iBase, i, ~(Bitmask)0, WO_EQ, pIdx) ){ + if( findIndexCol(pParse, pDistinct, iBase, pIdx, i)<0 ) break; + if( indexColumnNotNull(pIdx, i)==0 ) break; + } + } + if( i==pIdx->nKeyCol ){ + /* This index implies that the DISTINCT qualifier is redundant. */ + return 1; + } + } + + return 0; +} + + +/* +** Estimate the logarithm of the input value to base 2. +*/ +static LogEst estLog(LogEst N){ + return N<=10 ? 0 : sqlite3LogEst(N) - 33; +} + +/* +** Convert OP_Column opcodes to OP_Copy in previously generated code. +** +** This routine runs over generated VDBE code and translates OP_Column +** opcodes into OP_Copy when the table is being accessed via co-routine +** instead of via table lookup. +** +** If the bIncrRowid parameter is 0, then any OP_Rowid instructions on +** cursor iTabCur are transformed into OP_Null. Or, if bIncrRowid is non-zero, +** then each OP_Rowid is transformed into an instruction to increment the +** value stored in its output register. +*/ +static void translateColumnToCopy( + Vdbe *v, /* The VDBE containing code to translate */ + int iStart, /* Translate from this opcode to the end */ + int iTabCur, /* OP_Column/OP_Rowid references to this table */ + int iRegister, /* The first column is in this register */ + int bIncrRowid /* If non-zero, transform OP_rowid to OP_AddImm(1) */ +){ + VdbeOp *pOp = sqlite3VdbeGetOp(v, iStart); + int iEnd = sqlite3VdbeCurrentAddr(v); + for(; iStartp1!=iTabCur ) continue; + if( pOp->opcode==OP_Column ){ + pOp->opcode = OP_Copy; + pOp->p1 = pOp->p2 + iRegister; + pOp->p2 = pOp->p3; + pOp->p3 = 0; + }else if( pOp->opcode==OP_Rowid ){ + if( bIncrRowid ){ + /* Increment the value stored in the P2 operand of the OP_Rowid. */ + pOp->opcode = OP_AddImm; + pOp->p1 = pOp->p2; + pOp->p2 = 1; + }else{ + pOp->opcode = OP_Null; + pOp->p1 = 0; + pOp->p3 = 0; + } + } + } +} + +/* +** Two routines for printing the content of an sqlite3_index_info +** structure. Used for testing and debugging only. If neither +** SQLITE_TEST or SQLITE_DEBUG are defined, then these routines +** are no-ops. +*/ +#if !defined(SQLITE_OMIT_VIRTUALTABLE) && defined(WHERETRACE_ENABLED) +static void TRACE_IDX_INPUTS(sqlite3_index_info *p){ + int i; + if( !sqlite3WhereTrace ) return; + for(i=0; inConstraint; i++){ + sqlite3DebugPrintf(" constraint[%d]: col=%d termid=%d op=%d usabled=%d\n", + i, + p->aConstraint[i].iColumn, + p->aConstraint[i].iTermOffset, + p->aConstraint[i].op, + p->aConstraint[i].usable); + } + for(i=0; inOrderBy; i++){ + sqlite3DebugPrintf(" orderby[%d]: col=%d desc=%d\n", + i, + p->aOrderBy[i].iColumn, + p->aOrderBy[i].desc); + } +} +static void TRACE_IDX_OUTPUTS(sqlite3_index_info *p){ + int i; + if( !sqlite3WhereTrace ) return; + for(i=0; inConstraint; i++){ + sqlite3DebugPrintf(" usage[%d]: argvIdx=%d omit=%d\n", + i, + p->aConstraintUsage[i].argvIndex, + p->aConstraintUsage[i].omit); + } + sqlite3DebugPrintf(" idxNum=%d\n", p->idxNum); + sqlite3DebugPrintf(" idxStr=%s\n", p->idxStr); + sqlite3DebugPrintf(" orderByConsumed=%d\n", p->orderByConsumed); + sqlite3DebugPrintf(" estimatedCost=%g\n", p->estimatedCost); + sqlite3DebugPrintf(" estimatedRows=%lld\n", p->estimatedRows); +} +#else +#define TRACE_IDX_INPUTS(A) +#define TRACE_IDX_OUTPUTS(A) +#endif + +#ifndef SQLITE_OMIT_AUTOMATIC_INDEX +/* +** Return TRUE if the WHERE clause term pTerm is of a form where it +** could be used with an index to access pSrc, assuming an appropriate +** index existed. +*/ +static int termCanDriveIndex( + WhereTerm *pTerm, /* WHERE clause term to check */ + struct SrcList_item *pSrc, /* Table we are trying to access */ + Bitmask notReady /* Tables in outer loops of the join */ +){ + char aff; + if( pTerm->leftCursor!=pSrc->iCursor ) return 0; + if( (pTerm->eOperator & (WO_EQ|WO_IS))==0 ) return 0; + if( (pTerm->prereqRight & notReady)!=0 ) return 0; + if( pTerm->u.leftColumn<0 ) return 0; + aff = pSrc->pTab->aCol[pTerm->u.leftColumn].affinity; + if( !sqlite3IndexAffinityOk(pTerm->pExpr, aff) ) return 0; + testcase( pTerm->pExpr->op==TK_IS ); + return 1; +} +#endif + + +#ifndef SQLITE_OMIT_AUTOMATIC_INDEX +/* +** Generate code to construct the Index object for an automatic index +** and to set up the WhereLevel object pLevel so that the code generator +** makes use of the automatic index. +*/ +static void constructAutomaticIndex( + Parse *pParse, /* The parsing context */ + WhereClause *pWC, /* The WHERE clause */ + struct SrcList_item *pSrc, /* The FROM clause term to get the next index */ + Bitmask notReady, /* Mask of cursors that are not available */ + WhereLevel *pLevel /* Write new index here */ +){ + int nKeyCol; /* Number of columns in the constructed index */ + WhereTerm *pTerm; /* A single term of the WHERE clause */ + WhereTerm *pWCEnd; /* End of pWC->a[] */ + Index *pIdx; /* Object describing the transient index */ + Vdbe *v; /* Prepared statement under construction */ + int addrInit; /* Address of the initialization bypass jump */ + Table *pTable; /* The table being indexed */ + int addrTop; /* Top of the index fill loop */ + int regRecord; /* Register holding an index record */ + int n; /* Column counter */ + int i; /* Loop counter */ + int mxBitCol; /* Maximum column in pSrc->colUsed */ + CollSeq *pColl; /* Collating sequence to on a column */ + WhereLoop *pLoop; /* The Loop object */ + char *zNotUsed; /* Extra space on the end of pIdx */ + Bitmask idxCols; /* Bitmap of columns used for indexing */ + Bitmask extraCols; /* Bitmap of additional columns */ + u8 sentWarning = 0; /* True if a warnning has been issued */ + Expr *pPartial = 0; /* Partial Index Expression */ + int iContinue = 0; /* Jump here to skip excluded rows */ + struct SrcList_item *pTabItem; /* FROM clause term being indexed */ + int addrCounter = 0; /* Address where integer counter is initialized */ + int regBase; /* Array of registers where record is assembled */ + + /* Generate code to skip over the creation and initialization of the + ** transient index on 2nd and subsequent iterations of the loop. */ + v = pParse->pVdbe; + assert( v!=0 ); + addrInit = sqlite3CodeOnce(pParse); VdbeCoverage(v); + + /* Count the number of columns that will be added to the index + ** and used to match WHERE clause constraints */ + nKeyCol = 0; + pTable = pSrc->pTab; + pWCEnd = &pWC->a[pWC->nTerm]; + pLoop = pLevel->pWLoop; + idxCols = 0; + for(pTerm=pWC->a; pTermpExpr; + assert( !ExprHasProperty(pExpr, EP_FromJoin) /* prereq always non-zero */ + || pExpr->iRightJoinTable!=pSrc->iCursor /* for the right-hand */ + || pLoop->prereq!=0 ); /* table of a LEFT JOIN */ + if( pLoop->prereq==0 + && (pTerm->wtFlags & TERM_VIRTUAL)==0 + && !ExprHasProperty(pExpr, EP_FromJoin) + && sqlite3ExprIsTableConstant(pExpr, pSrc->iCursor) ){ + pPartial = sqlite3ExprAnd(pParse->db, pPartial, + sqlite3ExprDup(pParse->db, pExpr, 0)); + } + if( termCanDriveIndex(pTerm, pSrc, notReady) ){ + int iCol = pTerm->u.leftColumn; + Bitmask cMask = iCol>=BMS ? MASKBIT(BMS-1) : MASKBIT(iCol); + testcase( iCol==BMS ); + testcase( iCol==BMS-1 ); + if( !sentWarning ){ + sqlite3_log(SQLITE_WARNING_AUTOINDEX, + "automatic index on %s(%s)", pTable->zName, + pTable->aCol[iCol].zName); + sentWarning = 1; + } + if( (idxCols & cMask)==0 ){ + if( whereLoopResize(pParse->db, pLoop, nKeyCol+1) ){ + goto end_auto_index_create; + } + pLoop->aLTerm[nKeyCol++] = pTerm; + idxCols |= cMask; + } + } + } + assert( nKeyCol>0 ); + pLoop->u.btree.nEq = pLoop->nLTerm = nKeyCol; + pLoop->wsFlags = WHERE_COLUMN_EQ | WHERE_IDX_ONLY | WHERE_INDEXED + | WHERE_AUTO_INDEX; + + /* Count the number of additional columns needed to create a + ** covering index. A "covering index" is an index that contains all + ** columns that are needed by the query. With a covering index, the + ** original table never needs to be accessed. Automatic indices must + ** be a covering index because the index will not be updated if the + ** original table changes and the index and table cannot both be used + ** if they go out of sync. + */ + extraCols = pSrc->colUsed & (~idxCols | MASKBIT(BMS-1)); + mxBitCol = MIN(BMS-1,pTable->nCol); + testcase( pTable->nCol==BMS-1 ); + testcase( pTable->nCol==BMS-2 ); + for(i=0; icolUsed & MASKBIT(BMS-1) ){ + nKeyCol += pTable->nCol - BMS + 1; + } + + /* Construct the Index object to describe this index */ + pIdx = sqlite3AllocateIndexObject(pParse->db, nKeyCol+1, 0, &zNotUsed); + if( pIdx==0 ) goto end_auto_index_create; + pLoop->u.btree.pIndex = pIdx; + pIdx->zName = "auto-index"; + pIdx->pTable = pTable; + n = 0; + idxCols = 0; + for(pTerm=pWC->a; pTermu.leftColumn; + Bitmask cMask = iCol>=BMS ? MASKBIT(BMS-1) : MASKBIT(iCol); + testcase( iCol==BMS-1 ); + testcase( iCol==BMS ); + if( (idxCols & cMask)==0 ){ + Expr *pX = pTerm->pExpr; + idxCols |= cMask; + pIdx->aiColumn[n] = pTerm->u.leftColumn; + pColl = sqlite3BinaryCompareCollSeq(pParse, pX->pLeft, pX->pRight); + pIdx->azColl[n] = pColl ? pColl->zName : sqlite3StrBINARY; + n++; + } + } + } + assert( (u32)n==pLoop->u.btree.nEq ); + + /* Add additional columns needed to make the automatic index into + ** a covering index */ + for(i=0; iaiColumn[n] = i; + pIdx->azColl[n] = sqlite3StrBINARY; + n++; + } + } + if( pSrc->colUsed & MASKBIT(BMS-1) ){ + for(i=BMS-1; inCol; i++){ + pIdx->aiColumn[n] = i; + pIdx->azColl[n] = sqlite3StrBINARY; + n++; + } + } + assert( n==nKeyCol ); + pIdx->aiColumn[n] = XN_ROWID; + pIdx->azColl[n] = sqlite3StrBINARY; + + /* Create the automatic index */ + assert( pLevel->iIdxCur>=0 ); + pLevel->iIdxCur = pParse->nTab++; + sqlite3VdbeAddOp2(v, OP_OpenAutoindex, pLevel->iIdxCur, nKeyCol+1); + sqlite3VdbeSetP4KeyInfo(pParse, pIdx); + VdbeComment((v, "for %s", pTable->zName)); + + /* Fill the automatic index with content */ + sqlite3ExprCachePush(pParse); + pTabItem = &pWC->pWInfo->pTabList->a[pLevel->iFrom]; + if( pTabItem->fg.viaCoroutine ){ + int regYield = pTabItem->regReturn; + addrCounter = sqlite3VdbeAddOp2(v, OP_Integer, 0, 0); + sqlite3VdbeAddOp3(v, OP_InitCoroutine, regYield, 0, pTabItem->addrFillSub); + addrTop = sqlite3VdbeAddOp1(v, OP_Yield, regYield); + VdbeCoverage(v); + VdbeComment((v, "next row of \"%s\"", pTabItem->pTab->zName)); + }else{ + addrTop = sqlite3VdbeAddOp1(v, OP_Rewind, pLevel->iTabCur); VdbeCoverage(v); + } + if( pPartial ){ + iContinue = sqlite3VdbeMakeLabel(v); + sqlite3ExprIfFalse(pParse, pPartial, iContinue, SQLITE_JUMPIFNULL); + pLoop->wsFlags |= WHERE_PARTIALIDX; + } + regRecord = sqlite3GetTempReg(pParse); + regBase = sqlite3GenerateIndexKey( + pParse, pIdx, pLevel->iTabCur, regRecord, 0, 0, 0, 0 + ); + sqlite3VdbeAddOp2(v, OP_IdxInsert, pLevel->iIdxCur, regRecord); + sqlite3VdbeChangeP5(v, OPFLAG_USESEEKRESULT); + if( pPartial ) sqlite3VdbeResolveLabel(v, iContinue); + if( pTabItem->fg.viaCoroutine ){ + sqlite3VdbeChangeP2(v, addrCounter, regBase+n); + translateColumnToCopy(v, addrTop, pLevel->iTabCur, pTabItem->regResult, 1); + sqlite3VdbeGoto(v, addrTop); + pTabItem->fg.viaCoroutine = 0; + }else{ + sqlite3VdbeAddOp2(v, OP_Next, pLevel->iTabCur, addrTop+1); VdbeCoverage(v); + } + sqlite3VdbeChangeP5(v, SQLITE_STMTSTATUS_AUTOINDEX); + sqlite3VdbeJumpHere(v, addrTop); + sqlite3ReleaseTempReg(pParse, regRecord); + sqlite3ExprCachePop(pParse); + + /* Jump here when skipping the initialization */ + sqlite3VdbeJumpHere(v, addrInit); + +end_auto_index_create: + sqlite3ExprDelete(pParse->db, pPartial); +} +#endif /* SQLITE_OMIT_AUTOMATIC_INDEX */ + +#ifndef SQLITE_OMIT_VIRTUALTABLE +/* +** Allocate and populate an sqlite3_index_info structure. It is the +** responsibility of the caller to eventually release the structure +** by passing the pointer returned by this function to sqlite3_free(). +*/ +static sqlite3_index_info *allocateIndexInfo( + Parse *pParse, + WhereClause *pWC, + Bitmask mUnusable, /* Ignore terms with these prereqs */ + struct SrcList_item *pSrc, + ExprList *pOrderBy +){ + int i, j; + int nTerm; + struct sqlite3_index_constraint *pIdxCons; + struct sqlite3_index_orderby *pIdxOrderBy; + struct sqlite3_index_constraint_usage *pUsage; + WhereTerm *pTerm; + int nOrderBy; + sqlite3_index_info *pIdxInfo; + + /* Count the number of possible WHERE clause constraints referring + ** to this virtual table */ + for(i=nTerm=0, pTerm=pWC->a; inTerm; i++, pTerm++){ + if( pTerm->leftCursor != pSrc->iCursor ) continue; + if( pTerm->prereqRight & mUnusable ) continue; + assert( IsPowerOfTwo(pTerm->eOperator & ~WO_EQUIV) ); + testcase( pTerm->eOperator & WO_IN ); + testcase( pTerm->eOperator & WO_ISNULL ); + testcase( pTerm->eOperator & WO_IS ); + testcase( pTerm->eOperator & WO_ALL ); + if( (pTerm->eOperator & ~(WO_ISNULL|WO_EQUIV|WO_IS))==0 ) continue; + if( pTerm->wtFlags & TERM_VNULL ) continue; + assert( pTerm->u.leftColumn>=(-1) ); + nTerm++; + } + + /* If the ORDER BY clause contains only columns in the current + ** virtual table then allocate space for the aOrderBy part of + ** the sqlite3_index_info structure. + */ + nOrderBy = 0; + if( pOrderBy ){ + int n = pOrderBy->nExpr; + for(i=0; ia[i].pExpr; + if( pExpr->op!=TK_COLUMN || pExpr->iTable!=pSrc->iCursor ) break; + } + if( i==n){ + nOrderBy = n; + } + } + + /* Allocate the sqlite3_index_info structure + */ + pIdxInfo = sqlite3DbMallocZero(pParse->db, sizeof(*pIdxInfo) + + (sizeof(*pIdxCons) + sizeof(*pUsage))*nTerm + + sizeof(*pIdxOrderBy)*nOrderBy ); + if( pIdxInfo==0 ){ + sqlite3ErrorMsg(pParse, "out of memory"); + return 0; + } + + /* Initialize the structure. The sqlite3_index_info structure contains + ** many fields that are declared "const" to prevent xBestIndex from + ** changing them. We have to do some funky casting in order to + ** initialize those fields. + */ + pIdxCons = (struct sqlite3_index_constraint*)&pIdxInfo[1]; + pIdxOrderBy = (struct sqlite3_index_orderby*)&pIdxCons[nTerm]; + pUsage = (struct sqlite3_index_constraint_usage*)&pIdxOrderBy[nOrderBy]; + *(int*)&pIdxInfo->nConstraint = nTerm; + *(int*)&pIdxInfo->nOrderBy = nOrderBy; + *(struct sqlite3_index_constraint**)&pIdxInfo->aConstraint = pIdxCons; + *(struct sqlite3_index_orderby**)&pIdxInfo->aOrderBy = pIdxOrderBy; + *(struct sqlite3_index_constraint_usage**)&pIdxInfo->aConstraintUsage = + pUsage; + + for(i=j=0, pTerm=pWC->a; inTerm; i++, pTerm++){ + u8 op; + if( pTerm->leftCursor != pSrc->iCursor ) continue; + if( pTerm->prereqRight & mUnusable ) continue; + assert( IsPowerOfTwo(pTerm->eOperator & ~WO_EQUIV) ); + testcase( pTerm->eOperator & WO_IN ); + testcase( pTerm->eOperator & WO_IS ); + testcase( pTerm->eOperator & WO_ISNULL ); + testcase( pTerm->eOperator & WO_ALL ); + if( (pTerm->eOperator & ~(WO_ISNULL|WO_EQUIV|WO_IS))==0 ) continue; + if( pTerm->wtFlags & TERM_VNULL ) continue; + assert( pTerm->u.leftColumn>=(-1) ); + pIdxCons[j].iColumn = pTerm->u.leftColumn; + pIdxCons[j].iTermOffset = i; + op = (u8)pTerm->eOperator & WO_ALL; + if( op==WO_IN ) op = WO_EQ; + if( op==WO_MATCH ){ + op = pTerm->eMatchOp; + } + pIdxCons[j].op = op; + /* The direct assignment in the previous line is possible only because + ** the WO_ and SQLITE_INDEX_CONSTRAINT_ codes are identical. The + ** following asserts verify this fact. */ + assert( WO_EQ==SQLITE_INDEX_CONSTRAINT_EQ ); + assert( WO_LT==SQLITE_INDEX_CONSTRAINT_LT ); + assert( WO_LE==SQLITE_INDEX_CONSTRAINT_LE ); + assert( WO_GT==SQLITE_INDEX_CONSTRAINT_GT ); + assert( WO_GE==SQLITE_INDEX_CONSTRAINT_GE ); + assert( WO_MATCH==SQLITE_INDEX_CONSTRAINT_MATCH ); + assert( pTerm->eOperator & (WO_IN|WO_EQ|WO_LT|WO_LE|WO_GT|WO_GE|WO_MATCH) ); + j++; + } + for(i=0; ia[i].pExpr; + pIdxOrderBy[i].iColumn = pExpr->iColumn; + pIdxOrderBy[i].desc = pOrderBy->a[i].sortOrder; + } + + return pIdxInfo; +} + +/* +** The table object reference passed as the second argument to this function +** must represent a virtual table. This function invokes the xBestIndex() +** method of the virtual table with the sqlite3_index_info object that +** comes in as the 3rd argument to this function. +** +** If an error occurs, pParse is populated with an error message and a +** non-zero value is returned. Otherwise, 0 is returned and the output +** part of the sqlite3_index_info structure is left populated. +** +** Whether or not an error is returned, it is the responsibility of the +** caller to eventually free p->idxStr if p->needToFreeIdxStr indicates +** that this is required. +*/ +static int vtabBestIndex(Parse *pParse, Table *pTab, sqlite3_index_info *p){ + sqlite3_vtab *pVtab = sqlite3GetVTable(pParse->db, pTab)->pVtab; + int i; + int rc; + + TRACE_IDX_INPUTS(p); + rc = pVtab->pModule->xBestIndex(pVtab, p); + TRACE_IDX_OUTPUTS(p); + + if( rc!=SQLITE_OK ){ + if( rc==SQLITE_NOMEM ){ + pParse->db->mallocFailed = 1; + }else if( !pVtab->zErrMsg ){ + sqlite3ErrorMsg(pParse, "%s", sqlite3ErrStr(rc)); + }else{ + sqlite3ErrorMsg(pParse, "%s", pVtab->zErrMsg); + } + } + sqlite3_free(pVtab->zErrMsg); + pVtab->zErrMsg = 0; + + for(i=0; inConstraint; i++){ + if( !p->aConstraint[i].usable && p->aConstraintUsage[i].argvIndex>0 ){ + sqlite3ErrorMsg(pParse, + "table %s: xBestIndex returned an invalid plan", pTab->zName); + } + } + + return pParse->nErr; +} +#endif /* !defined(SQLITE_OMIT_VIRTUALTABLE) */ + +#ifdef SQLITE_ENABLE_STAT3_OR_STAT4 +/* +** Estimate the location of a particular key among all keys in an +** index. Store the results in aStat as follows: +** +** aStat[0] Est. number of rows less than pRec +** aStat[1] Est. number of rows equal to pRec +** +** Return the index of the sample that is the smallest sample that +** is greater than or equal to pRec. Note that this index is not an index +** into the aSample[] array - it is an index into a virtual set of samples +** based on the contents of aSample[] and the number of fields in record +** pRec. +*/ +static int whereKeyStats( + Parse *pParse, /* Database connection */ + Index *pIdx, /* Index to consider domain of */ + UnpackedRecord *pRec, /* Vector of values to consider */ + int roundUp, /* Round up if true. Round down if false */ + tRowcnt *aStat /* OUT: stats written here */ +){ + IndexSample *aSample = pIdx->aSample; + int iCol; /* Index of required stats in anEq[] etc. */ + int i; /* Index of first sample >= pRec */ + int iSample; /* Smallest sample larger than or equal to pRec */ + int iMin = 0; /* Smallest sample not yet tested */ + int iTest; /* Next sample to test */ + int res; /* Result of comparison operation */ + int nField; /* Number of fields in pRec */ + tRowcnt iLower = 0; /* anLt[] + anEq[] of largest sample pRec is > */ + +#ifndef SQLITE_DEBUG + UNUSED_PARAMETER( pParse ); +#endif + assert( pRec!=0 ); + assert( pIdx->nSample>0 ); + assert( pRec->nField>0 && pRec->nField<=pIdx->nSampleCol ); + + /* Do a binary search to find the first sample greater than or equal + ** to pRec. If pRec contains a single field, the set of samples to search + ** is simply the aSample[] array. If the samples in aSample[] contain more + ** than one fields, all fields following the first are ignored. + ** + ** If pRec contains N fields, where N is more than one, then as well as the + ** samples in aSample[] (truncated to N fields), the search also has to + ** consider prefixes of those samples. For example, if the set of samples + ** in aSample is: + ** + ** aSample[0] = (a, 5) + ** aSample[1] = (a, 10) + ** aSample[2] = (b, 5) + ** aSample[3] = (c, 100) + ** aSample[4] = (c, 105) + ** + ** Then the search space should ideally be the samples above and the + ** unique prefixes [a], [b] and [c]. But since that is hard to organize, + ** the code actually searches this set: + ** + ** 0: (a) + ** 1: (a, 5) + ** 2: (a, 10) + ** 3: (a, 10) + ** 4: (b) + ** 5: (b, 5) + ** 6: (c) + ** 7: (c, 100) + ** 8: (c, 105) + ** 9: (c, 105) + ** + ** For each sample in the aSample[] array, N samples are present in the + ** effective sample array. In the above, samples 0 and 1 are based on + ** sample aSample[0]. Samples 2 and 3 on aSample[1] etc. + ** + ** Often, sample i of each block of N effective samples has (i+1) fields. + ** Except, each sample may be extended to ensure that it is greater than or + ** equal to the previous sample in the array. For example, in the above, + ** sample 2 is the first sample of a block of N samples, so at first it + ** appears that it should be 1 field in size. However, that would make it + ** smaller than sample 1, so the binary search would not work. As a result, + ** it is extended to two fields. The duplicates that this creates do not + ** cause any problems. + */ + nField = pRec->nField; + iCol = 0; + iSample = pIdx->nSample * nField; + do{ + int iSamp; /* Index in aSample[] of test sample */ + int n; /* Number of fields in test sample */ + + iTest = (iMin+iSample)/2; + iSamp = iTest / nField; + if( iSamp>0 ){ + /* The proposed effective sample is a prefix of sample aSample[iSamp]. + ** Specifically, the shortest prefix of at least (1 + iTest%nField) + ** fields that is greater than the previous effective sample. */ + for(n=(iTest % nField) + 1; nnField = n; + res = sqlite3VdbeRecordCompare(aSample[iSamp].n, aSample[iSamp].p, pRec); + if( res<0 ){ + iLower = aSample[iSamp].anLt[n-1] + aSample[iSamp].anEq[n-1]; + iMin = iTest+1; + }else if( res==0 && ndb->mallocFailed==0 ){ + if( res==0 ){ + /* If (res==0) is true, then pRec must be equal to sample i. */ + assert( inSample ); + assert( iCol==nField-1 ); + pRec->nField = nField; + assert( 0==sqlite3VdbeRecordCompare(aSample[i].n, aSample[i].p, pRec) + || pParse->db->mallocFailed + ); + }else{ + /* Unless i==pIdx->nSample, indicating that pRec is larger than + ** all samples in the aSample[] array, pRec must be smaller than the + ** (iCol+1) field prefix of sample i. */ + assert( i<=pIdx->nSample && i>=0 ); + pRec->nField = iCol+1; + assert( i==pIdx->nSample + || sqlite3VdbeRecordCompare(aSample[i].n, aSample[i].p, pRec)>0 + || pParse->db->mallocFailed ); + + /* if i==0 and iCol==0, then record pRec is smaller than all samples + ** in the aSample[] array. Otherwise, if (iCol>0) then pRec must + ** be greater than or equal to the (iCol) field prefix of sample i. + ** If (i>0), then pRec must also be greater than sample (i-1). */ + if( iCol>0 ){ + pRec->nField = iCol; + assert( sqlite3VdbeRecordCompare(aSample[i].n, aSample[i].p, pRec)<=0 + || pParse->db->mallocFailed ); + } + if( i>0 ){ + pRec->nField = nField; + assert( sqlite3VdbeRecordCompare(aSample[i-1].n, aSample[i-1].p, pRec)<0 + || pParse->db->mallocFailed ); + } + } + } +#endif /* ifdef SQLITE_DEBUG */ + + if( res==0 ){ + /* Record pRec is equal to sample i */ + assert( iCol==nField-1 ); + aStat[0] = aSample[i].anLt[iCol]; + aStat[1] = aSample[i].anEq[iCol]; + }else{ + /* At this point, the (iCol+1) field prefix of aSample[i] is the first + ** sample that is greater than pRec. Or, if i==pIdx->nSample then pRec + ** is larger than all samples in the array. */ + tRowcnt iUpper, iGap; + if( i>=pIdx->nSample ){ + iUpper = sqlite3LogEstToInt(pIdx->aiRowLogEst[0]); + }else{ + iUpper = aSample[i].anLt[iCol]; + } + + if( iLower>=iUpper ){ + iGap = 0; + }else{ + iGap = iUpper - iLower; + } + if( roundUp ){ + iGap = (iGap*2)/3; + }else{ + iGap = iGap/3; + } + aStat[0] = iLower + iGap; + aStat[1] = pIdx->aAvgEq[iCol]; + } + + /* Restore the pRec->nField value before returning. */ + pRec->nField = nField; + return i; +} +#endif /* SQLITE_ENABLE_STAT3_OR_STAT4 */ + +/* +** If it is not NULL, pTerm is a term that provides an upper or lower +** bound on a range scan. Without considering pTerm, it is estimated +** that the scan will visit nNew rows. This function returns the number +** estimated to be visited after taking pTerm into account. +** +** If the user explicitly specified a likelihood() value for this term, +** then the return value is the likelihood multiplied by the number of +** input rows. Otherwise, this function assumes that an "IS NOT NULL" term +** has a likelihood of 0.50, and any other term a likelihood of 0.25. +*/ +static LogEst whereRangeAdjust(WhereTerm *pTerm, LogEst nNew){ + LogEst nRet = nNew; + if( pTerm ){ + if( pTerm->truthProb<=0 ){ + nRet += pTerm->truthProb; + }else if( (pTerm->wtFlags & TERM_VNULL)==0 ){ + nRet -= 20; assert( 20==sqlite3LogEst(4) ); + } + } + return nRet; +} + + +#ifdef SQLITE_ENABLE_STAT3_OR_STAT4 +/* +** Return the affinity for a single column of an index. +*/ +static char sqlite3IndexColumnAffinity(sqlite3 *db, Index *pIdx, int iCol){ + assert( iCol>=0 && iColnColumn ); + if( !pIdx->zColAff ){ + if( sqlite3IndexAffinityStr(db, pIdx)==0 ) return SQLITE_AFF_BLOB; + } + return pIdx->zColAff[iCol]; +} +#endif + + +#ifdef SQLITE_ENABLE_STAT3_OR_STAT4 +/* +** This function is called to estimate the number of rows visited by a +** range-scan on a skip-scan index. For example: +** +** CREATE INDEX i1 ON t1(a, b, c); +** SELECT * FROM t1 WHERE a=? AND c BETWEEN ? AND ?; +** +** Value pLoop->nOut is currently set to the estimated number of rows +** visited for scanning (a=? AND b=?). This function reduces that estimate +** by some factor to account for the (c BETWEEN ? AND ?) expression based +** on the stat4 data for the index. this scan will be peformed multiple +** times (once for each (a,b) combination that matches a=?) is dealt with +** by the caller. +** +** It does this by scanning through all stat4 samples, comparing values +** extracted from pLower and pUpper with the corresponding column in each +** sample. If L and U are the number of samples found to be less than or +** equal to the values extracted from pLower and pUpper respectively, and +** N is the total number of samples, the pLoop->nOut value is adjusted +** as follows: +** +** nOut = nOut * ( min(U - L, 1) / N ) +** +** If pLower is NULL, or a value cannot be extracted from the term, L is +** set to zero. If pUpper is NULL, or a value cannot be extracted from it, +** U is set to N. +** +** Normally, this function sets *pbDone to 1 before returning. However, +** if no value can be extracted from either pLower or pUpper (and so the +** estimate of the number of rows delivered remains unchanged), *pbDone +** is left as is. +** +** If an error occurs, an SQLite error code is returned. Otherwise, +** SQLITE_OK. +*/ +static int whereRangeSkipScanEst( + Parse *pParse, /* Parsing & code generating context */ + WhereTerm *pLower, /* Lower bound on the range. ex: "x>123" Might be NULL */ + WhereTerm *pUpper, /* Upper bound on the range. ex: "x<455" Might be NULL */ + WhereLoop *pLoop, /* Update the .nOut value of this loop */ + int *pbDone /* Set to true if at least one expr. value extracted */ +){ + Index *p = pLoop->u.btree.pIndex; + int nEq = pLoop->u.btree.nEq; + sqlite3 *db = pParse->db; + int nLower = -1; + int nUpper = p->nSample+1; + int rc = SQLITE_OK; + u8 aff = sqlite3IndexColumnAffinity(db, p, nEq); + CollSeq *pColl; + + sqlite3_value *p1 = 0; /* Value extracted from pLower */ + sqlite3_value *p2 = 0; /* Value extracted from pUpper */ + sqlite3_value *pVal = 0; /* Value extracted from record */ + + pColl = sqlite3LocateCollSeq(pParse, p->azColl[nEq]); + if( pLower ){ + rc = sqlite3Stat4ValueFromExpr(pParse, pLower->pExpr->pRight, aff, &p1); + nLower = 0; + } + if( pUpper && rc==SQLITE_OK ){ + rc = sqlite3Stat4ValueFromExpr(pParse, pUpper->pExpr->pRight, aff, &p2); + nUpper = p2 ? 0 : p->nSample; + } + + if( p1 || p2 ){ + int i; + int nDiff; + for(i=0; rc==SQLITE_OK && inSample; i++){ + rc = sqlite3Stat4Column(db, p->aSample[i].p, p->aSample[i].n, nEq, &pVal); + if( rc==SQLITE_OK && p1 ){ + int res = sqlite3MemCompare(p1, pVal, pColl); + if( res>=0 ) nLower++; + } + if( rc==SQLITE_OK && p2 ){ + int res = sqlite3MemCompare(p2, pVal, pColl); + if( res>=0 ) nUpper++; + } + } + nDiff = (nUpper - nLower); + if( nDiff<=0 ) nDiff = 1; + + /* If there is both an upper and lower bound specified, and the + ** comparisons indicate that they are close together, use the fallback + ** method (assume that the scan visits 1/64 of the rows) for estimating + ** the number of rows visited. Otherwise, estimate the number of rows + ** using the method described in the header comment for this function. */ + if( nDiff!=1 || pUpper==0 || pLower==0 ){ + int nAdjust = (sqlite3LogEst(p->nSample) - sqlite3LogEst(nDiff)); + pLoop->nOut -= nAdjust; + *pbDone = 1; + WHERETRACE(0x10, ("range skip-scan regions: %u..%u adjust=%d est=%d\n", + nLower, nUpper, nAdjust*-1, pLoop->nOut)); + } + + }else{ + assert( *pbDone==0 ); + } + + sqlite3ValueFree(p1); + sqlite3ValueFree(p2); + sqlite3ValueFree(pVal); + + return rc; +} +#endif /* SQLITE_ENABLE_STAT3_OR_STAT4 */ + +/* +** This function is used to estimate the number of rows that will be visited +** by scanning an index for a range of values. The range may have an upper +** bound, a lower bound, or both. The WHERE clause terms that set the upper +** and lower bounds are represented by pLower and pUpper respectively. For +** example, assuming that index p is on t1(a): +** +** ... FROM t1 WHERE a > ? AND a < ? ... +** |_____| |_____| +** | | +** pLower pUpper +** +** If either of the upper or lower bound is not present, then NULL is passed in +** place of the corresponding WhereTerm. +** +** The value in (pBuilder->pNew->u.btree.nEq) is the number of the index +** column subject to the range constraint. Or, equivalently, the number of +** equality constraints optimized by the proposed index scan. For example, +** assuming index p is on t1(a, b), and the SQL query is: +** +** ... FROM t1 WHERE a = ? AND b > ? AND b < ? ... +** +** then nEq is set to 1 (as the range restricted column, b, is the second +** left-most column of the index). Or, if the query is: +** +** ... FROM t1 WHERE a > ? AND a < ? ... +** +** then nEq is set to 0. +** +** When this function is called, *pnOut is set to the sqlite3LogEst() of the +** number of rows that the index scan is expected to visit without +** considering the range constraints. If nEq is 0, then *pnOut is the number of +** rows in the index. Assuming no error occurs, *pnOut is adjusted (reduced) +** to account for the range constraints pLower and pUpper. +** +** In the absence of sqlite_stat4 ANALYZE data, or if such data cannot be +** used, a single range inequality reduces the search space by a factor of 4. +** and a pair of constraints (x>? AND x123" Might be NULL */ + WhereTerm *pUpper, /* Upper bound on the range. ex: "x<455" Might be NULL */ + WhereLoop *pLoop /* Modify the .nOut and maybe .rRun fields */ +){ + int rc = SQLITE_OK; + int nOut = pLoop->nOut; + LogEst nNew; + +#ifdef SQLITE_ENABLE_STAT3_OR_STAT4 + Index *p = pLoop->u.btree.pIndex; + int nEq = pLoop->u.btree.nEq; + + if( p->nSample>0 && nEqnSampleCol ){ + if( nEq==pBuilder->nRecValid ){ + UnpackedRecord *pRec = pBuilder->pRec; + tRowcnt a[2]; + u8 aff; + + /* Variable iLower will be set to the estimate of the number of rows in + ** the index that are less than the lower bound of the range query. The + ** lower bound being the concatenation of $P and $L, where $P is the + ** key-prefix formed by the nEq values matched against the nEq left-most + ** columns of the index, and $L is the value in pLower. + ** + ** Or, if pLower is NULL or $L cannot be extracted from it (because it + ** is not a simple variable or literal value), the lower bound of the + ** range is $P. Due to a quirk in the way whereKeyStats() works, even + ** if $L is available, whereKeyStats() is called for both ($P) and + ** ($P:$L) and the larger of the two returned values is used. + ** + ** Similarly, iUpper is to be set to the estimate of the number of rows + ** less than the upper bound of the range query. Where the upper bound + ** is either ($P) or ($P:$U). Again, even if $U is available, both values + ** of iUpper are requested of whereKeyStats() and the smaller used. + ** + ** The number of rows between the two bounds is then just iUpper-iLower. + */ + tRowcnt iLower; /* Rows less than the lower bound */ + tRowcnt iUpper; /* Rows less than the upper bound */ + int iLwrIdx = -2; /* aSample[] for the lower bound */ + int iUprIdx = -1; /* aSample[] for the upper bound */ + + if( pRec ){ + testcase( pRec->nField!=pBuilder->nRecValid ); + pRec->nField = pBuilder->nRecValid; + } + aff = sqlite3IndexColumnAffinity(pParse->db, p, nEq); + assert( nEq!=p->nKeyCol || aff==SQLITE_AFF_INTEGER ); + /* Determine iLower and iUpper using ($P) only. */ + if( nEq==0 ){ + iLower = 0; + iUpper = p->nRowEst0; + }else{ + /* Note: this call could be optimized away - since the same values must + ** have been requested when testing key $P in whereEqualScanEst(). */ + whereKeyStats(pParse, p, pRec, 0, a); + iLower = a[0]; + iUpper = a[0] + a[1]; + } + + assert( pLower==0 || (pLower->eOperator & (WO_GT|WO_GE))!=0 ); + assert( pUpper==0 || (pUpper->eOperator & (WO_LT|WO_LE))!=0 ); + assert( p->aSortOrder!=0 ); + if( p->aSortOrder[nEq] ){ + /* The roles of pLower and pUpper are swapped for a DESC index */ + SWAP(WhereTerm*, pLower, pUpper); + } + + /* If possible, improve on the iLower estimate using ($P:$L). */ + if( pLower ){ + int bOk; /* True if value is extracted from pExpr */ + Expr *pExpr = pLower->pExpr->pRight; + rc = sqlite3Stat4ProbeSetValue(pParse, p, &pRec, pExpr, aff, nEq, &bOk); + if( rc==SQLITE_OK && bOk ){ + tRowcnt iNew; + iLwrIdx = whereKeyStats(pParse, p, pRec, 0, a); + iNew = a[0] + ((pLower->eOperator & (WO_GT|WO_LE)) ? a[1] : 0); + if( iNew>iLower ) iLower = iNew; + nOut--; + pLower = 0; + } + } + + /* If possible, improve on the iUpper estimate using ($P:$U). */ + if( pUpper ){ + int bOk; /* True if value is extracted from pExpr */ + Expr *pExpr = pUpper->pExpr->pRight; + rc = sqlite3Stat4ProbeSetValue(pParse, p, &pRec, pExpr, aff, nEq, &bOk); + if( rc==SQLITE_OK && bOk ){ + tRowcnt iNew; + iUprIdx = whereKeyStats(pParse, p, pRec, 1, a); + iNew = a[0] + ((pUpper->eOperator & (WO_GT|WO_LE)) ? a[1] : 0); + if( iNewpRec = pRec; + if( rc==SQLITE_OK ){ + if( iUpper>iLower ){ + nNew = sqlite3LogEst(iUpper - iLower); + /* TUNING: If both iUpper and iLower are derived from the same + ** sample, then assume they are 4x more selective. This brings + ** the estimated selectivity more in line with what it would be + ** if estimated without the use of STAT3/4 tables. */ + if( iLwrIdx==iUprIdx ) nNew -= 20; assert( 20==sqlite3LogEst(4) ); + }else{ + nNew = 10; assert( 10==sqlite3LogEst(2) ); + } + if( nNewwtFlags & TERM_VNULL)==0 ); + nNew = whereRangeAdjust(pLower, nOut); + nNew = whereRangeAdjust(pUpper, nNew); + + /* TUNING: If there is both an upper and lower limit and neither limit + ** has an application-defined likelihood(), assume the range is + ** reduced by an additional 75%. This means that, by default, an open-ended + ** range query (e.g. col > ?) is assumed to match 1/4 of the rows in the + ** index. While a closed range (e.g. col BETWEEN ? AND ?) is estimated to + ** match 1/64 of the index. */ + if( pLower && pLower->truthProb>0 && pUpper && pUpper->truthProb>0 ){ + nNew -= 20; + } + + nOut -= (pLower!=0) + (pUpper!=0); + if( nNew<10 ) nNew = 10; + if( nNewnOut>nOut ){ + WHERETRACE(0x10,("Range scan lowers nOut from %d to %d\n", + pLoop->nOut, nOut)); + } +#endif + pLoop->nOut = (LogEst)nOut; + return rc; +} + +#ifdef SQLITE_ENABLE_STAT3_OR_STAT4 +/* +** Estimate the number of rows that will be returned based on +** an equality constraint x=VALUE and where that VALUE occurs in +** the histogram data. This only works when x is the left-most +** column of an index and sqlite_stat3 histogram data is available +** for that index. When pExpr==NULL that means the constraint is +** "x IS NULL" instead of "x=VALUE". +** +** Write the estimated row count into *pnRow and return SQLITE_OK. +** If unable to make an estimate, leave *pnRow unchanged and return +** non-zero. +** +** This routine can fail if it is unable to load a collating sequence +** required for string comparison, or if unable to allocate memory +** for a UTF conversion required for comparison. The error is stored +** in the pParse structure. +*/ +static int whereEqualScanEst( + Parse *pParse, /* Parsing & code generating context */ + WhereLoopBuilder *pBuilder, + Expr *pExpr, /* Expression for VALUE in the x=VALUE constraint */ + tRowcnt *pnRow /* Write the revised row estimate here */ +){ + Index *p = pBuilder->pNew->u.btree.pIndex; + int nEq = pBuilder->pNew->u.btree.nEq; + UnpackedRecord *pRec = pBuilder->pRec; + u8 aff; /* Column affinity */ + int rc; /* Subfunction return code */ + tRowcnt a[2]; /* Statistics */ + int bOk; + + assert( nEq>=1 ); + assert( nEq<=p->nColumn ); + assert( p->aSample!=0 ); + assert( p->nSample>0 ); + assert( pBuilder->nRecValidnRecValid<(nEq-1) ){ + return SQLITE_NOTFOUND; + } + + /* This is an optimization only. The call to sqlite3Stat4ProbeSetValue() + ** below would return the same value. */ + if( nEq>=p->nColumn ){ + *pnRow = 1; + return SQLITE_OK; + } + + aff = sqlite3IndexColumnAffinity(pParse->db, p, nEq-1); + rc = sqlite3Stat4ProbeSetValue(pParse, p, &pRec, pExpr, aff, nEq-1, &bOk); + pBuilder->pRec = pRec; + if( rc!=SQLITE_OK ) return rc; + if( bOk==0 ) return SQLITE_NOTFOUND; + pBuilder->nRecValid = nEq; + + whereKeyStats(pParse, p, pRec, 0, a); + WHERETRACE(0x10,("equality scan regions: %d\n", (int)a[1])); + *pnRow = a[1]; + + return rc; +} +#endif /* SQLITE_ENABLE_STAT3_OR_STAT4 */ + +#ifdef SQLITE_ENABLE_STAT3_OR_STAT4 +/* +** Estimate the number of rows that will be returned based on +** an IN constraint where the right-hand side of the IN operator +** is a list of values. Example: +** +** WHERE x IN (1,2,3,4) +** +** Write the estimated row count into *pnRow and return SQLITE_OK. +** If unable to make an estimate, leave *pnRow unchanged and return +** non-zero. +** +** This routine can fail if it is unable to load a collating sequence +** required for string comparison, or if unable to allocate memory +** for a UTF conversion required for comparison. The error is stored +** in the pParse structure. +*/ +static int whereInScanEst( + Parse *pParse, /* Parsing & code generating context */ + WhereLoopBuilder *pBuilder, + ExprList *pList, /* The value list on the RHS of "x IN (v1,v2,v3,...)" */ + tRowcnt *pnRow /* Write the revised row estimate here */ +){ + Index *p = pBuilder->pNew->u.btree.pIndex; + i64 nRow0 = sqlite3LogEstToInt(p->aiRowLogEst[0]); + int nRecValid = pBuilder->nRecValid; + int rc = SQLITE_OK; /* Subfunction return code */ + tRowcnt nEst; /* Number of rows for a single term */ + tRowcnt nRowEst = 0; /* New estimate of the number of rows */ + int i; /* Loop counter */ + + assert( p->aSample!=0 ); + for(i=0; rc==SQLITE_OK && inExpr; i++){ + nEst = nRow0; + rc = whereEqualScanEst(pParse, pBuilder, pList->a[i].pExpr, &nEst); + nRowEst += nEst; + pBuilder->nRecValid = nRecValid; + } + + if( rc==SQLITE_OK ){ + if( nRowEst > nRow0 ) nRowEst = nRow0; + *pnRow = nRowEst; + WHERETRACE(0x10,("IN row estimate: est=%d\n", nRowEst)); + } + assert( pBuilder->nRecValid==nRecValid ); + return rc; +} +#endif /* SQLITE_ENABLE_STAT3_OR_STAT4 */ + + +#ifdef WHERETRACE_ENABLED +/* +** Print the content of a WhereTerm object +*/ +static void whereTermPrint(WhereTerm *pTerm, int iTerm){ + if( pTerm==0 ){ + sqlite3DebugPrintf("TERM-%-3d NULL\n", iTerm); + }else{ + char zType[4]; + memcpy(zType, "...", 4); + if( pTerm->wtFlags & TERM_VIRTUAL ) zType[0] = 'V'; + if( pTerm->eOperator & WO_EQUIV ) zType[1] = 'E'; + if( ExprHasProperty(pTerm->pExpr, EP_FromJoin) ) zType[2] = 'L'; + sqlite3DebugPrintf( + "TERM-%-3d %p %s cursor=%-3d prob=%-3d op=0x%03x wtFlags=0x%04x\n", + iTerm, pTerm, zType, pTerm->leftCursor, pTerm->truthProb, + pTerm->eOperator, pTerm->wtFlags); + sqlite3TreeViewExpr(0, pTerm->pExpr, 0); + } +} +#endif #ifdef WHERETRACE_ENABLED /* @@ -113704,8 +124245,8 @@ static void whereLoopPrint(WhereLoop *p, WhereClause *pWC){ sqlite3DebugPrintf(" %12s", pItem->zAlias ? pItem->zAlias : pTab->zName); if( (p->wsFlags & WHERE_VIRTUALTABLE)==0 ){ - const char *zName; - if( p->u.btree.pIndex && (zName = p->u.btree.pIndex->zName)!=0 ){ + const char *zName; + if( p->u.btree.pIndex && (zName = p->u.btree.pIndex->zName)!=0 ){ if( strncmp(zName, "sqlite_autoindex_", 17)==0 ){ int i = sqlite3Strlen30(zName) - 1; while( zName[i]!='_' ) i--; @@ -113726,29 +124267,18 @@ static void whereLoopPrint(WhereLoop *p, WhereClause *pWC){ sqlite3DebugPrintf(" %-19s", z); sqlite3_free(z); } - sqlite3DebugPrintf(" f %04x N %d", p->wsFlags, p->nLTerm); + if( p->wsFlags & WHERE_SKIPSCAN ){ + sqlite3DebugPrintf(" f %05x %d-%d", p->wsFlags, p->nLTerm,p->nSkip); + }else{ + sqlite3DebugPrintf(" f %05x N %d", p->wsFlags, p->nLTerm); + } sqlite3DebugPrintf(" cost %d,%d,%d\n", p->rSetup, p->rRun, p->nOut); -#ifdef SQLITE_ENABLE_TREE_EXPLAIN - /* If the 0x100 bit of wheretracing is set, then show all of the constraint - ** expressions in the WhereLoop.aLTerm[] array. - */ - if( p->nLTerm && (sqlite3WhereTrace & 0x100)!=0 ){ /* WHERETRACE 0x100 */ + if( p->nLTerm && (sqlite3WhereTrace & 0x100)!=0 ){ int i; - Vdbe *v = pWInfo->pParse->pVdbe; - sqlite3ExplainBegin(v); for(i=0; inLTerm; i++){ - WhereTerm *pTerm = p->aLTerm[i]; - if( pTerm==0 ) continue; - sqlite3ExplainPrintf(v, " (%d) #%-2d ", i+1, (int)(pTerm-pWC->a)); - sqlite3ExplainPush(v); - whereExplainTerm(v, pTerm); - sqlite3ExplainPop(v); - sqlite3ExplainNL(v); + whereTermPrint(p->aLTerm[i], i); } - sqlite3ExplainFinish(v); - sqlite3DebugPrintf("%s", sqlite3VdbeExplanation(v)); } -#endif } #endif @@ -113774,7 +124304,6 @@ static void whereLoopClearUnion(sqlite3 *db, WhereLoop *p){ p->u.vtab.idxStr = 0; }else if( (p->wsFlags & WHERE_AUTO_INDEX)!=0 && p->u.btree.pIndex!=0 ){ sqlite3DbFree(db, p->u.btree.pIndex->zColAff); - sqlite3KeyInfoUnref(p->u.btree.pIndex->pKeyInfo); sqlite3DbFree(db, p->u.btree.pIndex); p->u.btree.pIndex = 0; } @@ -113838,7 +124367,14 @@ static void whereLoopDelete(sqlite3 *db, WhereLoop *p){ */ static void whereInfoFree(sqlite3 *db, WhereInfo *pWInfo){ if( ALWAYS(pWInfo) ){ - whereClauseClear(&pWInfo->sWC); + int i; + for(i=0; inLevel; i++){ + WhereLevel *pLevel = &pWInfo->a[i]; + if( pLevel->pWLoop && (pLevel->pWLoop->wsFlags & WHERE_IN_ABLE) ){ + sqlite3DbFree(db, pLevel->u.in.aInLoop); + } + } + sqlite3WhereClauseClear(&pWInfo->sWC); while( pWInfo->pLoops ){ WhereLoop *p = pWInfo->pLoops; pWInfo->pLoops = p->pNextLoop; @@ -113849,10 +124385,11 @@ static void whereInfoFree(sqlite3 *db, WhereInfo *pWInfo){ } /* -** Return TRUE if both of the following are true: +** Return TRUE if all of the following are true: ** ** (1) X has the same or lower cost that Y ** (2) X is a proper subset of Y +** (3) X skips at least as many columns as Y ** ** By "proper subset" we mean that X uses fewer WHERE clause terms ** than Y and that every WHERE clause term used by X is also used @@ -113860,19 +124397,25 @@ static void whereInfoFree(sqlite3 *db, WhereInfo *pWInfo){ ** ** If X is a proper subset of Y then Y is a better choice and ought ** to have a lower cost. This routine returns TRUE when that cost -** relationship is inverted and needs to be adjusted. +** relationship is inverted and needs to be adjusted. The third rule +** was added because if X uses skip-scan less than Y it still might +** deserve a lower cost even if it is a proper subset of Y. */ static int whereLoopCheaperProperSubset( const WhereLoop *pX, /* First WhereLoop to compare */ const WhereLoop *pY /* Compare against this WhereLoop */ ){ int i, j; - if( pX->nLTerm >= pY->nLTerm ) return 0; /* X is not a subset of Y */ + if( pX->nLTerm-pX->nSkip >= pY->nLTerm-pY->nSkip ){ + return 0; /* X is not a subset of Y */ + } + if( pY->nSkip > pX->nSkip ) return 0; if( pX->rRun >= pY->rRun ){ if( pX->rRun > pY->rRun ) return 0; /* X costs more than Y */ if( pX->nOut > pY->nOut ) return 0; /* X costs more than Y */ } for(i=pX->nLTerm-1; i>=0; i--){ + if( pX->aLTerm[i]==0 ) continue; for(j=pY->nLTerm-1; j>=0; j--){ if( pY->aLTerm[j]==pX->aLTerm[i] ) break; } @@ -113894,33 +124437,24 @@ static int whereLoopCheaperProperSubset( ** To say "WhereLoop X is a proper subset of Y" means that X uses fewer ** WHERE clause terms than Y and that every WHERE clause term used by X is ** also used by Y. -** -** This adjustment is omitted for SKIPSCAN loops. In a SKIPSCAN loop, the -** WhereLoop.nLTerm field is not an accurate measure of the number of WHERE -** clause terms covered, since some of the first nLTerm entries in aLTerm[] -** will be NULL (because they are skipped). That makes it more difficult -** to compare the loops. We could add extra code to do the comparison, and -** perhaps we will someday. But SKIPSCAN is sufficiently uncommon, and this -** adjustment is sufficient minor, that it is very difficult to construct -** a test case where the extra code would improve the query plan. Better -** to avoid the added complexity and just omit cost adjustments to SKIPSCAN -** loops. */ static void whereLoopAdjustCost(const WhereLoop *p, WhereLoop *pTemplate){ if( (pTemplate->wsFlags & WHERE_INDEXED)==0 ) return; - if( (pTemplate->wsFlags & WHERE_SKIPSCAN)!=0 ) return; for(; p; p=p->pNextLoop){ if( p->iTab!=pTemplate->iTab ) continue; if( (p->wsFlags & WHERE_INDEXED)==0 ) continue; - if( (p->wsFlags & WHERE_SKIPSCAN)!=0 ) continue; if( whereLoopCheaperProperSubset(p, pTemplate) ){ /* Adjust pTemplate cost downward so that it is cheaper than its - ** subset p */ + ** subset p. */ + WHERETRACE(0x80,("subset cost adjustment %d,%d to %d,%d\n", + pTemplate->rRun, pTemplate->nOut, p->rRun, p->nOut-1)); pTemplate->rRun = p->rRun; pTemplate->nOut = p->nOut - 1; }else if( whereLoopCheaperProperSubset(pTemplate, p) ){ /* Adjust pTemplate cost upward so that it is costlier than p since ** pTemplate is a proper subset of p */ + WHERETRACE(0x80,("subset cost adjustment %d,%d to %d,%d\n", + pTemplate->rRun, pTemplate->nOut, p->rRun, p->nOut+1)); pTemplate->rRun = p->rRun; pTemplate->nOut = p->nOut + 1; } @@ -113963,6 +124497,18 @@ static WhereLoop **whereLoopFindLesser( ** rSetup. Call this SETUP-INVARIANT */ assert( p->rSetup>=pTemplate->rSetup ); + /* Any loop using an appliation-defined index (or PRIMARY KEY or + ** UNIQUE constraint) with one or more == constraints is better + ** than an automatic index. Unless it is a skip-scan. */ + if( (p->wsFlags & WHERE_AUTO_INDEX)!=0 + && (pTemplate->nSkip)==0 + && (pTemplate->wsFlags & WHERE_INDEXED)!=0 + && (pTemplate->wsFlags & WHERE_COLUMN_EQ)!=0 + && (p->prereq & pTemplate->prereq)==pTemplate->prereq + ){ + break; + } + /* If existing WhereLoop p is better than pTemplate, pTemplate can be ** discarded. WhereLoop p is better if: ** (1) p has no more dependencies than pTemplate, and @@ -114025,18 +124571,20 @@ static int whereLoopInsert(WhereLoopBuilder *pBuilder, WhereLoop *pTemplate){ ** and prereqs. */ if( pBuilder->pOrSet!=0 ){ + if( pTemplate->nLTerm ){ #if WHERETRACE_ENABLED - u16 n = pBuilder->pOrSet->n; - int x = + u16 n = pBuilder->pOrSet->n; + int x = #endif - whereOrInsert(pBuilder->pOrSet, pTemplate->prereq, pTemplate->rRun, + whereOrInsert(pBuilder->pOrSet, pTemplate->prereq, pTemplate->rRun, pTemplate->nOut); #if WHERETRACE_ENABLED /* 0x8 */ - if( sqlite3WhereTrace & 0x8 ){ - sqlite3DebugPrintf(x?" or-%d: ":" or-X: ", n); - whereLoopPrint(pTemplate, pBuilder->pWC); - } + if( sqlite3WhereTrace & 0x8 ){ + sqlite3DebugPrintf(x?" or-%d: ":" or-X: ", n); + whereLoopPrint(pTemplate, pBuilder->pWC); + } #endif + } return SQLITE_OK; } @@ -114050,7 +124598,7 @@ static int whereLoopInsert(WhereLoopBuilder *pBuilder, WhereLoop *pTemplate){ ** than pTemplate, so just ignore pTemplate */ #if WHERETRACE_ENABLED /* 0x8 */ if( sqlite3WhereTrace & 0x8 ){ - sqlite3DebugPrintf("ins-noop: "); + sqlite3DebugPrintf(" skip: "); whereLoopPrint(pTemplate, pBuilder->pWC); } #endif @@ -114066,10 +124614,10 @@ static int whereLoopInsert(WhereLoopBuilder *pBuilder, WhereLoop *pTemplate){ #if WHERETRACE_ENABLED /* 0x8 */ if( sqlite3WhereTrace & 0x8 ){ if( p!=0 ){ - sqlite3DebugPrintf("ins-del: "); + sqlite3DebugPrintf("replace: "); whereLoopPrint(p, pBuilder->pWC); } - sqlite3DebugPrintf("ins-new: "); + sqlite3DebugPrintf(" add: "); whereLoopPrint(pTemplate, pBuilder->pWC); } #endif @@ -114087,13 +124635,13 @@ static int whereLoopInsert(WhereLoopBuilder *pBuilder, WhereLoop *pTemplate){ WhereLoop *pToDel; while( *ppTail ){ ppTail = whereLoopFindLesser(ppTail, pTemplate); - if( NEVER(ppTail==0) ) break; + if( ppTail==0 ) break; pToDel = *ppTail; if( pToDel==0 ) break; *ppTail = pToDel->pNextLoop; #if WHERETRACE_ENABLED /* 0x8 */ if( sqlite3WhereTrace & 0x8 ){ - sqlite3DebugPrintf("ins-del: "); + sqlite3DebugPrintf(" delete: "); whereLoopPrint(pToDel, pBuilder->pWC); } #endif @@ -114114,19 +124662,42 @@ static int whereLoopInsert(WhereLoopBuilder *pBuilder, WhereLoop *pTemplate){ ** Adjust the WhereLoop.nOut value downward to account for terms of the ** WHERE clause that reference the loop but which are not used by an ** index. +* +** For every WHERE clause term that is not used by the index +** and which has a truth probability assigned by one of the likelihood(), +** likely(), or unlikely() SQL functions, reduce the estimated number +** of output rows by the probability specified. ** -** In the current implementation, the first extra WHERE clause term reduces -** the number of output rows by a factor of 10 and each additional term -** reduces the number of output rows by sqrt(2). +** TUNING: For every WHERE clause term that is not used by the index +** and which does not have an assigned truth probability, heuristics +** described below are used to try to estimate the truth probability. +** TODO --> Perhaps this is something that could be improved by better +** table statistics. +** +** Heuristic 1: Estimate the truth probability as 93.75%. The 93.75% +** value corresponds to -1 in LogEst notation, so this means decrement +** the WhereLoop.nOut field for every such WHERE clause term. +** +** Heuristic 2: If there exists one or more WHERE clause terms of the +** form "x==EXPR" and EXPR is not a constant 0 or 1, then make sure the +** final output row estimate is no greater than 1/4 of the total number +** of rows in the table. In other words, assume that x==EXPR will filter +** out at least 3 out of 4 rows. If EXPR is -1 or 0 or 1, then maybe the +** "x" column is boolean or else -1 or 0 or 1 is a common default value +** on the "x" column and so in that case only cap the output row estimate +** at 1/2 instead of 1/4. */ -static void whereLoopOutputAdjust(WhereClause *pWC, WhereLoop *pLoop){ +static void whereLoopOutputAdjust( + WhereClause *pWC, /* The WHERE clause */ + WhereLoop *pLoop, /* The loop to adjust downward */ + LogEst nRow /* Number of rows in the entire table */ +){ WhereTerm *pTerm, *pX; Bitmask notAllowed = ~(pLoop->prereq|pLoop->maskSelf); - int i, j; + int i, j, k; + LogEst iReduce = 0; /* pLoop->nOut should not exceed nRow-iReduce */ - if( !OptimizationEnabled(pWC->pWInfo->pParse->db, SQLITE_AdjustOutEst) ){ - return; - } + assert( (pLoop->wsFlags & WHERE_AUTO_INDEX)==0 ); for(i=pWC->nTerm, pTerm=pWC->a; i>0; i--, pTerm++){ if( (pTerm->wtFlags & TERM_VIRTUAL)!=0 ) break; if( (pTerm->prereqAll & pLoop->maskSelf)==0 ) continue; @@ -114138,11 +124709,40 @@ static void whereLoopOutputAdjust(WhereClause *pWC, WhereLoop *pLoop){ if( pX->iParent>=0 && (&pWC->a[pX->iParent])==pTerm ) break; } if( j<0 ){ - pLoop->nOut += (pTerm->truthProb<=0 ? pTerm->truthProb : -1); + if( pTerm->truthProb<=0 ){ + /* If a truth probability is specified using the likelihood() hints, + ** then use the probability provided by the application. */ + pLoop->nOut += pTerm->truthProb; + }else{ + /* In the absence of explicit truth probabilities, use heuristics to + ** guess a reasonable truth probability. */ + pLoop->nOut--; + if( pTerm->eOperator&(WO_EQ|WO_IS) ){ + Expr *pRight = pTerm->pExpr->pRight; + testcase( pTerm->pExpr->op==TK_IS ); + if( sqlite3ExprIsInteger(pRight, &k) && k>=(-1) && k<=1 ){ + k = 10; + }else{ + k = 20; + } + if( iReducenOut > nRow-iReduce ) pLoop->nOut = nRow - iReduce; } +/* +** Adjust the cost C by the costMult facter T. This only occurs if +** compiled with -DSQLITE_ENABLE_COSTMULT +*/ +#ifdef SQLITE_ENABLE_COSTMULT +# define ApplyCostMultiplier(C,T) C += T +#else +# define ApplyCostMultiplier(C,T) +#endif + /* ** We have so far matched pBuilder->pNew->u.btree.nEq terms of the ** index pIndex. Try to match one more. @@ -114171,11 +124771,11 @@ static int whereLoopAddBtreeIndex( Bitmask saved_prereq; /* Original value of pNew->prereq */ u16 saved_nLTerm; /* Original value of pNew->nLTerm */ u16 saved_nEq; /* Original value of pNew->u.btree.nEq */ - u16 saved_nSkip; /* Original value of pNew->u.btree.nSkip */ + u16 saved_nSkip; /* Original value of pNew->nSkip */ u32 saved_wsFlags; /* Original value of pNew->wsFlags */ LogEst saved_nOut; /* Original value of pNew->nOut */ - int iCol; /* Index of the column in the table */ int rc = SQLITE_OK; /* Return code */ + LogEst rSize; /* Number of rows in the table */ LogEst rLogSize; /* Logarithm of table size */ WhereTerm *pTop = 0, *pBtm = 0; /* Top and bottom range constraints */ @@ -114186,57 +124786,26 @@ static int whereLoopAddBtreeIndex( assert( (pNew->wsFlags & WHERE_TOP_LIMIT)==0 ); if( pNew->wsFlags & WHERE_BTM_LIMIT ){ opMask = WO_LT|WO_LE; - }else if( pProbe->tnum<=0 || (pSrc->jointype & JT_LEFT)!=0 ){ + }else if( /*pProbe->tnum<=0 ||*/ (pSrc->fg.jointype & JT_LEFT)!=0 ){ opMask = WO_EQ|WO_IN|WO_GT|WO_GE|WO_LT|WO_LE; }else{ - opMask = WO_EQ|WO_IN|WO_ISNULL|WO_GT|WO_GE|WO_LT|WO_LE; + opMask = WO_EQ|WO_IN|WO_GT|WO_GE|WO_LT|WO_LE|WO_ISNULL|WO_IS; } if( pProbe->bUnordered ) opMask &= ~(WO_GT|WO_GE|WO_LT|WO_LE); - assert( pNew->u.btree.nEq<=pProbe->nKeyCol ); - if( pNew->u.btree.nEq < pProbe->nKeyCol ){ - iCol = pProbe->aiColumn[pNew->u.btree.nEq]; - }else{ - iCol = -1; - } - pTerm = whereScanInit(&scan, pBuilder->pWC, pSrc->iCursor, iCol, - opMask, pProbe); + assert( pNew->u.btree.nEqnColumn ); + saved_nEq = pNew->u.btree.nEq; - saved_nSkip = pNew->u.btree.nSkip; + saved_nSkip = pNew->nSkip; saved_nLTerm = pNew->nLTerm; saved_wsFlags = pNew->wsFlags; saved_prereq = pNew->prereq; saved_nOut = pNew->nOut; + pTerm = whereScanInit(&scan, pBuilder->pWC, pSrc->iCursor, saved_nEq, + opMask, pProbe); pNew->rSetup = 0; - rLogSize = estLog(pProbe->aiRowLogEst[0]); - - /* Consider using a skip-scan if there are no WHERE clause constraints - ** available for the left-most terms of the index, and if the average - ** number of repeats in the left-most terms is at least 18. - ** - ** The magic number 18 is selected on the basis that scanning 17 rows - ** is almost always quicker than an index seek (even though if the index - ** contains fewer than 2^17 rows we assume otherwise in other parts of - ** the code). And, even if it is not, it should not be too much slower. - ** On the other hand, the extra seeks could end up being significantly - ** more expensive. */ - assert( 42==sqlite3LogEst(18) ); - if( pTerm==0 - && saved_nEq==saved_nSkip - && saved_nEq+1nKeyCol - && pProbe->aiRowLogEst[saved_nEq+1]>=42 /* TUNING: Minimum for skip-scan */ - && (rc = whereLoopResize(db, pNew, pNew->nLTerm+1))==SQLITE_OK - ){ - LogEst nIter; - pNew->u.btree.nEq++; - pNew->u.btree.nSkip++; - pNew->aLTerm[pNew->nLTerm++] = 0; - pNew->wsFlags |= WHERE_SKIPSCAN; - nIter = pProbe->aiRowLogEst[saved_nEq] - pProbe->aiRowLogEst[saved_nEq+1]; - pNew->nOut -= nIter; - whereLoopAddBtreeIndex(pBuilder, pSrc, pProbe, nIter + nInMul); - pNew->nOut = saved_nOut; - } + rSize = pProbe->aiRowLogEst[0]; + rLogSize = estLog(rSize); for(; rc==SQLITE_OK && pTerm!=0; pTerm = whereScanNext(&scan)){ u16 eOp = pTerm->eOperator; /* Shorthand for pTerm->eOperator */ LogEst rCostIdx; @@ -114246,12 +124815,16 @@ static int whereLoopAddBtreeIndex( int nRecValid = pBuilder->nRecValid; #endif if( (eOp==WO_ISNULL || (pTerm->wtFlags&TERM_VNULL)!=0) - && (iCol<0 || pSrc->pTab->aCol[iCol].notNull) + && indexColumnNotNull(pProbe, saved_nEq) ){ continue; /* ignore IS [NOT] NULL constraints on NOT NULL columns */ } if( pTerm->prereqRight & pNew->maskSelf ) continue; + /* Do not allow the upper bound of a LIKE optimization range constraint + ** to mix with a lower range bound from some other source */ + if( pTerm->wtFlags & TERM_LIKEOPT && pTerm->eOperator==WO_LT ) continue; + pNew->wsFlags = saved_wsFlags; pNew->u.btree.nEq = saved_nEq; pNew->nLTerm = saved_nLTerm; @@ -114278,10 +124851,14 @@ static int whereLoopAddBtreeIndex( assert( nIn>0 ); /* RHS always has 2 or more terms... The parser ** changes "x IN (?)" into "x=?". */ - }else if( eOp & (WO_EQ) ){ + }else if( eOp & (WO_EQ|WO_IS) ){ + int iCol = pProbe->aiColumn[saved_nEq]; pNew->wsFlags |= WHERE_COLUMN_EQ; - if( iCol<0 || (nInMul==0 && pNew->u.btree.nEq==pProbe->nKeyCol-1) ){ - if( iCol>=0 && pProbe->onError==OE_None ){ + assert( saved_nEq==pNew->u.btree.nEq ); + if( iCol==XN_ROWID + || (iCol>0 && nInMul==0 && saved_nEq==pProbe->nKeyCol-1) + ){ + if( iCol>=0 && pProbe->uniqNotNull==0 ){ pNew->wsFlags |= WHERE_UNQ_WANTED; }else{ pNew->wsFlags |= WHERE_ONEROW; @@ -114295,6 +124872,17 @@ static int whereLoopAddBtreeIndex( pNew->wsFlags |= WHERE_COLUMN_RANGE|WHERE_BTM_LIMIT; pBtm = pTerm; pTop = 0; + if( pTerm->wtFlags & TERM_LIKEOPT ){ + /* Range contraints that come from the LIKE optimization are + ** always used in pairs. */ + pTop = &pTerm[1]; + assert( (pTop-(pTerm->pWC->a))pWC->nTerm ); + assert( pTop->wtFlags & TERM_LIKEOPT ); + assert( pTop->eOperator==WO_LT ); + if( whereLoopResize(db, pNew, pNew->nLTerm+1) ) break; /* OOM */ + pNew->aLTerm[pNew->nLTerm++] = pTop; + pNew->wsFlags |= WHERE_TOP_LIMIT; + } }else{ assert( eOp & (WO_LT|WO_LE) ); testcase( eOp & WO_LT ); @@ -114317,10 +124905,10 @@ static int whereLoopAddBtreeIndex( whereRangeScanEst(pParse, pBuilder, pBtm, pTop, pNew); }else{ int nEq = ++pNew->u.btree.nEq; - assert( eOp & (WO_ISNULL|WO_EQ|WO_IN) ); + assert( eOp & (WO_ISNULL|WO_EQ|WO_IN|WO_IS) ); assert( pNew->nOut==saved_nOut ); - if( pTerm->truthProb<=0 && iCol>=0 ){ + if( pTerm->truthProb<=0 && pProbe->aiColumn[saved_nEq]>=0 ){ assert( (eOp & WO_IN) || nIn==0 ); testcase( eOp & WO_IN ); pNew->nOut += pTerm->truthProb; @@ -114331,18 +124919,17 @@ static int whereLoopAddBtreeIndex( if( nInMul==0 && pProbe->nSample && pNew->u.btree.nEq<=pProbe->nSampleCol - && OptimizationEnabled(db, SQLITE_Stat3) && ((eOp & WO_IN)==0 || !ExprHasProperty(pTerm->pExpr, EP_xIsSelect)) ){ Expr *pExpr = pTerm->pExpr; - if( (eOp & (WO_EQ|WO_ISNULL))!=0 ){ + if( (eOp & (WO_EQ|WO_ISNULL|WO_IS))!=0 ){ testcase( eOp & WO_EQ ); + testcase( eOp & WO_IS ); testcase( eOp & WO_ISNULL ); rc = whereEqualScanEst(pParse, pBuilder, pExpr->pRight, &nOut); }else{ rc = whereInScanEst(pParse, pBuilder, pExpr->x.pList, &nOut); } - assert( rc!=SQLITE_OK || nOut>0 ); if( rc==SQLITE_NOTFOUND ) rc = SQLITE_OK; if( rc!=SQLITE_OK ) break; /* Jump out of the pTerm loop */ if( nOut ){ @@ -114374,11 +124961,12 @@ static int whereLoopAddBtreeIndex( if( (pNew->wsFlags & (WHERE_IDX_ONLY|WHERE_IPK))==0 ){ pNew->rRun = sqlite3LogEstAdd(pNew->rRun, pNew->nOut + 16); } + ApplyCostMultiplier(pNew->rRun, pProbe->pTable->costMult); nOutUnadjusted = pNew->nOut; pNew->rRun += nInMul + nIn; pNew->nOut += nInMul + nIn; - whereLoopOutputAdjust(pBuilder->pWC, pNew); + whereLoopOutputAdjust(pBuilder->pWC, pNew, rSize); rc = whereLoopInsert(pBuilder, pNew); if( pNew->wsFlags & WHERE_COLUMN_RANGE ){ @@ -114388,7 +124976,7 @@ static int whereLoopAddBtreeIndex( } if( (pNew->wsFlags & WHERE_TOP_LIMIT)==0 - && pNew->u.btree.nEq<(pProbe->nKeyCol + (pProbe->zName!=0)) + && pNew->u.btree.nEqnColumn ){ whereLoopAddBtreeIndex(pBuilder, pSrc, pProbe, nInMul+nIn); } @@ -114399,10 +124987,45 @@ static int whereLoopAddBtreeIndex( } pNew->prereq = saved_prereq; pNew->u.btree.nEq = saved_nEq; - pNew->u.btree.nSkip = saved_nSkip; + pNew->nSkip = saved_nSkip; pNew->wsFlags = saved_wsFlags; pNew->nOut = saved_nOut; pNew->nLTerm = saved_nLTerm; + + /* Consider using a skip-scan if there are no WHERE clause constraints + ** available for the left-most terms of the index, and if the average + ** number of repeats in the left-most terms is at least 18. + ** + ** The magic number 18 is selected on the basis that scanning 17 rows + ** is almost always quicker than an index seek (even though if the index + ** contains fewer than 2^17 rows we assume otherwise in other parts of + ** the code). And, even if it is not, it should not be too much slower. + ** On the other hand, the extra seeks could end up being significantly + ** more expensive. */ + assert( 42==sqlite3LogEst(18) ); + if( saved_nEq==saved_nSkip + && saved_nEq+1nKeyCol + && pProbe->noSkipScan==0 + && pProbe->aiRowLogEst[saved_nEq+1]>=42 /* TUNING: Minimum for skip-scan */ + && (rc = whereLoopResize(db, pNew, pNew->nLTerm+1))==SQLITE_OK + ){ + LogEst nIter; + pNew->u.btree.nEq++; + pNew->nSkip++; + pNew->aLTerm[pNew->nLTerm++] = 0; + pNew->wsFlags |= WHERE_SKIPSCAN; + nIter = pProbe->aiRowLogEst[saved_nEq] - pProbe->aiRowLogEst[saved_nEq+1]; + pNew->nOut -= nIter; + /* TUNING: Because uncertainties in the estimates for skip-scan queries, + ** add a 1.375 fudge factor to make skip-scan slightly less likely. */ + nIter += 5; + whereLoopAddBtreeIndex(pBuilder, pSrc, pProbe, nIter + nInMul); + pNew->nOut = saved_nOut; + pNew->u.btree.nEq = saved_nEq; + pNew->nSkip = saved_nSkip; + pNew->wsFlags = saved_wsFlags; + } + return rc; } @@ -114420,17 +125043,25 @@ static int indexMightHelpWithOrderBy( int iCursor ){ ExprList *pOB; + ExprList *aColExpr; int ii, jj; if( pIndex->bUnordered ) return 0; if( (pOB = pBuilder->pWInfo->pOrderBy)==0 ) return 0; for(ii=0; iinExpr; ii++){ Expr *pExpr = sqlite3ExprSkipCollate(pOB->a[ii].pExpr); - if( pExpr->op!=TK_COLUMN ) return 0; - if( pExpr->iTable==iCursor ){ + if( pExpr->op==TK_COLUMN && pExpr->iTable==iCursor ){ + if( pExpr->iColumn<0 ) return 1; for(jj=0; jjnKeyCol; jj++){ if( pExpr->iColumn==pIndex->aiColumn[jj] ) return 1; } + }else if( (aColExpr = pIndex->aColExpr)!=0 ){ + for(jj=0; jjnKeyCol; jj++){ + if( pIndex->aiColumn[jj]!=XN_EXPR ) continue; + if( sqlite3ExprCompare(pExpr,aColExpr->a[jj].pExpr,iCursor)==0 ){ + return 1; + } + } } } return 0; @@ -114460,8 +125091,17 @@ static Bitmask columnsInIndex(Index *pIdx){ static int whereUsablePartialIndex(int iTab, WhereClause *pWC, Expr *pWhere){ int i; WhereTerm *pTerm; + while( pWhere->op==TK_AND ){ + if( !whereUsablePartialIndex(iTab,pWC,pWhere->pLeft) ) return 0; + pWhere = pWhere->pRight; + } for(i=0, pTerm=pWC->a; inTerm; i++, pTerm++){ - if( sqlite3ExprImpliesExpr(pTerm->pExpr, pWhere, iTab) ) return 1; + Expr *pExpr = pTerm->pExpr; + if( sqlite3ExprImpliesExpr(pExpr, pWhere, iTab) + && (!ExprHasProperty(pExpr, EP_FromJoin) || pExpr->iRightJoinTable==iTab) + ){ + return 1; + } } return 0; } @@ -114493,6 +125133,14 @@ static int whereUsablePartialIndex(int iTab, WhereClause *pWC, Expr *pWhere){ ** Normally, nSeek is 1. nSeek values greater than 1 come about if the ** WHERE clause includes "x IN (....)" terms used in place of "x=?". Or when ** implicit "x IN (SELECT x FROM tbl)" terms are added for skip-scans. +** +** The estimated values (nRow, nVisit, nSeek) often contain a large amount +** of uncertainty. For this reason, scoring is designed to pick plans that +** "do the least harm" if the estimates are inaccurate. For example, a +** log(nRow) factor is omitted from a non-covering index scan in order to +** bias the scoring in favor of using an index, since the worst-case +** performance of using an index is far better than the worst-case performance +** of a full table scan. */ static int whereLoopAddBtree( WhereLoopBuilder *pBuilder, /* WHERE clause information */ @@ -114522,9 +125170,9 @@ static int whereLoopAddBtree( pWC = pBuilder->pWC; assert( !IsVirtual(pSrc->pTab) ); - if( pSrc->pIndex ){ + if( pSrc->pIBIndex ){ /* An INDEXED BY clause specifies a particular index to use */ - pProbe = pSrc->pIndex; + pProbe = pSrc->pIBIndex; }else if( !HasRowid(pTab) ){ pProbe = pTab->pIndex; }else{ @@ -114535,6 +125183,7 @@ static int whereLoopAddBtree( Index *pFirst; /* First of real indices on the table */ memset(&sPk, 0, sizeof(Index)); sPk.nKeyCol = 1; + sPk.nColumn = 1; sPk.aiColumn = &aiColumnPk; sPk.aiRowLogEst = aiRowEstPk; sPk.onError = OE_Replace; @@ -114543,7 +125192,7 @@ static int whereLoopAddBtree( aiRowEstPk[0] = pTab->nRowLogEst; aiRowEstPk[1] = 0; pFirst = pSrc->pTab->pIndex; - if( pSrc->notIndexed==0 ){ + if( pSrc->fg.notIndexed==0 ){ /* The real indices of the table are only considered if the ** NOT INDEXED qualifier is omitted from the FROM clause */ sPk.pNext = pFirst; @@ -114555,14 +125204,14 @@ static int whereLoopAddBtree( #ifndef SQLITE_OMIT_AUTOMATIC_INDEX /* Automatic indexes */ - if( !pBuilder->pOrSet + if( !pBuilder->pOrSet /* Not part of an OR optimization */ + && (pWInfo->wctrlFlags & WHERE_NO_AUTOINDEX)==0 && (pWInfo->pParse->db->flags & SQLITE_AutoIndex)!=0 - && pSrc->pIndex==0 - && !pSrc->viaCoroutine - && !pSrc->notIndexed - && HasRowid(pTab) - && !pSrc->isCorrelated - && !pSrc->isRecursive + && pSrc->pIBIndex==0 /* Has no INDEXED BY clause */ + && !pSrc->fg.notIndexed /* Has no NOT INDEXED clause */ + && HasRowid(pTab) /* Not WITHOUT ROWID table. (FIXME: Why not?) */ + && !pSrc->fg.isCorrelated /* Not a correlated subquery */ + && !pSrc->fg.isRecursive /* Not a recursive common table expression. */ ){ /* Generate auto-index WhereLoops */ WhereTerm *pTerm; @@ -114571,17 +125220,26 @@ static int whereLoopAddBtree( if( pTerm->prereqRight & pNew->maskSelf ) continue; if( termCanDriveIndex(pTerm, pSrc, 0) ){ pNew->u.btree.nEq = 1; - pNew->u.btree.nSkip = 0; + pNew->nSkip = 0; pNew->u.btree.pIndex = 0; pNew->nLTerm = 1; pNew->aLTerm[0] = pTerm; /* TUNING: One-time cost for computing the automatic index is - ** approximately 7*N*log2(N) where N is the number of rows in - ** the table being indexed. */ - pNew->rSetup = rLogSize + rSize + 28; assert( 28==sqlite3LogEst(7) ); + ** estimated to be X*N*log2(N) where N is the number of rows in + ** the table being indexed and where X is 7 (LogEst=28) for normal + ** tables or 1.375 (LogEst=4) for views and subqueries. The value + ** of X is smaller for views and subqueries so that the query planner + ** will be more aggressive about generating automatic indexes for + ** those objects, since there is no opportunity to add schema + ** indexes on subqueries and views. */ + pNew->rSetup = rLogSize + rSize + 4; + if( pTab->pSelect==0 && (pTab->tabFlags & TF_Ephemeral)==0 ){ + pNew->rSetup += 24; + } + ApplyCostMultiplier(pNew->rSetup, pTab->costMult); /* TUNING: Each index lookup yields 20 rows in the table. This ** is more than the usual guess of 10 rows, since we have no way - ** of knowning how selective the index will ultimately be. It would + ** of knowing how selective the index will ultimately be. It would ** not be unreasonable to make this value much larger. */ pNew->nOut = 43; assert( 43==sqlite3LogEst(20) ); pNew->rRun = sqlite3LogEstAdd(rLogSize,pNew->nOut); @@ -114597,12 +125255,13 @@ static int whereLoopAddBtree( */ for(; rc==SQLITE_OK && pProbe; pProbe=pProbe->pNext, iSortIdx++){ if( pProbe->pPartIdxWhere!=0 - && !whereUsablePartialIndex(pNew->iTab, pWC, pProbe->pPartIdxWhere) ){ + && !whereUsablePartialIndex(pSrc->iCursor, pWC, pProbe->pPartIdxWhere) ){ + testcase( pNew->iTab!=pSrc->iCursor ); /* See ticket [98d973b8f5] */ continue; /* Partial index inappropriate for this query */ } rSize = pProbe->aiRowLogEst[0]; pNew->u.btree.nEq = 0; - pNew->u.btree.nSkip = 0; + pNew->nSkip = 0; pNew->nLTerm = 0; pNew->iSortIdx = 0; pNew->rSetup = 0; @@ -114620,7 +125279,8 @@ static int whereLoopAddBtree( pNew->iSortIdx = b ? iSortIdx : 0; /* TUNING: Cost of full table scan is (N*3.0). */ pNew->rRun = rSize + 16; - whereLoopOutputAdjust(pWC, pNew); + ApplyCostMultiplier(pNew->rRun, pTab->costMult); + whereLoopOutputAdjust(pWC, pNew, rSize); rc = whereLoopInsert(pBuilder, pNew); pNew->nOut = rSize; if( rc ) break; @@ -114655,8 +125315,8 @@ static int whereLoopAddBtree( if( m!=0 ){ pNew->rRun = sqlite3LogEstAdd(pNew->rRun, rSize+16); } - - whereLoopOutputAdjust(pWC, pNew); + ApplyCostMultiplier(pNew->rRun, pTab->costMult); + whereLoopOutputAdjust(pWC, pNew, rSize); rc = whereLoopInsert(pBuilder, pNew); pNew->nOut = rSize; if( rc ) break; @@ -114672,7 +125332,7 @@ static int whereLoopAddBtree( /* If there was an INDEXED BY clause, then only that one index is ** considered. */ - if( pSrc->pIndex ) break; + if( pSrc->pIBIndex ) break; } return rc; } @@ -114681,10 +125341,32 @@ static int whereLoopAddBtree( /* ** Add all WhereLoop objects for a table of the join identified by ** pBuilder->pNew->iTab. That table is guaranteed to be a virtual table. +** +** If there are no LEFT or CROSS JOIN joins in the query, both mExtra and +** mUnusable are set to 0. Otherwise, mExtra is a mask of all FROM clause +** entries that occur before the virtual table in the FROM clause and are +** separated from it by at least one LEFT or CROSS JOIN. Similarly, the +** mUnusable mask contains all FROM clause entries that occur after the +** virtual table and are separated from it by at least one LEFT or +** CROSS JOIN. +** +** For example, if the query were: +** +** ... FROM t1, t2 LEFT JOIN t3, t4, vt CROSS JOIN t5, t6; +** +** then mExtra corresponds to (t1, t2) and mUnusable to (t5, t6). +** +** All the tables in mExtra must be scanned before the current virtual +** table. So any terms for which all prerequisites are satisfied by +** mExtra may be specified as "usable" in all calls to xBestIndex. +** Conversely, all tables in mUnusable must be scanned after the current +** virtual table, so any terms for which the prerequisites overlap with +** mUnusable should always be configured as "not-usable" for xBestIndex. */ static int whereLoopAddVirtual( WhereLoopBuilder *pBuilder, /* WHERE clause information */ - Bitmask mExtra + Bitmask mExtra, /* Tables that must be scanned before this one */ + Bitmask mUnusable /* Tables that must be scanned after this one */ ){ WhereInfo *pWInfo; /* WHERE analysis context */ Parse *pParse; /* The parsing context */ @@ -114705,6 +125387,7 @@ static int whereLoopAddVirtual( WhereLoop *pNew; int rc = SQLITE_OK; + assert( (mExtra & mUnusable)==0 ); pWInfo = pBuilder->pWInfo; pParse = pWInfo->pParse; db = pParse->db; @@ -114713,7 +125396,7 @@ static int whereLoopAddVirtual( pSrc = &pWInfo->pTabList->a[pNew->iTab]; pTab = pSrc->pTab; assert( IsVirtual(pTab) ); - pIdxInfo = allocateIndexInfo(pParse, pWC, pSrc, pBuilder->pOrderBy); + pIdxInfo = allocateIndexInfo(pParse, pWC, mUnusable, pSrc,pBuilder->pOrderBy); if( pIdxInfo==0 ) return SQLITE_NOMEM; pNew->prereq = 0; pNew->rSetup = 0; @@ -114743,7 +125426,7 @@ static int whereLoopAddVirtual( if( (pTerm->eOperator & WO_IN)!=0 ){ seenIn = 1; } - if( pTerm->prereqRight!=0 ){ + if( (pTerm->prereqRight & ~mExtra)!=0 ){ seenVar = 1; }else if( (pTerm->eOperator & WO_IN)==0 ){ pIdxCons->usable = 1; @@ -114751,7 +125434,7 @@ static int whereLoopAddVirtual( break; case 1: /* Constants with IN operators */ assert( seenIn ); - pIdxCons->usable = (pTerm->prereqRight==0); + pIdxCons->usable = (pTerm->prereqRight & ~mExtra)==0; break; case 2: /* Variables without IN */ assert( seenVar ); @@ -114771,6 +125454,8 @@ static int whereLoopAddVirtual( pIdxInfo->orderByConsumed = 0; pIdxInfo->estimatedCost = SQLITE_BIG_DBL / (double)2; pIdxInfo->estimatedRows = 25; + pIdxInfo->idxFlags = 0; + pIdxInfo->colUsed = (sqlite3_int64)pSrc->colUsed; rc = vtabBestIndex(pParse, pTab, pIdxInfo); if( rc ) goto whereLoopAddVtab_exit; pIdxCons = *(struct sqlite3_index_constraint**)&pIdxInfo->aConstraint; @@ -114816,6 +125501,7 @@ static int whereLoopAddVirtual( ** (2) Multiple outputs from a single IN value will not merge ** together. */ pIdxInfo->orderByConsumed = 0; + pIdxInfo->idxFlags &= ~SQLITE_INDEX_SCAN_UNIQUE; } } } @@ -114831,6 +125517,14 @@ static int whereLoopAddVirtual( pNew->rSetup = 0; pNew->rRun = sqlite3LogEstFromDouble(pIdxInfo->estimatedCost); pNew->nOut = sqlite3LogEst(pIdxInfo->estimatedRows); + + /* Set the WHERE_ONEROW flag if the xBestIndex() method indicated + ** that the scan will visit at most one row. Clear it otherwise. */ + if( pIdxInfo->idxFlags & SQLITE_INDEX_SCAN_UNIQUE ){ + pNew->wsFlags |= WHERE_ONEROW; + }else{ + pNew->wsFlags &= ~WHERE_ONEROW; + } whereLoopInsert(pBuilder, pNew); if( pNew->u.vtab.needFree ){ sqlite3_free(pNew->u.vtab.idxStr); @@ -114850,7 +125544,11 @@ whereLoopAddVtab_exit: ** Add WhereLoop entries to handle OR terms. This works for either ** btrees or virtual tables. */ -static int whereLoopAddOr(WhereLoopBuilder *pBuilder, Bitmask mExtra){ +static int whereLoopAddOr( + WhereLoopBuilder *pBuilder, + Bitmask mExtra, + Bitmask mUnusable +){ WhereInfo *pWInfo = pBuilder->pWInfo; WhereClause *pWC; WhereLoop *pNew; @@ -114863,7 +125561,6 @@ static int whereLoopAddOr(WhereLoopBuilder *pBuilder, Bitmask mExtra){ struct SrcList_item *pItem; pWC = pBuilder->pWC; - if( pWInfo->wctrlFlags & WHERE_AND_ONLY ) return SQLITE_OK; pWCEnd = pWC->a + pWC->nTerm; pNew = pBuilder->pNew; memset(&sSum, 0, sizeof(sSum)); @@ -114884,6 +125581,7 @@ static int whereLoopAddOr(WhereLoopBuilder *pBuilder, Bitmask mExtra){ sSubBuild.pOrderBy = 0; sSubBuild.pOrSet = &sCur; + WHERETRACE(0x200, ("Begin processing OR-clause %p\n", pTerm)); for(pOrTerm=pOrWC->a; pOrTermeOperator & WO_AND)!=0 ){ sSubBuild.pWC = &pOrTerm->u.pAndInfo->wc; @@ -114898,14 +125596,26 @@ static int whereLoopAddOr(WhereLoopBuilder *pBuilder, Bitmask mExtra){ continue; } sCur.n = 0; +#ifdef WHERETRACE_ENABLED + WHERETRACE(0x200, ("OR-term %d of %p has %d subterms:\n", + (int)(pOrTerm-pOrWC->a), pTerm, sSubBuild.pWC->nTerm)); + if( sqlite3WhereTrace & 0x400 ){ + for(i=0; inTerm; i++){ + whereTermPrint(&sSubBuild.pWC->a[i], i); + } + } +#endif #ifndef SQLITE_OMIT_VIRTUALTABLE if( IsVirtual(pItem->pTab) ){ - rc = whereLoopAddVirtual(&sSubBuild, mExtra); + rc = whereLoopAddVirtual(&sSubBuild, mExtra, mUnusable); }else #endif { rc = whereLoopAddBtree(&sSubBuild, mExtra); } + if( rc==SQLITE_OK ){ + rc = whereLoopAddOr(&sSubBuild, mExtra, mUnusable); + } assert( rc==SQLITE_OK || sCur.n==0 ); if( sCur.n==0 ){ sSum.n = 0; @@ -114950,6 +125660,7 @@ static int whereLoopAddOr(WhereLoopBuilder *pBuilder, Bitmask mExtra){ pNew->prereq = sSum.a[i].prereq; rc = whereLoopInsert(pBuilder, pNew); } + WHERETRACE(0x200, ("End processing OR-clause %p\n", pTerm)); } } return rc; @@ -114965,33 +125676,43 @@ static int whereLoopAddAll(WhereLoopBuilder *pBuilder){ int iTab; SrcList *pTabList = pWInfo->pTabList; struct SrcList_item *pItem; + struct SrcList_item *pEnd = &pTabList->a[pWInfo->nLevel]; sqlite3 *db = pWInfo->pParse->db; - int nTabList = pWInfo->nLevel; int rc = SQLITE_OK; - u8 priorJoinType = 0; WhereLoop *pNew; + u8 priorJointype = 0; /* Loop over the tables in the join, from left to right */ pNew = pBuilder->pNew; whereLoopInit(pNew); - for(iTab=0, pItem=pTabList->a; iTaba; pItemiTab = iTab; - pNew->maskSelf = getMask(&pWInfo->sMaskSet, pItem->iCursor); - if( ((pItem->jointype|priorJoinType) & (JT_LEFT|JT_CROSS))!=0 ){ + pNew->maskSelf = sqlite3WhereGetMask(&pWInfo->sMaskSet, pItem->iCursor); + if( ((pItem->fg.jointype|priorJointype) & (JT_LEFT|JT_CROSS))!=0 ){ + /* This condition is true when pItem is the FROM clause term on the + ** right-hand-side of a LEFT or CROSS JOIN. */ mExtra = mPrior; } - priorJoinType = pItem->jointype; + priorJointype = pItem->fg.jointype; if( IsVirtual(pItem->pTab) ){ - rc = whereLoopAddVirtual(pBuilder, mExtra); + struct SrcList_item *p; + for(p=&pItem[1]; pfg.jointype & (JT_LEFT|JT_CROSS)) ){ + mUnusable |= sqlite3WhereGetMask(&pWInfo->sMaskSet, p->iCursor); + } + } + rc = whereLoopAddVirtual(pBuilder, mExtra, mUnusable); }else{ rc = whereLoopAddBtree(pBuilder, mExtra); } if( rc==SQLITE_OK ){ - rc = whereLoopAddOr(pBuilder, mExtra); + rc = whereLoopAddOr(pBuilder, mExtra, mUnusable); } mPrior |= pNew->maskSelf; if( rc || db->mallocFailed ) break; } + whereLoopClear(db, pNew); return rc; } @@ -115009,7 +125730,7 @@ static int whereLoopAddAll(WhereLoopBuilder *pBuilder){ ** strict. With GROUP BY and DISTINCT the only requirement is that ** equivalent rows appear immediately adjacent to one another. GROUP BY ** and DISTINCT do not require rows to appear in any particular order as long -** as equivelent rows are grouped together. Thus for GROUP BY and DISTINCT +** as equivalent rows are grouped together. Thus for GROUP BY and DISTINCT ** the pOrderBy terms can be matched in any order. With ORDER BY, the ** pOrderBy terms must be matched in strict left-to-right order. */ @@ -115097,10 +125818,10 @@ static i8 wherePathSatisfiesOrderBy( pOBExpr = sqlite3ExprSkipCollate(pOrderBy->a[i].pExpr); if( pOBExpr->op!=TK_COLUMN ) continue; if( pOBExpr->iTable!=iCur ) continue; - pTerm = findTerm(&pWInfo->sWC, iCur, pOBExpr->iColumn, - ~ready, WO_EQ|WO_ISNULL, 0); + pTerm = sqlite3WhereFindTerm(&pWInfo->sWC, iCur, pOBExpr->iColumn, + ~ready, WO_EQ|WO_ISNULL|WO_IS, 0); if( pTerm==0 ) continue; - if( (pTerm->eOperator&WO_EQ)!=0 && pOBExpr->iColumn>=0 ){ + if( (pTerm->eOperator&(WO_EQ|WO_IS))!=0 && pOBExpr->iColumn>=0 ){ const char *z1, *z2; pColl = sqlite3ExprCollSeq(pWInfo->pParse, pOrderBy->a[i].pExpr); if( !pColl ) pColl = db->pDfltColl; @@ -115109,6 +125830,7 @@ static i8 wherePathSatisfiesOrderBy( if( !pColl ) pColl = db->pDfltColl; z2 = pColl->zName; if( sqlite3StrICmp(z1, z2)!=0 ) continue; + testcase( pTerm->pExpr->op==TK_IS ); } obSat |= MASKBIT(i); } @@ -115124,8 +125846,9 @@ static i8 wherePathSatisfiesOrderBy( nKeyCol = pIndex->nKeyCol; nColumn = pIndex->nColumn; assert( nColumn==nKeyCol+1 || !HasRowid(pIndex->pTable) ); - assert( pIndex->aiColumn[nColumn-1]==(-1) || !HasRowid(pIndex->pTable)); - isOrderDistinct = pIndex->onError!=OE_None; + assert( pIndex->aiColumn[nColumn-1]==XN_ROWID + || !HasRowid(pIndex->pTable)); + isOrderDistinct = IsUniqueIndex(pIndex); } /* Loop through all columns of the index and deal with the ones @@ -115138,8 +125861,8 @@ static i8 wherePathSatisfiesOrderBy( /* Skip over == and IS NULL terms */ if( ju.btree.nEq - && pLoop->u.btree.nSkip==0 - && ((i = pLoop->aLTerm[j]->eOperator) & (WO_EQ|WO_ISNULL))!=0 + && pLoop->nSkip==0 + && ((i = pLoop->aLTerm[j]->eOperator) & (WO_EQ|WO_ISNULL|WO_IS))!=0 ){ if( i & WO_ISNULL ){ testcase( isOrderDistinct ); @@ -115156,7 +125879,7 @@ static i8 wherePathSatisfiesOrderBy( revIdx = pIndex->aSortOrder[j]; if( iColumn==pIndex->pTable->iPKey ) iColumn = -1; }else{ - iColumn = -1; + iColumn = XN_ROWID; revIdx = 0; } @@ -115182,9 +125905,15 @@ static i8 wherePathSatisfiesOrderBy( testcase( wctrlFlags & WHERE_GROUPBY ); testcase( wctrlFlags & WHERE_DISTINCTBY ); if( (wctrlFlags & (WHERE_GROUPBY|WHERE_DISTINCTBY))==0 ) bOnce = 0; - if( pOBExpr->op!=TK_COLUMN ) continue; - if( pOBExpr->iTable!=iCur ) continue; - if( pOBExpr->iColumn!=iColumn ) continue; + if( iColumn>=(-1) ){ + if( pOBExpr->op!=TK_COLUMN ) continue; + if( pOBExpr->iTable!=iCur ) continue; + if( pOBExpr->iColumn!=iColumn ) continue; + }else{ + if( sqlite3ExprCompare(pOBExpr,pIndex->aColExpr->a[j].pExpr,iCur) ){ + continue; + } + } if( iColumn>=0 ){ pColl = sqlite3ExprCollSeq(pWInfo->pParse, pOrderBy->a[i].pExpr); if( !pColl ) pColl = db->pDfltColl; @@ -115193,7 +125922,7 @@ static i8 wherePathSatisfiesOrderBy( isMatch = 1; break; } - if( isMatch && (pWInfo->wctrlFlags & WHERE_GROUPBY)==0 ){ + if( isMatch && (wctrlFlags & WHERE_GROUPBY)==0 ){ /* Make sure the sort order is compatible in an ORDER BY clause. ** Sort order is irrelevant for a GROUP BY clause. */ if( revSet ){ @@ -115233,7 +125962,7 @@ static i8 wherePathSatisfiesOrderBy( Bitmask mTerm; if( MASKBIT(i) & obSat ) continue; p = pOrderBy->a[i].pExpr; - mTerm = exprTableUsage(&pWInfo->sMaskSet,p); + mTerm = sqlite3WhereExprUsage(&pWInfo->sMaskSet,p); if( mTerm==0 && !sqlite3ExprIsConstant(p) ) continue; if( (mTerm&~orderDistinctMask)==0 ){ obSat |= MASKBIT(i); @@ -115294,6 +126023,45 @@ static const char *wherePathName(WherePath *pPath, int nLoop, WhereLoop *pLast){ } #endif +/* +** Return the cost of sorting nRow rows, assuming that the keys have +** nOrderby columns and that the first nSorted columns are already in +** order. +*/ +static LogEst whereSortingCost( + WhereInfo *pWInfo, + LogEst nRow, + int nOrderBy, + int nSorted +){ + /* TUNING: Estimated cost of a full external sort, where N is + ** the number of rows to sort is: + ** + ** cost = (3.0 * N * log(N)). + ** + ** Or, if the order-by clause has X terms but only the last Y + ** terms are out of order, then block-sorting will reduce the + ** sorting cost to: + ** + ** cost = (3.0 * N * log(N)) * (Y/X) + ** + ** The (Y/X) term is implemented using stack variable rScale + ** below. */ + LogEst rScale, rSortCost; + assert( nOrderBy>0 && 66==sqlite3LogEst(100) ); + rScale = sqlite3LogEst((nOrderBy-nSorted)*100/nOrderBy) - 66; + rSortCost = nRow + estLog(nRow) + rScale + 16; + + /* TUNING: The cost of implementing DISTINCT using a B-TREE is + ** similar but with a larger constant of proportionality. + ** Multiply by an additional factor of 3.0. */ + if( pWInfo->wctrlFlags & WHERE_WANT_DISTINCT ){ + rSortCost += 16; + } + + return rSortCost; +} + /* ** Given the list of WhereLoop objects at pWInfo->pLoops, this routine ** attempts to find the lowest cost path that visits each WhereLoop @@ -115315,10 +126083,8 @@ static int wherePathSolver(WhereInfo *pWInfo, LogEst nRowEst){ int ii, jj; /* Loop counters */ int mxI = 0; /* Index of next entry to replace */ int nOrderBy; /* Number of ORDER BY clause terms */ - LogEst rCost; /* Cost of a path */ - LogEst nOut; /* Number of outputs */ LogEst mxCost = 0; /* Maximum cost of a set of paths */ - LogEst mxOut = 0; /* Maximum nOut value on the set of paths */ + LogEst mxUnsorted = 0; /* Maximum unsorted cost of a set of path */ int nTo, nFrom; /* Number of valid entries in aTo[] and aFrom[] */ WherePath *aFrom; /* All nFrom paths at the previous level */ WherePath *aTo; /* The nTo best paths at the current level */ @@ -115326,7 +126092,9 @@ static int wherePathSolver(WhereInfo *pWInfo, LogEst nRowEst){ WherePath *pTo; /* An element of aTo[] that we are working on */ WhereLoop *pWLoop; /* One of the WhereLoop objects */ WhereLoop **pX; /* Used to divy up the pSpace memory */ + LogEst *aSortCost = 0; /* Sorting and partial sorting costs */ char *pSpace; /* Temporary memory used by this routine */ + int nSpace; /* Bytes of space allocated at pSpace */ pParse = pWInfo->pParse; db = pParse->db; @@ -115336,11 +126104,23 @@ static int wherePathSolver(WhereInfo *pWInfo, LogEst nRowEst){ ** For joins of 3 or more tables, track the 10 best paths */ mxChoice = (nLoop<=1) ? 1 : (nLoop==2 ? 5 : 10); assert( nLoop<=pWInfo->pTabList->nSrc ); - WHERETRACE(0x002, ("---- begin solver\n")); + WHERETRACE(0x002, ("---- begin solver. (nRowEst=%d)\n", nRowEst)); - /* Allocate and initialize space for aTo and aFrom */ - ii = (sizeof(WherePath)+sizeof(WhereLoop*)*nLoop)*mxChoice*2; - pSpace = sqlite3DbMallocRaw(db, ii); + /* If nRowEst is zero and there is an ORDER BY clause, ignore it. In this + ** case the purpose of this call is to estimate the number of rows returned + ** by the overall query. Once this estimate has been obtained, the caller + ** will invoke this function a second time, passing the estimate as the + ** nRowEst parameter. */ + if( pWInfo->pOrderBy==0 || nRowEst==0 ){ + nOrderBy = 0; + }else{ + nOrderBy = pWInfo->pOrderBy->nExpr; + } + + /* Allocate and initialize space for aTo, aFrom and aSortCost[] */ + nSpace = (sizeof(WherePath)+sizeof(WhereLoop*)*nLoop)*mxChoice*2; + nSpace += sizeof(LogEst) * nOrderBy; + pSpace = sqlite3DbMallocRaw(db, nSpace); if( pSpace==0 ) return SQLITE_NOMEM; aTo = (WherePath*)pSpace; aFrom = aTo+mxChoice; @@ -115349,23 +126129,35 @@ static int wherePathSolver(WhereInfo *pWInfo, LogEst nRowEst){ for(ii=mxChoice*2, pFrom=aTo; ii>0; ii--, pFrom++, pX += nLoop){ pFrom->aLoop = pX; } + if( nOrderBy ){ + /* If there is an ORDER BY clause and it is not being ignored, set up + ** space for the aSortCost[] array. Each element of the aSortCost array + ** is either zero - meaning it has not yet been initialized - or the + ** cost of sorting nRowEst rows of data where the first X terms of + ** the ORDER BY clause are already in order, where X is the array + ** index. */ + aSortCost = (LogEst*)pX; + memset(aSortCost, 0, sizeof(LogEst) * nOrderBy); + } + assert( aSortCost==0 || &pSpace[nSpace]==(char*)&aSortCost[nOrderBy] ); + assert( aSortCost!=0 || &pSpace[nSpace]==(char*)pX ); /* Seed the search with a single WherePath containing zero WhereLoops. ** - ** TUNING: Do not let the number of iterations go above 25. If the cost - ** of computing an automatic index is not paid back within the first 25 + ** TUNING: Do not let the number of iterations go above 28. If the cost + ** of computing an automatic index is not paid back within the first 28 ** rows, then do not use the automatic index. */ - aFrom[0].nRow = MIN(pParse->nQueryLoop, 46); assert( 46==sqlite3LogEst(25) ); + aFrom[0].nRow = MIN(pParse->nQueryLoop, 48); assert( 48==sqlite3LogEst(28) ); nFrom = 1; - - /* Precompute the cost of sorting the final result set, if the caller - ** to sqlite3WhereBegin() was concerned about sorting */ - if( pWInfo->pOrderBy==0 || nRowEst==0 ){ - aFrom[0].isOrdered = 0; - nOrderBy = 0; - }else{ - aFrom[0].isOrdered = nLoop>0 ? -1 : 1; - nOrderBy = pWInfo->pOrderBy->nExpr; + assert( aFrom[0].isOrdered==0 ); + if( nOrderBy ){ + /* If nLoop is zero, then there are no FROM terms in the query. Since + ** in this case the query may return a maximum of one row, the results + ** are already in the requested order. Set isOrdered to nOrderBy to + ** indicate this. Or, if nLoop is greater than zero, set isOrdered to + ** -1, indicating that the result set may or may not be ordered, + ** depending on the loops added to the current plan. */ + aFrom[0].isOrdered = nLoop>0 ? -1 : nOrderBy; } /* Compute successively longer WherePaths using the previous generation @@ -115375,68 +126167,71 @@ static int wherePathSolver(WhereInfo *pWInfo, LogEst nRowEst){ nTo = 0; for(ii=0, pFrom=aFrom; iipLoops; pWLoop; pWLoop=pWLoop->pNextLoop){ - Bitmask maskNew; - Bitmask revMask = 0; - i8 isOrdered = pFrom->isOrdered; + LogEst nOut; /* Rows visited by (pFrom+pWLoop) */ + LogEst rCost; /* Cost of path (pFrom+pWLoop) */ + LogEst rUnsorted; /* Unsorted cost of (pFrom+pWLoop) */ + i8 isOrdered = pFrom->isOrdered; /* isOrdered for (pFrom+pWLoop) */ + Bitmask maskNew; /* Mask of src visited by (..) */ + Bitmask revMask = 0; /* Mask of rev-order loops for (..) */ + if( (pWLoop->prereq & ~pFrom->maskLoop)!=0 ) continue; if( (pWLoop->maskSelf & pFrom->maskLoop)!=0 ) continue; /* At this point, pWLoop is a candidate to be the next loop. ** Compute its cost */ - rCost = sqlite3LogEstAdd(pWLoop->rSetup,pWLoop->rRun + pFrom->nRow); - rCost = sqlite3LogEstAdd(rCost, pFrom->rCost); + rUnsorted = sqlite3LogEstAdd(pWLoop->rSetup,pWLoop->rRun + pFrom->nRow); + rUnsorted = sqlite3LogEstAdd(rUnsorted, pFrom->rUnsorted); nOut = pFrom->nRow + pWLoop->nOut; maskNew = pFrom->maskLoop | pWLoop->maskSelf; if( isOrdered<0 ){ isOrdered = wherePathSatisfiesOrderBy(pWInfo, pWInfo->pOrderBy, pFrom, pWInfo->wctrlFlags, iLoop, pWLoop, &revMask); - if( isOrdered>=0 && isOrdered0 && 66==sqlite3LogEst(100) ); - rScale = sqlite3LogEst((nOrderBy-isOrdered)*100/nOrderBy) - 66; - rSortCost = nRowEst + estLog(nRowEst) + rScale + 16; - - /* TUNING: The cost of implementing DISTINCT using a B-TREE is - ** similar but with a larger constant of proportionality. - ** Multiply by an additional factor of 3.0. */ - if( pWInfo->wctrlFlags & WHERE_WANT_DISTINCT ){ - rSortCost += 16; - } - WHERETRACE(0x002, - ("---- sort cost=%-3d (%d/%d) increases cost %3d to %-3d\n", - rSortCost, (nOrderBy-isOrdered), nOrderBy, rCost, - sqlite3LogEstAdd(rCost,rSortCost))); - rCost = sqlite3LogEstAdd(rCost, rSortCost); - } }else{ revMask = pFrom->revLoop; } - /* Check to see if pWLoop should be added to the mxChoice best so far */ + if( isOrdered>=0 && isOrderedisOrdered^isOrdered)&0x80)==0" is equivalent + ** to (pTo->isOrdered==(-1))==(isOrdered==(-1))" for the range + ** of legal values for isOrdered, -1..64. + */ for(jj=0, pTo=aTo; jjmaskLoop==maskNew - && ((pTo->isOrdered^isOrdered)&80)==0 - && ((pTo->rCost<=rCost && pTo->nRow<=nOut) || - (pTo->rCost>=rCost && pTo->nRow>=nOut)) + && ((pTo->isOrdered^isOrdered)&0x80)==0 ){ testcase( jj==nTo-1 ); break; } } if( jj>=nTo ){ - if( nTo>=mxChoice && rCost>=mxCost ){ + /* None of the existing best-so-far paths match the candidate. */ + if( nTo>=mxChoice + && (rCost>mxCost || (rCost==mxCost && rUnsorted>=mxUnsorted)) + ){ + /* The current candidate is no better than any of the mxChoice + ** paths currently in the best-so-far buffer. So discard + ** this candidate as not viable. */ #ifdef WHERETRACE_ENABLED /* 0x4 */ if( sqlite3WhereTrace&0x4 ){ sqlite3DebugPrintf("Skip %s cost=%-3d,%3d order=%c\n", @@ -115446,7 +126241,8 @@ static int wherePathSolver(WhereInfo *pWInfo, LogEst nRowEst){ #endif continue; } - /* Add a new Path to the aTo[] set */ + /* If we reach this points it means that the new candidate path + ** needs to be added to the set of best-so-far paths. */ if( nTorCost<=rCost && pTo->nRow<=nOut ){ + /* Control reaches here if best-so-far path pTo=aTo[jj] covers the + ** same set of loops and has the sam isOrdered setting as the + ** candidate path. Check to see if the candidate should replace + ** pTo or if the candidate should be skipped */ + if( pTo->rCostrCost==rCost && pTo->nRow<=nOut) ){ #ifdef WHERETRACE_ENABLED /* 0x4 */ if( sqlite3WhereTrace&0x4 ){ sqlite3DebugPrintf( @@ -115475,11 +126275,13 @@ static int wherePathSolver(WhereInfo *pWInfo, LogEst nRowEst){ pTo->isOrdered>=0 ? pTo->isOrdered+'0' : '?'); } #endif + /* Discard the candidate path from further consideration */ testcase( pTo->rCost==rCost ); continue; } testcase( pTo->rCost==rCost+1 ); - /* A new and better score for a previously created equivalent path */ + /* Control reaches here if the candidate path is better than the + ** pTo path. Replace pTo with the candidate. */ #ifdef WHERETRACE_ENABLED /* 0x4 */ if( sqlite3WhereTrace&0x4 ){ sqlite3DebugPrintf( @@ -115497,17 +126299,20 @@ static int wherePathSolver(WhereInfo *pWInfo, LogEst nRowEst){ pTo->revLoop = revMask; pTo->nRow = nOut; pTo->rCost = rCost; + pTo->rUnsorted = rUnsorted; pTo->isOrdered = isOrdered; memcpy(pTo->aLoop, pFrom->aLoop, sizeof(WhereLoop*)*iLoop); pTo->aLoop[iLoop] = pWLoop; if( nTo>=mxChoice ){ mxI = 0; mxCost = aTo[0].rCost; - mxOut = aTo[0].nRow; + mxUnsorted = aTo[0].nRow; for(jj=1, pTo=&aTo[1]; jjrCost>mxCost || (pTo->rCost==mxCost && pTo->nRow>mxOut) ){ + if( pTo->rCost>mxCost + || (pTo->rCost==mxCost && pTo->rUnsorted>mxUnsorted) + ){ mxCost = pTo->rCost; - mxOut = pTo->nRow; + mxUnsorted = pTo->rUnsorted; mxI = jj; } } @@ -115516,7 +126321,7 @@ static int wherePathSolver(WhereInfo *pWInfo, LogEst nRowEst){ } #ifdef WHERETRACE_ENABLED /* >=2 */ - if( sqlite3WhereTrace>=2 ){ + if( sqlite3WhereTrace & 0x02 ){ sqlite3DebugPrintf("---- after round %d ----\n", iLoop); for(ii=0, pTo=aTo; iirevMask = pFrom->revLoop; } if( (pWInfo->wctrlFlags & WHERE_SORTBYGROUP) - && pWInfo->nOBSat==pWInfo->pOrderBy->nExpr + && pWInfo->nOBSat==pWInfo->pOrderBy->nExpr && nLoop>0 ){ - Bitmask notUsed = 0; + Bitmask revMask = 0; int nOrder = wherePathSatisfiesOrderBy(pWInfo, pWInfo->pOrderBy, - pFrom, 0, nLoop-1, pFrom->aLoop[nLoop-1], ¬Used + pFrom, 0, nLoop-1, pFrom->aLoop[nLoop-1], &revMask ); assert( pWInfo->sorted==0 ); - pWInfo->sorted = (nOrder==pWInfo->pOrderBy->nExpr); + if( nOrder==pWInfo->pOrderBy->nExpr ){ + pWInfo->sorted = 1; + pWInfo->revMask = revMask; + } } } @@ -115627,14 +126435,15 @@ static int whereShortCut(WhereLoopBuilder *pBuilder){ pItem = pWInfo->pTabList->a; pTab = pItem->pTab; if( IsVirtual(pTab) ) return 0; - if( pItem->zIndex ) return 0; + if( pItem->fg.isIndexedBy ) return 0; iCur = pItem->iCursor; pWC = &pWInfo->sWC; pLoop = pBuilder->pNew; pLoop->wsFlags = 0; - pLoop->u.btree.nSkip = 0; - pTerm = findTerm(pWC, iCur, -1, 0, WO_EQ, 0); + pLoop->nSkip = 0; + pTerm = sqlite3WhereFindTerm(pWC, iCur, -1, 0, WO_EQ|WO_IS, 0); if( pTerm ){ + testcase( pTerm->eOperator & WO_IS ); pLoop->wsFlags = WHERE_COLUMN_EQ|WHERE_IPK|WHERE_ONEROW; pLoop->aLTerm[0] = pTerm; pLoop->nLTerm = 1; @@ -115643,15 +126452,17 @@ static int whereShortCut(WhereLoopBuilder *pBuilder){ pLoop->rRun = 33; /* 33==sqlite3LogEst(10) */ }else{ for(pIdx=pTab->pIndex; pIdx; pIdx=pIdx->pNext){ + int opMask; assert( pLoop->aLTermSpace==pLoop->aLTerm ); - assert( ArraySize(pLoop->aLTermSpace)==4 ); - if( pIdx->onError==OE_None + if( !IsUniqueIndex(pIdx) || pIdx->pPartIdxWhere!=0 || pIdx->nKeyCol>ArraySize(pLoop->aLTermSpace) ) continue; + opMask = pIdx->uniqNotNull ? (WO_EQ|WO_IS) : WO_EQ; for(j=0; jnKeyCol; j++){ - pTerm = findTerm(pWC, iCur, pIdx->aiColumn[j], 0, WO_EQ, pIdx); + pTerm = sqlite3WhereFindTerm(pWC, iCur, j, 0, opMask, pIdx); if( pTerm==0 ) break; + testcase( pTerm->eOperator & WO_IS ); pLoop->aLTerm[j] = pTerm; } if( j!=pIdx->nKeyCol ) continue; @@ -115670,7 +126481,7 @@ static int whereShortCut(WhereLoopBuilder *pBuilder){ if( pLoop->wsFlags ){ pLoop->nOut = (LogEst)1; pWInfo->a[0].pWLoop = pLoop; - pLoop->maskSelf = getMask(&pWInfo->sMaskSet, iCur); + pLoop->maskSelf = sqlite3WhereGetMask(&pWInfo->sMaskSet, iCur); pWInfo->a[0].iTabCur = iCur; pWInfo->nRowOut = 1; if( pWInfo->pOrderBy ) pWInfo->nOBSat = pWInfo->pOrderBy->nExpr; @@ -115794,7 +126605,12 @@ SQLITE_PRIVATE WhereInfo *sqlite3WhereBegin( int ii; /* Loop counter */ sqlite3 *db; /* Database connection */ int rc; /* Return code */ + u8 bFordelete = 0; + assert( (wctrlFlags & WHERE_ONEPASS_MULTIROW)==0 || ( + (wctrlFlags & WHERE_ONEPASS_DESIRED)!=0 + && (wctrlFlags & WHERE_OMIT_OPEN_CLOSE)==0 + )); /* Variable initialization */ db = pParse->db; @@ -115850,6 +126666,7 @@ SQLITE_PRIVATE WhereInfo *sqlite3WhereBegin( pWInfo->iBreak = pWInfo->iContinue = sqlite3VdbeMakeLabel(v); pWInfo->wctrlFlags = wctrlFlags; pWInfo->savedNQueryLoop = pParse->nQueryLoop; + assert( pWInfo->eOnePass==ONEPASS_OFF ); /* ONEPASS defaults to OFF */ pMaskSet = &pWInfo->sMaskSet; sWLB.pWInfo = pWInfo; sWLB.pWC = &pWInfo->sWC; @@ -115864,8 +126681,8 @@ SQLITE_PRIVATE WhereInfo *sqlite3WhereBegin( ** subexpression is separated by an AND operator. */ initMaskSet(pMaskSet); - whereClauseInit(&pWInfo->sWC, pWInfo); - whereSplit(&pWInfo->sWC, pWhere, TK_AND); + sqlite3WhereClauseInit(&pWInfo->sWC, pWInfo); + sqlite3WhereSplit(&pWInfo->sWC, pWhere, TK_AND); /* Special case: a WHERE clause that is constant. Evaluate the ** expression and either jump over all of the code or fall thru. @@ -115889,14 +126706,12 @@ SQLITE_PRIVATE WhereInfo *sqlite3WhereBegin( /* Assign a bit from the bitmask to every term in the FROM clause. ** - ** When assigning bitmask values to FROM clause cursors, it must be - ** the case that if X is the bitmask for the N-th FROM clause term then - ** the bitmask for all FROM clause terms to the left of the N-th term - ** is (X-1). An expression from the ON clause of a LEFT JOIN can use - ** its Expr.iRightJoinTable value to find the bitmask of the right table - ** of the join. Subtracting one from the right table bitmask gives a - ** bitmask for all tables to the left of the join. Knowing the bitmask - ** for all tables to the left of a left join is important. Ticket #3015. + ** The N-th term of the FROM clause is assigned a bitmask of 1<nSrc tables in ** pTabList, not just the first nTabList tables. nTabList is normally @@ -115905,27 +126720,18 @@ SQLITE_PRIVATE WhereInfo *sqlite3WhereBegin( */ for(ii=0; iinSrc; ii++){ createMask(pMaskSet, pTabList->a[ii].iCursor); + sqlite3WhereTabFuncArgs(pParse, &pTabList->a[ii], &pWInfo->sWC); } -#ifndef NDEBUG - { - Bitmask toTheLeft = 0; - for(ii=0; iinSrc; ii++){ - Bitmask m = getMask(pMaskSet, pTabList->a[ii].iCursor); - assert( (m-1)==toTheLeft ); - toTheLeft |= m; - } +#ifdef SQLITE_DEBUG + for(ii=0; iinSrc; ii++){ + Bitmask m = sqlite3WhereGetMask(pMaskSet, pTabList->a[ii].iCursor); + assert( m==MASKBIT(ii) ); } #endif - /* Analyze all of the subexpressions. Note that exprAnalyze() might - ** add new virtual terms onto the end of the WHERE clause. We do not - ** want to analyze these virtual terms, so start analyzing at the end - ** and work forward so that the added virtual terms are never processed. - */ - exprAnalyzeAll(pTabList, &pWInfo->sWC); - if( db->mallocFailed ){ - goto whereBeginError; - } + /* Analyze all of the subexpressions. */ + sqlite3WhereExprAnalyze(pTabList, &pWInfo->sWC); + if( db->mallocFailed ) goto whereBeginError; if( wctrlFlags & WHERE_WANT_DISTINCT ){ if( isDistinctRedundant(pParse, pTabList, &pWInfo->sWC, pResultSet) ){ @@ -115939,35 +126745,27 @@ SQLITE_PRIVATE WhereInfo *sqlite3WhereBegin( } /* Construct the WhereLoop objects */ - WHERETRACE(0xffff,("*** Optimizer Start ***\n")); - /* Display all terms of the WHERE clause */ -#if defined(WHERETRACE_ENABLED) && defined(SQLITE_ENABLE_TREE_EXPLAIN) - if( sqlite3WhereTrace & 0x100 ){ + WHERETRACE(0xffff,("*** Optimizer Start *** (wctrlFlags: 0x%x)\n", + wctrlFlags)); +#if defined(WHERETRACE_ENABLED) + if( sqlite3WhereTrace & 0x100 ){ /* Display all terms of the WHERE clause */ int i; - Vdbe *v = pParse->pVdbe; - sqlite3ExplainBegin(v); for(i=0; inTerm; i++){ - sqlite3ExplainPrintf(v, "#%-2d ", i); - sqlite3ExplainPush(v); - whereExplainTerm(v, &sWLB.pWC->a[i]); - sqlite3ExplainPop(v); - sqlite3ExplainNL(v); + whereTermPrint(&sWLB.pWC->a[i], i); } - sqlite3ExplainFinish(v); - sqlite3DebugPrintf("%s", sqlite3VdbeExplanation(v)); } #endif + if( nTabList!=1 || whereShortCut(&sWLB)==0 ){ rc = whereLoopAddAll(&sWLB); if( rc ) goto whereBeginError; - /* Display all of the WhereLoop objects if wheretrace is enabled */ -#ifdef WHERETRACE_ENABLED /* !=0 */ - if( sqlite3WhereTrace ){ +#ifdef WHERETRACE_ENABLED + if( sqlite3WhereTrace ){ /* Display all of the WhereLoop objects */ WhereLoop *p; int i; - static char zLabel[] = "0123456789abcdefghijklmnopqrstuvwyxz" - "ABCDEFGHIJKLMNOPQRSTUVWYXZ"; + static const char zLabel[] = "0123456789abcdefghijklmnopqrstuvwyxz" + "ABCDEFGHIJKLMNOPQRSTUVWYXZ"; for(p=pWInfo->pLoops, i=0; p; p=p->pNextLoop, i++){ p->cId = zLabel[i%sizeof(zLabel)]; whereLoopPrint(p, sWLB.pWC); @@ -115988,9 +126786,8 @@ SQLITE_PRIVATE WhereInfo *sqlite3WhereBegin( if( pParse->nErr || NEVER(db->mallocFailed) ){ goto whereBeginError; } -#ifdef WHERETRACE_ENABLED /* !=0 */ +#ifdef WHERETRACE_ENABLED if( sqlite3WhereTrace ){ - int ii; sqlite3DebugPrintf("---- Solution nRow=%d", pWInfo->nRowOut); if( pWInfo->nOBSat>0 ){ sqlite3DebugPrintf(" ORDERBY=%d,0x%llx", pWInfo->nOBSat, pWInfo->revMask); @@ -116020,12 +126817,14 @@ SQLITE_PRIVATE WhereInfo *sqlite3WhereBegin( && pResultSet!=0 && OptimizationEnabled(db, SQLITE_OmitNoopJoin) ){ - Bitmask tabUsed = exprListTableUsage(pMaskSet, pResultSet); - if( sWLB.pOrderBy ) tabUsed |= exprListTableUsage(pMaskSet, sWLB.pOrderBy); + Bitmask tabUsed = sqlite3WhereExprListUsage(pMaskSet, pResultSet); + if( sWLB.pOrderBy ){ + tabUsed |= sqlite3WhereExprListUsage(pMaskSet, sWLB.pOrderBy); + } while( pWInfo->nLevel>=2 ){ WhereTerm *pTerm, *pEnd; pLoop = pWInfo->a[pWInfo->nLevel-1].pWLoop; - if( (pWInfo->pTabList->a[pLoop->iTab].jointype & JT_LEFT)==0 ) break; + if( (pWInfo->pTabList->a[pLoop->iTab].fg.jointype & JT_LEFT)==0 ) break; if( (wctrlFlags & WHERE_WANT_DISTINCT)==0 && (pLoop->wsFlags & WHERE_ONEROW)==0 ){ @@ -116052,21 +126851,28 @@ SQLITE_PRIVATE WhereInfo *sqlite3WhereBegin( /* If the caller is an UPDATE or DELETE statement that is requesting ** to use a one-pass algorithm, determine if this is appropriate. ** The one-pass algorithm only works if the WHERE clause constrains - ** the statement to update a single row. + ** the statement to update or delete a single row. */ assert( (wctrlFlags & WHERE_ONEPASS_DESIRED)==0 || pWInfo->nLevel==1 ); - if( (wctrlFlags & WHERE_ONEPASS_DESIRED)!=0 - && (pWInfo->a[0].pWLoop->wsFlags & WHERE_ONEROW)!=0 ){ - pWInfo->okOnePass = 1; - if( HasRowid(pTabList->a[0].pTab) ){ - pWInfo->a[0].pWLoop->wsFlags &= ~WHERE_IDX_ONLY; + if( (wctrlFlags & WHERE_ONEPASS_DESIRED)!=0 ){ + int wsFlags = pWInfo->a[0].pWLoop->wsFlags; + int bOnerow = (wsFlags & WHERE_ONEROW)!=0; + if( bOnerow || ( (wctrlFlags & WHERE_ONEPASS_MULTIROW) + && 0==(wsFlags & WHERE_VIRTUALTABLE) + )){ + pWInfo->eOnePass = bOnerow ? ONEPASS_SINGLE : ONEPASS_MULTI; + if( HasRowid(pTabList->a[0].pTab) && (wsFlags & WHERE_IDX_ONLY) ){ + if( wctrlFlags & WHERE_ONEPASS_MULTIROW ){ + bFordelete = OPFLAG_FORDELETE; + } + pWInfo->a[0].pWLoop->wsFlags = (wsFlags & ~WHERE_IDX_ONLY); + } } } /* Open all tables in the pTabList and any indices selected for ** searching those tables. */ - notReady = ~(Bitmask)0; for(ii=0, pLevel=pWInfo->a; iiwsFlags & WHERE_IDX_ONLY)==0 && (wctrlFlags & WHERE_OMIT_OPEN_CLOSE)==0 ){ int op = OP_OpenRead; - if( pWInfo->okOnePass ){ + if( pWInfo->eOnePass!=ONEPASS_OFF ){ op = OP_OpenWrite; pWInfo->aiCurOnePass[0] = pTabItem->iCursor; }; sqlite3OpenTable(pParse, pTabItem->iCursor, iDb, pTab, op); assert( pTabItem->iCursor==pLevel->iTabCur ); - testcase( !pWInfo->okOnePass && pTab->nCol==BMS-1 ); - testcase( !pWInfo->okOnePass && pTab->nCol==BMS ); - if( !pWInfo->okOnePass && pTab->nColeOnePass==ONEPASS_OFF && pTab->nCol==BMS-1 ); + testcase( pWInfo->eOnePass==ONEPASS_OFF && pTab->nCol==BMS ); + if( pWInfo->eOnePass==ONEPASS_OFF && pTab->nColcolUsed; int n = 0; for(; b; b=b>>1, n++){} @@ -116107,6 +126913,18 @@ SQLITE_PRIVATE WhereInfo *sqlite3WhereBegin( SQLITE_INT_TO_PTR(n), P4_INT32); assert( n<=pTab->nCol ); } +#ifdef SQLITE_ENABLE_CURSOR_HINTS + if( pLoop->u.btree.pIndex!=0 ){ + sqlite3VdbeChangeP5(v, OPFLAG_SEEKEQ|bFordelete); + }else +#endif + { + sqlite3VdbeChangeP5(v, bFordelete); + } +#ifdef SQLITE_ENABLE_COLUMN_USED_MASK + sqlite3VdbeAddOp4Dup8(v, OP_ColumnsUsed, pTabItem->iCursor, 0, 0, + (const u8*)&pTabItem->colUsed, P4_INT64); +#endif }else{ sqlite3TableLock(pParse, iDb, pTab->tnum, 0, pTab->zName); } @@ -116123,7 +126941,7 @@ SQLITE_PRIVATE WhereInfo *sqlite3WhereBegin( ** WITHOUT ROWID table. No need for a separate index */ iIndexCur = pLevel->iTabCur; op = 0; - }else if( pWInfo->okOnePass ){ + }else if( pWInfo->eOnePass!=ONEPASS_OFF ){ Index *pJ = pTabItem->pTab->pIndex; iIndexCur = iIdxCur; assert( wctrlFlags & WHERE_ONEPASS_DESIRED ); @@ -116135,6 +126953,7 @@ SQLITE_PRIVATE WhereInfo *sqlite3WhereBegin( pWInfo->aiCurOnePass[1] = iIndexCur; }else if( iIdxCur && (wctrlFlags & WHERE_ONETABLE_ONLY)!=0 ){ iIndexCur = iIdxCur; + if( wctrlFlags & WHERE_REOPEN_IDX ) op = OP_ReopenIdx; }else{ iIndexCur = pParse->nTab++; } @@ -116144,11 +126963,31 @@ SQLITE_PRIVATE WhereInfo *sqlite3WhereBegin( if( op ){ sqlite3VdbeAddOp3(v, op, iIndexCur, pIx->tnum, iDb); sqlite3VdbeSetP4KeyInfo(pParse, pIx); + if( (pLoop->wsFlags & WHERE_CONSTRAINT)!=0 + && (pLoop->wsFlags & (WHERE_COLUMN_RANGE|WHERE_SKIPSCAN))==0 + && (pWInfo->wctrlFlags&WHERE_ORDERBY_MIN)==0 + ){ + sqlite3VdbeChangeP5(v, OPFLAG_SEEKEQ); /* Hint to COMDB2 */ + } VdbeComment((v, "%s", pIx->zName)); +#ifdef SQLITE_ENABLE_COLUMN_USED_MASK + { + u64 colUsed = 0; + int ii, jj; + for(ii=0; iinColumn; ii++){ + jj = pIx->aiColumn[ii]; + if( jj<0 ) continue; + if( jj>63 ) jj = 63; + if( (pTabItem->colUsed & MASKBIT(jj))==0 ) continue; + colUsed |= ((u64)1)<<(ii<63 ? ii : 63); + } + sqlite3VdbeAddOp4Dup8(v, OP_ColumnsUsed, iIndexCur, 0, 0, + (u8*)&colUsed, P4_INT64); + } +#endif /* SQLITE_ENABLE_COLUMN_USED_MASK */ } } if( iDb>=0 ) sqlite3CodeVerifySchema(pParse, iDb); - notReady &= ~getMask(&pWInfo->sMaskSet, pTabItem->iCursor); } pWInfo->iTop = sqlite3VdbeCurrentAddr(v); if( db->mallocFailed ) goto whereBeginError; @@ -116159,7 +126998,10 @@ SQLITE_PRIVATE WhereInfo *sqlite3WhereBegin( */ notReady = ~(Bitmask)0; for(ii=0; iia[ii]; + wsFlags = pLevel->pWLoop->wsFlags; #ifndef SQLITE_OMIT_AUTOMATIC_INDEX if( (pLevel->pWLoop->wsFlags & WHERE_AUTO_INDEX)!=0 ){ constructAutomaticIndex(pParse, &pWInfo->sWC, @@ -116167,10 +127009,15 @@ SQLITE_PRIVATE WhereInfo *sqlite3WhereBegin( if( db->mallocFailed ) goto whereBeginError; } #endif - explainOneScan(pParse, pTabList, pLevel, ii, pLevel->iFrom, wctrlFlags); + addrExplain = sqlite3WhereExplainOneScan( + pParse, pTabList, pLevel, ii, pLevel->iFrom, wctrlFlags + ); pLevel->addrBody = sqlite3VdbeCurrentAddr(v); - notReady = codeOneLoopStart(pWInfo, ii, notReady); + notReady = sqlite3WhereCodeOneLoopStart(pWInfo, ii, notReady); pWInfo->iContinue = pLevel->addrCont; + if( (wsFlags&WHERE_MULTI_OR)==0 && (wctrlFlags&WHERE_ONETABLE_ONLY)==0 ){ + sqlite3WhereAddScanStatus(v, pTabList, pLevel, addrExplain); + } } /* Done. */ @@ -116228,15 +127075,26 @@ SQLITE_PRIVATE void sqlite3WhereEnd(WhereInfo *pWInfo){ VdbeCoverageIf(v, pIn->eEndLoopOp==OP_NextIfOpen); sqlite3VdbeJumpHere(v, pIn->addrInTop-1); } - sqlite3DbFree(db, pLevel->u.in.aInLoop); } sqlite3VdbeResolveLabel(v, pLevel->addrBrk); if( pLevel->addrSkip ){ - sqlite3VdbeAddOp2(v, OP_Goto, 0, pLevel->addrSkip); + sqlite3VdbeGoto(v, pLevel->addrSkip); VdbeComment((v, "next skip-scan on %s", pLoop->u.btree.pIndex->zName)); sqlite3VdbeJumpHere(v, pLevel->addrSkip); sqlite3VdbeJumpHere(v, pLevel->addrSkip-2); } +#ifndef SQLITE_LIKE_DOESNT_MATCH_BLOBS + if( pLevel->addrLikeRep ){ + int op; + if( sqlite3VdbeGetOp(v, pLevel->addrLikeRep-1)->p1 ){ + op = OP_DecrJumpZero; + }else{ + op = OP_JumpZeroIncr; + } + sqlite3VdbeAddOp2(v, op, pLevel->iLikeRepCntr, pLevel->addrLikeRep); + VdbeCoverage(v); + } +#endif if( pLevel->iLeftJoin ){ addr = sqlite3VdbeAddOp1(v, OP_IfPos, pLevel->iLeftJoin); VdbeCoverage(v); assert( (pLoop->wsFlags & WHERE_IDX_ONLY)==0 @@ -116250,7 +127108,7 @@ SQLITE_PRIVATE void sqlite3WhereEnd(WhereInfo *pWInfo){ if( pLevel->op==OP_Return ){ sqlite3VdbeAddOp2(v, OP_Gosub, pLevel->p1, pLevel->addrFirst); }else{ - sqlite3VdbeAddOp2(v, OP_Goto, 0, pLevel->addrFirst); + sqlite3VdbeGoto(v, pLevel->addrFirst); } sqlite3VdbeJumpHere(v, addr); } @@ -116274,26 +127132,12 @@ SQLITE_PRIVATE void sqlite3WhereEnd(WhereInfo *pWInfo){ pLoop = pLevel->pWLoop; /* For a co-routine, change all OP_Column references to the table of - ** the co-routine into OP_SCopy of result contained in a register. + ** the co-routine into OP_Copy of result contained in a register. ** OP_Rowid becomes OP_Null. */ - if( pTabItem->viaCoroutine && !db->mallocFailed ){ - last = sqlite3VdbeCurrentAddr(v); - k = pLevel->addrBody; - pOp = sqlite3VdbeGetOp(v, k); - for(; kp1!=pLevel->iTabCur ) continue; - if( pOp->opcode==OP_Column ){ - pOp->opcode = OP_Copy; - pOp->p1 = pOp->p2 + pTabItem->regResult; - pOp->p2 = pOp->p3; - pOp->p3 = 0; - }else if( pOp->opcode==OP_Rowid ){ - pOp->opcode = OP_Null; - pOp->p1 = 0; - pOp->p3 = 0; - } - } + if( pTabItem->fg.viaCoroutine && !db->mallocFailed ){ + translateColumnToCopy(v, pLevel->addrBody, pLevel->iTabCur, + pTabItem->regResult, 0); continue; } @@ -116307,7 +127151,7 @@ SQLITE_PRIVATE void sqlite3WhereEnd(WhereInfo *pWInfo){ && (pWInfo->wctrlFlags & WHERE_OMIT_OPEN_CLOSE)==0 ){ int ws = pLoop->wsFlags; - if( !pWInfo->okOnePass && (ws & WHERE_IDX_ONLY)==0 ){ + if( pWInfo->eOnePass==ONEPASS_OFF && (ws & WHERE_IDX_ONLY)==0 ){ sqlite3VdbeAddOp1(v, OP_Close, pTabItem->iCursor); } if( (ws & WHERE_INDEXED)!=0 @@ -116334,7 +127178,10 @@ SQLITE_PRIVATE void sqlite3WhereEnd(WhereInfo *pWInfo){ }else if( pLoop->wsFlags & WHERE_MULTI_OR ){ pIdx = pLevel->u.pCovidx; } - if( pIdx && !db->mallocFailed ){ + if( pIdx + && (pWInfo->eOnePass==ONEPASS_OFF || !HasRowid(pIdx->pTable)) + && !db->mallocFailed + ){ last = sqlite3VdbeCurrentAddr(v); k = pLevel->addrBody; pOp = sqlite3VdbeGetOp(v, k); @@ -116346,6 +127193,7 @@ SQLITE_PRIVATE void sqlite3WhereEnd(WhereInfo *pWInfo){ if( !HasRowid(pTab) ){ Index *pPk = sqlite3PrimaryKeyIndex(pTab); x = pPk->aiColumn[x]; + assert( x>=0 ); } x = sqlite3ColumnOfIndex(pIdx, x); if( x>=0 ){ @@ -116370,19 +127218,34 @@ SQLITE_PRIVATE void sqlite3WhereEnd(WhereInfo *pWInfo){ /************** End of where.c ***********************************************/ /************** Begin file parse.c *******************************************/ -/* Driver template for the LEMON parser generator. -** The author disclaims copyright to this source code. +/* +** 2000-05-29 ** -** This version of "lempar.c" is modified, slightly, for use by SQLite. -** The only modifications are the addition of a couple of NEVER() -** macros to disable tests that are needed in the case of a general -** LALR(1) grammar but which are always false in the -** specific grammar used by SQLite. +** The author disclaims copyright to this source code. In place of +** a legal notice, here is a blessing: +** +** May you do good and not evil. +** May you find forgiveness for yourself and forgive others. +** May you share freely, never taking more than you give. +** +************************************************************************* +** Driver template for the LEMON parser generator. +** +** The "lemon" program processes an LALR(1) input grammar file, then uses +** this template to construct a parser. The "lemon" program inserts text +** at each "%%" line. Also, any "P-a-r-s-e" identifer prefix (without the +** interstitial "-" characters) contained in this template is changed into +** the value of the %name directive from the grammar. Otherwise, the content +** of this template is copied straight through into the generate parser +** source file. +** +** The following is the concatenation of all %include directives from the +** input grammar file: */ -/* First off, code is included that follows the "include" declaration -** in the input grammar file. */ /* #include */ +/************ Begin %include sections from the grammar ************************/ +/* #include "sqliteInt.h" */ /* ** Disable all error recovery processing in the parser push-down @@ -116395,6 +127258,18 @@ SQLITE_PRIVATE void sqlite3WhereEnd(WhereInfo *pWInfo){ */ #define yytestcase(X) testcase(X) +/* +** Indicate that sqlite3ParserFree() will never be called with a null +** pointer. +*/ +#define YYPARSEFREENEVERNULL 1 + +/* +** Alternative datatype for the argument to the malloc() routine passed +** into sqlite3ParserAlloc(). The default is size_t. +*/ +#define YYMALLOCARGTYPE u64 + /* ** An instance of this structure holds information about the ** LIMIT clause of a SELECT statement. @@ -116430,6 +127305,28 @@ struct TrigEvent { int a; IdList * b; }; struct AttachKey { int type; Token key; }; + /* + ** For a compound SELECT statement, make sure p->pPrior->pNext==p for + ** all elements in the list. And make sure list length does not exceed + ** SQLITE_LIMIT_COMPOUND_SELECT. + */ + static void parserDoubleLinkSelect(Parse *pParse, Select *p){ + if( p->pPrior ){ + Select *pNext = 0, *pLoop; + int mxSelect, cnt = 0; + for(pLoop=p; pLoop; pNext=pLoop, pLoop=pLoop->pPrior, cnt++){ + pLoop->pNext = pNext; + pLoop->selFlags |= SF_Compound; + } + if( (p->selFlags & SF_MultiValue)==0 && + (mxSelect = pParse->db->aLimit[SQLITE_LIMIT_COMPOUND_SELECT])>0 && + cnt>mxSelect + ){ + sqlite3ErrorMsg(pParse, "too many terms in compound SELECT"); + } + } + } + /* This is a utility routine used to set the ExprSpan.zStart and ** ExprSpan.zEnd values of pOut so that the span covers the complete ** range of text beginning with pStart and going to the end of pEnd. @@ -116464,6 +127361,13 @@ struct AttachKey { int type; Token key; }; pOut->zEnd = pRight->zEnd; } + /* If doNot is true, then add a TK_NOT Expr-node wrapper around the + ** outside of *ppExpr. + */ + static void exprNot(Parse *pParse, int doNot, Expr **ppExpr){ + if( doNot ) *ppExpr = sqlite3PExpr(pParse, TK_NOT, *ppExpr, 0, 0); + } + /* Construct an expression node for a unary postfix operator */ static void spanUnaryPostfix( @@ -116482,7 +127386,7 @@ struct AttachKey { int type; Token key; }; ** unary TK_ISNULL or TK_NOTNULL expression. */ static void binaryToUnaryIfNull(Parse *pParse, Expr *pY, Expr *pA, int op){ sqlite3 *db = pParse->db; - if( db->mallocFailed==0 && pY->op==TK_NULL ){ + if( pY && pA && pY->op==TK_NULL ){ pA->op = (u8)op; sqlite3ExprDelete(db, pA->pRight); pA->pRight = 0; @@ -116502,78 +127406,108 @@ struct AttachKey { int type; Token key; }; pOut->zStart = pPreOp->z; pOut->zEnd = pOperand->zEnd; } -/* Next is all token values, in a form suitable for use by makeheaders. -** This section will be null unless lemon is run with the -m switch. -*/ -/* -** These constants (all generated automatically by the parser generator) -** specify the various kinds of tokens (terminals) that the parser -** understands. -** -** Each symbol here is a terminal symbol in the grammar. -*/ -/* Make sure the INTERFACE macro is defined. -*/ -#ifndef INTERFACE -# define INTERFACE 1 -#endif -/* The next thing included is series of defines which control + + /* Add a single new term to an ExprList that is used to store a + ** list of identifiers. Report an error if the ID list contains + ** a COLLATE clause or an ASC or DESC keyword, except ignore the + ** error while parsing a legacy schema. + */ + static ExprList *parserAddExprIdListTerm( + Parse *pParse, + ExprList *pPrior, + Token *pIdToken, + int hasCollate, + int sortOrder + ){ + ExprList *p = sqlite3ExprListAppend(pParse, pPrior, 0); + if( (hasCollate || sortOrder!=SQLITE_SO_UNDEFINED) + && pParse->db->init.busy==0 + ){ + sqlite3ErrorMsg(pParse, "syntax error after column name \"%.*s\"", + pIdToken->n, pIdToken->z); + } + sqlite3ExprListSetName(pParse, p, pIdToken, 1); + return p; + } +/**************** End of %include directives **********************************/ +/* These constants specify the various numeric values for terminal symbols +** in a format understandable to "makeheaders". This section is blank unless +** "lemon" is run with the "-m" command-line option. +***************** Begin makeheaders token definitions *************************/ +/**************** End makeheaders token definitions ***************************/ + +/* The next sections is a series of control #defines. ** various aspects of the generated parser. -** YYCODETYPE is the data type used for storing terminal -** and nonterminal numbers. "unsigned char" is -** used if there are fewer than 250 terminals -** and nonterminals. "int" is used otherwise. -** YYNOCODE is a number of type YYCODETYPE which corresponds -** to no legal terminal or nonterminal number. This -** number is used to fill in empty slots of the hash -** table. +** YYCODETYPE is the data type used to store the integer codes +** that represent terminal and non-terminal symbols. +** "unsigned char" is used if there are fewer than +** 256 symbols. Larger types otherwise. +** YYNOCODE is a number of type YYCODETYPE that is not used for +** any terminal or nonterminal symbol. ** YYFALLBACK If defined, this indicates that one or more tokens -** have fall-back values which should be used if the -** original value of the token will not parse. -** YYACTIONTYPE is the data type used for storing terminal -** and nonterminal numbers. "unsigned char" is -** used if there are fewer than 250 rules and -** states combined. "int" is used otherwise. -** sqlite3ParserTOKENTYPE is the data type used for minor tokens given -** directly to the parser from the tokenizer. -** YYMINORTYPE is the data type used for all minor tokens. +** (also known as: "terminal symbols") have fall-back +** values which should be used if the original symbol +** would not parse. This permits keywords to sometimes +** be used as identifiers, for example. +** YYACTIONTYPE is the data type used for "action codes" - numbers +** that indicate what to do in response to the next +** token. +** sqlite3ParserTOKENTYPE is the data type used for minor type for terminal +** symbols. Background: A "minor type" is a semantic +** value associated with a terminal or non-terminal +** symbols. For example, for an "ID" terminal symbol, +** the minor type might be the name of the identifier. +** Each non-terminal can have a different minor type. +** Terminal symbols all have the same minor type, though. +** This macros defines the minor type for terminal +** symbols. +** YYMINORTYPE is the data type used for all minor types. ** This is typically a union of many types, one of ** which is sqlite3ParserTOKENTYPE. The entry in the union -** for base tokens is called "yy0". +** for terminal symbols is called "yy0". ** YYSTACKDEPTH is the maximum depth of the parser's stack. If ** zero the stack is dynamically sized using realloc() ** sqlite3ParserARG_SDECL A static variable declaration for the %extra_argument ** sqlite3ParserARG_PDECL A parameter declaration for the %extra_argument ** sqlite3ParserARG_STORE Code to store %extra_argument into yypParser ** sqlite3ParserARG_FETCH Code to extract %extra_argument from yypParser -** YYNSTATE the combined number of states. -** YYNRULE the number of rules in the grammar ** YYERRORSYMBOL is the code number of the error symbol. If not ** defined, then do no error processing. +** YYNSTATE the combined number of states. +** YYNRULE the number of rules in the grammar +** YY_MAX_SHIFT Maximum value for shift actions +** YY_MIN_SHIFTREDUCE Minimum value for shift-reduce actions +** YY_MAX_SHIFTREDUCE Maximum value for shift-reduce actions +** YY_MIN_REDUCE Maximum value for reduce actions +** YY_ERROR_ACTION The yy_action[] code for syntax error +** YY_ACCEPT_ACTION The yy_action[] code for accept +** YY_NO_ACTION The yy_action[] code for no-op */ +#ifndef INTERFACE +# define INTERFACE 1 +#endif +/************* Begin control #defines *****************************************/ #define YYCODETYPE unsigned char -#define YYNOCODE 254 +#define YYNOCODE 253 #define YYACTIONTYPE unsigned short int #define YYWILDCARD 70 #define sqlite3ParserTOKENTYPE Token typedef union { int yyinit; sqlite3ParserTOKENTYPE yy0; - Select* yy3; - ExprList* yy14; - With* yy59; - SrcList* yy65; - struct LikeOp yy96; - Expr* yy132; - u8 yy186; - int yy328; - ExprSpan yy346; - struct TrigEvent yy378; - u16 yy381; - IdList* yy408; - struct {int value; int mask;} yy429; - TriggerStep* yy473; - struct LimitVal yy476; + int yy4; + struct TrigEvent yy90; + ExprSpan yy118; + TriggerStep* yy203; + struct {int value; int mask;} yy215; + SrcList* yy259; + struct LimitVal yy292; + Expr* yy314; + ExprList* yy322; + struct LikeOp yy342; + IdList* yy384; + Select* yy387; + With* yy451; } YYMINORTYPE; #ifndef YYSTACKDEPTH #define YYSTACKDEPTH 100 @@ -116582,12 +127516,18 @@ typedef union { #define sqlite3ParserARG_PDECL ,Parse *pParse #define sqlite3ParserARG_FETCH Parse *pParse = yypParser->pParse #define sqlite3ParserARG_STORE yypParser->pParse = pParse -#define YYNSTATE 642 -#define YYNRULE 327 #define YYFALLBACK 1 -#define YY_NO_ACTION (YYNSTATE+YYNRULE+2) -#define YY_ACCEPT_ACTION (YYNSTATE+YYNRULE+1) -#define YY_ERROR_ACTION (YYNSTATE+YYNRULE) +#define YYNSTATE 436 +#define YYNRULE 328 +#define YY_MAX_SHIFT 435 +#define YY_MIN_SHIFTREDUCE 649 +#define YY_MAX_SHIFTREDUCE 976 +#define YY_MIN_REDUCE 977 +#define YY_MAX_REDUCE 1304 +#define YY_ERROR_ACTION 1305 +#define YY_ACCEPT_ACTION 1306 +#define YY_NO_ACTION 1307 +/************* End control #defines *******************************************/ /* The yyzerominor constant is used to initialize instances of ** YYMINORTYPE objects to zero. */ @@ -116614,16 +127554,20 @@ static const YYMINORTYPE yyzerominor = { 0 }; ** Suppose the action integer is N. Then the action is determined as ** follows ** -** 0 <= N < YYNSTATE Shift N. That is, push the lookahead +** 0 <= N <= YY_MAX_SHIFT Shift N. That is, push the lookahead ** token onto the stack and goto state N. ** -** YYNSTATE <= N < YYNSTATE+YYNRULE Reduce by rule N-YYNSTATE. +** N between YY_MIN_SHIFTREDUCE Shift to an arbitrary state then +** and YY_MAX_SHIFTREDUCE reduce by rule N-YY_MIN_SHIFTREDUCE. ** -** N == YYNSTATE+YYNRULE A syntax error has occurred. +** N between YY_MIN_REDUCE Reduce by rule N-YY_MIN_REDUCE +** and YY_MAX_REDUCE + +** N == YY_ERROR_ACTION A syntax error has occurred. ** -** N == YYNSTATE+YYNRULE+1 The parser accepts its input. +** N == YY_ACCEPT_ACTION The parser accepts its input. ** -** N == YYNSTATE+YYNRULE+2 No such action. Denotes unused +** N == YY_NO_ACTION No such action. Denotes unused ** slots in the yy_action[] table. ** ** The action table is constructed as a single large table named yy_action[]. @@ -116652,468 +127596,453 @@ static const YYMINORTYPE yyzerominor = { 0 }; ** yy_reduce_ofst[] For each state, the offset into yy_action for ** shifting non-terminals after a reduce. ** yy_default[] Default action for each state. -*/ -#define YY_ACTTAB_COUNT (1497) +** +*********** Begin parsing tables **********************************************/ +#define YY_ACTTAB_COUNT (1501) static const YYACTIONTYPE yy_action[] = { - /* 0 */ 306, 212, 432, 955, 639, 191, 955, 295, 559, 88, - /* 10 */ 88, 88, 88, 81, 86, 86, 86, 86, 85, 85, - /* 20 */ 84, 84, 84, 83, 330, 185, 184, 183, 635, 635, - /* 30 */ 292, 606, 606, 88, 88, 88, 88, 683, 86, 86, - /* 40 */ 86, 86, 85, 85, 84, 84, 84, 83, 330, 16, - /* 50 */ 436, 597, 89, 90, 80, 600, 599, 601, 601, 87, - /* 60 */ 87, 88, 88, 88, 88, 684, 86, 86, 86, 86, - /* 70 */ 85, 85, 84, 84, 84, 83, 330, 306, 559, 84, - /* 80 */ 84, 84, 83, 330, 65, 86, 86, 86, 86, 85, - /* 90 */ 85, 84, 84, 84, 83, 330, 635, 635, 634, 633, - /* 100 */ 182, 682, 550, 379, 376, 375, 17, 322, 606, 606, - /* 110 */ 371, 198, 479, 91, 374, 82, 79, 165, 85, 85, - /* 120 */ 84, 84, 84, 83, 330, 598, 635, 635, 107, 89, - /* 130 */ 90, 80, 600, 599, 601, 601, 87, 87, 88, 88, - /* 140 */ 88, 88, 186, 86, 86, 86, 86, 85, 85, 84, - /* 150 */ 84, 84, 83, 330, 306, 594, 594, 142, 328, 327, - /* 160 */ 484, 249, 344, 238, 635, 635, 634, 633, 585, 448, - /* 170 */ 526, 525, 229, 388, 1, 394, 450, 584, 449, 635, - /* 180 */ 635, 635, 635, 319, 395, 606, 606, 199, 157, 273, - /* 190 */ 382, 268, 381, 187, 635, 635, 634, 633, 311, 555, - /* 200 */ 266, 593, 593, 266, 347, 588, 89, 90, 80, 600, - /* 210 */ 599, 601, 601, 87, 87, 88, 88, 88, 88, 478, - /* 220 */ 86, 86, 86, 86, 85, 85, 84, 84, 84, 83, - /* 230 */ 330, 306, 272, 536, 634, 633, 146, 610, 197, 310, - /* 240 */ 575, 182, 482, 271, 379, 376, 375, 506, 21, 634, - /* 250 */ 633, 634, 633, 635, 635, 374, 611, 574, 548, 440, - /* 260 */ 111, 563, 606, 606, 634, 633, 324, 479, 608, 608, - /* 270 */ 608, 300, 435, 573, 119, 407, 210, 162, 562, 883, - /* 280 */ 592, 592, 306, 89, 90, 80, 600, 599, 601, 601, - /* 290 */ 87, 87, 88, 88, 88, 88, 506, 86, 86, 86, - /* 300 */ 86, 85, 85, 84, 84, 84, 83, 330, 620, 111, - /* 310 */ 635, 635, 361, 606, 606, 358, 249, 349, 248, 433, - /* 320 */ 243, 479, 586, 634, 633, 195, 611, 93, 119, 221, - /* 330 */ 575, 497, 534, 534, 89, 90, 80, 600, 599, 601, - /* 340 */ 601, 87, 87, 88, 88, 88, 88, 574, 86, 86, - /* 350 */ 86, 86, 85, 85, 84, 84, 84, 83, 330, 306, - /* 360 */ 77, 429, 638, 573, 589, 530, 240, 230, 242, 105, - /* 370 */ 249, 349, 248, 515, 588, 208, 460, 529, 564, 173, - /* 380 */ 634, 633, 970, 144, 430, 2, 424, 228, 380, 557, - /* 390 */ 606, 606, 190, 153, 159, 158, 514, 51, 632, 631, - /* 400 */ 630, 71, 536, 432, 954, 196, 610, 954, 614, 45, - /* 410 */ 18, 89, 90, 80, 600, 599, 601, 601, 87, 87, - /* 420 */ 88, 88, 88, 88, 261, 86, 86, 86, 86, 85, - /* 430 */ 85, 84, 84, 84, 83, 330, 306, 608, 608, 608, - /* 440 */ 542, 424, 402, 385, 241, 506, 451, 320, 211, 543, - /* 450 */ 164, 436, 386, 293, 451, 587, 108, 496, 111, 334, - /* 460 */ 391, 591, 424, 614, 27, 452, 453, 606, 606, 72, - /* 470 */ 257, 70, 259, 452, 339, 342, 564, 582, 68, 415, - /* 480 */ 469, 328, 327, 62, 614, 45, 110, 393, 89, 90, - /* 490 */ 80, 600, 599, 601, 601, 87, 87, 88, 88, 88, - /* 500 */ 88, 152, 86, 86, 86, 86, 85, 85, 84, 84, - /* 510 */ 84, 83, 330, 306, 110, 499, 520, 538, 402, 389, - /* 520 */ 424, 110, 566, 500, 593, 593, 454, 82, 79, 165, - /* 530 */ 424, 591, 384, 564, 340, 615, 188, 162, 424, 350, - /* 540 */ 616, 424, 614, 44, 606, 606, 445, 582, 300, 434, - /* 550 */ 151, 19, 614, 9, 568, 580, 348, 615, 469, 567, - /* 560 */ 614, 26, 616, 614, 45, 89, 90, 80, 600, 599, - /* 570 */ 601, 601, 87, 87, 88, 88, 88, 88, 411, 86, - /* 580 */ 86, 86, 86, 85, 85, 84, 84, 84, 83, 330, - /* 590 */ 306, 579, 110, 578, 521, 282, 433, 398, 400, 255, - /* 600 */ 486, 82, 79, 165, 487, 164, 82, 79, 165, 488, - /* 610 */ 488, 364, 387, 424, 544, 544, 509, 350, 362, 155, - /* 620 */ 191, 606, 606, 559, 642, 640, 333, 82, 79, 165, - /* 630 */ 305, 564, 507, 312, 357, 614, 45, 329, 596, 595, - /* 640 */ 194, 337, 89, 90, 80, 600, 599, 601, 601, 87, - /* 650 */ 87, 88, 88, 88, 88, 424, 86, 86, 86, 86, - /* 660 */ 85, 85, 84, 84, 84, 83, 330, 306, 20, 323, - /* 670 */ 150, 263, 211, 543, 421, 596, 595, 614, 22, 424, - /* 680 */ 193, 424, 284, 424, 391, 424, 509, 424, 577, 424, - /* 690 */ 186, 335, 424, 559, 424, 313, 120, 546, 606, 606, - /* 700 */ 67, 614, 47, 614, 50, 614, 48, 614, 100, 614, - /* 710 */ 99, 614, 101, 576, 614, 102, 614, 109, 326, 89, - /* 720 */ 90, 80, 600, 599, 601, 601, 87, 87, 88, 88, - /* 730 */ 88, 88, 424, 86, 86, 86, 86, 85, 85, 84, - /* 740 */ 84, 84, 83, 330, 306, 424, 311, 424, 585, 54, - /* 750 */ 424, 516, 517, 590, 614, 112, 424, 584, 424, 572, - /* 760 */ 424, 195, 424, 571, 424, 67, 424, 614, 94, 614, - /* 770 */ 98, 424, 614, 97, 264, 606, 606, 195, 614, 46, - /* 780 */ 614, 96, 614, 30, 614, 49, 614, 115, 614, 114, - /* 790 */ 418, 229, 388, 614, 113, 306, 89, 90, 80, 600, - /* 800 */ 599, 601, 601, 87, 87, 88, 88, 88, 88, 424, - /* 810 */ 86, 86, 86, 86, 85, 85, 84, 84, 84, 83, - /* 820 */ 330, 119, 424, 590, 110, 372, 606, 606, 195, 53, - /* 830 */ 250, 614, 29, 195, 472, 438, 729, 190, 302, 498, - /* 840 */ 14, 523, 641, 2, 614, 43, 306, 89, 90, 80, - /* 850 */ 600, 599, 601, 601, 87, 87, 88, 88, 88, 88, - /* 860 */ 424, 86, 86, 86, 86, 85, 85, 84, 84, 84, - /* 870 */ 83, 330, 424, 613, 964, 964, 354, 606, 606, 420, - /* 880 */ 312, 64, 614, 42, 391, 355, 283, 437, 301, 255, - /* 890 */ 414, 410, 495, 492, 614, 28, 471, 306, 89, 90, - /* 900 */ 80, 600, 599, 601, 601, 87, 87, 88, 88, 88, - /* 910 */ 88, 424, 86, 86, 86, 86, 85, 85, 84, 84, - /* 920 */ 84, 83, 330, 424, 110, 110, 110, 110, 606, 606, - /* 930 */ 110, 254, 13, 614, 41, 532, 531, 283, 481, 531, - /* 940 */ 457, 284, 119, 561, 356, 614, 40, 284, 306, 89, - /* 950 */ 78, 80, 600, 599, 601, 601, 87, 87, 88, 88, - /* 960 */ 88, 88, 424, 86, 86, 86, 86, 85, 85, 84, - /* 970 */ 84, 84, 83, 330, 110, 424, 341, 220, 555, 606, - /* 980 */ 606, 351, 555, 318, 614, 95, 413, 255, 83, 330, - /* 990 */ 284, 284, 255, 640, 333, 356, 255, 614, 39, 306, - /* 1000 */ 356, 90, 80, 600, 599, 601, 601, 87, 87, 88, - /* 1010 */ 88, 88, 88, 424, 86, 86, 86, 86, 85, 85, - /* 1020 */ 84, 84, 84, 83, 330, 424, 317, 316, 141, 465, - /* 1030 */ 606, 606, 219, 619, 463, 614, 10, 417, 462, 255, - /* 1040 */ 189, 510, 553, 351, 207, 363, 161, 614, 38, 315, - /* 1050 */ 218, 255, 255, 80, 600, 599, 601, 601, 87, 87, - /* 1060 */ 88, 88, 88, 88, 424, 86, 86, 86, 86, 85, - /* 1070 */ 85, 84, 84, 84, 83, 330, 76, 419, 255, 3, - /* 1080 */ 878, 461, 424, 247, 331, 331, 614, 37, 217, 76, - /* 1090 */ 419, 390, 3, 216, 215, 422, 4, 331, 331, 424, - /* 1100 */ 547, 12, 424, 545, 614, 36, 424, 541, 422, 424, - /* 1110 */ 540, 424, 214, 424, 408, 424, 539, 403, 605, 605, - /* 1120 */ 237, 614, 25, 119, 614, 24, 588, 408, 614, 45, - /* 1130 */ 118, 614, 35, 614, 34, 614, 33, 614, 23, 588, - /* 1140 */ 60, 223, 603, 602, 513, 378, 73, 74, 140, 139, - /* 1150 */ 424, 110, 265, 75, 426, 425, 59, 424, 610, 73, - /* 1160 */ 74, 549, 402, 404, 424, 373, 75, 426, 425, 604, - /* 1170 */ 138, 610, 614, 11, 392, 76, 419, 181, 3, 614, - /* 1180 */ 32, 271, 369, 331, 331, 493, 614, 31, 149, 608, - /* 1190 */ 608, 608, 607, 15, 422, 365, 614, 8, 137, 489, - /* 1200 */ 136, 190, 608, 608, 608, 607, 15, 485, 176, 135, - /* 1210 */ 7, 252, 477, 408, 174, 133, 175, 474, 57, 56, - /* 1220 */ 132, 130, 119, 76, 419, 588, 3, 468, 245, 464, - /* 1230 */ 171, 331, 331, 125, 123, 456, 447, 122, 446, 104, - /* 1240 */ 336, 231, 422, 166, 154, 73, 74, 332, 116, 431, - /* 1250 */ 121, 309, 75, 426, 425, 222, 106, 610, 308, 637, - /* 1260 */ 204, 408, 629, 627, 628, 6, 200, 428, 427, 290, - /* 1270 */ 203, 622, 201, 588, 62, 63, 289, 66, 419, 399, - /* 1280 */ 3, 401, 288, 92, 143, 331, 331, 287, 608, 608, - /* 1290 */ 608, 607, 15, 73, 74, 227, 422, 325, 69, 416, - /* 1300 */ 75, 426, 425, 612, 412, 610, 192, 61, 569, 209, - /* 1310 */ 396, 226, 278, 225, 383, 408, 527, 558, 276, 533, - /* 1320 */ 552, 528, 321, 523, 370, 508, 180, 588, 494, 179, - /* 1330 */ 366, 117, 253, 269, 522, 503, 608, 608, 608, 607, - /* 1340 */ 15, 551, 502, 58, 274, 524, 178, 73, 74, 304, - /* 1350 */ 501, 368, 303, 206, 75, 426, 425, 491, 360, 610, - /* 1360 */ 213, 177, 483, 131, 345, 298, 297, 296, 202, 294, - /* 1370 */ 480, 490, 466, 134, 172, 129, 444, 346, 470, 128, - /* 1380 */ 314, 459, 103, 127, 126, 148, 124, 167, 443, 235, - /* 1390 */ 608, 608, 608, 607, 15, 442, 439, 623, 234, 299, - /* 1400 */ 145, 583, 291, 377, 581, 160, 119, 156, 270, 636, - /* 1410 */ 971, 169, 279, 626, 520, 625, 473, 624, 170, 621, - /* 1420 */ 618, 119, 168, 55, 409, 423, 537, 609, 286, 285, - /* 1430 */ 405, 570, 560, 556, 5, 52, 458, 554, 147, 267, - /* 1440 */ 519, 504, 518, 406, 262, 239, 260, 512, 343, 511, - /* 1450 */ 258, 353, 565, 256, 224, 251, 359, 277, 275, 476, - /* 1460 */ 475, 246, 352, 244, 467, 455, 236, 233, 232, 307, - /* 1470 */ 441, 281, 205, 163, 397, 280, 535, 505, 330, 617, - /* 1480 */ 971, 971, 971, 971, 367, 971, 971, 971, 971, 971, - /* 1490 */ 971, 971, 971, 971, 971, 971, 338, + /* 0 */ 311, 1306, 145, 651, 2, 192, 652, 338, 780, 92, + /* 10 */ 92, 92, 92, 85, 90, 90, 90, 90, 89, 89, + /* 20 */ 88, 88, 88, 87, 335, 88, 88, 88, 87, 335, + /* 30 */ 327, 856, 856, 92, 92, 92, 92, 697, 90, 90, + /* 40 */ 90, 90, 89, 89, 88, 88, 88, 87, 335, 76, + /* 50 */ 807, 74, 93, 94, 84, 868, 871, 860, 860, 91, + /* 60 */ 91, 92, 92, 92, 92, 335, 90, 90, 90, 90, + /* 70 */ 89, 89, 88, 88, 88, 87, 335, 311, 780, 90, + /* 80 */ 90, 90, 90, 89, 89, 88, 88, 88, 87, 335, + /* 90 */ 356, 808, 776, 701, 689, 689, 86, 83, 166, 257, + /* 100 */ 809, 715, 430, 86, 83, 166, 324, 697, 856, 856, + /* 110 */ 201, 158, 276, 387, 271, 386, 188, 689, 689, 828, + /* 120 */ 86, 83, 166, 269, 833, 49, 123, 87, 335, 93, + /* 130 */ 94, 84, 868, 871, 860, 860, 91, 91, 92, 92, + /* 140 */ 92, 92, 239, 90, 90, 90, 90, 89, 89, 88, + /* 150 */ 88, 88, 87, 335, 311, 763, 333, 332, 216, 408, + /* 160 */ 394, 69, 231, 393, 690, 691, 396, 910, 251, 354, + /* 170 */ 250, 288, 315, 430, 908, 430, 909, 89, 89, 88, + /* 180 */ 88, 88, 87, 335, 391, 856, 856, 690, 691, 183, + /* 190 */ 95, 123, 384, 381, 380, 833, 31, 833, 49, 912, + /* 200 */ 912, 751, 752, 379, 123, 311, 93, 94, 84, 868, + /* 210 */ 871, 860, 860, 91, 91, 92, 92, 92, 92, 114, + /* 220 */ 90, 90, 90, 90, 89, 89, 88, 88, 88, 87, + /* 230 */ 335, 430, 408, 399, 435, 657, 856, 856, 346, 57, + /* 240 */ 232, 828, 109, 704, 366, 689, 689, 363, 825, 760, + /* 250 */ 97, 749, 752, 833, 49, 708, 708, 93, 94, 84, + /* 260 */ 868, 871, 860, 860, 91, 91, 92, 92, 92, 92, + /* 270 */ 423, 90, 90, 90, 90, 89, 89, 88, 88, 88, + /* 280 */ 87, 335, 311, 114, 22, 361, 688, 58, 408, 390, + /* 290 */ 251, 349, 240, 213, 762, 689, 689, 847, 685, 115, + /* 300 */ 361, 231, 393, 689, 689, 396, 183, 689, 689, 384, + /* 310 */ 381, 380, 361, 856, 856, 690, 691, 160, 159, 223, + /* 320 */ 379, 738, 25, 806, 707, 841, 143, 689, 689, 835, + /* 330 */ 392, 339, 766, 766, 93, 94, 84, 868, 871, 860, + /* 340 */ 860, 91, 91, 92, 92, 92, 92, 914, 90, 90, + /* 350 */ 90, 90, 89, 89, 88, 88, 88, 87, 335, 311, + /* 360 */ 840, 840, 840, 266, 257, 690, 691, 778, 706, 86, + /* 370 */ 83, 166, 219, 690, 691, 737, 1, 690, 691, 689, + /* 380 */ 689, 689, 689, 430, 86, 83, 166, 249, 688, 937, + /* 390 */ 856, 856, 427, 699, 700, 828, 298, 690, 691, 221, + /* 400 */ 686, 115, 123, 944, 795, 833, 48, 342, 305, 970, + /* 410 */ 847, 93, 94, 84, 868, 871, 860, 860, 91, 91, + /* 420 */ 92, 92, 92, 92, 114, 90, 90, 90, 90, 89, + /* 430 */ 89, 88, 88, 88, 87, 335, 311, 940, 841, 679, + /* 440 */ 713, 429, 835, 430, 251, 354, 250, 355, 288, 690, + /* 450 */ 691, 690, 691, 285, 941, 340, 971, 287, 210, 23, + /* 460 */ 174, 793, 832, 430, 353, 833, 10, 856, 856, 24, + /* 470 */ 942, 151, 753, 840, 840, 840, 794, 968, 1290, 321, + /* 480 */ 398, 1290, 356, 352, 754, 833, 49, 935, 93, 94, + /* 490 */ 84, 868, 871, 860, 860, 91, 91, 92, 92, 92, + /* 500 */ 92, 430, 90, 90, 90, 90, 89, 89, 88, 88, + /* 510 */ 88, 87, 335, 311, 376, 114, 907, 705, 430, 907, + /* 520 */ 328, 890, 114, 833, 10, 966, 430, 857, 857, 320, + /* 530 */ 189, 163, 832, 165, 430, 906, 344, 323, 906, 904, + /* 540 */ 833, 10, 965, 306, 856, 856, 187, 419, 833, 10, + /* 550 */ 220, 869, 872, 832, 222, 403, 833, 49, 1219, 793, + /* 560 */ 68, 937, 406, 245, 66, 93, 94, 84, 868, 871, + /* 570 */ 860, 860, 91, 91, 92, 92, 92, 92, 861, 90, + /* 580 */ 90, 90, 90, 89, 89, 88, 88, 88, 87, 335, + /* 590 */ 311, 404, 213, 762, 834, 345, 114, 940, 902, 368, + /* 600 */ 727, 5, 316, 192, 396, 772, 780, 269, 230, 242, + /* 610 */ 771, 244, 397, 164, 941, 385, 123, 347, 55, 355, + /* 620 */ 329, 856, 856, 728, 333, 332, 688, 968, 1291, 724, + /* 630 */ 942, 1291, 413, 214, 833, 9, 362, 286, 955, 115, + /* 640 */ 718, 311, 93, 94, 84, 868, 871, 860, 860, 91, + /* 650 */ 91, 92, 92, 92, 92, 430, 90, 90, 90, 90, + /* 660 */ 89, 89, 88, 88, 88, 87, 335, 912, 912, 1300, + /* 670 */ 1300, 758, 856, 856, 325, 966, 780, 833, 35, 747, + /* 680 */ 720, 334, 699, 700, 977, 652, 338, 243, 745, 920, + /* 690 */ 920, 369, 187, 93, 94, 84, 868, 871, 860, 860, + /* 700 */ 91, 91, 92, 92, 92, 92, 114, 90, 90, 90, + /* 710 */ 90, 89, 89, 88, 88, 88, 87, 335, 311, 430, + /* 720 */ 954, 430, 112, 310, 430, 693, 317, 698, 400, 430, + /* 730 */ 793, 359, 430, 1017, 430, 192, 430, 401, 780, 430, + /* 740 */ 360, 833, 36, 833, 12, 430, 833, 27, 316, 856, + /* 750 */ 856, 833, 37, 20, 833, 38, 833, 39, 833, 28, + /* 760 */ 72, 833, 29, 663, 664, 665, 264, 833, 40, 234, + /* 770 */ 93, 94, 84, 868, 871, 860, 860, 91, 91, 92, + /* 780 */ 92, 92, 92, 430, 90, 90, 90, 90, 89, 89, + /* 790 */ 88, 88, 88, 87, 335, 311, 430, 698, 430, 917, + /* 800 */ 147, 430, 165, 916, 275, 833, 41, 430, 780, 430, + /* 810 */ 21, 430, 259, 430, 262, 274, 430, 367, 833, 42, + /* 820 */ 833, 11, 430, 833, 43, 235, 856, 856, 793, 833, + /* 830 */ 99, 833, 44, 833, 45, 833, 32, 75, 833, 46, + /* 840 */ 305, 967, 257, 257, 833, 47, 311, 93, 94, 84, + /* 850 */ 868, 871, 860, 860, 91, 91, 92, 92, 92, 92, + /* 860 */ 430, 90, 90, 90, 90, 89, 89, 88, 88, 88, + /* 870 */ 87, 335, 430, 186, 185, 184, 238, 856, 856, 650, + /* 880 */ 2, 1064, 833, 33, 739, 217, 218, 257, 971, 257, + /* 890 */ 426, 317, 257, 774, 833, 117, 257, 311, 93, 94, + /* 900 */ 84, 868, 871, 860, 860, 91, 91, 92, 92, 92, + /* 910 */ 92, 430, 90, 90, 90, 90, 89, 89, 88, 88, + /* 920 */ 88, 87, 335, 430, 318, 124, 212, 163, 856, 856, + /* 930 */ 943, 900, 898, 833, 118, 759, 726, 725, 257, 755, + /* 940 */ 289, 289, 733, 734, 961, 833, 119, 682, 311, 93, + /* 950 */ 82, 84, 868, 871, 860, 860, 91, 91, 92, 92, + /* 960 */ 92, 92, 430, 90, 90, 90, 90, 89, 89, 88, + /* 970 */ 88, 88, 87, 335, 430, 716, 246, 322, 331, 856, + /* 980 */ 856, 256, 114, 357, 833, 53, 808, 913, 913, 932, + /* 990 */ 156, 416, 420, 424, 930, 809, 833, 34, 364, 311, + /* 1000 */ 253, 94, 84, 868, 871, 860, 860, 91, 91, 92, + /* 1010 */ 92, 92, 92, 430, 90, 90, 90, 90, 89, 89, + /* 1020 */ 88, 88, 88, 87, 335, 430, 114, 114, 114, 960, + /* 1030 */ 856, 856, 307, 258, 830, 833, 100, 191, 252, 377, + /* 1040 */ 267, 68, 197, 68, 261, 716, 769, 833, 50, 71, + /* 1050 */ 911, 911, 263, 84, 868, 871, 860, 860, 91, 91, + /* 1060 */ 92, 92, 92, 92, 430, 90, 90, 90, 90, 89, + /* 1070 */ 89, 88, 88, 88, 87, 335, 80, 425, 802, 3, + /* 1080 */ 1214, 191, 430, 265, 336, 336, 833, 101, 741, 80, + /* 1090 */ 425, 897, 3, 723, 722, 428, 721, 336, 336, 430, + /* 1100 */ 893, 270, 430, 197, 833, 102, 430, 800, 428, 430, + /* 1110 */ 695, 430, 843, 111, 414, 430, 784, 409, 430, 831, + /* 1120 */ 430, 833, 98, 123, 833, 116, 847, 414, 833, 49, + /* 1130 */ 779, 833, 113, 833, 106, 226, 123, 833, 105, 847, + /* 1140 */ 833, 103, 833, 104, 791, 411, 77, 78, 290, 412, + /* 1150 */ 430, 291, 114, 79, 432, 431, 389, 430, 835, 77, + /* 1160 */ 78, 897, 839, 408, 410, 430, 79, 432, 431, 372, + /* 1170 */ 703, 835, 833, 52, 430, 80, 425, 430, 3, 833, + /* 1180 */ 54, 772, 843, 336, 336, 684, 771, 833, 51, 840, + /* 1190 */ 840, 840, 842, 19, 428, 672, 833, 26, 671, 833, + /* 1200 */ 30, 673, 840, 840, 840, 842, 19, 207, 661, 278, + /* 1210 */ 304, 148, 280, 414, 282, 248, 358, 822, 382, 6, + /* 1220 */ 348, 161, 273, 80, 425, 847, 3, 934, 895, 720, + /* 1230 */ 894, 336, 336, 296, 157, 415, 241, 284, 674, 958, + /* 1240 */ 194, 953, 428, 951, 948, 77, 78, 777, 319, 56, + /* 1250 */ 59, 135, 79, 432, 431, 121, 66, 835, 146, 128, + /* 1260 */ 350, 414, 819, 130, 351, 131, 132, 133, 375, 173, + /* 1270 */ 107, 138, 149, 847, 365, 178, 62, 70, 425, 936, + /* 1280 */ 3, 827, 889, 371, 255, 336, 336, 792, 840, 840, + /* 1290 */ 840, 842, 19, 77, 78, 915, 428, 208, 179, 144, + /* 1300 */ 79, 432, 431, 373, 260, 835, 180, 326, 675, 181, + /* 1310 */ 308, 744, 388, 743, 731, 414, 718, 742, 730, 712, + /* 1320 */ 402, 309, 711, 272, 788, 65, 710, 847, 709, 277, + /* 1330 */ 193, 789, 787, 279, 876, 73, 840, 840, 840, 842, + /* 1340 */ 19, 786, 281, 418, 283, 422, 227, 77, 78, 330, + /* 1350 */ 228, 229, 96, 767, 79, 432, 431, 407, 67, 835, + /* 1360 */ 215, 292, 293, 405, 294, 303, 302, 301, 204, 299, + /* 1370 */ 295, 202, 676, 681, 7, 433, 669, 203, 205, 206, + /* 1380 */ 125, 110, 313, 434, 667, 666, 658, 168, 224, 237, + /* 1390 */ 840, 840, 840, 842, 19, 120, 656, 337, 236, 155, + /* 1400 */ 167, 341, 233, 314, 108, 905, 903, 826, 127, 126, + /* 1410 */ 756, 170, 129, 172, 247, 928, 134, 136, 171, 60, + /* 1420 */ 61, 123, 169, 137, 933, 175, 176, 927, 8, 13, + /* 1430 */ 177, 254, 918, 139, 191, 924, 140, 370, 678, 150, + /* 1440 */ 374, 182, 274, 268, 141, 122, 63, 14, 378, 15, + /* 1450 */ 383, 64, 225, 846, 845, 874, 16, 4, 729, 765, + /* 1460 */ 770, 162, 395, 209, 211, 142, 801, 878, 796, 312, + /* 1470 */ 71, 68, 875, 873, 939, 190, 417, 938, 17, 195, + /* 1480 */ 196, 152, 18, 975, 199, 976, 153, 198, 154, 421, + /* 1490 */ 877, 844, 696, 81, 200, 297, 343, 1019, 1018, 300, + /* 1500 */ 653, }; static const YYCODETYPE yy_lookahead[] = { - /* 0 */ 19, 22, 22, 23, 1, 24, 26, 15, 27, 80, + /* 0 */ 19, 144, 145, 146, 147, 24, 1, 2, 27, 80, /* 10 */ 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, - /* 20 */ 91, 92, 93, 94, 95, 108, 109, 110, 27, 28, - /* 30 */ 23, 50, 51, 80, 81, 82, 83, 122, 85, 86, - /* 40 */ 87, 88, 89, 90, 91, 92, 93, 94, 95, 22, - /* 50 */ 70, 23, 71, 72, 73, 74, 75, 76, 77, 78, - /* 60 */ 79, 80, 81, 82, 83, 122, 85, 86, 87, 88, - /* 70 */ 89, 90, 91, 92, 93, 94, 95, 19, 97, 91, - /* 80 */ 92, 93, 94, 95, 26, 85, 86, 87, 88, 89, - /* 90 */ 90, 91, 92, 93, 94, 95, 27, 28, 97, 98, - /* 100 */ 99, 122, 211, 102, 103, 104, 79, 19, 50, 51, - /* 110 */ 19, 122, 59, 55, 113, 224, 225, 226, 89, 90, - /* 120 */ 91, 92, 93, 94, 95, 23, 27, 28, 26, 71, + /* 20 */ 91, 92, 93, 94, 95, 91, 92, 93, 94, 95, + /* 30 */ 19, 50, 51, 80, 81, 82, 83, 27, 85, 86, + /* 40 */ 87, 88, 89, 90, 91, 92, 93, 94, 95, 137, + /* 50 */ 177, 139, 71, 72, 73, 74, 75, 76, 77, 78, + /* 60 */ 79, 80, 81, 82, 83, 95, 85, 86, 87, 88, + /* 70 */ 89, 90, 91, 92, 93, 94, 95, 19, 97, 85, + /* 80 */ 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, + /* 90 */ 152, 33, 212, 173, 27, 28, 223, 224, 225, 152, + /* 100 */ 42, 181, 152, 223, 224, 225, 95, 97, 50, 51, + /* 110 */ 99, 100, 101, 102, 103, 104, 105, 27, 28, 59, + /* 120 */ 223, 224, 225, 112, 174, 175, 66, 94, 95, 71, /* 130 */ 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, - /* 140 */ 82, 83, 51, 85, 86, 87, 88, 89, 90, 91, - /* 150 */ 92, 93, 94, 95, 19, 132, 133, 58, 89, 90, - /* 160 */ 21, 108, 109, 110, 27, 28, 97, 98, 33, 100, - /* 170 */ 7, 8, 119, 120, 22, 19, 107, 42, 109, 27, - /* 180 */ 28, 27, 28, 95, 28, 50, 51, 99, 100, 101, - /* 190 */ 102, 103, 104, 105, 27, 28, 97, 98, 107, 152, - /* 200 */ 112, 132, 133, 112, 65, 69, 71, 72, 73, 74, - /* 210 */ 75, 76, 77, 78, 79, 80, 81, 82, 83, 11, + /* 140 */ 82, 83, 195, 85, 86, 87, 88, 89, 90, 91, + /* 150 */ 92, 93, 94, 95, 19, 197, 89, 90, 220, 209, + /* 160 */ 210, 26, 119, 120, 97, 98, 208, 100, 108, 109, + /* 170 */ 110, 152, 157, 152, 107, 152, 109, 89, 90, 91, + /* 180 */ 92, 93, 94, 95, 163, 50, 51, 97, 98, 99, + /* 190 */ 55, 66, 102, 103, 104, 174, 175, 174, 175, 132, + /* 200 */ 133, 192, 193, 113, 66, 19, 71, 72, 73, 74, + /* 210 */ 75, 76, 77, 78, 79, 80, 81, 82, 83, 198, /* 220 */ 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, - /* 230 */ 95, 19, 101, 97, 97, 98, 24, 101, 122, 157, - /* 240 */ 12, 99, 103, 112, 102, 103, 104, 152, 22, 97, - /* 250 */ 98, 97, 98, 27, 28, 113, 27, 29, 91, 164, - /* 260 */ 165, 124, 50, 51, 97, 98, 219, 59, 132, 133, - /* 270 */ 134, 22, 23, 45, 66, 47, 212, 213, 124, 140, - /* 280 */ 132, 133, 19, 71, 72, 73, 74, 75, 76, 77, - /* 290 */ 78, 79, 80, 81, 82, 83, 152, 85, 86, 87, - /* 300 */ 88, 89, 90, 91, 92, 93, 94, 95, 164, 165, - /* 310 */ 27, 28, 230, 50, 51, 233, 108, 109, 110, 70, - /* 320 */ 16, 59, 23, 97, 98, 26, 97, 22, 66, 185, - /* 330 */ 12, 187, 27, 28, 71, 72, 73, 74, 75, 76, - /* 340 */ 77, 78, 79, 80, 81, 82, 83, 29, 85, 86, + /* 230 */ 95, 152, 209, 210, 148, 149, 50, 51, 100, 53, + /* 240 */ 154, 59, 156, 174, 229, 27, 28, 232, 163, 163, + /* 250 */ 22, 192, 193, 174, 175, 27, 28, 71, 72, 73, + /* 260 */ 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, + /* 270 */ 251, 85, 86, 87, 88, 89, 90, 91, 92, 93, + /* 280 */ 94, 95, 19, 198, 198, 152, 152, 24, 209, 210, + /* 290 */ 108, 109, 110, 196, 197, 27, 28, 69, 164, 165, + /* 300 */ 152, 119, 120, 27, 28, 208, 99, 27, 28, 102, + /* 310 */ 103, 104, 152, 50, 51, 97, 98, 89, 90, 185, + /* 320 */ 113, 187, 22, 177, 174, 97, 58, 27, 28, 101, + /* 330 */ 115, 245, 117, 118, 71, 72, 73, 74, 75, 76, + /* 340 */ 77, 78, 79, 80, 81, 82, 83, 11, 85, 86, /* 350 */ 87, 88, 89, 90, 91, 92, 93, 94, 95, 19, - /* 360 */ 22, 148, 149, 45, 23, 47, 62, 154, 64, 156, - /* 370 */ 108, 109, 110, 37, 69, 23, 163, 59, 26, 26, - /* 380 */ 97, 98, 144, 145, 146, 147, 152, 200, 52, 23, - /* 390 */ 50, 51, 26, 22, 89, 90, 60, 210, 7, 8, - /* 400 */ 9, 138, 97, 22, 23, 26, 101, 26, 174, 175, - /* 410 */ 197, 71, 72, 73, 74, 75, 76, 77, 78, 79, - /* 420 */ 80, 81, 82, 83, 16, 85, 86, 87, 88, 89, - /* 430 */ 90, 91, 92, 93, 94, 95, 19, 132, 133, 134, - /* 440 */ 23, 152, 208, 209, 140, 152, 152, 111, 195, 196, - /* 450 */ 98, 70, 163, 160, 152, 23, 22, 164, 165, 246, - /* 460 */ 207, 27, 152, 174, 175, 171, 172, 50, 51, 137, - /* 470 */ 62, 139, 64, 171, 172, 222, 124, 27, 138, 24, - /* 480 */ 163, 89, 90, 130, 174, 175, 197, 163, 71, 72, + /* 360 */ 132, 133, 134, 23, 152, 97, 98, 91, 174, 223, + /* 370 */ 224, 225, 239, 97, 98, 187, 22, 97, 98, 27, + /* 380 */ 28, 27, 28, 152, 223, 224, 225, 239, 152, 163, + /* 390 */ 50, 51, 170, 171, 172, 59, 160, 97, 98, 239, + /* 400 */ 164, 165, 66, 242, 124, 174, 175, 195, 22, 23, + /* 410 */ 69, 71, 72, 73, 74, 75, 76, 77, 78, 79, + /* 420 */ 80, 81, 82, 83, 198, 85, 86, 87, 88, 89, + /* 430 */ 90, 91, 92, 93, 94, 95, 19, 12, 97, 21, + /* 440 */ 23, 152, 101, 152, 108, 109, 110, 221, 152, 97, + /* 450 */ 98, 97, 98, 152, 29, 243, 70, 226, 23, 233, + /* 460 */ 26, 26, 152, 152, 238, 174, 175, 50, 51, 22, + /* 470 */ 45, 24, 47, 132, 133, 134, 124, 22, 23, 188, + /* 480 */ 163, 26, 152, 65, 59, 174, 175, 163, 71, 72, /* 490 */ 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, - /* 500 */ 83, 22, 85, 86, 87, 88, 89, 90, 91, 92, - /* 510 */ 93, 94, 95, 19, 197, 181, 182, 23, 208, 209, - /* 520 */ 152, 197, 26, 189, 132, 133, 232, 224, 225, 226, - /* 530 */ 152, 97, 91, 26, 232, 116, 212, 213, 152, 222, - /* 540 */ 121, 152, 174, 175, 50, 51, 243, 97, 22, 23, - /* 550 */ 22, 234, 174, 175, 177, 23, 239, 116, 163, 177, - /* 560 */ 174, 175, 121, 174, 175, 71, 72, 73, 74, 75, - /* 570 */ 76, 77, 78, 79, 80, 81, 82, 83, 24, 85, + /* 500 */ 83, 152, 85, 86, 87, 88, 89, 90, 91, 92, + /* 510 */ 93, 94, 95, 19, 19, 198, 152, 23, 152, 152, + /* 520 */ 209, 103, 198, 174, 175, 70, 152, 50, 51, 219, + /* 530 */ 213, 214, 152, 98, 152, 171, 172, 188, 171, 172, + /* 540 */ 174, 175, 248, 249, 50, 51, 51, 251, 174, 175, + /* 550 */ 220, 74, 75, 152, 188, 152, 174, 175, 140, 124, + /* 560 */ 26, 163, 188, 16, 130, 71, 72, 73, 74, 75, + /* 570 */ 76, 77, 78, 79, 80, 81, 82, 83, 101, 85, /* 580 */ 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, - /* 590 */ 19, 23, 197, 11, 23, 227, 70, 208, 220, 152, - /* 600 */ 31, 224, 225, 226, 35, 98, 224, 225, 226, 108, - /* 610 */ 109, 110, 115, 152, 117, 118, 27, 222, 49, 123, - /* 620 */ 24, 50, 51, 27, 0, 1, 2, 224, 225, 226, - /* 630 */ 166, 124, 168, 169, 239, 174, 175, 170, 171, 172, - /* 640 */ 22, 194, 71, 72, 73, 74, 75, 76, 77, 78, + /* 590 */ 19, 209, 196, 197, 23, 231, 198, 12, 231, 219, + /* 600 */ 37, 22, 107, 24, 208, 116, 27, 112, 201, 62, + /* 610 */ 121, 64, 152, 152, 29, 52, 66, 221, 211, 221, + /* 620 */ 219, 50, 51, 60, 89, 90, 152, 22, 23, 183, + /* 630 */ 45, 26, 47, 22, 174, 175, 238, 152, 164, 165, + /* 640 */ 106, 19, 71, 72, 73, 74, 75, 76, 77, 78, /* 650 */ 79, 80, 81, 82, 83, 152, 85, 86, 87, 88, - /* 660 */ 89, 90, 91, 92, 93, 94, 95, 19, 22, 208, - /* 670 */ 24, 23, 195, 196, 170, 171, 172, 174, 175, 152, - /* 680 */ 26, 152, 152, 152, 207, 152, 97, 152, 23, 152, - /* 690 */ 51, 244, 152, 97, 152, 247, 248, 23, 50, 51, - /* 700 */ 26, 174, 175, 174, 175, 174, 175, 174, 175, 174, - /* 710 */ 175, 174, 175, 23, 174, 175, 174, 175, 188, 71, - /* 720 */ 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, - /* 730 */ 82, 83, 152, 85, 86, 87, 88, 89, 90, 91, - /* 740 */ 92, 93, 94, 95, 19, 152, 107, 152, 33, 24, - /* 750 */ 152, 100, 101, 27, 174, 175, 152, 42, 152, 23, - /* 760 */ 152, 26, 152, 23, 152, 26, 152, 174, 175, 174, - /* 770 */ 175, 152, 174, 175, 23, 50, 51, 26, 174, 175, - /* 780 */ 174, 175, 174, 175, 174, 175, 174, 175, 174, 175, - /* 790 */ 163, 119, 120, 174, 175, 19, 71, 72, 73, 74, - /* 800 */ 75, 76, 77, 78, 79, 80, 81, 82, 83, 152, - /* 810 */ 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, - /* 820 */ 95, 66, 152, 97, 197, 23, 50, 51, 26, 53, - /* 830 */ 23, 174, 175, 26, 23, 23, 23, 26, 26, 26, - /* 840 */ 36, 106, 146, 147, 174, 175, 19, 71, 72, 73, + /* 660 */ 89, 90, 91, 92, 93, 94, 95, 132, 133, 119, + /* 670 */ 120, 163, 50, 51, 111, 70, 97, 174, 175, 181, + /* 680 */ 182, 170, 171, 172, 0, 1, 2, 140, 190, 108, + /* 690 */ 109, 110, 51, 71, 72, 73, 74, 75, 76, 77, + /* 700 */ 78, 79, 80, 81, 82, 83, 198, 85, 86, 87, + /* 710 */ 88, 89, 90, 91, 92, 93, 94, 95, 19, 152, + /* 720 */ 152, 152, 22, 166, 152, 168, 169, 27, 19, 152, + /* 730 */ 26, 19, 152, 122, 152, 24, 152, 28, 27, 152, + /* 740 */ 28, 174, 175, 174, 175, 152, 174, 175, 107, 50, + /* 750 */ 51, 174, 175, 22, 174, 175, 174, 175, 174, 175, + /* 760 */ 138, 174, 175, 7, 8, 9, 16, 174, 175, 152, + /* 770 */ 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, + /* 780 */ 81, 82, 83, 152, 85, 86, 87, 88, 89, 90, + /* 790 */ 91, 92, 93, 94, 95, 19, 152, 97, 152, 31, + /* 800 */ 24, 152, 98, 35, 101, 174, 175, 152, 97, 152, + /* 810 */ 79, 152, 62, 152, 64, 112, 152, 49, 174, 175, + /* 820 */ 174, 175, 152, 174, 175, 152, 50, 51, 124, 174, + /* 830 */ 175, 174, 175, 174, 175, 174, 175, 138, 174, 175, + /* 840 */ 22, 23, 152, 152, 174, 175, 19, 71, 72, 73, /* 850 */ 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, /* 860 */ 152, 85, 86, 87, 88, 89, 90, 91, 92, 93, - /* 870 */ 94, 95, 152, 196, 119, 120, 19, 50, 51, 168, - /* 880 */ 169, 26, 174, 175, 207, 28, 152, 249, 250, 152, - /* 890 */ 163, 163, 163, 163, 174, 175, 163, 19, 71, 72, + /* 870 */ 94, 95, 152, 108, 109, 110, 152, 50, 51, 146, + /* 880 */ 147, 23, 174, 175, 26, 195, 195, 152, 70, 152, + /* 890 */ 168, 169, 152, 26, 174, 175, 152, 19, 71, 72, /* 900 */ 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, /* 910 */ 83, 152, 85, 86, 87, 88, 89, 90, 91, 92, - /* 920 */ 93, 94, 95, 152, 197, 197, 197, 197, 50, 51, - /* 930 */ 197, 194, 36, 174, 175, 191, 192, 152, 191, 192, - /* 940 */ 163, 152, 66, 124, 152, 174, 175, 152, 19, 71, + /* 920 */ 93, 94, 95, 152, 246, 247, 213, 214, 50, 51, + /* 930 */ 195, 152, 195, 174, 175, 195, 100, 101, 152, 195, + /* 940 */ 152, 152, 7, 8, 152, 174, 175, 163, 19, 71, /* 950 */ 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, /* 960 */ 82, 83, 152, 85, 86, 87, 88, 89, 90, 91, - /* 970 */ 92, 93, 94, 95, 197, 152, 100, 188, 152, 50, - /* 980 */ 51, 152, 152, 188, 174, 175, 252, 152, 94, 95, - /* 990 */ 152, 152, 152, 1, 2, 152, 152, 174, 175, 19, + /* 970 */ 92, 93, 94, 95, 152, 27, 152, 189, 189, 50, + /* 980 */ 51, 195, 198, 152, 174, 175, 33, 132, 133, 152, + /* 990 */ 123, 163, 163, 163, 152, 42, 174, 175, 152, 19, /* 1000 */ 152, 72, 73, 74, 75, 76, 77, 78, 79, 80, /* 1010 */ 81, 82, 83, 152, 85, 86, 87, 88, 89, 90, - /* 1020 */ 91, 92, 93, 94, 95, 152, 188, 188, 22, 194, - /* 1030 */ 50, 51, 240, 173, 194, 174, 175, 252, 194, 152, - /* 1040 */ 36, 181, 28, 152, 23, 219, 122, 174, 175, 219, - /* 1050 */ 221, 152, 152, 73, 74, 75, 76, 77, 78, 79, + /* 1020 */ 91, 92, 93, 94, 95, 152, 198, 198, 198, 23, + /* 1030 */ 50, 51, 26, 152, 23, 174, 175, 26, 23, 23, + /* 1040 */ 23, 26, 26, 26, 152, 97, 23, 174, 175, 26, + /* 1050 */ 132, 133, 152, 73, 74, 75, 76, 77, 78, 79, /* 1060 */ 80, 81, 82, 83, 152, 85, 86, 87, 88, 89, - /* 1070 */ 90, 91, 92, 93, 94, 95, 19, 20, 152, 22, - /* 1080 */ 23, 194, 152, 240, 27, 28, 174, 175, 240, 19, - /* 1090 */ 20, 26, 22, 194, 194, 38, 22, 27, 28, 152, - /* 1100 */ 23, 22, 152, 116, 174, 175, 152, 23, 38, 152, - /* 1110 */ 23, 152, 221, 152, 57, 152, 23, 163, 50, 51, - /* 1120 */ 194, 174, 175, 66, 174, 175, 69, 57, 174, 175, - /* 1130 */ 40, 174, 175, 174, 175, 174, 175, 174, 175, 69, - /* 1140 */ 22, 53, 74, 75, 30, 53, 89, 90, 22, 22, - /* 1150 */ 152, 197, 23, 96, 97, 98, 22, 152, 101, 89, - /* 1160 */ 90, 91, 208, 209, 152, 53, 96, 97, 98, 101, - /* 1170 */ 22, 101, 174, 175, 152, 19, 20, 105, 22, 174, - /* 1180 */ 175, 112, 19, 27, 28, 20, 174, 175, 24, 132, - /* 1190 */ 133, 134, 135, 136, 38, 44, 174, 175, 107, 61, - /* 1200 */ 54, 26, 132, 133, 134, 135, 136, 54, 107, 22, - /* 1210 */ 5, 140, 1, 57, 36, 111, 122, 28, 79, 79, - /* 1220 */ 131, 123, 66, 19, 20, 69, 22, 1, 16, 20, - /* 1230 */ 125, 27, 28, 123, 111, 120, 23, 131, 23, 16, - /* 1240 */ 68, 142, 38, 15, 22, 89, 90, 3, 167, 4, - /* 1250 */ 248, 251, 96, 97, 98, 180, 180, 101, 251, 151, - /* 1260 */ 6, 57, 151, 13, 151, 26, 25, 151, 161, 202, - /* 1270 */ 153, 162, 153, 69, 130, 128, 203, 19, 20, 127, - /* 1280 */ 22, 126, 204, 129, 22, 27, 28, 205, 132, 133, - /* 1290 */ 134, 135, 136, 89, 90, 231, 38, 95, 137, 179, - /* 1300 */ 96, 97, 98, 206, 179, 101, 122, 107, 159, 159, - /* 1310 */ 125, 231, 216, 228, 107, 57, 184, 217, 216, 176, - /* 1320 */ 217, 176, 48, 106, 18, 184, 158, 69, 159, 158, - /* 1330 */ 46, 71, 237, 176, 176, 176, 132, 133, 134, 135, - /* 1340 */ 136, 217, 176, 137, 216, 178, 158, 89, 90, 179, - /* 1350 */ 176, 159, 179, 159, 96, 97, 98, 159, 159, 101, - /* 1360 */ 5, 158, 202, 22, 18, 10, 11, 12, 13, 14, - /* 1370 */ 190, 238, 17, 190, 158, 193, 41, 159, 202, 193, - /* 1380 */ 159, 202, 245, 193, 193, 223, 190, 32, 159, 34, - /* 1390 */ 132, 133, 134, 135, 136, 159, 39, 155, 43, 150, - /* 1400 */ 223, 177, 201, 178, 177, 186, 66, 199, 177, 152, - /* 1410 */ 253, 56, 215, 152, 182, 152, 202, 152, 63, 152, - /* 1420 */ 152, 66, 67, 242, 229, 152, 174, 152, 152, 152, - /* 1430 */ 152, 152, 152, 152, 199, 242, 202, 152, 198, 152, - /* 1440 */ 152, 152, 183, 192, 152, 215, 152, 183, 215, 183, - /* 1450 */ 152, 241, 214, 152, 211, 152, 152, 211, 211, 152, - /* 1460 */ 152, 241, 152, 152, 152, 152, 152, 152, 152, 114, - /* 1470 */ 152, 152, 235, 152, 152, 152, 174, 187, 95, 174, - /* 1480 */ 253, 253, 253, 253, 236, 253, 253, 253, 253, 253, - /* 1490 */ 253, 253, 253, 253, 253, 253, 141, + /* 1070 */ 90, 91, 92, 93, 94, 95, 19, 20, 23, 22, + /* 1080 */ 23, 26, 152, 152, 27, 28, 174, 175, 152, 19, + /* 1090 */ 20, 27, 22, 183, 183, 38, 152, 27, 28, 152, + /* 1100 */ 23, 152, 152, 26, 174, 175, 152, 152, 38, 152, + /* 1110 */ 23, 152, 27, 26, 57, 152, 215, 163, 152, 152, + /* 1120 */ 152, 174, 175, 66, 174, 175, 69, 57, 174, 175, + /* 1130 */ 152, 174, 175, 174, 175, 212, 66, 174, 175, 69, + /* 1140 */ 174, 175, 174, 175, 152, 152, 89, 90, 152, 193, + /* 1150 */ 152, 152, 198, 96, 97, 98, 91, 152, 101, 89, + /* 1160 */ 90, 97, 152, 209, 210, 152, 96, 97, 98, 235, + /* 1170 */ 152, 101, 174, 175, 152, 19, 20, 152, 22, 174, + /* 1180 */ 175, 116, 97, 27, 28, 152, 121, 174, 175, 132, + /* 1190 */ 133, 134, 135, 136, 38, 152, 174, 175, 152, 174, + /* 1200 */ 175, 152, 132, 133, 134, 135, 136, 234, 152, 212, + /* 1210 */ 150, 199, 212, 57, 212, 240, 240, 203, 178, 200, + /* 1220 */ 216, 186, 177, 19, 20, 69, 22, 203, 177, 182, + /* 1230 */ 177, 27, 28, 202, 200, 228, 216, 216, 155, 39, + /* 1240 */ 122, 159, 38, 159, 41, 89, 90, 91, 159, 241, + /* 1250 */ 241, 22, 96, 97, 98, 71, 130, 101, 222, 191, + /* 1260 */ 18, 57, 203, 194, 159, 194, 194, 194, 18, 158, + /* 1270 */ 244, 191, 222, 69, 159, 158, 137, 19, 20, 203, + /* 1280 */ 22, 191, 203, 46, 236, 27, 28, 159, 132, 133, + /* 1290 */ 134, 135, 136, 89, 90, 237, 38, 159, 158, 22, + /* 1300 */ 96, 97, 98, 179, 159, 101, 158, 48, 159, 158, + /* 1310 */ 179, 176, 107, 176, 184, 57, 106, 176, 184, 176, + /* 1320 */ 125, 179, 178, 176, 218, 107, 176, 69, 176, 217, + /* 1330 */ 159, 218, 218, 217, 159, 137, 132, 133, 134, 135, + /* 1340 */ 136, 218, 217, 179, 217, 179, 227, 89, 90, 95, + /* 1350 */ 230, 230, 129, 207, 96, 97, 98, 126, 128, 101, + /* 1360 */ 5, 206, 205, 127, 204, 10, 11, 12, 13, 14, + /* 1370 */ 203, 25, 17, 162, 26, 161, 13, 153, 153, 6, + /* 1380 */ 247, 180, 250, 151, 151, 151, 151, 32, 180, 34, + /* 1390 */ 132, 133, 134, 135, 136, 167, 4, 3, 43, 22, + /* 1400 */ 15, 68, 142, 250, 16, 23, 23, 120, 111, 131, + /* 1410 */ 20, 56, 123, 125, 16, 1, 123, 131, 63, 79, + /* 1420 */ 79, 66, 67, 111, 28, 36, 122, 1, 5, 22, + /* 1430 */ 107, 140, 54, 54, 26, 61, 107, 44, 20, 24, + /* 1440 */ 19, 105, 112, 23, 22, 40, 22, 22, 53, 22, + /* 1450 */ 53, 22, 53, 23, 23, 23, 22, 22, 30, 116, + /* 1460 */ 23, 122, 26, 23, 23, 22, 28, 11, 124, 114, + /* 1470 */ 26, 26, 23, 23, 23, 36, 24, 23, 36, 26, + /* 1480 */ 22, 22, 36, 23, 122, 23, 22, 26, 22, 24, + /* 1490 */ 23, 23, 23, 22, 122, 23, 141, 122, 122, 15, + /* 1500 */ 1, }; -#define YY_SHIFT_USE_DFLT (-86) -#define YY_SHIFT_COUNT (429) -#define YY_SHIFT_MIN (-85) -#define YY_SHIFT_MAX (1383) +#define YY_SHIFT_USE_DFLT (-89) +#define YY_SHIFT_COUNT (435) +#define YY_SHIFT_MIN (-88) +#define YY_SHIFT_MAX (1499) static const short yy_shift_ofst[] = { - /* 0 */ 992, 1057, 1355, 1156, 1204, 1204, 1, 262, -19, 135, - /* 10 */ 135, 776, 1204, 1204, 1204, 1204, 69, 69, 53, 208, - /* 20 */ 283, 755, 58, 725, 648, 571, 494, 417, 340, 263, - /* 30 */ 212, 827, 827, 827, 827, 827, 827, 827, 827, 827, - /* 40 */ 827, 827, 827, 827, 827, 827, 878, 827, 929, 980, - /* 50 */ 980, 1070, 1204, 1204, 1204, 1204, 1204, 1204, 1204, 1204, + /* 0 */ 5, 1057, 1355, 1070, 1204, 1204, 1204, 90, 60, -19, + /* 10 */ 58, 58, 186, 1204, 1204, 1204, 1204, 1204, 1204, 1204, + /* 20 */ 67, 67, 182, 336, 218, 550, 135, 263, 340, 417, + /* 30 */ 494, 571, 622, 699, 776, 827, 827, 827, 827, 827, + /* 40 */ 827, 827, 827, 827, 827, 827, 827, 827, 827, 827, + /* 50 */ 878, 827, 929, 980, 980, 1156, 1204, 1204, 1204, 1204, /* 60 */ 1204, 1204, 1204, 1204, 1204, 1204, 1204, 1204, 1204, 1204, /* 70 */ 1204, 1204, 1204, 1204, 1204, 1204, 1204, 1204, 1204, 1204, - /* 80 */ 1258, 1204, 1204, 1204, 1204, 1204, 1204, 1204, 1204, 1204, - /* 90 */ 1204, 1204, 1204, 1204, -71, -47, -47, -47, -47, -47, - /* 100 */ 0, 29, -12, 283, 283, 139, 91, 392, 392, 894, - /* 110 */ 672, 726, 1383, -86, -86, -86, 88, 318, 318, 99, - /* 120 */ 381, -20, 283, 283, 283, 283, 283, 283, 283, 283, - /* 130 */ 283, 283, 283, 283, 283, 283, 283, 283, 283, 283, - /* 140 */ 283, 283, 283, 283, 624, 876, 726, 672, 1340, 1340, - /* 150 */ 1340, 1340, 1340, 1340, -86, -86, -86, 305, 136, 136, - /* 160 */ 142, 167, 226, 154, 137, 152, 283, 283, 283, 283, - /* 170 */ 283, 283, 283, 283, 283, 283, 283, 283, 283, 283, - /* 180 */ 283, 283, 283, 336, 336, 336, 283, 283, 352, 283, - /* 190 */ 283, 283, 283, 283, 228, 283, 283, 283, 283, 283, - /* 200 */ 283, 283, 283, 283, 283, 501, 569, 596, 596, 596, - /* 210 */ 507, 497, 441, 391, 353, 156, 156, 857, 353, 857, - /* 220 */ 735, 813, 639, 715, 156, 332, 715, 715, 496, 419, - /* 230 */ 646, 1357, 1184, 1184, 1335, 1335, 1184, 1341, 1260, 1144, - /* 240 */ 1346, 1346, 1346, 1346, 1184, 1306, 1144, 1341, 1260, 1260, - /* 250 */ 1144, 1184, 1306, 1206, 1284, 1184, 1184, 1306, 1184, 1306, - /* 260 */ 1184, 1306, 1262, 1207, 1207, 1207, 1274, 1262, 1207, 1217, - /* 270 */ 1207, 1274, 1207, 1207, 1185, 1200, 1185, 1200, 1185, 1200, - /* 280 */ 1184, 1184, 1161, 1262, 1202, 1202, 1262, 1154, 1155, 1147, - /* 290 */ 1152, 1144, 1241, 1239, 1250, 1250, 1254, 1254, 1254, 1254, - /* 300 */ -86, -86, -86, -86, -86, -86, 1068, 304, 526, 249, - /* 310 */ 408, -83, 434, 812, 27, 811, 807, 802, 751, 589, - /* 320 */ 651, 163, 131, 674, 366, 450, 299, 148, 23, 102, - /* 330 */ 229, -21, 1245, 1244, 1222, 1099, 1228, 1172, 1223, 1215, - /* 340 */ 1213, 1115, 1106, 1123, 1110, 1209, 1105, 1212, 1226, 1098, - /* 350 */ 1089, 1140, 1139, 1104, 1189, 1178, 1094, 1211, 1205, 1187, - /* 360 */ 1101, 1071, 1153, 1175, 1146, 1138, 1151, 1091, 1164, 1165, - /* 370 */ 1163, 1069, 1072, 1148, 1112, 1134, 1127, 1129, 1126, 1092, - /* 380 */ 1114, 1118, 1088, 1090, 1093, 1087, 1084, 987, 1079, 1077, - /* 390 */ 1074, 1065, 924, 1021, 1014, 1004, 1006, 819, 739, 896, - /* 400 */ 855, 804, 739, 740, 736, 690, 654, 665, 618, 582, - /* 410 */ 568, 528, 554, 379, 532, 479, 455, 379, 432, 371, - /* 420 */ 341, 28, 338, 116, -11, -57, -85, 7, -8, 3, + /* 80 */ 1204, 1204, 1204, 1204, 1258, 1204, 1204, 1204, 1204, 1204, + /* 90 */ 1204, 1204, 1204, 1204, 1204, 1204, 1204, 1204, -71, -47, + /* 100 */ -47, -47, -47, -47, -6, 88, -66, 218, 218, 418, + /* 110 */ 495, 535, 535, 33, 43, 10, -30, -89, -89, -89, + /* 120 */ 11, 425, 425, 268, 455, 605, 218, 218, 218, 218, + /* 130 */ 218, 218, 218, 218, 218, 218, 218, 218, 218, 218, + /* 140 */ 218, 218, 218, 218, 218, 684, 138, 10, 43, 125, + /* 150 */ 125, 125, 125, 125, 125, -89, -89, -89, 228, 341, + /* 160 */ 341, 207, 276, 300, 280, 352, 354, 218, 218, 218, + /* 170 */ 218, 218, 218, 218, 218, 218, 218, 218, 218, 218, + /* 180 */ 218, 218, 218, 218, 563, 563, 563, 218, 218, 435, + /* 190 */ 218, 218, 218, 579, 218, 218, 585, 218, 218, 218, + /* 200 */ 218, 218, 218, 218, 218, 218, 218, 581, 768, 711, + /* 210 */ 711, 711, 704, 215, 1065, 756, 434, 709, 709, 712, + /* 220 */ 434, 712, 534, 858, 641, 953, 709, -88, 953, 953, + /* 230 */ 867, 489, 447, 1200, 1118, 1118, 1203, 1203, 1118, 1229, + /* 240 */ 1184, 1126, 1242, 1242, 1242, 1242, 1118, 1250, 1126, 1229, + /* 250 */ 1184, 1184, 1126, 1118, 1250, 1139, 1237, 1118, 1118, 1250, + /* 260 */ 1277, 1118, 1250, 1118, 1250, 1277, 1205, 1205, 1205, 1259, + /* 270 */ 1277, 1205, 1210, 1205, 1259, 1205, 1205, 1195, 1218, 1195, + /* 280 */ 1218, 1195, 1218, 1195, 1218, 1118, 1118, 1198, 1277, 1254, + /* 290 */ 1254, 1277, 1223, 1231, 1230, 1236, 1126, 1346, 1348, 1363, + /* 300 */ 1363, 1373, 1373, 1373, 1373, -89, -89, -89, -89, -89, + /* 310 */ -89, 477, 547, 386, 818, 750, 765, 700, 1006, 731, + /* 320 */ 1011, 1015, 1016, 1017, 948, 836, 935, 703, 1023, 1055, + /* 330 */ 1064, 1077, 855, 918, 1087, 1085, 611, 1392, 1394, 1377, + /* 340 */ 1260, 1385, 1333, 1388, 1382, 1383, 1287, 1278, 1297, 1289, + /* 350 */ 1390, 1288, 1398, 1414, 1293, 1286, 1340, 1341, 1312, 1396, + /* 360 */ 1389, 1304, 1426, 1423, 1407, 1323, 1291, 1378, 1408, 1379, + /* 370 */ 1374, 1393, 1329, 1415, 1418, 1421, 1330, 1336, 1422, 1395, + /* 380 */ 1424, 1425, 1420, 1427, 1397, 1428, 1429, 1399, 1405, 1430, + /* 390 */ 1431, 1432, 1343, 1434, 1437, 1435, 1436, 1339, 1440, 1441, + /* 400 */ 1438, 1439, 1443, 1344, 1444, 1442, 1445, 1446, 1444, 1449, + /* 410 */ 1450, 1451, 1453, 1454, 1458, 1456, 1460, 1459, 1452, 1461, + /* 420 */ 1462, 1464, 1465, 1461, 1467, 1466, 1468, 1469, 1471, 1362, + /* 430 */ 1372, 1375, 1376, 1472, 1484, 1499, }; -#define YY_REDUCE_USE_DFLT (-110) -#define YY_REDUCE_COUNT (305) -#define YY_REDUCE_MIN (-109) -#define YY_REDUCE_MAX (1323) +#define YY_REDUCE_USE_DFLT (-144) +#define YY_REDUCE_COUNT (310) +#define YY_REDUCE_MIN (-143) +#define YY_REDUCE_MAX (1235) static const short yy_reduce_ofst[] = { - /* 0 */ 238, 954, 213, 289, 310, 234, 144, 317, -109, 382, - /* 10 */ 377, 303, 461, 389, 378, 368, 302, 294, 253, 395, - /* 20 */ 293, 324, 403, 403, 403, 403, 403, 403, 403, 403, - /* 30 */ 403, 403, 403, 403, 403, 403, 403, 403, 403, 403, - /* 40 */ 403, 403, 403, 403, 403, 403, 403, 403, 403, 403, - /* 50 */ 403, 1022, 1012, 1005, 998, 963, 961, 959, 957, 950, - /* 60 */ 947, 930, 912, 873, 861, 823, 810, 771, 759, 720, - /* 70 */ 708, 670, 657, 619, 614, 612, 610, 608, 606, 604, - /* 80 */ 598, 595, 593, 580, 542, 540, 537, 535, 533, 531, - /* 90 */ 529, 527, 503, 386, 403, 403, 403, 403, 403, 403, - /* 100 */ 403, 403, 403, 95, 447, 82, 334, 504, 467, 403, - /* 110 */ 477, 464, 403, 403, 403, 403, 860, 747, 744, 785, - /* 120 */ 638, 638, 926, 891, 900, 899, 887, 844, 840, 835, - /* 130 */ 848, 830, 843, 829, 792, 839, 826, 737, 838, 795, - /* 140 */ 789, 47, 734, 530, 696, 777, 711, 677, 733, 730, - /* 150 */ 729, 728, 727, 627, 448, 64, 187, 1305, 1302, 1252, - /* 160 */ 1290, 1273, 1323, 1322, 1321, 1319, 1318, 1316, 1315, 1314, - /* 170 */ 1313, 1312, 1311, 1310, 1308, 1307, 1304, 1303, 1301, 1298, - /* 180 */ 1294, 1292, 1289, 1266, 1264, 1259, 1288, 1287, 1238, 1285, - /* 190 */ 1281, 1280, 1279, 1278, 1251, 1277, 1276, 1275, 1273, 1268, - /* 200 */ 1267, 1265, 1263, 1261, 1257, 1248, 1237, 1247, 1246, 1243, - /* 210 */ 1238, 1240, 1235, 1249, 1234, 1233, 1230, 1220, 1214, 1210, - /* 220 */ 1225, 1219, 1232, 1231, 1197, 1195, 1227, 1224, 1201, 1208, - /* 230 */ 1242, 1137, 1236, 1229, 1193, 1181, 1221, 1177, 1196, 1179, - /* 240 */ 1191, 1190, 1186, 1182, 1218, 1216, 1176, 1162, 1183, 1180, - /* 250 */ 1160, 1199, 1203, 1133, 1095, 1198, 1194, 1188, 1192, 1171, - /* 260 */ 1169, 1168, 1173, 1174, 1166, 1159, 1141, 1170, 1158, 1167, - /* 270 */ 1157, 1132, 1145, 1143, 1124, 1128, 1103, 1102, 1100, 1096, - /* 280 */ 1150, 1149, 1085, 1125, 1080, 1064, 1120, 1097, 1082, 1078, - /* 290 */ 1073, 1067, 1109, 1107, 1119, 1117, 1116, 1113, 1111, 1108, - /* 300 */ 1007, 1000, 1002, 1076, 1075, 1081, + /* 0 */ -143, 954, 86, 21, -50, 23, 79, 134, 226, -120, + /* 10 */ -127, 146, 161, 291, 349, 366, 311, 382, 374, 231, + /* 20 */ 364, 367, 396, 398, 236, 317, -103, -103, -103, -103, + /* 30 */ -103, -103, -103, -103, -103, -103, -103, -103, -103, -103, + /* 40 */ -103, -103, -103, -103, -103, -103, -103, -103, -103, -103, + /* 50 */ -103, -103, -103, -103, -103, 460, 503, 567, 569, 572, + /* 60 */ 577, 580, 582, 584, 587, 593, 631, 644, 646, 649, + /* 70 */ 655, 657, 659, 661, 664, 670, 708, 720, 759, 771, + /* 80 */ 810, 822, 861, 873, 912, 930, 947, 950, 957, 959, + /* 90 */ 963, 966, 968, 998, 1005, 1013, 1022, 1025, -103, -103, + /* 100 */ -103, -103, -103, -103, -103, -103, -103, 474, 212, 15, + /* 110 */ 498, 222, 511, -103, 97, 557, -103, -103, -103, -103, + /* 120 */ -80, 9, 59, 19, 294, 294, -53, -62, 690, 691, + /* 130 */ 735, 737, 740, 744, 133, 310, 148, 330, 160, 380, + /* 140 */ 786, 788, 401, 296, 789, 733, 85, 722, -42, 324, + /* 150 */ 508, 784, 828, 829, 830, 678, 713, 407, 69, 150, + /* 160 */ 194, 188, 289, 301, 403, 461, 485, 568, 617, 673, + /* 170 */ 724, 779, 792, 824, 831, 837, 842, 846, 848, 881, + /* 180 */ 892, 900, 931, 936, 446, 910, 911, 944, 949, 901, + /* 190 */ 955, 967, 978, 923, 992, 993, 956, 996, 999, 1010, + /* 200 */ 289, 1018, 1033, 1043, 1046, 1049, 1056, 934, 973, 997, + /* 210 */ 1000, 1002, 901, 1012, 1019, 1060, 1014, 1004, 1020, 975, + /* 220 */ 1024, 976, 1040, 1035, 1047, 1045, 1021, 1007, 1051, 1053, + /* 230 */ 1031, 1034, 1083, 1026, 1082, 1084, 1008, 1009, 1089, 1036, + /* 240 */ 1068, 1059, 1069, 1071, 1072, 1073, 1105, 1111, 1076, 1050, + /* 250 */ 1080, 1090, 1079, 1115, 1117, 1058, 1048, 1128, 1138, 1140, + /* 260 */ 1124, 1145, 1148, 1149, 1151, 1131, 1135, 1137, 1141, 1130, + /* 270 */ 1142, 1143, 1144, 1147, 1134, 1150, 1152, 1106, 1112, 1113, + /* 280 */ 1116, 1114, 1125, 1123, 1127, 1171, 1175, 1119, 1164, 1120, + /* 290 */ 1121, 1166, 1146, 1155, 1157, 1160, 1167, 1211, 1214, 1224, + /* 300 */ 1225, 1232, 1233, 1234, 1235, 1132, 1153, 1133, 1201, 1208, + /* 310 */ 1228, }; static const YYACTIONTYPE yy_default[] = { - /* 0 */ 647, 964, 964, 964, 878, 878, 969, 964, 774, 802, - /* 10 */ 802, 938, 969, 969, 969, 876, 969, 969, 969, 964, - /* 20 */ 969, 778, 808, 969, 969, 969, 969, 969, 969, 969, - /* 30 */ 969, 937, 939, 816, 815, 918, 789, 813, 806, 810, - /* 40 */ 879, 872, 873, 871, 875, 880, 969, 809, 841, 856, - /* 50 */ 840, 969, 969, 969, 969, 969, 969, 969, 969, 969, - /* 60 */ 969, 969, 969, 969, 969, 969, 969, 969, 969, 969, - /* 70 */ 969, 969, 969, 969, 969, 969, 969, 969, 969, 969, - /* 80 */ 969, 969, 969, 969, 969, 969, 969, 969, 969, 969, - /* 90 */ 969, 969, 969, 969, 850, 855, 862, 854, 851, 843, - /* 100 */ 842, 844, 845, 969, 969, 673, 739, 969, 969, 846, - /* 110 */ 969, 685, 847, 859, 858, 857, 680, 969, 969, 969, - /* 120 */ 969, 969, 969, 969, 969, 969, 969, 969, 969, 969, - /* 130 */ 969, 969, 969, 969, 969, 969, 969, 969, 969, 969, - /* 140 */ 969, 969, 969, 969, 647, 964, 969, 969, 964, 964, - /* 150 */ 964, 964, 964, 964, 956, 778, 768, 969, 969, 969, - /* 160 */ 969, 969, 969, 969, 969, 969, 969, 944, 942, 969, - /* 170 */ 891, 969, 969, 969, 969, 969, 969, 969, 969, 969, - /* 180 */ 969, 969, 969, 969, 969, 969, 969, 969, 969, 969, - /* 190 */ 969, 969, 969, 969, 969, 969, 969, 969, 969, 969, - /* 200 */ 969, 969, 969, 969, 653, 969, 911, 774, 774, 774, - /* 210 */ 776, 754, 766, 655, 812, 791, 791, 923, 812, 923, - /* 220 */ 710, 733, 707, 802, 791, 874, 802, 802, 775, 766, - /* 230 */ 969, 949, 782, 782, 941, 941, 782, 821, 743, 812, - /* 240 */ 750, 750, 750, 750, 782, 670, 812, 821, 743, 743, - /* 250 */ 812, 782, 670, 917, 915, 782, 782, 670, 782, 670, - /* 260 */ 782, 670, 884, 741, 741, 741, 725, 884, 741, 710, - /* 270 */ 741, 725, 741, 741, 795, 790, 795, 790, 795, 790, - /* 280 */ 782, 782, 969, 884, 888, 888, 884, 807, 796, 805, - /* 290 */ 803, 812, 676, 728, 663, 663, 652, 652, 652, 652, - /* 300 */ 961, 961, 956, 712, 712, 695, 969, 969, 969, 969, - /* 310 */ 969, 969, 687, 969, 893, 969, 969, 969, 969, 969, - /* 320 */ 969, 969, 969, 969, 969, 969, 969, 969, 969, 969, - /* 330 */ 969, 828, 969, 648, 951, 969, 969, 948, 969, 969, - /* 340 */ 969, 969, 969, 969, 969, 969, 969, 969, 969, 969, - /* 350 */ 969, 969, 969, 969, 969, 969, 921, 969, 969, 969, - /* 360 */ 969, 969, 969, 914, 913, 969, 969, 969, 969, 969, - /* 370 */ 969, 969, 969, 969, 969, 969, 969, 969, 969, 969, - /* 380 */ 969, 969, 969, 969, 969, 969, 969, 757, 969, 969, - /* 390 */ 969, 761, 969, 969, 969, 969, 969, 969, 804, 969, - /* 400 */ 797, 969, 877, 969, 969, 969, 969, 969, 969, 969, - /* 410 */ 969, 969, 969, 966, 969, 969, 969, 965, 969, 969, - /* 420 */ 969, 969, 969, 830, 969, 829, 833, 969, 661, 969, - /* 430 */ 644, 649, 960, 963, 962, 959, 958, 957, 952, 950, - /* 440 */ 947, 946, 945, 943, 940, 936, 897, 895, 902, 901, - /* 450 */ 900, 899, 898, 896, 894, 892, 818, 817, 814, 811, - /* 460 */ 753, 935, 890, 752, 749, 748, 669, 953, 920, 929, - /* 470 */ 928, 927, 822, 926, 925, 924, 922, 919, 906, 820, - /* 480 */ 819, 744, 882, 881, 672, 910, 909, 908, 912, 916, - /* 490 */ 907, 784, 751, 671, 668, 675, 679, 731, 732, 740, - /* 500 */ 738, 737, 736, 735, 734, 730, 681, 686, 724, 709, - /* 510 */ 708, 717, 716, 722, 721, 720, 719, 718, 715, 714, - /* 520 */ 713, 706, 705, 711, 704, 727, 726, 723, 703, 747, - /* 530 */ 746, 745, 742, 702, 701, 700, 833, 699, 698, 838, - /* 540 */ 837, 866, 826, 755, 759, 758, 762, 763, 771, 770, - /* 550 */ 769, 780, 781, 793, 792, 824, 823, 794, 779, 773, - /* 560 */ 772, 788, 787, 786, 785, 777, 767, 799, 798, 868, - /* 570 */ 783, 867, 865, 934, 933, 932, 931, 930, 870, 967, - /* 580 */ 968, 887, 889, 886, 801, 800, 885, 869, 839, 836, - /* 590 */ 690, 691, 905, 904, 903, 693, 692, 689, 688, 863, - /* 600 */ 860, 852, 864, 861, 853, 849, 848, 834, 832, 831, - /* 610 */ 827, 835, 760, 756, 825, 765, 764, 697, 696, 694, - /* 620 */ 678, 677, 674, 667, 665, 664, 666, 662, 660, 659, - /* 630 */ 658, 657, 656, 684, 683, 682, 654, 651, 650, 646, - /* 640 */ 645, 643, + /* 0 */ 982, 1300, 1300, 1300, 1214, 1214, 1214, 1305, 1300, 1109, + /* 10 */ 1138, 1138, 1274, 1305, 1305, 1305, 1305, 1305, 1305, 1212, + /* 20 */ 1305, 1305, 1305, 1300, 1305, 1113, 1144, 1305, 1305, 1305, + /* 30 */ 1305, 1305, 1305, 1305, 1305, 1273, 1275, 1152, 1151, 1254, + /* 40 */ 1125, 1149, 1142, 1146, 1215, 1208, 1209, 1207, 1211, 1216, + /* 50 */ 1305, 1145, 1177, 1192, 1176, 1305, 1305, 1305, 1305, 1305, + /* 60 */ 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, + /* 70 */ 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, + /* 80 */ 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, + /* 90 */ 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1186, 1191, + /* 100 */ 1198, 1190, 1187, 1179, 1178, 1180, 1181, 1305, 1305, 1008, + /* 110 */ 1074, 1305, 1305, 1182, 1305, 1020, 1183, 1195, 1194, 1193, + /* 120 */ 1015, 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, + /* 130 */ 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, + /* 140 */ 1305, 1305, 1305, 1305, 1305, 982, 1300, 1305, 1305, 1300, + /* 150 */ 1300, 1300, 1300, 1300, 1300, 1292, 1113, 1103, 1305, 1305, + /* 160 */ 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1280, 1278, + /* 170 */ 1305, 1227, 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, + /* 180 */ 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, + /* 190 */ 1305, 1305, 1305, 1109, 1305, 1305, 1305, 1305, 1305, 1305, + /* 200 */ 1305, 1305, 1305, 1305, 1305, 1305, 988, 1305, 1247, 1109, + /* 210 */ 1109, 1109, 1111, 1089, 1101, 990, 1148, 1127, 1127, 1259, + /* 220 */ 1148, 1259, 1045, 1068, 1042, 1138, 1127, 1210, 1138, 1138, + /* 230 */ 1110, 1101, 1305, 1285, 1118, 1118, 1277, 1277, 1118, 1157, + /* 240 */ 1078, 1148, 1085, 1085, 1085, 1085, 1118, 1005, 1148, 1157, + /* 250 */ 1078, 1078, 1148, 1118, 1005, 1253, 1251, 1118, 1118, 1005, + /* 260 */ 1220, 1118, 1005, 1118, 1005, 1220, 1076, 1076, 1076, 1060, + /* 270 */ 1220, 1076, 1045, 1076, 1060, 1076, 1076, 1131, 1126, 1131, + /* 280 */ 1126, 1131, 1126, 1131, 1126, 1118, 1118, 1305, 1220, 1224, + /* 290 */ 1224, 1220, 1143, 1132, 1141, 1139, 1148, 1011, 1063, 998, + /* 300 */ 998, 987, 987, 987, 987, 1297, 1297, 1292, 1047, 1047, + /* 310 */ 1030, 1305, 1305, 1305, 1305, 1305, 1305, 1022, 1305, 1229, + /* 320 */ 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, + /* 330 */ 1305, 1305, 1305, 1305, 1305, 1305, 1164, 1305, 983, 1287, + /* 340 */ 1305, 1305, 1284, 1305, 1305, 1305, 1305, 1305, 1305, 1305, + /* 350 */ 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, + /* 360 */ 1305, 1257, 1305, 1305, 1305, 1305, 1305, 1305, 1250, 1249, + /* 370 */ 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, + /* 380 */ 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, + /* 390 */ 1305, 1305, 1092, 1305, 1305, 1305, 1096, 1305, 1305, 1305, + /* 400 */ 1305, 1305, 1305, 1305, 1140, 1305, 1133, 1305, 1213, 1305, + /* 410 */ 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1305, 1302, + /* 420 */ 1305, 1305, 1305, 1301, 1305, 1305, 1305, 1305, 1305, 1166, + /* 430 */ 1305, 1165, 1169, 1305, 996, 1305, }; +/********** End of lemon-generated parsing tables *****************************/ -/* The next table maps tokens into fallback tokens. If a construct -** like the following: +/* The next table maps tokens (terminal symbols) into fallback tokens. +** If a construct like the following: ** ** %fallback ID X Y Z. ** @@ -117121,6 +128050,10 @@ static const YYACTIONTYPE yy_default[] = { ** and Z. Whenever one of the tokens X, Y, or Z is input to the parser ** but it does not parse, the type of the token is changed to ID and ** the parse is retried before an error is thrown. +** +** This feature can be used, for example, to cause some keywords in a language +** to revert to identifiers if they keyword does not apply in the context where +** it appears. */ #ifdef YYFALLBACK static const YYCODETYPE yyFallback[] = { @@ -117208,9 +128141,13 @@ static const YYCODETYPE yyFallback[] = { ** + The semantic value stored at this level of the stack. This is ** the information used by the action routines in the grammar. ** It is sometimes called the "minor" token. +** +** After the "shift" half of a SHIFTREDUCE action, the stateno field +** actually contains the reduce action for the second half of the +** SHIFTREDUCE. */ struct yyStackEntry { - YYACTIONTYPE stateno; /* The state-number */ + YYACTIONTYPE stateno; /* The state-number, or reduce action in SHIFTREDUCE */ YYCODETYPE major; /* The major token value. This is the code ** number for the token at this stack level */ YYMINORTYPE minor; /* The user-supplied minor token value. This @@ -117316,26 +128253,25 @@ static const char *const yyTokenName[] = { "column", "columnid", "type", "carglist", "typetoken", "typename", "signed", "plus_num", "minus_num", "ccons", "term", "expr", - "onconf", "sortorder", "autoinc", "idxlist_opt", + "onconf", "sortorder", "autoinc", "eidlist_opt", "refargs", "defer_subclause", "refarg", "refact", "init_deferred_pred_opt", "conslist", "tconscomma", "tcons", - "idxlist", "defer_subclause_opt", "orconf", "resolvetype", - "raisetype", "ifexists", "fullname", "selectnowith", - "oneselect", "with", "multiselect_op", "distinct", - "selcollist", "from", "where_opt", "groupby_opt", - "having_opt", "orderby_opt", "limit_opt", "values", - "nexprlist", "exprlist", "sclp", "as", - "seltablist", "stl_prefix", "joinop", "indexed_opt", - "on_opt", "using_opt", "joinop2", "idlist", - "sortlist", "setlist", "insert_cmd", "inscollist_opt", - "likeop", "between_op", "in_op", "case_operand", - "case_exprlist", "case_else", "uniqueflag", "collate", - "nmnum", "trigger_decl", "trigger_cmd_list", "trigger_time", - "trigger_event", "foreach_clause", "when_clause", "trigger_cmd", - "trnm", "tridxby", "database_kw_opt", "key_opt", - "add_column_fullname", "kwcolumn_opt", "create_vtab", "vtabarglist", - "vtabarg", "vtabargtoken", "lp", "anylist", - "wqlist", + "sortlist", "eidlist", "defer_subclause_opt", "orconf", + "resolvetype", "raisetype", "ifexists", "fullname", + "selectnowith", "oneselect", "with", "multiselect_op", + "distinct", "selcollist", "from", "where_opt", + "groupby_opt", "having_opt", "orderby_opt", "limit_opt", + "values", "nexprlist", "exprlist", "sclp", + "as", "seltablist", "stl_prefix", "joinop", + "indexed_opt", "on_opt", "using_opt", "idlist", + "setlist", "insert_cmd", "idlist_opt", "likeop", + "between_op", "in_op", "case_operand", "case_exprlist", + "case_else", "uniqueflag", "collate", "nmnum", + "trigger_decl", "trigger_cmd_list", "trigger_time", "trigger_event", + "foreach_clause", "when_clause", "trigger_cmd", "trnm", + "tridxby", "database_kw_opt", "key_opt", "add_column_fullname", + "kwcolumn_opt", "create_vtab", "vtabarglist", "vtabarg", + "vtabargtoken", "lp", "anylist", "wqlist", }; #endif /* NDEBUG */ @@ -117408,7 +128344,7 @@ static const char *const yyRuleName[] = { /* 62 */ "ccons ::= PRIMARY KEY sortorder onconf autoinc", /* 63 */ "ccons ::= UNIQUE onconf", /* 64 */ "ccons ::= CHECK LP expr RP", - /* 65 */ "ccons ::= REFERENCES nm idxlist_opt refargs", + /* 65 */ "ccons ::= REFERENCES nm eidlist_opt refargs", /* 66 */ "ccons ::= defer_subclause", /* 67 */ "ccons ::= COLLATE ID|STRING", /* 68 */ "autoinc ::=", @@ -117436,10 +128372,10 @@ static const char *const yyRuleName[] = { /* 90 */ "tconscomma ::= COMMA", /* 91 */ "tconscomma ::=", /* 92 */ "tcons ::= CONSTRAINT nm", - /* 93 */ "tcons ::= PRIMARY KEY LP idxlist autoinc RP onconf", - /* 94 */ "tcons ::= UNIQUE LP idxlist RP onconf", + /* 93 */ "tcons ::= PRIMARY KEY LP sortlist autoinc RP onconf", + /* 94 */ "tcons ::= UNIQUE LP sortlist RP onconf", /* 95 */ "tcons ::= CHECK LP expr RP onconf", - /* 96 */ "tcons ::= FOREIGN KEY LP idxlist RP REFERENCES nm idxlist_opt refargs defer_subclause_opt", + /* 96 */ "tcons ::= FOREIGN KEY LP eidlist RP REFERENCES nm eidlist_opt refargs defer_subclause_opt", /* 97 */ "defer_subclause_opt ::=", /* 98 */ "defer_subclause_opt ::= defer_subclause", /* 99 */ "onconf ::=", @@ -117452,7 +128388,7 @@ static const char *const yyRuleName[] = { /* 106 */ "cmd ::= DROP TABLE ifexists fullname", /* 107 */ "ifexists ::= IF EXISTS", /* 108 */ "ifexists ::=", - /* 109 */ "cmd ::= createkw temp VIEW ifnotexists nm dbnm AS select", + /* 109 */ "cmd ::= createkw temp VIEW ifnotexists nm dbnm eidlist_opt AS select", /* 110 */ "cmd ::= DROP VIEW ifexists fullname", /* 111 */ "cmd ::= select", /* 112 */ "select ::= with selectnowith", @@ -117481,195 +128417,196 @@ static const char *const yyRuleName[] = { /* 135 */ "stl_prefix ::= seltablist joinop", /* 136 */ "stl_prefix ::=", /* 137 */ "seltablist ::= stl_prefix nm dbnm as indexed_opt on_opt using_opt", - /* 138 */ "seltablist ::= stl_prefix LP select RP as on_opt using_opt", - /* 139 */ "seltablist ::= stl_prefix LP seltablist RP as on_opt using_opt", - /* 140 */ "dbnm ::=", - /* 141 */ "dbnm ::= DOT nm", - /* 142 */ "fullname ::= nm dbnm", - /* 143 */ "joinop ::= COMMA|JOIN", - /* 144 */ "joinop ::= JOIN_KW JOIN", - /* 145 */ "joinop ::= JOIN_KW nm JOIN", - /* 146 */ "joinop ::= JOIN_KW nm nm JOIN", - /* 147 */ "on_opt ::= ON expr", - /* 148 */ "on_opt ::=", - /* 149 */ "indexed_opt ::=", - /* 150 */ "indexed_opt ::= INDEXED BY nm", - /* 151 */ "indexed_opt ::= NOT INDEXED", - /* 152 */ "using_opt ::= USING LP idlist RP", - /* 153 */ "using_opt ::=", - /* 154 */ "orderby_opt ::=", - /* 155 */ "orderby_opt ::= ORDER BY sortlist", - /* 156 */ "sortlist ::= sortlist COMMA expr sortorder", - /* 157 */ "sortlist ::= expr sortorder", - /* 158 */ "sortorder ::= ASC", - /* 159 */ "sortorder ::= DESC", - /* 160 */ "sortorder ::=", - /* 161 */ "groupby_opt ::=", - /* 162 */ "groupby_opt ::= GROUP BY nexprlist", - /* 163 */ "having_opt ::=", - /* 164 */ "having_opt ::= HAVING expr", - /* 165 */ "limit_opt ::=", - /* 166 */ "limit_opt ::= LIMIT expr", - /* 167 */ "limit_opt ::= LIMIT expr OFFSET expr", - /* 168 */ "limit_opt ::= LIMIT expr COMMA expr", - /* 169 */ "cmd ::= with DELETE FROM fullname indexed_opt where_opt", - /* 170 */ "where_opt ::=", - /* 171 */ "where_opt ::= WHERE expr", - /* 172 */ "cmd ::= with UPDATE orconf fullname indexed_opt SET setlist where_opt", - /* 173 */ "setlist ::= setlist COMMA nm EQ expr", - /* 174 */ "setlist ::= nm EQ expr", - /* 175 */ "cmd ::= with insert_cmd INTO fullname inscollist_opt select", - /* 176 */ "cmd ::= with insert_cmd INTO fullname inscollist_opt DEFAULT VALUES", - /* 177 */ "insert_cmd ::= INSERT orconf", - /* 178 */ "insert_cmd ::= REPLACE", - /* 179 */ "inscollist_opt ::=", - /* 180 */ "inscollist_opt ::= LP idlist RP", - /* 181 */ "idlist ::= idlist COMMA nm", - /* 182 */ "idlist ::= nm", - /* 183 */ "expr ::= term", - /* 184 */ "expr ::= LP expr RP", - /* 185 */ "term ::= NULL", - /* 186 */ "expr ::= ID|INDEXED", - /* 187 */ "expr ::= JOIN_KW", - /* 188 */ "expr ::= nm DOT nm", - /* 189 */ "expr ::= nm DOT nm DOT nm", - /* 190 */ "term ::= INTEGER|FLOAT|BLOB", - /* 191 */ "term ::= STRING", - /* 192 */ "expr ::= VARIABLE", - /* 193 */ "expr ::= expr COLLATE ID|STRING", - /* 194 */ "expr ::= CAST LP expr AS typetoken RP", - /* 195 */ "expr ::= ID|INDEXED LP distinct exprlist RP", - /* 196 */ "expr ::= ID|INDEXED LP STAR RP", - /* 197 */ "term ::= CTIME_KW", - /* 198 */ "expr ::= expr AND expr", - /* 199 */ "expr ::= expr OR expr", - /* 200 */ "expr ::= expr LT|GT|GE|LE expr", - /* 201 */ "expr ::= expr EQ|NE expr", - /* 202 */ "expr ::= expr BITAND|BITOR|LSHIFT|RSHIFT expr", - /* 203 */ "expr ::= expr PLUS|MINUS expr", - /* 204 */ "expr ::= expr STAR|SLASH|REM expr", - /* 205 */ "expr ::= expr CONCAT expr", - /* 206 */ "likeop ::= LIKE_KW|MATCH", - /* 207 */ "likeop ::= NOT LIKE_KW|MATCH", - /* 208 */ "expr ::= expr likeop expr", - /* 209 */ "expr ::= expr likeop expr ESCAPE expr", - /* 210 */ "expr ::= expr ISNULL|NOTNULL", - /* 211 */ "expr ::= expr NOT NULL", - /* 212 */ "expr ::= expr IS expr", - /* 213 */ "expr ::= expr IS NOT expr", - /* 214 */ "expr ::= NOT expr", - /* 215 */ "expr ::= BITNOT expr", - /* 216 */ "expr ::= MINUS expr", - /* 217 */ "expr ::= PLUS expr", - /* 218 */ "between_op ::= BETWEEN", - /* 219 */ "between_op ::= NOT BETWEEN", - /* 220 */ "expr ::= expr between_op expr AND expr", - /* 221 */ "in_op ::= IN", - /* 222 */ "in_op ::= NOT IN", - /* 223 */ "expr ::= expr in_op LP exprlist RP", - /* 224 */ "expr ::= LP select RP", - /* 225 */ "expr ::= expr in_op LP select RP", - /* 226 */ "expr ::= expr in_op nm dbnm", - /* 227 */ "expr ::= EXISTS LP select RP", - /* 228 */ "expr ::= CASE case_operand case_exprlist case_else END", - /* 229 */ "case_exprlist ::= case_exprlist WHEN expr THEN expr", - /* 230 */ "case_exprlist ::= WHEN expr THEN expr", - /* 231 */ "case_else ::= ELSE expr", - /* 232 */ "case_else ::=", - /* 233 */ "case_operand ::= expr", - /* 234 */ "case_operand ::=", - /* 235 */ "exprlist ::= nexprlist", - /* 236 */ "exprlist ::=", - /* 237 */ "nexprlist ::= nexprlist COMMA expr", - /* 238 */ "nexprlist ::= expr", - /* 239 */ "cmd ::= createkw uniqueflag INDEX ifnotexists nm dbnm ON nm LP idxlist RP where_opt", - /* 240 */ "uniqueflag ::= UNIQUE", - /* 241 */ "uniqueflag ::=", - /* 242 */ "idxlist_opt ::=", - /* 243 */ "idxlist_opt ::= LP idxlist RP", - /* 244 */ "idxlist ::= idxlist COMMA nm collate sortorder", - /* 245 */ "idxlist ::= nm collate sortorder", - /* 246 */ "collate ::=", - /* 247 */ "collate ::= COLLATE ID|STRING", - /* 248 */ "cmd ::= DROP INDEX ifexists fullname", - /* 249 */ "cmd ::= VACUUM", - /* 250 */ "cmd ::= VACUUM nm", - /* 251 */ "cmd ::= PRAGMA nm dbnm", - /* 252 */ "cmd ::= PRAGMA nm dbnm EQ nmnum", - /* 253 */ "cmd ::= PRAGMA nm dbnm LP nmnum RP", - /* 254 */ "cmd ::= PRAGMA nm dbnm EQ minus_num", - /* 255 */ "cmd ::= PRAGMA nm dbnm LP minus_num RP", - /* 256 */ "nmnum ::= plus_num", - /* 257 */ "nmnum ::= nm", - /* 258 */ "nmnum ::= ON", - /* 259 */ "nmnum ::= DELETE", - /* 260 */ "nmnum ::= DEFAULT", - /* 261 */ "plus_num ::= PLUS INTEGER|FLOAT", - /* 262 */ "plus_num ::= INTEGER|FLOAT", - /* 263 */ "minus_num ::= MINUS INTEGER|FLOAT", - /* 264 */ "cmd ::= createkw trigger_decl BEGIN trigger_cmd_list END", - /* 265 */ "trigger_decl ::= temp TRIGGER ifnotexists nm dbnm trigger_time trigger_event ON fullname foreach_clause when_clause", - /* 266 */ "trigger_time ::= BEFORE", - /* 267 */ "trigger_time ::= AFTER", - /* 268 */ "trigger_time ::= INSTEAD OF", - /* 269 */ "trigger_time ::=", - /* 270 */ "trigger_event ::= DELETE|INSERT", - /* 271 */ "trigger_event ::= UPDATE", - /* 272 */ "trigger_event ::= UPDATE OF idlist", - /* 273 */ "foreach_clause ::=", - /* 274 */ "foreach_clause ::= FOR EACH ROW", - /* 275 */ "when_clause ::=", - /* 276 */ "when_clause ::= WHEN expr", - /* 277 */ "trigger_cmd_list ::= trigger_cmd_list trigger_cmd SEMI", - /* 278 */ "trigger_cmd_list ::= trigger_cmd SEMI", - /* 279 */ "trnm ::= nm", - /* 280 */ "trnm ::= nm DOT nm", - /* 281 */ "tridxby ::=", - /* 282 */ "tridxby ::= INDEXED BY nm", - /* 283 */ "tridxby ::= NOT INDEXED", - /* 284 */ "trigger_cmd ::= UPDATE orconf trnm tridxby SET setlist where_opt", - /* 285 */ "trigger_cmd ::= insert_cmd INTO trnm inscollist_opt select", - /* 286 */ "trigger_cmd ::= DELETE FROM trnm tridxby where_opt", - /* 287 */ "trigger_cmd ::= select", - /* 288 */ "expr ::= RAISE LP IGNORE RP", - /* 289 */ "expr ::= RAISE LP raisetype COMMA nm RP", - /* 290 */ "raisetype ::= ROLLBACK", - /* 291 */ "raisetype ::= ABORT", - /* 292 */ "raisetype ::= FAIL", - /* 293 */ "cmd ::= DROP TRIGGER ifexists fullname", - /* 294 */ "cmd ::= ATTACH database_kw_opt expr AS expr key_opt", - /* 295 */ "cmd ::= DETACH database_kw_opt expr", - /* 296 */ "key_opt ::=", - /* 297 */ "key_opt ::= KEY expr", - /* 298 */ "database_kw_opt ::= DATABASE", - /* 299 */ "database_kw_opt ::=", - /* 300 */ "cmd ::= REINDEX", - /* 301 */ "cmd ::= REINDEX nm dbnm", - /* 302 */ "cmd ::= ANALYZE", - /* 303 */ "cmd ::= ANALYZE nm dbnm", - /* 304 */ "cmd ::= ALTER TABLE fullname RENAME TO nm", - /* 305 */ "cmd ::= ALTER TABLE add_column_fullname ADD kwcolumn_opt column", - /* 306 */ "add_column_fullname ::= fullname", - /* 307 */ "kwcolumn_opt ::=", - /* 308 */ "kwcolumn_opt ::= COLUMNKW", - /* 309 */ "cmd ::= create_vtab", - /* 310 */ "cmd ::= create_vtab LP vtabarglist RP", - /* 311 */ "create_vtab ::= createkw VIRTUAL TABLE ifnotexists nm dbnm USING nm", - /* 312 */ "vtabarglist ::= vtabarg", - /* 313 */ "vtabarglist ::= vtabarglist COMMA vtabarg", - /* 314 */ "vtabarg ::=", - /* 315 */ "vtabarg ::= vtabarg vtabargtoken", - /* 316 */ "vtabargtoken ::= ANY", - /* 317 */ "vtabargtoken ::= lp anylist RP", - /* 318 */ "lp ::= LP", - /* 319 */ "anylist ::=", - /* 320 */ "anylist ::= anylist LP anylist RP", - /* 321 */ "anylist ::= anylist ANY", - /* 322 */ "with ::=", - /* 323 */ "with ::= WITH wqlist", - /* 324 */ "with ::= WITH RECURSIVE wqlist", - /* 325 */ "wqlist ::= nm idxlist_opt AS LP select RP", - /* 326 */ "wqlist ::= wqlist COMMA nm idxlist_opt AS LP select RP", + /* 138 */ "seltablist ::= stl_prefix nm dbnm LP exprlist RP as on_opt using_opt", + /* 139 */ "seltablist ::= stl_prefix LP select RP as on_opt using_opt", + /* 140 */ "seltablist ::= stl_prefix LP seltablist RP as on_opt using_opt", + /* 141 */ "dbnm ::=", + /* 142 */ "dbnm ::= DOT nm", + /* 143 */ "fullname ::= nm dbnm", + /* 144 */ "joinop ::= COMMA|JOIN", + /* 145 */ "joinop ::= JOIN_KW JOIN", + /* 146 */ "joinop ::= JOIN_KW nm JOIN", + /* 147 */ "joinop ::= JOIN_KW nm nm JOIN", + /* 148 */ "on_opt ::= ON expr", + /* 149 */ "on_opt ::=", + /* 150 */ "indexed_opt ::=", + /* 151 */ "indexed_opt ::= INDEXED BY nm", + /* 152 */ "indexed_opt ::= NOT INDEXED", + /* 153 */ "using_opt ::= USING LP idlist RP", + /* 154 */ "using_opt ::=", + /* 155 */ "orderby_opt ::=", + /* 156 */ "orderby_opt ::= ORDER BY sortlist", + /* 157 */ "sortlist ::= sortlist COMMA expr sortorder", + /* 158 */ "sortlist ::= expr sortorder", + /* 159 */ "sortorder ::= ASC", + /* 160 */ "sortorder ::= DESC", + /* 161 */ "sortorder ::=", + /* 162 */ "groupby_opt ::=", + /* 163 */ "groupby_opt ::= GROUP BY nexprlist", + /* 164 */ "having_opt ::=", + /* 165 */ "having_opt ::= HAVING expr", + /* 166 */ "limit_opt ::=", + /* 167 */ "limit_opt ::= LIMIT expr", + /* 168 */ "limit_opt ::= LIMIT expr OFFSET expr", + /* 169 */ "limit_opt ::= LIMIT expr COMMA expr", + /* 170 */ "cmd ::= with DELETE FROM fullname indexed_opt where_opt", + /* 171 */ "where_opt ::=", + /* 172 */ "where_opt ::= WHERE expr", + /* 173 */ "cmd ::= with UPDATE orconf fullname indexed_opt SET setlist where_opt", + /* 174 */ "setlist ::= setlist COMMA nm EQ expr", + /* 175 */ "setlist ::= nm EQ expr", + /* 176 */ "cmd ::= with insert_cmd INTO fullname idlist_opt select", + /* 177 */ "cmd ::= with insert_cmd INTO fullname idlist_opt DEFAULT VALUES", + /* 178 */ "insert_cmd ::= INSERT orconf", + /* 179 */ "insert_cmd ::= REPLACE", + /* 180 */ "idlist_opt ::=", + /* 181 */ "idlist_opt ::= LP idlist RP", + /* 182 */ "idlist ::= idlist COMMA nm", + /* 183 */ "idlist ::= nm", + /* 184 */ "expr ::= term", + /* 185 */ "expr ::= LP expr RP", + /* 186 */ "term ::= NULL", + /* 187 */ "expr ::= ID|INDEXED", + /* 188 */ "expr ::= JOIN_KW", + /* 189 */ "expr ::= nm DOT nm", + /* 190 */ "expr ::= nm DOT nm DOT nm", + /* 191 */ "term ::= INTEGER|FLOAT|BLOB", + /* 192 */ "term ::= STRING", + /* 193 */ "expr ::= VARIABLE", + /* 194 */ "expr ::= expr COLLATE ID|STRING", + /* 195 */ "expr ::= CAST LP expr AS typetoken RP", + /* 196 */ "expr ::= ID|INDEXED LP distinct exprlist RP", + /* 197 */ "expr ::= ID|INDEXED LP STAR RP", + /* 198 */ "term ::= CTIME_KW", + /* 199 */ "expr ::= expr AND expr", + /* 200 */ "expr ::= expr OR expr", + /* 201 */ "expr ::= expr LT|GT|GE|LE expr", + /* 202 */ "expr ::= expr EQ|NE expr", + /* 203 */ "expr ::= expr BITAND|BITOR|LSHIFT|RSHIFT expr", + /* 204 */ "expr ::= expr PLUS|MINUS expr", + /* 205 */ "expr ::= expr STAR|SLASH|REM expr", + /* 206 */ "expr ::= expr CONCAT expr", + /* 207 */ "likeop ::= LIKE_KW|MATCH", + /* 208 */ "likeop ::= NOT LIKE_KW|MATCH", + /* 209 */ "expr ::= expr likeop expr", + /* 210 */ "expr ::= expr likeop expr ESCAPE expr", + /* 211 */ "expr ::= expr ISNULL|NOTNULL", + /* 212 */ "expr ::= expr NOT NULL", + /* 213 */ "expr ::= expr IS expr", + /* 214 */ "expr ::= expr IS NOT expr", + /* 215 */ "expr ::= NOT expr", + /* 216 */ "expr ::= BITNOT expr", + /* 217 */ "expr ::= MINUS expr", + /* 218 */ "expr ::= PLUS expr", + /* 219 */ "between_op ::= BETWEEN", + /* 220 */ "between_op ::= NOT BETWEEN", + /* 221 */ "expr ::= expr between_op expr AND expr", + /* 222 */ "in_op ::= IN", + /* 223 */ "in_op ::= NOT IN", + /* 224 */ "expr ::= expr in_op LP exprlist RP", + /* 225 */ "expr ::= LP select RP", + /* 226 */ "expr ::= expr in_op LP select RP", + /* 227 */ "expr ::= expr in_op nm dbnm", + /* 228 */ "expr ::= EXISTS LP select RP", + /* 229 */ "expr ::= CASE case_operand case_exprlist case_else END", + /* 230 */ "case_exprlist ::= case_exprlist WHEN expr THEN expr", + /* 231 */ "case_exprlist ::= WHEN expr THEN expr", + /* 232 */ "case_else ::= ELSE expr", + /* 233 */ "case_else ::=", + /* 234 */ "case_operand ::= expr", + /* 235 */ "case_operand ::=", + /* 236 */ "exprlist ::= nexprlist", + /* 237 */ "exprlist ::=", + /* 238 */ "nexprlist ::= nexprlist COMMA expr", + /* 239 */ "nexprlist ::= expr", + /* 240 */ "cmd ::= createkw uniqueflag INDEX ifnotexists nm dbnm ON nm LP sortlist RP where_opt", + /* 241 */ "uniqueflag ::= UNIQUE", + /* 242 */ "uniqueflag ::=", + /* 243 */ "eidlist_opt ::=", + /* 244 */ "eidlist_opt ::= LP eidlist RP", + /* 245 */ "eidlist ::= eidlist COMMA nm collate sortorder", + /* 246 */ "eidlist ::= nm collate sortorder", + /* 247 */ "collate ::=", + /* 248 */ "collate ::= COLLATE ID|STRING", + /* 249 */ "cmd ::= DROP INDEX ifexists fullname", + /* 250 */ "cmd ::= VACUUM", + /* 251 */ "cmd ::= VACUUM nm", + /* 252 */ "cmd ::= PRAGMA nm dbnm", + /* 253 */ "cmd ::= PRAGMA nm dbnm EQ nmnum", + /* 254 */ "cmd ::= PRAGMA nm dbnm LP nmnum RP", + /* 255 */ "cmd ::= PRAGMA nm dbnm EQ minus_num", + /* 256 */ "cmd ::= PRAGMA nm dbnm LP minus_num RP", + /* 257 */ "nmnum ::= plus_num", + /* 258 */ "nmnum ::= nm", + /* 259 */ "nmnum ::= ON", + /* 260 */ "nmnum ::= DELETE", + /* 261 */ "nmnum ::= DEFAULT", + /* 262 */ "plus_num ::= PLUS INTEGER|FLOAT", + /* 263 */ "plus_num ::= INTEGER|FLOAT", + /* 264 */ "minus_num ::= MINUS INTEGER|FLOAT", + /* 265 */ "cmd ::= createkw trigger_decl BEGIN trigger_cmd_list END", + /* 266 */ "trigger_decl ::= temp TRIGGER ifnotexists nm dbnm trigger_time trigger_event ON fullname foreach_clause when_clause", + /* 267 */ "trigger_time ::= BEFORE", + /* 268 */ "trigger_time ::= AFTER", + /* 269 */ "trigger_time ::= INSTEAD OF", + /* 270 */ "trigger_time ::=", + /* 271 */ "trigger_event ::= DELETE|INSERT", + /* 272 */ "trigger_event ::= UPDATE", + /* 273 */ "trigger_event ::= UPDATE OF idlist", + /* 274 */ "foreach_clause ::=", + /* 275 */ "foreach_clause ::= FOR EACH ROW", + /* 276 */ "when_clause ::=", + /* 277 */ "when_clause ::= WHEN expr", + /* 278 */ "trigger_cmd_list ::= trigger_cmd_list trigger_cmd SEMI", + /* 279 */ "trigger_cmd_list ::= trigger_cmd SEMI", + /* 280 */ "trnm ::= nm", + /* 281 */ "trnm ::= nm DOT nm", + /* 282 */ "tridxby ::=", + /* 283 */ "tridxby ::= INDEXED BY nm", + /* 284 */ "tridxby ::= NOT INDEXED", + /* 285 */ "trigger_cmd ::= UPDATE orconf trnm tridxby SET setlist where_opt", + /* 286 */ "trigger_cmd ::= insert_cmd INTO trnm idlist_opt select", + /* 287 */ "trigger_cmd ::= DELETE FROM trnm tridxby where_opt", + /* 288 */ "trigger_cmd ::= select", + /* 289 */ "expr ::= RAISE LP IGNORE RP", + /* 290 */ "expr ::= RAISE LP raisetype COMMA nm RP", + /* 291 */ "raisetype ::= ROLLBACK", + /* 292 */ "raisetype ::= ABORT", + /* 293 */ "raisetype ::= FAIL", + /* 294 */ "cmd ::= DROP TRIGGER ifexists fullname", + /* 295 */ "cmd ::= ATTACH database_kw_opt expr AS expr key_opt", + /* 296 */ "cmd ::= DETACH database_kw_opt expr", + /* 297 */ "key_opt ::=", + /* 298 */ "key_opt ::= KEY expr", + /* 299 */ "database_kw_opt ::= DATABASE", + /* 300 */ "database_kw_opt ::=", + /* 301 */ "cmd ::= REINDEX", + /* 302 */ "cmd ::= REINDEX nm dbnm", + /* 303 */ "cmd ::= ANALYZE", + /* 304 */ "cmd ::= ANALYZE nm dbnm", + /* 305 */ "cmd ::= ALTER TABLE fullname RENAME TO nm", + /* 306 */ "cmd ::= ALTER TABLE add_column_fullname ADD kwcolumn_opt column", + /* 307 */ "add_column_fullname ::= fullname", + /* 308 */ "kwcolumn_opt ::=", + /* 309 */ "kwcolumn_opt ::= COLUMNKW", + /* 310 */ "cmd ::= create_vtab", + /* 311 */ "cmd ::= create_vtab LP vtabarglist RP", + /* 312 */ "create_vtab ::= createkw VIRTUAL TABLE ifnotexists nm dbnm USING nm", + /* 313 */ "vtabarglist ::= vtabarg", + /* 314 */ "vtabarglist ::= vtabarglist COMMA vtabarg", + /* 315 */ "vtabarg ::=", + /* 316 */ "vtabarg ::= vtabarg vtabargtoken", + /* 317 */ "vtabargtoken ::= ANY", + /* 318 */ "vtabargtoken ::= lp anylist RP", + /* 319 */ "lp ::= LP", + /* 320 */ "anylist ::=", + /* 321 */ "anylist ::= anylist LP anylist RP", + /* 322 */ "anylist ::= anylist ANY", + /* 323 */ "with ::=", + /* 324 */ "with ::= WITH wqlist", + /* 325 */ "with ::= WITH RECURSIVE wqlist", + /* 326 */ "wqlist ::= nm eidlist_opt AS LP select RP", + /* 327 */ "wqlist ::= wqlist COMMA nm eidlist_opt AS LP select RP", }; #endif /* NDEBUG */ @@ -117697,6 +128634,15 @@ static void yyGrowStack(yyParser *p){ } #endif +/* Datatype of the argument to the memory allocated passed as the +** second argument to sqlite3ParserAlloc() below. This can be changed by +** putting an appropriate #define in the %include section of the input +** grammar. +*/ +#ifndef YYMALLOCARGTYPE +# define YYMALLOCARGTYPE size_t +#endif + /* ** This function allocates a new parser. ** The only argument is a pointer to a function which works like @@ -117709,9 +128655,9 @@ static void yyGrowStack(yyParser *p){ ** A pointer to a parser. This pointer is used in subsequent calls ** to sqlite3Parser and sqlite3ParserFree. */ -SQLITE_PRIVATE void *sqlite3ParserAlloc(void *(*mallocProc)(size_t)){ +SQLITE_PRIVATE void *sqlite3ParserAlloc(void *(*mallocProc)(YYMALLOCARGTYPE)){ yyParser *pParser; - pParser = (yyParser*)(*mallocProc)( (size_t)sizeof(yyParser) ); + pParser = (yyParser*)(*mallocProc)( (YYMALLOCARGTYPE)sizeof(yyParser) ); if( pParser ){ pParser->yyidx = -1; #ifdef YYTRACKMAXSTACKDEPTH @@ -117726,10 +128672,12 @@ SQLITE_PRIVATE void *sqlite3ParserAlloc(void *(*mallocProc)(size_t)){ return pParser; } -/* The following function deletes the value associated with a -** symbol. The symbol can be either a terminal or nonterminal. -** "yymajor" is the symbol code, and "yypminor" is a pointer to -** the value. +/* The following function deletes the "minor type" or semantic value +** associated with a symbol. The symbol can be either a terminal +** or nonterminal. "yymajor" is the symbol code, and "yypminor" is +** a pointer to the value to be deleted. The code used to do the +** deletions is derived from the %destructor and/or %token_destructor +** directives of the input grammar. */ static void yy_destructor( yyParser *yypParser, /* The parser */ @@ -117745,81 +128693,83 @@ static void yy_destructor( ** being destroyed before it is finished parsing. ** ** Note: during a reduce, the only symbols destroyed are those - ** which appear on the RHS of the rule, but which are not used + ** which appear on the RHS of the rule, but which are *not* used ** inside the C code. */ +/********* Begin destructor definitions ***************************************/ case 163: /* select */ - case 195: /* selectnowith */ - case 196: /* oneselect */ - case 207: /* values */ + case 196: /* selectnowith */ + case 197: /* oneselect */ + case 208: /* values */ { -sqlite3SelectDelete(pParse->db, (yypminor->yy3)); +sqlite3SelectDelete(pParse->db, (yypminor->yy387)); } break; case 174: /* term */ case 175: /* expr */ { -sqlite3ExprDelete(pParse->db, (yypminor->yy346).pExpr); +sqlite3ExprDelete(pParse->db, (yypminor->yy118).pExpr); } break; - case 179: /* idxlist_opt */ - case 188: /* idxlist */ - case 200: /* selcollist */ - case 203: /* groupby_opt */ - case 205: /* orderby_opt */ - case 208: /* nexprlist */ - case 209: /* exprlist */ - case 210: /* sclp */ - case 220: /* sortlist */ - case 221: /* setlist */ - case 228: /* case_exprlist */ + case 179: /* eidlist_opt */ + case 188: /* sortlist */ + case 189: /* eidlist */ + case 201: /* selcollist */ + case 204: /* groupby_opt */ + case 206: /* orderby_opt */ + case 209: /* nexprlist */ + case 210: /* exprlist */ + case 211: /* sclp */ + case 220: /* setlist */ + case 227: /* case_exprlist */ { -sqlite3ExprListDelete(pParse->db, (yypminor->yy14)); +sqlite3ExprListDelete(pParse->db, (yypminor->yy322)); } break; - case 194: /* fullname */ - case 201: /* from */ - case 212: /* seltablist */ - case 213: /* stl_prefix */ + case 195: /* fullname */ + case 202: /* from */ + case 213: /* seltablist */ + case 214: /* stl_prefix */ { -sqlite3SrcListDelete(pParse->db, (yypminor->yy65)); +sqlite3SrcListDelete(pParse->db, (yypminor->yy259)); } break; - case 197: /* with */ - case 252: /* wqlist */ + case 198: /* with */ + case 251: /* wqlist */ { -sqlite3WithDelete(pParse->db, (yypminor->yy59)); +sqlite3WithDelete(pParse->db, (yypminor->yy451)); } break; - case 202: /* where_opt */ - case 204: /* having_opt */ - case 216: /* on_opt */ - case 227: /* case_operand */ - case 229: /* case_else */ - case 238: /* when_clause */ - case 243: /* key_opt */ + case 203: /* where_opt */ + case 205: /* having_opt */ + case 217: /* on_opt */ + case 226: /* case_operand */ + case 228: /* case_else */ + case 237: /* when_clause */ + case 242: /* key_opt */ { -sqlite3ExprDelete(pParse->db, (yypminor->yy132)); +sqlite3ExprDelete(pParse->db, (yypminor->yy314)); } break; - case 217: /* using_opt */ + case 218: /* using_opt */ case 219: /* idlist */ - case 223: /* inscollist_opt */ + case 222: /* idlist_opt */ { -sqlite3IdListDelete(pParse->db, (yypminor->yy408)); +sqlite3IdListDelete(pParse->db, (yypminor->yy384)); } break; - case 234: /* trigger_cmd_list */ - case 239: /* trigger_cmd */ + case 233: /* trigger_cmd_list */ + case 238: /* trigger_cmd */ { -sqlite3DeleteTriggerStep(pParse->db, (yypminor->yy473)); +sqlite3DeleteTriggerStep(pParse->db, (yypminor->yy203)); } break; - case 236: /* trigger_event */ + case 235: /* trigger_event */ { -sqlite3IdListDelete(pParse->db, (yypminor->yy378).b); +sqlite3IdListDelete(pParse->db, (yypminor->yy90).b); } break; +/********* End destructor definitions *****************************************/ default: break; /* If no destructor action specified: do nothing */ } } @@ -117829,49 +128779,37 @@ sqlite3IdListDelete(pParse->db, (yypminor->yy378).b); ** ** If there is a destructor routine associated with the token which ** is popped from the stack, then call it. -** -** Return the major token number for the symbol popped. */ -static int yy_pop_parser_stack(yyParser *pParser){ - YYCODETYPE yymajor; - yyStackEntry *yytos = &pParser->yystack[pParser->yyidx]; - - /* There is no mechanism by which the parser stack can be popped below - ** empty in SQLite. */ - if( NEVER(pParser->yyidx<0) ) return 0; +static void yy_pop_parser_stack(yyParser *pParser){ + yyStackEntry *yytos; + assert( pParser->yyidx>=0 ); + yytos = &pParser->yystack[pParser->yyidx--]; #ifndef NDEBUG - if( yyTraceFILE && pParser->yyidx>=0 ){ + if( yyTraceFILE ){ fprintf(yyTraceFILE,"%sPopping %s\n", yyTracePrompt, yyTokenName[yytos->major]); } #endif - yymajor = yytos->major; - yy_destructor(pParser, yymajor, &yytos->minor); - pParser->yyidx--; - return yymajor; + yy_destructor(pParser, yytos->major, &yytos->minor); } /* -** Deallocate and destroy a parser. Destructors are all called for +** Deallocate and destroy a parser. Destructors are called for ** all stack elements before shutting the parser down. ** -** Inputs: -**
      -**
    • A pointer to the parser. This should be a pointer -** obtained from sqlite3ParserAlloc. -**
    • A pointer to a function used to reclaim memory obtained -** from malloc. -**
    +** If the YYPARSEFREENEVERNULL macro exists (for example because it +** is defined in a %include section of the input grammar) then it is +** assumed that the input pointer is never NULL. */ SQLITE_PRIVATE void sqlite3ParserFree( void *p, /* The parser to be deleted */ void (*freeProc)(void*) /* Function used to reclaim memory */ ){ yyParser *pParser = (yyParser*)p; - /* In SQLite, we never try to destroy a parser that was not successfully - ** created in the first place. */ - if( NEVER(pParser==0) ) return; +#ifndef YYPARSEFREENEVERNULL + if( pParser==0 ) return; +#endif while( pParser->yyidx>=0 ) yy_pop_parser_stack(pParser); #if YYSTACKDEPTH<=0 free(pParser->yystack); @@ -117892,10 +128830,6 @@ SQLITE_PRIVATE int sqlite3ParserStackPeak(void *p){ /* ** Find the appropriate action for a parser given the terminal ** look-ahead token iLookAhead. -** -** If the look-ahead token is YYNOCODE, then check to see if the action is -** independent of the look-ahead. If it is, return the action, otherwise -** return YY_NO_ACTION. */ static int yy_find_shift_action( yyParser *pParser, /* The parser */ @@ -117904,63 +128838,64 @@ static int yy_find_shift_action( int i; int stateno = pParser->yystack[pParser->yyidx].stateno; - if( stateno>YY_SHIFT_COUNT - || (i = yy_shift_ofst[stateno])==YY_SHIFT_USE_DFLT ){ - return yy_default[stateno]; - } - assert( iLookAhead!=YYNOCODE ); - i += iLookAhead; - if( i<0 || i>=YY_ACTTAB_COUNT || yy_lookahead[i]!=iLookAhead ){ - if( iLookAhead>0 ){ + if( stateno>=YY_MIN_REDUCE ) return stateno; + assert( stateno <= YY_SHIFT_COUNT ); + do{ + i = yy_shift_ofst[stateno]; + if( i==YY_SHIFT_USE_DFLT ) return yy_default[stateno]; + assert( iLookAhead!=YYNOCODE ); + i += iLookAhead; + if( i<0 || i>=YY_ACTTAB_COUNT || yy_lookahead[i]!=iLookAhead ){ + if( iLookAhead>0 ){ #ifdef YYFALLBACK - YYCODETYPE iFallback; /* Fallback token */ - if( iLookAhead %s\n", - yyTracePrompt, yyTokenName[iLookAhead], yyTokenName[iFallback]); - } -#endif - return yy_find_shift_action(pParser, iFallback); - } -#endif -#ifdef YYWILDCARD - { - int j = i - iLookAhead + YYWILDCARD; - if( -#if YY_SHIFT_MIN+YYWILDCARD<0 - j>=0 && -#endif -#if YY_SHIFT_MAX+YYWILDCARD>=YY_ACTTAB_COUNT - j %s\n", - yyTracePrompt, yyTokenName[iLookAhead], yyTokenName[YYWILDCARD]); + fprintf(yyTraceFILE, "%sFALLBACK %s => %s\n", + yyTracePrompt, yyTokenName[iLookAhead], yyTokenName[iFallback]); + } +#endif + assert( yyFallback[iFallback]==0 ); /* Fallback loop must terminate */ + iLookAhead = iFallback; + continue; + } +#endif +#ifdef YYWILDCARD + { + int j = i - iLookAhead + YYWILDCARD; + if( +#if YY_SHIFT_MIN+YYWILDCARD<0 + j>=0 && +#endif +#if YY_SHIFT_MAX+YYWILDCARD>=YY_ACTTAB_COUNT + j %s\n", + yyTracePrompt, yyTokenName[iLookAhead], + yyTokenName[YYWILDCARD]); + } +#endif /* NDEBUG */ + return yy_action[j]; } -#endif /* NDEBUG */ - return yy_action[j]; } - } #endif /* YYWILDCARD */ + } + return yy_default[stateno]; + }else{ + return yy_action[i]; } - return yy_default[stateno]; - }else{ - return yy_action[i]; - } + }while(1); } /* ** Find the appropriate action for a parser given the non-terminal ** look-ahead token iLookAhead. -** -** If the look-ahead token is YYNOCODE, then check to see if the action is -** independent of the look-ahead. If it is, return the action, otherwise -** return YY_NO_ACTION. */ static int yy_find_reduce_action( int stateno, /* Current state number */ @@ -118003,12 +128938,34 @@ static void yyStackOverflow(yyParser *yypParser, YYMINORTYPE *yypMinor){ while( yypParser->yyidx>=0 ) yy_pop_parser_stack(yypParser); /* Here code is inserted which will execute if the parser ** stack every overflows */ +/******** Begin %stack_overflow code ******************************************/ UNUSED_PARAMETER(yypMinor); /* Silence some compiler warnings */ sqlite3ErrorMsg(pParse, "parser stack overflow"); +/******** End %stack_overflow code ********************************************/ sqlite3ParserARG_STORE; /* Suppress warning about unused %extra_argument var */ } +/* +** Print tracing information for a SHIFT action +*/ +#ifndef NDEBUG +static void yyTraceShift(yyParser *yypParser, int yyNewState){ + if( yyTraceFILE ){ + if( yyNewStateyystack[yypParser->yyidx].major], + yyNewState); + }else{ + fprintf(yyTraceFILE,"%sShift '%s'\n", + yyTracePrompt,yyTokenName[yypParser->yystack[yypParser->yyidx].major]); + } + } +} +#else +# define yyTraceShift(X,Y) +#endif + /* ** Perform a shift action. */ @@ -118043,16 +129000,7 @@ static void yy_shift( yytos->stateno = (YYACTIONTYPE)yyNewState; yytos->major = (YYCODETYPE)yyMajor; yytos->minor = *yypMinor; -#ifndef NDEBUG - if( yyTraceFILE && yypParser->yyidx>0 ){ - int i; - fprintf(yyTraceFILE,"%sShift %d\n",yyTracePrompt,yyNewState); - fprintf(yyTraceFILE,"%sStack:",yyTracePrompt); - for(i=1; i<=yypParser->yyidx; i++) - fprintf(yyTraceFILE," %s",yyTokenName[yypParser->yystack[i].major]); - fprintf(yyTraceFILE,"\n"); - } -#endif + yyTraceShift(yypParser, yyNewState); } /* The following table contains information about every rule that @@ -118159,90 +129107,91 @@ static const struct { { 187, 5 }, { 187, 5 }, { 187, 10 }, - { 189, 0 }, - { 189, 1 }, + { 190, 0 }, + { 190, 1 }, { 176, 0 }, { 176, 3 }, - { 190, 0 }, - { 190, 2 }, - { 191, 1 }, - { 191, 1 }, - { 191, 1 }, + { 191, 0 }, + { 191, 2 }, + { 192, 1 }, + { 192, 1 }, + { 192, 1 }, { 149, 4 }, - { 193, 2 }, - { 193, 0 }, - { 149, 8 }, + { 194, 2 }, + { 194, 0 }, + { 149, 9 }, { 149, 4 }, { 149, 1 }, { 163, 2 }, - { 195, 1 }, - { 195, 3 }, - { 198, 1 }, - { 198, 2 }, - { 198, 1 }, - { 196, 9 }, { 196, 1 }, - { 207, 4 }, - { 207, 5 }, + { 196, 3 }, { 199, 1 }, + { 199, 2 }, { 199, 1 }, - { 199, 0 }, - { 210, 2 }, - { 210, 0 }, - { 200, 3 }, - { 200, 2 }, - { 200, 4 }, + { 197, 9 }, + { 197, 1 }, + { 208, 4 }, + { 208, 5 }, + { 200, 1 }, + { 200, 1 }, + { 200, 0 }, { 211, 2 }, - { 211, 1 }, { 211, 0 }, - { 201, 0 }, + { 201, 3 }, { 201, 2 }, - { 213, 2 }, - { 213, 0 }, - { 212, 7 }, - { 212, 7 }, - { 212, 7 }, + { 201, 4 }, + { 212, 2 }, + { 212, 1 }, + { 212, 0 }, + { 202, 0 }, + { 202, 2 }, + { 214, 2 }, + { 214, 0 }, + { 213, 7 }, + { 213, 9 }, + { 213, 7 }, + { 213, 7 }, { 159, 0 }, { 159, 2 }, - { 194, 2 }, - { 214, 1 }, - { 214, 2 }, - { 214, 3 }, - { 214, 4 }, - { 216, 2 }, - { 216, 0 }, - { 215, 0 }, - { 215, 3 }, + { 195, 2 }, + { 215, 1 }, { 215, 2 }, - { 217, 4 }, + { 215, 3 }, + { 215, 4 }, + { 217, 2 }, { 217, 0 }, - { 205, 0 }, - { 205, 3 }, - { 220, 4 }, - { 220, 2 }, + { 216, 0 }, + { 216, 3 }, + { 216, 2 }, + { 218, 4 }, + { 218, 0 }, + { 206, 0 }, + { 206, 3 }, + { 188, 4 }, + { 188, 2 }, { 177, 1 }, { 177, 1 }, { 177, 0 }, - { 203, 0 }, - { 203, 3 }, { 204, 0 }, - { 204, 2 }, - { 206, 0 }, - { 206, 2 }, - { 206, 4 }, - { 206, 4 }, + { 204, 3 }, + { 205, 0 }, + { 205, 2 }, + { 207, 0 }, + { 207, 2 }, + { 207, 4 }, + { 207, 4 }, { 149, 6 }, - { 202, 0 }, - { 202, 2 }, + { 203, 0 }, + { 203, 2 }, { 149, 8 }, - { 221, 5 }, - { 221, 3 }, + { 220, 5 }, + { 220, 3 }, { 149, 6 }, { 149, 7 }, - { 222, 2 }, - { 222, 1 }, - { 223, 0 }, - { 223, 3 }, + { 221, 2 }, + { 221, 1 }, + { 222, 0 }, + { 222, 3 }, { 219, 3 }, { 219, 1 }, { 175, 1 }, @@ -118268,8 +129217,8 @@ static const struct { { 175, 3 }, { 175, 3 }, { 175, 3 }, - { 224, 1 }, - { 224, 2 }, + { 223, 1 }, + { 223, 2 }, { 175, 3 }, { 175, 5 }, { 175, 2 }, @@ -118280,36 +129229,36 @@ static const struct { { 175, 2 }, { 175, 2 }, { 175, 2 }, + { 224, 1 }, + { 224, 2 }, + { 175, 5 }, { 225, 1 }, { 225, 2 }, { 175, 5 }, - { 226, 1 }, - { 226, 2 }, - { 175, 5 }, { 175, 3 }, { 175, 5 }, { 175, 4 }, { 175, 4 }, { 175, 5 }, - { 228, 5 }, - { 228, 4 }, - { 229, 2 }, - { 229, 0 }, - { 227, 1 }, - { 227, 0 }, + { 227, 5 }, + { 227, 4 }, + { 228, 2 }, + { 228, 0 }, + { 226, 1 }, + { 226, 0 }, + { 210, 1 }, + { 210, 0 }, + { 209, 3 }, { 209, 1 }, - { 209, 0 }, - { 208, 3 }, - { 208, 1 }, { 149, 12 }, - { 230, 1 }, - { 230, 0 }, + { 229, 1 }, + { 229, 0 }, { 179, 0 }, { 179, 3 }, - { 188, 5 }, - { 188, 3 }, - { 231, 0 }, - { 231, 2 }, + { 189, 5 }, + { 189, 3 }, + { 230, 0 }, + { 230, 2 }, { 149, 4 }, { 149, 1 }, { 149, 2 }, @@ -118318,77 +129267,77 @@ static const struct { { 149, 6 }, { 149, 5 }, { 149, 6 }, - { 232, 1 }, - { 232, 1 }, - { 232, 1 }, - { 232, 1 }, - { 232, 1 }, + { 231, 1 }, + { 231, 1 }, + { 231, 1 }, + { 231, 1 }, + { 231, 1 }, { 171, 2 }, { 171, 1 }, { 172, 2 }, { 149, 5 }, - { 233, 11 }, + { 232, 11 }, + { 234, 1 }, + { 234, 1 }, + { 234, 2 }, + { 234, 0 }, { 235, 1 }, { 235, 1 }, - { 235, 2 }, - { 235, 0 }, - { 236, 1 }, - { 236, 1 }, + { 235, 3 }, + { 236, 0 }, { 236, 3 }, { 237, 0 }, - { 237, 3 }, - { 238, 0 }, - { 238, 2 }, - { 234, 3 }, - { 234, 2 }, - { 240, 1 }, - { 240, 3 }, - { 241, 0 }, - { 241, 3 }, - { 241, 2 }, - { 239, 7 }, - { 239, 5 }, - { 239, 5 }, + { 237, 2 }, + { 233, 3 }, + { 233, 2 }, { 239, 1 }, + { 239, 3 }, + { 240, 0 }, + { 240, 3 }, + { 240, 2 }, + { 238, 7 }, + { 238, 5 }, + { 238, 5 }, + { 238, 1 }, { 175, 4 }, { 175, 6 }, - { 192, 1 }, - { 192, 1 }, - { 192, 1 }, + { 193, 1 }, + { 193, 1 }, + { 193, 1 }, { 149, 4 }, { 149, 6 }, { 149, 3 }, - { 243, 0 }, - { 243, 2 }, - { 242, 1 }, { 242, 0 }, + { 242, 2 }, + { 241, 1 }, + { 241, 0 }, { 149, 1 }, { 149, 3 }, { 149, 1 }, { 149, 3 }, { 149, 6 }, { 149, 6 }, + { 243, 1 }, + { 244, 0 }, { 244, 1 }, - { 245, 0 }, - { 245, 1 }, { 149, 1 }, { 149, 4 }, - { 246, 8 }, - { 247, 1 }, - { 247, 3 }, - { 248, 0 }, - { 248, 2 }, + { 245, 8 }, + { 246, 1 }, + { 246, 3 }, + { 247, 0 }, + { 247, 2 }, + { 248, 1 }, + { 248, 3 }, { 249, 1 }, - { 249, 3 }, - { 250, 1 }, - { 251, 0 }, - { 251, 4 }, - { 251, 2 }, - { 197, 0 }, - { 197, 2 }, - { 197, 3 }, - { 252, 6 }, - { 252, 8 }, + { 250, 0 }, + { 250, 4 }, + { 250, 2 }, + { 198, 0 }, + { 198, 2 }, + { 198, 3 }, + { 251, 6 }, + { 251, 8 }, }; static void yy_accept(yyParser*); /* Forward Declaration */ @@ -118411,29 +129360,13 @@ static void yy_reduce( #ifndef NDEBUG if( yyTraceFILE && yyruleno>=0 && yyruleno<(int)(sizeof(yyRuleName)/sizeof(yyRuleName[0])) ){ - fprintf(yyTraceFILE, "%sReduce [%s].\n", yyTracePrompt, - yyRuleName[yyruleno]); + yysize = yyRuleInfo[yyruleno].nrhs; + fprintf(yyTraceFILE, "%sReduce [%s], go to state %d.\n", yyTracePrompt, + yyRuleName[yyruleno], yymsp[-yysize].stateno); } #endif /* NDEBUG */ - - /* Silence complaints from purify about yygotominor being uninitialized - ** in some cases when it is copied into the stack after the following - ** switch. yygotominor is uninitialized when a rule reduces that does - ** not set the value of its left-hand side nonterminal. Leaving the - ** value of the nonterminal uninitialized is utterly harmless as long - ** as the value is never used. So really the only thing this code - ** accomplishes is to quieten purify. - ** - ** 2007-01-16: The wireshark project (www.wireshark.org) reports that - ** without this code, their parser segfaults. I'm not sure what there - ** parser is doing to make this happen. This is the second bug report - ** from wireshark this week. Clearly they are stressing Lemon in ways - ** that it has not been previously stressed... (SQLite ticket #2172) - */ - /*memset(&yygotominor, 0, sizeof(yygotominor));*/ yygotominor = yyzerominor; - switch( yyruleno ){ /* Beginning here are the reduction cases. A typical example ** follows: @@ -118443,6 +129376,7 @@ static void yy_reduce( ** #line ** break; */ +/********** Begin reduce actions **********************************************/ case 5: /* explain ::= */ { sqlite3BeginParse(pParse, 0); } break; @@ -118456,17 +129390,17 @@ static void yy_reduce( { sqlite3FinishCoding(pParse); } break; case 9: /* cmd ::= BEGIN transtype trans_opt */ -{sqlite3BeginTransaction(pParse, yymsp[-1].minor.yy328);} +{sqlite3BeginTransaction(pParse, yymsp[-1].minor.yy4);} break; case 13: /* transtype ::= */ -{yygotominor.yy328 = TK_DEFERRED;} +{yygotominor.yy4 = TK_DEFERRED;} break; case 14: /* transtype ::= DEFERRED */ case 15: /* transtype ::= IMMEDIATE */ yytestcase(yyruleno==15); case 16: /* transtype ::= EXCLUSIVE */ yytestcase(yyruleno==16); case 115: /* multiselect_op ::= UNION */ yytestcase(yyruleno==115); case 117: /* multiselect_op ::= EXCEPT|INTERSECT */ yytestcase(yyruleno==117); -{yygotominor.yy328 = yymsp[0].major;} +{yygotominor.yy4 = yymsp[0].major;} break; case 17: /* cmd ::= COMMIT trans_opt */ case 18: /* cmd ::= END trans_opt */ yytestcase(yyruleno==18); @@ -118492,7 +129426,7 @@ static void yy_reduce( break; case 26: /* create_table ::= createkw temp TABLE ifnotexists nm dbnm */ { - sqlite3StartTable(pParse,&yymsp[-1].minor.yy0,&yymsp[0].minor.yy0,yymsp[-4].minor.yy328,0,0,yymsp[-2].minor.yy328); + sqlite3StartTable(pParse,&yymsp[-1].minor.yy0,&yymsp[0].minor.yy0,yymsp[-4].minor.yy4,0,0,yymsp[-2].minor.yy4); } break; case 27: /* createkw ::= CREATE */ @@ -118503,45 +129437,46 @@ static void yy_reduce( break; case 28: /* ifnotexists ::= */ case 31: /* temp ::= */ yytestcase(yyruleno==31); + case 34: /* table_options ::= */ yytestcase(yyruleno==34); case 68: /* autoinc ::= */ yytestcase(yyruleno==68); case 81: /* defer_subclause ::= NOT DEFERRABLE init_deferred_pred_opt */ yytestcase(yyruleno==81); case 83: /* init_deferred_pred_opt ::= */ yytestcase(yyruleno==83); case 85: /* init_deferred_pred_opt ::= INITIALLY IMMEDIATE */ yytestcase(yyruleno==85); case 97: /* defer_subclause_opt ::= */ yytestcase(yyruleno==97); case 108: /* ifexists ::= */ yytestcase(yyruleno==108); - case 218: /* between_op ::= BETWEEN */ yytestcase(yyruleno==218); - case 221: /* in_op ::= IN */ yytestcase(yyruleno==221); -{yygotominor.yy328 = 0;} + case 124: /* distinct ::= */ yytestcase(yyruleno==124); + case 219: /* between_op ::= BETWEEN */ yytestcase(yyruleno==219); + case 222: /* in_op ::= IN */ yytestcase(yyruleno==222); + case 247: /* collate ::= */ yytestcase(yyruleno==247); +{yygotominor.yy4 = 0;} break; case 29: /* ifnotexists ::= IF NOT EXISTS */ case 30: /* temp ::= TEMP */ yytestcase(yyruleno==30); case 69: /* autoinc ::= AUTOINCR */ yytestcase(yyruleno==69); case 84: /* init_deferred_pred_opt ::= INITIALLY DEFERRED */ yytestcase(yyruleno==84); case 107: /* ifexists ::= IF EXISTS */ yytestcase(yyruleno==107); - case 219: /* between_op ::= NOT BETWEEN */ yytestcase(yyruleno==219); - case 222: /* in_op ::= NOT IN */ yytestcase(yyruleno==222); -{yygotominor.yy328 = 1;} + case 220: /* between_op ::= NOT BETWEEN */ yytestcase(yyruleno==220); + case 223: /* in_op ::= NOT IN */ yytestcase(yyruleno==223); + case 248: /* collate ::= COLLATE ID|STRING */ yytestcase(yyruleno==248); +{yygotominor.yy4 = 1;} break; case 32: /* create_table_args ::= LP columnlist conslist_opt RP table_options */ { - sqlite3EndTable(pParse,&yymsp[-2].minor.yy0,&yymsp[-1].minor.yy0,yymsp[0].minor.yy186,0); + sqlite3EndTable(pParse,&yymsp[-2].minor.yy0,&yymsp[-1].minor.yy0,yymsp[0].minor.yy4,0); } break; case 33: /* create_table_args ::= AS select */ { - sqlite3EndTable(pParse,0,0,0,yymsp[0].minor.yy3); - sqlite3SelectDelete(pParse->db, yymsp[0].minor.yy3); + sqlite3EndTable(pParse,0,0,0,yymsp[0].minor.yy387); + sqlite3SelectDelete(pParse->db, yymsp[0].minor.yy387); } break; - case 34: /* table_options ::= */ -{yygotominor.yy186 = 0;} - break; case 35: /* table_options ::= WITHOUT nm */ { if( yymsp[0].minor.yy0.n==5 && sqlite3_strnicmp(yymsp[0].minor.yy0.z,"rowid",5)==0 ){ - yygotominor.yy186 = TF_WithoutRowid; + yygotominor.yy4 = TF_WithoutRowid | TF_NoVisibleRowid; }else{ - yygotominor.yy186 = 0; + yygotominor.yy4 = 0; sqlite3ErrorMsg(pParse, "unknown table option: %.*s", yymsp[0].minor.yy0.n, yymsp[0].minor.yy0.z); } } @@ -118566,18 +129501,17 @@ static void yy_reduce( case 48: /* typename ::= ID|STRING */ yytestcase(yyruleno==48); case 130: /* as ::= AS nm */ yytestcase(yyruleno==130); case 131: /* as ::= ID|STRING */ yytestcase(yyruleno==131); - case 141: /* dbnm ::= DOT nm */ yytestcase(yyruleno==141); - case 150: /* indexed_opt ::= INDEXED BY nm */ yytestcase(yyruleno==150); - case 247: /* collate ::= COLLATE ID|STRING */ yytestcase(yyruleno==247); - case 256: /* nmnum ::= plus_num */ yytestcase(yyruleno==256); - case 257: /* nmnum ::= nm */ yytestcase(yyruleno==257); - case 258: /* nmnum ::= ON */ yytestcase(yyruleno==258); - case 259: /* nmnum ::= DELETE */ yytestcase(yyruleno==259); - case 260: /* nmnum ::= DEFAULT */ yytestcase(yyruleno==260); - case 261: /* plus_num ::= PLUS INTEGER|FLOAT */ yytestcase(yyruleno==261); - case 262: /* plus_num ::= INTEGER|FLOAT */ yytestcase(yyruleno==262); - case 263: /* minus_num ::= MINUS INTEGER|FLOAT */ yytestcase(yyruleno==263); - case 279: /* trnm ::= nm */ yytestcase(yyruleno==279); + case 142: /* dbnm ::= DOT nm */ yytestcase(yyruleno==142); + case 151: /* indexed_opt ::= INDEXED BY nm */ yytestcase(yyruleno==151); + case 257: /* nmnum ::= plus_num */ yytestcase(yyruleno==257); + case 258: /* nmnum ::= nm */ yytestcase(yyruleno==258); + case 259: /* nmnum ::= ON */ yytestcase(yyruleno==259); + case 260: /* nmnum ::= DELETE */ yytestcase(yyruleno==260); + case 261: /* nmnum ::= DEFAULT */ yytestcase(yyruleno==261); + case 262: /* plus_num ::= PLUS INTEGER|FLOAT */ yytestcase(yyruleno==262); + case 263: /* plus_num ::= INTEGER|FLOAT */ yytestcase(yyruleno==263); + case 264: /* minus_num ::= MINUS INTEGER|FLOAT */ yytestcase(yyruleno==264); + case 280: /* trnm ::= nm */ yytestcase(yyruleno==280); {yygotominor.yy0 = yymsp[0].minor.yy0;} break; case 44: /* type ::= typetoken */ @@ -118604,17 +129538,17 @@ static void yy_reduce( break; case 55: /* ccons ::= DEFAULT term */ case 57: /* ccons ::= DEFAULT PLUS term */ yytestcase(yyruleno==57); -{sqlite3AddDefaultValue(pParse,&yymsp[0].minor.yy346);} +{sqlite3AddDefaultValue(pParse,&yymsp[0].minor.yy118);} break; case 56: /* ccons ::= DEFAULT LP expr RP */ -{sqlite3AddDefaultValue(pParse,&yymsp[-1].minor.yy346);} +{sqlite3AddDefaultValue(pParse,&yymsp[-1].minor.yy118);} break; case 58: /* ccons ::= DEFAULT MINUS term */ { ExprSpan v; - v.pExpr = sqlite3PExpr(pParse, TK_UMINUS, yymsp[0].minor.yy346.pExpr, 0, 0); + v.pExpr = sqlite3PExpr(pParse, TK_UMINUS, yymsp[0].minor.yy118.pExpr, 0, 0); v.zStart = yymsp[-1].minor.yy0.z; - v.zEnd = yymsp[0].minor.yy346.zEnd; + v.zEnd = yymsp[0].minor.yy118.zEnd; sqlite3AddDefaultValue(pParse,&v); } break; @@ -118626,62 +129560,64 @@ static void yy_reduce( } break; case 61: /* ccons ::= NOT NULL onconf */ -{sqlite3AddNotNull(pParse, yymsp[0].minor.yy328);} +{sqlite3AddNotNull(pParse, yymsp[0].minor.yy4);} break; case 62: /* ccons ::= PRIMARY KEY sortorder onconf autoinc */ -{sqlite3AddPrimaryKey(pParse,0,yymsp[-1].minor.yy328,yymsp[0].minor.yy328,yymsp[-2].minor.yy328);} +{sqlite3AddPrimaryKey(pParse,0,yymsp[-1].minor.yy4,yymsp[0].minor.yy4,yymsp[-2].minor.yy4);} break; case 63: /* ccons ::= UNIQUE onconf */ -{sqlite3CreateIndex(pParse,0,0,0,0,yymsp[0].minor.yy328,0,0,0,0);} +{sqlite3CreateIndex(pParse,0,0,0,0,yymsp[0].minor.yy4,0,0,0,0);} break; case 64: /* ccons ::= CHECK LP expr RP */ -{sqlite3AddCheckConstraint(pParse,yymsp[-1].minor.yy346.pExpr);} +{sqlite3AddCheckConstraint(pParse,yymsp[-1].minor.yy118.pExpr);} break; - case 65: /* ccons ::= REFERENCES nm idxlist_opt refargs */ -{sqlite3CreateForeignKey(pParse,0,&yymsp[-2].minor.yy0,yymsp[-1].minor.yy14,yymsp[0].minor.yy328);} + case 65: /* ccons ::= REFERENCES nm eidlist_opt refargs */ +{sqlite3CreateForeignKey(pParse,0,&yymsp[-2].minor.yy0,yymsp[-1].minor.yy322,yymsp[0].minor.yy4);} break; case 66: /* ccons ::= defer_subclause */ -{sqlite3DeferForeignKey(pParse,yymsp[0].minor.yy328);} +{sqlite3DeferForeignKey(pParse,yymsp[0].minor.yy4);} break; case 67: /* ccons ::= COLLATE ID|STRING */ {sqlite3AddCollateType(pParse, &yymsp[0].minor.yy0);} break; case 70: /* refargs ::= */ -{ yygotominor.yy328 = OE_None*0x0101; /* EV: R-19803-45884 */} +{ yygotominor.yy4 = OE_None*0x0101; /* EV: R-19803-45884 */} break; case 71: /* refargs ::= refargs refarg */ -{ yygotominor.yy328 = (yymsp[-1].minor.yy328 & ~yymsp[0].minor.yy429.mask) | yymsp[0].minor.yy429.value; } +{ yygotominor.yy4 = (yymsp[-1].minor.yy4 & ~yymsp[0].minor.yy215.mask) | yymsp[0].minor.yy215.value; } break; case 72: /* refarg ::= MATCH nm */ case 73: /* refarg ::= ON INSERT refact */ yytestcase(yyruleno==73); -{ yygotominor.yy429.value = 0; yygotominor.yy429.mask = 0x000000; } +{ yygotominor.yy215.value = 0; yygotominor.yy215.mask = 0x000000; } break; case 74: /* refarg ::= ON DELETE refact */ -{ yygotominor.yy429.value = yymsp[0].minor.yy328; yygotominor.yy429.mask = 0x0000ff; } +{ yygotominor.yy215.value = yymsp[0].minor.yy4; yygotominor.yy215.mask = 0x0000ff; } break; case 75: /* refarg ::= ON UPDATE refact */ -{ yygotominor.yy429.value = yymsp[0].minor.yy328<<8; yygotominor.yy429.mask = 0x00ff00; } +{ yygotominor.yy215.value = yymsp[0].minor.yy4<<8; yygotominor.yy215.mask = 0x00ff00; } break; case 76: /* refact ::= SET NULL */ -{ yygotominor.yy328 = OE_SetNull; /* EV: R-33326-45252 */} +{ yygotominor.yy4 = OE_SetNull; /* EV: R-33326-45252 */} break; case 77: /* refact ::= SET DEFAULT */ -{ yygotominor.yy328 = OE_SetDflt; /* EV: R-33326-45252 */} +{ yygotominor.yy4 = OE_SetDflt; /* EV: R-33326-45252 */} break; case 78: /* refact ::= CASCADE */ -{ yygotominor.yy328 = OE_Cascade; /* EV: R-33326-45252 */} +{ yygotominor.yy4 = OE_Cascade; /* EV: R-33326-45252 */} break; case 79: /* refact ::= RESTRICT */ -{ yygotominor.yy328 = OE_Restrict; /* EV: R-33326-45252 */} +{ yygotominor.yy4 = OE_Restrict; /* EV: R-33326-45252 */} break; case 80: /* refact ::= NO ACTION */ -{ yygotominor.yy328 = OE_None; /* EV: R-33326-45252 */} +{ yygotominor.yy4 = OE_None; /* EV: R-33326-45252 */} break; case 82: /* defer_subclause ::= DEFERRABLE init_deferred_pred_opt */ case 98: /* defer_subclause_opt ::= defer_subclause */ yytestcase(yyruleno==98); case 100: /* onconf ::= ON CONFLICT resolvetype */ yytestcase(yyruleno==100); + case 102: /* orconf ::= OR resolvetype */ yytestcase(yyruleno==102); case 103: /* resolvetype ::= raisetype */ yytestcase(yyruleno==103); -{yygotominor.yy328 = yymsp[0].minor.yy328;} + case 178: /* insert_cmd ::= INSERT orconf */ yytestcase(yyruleno==178); +{yygotominor.yy4 = yymsp[0].minor.yy4;} break; case 86: /* conslist_opt ::= */ {yygotominor.yy0.n = 0; yygotominor.yy0.z = 0;} @@ -118692,393 +129628,407 @@ static void yy_reduce( case 90: /* tconscomma ::= COMMA */ {pParse->constraintName.n = 0;} break; - case 93: /* tcons ::= PRIMARY KEY LP idxlist autoinc RP onconf */ -{sqlite3AddPrimaryKey(pParse,yymsp[-3].minor.yy14,yymsp[0].minor.yy328,yymsp[-2].minor.yy328,0);} + case 93: /* tcons ::= PRIMARY KEY LP sortlist autoinc RP onconf */ +{sqlite3AddPrimaryKey(pParse,yymsp[-3].minor.yy322,yymsp[0].minor.yy4,yymsp[-2].minor.yy4,0);} break; - case 94: /* tcons ::= UNIQUE LP idxlist RP onconf */ -{sqlite3CreateIndex(pParse,0,0,0,yymsp[-2].minor.yy14,yymsp[0].minor.yy328,0,0,0,0);} + case 94: /* tcons ::= UNIQUE LP sortlist RP onconf */ +{sqlite3CreateIndex(pParse,0,0,0,yymsp[-2].minor.yy322,yymsp[0].minor.yy4,0,0,0,0);} break; case 95: /* tcons ::= CHECK LP expr RP onconf */ -{sqlite3AddCheckConstraint(pParse,yymsp[-2].minor.yy346.pExpr);} +{sqlite3AddCheckConstraint(pParse,yymsp[-2].minor.yy118.pExpr);} break; - case 96: /* tcons ::= FOREIGN KEY LP idxlist RP REFERENCES nm idxlist_opt refargs defer_subclause_opt */ + case 96: /* tcons ::= FOREIGN KEY LP eidlist RP REFERENCES nm eidlist_opt refargs defer_subclause_opt */ { - sqlite3CreateForeignKey(pParse, yymsp[-6].minor.yy14, &yymsp[-3].minor.yy0, yymsp[-2].minor.yy14, yymsp[-1].minor.yy328); - sqlite3DeferForeignKey(pParse, yymsp[0].minor.yy328); + sqlite3CreateForeignKey(pParse, yymsp[-6].minor.yy322, &yymsp[-3].minor.yy0, yymsp[-2].minor.yy322, yymsp[-1].minor.yy4); + sqlite3DeferForeignKey(pParse, yymsp[0].minor.yy4); } break; case 99: /* onconf ::= */ -{yygotominor.yy328 = OE_Default;} - break; - case 101: /* orconf ::= */ -{yygotominor.yy186 = OE_Default;} - break; - case 102: /* orconf ::= OR resolvetype */ -{yygotominor.yy186 = (u8)yymsp[0].minor.yy328;} + case 101: /* orconf ::= */ yytestcase(yyruleno==101); +{yygotominor.yy4 = OE_Default;} break; case 104: /* resolvetype ::= IGNORE */ -{yygotominor.yy328 = OE_Ignore;} +{yygotominor.yy4 = OE_Ignore;} break; case 105: /* resolvetype ::= REPLACE */ -{yygotominor.yy328 = OE_Replace;} + case 179: /* insert_cmd ::= REPLACE */ yytestcase(yyruleno==179); +{yygotominor.yy4 = OE_Replace;} break; case 106: /* cmd ::= DROP TABLE ifexists fullname */ { - sqlite3DropTable(pParse, yymsp[0].minor.yy65, 0, yymsp[-1].minor.yy328); + sqlite3DropTable(pParse, yymsp[0].minor.yy259, 0, yymsp[-1].minor.yy4); } break; - case 109: /* cmd ::= createkw temp VIEW ifnotexists nm dbnm AS select */ + case 109: /* cmd ::= createkw temp VIEW ifnotexists nm dbnm eidlist_opt AS select */ { - sqlite3CreateView(pParse, &yymsp[-7].minor.yy0, &yymsp[-3].minor.yy0, &yymsp[-2].minor.yy0, yymsp[0].minor.yy3, yymsp[-6].minor.yy328, yymsp[-4].minor.yy328); + sqlite3CreateView(pParse, &yymsp[-8].minor.yy0, &yymsp[-4].minor.yy0, &yymsp[-3].minor.yy0, yymsp[-2].minor.yy322, yymsp[0].minor.yy387, yymsp[-7].minor.yy4, yymsp[-5].minor.yy4); } break; case 110: /* cmd ::= DROP VIEW ifexists fullname */ { - sqlite3DropTable(pParse, yymsp[0].minor.yy65, 1, yymsp[-1].minor.yy328); + sqlite3DropTable(pParse, yymsp[0].minor.yy259, 1, yymsp[-1].minor.yy4); } break; case 111: /* cmd ::= select */ { SelectDest dest = {SRT_Output, 0, 0, 0, 0, 0}; - sqlite3Select(pParse, yymsp[0].minor.yy3, &dest); - sqlite3ExplainBegin(pParse->pVdbe); - sqlite3ExplainSelect(pParse->pVdbe, yymsp[0].minor.yy3); - sqlite3ExplainFinish(pParse->pVdbe); - sqlite3SelectDelete(pParse->db, yymsp[0].minor.yy3); + sqlite3Select(pParse, yymsp[0].minor.yy387, &dest); + sqlite3SelectDelete(pParse->db, yymsp[0].minor.yy387); } break; case 112: /* select ::= with selectnowith */ { - Select *p = yymsp[0].minor.yy3, *pNext, *pLoop; + Select *p = yymsp[0].minor.yy387; if( p ){ - int cnt = 0, mxSelect; - p->pWith = yymsp[-1].minor.yy59; - if( p->pPrior ){ - pNext = 0; - for(pLoop=p; pLoop; pNext=pLoop, pLoop=pLoop->pPrior, cnt++){ - pLoop->pNext = pNext; - pLoop->selFlags |= SF_Compound; - } - mxSelect = pParse->db->aLimit[SQLITE_LIMIT_COMPOUND_SELECT]; - if( mxSelect && cnt>mxSelect ){ - sqlite3ErrorMsg(pParse, "too many terms in compound SELECT"); - } - } + p->pWith = yymsp[-1].minor.yy451; + parserDoubleLinkSelect(pParse, p); }else{ - sqlite3WithDelete(pParse->db, yymsp[-1].minor.yy59); + sqlite3WithDelete(pParse->db, yymsp[-1].minor.yy451); } - yygotominor.yy3 = p; + yygotominor.yy387 = p; } break; case 113: /* selectnowith ::= oneselect */ case 119: /* oneselect ::= values */ yytestcase(yyruleno==119); -{yygotominor.yy3 = yymsp[0].minor.yy3;} +{yygotominor.yy387 = yymsp[0].minor.yy387;} break; case 114: /* selectnowith ::= selectnowith multiselect_op oneselect */ { - Select *pRhs = yymsp[0].minor.yy3; + Select *pRhs = yymsp[0].minor.yy387; + Select *pLhs = yymsp[-2].minor.yy387; if( pRhs && pRhs->pPrior ){ SrcList *pFrom; Token x; x.n = 0; + parserDoubleLinkSelect(pParse, pRhs); pFrom = sqlite3SrcListAppendFromTerm(pParse,0,0,0,&x,pRhs,0,0); pRhs = sqlite3SelectNew(pParse,0,pFrom,0,0,0,0,0,0,0); } if( pRhs ){ - pRhs->op = (u8)yymsp[-1].minor.yy328; - pRhs->pPrior = yymsp[-2].minor.yy3; - if( yymsp[-1].minor.yy328!=TK_ALL ) pParse->hasCompound = 1; + pRhs->op = (u8)yymsp[-1].minor.yy4; + pRhs->pPrior = pLhs; + if( ALWAYS(pLhs) ) pLhs->selFlags &= ~SF_MultiValue; + pRhs->selFlags &= ~SF_MultiValue; + if( yymsp[-1].minor.yy4!=TK_ALL ) pParse->hasCompound = 1; }else{ - sqlite3SelectDelete(pParse->db, yymsp[-2].minor.yy3); + sqlite3SelectDelete(pParse->db, pLhs); } - yygotominor.yy3 = pRhs; + yygotominor.yy387 = pRhs; } break; case 116: /* multiselect_op ::= UNION ALL */ -{yygotominor.yy328 = TK_ALL;} +{yygotominor.yy4 = TK_ALL;} break; case 118: /* oneselect ::= SELECT distinct selcollist from where_opt groupby_opt having_opt orderby_opt limit_opt */ { - yygotominor.yy3 = sqlite3SelectNew(pParse,yymsp[-6].minor.yy14,yymsp[-5].minor.yy65,yymsp[-4].minor.yy132,yymsp[-3].minor.yy14,yymsp[-2].minor.yy132,yymsp[-1].minor.yy14,yymsp[-7].minor.yy381,yymsp[0].minor.yy476.pLimit,yymsp[0].minor.yy476.pOffset); + yygotominor.yy387 = sqlite3SelectNew(pParse,yymsp[-6].minor.yy322,yymsp[-5].minor.yy259,yymsp[-4].minor.yy314,yymsp[-3].minor.yy322,yymsp[-2].minor.yy314,yymsp[-1].minor.yy322,yymsp[-7].minor.yy4,yymsp[0].minor.yy292.pLimit,yymsp[0].minor.yy292.pOffset); +#if SELECTTRACE_ENABLED + /* Populate the Select.zSelName[] string that is used to help with + ** query planner debugging, to differentiate between multiple Select + ** objects in a complex query. + ** + ** If the SELECT keyword is immediately followed by a C-style comment + ** then extract the first few alphanumeric characters from within that + ** comment to be the zSelName value. Otherwise, the label is #N where + ** is an integer that is incremented with each SELECT statement seen. + */ + if( yygotominor.yy387!=0 ){ + const char *z = yymsp[-8].minor.yy0.z+6; + int i; + sqlite3_snprintf(sizeof(yygotominor.yy387->zSelName), yygotominor.yy387->zSelName, "#%d", + ++pParse->nSelect); + while( z[0]==' ' ) z++; + if( z[0]=='/' && z[1]=='*' ){ + z += 2; + while( z[0]==' ' ) z++; + for(i=0; sqlite3Isalnum(z[i]); i++){} + sqlite3_snprintf(sizeof(yygotominor.yy387->zSelName), yygotominor.yy387->zSelName, "%.*s", i, z); + } + } +#endif /* SELECTRACE_ENABLED */ } break; case 120: /* values ::= VALUES LP nexprlist RP */ { - yygotominor.yy3 = sqlite3SelectNew(pParse,yymsp[-1].minor.yy14,0,0,0,0,0,SF_Values,0,0); + yygotominor.yy387 = sqlite3SelectNew(pParse,yymsp[-1].minor.yy322,0,0,0,0,0,SF_Values,0,0); } break; case 121: /* values ::= values COMMA LP exprlist RP */ { - Select *pRight = sqlite3SelectNew(pParse,yymsp[-1].minor.yy14,0,0,0,0,0,SF_Values,0,0); + Select *pRight, *pLeft = yymsp[-4].minor.yy387; + pRight = sqlite3SelectNew(pParse,yymsp[-1].minor.yy322,0,0,0,0,0,SF_Values|SF_MultiValue,0,0); + if( ALWAYS(pLeft) ) pLeft->selFlags &= ~SF_MultiValue; if( pRight ){ pRight->op = TK_ALL; - pRight->pPrior = yymsp[-4].minor.yy3; - yygotominor.yy3 = pRight; + pLeft = yymsp[-4].minor.yy387; + pRight->pPrior = pLeft; + yygotominor.yy387 = pRight; }else{ - yygotominor.yy3 = yymsp[-4].minor.yy3; + yygotominor.yy387 = pLeft; } } break; case 122: /* distinct ::= DISTINCT */ -{yygotominor.yy381 = SF_Distinct;} +{yygotominor.yy4 = SF_Distinct;} break; case 123: /* distinct ::= ALL */ - case 124: /* distinct ::= */ yytestcase(yyruleno==124); -{yygotominor.yy381 = 0;} +{yygotominor.yy4 = SF_All;} break; case 125: /* sclp ::= selcollist COMMA */ - case 243: /* idxlist_opt ::= LP idxlist RP */ yytestcase(yyruleno==243); -{yygotominor.yy14 = yymsp[-1].minor.yy14;} + case 244: /* eidlist_opt ::= LP eidlist RP */ yytestcase(yyruleno==244); +{yygotominor.yy322 = yymsp[-1].minor.yy322;} break; case 126: /* sclp ::= */ - case 154: /* orderby_opt ::= */ yytestcase(yyruleno==154); - case 161: /* groupby_opt ::= */ yytestcase(yyruleno==161); - case 236: /* exprlist ::= */ yytestcase(yyruleno==236); - case 242: /* idxlist_opt ::= */ yytestcase(yyruleno==242); -{yygotominor.yy14 = 0;} + case 155: /* orderby_opt ::= */ yytestcase(yyruleno==155); + case 162: /* groupby_opt ::= */ yytestcase(yyruleno==162); + case 237: /* exprlist ::= */ yytestcase(yyruleno==237); + case 243: /* eidlist_opt ::= */ yytestcase(yyruleno==243); +{yygotominor.yy322 = 0;} break; case 127: /* selcollist ::= sclp expr as */ { - yygotominor.yy14 = sqlite3ExprListAppend(pParse, yymsp[-2].minor.yy14, yymsp[-1].minor.yy346.pExpr); - if( yymsp[0].minor.yy0.n>0 ) sqlite3ExprListSetName(pParse, yygotominor.yy14, &yymsp[0].minor.yy0, 1); - sqlite3ExprListSetSpan(pParse,yygotominor.yy14,&yymsp[-1].minor.yy346); + yygotominor.yy322 = sqlite3ExprListAppend(pParse, yymsp[-2].minor.yy322, yymsp[-1].minor.yy118.pExpr); + if( yymsp[0].minor.yy0.n>0 ) sqlite3ExprListSetName(pParse, yygotominor.yy322, &yymsp[0].minor.yy0, 1); + sqlite3ExprListSetSpan(pParse,yygotominor.yy322,&yymsp[-1].minor.yy118); } break; case 128: /* selcollist ::= sclp STAR */ { - Expr *p = sqlite3Expr(pParse->db, TK_ALL, 0); - yygotominor.yy14 = sqlite3ExprListAppend(pParse, yymsp[-1].minor.yy14, p); + Expr *p = sqlite3Expr(pParse->db, TK_ASTERISK, 0); + yygotominor.yy322 = sqlite3ExprListAppend(pParse, yymsp[-1].minor.yy322, p); } break; case 129: /* selcollist ::= sclp nm DOT STAR */ { - Expr *pRight = sqlite3PExpr(pParse, TK_ALL, 0, 0, &yymsp[0].minor.yy0); + Expr *pRight = sqlite3PExpr(pParse, TK_ASTERISK, 0, 0, &yymsp[0].minor.yy0); Expr *pLeft = sqlite3PExpr(pParse, TK_ID, 0, 0, &yymsp[-2].minor.yy0); Expr *pDot = sqlite3PExpr(pParse, TK_DOT, pLeft, pRight, 0); - yygotominor.yy14 = sqlite3ExprListAppend(pParse,yymsp[-3].minor.yy14, pDot); + yygotominor.yy322 = sqlite3ExprListAppend(pParse,yymsp[-3].minor.yy322, pDot); } break; case 132: /* as ::= */ {yygotominor.yy0.n = 0;} break; case 133: /* from ::= */ -{yygotominor.yy65 = sqlite3DbMallocZero(pParse->db, sizeof(*yygotominor.yy65));} +{yygotominor.yy259 = sqlite3DbMallocZero(pParse->db, sizeof(*yygotominor.yy259));} break; case 134: /* from ::= FROM seltablist */ { - yygotominor.yy65 = yymsp[0].minor.yy65; - sqlite3SrcListShiftJoinType(yygotominor.yy65); + yygotominor.yy259 = yymsp[0].minor.yy259; + sqlite3SrcListShiftJoinType(yygotominor.yy259); } break; case 135: /* stl_prefix ::= seltablist joinop */ { - yygotominor.yy65 = yymsp[-1].minor.yy65; - if( ALWAYS(yygotominor.yy65 && yygotominor.yy65->nSrc>0) ) yygotominor.yy65->a[yygotominor.yy65->nSrc-1].jointype = (u8)yymsp[0].minor.yy328; + yygotominor.yy259 = yymsp[-1].minor.yy259; + if( ALWAYS(yygotominor.yy259 && yygotominor.yy259->nSrc>0) ) yygotominor.yy259->a[yygotominor.yy259->nSrc-1].fg.jointype = (u8)yymsp[0].minor.yy4; } break; case 136: /* stl_prefix ::= */ -{yygotominor.yy65 = 0;} +{yygotominor.yy259 = 0;} break; case 137: /* seltablist ::= stl_prefix nm dbnm as indexed_opt on_opt using_opt */ { - yygotominor.yy65 = sqlite3SrcListAppendFromTerm(pParse,yymsp[-6].minor.yy65,&yymsp[-5].minor.yy0,&yymsp[-4].minor.yy0,&yymsp[-3].minor.yy0,0,yymsp[-1].minor.yy132,yymsp[0].minor.yy408); - sqlite3SrcListIndexedBy(pParse, yygotominor.yy65, &yymsp[-2].minor.yy0); + yygotominor.yy259 = sqlite3SrcListAppendFromTerm(pParse,yymsp[-6].minor.yy259,&yymsp[-5].minor.yy0,&yymsp[-4].minor.yy0,&yymsp[-3].minor.yy0,0,yymsp[-1].minor.yy314,yymsp[0].minor.yy384); + sqlite3SrcListIndexedBy(pParse, yygotominor.yy259, &yymsp[-2].minor.yy0); } break; - case 138: /* seltablist ::= stl_prefix LP select RP as on_opt using_opt */ + case 138: /* seltablist ::= stl_prefix nm dbnm LP exprlist RP as on_opt using_opt */ { - yygotominor.yy65 = sqlite3SrcListAppendFromTerm(pParse,yymsp[-6].minor.yy65,0,0,&yymsp[-2].minor.yy0,yymsp[-4].minor.yy3,yymsp[-1].minor.yy132,yymsp[0].minor.yy408); + yygotominor.yy259 = sqlite3SrcListAppendFromTerm(pParse,yymsp[-8].minor.yy259,&yymsp[-7].minor.yy0,&yymsp[-6].minor.yy0,&yymsp[-2].minor.yy0,0,yymsp[-1].minor.yy314,yymsp[0].minor.yy384); + sqlite3SrcListFuncArgs(pParse, yygotominor.yy259, yymsp[-4].minor.yy322); +} + break; + case 139: /* seltablist ::= stl_prefix LP select RP as on_opt using_opt */ +{ + yygotominor.yy259 = sqlite3SrcListAppendFromTerm(pParse,yymsp[-6].minor.yy259,0,0,&yymsp[-2].minor.yy0,yymsp[-4].minor.yy387,yymsp[-1].minor.yy314,yymsp[0].minor.yy384); } break; - case 139: /* seltablist ::= stl_prefix LP seltablist RP as on_opt using_opt */ + case 140: /* seltablist ::= stl_prefix LP seltablist RP as on_opt using_opt */ { - if( yymsp[-6].minor.yy65==0 && yymsp[-2].minor.yy0.n==0 && yymsp[-1].minor.yy132==0 && yymsp[0].minor.yy408==0 ){ - yygotominor.yy65 = yymsp[-4].minor.yy65; - }else if( yymsp[-4].minor.yy65->nSrc==1 ){ - yygotominor.yy65 = sqlite3SrcListAppendFromTerm(pParse,yymsp[-6].minor.yy65,0,0,&yymsp[-2].minor.yy0,0,yymsp[-1].minor.yy132,yymsp[0].minor.yy408); - if( yygotominor.yy65 ){ - struct SrcList_item *pNew = &yygotominor.yy65->a[yygotominor.yy65->nSrc-1]; - struct SrcList_item *pOld = yymsp[-4].minor.yy65->a; + if( yymsp[-6].minor.yy259==0 && yymsp[-2].minor.yy0.n==0 && yymsp[-1].minor.yy314==0 && yymsp[0].minor.yy384==0 ){ + yygotominor.yy259 = yymsp[-4].minor.yy259; + }else if( yymsp[-4].minor.yy259->nSrc==1 ){ + yygotominor.yy259 = sqlite3SrcListAppendFromTerm(pParse,yymsp[-6].minor.yy259,0,0,&yymsp[-2].minor.yy0,0,yymsp[-1].minor.yy314,yymsp[0].minor.yy384); + if( yygotominor.yy259 ){ + struct SrcList_item *pNew = &yygotominor.yy259->a[yygotominor.yy259->nSrc-1]; + struct SrcList_item *pOld = yymsp[-4].minor.yy259->a; pNew->zName = pOld->zName; pNew->zDatabase = pOld->zDatabase; pNew->pSelect = pOld->pSelect; pOld->zName = pOld->zDatabase = 0; pOld->pSelect = 0; } - sqlite3SrcListDelete(pParse->db, yymsp[-4].minor.yy65); + sqlite3SrcListDelete(pParse->db, yymsp[-4].minor.yy259); }else{ Select *pSubquery; - sqlite3SrcListShiftJoinType(yymsp[-4].minor.yy65); - pSubquery = sqlite3SelectNew(pParse,0,yymsp[-4].minor.yy65,0,0,0,0,SF_NestedFrom,0,0); - yygotominor.yy65 = sqlite3SrcListAppendFromTerm(pParse,yymsp[-6].minor.yy65,0,0,&yymsp[-2].minor.yy0,pSubquery,yymsp[-1].minor.yy132,yymsp[0].minor.yy408); + sqlite3SrcListShiftJoinType(yymsp[-4].minor.yy259); + pSubquery = sqlite3SelectNew(pParse,0,yymsp[-4].minor.yy259,0,0,0,0,SF_NestedFrom,0,0); + yygotominor.yy259 = sqlite3SrcListAppendFromTerm(pParse,yymsp[-6].minor.yy259,0,0,&yymsp[-2].minor.yy0,pSubquery,yymsp[-1].minor.yy314,yymsp[0].minor.yy384); } } break; - case 140: /* dbnm ::= */ - case 149: /* indexed_opt ::= */ yytestcase(yyruleno==149); + case 141: /* dbnm ::= */ + case 150: /* indexed_opt ::= */ yytestcase(yyruleno==150); {yygotominor.yy0.z=0; yygotominor.yy0.n=0;} break; - case 142: /* fullname ::= nm dbnm */ -{yygotominor.yy65 = sqlite3SrcListAppend(pParse->db,0,&yymsp[-1].minor.yy0,&yymsp[0].minor.yy0);} + case 143: /* fullname ::= nm dbnm */ +{yygotominor.yy259 = sqlite3SrcListAppend(pParse->db,0,&yymsp[-1].minor.yy0,&yymsp[0].minor.yy0);} break; - case 143: /* joinop ::= COMMA|JOIN */ -{ yygotominor.yy328 = JT_INNER; } + case 144: /* joinop ::= COMMA|JOIN */ +{ yygotominor.yy4 = JT_INNER; } break; - case 144: /* joinop ::= JOIN_KW JOIN */ -{ yygotominor.yy328 = sqlite3JoinType(pParse,&yymsp[-1].minor.yy0,0,0); } + case 145: /* joinop ::= JOIN_KW JOIN */ +{ yygotominor.yy4 = sqlite3JoinType(pParse,&yymsp[-1].minor.yy0,0,0); } break; - case 145: /* joinop ::= JOIN_KW nm JOIN */ -{ yygotominor.yy328 = sqlite3JoinType(pParse,&yymsp[-2].minor.yy0,&yymsp[-1].minor.yy0,0); } + case 146: /* joinop ::= JOIN_KW nm JOIN */ +{ yygotominor.yy4 = sqlite3JoinType(pParse,&yymsp[-2].minor.yy0,&yymsp[-1].minor.yy0,0); } break; - case 146: /* joinop ::= JOIN_KW nm nm JOIN */ -{ yygotominor.yy328 = sqlite3JoinType(pParse,&yymsp[-3].minor.yy0,&yymsp[-2].minor.yy0,&yymsp[-1].minor.yy0); } + case 147: /* joinop ::= JOIN_KW nm nm JOIN */ +{ yygotominor.yy4 = sqlite3JoinType(pParse,&yymsp[-3].minor.yy0,&yymsp[-2].minor.yy0,&yymsp[-1].minor.yy0); } break; - case 147: /* on_opt ::= ON expr */ - case 164: /* having_opt ::= HAVING expr */ yytestcase(yyruleno==164); - case 171: /* where_opt ::= WHERE expr */ yytestcase(yyruleno==171); - case 231: /* case_else ::= ELSE expr */ yytestcase(yyruleno==231); - case 233: /* case_operand ::= expr */ yytestcase(yyruleno==233); -{yygotominor.yy132 = yymsp[0].minor.yy346.pExpr;} + case 148: /* on_opt ::= ON expr */ + case 165: /* having_opt ::= HAVING expr */ yytestcase(yyruleno==165); + case 172: /* where_opt ::= WHERE expr */ yytestcase(yyruleno==172); + case 232: /* case_else ::= ELSE expr */ yytestcase(yyruleno==232); + case 234: /* case_operand ::= expr */ yytestcase(yyruleno==234); +{yygotominor.yy314 = yymsp[0].minor.yy118.pExpr;} break; - case 148: /* on_opt ::= */ - case 163: /* having_opt ::= */ yytestcase(yyruleno==163); - case 170: /* where_opt ::= */ yytestcase(yyruleno==170); - case 232: /* case_else ::= */ yytestcase(yyruleno==232); - case 234: /* case_operand ::= */ yytestcase(yyruleno==234); -{yygotominor.yy132 = 0;} + case 149: /* on_opt ::= */ + case 164: /* having_opt ::= */ yytestcase(yyruleno==164); + case 171: /* where_opt ::= */ yytestcase(yyruleno==171); + case 233: /* case_else ::= */ yytestcase(yyruleno==233); + case 235: /* case_operand ::= */ yytestcase(yyruleno==235); +{yygotominor.yy314 = 0;} break; - case 151: /* indexed_opt ::= NOT INDEXED */ + case 152: /* indexed_opt ::= NOT INDEXED */ {yygotominor.yy0.z=0; yygotominor.yy0.n=1;} break; - case 152: /* using_opt ::= USING LP idlist RP */ - case 180: /* inscollist_opt ::= LP idlist RP */ yytestcase(yyruleno==180); -{yygotominor.yy408 = yymsp[-1].minor.yy408;} + case 153: /* using_opt ::= USING LP idlist RP */ + case 181: /* idlist_opt ::= LP idlist RP */ yytestcase(yyruleno==181); +{yygotominor.yy384 = yymsp[-1].minor.yy384;} break; - case 153: /* using_opt ::= */ - case 179: /* inscollist_opt ::= */ yytestcase(yyruleno==179); -{yygotominor.yy408 = 0;} + case 154: /* using_opt ::= */ + case 180: /* idlist_opt ::= */ yytestcase(yyruleno==180); +{yygotominor.yy384 = 0;} break; - case 155: /* orderby_opt ::= ORDER BY sortlist */ - case 162: /* groupby_opt ::= GROUP BY nexprlist */ yytestcase(yyruleno==162); - case 235: /* exprlist ::= nexprlist */ yytestcase(yyruleno==235); -{yygotominor.yy14 = yymsp[0].minor.yy14;} + case 156: /* orderby_opt ::= ORDER BY sortlist */ + case 163: /* groupby_opt ::= GROUP BY nexprlist */ yytestcase(yyruleno==163); + case 236: /* exprlist ::= nexprlist */ yytestcase(yyruleno==236); +{yygotominor.yy322 = yymsp[0].minor.yy322;} break; - case 156: /* sortlist ::= sortlist COMMA expr sortorder */ + case 157: /* sortlist ::= sortlist COMMA expr sortorder */ { - yygotominor.yy14 = sqlite3ExprListAppend(pParse,yymsp[-3].minor.yy14,yymsp[-1].minor.yy346.pExpr); - if( yygotominor.yy14 ) yygotominor.yy14->a[yygotominor.yy14->nExpr-1].sortOrder = (u8)yymsp[0].minor.yy328; + yygotominor.yy322 = sqlite3ExprListAppend(pParse,yymsp[-3].minor.yy322,yymsp[-1].minor.yy118.pExpr); + sqlite3ExprListSetSortOrder(yygotominor.yy322,yymsp[0].minor.yy4); } break; - case 157: /* sortlist ::= expr sortorder */ + case 158: /* sortlist ::= expr sortorder */ { - yygotominor.yy14 = sqlite3ExprListAppend(pParse,0,yymsp[-1].minor.yy346.pExpr); - if( yygotominor.yy14 && ALWAYS(yygotominor.yy14->a) ) yygotominor.yy14->a[0].sortOrder = (u8)yymsp[0].minor.yy328; + yygotominor.yy322 = sqlite3ExprListAppend(pParse,0,yymsp[-1].minor.yy118.pExpr); + sqlite3ExprListSetSortOrder(yygotominor.yy322,yymsp[0].minor.yy4); } break; - case 158: /* sortorder ::= ASC */ - case 160: /* sortorder ::= */ yytestcase(yyruleno==160); -{yygotominor.yy328 = SQLITE_SO_ASC;} + case 159: /* sortorder ::= ASC */ +{yygotominor.yy4 = SQLITE_SO_ASC;} break; - case 159: /* sortorder ::= DESC */ -{yygotominor.yy328 = SQLITE_SO_DESC;} + case 160: /* sortorder ::= DESC */ +{yygotominor.yy4 = SQLITE_SO_DESC;} break; - case 165: /* limit_opt ::= */ -{yygotominor.yy476.pLimit = 0; yygotominor.yy476.pOffset = 0;} + case 161: /* sortorder ::= */ +{yygotominor.yy4 = SQLITE_SO_UNDEFINED;} break; - case 166: /* limit_opt ::= LIMIT expr */ -{yygotominor.yy476.pLimit = yymsp[0].minor.yy346.pExpr; yygotominor.yy476.pOffset = 0;} + case 166: /* limit_opt ::= */ +{yygotominor.yy292.pLimit = 0; yygotominor.yy292.pOffset = 0;} break; - case 167: /* limit_opt ::= LIMIT expr OFFSET expr */ -{yygotominor.yy476.pLimit = yymsp[-2].minor.yy346.pExpr; yygotominor.yy476.pOffset = yymsp[0].minor.yy346.pExpr;} + case 167: /* limit_opt ::= LIMIT expr */ +{yygotominor.yy292.pLimit = yymsp[0].minor.yy118.pExpr; yygotominor.yy292.pOffset = 0;} break; - case 168: /* limit_opt ::= LIMIT expr COMMA expr */ -{yygotominor.yy476.pOffset = yymsp[-2].minor.yy346.pExpr; yygotominor.yy476.pLimit = yymsp[0].minor.yy346.pExpr;} + case 168: /* limit_opt ::= LIMIT expr OFFSET expr */ +{yygotominor.yy292.pLimit = yymsp[-2].minor.yy118.pExpr; yygotominor.yy292.pOffset = yymsp[0].minor.yy118.pExpr;} break; - case 169: /* cmd ::= with DELETE FROM fullname indexed_opt where_opt */ + case 169: /* limit_opt ::= LIMIT expr COMMA expr */ +{yygotominor.yy292.pOffset = yymsp[-2].minor.yy118.pExpr; yygotominor.yy292.pLimit = yymsp[0].minor.yy118.pExpr;} + break; + case 170: /* cmd ::= with DELETE FROM fullname indexed_opt where_opt */ { - sqlite3WithPush(pParse, yymsp[-5].minor.yy59, 1); - sqlite3SrcListIndexedBy(pParse, yymsp[-2].minor.yy65, &yymsp[-1].minor.yy0); - sqlite3DeleteFrom(pParse,yymsp[-2].minor.yy65,yymsp[0].minor.yy132); + sqlite3WithPush(pParse, yymsp[-5].minor.yy451, 1); + sqlite3SrcListIndexedBy(pParse, yymsp[-2].minor.yy259, &yymsp[-1].minor.yy0); + sqlite3DeleteFrom(pParse,yymsp[-2].minor.yy259,yymsp[0].minor.yy314); } break; - case 172: /* cmd ::= with UPDATE orconf fullname indexed_opt SET setlist where_opt */ + case 173: /* cmd ::= with UPDATE orconf fullname indexed_opt SET setlist where_opt */ { - sqlite3WithPush(pParse, yymsp[-7].minor.yy59, 1); - sqlite3SrcListIndexedBy(pParse, yymsp[-4].minor.yy65, &yymsp[-3].minor.yy0); - sqlite3ExprListCheckLength(pParse,yymsp[-1].minor.yy14,"set list"); - sqlite3Update(pParse,yymsp[-4].minor.yy65,yymsp[-1].minor.yy14,yymsp[0].minor.yy132,yymsp[-5].minor.yy186); + sqlite3WithPush(pParse, yymsp[-7].minor.yy451, 1); + sqlite3SrcListIndexedBy(pParse, yymsp[-4].minor.yy259, &yymsp[-3].minor.yy0); + sqlite3ExprListCheckLength(pParse,yymsp[-1].minor.yy322,"set list"); + sqlite3Update(pParse,yymsp[-4].minor.yy259,yymsp[-1].minor.yy322,yymsp[0].minor.yy314,yymsp[-5].minor.yy4); } break; - case 173: /* setlist ::= setlist COMMA nm EQ expr */ + case 174: /* setlist ::= setlist COMMA nm EQ expr */ { - yygotominor.yy14 = sqlite3ExprListAppend(pParse, yymsp[-4].minor.yy14, yymsp[0].minor.yy346.pExpr); - sqlite3ExprListSetName(pParse, yygotominor.yy14, &yymsp[-2].minor.yy0, 1); + yygotominor.yy322 = sqlite3ExprListAppend(pParse, yymsp[-4].minor.yy322, yymsp[0].minor.yy118.pExpr); + sqlite3ExprListSetName(pParse, yygotominor.yy322, &yymsp[-2].minor.yy0, 1); } break; - case 174: /* setlist ::= nm EQ expr */ + case 175: /* setlist ::= nm EQ expr */ { - yygotominor.yy14 = sqlite3ExprListAppend(pParse, 0, yymsp[0].minor.yy346.pExpr); - sqlite3ExprListSetName(pParse, yygotominor.yy14, &yymsp[-2].minor.yy0, 1); + yygotominor.yy322 = sqlite3ExprListAppend(pParse, 0, yymsp[0].minor.yy118.pExpr); + sqlite3ExprListSetName(pParse, yygotominor.yy322, &yymsp[-2].minor.yy0, 1); } break; - case 175: /* cmd ::= with insert_cmd INTO fullname inscollist_opt select */ + case 176: /* cmd ::= with insert_cmd INTO fullname idlist_opt select */ { - sqlite3WithPush(pParse, yymsp[-5].minor.yy59, 1); - sqlite3Insert(pParse, yymsp[-2].minor.yy65, yymsp[0].minor.yy3, yymsp[-1].minor.yy408, yymsp[-4].minor.yy186); + sqlite3WithPush(pParse, yymsp[-5].minor.yy451, 1); + sqlite3Insert(pParse, yymsp[-2].minor.yy259, yymsp[0].minor.yy387, yymsp[-1].minor.yy384, yymsp[-4].minor.yy4); } break; - case 176: /* cmd ::= with insert_cmd INTO fullname inscollist_opt DEFAULT VALUES */ + case 177: /* cmd ::= with insert_cmd INTO fullname idlist_opt DEFAULT VALUES */ { - sqlite3WithPush(pParse, yymsp[-6].minor.yy59, 1); - sqlite3Insert(pParse, yymsp[-3].minor.yy65, 0, yymsp[-2].minor.yy408, yymsp[-5].minor.yy186); + sqlite3WithPush(pParse, yymsp[-6].minor.yy451, 1); + sqlite3Insert(pParse, yymsp[-3].minor.yy259, 0, yymsp[-2].minor.yy384, yymsp[-5].minor.yy4); } break; - case 177: /* insert_cmd ::= INSERT orconf */ -{yygotominor.yy186 = yymsp[0].minor.yy186;} + case 182: /* idlist ::= idlist COMMA nm */ +{yygotominor.yy384 = sqlite3IdListAppend(pParse->db,yymsp[-2].minor.yy384,&yymsp[0].minor.yy0);} break; - case 178: /* insert_cmd ::= REPLACE */ -{yygotominor.yy186 = OE_Replace;} + case 183: /* idlist ::= nm */ +{yygotominor.yy384 = sqlite3IdListAppend(pParse->db,0,&yymsp[0].minor.yy0);} break; - case 181: /* idlist ::= idlist COMMA nm */ -{yygotominor.yy408 = sqlite3IdListAppend(pParse->db,yymsp[-2].minor.yy408,&yymsp[0].minor.yy0);} + case 184: /* expr ::= term */ +{yygotominor.yy118 = yymsp[0].minor.yy118;} break; - case 182: /* idlist ::= nm */ -{yygotominor.yy408 = sqlite3IdListAppend(pParse->db,0,&yymsp[0].minor.yy0);} + case 185: /* expr ::= LP expr RP */ +{yygotominor.yy118.pExpr = yymsp[-1].minor.yy118.pExpr; spanSet(&yygotominor.yy118,&yymsp[-2].minor.yy0,&yymsp[0].minor.yy0);} break; - case 183: /* expr ::= term */ -{yygotominor.yy346 = yymsp[0].minor.yy346;} + case 186: /* term ::= NULL */ + case 191: /* term ::= INTEGER|FLOAT|BLOB */ yytestcase(yyruleno==191); + case 192: /* term ::= STRING */ yytestcase(yyruleno==192); +{spanExpr(&yygotominor.yy118, pParse, yymsp[0].major, &yymsp[0].minor.yy0);} break; - case 184: /* expr ::= LP expr RP */ -{yygotominor.yy346.pExpr = yymsp[-1].minor.yy346.pExpr; spanSet(&yygotominor.yy346,&yymsp[-2].minor.yy0,&yymsp[0].minor.yy0);} + case 187: /* expr ::= ID|INDEXED */ + case 188: /* expr ::= JOIN_KW */ yytestcase(yyruleno==188); +{spanExpr(&yygotominor.yy118, pParse, TK_ID, &yymsp[0].minor.yy0);} break; - case 185: /* term ::= NULL */ - case 190: /* term ::= INTEGER|FLOAT|BLOB */ yytestcase(yyruleno==190); - case 191: /* term ::= STRING */ yytestcase(yyruleno==191); -{spanExpr(&yygotominor.yy346, pParse, yymsp[0].major, &yymsp[0].minor.yy0);} - break; - case 186: /* expr ::= ID|INDEXED */ - case 187: /* expr ::= JOIN_KW */ yytestcase(yyruleno==187); -{spanExpr(&yygotominor.yy346, pParse, TK_ID, &yymsp[0].minor.yy0);} - break; - case 188: /* expr ::= nm DOT nm */ + case 189: /* expr ::= nm DOT nm */ { Expr *temp1 = sqlite3PExpr(pParse, TK_ID, 0, 0, &yymsp[-2].minor.yy0); Expr *temp2 = sqlite3PExpr(pParse, TK_ID, 0, 0, &yymsp[0].minor.yy0); - yygotominor.yy346.pExpr = sqlite3PExpr(pParse, TK_DOT, temp1, temp2, 0); - spanSet(&yygotominor.yy346,&yymsp[-2].minor.yy0,&yymsp[0].minor.yy0); + yygotominor.yy118.pExpr = sqlite3PExpr(pParse, TK_DOT, temp1, temp2, 0); + spanSet(&yygotominor.yy118,&yymsp[-2].minor.yy0,&yymsp[0].minor.yy0); } break; - case 189: /* expr ::= nm DOT nm DOT nm */ + case 190: /* expr ::= nm DOT nm DOT nm */ { Expr *temp1 = sqlite3PExpr(pParse, TK_ID, 0, 0, &yymsp[-4].minor.yy0); Expr *temp2 = sqlite3PExpr(pParse, TK_ID, 0, 0, &yymsp[-2].minor.yy0); Expr *temp3 = sqlite3PExpr(pParse, TK_ID, 0, 0, &yymsp[0].minor.yy0); Expr *temp4 = sqlite3PExpr(pParse, TK_DOT, temp2, temp3, 0); - yygotominor.yy346.pExpr = sqlite3PExpr(pParse, TK_DOT, temp1, temp4, 0); - spanSet(&yygotominor.yy346,&yymsp[-4].minor.yy0,&yymsp[0].minor.yy0); + yygotominor.yy118.pExpr = sqlite3PExpr(pParse, TK_DOT, temp1, temp4, 0); + spanSet(&yygotominor.yy118,&yymsp[-4].minor.yy0,&yymsp[0].minor.yy0); } break; - case 192: /* expr ::= VARIABLE */ + case 193: /* expr ::= VARIABLE */ { if( yymsp[0].minor.yy0.n>=2 && yymsp[0].minor.yy0.z[0]=='#' && sqlite3Isdigit(yymsp[0].minor.yy0.z[1]) ){ /* When doing a nested parse, one can include terms in an expression @@ -119086,142 +130036,142 @@ static void yy_reduce( ** in the virtual machine. #N is the N-th register. */ if( pParse->nested==0 ){ sqlite3ErrorMsg(pParse, "near \"%T\": syntax error", &yymsp[0].minor.yy0); - yygotominor.yy346.pExpr = 0; + yygotominor.yy118.pExpr = 0; }else{ - yygotominor.yy346.pExpr = sqlite3PExpr(pParse, TK_REGISTER, 0, 0, &yymsp[0].minor.yy0); - if( yygotominor.yy346.pExpr ) sqlite3GetInt32(&yymsp[0].minor.yy0.z[1], &yygotominor.yy346.pExpr->iTable); + yygotominor.yy118.pExpr = sqlite3PExpr(pParse, TK_REGISTER, 0, 0, &yymsp[0].minor.yy0); + if( yygotominor.yy118.pExpr ) sqlite3GetInt32(&yymsp[0].minor.yy0.z[1], &yygotominor.yy118.pExpr->iTable); } }else{ - spanExpr(&yygotominor.yy346, pParse, TK_VARIABLE, &yymsp[0].minor.yy0); - sqlite3ExprAssignVarNumber(pParse, yygotominor.yy346.pExpr); + spanExpr(&yygotominor.yy118, pParse, TK_VARIABLE, &yymsp[0].minor.yy0); + sqlite3ExprAssignVarNumber(pParse, yygotominor.yy118.pExpr); } - spanSet(&yygotominor.yy346, &yymsp[0].minor.yy0, &yymsp[0].minor.yy0); + spanSet(&yygotominor.yy118, &yymsp[0].minor.yy0, &yymsp[0].minor.yy0); } break; - case 193: /* expr ::= expr COLLATE ID|STRING */ + case 194: /* expr ::= expr COLLATE ID|STRING */ { - yygotominor.yy346.pExpr = sqlite3ExprAddCollateToken(pParse, yymsp[-2].minor.yy346.pExpr, &yymsp[0].minor.yy0); - yygotominor.yy346.zStart = yymsp[-2].minor.yy346.zStart; - yygotominor.yy346.zEnd = &yymsp[0].minor.yy0.z[yymsp[0].minor.yy0.n]; + yygotominor.yy118.pExpr = sqlite3ExprAddCollateToken(pParse, yymsp[-2].minor.yy118.pExpr, &yymsp[0].minor.yy0, 1); + yygotominor.yy118.zStart = yymsp[-2].minor.yy118.zStart; + yygotominor.yy118.zEnd = &yymsp[0].minor.yy0.z[yymsp[0].minor.yy0.n]; } break; - case 194: /* expr ::= CAST LP expr AS typetoken RP */ + case 195: /* expr ::= CAST LP expr AS typetoken RP */ { - yygotominor.yy346.pExpr = sqlite3PExpr(pParse, TK_CAST, yymsp[-3].minor.yy346.pExpr, 0, &yymsp[-1].minor.yy0); - spanSet(&yygotominor.yy346,&yymsp[-5].minor.yy0,&yymsp[0].minor.yy0); + yygotominor.yy118.pExpr = sqlite3PExpr(pParse, TK_CAST, yymsp[-3].minor.yy118.pExpr, 0, &yymsp[-1].minor.yy0); + spanSet(&yygotominor.yy118,&yymsp[-5].minor.yy0,&yymsp[0].minor.yy0); } break; - case 195: /* expr ::= ID|INDEXED LP distinct exprlist RP */ + case 196: /* expr ::= ID|INDEXED LP distinct exprlist RP */ { - if( yymsp[-1].minor.yy14 && yymsp[-1].minor.yy14->nExpr>pParse->db->aLimit[SQLITE_LIMIT_FUNCTION_ARG] ){ + if( yymsp[-1].minor.yy322 && yymsp[-1].minor.yy322->nExpr>pParse->db->aLimit[SQLITE_LIMIT_FUNCTION_ARG] ){ sqlite3ErrorMsg(pParse, "too many arguments on function %T", &yymsp[-4].minor.yy0); } - yygotominor.yy346.pExpr = sqlite3ExprFunction(pParse, yymsp[-1].minor.yy14, &yymsp[-4].minor.yy0); - spanSet(&yygotominor.yy346,&yymsp[-4].minor.yy0,&yymsp[0].minor.yy0); - if( yymsp[-2].minor.yy381 && yygotominor.yy346.pExpr ){ - yygotominor.yy346.pExpr->flags |= EP_Distinct; + yygotominor.yy118.pExpr = sqlite3ExprFunction(pParse, yymsp[-1].minor.yy322, &yymsp[-4].minor.yy0); + spanSet(&yygotominor.yy118,&yymsp[-4].minor.yy0,&yymsp[0].minor.yy0); + if( yymsp[-2].minor.yy4==SF_Distinct && yygotominor.yy118.pExpr ){ + yygotominor.yy118.pExpr->flags |= EP_Distinct; } } break; - case 196: /* expr ::= ID|INDEXED LP STAR RP */ + case 197: /* expr ::= ID|INDEXED LP STAR RP */ { - yygotominor.yy346.pExpr = sqlite3ExprFunction(pParse, 0, &yymsp[-3].minor.yy0); - spanSet(&yygotominor.yy346,&yymsp[-3].minor.yy0,&yymsp[0].minor.yy0); + yygotominor.yy118.pExpr = sqlite3ExprFunction(pParse, 0, &yymsp[-3].minor.yy0); + spanSet(&yygotominor.yy118,&yymsp[-3].minor.yy0,&yymsp[0].minor.yy0); } break; - case 197: /* term ::= CTIME_KW */ + case 198: /* term ::= CTIME_KW */ { - yygotominor.yy346.pExpr = sqlite3ExprFunction(pParse, 0, &yymsp[0].minor.yy0); - spanSet(&yygotominor.yy346, &yymsp[0].minor.yy0, &yymsp[0].minor.yy0); + yygotominor.yy118.pExpr = sqlite3ExprFunction(pParse, 0, &yymsp[0].minor.yy0); + spanSet(&yygotominor.yy118, &yymsp[0].minor.yy0, &yymsp[0].minor.yy0); } break; - case 198: /* expr ::= expr AND expr */ - case 199: /* expr ::= expr OR expr */ yytestcase(yyruleno==199); - case 200: /* expr ::= expr LT|GT|GE|LE expr */ yytestcase(yyruleno==200); - case 201: /* expr ::= expr EQ|NE expr */ yytestcase(yyruleno==201); - case 202: /* expr ::= expr BITAND|BITOR|LSHIFT|RSHIFT expr */ yytestcase(yyruleno==202); - case 203: /* expr ::= expr PLUS|MINUS expr */ yytestcase(yyruleno==203); - case 204: /* expr ::= expr STAR|SLASH|REM expr */ yytestcase(yyruleno==204); - case 205: /* expr ::= expr CONCAT expr */ yytestcase(yyruleno==205); -{spanBinaryExpr(&yygotominor.yy346,pParse,yymsp[-1].major,&yymsp[-2].minor.yy346,&yymsp[0].minor.yy346);} + case 199: /* expr ::= expr AND expr */ + case 200: /* expr ::= expr OR expr */ yytestcase(yyruleno==200); + case 201: /* expr ::= expr LT|GT|GE|LE expr */ yytestcase(yyruleno==201); + case 202: /* expr ::= expr EQ|NE expr */ yytestcase(yyruleno==202); + case 203: /* expr ::= expr BITAND|BITOR|LSHIFT|RSHIFT expr */ yytestcase(yyruleno==203); + case 204: /* expr ::= expr PLUS|MINUS expr */ yytestcase(yyruleno==204); + case 205: /* expr ::= expr STAR|SLASH|REM expr */ yytestcase(yyruleno==205); + case 206: /* expr ::= expr CONCAT expr */ yytestcase(yyruleno==206); +{spanBinaryExpr(&yygotominor.yy118,pParse,yymsp[-1].major,&yymsp[-2].minor.yy118,&yymsp[0].minor.yy118);} break; - case 206: /* likeop ::= LIKE_KW|MATCH */ -{yygotominor.yy96.eOperator = yymsp[0].minor.yy0; yygotominor.yy96.bNot = 0;} + case 207: /* likeop ::= LIKE_KW|MATCH */ +{yygotominor.yy342.eOperator = yymsp[0].minor.yy0; yygotominor.yy342.bNot = 0;} break; - case 207: /* likeop ::= NOT LIKE_KW|MATCH */ -{yygotominor.yy96.eOperator = yymsp[0].minor.yy0; yygotominor.yy96.bNot = 1;} + case 208: /* likeop ::= NOT LIKE_KW|MATCH */ +{yygotominor.yy342.eOperator = yymsp[0].minor.yy0; yygotominor.yy342.bNot = 1;} break; - case 208: /* expr ::= expr likeop expr */ + case 209: /* expr ::= expr likeop expr */ { ExprList *pList; - pList = sqlite3ExprListAppend(pParse,0, yymsp[0].minor.yy346.pExpr); - pList = sqlite3ExprListAppend(pParse,pList, yymsp[-2].minor.yy346.pExpr); - yygotominor.yy346.pExpr = sqlite3ExprFunction(pParse, pList, &yymsp[-1].minor.yy96.eOperator); - if( yymsp[-1].minor.yy96.bNot ) yygotominor.yy346.pExpr = sqlite3PExpr(pParse, TK_NOT, yygotominor.yy346.pExpr, 0, 0); - yygotominor.yy346.zStart = yymsp[-2].minor.yy346.zStart; - yygotominor.yy346.zEnd = yymsp[0].minor.yy346.zEnd; - if( yygotominor.yy346.pExpr ) yygotominor.yy346.pExpr->flags |= EP_InfixFunc; + pList = sqlite3ExprListAppend(pParse,0, yymsp[0].minor.yy118.pExpr); + pList = sqlite3ExprListAppend(pParse,pList, yymsp[-2].minor.yy118.pExpr); + yygotominor.yy118.pExpr = sqlite3ExprFunction(pParse, pList, &yymsp[-1].minor.yy342.eOperator); + exprNot(pParse, yymsp[-1].minor.yy342.bNot, &yygotominor.yy118.pExpr); + yygotominor.yy118.zStart = yymsp[-2].minor.yy118.zStart; + yygotominor.yy118.zEnd = yymsp[0].minor.yy118.zEnd; + if( yygotominor.yy118.pExpr ) yygotominor.yy118.pExpr->flags |= EP_InfixFunc; } break; - case 209: /* expr ::= expr likeop expr ESCAPE expr */ + case 210: /* expr ::= expr likeop expr ESCAPE expr */ { ExprList *pList; - pList = sqlite3ExprListAppend(pParse,0, yymsp[-2].minor.yy346.pExpr); - pList = sqlite3ExprListAppend(pParse,pList, yymsp[-4].minor.yy346.pExpr); - pList = sqlite3ExprListAppend(pParse,pList, yymsp[0].minor.yy346.pExpr); - yygotominor.yy346.pExpr = sqlite3ExprFunction(pParse, pList, &yymsp[-3].minor.yy96.eOperator); - if( yymsp[-3].minor.yy96.bNot ) yygotominor.yy346.pExpr = sqlite3PExpr(pParse, TK_NOT, yygotominor.yy346.pExpr, 0, 0); - yygotominor.yy346.zStart = yymsp[-4].minor.yy346.zStart; - yygotominor.yy346.zEnd = yymsp[0].minor.yy346.zEnd; - if( yygotominor.yy346.pExpr ) yygotominor.yy346.pExpr->flags |= EP_InfixFunc; + pList = sqlite3ExprListAppend(pParse,0, yymsp[-2].minor.yy118.pExpr); + pList = sqlite3ExprListAppend(pParse,pList, yymsp[-4].minor.yy118.pExpr); + pList = sqlite3ExprListAppend(pParse,pList, yymsp[0].minor.yy118.pExpr); + yygotominor.yy118.pExpr = sqlite3ExprFunction(pParse, pList, &yymsp[-3].minor.yy342.eOperator); + exprNot(pParse, yymsp[-3].minor.yy342.bNot, &yygotominor.yy118.pExpr); + yygotominor.yy118.zStart = yymsp[-4].minor.yy118.zStart; + yygotominor.yy118.zEnd = yymsp[0].minor.yy118.zEnd; + if( yygotominor.yy118.pExpr ) yygotominor.yy118.pExpr->flags |= EP_InfixFunc; } break; - case 210: /* expr ::= expr ISNULL|NOTNULL */ -{spanUnaryPostfix(&yygotominor.yy346,pParse,yymsp[0].major,&yymsp[-1].minor.yy346,&yymsp[0].minor.yy0);} + case 211: /* expr ::= expr ISNULL|NOTNULL */ +{spanUnaryPostfix(&yygotominor.yy118,pParse,yymsp[0].major,&yymsp[-1].minor.yy118,&yymsp[0].minor.yy0);} break; - case 211: /* expr ::= expr NOT NULL */ -{spanUnaryPostfix(&yygotominor.yy346,pParse,TK_NOTNULL,&yymsp[-2].minor.yy346,&yymsp[0].minor.yy0);} + case 212: /* expr ::= expr NOT NULL */ +{spanUnaryPostfix(&yygotominor.yy118,pParse,TK_NOTNULL,&yymsp[-2].minor.yy118,&yymsp[0].minor.yy0);} break; - case 212: /* expr ::= expr IS expr */ + case 213: /* expr ::= expr IS expr */ { - spanBinaryExpr(&yygotominor.yy346,pParse,TK_IS,&yymsp[-2].minor.yy346,&yymsp[0].minor.yy346); - binaryToUnaryIfNull(pParse, yymsp[0].minor.yy346.pExpr, yygotominor.yy346.pExpr, TK_ISNULL); + spanBinaryExpr(&yygotominor.yy118,pParse,TK_IS,&yymsp[-2].minor.yy118,&yymsp[0].minor.yy118); + binaryToUnaryIfNull(pParse, yymsp[0].minor.yy118.pExpr, yygotominor.yy118.pExpr, TK_ISNULL); } break; - case 213: /* expr ::= expr IS NOT expr */ + case 214: /* expr ::= expr IS NOT expr */ { - spanBinaryExpr(&yygotominor.yy346,pParse,TK_ISNOT,&yymsp[-3].minor.yy346,&yymsp[0].minor.yy346); - binaryToUnaryIfNull(pParse, yymsp[0].minor.yy346.pExpr, yygotominor.yy346.pExpr, TK_NOTNULL); + spanBinaryExpr(&yygotominor.yy118,pParse,TK_ISNOT,&yymsp[-3].minor.yy118,&yymsp[0].minor.yy118); + binaryToUnaryIfNull(pParse, yymsp[0].minor.yy118.pExpr, yygotominor.yy118.pExpr, TK_NOTNULL); } break; - case 214: /* expr ::= NOT expr */ - case 215: /* expr ::= BITNOT expr */ yytestcase(yyruleno==215); -{spanUnaryPrefix(&yygotominor.yy346,pParse,yymsp[-1].major,&yymsp[0].minor.yy346,&yymsp[-1].minor.yy0);} + case 215: /* expr ::= NOT expr */ + case 216: /* expr ::= BITNOT expr */ yytestcase(yyruleno==216); +{spanUnaryPrefix(&yygotominor.yy118,pParse,yymsp[-1].major,&yymsp[0].minor.yy118,&yymsp[-1].minor.yy0);} break; - case 216: /* expr ::= MINUS expr */ -{spanUnaryPrefix(&yygotominor.yy346,pParse,TK_UMINUS,&yymsp[0].minor.yy346,&yymsp[-1].minor.yy0);} + case 217: /* expr ::= MINUS expr */ +{spanUnaryPrefix(&yygotominor.yy118,pParse,TK_UMINUS,&yymsp[0].minor.yy118,&yymsp[-1].minor.yy0);} break; - case 217: /* expr ::= PLUS expr */ -{spanUnaryPrefix(&yygotominor.yy346,pParse,TK_UPLUS,&yymsp[0].minor.yy346,&yymsp[-1].minor.yy0);} + case 218: /* expr ::= PLUS expr */ +{spanUnaryPrefix(&yygotominor.yy118,pParse,TK_UPLUS,&yymsp[0].minor.yy118,&yymsp[-1].minor.yy0);} break; - case 220: /* expr ::= expr between_op expr AND expr */ + case 221: /* expr ::= expr between_op expr AND expr */ { - ExprList *pList = sqlite3ExprListAppend(pParse,0, yymsp[-2].minor.yy346.pExpr); - pList = sqlite3ExprListAppend(pParse,pList, yymsp[0].minor.yy346.pExpr); - yygotominor.yy346.pExpr = sqlite3PExpr(pParse, TK_BETWEEN, yymsp[-4].minor.yy346.pExpr, 0, 0); - if( yygotominor.yy346.pExpr ){ - yygotominor.yy346.pExpr->x.pList = pList; + ExprList *pList = sqlite3ExprListAppend(pParse,0, yymsp[-2].minor.yy118.pExpr); + pList = sqlite3ExprListAppend(pParse,pList, yymsp[0].minor.yy118.pExpr); + yygotominor.yy118.pExpr = sqlite3PExpr(pParse, TK_BETWEEN, yymsp[-4].minor.yy118.pExpr, 0, 0); + if( yygotominor.yy118.pExpr ){ + yygotominor.yy118.pExpr->x.pList = pList; }else{ sqlite3ExprListDelete(pParse->db, pList); } - if( yymsp[-3].minor.yy328 ) yygotominor.yy346.pExpr = sqlite3PExpr(pParse, TK_NOT, yygotominor.yy346.pExpr, 0, 0); - yygotominor.yy346.zStart = yymsp[-4].minor.yy346.zStart; - yygotominor.yy346.zEnd = yymsp[0].minor.yy346.zEnd; + exprNot(pParse, yymsp[-3].minor.yy4, &yygotominor.yy118.pExpr); + yygotominor.yy118.zStart = yymsp[-4].minor.yy118.zStart; + yygotominor.yy118.zEnd = yymsp[0].minor.yy118.zEnd; } break; - case 223: /* expr ::= expr in_op LP exprlist RP */ + case 224: /* expr ::= expr in_op LP exprlist RP */ { - if( yymsp[-1].minor.yy14==0 ){ + if( yymsp[-1].minor.yy322==0 ){ /* Expressions of the form ** ** expr1 IN () @@ -119230,9 +130180,9 @@ static void yy_reduce( ** simplify to constants 0 (false) and 1 (true), respectively, ** regardless of the value of expr1. */ - yygotominor.yy346.pExpr = sqlite3PExpr(pParse, TK_INTEGER, 0, 0, &sqlite3IntTokens[yymsp[-3].minor.yy328]); - sqlite3ExprDelete(pParse->db, yymsp[-4].minor.yy346.pExpr); - }else if( yymsp[-1].minor.yy14->nExpr==1 ){ + yygotominor.yy118.pExpr = sqlite3PExpr(pParse, TK_INTEGER, 0, 0, &sqlite3IntTokens[yymsp[-3].minor.yy4]); + sqlite3ExprDelete(pParse->db, yymsp[-4].minor.yy118.pExpr); + }else if( yymsp[-1].minor.yy322->nExpr==1 ){ /* Expressions of the form: ** ** expr1 IN (?1) @@ -119249,233 +130199,222 @@ static void yy_reduce( ** affinity or the collating sequence to use for comparison. Otherwise, ** the semantics would be subtly different from IN or NOT IN. */ - Expr *pRHS = yymsp[-1].minor.yy14->a[0].pExpr; - yymsp[-1].minor.yy14->a[0].pExpr = 0; - sqlite3ExprListDelete(pParse->db, yymsp[-1].minor.yy14); + Expr *pRHS = yymsp[-1].minor.yy322->a[0].pExpr; + yymsp[-1].minor.yy322->a[0].pExpr = 0; + sqlite3ExprListDelete(pParse->db, yymsp[-1].minor.yy322); /* pRHS cannot be NULL because a malloc error would have been detected ** before now and control would have never reached this point */ if( ALWAYS(pRHS) ){ pRHS->flags &= ~EP_Collate; pRHS->flags |= EP_Generic; } - yygotominor.yy346.pExpr = sqlite3PExpr(pParse, yymsp[-3].minor.yy328 ? TK_NE : TK_EQ, yymsp[-4].minor.yy346.pExpr, pRHS, 0); + yygotominor.yy118.pExpr = sqlite3PExpr(pParse, yymsp[-3].minor.yy4 ? TK_NE : TK_EQ, yymsp[-4].minor.yy118.pExpr, pRHS, 0); }else{ - yygotominor.yy346.pExpr = sqlite3PExpr(pParse, TK_IN, yymsp[-4].minor.yy346.pExpr, 0, 0); - if( yygotominor.yy346.pExpr ){ - yygotominor.yy346.pExpr->x.pList = yymsp[-1].minor.yy14; - sqlite3ExprSetHeight(pParse, yygotominor.yy346.pExpr); + yygotominor.yy118.pExpr = sqlite3PExpr(pParse, TK_IN, yymsp[-4].minor.yy118.pExpr, 0, 0); + if( yygotominor.yy118.pExpr ){ + yygotominor.yy118.pExpr->x.pList = yymsp[-1].minor.yy322; + sqlite3ExprSetHeightAndFlags(pParse, yygotominor.yy118.pExpr); }else{ - sqlite3ExprListDelete(pParse->db, yymsp[-1].minor.yy14); + sqlite3ExprListDelete(pParse->db, yymsp[-1].minor.yy322); } - if( yymsp[-3].minor.yy328 ) yygotominor.yy346.pExpr = sqlite3PExpr(pParse, TK_NOT, yygotominor.yy346.pExpr, 0, 0); + exprNot(pParse, yymsp[-3].minor.yy4, &yygotominor.yy118.pExpr); } - yygotominor.yy346.zStart = yymsp[-4].minor.yy346.zStart; - yygotominor.yy346.zEnd = &yymsp[0].minor.yy0.z[yymsp[0].minor.yy0.n]; + yygotominor.yy118.zStart = yymsp[-4].minor.yy118.zStart; + yygotominor.yy118.zEnd = &yymsp[0].minor.yy0.z[yymsp[0].minor.yy0.n]; } break; - case 224: /* expr ::= LP select RP */ + case 225: /* expr ::= LP select RP */ { - yygotominor.yy346.pExpr = sqlite3PExpr(pParse, TK_SELECT, 0, 0, 0); - if( yygotominor.yy346.pExpr ){ - yygotominor.yy346.pExpr->x.pSelect = yymsp[-1].minor.yy3; - ExprSetProperty(yygotominor.yy346.pExpr, EP_xIsSelect); - sqlite3ExprSetHeight(pParse, yygotominor.yy346.pExpr); + yygotominor.yy118.pExpr = sqlite3PExpr(pParse, TK_SELECT, 0, 0, 0); + if( yygotominor.yy118.pExpr ){ + yygotominor.yy118.pExpr->x.pSelect = yymsp[-1].minor.yy387; + ExprSetProperty(yygotominor.yy118.pExpr, EP_xIsSelect|EP_Subquery); + sqlite3ExprSetHeightAndFlags(pParse, yygotominor.yy118.pExpr); }else{ - sqlite3SelectDelete(pParse->db, yymsp[-1].minor.yy3); + sqlite3SelectDelete(pParse->db, yymsp[-1].minor.yy387); } - yygotominor.yy346.zStart = yymsp[-2].minor.yy0.z; - yygotominor.yy346.zEnd = &yymsp[0].minor.yy0.z[yymsp[0].minor.yy0.n]; + yygotominor.yy118.zStart = yymsp[-2].minor.yy0.z; + yygotominor.yy118.zEnd = &yymsp[0].minor.yy0.z[yymsp[0].minor.yy0.n]; } break; - case 225: /* expr ::= expr in_op LP select RP */ + case 226: /* expr ::= expr in_op LP select RP */ { - yygotominor.yy346.pExpr = sqlite3PExpr(pParse, TK_IN, yymsp[-4].minor.yy346.pExpr, 0, 0); - if( yygotominor.yy346.pExpr ){ - yygotominor.yy346.pExpr->x.pSelect = yymsp[-1].minor.yy3; - ExprSetProperty(yygotominor.yy346.pExpr, EP_xIsSelect); - sqlite3ExprSetHeight(pParse, yygotominor.yy346.pExpr); + yygotominor.yy118.pExpr = sqlite3PExpr(pParse, TK_IN, yymsp[-4].minor.yy118.pExpr, 0, 0); + if( yygotominor.yy118.pExpr ){ + yygotominor.yy118.pExpr->x.pSelect = yymsp[-1].minor.yy387; + ExprSetProperty(yygotominor.yy118.pExpr, EP_xIsSelect|EP_Subquery); + sqlite3ExprSetHeightAndFlags(pParse, yygotominor.yy118.pExpr); }else{ - sqlite3SelectDelete(pParse->db, yymsp[-1].minor.yy3); + sqlite3SelectDelete(pParse->db, yymsp[-1].minor.yy387); } - if( yymsp[-3].minor.yy328 ) yygotominor.yy346.pExpr = sqlite3PExpr(pParse, TK_NOT, yygotominor.yy346.pExpr, 0, 0); - yygotominor.yy346.zStart = yymsp[-4].minor.yy346.zStart; - yygotominor.yy346.zEnd = &yymsp[0].minor.yy0.z[yymsp[0].minor.yy0.n]; + exprNot(pParse, yymsp[-3].minor.yy4, &yygotominor.yy118.pExpr); + yygotominor.yy118.zStart = yymsp[-4].minor.yy118.zStart; + yygotominor.yy118.zEnd = &yymsp[0].minor.yy0.z[yymsp[0].minor.yy0.n]; } break; - case 226: /* expr ::= expr in_op nm dbnm */ + case 227: /* expr ::= expr in_op nm dbnm */ { SrcList *pSrc = sqlite3SrcListAppend(pParse->db, 0,&yymsp[-1].minor.yy0,&yymsp[0].minor.yy0); - yygotominor.yy346.pExpr = sqlite3PExpr(pParse, TK_IN, yymsp[-3].minor.yy346.pExpr, 0, 0); - if( yygotominor.yy346.pExpr ){ - yygotominor.yy346.pExpr->x.pSelect = sqlite3SelectNew(pParse, 0,pSrc,0,0,0,0,0,0,0); - ExprSetProperty(yygotominor.yy346.pExpr, EP_xIsSelect); - sqlite3ExprSetHeight(pParse, yygotominor.yy346.pExpr); + yygotominor.yy118.pExpr = sqlite3PExpr(pParse, TK_IN, yymsp[-3].minor.yy118.pExpr, 0, 0); + if( yygotominor.yy118.pExpr ){ + yygotominor.yy118.pExpr->x.pSelect = sqlite3SelectNew(pParse, 0,pSrc,0,0,0,0,0,0,0); + ExprSetProperty(yygotominor.yy118.pExpr, EP_xIsSelect|EP_Subquery); + sqlite3ExprSetHeightAndFlags(pParse, yygotominor.yy118.pExpr); }else{ sqlite3SrcListDelete(pParse->db, pSrc); } - if( yymsp[-2].minor.yy328 ) yygotominor.yy346.pExpr = sqlite3PExpr(pParse, TK_NOT, yygotominor.yy346.pExpr, 0, 0); - yygotominor.yy346.zStart = yymsp[-3].minor.yy346.zStart; - yygotominor.yy346.zEnd = yymsp[0].minor.yy0.z ? &yymsp[0].minor.yy0.z[yymsp[0].minor.yy0.n] : &yymsp[-1].minor.yy0.z[yymsp[-1].minor.yy0.n]; + exprNot(pParse, yymsp[-2].minor.yy4, &yygotominor.yy118.pExpr); + yygotominor.yy118.zStart = yymsp[-3].minor.yy118.zStart; + yygotominor.yy118.zEnd = yymsp[0].minor.yy0.z ? &yymsp[0].minor.yy0.z[yymsp[0].minor.yy0.n] : &yymsp[-1].minor.yy0.z[yymsp[-1].minor.yy0.n]; } break; - case 227: /* expr ::= EXISTS LP select RP */ + case 228: /* expr ::= EXISTS LP select RP */ { - Expr *p = yygotominor.yy346.pExpr = sqlite3PExpr(pParse, TK_EXISTS, 0, 0, 0); + Expr *p = yygotominor.yy118.pExpr = sqlite3PExpr(pParse, TK_EXISTS, 0, 0, 0); if( p ){ - p->x.pSelect = yymsp[-1].minor.yy3; - ExprSetProperty(p, EP_xIsSelect); - sqlite3ExprSetHeight(pParse, p); + p->x.pSelect = yymsp[-1].minor.yy387; + ExprSetProperty(p, EP_xIsSelect|EP_Subquery); + sqlite3ExprSetHeightAndFlags(pParse, p); }else{ - sqlite3SelectDelete(pParse->db, yymsp[-1].minor.yy3); + sqlite3SelectDelete(pParse->db, yymsp[-1].minor.yy387); } - yygotominor.yy346.zStart = yymsp[-3].minor.yy0.z; - yygotominor.yy346.zEnd = &yymsp[0].minor.yy0.z[yymsp[0].minor.yy0.n]; + yygotominor.yy118.zStart = yymsp[-3].minor.yy0.z; + yygotominor.yy118.zEnd = &yymsp[0].minor.yy0.z[yymsp[0].minor.yy0.n]; } break; - case 228: /* expr ::= CASE case_operand case_exprlist case_else END */ + case 229: /* expr ::= CASE case_operand case_exprlist case_else END */ { - yygotominor.yy346.pExpr = sqlite3PExpr(pParse, TK_CASE, yymsp[-3].minor.yy132, 0, 0); - if( yygotominor.yy346.pExpr ){ - yygotominor.yy346.pExpr->x.pList = yymsp[-1].minor.yy132 ? sqlite3ExprListAppend(pParse,yymsp[-2].minor.yy14,yymsp[-1].minor.yy132) : yymsp[-2].minor.yy14; - sqlite3ExprSetHeight(pParse, yygotominor.yy346.pExpr); + yygotominor.yy118.pExpr = sqlite3PExpr(pParse, TK_CASE, yymsp[-3].minor.yy314, 0, 0); + if( yygotominor.yy118.pExpr ){ + yygotominor.yy118.pExpr->x.pList = yymsp[-1].minor.yy314 ? sqlite3ExprListAppend(pParse,yymsp[-2].minor.yy322,yymsp[-1].minor.yy314) : yymsp[-2].minor.yy322; + sqlite3ExprSetHeightAndFlags(pParse, yygotominor.yy118.pExpr); }else{ - sqlite3ExprListDelete(pParse->db, yymsp[-2].minor.yy14); - sqlite3ExprDelete(pParse->db, yymsp[-1].minor.yy132); + sqlite3ExprListDelete(pParse->db, yymsp[-2].minor.yy322); + sqlite3ExprDelete(pParse->db, yymsp[-1].minor.yy314); } - yygotominor.yy346.zStart = yymsp[-4].minor.yy0.z; - yygotominor.yy346.zEnd = &yymsp[0].minor.yy0.z[yymsp[0].minor.yy0.n]; + yygotominor.yy118.zStart = yymsp[-4].minor.yy0.z; + yygotominor.yy118.zEnd = &yymsp[0].minor.yy0.z[yymsp[0].minor.yy0.n]; } break; - case 229: /* case_exprlist ::= case_exprlist WHEN expr THEN expr */ + case 230: /* case_exprlist ::= case_exprlist WHEN expr THEN expr */ { - yygotominor.yy14 = sqlite3ExprListAppend(pParse,yymsp[-4].minor.yy14, yymsp[-2].minor.yy346.pExpr); - yygotominor.yy14 = sqlite3ExprListAppend(pParse,yygotominor.yy14, yymsp[0].minor.yy346.pExpr); + yygotominor.yy322 = sqlite3ExprListAppend(pParse,yymsp[-4].minor.yy322, yymsp[-2].minor.yy118.pExpr); + yygotominor.yy322 = sqlite3ExprListAppend(pParse,yygotominor.yy322, yymsp[0].minor.yy118.pExpr); } break; - case 230: /* case_exprlist ::= WHEN expr THEN expr */ + case 231: /* case_exprlist ::= WHEN expr THEN expr */ { - yygotominor.yy14 = sqlite3ExprListAppend(pParse,0, yymsp[-2].minor.yy346.pExpr); - yygotominor.yy14 = sqlite3ExprListAppend(pParse,yygotominor.yy14, yymsp[0].minor.yy346.pExpr); + yygotominor.yy322 = sqlite3ExprListAppend(pParse,0, yymsp[-2].minor.yy118.pExpr); + yygotominor.yy322 = sqlite3ExprListAppend(pParse,yygotominor.yy322, yymsp[0].minor.yy118.pExpr); } break; - case 237: /* nexprlist ::= nexprlist COMMA expr */ -{yygotominor.yy14 = sqlite3ExprListAppend(pParse,yymsp[-2].minor.yy14,yymsp[0].minor.yy346.pExpr);} + case 238: /* nexprlist ::= nexprlist COMMA expr */ +{yygotominor.yy322 = sqlite3ExprListAppend(pParse,yymsp[-2].minor.yy322,yymsp[0].minor.yy118.pExpr);} break; - case 238: /* nexprlist ::= expr */ -{yygotominor.yy14 = sqlite3ExprListAppend(pParse,0,yymsp[0].minor.yy346.pExpr);} + case 239: /* nexprlist ::= expr */ +{yygotominor.yy322 = sqlite3ExprListAppend(pParse,0,yymsp[0].minor.yy118.pExpr);} break; - case 239: /* cmd ::= createkw uniqueflag INDEX ifnotexists nm dbnm ON nm LP idxlist RP where_opt */ + case 240: /* cmd ::= createkw uniqueflag INDEX ifnotexists nm dbnm ON nm LP sortlist RP where_opt */ { sqlite3CreateIndex(pParse, &yymsp[-7].minor.yy0, &yymsp[-6].minor.yy0, - sqlite3SrcListAppend(pParse->db,0,&yymsp[-4].minor.yy0,0), yymsp[-2].minor.yy14, yymsp[-10].minor.yy328, - &yymsp[-11].minor.yy0, yymsp[0].minor.yy132, SQLITE_SO_ASC, yymsp[-8].minor.yy328); + sqlite3SrcListAppend(pParse->db,0,&yymsp[-4].minor.yy0,0), yymsp[-2].minor.yy322, yymsp[-10].minor.yy4, + &yymsp[-11].minor.yy0, yymsp[0].minor.yy314, SQLITE_SO_ASC, yymsp[-8].minor.yy4); } break; - case 240: /* uniqueflag ::= UNIQUE */ - case 291: /* raisetype ::= ABORT */ yytestcase(yyruleno==291); -{yygotominor.yy328 = OE_Abort;} + case 241: /* uniqueflag ::= UNIQUE */ + case 292: /* raisetype ::= ABORT */ yytestcase(yyruleno==292); +{yygotominor.yy4 = OE_Abort;} break; - case 241: /* uniqueflag ::= */ -{yygotominor.yy328 = OE_None;} + case 242: /* uniqueflag ::= */ +{yygotominor.yy4 = OE_None;} break; - case 244: /* idxlist ::= idxlist COMMA nm collate sortorder */ + case 245: /* eidlist ::= eidlist COMMA nm collate sortorder */ { - Expr *p = sqlite3ExprAddCollateToken(pParse, 0, &yymsp[-1].minor.yy0); - yygotominor.yy14 = sqlite3ExprListAppend(pParse,yymsp[-4].minor.yy14, p); - sqlite3ExprListSetName(pParse,yygotominor.yy14,&yymsp[-2].minor.yy0,1); - sqlite3ExprListCheckLength(pParse, yygotominor.yy14, "index"); - if( yygotominor.yy14 ) yygotominor.yy14->a[yygotominor.yy14->nExpr-1].sortOrder = (u8)yymsp[0].minor.yy328; + yygotominor.yy322 = parserAddExprIdListTerm(pParse, yymsp[-4].minor.yy322, &yymsp[-2].minor.yy0, yymsp[-1].minor.yy4, yymsp[0].minor.yy4); } break; - case 245: /* idxlist ::= nm collate sortorder */ + case 246: /* eidlist ::= nm collate sortorder */ { - Expr *p = sqlite3ExprAddCollateToken(pParse, 0, &yymsp[-1].minor.yy0); - yygotominor.yy14 = sqlite3ExprListAppend(pParse,0, p); - sqlite3ExprListSetName(pParse, yygotominor.yy14, &yymsp[-2].minor.yy0, 1); - sqlite3ExprListCheckLength(pParse, yygotominor.yy14, "index"); - if( yygotominor.yy14 ) yygotominor.yy14->a[yygotominor.yy14->nExpr-1].sortOrder = (u8)yymsp[0].minor.yy328; + yygotominor.yy322 = parserAddExprIdListTerm(pParse, 0, &yymsp[-2].minor.yy0, yymsp[-1].minor.yy4, yymsp[0].minor.yy4); } break; - case 246: /* collate ::= */ -{yygotominor.yy0.z = 0; yygotominor.yy0.n = 0;} + case 249: /* cmd ::= DROP INDEX ifexists fullname */ +{sqlite3DropIndex(pParse, yymsp[0].minor.yy259, yymsp[-1].minor.yy4);} break; - case 248: /* cmd ::= DROP INDEX ifexists fullname */ -{sqlite3DropIndex(pParse, yymsp[0].minor.yy65, yymsp[-1].minor.yy328);} - break; - case 249: /* cmd ::= VACUUM */ - case 250: /* cmd ::= VACUUM nm */ yytestcase(yyruleno==250); + case 250: /* cmd ::= VACUUM */ + case 251: /* cmd ::= VACUUM nm */ yytestcase(yyruleno==251); {sqlite3Vacuum(pParse);} break; - case 251: /* cmd ::= PRAGMA nm dbnm */ + case 252: /* cmd ::= PRAGMA nm dbnm */ {sqlite3Pragma(pParse,&yymsp[-1].minor.yy0,&yymsp[0].minor.yy0,0,0);} break; - case 252: /* cmd ::= PRAGMA nm dbnm EQ nmnum */ + case 253: /* cmd ::= PRAGMA nm dbnm EQ nmnum */ {sqlite3Pragma(pParse,&yymsp[-3].minor.yy0,&yymsp[-2].minor.yy0,&yymsp[0].minor.yy0,0);} break; - case 253: /* cmd ::= PRAGMA nm dbnm LP nmnum RP */ + case 254: /* cmd ::= PRAGMA nm dbnm LP nmnum RP */ {sqlite3Pragma(pParse,&yymsp[-4].minor.yy0,&yymsp[-3].minor.yy0,&yymsp[-1].minor.yy0,0);} break; - case 254: /* cmd ::= PRAGMA nm dbnm EQ minus_num */ + case 255: /* cmd ::= PRAGMA nm dbnm EQ minus_num */ {sqlite3Pragma(pParse,&yymsp[-3].minor.yy0,&yymsp[-2].minor.yy0,&yymsp[0].minor.yy0,1);} break; - case 255: /* cmd ::= PRAGMA nm dbnm LP minus_num RP */ + case 256: /* cmd ::= PRAGMA nm dbnm LP minus_num RP */ {sqlite3Pragma(pParse,&yymsp[-4].minor.yy0,&yymsp[-3].minor.yy0,&yymsp[-1].minor.yy0,1);} break; - case 264: /* cmd ::= createkw trigger_decl BEGIN trigger_cmd_list END */ + case 265: /* cmd ::= createkw trigger_decl BEGIN trigger_cmd_list END */ { Token all; all.z = yymsp[-3].minor.yy0.z; all.n = (int)(yymsp[0].minor.yy0.z - yymsp[-3].minor.yy0.z) + yymsp[0].minor.yy0.n; - sqlite3FinishTrigger(pParse, yymsp[-1].minor.yy473, &all); + sqlite3FinishTrigger(pParse, yymsp[-1].minor.yy203, &all); } break; - case 265: /* trigger_decl ::= temp TRIGGER ifnotexists nm dbnm trigger_time trigger_event ON fullname foreach_clause when_clause */ + case 266: /* trigger_decl ::= temp TRIGGER ifnotexists nm dbnm trigger_time trigger_event ON fullname foreach_clause when_clause */ { - sqlite3BeginTrigger(pParse, &yymsp[-7].minor.yy0, &yymsp[-6].minor.yy0, yymsp[-5].minor.yy328, yymsp[-4].minor.yy378.a, yymsp[-4].minor.yy378.b, yymsp[-2].minor.yy65, yymsp[0].minor.yy132, yymsp[-10].minor.yy328, yymsp[-8].minor.yy328); + sqlite3BeginTrigger(pParse, &yymsp[-7].minor.yy0, &yymsp[-6].minor.yy0, yymsp[-5].minor.yy4, yymsp[-4].minor.yy90.a, yymsp[-4].minor.yy90.b, yymsp[-2].minor.yy259, yymsp[0].minor.yy314, yymsp[-10].minor.yy4, yymsp[-8].minor.yy4); yygotominor.yy0 = (yymsp[-6].minor.yy0.n==0?yymsp[-7].minor.yy0:yymsp[-6].minor.yy0); } break; - case 266: /* trigger_time ::= BEFORE */ - case 269: /* trigger_time ::= */ yytestcase(yyruleno==269); -{ yygotominor.yy328 = TK_BEFORE; } + case 267: /* trigger_time ::= BEFORE */ + case 270: /* trigger_time ::= */ yytestcase(yyruleno==270); +{ yygotominor.yy4 = TK_BEFORE; } break; - case 267: /* trigger_time ::= AFTER */ -{ yygotominor.yy328 = TK_AFTER; } + case 268: /* trigger_time ::= AFTER */ +{ yygotominor.yy4 = TK_AFTER; } break; - case 268: /* trigger_time ::= INSTEAD OF */ -{ yygotominor.yy328 = TK_INSTEAD;} + case 269: /* trigger_time ::= INSTEAD OF */ +{ yygotominor.yy4 = TK_INSTEAD;} break; - case 270: /* trigger_event ::= DELETE|INSERT */ - case 271: /* trigger_event ::= UPDATE */ yytestcase(yyruleno==271); -{yygotominor.yy378.a = yymsp[0].major; yygotominor.yy378.b = 0;} + case 271: /* trigger_event ::= DELETE|INSERT */ + case 272: /* trigger_event ::= UPDATE */ yytestcase(yyruleno==272); +{yygotominor.yy90.a = yymsp[0].major; yygotominor.yy90.b = 0;} break; - case 272: /* trigger_event ::= UPDATE OF idlist */ -{yygotominor.yy378.a = TK_UPDATE; yygotominor.yy378.b = yymsp[0].minor.yy408;} + case 273: /* trigger_event ::= UPDATE OF idlist */ +{yygotominor.yy90.a = TK_UPDATE; yygotominor.yy90.b = yymsp[0].minor.yy384;} break; - case 275: /* when_clause ::= */ - case 296: /* key_opt ::= */ yytestcase(yyruleno==296); -{ yygotominor.yy132 = 0; } + case 276: /* when_clause ::= */ + case 297: /* key_opt ::= */ yytestcase(yyruleno==297); +{ yygotominor.yy314 = 0; } break; - case 276: /* when_clause ::= WHEN expr */ - case 297: /* key_opt ::= KEY expr */ yytestcase(yyruleno==297); -{ yygotominor.yy132 = yymsp[0].minor.yy346.pExpr; } + case 277: /* when_clause ::= WHEN expr */ + case 298: /* key_opt ::= KEY expr */ yytestcase(yyruleno==298); +{ yygotominor.yy314 = yymsp[0].minor.yy118.pExpr; } break; - case 277: /* trigger_cmd_list ::= trigger_cmd_list trigger_cmd SEMI */ + case 278: /* trigger_cmd_list ::= trigger_cmd_list trigger_cmd SEMI */ { - assert( yymsp[-2].minor.yy473!=0 ); - yymsp[-2].minor.yy473->pLast->pNext = yymsp[-1].minor.yy473; - yymsp[-2].minor.yy473->pLast = yymsp[-1].minor.yy473; - yygotominor.yy473 = yymsp[-2].minor.yy473; + assert( yymsp[-2].minor.yy203!=0 ); + yymsp[-2].minor.yy203->pLast->pNext = yymsp[-1].minor.yy203; + yymsp[-2].minor.yy203->pLast = yymsp[-1].minor.yy203; + yygotominor.yy203 = yymsp[-2].minor.yy203; } break; - case 278: /* trigger_cmd_list ::= trigger_cmd SEMI */ + case 279: /* trigger_cmd_list ::= trigger_cmd SEMI */ { - assert( yymsp[-1].minor.yy473!=0 ); - yymsp[-1].minor.yy473->pLast = yymsp[-1].minor.yy473; - yygotominor.yy473 = yymsp[-1].minor.yy473; + assert( yymsp[-1].minor.yy203!=0 ); + yymsp[-1].minor.yy203->pLast = yymsp[-1].minor.yy203; + yygotominor.yy203 = yymsp[-1].minor.yy203; } break; - case 280: /* trnm ::= nm DOT nm */ + case 281: /* trnm ::= nm DOT nm */ { yygotominor.yy0 = yymsp[0].minor.yy0; sqlite3ErrorMsg(pParse, @@ -119483,135 +130422,135 @@ static void yy_reduce( "statements within triggers"); } break; - case 282: /* tridxby ::= INDEXED BY nm */ + case 283: /* tridxby ::= INDEXED BY nm */ { sqlite3ErrorMsg(pParse, "the INDEXED BY clause is not allowed on UPDATE or DELETE statements " "within triggers"); } break; - case 283: /* tridxby ::= NOT INDEXED */ + case 284: /* tridxby ::= NOT INDEXED */ { sqlite3ErrorMsg(pParse, "the NOT INDEXED clause is not allowed on UPDATE or DELETE statements " "within triggers"); } break; - case 284: /* trigger_cmd ::= UPDATE orconf trnm tridxby SET setlist where_opt */ -{ yygotominor.yy473 = sqlite3TriggerUpdateStep(pParse->db, &yymsp[-4].minor.yy0, yymsp[-1].minor.yy14, yymsp[0].minor.yy132, yymsp[-5].minor.yy186); } + case 285: /* trigger_cmd ::= UPDATE orconf trnm tridxby SET setlist where_opt */ +{ yygotominor.yy203 = sqlite3TriggerUpdateStep(pParse->db, &yymsp[-4].minor.yy0, yymsp[-1].minor.yy322, yymsp[0].minor.yy314, yymsp[-5].minor.yy4); } break; - case 285: /* trigger_cmd ::= insert_cmd INTO trnm inscollist_opt select */ -{yygotominor.yy473 = sqlite3TriggerInsertStep(pParse->db, &yymsp[-2].minor.yy0, yymsp[-1].minor.yy408, yymsp[0].minor.yy3, yymsp[-4].minor.yy186);} + case 286: /* trigger_cmd ::= insert_cmd INTO trnm idlist_opt select */ +{yygotominor.yy203 = sqlite3TriggerInsertStep(pParse->db, &yymsp[-2].minor.yy0, yymsp[-1].minor.yy384, yymsp[0].minor.yy387, yymsp[-4].minor.yy4);} break; - case 286: /* trigger_cmd ::= DELETE FROM trnm tridxby where_opt */ -{yygotominor.yy473 = sqlite3TriggerDeleteStep(pParse->db, &yymsp[-2].minor.yy0, yymsp[0].minor.yy132);} + case 287: /* trigger_cmd ::= DELETE FROM trnm tridxby where_opt */ +{yygotominor.yy203 = sqlite3TriggerDeleteStep(pParse->db, &yymsp[-2].minor.yy0, yymsp[0].minor.yy314);} break; - case 287: /* trigger_cmd ::= select */ -{yygotominor.yy473 = sqlite3TriggerSelectStep(pParse->db, yymsp[0].minor.yy3); } + case 288: /* trigger_cmd ::= select */ +{yygotominor.yy203 = sqlite3TriggerSelectStep(pParse->db, yymsp[0].minor.yy387); } break; - case 288: /* expr ::= RAISE LP IGNORE RP */ + case 289: /* expr ::= RAISE LP IGNORE RP */ { - yygotominor.yy346.pExpr = sqlite3PExpr(pParse, TK_RAISE, 0, 0, 0); - if( yygotominor.yy346.pExpr ){ - yygotominor.yy346.pExpr->affinity = OE_Ignore; + yygotominor.yy118.pExpr = sqlite3PExpr(pParse, TK_RAISE, 0, 0, 0); + if( yygotominor.yy118.pExpr ){ + yygotominor.yy118.pExpr->affinity = OE_Ignore; } - yygotominor.yy346.zStart = yymsp[-3].minor.yy0.z; - yygotominor.yy346.zEnd = &yymsp[0].minor.yy0.z[yymsp[0].minor.yy0.n]; + yygotominor.yy118.zStart = yymsp[-3].minor.yy0.z; + yygotominor.yy118.zEnd = &yymsp[0].minor.yy0.z[yymsp[0].minor.yy0.n]; } break; - case 289: /* expr ::= RAISE LP raisetype COMMA nm RP */ + case 290: /* expr ::= RAISE LP raisetype COMMA nm RP */ { - yygotominor.yy346.pExpr = sqlite3PExpr(pParse, TK_RAISE, 0, 0, &yymsp[-1].minor.yy0); - if( yygotominor.yy346.pExpr ) { - yygotominor.yy346.pExpr->affinity = (char)yymsp[-3].minor.yy328; + yygotominor.yy118.pExpr = sqlite3PExpr(pParse, TK_RAISE, 0, 0, &yymsp[-1].minor.yy0); + if( yygotominor.yy118.pExpr ) { + yygotominor.yy118.pExpr->affinity = (char)yymsp[-3].minor.yy4; } - yygotominor.yy346.zStart = yymsp[-5].minor.yy0.z; - yygotominor.yy346.zEnd = &yymsp[0].minor.yy0.z[yymsp[0].minor.yy0.n]; + yygotominor.yy118.zStart = yymsp[-5].minor.yy0.z; + yygotominor.yy118.zEnd = &yymsp[0].minor.yy0.z[yymsp[0].minor.yy0.n]; } break; - case 290: /* raisetype ::= ROLLBACK */ -{yygotominor.yy328 = OE_Rollback;} + case 291: /* raisetype ::= ROLLBACK */ +{yygotominor.yy4 = OE_Rollback;} break; - case 292: /* raisetype ::= FAIL */ -{yygotominor.yy328 = OE_Fail;} + case 293: /* raisetype ::= FAIL */ +{yygotominor.yy4 = OE_Fail;} break; - case 293: /* cmd ::= DROP TRIGGER ifexists fullname */ + case 294: /* cmd ::= DROP TRIGGER ifexists fullname */ { - sqlite3DropTrigger(pParse,yymsp[0].minor.yy65,yymsp[-1].minor.yy328); + sqlite3DropTrigger(pParse,yymsp[0].minor.yy259,yymsp[-1].minor.yy4); } break; - case 294: /* cmd ::= ATTACH database_kw_opt expr AS expr key_opt */ + case 295: /* cmd ::= ATTACH database_kw_opt expr AS expr key_opt */ { - sqlite3Attach(pParse, yymsp[-3].minor.yy346.pExpr, yymsp[-1].minor.yy346.pExpr, yymsp[0].minor.yy132); + sqlite3Attach(pParse, yymsp[-3].minor.yy118.pExpr, yymsp[-1].minor.yy118.pExpr, yymsp[0].minor.yy314); } break; - case 295: /* cmd ::= DETACH database_kw_opt expr */ + case 296: /* cmd ::= DETACH database_kw_opt expr */ { - sqlite3Detach(pParse, yymsp[0].minor.yy346.pExpr); + sqlite3Detach(pParse, yymsp[0].minor.yy118.pExpr); } break; - case 300: /* cmd ::= REINDEX */ + case 301: /* cmd ::= REINDEX */ {sqlite3Reindex(pParse, 0, 0);} break; - case 301: /* cmd ::= REINDEX nm dbnm */ + case 302: /* cmd ::= REINDEX nm dbnm */ {sqlite3Reindex(pParse, &yymsp[-1].minor.yy0, &yymsp[0].minor.yy0);} break; - case 302: /* cmd ::= ANALYZE */ + case 303: /* cmd ::= ANALYZE */ {sqlite3Analyze(pParse, 0, 0);} break; - case 303: /* cmd ::= ANALYZE nm dbnm */ + case 304: /* cmd ::= ANALYZE nm dbnm */ {sqlite3Analyze(pParse, &yymsp[-1].minor.yy0, &yymsp[0].minor.yy0);} break; - case 304: /* cmd ::= ALTER TABLE fullname RENAME TO nm */ + case 305: /* cmd ::= ALTER TABLE fullname RENAME TO nm */ { - sqlite3AlterRenameTable(pParse,yymsp[-3].minor.yy65,&yymsp[0].minor.yy0); + sqlite3AlterRenameTable(pParse,yymsp[-3].minor.yy259,&yymsp[0].minor.yy0); } break; - case 305: /* cmd ::= ALTER TABLE add_column_fullname ADD kwcolumn_opt column */ + case 306: /* cmd ::= ALTER TABLE add_column_fullname ADD kwcolumn_opt column */ { sqlite3AlterFinishAddColumn(pParse, &yymsp[0].minor.yy0); } break; - case 306: /* add_column_fullname ::= fullname */ + case 307: /* add_column_fullname ::= fullname */ { pParse->db->lookaside.bEnabled = 0; - sqlite3AlterBeginAddColumn(pParse, yymsp[0].minor.yy65); + sqlite3AlterBeginAddColumn(pParse, yymsp[0].minor.yy259); } break; - case 309: /* cmd ::= create_vtab */ + case 310: /* cmd ::= create_vtab */ {sqlite3VtabFinishParse(pParse,0);} break; - case 310: /* cmd ::= create_vtab LP vtabarglist RP */ + case 311: /* cmd ::= create_vtab LP vtabarglist RP */ {sqlite3VtabFinishParse(pParse,&yymsp[0].minor.yy0);} break; - case 311: /* create_vtab ::= createkw VIRTUAL TABLE ifnotexists nm dbnm USING nm */ + case 312: /* create_vtab ::= createkw VIRTUAL TABLE ifnotexists nm dbnm USING nm */ { - sqlite3VtabBeginParse(pParse, &yymsp[-3].minor.yy0, &yymsp[-2].minor.yy0, &yymsp[0].minor.yy0, yymsp[-4].minor.yy328); + sqlite3VtabBeginParse(pParse, &yymsp[-3].minor.yy0, &yymsp[-2].minor.yy0, &yymsp[0].minor.yy0, yymsp[-4].minor.yy4); } break; - case 314: /* vtabarg ::= */ + case 315: /* vtabarg ::= */ {sqlite3VtabArgInit(pParse);} break; - case 316: /* vtabargtoken ::= ANY */ - case 317: /* vtabargtoken ::= lp anylist RP */ yytestcase(yyruleno==317); - case 318: /* lp ::= LP */ yytestcase(yyruleno==318); + case 317: /* vtabargtoken ::= ANY */ + case 318: /* vtabargtoken ::= lp anylist RP */ yytestcase(yyruleno==318); + case 319: /* lp ::= LP */ yytestcase(yyruleno==319); {sqlite3VtabArgExtend(pParse,&yymsp[0].minor.yy0);} break; - case 322: /* with ::= */ -{yygotominor.yy59 = 0;} + case 323: /* with ::= */ +{yygotominor.yy451 = 0;} break; - case 323: /* with ::= WITH wqlist */ - case 324: /* with ::= WITH RECURSIVE wqlist */ yytestcase(yyruleno==324); -{ yygotominor.yy59 = yymsp[0].minor.yy59; } + case 324: /* with ::= WITH wqlist */ + case 325: /* with ::= WITH RECURSIVE wqlist */ yytestcase(yyruleno==325); +{ yygotominor.yy451 = yymsp[0].minor.yy451; } break; - case 325: /* wqlist ::= nm idxlist_opt AS LP select RP */ + case 326: /* wqlist ::= nm eidlist_opt AS LP select RP */ { - yygotominor.yy59 = sqlite3WithAdd(pParse, 0, &yymsp[-5].minor.yy0, yymsp[-4].minor.yy14, yymsp[-1].minor.yy3); + yygotominor.yy451 = sqlite3WithAdd(pParse, 0, &yymsp[-5].minor.yy0, yymsp[-4].minor.yy322, yymsp[-1].minor.yy387); } break; - case 326: /* wqlist ::= wqlist COMMA nm idxlist_opt AS LP select RP */ + case 327: /* wqlist ::= wqlist COMMA nm eidlist_opt AS LP select RP */ { - yygotominor.yy59 = sqlite3WithAdd(pParse, yymsp[-7].minor.yy59, &yymsp[-5].minor.yy0, yymsp[-4].minor.yy14, yymsp[-1].minor.yy3); + yygotominor.yy451 = sqlite3WithAdd(pParse, yymsp[-7].minor.yy451, &yymsp[-5].minor.yy0, yymsp[-4].minor.yy322, yymsp[-1].minor.yy387); } break; default: @@ -119637,29 +130576,30 @@ static void yy_reduce( /* (88) conslist ::= conslist tconscomma tcons */ yytestcase(yyruleno==88); /* (89) conslist ::= tcons */ yytestcase(yyruleno==89); /* (91) tconscomma ::= */ yytestcase(yyruleno==91); - /* (273) foreach_clause ::= */ yytestcase(yyruleno==273); - /* (274) foreach_clause ::= FOR EACH ROW */ yytestcase(yyruleno==274); - /* (281) tridxby ::= */ yytestcase(yyruleno==281); - /* (298) database_kw_opt ::= DATABASE */ yytestcase(yyruleno==298); - /* (299) database_kw_opt ::= */ yytestcase(yyruleno==299); - /* (307) kwcolumn_opt ::= */ yytestcase(yyruleno==307); - /* (308) kwcolumn_opt ::= COLUMNKW */ yytestcase(yyruleno==308); - /* (312) vtabarglist ::= vtabarg */ yytestcase(yyruleno==312); - /* (313) vtabarglist ::= vtabarglist COMMA vtabarg */ yytestcase(yyruleno==313); - /* (315) vtabarg ::= vtabarg vtabargtoken */ yytestcase(yyruleno==315); - /* (319) anylist ::= */ yytestcase(yyruleno==319); - /* (320) anylist ::= anylist LP anylist RP */ yytestcase(yyruleno==320); - /* (321) anylist ::= anylist ANY */ yytestcase(yyruleno==321); + /* (274) foreach_clause ::= */ yytestcase(yyruleno==274); + /* (275) foreach_clause ::= FOR EACH ROW */ yytestcase(yyruleno==275); + /* (282) tridxby ::= */ yytestcase(yyruleno==282); + /* (299) database_kw_opt ::= DATABASE */ yytestcase(yyruleno==299); + /* (300) database_kw_opt ::= */ yytestcase(yyruleno==300); + /* (308) kwcolumn_opt ::= */ yytestcase(yyruleno==308); + /* (309) kwcolumn_opt ::= COLUMNKW */ yytestcase(yyruleno==309); + /* (313) vtabarglist ::= vtabarg */ yytestcase(yyruleno==313); + /* (314) vtabarglist ::= vtabarglist COMMA vtabarg */ yytestcase(yyruleno==314); + /* (316) vtabarg ::= vtabarg vtabargtoken */ yytestcase(yyruleno==316); + /* (320) anylist ::= */ yytestcase(yyruleno==320); + /* (321) anylist ::= anylist LP anylist RP */ yytestcase(yyruleno==321); + /* (322) anylist ::= anylist ANY */ yytestcase(yyruleno==322); break; +/********** End reduce actions ************************************************/ }; assert( yyruleno>=0 && yyrulenoyyidx -= yysize; yyact = yy_find_reduce_action(yymsp[-yysize].stateno,(YYCODETYPE)yygoto); - if( yyact < YYNSTATE ){ -#ifdef NDEBUG - /* If we are not debugging and the reduce action popped at least + if( yyact <= YY_MAX_SHIFTREDUCE ){ + if( yyact>YY_MAX_SHIFT ) yyact += YY_MIN_REDUCE - YY_MIN_SHIFTREDUCE; + /* If the reduce action popped at least ** one element off the stack, then we can push the new element back ** onto the stack here, and skip the stack overflow test in yy_shift(). ** That gives a significant speed improvement. */ @@ -119669,13 +130609,12 @@ static void yy_reduce( yymsp->stateno = (YYACTIONTYPE)yyact; yymsp->major = (YYCODETYPE)yygoto; yymsp->minor = yygotominor; - }else -#endif - { + yyTraceShift(yypParser, yyact); + }else{ yy_shift(yypParser,yyact,yygoto,&yygotominor); } }else{ - assert( yyact == YYNSTATE + YYNRULE + 1 ); + assert( yyact == YY_ACCEPT_ACTION ); yy_accept(yypParser); } } @@ -119696,6 +130635,8 @@ static void yy_parse_failed( while( yypParser->yyidx>=0 ) yy_pop_parser_stack(yypParser); /* Here code is inserted which will be executed whenever the ** parser fails */ +/************ Begin %parse_failure code ***************************************/ +/************ End %parse_failure code *****************************************/ sqlite3ParserARG_STORE; /* Suppress warning about unused %extra_argument variable */ } #endif /* YYNOERRORRECOVERY */ @@ -119710,10 +130651,12 @@ static void yy_syntax_error( ){ sqlite3ParserARG_FETCH; #define TOKEN (yyminor.yy0) +/************ Begin %syntax_error code ****************************************/ UNUSED_PARAMETER(yymajor); /* Silence some compiler warnings */ assert( TOKEN.z[0] ); /* The tokenizer always gives us a token */ sqlite3ErrorMsg(pParse, "near \"%T\": syntax error", &TOKEN); +/************ End %syntax_error code ******************************************/ sqlite3ParserARG_STORE; /* Suppress warning about unused %extra_argument variable */ } @@ -119732,6 +130675,8 @@ static void yy_accept( while( yypParser->yyidx>=0 ) yy_pop_parser_stack(yypParser); /* Here code is inserted which will be executed whenever the ** parser accepts */ +/*********** Begin %parse_accept code *****************************************/ +/*********** End %parse_accept code *******************************************/ sqlite3ParserARG_STORE; /* Suppress warning about unused %extra_argument variable */ } @@ -119785,6 +130730,12 @@ SQLITE_PRIVATE void sqlite3Parser( yypParser->yyerrcnt = -1; yypParser->yystack[0].stateno = 0; yypParser->yystack[0].major = 0; +#ifndef NDEBUG + if( yyTraceFILE ){ + fprintf(yyTraceFILE,"%sInitialize. Empty stack. State 0\n", + yyTracePrompt); + } +#endif } yyminorunion.yy0 = yyminor; #if !defined(YYERRORSYMBOL) && !defined(YYNOERRORRECOVERY) @@ -119794,18 +130745,19 @@ SQLITE_PRIVATE void sqlite3Parser( #ifndef NDEBUG if( yyTraceFILE ){ - fprintf(yyTraceFILE,"%sInput %s\n",yyTracePrompt,yyTokenName[yymajor]); + fprintf(yyTraceFILE,"%sInput '%s'\n",yyTracePrompt,yyTokenName[yymajor]); } #endif do{ yyact = yy_find_shift_action(yypParser,(YYCODETYPE)yymajor); - if( yyact YY_MAX_SHIFT ) yyact += YY_MIN_REDUCE - YY_MIN_SHIFTREDUCE; yy_shift(yypParser,yyact,yymajor,&yyminorunion); yypParser->yyerrcnt--; yymajor = YYNOCODE; - }else if( yyact < YYNSTATE + YYNRULE ){ - yy_reduce(yypParser,yyact-YYNSTATE); + }else if( yyact <= YY_MAX_REDUCE ){ + yy_reduce(yypParser,yyact-YY_MIN_REDUCE); }else{ assert( yyact == YY_ERROR_ACTION ); #ifdef YYERRORSYMBOL @@ -119855,7 +130807,7 @@ SQLITE_PRIVATE void sqlite3Parser( yymx != YYERRORSYMBOL && (yyact = yy_find_reduce_action( yypParser->yystack[yypParser->yyidx].stateno, - YYERRORSYMBOL)) >= YYNSTATE + YYERRORSYMBOL)) >= YY_MIN_REDUCE ){ yy_pop_parser_stack(yypParser); } @@ -119905,6 +130857,16 @@ SQLITE_PRIVATE void sqlite3Parser( #endif } }while( yymajor!=YYNOCODE && yypParser->yyidx>=0 ); +#ifndef NDEBUG + if( yyTraceFILE ){ + int i; + fprintf(yyTraceFILE,"%sReturn. Stack=",yyTracePrompt); + for(i=1; i<=yypParser->yyidx; i++) + fprintf(yyTraceFILE,"%c%s", i==1 ? '[' : ' ', + yyTokenName[yypParser->yystack[i].major]); + fprintf(yyTraceFILE,"]\n"); + } +#endif return; } @@ -119927,6 +130889,7 @@ SQLITE_PRIVATE void sqlite3Parser( ** individual tokens and sends those tokens one-by-one over to the ** parser for analysis. */ +/* #include "sqliteInt.h" */ /* #include */ /* @@ -119989,7 +130952,7 @@ const unsigned char ebcdicToAscii[] = { ** on platforms with limited memory. */ /* Hash score: 182 */ -static int keywordCode(const char *z, int n){ +static int keywordCode(const char *z, int n, int *pType){ /* zText[] encodes 834 bytes of keywords in 554 bytes */ /* REINDEXEDESCAPEACHECKEYBEFOREIGNOREGEXPLAINSTEADDATABASELECT */ /* ABLEFTHENDEFERRABLELSEXCEPTRANSACTIONATURALTERAISEXCLUSIVE */ @@ -120110,143 +131073,145 @@ static int keywordCode(const char *z, int n){ TK_VACUUM, TK_VIEW, TK_INITIALLY, TK_ALL, }; int h, i; - if( n<2 ) return TK_ID; - h = ((charMap(z[0])*4) ^ - (charMap(z[n-1])*3) ^ - n) % 127; - for(i=((int)aHash[h])-1; i>=0; i=((int)aNext[i])-1){ - if( aLen[i]==n && sqlite3StrNICmp(&zText[aOffset[i]],z,n)==0 ){ - testcase( i==0 ); /* REINDEX */ - testcase( i==1 ); /* INDEXED */ - testcase( i==2 ); /* INDEX */ - testcase( i==3 ); /* DESC */ - testcase( i==4 ); /* ESCAPE */ - testcase( i==5 ); /* EACH */ - testcase( i==6 ); /* CHECK */ - testcase( i==7 ); /* KEY */ - testcase( i==8 ); /* BEFORE */ - testcase( i==9 ); /* FOREIGN */ - testcase( i==10 ); /* FOR */ - testcase( i==11 ); /* IGNORE */ - testcase( i==12 ); /* REGEXP */ - testcase( i==13 ); /* EXPLAIN */ - testcase( i==14 ); /* INSTEAD */ - testcase( i==15 ); /* ADD */ - testcase( i==16 ); /* DATABASE */ - testcase( i==17 ); /* AS */ - testcase( i==18 ); /* SELECT */ - testcase( i==19 ); /* TABLE */ - testcase( i==20 ); /* LEFT */ - testcase( i==21 ); /* THEN */ - testcase( i==22 ); /* END */ - testcase( i==23 ); /* DEFERRABLE */ - testcase( i==24 ); /* ELSE */ - testcase( i==25 ); /* EXCEPT */ - testcase( i==26 ); /* TRANSACTION */ - testcase( i==27 ); /* ACTION */ - testcase( i==28 ); /* ON */ - testcase( i==29 ); /* NATURAL */ - testcase( i==30 ); /* ALTER */ - testcase( i==31 ); /* RAISE */ - testcase( i==32 ); /* EXCLUSIVE */ - testcase( i==33 ); /* EXISTS */ - testcase( i==34 ); /* SAVEPOINT */ - testcase( i==35 ); /* INTERSECT */ - testcase( i==36 ); /* TRIGGER */ - testcase( i==37 ); /* REFERENCES */ - testcase( i==38 ); /* CONSTRAINT */ - testcase( i==39 ); /* INTO */ - testcase( i==40 ); /* OFFSET */ - testcase( i==41 ); /* OF */ - testcase( i==42 ); /* SET */ - testcase( i==43 ); /* TEMPORARY */ - testcase( i==44 ); /* TEMP */ - testcase( i==45 ); /* OR */ - testcase( i==46 ); /* UNIQUE */ - testcase( i==47 ); /* QUERY */ - testcase( i==48 ); /* WITHOUT */ - testcase( i==49 ); /* WITH */ - testcase( i==50 ); /* OUTER */ - testcase( i==51 ); /* RELEASE */ - testcase( i==52 ); /* ATTACH */ - testcase( i==53 ); /* HAVING */ - testcase( i==54 ); /* GROUP */ - testcase( i==55 ); /* UPDATE */ - testcase( i==56 ); /* BEGIN */ - testcase( i==57 ); /* INNER */ - testcase( i==58 ); /* RECURSIVE */ - testcase( i==59 ); /* BETWEEN */ - testcase( i==60 ); /* NOTNULL */ - testcase( i==61 ); /* NOT */ - testcase( i==62 ); /* NO */ - testcase( i==63 ); /* NULL */ - testcase( i==64 ); /* LIKE */ - testcase( i==65 ); /* CASCADE */ - testcase( i==66 ); /* ASC */ - testcase( i==67 ); /* DELETE */ - testcase( i==68 ); /* CASE */ - testcase( i==69 ); /* COLLATE */ - testcase( i==70 ); /* CREATE */ - testcase( i==71 ); /* CURRENT_DATE */ - testcase( i==72 ); /* DETACH */ - testcase( i==73 ); /* IMMEDIATE */ - testcase( i==74 ); /* JOIN */ - testcase( i==75 ); /* INSERT */ - testcase( i==76 ); /* MATCH */ - testcase( i==77 ); /* PLAN */ - testcase( i==78 ); /* ANALYZE */ - testcase( i==79 ); /* PRAGMA */ - testcase( i==80 ); /* ABORT */ - testcase( i==81 ); /* VALUES */ - testcase( i==82 ); /* VIRTUAL */ - testcase( i==83 ); /* LIMIT */ - testcase( i==84 ); /* WHEN */ - testcase( i==85 ); /* WHERE */ - testcase( i==86 ); /* RENAME */ - testcase( i==87 ); /* AFTER */ - testcase( i==88 ); /* REPLACE */ - testcase( i==89 ); /* AND */ - testcase( i==90 ); /* DEFAULT */ - testcase( i==91 ); /* AUTOINCREMENT */ - testcase( i==92 ); /* TO */ - testcase( i==93 ); /* IN */ - testcase( i==94 ); /* CAST */ - testcase( i==95 ); /* COLUMN */ - testcase( i==96 ); /* COMMIT */ - testcase( i==97 ); /* CONFLICT */ - testcase( i==98 ); /* CROSS */ - testcase( i==99 ); /* CURRENT_TIMESTAMP */ - testcase( i==100 ); /* CURRENT_TIME */ - testcase( i==101 ); /* PRIMARY */ - testcase( i==102 ); /* DEFERRED */ - testcase( i==103 ); /* DISTINCT */ - testcase( i==104 ); /* IS */ - testcase( i==105 ); /* DROP */ - testcase( i==106 ); /* FAIL */ - testcase( i==107 ); /* FROM */ - testcase( i==108 ); /* FULL */ - testcase( i==109 ); /* GLOB */ - testcase( i==110 ); /* BY */ - testcase( i==111 ); /* IF */ - testcase( i==112 ); /* ISNULL */ - testcase( i==113 ); /* ORDER */ - testcase( i==114 ); /* RESTRICT */ - testcase( i==115 ); /* RIGHT */ - testcase( i==116 ); /* ROLLBACK */ - testcase( i==117 ); /* ROW */ - testcase( i==118 ); /* UNION */ - testcase( i==119 ); /* USING */ - testcase( i==120 ); /* VACUUM */ - testcase( i==121 ); /* VIEW */ - testcase( i==122 ); /* INITIALLY */ - testcase( i==123 ); /* ALL */ - return aCode[i]; + if( n>=2 ){ + h = ((charMap(z[0])*4) ^ (charMap(z[n-1])*3) ^ n) % 127; + for(i=((int)aHash[h])-1; i>=0; i=((int)aNext[i])-1){ + if( aLen[i]==n && sqlite3StrNICmp(&zText[aOffset[i]],z,n)==0 ){ + testcase( i==0 ); /* REINDEX */ + testcase( i==1 ); /* INDEXED */ + testcase( i==2 ); /* INDEX */ + testcase( i==3 ); /* DESC */ + testcase( i==4 ); /* ESCAPE */ + testcase( i==5 ); /* EACH */ + testcase( i==6 ); /* CHECK */ + testcase( i==7 ); /* KEY */ + testcase( i==8 ); /* BEFORE */ + testcase( i==9 ); /* FOREIGN */ + testcase( i==10 ); /* FOR */ + testcase( i==11 ); /* IGNORE */ + testcase( i==12 ); /* REGEXP */ + testcase( i==13 ); /* EXPLAIN */ + testcase( i==14 ); /* INSTEAD */ + testcase( i==15 ); /* ADD */ + testcase( i==16 ); /* DATABASE */ + testcase( i==17 ); /* AS */ + testcase( i==18 ); /* SELECT */ + testcase( i==19 ); /* TABLE */ + testcase( i==20 ); /* LEFT */ + testcase( i==21 ); /* THEN */ + testcase( i==22 ); /* END */ + testcase( i==23 ); /* DEFERRABLE */ + testcase( i==24 ); /* ELSE */ + testcase( i==25 ); /* EXCEPT */ + testcase( i==26 ); /* TRANSACTION */ + testcase( i==27 ); /* ACTION */ + testcase( i==28 ); /* ON */ + testcase( i==29 ); /* NATURAL */ + testcase( i==30 ); /* ALTER */ + testcase( i==31 ); /* RAISE */ + testcase( i==32 ); /* EXCLUSIVE */ + testcase( i==33 ); /* EXISTS */ + testcase( i==34 ); /* SAVEPOINT */ + testcase( i==35 ); /* INTERSECT */ + testcase( i==36 ); /* TRIGGER */ + testcase( i==37 ); /* REFERENCES */ + testcase( i==38 ); /* CONSTRAINT */ + testcase( i==39 ); /* INTO */ + testcase( i==40 ); /* OFFSET */ + testcase( i==41 ); /* OF */ + testcase( i==42 ); /* SET */ + testcase( i==43 ); /* TEMPORARY */ + testcase( i==44 ); /* TEMP */ + testcase( i==45 ); /* OR */ + testcase( i==46 ); /* UNIQUE */ + testcase( i==47 ); /* QUERY */ + testcase( i==48 ); /* WITHOUT */ + testcase( i==49 ); /* WITH */ + testcase( i==50 ); /* OUTER */ + testcase( i==51 ); /* RELEASE */ + testcase( i==52 ); /* ATTACH */ + testcase( i==53 ); /* HAVING */ + testcase( i==54 ); /* GROUP */ + testcase( i==55 ); /* UPDATE */ + testcase( i==56 ); /* BEGIN */ + testcase( i==57 ); /* INNER */ + testcase( i==58 ); /* RECURSIVE */ + testcase( i==59 ); /* BETWEEN */ + testcase( i==60 ); /* NOTNULL */ + testcase( i==61 ); /* NOT */ + testcase( i==62 ); /* NO */ + testcase( i==63 ); /* NULL */ + testcase( i==64 ); /* LIKE */ + testcase( i==65 ); /* CASCADE */ + testcase( i==66 ); /* ASC */ + testcase( i==67 ); /* DELETE */ + testcase( i==68 ); /* CASE */ + testcase( i==69 ); /* COLLATE */ + testcase( i==70 ); /* CREATE */ + testcase( i==71 ); /* CURRENT_DATE */ + testcase( i==72 ); /* DETACH */ + testcase( i==73 ); /* IMMEDIATE */ + testcase( i==74 ); /* JOIN */ + testcase( i==75 ); /* INSERT */ + testcase( i==76 ); /* MATCH */ + testcase( i==77 ); /* PLAN */ + testcase( i==78 ); /* ANALYZE */ + testcase( i==79 ); /* PRAGMA */ + testcase( i==80 ); /* ABORT */ + testcase( i==81 ); /* VALUES */ + testcase( i==82 ); /* VIRTUAL */ + testcase( i==83 ); /* LIMIT */ + testcase( i==84 ); /* WHEN */ + testcase( i==85 ); /* WHERE */ + testcase( i==86 ); /* RENAME */ + testcase( i==87 ); /* AFTER */ + testcase( i==88 ); /* REPLACE */ + testcase( i==89 ); /* AND */ + testcase( i==90 ); /* DEFAULT */ + testcase( i==91 ); /* AUTOINCREMENT */ + testcase( i==92 ); /* TO */ + testcase( i==93 ); /* IN */ + testcase( i==94 ); /* CAST */ + testcase( i==95 ); /* COLUMN */ + testcase( i==96 ); /* COMMIT */ + testcase( i==97 ); /* CONFLICT */ + testcase( i==98 ); /* CROSS */ + testcase( i==99 ); /* CURRENT_TIMESTAMP */ + testcase( i==100 ); /* CURRENT_TIME */ + testcase( i==101 ); /* PRIMARY */ + testcase( i==102 ); /* DEFERRED */ + testcase( i==103 ); /* DISTINCT */ + testcase( i==104 ); /* IS */ + testcase( i==105 ); /* DROP */ + testcase( i==106 ); /* FAIL */ + testcase( i==107 ); /* FROM */ + testcase( i==108 ); /* FULL */ + testcase( i==109 ); /* GLOB */ + testcase( i==110 ); /* BY */ + testcase( i==111 ); /* IF */ + testcase( i==112 ); /* ISNULL */ + testcase( i==113 ); /* ORDER */ + testcase( i==114 ); /* RESTRICT */ + testcase( i==115 ); /* RIGHT */ + testcase( i==116 ); /* ROLLBACK */ + testcase( i==117 ); /* ROW */ + testcase( i==118 ); /* UNION */ + testcase( i==119 ); /* USING */ + testcase( i==120 ); /* VACUUM */ + testcase( i==121 ); /* VIEW */ + testcase( i==122 ); /* INITIALLY */ + testcase( i==123 ); /* ALL */ + *pType = aCode[i]; + break; + } } } - return TK_ID; + return n; } SQLITE_PRIVATE int sqlite3KeywordCode(const unsigned char *z, int n){ - return keywordCode((char*)z, n); + int id = TK_ID; + keywordCode((char*)z, n, &id); + return id; } #define SQLITE_N_KEYWORD 124 @@ -120266,7 +131231,7 @@ SQLITE_PRIVATE int sqlite3KeywordCode(const unsigned char *z, int n){ ** end result. ** ** Ticket #1066. the SQL standard does not allow '$' in the -** middle of identfiers. But many SQL implementations do. +** middle of identifiers. But many SQL implementations do. ** SQLite will allow '$' in identifiers for compatibility. ** But the feature is undocumented. */ @@ -120292,6 +131257,11 @@ SQLITE_PRIVATE const char sqlite3IsEbcdicIdChar[] = { #define IdChar(C) (((c=C)>=0x42 && sqlite3IsEbcdicIdChar[c-0x40])) #endif +/* Make the IdChar function accessible from ctime.c */ +#ifndef SQLITE_OMIT_COMPILEOPTION_DIAGS +SQLITE_PRIVATE int sqlite3IsIdChar(u8 c){ return IdChar(c); } +#endif + /* ** Return the length of the token that begins at z[0]. @@ -120459,6 +131429,12 @@ SQLITE_PRIVATE int sqlite3GetToken(const unsigned char *z, int *tokenType){ testcase( z[0]=='6' ); testcase( z[0]=='7' ); testcase( z[0]=='8' ); testcase( z[0]=='9' ); *tokenType = TK_INTEGER; +#ifndef SQLITE_OMIT_HEX_INTEGER + if( z[0]=='0' && (z[1]=='x' || z[1]=='X') && sqlite3Isxdigit(z[2]) ){ + for(i=3; sqlite3Isxdigit(z[i]); i++){} + return i; + } +#endif for(i=0; sqlite3Isdigit(z[i]); i++){} #ifndef SQLITE_OMIT_FLOATING_POINT if( z[i]=='.' ){ @@ -120547,8 +131523,8 @@ SQLITE_PRIVATE int sqlite3GetToken(const unsigned char *z, int *tokenType){ break; } for(i=1; IdChar(z[i]); i++){} - *tokenType = keywordCode((char*)z, i); - return i; + *tokenType = TK_ID; + return keywordCode((char*)z, i, tokenType); } } *tokenType = TK_ILLEGAL; @@ -120572,7 +131548,7 @@ SQLITE_PRIVATE int sqlite3RunParser(Parse *pParse, const char *zSql, char **pzEr sqlite3 *db = pParse->db; /* The database connection */ int mxSqlLen; /* Max length of an SQL string */ - + assert( zSql!=0 ); mxSqlLen = db->aLimit[SQLITE_LIMIT_SQL_LENGTH]; if( db->nVdbeActive==0 ){ db->u1.isInterrupted = 0; @@ -120581,7 +131557,8 @@ SQLITE_PRIVATE int sqlite3RunParser(Parse *pParse, const char *zSql, char **pzEr pParse->zTail = zSql; i = 0; assert( pzErrMsg!=0 ); - pEngine = sqlite3ParserAlloc((void*(*)(size_t))sqlite3Malloc); + /* sqlite3ParserTrace(stdout, "parser: "); */ + pEngine = sqlite3ParserAlloc(sqlite3Malloc); if( pEngine==0 ){ db->mallocFailed = 1; return SQLITE_NOMEM; @@ -120593,7 +131570,7 @@ SQLITE_PRIVATE int sqlite3RunParser(Parse *pParse, const char *zSql, char **pzEr assert( pParse->azVar==0 ); enableLookaside = db->lookaside.bEnabled; if( db->lookaside.pStart ) db->lookaside.bEnabled = 1; - while( !db->mallocFailed && zSql[i]!=0 ){ + while( zSql[i]!=0 ){ assert( i>=0 ); pParse->sLastToken.z = &zSql[i]; pParse->sLastToken.n = sqlite3GetToken((unsigned char*)&zSql[i],&tokenType); @@ -120602,48 +131579,42 @@ SQLITE_PRIVATE int sqlite3RunParser(Parse *pParse, const char *zSql, char **pzEr pParse->rc = SQLITE_TOOBIG; break; } - switch( tokenType ){ - case TK_SPACE: { - if( db->u1.isInterrupted ){ - sqlite3ErrorMsg(pParse, "interrupt"); - pParse->rc = SQLITE_INTERRUPT; - goto abort_parse; - } + if( tokenType>=TK_SPACE ){ + assert( tokenType==TK_SPACE || tokenType==TK_ILLEGAL ); + if( db->u1.isInterrupted ){ + sqlite3ErrorMsg(pParse, "interrupt"); + pParse->rc = SQLITE_INTERRUPT; break; } - case TK_ILLEGAL: { - sqlite3DbFree(db, *pzErrMsg); - *pzErrMsg = sqlite3MPrintf(db, "unrecognized token: \"%T\"", + if( tokenType==TK_ILLEGAL ){ + sqlite3ErrorMsg(pParse, "unrecognized token: \"%T\"", &pParse->sLastToken); - nErr++; - goto abort_parse; - } - case TK_SEMI: { - pParse->zTail = &zSql[i]; - /* Fall thru into the default case */ - } - default: { - sqlite3Parser(pEngine, tokenType, pParse->sLastToken, pParse); - lastTokenParsed = tokenType; - if( pParse->rc!=SQLITE_OK ){ - goto abort_parse; - } break; } + }else{ + if( tokenType==TK_SEMI ) pParse->zTail = &zSql[i]; + sqlite3Parser(pEngine, tokenType, pParse->sLastToken, pParse); + lastTokenParsed = tokenType; + if( pParse->rc!=SQLITE_OK || db->mallocFailed ) break; } } -abort_parse: - if( zSql[i]==0 && nErr==0 && pParse->rc==SQLITE_OK ){ + assert( nErr==0 ); + if( pParse->rc==SQLITE_OK && db->mallocFailed==0 ){ + assert( zSql[i]==0 ); if( lastTokenParsed!=TK_SEMI ){ sqlite3Parser(pEngine, TK_SEMI, pParse->sLastToken, pParse); pParse->zTail = &zSql[i]; } - sqlite3Parser(pEngine, 0, pParse->sLastToken, pParse); + if( pParse->rc==SQLITE_OK && db->mallocFailed==0 ){ + sqlite3Parser(pEngine, 0, pParse->sLastToken, pParse); + } } #ifdef YYTRACKMAXSTACKDEPTH - sqlite3StatusSet(SQLITE_STATUS_PARSER_STACK, + sqlite3_mutex_enter(sqlite3MallocMutex()); + sqlite3StatusHighwater(SQLITE_STATUS_PARSER_STACK, sqlite3ParserStackPeak(pEngine) ); + sqlite3_mutex_leave(sqlite3MallocMutex()); #endif /* YYDEBUG */ sqlite3ParserFree(pEngine, sqlite3_free); db->lookaside.bEnabled = enableLookaside; @@ -120651,7 +131622,7 @@ abort_parse: pParse->rc = SQLITE_NOMEM; } if( pParse->rc!=SQLITE_OK && pParse->rc!=SQLITE_DONE && pParse->zErrMsg==0 ){ - sqlite3SetString(&pParse->zErrMsg, db, "%s", sqlite3ErrStr(pParse->rc)); + pParse->zErrMsg = sqlite3MPrintf(db, "%s", sqlite3ErrStr(pParse->rc)); } assert( pzErrMsg!=0 ); if( pParse->zErrMsg ){ @@ -120683,7 +131654,7 @@ abort_parse: sqlite3DeleteTable(db, pParse->pNewTable); } - if( pParse->bFreeWith ) sqlite3WithDelete(db, pParse->pWith); + sqlite3WithDelete(db, pParse->pWithToFree); sqlite3DeleteTrigger(db, pParse->pNewTrigger); for(i=pParse->nzVar-1; i>=0; i--) sqlite3DbFree(db, pParse->azVar[i]); sqlite3DbFree(db, pParse->azVar); @@ -120697,9 +131668,7 @@ abort_parse: pParse->pZombieTab = p->pNextZombie; sqlite3DeleteTable(db, p); } - if( nErr>0 && pParse->rc==SQLITE_OK ){ - pParse->rc = SQLITE_ERROR; - } + assert( nErr==0 || pParse->rc!=SQLITE_OK ); return nErr; } @@ -120723,6 +131692,7 @@ abort_parse: ** separating it out, the code will be automatically omitted from ** static links that do not use it. */ +/* #include "sqliteInt.h" */ #ifndef SQLITE_OMIT_COMPLETE /* @@ -120776,7 +131746,7 @@ SQLITE_PRIVATE const char sqlite3IsEbcdicIdChar[]; ** a statement. ** ** (4) CREATE The keyword CREATE has been seen at the beginning of a -** statement, possibly preceeded by EXPLAIN and/or followed by +** statement, possibly preceded by EXPLAIN and/or followed by ** TEMP or TEMPORARY ** ** (5) TRIGGER We are in the middle of a trigger definition that must be @@ -120786,7 +131756,7 @@ SQLITE_PRIVATE const char sqlite3IsEbcdicIdChar[]; ** the end of a trigger definition. ** ** (7) END We've seen the ";END" of the ";END;" that occurs at the end -** of a trigger difinition. +** of a trigger definition. ** ** Transitions between states above are determined by tokens extracted ** from the input. The following tokens are significant: @@ -120807,7 +131777,7 @@ SQLITE_PRIVATE const char sqlite3IsEbcdicIdChar[]; ** to recognize the end of a trigger can be omitted. All we have to do ** is look for a semicolon that is not part of an string or comment. */ -SQLITE_API int sqlite3_complete(const char *zSql){ +SQLITE_API int SQLITE_STDCALL sqlite3_complete(const char *zSql){ u8 state = 0; /* Current state, using numbers defined in header comment */ u8 token; /* Value of the next token */ @@ -120829,7 +131799,7 @@ SQLITE_API int sqlite3_complete(const char *zSql){ }; #else /* If triggers are not supported by this compile then the statement machine - ** used to detect the end of a statement is much simplier + ** used to detect the end of a statement is much simpler */ static const u8 trans[3][3] = { /* Token: */ @@ -120840,6 +131810,13 @@ SQLITE_API int sqlite3_complete(const char *zSql){ }; #endif /* SQLITE_OMIT_TRIGGER */ +#ifdef SQLITE_ENABLE_API_ARMOR + if( zSql==0 ){ + (void)SQLITE_MISUSE_BKPT; + return 0; + } +#endif + while( *zSql ){ switch( *zSql ){ case ';': { /* A semicolon */ @@ -120965,10 +131942,10 @@ SQLITE_API int sqlite3_complete(const char *zSql){ ** above, except that the parameter is required to be UTF-16 encoded, not ** UTF-8. */ -SQLITE_API int sqlite3_complete16(const void *zSql){ +SQLITE_API int SQLITE_STDCALL sqlite3_complete16(const void *zSql){ sqlite3_value *pVal; char const *zSql8; - int rc = SQLITE_NOMEM; + int rc; #ifndef SQLITE_OMIT_AUTOINIT rc = sqlite3_initialize(); @@ -120983,7 +131960,7 @@ SQLITE_API int sqlite3_complete16(const void *zSql){ rc = SQLITE_NOMEM; } sqlite3ValueFree(pVal); - return sqlite3ApiExit(0, rc); + return rc & 0xff; } #endif /* SQLITE_OMIT_UTF16 */ #endif /* SQLITE_OMIT_COMPLETE */ @@ -121006,6 +131983,7 @@ SQLITE_API int sqlite3_complete16(const void *zSql){ ** other files are for internal use by SQLite and should not be ** accessed by users of the library. */ +/* #include "sqliteInt.h" */ #ifdef SQLITE_ENABLE_FTS3 /************** Include fts3.h in the middle of main.c ***********************/ @@ -121025,6 +132003,7 @@ SQLITE_API int sqlite3_complete16(const void *zSql){ ** This header file is used by programs that want to link against the ** FTS3 library. All it does is declare the sqlite3Fts3Init() interface. */ +/* #include "sqlite3.h" */ #if 0 extern "C" { @@ -121057,6 +132036,7 @@ SQLITE_PRIVATE int sqlite3Fts3Init(sqlite3 *db); ** This header file is used by programs that want to link against the ** RTREE library. All it does is declare the sqlite3RtreeInit() interface. */ +/* #include "sqlite3.h" */ #if 0 extern "C" { @@ -121089,6 +132069,7 @@ SQLITE_PRIVATE int sqlite3RtreeInit(sqlite3 *db); ** This header file is used by programs that want to link against the ** ICU extension. All it does is declare the sqlite3IcuInit() interface. */ +/* #include "sqlite3.h" */ #if 0 extern "C" { @@ -121104,6 +132085,12 @@ SQLITE_PRIVATE int sqlite3IcuInit(sqlite3 *db); /************** End of sqliteicu.h *******************************************/ /************** Continuing where we left off in main.c ***********************/ #endif +#ifdef SQLITE_ENABLE_JSON1 +SQLITE_PRIVATE int sqlite3Json1Init(sqlite3*); +#endif +#ifdef SQLITE_ENABLE_FTS5 +SQLITE_PRIVATE int sqlite3Fts5Init(sqlite3*); +#endif #ifndef SQLITE_AMALGAMATION /* IMPLEMENTATION-OF: R-46656-45156 The sqlite3_version[] string constant @@ -121115,24 +132102,36 @@ SQLITE_API const char sqlite3_version[] = SQLITE_VERSION; /* IMPLEMENTATION-OF: R-53536-42575 The sqlite3_libversion() function returns ** a pointer to the to the sqlite3_version[] string constant. */ -SQLITE_API const char *sqlite3_libversion(void){ return sqlite3_version; } +SQLITE_API const char *SQLITE_STDCALL sqlite3_libversion(void){ return sqlite3_version; } /* IMPLEMENTATION-OF: R-63124-39300 The sqlite3_sourceid() function returns a ** pointer to a string constant whose value is the same as the ** SQLITE_SOURCE_ID C preprocessor macro. */ -SQLITE_API const char *sqlite3_sourceid(void){ return SQLITE_SOURCE_ID; } +SQLITE_API const char *SQLITE_STDCALL sqlite3_sourceid(void){ return SQLITE_SOURCE_ID; } /* IMPLEMENTATION-OF: R-35210-63508 The sqlite3_libversion_number() function ** returns an integer equal to SQLITE_VERSION_NUMBER. */ -SQLITE_API int sqlite3_libversion_number(void){ return SQLITE_VERSION_NUMBER; } +SQLITE_API int SQLITE_STDCALL sqlite3_libversion_number(void){ return SQLITE_VERSION_NUMBER; } /* IMPLEMENTATION-OF: R-20790-14025 The sqlite3_threadsafe() function returns ** zero if and only if SQLite was compiled with mutexing code omitted due to ** the SQLITE_THREADSAFE compile-time option being set to 0. */ -SQLITE_API int sqlite3_threadsafe(void){ return SQLITE_THREADSAFE; } +SQLITE_API int SQLITE_STDCALL sqlite3_threadsafe(void){ return SQLITE_THREADSAFE; } + +/* +** When compiling the test fixture or with debugging enabled (on Win32), +** this variable being set to non-zero will cause OSTRACE macros to emit +** extra diagnostic information. +*/ +#ifdef SQLITE_HAVE_OS_TRACE +# ifndef SQLITE_DEBUG_OS_TRACE +# define SQLITE_DEBUG_OS_TRACE 0 +# endif + int sqlite3OSTrace = SQLITE_DEBUG_OS_TRACE; +#endif #if !defined(SQLITE_OMIT_TRACE) && defined(SQLITE_ENABLE_IOTRACE) /* @@ -121141,7 +132140,7 @@ SQLITE_API int sqlite3_threadsafe(void){ return SQLITE_THREADSAFE; } ** I/O active are written using this function. These messages ** are intended for debugging activity only. */ -SQLITE_PRIVATE void (*sqlite3IoTrace)(const char*, ...) = 0; +SQLITE_API void (SQLITE_CDECL *sqlite3IoTrace)(const char*, ...) = 0; #endif /* @@ -121193,7 +132192,7 @@ SQLITE_API char *sqlite3_data_directory = 0; ** * Recursive calls to this routine from thread X return immediately ** without blocking. */ -SQLITE_API int sqlite3_initialize(void){ +SQLITE_API int SQLITE_STDCALL sqlite3_initialize(void){ MUTEX_LOGIC( sqlite3_mutex *pMaster; ) /* The main static mutex */ int rc; /* Result code */ #ifdef SQLITE_EXTRA_INIT @@ -121207,6 +132206,11 @@ SQLITE_API int sqlite3_initialize(void){ } #endif + /* If the following assert() fails on some obscure processor/compiler + ** combination, the work-around is to set the correct pointer + ** size at compile-time using -DSQLITE_PTRSIZE=n compile-time option */ + assert( SQLITE_PTRSIZE==sizeof(char*) ); + /* If SQLite is already completely initialized, then this call ** to sqlite3_initialize() should be a no-op. But the initialization ** must be complete. So isInit must not be set until the very end @@ -121276,6 +132280,12 @@ SQLITE_API int sqlite3_initialize(void){ if( sqlite3GlobalConfig.isInit==0 && sqlite3GlobalConfig.inProgress==0 ){ FuncDefHash *pHash = &GLOBAL(FuncDefHash, sqlite3GlobalFunctions); sqlite3GlobalConfig.inProgress = 1; +#ifdef SQLITE_ENABLE_SQLLOG + { + extern void sqlite3_init_sqllog(void); + sqlite3_init_sqllog(); + } +#endif memset(pHash, 0, sizeof(sqlite3GlobalFunctions)); sqlite3RegisterGlobalFunctions(); if( sqlite3GlobalConfig.isPCacheInit==0 ){ @@ -121349,7 +132359,14 @@ SQLITE_API int sqlite3_initialize(void){ ** on when SQLite is already shut down. If SQLite is already shut down ** when this routine is invoked, then this routine is a harmless no-op. */ -SQLITE_API int sqlite3_shutdown(void){ +SQLITE_API int SQLITE_STDCALL sqlite3_shutdown(void){ +#ifdef SQLITE_OMIT_WSD + int rc = sqlite3_wsd_init(4096, 24); + if( rc!=SQLITE_OK ){ + return rc; + } +#endif + if( sqlite3GlobalConfig.isInit ){ #ifdef SQLITE_EXTRA_SHUTDOWN void SQLITE_EXTRA_SHUTDOWN(void); @@ -121396,7 +132413,7 @@ SQLITE_API int sqlite3_shutdown(void){ ** threadsafe. Failure to heed these warnings can lead to unpredictable ** behavior. */ -SQLITE_API int sqlite3_config(int op, ...){ +SQLITE_API int SQLITE_CDECL sqlite3_config(int op, ...){ va_list ap; int rc = SQLITE_OK; @@ -121408,33 +132425,43 @@ SQLITE_API int sqlite3_config(int op, ...){ switch( op ){ /* Mutex configuration options are only available in a threadsafe - ** compile. + ** compile. */ -#if defined(SQLITE_THREADSAFE) && SQLITE_THREADSAFE>0 +#if defined(SQLITE_THREADSAFE) && SQLITE_THREADSAFE>0 /* IMP: R-54466-46756 */ case SQLITE_CONFIG_SINGLETHREAD: { - /* Disable all mutexing */ - sqlite3GlobalConfig.bCoreMutex = 0; - sqlite3GlobalConfig.bFullMutex = 0; + /* EVIDENCE-OF: R-02748-19096 This option sets the threading mode to + ** Single-thread. */ + sqlite3GlobalConfig.bCoreMutex = 0; /* Disable mutex on core */ + sqlite3GlobalConfig.bFullMutex = 0; /* Disable mutex on connections */ break; } +#endif +#if defined(SQLITE_THREADSAFE) && SQLITE_THREADSAFE>0 /* IMP: R-20520-54086 */ case SQLITE_CONFIG_MULTITHREAD: { - /* Disable mutexing of database connections */ - /* Enable mutexing of core data structures */ - sqlite3GlobalConfig.bCoreMutex = 1; - sqlite3GlobalConfig.bFullMutex = 0; + /* EVIDENCE-OF: R-14374-42468 This option sets the threading mode to + ** Multi-thread. */ + sqlite3GlobalConfig.bCoreMutex = 1; /* Enable mutex on core */ + sqlite3GlobalConfig.bFullMutex = 0; /* Disable mutex on connections */ break; } +#endif +#if defined(SQLITE_THREADSAFE) && SQLITE_THREADSAFE>0 /* IMP: R-59593-21810 */ case SQLITE_CONFIG_SERIALIZED: { - /* Enable all mutexing */ - sqlite3GlobalConfig.bCoreMutex = 1; - sqlite3GlobalConfig.bFullMutex = 1; + /* EVIDENCE-OF: R-41220-51800 This option sets the threading mode to + ** Serialized. */ + sqlite3GlobalConfig.bCoreMutex = 1; /* Enable mutex on core */ + sqlite3GlobalConfig.bFullMutex = 1; /* Enable mutex on connections */ break; } +#endif +#if defined(SQLITE_THREADSAFE) && SQLITE_THREADSAFE>0 /* IMP: R-63666-48755 */ case SQLITE_CONFIG_MUTEX: { /* Specify an alternative mutex implementation */ sqlite3GlobalConfig.mutex = *va_arg(ap, sqlite3_mutex_methods*); break; } +#endif +#if defined(SQLITE_THREADSAFE) && SQLITE_THREADSAFE>0 /* IMP: R-14450-37597 */ case SQLITE_CONFIG_GETMUTEX: { /* Retrieve the current mutex implementation */ *va_arg(ap, sqlite3_mutex_methods*) = sqlite3GlobalConfig.mutex; @@ -121442,37 +132469,62 @@ SQLITE_API int sqlite3_config(int op, ...){ } #endif - case SQLITE_CONFIG_MALLOC: { - /* Specify an alternative malloc implementation */ + /* EVIDENCE-OF: R-55594-21030 The SQLITE_CONFIG_MALLOC option takes a + ** single argument which is a pointer to an instance of the + ** sqlite3_mem_methods structure. The argument specifies alternative + ** low-level memory allocation routines to be used in place of the memory + ** allocation routines built into SQLite. */ sqlite3GlobalConfig.m = *va_arg(ap, sqlite3_mem_methods*); break; } case SQLITE_CONFIG_GETMALLOC: { - /* Retrieve the current malloc() implementation */ + /* EVIDENCE-OF: R-51213-46414 The SQLITE_CONFIG_GETMALLOC option takes a + ** single argument which is a pointer to an instance of the + ** sqlite3_mem_methods structure. The sqlite3_mem_methods structure is + ** filled with the currently defined memory allocation routines. */ if( sqlite3GlobalConfig.m.xMalloc==0 ) sqlite3MemSetDefault(); *va_arg(ap, sqlite3_mem_methods*) = sqlite3GlobalConfig.m; break; } case SQLITE_CONFIG_MEMSTATUS: { - /* Enable or disable the malloc status collection */ + /* EVIDENCE-OF: R-61275-35157 The SQLITE_CONFIG_MEMSTATUS option takes + ** single argument of type int, interpreted as a boolean, which enables + ** or disables the collection of memory allocation statistics. */ sqlite3GlobalConfig.bMemstat = va_arg(ap, int); break; } case SQLITE_CONFIG_SCRATCH: { - /* Designate a buffer for scratch memory space */ + /* EVIDENCE-OF: R-08404-60887 There are three arguments to + ** SQLITE_CONFIG_SCRATCH: A pointer an 8-byte aligned memory buffer from + ** which the scratch allocations will be drawn, the size of each scratch + ** allocation (sz), and the maximum number of scratch allocations (N). */ sqlite3GlobalConfig.pScratch = va_arg(ap, void*); sqlite3GlobalConfig.szScratch = va_arg(ap, int); sqlite3GlobalConfig.nScratch = va_arg(ap, int); break; } case SQLITE_CONFIG_PAGECACHE: { - /* Designate a buffer for page cache memory space */ + /* EVIDENCE-OF: R-18761-36601 There are three arguments to + ** SQLITE_CONFIG_PAGECACHE: A pointer to 8-byte aligned memory (pMem), + ** the size of each page cache line (sz), and the number of cache lines + ** (N). */ sqlite3GlobalConfig.pPage = va_arg(ap, void*); sqlite3GlobalConfig.szPage = va_arg(ap, int); sqlite3GlobalConfig.nPage = va_arg(ap, int); break; } + case SQLITE_CONFIG_PCACHE_HDRSZ: { + /* EVIDENCE-OF: R-39100-27317 The SQLITE_CONFIG_PCACHE_HDRSZ option takes + ** a single parameter which is a pointer to an integer and writes into + ** that integer the number of extra bytes per page required for each page + ** in SQLITE_CONFIG_PAGECACHE. */ + *va_arg(ap, int*) = + sqlite3HeaderSizeBtree() + + sqlite3HeaderSizePcache() + + sqlite3HeaderSizePcache1(); + break; + } case SQLITE_CONFIG_PCACHE: { /* no-op */ @@ -121485,11 +132537,18 @@ SQLITE_API int sqlite3_config(int op, ...){ } case SQLITE_CONFIG_PCACHE2: { - /* Specify an alternative page cache implementation */ + /* EVIDENCE-OF: R-63325-48378 The SQLITE_CONFIG_PCACHE2 option takes a + ** single argument which is a pointer to an sqlite3_pcache_methods2 + ** object. This object specifies the interface to a custom page cache + ** implementation. */ sqlite3GlobalConfig.pcache2 = *va_arg(ap, sqlite3_pcache_methods2*); break; } case SQLITE_CONFIG_GETPCACHE2: { + /* EVIDENCE-OF: R-22035-46182 The SQLITE_CONFIG_GETPCACHE2 option takes a + ** single argument which is a pointer to an sqlite3_pcache_methods2 + ** object. SQLite copies of the current page cache implementation into + ** that object. */ if( sqlite3GlobalConfig.pcache2.xInit==0 ){ sqlite3PCacheSetDefault(); } @@ -121497,9 +132556,15 @@ SQLITE_API int sqlite3_config(int op, ...){ break; } +/* EVIDENCE-OF: R-06626-12911 The SQLITE_CONFIG_HEAP option is only +** available if SQLite is compiled with either SQLITE_ENABLE_MEMSYS3 or +** SQLITE_ENABLE_MEMSYS5 and returns SQLITE_ERROR if invoked otherwise. */ #if defined(SQLITE_ENABLE_MEMSYS3) || defined(SQLITE_ENABLE_MEMSYS5) case SQLITE_CONFIG_HEAP: { - /* Designate a buffer for heap memory space */ + /* EVIDENCE-OF: R-19854-42126 There are three arguments to + ** SQLITE_CONFIG_HEAP: An 8-byte aligned pointer to the memory, the + ** number of bytes in the memory buffer, and the minimum allocation size. + */ sqlite3GlobalConfig.pHeap = va_arg(ap, void*); sqlite3GlobalConfig.nHeap = va_arg(ap, int); sqlite3GlobalConfig.mnReq = va_arg(ap, int); @@ -121512,17 +132577,19 @@ SQLITE_API int sqlite3_config(int op, ...){ } if( sqlite3GlobalConfig.pHeap==0 ){ - /* If the heap pointer is NULL, then restore the malloc implementation - ** back to NULL pointers too. This will cause the malloc to go - ** back to its default implementation when sqlite3_initialize() is - ** run. + /* EVIDENCE-OF: R-49920-60189 If the first pointer (the memory pointer) + ** is NULL, then SQLite reverts to using its default memory allocator + ** (the system malloc() implementation), undoing any prior invocation of + ** SQLITE_CONFIG_MALLOC. + ** + ** Setting sqlite3GlobalConfig.m to all zeros will cause malloc to + ** revert to its default implementation when sqlite3_initialize() is run */ memset(&sqlite3GlobalConfig.m, 0, sizeof(sqlite3GlobalConfig.m)); }else{ - /* The heap pointer is not NULL, then install one of the - ** mem5.c/mem3.c methods. The enclosing #if guarantees at - ** least one of these methods is currently enabled. - */ + /* EVIDENCE-OF: R-61006-08918 If the memory pointer is not NULL then the + ** alternative memory allocator is engaged to handle all of SQLites + ** memory allocation needs. */ #ifdef SQLITE_ENABLE_MEMSYS3 sqlite3GlobalConfig.m = *sqlite3MemGetMemsys3(); #endif @@ -121555,12 +132622,25 @@ SQLITE_API int sqlite3_config(int op, ...){ break; } + /* EVIDENCE-OF: R-55548-33817 The compile-time setting for URI filenames + ** can be changed at start-time using the + ** sqlite3_config(SQLITE_CONFIG_URI,1) or + ** sqlite3_config(SQLITE_CONFIG_URI,0) configuration calls. + */ case SQLITE_CONFIG_URI: { + /* EVIDENCE-OF: R-25451-61125 The SQLITE_CONFIG_URI option takes a single + ** argument of type int. If non-zero, then URI handling is globally + ** enabled. If the parameter is zero, then URI handling is globally + ** disabled. */ sqlite3GlobalConfig.bOpenUri = va_arg(ap, int); break; } case SQLITE_CONFIG_COVERING_INDEX_SCAN: { + /* EVIDENCE-OF: R-36592-02772 The SQLITE_CONFIG_COVERING_INDEX_SCAN + ** option takes a single integer argument which is interpreted as a + ** boolean in order to enable or disable the use of covering indices for + ** full table scans in the query optimizer. */ sqlite3GlobalConfig.bUseCis = va_arg(ap, int); break; } @@ -121575,25 +132655,45 @@ SQLITE_API int sqlite3_config(int op, ...){ #endif case SQLITE_CONFIG_MMAP_SIZE: { + /* EVIDENCE-OF: R-58063-38258 SQLITE_CONFIG_MMAP_SIZE takes two 64-bit + ** integer (sqlite3_int64) values that are the default mmap size limit + ** (the default setting for PRAGMA mmap_size) and the maximum allowed + ** mmap size limit. */ sqlite3_int64 szMmap = va_arg(ap, sqlite3_int64); sqlite3_int64 mxMmap = va_arg(ap, sqlite3_int64); + /* EVIDENCE-OF: R-53367-43190 If either argument to this option is + ** negative, then that argument is changed to its compile-time default. + ** + ** EVIDENCE-OF: R-34993-45031 The maximum allowed mmap size will be + ** silently truncated if necessary so that it does not exceed the + ** compile-time maximum mmap size set by the SQLITE_MAX_MMAP_SIZE + ** compile-time option. + */ if( mxMmap<0 || mxMmap>SQLITE_MAX_MMAP_SIZE ){ mxMmap = SQLITE_MAX_MMAP_SIZE; } - sqlite3GlobalConfig.mxMmap = mxMmap; if( szMmap<0 ) szMmap = SQLITE_DEFAULT_MMAP_SIZE; if( szMmap>mxMmap) szMmap = mxMmap; + sqlite3GlobalConfig.mxMmap = mxMmap; sqlite3GlobalConfig.szMmap = szMmap; break; } -#if SQLITE_OS_WIN && defined(SQLITE_WIN32_MALLOC) +#if SQLITE_OS_WIN && defined(SQLITE_WIN32_MALLOC) /* IMP: R-04780-55815 */ case SQLITE_CONFIG_WIN32_HEAPSIZE: { + /* EVIDENCE-OF: R-34926-03360 SQLITE_CONFIG_WIN32_HEAPSIZE takes a 32-bit + ** unsigned integer value that specifies the maximum size of the created + ** heap. */ sqlite3GlobalConfig.nHeap = va_arg(ap, int); break; } #endif + case SQLITE_CONFIG_PMASZ: { + sqlite3GlobalConfig.szPma = va_arg(ap, unsigned int); + break; + } + default: { rc = SQLITE_ERROR; break; @@ -121615,6 +132715,7 @@ SQLITE_API int sqlite3_config(int op, ...){ ** the lookaside memory. */ static int setupLookaside(sqlite3 *db, void *pBuf, int sz, int cnt){ +#ifndef SQLITE_OMIT_LOOKASIDE void *pStart; if( db->lookaside.nOut ){ return SQLITE_BUSY; @@ -121665,13 +132766,20 @@ static int setupLookaside(sqlite3 *db, void *pBuf, int sz, int cnt){ db->lookaside.bEnabled = 0; db->lookaside.bMalloced = 0; } +#endif /* SQLITE_OMIT_LOOKASIDE */ return SQLITE_OK; } /* ** Return the mutex associated with a database connection. */ -SQLITE_API sqlite3_mutex *sqlite3_db_mutex(sqlite3 *db){ +SQLITE_API sqlite3_mutex *SQLITE_STDCALL sqlite3_db_mutex(sqlite3 *db){ +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ){ + (void)SQLITE_MISUSE_BKPT; + return 0; + } +#endif return db->mutex; } @@ -121679,8 +132787,12 @@ SQLITE_API sqlite3_mutex *sqlite3_db_mutex(sqlite3 *db){ ** Free up as much memory as we can from the given database ** connection. */ -SQLITE_API int sqlite3_db_release_memory(sqlite3 *db){ +SQLITE_API int SQLITE_STDCALL sqlite3_db_release_memory(sqlite3 *db){ int i; + +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ) return SQLITE_MISUSE_BKPT; +#endif sqlite3_mutex_enter(db->mutex); sqlite3BtreeEnterAll(db); for(i=0; inDb; i++){ @@ -121695,10 +132807,40 @@ SQLITE_API int sqlite3_db_release_memory(sqlite3 *db){ return SQLITE_OK; } +/* +** Flush any dirty pages in the pager-cache for any attached database +** to disk. +*/ +SQLITE_API int SQLITE_STDCALL sqlite3_db_cacheflush(sqlite3 *db){ + int i; + int rc = SQLITE_OK; + int bSeenBusy = 0; + +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ) return SQLITE_MISUSE_BKPT; +#endif + sqlite3_mutex_enter(db->mutex); + sqlite3BtreeEnterAll(db); + for(i=0; rc==SQLITE_OK && inDb; i++){ + Btree *pBt = db->aDb[i].pBt; + if( pBt && sqlite3BtreeIsInTrans(pBt) ){ + Pager *pPager = sqlite3BtreePager(pBt); + rc = sqlite3PagerFlush(pPager); + if( rc==SQLITE_BUSY ){ + bSeenBusy = 1; + rc = SQLITE_OK; + } + } + } + sqlite3BtreeLeaveAll(db); + sqlite3_mutex_leave(db->mutex); + return ((rc==SQLITE_OK && bSeenBusy) ? SQLITE_BUSY : rc); +} + /* ** Configuration settings for an individual database connection */ -SQLITE_API int sqlite3_db_config(sqlite3 *db, int op, ...){ +SQLITE_API int SQLITE_CDECL sqlite3_db_config(sqlite3 *db, int op, ...){ va_list ap; int rc; va_start(ap, op); @@ -121770,13 +132912,20 @@ static int binCollFunc( ){ int rc, n; n = nKey1lastRowid; } /* ** Return the number of changes in the most recent call to sqlite3_exec(). */ -SQLITE_API int sqlite3_changes(sqlite3 *db){ +SQLITE_API int SQLITE_STDCALL sqlite3_changes(sqlite3 *db){ +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ){ + (void)SQLITE_MISUSE_BKPT; + return 0; + } +#endif return db->nChange; } /* ** Return the number of changes since the database handle was opened. */ -SQLITE_API int sqlite3_total_changes(sqlite3 *db){ +SQLITE_API int SQLITE_STDCALL sqlite3_total_changes(sqlite3 *db){ +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ){ + (void)SQLITE_MISUSE_BKPT; + return 0; + } +#endif return db->nTotalChange; } @@ -121868,17 +133035,23 @@ static void functionDestroy(sqlite3 *db, FuncDef *p){ static void disconnectAllVtab(sqlite3 *db){ #ifndef SQLITE_OMIT_VIRTUALTABLE int i; + HashElem *p; sqlite3BtreeEnterAll(db); for(i=0; inDb; i++){ Schema *pSchema = db->aDb[i].pSchema; if( db->aDb[i].pSchema ){ - HashElem *p; for(p=sqliteHashFirst(&pSchema->tblHash); p; p=sqliteHashNext(p)){ Table *pTab = (Table *)sqliteHashData(p); if( IsVirtual(pTab) ) sqlite3VtabDisconnect(db, pTab); } } } + for(p=sqliteHashFirst(&db->aModule); p; p=sqliteHashNext(p)){ + Module *pMod = (Module *)sqliteHashData(p); + if( pMod->pEpoTab ){ + sqlite3VtabDisconnect(db, pMod->pEpoTab); + } + } sqlite3VtabUnlockList(db); sqlite3BtreeLeaveAll(db); #else @@ -121906,6 +133079,8 @@ static int connectionIsBusy(sqlite3 *db){ */ static int sqlite3Close(sqlite3 *db, int forceZombie){ if( !db ){ + /* EVIDENCE-OF: R-63257-11740 Calling sqlite3_close() or + ** sqlite3_close_v2() with a NULL pointer argument is a harmless no-op. */ return SQLITE_OK; } if( !sqlite3SafetyCheckSickOrOk(db) ){ @@ -121929,7 +133104,7 @@ static int sqlite3Close(sqlite3 *db, int forceZombie){ ** SQLITE_BUSY if the connection can not be closed immediately. */ if( !forceZombie && connectionIsBusy(db) ){ - sqlite3Error(db, SQLITE_BUSY, "unable to close due to unfinalized " + sqlite3ErrorWithMsg(db, SQLITE_BUSY, "unable to close due to unfinalized " "statements or unfinished backups"); sqlite3_mutex_leave(db->mutex); return SQLITE_BUSY; @@ -121958,8 +133133,8 @@ static int sqlite3Close(sqlite3 *db, int forceZombie){ ** unclosed resources, and arranges for deallocation when the last ** prepare statement or sqlite3_backup closes. */ -SQLITE_API int sqlite3_close(sqlite3 *db){ return sqlite3Close(db,0); } -SQLITE_API int sqlite3_close_v2(sqlite3 *db){ return sqlite3Close(db,1); } +SQLITE_API int SQLITE_STDCALL sqlite3_close(sqlite3 *db){ return sqlite3Close(db,0); } +SQLITE_API int SQLITE_STDCALL sqlite3_close_v2(sqlite3 *db){ return sqlite3Close(db,1); } /* @@ -122054,14 +133229,19 @@ SQLITE_PRIVATE void sqlite3LeaveMutexAndCloseZombie(sqlite3 *db){ if( pMod->xDestroy ){ pMod->xDestroy(pMod->pAux); } + sqlite3VtabEponymousTableClear(db, pMod); sqlite3DbFree(db, pMod); } sqlite3HashClear(&db->aModule); #endif - sqlite3Error(db, SQLITE_OK, 0); /* Deallocates any cached error strings. */ + sqlite3Error(db, SQLITE_OK); /* Deallocates any cached error strings. */ sqlite3ValueFree(db->pErr); sqlite3CloseExtensions(db); +#if SQLITE_USER_AUTHENTICATION + sqlite3_free(db->auth.zAuthUser); + sqlite3_free(db->auth.zAuthPW); +#endif db->magic = SQLITE_MAGIC_ERROR; @@ -122084,13 +133264,15 @@ SQLITE_PRIVATE void sqlite3LeaveMutexAndCloseZombie(sqlite3 *db){ /* ** Rollback all database files. If tripCode is not SQLITE_OK, then -** any open cursors are invalidated ("tripped" - as in "tripping a circuit +** any write cursors are invalidated ("tripped" - as in "tripping a circuit ** breaker") and made to return tripCode if there are any further -** attempts to use that cursor. +** attempts to use that cursor. Read cursors remain open and valid +** but are "saved" in case the table pages are moved around. */ SQLITE_PRIVATE void sqlite3RollbackAll(sqlite3 *db, int tripCode){ int i; int inTrans = 0; + int schemaChange; assert( sqlite3_mutex_held(db->mutex) ); sqlite3BeginBenignMalloc(); @@ -122101,6 +133283,7 @@ SQLITE_PRIVATE void sqlite3RollbackAll(sqlite3 *db, int tripCode){ ** the database rollback and schema reset, which can cause false ** corruption reports in some cases. */ sqlite3BtreeEnterAll(db); + schemaChange = (db->flags & SQLITE_InternChanges)!=0 && db->init.busy==0; for(i=0; inDb; i++){ Btree *p = db->aDb[i].pBt; @@ -122108,7 +133291,7 @@ SQLITE_PRIVATE void sqlite3RollbackAll(sqlite3 *db, int tripCode){ if( sqlite3BtreeIsInTrans(p) ){ inTrans = 1; } - sqlite3BtreeRollback(p, tripCode); + sqlite3BtreeRollback(p, tripCode, !schemaChange); } } sqlite3VtabRollback(db); @@ -122135,7 +133318,7 @@ SQLITE_PRIVATE void sqlite3RollbackAll(sqlite3 *db, int tripCode){ ** Return a static string containing the name corresponding to the error code ** specified in the argument. */ -#if defined(SQLITE_TEST) +#if defined(SQLITE_NEED_ERR_NAME) SQLITE_PRIVATE const char *sqlite3ErrName(int rc){ const char *zName = 0; int i, origRc = rc; @@ -122170,7 +133353,6 @@ SQLITE_PRIVATE const char *sqlite3ErrName(int rc){ case SQLITE_IOERR_UNLOCK: zName = "SQLITE_IOERR_UNLOCK"; break; case SQLITE_IOERR_RDLOCK: zName = "SQLITE_IOERR_RDLOCK"; break; case SQLITE_IOERR_DELETE: zName = "SQLITE_IOERR_DELETE"; break; - case SQLITE_IOERR_BLOCKED: zName = "SQLITE_IOERR_BLOCKED"; break; case SQLITE_IOERR_NOMEM: zName = "SQLITE_IOERR_NOMEM"; break; case SQLITE_IOERR_ACCESS: zName = "SQLITE_IOERR_ACCESS"; break; case SQLITE_IOERR_CHECKRESERVEDLOCK: @@ -122302,7 +133484,7 @@ static int sqliteDefaultBusyCallback( void *ptr, /* Database connection */ int count /* Number of times table has been busy */ ){ -#if SQLITE_OS_WIN || (defined(HAVE_USLEEP) && HAVE_USLEEP) +#if SQLITE_OS_WIN || HAVE_USLEEP static const u8 delays[] = { 1, 2, 5, 10, 15, 20, 25, 25, 25, 50, 50, 100 }; static const u8 totals[] = @@ -122360,11 +133542,14 @@ SQLITE_PRIVATE int sqlite3InvokeBusyHandler(BusyHandler *p){ ** This routine sets the busy callback for an Sqlite database to the ** given callback function with the given argument. */ -SQLITE_API int sqlite3_busy_handler( +SQLITE_API int SQLITE_STDCALL sqlite3_busy_handler( sqlite3 *db, int (*xBusy)(void*,int), void *pArg ){ +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ) return SQLITE_MISUSE_BKPT; +#endif sqlite3_mutex_enter(db->mutex); db->busyHandler.xFunc = xBusy; db->busyHandler.pArg = pArg; @@ -122380,12 +133565,18 @@ SQLITE_API int sqlite3_busy_handler( ** given callback function with the given argument. The progress callback will ** be invoked every nOps opcodes. */ -SQLITE_API void sqlite3_progress_handler( +SQLITE_API void SQLITE_STDCALL sqlite3_progress_handler( sqlite3 *db, int nOps, int (*xProgress)(void*), void *pArg ){ +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ){ + (void)SQLITE_MISUSE_BKPT; + return; + } +#endif sqlite3_mutex_enter(db->mutex); if( nOps>0 ){ db->xProgress = xProgress; @@ -122405,7 +133596,10 @@ SQLITE_API void sqlite3_progress_handler( ** This routine installs a default busy handler that waits for the ** specified number of milliseconds before returning 0. */ -SQLITE_API int sqlite3_busy_timeout(sqlite3 *db, int ms){ +SQLITE_API int SQLITE_STDCALL sqlite3_busy_timeout(sqlite3 *db, int ms){ +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ) return SQLITE_MISUSE_BKPT; +#endif if( ms>0 ){ sqlite3_busy_handler(db, sqliteDefaultBusyCallback, (void*)db); db->busyTimeout = ms; @@ -122418,7 +133612,13 @@ SQLITE_API int sqlite3_busy_timeout(sqlite3 *db, int ms){ /* ** Cause any pending operation to stop at its earliest opportunity. */ -SQLITE_API void sqlite3_interrupt(sqlite3 *db){ +SQLITE_API void SQLITE_STDCALL sqlite3_interrupt(sqlite3 *db){ +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ){ + (void)SQLITE_MISUSE_BKPT; + return; + } +#endif db->u1.isInterrupted = 1; } @@ -122493,7 +133693,7 @@ SQLITE_PRIVATE int sqlite3CreateFunc( p = sqlite3FindFunction(db, zFunctionName, nName, nArg, (u8)enc, 0); if( p && (p->funcFlags & SQLITE_FUNC_ENCMASK)==enc && p->nArg==nArg ){ if( db->nVdbeActive ){ - sqlite3Error(db, SQLITE_BUSY, + sqlite3ErrorWithMsg(db, SQLITE_BUSY, "unable to delete/modify user-function due to active statements"); assert( !db->mallocFailed ); return SQLITE_BUSY; @@ -122529,7 +133729,7 @@ SQLITE_PRIVATE int sqlite3CreateFunc( /* ** Create new user functions. */ -SQLITE_API int sqlite3_create_function( +SQLITE_API int SQLITE_STDCALL sqlite3_create_function( sqlite3 *db, const char *zFunc, int nArg, @@ -122543,7 +133743,7 @@ SQLITE_API int sqlite3_create_function( xFinal, 0); } -SQLITE_API int sqlite3_create_function_v2( +SQLITE_API int SQLITE_STDCALL sqlite3_create_function_v2( sqlite3 *db, const char *zFunc, int nArg, @@ -122556,6 +133756,12 @@ SQLITE_API int sqlite3_create_function_v2( ){ int rc = SQLITE_ERROR; FuncDestructor *pArg = 0; + +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ){ + return SQLITE_MISUSE_BKPT; + } +#endif sqlite3_mutex_enter(db->mutex); if( xDestroy ){ pArg = (FuncDestructor *)sqlite3DbMallocZero(db, sizeof(FuncDestructor)); @@ -122580,7 +133786,7 @@ SQLITE_API int sqlite3_create_function_v2( } #ifndef SQLITE_OMIT_UTF16 -SQLITE_API int sqlite3_create_function16( +SQLITE_API int SQLITE_STDCALL sqlite3_create_function16( sqlite3 *db, const void *zFunctionName, int nArg, @@ -122592,6 +133798,10 @@ SQLITE_API int sqlite3_create_function16( ){ int rc; char *zFunc8; + +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) || zFunctionName==0 ) return SQLITE_MISUSE_BKPT; +#endif sqlite3_mutex_enter(db->mutex); assert( !db->mallocFailed ); zFunc8 = sqlite3Utf16to8(db, zFunctionName, -1, SQLITE_UTF16NATIVE); @@ -122616,13 +133826,19 @@ SQLITE_API int sqlite3_create_function16( ** A global function must exist in order for name resolution to work ** properly. */ -SQLITE_API int sqlite3_overload_function( +SQLITE_API int SQLITE_STDCALL sqlite3_overload_function( sqlite3 *db, const char *zName, int nArg ){ int nName = sqlite3Strlen30(zName); int rc = SQLITE_OK; + +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) || zName==0 || nArg<-2 ){ + return SQLITE_MISUSE_BKPT; + } +#endif sqlite3_mutex_enter(db->mutex); if( sqlite3FindFunction(db, zName, nName, nArg, SQLITE_UTF8, 0)==0 ){ rc = sqlite3CreateFunc(db, zName, nArg, SQLITE_UTF8, @@ -122642,8 +133858,15 @@ SQLITE_API int sqlite3_overload_function( ** trace is a pointer to a function that is invoked at the start of each ** SQL statement. */ -SQLITE_API void *sqlite3_trace(sqlite3 *db, void (*xTrace)(void*,const char*), void *pArg){ +SQLITE_API void *SQLITE_STDCALL sqlite3_trace(sqlite3 *db, void (*xTrace)(void*,const char*), void *pArg){ void *pOld; + +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ){ + (void)SQLITE_MISUSE_BKPT; + return 0; + } +#endif sqlite3_mutex_enter(db->mutex); pOld = db->pTraceArg; db->xTrace = xTrace; @@ -122659,12 +133882,19 @@ SQLITE_API void *sqlite3_trace(sqlite3 *db, void (*xTrace)(void*,const char*), v ** profile is a pointer to a function that is invoked at the conclusion of ** each SQL statement that is run. */ -SQLITE_API void *sqlite3_profile( +SQLITE_API void *SQLITE_STDCALL sqlite3_profile( sqlite3 *db, void (*xProfile)(void*,const char*,sqlite_uint64), void *pArg ){ void *pOld; + +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ){ + (void)SQLITE_MISUSE_BKPT; + return 0; + } +#endif sqlite3_mutex_enter(db->mutex); pOld = db->pProfileArg; db->xProfile = xProfile; @@ -122679,12 +133909,19 @@ SQLITE_API void *sqlite3_profile( ** If the invoked function returns non-zero, then the commit becomes a ** rollback. */ -SQLITE_API void *sqlite3_commit_hook( +SQLITE_API void *SQLITE_STDCALL sqlite3_commit_hook( sqlite3 *db, /* Attach the hook to this database */ int (*xCallback)(void*), /* Function to invoke on each commit */ void *pArg /* Argument to the function */ ){ void *pOld; + +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ){ + (void)SQLITE_MISUSE_BKPT; + return 0; + } +#endif sqlite3_mutex_enter(db->mutex); pOld = db->pCommitArg; db->xCommitCallback = xCallback; @@ -122697,12 +133934,19 @@ SQLITE_API void *sqlite3_commit_hook( ** Register a callback to be invoked each time a row is updated, ** inserted or deleted using this database connection. */ -SQLITE_API void *sqlite3_update_hook( +SQLITE_API void *SQLITE_STDCALL sqlite3_update_hook( sqlite3 *db, /* Attach the hook to this database */ void (*xCallback)(void*,int,char const *,char const *,sqlite_int64), void *pArg /* Argument to the function */ ){ void *pRet; + +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ){ + (void)SQLITE_MISUSE_BKPT; + return 0; + } +#endif sqlite3_mutex_enter(db->mutex); pRet = db->pUpdateArg; db->xUpdateCallback = xCallback; @@ -122715,12 +133959,19 @@ SQLITE_API void *sqlite3_update_hook( ** Register a callback to be invoked each time a transaction is rolled ** back by this database connection. */ -SQLITE_API void *sqlite3_rollback_hook( +SQLITE_API void *SQLITE_STDCALL sqlite3_rollback_hook( sqlite3 *db, /* Attach the hook to this database */ void (*xCallback)(void*), /* Callback function */ void *pArg /* Argument to the function */ ){ void *pRet; + +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ){ + (void)SQLITE_MISUSE_BKPT; + return 0; + } +#endif sqlite3_mutex_enter(db->mutex); pRet = db->pRollbackArg; db->xRollbackCallback = xCallback; @@ -122762,11 +134013,14 @@ SQLITE_PRIVATE int sqlite3WalDefaultHook( ** using sqlite3_wal_hook() disables the automatic checkpoint mechanism ** configured by this function. */ -SQLITE_API int sqlite3_wal_autocheckpoint(sqlite3 *db, int nFrame){ +SQLITE_API int SQLITE_STDCALL sqlite3_wal_autocheckpoint(sqlite3 *db, int nFrame){ #ifdef SQLITE_OMIT_WAL UNUSED_PARAMETER(db); UNUSED_PARAMETER(nFrame); #else +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ) return SQLITE_MISUSE_BKPT; +#endif if( nFrame>0 ){ sqlite3_wal_hook(db, sqlite3WalDefaultHook, SQLITE_INT_TO_PTR(nFrame)); }else{ @@ -122780,13 +134034,19 @@ SQLITE_API int sqlite3_wal_autocheckpoint(sqlite3 *db, int nFrame){ ** Register a callback to be invoked each time a transaction is written ** into the write-ahead-log by this database connection. */ -SQLITE_API void *sqlite3_wal_hook( +SQLITE_API void *SQLITE_STDCALL sqlite3_wal_hook( sqlite3 *db, /* Attach the hook to this db handle */ int(*xCallback)(void *, sqlite3*, const char*, int), void *pArg /* First argument passed to xCallback() */ ){ #ifndef SQLITE_OMIT_WAL void *pRet; +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ){ + (void)SQLITE_MISUSE_BKPT; + return 0; + } +#endif sqlite3_mutex_enter(db->mutex); pRet = db->pWalArg; db->xWalCallback = xCallback; @@ -122801,7 +134061,7 @@ SQLITE_API void *sqlite3_wal_hook( /* ** Checkpoint database zDb. */ -SQLITE_API int sqlite3_wal_checkpoint_v2( +SQLITE_API int SQLITE_STDCALL sqlite3_wal_checkpoint_v2( sqlite3 *db, /* Database handle */ const char *zDb, /* Name of attached database (or NULL) */ int eMode, /* SQLITE_CHECKPOINT_* value */ @@ -122814,14 +134074,21 @@ SQLITE_API int sqlite3_wal_checkpoint_v2( int rc; /* Return code */ int iDb = SQLITE_MAX_ATTACHED; /* sqlite3.aDb[] index of db to checkpoint */ +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ) return SQLITE_MISUSE_BKPT; +#endif + /* Initialize the output variables to -1 in case an error occurs. */ if( pnLog ) *pnLog = -1; if( pnCkpt ) *pnCkpt = -1; - assert( SQLITE_CHECKPOINT_FULL>SQLITE_CHECKPOINT_PASSIVE ); - assert( SQLITE_CHECKPOINT_FULLSQLITE_CHECKPOINT_RESTART ){ + assert( SQLITE_CHECKPOINT_PASSIVE==0 ); + assert( SQLITE_CHECKPOINT_FULL==1 ); + assert( SQLITE_CHECKPOINT_RESTART==2 ); + assert( SQLITE_CHECKPOINT_TRUNCATE==3 ); + if( eModeSQLITE_CHECKPOINT_TRUNCATE ){ + /* EVIDENCE-OF: R-03996-12088 The M parameter must be a valid checkpoint + ** mode: */ return SQLITE_MISUSE; } @@ -122831,10 +134098,11 @@ SQLITE_API int sqlite3_wal_checkpoint_v2( } if( iDb<0 ){ rc = SQLITE_ERROR; - sqlite3Error(db, SQLITE_ERROR, "unknown database: %s", zDb); + sqlite3ErrorWithMsg(db, SQLITE_ERROR, "unknown database: %s", zDb); }else{ + db->busyHandler.nBusy = 0; rc = sqlite3Checkpoint(db, iDb, eMode, pnLog, pnCkpt); - sqlite3Error(db, rc, 0); + sqlite3Error(db, rc); } rc = sqlite3ApiExit(db, rc); sqlite3_mutex_leave(db->mutex); @@ -122848,8 +134116,10 @@ SQLITE_API int sqlite3_wal_checkpoint_v2( ** to contains a zero-length string, all attached databases are ** checkpointed. */ -SQLITE_API int sqlite3_wal_checkpoint(sqlite3 *db, const char *zDb){ - return sqlite3_wal_checkpoint_v2(db, zDb, SQLITE_CHECKPOINT_PASSIVE, 0, 0); +SQLITE_API int SQLITE_STDCALL sqlite3_wal_checkpoint(sqlite3 *db, const char *zDb){ + /* EVIDENCE-OF: R-41613-20553 The sqlite3_wal_checkpoint(D,X) is equivalent to + ** sqlite3_wal_checkpoint_v2(D,X,SQLITE_CHECKPOINT_PASSIVE,0,0). */ + return sqlite3_wal_checkpoint_v2(db,zDb,SQLITE_CHECKPOINT_PASSIVE,0,0); } #ifndef SQLITE_OMIT_WAL @@ -122924,9 +134194,11 @@ SQLITE_PRIVATE int sqlite3TempInMemory(const sqlite3 *db){ return ( db->temp_store!=1 ); #endif #if SQLITE_TEMP_STORE==3 + UNUSED_PARAMETER(db); return 1; #endif #if SQLITE_TEMP_STORE<1 || SQLITE_TEMP_STORE>3 + UNUSED_PARAMETER(db); return 0; #endif } @@ -122935,7 +134207,7 @@ SQLITE_PRIVATE int sqlite3TempInMemory(const sqlite3 *db){ ** Return UTF-8 encoded English language explanation of the most recent ** error. */ -SQLITE_API const char *sqlite3_errmsg(sqlite3 *db){ +SQLITE_API const char *SQLITE_STDCALL sqlite3_errmsg(sqlite3 *db){ const char *z; if( !db ){ return sqlite3ErrStr(SQLITE_NOMEM); @@ -122963,7 +134235,7 @@ SQLITE_API const char *sqlite3_errmsg(sqlite3 *db){ ** Return UTF-16 encoded English language explanation of the most recent ** error. */ -SQLITE_API const void *sqlite3_errmsg16(sqlite3 *db){ +SQLITE_API const void *SQLITE_STDCALL sqlite3_errmsg16(sqlite3 *db){ static const u16 outOfMem[] = { 'o', 'u', 't', ' ', 'o', 'f', ' ', 'm', 'e', 'm', 'o', 'r', 'y', 0 }; @@ -122989,7 +134261,7 @@ SQLITE_API const void *sqlite3_errmsg16(sqlite3 *db){ }else{ z = sqlite3_value_text16(db->pErr); if( z==0 ){ - sqlite3Error(db, db->errCode, sqlite3ErrStr(db->errCode)); + sqlite3ErrorWithMsg(db, db->errCode, sqlite3ErrStr(db->errCode)); z = sqlite3_value_text16(db->pErr); } /* A malloc() may have failed within the call to sqlite3_value_text16() @@ -123008,7 +134280,7 @@ SQLITE_API const void *sqlite3_errmsg16(sqlite3 *db){ ** Return the most recent error code generated by an SQLite routine. If NULL is ** passed to this function, we assume a malloc() failed during sqlite3_open(). */ -SQLITE_API int sqlite3_errcode(sqlite3 *db){ +SQLITE_API int SQLITE_STDCALL sqlite3_errcode(sqlite3 *db){ if( db && !sqlite3SafetyCheckSickOrOk(db) ){ return SQLITE_MISUSE_BKPT; } @@ -123017,7 +134289,7 @@ SQLITE_API int sqlite3_errcode(sqlite3 *db){ } return db->errCode & db->errMask; } -SQLITE_API int sqlite3_extended_errcode(sqlite3 *db){ +SQLITE_API int SQLITE_STDCALL sqlite3_extended_errcode(sqlite3 *db){ if( db && !sqlite3SafetyCheckSickOrOk(db) ){ return SQLITE_MISUSE_BKPT; } @@ -123032,36 +134304,10 @@ SQLITE_API int sqlite3_extended_errcode(sqlite3 *db){ ** argument. For now, this simply calls the internal sqlite3ErrStr() ** function. */ -SQLITE_API const char *sqlite3_errstr(int rc){ +SQLITE_API const char *SQLITE_STDCALL sqlite3_errstr(int rc){ return sqlite3ErrStr(rc); } -/* -** Invalidate all cached KeyInfo objects for database connection "db" -*/ -static void invalidateCachedKeyInfo(sqlite3 *db){ - Db *pDb; /* A single database */ - int iDb; /* The database index number */ - HashElem *k; /* For looping over tables in pDb */ - Table *pTab; /* A table in the database */ - Index *pIdx; /* Each index */ - - for(iDb=0, pDb=db->aDb; iDbnDb; iDb++, pDb++){ - if( pDb->pBt==0 ) continue; - sqlite3BtreeEnter(pDb->pBt); - for(k=sqliteHashFirst(&pDb->pSchema->tblHash); k; k=sqliteHashNext(k)){ - pTab = (Table*)sqliteHashData(k); - for(pIdx=pTab->pIndex; pIdx; pIdx=pIdx->pNext){ - if( pIdx->pKeyInfo && pIdx->pKeyInfo->db==db ){ - sqlite3KeyInfoUnref(pIdx->pKeyInfo); - pIdx->pKeyInfo = 0; - } - } - } - sqlite3BtreeLeave(pDb->pBt); - } -} - /* ** Create a new collating function for database "db". The name is zName ** and the encoding is enc. @@ -123076,7 +134322,6 @@ static int createCollation( ){ CollSeq *pColl; int enc2; - int nName = sqlite3Strlen30(zName); assert( sqlite3_mutex_held(db->mutex) ); @@ -123101,12 +134346,11 @@ static int createCollation( pColl = sqlite3FindCollSeq(db, (u8)enc2, zName, 0); if( pColl && pColl->xCmp ){ if( db->nVdbeActive ){ - sqlite3Error(db, SQLITE_BUSY, + sqlite3ErrorWithMsg(db, SQLITE_BUSY, "unable to delete/modify collation sequence due to active statements"); return SQLITE_BUSY; } sqlite3ExpirePreparedStatements(db); - invalidateCachedKeyInfo(db); /* If collation sequence pColl was created directly by a call to ** sqlite3_create_collation, and not generated by synthCollSeq(), @@ -123115,7 +134359,7 @@ static int createCollation( ** to be called. */ if( (pColl->enc & ~SQLITE_UTF16_ALIGNED)==enc2 ){ - CollSeq *aColl = sqlite3HashFind(&db->aCollSeq, zName, nName); + CollSeq *aColl = sqlite3HashFind(&db->aCollSeq, zName); int j; for(j=0; j<3; j++){ CollSeq *p = &aColl[j]; @@ -123135,7 +134379,7 @@ static int createCollation( pColl->pUser = pCtx; pColl->xDel = xDel; pColl->enc = (u8)(enc2 | (enc & SQLITE_UTF16_ALIGNED)); - sqlite3Error(db, SQLITE_OK, 0); + sqlite3Error(db, SQLITE_OK); return SQLITE_OK; } @@ -123155,8 +134399,9 @@ static const int aHardLimit[] = { SQLITE_MAX_FUNCTION_ARG, SQLITE_MAX_ATTACHED, SQLITE_MAX_LIKE_PATTERN_LENGTH, - SQLITE_MAX_VARIABLE_NUMBER, + SQLITE_MAX_VARIABLE_NUMBER, /* IMP: R-38091-32352 */ SQLITE_MAX_TRIGGER_DEPTH, + SQLITE_MAX_WORKER_THREADS, }; /* @@ -123180,8 +134425,8 @@ static const int aHardLimit[] = { #if SQLITE_MAX_FUNCTION_ARG<0 || SQLITE_MAX_FUNCTION_ARG>1000 # error SQLITE_MAX_FUNCTION_ARG must be between 0 and 1000 #endif -#if SQLITE_MAX_ATTACHED<0 || SQLITE_MAX_ATTACHED>62 -# error SQLITE_MAX_ATTACHED must be between 0 and 62 +#if SQLITE_MAX_ATTACHED<0 || SQLITE_MAX_ATTACHED>125 +# error SQLITE_MAX_ATTACHED must be between 0 and 125 #endif #if SQLITE_MAX_LIKE_PATTERN_LENGTH<1 # error SQLITE_MAX_LIKE_PATTERN_LENGTH must be at least 1 @@ -123192,6 +134437,9 @@ static const int aHardLimit[] = { #if SQLITE_MAX_TRIGGER_DEPTH<1 # error SQLITE_MAX_TRIGGER_DEPTH must be at least 1 #endif +#if SQLITE_MAX_WORKER_THREADS<0 || SQLITE_MAX_WORKER_THREADS>50 +# error SQLITE_MAX_WORKER_THREADS must be between 0 and 50 +#endif /* @@ -123204,9 +134452,15 @@ static const int aHardLimit[] = { ** It merely prevents new constructs that exceed the limit ** from forming. */ -SQLITE_API int sqlite3_limit(sqlite3 *db, int limitId, int newLimit){ +SQLITE_API int SQLITE_STDCALL sqlite3_limit(sqlite3 *db, int limitId, int newLimit){ int oldLimit; +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ){ + (void)SQLITE_MISUSE_BKPT; + return -1; + } +#endif /* EVIDENCE-OF: R-30189-54097 For each limit category SQLITE_LIMIT_NAME ** there is a hard upper bound set at compile-time by a C preprocessor @@ -123225,7 +134479,8 @@ SQLITE_API int sqlite3_limit(sqlite3 *db, int limitId, int newLimit){ SQLITE_MAX_LIKE_PATTERN_LENGTH ); assert( aHardLimit[SQLITE_LIMIT_VARIABLE_NUMBER]==SQLITE_MAX_VARIABLE_NUMBER); assert( aHardLimit[SQLITE_LIMIT_TRIGGER_DEPTH]==SQLITE_MAX_TRIGGER_DEPTH ); - assert( SQLITE_LIMIT_TRIGGER_DEPTH==(SQLITE_N_LIMIT-1) ); + assert( aHardLimit[SQLITE_LIMIT_WORKER_THREADS]==SQLITE_MAX_WORKER_THREADS ); + assert( SQLITE_LIMIT_WORKER_THREADS==(SQLITE_N_LIMIT-1) ); if( limitId<0 || limitId>=SQLITE_N_LIMIT ){ @@ -123282,25 +134537,38 @@ SQLITE_PRIVATE int sqlite3ParseUri( assert( *pzErrMsg==0 ); - if( ((flags & SQLITE_OPEN_URI) || sqlite3GlobalConfig.bOpenUri) - && nUri>=5 && memcmp(zUri, "file:", 5)==0 + if( ((flags & SQLITE_OPEN_URI) /* IMP: R-48725-32206 */ + || sqlite3GlobalConfig.bOpenUri) /* IMP: R-51689-46548 */ + && nUri>=5 && memcmp(zUri, "file:", 5)==0 /* IMP: R-57884-37496 */ ){ char *zOpt; int eState; /* Parser state when parsing URI */ int iIn; /* Input character index */ int iOut = 0; /* Output character index */ - int nByte = nUri+2; /* Bytes of space to allocate */ + u64 nByte = nUri+2; /* Bytes of space to allocate */ /* Make sure the SQLITE_OPEN_URI flag is set to indicate to the VFS xOpen ** method that there may be extra parameters following the file-name. */ flags |= SQLITE_OPEN_URI; for(iIn=0; iInaLimit)==sizeof(aHardLimit) ); memcpy(db->aLimit, aHardLimit, sizeof(db->aLimit)); + db->aLimit[SQLITE_LIMIT_WORKER_THREADS] = SQLITE_DEFAULT_WORKER_THREADS; db->autoCommit = 1; db->nextAutovac = -1; db->szMmap = sqlite3GlobalConfig.szMmap; db->nextPagesize = 0; + db->nMaxSorterMmap = 0x7FFFFFFF; db->flags |= SQLITE_ShortColNames | SQLITE_EnableTrigger | SQLITE_CacheSpill #if !defined(SQLITE_DEFAULT_AUTOMATIC_INDEX) || SQLITE_DEFAULT_AUTOMATIC_INDEX | SQLITE_AutoIndex #endif +#if SQLITE_DEFAULT_CKPTFULLFSYNC + | SQLITE_CkptFullFSync +#endif #if SQLITE_DEFAULT_FILE_FORMAT<4 | SQLITE_LegacyFileFmt #endif @@ -123591,6 +134869,12 @@ static int openDatabase( #endif #if defined(SQLITE_DEFAULT_FOREIGN_KEYS) && SQLITE_DEFAULT_FOREIGN_KEYS | SQLITE_ForeignKeys +#endif +#if defined(SQLITE_REVERSE_UNORDERED_SELECTS) + | SQLITE_ReverseOrder +#endif +#if defined(SQLITE_ENABLE_OVERSIZE_CELL_CHECK) + | SQLITE_CellSizeCk #endif ; sqlite3HashInit(&db->aCollSeq); @@ -123601,26 +134885,30 @@ static int openDatabase( /* Add the default collation sequence BINARY. BINARY works for both UTF-8 ** and UTF-16, so add a version for each to avoid any unnecessary ** conversions. The only error that can occur here is a malloc() failure. + ** + ** EVIDENCE-OF: R-52786-44878 SQLite defines three built-in collating + ** functions: */ - createCollation(db, "BINARY", SQLITE_UTF8, 0, binCollFunc, 0); - createCollation(db, "BINARY", SQLITE_UTF16BE, 0, binCollFunc, 0); - createCollation(db, "BINARY", SQLITE_UTF16LE, 0, binCollFunc, 0); + createCollation(db, sqlite3StrBINARY, SQLITE_UTF8, 0, binCollFunc, 0); + createCollation(db, sqlite3StrBINARY, SQLITE_UTF16BE, 0, binCollFunc, 0); + createCollation(db, sqlite3StrBINARY, SQLITE_UTF16LE, 0, binCollFunc, 0); + createCollation(db, "NOCASE", SQLITE_UTF8, 0, nocaseCollatingFunc, 0); createCollation(db, "RTRIM", SQLITE_UTF8, (void*)1, binCollFunc, 0); if( db->mallocFailed ){ goto opendb_out; } - db->pDfltColl = sqlite3FindCollSeq(db, SQLITE_UTF8, "BINARY", 0); + /* EVIDENCE-OF: R-08308-17224 The default collating function for all + ** strings is BINARY. + */ + db->pDfltColl = sqlite3FindCollSeq(db, SQLITE_UTF8, sqlite3StrBINARY, 0); assert( db->pDfltColl!=0 ); - /* Also add a UTF-8 case-insensitive collation sequence. */ - createCollation(db, "NOCASE", SQLITE_UTF8, 0, nocaseCollatingFunc, 0); - /* Parse the filename/URI argument. */ db->openFlags = flags; rc = sqlite3ParseUri(zVfs, zFilename, &flags, &db->pVfs, &zOpen, &zErrMsg); if( rc!=SQLITE_OK ){ if( rc==SQLITE_NOMEM ) db->mallocFailed = 1; - sqlite3Error(db, rc, zErrMsg ? "%s" : 0, zErrMsg); + sqlite3ErrorWithMsg(db, rc, zErrMsg ? "%s" : 0, zErrMsg); sqlite3_free(zErrMsg); goto opendb_out; } @@ -123632,13 +134920,15 @@ static int openDatabase( if( rc==SQLITE_IOERR_NOMEM ){ rc = SQLITE_NOMEM; } - sqlite3Error(db, rc, 0); + sqlite3Error(db, rc); goto opendb_out; } + sqlite3BtreeEnter(db->aDb[0].pBt); db->aDb[0].pSchema = sqlite3SchemaGet(db, db->aDb[0].pBt); + if( !db->mallocFailed ) ENC(db) = SCHEMA_ENC(db); + sqlite3BtreeLeave(db->aDb[0].pBt); db->aDb[1].pSchema = sqlite3SchemaGet(db, 0); - /* The default safety_level for the main database is 'full'; for the temp ** database it is 'NONE'. This matches the pager layer defaults. */ @@ -123656,7 +134946,7 @@ static int openDatabase( ** database schema yet. This is delayed until the first time the database ** is accessed. */ - sqlite3Error(db, SQLITE_OK, 0); + sqlite3Error(db, SQLITE_OK); sqlite3RegisterBuiltinFunctions(db); /* Load automatic extensions - extensions that have been registered @@ -123685,12 +134975,18 @@ static int openDatabase( } #endif -#ifdef SQLITE_ENABLE_FTS3 +#ifdef SQLITE_ENABLE_FTS3 /* automatically defined by SQLITE_ENABLE_FTS4 */ if( !db->mallocFailed && rc==SQLITE_OK ){ rc = sqlite3Fts3Init(db); } #endif +#ifdef SQLITE_ENABLE_FTS5 + if( !db->mallocFailed && rc==SQLITE_OK ){ + rc = sqlite3Fts5Init(db); + } +#endif + #ifdef SQLITE_ENABLE_ICU if( !db->mallocFailed && rc==SQLITE_OK ){ rc = sqlite3IcuInit(db); @@ -123703,6 +134999,18 @@ static int openDatabase( } #endif +#ifdef SQLITE_ENABLE_DBSTAT_VTAB + if( !db->mallocFailed && rc==SQLITE_OK){ + rc = sqlite3DbstatRegister(db); + } +#endif + +#ifdef SQLITE_ENABLE_JSON1 + if( !db->mallocFailed && rc==SQLITE_OK){ + rc = sqlite3Json1Init(db); + } +#endif + /* -DSQLITE_DEFAULT_LOCKING_MODE=1 makes EXCLUSIVE the default locking ** mode. -DSQLITE_DEFAULT_LOCKING_MODE=0 make NORMAL the default locking ** mode. Doing nothing at all also makes NORMAL the default. @@ -123713,7 +135021,7 @@ static int openDatabase( SQLITE_DEFAULT_LOCKING_MODE); #endif - if( rc ) sqlite3Error(db, rc, 0); + if( rc ) sqlite3Error(db, rc); /* Enable the lookaside-malloc subsystem */ setupLookaside(db, 0, sqlite3GlobalConfig.szLookaside, @@ -123722,9 +135030,9 @@ static int openDatabase( sqlite3_wal_autocheckpoint(db, SQLITE_DEFAULT_WAL_AUTOCHECKPOINT); opendb_out: - sqlite3_free(zOpen); if( db ){ - assert( db->mutex!=0 || isThreadsafe==0 || sqlite3GlobalConfig.bFullMutex==0 ); + assert( db->mutex!=0 || isThreadsafe==0 + || sqlite3GlobalConfig.bFullMutex==0 ); sqlite3_mutex_leave(db->mutex); } rc = sqlite3_errcode(db); @@ -123743,20 +135051,36 @@ opendb_out: sqlite3GlobalConfig.xSqllog(pArg, db, zFilename, 0); } #endif - return sqlite3ApiExit(0, rc); +#if defined(SQLITE_HAS_CODEC) + if( rc==SQLITE_OK ){ + const char *zHexKey = sqlite3_uri_parameter(zOpen, "hexkey"); + if( zHexKey && zHexKey[0] ){ + u8 iByte; + int i; + char zKey[40]; + for(i=0, iByte=0; imutex); - assert( !db->mallocFailed ); - rc = createCollation(db, zName, (u8)enc, pCtx, xCompare, 0); - rc = sqlite3ApiExit(db, rc); - sqlite3_mutex_leave(db->mutex); - return rc; + return sqlite3_create_collation_v2(db, zName, enc, pCtx, xCompare, 0); } /* ** Register a new collation sequence with the database handle db. */ -SQLITE_API int sqlite3_create_collation_v2( +SQLITE_API int SQLITE_STDCALL sqlite3_create_collation_v2( sqlite3* db, const char *zName, int enc, @@ -123834,6 +135154,10 @@ SQLITE_API int sqlite3_create_collation_v2( void(*xDel)(void*) ){ int rc; + +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) || zName==0 ) return SQLITE_MISUSE_BKPT; +#endif sqlite3_mutex_enter(db->mutex); assert( !db->mallocFailed ); rc = createCollation(db, zName, (u8)enc, pCtx, xCompare, xDel); @@ -123846,7 +135170,7 @@ SQLITE_API int sqlite3_create_collation_v2( /* ** Register a new collation sequence with the database handle db. */ -SQLITE_API int sqlite3_create_collation16( +SQLITE_API int SQLITE_STDCALL sqlite3_create_collation16( sqlite3* db, const void *zName, int enc, @@ -123855,6 +135179,10 @@ SQLITE_API int sqlite3_create_collation16( ){ int rc = SQLITE_OK; char *zName8; + +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) || zName==0 ) return SQLITE_MISUSE_BKPT; +#endif sqlite3_mutex_enter(db->mutex); assert( !db->mallocFailed ); zName8 = sqlite3Utf16to8(db, zName, -1, SQLITE_UTF16NATIVE); @@ -123872,11 +135200,14 @@ SQLITE_API int sqlite3_create_collation16( ** Register a collation sequence factory callback with the database handle ** db. Replace any previously installed collation sequence factory. */ -SQLITE_API int sqlite3_collation_needed( +SQLITE_API int SQLITE_STDCALL sqlite3_collation_needed( sqlite3 *db, void *pCollNeededArg, void(*xCollNeeded)(void*,sqlite3*,int eTextRep,const char*) ){ +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ) return SQLITE_MISUSE_BKPT; +#endif sqlite3_mutex_enter(db->mutex); db->xCollNeeded = xCollNeeded; db->xCollNeeded16 = 0; @@ -123890,11 +135221,14 @@ SQLITE_API int sqlite3_collation_needed( ** Register a collation sequence factory callback with the database handle ** db. Replace any previously installed collation sequence factory. */ -SQLITE_API int sqlite3_collation_needed16( +SQLITE_API int SQLITE_STDCALL sqlite3_collation_needed16( sqlite3 *db, void *pCollNeededArg, void(*xCollNeeded16)(void*,sqlite3*,int eTextRep,const void*) ){ +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ) return SQLITE_MISUSE_BKPT; +#endif sqlite3_mutex_enter(db->mutex); db->xCollNeeded = 0; db->xCollNeeded16 = xCollNeeded16; @@ -123909,7 +135243,7 @@ SQLITE_API int sqlite3_collation_needed16( ** This function is now an anachronism. It used to be used to recover from a ** malloc() failure, but SQLite now does this automatically. */ -SQLITE_API int sqlite3_global_recover(void){ +SQLITE_API int SQLITE_STDCALL sqlite3_global_recover(void){ return SQLITE_OK; } #endif @@ -123920,14 +135254,20 @@ SQLITE_API int sqlite3_global_recover(void){ ** by default. Autocommit is disabled by a BEGIN statement and reenabled ** by the next COMMIT or ROLLBACK. */ -SQLITE_API int sqlite3_get_autocommit(sqlite3 *db){ +SQLITE_API int SQLITE_STDCALL sqlite3_get_autocommit(sqlite3 *db){ +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ){ + (void)SQLITE_MISUSE_BKPT; + return 0; + } +#endif return db->autoCommit; } /* -** The following routines are subtitutes for constants SQLITE_CORRUPT, +** The following routines are substitutes for constants SQLITE_CORRUPT, ** SQLITE_MISUSE, SQLITE_CANTOPEN, SQLITE_IOERR and possibly other error -** constants. They server two purposes: +** constants. They serve two purposes: ** ** 1. Serve as a convenient place to set a breakpoint in a debugger ** to detect when version error conditions occurs. @@ -123966,7 +135306,7 @@ SQLITE_PRIVATE int sqlite3CantopenError(int lineno){ ** SQLite no longer uses thread-specific data so this routine is now a ** no-op. It is retained for historical compatibility. */ -SQLITE_API void sqlite3_thread_cleanup(void){ +SQLITE_API void SQLITE_STDCALL sqlite3_thread_cleanup(void){ } #endif @@ -123974,8 +135314,7 @@ SQLITE_API void sqlite3_thread_cleanup(void){ ** Return meta information about a specific column of a database table. ** See comment in sqlite3.h (sqlite.h.in) for details. */ -#ifdef SQLITE_ENABLE_COLUMN_METADATA -SQLITE_API int sqlite3_table_column_metadata( +SQLITE_API int SQLITE_STDCALL sqlite3_table_column_metadata( sqlite3 *db, /* Connection handle */ const char *zDbName, /* Database name or NULL */ const char *zTableName, /* Table name */ @@ -123990,14 +135329,20 @@ SQLITE_API int sqlite3_table_column_metadata( char *zErrMsg = 0; Table *pTab = 0; Column *pCol = 0; - int iCol; - + int iCol = 0; char const *zDataType = 0; char const *zCollSeq = 0; int notnull = 0; int primarykey = 0; int autoinc = 0; + +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) || zTableName==0 ){ + return SQLITE_MISUSE_BKPT; + } +#endif + /* Ensure the database schema has been loaded */ sqlite3_mutex_enter(db->mutex); sqlite3BtreeEnterAll(db); @@ -124014,11 +135359,8 @@ SQLITE_API int sqlite3_table_column_metadata( } /* Find the column for which info is requested */ - if( sqlite3IsRowid(zColumnName) ){ - iCol = pTab->iPKey; - if( iCol>=0 ){ - pCol = &pTab->aCol[iCol]; - } + if( zColumnName==0 ){ + /* Query for existance of table only */ }else{ for(iCol=0; iColnCol; iCol++){ pCol = &pTab->aCol[iCol]; @@ -124027,8 +135369,13 @@ SQLITE_API int sqlite3_table_column_metadata( } } if( iCol==pTab->nCol ){ - pTab = 0; - goto error_out; + if( HasRowid(pTab) && sqlite3IsRowid(zColumnName) ){ + iCol = pTab->iPKey; + pCol = iCol>=0 ? &pTab->aCol[iCol] : 0; + }else{ + pTab = 0; + goto error_out; + } } } @@ -124053,7 +135400,7 @@ SQLITE_API int sqlite3_table_column_metadata( primarykey = 1; } if( !zCollSeq ){ - zCollSeq = "BINARY"; + zCollSeq = sqlite3StrBINARY; } error_out: @@ -124075,18 +135422,17 @@ error_out: zColumnName); rc = SQLITE_ERROR; } - sqlite3Error(db, rc, (zErrMsg?"%s":0), zErrMsg); + sqlite3ErrorWithMsg(db, rc, (zErrMsg?"%s":0), zErrMsg); sqlite3DbFree(db, zErrMsg); rc = sqlite3ApiExit(db, rc); sqlite3_mutex_leave(db->mutex); return rc; } -#endif /* ** Sleep for a little while. Return the amount of time slept. */ -SQLITE_API int sqlite3_sleep(int ms){ +SQLITE_API int SQLITE_STDCALL sqlite3_sleep(int ms){ sqlite3_vfs *pVfs; int rc; pVfs = sqlite3_vfs_find(0); @@ -124102,7 +135448,10 @@ SQLITE_API int sqlite3_sleep(int ms){ /* ** Enable or disable the extended result codes. */ -SQLITE_API int sqlite3_extended_result_codes(sqlite3 *db, int onoff){ +SQLITE_API int SQLITE_STDCALL sqlite3_extended_result_codes(sqlite3 *db, int onoff){ +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ) return SQLITE_MISUSE_BKPT; +#endif sqlite3_mutex_enter(db->mutex); db->errMask = onoff ? 0xffffffff : 0xff; sqlite3_mutex_leave(db->mutex); @@ -124112,10 +135461,13 @@ SQLITE_API int sqlite3_extended_result_codes(sqlite3 *db, int onoff){ /* ** Invoke the xFileControl method on a particular database. */ -SQLITE_API int sqlite3_file_control(sqlite3 *db, const char *zDbName, int op, void *pArg){ +SQLITE_API int SQLITE_STDCALL sqlite3_file_control(sqlite3 *db, const char *zDbName, int op, void *pArg){ int rc = SQLITE_ERROR; Btree *pBtree; +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ) return SQLITE_MISUSE_BKPT; +#endif sqlite3_mutex_enter(db->mutex); pBtree = sqlite3DbNameToBtree(db, zDbName); if( pBtree ){ @@ -124129,6 +135481,12 @@ SQLITE_API int sqlite3_file_control(sqlite3 *db, const char *zDbName, int op, vo if( op==SQLITE_FCNTL_FILE_POINTER ){ *(sqlite3_file**)pArg = fd; rc = SQLITE_OK; + }else if( op==SQLITE_FCNTL_VFS_POINTER ){ + *(sqlite3_vfs**)pArg = sqlite3PagerVfs(pPager); + rc = SQLITE_OK; + }else if( op==SQLITE_FCNTL_JOURNAL_POINTER ){ + *(sqlite3_file**)pArg = sqlite3PagerJrnlFile(pPager); + rc = SQLITE_OK; }else if( fd->pMethods ){ rc = sqlite3OsFileControl(fd, op, pArg); }else{ @@ -124137,15 +135495,17 @@ SQLITE_API int sqlite3_file_control(sqlite3 *db, const char *zDbName, int op, vo sqlite3BtreeLeave(pBtree); } sqlite3_mutex_leave(db->mutex); - return rc; + return rc; } /* ** Interface to the testing logic. */ -SQLITE_API int sqlite3_test_control(int op, ...){ +SQLITE_API int SQLITE_CDECL sqlite3_test_control(int op, ...){ int rc = 0; -#ifndef SQLITE_OMIT_BUILTIN_TEST +#ifdef SQLITE_OMIT_BUILTIN_TEST + UNUSED_PARAMETER(op); +#else va_list ap; va_start(ap, op); switch( op ){ @@ -124207,10 +135567,10 @@ SQLITE_API int sqlite3_test_control(int op, ...){ case SQLITE_TESTCTRL_FAULT_INSTALL: { /* MSVC is picky about pulling func ptrs from va lists. ** http://support.microsoft.com/kb/47961 - ** sqlite3Config.xTestCallback = va_arg(ap, int(*)(int)); + ** sqlite3GlobalConfig.xTestCallback = va_arg(ap, int(*)(int)); */ typedef int(*TESTCALLBACKFUNC_t)(int); - sqlite3Config.xTestCallback = va_arg(ap, TESTCALLBACKFUNC_t); + sqlite3GlobalConfig.xTestCallback = va_arg(ap, TESTCALLBACKFUNC_t); rc = sqlite3FaultSim(0); break; } @@ -124241,7 +135601,7 @@ SQLITE_API int sqlite3_test_control(int op, ...){ ** IMPORTANT: Changing the PENDING byte from 0x40000000 results in ** an incompatible database file format. Changing the PENDING byte ** while any database connection is open results in undefined and - ** dileterious behavior. + ** deleterious behavior. */ case SQLITE_TESTCTRL_PENDING_BYTE: { rc = PENDING_BYTE; @@ -124396,22 +135756,6 @@ SQLITE_API int sqlite3_test_control(int op, ...){ break; } -#if defined(SQLITE_ENABLE_TREE_EXPLAIN) - /* sqlite3_test_control(SQLITE_TESTCTRL_EXPLAIN_STMT, - ** sqlite3_stmt*,const char**); - ** - ** If compiled with SQLITE_ENABLE_TREE_EXPLAIN, each sqlite3_stmt holds - ** a string that describes the optimized parse tree. This test-control - ** returns a pointer to that string. - */ - case SQLITE_TESTCTRL_EXPLAIN_STMT: { - sqlite3_stmt *pStmt = va_arg(ap, sqlite3_stmt*); - const char **pzRet = va_arg(ap, const char**); - *pzRet = sqlite3VdbeExplanation((Vdbe*)pStmt); - break; - } -#endif - /* sqlite3_test_control(SQLITE_TESTCTRL_NEVER_CORRUPT, int); ** ** Set or clear a flag that indicates that the database file is always well- @@ -124440,6 +135784,51 @@ SQLITE_API int sqlite3_test_control(int op, ...){ break; } + /* sqlite3_test_control(SQLITE_TESTCTRL_SORTER_MMAP, db, nMax); */ + case SQLITE_TESTCTRL_SORTER_MMAP: { + sqlite3 *db = va_arg(ap, sqlite3*); + db->nMaxSorterMmap = va_arg(ap, int); + break; + } + + /* sqlite3_test_control(SQLITE_TESTCTRL_ISINIT); + ** + ** Return SQLITE_OK if SQLite has been initialized and SQLITE_ERROR if + ** not. + */ + case SQLITE_TESTCTRL_ISINIT: { + if( sqlite3GlobalConfig.isInit==0 ) rc = SQLITE_ERROR; + break; + } + + /* sqlite3_test_control(SQLITE_TESTCTRL_IMPOSTER, db, dbName, onOff, tnum); + ** + ** This test control is used to create imposter tables. "db" is a pointer + ** to the database connection. dbName is the database name (ex: "main" or + ** "temp") which will receive the imposter. "onOff" turns imposter mode on + ** or off. "tnum" is the root page of the b-tree to which the imposter + ** table should connect. + ** + ** Enable imposter mode only when the schema has already been parsed. Then + ** run a single CREATE TABLE statement to construct the imposter table in + ** the parsed schema. Then turn imposter mode back off again. + ** + ** If onOff==0 and tnum>0 then reset the schema for all databases, causing + ** the schema to be reparsed the next time it is needed. This has the + ** effect of erasing all imposter tables. + */ + case SQLITE_TESTCTRL_IMPOSTER: { + sqlite3 *db = va_arg(ap, sqlite3*); + sqlite3_mutex_enter(db->mutex); + db->init.iDb = sqlite3FindDbName(db, va_arg(ap,const char*)); + db->init.busy = db->init.imposterTable = va_arg(ap,int); + db->init.newTnum = va_arg(ap,int); + if( db->init.busy==0 && db->init.newTnum>0 ){ + sqlite3ResetAllSchemasOfConnection(db); + } + sqlite3_mutex_leave(db->mutex); + break; + } } va_end(ap); #endif /* SQLITE_OMIT_BUILTIN_TEST */ @@ -124457,8 +135846,8 @@ SQLITE_API int sqlite3_test_control(int op, ...){ ** parameter if it exists. If the parameter does not exist, this routine ** returns a NULL pointer. */ -SQLITE_API const char *sqlite3_uri_parameter(const char *zFilename, const char *zParam){ - if( zFilename==0 ) return 0; +SQLITE_API const char *SQLITE_STDCALL sqlite3_uri_parameter(const char *zFilename, const char *zParam){ + if( zFilename==0 || zParam==0 ) return 0; zFilename += sqlite3Strlen30(zFilename) + 1; while( zFilename[0] ){ int x = strcmp(zFilename, zParam); @@ -124472,7 +135861,7 @@ SQLITE_API const char *sqlite3_uri_parameter(const char *zFilename, const char * /* ** Return a boolean value for a query parameter. */ -SQLITE_API int sqlite3_uri_boolean(const char *zFilename, const char *zParam, int bDflt){ +SQLITE_API int SQLITE_STDCALL sqlite3_uri_boolean(const char *zFilename, const char *zParam, int bDflt){ const char *z = sqlite3_uri_parameter(zFilename, zParam); bDflt = bDflt!=0; return z ? sqlite3GetBoolean(z, bDflt) : bDflt; @@ -124481,14 +135870,14 @@ SQLITE_API int sqlite3_uri_boolean(const char *zFilename, const char *zParam, in /* ** Return a 64-bit integer value for a query parameter. */ -SQLITE_API sqlite3_int64 sqlite3_uri_int64( +SQLITE_API sqlite3_int64 SQLITE_STDCALL sqlite3_uri_int64( const char *zFilename, /* Filename as passed to xOpen */ const char *zParam, /* URI parameter sought */ sqlite3_int64 bDflt /* return if parameter is missing */ ){ const char *z = sqlite3_uri_parameter(zFilename, zParam); sqlite3_int64 v; - if( z && sqlite3Atoi64(z, &v, sqlite3Strlen30(z), SQLITE_UTF8)==SQLITE_OK ){ + if( z && sqlite3DecOrHexToI64(z, &v)==SQLITE_OK ){ bDflt = v; } return bDflt; @@ -124513,8 +135902,15 @@ SQLITE_PRIVATE Btree *sqlite3DbNameToBtree(sqlite3 *db, const char *zDbName){ ** Return the filename of the database associated with a database ** connection. */ -SQLITE_API const char *sqlite3_db_filename(sqlite3 *db, const char *zDbName){ - Btree *pBt = sqlite3DbNameToBtree(db, zDbName); +SQLITE_API const char *SQLITE_STDCALL sqlite3_db_filename(sqlite3 *db, const char *zDbName){ + Btree *pBt; +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ){ + (void)SQLITE_MISUSE_BKPT; + return 0; + } +#endif + pBt = sqlite3DbNameToBtree(db, zDbName); return pBt ? sqlite3BtreeGetFilename(pBt) : 0; } @@ -124522,11 +135918,100 @@ SQLITE_API const char *sqlite3_db_filename(sqlite3 *db, const char *zDbName){ ** Return 1 if database is read-only or 0 if read/write. Return -1 if ** no such database exists. */ -SQLITE_API int sqlite3_db_readonly(sqlite3 *db, const char *zDbName){ - Btree *pBt = sqlite3DbNameToBtree(db, zDbName); +SQLITE_API int SQLITE_STDCALL sqlite3_db_readonly(sqlite3 *db, const char *zDbName){ + Btree *pBt; +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ){ + (void)SQLITE_MISUSE_BKPT; + return -1; + } +#endif + pBt = sqlite3DbNameToBtree(db, zDbName); return pBt ? sqlite3BtreeIsReadonly(pBt) : -1; } +#ifdef SQLITE_ENABLE_SNAPSHOT +/* +** Obtain a snapshot handle for the snapshot of database zDb currently +** being read by handle db. +*/ +SQLITE_API int SQLITE_STDCALL sqlite3_snapshot_get( + sqlite3 *db, + const char *zDb, + sqlite3_snapshot **ppSnapshot +){ + int rc = SQLITE_ERROR; +#ifndef SQLITE_OMIT_WAL + int iDb; + +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ){ + return SQLITE_MISUSE_BKPT; + } +#endif + sqlite3_mutex_enter(db->mutex); + + iDb = sqlite3FindDbName(db, zDb); + if( iDb==0 || iDb>1 ){ + Btree *pBt = db->aDb[iDb].pBt; + if( 0==sqlite3BtreeIsInTrans(pBt) ){ + rc = sqlite3BtreeBeginTrans(pBt, 0); + if( rc==SQLITE_OK ){ + rc = sqlite3PagerSnapshotGet(sqlite3BtreePager(pBt), ppSnapshot); + } + } + } + + sqlite3_mutex_leave(db->mutex); +#endif /* SQLITE_OMIT_WAL */ + return rc; +} + +/* +** Open a read-transaction on the snapshot idendified by pSnapshot. +*/ +SQLITE_API int SQLITE_STDCALL sqlite3_snapshot_open( + sqlite3 *db, + const char *zDb, + sqlite3_snapshot *pSnapshot +){ + int rc = SQLITE_ERROR; +#ifndef SQLITE_OMIT_WAL + +#ifdef SQLITE_ENABLE_API_ARMOR + if( !sqlite3SafetyCheckOk(db) ){ + return SQLITE_MISUSE_BKPT; + } +#endif + sqlite3_mutex_enter(db->mutex); + if( db->autoCommit==0 ){ + int iDb; + iDb = sqlite3FindDbName(db, zDb); + if( iDb==0 || iDb>1 ){ + Btree *pBt = db->aDb[iDb].pBt; + if( 0==sqlite3BtreeIsInReadTrans(pBt) ){ + rc = sqlite3PagerSnapshotOpen(sqlite3BtreePager(pBt), pSnapshot); + if( rc==SQLITE_OK ){ + rc = sqlite3BtreeBeginTrans(pBt, 0); + sqlite3PagerSnapshotOpen(sqlite3BtreePager(pBt), 0); + } + } + } + } + + sqlite3_mutex_leave(db->mutex); +#endif /* SQLITE_OMIT_WAL */ + return rc; +} + +/* +** Free a snapshot handle obtained from sqlite3_snapshot_get(). +*/ +SQLITE_API void SQLITE_STDCALL sqlite3_snapshot_free(sqlite3_snapshot *pSnapshot){ + sqlite3_free(pSnapshot); +} +#endif /* SQLITE_ENABLE_SNAPSHOT */ + /************** End of main.c ************************************************/ /************** Begin file notify.c ******************************************/ /* @@ -124544,6 +136029,8 @@ SQLITE_API int sqlite3_db_readonly(sqlite3 *db, const char *zDbName){ ** This file contains the implementation of the sqlite3_unlock_notify() ** API method and its associated functionality. */ +/* #include "sqliteInt.h" */ +/* #include "btreeInt.h" */ /* Omit this entire file if SQLITE_ENABLE_UNLOCK_NOTIFY is not defined. */ #ifdef SQLITE_ENABLE_UNLOCK_NOTIFY @@ -124674,7 +136161,7 @@ static void leaveMutex(void){ ** on the same "db". If xNotify==0 then any prior callbacks are immediately ** cancelled. */ -SQLITE_API int sqlite3_unlock_notify( +SQLITE_API int SQLITE_STDCALL sqlite3_unlock_notify( sqlite3 *db, void (*xNotify)(void **, int), void *pArg @@ -124713,7 +136200,7 @@ SQLITE_API int sqlite3_unlock_notify( leaveMutex(); assert( !db->mallocFailed ); - sqlite3Error(db, rc, (rc?"database is deadlocked":0)); + sqlite3ErrorWithMsg(db, rc, (rc?"database is deadlocked":0)); sqlite3_mutex_leave(db->mutex); return rc; } @@ -125187,9 +136674,11 @@ SQLITE_PRIVATE void sqlite3ConnectionClosed(sqlite3 *db){ /* If not building as part of the core, include sqlite3ext.h. */ #ifndef SQLITE_CORE +/* # include "sqlite3ext.h" */ SQLITE_EXTENSION_INIT3 #endif +/* #include "sqlite3.h" */ /************** Include fts3_tokenizer.h in the middle of fts3Int.h **********/ /************** Begin file fts3_tokenizer.h **********************************/ /* @@ -125218,6 +136707,7 @@ SQLITE_EXTENSION_INIT3 ** If tokenizers are to be allowed to call sqlite3_*() functions, then ** we will need a way to register the API consistently. */ +/* #include "sqlite3.h" */ /* ** Structures used by the tokenizer interface. When a new tokenizer @@ -125568,6 +137058,11 @@ SQLITE_PRIVATE Fts3HashElem *sqlite3Fts3HashFindElem(const Fts3Hash *, const voi #ifdef SQLITE_COVERAGE_TEST # define ALWAYS(x) (1) # define NEVER(X) (0) +#elif defined(SQLITE_DEBUG) +# define ALWAYS(x) sqlite3Fts3Always((x)!=0) +# define NEVER(x) sqlite3Fts3Never((x)!=0) +SQLITE_PRIVATE int sqlite3Fts3Always(int b); +SQLITE_PRIVATE int sqlite3Fts3Never(int b); #else # define ALWAYS(x) (x) # define NEVER(x) (x) @@ -125626,6 +137121,8 @@ typedef struct Fts3DeferredToken Fts3DeferredToken; typedef struct Fts3SegReader Fts3SegReader; typedef struct Fts3MultiSegReader Fts3MultiSegReader; +typedef struct MatchinfoBuffer MatchinfoBuffer; + /* ** A connection to a fulltext index is an instance of the following ** structure. The xCreate and xConnect methods create an instance @@ -125691,6 +137188,7 @@ struct Fts3Table { int nPendingData; /* Current bytes of pending data */ sqlite_int64 iPrevDocid; /* Docid of most recently inserted document */ int iPrevLangid; /* Langid of recently inserted document */ + int bPrevDelete; /* True if last operation was a delete */ #if defined(SQLITE_DEBUG) || defined(SQLITE_COVERAGE_TEST) /* State variables used for validating that the transaction control @@ -125735,9 +137233,7 @@ struct Fts3Cursor { i64 iMinDocid; /* Minimum docid to return */ i64 iMaxDocid; /* Maximum docid to return */ int isMatchinfoNeeded; /* True when aMatchinfo[] needs filling in */ - u32 *aMatchinfo; /* Information about most recent match */ - int nMatchinfo; /* Number of elements in aMatchinfo[] */ - char *zMatchinfo; /* Matchinfo specification */ + MatchinfoBuffer *pMIBuffer; /* Buffer for matchinfo data */ }; #define FTS3_EVAL_FILTER 0 @@ -125809,6 +137305,11 @@ struct Fts3Phrase { int bIncr; /* True if doclist is loaded incrementally */ int iDoclistToken; + /* Used by sqlite3Fts3EvalPhrasePoslist() if this is a descendent of an + ** OR condition. */ + char *pOrPoslist; + i64 iOrDocid; + /* Variables below this point are populated by fts3_expr.c when parsing ** a MATCH expression. Everything above is part of the evaluation phase. */ @@ -125852,7 +137353,9 @@ struct Fts3Expr { u8 bStart; /* True if iDocid is valid */ u8 bDeferred; /* True if this expression is entirely deferred */ - u32 *aMI; + /* The following are used by the fts3_snippet.c module. */ + int iPhrase; /* Index of this phrase in matchinfo() results */ + u32 *aMI; /* See above */ }; /* @@ -125963,6 +137466,7 @@ SQLITE_PRIVATE int sqlite3Fts3Incrmerge(Fts3Table*,int,int); ) /* fts3.c */ +SQLITE_PRIVATE void sqlite3Fts3ErrMsg(char**,const char*,...); SQLITE_PRIVATE int sqlite3Fts3PutVarint(char *, sqlite3_int64); SQLITE_PRIVATE int sqlite3Fts3GetVarint(const char *, sqlite_int64 *); SQLITE_PRIVATE int sqlite3Fts3GetVarint32(const char *, int *); @@ -125972,6 +137476,7 @@ SQLITE_PRIVATE void sqlite3Fts3DoclistPrev(int,char*,int,char**,sqlite3_int64*,i SQLITE_PRIVATE int sqlite3Fts3EvalPhraseStats(Fts3Cursor *, Fts3Expr *, u32 *); SQLITE_PRIVATE int sqlite3Fts3FirstFilter(sqlite3_int64, char *, int, char *); SQLITE_PRIVATE void sqlite3Fts3CreateStatTable(int*, Fts3Table*); +SQLITE_PRIVATE int sqlite3Fts3EvalTestDeferred(Fts3Cursor *pCsr, int *pRc); /* fts3_tokenizer.c */ SQLITE_PRIVATE const char *sqlite3Fts3NextToken(const char *, int *); @@ -125987,6 +137492,7 @@ SQLITE_PRIVATE void sqlite3Fts3Snippet(sqlite3_context *, Fts3Cursor *, const ch const char *, const char *, int, int ); SQLITE_PRIVATE void sqlite3Fts3Matchinfo(sqlite3_context *, Fts3Cursor *, const char *); +SQLITE_PRIVATE void sqlite3Fts3MIBufferFree(MatchinfoBuffer *p); /* fts3_expr.c */ SQLITE_PRIVATE int sqlite3Fts3ExprParse(sqlite3_tokenizer *, int, @@ -126019,7 +137525,7 @@ SQLITE_PRIVATE int sqlite3Fts3MsrIncrRestart(Fts3MultiSegReader *pCsr); SQLITE_PRIVATE int sqlite3Fts3InitTok(sqlite3*, Fts3Hash *); /* fts3_unicode2.c (functions generated by parsing unicode text files) */ -#ifdef SQLITE_ENABLE_FTS4_UNICODE61 +#ifndef SQLITE_DISABLE_FTS3_UNICODE SQLITE_PRIVATE int sqlite3FtsUnicodeFold(int, int); SQLITE_PRIVATE int sqlite3FtsUnicodeIsalnum(int); SQLITE_PRIVATE int sqlite3FtsUnicodeIsdiacritic(int); @@ -126043,7 +137549,9 @@ SQLITE_PRIVATE int sqlite3FtsUnicodeIsdiacritic(int); /* #include */ /* #include */ +/* #include "fts3.h" */ #ifndef SQLITE_CORE +/* # include "sqlite3ext.h" */ SQLITE_EXTENSION_INIT1 #endif @@ -126052,6 +137560,13 @@ static int fts3EvalStart(Fts3Cursor *pCsr); static int fts3TermSegReaderCursor( Fts3Cursor *, const char *, int, int, Fts3MultiSegReader **); +#ifndef SQLITE_AMALGAMATION +# if defined(SQLITE_DEBUG) +SQLITE_PRIVATE int sqlite3Fts3Always(int b) { assert( b ); return b; } +SQLITE_PRIVATE int sqlite3Fts3Never(int b) { assert( !b ); return b; } +# endif +#endif + /* ** Write a 64-bit variable-length integer to memory starting at p[0]. ** The length of data written will be between 1 and FTS3_VARINT_MAX bytes. @@ -126161,7 +137676,7 @@ SQLITE_PRIVATE void sqlite3Fts3Dequote(char *z){ /* If the first byte was a '[', then the close-quote character is a ']' */ if( quote=='[' ) quote = ']'; - while( ALWAYS(z[iIn]) ){ + while( z[iIn] ){ if( z[iIn]==quote ){ if( z[iIn+1]!=quote ) break; z[iOut++] = quote; @@ -126240,6 +137755,17 @@ static int fts3DisconnectMethod(sqlite3_vtab *pVtab){ return SQLITE_OK; } +/* +** Write an error message into *pzErr +*/ +SQLITE_PRIVATE void sqlite3Fts3ErrMsg(char **pzErr, const char *zFormat, ...){ + va_list ap; + sqlite3_free(*pzErr); + va_start(ap, zFormat); + *pzErr = sqlite3_vmprintf(zFormat, ap); + va_end(ap); +} + /* ** Construct one or more SQL statements from the format string given ** and then evaluate those statements. The success code is written @@ -126649,11 +138175,16 @@ static char *fts3WriteExprList(Fts3Table *p, const char *zFunc, int *pRc){ ** This function is used when parsing the "prefix=" FTS4 parameter. */ static int fts3GobbleInt(const char **pp, int *pnOut){ + const int MAX_NPREFIX = 10000000; const char *p; /* Iterator pointer */ int nInt = 0; /* Output value */ for(p=*pp; p[0]>='0' && p[0]<='9'; p++){ nInt = nInt * 10 + (p[0] - '0'); + if( nInt>MAX_NPREFIX ){ + nInt = 0; + break; + } } if( p==*pp ) return SQLITE_ERROR; *pnOut = nInt; @@ -126696,7 +138227,6 @@ static int fts3PrefixParameter( aIndex = sqlite3_malloc(sizeof(struct Fts3Index) * nIndex); *apIndex = aIndex; - *pnIndex = nIndex; if( !aIndex ){ return SQLITE_NOMEM; } @@ -126706,13 +138236,20 @@ static int fts3PrefixParameter( const char *p = zParam; int i; for(i=1; i=0 ); + if( nPrefix==0 ){ + nIndex--; + i--; + }else{ + aIndex[i].nPrefix = nPrefix; + } p++; } } + *pnIndex = nIndex; return SQLITE_OK; } @@ -126747,7 +138284,8 @@ static int fts3ContentColumns( const char *zTbl, /* Name of content table */ const char ***pazCol, /* OUT: Malloc'd array of column names */ int *pnCol, /* OUT: Size of array *pazCol */ - int *pnStr /* OUT: Bytes of string content */ + int *pnStr, /* OUT: Bytes of string content */ + char **pzErr /* OUT: error message */ ){ int rc = SQLITE_OK; /* Return code */ char *zSql; /* "SELECT *" statement on zTbl */ @@ -126758,6 +138296,9 @@ static int fts3ContentColumns( rc = SQLITE_NOMEM; }else{ rc = sqlite3_prepare(db, zSql, -1, &pStmt, 0); + if( rc!=SQLITE_OK ){ + sqlite3Fts3ErrMsg(pzErr, "%s", sqlite3_errmsg(db)); + } } sqlite3_free(zSql); @@ -126836,7 +138377,7 @@ static int fts3InitVtab( const char **aCol; /* Array of column names */ sqlite3_tokenizer *pTokenizer = 0; /* Tokenizer for this table */ - int nIndex; /* Size of aIndex[] array */ + int nIndex = 0; /* Size of aIndex[] array */ struct Fts3Index *aIndex = 0; /* Array of indexes for this table */ /* The results of parsing supported FTS4 key=value options: */ @@ -126924,13 +138465,13 @@ static int fts3InitVtab( } } if( iOpt==SizeofArray(aFts4Opt) ){ - *pzErr = sqlite3_mprintf("unrecognized parameter: %s", z); + sqlite3Fts3ErrMsg(pzErr, "unrecognized parameter: %s", z); rc = SQLITE_ERROR; }else{ switch( iOpt ){ case 0: /* MATCHINFO */ if( strlen(zVal)!=4 || sqlite3_strnicmp(zVal, "fts3", 4) ){ - *pzErr = sqlite3_mprintf("unrecognized matchinfo: %s", zVal); + sqlite3Fts3ErrMsg(pzErr, "unrecognized matchinfo: %s", zVal); rc = SQLITE_ERROR; } bNoDocsize = 1; @@ -126958,7 +138499,7 @@ static int fts3InitVtab( if( (strlen(zVal)!=3 || sqlite3_strnicmp(zVal, "asc", 3)) && (strlen(zVal)!=4 || sqlite3_strnicmp(zVal, "desc", 4)) ){ - *pzErr = sqlite3_mprintf("unrecognized order: %s", zVal); + sqlite3Fts3ErrMsg(pzErr, "unrecognized order: %s", zVal); rc = SQLITE_ERROR; } bDescIdx = (zVal[0]=='d' || zVal[0]=='D'); @@ -127009,7 +138550,7 @@ static int fts3InitVtab( if( nCol==0 ){ sqlite3_free((void*)aCol); aCol = 0; - rc = fts3ContentColumns(db, argv[1], zContent, &aCol, &nCol, &nString); + rc = fts3ContentColumns(db, argv[1], zContent,&aCol,&nCol,&nString,pzErr); /* If a languageid= option was specified, remove the language id ** column from the aCol[] array. */ @@ -127044,7 +138585,7 @@ static int fts3InitVtab( rc = fts3PrefixParameter(zPrefix, &nIndex, &aIndex); if( rc==SQLITE_ERROR ){ assert( zPrefix ); - *pzErr = sqlite3_mprintf("error parsing prefix parameter: %s", zPrefix); + sqlite3Fts3ErrMsg(pzErr, "error parsing prefix parameter: %s", zPrefix); } if( rc!=SQLITE_OK ) goto fts3_init_out; @@ -127126,7 +138667,7 @@ static int fts3InitVtab( } for(i=0; izReadExprlist = fts3ReadExprList(p, zUncompress, &rc); p->zWriteExprlist = fts3WriteExprList(p, zCompress, &rc); @@ -127223,6 +138764,19 @@ static void fts3SetEstimatedRows(sqlite3_index_info *pIdxInfo, i64 nRow){ #endif } +/* +** Set the SQLITE_INDEX_SCAN_UNIQUE flag in pIdxInfo->flags. Unless this +** extension is currently being used by a version of SQLite too old to +** support index-info flags. In that case this function is a no-op. +*/ +static void fts3SetUniqueFlag(sqlite3_index_info *pIdxInfo){ +#if SQLITE_VERSION_NUMBER>=3008012 + if( sqlite3_libversion_number()>=3008012 ){ + pIdxInfo->idxFlags |= SQLITE_INDEX_SCAN_UNIQUE; + } +#endif +} + /* ** Implementation of the xBestIndex method for FTS3 tables. There ** are three possible strategies, in order of preference: @@ -127313,6 +138867,9 @@ static int fts3BestIndexMethod(sqlite3_vtab *pVTab, sqlite3_index_info *pInfo){ } } + /* If using a docid=? or rowid=? strategy, set the UNIQUE flag. */ + if( pInfo->idxNum==FTS3_DOCID_SEARCH ) fts3SetUniqueFlag(pInfo); + iIdx = 1; if( iCons>=0 ){ pInfo->aConstraintUsage[iCons].argvIndex = iIdx++; @@ -127381,7 +138938,7 @@ static int fts3CloseMethod(sqlite3_vtab_cursor *pCursor){ sqlite3Fts3ExprFree(pCsr->pExpr); sqlite3Fts3FreeDeferredTokens(pCsr); sqlite3_free(pCsr->aDoclist); - sqlite3_free(pCsr->aMatchinfo); + sqlite3Fts3MIBufferFree(pCsr->pMIBuffer); assert( ((Fts3Table *)pCsr->base.pVtab)->pSegments==0 ); sqlite3_free(pCsr); return SQLITE_OK; @@ -127592,7 +139149,7 @@ static int fts3SelectLeaf( sqlite3_int64 *piLeaf, /* Selected leaf node */ sqlite3_int64 *piLeaf2 /* Selected leaf node */ ){ - int rc; /* Return code */ + int rc = SQLITE_OK; /* Return code */ int iHeight; /* Height of this node in tree */ assert( piLeaf || piLeaf2 ); @@ -127603,7 +139160,7 @@ static int fts3SelectLeaf( if( rc==SQLITE_OK && iHeight>1 ){ char *zBlob = 0; /* Blob read from %_segments table */ - int nBlob; /* Size of zBlob in bytes */ + int nBlob = 0; /* Size of zBlob in bytes */ if( piLeaf && piLeaf2 && (*piLeaf!=*piLeaf2) ){ rc = sqlite3Fts3ReadBlock(p, *piLeaf, &zBlob, &nBlob, 0); @@ -128230,26 +139787,33 @@ static int fts3DoclistOrMerge( ** ** The right-hand input doclist is overwritten by this function. */ -static void fts3DoclistPhraseMerge( +static int fts3DoclistPhraseMerge( int bDescDoclist, /* True if arguments are desc */ int nDist, /* Distance from left to right (1=adjacent) */ char *aLeft, int nLeft, /* Left doclist */ - char *aRight, int *pnRight /* IN/OUT: Right/output doclist */ + char **paRight, int *pnRight /* IN/OUT: Right/output doclist */ ){ sqlite3_int64 i1 = 0; sqlite3_int64 i2 = 0; sqlite3_int64 iPrev = 0; + char *aRight = *paRight; char *pEnd1 = &aLeft[nLeft]; char *pEnd2 = &aRight[*pnRight]; char *p1 = aLeft; char *p2 = aRight; char *p; int bFirstOut = 0; - char *aOut = aRight; + char *aOut; assert( nDist>0 ); - + if( bDescDoclist ){ + aOut = sqlite3_malloc(*pnRight + FTS3_VARINT_MAX); + if( aOut==0 ) return SQLITE_NOMEM; + }else{ + aOut = aRight; + } p = aOut; + fts3GetDeltaVarint3(&p1, pEnd1, 0, &i1); fts3GetDeltaVarint3(&p2, pEnd2, 0, &i2); @@ -128278,6 +139842,12 @@ static void fts3DoclistPhraseMerge( } *pnRight = (int)(p - aOut); + if( bDescDoclist ){ + sqlite3_free(aRight); + *paRight = aOut; + } + + return SQLITE_OK; } /* @@ -128402,8 +139972,22 @@ static int fts3TermSelectMerge( ){ if( pTS->aaOutput[0]==0 ){ /* If this is the first term selected, copy the doclist to the output - ** buffer using memcpy(). */ - pTS->aaOutput[0] = sqlite3_malloc(nDoclist); + ** buffer using memcpy(). + ** + ** Add FTS3_VARINT_MAX bytes of unused space to the end of the + ** allocation. This is so as to ensure that the buffer is big enough + ** to hold the current doclist AND'd with any other doclist. If the + ** doclists are stored in order=ASC order, this padding would not be + ** required (since the size of [doclistA AND doclistB] is always less + ** than or equal to the size of [doclistA] in that case). But this is + ** not true for order=DESC. For example, a doclist containing (1, -1) + ** may be smaller than (-1), as in the first example the -1 may be stored + ** as a single-byte delta, whereas in the second it must be stored as a + ** FTS3_VARINT_MAX byte varint. + ** + ** Similar padding is added in the fts3DoclistOrMerge() function. + */ + pTS->aaOutput[0] = sqlite3_malloc(nDoclist + FTS3_VARINT_MAX + 1); pTS->anOutput[0] = nDoclist; if( pTS->aaOutput[0] ){ memcpy(pTS->aaOutput[0], aDoclist, nDoclist); @@ -128500,7 +140084,7 @@ static int fts3SegReaderCursor( ** calls out here. */ if( iLevel<0 && p->aIndex ){ Fts3SegReader *pSeg = 0; - rc = sqlite3Fts3SegReaderPending(p, iIndex, zTerm, nTerm, isPrefix, &pSeg); + rc = sqlite3Fts3SegReaderPending(p, iIndex, zTerm, nTerm, isPrefix||isScan, &pSeg); if( rc==SQLITE_OK && pSeg ){ rc = fts3SegReaderCursorAppend(pCsr, pSeg); } @@ -128825,7 +140409,7 @@ static int fts3FilterMethod( int nVal, /* Number of elements in apVal */ sqlite3_value **apVal /* Arguments for the indexing scheme */ ){ - int rc; + int rc = SQLITE_OK; char *zSql; /* SQL statement used to access %_content */ int eSearch; Fts3Table *p = (Fts3Table *)pCursor->pVtab; @@ -128855,6 +140439,7 @@ static int fts3FilterMethod( /* In case the cursor has been used before, clear it now. */ sqlite3_finalize(pCsr->pStmt); sqlite3_free(pCsr->aDoclist); + sqlite3Fts3MIBufferFree(pCsr->pMIBuffer); sqlite3Fts3ExprFree(pCsr->pExpr); memset(&pCursor[1], 0, sizeof(Fts3Cursor)-sizeof(sqlite3_vtab_cursor)); @@ -128902,10 +140487,17 @@ static int fts3FilterMethod( ** row by docid. */ if( eSearch==FTS3_FULLSCAN_SEARCH ){ - zSql = sqlite3_mprintf( - "SELECT %s ORDER BY rowid %s", - p->zReadExprlist, (pCsr->bDesc ? "DESC" : "ASC") - ); + if( pDocidGe || pDocidLe ){ + zSql = sqlite3_mprintf( + "SELECT %s WHERE rowid BETWEEN %lld AND %lld ORDER BY rowid %s", + p->zReadExprlist, pCsr->iMinDocid, pCsr->iMaxDocid, + (pCsr->bDesc ? "DESC" : "ASC") + ); + }else{ + zSql = sqlite3_mprintf("SELECT %s ORDER BY rowid %s", + p->zReadExprlist, (pCsr->bDesc ? "DESC" : "ASC") + ); + } if( zSql ){ rc = sqlite3_prepare_v2(p->db, zSql, -1, &pCsr->pStmt, 0); sqlite3_free(zSql); @@ -129141,11 +140733,31 @@ static void fts3ReversePoslist(char *pStart, char **ppPoslist){ char *p = &(*ppPoslist)[-2]; char c = 0; + /* Skip backwards passed any trailing 0x00 bytes added by NearTrim() */ while( p>pStart && (c=*p--)==0 ); + + /* Search backwards for a varint with value zero (the end of the previous + ** poslist). This is an 0x00 byte preceded by some byte that does not + ** have the 0x80 bit set. */ while( p>pStart && (*p & 0x80) | c ){ c = *p--; } - if( p>pStart ){ p = &p[2]; } + assert( p==pStart || c==0 ); + + /* At this point p points to that preceding byte without the 0x80 bit + ** set. So to find the start of the poslist, skip forward 2 bytes then + ** over a varint. + ** + ** Normally. The other case is that p==pStart and the poslist to return + ** is the first in the doclist. In this case do not skip forward 2 bytes. + ** The second part of the if condition (c==0 && *ppPoslist>&p[2]) + ** is required for cases where the first byte of a doclist and the + ** doclist is empty. For example, if the first docid is 10, a doclist + ** that begins with: + ** + ** 0x0A 0x00 + */ + if( p>pStart || (c==0 && *ppPoslist>&p[2]) ){ p = &p[2]; } while( *p++&0x80 ); *ppPoslist = p; } @@ -129216,6 +140828,8 @@ static void fts3SnippetFunc( } if( !zEllipsis || !zEnd || !zStart ){ sqlite3_result_error_nomem(pContext); + }else if( nToken==0 ){ + sqlite3_result_text(pContext, "", -1, SQLITE_STATIC); }else if( SQLITE_OK==fts3CursorSeek(pContext, pCsr) ){ sqlite3Fts3Snippet(pContext, pCsr, zStart, zEnd, zEllipsis, iCol, nToken); } @@ -129489,7 +141103,7 @@ static void hashDestroy(void *p){ */ SQLITE_PRIVATE void sqlite3Fts3SimpleTokenizerModule(sqlite3_tokenizer_module const**ppModule); SQLITE_PRIVATE void sqlite3Fts3PorterTokenizerModule(sqlite3_tokenizer_module const**ppModule); -#ifdef SQLITE_ENABLE_FTS4_UNICODE61 +#ifndef SQLITE_DISABLE_FTS3_UNICODE SQLITE_PRIVATE void sqlite3Fts3UnicodeTokenizer(sqlite3_tokenizer_module const**ppModule); #endif #ifdef SQLITE_ENABLE_ICU @@ -129507,7 +141121,7 @@ SQLITE_PRIVATE int sqlite3Fts3Init(sqlite3 *db){ Fts3Hash *pHash = 0; const sqlite3_tokenizer_module *pSimple = 0; const sqlite3_tokenizer_module *pPorter = 0; -#ifdef SQLITE_ENABLE_FTS4_UNICODE61 +#ifndef SQLITE_DISABLE_FTS3_UNICODE const sqlite3_tokenizer_module *pUnicode = 0; #endif @@ -129516,7 +141130,7 @@ SQLITE_PRIVATE int sqlite3Fts3Init(sqlite3 *db){ sqlite3Fts3IcuTokenizerModule(&pIcu); #endif -#ifdef SQLITE_ENABLE_FTS4_UNICODE61 +#ifndef SQLITE_DISABLE_FTS3_UNICODE sqlite3Fts3UnicodeTokenizer(&pUnicode); #endif @@ -129544,7 +141158,7 @@ SQLITE_PRIVATE int sqlite3Fts3Init(sqlite3 *db){ if( sqlite3Fts3HashInsert(pHash, "simple", 7, (void *)pSimple) || sqlite3Fts3HashInsert(pHash, "porter", 7, (void *)pPorter) -#ifdef SQLITE_ENABLE_FTS4_UNICODE61 +#ifndef SQLITE_DISABLE_FTS3_UNICODE || sqlite3Fts3HashInsert(pHash, "unicode61", 10, (void *)pUnicode) #endif #ifdef SQLITE_ENABLE_ICU @@ -129651,14 +141265,17 @@ static void fts3EvalAllocateReaders( ** This function assumes that pList points to a buffer allocated using ** sqlite3_malloc(). This function takes responsibility for eventually ** freeing the buffer. +** +** SQLITE_OK is returned if successful, or SQLITE_NOMEM if an error occurs. */ -static void fts3EvalPhraseMergeToken( +static int fts3EvalPhraseMergeToken( Fts3Table *pTab, /* FTS Table pointer */ Fts3Phrase *p, /* Phrase to merge pList/nList into */ int iToken, /* Token pList/nList corresponds to */ char *pList, /* Pointer to doclist */ int nList /* Number of bytes in pList */ ){ + int rc = SQLITE_OK; assert( iToken!=p->iDoclistToken ); if( pList==0 ){ @@ -129697,13 +141314,16 @@ static void fts3EvalPhraseMergeToken( nDiff = p->iDoclistToken - iToken; } - fts3DoclistPhraseMerge(pTab->bDescIdx, nDiff, pLeft, nLeft, pRight,&nRight); + rc = fts3DoclistPhraseMerge( + pTab->bDescIdx, nDiff, pLeft, nLeft, &pRight, &nRight + ); sqlite3_free(pLeft); p->doclist.aAll = pRight; p->doclist.nAll = nRight; } if( iToken>p->iDoclistToken ) p->iDoclistToken = iToken; + return rc; } /* @@ -129729,7 +141349,7 @@ static int fts3EvalPhraseLoad( char *pThis = 0; rc = fts3TermSelect(pTab, pToken, p->iColumn, &nThis, &pThis); if( rc==SQLITE_OK ){ - fts3EvalPhraseMergeToken(pTab, p, iToken, pThis, nThis); + rc = fts3EvalPhraseMergeToken(pTab, p, iToken, pThis, nThis); } } assert( pToken->pSegcsr==0 ); @@ -129874,7 +141494,6 @@ static int fts3EvalPhraseStart(Fts3Cursor *pCsr, int bOptOk, Fts3Phrase *p){ int bIncrOk = (bOptOk && pCsr->bDesc==pTab->bDescIdx && p->nToken<=MAX_INCR_PHRASE_TOKENS && p->nToken>0 - && p->nToken<=MAX_INCR_PHRASE_TOKENS && p->nToken>0 #ifdef SQLITE_TEST && pTab->bNoIncrDoclist==0 #endif @@ -129994,6 +141613,7 @@ SQLITE_PRIVATE void sqlite3Fts3DoclistNext( p += sqlite3Fts3GetVarint(p, piDocid); }else{ fts3PoslistCopy(0, &p); + while( p<&aDoclist[nDoclist] && *p==0 ) p++; if( p>=&aDoclist[nDoclist] ){ *pbEof = 1; }else{ @@ -130165,7 +141785,7 @@ static int fts3EvalIncrPhraseNext( bMaxSet = 1; } } - assert( rc!=SQLITE_OK || a[p->nToken-1].bIgnore==0 ); + assert( rc!=SQLITE_OK || (p->nToken>=1 && a[p->nToken-1].bIgnore==0) ); assert( rc!=SQLITE_OK || bMaxSet ); /* Keep advancing iterators until they all point to the same document */ @@ -130271,12 +141891,14 @@ static void fts3EvalStartReaders( ){ if( pExpr && SQLITE_OK==*pRc ){ if( pExpr->eType==FTSQUERY_PHRASE ){ - int i; int nToken = pExpr->pPhrase->nToken; - for(i=0; ipPhrase->aToken[i].pDeferred==0 ) break; + if( nToken ){ + int i; + for(i=0; ipPhrase->aToken[i].pDeferred==0 ) break; + } + pExpr->bDeferred = (i==nToken); } - pExpr->bDeferred = (i==nToken); *pRc = fts3EvalPhraseStart(pCsr, 1, pExpr->pPhrase); }else{ fts3EvalStartReaders(pCsr, pExpr->pLeft, pRc); @@ -130531,9 +142153,13 @@ static int fts3EvalSelectDeferred( char *pList = 0; rc = fts3TermSelect(pTab, pToken, pTC->iCol, &nList, &pList); assert( rc==SQLITE_OK || pList==0 ); + if( rc==SQLITE_OK ){ + rc = fts3EvalPhraseMergeToken( + pTab, pTC->pPhrase, pTC->iToken,pList,nList + ); + } if( rc==SQLITE_OK ){ int nCount; - fts3EvalPhraseMergeToken(pTab, pTC->pPhrase, pTC->iToken,pList,nList); nCount = fts3DoclistCountDocids( pTC->pPhrase->doclist.aAll, pTC->pPhrase->doclist.nAll ); @@ -130711,7 +142337,7 @@ static int fts3EvalNearTrim( ** 2. NEAR is treated as AND. If the expression is "x NEAR y", it is ** advanced to point to the next row that matches "x AND y". ** -** See fts3EvalTestDeferredAndNear() for details on testing if a row is +** See sqlite3Fts3EvalTestDeferred() for details on testing if a row is ** really a match, taking into account deferred tokens and NEAR operators. */ static void fts3EvalNextRow( @@ -130758,6 +142384,22 @@ static void fts3EvalNextRow( } pExpr->iDocid = pLeft->iDocid; pExpr->bEof = (pLeft->bEof || pRight->bEof); + if( pExpr->eType==FTSQUERY_NEAR && pExpr->bEof ){ + if( pRight->pPhrase && pRight->pPhrase->doclist.aAll ){ + Fts3Doclist *pDl = &pRight->pPhrase->doclist; + while( *pRc==SQLITE_OK && pRight->bEof==0 ){ + memset(pDl->pList, 0, pDl->nList); + fts3EvalNextRow(pCsr, pRight, pRc); + } + } + if( pLeft->pPhrase && pLeft->pPhrase->doclist.aAll ){ + Fts3Doclist *pDl = &pLeft->pPhrase->doclist; + while( *pRc==SQLITE_OK && pLeft->bEof==0 ){ + memset(pDl->pList, 0, pDl->nList); + fts3EvalNextRow(pCsr, pLeft, pRc); + } + } + } } break; } @@ -130915,7 +142557,7 @@ static int fts3EvalNearTest(Fts3Expr *pExpr, int *pRc){ } /* -** This function is a helper function for fts3EvalTestDeferredAndNear(). +** This function is a helper function for sqlite3Fts3EvalTestDeferred(). ** Assuming no error occurs or has occurred, It returns non-zero if the ** expression passed as the second argument matches the row that pCsr ** currently points to, or zero if it does not. @@ -131036,7 +142678,7 @@ static int fts3EvalTestExpr( ** Or, if no error occurs and it seems the current row does match the FTS ** query, return 0. */ -static int fts3EvalTestDeferredAndNear(Fts3Cursor *pCsr, int *pRc){ +SQLITE_PRIVATE int sqlite3Fts3EvalTestDeferred(Fts3Cursor *pCsr, int *pRc){ int rc = *pRc; int bMiss = 0; if( rc==SQLITE_OK ){ @@ -131083,7 +142725,7 @@ static int fts3EvalNext(Fts3Cursor *pCsr){ pCsr->isRequireSeek = 1; pCsr->isMatchinfoNeeded = 1; pCsr->iPrevId = pExpr->iDocid; - }while( pCsr->isEof==0 && fts3EvalTestDeferredAndNear(pCsr, &rc) ); + }while( pCsr->isEof==0 && sqlite3Fts3EvalTestDeferred(pCsr, &rc) ); } /* Check if the cursor is past the end of the docid range specified @@ -131130,6 +142772,7 @@ static void fts3EvalRestart( } pPhrase->doclist.pNextDocid = 0; pPhrase->doclist.iDocid = 0; + pPhrase->pOrPoslist = 0; } pExpr->iDocid = 0; @@ -131243,7 +142886,7 @@ static int fts3EvalGatherStats( pCsr->iPrevId = pRoot->iDocid; }while( pCsr->isEof==0 && pRoot->eType==FTSQUERY_NEAR - && fts3EvalTestDeferredAndNear(pCsr, &rc) + && sqlite3Fts3EvalTestDeferred(pCsr, &rc) ); if( rc==SQLITE_OK && pCsr->isEof==0 ){ @@ -131268,7 +142911,6 @@ static int fts3EvalGatherStats( fts3EvalNextRow(pCsr, pRoot, &rc); assert( pRoot->bEof==0 ); }while( pRoot->iDocid!=iDocid && rc==SQLITE_OK ); - fts3EvalTestDeferredAndNear(pCsr, &rc); } } return rc; @@ -131375,13 +143017,13 @@ SQLITE_PRIVATE int sqlite3Fts3EvalPhrasePoslist( iDocid = pExpr->iDocid; pIter = pPhrase->doclist.pList; if( iDocid!=pCsr->iPrevId || pExpr->bEof ){ + int rc = SQLITE_OK; int bDescDoclist = pTab->bDescIdx; /* For DOCID_CMP macro */ - int iMul; /* +1 if csr dir matches index dir, else -1 */ int bOr = 0; - u8 bEof = 0; u8 bTreeEof = 0; Fts3Expr *p; /* Used to iterate from pExpr to root */ Fts3Expr *pNear; /* Most senior NEAR ancestor (or pExpr) */ + int bMatch; /* Check if this phrase descends from an OR expression node. If not, ** return NULL. Otherwise, the entry that corresponds to docid @@ -131400,74 +143042,62 @@ SQLITE_PRIVATE int sqlite3Fts3EvalPhrasePoslist( ** an incremental phrase. Load the entire doclist for the phrase ** into memory in this case. */ if( pPhrase->bIncr ){ - int rc = SQLITE_OK; - int bEofSave = pExpr->bEof; - fts3EvalRestart(pCsr, pExpr, &rc); - while( rc==SQLITE_OK && !pExpr->bEof ){ - fts3EvalNextRow(pCsr, pExpr, &rc); - if( bEofSave==0 && pExpr->iDocid==iDocid ) break; + int bEofSave = pNear->bEof; + fts3EvalRestart(pCsr, pNear, &rc); + while( rc==SQLITE_OK && !pNear->bEof ){ + fts3EvalNextRow(pCsr, pNear, &rc); + if( bEofSave==0 && pNear->iDocid==iDocid ) break; } - pIter = pPhrase->doclist.pList; assert( rc!=SQLITE_OK || pPhrase->bIncr==0 ); - if( rc!=SQLITE_OK ) return rc; } - - iMul = ((pCsr->bDesc==bDescDoclist) ? 1 : -1); - while( bTreeEof==1 - && pNear->bEof==0 - && (DOCID_CMP(pNear->iDocid, pCsr->iPrevId) * iMul)<0 - ){ - int rc = SQLITE_OK; - fts3EvalNextRow(pCsr, pExpr, &rc); - if( rc!=SQLITE_OK ) return rc; - iDocid = pExpr->iDocid; - pIter = pPhrase->doclist.pList; + if( bTreeEof ){ + while( rc==SQLITE_OK && !pNear->bEof ){ + fts3EvalNextRow(pCsr, pNear, &rc); + } } + if( rc!=SQLITE_OK ) return rc; - bEof = (pPhrase->doclist.nAll==0); - assert( bDescDoclist==0 || bDescDoclist==1 ); - assert( pCsr->bDesc==0 || pCsr->bDesc==1 ); + bMatch = 1; + for(p=pNear; p; p=p->pLeft){ + u8 bEof = 0; + Fts3Expr *pTest = p; + Fts3Phrase *pPh; + assert( pTest->eType==FTSQUERY_NEAR || pTest->eType==FTSQUERY_PHRASE ); + if( pTest->eType==FTSQUERY_NEAR ) pTest = pTest->pRight; + assert( pTest->eType==FTSQUERY_PHRASE ); + pPh = pTest->pPhrase; - if( bEof==0 ){ + pIter = pPh->pOrPoslist; + iDocid = pPh->iOrDocid; if( pCsr->bDesc==bDescDoclist ){ - int dummy; - if( pNear->bEof ){ - /* This expression is already at EOF. So position it to point to the - ** last entry in the doclist at pPhrase->doclist.aAll[]. Variable - ** iDocid is already set for this entry, so all that is required is - ** to set pIter to point to the first byte of the last position-list - ** in the doclist. - ** - ** It would also be correct to set pIter and iDocid to zero. In - ** this case, the first call to sqltie3Fts4DoclistPrev() below - ** would also move the iterator to point to the last entry in the - ** doclist. However, this is expensive, as to do so it has to - ** iterate through the entire doclist from start to finish (since - ** it does not know the docid for the last entry). */ - pIter = &pPhrase->doclist.aAll[pPhrase->doclist.nAll-1]; - fts3ReversePoslist(pPhrase->doclist.aAll, &pIter); - } - while( (pIter==0 || DOCID_CMP(iDocid, pCsr->iPrevId)>0 ) && bEof==0 ){ - sqlite3Fts3DoclistPrev( - bDescDoclist, pPhrase->doclist.aAll, pPhrase->doclist.nAll, - &pIter, &iDocid, &dummy, &bEof - ); - } - }else{ - if( pNear->bEof ){ - pIter = 0; - iDocid = 0; - } + bEof = !pPh->doclist.nAll || + (pIter >= (pPh->doclist.aAll + pPh->doclist.nAll)); while( (pIter==0 || DOCID_CMP(iDocid, pCsr->iPrevId)<0 ) && bEof==0 ){ sqlite3Fts3DoclistNext( - bDescDoclist, pPhrase->doclist.aAll, pPhrase->doclist.nAll, + bDescDoclist, pPh->doclist.aAll, pPh->doclist.nAll, &pIter, &iDocid, &bEof ); } + }else{ + bEof = !pPh->doclist.nAll || (pIter && pIter<=pPh->doclist.aAll); + while( (pIter==0 || DOCID_CMP(iDocid, pCsr->iPrevId)>0 ) && bEof==0 ){ + int dummy; + sqlite3Fts3DoclistPrev( + bDescDoclist, pPh->doclist.aAll, pPh->doclist.nAll, + &pIter, &iDocid, &dummy, &bEof + ); + } } + pPh->pOrPoslist = pIter; + pPh->iOrDocid = iDocid; + if( bEof || iDocid!=pCsr->iPrevId ) bMatch = 0; } - if( bEof || iDocid!=pCsr->iPrevId ) pIter = 0; + if( bMatch ){ + pIter = pPhrase->pOrPoslist; + }else{ + pIter = 0; + } } if( pIter==0 ) return SQLITE_OK; @@ -131479,10 +143109,13 @@ SQLITE_PRIVATE int sqlite3Fts3EvalPhrasePoslist( } while( iThis */ @@ -131656,7 +143290,7 @@ static int fts3auxConnectMethod( return SQLITE_OK; bad_args: - *pzErr = sqlite3_mprintf("invalid arguments to fts4aux constructor"); + sqlite3Fts3ErrMsg(pzErr, "invalid arguments to fts4aux constructor"); return SQLITE_ERROR; } @@ -132108,6 +143742,7 @@ SQLITE_PRIVATE int sqlite3Fts3InitAux(sqlite3 *db){ ** syntax is relatively simple, the whole tokenizer/parser system is ** hand-coded. */ +/* #include "fts3Int.h" */ #if !defined(SQLITE_CORE) || defined(SQLITE_ENABLE_FTS3) /* @@ -132282,7 +143917,7 @@ static int getNextToken( /* Set variable i to the maximum number of bytes of input to tokenize. */ for(i=0; ieType==eType; p=p->pLeft){ - assert( p->pParent==0 || p->pParent->pLeft==p ); - assert( p->pLeft && p->pRight ); - } - - /* This loop runs once for each leaf in the tree of eType nodes. */ - while( 1 ){ - int iLvl; - Fts3Expr *pParent = p->pParent; /* Current parent of p */ - - assert( pParent==0 || pParent->pLeft==p ); - p->pParent = 0; - if( pParent ){ - pParent->pLeft = 0; - }else{ - pRoot = 0; - } - rc = fts3ExprBalance(&p, nMaxDepth-1); - if( rc!=SQLITE_OK ) break; - - for(iLvl=0; p && iLvlpLeft = apLeaf[iLvl]; - pFree->pRight = p; - pFree->pLeft->pParent = pFree; - pFree->pRight->pParent = pFree; - - p = pFree; - pFree = pFree->pParent; - p->pParent = 0; - apLeaf[iLvl] = 0; - } - } - if( p ){ - sqlite3Fts3ExprFree(p); - rc = SQLITE_TOOBIG; - break; - } - - /* If that was the last leaf node, break out of the loop */ - if( pParent==0 ) break; - - /* Set $p to point to the next leaf in the tree of eType nodes */ - for(p=pParent->pRight; p->eType==eType; p=p->pLeft); - - /* Remove pParent from the original tree. */ - assert( pParent->pParent==0 || pParent->pParent->pLeft==pParent ); - pParent->pRight->pParent = pParent->pParent; - if( pParent->pParent ){ - pParent->pParent->pLeft = pParent->pRight; - }else{ - assert( pParent==pRoot ); - pRoot = pParent->pRight; - } - - /* Link pParent into the free node list. It will be used as an - ** internal node of the new tree. */ - pParent->pParent = pFree; - pFree = pParent; + if( rc==SQLITE_OK ){ + if( (eType==FTSQUERY_AND || eType==FTSQUERY_OR) ){ + Fts3Expr **apLeaf; + apLeaf = (Fts3Expr **)sqlite3_malloc(sizeof(Fts3Expr *) * nMaxDepth); + if( 0==apLeaf ){ + rc = SQLITE_NOMEM; + }else{ + memset(apLeaf, 0, sizeof(Fts3Expr *) * nMaxDepth); } if( rc==SQLITE_OK ){ - p = 0; - for(i=0; ipParent = 0; + int i; + Fts3Expr *p; + + /* Set $p to point to the left-most leaf in the tree of eType nodes. */ + for(p=pRoot; p->eType==eType; p=p->pLeft){ + assert( p->pParent==0 || p->pParent->pLeft==p ); + assert( p->pLeft && p->pRight ); + } + + /* This loop runs once for each leaf in the tree of eType nodes. */ + while( 1 ){ + int iLvl; + Fts3Expr *pParent = p->pParent; /* Current parent of p */ + + assert( pParent==0 || pParent->pLeft==p ); + p->pParent = 0; + if( pParent ){ + pParent->pLeft = 0; + }else{ + pRoot = 0; + } + rc = fts3ExprBalance(&p, nMaxDepth-1); + if( rc!=SQLITE_OK ) break; + + for(iLvl=0; p && iLvlpLeft = apLeaf[iLvl]; pFree->pRight = p; - pFree->pLeft = apLeaf[i]; pFree->pLeft->pParent = pFree; pFree->pRight->pParent = pFree; p = pFree; pFree = pFree->pParent; p->pParent = 0; + apLeaf[iLvl] = 0; } } + if( p ){ + sqlite3Fts3ExprFree(p); + rc = SQLITE_TOOBIG; + break; + } + + /* If that was the last leaf node, break out of the loop */ + if( pParent==0 ) break; + + /* Set $p to point to the next leaf in the tree of eType nodes */ + for(p=pParent->pRight; p->eType==eType; p=p->pLeft); + + /* Remove pParent from the original tree. */ + assert( pParent->pParent==0 || pParent->pParent->pLeft==pParent ); + pParent->pRight->pParent = pParent->pParent; + if( pParent->pParent ){ + pParent->pParent->pLeft = pParent->pRight; + }else{ + assert( pParent==pRoot ); + pRoot = pParent->pRight; + } + + /* Link pParent into the free node list. It will be used as an + ** internal node of the new tree. */ + pParent->pParent = pFree; + pFree = pParent; } - pRoot = p; - }else{ - /* An error occurred. Delete the contents of the apLeaf[] array - ** and pFree list. Everything else is cleaned up by the call to - ** sqlite3Fts3ExprFree(pRoot) below. */ - Fts3Expr *pDel; - for(i=0; ipParent; - sqlite3_free(pDel); + + if( rc==SQLITE_OK ){ + p = 0; + for(i=0; ipParent = 0; + }else{ + assert( pFree!=0 ); + pFree->pRight = p; + pFree->pLeft = apLeaf[i]; + pFree->pLeft->pParent = pFree; + pFree->pRight->pParent = pFree; + + p = pFree; + pFree = pFree->pParent; + p->pParent = 0; + } + } + } + pRoot = p; + }else{ + /* An error occurred. Delete the contents of the apLeaf[] array + ** and pFree list. Everything else is cleaned up by the call to + ** sqlite3Fts3ExprFree(pRoot) below. */ + Fts3Expr *pDel; + for(i=0; ipParent; + sqlite3_free(pDel); + } } + + assert( pFree==0 ); + sqlite3_free( apLeaf ); + } + }else if( eType==FTSQUERY_NOT ){ + Fts3Expr *pLeft = pRoot->pLeft; + Fts3Expr *pRight = pRoot->pRight; + + pRoot->pLeft = 0; + pRoot->pRight = 0; + pLeft->pParent = 0; + pRight->pParent = 0; + + rc = fts3ExprBalance(&pLeft, nMaxDepth-1); + if( rc==SQLITE_OK ){ + rc = fts3ExprBalance(&pRight, nMaxDepth-1); } - assert( pFree==0 ); - sqlite3_free( apLeaf ); + if( rc!=SQLITE_OK ){ + sqlite3Fts3ExprFree(pRight); + sqlite3Fts3ExprFree(pLeft); + }else{ + assert( pLeft && pRight ); + pRoot->pLeft = pLeft; + pLeft->pParent = pRoot; + pRoot->pRight = pRight; + pRight->pParent = pRoot; + } } } - + if( rc!=SQLITE_OK ){ sqlite3Fts3ExprFree(pRoot); pRoot = 0; @@ -133114,13 +144775,13 @@ SQLITE_PRIVATE int sqlite3Fts3ExprParse( sqlite3Fts3ExprFree(*ppExpr); *ppExpr = 0; if( rc==SQLITE_TOOBIG ){ - *pzErr = sqlite3_mprintf( + sqlite3Fts3ErrMsg(pzErr, "FTS expression tree is too large (maximum depth %d)", SQLITE_FTS3_MAX_EXPR_DEPTH ); rc = SQLITE_ERROR; }else if( rc==SQLITE_ERROR ){ - *pzErr = sqlite3_mprintf("malformed MATCH expression: [%s]", z); + sqlite3Fts3ErrMsg(pzErr, "malformed MATCH expression: [%s]", z); } } @@ -133401,12 +145062,14 @@ SQLITE_PRIVATE int sqlite3Fts3ExprInitTestInterface(sqlite3* db){ ** * The FTS3 module is being built into the core of ** SQLite (in which case SQLITE_ENABLE_FTS3 is defined). */ +/* #include "fts3Int.h" */ #if !defined(SQLITE_CORE) || defined(SQLITE_ENABLE_FTS3) /* #include */ /* #include */ /* #include */ +/* #include "fts3_hash.h" */ /* ** Malloc and Free functions @@ -133784,6 +145447,7 @@ SQLITE_PRIVATE void *sqlite3Fts3HashInsert( ** * The FTS3 module is being built into the core of ** SQLite (in which case SQLITE_ENABLE_FTS3 is defined). */ +/* #include "fts3Int.h" */ #if !defined(SQLITE_CORE) || defined(SQLITE_ENABLE_FTS3) /* #include */ @@ -133791,6 +145455,7 @@ SQLITE_PRIVATE void *sqlite3Fts3HashInsert( /* #include */ /* #include */ +/* #include "fts3_tokenizer.h" */ /* ** Class derived from sqlite3_tokenizer @@ -133943,7 +145608,7 @@ static int isVowel(const char *z){ ** by a consonant. ** ** In this routine z[] is in reverse order. So we are really looking -** for an instance of of a consonant followed by a vowel. +** for an instance of a consonant followed by a vowel. */ static int m_gt_0(const char *z){ while( isVowel(z) ){ z++; } @@ -134448,6 +146113,7 @@ SQLITE_PRIVATE void sqlite3Fts3PorterTokenizerModule( ** * The FTS3 module is being built into the core of ** SQLite (in which case SQLITE_ENABLE_FTS3 is defined). */ +/* #include "fts3Int.h" */ #if !defined(SQLITE_CORE) || defined(SQLITE_ENABLE_FTS3) /* #include */ @@ -134493,7 +146159,7 @@ static void scalarFunc( if( argc==2 ){ void *pOld; int n = sqlite3_value_bytes(argv[1]); - if( n!=sizeof(pPtr) ){ + if( zName==0 || n!=sizeof(pPtr) ){ sqlite3_result_error(context, "argument type mismatch", -1); return; } @@ -134504,7 +146170,9 @@ static void scalarFunc( return; } }else{ - pPtr = sqlite3Fts3HashFind(pHash, zName, nName); + if( zName ){ + pPtr = sqlite3Fts3HashFind(pHash, zName, nName); + } if( !pPtr ){ char *zErr = sqlite3_mprintf("unknown tokenizer: %s", zName); sqlite3_result_error(context, zErr, -1); @@ -134585,12 +146253,16 @@ SQLITE_PRIVATE int sqlite3Fts3InitTokenizer( zEnd = &zCopy[strlen(zCopy)]; z = (char *)sqlite3Fts3NextToken(zCopy, &n); + if( z==0 ){ + assert( n==0 ); + z = zCopy; + } z[n] = '\0'; sqlite3Fts3Dequote(z); m = (sqlite3_tokenizer_module *)sqlite3Fts3HashFind(pHash,z,(int)strlen(z)+1); if( !m ){ - *pzErr = sqlite3_mprintf("unknown tokenizer: %s", z); + sqlite3Fts3ErrMsg(pzErr, "unknown tokenizer: %s", z); rc = SQLITE_ERROR; }else{ char const **aArg = 0; @@ -134613,7 +146285,7 @@ SQLITE_PRIVATE int sqlite3Fts3InitTokenizer( rc = m->xCreate(iArg, aArg, ppTok); assert( rc!=SQLITE_OK || *ppTok ); if( rc!=SQLITE_OK ){ - *pzErr = sqlite3_mprintf("unknown tokenizer"); + sqlite3Fts3ErrMsg(pzErr, "unknown tokenizer"); }else{ (*ppTok)->pModule = m; } @@ -134697,9 +146369,9 @@ static void testFunc( p = (sqlite3_tokenizer_module *)sqlite3Fts3HashFind(pHash, zName, nName+1); if( !p ){ - char *zErr = sqlite3_mprintf("unknown tokenizer: %s", zName); - sqlite3_result_error(context, zErr, -1); - sqlite3_free(zErr); + char *zErr2 = sqlite3_mprintf("unknown tokenizer: %s", zName); + sqlite3_result_error(context, zErr2, -1); + sqlite3_free(zErr2); return; } @@ -134937,6 +146609,7 @@ SQLITE_PRIVATE int sqlite3Fts3InitHashTable( ** * The FTS3 module is being built into the core of ** SQLite (in which case SQLITE_ENABLE_FTS3 is defined). */ +/* #include "fts3Int.h" */ #if !defined(SQLITE_CORE) || defined(SQLITE_ENABLE_FTS3) /* #include */ @@ -134944,6 +146617,7 @@ SQLITE_PRIVATE int sqlite3Fts3InitHashTable( /* #include */ /* #include */ +/* #include "fts3_tokenizer.h" */ typedef struct simple_tokenizer { sqlite3_tokenizer base; @@ -135188,6 +146862,7 @@ SQLITE_PRIVATE void sqlite3Fts3SimpleTokenizerModule( ** pos: Token offset of token within input. ** */ +/* #include "fts3Int.h" */ #if !defined(SQLITE_CORE) || defined(SQLITE_ENABLE_FTS3) /* #include */ @@ -135234,7 +146909,7 @@ static int fts3tokQueryTokenizer( p = (sqlite3_tokenizer_module *)sqlite3Fts3HashFind(pHash, zName, nName+1); if( !p ){ - *pzErr = sqlite3_mprintf("unknown tokenizer: %s", zName); + sqlite3Fts3ErrMsg(pzErr, "unknown tokenizer: %s", zName); return SQLITE_ERROR; } @@ -135312,7 +146987,7 @@ static int fts3tokConnectMethod( sqlite3_vtab **ppVtab, /* OUT: New sqlite3_vtab object */ char **pzErr /* OUT: sqlite3_malloc'd error message */ ){ - Fts3tokTable *pTab; + Fts3tokTable *pTab = 0; const sqlite3_tokenizer_module *pMod = 0; sqlite3_tokenizer *pTok = 0; int rc; @@ -135623,6 +147298,7 @@ SQLITE_PRIVATE int sqlite3Fts3InitTok(sqlite3 *db, Fts3Hash *pHash){ ** code in fts3.c. */ +/* #include "fts3Int.h" */ #if !defined(SQLITE_CORE) || defined(SQLITE_ENABLE_FTS3) /* #include */ @@ -135931,7 +147607,7 @@ static int fts3SqlStmt( /* 25 */ "", /* 26 */ "DELETE FROM %Q.'%q_segdir' WHERE level BETWEEN ? AND ?", -/* 27 */ "SELECT DISTINCT level / (1024 * ?) FROM %Q.'%q_segdir'", +/* 27 */ "SELECT ? UNION SELECT level / (1024 * ?) FROM %Q.'%q_segdir'", /* This statement is used to determine which level to read the input from ** when performing an incremental merge. It returns the absolute level number @@ -136465,10 +148141,12 @@ static int fts3PendingTermsAdd( */ static int fts3PendingTermsDocid( Fts3Table *p, /* Full-text table handle */ + int bDelete, /* True if this op is a delete */ int iLangid, /* Language id of row being written */ sqlite_int64 iDocid /* Docid of row being written */ ){ assert( iLangid>=0 ); + assert( bDelete==1 || bDelete==0 ); /* TODO(shess) Explore whether partially flushing the buffer on ** forced-flush would provide better performance. I suspect that if @@ -136476,7 +148154,8 @@ static int fts3PendingTermsDocid( ** buffer was half empty, that would let the less frequent terms ** generate longer doclists. */ - if( iDocid<=p->iPrevDocid + if( iDocidiPrevDocid + || (iDocid==p->iPrevDocid && p->bPrevDelete==0) || p->iPrevLangid!=iLangid || p->nPendingData>p->nMaxPendingData ){ @@ -136485,6 +148164,7 @@ static int fts3PendingTermsDocid( } p->iPrevDocid = iDocid; p->iPrevLangid = iLangid; + p->bPrevDelete = bDelete; return SQLITE_OK; } @@ -136674,7 +148354,8 @@ static void fts3DeleteTerms( if( SQLITE_ROW==sqlite3_step(pSelect) ){ int i; int iLangid = langidFromSelect(p, pSelect); - rc = fts3PendingTermsDocid(p, iLangid, sqlite3_column_int64(pSelect, 0)); + i64 iDocid = sqlite3_column_int64(pSelect, 0); + rc = fts3PendingTermsDocid(p, 1, iLangid, iDocid); for(i=1; rc==SQLITE_OK && i<=p->nColumn; i++){ int iCol = i-1; if( p->abNotindexed[iCol]==0 ){ @@ -136922,14 +148603,19 @@ static int fts3SegReaderNext( if( fts3SegReaderIsPending(pReader) ){ Fts3HashElem *pElem = *(pReader->ppNextElem); - if( pElem==0 ){ - pReader->aNode = 0; - }else{ + sqlite3_free(pReader->aNode); + pReader->aNode = 0; + if( pElem ){ + char *aCopy; PendingList *pList = (PendingList *)fts3HashData(pElem); + int nCopy = pList->nData+1; pReader->zTerm = (char *)fts3HashKey(pElem); pReader->nTerm = fts3HashKeysize(pElem); - pReader->nNode = pReader->nDoclist = pList->nData + 1; - pReader->aNode = pReader->aDoclist = pList->aData; + aCopy = (char*)sqlite3_malloc(nCopy); + if( !aCopy ) return SQLITE_NOMEM; + memcpy(aCopy, pList->aData, nCopy); + pReader->nNode = pReader->nDoclist = nCopy; + pReader->aNode = pReader->aDoclist = aCopy; pReader->ppNextElem++; assert( pReader->aNode ); } @@ -137169,12 +148855,14 @@ SQLITE_PRIVATE int sqlite3Fts3MsrOvfl( ** second argument. */ SQLITE_PRIVATE void sqlite3Fts3SegReaderFree(Fts3SegReader *pReader){ - if( pReader && !fts3SegReaderIsPending(pReader) ){ - sqlite3_free(pReader->zTerm); + if( pReader ){ + if( !fts3SegReaderIsPending(pReader) ){ + sqlite3_free(pReader->zTerm); + } if( !fts3SegReaderIsRootOnly(pReader) ){ sqlite3_free(pReader->aNode); - sqlite3_blob_close(pReader->pBlob); } + sqlite3_blob_close(pReader->pBlob); } sqlite3_free(pReader); } @@ -137230,7 +148918,10 @@ SQLITE_PRIVATE int sqlite3Fts3SegReaderNew( ** an array of pending terms by term. This occurs as part of flushing ** the contents of the pending-terms hash table to the database. */ -static int fts3CompareElemByTerm(const void *lhs, const void *rhs){ +static int SQLITE_CDECL fts3CompareElemByTerm( + const void *lhs, + const void *rhs +){ char *z1 = fts3HashKey(*(Fts3HashElem **)lhs); char *z2 = fts3HashKey(*(Fts3HashElem **)rhs); int n1 = fts3HashKeysize(*(Fts3HashElem **)lhs); @@ -138687,8 +150378,8 @@ static int fts3PromoteSegments( if( bOk ){ int iIdx = 0; - sqlite3_stmt *pUpdate1; - sqlite3_stmt *pUpdate2; + sqlite3_stmt *pUpdate1 = 0; + sqlite3_stmt *pUpdate2 = 0; if( rc==SQLITE_OK ){ rc = fts3SqlStmt(p, SQL_UPDATE_LEVEL_IDX, &pUpdate1, 0); @@ -139046,7 +150737,8 @@ static int fts3DoOptimize(Fts3Table *p, int bReturnDone){ rc = fts3SqlStmt(p, SQL_SELECT_ALL_LANGID, &pAllLangid, 0); if( rc==SQLITE_OK ){ int rc2; - sqlite3_bind_int(pAllLangid, 1, p->nIndex); + sqlite3_bind_int(pAllLangid, 1, p->iPrevLangid); + sqlite3_bind_int(pAllLangid, 2, p->nIndex); while( sqlite3_step(pAllLangid)==SQLITE_ROW ){ int i; int iLangid = sqlite3_column_int(pAllLangid, 0); @@ -139113,7 +150805,7 @@ static int fts3DoRebuild(Fts3Table *p){ while( rc==SQLITE_OK && SQLITE_ROW==sqlite3_step(pStmt) ){ int iCol; int iLangid = langidFromSelect(p, pStmt); - rc = fts3PendingTermsDocid(p, iLangid, sqlite3_column_int64(pStmt, 0)); + rc = fts3PendingTermsDocid(p, 0, iLangid, sqlite3_column_int64(pStmt, 0)); memset(aSz, 0, sizeof(aSz[0]) * (p->nColumn+1)); for(iCol=0; rc==SQLITE_OK && iColnColumn; iCol++){ if( p->abNotindexed[iCol]==0 ){ @@ -140378,7 +152070,7 @@ static int fts3IncrmergeHintPop(Blob *pHint, i64 *piAbsLevel, int *pnInput){ pHint->n = i; i += sqlite3Fts3GetVarint(&pHint->a[i], piAbsLevel); i += fts3GetVarint32(&pHint->a[i], pnInput); - if( i!=nHint ) return SQLITE_CORRUPT_VTAB; + if( i!=nHint ) return FTS_CORRUPT_VTAB; return SQLITE_OK; } @@ -140746,7 +152438,8 @@ static int fts3IntegrityCheck(Fts3Table *p, int *pbOk){ rc = fts3SqlStmt(p, SQL_SELECT_ALL_LANGID, &pAllLangid, 0); if( rc==SQLITE_OK ){ int rc2; - sqlite3_bind_int(pAllLangid, 1, p->nIndex); + sqlite3_bind_int(pAllLangid, 1, p->iPrevLangid); + sqlite3_bind_int(pAllLangid, 2, p->nIndex); while( rc==SQLITE_OK && sqlite3_step(pAllLangid)==SQLITE_ROW ){ int iLangid = sqlite3_column_int(pAllLangid, 0); int i; @@ -140759,7 +152452,6 @@ static int fts3IntegrityCheck(Fts3Table *p, int *pbOk){ } /* This block calculates the checksum according to the %_content table */ - rc = fts3SqlStmt(p, SQL_SELECT_ALL_LANGID, &pAllLangid, 0); if( rc==SQLITE_OK ){ sqlite3_tokenizer_module const *pModule = p->pTokenizer->pModule; sqlite3_stmt *pStmt = 0; @@ -140779,34 +152471,36 @@ static int fts3IntegrityCheck(Fts3Table *p, int *pbOk){ int iCol; for(iCol=0; rc==SQLITE_OK && iColnColumn; iCol++){ - const char *zText = (const char *)sqlite3_column_text(pStmt, iCol+1); - int nText = sqlite3_column_bytes(pStmt, iCol+1); - sqlite3_tokenizer_cursor *pT = 0; + if( p->abNotindexed[iCol]==0 ){ + const char *zText = (const char *)sqlite3_column_text(pStmt, iCol+1); + int nText = sqlite3_column_bytes(pStmt, iCol+1); + sqlite3_tokenizer_cursor *pT = 0; - rc = sqlite3Fts3OpenTokenizer(p->pTokenizer, iLang, zText, nText, &pT); - while( rc==SQLITE_OK ){ - char const *zToken; /* Buffer containing token */ - int nToken = 0; /* Number of bytes in token */ - int iDum1 = 0, iDum2 = 0; /* Dummy variables */ - int iPos = 0; /* Position of token in zText */ + rc = sqlite3Fts3OpenTokenizer(p->pTokenizer, iLang, zText, nText,&pT); + while( rc==SQLITE_OK ){ + char const *zToken; /* Buffer containing token */ + int nToken = 0; /* Number of bytes in token */ + int iDum1 = 0, iDum2 = 0; /* Dummy variables */ + int iPos = 0; /* Position of token in zText */ - rc = pModule->xNext(pT, &zToken, &nToken, &iDum1, &iDum2, &iPos); - if( rc==SQLITE_OK ){ - int i; - cksum2 = cksum2 ^ fts3ChecksumEntry( - zToken, nToken, iLang, 0, iDocid, iCol, iPos - ); - for(i=1; inIndex; i++){ - if( p->aIndex[i].nPrefix<=nToken ){ - cksum2 = cksum2 ^ fts3ChecksumEntry( - zToken, p->aIndex[i].nPrefix, iLang, i, iDocid, iCol, iPos - ); + rc = pModule->xNext(pT, &zToken, &nToken, &iDum1, &iDum2, &iPos); + if( rc==SQLITE_OK ){ + int i; + cksum2 = cksum2 ^ fts3ChecksumEntry( + zToken, nToken, iLang, 0, iDocid, iCol, iPos + ); + for(i=1; inIndex; i++){ + if( p->aIndex[i].nPrefix<=nToken ){ + cksum2 = cksum2 ^ fts3ChecksumEntry( + zToken, p->aIndex[i].nPrefix, iLang, i, iDocid, iCol, iPos + ); + } } } } + if( pT ) pModule->xClose(pT); + if( rc==SQLITE_DONE ) rc = SQLITE_OK; } - if( pT ) pModule->xClose(pT); - if( rc==SQLITE_DONE ) rc = SQLITE_OK; } } @@ -140854,7 +152548,7 @@ static int fts3DoIntegrityCheck( int rc; int bOk = 0; rc = fts3IntegrityCheck(p, &bOk); - if( rc==SQLITE_OK && bOk==0 ) rc = SQLITE_CORRUPT_VTAB; + if( rc==SQLITE_OK && bOk==0 ) rc = FTS_CORRUPT_VTAB; return rc; } @@ -141216,7 +152910,7 @@ SQLITE_PRIVATE int sqlite3Fts3UpdateMethod( } } if( rc==SQLITE_OK && (!isRemove || *pRowid!=p->iPrevDocid ) ){ - rc = fts3PendingTermsDocid(p, iLangid, *pRowid); + rc = fts3PendingTermsDocid(p, 0, iLangid, *pRowid); } if( rc==SQLITE_OK ){ assert( p->iPrevDocid==*pRowid ); @@ -141277,6 +152971,7 @@ SQLITE_PRIVATE int sqlite3Fts3Optimize(Fts3Table *p){ ****************************************************************************** */ +/* #include "fts3Int.h" */ #if !defined(SQLITE_CORE) || defined(SQLITE_ENABLE_FTS3) /* #include */ @@ -141292,6 +152987,8 @@ SQLITE_PRIVATE int sqlite3Fts3Optimize(Fts3Table *p){ #define FTS3_MATCHINFO_LENGTH 'l' /* nCol values */ #define FTS3_MATCHINFO_LCS 's' /* nCol values */ #define FTS3_MATCHINFO_HITS 'x' /* 3*nCol*nPhrase values */ +#define FTS3_MATCHINFO_LHITS 'y' /* nCol*nPhrase values */ +#define FTS3_MATCHINFO_LHITS_BM 'b' /* nCol*nPhrase values */ /* ** The default value for the second argument to matchinfo(). @@ -141353,9 +153050,22 @@ struct MatchInfo { int nCol; /* Number of columns in table */ int nPhrase; /* Number of matchable phrases in query */ sqlite3_int64 nDoc; /* Number of docs in database */ + char flag; u32 *aMatchinfo; /* Pre-allocated buffer */ }; +/* +** An instance of this structure is used to manage a pair of buffers, each +** (nElem * sizeof(u32)) bytes in size. See the MatchinfoBuffer code below +** for details. +*/ +struct MatchinfoBuffer { + u8 aRef[3]; + int nElem; + int bGlobal; /* Set if global data is loaded */ + char *zMatchinfo; + u32 aMatchinfo[1]; +}; /* @@ -141371,6 +153081,97 @@ struct StrBuffer { }; +/************************************************************************* +** Start of MatchinfoBuffer code. +*/ + +/* +** Allocate a two-slot MatchinfoBuffer object. +*/ +static MatchinfoBuffer *fts3MIBufferNew(int nElem, const char *zMatchinfo){ + MatchinfoBuffer *pRet; + int nByte = sizeof(u32) * (2*nElem + 1) + sizeof(MatchinfoBuffer); + int nStr = (int)strlen(zMatchinfo); + + pRet = sqlite3_malloc(nByte + nStr+1); + if( pRet ){ + memset(pRet, 0, nByte); + pRet->aMatchinfo[0] = (u8*)(&pRet->aMatchinfo[1]) - (u8*)pRet; + pRet->aMatchinfo[1+nElem] = pRet->aMatchinfo[0] + sizeof(u32)*(nElem+1); + pRet->nElem = nElem; + pRet->zMatchinfo = ((char*)pRet) + nByte; + memcpy(pRet->zMatchinfo, zMatchinfo, nStr+1); + pRet->aRef[0] = 1; + } + + return pRet; +} + +static void fts3MIBufferFree(void *p){ + MatchinfoBuffer *pBuf = (MatchinfoBuffer*)((u8*)p - ((u32*)p)[-1]); + + assert( (u32*)p==&pBuf->aMatchinfo[1] + || (u32*)p==&pBuf->aMatchinfo[pBuf->nElem+2] + ); + if( (u32*)p==&pBuf->aMatchinfo[1] ){ + pBuf->aRef[1] = 0; + }else{ + pBuf->aRef[2] = 0; + } + + if( pBuf->aRef[0]==0 && pBuf->aRef[1]==0 && pBuf->aRef[2]==0 ){ + sqlite3_free(pBuf); + } +} + +static void (*fts3MIBufferAlloc(MatchinfoBuffer *p, u32 **paOut))(void*){ + void (*xRet)(void*) = 0; + u32 *aOut = 0; + + if( p->aRef[1]==0 ){ + p->aRef[1] = 1; + aOut = &p->aMatchinfo[1]; + xRet = fts3MIBufferFree; + } + else if( p->aRef[2]==0 ){ + p->aRef[2] = 1; + aOut = &p->aMatchinfo[p->nElem+2]; + xRet = fts3MIBufferFree; + }else{ + aOut = (u32*)sqlite3_malloc(p->nElem * sizeof(u32)); + if( aOut ){ + xRet = sqlite3_free; + if( p->bGlobal ) memcpy(aOut, &p->aMatchinfo[1], p->nElem*sizeof(u32)); + } + } + + *paOut = aOut; + return xRet; +} + +static void fts3MIBufferSetGlobal(MatchinfoBuffer *p){ + p->bGlobal = 1; + memcpy(&p->aMatchinfo[2+p->nElem], &p->aMatchinfo[1], p->nElem*sizeof(u32)); +} + +/* +** Free a MatchinfoBuffer object allocated using fts3MIBufferNew() +*/ +SQLITE_PRIVATE void sqlite3Fts3MIBufferFree(MatchinfoBuffer *p){ + if( p ){ + assert( p->aRef[0]==1 ); + p->aRef[0] = 0; + if( p->aRef[0]==0 && p->aRef[1]==0 && p->aRef[2]==0 ){ + sqlite3_free(p); + } + } +} + +/* +** End of MatchinfoBuffer code. +*************************************************************************/ + + /* ** This function is used to help iterate through a position-list. A position ** list is a list of unique integers, sorted from smallest to largest. Each @@ -141407,7 +153208,7 @@ static int fts3ExprIterate2( void *pCtx /* Second argument to pass to callback */ ){ int rc; /* Return code */ - int eType = pExpr->eType; /* Type of expression node pExpr */ + int eType = pExpr->eType; /* Type of expression node pExpr */ if( eType!=FTSQUERY_PHRASE ){ assert( pExpr->pLeft && pExpr->pRight ); @@ -141441,6 +153242,7 @@ static int fts3ExprIterate( return fts3ExprIterate2(pExpr, &iPhrase, x, pCtx); } + /* ** This is an fts3ExprIterate() callback used while loading the doclists ** for each phrase into Fts3Expr.aDoclist[]/nDoclist. See also @@ -141485,8 +153287,7 @@ static int fts3ExprLoadDoclists( static int fts3ExprPhraseCountCb(Fts3Expr *pExpr, int iPhrase, void *ctx){ (*(int *)ctx)++; - UNUSED_PARAMETER(pExpr); - UNUSED_PARAMETER(iPhrase); + pExpr->iPhrase = iPhrase; return SQLITE_OK; } static int fts3ExprPhraseCount(Fts3Expr *pExpr){ @@ -141707,37 +153508,39 @@ static int fts3BestSnippet( sIter.nSnippet = nSnippet; sIter.nPhrase = nList; sIter.iCurrent = -1; - (void)fts3ExprIterate(pCsr->pExpr, fts3SnippetFindPositions, (void *)&sIter); + rc = fts3ExprIterate(pCsr->pExpr, fts3SnippetFindPositions, (void*)&sIter); + if( rc==SQLITE_OK ){ - /* Set the *pmSeen output variable. */ - for(i=0; iiCol = iCol; - while( !fts3SnippetNextCandidate(&sIter) ){ - int iPos; - int iScore; - u64 mCover; - u64 mHighlight; - fts3SnippetDetails(&sIter, mCovered, &iPos, &iScore, &mCover, &mHighlight); - assert( iScore>=0 ); - if( iScore>iBestScore ){ - pFragment->iPos = iPos; - pFragment->hlmask = mHighlight; - pFragment->covered = mCover; - iBestScore = iScore; + /* Loop through all candidate snippets. Store the best snippet in + ** *pFragment. Store its associated 'score' in iBestScore. + */ + pFragment->iCol = iCol; + while( !fts3SnippetNextCandidate(&sIter) ){ + int iPos; + int iScore; + u64 mCover; + u64 mHighlite; + fts3SnippetDetails(&sIter, mCovered, &iPos, &iScore, &mCover,&mHighlite); + assert( iScore>=0 ); + if( iScore>iBestScore ){ + pFragment->iPos = iPos; + pFragment->hlmask = mHighlite; + pFragment->covered = mCover; + iBestScore = iScore; + } } - } + *piScore = iBestScore; + } sqlite3_free(sIter.aPhrase); - *piScore = iBestScore; - return SQLITE_OK; + return rc; } @@ -141945,8 +153748,12 @@ static int fts3SnippetText( ** required. They are required if (a) this is not the first fragment, ** or (b) this fragment does not begin at position 0 of its column. */ - if( rc==SQLITE_OK && (iPos>0 || iFragment>0) ){ - rc = fts3StringAppend(pOut, zEllipsis, -1); + if( rc==SQLITE_OK ){ + if( iPos>0 || iFragment>0 ){ + rc = fts3StringAppend(pOut, zEllipsis, -1); + }else if( iBegin ){ + rc = fts3StringAppend(pOut, zDoc, iBegin); + } } if( rc!=SQLITE_OK || iCurrentpCursor->base.pVtab; + int iStart; + Fts3Phrase *pPhrase = pExpr->pPhrase; + char *pIter = pPhrase->doclist.pList; + int iCol = 0; + + assert( p->flag==FTS3_MATCHINFO_LHITS_BM || p->flag==FTS3_MATCHINFO_LHITS ); + if( p->flag==FTS3_MATCHINFO_LHITS ){ + iStart = pExpr->iPhrase * p->nCol; + }else{ + iStart = pExpr->iPhrase * ((p->nCol + 31) / 32); + } + + while( 1 ){ + int nHit = fts3ColumnlistCount(&pIter); + if( (pPhrase->iColumn>=pTab->nColumn || pPhrase->iColumn==iCol) ){ + if( p->flag==FTS3_MATCHINFO_LHITS ){ + p->aMatchinfo[iStart + iCol] = (u32)nHit; + }else if( nHit ){ + p->aMatchinfo[iStart + (iCol+1)/32] |= (1 << (iCol&0x1F)); + } + } + assert( *pIter==0x00 || *pIter==0x01 ); + if( *pIter!=0x01 ) break; + pIter++; + pIter += fts3GetVarint32(pIter, &iCol); + } +} + +/* +** Gather the results for matchinfo directives 'y' and 'b'. +*/ +static void fts3ExprLHitGather( + Fts3Expr *pExpr, + MatchInfo *p +){ + assert( (pExpr->pLeft==0)==(pExpr->pRight==0) ); + if( pExpr->bEof==0 && pExpr->iDocid==p->pCursor->iPrevId ){ + if( pExpr->pLeft ){ + fts3ExprLHitGather(pExpr->pLeft, p); + fts3ExprLHitGather(pExpr->pRight, p); + }else{ + fts3ExprLHits(pExpr, p); + } + } +} + /* ** fts3ExprIterate() callback used to collect the "global" matchinfo stats ** for a single query. @@ -142080,10 +153941,12 @@ static int fts3MatchinfoCheck( || (cArg==FTS3_MATCHINFO_LENGTH && pTab->bHasDocsize) || (cArg==FTS3_MATCHINFO_LCS) || (cArg==FTS3_MATCHINFO_HITS) + || (cArg==FTS3_MATCHINFO_LHITS) + || (cArg==FTS3_MATCHINFO_LHITS_BM) ){ return SQLITE_OK; } - *pzErr = sqlite3_mprintf("unrecognized matchinfo request: %c", cArg); + sqlite3Fts3ErrMsg(pzErr, "unrecognized matchinfo request: %c", cArg); return SQLITE_ERROR; } @@ -142103,6 +153966,14 @@ static int fts3MatchinfoSize(MatchInfo *pInfo, char cArg){ nVal = pInfo->nCol; break; + case FTS3_MATCHINFO_LHITS: + nVal = pInfo->nCol * pInfo->nPhrase; + break; + + case FTS3_MATCHINFO_LHITS_BM: + nVal = pInfo->nPhrase * ((pInfo->nCol + 31) / 32); + break; + default: assert( cArg==FTS3_MATCHINFO_HITS ); nVal = pInfo->nCol * pInfo->nPhrase * 3; @@ -142297,7 +154168,7 @@ static int fts3MatchinfoValues( sqlite3_stmt *pSelect = 0; for(i=0; rc==SQLITE_OK && zArg[i]; i++){ - + pInfo->flag = zArg[i]; switch( zArg[i] ){ case FTS3_MATCHINFO_NPHRASE: if( bGlobal ) pInfo->aMatchinfo[0] = pInfo->nPhrase; @@ -142357,6 +154228,14 @@ static int fts3MatchinfoValues( } break; + case FTS3_MATCHINFO_LHITS_BM: + case FTS3_MATCHINFO_LHITS: { + int nZero = fts3MatchinfoSize(pInfo, zArg[i]) * sizeof(u32); + memset(pInfo->aMatchinfo, 0, nZero); + fts3ExprLHitGather(pCsr->pExpr, pInfo); + break; + } + default: { Fts3Expr *pExpr; assert( zArg[i]==FTS3_MATCHINFO_HITS ); @@ -142369,6 +154248,7 @@ static int fts3MatchinfoValues( if( rc!=SQLITE_OK ) break; } rc = fts3ExprIterate(pExpr, fts3ExprGlobalHitsCb,(void*)pInfo); + sqlite3Fts3EvalTestDeferred(pCsr, &rc); if( rc!=SQLITE_OK ) break; } (void)fts3ExprIterate(pExpr, fts3ExprLocalHitsCb,(void*)pInfo); @@ -142388,7 +154268,8 @@ static int fts3MatchinfoValues( ** Populate pCsr->aMatchinfo[] with data for the current row. The ** 'matchinfo' data is an array of 32-bit unsigned integers (C type u32). */ -static int fts3GetMatchinfo( +static void fts3GetMatchinfo( + sqlite3_context *pCtx, /* Return results here */ Fts3Cursor *pCsr, /* FTS3 Cursor object */ const char *zArg /* Second argument to matchinfo() function */ ){ @@ -142397,6 +154278,9 @@ static int fts3GetMatchinfo( int rc = SQLITE_OK; int bGlobal = 0; /* Collect 'global' stats as well as local */ + u32 *aOut = 0; + void (*xDestroyOut)(void*) = 0; + memset(&sInfo, 0, sizeof(MatchInfo)); sInfo.pCursor = pCsr; sInfo.nCol = pTab->nColumn; @@ -142404,21 +154288,18 @@ static int fts3GetMatchinfo( /* If there is cached matchinfo() data, but the format string for the ** cache does not match the format string for this request, discard ** the cached data. */ - if( pCsr->zMatchinfo && strcmp(pCsr->zMatchinfo, zArg) ){ - assert( pCsr->aMatchinfo ); - sqlite3_free(pCsr->aMatchinfo); - pCsr->zMatchinfo = 0; - pCsr->aMatchinfo = 0; + if( pCsr->pMIBuffer && strcmp(pCsr->pMIBuffer->zMatchinfo, zArg) ){ + sqlite3Fts3MIBufferFree(pCsr->pMIBuffer); + pCsr->pMIBuffer = 0; } - /* If Fts3Cursor.aMatchinfo[] is NULL, then this is the first time the + /* If Fts3Cursor.pMIBuffer is NULL, then this is the first time the ** matchinfo function has been called for this query. In this case ** allocate the array used to accumulate the matchinfo data and ** initialize those elements that are constant for every row. */ - if( pCsr->aMatchinfo==0 ){ + if( pCsr->pMIBuffer==0 ){ int nMatchinfo = 0; /* Number of u32 elements in match-info */ - int nArg; /* Bytes in zArg */ int i; /* Used to iterate through zArg */ /* Determine the number of phrases in the query */ @@ -142427,30 +154308,46 @@ static int fts3GetMatchinfo( /* Determine the number of integers in the buffer returned by this call. */ for(i=0; zArg[i]; i++){ + char *zErr = 0; + if( fts3MatchinfoCheck(pTab, zArg[i], &zErr) ){ + sqlite3_result_error(pCtx, zErr, -1); + sqlite3_free(zErr); + return; + } nMatchinfo += fts3MatchinfoSize(&sInfo, zArg[i]); } /* Allocate space for Fts3Cursor.aMatchinfo[] and Fts3Cursor.zMatchinfo. */ - nArg = (int)strlen(zArg); - pCsr->aMatchinfo = (u32 *)sqlite3_malloc(sizeof(u32)*nMatchinfo + nArg + 1); - if( !pCsr->aMatchinfo ) return SQLITE_NOMEM; + pCsr->pMIBuffer = fts3MIBufferNew(nMatchinfo, zArg); + if( !pCsr->pMIBuffer ) rc = SQLITE_NOMEM; - pCsr->zMatchinfo = (char *)&pCsr->aMatchinfo[nMatchinfo]; - pCsr->nMatchinfo = nMatchinfo; - memcpy(pCsr->zMatchinfo, zArg, nArg+1); - memset(pCsr->aMatchinfo, 0, sizeof(u32)*nMatchinfo); pCsr->isMatchinfoNeeded = 1; bGlobal = 1; } - sInfo.aMatchinfo = pCsr->aMatchinfo; - sInfo.nPhrase = pCsr->nPhrase; - if( pCsr->isMatchinfoNeeded ){ - rc = fts3MatchinfoValues(pCsr, bGlobal, &sInfo, zArg); - pCsr->isMatchinfoNeeded = 0; + if( rc==SQLITE_OK ){ + xDestroyOut = fts3MIBufferAlloc(pCsr->pMIBuffer, &aOut); + if( xDestroyOut==0 ){ + rc = SQLITE_NOMEM; + } } - return rc; + if( rc==SQLITE_OK ){ + sInfo.aMatchinfo = aOut; + sInfo.nPhrase = pCsr->nPhrase; + rc = fts3MatchinfoValues(pCsr, bGlobal, &sInfo, zArg); + if( bGlobal ){ + fts3MIBufferSetGlobal(pCsr->pMIBuffer); + } + } + + if( rc!=SQLITE_OK ){ + sqlite3_result_error_code(pCtx, rc); + if( xDestroyOut ) xDestroyOut(aOut); + }else{ + int n = pCsr->pMIBuffer->nElem * sizeof(u32); + sqlite3_result_blob(pCtx, aOut, n, xDestroyOut); + } } /* @@ -142512,7 +154409,7 @@ SQLITE_PRIVATE void sqlite3Fts3Snippet( */ for(iRead=0; iReadnColumn; iRead++){ SnippetFragment sF = {0, 0, 0, 0}; - int iS; + int iS = 0; if( iCol>=0 && iRead!=iCol ) continue; /* Find the best snippet of nFToken tokens in column iRead. */ @@ -142656,7 +154553,7 @@ SQLITE_PRIVATE void sqlite3Fts3Offsets( */ sCtx.iCol = iCol; sCtx.iTerm = 0; - (void)fts3ExprIterate(pCsr->pExpr, fts3ExprTermOffsetInit, (void *)&sCtx); + (void)fts3ExprIterate(pCsr->pExpr, fts3ExprTermOffsetInit, (void*)&sCtx); /* Retreive the text stored in column iCol. If an SQL NULL is stored ** in column iCol, jump immediately to the next iteration of the loop. @@ -142748,19 +154645,9 @@ SQLITE_PRIVATE void sqlite3Fts3Matchinfo( const char *zArg /* Second arg to matchinfo() function */ ){ Fts3Table *pTab = (Fts3Table *)pCsr->base.pVtab; - int rc; - int i; const char *zFormat; if( zArg ){ - for(i=0; zArg[i]; i++){ - char *zErr = 0; - if( fts3MatchinfoCheck(pTab, zArg[i], &zErr) ){ - sqlite3_result_error(pContext, zErr, -1); - sqlite3_free(zErr); - return; - } - } zFormat = zArg; }else{ zFormat = FTS3_MATCHINFO_DEFAULT; @@ -142769,17 +154656,10 @@ SQLITE_PRIVATE void sqlite3Fts3Matchinfo( if( !pCsr->pExpr ){ sqlite3_result_blob(pContext, "", 0, SQLITE_STATIC); return; - } - - /* Retrieve matchinfo() data. */ - rc = fts3GetMatchinfo(pCsr, zFormat); - sqlite3Fts3SegmentsClose(pTab); - - if( rc!=SQLITE_OK ){ - sqlite3_result_error_code(pContext, rc); }else{ - int n = pCsr->nMatchinfo * sizeof(u32); - sqlite3_result_blob(pContext, pCsr->aMatchinfo, n, SQLITE_TRANSIENT); + /* Retrieve matchinfo() data. */ + fts3GetMatchinfo(pContext, pCsr, zFormat); + sqlite3Fts3SegmentsClose(pTab); } } @@ -142802,8 +154682,9 @@ SQLITE_PRIVATE void sqlite3Fts3Matchinfo( ** Implementation of the "unicode" full-text-search tokenizer. */ -#ifdef SQLITE_ENABLE_FTS4_UNICODE61 +#ifndef SQLITE_DISABLE_FTS3_UNICODE +/* #include "fts3Int.h" */ #if !defined(SQLITE_CORE) || defined(SQLITE_ENABLE_FTS3) /* #include */ @@ -142811,6 +154692,7 @@ SQLITE_PRIVATE void sqlite3Fts3Matchinfo( /* #include */ /* #include */ +/* #include "fts3_tokenizer.h" */ /* ** The following two macros - READ_UTF8 and WRITE_UTF8 - have been copied @@ -143018,7 +154900,7 @@ static int unicodeCreate( for(i=0; rc==SQLITE_OK && ibRemoveDiacritic = 1; @@ -143105,7 +154987,7 @@ static int unicodeNext( ){ unicode_cursor *pCsr = (unicode_cursor *)pC; unicode_tokenizer *p = ((unicode_tokenizer *)pCsr->base.pTokenizer); - int iCode; + int iCode = 0; char *zOut; const unsigned char *z = &pCsr->aInput[pCsr->iOff]; const unsigned char *zStart = z; @@ -143150,11 +155032,11 @@ static int unicodeNext( ); /* Set the output variables and return. */ - pCsr->iOff = (z - pCsr->aInput); + pCsr->iOff = (int)(z - pCsr->aInput); *paToken = pCsr->zToken; - *pnToken = zOut - pCsr->zToken; - *piStart = (zStart - pCsr->aInput); - *piEnd = (zEnd - pCsr->aInput); + *pnToken = (int)(zOut - pCsr->zToken); + *piStart = (int)(zStart - pCsr->aInput); + *piEnd = (int)(zEnd - pCsr->aInput); *piPos = pCsr->iToken++; return SQLITE_OK; } @@ -143177,7 +155059,7 @@ SQLITE_PRIVATE void sqlite3Fts3UnicodeTokenizer(sqlite3_tokenizer_module const * } #endif /* !defined(SQLITE_CORE) || defined(SQLITE_ENABLE_FTS3) */ -#endif /* ifndef SQLITE_ENABLE_FTS4_UNICODE61 */ +#endif /* ifndef SQLITE_DISABLE_FTS3_UNICODE */ /************** End of fts3_unicode.c ****************************************/ /************** Begin file fts3_unicode2.c ***********************************/ @@ -143198,7 +155080,7 @@ SQLITE_PRIVATE void sqlite3Fts3UnicodeTokenizer(sqlite3_tokenizer_module const * ** DO NOT EDIT THIS MACHINE GENERATED FILE. */ -#if defined(SQLITE_ENABLE_FTS4_UNICODE61) +#ifndef SQLITE_DISABLE_FTS3_UNICODE #if defined(SQLITE_ENABLE_FTS3) || defined(SQLITE_ENABLE_FTS4) /* #include */ @@ -143222,7 +155104,7 @@ SQLITE_PRIVATE int sqlite3FtsUnicodeIsalnum(int c){ ** C. It is not possible to represent a range larger than 1023 codepoints ** using this format. */ - const static unsigned int aEntry[] = { + static const unsigned int aEntry[] = { 0x00000030, 0x0000E807, 0x00016C06, 0x0001EC2F, 0x0002AC07, 0x0002D001, 0x0002D803, 0x0002EC01, 0x0002FC01, 0x00035C01, 0x0003DC01, 0x000B0804, 0x000B480E, 0x000B9407, 0x000BB401, @@ -143314,7 +155196,7 @@ SQLITE_PRIVATE int sqlite3FtsUnicodeIsalnum(int c){ return ( (aAscii[c >> 5] & (1 << (c & 0x001F)))==0 ); }else if( c<(1<<22) ){ unsigned int key = (((unsigned int)c)<<10) | 0x000003FF; - int iRes; + int iRes = 0; int iHi = sizeof(aEntry)/sizeof(aEntry[0]) - 1; int iLo = 0; while( iHi>=iLo ){ @@ -143385,7 +155267,7 @@ static int remove_diacritic(int c){ } assert( key>=aDia[iRes] ); return ((c > (aDia[iRes]>>3) + (aDia[iRes]&0x07)) ? c : (int)aChar[iRes]); -}; +} /* @@ -143545,7 +155427,7 @@ SQLITE_PRIVATE int sqlite3FtsUnicodeFold(int c, int bRemoveDiacritic){ return ret; } #endif /* defined(SQLITE_ENABLE_FTS3) || defined(SQLITE_ENABLE_FTS4) */ -#endif /* !defined(SQLITE_ENABLE_FTS4_UNICODE61) */ +#endif /* !defined(SQLITE_DISABLE_FTS3_UNICODE) */ /************** End of fts3_unicode2.c ***************************************/ /************** Begin file rtree.c *******************************************/ @@ -143606,8 +155488,10 @@ SQLITE_PRIVATE int sqlite3FtsUnicodeFold(int c, int bRemoveDiacritic){ #if !defined(SQLITE_CORE) || defined(SQLITE_ENABLE_RTREE) #ifndef SQLITE_CORE +/* #include "sqlite3ext.h" */ SQLITE_EXTENSION_INIT1 #else +/* #include "sqlite3.h" */ #endif /* #include */ @@ -143900,6 +155784,7 @@ struct RtreeMatchArg { u32 magic; /* Always RTREE_GEOMETRY_MAGIC */ RtreeGeomCallback cb; /* Info about the callback functions */ int nParam; /* Number of parameters to the SQL function */ + sqlite3_value **apSqlParam; /* Original SQL parameter values */ RtreeDValue aParam[1]; /* Values for parameters to the SQL function */ }; @@ -143918,13 +155803,12 @@ static int readInt16(u8 *p){ return (p[0]<<8) + p[1]; } static void readCoord(u8 *p, RtreeCoord *pCoord){ - u32 i = ( + pCoord->u = ( (((u32)p[0]) << 24) + (((u32)p[1]) << 16) + (((u32)p[2]) << 8) + (((u32)p[3]) << 0) ); - *(u32 *)pCoord = i; } static i64 readInt64(u8 *p){ return ( @@ -143953,7 +155837,7 @@ static int writeCoord(u8 *p, RtreeCoord *pCoord){ u32 i; assert( sizeof(RtreeCoord)==4 ); assert( sizeof(u32)==4 ); - i = *(u32 *)pCoord; + i = pCoord->u; p[0] = (i>>24)&0xFF; p[1] = (i>>16)&0xFF; p[2] = (i>> 8)&0xFF; @@ -144284,14 +156168,13 @@ static void nodeGetCell( RtreeCell *pCell /* OUT: Write the cell contents here */ ){ u8 *pData; - u8 *pEnd; RtreeCoord *pCoord; + int ii; pCell->iRowid = nodeGetRowid(pRtree, pNode, iCell); pData = pNode->zData + (12 + pRtree->nBytesPerCell*iCell); - pEnd = pData + pRtree->nDim*8; pCoord = pCell->aCoord; - for(; pDatanDim*2; ii++){ + readCoord(&pData[ii*4], &pCoord[ii]); } } @@ -144731,7 +156614,7 @@ static RtreeSearchPoint *rtreeEnqueue( pNew = pCur->aPoint + i; pNew->rScore = rScore; pNew->iLevel = iLevel; - assert( iLevel>=0 && iLevel<=RTREE_MAX_DEPTH ); + assert( iLevel<=RTREE_MAX_DEPTH ); while( i>0 ){ RtreeSearchPoint *pParent; j = (i-1)/2; @@ -145033,9 +156916,7 @@ static int deserializeGeometry(sqlite3_value *pValue, RtreeConstraint *pCons){ /* Check that the blob is roughly the right size. */ nBlob = sqlite3_value_bytes(pValue); - if( nBlob<(int)sizeof(RtreeMatchArg) - || ((nBlob-sizeof(RtreeMatchArg))%sizeof(RtreeDValue))!=0 - ){ + if( nBlob<(int)sizeof(RtreeMatchArg) ){ return SQLITE_ERROR; } @@ -145046,6 +156927,7 @@ static int deserializeGeometry(sqlite3_value *pValue, RtreeConstraint *pCons){ memcpy(pBlob, sqlite3_value_blob(pValue), nBlob); nExpected = (int)(sizeof(RtreeMatchArg) + + pBlob->nParam*sizeof(sqlite3_value*) + (pBlob->nParam-1)*sizeof(RtreeDValue)); if( pBlob->magic!=RTREE_GEOMETRY_MAGIC || nBlob!=nExpected ){ sqlite3_free(pInfo); @@ -145054,6 +156936,7 @@ static int deserializeGeometry(sqlite3_value *pValue, RtreeConstraint *pCons){ pInfo->pContext = pBlob->cb.pContext; pInfo->nParam = pBlob->nParam; pInfo->aParam = pBlob->aParam; + pInfo->apSqlParam = pBlob->apSqlParam; if( pBlob->cb.xGeom ){ pCons->u.xGeom = pBlob->cb.xGeom; @@ -145082,9 +156965,13 @@ static int rtreeFilter( rtreeReference(pRtree); + /* Reset the cursor to the same state as rtreeOpen() leaves it in. */ freeCursorConstraints(pCsr); - pCsr->iStrategy = idxNum; + sqlite3_free(pCsr->aPoint); + memset(pCsr, 0, sizeof(RtreeCursor)); + pCsr->base.pVtab = (sqlite3_vtab*)pRtree; + pCsr->iStrategy = idxNum; if( idxNum==1 ){ /* Special case - lookup by rowid. */ RtreeNode *pLeaf; /* Leaf on which the required cell resides */ @@ -145216,17 +157103,30 @@ static int rtreeBestIndex(sqlite3_vtab *tab, sqlite3_index_info *pIdxInfo){ Rtree *pRtree = (Rtree*)tab; int rc = SQLITE_OK; int ii; + int bMatch = 0; /* True if there exists a MATCH constraint */ i64 nRow; /* Estimated rows returned by this scan */ int iIdx = 0; char zIdxStr[RTREE_MAX_DIMENSIONS*8+1]; memset(zIdxStr, 0, sizeof(zIdxStr)); + /* Check if there exists a MATCH constraint - even an unusable one. If there + ** is, do not consider the lookup-by-rowid plan as using such a plan would + ** require the VDBE to evaluate the MATCH constraint, which is not currently + ** possible. */ + for(ii=0; iinConstraint; ii++){ + if( pIdxInfo->aConstraint[ii].op==SQLITE_INDEX_CONSTRAINT_MATCH ){ + bMatch = 1; + } + } + assert( pIdxInfo->idxStr==0 ); for(ii=0; iinConstraint && iIdx<(int)(sizeof(zIdxStr)-1); ii++){ struct sqlite3_index_constraint *p = &pIdxInfo->aConstraint[ii]; - if( p->usable && p->iColumn==0 && p->op==SQLITE_INDEX_CONSTRAINT_EQ ){ + if( bMatch==0 && p->usable + && p->iColumn==0 && p->op==SQLITE_INDEX_CONSTRAINT_EQ + ){ /* We have an equality constraint on the rowid. Use strategy 1. */ int jj; for(jj=0; jj=1); + cell.iRowid = 0; /* Used only to suppress a compiler warning */ + /* Constraint handling. A write operation on an r-tree table may return ** SQLITE_CONSTRAINT for two reasons: ** @@ -146365,11 +158267,19 @@ static int rtreeUpdate( if( nData>1 ){ int ii; - /* Populate the cell.aCoord[] array. The first coordinate is azData[3]. */ - assert( nData==(pRtree->nDim*2 + 3) ); + /* Populate the cell.aCoord[] array. The first coordinate is azData[3]. + ** + ** NB: nData can only be less than nDim*2+3 if the rtree is mis-declared + ** with "column" that are interpreted as table constraints. + ** Example: CREATE VIRTUAL TABLE bad USING rtree(x,y,CHECK(y>5)); + ** This problem was discovered after years of use, so we silently ignore + ** these kinds of misdeclared tables to avoid breaking any legacy. + */ + assert( nData<=(pRtree->nDim*2 + 3) ); + #ifndef SQLITE_RTREE_INT_ONLY if( pRtree->eCoordType==RTREE_COORD_REAL32 ){ - for(ii=0; ii<(pRtree->nDim*2); ii+=2){ + for(ii=0; iicell.aCoord[ii+1].f ){ @@ -146380,7 +158290,7 @@ static int rtreeUpdate( }else #endif { - for(ii=0; ii<(pRtree->nDim*2); ii+=2){ + for(ii=0; iicell.aCoord[ii+1].i ){ @@ -146909,6 +158819,18 @@ static void rtreeFreeCallback(void *p){ sqlite3_free(p); } +/* +** This routine frees the BLOB that is returned by geomCallback(). +*/ +static void rtreeMatchArgFree(void *pArg){ + int i; + RtreeMatchArg *p = (RtreeMatchArg*)pArg; + for(i=0; inParam; i++){ + sqlite3_value_free(p->apSqlParam[i]); + } + sqlite3_free(p); +} + /* ** Each call to sqlite3_rtree_geometry_callback() or ** sqlite3_rtree_query_callback() creates an ordinary SQLite @@ -146927,8 +158849,10 @@ static void geomCallback(sqlite3_context *ctx, int nArg, sqlite3_value **aArg){ RtreeGeomCallback *pGeomCtx = (RtreeGeomCallback *)sqlite3_user_data(ctx); RtreeMatchArg *pBlob; int nBlob; + int memErr = 0; - nBlob = sizeof(RtreeMatchArg) + (nArg-1)*sizeof(RtreeDValue); + nBlob = sizeof(RtreeMatchArg) + (nArg-1)*sizeof(RtreeDValue) + + nArg*sizeof(sqlite3_value*); pBlob = (RtreeMatchArg *)sqlite3_malloc(nBlob); if( !pBlob ){ sqlite3_result_error_nomem(ctx); @@ -146936,22 +158860,30 @@ static void geomCallback(sqlite3_context *ctx, int nArg, sqlite3_value **aArg){ int i; pBlob->magic = RTREE_GEOMETRY_MAGIC; pBlob->cb = pGeomCtx[0]; + pBlob->apSqlParam = (sqlite3_value**)&pBlob->aParam[nArg]; pBlob->nParam = nArg; for(i=0; iapSqlParam[i] = sqlite3_value_dup(aArg[i]); + if( pBlob->apSqlParam[i]==0 ) memErr = 1; #ifdef SQLITE_RTREE_INT_ONLY pBlob->aParam[i] = sqlite3_value_int64(aArg[i]); #else pBlob->aParam[i] = sqlite3_value_double(aArg[i]); #endif } - sqlite3_result_blob(ctx, pBlob, nBlob, sqlite3_free); + if( memErr ){ + sqlite3_result_error_nomem(ctx); + rtreeMatchArgFree(pBlob); + }else{ + sqlite3_result_blob(ctx, pBlob, nBlob, rtreeMatchArgFree); + } } } /* ** Register a new geometry function for use with the r-tree MATCH operator. */ -SQLITE_API int sqlite3_rtree_geometry_callback( +SQLITE_API int SQLITE_STDCALL sqlite3_rtree_geometry_callback( sqlite3 *db, /* Register SQL function on this connection */ const char *zGeom, /* Name of the new SQL function */ int (*xGeom)(sqlite3_rtree_geometry*,int,RtreeDValue*,int*), /* Callback */ @@ -146975,7 +158907,7 @@ SQLITE_API int sqlite3_rtree_geometry_callback( ** Register a new 2nd-generation geometry function for use with the ** r-tree MATCH operator. */ -SQLITE_API int sqlite3_rtree_query_callback( +SQLITE_API int SQLITE_STDCALL sqlite3_rtree_query_callback( sqlite3 *db, /* Register SQL function on this connection */ const char *zQueryFunc, /* Name of new SQL function */ int (*xQueryFunc)(sqlite3_rtree_query_info*), /* Callback */ @@ -147000,7 +158932,7 @@ SQLITE_API int sqlite3_rtree_query_callback( #ifdef _WIN32 __declspec(dllexport) #endif -SQLITE_API int sqlite3_rtree_init( +SQLITE_API int SQLITE_STDCALL sqlite3_rtree_init( sqlite3 *db, char **pzErrMsg, const sqlite3_api_routines *pApi @@ -147055,8 +158987,10 @@ SQLITE_API int sqlite3_rtree_init( /* #include */ #ifndef SQLITE_CORE +/* #include "sqlite3ext.h" */ SQLITE_EXTENSION_INIT1 #else +/* #include "sqlite3.h" */ #endif /* @@ -147097,7 +159031,6 @@ static int icuLikeCompare( /* Read (and consume) the next character from the input pattern. */ UChar32 uPattern; U8_NEXT_UNSAFE(zPattern, iPattern, uPattern); - assert(uPattern!=0); /* There are now 4 possibilities: ** @@ -147436,6 +159369,7 @@ static void icuLoadCollation( int rc; /* Return code from sqlite3_create_collation_x() */ assert(nArg==2); + (void)nArg; /* Unused parameter */ zLocale = (const char *)sqlite3_value_text(apArg[0]); zName = (const char *)sqlite3_value_text(apArg[1]); @@ -147505,7 +159439,7 @@ SQLITE_PRIVATE int sqlite3IcuInit(sqlite3 *db){ #ifdef _WIN32 __declspec(dllexport) #endif -SQLITE_API int sqlite3_icu_init( +SQLITE_API int SQLITE_STDCALL sqlite3_icu_init( sqlite3 *db, char **pzErrMsg, const sqlite3_api_routines *pApi @@ -147532,11 +159466,13 @@ SQLITE_API int sqlite3_icu_init( ************************************************************************* ** This file implements a tokenizer for fts3 based on the ICU library. */ +/* #include "fts3Int.h" */ #if !defined(SQLITE_CORE) || defined(SQLITE_ENABLE_FTS3) #ifdef SQLITE_ENABLE_ICU /* #include */ /* #include */ +/* #include "fts3_tokenizer.h" */ #include /* #include */ @@ -147759,12 +159695,13 @@ static int icuNext( ** The set of routines that implement the simple tokenizer */ static const sqlite3_tokenizer_module icuTokenizerModule = { - 0, /* iVersion */ - icuCreate, /* xCreate */ - icuDestroy, /* xCreate */ - icuOpen, /* xOpen */ - icuClose, /* xClose */ - icuNext, /* xNext */ + 0, /* iVersion */ + icuCreate, /* xCreate */ + icuDestroy, /* xCreate */ + icuOpen, /* xOpen */ + icuClose, /* xClose */ + icuNext, /* xNext */ + 0, /* xLanguageid */ }; /* @@ -147780,3 +159717,26325 @@ SQLITE_PRIVATE void sqlite3Fts3IcuTokenizerModule( #endif /* !defined(SQLITE_CORE) || defined(SQLITE_ENABLE_FTS3) */ /************** End of fts3_icu.c ********************************************/ +/************** Begin file sqlite3rbu.c **************************************/ +/* +** 2014 August 30 +** +** The author disclaims copyright to this source code. In place of +** a legal notice, here is a blessing: +** +** May you do good and not evil. +** May you find forgiveness for yourself and forgive others. +** May you share freely, never taking more than you give. +** +************************************************************************* +** +** +** OVERVIEW +** +** The RBU extension requires that the RBU update be packaged as an +** SQLite database. The tables it expects to find are described in +** sqlite3rbu.h. Essentially, for each table xyz in the target database +** that the user wishes to write to, a corresponding data_xyz table is +** created in the RBU database and populated with one row for each row to +** update, insert or delete from the target table. +** +** The update proceeds in three stages: +** +** 1) The database is updated. The modified database pages are written +** to a *-oal file. A *-oal file is just like a *-wal file, except +** that it is named "-oal" instead of "-wal". +** Because regular SQLite clients do not look for file named +** "-oal", they go on using the original database in +** rollback mode while the *-oal file is being generated. +** +** During this stage RBU does not update the database by writing +** directly to the target tables. Instead it creates "imposter" +** tables using the SQLITE_TESTCTRL_IMPOSTER interface that it uses +** to update each b-tree individually. All updates required by each +** b-tree are completed before moving on to the next, and all +** updates are done in sorted key order. +** +** 2) The "-oal" file is moved to the equivalent "-wal" +** location using a call to rename(2). Before doing this the RBU +** module takes an EXCLUSIVE lock on the database file, ensuring +** that there are no other active readers. +** +** Once the EXCLUSIVE lock is released, any other database readers +** detect the new *-wal file and read the database in wal mode. At +** this point they see the new version of the database - including +** the updates made as part of the RBU update. +** +** 3) The new *-wal file is checkpointed. This proceeds in the same way +** as a regular database checkpoint, except that a single frame is +** checkpointed each time sqlite3rbu_step() is called. If the RBU +** handle is closed before the entire *-wal file is checkpointed, +** the checkpoint progress is saved in the RBU database and the +** checkpoint can be resumed by another RBU client at some point in +** the future. +** +** POTENTIAL PROBLEMS +** +** The rename() call might not be portable. And RBU is not currently +** syncing the directory after renaming the file. +** +** When state is saved, any commit to the *-oal file and the commit to +** the RBU update database are not atomic. So if the power fails at the +** wrong moment they might get out of sync. As the main database will be +** committed before the RBU update database this will likely either just +** pass unnoticed, or result in SQLITE_CONSTRAINT errors (due to UNIQUE +** constraint violations). +** +** If some client does modify the target database mid RBU update, or some +** other error occurs, the RBU extension will keep throwing errors. It's +** not really clear how to get out of this state. The system could just +** by delete the RBU update database and *-oal file and have the device +** download the update again and start over. +** +** At present, for an UPDATE, both the new.* and old.* records are +** collected in the rbu_xyz table. And for both UPDATEs and DELETEs all +** fields are collected. This means we're probably writing a lot more +** data to disk when saving the state of an ongoing update to the RBU +** update database than is strictly necessary. +** +*/ + +/* #include */ +/* #include */ +/* #include */ + +/* #include "sqlite3.h" */ + +#if !defined(SQLITE_CORE) || defined(SQLITE_ENABLE_RBU) +/************** Include sqlite3rbu.h in the middle of sqlite3rbu.c ***********/ +/************** Begin file sqlite3rbu.h **************************************/ +/* +** 2014 August 30 +** +** The author disclaims copyright to this source code. In place of +** a legal notice, here is a blessing: +** +** May you do good and not evil. +** May you find forgiveness for yourself and forgive others. +** May you share freely, never taking more than you give. +** +************************************************************************* +** +** This file contains the public interface for the RBU extension. +*/ + +/* +** SUMMARY +** +** Writing a transaction containing a large number of operations on +** b-tree indexes that are collectively larger than the available cache +** memory can be very inefficient. +** +** The problem is that in order to update a b-tree, the leaf page (at least) +** containing the entry being inserted or deleted must be modified. If the +** working set of leaves is larger than the available cache memory, then a +** single leaf that is modified more than once as part of the transaction +** may be loaded from or written to the persistent media multiple times. +** Additionally, because the index updates are likely to be applied in +** random order, access to pages within the database is also likely to be in +** random order, which is itself quite inefficient. +** +** One way to improve the situation is to sort the operations on each index +** by index key before applying them to the b-tree. This leads to an IO +** pattern that resembles a single linear scan through the index b-tree, +** and all but guarantees each modified leaf page is loaded and stored +** exactly once. SQLite uses this trick to improve the performance of +** CREATE INDEX commands. This extension allows it to be used to improve +** the performance of large transactions on existing databases. +** +** Additionally, this extension allows the work involved in writing the +** large transaction to be broken down into sub-transactions performed +** sequentially by separate processes. This is useful if the system cannot +** guarantee that a single update process will run for long enough to apply +** the entire update, for example because the update is being applied on a +** mobile device that is frequently rebooted. Even after the writer process +** has committed one or more sub-transactions, other database clients continue +** to read from the original database snapshot. In other words, partially +** applied transactions are not visible to other clients. +** +** "RBU" stands for "Resumable Bulk Update". As in a large database update +** transmitted via a wireless network to a mobile device. A transaction +** applied using this extension is hence refered to as an "RBU update". +** +** +** LIMITATIONS +** +** An "RBU update" transaction is subject to the following limitations: +** +** * The transaction must consist of INSERT, UPDATE and DELETE operations +** only. +** +** * INSERT statements may not use any default values. +** +** * UPDATE and DELETE statements must identify their target rows by +** non-NULL PRIMARY KEY values. Rows with NULL values stored in PRIMARY +** KEY fields may not be updated or deleted. If the table being written +** has no PRIMARY KEY, affected rows must be identified by rowid. +** +** * UPDATE statements may not modify PRIMARY KEY columns. +** +** * No triggers will be fired. +** +** * No foreign key violations are detected or reported. +** +** * CHECK constraints are not enforced. +** +** * No constraint handling mode except for "OR ROLLBACK" is supported. +** +** +** PREPARATION +** +** An "RBU update" is stored as a separate SQLite database. A database +** containing an RBU update is an "RBU database". For each table in the +** target database to be updated, the RBU database should contain a table +** named "data_" containing the same set of columns as the +** target table, and one more - "rbu_control". The data_% table should +** have no PRIMARY KEY or UNIQUE constraints, but each column should have +** the same type as the corresponding column in the target database. +** The "rbu_control" column should have no type at all. For example, if +** the target database contains: +** +** CREATE TABLE t1(a INTEGER PRIMARY KEY, b TEXT, c UNIQUE); +** +** Then the RBU database should contain: +** +** CREATE TABLE data_t1(a INTEGER, b TEXT, c, rbu_control); +** +** The order of the columns in the data_% table does not matter. +** +** Instead of a regular table, the RBU database may also contain virtual +** tables or view named using the data_ naming scheme. +** +** Instead of the plain data_ naming scheme, RBU database tables +** may also be named data_, where is any sequence +** of zero or more numeric characters (0-9). This can be significant because +** tables within the RBU database are always processed in order sorted by +** name. By judicious selection of the the portion of the names +** of the RBU tables the user can therefore control the order in which they +** are processed. This can be useful, for example, to ensure that "external +** content" FTS4 tables are updated before their underlying content tables. +** +** If the target database table is a virtual table or a table that has no +** PRIMARY KEY declaration, the data_% table must also contain a column +** named "rbu_rowid". This column is mapped to the tables implicit primary +** key column - "rowid". Virtual tables for which the "rowid" column does +** not function like a primary key value cannot be updated using RBU. For +** example, if the target db contains either of the following: +** +** CREATE VIRTUAL TABLE x1 USING fts3(a, b); +** CREATE TABLE x1(a, b) +** +** then the RBU database should contain: +** +** CREATE TABLE data_x1(a, b, rbu_rowid, rbu_control); +** +** All non-hidden columns (i.e. all columns matched by "SELECT *") of the +** target table must be present in the input table. For virtual tables, +** hidden columns are optional - they are updated by RBU if present in +** the input table, or not otherwise. For example, to write to an fts4 +** table with a hidden languageid column such as: +** +** CREATE VIRTUAL TABLE ft1 USING fts4(a, b, languageid='langid'); +** +** Either of the following input table schemas may be used: +** +** CREATE TABLE data_ft1(a, b, langid, rbu_rowid, rbu_control); +** CREATE TABLE data_ft1(a, b, rbu_rowid, rbu_control); +** +** For each row to INSERT into the target database as part of the RBU +** update, the corresponding data_% table should contain a single record +** with the "rbu_control" column set to contain integer value 0. The +** other columns should be set to the values that make up the new record +** to insert. +** +** If the target database table has an INTEGER PRIMARY KEY, it is not +** possible to insert a NULL value into the IPK column. Attempting to +** do so results in an SQLITE_MISMATCH error. +** +** For each row to DELETE from the target database as part of the RBU +** update, the corresponding data_% table should contain a single record +** with the "rbu_control" column set to contain integer value 1. The +** real primary key values of the row to delete should be stored in the +** corresponding columns of the data_% table. The values stored in the +** other columns are not used. +** +** For each row to UPDATE from the target database as part of the RBU +** update, the corresponding data_% table should contain a single record +** with the "rbu_control" column set to contain a value of type text. +** The real primary key values identifying the row to update should be +** stored in the corresponding columns of the data_% table row, as should +** the new values of all columns being update. The text value in the +** "rbu_control" column must contain the same number of characters as +** there are columns in the target database table, and must consist entirely +** of 'x' and '.' characters (or in some special cases 'd' - see below). For +** each column that is being updated, the corresponding character is set to +** 'x'. For those that remain as they are, the corresponding character of the +** rbu_control value should be set to '.'. For example, given the tables +** above, the update statement: +** +** UPDATE t1 SET c = 'usa' WHERE a = 4; +** +** is represented by the data_t1 row created by: +** +** INSERT INTO data_t1(a, b, c, rbu_control) VALUES(4, NULL, 'usa', '..x'); +** +** Instead of an 'x' character, characters of the rbu_control value specified +** for UPDATEs may also be set to 'd'. In this case, instead of updating the +** target table with the value stored in the corresponding data_% column, the +** user-defined SQL function "rbu_delta()" is invoked and the result stored in +** the target table column. rbu_delta() is invoked with two arguments - the +** original value currently stored in the target table column and the +** value specified in the data_xxx table. +** +** For example, this row: +** +** INSERT INTO data_t1(a, b, c, rbu_control) VALUES(4, NULL, 'usa', '..d'); +** +** is similar to an UPDATE statement such as: +** +** UPDATE t1 SET c = rbu_delta(c, 'usa') WHERE a = 4; +** +** Finally, if an 'f' character appears in place of a 'd' or 's' in an +** ota_control string, the contents of the data_xxx table column is assumed +** to be a "fossil delta" - a patch to be applied to a blob value in the +** format used by the fossil source-code management system. In this case +** the existing value within the target database table must be of type BLOB. +** It is replaced by the result of applying the specified fossil delta to +** itself. +** +** If the target database table is a virtual table or a table with no PRIMARY +** KEY, the rbu_control value should not include a character corresponding +** to the rbu_rowid value. For example, this: +** +** INSERT INTO data_ft1(a, b, rbu_rowid, rbu_control) +** VALUES(NULL, 'usa', 12, '.x'); +** +** causes a result similar to: +** +** UPDATE ft1 SET b = 'usa' WHERE rowid = 12; +** +** The data_xxx tables themselves should have no PRIMARY KEY declarations. +** However, RBU is more efficient if reading the rows in from each data_xxx +** table in "rowid" order is roughly the same as reading them sorted by +** the PRIMARY KEY of the corresponding target database table. In other +** words, rows should be sorted using the destination table PRIMARY KEY +** fields before they are inserted into the data_xxx tables. +** +** USAGE +** +** The API declared below allows an application to apply an RBU update +** stored on disk to an existing target database. Essentially, the +** application: +** +** 1) Opens an RBU handle using the sqlite3rbu_open() function. +** +** 2) Registers any required virtual table modules with the database +** handle returned by sqlite3rbu_db(). Also, if required, register +** the rbu_delta() implementation. +** +** 3) Calls the sqlite3rbu_step() function one or more times on +** the new handle. Each call to sqlite3rbu_step() performs a single +** b-tree operation, so thousands of calls may be required to apply +** a complete update. +** +** 4) Calls sqlite3rbu_close() to close the RBU update handle. If +** sqlite3rbu_step() has been called enough times to completely +** apply the update to the target database, then the RBU database +** is marked as fully applied. Otherwise, the state of the RBU +** update application is saved in the RBU database for later +** resumption. +** +** See comments below for more detail on APIs. +** +** If an update is only partially applied to the target database by the +** time sqlite3rbu_close() is called, various state information is saved +** within the RBU database. This allows subsequent processes to automatically +** resume the RBU update from where it left off. +** +** To remove all RBU extension state information, returning an RBU database +** to its original contents, it is sufficient to drop all tables that begin +** with the prefix "rbu_" +** +** DATABASE LOCKING +** +** An RBU update may not be applied to a database in WAL mode. Attempting +** to do so is an error (SQLITE_ERROR). +** +** While an RBU handle is open, a SHARED lock may be held on the target +** database file. This means it is possible for other clients to read the +** database, but not to write it. +** +** If an RBU update is started and then suspended before it is completed, +** then an external client writes to the database, then attempting to resume +** the suspended RBU update is also an error (SQLITE_BUSY). +*/ + +#ifndef _SQLITE3RBU_H +#define _SQLITE3RBU_H + +/* #include "sqlite3.h" ** Required for error code definitions ** */ + +#if 0 +extern "C" { +#endif + +typedef struct sqlite3rbu sqlite3rbu; + +/* +** Open an RBU handle. +** +** Argument zTarget is the path to the target database. Argument zRbu is +** the path to the RBU database. Each call to this function must be matched +** by a call to sqlite3rbu_close(). When opening the databases, RBU passes +** the SQLITE_CONFIG_URI flag to sqlite3_open_v2(). So if either zTarget +** or zRbu begin with "file:", it will be interpreted as an SQLite +** database URI, not a regular file name. +** +** If the zState argument is passed a NULL value, the RBU extension stores +** the current state of the update (how many rows have been updated, which +** indexes are yet to be updated etc.) within the RBU database itself. This +** can be convenient, as it means that the RBU application does not need to +** organize removing a separate state file after the update is concluded. +** Or, if zState is non-NULL, it must be a path to a database file in which +** the RBU extension can store the state of the update. +** +** When resuming an RBU update, the zState argument must be passed the same +** value as when the RBU update was started. +** +** Once the RBU update is finished, the RBU extension does not +** automatically remove any zState database file, even if it created it. +** +** By default, RBU uses the default VFS to access the files on disk. To +** use a VFS other than the default, an SQLite "file:" URI containing a +** "vfs=..." option may be passed as the zTarget option. +** +** IMPORTANT NOTE FOR ZIPVFS USERS: The RBU extension works with all of +** SQLite's built-in VFSs, including the multiplexor VFS. However it does +** not work out of the box with zipvfs. Refer to the comment describing +** the zipvfs_create_vfs() API below for details on using RBU with zipvfs. +*/ +SQLITE_API sqlite3rbu *SQLITE_STDCALL sqlite3rbu_open( + const char *zTarget, + const char *zRbu, + const char *zState +); + +/* +** Internally, each RBU connection uses a separate SQLite database +** connection to access the target and rbu update databases. This +** API allows the application direct access to these database handles. +** +** The first argument passed to this function must be a valid, open, RBU +** handle. The second argument should be passed zero to access the target +** database handle, or non-zero to access the rbu update database handle. +** Accessing the underlying database handles may be useful in the +** following scenarios: +** +** * If any target tables are virtual tables, it may be necessary to +** call sqlite3_create_module() on the target database handle to +** register the required virtual table implementations. +** +** * If the data_xxx tables in the RBU source database are virtual +** tables, the application may need to call sqlite3_create_module() on +** the rbu update db handle to any required virtual table +** implementations. +** +** * If the application uses the "rbu_delta()" feature described above, +** it must use sqlite3_create_function() or similar to register the +** rbu_delta() implementation with the target database handle. +** +** If an error has occurred, either while opening or stepping the RBU object, +** this function may return NULL. The error code and message may be collected +** when sqlite3rbu_close() is called. +** +** Database handles returned by this function remain valid until the next +** call to any sqlite3rbu_xxx() function other than sqlite3rbu_db(). +*/ +SQLITE_API sqlite3 *SQLITE_STDCALL sqlite3rbu_db(sqlite3rbu*, int bRbu); + +/* +** Do some work towards applying the RBU update to the target db. +** +** Return SQLITE_DONE if the update has been completely applied, or +** SQLITE_OK if no error occurs but there remains work to do to apply +** the RBU update. If an error does occur, some other error code is +** returned. +** +** Once a call to sqlite3rbu_step() has returned a value other than +** SQLITE_OK, all subsequent calls on the same RBU handle are no-ops +** that immediately return the same value. +*/ +SQLITE_API int SQLITE_STDCALL sqlite3rbu_step(sqlite3rbu *pRbu); + +/* +** Force RBU to save its state to disk. +** +** If a power failure or application crash occurs during an update, following +** system recovery RBU may resume the update from the point at which the state +** was last saved. In other words, from the most recent successful call to +** sqlite3rbu_close() or this function. +** +** SQLITE_OK is returned if successful, or an SQLite error code otherwise. +*/ +SQLITE_API int SQLITE_STDCALL sqlite3rbu_savestate(sqlite3rbu *pRbu); + +/* +** Close an RBU handle. +** +** If the RBU update has been completely applied, mark the RBU database +** as fully applied. Otherwise, assuming no error has occurred, save the +** current state of the RBU update appliation to the RBU database. +** +** If an error has already occurred as part of an sqlite3rbu_step() +** or sqlite3rbu_open() call, or if one occurs within this function, an +** SQLite error code is returned. Additionally, *pzErrmsg may be set to +** point to a buffer containing a utf-8 formatted English language error +** message. It is the responsibility of the caller to eventually free any +** such buffer using sqlite3_free(). +** +** Otherwise, if no error occurs, this function returns SQLITE_OK if the +** update has been partially applied, or SQLITE_DONE if it has been +** completely applied. +*/ +SQLITE_API int SQLITE_STDCALL sqlite3rbu_close(sqlite3rbu *pRbu, char **pzErrmsg); + +/* +** Return the total number of key-value operations (inserts, deletes or +** updates) that have been performed on the target database since the +** current RBU update was started. +*/ +SQLITE_API sqlite3_int64 SQLITE_STDCALL sqlite3rbu_progress(sqlite3rbu *pRbu); + +/* +** Create an RBU VFS named zName that accesses the underlying file-system +** via existing VFS zParent. Or, if the zParent parameter is passed NULL, +** then the new RBU VFS uses the default system VFS to access the file-system. +** The new object is registered as a non-default VFS with SQLite before +** returning. +** +** Part of the RBU implementation uses a custom VFS object. Usually, this +** object is created and deleted automatically by RBU. +** +** The exception is for applications that also use zipvfs. In this case, +** the custom VFS must be explicitly created by the user before the RBU +** handle is opened. The RBU VFS should be installed so that the zipvfs +** VFS uses the RBU VFS, which in turn uses any other VFS layers in use +** (for example multiplexor) to access the file-system. For example, +** to assemble an RBU enabled VFS stack that uses both zipvfs and +** multiplexor (error checking omitted): +** +** // Create a VFS named "multiplex" (not the default). +** sqlite3_multiplex_initialize(0, 0); +** +** // Create an rbu VFS named "rbu" that uses multiplexor. If the +** // second argument were replaced with NULL, the "rbu" VFS would +** // access the file-system via the system default VFS, bypassing the +** // multiplexor. +** sqlite3rbu_create_vfs("rbu", "multiplex"); +** +** // Create a zipvfs VFS named "zipvfs" that uses rbu. +** zipvfs_create_vfs_v3("zipvfs", "rbu", 0, xCompressorAlgorithmDetector); +** +** // Make zipvfs the default VFS. +** sqlite3_vfs_register(sqlite3_vfs_find("zipvfs"), 1); +** +** Because the default VFS created above includes a RBU functionality, it +** may be used by RBU clients. Attempting to use RBU with a zipvfs VFS stack +** that does not include the RBU layer results in an error. +** +** The overhead of adding the "rbu" VFS to the system is negligible for +** non-RBU users. There is no harm in an application accessing the +** file-system via "rbu" all the time, even if it only uses RBU functionality +** occasionally. +*/ +SQLITE_API int SQLITE_STDCALL sqlite3rbu_create_vfs(const char *zName, const char *zParent); + +/* +** Deregister and destroy an RBU vfs created by an earlier call to +** sqlite3rbu_create_vfs(). +** +** VFS objects are not reference counted. If a VFS object is destroyed +** before all database handles that use it have been closed, the results +** are undefined. +*/ +SQLITE_API void SQLITE_STDCALL sqlite3rbu_destroy_vfs(const char *zName); + +#if 0 +} /* end of the 'extern "C"' block */ +#endif + +#endif /* _SQLITE3RBU_H */ + +/************** End of sqlite3rbu.h ******************************************/ +/************** Continuing where we left off in sqlite3rbu.c *****************/ + +#if defined(_WIN32_WCE) +/* #include "windows.h" */ +#endif + +/* Maximum number of prepared UPDATE statements held by this module */ +#define SQLITE_RBU_UPDATE_CACHESIZE 16 + +/* +** Swap two objects of type TYPE. +*/ +#if !defined(SQLITE_AMALGAMATION) +# define SWAP(TYPE,A,B) {TYPE t=A; A=B; B=t;} +#endif + +/* +** The rbu_state table is used to save the state of a partially applied +** update so that it can be resumed later. The table consists of integer +** keys mapped to values as follows: +** +** RBU_STATE_STAGE: +** May be set to integer values 1, 2, 4 or 5. As follows: +** 1: the *-rbu file is currently under construction. +** 2: the *-rbu file has been constructed, but not yet moved +** to the *-wal path. +** 4: the checkpoint is underway. +** 5: the rbu update has been checkpointed. +** +** RBU_STATE_TBL: +** Only valid if STAGE==1. The target database name of the table +** currently being written. +** +** RBU_STATE_IDX: +** Only valid if STAGE==1. The target database name of the index +** currently being written, or NULL if the main table is currently being +** updated. +** +** RBU_STATE_ROW: +** Only valid if STAGE==1. Number of rows already processed for the current +** table/index. +** +** RBU_STATE_PROGRESS: +** Trbul number of sqlite3rbu_step() calls made so far as part of this +** rbu update. +** +** RBU_STATE_CKPT: +** Valid if STAGE==4. The 64-bit checksum associated with the wal-index +** header created by recovering the *-wal file. This is used to detect +** cases when another client appends frames to the *-wal file in the +** middle of an incremental checkpoint (an incremental checkpoint cannot +** be continued if this happens). +** +** RBU_STATE_COOKIE: +** Valid if STAGE==1. The current change-counter cookie value in the +** target db file. +** +** RBU_STATE_OALSZ: +** Valid if STAGE==1. The size in bytes of the *-oal file. +*/ +#define RBU_STATE_STAGE 1 +#define RBU_STATE_TBL 2 +#define RBU_STATE_IDX 3 +#define RBU_STATE_ROW 4 +#define RBU_STATE_PROGRESS 5 +#define RBU_STATE_CKPT 6 +#define RBU_STATE_COOKIE 7 +#define RBU_STATE_OALSZ 8 + +#define RBU_STAGE_OAL 1 +#define RBU_STAGE_MOVE 2 +#define RBU_STAGE_CAPTURE 3 +#define RBU_STAGE_CKPT 4 +#define RBU_STAGE_DONE 5 + + +#define RBU_CREATE_STATE \ + "CREATE TABLE IF NOT EXISTS %s.rbu_state(k INTEGER PRIMARY KEY, v)" + +typedef struct RbuFrame RbuFrame; +typedef struct RbuObjIter RbuObjIter; +typedef struct RbuState RbuState; +typedef struct rbu_vfs rbu_vfs; +typedef struct rbu_file rbu_file; +typedef struct RbuUpdateStmt RbuUpdateStmt; + +#if !defined(SQLITE_AMALGAMATION) +typedef unsigned int u32; +typedef unsigned char u8; +typedef sqlite3_int64 i64; +#endif + +/* +** These values must match the values defined in wal.c for the equivalent +** locks. These are not magic numbers as they are part of the SQLite file +** format. +*/ +#define WAL_LOCK_WRITE 0 +#define WAL_LOCK_CKPT 1 +#define WAL_LOCK_READ0 3 + +/* +** A structure to store values read from the rbu_state table in memory. +*/ +struct RbuState { + int eStage; + char *zTbl; + char *zIdx; + i64 iWalCksum; + int nRow; + i64 nProgress; + u32 iCookie; + i64 iOalSz; +}; + +struct RbuUpdateStmt { + char *zMask; /* Copy of update mask used with pUpdate */ + sqlite3_stmt *pUpdate; /* Last update statement (or NULL) */ + RbuUpdateStmt *pNext; +}; + +/* +** An iterator of this type is used to iterate through all objects in +** the target database that require updating. For each such table, the +** iterator visits, in order: +** +** * the table itself, +** * each index of the table (zero or more points to visit), and +** * a special "cleanup table" state. +** +** abIndexed: +** If the table has no indexes on it, abIndexed is set to NULL. Otherwise, +** it points to an array of flags nTblCol elements in size. The flag is +** set for each column that is either a part of the PK or a part of an +** index. Or clear otherwise. +** +*/ +struct RbuObjIter { + sqlite3_stmt *pTblIter; /* Iterate through tables */ + sqlite3_stmt *pIdxIter; /* Index iterator */ + int nTblCol; /* Size of azTblCol[] array */ + char **azTblCol; /* Array of unquoted target column names */ + char **azTblType; /* Array of target column types */ + int *aiSrcOrder; /* src table col -> target table col */ + u8 *abTblPk; /* Array of flags, set on target PK columns */ + u8 *abNotNull; /* Array of flags, set on NOT NULL columns */ + u8 *abIndexed; /* Array of flags, set on indexed & PK cols */ + int eType; /* Table type - an RBU_PK_XXX value */ + + /* Output variables. zTbl==0 implies EOF. */ + int bCleanup; /* True in "cleanup" state */ + const char *zTbl; /* Name of target db table */ + const char *zDataTbl; /* Name of rbu db table (or null) */ + const char *zIdx; /* Name of target db index (or null) */ + int iTnum; /* Root page of current object */ + int iPkTnum; /* If eType==EXTERNAL, root of PK index */ + int bUnique; /* Current index is unique */ + + /* Statements created by rbuObjIterPrepareAll() */ + int nCol; /* Number of columns in current object */ + sqlite3_stmt *pSelect; /* Source data */ + sqlite3_stmt *pInsert; /* Statement for INSERT operations */ + sqlite3_stmt *pDelete; /* Statement for DELETE ops */ + sqlite3_stmt *pTmpInsert; /* Insert into rbu_tmp_$zDataTbl */ + + /* Last UPDATE used (for PK b-tree updates only), or NULL. */ + RbuUpdateStmt *pRbuUpdate; +}; + +/* +** Values for RbuObjIter.eType +** +** 0: Table does not exist (error) +** 1: Table has an implicit rowid. +** 2: Table has an explicit IPK column. +** 3: Table has an external PK index. +** 4: Table is WITHOUT ROWID. +** 5: Table is a virtual table. +*/ +#define RBU_PK_NOTABLE 0 +#define RBU_PK_NONE 1 +#define RBU_PK_IPK 2 +#define RBU_PK_EXTERNAL 3 +#define RBU_PK_WITHOUT_ROWID 4 +#define RBU_PK_VTAB 5 + + +/* +** Within the RBU_STAGE_OAL stage, each call to sqlite3rbu_step() performs +** one of the following operations. +*/ +#define RBU_INSERT 1 /* Insert on a main table b-tree */ +#define RBU_DELETE 2 /* Delete a row from a main table b-tree */ +#define RBU_IDX_DELETE 3 /* Delete a row from an aux. index b-tree */ +#define RBU_IDX_INSERT 4 /* Insert on an aux. index b-tree */ +#define RBU_UPDATE 5 /* Update a row in a main table b-tree */ + + +/* +** A single step of an incremental checkpoint - frame iWalFrame of the wal +** file should be copied to page iDbPage of the database file. +*/ +struct RbuFrame { + u32 iDbPage; + u32 iWalFrame; +}; + +/* +** RBU handle. +*/ +struct sqlite3rbu { + int eStage; /* Value of RBU_STATE_STAGE field */ + sqlite3 *dbMain; /* target database handle */ + sqlite3 *dbRbu; /* rbu database handle */ + char *zTarget; /* Path to target db */ + char *zRbu; /* Path to rbu db */ + char *zState; /* Path to state db (or NULL if zRbu) */ + char zStateDb[5]; /* Db name for state ("stat" or "main") */ + int rc; /* Value returned by last rbu_step() call */ + char *zErrmsg; /* Error message if rc!=SQLITE_OK */ + int nStep; /* Rows processed for current object */ + int nProgress; /* Rows processed for all objects */ + RbuObjIter objiter; /* Iterator for skipping through tbl/idx */ + const char *zVfsName; /* Name of automatically created rbu vfs */ + rbu_file *pTargetFd; /* File handle open on target db */ + i64 iOalSz; + + /* The following state variables are used as part of the incremental + ** checkpoint stage (eStage==RBU_STAGE_CKPT). See comments surrounding + ** function rbuSetupCheckpoint() for details. */ + u32 iMaxFrame; /* Largest iWalFrame value in aFrame[] */ + u32 mLock; + int nFrame; /* Entries in aFrame[] array */ + int nFrameAlloc; /* Allocated size of aFrame[] array */ + RbuFrame *aFrame; + int pgsz; + u8 *aBuf; + i64 iWalCksum; +}; + +/* +** An rbu VFS is implemented using an instance of this structure. +*/ +struct rbu_vfs { + sqlite3_vfs base; /* rbu VFS shim methods */ + sqlite3_vfs *pRealVfs; /* Underlying VFS */ + sqlite3_mutex *mutex; /* Mutex to protect pMain */ + rbu_file *pMain; /* Linked list of main db files */ +}; + +/* +** Each file opened by an rbu VFS is represented by an instance of +** the following structure. +*/ +struct rbu_file { + sqlite3_file base; /* sqlite3_file methods */ + sqlite3_file *pReal; /* Underlying file handle */ + rbu_vfs *pRbuVfs; /* Pointer to the rbu_vfs object */ + sqlite3rbu *pRbu; /* Pointer to rbu object (rbu target only) */ + + int openFlags; /* Flags this file was opened with */ + u32 iCookie; /* Cookie value for main db files */ + u8 iWriteVer; /* "write-version" value for main db files */ + + int nShm; /* Number of entries in apShm[] array */ + char **apShm; /* Array of mmap'd *-shm regions */ + char *zDel; /* Delete this when closing file */ + + const char *zWal; /* Wal filename for this main db file */ + rbu_file *pWalFd; /* Wal file descriptor for this main db */ + rbu_file *pMainNext; /* Next MAIN_DB file */ +}; + + +/************************************************************************* +** The following three functions, found below: +** +** rbuDeltaGetInt() +** rbuDeltaChecksum() +** rbuDeltaApply() +** +** are lifted from the fossil source code (http://fossil-scm.org). They +** are used to implement the scalar SQL function rbu_fossil_delta(). +*/ + +/* +** Read bytes from *pz and convert them into a positive integer. When +** finished, leave *pz pointing to the first character past the end of +** the integer. The *pLen parameter holds the length of the string +** in *pz and is decremented once for each character in the integer. +*/ +static unsigned int rbuDeltaGetInt(const char **pz, int *pLen){ + static const signed char zValue[] = { + -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, + -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, + -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, + 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, -1, -1, -1, -1, -1, -1, + -1, 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, -1, -1, -1, -1, 36, + -1, 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, -1, -1, -1, 63, -1, + }; + unsigned int v = 0; + int c; + unsigned char *z = (unsigned char*)*pz; + unsigned char *zStart = z; + while( (c = zValue[0x7f&*(z++)])>=0 ){ + v = (v<<6) + c; + } + z--; + *pLen -= z - zStart; + *pz = (char*)z; + return v; +} + +/* +** Compute a 32-bit checksum on the N-byte buffer. Return the result. +*/ +static unsigned int rbuDeltaChecksum(const char *zIn, size_t N){ + const unsigned char *z = (const unsigned char *)zIn; + unsigned sum0 = 0; + unsigned sum1 = 0; + unsigned sum2 = 0; + unsigned sum3 = 0; + while(N >= 16){ + sum0 += ((unsigned)z[0] + z[4] + z[8] + z[12]); + sum1 += ((unsigned)z[1] + z[5] + z[9] + z[13]); + sum2 += ((unsigned)z[2] + z[6] + z[10]+ z[14]); + sum3 += ((unsigned)z[3] + z[7] + z[11]+ z[15]); + z += 16; + N -= 16; + } + while(N >= 4){ + sum0 += z[0]; + sum1 += z[1]; + sum2 += z[2]; + sum3 += z[3]; + z += 4; + N -= 4; + } + sum3 += (sum2 << 8) + (sum1 << 16) + (sum0 << 24); + switch(N){ + case 3: sum3 += (z[2] << 8); + case 2: sum3 += (z[1] << 16); + case 1: sum3 += (z[0] << 24); + default: ; + } + return sum3; +} + +/* +** Apply a delta. +** +** The output buffer should be big enough to hold the whole output +** file and a NUL terminator at the end. The delta_output_size() +** routine will determine this size for you. +** +** The delta string should be null-terminated. But the delta string +** may contain embedded NUL characters (if the input and output are +** binary files) so we also have to pass in the length of the delta in +** the lenDelta parameter. +** +** This function returns the size of the output file in bytes (excluding +** the final NUL terminator character). Except, if the delta string is +** malformed or intended for use with a source file other than zSrc, +** then this routine returns -1. +** +** Refer to the delta_create() documentation above for a description +** of the delta file format. +*/ +static int rbuDeltaApply( + const char *zSrc, /* The source or pattern file */ + int lenSrc, /* Length of the source file */ + const char *zDelta, /* Delta to apply to the pattern */ + int lenDelta, /* Length of the delta */ + char *zOut /* Write the output into this preallocated buffer */ +){ + unsigned int limit; + unsigned int total = 0; +#ifndef FOSSIL_OMIT_DELTA_CKSUM_TEST + char *zOrigOut = zOut; +#endif + + limit = rbuDeltaGetInt(&zDelta, &lenDelta); + if( *zDelta!='\n' ){ + /* ERROR: size integer not terminated by "\n" */ + return -1; + } + zDelta++; lenDelta--; + while( *zDelta && lenDelta>0 ){ + unsigned int cnt, ofst; + cnt = rbuDeltaGetInt(&zDelta, &lenDelta); + switch( zDelta[0] ){ + case '@': { + zDelta++; lenDelta--; + ofst = rbuDeltaGetInt(&zDelta, &lenDelta); + if( lenDelta>0 && zDelta[0]!=',' ){ + /* ERROR: copy command not terminated by ',' */ + return -1; + } + zDelta++; lenDelta--; + total += cnt; + if( total>limit ){ + /* ERROR: copy exceeds output file size */ + return -1; + } + if( (int)(ofst+cnt) > lenSrc ){ + /* ERROR: copy extends past end of input */ + return -1; + } + memcpy(zOut, &zSrc[ofst], cnt); + zOut += cnt; + break; + } + case ':': { + zDelta++; lenDelta--; + total += cnt; + if( total>limit ){ + /* ERROR: insert command gives an output larger than predicted */ + return -1; + } + if( (int)cnt>lenDelta ){ + /* ERROR: insert count exceeds size of delta */ + return -1; + } + memcpy(zOut, zDelta, cnt); + zOut += cnt; + zDelta += cnt; + lenDelta -= cnt; + break; + } + case ';': { + zDelta++; lenDelta--; + zOut[0] = 0; +#ifndef FOSSIL_OMIT_DELTA_CKSUM_TEST + if( cnt!=rbuDeltaChecksum(zOrigOut, total) ){ + /* ERROR: bad checksum */ + return -1; + } +#endif + if( total!=limit ){ + /* ERROR: generated size does not match predicted size */ + return -1; + } + return total; + } + default: { + /* ERROR: unknown delta operator */ + return -1; + } + } + } + /* ERROR: unterminated delta */ + return -1; +} + +static int rbuDeltaOutputSize(const char *zDelta, int lenDelta){ + int size; + size = rbuDeltaGetInt(&zDelta, &lenDelta); + if( *zDelta!='\n' ){ + /* ERROR: size integer not terminated by "\n" */ + return -1; + } + return size; +} + +/* +** End of code taken from fossil. +*************************************************************************/ + +/* +** Implementation of SQL scalar function rbu_fossil_delta(). +** +** This function applies a fossil delta patch to a blob. Exactly two +** arguments must be passed to this function. The first is the blob to +** patch and the second the patch to apply. If no error occurs, this +** function returns the patched blob. +*/ +static void rbuFossilDeltaFunc( + sqlite3_context *context, + int argc, + sqlite3_value **argv +){ + const char *aDelta; + int nDelta; + const char *aOrig; + int nOrig; + + int nOut; + int nOut2; + char *aOut; + + assert( argc==2 ); + + nOrig = sqlite3_value_bytes(argv[0]); + aOrig = (const char*)sqlite3_value_blob(argv[0]); + nDelta = sqlite3_value_bytes(argv[1]); + aDelta = (const char*)sqlite3_value_blob(argv[1]); + + /* Figure out the size of the output */ + nOut = rbuDeltaOutputSize(aDelta, nDelta); + if( nOut<0 ){ + sqlite3_result_error(context, "corrupt fossil delta", -1); + return; + } + + aOut = sqlite3_malloc(nOut+1); + if( aOut==0 ){ + sqlite3_result_error_nomem(context); + }else{ + nOut2 = rbuDeltaApply(aOrig, nOrig, aDelta, nDelta, aOut); + if( nOut2!=nOut ){ + sqlite3_result_error(context, "corrupt fossil delta", -1); + }else{ + sqlite3_result_blob(context, aOut, nOut, sqlite3_free); + } + } +} + + +/* +** Prepare the SQL statement in buffer zSql against database handle db. +** If successful, set *ppStmt to point to the new statement and return +** SQLITE_OK. +** +** Otherwise, if an error does occur, set *ppStmt to NULL and return +** an SQLite error code. Additionally, set output variable *pzErrmsg to +** point to a buffer containing an error message. It is the responsibility +** of the caller to (eventually) free this buffer using sqlite3_free(). +*/ +static int prepareAndCollectError( + sqlite3 *db, + sqlite3_stmt **ppStmt, + char **pzErrmsg, + const char *zSql +){ + int rc = sqlite3_prepare_v2(db, zSql, -1, ppStmt, 0); + if( rc!=SQLITE_OK ){ + *pzErrmsg = sqlite3_mprintf("%s", sqlite3_errmsg(db)); + *ppStmt = 0; + } + return rc; +} + +/* +** Reset the SQL statement passed as the first argument. Return a copy +** of the value returned by sqlite3_reset(). +** +** If an error has occurred, then set *pzErrmsg to point to a buffer +** containing an error message. It is the responsibility of the caller +** to eventually free this buffer using sqlite3_free(). +*/ +static int resetAndCollectError(sqlite3_stmt *pStmt, char **pzErrmsg){ + int rc = sqlite3_reset(pStmt); + if( rc!=SQLITE_OK ){ + *pzErrmsg = sqlite3_mprintf("%s", sqlite3_errmsg(sqlite3_db_handle(pStmt))); + } + return rc; +} + +/* +** Unless it is NULL, argument zSql points to a buffer allocated using +** sqlite3_malloc containing an SQL statement. This function prepares the SQL +** statement against database db and frees the buffer. If statement +** compilation is successful, *ppStmt is set to point to the new statement +** handle and SQLITE_OK is returned. +** +** Otherwise, if an error occurs, *ppStmt is set to NULL and an error code +** returned. In this case, *pzErrmsg may also be set to point to an error +** message. It is the responsibility of the caller to free this error message +** buffer using sqlite3_free(). +** +** If argument zSql is NULL, this function assumes that an OOM has occurred. +** In this case SQLITE_NOMEM is returned and *ppStmt set to NULL. +*/ +static int prepareFreeAndCollectError( + sqlite3 *db, + sqlite3_stmt **ppStmt, + char **pzErrmsg, + char *zSql +){ + int rc; + assert( *pzErrmsg==0 ); + if( zSql==0 ){ + rc = SQLITE_NOMEM; + *ppStmt = 0; + }else{ + rc = prepareAndCollectError(db, ppStmt, pzErrmsg, zSql); + sqlite3_free(zSql); + } + return rc; +} + +/* +** Free the RbuObjIter.azTblCol[] and RbuObjIter.abTblPk[] arrays allocated +** by an earlier call to rbuObjIterCacheTableInfo(). +*/ +static void rbuObjIterFreeCols(RbuObjIter *pIter){ + int i; + for(i=0; inTblCol; i++){ + sqlite3_free(pIter->azTblCol[i]); + sqlite3_free(pIter->azTblType[i]); + } + sqlite3_free(pIter->azTblCol); + pIter->azTblCol = 0; + pIter->azTblType = 0; + pIter->aiSrcOrder = 0; + pIter->abTblPk = 0; + pIter->abNotNull = 0; + pIter->nTblCol = 0; + pIter->eType = 0; /* Invalid value */ +} + +/* +** Finalize all statements and free all allocations that are specific to +** the current object (table/index pair). +*/ +static void rbuObjIterClearStatements(RbuObjIter *pIter){ + RbuUpdateStmt *pUp; + + sqlite3_finalize(pIter->pSelect); + sqlite3_finalize(pIter->pInsert); + sqlite3_finalize(pIter->pDelete); + sqlite3_finalize(pIter->pTmpInsert); + pUp = pIter->pRbuUpdate; + while( pUp ){ + RbuUpdateStmt *pTmp = pUp->pNext; + sqlite3_finalize(pUp->pUpdate); + sqlite3_free(pUp); + pUp = pTmp; + } + + pIter->pSelect = 0; + pIter->pInsert = 0; + pIter->pDelete = 0; + pIter->pRbuUpdate = 0; + pIter->pTmpInsert = 0; + pIter->nCol = 0; +} + +/* +** Clean up any resources allocated as part of the iterator object passed +** as the only argument. +*/ +static void rbuObjIterFinalize(RbuObjIter *pIter){ + rbuObjIterClearStatements(pIter); + sqlite3_finalize(pIter->pTblIter); + sqlite3_finalize(pIter->pIdxIter); + rbuObjIterFreeCols(pIter); + memset(pIter, 0, sizeof(RbuObjIter)); +} + +/* +** Advance the iterator to the next position. +** +** If no error occurs, SQLITE_OK is returned and the iterator is left +** pointing to the next entry. Otherwise, an error code and message is +** left in the RBU handle passed as the first argument. A copy of the +** error code is returned. +*/ +static int rbuObjIterNext(sqlite3rbu *p, RbuObjIter *pIter){ + int rc = p->rc; + if( rc==SQLITE_OK ){ + + /* Free any SQLite statements used while processing the previous object */ + rbuObjIterClearStatements(pIter); + if( pIter->zIdx==0 ){ + rc = sqlite3_exec(p->dbMain, + "DROP TRIGGER IF EXISTS temp.rbu_insert_tr;" + "DROP TRIGGER IF EXISTS temp.rbu_update1_tr;" + "DROP TRIGGER IF EXISTS temp.rbu_update2_tr;" + "DROP TRIGGER IF EXISTS temp.rbu_delete_tr;" + , 0, 0, &p->zErrmsg + ); + } + + if( rc==SQLITE_OK ){ + if( pIter->bCleanup ){ + rbuObjIterFreeCols(pIter); + pIter->bCleanup = 0; + rc = sqlite3_step(pIter->pTblIter); + if( rc!=SQLITE_ROW ){ + rc = resetAndCollectError(pIter->pTblIter, &p->zErrmsg); + pIter->zTbl = 0; + }else{ + pIter->zTbl = (const char*)sqlite3_column_text(pIter->pTblIter, 0); + pIter->zDataTbl = (const char*)sqlite3_column_text(pIter->pTblIter,1); + rc = (pIter->zDataTbl && pIter->zTbl) ? SQLITE_OK : SQLITE_NOMEM; + } + }else{ + if( pIter->zIdx==0 ){ + sqlite3_stmt *pIdx = pIter->pIdxIter; + rc = sqlite3_bind_text(pIdx, 1, pIter->zTbl, -1, SQLITE_STATIC); + } + if( rc==SQLITE_OK ){ + rc = sqlite3_step(pIter->pIdxIter); + if( rc!=SQLITE_ROW ){ + rc = resetAndCollectError(pIter->pIdxIter, &p->zErrmsg); + pIter->bCleanup = 1; + pIter->zIdx = 0; + }else{ + pIter->zIdx = (const char*)sqlite3_column_text(pIter->pIdxIter, 0); + pIter->iTnum = sqlite3_column_int(pIter->pIdxIter, 1); + pIter->bUnique = sqlite3_column_int(pIter->pIdxIter, 2); + rc = pIter->zIdx ? SQLITE_OK : SQLITE_NOMEM; + } + } + } + } + } + + if( rc!=SQLITE_OK ){ + rbuObjIterFinalize(pIter); + p->rc = rc; + } + return rc; +} + + +/* +** The implementation of the rbu_target_name() SQL function. This function +** accepts one argument - the name of a table in the RBU database. If the +** table name matches the pattern: +** +** data[0-9]_ +** +** where is any sequence of 1 or more characters, is returned. +** Otherwise, if the only argument does not match the above pattern, an SQL +** NULL is returned. +** +** "data_t1" -> "t1" +** "data0123_t2" -> "t2" +** "dataAB_t3" -> NULL +*/ +static void rbuTargetNameFunc( + sqlite3_context *context, + int argc, + sqlite3_value **argv +){ + const char *zIn; + assert( argc==1 ); + + zIn = (const char*)sqlite3_value_text(argv[0]); + if( zIn && strlen(zIn)>4 && memcmp("data", zIn, 4)==0 ){ + int i; + for(i=4; zIn[i]>='0' && zIn[i]<='9'; i++); + if( zIn[i]=='_' && zIn[i+1] ){ + sqlite3_result_text(context, &zIn[i+1], -1, SQLITE_STATIC); + } + } +} + +/* +** Initialize the iterator structure passed as the second argument. +** +** If no error occurs, SQLITE_OK is returned and the iterator is left +** pointing to the first entry. Otherwise, an error code and message is +** left in the RBU handle passed as the first argument. A copy of the +** error code is returned. +*/ +static int rbuObjIterFirst(sqlite3rbu *p, RbuObjIter *pIter){ + int rc; + memset(pIter, 0, sizeof(RbuObjIter)); + + rc = prepareAndCollectError(p->dbRbu, &pIter->pTblIter, &p->zErrmsg, + "SELECT rbu_target_name(name) AS target, name FROM sqlite_master " + "WHERE type IN ('table', 'view') AND target IS NOT NULL " + "ORDER BY name" + ); + + if( rc==SQLITE_OK ){ + rc = prepareAndCollectError(p->dbMain, &pIter->pIdxIter, &p->zErrmsg, + "SELECT name, rootpage, sql IS NULL OR substr(8, 6)=='UNIQUE' " + " FROM main.sqlite_master " + " WHERE type='index' AND tbl_name = ?" + ); + } + + pIter->bCleanup = 1; + p->rc = rc; + return rbuObjIterNext(p, pIter); +} + +/* +** This is a wrapper around "sqlite3_mprintf(zFmt, ...)". If an OOM occurs, +** an error code is stored in the RBU handle passed as the first argument. +** +** If an error has already occurred (p->rc is already set to something other +** than SQLITE_OK), then this function returns NULL without modifying the +** stored error code. In this case it still calls sqlite3_free() on any +** printf() parameters associated with %z conversions. +*/ +static char *rbuMPrintf(sqlite3rbu *p, const char *zFmt, ...){ + char *zSql = 0; + va_list ap; + va_start(ap, zFmt); + zSql = sqlite3_vmprintf(zFmt, ap); + if( p->rc==SQLITE_OK ){ + if( zSql==0 ) p->rc = SQLITE_NOMEM; + }else{ + sqlite3_free(zSql); + zSql = 0; + } + va_end(ap); + return zSql; +} + +/* +** Argument zFmt is a sqlite3_mprintf() style format string. The trailing +** arguments are the usual subsitution values. This function performs +** the printf() style substitutions and executes the result as an SQL +** statement on the RBU handles database. +** +** If an error occurs, an error code and error message is stored in the +** RBU handle. If an error has already occurred when this function is +** called, it is a no-op. +*/ +static int rbuMPrintfExec(sqlite3rbu *p, sqlite3 *db, const char *zFmt, ...){ + va_list ap; + char *zSql; + va_start(ap, zFmt); + zSql = sqlite3_vmprintf(zFmt, ap); + if( p->rc==SQLITE_OK ){ + if( zSql==0 ){ + p->rc = SQLITE_NOMEM; + }else{ + p->rc = sqlite3_exec(db, zSql, 0, 0, &p->zErrmsg); + } + } + sqlite3_free(zSql); + va_end(ap); + return p->rc; +} + +/* +** Attempt to allocate and return a pointer to a zeroed block of nByte +** bytes. +** +** If an error (i.e. an OOM condition) occurs, return NULL and leave an +** error code in the rbu handle passed as the first argument. Or, if an +** error has already occurred when this function is called, return NULL +** immediately without attempting the allocation or modifying the stored +** error code. +*/ +static void *rbuMalloc(sqlite3rbu *p, int nByte){ + void *pRet = 0; + if( p->rc==SQLITE_OK ){ + assert( nByte>0 ); + pRet = sqlite3_malloc(nByte); + if( pRet==0 ){ + p->rc = SQLITE_NOMEM; + }else{ + memset(pRet, 0, nByte); + } + } + return pRet; +} + + +/* +** Allocate and zero the pIter->azTblCol[] and abTblPk[] arrays so that +** there is room for at least nCol elements. If an OOM occurs, store an +** error code in the RBU handle passed as the first argument. +*/ +static void rbuAllocateIterArrays(sqlite3rbu *p, RbuObjIter *pIter, int nCol){ + int nByte = (2*sizeof(char*) + sizeof(int) + 3*sizeof(u8)) * nCol; + char **azNew; + + azNew = (char**)rbuMalloc(p, nByte); + if( azNew ){ + pIter->azTblCol = azNew; + pIter->azTblType = &azNew[nCol]; + pIter->aiSrcOrder = (int*)&pIter->azTblType[nCol]; + pIter->abTblPk = (u8*)&pIter->aiSrcOrder[nCol]; + pIter->abNotNull = (u8*)&pIter->abTblPk[nCol]; + pIter->abIndexed = (u8*)&pIter->abNotNull[nCol]; + } +} + +/* +** The first argument must be a nul-terminated string. This function +** returns a copy of the string in memory obtained from sqlite3_malloc(). +** It is the responsibility of the caller to eventually free this memory +** using sqlite3_free(). +** +** If an OOM condition is encountered when attempting to allocate memory, +** output variable (*pRc) is set to SQLITE_NOMEM before returning. Otherwise, +** if the allocation succeeds, (*pRc) is left unchanged. +*/ +static char *rbuStrndup(const char *zStr, int *pRc){ + char *zRet = 0; + + assert( *pRc==SQLITE_OK ); + if( zStr ){ + int nCopy = strlen(zStr) + 1; + zRet = (char*)sqlite3_malloc(nCopy); + if( zRet ){ + memcpy(zRet, zStr, nCopy); + }else{ + *pRc = SQLITE_NOMEM; + } + } + + return zRet; +} + +/* +** Finalize the statement passed as the second argument. +** +** If the sqlite3_finalize() call indicates that an error occurs, and the +** rbu handle error code is not already set, set the error code and error +** message accordingly. +*/ +static void rbuFinalize(sqlite3rbu *p, sqlite3_stmt *pStmt){ + sqlite3 *db = sqlite3_db_handle(pStmt); + int rc = sqlite3_finalize(pStmt); + if( p->rc==SQLITE_OK && rc!=SQLITE_OK ){ + p->rc = rc; + p->zErrmsg = sqlite3_mprintf("%s", sqlite3_errmsg(db)); + } +} + +/* Determine the type of a table. +** +** peType is of type (int*), a pointer to an output parameter of type +** (int). This call sets the output parameter as follows, depending +** on the type of the table specified by parameters dbName and zTbl. +** +** RBU_PK_NOTABLE: No such table. +** RBU_PK_NONE: Table has an implicit rowid. +** RBU_PK_IPK: Table has an explicit IPK column. +** RBU_PK_EXTERNAL: Table has an external PK index. +** RBU_PK_WITHOUT_ROWID: Table is WITHOUT ROWID. +** RBU_PK_VTAB: Table is a virtual table. +** +** Argument *piPk is also of type (int*), and also points to an output +** parameter. Unless the table has an external primary key index +** (i.e. unless *peType is set to 3), then *piPk is set to zero. Or, +** if the table does have an external primary key index, then *piPk +** is set to the root page number of the primary key index before +** returning. +** +** ALGORITHM: +** +** if( no entry exists in sqlite_master ){ +** return RBU_PK_NOTABLE +** }else if( sql for the entry starts with "CREATE VIRTUAL" ){ +** return RBU_PK_VTAB +** }else if( "PRAGMA index_list()" for the table contains a "pk" index ){ +** if( the index that is the pk exists in sqlite_master ){ +** *piPK = rootpage of that index. +** return RBU_PK_EXTERNAL +** }else{ +** return RBU_PK_WITHOUT_ROWID +** } +** }else if( "PRAGMA table_info()" lists one or more "pk" columns ){ +** return RBU_PK_IPK +** }else{ +** return RBU_PK_NONE +** } +*/ +static void rbuTableType( + sqlite3rbu *p, + const char *zTab, + int *peType, + int *piTnum, + int *piPk +){ + /* + ** 0) SELECT count(*) FROM sqlite_master where name=%Q AND IsVirtual(%Q) + ** 1) PRAGMA index_list = ? + ** 2) SELECT count(*) FROM sqlite_master where name=%Q + ** 3) PRAGMA table_info = ? + */ + sqlite3_stmt *aStmt[4] = {0, 0, 0, 0}; + + *peType = RBU_PK_NOTABLE; + *piPk = 0; + + assert( p->rc==SQLITE_OK ); + p->rc = prepareFreeAndCollectError(p->dbMain, &aStmt[0], &p->zErrmsg, + sqlite3_mprintf( + "SELECT (sql LIKE 'create virtual%%'), rootpage" + " FROM sqlite_master" + " WHERE name=%Q", zTab + )); + if( p->rc!=SQLITE_OK || sqlite3_step(aStmt[0])!=SQLITE_ROW ){ + /* Either an error, or no such table. */ + goto rbuTableType_end; + } + if( sqlite3_column_int(aStmt[0], 0) ){ + *peType = RBU_PK_VTAB; /* virtual table */ + goto rbuTableType_end; + } + *piTnum = sqlite3_column_int(aStmt[0], 1); + + p->rc = prepareFreeAndCollectError(p->dbMain, &aStmt[1], &p->zErrmsg, + sqlite3_mprintf("PRAGMA index_list=%Q",zTab) + ); + if( p->rc ) goto rbuTableType_end; + while( sqlite3_step(aStmt[1])==SQLITE_ROW ){ + const u8 *zOrig = sqlite3_column_text(aStmt[1], 3); + const u8 *zIdx = sqlite3_column_text(aStmt[1], 1); + if( zOrig && zIdx && zOrig[0]=='p' ){ + p->rc = prepareFreeAndCollectError(p->dbMain, &aStmt[2], &p->zErrmsg, + sqlite3_mprintf( + "SELECT rootpage FROM sqlite_master WHERE name = %Q", zIdx + )); + if( p->rc==SQLITE_OK ){ + if( sqlite3_step(aStmt[2])==SQLITE_ROW ){ + *piPk = sqlite3_column_int(aStmt[2], 0); + *peType = RBU_PK_EXTERNAL; + }else{ + *peType = RBU_PK_WITHOUT_ROWID; + } + } + goto rbuTableType_end; + } + } + + p->rc = prepareFreeAndCollectError(p->dbMain, &aStmt[3], &p->zErrmsg, + sqlite3_mprintf("PRAGMA table_info=%Q",zTab) + ); + if( p->rc==SQLITE_OK ){ + while( sqlite3_step(aStmt[3])==SQLITE_ROW ){ + if( sqlite3_column_int(aStmt[3],5)>0 ){ + *peType = RBU_PK_IPK; /* explicit IPK column */ + goto rbuTableType_end; + } + } + *peType = RBU_PK_NONE; + } + +rbuTableType_end: { + unsigned int i; + for(i=0; iabIndexed[] array. +*/ +static void rbuObjIterCacheIndexedCols(sqlite3rbu *p, RbuObjIter *pIter){ + sqlite3_stmt *pList = 0; + int bIndex = 0; + + if( p->rc==SQLITE_OK ){ + memcpy(pIter->abIndexed, pIter->abTblPk, sizeof(u8)*pIter->nTblCol); + p->rc = prepareFreeAndCollectError(p->dbMain, &pList, &p->zErrmsg, + sqlite3_mprintf("PRAGMA main.index_list = %Q", pIter->zTbl) + ); + } + + while( p->rc==SQLITE_OK && SQLITE_ROW==sqlite3_step(pList) ){ + const char *zIdx = (const char*)sqlite3_column_text(pList, 1); + sqlite3_stmt *pXInfo = 0; + if( zIdx==0 ) break; + p->rc = prepareFreeAndCollectError(p->dbMain, &pXInfo, &p->zErrmsg, + sqlite3_mprintf("PRAGMA main.index_xinfo = %Q", zIdx) + ); + while( p->rc==SQLITE_OK && SQLITE_ROW==sqlite3_step(pXInfo) ){ + int iCid = sqlite3_column_int(pXInfo, 1); + if( iCid>=0 ) pIter->abIndexed[iCid] = 1; + } + rbuFinalize(p, pXInfo); + bIndex = 1; + } + + rbuFinalize(p, pList); + if( bIndex==0 ) pIter->abIndexed = 0; +} + + +/* +** If they are not already populated, populate the pIter->azTblCol[], +** pIter->abTblPk[], pIter->nTblCol and pIter->bRowid variables according to +** the table (not index) that the iterator currently points to. +** +** Return SQLITE_OK if successful, or an SQLite error code otherwise. If +** an error does occur, an error code and error message are also left in +** the RBU handle. +*/ +static int rbuObjIterCacheTableInfo(sqlite3rbu *p, RbuObjIter *pIter){ + if( pIter->azTblCol==0 ){ + sqlite3_stmt *pStmt = 0; + int nCol = 0; + int i; /* for() loop iterator variable */ + int bRbuRowid = 0; /* If input table has column "rbu_rowid" */ + int iOrder = 0; + int iTnum = 0; + + /* Figure out the type of table this step will deal with. */ + assert( pIter->eType==0 ); + rbuTableType(p, pIter->zTbl, &pIter->eType, &iTnum, &pIter->iPkTnum); + if( p->rc==SQLITE_OK && pIter->eType==RBU_PK_NOTABLE ){ + p->rc = SQLITE_ERROR; + p->zErrmsg = sqlite3_mprintf("no such table: %s", pIter->zTbl); + } + if( p->rc ) return p->rc; + if( pIter->zIdx==0 ) pIter->iTnum = iTnum; + + assert( pIter->eType==RBU_PK_NONE || pIter->eType==RBU_PK_IPK + || pIter->eType==RBU_PK_EXTERNAL || pIter->eType==RBU_PK_WITHOUT_ROWID + || pIter->eType==RBU_PK_VTAB + ); + + /* Populate the azTblCol[] and nTblCol variables based on the columns + ** of the input table. Ignore any input table columns that begin with + ** "rbu_". */ + p->rc = prepareFreeAndCollectError(p->dbRbu, &pStmt, &p->zErrmsg, + sqlite3_mprintf("SELECT * FROM '%q'", pIter->zDataTbl) + ); + if( p->rc==SQLITE_OK ){ + nCol = sqlite3_column_count(pStmt); + rbuAllocateIterArrays(p, pIter, nCol); + } + for(i=0; p->rc==SQLITE_OK && irc); + pIter->aiSrcOrder[pIter->nTblCol] = pIter->nTblCol; + pIter->azTblCol[pIter->nTblCol++] = zCopy; + } + else if( 0==sqlite3_stricmp("rbu_rowid", zName) ){ + bRbuRowid = 1; + } + } + sqlite3_finalize(pStmt); + pStmt = 0; + + if( p->rc==SQLITE_OK + && bRbuRowid!=(pIter->eType==RBU_PK_VTAB || pIter->eType==RBU_PK_NONE) + ){ + p->rc = SQLITE_ERROR; + p->zErrmsg = sqlite3_mprintf( + "table %q %s rbu_rowid column", pIter->zDataTbl, + (bRbuRowid ? "may not have" : "requires") + ); + } + + /* Check that all non-HIDDEN columns in the destination table are also + ** present in the input table. Populate the abTblPk[], azTblType[] and + ** aiTblOrder[] arrays at the same time. */ + if( p->rc==SQLITE_OK ){ + p->rc = prepareFreeAndCollectError(p->dbMain, &pStmt, &p->zErrmsg, + sqlite3_mprintf("PRAGMA table_info(%Q)", pIter->zTbl) + ); + } + while( p->rc==SQLITE_OK && SQLITE_ROW==sqlite3_step(pStmt) ){ + const char *zName = (const char*)sqlite3_column_text(pStmt, 1); + if( zName==0 ) break; /* An OOM - finalize() below returns S_NOMEM */ + for(i=iOrder; inTblCol; i++){ + if( 0==strcmp(zName, pIter->azTblCol[i]) ) break; + } + if( i==pIter->nTblCol ){ + p->rc = SQLITE_ERROR; + p->zErrmsg = sqlite3_mprintf("column missing from %q: %s", + pIter->zDataTbl, zName + ); + }else{ + int iPk = sqlite3_column_int(pStmt, 5); + int bNotNull = sqlite3_column_int(pStmt, 3); + const char *zType = (const char*)sqlite3_column_text(pStmt, 2); + + if( i!=iOrder ){ + SWAP(int, pIter->aiSrcOrder[i], pIter->aiSrcOrder[iOrder]); + SWAP(char*, pIter->azTblCol[i], pIter->azTblCol[iOrder]); + } + + pIter->azTblType[iOrder] = rbuStrndup(zType, &p->rc); + pIter->abTblPk[iOrder] = (iPk!=0); + pIter->abNotNull[iOrder] = (u8)bNotNull || (iPk!=0); + iOrder++; + } + } + + rbuFinalize(p, pStmt); + rbuObjIterCacheIndexedCols(p, pIter); + assert( pIter->eType!=RBU_PK_VTAB || pIter->abIndexed==0 ); + } + + return p->rc; +} + +/* +** This function constructs and returns a pointer to a nul-terminated +** string containing some SQL clause or list based on one or more of the +** column names currently stored in the pIter->azTblCol[] array. +*/ +static char *rbuObjIterGetCollist( + sqlite3rbu *p, /* RBU object */ + RbuObjIter *pIter /* Object iterator for column names */ +){ + char *zList = 0; + const char *zSep = ""; + int i; + for(i=0; inTblCol; i++){ + const char *z = pIter->azTblCol[i]; + zList = rbuMPrintf(p, "%z%s\"%w\"", zList, zSep, z); + zSep = ", "; + } + return zList; +} + +/* +** This function is used to create a SELECT list (the list of SQL +** expressions that follows a SELECT keyword) for a SELECT statement +** used to read from an data_xxx or rbu_tmp_xxx table while updating the +** index object currently indicated by the iterator object passed as the +** second argument. A "PRAGMA index_xinfo = " statement is used +** to obtain the required information. +** +** If the index is of the following form: +** +** CREATE INDEX i1 ON t1(c, b COLLATE nocase); +** +** and "t1" is a table with an explicit INTEGER PRIMARY KEY column +** "ipk", the returned string is: +** +** "`c` COLLATE 'BINARY', `b` COLLATE 'NOCASE', `ipk` COLLATE 'BINARY'" +** +** As well as the returned string, three other malloc'd strings are +** returned via output parameters. As follows: +** +** pzImposterCols: ... +** pzImposterPk: ... +** pzWhere: ... +*/ +static char *rbuObjIterGetIndexCols( + sqlite3rbu *p, /* RBU object */ + RbuObjIter *pIter, /* Object iterator for column names */ + char **pzImposterCols, /* OUT: Columns for imposter table */ + char **pzImposterPk, /* OUT: Imposter PK clause */ + char **pzWhere, /* OUT: WHERE clause */ + int *pnBind /* OUT: Trbul number of columns */ +){ + int rc = p->rc; /* Error code */ + int rc2; /* sqlite3_finalize() return code */ + char *zRet = 0; /* String to return */ + char *zImpCols = 0; /* String to return via *pzImposterCols */ + char *zImpPK = 0; /* String to return via *pzImposterPK */ + char *zWhere = 0; /* String to return via *pzWhere */ + int nBind = 0; /* Value to return via *pnBind */ + const char *zCom = ""; /* Set to ", " later on */ + const char *zAnd = ""; /* Set to " AND " later on */ + sqlite3_stmt *pXInfo = 0; /* PRAGMA index_xinfo = ? */ + + if( rc==SQLITE_OK ){ + assert( p->zErrmsg==0 ); + rc = prepareFreeAndCollectError(p->dbMain, &pXInfo, &p->zErrmsg, + sqlite3_mprintf("PRAGMA main.index_xinfo = %Q", pIter->zIdx) + ); + } + + while( rc==SQLITE_OK && SQLITE_ROW==sqlite3_step(pXInfo) ){ + int iCid = sqlite3_column_int(pXInfo, 1); + int bDesc = sqlite3_column_int(pXInfo, 3); + const char *zCollate = (const char*)sqlite3_column_text(pXInfo, 4); + const char *zCol; + const char *zType; + + if( iCid<0 ){ + /* An integer primary key. If the table has an explicit IPK, use + ** its name. Otherwise, use "rbu_rowid". */ + if( pIter->eType==RBU_PK_IPK ){ + int i; + for(i=0; pIter->abTblPk[i]==0; i++); + assert( inTblCol ); + zCol = pIter->azTblCol[i]; + }else{ + zCol = "rbu_rowid"; + } + zType = "INTEGER"; + }else{ + zCol = pIter->azTblCol[iCid]; + zType = pIter->azTblType[iCid]; + } + + zRet = sqlite3_mprintf("%z%s\"%w\" COLLATE %Q", zRet, zCom, zCol, zCollate); + if( pIter->bUnique==0 || sqlite3_column_int(pXInfo, 5) ){ + const char *zOrder = (bDesc ? " DESC" : ""); + zImpPK = sqlite3_mprintf("%z%s\"rbu_imp_%d%w\"%s", + zImpPK, zCom, nBind, zCol, zOrder + ); + } + zImpCols = sqlite3_mprintf("%z%s\"rbu_imp_%d%w\" %s COLLATE %Q", + zImpCols, zCom, nBind, zCol, zType, zCollate + ); + zWhere = sqlite3_mprintf( + "%z%s\"rbu_imp_%d%w\" IS ?", zWhere, zAnd, nBind, zCol + ); + if( zRet==0 || zImpPK==0 || zImpCols==0 || zWhere==0 ) rc = SQLITE_NOMEM; + zCom = ", "; + zAnd = " AND "; + nBind++; + } + + rc2 = sqlite3_finalize(pXInfo); + if( rc==SQLITE_OK ) rc = rc2; + + if( rc!=SQLITE_OK ){ + sqlite3_free(zRet); + sqlite3_free(zImpCols); + sqlite3_free(zImpPK); + sqlite3_free(zWhere); + zRet = 0; + zImpCols = 0; + zImpPK = 0; + zWhere = 0; + p->rc = rc; + } + + *pzImposterCols = zImpCols; + *pzImposterPk = zImpPK; + *pzWhere = zWhere; + *pnBind = nBind; + return zRet; +} + +/* +** Assuming the current table columns are "a", "b" and "c", and the zObj +** paramter is passed "old", return a string of the form: +** +** "old.a, old.b, old.b" +** +** With the column names escaped. +** +** For tables with implicit rowids - RBU_PK_EXTERNAL and RBU_PK_NONE, append +** the text ", old._rowid_" to the returned value. +*/ +static char *rbuObjIterGetOldlist( + sqlite3rbu *p, + RbuObjIter *pIter, + const char *zObj +){ + char *zList = 0; + if( p->rc==SQLITE_OK && pIter->abIndexed ){ + const char *zS = ""; + int i; + for(i=0; inTblCol; i++){ + if( pIter->abIndexed[i] ){ + const char *zCol = pIter->azTblCol[i]; + zList = sqlite3_mprintf("%z%s%s.\"%w\"", zList, zS, zObj, zCol); + }else{ + zList = sqlite3_mprintf("%z%sNULL", zList, zS); + } + zS = ", "; + if( zList==0 ){ + p->rc = SQLITE_NOMEM; + break; + } + } + + /* For a table with implicit rowids, append "old._rowid_" to the list. */ + if( pIter->eType==RBU_PK_EXTERNAL || pIter->eType==RBU_PK_NONE ){ + zList = rbuMPrintf(p, "%z, %s._rowid_", zList, zObj); + } + } + return zList; +} + +/* +** Return an expression that can be used in a WHERE clause to match the +** primary key of the current table. For example, if the table is: +** +** CREATE TABLE t1(a, b, c, PRIMARY KEY(b, c)); +** +** Return the string: +** +** "b = ?1 AND c = ?2" +*/ +static char *rbuObjIterGetWhere( + sqlite3rbu *p, + RbuObjIter *pIter +){ + char *zList = 0; + if( pIter->eType==RBU_PK_VTAB || pIter->eType==RBU_PK_NONE ){ + zList = rbuMPrintf(p, "_rowid_ = ?%d", pIter->nTblCol+1); + }else if( pIter->eType==RBU_PK_EXTERNAL ){ + const char *zSep = ""; + int i; + for(i=0; inTblCol; i++){ + if( pIter->abTblPk[i] ){ + zList = rbuMPrintf(p, "%z%sc%d=?%d", zList, zSep, i, i+1); + zSep = " AND "; + } + } + zList = rbuMPrintf(p, + "_rowid_ = (SELECT id FROM rbu_imposter2 WHERE %z)", zList + ); + + }else{ + const char *zSep = ""; + int i; + for(i=0; inTblCol; i++){ + if( pIter->abTblPk[i] ){ + const char *zCol = pIter->azTblCol[i]; + zList = rbuMPrintf(p, "%z%s\"%w\"=?%d", zList, zSep, zCol, i+1); + zSep = " AND "; + } + } + } + return zList; +} + +/* +** The SELECT statement iterating through the keys for the current object +** (p->objiter.pSelect) currently points to a valid row. However, there +** is something wrong with the rbu_control value in the rbu_control value +** stored in the (p->nCol+1)'th column. Set the error code and error message +** of the RBU handle to something reflecting this. +*/ +static void rbuBadControlError(sqlite3rbu *p){ + p->rc = SQLITE_ERROR; + p->zErrmsg = sqlite3_mprintf("invalid rbu_control value"); +} + + +/* +** Return a nul-terminated string containing the comma separated list of +** assignments that should be included following the "SET" keyword of +** an UPDATE statement used to update the table object that the iterator +** passed as the second argument currently points to if the rbu_control +** column of the data_xxx table entry is set to zMask. +** +** The memory for the returned string is obtained from sqlite3_malloc(). +** It is the responsibility of the caller to eventually free it using +** sqlite3_free(). +** +** If an OOM error is encountered when allocating space for the new +** string, an error code is left in the rbu handle passed as the first +** argument and NULL is returned. Or, if an error has already occurred +** when this function is called, NULL is returned immediately, without +** attempting the allocation or modifying the stored error code. +*/ +static char *rbuObjIterGetSetlist( + sqlite3rbu *p, + RbuObjIter *pIter, + const char *zMask +){ + char *zList = 0; + if( p->rc==SQLITE_OK ){ + int i; + + if( (int)strlen(zMask)!=pIter->nTblCol ){ + rbuBadControlError(p); + }else{ + const char *zSep = ""; + for(i=0; inTblCol; i++){ + char c = zMask[pIter->aiSrcOrder[i]]; + if( c=='x' ){ + zList = rbuMPrintf(p, "%z%s\"%w\"=?%d", + zList, zSep, pIter->azTblCol[i], i+1 + ); + zSep = ", "; + } + else if( c=='d' ){ + zList = rbuMPrintf(p, "%z%s\"%w\"=rbu_delta(\"%w\", ?%d)", + zList, zSep, pIter->azTblCol[i], pIter->azTblCol[i], i+1 + ); + zSep = ", "; + } + else if( c=='f' ){ + zList = rbuMPrintf(p, "%z%s\"%w\"=rbu_fossil_delta(\"%w\", ?%d)", + zList, zSep, pIter->azTblCol[i], pIter->azTblCol[i], i+1 + ); + zSep = ", "; + } + } + } + } + return zList; +} + +/* +** Return a nul-terminated string consisting of nByte comma separated +** "?" expressions. For example, if nByte is 3, return a pointer to +** a buffer containing the string "?,?,?". +** +** The memory for the returned string is obtained from sqlite3_malloc(). +** It is the responsibility of the caller to eventually free it using +** sqlite3_free(). +** +** If an OOM error is encountered when allocating space for the new +** string, an error code is left in the rbu handle passed as the first +** argument and NULL is returned. Or, if an error has already occurred +** when this function is called, NULL is returned immediately, without +** attempting the allocation or modifying the stored error code. +*/ +static char *rbuObjIterGetBindlist(sqlite3rbu *p, int nBind){ + char *zRet = 0; + int nByte = nBind*2 + 1; + + zRet = (char*)rbuMalloc(p, nByte); + if( zRet ){ + int i; + for(i=0; izIdx==0 ); + if( p->rc==SQLITE_OK ){ + const char *zSep = "PRIMARY KEY("; + sqlite3_stmt *pXList = 0; /* PRAGMA index_list = (pIter->zTbl) */ + sqlite3_stmt *pXInfo = 0; /* PRAGMA index_xinfo = */ + + p->rc = prepareFreeAndCollectError(p->dbMain, &pXList, &p->zErrmsg, + sqlite3_mprintf("PRAGMA main.index_list = %Q", pIter->zTbl) + ); + while( p->rc==SQLITE_OK && SQLITE_ROW==sqlite3_step(pXList) ){ + const char *zOrig = (const char*)sqlite3_column_text(pXList,3); + if( zOrig && strcmp(zOrig, "pk")==0 ){ + const char *zIdx = (const char*)sqlite3_column_text(pXList,1); + if( zIdx ){ + p->rc = prepareFreeAndCollectError(p->dbMain, &pXInfo, &p->zErrmsg, + sqlite3_mprintf("PRAGMA main.index_xinfo = %Q", zIdx) + ); + } + break; + } + } + rbuFinalize(p, pXList); + + while( p->rc==SQLITE_OK && SQLITE_ROW==sqlite3_step(pXInfo) ){ + if( sqlite3_column_int(pXInfo, 5) ){ + /* int iCid = sqlite3_column_int(pXInfo, 0); */ + const char *zCol = (const char*)sqlite3_column_text(pXInfo, 2); + const char *zDesc = sqlite3_column_int(pXInfo, 3) ? " DESC" : ""; + z = rbuMPrintf(p, "%z%s\"%w\"%s", z, zSep, zCol, zDesc); + zSep = ", "; + } + } + z = rbuMPrintf(p, "%z)", z); + rbuFinalize(p, pXInfo); + } + return z; +} + +/* +** This function creates the second imposter table used when writing to +** a table b-tree where the table has an external primary key. If the +** iterator passed as the second argument does not currently point to +** a table (not index) with an external primary key, this function is a +** no-op. +** +** Assuming the iterator does point to a table with an external PK, this +** function creates a WITHOUT ROWID imposter table named "rbu_imposter2" +** used to access that PK index. For example, if the target table is +** declared as follows: +** +** CREATE TABLE t1(a, b TEXT, c REAL, PRIMARY KEY(b, c)); +** +** then the imposter table schema is: +** +** CREATE TABLE rbu_imposter2(c1 TEXT, c2 REAL, id INTEGER) WITHOUT ROWID; +** +*/ +static void rbuCreateImposterTable2(sqlite3rbu *p, RbuObjIter *pIter){ + if( p->rc==SQLITE_OK && pIter->eType==RBU_PK_EXTERNAL ){ + int tnum = pIter->iPkTnum; /* Root page of PK index */ + sqlite3_stmt *pQuery = 0; /* SELECT name ... WHERE rootpage = $tnum */ + const char *zIdx = 0; /* Name of PK index */ + sqlite3_stmt *pXInfo = 0; /* PRAGMA main.index_xinfo = $zIdx */ + const char *zComma = ""; + char *zCols = 0; /* Used to build up list of table cols */ + char *zPk = 0; /* Used to build up table PK declaration */ + + /* Figure out the name of the primary key index for the current table. + ** This is needed for the argument to "PRAGMA index_xinfo". Set + ** zIdx to point to a nul-terminated string containing this name. */ + p->rc = prepareAndCollectError(p->dbMain, &pQuery, &p->zErrmsg, + "SELECT name FROM sqlite_master WHERE rootpage = ?" + ); + if( p->rc==SQLITE_OK ){ + sqlite3_bind_int(pQuery, 1, tnum); + if( SQLITE_ROW==sqlite3_step(pQuery) ){ + zIdx = (const char*)sqlite3_column_text(pQuery, 0); + } + } + if( zIdx ){ + p->rc = prepareFreeAndCollectError(p->dbMain, &pXInfo, &p->zErrmsg, + sqlite3_mprintf("PRAGMA main.index_xinfo = %Q", zIdx) + ); + } + rbuFinalize(p, pQuery); + + while( p->rc==SQLITE_OK && SQLITE_ROW==sqlite3_step(pXInfo) ){ + int bKey = sqlite3_column_int(pXInfo, 5); + if( bKey ){ + int iCid = sqlite3_column_int(pXInfo, 1); + int bDesc = sqlite3_column_int(pXInfo, 3); + const char *zCollate = (const char*)sqlite3_column_text(pXInfo, 4); + zCols = rbuMPrintf(p, "%z%sc%d %s COLLATE %s", zCols, zComma, + iCid, pIter->azTblType[iCid], zCollate + ); + zPk = rbuMPrintf(p, "%z%sc%d%s", zPk, zComma, iCid, bDesc?" DESC":""); + zComma = ", "; + } + } + zCols = rbuMPrintf(p, "%z, id INTEGER", zCols); + rbuFinalize(p, pXInfo); + + sqlite3_test_control(SQLITE_TESTCTRL_IMPOSTER, p->dbMain, "main", 1, tnum); + rbuMPrintfExec(p, p->dbMain, + "CREATE TABLE rbu_imposter2(%z, PRIMARY KEY(%z)) WITHOUT ROWID", + zCols, zPk + ); + sqlite3_test_control(SQLITE_TESTCTRL_IMPOSTER, p->dbMain, "main", 0, 0); + } +} + +/* +** If an error has already occurred when this function is called, it +** immediately returns zero (without doing any work). Or, if an error +** occurs during the execution of this function, it sets the error code +** in the sqlite3rbu object indicated by the first argument and returns +** zero. +** +** The iterator passed as the second argument is guaranteed to point to +** a table (not an index) when this function is called. This function +** attempts to create any imposter table required to write to the main +** table b-tree of the table before returning. Non-zero is returned if +** an imposter table are created, or zero otherwise. +** +** An imposter table is required in all cases except RBU_PK_VTAB. Only +** virtual tables are written to directly. The imposter table has the +** same schema as the actual target table (less any UNIQUE constraints). +** More precisely, the "same schema" means the same columns, types, +** collation sequences. For tables that do not have an external PRIMARY +** KEY, it also means the same PRIMARY KEY declaration. +*/ +static void rbuCreateImposterTable(sqlite3rbu *p, RbuObjIter *pIter){ + if( p->rc==SQLITE_OK && pIter->eType!=RBU_PK_VTAB ){ + int tnum = pIter->iTnum; + const char *zComma = ""; + char *zSql = 0; + int iCol; + sqlite3_test_control(SQLITE_TESTCTRL_IMPOSTER, p->dbMain, "main", 0, 1); + + for(iCol=0; p->rc==SQLITE_OK && iColnTblCol; iCol++){ + const char *zPk = ""; + const char *zCol = pIter->azTblCol[iCol]; + const char *zColl = 0; + + p->rc = sqlite3_table_column_metadata( + p->dbMain, "main", pIter->zTbl, zCol, 0, &zColl, 0, 0, 0 + ); + + if( pIter->eType==RBU_PK_IPK && pIter->abTblPk[iCol] ){ + /* If the target table column is an "INTEGER PRIMARY KEY", add + ** "PRIMARY KEY" to the imposter table column declaration. */ + zPk = "PRIMARY KEY "; + } + zSql = rbuMPrintf(p, "%z%s\"%w\" %s %sCOLLATE %s%s", + zSql, zComma, zCol, pIter->azTblType[iCol], zPk, zColl, + (pIter->abNotNull[iCol] ? " NOT NULL" : "") + ); + zComma = ", "; + } + + if( pIter->eType==RBU_PK_WITHOUT_ROWID ){ + char *zPk = rbuWithoutRowidPK(p, pIter); + if( zPk ){ + zSql = rbuMPrintf(p, "%z, %z", zSql, zPk); + } + } + + sqlite3_test_control(SQLITE_TESTCTRL_IMPOSTER, p->dbMain, "main", 1, tnum); + rbuMPrintfExec(p, p->dbMain, "CREATE TABLE \"rbu_imp_%w\"(%z)%s", + pIter->zTbl, zSql, + (pIter->eType==RBU_PK_WITHOUT_ROWID ? " WITHOUT ROWID" : "") + ); + sqlite3_test_control(SQLITE_TESTCTRL_IMPOSTER, p->dbMain, "main", 0, 0); + } +} + +/* +** Prepare a statement used to insert rows into the "rbu_tmp_xxx" table. +** Specifically a statement of the form: +** +** INSERT INTO rbu_tmp_xxx VALUES(?, ?, ? ...); +** +** The number of bound variables is equal to the number of columns in +** the target table, plus one (for the rbu_control column), plus one more +** (for the rbu_rowid column) if the target table is an implicit IPK or +** virtual table. +*/ +static void rbuObjIterPrepareTmpInsert( + sqlite3rbu *p, + RbuObjIter *pIter, + const char *zCollist, + const char *zRbuRowid +){ + int bRbuRowid = (pIter->eType==RBU_PK_EXTERNAL || pIter->eType==RBU_PK_NONE); + char *zBind = rbuObjIterGetBindlist(p, pIter->nTblCol + 1 + bRbuRowid); + if( zBind ){ + assert( pIter->pTmpInsert==0 ); + p->rc = prepareFreeAndCollectError( + p->dbRbu, &pIter->pTmpInsert, &p->zErrmsg, sqlite3_mprintf( + "INSERT INTO %s.'rbu_tmp_%q'(rbu_control,%s%s) VALUES(%z)", + p->zStateDb, pIter->zDataTbl, zCollist, zRbuRowid, zBind + )); + } +} + +static void rbuTmpInsertFunc( + sqlite3_context *pCtx, + int nVal, + sqlite3_value **apVal +){ + sqlite3rbu *p = sqlite3_user_data(pCtx); + int rc = SQLITE_OK; + int i; + + for(i=0; rc==SQLITE_OK && iobjiter.pTmpInsert, i+1, apVal[i]); + } + if( rc==SQLITE_OK ){ + sqlite3_step(p->objiter.pTmpInsert); + rc = sqlite3_reset(p->objiter.pTmpInsert); + } + + if( rc!=SQLITE_OK ){ + sqlite3_result_error_code(pCtx, rc); + } +} + +/* +** Ensure that the SQLite statement handles required to update the +** target database object currently indicated by the iterator passed +** as the second argument are available. +*/ +static int rbuObjIterPrepareAll( + sqlite3rbu *p, + RbuObjIter *pIter, + int nOffset /* Add "LIMIT -1 OFFSET $nOffset" to SELECT */ +){ + assert( pIter->bCleanup==0 ); + if( pIter->pSelect==0 && rbuObjIterCacheTableInfo(p, pIter)==SQLITE_OK ){ + const int tnum = pIter->iTnum; + char *zCollist = 0; /* List of indexed columns */ + char **pz = &p->zErrmsg; + const char *zIdx = pIter->zIdx; + char *zLimit = 0; + + if( nOffset ){ + zLimit = sqlite3_mprintf(" LIMIT -1 OFFSET %d", nOffset); + if( !zLimit ) p->rc = SQLITE_NOMEM; + } + + if( zIdx ){ + const char *zTbl = pIter->zTbl; + char *zImposterCols = 0; /* Columns for imposter table */ + char *zImposterPK = 0; /* Primary key declaration for imposter */ + char *zWhere = 0; /* WHERE clause on PK columns */ + char *zBind = 0; + int nBind = 0; + + assert( pIter->eType!=RBU_PK_VTAB ); + zCollist = rbuObjIterGetIndexCols( + p, pIter, &zImposterCols, &zImposterPK, &zWhere, &nBind + ); + zBind = rbuObjIterGetBindlist(p, nBind); + + /* Create the imposter table used to write to this index. */ + sqlite3_test_control(SQLITE_TESTCTRL_IMPOSTER, p->dbMain, "main", 0, 1); + sqlite3_test_control(SQLITE_TESTCTRL_IMPOSTER, p->dbMain, "main", 1,tnum); + rbuMPrintfExec(p, p->dbMain, + "CREATE TABLE \"rbu_imp_%w\"( %s, PRIMARY KEY( %s ) ) WITHOUT ROWID", + zTbl, zImposterCols, zImposterPK + ); + sqlite3_test_control(SQLITE_TESTCTRL_IMPOSTER, p->dbMain, "main", 0, 0); + + /* Create the statement to insert index entries */ + pIter->nCol = nBind; + if( p->rc==SQLITE_OK ){ + p->rc = prepareFreeAndCollectError( + p->dbMain, &pIter->pInsert, &p->zErrmsg, + sqlite3_mprintf("INSERT INTO \"rbu_imp_%w\" VALUES(%s)", zTbl, zBind) + ); + } + + /* And to delete index entries */ + if( p->rc==SQLITE_OK ){ + p->rc = prepareFreeAndCollectError( + p->dbMain, &pIter->pDelete, &p->zErrmsg, + sqlite3_mprintf("DELETE FROM \"rbu_imp_%w\" WHERE %s", zTbl, zWhere) + ); + } + + /* Create the SELECT statement to read keys in sorted order */ + if( p->rc==SQLITE_OK ){ + char *zSql; + if( pIter->eType==RBU_PK_EXTERNAL || pIter->eType==RBU_PK_NONE ){ + zSql = sqlite3_mprintf( + "SELECT %s, rbu_control FROM %s.'rbu_tmp_%q' ORDER BY %s%s", + zCollist, p->zStateDb, pIter->zDataTbl, + zCollist, zLimit + ); + }else{ + zSql = sqlite3_mprintf( + "SELECT %s, rbu_control FROM '%q' " + "WHERE typeof(rbu_control)='integer' AND rbu_control!=1 " + "UNION ALL " + "SELECT %s, rbu_control FROM %s.'rbu_tmp_%q' " + "ORDER BY %s%s", + zCollist, pIter->zDataTbl, + zCollist, p->zStateDb, pIter->zDataTbl, + zCollist, zLimit + ); + } + p->rc = prepareFreeAndCollectError(p->dbRbu, &pIter->pSelect, pz, zSql); + } + + sqlite3_free(zImposterCols); + sqlite3_free(zImposterPK); + sqlite3_free(zWhere); + sqlite3_free(zBind); + }else{ + int bRbuRowid = (pIter->eType==RBU_PK_VTAB || pIter->eType==RBU_PK_NONE); + const char *zTbl = pIter->zTbl; /* Table this step applies to */ + const char *zWrite; /* Imposter table name */ + + char *zBindings = rbuObjIterGetBindlist(p, pIter->nTblCol + bRbuRowid); + char *zWhere = rbuObjIterGetWhere(p, pIter); + char *zOldlist = rbuObjIterGetOldlist(p, pIter, "old"); + char *zNewlist = rbuObjIterGetOldlist(p, pIter, "new"); + + zCollist = rbuObjIterGetCollist(p, pIter); + pIter->nCol = pIter->nTblCol; + + /* Create the imposter table or tables (if required). */ + rbuCreateImposterTable(p, pIter); + rbuCreateImposterTable2(p, pIter); + zWrite = (pIter->eType==RBU_PK_VTAB ? "" : "rbu_imp_"); + + /* Create the INSERT statement to write to the target PK b-tree */ + if( p->rc==SQLITE_OK ){ + p->rc = prepareFreeAndCollectError(p->dbMain, &pIter->pInsert, pz, + sqlite3_mprintf( + "INSERT INTO \"%s%w\"(%s%s) VALUES(%s)", + zWrite, zTbl, zCollist, (bRbuRowid ? ", _rowid_" : ""), zBindings + ) + ); + } + + /* Create the DELETE statement to write to the target PK b-tree */ + if( p->rc==SQLITE_OK ){ + p->rc = prepareFreeAndCollectError(p->dbMain, &pIter->pDelete, pz, + sqlite3_mprintf( + "DELETE FROM \"%s%w\" WHERE %s", zWrite, zTbl, zWhere + ) + ); + } + + if( pIter->abIndexed ){ + const char *zRbuRowid = ""; + if( pIter->eType==RBU_PK_EXTERNAL || pIter->eType==RBU_PK_NONE ){ + zRbuRowid = ", rbu_rowid"; + } + + /* Create the rbu_tmp_xxx table and the triggers to populate it. */ + rbuMPrintfExec(p, p->dbRbu, + "CREATE TABLE IF NOT EXISTS %s.'rbu_tmp_%q' AS " + "SELECT *%s FROM '%q' WHERE 0;" + , p->zStateDb, pIter->zDataTbl + , (pIter->eType==RBU_PK_EXTERNAL ? ", 0 AS rbu_rowid" : "") + , pIter->zDataTbl + ); + + rbuMPrintfExec(p, p->dbMain, + "CREATE TEMP TRIGGER rbu_delete_tr BEFORE DELETE ON \"%s%w\" " + "BEGIN " + " SELECT rbu_tmp_insert(2, %s);" + "END;" + + "CREATE TEMP TRIGGER rbu_update1_tr BEFORE UPDATE ON \"%s%w\" " + "BEGIN " + " SELECT rbu_tmp_insert(2, %s);" + "END;" + + "CREATE TEMP TRIGGER rbu_update2_tr AFTER UPDATE ON \"%s%w\" " + "BEGIN " + " SELECT rbu_tmp_insert(3, %s);" + "END;", + zWrite, zTbl, zOldlist, + zWrite, zTbl, zOldlist, + zWrite, zTbl, zNewlist + ); + + if( pIter->eType==RBU_PK_EXTERNAL || pIter->eType==RBU_PK_NONE ){ + rbuMPrintfExec(p, p->dbMain, + "CREATE TEMP TRIGGER rbu_insert_tr AFTER INSERT ON \"%s%w\" " + "BEGIN " + " SELECT rbu_tmp_insert(0, %s);" + "END;", + zWrite, zTbl, zNewlist + ); + } + + rbuObjIterPrepareTmpInsert(p, pIter, zCollist, zRbuRowid); + } + + /* Create the SELECT statement to read keys from data_xxx */ + if( p->rc==SQLITE_OK ){ + p->rc = prepareFreeAndCollectError(p->dbRbu, &pIter->pSelect, pz, + sqlite3_mprintf( + "SELECT %s, rbu_control%s FROM '%q'%s", + zCollist, (bRbuRowid ? ", rbu_rowid" : ""), + pIter->zDataTbl, zLimit + ) + ); + } + + sqlite3_free(zWhere); + sqlite3_free(zOldlist); + sqlite3_free(zNewlist); + sqlite3_free(zBindings); + } + sqlite3_free(zCollist); + sqlite3_free(zLimit); + } + + return p->rc; +} + +/* +** Set output variable *ppStmt to point to an UPDATE statement that may +** be used to update the imposter table for the main table b-tree of the +** table object that pIter currently points to, assuming that the +** rbu_control column of the data_xyz table contains zMask. +** +** If the zMask string does not specify any columns to update, then this +** is not an error. Output variable *ppStmt is set to NULL in this case. +*/ +static int rbuGetUpdateStmt( + sqlite3rbu *p, /* RBU handle */ + RbuObjIter *pIter, /* Object iterator */ + const char *zMask, /* rbu_control value ('x.x.') */ + sqlite3_stmt **ppStmt /* OUT: UPDATE statement handle */ +){ + RbuUpdateStmt **pp; + RbuUpdateStmt *pUp = 0; + int nUp = 0; + + /* In case an error occurs */ + *ppStmt = 0; + + /* Search for an existing statement. If one is found, shift it to the front + ** of the LRU queue and return immediately. Otherwise, leave nUp pointing + ** to the number of statements currently in the cache and pUp to the + ** last object in the list. */ + for(pp=&pIter->pRbuUpdate; *pp; pp=&((*pp)->pNext)){ + pUp = *pp; + if( strcmp(pUp->zMask, zMask)==0 ){ + *pp = pUp->pNext; + pUp->pNext = pIter->pRbuUpdate; + pIter->pRbuUpdate = pUp; + *ppStmt = pUp->pUpdate; + return SQLITE_OK; + } + nUp++; + } + assert( pUp==0 || pUp->pNext==0 ); + + if( nUp>=SQLITE_RBU_UPDATE_CACHESIZE ){ + for(pp=&pIter->pRbuUpdate; *pp!=pUp; pp=&((*pp)->pNext)); + *pp = 0; + sqlite3_finalize(pUp->pUpdate); + pUp->pUpdate = 0; + }else{ + pUp = (RbuUpdateStmt*)rbuMalloc(p, sizeof(RbuUpdateStmt)+pIter->nTblCol+1); + } + + if( pUp ){ + char *zWhere = rbuObjIterGetWhere(p, pIter); + char *zSet = rbuObjIterGetSetlist(p, pIter, zMask); + char *zUpdate = 0; + + pUp->zMask = (char*)&pUp[1]; + memcpy(pUp->zMask, zMask, pIter->nTblCol); + pUp->pNext = pIter->pRbuUpdate; + pIter->pRbuUpdate = pUp; + + if( zSet ){ + const char *zPrefix = ""; + + if( pIter->eType!=RBU_PK_VTAB ) zPrefix = "rbu_imp_"; + zUpdate = sqlite3_mprintf("UPDATE \"%s%w\" SET %s WHERE %s", + zPrefix, pIter->zTbl, zSet, zWhere + ); + p->rc = prepareFreeAndCollectError( + p->dbMain, &pUp->pUpdate, &p->zErrmsg, zUpdate + ); + *ppStmt = pUp->pUpdate; + } + sqlite3_free(zWhere); + sqlite3_free(zSet); + } + + return p->rc; +} + +static sqlite3 *rbuOpenDbhandle(sqlite3rbu *p, const char *zName){ + sqlite3 *db = 0; + if( p->rc==SQLITE_OK ){ + const int flags = SQLITE_OPEN_READWRITE|SQLITE_OPEN_CREATE|SQLITE_OPEN_URI; + p->rc = sqlite3_open_v2(zName, &db, flags, p->zVfsName); + if( p->rc ){ + p->zErrmsg = sqlite3_mprintf("%s", sqlite3_errmsg(db)); + sqlite3_close(db); + db = 0; + } + } + return db; +} + +/* +** Open the database handle and attach the RBU database as "rbu". If an +** error occurs, leave an error code and message in the RBU handle. +*/ +static void rbuOpenDatabase(sqlite3rbu *p){ + assert( p->rc==SQLITE_OK ); + assert( p->dbMain==0 && p->dbRbu==0 ); + + p->eStage = 0; + p->dbMain = rbuOpenDbhandle(p, p->zTarget); + p->dbRbu = rbuOpenDbhandle(p, p->zRbu); + + /* If using separate RBU and state databases, attach the state database to + ** the RBU db handle now. */ + if( p->zState ){ + rbuMPrintfExec(p, p->dbRbu, "ATTACH %Q AS stat", p->zState); + memcpy(p->zStateDb, "stat", 4); + }else{ + memcpy(p->zStateDb, "main", 4); + } + + if( p->rc==SQLITE_OK ){ + p->rc = sqlite3_create_function(p->dbMain, + "rbu_tmp_insert", -1, SQLITE_UTF8, (void*)p, rbuTmpInsertFunc, 0, 0 + ); + } + + if( p->rc==SQLITE_OK ){ + p->rc = sqlite3_create_function(p->dbMain, + "rbu_fossil_delta", 2, SQLITE_UTF8, 0, rbuFossilDeltaFunc, 0, 0 + ); + } + + if( p->rc==SQLITE_OK ){ + p->rc = sqlite3_create_function(p->dbRbu, + "rbu_target_name", 1, SQLITE_UTF8, (void*)p, rbuTargetNameFunc, 0, 0 + ); + } + + if( p->rc==SQLITE_OK ){ + p->rc = sqlite3_file_control(p->dbMain, "main", SQLITE_FCNTL_RBU, (void*)p); + } + rbuMPrintfExec(p, p->dbMain, "SELECT * FROM sqlite_master"); + + /* Mark the database file just opened as an RBU target database. If + ** this call returns SQLITE_NOTFOUND, then the RBU vfs is not in use. + ** This is an error. */ + if( p->rc==SQLITE_OK ){ + p->rc = sqlite3_file_control(p->dbMain, "main", SQLITE_FCNTL_RBU, (void*)p); + } + + if( p->rc==SQLITE_NOTFOUND ){ + p->rc = SQLITE_ERROR; + p->zErrmsg = sqlite3_mprintf("rbu vfs not found"); + } +} + +/* +** This routine is a copy of the sqlite3FileSuffix3() routine from the core. +** It is a no-op unless SQLITE_ENABLE_8_3_NAMES is defined. +** +** If SQLITE_ENABLE_8_3_NAMES is set at compile-time and if the database +** filename in zBaseFilename is a URI with the "8_3_names=1" parameter and +** if filename in z[] has a suffix (a.k.a. "extension") that is longer than +** three characters, then shorten the suffix on z[] to be the last three +** characters of the original suffix. +** +** If SQLITE_ENABLE_8_3_NAMES is set to 2 at compile-time, then always +** do the suffix shortening regardless of URI parameter. +** +** Examples: +** +** test.db-journal => test.nal +** test.db-wal => test.wal +** test.db-shm => test.shm +** test.db-mj7f3319fa => test.9fa +*/ +static void rbuFileSuffix3(const char *zBase, char *z){ +#ifdef SQLITE_ENABLE_8_3_NAMES +#if SQLITE_ENABLE_8_3_NAMES<2 + if( sqlite3_uri_boolean(zBase, "8_3_names", 0) ) +#endif + { + int i, sz; + sz = sqlite3Strlen30(z); + for(i=sz-1; i>0 && z[i]!='/' && z[i]!='.'; i--){} + if( z[i]=='.' && ALWAYS(sz>i+4) ) memmove(&z[i+1], &z[sz-3], 4); + } +#endif +} + +/* +** Return the current wal-index header checksum for the target database +** as a 64-bit integer. +** +** The checksum is store in the first page of xShmMap memory as an 8-byte +** blob starting at byte offset 40. +*/ +static i64 rbuShmChecksum(sqlite3rbu *p){ + i64 iRet = 0; + if( p->rc==SQLITE_OK ){ + sqlite3_file *pDb = p->pTargetFd->pReal; + u32 volatile *ptr; + p->rc = pDb->pMethods->xShmMap(pDb, 0, 32*1024, 0, (void volatile**)&ptr); + if( p->rc==SQLITE_OK ){ + iRet = ((i64)ptr[10] << 32) + ptr[11]; + } + } + return iRet; +} + +/* +** This function is called as part of initializing or reinitializing an +** incremental checkpoint. +** +** It populates the sqlite3rbu.aFrame[] array with the set of +** (wal frame -> db page) copy operations required to checkpoint the +** current wal file, and obtains the set of shm locks required to safely +** perform the copy operations directly on the file-system. +** +** If argument pState is not NULL, then the incremental checkpoint is +** being resumed. In this case, if the checksum of the wal-index-header +** following recovery is not the same as the checksum saved in the RbuState +** object, then the rbu handle is set to DONE state. This occurs if some +** other client appends a transaction to the wal file in the middle of +** an incremental checkpoint. +*/ +static void rbuSetupCheckpoint(sqlite3rbu *p, RbuState *pState){ + + /* If pState is NULL, then the wal file may not have been opened and + ** recovered. Running a read-statement here to ensure that doing so + ** does not interfere with the "capture" process below. */ + if( pState==0 ){ + p->eStage = 0; + if( p->rc==SQLITE_OK ){ + p->rc = sqlite3_exec(p->dbMain, "SELECT * FROM sqlite_master", 0, 0, 0); + } + } + + /* Assuming no error has occurred, run a "restart" checkpoint with the + ** sqlite3rbu.eStage variable set to CAPTURE. This turns on the following + ** special behaviour in the rbu VFS: + ** + ** * If the exclusive shm WRITER or READ0 lock cannot be obtained, + ** the checkpoint fails with SQLITE_BUSY (normally SQLite would + ** proceed with running a passive checkpoint instead of failing). + ** + ** * Attempts to read from the *-wal file or write to the database file + ** do not perform any IO. Instead, the frame/page combinations that + ** would be read/written are recorded in the sqlite3rbu.aFrame[] + ** array. + ** + ** * Calls to xShmLock(UNLOCK) to release the exclusive shm WRITER, + ** READ0 and CHECKPOINT locks taken as part of the checkpoint are + ** no-ops. These locks will not be released until the connection + ** is closed. + ** + ** * Attempting to xSync() the database file causes an SQLITE_INTERNAL + ** error. + ** + ** As a result, unless an error (i.e. OOM or SQLITE_BUSY) occurs, the + ** checkpoint below fails with SQLITE_INTERNAL, and leaves the aFrame[] + ** array populated with a set of (frame -> page) mappings. Because the + ** WRITER, CHECKPOINT and READ0 locks are still held, it is safe to copy + ** data from the wal file into the database file according to the + ** contents of aFrame[]. + */ + if( p->rc==SQLITE_OK ){ + int rc2; + p->eStage = RBU_STAGE_CAPTURE; + rc2 = sqlite3_exec(p->dbMain, "PRAGMA main.wal_checkpoint=restart", 0, 0,0); + if( rc2!=SQLITE_INTERNAL ) p->rc = rc2; + } + + if( p->rc==SQLITE_OK ){ + p->eStage = RBU_STAGE_CKPT; + p->nStep = (pState ? pState->nRow : 0); + p->aBuf = rbuMalloc(p, p->pgsz); + p->iWalCksum = rbuShmChecksum(p); + } + + if( p->rc==SQLITE_OK && pState && pState->iWalCksum!=p->iWalCksum ){ + p->rc = SQLITE_DONE; + p->eStage = RBU_STAGE_DONE; + } +} + +/* +** Called when iAmt bytes are read from offset iOff of the wal file while +** the rbu object is in capture mode. Record the frame number of the frame +** being read in the aFrame[] array. +*/ +static int rbuCaptureWalRead(sqlite3rbu *pRbu, i64 iOff, int iAmt){ + const u32 mReq = (1<mLock!=mReq ){ + pRbu->rc = SQLITE_BUSY; + return SQLITE_INTERNAL; + } + + pRbu->pgsz = iAmt; + if( pRbu->nFrame==pRbu->nFrameAlloc ){ + int nNew = (pRbu->nFrameAlloc ? pRbu->nFrameAlloc : 64) * 2; + RbuFrame *aNew; + aNew = (RbuFrame*)sqlite3_realloc(pRbu->aFrame, nNew * sizeof(RbuFrame)); + if( aNew==0 ) return SQLITE_NOMEM; + pRbu->aFrame = aNew; + pRbu->nFrameAlloc = nNew; + } + + iFrame = (u32)((iOff-32) / (i64)(iAmt+24)) + 1; + if( pRbu->iMaxFrame