summaryrefslogtreecommitdiffstats
path: root/o3d/command_buffer
diff options
context:
space:
mode:
Diffstat (limited to 'o3d/command_buffer')
-rw-r--r--o3d/command_buffer/client/build.scons70
-rw-r--r--o3d/command_buffer/client/cross/big_test_client.cc407
-rw-r--r--o3d/command_buffer/client/cross/buffer_sync_proxy.cc128
-rw-r--r--o3d/command_buffer/client/cross/buffer_sync_proxy.h102
-rw-r--r--o3d/command_buffer/client/cross/buffer_sync_proxy_test.cc260
-rw-r--r--o3d/command_buffer/client/cross/cmd_buffer_helper.cc185
-rw-r--r--o3d/command_buffer/client/cross/cmd_buffer_helper.h158
-rw-r--r--o3d/command_buffer/client/cross/cmd_buffer_helper_test.cc276
-rw-r--r--o3d/command_buffer/client/cross/effect_helper.cc211
-rw-r--r--o3d/command_buffer/client/cross/effect_helper.h134
-rw-r--r--o3d/command_buffer/client/cross/fenced_allocator.cc216
-rw-r--r--o3d/command_buffer/client/cross/fenced_allocator.h269
-rw-r--r--o3d/command_buffer/client/cross/fenced_allocator_test.cc498
-rw-r--r--o3d/command_buffer/client/cross/id_allocator.cc87
-rw-r--r--o3d/command_buffer/client/cross/id_allocator.h80
-rw-r--r--o3d/command_buffer/client/cross/id_allocator_test.cc114
-rw-r--r--o3d/command_buffer/common/build.scons40
-rw-r--r--o3d/command_buffer/common/cross/bitfield_helpers.h71
-rw-r--r--o3d/command_buffer/common/cross/bitfield_helpers_test.cc68
-rw-r--r--o3d/command_buffer/common/cross/buffer_sync_api.cc43
-rw-r--r--o3d/command_buffer/common/cross/buffer_sync_api.h168
-rw-r--r--o3d/command_buffer/common/cross/cmd_buffer_format.h324
-rw-r--r--o3d/command_buffer/common/cross/gapi_interface.h826
-rw-r--r--o3d/command_buffer/common/cross/logging.h67
-rw-r--r--o3d/command_buffer/common/cross/mocks.h148
-rw-r--r--o3d/command_buffer/common/cross/resource.cc113
-rw-r--r--o3d/command_buffer/common/cross/resource.h208
-rw-r--r--o3d/command_buffer/common/cross/rpc.h160
-rw-r--r--o3d/command_buffer/common/cross/rpc_fake.cc226
-rw-r--r--o3d/command_buffer/common/cross/rpc_fake.h205
-rw-r--r--o3d/command_buffer/common/cross/rpc_imc.cc231
-rw-r--r--o3d/command_buffer/common/cross/rpc_imc.h109
-rw-r--r--o3d/command_buffer/common/cross/types.h61
-rw-r--r--o3d/command_buffer/samples/bubble/bubble.html83
-rw-r--r--o3d/command_buffer/samples/bubble/bubble_module.cc1266
-rw-r--r--o3d/command_buffer/samples/bubble/cubemap.cc12326
-rw-r--r--o3d/command_buffer/samples/bubble/iridescence_texture.cc167
-rw-r--r--o3d/command_buffer/samples/bubble/iridescence_texture.h105
-rw-r--r--o3d/command_buffer/samples/bubble/perlin_noise.cc107
-rw-r--r--o3d/command_buffer/samples/bubble/perlin_noise.h74
-rw-r--r--o3d/command_buffer/samples/bubble/utils.h73
-rw-r--r--o3d/command_buffer/samples/build.scons55
-rw-r--r--o3d/command_buffer/service/build.scons114
-rw-r--r--o3d/command_buffer/service/cross/big_test.cc106
-rw-r--r--o3d/command_buffer/service/cross/big_test_helpers.h70
-rw-r--r--o3d/command_buffer/service/cross/buffer_rpc.cc136
-rw-r--r--o3d/command_buffer/service/cross/buffer_rpc.h101
-rw-r--r--o3d/command_buffer/service/cross/buffer_rpc_test.cc171
-rw-r--r--o3d/command_buffer/service/cross/cmd_buffer_engine.cc290
-rw-r--r--o3d/command_buffer/service/cross/cmd_buffer_engine.h214
-rw-r--r--o3d/command_buffer/service/cross/cmd_buffer_engine_test.cc626
-rw-r--r--o3d/command_buffer/service/cross/cmd_parser.cc92
-rw-r--r--o3d/command_buffer/service/cross/cmd_parser.h113
-rw-r--r--o3d/command_buffer/service/cross/cmd_parser_test.cc315
-rw-r--r--o3d/command_buffer/service/cross/effect_utils.cc70
-rw-r--r--o3d/command_buffer/service/cross/effect_utils.h56
-rw-r--r--o3d/command_buffer/service/cross/effect_utils_test.cc86
-rw-r--r--o3d/command_buffer/service/cross/gapi_decoder.cc881
-rw-r--r--o3d/command_buffer/service/cross/gapi_decoder.h131
-rw-r--r--o3d/command_buffer/service/cross/gl/effect_gl.cc633
-rw-r--r--o3d/command_buffer/service/cross/gl/effect_gl.h151
-rw-r--r--o3d/command_buffer/service/cross/gl/gapi_gl.cc141
-rw-r--r--o3d/command_buffer/service/cross/gl/gapi_gl.h395
-rw-r--r--o3d/command_buffer/service/cross/gl/geometry_gl.cc548
-rw-r--r--o3d/command_buffer/service/cross/gl/geometry_gl.h144
-rw-r--r--o3d/command_buffer/service/cross/gl/gl_utils.h63
-rw-r--r--o3d/command_buffer/service/cross/gl/sampler_gl.cc235
-rw-r--r--o3d/command_buffer/service/cross/gl/sampler_gl.h87
-rw-r--r--o3d/command_buffer/service/cross/gl/states_gl.cc342
-rw-r--r--o3d/command_buffer/service/cross/gl/texture_gl.cc678
-rw-r--r--o3d/command_buffer/service/cross/gl/texture_gl.h223
-rw-r--r--o3d/command_buffer/service/cross/mocks.h149
-rw-r--r--o3d/command_buffer/service/cross/plugin.cc439
-rw-r--r--o3d/command_buffer/service/cross/resource.cc102
-rw-r--r--o3d/command_buffer/service/cross/resource.h249
-rw-r--r--o3d/command_buffer/service/cross/resource_test.cc128
-rw-r--r--o3d/command_buffer/service/cross/texture_utils.cc104
-rw-r--r--o3d/command_buffer/service/cross/texture_utils.h158
-rw-r--r--o3d/command_buffer/service/linux/big_test_main.cc125
-rw-r--r--o3d/command_buffer/service/linux/x_utils.cc93
-rw-r--r--o3d/command_buffer/service/linux/x_utils.h78
-rw-r--r--o3d/command_buffer/service/win/big_test_main.cc163
-rw-r--r--o3d/command_buffer/service/win/d3d9/d3d9_utils.h102
-rw-r--r--o3d/command_buffer/service/win/d3d9/effect_d3d9.cc569
-rw-r--r--o3d/command_buffer/service/win/d3d9/effect_d3d9.h127
-rw-r--r--o3d/command_buffer/service/win/d3d9/gapi_d3d9.cc305
-rw-r--r--o3d/command_buffer/service/win/d3d9/gapi_d3d9.h384
-rw-r--r--o3d/command_buffer/service/win/d3d9/geometry_d3d9.cc428
-rw-r--r--o3d/command_buffer/service/win/d3d9/geometry_d3d9.h126
-rw-r--r--o3d/command_buffer/service/win/d3d9/sampler_d3d9.cc199
-rw-r--r--o3d/command_buffer/service/win/d3d9/sampler_d3d9.h85
-rw-r--r--o3d/command_buffer/service/win/d3d9/states_d3d9.cc349
-rw-r--r--o3d/command_buffer/service/win/d3d9/texture_d3d9.cc636
-rw-r--r--o3d/command_buffer/service/win/d3d9/texture_d3d9.h245
-rw-r--r--o3d/command_buffer/service/win/plugin.def6
-rw-r--r--o3d/command_buffer/service/win/plugin.rc100
96 files changed, 33180 insertions, 0 deletions
diff --git a/o3d/command_buffer/client/build.scons b/o3d/command_buffer/client/build.scons
new file mode 100644
index 0000000..eeefca6
--- /dev/null
+++ b/o3d/command_buffer/client/build.scons
@@ -0,0 +1,70 @@
+# Copyright 2009, Google Inc.
+# 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.
+
+
+Import('env')
+
+INPUTS = [
+ 'cross/buffer_sync_proxy.cc',
+ 'cross/cmd_buffer_helper.cc',
+ 'cross/effect_helper.cc',
+ 'cross/fenced_allocator.cc',
+ 'cross/id_allocator.cc',
+]
+
+# Create a target library from the sources called 'o3dCmdBuf'
+o3dcmdbuf_lib = env.ComponentLibrary('o3dCmdBuf_client', INPUTS)
+
+# Add some flags and libraries to the build environment for the unit tests
+env.Append(
+ LIBS = [
+ 'o3dCmdBuf_client',
+ 'o3dCmdBuf_common',
+ ] + env['NACL_HTP_LIBS'],
+ LIBPATH = ['$NACL_LIB_DIR'],
+)
+
+if env['TARGET_PLATFORM'] == 'WINDOWS':
+ env.Append(CCFLAGS = ['/Wp64'],
+ LINKFLAGS=['/SUBSYSTEM:CONSOLE'])
+
+if env['TARGET_PLATFORM'] != 'NACL':
+ env.Append(LIBS = ['o3d_base'] + env['ICU_LIBS'])
+
+# Build the big tests
+BIG_TEST_CLIENT = [
+ 'cross/big_test_client.cc',
+]
+
+# Create a target executable program called 'o3dCmdBuf_bigtest_client' from the
+# list of big test client files.
+big_test_client = env.Program('o3dCmdBuf_bigtest_client', BIG_TEST_CLIENT)
+
+# Copy the resulting executable to the Artifacts directory.
+env.Replicate('$ARTIFACTS_DIR', big_test_client)
diff --git a/o3d/command_buffer/client/cross/big_test_client.cc b/o3d/command_buffer/client/cross/big_test_client.cc
new file mode 100644
index 0000000..f829187
--- /dev/null
+++ b/o3d/command_buffer/client/cross/big_test_client.cc
@@ -0,0 +1,407 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+#include <math.h>
+#ifdef __native_client__
+#include <sys/nacl_syscalls.h>
+#else
+#include "native_client/service_runtime/nrd_xfer_lib/nrd_all_modules.h"
+#endif
+#include "command_buffer/common/cross/gapi_interface.h"
+#include "command_buffer/common/cross/rpc_imc.h"
+#include "command_buffer/client/cross/cmd_buffer_helper.h"
+#include "command_buffer/client/cross/buffer_sync_proxy.h"
+#include "third_party/vectormath/files/vectormathlibrary/include/vectormath/scalar/cpp/vectormath_aos.h" // NOLINT
+
+namespace o3d {
+namespace command_buffer {
+
+namespace math = Vectormath::Aos;
+
+// Adds a Clear command into the command buffer.
+// Parameters:
+// cmd_buffer: the command buffer helper.
+// buffers: a bitfield of which buffers to clear (a combination of
+// GAPIInterface::COLOR, GAPIInterface::DEPTH and GAPIInterface::STENCIL).
+// color: the color buffer clear value.
+// depth: the depth buffer clear value.
+// stencil: the stencil buffer clear value.
+void ClearCmd(CommandBufferHelper *cmd_buffer,
+ const unsigned int buffers,
+ const RGBA &color,
+ float depth,
+ unsigned int stencil) {
+ CommandBufferEntry args[7];
+ args[0].value_uint32 = buffers;
+ args[1].value_float = color.red;
+ args[2].value_float = color.green;
+ args[3].value_float = color.blue;
+ args[4].value_float = color.alpha;
+ args[5].value_float = depth;
+ args[6].value_uint32 = stencil;
+ cmd_buffer->AddCommand(command_buffer::CLEAR, 7, args);
+}
+
+// Adds a SetViewport command into the buffer.
+// Parameters:
+// cmd_buffer: the command buffer helper.
+// x, y, width, height: the dimensions of the Viewport.
+// z_near, z_far: the near and far clip plane distances.
+void SetViewportCmd(CommandBufferHelper *cmd_buffer,
+ unsigned int x,
+ unsigned int y,
+ unsigned int width,
+ unsigned int height,
+ float z_near,
+ float z_far) {
+ CommandBufferEntry args[6];
+ args[0].value_uint32 = x;
+ args[1].value_uint32 = y;
+ args[2].value_uint32 = width;
+ args[3].value_uint32 = height;
+ args[4].value_float = z_near;
+ args[5].value_float = z_far;
+ cmd_buffer->AddCommand(command_buffer::SET_VIEWPORT, 6, args);
+}
+
+// Copy a data buffer to args, for IMMEDIATE commands. Returns the number of
+// args used.
+unsigned int CopyToArgs(CommandBufferEntry *args,
+ const void *data,
+ size_t size) {
+ memcpy(args, data, size);
+ const unsigned int arg_size = sizeof(args[0]);
+ return static_cast<unsigned int>((size + arg_size - 1) / arg_size);
+}
+
+// Our effect: pass through position and UV, look up texture.
+// This follows the command buffer effect format :
+// vertex_program_entry \0 fragment_program_entry \0 effect_code.
+const char effect_data[] =
+ "vs\0" // Vertex program entry point
+ "ps\0" // Fragment program entry point
+ "struct a2v {float4 pos: POSITION; float2 uv: TEXCOORD0;};\n"
+ "struct v2f {float4 pos: POSITION; float2 uv: TEXCOORD0;};\n"
+ "float4x4 worldViewProj : WorldViewProjection;\n"
+ "v2f vs(a2v i) {\n"
+ " v2f o;\n"
+ " o.pos = mul(i.pos, worldViewProj);\n"
+ " o.uv = i.uv;\n"
+ " return o;\n"
+ "}\n"
+ "sampler s0;\n"
+ "float4 ps(v2f i) : COLOR { return tex2D(s0, i.uv); }\n";
+
+// Custom vertex, with position and color.
+struct CustomVertex {
+ float x, y, z, w;
+ float u, v;
+};
+
+void BigTestClient(nacl::HtpHandle handle) {
+ IMCSender sender(handle);
+ BufferSyncProxy proxy(&sender);
+
+ proxy.InitConnection();
+ const int kShmSize = 2048;
+ RPCShmHandle shm = CreateShm(kShmSize);
+ void *shm_address = MapShm(shm, kShmSize);
+ unsigned int shm_id = proxy.RegisterSharedMemory(shm, kShmSize);
+
+ {
+ CommandBufferHelper cmd_buffer(&proxy);
+ cmd_buffer.Init(500);
+
+ // Clear the buffers.
+ RGBA color = {0.2f, 0.2f, 0.2f, 1.f};
+ ClearCmd(&cmd_buffer, GAPIInterface::COLOR | GAPIInterface::DEPTH, color,
+ 1.f, 0);
+
+ const ResourceID vertex_buffer_id = 1;
+ const ResourceID vertex_struct_id = 1;
+
+ // AddCommand copies the args, so it is safe to re-use args across various
+ // calls.
+ // 20 is the largest command we use (SET_PARAM_DATA_IMMEDIATE for matrices).
+ CommandBufferEntry args[20];
+
+ CustomVertex vertices[4] = {
+ {-.5f, -.5f, 0.f, 1.f, 0, 0},
+ {.5f, -.5f, 0.f, 1.f, 1, 0},
+ {-.5f, .5f, 0.f, 1.f, 0, 1},
+ {.5f, .5f, 0.f, 1.f, 1, 1},
+ };
+ args[0].value_uint32 = vertex_buffer_id;
+ args[1].value_uint32 = sizeof(vertices); // size
+ args[2].value_uint32 = 0; // flags
+ cmd_buffer.AddCommand(command_buffer::CREATE_VERTEX_BUFFER, 3, args);
+
+ memcpy(shm_address, vertices, sizeof(vertices));
+ args[0].value_uint32 = vertex_buffer_id;
+ args[1].value_uint32 = 0; // offset in VB
+ args[2].value_uint32 = sizeof(vertices); // size
+ args[3].value_uint32 = shm_id; // shm
+ args[4].value_uint32 = 0; // offset in shm
+ cmd_buffer.AddCommand(command_buffer::SET_VERTEX_BUFFER_DATA, 5, args);
+ unsigned int token = cmd_buffer.InsertToken();
+
+ args[0].value_uint32 = vertex_struct_id;
+ args[1].value_uint32 = 2; // input count
+ cmd_buffer.AddCommand(command_buffer::CREATE_VERTEX_STRUCT, 2, args);
+
+ // Set POSITION input stream
+ args[0].value_uint32 = vertex_struct_id;
+ args[1].value_uint32 = 0; // input
+ args[2].value_uint32 = vertex_buffer_id; // buffer
+ args[3].value_uint32 = 0; // offset
+ args[4].value_uint32 =
+ set_vertex_input_cmd::Stride::MakeValue(sizeof(CustomVertex)) |
+ set_vertex_input_cmd::Type::MakeValue(vertex_struct::FLOAT4) |
+ set_vertex_input_cmd::Semantic::MakeValue(vertex_struct::POSITION) |
+ set_vertex_input_cmd::SemanticIndex::MakeValue(0);
+ cmd_buffer.AddCommand(command_buffer::SET_VERTEX_INPUT, 5, args);
+
+ // Set TEXCOORD0 input stream
+ args[1].value_uint32 = 1; // input
+ args[3].value_uint32 = 16; // offset
+ args[4].value_uint32 =
+ set_vertex_input_cmd::Stride::MakeValue(sizeof(CustomVertex)) |
+ set_vertex_input_cmd::Type::MakeValue(vertex_struct::FLOAT2) |
+ set_vertex_input_cmd::Semantic::MakeValue(vertex_struct::TEX_COORD) |
+ set_vertex_input_cmd::SemanticIndex::MakeValue(0);
+ cmd_buffer.AddCommand(command_buffer::SET_VERTEX_INPUT, 5, args);
+
+ // wait for previous transfer to be executed, so that we can re-use the
+ // transfer shared memory buffer.
+ cmd_buffer.WaitForToken(token);
+ memcpy(shm_address, effect_data, sizeof(effect_data));
+ const ResourceID effect_id = 1;
+ args[0].value_uint32 = effect_id;
+ args[1].value_uint32 = sizeof(effect_data); // size
+ args[2].value_uint32 = shm_id; // shm
+ args[3].value_uint32 = 0; // offset in shm
+ cmd_buffer.AddCommand(command_buffer::CREATE_EFFECT, 4, args);
+ token = cmd_buffer.InsertToken();
+
+ // Create a 4x4 2D texture.
+ const ResourceID texture_id = 1;
+ args[0].value_uint32 = texture_id;
+ args[1].value_uint32 =
+ create_texture_2d_cmd::Width::MakeValue(4) |
+ create_texture_2d_cmd::Height::MakeValue(4);
+ args[2].value_uint32 =
+ create_texture_2d_cmd::Levels::MakeValue(0) |
+ create_texture_2d_cmd::Format::MakeValue(texture::ARGB8) |
+ create_texture_2d_cmd::Flags::MakeValue(0);
+ cmd_buffer.AddCommand(command_buffer::CREATE_TEXTURE_2D, 3, args);
+
+ unsigned int texels[4] = {
+ 0xff0000ff,
+ 0xffff00ff,
+ 0xff00ffff,
+ 0xffffffff,
+ };
+ // wait for previous transfer to be executed, so that we can re-use the
+ // transfer shared memory buffer.
+ cmd_buffer.WaitForToken(token);
+ memcpy(shm_address, texels, sizeof(texels));
+ // Creates a 4x4 texture by uploading 2x2 data in each quadrant.
+ for (unsigned int x = 0; x < 2; ++x)
+ for (unsigned int y = 0; y < 2; ++y) {
+ args[0].value_uint32 = texture_id;
+ args[1].value_uint32 =
+ set_texture_data_cmd::X::MakeValue(x*2) |
+ set_texture_data_cmd::Y::MakeValue(y*2);
+ args[2].value_uint32 =
+ set_texture_data_cmd::Width::MakeValue(2) |
+ set_texture_data_cmd::Height::MakeValue(2);
+ args[3].value_uint32 =
+ set_texture_data_cmd::Z::MakeValue(0) |
+ set_texture_data_cmd::Depth::MakeValue(1);
+ args[4].value_uint32 = set_texture_data_cmd::Level::MakeValue(0);
+ args[5].value_uint32 = sizeof(texels[0]) * 2; // row_pitch
+ args[6].value_uint32 = 0; // slice_pitch
+ args[7].value_uint32 = sizeof(texels); // size
+ args[8].value_uint32 = shm_id;
+ args[9].value_uint32 = 0;
+ cmd_buffer.AddCommand(command_buffer::SET_TEXTURE_DATA, 10, args);
+ }
+ token = cmd_buffer.InsertToken();
+
+ const ResourceID sampler_id = 1;
+ args[0].value_uint32 = sampler_id;
+ cmd_buffer.AddCommand(command_buffer::CREATE_SAMPLER, 1, args);
+
+ args[0].value_uint32 = sampler_id;
+ args[1].value_uint32 = texture_id;
+ cmd_buffer.AddCommand(command_buffer::SET_SAMPLER_TEXTURE, 2, args);
+
+ args[0].value_uint32 = sampler_id;
+ args[1].value_uint32 =
+ set_sampler_states::AddressingU::MakeValue(sampler::CLAMP_TO_EDGE) |
+ set_sampler_states::AddressingV::MakeValue(sampler::CLAMP_TO_EDGE) |
+ set_sampler_states::AddressingW::MakeValue(sampler::CLAMP_TO_EDGE) |
+ set_sampler_states::MagFilter::MakeValue(sampler::POINT) |
+ set_sampler_states::MinFilter::MakeValue(sampler::POINT) |
+ set_sampler_states::MipFilter::MakeValue(sampler::NONE) |
+ set_sampler_states::MaxAnisotropy::MakeValue(1);
+ cmd_buffer.AddCommand(command_buffer::SET_SAMPLER_STATES, 2, args);
+
+ // Create a parameter for the sampler.
+ const ResourceID sampler_param_id = 1;
+ {
+ const char param_name[] = "s0";
+ args[0].value_uint32 = sampler_param_id;
+ args[1].value_uint32 = effect_id;
+ args[2].value_uint32 = sizeof(param_name);
+ unsigned int arg_count = CopyToArgs(args + 3, param_name,
+ sizeof(param_name));
+ cmd_buffer.AddCommand(command_buffer::CREATE_PARAM_BY_NAME_IMMEDIATE,
+ 3 + arg_count, args);
+ }
+
+ const ResourceID matrix_param_id = 2;
+ {
+ const char param_name[] = "worldViewProj";
+ args[0].value_uint32 = matrix_param_id;
+ args[1].value_uint32 = effect_id;
+ args[2].value_uint32 = sizeof(param_name);
+ unsigned int arg_count = CopyToArgs(args + 3, param_name,
+ sizeof(param_name));
+ cmd_buffer.AddCommand(command_buffer::CREATE_PARAM_BY_NAME_IMMEDIATE,
+ 3 + arg_count, args);
+ }
+
+ float t = 0.f;
+ while (true) {
+ t = fmodf(t + .01f, 1.f);
+ math::Matrix4 m =
+ math::Matrix4::translation(math::Vector3(0.f, 0.f, .5f));
+ m *= math::Matrix4::rotationY(t * 2 * 3.1415926f);
+ cmd_buffer.AddCommand(command_buffer::BEGIN_FRAME, 0 , NULL);
+ // Clear the background with an animated color (black to red).
+ ClearCmd(&cmd_buffer, GAPIInterface::COLOR | GAPIInterface::DEPTH, color,
+ 1.f, 0);
+
+ args[0].value_uint32 = vertex_struct_id;
+ cmd_buffer.AddCommand(command_buffer::SET_VERTEX_STRUCT, 1, args);
+
+ args[0].value_uint32 = effect_id;
+ cmd_buffer.AddCommand(command_buffer::SET_EFFECT, 1, args);
+
+ args[0].value_uint32 = sampler_param_id;
+ args[1].value_uint32 = sizeof(Uint32); // NOLINT
+ args[2].value_uint32 = sampler_id;
+ cmd_buffer.AddCommand(command_buffer::SET_PARAM_DATA_IMMEDIATE, 3, args);
+
+ args[0].value_uint32 = matrix_param_id;
+ args[1].value_uint32 = sizeof(m);
+ unsigned int arg_count = CopyToArgs(args + 2, &m, sizeof(m));
+ cmd_buffer.AddCommand(command_buffer::SET_PARAM_DATA_IMMEDIATE,
+ 2 + arg_count, args);
+
+ args[0].value_uint32 = GAPIInterface::TRIANGLE_STRIPS;
+ args[1].value_uint32 = 0; // first
+ args[2].value_uint32 = 2; // primitive count
+ cmd_buffer.AddCommand(command_buffer::DRAW, 3, args);
+
+ cmd_buffer.AddCommand(command_buffer::END_FRAME, 0 , NULL);
+ cmd_buffer.Flush();
+ }
+
+ cmd_buffer.Finish();
+ }
+
+ proxy.CloseConnection();
+ proxy.UnregisterSharedMemory(shm_id);
+ DestroyShm(shm);
+
+ sender.SendCall(POISONED_MESSAGE_ID, NULL, 0, NULL, 0);
+}
+
+} // namespace command_buffer
+} // namespace o3d
+
+nacl::HtpHandle InitConnection(int argc, char **argv) {
+ nacl::Handle handle = nacl::kInvalidHandle;
+#ifndef __native_client__
+ NaClNrdAllModulesInit();
+
+ static nacl::SocketAddress g_address = { "command-buffer" };
+ static nacl::SocketAddress g_local_address = { "cb-client" };
+
+ nacl::Handle sockets[2];
+ nacl::SocketPair(sockets);
+
+ nacl::MessageHeader msg;
+ msg.iov = NULL;
+ msg.iov_length = 0;
+ msg.handles = &sockets[1];
+ msg.handle_count = 1;
+ nacl::Handle local_socket = nacl::BoundSocket(&g_local_address);
+ nacl::SendDatagramTo(local_socket, &msg, 0, &g_address);
+ nacl::Close(local_socket);
+ nacl::Close(sockets[1]);
+ handle = sockets[0];
+#else
+ if (argc < 3 || strcmp(argv[1], "-fd") != 0) {
+ fprintf(stderr, "Usage: %s -fd file_descriptor\n", argv[0]);
+ return nacl::kInvalidHtpHandle;
+ }
+ int fd = atoi(argv[2]);
+ handle = imc_connect(fd);
+ if (handle < 0) {
+ fprintf(stderr, "Could not connect to file descriptor %d.\n"
+ "Did you use the -a and -X options to sel_ldr ?\n", fd);
+ return nacl::kInvalidHtpHandle;
+ }
+#endif
+ return nacl::CreateImcDesc(handle);
+}
+
+void CloseConnection(nacl::HtpHandle handle) {
+ nacl::Close(handle);
+#ifndef __native_client__
+ NaClNrdAllModulesFini();
+#endif
+}
+
+int main(int argc, char **argv) {
+ nacl::HtpHandle htp_handle = InitConnection(argc, argv);
+ if (htp_handle == nacl::kInvalidHtpHandle) {
+ return 1;
+ }
+
+ o3d::command_buffer::BigTestClient(htp_handle);
+ CloseConnection(htp_handle);
+ return 0;
+}
diff --git a/o3d/command_buffer/client/cross/buffer_sync_proxy.cc b/o3d/command_buffer/client/cross/buffer_sync_proxy.cc
new file mode 100644
index 0000000..8439085
--- /dev/null
+++ b/o3d/command_buffer/client/cross/buffer_sync_proxy.cc
@@ -0,0 +1,128 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file has the implementation of the Command Buffer Synchronous API RPC
+// glue, client-side (proxy).
+
+#include "command_buffer/client/cross/buffer_sync_proxy.h"
+#include "command_buffer/service/cross/buffer_rpc.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// Implements the proxy InitConnection, forwarding the call with its argument to
+// the RPC server.
+void BufferSyncProxy::InitConnection() {
+ server_->SendCall(BufferRPCImpl::INIT_CONNECTION, NULL, 0, NULL, 0);
+}
+
+// Implements the proxy CloseConnection, forwarding the call to the RPC server.
+void BufferSyncProxy::CloseConnection() {
+ server_->SendCall(BufferRPCImpl::CLOSE_CONNECTION, NULL, 0, NULL, 0);
+}
+
+unsigned int BufferSyncProxy::RegisterSharedMemory(RPCShmHandle buffer,
+ size_t size) {
+ RPCHandle handles[1] = {buffer};
+ return server_->SendCall(BufferRPCImpl::REGISTER_SHARED_MEMORY, &size,
+ sizeof(size), handles, 1);
+}
+
+void BufferSyncProxy::UnregisterSharedMemory(unsigned int shm_id) {
+ server_->SendCall(BufferRPCImpl::UNREGISTER_SHARED_MEMORY, &shm_id,
+ sizeof(shm_id), NULL, 0);
+}
+
+// Implements the proxy SetCommandBuffer, forwarding the call with its
+// arguments to the RPC server.
+void BufferSyncProxy::SetCommandBuffer(unsigned int shm_id,
+ ptrdiff_t offset,
+ size_t size,
+ CommandBufferOffset start_get) {
+ BufferRPCImpl::SetCommandBufferStruct params;
+ params.shm_id = shm_id;
+ params.offset = offset;
+ params.size = size;
+ params.start_get = start_get;
+ server_->SendCall(BufferRPCImpl::SET_COMMAND_BUFFER, &params, sizeof(params),
+ NULL, 0);
+}
+
+// Implements the proxy Put, forwarding the call with its argument to the RPC
+// server.
+void BufferSyncProxy::Put(CommandBufferOffset offset) {
+ server_->SendCall(BufferRPCImpl::PUT, &offset, sizeof(offset), NULL, 0);
+}
+
+// Implements the proxy Get, forwarding the call to the RPC server.
+CommandBufferOffset BufferSyncProxy::Get() {
+ return server_->SendCall(BufferRPCImpl::GET, NULL, 0, NULL, 0);
+}
+
+// Implements the proxy GetToken, forwarding the call to the RPC server.
+unsigned int BufferSyncProxy::GetToken() {
+ return server_->SendCall(BufferRPCImpl::GET_TOKEN, NULL, 0, NULL, 0);
+}
+
+// Implements the proxy WaitGetChanges, forwarding the call with its argument
+// to the RPC server.
+CommandBufferOffset BufferSyncProxy::WaitGetChanges(
+ CommandBufferOffset current_value) {
+ return server_->SendCall(BufferRPCImpl::WAIT_GET_CHANGES, &current_value,
+ sizeof(current_value), NULL, 0);
+}
+
+// Implements the proxy SignalGetChanges, forwarding the call with its
+// arguments to the RPC server.
+void BufferSyncProxy::SignalGetChanges(CommandBufferOffset current_value,
+ int rpc_message_id) {
+ BufferRPCImpl::SignalGetChangesStruct params;
+ params.current_value = current_value;
+ params.rpc_message_id = rpc_message_id;
+ server_->SendCall(BufferRPCImpl::SIGNAL_GET_CHANGES, &params, sizeof(params),
+ NULL, 0);
+}
+
+// Implements the proxy GetStatus, forwarding the call to the RPC server.
+BufferSyncInterface::ParserStatus BufferSyncProxy::GetStatus() {
+ return static_cast<BufferSyncInterface::ParserStatus>(
+ server_->SendCall(BufferRPCImpl::GET_STATUS, NULL, 0, NULL, 0));
+}
+
+// Implements the proxy GetParseError, forwarding the call to the RPC server.
+BufferSyncInterface::ParseError BufferSyncProxy::GetParseError() {
+ return static_cast<ParseError>(
+ server_->SendCall(BufferRPCImpl::GET_PARSE_ERROR, NULL, 0, NULL, 0));
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/client/cross/buffer_sync_proxy.h b/o3d/command_buffer/client/cross/buffer_sync_proxy.h
new file mode 100644
index 0000000..341b935
--- /dev/null
+++ b/o3d/command_buffer/client/cross/buffer_sync_proxy.h
@@ -0,0 +1,102 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file defines the RPC glue for the Command Buffer Synchronous API,
+// client side: a proxy implementation of BufferSyncInterface, forwarding calls
+// to a RPC send interface.
+
+#ifndef O3D_COMMAND_BUFFER_CLIENT_CROSS_BUFFER_SYNC_PROXY_H_
+#define O3D_COMMAND_BUFFER_CLIENT_CROSS_BUFFER_SYNC_PROXY_H_
+
+#include "command_buffer/common/cross/rpc.h"
+#include "command_buffer/common/cross/buffer_sync_api.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// Class implementing the Command Buffer Synchronous API, forwarding all the
+// calls to a RPC server, according to the (trivial) protocol defined in
+// BufferRPCImpl.
+class BufferSyncProxy : public BufferSyncInterface {
+ public:
+ explicit BufferSyncProxy(RPCSendInterface *server) : server_(server) {}
+ virtual ~BufferSyncProxy() {}
+
+ // Implements the InitConnection call, forwarding it to the RPC server.
+ virtual void InitConnection();
+
+ // Implements the CloseConnection call, forwarding it to the RPC server.
+ virtual void CloseConnection();
+
+ // Implements the RegisterSharedMemory call, forwarding it to the RPC server.
+ virtual unsigned int RegisterSharedMemory(RPCShmHandle buffer, size_t size);
+
+ // Implements the UnregisterSharedMemory call, forwarding it to the RPC
+ // server.
+ virtual void UnregisterSharedMemory(unsigned int shm_id);
+
+ // Implements the SetCommandBuffer call, forwarding it to the RPC server.
+ virtual void SetCommandBuffer(unsigned int shm_id,
+ ptrdiff_t offset,
+ size_t size,
+ CommandBufferOffset start_get);
+
+ // Implements the Put call, forwarding it to the RPC server.
+ virtual void Put(CommandBufferOffset offset);
+
+ // Implements the Get call, forwarding it to the RPC server.
+ virtual CommandBufferOffset Get();
+
+ // Implements the GetToken call, forwarding it to the RPC server.
+ virtual unsigned int GetToken();
+
+ // Implements the WaitGetChanges call, forwarding it to the RPC server.
+ virtual CommandBufferOffset WaitGetChanges(
+ CommandBufferOffset current_value);
+
+ // Implements the SignalGetChanges call, forwarding it to the RPC server.
+ virtual void SignalGetChanges(CommandBufferOffset current_value,
+ int rpc_message_id);
+
+ // Implements the GetStatus call, forwarding it to the RPC server.
+ virtual ParserStatus GetStatus();
+
+ // Implements the GetParseError call, forwarding it to the RPC server.
+ virtual ParseError GetParseError();
+ private:
+ RPCSendInterface *server_;
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_CLIENT_CROSS_BUFFER_SYNC_PROXY_H_
diff --git a/o3d/command_buffer/client/cross/buffer_sync_proxy_test.cc b/o3d/command_buffer/client/cross/buffer_sync_proxy_test.cc
new file mode 100644
index 0000000..790a693
--- /dev/null
+++ b/o3d/command_buffer/client/cross/buffer_sync_proxy_test.cc
@@ -0,0 +1,260 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// Tests for the Command Buffer RPC glue, client side (proxy).
+
+#include "base/scoped_ptr.h"
+#include "tests/common/win/testing_common.h"
+#include "command_buffer/client/cross/buffer_sync_proxy.h"
+#include "command_buffer/common/cross/mocks.h"
+#include "command_buffer/service/cross/buffer_rpc.h"
+
+namespace o3d {
+namespace command_buffer {
+
+using testing::Return;
+
+// Test fixture for BufferSyncProxy test - Creates a BufferSyncProxy, using a
+// mock RPCSendInterface.
+class BufferSyncProxyTest : public testing::Test {
+ protected:
+ virtual void SetUp() {
+ server_mock_.reset(new RPCSendInterfaceMock);
+ proxy_.reset(new BufferSyncProxy(server_mock_.get()));
+ }
+ virtual void TearDown() {}
+
+ RPCSendInterfaceMock *server_mock() { return server_mock_.get(); }
+ BufferSyncProxy *proxy() { return proxy_.get(); }
+ private:
+ scoped_ptr<RPCSendInterfaceMock> server_mock_;
+ scoped_ptr<BufferSyncProxy> proxy_;
+};
+
+// Tests the implementation of InitConnection, checking that it sends the
+// correct message.
+TEST_F(BufferSyncProxyTest, TestInitConnection) {
+ RPCSendInterfaceMock::SendCallExpect expect;
+ expect._return = 0;
+ expect.message_id = BufferRPCImpl::INIT_CONNECTION;
+ expect.data = NULL;
+ expect.size = 0;
+ expect.handles = NULL;
+ expect.handle_count = 0;
+ server_mock()->AddSendCallExpect(expect);
+
+ proxy()->InitConnection();
+}
+
+// Tests the implementation of CloseConnection, checking that it sends the
+// correct message.
+TEST_F(BufferSyncProxyTest, TestCloseConnection) {
+ RPCSendInterfaceMock::SendCallExpect expect;
+ expect._return = 0;
+ expect.message_id = BufferRPCImpl::CLOSE_CONNECTION;
+ expect.data = NULL;
+ expect.size = 0;
+ expect.handles = NULL;
+ expect.handle_count = 0;
+ server_mock()->AddSendCallExpect(expect);
+
+ proxy()->CloseConnection();
+}
+
+// Tests the implementation of RegisterSharedMemory, checking that it sends the
+// correct message and returns the correct value.
+TEST_F(BufferSyncProxyTest, TestRegisterSharedMemory) {
+ RPCShmHandle shm = reinterpret_cast<RPCShmHandle>(456);
+ RPCHandle handles[1] = {shm};
+ size_t size = 789;
+ RPCSendInterfaceMock::SendCallExpect expect;
+ expect._return = 123;
+ expect.message_id = BufferRPCImpl::REGISTER_SHARED_MEMORY;
+ expect.data = &size;
+ expect.size = sizeof(size);
+ expect.handles = handles;
+ expect.handle_count = 1;
+ server_mock()->AddSendCallExpect(expect);
+
+ EXPECT_EQ(123, proxy()->RegisterSharedMemory(shm, size));
+}
+
+// Tests the implementation of UnregisterSharedMemory, checking that it sends
+// the correct message.
+TEST_F(BufferSyncProxyTest, TestUnregisterSharedMemory) {
+ unsigned int shm_id = 456;
+ RPCSendInterfaceMock::SendCallExpect expect;
+ expect._return = 0;
+ expect.message_id = BufferRPCImpl::UNREGISTER_SHARED_MEMORY;
+ expect.data = &shm_id;
+ expect.size = sizeof(shm_id);
+ expect.handles = NULL;
+ expect.handle_count = 0;
+ server_mock()->AddSendCallExpect(expect);
+
+ proxy()->UnregisterSharedMemory(456);
+}
+
+// Tests the implementation of SetCommandBuffer, checking that it sends the
+// correct message.
+TEST_F(BufferSyncProxyTest, TestSetCommandBuffer) {
+ BufferRPCImpl::SetCommandBufferStruct params;
+ params.shm_id = 53;
+ params.offset = 1234;
+ params.size = 5678;
+ params.start_get = 42;
+
+ RPCSendInterfaceMock::SendCallExpect expect;
+ expect._return = 0;
+ expect.message_id = BufferRPCImpl::SET_COMMAND_BUFFER;
+ expect.data = &params;
+ expect.size = sizeof(params);
+ expect.handles = NULL;
+ expect.handle_count = 0;
+ server_mock()->AddSendCallExpect(expect);
+
+ proxy()->SetCommandBuffer(53, 1234, 5678, 42);
+}
+
+// Tests the implementation of Put, checking that it sends the correct message.
+TEST_F(BufferSyncProxyTest, TestPut) {
+ RPCSendInterfaceMock::SendCallExpect expect;
+ expect._return = 0;
+ expect.message_id = BufferRPCImpl::PUT;
+ CommandBufferOffset value = 67;
+ expect.data = &value;
+ expect.size = sizeof(value);
+ expect.handles = NULL;
+ expect.handle_count = 0;
+ server_mock()->AddSendCallExpect(expect);
+
+ proxy()->Put(67);
+}
+
+// Tests the implementation of Get, checking that it sends the correct message
+// and returns the correct value.
+TEST_F(BufferSyncProxyTest, TestGet) {
+ RPCSendInterfaceMock::SendCallExpect expect;
+ expect._return = 72;
+ expect.message_id = BufferRPCImpl::GET;
+ expect.data = NULL;
+ expect.size = 0;
+ expect.handles = NULL;
+ expect.handle_count = 0;
+ server_mock()->AddSendCallExpect(expect);
+
+ EXPECT_EQ(72, proxy()->Get());
+}
+
+// Tests the implementation of GetToken, checking that it sends the correct
+// message and returns the correct value.
+TEST_F(BufferSyncProxyTest, TestGetToken) {
+ RPCSendInterfaceMock::SendCallExpect expect;
+ expect._return = 38;
+ expect.message_id = BufferRPCImpl::GET_TOKEN;
+ expect.data = NULL;
+ expect.size = 0;
+ expect.handles = NULL;
+ expect.handle_count = 0;
+ server_mock()->AddSendCallExpect(expect);
+
+ EXPECT_EQ(38, proxy()->GetToken());
+}
+
+// Tests the implementation of WaitGetChanges, checking that it sends the
+// correct message and returns the correct value.
+TEST_F(BufferSyncProxyTest, TestWaitGetChanges) {
+ RPCSendInterfaceMock::SendCallExpect expect;
+ expect._return = 53;
+ expect.message_id = BufferRPCImpl::WAIT_GET_CHANGES;
+ CommandBufferOffset value = 101;
+ expect.data = &value;
+ expect.size = sizeof(value);
+ expect.handles = NULL;
+ expect.handle_count = 0;
+ server_mock()->AddSendCallExpect(expect);
+
+ EXPECT_EQ(53, proxy()->WaitGetChanges(101));
+}
+
+// Tests the implementation of SignalGetChanges, checking that it sends the
+// correct message.
+TEST_F(BufferSyncProxyTest, TestSignalGetChanges) {
+ BufferRPCImpl::SignalGetChangesStruct params;
+ params.current_value = 3141;
+ params.rpc_message_id = 5926;
+
+ RPCSendInterfaceMock::SendCallExpect expect;
+ expect._return = 0;
+ expect.message_id = BufferRPCImpl::SIGNAL_GET_CHANGES;
+ expect.data = &params;
+ expect.size = sizeof(params);
+ expect.handles = NULL;
+ expect.handle_count = 0;
+ server_mock()->AddSendCallExpect(expect);
+
+ proxy()->SignalGetChanges(3141, 5926);
+}
+
+// Tests the implementation of GetStatus, checking that it sends the correct
+// message and returns the correct value.
+TEST_F(BufferSyncProxyTest, TestGetStatus) {
+ RPCSendInterfaceMock::SendCallExpect expect;
+ expect._return = BufferSyncInterface::PARSING;
+ expect.message_id = BufferRPCImpl::GET_STATUS;
+ expect.data = NULL;
+ expect.size = 0;
+ expect.handles = NULL;
+ expect.handle_count = 0;
+ server_mock()->AddSendCallExpect(expect);
+
+ EXPECT_EQ(BufferSyncInterface::PARSING, proxy()->GetStatus());
+}
+
+// Tests the implementation of GetParseError, checking that it sends the correct
+// message and returns the correct value.
+TEST_F(BufferSyncProxyTest, TestGetParseError) {
+ RPCSendInterfaceMock::SendCallExpect expect;
+ expect._return = BufferSyncInterface::PARSE_UNKNOWN_COMMAND;
+ expect.message_id = BufferRPCImpl::GET_PARSE_ERROR;
+ expect.data = NULL;
+ expect.size = 0;
+ expect.handles = NULL;
+ expect.handle_count = 0;
+ server_mock()->AddSendCallExpect(expect);
+
+ EXPECT_EQ(BufferSyncInterface::PARSE_UNKNOWN_COMMAND,
+ proxy()->GetParseError());
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/client/cross/cmd_buffer_helper.cc b/o3d/command_buffer/client/cross/cmd_buffer_helper.cc
new file mode 100644
index 0000000..481f0c7
--- /dev/null
+++ b/o3d/command_buffer/client/cross/cmd_buffer_helper.cc
@@ -0,0 +1,185 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the implementation of the command buffer helper class.
+
+#include "command_buffer/client/cross/cmd_buffer_helper.h"
+
+namespace o3d {
+namespace command_buffer {
+
+CommandBufferHelper::CommandBufferHelper(BufferSyncInterface *interface)
+ : interface_(interface),
+ entries_(NULL),
+ entry_count_(0),
+ token_(0) {
+ // The interface should be connected already.
+ DCHECK_NE(BufferSyncInterface::NOT_CONNECTED, interface_->GetStatus());
+}
+
+bool CommandBufferHelper::Init(unsigned int entry_count) {
+ if (entry_count == 0)
+ return false;
+ size_t size = entry_count * sizeof(CommandBufferEntry); // NOLINT
+ shm_handle_ = CreateShm(size);
+ if (shm_handle_ == kRPCInvalidHandle)
+ return false;
+ void *address = MapShm(shm_handle_, size);
+ if (!address) {
+ DestroyShm(shm_handle_);
+ shm_handle_ = kRPCInvalidHandle;
+ return false;
+ }
+ entries_ = static_cast<CommandBufferEntry *>(address);
+ entry_count_ = entry_count;
+ shm_id_ = interface_->RegisterSharedMemory(shm_handle_, size);
+ interface_->SetCommandBuffer(shm_id_, 0, size, 0);
+ get_ = interface_->Get();
+ put_ = get_;
+ last_token_read_ = interface_->GetToken();
+ return true;
+}
+
+CommandBufferHelper::~CommandBufferHelper() {
+ if (entries_) {
+ interface_->UnregisterSharedMemory(shm_id_);
+ UnmapShm(entries_, entry_count_ * sizeof(CommandBufferEntry)); // NOLINT
+ DestroyShm(shm_handle_);
+ }
+}
+
+// Calls Flush() and then waits until the buffer is empty. Break early if the
+// error is set.
+void CommandBufferHelper::Finish() {
+ Flush();
+ while (put_ != get_) {
+ WaitForGetChange();
+ }
+}
+
+// Inserts a new token into the command stream. It uses an increasing value
+// scheme so that we don't lose tokens (a token has passed if the current token
+// value is higher than that token). Calls Finish() if the token value wraps,
+// which will be rare.
+unsigned int CommandBufferHelper::InsertToken() {
+ ++token_;
+ CommandBufferEntry args;
+ args.value_uint32 = token_;
+ AddCommand(SET_TOKEN, 1, &args);
+ if (token_ == 0) {
+ // we wrapped
+ Finish();
+ last_token_read_ = interface_->GetToken();
+ DCHECK_EQ(token_, last_token_read_);
+ }
+ return token_;
+}
+
+// Waits until the current token value is greater or equal to the value passed
+// in argument.
+void CommandBufferHelper::WaitForToken(unsigned int token) {
+ if (last_token_read_ >= token) return; // fast path.
+ if (token > token_) return; // we wrapped
+ Flush();
+ last_token_read_ = interface_->GetToken();
+ while (last_token_read_ < token) {
+ if (get_ == put_) {
+ LOG(FATAL) << "Empty command buffer while waiting on a token.";
+ return;
+ }
+ WaitForGetChange();
+ last_token_read_ = interface_->GetToken();
+ }
+}
+
+// Waits for get to change. In case get doesn't change or becomes invalid,
+// check for an error.
+void CommandBufferHelper::WaitForGetChange() {
+ CommandBufferOffset new_get = interface_->WaitGetChanges(get_);
+ if (new_get == get_ || new_get == -1) {
+ // If get_ didn't change or is invalid (-1), it means an error may have
+ // occured. Check that.
+ BufferSyncInterface::ParserStatus status = interface_->GetStatus();
+ if (status != BufferSyncInterface::PARSING) {
+ switch (status) {
+ case BufferSyncInterface::NOT_CONNECTED:
+ LOG(FATAL) << "Service disconnected.";
+ return;
+ case BufferSyncInterface::NO_BUFFER:
+ LOG(FATAL) << "Service doesn't have a buffer set.";
+ return;
+ case BufferSyncInterface::PARSE_ERROR: {
+ BufferSyncInterface::ParseError error = interface_->GetParseError();
+ LOG(WARNING) << "Parse error: " << error;
+ return;
+ }
+ case BufferSyncInterface::PARSING:
+ break;
+ }
+ }
+ }
+ get_ = new_get;
+}
+
+// Waits for available entries, basically waiting until get >= put + count + 1.
+// It actually waits for contiguous entries, so it may need to wrap the buffer
+// around, adding noops. Thus this function may change the value of put_.
+// The function will return early if an error occurs, in which case the
+// available space may not be available.
+void CommandBufferHelper::WaitForAvailableEntries(unsigned int count) {
+ CHECK(count < entry_count_);
+ if (put_ + count > entry_count_) {
+ // There's not enough room between the current put and the end of the
+ // buffer, so we need to wrap. We will add noops all the way to the end,
+ // but we need to make sure get wraps first, actually that get is 1 or
+ // more (since put will wrap to 0 after we add the noops).
+ DCHECK_LE(1, put_);
+ Flush();
+ while (get_ > put_ || get_ == 0) WaitForGetChange();
+ // Add the noops. By convention, a noop is a command 0 with no args.
+ CommandHeader header;
+ header.size = 1;
+ header.command = 0;
+ while (put_ < entry_count_) {
+ entries_[put_++].value_header = header;
+ }
+ put_ = 0;
+ }
+ // If we have enough room, return immediatly.
+ if (count <= AvailableEntries()) return;
+ // Otherwise flush, and wait until we do have enough room.
+ Flush();
+ while (AvailableEntries() < count) WaitForGetChange();
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/client/cross/cmd_buffer_helper.h b/o3d/command_buffer/client/cross/cmd_buffer_helper.h
new file mode 100644
index 0000000..775835b
--- /dev/null
+++ b/o3d/command_buffer/client/cross/cmd_buffer_helper.h
@@ -0,0 +1,158 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the command buffer helper class.
+
+#ifndef O3D_COMMAND_BUFFER_CLIENT_CROSS_CMD_BUFFER_HELPER_H_
+#define O3D_COMMAND_BUFFER_CLIENT_CROSS_CMD_BUFFER_HELPER_H_
+
+#include "command_buffer/common/cross/logging.h"
+#include "command_buffer/common/cross/buffer_sync_api.h"
+#include "command_buffer/common/cross/cmd_buffer_format.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// Command buffer helper class. This class simplifies ring buffer management:
+// it will allocate the buffer, give it to the buffer interface, and let the
+// user add commands to it, while taking care of the synchronization (put and
+// get). It also provides a way to ensure commands have been executed, through
+// the token mechanism:
+//
+// helper.AddCommand(...);
+// helper.AddCommand(...);
+// unsigned int token = helper.InsertToken();
+// helper.AddCommand(...);
+// helper.AddCommand(...);
+// [...]
+//
+// helper.WaitForToken(token); // this doesn't return until the first two
+// // commands have been executed.
+class CommandBufferHelper {
+ public:
+ // Constructs a CommandBufferHelper object. The helper needs to be
+ // initialized by calling Init() before use.
+ // Parameters:
+ // interface: the buffer interface the helper sends commands to.
+ explicit CommandBufferHelper(BufferSyncInterface *interface);
+ ~CommandBufferHelper();
+
+ // Initializes the command buffer by allocating shared memory.
+ // Parameters:
+ // entry_count: the number of entries in the buffer. Note that commands
+ // sent through the buffer must use at most entry_count-2 arguments
+ // (entry_count-1 size).
+ // Returns:
+ // true if successful.
+ bool Init(unsigned int entry_count);
+
+ // Flushes the commands, setting the put pointer to let the buffer interface
+ // know that new commands have been added.
+ void Flush() {
+ interface_->Put(put_);
+ }
+
+ // Waits until all the commands have been executed.
+ void Finish();
+
+ // Waits until a given number of available entries are available.
+ // Parameters:
+ // count: number of entries needed. This value must be at most
+ // the size of the buffer minus one.
+ void WaitForAvailableEntries(unsigned int count);
+
+ // Adds a command to the command buffer. This may wait until sufficient space
+ // is available.
+ // Parameters:
+ // command: the command index.
+ // arg_count: the number of arguments for the command.
+ // args: the arguments for the command (these are copied before the
+ // function returns).
+ void AddCommand(unsigned int command,
+ unsigned int arg_count,
+ CommandBufferEntry *args) {
+ CommandHeader header;
+ header.size = arg_count + 1;
+ header.command = command;
+ WaitForAvailableEntries(header.size);
+ entries_[put_++].value_header = header;
+ for (unsigned int i = 0; i < arg_count; ++i) {
+ entries_[put_++] = args[i];
+ }
+ DCHECK_LE(put_, entry_count_);
+ if (put_ == entry_count_) put_ = 0;
+ }
+
+ // Inserts a new token into the command buffer. This token either has a value
+ // different from previously inserted tokens, or ensures that previously
+ // inserted tokens with that value have already passed through the command
+ // stream.
+ // Returns:
+ // the value of the new token.
+ unsigned int InsertToken();
+
+ // Waits until the token of a particular value has passed through the command
+ // stream (i.e. commands inserted before that token have been executed).
+ // NOTE: This will call Flush if it needs to block.
+ // Parameters:
+ // the value of the token to wait for.
+ void WaitForToken(unsigned int token);
+
+ // Returns the buffer interface used to send synchronous commands.
+ BufferSyncInterface *interface() { return interface_; }
+
+ private:
+ // Waits until get changes, updating the value of get_.
+ void WaitForGetChange();
+
+ // Returns the number of available entries (they may not be contiguous).
+ unsigned int AvailableEntries() {
+ return (get_ - put_ - 1 + entry_count_) % entry_count_;
+ }
+
+ BufferSyncInterface *interface_;
+ CommandBufferEntry *entries_;
+ unsigned int entry_count_;
+ unsigned int token_;
+ unsigned int last_token_read_;
+ RPCShmHandle shm_handle_;
+ unsigned int shm_id_;
+ CommandBufferOffset get_;
+ CommandBufferOffset put_;
+
+ friend class CommandBufferHelperTest;
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_CLIENT_CROSS_CMD_BUFFER_HELPER_H_
diff --git a/o3d/command_buffer/client/cross/cmd_buffer_helper_test.cc b/o3d/command_buffer/client/cross/cmd_buffer_helper_test.cc
new file mode 100644
index 0000000..e25bcd9
--- /dev/null
+++ b/o3d/command_buffer/client/cross/cmd_buffer_helper_test.cc
@@ -0,0 +1,276 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// Tests for the Command Buffer Helper.
+
+#include "tests/common/win/testing_common.h"
+#include "command_buffer/client/cross/cmd_buffer_helper.h"
+#include "command_buffer/service/cross/cmd_buffer_engine.h"
+#include "command_buffer/service/cross/mocks.h"
+
+namespace o3d {
+namespace command_buffer {
+
+using testing::Return;
+using testing::Mock;
+using testing::Truly;
+using testing::Sequence;
+using testing::DoAll;
+using testing::Invoke;
+using testing::_;
+
+// Test fixture for CommandBufferHelper test - Creates a CommandBufferHelper,
+// using a CommandBufferEngine with a mock AsyncAPIInterface for its interface
+// (calling it directly, not through the RPC mechanism).
+class CommandBufferHelperTest : public testing::Test {
+ protected:
+ virtual void SetUp() {
+ api_mock_.reset(new AsyncAPIMock);
+ // ignore noops in the mock - we don't want to inspect the internals of the
+ // helper.
+ EXPECT_CALL(*api_mock_, DoCommand(0, 0, _))
+ .WillRepeatedly(Return(BufferSyncInterface::PARSE_NO_ERROR));
+ engine_.reset(new CommandBufferEngine(api_mock_.get()));
+ api_mock_->set_engine(engine_.get());
+
+ engine_->InitConnection();
+ helper_.reset(new CommandBufferHelper(engine_.get()));
+ helper_->Init(10);
+ }
+
+ virtual void TearDown() {
+ helper_.release();
+ engine_->CloseConnection();
+ }
+
+ // Adds a command to the buffer through the helper, while adding it as an
+ // expected call on the API mock.
+ void AddCommandWithExpect(BufferSyncInterface::ParseError _return,
+ unsigned int command,
+ unsigned int arg_count,
+ CommandBufferEntry *args) {
+ helper_->AddCommand(command, arg_count, args);
+ EXPECT_CALL(*api_mock(), DoCommand(command, arg_count,
+ Truly(AsyncAPIMock::IsArgs(arg_count, args))))
+ .InSequence(sequence_)
+ .WillOnce(Return(_return));
+ }
+
+ // Checks that the buffer from put to put+size is free in the parser.
+ void CheckFreeSpace(CommandBufferOffset put, unsigned int size) {
+ CommandBufferOffset parser_put = engine()->parser()->put();
+ CommandBufferOffset parser_get = engine()->parser()->get();
+ CommandBufferOffset limit = put + size;
+ if (parser_get > parser_put) {
+ // "busy" buffer wraps, so "free" buffer is between put (inclusive) and
+ // get (exclusive).
+ EXPECT_LE(parser_put, put);
+ EXPECT_GT(parser_get, limit);
+ } else {
+ // "busy" buffer does not wrap, so the "free" buffer is the top side (from
+ // put to the limit) and the bottom side (from 0 to get).
+ if (put >= parser_put) {
+ // we're on the top side, check we are below the limit.
+ EXPECT_GE(10, limit);
+ } else {
+ // we're on the bottom side, check we are below get.
+ EXPECT_GT(parser_get, limit);
+ }
+ }
+ }
+
+ CommandBufferHelper *helper() { return helper_.get(); }
+ CommandBufferEngine *engine() { return engine_.get(); }
+ AsyncAPIMock *api_mock() { return api_mock_.get(); }
+ CommandBufferOffset get_helper_put() { return helper_->put_; }
+ private:
+ scoped_ptr<AsyncAPIMock> api_mock_;
+ scoped_ptr<CommandBufferEngine> engine_;
+ scoped_ptr<CommandBufferHelper> helper_;
+ Sequence sequence_;
+};
+
+// Checks that commands in the buffer are properly executed, and that the
+// status/error stay valid.
+TEST_F(CommandBufferHelperTest, TestCommandProcessing) {
+ // Check initial state of the engine - it should have been configured by the
+ // helper.
+ EXPECT_TRUE(engine()->rpc_impl() != NULL);
+ EXPECT_TRUE(engine()->parser() != NULL);
+ EXPECT_EQ(BufferSyncInterface::PARSING, engine()->GetStatus());
+ EXPECT_EQ(BufferSyncInterface::PARSE_NO_ERROR, engine()->GetParseError());
+ EXPECT_EQ(0, engine()->Get());
+
+ // Add 3 commands through the helper
+ AddCommandWithExpect(BufferSyncInterface::PARSE_NO_ERROR, 1, 0, NULL);
+
+ CommandBufferEntry args1[2];
+ args1[0].value_uint32 = 3;
+ args1[1].value_float = 4.f;
+ AddCommandWithExpect(BufferSyncInterface::PARSE_NO_ERROR, 2, 2, args1);
+
+ CommandBufferEntry args2[2];
+ args2[0].value_uint32 = 5;
+ args2[1].value_float = 6.f;
+ AddCommandWithExpect(BufferSyncInterface::PARSE_NO_ERROR, 3, 2, args2);
+
+ helper()->Flush();
+ // Check that the engine has work to do now.
+ EXPECT_FALSE(engine()->parser()->IsEmpty());
+
+ // Wait until it's done.
+ helper()->Finish();
+ // Check that the engine has no more work to do.
+ EXPECT_TRUE(engine()->parser()->IsEmpty());
+
+ // Check that the commands did happen.
+ Mock::VerifyAndClearExpectations(api_mock());
+
+ // Check the error status.
+ ASSERT_EQ(BufferSyncInterface::PARSING, engine()->GetStatus());
+ EXPECT_EQ(BufferSyncInterface::PARSE_NO_ERROR, engine()->GetParseError());
+}
+
+// Checks that commands in the buffer are properly executed when wrapping the
+// buffer, and that the status/error stay valid.
+TEST_F(CommandBufferHelperTest, TestCommandWrapping) {
+ // Add 5 commands of size 3 through the helper to make sure we do wrap.
+ CommandBufferEntry args1[2];
+ args1[0].value_uint32 = 3;
+ args1[1].value_float = 4.f;
+
+ for (unsigned int i = 0; i < 5; ++i) {
+ AddCommandWithExpect(BufferSyncInterface::PARSE_NO_ERROR, i+1, 2, args1);
+ }
+
+ helper()->Finish();
+ // Check that the commands did happen.
+ Mock::VerifyAndClearExpectations(api_mock());
+
+ // Check the error status.
+ ASSERT_EQ(BufferSyncInterface::PARSING, engine()->GetStatus());
+ EXPECT_EQ(BufferSyncInterface::PARSE_NO_ERROR, engine()->GetParseError());
+}
+
+
+// Checks that commands in the buffer are properly executed, even if they
+// generate a recoverable error. Check that the error status is properly set,
+// and reset when queried.
+TEST_F(CommandBufferHelperTest, TestRecoverableError) {
+ CommandBufferEntry args[2];
+ args[0].value_uint32 = 3;
+ args[1].value_float = 4.f;
+
+ // Create a command buffer with 3 commands, 2 of them generating errors
+ AddCommandWithExpect(BufferSyncInterface::PARSE_NO_ERROR, 1, 2, args);
+ AddCommandWithExpect(BufferSyncInterface::PARSE_UNKNOWN_COMMAND, 2, 2, args);
+ AddCommandWithExpect(BufferSyncInterface::PARSE_INVALID_ARGUMENTS, 3, 2,
+ args);
+
+ helper()->Finish();
+ // Check that the commands did happen.
+ Mock::VerifyAndClearExpectations(api_mock());
+
+ // Check that the error status was set to the first error.
+ EXPECT_EQ(BufferSyncInterface::PARSE_UNKNOWN_COMMAND,
+ engine()->GetParseError());
+ // Check that the error status was reset after the query.
+ EXPECT_EQ(BufferSyncInterface::PARSE_NO_ERROR, engine()->GetParseError());
+
+ engine()->CloseConnection();
+}
+
+// Checks that asking for available entries work, and that the parser
+// effectively won't use that space.
+TEST_F(CommandBufferHelperTest, TestAvailableEntries) {
+ CommandBufferEntry args[2];
+ args[0].value_uint32 = 3;
+ args[1].value_float = 4.f;
+
+ // Add 2 commands through the helper - 8 entries
+ AddCommandWithExpect(BufferSyncInterface::PARSE_NO_ERROR, 1, 0, NULL);
+ AddCommandWithExpect(BufferSyncInterface::PARSE_NO_ERROR, 2, 0, NULL);
+ AddCommandWithExpect(BufferSyncInterface::PARSE_NO_ERROR, 3, 2, args);
+ AddCommandWithExpect(BufferSyncInterface::PARSE_NO_ERROR, 4, 2, args);
+
+ // Ask for 5 entries.
+ helper()->WaitForAvailableEntries(5);
+
+ CommandBufferOffset put = get_helper_put();
+ CheckFreeSpace(put, 5);
+
+ // Add more commands.
+ AddCommandWithExpect(BufferSyncInterface::PARSE_NO_ERROR, 5, 2, args);
+
+ // Wait until everything is done done.
+ helper()->Finish();
+
+ // Check that the commands did happen.
+ Mock::VerifyAndClearExpectations(api_mock());
+
+ // Check the error status.
+ ASSERT_EQ(BufferSyncInterface::PARSING, engine()->GetStatus());
+ EXPECT_EQ(BufferSyncInterface::PARSE_NO_ERROR, engine()->GetParseError());
+}
+
+// Checks that the InsertToken/WaitForToken work.
+TEST_F(CommandBufferHelperTest, TestToken) {
+ CommandBufferEntry args[2];
+ args[0].value_uint32 = 3;
+ args[1].value_float = 4.f;
+
+ // Add a first command.
+ AddCommandWithExpect(BufferSyncInterface::PARSE_NO_ERROR, 3, 2, args);
+ // keep track of the buffer position.
+ CommandBufferOffset command1_put = get_helper_put();
+ unsigned int token = helper()->InsertToken();
+
+ EXPECT_CALL(*api_mock(), DoCommand(SET_TOKEN, 1, _))
+ .WillOnce(DoAll(Invoke(api_mock(), &AsyncAPIMock::SetToken),
+ Return(BufferSyncInterface::PARSE_NO_ERROR)));
+ // Add another command.
+ AddCommandWithExpect(BufferSyncInterface::PARSE_NO_ERROR, 4, 2, args);
+ helper()->WaitForToken(token);
+ // check that the get pointer is beyond the first command.
+ EXPECT_LE(command1_put, engine()->Get());
+ helper()->Finish();
+
+ // Check that the commands did happen.
+ Mock::VerifyAndClearExpectations(api_mock());
+
+ // Check the error status.
+ ASSERT_EQ(BufferSyncInterface::PARSING, engine()->GetStatus());
+ EXPECT_EQ(BufferSyncInterface::PARSE_NO_ERROR, engine()->GetParseError());
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/client/cross/effect_helper.cc b/o3d/command_buffer/client/cross/effect_helper.cc
new file mode 100644
index 0000000..0cab6ee
--- /dev/null
+++ b/o3d/command_buffer/client/cross/effect_helper.cc
@@ -0,0 +1,211 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file implements the EffectHelper class.
+
+#include "command_buffer/common/cross/cmd_buffer_format.h"
+#include "command_buffer/client/cross/cmd_buffer_helper.h"
+#include "command_buffer/client/cross/effect_helper.h"
+#include "command_buffer/client/cross/fenced_allocator.h"
+#include "command_buffer/client/cross/id_allocator.h"
+
+// TODO: write a unit test.
+
+namespace o3d {
+namespace command_buffer {
+
+bool EffectHelper::CreateEffectParameters(ResourceID effect_id,
+ std::vector<EffectParamDesc> *descs) {
+ using effect_param::Desc;
+ DCHECK_NE(effect_id, kInvalidResource);
+ DCHECK(descs);
+ descs->clear();
+
+ // Get the param count.
+ Uint32 *retval = shm_allocator_->AllocTyped<Uint32>(1);
+ CommandBufferEntry args[4];
+ args[0].value_uint32 = effect_id;
+ args[1].value_uint32 = sizeof(*retval);
+ args[2].value_uint32 = shm_id_;
+ args[3].value_uint32 = shm_allocator_->GetOffset(retval);
+ helper_->AddCommand(GET_PARAM_COUNT, 4, args);
+ // Finish has to be called to get the result.
+ helper_->Finish();
+
+ // We could have failed if the effect_id is invalid.
+ if (helper_->interface()->GetParseError() !=
+ BufferSyncInterface::PARSE_NO_ERROR) {
+ shm_allocator_->Free(retval);
+ return false;
+ }
+ unsigned int param_count = *retval;
+
+ shm_allocator_->Free(retval);
+ unsigned int max_buffer_size = shm_allocator_->GetLargestFreeOrPendingSize();
+ if (max_buffer_size < sizeof(Desc)) { // NOLINT
+ // Not enough memory to get at least 1 param desc.
+ return false;
+ }
+ descs->resize(param_count);
+ for (unsigned int i = 0; i < param_count; ++i) {
+ EffectParamDesc *desc = &((*descs)[i]);
+ desc->id = param_id_allocator_->AllocateID();
+ args[0].value_uint32 = desc->id;
+ args[1].value_uint32 = effect_id;
+ args[2].value_uint32 = i;
+ helper_->AddCommand(CREATE_PARAM, 3, args);
+ }
+
+ // Read param descriptions in batches. We use as much shared memory as
+ // possible so that we only call Finish as little as possible.
+ unsigned int max_param_per_batch =
+ std::min(param_count, max_buffer_size / sizeof(Desc)); // NOLINT
+ Desc *raw_descs = shm_allocator_->AllocTyped<Desc>(max_param_per_batch);
+ DCHECK(raw_descs);
+ for (unsigned int i = 0; i < param_count; i += max_param_per_batch) {
+ unsigned int count = std::min(param_count - i, max_param_per_batch);
+ for (unsigned int j = 0 ; j < count; ++j) {
+ EffectParamDesc *desc = &((*descs)[i + j]);
+ Desc *raw_desc = raw_descs + j;
+ args[0].value_uint32 = desc->id;
+ args[1].value_uint32 = sizeof(*raw_desc);
+ args[2].value_uint32 = shm_id_;
+ args[3].value_uint32 = shm_allocator_->GetOffset(raw_desc);
+ helper_->AddCommand(GET_PARAM_DESC, 4, args);
+ }
+ // Finish to get the results.
+ helper_->Finish();
+ DCHECK_EQ(helper_->interface()->GetParseError(),
+ BufferSyncInterface::PARSE_NO_ERROR);
+ for (unsigned int j = 0 ; j < count; ++j) {
+ EffectParamDesc *desc = &((*descs)[i + j]);
+ Desc *raw_desc = raw_descs + j;
+ desc->data_type = raw_desc->data_type;
+ desc->data_size = raw_desc->data_size;
+ desc->cmd_desc_size = raw_desc->size;
+ }
+ }
+ shm_allocator_->Free(raw_descs);
+ return true;
+}
+
+bool EffectHelper::GetParamStrings(EffectParamDesc *desc) {
+ using effect_param::Desc;
+ DCHECK(desc);
+ DCHECK_NE(desc->id, kInvalidResource);
+ // desc may not have come directly from CreateEffectParameters, so it may be
+ // less than the minimum required size.
+ unsigned int size = std::max(desc->cmd_desc_size, sizeof(Desc)); // NOLINT
+ Desc *raw_desc = static_cast<Desc *>(shm_allocator_->Alloc(size));
+ if (!raw_desc) {
+ // Not enough memory to get the param desc.
+ return false;
+ }
+ CommandBufferEntry args[4];
+ args[0].value_uint32 = desc->id;
+ args[1].value_uint32 = size;
+ args[2].value_uint32 = shm_id_;
+ args[3].value_uint32 = shm_allocator_->GetOffset(raw_desc);
+ helper_->AddCommand(GET_PARAM_DESC, 4, args);
+ // Finish to get the results.
+ helper_->Finish();
+
+ // We could have failed if the param ID is invalid.
+ if (helper_->interface()->GetParseError() !=
+ BufferSyncInterface::PARSE_NO_ERROR) {
+ shm_allocator_->Free(raw_desc);
+ return false;
+ }
+
+ if (raw_desc->size > size) {
+ // We had not allocated enough memory the first time (e.g. if the
+ // EffectParamDesc didn't come from CreateEffectParameters, so the user had
+ // no way of knowing what size was needed for the strings), so re-allocate
+ // and try again.
+ size = raw_desc->size;
+ desc->cmd_desc_size = size;
+ shm_allocator_->Free(raw_desc);
+ raw_desc = static_cast<Desc *>(shm_allocator_->Alloc(size));
+ if (!raw_desc) {
+ // Not enough memory to get the param desc.
+ return false;
+ }
+ args[1].value_uint32 = size;
+ args[3].value_uint32 = shm_allocator_->GetOffset(raw_desc);
+ helper_->AddCommand(GET_PARAM_DESC, 4, args);
+ // Finish to get the results.
+ helper_->Finish();
+ DCHECK_EQ(helper_->interface()->GetParseError(),
+ BufferSyncInterface::PARSE_NO_ERROR);
+ DCHECK_EQ(raw_desc->size, size);
+ }
+
+ const char *raw_desc_string = reinterpret_cast<char *>(raw_desc);
+ if (raw_desc->name_offset) {
+ DCHECK_LE(raw_desc->name_offset + raw_desc->name_size, raw_desc->size);
+ DCHECK_GT(raw_desc->name_size, 0);
+ DCHECK_EQ(raw_desc_string[raw_desc->name_offset + raw_desc->name_size - 1],
+ 0);
+ desc->name = String(raw_desc_string + raw_desc->name_offset,
+ raw_desc->name_size - 1);
+ } else {
+ desc->name.clear();
+ }
+ if (raw_desc->semantic_offset) {
+ DCHECK_LE(raw_desc->semantic_offset + raw_desc->semantic_size,
+ raw_desc->size);
+ DCHECK_GT(raw_desc->semantic_size, 0);
+ DCHECK_EQ(raw_desc_string[raw_desc->semantic_offset +
+ raw_desc->semantic_size - 1],
+ 0);
+ desc->semantic = String(raw_desc_string + raw_desc->semantic_offset,
+ raw_desc->semantic_size - 1);
+ } else {
+ desc->semantic.clear();
+ }
+ shm_allocator_->Free(raw_desc);
+ return true;
+}
+
+void EffectHelper::DestroyEffectParameters(
+ const std::vector<EffectParamDesc> &descs) {
+ CommandBufferEntry args[1];
+ for (unsigned int i = 0; i < descs.size(); ++i) {
+ const EffectParamDesc &desc = descs[i];
+ args[0].value_uint32 = desc.id;
+ helper_->AddCommand(DESTROY_PARAM, 1, args);
+ param_id_allocator_->FreeID(desc.id);
+ }
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/client/cross/effect_helper.h b/o3d/command_buffer/client/cross/effect_helper.h
new file mode 100644
index 0000000..19523ee
--- /dev/null
+++ b/o3d/command_buffer/client/cross/effect_helper.h
@@ -0,0 +1,134 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file defines the EffectHelper class.
+
+#ifndef O3D_COMMAND_BUFFER_CLIENT_CROSS_EFFECT_HELPER_H_
+#define O3D_COMMAND_BUFFER_CLIENT_CROSS_EFFECT_HELPER_H_
+
+#include <vector>
+#include "command_buffer/common/cross/resource.h"
+
+namespace o3d {
+namespace command_buffer {
+
+class FencedAllocatorWrapper;
+class IdAllocator;
+class CommandBufferHelper;
+
+// A helper class to find parameters in an effect.
+class EffectHelper {
+ public:
+ // A more usable version of effect_param::Desc
+ struct EffectParamDesc {
+ ResourceID id; // The resource ID for the param.
+ String name; // The name of the param.
+ String semantic; // The semantic of the param.
+ effect_param::DataType data_type; // The data type of a param.
+ unsigned int data_size; // The size of the data for a param.
+ unsigned int cmd_desc_size; // The size of the effect_param::Desc
+ // structure (counting strings) for a
+ // param.
+ };
+
+ EffectHelper(CommandBufferHelper *helper,
+ FencedAllocatorWrapper *shm_allocator,
+ unsigned int shm_id,
+ IdAllocator *param_id_allocator)
+ : helper_(helper),
+ shm_allocator_(shm_allocator),
+ shm_id_(shm_id),
+ param_id_allocator_(param_id_allocator) {
+ DCHECK(helper);
+ DCHECK(shm_allocator);
+ DCHECK(param_id_allocator);
+ }
+
+ // Creates all the parameters in an effect and gets their descriptions. The
+ // strings will not be retrieved, so name and semantic will be empty. The
+ // cmd_desc_size field will be set to the proper size to be able to get the
+ // strings with a single command within GetParamStrings, so it should be left
+ // alone.
+ //
+ // The ResourceIDs will be allocated in the param_id_allocator.
+ // Temporary buffers will be allocated in the shm_allocator, but they will be
+ // freed before the function returns (possibly pending a token). At least
+ // sizeof(effect_param::Desc) must be available for this function to succeed.
+ // This function will call Finish(), hence will block.
+ //
+ // Parameters:
+ // effect_id: the ResourceID of the effect.
+ // descs: A pointer to a vector containing the returned descriptions.
+ // The pointed vector will be cleared.
+ // Returns:
+ // true if successful. Reasons for failure are:
+ // - invalid effect_id,
+ // - not enough memory in the shm_allocator_.
+ bool CreateEffectParameters(ResourceID effect_id,
+ std::vector<EffectParamDesc> *descs);
+
+ // Gets the strings for a desc. This will fill in the values for the name and
+ // semantic fields.
+ // Temporary buffers will be allocated in the shm_allocator, but they will be
+ // freed before the function returns (possibly pending a token). At least
+ // desc.cmd_desc_size (as returned by CreateEffectParameters) must be
+ // available for this function to succeed.
+ // This function will call Finish(), hence will block.
+ //
+ // Parameters:
+ // desc: a pointer to the description for a parameter. The id field should
+ // be set to the ResourceID of the parameter.
+ // Returns:
+ // true if successful. Reasons for failure are:
+ // - invalid parameter ResourceID,
+ // - not enough memory in the shm_allocator_.
+ bool GetParamStrings(EffectParamDesc *desc);
+
+ // Destroys all parameter resources referenced by the descriptions. The
+ // ResourceID will be freed from the param_id_allocator.
+ // Parameters:
+ // descs: the vector of descriptions containing the ResourceIDs of the
+ // parameters to destroy.
+ void DestroyEffectParameters(const std::vector<EffectParamDesc> &descs);
+ private:
+ CommandBufferHelper *helper_;
+ FencedAllocatorWrapper *shm_allocator_;
+ unsigned int shm_id_;
+ IdAllocator *param_id_allocator_;
+
+ DISALLOW_COPY_AND_ASSIGN(EffectHelper);
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_CLIENT_CROSS_EFFECT_HELPER_H_
diff --git a/o3d/command_buffer/client/cross/fenced_allocator.cc b/o3d/command_buffer/client/cross/fenced_allocator.cc
new file mode 100644
index 0000000..3c66f5d
--- /dev/null
+++ b/o3d/command_buffer/client/cross/fenced_allocator.cc
@@ -0,0 +1,216 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the implementation of the FencedAllocator class.
+
+#include "command_buffer/client/cross/fenced_allocator.h"
+#include <algorithm>
+#include "command_buffer/client/cross/cmd_buffer_helper.h"
+
+namespace o3d {
+namespace command_buffer {
+
+#ifndef COMPILER_MSVC
+const FencedAllocator::Offset FencedAllocator::kInvalidOffset;
+#endif
+
+FencedAllocator::~FencedAllocator() {
+ // Free blocks pending tokens.
+ for (unsigned int i = 0; i < blocks_.size(); ++i) {
+ if (blocks_[i].state == FREE_PENDING_TOKEN) {
+ i = WaitForTokenAndFreeBlock(i);
+ }
+ }
+ DCHECK_EQ(blocks_.size(), 1);
+ DCHECK_EQ(blocks_[0].state, FREE);
+}
+
+// Looks for a non-allocated block that is big enough. Search in the FREE
+// blocks first (for direct usage), first-fit, then in the FREE_PENDING_TOKEN
+// blocks, waiting for them. The current implementation isn't smart about
+// optimizing what to wait for, just looks inside the block in order (first-fit
+// as well).
+FencedAllocator::Offset FencedAllocator::Alloc(unsigned int size) {
+ // Similarly to malloc, an allocation of 0 allocates at least 1 byte, to
+ // return different pointers every time.
+ if (size == 0) size = 1;
+
+ // Try first to allocate in a free block.
+ for (unsigned int i = 0; i < blocks_.size(); ++i) {
+ Block &block = blocks_[i];
+ if (block.state == FREE && block.size >= size) {
+ return AllocInBlock(i, size);
+ }
+ }
+
+ // No free block is available. Look for blocks pending tokens, and wait for
+ // them to be re-usable.
+ for (unsigned int i = 0; i < blocks_.size(); ++i) {
+ if (blocks_[i].state != FREE_PENDING_TOKEN)
+ continue;
+ i = WaitForTokenAndFreeBlock(i);
+ if (blocks_[i].size >= size)
+ return AllocInBlock(i, size);
+ }
+ return kInvalidOffset;
+}
+
+// Looks for the corresponding block, mark it FREE, and collapse it if
+// necessary.
+void FencedAllocator::Free(FencedAllocator::Offset offset) {
+ BlockIndex index = GetBlockByOffset(offset);
+ DCHECK_NE(blocks_[index].state, FREE);
+ blocks_[index].state = FREE;
+ CollapseFreeBlock(index);
+}
+
+// Looks for the corresponding block, mark it FREE_PENDING_TOKEN.
+void FencedAllocator::FreePendingToken(FencedAllocator::Offset offset,
+ unsigned int token) {
+ BlockIndex index = GetBlockByOffset(offset);
+ Block &block = blocks_[index];
+ block.state = FREE_PENDING_TOKEN;
+ block.token = token;
+}
+
+// Gets the max of the size of the blocks marked as free.
+unsigned int FencedAllocator::GetLargestFreeSize() {
+ unsigned int max_size = 0;
+ for (unsigned int i = 0; i < blocks_.size(); ++i) {
+ Block &block = blocks_[i];
+ if (block.state == FREE)
+ max_size = std::max(max_size, block.size);
+ }
+ return max_size;
+}
+
+// Gets the size of the largest segment of blocks that are either FREE or
+// FREE_PENDING_TOKEN.
+unsigned int FencedAllocator::GetLargestFreeOrPendingSize() {
+ unsigned int max_size = 0;
+ unsigned int current_size = 0;
+ for (unsigned int i = 0; i < blocks_.size(); ++i) {
+ Block &block = blocks_[i];
+ if (block.state == IN_USE) {
+ max_size = std::max(max_size, current_size);
+ current_size = 0;
+ } else {
+ DCHECK(block.state == FREE || block.state == FREE_PENDING_TOKEN);
+ current_size += block.size;
+ }
+ }
+ return std::max(max_size, current_size);
+}
+
+// Makes sure that:
+// - there is at least one block.
+// - there are no contiguous FREE blocks (they should have been collapsed).
+// - the successive offsets match the block sizes, and they are in order.
+bool FencedAllocator::CheckConsistency() {
+ if (blocks_.size() < 1) return false;
+ for (unsigned int i = 0; i < blocks_.size() - 1; ++i) {
+ Block &current = blocks_[i];
+ Block &next = blocks_[i + 1];
+ // This test is NOT included in the next one, because offset is unsigned.
+ if (next.offset <= current.offset)
+ return false;
+ if (next.offset != current.offset + current.size)
+ return false;
+ if (current.state == FREE && next.state == FREE)
+ return false;
+ }
+ return true;
+}
+
+// Collapse the block to the next one, then to the previous one. Provided the
+// structure is consistent, those are the only blocks eligible for collapse.
+FencedAllocator::BlockIndex FencedAllocator::CollapseFreeBlock(
+ BlockIndex index) {
+ if (index + 1 < blocks_.size()) {
+ Block &next = blocks_[index + 1];
+ if (next.state == FREE) {
+ blocks_[index].size += next.size;
+ blocks_.erase(blocks_.begin() + index + 1);
+ }
+ }
+ if (index > 0) {
+ Block &prev = blocks_[index - 1];
+ if (prev.state == FREE) {
+ prev.size += blocks_[index].size;
+ blocks_.erase(blocks_.begin() + index);
+ --index;
+ }
+ }
+ return index;
+}
+
+// Waits for the block's token, then mark the block as free, then collapse it.
+FencedAllocator::BlockIndex FencedAllocator::WaitForTokenAndFreeBlock(
+ BlockIndex index) {
+ Block &block = blocks_[index];
+ DCHECK_EQ(block.state, FREE_PENDING_TOKEN);
+ helper_->WaitForToken(block.token);
+ block.state = FREE;
+ return CollapseFreeBlock(index);
+}
+
+// If the block is exactly the requested size, simply mark it IN_USE, otherwise
+// split it and mark the first one (of the requested size) IN_USE.
+FencedAllocator::Offset FencedAllocator::AllocInBlock(BlockIndex index,
+ unsigned int size) {
+ Block &block = blocks_[index];
+ DCHECK_GE(block.size, size);
+ DCHECK_EQ(block.state, FREE);
+ Offset offset = block.offset;
+ if (block.size == size) {
+ block.state = IN_USE;
+ return offset;
+ }
+ Block newblock = { FREE, offset + size, block.size - size, kUnusedToken};
+ block.state = IN_USE;
+ block.size = size;
+ // this is the last thing being done because it may invalidate block;
+ blocks_.insert(blocks_.begin() + index + 1, newblock);
+ return offset;
+}
+
+// The blocks are in offset order, so we can do a binary search.
+FencedAllocator::BlockIndex FencedAllocator::GetBlockByOffset(Offset offset) {
+ Block templ = { IN_USE, offset, 0, kUnusedToken };
+ Container::iterator it = std::lower_bound(blocks_.begin(), blocks_.end(),
+ templ, OffsetCmp());
+ DCHECK(it != blocks_.end() && it->offset == offset);
+ return it-blocks_.begin();
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/client/cross/fenced_allocator.h b/o3d/command_buffer/client/cross/fenced_allocator.h
new file mode 100644
index 0000000..d6a4904
--- /dev/null
+++ b/o3d/command_buffer/client/cross/fenced_allocator.h
@@ -0,0 +1,269 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the definition of the FencedAllocator class.
+
+#ifndef O3D_COMMAND_BUFFER_CLIENT_CROSS_FENCED_ALLOCATOR_H_
+#define O3D_COMMAND_BUFFER_CLIENT_CROSS_FENCED_ALLOCATOR_H_
+
+#include <vector>
+#include "base/basictypes.h"
+#include "command_buffer/common/cross/logging.h"
+
+namespace o3d {
+namespace command_buffer {
+class CommandBufferHelper;
+
+// FencedAllocator provides a mechanism to manage allocations within a fixed
+// block of memory (storing the book-keeping externally). Furthermore this
+// class allows to free data "pending" the passage of a command buffer token,
+// that is, the memory won't be reused until the command buffer has processed
+// that token.
+//
+// NOTE: Although this class is intended to be used in the command buffer
+// environment which is multi-process, this class isn't "thread safe", because
+// it isn't meant to be shared across modules. It is thread-compatible though
+// (see http://www.corp.google.com/eng/doc/cpp_primer.html#thread_safety).
+class FencedAllocator {
+ public:
+ typedef unsigned int Offset;
+ // Invalid offset, returned by Alloc in case of failure.
+ static const Offset kInvalidOffset = 0xffffffffU;
+
+ // Creates a FencedAllocator. Note that the size of the buffer is passed, but
+ // not its base address: everything is handled as offsets into the buffer.
+ FencedAllocator(unsigned int size,
+ CommandBufferHelper *helper)
+ : helper_(helper) {
+ Block block = { FREE, 0, size, kUnusedToken };
+ blocks_.push_back(block);
+ }
+
+ ~FencedAllocator();
+
+ // Allocates a block of memory. If the buffer is out of directly available
+ // memory, this function may wait until memory that was freed "pending a
+ // token" can be re-used.
+ //
+ // Parameters:
+ // size: the size of the memory block to allocate.
+ //
+ // Returns:
+ // the offset of the allocated memory block, or kInvalidOffset if out of
+ // memory.
+ Offset Alloc(unsigned int size);
+
+ // Frees a block of memory.
+ //
+ // Parameters:
+ // offset: the offset of the memory block to free.
+ void Free(Offset offset);
+
+ // Frees a block of memory, pending the passage of a token. That memory won't
+ // be re-allocated until the token has passed through the command stream.
+ //
+ // Parameters:
+ // offset: the offset of the memory block to free.
+ // token: the token value to wait for before re-using the memory.
+ void FreePendingToken(Offset offset, unsigned int token);
+
+ // Gets the size of the largest free block that is available without waiting.
+ unsigned int GetLargestFreeSize();
+
+ // Gets the size of the largest free block that can be allocated if the
+ // caller can wait. Allocating a block of this size will succeed, but may
+ // block.
+ unsigned int GetLargestFreeOrPendingSize();
+
+ // Checks for consistency inside the book-keeping structures. Used for
+ // testing.
+ bool CheckConsistency();
+
+ private:
+ // Status of a block of memory, for book-keeping.
+ enum State {
+ IN_USE,
+ FREE,
+ FREE_PENDING_TOKEN
+ };
+
+ // Book-keeping sturcture that describes a block of memory.
+ struct Block {
+ State state;
+ Offset offset;
+ unsigned int size;
+ unsigned int token; // token to wait for in the FREE_PENDING_TOKEN case.
+ };
+
+ // Comparison functor for memory block sorting.
+ class OffsetCmp {
+ public:
+ bool operator() (const Block &left, const Block &right) {
+ return left.offset < right.offset;
+ }
+ };
+
+ typedef std::vector<Block> Container;
+ typedef unsigned int BlockIndex;
+
+ static const unsigned int kUnusedToken = 0;
+
+ // Gets the index of a memory block, given its offset.
+ BlockIndex GetBlockByOffset(Offset offset);
+
+ // Collapse a free block with its neighbours if they are free. Returns the
+ // index of the collapsed block.
+ // NOTE: this will invalidate block indices.
+ BlockIndex CollapseFreeBlock(BlockIndex index);
+
+ // Waits for a FREE_PENDING_TOKEN block to be usable, and free it. Returns
+ // the new index of that block (since it may have been collapsed).
+ // NOTE: this will invalidate block indices.
+ BlockIndex WaitForTokenAndFreeBlock(BlockIndex index);
+
+ // Allocates a block of memory inside a given block, splitting it in two
+ // (unless that block is of the exact requested size).
+ // NOTE: this will invalidate block indices.
+ // Returns the offset of the allocated block (NOTE: this is different from
+ // the other functions that return a block index).
+ Offset AllocInBlock(BlockIndex index, unsigned int size);
+
+ command_buffer::CommandBufferHelper *helper_;
+ Container blocks_;
+
+ DISALLOW_IMPLICIT_CONSTRUCTORS(FencedAllocator);
+};
+
+// This class functions just like FencedAllocator, but its API uses pointers
+// instead of offsets.
+class FencedAllocatorWrapper {
+ public:
+ FencedAllocatorWrapper(unsigned int size,
+ CommandBufferHelper *helper,
+ void *base)
+ : allocator_(size, helper),
+ base_(base) { }
+
+ // Allocates a block of memory. If the buffer is out of directly available
+ // memory, this function may wait until memory that was freed "pending a
+ // token" can be re-used.
+ //
+ // Parameters:
+ // size: the size of the memory block to allocate.
+ //
+ // Returns:
+ // the pointer to the allocated memory block, or NULL if out of
+ // memory.
+ void *Alloc(unsigned int size) {
+ FencedAllocator::Offset offset = allocator_.Alloc(size);
+ return GetPointer(offset);
+ }
+
+ // Allocates a block of memory. If the buffer is out of directly available
+ // memory, this function may wait until memory that was freed "pending a
+ // token" can be re-used.
+ // This is a type-safe version of Alloc, returning a typed pointer.
+ //
+ // Parameters:
+ // count: the number of elements to allocate.
+ //
+ // Returns:
+ // the pointer to the allocated memory block, or NULL if out of
+ // memory.
+ template <typename T> T *AllocTyped(unsigned int count) {
+ return static_cast<T *>(Alloc(count * sizeof(T)));
+ }
+
+ // Frees a block of memory.
+ //
+ // Parameters:
+ // pointer: the pointer to the memory block to free.
+ void Free(void *pointer) {
+ DCHECK(pointer);
+ allocator_.Free(GetOffset(pointer));
+ }
+
+ // Frees a block of memory, pending the passage of a token. That memory won't
+ // be re-allocated until the token has passed through the command stream.
+ //
+ // Parameters:
+ // pointer: the pointer to the memory block to free.
+ // token: the token value to wait for before re-using the memory.
+ void FreePendingToken(void *pointer, unsigned int token) {
+ DCHECK(pointer);
+ allocator_.FreePendingToken(GetOffset(pointer), token);
+ }
+
+ // Gets a pointer to a memory block given the base memory and the offset.
+ // It translates FencedAllocator::kInvalidOffset to NULL.
+ void *GetPointer(FencedAllocator::Offset offset) {
+ return (offset == FencedAllocator::kInvalidOffset) ?
+ NULL : static_cast<char *>(base_) + offset;
+ }
+
+ // Gets the offset to a memory block given the base memory and the address.
+ // It translates NULL to FencedAllocator::kInvalidOffset.
+ FencedAllocator::Offset GetOffset(void *pointer) {
+ return pointer ? static_cast<char *>(pointer) - static_cast<char *>(base_) :
+ FencedAllocator::kInvalidOffset;
+ }
+
+ // Gets the size of the largest free block that is available without waiting.
+ unsigned int GetLargestFreeSize() {
+ return allocator_.GetLargestFreeSize();
+ }
+
+ // Gets the size of the largest free block that can be allocated if the
+ // caller can wait.
+ unsigned int GetLargestFreeOrPendingSize() {
+ return allocator_.GetLargestFreeOrPendingSize();
+ }
+
+ // Checks for consistency inside the book-keeping structures. Used for
+ // testing.
+ bool CheckConsistency() {
+ return allocator_.CheckConsistency();
+ }
+
+ FencedAllocator &allocator() { return allocator_; }
+
+ private:
+ FencedAllocator allocator_;
+ void *base_;
+ DISALLOW_IMPLICIT_CONSTRUCTORS(FencedAllocatorWrapper);
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+
+#endif // O3D_COMMAND_BUFFER_CLIENT_CROSS_FENCED_ALLOCATOR_H_
diff --git a/o3d/command_buffer/client/cross/fenced_allocator_test.cc b/o3d/command_buffer/client/cross/fenced_allocator_test.cc
new file mode 100644
index 0000000..93dedca
--- /dev/null
+++ b/o3d/command_buffer/client/cross/fenced_allocator_test.cc
@@ -0,0 +1,498 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the tests for the FencedAllocator class.
+
+#include "tests/common/win/testing_common.h"
+#include "command_buffer/client/cross/cmd_buffer_helper.h"
+#include "command_buffer/client/cross/fenced_allocator.h"
+#include "command_buffer/service/cross/cmd_buffer_engine.h"
+#include "command_buffer/service/cross/mocks.h"
+
+namespace o3d {
+namespace command_buffer {
+using testing::Return;
+using testing::Mock;
+using testing::Truly;
+using testing::Sequence;
+using testing::DoAll;
+using testing::Invoke;
+using testing::_;
+
+// Test fixture for FencedAllocator test - Creates a FencedAllocator, using a
+// CommandBufferHelper with a mock AsyncAPIInterface for its interface (calling
+// it directly, not through the RPC mechanism), making sure NOOPs are ignored
+// and SET_TOKEN are properly forwarded to the engine.
+class FencedAllocatorTest : public testing::Test {
+ public:
+ static const unsigned int kBufferSize = 1024;
+
+ protected:
+ virtual void SetUp() {
+ api_mock_.reset(new AsyncAPIMock);
+ // ignore noops in the mock - we don't want to inspect the internals of the
+ // helper.
+ EXPECT_CALL(*api_mock_, DoCommand(NOOP, 0, _))
+ .WillRepeatedly(Return(BufferSyncInterface::PARSE_NO_ERROR));
+ // Forward the SetToken calls to the engine
+ EXPECT_CALL(*api_mock(), DoCommand(SET_TOKEN, 1, _))
+ .WillRepeatedly(DoAll(Invoke(api_mock(), &AsyncAPIMock::SetToken),
+ Return(BufferSyncInterface::PARSE_NO_ERROR)));
+ engine_.reset(new CommandBufferEngine(api_mock_.get()));
+ api_mock_->set_engine(engine_.get());
+
+ nacl::SocketAddress client_address = { "test-socket" };
+ client_socket_ = nacl::BoundSocket(&client_address);
+ engine_->InitConnection();
+ helper_.reset(new CommandBufferHelper(engine_.get()));
+ helper_->Init(100);
+
+ allocator_.reset(new FencedAllocator(kBufferSize, helper_.get()));
+ }
+
+ virtual void TearDown() {
+ EXPECT_TRUE(allocator_->CheckConsistency());
+ allocator_.release();
+ helper_.release();
+ engine_->CloseConnection();
+ nacl::Close(client_socket_);
+ }
+
+ CommandBufferHelper *helper() { return helper_.get(); }
+ CommandBufferEngine *engine() { return engine_.get(); }
+ AsyncAPIMock *api_mock() { return api_mock_.get(); }
+ FencedAllocator *allocator() { return allocator_.get(); }
+ private:
+ scoped_ptr<AsyncAPIMock> api_mock_;
+ scoped_ptr<CommandBufferEngine> engine_;
+ scoped_ptr<CommandBufferHelper> helper_;
+ scoped_ptr<FencedAllocator> allocator_;
+ nacl::Handle client_socket_;
+};
+
+#ifndef COMPILER_MSVC
+const unsigned int FencedAllocatorTest::kBufferSize;
+#endif
+
+// Checks basic alloc and free.
+TEST_F(FencedAllocatorTest, TestBasic) {
+ allocator()->CheckConsistency();
+
+ const unsigned int kSize = 16;
+ FencedAllocator::Offset offset = allocator()->Alloc(kSize);
+ EXPECT_NE(FencedAllocator::kInvalidOffset, offset);
+ EXPECT_GE(kBufferSize, offset+kSize);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+
+ allocator()->Free(offset);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+}
+
+// Checks out-of-memory condition.
+TEST_F(FencedAllocatorTest, TestOutOfMemory) {
+ EXPECT_TRUE(allocator()->CheckConsistency());
+
+ const unsigned int kSize = 16;
+ const unsigned int kAllocCount = kBufferSize / kSize;
+ CHECK(kAllocCount * kSize == kBufferSize);
+
+ // Allocate several buffers to fill in the memory.
+ FencedAllocator::Offset offsets[kAllocCount];
+ for (unsigned int i = 0; i < kAllocCount; ++i) {
+ offsets[i] = allocator()->Alloc(kSize);
+ EXPECT_NE(FencedAllocator::kInvalidOffset, offsets[i]);
+ EXPECT_GE(kBufferSize, offsets[i]+kSize);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+ }
+
+ // This allocation should fail.
+ FencedAllocator::Offset offset_failed = allocator()->Alloc(kSize);
+ EXPECT_EQ(FencedAllocator::kInvalidOffset, offset_failed);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+
+ // Free one successful allocation, reallocate with half the size
+ allocator()->Free(offsets[0]);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+ offsets[0] = allocator()->Alloc(kSize/2);
+ EXPECT_NE(FencedAllocator::kInvalidOffset, offsets[0]);
+ EXPECT_GE(kBufferSize, offsets[0]+kSize);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+
+ // This allocation should fail as well.
+ offset_failed = allocator()->Alloc(kSize);
+ EXPECT_EQ(FencedAllocator::kInvalidOffset, offset_failed);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+
+ // Free up everything.
+ for (unsigned int i = 0; i < kAllocCount; ++i) {
+ allocator()->Free(offsets[i]);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+ }
+}
+
+// Checks the free-pending-token mechanism.
+TEST_F(FencedAllocatorTest, TestFreePendingToken) {
+ EXPECT_TRUE(allocator()->CheckConsistency());
+
+ const unsigned int kSize = 16;
+ const unsigned int kAllocCount = kBufferSize / kSize;
+ CHECK(kAllocCount * kSize == kBufferSize);
+
+ // Allocate several buffers to fill in the memory.
+ FencedAllocator::Offset offsets[kAllocCount];
+ for (unsigned int i = 0; i < kAllocCount; ++i) {
+ offsets[i] = allocator()->Alloc(kSize);
+ EXPECT_NE(FencedAllocator::kInvalidOffset, offsets[i]);
+ EXPECT_GE(kBufferSize, offsets[i]+kSize);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+ }
+
+ // This allocation should fail.
+ FencedAllocator::Offset offset_failed = allocator()->Alloc(kSize);
+ EXPECT_EQ(FencedAllocator::kInvalidOffset, offset_failed);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+
+ // Free one successful allocation, pending fence.
+ unsigned int token = helper()->InsertToken();
+ allocator()->FreePendingToken(offsets[0], token);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+
+ // The way we hooked up the helper and engine, it won't process commands
+ // until it has to wait for something. Which means the token shouldn't have
+ // passed yet at this point.
+ EXPECT_GT(token, engine()->GetToken());
+
+ // This allocation will need to reclaim the space freed above, so that should
+ // process the commands until the token is passed.
+ offsets[0] = allocator()->Alloc(kSize);
+ EXPECT_NE(FencedAllocator::kInvalidOffset, offsets[0]);
+ EXPECT_GE(kBufferSize, offsets[0]+kSize);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+ // Check that the token has indeed passed.
+ EXPECT_LE(token, engine()->GetToken());
+
+ // Free up everything.
+ for (unsigned int i = 0; i < kAllocCount; ++i) {
+ allocator()->Free(offsets[i]);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+ }
+}
+
+// Tests GetLargestFreeSize
+TEST_F(FencedAllocatorTest, TestGetLargestFreeSize) {
+ EXPECT_TRUE(allocator()->CheckConsistency());
+ EXPECT_EQ(kBufferSize, allocator()->GetLargestFreeSize());
+
+ FencedAllocator::Offset offset = allocator()->Alloc(kBufferSize);
+ ASSERT_NE(FencedAllocator::kInvalidOffset, offset);
+ EXPECT_EQ(0, allocator()->GetLargestFreeSize());
+ allocator()->Free(offset);
+ EXPECT_EQ(kBufferSize, allocator()->GetLargestFreeSize());
+
+ const unsigned int kSize = 16;
+ offset = allocator()->Alloc(kSize);
+ ASSERT_NE(FencedAllocator::kInvalidOffset, offset);
+ // The following checks that the buffer is allocated "smartly" - which is
+ // dependent on the implementation. But both first-fit or best-fit would
+ // ensure that.
+ EXPECT_EQ(kBufferSize - kSize, allocator()->GetLargestFreeSize());
+
+ // Allocate 2 more buffers (now 3), and then free the first two. This is to
+ // ensure a hole. Note that this is dependent on the first-fit current
+ // implementation.
+ FencedAllocator::Offset offset1 = allocator()->Alloc(kSize);
+ ASSERT_NE(FencedAllocator::kInvalidOffset, offset1);
+ FencedAllocator::Offset offset2 = allocator()->Alloc(kSize);
+ ASSERT_NE(FencedAllocator::kInvalidOffset, offset2);
+ allocator()->Free(offset);
+ allocator()->Free(offset1);
+ EXPECT_EQ(kBufferSize - 3 * kSize, allocator()->GetLargestFreeSize());
+
+ offset = allocator()->Alloc(kBufferSize - 3 * kSize);
+ ASSERT_NE(FencedAllocator::kInvalidOffset, offset);
+ EXPECT_EQ(2 * kSize, allocator()->GetLargestFreeSize());
+
+ offset1 = allocator()->Alloc(2 * kSize);
+ ASSERT_NE(FencedAllocator::kInvalidOffset, offset1);
+ EXPECT_EQ(0, allocator()->GetLargestFreeSize());
+
+ allocator()->Free(offset);
+ allocator()->Free(offset1);
+ allocator()->Free(offset2);
+}
+
+// Tests GetLargestFreeOrPendingSize
+TEST_F(FencedAllocatorTest, TestGetLargestFreeOrPendingSize) {
+ EXPECT_TRUE(allocator()->CheckConsistency());
+ EXPECT_EQ(kBufferSize, allocator()->GetLargestFreeOrPendingSize());
+
+ FencedAllocator::Offset offset = allocator()->Alloc(kBufferSize);
+ ASSERT_NE(FencedAllocator::kInvalidOffset, offset);
+ EXPECT_EQ(0, allocator()->GetLargestFreeOrPendingSize());
+ allocator()->Free(offset);
+ EXPECT_EQ(kBufferSize, allocator()->GetLargestFreeOrPendingSize());
+
+ const unsigned int kSize = 16;
+ offset = allocator()->Alloc(kSize);
+ ASSERT_NE(FencedAllocator::kInvalidOffset, offset);
+ // The following checks that the buffer is allocates "smartly" - which is
+ // dependent on the implementation. But both first-fit or best-fit would
+ // ensure that.
+ EXPECT_EQ(kBufferSize - kSize, allocator()->GetLargestFreeOrPendingSize());
+
+ // Allocate 2 more buffers (now 3), and then free the first two. This is to
+ // ensure a hole. Note that this is dependent on the first-fit current
+ // implementation.
+ FencedAllocator::Offset offset1 = allocator()->Alloc(kSize);
+ ASSERT_NE(FencedAllocator::kInvalidOffset, offset1);
+ FencedAllocator::Offset offset2 = allocator()->Alloc(kSize);
+ ASSERT_NE(FencedAllocator::kInvalidOffset, offset2);
+ allocator()->Free(offset);
+ allocator()->Free(offset1);
+ EXPECT_EQ(kBufferSize - 3 * kSize,
+ allocator()->GetLargestFreeOrPendingSize());
+
+ // Free the last one, pending a token.
+ unsigned int token = helper()->InsertToken();
+ allocator()->FreePendingToken(offset2, token);
+
+ // Now all the buffers have been freed...
+ EXPECT_EQ(kBufferSize, allocator()->GetLargestFreeOrPendingSize());
+ // .. but one is still waiting for the token.
+ EXPECT_EQ(kBufferSize - 3 * kSize,
+ allocator()->GetLargestFreeSize());
+
+ // The way we hooked up the helper and engine, it won't process commands
+ // until it has to wait for something. Which means the token shouldn't have
+ // passed yet at this point.
+ EXPECT_GT(token, engine()->GetToken());
+ // This allocation will need to reclaim the space freed above, so that should
+ // process the commands until the token is passed, but it will succeed.
+ offset = allocator()->Alloc(kBufferSize);
+ ASSERT_NE(FencedAllocator::kInvalidOffset, offset);
+ // Check that the token has indeed passed.
+ EXPECT_LE(token, engine()->GetToken());
+ allocator()->Free(offset);
+
+ // Everything now has been freed...
+ EXPECT_EQ(kBufferSize, allocator()->GetLargestFreeOrPendingSize());
+ // ... for real.
+ EXPECT_EQ(kBufferSize, allocator()->GetLargestFreeSize());
+}
+
+// Test fixture for FencedAllocatorWrapper test - Creates a
+// FencedAllocatorWrapper, using a CommandBufferHelper with a mock
+// AsyncAPIInterface for its interface (calling it directly, not through the
+// RPC mechanism), making sure NOOPs are ignored and SET_TOKEN are properly
+// forwarded to the engine.
+class FencedAllocatorWrapperTest : public testing::Test {
+ public:
+ static const unsigned int kBufferSize = 1024;
+
+ protected:
+ virtual void SetUp() {
+ api_mock_.reset(new AsyncAPIMock);
+ // ignore noops in the mock - we don't want to inspect the internals of the
+ // helper.
+ EXPECT_CALL(*api_mock_, DoCommand(NOOP, 0, _))
+ .WillRepeatedly(Return(BufferSyncInterface::PARSE_NO_ERROR));
+ // Forward the SetToken calls to the engine
+ EXPECT_CALL(*api_mock(), DoCommand(SET_TOKEN, 1, _))
+ .WillRepeatedly(DoAll(Invoke(api_mock(), &AsyncAPIMock::SetToken),
+ Return(BufferSyncInterface::PARSE_NO_ERROR)));
+ engine_.reset(new CommandBufferEngine(api_mock_.get()));
+ api_mock_->set_engine(engine_.get());
+
+ nacl::SocketAddress client_address = { "test-socket" };
+ client_socket_ = nacl::BoundSocket(&client_address);
+ engine_->InitConnection();
+ helper_.reset(new CommandBufferHelper(engine_.get()));
+ helper_->Init(100);
+
+ // Though allocating this buffer isn't strictly necessary, it makes
+ // allocations point to valid addresses, so they could be used for
+ // something.
+ buffer_.reset(new char[kBufferSize]);
+ allocator_.reset(new FencedAllocatorWrapper(kBufferSize, helper_.get(),
+ base()));
+ }
+
+ virtual void TearDown() {
+ EXPECT_TRUE(allocator_->CheckConsistency());
+ allocator_.release();
+ buffer_.release();
+ helper_.release();
+ engine_->CloseConnection();
+ nacl::Close(client_socket_);
+ }
+
+ CommandBufferHelper *helper() { return helper_.get(); }
+ CommandBufferEngine *engine() { return engine_.get(); }
+ AsyncAPIMock *api_mock() { return api_mock_.get(); }
+ FencedAllocatorWrapper *allocator() { return allocator_.get(); }
+ char *base() { return buffer_.get(); }
+ private:
+ scoped_ptr<AsyncAPIMock> api_mock_;
+ scoped_ptr<CommandBufferEngine> engine_;
+ scoped_ptr<CommandBufferHelper> helper_;
+ scoped_ptr<FencedAllocatorWrapper> allocator_;
+ scoped_array<char> buffer_;
+ nacl::Handle client_socket_;
+};
+
+#ifndef COMPILER_MSVC
+const unsigned int FencedAllocatorWrapperTest::kBufferSize;
+#endif
+
+// Checks basic alloc and free.
+TEST_F(FencedAllocatorWrapperTest, TestBasic) {
+ allocator()->CheckConsistency();
+
+ const unsigned int kSize = 16;
+ void *pointer = allocator()->Alloc(kSize);
+ ASSERT_TRUE(pointer);
+ EXPECT_LE(base(), static_cast<char *>(pointer));
+ EXPECT_GE(kBufferSize, static_cast<char *>(pointer) - base() + kSize);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+
+ allocator()->Free(pointer);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+
+ char *pointer_char = allocator()->AllocTyped<char>(kSize);
+ ASSERT_TRUE(pointer_char);
+ EXPECT_LE(base(), pointer_char);
+ EXPECT_GE(base() + kBufferSize, pointer_char + kSize);
+ allocator()->Free(pointer_char);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+
+ unsigned int *pointer_uint = allocator()->AllocTyped<unsigned int>(kSize);
+ ASSERT_TRUE(pointer_uint);
+ EXPECT_LE(base(), reinterpret_cast<char *>(pointer_uint));
+ EXPECT_GE(base() + kBufferSize,
+ reinterpret_cast<char *>(pointer_uint + kSize));
+
+ // Check that it did allocate kSize * sizeof(unsigned int). We can't tell
+ // directly, except from the remaining size.
+ EXPECT_EQ(kBufferSize - kSize * sizeof(*pointer_uint),
+ allocator()->GetLargestFreeSize());
+ allocator()->Free(pointer_uint);
+}
+
+// Checks out-of-memory condition.
+TEST_F(FencedAllocatorWrapperTest, TestOutOfMemory) {
+ allocator()->CheckConsistency();
+
+ const unsigned int kSize = 16;
+ const unsigned int kAllocCount = kBufferSize / kSize;
+ CHECK(kAllocCount * kSize == kBufferSize);
+
+ // Allocate several buffers to fill in the memory.
+ void *pointers[kAllocCount];
+ for (unsigned int i = 0; i < kAllocCount; ++i) {
+ pointers[i] = allocator()->Alloc(kSize);
+ EXPECT_TRUE(pointers[i]);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+ }
+
+ // This allocation should fail.
+ void *pointer_failed = allocator()->Alloc(kSize);
+ EXPECT_FALSE(pointer_failed);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+
+ // Free one successful allocation, reallocate with half the size
+ allocator()->Free(pointers[0]);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+ pointers[0] = allocator()->Alloc(kSize/2);
+ EXPECT_TRUE(pointers[0]);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+
+ // This allocation should fail as well.
+ pointer_failed = allocator()->Alloc(kSize);
+ EXPECT_FALSE(pointer_failed);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+
+ // Free up everything.
+ for (unsigned int i = 0; i < kAllocCount; ++i) {
+ allocator()->Free(pointers[i]);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+ }
+}
+
+// Checks the free-pending-token mechanism.
+TEST_F(FencedAllocatorWrapperTest, TestFreePendingToken) {
+ allocator()->CheckConsistency();
+
+ const unsigned int kSize = 16;
+ const unsigned int kAllocCount = kBufferSize / kSize;
+ CHECK(kAllocCount * kSize == kBufferSize);
+
+ // Allocate several buffers to fill in the memory.
+ void *pointers[kAllocCount];
+ for (unsigned int i = 0; i < kAllocCount; ++i) {
+ pointers[i] = allocator()->Alloc(kSize);
+ EXPECT_TRUE(pointers[i]);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+ }
+
+ // This allocation should fail.
+ void *pointer_failed = allocator()->Alloc(kSize);
+ EXPECT_FALSE(pointer_failed);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+
+ // Free one successful allocation, pending fence.
+ unsigned int token = helper()->InsertToken();
+ allocator()->FreePendingToken(pointers[0], token);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+
+ // The way we hooked up the helper and engine, it won't process commands
+ // until it has to wait for something. Which means the token shouldn't have
+ // passed yet at this point.
+ EXPECT_GT(token, engine()->GetToken());
+
+ // This allocation will need to reclaim the space freed above, so that should
+ // process the commands until the token is passed.
+ pointers[0] = allocator()->Alloc(kSize);
+ EXPECT_TRUE(pointers[0]);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+ // Check that the token has indeed passed.
+ EXPECT_LE(token, engine()->GetToken());
+
+ // Free up everything.
+ for (unsigned int i = 0; i < kAllocCount; ++i) {
+ allocator()->Free(pointers[i]);
+ EXPECT_TRUE(allocator()->CheckConsistency());
+ }
+}
+
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/client/cross/id_allocator.cc b/o3d/command_buffer/client/cross/id_allocator.cc
new file mode 100644
index 0000000..e13604f
--- /dev/null
+++ b/o3d/command_buffer/client/cross/id_allocator.cc
@@ -0,0 +1,87 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the implementation of IdAllocator.
+
+#include "command_buffer/client/cross/id_allocator.h"
+
+namespace o3d {
+namespace command_buffer {
+
+IdAllocator::IdAllocator() : bitmap_(1) { bitmap_[0] = 0; }
+
+static const unsigned int kBitsPerUint32 = sizeof(Uint32) * 8; // NOLINT
+
+// Looks for the first non-full entry, and return the first free bit in that
+// entry. If all the entries are full, it will return the first bit of an entry
+// that would be appended, but doesn't actually append that entry to the vector.
+unsigned int IdAllocator::FindFirstFree() const {
+ size_t size = bitmap_.size();
+ for (unsigned int i = 0; i < size; ++i) {
+ Uint32 value = bitmap_[i];
+ if (value != 0xffffffffU) {
+ for (unsigned int j = 0; j < kBitsPerUint32; ++j) {
+ if (!(value & (1 << j))) return i * kBitsPerUint32 + j;
+ }
+ DLOG(FATAL) << "Code should not reach here.";
+ }
+ }
+ return size*kBitsPerUint32;
+}
+
+// Sets the correct bit in the proper entry, resizing the vector if needed.
+void IdAllocator::SetBit(unsigned int bit, bool value) {
+ size_t size = bitmap_.size();
+ if (bit >= size * kBitsPerUint32) {
+ size_t newsize = bit / kBitsPerUint32 + 1;
+ bitmap_.resize(newsize);
+ for (size_t i = size; i < newsize; ++i) bitmap_[i] = 0;
+ }
+ Uint32 mask = 1U << (bit % kBitsPerUint32);
+ if (value) {
+ bitmap_[bit / kBitsPerUint32] |= mask;
+ } else {
+ bitmap_[bit / kBitsPerUint32] &= ~mask;
+ }
+}
+
+// Gets the bit from the proper entry. This doesn't resize the vector, just
+// returns false if the bit is beyond the last entry.
+bool IdAllocator::GetBit(unsigned int bit) const {
+ size_t size = bitmap_.size();
+ if (bit / kBitsPerUint32 >= size) return false;
+ Uint32 mask = 1U << (bit % kBitsPerUint32);
+ return (bitmap_[bit / kBitsPerUint32] & mask) != 0;
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/client/cross/id_allocator.h b/o3d/command_buffer/client/cross/id_allocator.h
new file mode 100644
index 0000000..26fe1f5
--- /dev/null
+++ b/o3d/command_buffer/client/cross/id_allocator.h
@@ -0,0 +1,80 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the definition of the IdAllocator class.
+
+#ifndef O3D_COMMAND_BUFFER_CLIENT_CROSS_ID_ALLOCATOR_H_
+#define O3D_COMMAND_BUFFER_CLIENT_CROSS_ID_ALLOCATOR_H_
+
+#include <vector>
+#include "base/basictypes.h"
+#include "command_buffer/common/cross/types.h"
+#include "command_buffer/common/cross/resource.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// A class to manage the allocation of resource IDs. It uses a bitfield stored
+// into a vector of unsigned ints.
+class IdAllocator {
+ public:
+ IdAllocator();
+
+ // Allocates a new resource ID.
+ command_buffer::ResourceID AllocateID() {
+ unsigned int bit = FindFirstFree();
+ SetBit(bit, true);
+ return bit;
+ }
+
+ // Frees a resource ID.
+ void FreeID(command_buffer::ResourceID id) {
+ SetBit(id, false);
+ }
+
+ // Checks whether or not a resource ID is in use.
+ bool InUse(command_buffer::ResourceID id) {
+ return GetBit(id);
+ }
+ private:
+ void SetBit(unsigned int bit, bool value);
+ bool GetBit(unsigned int bit) const;
+ unsigned int FindFirstFree() const;
+
+ std::vector<Uint32> bitmap_;
+ DISALLOW_COPY_AND_ASSIGN(IdAllocator);
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_CLIENT_CROSS_ID_ALLOCATOR_H_
diff --git a/o3d/command_buffer/client/cross/id_allocator_test.cc b/o3d/command_buffer/client/cross/id_allocator_test.cc
new file mode 100644
index 0000000..3cc2674
--- /dev/null
+++ b/o3d/command_buffer/client/cross/id_allocator_test.cc
@@ -0,0 +1,114 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file has the unit tests for the IdAllocator class.
+
+#include "tests/common/win/testing_common.h"
+#include "command_buffer/client/cross/id_allocator.h"
+
+namespace o3d {
+namespace command_buffer {
+
+using command_buffer::ResourceID;
+
+class IdAllocatorTest : public testing::Test {
+ protected:
+ virtual void SetUp() {}
+ virtual void TearDown() {}
+
+ IdAllocator* id_allocator() { return &id_allocator_; }
+
+ private:
+ IdAllocator id_allocator_;
+};
+
+// Checks basic functionality: AllocateID, FreeID, InUse.
+TEST_F(IdAllocatorTest, TestBasic) {
+ IdAllocator *allocator = id_allocator();
+ // Check that resource 0 is not in use
+ EXPECT_FALSE(allocator->InUse(0));
+
+ // Allocate an ID, check that it's in use.
+ ResourceID id1 = allocator->AllocateID();
+ EXPECT_TRUE(allocator->InUse(id1));
+
+ // Allocate another ID, check that it's in use, and different from the first
+ // one.
+ ResourceID id2 = allocator->AllocateID();
+ EXPECT_TRUE(allocator->InUse(id2));
+ EXPECT_NE(id1, id2);
+
+ // Free one of the IDs, check that it's not in use any more.
+ allocator->FreeID(id1);
+ EXPECT_FALSE(allocator->InUse(id1));
+
+ // Frees the other ID, check that it's not in use any more.
+ allocator->FreeID(id2);
+ EXPECT_FALSE(allocator->InUse(id2));
+}
+
+// Checks that the resource IDs are allocated conservatively, and re-used after
+// being freed.
+TEST_F(IdAllocatorTest, TestAdvanced) {
+ IdAllocator *allocator = id_allocator();
+
+ // Allocate a significant number of resources.
+ const int kNumResources = 100;
+ ResourceID ids[kNumResources];
+ for (int i = 0; i < kNumResources; ++i) {
+ ids[i] = allocator->AllocateID();
+ EXPECT_TRUE(allocator->InUse(ids[i]));
+ }
+
+ // Check that the allocation is conservative with resource IDs, that is that
+ // the resource IDs don't go over kNumResources - so that the service doesn't
+ // have to allocate too many internal structures when the resources are used.
+ for (int i = 0; i < kNumResources; ++i) {
+ EXPECT_GT(kNumResources, ids[i]);
+ }
+
+ // Check that the next resources are still free.
+ for (int i = 0; i < kNumResources; ++i) {
+ EXPECT_FALSE(allocator->InUse(kNumResources + i));
+ }
+
+ // Check that a new allocation re-uses the resource we just freed.
+ ResourceID id1 = ids[kNumResources / 2];
+ allocator->FreeID(id1);
+ EXPECT_FALSE(allocator->InUse(id1));
+ ResourceID id2 = allocator->AllocateID();
+ EXPECT_TRUE(allocator->InUse(id2));
+ EXPECT_EQ(id1, id2);
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/common/build.scons b/o3d/command_buffer/common/build.scons
new file mode 100644
index 0000000..0aefd76
--- /dev/null
+++ b/o3d/command_buffer/common/build.scons
@@ -0,0 +1,40 @@
+# Copyright 2009, Google Inc.
+# 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.
+
+
+Import('env')
+
+INPUTS = [
+ 'cross/buffer_sync_api.cc',
+ 'cross/resource.cc',
+ 'cross/rpc_imc.cc',
+]
+
+# Create a target library from the sources called 'o3dCmdBuf_common'
+o3dcmdbuf_lib = env.ComponentLibrary('o3dCmdBuf_common', INPUTS)
diff --git a/o3d/command_buffer/common/cross/bitfield_helpers.h b/o3d/command_buffer/common/cross/bitfield_helpers.h
new file mode 100644
index 0000000..09a4b2f
--- /dev/null
+++ b/o3d/command_buffer/common/cross/bitfield_helpers.h
@@ -0,0 +1,71 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains a helper template class used to access bit fields in
+// unsigned int_ts.
+
+#ifndef O3D_COMMAND_BUFFER_COMMON_CROSS_BITFIELD_HELPERS_H__
+#define O3D_COMMAND_BUFFER_COMMON_CROSS_BITFIELD_HELPERS_H__
+
+namespace o3d {
+namespace command_buffer {
+
+// Bitfield template class, used to access bit fields in unsigned int_ts.
+template<int shift, int length> class BitField {
+ public:
+ static const unsigned int kShift = shift;
+ static const unsigned int kLength = length;
+ // the following is really (1<<length)-1 but also work for length == 32
+ // without compiler warning.
+ static const unsigned int kMask = 1U + ((1U << (length-1)) - 1U) * 2U;
+
+ // Gets the value contained in this field.
+ static unsigned int Get(unsigned int container) {
+ return (container >> kShift) & kMask;
+ }
+
+ // Makes a value that can be or-ed into this field.
+ static unsigned int MakeValue(unsigned int value) {
+ return (value & kMask) << kShift;
+ }
+
+ // Changes the value of this field.
+ static void Set(unsigned int *container, unsigned int field_value) {
+ *container = (*container & ~(kMask << kShift)) | MakeValue(field_value);
+ }
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+
+#endif // O3D_COMMAND_BUFFER_COMMON_CROSS_BITFIELD_HELPERS_H__
diff --git a/o3d/command_buffer/common/cross/bitfield_helpers_test.cc b/o3d/command_buffer/common/cross/bitfield_helpers_test.cc
new file mode 100644
index 0000000..ab88de42
--- /dev/null
+++ b/o3d/command_buffer/common/cross/bitfield_helpers_test.cc
@@ -0,0 +1,68 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// Tests for the bitfield helper class.
+
+#include "gtest/gtest.h"
+#include "command_buffer/common/cross/bitfield_helpers.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// Tests that BitField<>::Get returns the right bits.
+TEST(BitFieldTest, TestGet) {
+ unsigned int value = 0x12345678;
+ EXPECT_EQ(0x8, (BitField<0, 4>::Get(value)));
+ EXPECT_EQ(0x45, (BitField<12, 8>::Get(value)));
+ EXPECT_EQ(0x12345678, (BitField<0, 32>::Get(value)));
+}
+
+// Tests that BitField<>::MakeValue generates the right bits.
+TEST(BitFieldTest, TestMakeValue) {
+ EXPECT_EQ(0x00000003, (BitField<0, 4>::MakeValue(0x3)));
+ EXPECT_EQ(0x00023000, (BitField<12, 8>::MakeValue(0x123)));
+ EXPECT_EQ(0x87654321, (BitField<0, 32>::MakeValue(0x87654321)));
+}
+
+// Tests that BitField<>::Set modifies the right bits.
+TEST(BitFieldTest, TestSet) {
+ unsigned int value = 0x12345678;
+ BitField<0, 4>::Set(&value, 0x9);
+ EXPECT_EQ(0x12345679, value);
+ BitField<12, 8>::Set(&value, 0x123);
+ EXPECT_EQ(0x12323679, value);
+ BitField<0, 32>::Set(&value, 0x87654321);
+ EXPECT_EQ(0x87654321, value);
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/common/cross/buffer_sync_api.cc b/o3d/command_buffer/common/cross/buffer_sync_api.cc
new file mode 100644
index 0000000..6679108
--- /dev/null
+++ b/o3d/command_buffer/common/cross/buffer_sync_api.cc
@@ -0,0 +1,43 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+#include "command_buffer/common/cross/buffer_sync_api.h"
+
+namespace o3d {
+namespace command_buffer {
+
+#ifndef COMPILER_MSVC
+const unsigned int BufferSyncInterface::kInvalidSharedMemoryId;
+#endif
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/common/cross/buffer_sync_api.h b/o3d/command_buffer/common/cross/buffer_sync_api.h
new file mode 100644
index 0000000..6892b20
--- /dev/null
+++ b/o3d/command_buffer/common/cross/buffer_sync_api.h
@@ -0,0 +1,168 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file defines the Command Buffer Synchronous API.
+
+#ifndef O3D_COMMAND_BUFFER_COMMON_CROSS_BUFFER_SYNC_API_H__
+#define O3D_COMMAND_BUFFER_COMMON_CROSS_BUFFER_SYNC_API_H__
+
+#include "command_buffer/common/cross/rpc.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// Command buffer type.
+typedef ptrdiff_t CommandBufferOffset;
+
+// Interface class for the Command Buffer Synchronous API.
+// This is the part of the command buffer API that is accessible through the
+// RPC mechanism, synchronously.
+class BufferSyncInterface {
+ public:
+ // Status of the command buffer service. It does not process commands
+ // (meaning: get will not change) unless in PARSING state.
+ enum ParserStatus {
+ NOT_CONNECTED, // The service is not connected - initial state.
+ NO_BUFFER, // The service is connected but no buffer was set.
+ PARSING, // The service is connected, and parsing commands from the
+ // buffer.
+ PARSE_ERROR, // Parsing stopped because a parse error was found.
+ };
+
+ enum ParseError {
+ PARSE_NO_ERROR,
+ PARSE_INVALID_SIZE,
+ PARSE_OUT_OF_BOUNDS,
+ PARSE_UNKNOWN_COMMAND,
+ PARSE_INVALID_ARGUMENTS,
+ };
+
+ // Invalid shared memory Id, returned by RegisterSharedMemory in case of
+ // failure.
+ static const unsigned int kInvalidSharedMemoryId = 0xffffffffU;
+
+ BufferSyncInterface() {}
+ virtual ~BufferSyncInterface() {}
+
+ // Initializes the connection with the client.
+ virtual void InitConnection() = 0;
+
+ // Closes the connection with the client.
+ virtual void CloseConnection() = 0;
+
+ // Registers a shared memory buffer. While a buffer is registered, it can be
+ // accessed by the service, including the underlying asynchronous API,
+ // through a single identifier.
+ // Parameters:
+ // buffer: the shared memory buffer handle.
+ // Returns:
+ // an identifier for the shared memory, or kInvalidSharedMemoryId in case
+ // of failure.
+ virtual unsigned int RegisterSharedMemory(RPCShmHandle buffer,
+ size_t size) = 0;
+
+ // Unregisters a shared memory buffer.
+ // Parameters:
+ // shm_id: the identifier for the shared memory buffer.
+ virtual void UnregisterSharedMemory(unsigned int shm_id) = 0;
+
+ // Initializes the command buffer.
+ // Parameters:
+ // shm_id: the registered memory buffer in which the command buffer
+ // resides.
+ // offset: the offset of the command buffer, relative to the memory
+ // buffer.
+ // size: the size of the command buffer.
+ // start_get: the inital value for the Get pointer, relative to the
+ // command buffer, where the parser will start interpreting
+ // commands. Put is also initialized to that value.
+ virtual void SetCommandBuffer(unsigned int shm_id,
+ ptrdiff_t offset,
+ size_t size,
+ CommandBufferOffset start_get) = 0;
+
+ // Sets the value of the Put pointer.
+ // Parameters:
+ // offset: the new value of the Put pointer, as an offset into the command
+ // buffer.
+ virtual void Put(CommandBufferOffset offset) = 0;
+
+ // Gets the value of the Get pointer.
+ // Returns:
+ // the current value of the Get pointer, as an offset into the command
+ // buffer.
+ virtual CommandBufferOffset Get() = 0;
+
+ // Gets the current token value.
+ // Returns:
+ // the current token value.
+ virtual unsigned int GetToken() = 0;
+
+ // Waits until Get changes from the currently known value.
+ // Parameters:
+ // current_value: the currently known value. This call will block until
+ // Get is different from that value (returning immediately
+ // if it is different).
+ // Returns:
+ // the current (changed) value of Get.
+ virtual CommandBufferOffset WaitGetChanges(
+ CommandBufferOffset current_value) = 0;
+
+ // Asks the service to signal the client when Get changes from the currently
+ // known value. This is a non-blocking version of WaitGetChanges.
+ // Parameters:
+ // current_value: the currently known value of Get.
+ // rpc_message_id: the RPC message ID to call on the client when Get is
+ // different from current_value. That RPC is called
+ // immediately if Get is already different from
+ // current_value.
+ virtual void SignalGetChanges(CommandBufferOffset current_value,
+ int rpc_message_id) = 0;
+
+ // Gets the status of the service.
+ // Returns:
+ // The status of the service.
+ virtual ParserStatus GetStatus() = 0;
+
+ // Gets the current parse error. The current parse error is set when the
+ // service is in the PARSE_ERROR status. It may also be set while in the
+ // PARSING state, if a recoverable error (like PARSE_UNKNOWN_METHOD) was
+ // encountered. Getting the error resets it to PARSE_NO_ERROR.
+ // Returns:
+ // The current parse error.
+ virtual ParseError GetParseError() = 0;
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_COMMON_CROSS_BUFFER_SYNC_API_H__
diff --git a/o3d/command_buffer/common/cross/cmd_buffer_format.h b/o3d/command_buffer/common/cross/cmd_buffer_format.h
new file mode 100644
index 0000000..b0b9386
--- /dev/null
+++ b/o3d/command_buffer/common/cross/cmd_buffer_format.h
@@ -0,0 +1,324 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the binary format definition of the command buffer.
+
+#ifndef O3D_COMMAND_BUFFER_COMMON_CROSS_CMD_BUFFER_FORMAT_H_
+#define O3D_COMMAND_BUFFER_COMMON_CROSS_CMD_BUFFER_FORMAT_H_
+
+#include "base/basictypes.h"
+#include "command_buffer/common/cross/types.h"
+#include "command_buffer/common/cross/bitfield_helpers.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// Struct that defines the command header in the command buffer.
+struct CommandHeader {
+ Uint32 size:8;
+ Uint32 command:24;
+};
+COMPILE_ASSERT(sizeof(CommandHeader) == 4, Sizeof_CommandHeader_is_not_4);
+
+// Union that defines possible command buffer entries.
+union CommandBufferEntry {
+ CommandHeader value_header;
+ Uint32 value_uint32;
+ Int32 value_int32;
+ float value_float;
+};
+
+COMPILE_ASSERT(sizeof(CommandBufferEntry) == 4,
+ Sizeof_CommandBufferEntry_is_not_4);
+
+// Bitfields for the SET_VERTEX_INPUT command.
+namespace set_vertex_input_cmd {
+// argument 4
+typedef BitField<0, 4> SemanticIndex;
+typedef BitField<4, 4> Semantic;
+typedef BitField<8, 8> Type;
+typedef BitField<16, 16> Stride;
+} // namespace set_vertex_input_cmd
+
+// Bitfields for the CREATE_TEXTURE_2D command.
+namespace create_texture_2d_cmd {
+// argument 1
+typedef BitField<0, 16> Width;
+typedef BitField<16, 16> Height;
+// argument 2
+typedef BitField<0, 4> Levels;
+typedef BitField<4, 4> Unused;
+typedef BitField<8, 8> Format;
+typedef BitField<16, 16> Flags;
+} // namespace create_texture_2d_cmd
+
+// Bitfields for the CREATE_TEXTURE_3D command.
+namespace create_texture_3d_cmd {
+// argument 1
+typedef BitField<0, 16> Width;
+typedef BitField<16, 16> Height;
+// argument 2
+typedef BitField<0, 16> Depth;
+typedef BitField<16, 16> Unused1;
+// argument 3
+typedef BitField<0, 4> Levels;
+typedef BitField<4, 4> Unused2;
+typedef BitField<8, 8> Format;
+typedef BitField<16, 16> Flags;
+} // namespace create_texture_3d_cmd
+
+// Bitfields for the CREATE_TEXTURE_CUBE command.
+namespace create_texture_cube_cmd {
+// argument 1
+typedef BitField<0, 16> Side;
+typedef BitField<16, 16> Unused1;
+// argument 2
+typedef BitField<0, 4> Levels;
+typedef BitField<4, 4> Unused2;
+typedef BitField<8, 8> Format;
+typedef BitField<16, 16> Flags;
+} // namespace create_texture_cube_cmd
+
+// Bitfields for the SET_TEXTURE_DATA command.
+namespace set_texture_data_cmd {
+// argument 1
+typedef BitField<0, 16> X;
+typedef BitField<16, 16> Y;
+// argument 2
+typedef BitField<0, 16> Width;
+typedef BitField<16, 16> Height;
+// argument 3
+typedef BitField<0, 16> Z;
+typedef BitField<16, 16> Depth;
+// argument 4
+typedef BitField<0, 4> Level;
+typedef BitField<4, 3> Face;
+typedef BitField<7, 25> Unused;
+} // namespace set_texture_data_cmd
+
+// Bitfields for the SET_TEXTURE_DATA_IMMEDIATE command.
+namespace set_texture_data_immediate_cmd {
+// argument 1
+typedef BitField<0, 16> X;
+typedef BitField<16, 16> Y;
+// argument 2
+typedef BitField<0, 16> Width;
+typedef BitField<16, 16> Height;
+// argument 3
+typedef BitField<0, 16> Z;
+typedef BitField<16, 16> Depth;
+// argument 4
+typedef BitField<0, 4> Level;
+typedef BitField<4, 3> Face;
+typedef BitField<7, 25> Unused;
+} // namespace set_texture_data_immediate_cmd
+
+// Bitfields for the GET_TEXTURE_DATA command.
+namespace get_texture_data_cmd {
+// argument 1
+typedef BitField<0, 16> X;
+typedef BitField<16, 16> Y;
+// argument 2
+typedef BitField<0, 16> Width;
+typedef BitField<16, 16> Height;
+// argument 3
+typedef BitField<0, 16> Z;
+typedef BitField<16, 16> Depth;
+// argument 4
+typedef BitField<0, 4> Level;
+typedef BitField<4, 3> Face;
+typedef BitField<7, 25> Unused;
+} // namespace get_texture_data_cmd
+
+// Bitfields for the SET_SAMPLER_STATES command.
+namespace set_sampler_states {
+// argument 2
+typedef BitField<0, 3> AddressingU;
+typedef BitField<3, 3> AddressingV;
+typedef BitField<6, 3> AddressingW;
+typedef BitField<9, 3> MagFilter;
+typedef BitField<12, 3> MinFilter;
+typedef BitField<15, 3> MipFilter;
+typedef BitField<18, 6> Unused;
+typedef BitField<24, 8> MaxAnisotropy;
+} // namespace get_texture_data_cmd
+
+namespace set_scissor {
+// argument 0
+typedef BitField<0, 15> X;
+typedef BitField<15, 1> Unused;
+typedef BitField<16, 15> Y;
+typedef BitField<31, 1> Enable;
+// argument 1
+typedef BitField<0, 16> Width;
+typedef BitField<16, 16> Height;
+} // namespace set_scissor
+
+namespace set_point_line_raster {
+// argument 0
+typedef BitField<0, 1> LineSmoothEnable;
+typedef BitField<1, 1> PointSpriteEnable;
+typedef BitField<2, 30> Unused;
+} // namespace set_point_line_raster
+
+namespace set_polygon_raster {
+// argument 0
+typedef BitField<0, 2> FillMode;
+typedef BitField<2, 2> CullMode;
+typedef BitField<4, 28> Unused;
+} // namespace set_polygon_raster
+
+namespace set_alpha_test {
+// argument 0
+typedef BitField<0, 3> Func;
+typedef BitField<3, 28> Unused;
+typedef BitField<31, 1> Enable;
+} // namespace set_alpha_test
+
+namespace set_depth_test {
+// argument 0
+typedef BitField<0, 3> Func;
+typedef BitField<3, 27> Unused;
+typedef BitField<30, 1> WriteEnable;
+typedef BitField<31, 1> Enable;
+} // namespace set_depth_test
+
+namespace set_stencil_test {
+// argument 0
+typedef BitField<0, 8> WriteMask;
+typedef BitField<8, 8> CompareMask;
+typedef BitField<16, 8> ReferenceValue;
+typedef BitField<24, 6> Unused0;
+typedef BitField<30, 1> SeparateCCW;
+typedef BitField<31, 1> Enable;
+// argument 1
+typedef BitField<0, 3> CWFunc;
+typedef BitField<3, 3> CWPassOp;
+typedef BitField<6, 3> CWFailOp;
+typedef BitField<9, 3> CWZFailOp;
+typedef BitField<12, 4> Unused1;
+typedef BitField<16, 3> CCWFunc;
+typedef BitField<19, 3> CCWPassOp;
+typedef BitField<22, 3> CCWFailOp;
+typedef BitField<25, 3> CCWZFailOp;
+typedef BitField<28, 4> Unused2;
+} // namespace set_stencil_test
+
+namespace set_color_write {
+// argument 0
+typedef BitField<0, 1> RedMask;
+typedef BitField<1, 1> GreenMask;
+typedef BitField<2, 1> BlueMask;
+typedef BitField<3, 1> AlphaMask;
+typedef BitField<0, 4> AllColorsMask; // alias for RGBA
+typedef BitField<4, 27> Unused;
+typedef BitField<31, 1> DitherEnable;
+} // namespace set_color_write
+
+namespace set_blending {
+// argument 0
+typedef BitField<0, 4> ColorSrcFunc;
+typedef BitField<4, 4> ColorDstFunc;
+typedef BitField<8, 3> ColorEq;
+typedef BitField<11, 5> Unused0;
+typedef BitField<16, 4> AlphaSrcFunc;
+typedef BitField<20, 4> AlphaDstFunc;
+typedef BitField<24, 3> AlphaEq;
+typedef BitField<27, 3> Unused1;
+typedef BitField<30, 1> SeparateAlpha;
+typedef BitField<31, 1> Enable;
+} // namespace set_blending
+
+// GAPI commands.
+enum CommandId {
+ NOOP, // No operation. Arbitrary argument size.
+ SET_TOKEN, // Sets token. 1 argument.
+ BEGIN_FRAME, // BeginFrame. 0 argument.
+ END_FRAME, // EndFrame. 0 argument.
+ CLEAR, // Clear. 7 arguments.
+ CREATE_VERTEX_BUFFER, // CreateVertexBuffer, 3 arguments.
+ DESTROY_VERTEX_BUFFER, // DestroyVertexBuffer. 1 argument.
+ SET_VERTEX_BUFFER_DATA, // SetVertexBufferData, 5 args
+ SET_VERTEX_BUFFER_DATA_IMMEDIATE, // SetVertexBufferData, 2 args + data
+ GET_VERTEX_BUFFER_DATA, // GetVertexBufferData, 5 args
+ CREATE_INDEX_BUFFER, // CreateIndexBuffer, 3 arguments.
+ DESTROY_INDEX_BUFFER, // DestroyIndexBuffer. 1 argument.
+ SET_INDEX_BUFFER_DATA, // SetIndexBufferData, 5 args
+ SET_INDEX_BUFFER_DATA_IMMEDIATE, // SetIndexBufferData, 2 args + data
+ GET_INDEX_BUFFER_DATA, // GetIndexBufferData, 5 args
+ CREATE_VERTEX_STRUCT, // CreateVertexStruct, 2 args.
+ DESTROY_VERTEX_STRUCT, // DestroyVertexStruct. 1 argument.
+ SET_VERTEX_INPUT, // SetVertexInput, 5 args.
+ SET_VERTEX_STRUCT, // SetVertexStruct, 1 arg.
+ DRAW, // Draw, 3 args.
+ DRAW_INDEXED, // DrawIndexed, 6 args.
+ CREATE_EFFECT, // CreateEffect, 4 args.
+ CREATE_EFFECT_IMMEDIATE, // CreateEffect, 2 args + data
+ DESTROY_EFFECT, // DestroyEffect, 1 arg.
+ SET_EFFECT, // SetEffect, 1 arg.
+ GET_PARAM_COUNT, // GetParamCount, 4 args.
+ CREATE_PARAM, // CreateParam, 3 args.
+ CREATE_PARAM_BY_NAME, // CreateParamByName, 5 args.
+ CREATE_PARAM_BY_NAME_IMMEDIATE, // CreateParamByName, 3 args + data
+ DESTROY_PARAM, // DestroyParam, 1 arg
+ SET_PARAM_DATA, // SetParamData, 4 args
+ SET_PARAM_DATA_IMMEDIATE, // SetParamData, 2 args + data
+ GET_PARAM_DESC, // GetParamDesc, 4 args
+ DESTROY_TEXTURE, // DestroyTexture, 1 arg
+ CREATE_TEXTURE_2D, // CreateTexture2D, 3 args
+ CREATE_TEXTURE_3D, // CreateTexture3D, 4 args
+ CREATE_TEXTURE_CUBE, // CreateTextureCube, 3 args
+ SET_TEXTURE_DATA, // SetTextureData, 10 args
+ SET_TEXTURE_DATA_IMMEDIATE, // SetTextureData, 8 args + data
+ GET_TEXTURE_DATA, // GetTextureData, 10 args
+ CREATE_SAMPLER, // CreateSampler, 1 arg
+ DESTROY_SAMPLER, // DestroySampler, 1 arg
+ SET_SAMPLER_STATES, // SetSamplerStates, 2 arg
+ SET_SAMPLER_BORDER_COLOR, // SetSamplerBorderColor, 5 arg
+ SET_SAMPLER_TEXTURE, // SetSamplerTexture, 2 arg
+ SET_VIEWPORT, // SetViewport. 6 arguments.
+ SET_SCISSOR, // SetScissor, 2 args
+ SET_POINT_LINE_RASTER, // SetPointLineRaster, 2 args
+ SET_POLYGON_RASTER, // SetPolygonRaster, 1 args
+ SET_POLYGON_OFFSET, // SetPolygonOffest, 2 args
+ SET_ALPHA_TEST, // SetAlphaTest, 2 args
+ SET_DEPTH_TEST, // SetDepthTest, 1 args
+ SET_STENCIL_TEST, // SetStencilTest, 2 args
+ SET_BLENDING, // SetBlending, 1 args
+ SET_BLENDING_COLOR, // SetBlendingColor, 4 args
+ SET_COLOR_WRITE, // SetColorWrite, 1 args
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_COMMON_CROSS_CMD_BUFFER_FORMAT_H_
diff --git a/o3d/command_buffer/common/cross/gapi_interface.h b/o3d/command_buffer/common/cross/gapi_interface.h
new file mode 100644
index 0000000..9531973
--- /dev/null
+++ b/o3d/command_buffer/common/cross/gapi_interface.h
@@ -0,0 +1,826 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the interface class for the low-level graphics API
+// (GAPI).
+
+#ifndef O3D_COMMAND_BUFFER_COMMON_CROSS_GAPI_INTERFACE_H__
+#define O3D_COMMAND_BUFFER_COMMON_CROSS_GAPI_INTERFACE_H__
+
+#include "command_buffer/common/cross/buffer_sync_api.h"
+#include "command_buffer/common/cross/resource.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// RBGA color definition.
+struct RGBA {
+ float red;
+ float green;
+ float blue;
+ float alpha;
+};
+
+// This class defines the low-level graphics API, as a pure interface class.
+class GAPIInterface {
+ public:
+ typedef BufferSyncInterface::ParseError ParseError;
+
+ GAPIInterface() {}
+ virtual ~GAPIInterface() {}
+
+ // Initializes the graphics context.
+ // Returns:
+ // true if successful.
+ virtual bool Initialize() = 0;
+
+ // Destroys the graphics context.
+ virtual void Destroy() = 0;
+
+ // Bit definitions for buffers to clear.
+ enum ClearBuffer {
+ COLOR = 0x1,
+ DEPTH = 0x2,
+ STENCIL = 0x4,
+ ALL_BUFFERS = COLOR | DEPTH | STENCIL
+ };
+
+ // Primitive type for Draw and DrawIndexed.
+ enum PrimitiveType {
+ POINTS,
+ LINES,
+ LINE_STRIPS,
+ TRIANGLES,
+ TRIANGLE_STRIPS,
+ TRIANGLE_FANS,
+ MAX_PRIMITIVE_TYPE
+ };
+
+ // Polygon mode for SetPolygonRaster
+ enum PolygonMode {
+ POLYGON_MODE_POINTS,
+ POLYGON_MODE_LINES,
+ POLYGON_MODE_FILL,
+ NUM_POLYGON_MODE
+ };
+
+ // Face culling mode for SetPolygonRaster
+ enum FaceCullMode {
+ CULL_NONE,
+ CULL_CW,
+ CULL_CCW,
+ NUM_FACE_CULL_MODE
+ };
+
+ // Comparison function for alpha or depth test
+ enum Comparison {
+ NEVER,
+ LESS,
+ EQUAL,
+ LEQUAL,
+ GREATER,
+ NOT_EQUAL,
+ GEQUAL,
+ ALWAYS,
+ NUM_COMPARISON
+ };
+
+ // Stencil operation
+ enum StencilOp {
+ KEEP,
+ ZERO,
+ REPLACE,
+ INC_NO_WRAP,
+ DEC_NO_WRAP,
+ INVERT,
+ INC_WRAP,
+ DEC_WRAP,
+ NUM_STENCIL_OP
+ };
+
+ // Blend Equation
+ enum BlendEq {
+ BLEND_EQ_ADD,
+ BLEND_EQ_SUB,
+ BLEND_EQ_REV_SUB,
+ BLEND_EQ_MIN,
+ BLEND_EQ_MAX,
+ NUM_BLEND_EQ
+ };
+
+ // Blend Funtion
+ enum BlendFunc {
+ BLEND_FUNC_ZERO,
+ BLEND_FUNC_ONE,
+ BLEND_FUNC_SRC_COLOR,
+ BLEND_FUNC_INV_SRC_COLOR,
+ BLEND_FUNC_SRC_ALPHA,
+ BLEND_FUNC_INV_SRC_ALPHA,
+ BLEND_FUNC_DST_ALPHA,
+ BLEND_FUNC_INV_DST_ALPHA,
+ BLEND_FUNC_DST_COLOR,
+ BLEND_FUNC_INV_DST_COLOR,
+ BLEND_FUNC_SRC_ALPHA_SATUTRATE,
+ BLEND_FUNC_BLEND_COLOR,
+ BLEND_FUNC_INV_BLEND_COLOR,
+ NUM_BLEND_FUNC
+ };
+
+ // Starts a frame. Rendering should occur between BeginFrame and EndFrame.
+ virtual void BeginFrame() = 0;
+
+ // Ends the frame, and bring the back buffer to front. Rendering should occur
+ // between BeginFrame and EndFrame.
+ virtual void EndFrame() = 0;
+
+ // Clear buffers, filling them with a constant value.
+ // Parameters:
+ // buffers: which buffers to clear. Can be a combination (bitwise or) of
+ // values from ClearBuffer.
+ // color: the RGBA color to clear the color target with.
+ // depth: the depth to clear the depth buffer with.
+ // stencil: the stencil value to clear the stencil buffer with.
+ virtual void Clear(unsigned int buffers,
+ const RGBA &color,
+ float depth,
+ unsigned int stencil) = 0;
+
+ // Creates a vertex buffer.
+ // Parameters:
+ // id: the resource ID for the new vertex buffer.
+ // size: the size of the vertex buffer, in bytes.
+ // flags: the vertex buffer flags, as a combination of vertex_buffer::Flags
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if invalid arguments are
+ // passed, BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError CreateVertexBuffer(ResourceID id,
+ unsigned int size,
+ unsigned int flags) = 0;
+
+ // Destroys a vertex buffer.
+ // Parameters:
+ // id: the resource ID of the vertex buffer.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if an invalid vertex buffer
+ // ID was passed, BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError DestroyVertexBuffer(ResourceID id) = 0;
+
+ // Sets data into a vertex buffer.
+ // Parameters:
+ // id: the resource ID of the vertex buffer.
+ // offset: the offset into the vertex buffer where to place the data.
+ // size: the size of the data.
+ // data: the source data.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if invalid arguments were
+ // passed: invalid resource ID, or offset or size out of range.
+ // BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError SetVertexBufferData(ResourceID id,
+ unsigned int offset,
+ unsigned int size,
+ const void *data) = 0;
+
+ // Gets data from a vertex buffer.
+ // Parameters:
+ // id: the resource ID of the vertex buffer.
+ // offset: the offset into the vertex buffer where to get the data.
+ // size: the size of the data.
+ // data: the destination buffer.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if invalid arguments were
+ // passed: invalid resource ID, or offset or size out of range.
+ // BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError GetVertexBufferData(ResourceID id,
+ unsigned int offset,
+ unsigned int size,
+ void *data) = 0;
+
+ // Creates an index buffer.
+ // Parameters:
+ // id: the resource ID for the new index buffer.
+ // size: the size of the index buffer, in bytes.
+ // flags: the index buffer flags, as a combination of index_buffer::Flags.
+ // Note that indices are 16 bits unless the index_buffer::INDEX_32BIT
+ // flag is specified.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if invalid arguments are
+ // passed, BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError CreateIndexBuffer(ResourceID id,
+ unsigned int size,
+ unsigned int flags) = 0;
+
+ // Destroys an index buffer.
+ // Parameters:
+ // id: the resource ID of the index buffer.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if an invalid index buffer
+ // ID was passed, BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError DestroyIndexBuffer(ResourceID id) = 0;
+
+ // Sets data into an index buffer.
+ // Parameters:
+ // id: the resource ID of the index buffer.
+ // offset: the offset into the index buffer where to place the data.
+ // size: the size of the data.
+ // data: the source data.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if invalid arguments were
+ // passed: invalid resource ID, or offset or size out of range.
+ // BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError SetIndexBufferData(ResourceID id,
+ unsigned int offset,
+ unsigned int size,
+ const void *data) = 0;
+
+ // Gets data from an index buffer.
+ // Parameters:
+ // id: the resource ID of the index buffer.
+ // offset: the offset into the index buffer where to get the data.
+ // size: the size of the data.
+ // data: the destination buffer.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if invalid arguments were
+ // passed: invalid resource ID, or offset or size out of range.
+ // BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError GetIndexBufferData(ResourceID id,
+ unsigned int offset,
+ unsigned int size,
+ void *data) = 0;
+
+ // Creates a vertex struct. A vertex struct describes the input vertex
+ // attribute streams.
+ // Parameters:
+ // id: the resource ID of the vertex struct.
+ // input_count: the number of input vertex attributes.
+ // returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if invalid arguments are
+ // passed, BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError CreateVertexStruct(ResourceID id,
+ unsigned int input_count) = 0;
+
+ // Destroys a vertex struct.
+ // Parameters:
+ // id: the resource ID of the vertex struct.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if an invalid vertex struct
+ // ID was passed, BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError DestroyVertexStruct(ResourceID id) = 0;
+
+ // Sets an input into a vertex struct.
+ // Parameters:
+ // vertex_struct_id: the resource ID of the vertex struct.
+ // input_index: the index of the input being set.
+ // vertex_buffer_id: the resource ID of the vertex buffer containing the
+ // data.
+ // offset: the offset into the vertex buffer of the input data, in bytes.
+ // stride: the stride of the input data, in bytes.
+ // type: the type of the input data.
+ // semantic: the semantic of the input.
+ // semantic_index: the semantic index of the input.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if invalid arguments are
+ // passed, BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError SetVertexInput(ResourceID vertex_struct_id,
+ unsigned int input_index,
+ ResourceID vertex_buffer_id,
+ unsigned int offset,
+ unsigned int stride,
+ vertex_struct::Type type,
+ vertex_struct::Semantic semantic,
+ unsigned int semantic_index) = 0;
+
+ // Sets the current vertex struct for drawing.
+ // Parameters:
+ // id: the resource ID of the vertex struct.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if invalid arguments are
+ // passed (invalid vertex struct), BufferSyncInterface::PARSE_NO_ERROR
+ // otherwise.
+ virtual ParseError SetVertexStruct(ResourceID id) = 0;
+
+ // Draws primitives, using the current vertex struct and the current effect.
+ // Parameters:
+ // primitive_type: the type of primitive to draw.
+ // first: the index of the first vertex.
+ // count: the number of primitives to draw.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if invalid arguments are
+ // passed, BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError Draw(PrimitiveType primitive_type,
+ unsigned int first,
+ unsigned int count) = 0;
+
+ // Draws primitives, using the current vertex struct and the current effect,
+ // as well as an index buffer.
+ // Parameters:
+ // primitive_type: the type of primitive to draw.
+ // index_buffer_id: the resource ID of the index buffer.
+ // first: the index into the index buffer of the first index to draw.
+ // count: the number of primitives to draw.
+ // min_index: the lowest index being drawn.
+ // max_index: the highest index being drawn.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if invalid arguments are
+ // passed, BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError DrawIndexed(PrimitiveType primitive_type,
+ ResourceID index_buffer_id,
+ unsigned int first,
+ unsigned int count,
+ unsigned int min_index,
+ unsigned int max_index) = 0;
+
+ // Creates an effect, from source code.
+ // Parameters:
+ // id: the resource ID of the effect.
+ // size: the size of data.
+ // data: the source code for the effect.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if invalid arguments are
+ // passed or the effect failed to compile,
+ // BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError CreateEffect(ResourceID id,
+ unsigned int size,
+ const void *data) = 0;
+
+ // Destroys an effect.
+ // Parameters:
+ // id: the resource ID of the effect.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if an invalid effect ID
+ // was passed, BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError DestroyEffect(ResourceID id) = 0;
+
+ // Sets the active effect for drawing.
+ // Parameters:
+ // id: the resource ID of the effect.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if invalid arguments are
+ // passed, BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError SetEffect(ResourceID id) = 0;
+
+ // Gets the number of parameters in an effect, returning it in a memory
+ // buffer as a Uint32.
+ // Parameters:
+ // id: the resource ID of the effect.
+ // size: the size of the data buffer. Must be at least 4 (the size of the
+ // Uint32).
+ // data: the buffer receiving the data.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if invalid arguments are
+ // passed, BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError GetParamCount(ResourceID id,
+ unsigned int size,
+ void *data) = 0;
+
+ // Creates an effect parameter by index.
+ // Parameters:
+ // param_id: the resource ID of the parameter being created.
+ // effect_id: the resource ID of the effect containing the parameter.
+ // data_type: the data type for the parameter. Must match the data type in
+ // the effect source.
+ // index: the index of the parameter.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if invalid arguments are
+ // passed, such as invalid effect ID, unmatching data type or invalid
+ // index, BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError CreateParam(ResourceID param_id,
+ ResourceID effect_id,
+ unsigned int index) = 0;
+
+ // Creates an effect parameter by name.
+ // Parameters:
+ // param_id: the resource ID of the parameter being created.
+ // effect_id: the resource ID of the effect containing the parameter.
+ // data_type: the data type for the parameter. Must match the data type in
+ // the effect source.
+ // size: the size of the parameter name.
+ // name: the parameter name, as an array of char. Doesn't have to be
+ // nul-terminated (though nul will terminate the string).
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if invalid arguments are
+ // passed, such as invalid effect ID, unmatching data type or no parameter
+ // was found with this name, BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError CreateParamByName(ResourceID param_id,
+ ResourceID effect_id,
+ unsigned int size,
+ const void *name) = 0;
+
+ // Destroys an effect parameter.
+ // Parameters:
+ // id: the resource ID of the parameter.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if an invalid parameter ID
+ // was passed, BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError DestroyParam(ResourceID id) = 0;
+
+ // Sets the effect parameter data.
+ // Parameters:
+ // id: the resource ID of the parameter.
+ // size: the size of the data. Must be at least the size of the parameter
+ // as described by its type.
+ // data: the parameter data.
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if invalid arguments are
+ // passed, such as invalid parameter ID, or unmatching data size,
+ // BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError SetParamData(ResourceID id,
+ unsigned int size,
+ const void *data) = 0;
+
+ // Gets the parameter description, storing it into a memory buffer. The
+ // parameter is described by a effect_param::Desc structure. The size must be
+ // at least the size of that structure. The name and semantic fields are only
+ // filled if the character strings fit into the memory buffer. In any case,
+ // the size field (in the effect_param::Desc) is filled with the size needed
+ // to fill in the structure, the name and the semantic (if any). Thus to get
+ // the complete information, GetParamDesc can be called twice, once to get
+ // the size, and, after allocating a big enough buffer, again to fill in the
+ // complete information including the text strings.
+ // Parameters:
+ // id: the resource ID of the parameter.
+ // size: the size of the memory buffer that wil receive the parameter
+ // description. Must be at least sizeof(effect_param::Desc).
+ // data: the memory buffer.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if invalid arguments are
+ // passed, such as invalid parameter ID, or unsufficient data size,
+ // BufferSyncInterface::PARSE_NO_ERROR otherwise. Note that
+ // BufferSyncInterface::PARSE_NO_ERROR will be returned if the structure
+ // itself fits, not necessarily the names. To make sure all the information
+ // is available, the caller should compare the returned size member of the
+ // effect_param::Desc structure to the size parameter passed in.
+ virtual ParseError GetParamDesc(ResourceID id,
+ unsigned int size,
+ void *data) = 0;
+
+ // Creates a 2D texture resource.
+ // Parameters:
+ // id: the resource ID of the texture.
+ // width: the texture width. Must be positive.
+ // height: the texture height. Must be positive.
+ // levels: the number of mipmap levels in the texture, or 0 to use the
+ // maximum.
+ // format: the format of the texels in the texture.
+ // flags: the texture flags, as a combination of texture::Flags.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if invalid arguments are
+ // passed, BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError CreateTexture2D(ResourceID id,
+ unsigned int width,
+ unsigned int height,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags) = 0;
+
+ // Creates a 3D texture resource.
+ // Parameters:
+ // id: the resource ID of the texture.
+ // width: the texture width. Must be positive.
+ // height: the texture height. Must be positive.
+ // depth: the texture depth. Must be positive.
+ // levels: the number of mipmap levels in the texture, or 0 to use the
+ // maximum.
+ // format: the format of the pixels in the texture.
+ // flags: the texture flags, as a combination of texture::Flags.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if invalid arguments are
+ // passed, BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError CreateTexture3D(ResourceID id,
+ unsigned int width,
+ unsigned int height,
+ unsigned int depth,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags) = 0;
+
+ // Creates a cube map texture resource.
+ // Parameters:
+ // id: the resource ID of the texture.
+ // side: the texture side length. Must be positive.
+ // levels: the number of mipmap levels in the texture, or 0 to use the
+ // maximum.
+ // format: the format of the pixels in the texture.
+ // flags: the texture flags, as a combination of texture::Flags.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if invalid arguments are
+ // passed, BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError CreateTextureCube(ResourceID id,
+ unsigned int side,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags) = 0;
+
+ // Sets texel data into a texture resource. This is a common function for
+ // each of the texture types, but some restrictions exist based on the
+ // texture type. The specified rectangle or volume of data, defined by x, y,
+ // width, height and possibly z and depth must fit into the selected mimmap
+ // level. Data is encoded by rows of 2D blocks, whose size depends on the
+ // texel format, usually 1x1 texel, but can be 4x4 for DXT* formats. See
+ // texture::GetBytesPerBlock, texture::GetBlockSizeX and
+ // texture::GetBlockSizeY.
+ // Parameters:
+ // id: the resource ID of the texture.
+ // x: the x position of the texel corresponding to the first byte of data.
+ // y: the y position of the texel corresponding to the first byte of data.
+ // z: the z position of the texel corresponding to the first byte of data.
+ // Must be 0 for non-3D textures.
+ // width: the width of the data rectangle/volume.
+ // height: the height of the data rectangle/volume.
+ // depth: the depth of the data volume. Must be 1 for non-3D textures.
+ // level: the mipmap level to put the data into.
+ // face: which face of the cube to put the data into. Is ignored for
+ // non-cube map textures.
+ // row_pitch: the number of bytes between two consecutive rows of blocks,
+ // in the source data.
+ // slice_pitch: the number of bytes between two consecutive slices of
+ // blocks, in the source data. Is ignored for non-3D textures.
+ // size: the size of the data.
+ // data: the texel data.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if invalid arguments are
+ // passed, for example invalid size, or out-of-bounds rectangle/volume,
+ // BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError SetTextureData(ResourceID id,
+ unsigned int x,
+ unsigned int y,
+ unsigned int z,
+ unsigned int width,
+ unsigned int height,
+ unsigned int depth,
+ unsigned int level,
+ texture::Face face,
+ unsigned int pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ const void *data) = 0;
+
+ // Gets texel data from a texture resource. This is a common function for
+ // each of the texture types, but some restrictions exist based on the
+ // texture type. The specified rectangle or volume of data, defined by x, y,
+ // width, height and possibly z and depth must fit into the selected mimmap
+ // level. Data is encoded by rows of 2D blocks, whose size depends on the
+ // texel format, usually 1x1 texel, but can be 4x4 for DXT* formats. See
+ // texture::GetBytesPerBlock, texture::GetBlockSizeX and
+ // texture::GetBlockSizeY.
+ // Parameters:
+ // id: the resource ID of the texture.
+ // x: the x position of the texel corresponding to the first byte of data.
+ // y: the y position of the texel corresponding to the first byte of data.
+ // z: the z position of the texel corresponding to the first byte of data.
+ // Must be 0 for non-3D textures.
+ // width: the width of the data rectangle/volume.
+ // height: the height of the data rectangle/volume.
+ // depth: the depth of the data volume. Must be 1 for non-3D textures.
+ // level: the mipmap level to put the data into.
+ // face: which face of the cube to put the data into. Is ignored for
+ // non-cube map textures.
+ // row_pitch: the number of bytes between two consecutive rows of blocks,
+ // in the destination buffer.
+ // slice_pitch: the number of bytes between two consecutive slices of
+ // blocks, in the destination buffer. Is ignored for non-3D textures.
+ // size: the size of the data.
+ // data: the destination buffer.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if invalid arguments are
+ // passed, for example invalid size, or out-of-bounds rectangle/volume,
+ // BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError GetTextureData(ResourceID id,
+ unsigned int x,
+ unsigned int y,
+ unsigned int z,
+ unsigned int width,
+ unsigned int height,
+ unsigned int depth,
+ unsigned int level,
+ texture::Face face,
+ unsigned int pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ void *data) = 0;
+
+ // Destroys a texture resource.
+ // Parameters:
+ // id: the resource ID of the texture.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if an invalid texture
+ // resource ID was passed, BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError DestroyTexture(ResourceID id) = 0;
+
+ // Creates a sampler resource.
+ // Parameters:
+ // id: the resource ID of the sampler.
+ // Returns:
+ // BufferSyncInterface::PARSE_NO_ERROR.
+ virtual ParseError CreateSampler(ResourceID id) = 0;
+
+ // Destroys a sampler resource.
+ // Parameters:
+ // id: the resource ID of the sampler.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if an invalid sampler
+ // resource ID was passed, BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError DestroySampler(ResourceID id) = 0;
+
+ // Sets the states in a sampler resource.
+ // Parameters:
+ // id: the resource ID of the sampler.
+ // addressing_u: the addressing mode for the U coordinate.
+ // addressing_v: the addressing mode for the V coordinate.
+ // addressing_w: the addressing mode for the W coordinate.
+ // mag_filter: the filtering mode when magnifying textures.
+ // min_filter: the filtering mode when minifying textures.
+ // mip_filter: the filtering mode for mip-map interpolation textures.
+ // max_anisotropy: the maximum anisotropy.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if an invalid sampler
+ // resource ID was passed, BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError SetSamplerStates(ResourceID id,
+ sampler::AddressingMode addressing_u,
+ sampler::AddressingMode addressing_v,
+ sampler::AddressingMode addressing_w,
+ sampler::FilteringMode mag_filter,
+ sampler::FilteringMode min_filter,
+ sampler::FilteringMode mip_filter,
+ unsigned int max_anisotropy) = 0;
+
+ // Sets the color of border pixels.
+ // Parameters:
+ // id: the resource ID of the sampler.
+ // color: the border color.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if an invalid sampler
+ // resource ID was passed, BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError SetSamplerBorderColor(ResourceID id,
+ const RGBA &color) = 0;
+
+ // Sets the texture resource used by a sampler resource.
+ // Parameters:
+ // id: the resource ID of the sampler.
+ // texture_id: the resource id of the texture.
+ // Returns:
+ // BufferSyncInterface::PARSE_INVALID_ARGUMENTS if an invalid sampler
+ // resource ID was passed, BufferSyncInterface::PARSE_NO_ERROR otherwise.
+ virtual ParseError SetSamplerTexture(ResourceID id,
+ ResourceID texture_id) = 0;
+
+ // Sets the viewport, and depth range.
+ // Parameters:
+ // x, y: upper left corner of the viewport.
+ // width, height: dimensions of the viewport.
+ // z_min, z_max: depth range.
+ virtual void SetViewport(unsigned int x,
+ unsigned int y,
+ unsigned int width,
+ unsigned int height,
+ float z_min,
+ float z_max) = 0;
+
+ // Sets the scissor test enable flag and rectangle.
+ // Parameters:
+ // enable: whether or not scissor test is enabled.
+ // x, y: upper left corner of the scissor rectangle.
+ // width, height: dimensions of the scissor rectangle.
+ virtual void SetScissor(bool enable,
+ unsigned int x,
+ unsigned int y,
+ unsigned int width,
+ unsigned int height) = 0;
+
+ // Sets the point and line rasterization state.
+ // Parameters:
+ // line_smooth: Whether or not line anti-aliasing is enabled.
+ // point_sprite: Whether or not point sprites are enabled.
+ // point_size: The point size.
+ virtual void SetPointLineRaster(bool line_smooth,
+ bool point_sprite,
+ float point_size) = 0;
+
+ // Sets the polygon rasterization state.
+ // Parameters:
+ // fill_mode: The polygon filling mode.
+ // cull_mode: The polygon face culling mode.
+ virtual void SetPolygonRaster(PolygonMode fill_mode,
+ FaceCullMode cull_mode) = 0;
+
+ // Sets the polygon offset state. Polygon offset is enabled if slope_factor
+ // or units is not 0.
+ // The applied offset (in window coordinates) is:
+ // o = max_slope * slope_factor + r * units
+ // Where max_slope is the maximum slope of the polygon (in window
+ // coordinates again), and r is the minimum resolvable z unit.
+ // Parameters:
+ // slope_factor: slope factor for the offset.
+ // units: constant factor for the offset.
+ virtual void SetPolygonOffset(float slope_factor, float units) = 0;
+
+ // Sets the alpha test states.
+ // Parameters:
+ // enable: alpha test enable state.
+ // reference: reference value for comparison.
+ // comp: alpha comparison function.
+ virtual void SetAlphaTest(bool enable,
+ float reference,
+ Comparison comp) = 0;
+
+ // Sets the depth test states.
+ // Note: if the depth test is disabled, z values are not written to the z
+ // buffer (i.e enable/ALWAYS is different from disable/*).
+ // Parameters:
+ // enable: depth test enable state.
+ // write_enable: depth write enable state.
+ // comp: depth comparison function.
+ virtual void SetDepthTest(bool enable,
+ bool write_enable,
+ Comparison comp) = 0;
+
+ // Sets the stencil test states.
+ // Parameters:
+ // enable: stencil test enable state.
+ // separate_ccw: whether or not counter-clockwise faces use separate
+ // functions/operations (2-sided stencil).
+ // write_mask: stencil write mask.
+ // compare_mask: stencil compare mask.
+ // ref: stencil reference value.
+ // func_ops: stencil test function and operations for both clockwise and
+ // counter-clockwise faces. This is a bitfield following the following
+ // description (little-endian addressing):
+ // bits 0 - 11: clockwise functions/operations
+ // bits 12 - 15: must be 0.
+ // bits 16 - 28: counter-clockwise functions/operations
+ // bits 29 - 32: must be 0.
+ virtual void SetStencilTest(bool enable,
+ bool separate_ccw,
+ unsigned int write_mask,
+ unsigned int compare_mask,
+ unsigned int ref,
+ Uint32 func_ops) = 0;
+
+ // Sets the color write paramters.
+ // Parameters:
+ // red: enable red write.
+ // green: enable green write.
+ // blue: enable blue write.
+ // alpha: enable alpha write.
+ // dither: enable dithering.
+ virtual void SetColorWrite(bool red,
+ bool green,
+ bool blue,
+ bool alpha,
+ bool dither) = 0;
+
+ // Sets the blending mode.
+ // Parameters:
+ // enable: whether or not to enable blending.
+ // separate_alpha: whether or not alpha uses separate Equation/Functions
+ // (if false, it uses the color ones).
+ // color_eq: the equation for blending of color values.
+ // color_src_func: the source function for blending of color values.
+ // color_dst_func: the destination function for blending of color values.
+ // alpha_eq: the equation for blending of alpha values.
+ // alpha_src_func: the source function for blending of alpha values.
+ // alpha_dst_func: the destination function for blending of alpha values.
+ virtual void SetBlending(bool enable,
+ bool separate_alpha,
+ BlendEq color_eq,
+ BlendFunc color_src_func,
+ BlendFunc color_dst_func,
+ BlendEq alpha_eq,
+ BlendFunc alpha_src_func,
+ BlendFunc alpha_dst_func) = 0;
+
+ // Sets the blending color.
+ virtual void SetBlendingColor(const RGBA &color) = 0;
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_COMMON_CROSS_GAPI_INTERFACE_H__
diff --git a/o3d/command_buffer/common/cross/logging.h b/o3d/command_buffer/common/cross/logging.h
new file mode 100644
index 0000000..7e249bc
--- /dev/null
+++ b/o3d/command_buffer/common/cross/logging.h
@@ -0,0 +1,67 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file abstracts differences in logging between NaCl and host
+// environment.
+
+#ifndef O3D_COMMAND_BUFFER_COMMON_CROSS_LOGGING_H_
+#define O3D_COMMAND_BUFFER_COMMON_CROSS_LOGGING_H_
+
+#ifndef __native_client__
+#include "base/logging.h"
+#else
+#include <sstream>
+
+// TODO: implement logging through nacl's debug service runtime if
+// available.
+#define CHECK(X) do {} while (0)
+#define CHECK_EQ(X, Y) do {} while (0)
+#define CHECK_NE(X, Y) do {} while (0)
+#define CHECK_GT(X, Y) do {} while (0)
+#define CHECK_GE(X, Y) do {} while (0)
+#define CHECK_LT(X, Y) do {} while (0)
+#define CHECK_LE(X, Y) do {} while (0)
+
+#define DCHECK(X) do {} while (0)
+#define DCHECK_EQ(X, Y) do {} while (0)
+#define DCHECK_NE(X, Y) do {} while (0)
+#define DCHECK_GT(X, Y) do {} while (0)
+#define DCHECK_GE(X, Y) do {} while (0)
+#define DCHECK_LT(X, Y) do {} while (0)
+#define DCHECK_LE(X, Y) do {} while (0)
+
+#define LOG(LEVEL) if (0) std::ostringstream()
+#define DLOG(LEVEL) if (0) std::ostringstream()
+
+#endif
+
+#endif // O3D_COMMAND_BUFFER_COMMON_CROSS_LOGGING_H_
diff --git a/o3d/command_buffer/common/cross/mocks.h b/o3d/command_buffer/common/cross/mocks.h
new file mode 100644
index 0000000..9573c6b
--- /dev/null
+++ b/o3d/command_buffer/common/cross/mocks.h
@@ -0,0 +1,148 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains definitions for mock objects, used for testing.
+
+// TODO: This file "manually" defines some mock objects. Using gMock
+// would be definitely preferable, unfortunately it doesn't work on Windows
+// yet.
+
+#ifndef O3D_COMMAND_BUFFER_COMMON_CROSS_MOCKS_H__
+#define O3D_COMMAND_BUFFER_COMMON_CROSS_MOCKS_H__
+
+#include <vector>
+#include "gmock/gmock.h"
+#include "command_buffer/common/cross/rpc.h"
+#include "command_buffer/common/cross/buffer_sync_api.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// Mocks a RPC send interface. This class only mocks SendCall currently.
+// Set call expectations with AddSendCallExpect: one for each call with exact
+// parameters, and desired return value, then run the test.
+class RPCSendInterfaceMock : public RPCSendInterface {
+ public:
+ RPCSendInterfaceMock() : called_(0) {}
+ virtual ~RPCSendInterfaceMock() { Check(); }
+
+ // Checks that the expected number of calls actually happened.
+ void Check() {
+ EXPECT_EQ(expects_.size(), called_);
+ }
+
+ // Struct describing a SendCall call expectation, with the desired return
+ // value.
+ struct SendCallExpect {
+ RPCImplInterface::ReturnValue _return;
+ int message_id;
+ const void * data;
+ size_t size;
+ RPCHandle * handles;
+ size_t handle_count;
+ };
+
+ // Adds an expectation for a SendCall call.
+ void AddSendCallExpect(const SendCallExpect &expect) {
+ expects_.push_back(expect);
+ }
+
+ // Mock SendCall implementation. This will check the arguments against the
+ // expected values (the values pointed by 'data' are compared, not the
+ // pointer), and return the desired return value.
+ virtual RPCImplInterface::ReturnValue SendCall(int message_id,
+ const void * data,
+ size_t size,
+ RPCHandle const *handles,
+ size_t handle_count) {
+ if (called_ < expects_.size()) {
+ const SendCallExpect &expect = expects_[called_];
+ ++called_;
+ EXPECT_EQ(expect.message_id, message_id);
+ EXPECT_EQ(expect.size, size);
+ if (expect.size != size) return 0;
+ EXPECT_EQ(expect.handle_count, handle_count);
+ if (expect.handle_count != handle_count) return 0;
+ if (size > 0) {
+ EXPECT_EQ(0, memcmp(expect.data, data, size));
+ } else {
+ EXPECT_FALSE(data);
+ }
+ if (handle_count > 0) {
+ for (unsigned int i = 0; i < handle_count; ++i) {
+ EXPECT_TRUE(expect.handles[i] == handles[i]);
+ }
+ } else {
+ EXPECT_FALSE(handles);
+ }
+ return expect._return;
+ } else {
+ ++called_;
+ // This is really an EXPECT_FALSE, but we get to display useful values.
+ EXPECT_GE(expects_.size(), called_);
+ // We need to return something but we don't know what, we don't have any
+ // expectation for this call. 0 will do.
+ return 0;
+ }
+ }
+ private:
+ size_t called_;
+ std::vector<SendCallExpect> expects_;
+};
+
+// Mocks a BufferSyncInterface, using GMock.
+class BufferSyncMock : public BufferSyncInterface {
+ public:
+ MOCK_METHOD0(InitConnection, void());
+ MOCK_METHOD0(CloseConnection, void());
+ MOCK_METHOD2(RegisterSharedMemory, unsigned int(RPCShmHandle buffer,
+ size_t size));
+ MOCK_METHOD1(UnregisterSharedMemory, void(unsigned int shm_id));
+ MOCK_METHOD4(SetCommandBuffer, void(unsigned int shm_id,
+ ptrdiff_t offset,
+ size_t size,
+ CommandBufferOffset start_get));
+ MOCK_METHOD1(Put, void(CommandBufferOffset offset));
+ MOCK_METHOD0(Get, CommandBufferOffset());
+ MOCK_METHOD0(GetToken, unsigned int());
+ MOCK_METHOD1(WaitGetChanges,
+ CommandBufferOffset(CommandBufferOffset current_value));
+ MOCK_METHOD2(SignalGetChanges, void(CommandBufferOffset current_value,
+ int rpc_message_id));
+ MOCK_METHOD0(GetStatus, ParserStatus());
+ MOCK_METHOD0(GetParseError, ParseError());
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_COMMON_CROSS_MOCKS_H__
diff --git a/o3d/command_buffer/common/cross/resource.cc b/o3d/command_buffer/common/cross/resource.cc
new file mode 100644
index 0000000..7619ba0
--- /dev/null
+++ b/o3d/command_buffer/common/cross/resource.cc
@@ -0,0 +1,113 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the implementation of the helper functions for resources.
+
+#include "command_buffer/common/cross/resource.h"
+
+namespace o3d {
+namespace command_buffer {
+
+namespace texture {
+
+// Gets the number of bytes per block for a given format.
+unsigned int GetBytesPerBlock(Format format) {
+ switch (format) {
+ case XRGB8:
+ case ARGB8:
+ return 4;
+ case ABGR16F:
+ return 8;
+ case DXT1:
+ return 8;
+ default:
+ LOG(FATAL) << "Invalid format";
+ return 1;
+ }
+}
+
+// Gets the width of a block for a given format.
+unsigned int GetBlockSizeX(Format format) {
+ switch (format) {
+ case XRGB8:
+ case ARGB8:
+ case ABGR16F:
+ return 1;
+ case DXT1:
+ return 4;
+ default:
+ LOG(FATAL) << "Invalid format";
+ return 1;
+ }
+}
+
+// Gets the height of a block for a given format.
+unsigned int GetBlockSizeY(Format format) {
+ // NOTE: currently only supported formats use square blocks.
+ return GetBlockSizeX(format);
+}
+
+} // namespace texture
+
+namespace effect_param {
+
+// Gets the size of the data of a given parameter type.
+unsigned int GetDataSize(DataType type) {
+ switch (type) {
+ case UNKNOWN:
+ return 0;
+ case FLOAT1:
+ return sizeof(float); // NOLINT
+ case FLOAT2:
+ return sizeof(float)*2; // NOLINT
+ case FLOAT3:
+ return sizeof(float)*3; // NOLINT
+ case FLOAT4:
+ return sizeof(float)*4; // NOLINT
+ case MATRIX4:
+ return sizeof(float)*16; // NOLINT
+ case INT:
+ return sizeof(int); // NOLINT
+ case BOOL:
+ return sizeof(bool); // NOLINT
+ case SAMPLER:
+ return sizeof(ResourceID); // NOLINT
+ default:
+ LOG(FATAL) << "Invalid type.";
+ return 0;
+ }
+}
+
+} // namespace effect_param
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/common/cross/resource.h b/o3d/command_buffer/common/cross/resource.h
new file mode 100644
index 0000000..cbdff26
--- /dev/null
+++ b/o3d/command_buffer/common/cross/resource.h
@@ -0,0 +1,208 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains definitions for resource flags, enums, and helper
+// functions.
+
+#ifndef O3D_COMMAND_BUFFER_COMMON_CROSS_RESOURCE_H__
+#define O3D_COMMAND_BUFFER_COMMON_CROSS_RESOURCE_H__
+
+#include <algorithm>
+#include "base/basictypes.h"
+#include "base/scoped_ptr.h"
+#include "command_buffer/common/cross/types.h"
+#include "command_buffer/common/cross/logging.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// A resource ID, key to the resource maps.
+typedef unsigned int ResourceID;
+// Invalid resource ID.
+static const ResourceID kInvalidResource = 0xffffffffU;
+
+namespace vertex_buffer {
+// Vertex buffer flags.
+enum Flags {
+ DYNAMIC = 0x01, // This vertex buffer is dynamic and is expected to have
+ // its data updated often.
+};
+} // namespace vertex_buffer
+
+namespace index_buffer {
+// Index buffer flags.
+enum Flags {
+ DYNAMIC = 0x01, // This index buffer is dynamic and is expected to have
+ // its data updated often.
+ INDEX_32BIT = 0x02, // Indices contained in this index buffer are 32 bits
+ // (unsigned int) instead of 16 bit (unsigned short).
+};
+} // namespace index_buffer
+
+namespace vertex_struct {
+// Semantics for input data.
+enum Semantic {
+ POSITION,
+ NORMAL,
+ COLOR,
+ TEX_COORD,
+ NUM_SEMANTICS
+};
+
+// Input data types.
+enum Type {
+ FLOAT1,
+ FLOAT2,
+ FLOAT3,
+ FLOAT4,
+ UCHAR4N,
+ NUM_TYPES
+};
+} // namespace vertex_struct
+
+namespace effect_param {
+enum DataType {
+ UNKNOWN, // A parameter exists in the effect, but the type is not
+ // representable (e.g. MATRIX3x4).
+ FLOAT1,
+ FLOAT2,
+ FLOAT3,
+ FLOAT4,
+ MATRIX4,
+ INT,
+ BOOL,
+ SAMPLER,
+ NUM_TYPES,
+ MAKE_32_BIT = 0x7fffffff,
+};
+COMPILE_ASSERT(sizeof(DataType) == 4, DataType_should_be_32_bits);
+
+// Gets the size of the data of a particular type.
+unsigned int GetDataSize(DataType type);
+
+// Structure describing a parameter, filled in by the
+// GAPIInterface::GetParamDesc call.
+struct Desc {
+ Uint32 size; // the total memory size needed for the complete
+ // description.
+ Uint32 name_offset; // the offset of the parameter name, relative to
+ // the beginning of the structure. May be 0 if the
+ // name doesn't fit into the memory buffer.
+ Uint32 name_size; // the size of the parameter name, including the
+ // terminating nul character. Will always be set
+ // even if the name doesn't fit into the buffer.
+ Uint32 semantic_offset; // the offset of the parameter semantic, relative
+ // to the beginning of the structure. May be 0 if
+ // the semantic doesn't fit into the memory
+ // buffer.
+ Uint32 semantic_size; // the size of the parameter semantic, including
+ // the terminating nul character. Will always be
+ // set even if the semantic doesn't fit into the
+ // buffer.
+ DataType data_type; // the data type of the parameter.
+ Uint32 data_size; // the size of the parameter data, in bytes.
+};
+} // namespace effect_param
+
+namespace texture {
+// Texture flags.
+enum Flags {
+ DYNAMIC = 0x01, // This texture is dynamic and is expected to have
+ // its data updated often.
+};
+
+// Texel formats.
+enum Format {
+ XRGB8,
+ ARGB8,
+ ABGR16F,
+ DXT1,
+ NUM_FORMATS
+};
+
+// Texture type.
+enum Type {
+ TEXTURE_2D,
+ TEXTURE_3D,
+ TEXTURE_CUBE,
+};
+
+// Cube map face.
+enum Face {
+ FACE_POSITIVE_X,
+ FACE_NEGATIVE_X,
+ FACE_POSITIVE_Y,
+ FACE_NEGATIVE_Y,
+ FACE_POSITIVE_Z,
+ FACE_NEGATIVE_Z,
+};
+
+// Gets the number of bytes per block for a given texture format. For most
+// texture formats, a block is 1x1 texels, but DXT* formats have 4x4 blocks.
+unsigned int GetBytesPerBlock(Format format);
+// Gets the x dimension of a texel block for a given texture format. For most
+// texture formats, a block is 1x1 texels, but DXT* formats have 4x4 blocks.
+unsigned int GetBlockSizeX(Format format);
+// Gets the y dimension of a texel block for a given texture format. For most
+// texture formats, a block is 1x1 texels, but DXT* formats have 4x4 blocks.
+unsigned int GetBlockSizeY(Format format);
+// Gets the dimension of a mipmap level given the dimension of the base
+// level. Every mipmap level is half the size of the previous level, rounding
+// down.
+static unsigned int GetMipMapDimension(unsigned int base,
+ unsigned int level) {
+ DCHECK_GT(base, 0);
+ return std::max(1U, base >> level);
+}
+} // namespace texture
+
+namespace sampler {
+enum AddressingMode {
+ WRAP,
+ MIRROR_REPEAT,
+ CLAMP_TO_EDGE,
+ CLAMP_TO_BORDER,
+ NUM_ADDRESSING_MODE
+};
+
+enum FilteringMode {
+ NONE,
+ POINT,
+ LINEAR,
+ NUM_FILTERING_MODE
+};
+} // namespace sampler
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_COMMON_CROSS_RESOURCE_H__
diff --git a/o3d/command_buffer/common/cross/rpc.h b/o3d/command_buffer/common/cross/rpc.h
new file mode 100644
index 0000000..d2e0d9f
--- /dev/null
+++ b/o3d/command_buffer/common/cross/rpc.h
@@ -0,0 +1,160 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+#ifndef O3D_COMMAND_BUFFER_COMMON_CROSS_RPC_H_
+#define O3D_COMMAND_BUFFER_COMMON_CROSS_RPC_H_
+
+#include "base/basictypes.h"
+
+#include "native_client/intermodule_comm/nacl_htp.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// Pre-defined message IDs.
+enum {
+ POISONED_MESSAGE_ID, // sent to kill the RPC server.
+ RESPONSE_ID, // sent as a response to a RPC call.
+};
+
+typedef nacl::HtpHandle RPCHandle;
+typedef RPCHandle RPCShmHandle;
+typedef RPCHandle RPCSocketHandle;
+static const RPCHandle kRPCInvalidHandle = nacl::kInvalidHtpHandle;
+
+// Interface for a RPC implementation. This class defines the calls a RPC
+// service needs to implement.
+class RPCImplInterface {
+ public:
+ // The type of return values for RPC calls. The RPC model is an arbitrary
+ // set of parameters, but a single return value.
+ typedef unsigned int ReturnValue;
+
+ RPCImplInterface() {}
+ virtual ~RPCImplInterface() {}
+
+ // De-multiplexes a RPC call. This function takes the message ID and the data
+ // to deduce a proper function to call, with its arguments, returning a
+ // single value. Most protocols will select the function from the message ID,
+ // and take the arguments from the data.
+ // Parameters:
+ // message_id: the RPC message ID.
+ // data: the RPC message payload.
+ // size: the size of the data.
+ // Returns:
+ // a single return value from the function called.
+ virtual ReturnValue DoCall(int message_id,
+ const void * data,
+ size_t size,
+ RPCHandle const *handles,
+ size_t handle_count) = 0;
+
+ private:
+ DISALLOW_COPY_AND_ASSIGN(RPCImplInterface);
+};
+
+class RPCSendInterface {
+ public:
+ virtual ~RPCSendInterface() {}
+ // Sends a call to the server thread. This call will be dispatched by the
+ // server thread to the RPC implementation. This call will block until the
+ // call is processed and the return value is sent back.
+ // Parameters:
+ // message_id: the RPC message ID.
+ // data: the RPC message payload.
+ // size: the size of the data.
+ // handles: an array of RPC handles to transmit
+ // handle_count: the number of RPC handles in the array
+ // Returns:
+ // the return value of the RPC call.
+ virtual RPCImplInterface::ReturnValue SendCall(int message_id,
+ const void * data,
+ size_t size,
+ RPCHandle const *handles,
+ size_t handle_count) = 0;
+};
+
+class RPCProcessInterface {
+ public:
+ virtual ~RPCProcessInterface() {}
+ // Processes one message, blocking if necessary until a message is available
+ // or the server is killed. This will dispatch the received message to the
+ // RPC implementation, and send back a response message with the return
+ // value to the client.
+ // Returns:
+ // false if the server was killed.
+ virtual bool ProcessMessage() = 0;
+
+ // Checks whether a message is available for processing - allowing to test if
+ // ProcessMessage will block.
+ // Returns:
+ // true if a message is available.
+ virtual bool HasMessage() = 0;
+};
+
+// Creates a RPCSendInterface from a RPCSocketHandle.
+RPCSendInterface *MakeSendInterface(RPCSocketHandle handle);
+
+// Creates a shared memory buffer.
+// Parameters:
+// size: the size of the buffer.
+// Returns:
+// the handle to the shared memory buffer.
+RPCShmHandle CreateShm(size_t size);
+
+// Destroys a shared memory buffer.
+// Parameters:
+// handle: the handle to the shared memory buffer.
+void DestroyShm(RPCShmHandle handle);
+
+// Maps a shared memory buffer into the address space.
+// Parameters:
+// handle: the handle to the shared memory buffer.
+// size: the size of the region to map in the memory buffer. May be smaller
+// than the shared memory region, but the underlying implementation
+// will round it up to the page size or the whole shared memory.
+// Returns:
+// the address of the mapped region, or NULL if failure.
+void *MapShm(RPCShmHandle handle, size_t size);
+
+// Unmaps a previously mapped memory buffer.
+// Parameters:
+// address: the address of the mapped region.
+// size: the size of the region to un-map. It can be a subset of the
+// previously mapped region, but the underlying implementation will
+// round it up to the page size.
+void UnmapShm(void *address, size_t size);
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_COMMON_CROSS_RPC_H_
diff --git a/o3d/command_buffer/common/cross/rpc_fake.cc b/o3d/command_buffer/common/cross/rpc_fake.cc
new file mode 100644
index 0000000..ed09b90
--- /dev/null
+++ b/o3d/command_buffer/common/cross/rpc_fake.cc
@@ -0,0 +1,226 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+#include <windows.h>
+#include "command_buffer/common/cross/rpc_fake.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// Create the queue, initializing the synchronization structures: a mutex for
+// the queue itself, and an event to signal the consumers.
+RPCQueue::RPCQueue() {
+ event_ = ::CreateEvent(NULL, FALSE, FALSE, NULL);
+ ::InitializeCriticalSection(&mutex_);
+}
+
+RPCQueue::~RPCQueue() {
+ ::DeleteCriticalSection(&mutex_);
+ ::CloseHandle(event_);
+}
+
+// Adds a message into the queue. Signal waiting threads that a new message is
+// available.
+void RPCQueue::AddMessage(const RPCMessage &call) {
+ ::EnterCriticalSection(&mutex_);
+ queue_.push(call);
+ ::SetEvent(event_);
+ ::LeaveCriticalSection(&mutex_);
+}
+
+// Checks whether the queue is empty.
+bool RPCQueue::IsEmpty() {
+ ::EnterCriticalSection(&mutex_);
+ bool result = queue_.empty();
+ ::LeaveCriticalSection(&mutex_);
+ return result;
+}
+
+// Gets a message, waiting for one if the queue is empty.
+void RPCQueue::GetMessage(RPCMessage *message) {
+ ::EnterCriticalSection(&mutex_);
+ while (queue_.empty()) {
+ ::LeaveCriticalSection(&mutex_);
+ ::WaitForSingleObject(event_, INFINITE);
+ ::EnterCriticalSection(&mutex_);
+ }
+ *message = queue_.front();
+ queue_.pop();
+ ::LeaveCriticalSection(&mutex_);
+}
+
+// Tries to gets a message, returning immediately if the queue is empty.
+bool RPCQueue::TryGetMessage(RPCMessage *message) {
+ ::EnterCriticalSection(&mutex_);
+ bool result = !queue_.empty();
+ if (result) {
+ *message = queue_.front();
+ queue_.pop();
+ }
+ ::LeaveCriticalSection(&mutex_);
+ return result;
+}
+
+// Creates the RPC server. The RPC server uses 2 RPC Queues, one for "incoming"
+// calls (in_queue_), and one for "outgoing" return values (out_queue_).
+RPCServer::RPCServer(RPCImplInterface * impl) {
+ sender_.reset(new Sender(&in_queue_, &out_queue_));
+ processor_.reset(new Processor(&in_queue_, &out_queue_, impl));
+}
+
+RPCServer::~RPCServer() {}
+
+// Allocates the data for a message, if needed. Initializes the RPCMessage
+// structure.
+void RPCServer::AllocMessage(int message_id,
+ const void *data,
+ size_t size,
+ RPCHandle const *handles,
+ size_t handle_count,
+ RPCMessage *message) {
+ message->message_id = message_id;
+ message->size = size;
+ message->handle_count = handle_count;
+ if (data) {
+ message->data = malloc(size);
+ memcpy(message->data, data, size);
+ } else {
+ DCHECK(size == 0);
+ message->data = NULL;
+ }
+ if (handles) {
+ DCHECK(handle_count > 0);
+ message->handles = new RPCHandle[handle_count];
+ for (unsigned int i = 0; i < handle_count; ++i)
+ message->handles[i] = handles[i];
+ } else {
+ DCHECK(handle_count == 0);
+ message->handles = NULL;
+ }
+}
+
+// Destroys the message data if needed.
+void RPCServer::DestroyMessage(RPCMessage *message) {
+ if (message->data) free(message->data);
+ if (message->handles) delete [] message->handles;
+}
+
+// Processes one message, getting one from the incoming queue (blocking),
+// dispatching it to the implementation (if not the "poisoned" message), and
+// adding the return value to the outgoing queue.
+bool RPCServer::Processor::ProcessMessage() {
+ RPCMessage input;
+ in_queue_->GetMessage(&input);
+ RPCImplInterface::ReturnValue result = 0;
+ int continue_processing = true;
+ if (input.message_id == POISONED_MESSAGE_ID) {
+ continue_processing = false;
+ } else {
+ result = impl_->DoCall(input.message_id, input.data, input.size,
+ input.handles, input.handle_count);
+ }
+ DestroyMessage(&input);
+
+ RPCMessage output;
+ AllocMessage(RESPONSE_ID, &result, sizeof(result), NULL, 0, &output);
+ out_queue_->AddMessage(output);
+ return continue_processing;
+}
+
+// Checks if the incoming queue is empty.
+bool RPCServer::Processor::HasMessage() {
+ return !in_queue_->IsEmpty();
+}
+
+// Processes all messages until the server is killed.
+void RPCServer::MessageLoop() {
+ do {} while (processor_->ProcessMessage());
+}
+
+// Sends a "poisoned" call to the server thread, making it exit the processing
+// loop.
+void RPCServer::KillServer() {
+ sender_->SendCall(POISONED_MESSAGE_ID, NULL, 0, NULL, 0);
+}
+
+// Sends a call to the server thread. This puts a message into the "incoming"
+// queue, and waits for the return message on the "outgoing" queue.
+RPCImplInterface::ReturnValue RPCServer::Sender::SendCall(
+ int message_id,
+ const void * data,
+ size_t size,
+ RPCHandle const *handles,
+ size_t handle_count) {
+ RPCMessage input;
+ AllocMessage(message_id, data, size, handles, handle_count, &input);
+ in_queue_->AddMessage(input);
+
+ RPCMessage output;
+ out_queue_->GetMessage(&output);
+ DCHECK(output.message_id == RESPONSE_ID);
+ DCHECK(output.size == sizeof(RPCImplInterface::ReturnValue));
+ RPCImplInterface::ReturnValue result =
+ *(reinterpret_cast<RPCImplInterface::ReturnValue *>(output.data));
+ DestroyMessage(&output);
+ return result;
+}
+
+class RPCSendProxy : public RPCSendInterface {
+ public:
+ explicit RPCSendProxy(RPCSendInterface *interface) : interface_(interface) {}
+ virtual ~RPCSendProxy() {}
+ virtual RPCImplInterface::ReturnValue SendCall(int message_id,
+ const void * data,
+ size_t size,
+ RPCHandle const *handles,
+ size_t handle_count) {
+ return interface_->SendCall(message_id, data, size, handles, handle_count);
+ }
+ private:
+ RPCSendInterface *interface_;
+};
+
+// Create a proxy so that it can be managed as a separate object, to have the
+// same semantics as the IMC implementation.
+RPCSendInterface *MakeSendInterface(RPCSocketHandle handle) {
+ return new RPCSendProxy(handle->GetSendInterface());
+}
+
+void *MapShm(RPCShmHandle handle, size_t size) {
+ return (size <= handle->size) ? return handle->address : NULL;
+}
+
+void UnmapShm(void * address, size_t size) {
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/common/cross/rpc_fake.h b/o3d/command_buffer/common/cross/rpc_fake.h
new file mode 100644
index 0000000..c7727c5
--- /dev/null
+++ b/o3d/command_buffer/common/cross/rpc_fake.h
@@ -0,0 +1,205 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file defines classes faking the NativeClient RPC mechanism. This is
+// intended as a temporary replacement of NativeClient until it is ready. It
+// assumes the various clients and services run in separate threads of the same
+// process.
+
+#ifndef O3D_COMMAND_BUFFER_COMMON_CROSS_RPC_FAKE_H_
+#define O3D_COMMAND_BUFFER_COMMON_CROSS_RPC_FAKE_H_
+
+#include <windows.h>
+#include <queue>
+#include "core/cross/types.h"
+#include "command_buffer/common/cross/rpc.h"
+
+namespace o3d {
+namespace command_buffer {
+
+typedef CRITICAL_SECTION Mutex;
+typedef HANDLE Event;
+
+// Struct describing a RPC message, as a message ID and a data payload.
+// It "owns" the data pointer.
+struct RPCMessage {
+ int message_id;
+ size_t size;
+ void *data;
+ RPCHandle *handles;
+ size_t handle_count;
+};
+
+// Implementation of a (thread-safe) RPC message queue (FIFO). It allows simply
+// to enqueue and dequeue messages, in a blocking or non-blocking fashion.
+class RPCQueue {
+ public:
+ RPCQueue();
+ ~RPCQueue();
+
+ // Adds a message into the back of the queue.
+ // Parameters:
+ // message: the message to enqueue. Ownership of the message data is taken
+ // by the queue.
+ void AddMessage(const RPCMessage &message);
+
+ // Tests whether or not the queue is empty.
+ // Returns:
+ // true if the queue is empty.
+ bool IsEmpty();
+
+ // Gets a message from the front of the queue. This call blocks until a
+ // message is available in the queue.
+ // Parameters:
+ // message: a pointer to a RPCMessage structure receiving the message.
+ // That structure takes ownership of the message data.
+ void GetMessage(RPCMessage *message);
+
+ // Try to get a message from the front of the queue, if any. This call will
+ // not block if the queue is empty.
+ // Parameters:
+ // message: a pointer to a RPCMessage structure receiving the message, if
+ // any. That structure takes ownership of the message data. If no
+ // message is available, that structure is unchanged.
+ // Returns:
+ // true if a message was available.
+ bool TryGetMessage(RPCMessage *message);
+
+ private:
+ std::queue<RPCMessage> queue_;
+ Mutex mutex_;
+ Event event_;
+
+ DISALLOW_COPY_AND_ASSIGN(RPCQueue);
+};
+
+// Implements a fake RPC server interface. This class is intended to be used
+// across different threads (it is thread safe):
+// - one server thread, that processes messages (using MessageLoop() or
+// ProcessMessage()), to execute the RPC calls.
+// - one or several client threads, that can send RPC calls to it.
+//
+// One of the client threads can "kill" the server so that it exits its
+// processing loop.
+class RPCServer {
+ public:
+ explicit RPCServer(RPCImplInterface *impl);
+ ~RPCServer();
+
+ // Server thread functions
+
+ // Processes all messages, until the server is killed.
+ void MessageLoop();
+ RPCProcessInterface *GetProcessInterface() { return processor_.get(); }
+
+ // client thread functions
+ RPCSendInterface *GetSendInterface() { return sender_.get(); }
+
+ // Kills the server thread, making it exit its processing loop. This call
+ // will block until the server has finished processing all the previous
+ // messages.
+ void KillServer();
+
+ private:
+ static void AllocMessage(int message_id,
+ const void * data,
+ size_t size,
+ RPCHandle const *handles,
+ size_t handle_count,
+ RPCMessage *message);
+ static void DestroyMessage(RPCMessage *message);
+
+ class Sender : public RPCSendInterface {
+ public:
+ Sender(RPCQueue *in_queue, RPCQueue *out_queue)
+ : in_queue_(in_queue),
+ out_queue_(out_queue) {}
+ // Sends a call to the server thread. This call will be dispatched by the
+ // server thread to the RPC implementation. This call will block until the
+ // call is processed and the return value is sent back.
+ // Parameters:
+ // message_id: the RPC message ID.
+ // data: the RPC message payload.
+ // size: the size of the data.
+ // handles: an array of RPC handles to transmit
+ // handle_count: the number of RPC handles in the array
+ // Returns:
+ // the return value of the RPC call.
+ virtual RPCImplInterface::ReturnValue SendCall(int message_id,
+ const void * data,
+ size_t size,
+ RPCHandle const *handles,
+ size_t handle_count);
+ private:
+ RPCQueue *in_queue_;
+ RPCQueue *out_queue_;
+ DISALLOW_COPY_AND_ASSIGN(Sender);
+ };
+
+ class Processor : public RPCProcessInterface {
+ public:
+ Processor(RPCQueue *in_queue, RPCQueue *out_queue, RPCImplInterface *impl)
+ : in_queue_(in_queue),
+ out_queue_(out_queue),
+ impl_(impl) {}
+ virtual ~Processor() {}
+ // Processes one message, blocking if necessary until a message is available
+ // or the server is killed. This will dispatch the received message to the
+ // RPC implementation, and send back a response message with the return
+ // value to the client.
+ // Returns:
+ // false if the server was killed.
+ virtual bool ProcessMessage();
+
+ // Checks whether a message is available for processing - allowing to test
+ // if ProcessMessage will block.
+ // Returns:
+ // true if a message is available.
+ virtual bool HasMessage();
+ private:
+ RPCQueue *in_queue_;
+ RPCQueue *out_queue_;
+ RPCImplInterface *impl_;
+ DISALLOW_COPY_AND_ASSIGN(Processor);
+ };
+
+ RPCQueue in_queue_;
+ RPCQueue out_queue_;
+ scoped_ptr<Sender> sender_;
+ scoped_ptr<Processor> processor_;
+ DISALLOW_COPY_AND_ASSIGN(RPCServer);
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_COMMON_CROSS_RPC_FAKE_H_
diff --git a/o3d/command_buffer/common/cross/rpc_imc.cc b/o3d/command_buffer/common/cross/rpc_imc.cc
new file mode 100644
index 0000000..1fcb9c7
--- /dev/null
+++ b/o3d/command_buffer/common/cross/rpc_imc.cc
@@ -0,0 +1,231 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+#include <algorithm>
+#include "command_buffer/common/cross/logging.h"
+#include "command_buffer/common/cross/rpc_imc.h"
+#include "native_client/intermodule_comm/nacl_htp.h"
+
+namespace o3d {
+namespace command_buffer {
+
+int NaclSendData(nacl::HtpHandle channel,
+ const void *data,
+ size_t size,
+ int flags) {
+ nacl::HtpHeader msg;
+ nacl::IOVec vec;
+ vec.base = const_cast<void *>(data);
+ vec.length = size;
+ msg.iov = &vec;
+ msg.iov_length = 1;
+ msg.handles = NULL;
+ msg.handle_count = 0;
+ msg.flags = 0;
+ return nacl::SendDatagram(channel, &msg, flags);
+}
+
+int NaclSendHandles(nacl::HtpHandle channel,
+ const nacl::HtpHandle *handles,
+ size_t count,
+ int flags) {
+ nacl::HtpHeader msg;
+ msg.iov = NULL;
+ msg.iov_length = 0;
+ msg.handles = const_cast<nacl::HtpHandle *>(handles);
+ msg.handle_count = count;
+ msg.flags = 0;
+ return nacl::SendDatagram(channel, &msg, flags);
+}
+
+int NaclReceiveData(nacl::HtpHandle channel,
+ void *data,
+ size_t size,
+ int flags) {
+ nacl::HtpHeader msg;
+ nacl::IOVec vec[1];
+ vec[0].base = data;
+ vec[0].length = size;
+ msg.iov = vec;
+ msg.iov_length = 1;
+ msg.handles = NULL;
+ msg.handle_count = 0;
+ msg.flags = 0;
+ int result = nacl::ReceiveDatagram(channel, &msg, flags);
+ return result;
+}
+
+int NaclReceiveHandles(nacl::HtpHandle channel,
+ nacl::HtpHandle *handles,
+ size_t count,
+ int flags) {
+ nacl::HtpHeader msg;
+ msg.iov = NULL;
+ msg.iov_length = 0;
+ msg.handles = handles;
+ msg.handle_count = count;
+ msg.flags = 0;
+ return nacl::ReceiveDatagram(channel, &msg, flags);
+}
+
+struct RPCMessageHeader {
+ int message_id;
+ size_t size;
+ size_t handle_count;
+};
+
+RPCImplInterface::ReturnValue IMCSender::SendCall(
+ int message_id,
+ const void * data,
+ size_t size,
+ RPCHandle const *handles,
+ size_t handle_count) {
+ // Send 3 messages: first contains message id, and data size, second
+ // contains data and third handles.
+ // The reason for that is to have the size first so that we can allocate the
+ // data buffer on the receiving side.
+ RPCMessageHeader msg = {message_id, size, handle_count};
+ int result = NaclSendData(handle_, &msg, sizeof(msg), 0);
+ DCHECK_NE(-1, result);
+ if (size > 0) {
+ result = NaclSendData(handle_, data, size, 0);
+ DCHECK_NE(-1, result);
+ }
+ if (handle_count > 0) {
+ result = NaclSendHandles(handle_, handles, handle_count, 0);
+ DCHECK_NE(-1, result);
+ }
+
+ RPCImplInterface::ReturnValue ret;
+ result = NaclReceiveData(handle_, &ret, sizeof(ret), 0);
+ DCHECK_EQ(sizeof(ret), result);
+ return ret;
+}
+
+bool IMCMessageProcessor::GetMessageIDSize(bool wait) {
+ if (has_message_) return true;
+ RPCMessageHeader msg = {0};
+ int result = NaclReceiveData(handle_, &msg, sizeof(msg),
+ wait ? 0 : nacl::kDontWait);
+ if (result != sizeof(msg)) {
+ if (result >=0 || wait || !nacl::WouldBlock()) return false;
+ has_message_ = false;
+ } else {
+ incoming_message_id_ = msg.message_id;
+ incoming_message_size_ = msg.size;
+ incoming_message_handles_ = msg.handle_count;
+ has_message_ = true;
+ }
+ return true;
+}
+
+bool IMCMessageProcessor::ProcessMessage() {
+ if (!GetMessageIDSize(true)) return false;
+ if (incoming_message_size_ > 0) {
+ if (incoming_message_size_ > data_size_) {
+ data_size_ = incoming_message_size_;
+ data_.reset(new char[incoming_message_size_]);
+ }
+ int result = NaclReceiveData(handle_, data_.get(), incoming_message_size_,
+ 0);
+ if (result < 0) return false;
+ }
+ if (incoming_message_handles_ > 0) {
+ if (incoming_message_handles_ > handle_count_) {
+ handle_count_ = incoming_message_handles_;
+ handles_.reset(new nacl::HtpHandle[incoming_message_handles_]);
+ }
+ int result = NaclReceiveHandles(handle_, handles_.get(),
+ incoming_message_handles_, 0);
+ if (result < 0) return false;
+ }
+ has_message_ = false;
+ RPCImplInterface::ReturnValue retval = 0;
+ bool continue_processing = true;
+ if (incoming_message_id_ == POISONED_MESSAGE_ID) {
+ continue_processing = false;
+ } else {
+ retval = impl_->DoCall(incoming_message_id_, data_.get(),
+ incoming_message_size_, handles_.get(),
+ incoming_message_handles_);
+ // Note: the handles that got received are a "copy" of the original handle,
+ // so they need to be closed eventually. It's hard to impose an
+ // "ownership" policy onto the RPCImplInterface, because it makes the API
+ // very clunky. Currently, we only pass handles across for
+ // RegisterSharedMemory, and so we can safely close the handle immediately
+ // (the memory will stay mapped).
+ // TODO: Fix this. Possibly using a global registration mechanism
+ // and ref-counting would make it work nicely.
+ for (unsigned int i = 0; i < incoming_message_handles_; ++i) {
+ nacl::Close(handles_[i]);
+ }
+ }
+
+ int result = NaclSendData(handle_, &retval, sizeof(retval), 0);
+ if (result < 0) return false;
+ return continue_processing;
+}
+
+bool IMCMessageProcessor::HasMessage() {
+ GetMessageIDSize(false);
+ return has_message_;
+}
+
+RPCSendInterface *MakeSendInterface(RPCSocketHandle handle) {
+ return new IMCSender(handle);
+}
+
+RPCShmHandle CreateShm(size_t size) {
+ size = (size + nacl::kMapPageSize - 1) & ~(nacl::kMapPageSize - 1);
+ nacl::Handle nacl_handle = nacl::CreateMemoryObject(size);
+ return nacl_handle == nacl::kInvalidHandle ? kRPCInvalidHandle :
+ nacl::CreateShmDesc(nacl_handle, size);
+}
+
+void DestroyShm(RPCShmHandle handle) {
+ nacl::Close(handle);
+}
+
+void *MapShm(RPCShmHandle handle, size_t size) {
+ size = (size + nacl::kMapPageSize - 1) & ~(nacl::kMapPageSize - 1);
+ void *address = nacl::Map(NULL, size, nacl::kProtRead | nacl::kProtWrite,
+ nacl::kMapShared, handle, 0);
+ return address == nacl::kMapFailed ? NULL : address;
+}
+
+void UnmapShm(void *address, size_t size) {
+ size = (size + nacl::kMapPageSize - 1) & ~(nacl::kMapPageSize - 1);
+ nacl::Unmap(address, size);
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/common/cross/rpc_imc.h b/o3d/command_buffer/common/cross/rpc_imc.h
new file mode 100644
index 0000000..5d2624f
--- /dev/null
+++ b/o3d/command_buffer/common/cross/rpc_imc.h
@@ -0,0 +1,109 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+#ifndef O3D_COMMAND_BUFFER_COMMON_CROSS_RPC_IMC_H_
+#define O3D_COMMAND_BUFFER_COMMON_CROSS_RPC_IMC_H_
+
+#include "native_client/intermodule_comm/nacl_imc.h"
+#include "base/scoped_ptr.h"
+#include "command_buffer/common/cross/rpc.h"
+
+namespace o3d {
+namespace command_buffer {
+
+class IMCSender : public RPCSendInterface {
+ public:
+ explicit IMCSender(nacl::HtpHandle handle) : handle_(handle) {}
+ virtual ~IMCSender() {}
+ // Sends a call to the server thread. This call will be dispatched by the
+ // server thread to the RPC implementation. This call will block until the
+ // call is processed and the return value is sent back.
+ // Parameters:
+ // message_id: the RPC message ID.
+ // data: the RPC message payload.
+ // size: the size of the data.
+ // handles: an array of RPC handles to transmit
+ // handle_count: the number of RPC handles in the array
+ // Returns:
+ // the return value of the RPC call.
+ virtual RPCImplInterface::ReturnValue SendCall(int message_id,
+ const void * data,
+ size_t size,
+ RPCHandle const *handles,
+ size_t handle_count);
+ private:
+ nacl::HtpHandle handle_;
+};
+
+class IMCMessageProcessor : public RPCProcessInterface {
+ public:
+ IMCMessageProcessor(nacl::HtpHandle handle, RPCImplInterface *impl)
+ : handle_(handle),
+ impl_(impl),
+ has_message_(false),
+ incoming_message_id_(0),
+ incoming_message_size_(0),
+ incoming_message_handles_(0),
+ data_size_(0),
+ handle_count_(0) {}
+ virtual ~IMCMessageProcessor() {}
+ // Processes one message, blocking if necessary until a message is available
+ // or the server is killed. This will dispatch the received message to the
+ // RPC implementation, and send back a response message with the return
+ // value to the client.
+ // Returns:
+ // false if the server was killed.
+ virtual bool ProcessMessage();
+
+ // Checks whether a message is available for processing - allowing to test if
+ // ProcessMessage will block.
+ // Returns:
+ // true if a message is available.
+ virtual bool HasMessage();
+ private:
+ bool GetMessageIDSize(bool wait);
+ nacl::HtpHandle handle_;
+ RPCImplInterface *impl_;
+ bool has_message_;
+ int incoming_message_id_;
+ size_t incoming_message_size_;
+ size_t incoming_message_handles_;
+ size_t data_size_;
+ scoped_array<char> data_;
+ size_t handle_count_;
+ scoped_array<RPCHandle> handles_;
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_COMMON_CROSS_RPC_IMC_H_
diff --git a/o3d/command_buffer/common/cross/types.h b/o3d/command_buffer/common/cross/types.h
new file mode 100644
index 0000000..add362f
--- /dev/null
+++ b/o3d/command_buffer/common/cross/types.h
@@ -0,0 +1,61 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains cross-platform basic type definitions
+
+#ifndef O3D_COMMAND_BUFFER_COMMON_CROSS_TYPES_H_
+#define O3D_COMMAND_BUFFER_COMMON_CROSS_TYPES_H_
+
+#if !defined(COMPILER_MSVC)
+#include <stdint.h>
+#endif
+#include <string>
+
+namespace o3d {
+namespace command_buffer {
+#if defined(COMPILER_MSVC)
+typedef short Int16;
+typedef unsigned short Uint16;
+typedef int Int32;
+typedef unsigned int Uint32;
+#else
+typedef int16_t Int16;
+typedef uint16_t Uint16;
+typedef int32_t Int32;
+typedef uint32_t Uint32;
+#endif
+
+typedef std::string String;
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_COMMON_CROSS_TYPES_H_
diff --git a/o3d/command_buffer/samples/bubble/bubble.html b/o3d/command_buffer/samples/bubble/bubble.html
new file mode 100644
index 0000000..5ccc8ef
--- /dev/null
+++ b/o3d/command_buffer/samples/bubble/bubble.html
@@ -0,0 +1,83 @@
+<!--
+Copyright 2009, Google Inc.
+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.
+-->
+
+<HTML>
+<HEAD>
+ <TITLE>Native Client + Command buffer bubble test</TITLE>
+
+<script type="text/javascript">
+
+var client;
+var server;
+var timeout;
+var interval;
+
+var PostInit = function() {
+ if ((client == undefined) || (server == undefined)) {
+ alert('Unable to load, try reloading page (or missing plugins?)');
+ return;
+ }
+ if ((client.create == undefined) || (server.create == undefined)) {
+ timeout = setTimeout(PostInit, 100);
+ } else {
+ var handle;
+ handle = client.create();
+ server.create(handle);
+ client.initialize();
+ interval = setInterval(function() {client.render();}, 10);
+ }
+}
+
+function start() {
+ client = document.getElementById('client');
+ server = document.getElementById('server');
+ PostInit();
+}
+
+function doUnload() {
+ clearTimeout(timeout);
+ clearInterval(interval);
+}
+
+</script>
+
+</HEAD>
+<BODY id="bodyId" onload="start()" onunload="doUnload()">
+
+<h1>Native Client + Command buffer bubble test</h1>
+
+<embed id="client" src="bubble_module.nexe" type="application/x-nacl-npapi" width="0" height="0"></embed>
+<object id="server" type="application/vnd.cmdbuf" width="1000" height="1000"></object>
+
+<br>
+
+</BODY>
+</HTML>
diff --git a/o3d/command_buffer/samples/bubble/bubble_module.cc b/o3d/command_buffer/samples/bubble/bubble_module.cc
new file mode 100644
index 0000000..42eae04
--- /dev/null
+++ b/o3d/command_buffer/samples/bubble/bubble_module.cc
@@ -0,0 +1,1266 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This is the Soap Bubble sample / demo. It runs as a native client NPAPI
+// plug-in.
+
+#include <math.h>
+#include <stdint.h>
+#ifdef __native_demo__
+#include <sys/nacl_syscalls.h>
+#else
+#include "native_client/service_runtime/nrd_xfer_lib/nrd_all_modules.h"
+#endif
+#include "command_buffer/common/cross/gapi_interface.h"
+#include "command_buffer/common/cross/rpc_imc.h"
+#include "command_buffer/client/cross/cmd_buffer_helper.h"
+#include "command_buffer/client/cross/buffer_sync_proxy.h"
+#include "command_buffer/client/cross/fenced_allocator.h"
+#include "command_buffer/samples/bubble/utils.h"
+#include "command_buffer/samples/bubble/iridescence_texture.h"
+#include "command_buffer/samples/bubble/perlin_noise.h"
+#include "third_party/vectormath/files/vectormathlibrary/include/vectormath/scalar/cpp/vectormath_aos.h" // NOLINT
+
+#include "native_client/intermodule_comm/nacl_imc.h"
+#include "native_client/tools/npapi_runtime/nacl_npapi.h"
+
+// Cube map data is hard-coded in cubemap.cc as a byte array.
+// Format is 64x64xBRGA, D3D face ordering (+X, -X, +Y, -Y, +Z, -Z).
+extern unsigned char g_cubemap_data[];
+const unsigned int kCubeMapWidth = 64;
+const unsigned int kCubeMapHeight = 64;
+const unsigned int kCubeMapFaceSize = kCubeMapWidth * kCubeMapHeight * 4;
+
+// Define this to debug command buffers: it will call Finish() and check for a
+// parse error. If there was one, it will warn about it in the console window.
+// #define DEBUG_CMD
+#ifdef DEBUG_CMD
+#define CHECK_ERROR(HELPER) do { \
+ HELPER->Finish(); \
+ BufferSyncInterface::ParseError error = \
+ HELPER->interface()->GetParseError(); \
+ if (error != BufferSyncInterface::PARSE_NO_ERROR) { \
+ printf("CMD error %d at %s:%d\n", error, __FILE__, __LINE__); \
+ } \
+ } while (false)
+#else
+#define CHECK_ERROR(HELPER) do { } while (false)
+#endif
+
+namespace Vectormath {
+namespace Aos {
+
+// Creates a perspective projection matrix.
+Matrix4 CreatePerspectiveMatrix(float vertical_field_of_view_radians,
+ float aspect,
+ float z_near,
+ float z_far) {
+ float dz = z_near - z_far;
+ float vertical_scale = 1.0f / tanf(vertical_field_of_view_radians / 2.0f);
+ float horizontal_scale = vertical_scale / aspect;
+ return Matrix4(Vector4(horizontal_scale, 0.0f, 0.0f, 0.0f),
+ Vector4(0.0f, vertical_scale, 0.0f, 0.0f),
+ Vector4(0.0f, 0.0f, z_far / dz, -1.0f),
+ Vector4(0.0f, 0.0f, z_near * z_far / dz, 0.0f));
+}
+
+} // namespace Aos
+} // namespace Vectormath
+
+namespace o3d {
+namespace command_buffer {
+
+namespace math = Vectormath::Aos;
+
+// Adds a Clear command into the command buffer.
+// Parameters:
+// cmd_buffer: the command buffer helper.
+// buffers: a bitfield of which buffers to clear (a combination of
+// GAPIInterface::COLOR, GAPIInterface::DEPTH and GAPIInterface::STENCIL).
+// color: the color buffer clear value.
+// depth: the depth buffer clear value.
+// stencil: the stencil buffer clear value.
+void ClearCmd(CommandBufferHelper *cmd_buffer,
+ const unsigned int buffers,
+ const RGBA &color,
+ float depth,
+ unsigned int stencil) {
+ CommandBufferEntry args[7];
+ args[0].value_uint32 = buffers;
+ args[1].value_float = color.red;
+ args[2].value_float = color.green;
+ args[3].value_float = color.blue;
+ args[4].value_float = color.alpha;
+ args[5].value_float = depth;
+ args[6].value_uint32 = stencil;
+ cmd_buffer->AddCommand(command_buffer::CLEAR, 7, args);
+ CHECK_ERROR(cmd_buffer);
+}
+
+// Adds a SetViewport command into the buffer.
+// Parameters:
+// cmd_buffer: the command buffer helper.
+// x, y, width, height: the dimensions of the Viewport.
+// z_near, z_far: the near and far clip plane distances.
+void SetViewportCmd(CommandBufferHelper *cmd_buffer,
+ unsigned int x,
+ unsigned int y,
+ unsigned int width,
+ unsigned int height,
+ float z_near,
+ float z_far) {
+ CommandBufferEntry args[6];
+ args[0].value_uint32 = x;
+ args[1].value_uint32 = y;
+ args[2].value_uint32 = width;
+ args[3].value_uint32 = height;
+ args[4].value_float = z_near;
+ args[5].value_float = z_far;
+ cmd_buffer->AddCommand(command_buffer::SET_VIEWPORT, 6, args);
+ CHECK_ERROR(cmd_buffer);
+}
+
+// Copy a data buffer to args, for IMMEDIATE commands. Returns the number of
+// args used.
+unsigned int CopyToArgs(CommandBufferEntry *args,
+ const void *data,
+ size_t size) {
+ memcpy(args, data, size);
+ const unsigned int arg_size = sizeof(args[0]);
+ return static_cast<unsigned int>((size + arg_size - 1) / arg_size);
+}
+
+// Our effect: this computes the reflection color using the iridescence texture,
+// and modulates it with the cubemap lookup on the reflected ray, passing the
+// transmission factor in the alpha (this should be used with One/SourceAlpha
+// blending mode).
+// We also attenuate the back face color because the incident light has already
+// been through the front face.
+// The width is modulated by an exponential factor of the Y component, to
+// simulate gravity, and by a noise texture.
+const char effect_data[] =
+ "vs\0" // Vertex program entry point
+ "ps\0" // Fragment program entry point
+ "struct a2v {\n"
+ " float3 position: POSITION;\n" // Object-space position
+ " float3 normal: NORMAL;\n" // Object-space normal
+ " float2 uv: TEXCOORD0;\n" // Noise texture UVs
+ "};\n"
+ "struct v2f {\n"
+ " float4 position: POSITION;\n" // Homogeneous clip space position
+ " float2 uv: TEXCOORD0;\n" // Noise texture UVs
+ " float2 params: TEXCOORD1;\n" // (cos i, thickness), where i is the
+ // angle of the incident ray
+ " float3 reflected: TEXCOORD4;\n" // Reflected ray direction
+ "};\n"
+ "\n"
+ "float4x4 worldViewProj : WorldViewProjection;\n" // MVP matrix
+ "float4x4 world : World;\n" // Object-to-world matrix
+ "float4x4 worldIT : WorldInverseTranspose;\n" // Object-to-world matrix
+ "float3 eye;\n" // World-space eye position
+ "float4 thickness_params;\n" // Thickness modulation parameters (xyz),
+ // Back face attenuation (w)
+ "sampler noise_sampler;\n" // Noise sampler
+ "sampler iridescence_sampler;\n" // Iridescence sampler
+ "sampler env_sampler;\n" // Environment map sampler
+ "\n"
+ "v2f vs(a2v i) {\n"
+ " v2f o;\n"
+ // Object-space position and normal
+ " float4 object_position =\n"
+ " float4(i.position.x, i.position.y, i.position.z, 1);\n"
+ " float4 object_normal = float4(i.normal.x, i.normal.y, i.normal.z, 0);\n"
+ // World-space position, normal, object center, and eye vector (incident
+ // ray)
+ " float3 normal = normalize(mul(object_normal, worldIT).xyz);\n"
+ " float4 position = mul(object_position, world);\n"
+ " float4 center = mul(float4(0, 0, 0, 1), world);\n"
+ " float3 eye_vector = normalize(position.xyz - eye);\n"
+ // cos i (absolute value for back faces)
+ " float cos_i = abs(dot(normal, eye_vector));\n"
+ " float thickness =\n"
+ " exp(-(position.y-center.y)*thickness_params.x)*thickness_params.y;\n"
+ // Output parameters
+ " o.position = mul(object_position, worldViewProj);\n"
+ " o.params = float2(cos_i, thickness);\n"
+ " o.reflected = reflect(eye_vector, normal);\n"
+ " o.uv = i.uv;\n"
+ " return o;\n"
+ "}\n"
+ "float4 ps(v2f i) : COLOR {\n"
+ // noise: remap [0 .. 1] to [-0.5 .. 0.5]
+ " float noise = tex2D(noise_sampler, i.uv).x - .5;\n"
+ " float thickness = i.params.y - noise * thickness_params.z;\n"
+ " float cos_i = i.params.x;\n"
+ // Modulate iridescence color by the environment looked up along the
+ // reflected ray.
+ " float4 color = tex2D(iridescence_sampler, float2(cos_i, thickness));\n"
+ " color *= texCUBE(env_sampler, i.reflected);\n"
+ // Modulate by per-face attenuation
+ " color.rgb *= thickness_params.w;\n"
+ " return color;\n"
+ "};\n"
+ "\n";
+
+// Custom vertex, with position, normal and UVs.
+struct CustomVertex {
+ float x, y, z;
+ float nx, ny, nz;
+ float u, v;
+};
+
+// Creates a sphere shape, filling vertices and indices.
+// There must be space for (rows+1) * (cols+1) vertices, and 6 * rows * cols
+// indices.
+void MakeSphere(unsigned int rows,
+ unsigned int cols,
+ CustomVertex *vertices,
+ unsigned int *indices) {
+ for (unsigned int y = 0; y < rows + 1; ++y) {
+ float phi = y * kPi / rows;
+ float y1 = cosf(phi);
+ float r = sinf(phi);
+ for (unsigned int x = 0; x < cols + 1; ++x) {
+ float theta = x * 2.f * kPi / cols;
+ float x1 = cosf(theta) * r;
+ float z1 = sinf(theta) * r;
+ unsigned int index = x + y * (cols + 1);
+ CustomVertex * vertex = vertices + index;
+ vertex->x = x1;
+ vertex->y = y1;
+ vertex->z = z1;
+ vertex->nx = x1;
+ vertex->ny = y1;
+ vertex->nz = z1;
+ vertex->u = x * 1.f / cols;
+ vertex->v = y * 1.f / rows;
+ if (x != cols && y != rows) {
+ // For each vertex, we add indices for 2 triangles representing the
+ // quad using this vertex as the upper left corner:
+ // [(x, y), (x+1, y), (x+1, y+1)] and
+ // [(x, y), (x+1, y+1), (x, y+1)].
+ // Note that we don't create triangles for the last row and the last
+ // column of vertices.
+ *indices++ = index;
+ *indices++ = index + 1;
+ *indices++ = index + cols + 2;
+ *indices++ = index;
+ *indices++ = index + cols + 2;
+ *indices++ = index + cols + 1;
+ }
+ }
+ }
+}
+
+// Makes a BGRA noise texture.
+void MakeNoiseTexture(unsigned int width,
+ unsigned int height,
+ unsigned int frequency,
+ unsigned int *seed,
+ unsigned char *texture) {
+ PerlinNoise2D perlin(frequency);
+ perlin.Initialize(seed);
+ scoped_array<float> values(new float[width * height]);
+ perlin.Generate(width, height, values.get());
+ for (unsigned int y = 0; y < height; ++y) {
+ // Attenuate the noise value with a function that goes to 0 on the poles to
+ // avoid discontinuities.
+ // Note: it'd be better to have a 3D noise texture, but they are way
+ // too expensive.
+ float attenuation = sinf(y * kPi / height);
+ for (unsigned int x = 0; x < width; ++x) {
+ float attenuated_value = values[y * width + x] * attenuation;
+ // remap [-1..1] to [0..1] and convert to color values.
+ unsigned char value = ToChar(attenuated_value * .5f + .5f);
+ *texture++ = value;
+ *texture++ = value;
+ *texture++ = value;
+ *texture++ = value;
+ }
+ }
+}
+
+// Gets current time in microseconds.
+uint64_t GetTimeUsec() {
+ struct timeval tv;
+ gettimeofday(&tv, NULL);
+ return tv.tv_sec * 1000000ULL + tv.tv_usec;
+}
+
+class BubbleDemo {
+ public:
+ BubbleDemo();
+ ~BubbleDemo() {}
+
+ // Creates the socket pair for the connection.
+ nacl::HtpHandle CreateSockets();
+
+ // Initializes the demo once connected.
+ void Initialize();
+ // Finalizes the demo.
+ void Finalize();
+ // Renders a frame.
+ void Render();
+ private:
+ // A bubble instance.
+ struct Bubble {
+ math::Point3 position;
+ math::Vector3 rotation_speed;
+ float scale;
+ float base_thickness;
+ float thickness_falloff;
+ float noise_ratio;
+ };
+
+ // Depth sort functor for bubbles.
+ class BubbleSorter {
+ public:
+ explicit BubbleSorter(const math::Matrix4 &view) : view_(view) {}
+ bool operator()(const Bubble &l, const Bubble &r) {
+ return (view_ * l.position)[2] < (view_ * r.position)[2];
+ }
+ private:
+ const math::Matrix4 &view_;
+ };
+
+ // Draws one bubble.
+ void DrawBubble(const math::Matrix4& view,
+ const math::Matrix4& proj,
+ const BubbleDemo::Bubble &bubble,
+ const math::Vector3& rotation);
+
+ nacl::HtpHandle handle_pair_[2];
+ ResourceID vertex_buffer_id_;
+ ResourceID index_buffer_id_;
+ ResourceID vertex_struct_id_;
+ ResourceID effect_id_;
+ ResourceID noise_texture_id_;
+ ResourceID iridescence_texture_id_;
+ ResourceID cubemap_id_;
+ ResourceID noise_sampler_id_;
+ ResourceID iridescence_sampler_id_;
+ ResourceID cubemap_sampler_id_;
+ ResourceID noise_sampler_param_id_;
+ ResourceID iridescence_sampler_param_id_;
+ ResourceID cubemap_sampler_param_id_;
+ ResourceID mvp_param_id_;
+ ResourceID world_param_id_;
+ ResourceID worldIT_param_id_;
+ ResourceID eye_param_id_;
+ ResourceID thickness_param_id_;
+ scoped_ptr<IMCSender> sender_;
+ scoped_ptr<BufferSyncProxy> proxy_;
+ scoped_ptr<CommandBufferHelper> helper_;
+ scoped_ptr<FencedAllocatorWrapper> allocator_;
+ RPCShmHandle shm_;
+ unsigned int shm_id_;
+ void *shm_address_;
+ CustomVertex *vertices_;
+ unsigned int *indices_;
+ unsigned char *noise_texture_;
+ unsigned char *iridescence_texture_;
+ unsigned int seed_;
+ uint64_t start_time_;
+ float time_;
+ std::vector<Bubble> bubbles_;
+};
+
+BubbleDemo::BubbleDemo()
+ : vertex_buffer_id_(1),
+ index_buffer_id_(1),
+ vertex_struct_id_(1),
+ effect_id_(1),
+ noise_texture_id_(1),
+ iridescence_texture_id_(2),
+ cubemap_id_(3),
+ noise_sampler_id_(1),
+ iridescence_sampler_id_(2),
+ cubemap_sampler_id_(3),
+ noise_sampler_param_id_(1),
+ iridescence_sampler_param_id_(2),
+ cubemap_sampler_param_id_(3),
+ mvp_param_id_(4),
+ world_param_id_(5),
+ worldIT_param_id_(6),
+ eye_param_id_(7),
+ thickness_param_id_(8),
+ shm_(kRPCInvalidHandle),
+ shm_id_(UINT_MAX),
+ shm_address_(NULL),
+ vertices_(NULL),
+ indices_(NULL),
+ noise_texture_(NULL),
+ iridescence_texture_(NULL),
+ seed_(GetTimeUsec()),
+ start_time_(0),
+ time_(0.f) {
+ handle_pair_[0] = nacl::kInvalidHtpHandle;
+ handle_pair_[1] = nacl::kInvalidHtpHandle;
+}
+
+nacl::HtpHandle BubbleDemo::CreateSockets() {
+ nacl::Handle socket_pair[2];
+ if (nacl::SocketPair(socket_pair) < 0) {
+ return nacl::kInvalidHtpHandle;
+ }
+ handle_pair_[0] = nacl::CreateImcDesc(socket_pair[0]);
+ handle_pair_[1] = nacl::CreateImcDesc(socket_pair[1]);
+ return handle_pair_[1];
+}
+
+const unsigned int kRows = 50;
+const unsigned int kCols = 100;
+const unsigned int kVertexCount = (kRows + 1) * (kCols + 1);
+const unsigned int kIndexCount = 6 * kRows * kCols;
+const unsigned int kVertexBufferSize = kVertexCount * sizeof(CustomVertex);
+const unsigned int kIndexBufferSize = kIndexCount * sizeof(unsigned int);
+
+const unsigned int kTexWidth = 512;
+const unsigned int kTexHeight = 512;
+const unsigned int kTexSize = kTexWidth * kTexHeight * 4;
+
+const unsigned int kShmSize = 3 << 20;
+const unsigned int kCommandBufferEntries = 1 << 16;
+
+const float kRefractionIndex = 1.33;
+const unsigned int kBubbleCount = 10;
+
+void BubbleDemo::Initialize() {
+ sender_.reset(new IMCSender(handle_pair_[0]));
+ proxy_.reset(new BufferSyncProxy(sender_.get()));
+ proxy_->InitConnection();
+
+ DCHECK_LE(kVertexBufferSize + kIndexBufferSize + 2 * kTexSize, kShmSize);
+ shm_ = CreateShm(kShmSize);
+ shm_address_ = MapShm(shm_, kShmSize);
+ shm_id_ = proxy_->RegisterSharedMemory(shm_, kShmSize);
+ helper_.reset(new CommandBufferHelper(proxy_.get()));
+ helper_->Init(kCommandBufferEntries);
+
+ allocator_.reset(new FencedAllocatorWrapper(kShmSize,
+ helper_.get(),
+ shm_address_));
+ vertices_ = allocator_->AllocTyped<CustomVertex>(kVertexCount);
+ indices_ = allocator_->AllocTyped<unsigned int>(kIndexCount);
+ MakeSphere(kRows, kCols, vertices_, indices_);
+ noise_texture_ = allocator_->AllocTyped<unsigned char>(kTexSize);
+ MakeNoiseTexture(kTexWidth, kTexHeight, 8, &seed_, noise_texture_);
+ iridescence_texture_ = allocator_->AllocTyped<unsigned char>(kTexSize);
+ MakeIridescenceTexture(kTexWidth, kTexHeight, kRefractionIndex,
+ kRedWavelength, iridescence_texture_);
+
+ // Clear the buffers.
+ RGBA color = {0.f, 0.f, 0.f, 1.f};
+ ClearCmd(helper_.get(), GAPIInterface::COLOR | GAPIInterface::DEPTH, color,
+ 1.f, 0);
+
+ // AddCommand copies the args, so it is safe to re-use args across various
+ // calls.
+ // 20 is the largest command we use (SET_PARAM_DATA_IMMEDIATE for matrices).
+ CommandBufferEntry args[20];
+
+ // Create geometry arrays and structures
+ args[0].value_uint32 = vertex_buffer_id_;
+ args[1].value_uint32 = kVertexBufferSize; // size
+ args[2].value_uint32 = 0; // flags
+ helper_->AddCommand(CREATE_VERTEX_BUFFER, 3, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 = vertex_buffer_id_;
+ args[1].value_uint32 = 0; // offset in VB
+ args[2].value_uint32 = kVertexBufferSize; // size
+ args[3].value_uint32 = shm_id_; // shm
+ args[4].value_uint32 = allocator_->GetOffset(vertices_); // offset in shm
+ helper_->AddCommand(SET_VERTEX_BUFFER_DATA, 5, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 = index_buffer_id_;
+ args[1].value_uint32 = kIndexBufferSize; // size
+ args[2].value_uint32 = index_buffer::INDEX_32BIT; // flags
+ helper_->AddCommand(CREATE_INDEX_BUFFER, 3, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 = index_buffer_id_;
+ args[1].value_uint32 = 0; // offset in IB
+ args[2].value_uint32 = kIndexBufferSize; // size
+ args[3].value_uint32 = shm_id_; // shm
+ args[4].value_uint32 = allocator_->GetOffset(indices_); // offset in shm
+ helper_->AddCommand(SET_INDEX_BUFFER_DATA, 5, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 = vertex_struct_id_;
+ args[1].value_uint32 = 3; // input count
+ helper_->AddCommand(CREATE_VERTEX_STRUCT, 2, args);
+ CHECK_ERROR(helper_);
+
+ // Set POSITION input stream
+ args[0].value_uint32 = vertex_struct_id_;
+ args[1].value_uint32 = 0; // input
+ args[2].value_uint32 = vertex_buffer_id_; // buffer
+ args[3].value_uint32 = 0; // offset
+ args[4].value_uint32 =
+ set_vertex_input_cmd::Stride::MakeValue(sizeof(CustomVertex)) |
+ set_vertex_input_cmd::Type::MakeValue(vertex_struct::FLOAT3) |
+ set_vertex_input_cmd::Semantic::MakeValue(vertex_struct::POSITION) |
+ set_vertex_input_cmd::SemanticIndex::MakeValue(0);
+ helper_->AddCommand(SET_VERTEX_INPUT, 5, args);
+ CHECK_ERROR(helper_);
+
+ // Set NORMAL input stream
+ args[1].value_uint32 = 1; // input
+ args[3].value_uint32 = 12; // offset
+ args[4].value_uint32 =
+ set_vertex_input_cmd::Stride::MakeValue(sizeof(CustomVertex)) |
+ set_vertex_input_cmd::Type::MakeValue(vertex_struct::FLOAT3) |
+ set_vertex_input_cmd::Semantic::MakeValue(vertex_struct::NORMAL) |
+ set_vertex_input_cmd::SemanticIndex::MakeValue(0);
+ helper_->AddCommand(SET_VERTEX_INPUT, 5, args);
+ CHECK_ERROR(helper_);
+
+ // Set TEXCOORD0 input stream
+ args[1].value_uint32 = 2; // input
+ args[3].value_uint32 = 24; // offset
+ args[4].value_uint32 =
+ set_vertex_input_cmd::Stride::MakeValue(sizeof(CustomVertex)) |
+ set_vertex_input_cmd::Type::MakeValue(vertex_struct::FLOAT2) |
+ set_vertex_input_cmd::Semantic::MakeValue(vertex_struct::TEX_COORD) |
+ set_vertex_input_cmd::SemanticIndex::MakeValue(0);
+ helper_->AddCommand(SET_VERTEX_INPUT, 5, args);
+ CHECK_ERROR(helper_);
+
+ // Create a 2D texture.
+ args[0].value_uint32 = noise_texture_id_;
+ args[1].value_uint32 =
+ create_texture_2d_cmd::Width::MakeValue(kTexWidth) |
+ create_texture_2d_cmd::Height::MakeValue(kTexHeight);
+ args[2].value_uint32 =
+ create_texture_2d_cmd::Levels::MakeValue(0) |
+ create_texture_2d_cmd::Format::MakeValue(texture::ARGB8) |
+ create_texture_2d_cmd::Flags::MakeValue(0);
+ helper_->AddCommand(CREATE_TEXTURE_2D, 3, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 = noise_texture_id_;
+ args[1].value_uint32 =
+ set_texture_data_cmd::X::MakeValue(0) |
+ set_texture_data_cmd::Y::MakeValue(0);
+ args[2].value_uint32 =
+ set_texture_data_cmd::Width::MakeValue(kTexWidth) |
+ set_texture_data_cmd::Height::MakeValue(kTexHeight);
+ args[3].value_uint32 =
+ set_texture_data_cmd::Z::MakeValue(0) |
+ set_texture_data_cmd::Depth::MakeValue(1);
+ args[4].value_uint32 = set_texture_data_cmd::Level::MakeValue(0);
+ args[5].value_uint32 = kTexWidth * 4; // row_pitch
+ args[6].value_uint32 = 0; // slice_pitch
+ args[7].value_uint32 = kTexSize; // size
+ args[8].value_uint32 = shm_id_;
+ args[9].value_uint32 = allocator_->GetOffset(noise_texture_);
+ helper_->AddCommand(SET_TEXTURE_DATA, 10, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 = noise_sampler_id_;
+ helper_->AddCommand(CREATE_SAMPLER, 1, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 = noise_sampler_id_;
+ args[1].value_uint32 = noise_texture_id_;
+ helper_->AddCommand(SET_SAMPLER_TEXTURE, 2, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 = noise_sampler_id_;
+ args[1].value_uint32 =
+ set_sampler_states::AddressingU::MakeValue(sampler::WRAP) |
+ set_sampler_states::AddressingV::MakeValue(sampler::WRAP) |
+ set_sampler_states::AddressingW::MakeValue(sampler::WRAP) |
+ set_sampler_states::MagFilter::MakeValue(sampler::LINEAR) |
+ set_sampler_states::MinFilter::MakeValue(sampler::LINEAR) |
+ set_sampler_states::MipFilter::MakeValue(sampler::NONE) |
+ set_sampler_states::MaxAnisotropy::MakeValue(1);
+ helper_->AddCommand(SET_SAMPLER_STATES, 2, args);
+ CHECK_ERROR(helper_);
+
+ // Create a 2D texture.
+ args[0].value_uint32 = iridescence_texture_id_;
+ args[1].value_uint32 =
+ create_texture_2d_cmd::Width::MakeValue(kTexWidth) |
+ create_texture_2d_cmd::Height::MakeValue(kTexHeight);
+ args[2].value_uint32 =
+ create_texture_2d_cmd::Levels::MakeValue(0) |
+ create_texture_2d_cmd::Format::MakeValue(texture::ARGB8) |
+ create_texture_2d_cmd::Flags::MakeValue(0);
+ helper_->AddCommand(CREATE_TEXTURE_2D, 3, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 = iridescence_texture_id_;
+ args[1].value_uint32 =
+ set_texture_data_cmd::X::MakeValue(0) |
+ set_texture_data_cmd::Y::MakeValue(0);
+ args[2].value_uint32 =
+ set_texture_data_cmd::Width::MakeValue(kTexWidth) |
+ set_texture_data_cmd::Height::MakeValue(kTexHeight);
+ args[3].value_uint32 =
+ set_texture_data_cmd::Z::MakeValue(0) |
+ set_texture_data_cmd::Depth::MakeValue(1);
+ args[4].value_uint32 = set_texture_data_cmd::Level::MakeValue(0);
+ args[5].value_uint32 = kTexWidth * 4; // row_pitch
+ args[6].value_uint32 = 0; // slice_pitch
+ args[7].value_uint32 = kTexSize; // size
+ args[8].value_uint32 = shm_id_;
+ args[9].value_uint32 = allocator_->GetOffset(iridescence_texture_);
+ helper_->AddCommand(SET_TEXTURE_DATA, 10, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 = iridescence_sampler_id_;
+ helper_->AddCommand(CREATE_SAMPLER, 1, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 = iridescence_sampler_id_;
+ args[1].value_uint32 = iridescence_texture_id_;
+ helper_->AddCommand(SET_SAMPLER_TEXTURE, 2, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 = iridescence_sampler_id_;
+ args[1].value_uint32 =
+ set_sampler_states::AddressingU::MakeValue(sampler::CLAMP_TO_EDGE) |
+ set_sampler_states::AddressingV::MakeValue(sampler::CLAMP_TO_EDGE) |
+ set_sampler_states::AddressingW::MakeValue(sampler::CLAMP_TO_EDGE) |
+ set_sampler_states::MagFilter::MakeValue(sampler::LINEAR) |
+ set_sampler_states::MinFilter::MakeValue(sampler::LINEAR) |
+ set_sampler_states::MipFilter::MakeValue(sampler::NONE) |
+ set_sampler_states::MaxAnisotropy::MakeValue(1);
+ helper_->AddCommand(SET_SAMPLER_STATES, 2, args);
+ CHECK_ERROR(helper_);
+
+ // Create a Cubemap texture.
+ args[0].value_uint32 = cubemap_id_;
+ args[1].value_uint32 =
+ create_texture_cube_cmd::Side::MakeValue(kCubeMapWidth);
+ args[2].value_uint32 =
+ create_texture_cube_cmd::Levels::MakeValue(0) |
+ create_texture_cube_cmd::Format::MakeValue(texture::ARGB8) |
+ create_texture_cube_cmd::Flags::MakeValue(0);
+ helper_->AddCommand(CREATE_TEXTURE_CUBE, 3, args);
+ CHECK_ERROR(helper_);
+
+ for (unsigned int face = 0; face < 6; ++face) {
+ void *data = allocator_->Alloc(kCubeMapFaceSize);
+ memcpy(data, g_cubemap_data + face*kCubeMapFaceSize, kCubeMapFaceSize);
+ args[0].value_uint32 = cubemap_id_;
+ args[1].value_uint32 =
+ set_texture_data_cmd::X::MakeValue(0) |
+ set_texture_data_cmd::Y::MakeValue(0);
+ args[2].value_uint32 =
+ set_texture_data_cmd::Width::MakeValue(kCubeMapWidth) |
+ set_texture_data_cmd::Height::MakeValue(kCubeMapHeight);
+ args[3].value_uint32 =
+ set_texture_data_cmd::Z::MakeValue(0) |
+ set_texture_data_cmd::Depth::MakeValue(1);
+ args[4].value_uint32 =
+ set_texture_data_cmd::Level::MakeValue(0) |
+ set_texture_data_cmd::Face::MakeValue(face);
+ args[5].value_uint32 = kCubeMapWidth * 4; // row_pitch
+ args[6].value_uint32 = 0; // slice_pitch
+ args[7].value_uint32 = kCubeMapFaceSize; // size
+ args[8].value_uint32 = shm_id_;
+ args[9].value_uint32 = allocator_->GetOffset(data);
+ helper_->AddCommand(SET_TEXTURE_DATA, 10, args);
+ CHECK_ERROR(helper_);
+ allocator_->FreePendingToken(data, helper_->InsertToken());
+ }
+
+ args[0].value_uint32 = cubemap_sampler_id_;
+ helper_->AddCommand(CREATE_SAMPLER, 1, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 = cubemap_sampler_id_;
+ args[1].value_uint32 = cubemap_id_;
+ helper_->AddCommand(SET_SAMPLER_TEXTURE, 2, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 = cubemap_sampler_id_;
+ args[1].value_uint32 =
+ set_sampler_states::AddressingU::MakeValue(sampler::CLAMP_TO_EDGE) |
+ set_sampler_states::AddressingV::MakeValue(sampler::CLAMP_TO_EDGE) |
+ set_sampler_states::AddressingW::MakeValue(sampler::CLAMP_TO_EDGE) |
+ set_sampler_states::MagFilter::MakeValue(sampler::LINEAR) |
+ set_sampler_states::MinFilter::MakeValue(sampler::LINEAR) |
+ set_sampler_states::MipFilter::MakeValue(sampler::NONE) |
+ set_sampler_states::MaxAnisotropy::MakeValue(1);
+ helper_->AddCommand(SET_SAMPLER_STATES, 2, args);
+ CHECK_ERROR(helper_);
+
+ // Create the effect, and parameters.
+ void *data = allocator_->Alloc(sizeof(effect_data));
+ memcpy(data, effect_data, sizeof(effect_data));
+ args[0].value_uint32 = effect_id_;
+ args[1].value_uint32 = sizeof(effect_data); // size
+ args[2].value_uint32 = shm_id_; // shm
+ args[3].value_uint32 = allocator_->GetOffset(data); // offset in shm
+ helper_->AddCommand(CREATE_EFFECT, 4, args);
+ CHECK_ERROR(helper_);
+ allocator_->FreePendingToken(data, helper_->InsertToken());
+
+ {
+ const char param_name[] = "noise_sampler";
+ args[0].value_uint32 = noise_sampler_param_id_;
+ args[1].value_uint32 = effect_id_;
+ args[2].value_uint32 = sizeof(param_name);
+ unsigned int arg_count = CopyToArgs(args + 3, param_name,
+ sizeof(param_name));
+ helper_->AddCommand(CREATE_PARAM_BY_NAME_IMMEDIATE, 3 + arg_count, args);
+ CHECK_ERROR(helper_);
+ }
+
+ {
+ const char param_name[] = "iridescence_sampler";
+ args[0].value_uint32 = iridescence_sampler_param_id_;
+ args[1].value_uint32 = effect_id_;
+ args[2].value_uint32 = sizeof(param_name);
+ unsigned int arg_count = CopyToArgs(args + 3, param_name,
+ sizeof(param_name));
+ helper_->AddCommand(CREATE_PARAM_BY_NAME_IMMEDIATE, 3 + arg_count, args);
+ CHECK_ERROR(helper_);
+ }
+
+ {
+ const char param_name[] = "env_sampler";
+ args[0].value_uint32 = cubemap_sampler_param_id_;
+ args[1].value_uint32 = effect_id_;
+ args[2].value_uint32 = sizeof(param_name);
+ unsigned int arg_count = CopyToArgs(args + 3, param_name,
+ sizeof(param_name));
+ helper_->AddCommand(CREATE_PARAM_BY_NAME_IMMEDIATE, 3 + arg_count, args);
+ CHECK_ERROR(helper_);
+ }
+
+ {
+ const char param_name[] = "worldViewProj";
+ args[0].value_uint32 = mvp_param_id_;
+ args[1].value_uint32 = effect_id_;
+ args[2].value_uint32 = sizeof(param_name);
+ unsigned int arg_count = CopyToArgs(args + 3, param_name,
+ sizeof(param_name));
+ helper_->AddCommand(CREATE_PARAM_BY_NAME_IMMEDIATE, 3 + arg_count, args);
+ CHECK_ERROR(helper_);
+ }
+
+ {
+ const char param_name[] = "world";
+ args[0].value_uint32 = world_param_id_;
+ args[1].value_uint32 = effect_id_;
+ args[2].value_uint32 = sizeof(param_name);
+ unsigned int arg_count = CopyToArgs(args + 3, param_name,
+ sizeof(param_name));
+ helper_->AddCommand(CREATE_PARAM_BY_NAME_IMMEDIATE, 3 + arg_count, args);
+ CHECK_ERROR(helper_);
+ }
+
+ {
+ const char param_name[] = "worldIT";
+ args[0].value_uint32 = worldIT_param_id_;
+ args[1].value_uint32 = effect_id_;
+ args[2].value_uint32 = sizeof(param_name);
+ unsigned int arg_count = CopyToArgs(args + 3, param_name,
+ sizeof(param_name));
+ helper_->AddCommand(CREATE_PARAM_BY_NAME_IMMEDIATE, 3 + arg_count, args);
+ CHECK_ERROR(helper_);
+ }
+
+ {
+ const char param_name[] = "eye";
+ args[0].value_uint32 = eye_param_id_;
+ args[1].value_uint32 = effect_id_;
+ args[2].value_uint32 = sizeof(param_name);
+ unsigned int arg_count = CopyToArgs(args + 3, param_name,
+ sizeof(param_name));
+ helper_->AddCommand(CREATE_PARAM_BY_NAME_IMMEDIATE, 3 + arg_count, args);
+ CHECK_ERROR(helper_);
+ }
+
+ {
+ const char param_name[] = "thickness_params";
+ args[0].value_uint32 = thickness_param_id_;
+ args[1].value_uint32 = effect_id_;
+ args[2].value_uint32 = sizeof(param_name);
+ unsigned int arg_count = CopyToArgs(args + 3, param_name,
+ sizeof(param_name));
+ helper_->AddCommand(CREATE_PARAM_BY_NAME_IMMEDIATE, 3 + arg_count, args);
+ CHECK_ERROR(helper_);
+ }
+
+ // Bind textures to the parameters
+ args[0].value_uint32 = noise_sampler_param_id_;
+ args[1].value_uint32 = sizeof(Uint32); // NOLINT
+ args[2].value_uint32 = noise_sampler_id_;
+ helper_->AddCommand(SET_PARAM_DATA_IMMEDIATE, 3, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 = iridescence_sampler_param_id_;
+ args[1].value_uint32 = sizeof(Uint32); // NOLINT
+ args[2].value_uint32 = iridescence_sampler_id_;
+ helper_->AddCommand(SET_PARAM_DATA_IMMEDIATE, 3, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 = cubemap_sampler_param_id_;
+ args[1].value_uint32 = sizeof(Uint32); // NOLINT
+ args[2].value_uint32 = cubemap_sampler_id_;
+ helper_->AddCommand(SET_PARAM_DATA_IMMEDIATE, 3, args);
+ CHECK_ERROR(helper_);
+
+ // Create our random bubbles.
+ for (unsigned int i = 0; i < kBubbleCount; ++i) {
+ Bubble bubble;
+ bubble.position = math::Point3(Randf(-6.f, 6.f, &seed_),
+ Randf(-6.f, 6.f, &seed_),
+ Randf(-6.f, 6.f, &seed_));
+ bubble.rotation_speed = math::Vector3(Randf(-.1f, .1f, &seed_),
+ Randf(-.1f, .1f, &seed_),
+ Randf(-.1f, .1f, &seed_));
+ bubble.scale = Randf(.5, 2.f, &seed_);
+ float max_thickness = Randf(.3f, .5f, &seed_);
+ float min_thickness = Randf(.3f, max_thickness, &seed_);
+ // thickness = base * e^(-y*falloff) for y in [-scale..scale].
+ bubble.thickness_falloff =
+ logf(max_thickness/min_thickness)/(2 * bubble.scale);
+ bubble.base_thickness =
+ max_thickness * expf(-bubble.scale * bubble.thickness_falloff);
+ bubble.noise_ratio = Randf(.2f, .5f, &seed_);
+ bubbles_.push_back(bubble);
+ }
+ start_time_ = GetTimeUsec();
+}
+
+void BubbleDemo::Finalize() {
+ helper_->Finish();
+
+ allocator_->Free(iridescence_texture_);
+ allocator_->Free(noise_texture_);
+ allocator_->Free(indices_);
+ allocator_->Free(vertices_);
+ allocator_.reset(NULL);
+
+ helper_.reset(NULL);
+
+ proxy_->CloseConnection();
+ proxy_->UnregisterSharedMemory(shm_id_);
+ proxy_.reset(NULL);
+ DestroyShm(shm_);
+
+ sender_->SendCall(POISONED_MESSAGE_ID, NULL, 0, NULL, 0);
+ sender_.reset(NULL);
+ nacl::Close(handle_pair_[0]);
+ handle_pair_[0] = nacl::kInvalidHtpHandle;
+ nacl::Close(handle_pair_[1]);
+ handle_pair_[1] = nacl::kInvalidHtpHandle;
+}
+
+void BubbleDemo::DrawBubble(const math::Matrix4& view,
+ const math::Matrix4& proj,
+ const BubbleDemo::Bubble &bubble,
+ const math::Vector3& rotation) {
+ math::Matrix4 view_inv = math::inverse(view);
+ math::Point3 eye(view_inv.getTranslation());
+ math::Matrix4 model =
+ math::Matrix4::translation(math::Vector3(bubble.position)) *
+ math::Matrix4::scale(math::Vector3(bubble.scale, bubble.scale,
+ bubble.scale)) *
+ math::Matrix4::rotationZYX(rotation);
+ math::Matrix4 modelIT = math::inverse(math::transpose(model));
+ math::Matrix4 mvp = proj * view * model;
+
+ // AddCommand copies the args, so it is safe to re-use args across various
+ // calls.
+ // 20 is the largest command we use (SET_PARAM_DATA_IMMEDIATE for matrices).
+ CommandBufferEntry args[20];
+
+ args[0].value_uint32 = vertex_struct_id_;
+ helper_->AddCommand(SET_VERTEX_STRUCT, 1, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 = mvp_param_id_;
+ args[1].value_uint32 = sizeof(mvp);
+ unsigned int arg_count = CopyToArgs(args + 2, &mvp, sizeof(mvp));
+ helper_->AddCommand(SET_PARAM_DATA_IMMEDIATE, 2 + arg_count, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 = world_param_id_;
+ args[1].value_uint32 = sizeof(model);
+ arg_count = CopyToArgs(args + 2, &model, sizeof(model));
+ helper_->AddCommand(SET_PARAM_DATA_IMMEDIATE, 2 + arg_count, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 = worldIT_param_id_;
+ args[1].value_uint32 = sizeof(modelIT);
+ arg_count = CopyToArgs(args + 2, &modelIT, sizeof(modelIT));
+ helper_->AddCommand(SET_PARAM_DATA_IMMEDIATE, 2 + arg_count, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 = eye_param_id_;
+ args[1].value_uint32 = sizeof(eye);
+ arg_count = CopyToArgs(args + 2, &eye, sizeof(eye));
+ helper_->AddCommand(SET_PARAM_DATA_IMMEDIATE, 2 + arg_count, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 =
+ set_blending::ColorSrcFunc::MakeValue(GAPIInterface::BLEND_FUNC_ONE) |
+ set_blending::ColorDstFunc::MakeValue(
+ GAPIInterface::BLEND_FUNC_SRC_ALPHA) |
+ set_blending::ColorEq::MakeValue(GAPIInterface::BLEND_EQ_ADD) |
+ set_blending::SeparateAlpha::MakeValue(0) |
+ set_blending::Enable::MakeValue(1);
+ helper_->AddCommand(SET_BLENDING, 1, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 = effect_id_;
+ helper_->AddCommand(SET_EFFECT, 1, args);
+ CHECK_ERROR(helper_);
+
+ // Draw back faces first.
+ args[0].value_uint32 =
+ set_polygon_raster::FillMode::MakeValue(
+ GAPIInterface::POLYGON_MODE_FILL) |
+ set_polygon_raster::CullMode::MakeValue(GAPIInterface::CULL_CCW);
+ helper_->AddCommand(SET_POLYGON_RASTER, 1, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 = thickness_param_id_;
+ args[1].value_uint32 = 4*sizeof(float); // NOLINT
+ args[2].value_float = bubble.thickness_falloff;
+ args[3].value_float = bubble.base_thickness;
+ args[4].value_float = bubble.noise_ratio;
+ args[5].value_float = .5f; // back face attenuation
+ helper_->AddCommand(SET_PARAM_DATA_IMMEDIATE, 6, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 = GAPIInterface::TRIANGLES;
+ args[1].value_uint32 = index_buffer_id_;
+ args[2].value_uint32 = 0; // first
+ args[3].value_uint32 = kIndexCount/3; // primitive count
+ args[4].value_uint32 = 0; // min index
+ args[5].value_uint32 = kVertexCount-1; // max index
+ helper_->AddCommand(DRAW_INDEXED, 6, args);
+ CHECK_ERROR(helper_);
+
+ // Then front faces.
+ args[0].value_uint32 =
+ set_polygon_raster::FillMode::MakeValue(
+ GAPIInterface::POLYGON_MODE_FILL) |
+ set_polygon_raster::CullMode::MakeValue(GAPIInterface::CULL_CW);
+ helper_->AddCommand(SET_POLYGON_RASTER, 1, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 = thickness_param_id_;
+ args[1].value_uint32 = 4*sizeof(float); // NOLINT
+ args[2].value_float = bubble.thickness_falloff;
+ args[3].value_float = bubble.base_thickness;
+ args[4].value_float = bubble.noise_ratio;
+ args[5].value_float = 1.f;
+ helper_->AddCommand(SET_PARAM_DATA_IMMEDIATE, 6, args);
+ CHECK_ERROR(helper_);
+
+ args[0].value_uint32 = GAPIInterface::TRIANGLES;
+ args[1].value_uint32 = index_buffer_id_;
+ args[2].value_uint32 = 0; // first
+ args[3].value_uint32 = kIndexCount/3; // primitive count
+ args[4].value_uint32 = 0; // min index
+ args[5].value_uint32 = kVertexCount-1; // max index
+ helper_->AddCommand(DRAW_INDEXED, 6, args);
+ CHECK_ERROR(helper_);
+}
+
+void BubbleDemo::Render() {
+ uint64_t time_usec = GetTimeUsec() - start_time_;
+ time_ = time_usec * 1.e-6f;
+ // Camera path
+ float r = 20.f;
+ float theta = time_ / 4.f;
+ float phi = 2 * theta;
+ math::Point3 eye(r * cosf(theta), r / 3.f * sinf(phi), r * sinf(theta));
+ math::Point3 target(0.f, 0.f, 0.f);
+ math::Vector3 up(0.f, 1.f, 0.f);
+ math::Matrix4 proj =
+ math::CreatePerspectiveMatrix(kPi / 4.f, 1.f, .1f, 10000.f);
+ math::Matrix4 view = math::Matrix4::lookAt(eye, target, up);
+
+ helper_->AddCommand(BEGIN_FRAME, 0 , NULL);
+ CHECK_ERROR(helper_);
+ RGBA color = {0.2f, 0.2f, 0.2f, 1.f};
+ ClearCmd(helper_.get(), GAPIInterface::COLOR | GAPIInterface::DEPTH, color,
+ 1.f, 0);
+
+ // Sort bubbles back-to-front.
+ std::sort(bubbles_.begin(), bubbles_.end(), BubbleSorter(view));
+ // Then render them all.
+ for (unsigned int i = 0; i < bubbles_.size(); ++i) {
+ const Bubble &bubble = bubbles_[i];
+ DrawBubble(view, proj, bubble, time_ * 2.f * kPi * bubble.rotation_speed);
+ }
+
+ helper_->AddCommand(END_FRAME, 0 , NULL);
+ CHECK_ERROR(helper_);
+ helper_->Flush();
+}
+
+} // namespace command_buffer
+} // namespace o3d
+
+// Scriptable object for the plug-in, provides the glue with the browser.
+// Creates a BubbleDemo object and delegates calls to it.
+class Plugin : public NPObject {
+ public:
+ NPError SetWindow(NPWindow *window) { return NPERR_NO_ERROR;}
+
+ static NPClass *GetNPClass() {
+ return &class_;
+ }
+
+ private:
+ explicit Plugin(NPP npp);
+ ~Plugin();
+
+ nacl::HtpHandle Create();
+ void Initialize();
+ void Destroy();
+ void Render();
+
+ static NPObject *Allocate(NPP npp, NPClass *npclass);
+ static void Deallocate(NPObject *object);
+ static bool HasMethod(NPObject *header, NPIdentifier name);
+ static bool Invoke(NPObject *header, NPIdentifier name,
+ const NPVariant *args, uint32_t argCount,
+ NPVariant *result);
+ static bool InvokeDefault(NPObject *header, const NPVariant *args,
+ uint32_t argCount, NPVariant *result);
+ static bool HasProperty(NPObject *header, NPIdentifier name);
+ static bool GetProperty(NPObject *header, NPIdentifier name,
+ NPVariant *variant);
+ static bool SetProperty(NPObject *header, NPIdentifier name,
+ const NPVariant *variant);
+ static bool Enumerate(NPObject *header, NPIdentifier **value,
+ uint32_t *count);
+
+ NPP npp_;
+ static NPClass class_;
+ NPIdentifier create_id_;
+ NPIdentifier initialize_id_;
+ NPIdentifier destroy_id_;
+ NPIdentifier render_id_;
+
+ scoped_ptr<o3d::command_buffer::BubbleDemo> demo_;
+};
+
+Plugin::Plugin(NPP npp)
+ : npp_(npp) {
+ const char *names[4] = {"create", "initialize", "destroy", "render"};
+ NPIdentifier ids[4];
+ NPN_GetStringIdentifiers(names, 4, ids);
+ create_id_ = ids[0];
+ initialize_id_ = ids[1];
+ destroy_id_ = ids[2];
+ render_id_ = ids[3];
+}
+
+Plugin::~Plugin() {
+ if (demo_.get()) demo_->Finalize();
+}
+
+nacl::HtpHandle Plugin::Create() {
+ demo_.reset(new o3d::command_buffer::BubbleDemo());
+ return demo_->CreateSockets();
+}
+
+void Plugin::Initialize() {
+ if (demo_.get()) demo_->Initialize();
+}
+
+void Plugin::Destroy() {
+ if (demo_.get()) {
+ demo_->Finalize();
+ demo_.reset(NULL);
+ }
+}
+
+void Plugin::Render() {
+ if (demo_.get()) demo_->Render();
+}
+
+NPClass Plugin::class_ = {
+ NP_CLASS_STRUCT_VERSION,
+ Plugin::Allocate,
+ Plugin::Deallocate,
+ 0,
+ Plugin::HasMethod,
+ Plugin::Invoke,
+ 0,
+ Plugin::HasProperty,
+ Plugin::GetProperty,
+ Plugin::SetProperty,
+ 0,
+ Plugin::Enumerate,
+};
+
+NPObject *Plugin::Allocate(NPP npp, NPClass *npclass) {
+ return new Plugin(npp);
+}
+
+void Plugin::Deallocate(NPObject *object) {
+ delete static_cast<Plugin *>(object);
+}
+
+bool Plugin::HasMethod(NPObject *header, NPIdentifier name) {
+ Plugin *plugin = static_cast<Plugin *>(header);
+ return (name == plugin->create_id_ ||
+ name == plugin->initialize_id_ ||
+ name == plugin->destroy_id_ ||
+ name == plugin->render_id_);
+}
+
+bool Plugin::Invoke(NPObject *header, NPIdentifier name,
+ const NPVariant *args, uint32_t argCount,
+ NPVariant *result) {
+ Plugin *plugin = static_cast<Plugin *>(header);
+ VOID_TO_NPVARIANT(*result);
+ if (name == plugin->create_id_ && argCount == 0) {
+ nacl::HtpHandle handle = plugin->Create();
+ if (handle == nacl::kInvalidHtpHandle) {
+ return false;
+ }
+ HANDLE_TO_NPVARIANT(handle, *result);
+ return true;
+ } else if (name == plugin->initialize_id_ && argCount == 0) {
+ plugin->Initialize();
+ return true;
+ } else if (name == plugin->destroy_id_ && argCount == 0) {
+ plugin->Destroy();
+ return true;
+ } else if (name == plugin->render_id_ && argCount == 0) {
+ plugin->Render();
+ return true;
+ } else {
+ return false;
+ }
+}
+
+bool Plugin::InvokeDefault(NPObject *header, const NPVariant *args,
+ uint32_t argCount, NPVariant *result) {
+ return false;
+}
+
+bool Plugin::HasProperty(NPObject *header, NPIdentifier name) {
+ return false;
+}
+
+bool Plugin::GetProperty(NPObject *header, NPIdentifier name,
+ NPVariant *variant) {
+ return false;
+}
+
+bool Plugin::SetProperty(NPObject *header, NPIdentifier name,
+ const NPVariant *variant) {
+ return false;
+}
+
+bool Plugin::Enumerate(NPObject *header, NPIdentifier **value,
+ uint32_t *count) {
+ Plugin *plugin = static_cast<Plugin *>(header);
+ *count = 4;
+ NPIdentifier *ids = static_cast<NPIdentifier *>(
+ NPN_MemAlloc(*count * sizeof(NPIdentifier)));
+ ids[0] = plugin->create_id_;
+ ids[1] = plugin->initialize_id_;
+ ids[2] = plugin->destroy_id_;
+ ids[3] = plugin->render_id_;
+ *value = ids;
+ return true;
+}
+
+NPError NPP_New(NPMIMEType mime_type, NPP instance, uint16_t mode,
+ int16_t argc, char* argn[], char* argv[],
+ NPSavedData* saved) {
+ if (instance == NULL) {
+ return NPERR_INVALID_INSTANCE_ERROR;
+ }
+
+ NPObject *object = NPN_CreateObject(instance, Plugin::GetNPClass());
+ if (object == NULL) {
+ return NPERR_OUT_OF_MEMORY_ERROR;
+ }
+
+ instance->pdata = object;
+ return NPERR_NO_ERROR;
+}
+
+NPError NPP_Destroy(NPP instance, NPSavedData** save) {
+ if (instance == NULL) {
+ return NPERR_INVALID_INSTANCE_ERROR;
+ }
+
+ Plugin* plugin = static_cast<Plugin*>(instance->pdata);
+ if (plugin != NULL) {
+ NPN_ReleaseObject(plugin);
+ }
+ return NPERR_NO_ERROR;
+}
+
+NPObject* NPP_GetScriptableInstance(NPP instance) {
+ if (instance == NULL) {
+ return NULL;
+ }
+
+ NPObject* object = static_cast<NPObject*>(instance->pdata);
+ if (object) {
+ NPN_RetainObject(object);
+ }
+ return object;
+}
+
+NPError NPP_SetWindow(NPP instance, NPWindow* window) {
+ if (instance == NULL) {
+ return NPERR_INVALID_INSTANCE_ERROR;
+ }
+ if (window == NULL) {
+ return NPERR_GENERIC_ERROR;
+ }
+ Plugin* plugin = static_cast<Plugin*>(instance->pdata);
+ if (plugin != NULL) {
+ return plugin->SetWindow(window);
+ }
+ return NPERR_GENERIC_ERROR;
+}
+
+int main(int argc, char **argv) {
+ printf("Bubble demo\n");
+ NaClNP_Init(&argc, argv);
+ NaClNP_MainLoop(0);
+ return 0;
+}
diff --git a/o3d/command_buffer/samples/bubble/cubemap.cc b/o3d/command_buffer/samples/bubble/cubemap.cc
new file mode 100644
index 0000000..1445f5e
--- /dev/null
+++ b/o3d/command_buffer/samples/bubble/cubemap.cc
@@ -0,0 +1,12326 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the environment cube map for the bubble demo. It is
+// hard-coded as a byte array. Format is 64x64xBRGA, D3D face ordering (+X,
+// -X, +Y, -Y, +Z, -Z).
+
+unsigned char g_cubemap_data[] = {
+ 0xef, 0xdb, 0xce, 0xff, 0xef, 0xdb, 0xce, 0xff,
+ 0xd6, 0xc3, 0xb3, 0xff, 0xee, 0xda, 0xcd, 0xff,
+ 0xff, 0xf7, 0xef, 0xff, 0xff, 0xf7, 0xef, 0xff,
+ 0xf4, 0xe6, 0xd6, 0xff, 0xf4, 0xe5, 0xd6, 0xff,
+ 0xff, 0xfb, 0xef, 0xff, 0xff, 0xfb, 0xef, 0xff,
+ 0xff, 0xfb, 0xef, 0xff, 0xff, 0xfb, 0xee, 0xff,
+ 0xff, 0xef, 0xd6, 0xff, 0xff, 0xef, 0xd6, 0xff,
+ 0xd9, 0xc3, 0xb0, 0xff, 0xd8, 0xc2, 0xaf, 0xff,
+ 0xff, 0xe3, 0xc6, 0xff, 0xff, 0xe3, 0xc5, 0xff,
+ 0xff, 0xe3, 0xc6, 0xff, 0xff, 0xe3, 0xc5, 0xff,
+ 0xff, 0xcf, 0xbe, 0xff, 0xff, 0xc8, 0xb2, 0xff,
+ 0xff, 0xc1, 0xa8, 0xff, 0xff, 0xba, 0x9c, 0xff,
+ 0xfd, 0xb5, 0x9d, 0xff, 0xf9, 0xaf, 0x94, 0xff,
+ 0xfa, 0xb0, 0x94, 0xff, 0xf7, 0xaa, 0x8c, 0xff,
+ 0xf7, 0xaa, 0x8c, 0xff, 0xf1, 0xa6, 0x89, 0xff,
+ 0xf2, 0xa6, 0x89, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xe7, 0x9c, 0x81, 0xff, 0xe6, 0x98, 0x7e, 0xff,
+ 0xe7, 0x96, 0x7c, 0xff, 0xe6, 0x96, 0x7b, 0xff,
+ 0xe7, 0x94, 0x79, 0xff, 0xe6, 0x92, 0x7b, 0xff,
+ 0xe7, 0x92, 0x7c, 0xff, 0xe6, 0x93, 0x78, 0xff,
+ 0xea, 0x95, 0x7c, 0xff, 0xec, 0x9b, 0x84, 0xff,
+ 0xef, 0xa2, 0x8c, 0xff, 0xec, 0x9b, 0x83, 0xff,
+ 0xe7, 0x9a, 0x7c, 0xff, 0xe6, 0x92, 0x76, 0xff,
+ 0xe7, 0x8e, 0x74, 0xff, 0xe6, 0x8e, 0x73, 0xff,
+ 0xe7, 0x8e, 0x6b, 0xff, 0xe6, 0x8e, 0x6b, 0xff,
+ 0xe7, 0x8f, 0x6e, 0xff, 0xe6, 0x8f, 0x6e, 0xff,
+ 0xe7, 0x8e, 0x6b, 0xff, 0xe6, 0x8e, 0x6b, 0xff,
+ 0xe9, 0x92, 0x71, 0xff, 0xe6, 0x8e, 0x6b, 0xff,
+ 0xea, 0x92, 0x76, 0xff, 0xe6, 0x8e, 0x73, 0xff,
+ 0xe9, 0x92, 0x76, 0xff, 0xec, 0x96, 0x78, 0xff,
+ 0xef, 0x9a, 0x7c, 0xff, 0xef, 0x9a, 0x7b, 0xff,
+ 0xef, 0xa0, 0x81, 0xff, 0xee, 0x9f, 0x81, 0xff,
+ 0xd6, 0xc2, 0xb2, 0xff, 0xee, 0xda, 0xcd, 0xff,
+ 0xbd, 0xaa, 0x97, 0xff, 0xa4, 0x91, 0x7b, 0xff,
+ 0xff, 0xf7, 0xef, 0xff, 0xff, 0xf6, 0xee, 0xff,
+ 0xf4, 0xe6, 0xd6, 0xff, 0xff, 0xf7, 0xee, 0xff,
+ 0xff, 0xfb, 0xef, 0xff, 0xff, 0xfb, 0xee, 0xff,
+ 0xfa, 0xec, 0xdc, 0xff, 0xff, 0xfb, 0xee, 0xff,
+ 0xff, 0xef, 0xd6, 0xff, 0xff, 0xee, 0xd5, 0xff,
+ 0xd9, 0xc3, 0xb0, 0xff, 0xb2, 0x95, 0x89, 0xff,
+ 0xad, 0x8f, 0x73, 0xff, 0xd5, 0xb8, 0x9c, 0xff,
+ 0xff, 0xe3, 0xc6, 0xff, 0xff, 0xe2, 0xc5, 0xff,
+ 0xff, 0xcf, 0xbd, 0xff, 0xff, 0xc7, 0xb2, 0xff,
+ 0xff, 0xc1, 0xa7, 0xff, 0xff, 0xc1, 0xa7, 0xff,
+ 0xfc, 0xb5, 0x9c, 0xff, 0xfc, 0xb4, 0x9c, 0xff,
+ 0xfa, 0xb0, 0x94, 0xff, 0xf6, 0xaa, 0x8c, 0xff,
+ 0xf7, 0xaa, 0x8c, 0xff, 0xf1, 0xa6, 0x89, 0xff,
+ 0xf2, 0xa6, 0x89, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xe6, 0x9e, 0x84, 0xff, 0xe6, 0x9b, 0x80, 0xff,
+ 0xe7, 0x99, 0x7e, 0xff, 0xe6, 0x98, 0x7e, 0xff,
+ 0xe6, 0x95, 0x76, 0xff, 0xe6, 0x93, 0x78, 0xff,
+ 0xe7, 0x93, 0x79, 0xff, 0xe6, 0x93, 0x78, 0xff,
+ 0xe9, 0x95, 0x7b, 0xff, 0xe9, 0x94, 0x7b, 0xff,
+ 0xec, 0x9b, 0x84, 0xff, 0xec, 0x9b, 0x83, 0xff,
+ 0xe6, 0x96, 0x79, 0xff, 0xe6, 0x91, 0x75, 0xff,
+ 0xe7, 0x8e, 0x73, 0xff, 0xe6, 0x8d, 0x73, 0xff,
+ 0xe6, 0x8e, 0x6b, 0xff, 0xe6, 0x8f, 0x6d, 0xff,
+ 0xe7, 0x91, 0x71, 0xff, 0xe6, 0x8f, 0x6d, 0xff,
+ 0xe9, 0x92, 0x71, 0xff, 0xe6, 0x8d, 0x6b, 0xff,
+ 0xe7, 0x8e, 0x6b, 0xff, 0xe9, 0x91, 0x70, 0xff,
+ 0xe6, 0x8e, 0x73, 0xff, 0xe9, 0x91, 0x75, 0xff,
+ 0xe9, 0x92, 0x76, 0xff, 0xec, 0x95, 0x78, 0xff,
+ 0xef, 0x9a, 0x7b, 0xff, 0xee, 0x9c, 0x7e, 0xff,
+ 0xef, 0x9f, 0x81, 0xff, 0xee, 0x9f, 0x81, 0xff,
+ 0xef, 0xdb, 0xce, 0xff, 0xd6, 0xc2, 0xb2, 0xff,
+ 0xd6, 0xc3, 0xb3, 0xff, 0xbd, 0xaa, 0x97, 0xff,
+ 0xf4, 0xe6, 0xd6, 0xff, 0xf4, 0xe5, 0xd6, 0xff,
+ 0xf4, 0xe6, 0xd6, 0xff, 0xf4, 0xe5, 0xd6, 0xff,
+ 0xff, 0xfb, 0xef, 0xff, 0xf4, 0xdd, 0xc8, 0xff,
+ 0xfa, 0xed, 0xdc, 0xff, 0xff, 0xfb, 0xee, 0xff,
+ 0xff, 0xef, 0xd6, 0xff, 0xff, 0xef, 0xd6, 0xff,
+ 0xb3, 0x96, 0x8a, 0xff, 0x8c, 0x69, 0x63, 0xff,
+ 0x84, 0x65, 0x4a, 0xff, 0xad, 0x8f, 0x73, 0xff,
+ 0xd6, 0xb9, 0x9d, 0xff, 0xff, 0xe3, 0xc5, 0xff,
+ 0xff, 0xcf, 0xbd, 0xff, 0xff, 0xce, 0xbd, 0xff,
+ 0xff, 0xc1, 0xa8, 0xff, 0xff, 0xc1, 0xa7, 0xff,
+ 0xff, 0xba, 0xa5, 0xff, 0xfc, 0xb5, 0x9c, 0xff,
+ 0xfa, 0xb0, 0x94, 0xff, 0xf9, 0xaf, 0x94, 0xff,
+ 0xf7, 0xaa, 0x8c, 0xff, 0xf7, 0xaa, 0x8c, 0xff,
+ 0xec, 0xa2, 0x87, 0xff, 0xec, 0xa2, 0x86, 0xff,
+ 0xe7, 0x9e, 0x84, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xe7, 0x99, 0x7f, 0xff, 0xe6, 0x98, 0x7e, 0xff,
+ 0xe7, 0x95, 0x76, 0xff, 0xe6, 0x93, 0x78, 0xff,
+ 0xe7, 0x92, 0x7c, 0xff, 0xe6, 0x93, 0x79, 0xff,
+ 0xe7, 0x8e, 0x73, 0xff, 0xe6, 0x8d, 0x73, 0xff,
+ 0xe7, 0x8e, 0x74, 0xff, 0xe9, 0x94, 0x7b, 0xff,
+ 0xe7, 0x92, 0x76, 0xff, 0xe6, 0x91, 0x76, 0xff,
+ 0xe7, 0x8e, 0x74, 0xff, 0xe6, 0x8e, 0x73, 0xff,
+ 0xe7, 0x8f, 0x6e, 0xff, 0xe6, 0x8f, 0x6d, 0xff,
+ 0xe7, 0x91, 0x71, 0xff, 0xe6, 0x90, 0x70, 0xff,
+ 0xe9, 0x92, 0x71, 0xff, 0xe9, 0x91, 0x70, 0xff,
+ 0xe9, 0x92, 0x71, 0xff, 0xec, 0x96, 0x76, 0xff,
+ 0xec, 0x96, 0x79, 0xff, 0xe9, 0x91, 0x76, 0xff,
+ 0xec, 0x96, 0x79, 0xff, 0xee, 0x9a, 0x7b, 0xff,
+ 0xef, 0x9d, 0x7e, 0xff, 0xee, 0x9f, 0x81, 0xff,
+ 0xef, 0x9d, 0x7f, 0xff, 0xee, 0x9f, 0x81, 0xff,
+ 0xef, 0xdb, 0xce, 0xff, 0xd6, 0xc2, 0xb2, 0xff,
+ 0xbd, 0xaa, 0x97, 0xff, 0xa4, 0x91, 0x7b, 0xff,
+ 0xde, 0xc2, 0xa5, 0xff, 0xe9, 0xd3, 0xbd, 0xff,
+ 0xf4, 0xe5, 0xd6, 0xff, 0xe9, 0xd3, 0xbd, 0xff,
+ 0xef, 0xcf, 0xb5, 0xff, 0xf4, 0xdd, 0xc8, 0xff,
+ 0xfa, 0xec, 0xdb, 0xff, 0xff, 0xfa, 0xee, 0xff,
+ 0xff, 0xef, 0xd6, 0xff, 0xff, 0xee, 0xd6, 0xff,
+ 0xb2, 0x96, 0x89, 0xff, 0x8b, 0x69, 0x62, 0xff,
+ 0x84, 0x65, 0x4a, 0xff, 0xac, 0x8f, 0x73, 0xff,
+ 0xd6, 0xb9, 0x9c, 0xff, 0xd5, 0xb8, 0x9c, 0xff,
+ 0xff, 0xcf, 0xbd, 0xff, 0xff, 0xc7, 0xb2, 0xff,
+ 0xff, 0xc8, 0xb2, 0xff, 0xff, 0xc0, 0xa7, 0xff,
+ 0xff, 0xba, 0xa5, 0xff, 0xfc, 0xb4, 0x9c, 0xff,
+ 0xfc, 0xb5, 0x9c, 0xff, 0xf9, 0xaf, 0x94, 0xff,
+ 0xf7, 0xaa, 0x8c, 0xff, 0xf6, 0xaa, 0x8b, 0xff,
+ 0xec, 0xa2, 0x86, 0xff, 0xeb, 0xa1, 0x86, 0xff,
+ 0xe6, 0x9e, 0x84, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xe6, 0x9b, 0x81, 0xff, 0xe6, 0x98, 0x7e, 0xff,
+ 0xe6, 0x95, 0x76, 0xff, 0xe6, 0x93, 0x78, 0xff,
+ 0xe6, 0x94, 0x76, 0xff, 0xe6, 0x93, 0x78, 0xff,
+ 0xe6, 0x8e, 0x73, 0xff, 0xe9, 0x94, 0x7b, 0xff,
+ 0xe9, 0x94, 0x7b, 0xff, 0xe9, 0x94, 0x7b, 0xff,
+ 0xe6, 0x92, 0x76, 0xff, 0xe6, 0x91, 0x76, 0xff,
+ 0xe6, 0x92, 0x76, 0xff, 0xe6, 0x91, 0x75, 0xff,
+ 0xe6, 0x91, 0x71, 0xff, 0xe6, 0x91, 0x73, 0xff,
+ 0xe6, 0x92, 0x73, 0xff, 0xe6, 0x91, 0x73, 0xff,
+ 0xe9, 0x92, 0x71, 0xff, 0xeb, 0x95, 0x76, 0xff,
+ 0xef, 0x9a, 0x7b, 0xff, 0xeb, 0x95, 0x75, 0xff,
+ 0xec, 0x96, 0x79, 0xff, 0xeb, 0x95, 0x78, 0xff,
+ 0xef, 0x9a, 0x7b, 0xff, 0xee, 0x99, 0x7b, 0xff,
+ 0xef, 0x9a, 0x7c, 0xff, 0xee, 0x9c, 0x7e, 0xff,
+ 0xef, 0x9a, 0x7b, 0xff, 0xee, 0x9c, 0x7e, 0xff,
+ 0xd4, 0xc5, 0xb8, 0xff, 0xc0, 0xaf, 0xa2, 0xff,
+ 0xad, 0x9a, 0x8c, 0xff, 0xad, 0x9a, 0x8c, 0xff,
+ 0xcb, 0xb7, 0xa0, 0xff, 0xcb, 0xb6, 0x9f, 0xff,
+ 0xe7, 0xcf, 0xb5, 0xff, 0xe6, 0xce, 0xb5, 0xff,
+ 0xef, 0xd7, 0xc6, 0xff, 0xef, 0xd6, 0xc5, 0xff,
+ 0xef, 0xd7, 0xc6, 0xff, 0xee, 0xd6, 0xc5, 0xff,
+ 0xef, 0xd7, 0xc6, 0xff, 0xef, 0xd6, 0xc5, 0xff,
+ 0x9d, 0x86, 0x79, 0xff, 0x73, 0x5d, 0x52, 0xff,
+ 0x5b, 0x45, 0x32, 0xff, 0x9c, 0x75, 0x63, 0xff,
+ 0xbe, 0x8e, 0x7c, 0xff, 0xbd, 0x8e, 0x7b, 0xff,
+ 0xec, 0xc0, 0xa2, 0xff, 0xff, 0xd2, 0xb5, 0xff,
+ 0xec, 0xc0, 0xa2, 0xff, 0xec, 0xbf, 0xa2, 0xff,
+ 0xff, 0xc0, 0xa5, 0xff, 0xff, 0xb9, 0x9c, 0xff,
+ 0xff, 0xb2, 0x94, 0xff, 0xff, 0xb2, 0x94, 0xff,
+ 0xf7, 0xb3, 0x95, 0xff, 0xf1, 0xa5, 0x89, 0xff,
+ 0xf2, 0xa5, 0x89, 0xff, 0xee, 0x9e, 0x83, 0xff,
+ 0xef, 0x9e, 0x84, 0xff, 0xef, 0x9e, 0x84, 0xff,
+ 0xe9, 0x9c, 0x7e, 0xff, 0xe6, 0x9a, 0x7b, 0xff,
+ 0xec, 0x9a, 0x7f, 0xff, 0xe9, 0x96, 0x79, 0xff,
+ 0xe9, 0x96, 0x79, 0xff, 0xe9, 0x96, 0x78, 0xff,
+ 0xe7, 0x92, 0x74, 0xff, 0xe6, 0x92, 0x73, 0xff,
+ 0xe9, 0x96, 0x76, 0xff, 0xe6, 0x92, 0x73, 0xff,
+ 0xea, 0x96, 0x79, 0xff, 0xe6, 0x92, 0x73, 0xff,
+ 0xe7, 0x92, 0x74, 0xff, 0xe6, 0x92, 0x73, 0xff,
+ 0xe7, 0x92, 0x7c, 0xff, 0xe9, 0x98, 0x81, 0xff,
+ 0xe7, 0x92, 0x7c, 0xff, 0xe6, 0x92, 0x7b, 0xff,
+ 0xef, 0x96, 0x74, 0xff, 0xef, 0x96, 0x73, 0xff,
+ 0xef, 0x9c, 0x7c, 0xff, 0xee, 0x96, 0x73, 0xff,
+ 0xef, 0x9a, 0x7c, 0xff, 0xef, 0x9c, 0x7e, 0xff,
+ 0xef, 0x9d, 0x7e, 0xff, 0xee, 0x9c, 0x7e, 0xff,
+ 0xec, 0x9d, 0x81, 0xff, 0xf1, 0x9f, 0x7e, 0xff,
+ 0xec, 0x9d, 0x81, 0xff, 0xf7, 0xa2, 0x7b, 0xff,
+ 0xe6, 0xdb, 0xce, 0xff, 0xe6, 0xda, 0xcd, 0xff,
+ 0xc0, 0xb0, 0xa2, 0xff, 0xc0, 0xaf, 0xa1, 0xff,
+ 0xb0, 0x9e, 0x89, 0xff, 0xaf, 0x9d, 0x89, 0xff,
+ 0xe7, 0xcf, 0xb5, 0xff, 0xe6, 0xce, 0xb5, 0xff,
+ 0xc8, 0xaf, 0x9f, 0xff, 0xc8, 0xaf, 0x9f, 0xff,
+ 0xc8, 0xb0, 0x9f, 0xff, 0xc8, 0xaf, 0x9f, 0xff,
+ 0xc6, 0xae, 0x9f, 0xff, 0xc5, 0xae, 0x9f, 0xff,
+ 0xc6, 0xae, 0x9f, 0xff, 0x73, 0x5d, 0x52, 0xff,
+ 0x5b, 0x45, 0x31, 0xff, 0x7b, 0x5d, 0x4a, 0xff,
+ 0x7c, 0x5d, 0x4a, 0xff, 0x7b, 0x5d, 0x4a, 0xff,
+ 0xec, 0xc0, 0xa2, 0xff, 0xff, 0xd2, 0xb5, 0xff,
+ 0xec, 0xc0, 0xa2, 0xff, 0xec, 0xbf, 0xa1, 0xff,
+ 0xff, 0xc0, 0xa5, 0xff, 0xff, 0xb8, 0x9c, 0xff,
+ 0xff, 0xb2, 0x94, 0xff, 0xff, 0xb2, 0x94, 0xff,
+ 0xf7, 0xb2, 0x94, 0xff, 0xf4, 0xab, 0x8e, 0xff,
+ 0xf2, 0xa5, 0x89, 0xff, 0xf1, 0xa4, 0x89, 0xff,
+ 0xef, 0x9e, 0x84, 0xff, 0xee, 0x9d, 0x83, 0xff,
+ 0xef, 0x9e, 0x84, 0xff, 0xec, 0x9c, 0x81, 0xff,
+ 0xec, 0x9a, 0x7e, 0xff, 0xeb, 0x99, 0x7e, 0xff,
+ 0xe9, 0x96, 0x79, 0xff, 0xe9, 0x95, 0x78, 0xff,
+ 0xe6, 0x92, 0x73, 0xff, 0xe9, 0x95, 0x75, 0xff,
+ 0xe7, 0x92, 0x73, 0xff, 0xe9, 0x95, 0x76, 0xff,
+ 0xe9, 0x96, 0x79, 0xff, 0xe9, 0x95, 0x78, 0xff,
+ 0xe9, 0x96, 0x79, 0xff, 0xe6, 0x91, 0x73, 0xff,
+ 0xe6, 0x92, 0x7b, 0xff, 0xe9, 0x98, 0x80, 0xff,
+ 0xe9, 0x99, 0x81, 0xff, 0xe9, 0x98, 0x81, 0xff,
+ 0xef, 0x9b, 0x7b, 0xff, 0xee, 0x95, 0x73, 0xff,
+ 0xef, 0x96, 0x73, 0xff, 0xee, 0x9b, 0x7b, 0xff,
+ 0xef, 0x9d, 0x7e, 0xff, 0xee, 0x9f, 0x80, 0xff,
+ 0xef, 0x9f, 0x81, 0xff, 0xee, 0x9c, 0x7e, 0xff,
+ 0xf1, 0x9f, 0x7e, 0xff, 0xf1, 0x9f, 0x7e, 0xff,
+ 0xf2, 0x9f, 0x7e, 0xff, 0xf1, 0x9f, 0x7e, 0xff,
+ 0xd3, 0xc5, 0xb8, 0xff, 0xe6, 0xda, 0xcd, 0xff,
+ 0xd4, 0xc5, 0xb8, 0xff, 0xc0, 0xaf, 0xa2, 0xff,
+ 0x94, 0x86, 0x73, 0xff, 0x94, 0x85, 0x73, 0xff,
+ 0xcb, 0xb7, 0x9f, 0xff, 0xcb, 0xb6, 0x9f, 0xff,
+ 0xc8, 0xb0, 0x9f, 0xff, 0xa2, 0x88, 0x78, 0xff,
+ 0xa2, 0x89, 0x79, 0xff, 0x7b, 0x61, 0x52, 0xff,
+ 0x9d, 0x86, 0x79, 0xff, 0x73, 0x5d, 0x52, 0xff,
+ 0x9d, 0x86, 0x79, 0xff, 0x9c, 0x85, 0x79, 0xff,
+ 0x9d, 0x76, 0x63, 0xff, 0x7b, 0x5d, 0x4a, 0xff,
+ 0x7c, 0x5e, 0x4a, 0xff, 0x7b, 0x5d, 0x4a, 0xff,
+ 0xd9, 0xad, 0x8f, 0xff, 0xff, 0xd2, 0xb5, 0xff,
+ 0xff, 0xd3, 0xb5, 0xff, 0xec, 0xbf, 0xa2, 0xff,
+ 0xff, 0xc0, 0xa5, 0xff, 0xff, 0xb9, 0x9c, 0xff,
+ 0xff, 0xb9, 0x9d, 0xff, 0xff, 0xb2, 0x94, 0xff,
+ 0xf4, 0xac, 0x8f, 0xff, 0xf4, 0xab, 0x8e, 0xff,
+ 0xf2, 0xa5, 0x8a, 0xff, 0xee, 0x9e, 0x84, 0xff,
+ 0xef, 0x9e, 0x84, 0xff, 0xee, 0x9e, 0x83, 0xff,
+ 0xec, 0x9d, 0x81, 0xff, 0xec, 0x9c, 0x81, 0xff,
+ 0xec, 0x9a, 0x7e, 0xff, 0xec, 0x9a, 0x7e, 0xff,
+ 0xef, 0x9e, 0x84, 0xff, 0xec, 0x9a, 0x7e, 0xff,
+ 0xec, 0x9a, 0x79, 0xff, 0xe9, 0x96, 0x76, 0xff,
+ 0xe9, 0x96, 0x76, 0xff, 0xec, 0x9a, 0x79, 0xff,
+ 0xec, 0x9a, 0x7e, 0xff, 0xe9, 0x96, 0x78, 0xff,
+ 0xe9, 0x96, 0x79, 0xff, 0xec, 0x9a, 0x7e, 0xff,
+ 0xe9, 0x99, 0x81, 0xff, 0xec, 0x9f, 0x86, 0xff,
+ 0xe9, 0x99, 0x81, 0xff, 0xe9, 0x98, 0x81, 0xff,
+ 0xef, 0xa1, 0x84, 0xff, 0xee, 0xa0, 0x83, 0xff,
+ 0xef, 0xa1, 0x84, 0xff, 0xee, 0xa0, 0x84, 0xff,
+ 0xef, 0x9f, 0x81, 0xff, 0xee, 0x9f, 0x81, 0xff,
+ 0xef, 0xa0, 0x81, 0xff, 0xee, 0x9f, 0x81, 0xff,
+ 0xec, 0x9d, 0x81, 0xff, 0xf1, 0x9f, 0x7e, 0xff,
+ 0xf2, 0xa0, 0x7f, 0xff, 0xf1, 0x9f, 0x7e, 0xff,
+ 0xd3, 0xc5, 0xb8, 0xff, 0xc0, 0xaf, 0xa1, 0xff,
+ 0xad, 0x9a, 0x8c, 0xff, 0xd3, 0xc5, 0xb7, 0xff,
+ 0x94, 0x86, 0x73, 0xff, 0x94, 0x85, 0x73, 0xff,
+ 0x94, 0x86, 0x73, 0xff, 0xaf, 0x9d, 0x89, 0xff,
+ 0xa2, 0x88, 0x79, 0xff, 0x7b, 0x61, 0x52, 0xff,
+ 0x7b, 0x61, 0x52, 0xff, 0x7b, 0x61, 0x52, 0xff,
+ 0x73, 0x5d, 0x52, 0xff, 0x73, 0x5d, 0x52, 0xff,
+ 0x73, 0x5d, 0x52, 0xff, 0x73, 0x5d, 0x52, 0xff,
+ 0x7c, 0x5d, 0x4a, 0xff, 0x5a, 0x44, 0x31, 0xff,
+ 0x7b, 0x5d, 0x4a, 0xff, 0x9c, 0x75, 0x62, 0xff,
+ 0xc6, 0x9a, 0x7c, 0xff, 0xd8, 0xac, 0x8e, 0xff,
+ 0xc5, 0x9a, 0x7b, 0xff, 0xeb, 0xbf, 0xa1, 0xff,
+ 0xff, 0xc6, 0xad, 0xff, 0xff, 0xb8, 0x9c, 0xff,
+ 0xff, 0xb2, 0x94, 0xff, 0xff, 0xb2, 0x94, 0xff,
+ 0xf7, 0xb2, 0x94, 0xff, 0xf4, 0xab, 0x8e, 0xff,
+ 0xf1, 0xa5, 0x89, 0xff, 0xee, 0x9d, 0x83, 0xff,
+ 0xef, 0x9e, 0x84, 0xff, 0xeb, 0x9c, 0x81, 0xff,
+ 0xec, 0x9d, 0x81, 0xff, 0xe9, 0x9b, 0x7e, 0xff,
+ 0xec, 0x9a, 0x7e, 0xff, 0xeb, 0x99, 0x7e, 0xff,
+ 0xef, 0x9e, 0x84, 0xff, 0xee, 0x9d, 0x83, 0xff,
+ 0xef, 0x9e, 0x7c, 0xff, 0xeb, 0x99, 0x78, 0xff,
+ 0xec, 0x9a, 0x79, 0xff, 0xeb, 0x99, 0x78, 0xff,
+ 0xec, 0x9a, 0x7e, 0xff, 0xe9, 0x95, 0x78, 0xff,
+ 0xec, 0x9a, 0x7e, 0xff, 0xeb, 0x99, 0x7e, 0xff,
+ 0xec, 0x9f, 0x87, 0xff, 0xeb, 0x9f, 0x86, 0xff,
+ 0xef, 0xa6, 0x8c, 0xff, 0xee, 0xa5, 0x8b, 0xff,
+ 0xef, 0xa1, 0x84, 0xff, 0xee, 0xa0, 0x83, 0xff,
+ 0xef, 0xa1, 0x84, 0xff, 0xee, 0xa5, 0x8b, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa2, 0x83, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0x9f, 0x80, 0xff,
+ 0xf1, 0x9f, 0x7e, 0xff, 0xf1, 0x9f, 0x7e, 0xff,
+ 0xf1, 0x9f, 0x7e, 0xff, 0xeb, 0x9c, 0x80, 0xff,
+ 0xb5, 0xa2, 0x92, 0xff, 0xce, 0xb6, 0xa4, 0xff,
+ 0xb5, 0xa2, 0x92, 0xff, 0xb5, 0xa2, 0x91, 0xff,
+ 0xb5, 0xa2, 0x8c, 0xff, 0x9c, 0x8b, 0x76, 0xff,
+ 0x84, 0x74, 0x60, 0xff, 0xb5, 0xa2, 0x8c, 0xff,
+ 0x9d, 0x8a, 0x7c, 0xff, 0x70, 0x61, 0x55, 0xff,
+ 0x87, 0x76, 0x69, 0xff, 0x70, 0x61, 0x55, 0xff,
+ 0x76, 0x60, 0x4d, 0xff, 0x76, 0x60, 0x4d, 0xff,
+ 0x5b, 0x45, 0x32, 0xff, 0x5a, 0x45, 0x31, 0xff,
+ 0x53, 0x39, 0x2a, 0xff, 0x52, 0x39, 0x29, 0xff,
+ 0x6b, 0x54, 0x45, 0xff, 0x6b, 0x53, 0x44, 0xff,
+ 0xb0, 0x7e, 0x69, 0xff, 0xd6, 0x9e, 0x84, 0xff,
+ 0xb0, 0x7e, 0x69, 0xff, 0xaf, 0x7d, 0x68, 0xff,
+ 0xf7, 0xb7, 0x95, 0xff, 0xf7, 0xb6, 0x94, 0xff,
+ 0xf7, 0xb6, 0x94, 0xff, 0xf7, 0xb6, 0x94, 0xff,
+ 0xfa, 0xac, 0x8f, 0xff, 0xf9, 0xab, 0x8f, 0xff,
+ 0xf4, 0xa5, 0x89, 0xff, 0xee, 0x9e, 0x83, 0xff,
+ 0xef, 0x9e, 0x84, 0xff, 0xef, 0x9e, 0x84, 0xff,
+ 0xef, 0x9e, 0x84, 0xff, 0xee, 0x9e, 0x83, 0xff,
+ 0xe7, 0x9a, 0x84, 0xff, 0xec, 0x9f, 0x86, 0xff,
+ 0xec, 0xa0, 0x87, 0xff, 0xec, 0x9f, 0x86, 0xff,
+ 0xef, 0x9e, 0x84, 0xff, 0xef, 0x9f, 0x84, 0xff,
+ 0xef, 0xa0, 0x84, 0xff, 0xee, 0x9e, 0x83, 0xff,
+ 0xef, 0x9d, 0x7f, 0xff, 0xef, 0x9c, 0x7e, 0xff,
+ 0xef, 0x9a, 0x7c, 0xff, 0xee, 0x9f, 0x81, 0xff,
+ 0xf2, 0xa2, 0x81, 0xff, 0xf4, 0xa6, 0x86, 0xff,
+ 0xf2, 0xa2, 0x81, 0xff, 0xf4, 0xa6, 0x86, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xef, 0xa2, 0x84, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa2, 0x83, 0xff,
+ 0xff, 0xa6, 0x84, 0xff, 0xff, 0xa6, 0x84, 0xff,
+ 0xff, 0xa6, 0x84, 0xff, 0xe3, 0x98, 0x7e, 0xff,
+ 0xe7, 0x9a, 0x84, 0xff, 0xe6, 0x9a, 0x84, 0xff,
+ 0xe7, 0x9a, 0x84, 0xff, 0xd3, 0x90, 0x7b, 0xff,
+ 0x9c, 0x8e, 0x7e, 0xff, 0xb5, 0xa1, 0x91, 0xff,
+ 0xb5, 0xa2, 0x92, 0xff, 0x9c, 0x8d, 0x7e, 0xff,
+ 0x9c, 0x8b, 0x76, 0xff, 0x9c, 0x8b, 0x75, 0xff,
+ 0x84, 0x74, 0x60, 0xff, 0x83, 0x74, 0x60, 0xff,
+ 0x71, 0x61, 0x55, 0xff, 0x70, 0x61, 0x55, 0xff,
+ 0x87, 0x76, 0x68, 0xff, 0x86, 0x75, 0x68, 0xff,
+ 0x91, 0x7b, 0x68, 0xff, 0x75, 0x5f, 0x4c, 0xff,
+ 0x92, 0x7b, 0x68, 0xff, 0x76, 0x60, 0x4c, 0xff,
+ 0x6b, 0x54, 0x45, 0xff, 0x52, 0x38, 0x29, 0xff,
+ 0x52, 0x39, 0x29, 0xff, 0x6b, 0x53, 0x44, 0xff,
+ 0x89, 0x5d, 0x4d, 0xff, 0xaf, 0x7d, 0x68, 0xff,
+ 0x89, 0x5d, 0x4d, 0xff, 0x89, 0x5d, 0x4c, 0xff,
+ 0xc3, 0x8c, 0x6e, 0xff, 0xf6, 0xb6, 0x94, 0xff,
+ 0xf7, 0xb6, 0x94, 0xff, 0xf6, 0xb6, 0x94, 0xff,
+ 0xff, 0xb2, 0x94, 0xff, 0xf4, 0xa4, 0x89, 0xff,
+ 0xf4, 0xa5, 0x89, 0xff, 0xee, 0x9e, 0x83, 0xff,
+ 0xef, 0x9e, 0x84, 0xff, 0xee, 0x9d, 0x83, 0xff,
+ 0xef, 0x9e, 0x84, 0xff, 0xf1, 0xa2, 0x89, 0xff,
+ 0xec, 0x9f, 0x86, 0xff, 0xf1, 0xa4, 0x89, 0xff,
+ 0xf2, 0xa5, 0x89, 0xff, 0xec, 0x9f, 0x86, 0xff,
+ 0xef, 0xa1, 0x84, 0xff, 0xee, 0xa0, 0x83, 0xff,
+ 0xef, 0xa1, 0x84, 0xff, 0xee, 0xa0, 0x83, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0x9f, 0x80, 0xff,
+ 0xef, 0x9d, 0x7e, 0xff, 0xee, 0x9f, 0x81, 0xff,
+ 0xf1, 0xa2, 0x81, 0xff, 0xf1, 0xa1, 0x80, 0xff,
+ 0xef, 0x9e, 0x7c, 0xff, 0xf1, 0xa2, 0x81, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa1, 0x83, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa2, 0x83, 0xff,
+ 0xff, 0xa6, 0x84, 0xff, 0xff, 0xa6, 0x83, 0xff,
+ 0xe4, 0x99, 0x7e, 0xff, 0xc8, 0x8b, 0x78, 0xff,
+ 0xd3, 0x90, 0x7b, 0xff, 0xe6, 0x99, 0x83, 0xff,
+ 0xc0, 0x87, 0x73, 0xff, 0xc0, 0x87, 0x73, 0xff,
+ 0x9d, 0x8e, 0x7e, 0xff, 0x9c, 0x8d, 0x7e, 0xff,
+ 0x9d, 0x8e, 0x7f, 0xff, 0x9c, 0x8e, 0x7e, 0xff,
+ 0x84, 0x74, 0x60, 0xff, 0x83, 0x74, 0x60, 0xff,
+ 0x6b, 0x5e, 0x4a, 0xff, 0x84, 0x74, 0x60, 0xff,
+ 0x5b, 0x4d, 0x42, 0xff, 0x5a, 0x4d, 0x42, 0xff,
+ 0x71, 0x62, 0x55, 0xff, 0x70, 0x61, 0x55, 0xff,
+ 0x92, 0x7b, 0x68, 0xff, 0x91, 0x7b, 0x68, 0xff,
+ 0x92, 0x7b, 0x69, 0xff, 0x76, 0x60, 0x4d, 0xff,
+ 0x6b, 0x54, 0x45, 0xff, 0x6b, 0x53, 0x44, 0xff,
+ 0x53, 0x39, 0x2a, 0xff, 0x6b, 0x54, 0x44, 0xff,
+ 0x63, 0x3d, 0x32, 0xff, 0xaf, 0x7d, 0x68, 0xff,
+ 0x8a, 0x5e, 0x4d, 0xff, 0x63, 0x3d, 0x31, 0xff,
+ 0xc3, 0x8d, 0x6e, 0xff, 0xc2, 0x8c, 0x6d, 0xff,
+ 0x8f, 0x63, 0x48, 0xff, 0xf7, 0xb6, 0x94, 0xff,
+ 0xff, 0xb2, 0x94, 0xff, 0xf9, 0xab, 0x8e, 0xff,
+ 0xf4, 0xa5, 0x8a, 0xff, 0xee, 0x9e, 0x84, 0xff,
+ 0xef, 0x9e, 0x84, 0xff, 0xee, 0x9e, 0x83, 0xff,
+ 0xf2, 0xa2, 0x8a, 0xff, 0xf4, 0xa6, 0x8e, 0xff,
+ 0xf2, 0xa5, 0x89, 0xff, 0xf1, 0xa4, 0x89, 0xff,
+ 0xf2, 0xa5, 0x8a, 0xff, 0xf1, 0xa5, 0x89, 0xff,
+ 0xef, 0xa1, 0x84, 0xff, 0xee, 0xa0, 0x83, 0xff,
+ 0xef, 0xa1, 0x84, 0xff, 0xee, 0xa0, 0x84, 0xff,
+ 0xef, 0x9f, 0x81, 0xff, 0xee, 0x9f, 0x81, 0xff,
+ 0xef, 0xa0, 0x81, 0xff, 0xee, 0x9f, 0x81, 0xff,
+ 0xef, 0x9e, 0x7c, 0xff, 0xee, 0x9e, 0x7b, 0xff,
+ 0xf2, 0xa2, 0x81, 0xff, 0xf4, 0xa6, 0x86, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa2, 0x83, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa2, 0x84, 0xff,
+ 0xe4, 0x99, 0x7e, 0xff, 0xe3, 0x98, 0x7e, 0xff,
+ 0xc9, 0x8b, 0x79, 0xff, 0xad, 0x7d, 0x73, 0xff,
+ 0xd3, 0x91, 0x7c, 0xff, 0xd3, 0x90, 0x7b, 0xff,
+ 0xc0, 0x87, 0x74, 0xff, 0xad, 0x7d, 0x6b, 0xff,
+ 0x84, 0x7a, 0x6b, 0xff, 0x9c, 0x8d, 0x7e, 0xff,
+ 0x9c, 0x8e, 0x7e, 0xff, 0x83, 0x79, 0x6a, 0xff,
+ 0x84, 0x74, 0x60, 0xff, 0x83, 0x74, 0x60, 0xff,
+ 0x6b, 0x5d, 0x4a, 0xff, 0x6a, 0x5d, 0x4a, 0xff,
+ 0x5b, 0x4d, 0x42, 0xff, 0x5a, 0x4d, 0x41, 0xff,
+ 0x5b, 0x4d, 0x42, 0xff, 0x5a, 0x4c, 0x41, 0xff,
+ 0x76, 0x60, 0x4d, 0xff, 0x76, 0x5f, 0x4c, 0xff,
+ 0xad, 0x96, 0x84, 0xff, 0xac, 0x95, 0x83, 0xff,
+ 0x84, 0x6f, 0x60, 0xff, 0x6b, 0x53, 0x44, 0xff,
+ 0x9c, 0x8a, 0x7b, 0xff, 0x9c, 0x89, 0x7b, 0xff,
+ 0x89, 0x5d, 0x4d, 0xff, 0x62, 0x3c, 0x31, 0xff,
+ 0x63, 0x3d, 0x31, 0xff, 0x62, 0x3c, 0x31, 0xff,
+ 0x5b, 0x39, 0x21, 0xff, 0x8e, 0x62, 0x47, 0xff,
+ 0x8f, 0x63, 0x47, 0xff, 0xc2, 0x8c, 0x6d, 0xff,
+ 0xff, 0xb2, 0x94, 0xff, 0xf9, 0xab, 0x8e, 0xff,
+ 0xf4, 0xa5, 0x89, 0xff, 0xee, 0x9d, 0x83, 0xff,
+ 0xef, 0x9e, 0x84, 0xff, 0xf1, 0xa2, 0x89, 0xff,
+ 0xf4, 0xa6, 0x8f, 0xff, 0xf6, 0xaa, 0x94, 0xff,
+ 0xf7, 0xaa, 0x8c, 0xff, 0xf1, 0xa4, 0x89, 0xff,
+ 0xf7, 0xaa, 0x8c, 0xff, 0xf1, 0xa4, 0x89, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa2, 0x83, 0xff,
+ 0xef, 0xa1, 0x84, 0xff, 0xee, 0xa1, 0x83, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0x9f, 0x81, 0xff,
+ 0xef, 0x9f, 0x81, 0xff, 0xee, 0x9f, 0x80, 0xff,
+ 0xf1, 0xa2, 0x81, 0xff, 0xf1, 0xa2, 0x81, 0xff,
+ 0xf4, 0xa6, 0x86, 0xff, 0xf6, 0xaa, 0x8b, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xd8, 0x94, 0x7b, 0xff,
+ 0xc3, 0x87, 0x73, 0xff, 0xc2, 0x86, 0x73, 0xff,
+ 0xc8, 0x8b, 0x79, 0xff, 0xac, 0x7d, 0x73, 0xff,
+ 0xad, 0x7e, 0x73, 0xff, 0xac, 0x7d, 0x73, 0xff,
+ 0xd3, 0x91, 0x7c, 0xff, 0xc0, 0x87, 0x73, 0xff,
+ 0xc0, 0x87, 0x73, 0xff, 0xbf, 0x86, 0x73, 0xff,
+ 0x9d, 0x8a, 0x79, 0xff, 0x6b, 0x59, 0x42, 0xff,
+ 0x84, 0x72, 0x5e, 0xff, 0x83, 0x71, 0x5d, 0xff,
+ 0x74, 0x66, 0x50, 0xff, 0x73, 0x65, 0x4f, 0xff,
+ 0x63, 0x51, 0x3d, 0xff, 0x63, 0x51, 0x3c, 0xff,
+ 0x5b, 0x49, 0x32, 0xff, 0x52, 0x42, 0x2c, 0xff,
+ 0x53, 0x42, 0x2c, 0xff, 0x52, 0x42, 0x2c, 0xff,
+ 0x60, 0x49, 0x35, 0xff, 0x60, 0x49, 0x34, 0xff,
+ 0x8c, 0x72, 0x5b, 0xff, 0x8c, 0x71, 0x5a, 0xff,
+ 0x92, 0x87, 0x74, 0xff, 0x65, 0x5c, 0x4a, 0xff,
+ 0x92, 0x87, 0x74, 0xff, 0xbd, 0xb2, 0x9c, 0xff,
+ 0xd6, 0xb3, 0xad, 0xff, 0x68, 0x4e, 0x45, 0xff,
+ 0x32, 0x1d, 0x11, 0xff, 0x31, 0x1c, 0x10, 0xff,
+ 0x42, 0x25, 0x11, 0xff, 0x42, 0x24, 0x10, 0xff,
+ 0x7e, 0x59, 0x3f, 0xff, 0xba, 0x8e, 0x6e, 0xff,
+ 0xfd, 0xbb, 0xa0, 0xff, 0xf9, 0xae, 0x91, 0xff,
+ 0xfa, 0xae, 0x92, 0xff, 0xf7, 0xa2, 0x83, 0xff,
+ 0xef, 0x9e, 0x84, 0xff, 0xef, 0x9e, 0x84, 0xff,
+ 0xf2, 0xa2, 0x87, 0xff, 0xf7, 0xaa, 0x8c, 0xff,
+ 0xf7, 0xa6, 0x8c, 0xff, 0xf7, 0xa6, 0x8c, 0xff,
+ 0xfa, 0xaa, 0x8f, 0xff, 0xf7, 0xa6, 0x8c, 0xff,
+ 0xf7, 0xa2, 0x84, 0xff, 0xf7, 0xa2, 0x84, 0xff,
+ 0xf7, 0xa2, 0x84, 0xff, 0xf7, 0xa2, 0x83, 0xff,
+ 0xf7, 0xa2, 0x84, 0xff, 0xf7, 0xa2, 0x84, 0xff,
+ 0xf7, 0xa2, 0x84, 0xff, 0xf7, 0xa2, 0x83, 0xff,
+ 0xe7, 0xa4, 0x8a, 0xff, 0xe6, 0xa3, 0x89, 0xff,
+ 0xff, 0xb2, 0x94, 0xff, 0xe6, 0xa3, 0x89, 0xff,
+ 0xce, 0x92, 0x7c, 0xff, 0xbd, 0x88, 0x76, 0xff,
+ 0xad, 0x7f, 0x71, 0xff, 0x9c, 0x75, 0x6b, 0xff,
+ 0x9d, 0x76, 0x6b, 0xff, 0x9c, 0x75, 0x6b, 0xff,
+ 0xd3, 0x9c, 0x87, 0xff, 0xd3, 0x9b, 0x86, 0xff,
+ 0xce, 0x92, 0x74, 0xff, 0xce, 0x92, 0x73, 0xff,
+ 0xce, 0x92, 0x74, 0xff, 0xcd, 0x92, 0x73, 0xff,
+ 0xb5, 0xa2, 0x94, 0xff, 0x83, 0x71, 0x5d, 0xff,
+ 0x6b, 0x59, 0x42, 0xff, 0x6b, 0x59, 0x42, 0xff,
+ 0x84, 0x7a, 0x63, 0xff, 0x62, 0x51, 0x3c, 0xff,
+ 0x73, 0x65, 0x50, 0xff, 0x62, 0x51, 0x3c, 0xff,
+ 0x4a, 0x3b, 0x26, 0xff, 0x4a, 0x3b, 0x26, 0xff,
+ 0x52, 0x42, 0x2c, 0xff, 0x4a, 0x3b, 0x26, 0xff,
+ 0x60, 0x49, 0x34, 0xff, 0x60, 0x48, 0x34, 0xff,
+ 0x76, 0x5d, 0x48, 0xff, 0x76, 0x5d, 0x47, 0xff,
+ 0x66, 0x5c, 0x4a, 0xff, 0x91, 0x87, 0x73, 0xff,
+ 0x66, 0x5c, 0x4a, 0xff, 0x91, 0x87, 0x73, 0xff,
+ 0xd6, 0xb2, 0xad, 0xff, 0x68, 0x4e, 0x44, 0xff,
+ 0x32, 0x1d, 0x11, 0xff, 0x31, 0x1c, 0x10, 0xff,
+ 0x42, 0x25, 0x11, 0xff, 0x41, 0x24, 0x10, 0xff,
+ 0x7e, 0x59, 0x3f, 0xff, 0xf6, 0xc2, 0x9c, 0xff,
+ 0xff, 0xc6, 0xad, 0xff, 0xf9, 0xae, 0x91, 0xff,
+ 0xfa, 0xae, 0x92, 0xff, 0xf6, 0xa2, 0x83, 0xff,
+ 0xef, 0x9e, 0x84, 0xff, 0xee, 0x9d, 0x83, 0xff,
+ 0xf2, 0xa2, 0x87, 0xff, 0xf4, 0xa6, 0x89, 0xff,
+ 0xf7, 0xa6, 0x8c, 0xff, 0xf6, 0xa6, 0x8b, 0xff,
+ 0xfa, 0xaa, 0x8f, 0xff, 0xf6, 0xa6, 0x8c, 0xff,
+ 0xf7, 0xa6, 0x86, 0xff, 0xf6, 0xa6, 0x86, 0xff,
+ 0xf7, 0xaa, 0x89, 0xff, 0xf6, 0xa2, 0x83, 0xff,
+ 0xf7, 0xa2, 0x84, 0xff, 0xf6, 0xa1, 0x83, 0xff,
+ 0xf7, 0xa2, 0x84, 0xff, 0xf9, 0xa8, 0x89, 0xff,
+ 0xff, 0xb2, 0x94, 0xff, 0xff, 0xb2, 0x94, 0xff,
+ 0xe7, 0xa3, 0x89, 0xff, 0xe6, 0xa3, 0x89, 0xff,
+ 0xbd, 0x88, 0x76, 0xff, 0x9c, 0x75, 0x6b, 0xff,
+ 0x9d, 0x76, 0x6b, 0xff, 0xac, 0x7f, 0x70, 0xff,
+ 0xb8, 0x88, 0x79, 0xff, 0x9c, 0x75, 0x6b, 0xff,
+ 0x9d, 0x76, 0x6b, 0xff, 0xd3, 0x9b, 0x86, 0xff,
+ 0xce, 0x92, 0x73, 0xff, 0xcd, 0x91, 0x73, 0xff,
+ 0xc0, 0x87, 0x6b, 0xff, 0xcd, 0x91, 0x73, 0xff,
+ 0x9d, 0x8a, 0x79, 0xff, 0x9c, 0x89, 0x78, 0xff,
+ 0x84, 0x72, 0x5e, 0xff, 0x84, 0x71, 0x5d, 0xff,
+ 0x63, 0x51, 0x3d, 0xff, 0x62, 0x51, 0x3c, 0xff,
+ 0x63, 0x51, 0x3d, 0xff, 0x52, 0x3d, 0x29, 0xff,
+ 0x53, 0x42, 0x2c, 0xff, 0x4a, 0x3b, 0x26, 0xff,
+ 0x42, 0x35, 0x21, 0xff, 0x4a, 0x3b, 0x26, 0xff,
+ 0x4a, 0x35, 0x21, 0xff, 0x4a, 0x34, 0x21, 0xff,
+ 0x60, 0x49, 0x35, 0xff, 0x60, 0x49, 0x34, 0xff,
+ 0x66, 0x5c, 0x4a, 0xff, 0x65, 0x5c, 0x4a, 0xff,
+ 0x66, 0x5c, 0x4a, 0xff, 0x65, 0x5c, 0x4a, 0xff,
+ 0x68, 0x4f, 0x45, 0xff, 0x68, 0x4e, 0x44, 0xff,
+ 0x69, 0x4f, 0x45, 0xff, 0x31, 0x1c, 0x10, 0xff,
+ 0x42, 0x25, 0x11, 0xff, 0x7e, 0x59, 0x3f, 0xff,
+ 0xf7, 0xc3, 0x9d, 0xff, 0xf7, 0xc2, 0x9c, 0xff,
+ 0xfd, 0xba, 0x9f, 0xff, 0xf9, 0xae, 0x91, 0xff,
+ 0xfa, 0xae, 0x92, 0xff, 0xf9, 0xae, 0x91, 0xff,
+ 0xef, 0x9e, 0x84, 0xff, 0xf1, 0xa2, 0x86, 0xff,
+ 0xf2, 0xa2, 0x87, 0xff, 0xf1, 0xa2, 0x86, 0xff,
+ 0xfa, 0xaa, 0x8f, 0xff, 0xf9, 0xaa, 0x8e, 0xff,
+ 0xfa, 0xaa, 0x8f, 0xff, 0xff, 0xb2, 0x94, 0xff,
+ 0xf7, 0xae, 0x8c, 0xff, 0xf7, 0xae, 0x8c, 0xff,
+ 0xf7, 0xa6, 0x87, 0xff, 0xf7, 0xa2, 0x84, 0xff,
+ 0xf7, 0xa2, 0x84, 0xff, 0xf9, 0xa8, 0x89, 0xff,
+ 0xfa, 0xa9, 0x8a, 0xff, 0xfc, 0xaf, 0x8e, 0xff,
+ 0xff, 0xb2, 0x94, 0xff, 0xff, 0xb2, 0x94, 0xff,
+ 0xe7, 0xa4, 0x8a, 0xff, 0xce, 0x94, 0x7e, 0xff,
+ 0xad, 0x7f, 0x71, 0xff, 0x9c, 0x75, 0x6b, 0xff,
+ 0x9d, 0x76, 0x6b, 0xff, 0xad, 0x7f, 0x70, 0xff,
+ 0xb8, 0x89, 0x79, 0xff, 0xb7, 0x88, 0x78, 0xff,
+ 0x9d, 0x76, 0x6b, 0xff, 0xb8, 0x88, 0x79, 0xff,
+ 0xa5, 0x72, 0x5b, 0xff, 0xc0, 0x87, 0x6b, 0xff,
+ 0xb3, 0x7d, 0x63, 0xff, 0xce, 0x92, 0x73, 0xff,
+ 0x9c, 0x8a, 0x79, 0xff, 0x9c, 0x89, 0x78, 0xff,
+ 0x9c, 0x8a, 0x79, 0xff, 0x83, 0x71, 0x5d, 0xff,
+ 0x63, 0x51, 0x3c, 0xff, 0x62, 0x51, 0x3c, 0xff,
+ 0x52, 0x3d, 0x29, 0xff, 0x52, 0x3c, 0x29, 0xff,
+ 0x52, 0x42, 0x2c, 0xff, 0x52, 0x42, 0x2c, 0xff,
+ 0x42, 0x35, 0x21, 0xff, 0x4a, 0x3b, 0x26, 0xff,
+ 0x4a, 0x35, 0x21, 0xff, 0x4a, 0x34, 0x21, 0xff,
+ 0x4a, 0x35, 0x21, 0xff, 0x4a, 0x34, 0x20, 0xff,
+ 0x3a, 0x31, 0x21, 0xff, 0x39, 0x30, 0x21, 0xff,
+ 0x65, 0x5c, 0x4a, 0xff, 0x65, 0x5b, 0x4a, 0xff,
+ 0x9f, 0x80, 0x79, 0xff, 0x9f, 0x80, 0x78, 0xff,
+ 0x68, 0x4e, 0x45, 0xff, 0x31, 0x1c, 0x10, 0xff,
+ 0x42, 0x25, 0x11, 0xff, 0xba, 0x8d, 0x6d, 0xff,
+ 0xf7, 0xc2, 0x9c, 0xff, 0xf6, 0xc2, 0x9c, 0xff,
+ 0xff, 0xc6, 0xad, 0xff, 0xfc, 0xba, 0x9f, 0xff,
+ 0xfa, 0xae, 0x91, 0xff, 0xf6, 0xa1, 0x83, 0xff,
+ 0xf1, 0xa2, 0x87, 0xff, 0xf1, 0xa2, 0x86, 0xff,
+ 0xf1, 0xa2, 0x86, 0xff, 0xf4, 0xa5, 0x89, 0xff,
+ 0xfc, 0xae, 0x91, 0xff, 0xff, 0xb2, 0x94, 0xff,
+ 0xfc, 0xae, 0x91, 0xff, 0xfc, 0xae, 0x91, 0xff,
+ 0xf7, 0xae, 0x8c, 0xff, 0xf6, 0xa6, 0x86, 0xff,
+ 0xf7, 0xaa, 0x89, 0xff, 0xf6, 0xa5, 0x86, 0xff,
+ 0xfa, 0xa9, 0x89, 0xff, 0xf9, 0xa8, 0x89, 0xff,
+ 0xfc, 0xaf, 0x8f, 0xff, 0xff, 0xb6, 0x94, 0xff,
+ 0xff, 0xb2, 0x94, 0xff, 0xff, 0xb2, 0x94, 0xff,
+ 0xce, 0x94, 0x7e, 0xff, 0xb4, 0x85, 0x73, 0xff,
+ 0xad, 0x7f, 0x71, 0xff, 0xbd, 0x88, 0x76, 0xff,
+ 0xbd, 0x88, 0x76, 0xff, 0xcd, 0x91, 0x7b, 0xff,
+ 0xb8, 0x88, 0x79, 0xff, 0xb7, 0x88, 0x78, 0xff,
+ 0xef, 0xae, 0x94, 0xff, 0xb7, 0x88, 0x78, 0xff,
+ 0xa5, 0x71, 0x5b, 0xff, 0xc0, 0x87, 0x6b, 0xff,
+ 0xce, 0x92, 0x73, 0xff, 0xcd, 0x91, 0x73, 0xff,
+ 0x81, 0x75, 0x63, 0xff, 0x94, 0x8a, 0x7b, 0xff,
+ 0x94, 0x8a, 0x7c, 0xff, 0x81, 0x74, 0x63, 0xff,
+ 0x7c, 0x6a, 0x5b, 0xff, 0x55, 0x49, 0x3a, 0xff,
+ 0x55, 0x49, 0x3a, 0xff, 0x55, 0x49, 0x39, 0xff,
+ 0x4b, 0x3d, 0x2a, 0xff, 0x3f, 0x2f, 0x1e, 0xff,
+ 0x45, 0x36, 0x24, 0xff, 0x44, 0x36, 0x23, 0xff,
+ 0x4b, 0x3d, 0x2a, 0xff, 0x42, 0x35, 0x24, 0xff,
+ 0x42, 0x35, 0x24, 0xff, 0x42, 0x34, 0x23, 0xff,
+ 0x3a, 0x2e, 0x21, 0xff, 0x4a, 0x3b, 0x29, 0xff,
+ 0x5b, 0x49, 0x32, 0xff, 0x5a, 0x49, 0x31, 0xff,
+ 0xbe, 0x9a, 0x84, 0xff, 0xbd, 0x9a, 0x84, 0xff,
+ 0x66, 0x4c, 0x3d, 0xff, 0x39, 0x24, 0x19, 0xff,
+ 0xb3, 0x8f, 0x76, 0xff, 0xef, 0xc2, 0xa4, 0xff,
+ 0xef, 0xc3, 0xa5, 0xff, 0xee, 0xc2, 0xa4, 0xff,
+ 0xf7, 0xbb, 0x9d, 0xff, 0xf7, 0xba, 0x9c, 0xff,
+ 0xf7, 0xbb, 0x9d, 0xff, 0xc5, 0x96, 0x7b, 0xff,
+ 0xf7, 0xaa, 0x8c, 0xff, 0xf7, 0xaa, 0x8c, 0xff,
+ 0xf7, 0xaa, 0x8c, 0xff, 0xf7, 0xaa, 0x8c, 0xff,
+ 0xff, 0xaa, 0x8a, 0xff, 0xff, 0xae, 0x8f, 0xff,
+ 0xff, 0xa6, 0x84, 0xff, 0xff, 0xaa, 0x89, 0xff,
+ 0xf5, 0xad, 0x8f, 0xff, 0xe9, 0xa3, 0x89, 0xff,
+ 0xf4, 0xad, 0x8f, 0xff, 0xf4, 0xad, 0x8e, 0xff,
+ 0xef, 0xa9, 0x8a, 0xff, 0xef, 0xa9, 0x89, 0xff,
+ 0xff, 0xb6, 0x94, 0xff, 0xff, 0xb6, 0x94, 0xff,
+ 0xff, 0xbf, 0xa5, 0xff, 0xe1, 0xa7, 0x8f, 0xff,
+ 0xe1, 0xa8, 0x8f, 0xff, 0xa4, 0x79, 0x63, 0xff,
+ 0x95, 0x6e, 0x63, 0xff, 0xcb, 0x96, 0x84, 0xff,
+ 0xb0, 0x82, 0x74, 0xff, 0xcb, 0x96, 0x83, 0xff,
+ 0xcb, 0x91, 0x7c, 0xff, 0xcb, 0x90, 0x7b, 0xff,
+ 0xe1, 0xa4, 0x8c, 0xff, 0xb5, 0x7d, 0x6b, 0xff,
+ 0xcb, 0x94, 0x7f, 0xff, 0xcb, 0x93, 0x7e, 0xff,
+ 0xe1, 0xa9, 0x92, 0xff, 0xe1, 0xa8, 0x91, 0xff,
+ 0x5b, 0x49, 0x31, 0xff, 0x80, 0x74, 0x62, 0xff,
+ 0x81, 0x74, 0x63, 0xff, 0x81, 0x74, 0x62, 0xff,
+ 0x7b, 0x69, 0x5b, 0xff, 0x55, 0x48, 0x39, 0xff,
+ 0x55, 0x49, 0x3a, 0xff, 0x42, 0x38, 0x29, 0xff,
+ 0x45, 0x36, 0x24, 0xff, 0x4a, 0x3c, 0x29, 0xff,
+ 0x4a, 0x3d, 0x29, 0xff, 0x44, 0x36, 0x23, 0xff,
+ 0x4a, 0x3d, 0x29, 0xff, 0x41, 0x34, 0x23, 0xff,
+ 0x3a, 0x2d, 0x1e, 0xff, 0x42, 0x34, 0x23, 0xff,
+ 0x3a, 0x2e, 0x21, 0xff, 0x5a, 0x48, 0x31, 0xff,
+ 0x4a, 0x3c, 0x29, 0xff, 0x39, 0x2e, 0x21, 0xff,
+ 0x66, 0x4c, 0x3c, 0xff, 0x65, 0x4b, 0x3c, 0xff,
+ 0x66, 0x4c, 0x3d, 0xff, 0x65, 0x4b, 0x3c, 0xff,
+ 0xb2, 0x8f, 0x76, 0xff, 0xb2, 0x8f, 0x75, 0xff,
+ 0xb2, 0x8f, 0x76, 0xff, 0xb2, 0x8f, 0x76, 0xff,
+ 0xc6, 0x96, 0x7b, 0xff, 0xf6, 0xba, 0x9c, 0xff,
+ 0xf7, 0xba, 0x9d, 0xff, 0xf6, 0xba, 0x9c, 0xff,
+ 0xf7, 0xaa, 0x8c, 0xff, 0xf6, 0xaa, 0x8b, 0xff,
+ 0xf7, 0xaa, 0x8c, 0xff, 0xf6, 0xaa, 0x8c, 0xff,
+ 0xff, 0xaa, 0x89, 0xff, 0xff, 0xa6, 0x83, 0xff,
+ 0xff, 0xaa, 0x89, 0xff, 0xff, 0xaa, 0x89, 0xff,
+ 0xf4, 0xad, 0x8f, 0xff, 0xf4, 0xac, 0x8e, 0xff,
+ 0xf4, 0xad, 0x8f, 0xff, 0xf4, 0xac, 0x8e, 0xff,
+ 0xef, 0xa9, 0x89, 0xff, 0xee, 0xa8, 0x89, 0xff,
+ 0xff, 0xb6, 0x94, 0xff, 0xee, 0xa8, 0x89, 0xff,
+ 0xe1, 0xa7, 0x8f, 0xff, 0xe0, 0xa7, 0x8e, 0xff,
+ 0xe1, 0xa8, 0x8f, 0xff, 0xc2, 0x90, 0x78, 0xff,
+ 0x94, 0x6d, 0x63, 0xff, 0xaf, 0x81, 0x73, 0xff,
+ 0xb0, 0x82, 0x73, 0xff, 0xcb, 0x95, 0x83, 0xff,
+ 0xe1, 0xa3, 0x8c, 0xff, 0xb5, 0x7d, 0x6b, 0xff,
+ 0xe1, 0xa3, 0x8c, 0xff, 0xe1, 0xa3, 0x8c, 0xff,
+ 0xcb, 0x93, 0x7e, 0xff, 0xca, 0x93, 0x7e, 0xff,
+ 0xcb, 0x93, 0x7e, 0xff, 0xcb, 0x93, 0x7e, 0xff,
+ 0x6e, 0x5f, 0x4a, 0xff, 0x6d, 0x5e, 0x4a, 0xff,
+ 0x6e, 0x5f, 0x4a, 0xff, 0x6e, 0x5e, 0x4a, 0xff,
+ 0x55, 0x49, 0x3a, 0xff, 0x42, 0x38, 0x29, 0xff,
+ 0x42, 0x39, 0x2a, 0xff, 0x42, 0x39, 0x29, 0xff,
+ 0x45, 0x36, 0x24, 0xff, 0x44, 0x36, 0x23, 0xff,
+ 0x45, 0x36, 0x24, 0xff, 0x44, 0x36, 0x24, 0xff,
+ 0x42, 0x35, 0x24, 0xff, 0x39, 0x2c, 0x1e, 0xff,
+ 0x3a, 0x2d, 0x1f, 0xff, 0x39, 0x2c, 0x1e, 0xff,
+ 0x3a, 0x2e, 0x21, 0xff, 0x29, 0x20, 0x18, 0xff,
+ 0x3a, 0x2e, 0x21, 0xff, 0x29, 0x20, 0x19, 0xff,
+ 0x3a, 0x25, 0x19, 0xff, 0x39, 0x24, 0x18, 0xff,
+ 0x66, 0x4c, 0x3d, 0xff, 0x39, 0x24, 0x19, 0xff,
+ 0x3a, 0x29, 0x19, 0xff, 0x39, 0x28, 0x18, 0xff,
+ 0x76, 0x5c, 0x48, 0xff, 0x39, 0x28, 0x19, 0xff,
+ 0x94, 0x72, 0x5b, 0xff, 0xf7, 0xba, 0x9c, 0xff,
+ 0xf7, 0xbb, 0x9d, 0xff, 0xf7, 0xba, 0x9c, 0xff,
+ 0xfa, 0xb2, 0x94, 0xff, 0xf7, 0xaa, 0x8c, 0xff,
+ 0xf7, 0xaa, 0x8c, 0xff, 0xf7, 0xaa, 0x8c, 0xff,
+ 0xff, 0xaa, 0x89, 0xff, 0xff, 0xae, 0x8e, 0xff,
+ 0xff, 0xaa, 0x8a, 0xff, 0xff, 0xae, 0x8e, 0xff,
+ 0xf4, 0xad, 0x8f, 0xff, 0xf4, 0xac, 0x8e, 0xff,
+ 0xff, 0xb7, 0x94, 0xff, 0xe9, 0xa3, 0x89, 0xff,
+ 0xce, 0x8e, 0x73, 0xff, 0xde, 0x9b, 0x7e, 0xff,
+ 0xef, 0xa9, 0x8a, 0xff, 0xce, 0x8e, 0x73, 0xff,
+ 0xc3, 0x91, 0x79, 0xff, 0xc2, 0x90, 0x78, 0xff,
+ 0xa5, 0x7a, 0x63, 0xff, 0xc3, 0x90, 0x79, 0xff,
+ 0xb0, 0x82, 0x73, 0xff, 0x94, 0x6d, 0x62, 0xff,
+ 0x94, 0x6e, 0x63, 0xff, 0xe6, 0xaa, 0x94, 0xff,
+ 0xcb, 0x91, 0x7c, 0xff, 0xe1, 0xa3, 0x8c, 0xff,
+ 0xf7, 0xb7, 0x9d, 0xff, 0xe1, 0xa3, 0x8c, 0xff,
+ 0xb5, 0x7e, 0x6b, 0xff, 0xb5, 0x7d, 0x6b, 0xff,
+ 0xcb, 0x93, 0x7f, 0xff, 0xcb, 0x93, 0x7e, 0xff,
+ 0x5b, 0x49, 0x32, 0xff, 0x5a, 0x49, 0x31, 0xff,
+ 0x5b, 0x49, 0x31, 0xff, 0x6d, 0x5e, 0x4a, 0xff,
+ 0x68, 0x59, 0x4a, 0xff, 0x41, 0x38, 0x29, 0xff,
+ 0x42, 0x39, 0x29, 0xff, 0x41, 0x38, 0x29, 0xff,
+ 0x3f, 0x2f, 0x1e, 0xff, 0x39, 0x28, 0x18, 0xff,
+ 0x3a, 0x29, 0x19, 0xff, 0x39, 0x28, 0x18, 0xff,
+ 0x32, 0x25, 0x19, 0xff, 0x31, 0x24, 0x18, 0xff,
+ 0x31, 0x24, 0x19, 0xff, 0x31, 0x24, 0x18, 0xff,
+ 0x29, 0x21, 0x19, 0xff, 0x29, 0x20, 0x18, 0xff,
+ 0x29, 0x20, 0x19, 0xff, 0x29, 0x20, 0x18, 0xff,
+ 0x3a, 0x25, 0x19, 0xff, 0x39, 0x24, 0x18, 0xff,
+ 0x65, 0x4c, 0x3c, 0xff, 0x65, 0x4b, 0x3c, 0xff,
+ 0x3a, 0x29, 0x19, 0xff, 0x39, 0x28, 0x18, 0xff,
+ 0x3a, 0x29, 0x19, 0xff, 0x39, 0x28, 0x18, 0xff,
+ 0x63, 0x4d, 0x3a, 0xff, 0xc5, 0x95, 0x7b, 0xff,
+ 0xc5, 0x96, 0x7b, 0xff, 0xf6, 0xba, 0x9c, 0xff,
+ 0xff, 0xc2, 0xa5, 0xff, 0xfc, 0xba, 0x9c, 0xff,
+ 0xf7, 0xaa, 0x8c, 0xff, 0xf9, 0xb2, 0x94, 0xff,
+ 0xff, 0xae, 0x8f, 0xff, 0xff, 0xb2, 0x94, 0xff,
+ 0xff, 0xae, 0x8f, 0xff, 0xff, 0xb2, 0x94, 0xff,
+ 0xff, 0xb6, 0x94, 0xff, 0xff, 0xb6, 0x94, 0xff,
+ 0xf4, 0xad, 0x8f, 0xff, 0xde, 0x99, 0x83, 0xff,
+ 0xce, 0x8e, 0x73, 0xff, 0xde, 0x9b, 0x7e, 0xff,
+ 0xde, 0x9b, 0x7e, 0xff, 0xde, 0x9b, 0x7e, 0xff,
+ 0xc3, 0x91, 0x79, 0xff, 0xc2, 0x90, 0x78, 0xff,
+ 0xa5, 0x79, 0x63, 0xff, 0xa4, 0x79, 0x62, 0xff,
+ 0xb0, 0x82, 0x73, 0xff, 0xaf, 0x81, 0x73, 0xff,
+ 0xb0, 0x82, 0x73, 0xff, 0xe6, 0xaa, 0x94, 0xff,
+ 0xb5, 0x7e, 0x6b, 0xff, 0xe0, 0xa3, 0x8b, 0xff,
+ 0xe1, 0xa3, 0x8c, 0xff, 0xca, 0x90, 0x7b, 0xff,
+ 0xcb, 0x93, 0x7e, 0xff, 0xcb, 0x93, 0x7e, 0xff,
+ 0xe1, 0xa9, 0x91, 0xff, 0xf6, 0xbe, 0xa4, 0xff,
+ 0x4b, 0x3d, 0x21, 0xff, 0x7b, 0x6c, 0x55, 0xff,
+ 0x7c, 0x6c, 0x55, 0xff, 0x7b, 0x6c, 0x55, 0xff,
+ 0x5b, 0x55, 0x4b, 0xff, 0x4a, 0x3d, 0x2f, 0xff,
+ 0x4a, 0x3d, 0x2f, 0xff, 0x42, 0x30, 0x21, 0xff,
+ 0x42, 0x31, 0x21, 0xff, 0x37, 0x2a, 0x1b, 0xff,
+ 0x37, 0x2a, 0x1c, 0xff, 0x37, 0x2a, 0x1b, 0xff,
+ 0x32, 0x25, 0x21, 0xff, 0x31, 0x24, 0x21, 0xff,
+ 0x2c, 0x21, 0x1c, 0xff, 0x2c, 0x20, 0x1b, 0xff,
+ 0x27, 0x1e, 0x16, 0xff, 0x29, 0x20, 0x19, 0xff,
+ 0x27, 0x1e, 0x16, 0xff, 0x26, 0x1e, 0x16, 0xff,
+ 0x24, 0x1d, 0x19, 0xff, 0x24, 0x1c, 0x19, 0xff,
+ 0x24, 0x1d, 0x19, 0xff, 0x4a, 0x34, 0x29, 0xff,
+ 0x1c, 0x17, 0x16, 0xff, 0x08, 0x0c, 0x10, 0xff,
+ 0x42, 0x2d, 0x21, 0xff, 0x42, 0x2c, 0x21, 0xff,
+ 0x6b, 0x55, 0x42, 0xff, 0x4f, 0x3f, 0x31, 0xff,
+ 0x34, 0x2a, 0x21, 0xff, 0x6b, 0x55, 0x42, 0xff,
+ 0xaa, 0x79, 0x69, 0xff, 0xf7, 0xae, 0x94, 0xff,
+ 0xf7, 0xae, 0x94, 0xff, 0xf7, 0xae, 0x94, 0xff,
+ 0xff, 0xc3, 0xad, 0xff, 0xff, 0xc2, 0xad, 0xff,
+ 0xff, 0xc3, 0xad, 0xff, 0xff, 0xc2, 0xad, 0xff,
+ 0xf5, 0xc5, 0xad, 0xff, 0xf4, 0xc5, 0xad, 0xff,
+ 0xe9, 0xb4, 0x9d, 0xff, 0xde, 0xa2, 0x8c, 0xff,
+ 0xd6, 0x9e, 0x8a, 0xff, 0xd6, 0x9e, 0x89, 0xff,
+ 0xd6, 0x9e, 0x89, 0xff, 0xd6, 0x9e, 0x89, 0xff,
+ 0xdf, 0x9e, 0x84, 0xff, 0xde, 0x9e, 0x84, 0xff,
+ 0xde, 0x9e, 0x84, 0xff, 0xde, 0x9e, 0x83, 0xff,
+ 0x84, 0x68, 0x5e, 0xff, 0x84, 0x68, 0x5d, 0xff,
+ 0xd6, 0xa6, 0x94, 0xff, 0xd6, 0xa6, 0x94, 0xff,
+ 0x8c, 0x6e, 0x66, 0xff, 0xbd, 0x92, 0x81, 0xff,
+ 0xbe, 0x92, 0x81, 0xff, 0xbd, 0x92, 0x81, 0xff,
+ 0xcb, 0xa2, 0x8c, 0xff, 0xff, 0xca, 0xad, 0xff,
+ 0xff, 0xcb, 0xad, 0xff, 0xff, 0xca, 0xad, 0xff,
+ 0x7b, 0x6c, 0x55, 0xff, 0xac, 0x9b, 0x89, 0xff,
+ 0xde, 0xcb, 0xbd, 0xff, 0x4a, 0x3c, 0x21, 0xff,
+ 0x52, 0x49, 0x3c, 0xff, 0x4a, 0x3c, 0x2e, 0xff,
+ 0x42, 0x31, 0x21, 0xff, 0x42, 0x30, 0x21, 0xff,
+ 0x42, 0x31, 0x21, 0xff, 0x41, 0x30, 0x20, 0xff,
+ 0x2c, 0x23, 0x16, 0xff, 0x2c, 0x23, 0x16, 0xff,
+ 0x26, 0x1c, 0x16, 0xff, 0x2b, 0x20, 0x1b, 0xff,
+ 0x27, 0x1d, 0x16, 0xff, 0x26, 0x1c, 0x16, 0xff,
+ 0x26, 0x1e, 0x16, 0xff, 0x26, 0x1d, 0x16, 0xff,
+ 0x27, 0x1e, 0x16, 0xff, 0x26, 0x1d, 0x16, 0xff,
+ 0x24, 0x1c, 0x19, 0xff, 0x23, 0x1c, 0x18, 0xff,
+ 0x24, 0x1d, 0x19, 0xff, 0x23, 0x1c, 0x18, 0xff,
+ 0x2f, 0x22, 0x1c, 0xff, 0x1b, 0x17, 0x16, 0xff,
+ 0x08, 0x0c, 0x11, 0xff, 0x42, 0x2c, 0x21, 0xff,
+ 0x34, 0x2a, 0x21, 0xff, 0x4f, 0x3f, 0x31, 0xff,
+ 0x6b, 0x55, 0x42, 0xff, 0x34, 0x2a, 0x21, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x5d, 0x42, 0x3c, 0xff,
+ 0xaa, 0x78, 0x68, 0xff, 0xf6, 0xae, 0x94, 0xff,
+ 0xff, 0xc2, 0xad, 0xff, 0xff, 0xc2, 0xac, 0xff,
+ 0xff, 0xc3, 0xad, 0xff, 0xff, 0xc2, 0xac, 0xff,
+ 0xf4, 0xc5, 0xad, 0xff, 0xf4, 0xc5, 0xac, 0xff,
+ 0xf4, 0xc5, 0xad, 0xff, 0xe9, 0xb3, 0x9c, 0xff,
+ 0xd6, 0x9e, 0x89, 0xff, 0xd5, 0x9d, 0x89, 0xff,
+ 0xf7, 0xb6, 0x9d, 0xff, 0xd6, 0x9e, 0x89, 0xff,
+ 0xbd, 0x8a, 0x76, 0xff, 0xbd, 0x89, 0x75, 0xff,
+ 0xde, 0x9e, 0x84, 0xff, 0xbd, 0x89, 0x76, 0xff,
+ 0x84, 0x68, 0x5d, 0xff, 0x83, 0x67, 0x5d, 0xff,
+ 0xad, 0x87, 0x79, 0xff, 0xd6, 0xa6, 0x94, 0xff,
+ 0x8c, 0x6d, 0x66, 0xff, 0x8b, 0x6d, 0x65, 0xff,
+ 0x8c, 0x6e, 0x66, 0xff, 0xee, 0xb6, 0x9c, 0xff,
+ 0xff, 0xca, 0xad, 0xff, 0xff, 0xca, 0xac, 0xff,
+ 0xff, 0xcb, 0xad, 0xff, 0xff, 0xca, 0xac, 0xff,
+ 0x7c, 0x6c, 0x55, 0xff, 0xad, 0x9b, 0x89, 0xff,
+ 0xad, 0x9c, 0x8a, 0xff, 0x7b, 0x6c, 0x55, 0xff,
+ 0x42, 0x31, 0x21, 0xff, 0x4a, 0x3c, 0x2e, 0xff,
+ 0x42, 0x31, 0x21, 0xff, 0x42, 0x30, 0x21, 0xff,
+ 0x37, 0x2a, 0x1c, 0xff, 0x37, 0x2a, 0x1b, 0xff,
+ 0x2c, 0x23, 0x16, 0xff, 0x21, 0x1c, 0x10, 0xff,
+ 0x27, 0x1d, 0x16, 0xff, 0x26, 0x1c, 0x16, 0xff,
+ 0x2c, 0x21, 0x1c, 0xff, 0x26, 0x1c, 0x16, 0xff,
+ 0x21, 0x19, 0x11, 0xff, 0x23, 0x1b, 0x13, 0xff,
+ 0x2a, 0x21, 0x19, 0xff, 0x24, 0x1b, 0x13, 0xff,
+ 0x24, 0x1d, 0x19, 0xff, 0x23, 0x1c, 0x18, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x1c, 0x17, 0x16, 0xff, 0x08, 0x0c, 0x10, 0xff,
+ 0x09, 0x0d, 0x11, 0xff, 0x08, 0x0c, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x6b, 0x55, 0x42, 0xff, 0x34, 0x2a, 0x21, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x11, 0x0d, 0x11, 0xff, 0x5d, 0x42, 0x3c, 0xff,
+ 0xff, 0xc3, 0xad, 0xff, 0xff, 0xc2, 0xad, 0xff,
+ 0xff, 0xc3, 0xad, 0xff, 0xff, 0xc2, 0xad, 0xff,
+ 0xf4, 0xc5, 0xad, 0xff, 0xff, 0xd6, 0xbd, 0xff,
+ 0xff, 0xd7, 0xbe, 0xff, 0xff, 0xd6, 0xbd, 0xff,
+ 0xf7, 0xb6, 0x9d, 0xff, 0xd6, 0x9e, 0x89, 0xff,
+ 0xb5, 0x86, 0x76, 0xff, 0xd6, 0x9e, 0x89, 0xff,
+ 0x9d, 0x76, 0x68, 0xff, 0xbd, 0x89, 0x76, 0xff,
+ 0x9d, 0x76, 0x69, 0xff, 0x7b, 0x61, 0x5a, 0xff,
+ 0x84, 0x68, 0x5e, 0xff, 0x83, 0x68, 0x5d, 0xff,
+ 0xad, 0x87, 0x79, 0xff, 0xad, 0x87, 0x79, 0xff,
+ 0x5b, 0x49, 0x4a, 0xff, 0x8c, 0x6d, 0x65, 0xff,
+ 0x8c, 0x6e, 0x66, 0xff, 0xbd, 0x92, 0x81, 0xff,
+ 0x97, 0x7a, 0x6b, 0xff, 0x97, 0x79, 0x6b, 0xff,
+ 0xcb, 0xa2, 0x8c, 0xff, 0xcb, 0xa2, 0x8c, 0xff,
+ 0x4a, 0x3d, 0x21, 0xff, 0x7b, 0x6c, 0x55, 0xff,
+ 0x4a, 0x3d, 0x21, 0xff, 0xac, 0x9b, 0x89, 0xff,
+ 0x52, 0x49, 0x3c, 0xff, 0x41, 0x30, 0x21, 0xff,
+ 0x4a, 0x3d, 0x2f, 0xff, 0x41, 0x30, 0x20, 0xff,
+ 0x37, 0x2a, 0x1c, 0xff, 0x2c, 0x23, 0x16, 0xff,
+ 0x2c, 0x23, 0x16, 0xff, 0x2b, 0x23, 0x15, 0xff,
+ 0x27, 0x1c, 0x16, 0xff, 0x2c, 0x20, 0x1b, 0xff,
+ 0x26, 0x1c, 0x16, 0xff, 0x26, 0x1c, 0x15, 0xff,
+ 0x24, 0x1b, 0x13, 0xff, 0x23, 0x1b, 0x13, 0xff,
+ 0x21, 0x18, 0x10, 0xff, 0x20, 0x18, 0x10, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x24, 0x1c, 0x19, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x1c, 0x17, 0x16, 0xff, 0x1b, 0x17, 0x16, 0xff,
+ 0x08, 0x0c, 0x10, 0xff, 0x08, 0x0c, 0x10, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x34, 0x2a, 0x21, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x10, 0x0c, 0x10, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x32, 0x18, 0x19, 0xff, 0xba, 0x89, 0x7b, 0xff,
+ 0xff, 0xc2, 0xad, 0xff, 0xba, 0x89, 0x7b, 0xff,
+ 0xde, 0xa2, 0x8c, 0xff, 0xff, 0xd6, 0xbd, 0xff,
+ 0xf4, 0xc5, 0xad, 0xff, 0xe9, 0xb3, 0x9c, 0xff,
+ 0xd6, 0x9e, 0x89, 0xff, 0xd6, 0x9e, 0x89, 0xff,
+ 0x94, 0x6d, 0x63, 0xff, 0x94, 0x6d, 0x62, 0xff,
+ 0x7c, 0x61, 0x5b, 0xff, 0x9c, 0x75, 0x68, 0xff,
+ 0x9c, 0x75, 0x68, 0xff, 0x7b, 0x61, 0x5a, 0xff,
+ 0x84, 0x68, 0x5d, 0xff, 0xac, 0x87, 0x78, 0xff,
+ 0x5b, 0x49, 0x42, 0xff, 0x5a, 0x48, 0x41, 0xff,
+ 0x5b, 0x49, 0x4a, 0xff, 0x5a, 0x49, 0x4a, 0xff,
+ 0x5b, 0x49, 0x4a, 0xff, 0x5a, 0x48, 0x4a, 0xff,
+ 0x63, 0x51, 0x4a, 0xff, 0x62, 0x51, 0x4a, 0xff,
+ 0x63, 0x51, 0x4a, 0xff, 0x62, 0x50, 0x4a, 0xff,
+ 0x42, 0x38, 0x24, 0xff, 0x42, 0x37, 0x24, 0xff,
+ 0x4a, 0x3e, 0x27, 0xff, 0x42, 0x37, 0x23, 0xff,
+ 0x42, 0x31, 0x21, 0xff, 0x42, 0x31, 0x21, 0xff,
+ 0x42, 0x31, 0x21, 0xff, 0x42, 0x30, 0x21, 0xff,
+ 0x3a, 0x2d, 0x21, 0xff, 0x34, 0x27, 0x1b, 0xff,
+ 0x2f, 0x22, 0x16, 0xff, 0x2e, 0x22, 0x16, 0xff,
+ 0x2a, 0x25, 0x19, 0xff, 0x24, 0x1f, 0x16, 0xff,
+ 0x1f, 0x1a, 0x14, 0xff, 0x1e, 0x19, 0x13, 0xff,
+ 0x21, 0x19, 0x11, 0xff, 0x21, 0x18, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x21, 0x18, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x16, 0x12, 0x10, 0xff,
+ 0x14, 0x0f, 0x11, 0xff, 0x13, 0x0f, 0x10, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x19, 0x18, 0x19, 0xff,
+ 0x14, 0x13, 0x14, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x0b, 0x0f, 0x0e, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x0b, 0x0f, 0x0e, 0xff, 0x0b, 0x0f, 0x0e, 0xff,
+ 0x09, 0x09, 0x09, 0xff, 0x13, 0x14, 0x13, 0xff,
+ 0x14, 0x15, 0x14, 0xff, 0x13, 0x14, 0x13, 0xff,
+ 0x09, 0x0d, 0x09, 0xff, 0x19, 0x18, 0x16, 0xff,
+ 0x3a, 0x31, 0x32, 0xff, 0x39, 0x30, 0x31, 0xff,
+ 0x4b, 0x41, 0x40, 0xff, 0x63, 0x55, 0x52, 0xff,
+ 0x4a, 0x41, 0x3f, 0xff, 0x63, 0x55, 0x52, 0xff,
+ 0x9d, 0x85, 0x76, 0xff, 0xe6, 0xc2, 0xad, 0xff,
+ 0x9d, 0x85, 0x76, 0xff, 0x52, 0x46, 0x3f, 0xff,
+ 0x53, 0x49, 0x42, 0xff, 0x45, 0x3f, 0x3c, 0xff,
+ 0x45, 0x40, 0x3d, 0xff, 0x52, 0x49, 0x42, 0xff,
+ 0x53, 0x51, 0x4b, 0xff, 0x52, 0x51, 0x4a, 0xff,
+ 0x3f, 0x3e, 0x3a, 0xff, 0x2c, 0x2b, 0x29, 0xff,
+ 0x45, 0x45, 0x40, 0xff, 0x45, 0x45, 0x3f, 0xff,
+ 0x45, 0x45, 0x3f, 0xff, 0x29, 0x2c, 0x29, 0xff,
+ 0x32, 0x31, 0x32, 0xff, 0x37, 0x3f, 0x3f, 0xff,
+ 0x37, 0x40, 0x3f, 0xff, 0x37, 0x3f, 0x3f, 0xff,
+ 0x52, 0x45, 0x29, 0xff, 0x4a, 0x3e, 0x26, 0xff,
+ 0x42, 0x38, 0x24, 0xff, 0x42, 0x37, 0x23, 0xff,
+ 0x42, 0x31, 0x21, 0xff, 0x39, 0x29, 0x1e, 0xff,
+ 0x42, 0x31, 0x21, 0xff, 0x39, 0x2a, 0x1e, 0xff,
+ 0x34, 0x27, 0x1c, 0xff, 0x39, 0x2c, 0x20, 0xff,
+ 0x2f, 0x22, 0x16, 0xff, 0x29, 0x1c, 0x10, 0xff,
+ 0x24, 0x1f, 0x16, 0xff, 0x1e, 0x19, 0x13, 0xff,
+ 0x24, 0x1f, 0x16, 0xff, 0x1e, 0x19, 0x13, 0xff,
+ 0x21, 0x18, 0x11, 0xff, 0x20, 0x18, 0x10, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x16, 0x12, 0x11, 0xff, 0x16, 0x11, 0x10, 0xff,
+ 0x16, 0x12, 0x11, 0xff, 0x13, 0x0f, 0x10, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x0d, 0x0d, 0x0d, 0xff,
+ 0x13, 0x13, 0x13, 0xff, 0x0d, 0x0d, 0x0d, 0xff,
+ 0x0b, 0x0f, 0x0e, 0xff, 0x0b, 0x0e, 0x0d, 0xff,
+ 0x0b, 0x0f, 0x0e, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x13, 0x14, 0x13, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x13, 0x14, 0x13, 0xff, 0x13, 0x14, 0x13, 0xff,
+ 0x08, 0x0c, 0x08, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x19, 0x19, 0x16, 0xff, 0x29, 0x24, 0x23, 0xff,
+ 0x31, 0x2d, 0x2c, 0xff, 0x31, 0x2c, 0x2b, 0xff,
+ 0x4a, 0x41, 0x3f, 0xff, 0x4a, 0x40, 0x3f, 0xff,
+ 0x52, 0x46, 0x3f, 0xff, 0x52, 0x46, 0x3f, 0xff,
+ 0x52, 0x46, 0x3f, 0xff, 0x52, 0x46, 0x3f, 0xff,
+ 0x37, 0x36, 0x37, 0xff, 0x36, 0x36, 0x36, 0xff,
+ 0x29, 0x2d, 0x32, 0xff, 0x37, 0x36, 0x37, 0xff,
+ 0x2c, 0x2b, 0x29, 0xff, 0x2b, 0x2b, 0x29, 0xff,
+ 0x2c, 0x2b, 0x29, 0xff, 0x3f, 0x3e, 0x39, 0xff,
+ 0x29, 0x2d, 0x29, 0xff, 0x36, 0x38, 0x34, 0xff,
+ 0x45, 0x45, 0x3f, 0xff, 0x44, 0x45, 0x3f, 0xff,
+ 0x3c, 0x4e, 0x4d, 0xff, 0x36, 0x3f, 0x3f, 0xff,
+ 0x32, 0x31, 0x32, 0xff, 0x37, 0x3f, 0x3f, 0xff,
+ 0x42, 0x38, 0x24, 0xff, 0x42, 0x37, 0x23, 0xff,
+ 0x42, 0x38, 0x24, 0xff, 0x42, 0x37, 0x24, 0xff,
+ 0x42, 0x31, 0x21, 0xff, 0x31, 0x23, 0x1b, 0xff,
+ 0x32, 0x23, 0x1c, 0xff, 0x31, 0x23, 0x1b, 0xff,
+ 0x2f, 0x22, 0x16, 0xff, 0x34, 0x27, 0x1b, 0xff,
+ 0x35, 0x28, 0x1c, 0xff, 0x29, 0x1c, 0x10, 0xff,
+ 0x1e, 0x1a, 0x13, 0xff, 0x1e, 0x19, 0x13, 0xff,
+ 0x1f, 0x1a, 0x14, 0xff, 0x19, 0x14, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x21, 0x18, 0x10, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x13, 0x0f, 0x11, 0xff, 0x13, 0x0f, 0x10, 0xff,
+ 0x14, 0x0f, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x09, 0x08, 0x09, 0xff, 0x0d, 0x0d, 0x0d, 0xff,
+ 0x09, 0x09, 0x09, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x06, 0x0a, 0x0b, 0xff, 0x05, 0x09, 0x0b, 0xff,
+ 0x06, 0x0a, 0x0b, 0xff, 0x05, 0x09, 0x0b, 0xff,
+ 0x13, 0x15, 0x13, 0xff, 0x13, 0x14, 0x13, 0xff,
+ 0x2a, 0x2d, 0x2a, 0xff, 0x1e, 0x20, 0x1e, 0xff,
+ 0x09, 0x0c, 0x09, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x09, 0x0d, 0x09, 0xff, 0x19, 0x18, 0x16, 0xff,
+ 0x19, 0x19, 0x19, 0xff, 0x18, 0x18, 0x18, 0xff,
+ 0x4a, 0x41, 0x3f, 0xff, 0x31, 0x2c, 0x2c, 0xff,
+ 0x09, 0x08, 0x09, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x53, 0x47, 0x3f, 0xff, 0x52, 0x46, 0x3f, 0xff,
+ 0x37, 0x36, 0x37, 0xff, 0x37, 0x36, 0x37, 0xff,
+ 0x45, 0x40, 0x3d, 0xff, 0x29, 0x2c, 0x31, 0xff,
+ 0x2c, 0x2b, 0x29, 0xff, 0x18, 0x18, 0x18, 0xff,
+ 0x2c, 0x2c, 0x2a, 0xff, 0x2c, 0x2b, 0x29, 0xff,
+ 0x37, 0x39, 0x34, 0xff, 0x44, 0x45, 0x3f, 0xff,
+ 0x45, 0x45, 0x3f, 0xff, 0x52, 0x51, 0x4a, 0xff,
+ 0x42, 0x5d, 0x5b, 0xff, 0x3c, 0x4e, 0x4d, 0xff,
+ 0x37, 0x40, 0x3f, 0xff, 0x31, 0x30, 0x31, 0xff,
+ 0x3a, 0x31, 0x21, 0xff, 0x39, 0x30, 0x21, 0xff,
+ 0x4a, 0x3e, 0x26, 0xff, 0x39, 0x30, 0x20, 0xff,
+ 0x42, 0x31, 0x21, 0xff, 0x31, 0x23, 0x1b, 0xff,
+ 0x29, 0x1c, 0x19, 0xff, 0x29, 0x1c, 0x18, 0xff,
+ 0x29, 0x1c, 0x11, 0xff, 0x29, 0x1c, 0x10, 0xff,
+ 0x34, 0x27, 0x1b, 0xff, 0x2e, 0x21, 0x15, 0xff,
+ 0x1e, 0x1a, 0x13, 0xff, 0x1e, 0x19, 0x13, 0xff,
+ 0x1e, 0x1a, 0x13, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x10, 0x10, 0x10, 0xff, 0x08, 0x0c, 0x10, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x10, 0x0c, 0x10, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x00, 0x04, 0x08, 0xff, 0x05, 0x09, 0x0b, 0xff,
+ 0x00, 0x04, 0x08, 0xff, 0x00, 0x04, 0x08, 0xff,
+ 0x1e, 0x21, 0x1e, 0xff, 0x29, 0x2c, 0x29, 0xff,
+ 0x29, 0x2d, 0x29, 0xff, 0x1e, 0x20, 0x1e, 0xff,
+ 0x19, 0x18, 0x16, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x08, 0x0c, 0x08, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x19, 0x18, 0x19, 0xff, 0x31, 0x2c, 0x2c, 0xff,
+ 0x31, 0x2d, 0x2c, 0xff, 0x18, 0x18, 0x18, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x29, 0x2d, 0x32, 0xff, 0x44, 0x3f, 0x3c, 0xff,
+ 0x37, 0x36, 0x37, 0xff, 0x36, 0x35, 0x36, 0xff,
+ 0x2c, 0x2b, 0x29, 0xff, 0x18, 0x18, 0x18, 0xff,
+ 0x19, 0x18, 0x19, 0xff, 0x18, 0x18, 0x18, 0xff,
+ 0x29, 0x2d, 0x29, 0xff, 0x29, 0x2c, 0x29, 0xff,
+ 0x37, 0x39, 0x34, 0xff, 0x52, 0x50, 0x4a, 0xff,
+ 0x42, 0x5d, 0x5b, 0xff, 0x3c, 0x4e, 0x4c, 0xff,
+ 0x37, 0x3f, 0x3f, 0xff, 0x36, 0x3f, 0x3f, 0xff,
+ 0x4b, 0x35, 0x21, 0xff, 0x4a, 0x35, 0x21, 0xff,
+ 0x45, 0x31, 0x1f, 0xff, 0x44, 0x30, 0x1e, 0xff,
+ 0x3a, 0x29, 0x19, 0xff, 0x34, 0x24, 0x19, 0xff,
+ 0x34, 0x25, 0x19, 0xff, 0x29, 0x1c, 0x19, 0xff,
+ 0x21, 0x19, 0x11, 0xff, 0x26, 0x1c, 0x16, 0xff,
+ 0x32, 0x25, 0x21, 0xff, 0x2c, 0x20, 0x1b, 0xff,
+ 0x21, 0x1d, 0x19, 0xff, 0x1e, 0x18, 0x16, 0xff,
+ 0x1f, 0x19, 0x16, 0xff, 0x1b, 0x14, 0x13, 0xff,
+ 0x16, 0x15, 0x16, 0xff, 0x16, 0x14, 0x16, 0xff,
+ 0x19, 0x19, 0x19, 0xff, 0x13, 0x10, 0x13, 0xff,
+ 0x09, 0x0d, 0x09, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x09, 0x0c, 0x09, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x06, 0x09, 0x0b, 0xff, 0x0b, 0x0c, 0x0e, 0xff,
+ 0x06, 0x08, 0x0b, 0xff, 0x05, 0x08, 0x0b, 0xff,
+ 0x09, 0x09, 0x09, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x09, 0x08, 0x09, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x2a, 0x29, 0x2a, 0xff, 0x29, 0x28, 0x29, 0xff,
+ 0x1f, 0x1d, 0x1f, 0xff, 0x1e, 0x1c, 0x1e, 0xff,
+ 0x19, 0x19, 0x19, 0xff, 0x19, 0x18, 0x19, 0xff,
+ 0x19, 0x19, 0x19, 0xff, 0x13, 0x11, 0x10, 0xff,
+ 0x21, 0x21, 0x21, 0xff, 0x21, 0x20, 0x21, 0xff,
+ 0x0b, 0x0e, 0x0b, 0xff, 0x0b, 0x0d, 0x0b, 0xff,
+ 0x0b, 0x0b, 0x0b, 0xff, 0x0b, 0x0b, 0x0b, 0xff,
+ 0x06, 0x06, 0x06, 0xff, 0x05, 0x05, 0x05, 0xff,
+ 0x0e, 0x12, 0x0e, 0xff, 0x1b, 0x1f, 0x1b, 0xff,
+ 0x1c, 0x1f, 0x1c, 0xff, 0x29, 0x2c, 0x29, 0xff,
+ 0x27, 0x29, 0x27, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x1c, 0x1d, 0x1c, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x2a, 0x30, 0x2c, 0xff, 0x29, 0x2f, 0x2c, 0xff,
+ 0x29, 0x30, 0x2c, 0xff, 0x31, 0x3d, 0x39, 0xff,
+ 0x32, 0x41, 0x40, 0xff, 0x31, 0x41, 0x3f, 0xff,
+ 0x32, 0x41, 0x3f, 0xff, 0x31, 0x41, 0x3f, 0xff,
+ 0x4a, 0x35, 0x21, 0xff, 0x4a, 0x34, 0x20, 0xff,
+ 0x45, 0x31, 0x1e, 0xff, 0x3f, 0x2c, 0x1b, 0xff,
+ 0x34, 0x25, 0x19, 0xff, 0x39, 0x28, 0x18, 0xff,
+ 0x34, 0x25, 0x19, 0xff, 0x34, 0x24, 0x18, 0xff,
+ 0x2c, 0x20, 0x1c, 0xff, 0x26, 0x1c, 0x16, 0xff,
+ 0x27, 0x1d, 0x16, 0xff, 0x21, 0x18, 0x10, 0xff,
+ 0x1e, 0x18, 0x16, 0xff, 0x1b, 0x14, 0x13, 0xff,
+ 0x19, 0x10, 0x11, 0xff, 0x18, 0x10, 0x10, 0xff,
+ 0x13, 0x10, 0x13, 0xff, 0x16, 0x14, 0x16, 0xff,
+ 0x19, 0x19, 0x19, 0xff, 0x16, 0x14, 0x16, 0xff,
+ 0x08, 0x0c, 0x08, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x08, 0x0c, 0x08, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x0b, 0x0c, 0x0e, 0xff, 0x0b, 0x0c, 0x0d, 0xff,
+ 0x06, 0x08, 0x0b, 0xff, 0x0b, 0x0c, 0x0d, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x29, 0x29, 0x29, 0xff, 0x1e, 0x1c, 0x1e, 0xff,
+ 0x13, 0x10, 0x13, 0xff, 0x13, 0x10, 0x13, 0xff,
+ 0x13, 0x12, 0x11, 0xff, 0x0d, 0x0a, 0x08, 0xff,
+ 0x13, 0x12, 0x11, 0xff, 0x0d, 0x0b, 0x08, 0xff,
+ 0x0b, 0x0e, 0x0b, 0xff, 0x0b, 0x0d, 0x0b, 0xff,
+ 0x0b, 0x0e, 0x0b, 0xff, 0x00, 0x04, 0x00, 0xff,
+ 0x06, 0x05, 0x06, 0xff, 0x05, 0x05, 0x05, 0xff,
+ 0x06, 0x06, 0x06, 0xff, 0x0b, 0x0b, 0x0b, 0xff,
+ 0x0e, 0x12, 0x0e, 0xff, 0x1b, 0x1f, 0x1b, 0xff,
+ 0x1c, 0x1f, 0x1c, 0xff, 0x29, 0x2c, 0x29, 0xff,
+ 0x26, 0x29, 0x26, 0xff, 0x1b, 0x1c, 0x1b, 0xff,
+ 0x1c, 0x1d, 0x1c, 0xff, 0x31, 0x34, 0x31, 0xff,
+ 0x31, 0x3d, 0x3a, 0xff, 0x29, 0x2f, 0x2b, 0xff,
+ 0x21, 0x22, 0x1e, 0xff, 0x31, 0x3c, 0x39, 0xff,
+ 0x31, 0x41, 0x3f, 0xff, 0x31, 0x40, 0x3f, 0xff,
+ 0x3a, 0x4d, 0x4a, 0xff, 0x31, 0x40, 0x3f, 0xff,
+ 0x3f, 0x2d, 0x1c, 0xff, 0x44, 0x30, 0x1e, 0xff,
+ 0x4a, 0x35, 0x21, 0xff, 0x3f, 0x2c, 0x1b, 0xff,
+ 0x34, 0x25, 0x19, 0xff, 0x39, 0x28, 0x18, 0xff,
+ 0x35, 0x25, 0x19, 0xff, 0x34, 0x24, 0x19, 0xff,
+ 0x2c, 0x21, 0x1c, 0xff, 0x2c, 0x20, 0x1b, 0xff,
+ 0x27, 0x1d, 0x16, 0xff, 0x21, 0x18, 0x10, 0xff,
+ 0x1e, 0x19, 0x16, 0xff, 0x1e, 0x18, 0x16, 0xff,
+ 0x1c, 0x15, 0x14, 0xff, 0x19, 0x10, 0x10, 0xff,
+ 0x13, 0x10, 0x13, 0xff, 0x13, 0x10, 0x13, 0xff,
+ 0x11, 0x0d, 0x11, 0xff, 0x13, 0x10, 0x13, 0xff,
+ 0x09, 0x0c, 0x09, 0xff, 0x1b, 0x1c, 0x18, 0xff,
+ 0x09, 0x0d, 0x09, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x06, 0x08, 0x0b, 0xff, 0x0b, 0x0c, 0x0d, 0xff,
+ 0x0b, 0x0d, 0x0e, 0xff, 0x0b, 0x0c, 0x0e, 0xff,
+ 0x13, 0x13, 0x11, 0xff, 0x13, 0x13, 0x10, 0xff,
+ 0x14, 0x13, 0x11, 0xff, 0x1e, 0x1e, 0x19, 0xff,
+ 0x13, 0x10, 0x13, 0xff, 0x1e, 0x1c, 0x1e, 0xff,
+ 0x14, 0x11, 0x14, 0xff, 0x13, 0x10, 0x13, 0xff,
+ 0x09, 0x04, 0x00, 0xff, 0x08, 0x04, 0x00, 0xff,
+ 0x0e, 0x0b, 0x09, 0xff, 0x19, 0x18, 0x19, 0xff,
+ 0x0b, 0x0e, 0x0b, 0xff, 0x00, 0x04, 0x00, 0xff,
+ 0x00, 0x04, 0x00, 0xff, 0x00, 0x04, 0x00, 0xff,
+ 0x06, 0x06, 0x06, 0xff, 0x05, 0x05, 0x05, 0xff,
+ 0x06, 0x06, 0x06, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x1c, 0x1f, 0x1c, 0xff, 0x0d, 0x11, 0x0d, 0xff,
+ 0x0e, 0x12, 0x0e, 0xff, 0x0e, 0x11, 0x0e, 0xff,
+ 0x1c, 0x1d, 0x1c, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x1c, 0x1d, 0x1c, 0xff, 0x31, 0x35, 0x31, 0xff,
+ 0x29, 0x30, 0x2c, 0xff, 0x31, 0x3c, 0x39, 0xff,
+ 0x2a, 0x30, 0x2c, 0xff, 0x29, 0x2f, 0x2c, 0xff,
+ 0x32, 0x41, 0x3f, 0xff, 0x39, 0x4d, 0x4a, 0xff,
+ 0x3a, 0x4d, 0x4a, 0xff, 0x31, 0x41, 0x3f, 0xff,
+ 0x3a, 0x29, 0x19, 0xff, 0x4a, 0x34, 0x21, 0xff,
+ 0x45, 0x31, 0x1e, 0xff, 0x39, 0x28, 0x18, 0xff,
+ 0x34, 0x25, 0x19, 0xff, 0x34, 0x24, 0x18, 0xff,
+ 0x2f, 0x20, 0x19, 0xff, 0x2e, 0x20, 0x18, 0xff,
+ 0x2c, 0x21, 0x1c, 0xff, 0x2c, 0x20, 0x1b, 0xff,
+ 0x26, 0x1c, 0x16, 0xff, 0x26, 0x1c, 0x15, 0xff,
+ 0x1e, 0x18, 0x16, 0xff, 0x1b, 0x14, 0x13, 0xff,
+ 0x1b, 0x14, 0x13, 0xff, 0x1b, 0x14, 0x13, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x10, 0x0c, 0x10, 0xff, 0x13, 0x10, 0x13, 0xff,
+ 0x1c, 0x1c, 0x19, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x2f, 0x2d, 0x29, 0xff, 0x41, 0x3c, 0x39, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x05, 0x08, 0x0b, 0xff,
+ 0x06, 0x08, 0x0b, 0xff, 0x00, 0x04, 0x08, 0xff,
+ 0x13, 0x13, 0x11, 0xff, 0x29, 0x28, 0x21, 0xff,
+ 0x29, 0x29, 0x21, 0xff, 0x1e, 0x1d, 0x18, 0xff,
+ 0x08, 0x04, 0x08, 0xff, 0x13, 0x10, 0x13, 0xff,
+ 0x08, 0x04, 0x08, 0xff, 0x08, 0x04, 0x08, 0xff,
+ 0x0e, 0x0b, 0x08, 0xff, 0x0d, 0x0a, 0x08, 0xff,
+ 0x13, 0x12, 0x10, 0xff, 0x13, 0x11, 0x10, 0xff,
+ 0x0b, 0x0e, 0x0b, 0xff, 0x00, 0x04, 0x00, 0xff,
+ 0x00, 0x04, 0x00, 0xff, 0x00, 0x04, 0x00, 0xff,
+ 0x00, 0x00, 0x00, 0xff, 0x0b, 0x0a, 0x0b, 0xff,
+ 0x0b, 0x0b, 0x0b, 0xff, 0x00, 0x00, 0x00, 0xff,
+ 0x00, 0x04, 0x00, 0xff, 0x00, 0x04, 0x00, 0xff,
+ 0x00, 0x04, 0x00, 0xff, 0x0d, 0x11, 0x0d, 0xff,
+ 0x1c, 0x1c, 0x1c, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x10, 0x10, 0x10, 0xff, 0x26, 0x28, 0x26, 0xff,
+ 0x29, 0x2f, 0x2c, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x19, 0x14, 0x10, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x21, 0x29, 0x29, 0xff, 0x39, 0x4d, 0x4a, 0xff,
+ 0x31, 0x41, 0x3f, 0xff, 0x31, 0x40, 0x3f, 0xff,
+ 0x3a, 0x2d, 0x19, 0xff, 0x3a, 0x2c, 0x19, 0xff,
+ 0x34, 0x29, 0x19, 0xff, 0x34, 0x28, 0x19, 0xff,
+ 0x32, 0x25, 0x11, 0xff, 0x2f, 0x22, 0x13, 0xff,
+ 0x29, 0x1d, 0x19, 0xff, 0x2c, 0x1f, 0x16, 0xff,
+ 0x24, 0x1d, 0x16, 0xff, 0x24, 0x1c, 0x16, 0xff,
+ 0x24, 0x1d, 0x16, 0xff, 0x23, 0x1c, 0x16, 0xff,
+ 0x19, 0x19, 0x19, 0xff, 0x19, 0x16, 0x16, 0xff,
+ 0x19, 0x13, 0x14, 0xff, 0x19, 0x10, 0x10, 0xff,
+ 0x09, 0x0d, 0x09, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x09, 0x0c, 0x09, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x11, 0x0d, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x42, 0x3d, 0x3a, 0xff, 0x31, 0x2c, 0x2c, 0xff,
+ 0x21, 0x19, 0x11, 0xff, 0x16, 0x12, 0x0b, 0xff,
+ 0x16, 0x12, 0x0b, 0xff, 0x16, 0x11, 0x0b, 0xff,
+ 0x19, 0x1d, 0x19, 0xff, 0x19, 0x1c, 0x19, 0xff,
+ 0x19, 0x1d, 0x19, 0xff, 0x19, 0x1c, 0x19, 0xff,
+ 0x09, 0x00, 0x00, 0xff, 0x08, 0x00, 0x00, 0xff,
+ 0x09, 0x00, 0x00, 0xff, 0x08, 0x00, 0x00, 0xff,
+ 0x11, 0x09, 0x09, 0xff, 0x10, 0x08, 0x08, 0xff,
+ 0x27, 0x47, 0x3a, 0xff, 0x10, 0x08, 0x08, 0xff,
+ 0x24, 0x20, 0x1c, 0xff, 0x24, 0x1f, 0x1b, 0xff,
+ 0x19, 0x08, 0x09, 0xff, 0x19, 0x08, 0x08, 0xff,
+ 0x21, 0x19, 0x11, 0xff, 0x21, 0x18, 0x10, 0xff,
+ 0x2f, 0x2d, 0x27, 0xff, 0x3c, 0x41, 0x3c, 0xff,
+ 0x48, 0x43, 0x48, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x2c, 0x2c, 0x2c, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x2a, 0x24, 0x21, 0xff, 0x29, 0x23, 0x21, 0xff,
+ 0x11, 0x08, 0x09, 0xff, 0x10, 0x08, 0x08, 0xff,
+ 0x24, 0x30, 0x2a, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x09, 0x0c, 0x09, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x00, 0x05, 0x00, 0xff, 0x29, 0x2f, 0x31, 0xff,
+ 0x29, 0x30, 0x32, 0xff, 0x52, 0x5a, 0x63, 0xff,
+ 0x2f, 0x25, 0x19, 0xff, 0x2e, 0x24, 0x18, 0xff,
+ 0x34, 0x29, 0x19, 0xff, 0x29, 0x20, 0x18, 0xff,
+ 0x2c, 0x1f, 0x16, 0xff, 0x2b, 0x1f, 0x16, 0xff,
+ 0x2c, 0x1f, 0x16, 0xff, 0x2c, 0x1f, 0x16, 0xff,
+ 0x1e, 0x18, 0x13, 0xff, 0x1e, 0x18, 0x13, 0xff,
+ 0x1e, 0x19, 0x13, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x19, 0x13, 0x13, 0xff, 0x18, 0x12, 0x13, 0xff,
+ 0x19, 0x16, 0x16, 0xff, 0x18, 0x10, 0x10, 0xff,
+ 0x08, 0x0c, 0x08, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x08, 0x0c, 0x08, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x21, 0x1d, 0x1e, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x16, 0x12, 0x0b, 0xff, 0x16, 0x11, 0x0b, 0xff,
+ 0x16, 0x12, 0x0b, 0xff, 0x0b, 0x0b, 0x05, 0xff,
+ 0x19, 0x1c, 0x19, 0xff, 0x18, 0x1c, 0x18, 0xff,
+ 0x21, 0x35, 0x29, 0xff, 0x18, 0x1c, 0x18, 0xff,
+ 0x11, 0x17, 0x11, 0xff, 0x10, 0x17, 0x10, 0xff,
+ 0x11, 0x17, 0x11, 0xff, 0x10, 0x17, 0x10, 0xff,
+ 0x11, 0x08, 0x08, 0xff, 0x1b, 0x27, 0x20, 0xff,
+ 0x1c, 0x27, 0x21, 0xff, 0x1b, 0x27, 0x21, 0xff,
+ 0x24, 0x1f, 0x1c, 0xff, 0x23, 0x1f, 0x1b, 0xff,
+ 0x24, 0x1f, 0x1c, 0xff, 0x23, 0x1f, 0x1b, 0xff,
+ 0x2f, 0x2d, 0x26, 0xff, 0x2e, 0x2c, 0x26, 0xff,
+ 0x3d, 0x41, 0x3d, 0xff, 0x3c, 0x40, 0x3c, 0xff,
+ 0x47, 0x42, 0x47, 0xff, 0x2b, 0x2b, 0x2b, 0xff,
+ 0x63, 0x59, 0x63, 0xff, 0x2c, 0x2b, 0x2c, 0xff,
+ 0x42, 0x3e, 0x3a, 0xff, 0x29, 0x23, 0x20, 0xff,
+ 0x29, 0x23, 0x21, 0xff, 0x29, 0x23, 0x21, 0xff,
+ 0x24, 0x2f, 0x29, 0xff, 0x23, 0x2f, 0x29, 0xff,
+ 0x08, 0x0c, 0x08, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x29, 0x2f, 0x31, 0xff, 0x29, 0x2f, 0x31, 0xff,
+ 0x52, 0x5b, 0x63, 0xff, 0x7b, 0x85, 0x94, 0xff,
+ 0x29, 0x21, 0x19, 0xff, 0x29, 0x20, 0x18, 0xff,
+ 0x2a, 0x21, 0x19, 0xff, 0x29, 0x20, 0x19, 0xff,
+ 0x29, 0x1d, 0x19, 0xff, 0x29, 0x1c, 0x18, 0xff,
+ 0x2a, 0x1d, 0x19, 0xff, 0x29, 0x1c, 0x19, 0xff,
+ 0x1e, 0x19, 0x13, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x1e, 0x18, 0x13, 0xff,
+ 0x19, 0x16, 0x16, 0xff, 0x18, 0x13, 0x13, 0xff,
+ 0x19, 0x11, 0x11, 0xff, 0x19, 0x13, 0x13, 0xff,
+ 0x11, 0x13, 0x0e, 0xff, 0x10, 0x13, 0x0d, 0xff,
+ 0x11, 0x13, 0x0e, 0xff, 0x10, 0x13, 0x0e, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x11, 0x0d, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x16, 0x12, 0x0b, 0xff, 0x00, 0x04, 0x00, 0xff,
+ 0x00, 0x04, 0x00, 0xff, 0x0b, 0x0b, 0x05, 0xff,
+ 0x19, 0x1d, 0x19, 0xff, 0x29, 0x4d, 0x39, 0xff,
+ 0x2a, 0x4d, 0x3a, 0xff, 0x29, 0x4d, 0x39, 0xff,
+ 0x21, 0x45, 0x32, 0xff, 0x21, 0x45, 0x31, 0xff,
+ 0x19, 0x2e, 0x21, 0xff, 0x19, 0x2e, 0x21, 0xff,
+ 0x1c, 0x27, 0x21, 0xff, 0x1b, 0x27, 0x21, 0xff,
+ 0x1c, 0x28, 0x21, 0xff, 0x10, 0x08, 0x08, 0xff,
+ 0x24, 0x1f, 0x1c, 0xff, 0x23, 0x1f, 0x1b, 0xff,
+ 0x24, 0x1f, 0x1c, 0xff, 0x2f, 0x36, 0x2f, 0xff,
+ 0x3d, 0x41, 0x3d, 0xff, 0x3c, 0x41, 0x3c, 0xff,
+ 0x3d, 0x41, 0x3d, 0xff, 0x2f, 0x2c, 0x26, 0xff,
+ 0x2c, 0x2b, 0x2c, 0xff, 0x2c, 0x2b, 0x2c, 0xff,
+ 0x2c, 0x2c, 0x2c, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x08, 0x09, 0xff, 0x10, 0x08, 0x08, 0xff,
+ 0x11, 0x09, 0x09, 0xff, 0x5a, 0x59, 0x52, 0xff,
+ 0x5b, 0x76, 0x6b, 0xff, 0x5a, 0x75, 0x6b, 0xff,
+ 0x3f, 0x53, 0x4a, 0xff, 0x5a, 0x75, 0x6b, 0xff,
+ 0x7c, 0x86, 0x94, 0xff, 0x7b, 0x85, 0x94, 0xff,
+ 0x53, 0x5b, 0x63, 0xff, 0x7b, 0x85, 0x94, 0xff,
+ 0x34, 0x29, 0x19, 0xff, 0x2e, 0x24, 0x18, 0xff,
+ 0x29, 0x20, 0x19, 0xff, 0x29, 0x20, 0x18, 0xff,
+ 0x29, 0x1c, 0x19, 0xff, 0x29, 0x1c, 0x18, 0xff,
+ 0x29, 0x1c, 0x19, 0xff, 0x29, 0x1c, 0x18, 0xff,
+ 0x29, 0x21, 0x19, 0xff, 0x23, 0x1c, 0x16, 0xff,
+ 0x1e, 0x18, 0x13, 0xff, 0x1e, 0x18, 0x13, 0xff,
+ 0x19, 0x16, 0x16, 0xff, 0x18, 0x18, 0x18, 0xff,
+ 0x19, 0x18, 0x19, 0xff, 0x18, 0x18, 0x18, 0xff,
+ 0x21, 0x21, 0x19, 0xff, 0x21, 0x20, 0x18, 0xff,
+ 0x21, 0x20, 0x19, 0xff, 0x18, 0x19, 0x13, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x10, 0x0c, 0x10, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x0b, 0x0b, 0x06, 0xff, 0x0b, 0x0a, 0x05, 0xff,
+ 0x0b, 0x0b, 0x06, 0xff, 0x0a, 0x0a, 0x05, 0xff,
+ 0x11, 0x04, 0x08, 0xff, 0x10, 0x04, 0x08, 0xff,
+ 0x19, 0x1c, 0x19, 0xff, 0x18, 0x1c, 0x18, 0xff,
+ 0x19, 0x2e, 0x21, 0xff, 0x18, 0x2e, 0x21, 0xff,
+ 0x19, 0x2e, 0x21, 0xff, 0x20, 0x44, 0x31, 0xff,
+ 0x32, 0x65, 0x52, 0xff, 0x31, 0x65, 0x52, 0xff,
+ 0x31, 0x65, 0x52, 0xff, 0x31, 0x65, 0x52, 0xff,
+ 0x3a, 0x4d, 0x42, 0xff, 0x2e, 0x36, 0x2e, 0xff,
+ 0x2f, 0x36, 0x2f, 0xff, 0x2e, 0x35, 0x2e, 0xff,
+ 0x3c, 0x41, 0x3c, 0xff, 0x3c, 0x40, 0x3c, 0xff,
+ 0x4a, 0x55, 0x52, 0xff, 0x4a, 0x55, 0x52, 0xff,
+ 0x47, 0x42, 0x47, 0xff, 0x2c, 0x2b, 0x2c, 0xff,
+ 0x2c, 0x2b, 0x2c, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x29, 0x23, 0x21, 0xff, 0x29, 0x23, 0x21, 0xff,
+ 0x29, 0x23, 0x21, 0xff, 0x29, 0x23, 0x20, 0xff,
+ 0x24, 0x2f, 0x29, 0xff, 0x23, 0x2f, 0x29, 0xff,
+ 0x3f, 0x52, 0x4a, 0xff, 0x3f, 0x52, 0x4a, 0xff,
+ 0x52, 0x5b, 0x63, 0xff, 0x29, 0x2f, 0x31, 0xff,
+ 0x52, 0x5a, 0x63, 0xff, 0x52, 0x5a, 0x62, 0xff,
+ 0x37, 0x3d, 0x2c, 0xff, 0x37, 0x3d, 0x2c, 0xff,
+ 0x37, 0x3d, 0x2c, 0xff, 0x39, 0x45, 0x31, 0xff,
+ 0x32, 0x41, 0x2a, 0xff, 0x2f, 0x37, 0x24, 0xff,
+ 0x2f, 0x38, 0x24, 0xff, 0x2c, 0x2e, 0x1e, 0xff,
+ 0x27, 0x2d, 0x1f, 0xff, 0x29, 0x35, 0x21, 0xff,
+ 0x27, 0x2d, 0x1f, 0xff, 0x23, 0x24, 0x1b, 0xff,
+ 0x16, 0x20, 0x14, 0xff, 0x16, 0x1f, 0x13, 0xff,
+ 0x16, 0x1f, 0x14, 0xff, 0x16, 0x1f, 0x13, 0xff,
+ 0x19, 0x21, 0x11, 0xff, 0x19, 0x20, 0x10, 0xff,
+ 0x16, 0x1b, 0x11, 0xff, 0x16, 0x1b, 0x10, 0xff,
+ 0x14, 0x16, 0x14, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x13, 0x16, 0x10, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x13, 0x13, 0x13, 0xff,
+ 0x11, 0x0f, 0x11, 0xff, 0x10, 0x12, 0x10, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x19, 0x26, 0x24, 0xff, 0x19, 0x26, 0x24, 0xff,
+ 0x21, 0x3c, 0x37, 0xff, 0x29, 0x51, 0x4a, 0xff,
+ 0x3a, 0x76, 0x6b, 0xff, 0x3a, 0x75, 0x6b, 0xff,
+ 0x3a, 0x76, 0x6b, 0xff, 0x39, 0x75, 0x6b, 0xff,
+ 0x40, 0x5e, 0x58, 0xff, 0x3f, 0x5d, 0x58, 0xff,
+ 0x3f, 0x5d, 0x58, 0xff, 0x3f, 0x5d, 0x58, 0xff,
+ 0x27, 0x3f, 0x3d, 0xff, 0x26, 0x3e, 0x3c, 0xff,
+ 0x27, 0x3e, 0x3d, 0xff, 0x26, 0x3e, 0x3c, 0xff,
+ 0x2a, 0x35, 0x32, 0xff, 0x29, 0x35, 0x31, 0xff,
+ 0x29, 0x35, 0x32, 0xff, 0x29, 0x34, 0x31, 0xff,
+ 0x2a, 0x3d, 0x32, 0xff, 0x29, 0x3d, 0x31, 0xff,
+ 0x3a, 0x57, 0x4d, 0xff, 0x39, 0x56, 0x4d, 0xff,
+ 0x4b, 0x5e, 0x5b, 0xff, 0x4a, 0x5d, 0x5a, 0xff,
+ 0x66, 0x73, 0x71, 0xff, 0x65, 0x73, 0x70, 0xff,
+ 0x37, 0x3d, 0x2c, 0xff, 0x36, 0x3c, 0x2b, 0xff,
+ 0x32, 0x2d, 0x21, 0xff, 0x31, 0x2c, 0x21, 0xff,
+ 0x2c, 0x2e, 0x1e, 0xff, 0x2b, 0x2d, 0x1e, 0xff,
+ 0x32, 0x41, 0x29, 0xff, 0x31, 0x40, 0x29, 0xff,
+ 0x26, 0x2d, 0x1e, 0xff, 0x29, 0x34, 0x20, 0xff,
+ 0x29, 0x35, 0x21, 0xff, 0x26, 0x2c, 0x1e, 0xff,
+ 0x19, 0x25, 0x11, 0xff, 0x16, 0x1f, 0x13, 0xff,
+ 0x16, 0x1f, 0x13, 0xff, 0x13, 0x19, 0x16, 0xff,
+ 0x16, 0x1b, 0x11, 0xff, 0x16, 0x1b, 0x10, 0xff,
+ 0x16, 0x1b, 0x11, 0xff, 0x16, 0x1b, 0x10, 0xff,
+ 0x16, 0x1b, 0x16, 0xff, 0x13, 0x15, 0x13, 0xff,
+ 0x16, 0x1b, 0x16, 0xff, 0x18, 0x20, 0x18, 0xff,
+ 0x16, 0x1b, 0x11, 0xff, 0x16, 0x1b, 0x10, 0xff,
+ 0x13, 0x16, 0x11, 0xff, 0x16, 0x1b, 0x10, 0xff,
+ 0x19, 0x18, 0x19, 0xff, 0x13, 0x12, 0x13, 0xff,
+ 0x13, 0x13, 0x13, 0xff, 0x13, 0x13, 0x13, 0xff,
+ 0x11, 0x14, 0x11, 0xff, 0x10, 0x11, 0x10, 0xff,
+ 0x11, 0x12, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x19, 0x14, 0x19, 0xff, 0x23, 0x34, 0x34, 0xff,
+ 0x24, 0x35, 0x34, 0xff, 0x2e, 0x55, 0x4f, 0xff,
+ 0x52, 0x82, 0x7b, 0xff, 0x52, 0x81, 0x7b, 0xff,
+ 0x52, 0x82, 0x7c, 0xff, 0x52, 0x81, 0x7b, 0xff,
+ 0x42, 0x7a, 0x73, 0xff, 0x41, 0x79, 0x73, 0xff,
+ 0x42, 0x7a, 0x73, 0xff, 0x42, 0x79, 0x73, 0xff,
+ 0x42, 0x7e, 0x73, 0xff, 0x41, 0x7d, 0x73, 0xff,
+ 0x42, 0x7e, 0x73, 0xff, 0x39, 0x65, 0x5d, 0xff,
+ 0x4a, 0x70, 0x68, 0xff, 0x5a, 0x89, 0x83, 0xff,
+ 0x5b, 0x8a, 0x84, 0xff, 0x5a, 0x89, 0x83, 0xff,
+ 0x81, 0x88, 0x86, 0xff, 0x9c, 0x9d, 0x9c, 0xff,
+ 0x9d, 0x9e, 0x9d, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0x34, 0x35, 0x27, 0xff, 0x31, 0x2c, 0x21, 0xff,
+ 0x32, 0x2d, 0x21, 0xff, 0x31, 0x2c, 0x21, 0xff,
+ 0x29, 0x25, 0x19, 0xff, 0x29, 0x24, 0x18, 0xff,
+ 0x2a, 0x25, 0x19, 0xff, 0x29, 0x24, 0x19, 0xff,
+ 0x24, 0x25, 0x1c, 0xff, 0x23, 0x24, 0x1b, 0xff,
+ 0x24, 0x25, 0x1c, 0xff, 0x21, 0x1c, 0x19, 0xff,
+ 0x13, 0x1a, 0x16, 0xff, 0x13, 0x19, 0x16, 0xff,
+ 0x14, 0x1a, 0x16, 0xff, 0x13, 0x1a, 0x16, 0xff,
+ 0x13, 0x16, 0x11, 0xff, 0x16, 0x1b, 0x10, 0xff,
+ 0x14, 0x16, 0x11, 0xff, 0x16, 0x1b, 0x10, 0xff,
+ 0x13, 0x16, 0x13, 0xff, 0x13, 0x15, 0x13, 0xff,
+ 0x14, 0x16, 0x14, 0xff, 0x19, 0x20, 0x19, 0xff,
+ 0x19, 0x21, 0x11, 0xff, 0x16, 0x1b, 0x10, 0xff,
+ 0x14, 0x16, 0x11, 0xff, 0x13, 0x15, 0x10, 0xff,
+ 0x13, 0x13, 0x13, 0xff, 0x13, 0x13, 0x13, 0xff,
+ 0x14, 0x13, 0x14, 0xff, 0x13, 0x13, 0x13, 0xff,
+ 0x11, 0x0f, 0x11, 0xff, 0x10, 0x0f, 0x10, 0xff,
+ 0x11, 0x0f, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x19, 0x15, 0x19, 0xff, 0x18, 0x14, 0x18, 0xff,
+ 0x19, 0x15, 0x19, 0xff, 0x19, 0x14, 0x19, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x2c, 0x38, 0x34, 0xff,
+ 0x2c, 0x39, 0x35, 0xff, 0x2c, 0x39, 0x34, 0xff,
+ 0x34, 0x5c, 0x58, 0xff, 0x34, 0x5c, 0x58, 0xff,
+ 0x42, 0x7a, 0x74, 0xff, 0x42, 0x79, 0x73, 0xff,
+ 0x42, 0x7e, 0x73, 0xff, 0x42, 0x7d, 0x73, 0xff,
+ 0x42, 0x7e, 0x74, 0xff, 0x42, 0x7d, 0x73, 0xff,
+ 0x5b, 0x8a, 0x84, 0xff, 0x4a, 0x70, 0x68, 0xff,
+ 0x5b, 0x8a, 0x84, 0xff, 0x5a, 0x8a, 0x84, 0xff,
+ 0x81, 0x89, 0x87, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0x9d, 0x9e, 0x9d, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0x37, 0x3d, 0x2c, 0xff, 0x34, 0x34, 0x26, 0xff,
+ 0x31, 0x2d, 0x21, 0xff, 0x31, 0x2c, 0x20, 0xff,
+ 0x2c, 0x2e, 0x1e, 0xff, 0x29, 0x24, 0x18, 0xff,
+ 0x29, 0x24, 0x19, 0xff, 0x29, 0x24, 0x18, 0xff,
+ 0x24, 0x25, 0x1c, 0xff, 0x26, 0x2c, 0x1e, 0xff,
+ 0x24, 0x24, 0x1b, 0xff, 0x23, 0x24, 0x1b, 0xff,
+ 0x13, 0x1a, 0x16, 0xff, 0x10, 0x14, 0x18, 0xff,
+ 0x13, 0x1a, 0x16, 0xff, 0x10, 0x14, 0x18, 0xff,
+ 0x13, 0x16, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x10, 0x10, 0x10, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x10, 0x10, 0x10, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x13, 0x16, 0x11, 0xff, 0x13, 0x15, 0x10, 0xff,
+ 0x13, 0x16, 0x10, 0xff, 0x13, 0x15, 0x10, 0xff,
+ 0x19, 0x18, 0x19, 0xff, 0x0d, 0x0d, 0x0d, 0xff,
+ 0x13, 0x13, 0x13, 0xff, 0x0d, 0x0d, 0x0d, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x10, 0x0e, 0x10, 0xff,
+ 0x10, 0x0f, 0x10, 0xff, 0x10, 0x0e, 0x10, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x10, 0x10, 0x10, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x19, 0x14, 0x19, 0xff, 0x18, 0x14, 0x18, 0xff,
+ 0x19, 0x14, 0x19, 0xff, 0x18, 0x14, 0x18, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x19, 0x14, 0x10, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x19, 0x21, 0x21, 0xff, 0x18, 0x20, 0x21, 0xff,
+ 0x26, 0x3e, 0x3c, 0xff, 0x26, 0x3e, 0x3c, 0xff,
+ 0x32, 0x4d, 0x47, 0xff, 0x31, 0x4d, 0x47, 0xff,
+ 0x3a, 0x65, 0x5d, 0xff, 0x41, 0x7d, 0x73, 0xff,
+ 0x4a, 0x70, 0x68, 0xff, 0x5a, 0x89, 0x83, 0xff,
+ 0x5b, 0x8a, 0x84, 0xff, 0x5a, 0x89, 0x83, 0xff,
+ 0x9c, 0x9e, 0x9c, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0x9c, 0x9e, 0x9c, 0xff, 0x9c, 0x9d, 0x9c, 0xff,
+ 0x4b, 0x45, 0x3a, 0xff, 0x4a, 0x45, 0x3a, 0xff,
+ 0x4a, 0x45, 0x3a, 0xff, 0x4a, 0x45, 0x39, 0xff,
+ 0x3a, 0x43, 0x37, 0xff, 0x3a, 0x2c, 0x21, 0xff,
+ 0x3a, 0x2d, 0x21, 0xff, 0x39, 0x2c, 0x21, 0xff,
+ 0x2c, 0x34, 0x2c, 0xff, 0x21, 0x18, 0x10, 0xff,
+ 0x21, 0x19, 0x11, 0xff, 0x21, 0x18, 0x10, 0xff,
+ 0x19, 0x15, 0x19, 0xff, 0x19, 0x14, 0x19, 0xff,
+ 0x19, 0x15, 0x19, 0xff, 0x19, 0x14, 0x19, 0xff,
+ 0x16, 0x17, 0x14, 0xff, 0x16, 0x17, 0x13, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x19, 0x11, 0x11, 0xff, 0x19, 0x16, 0x13, 0xff,
+ 0x19, 0x16, 0x14, 0xff, 0x19, 0x15, 0x13, 0xff,
+ 0x16, 0x17, 0x16, 0xff, 0x21, 0x24, 0x21, 0xff,
+ 0x1c, 0x1e, 0x1c, 0xff, 0x1b, 0x1e, 0x1b, 0xff,
+ 0x21, 0x25, 0x21, 0xff, 0x1b, 0x1f, 0x1b, 0xff,
+ 0x16, 0x1a, 0x16, 0xff, 0x16, 0x19, 0x16, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x13, 0x14, 0x13, 0xff,
+ 0x14, 0x15, 0x14, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x16, 0x16, 0x16, 0xff, 0x16, 0x16, 0x16, 0xff,
+ 0x16, 0x16, 0x16, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x15, 0x19, 0xff, 0x10, 0x14, 0x19, 0xff,
+ 0x11, 0x15, 0x19, 0xff, 0x23, 0x20, 0x21, 0xff,
+ 0x32, 0x25, 0x21, 0xff, 0x42, 0x35, 0x31, 0xff,
+ 0x53, 0x45, 0x42, 0xff, 0x63, 0x55, 0x52, 0xff,
+ 0x7f, 0x77, 0x79, 0xff, 0x7e, 0x77, 0x79, 0xff,
+ 0x94, 0x8e, 0x94, 0xff, 0x94, 0x8e, 0x94, 0xff,
+ 0x95, 0x96, 0x95, 0xff, 0x94, 0x96, 0x94, 0xff,
+ 0x94, 0x96, 0x94, 0xff, 0x94, 0x96, 0x94, 0xff,
+ 0x4d, 0x5f, 0x52, 0xff, 0x4a, 0x44, 0x39, 0xff,
+ 0x4a, 0x45, 0x3a, 0xff, 0x4a, 0x45, 0x39, 0xff,
+ 0x3a, 0x42, 0x37, 0xff, 0x39, 0x42, 0x36, 0xff,
+ 0x3a, 0x42, 0x37, 0xff, 0x39, 0x2c, 0x21, 0xff,
+ 0x2c, 0x33, 0x2c, 0xff, 0x2b, 0x33, 0x2b, 0xff,
+ 0x27, 0x26, 0x1e, 0xff, 0x26, 0x25, 0x1e, 0xff,
+ 0x1c, 0x1e, 0x1c, 0xff, 0x1b, 0x1d, 0x1b, 0xff,
+ 0x1c, 0x1e, 0x1c, 0xff, 0x1b, 0x1d, 0x1b, 0xff,
+ 0x16, 0x17, 0x13, 0xff, 0x16, 0x17, 0x13, 0xff,
+ 0x1c, 0x1e, 0x16, 0xff, 0x16, 0x17, 0x13, 0xff,
+ 0x19, 0x16, 0x13, 0xff, 0x18, 0x15, 0x13, 0xff,
+ 0x19, 0x16, 0x13, 0xff, 0x18, 0x15, 0x13, 0xff,
+ 0x16, 0x17, 0x16, 0xff, 0x16, 0x17, 0x16, 0xff,
+ 0x1c, 0x1e, 0x1c, 0xff, 0x16, 0x17, 0x16, 0xff,
+ 0x11, 0x14, 0x11, 0xff, 0x1b, 0x1f, 0x1b, 0xff,
+ 0x1c, 0x1f, 0x1c, 0xff, 0x16, 0x19, 0x16, 0xff,
+ 0x16, 0x18, 0x16, 0xff, 0x13, 0x14, 0x13, 0xff,
+ 0x13, 0x14, 0x13, 0xff, 0x18, 0x1c, 0x18, 0xff,
+ 0x1c, 0x1f, 0x1c, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x1c, 0x1f, 0x1c, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x14, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x14, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x16, 0x16, 0x16, 0xff, 0x16, 0x15, 0x16, 0xff,
+ 0x16, 0x16, 0x16, 0xff, 0x1b, 0x1b, 0x1b, 0xff,
+ 0x11, 0x14, 0x19, 0xff, 0x10, 0x14, 0x18, 0xff,
+ 0x24, 0x21, 0x21, 0xff, 0x37, 0x2c, 0x29, 0xff,
+ 0x31, 0x25, 0x21, 0xff, 0x41, 0x34, 0x31, 0xff,
+ 0x52, 0x45, 0x42, 0xff, 0x62, 0x55, 0x52, 0xff,
+ 0x68, 0x60, 0x5d, 0xff, 0x94, 0x8d, 0x94, 0xff,
+ 0x94, 0x8e, 0x94, 0xff, 0x94, 0x8d, 0x94, 0xff,
+ 0x94, 0x96, 0x94, 0xff, 0x94, 0x95, 0x94, 0xff,
+ 0x94, 0x96, 0x94, 0xff, 0x68, 0x7a, 0x76, 0xff,
+ 0x50, 0x78, 0x6b, 0xff, 0x4f, 0x78, 0x6b, 0xff,
+ 0x4d, 0x5f, 0x53, 0xff, 0x4a, 0x45, 0x39, 0xff,
+ 0x3a, 0x42, 0x37, 0xff, 0x39, 0x42, 0x37, 0xff,
+ 0x3a, 0x43, 0x37, 0xff, 0x39, 0x42, 0x37, 0xff,
+ 0x2c, 0x34, 0x2c, 0xff, 0x31, 0x41, 0x39, 0xff,
+ 0x2c, 0x34, 0x2c, 0xff, 0x2c, 0x33, 0x2c, 0xff,
+ 0x1e, 0x27, 0x1e, 0xff, 0x1e, 0x27, 0x1e, 0xff,
+ 0x1c, 0x1e, 0x1c, 0xff, 0x1b, 0x1e, 0x1b, 0xff,
+ 0x1c, 0x1e, 0x16, 0xff, 0x1b, 0x1d, 0x16, 0xff,
+ 0x21, 0x25, 0x19, 0xff, 0x1b, 0x1e, 0x16, 0xff,
+ 0x19, 0x21, 0x19, 0xff, 0x18, 0x1b, 0x16, 0xff,
+ 0x19, 0x1b, 0x16, 0xff, 0x19, 0x1b, 0x16, 0xff,
+ 0x1c, 0x1e, 0x1c, 0xff, 0x16, 0x17, 0x16, 0xff,
+ 0x16, 0x17, 0x16, 0xff, 0x16, 0x17, 0x16, 0xff,
+ 0x16, 0x1a, 0x16, 0xff, 0x16, 0x19, 0x16, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x16, 0x1a, 0x16, 0xff,
+ 0x13, 0x15, 0x13, 0xff, 0x13, 0x14, 0x13, 0xff,
+ 0x14, 0x15, 0x14, 0xff, 0x13, 0x14, 0x13, 0xff,
+ 0x1c, 0x1f, 0x1c, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x1c, 0x1f, 0x1c, 0xff, 0x1b, 0x1f, 0x1b, 0xff,
+ 0x19, 0x1f, 0x1c, 0xff, 0x18, 0x1f, 0x1b, 0xff,
+ 0x19, 0x1f, 0x1c, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x16, 0x16, 0x16, 0xff, 0x16, 0x15, 0x16, 0xff,
+ 0x16, 0x16, 0x16, 0xff, 0x16, 0x15, 0x16, 0xff,
+ 0x24, 0x21, 0x21, 0xff, 0x4a, 0x38, 0x31, 0xff,
+ 0x4a, 0x39, 0x32, 0xff, 0x4a, 0x39, 0x31, 0xff,
+ 0x53, 0x45, 0x42, 0xff, 0x52, 0x45, 0x42, 0xff,
+ 0x53, 0x45, 0x42, 0xff, 0x63, 0x55, 0x52, 0xff,
+ 0x68, 0x60, 0x5e, 0xff, 0x68, 0x60, 0x5d, 0xff,
+ 0x69, 0x60, 0x5e, 0xff, 0x7e, 0x77, 0x79, 0xff,
+ 0x68, 0x7b, 0x76, 0xff, 0x68, 0x7b, 0x76, 0xff,
+ 0x69, 0x7b, 0x76, 0xff, 0x68, 0x7b, 0x76, 0xff,
+ 0x52, 0x92, 0x84, 0xff, 0x52, 0x91, 0x83, 0xff,
+ 0x50, 0x78, 0x6b, 0xff, 0x4f, 0x78, 0x6a, 0xff,
+ 0x3a, 0x6d, 0x63, 0xff, 0x39, 0x6d, 0x62, 0xff,
+ 0x3a, 0x6d, 0x63, 0xff, 0x39, 0x57, 0x4c, 0xff,
+ 0x32, 0x41, 0x3a, 0xff, 0x31, 0x40, 0x39, 0xff,
+ 0x31, 0x41, 0x3a, 0xff, 0x2b, 0x33, 0x2b, 0xff,
+ 0x21, 0x31, 0x21, 0xff, 0x21, 0x30, 0x21, 0xff,
+ 0x21, 0x31, 0x21, 0xff, 0x1e, 0x27, 0x1e, 0xff,
+ 0x1c, 0x1e, 0x16, 0xff, 0x1b, 0x1d, 0x16, 0xff,
+ 0x1b, 0x1e, 0x16, 0xff, 0x1b, 0x1d, 0x15, 0xff,
+ 0x19, 0x21, 0x19, 0xff, 0x18, 0x20, 0x18, 0xff,
+ 0x19, 0x1b, 0x16, 0xff, 0x18, 0x1b, 0x15, 0xff,
+ 0x21, 0x25, 0x21, 0xff, 0x21, 0x24, 0x21, 0xff,
+ 0x1b, 0x1e, 0x1b, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x14, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x16, 0x1a, 0x16, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x13, 0x14, 0x13, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x16, 0x18, 0x16, 0xff, 0x15, 0x18, 0x15, 0xff,
+ 0x1c, 0x1f, 0x1c, 0xff, 0x26, 0x29, 0x26, 0xff,
+ 0x26, 0x2a, 0x26, 0xff, 0x31, 0x34, 0x31, 0xff,
+ 0x29, 0x35, 0x32, 0xff, 0x21, 0x29, 0x26, 0xff,
+ 0x21, 0x2a, 0x26, 0xff, 0x18, 0x1f, 0x1b, 0xff,
+ 0x16, 0x16, 0x16, 0xff, 0x16, 0x15, 0x16, 0xff,
+ 0x16, 0x16, 0x16, 0xff, 0x20, 0x20, 0x20, 0xff,
+ 0x37, 0x2d, 0x29, 0xff, 0x4a, 0x38, 0x31, 0xff,
+ 0x4a, 0x39, 0x31, 0xff, 0x4a, 0x38, 0x31, 0xff,
+ 0x42, 0x35, 0x32, 0xff, 0x41, 0x34, 0x31, 0xff,
+ 0x42, 0x35, 0x31, 0xff, 0x52, 0x44, 0x41, 0xff,
+ 0x52, 0x49, 0x42, 0xff, 0x52, 0x49, 0x41, 0xff,
+ 0x52, 0x49, 0x42, 0xff, 0x52, 0x48, 0x41, 0xff,
+ 0x11, 0x45, 0x3a, 0xff, 0x3c, 0x5f, 0x57, 0xff,
+ 0x10, 0x45, 0x3a, 0xff, 0x3c, 0x5f, 0x57, 0xff,
+ 0x5b, 0x7e, 0x74, 0xff, 0x4a, 0x6f, 0x65, 0xff,
+ 0x5b, 0x7e, 0x74, 0xff, 0x4a, 0x6e, 0x65, 0xff,
+ 0x40, 0x66, 0x5b, 0xff, 0x29, 0x4d, 0x4a, 0xff,
+ 0x29, 0x4d, 0x4a, 0xff, 0x4a, 0x71, 0x63, 0xff,
+ 0x53, 0x66, 0x63, 0xff, 0x42, 0x54, 0x4f, 0xff,
+ 0x32, 0x42, 0x3d, 0xff, 0x42, 0x53, 0x4f, 0xff,
+ 0x3a, 0x5e, 0x53, 0xff, 0x3a, 0x5d, 0x52, 0xff,
+ 0x24, 0x3a, 0x32, 0xff, 0x19, 0x28, 0x21, 0xff,
+ 0x21, 0x21, 0x19, 0xff, 0x21, 0x20, 0x19, 0xff,
+ 0x21, 0x21, 0x19, 0xff, 0x21, 0x20, 0x19, 0xff,
+ 0x21, 0x24, 0x21, 0xff, 0x21, 0x23, 0x21, 0xff,
+ 0x21, 0x19, 0x19, 0xff, 0x21, 0x23, 0x21, 0xff,
+ 0x19, 0x1d, 0x19, 0xff, 0x24, 0x2c, 0x26, 0xff,
+ 0x24, 0x2d, 0x27, 0xff, 0x23, 0x2c, 0x26, 0xff,
+ 0x19, 0x1d, 0x19, 0xff, 0x19, 0x1c, 0x19, 0xff,
+ 0x19, 0x1d, 0x19, 0xff, 0x19, 0x1c, 0x19, 0xff,
+ 0x27, 0x2c, 0x2a, 0xff, 0x08, 0x14, 0x10, 0xff,
+ 0x09, 0x15, 0x11, 0xff, 0x08, 0x14, 0x10, 0xff,
+ 0x21, 0x19, 0x19, 0xff, 0x21, 0x18, 0x19, 0xff,
+ 0x37, 0x2d, 0x2c, 0xff, 0x37, 0x2c, 0x2c, 0xff,
+ 0x32, 0x29, 0x2a, 0xff, 0x45, 0x3a, 0x3a, 0xff,
+ 0x45, 0x3a, 0x3a, 0xff, 0x44, 0x3a, 0x39, 0xff,
+ 0x3a, 0x31, 0x32, 0xff, 0x3a, 0x31, 0x31, 0xff,
+ 0x3a, 0x31, 0x32, 0xff, 0x39, 0x30, 0x31, 0xff,
+ 0x4b, 0x39, 0x3a, 0xff, 0x4a, 0x39, 0x3a, 0xff,
+ 0x4a, 0x39, 0x3a, 0xff, 0x4a, 0x39, 0x39, 0xff,
+ 0x37, 0x3d, 0x35, 0xff, 0x37, 0x3d, 0x34, 0xff,
+ 0x3a, 0x25, 0x21, 0xff, 0x37, 0x3d, 0x34, 0xff,
+ 0x19, 0x2d, 0x21, 0xff, 0x19, 0x2c, 0x21, 0xff,
+ 0x19, 0x2d, 0x21, 0xff, 0x19, 0x2c, 0x21, 0xff,
+ 0x11, 0x31, 0x21, 0xff, 0x10, 0x31, 0x21, 0xff,
+ 0x11, 0x31, 0x21, 0xff, 0x2c, 0x46, 0x39, 0xff,
+ 0x3a, 0x60, 0x58, 0xff, 0x29, 0x51, 0x4a, 0xff,
+ 0x3a, 0x60, 0x58, 0xff, 0x4a, 0x6e, 0x65, 0xff,
+ 0x3f, 0x65, 0x5b, 0xff, 0x34, 0x59, 0x52, 0xff,
+ 0x34, 0x59, 0x52, 0xff, 0x4a, 0x71, 0x62, 0xff,
+ 0x42, 0x54, 0x50, 0xff, 0x31, 0x42, 0x3c, 0xff,
+ 0x21, 0x31, 0x29, 0xff, 0x21, 0x30, 0x29, 0xff,
+ 0x2f, 0x4c, 0x42, 0xff, 0x39, 0x5d, 0x52, 0xff,
+ 0x24, 0x3a, 0x32, 0xff, 0x18, 0x28, 0x21, 0xff,
+ 0x21, 0x20, 0x19, 0xff, 0x20, 0x20, 0x18, 0xff,
+ 0x27, 0x38, 0x2f, 0xff, 0x26, 0x37, 0x2e, 0xff,
+ 0x21, 0x18, 0x19, 0xff, 0x20, 0x23, 0x20, 0xff,
+ 0x21, 0x23, 0x21, 0xff, 0x21, 0x18, 0x18, 0xff,
+ 0x19, 0x1c, 0x19, 0xff, 0x23, 0x2c, 0x26, 0xff,
+ 0x2f, 0x3d, 0x34, 0xff, 0x2e, 0x3c, 0x34, 0xff,
+ 0x3a, 0x3a, 0x34, 0xff, 0x29, 0x2b, 0x26, 0xff,
+ 0x29, 0x2b, 0x27, 0xff, 0x29, 0x2b, 0x26, 0xff,
+ 0x26, 0x2b, 0x29, 0xff, 0x26, 0x2b, 0x29, 0xff,
+ 0x27, 0x2b, 0x29, 0xff, 0x08, 0x14, 0x10, 0xff,
+ 0x37, 0x2d, 0x2c, 0xff, 0x36, 0x2c, 0x2b, 0xff,
+ 0x37, 0x2d, 0x2c, 0xff, 0x4c, 0x40, 0x3f, 0xff,
+ 0x45, 0x3a, 0x3a, 0xff, 0x44, 0x3a, 0x39, 0xff,
+ 0x58, 0x4c, 0x4a, 0xff, 0x57, 0x4b, 0x4a, 0xff,
+ 0x50, 0x4a, 0x4a, 0xff, 0x4f, 0x4a, 0x4a, 0xff,
+ 0x50, 0x4a, 0x4a, 0xff, 0x39, 0x30, 0x31, 0xff,
+ 0x4a, 0x39, 0x3a, 0xff, 0x4a, 0x38, 0x39, 0xff,
+ 0x4a, 0x39, 0x3a, 0xff, 0x4a, 0x38, 0x39, 0xff,
+ 0x37, 0x3d, 0x34, 0xff, 0x36, 0x3c, 0x34, 0xff,
+ 0x3a, 0x25, 0x21, 0xff, 0x39, 0x24, 0x21, 0xff,
+ 0x19, 0x2d, 0x21, 0xff, 0x23, 0x40, 0x31, 0xff,
+ 0x19, 0x2d, 0x21, 0xff, 0x18, 0x2c, 0x21, 0xff,
+ 0x11, 0x31, 0x21, 0xff, 0x10, 0x30, 0x20, 0xff,
+ 0x11, 0x31, 0x21, 0xff, 0x2c, 0x46, 0x39, 0xff,
+ 0x5b, 0x7e, 0x73, 0xff, 0x39, 0x60, 0x58, 0xff,
+ 0x4a, 0x6f, 0x66, 0xff, 0x39, 0x60, 0x58, 0xff,
+ 0x34, 0x59, 0x53, 0xff, 0x4a, 0x71, 0x62, 0xff,
+ 0x3f, 0x66, 0x5b, 0xff, 0x34, 0x59, 0x52, 0xff,
+ 0x53, 0x65, 0x63, 0xff, 0x31, 0x42, 0x3c, 0xff,
+ 0x42, 0x54, 0x50, 0xff, 0x31, 0x42, 0x3c, 0xff,
+ 0x2f, 0x4c, 0x42, 0xff, 0x39, 0x5d, 0x52, 0xff,
+ 0x2f, 0x4c, 0x42, 0xff, 0x2f, 0x4b, 0x42, 0xff,
+ 0x27, 0x38, 0x2f, 0xff, 0x26, 0x37, 0x2e, 0xff,
+ 0x27, 0x38, 0x2f, 0xff, 0x26, 0x37, 0x2f, 0xff,
+ 0x21, 0x2e, 0x29, 0xff, 0x21, 0x18, 0x18, 0xff,
+ 0x21, 0x19, 0x19, 0xff, 0x21, 0x18, 0x19, 0xff,
+ 0x19, 0x1d, 0x19, 0xff, 0x23, 0x2c, 0x26, 0xff,
+ 0x2f, 0x3d, 0x35, 0xff, 0x39, 0x4d, 0x42, 0xff,
+ 0x3a, 0x3a, 0x34, 0xff, 0x18, 0x1c, 0x18, 0xff,
+ 0x2a, 0x2c, 0x27, 0xff, 0x39, 0x3a, 0x34, 0xff,
+ 0x45, 0x42, 0x42, 0xff, 0x44, 0x42, 0x42, 0xff,
+ 0x45, 0x43, 0x42, 0xff, 0x44, 0x42, 0x42, 0xff,
+ 0x4d, 0x41, 0x3f, 0xff, 0x4d, 0x41, 0x3f, 0xff,
+ 0x4d, 0x41, 0x3f, 0xff, 0x4d, 0x41, 0x3f, 0xff,
+ 0x58, 0x4c, 0x4a, 0xff, 0x6b, 0x5d, 0x5a, 0xff,
+ 0x6b, 0x5e, 0x5b, 0xff, 0x6b, 0x5d, 0x5a, 0xff,
+ 0x66, 0x64, 0x63, 0xff, 0x65, 0x64, 0x62, 0xff,
+ 0x7c, 0x7e, 0x7c, 0xff, 0x65, 0x64, 0x63, 0xff,
+ 0x66, 0x61, 0x60, 0xff, 0x58, 0x4d, 0x4d, 0xff,
+ 0x4a, 0x39, 0x3a, 0xff, 0x58, 0x4d, 0x4d, 0xff,
+ 0x3a, 0x25, 0x21, 0xff, 0x37, 0x3c, 0x34, 0xff,
+ 0x37, 0x3d, 0x35, 0xff, 0x37, 0x3d, 0x34, 0xff,
+ 0x24, 0x41, 0x32, 0xff, 0x23, 0x41, 0x31, 0xff,
+ 0x24, 0x41, 0x32, 0xff, 0x39, 0x69, 0x52, 0xff,
+ 0x2c, 0x46, 0x3a, 0xff, 0x2c, 0x46, 0x39, 0xff,
+ 0x11, 0x31, 0x21, 0xff, 0x2c, 0x46, 0x39, 0xff,
+ 0x5b, 0x7e, 0x73, 0xff, 0x5a, 0x7d, 0x73, 0xff,
+ 0x4a, 0x6f, 0x65, 0xff, 0x39, 0x5f, 0x57, 0xff,
+ 0x34, 0x59, 0x52, 0xff, 0x29, 0x4d, 0x4a, 0xff,
+ 0x29, 0x4d, 0x4a, 0xff, 0x34, 0x59, 0x52, 0xff,
+ 0x42, 0x54, 0x50, 0xff, 0x41, 0x53, 0x4f, 0xff,
+ 0x42, 0x54, 0x50, 0xff, 0x52, 0x65, 0x62, 0xff,
+ 0x3a, 0x5d, 0x52, 0xff, 0x2e, 0x4b, 0x41, 0xff,
+ 0x3a, 0x5d, 0x52, 0xff, 0x39, 0x5d, 0x52, 0xff,
+ 0x32, 0x65, 0x5b, 0xff, 0x31, 0x65, 0x5a, 0xff,
+ 0x2c, 0x4e, 0x45, 0xff, 0x2b, 0x4e, 0x44, 0xff,
+ 0x21, 0x39, 0x32, 0xff, 0x21, 0x2e, 0x29, 0xff,
+ 0x21, 0x23, 0x21, 0xff, 0x20, 0x2d, 0x29, 0xff,
+ 0x19, 0x1c, 0x19, 0xff, 0x18, 0x1c, 0x18, 0xff,
+ 0x19, 0x1c, 0x19, 0xff, 0x23, 0x2c, 0x26, 0xff,
+ 0x29, 0x2b, 0x27, 0xff, 0x29, 0x2b, 0x26, 0xff,
+ 0x3a, 0x3a, 0x34, 0xff, 0x4a, 0x48, 0x41, 0xff,
+ 0x63, 0x59, 0x5b, 0xff, 0x62, 0x59, 0x5a, 0xff,
+ 0x63, 0x59, 0x5b, 0xff, 0x44, 0x42, 0x41, 0xff,
+ 0x4d, 0x41, 0x3f, 0xff, 0x62, 0x55, 0x52, 0xff,
+ 0x4d, 0x41, 0x3f, 0xff, 0x62, 0x55, 0x52, 0xff,
+ 0x58, 0x4c, 0x4a, 0xff, 0x57, 0x4b, 0x4a, 0xff,
+ 0x58, 0x4c, 0x4a, 0xff, 0x57, 0x4b, 0x4a, 0xff,
+ 0x66, 0x64, 0x63, 0xff, 0x7b, 0x7d, 0x7b, 0xff,
+ 0x7b, 0x7e, 0x7b, 0xff, 0x7b, 0x7d, 0x7b, 0xff,
+ 0x73, 0x76, 0x73, 0xff, 0x73, 0x75, 0x73, 0xff,
+ 0x65, 0x61, 0x60, 0xff, 0x57, 0x4c, 0x4c, 0xff,
+ 0x37, 0x3d, 0x34, 0xff, 0x34, 0x55, 0x47, 0xff,
+ 0x31, 0x6d, 0x5b, 0xff, 0x31, 0x6d, 0x5a, 0xff,
+ 0x3a, 0x69, 0x52, 0xff, 0x2e, 0x55, 0x41, 0xff,
+ 0x2f, 0x55, 0x42, 0xff, 0x2e, 0x55, 0x41, 0xff,
+ 0x47, 0x5c, 0x52, 0xff, 0x62, 0x71, 0x6b, 0xff,
+ 0x47, 0x5c, 0x52, 0xff, 0x62, 0x71, 0x6a, 0xff,
+ 0x48, 0x73, 0x6e, 0xff, 0x42, 0x55, 0x52, 0xff,
+ 0x42, 0x55, 0x53, 0xff, 0x42, 0x55, 0x52, 0xff,
+ 0x2a, 0x51, 0x42, 0xff, 0x29, 0x51, 0x42, 0xff,
+ 0x32, 0x5f, 0x50, 0xff, 0x39, 0x6c, 0x5d, 0xff,
+ 0x35, 0x5a, 0x50, 0xff, 0x31, 0x49, 0x42, 0xff,
+ 0x32, 0x49, 0x42, 0xff, 0x34, 0x59, 0x4f, 0xff,
+ 0x2a, 0x55, 0x4b, 0xff, 0x2c, 0x60, 0x52, 0xff,
+ 0x2f, 0x6b, 0x5b, 0xff, 0x2e, 0x6a, 0x5a, 0xff,
+ 0x3a, 0x66, 0x5b, 0xff, 0x3a, 0x65, 0x5a, 0xff,
+ 0x3a, 0x66, 0x5b, 0xff, 0x34, 0x4f, 0x47, 0xff,
+ 0x37, 0x34, 0x2c, 0xff, 0x37, 0x33, 0x2c, 0xff,
+ 0x21, 0x21, 0x19, 0xff, 0x21, 0x20, 0x19, 0xff,
+ 0x32, 0x29, 0x2a, 0xff, 0x31, 0x28, 0x29, 0xff,
+ 0x32, 0x29, 0x29, 0xff, 0x31, 0x28, 0x29, 0xff,
+ 0x4b, 0x3d, 0x3a, 0xff, 0x4a, 0x3d, 0x3a, 0xff,
+ 0x58, 0x4d, 0x4d, 0xff, 0x58, 0x4d, 0x4d, 0xff,
+ 0x53, 0x49, 0x4b, 0xff, 0x5d, 0x58, 0x58, 0xff,
+ 0x5e, 0x58, 0x58, 0xff, 0x5d, 0x58, 0x58, 0xff,
+ 0x53, 0x45, 0x42, 0xff, 0x52, 0x45, 0x42, 0xff,
+ 0x53, 0x45, 0x42, 0xff, 0x63, 0x5c, 0x5a, 0xff,
+ 0x40, 0x50, 0x48, 0xff, 0x45, 0x42, 0x3c, 0xff,
+ 0x4a, 0x35, 0x32, 0xff, 0x4a, 0x34, 0x31, 0xff,
+ 0x32, 0x31, 0x2a, 0xff, 0x34, 0x43, 0x3c, 0xff,
+ 0x37, 0x57, 0x50, 0xff, 0x39, 0x69, 0x63, 0xff,
+ 0x4b, 0x72, 0x6b, 0xff, 0x4a, 0x71, 0x6b, 0xff,
+ 0x4a, 0x72, 0x6b, 0xff, 0x4a, 0x71, 0x6b, 0xff,
+ 0x1f, 0x66, 0x53, 0xff, 0x29, 0x75, 0x63, 0xff,
+ 0x29, 0x76, 0x63, 0xff, 0x29, 0x75, 0x63, 0xff,
+ 0x27, 0x73, 0x5b, 0xff, 0x26, 0x73, 0x5a, 0xff,
+ 0x27, 0x73, 0x5b, 0xff, 0x26, 0x73, 0x5a, 0xff,
+ 0x2c, 0x75, 0x5e, 0xff, 0x2c, 0x74, 0x5d, 0xff,
+ 0x2c, 0x74, 0x5e, 0xff, 0x42, 0x81, 0x73, 0xff,
+ 0x45, 0x64, 0x60, 0xff, 0x47, 0x72, 0x6d, 0xff,
+ 0x45, 0x64, 0x60, 0xff, 0x47, 0x72, 0x6d, 0xff,
+ 0x3a, 0x6c, 0x5d, 0xff, 0x39, 0x6c, 0x5d, 0xff,
+ 0x32, 0x5f, 0x50, 0xff, 0x29, 0x51, 0x42, 0xff,
+ 0x31, 0x49, 0x42, 0xff, 0x31, 0x48, 0x41, 0xff,
+ 0x34, 0x59, 0x50, 0xff, 0x34, 0x59, 0x4f, 0xff,
+ 0x2f, 0x6b, 0x5b, 0xff, 0x2e, 0x6a, 0x5a, 0xff,
+ 0x2c, 0x60, 0x52, 0xff, 0x2e, 0x6a, 0x5a, 0xff,
+ 0x3a, 0x65, 0x5b, 0xff, 0x39, 0x65, 0x5a, 0xff,
+ 0x34, 0x50, 0x48, 0xff, 0x29, 0x24, 0x21, 0xff,
+ 0x21, 0x20, 0x19, 0xff, 0x20, 0x20, 0x18, 0xff,
+ 0x37, 0x33, 0x2c, 0xff, 0x37, 0x33, 0x2c, 0xff,
+ 0x47, 0x3e, 0x3f, 0xff, 0x47, 0x3e, 0x3f, 0xff,
+ 0x48, 0x3e, 0x3f, 0xff, 0x5d, 0x53, 0x55, 0xff,
+ 0x58, 0x4d, 0x4d, 0xff, 0x57, 0x4c, 0x4c, 0xff,
+ 0x66, 0x5d, 0x60, 0xff, 0x65, 0x5d, 0x60, 0xff,
+ 0x68, 0x67, 0x66, 0xff, 0x68, 0x66, 0x65, 0xff,
+ 0x73, 0x76, 0x73, 0xff, 0x73, 0x75, 0x73, 0xff,
+ 0x73, 0x73, 0x73, 0xff, 0x73, 0x72, 0x73, 0xff,
+ 0x63, 0x5c, 0x5b, 0xff, 0x62, 0x5b, 0x5a, 0xff,
+ 0x45, 0x42, 0x3c, 0xff, 0x4a, 0x34, 0x31, 0xff,
+ 0x4a, 0x35, 0x32, 0xff, 0x4a, 0x34, 0x31, 0xff,
+ 0x31, 0x31, 0x29, 0xff, 0x31, 0x30, 0x29, 0xff,
+ 0x32, 0x31, 0x29, 0xff, 0x34, 0x43, 0x3c, 0xff,
+ 0x00, 0x51, 0x3a, 0xff, 0x31, 0x66, 0x5a, 0xff,
+ 0x19, 0x5c, 0x4a, 0xff, 0x31, 0x66, 0x5a, 0xff,
+ 0x29, 0x75, 0x63, 0xff, 0x29, 0x75, 0x62, 0xff,
+ 0x29, 0x76, 0x63, 0xff, 0x29, 0x75, 0x62, 0xff,
+ 0x31, 0x7e, 0x63, 0xff, 0x26, 0x72, 0x5a, 0xff,
+ 0x27, 0x73, 0x5b, 0xff, 0x31, 0x7d, 0x62, 0xff,
+ 0x37, 0x7b, 0x68, 0xff, 0x36, 0x7a, 0x68, 0xff,
+ 0x42, 0x82, 0x73, 0xff, 0x2c, 0x74, 0x5d, 0xff,
+ 0x4a, 0x82, 0x7c, 0xff, 0x47, 0x72, 0x6d, 0xff,
+ 0x48, 0x73, 0x6e, 0xff, 0x47, 0x73, 0x6e, 0xff,
+ 0x42, 0x7a, 0x6b, 0xff, 0x39, 0x6c, 0x5d, 0xff,
+ 0x3a, 0x6c, 0x5e, 0xff, 0x31, 0x5e, 0x4f, 0xff,
+ 0x34, 0x59, 0x50, 0xff, 0x37, 0x69, 0x5d, 0xff,
+ 0x3a, 0x7a, 0x6b, 0xff, 0x39, 0x79, 0x6b, 0xff,
+ 0x32, 0x76, 0x63, 0xff, 0x31, 0x75, 0x62, 0xff,
+ 0x32, 0x76, 0x63, 0xff, 0x29, 0x55, 0x4a, 0xff,
+ 0x34, 0x50, 0x48, 0xff, 0x34, 0x4f, 0x47, 0xff,
+ 0x2f, 0x3a, 0x35, 0xff, 0x2f, 0x3a, 0x34, 0xff,
+ 0x37, 0x34, 0x2c, 0xff, 0x4d, 0x46, 0x3f, 0xff,
+ 0x4d, 0x47, 0x3f, 0xff, 0x4d, 0x46, 0x3f, 0xff,
+ 0x5e, 0x54, 0x55, 0xff, 0x5d, 0x53, 0x55, 0xff,
+ 0x5e, 0x54, 0x55, 0xff, 0x73, 0x69, 0x6b, 0xff,
+ 0x73, 0x6e, 0x73, 0xff, 0x73, 0x6d, 0x73, 0xff,
+ 0x74, 0x6e, 0x74, 0xff, 0x73, 0x6d, 0x73, 0xff,
+ 0x68, 0x67, 0x66, 0xff, 0x68, 0x66, 0x65, 0xff,
+ 0x74, 0x76, 0x74, 0xff, 0x73, 0x75, 0x73, 0xff,
+ 0x73, 0x73, 0x73, 0xff, 0x83, 0x89, 0x8c, 0xff,
+ 0x74, 0x73, 0x74, 0xff, 0x63, 0x5c, 0x5a, 0xff,
+ 0x4a, 0x35, 0x32, 0xff, 0x4a, 0x34, 0x31, 0xff,
+ 0x45, 0x43, 0x3d, 0xff, 0x44, 0x42, 0x3c, 0xff,
+ 0x34, 0x44, 0x3d, 0xff, 0x34, 0x43, 0x3c, 0xff,
+ 0x35, 0x44, 0x3d, 0xff, 0x34, 0x43, 0x3c, 0xff,
+ 0x19, 0x5c, 0x4a, 0xff, 0x18, 0x5c, 0x4a, 0xff,
+ 0x32, 0x67, 0x5b, 0xff, 0x19, 0x5c, 0x4a, 0xff,
+ 0x13, 0x55, 0x42, 0xff, 0x13, 0x55, 0x42, 0xff,
+ 0x1f, 0x66, 0x53, 0xff, 0x29, 0x75, 0x63, 0xff,
+ 0x1c, 0x68, 0x53, 0xff, 0x31, 0x7d, 0x62, 0xff,
+ 0x27, 0x73, 0x5b, 0xff, 0x31, 0x7d, 0x63, 0xff,
+ 0x37, 0x7b, 0x68, 0xff, 0x37, 0x7b, 0x68, 0xff,
+ 0x2c, 0x74, 0x5e, 0xff, 0x21, 0x6d, 0x52, 0xff,
+ 0x47, 0x73, 0x6e, 0xff, 0x4a, 0x81, 0x7b, 0xff,
+ 0x4a, 0x82, 0x7b, 0xff, 0x4a, 0x81, 0x7b, 0xff,
+ 0x42, 0x7a, 0x6b, 0xff, 0x31, 0x5e, 0x4f, 0xff,
+ 0x31, 0x5e, 0x50, 0xff, 0x29, 0x50, 0x41, 0xff,
+ 0x32, 0x49, 0x42, 0xff, 0x36, 0x69, 0x5d, 0xff,
+ 0x3a, 0x79, 0x6b, 0xff, 0x39, 0x79, 0x6a, 0xff,
+ 0x2c, 0x60, 0x52, 0xff, 0x29, 0x55, 0x4a, 0xff,
+ 0x29, 0x55, 0x4a, 0xff, 0x29, 0x55, 0x4a, 0xff,
+ 0x34, 0x50, 0x47, 0xff, 0x34, 0x4f, 0x47, 0xff,
+ 0x34, 0x50, 0x47, 0xff, 0x39, 0x65, 0x5a, 0xff,
+ 0x63, 0x59, 0x52, 0xff, 0x62, 0x59, 0x52, 0xff,
+ 0x63, 0x59, 0x52, 0xff, 0x62, 0x59, 0x52, 0xff,
+ 0x73, 0x69, 0x6b, 0xff, 0x73, 0x69, 0x6b, 0xff,
+ 0x73, 0x69, 0x6b, 0xff, 0x73, 0x69, 0x6a, 0xff,
+ 0x73, 0x6d, 0x73, 0xff, 0x73, 0x6d, 0x73, 0xff,
+ 0x65, 0x5d, 0x60, 0xff, 0x65, 0x5d, 0x5f, 0xff,
+ 0x68, 0x67, 0x66, 0xff, 0x68, 0x66, 0x65, 0xff,
+ 0x68, 0x67, 0x65, 0xff, 0x68, 0x66, 0x65, 0xff,
+ 0x73, 0x73, 0x73, 0xff, 0x73, 0x72, 0x73, 0xff,
+ 0x84, 0x8a, 0x8c, 0xff, 0x62, 0x5b, 0x5a, 0xff,
+ 0x3f, 0x50, 0x47, 0xff, 0x44, 0x42, 0x3c, 0xff,
+ 0x3a, 0x5d, 0x52, 0xff, 0x39, 0x5d, 0x52, 0xff,
+ 0x37, 0x57, 0x50, 0xff, 0x36, 0x56, 0x4f, 0xff,
+ 0x37, 0x56, 0x50, 0xff, 0x36, 0x56, 0x4f, 0xff,
+ 0x19, 0x5c, 0x4a, 0xff, 0x18, 0x5b, 0x4a, 0xff,
+ 0x19, 0x5c, 0x4a, 0xff, 0x00, 0x50, 0x39, 0xff,
+ 0x08, 0x45, 0x32, 0xff, 0x13, 0x55, 0x41, 0xff,
+ 0x1e, 0x65, 0x52, 0xff, 0x13, 0x55, 0x41, 0xff,
+ 0x11, 0x5d, 0x4a, 0xff, 0x10, 0x5d, 0x4a, 0xff,
+ 0x10, 0x5d, 0x4a, 0xff, 0x26, 0x72, 0x5a, 0xff,
+ 0x21, 0x6d, 0x52, 0xff, 0x21, 0x6d, 0x52, 0xff,
+ 0x2c, 0x74, 0x5d, 0xff, 0x20, 0x6d, 0x52, 0xff,
+ 0x4b, 0x86, 0x7c, 0xff, 0x4a, 0x86, 0x7b, 0xff,
+ 0x4a, 0x86, 0x7c, 0xff, 0x4a, 0x74, 0x6b, 0xff,
+ 0x45, 0x66, 0x5e, 0xff, 0x45, 0x65, 0x5d, 0xff,
+ 0x60, 0x76, 0x71, 0xff, 0x44, 0x65, 0x5d, 0xff,
+ 0x4d, 0x62, 0x5b, 0xff, 0x31, 0x55, 0x4a, 0xff,
+ 0x4d, 0x61, 0x5b, 0xff, 0x4d, 0x61, 0x5a, 0xff,
+ 0x63, 0x66, 0x63, 0xff, 0x63, 0x65, 0x63, 0xff,
+ 0x6e, 0x70, 0x6e, 0xff, 0x6e, 0x70, 0x6e, 0xff,
+ 0x79, 0x75, 0x74, 0xff, 0x79, 0x74, 0x73, 0xff,
+ 0x74, 0x6e, 0x6b, 0xff, 0x7e, 0x7b, 0x7b, 0xff,
+ 0x7f, 0x79, 0x7c, 0xff, 0x79, 0x73, 0x73, 0xff,
+ 0x7e, 0x78, 0x7c, 0xff, 0x78, 0x73, 0x73, 0xff,
+ 0x74, 0x72, 0x71, 0xff, 0x84, 0x81, 0x7b, 0xff,
+ 0x7c, 0x7a, 0x76, 0xff, 0x6b, 0x69, 0x6b, 0xff,
+ 0x6e, 0x6c, 0x6e, 0xff, 0x6e, 0x6c, 0x6e, 0xff,
+ 0x53, 0x51, 0x53, 0xff, 0x52, 0x51, 0x52, 0xff,
+ 0x5b, 0x5e, 0x5b, 0xff, 0x63, 0x65, 0x63, 0xff,
+ 0x63, 0x66, 0x63, 0xff, 0x63, 0x65, 0x63, 0xff,
+ 0x40, 0x6e, 0x66, 0xff, 0x3f, 0x6d, 0x65, 0xff,
+ 0x3f, 0x6e, 0x66, 0xff, 0x3f, 0x6d, 0x65, 0xff,
+ 0x19, 0x4d, 0x3a, 0xff, 0x1b, 0x5a, 0x47, 0xff,
+ 0x1f, 0x68, 0x55, 0xff, 0x19, 0x4d, 0x39, 0xff,
+ 0x11, 0x35, 0x2a, 0xff, 0x10, 0x35, 0x29, 0xff,
+ 0x11, 0x35, 0x29, 0xff, 0x19, 0x4b, 0x3c, 0xff,
+ 0x19, 0x58, 0x42, 0xff, 0x19, 0x58, 0x42, 0xff,
+ 0x11, 0x47, 0x32, 0xff, 0x08, 0x34, 0x21, 0xff,
+ 0x19, 0x53, 0x3a, 0xff, 0x19, 0x52, 0x3a, 0xff,
+ 0x19, 0x53, 0x3a, 0xff, 0x19, 0x52, 0x39, 0xff,
+ 0x1f, 0x57, 0x3d, 0xff, 0x08, 0x39, 0x21, 0xff,
+ 0x09, 0x39, 0x21, 0xff, 0x1e, 0x56, 0x3c, 0xff,
+ 0x21, 0x62, 0x4b, 0xff, 0x21, 0x61, 0x4a, 0xff,
+ 0x19, 0x54, 0x3f, 0xff, 0x10, 0x46, 0x34, 0xff,
+ 0x4a, 0x86, 0x7b, 0xff, 0x4a, 0x85, 0x7b, 0xff,
+ 0x4a, 0x86, 0x7c, 0xff, 0x4a, 0x62, 0x5a, 0xff,
+ 0x29, 0x55, 0x4a, 0xff, 0x44, 0x65, 0x5d, 0xff,
+ 0x60, 0x76, 0x71, 0xff, 0x60, 0x75, 0x70, 0xff,
+ 0x31, 0x55, 0x4a, 0xff, 0x4c, 0x61, 0x5a, 0xff,
+ 0x4d, 0x61, 0x5b, 0xff, 0x83, 0x79, 0x7b, 0xff,
+ 0x79, 0x7b, 0x79, 0xff, 0x78, 0x7a, 0x78, 0xff,
+ 0x84, 0x86, 0x84, 0xff, 0x83, 0x85, 0x83, 0xff,
+ 0x84, 0x82, 0x84, 0xff, 0x7e, 0x7a, 0x7b, 0xff,
+ 0x73, 0x6e, 0x6b, 0xff, 0x7e, 0x7a, 0x7b, 0xff,
+ 0x7e, 0x78, 0x7b, 0xff, 0x73, 0x6d, 0x6b, 0xff,
+ 0x79, 0x73, 0x73, 0xff, 0x78, 0x72, 0x73, 0xff,
+ 0x73, 0x71, 0x71, 0xff, 0x7b, 0x79, 0x75, 0xff,
+ 0x84, 0x82, 0x7c, 0xff, 0x73, 0x71, 0x70, 0xff,
+ 0x6e, 0x6c, 0x6e, 0xff, 0x7b, 0x79, 0x7b, 0xff,
+ 0x6e, 0x6c, 0x6e, 0xff, 0x60, 0x5e, 0x60, 0xff,
+ 0x63, 0x65, 0x63, 0xff, 0x6b, 0x6d, 0x6b, 0xff,
+ 0x6b, 0x6e, 0x6b, 0xff, 0x62, 0x65, 0x62, 0xff,
+ 0x5b, 0x55, 0x5b, 0xff, 0x4c, 0x61, 0x60, 0xff,
+ 0x4d, 0x61, 0x60, 0xff, 0x31, 0x79, 0x6b, 0xff,
+ 0x21, 0x75, 0x63, 0xff, 0x1e, 0x67, 0x55, 0xff,
+ 0x1e, 0x68, 0x55, 0xff, 0x18, 0x4d, 0x39, 0xff,
+ 0x11, 0x35, 0x29, 0xff, 0x18, 0x4b, 0x3c, 0xff,
+ 0x19, 0x4c, 0x3d, 0xff, 0x21, 0x62, 0x4f, 0xff,
+ 0x19, 0x58, 0x42, 0xff, 0x10, 0x46, 0x31, 0xff,
+ 0x11, 0x46, 0x32, 0xff, 0x08, 0x34, 0x21, 0xff,
+ 0x11, 0x3b, 0x29, 0xff, 0x18, 0x52, 0x39, 0xff,
+ 0x19, 0x53, 0x3a, 0xff, 0x10, 0x3b, 0x29, 0xff,
+ 0x08, 0x39, 0x21, 0xff, 0x08, 0x38, 0x20, 0xff,
+ 0x08, 0x39, 0x21, 0xff, 0x13, 0x47, 0x2e, 0xff,
+ 0x08, 0x39, 0x29, 0xff, 0x18, 0x53, 0x3f, 0xff,
+ 0x21, 0x61, 0x4a, 0xff, 0x18, 0x53, 0x3f, 0xff,
+ 0x4a, 0x63, 0x5b, 0xff, 0x4a, 0x62, 0x5a, 0xff,
+ 0x4a, 0x51, 0x4a, 0xff, 0x4a, 0x51, 0x4a, 0xff,
+ 0x29, 0x55, 0x4a, 0xff, 0x44, 0x65, 0x5d, 0xff,
+ 0x60, 0x76, 0x71, 0xff, 0x60, 0x75, 0x70, 0xff,
+ 0x68, 0x6e, 0x6b, 0xff, 0x68, 0x6d, 0x6b, 0xff,
+ 0x84, 0x7a, 0x7c, 0xff, 0x84, 0x79, 0x7b, 0xff,
+ 0x84, 0x86, 0x84, 0xff, 0x78, 0x7b, 0x78, 0xff,
+ 0x84, 0x86, 0x84, 0xff, 0x84, 0x85, 0x84, 0xff,
+ 0x7e, 0x7b, 0x7c, 0xff, 0x7e, 0x7b, 0x7b, 0xff,
+ 0x7f, 0x7b, 0x7c, 0xff, 0x7e, 0x7b, 0x7b, 0xff,
+ 0x84, 0x7e, 0x84, 0xff, 0x7e, 0x78, 0x7b, 0xff,
+ 0x74, 0x6e, 0x6b, 0xff, 0x79, 0x73, 0x73, 0xff,
+ 0x73, 0x72, 0x71, 0xff, 0x6b, 0x69, 0x6b, 0xff,
+ 0x6b, 0x6a, 0x6b, 0xff, 0x7b, 0x79, 0x76, 0xff,
+ 0x7c, 0x7a, 0x7c, 0xff, 0x7b, 0x79, 0x7b, 0xff,
+ 0x7c, 0x7a, 0x7c, 0xff, 0x6e, 0x6c, 0x6e, 0xff,
+ 0x63, 0x65, 0x63, 0xff, 0x62, 0x65, 0x62, 0xff,
+ 0x6b, 0x6e, 0x6b, 0xff, 0x5a, 0x5d, 0x5a, 0xff,
+ 0x5b, 0x55, 0x5b, 0xff, 0x4d, 0x61, 0x60, 0xff,
+ 0x3f, 0x6e, 0x66, 0xff, 0x3f, 0x6d, 0x65, 0xff,
+ 0x1e, 0x68, 0x55, 0xff, 0x1e, 0x68, 0x55, 0xff,
+ 0x1f, 0x68, 0x55, 0xff, 0x1b, 0x5a, 0x47, 0xff,
+ 0x19, 0x4c, 0x3d, 0xff, 0x21, 0x62, 0x4f, 0xff,
+ 0x21, 0x63, 0x50, 0xff, 0x29, 0x79, 0x63, 0xff,
+ 0x21, 0x6a, 0x53, 0xff, 0x18, 0x57, 0x42, 0xff,
+ 0x11, 0x47, 0x32, 0xff, 0x08, 0x35, 0x21, 0xff,
+ 0x09, 0x25, 0x19, 0xff, 0x18, 0x52, 0x39, 0xff,
+ 0x21, 0x6a, 0x4a, 0xff, 0x19, 0x52, 0x39, 0xff,
+ 0x13, 0x48, 0x2f, 0xff, 0x08, 0x38, 0x21, 0xff,
+ 0x14, 0x48, 0x2f, 0xff, 0x13, 0x47, 0x2f, 0xff,
+ 0x11, 0x46, 0x34, 0xff, 0x18, 0x53, 0x3f, 0xff,
+ 0x19, 0x54, 0x3f, 0xff, 0x21, 0x61, 0x4a, 0xff,
+ 0x4a, 0x51, 0x4a, 0xff, 0x4a, 0x62, 0x5a, 0xff,
+ 0x4a, 0x63, 0x5b, 0xff, 0x4a, 0x62, 0x5a, 0xff,
+ 0x45, 0x65, 0x5d, 0xff, 0x60, 0x75, 0x70, 0xff,
+ 0x7b, 0x86, 0x84, 0xff, 0x5f, 0x75, 0x70, 0xff,
+ 0x68, 0x6d, 0x6b, 0xff, 0x68, 0x6d, 0x6b, 0xff,
+ 0x68, 0x6d, 0x6b, 0xff, 0x68, 0x6d, 0x6a, 0xff,
+ 0x79, 0x7b, 0x79, 0xff, 0x78, 0x7a, 0x78, 0xff,
+ 0x84, 0x86, 0x84, 0xff, 0x78, 0x7a, 0x78, 0xff,
+ 0x84, 0x82, 0x84, 0xff, 0x83, 0x81, 0x83, 0xff,
+ 0x84, 0x82, 0x84, 0xff, 0x83, 0x81, 0x83, 0xff,
+ 0x84, 0x7e, 0x84, 0xff, 0x83, 0x7d, 0x83, 0xff,
+ 0x7e, 0x78, 0x7b, 0xff, 0x7e, 0x78, 0x7b, 0xff,
+ 0x7c, 0x7a, 0x76, 0xff, 0x73, 0x71, 0x70, 0xff,
+ 0x6b, 0x69, 0x6b, 0xff, 0x6a, 0x69, 0x6a, 0xff,
+ 0x7c, 0x7a, 0x7c, 0xff, 0x6d, 0x6c, 0x6d, 0xff,
+ 0x6e, 0x6c, 0x6e, 0xff, 0x6d, 0x6b, 0x6d, 0xff,
+ 0x63, 0x65, 0x63, 0xff, 0x62, 0x65, 0x62, 0xff,
+ 0x5b, 0x5d, 0x5b, 0xff, 0x52, 0x55, 0x52, 0xff,
+ 0x5b, 0x55, 0x5b, 0xff, 0x3f, 0x6d, 0x65, 0xff,
+ 0x31, 0x79, 0x6b, 0xff, 0x3f, 0x6d, 0x65, 0xff,
+ 0x21, 0x76, 0x63, 0xff, 0x21, 0x75, 0x62, 0xff,
+ 0x1e, 0x68, 0x55, 0xff, 0x18, 0x4c, 0x39, 0xff,
+ 0x19, 0x4c, 0x3c, 0xff, 0x21, 0x62, 0x4f, 0xff,
+ 0x29, 0x79, 0x63, 0xff, 0x20, 0x62, 0x4f, 0xff,
+ 0x21, 0x69, 0x52, 0xff, 0x21, 0x69, 0x52, 0xff,
+ 0x19, 0x58, 0x42, 0xff, 0x18, 0x57, 0x41, 0xff,
+ 0x11, 0x3c, 0x29, 0xff, 0x18, 0x52, 0x39, 0xff,
+ 0x21, 0x69, 0x4a, 0xff, 0x20, 0x69, 0x4a, 0xff,
+ 0x29, 0x65, 0x4a, 0xff, 0x29, 0x65, 0x4a, 0xff,
+ 0x29, 0x65, 0x4a, 0xff, 0x29, 0x65, 0x4a, 0xff,
+ 0x19, 0x54, 0x3f, 0xff, 0x10, 0x46, 0x34, 0xff,
+ 0x08, 0x39, 0x29, 0xff, 0x08, 0x38, 0x29, 0xff,
+ 0x74, 0x72, 0x6b, 0xff, 0x7b, 0x7b, 0x76, 0xff,
+ 0x7c, 0x7b, 0x76, 0xff, 0x7b, 0x7b, 0x76, 0xff,
+ 0x87, 0x86, 0x84, 0xff, 0x79, 0x75, 0x73, 0xff,
+ 0x79, 0x76, 0x74, 0xff, 0x78, 0x75, 0x73, 0xff,
+ 0x7f, 0x7b, 0x79, 0xff, 0x7e, 0x7b, 0x79, 0xff,
+ 0x74, 0x6e, 0x6b, 0xff, 0x73, 0x6d, 0x6b, 0xff,
+ 0x74, 0x72, 0x74, 0xff, 0x7b, 0x78, 0x79, 0xff,
+ 0x84, 0x7f, 0x7e, 0xff, 0x83, 0x7f, 0x7e, 0xff,
+ 0x87, 0x87, 0x87, 0xff, 0x81, 0x80, 0x81, 0xff,
+ 0x87, 0x87, 0x87, 0xff, 0x81, 0x80, 0x81, 0xff,
+ 0x8c, 0x86, 0x84, 0xff, 0x8c, 0x86, 0x84, 0xff,
+ 0x8c, 0x86, 0x84, 0xff, 0x86, 0x80, 0x7e, 0xff,
+ 0x7c, 0x7e, 0x7c, 0xff, 0x73, 0x71, 0x70, 0xff,
+ 0x74, 0x72, 0x71, 0xff, 0x6b, 0x65, 0x65, 0xff,
+ 0x6b, 0x6a, 0x6b, 0xff, 0x6b, 0x69, 0x6b, 0xff,
+ 0x6b, 0x6a, 0x6b, 0xff, 0x6b, 0x69, 0x6b, 0xff,
+ 0x2f, 0x64, 0x5b, 0xff, 0x3c, 0x5a, 0x52, 0xff,
+ 0x4a, 0x51, 0x4a, 0xff, 0x3c, 0x5a, 0x52, 0xff,
+ 0x21, 0x6e, 0x5b, 0xff, 0x21, 0x6d, 0x5a, 0xff,
+ 0x21, 0x6e, 0x5b, 0xff, 0x21, 0x6d, 0x5a, 0xff,
+ 0x19, 0x68, 0x58, 0xff, 0x21, 0x79, 0x6b, 0xff,
+ 0x19, 0x68, 0x58, 0xff, 0x19, 0x68, 0x58, 0xff,
+ 0x21, 0x70, 0x5b, 0xff, 0x10, 0x5d, 0x4a, 0xff,
+ 0x11, 0x5d, 0x4a, 0xff, 0x19, 0x66, 0x52, 0xff,
+ 0x21, 0x66, 0x53, 0xff, 0x29, 0x6d, 0x5a, 0xff,
+ 0x19, 0x5d, 0x4a, 0xff, 0x31, 0x75, 0x63, 0xff,
+ 0x21, 0x6f, 0x58, 0xff, 0x21, 0x6f, 0x58, 0xff,
+ 0x21, 0x6f, 0x58, 0xff, 0x21, 0x6e, 0x58, 0xff,
+ 0x19, 0x66, 0x4b, 0xff, 0x19, 0x65, 0x4a, 0xff,
+ 0x2f, 0x7e, 0x66, 0xff, 0x2e, 0x7d, 0x65, 0xff,
+ 0x27, 0x6e, 0x58, 0xff, 0x1b, 0x61, 0x4d, 0xff,
+ 0x11, 0x55, 0x42, 0xff, 0x10, 0x55, 0x42, 0xff,
+ 0x8c, 0x8e, 0x8c, 0xff, 0x8b, 0x8d, 0x8b, 0xff,
+ 0x8c, 0x8e, 0x8c, 0xff, 0x83, 0x84, 0x81, 0xff,
+ 0x79, 0x75, 0x73, 0xff, 0x78, 0x75, 0x73, 0xff,
+ 0x6b, 0x65, 0x63, 0xff, 0x6b, 0x65, 0x62, 0xff,
+ 0x73, 0x6d, 0x6b, 0xff, 0x89, 0x88, 0x86, 0xff,
+ 0x89, 0x88, 0x87, 0xff, 0x7e, 0x7a, 0x78, 0xff,
+ 0x7b, 0x78, 0x79, 0xff, 0x83, 0x7e, 0x7e, 0xff,
+ 0x84, 0x7f, 0x7e, 0xff, 0x8c, 0x85, 0x83, 0xff,
+ 0x86, 0x87, 0x86, 0xff, 0x8b, 0x8d, 0x8b, 0xff,
+ 0x87, 0x87, 0x87, 0xff, 0x81, 0x80, 0x81, 0xff,
+ 0x86, 0x80, 0x7e, 0xff, 0x86, 0x80, 0x7e, 0xff,
+ 0x87, 0x80, 0x7e, 0xff, 0x86, 0x80, 0x7e, 0xff,
+ 0x7b, 0x7e, 0x7b, 0xff, 0x6b, 0x65, 0x65, 0xff,
+ 0x6b, 0x65, 0x66, 0xff, 0x6b, 0x65, 0x65, 0xff,
+ 0x6b, 0x69, 0x6b, 0xff, 0x60, 0x5e, 0x5d, 0xff,
+ 0x60, 0x5f, 0x5d, 0xff, 0x55, 0x53, 0x4f, 0xff,
+ 0x4a, 0x51, 0x4a, 0xff, 0x4a, 0x51, 0x4a, 0xff,
+ 0x2f, 0x64, 0x5b, 0xff, 0x21, 0x6d, 0x62, 0xff,
+ 0x1c, 0x67, 0x52, 0xff, 0x16, 0x5f, 0x4a, 0xff,
+ 0x1c, 0x67, 0x52, 0xff, 0x21, 0x6d, 0x5a, 0xff,
+ 0x19, 0x68, 0x58, 0xff, 0x18, 0x67, 0x57, 0xff,
+ 0x19, 0x68, 0x58, 0xff, 0x21, 0x79, 0x6b, 0xff,
+ 0x29, 0x7a, 0x63, 0xff, 0x20, 0x70, 0x5a, 0xff,
+ 0x21, 0x70, 0x5b, 0xff, 0x21, 0x70, 0x5a, 0xff,
+ 0x31, 0x75, 0x63, 0xff, 0x31, 0x75, 0x62, 0xff,
+ 0x29, 0x6e, 0x5b, 0xff, 0x31, 0x75, 0x62, 0xff,
+ 0x31, 0x78, 0x66, 0xff, 0x41, 0x81, 0x73, 0xff,
+ 0x42, 0x82, 0x73, 0xff, 0x31, 0x78, 0x65, 0xff,
+ 0x2f, 0x7e, 0x66, 0xff, 0x2e, 0x7d, 0x65, 0xff,
+ 0x3a, 0x8a, 0x73, 0xff, 0x2e, 0x7d, 0x65, 0xff,
+ 0x26, 0x6d, 0x58, 0xff, 0x26, 0x6d, 0x57, 0xff,
+ 0x32, 0x7a, 0x63, 0xff, 0x31, 0x79, 0x62, 0xff,
+ 0x8c, 0x8e, 0x8c, 0xff, 0x83, 0x84, 0x81, 0xff,
+ 0x74, 0x72, 0x6b, 0xff, 0x73, 0x71, 0x6b, 0xff,
+ 0x87, 0x86, 0x84, 0xff, 0x86, 0x85, 0x83, 0xff,
+ 0x79, 0x76, 0x74, 0xff, 0x6b, 0x65, 0x63, 0xff,
+ 0x89, 0x89, 0x87, 0xff, 0x94, 0x96, 0x94, 0xff,
+ 0x8a, 0x89, 0x87, 0xff, 0x7e, 0x7b, 0x79, 0xff,
+ 0x8c, 0x86, 0x84, 0xff, 0x8c, 0x85, 0x83, 0xff,
+ 0x8c, 0x86, 0x84, 0xff, 0x8c, 0x85, 0x84, 0xff,
+ 0x87, 0x87, 0x87, 0xff, 0x8c, 0x8d, 0x8c, 0xff,
+ 0x81, 0x81, 0x81, 0xff, 0x81, 0x80, 0x81, 0xff,
+ 0x81, 0x7b, 0x79, 0xff, 0x86, 0x80, 0x7e, 0xff,
+ 0x81, 0x7b, 0x79, 0xff, 0x86, 0x80, 0x7e, 0xff,
+ 0x73, 0x72, 0x71, 0xff, 0x6b, 0x65, 0x65, 0xff,
+ 0x63, 0x59, 0x5b, 0xff, 0x63, 0x59, 0x5a, 0xff,
+ 0x6b, 0x6a, 0x6b, 0xff, 0x60, 0x5e, 0x5d, 0xff,
+ 0x55, 0x54, 0x50, 0xff, 0x4a, 0x49, 0x42, 0xff,
+ 0x4a, 0x51, 0x4a, 0xff, 0x2e, 0x64, 0x5a, 0xff,
+ 0x21, 0x6e, 0x63, 0xff, 0x21, 0x6d, 0x63, 0xff,
+ 0x11, 0x59, 0x42, 0xff, 0x10, 0x59, 0x42, 0xff,
+ 0x21, 0x6e, 0x5b, 0xff, 0x21, 0x6d, 0x5a, 0xff,
+ 0x19, 0x68, 0x58, 0xff, 0x18, 0x68, 0x58, 0xff,
+ 0x19, 0x68, 0x58, 0xff, 0x19, 0x68, 0x58, 0xff,
+ 0x19, 0x67, 0x53, 0xff, 0x21, 0x70, 0x5a, 0xff,
+ 0x21, 0x70, 0x5b, 0xff, 0x21, 0x70, 0x5a, 0xff,
+ 0x29, 0x6e, 0x5b, 0xff, 0x29, 0x6d, 0x5a, 0xff,
+ 0x32, 0x76, 0x63, 0xff, 0x31, 0x75, 0x63, 0xff,
+ 0x21, 0x6f, 0x58, 0xff, 0x21, 0x6e, 0x58, 0xff,
+ 0x32, 0x78, 0x66, 0xff, 0x31, 0x78, 0x65, 0xff,
+ 0x24, 0x72, 0x58, 0xff, 0x23, 0x71, 0x58, 0xff,
+ 0x2f, 0x7e, 0x66, 0xff, 0x24, 0x71, 0x58, 0xff,
+ 0x27, 0x6e, 0x58, 0xff, 0x1b, 0x61, 0x4d, 0xff,
+ 0x1c, 0x62, 0x4d, 0xff, 0x31, 0x79, 0x63, 0xff,
+ 0x7c, 0x7b, 0x76, 0xff, 0x73, 0x71, 0x6b, 0xff,
+ 0x73, 0x71, 0x6b, 0xff, 0x83, 0x84, 0x80, 0xff,
+ 0x94, 0x96, 0x94, 0xff, 0x94, 0x95, 0x94, 0xff,
+ 0x86, 0x86, 0x84, 0xff, 0x86, 0x85, 0x83, 0xff,
+ 0x94, 0x96, 0x94, 0xff, 0x89, 0x88, 0x86, 0xff,
+ 0x89, 0x88, 0x86, 0xff, 0x89, 0x88, 0x86, 0xff,
+ 0x84, 0x7f, 0x7e, 0xff, 0x8b, 0x85, 0x83, 0xff,
+ 0x8c, 0x86, 0x84, 0xff, 0x83, 0x7e, 0x7e, 0xff,
+ 0x87, 0x87, 0x87, 0xff, 0x81, 0x80, 0x81, 0xff,
+ 0x7b, 0x79, 0x7b, 0xff, 0x7b, 0x79, 0x7b, 0xff,
+ 0x81, 0x7b, 0x79, 0xff, 0x7b, 0x75, 0x73, 0xff,
+ 0x7b, 0x75, 0x73, 0xff, 0x80, 0x7a, 0x78, 0xff,
+ 0x73, 0x71, 0x71, 0xff, 0x62, 0x59, 0x5a, 0xff,
+ 0x63, 0x59, 0x5b, 0xff, 0x62, 0x59, 0x5a, 0xff,
+ 0x60, 0x5f, 0x5d, 0xff, 0x60, 0x5e, 0x5d, 0xff,
+ 0x60, 0x5e, 0x5d, 0xff, 0x5f, 0x5e, 0x5d, 0xff,
+ 0x21, 0x6d, 0x63, 0xff, 0x2e, 0x63, 0x5a, 0xff,
+ 0x2f, 0x64, 0x5b, 0xff, 0x3c, 0x5a, 0x52, 0xff,
+ 0x11, 0x59, 0x42, 0xff, 0x10, 0x59, 0x41, 0xff,
+ 0x21, 0x6d, 0x5b, 0xff, 0x10, 0x59, 0x41, 0xff,
+ 0x08, 0x45, 0x32, 0xff, 0x08, 0x44, 0x31, 0xff,
+ 0x08, 0x45, 0x31, 0xff, 0x10, 0x56, 0x44, 0xff,
+ 0x11, 0x5d, 0x4a, 0xff, 0x18, 0x66, 0x52, 0xff,
+ 0x10, 0x5d, 0x4a, 0xff, 0x18, 0x66, 0x52, 0xff,
+ 0x21, 0x65, 0x52, 0xff, 0x21, 0x65, 0x52, 0xff,
+ 0x31, 0x75, 0x63, 0xff, 0x29, 0x6d, 0x5a, 0xff,
+ 0x21, 0x6f, 0x58, 0xff, 0x10, 0x65, 0x4a, 0xff,
+ 0x21, 0x6f, 0x58, 0xff, 0x31, 0x78, 0x65, 0xff,
+ 0x24, 0x71, 0x58, 0xff, 0x23, 0x71, 0x57, 0xff,
+ 0x24, 0x71, 0x58, 0xff, 0x23, 0x71, 0x57, 0xff,
+ 0x1c, 0x61, 0x4d, 0xff, 0x1b, 0x61, 0x4c, 0xff,
+ 0x1b, 0x61, 0x4d, 0xff, 0x26, 0x6d, 0x57, 0xff,
+ 0x6b, 0x6e, 0x6b, 0xff, 0x6b, 0x6d, 0x6b, 0xff,
+ 0x7e, 0x7e, 0x7c, 0xff, 0xa4, 0x9e, 0x9c, 0xff,
+ 0x9d, 0x9a, 0x9d, 0xff, 0x9c, 0x9a, 0x9c, 0xff,
+ 0x9d, 0x9a, 0x9d, 0xff, 0x9c, 0x9a, 0x9c, 0xff,
+ 0x8c, 0x8a, 0x8c, 0xff, 0x84, 0x81, 0x84, 0xff,
+ 0x8c, 0x8a, 0x8c, 0xff, 0x83, 0x81, 0x83, 0xff,
+ 0x8c, 0x86, 0x84, 0xff, 0x86, 0x80, 0x7e, 0xff,
+ 0x87, 0x81, 0x7e, 0xff, 0x81, 0x7b, 0x78, 0xff,
+ 0x7c, 0x7e, 0x7c, 0xff, 0x7b, 0x7d, 0x7b, 0xff,
+ 0x76, 0x76, 0x74, 0xff, 0x76, 0x75, 0x73, 0xff,
+ 0x74, 0x72, 0x74, 0xff, 0x73, 0x71, 0x73, 0xff,
+ 0x74, 0x72, 0x74, 0xff, 0x73, 0x71, 0x73, 0xff,
+ 0x58, 0x5c, 0x58, 0xff, 0x58, 0x5c, 0x58, 0xff,
+ 0x58, 0x5c, 0x58, 0xff, 0x58, 0x5c, 0x58, 0xff,
+ 0x3a, 0x6c, 0x60, 0xff, 0x3a, 0x6c, 0x60, 0xff,
+ 0x3a, 0x6c, 0x60, 0xff, 0x52, 0x7d, 0x73, 0xff,
+ 0x2a, 0x76, 0x63, 0xff, 0x21, 0x61, 0x4f, 0xff,
+ 0x19, 0x4d, 0x3d, 0xff, 0x29, 0x75, 0x63, 0xff,
+ 0x21, 0x60, 0x4b, 0xff, 0x21, 0x60, 0x4a, 0xff,
+ 0x21, 0x60, 0x4a, 0xff, 0x19, 0x4a, 0x39, 0xff,
+ 0x11, 0x31, 0x21, 0xff, 0x10, 0x31, 0x21, 0xff,
+ 0x1c, 0x48, 0x37, 0xff, 0x1b, 0x47, 0x37, 0xff,
+ 0x11, 0x45, 0x32, 0xff, 0x1b, 0x58, 0x45, 0xff,
+ 0x11, 0x45, 0x32, 0xff, 0x1b, 0x58, 0x44, 0xff,
+ 0x1f, 0x58, 0x45, 0xff, 0x2c, 0x6b, 0x58, 0xff,
+ 0x2c, 0x6b, 0x58, 0xff, 0x2c, 0x6a, 0x58, 0xff,
+ 0x21, 0x6e, 0x53, 0xff, 0x1b, 0x5a, 0x42, 0xff,
+ 0x1c, 0x5b, 0x42, 0xff, 0x1b, 0x5a, 0x42, 0xff,
+ 0x2a, 0x72, 0x5b, 0xff, 0x29, 0x71, 0x5a, 0xff,
+ 0x29, 0x72, 0x5b, 0xff, 0x29, 0x71, 0x5a, 0xff,
+ 0x1f, 0x63, 0x50, 0xff, 0x1e, 0x62, 0x4f, 0xff,
+ 0x1f, 0x63, 0x50, 0xff, 0x1e, 0x62, 0x4f, 0xff,
+ 0x91, 0x8e, 0x8c, 0xff, 0x91, 0x8d, 0x8b, 0xff,
+ 0x92, 0x8e, 0x8c, 0xff, 0xa4, 0x9e, 0x9c, 0xff,
+ 0x94, 0x90, 0x91, 0xff, 0x94, 0x90, 0x91, 0xff,
+ 0x94, 0x91, 0x92, 0xff, 0x8c, 0x87, 0x86, 0xff,
+ 0x8c, 0x8a, 0x8c, 0xff, 0x8b, 0x89, 0x8b, 0xff,
+ 0x8c, 0x8a, 0x8c, 0xff, 0x8c, 0x89, 0x8c, 0xff,
+ 0x86, 0x80, 0x7e, 0xff, 0x86, 0x80, 0x7e, 0xff,
+ 0x7c, 0x76, 0x73, 0xff, 0x81, 0x7a, 0x78, 0xff,
+ 0x76, 0x75, 0x73, 0xff, 0x75, 0x75, 0x73, 0xff,
+ 0x76, 0x76, 0x73, 0xff, 0x76, 0x75, 0x73, 0xff,
+ 0x73, 0x71, 0x73, 0xff, 0x73, 0x71, 0x73, 0xff,
+ 0x68, 0x64, 0x66, 0xff, 0x5d, 0x56, 0x57, 0xff,
+ 0x58, 0x5c, 0x58, 0xff, 0x57, 0x5b, 0x57, 0xff,
+ 0x58, 0x5c, 0x58, 0xff, 0x52, 0x79, 0x73, 0xff,
+ 0x52, 0x7e, 0x73, 0xff, 0x39, 0x6c, 0x60, 0xff,
+ 0x3a, 0x6c, 0x60, 0xff, 0x21, 0x5a, 0x4c, 0xff,
+ 0x19, 0x4d, 0x3c, 0xff, 0x18, 0x4c, 0x3c, 0xff,
+ 0x19, 0x4d, 0x3d, 0xff, 0x21, 0x61, 0x4f, 0xff,
+ 0x21, 0x60, 0x4a, 0xff, 0x20, 0x5f, 0x4a, 0xff,
+ 0x19, 0x4a, 0x3a, 0xff, 0x10, 0x34, 0x29, 0xff,
+ 0x11, 0x31, 0x21, 0xff, 0x10, 0x30, 0x20, 0xff,
+ 0x1c, 0x48, 0x37, 0xff, 0x26, 0x5e, 0x4c, 0xff,
+ 0x11, 0x45, 0x31, 0xff, 0x10, 0x44, 0x31, 0xff,
+ 0x11, 0x45, 0x32, 0xff, 0x1b, 0x57, 0x44, 0xff,
+ 0x1e, 0x58, 0x45, 0xff, 0x1e, 0x57, 0x44, 0xff,
+ 0x1e, 0x58, 0x45, 0xff, 0x1e, 0x57, 0x44, 0xff,
+ 0x1e, 0x64, 0x4a, 0xff, 0x20, 0x6d, 0x52, 0xff,
+ 0x21, 0x6e, 0x52, 0xff, 0x21, 0x6d, 0x52, 0xff,
+ 0x1e, 0x5a, 0x45, 0xff, 0x1e, 0x5a, 0x44, 0xff,
+ 0x1e, 0x5b, 0x45, 0xff, 0x29, 0x71, 0x5a, 0xff,
+ 0x1e, 0x63, 0x50, 0xff, 0x1e, 0x62, 0x4f, 0xff,
+ 0x1e, 0x63, 0x50, 0xff, 0x1e, 0x62, 0x4f, 0xff,
+ 0x92, 0x8e, 0x8c, 0xff, 0x91, 0x8d, 0x8c, 0xff,
+ 0x92, 0x8e, 0x8c, 0xff, 0x91, 0x8e, 0x8c, 0xff,
+ 0x8c, 0x87, 0x87, 0xff, 0x8c, 0x87, 0x86, 0xff,
+ 0x8c, 0x87, 0x87, 0xff, 0x8c, 0x87, 0x86, 0xff,
+ 0x8c, 0x8a, 0x8c, 0xff, 0x94, 0x91, 0x94, 0xff,
+ 0x94, 0x92, 0x94, 0xff, 0x84, 0x81, 0x84, 0xff,
+ 0x87, 0x80, 0x7e, 0xff, 0x81, 0x7b, 0x78, 0xff,
+ 0x81, 0x7b, 0x79, 0xff, 0x7b, 0x75, 0x73, 0xff,
+ 0x76, 0x76, 0x73, 0xff, 0x76, 0x75, 0x73, 0xff,
+ 0x76, 0x76, 0x74, 0xff, 0x70, 0x6d, 0x6b, 0xff,
+ 0x68, 0x64, 0x66, 0xff, 0x68, 0x64, 0x65, 0xff,
+ 0x69, 0x64, 0x66, 0xff, 0x5d, 0x56, 0x58, 0xff,
+ 0x5b, 0x4d, 0x4a, 0xff, 0x5a, 0x4d, 0x4a, 0xff,
+ 0x55, 0x6b, 0x66, 0xff, 0x52, 0x79, 0x73, 0xff,
+ 0x3a, 0x6c, 0x60, 0xff, 0x21, 0x5a, 0x4d, 0xff,
+ 0x3a, 0x6c, 0x60, 0xff, 0x08, 0x49, 0x39, 0xff,
+ 0x11, 0x39, 0x29, 0xff, 0x10, 0x38, 0x29, 0xff,
+ 0x21, 0x62, 0x50, 0xff, 0x29, 0x75, 0x63, 0xff,
+ 0x29, 0x76, 0x5b, 0xff, 0x21, 0x60, 0x4a, 0xff,
+ 0x21, 0x60, 0x4a, 0xff, 0x10, 0x35, 0x29, 0xff,
+ 0x1c, 0x48, 0x37, 0xff, 0x1b, 0x47, 0x37, 0xff,
+ 0x32, 0x76, 0x63, 0xff, 0x31, 0x75, 0x63, 0xff,
+ 0x27, 0x6b, 0x58, 0xff, 0x26, 0x6a, 0x58, 0xff,
+ 0x1c, 0x58, 0x45, 0xff, 0x1b, 0x58, 0x44, 0xff,
+ 0x2c, 0x6b, 0x58, 0xff, 0x2c, 0x6a, 0x58, 0xff,
+ 0x1f, 0x58, 0x45, 0xff, 0x1e, 0x58, 0x44, 0xff,
+ 0x1c, 0x5b, 0x42, 0xff, 0x21, 0x6d, 0x52, 0xff,
+ 0x21, 0x6e, 0x53, 0xff, 0x21, 0x6d, 0x52, 0xff,
+ 0x29, 0x72, 0x5b, 0xff, 0x1e, 0x5a, 0x44, 0xff,
+ 0x1f, 0x5b, 0x45, 0xff, 0x13, 0x43, 0x2f, 0xff,
+ 0x13, 0x4c, 0x3d, 0xff, 0x1e, 0x62, 0x4f, 0xff,
+ 0x1f, 0x63, 0x50, 0xff, 0x1e, 0x62, 0x4f, 0xff,
+ 0x7e, 0x7e, 0x7c, 0xff, 0x7e, 0x7d, 0x7b, 0xff,
+ 0x7e, 0x7e, 0x7b, 0xff, 0x7e, 0x7d, 0x7b, 0xff,
+ 0x84, 0x7e, 0x7c, 0xff, 0x83, 0x7d, 0x7b, 0xff,
+ 0x84, 0x7e, 0x7b, 0xff, 0x8b, 0x86, 0x86, 0xff,
+ 0x84, 0x82, 0x84, 0xff, 0x83, 0x81, 0x83, 0xff,
+ 0x7b, 0x79, 0x7b, 0xff, 0x7b, 0x79, 0x7b, 0xff,
+ 0x7c, 0x76, 0x73, 0xff, 0x86, 0x80, 0x7e, 0xff,
+ 0x86, 0x80, 0x7e, 0xff, 0x80, 0x7a, 0x78, 0xff,
+ 0x76, 0x76, 0x73, 0xff, 0x6b, 0x65, 0x62, 0xff,
+ 0x6b, 0x65, 0x63, 0xff, 0x6a, 0x65, 0x62, 0xff,
+ 0x5d, 0x57, 0x58, 0xff, 0x5d, 0x56, 0x57, 0xff,
+ 0x5d, 0x56, 0x58, 0xff, 0x5d, 0x56, 0x57, 0xff,
+ 0x5b, 0x4d, 0x4a, 0xff, 0x52, 0x79, 0x73, 0xff,
+ 0x52, 0x79, 0x73, 0xff, 0x52, 0x79, 0x73, 0xff,
+ 0x21, 0x5b, 0x4d, 0xff, 0x21, 0x5a, 0x4c, 0xff,
+ 0x3a, 0x6c, 0x60, 0xff, 0x08, 0x48, 0x39, 0xff,
+ 0x19, 0x4d, 0x3c, 0xff, 0x18, 0x4d, 0x3c, 0xff,
+ 0x29, 0x75, 0x63, 0xff, 0x29, 0x75, 0x62, 0xff,
+ 0x29, 0x76, 0x5b, 0xff, 0x29, 0x75, 0x5a, 0xff,
+ 0x21, 0x60, 0x4a, 0xff, 0x20, 0x5f, 0x4a, 0xff,
+ 0x27, 0x5f, 0x4d, 0xff, 0x31, 0x75, 0x62, 0xff,
+ 0x31, 0x75, 0x63, 0xff, 0x31, 0x75, 0x62, 0xff,
+ 0x32, 0x7e, 0x6b, 0xff, 0x26, 0x6a, 0x57, 0xff,
+ 0x31, 0x7e, 0x6b, 0xff, 0x31, 0x7d, 0x6a, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x2c, 0x6a, 0x57, 0xff,
+ 0x10, 0x45, 0x31, 0xff, 0x10, 0x44, 0x31, 0xff,
+ 0x19, 0x51, 0x3a, 0xff, 0x1b, 0x5a, 0x41, 0xff,
+ 0x1e, 0x64, 0x4a, 0xff, 0x1e, 0x63, 0x4a, 0xff,
+ 0x29, 0x71, 0x5b, 0xff, 0x29, 0x71, 0x5a, 0xff,
+ 0x1e, 0x5a, 0x45, 0xff, 0x08, 0x2c, 0x18, 0xff,
+ 0x08, 0x35, 0x29, 0xff, 0x13, 0x4b, 0x3c, 0xff,
+ 0x13, 0x4c, 0x3c, 0xff, 0x13, 0x4b, 0x3c, 0xff,
+ 0x45, 0x3f, 0x35, 0xff, 0x2f, 0x2f, 0x26, 0xff,
+ 0x2f, 0x30, 0x27, 0xff, 0x44, 0x3e, 0x34, 0xff,
+ 0x32, 0x35, 0x32, 0xff, 0x47, 0x47, 0x42, 0xff,
+ 0x53, 0x51, 0x4a, 0xff, 0x47, 0x47, 0x42, 0xff,
+ 0x4b, 0x47, 0x3d, 0xff, 0x4a, 0x46, 0x3c, 0xff,
+ 0x4a, 0x47, 0x3d, 0xff, 0x63, 0x59, 0x4a, 0xff,
+ 0x69, 0x58, 0x45, 0xff, 0xe6, 0xa6, 0x8c, 0xff,
+ 0xe7, 0xa6, 0x8c, 0xff, 0xe6, 0xa6, 0x8c, 0xff,
+ 0x55, 0x4f, 0x4b, 0xff, 0x55, 0x4e, 0x4a, 0xff,
+ 0x55, 0x4f, 0x4a, 0xff, 0x55, 0x4e, 0x4a, 0xff,
+ 0x42, 0x41, 0x3a, 0xff, 0x42, 0x41, 0x3a, 0xff,
+ 0x6b, 0x59, 0x4a, 0xff, 0xbd, 0x89, 0x6b, 0xff,
+ 0xdf, 0x9a, 0x84, 0xff, 0xde, 0x9a, 0x84, 0xff,
+ 0xde, 0x9a, 0x84, 0xff, 0xde, 0x9a, 0x83, 0xff,
+ 0xdf, 0x96, 0x7c, 0xff, 0xde, 0x96, 0x7b, 0xff,
+ 0xe4, 0xa4, 0x92, 0xff, 0xe6, 0xaa, 0x9c, 0xff,
+ 0xea, 0xb1, 0x9a, 0xff, 0xe9, 0xb1, 0x9a, 0xff,
+ 0xe4, 0xa8, 0x8f, 0xff, 0xde, 0x9e, 0x83, 0xff,
+ 0xdf, 0x9e, 0x84, 0xff, 0xe6, 0xa3, 0x8c, 0xff,
+ 0xef, 0xa9, 0x94, 0xff, 0xf7, 0xae, 0x9c, 0xff,
+ 0xef, 0xa6, 0x8c, 0xff, 0xef, 0xa6, 0x8c, 0xff,
+ 0xf4, 0xb4, 0x9d, 0xff, 0xf9, 0xc1, 0xad, 0xff,
+ 0xff, 0xdb, 0xc6, 0xff, 0xff, 0xdb, 0xc5, 0xff,
+ 0xff, 0xdb, 0xc6, 0xff, 0xd8, 0xb2, 0x94, 0xff,
+ 0xad, 0x82, 0x63, 0xff, 0x55, 0x3b, 0x26, 0xff,
+ 0x55, 0x3c, 0x27, 0xff, 0x55, 0x3b, 0x26, 0xff,
+ 0x58, 0x49, 0x3a, 0xff, 0x29, 0x20, 0x10, 0xff,
+ 0x87, 0x72, 0x63, 0xff, 0xb5, 0x9a, 0x8c, 0xff,
+ 0xad, 0x8e, 0x6b, 0xff, 0x7e, 0x64, 0x47, 0xff,
+ 0x7e, 0x64, 0x48, 0xff, 0x4f, 0x3a, 0x23, 0xff,
+ 0x2a, 0x22, 0x16, 0xff, 0x31, 0x28, 0x19, 0xff,
+ 0x29, 0x22, 0x16, 0xff, 0x21, 0x1b, 0x13, 0xff,
+ 0x5b, 0x4d, 0x42, 0xff, 0x18, 0x20, 0x18, 0xff,
+ 0x19, 0x21, 0x19, 0xff, 0x2e, 0x2f, 0x26, 0xff,
+ 0x3c, 0x3e, 0x3a, 0xff, 0x3c, 0x3e, 0x39, 0xff,
+ 0x3d, 0x3e, 0x3a, 0xff, 0x31, 0x34, 0x31, 0xff,
+ 0x31, 0x33, 0x2f, 0xff, 0x4a, 0x46, 0x3c, 0xff,
+ 0x4a, 0x46, 0x3d, 0xff, 0x62, 0x59, 0x4a, 0xff,
+ 0x68, 0x58, 0x45, 0xff, 0xa7, 0x7e, 0x68, 0xff,
+ 0xe7, 0xa6, 0x8c, 0xff, 0xe6, 0xa6, 0x8c, 0xff,
+ 0x91, 0x70, 0x6b, 0xff, 0x55, 0x4e, 0x4a, 0xff,
+ 0x55, 0x4e, 0x4a, 0xff, 0x55, 0x4e, 0x4a, 0xff,
+ 0x42, 0x41, 0x3a, 0xff, 0x41, 0x40, 0x39, 0xff,
+ 0x6b, 0x59, 0x4a, 0xff, 0xbd, 0x89, 0x6b, 0xff,
+ 0xde, 0x9a, 0x84, 0xff, 0xde, 0x99, 0x83, 0xff,
+ 0xde, 0x9a, 0x84, 0xff, 0xde, 0x9a, 0x83, 0xff,
+ 0xde, 0x96, 0x7b, 0xff, 0xe0, 0x9c, 0x86, 0xff,
+ 0xe4, 0xa3, 0x92, 0xff, 0xe6, 0xaa, 0x9c, 0xff,
+ 0xef, 0xba, 0xa5, 0xff, 0xee, 0xba, 0xa4, 0xff,
+ 0xe4, 0xa8, 0x8f, 0xff, 0xde, 0x9e, 0x83, 0xff,
+ 0xde, 0x9e, 0x84, 0xff, 0xee, 0xa8, 0x94, 0xff,
+ 0xf7, 0xae, 0x9d, 0xff, 0xf6, 0xae, 0x9c, 0xff,
+ 0xf4, 0xb4, 0x9c, 0xff, 0xee, 0xa6, 0x8b, 0xff,
+ 0xf4, 0xb4, 0x9d, 0xff, 0xff, 0xce, 0xbd, 0xff,
+ 0xff, 0xdb, 0xc6, 0xff, 0xff, 0xda, 0xc5, 0xff,
+ 0xff, 0xdb, 0xc6, 0xff, 0xd8, 0xb2, 0x94, 0xff,
+ 0x81, 0x5f, 0x45, 0xff, 0x55, 0x3b, 0x26, 0xff,
+ 0x55, 0x3c, 0x27, 0xff, 0x81, 0x5e, 0x44, 0xff,
+ 0x58, 0x49, 0x3a, 0xff, 0x29, 0x20, 0x10, 0xff,
+ 0x58, 0x49, 0x3a, 0xff, 0x86, 0x71, 0x62, 0xff,
+ 0xad, 0x8e, 0x6b, 0xff, 0xac, 0x8d, 0x6b, 0xff,
+ 0x50, 0x3a, 0x24, 0xff, 0x21, 0x10, 0x00, 0xff,
+ 0x31, 0x29, 0x19, 0xff, 0x20, 0x1b, 0x13, 0xff,
+ 0x21, 0x1b, 0x13, 0xff, 0x21, 0x1b, 0x13, 0xff,
+ 0x2f, 0x30, 0x27, 0xff, 0x18, 0x20, 0x18, 0xff,
+ 0x2f, 0x30, 0x27, 0xff, 0x44, 0x3e, 0x34, 0xff,
+ 0x3d, 0x3e, 0x3a, 0xff, 0x3c, 0x3e, 0x39, 0xff,
+ 0x48, 0x48, 0x42, 0xff, 0x31, 0x35, 0x31, 0xff,
+ 0x32, 0x34, 0x2f, 0xff, 0x4a, 0x46, 0x3c, 0xff,
+ 0x32, 0x34, 0x2f, 0xff, 0x31, 0x33, 0x2f, 0xff,
+ 0x29, 0x31, 0x21, 0xff, 0xa7, 0x7f, 0x68, 0xff,
+ 0xe7, 0xa6, 0x8c, 0xff, 0xe6, 0xa6, 0x8c, 0xff,
+ 0xce, 0x92, 0x8c, 0xff, 0x55, 0x4e, 0x4a, 0xff,
+ 0x55, 0x4f, 0x4a, 0xff, 0x55, 0x4e, 0x4a, 0xff,
+ 0x42, 0x41, 0x3a, 0xff, 0x42, 0x41, 0x39, 0xff,
+ 0x94, 0x72, 0x5b, 0xff, 0xbd, 0x8a, 0x6b, 0xff,
+ 0xde, 0x9a, 0x84, 0xff, 0xde, 0x9a, 0x83, 0xff,
+ 0xdf, 0x9a, 0x84, 0xff, 0xde, 0x9a, 0x84, 0xff,
+ 0xde, 0x96, 0x7c, 0xff, 0xe1, 0x9c, 0x86, 0xff,
+ 0xe1, 0x9d, 0x87, 0xff, 0xe6, 0xaa, 0x9c, 0xff,
+ 0xef, 0xba, 0xa5, 0xff, 0xe9, 0xb1, 0x99, 0xff,
+ 0xe4, 0xa8, 0x8f, 0xff, 0xde, 0x9e, 0x84, 0xff,
+ 0xde, 0x9e, 0x84, 0xff, 0xee, 0xa8, 0x94, 0xff,
+ 0xef, 0xa9, 0x94, 0xff, 0xe6, 0xa3, 0x8c, 0xff,
+ 0xef, 0xa6, 0x8c, 0xff, 0xee, 0xa6, 0x8c, 0xff,
+ 0xfa, 0xc1, 0xad, 0xff, 0xff, 0xce, 0xbd, 0xff,
+ 0xff, 0xdb, 0xc6, 0xff, 0xff, 0xda, 0xc5, 0xff,
+ 0xff, 0xdb, 0xc6, 0xff, 0xd9, 0xb2, 0x94, 0xff,
+ 0xad, 0x82, 0x63, 0xff, 0xad, 0x81, 0x62, 0xff,
+ 0x55, 0x3c, 0x27, 0xff, 0x55, 0x3b, 0x26, 0xff,
+ 0x29, 0x21, 0x11, 0xff, 0x58, 0x49, 0x39, 0xff,
+ 0x2a, 0x21, 0x11, 0xff, 0x58, 0x49, 0x39, 0xff,
+ 0x50, 0x3a, 0x24, 0xff, 0x7e, 0x64, 0x47, 0xff,
+ 0x50, 0x3a, 0x24, 0xff, 0x21, 0x10, 0x00, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x19, 0x14, 0x10, 0xff,
+ 0x45, 0x3e, 0x34, 0xff, 0x44, 0x3e, 0x34, 0xff,
+ 0x19, 0x20, 0x19, 0xff, 0x2e, 0x2f, 0x26, 0xff,
+ 0x3c, 0x3e, 0x3a, 0xff, 0x3c, 0x3e, 0x39, 0xff,
+ 0x3c, 0x3e, 0x3a, 0xff, 0x3c, 0x3e, 0x39, 0xff,
+ 0x4a, 0x46, 0x3c, 0xff, 0x4a, 0x46, 0x3c, 0xff,
+ 0x19, 0x20, 0x21, 0xff, 0x18, 0x20, 0x20, 0xff,
+ 0x29, 0x31, 0x21, 0xff, 0x68, 0x57, 0x44, 0xff,
+ 0xe6, 0xa6, 0x8c, 0xff, 0xe6, 0xa5, 0x8b, 0xff,
+ 0xce, 0x92, 0x8c, 0xff, 0x55, 0x4e, 0x4a, 0xff,
+ 0x19, 0x2d, 0x29, 0xff, 0x55, 0x4e, 0x4a, 0xff,
+ 0x42, 0x41, 0x3a, 0xff, 0x6b, 0x59, 0x4a, 0xff,
+ 0x94, 0x71, 0x5b, 0xff, 0xbd, 0x89, 0x6a, 0xff,
+ 0x8c, 0x6d, 0x5b, 0xff, 0x8b, 0x6d, 0x5a, 0xff,
+ 0xde, 0x9a, 0x84, 0xff, 0xde, 0x99, 0x83, 0xff,
+ 0xde, 0x96, 0x7c, 0xff, 0xe0, 0x9c, 0x86, 0xff,
+ 0xe1, 0x9d, 0x86, 0xff, 0xe3, 0xa3, 0x91, 0xff,
+ 0xef, 0xba, 0xa5, 0xff, 0xe9, 0xb0, 0x99, 0xff,
+ 0xe9, 0xb1, 0x9a, 0xff, 0xe3, 0xa7, 0x8e, 0xff,
+ 0xe6, 0xa3, 0x8c, 0xff, 0xee, 0xa8, 0x94, 0xff,
+ 0xe6, 0xa3, 0x8c, 0xff, 0xe6, 0xa3, 0x8b, 0xff,
+ 0xef, 0xa6, 0x8c, 0xff, 0xee, 0xa6, 0x8b, 0xff,
+ 0xfa, 0xc1, 0xad, 0xff, 0xff, 0xce, 0xbd, 0xff,
+ 0xff, 0xdb, 0xc6, 0xff, 0xff, 0xda, 0xc5, 0xff,
+ 0xd9, 0xb2, 0x94, 0xff, 0x8b, 0x61, 0x31, 0xff,
+ 0x81, 0x5f, 0x45, 0xff, 0x81, 0x5e, 0x44, 0xff,
+ 0x29, 0x18, 0x08, 0xff, 0x29, 0x18, 0x08, 0xff,
+ 0x29, 0x21, 0x11, 0xff, 0x57, 0x49, 0x39, 0xff,
+ 0x29, 0x20, 0x10, 0xff, 0x29, 0x20, 0x10, 0xff,
+ 0x50, 0x3a, 0x24, 0xff, 0x4f, 0x3a, 0x23, 0xff,
+ 0x21, 0x10, 0x00, 0xff, 0x20, 0x10, 0x00, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x21, 0x1b, 0x13, 0xff,
+ 0x19, 0x14, 0x10, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x3d, 0x38, 0x2f, 0xff, 0x3c, 0x37, 0x2f, 0xff,
+ 0x3d, 0x38, 0x2f, 0xff, 0x21, 0x24, 0x21, 0xff,
+ 0x2a, 0x29, 0x21, 0xff, 0x29, 0x28, 0x21, 0xff,
+ 0x29, 0x29, 0x21, 0xff, 0x3c, 0x3d, 0x34, 0xff,
+ 0x42, 0x40, 0x3a, 0xff, 0x52, 0x51, 0x4a, 0xff,
+ 0x42, 0x40, 0x3a, 0xff, 0x21, 0x1c, 0x19, 0xff,
+ 0x2a, 0x25, 0x19, 0xff, 0x60, 0x49, 0x3a, 0xff,
+ 0xce, 0x92, 0x7c, 0xff, 0xcd, 0x92, 0x7b, 0xff,
+ 0xbe, 0x8a, 0x74, 0xff, 0x7e, 0x62, 0x55, 0xff,
+ 0x3f, 0x3c, 0x37, 0xff, 0x3f, 0x3b, 0x37, 0xff,
+ 0x2a, 0x39, 0x3a, 0xff, 0x4a, 0x4d, 0x47, 0xff,
+ 0x6b, 0x61, 0x55, 0xff, 0x8c, 0x75, 0x63, 0xff,
+ 0x4b, 0x49, 0x42, 0xff, 0x79, 0x62, 0x55, 0xff,
+ 0xa8, 0x7c, 0x69, 0xff, 0xd6, 0x96, 0x7b, 0xff,
+ 0xe4, 0x9d, 0x84, 0xff, 0xe4, 0x9c, 0x84, 0xff,
+ 0xe4, 0x9d, 0x84, 0xff, 0xee, 0xaa, 0x94, 0xff,
+ 0xf7, 0xc7, 0xb5, 0xff, 0xf1, 0xb9, 0xa7, 0xff,
+ 0xec, 0xac, 0x9a, 0xff, 0xec, 0xab, 0x99, 0xff,
+ 0xec, 0xa9, 0x95, 0xff, 0xe6, 0xa2, 0x8c, 0xff,
+ 0xe7, 0xa2, 0x8c, 0xff, 0xe6, 0xa2, 0x8c, 0xff,
+ 0xef, 0xaa, 0x95, 0xff, 0xf4, 0xb7, 0xa2, 0xff,
+ 0xfa, 0xc5, 0xb0, 0xff, 0xff, 0xd2, 0xbd, 0xff,
+ 0xff, 0xc7, 0xa5, 0xff, 0xff, 0xc6, 0xa4, 0xff,
+ 0x7c, 0x5d, 0x42, 0xff, 0x39, 0x28, 0x10, 0xff,
+ 0x35, 0x24, 0x1c, 0xff, 0x26, 0x1a, 0x16, 0xff,
+ 0x27, 0x1a, 0x16, 0xff, 0x26, 0x19, 0x16, 0xff,
+ 0x2f, 0x25, 0x19, 0xff, 0x2f, 0x24, 0x19, 0xff,
+ 0x11, 0x0c, 0x09, 0xff, 0x2e, 0x24, 0x19, 0xff,
+ 0x19, 0x11, 0x11, 0xff, 0x19, 0x10, 0x10, 0xff,
+ 0x29, 0x1e, 0x16, 0xff, 0x31, 0x24, 0x19, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x19, 0x14, 0x10, 0xff,
+ 0x19, 0x13, 0x11, 0xff, 0x19, 0x13, 0x10, 0xff,
+ 0x3c, 0x37, 0x2f, 0xff, 0x3c, 0x37, 0x2e, 0xff,
+ 0x58, 0x4a, 0x3d, 0xff, 0x21, 0x24, 0x21, 0xff,
+ 0x29, 0x29, 0x21, 0xff, 0x3c, 0x3c, 0x34, 0xff,
+ 0x3d, 0x3d, 0x34, 0xff, 0x3c, 0x3c, 0x34, 0xff,
+ 0x52, 0x51, 0x4a, 0xff, 0x52, 0x51, 0x4a, 0xff,
+ 0x52, 0x51, 0x4a, 0xff, 0x42, 0x3f, 0x39, 0xff,
+ 0x29, 0x25, 0x19, 0xff, 0x60, 0x48, 0x39, 0xff,
+ 0x97, 0x6e, 0x5b, 0xff, 0x60, 0x49, 0x39, 0xff,
+ 0x7e, 0x63, 0x55, 0xff, 0x7e, 0x62, 0x55, 0xff,
+ 0x3f, 0x3c, 0x37, 0xff, 0x3f, 0x3b, 0x37, 0xff,
+ 0x4a, 0x4d, 0x47, 0xff, 0x4a, 0x4c, 0x47, 0xff,
+ 0x4a, 0x4d, 0x48, 0xff, 0x4a, 0x4d, 0x47, 0xff,
+ 0x4a, 0x49, 0x42, 0xff, 0xa7, 0x7c, 0x68, 0xff,
+ 0x79, 0x63, 0x55, 0xff, 0xd6, 0x95, 0x7b, 0xff,
+ 0xe4, 0x9d, 0x84, 0xff, 0xe9, 0xa3, 0x8b, 0xff,
+ 0xe9, 0xa3, 0x8c, 0xff, 0xe9, 0xa3, 0x8c, 0xff,
+ 0xf7, 0xc6, 0xb5, 0xff, 0xf6, 0xc6, 0xb5, 0xff,
+ 0xf2, 0xb9, 0xa7, 0xff, 0xec, 0xab, 0x99, 0xff,
+ 0xec, 0xa9, 0x94, 0xff, 0xeb, 0xa8, 0x94, 0xff,
+ 0xec, 0xa9, 0x94, 0xff, 0xec, 0xa8, 0x94, 0xff,
+ 0xef, 0xaa, 0x94, 0xff, 0xf4, 0xb7, 0xa1, 0xff,
+ 0xfa, 0xc5, 0xb0, 0xff, 0xf9, 0xc5, 0xaf, 0xff,
+ 0xff, 0xc6, 0xa5, 0xff, 0xbd, 0x91, 0x73, 0xff,
+ 0x3a, 0x29, 0x11, 0xff, 0x39, 0x28, 0x10, 0xff,
+ 0x26, 0x1a, 0x16, 0xff, 0x26, 0x19, 0x16, 0xff,
+ 0x27, 0x1a, 0x16, 0xff, 0x18, 0x10, 0x10, 0xff,
+ 0x2f, 0x25, 0x19, 0xff, 0x2e, 0x24, 0x18, 0xff,
+ 0x11, 0x0c, 0x08, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x19, 0x10, 0x11, 0xff, 0x18, 0x10, 0x10, 0xff,
+ 0x32, 0x25, 0x19, 0xff, 0x29, 0x1d, 0x16, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x18, 0x11, 0x10, 0xff,
+ 0x19, 0x13, 0x11, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x3d, 0x38, 0x2f, 0xff, 0x3c, 0x37, 0x2e, 0xff,
+ 0x58, 0x4b, 0x3d, 0xff, 0x58, 0x4a, 0x3c, 0xff,
+ 0x50, 0x51, 0x48, 0xff, 0x3c, 0x3c, 0x34, 0xff,
+ 0x50, 0x51, 0x48, 0xff, 0x4f, 0x51, 0x47, 0xff,
+ 0x53, 0x51, 0x4a, 0xff, 0x52, 0x51, 0x4a, 0xff,
+ 0x53, 0x51, 0x4a, 0xff, 0x31, 0x2e, 0x29, 0xff,
+ 0x29, 0x25, 0x19, 0xff, 0x29, 0x24, 0x18, 0xff,
+ 0x60, 0x49, 0x3a, 0xff, 0x60, 0x49, 0x39, 0xff,
+ 0x00, 0x15, 0x19, 0xff, 0x3f, 0x3b, 0x37, 0xff,
+ 0x3f, 0x3c, 0x37, 0xff, 0x3f, 0x3b, 0x37, 0xff,
+ 0x29, 0x39, 0x3a, 0xff, 0x4a, 0x4d, 0x47, 0xff,
+ 0x4a, 0x4d, 0x48, 0xff, 0x29, 0x39, 0x39, 0xff,
+ 0x4a, 0x49, 0x42, 0xff, 0x78, 0x62, 0x55, 0xff,
+ 0xd6, 0x96, 0x7c, 0xff, 0xd6, 0x96, 0x7b, 0xff,
+ 0xe4, 0x9d, 0x84, 0xff, 0xe9, 0xa3, 0x8c, 0xff,
+ 0xe4, 0x9d, 0x84, 0xff, 0xe9, 0xa3, 0x8c, 0xff,
+ 0xec, 0xac, 0x9a, 0xff, 0xf1, 0xb9, 0xa7, 0xff,
+ 0xf2, 0xb9, 0xa8, 0xff, 0xec, 0xab, 0x99, 0xff,
+ 0xec, 0xa9, 0x94, 0xff, 0xec, 0xa8, 0x94, 0xff,
+ 0xf2, 0xb0, 0x9d, 0xff, 0xec, 0xa9, 0x94, 0xff,
+ 0xf4, 0xb8, 0xa2, 0xff, 0xf9, 0xc5, 0xaf, 0xff,
+ 0xfa, 0xc5, 0xb0, 0xff, 0xf9, 0xc5, 0xaf, 0xff,
+ 0xff, 0xc7, 0xa5, 0xff, 0xbd, 0x91, 0x73, 0xff,
+ 0x3a, 0x29, 0x11, 0xff, 0x39, 0x28, 0x10, 0xff,
+ 0x27, 0x1a, 0x16, 0xff, 0x26, 0x19, 0x16, 0xff,
+ 0x27, 0x1a, 0x16, 0xff, 0x42, 0x2c, 0x21, 0xff,
+ 0x6b, 0x55, 0x3a, 0xff, 0x2e, 0x24, 0x18, 0xff,
+ 0x11, 0x0d, 0x09, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x19, 0x10, 0x11, 0xff, 0x21, 0x17, 0x13, 0xff,
+ 0x21, 0x17, 0x14, 0xff, 0x21, 0x17, 0x13, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x18, 0x11, 0x10, 0xff,
+ 0x19, 0x13, 0x11, 0xff, 0x19, 0x14, 0x10, 0xff,
+ 0x73, 0x5d, 0x4a, 0xff, 0x73, 0x5d, 0x4a, 0xff,
+ 0x58, 0x4a, 0x3c, 0xff, 0x73, 0x5d, 0x4a, 0xff,
+ 0x63, 0x65, 0x5b, 0xff, 0x4f, 0x51, 0x47, 0xff,
+ 0x50, 0x51, 0x47, 0xff, 0x3c, 0x3c, 0x34, 0xff,
+ 0x52, 0x51, 0x4a, 0xff, 0x41, 0x3f, 0x39, 0xff,
+ 0x52, 0x51, 0x4a, 0xff, 0x20, 0x1c, 0x18, 0xff,
+ 0x29, 0x25, 0x19, 0xff, 0x29, 0x24, 0x18, 0xff,
+ 0x97, 0x6d, 0x5b, 0xff, 0xcd, 0x91, 0x7b, 0xff,
+ 0x3f, 0x3c, 0x37, 0xff, 0x00, 0x14, 0x18, 0xff,
+ 0x00, 0x14, 0x19, 0xff, 0x3f, 0x3b, 0x36, 0xff,
+ 0x29, 0x39, 0x3a, 0xff, 0x29, 0x38, 0x39, 0xff,
+ 0x4a, 0x4d, 0x47, 0xff, 0x4a, 0x4c, 0x47, 0xff,
+ 0x4a, 0x49, 0x42, 0xff, 0x78, 0x62, 0x55, 0xff,
+ 0xa7, 0x7c, 0x68, 0xff, 0xa7, 0x7c, 0x68, 0xff,
+ 0xde, 0x96, 0x7c, 0xff, 0xde, 0x95, 0x7b, 0xff,
+ 0xe9, 0xa3, 0x8c, 0xff, 0xe9, 0xa3, 0x8b, 0xff,
+ 0xe6, 0x9e, 0x8c, 0xff, 0xf1, 0xb8, 0xa7, 0xff,
+ 0xf7, 0xc6, 0xb5, 0xff, 0xf1, 0xb8, 0xa7, 0xff,
+ 0xec, 0xa9, 0x94, 0xff, 0xf1, 0xaf, 0x9c, 0xff,
+ 0xf7, 0xb6, 0xa5, 0xff, 0xf6, 0xb6, 0xa4, 0xff,
+ 0xfa, 0xc5, 0xb0, 0xff, 0xf9, 0xc5, 0xaf, 0xff,
+ 0xfa, 0xc5, 0xb0, 0xff, 0xf9, 0xc5, 0xaf, 0xff,
+ 0xff, 0xc6, 0xa5, 0xff, 0xbd, 0x91, 0x73, 0xff,
+ 0x3a, 0x29, 0x10, 0xff, 0x39, 0x28, 0x10, 0xff,
+ 0x19, 0x10, 0x11, 0xff, 0x26, 0x19, 0x16, 0xff,
+ 0x19, 0x10, 0x10, 0xff, 0x41, 0x2c, 0x20, 0xff,
+ 0x2f, 0x25, 0x19, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x10, 0x0c, 0x08, 0xff, 0x2e, 0x24, 0x18, 0xff,
+ 0x21, 0x17, 0x13, 0xff, 0x18, 0x10, 0x10, 0xff,
+ 0x19, 0x10, 0x10, 0xff, 0x20, 0x16, 0x13, 0xff,
+ 0x19, 0x10, 0x11, 0xff, 0x18, 0x11, 0x10, 0xff,
+ 0x19, 0x13, 0x10, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x7c, 0x63, 0x4d, 0xff, 0xa4, 0x7d, 0x63, 0xff,
+ 0x53, 0x48, 0x37, 0xff, 0xa4, 0x7d, 0x63, 0xff,
+ 0x8c, 0x7e, 0x6b, 0xff, 0x3f, 0x45, 0x3f, 0xff,
+ 0x66, 0x61, 0x55, 0xff, 0x3f, 0x45, 0x3f, 0xff,
+ 0x2a, 0x29, 0x2a, 0xff, 0x37, 0x37, 0x34, 0xff,
+ 0x45, 0x47, 0x3f, 0xff, 0x37, 0x37, 0x34, 0xff,
+ 0x2a, 0x1d, 0x19, 0xff, 0x29, 0x1c, 0x19, 0xff,
+ 0x9d, 0x6e, 0x5b, 0xff, 0x9c, 0x6d, 0x5a, 0xff,
+ 0x24, 0x20, 0x1c, 0xff, 0x24, 0x1f, 0x1b, 0xff,
+ 0x37, 0x2e, 0x27, 0xff, 0x4a, 0x3d, 0x31, 0xff,
+ 0x32, 0x3c, 0x37, 0xff, 0x31, 0x3b, 0x37, 0xff,
+ 0x3a, 0x49, 0x42, 0xff, 0x39, 0x49, 0x42, 0xff,
+ 0x3d, 0x49, 0x48, 0xff, 0x3c, 0x49, 0x47, 0xff,
+ 0x4a, 0x55, 0x53, 0xff, 0x4a, 0x55, 0x52, 0xff,
+ 0x6e, 0x62, 0x50, 0xff, 0x6e, 0x61, 0x4f, 0xff,
+ 0xe7, 0xaa, 0x8c, 0xff, 0xe6, 0xaa, 0x8c, 0xff,
+ 0xe7, 0xa6, 0x8c, 0xff, 0xf7, 0xba, 0xa4, 0xff,
+ 0xf7, 0xbb, 0xa5, 0xff, 0xec, 0xad, 0x94, 0xff,
+ 0xef, 0xaf, 0x95, 0xff, 0xef, 0xae, 0x94, 0xff,
+ 0xf4, 0xb6, 0x9d, 0xff, 0xf9, 0xbe, 0xa4, 0xff,
+ 0xff, 0xc4, 0xb0, 0xff, 0xff, 0xc4, 0xaf, 0xff,
+ 0xff, 0xc4, 0xb0, 0xff, 0xff, 0xba, 0xa4, 0xff,
+ 0xb8, 0xa1, 0x81, 0xff, 0x70, 0x5a, 0x45, 0xff,
+ 0x29, 0x15, 0x09, 0xff, 0x29, 0x14, 0x08, 0xff,
+ 0x21, 0x15, 0x11, 0xff, 0x21, 0x14, 0x10, 0xff,
+ 0x21, 0x15, 0x11, 0xff, 0x21, 0x14, 0x10, 0xff,
+ 0x19, 0x11, 0x11, 0xff, 0x31, 0x22, 0x1b, 0xff,
+ 0x32, 0x22, 0x1c, 0xff, 0x31, 0x22, 0x1b, 0xff,
+ 0x24, 0x1b, 0x16, 0xff, 0x24, 0x1b, 0x16, 0xff,
+ 0x24, 0x1b, 0x16, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x19, 0x14, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x19, 0x14, 0x10, 0xff,
+ 0x52, 0x48, 0x37, 0xff, 0x7b, 0x62, 0x4c, 0xff,
+ 0x52, 0x48, 0x37, 0xff, 0x7b, 0x62, 0x4c, 0xff,
+ 0x3f, 0x45, 0x3f, 0xff, 0x65, 0x61, 0x55, 0xff,
+ 0x3f, 0x45, 0x3f, 0xff, 0x18, 0x28, 0x29, 0xff,
+ 0x37, 0x37, 0x34, 0xff, 0x36, 0x37, 0x34, 0xff,
+ 0x52, 0x55, 0x4a, 0xff, 0x37, 0x37, 0x34, 0xff,
+ 0x29, 0x1c, 0x19, 0xff, 0x29, 0x1c, 0x18, 0xff,
+ 0x29, 0x1d, 0x19, 0xff, 0x76, 0x52, 0x44, 0xff,
+ 0x24, 0x1f, 0x1c, 0xff, 0x23, 0x1f, 0x1b, 0xff,
+ 0x24, 0x1f, 0x1c, 0xff, 0x37, 0x2e, 0x26, 0xff,
+ 0x31, 0x3b, 0x37, 0xff, 0x31, 0x3b, 0x36, 0xff,
+ 0x3a, 0x49, 0x42, 0xff, 0x31, 0x3b, 0x37, 0xff,
+ 0x3c, 0x49, 0x47, 0xff, 0x2e, 0x3c, 0x3c, 0xff,
+ 0x21, 0x31, 0x32, 0xff, 0x2e, 0x3c, 0x3c, 0xff,
+ 0x31, 0x3d, 0x31, 0xff, 0x6d, 0x61, 0x4f, 0xff,
+ 0xaa, 0x86, 0x6e, 0xff, 0xe6, 0xaa, 0x8c, 0xff,
+ 0xe6, 0xa6, 0x8c, 0xff, 0xeb, 0xac, 0x94, 0xff,
+ 0xec, 0xad, 0x94, 0xff, 0xec, 0xac, 0x94, 0xff,
+ 0xef, 0xae, 0x94, 0xff, 0xee, 0xae, 0x94, 0xff,
+ 0xf4, 0xb6, 0x9d, 0xff, 0xff, 0xc6, 0xac, 0xff,
+ 0xff, 0xba, 0xa5, 0xff, 0xff, 0xba, 0xa4, 0xff,
+ 0xff, 0xba, 0xa5, 0xff, 0xff, 0xc3, 0xaf, 0xff,
+ 0xb8, 0xa1, 0x81, 0xff, 0x70, 0x5a, 0x44, 0xff,
+ 0x29, 0x14, 0x08, 0xff, 0x29, 0x14, 0x08, 0xff,
+ 0x21, 0x14, 0x11, 0xff, 0x4c, 0x34, 0x29, 0xff,
+ 0x4d, 0x35, 0x29, 0xff, 0x21, 0x14, 0x10, 0xff,
+ 0x19, 0x10, 0x11, 0xff, 0x4a, 0x33, 0x26, 0xff,
+ 0x32, 0x22, 0x1c, 0xff, 0x31, 0x21, 0x1b, 0xff,
+ 0x37, 0x26, 0x1c, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x24, 0x1b, 0x16, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x66, 0x45, 0x32, 0xff, 0x8c, 0x5d, 0x42, 0xff,
+ 0x29, 0x2d, 0x21, 0xff, 0x7b, 0x62, 0x4d, 0xff,
+ 0x53, 0x48, 0x37, 0xff, 0x29, 0x2c, 0x21, 0xff,
+ 0x3f, 0x45, 0x3f, 0xff, 0x3f, 0x45, 0x3f, 0xff,
+ 0x3f, 0x45, 0x3f, 0xff, 0x19, 0x28, 0x29, 0xff,
+ 0x29, 0x29, 0x29, 0xff, 0x44, 0x46, 0x3f, 0xff,
+ 0x45, 0x47, 0x3f, 0xff, 0x37, 0x37, 0x34, 0xff,
+ 0x29, 0x1d, 0x19, 0xff, 0x9c, 0x6d, 0x5a, 0xff,
+ 0x76, 0x53, 0x45, 0xff, 0x29, 0x1c, 0x19, 0xff,
+ 0x24, 0x1f, 0x1c, 0xff, 0x23, 0x1f, 0x1b, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x24, 0x1f, 0x1b, 0xff,
+ 0x21, 0x21, 0x21, 0xff, 0x29, 0x2e, 0x2c, 0xff,
+ 0x32, 0x3c, 0x37, 0xff, 0x31, 0x3b, 0x37, 0xff,
+ 0x2f, 0x3d, 0x3d, 0xff, 0x21, 0x30, 0x31, 0xff,
+ 0x21, 0x31, 0x32, 0xff, 0x21, 0x30, 0x31, 0xff,
+ 0x32, 0x3d, 0x32, 0xff, 0x31, 0x3c, 0x31, 0xff,
+ 0xe7, 0xaa, 0x8c, 0xff, 0xe6, 0xaa, 0x8c, 0xff,
+ 0xe7, 0xa6, 0x8c, 0xff, 0xe6, 0xa6, 0x8c, 0xff,
+ 0xec, 0xad, 0x94, 0xff, 0xec, 0xad, 0x94, 0xff,
+ 0xef, 0xae, 0x94, 0xff, 0xf9, 0xbe, 0xa4, 0xff,
+ 0xff, 0xc7, 0xad, 0xff, 0xf9, 0xbe, 0xa4, 0xff,
+ 0xff, 0xba, 0xa5, 0xff, 0xff, 0xba, 0xa4, 0xff,
+ 0xff, 0xbb, 0xa5, 0xff, 0xff, 0xd6, 0xc5, 0xff,
+ 0xb8, 0xa1, 0x81, 0xff, 0x70, 0x5a, 0x44, 0xff,
+ 0x2a, 0x15, 0x09, 0xff, 0x70, 0x5a, 0x44, 0xff,
+ 0x79, 0x55, 0x42, 0xff, 0xa4, 0x75, 0x5a, 0xff,
+ 0x79, 0x55, 0x42, 0xff, 0x21, 0x14, 0x10, 0xff,
+ 0x32, 0x22, 0x1c, 0xff, 0x62, 0x45, 0x31, 0xff,
+ 0x63, 0x45, 0x32, 0xff, 0x31, 0x22, 0x1b, 0xff,
+ 0x4a, 0x31, 0x21, 0xff, 0x4a, 0x30, 0x21, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x3f, 0x2d, 0x21, 0xff, 0x8c, 0x5d, 0x42, 0xff,
+ 0x66, 0x45, 0x32, 0xff, 0x65, 0x45, 0x31, 0xff,
+ 0x29, 0x2d, 0x21, 0xff, 0x52, 0x47, 0x36, 0xff,
+ 0x52, 0x48, 0x37, 0xff, 0x29, 0x2c, 0x20, 0xff,
+ 0x3f, 0x45, 0x3f, 0xff, 0x3f, 0x44, 0x3f, 0xff,
+ 0x3f, 0x45, 0x3f, 0xff, 0x3f, 0x44, 0x3f, 0xff,
+ 0x45, 0x46, 0x3f, 0xff, 0x44, 0x46, 0x3f, 0xff,
+ 0x37, 0x37, 0x34, 0xff, 0x44, 0x46, 0x3f, 0xff,
+ 0x76, 0x52, 0x45, 0xff, 0x9c, 0x6d, 0x5a, 0xff,
+ 0x76, 0x52, 0x45, 0xff, 0x4f, 0x37, 0x2e, 0xff,
+ 0x4a, 0x3d, 0x32, 0xff, 0x23, 0x1f, 0x1b, 0xff,
+ 0x10, 0x10, 0x10, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x21, 0x21, 0x21, 0xff, 0x29, 0x2e, 0x2c, 0xff,
+ 0x3a, 0x49, 0x42, 0xff, 0x39, 0x48, 0x41, 0xff,
+ 0x2f, 0x3d, 0x3c, 0xff, 0x21, 0x30, 0x31, 0xff,
+ 0x21, 0x31, 0x31, 0xff, 0x20, 0x30, 0x31, 0xff,
+ 0x32, 0x3d, 0x32, 0xff, 0x31, 0x3c, 0x31, 0xff,
+ 0xaa, 0x86, 0x6e, 0xff, 0xe6, 0xaa, 0x8b, 0xff,
+ 0xec, 0xad, 0x94, 0xff, 0xeb, 0xac, 0x94, 0xff,
+ 0xe6, 0xa6, 0x8c, 0xff, 0xf1, 0xb3, 0x9c, 0xff,
+ 0xf4, 0xb6, 0x9c, 0xff, 0xf9, 0xbe, 0xa4, 0xff,
+ 0xfa, 0xbe, 0xa5, 0xff, 0xf4, 0xb6, 0x9c, 0xff,
+ 0xff, 0xba, 0xa5, 0xff, 0xff, 0xc3, 0xaf, 0xff,
+ 0xff, 0xcd, 0xba, 0xff, 0xff, 0xd6, 0xc5, 0xff,
+ 0xff, 0xe7, 0xbd, 0xff, 0xb7, 0xa0, 0x81, 0xff,
+ 0x70, 0x5a, 0x45, 0xff, 0x70, 0x5a, 0x44, 0xff,
+ 0xa5, 0x76, 0x5b, 0xff, 0x78, 0x55, 0x41, 0xff,
+ 0x21, 0x14, 0x10, 0xff, 0x20, 0x14, 0x10, 0xff,
+ 0x32, 0x22, 0x1c, 0xff, 0x62, 0x44, 0x31, 0xff,
+ 0x63, 0x45, 0x31, 0xff, 0x31, 0x21, 0x1b, 0xff,
+ 0x4a, 0x31, 0x21, 0xff, 0x23, 0x1b, 0x16, 0xff,
+ 0x10, 0x10, 0x10, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x3f, 0x2d, 0x21, 0xff, 0x3f, 0x2c, 0x21, 0xff,
+ 0x19, 0x14, 0x10, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x27, 0x2a, 0x21, 0xff, 0x31, 0x39, 0x29, 0xff,
+ 0x27, 0x2a, 0x21, 0xff, 0x1b, 0x1b, 0x19, 0xff,
+ 0x24, 0x21, 0x1f, 0xff, 0x3a, 0x41, 0x3a, 0xff,
+ 0x3a, 0x41, 0x3a, 0xff, 0x39, 0x41, 0x39, 0xff,
+ 0x3d, 0x48, 0x42, 0xff, 0x3c, 0x47, 0x42, 0xff,
+ 0x3d, 0x48, 0x42, 0xff, 0x3c, 0x47, 0x42, 0xff,
+ 0x58, 0x4f, 0x45, 0xff, 0x6b, 0x5d, 0x52, 0xff,
+ 0x32, 0x31, 0x29, 0xff, 0x31, 0x30, 0x29, 0xff,
+ 0x4b, 0x3d, 0x32, 0xff, 0x31, 0x2b, 0x24, 0xff,
+ 0x00, 0x08, 0x09, 0xff, 0x19, 0x19, 0x16, 0xff,
+ 0x21, 0x25, 0x21, 0xff, 0x2f, 0x2f, 0x2c, 0xff,
+ 0x3d, 0x3a, 0x37, 0xff, 0x3c, 0x3a, 0x37, 0xff,
+ 0x24, 0x31, 0x2f, 0xff, 0x24, 0x31, 0x2f, 0xff,
+ 0x19, 0x19, 0x19, 0xff, 0x1e, 0x24, 0x23, 0xff,
+ 0x3a, 0x41, 0x32, 0xff, 0x3a, 0x41, 0x31, 0xff,
+ 0xf7, 0xb6, 0x9d, 0xff, 0xf7, 0xb6, 0x9c, 0xff,
+ 0xf2, 0xb0, 0x9a, 0xff, 0xef, 0xaa, 0x94, 0xff,
+ 0xef, 0xaa, 0x94, 0xff, 0xf1, 0xaf, 0x99, 0xff,
+ 0xf7, 0xaf, 0x95, 0xff, 0xf9, 0xb3, 0x9a, 0xff,
+ 0xfd, 0xb9, 0x9f, 0xff, 0xfc, 0xb9, 0x9f, 0xff,
+ 0xff, 0xbb, 0xa5, 0xff, 0xff, 0xc4, 0xad, 0xff,
+ 0xff, 0xc4, 0xad, 0xff, 0xff, 0xd6, 0xbd, 0xff,
+ 0xff, 0xd7, 0xad, 0xff, 0xba, 0x9a, 0x79, 0xff,
+ 0x32, 0x21, 0x11, 0xff, 0x31, 0x20, 0x10, 0xff,
+ 0x21, 0x19, 0x11, 0xff, 0x84, 0x5c, 0x42, 0xff,
+ 0x53, 0x3a, 0x29, 0xff, 0x21, 0x18, 0x10, 0xff,
+ 0x3a, 0x29, 0x21, 0xff, 0x2f, 0x22, 0x1b, 0xff,
+ 0x24, 0x1b, 0x16, 0xff, 0x2e, 0x22, 0x1b, 0xff,
+ 0x2a, 0x22, 0x16, 0xff, 0x19, 0x14, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x19, 0x14, 0x10, 0xff,
+ 0x21, 0x19, 0x11, 0xff, 0x21, 0x18, 0x10, 0xff,
+ 0x21, 0x19, 0x11, 0xff, 0x21, 0x18, 0x10, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x1b, 0x1b, 0x18, 0xff,
+ 0x1c, 0x1b, 0x19, 0xff, 0x1b, 0x1b, 0x18, 0xff,
+ 0x19, 0x10, 0x11, 0xff, 0x18, 0x10, 0x10, 0xff,
+ 0x24, 0x21, 0x1e, 0xff, 0x2e, 0x30, 0x2c, 0xff,
+ 0x3c, 0x48, 0x42, 0xff, 0x4a, 0x59, 0x52, 0xff,
+ 0x4a, 0x59, 0x52, 0xff, 0x2e, 0x36, 0x31, 0xff,
+ 0x31, 0x31, 0x29, 0xff, 0x6b, 0x5d, 0x52, 0xff,
+ 0x6b, 0x5d, 0x52, 0xff, 0x31, 0x30, 0x29, 0xff,
+ 0x4a, 0x3d, 0x31, 0xff, 0x31, 0x2b, 0x23, 0xff,
+ 0x00, 0x08, 0x08, 0xff, 0x18, 0x19, 0x16, 0xff,
+ 0x21, 0x25, 0x21, 0xff, 0x2e, 0x2f, 0x2b, 0xff,
+ 0x3d, 0x3a, 0x37, 0xff, 0x2e, 0x2f, 0x2c, 0xff,
+ 0x1e, 0x25, 0x24, 0xff, 0x1e, 0x24, 0x23, 0xff,
+ 0x1e, 0x25, 0x24, 0xff, 0x23, 0x30, 0x2e, 0xff,
+ 0x3a, 0x41, 0x31, 0xff, 0x78, 0x67, 0x55, 0xff,
+ 0xf7, 0xb6, 0x9d, 0xff, 0xf6, 0xb6, 0x9c, 0xff,
+ 0xf1, 0xaf, 0x9a, 0xff, 0xee, 0xaa, 0x94, 0xff,
+ 0xf2, 0xb0, 0x9a, 0xff, 0xf1, 0xaf, 0x99, 0xff,
+ 0xf7, 0xae, 0x94, 0xff, 0xfc, 0xb8, 0x9f, 0xff,
+ 0xfc, 0xb9, 0x9f, 0xff, 0xfc, 0xb9, 0x9f, 0xff,
+ 0xff, 0xba, 0xa5, 0xff, 0xff, 0xba, 0xa4, 0xff,
+ 0xff, 0xc4, 0xad, 0xff, 0xff, 0xc3, 0xac, 0xff,
+ 0xff, 0xd7, 0xad, 0xff, 0x75, 0x5d, 0x44, 0xff,
+ 0x32, 0x21, 0x11, 0xff, 0x31, 0x20, 0x10, 0xff,
+ 0x84, 0x5c, 0x42, 0xff, 0xb5, 0x7d, 0x5a, 0xff,
+ 0x21, 0x19, 0x11, 0xff, 0x21, 0x18, 0x10, 0xff,
+ 0x3a, 0x29, 0x21, 0xff, 0x2e, 0x21, 0x1b, 0xff,
+ 0x24, 0x1b, 0x16, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x21, 0x1b, 0x13, 0xff,
+ 0x3c, 0x2f, 0x26, 0xff, 0x20, 0x18, 0x10, 0xff,
+ 0x21, 0x19, 0x11, 0xff, 0x21, 0x18, 0x10, 0xff,
+ 0x1c, 0x1b, 0x19, 0xff, 0x1b, 0x1b, 0x18, 0xff,
+ 0x11, 0x0d, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x19, 0x10, 0x11, 0xff, 0x18, 0x10, 0x10, 0xff,
+ 0x2f, 0x31, 0x2c, 0xff, 0x2f, 0x30, 0x2c, 0xff,
+ 0x3d, 0x48, 0x42, 0xff, 0x3c, 0x47, 0x42, 0xff,
+ 0x3d, 0x48, 0x42, 0xff, 0x3c, 0x47, 0x42, 0xff,
+ 0x45, 0x40, 0x37, 0xff, 0x58, 0x4e, 0x44, 0xff,
+ 0x6b, 0x5e, 0x53, 0xff, 0x58, 0x4e, 0x44, 0xff,
+ 0x4a, 0x3d, 0x32, 0xff, 0x18, 0x19, 0x16, 0xff,
+ 0x00, 0x09, 0x09, 0xff, 0x19, 0x1a, 0x16, 0xff,
+ 0x21, 0x25, 0x21, 0xff, 0x3c, 0x3a, 0x37, 0xff,
+ 0x2f, 0x30, 0x2c, 0xff, 0x21, 0x24, 0x21, 0xff,
+ 0x1e, 0x25, 0x24, 0xff, 0x18, 0x18, 0x18, 0xff,
+ 0x1f, 0x25, 0x24, 0xff, 0x24, 0x30, 0x2f, 0xff,
+ 0x3a, 0x41, 0x32, 0xff, 0x78, 0x68, 0x55, 0xff,
+ 0xb8, 0x8f, 0x79, 0xff, 0xf7, 0xb6, 0x9c, 0xff,
+ 0xf2, 0xb0, 0x9a, 0xff, 0xf1, 0xaf, 0x99, 0xff,
+ 0xf4, 0xb5, 0x9f, 0xff, 0xf7, 0xba, 0xa4, 0xff,
+ 0xfd, 0xb9, 0x9f, 0xff, 0xfc, 0xb9, 0x9f, 0xff,
+ 0xfd, 0xb9, 0x9f, 0xff, 0xff, 0xbe, 0xa4, 0xff,
+ 0xff, 0xba, 0xa5, 0xff, 0xff, 0xba, 0xa4, 0xff,
+ 0xff, 0xc4, 0xad, 0xff, 0xff, 0xcd, 0xb5, 0xff,
+ 0xbb, 0x9a, 0x79, 0xff, 0x31, 0x20, 0x10, 0xff,
+ 0x32, 0x21, 0x11, 0xff, 0x76, 0x5d, 0x44, 0xff,
+ 0x84, 0x5c, 0x42, 0xff, 0x21, 0x18, 0x10, 0xff,
+ 0x21, 0x19, 0x11, 0xff, 0x21, 0x18, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x19, 0x14, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x31, 0x28, 0x19, 0xff,
+ 0x21, 0x19, 0x11, 0xff, 0x21, 0x18, 0x10, 0xff,
+ 0x21, 0x19, 0x11, 0xff, 0x73, 0x5d, 0x52, 0xff,
+ 0x1c, 0x1b, 0x19, 0xff, 0x1b, 0x1b, 0x18, 0xff,
+ 0x1b, 0x1b, 0x19, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x19, 0x10, 0x11, 0xff, 0x18, 0x10, 0x10, 0xff,
+ 0x24, 0x20, 0x1e, 0xff, 0x23, 0x20, 0x1e, 0xff,
+ 0x2f, 0x36, 0x32, 0xff, 0x21, 0x24, 0x21, 0xff,
+ 0x21, 0x24, 0x21, 0xff, 0x2e, 0x35, 0x31, 0xff,
+ 0x32, 0x31, 0x29, 0xff, 0x31, 0x30, 0x29, 0xff,
+ 0x6b, 0x5d, 0x52, 0xff, 0x57, 0x4e, 0x44, 0xff,
+ 0x32, 0x2b, 0x24, 0xff, 0x31, 0x2b, 0x23, 0xff,
+ 0x19, 0x1a, 0x16, 0xff, 0x18, 0x19, 0x15, 0xff,
+ 0x3c, 0x3a, 0x37, 0xff, 0x3c, 0x3a, 0x36, 0xff,
+ 0x21, 0x24, 0x21, 0xff, 0x4a, 0x44, 0x41, 0xff,
+ 0x19, 0x18, 0x19, 0xff, 0x18, 0x18, 0x18, 0xff,
+ 0x1e, 0x24, 0x24, 0xff, 0x29, 0x3c, 0x39, 0xff,
+ 0x3a, 0x41, 0x32, 0xff, 0x39, 0x40, 0x31, 0xff,
+ 0x79, 0x68, 0x55, 0xff, 0xf6, 0xb6, 0x9c, 0xff,
+ 0xf4, 0xb5, 0x9f, 0xff, 0xf4, 0xb4, 0x9f, 0xff,
+ 0xf7, 0xba, 0xa5, 0xff, 0xf6, 0xba, 0xa4, 0xff,
+ 0xff, 0xbe, 0xa5, 0xff, 0xff, 0xbe, 0xa4, 0xff,
+ 0xfc, 0xb9, 0x9f, 0xff, 0xfc, 0xb8, 0x9f, 0xff,
+ 0xff, 0xba, 0xa5, 0xff, 0xff, 0xc3, 0xac, 0xff,
+ 0xff, 0xc4, 0xad, 0xff, 0xff, 0xc3, 0xac, 0xff,
+ 0xbb, 0x9a, 0x79, 0xff, 0x31, 0x20, 0x10, 0xff,
+ 0x31, 0x20, 0x10, 0xff, 0x31, 0x20, 0x10, 0xff,
+ 0x52, 0x3a, 0x29, 0xff, 0x21, 0x18, 0x10, 0xff,
+ 0x21, 0x18, 0x10, 0xff, 0x20, 0x18, 0x10, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x23, 0x1b, 0x16, 0xff,
+ 0x2f, 0x22, 0x1b, 0xff, 0x23, 0x1b, 0x15, 0xff,
+ 0x21, 0x1b, 0x13, 0xff, 0x31, 0x28, 0x18, 0xff,
+ 0x21, 0x1b, 0x13, 0xff, 0x20, 0x1b, 0x13, 0xff,
+ 0x21, 0x18, 0x11, 0xff, 0x3c, 0x2f, 0x26, 0xff,
+ 0x3c, 0x2f, 0x26, 0xff, 0x73, 0x5d, 0x52, 0xff,
+ 0x1c, 0x21, 0x1c, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x1c, 0x21, 0x1c, 0xff, 0x1b, 0x20, 0x1b, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x21, 0x1f, 0x1b, 0xff,
+ 0x42, 0x3d, 0x32, 0xff, 0x31, 0x2e, 0x26, 0xff,
+ 0x3d, 0x2c, 0x27, 0xff, 0x21, 0x18, 0x19, 0xff,
+ 0x21, 0x19, 0x19, 0xff, 0x3c, 0x2b, 0x26, 0xff,
+ 0x2c, 0x34, 0x2f, 0xff, 0x3f, 0x42, 0x3c, 0xff,
+ 0x53, 0x51, 0x4a, 0xff, 0x3f, 0x42, 0x3c, 0xff,
+ 0x2f, 0x3a, 0x35, 0xff, 0x24, 0x2b, 0x26, 0xff,
+ 0x24, 0x2c, 0x27, 0xff, 0x19, 0x1c, 0x19, 0xff,
+ 0x5b, 0x49, 0x3a, 0xff, 0x42, 0x35, 0x29, 0xff,
+ 0x5b, 0x49, 0x3a, 0xff, 0x5a, 0x49, 0x39, 0xff,
+ 0x4b, 0x43, 0x3d, 0xff, 0x29, 0x24, 0x21, 0xff,
+ 0x29, 0x25, 0x21, 0xff, 0x39, 0x33, 0x2e, 0xff,
+ 0x50, 0x41, 0x37, 0xff, 0x4f, 0x41, 0x37, 0xff,
+ 0x8f, 0x72, 0x5e, 0xff, 0xcd, 0xa2, 0x83, 0xff,
+ 0xe7, 0xb8, 0xa0, 0xff, 0xe6, 0xb7, 0x9f, 0xff,
+ 0xe7, 0xb8, 0x9f, 0xff, 0xe6, 0xb7, 0x9f, 0xff,
+ 0xef, 0xc5, 0xad, 0xff, 0xef, 0xc5, 0xad, 0xff,
+ 0xef, 0xc5, 0xad, 0xff, 0xee, 0xc5, 0xad, 0xff,
+ 0xec, 0xc0, 0xa5, 0xff, 0xec, 0xc0, 0xa4, 0xff,
+ 0xff, 0xd7, 0xbe, 0xff, 0xc5, 0x92, 0x73, 0xff,
+ 0x4b, 0x29, 0x19, 0xff, 0x4a, 0x28, 0x19, 0xff,
+ 0x4a, 0x29, 0x19, 0xff, 0x4a, 0x28, 0x19, 0xff,
+ 0x4d, 0x38, 0x27, 0xff, 0x29, 0x1c, 0x10, 0xff,
+ 0x29, 0x1d, 0x11, 0xff, 0x29, 0x1c, 0x10, 0xff,
+ 0x21, 0x19, 0x11, 0xff, 0x31, 0x24, 0x19, 0xff,
+ 0x42, 0x31, 0x21, 0xff, 0x21, 0x18, 0x10, 0xff,
+ 0x2f, 0x21, 0x19, 0xff, 0x5a, 0x41, 0x29, 0xff,
+ 0x5b, 0x41, 0x29, 0xff, 0x2e, 0x20, 0x19, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x21, 0x1b, 0x16, 0xff,
+ 0x32, 0x26, 0x1c, 0xff, 0x21, 0x1b, 0x16, 0xff,
+ 0x1c, 0x20, 0x1c, 0xff, 0x1b, 0x20, 0x1b, 0xff,
+ 0x27, 0x35, 0x2f, 0xff, 0x1b, 0x20, 0x1b, 0xff,
+ 0x21, 0x1f, 0x1c, 0xff, 0x31, 0x2d, 0x26, 0xff,
+ 0x32, 0x2e, 0x27, 0xff, 0x42, 0x3c, 0x31, 0xff,
+ 0x3c, 0x2b, 0x26, 0xff, 0x20, 0x18, 0x18, 0xff,
+ 0x21, 0x19, 0x19, 0xff, 0x21, 0x18, 0x18, 0xff,
+ 0x2c, 0x33, 0x2f, 0xff, 0x3f, 0x42, 0x3c, 0xff,
+ 0x3f, 0x42, 0x3d, 0xff, 0x2c, 0x33, 0x2e, 0xff,
+ 0x3a, 0x49, 0x42, 0xff, 0x39, 0x48, 0x41, 0xff,
+ 0x2f, 0x3a, 0x34, 0xff, 0x23, 0x2b, 0x26, 0xff,
+ 0x42, 0x35, 0x29, 0xff, 0x5a, 0x48, 0x39, 0xff,
+ 0x5b, 0x49, 0x3a, 0xff, 0x42, 0x34, 0x29, 0xff,
+ 0x4a, 0x42, 0x3c, 0xff, 0x5a, 0x51, 0x4a, 0xff,
+ 0x29, 0x25, 0x21, 0xff, 0x39, 0x33, 0x2e, 0xff,
+ 0x50, 0x41, 0x37, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x8e, 0x71, 0x5d, 0xff,
+ 0xe6, 0xb8, 0x9f, 0xff, 0xe6, 0xb7, 0x9f, 0xff,
+ 0xff, 0xd3, 0xb5, 0xff, 0xff, 0xd2, 0xb5, 0xff,
+ 0xef, 0xc5, 0xad, 0xff, 0xee, 0xc5, 0xac, 0xff,
+ 0xef, 0xc5, 0xad, 0xff, 0xee, 0xc5, 0xac, 0xff,
+ 0xff, 0xd7, 0xbd, 0xff, 0xeb, 0xbf, 0xa4, 0xff,
+ 0xff, 0xd7, 0xbd, 0xff, 0xd8, 0xa8, 0x8c, 0xff,
+ 0x4a, 0x29, 0x19, 0xff, 0x4a, 0x28, 0x18, 0xff,
+ 0x87, 0x61, 0x4a, 0xff, 0x86, 0x61, 0x4a, 0xff,
+ 0x94, 0x6d, 0x52, 0xff, 0x4c, 0x37, 0x26, 0xff,
+ 0x29, 0x1d, 0x11, 0xff, 0x29, 0x1c, 0x10, 0xff,
+ 0x31, 0x25, 0x19, 0xff, 0x31, 0x24, 0x18, 0xff,
+ 0x21, 0x19, 0x11, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x19, 0x10, 0x11, 0xff, 0x44, 0x30, 0x20, 0xff,
+ 0x45, 0x31, 0x21, 0xff, 0x18, 0x10, 0x10, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x32, 0x26, 0x1c, 0xff, 0x21, 0x1b, 0x16, 0xff,
+ 0x1c, 0x21, 0x1c, 0xff, 0x26, 0x34, 0x2e, 0xff,
+ 0x32, 0x49, 0x42, 0xff, 0x26, 0x35, 0x2f, 0xff,
+ 0x32, 0x2e, 0x27, 0xff, 0x21, 0x1f, 0x1b, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x58, 0x3e, 0x34, 0xff, 0x73, 0x51, 0x42, 0xff,
+ 0x21, 0x19, 0x19, 0xff, 0x3c, 0x2b, 0x26, 0xff,
+ 0x53, 0x51, 0x4a, 0xff, 0x18, 0x24, 0x21, 0xff,
+ 0x2c, 0x34, 0x2f, 0xff, 0x2c, 0x33, 0x2f, 0xff,
+ 0x2f, 0x3a, 0x34, 0xff, 0x2e, 0x3a, 0x34, 0xff,
+ 0x2f, 0x3a, 0x35, 0xff, 0x39, 0x49, 0x42, 0xff,
+ 0x5b, 0x49, 0x3a, 0xff, 0x29, 0x20, 0x18, 0xff,
+ 0x11, 0x0d, 0x09, 0xff, 0x29, 0x20, 0x19, 0xff,
+ 0x5b, 0x51, 0x4a, 0xff, 0x5a, 0x51, 0x4a, 0xff,
+ 0x3a, 0x34, 0x2f, 0xff, 0x4a, 0x42, 0x3c, 0xff,
+ 0x50, 0x41, 0x37, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x50, 0x41, 0x37, 0xff, 0x8e, 0x71, 0x5d, 0xff,
+ 0xe7, 0xb8, 0x9f, 0xff, 0xff, 0xd2, 0xb5, 0xff,
+ 0xe7, 0xb8, 0x9f, 0xff, 0xff, 0xd2, 0xb5, 0xff,
+ 0xef, 0xc5, 0xad, 0xff, 0xee, 0xc5, 0xad, 0xff,
+ 0xff, 0xd7, 0xbe, 0xff, 0xff, 0xd6, 0xbd, 0xff,
+ 0xff, 0xd7, 0xbd, 0xff, 0xff, 0xd6, 0xbd, 0xff,
+ 0xff, 0xd7, 0xbe, 0xff, 0xff, 0xd6, 0xbd, 0xff,
+ 0xc3, 0x9a, 0x7c, 0xff, 0xc2, 0x9a, 0x7b, 0xff,
+ 0x87, 0x62, 0x4a, 0xff, 0x86, 0x61, 0x4a, 0xff,
+ 0x71, 0x53, 0x3d, 0xff, 0x29, 0x1c, 0x10, 0xff,
+ 0x71, 0x53, 0x3d, 0xff, 0x4d, 0x37, 0x26, 0xff,
+ 0x21, 0x19, 0x11, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x11, 0x0d, 0x09, 0xff, 0x21, 0x18, 0x10, 0xff,
+ 0x2f, 0x21, 0x19, 0xff, 0x2e, 0x20, 0x18, 0xff,
+ 0x2f, 0x21, 0x19, 0xff, 0x19, 0x10, 0x10, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x21, 0x1b, 0x16, 0xff,
+ 0x42, 0x31, 0x21, 0xff, 0x21, 0x1b, 0x16, 0xff,
+ 0x11, 0x0c, 0x08, 0xff, 0x1b, 0x20, 0x1b, 0xff,
+ 0x31, 0x49, 0x42, 0xff, 0x26, 0x34, 0x2e, 0xff,
+ 0x42, 0x3d, 0x32, 0xff, 0x41, 0x3c, 0x31, 0xff,
+ 0x21, 0x1f, 0x1b, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x21, 0x18, 0x19, 0xff, 0x73, 0x51, 0x41, 0xff,
+ 0x58, 0x3e, 0x34, 0xff, 0x73, 0x50, 0x41, 0xff,
+ 0x2c, 0x33, 0x2f, 0xff, 0x18, 0x24, 0x21, 0xff,
+ 0x19, 0x24, 0x21, 0xff, 0x2b, 0x33, 0x2e, 0xff,
+ 0x2f, 0x3a, 0x34, 0xff, 0x2e, 0x3a, 0x34, 0xff,
+ 0x2f, 0x3a, 0x34, 0xff, 0x2e, 0x3a, 0x34, 0xff,
+ 0x5b, 0x49, 0x3a, 0xff, 0x29, 0x20, 0x18, 0xff,
+ 0x29, 0x20, 0x19, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x3a, 0x33, 0x2f, 0xff, 0x39, 0x33, 0x2e, 0xff,
+ 0x29, 0x24, 0x21, 0xff, 0x39, 0x33, 0x2e, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x50, 0x41, 0x37, 0xff, 0x4f, 0x40, 0x36, 0xff,
+ 0xb5, 0x82, 0x73, 0xff, 0xcd, 0x9c, 0x89, 0xff,
+ 0xff, 0xd3, 0xb5, 0xff, 0xe6, 0xb7, 0x9f, 0xff,
+ 0xef, 0xc5, 0xad, 0xff, 0xde, 0xb3, 0x9c, 0xff,
+ 0xce, 0xa2, 0x8c, 0xff, 0xcd, 0xa1, 0x8b, 0xff,
+ 0xc6, 0x92, 0x73, 0xff, 0xd8, 0xa8, 0x8b, 0xff,
+ 0xff, 0xd7, 0xbd, 0xff, 0xff, 0xd6, 0xbd, 0xff,
+ 0xff, 0xd3, 0xad, 0xff, 0xff, 0xd2, 0xac, 0xff,
+ 0x4a, 0x29, 0x19, 0xff, 0x4a, 0x28, 0x18, 0xff,
+ 0x29, 0x1c, 0x11, 0xff, 0x29, 0x1c, 0x10, 0xff,
+ 0x70, 0x52, 0x3c, 0xff, 0x4c, 0x37, 0x26, 0xff,
+ 0x32, 0x25, 0x19, 0xff, 0x31, 0x24, 0x18, 0xff,
+ 0x21, 0x18, 0x10, 0xff, 0x20, 0x18, 0x10, 0xff,
+ 0x19, 0x10, 0x11, 0xff, 0x18, 0x10, 0x10, 0xff,
+ 0x19, 0x10, 0x10, 0xff, 0x18, 0x10, 0x10, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x21, 0x1b, 0x16, 0xff,
+ 0x21, 0x1b, 0x16, 0xff, 0x20, 0x1b, 0x15, 0xff,
+ 0x21, 0x2e, 0x2c, 0xff, 0x21, 0x2e, 0x2c, 0xff,
+ 0x29, 0x3d, 0x3a, 0xff, 0x29, 0x3d, 0x39, 0xff,
+ 0x2a, 0x3c, 0x37, 0xff, 0x29, 0x3b, 0x37, 0xff,
+ 0x19, 0x21, 0x21, 0xff, 0x21, 0x2e, 0x2c, 0xff,
+ 0x1c, 0x1b, 0x19, 0xff, 0x1b, 0x1b, 0x19, 0xff,
+ 0x27, 0x2a, 0x29, 0xff, 0x26, 0x2a, 0x29, 0xff,
+ 0x1f, 0x21, 0x21, 0xff, 0x1e, 0x20, 0x21, 0xff,
+ 0x1f, 0x21, 0x21, 0xff, 0x23, 0x2c, 0x29, 0xff,
+ 0x2c, 0x3d, 0x37, 0xff, 0x31, 0x49, 0x42, 0xff,
+ 0x2c, 0x3d, 0x37, 0xff, 0x2c, 0x3d, 0x37, 0xff,
+ 0x2a, 0x39, 0x32, 0xff, 0x31, 0x49, 0x42, 0xff,
+ 0x21, 0x29, 0x21, 0xff, 0x19, 0x18, 0x10, 0xff,
+ 0x14, 0x16, 0x19, 0xff, 0x19, 0x1c, 0x21, 0xff,
+ 0x0e, 0x0f, 0x11, 0xff, 0x13, 0x15, 0x19, 0xff,
+ 0x11, 0x12, 0x11, 0xff, 0x10, 0x12, 0x10, 0xff,
+ 0x32, 0x2d, 0x21, 0xff, 0x21, 0x1f, 0x19, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x47, 0x3f, 0x34, 0xff,
+ 0xb5, 0x96, 0x7c, 0xff, 0x7e, 0x6a, 0x58, 0xff,
+ 0x9d, 0x76, 0x5b, 0xff, 0x9c, 0x75, 0x5a, 0xff,
+ 0x71, 0x57, 0x42, 0xff, 0x44, 0x37, 0x29, 0xff,
+ 0x42, 0x29, 0x21, 0xff, 0x81, 0x69, 0x5d, 0xff,
+ 0xc0, 0xaa, 0x9a, 0xff, 0xff, 0xeb, 0xd6, 0xff,
+ 0xff, 0xeb, 0xce, 0xff, 0xd3, 0xb9, 0x9c, 0xff,
+ 0x7c, 0x55, 0x3a, 0xff, 0x7b, 0x55, 0x39, 0xff,
+ 0x5b, 0x49, 0x37, 0xff, 0x5a, 0x49, 0x37, 0xff,
+ 0x29, 0x1d, 0x11, 0xff, 0x29, 0x1c, 0x10, 0xff,
+ 0x21, 0x1d, 0x19, 0xff, 0x19, 0x17, 0x13, 0xff,
+ 0x11, 0x12, 0x0e, 0xff, 0x10, 0x11, 0x0e, 0xff,
+ 0x19, 0x17, 0x16, 0xff, 0x19, 0x17, 0x16, 0xff,
+ 0x21, 0x1e, 0x1c, 0xff, 0x21, 0x1e, 0x1b, 0xff,
+ 0x16, 0x15, 0x14, 0xff, 0x1b, 0x18, 0x16, 0xff,
+ 0x1c, 0x19, 0x16, 0xff, 0x16, 0x14, 0x13, 0xff,
+ 0x19, 0x1f, 0x1e, 0xff, 0x20, 0x2d, 0x2b, 0xff,
+ 0x29, 0x3d, 0x3a, 0xff, 0x21, 0x2e, 0x2c, 0xff,
+ 0x21, 0x2e, 0x2c, 0xff, 0x20, 0x2d, 0x2b, 0xff,
+ 0x29, 0x3c, 0x37, 0xff, 0x21, 0x2e, 0x2c, 0xff,
+ 0x31, 0x39, 0x3a, 0xff, 0x31, 0x38, 0x39, 0xff,
+ 0x27, 0x2a, 0x29, 0xff, 0x1b, 0x1b, 0x18, 0xff,
+ 0x19, 0x14, 0x19, 0xff, 0x29, 0x38, 0x31, 0xff,
+ 0x24, 0x2d, 0x29, 0xff, 0x23, 0x2c, 0x29, 0xff,
+ 0x31, 0x49, 0x42, 0xff, 0x26, 0x30, 0x2b, 0xff,
+ 0x32, 0x49, 0x42, 0xff, 0x31, 0x49, 0x42, 0xff,
+ 0x29, 0x39, 0x31, 0xff, 0x31, 0x48, 0x41, 0xff,
+ 0x32, 0x49, 0x42, 0xff, 0x21, 0x28, 0x21, 0xff,
+ 0x13, 0x16, 0x19, 0xff, 0x0d, 0x0e, 0x10, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x00, 0x04, 0x08, 0xff, 0x00, 0x04, 0x08, 0xff,
+ 0x11, 0x12, 0x11, 0xff, 0x10, 0x11, 0x10, 0xff,
+ 0x11, 0x14, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x48, 0x40, 0x34, 0xff, 0x47, 0x3f, 0x34, 0xff,
+ 0x19, 0x18, 0x11, 0xff, 0x18, 0x18, 0x10, 0xff,
+ 0x19, 0x19, 0x11, 0xff, 0x18, 0x18, 0x10, 0xff,
+ 0x42, 0x29, 0x21, 0xff, 0x41, 0x28, 0x20, 0xff,
+ 0xc0, 0xaa, 0x9a, 0xff, 0xff, 0xea, 0xd6, 0xff,
+ 0xff, 0xeb, 0xce, 0xff, 0xd3, 0xb8, 0x9c, 0xff,
+ 0x7c, 0x55, 0x3a, 0xff, 0xa7, 0x87, 0x6b, 0xff,
+ 0x8c, 0x75, 0x5d, 0xff, 0x8b, 0x75, 0x5d, 0xff,
+ 0x29, 0x1d, 0x11, 0xff, 0x29, 0x1c, 0x10, 0xff,
+ 0x11, 0x12, 0x0e, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x11, 0x12, 0x0e, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x21, 0x1e, 0x1c, 0xff, 0x20, 0x1d, 0x1b, 0xff,
+ 0x21, 0x1e, 0x1c, 0xff, 0x18, 0x17, 0x16, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x1b, 0x18, 0x16, 0xff,
+ 0x16, 0x14, 0x13, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x18, 0x1f, 0x1e, 0xff,
+ 0x21, 0x2e, 0x2c, 0xff, 0x29, 0x3d, 0x39, 0xff,
+ 0x32, 0x49, 0x42, 0xff, 0x29, 0x3b, 0x37, 0xff,
+ 0x32, 0x49, 0x42, 0xff, 0x31, 0x49, 0x42, 0xff,
+ 0x32, 0x39, 0x3a, 0xff, 0x31, 0x38, 0x39, 0xff,
+ 0x27, 0x2a, 0x2a, 0xff, 0x1b, 0x1b, 0x19, 0xff,
+ 0x19, 0x15, 0x19, 0xff, 0x23, 0x2c, 0x29, 0xff,
+ 0x24, 0x2d, 0x2a, 0xff, 0x1e, 0x20, 0x21, 0xff,
+ 0x21, 0x25, 0x21, 0xff, 0x26, 0x30, 0x2c, 0xff,
+ 0x2c, 0x3d, 0x37, 0xff, 0x2c, 0x3d, 0x37, 0xff,
+ 0x29, 0x39, 0x32, 0xff, 0x29, 0x38, 0x31, 0xff,
+ 0x32, 0x49, 0x42, 0xff, 0x29, 0x39, 0x31, 0xff,
+ 0x13, 0x16, 0x19, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x09, 0x09, 0x09, 0xff, 0x0e, 0x0f, 0x10, 0xff,
+ 0x11, 0x12, 0x11, 0xff, 0x10, 0x11, 0x10, 0xff,
+ 0x11, 0x12, 0x11, 0xff, 0x00, 0x04, 0x08, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x19, 0x19, 0x11, 0xff, 0x18, 0x18, 0x10, 0xff,
+ 0x19, 0x19, 0x11, 0xff, 0x19, 0x18, 0x10, 0xff,
+ 0x42, 0x29, 0x21, 0xff, 0x81, 0x69, 0x5d, 0xff,
+ 0x81, 0x6a, 0x5e, 0xff, 0xc0, 0xaa, 0x99, 0xff,
+ 0xff, 0xeb, 0xce, 0xff, 0xa7, 0x87, 0x6b, 0xff,
+ 0xa8, 0x87, 0x6b, 0xff, 0xff, 0xeb, 0xce, 0xff,
+ 0xbd, 0xa2, 0x84, 0xff, 0xbd, 0xa2, 0x83, 0xff,
+ 0x5b, 0x49, 0x37, 0xff, 0x5a, 0x49, 0x37, 0xff,
+ 0x19, 0x17, 0x13, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x11, 0x12, 0x0e, 0xff, 0x10, 0x11, 0x0e, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x18, 0x17, 0x16, 0xff,
+ 0x21, 0x1e, 0x1c, 0xff, 0x19, 0x17, 0x16, 0xff,
+ 0x1c, 0x19, 0x16, 0xff, 0x1b, 0x18, 0x16, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x16, 0x14, 0x13, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x10, 0x10, 0x10, 0xff, 0x18, 0x1f, 0x1e, 0xff,
+ 0x21, 0x2e, 0x2c, 0xff, 0x21, 0x2e, 0x2c, 0xff,
+ 0x21, 0x2e, 0x2c, 0xff, 0x20, 0x2d, 0x2b, 0xff,
+ 0x27, 0x2a, 0x29, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x10, 0x0c, 0x08, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x19, 0x14, 0x19, 0xff, 0x18, 0x14, 0x18, 0xff,
+ 0x1e, 0x20, 0x21, 0xff, 0x1e, 0x20, 0x20, 0xff,
+ 0x21, 0x25, 0x21, 0xff, 0x21, 0x24, 0x21, 0xff,
+ 0x26, 0x31, 0x2c, 0xff, 0x2b, 0x3c, 0x36, 0xff,
+ 0x29, 0x39, 0x32, 0xff, 0x21, 0x28, 0x21, 0xff,
+ 0x21, 0x29, 0x21, 0xff, 0x20, 0x28, 0x20, 0xff,
+ 0x19, 0x1c, 0x21, 0xff, 0x18, 0x1c, 0x21, 0xff,
+ 0x0e, 0x0f, 0x10, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x00, 0x04, 0x08, 0xff, 0x00, 0x04, 0x08, 0xff,
+ 0x00, 0x04, 0x08, 0xff, 0x00, 0x04, 0x08, 0xff,
+ 0x11, 0x14, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x10, 0x14, 0x10, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x19, 0x18, 0x11, 0xff, 0x18, 0x18, 0x10, 0xff,
+ 0x19, 0x18, 0x10, 0xff, 0x18, 0x18, 0x10, 0xff,
+ 0x42, 0x29, 0x21, 0xff, 0x81, 0x69, 0x5d, 0xff,
+ 0x42, 0x29, 0x21, 0xff, 0x80, 0x69, 0x5d, 0xff,
+ 0xd3, 0xb9, 0x9c, 0xff, 0x7b, 0x55, 0x39, 0xff,
+ 0xa7, 0x87, 0x6b, 0xff, 0x7b, 0x55, 0x39, 0xff,
+ 0x5b, 0x49, 0x37, 0xff, 0x8b, 0x75, 0x5d, 0xff,
+ 0x8c, 0x75, 0x5d, 0xff, 0x5a, 0x48, 0x36, 0xff,
+ 0x08, 0x0c, 0x08, 0xff, 0x10, 0x11, 0x0d, 0xff,
+ 0x19, 0x17, 0x13, 0xff, 0x18, 0x16, 0x13, 0xff,
+ 0x19, 0x17, 0x16, 0xff, 0x29, 0x24, 0x21, 0xff,
+ 0x29, 0x24, 0x21, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x21, 0x1c, 0x19, 0xff, 0x21, 0x1c, 0x18, 0xff,
+ 0x16, 0x14, 0x13, 0xff, 0x15, 0x14, 0x13, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x1c, 0x1f, 0x1f, 0xff, 0x1b, 0x1f, 0x1e, 0xff,
+ 0x19, 0x1d, 0x19, 0xff, 0x21, 0x28, 0x21, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x19, 0x1c, 0x19, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x05, 0x05, 0x05, 0xff,
+ 0x06, 0x06, 0x06, 0xff, 0x0b, 0x0b, 0x0b, 0xff,
+ 0x11, 0x12, 0x11, 0xff, 0x10, 0x12, 0x10, 0xff,
+ 0x11, 0x12, 0x11, 0xff, 0x21, 0x24, 0x21, 0xff,
+ 0x21, 0x29, 0x27, 0xff, 0x21, 0x28, 0x26, 0xff,
+ 0x29, 0x35, 0x32, 0xff, 0x21, 0x28, 0x26, 0xff,
+ 0x2a, 0x26, 0x2a, 0xff, 0x29, 0x26, 0x29, 0xff,
+ 0x19, 0x17, 0x19, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x14, 0x11, 0x14, 0xff, 0x29, 0x28, 0x29, 0xff,
+ 0x14, 0x11, 0x14, 0xff, 0x13, 0x10, 0x13, 0xff,
+ 0x09, 0x0a, 0x0b, 0xff, 0x00, 0x04, 0x08, 0xff,
+ 0x00, 0x04, 0x09, 0xff, 0x00, 0x04, 0x08, 0xff,
+ 0x0b, 0x09, 0x0b, 0xff, 0x0e, 0x0c, 0x0e, 0xff,
+ 0x0e, 0x0c, 0x0e, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x14, 0x11, 0x0e, 0xff, 0x0e, 0x0c, 0x0b, 0xff,
+ 0x09, 0x08, 0x09, 0xff, 0x19, 0x14, 0x10, 0xff,
+ 0x4b, 0x3d, 0x32, 0xff, 0x37, 0x2e, 0x26, 0xff,
+ 0x24, 0x1f, 0x1c, 0xff, 0x23, 0x1f, 0x1b, 0xff,
+ 0x2c, 0x28, 0x27, 0xff, 0x3a, 0x35, 0x31, 0xff,
+ 0x3a, 0x35, 0x32, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x0e, 0x12, 0x14, 0xff, 0x13, 0x17, 0x16, 0xff,
+ 0x14, 0x17, 0x16, 0xff, 0x19, 0x1c, 0x19, 0xff,
+ 0x2c, 0x25, 0x1f, 0xff, 0x1e, 0x18, 0x13, 0xff,
+ 0x1f, 0x19, 0x14, 0xff, 0x1e, 0x18, 0x13, 0xff,
+ 0x24, 0x21, 0x1c, 0xff, 0x24, 0x20, 0x1b, 0xff,
+ 0x1f, 0x19, 0x16, 0xff, 0x19, 0x10, 0x10, 0xff,
+ 0x1c, 0x1f, 0x1e, 0xff, 0x1b, 0x1f, 0x1e, 0xff,
+ 0x27, 0x2e, 0x2c, 0xff, 0x1b, 0x1f, 0x1e, 0xff,
+ 0x19, 0x1c, 0x19, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x08, 0x04, 0x08, 0xff,
+ 0x0b, 0x0b, 0x0b, 0xff, 0x05, 0x05, 0x05, 0xff,
+ 0x06, 0x06, 0x06, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x10, 0x11, 0x10, 0xff,
+ 0x11, 0x12, 0x11, 0xff, 0x18, 0x1b, 0x18, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x18, 0x1c, 0x1b, 0xff,
+ 0x29, 0x35, 0x32, 0xff, 0x18, 0x1c, 0x1b, 0xff,
+ 0x19, 0x17, 0x19, 0xff, 0x18, 0x17, 0x18, 0xff,
+ 0x19, 0x17, 0x19, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x13, 0x10, 0x13, 0xff, 0x13, 0x10, 0x13, 0xff,
+ 0x08, 0x04, 0x08, 0xff, 0x08, 0x04, 0x08, 0xff,
+ 0x00, 0x04, 0x08, 0xff, 0x08, 0x09, 0x0b, 0xff,
+ 0x11, 0x0f, 0x0e, 0xff, 0x00, 0x04, 0x08, 0xff,
+ 0x08, 0x04, 0x08, 0xff, 0x0d, 0x0c, 0x0d, 0xff,
+ 0x0e, 0x0c, 0x0e, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x0d, 0x0e, 0x0d, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x0e, 0x0c, 0x0b, 0xff, 0x0d, 0x0c, 0x0b, 0xff,
+ 0x0e, 0x0c, 0x0b, 0xff, 0x0d, 0x0c, 0x0b, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x23, 0x1f, 0x1b, 0xff,
+ 0x37, 0x2e, 0x27, 0xff, 0x37, 0x2e, 0x26, 0xff,
+ 0x1e, 0x1a, 0x1c, 0xff, 0x2b, 0x27, 0x26, 0xff,
+ 0x1e, 0x1a, 0x1c, 0xff, 0x1e, 0x19, 0x1b, 0xff,
+ 0x13, 0x17, 0x16, 0xff, 0x13, 0x17, 0x16, 0xff,
+ 0x0e, 0x12, 0x13, 0xff, 0x0d, 0x11, 0x13, 0xff,
+ 0x1e, 0x18, 0x13, 0xff, 0x1e, 0x18, 0x13, 0xff,
+ 0x11, 0x0c, 0x08, 0xff, 0x1e, 0x18, 0x13, 0xff,
+ 0x29, 0x29, 0x21, 0xff, 0x23, 0x20, 0x1b, 0xff,
+ 0x1e, 0x19, 0x16, 0xff, 0x18, 0x10, 0x10, 0xff,
+ 0x32, 0x3d, 0x3a, 0xff, 0x26, 0x2e, 0x2c, 0xff,
+ 0x27, 0x2e, 0x2c, 0xff, 0x1b, 0x1f, 0x1e, 0xff,
+ 0x09, 0x04, 0x09, 0xff, 0x08, 0x04, 0x08, 0xff,
+ 0x09, 0x04, 0x09, 0xff, 0x08, 0x04, 0x08, 0xff,
+ 0x00, 0x00, 0x00, 0xff, 0x00, 0x00, 0x00, 0xff,
+ 0x06, 0x06, 0x06, 0xff, 0x05, 0x05, 0x05, 0xff,
+ 0x09, 0x08, 0x09, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x09, 0x09, 0x09, 0xff, 0x10, 0x11, 0x10, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x21, 0x29, 0x27, 0xff, 0x19, 0x1c, 0x1b, 0xff,
+ 0x19, 0x17, 0x19, 0xff, 0x29, 0x26, 0x29, 0xff,
+ 0x19, 0x17, 0x19, 0xff, 0x19, 0x17, 0x19, 0xff,
+ 0x13, 0x10, 0x13, 0xff, 0x13, 0x10, 0x13, 0xff,
+ 0x09, 0x04, 0x09, 0xff, 0x1e, 0x1c, 0x1e, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x08, 0x09, 0x0b, 0xff,
+ 0x00, 0x04, 0x09, 0xff, 0x08, 0x09, 0x0b, 0xff,
+ 0x0b, 0x08, 0x0b, 0xff, 0x0d, 0x0c, 0x0d, 0xff,
+ 0x0e, 0x0d, 0x0e, 0xff, 0x0e, 0x0c, 0x0e, 0xff,
+ 0x0b, 0x0e, 0x0b, 0xff, 0x0d, 0x0f, 0x0d, 0xff,
+ 0x0e, 0x0f, 0x0e, 0xff, 0x0b, 0x0d, 0x0b, 0xff,
+ 0x13, 0x10, 0x0e, 0xff, 0x0d, 0x0c, 0x0b, 0xff,
+ 0x0e, 0x0d, 0x0b, 0xff, 0x13, 0x10, 0x0e, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x23, 0x1f, 0x1b, 0xff,
+ 0x24, 0x1f, 0x1c, 0xff, 0x24, 0x1f, 0x1b, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x1e, 0x19, 0x1b, 0xff,
+ 0x1f, 0x1a, 0x1c, 0xff, 0x1e, 0x1a, 0x1b, 0xff,
+ 0x13, 0x17, 0x16, 0xff, 0x0d, 0x11, 0x13, 0xff,
+ 0x0e, 0x12, 0x14, 0xff, 0x13, 0x17, 0x16, 0xff,
+ 0x1e, 0x19, 0x13, 0xff, 0x1e, 0x18, 0x13, 0xff,
+ 0x11, 0x0d, 0x09, 0xff, 0x2c, 0x24, 0x1e, 0xff,
+ 0x29, 0x29, 0x21, 0xff, 0x23, 0x20, 0x1b, 0xff,
+ 0x19, 0x11, 0x11, 0xff, 0x1e, 0x18, 0x16, 0xff,
+ 0x27, 0x2e, 0x2c, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x10, 0x10, 0x10, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x19, 0x1c, 0x19, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x08, 0x04, 0x08, 0xff, 0x08, 0x04, 0x08, 0xff,
+ 0x0b, 0x0b, 0x0b, 0xff, 0x05, 0x05, 0x05, 0xff,
+ 0x0b, 0x0b, 0x0b, 0xff, 0x0a, 0x0a, 0x0a, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x10, 0x12, 0x10, 0xff, 0x10, 0x11, 0x10, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x18, 0x1c, 0x1b, 0xff,
+ 0x29, 0x35, 0x31, 0xff, 0x20, 0x28, 0x26, 0xff,
+ 0x19, 0x17, 0x19, 0xff, 0x39, 0x34, 0x39, 0xff,
+ 0x3a, 0x35, 0x3a, 0xff, 0x29, 0x25, 0x29, 0xff,
+ 0x29, 0x29, 0x29, 0xff, 0x29, 0x28, 0x29, 0xff,
+ 0x13, 0x10, 0x13, 0xff, 0x29, 0x28, 0x29, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x08, 0x09, 0x0b, 0xff,
+ 0x00, 0x04, 0x08, 0xff, 0x08, 0x09, 0x0a, 0xff,
+ 0x0e, 0x0c, 0x0e, 0xff, 0x0d, 0x0c, 0x0d, 0xff,
+ 0x0b, 0x08, 0x0b, 0xff, 0x0a, 0x08, 0x0a, 0xff,
+ 0x08, 0x0c, 0x08, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x0b, 0x0e, 0x0b, 0xff, 0x0a, 0x0d, 0x0a, 0xff,
+ 0x0e, 0x0c, 0x0b, 0xff, 0x0d, 0x0c, 0x0b, 0xff,
+ 0x0e, 0x0c, 0x0b, 0xff, 0x13, 0x10, 0x0d, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x24, 0x1f, 0x1b, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x1e, 0x1a, 0x1c, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x1e, 0x1a, 0x1b, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x13, 0x17, 0x16, 0xff, 0x08, 0x0c, 0x10, 0xff,
+ 0x0e, 0x12, 0x13, 0xff, 0x0d, 0x11, 0x13, 0xff,
+ 0x1e, 0x18, 0x13, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x2c, 0x24, 0x1e, 0xff, 0x39, 0x30, 0x29, 0xff,
+ 0x29, 0x29, 0x21, 0xff, 0x29, 0x28, 0x21, 0xff,
+ 0x1e, 0x18, 0x16, 0xff, 0x18, 0x10, 0x10, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x0e, 0x0d, 0x0e, 0xff,
+ 0x14, 0x13, 0x14, 0xff, 0x13, 0x13, 0x13, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x0b, 0x0c, 0x0e, 0xff,
+ 0x06, 0x08, 0x0b, 0xff, 0x05, 0x08, 0x0b, 0xff,
+ 0x09, 0x09, 0x09, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x09, 0x0d, 0x09, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x09, 0x0c, 0x09, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x21, 0x21, 0x21, 0xff, 0x31, 0x35, 0x3a, 0xff,
+ 0x42, 0x49, 0x53, 0xff, 0x42, 0x49, 0x52, 0xff,
+ 0x1f, 0x24, 0x21, 0xff, 0x5a, 0x61, 0x63, 0xff,
+ 0x3d, 0x42, 0x42, 0xff, 0x3c, 0x42, 0x42, 0xff,
+ 0x45, 0x48, 0x48, 0xff, 0x45, 0x47, 0x47, 0xff,
+ 0x27, 0x2a, 0x2c, 0xff, 0x26, 0x2a, 0x2c, 0xff,
+ 0x11, 0x0d, 0x09, 0xff, 0x0b, 0x08, 0x05, 0xff,
+ 0x0b, 0x08, 0x06, 0xff, 0x0b, 0x08, 0x05, 0xff,
+ 0x09, 0x09, 0x09, 0xff, 0x0b, 0x0b, 0x0b, 0xff,
+ 0x0b, 0x0b, 0x0b, 0xff, 0x0b, 0x0b, 0x0b, 0xff,
+ 0x09, 0x09, 0x09, 0xff, 0x0b, 0x0b, 0x0b, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x0e, 0x0d, 0x0e, 0xff,
+ 0x0b, 0x0e, 0x0b, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x0b, 0x0e, 0x0b, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x0d, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x16, 0x15, 0x14, 0xff, 0x1b, 0x1c, 0x16, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x19, 0x14, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x19, 0x14, 0x10, 0xff,
+ 0x16, 0x11, 0x11, 0xff, 0x16, 0x10, 0x10, 0xff,
+ 0x16, 0x11, 0x11, 0xff, 0x10, 0x08, 0x08, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x32, 0x39, 0x32, 0xff, 0x31, 0x39, 0x31, 0xff,
+ 0x2a, 0x31, 0x21, 0xff, 0x29, 0x31, 0x21, 0xff,
+ 0x29, 0x31, 0x21, 0xff, 0x21, 0x24, 0x1b, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x0d, 0x0d, 0x0d, 0xff,
+ 0x13, 0x13, 0x13, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x00, 0x04, 0x08, 0xff, 0x05, 0x08, 0x0b, 0xff,
+ 0x06, 0x08, 0x0b, 0xff, 0x05, 0x08, 0x0b, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x0d, 0x0d, 0x0d, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x08, 0x0c, 0x08, 0xff, 0x10, 0x15, 0x13, 0xff,
+ 0x08, 0x0c, 0x08, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x21, 0x20, 0x21, 0xff, 0x31, 0x34, 0x39, 0xff,
+ 0x32, 0x35, 0x3a, 0xff, 0x21, 0x20, 0x21, 0xff,
+ 0x3c, 0x42, 0x42, 0xff, 0x3c, 0x42, 0x41, 0xff,
+ 0x1e, 0x23, 0x21, 0xff, 0x1e, 0x23, 0x21, 0xff,
+ 0x08, 0x0c, 0x11, 0xff, 0x44, 0x47, 0x47, 0xff,
+ 0x45, 0x48, 0x48, 0xff, 0x08, 0x0c, 0x10, 0xff,
+ 0x11, 0x0c, 0x08, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x0b, 0x08, 0x06, 0xff, 0x0b, 0x08, 0x05, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x0b, 0x0b, 0x0b, 0xff, 0x0b, 0x0b, 0x0b, 0xff,
+ 0x0b, 0x0b, 0x0b, 0xff, 0x0b, 0x0a, 0x0b, 0xff,
+ 0x0b, 0x0b, 0x0b, 0xff, 0x0d, 0x0d, 0x0d, 0xff,
+ 0x0b, 0x0e, 0x0b, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x0b, 0x0e, 0x0b, 0xff, 0x0d, 0x0f, 0x0d, 0xff,
+ 0x16, 0x14, 0x13, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x16, 0x14, 0x13, 0xff, 0x16, 0x14, 0x13, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x16, 0x10, 0x11, 0xff, 0x1b, 0x18, 0x18, 0xff,
+ 0x21, 0x21, 0x21, 0xff, 0x21, 0x20, 0x21, 0xff,
+ 0x1c, 0x1e, 0x1c, 0xff, 0x1b, 0x1d, 0x1b, 0xff,
+ 0x1c, 0x1e, 0x1c, 0xff, 0x1b, 0x1d, 0x1b, 0xff,
+ 0x19, 0x18, 0x16, 0xff, 0x18, 0x18, 0x16, 0xff,
+ 0x19, 0x19, 0x16, 0xff, 0x18, 0x18, 0x16, 0xff,
+ 0x19, 0x19, 0x19, 0xff, 0x18, 0x18, 0x18, 0xff,
+ 0x09, 0x09, 0x09, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x06, 0x08, 0x0b, 0xff, 0x05, 0x08, 0x0b, 0xff,
+ 0x06, 0x09, 0x0b, 0xff, 0x00, 0x04, 0x08, 0xff,
+ 0x09, 0x08, 0x09, 0xff, 0x0d, 0x0d, 0x0d, 0xff,
+ 0x19, 0x19, 0x19, 0xff, 0x13, 0x13, 0x13, 0xff,
+ 0x09, 0x0c, 0x09, 0xff, 0x10, 0x15, 0x13, 0xff,
+ 0x19, 0x1f, 0x1f, 0xff, 0x19, 0x1f, 0x1e, 0xff,
+ 0x21, 0x21, 0x21, 0xff, 0x21, 0x20, 0x21, 0xff,
+ 0x21, 0x21, 0x21, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x1e, 0x23, 0x21, 0xff, 0x00, 0x04, 0x00, 0xff,
+ 0x1f, 0x23, 0x21, 0xff, 0x5a, 0x61, 0x63, 0xff,
+ 0x27, 0x2a, 0x2c, 0xff, 0x26, 0x2a, 0x2c, 0xff,
+ 0x09, 0x0d, 0x11, 0xff, 0x08, 0x0c, 0x10, 0xff,
+ 0x06, 0x04, 0x03, 0xff, 0x00, 0x00, 0x00, 0xff,
+ 0x06, 0x04, 0x03, 0xff, 0x0b, 0x08, 0x05, 0xff,
+ 0x0b, 0x0b, 0x0b, 0xff, 0x0b, 0x0b, 0x0b, 0xff,
+ 0x0b, 0x0b, 0x0b, 0xff, 0x0e, 0x0d, 0x0e, 0xff,
+ 0x0b, 0x0b, 0x0b, 0xff, 0x0b, 0x0b, 0x0b, 0xff,
+ 0x0b, 0x0b, 0x0b, 0xff, 0x0e, 0x0d, 0x0e, 0xff,
+ 0x0e, 0x0f, 0x0e, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x0b, 0x0e, 0x0b, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x16, 0x14, 0x13, 0xff,
+ 0x16, 0x15, 0x14, 0xff, 0x1b, 0x1c, 0x16, 0xff,
+ 0x1e, 0x22, 0x1c, 0xff, 0x21, 0x28, 0x21, 0xff,
+ 0x21, 0x29, 0x21, 0xff, 0x1e, 0x22, 0x1b, 0xff,
+ 0x21, 0x21, 0x21, 0xff, 0x21, 0x20, 0x21, 0xff,
+ 0x21, 0x21, 0x21, 0xff, 0x21, 0x20, 0x21, 0xff,
+ 0x1c, 0x1e, 0x1c, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x11, 0x0d, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x13, 0x13, 0x13, 0xff, 0x18, 0x18, 0x18, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x00, 0x04, 0x08, 0xff, 0x00, 0x04, 0x08, 0xff,
+ 0x06, 0x08, 0x0b, 0xff, 0x05, 0x08, 0x0a, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x18, 0x18, 0x18, 0xff,
+ 0x21, 0x29, 0x29, 0xff, 0x18, 0x1f, 0x1e, 0xff,
+ 0x10, 0x16, 0x13, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x21, 0x21, 0x21, 0xff, 0x21, 0x20, 0x21, 0xff,
+ 0x10, 0x0c, 0x08, 0xff, 0x20, 0x20, 0x20, 0xff,
+ 0x1e, 0x23, 0x21, 0xff, 0x00, 0x04, 0x00, 0xff,
+ 0x00, 0x04, 0x00, 0xff, 0x3c, 0x42, 0x41, 0xff,
+ 0x63, 0x65, 0x63, 0xff, 0x62, 0x65, 0x62, 0xff,
+ 0x08, 0x0c, 0x10, 0xff, 0x08, 0x0c, 0x10, 0xff,
+ 0x06, 0x04, 0x03, 0xff, 0x05, 0x04, 0x02, 0xff,
+ 0x06, 0x04, 0x03, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x0b, 0x0b, 0x0b, 0xff, 0x0b, 0x0a, 0x0b, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x0a, 0x0a, 0x0a, 0xff,
+ 0x0b, 0x0e, 0x0b, 0xff, 0x0d, 0x0e, 0x0d, 0xff,
+ 0x0e, 0x0f, 0x0e, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x1c, 0x1c, 0x16, 0xff, 0x1b, 0x1c, 0x16, 0xff,
+ 0x21, 0x24, 0x19, 0xff, 0x20, 0x24, 0x18, 0xff,
+ 0x1e, 0x22, 0x1c, 0xff, 0x21, 0x28, 0x21, 0xff,
+ 0x1b, 0x1b, 0x16, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x16, 0x10, 0x11, 0xff, 0x16, 0x10, 0x10, 0xff,
+ 0x16, 0x10, 0x10, 0xff, 0x15, 0x10, 0x10, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x10, 0x10, 0x10, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x10, 0x0c, 0x10, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x09, 0x09, 0x09, 0xff, 0x10, 0x14, 0x16, 0xff,
+ 0x11, 0x15, 0x16, 0xff, 0x10, 0x14, 0x16, 0xff,
+ 0x06, 0x09, 0x06, 0xff, 0x0b, 0x0c, 0x0b, 0xff,
+ 0x06, 0x08, 0x06, 0xff, 0x0b, 0x0c, 0x0b, 0xff,
+ 0x09, 0x09, 0x09, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x14, 0x13, 0x14, 0xff, 0x1e, 0x1e, 0x1e, 0xff,
+ 0x2a, 0x29, 0x2a, 0xff, 0x29, 0x28, 0x29, 0xff,
+ 0x14, 0x13, 0x14, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x09, 0x0d, 0x09, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x09, 0x0c, 0x09, 0xff, 0x21, 0x24, 0x29, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x19, 0x18, 0x19, 0xff,
+ 0x5b, 0x5e, 0x63, 0xff, 0x5a, 0x5d, 0x63, 0xff,
+ 0x42, 0x44, 0x48, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x06, 0x06, 0x06, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x06, 0x06, 0x06, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x0e, 0x0b, 0x0e, 0xff, 0x0b, 0x09, 0x0b, 0xff,
+ 0x09, 0x08, 0x09, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x0b, 0x0b, 0x0b, 0xff, 0x0e, 0x0d, 0x0e, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x0e, 0x0d, 0x0e, 0xff,
+ 0x11, 0x0e, 0x11, 0xff, 0x10, 0x0d, 0x10, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x10, 0x0f, 0x10, 0xff,
+ 0x16, 0x15, 0x11, 0xff, 0x19, 0x18, 0x10, 0xff,
+ 0x14, 0x11, 0x11, 0xff, 0x19, 0x18, 0x10, 0xff,
+ 0x14, 0x16, 0x0e, 0xff, 0x0e, 0x0f, 0x0b, 0xff,
+ 0x0e, 0x0f, 0x0b, 0xff, 0x0e, 0x0f, 0x0b, 0xff,
+ 0x09, 0x0d, 0x11, 0xff, 0x08, 0x0c, 0x10, 0xff,
+ 0x0e, 0x11, 0x11, 0xff, 0x13, 0x14, 0x10, 0xff,
+ 0x09, 0x0d, 0x09, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x09, 0x0c, 0x09, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x11, 0x0d, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x20, 0x2c, 0x31, 0xff,
+ 0x21, 0x2d, 0x32, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x0b, 0x0c, 0x0b, 0xff, 0x0b, 0x0c, 0x0b, 0xff,
+ 0x06, 0x08, 0x06, 0xff, 0x00, 0x04, 0x00, 0xff,
+ 0x1e, 0x1e, 0x1e, 0xff, 0x13, 0x12, 0x13, 0xff,
+ 0x13, 0x13, 0x13, 0xff, 0x13, 0x13, 0x13, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x13, 0x12, 0x13, 0xff,
+ 0x1e, 0x1e, 0x1e, 0xff, 0x13, 0x13, 0x13, 0xff,
+ 0x08, 0x0c, 0x08, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x08, 0x0c, 0x08, 0xff, 0x18, 0x1c, 0x1e, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x42, 0x44, 0x47, 0xff, 0x41, 0x43, 0x47, 0xff,
+ 0x5b, 0x5d, 0x63, 0xff, 0x29, 0x2a, 0x2c, 0xff,
+ 0x06, 0x05, 0x06, 0xff, 0x05, 0x05, 0x05, 0xff,
+ 0x06, 0x06, 0x06, 0xff, 0x02, 0x02, 0x02, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x0d, 0x0a, 0x0d, 0xff,
+ 0x0b, 0x0a, 0x0b, 0xff, 0x0b, 0x09, 0x0b, 0xff,
+ 0x0b, 0x0b, 0x0b, 0xff, 0x0b, 0x0a, 0x0b, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x0d, 0x0d, 0x0d, 0xff,
+ 0x11, 0x0e, 0x11, 0xff, 0x10, 0x0e, 0x10, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x13, 0x10, 0x11, 0xff, 0x13, 0x10, 0x10, 0xff,
+ 0x13, 0x10, 0x11, 0xff, 0x13, 0x10, 0x10, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x08, 0x0c, 0x11, 0xff, 0x0d, 0x10, 0x10, 0xff,
+ 0x0e, 0x10, 0x11, 0xff, 0x0d, 0x10, 0x10, 0xff,
+ 0x08, 0x0c, 0x08, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x08, 0x0c, 0x08, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x16, 0x15, 0x13, 0xff,
+ 0x09, 0x08, 0x09, 0xff, 0x18, 0x20, 0x23, 0xff,
+ 0x21, 0x2d, 0x32, 0xff, 0x19, 0x20, 0x24, 0xff,
+ 0x06, 0x08, 0x06, 0xff, 0x00, 0x04, 0x00, 0xff,
+ 0x00, 0x04, 0x00, 0xff, 0x05, 0x08, 0x05, 0xff,
+ 0x13, 0x13, 0x13, 0xff, 0x13, 0x13, 0x13, 0xff,
+ 0x14, 0x13, 0x14, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x09, 0x08, 0x09, 0xff, 0x1e, 0x1d, 0x1e, 0xff,
+ 0x14, 0x13, 0x14, 0xff, 0x1e, 0x1e, 0x1e, 0xff,
+ 0x21, 0x25, 0x29, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x11, 0x15, 0x14, 0xff, 0x19, 0x1c, 0x1e, 0xff,
+ 0x09, 0x08, 0x09, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x09, 0x09, 0x09, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x29, 0x2a, 0x2c, 0xff, 0x42, 0x43, 0x47, 0xff,
+ 0x42, 0x44, 0x48, 0xff, 0x29, 0x2a, 0x2c, 0xff,
+ 0x09, 0x08, 0x09, 0xff, 0x03, 0x02, 0x03, 0xff,
+ 0x03, 0x03, 0x03, 0xff, 0x05, 0x05, 0x05, 0xff,
+ 0x09, 0x08, 0x09, 0xff, 0x0b, 0x09, 0x0b, 0xff,
+ 0x0e, 0x0b, 0x0e, 0xff, 0x0b, 0x09, 0x0b, 0xff,
+ 0x09, 0x08, 0x09, 0xff, 0x0b, 0x0b, 0x0b, 0xff,
+ 0x0b, 0x0b, 0x0b, 0xff, 0x0e, 0x0d, 0x0e, 0xff,
+ 0x11, 0x0e, 0x11, 0xff, 0x10, 0x0d, 0x10, 0xff,
+ 0x11, 0x0e, 0x11, 0xff, 0x10, 0x0f, 0x10, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x11, 0x0d, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x09, 0x08, 0x09, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x0e, 0x0f, 0x0b, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x0e, 0x10, 0x11, 0xff, 0x0d, 0x10, 0x10, 0xff,
+ 0x0e, 0x11, 0x11, 0xff, 0x13, 0x14, 0x10, 0xff,
+ 0x19, 0x1a, 0x0e, 0xff, 0x18, 0x19, 0x0d, 0xff,
+ 0x21, 0x21, 0x11, 0xff, 0x21, 0x20, 0x10, 0xff,
+ 0x16, 0x16, 0x13, 0xff, 0x1b, 0x1f, 0x16, 0xff,
+ 0x16, 0x16, 0x14, 0xff, 0x1b, 0x1f, 0x16, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x10, 0x14, 0x16, 0xff,
+ 0x21, 0x2d, 0x31, 0xff, 0x18, 0x20, 0x23, 0xff,
+ 0x0b, 0x0c, 0x0b, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x0b, 0x0c, 0x0b, 0xff, 0x00, 0x04, 0x00, 0xff,
+ 0x13, 0x13, 0x13, 0xff, 0x29, 0x28, 0x29, 0xff,
+ 0x29, 0x29, 0x29, 0xff, 0x1e, 0x1d, 0x1e, 0xff,
+ 0x13, 0x13, 0x13, 0xff, 0x13, 0x13, 0x13, 0xff,
+ 0x1e, 0x1e, 0x1e, 0xff, 0x1e, 0x1d, 0x1e, 0xff,
+ 0x19, 0x1c, 0x1e, 0xff, 0x18, 0x1c, 0x1e, 0xff,
+ 0x21, 0x24, 0x29, 0xff, 0x18, 0x1c, 0x1e, 0xff,
+ 0x00, 0x00, 0x00, 0xff, 0x00, 0x00, 0x00, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x10, 0x10, 0x10, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x06, 0x06, 0x06, 0xff, 0x02, 0x02, 0x02, 0xff,
+ 0x06, 0x05, 0x06, 0xff, 0x05, 0x05, 0x05, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x0b, 0x09, 0x0b, 0xff,
+ 0x0e, 0x0b, 0x0e, 0xff, 0x0a, 0x09, 0x0a, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x0b, 0x0a, 0x0b, 0xff,
+ 0x0b, 0x0b, 0x0b, 0xff, 0x0d, 0x0d, 0x0d, 0xff,
+ 0x11, 0x0e, 0x11, 0xff, 0x10, 0x0e, 0x10, 0xff,
+ 0x10, 0x0c, 0x10, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x13, 0x10, 0x11, 0xff, 0x13, 0x10, 0x10, 0xff,
+ 0x13, 0x10, 0x10, 0xff, 0x15, 0x14, 0x10, 0xff,
+ 0x13, 0x16, 0x0e, 0xff, 0x13, 0x15, 0x0d, 0xff,
+ 0x19, 0x1c, 0x10, 0xff, 0x18, 0x1c, 0x10, 0xff,
+ 0x19, 0x18, 0x11, 0xff, 0x18, 0x18, 0x10, 0xff,
+ 0x19, 0x18, 0x10, 0xff, 0x18, 0x18, 0x10, 0xff,
+ 0x19, 0x1a, 0x0e, 0xff, 0x21, 0x20, 0x10, 0xff,
+ 0x21, 0x20, 0x10, 0xff, 0x18, 0x19, 0x0d, 0xff,
+ 0x1c, 0x1f, 0x16, 0xff, 0x1b, 0x1f, 0x16, 0xff,
+ 0x21, 0x29, 0x19, 0xff, 0x20, 0x28, 0x18, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x1c, 0x2c, 0x29, 0xff, 0x31, 0x59, 0x5a, 0xff,
+ 0x19, 0x1d, 0x2a, 0xff, 0x19, 0x1c, 0x29, 0xff,
+ 0x19, 0x1d, 0x29, 0xff, 0x19, 0x1c, 0x29, 0xff,
+ 0x2a, 0x29, 0x32, 0xff, 0x37, 0x49, 0x4a, 0xff,
+ 0x29, 0x29, 0x32, 0xff, 0x29, 0x28, 0x31, 0xff,
+ 0x19, 0x19, 0x19, 0xff, 0x29, 0x41, 0x3a, 0xff,
+ 0x29, 0x41, 0x3a, 0xff, 0x19, 0x18, 0x19, 0xff,
+ 0x11, 0x0d, 0x09, 0xff, 0x24, 0x35, 0x2c, 0xff,
+ 0x11, 0x0c, 0x09, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x09, 0x0d, 0x09, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x09, 0x0c, 0x09, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x09, 0x0d, 0x09, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x09, 0x0c, 0x09, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x19, 0x14, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x19, 0x14, 0x10, 0xff,
+ 0x21, 0x25, 0x11, 0xff, 0x21, 0x24, 0x10, 0xff,
+ 0x21, 0x25, 0x11, 0xff, 0x21, 0x24, 0x10, 0xff,
+ 0x24, 0x2d, 0x1c, 0xff, 0x24, 0x2c, 0x1b, 0xff,
+ 0x27, 0x39, 0x27, 0xff, 0x26, 0x39, 0x26, 0xff,
+ 0x21, 0x41, 0x2a, 0xff, 0x21, 0x41, 0x29, 0xff,
+ 0x21, 0x38, 0x21, 0xff, 0x21, 0x2e, 0x19, 0xff,
+ 0x24, 0x34, 0x1f, 0xff, 0x24, 0x33, 0x1e, 0xff,
+ 0x24, 0x34, 0x1f, 0xff, 0x26, 0x42, 0x2c, 0xff,
+ 0x1c, 0x2b, 0x29, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x27, 0x42, 0x42, 0xff, 0x31, 0x59, 0x5a, 0xff,
+ 0x29, 0x3b, 0x3f, 0xff, 0x29, 0x3b, 0x3f, 0xff,
+ 0x29, 0x3c, 0x3f, 0xff, 0x29, 0x3b, 0x3f, 0xff,
+ 0x37, 0x49, 0x4a, 0xff, 0x29, 0x28, 0x31, 0xff,
+ 0x29, 0x29, 0x32, 0xff, 0x37, 0x49, 0x4a, 0xff,
+ 0x29, 0x41, 0x3a, 0xff, 0x18, 0x18, 0x18, 0xff,
+ 0x19, 0x19, 0x19, 0xff, 0x18, 0x18, 0x18, 0xff,
+ 0x24, 0x35, 0x2c, 0xff, 0x36, 0x5d, 0x4f, 0xff,
+ 0x24, 0x35, 0x2c, 0xff, 0x23, 0x34, 0x2c, 0xff,
+ 0x1c, 0x33, 0x2c, 0xff, 0x1b, 0x33, 0x2b, 0xff,
+ 0x1c, 0x33, 0x2c, 0xff, 0x1b, 0x33, 0x2c, 0xff,
+ 0x1c, 0x35, 0x2c, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x1c, 0x35, 0x2c, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x11, 0x14, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x14, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x14, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x14, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x14, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x14, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x1e, 0x2f, 0x23, 0xff,
+ 0x21, 0x25, 0x11, 0xff, 0x20, 0x24, 0x10, 0xff,
+ 0x21, 0x25, 0x11, 0xff, 0x21, 0x24, 0x10, 0xff,
+ 0x24, 0x2d, 0x1c, 0xff, 0x23, 0x2c, 0x1b, 0xff,
+ 0x27, 0x39, 0x27, 0xff, 0x26, 0x38, 0x26, 0xff,
+ 0x21, 0x37, 0x21, 0xff, 0x20, 0x2d, 0x18, 0xff,
+ 0x21, 0x2e, 0x19, 0xff, 0x21, 0x2e, 0x18, 0xff,
+ 0x21, 0x25, 0x11, 0xff, 0x23, 0x33, 0x1e, 0xff,
+ 0x21, 0x25, 0x11, 0xff, 0x23, 0x33, 0x1e, 0xff,
+ 0x27, 0x42, 0x42, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x27, 0x43, 0x42, 0xff, 0x31, 0x59, 0x5a, 0xff,
+ 0x29, 0x3c, 0x3f, 0xff, 0x18, 0x1c, 0x29, 0xff,
+ 0x2a, 0x3c, 0x3f, 0xff, 0x29, 0x3b, 0x3f, 0xff,
+ 0x45, 0x6a, 0x63, 0xff, 0x37, 0x49, 0x4a, 0xff,
+ 0x37, 0x49, 0x4a, 0xff, 0x29, 0x28, 0x31, 0xff,
+ 0x29, 0x41, 0x3a, 0xff, 0x29, 0x41, 0x39, 0xff,
+ 0x3a, 0x6a, 0x5b, 0xff, 0x39, 0x69, 0x5a, 0xff,
+ 0x4a, 0x86, 0x73, 0xff, 0x4a, 0x85, 0x73, 0xff,
+ 0x4a, 0x86, 0x74, 0xff, 0x4a, 0x85, 0x73, 0xff,
+ 0x42, 0x82, 0x73, 0xff, 0x2e, 0x5a, 0x4f, 0xff,
+ 0x2f, 0x5b, 0x50, 0xff, 0x42, 0x81, 0x73, 0xff,
+ 0x2f, 0x5d, 0x50, 0xff, 0x2e, 0x5d, 0x4f, 0xff,
+ 0x1c, 0x35, 0x2c, 0xff, 0x1b, 0x35, 0x2c, 0xff,
+ 0x1c, 0x32, 0x29, 0xff, 0x1b, 0x32, 0x29, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x1e, 0x2b, 0x21, 0xff,
+ 0x1f, 0x2c, 0x21, 0xff, 0x1e, 0x2b, 0x21, 0xff,
+ 0x1c, 0x2b, 0x24, 0xff, 0x1b, 0x2b, 0x23, 0xff,
+ 0x1c, 0x2c, 0x24, 0xff, 0x1b, 0x2b, 0x24, 0xff,
+ 0x1e, 0x32, 0x27, 0xff, 0x2c, 0x4f, 0x3c, 0xff,
+ 0x1f, 0x32, 0x27, 0xff, 0x1e, 0x32, 0x26, 0xff,
+ 0x1e, 0x30, 0x24, 0xff, 0x1e, 0x2f, 0x23, 0xff,
+ 0x1f, 0x30, 0x24, 0xff, 0x19, 0x14, 0x10, 0xff,
+ 0x21, 0x25, 0x11, 0xff, 0x21, 0x24, 0x10, 0xff,
+ 0x21, 0x25, 0x11, 0xff, 0x21, 0x24, 0x10, 0xff,
+ 0x21, 0x21, 0x11, 0xff, 0x21, 0x20, 0x10, 0xff,
+ 0x21, 0x21, 0x11, 0xff, 0x21, 0x20, 0x10, 0xff,
+ 0x21, 0x25, 0x11, 0xff, 0x21, 0x24, 0x10, 0xff,
+ 0x21, 0x25, 0x11, 0xff, 0x21, 0x24, 0x10, 0xff,
+ 0x21, 0x25, 0x11, 0xff, 0x21, 0x24, 0x10, 0xff,
+ 0x21, 0x25, 0x11, 0xff, 0x24, 0x33, 0x1e, 0xff,
+ 0x27, 0x42, 0x42, 0xff, 0x31, 0x59, 0x5a, 0xff,
+ 0x31, 0x59, 0x5b, 0xff, 0x31, 0x59, 0x5a, 0xff,
+ 0x4a, 0x7a, 0x6b, 0xff, 0x4a, 0x79, 0x6b, 0xff,
+ 0x4a, 0x79, 0x6b, 0xff, 0x4a, 0x79, 0x6a, 0xff,
+ 0x52, 0x8a, 0x7c, 0xff, 0x52, 0x89, 0x7b, 0xff,
+ 0x52, 0x8a, 0x7b, 0xff, 0x52, 0x89, 0x7b, 0xff,
+ 0x4a, 0x92, 0x7c, 0xff, 0x4a, 0x91, 0x7b, 0xff,
+ 0x4a, 0x92, 0x7b, 0xff, 0x4a, 0x91, 0x7b, 0xff,
+ 0x4a, 0x86, 0x73, 0xff, 0x4a, 0x85, 0x73, 0xff,
+ 0x4a, 0x86, 0x73, 0xff, 0x4a, 0x85, 0x73, 0xff,
+ 0x42, 0x82, 0x73, 0xff, 0x41, 0x81, 0x73, 0xff,
+ 0x42, 0x82, 0x73, 0xff, 0x41, 0x81, 0x73, 0xff,
+ 0x42, 0x86, 0x73, 0xff, 0x2e, 0x5d, 0x4f, 0xff,
+ 0x2f, 0x5d, 0x50, 0xff, 0x2e, 0x5d, 0x4f, 0xff,
+ 0x32, 0x6d, 0x5b, 0xff, 0x26, 0x4f, 0x41, 0xff,
+ 0x26, 0x50, 0x42, 0xff, 0x26, 0x4f, 0x41, 0xff,
+ 0x2c, 0x42, 0x32, 0xff, 0x39, 0x59, 0x41, 0xff,
+ 0x3a, 0x59, 0x42, 0xff, 0x39, 0x59, 0x41, 0xff,
+ 0x27, 0x46, 0x37, 0xff, 0x31, 0x61, 0x4a, 0xff,
+ 0x31, 0x61, 0x4a, 0xff, 0x31, 0x61, 0x4a, 0xff,
+ 0x3a, 0x6d, 0x52, 0xff, 0x39, 0x6d, 0x52, 0xff,
+ 0x3a, 0x6d, 0x52, 0xff, 0x39, 0x6d, 0x52, 0xff,
+ 0x29, 0x65, 0x4a, 0xff, 0x29, 0x65, 0x4a, 0xff,
+ 0x29, 0x65, 0x4a, 0xff, 0x29, 0x65, 0x4a, 0xff,
+ 0x29, 0x59, 0x42, 0xff, 0x29, 0x59, 0x41, 0xff,
+ 0x29, 0x59, 0x42, 0xff, 0x26, 0x47, 0x31, 0xff,
+ 0x27, 0x39, 0x27, 0xff, 0x26, 0x38, 0x26, 0xff,
+ 0x29, 0x45, 0x31, 0xff, 0x29, 0x44, 0x31, 0xff,
+ 0x21, 0x41, 0x29, 0xff, 0x21, 0x37, 0x21, 0xff,
+ 0x21, 0x37, 0x21, 0xff, 0x20, 0x40, 0x29, 0xff,
+ 0x29, 0x51, 0x3a, 0xff, 0x29, 0x51, 0x39, 0xff,
+ 0x29, 0x51, 0x3a, 0xff, 0x29, 0x50, 0x39, 0xff,
+ 0x4b, 0x8a, 0x74, 0xff, 0x52, 0x8e, 0x79, 0xff,
+ 0x5b, 0x92, 0x7e, 0xff, 0x52, 0x8e, 0x78, 0xff,
+ 0x58, 0x8f, 0x84, 0xff, 0x63, 0x96, 0x8c, 0xff,
+ 0x58, 0x8f, 0x84, 0xff, 0x58, 0x8f, 0x83, 0xff,
+ 0x4b, 0x8a, 0x79, 0xff, 0x5a, 0x92, 0x84, 0xff,
+ 0x53, 0x8e, 0x7e, 0xff, 0x42, 0x85, 0x73, 0xff,
+ 0x50, 0x8d, 0x7c, 0xff, 0x5d, 0x93, 0x84, 0xff,
+ 0x5e, 0x93, 0x84, 0xff, 0x4f, 0x8c, 0x7b, 0xff,
+ 0x53, 0x8e, 0x7c, 0xff, 0x52, 0x8e, 0x7b, 0xff,
+ 0x4a, 0x8a, 0x76, 0xff, 0x42, 0x85, 0x70, 0xff,
+ 0x40, 0x82, 0x71, 0xff, 0x45, 0x86, 0x76, 0xff,
+ 0x3f, 0x82, 0x71, 0xff, 0x44, 0x85, 0x76, 0xff,
+ 0x42, 0x82, 0x74, 0xff, 0x42, 0x81, 0x73, 0xff,
+ 0x42, 0x82, 0x74, 0xff, 0x37, 0x7c, 0x6b, 0xff,
+ 0x32, 0x7a, 0x63, 0xff, 0x29, 0x73, 0x5d, 0xff,
+ 0x32, 0x7a, 0x63, 0xff, 0x31, 0x79, 0x63, 0xff,
+ 0x35, 0x76, 0x5e, 0xff, 0x2f, 0x71, 0x58, 0xff,
+ 0x3a, 0x7a, 0x63, 0xff, 0x39, 0x79, 0x63, 0xff,
+ 0x2c, 0x72, 0x5e, 0xff, 0x2c, 0x71, 0x5d, 0xff,
+ 0x42, 0x82, 0x74, 0xff, 0x37, 0x79, 0x68, 0xff,
+ 0x3a, 0x7b, 0x63, 0xff, 0x42, 0x81, 0x6b, 0xff,
+ 0x29, 0x6e, 0x53, 0xff, 0x39, 0x7b, 0x63, 0xff,
+ 0x45, 0x75, 0x60, 0xff, 0x3f, 0x7b, 0x65, 0xff,
+ 0x3f, 0x7b, 0x66, 0xff, 0x44, 0x74, 0x60, 0xff,
+ 0x40, 0x75, 0x5e, 0xff, 0x3f, 0x74, 0x5d, 0xff,
+ 0x4a, 0x7e, 0x63, 0xff, 0x3f, 0x74, 0x5d, 0xff,
+ 0x32, 0x63, 0x50, 0xff, 0x42, 0x78, 0x65, 0xff,
+ 0x42, 0x78, 0x66, 0xff, 0x42, 0x78, 0x65, 0xff,
+ 0x3d, 0x83, 0x6b, 0xff, 0x37, 0x7c, 0x63, 0xff,
+ 0x32, 0x76, 0x5b, 0xff, 0x3c, 0x83, 0x6b, 0xff,
+ 0x40, 0x87, 0x71, 0xff, 0x3f, 0x87, 0x70, 0xff,
+ 0x3f, 0x87, 0x71, 0xff, 0x3f, 0x87, 0x70, 0xff,
+ 0x63, 0x96, 0x84, 0xff, 0x52, 0x8d, 0x78, 0xff,
+ 0x52, 0x8e, 0x79, 0xff, 0x5a, 0x91, 0x7e, 0xff,
+ 0x58, 0x8f, 0x84, 0xff, 0x4c, 0x88, 0x7b, 0xff,
+ 0x42, 0x82, 0x73, 0xff, 0x42, 0x81, 0x73, 0xff,
+ 0x52, 0x8e, 0x7e, 0xff, 0x41, 0x85, 0x73, 0xff,
+ 0x5b, 0x92, 0x84, 0xff, 0x5a, 0x91, 0x83, 0xff,
+ 0x5d, 0x93, 0x84, 0xff, 0x6b, 0x99, 0x8b, 0xff,
+ 0x5d, 0x93, 0x84, 0xff, 0x4f, 0x8c, 0x7b, 0xff,
+ 0x52, 0x8e, 0x7b, 0xff, 0x52, 0x8d, 0x7b, 0xff,
+ 0x42, 0x86, 0x71, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x45, 0x86, 0x76, 0xff, 0x44, 0x85, 0x75, 0xff,
+ 0x3f, 0x82, 0x71, 0xff, 0x3f, 0x81, 0x70, 0xff,
+ 0x42, 0x82, 0x73, 0xff, 0x2b, 0x76, 0x62, 0xff,
+ 0x37, 0x7c, 0x6b, 0xff, 0x2c, 0x76, 0x62, 0xff,
+ 0x31, 0x7a, 0x63, 0xff, 0x29, 0x72, 0x5d, 0xff,
+ 0x29, 0x73, 0x5d, 0xff, 0x29, 0x72, 0x5d, 0xff,
+ 0x34, 0x75, 0x5d, 0xff, 0x2e, 0x71, 0x57, 0xff,
+ 0x2f, 0x72, 0x58, 0xff, 0x39, 0x79, 0x62, 0xff,
+ 0x37, 0x7a, 0x68, 0xff, 0x20, 0x69, 0x52, 0xff,
+ 0x2c, 0x72, 0x5d, 0xff, 0x37, 0x79, 0x68, 0xff,
+ 0x3a, 0x7b, 0x63, 0xff, 0x41, 0x81, 0x6b, 0xff,
+ 0x3a, 0x7b, 0x63, 0xff, 0x29, 0x6d, 0x52, 0xff,
+ 0x45, 0x74, 0x60, 0xff, 0x3f, 0x7a, 0x65, 0xff,
+ 0x4a, 0x6e, 0x5b, 0xff, 0x44, 0x74, 0x60, 0xff,
+ 0x3f, 0x74, 0x5d, 0xff, 0x34, 0x6a, 0x57, 0xff,
+ 0x4a, 0x7e, 0x63, 0xff, 0x3f, 0x74, 0x5d, 0xff,
+ 0x52, 0x8e, 0x7b, 0xff, 0x41, 0x78, 0x65, 0xff,
+ 0x42, 0x78, 0x66, 0xff, 0x42, 0x78, 0x65, 0xff,
+ 0x42, 0x8a, 0x73, 0xff, 0x41, 0x89, 0x73, 0xff,
+ 0x42, 0x8a, 0x73, 0xff, 0x3c, 0x83, 0x6b, 0xff,
+ 0x34, 0x7c, 0x66, 0xff, 0x34, 0x7c, 0x65, 0xff,
+ 0x4a, 0x92, 0x7c, 0xff, 0x4a, 0x91, 0x7b, 0xff,
+ 0x63, 0x96, 0x84, 0xff, 0x62, 0x96, 0x83, 0xff,
+ 0x63, 0x96, 0x84, 0xff, 0x5a, 0x92, 0x7e, 0xff,
+ 0x63, 0x96, 0x8c, 0xff, 0x58, 0x8f, 0x83, 0xff,
+ 0x58, 0x8f, 0x84, 0xff, 0x58, 0x8f, 0x84, 0xff,
+ 0x5b, 0x92, 0x84, 0xff, 0x4a, 0x89, 0x78, 0xff,
+ 0x4a, 0x8a, 0x79, 0xff, 0x52, 0x8e, 0x7e, 0xff,
+ 0x50, 0x8d, 0x7c, 0xff, 0x4f, 0x8c, 0x7b, 0xff,
+ 0x50, 0x8d, 0x7c, 0xff, 0x4f, 0x8c, 0x7b, 0xff,
+ 0x4a, 0x8a, 0x76, 0xff, 0x4a, 0x89, 0x76, 0xff,
+ 0x3a, 0x82, 0x6b, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x45, 0x86, 0x76, 0xff, 0x44, 0x85, 0x76, 0xff,
+ 0x3f, 0x82, 0x71, 0xff, 0x3f, 0x81, 0x70, 0xff,
+ 0x2c, 0x77, 0x63, 0xff, 0x2c, 0x77, 0x62, 0xff,
+ 0x2c, 0x77, 0x63, 0xff, 0x21, 0x71, 0x5a, 0xff,
+ 0x21, 0x6c, 0x58, 0xff, 0x21, 0x6c, 0x58, 0xff,
+ 0x2a, 0x73, 0x5e, 0xff, 0x31, 0x79, 0x63, 0xff,
+ 0x34, 0x76, 0x5e, 0xff, 0x34, 0x75, 0x5d, 0xff,
+ 0x35, 0x76, 0x5e, 0xff, 0x39, 0x79, 0x63, 0xff,
+ 0x37, 0x7a, 0x68, 0xff, 0x2c, 0x71, 0x5d, 0xff,
+ 0x2c, 0x72, 0x5e, 0xff, 0x21, 0x69, 0x52, 0xff,
+ 0x32, 0x74, 0x5b, 0xff, 0x39, 0x7b, 0x62, 0xff,
+ 0x3a, 0x7b, 0x63, 0xff, 0x39, 0x7b, 0x63, 0xff,
+ 0x3f, 0x7b, 0x66, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x3f, 0x7b, 0x66, 0xff, 0x44, 0x74, 0x60, 0xff,
+ 0x3f, 0x74, 0x5e, 0xff, 0x3f, 0x74, 0x5d, 0xff,
+ 0x4a, 0x7e, 0x63, 0xff, 0x3f, 0x74, 0x5d, 0xff,
+ 0x53, 0x8e, 0x7c, 0xff, 0x52, 0x8d, 0x7b, 0xff,
+ 0x42, 0x78, 0x66, 0xff, 0x42, 0x78, 0x65, 0xff,
+ 0x42, 0x8a, 0x73, 0xff, 0x42, 0x89, 0x73, 0xff,
+ 0x37, 0x7d, 0x63, 0xff, 0x37, 0x7c, 0x63, 0xff,
+ 0x29, 0x72, 0x5b, 0xff, 0x29, 0x71, 0x5a, 0xff,
+ 0x35, 0x7d, 0x66, 0xff, 0x34, 0x7c, 0x65, 0xff,
+ 0x52, 0x8e, 0x79, 0xff, 0x52, 0x8d, 0x78, 0xff,
+ 0x5b, 0x92, 0x7e, 0xff, 0x62, 0x95, 0x83, 0xff,
+ 0x63, 0x96, 0x8c, 0xff, 0x57, 0x8f, 0x83, 0xff,
+ 0x58, 0x8f, 0x84, 0xff, 0x57, 0x8f, 0x83, 0xff,
+ 0x52, 0x8e, 0x7e, 0xff, 0x52, 0x8d, 0x7e, 0xff,
+ 0x4a, 0x8a, 0x79, 0xff, 0x4a, 0x89, 0x78, 0xff,
+ 0x50, 0x8c, 0x7c, 0xff, 0x4f, 0x8c, 0x7b, 0xff,
+ 0x42, 0x86, 0x73, 0xff, 0x4f, 0x8c, 0x7b, 0xff,
+ 0x4a, 0x8a, 0x76, 0xff, 0x4a, 0x89, 0x76, 0xff,
+ 0x4a, 0x8a, 0x76, 0xff, 0x4a, 0x89, 0x75, 0xff,
+ 0x45, 0x86, 0x76, 0xff, 0x44, 0x85, 0x76, 0xff,
+ 0x45, 0x86, 0x76, 0xff, 0x39, 0x7d, 0x6a, 0xff,
+ 0x2c, 0x77, 0x63, 0xff, 0x2c, 0x76, 0x62, 0xff,
+ 0x2c, 0x77, 0x63, 0xff, 0x2b, 0x76, 0x62, 0xff,
+ 0x19, 0x65, 0x52, 0xff, 0x21, 0x6c, 0x57, 0xff,
+ 0x19, 0x65, 0x52, 0xff, 0x18, 0x65, 0x52, 0xff,
+ 0x29, 0x6d, 0x52, 0xff, 0x34, 0x75, 0x5d, 0xff,
+ 0x3a, 0x79, 0x63, 0xff, 0x34, 0x75, 0x5d, 0xff,
+ 0x37, 0x7a, 0x68, 0xff, 0x41, 0x81, 0x73, 0xff,
+ 0x37, 0x79, 0x68, 0xff, 0x36, 0x79, 0x68, 0xff,
+ 0x3a, 0x7b, 0x63, 0xff, 0x39, 0x7a, 0x62, 0xff,
+ 0x29, 0x6d, 0x52, 0xff, 0x39, 0x7a, 0x62, 0xff,
+ 0x3f, 0x7b, 0x66, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x3a, 0x82, 0x6b, 0xff, 0x39, 0x81, 0x6a, 0xff,
+ 0x3f, 0x74, 0x5d, 0xff, 0x29, 0x61, 0x52, 0xff,
+ 0x4a, 0x7e, 0x63, 0xff, 0x3f, 0x74, 0x5d, 0xff,
+ 0x32, 0x63, 0x50, 0xff, 0x21, 0x4d, 0x39, 0xff,
+ 0x21, 0x4d, 0x3a, 0xff, 0x31, 0x62, 0x4f, 0xff,
+ 0x37, 0x7c, 0x63, 0xff, 0x41, 0x89, 0x73, 0xff,
+ 0x42, 0x8a, 0x73, 0xff, 0x3c, 0x82, 0x6a, 0xff,
+ 0x3f, 0x87, 0x71, 0xff, 0x3f, 0x87, 0x70, 0xff,
+ 0x3f, 0x87, 0x70, 0xff, 0x34, 0x7c, 0x65, 0xff,
+ 0x4d, 0x8e, 0x79, 0xff, 0x42, 0x8a, 0x73, 0xff,
+ 0x42, 0x8a, 0x74, 0xff, 0x42, 0x89, 0x73, 0xff,
+ 0x45, 0x89, 0x74, 0xff, 0x45, 0x88, 0x73, 0xff,
+ 0x45, 0x89, 0x74, 0xff, 0x4f, 0x8f, 0x7b, 0xff,
+ 0x50, 0x8b, 0x7c, 0xff, 0x3a, 0x7d, 0x6b, 0xff,
+ 0x45, 0x85, 0x74, 0xff, 0x39, 0x7d, 0x6b, 0xff,
+ 0x2a, 0x6e, 0x5b, 0xff, 0x34, 0x77, 0x65, 0xff,
+ 0x3f, 0x81, 0x71, 0xff, 0x3f, 0x80, 0x70, 0xff,
+ 0x42, 0x7e, 0x74, 0xff, 0x42, 0x7d, 0x73, 0xff,
+ 0x4d, 0x8b, 0x7e, 0xff, 0x47, 0x84, 0x78, 0xff,
+ 0x32, 0x7b, 0x6b, 0xff, 0x31, 0x7b, 0x6b, 0xff,
+ 0x32, 0x7b, 0x6b, 0xff, 0x29, 0x75, 0x63, 0xff,
+ 0x19, 0x66, 0x53, 0xff, 0x24, 0x6c, 0x5a, 0xff,
+ 0x24, 0x6c, 0x5b, 0xff, 0x2e, 0x73, 0x63, 0xff,
+ 0x32, 0x76, 0x63, 0xff, 0x26, 0x69, 0x58, 0xff,
+ 0x11, 0x51, 0x42, 0xff, 0x1b, 0x5d, 0x4d, 0xff,
+ 0x21, 0x6a, 0x53, 0xff, 0x29, 0x70, 0x5a, 0xff,
+ 0x32, 0x77, 0x63, 0xff, 0x31, 0x77, 0x63, 0xff,
+ 0x32, 0x7a, 0x63, 0xff, 0x31, 0x79, 0x63, 0xff,
+ 0x32, 0x7a, 0x63, 0xff, 0x31, 0x79, 0x63, 0xff,
+ 0x3a, 0x82, 0x6b, 0xff, 0x2f, 0x74, 0x60, 0xff,
+ 0x29, 0x6e, 0x5b, 0xff, 0x29, 0x6d, 0x5a, 0xff,
+ 0x2c, 0x79, 0x60, 0xff, 0x31, 0x81, 0x6b, 0xff,
+ 0x32, 0x82, 0x6b, 0xff, 0x31, 0x81, 0x6b, 0xff,
+ 0x32, 0x7e, 0x66, 0xff, 0x29, 0x71, 0x58, 0xff,
+ 0x29, 0x72, 0x58, 0xff, 0x21, 0x65, 0x4a, 0xff,
+ 0x24, 0x49, 0x35, 0xff, 0x19, 0x2c, 0x19, 0xff,
+ 0x19, 0x2d, 0x19, 0xff, 0x23, 0x49, 0x34, 0xff,
+ 0x19, 0x55, 0x3a, 0xff, 0x24, 0x68, 0x4f, 0xff,
+ 0x3a, 0x8e, 0x7c, 0xff, 0x39, 0x8e, 0x7b, 0xff,
+ 0x40, 0x86, 0x71, 0xff, 0x45, 0x8a, 0x76, 0xff,
+ 0x3f, 0x86, 0x71, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x58, 0x92, 0x7e, 0xff, 0x4c, 0x8d, 0x78, 0xff,
+ 0x4d, 0x8e, 0x79, 0xff, 0x42, 0x89, 0x73, 0xff,
+ 0x45, 0x88, 0x73, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x45, 0x88, 0x73, 0xff, 0x44, 0x88, 0x73, 0xff,
+ 0x45, 0x84, 0x73, 0xff, 0x5a, 0x91, 0x83, 0xff,
+ 0x5b, 0x92, 0x84, 0xff, 0x44, 0x84, 0x73, 0xff,
+ 0x29, 0x6d, 0x5b, 0xff, 0x34, 0x76, 0x65, 0xff,
+ 0x4a, 0x8a, 0x7c, 0xff, 0x4a, 0x89, 0x7b, 0xff,
+ 0x42, 0x7e, 0x73, 0xff, 0x47, 0x84, 0x78, 0xff,
+ 0x4d, 0x8b, 0x7e, 0xff, 0x47, 0x84, 0x78, 0xff,
+ 0x42, 0x86, 0x7b, 0xff, 0x29, 0x75, 0x62, 0xff,
+ 0x29, 0x76, 0x63, 0xff, 0x39, 0x80, 0x73, 0xff,
+ 0x2f, 0x73, 0x63, 0xff, 0x2e, 0x72, 0x62, 0xff,
+ 0x19, 0x65, 0x52, 0xff, 0x23, 0x6c, 0x5a, 0xff,
+ 0x31, 0x75, 0x63, 0xff, 0x26, 0x69, 0x57, 0xff,
+ 0x1c, 0x5d, 0x4d, 0xff, 0x26, 0x69, 0x57, 0xff,
+ 0x29, 0x70, 0x5b, 0xff, 0x31, 0x76, 0x62, 0xff,
+ 0x32, 0x77, 0x63, 0xff, 0x29, 0x70, 0x5a, 0xff,
+ 0x21, 0x65, 0x52, 0xff, 0x20, 0x65, 0x52, 0xff,
+ 0x2c, 0x73, 0x5d, 0xff, 0x2c, 0x72, 0x5d, 0xff,
+ 0x2f, 0x74, 0x60, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x34, 0x7b, 0x66, 0xff, 0x29, 0x6d, 0x5a, 0xff,
+ 0x21, 0x65, 0x4a, 0xff, 0x26, 0x6e, 0x55, 0xff,
+ 0x32, 0x82, 0x6b, 0xff, 0x31, 0x81, 0x6b, 0xff,
+ 0x31, 0x7e, 0x66, 0xff, 0x39, 0x89, 0x73, 0xff,
+ 0x3a, 0x8a, 0x73, 0xff, 0x39, 0x89, 0x73, 0xff,
+ 0x3a, 0x82, 0x6b, 0xff, 0x2e, 0x65, 0x4f, 0xff,
+ 0x2f, 0x65, 0x50, 0xff, 0x2e, 0x65, 0x4f, 0xff,
+ 0x24, 0x68, 0x50, 0xff, 0x23, 0x67, 0x4f, 0xff,
+ 0x2f, 0x7b, 0x66, 0xff, 0x39, 0x8d, 0x7b, 0xff,
+ 0x45, 0x8a, 0x76, 0xff, 0x44, 0x89, 0x75, 0xff,
+ 0x3f, 0x86, 0x71, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x4d, 0x8e, 0x79, 0xff, 0x58, 0x91, 0x7e, 0xff,
+ 0x4d, 0x8e, 0x79, 0xff, 0x4d, 0x8e, 0x79, 0xff,
+ 0x50, 0x8f, 0x7c, 0xff, 0x44, 0x88, 0x73, 0xff,
+ 0x45, 0x89, 0x74, 0xff, 0x44, 0x88, 0x73, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x5a, 0x91, 0x83, 0xff,
+ 0x5b, 0x92, 0x84, 0xff, 0x4f, 0x8b, 0x7b, 0xff,
+ 0x3f, 0x80, 0x71, 0xff, 0x34, 0x77, 0x65, 0xff,
+ 0x4a, 0x8a, 0x7c, 0xff, 0x4a, 0x8a, 0x7b, 0xff,
+ 0x42, 0x7e, 0x73, 0xff, 0x4d, 0x8b, 0x7e, 0xff,
+ 0x48, 0x85, 0x79, 0xff, 0x4d, 0x8b, 0x7e, 0xff,
+ 0x3a, 0x80, 0x73, 0xff, 0x31, 0x7b, 0x6b, 0xff,
+ 0x3a, 0x81, 0x74, 0xff, 0x39, 0x80, 0x73, 0xff,
+ 0x3a, 0x7a, 0x6b, 0xff, 0x39, 0x79, 0x6b, 0xff,
+ 0x3a, 0x7a, 0x6b, 0xff, 0x2f, 0x73, 0x63, 0xff,
+ 0x32, 0x76, 0x63, 0xff, 0x26, 0x69, 0x58, 0xff,
+ 0x27, 0x6a, 0x58, 0xff, 0x26, 0x69, 0x58, 0xff,
+ 0x32, 0x77, 0x63, 0xff, 0x31, 0x77, 0x62, 0xff,
+ 0x32, 0x77, 0x63, 0xff, 0x31, 0x77, 0x63, 0xff,
+ 0x27, 0x6c, 0x58, 0xff, 0x2c, 0x72, 0x5d, 0xff,
+ 0x2c, 0x73, 0x5e, 0xff, 0x2c, 0x73, 0x5d, 0xff,
+ 0x34, 0x7b, 0x66, 0xff, 0x34, 0x7b, 0x65, 0xff,
+ 0x2f, 0x74, 0x60, 0xff, 0x2f, 0x74, 0x60, 0xff,
+ 0x27, 0x6f, 0x55, 0xff, 0x21, 0x65, 0x4a, 0xff,
+ 0x21, 0x66, 0x4a, 0xff, 0x31, 0x81, 0x6b, 0xff,
+ 0x32, 0x7e, 0x66, 0xff, 0x29, 0x71, 0x58, 0xff,
+ 0x32, 0x7e, 0x66, 0xff, 0x31, 0x7d, 0x65, 0xff,
+ 0x3a, 0x82, 0x6b, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x3a, 0x82, 0x6b, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x2f, 0x7b, 0x66, 0xff, 0x2e, 0x7b, 0x65, 0xff,
+ 0x2f, 0x7b, 0x66, 0xff, 0x2f, 0x7b, 0x65, 0xff,
+ 0x3f, 0x86, 0x71, 0xff, 0x3f, 0x85, 0x70, 0xff,
+ 0x45, 0x8a, 0x76, 0xff, 0x44, 0x8a, 0x76, 0xff,
+ 0x63, 0x96, 0x84, 0xff, 0x57, 0x91, 0x7e, 0xff,
+ 0x4d, 0x8e, 0x79, 0xff, 0x57, 0x91, 0x7e, 0xff,
+ 0x50, 0x8f, 0x7c, 0xff, 0x4f, 0x8f, 0x7b, 0xff,
+ 0x50, 0x8f, 0x7b, 0xff, 0x5a, 0x95, 0x83, 0xff,
+ 0x5b, 0x92, 0x84, 0xff, 0x4f, 0x8b, 0x7b, 0xff,
+ 0x50, 0x8b, 0x7b, 0xff, 0x4f, 0x8a, 0x7b, 0xff,
+ 0x4a, 0x8a, 0x7c, 0xff, 0x4a, 0x89, 0x7b, 0xff,
+ 0x4a, 0x8a, 0x7b, 0xff, 0x3f, 0x80, 0x70, 0xff,
+ 0x47, 0x84, 0x79, 0xff, 0x52, 0x91, 0x83, 0xff,
+ 0x47, 0x84, 0x79, 0xff, 0x41, 0x7d, 0x73, 0xff,
+ 0x32, 0x7b, 0x6b, 0xff, 0x31, 0x7a, 0x6b, 0xff,
+ 0x3a, 0x80, 0x73, 0xff, 0x31, 0x7a, 0x6a, 0xff,
+ 0x2f, 0x73, 0x63, 0xff, 0x39, 0x79, 0x6b, 0xff,
+ 0x2f, 0x73, 0x63, 0xff, 0x2e, 0x72, 0x62, 0xff,
+ 0x32, 0x76, 0x63, 0xff, 0x31, 0x75, 0x62, 0xff,
+ 0x26, 0x69, 0x58, 0xff, 0x31, 0x75, 0x62, 0xff,
+ 0x32, 0x77, 0x63, 0xff, 0x31, 0x76, 0x62, 0xff,
+ 0x29, 0x70, 0x5b, 0xff, 0x39, 0x7d, 0x6a, 0xff,
+ 0x27, 0x6c, 0x58, 0xff, 0x26, 0x6c, 0x57, 0xff,
+ 0x21, 0x65, 0x52, 0xff, 0x2b, 0x72, 0x5d, 0xff,
+ 0x34, 0x7b, 0x66, 0xff, 0x2e, 0x74, 0x60, 0xff,
+ 0x2f, 0x74, 0x60, 0xff, 0x34, 0x7a, 0x65, 0xff,
+ 0x2c, 0x78, 0x60, 0xff, 0x2c, 0x78, 0x60, 0xff,
+ 0x21, 0x65, 0x4a, 0xff, 0x2b, 0x78, 0x5f, 0xff,
+ 0x32, 0x7e, 0x66, 0xff, 0x29, 0x71, 0x57, 0xff,
+ 0x31, 0x7e, 0x65, 0xff, 0x31, 0x7d, 0x65, 0xff,
+ 0x3a, 0x82, 0x6b, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x3a, 0x82, 0x6b, 0xff, 0x39, 0x81, 0x6a, 0xff,
+ 0x3a, 0x8e, 0x7c, 0xff, 0x2e, 0x7a, 0x65, 0xff,
+ 0x2f, 0x7b, 0x65, 0xff, 0x39, 0x8d, 0x7b, 0xff,
+ 0x3a, 0x82, 0x6b, 0xff, 0x44, 0x89, 0x76, 0xff,
+ 0x4a, 0x8e, 0x7b, 0xff, 0x44, 0x89, 0x75, 0xff,
+ 0x53, 0x8b, 0x74, 0xff, 0x52, 0x8b, 0x73, 0xff,
+ 0x53, 0x8b, 0x74, 0xff, 0x5a, 0x96, 0x7b, 0xff,
+ 0x63, 0x96, 0x84, 0xff, 0x52, 0x8c, 0x79, 0xff,
+ 0x53, 0x8d, 0x79, 0xff, 0x52, 0x8c, 0x78, 0xff,
+ 0x4b, 0x8a, 0x7c, 0xff, 0x4a, 0x8a, 0x7b, 0xff,
+ 0x3f, 0x85, 0x71, 0xff, 0x4a, 0x89, 0x7b, 0xff,
+ 0x48, 0x87, 0x79, 0xff, 0x47, 0x87, 0x79, 0xff,
+ 0x48, 0x87, 0x79, 0xff, 0x31, 0x71, 0x63, 0xff,
+ 0x32, 0x72, 0x63, 0xff, 0x4a, 0x8a, 0x84, 0xff,
+ 0x42, 0x82, 0x79, 0xff, 0x39, 0x79, 0x6e, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x3a, 0x7d, 0x6b, 0xff,
+ 0x32, 0x72, 0x60, 0xff, 0x31, 0x71, 0x60, 0xff,
+ 0x32, 0x72, 0x5b, 0xff, 0x31, 0x71, 0x5a, 0xff,
+ 0x2c, 0x6b, 0x55, 0xff, 0x21, 0x5d, 0x4a, 0xff,
+ 0x21, 0x5e, 0x4b, 0xff, 0x2c, 0x6d, 0x5a, 0xff,
+ 0x27, 0x66, 0x53, 0xff, 0x2c, 0x6d, 0x5a, 0xff,
+ 0x3a, 0x72, 0x5b, 0xff, 0x3a, 0x71, 0x5a, 0xff,
+ 0x3a, 0x72, 0x5b, 0xff, 0x42, 0x7d, 0x63, 0xff,
+ 0x2f, 0x73, 0x5b, 0xff, 0x2f, 0x73, 0x5a, 0xff,
+ 0x29, 0x6a, 0x53, 0xff, 0x2e, 0x73, 0x5a, 0xff,
+ 0x32, 0x7a, 0x63, 0xff, 0x29, 0x61, 0x52, 0xff,
+ 0x2f, 0x72, 0x5e, 0xff, 0x31, 0x79, 0x63, 0xff,
+ 0x2c, 0x7b, 0x63, 0xff, 0x2c, 0x7b, 0x63, 0xff,
+ 0x2c, 0x7b, 0x63, 0xff, 0x2c, 0x7b, 0x63, 0xff,
+ 0x32, 0x7f, 0x6b, 0xff, 0x31, 0x7f, 0x6b, 0xff,
+ 0x29, 0x78, 0x63, 0xff, 0x21, 0x71, 0x5a, 0xff,
+ 0x2a, 0x7a, 0x63, 0xff, 0x2c, 0x7d, 0x68, 0xff,
+ 0x2c, 0x7e, 0x69, 0xff, 0x31, 0x85, 0x73, 0xff,
+ 0x3a, 0x8a, 0x7c, 0xff, 0x3a, 0x8a, 0x7b, 0xff,
+ 0x3a, 0x8a, 0x7c, 0xff, 0x34, 0x80, 0x6e, 0xff,
+ 0x3a, 0x83, 0x6b, 0xff, 0x42, 0x8a, 0x73, 0xff,
+ 0x42, 0x8a, 0x74, 0xff, 0x42, 0x89, 0x73, 0xff,
+ 0x5b, 0x96, 0x7b, 0xff, 0x52, 0x8b, 0x73, 0xff,
+ 0x5b, 0x96, 0x7c, 0xff, 0x52, 0x8b, 0x73, 0xff,
+ 0x63, 0x96, 0x84, 0xff, 0x41, 0x82, 0x6d, 0xff,
+ 0x42, 0x83, 0x6e, 0xff, 0x42, 0x83, 0x6d, 0xff,
+ 0x3f, 0x84, 0x71, 0xff, 0x44, 0x87, 0x75, 0xff,
+ 0x45, 0x87, 0x76, 0xff, 0x4a, 0x89, 0x7b, 0xff,
+ 0x47, 0x87, 0x79, 0xff, 0x52, 0x91, 0x83, 0xff,
+ 0x48, 0x87, 0x79, 0xff, 0x3c, 0x7c, 0x6d, 0xff,
+ 0x42, 0x82, 0x79, 0xff, 0x41, 0x81, 0x78, 0xff,
+ 0x32, 0x72, 0x63, 0xff, 0x39, 0x79, 0x6d, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x39, 0x7d, 0x6b, 0xff,
+ 0x29, 0x65, 0x55, 0xff, 0x29, 0x65, 0x55, 0xff,
+ 0x31, 0x71, 0x5b, 0xff, 0x31, 0x71, 0x5a, 0xff,
+ 0x32, 0x72, 0x5b, 0xff, 0x21, 0x5d, 0x4a, 0xff,
+ 0x21, 0x5d, 0x4a, 0xff, 0x26, 0x65, 0x52, 0xff,
+ 0x2c, 0x6e, 0x5b, 0xff, 0x2c, 0x6d, 0x5a, 0xff,
+ 0x3a, 0x71, 0x5b, 0xff, 0x31, 0x65, 0x52, 0xff,
+ 0x32, 0x65, 0x52, 0xff, 0x42, 0x7d, 0x62, 0xff,
+ 0x3a, 0x86, 0x6b, 0xff, 0x34, 0x7c, 0x62, 0xff,
+ 0x2f, 0x73, 0x5b, 0xff, 0x2e, 0x72, 0x5a, 0xff,
+ 0x2f, 0x71, 0x5d, 0xff, 0x2b, 0x69, 0x57, 0xff,
+ 0x32, 0x7a, 0x63, 0xff, 0x31, 0x79, 0x62, 0xff,
+ 0x26, 0x74, 0x5b, 0xff, 0x2b, 0x7a, 0x62, 0xff,
+ 0x32, 0x82, 0x6b, 0xff, 0x31, 0x81, 0x6b, 0xff,
+ 0x31, 0x7f, 0x6b, 0xff, 0x29, 0x78, 0x62, 0xff,
+ 0x3a, 0x86, 0x73, 0xff, 0x31, 0x7f, 0x6b, 0xff,
+ 0x29, 0x7a, 0x63, 0xff, 0x2b, 0x7d, 0x68, 0xff,
+ 0x2f, 0x82, 0x6e, 0xff, 0x29, 0x79, 0x62, 0xff,
+ 0x34, 0x80, 0x6e, 0xff, 0x2e, 0x76, 0x60, 0xff,
+ 0x3a, 0x8a, 0x7c, 0xff, 0x34, 0x80, 0x6d, 0xff,
+ 0x29, 0x75, 0x5b, 0xff, 0x29, 0x75, 0x5a, 0xff,
+ 0x32, 0x7c, 0x63, 0xff, 0x39, 0x83, 0x6b, 0xff,
+ 0x53, 0x8b, 0x73, 0xff, 0x5a, 0x96, 0x7b, 0xff,
+ 0x53, 0x8b, 0x74, 0xff, 0x52, 0x8b, 0x73, 0xff,
+ 0x53, 0x8d, 0x79, 0xff, 0x52, 0x8c, 0x78, 0xff,
+ 0x53, 0x8d, 0x79, 0xff, 0x52, 0x8c, 0x79, 0xff,
+ 0x3f, 0x85, 0x71, 0xff, 0x44, 0x87, 0x76, 0xff,
+ 0x3a, 0x82, 0x6b, 0xff, 0x3f, 0x84, 0x70, 0xff,
+ 0x48, 0x87, 0x79, 0xff, 0x52, 0x91, 0x83, 0xff,
+ 0x48, 0x87, 0x79, 0xff, 0x3c, 0x7c, 0x6e, 0xff,
+ 0x42, 0x82, 0x79, 0xff, 0x42, 0x81, 0x78, 0xff,
+ 0x3a, 0x7a, 0x6e, 0xff, 0x42, 0x81, 0x79, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x31, 0x71, 0x60, 0xff,
+ 0x21, 0x59, 0x4a, 0xff, 0x21, 0x59, 0x4a, 0xff,
+ 0x32, 0x72, 0x5b, 0xff, 0x31, 0x71, 0x5a, 0xff,
+ 0x32, 0x72, 0x5b, 0xff, 0x26, 0x64, 0x4f, 0xff,
+ 0x27, 0x65, 0x53, 0xff, 0x2c, 0x6d, 0x5a, 0xff,
+ 0x2c, 0x6e, 0x5b, 0xff, 0x26, 0x65, 0x52, 0xff,
+ 0x3a, 0x72, 0x5b, 0xff, 0x39, 0x71, 0x5a, 0xff,
+ 0x32, 0x66, 0x53, 0xff, 0x42, 0x7d, 0x63, 0xff,
+ 0x2f, 0x73, 0x5b, 0xff, 0x2e, 0x72, 0x5a, 0xff,
+ 0x35, 0x7d, 0x63, 0xff, 0x2f, 0x73, 0x5a, 0xff,
+ 0x2f, 0x72, 0x5e, 0xff, 0x2e, 0x71, 0x5d, 0xff,
+ 0x2f, 0x72, 0x5e, 0xff, 0x2f, 0x71, 0x5d, 0xff,
+ 0x21, 0x6e, 0x53, 0xff, 0x21, 0x6d, 0x52, 0xff,
+ 0x21, 0x6e, 0x53, 0xff, 0x31, 0x81, 0x6b, 0xff,
+ 0x32, 0x7f, 0x6b, 0xff, 0x31, 0x7f, 0x6b, 0xff,
+ 0x3a, 0x86, 0x74, 0xff, 0x31, 0x7f, 0x6b, 0xff,
+ 0x2f, 0x82, 0x6e, 0xff, 0x2e, 0x81, 0x6d, 0xff,
+ 0x2c, 0x7e, 0x69, 0xff, 0x29, 0x79, 0x63, 0xff,
+ 0x2f, 0x77, 0x60, 0xff, 0x29, 0x6d, 0x52, 0xff,
+ 0x2f, 0x77, 0x60, 0xff, 0x2f, 0x77, 0x60, 0xff,
+ 0x3a, 0x83, 0x6b, 0xff, 0x29, 0x75, 0x5a, 0xff,
+ 0x2a, 0x76, 0x5b, 0xff, 0x39, 0x83, 0x6b, 0xff,
+ 0x5b, 0x96, 0x7c, 0xff, 0x4a, 0x80, 0x6b, 0xff,
+ 0x42, 0x75, 0x63, 0xff, 0x4a, 0x80, 0x6a, 0xff,
+ 0x32, 0x7a, 0x63, 0xff, 0x41, 0x83, 0x6d, 0xff,
+ 0x52, 0x8c, 0x79, 0xff, 0x52, 0x8c, 0x78, 0xff,
+ 0x3f, 0x84, 0x71, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x45, 0x87, 0x76, 0xff, 0x44, 0x86, 0x75, 0xff,
+ 0x3c, 0x7c, 0x6e, 0xff, 0x47, 0x87, 0x78, 0xff,
+ 0x47, 0x87, 0x79, 0xff, 0x47, 0x86, 0x78, 0xff,
+ 0x42, 0x82, 0x79, 0xff, 0x41, 0x81, 0x78, 0xff,
+ 0x42, 0x82, 0x79, 0xff, 0x31, 0x71, 0x62, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x31, 0x71, 0x60, 0xff,
+ 0x21, 0x59, 0x4a, 0xff, 0x20, 0x59, 0x4a, 0xff,
+ 0x27, 0x64, 0x50, 0xff, 0x31, 0x71, 0x5a, 0xff,
+ 0x2c, 0x6b, 0x55, 0xff, 0x31, 0x71, 0x5a, 0xff,
+ 0x32, 0x76, 0x63, 0xff, 0x2c, 0x6d, 0x5a, 0xff,
+ 0x26, 0x65, 0x52, 0xff, 0x20, 0x5d, 0x4a, 0xff,
+ 0x32, 0x65, 0x52, 0xff, 0x31, 0x65, 0x52, 0xff,
+ 0x29, 0x59, 0x4a, 0xff, 0x39, 0x71, 0x5a, 0xff,
+ 0x2f, 0x73, 0x5b, 0xff, 0x29, 0x69, 0x52, 0xff,
+ 0x2f, 0x73, 0x5b, 0xff, 0x2e, 0x72, 0x5a, 0xff,
+ 0x2c, 0x69, 0x58, 0xff, 0x31, 0x79, 0x62, 0xff,
+ 0x31, 0x79, 0x63, 0xff, 0x2e, 0x71, 0x5d, 0xff,
+ 0x21, 0x6d, 0x52, 0xff, 0x26, 0x74, 0x5a, 0xff,
+ 0x26, 0x74, 0x5b, 0xff, 0x20, 0x6d, 0x52, 0xff,
+ 0x29, 0x78, 0x63, 0xff, 0x21, 0x71, 0x5a, 0xff,
+ 0x31, 0x7f, 0x6b, 0xff, 0x39, 0x85, 0x73, 0xff,
+ 0x32, 0x86, 0x73, 0xff, 0x31, 0x85, 0x73, 0xff,
+ 0x2c, 0x7e, 0x68, 0xff, 0x2e, 0x81, 0x6d, 0xff,
+ 0x2f, 0x77, 0x60, 0xff, 0x29, 0x6d, 0x52, 0xff,
+ 0x29, 0x6d, 0x52, 0xff, 0x29, 0x6d, 0x52, 0xff,
+ 0x3a, 0x83, 0x6b, 0xff, 0x41, 0x89, 0x73, 0xff,
+ 0x29, 0x75, 0x5b, 0xff, 0x31, 0x7c, 0x62, 0xff,
+ 0x5b, 0x92, 0x7c, 0xff, 0x45, 0x84, 0x70, 0xff,
+ 0x45, 0x85, 0x71, 0xff, 0x44, 0x84, 0x70, 0xff,
+ 0x4b, 0x87, 0x79, 0xff, 0x4a, 0x87, 0x79, 0xff,
+ 0x42, 0x82, 0x74, 0xff, 0x42, 0x81, 0x73, 0xff,
+ 0x42, 0x81, 0x71, 0xff, 0x4a, 0x87, 0x76, 0xff,
+ 0x4a, 0x87, 0x76, 0xff, 0x4a, 0x87, 0x76, 0xff,
+ 0x4b, 0x8a, 0x74, 0xff, 0x42, 0x7d, 0x6b, 0xff,
+ 0x45, 0x82, 0x6e, 0xff, 0x4a, 0x89, 0x73, 0xff,
+ 0x42, 0x86, 0x74, 0xff, 0x42, 0x86, 0x73, 0xff,
+ 0x3d, 0x7e, 0x6b, 0xff, 0x37, 0x75, 0x63, 0xff,
+ 0x42, 0x7e, 0x6b, 0xff, 0x3a, 0x77, 0x65, 0xff,
+ 0x29, 0x6a, 0x5b, 0xff, 0x29, 0x69, 0x5a, 0xff,
+ 0x21, 0x66, 0x53, 0xff, 0x3a, 0x79, 0x63, 0xff,
+ 0x29, 0x6c, 0x58, 0xff, 0x31, 0x73, 0x5d, 0xff,
+ 0x3a, 0x72, 0x5b, 0xff, 0x3a, 0x71, 0x5a, 0xff,
+ 0x3a, 0x72, 0x5b, 0xff, 0x39, 0x71, 0x5a, 0xff,
+ 0x4b, 0x7a, 0x6b, 0xff, 0x34, 0x69, 0x55, 0xff,
+ 0x29, 0x61, 0x4a, 0xff, 0x34, 0x69, 0x55, 0xff,
+ 0x2f, 0x6c, 0x53, 0xff, 0x29, 0x65, 0x4a, 0xff,
+ 0x2f, 0x6c, 0x53, 0xff, 0x2e, 0x6c, 0x52, 0xff,
+ 0x27, 0x6f, 0x55, 0xff, 0x2c, 0x78, 0x60, 0xff,
+ 0x2c, 0x78, 0x60, 0xff, 0x31, 0x81, 0x6b, 0xff,
+ 0x32, 0x76, 0x63, 0xff, 0x31, 0x75, 0x63, 0xff,
+ 0x32, 0x76, 0x63, 0xff, 0x2c, 0x6e, 0x5a, 0xff,
+ 0x2c, 0x76, 0x60, 0xff, 0x31, 0x81, 0x6b, 0xff,
+ 0x2c, 0x76, 0x60, 0xff, 0x31, 0x81, 0x6b, 0xff,
+ 0x3a, 0x83, 0x74, 0xff, 0x42, 0x8a, 0x7b, 0xff,
+ 0x3a, 0x83, 0x74, 0xff, 0x39, 0x83, 0x73, 0xff,
+ 0x32, 0x79, 0x63, 0xff, 0x31, 0x78, 0x63, 0xff,
+ 0x32, 0x78, 0x63, 0xff, 0x31, 0x78, 0x63, 0xff,
+ 0x3a, 0x7f, 0x69, 0xff, 0x42, 0x88, 0x76, 0xff,
+ 0x42, 0x89, 0x76, 0xff, 0x31, 0x75, 0x5a, 0xff,
+ 0x50, 0x8b, 0x76, 0xff, 0x4f, 0x8b, 0x75, 0xff,
+ 0x5b, 0x92, 0x7c, 0xff, 0x5a, 0x91, 0x7b, 0xff,
+ 0x52, 0x8c, 0x7e, 0xff, 0x52, 0x8c, 0x7e, 0xff,
+ 0x4a, 0x87, 0x79, 0xff, 0x42, 0x81, 0x73, 0xff,
+ 0x4a, 0x87, 0x76, 0xff, 0x52, 0x8d, 0x7b, 0xff,
+ 0x4a, 0x87, 0x76, 0xff, 0x42, 0x80, 0x70, 0xff,
+ 0x47, 0x86, 0x71, 0xff, 0x44, 0x81, 0x6d, 0xff,
+ 0x4a, 0x8a, 0x73, 0xff, 0x44, 0x81, 0x6d, 0xff,
+ 0x37, 0x75, 0x63, 0xff, 0x3c, 0x7d, 0x6b, 0xff,
+ 0x42, 0x86, 0x73, 0xff, 0x42, 0x85, 0x73, 0xff,
+ 0x3a, 0x77, 0x66, 0xff, 0x41, 0x7d, 0x6b, 0xff,
+ 0x3a, 0x77, 0x66, 0xff, 0x29, 0x69, 0x5a, 0xff,
+ 0x29, 0x6c, 0x58, 0xff, 0x31, 0x72, 0x5d, 0xff,
+ 0x21, 0x65, 0x52, 0xff, 0x29, 0x6c, 0x57, 0xff,
+ 0x2c, 0x5f, 0x4a, 0xff, 0x2b, 0x5e, 0x4a, 0xff,
+ 0x3a, 0x72, 0x5b, 0xff, 0x39, 0x71, 0x5a, 0xff,
+ 0x4a, 0x7a, 0x6b, 0xff, 0x4a, 0x79, 0x6b, 0xff,
+ 0x4a, 0x7a, 0x6b, 0xff, 0x29, 0x61, 0x4a, 0xff,
+ 0x2f, 0x6c, 0x52, 0xff, 0x2e, 0x6c, 0x52, 0xff,
+ 0x29, 0x65, 0x4a, 0xff, 0x2e, 0x6c, 0x52, 0xff,
+ 0x26, 0x6f, 0x55, 0xff, 0x20, 0x65, 0x4a, 0xff,
+ 0x2c, 0x78, 0x60, 0xff, 0x31, 0x81, 0x6b, 0xff,
+ 0x2c, 0x6f, 0x5b, 0xff, 0x2b, 0x6e, 0x5a, 0xff,
+ 0x2c, 0x6f, 0x5b, 0xff, 0x21, 0x61, 0x4a, 0xff,
+ 0x26, 0x69, 0x55, 0xff, 0x31, 0x81, 0x6b, 0xff,
+ 0x2c, 0x76, 0x60, 0xff, 0x31, 0x81, 0x6b, 0xff,
+ 0x42, 0x8a, 0x7b, 0xff, 0x39, 0x82, 0x73, 0xff,
+ 0x3a, 0x83, 0x73, 0xff, 0x42, 0x89, 0x7b, 0xff,
+ 0x31, 0x78, 0x63, 0xff, 0x31, 0x78, 0x62, 0xff,
+ 0x42, 0x87, 0x73, 0xff, 0x42, 0x87, 0x73, 0xff,
+ 0x31, 0x75, 0x5b, 0xff, 0x31, 0x75, 0x5a, 0xff,
+ 0x42, 0x88, 0x76, 0xff, 0x42, 0x88, 0x76, 0xff,
+ 0x45, 0x85, 0x71, 0xff, 0x4f, 0x8b, 0x76, 0xff,
+ 0x50, 0x8b, 0x76, 0xff, 0x5a, 0x92, 0x7b, 0xff,
+ 0x5b, 0x92, 0x84, 0xff, 0x52, 0x8c, 0x7e, 0xff,
+ 0x5b, 0x92, 0x84, 0xff, 0x52, 0x8c, 0x7e, 0xff,
+ 0x53, 0x8e, 0x7c, 0xff, 0x52, 0x8d, 0x7b, 0xff,
+ 0x4a, 0x87, 0x76, 0xff, 0x4a, 0x87, 0x76, 0xff,
+ 0x48, 0x86, 0x71, 0xff, 0x44, 0x81, 0x6d, 0xff,
+ 0x48, 0x86, 0x71, 0xff, 0x44, 0x81, 0x6e, 0xff,
+ 0x32, 0x6e, 0x5b, 0xff, 0x31, 0x6d, 0x5a, 0xff,
+ 0x3d, 0x7e, 0x6b, 0xff, 0x3c, 0x7d, 0x6b, 0xff,
+ 0x3a, 0x77, 0x66, 0xff, 0x39, 0x77, 0x65, 0xff,
+ 0x3a, 0x77, 0x66, 0xff, 0x31, 0x70, 0x60, 0xff,
+ 0x3a, 0x7a, 0x63, 0xff, 0x39, 0x79, 0x62, 0xff,
+ 0x2a, 0x6c, 0x58, 0xff, 0x21, 0x65, 0x52, 0xff,
+ 0x1e, 0x4c, 0x3a, 0xff, 0x10, 0x38, 0x29, 0xff,
+ 0x2c, 0x5f, 0x4a, 0xff, 0x39, 0x71, 0x5a, 0xff,
+ 0x4a, 0x7a, 0x6b, 0xff, 0x34, 0x69, 0x55, 0xff,
+ 0x35, 0x6a, 0x55, 0xff, 0x29, 0x61, 0x4a, 0xff,
+ 0x29, 0x65, 0x4a, 0xff, 0x2e, 0x6c, 0x52, 0xff,
+ 0x2f, 0x6c, 0x53, 0xff, 0x39, 0x79, 0x63, 0xff,
+ 0x21, 0x65, 0x4a, 0xff, 0x21, 0x65, 0x4a, 0xff,
+ 0x27, 0x6f, 0x55, 0xff, 0x2c, 0x78, 0x60, 0xff,
+ 0x32, 0x76, 0x63, 0xff, 0x31, 0x75, 0x62, 0xff,
+ 0x2c, 0x6f, 0x5b, 0xff, 0x21, 0x61, 0x4a, 0xff,
+ 0x21, 0x5d, 0x4a, 0xff, 0x26, 0x69, 0x55, 0xff,
+ 0x27, 0x6a, 0x55, 0xff, 0x2c, 0x75, 0x60, 0xff,
+ 0x3a, 0x83, 0x73, 0xff, 0x31, 0x7c, 0x6b, 0xff,
+ 0x32, 0x7d, 0x6b, 0xff, 0x39, 0x83, 0x73, 0xff,
+ 0x32, 0x78, 0x63, 0xff, 0x21, 0x69, 0x52, 0xff,
+ 0x42, 0x87, 0x74, 0xff, 0x52, 0x96, 0x84, 0xff,
+ 0x42, 0x89, 0x76, 0xff, 0x31, 0x75, 0x5a, 0xff,
+ 0x32, 0x76, 0x5b, 0xff, 0x39, 0x7f, 0x68, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x39, 0x7d, 0x6b, 0xff,
+ 0x45, 0x84, 0x70, 0xff, 0x44, 0x84, 0x70, 0xff,
+ 0x52, 0x8c, 0x7e, 0xff, 0x52, 0x8c, 0x7e, 0xff,
+ 0x52, 0x8c, 0x7e, 0xff, 0x52, 0x8c, 0x7e, 0xff,
+ 0x4a, 0x87, 0x76, 0xff, 0x52, 0x8d, 0x7b, 0xff,
+ 0x42, 0x80, 0x70, 0xff, 0x39, 0x79, 0x6a, 0xff,
+ 0x4a, 0x8a, 0x73, 0xff, 0x41, 0x7d, 0x6b, 0xff,
+ 0x47, 0x86, 0x70, 0xff, 0x41, 0x7d, 0x6a, 0xff,
+ 0x37, 0x76, 0x63, 0xff, 0x31, 0x6d, 0x5a, 0xff,
+ 0x3c, 0x7e, 0x6b, 0xff, 0x36, 0x75, 0x62, 0xff,
+ 0x42, 0x7e, 0x6b, 0xff, 0x41, 0x7d, 0x6b, 0xff,
+ 0x3a, 0x77, 0x65, 0xff, 0x31, 0x70, 0x5f, 0xff,
+ 0x32, 0x73, 0x5d, 0xff, 0x39, 0x79, 0x62, 0xff,
+ 0x31, 0x73, 0x5d, 0xff, 0x20, 0x65, 0x52, 0xff,
+ 0x1e, 0x4c, 0x3a, 0xff, 0x1e, 0x4b, 0x39, 0xff,
+ 0x1e, 0x4c, 0x3a, 0xff, 0x1e, 0x4b, 0x39, 0xff,
+ 0x34, 0x69, 0x55, 0xff, 0x34, 0x69, 0x55, 0xff,
+ 0x34, 0x69, 0x55, 0xff, 0x29, 0x61, 0x4a, 0xff,
+ 0x29, 0x65, 0x4a, 0xff, 0x34, 0x72, 0x5a, 0xff,
+ 0x34, 0x73, 0x5b, 0xff, 0x34, 0x72, 0x5a, 0xff,
+ 0x27, 0x6f, 0x55, 0xff, 0x21, 0x65, 0x4a, 0xff,
+ 0x21, 0x65, 0x4a, 0xff, 0x26, 0x6e, 0x55, 0xff,
+ 0x32, 0x76, 0x63, 0xff, 0x2c, 0x6e, 0x5a, 0xff,
+ 0x31, 0x75, 0x63, 0xff, 0x26, 0x67, 0x52, 0xff,
+ 0x27, 0x69, 0x55, 0xff, 0x26, 0x69, 0x55, 0xff,
+ 0x26, 0x69, 0x55, 0xff, 0x26, 0x69, 0x55, 0xff,
+ 0x29, 0x76, 0x63, 0xff, 0x29, 0x75, 0x62, 0xff,
+ 0x31, 0x7c, 0x6b, 0xff, 0x29, 0x75, 0x62, 0xff,
+ 0x42, 0x87, 0x73, 0xff, 0x21, 0x69, 0x52, 0xff,
+ 0x31, 0x78, 0x63, 0xff, 0x41, 0x86, 0x73, 0xff,
+ 0x4a, 0x92, 0x84, 0xff, 0x41, 0x88, 0x76, 0xff,
+ 0x42, 0x88, 0x76, 0xff, 0x39, 0x7e, 0x68, 0xff,
+ 0x32, 0x6a, 0x5b, 0xff, 0x3f, 0x78, 0x68, 0xff,
+ 0x5b, 0x96, 0x84, 0xff, 0x4d, 0x87, 0x76, 0xff,
+ 0x5b, 0x92, 0x84, 0xff, 0x45, 0x87, 0x73, 0xff,
+ 0x50, 0x8d, 0x7c, 0xff, 0x5a, 0x92, 0x83, 0xff,
+ 0x48, 0x87, 0x74, 0xff, 0x52, 0x8e, 0x7b, 0xff,
+ 0x48, 0x87, 0x74, 0xff, 0x31, 0x79, 0x63, 0xff,
+ 0x48, 0x86, 0x74, 0xff, 0x31, 0x75, 0x63, 0xff,
+ 0x48, 0x86, 0x74, 0xff, 0x3c, 0x7d, 0x6b, 0xff,
+ 0x32, 0x6f, 0x5b, 0xff, 0x31, 0x6f, 0x5a, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x31, 0x6e, 0x5a, 0xff,
+ 0x2f, 0x72, 0x5b, 0xff, 0x3a, 0x79, 0x63, 0xff,
+ 0x3a, 0x7a, 0x63, 0xff, 0x2e, 0x71, 0x5a, 0xff,
+ 0x2f, 0x73, 0x5b, 0xff, 0x2f, 0x73, 0x5a, 0xff,
+ 0x2c, 0x6c, 0x53, 0xff, 0x29, 0x65, 0x4a, 0xff,
+ 0x2f, 0x5f, 0x4b, 0xff, 0x2f, 0x5e, 0x4a, 0xff,
+ 0x24, 0x4c, 0x3a, 0xff, 0x23, 0x4b, 0x39, 0xff,
+ 0x32, 0x6a, 0x53, 0xff, 0x31, 0x69, 0x52, 0xff,
+ 0x32, 0x6a, 0x53, 0xff, 0x31, 0x69, 0x52, 0xff,
+ 0x2a, 0x55, 0x3a, 0xff, 0x31, 0x65, 0x4a, 0xff,
+ 0x32, 0x66, 0x4a, 0xff, 0x39, 0x75, 0x5a, 0xff,
+ 0x2c, 0x6f, 0x55, 0xff, 0x2c, 0x6f, 0x55, 0xff,
+ 0x32, 0x76, 0x5b, 0xff, 0x31, 0x75, 0x5a, 0xff,
+ 0x2f, 0x76, 0x5e, 0xff, 0x2c, 0x71, 0x58, 0xff,
+ 0x2c, 0x72, 0x58, 0xff, 0x2c, 0x71, 0x58, 0xff,
+ 0x32, 0x75, 0x5b, 0xff, 0x29, 0x6b, 0x52, 0xff,
+ 0x32, 0x74, 0x5b, 0xff, 0x39, 0x7d, 0x63, 0xff,
+ 0x2f, 0x73, 0x5b, 0xff, 0x24, 0x6c, 0x52, 0xff,
+ 0x2f, 0x73, 0x5b, 0xff, 0x2e, 0x73, 0x5a, 0xff,
+ 0x32, 0x7a, 0x63, 0xff, 0x31, 0x79, 0x63, 0xff,
+ 0x2c, 0x70, 0x5b, 0xff, 0x2c, 0x70, 0x5a, 0xff,
+ 0x3a, 0x81, 0x6b, 0xff, 0x3a, 0x80, 0x6b, 0xff,
+ 0x42, 0x92, 0x7c, 0xff, 0x42, 0x92, 0x7b, 0xff,
+ 0x4d, 0x87, 0x76, 0xff, 0x4c, 0x87, 0x75, 0xff,
+ 0x4d, 0x87, 0x76, 0xff, 0x5a, 0x95, 0x83, 0xff,
+ 0x5b, 0x92, 0x84, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x45, 0x87, 0x73, 0xff, 0x4f, 0x8c, 0x7b, 0xff,
+ 0x47, 0x87, 0x73, 0xff, 0x47, 0x87, 0x73, 0xff,
+ 0x48, 0x87, 0x73, 0xff, 0x3c, 0x80, 0x6b, 0xff,
+ 0x47, 0x86, 0x73, 0xff, 0x3c, 0x7d, 0x6b, 0xff,
+ 0x3d, 0x7e, 0x6b, 0xff, 0x3c, 0x7d, 0x6b, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x39, 0x7d, 0x6b, 0xff,
+ 0x29, 0x60, 0x4a, 0xff, 0x29, 0x60, 0x4a, 0xff,
+ 0x24, 0x69, 0x52, 0xff, 0x23, 0x69, 0x52, 0xff,
+ 0x3a, 0x7a, 0x63, 0xff, 0x39, 0x79, 0x62, 0xff,
+ 0x31, 0x7a, 0x63, 0xff, 0x2e, 0x72, 0x5a, 0xff,
+ 0x2f, 0x73, 0x5b, 0xff, 0x2e, 0x72, 0x5a, 0xff,
+ 0x2f, 0x5f, 0x4a, 0xff, 0x39, 0x71, 0x5a, 0xff,
+ 0x24, 0x4c, 0x3a, 0xff, 0x23, 0x4b, 0x39, 0xff,
+ 0x29, 0x5d, 0x47, 0xff, 0x29, 0x5d, 0x47, 0xff,
+ 0x29, 0x5d, 0x48, 0xff, 0x31, 0x69, 0x52, 0xff,
+ 0x29, 0x55, 0x3a, 0xff, 0x29, 0x55, 0x39, 0xff,
+ 0x32, 0x65, 0x4a, 0xff, 0x39, 0x75, 0x5a, 0xff,
+ 0x2c, 0x6f, 0x55, 0xff, 0x2b, 0x6e, 0x55, 0xff,
+ 0x27, 0x68, 0x50, 0xff, 0x31, 0x75, 0x5a, 0xff,
+ 0x31, 0x7a, 0x63, 0xff, 0x2b, 0x71, 0x57, 0xff,
+ 0x29, 0x6e, 0x52, 0xff, 0x2c, 0x71, 0x57, 0xff,
+ 0x29, 0x6b, 0x52, 0xff, 0x20, 0x61, 0x4a, 0xff,
+ 0x32, 0x74, 0x5b, 0xff, 0x39, 0x7d, 0x62, 0xff,
+ 0x3a, 0x7a, 0x63, 0xff, 0x23, 0x6c, 0x52, 0xff,
+ 0x19, 0x65, 0x4a, 0xff, 0x2e, 0x72, 0x5a, 0xff,
+ 0x26, 0x67, 0x52, 0xff, 0x2b, 0x70, 0x5a, 0xff,
+ 0x32, 0x7a, 0x63, 0xff, 0x2c, 0x70, 0x5a, 0xff,
+ 0x31, 0x6f, 0x5b, 0xff, 0x31, 0x6e, 0x5a, 0xff,
+ 0x3a, 0x80, 0x6b, 0xff, 0x39, 0x80, 0x6b, 0xff,
+ 0x5b, 0x96, 0x84, 0xff, 0x5a, 0x96, 0x83, 0xff,
+ 0x5b, 0x96, 0x84, 0xff, 0x5a, 0x96, 0x84, 0xff,
+ 0x45, 0x87, 0x73, 0xff, 0x44, 0x87, 0x73, 0xff,
+ 0x3a, 0x82, 0x6b, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x48, 0x87, 0x73, 0xff, 0x47, 0x87, 0x73, 0xff,
+ 0x48, 0x87, 0x74, 0xff, 0x3c, 0x80, 0x6b, 0xff,
+ 0x3d, 0x7e, 0x6b, 0xff, 0x47, 0x85, 0x73, 0xff,
+ 0x48, 0x86, 0x74, 0xff, 0x31, 0x75, 0x63, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x39, 0x7d, 0x6b, 0xff,
+ 0x21, 0x51, 0x3a, 0xff, 0x21, 0x51, 0x39, 0xff,
+ 0x3a, 0x7a, 0x63, 0xff, 0x23, 0x69, 0x52, 0xff,
+ 0x3a, 0x7a, 0x63, 0xff, 0x24, 0x69, 0x52, 0xff,
+ 0x32, 0x7a, 0x63, 0xff, 0x31, 0x79, 0x62, 0xff,
+ 0x2c, 0x6c, 0x53, 0xff, 0x2c, 0x6c, 0x52, 0xff,
+ 0x3a, 0x72, 0x5b, 0xff, 0x39, 0x71, 0x5a, 0xff,
+ 0x24, 0x4c, 0x3a, 0xff, 0x19, 0x39, 0x29, 0xff,
+ 0x29, 0x5d, 0x48, 0xff, 0x31, 0x69, 0x52, 0xff,
+ 0x21, 0x51, 0x3d, 0xff, 0x29, 0x5d, 0x47, 0xff,
+ 0x29, 0x55, 0x3a, 0xff, 0x29, 0x55, 0x39, 0xff,
+ 0x32, 0x66, 0x4a, 0xff, 0x39, 0x75, 0x5a, 0xff,
+ 0x27, 0x68, 0x50, 0xff, 0x31, 0x75, 0x5a, 0xff,
+ 0x21, 0x62, 0x4a, 0xff, 0x21, 0x61, 0x4a, 0xff,
+ 0x32, 0x7a, 0x63, 0xff, 0x2c, 0x71, 0x58, 0xff,
+ 0x2f, 0x76, 0x5e, 0xff, 0x2f, 0x75, 0x5d, 0xff,
+ 0x32, 0x74, 0x5b, 0xff, 0x21, 0x61, 0x4a, 0xff,
+ 0x3a, 0x7e, 0x63, 0xff, 0x31, 0x74, 0x5a, 0xff,
+ 0x2f, 0x73, 0x5b, 0xff, 0x2e, 0x72, 0x5a, 0xff,
+ 0x24, 0x6c, 0x53, 0xff, 0x2f, 0x73, 0x5a, 0xff,
+ 0x27, 0x67, 0x53, 0xff, 0x21, 0x5d, 0x4a, 0xff,
+ 0x2c, 0x70, 0x5b, 0xff, 0x31, 0x79, 0x63, 0xff,
+ 0x32, 0x6f, 0x5b, 0xff, 0x31, 0x6e, 0x5a, 0xff,
+ 0x3a, 0x81, 0x6b, 0xff, 0x39, 0x80, 0x6b, 0xff,
+ 0x4d, 0x87, 0x76, 0xff, 0x4c, 0x87, 0x76, 0xff,
+ 0x5b, 0x96, 0x84, 0xff, 0x4c, 0x86, 0x75, 0xff,
+ 0x3a, 0x82, 0x6b, 0xff, 0x44, 0x87, 0x73, 0xff,
+ 0x3a, 0x82, 0x6b, 0xff, 0x44, 0x86, 0x73, 0xff,
+ 0x3c, 0x80, 0x6b, 0xff, 0x47, 0x87, 0x73, 0xff,
+ 0x31, 0x79, 0x63, 0xff, 0x31, 0x79, 0x62, 0xff,
+ 0x32, 0x76, 0x63, 0xff, 0x31, 0x75, 0x62, 0xff,
+ 0x47, 0x86, 0x73, 0xff, 0x31, 0x75, 0x62, 0xff,
+ 0x32, 0x6f, 0x5b, 0xff, 0x31, 0x6e, 0x5a, 0xff,
+ 0x29, 0x60, 0x4a, 0xff, 0x20, 0x50, 0x39, 0xff,
+ 0x24, 0x69, 0x52, 0xff, 0x2e, 0x71, 0x5a, 0xff,
+ 0x24, 0x69, 0x52, 0xff, 0x23, 0x69, 0x52, 0xff,
+ 0x2c, 0x6c, 0x52, 0xff, 0x31, 0x79, 0x62, 0xff,
+ 0x2f, 0x73, 0x5b, 0xff, 0x2b, 0x6b, 0x52, 0xff,
+ 0x2f, 0x5f, 0x4a, 0xff, 0x2e, 0x5e, 0x4a, 0xff,
+ 0x24, 0x4c, 0x3a, 0xff, 0x18, 0x38, 0x29, 0xff,
+ 0x29, 0x5d, 0x47, 0xff, 0x29, 0x5d, 0x47, 0xff,
+ 0x29, 0x5d, 0x47, 0xff, 0x18, 0x44, 0x31, 0xff,
+ 0x21, 0x45, 0x29, 0xff, 0x29, 0x55, 0x39, 0xff,
+ 0x31, 0x65, 0x4a, 0xff, 0x31, 0x65, 0x4a, 0xff,
+ 0x2c, 0x6f, 0x55, 0xff, 0x31, 0x75, 0x5a, 0xff,
+ 0x2c, 0x6f, 0x55, 0xff, 0x26, 0x67, 0x4f, 0xff,
+ 0x2c, 0x71, 0x58, 0xff, 0x29, 0x6d, 0x52, 0xff,
+ 0x29, 0x6d, 0x52, 0xff, 0x2e, 0x75, 0x5d, 0xff,
+ 0x3a, 0x7e, 0x63, 0xff, 0x29, 0x6a, 0x52, 0xff,
+ 0x3a, 0x7e, 0x63, 0xff, 0x29, 0x6a, 0x52, 0xff,
+ 0x24, 0x6c, 0x52, 0xff, 0x39, 0x79, 0x62, 0xff,
+ 0x2f, 0x73, 0x5b, 0xff, 0x23, 0x6b, 0x52, 0xff,
+ 0x27, 0x67, 0x52, 0xff, 0x26, 0x66, 0x52, 0xff,
+ 0x21, 0x5d, 0x4a, 0xff, 0x2b, 0x70, 0x5a, 0xff,
+ 0x32, 0x6f, 0x5b, 0xff, 0x29, 0x5d, 0x4a, 0xff,
+ 0x29, 0x5d, 0x4a, 0xff, 0x39, 0x80, 0x6a, 0xff,
+ 0x53, 0x8a, 0x74, 0xff, 0x37, 0x79, 0x63, 0xff,
+ 0x45, 0x82, 0x6b, 0xff, 0x44, 0x81, 0x6b, 0xff,
+ 0x48, 0x87, 0x74, 0xff, 0x3c, 0x80, 0x6b, 0xff,
+ 0x32, 0x7a, 0x63, 0xff, 0x47, 0x87, 0x73, 0xff,
+ 0x4b, 0x8a, 0x7c, 0xff, 0x3f, 0x7c, 0x6e, 0xff,
+ 0x34, 0x6f, 0x60, 0xff, 0x29, 0x61, 0x52, 0xff,
+ 0x3a, 0x82, 0x6b, 0xff, 0x3a, 0x81, 0x6b, 0xff,
+ 0x3a, 0x82, 0x6b, 0xff, 0x34, 0x74, 0x5d, 0xff,
+ 0x3a, 0x72, 0x5b, 0xff, 0x31, 0x64, 0x4f, 0xff,
+ 0x29, 0x57, 0x45, 0xff, 0x31, 0x64, 0x4f, 0xff,
+ 0x2a, 0x62, 0x4d, 0xff, 0x31, 0x6d, 0x58, 0xff,
+ 0x32, 0x6e, 0x58, 0xff, 0x31, 0x6d, 0x58, 0xff,
+ 0x2f, 0x6f, 0x58, 0xff, 0x2f, 0x6f, 0x58, 0xff,
+ 0x2f, 0x6f, 0x58, 0xff, 0x2c, 0x64, 0x4d, 0xff,
+ 0x32, 0x62, 0x53, 0xff, 0x26, 0x54, 0x42, 0xff,
+ 0x32, 0x61, 0x53, 0xff, 0x21, 0x4d, 0x39, 0xff,
+ 0x32, 0x5a, 0x40, 0xff, 0x29, 0x4d, 0x34, 0xff,
+ 0x3a, 0x66, 0x4a, 0xff, 0x29, 0x4d, 0x34, 0xff,
+ 0x21, 0x45, 0x32, 0xff, 0x2c, 0x5d, 0x47, 0xff,
+ 0x2c, 0x5d, 0x48, 0xff, 0x21, 0x45, 0x31, 0xff,
+ 0x32, 0x64, 0x4d, 0xff, 0x3a, 0x71, 0x5a, 0xff,
+ 0x3a, 0x72, 0x5b, 0xff, 0x31, 0x64, 0x4d, 0xff,
+ 0x3a, 0x7a, 0x63, 0xff, 0x31, 0x64, 0x4d, 0xff,
+ 0x29, 0x4f, 0x37, 0xff, 0x29, 0x4e, 0x37, 0xff,
+ 0x35, 0x64, 0x4d, 0xff, 0x3a, 0x75, 0x5a, 0xff,
+ 0x3a, 0x76, 0x5b, 0xff, 0x39, 0x75, 0x5a, 0xff,
+ 0x3a, 0x77, 0x5e, 0xff, 0x3a, 0x77, 0x5d, 0xff,
+ 0x3a, 0x77, 0x5e, 0xff, 0x29, 0x59, 0x42, 0xff,
+ 0x2c, 0x5f, 0x4b, 0xff, 0x2f, 0x70, 0x5a, 0xff,
+ 0x32, 0x82, 0x6b, 0xff, 0x2e, 0x70, 0x5a, 0xff,
+ 0x35, 0x6a, 0x55, 0xff, 0x29, 0x49, 0x3a, 0xff,
+ 0x29, 0x49, 0x3a, 0xff, 0x34, 0x69, 0x55, 0xff,
+ 0x45, 0x82, 0x6b, 0xff, 0x52, 0x89, 0x73, 0xff,
+ 0x45, 0x82, 0x6b, 0xff, 0x44, 0x81, 0x6b, 0xff,
+ 0x3c, 0x80, 0x6b, 0xff, 0x3c, 0x80, 0x6b, 0xff,
+ 0x3d, 0x80, 0x6b, 0xff, 0x47, 0x87, 0x73, 0xff,
+ 0x4a, 0x8a, 0x7b, 0xff, 0x3f, 0x7c, 0x6d, 0xff,
+ 0x34, 0x6f, 0x60, 0xff, 0x3f, 0x7c, 0x6d, 0xff,
+ 0x34, 0x74, 0x5d, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x2f, 0x67, 0x50, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x3a, 0x71, 0x5b, 0xff, 0x29, 0x56, 0x44, 0xff,
+ 0x29, 0x57, 0x45, 0xff, 0x39, 0x71, 0x5a, 0xff,
+ 0x29, 0x61, 0x4d, 0xff, 0x29, 0x61, 0x4c, 0xff,
+ 0x32, 0x6e, 0x58, 0xff, 0x31, 0x6d, 0x57, 0xff,
+ 0x2f, 0x6f, 0x58, 0xff, 0x2b, 0x63, 0x4c, 0xff,
+ 0x2f, 0x6f, 0x58, 0xff, 0x2c, 0x64, 0x4c, 0xff,
+ 0x26, 0x54, 0x42, 0xff, 0x26, 0x53, 0x41, 0xff,
+ 0x2c, 0x5b, 0x4a, 0xff, 0x2c, 0x5a, 0x4a, 0xff,
+ 0x31, 0x59, 0x3f, 0xff, 0x29, 0x4c, 0x34, 0xff,
+ 0x32, 0x59, 0x3f, 0xff, 0x29, 0x4d, 0x34, 0xff,
+ 0x26, 0x51, 0x3c, 0xff, 0x31, 0x69, 0x52, 0xff,
+ 0x2c, 0x5d, 0x48, 0xff, 0x26, 0x51, 0x3c, 0xff,
+ 0x29, 0x56, 0x3f, 0xff, 0x31, 0x63, 0x4c, 0xff,
+ 0x3a, 0x72, 0x5b, 0xff, 0x31, 0x64, 0x4c, 0xff,
+ 0x3a, 0x7a, 0x63, 0xff, 0x39, 0x79, 0x62, 0xff,
+ 0x29, 0x4e, 0x37, 0xff, 0x21, 0x38, 0x21, 0xff,
+ 0x2f, 0x52, 0x3f, 0xff, 0x34, 0x63, 0x4c, 0xff,
+ 0x34, 0x64, 0x4d, 0xff, 0x39, 0x75, 0x5a, 0xff,
+ 0x3a, 0x77, 0x5d, 0xff, 0x39, 0x76, 0x5d, 0xff,
+ 0x3a, 0x77, 0x5d, 0xff, 0x31, 0x68, 0x4f, 0xff,
+ 0x2c, 0x5f, 0x4a, 0xff, 0x2e, 0x70, 0x5a, 0xff,
+ 0x2f, 0x70, 0x5b, 0xff, 0x31, 0x81, 0x6b, 0xff,
+ 0x3a, 0x7a, 0x63, 0xff, 0x34, 0x69, 0x55, 0xff,
+ 0x2f, 0x59, 0x48, 0xff, 0x29, 0x49, 0x39, 0xff,
+ 0x29, 0x72, 0x5b, 0xff, 0x52, 0x89, 0x73, 0xff,
+ 0x45, 0x82, 0x6b, 0xff, 0x37, 0x79, 0x63, 0xff,
+ 0x3d, 0x80, 0x6b, 0xff, 0x31, 0x79, 0x62, 0xff,
+ 0x48, 0x87, 0x74, 0xff, 0x52, 0x8e, 0x7b, 0xff,
+ 0x4a, 0x8a, 0x7c, 0xff, 0x3f, 0x7c, 0x6d, 0xff,
+ 0x2a, 0x62, 0x53, 0xff, 0x3f, 0x7c, 0x6e, 0xff,
+ 0x3a, 0x82, 0x6b, 0xff, 0x2e, 0x66, 0x4f, 0xff,
+ 0x35, 0x74, 0x5e, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x3a, 0x72, 0x5b, 0xff, 0x29, 0x56, 0x44, 0xff,
+ 0x2a, 0x57, 0x45, 0xff, 0x29, 0x56, 0x44, 0xff,
+ 0x32, 0x6e, 0x58, 0xff, 0x31, 0x6d, 0x58, 0xff,
+ 0x3a, 0x7a, 0x63, 0xff, 0x31, 0x6d, 0x58, 0xff,
+ 0x32, 0x7a, 0x63, 0xff, 0x2e, 0x6e, 0x58, 0xff,
+ 0x2a, 0x59, 0x42, 0xff, 0x29, 0x59, 0x42, 0xff,
+ 0x27, 0x54, 0x42, 0xff, 0x21, 0x4d, 0x39, 0xff,
+ 0x27, 0x54, 0x42, 0xff, 0x26, 0x54, 0x42, 0xff,
+ 0x29, 0x4d, 0x34, 0xff, 0x29, 0x4d, 0x34, 0xff,
+ 0x2a, 0x4d, 0x35, 0xff, 0x21, 0x41, 0x29, 0xff,
+ 0x2c, 0x5d, 0x48, 0xff, 0x2c, 0x5d, 0x47, 0xff,
+ 0x2c, 0x5e, 0x48, 0xff, 0x26, 0x51, 0x3c, 0xff,
+ 0x21, 0x49, 0x32, 0xff, 0x21, 0x49, 0x31, 0xff,
+ 0x32, 0x64, 0x4d, 0xff, 0x39, 0x71, 0x5a, 0xff,
+ 0x3a, 0x7a, 0x63, 0xff, 0x39, 0x79, 0x62, 0xff,
+ 0x32, 0x64, 0x4d, 0xff, 0x21, 0x39, 0x21, 0xff,
+ 0x29, 0x41, 0x32, 0xff, 0x2e, 0x52, 0x3f, 0xff,
+ 0x35, 0x64, 0x4d, 0xff, 0x34, 0x64, 0x4d, 0xff,
+ 0x3a, 0x77, 0x5e, 0xff, 0x39, 0x77, 0x5d, 0xff,
+ 0x32, 0x68, 0x50, 0xff, 0x31, 0x68, 0x4f, 0xff,
+ 0x29, 0x4d, 0x3a, 0xff, 0x29, 0x4d, 0x39, 0xff,
+ 0x2c, 0x5f, 0x4a, 0xff, 0x2f, 0x70, 0x5a, 0xff,
+ 0x3a, 0x7a, 0x63, 0xff, 0x39, 0x79, 0x62, 0xff,
+ 0x3a, 0x7a, 0x63, 0xff, 0x2f, 0x59, 0x47, 0xff,
+ 0x29, 0x71, 0x5b, 0xff, 0x52, 0x89, 0x73, 0xff,
+ 0x52, 0x8a, 0x73, 0xff, 0x44, 0x81, 0x6a, 0xff,
+ 0x47, 0x87, 0x73, 0xff, 0x3c, 0x80, 0x6b, 0xff,
+ 0x52, 0x8e, 0x7b, 0xff, 0x52, 0x8d, 0x7b, 0xff,
+ 0x4a, 0x8a, 0x7c, 0xff, 0x34, 0x6e, 0x60, 0xff,
+ 0x29, 0x61, 0x52, 0xff, 0x34, 0x6e, 0x5f, 0xff,
+ 0x34, 0x74, 0x5d, 0xff, 0x29, 0x59, 0x41, 0xff,
+ 0x2f, 0x67, 0x50, 0xff, 0x2e, 0x66, 0x4f, 0xff,
+ 0x3a, 0x71, 0x5b, 0xff, 0x31, 0x63, 0x4f, 0xff,
+ 0x31, 0x64, 0x50, 0xff, 0x20, 0x48, 0x39, 0xff,
+ 0x21, 0x55, 0x42, 0xff, 0x31, 0x6d, 0x57, 0xff,
+ 0x3a, 0x79, 0x63, 0xff, 0x39, 0x79, 0x62, 0xff,
+ 0x32, 0x7a, 0x63, 0xff, 0x2e, 0x6e, 0x57, 0xff,
+ 0x29, 0x59, 0x42, 0xff, 0x29, 0x59, 0x41, 0xff,
+ 0x2c, 0x5b, 0x4a, 0xff, 0x21, 0x4d, 0x39, 0xff,
+ 0x26, 0x54, 0x42, 0xff, 0x20, 0x4c, 0x39, 0xff,
+ 0x29, 0x4d, 0x34, 0xff, 0x31, 0x59, 0x3f, 0xff,
+ 0x29, 0x4d, 0x34, 0xff, 0x29, 0x4c, 0x34, 0xff,
+ 0x27, 0x51, 0x3c, 0xff, 0x31, 0x69, 0x52, 0xff,
+ 0x2c, 0x5d, 0x47, 0xff, 0x2b, 0x5d, 0x47, 0xff,
+ 0x21, 0x49, 0x32, 0xff, 0x29, 0x56, 0x3f, 0xff,
+ 0x31, 0x64, 0x4d, 0xff, 0x39, 0x71, 0x5a, 0xff,
+ 0x3a, 0x7a, 0x63, 0xff, 0x31, 0x63, 0x4c, 0xff,
+ 0x3a, 0x79, 0x63, 0xff, 0x39, 0x79, 0x62, 0xff,
+ 0x2f, 0x52, 0x3f, 0xff, 0x2e, 0x52, 0x3f, 0xff,
+ 0x34, 0x64, 0x4d, 0xff, 0x34, 0x63, 0x4c, 0xff,
+ 0x3a, 0x77, 0x5d, 0xff, 0x41, 0x85, 0x6b, 0xff,
+ 0x29, 0x59, 0x42, 0xff, 0x29, 0x59, 0x41, 0xff,
+ 0x2c, 0x5f, 0x4a, 0xff, 0x29, 0x4d, 0x39, 0xff,
+ 0x2c, 0x5e, 0x4a, 0xff, 0x2e, 0x70, 0x5a, 0xff,
+ 0x34, 0x69, 0x55, 0xff, 0x39, 0x79, 0x62, 0xff,
+ 0x3a, 0x79, 0x63, 0xff, 0x34, 0x69, 0x55, 0xff,
+ 0x3a, 0x35, 0x32, 0xff, 0x79, 0x60, 0x58, 0xff,
+ 0xf7, 0xb6, 0xa5, 0xff, 0xf7, 0xb6, 0xa4, 0xff,
+ 0xf7, 0xbb, 0xa5, 0xff, 0xf7, 0xba, 0xa4, 0xff,
+ 0xf7, 0xbb, 0xa5, 0xff, 0xf7, 0xba, 0xa4, 0xff,
+ 0xf5, 0xbc, 0xa5, 0xff, 0xf7, 0xc2, 0xad, 0xff,
+ 0xf7, 0xc3, 0xad, 0xff, 0xf1, 0xb5, 0x9c, 0xff,
+ 0xf2, 0xb0, 0x95, 0xff, 0xec, 0xa9, 0x8c, 0xff,
+ 0xe7, 0xa2, 0x84, 0xff, 0xe6, 0xa2, 0x83, 0xff,
+ 0xec, 0xa2, 0x87, 0xff, 0xe6, 0x9e, 0x84, 0xff,
+ 0xe7, 0x9e, 0x84, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xdf, 0x9a, 0x7c, 0xff, 0xde, 0x9a, 0x7b, 0xff,
+ 0xde, 0x9a, 0x7c, 0xff, 0xde, 0x9a, 0x7b, 0xff,
+ 0xe1, 0x99, 0x7f, 0xff, 0xe4, 0x9b, 0x81, 0xff,
+ 0xe1, 0x99, 0x7e, 0xff, 0xde, 0x96, 0x7b, 0xff,
+ 0xdf, 0x96, 0x79, 0xff, 0xd6, 0x92, 0x76, 0xff,
+ 0xce, 0x8e, 0x74, 0xff, 0xd6, 0x92, 0x76, 0xff,
+ 0xdf, 0x92, 0x74, 0xff, 0xde, 0x92, 0x73, 0xff,
+ 0xde, 0x92, 0x74, 0xff, 0xde, 0x92, 0x73, 0xff,
+ 0xdf, 0x92, 0x74, 0xff, 0xde, 0x92, 0x73, 0xff,
+ 0xe1, 0x95, 0x76, 0xff, 0xde, 0x92, 0x73, 0xff,
+ 0xdf, 0x92, 0x74, 0xff, 0xde, 0x92, 0x73, 0xff,
+ 0xe1, 0x95, 0x76, 0xff, 0xe1, 0x94, 0x76, 0xff,
+ 0xe7, 0x94, 0x76, 0xff, 0xe6, 0x92, 0x73, 0xff,
+ 0xe7, 0x92, 0x74, 0xff, 0xe6, 0x92, 0x73, 0xff,
+ 0xdf, 0x92, 0x74, 0xff, 0xde, 0x92, 0x73, 0xff,
+ 0xde, 0x92, 0x74, 0xff, 0xde, 0x92, 0x73, 0xff,
+ 0xd6, 0x92, 0x74, 0xff, 0xde, 0x97, 0x79, 0xff,
+ 0xd6, 0x92, 0x74, 0xff, 0xde, 0x97, 0x78, 0xff,
+ 0xea, 0x9a, 0x7f, 0xff, 0xe4, 0x96, 0x79, 0xff,
+ 0xe4, 0x96, 0x79, 0xff, 0xe3, 0x96, 0x78, 0xff,
+ 0xdf, 0x92, 0x74, 0xff, 0xde, 0x92, 0x73, 0xff,
+ 0xe4, 0x96, 0x76, 0xff, 0xe3, 0x96, 0x76, 0xff,
+ 0x3a, 0x35, 0x31, 0xff, 0x39, 0x34, 0x31, 0xff,
+ 0xb8, 0x8b, 0x7e, 0xff, 0xf6, 0xb6, 0xa4, 0xff,
+ 0xf7, 0xba, 0xa5, 0xff, 0xf6, 0xba, 0xa4, 0xff,
+ 0xf7, 0xba, 0xa5, 0xff, 0xf6, 0xba, 0xa4, 0xff,
+ 0xf7, 0xc2, 0xad, 0xff, 0xf6, 0xc2, 0xac, 0xff,
+ 0xf4, 0xbc, 0xa5, 0xff, 0xf1, 0xb5, 0x9c, 0xff,
+ 0xf7, 0xb6, 0x9c, 0xff, 0xf1, 0xaf, 0x94, 0xff,
+ 0xf2, 0xb0, 0x94, 0xff, 0xec, 0xa8, 0x8c, 0xff,
+ 0xf7, 0xaa, 0x8c, 0xff, 0xf1, 0xa6, 0x89, 0xff,
+ 0xec, 0xa2, 0x87, 0xff, 0xec, 0xa2, 0x86, 0xff,
+ 0xe6, 0xa2, 0x84, 0xff, 0xe3, 0x9f, 0x80, 0xff,
+ 0xe4, 0x9f, 0x81, 0xff, 0xe6, 0xa2, 0x83, 0xff,
+ 0xe6, 0x9e, 0x84, 0xff, 0xe6, 0x9d, 0x83, 0xff,
+ 0xe7, 0x9e, 0x84, 0xff, 0xe3, 0x9b, 0x81, 0xff,
+ 0xe6, 0x9a, 0x7b, 0xff, 0xde, 0x95, 0x78, 0xff,
+ 0xe7, 0x9a, 0x7c, 0xff, 0xe6, 0x9a, 0x7b, 0xff,
+ 0xef, 0x9a, 0x7b, 0xff, 0xe9, 0x97, 0x78, 0xff,
+ 0xe9, 0x97, 0x79, 0xff, 0xe9, 0x97, 0x78, 0xff,
+ 0xe6, 0x9a, 0x7b, 0xff, 0xe6, 0x99, 0x7b, 0xff,
+ 0xe4, 0x97, 0x79, 0xff, 0xe3, 0x97, 0x78, 0xff,
+ 0xe6, 0x9a, 0x7b, 0xff, 0xe3, 0x97, 0x78, 0xff,
+ 0xe4, 0x97, 0x79, 0xff, 0xde, 0x91, 0x73, 0xff,
+ 0xe6, 0x93, 0x76, 0xff, 0xe6, 0x93, 0x75, 0xff,
+ 0xe7, 0x92, 0x73, 0xff, 0xe6, 0x91, 0x73, 0xff,
+ 0xe4, 0x95, 0x76, 0xff, 0xe9, 0x97, 0x78, 0xff,
+ 0xe9, 0x97, 0x79, 0xff, 0xe9, 0x97, 0x78, 0xff,
+ 0xde, 0x97, 0x79, 0xff, 0xde, 0x97, 0x78, 0xff,
+ 0xe7, 0x9d, 0x7e, 0xff, 0xee, 0xa2, 0x83, 0xff,
+ 0xef, 0x9e, 0x84, 0xff, 0xee, 0x9d, 0x83, 0xff,
+ 0xe4, 0x96, 0x79, 0xff, 0xe3, 0x95, 0x78, 0xff,
+ 0xe4, 0x96, 0x76, 0xff, 0xe9, 0x99, 0x78, 0xff,
+ 0xe9, 0x9a, 0x79, 0xff, 0xee, 0x9e, 0x7b, 0xff,
+ 0x3a, 0x35, 0x32, 0xff, 0x39, 0x34, 0x31, 0xff,
+ 0x3a, 0x35, 0x32, 0xff, 0xb8, 0x8b, 0x7e, 0xff,
+ 0xf7, 0xba, 0xa5, 0xff, 0xf7, 0xba, 0xa4, 0xff,
+ 0xf7, 0xbb, 0xa5, 0xff, 0xf7, 0xba, 0xa4, 0xff,
+ 0xf4, 0xbc, 0xa5, 0xff, 0xf1, 0xb5, 0x9c, 0xff,
+ 0xf2, 0xb5, 0x9d, 0xff, 0xee, 0xae, 0x94, 0xff,
+ 0xf2, 0xb0, 0x94, 0xff, 0xf1, 0xaf, 0x94, 0xff,
+ 0xec, 0xa9, 0x8c, 0xff, 0xe6, 0xa2, 0x84, 0xff,
+ 0xec, 0xa2, 0x87, 0xff, 0xec, 0xa2, 0x86, 0xff,
+ 0xe7, 0x9e, 0x84, 0xff, 0xec, 0xa2, 0x86, 0xff,
+ 0xe4, 0x9f, 0x81, 0xff, 0xe3, 0x9f, 0x81, 0xff,
+ 0xe7, 0xa2, 0x84, 0xff, 0xe3, 0x9f, 0x81, 0xff,
+ 0xe7, 0x9e, 0x84, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xe7, 0x9e, 0x84, 0xff, 0xe1, 0x98, 0x7e, 0xff,
+ 0xde, 0x96, 0x79, 0xff, 0xde, 0x96, 0x78, 0xff,
+ 0xdf, 0x96, 0x79, 0xff, 0xde, 0x96, 0x79, 0xff,
+ 0xe9, 0x97, 0x79, 0xff, 0xe3, 0x94, 0x76, 0xff,
+ 0xdf, 0x92, 0x74, 0xff, 0xe3, 0x94, 0x76, 0xff,
+ 0xe4, 0x97, 0x79, 0xff, 0xe3, 0x97, 0x78, 0xff,
+ 0xe1, 0x95, 0x76, 0xff, 0xe1, 0x94, 0x76, 0xff,
+ 0xe1, 0x95, 0x76, 0xff, 0xe1, 0x94, 0x76, 0xff,
+ 0xdf, 0x92, 0x74, 0xff, 0xde, 0x92, 0x73, 0xff,
+ 0xe7, 0x92, 0x73, 0xff, 0xe6, 0x93, 0x76, 0xff,
+ 0xe7, 0x93, 0x76, 0xff, 0xe6, 0x93, 0x76, 0xff,
+ 0xe4, 0x95, 0x76, 0xff, 0xe9, 0x97, 0x78, 0xff,
+ 0xe4, 0x95, 0x76, 0xff, 0xe9, 0x97, 0x79, 0xff,
+ 0xde, 0x97, 0x79, 0xff, 0xe6, 0x9c, 0x7e, 0xff,
+ 0xe7, 0x9d, 0x7f, 0xff, 0xee, 0xa2, 0x84, 0xff,
+ 0xe9, 0x9a, 0x7e, 0xff, 0xe3, 0x96, 0x78, 0xff,
+ 0xdf, 0x92, 0x74, 0xff, 0xe3, 0x96, 0x79, 0xff,
+ 0xe9, 0x9a, 0x79, 0xff, 0xe9, 0x9a, 0x78, 0xff,
+ 0xe9, 0x9a, 0x79, 0xff, 0xe9, 0x9a, 0x79, 0xff,
+ 0x3a, 0x35, 0x32, 0xff, 0x39, 0x34, 0x31, 0xff,
+ 0x3a, 0x35, 0x31, 0xff, 0x39, 0x34, 0x31, 0xff,
+ 0x84, 0x65, 0x5b, 0xff, 0xd0, 0x9e, 0x8b, 0xff,
+ 0xf7, 0xba, 0xa5, 0xff, 0xf6, 0xba, 0xa4, 0xff,
+ 0xef, 0xae, 0x94, 0xff, 0xee, 0xae, 0x94, 0xff,
+ 0xef, 0xae, 0x94, 0xff, 0xee, 0xae, 0x94, 0xff,
+ 0xec, 0xa9, 0x8c, 0xff, 0xeb, 0xa8, 0x8b, 0xff,
+ 0xe6, 0xa2, 0x84, 0xff, 0xe6, 0xa1, 0x83, 0xff,
+ 0xec, 0xa2, 0x87, 0xff, 0xeb, 0xa2, 0x86, 0xff,
+ 0xe6, 0x9e, 0x84, 0xff, 0xeb, 0xa1, 0x86, 0xff,
+ 0xe6, 0xa2, 0x84, 0xff, 0xe6, 0xa2, 0x83, 0xff,
+ 0xe4, 0x9f, 0x81, 0xff, 0xe0, 0x9c, 0x7e, 0xff,
+ 0xe4, 0x9b, 0x81, 0xff, 0xe3, 0x9b, 0x81, 0xff,
+ 0xe4, 0x9b, 0x81, 0xff, 0xe0, 0x98, 0x7e, 0xff,
+ 0xde, 0x96, 0x79, 0xff, 0xde, 0x95, 0x78, 0xff,
+ 0xde, 0x96, 0x79, 0xff, 0xde, 0x95, 0x78, 0xff,
+ 0xde, 0x92, 0x73, 0xff, 0xe3, 0x94, 0x76, 0xff,
+ 0xe4, 0x94, 0x76, 0xff, 0xde, 0x91, 0x73, 0xff,
+ 0xde, 0x92, 0x73, 0xff, 0xe0, 0x94, 0x76, 0xff,
+ 0xe4, 0x97, 0x79, 0xff, 0xe0, 0x94, 0x75, 0xff,
+ 0xe1, 0x95, 0x76, 0xff, 0xde, 0x91, 0x73, 0xff,
+ 0xe1, 0x94, 0x76, 0xff, 0xe0, 0x94, 0x75, 0xff,
+ 0xe6, 0x95, 0x79, 0xff, 0xe6, 0x95, 0x7b, 0xff,
+ 0xe6, 0x94, 0x79, 0xff, 0xe6, 0x93, 0x75, 0xff,
+ 0xe4, 0x95, 0x76, 0xff, 0xe3, 0x94, 0x76, 0xff,
+ 0xe4, 0x94, 0x76, 0xff, 0xde, 0x91, 0x73, 0xff,
+ 0xde, 0x97, 0x79, 0xff, 0xe6, 0x9c, 0x7e, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xe6, 0x9c, 0x7e, 0xff,
+ 0xe4, 0x96, 0x79, 0xff, 0xde, 0x91, 0x73, 0xff,
+ 0xe4, 0x96, 0x79, 0xff, 0xe3, 0x95, 0x78, 0xff,
+ 0xe4, 0x96, 0x76, 0xff, 0xe3, 0x95, 0x76, 0xff,
+ 0xe9, 0x9a, 0x79, 0xff, 0xe9, 0x99, 0x78, 0xff,
+ 0x2a, 0x29, 0x2a, 0xff, 0x29, 0x28, 0x29, 0xff,
+ 0x3f, 0x44, 0x3f, 0xff, 0x29, 0x28, 0x29, 0xff,
+ 0x53, 0x49, 0x42, 0xff, 0x84, 0x69, 0x5d, 0xff,
+ 0xe7, 0xaa, 0x94, 0xff, 0xe6, 0xaa, 0x94, 0xff,
+ 0xef, 0xaf, 0x95, 0xff, 0xec, 0xaa, 0x91, 0xff,
+ 0xec, 0xaa, 0x92, 0xff, 0xec, 0xaa, 0x91, 0xff,
+ 0xef, 0xa6, 0x8c, 0xff, 0xec, 0xa3, 0x89, 0xff,
+ 0xe9, 0xa1, 0x87, 0xff, 0xe9, 0xa0, 0x86, 0xff,
+ 0xe7, 0xa1, 0x87, 0xff, 0xe6, 0xa1, 0x86, 0xff,
+ 0xe7, 0xa1, 0x87, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xe7, 0x9e, 0x84, 0xff, 0xe6, 0xa2, 0x84, 0xff,
+ 0xe7, 0x9e, 0x84, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xe4, 0x9c, 0x81, 0xff, 0xe6, 0x9e, 0x84, 0xff,
+ 0xe7, 0x9e, 0x84, 0xff, 0xe1, 0x98, 0x7e, 0xff,
+ 0xe1, 0x98, 0x79, 0xff, 0xde, 0x96, 0x73, 0xff,
+ 0xe1, 0x97, 0x79, 0xff, 0xe1, 0x97, 0x78, 0xff,
+ 0xdf, 0x91, 0x76, 0xff, 0xde, 0x90, 0x76, 0xff,
+ 0xde, 0x91, 0x76, 0xff, 0xde, 0x90, 0x76, 0xff,
+ 0xe4, 0x8f, 0x76, 0xff, 0xe4, 0x8f, 0x76, 0xff,
+ 0xe4, 0x8f, 0x76, 0xff, 0xe6, 0x92, 0x7b, 0xff,
+ 0xe4, 0x94, 0x79, 0xff, 0xe1, 0x90, 0x76, 0xff,
+ 0xe4, 0x93, 0x79, 0xff, 0xe3, 0x93, 0x78, 0xff,
+ 0xe7, 0x96, 0x7c, 0xff, 0xe4, 0x93, 0x79, 0xff,
+ 0xe7, 0x96, 0x7c, 0xff, 0xe3, 0x93, 0x78, 0xff,
+ 0xe7, 0x92, 0x74, 0xff, 0xe6, 0x97, 0x79, 0xff,
+ 0xe7, 0x92, 0x74, 0xff, 0xe6, 0x97, 0x78, 0xff,
+ 0xe7, 0x9a, 0x7f, 0xff, 0xe6, 0xa2, 0x84, 0xff,
+ 0xe7, 0x9e, 0x81, 0xff, 0xe6, 0x96, 0x7b, 0xff,
+ 0xe7, 0x94, 0x79, 0xff, 0xe6, 0x96, 0x7b, 0xff,
+ 0xe7, 0x96, 0x7c, 0xff, 0xe6, 0x96, 0x7b, 0xff,
+ 0xe7, 0x92, 0x76, 0xff, 0xe6, 0x92, 0x76, 0xff,
+ 0xe7, 0x96, 0x7c, 0xff, 0xe6, 0x96, 0x7b, 0xff,
+ 0x3f, 0x44, 0x3f, 0xff, 0x34, 0x36, 0x34, 0xff,
+ 0x34, 0x36, 0x34, 0xff, 0x3f, 0x43, 0x3f, 0xff,
+ 0x52, 0x49, 0x42, 0xff, 0x52, 0x48, 0x41, 0xff,
+ 0x84, 0x69, 0x5d, 0xff, 0xe6, 0xaa, 0x94, 0xff,
+ 0xec, 0xaa, 0x91, 0xff, 0xeb, 0xaa, 0x91, 0xff,
+ 0xe7, 0xa2, 0x8c, 0xff, 0xe9, 0xa6, 0x8e, 0xff,
+ 0xec, 0xa3, 0x89, 0xff, 0xeb, 0xa3, 0x89, 0xff,
+ 0xe7, 0x9e, 0x84, 0xff, 0xe9, 0xa0, 0x86, 0xff,
+ 0xe6, 0xa1, 0x86, 0xff, 0xe6, 0x9d, 0x83, 0xff,
+ 0xe7, 0xa1, 0x87, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xe6, 0x9e, 0x84, 0xff, 0xe6, 0xa1, 0x83, 0xff,
+ 0xe7, 0x9e, 0x84, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xe4, 0x9b, 0x81, 0xff, 0xe3, 0x9b, 0x80, 0xff,
+ 0xe1, 0x99, 0x7e, 0xff, 0xde, 0x95, 0x7b, 0xff,
+ 0xe1, 0x97, 0x79, 0xff, 0xe0, 0x97, 0x78, 0xff,
+ 0xe1, 0x97, 0x79, 0xff, 0xde, 0x95, 0x73, 0xff,
+ 0xde, 0x90, 0x76, 0xff, 0xde, 0x8f, 0x70, 0xff,
+ 0xde, 0x8f, 0x71, 0xff, 0xde, 0x8d, 0x6b, 0xff,
+ 0xe1, 0x8c, 0x71, 0xff, 0xe0, 0x8c, 0x70, 0xff,
+ 0xe1, 0x8d, 0x71, 0xff, 0xe1, 0x8c, 0x70, 0xff,
+ 0xe4, 0x93, 0x79, 0xff, 0xe3, 0x93, 0x78, 0xff,
+ 0xe1, 0x91, 0x76, 0xff, 0xe3, 0x93, 0x78, 0xff,
+ 0xe6, 0x96, 0x7b, 0xff, 0xe3, 0x93, 0x78, 0xff,
+ 0xe4, 0x93, 0x79, 0xff, 0xe3, 0x93, 0x78, 0xff,
+ 0xe6, 0x92, 0x73, 0xff, 0xe6, 0x97, 0x78, 0xff,
+ 0xe7, 0x97, 0x79, 0xff, 0xe6, 0x97, 0x78, 0xff,
+ 0xe6, 0xa2, 0x84, 0xff, 0xe6, 0x9d, 0x80, 0xff,
+ 0xe7, 0x9a, 0x7e, 0xff, 0xe6, 0x95, 0x7b, 0xff,
+ 0xe6, 0x93, 0x79, 0xff, 0xe6, 0x95, 0x7b, 0xff,
+ 0xe7, 0x96, 0x7c, 0xff, 0xe6, 0x93, 0x78, 0xff,
+ 0xe6, 0x92, 0x76, 0xff, 0xe6, 0x91, 0x75, 0xff,
+ 0xe7, 0x92, 0x76, 0xff, 0xe6, 0x91, 0x76, 0xff,
+ 0x4a, 0x51, 0x4a, 0xff, 0x4a, 0x51, 0x4a, 0xff,
+ 0x35, 0x36, 0x35, 0xff, 0x3f, 0x43, 0x3f, 0xff,
+ 0x53, 0x49, 0x42, 0xff, 0x52, 0x49, 0x42, 0xff,
+ 0x53, 0x49, 0x42, 0xff, 0xb5, 0x8a, 0x79, 0xff,
+ 0xe9, 0xa6, 0x8f, 0xff, 0xe9, 0xa6, 0x8e, 0xff,
+ 0xe7, 0xa2, 0x8c, 0xff, 0xe6, 0xa2, 0x8c, 0xff,
+ 0xe9, 0xa1, 0x87, 0xff, 0xe9, 0xa0, 0x86, 0xff,
+ 0xe9, 0xa1, 0x87, 0xff, 0xe9, 0xa0, 0x86, 0xff,
+ 0xe7, 0xa1, 0x87, 0xff, 0xe6, 0xa3, 0x89, 0xff,
+ 0xe7, 0xa1, 0x87, 0xff, 0xe6, 0xa0, 0x86, 0xff,
+ 0xe7, 0x9e, 0x84, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xe7, 0x9a, 0x84, 0xff, 0xe6, 0x9a, 0x84, 0xff,
+ 0xe4, 0x9b, 0x81, 0xff, 0xe1, 0x98, 0x7e, 0xff,
+ 0xdf, 0x96, 0x7c, 0xff, 0xde, 0x96, 0x7b, 0xff,
+ 0xe4, 0x99, 0x7e, 0xff, 0xe3, 0x98, 0x7e, 0xff,
+ 0xe1, 0x98, 0x79, 0xff, 0xe1, 0x97, 0x79, 0xff,
+ 0xde, 0x91, 0x76, 0xff, 0xde, 0x90, 0x76, 0xff,
+ 0xdf, 0x91, 0x76, 0xff, 0xde, 0x8f, 0x70, 0xff,
+ 0xe4, 0x8f, 0x76, 0xff, 0xe1, 0x8c, 0x70, 0xff,
+ 0xe1, 0x8d, 0x71, 0xff, 0xe1, 0x8c, 0x70, 0xff,
+ 0xde, 0x8e, 0x73, 0xff, 0xe1, 0x90, 0x76, 0xff,
+ 0xe1, 0x91, 0x76, 0xff, 0xe1, 0x90, 0x76, 0xff,
+ 0xe1, 0x91, 0x76, 0xff, 0xe1, 0x90, 0x76, 0xff,
+ 0xe1, 0x91, 0x76, 0xff, 0xe3, 0x93, 0x79, 0xff,
+ 0xe7, 0x92, 0x73, 0xff, 0xe6, 0x91, 0x73, 0xff,
+ 0xe7, 0x98, 0x79, 0xff, 0xe6, 0x9c, 0x7e, 0xff,
+ 0xe7, 0xa2, 0x84, 0xff, 0xe6, 0x9e, 0x81, 0xff,
+ 0xe7, 0x9a, 0x7f, 0xff, 0xe6, 0x96, 0x7b, 0xff,
+ 0xe7, 0x96, 0x7c, 0xff, 0xe6, 0x93, 0x78, 0xff,
+ 0xe7, 0x91, 0x76, 0xff, 0xe6, 0x8e, 0x73, 0xff,
+ 0xe7, 0x8e, 0x71, 0xff, 0xe6, 0x8d, 0x70, 0xff,
+ 0xe7, 0x92, 0x76, 0xff, 0xe6, 0x8e, 0x70, 0xff,
+ 0x3f, 0x44, 0x3f, 0xff, 0x34, 0x36, 0x34, 0xff,
+ 0x3f, 0x43, 0x3f, 0xff, 0x3f, 0x43, 0x3f, 0xff,
+ 0x52, 0x49, 0x42, 0xff, 0x52, 0x49, 0x41, 0xff,
+ 0x52, 0x49, 0x42, 0xff, 0x83, 0x69, 0x5d, 0xff,
+ 0xe9, 0xa6, 0x8f, 0xff, 0xe6, 0xa2, 0x8b, 0xff,
+ 0xe6, 0xa2, 0x8c, 0xff, 0xe6, 0xa1, 0x8b, 0xff,
+ 0xe6, 0x9e, 0x84, 0xff, 0xe9, 0xa0, 0x86, 0xff,
+ 0xec, 0xa3, 0x89, 0xff, 0xeb, 0xa3, 0x89, 0xff,
+ 0xe6, 0xa3, 0x89, 0xff, 0xe6, 0xa3, 0x89, 0xff,
+ 0xe6, 0xa3, 0x89, 0xff, 0xe6, 0x9d, 0x83, 0xff,
+ 0xe6, 0x9e, 0x84, 0xff, 0xe6, 0x99, 0x83, 0xff,
+ 0xe6, 0x9e, 0x84, 0xff, 0xe6, 0x95, 0x83, 0xff,
+ 0xe1, 0x99, 0x7e, 0xff, 0xe0, 0x98, 0x7e, 0xff,
+ 0xe1, 0x98, 0x7e, 0xff, 0xe0, 0x98, 0x7e, 0xff,
+ 0xe6, 0x9a, 0x84, 0xff, 0xe3, 0x98, 0x7e, 0xff,
+ 0xe6, 0x9a, 0x84, 0xff, 0xde, 0x95, 0x73, 0xff,
+ 0xde, 0x92, 0x7c, 0xff, 0xde, 0x90, 0x76, 0xff,
+ 0xde, 0x90, 0x76, 0xff, 0xde, 0x8f, 0x70, 0xff,
+ 0xe4, 0x8f, 0x76, 0xff, 0xe0, 0x8c, 0x70, 0xff,
+ 0xe1, 0x8c, 0x70, 0xff, 0xe0, 0x8c, 0x70, 0xff,
+ 0xde, 0x8e, 0x73, 0xff, 0xde, 0x8d, 0x73, 0xff,
+ 0xde, 0x8e, 0x73, 0xff, 0xde, 0x8d, 0x73, 0xff,
+ 0xde, 0x8e, 0x73, 0xff, 0xde, 0x8d, 0x73, 0xff,
+ 0xe1, 0x90, 0x76, 0xff, 0xe3, 0x93, 0x78, 0xff,
+ 0xe6, 0x97, 0x79, 0xff, 0xe6, 0x97, 0x78, 0xff,
+ 0xe6, 0x9d, 0x7e, 0xff, 0xe6, 0xa1, 0x83, 0xff,
+ 0xe6, 0xa2, 0x84, 0xff, 0xe6, 0xa2, 0x83, 0xff,
+ 0xe6, 0x9e, 0x81, 0xff, 0xe6, 0x99, 0x7e, 0xff,
+ 0xe6, 0x96, 0x7c, 0xff, 0xe6, 0x90, 0x76, 0xff,
+ 0xe6, 0x8e, 0x73, 0xff, 0xe6, 0x8d, 0x73, 0xff,
+ 0xe6, 0x8a, 0x6b, 0xff, 0xe6, 0x8d, 0x70, 0xff,
+ 0xe6, 0x8e, 0x70, 0xff, 0xe6, 0x8d, 0x70, 0xff,
+ 0x4d, 0x4d, 0x42, 0xff, 0x3a, 0x3d, 0x31, 0xff,
+ 0x4d, 0x4d, 0x42, 0xff, 0x4d, 0x4d, 0x42, 0xff,
+ 0x3a, 0x4d, 0x4b, 0xff, 0x3a, 0x4d, 0x4a, 0xff,
+ 0x71, 0x68, 0x5e, 0xff, 0x70, 0x68, 0x5d, 0xff,
+ 0xe4, 0x9e, 0x87, 0xff, 0xe6, 0xa2, 0x8c, 0xff,
+ 0xe4, 0x9e, 0x87, 0xff, 0xe3, 0x9e, 0x86, 0xff,
+ 0xe7, 0xa2, 0x8c, 0xff, 0xe6, 0xa2, 0x8c, 0xff,
+ 0xe7, 0xa2, 0x8c, 0xff, 0xe6, 0xa4, 0x8c, 0xff,
+ 0xe7, 0xa6, 0x8c, 0xff, 0xe6, 0xa6, 0x8c, 0xff,
+ 0xe7, 0xa1, 0x87, 0xff, 0xe6, 0xa0, 0x86, 0xff,
+ 0xe7, 0x9e, 0x84, 0xff, 0xe6, 0x9e, 0x84, 0xff,
+ 0xe4, 0x9a, 0x81, 0xff, 0xe3, 0x9a, 0x81, 0xff,
+ 0xdf, 0x9a, 0x84, 0xff, 0xde, 0x97, 0x81, 0xff,
+ 0xde, 0x95, 0x7e, 0xff, 0xde, 0x97, 0x81, 0xff,
+ 0xe4, 0x96, 0x7f, 0xff, 0xe6, 0x9a, 0x84, 0xff,
+ 0xe4, 0x96, 0x7e, 0xff, 0xe3, 0x96, 0x7e, 0xff,
+ 0xdf, 0x92, 0x74, 0xff, 0xde, 0x90, 0x73, 0xff,
+ 0xde, 0x91, 0x74, 0xff, 0xde, 0x8f, 0x73, 0xff,
+ 0xdf, 0x8d, 0x71, 0xff, 0xde, 0x8c, 0x70, 0xff,
+ 0xde, 0x8d, 0x71, 0xff, 0xde, 0x89, 0x6b, 0xff,
+ 0xdf, 0x8d, 0x6e, 0xff, 0xde, 0x8a, 0x6b, 0xff,
+ 0xde, 0x8d, 0x6e, 0xff, 0xde, 0x8c, 0x6e, 0xff,
+ 0xdf, 0x8f, 0x79, 0xff, 0xde, 0x90, 0x76, 0xff,
+ 0xde, 0x91, 0x76, 0xff, 0xde, 0x90, 0x76, 0xff,
+ 0xdf, 0x92, 0x7c, 0xff, 0xe4, 0x9a, 0x84, 0xff,
+ 0xe4, 0x9a, 0x84, 0xff, 0xe9, 0xa2, 0x8c, 0xff,
+ 0xea, 0xa5, 0x8c, 0xff, 0xec, 0xab, 0x94, 0xff,
+ 0xe9, 0xa5, 0x8c, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xdf, 0x9a, 0x84, 0xff, 0xe1, 0x94, 0x7b, 0xff,
+ 0xe4, 0x8f, 0x74, 0xff, 0xe6, 0x89, 0x6b, 0xff,
+ 0xe7, 0x8a, 0x6b, 0xff, 0xe6, 0x8a, 0x6b, 0xff,
+ 0xe7, 0x8d, 0x6e, 0xff, 0xe6, 0x8f, 0x70, 0xff,
+ 0x3a, 0x3d, 0x31, 0xff, 0x4c, 0x4c, 0x41, 0xff,
+ 0x60, 0x5d, 0x52, 0xff, 0x60, 0x5d, 0x52, 0xff,
+ 0x3a, 0x4d, 0x4a, 0xff, 0x39, 0x4c, 0x4a, 0xff,
+ 0xa7, 0x83, 0x71, 0xff, 0xa7, 0x83, 0x70, 0xff,
+ 0xde, 0x96, 0x7b, 0xff, 0xe3, 0x9d, 0x86, 0xff,
+ 0xe1, 0x9a, 0x81, 0xff, 0xe3, 0x9e, 0x86, 0xff,
+ 0xe6, 0xa2, 0x8c, 0xff, 0xe6, 0xa4, 0x8b, 0xff,
+ 0xe7, 0xa8, 0x8c, 0xff, 0xe6, 0xa7, 0x8c, 0xff,
+ 0xe6, 0xa6, 0x8c, 0xff, 0xe6, 0xa0, 0x86, 0xff,
+ 0xe7, 0xa1, 0x87, 0xff, 0xe6, 0x9b, 0x81, 0xff,
+ 0xe4, 0x9a, 0x81, 0xff, 0xe3, 0x99, 0x80, 0xff,
+ 0xe4, 0x9a, 0x81, 0xff, 0xe3, 0x9a, 0x81, 0xff,
+ 0xde, 0x9a, 0x84, 0xff, 0xde, 0x97, 0x80, 0xff,
+ 0xde, 0x97, 0x81, 0xff, 0xde, 0x97, 0x81, 0xff,
+ 0xe4, 0x96, 0x7e, 0xff, 0xe3, 0x95, 0x7e, 0xff,
+ 0xe4, 0x96, 0x7e, 0xff, 0xe1, 0x91, 0x78, 0xff,
+ 0xde, 0x8f, 0x73, 0xff, 0xde, 0x8d, 0x73, 0xff,
+ 0xde, 0x8e, 0x73, 0xff, 0xde, 0x8d, 0x73, 0xff,
+ 0xde, 0x8c, 0x71, 0xff, 0xde, 0x8c, 0x70, 0xff,
+ 0xde, 0x8a, 0x6b, 0xff, 0xde, 0x8c, 0x70, 0xff,
+ 0xde, 0x8a, 0x6b, 0xff, 0xde, 0x89, 0x6b, 0xff,
+ 0xde, 0x8d, 0x6e, 0xff, 0xde, 0x8f, 0x70, 0xff,
+ 0xde, 0x90, 0x76, 0xff, 0xde, 0x90, 0x75, 0xff,
+ 0xde, 0x92, 0x73, 0xff, 0xde, 0x90, 0x76, 0xff,
+ 0xde, 0x92, 0x7b, 0xff, 0xde, 0x91, 0x7b, 0xff,
+ 0xe9, 0xa2, 0x8c, 0xff, 0xee, 0xaa, 0x94, 0xff,
+ 0xec, 0xab, 0x94, 0xff, 0xeb, 0xab, 0x94, 0xff,
+ 0xe9, 0xa5, 0x8c, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xde, 0x9a, 0x84, 0xff, 0xe3, 0x8f, 0x73, 0xff,
+ 0xe4, 0x8f, 0x73, 0xff, 0xe6, 0x89, 0x6b, 0xff,
+ 0xe6, 0x8c, 0x6e, 0xff, 0xe6, 0x8c, 0x6d, 0xff,
+ 0xe7, 0x8d, 0x6e, 0xff, 0xe6, 0x8c, 0x6d, 0xff,
+ 0x4d, 0x4d, 0x42, 0xff, 0x4d, 0x4d, 0x42, 0xff,
+ 0x4d, 0x4d, 0x42, 0xff, 0x60, 0x5d, 0x52, 0xff,
+ 0x71, 0x68, 0x5e, 0xff, 0x70, 0x68, 0x5d, 0xff,
+ 0xdf, 0x9e, 0x84, 0xff, 0xde, 0x9e, 0x84, 0xff,
+ 0xe4, 0x9e, 0x87, 0xff, 0xe1, 0x9a, 0x81, 0xff,
+ 0xe4, 0x9e, 0x87, 0xff, 0xe3, 0x9e, 0x86, 0xff,
+ 0xe7, 0xa5, 0x8c, 0xff, 0xe6, 0xa7, 0x8c, 0xff,
+ 0xe7, 0xa8, 0x8c, 0xff, 0xe6, 0xa5, 0x8c, 0xff,
+ 0xe7, 0xa1, 0x87, 0xff, 0xe6, 0xa0, 0x86, 0xff,
+ 0xe7, 0x96, 0x7c, 0xff, 0xe6, 0x96, 0x7b, 0xff,
+ 0xe1, 0x96, 0x7e, 0xff, 0xe1, 0x96, 0x7e, 0xff,
+ 0xe1, 0x96, 0x7f, 0xff, 0xe3, 0x9a, 0x81, 0xff,
+ 0xde, 0x9a, 0x84, 0xff, 0xde, 0x9a, 0x83, 0xff,
+ 0xdf, 0x9a, 0x84, 0xff, 0xde, 0x97, 0x81, 0xff,
+ 0xe4, 0x96, 0x7e, 0xff, 0xe1, 0x91, 0x78, 0xff,
+ 0xe1, 0x92, 0x79, 0xff, 0xe1, 0x92, 0x79, 0xff,
+ 0xde, 0x8e, 0x73, 0xff, 0xde, 0x8d, 0x73, 0xff,
+ 0xdf, 0x8e, 0x74, 0xff, 0xde, 0x8e, 0x73, 0xff,
+ 0xde, 0x8d, 0x71, 0xff, 0xde, 0x8c, 0x70, 0xff,
+ 0xdf, 0x8f, 0x76, 0xff, 0xde, 0x8f, 0x76, 0xff,
+ 0xde, 0x92, 0x73, 0xff, 0xde, 0x8f, 0x70, 0xff,
+ 0xdf, 0x8f, 0x71, 0xff, 0xde, 0x92, 0x73, 0xff,
+ 0xde, 0x91, 0x76, 0xff, 0xde, 0x91, 0x73, 0xff,
+ 0xdf, 0x92, 0x74, 0xff, 0xde, 0x92, 0x73, 0xff,
+ 0xde, 0x92, 0x7c, 0xff, 0xde, 0x91, 0x7b, 0xff,
+ 0xe9, 0xa2, 0x8c, 0xff, 0xee, 0xaa, 0x94, 0xff,
+ 0xef, 0xb2, 0x9d, 0xff, 0xec, 0xab, 0x94, 0xff,
+ 0xe9, 0xa5, 0x8c, 0xff, 0xe6, 0x9e, 0x84, 0xff,
+ 0xe4, 0x8f, 0x73, 0xff, 0xe3, 0x8f, 0x73, 0xff,
+ 0xe7, 0x8a, 0x6b, 0xff, 0xe6, 0x8a, 0x6b, 0xff,
+ 0xe7, 0x8d, 0x6e, 0xff, 0xe6, 0x8c, 0x6d, 0xff,
+ 0xe7, 0x8a, 0x6b, 0xff, 0xe6, 0x8c, 0x6e, 0xff,
+ 0x60, 0x5d, 0x52, 0xff, 0x4c, 0x4d, 0x41, 0xff,
+ 0x4d, 0x4d, 0x42, 0xff, 0x73, 0x6d, 0x62, 0xff,
+ 0xa7, 0x83, 0x71, 0xff, 0xde, 0x9e, 0x83, 0xff,
+ 0xde, 0x9e, 0x84, 0xff, 0xde, 0x9d, 0x83, 0xff,
+ 0xe4, 0x9e, 0x87, 0xff, 0xe3, 0x9e, 0x86, 0xff,
+ 0xe4, 0x9e, 0x86, 0xff, 0xe3, 0x9d, 0x86, 0xff,
+ 0xe6, 0xa5, 0x8c, 0xff, 0xe6, 0xa7, 0x8b, 0xff,
+ 0xe6, 0xa7, 0x8c, 0xff, 0xe6, 0xa4, 0x8b, 0xff,
+ 0xe6, 0xa1, 0x87, 0xff, 0xe6, 0x9b, 0x81, 0xff,
+ 0xe6, 0x9b, 0x81, 0xff, 0xe6, 0x9b, 0x80, 0xff,
+ 0xe4, 0x9a, 0x81, 0xff, 0xe0, 0x95, 0x7e, 0xff,
+ 0xe1, 0x96, 0x7e, 0xff, 0xde, 0x91, 0x7b, 0xff,
+ 0xde, 0x95, 0x7e, 0xff, 0xde, 0x91, 0x7b, 0xff,
+ 0xde, 0x92, 0x7b, 0xff, 0xde, 0x91, 0x7b, 0xff,
+ 0xde, 0x8e, 0x73, 0xff, 0xe0, 0x91, 0x78, 0xff,
+ 0xde, 0x8e, 0x73, 0xff, 0xde, 0x8d, 0x73, 0xff,
+ 0xde, 0x8e, 0x73, 0xff, 0xde, 0x8f, 0x73, 0xff,
+ 0xde, 0x8f, 0x73, 0xff, 0xde, 0x8d, 0x73, 0xff,
+ 0xde, 0x8c, 0x71, 0xff, 0xde, 0x8f, 0x76, 0xff,
+ 0xde, 0x8f, 0x76, 0xff, 0xde, 0x8f, 0x75, 0xff,
+ 0xde, 0x92, 0x73, 0xff, 0xde, 0x8f, 0x70, 0xff,
+ 0xde, 0x8f, 0x70, 0xff, 0xde, 0x8f, 0x70, 0xff,
+ 0xde, 0x91, 0x76, 0xff, 0xde, 0x91, 0x73, 0xff,
+ 0xde, 0x90, 0x76, 0xff, 0xde, 0x8f, 0x78, 0xff,
+ 0xde, 0x92, 0x7c, 0xff, 0xde, 0x91, 0x7b, 0xff,
+ 0xe4, 0x9a, 0x84, 0xff, 0xe9, 0xa1, 0x8b, 0xff,
+ 0xe9, 0xa5, 0x8c, 0xff, 0xeb, 0xab, 0x94, 0xff,
+ 0xec, 0xab, 0x94, 0xff, 0xe6, 0x9d, 0x83, 0xff,
+ 0xe4, 0x8f, 0x73, 0xff, 0xe6, 0x89, 0x6b, 0xff,
+ 0xe6, 0x8a, 0x6b, 0xff, 0xe6, 0x89, 0x6a, 0xff,
+ 0xe6, 0x8a, 0x6b, 0xff, 0xe6, 0x8c, 0x6d, 0xff,
+ 0xe6, 0x8c, 0x6e, 0xff, 0xe6, 0x8c, 0x6d, 0xff,
+ 0x84, 0x70, 0x60, 0xff, 0x84, 0x70, 0x60, 0xff,
+ 0x53, 0x55, 0x4a, 0xff, 0x83, 0x70, 0x60, 0xff,
+ 0xe7, 0xa1, 0x87, 0xff, 0xe6, 0xa3, 0x89, 0xff,
+ 0xe7, 0xa1, 0x87, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xe7, 0x9e, 0x87, 0xff, 0xe6, 0x9a, 0x84, 0xff,
+ 0xe7, 0x9e, 0x87, 0xff, 0xe6, 0xa2, 0x89, 0xff,
+ 0xe7, 0xa6, 0x8c, 0xff, 0xe6, 0xa6, 0x8c, 0xff,
+ 0xe4, 0xa1, 0x87, 0xff, 0xe3, 0xa0, 0x86, 0xff,
+ 0xe7, 0xa2, 0x84, 0xff, 0xe1, 0x97, 0x7e, 0xff,
+ 0xe4, 0x9d, 0x81, 0xff, 0xe1, 0x97, 0x7e, 0xff,
+ 0xdf, 0x94, 0x79, 0xff, 0xde, 0x93, 0x79, 0xff,
+ 0xde, 0x92, 0x7c, 0xff, 0xde, 0x92, 0x7b, 0xff,
+ 0xdf, 0x91, 0x79, 0xff, 0xde, 0x90, 0x79, 0xff,
+ 0xde, 0x91, 0x79, 0xff, 0xde, 0x90, 0x78, 0xff,
+ 0xd6, 0x8e, 0x7c, 0xff, 0xd9, 0x8c, 0x76, 0xff,
+ 0xd9, 0x8d, 0x76, 0xff, 0xd8, 0x8c, 0x76, 0xff,
+ 0xdf, 0x8e, 0x74, 0xff, 0xde, 0x8e, 0x73, 0xff,
+ 0xde, 0x8e, 0x74, 0xff, 0xde, 0x8e, 0x73, 0xff,
+ 0xdf, 0x8e, 0x74, 0xff, 0xde, 0x8e, 0x73, 0xff,
+ 0xde, 0x8e, 0x74, 0xff, 0xde, 0x8e, 0x73, 0xff,
+ 0xdc, 0x8e, 0x71, 0xff, 0xdb, 0x8e, 0x70, 0xff,
+ 0xdc, 0x8e, 0x71, 0xff, 0xde, 0x92, 0x73, 0xff,
+ 0xdf, 0x8e, 0x74, 0xff, 0xde, 0x8c, 0x70, 0xff,
+ 0xde, 0x8a, 0x6b, 0xff, 0xde, 0x89, 0x6b, 0xff,
+ 0xdf, 0x8e, 0x74, 0xff, 0xde, 0x8e, 0x73, 0xff,
+ 0xe1, 0x95, 0x7c, 0xff, 0xe3, 0x9b, 0x83, 0xff,
+ 0xea, 0xa5, 0x8c, 0xff, 0xef, 0xb2, 0x9c, 0xff,
+ 0xec, 0xac, 0x94, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xe1, 0x92, 0x76, 0xff, 0xe6, 0x8a, 0x6b, 0xff,
+ 0xe7, 0x8a, 0x6b, 0xff, 0xe3, 0x8e, 0x70, 0xff,
+ 0xe7, 0x8b, 0x6e, 0xff, 0xe6, 0x8c, 0x70, 0xff,
+ 0xe7, 0x8d, 0x71, 0xff, 0xe6, 0x8c, 0x70, 0xff,
+ 0xe6, 0xa6, 0x8c, 0xff, 0xe6, 0xa6, 0x8b, 0xff,
+ 0x84, 0x70, 0x60, 0xff, 0xb5, 0x8b, 0x76, 0xff,
+ 0xe6, 0xa6, 0x8c, 0xff, 0xe6, 0xa3, 0x89, 0xff,
+ 0xe7, 0xa1, 0x87, 0xff, 0xe6, 0xa0, 0x86, 0xff,
+ 0xe6, 0x9e, 0x86, 0xff, 0xe6, 0x9d, 0x86, 0xff,
+ 0xe7, 0x9e, 0x87, 0xff, 0xe6, 0x9e, 0x86, 0xff,
+ 0xe4, 0xa1, 0x86, 0xff, 0xe6, 0xa6, 0x8b, 0xff,
+ 0xe4, 0xa1, 0x87, 0xff, 0xe3, 0xa0, 0x86, 0xff,
+ 0xe4, 0x9d, 0x81, 0xff, 0xe0, 0x97, 0x7e, 0xff,
+ 0xe1, 0x97, 0x7e, 0xff, 0xde, 0x91, 0x7b, 0xff,
+ 0xde, 0x92, 0x7b, 0xff, 0xde, 0x93, 0x78, 0xff,
+ 0xde, 0x92, 0x7c, 0xff, 0xde, 0x91, 0x7b, 0xff,
+ 0xde, 0x90, 0x79, 0xff, 0xde, 0x90, 0x78, 0xff,
+ 0xde, 0x8f, 0x76, 0xff, 0xde, 0x8d, 0x73, 0xff,
+ 0xd6, 0x8e, 0x7b, 0xff, 0xd8, 0x8c, 0x75, 0xff,
+ 0xdc, 0x8b, 0x71, 0xff, 0xdb, 0x8b, 0x70, 0xff,
+ 0xd9, 0x88, 0x6e, 0xff, 0xdb, 0x8b, 0x70, 0xff,
+ 0xd9, 0x88, 0x6e, 0xff, 0xd6, 0x85, 0x6b, 0xff,
+ 0xd9, 0x86, 0x68, 0xff, 0xdb, 0x89, 0x6d, 0xff,
+ 0xdc, 0x8a, 0x6e, 0xff, 0xdb, 0x89, 0x6d, 0xff,
+ 0xd9, 0x8a, 0x6e, 0xff, 0xd8, 0x89, 0x6d, 0xff,
+ 0xd9, 0x8a, 0x6e, 0xff, 0xdb, 0x8d, 0x70, 0xff,
+ 0xde, 0x8e, 0x73, 0xff, 0xde, 0x89, 0x6b, 0xff,
+ 0xde, 0x8a, 0x6b, 0xff, 0xde, 0x8c, 0x70, 0xff,
+ 0xde, 0x8e, 0x73, 0xff, 0xde, 0x8d, 0x73, 0xff,
+ 0xde, 0x8e, 0x73, 0xff, 0xe1, 0x94, 0x7b, 0xff,
+ 0xe9, 0xa5, 0x8c, 0xff, 0xeb, 0xab, 0x94, 0xff,
+ 0xec, 0xac, 0x94, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xde, 0x96, 0x7b, 0xff, 0xe3, 0x8d, 0x70, 0xff,
+ 0xe7, 0x8a, 0x6b, 0xff, 0xe6, 0x89, 0x6b, 0xff,
+ 0xe6, 0x8b, 0x6e, 0xff, 0xe6, 0x8d, 0x73, 0xff,
+ 0xe7, 0x8e, 0x73, 0xff, 0xe6, 0x8d, 0x73, 0xff,
+ 0xe7, 0xa6, 0x8c, 0xff, 0xe6, 0xa6, 0x8c, 0xff,
+ 0xe7, 0xa6, 0x8c, 0xff, 0xe6, 0xa6, 0x8c, 0xff,
+ 0xe7, 0xa6, 0x8c, 0xff, 0xe6, 0xa6, 0x8c, 0xff,
+ 0xe7, 0xa1, 0x87, 0xff, 0xe6, 0x9e, 0x84, 0xff,
+ 0xe7, 0x9a, 0x84, 0xff, 0xe6, 0x9a, 0x83, 0xff,
+ 0xe7, 0x9e, 0x87, 0xff, 0xe6, 0x9e, 0x86, 0xff,
+ 0xe4, 0xa1, 0x87, 0xff, 0xe6, 0xa6, 0x8c, 0xff,
+ 0xe4, 0xa1, 0x87, 0xff, 0xe1, 0x9b, 0x81, 0xff,
+ 0xde, 0x92, 0x7c, 0xff, 0xe1, 0x97, 0x7e, 0xff,
+ 0xdf, 0x92, 0x7c, 0xff, 0xe1, 0x97, 0x7e, 0xff,
+ 0xde, 0x93, 0x79, 0xff, 0xde, 0x91, 0x7b, 0xff,
+ 0xdf, 0x93, 0x79, 0xff, 0xde, 0x92, 0x7b, 0xff,
+ 0xde, 0x92, 0x7c, 0xff, 0xde, 0x91, 0x7b, 0xff,
+ 0xdf, 0x92, 0x7c, 0xff, 0xde, 0x8e, 0x73, 0xff,
+ 0xdc, 0x8b, 0x71, 0xff, 0xdb, 0x8b, 0x70, 0xff,
+ 0xdc, 0x8b, 0x71, 0xff, 0xdb, 0x8b, 0x70, 0xff,
+ 0xd9, 0x89, 0x6e, 0xff, 0xd8, 0x88, 0x6d, 0xff,
+ 0xd6, 0x86, 0x6b, 0xff, 0xd9, 0x88, 0x6e, 0xff,
+ 0xd9, 0x86, 0x68, 0xff, 0xd8, 0x85, 0x68, 0xff,
+ 0xd9, 0x86, 0x69, 0xff, 0xd6, 0x81, 0x63, 0xff,
+ 0xd6, 0x86, 0x6b, 0xff, 0xd8, 0x89, 0x6d, 0xff,
+ 0xd9, 0x8a, 0x6e, 0xff, 0xdb, 0x8e, 0x70, 0xff,
+ 0xde, 0x8e, 0x73, 0xff, 0xde, 0x8d, 0x73, 0xff,
+ 0xdf, 0x8d, 0x71, 0xff, 0xde, 0x8e, 0x73, 0xff,
+ 0xde, 0x8e, 0x73, 0xff, 0xde, 0x8d, 0x73, 0xff,
+ 0xe1, 0x95, 0x7c, 0xff, 0xe3, 0x9b, 0x84, 0xff,
+ 0xe9, 0xa5, 0x8c, 0xff, 0xec, 0xab, 0x94, 0xff,
+ 0xec, 0xac, 0x94, 0xff, 0xe6, 0x9e, 0x84, 0xff,
+ 0xe1, 0x92, 0x76, 0xff, 0xe3, 0x8d, 0x70, 0xff,
+ 0xe4, 0x8e, 0x71, 0xff, 0xe6, 0x8a, 0x6b, 0xff,
+ 0xe7, 0x8b, 0x6e, 0xff, 0xe6, 0x8c, 0x70, 0xff,
+ 0xe7, 0x8e, 0x74, 0xff, 0xe6, 0x8e, 0x73, 0xff,
+ 0xe6, 0xa6, 0x8c, 0xff, 0xe6, 0xa6, 0x8b, 0xff,
+ 0xe6, 0xa6, 0x8c, 0xff, 0xe6, 0xa5, 0x8b, 0xff,
+ 0xe6, 0xa3, 0x89, 0xff, 0xe6, 0xa3, 0x89, 0xff,
+ 0xe6, 0xa1, 0x86, 0xff, 0xe6, 0x9d, 0x83, 0xff,
+ 0xe6, 0x9a, 0x84, 0xff, 0xe6, 0x99, 0x83, 0xff,
+ 0xe6, 0x9a, 0x84, 0xff, 0xe6, 0x9d, 0x86, 0xff,
+ 0xe1, 0x9b, 0x81, 0xff, 0xe0, 0x9b, 0x81, 0xff,
+ 0xde, 0x96, 0x7b, 0xff, 0xde, 0x95, 0x7b, 0xff,
+ 0xe1, 0x97, 0x7e, 0xff, 0xde, 0x91, 0x7b, 0xff,
+ 0xde, 0x92, 0x7b, 0xff, 0xde, 0x91, 0x7b, 0xff,
+ 0xde, 0x93, 0x79, 0xff, 0xde, 0x91, 0x7b, 0xff,
+ 0xde, 0x92, 0x7b, 0xff, 0xde, 0x91, 0x7b, 0xff,
+ 0xde, 0x92, 0x7c, 0xff, 0xde, 0x91, 0x7b, 0xff,
+ 0xde, 0x92, 0x7b, 0xff, 0xde, 0x8f, 0x75, 0xff,
+ 0xd9, 0x8c, 0x76, 0xff, 0xd8, 0x8c, 0x76, 0xff,
+ 0xdb, 0x8b, 0x70, 0xff, 0xdb, 0x8a, 0x70, 0xff,
+ 0xdc, 0x8b, 0x71, 0xff, 0xde, 0x8d, 0x73, 0xff,
+ 0xdb, 0x8b, 0x70, 0xff, 0xdb, 0x8a, 0x70, 0xff,
+ 0xdc, 0x8a, 0x6e, 0xff, 0xd8, 0x85, 0x68, 0xff,
+ 0xd9, 0x86, 0x68, 0xff, 0xd8, 0x85, 0x68, 0xff,
+ 0xd9, 0x8a, 0x6e, 0xff, 0xd8, 0x89, 0x6d, 0xff,
+ 0xdb, 0x8e, 0x70, 0xff, 0xdb, 0x8d, 0x70, 0xff,
+ 0xde, 0x8e, 0x73, 0xff, 0xde, 0x8c, 0x70, 0xff,
+ 0xde, 0x8e, 0x73, 0xff, 0xde, 0x8d, 0x73, 0xff,
+ 0xde, 0x8e, 0x73, 0xff, 0xde, 0x8d, 0x73, 0xff,
+ 0xe1, 0x94, 0x7b, 0xff, 0xe6, 0xa1, 0x8b, 0xff,
+ 0xec, 0xac, 0x94, 0xff, 0xeb, 0xab, 0x94, 0xff,
+ 0xe9, 0xa5, 0x8c, 0xff, 0xe6, 0x9d, 0x83, 0xff,
+ 0xe1, 0x92, 0x76, 0xff, 0xe3, 0x8d, 0x70, 0xff,
+ 0xe4, 0x8e, 0x70, 0xff, 0xe3, 0x8d, 0x70, 0xff,
+ 0xe6, 0x8c, 0x71, 0xff, 0xe6, 0x8c, 0x70, 0xff,
+ 0xe6, 0x8b, 0x6e, 0xff, 0xe6, 0x8d, 0x73, 0xff,
+ 0x7c, 0x5e, 0x53, 0xff, 0xb5, 0x81, 0x73, 0xff,
+ 0xef, 0xa6, 0x94, 0xff, 0xee, 0xa6, 0x94, 0xff,
+ 0xe7, 0x9e, 0x84, 0xff, 0xe6, 0x9e, 0x84, 0xff,
+ 0xe7, 0x9e, 0x84, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xe4, 0x9c, 0x84, 0xff, 0xe4, 0x9b, 0x84, 0xff,
+ 0xe1, 0x99, 0x84, 0xff, 0xe1, 0x98, 0x83, 0xff,
+ 0xdf, 0x9a, 0x84, 0xff, 0xde, 0x97, 0x81, 0xff,
+ 0xde, 0x95, 0x7e, 0xff, 0xde, 0x94, 0x7e, 0xff,
+ 0xdf, 0x9a, 0x84, 0xff, 0xdb, 0x94, 0x7e, 0xff,
+ 0xd9, 0x8f, 0x79, 0xff, 0xd8, 0x8f, 0x78, 0xff,
+ 0xd6, 0x8e, 0x74, 0xff, 0xd6, 0x8e, 0x73, 0xff,
+ 0xd3, 0x8d, 0x74, 0xff, 0xd3, 0x8c, 0x73, 0xff,
+ 0xd4, 0x8e, 0x76, 0xff, 0xd0, 0x8a, 0x70, 0xff,
+ 0xd6, 0x92, 0x7c, 0xff, 0xd3, 0x8e, 0x76, 0xff,
+ 0xd6, 0x8e, 0x74, 0xff, 0xd6, 0x8b, 0x70, 0xff,
+ 0xd6, 0x86, 0x6b, 0xff, 0xd6, 0x88, 0x6e, 0xff,
+ 0xd6, 0x8a, 0x74, 0xff, 0xd6, 0x8a, 0x73, 0xff,
+ 0xd6, 0x87, 0x6e, 0xff, 0xd6, 0x87, 0x6e, 0xff,
+ 0xd6, 0x87, 0x6e, 0xff, 0xd6, 0x87, 0x6e, 0xff,
+ 0xd6, 0x85, 0x69, 0xff, 0xd6, 0x84, 0x68, 0xff,
+ 0xd9, 0x89, 0x6e, 0xff, 0xdb, 0x8b, 0x70, 0xff,
+ 0xde, 0x8e, 0x74, 0xff, 0xdb, 0x8b, 0x70, 0xff,
+ 0xdc, 0x8d, 0x76, 0xff, 0xdb, 0x8c, 0x76, 0xff,
+ 0xd9, 0x8f, 0x79, 0xff, 0xdb, 0x8c, 0x76, 0xff,
+ 0xdf, 0x92, 0x7c, 0xff, 0xde, 0x92, 0x7b, 0xff,
+ 0xe1, 0x9a, 0x84, 0xff, 0xe3, 0xa2, 0x8c, 0xff,
+ 0xf2, 0xb0, 0x9a, 0xff, 0xf1, 0xaf, 0x9a, 0xff,
+ 0xec, 0xa5, 0x8f, 0xff, 0xe6, 0x9a, 0x83, 0xff,
+ 0xe7, 0x92, 0x74, 0xff, 0xe6, 0x92, 0x73, 0xff,
+ 0xe7, 0x92, 0x74, 0xff, 0xe6, 0x92, 0x73, 0xff,
+ 0xe7, 0x8e, 0x71, 0xff, 0xe6, 0x8a, 0x6b, 0xff,
+ 0xe7, 0x8e, 0x71, 0xff, 0xe6, 0x89, 0x6b, 0xff,
+ 0x42, 0x39, 0x31, 0xff, 0x41, 0x38, 0x31, 0xff,
+ 0xb5, 0x82, 0x73, 0xff, 0xee, 0xa6, 0x94, 0xff,
+ 0xe6, 0x9e, 0x84, 0xff, 0xe6, 0x9d, 0x83, 0xff,
+ 0xe7, 0x9e, 0x84, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xe6, 0x9e, 0x84, 0xff, 0xe3, 0x9b, 0x83, 0xff,
+ 0xe4, 0x9b, 0x84, 0xff, 0xe3, 0x9b, 0x83, 0xff,
+ 0xde, 0x9a, 0x84, 0xff, 0xde, 0x99, 0x83, 0xff,
+ 0xde, 0x9a, 0x84, 0xff, 0xde, 0x91, 0x7b, 0xff,
+ 0xd9, 0x8f, 0x79, 0xff, 0xdb, 0x94, 0x7e, 0xff,
+ 0xd9, 0x8f, 0x79, 0xff, 0xd6, 0x89, 0x73, 0xff,
+ 0xd3, 0x8c, 0x73, 0xff, 0xd3, 0x8c, 0x73, 0xff,
+ 0xd3, 0x8d, 0x73, 0xff, 0xcd, 0x89, 0x73, 0xff,
+ 0xd0, 0x8a, 0x71, 0xff, 0xcd, 0x85, 0x6b, 0xff,
+ 0xd1, 0x8a, 0x71, 0xff, 0xd3, 0x8d, 0x76, 0xff,
+ 0xd6, 0x8b, 0x71, 0xff, 0xd5, 0x8b, 0x70, 0xff,
+ 0xd6, 0x8b, 0x71, 0xff, 0xd6, 0x88, 0x6d, 0xff,
+ 0xd6, 0x87, 0x6e, 0xff, 0xd5, 0x87, 0x6d, 0xff,
+ 0xd6, 0x82, 0x63, 0xff, 0xd6, 0x81, 0x62, 0xff,
+ 0xd6, 0x82, 0x63, 0xff, 0xd5, 0x81, 0x62, 0xff,
+ 0xd6, 0x84, 0x68, 0xff, 0xd6, 0x87, 0x6d, 0xff,
+ 0xd6, 0x86, 0x6b, 0xff, 0xd8, 0x88, 0x6d, 0xff,
+ 0xd9, 0x88, 0x6e, 0xff, 0xdb, 0x8b, 0x70, 0xff,
+ 0xde, 0x8a, 0x73, 0xff, 0xdb, 0x8c, 0x75, 0xff,
+ 0xdc, 0x8d, 0x76, 0xff, 0xdb, 0x8c, 0x76, 0xff,
+ 0xde, 0x92, 0x7b, 0xff, 0xe0, 0x99, 0x83, 0xff,
+ 0xe4, 0xa2, 0x8c, 0xff, 0xe6, 0xaa, 0x94, 0xff,
+ 0xf1, 0xaf, 0x9a, 0xff, 0xf1, 0xaf, 0x99, 0xff,
+ 0xec, 0xa5, 0x8f, 0xff, 0xe6, 0x9a, 0x83, 0xff,
+ 0xe6, 0x92, 0x73, 0xff, 0xe6, 0x91, 0x73, 0xff,
+ 0xe7, 0x92, 0x73, 0xff, 0xe6, 0x91, 0x73, 0xff,
+ 0xe6, 0x8e, 0x71, 0xff, 0xe6, 0x89, 0x6b, 0xff,
+ 0xe7, 0x8e, 0x71, 0xff, 0xe6, 0x89, 0x6b, 0xff,
+ 0x42, 0x39, 0x32, 0xff, 0x42, 0x38, 0x31, 0xff,
+ 0x7c, 0x5e, 0x53, 0xff, 0x7b, 0x5d, 0x52, 0xff,
+ 0xe7, 0x9e, 0x84, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xe7, 0x9e, 0x84, 0xff, 0xe6, 0x9e, 0x84, 0xff,
+ 0xe4, 0x9b, 0x84, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xe7, 0x9e, 0x84, 0xff, 0xe3, 0x9b, 0x84, 0xff,
+ 0xde, 0x97, 0x81, 0xff, 0xde, 0x97, 0x81, 0xff,
+ 0xdf, 0x98, 0x81, 0xff, 0xde, 0x92, 0x7b, 0xff,
+ 0xd9, 0x8f, 0x79, 0xff, 0xd6, 0x89, 0x73, 0xff,
+ 0xd6, 0x8a, 0x74, 0xff, 0xd9, 0x8f, 0x79, 0xff,
+ 0xd6, 0x8e, 0x73, 0xff, 0xd3, 0x8c, 0x73, 0xff,
+ 0xd4, 0x8d, 0x74, 0xff, 0xd3, 0x8c, 0x73, 0xff,
+ 0xd3, 0x8e, 0x76, 0xff, 0xd3, 0x8d, 0x76, 0xff,
+ 0xd4, 0x8e, 0x76, 0xff, 0xd3, 0x8e, 0x76, 0xff,
+ 0xd6, 0x8e, 0x73, 0xff, 0xd6, 0x8d, 0x73, 0xff,
+ 0xd6, 0x8e, 0x74, 0xff, 0xd6, 0x88, 0x6e, 0xff,
+ 0xd6, 0x85, 0x68, 0xff, 0xd6, 0x84, 0x68, 0xff,
+ 0xd6, 0x82, 0x63, 0xff, 0xd6, 0x81, 0x63, 0xff,
+ 0xd6, 0x87, 0x6e, 0xff, 0xd6, 0x84, 0x68, 0xff,
+ 0xd6, 0x87, 0x6e, 0xff, 0xd6, 0x87, 0x6e, 0xff,
+ 0xd9, 0x89, 0x6e, 0xff, 0xd6, 0x85, 0x6b, 0xff,
+ 0xd9, 0x89, 0x6e, 0xff, 0xdb, 0x8b, 0x70, 0xff,
+ 0xdc, 0x8d, 0x76, 0xff, 0xd8, 0x8f, 0x78, 0xff,
+ 0xd6, 0x92, 0x7c, 0xff, 0xd6, 0x92, 0x7b, 0xff,
+ 0xe1, 0x9a, 0x84, 0xff, 0xe1, 0x9a, 0x83, 0xff,
+ 0xe4, 0xa2, 0x8c, 0xff, 0xe6, 0xaa, 0x94, 0xff,
+ 0xf2, 0xb0, 0x9a, 0xff, 0xf7, 0xba, 0xa4, 0xff,
+ 0xf7, 0xbb, 0xa5, 0xff, 0xf1, 0xaf, 0x99, 0xff,
+ 0xe7, 0x9a, 0x7e, 0xff, 0xe6, 0x91, 0x73, 0xff,
+ 0xe7, 0x92, 0x74, 0xff, 0xe6, 0x92, 0x73, 0xff,
+ 0xe7, 0x92, 0x76, 0xff, 0xe6, 0x8d, 0x70, 0xff,
+ 0xe7, 0x8e, 0x71, 0xff, 0xe6, 0x8e, 0x70, 0xff,
+ 0x7c, 0x5d, 0x52, 0xff, 0x41, 0x38, 0x31, 0xff,
+ 0x7b, 0x5d, 0x52, 0xff, 0x7b, 0x5d, 0x52, 0xff,
+ 0x94, 0x69, 0x5b, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xe6, 0x9e, 0x84, 0xff, 0xe6, 0x9d, 0x83, 0xff,
+ 0xe6, 0x9e, 0x84, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xe6, 0x9e, 0x84, 0xff, 0xe0, 0x98, 0x83, 0xff,
+ 0xde, 0x97, 0x81, 0xff, 0xde, 0x94, 0x7e, 0xff,
+ 0xde, 0x94, 0x7e, 0xff, 0xde, 0x94, 0x7e, 0xff,
+ 0xd9, 0x8f, 0x79, 0xff, 0xd8, 0x8f, 0x78, 0xff,
+ 0xd9, 0x8f, 0x79, 0xff, 0xd8, 0x8f, 0x78, 0xff,
+ 0xd6, 0x8e, 0x73, 0xff, 0xd6, 0x8d, 0x73, 0xff,
+ 0xd3, 0x8c, 0x73, 0xff, 0xd5, 0x8d, 0x73, 0xff,
+ 0xd3, 0x8e, 0x76, 0xff, 0xd3, 0x8d, 0x76, 0xff,
+ 0xd3, 0x8e, 0x76, 0xff, 0xd5, 0x91, 0x7b, 0xff,
+ 0xd6, 0x8e, 0x73, 0xff, 0xd6, 0x8b, 0x70, 0xff,
+ 0xd6, 0x86, 0x6b, 0xff, 0xd5, 0x88, 0x6d, 0xff,
+ 0xd6, 0x87, 0x6e, 0xff, 0xd6, 0x84, 0x68, 0xff,
+ 0xd6, 0x84, 0x68, 0xff, 0xd5, 0x86, 0x6d, 0xff,
+ 0xd6, 0x8a, 0x73, 0xff, 0xd6, 0x89, 0x73, 0xff,
+ 0xd6, 0x8a, 0x73, 0xff, 0xd5, 0x89, 0x73, 0xff,
+ 0xd9, 0x88, 0x6e, 0xff, 0xd8, 0x88, 0x6d, 0xff,
+ 0xdb, 0x8b, 0x70, 0xff, 0xdb, 0x8a, 0x70, 0xff,
+ 0xdc, 0x8c, 0x76, 0xff, 0xdb, 0x8c, 0x76, 0xff,
+ 0xdb, 0x8c, 0x76, 0xff, 0xd5, 0x91, 0x7b, 0xff,
+ 0xde, 0x92, 0x7c, 0xff, 0xde, 0x91, 0x7b, 0xff,
+ 0xe1, 0x9a, 0x84, 0xff, 0xe0, 0x99, 0x83, 0xff,
+ 0xec, 0xa5, 0x8f, 0xff, 0xf6, 0xba, 0xa4, 0xff,
+ 0xf7, 0xba, 0xa5, 0xff, 0xf6, 0xba, 0xa4, 0xff,
+ 0xe6, 0xaa, 0x94, 0xff, 0xe6, 0x91, 0x73, 0xff,
+ 0xe6, 0x92, 0x73, 0xff, 0xe6, 0x91, 0x73, 0xff,
+ 0xe6, 0x96, 0x7c, 0xff, 0xe6, 0x8d, 0x70, 0xff,
+ 0xe6, 0x92, 0x76, 0xff, 0xe6, 0x91, 0x75, 0xff,
+ 0x53, 0x4d, 0x42, 0xff, 0x52, 0x4d, 0x42, 0xff,
+ 0x53, 0x4d, 0x42, 0xff, 0x70, 0x62, 0x52, 0xff,
+ 0xb5, 0x82, 0x6b, 0xff, 0xde, 0x9a, 0x84, 0xff,
+ 0xde, 0x9a, 0x84, 0xff, 0xde, 0x9a, 0x83, 0xff,
+ 0xdf, 0x9e, 0x84, 0xff, 0xde, 0x9e, 0x84, 0xff,
+ 0xde, 0x9e, 0x84, 0xff, 0xde, 0x96, 0x7e, 0xff,
+ 0xdc, 0x96, 0x7f, 0xff, 0xdb, 0x96, 0x7e, 0xff,
+ 0xd9, 0x92, 0x79, 0xff, 0xdb, 0x96, 0x7e, 0xff,
+ 0xdf, 0x92, 0x7c, 0xff, 0xd9, 0x8c, 0x76, 0xff,
+ 0xd9, 0x8d, 0x76, 0xff, 0xd8, 0x8c, 0x76, 0xff,
+ 0xd6, 0x8a, 0x71, 0xff, 0xd6, 0x8a, 0x70, 0xff,
+ 0xd6, 0x8a, 0x71, 0xff, 0xd6, 0x8e, 0x73, 0xff,
+ 0xd6, 0x8a, 0x76, 0xff, 0xd6, 0x8e, 0x79, 0xff,
+ 0xd6, 0x8e, 0x79, 0xff, 0xd6, 0x8e, 0x78, 0xff,
+ 0xd6, 0x8e, 0x7c, 0xff, 0xd6, 0x8b, 0x76, 0xff,
+ 0xd6, 0x86, 0x6b, 0xff, 0xd6, 0x88, 0x70, 0xff,
+ 0xd6, 0x85, 0x69, 0xff, 0xd6, 0x84, 0x68, 0xff,
+ 0xd6, 0x87, 0x6e, 0xff, 0xd6, 0x87, 0x6e, 0xff,
+ 0xd6, 0x87, 0x69, 0xff, 0xd6, 0x87, 0x68, 0xff,
+ 0xd6, 0x87, 0x69, 0xff, 0xd6, 0x87, 0x68, 0xff,
+ 0xd9, 0x86, 0x69, 0xff, 0xdb, 0x8a, 0x6e, 0xff,
+ 0xdc, 0x8a, 0x6e, 0xff, 0xdb, 0x89, 0x6e, 0xff,
+ 0xdc, 0x8a, 0x6e, 0xff, 0xde, 0x8e, 0x73, 0xff,
+ 0xdc, 0x8a, 0x6e, 0xff, 0xde, 0x8e, 0x73, 0xff,
+ 0xdf, 0x8f, 0x79, 0xff, 0xde, 0x94, 0x7e, 0xff,
+ 0xde, 0x95, 0x7e, 0xff, 0xde, 0x94, 0x7e, 0xff,
+ 0xdf, 0x92, 0x7c, 0xff, 0xe6, 0xa2, 0x8c, 0xff,
+ 0xe7, 0xa2, 0x8c, 0xff, 0xf7, 0xc2, 0xad, 0xff,
+ 0xf7, 0xbb, 0xa5, 0xff, 0xe6, 0x9f, 0x89, 0xff,
+ 0xde, 0x92, 0x7c, 0xff, 0xde, 0x92, 0x7b, 0xff,
+ 0xe7, 0x99, 0x81, 0xff, 0xe6, 0x98, 0x81, 0xff,
+ 0xe7, 0x92, 0x7c, 0xff, 0xe6, 0x92, 0x7b, 0xff,
+ 0x52, 0x4d, 0x42, 0xff, 0x70, 0x62, 0x52, 0xff,
+ 0x52, 0x4d, 0x42, 0xff, 0x52, 0x4d, 0x42, 0xff,
+ 0xc3, 0x8a, 0x73, 0xff, 0xde, 0x99, 0x83, 0xff,
+ 0xde, 0x9a, 0x84, 0xff, 0xde, 0x9a, 0x83, 0xff,
+ 0xde, 0x9a, 0x81, 0xff, 0xde, 0x99, 0x80, 0xff,
+ 0xde, 0x9e, 0x84, 0xff, 0xde, 0x9a, 0x81, 0xff,
+ 0xde, 0x9a, 0x84, 0xff, 0xdb, 0x95, 0x7e, 0xff,
+ 0xd9, 0x92, 0x79, 0xff, 0xd6, 0x8d, 0x73, 0xff,
+ 0xdb, 0x8f, 0x79, 0xff, 0xdb, 0x8f, 0x78, 0xff,
+ 0xdc, 0x8f, 0x79, 0xff, 0xd6, 0x89, 0x73, 0xff,
+ 0xd6, 0x8a, 0x71, 0xff, 0xd5, 0x89, 0x70, 0xff,
+ 0xd6, 0x8a, 0x71, 0xff, 0xd6, 0x89, 0x70, 0xff,
+ 0xd6, 0x8a, 0x76, 0xff, 0xd5, 0x8d, 0x78, 0xff,
+ 0xd6, 0x92, 0x7c, 0xff, 0xd6, 0x8d, 0x78, 0xff,
+ 0xd6, 0x8e, 0x7b, 0xff, 0xd5, 0x8b, 0x75, 0xff,
+ 0xd6, 0x86, 0x6b, 0xff, 0xd6, 0x85, 0x6b, 0xff,
+ 0xd6, 0x84, 0x68, 0xff, 0xd5, 0x87, 0x6d, 0xff,
+ 0xd6, 0x84, 0x68, 0xff, 0xd6, 0x84, 0x68, 0xff,
+ 0xd6, 0x84, 0x66, 0xff, 0xd5, 0x84, 0x65, 0xff,
+ 0xd6, 0x84, 0x66, 0xff, 0xd6, 0x87, 0x68, 0xff,
+ 0xdb, 0x8a, 0x6e, 0xff, 0xdb, 0x89, 0x6d, 0xff,
+ 0xdc, 0x8a, 0x6e, 0xff, 0xdb, 0x89, 0x6d, 0xff,
+ 0xdb, 0x8a, 0x6e, 0xff, 0xd8, 0x85, 0x68, 0xff,
+ 0xd9, 0x86, 0x68, 0xff, 0xdb, 0x89, 0x6d, 0xff,
+ 0xde, 0x8a, 0x73, 0xff, 0xde, 0x8f, 0x78, 0xff,
+ 0xde, 0x8a, 0x73, 0xff, 0xde, 0x89, 0x73, 0xff,
+ 0xde, 0x92, 0x7b, 0xff, 0xde, 0x91, 0x7b, 0xff,
+ 0xef, 0xb2, 0x9d, 0xff, 0xee, 0xb2, 0x9c, 0xff,
+ 0xef, 0xad, 0x97, 0xff, 0xee, 0xac, 0x96, 0xff,
+ 0xde, 0x92, 0x7c, 0xff, 0xe6, 0x9f, 0x89, 0xff,
+ 0xe6, 0x99, 0x81, 0xff, 0xe6, 0x98, 0x80, 0xff,
+ 0xe7, 0x99, 0x81, 0xff, 0xe6, 0x98, 0x81, 0xff,
+ 0x53, 0x4d, 0x42, 0xff, 0x70, 0x62, 0x52, 0xff,
+ 0x53, 0x4d, 0x42, 0xff, 0x70, 0x62, 0x52, 0xff,
+ 0xc3, 0x8a, 0x73, 0xff, 0xde, 0x9a, 0x83, 0xff,
+ 0xdf, 0x9a, 0x84, 0xff, 0xde, 0x9a, 0x84, 0xff,
+ 0xde, 0x96, 0x7e, 0xff, 0xde, 0x9a, 0x81, 0xff,
+ 0xdf, 0x9a, 0x81, 0xff, 0xde, 0x9a, 0x81, 0xff,
+ 0xdc, 0x96, 0x7e, 0xff, 0xdb, 0x96, 0x7e, 0xff,
+ 0xd9, 0x92, 0x79, 0xff, 0xd6, 0x8e, 0x73, 0xff,
+ 0xd9, 0x8d, 0x76, 0xff, 0xd6, 0x89, 0x73, 0xff,
+ 0xd6, 0x8a, 0x74, 0xff, 0xd6, 0x8a, 0x73, 0xff,
+ 0xd6, 0x8a, 0x71, 0xff, 0xd6, 0x89, 0x70, 0xff,
+ 0xd6, 0x8a, 0x71, 0xff, 0xd6, 0x8a, 0x70, 0xff,
+ 0xd6, 0x8e, 0x79, 0xff, 0xd6, 0x89, 0x76, 0xff,
+ 0xd6, 0x8e, 0x79, 0xff, 0xd6, 0x8a, 0x76, 0xff,
+ 0xd6, 0x89, 0x71, 0xff, 0xd6, 0x85, 0x6b, 0xff,
+ 0xd6, 0x86, 0x6b, 0xff, 0xd6, 0x85, 0x6b, 0xff,
+ 0xd6, 0x85, 0x68, 0xff, 0xd6, 0x84, 0x68, 0xff,
+ 0xd6, 0x85, 0x69, 0xff, 0xd6, 0x84, 0x68, 0xff,
+ 0xd6, 0x82, 0x63, 0xff, 0xd6, 0x81, 0x62, 0xff,
+ 0xd6, 0x82, 0x63, 0xff, 0xd6, 0x84, 0x65, 0xff,
+ 0xd9, 0x86, 0x68, 0xff, 0xd8, 0x85, 0x68, 0xff,
+ 0xd9, 0x86, 0x69, 0xff, 0xd9, 0x85, 0x68, 0xff,
+ 0xd9, 0x86, 0x68, 0xff, 0xd8, 0x85, 0x68, 0xff,
+ 0xd9, 0x86, 0x69, 0xff, 0xd9, 0x85, 0x68, 0xff,
+ 0xde, 0x8a, 0x73, 0xff, 0xde, 0x8f, 0x78, 0xff,
+ 0xdf, 0x8f, 0x79, 0xff, 0xde, 0x94, 0x7e, 0xff,
+ 0xde, 0x92, 0x7c, 0xff, 0xe6, 0xa2, 0x8c, 0xff,
+ 0xef, 0xb3, 0x9d, 0xff, 0xf7, 0xc2, 0xad, 0xff,
+ 0xf7, 0xba, 0xa5, 0xff, 0xee, 0xac, 0x97, 0xff,
+ 0xe7, 0xa0, 0x8a, 0xff, 0xe6, 0x9f, 0x89, 0xff,
+ 0xe7, 0xa6, 0x8c, 0xff, 0xe6, 0x9f, 0x86, 0xff,
+ 0xe7, 0x99, 0x81, 0xff, 0xe6, 0x92, 0x7b, 0xff,
+ 0x8f, 0x78, 0x63, 0xff, 0x8e, 0x78, 0x62, 0xff,
+ 0xad, 0x8e, 0x73, 0xff, 0xac, 0x8d, 0x73, 0xff,
+ 0xde, 0x9a, 0x84, 0xff, 0xde, 0x99, 0x83, 0xff,
+ 0xde, 0x9a, 0x84, 0xff, 0xde, 0x99, 0x83, 0xff,
+ 0xde, 0x9a, 0x81, 0xff, 0xde, 0x95, 0x7e, 0xff,
+ 0xde, 0x96, 0x7e, 0xff, 0xde, 0x91, 0x7b, 0xff,
+ 0xdc, 0x96, 0x7e, 0xff, 0xde, 0x99, 0x83, 0xff,
+ 0xd9, 0x92, 0x79, 0xff, 0xd5, 0x8d, 0x73, 0xff,
+ 0xd9, 0x8c, 0x76, 0xff, 0xd8, 0x8c, 0x76, 0xff,
+ 0xd6, 0x8a, 0x73, 0xff, 0xd5, 0x89, 0x73, 0xff,
+ 0xd6, 0x8a, 0x71, 0xff, 0xd6, 0x85, 0x6d, 0xff,
+ 0xd6, 0x82, 0x6b, 0xff, 0xd5, 0x85, 0x6d, 0xff,
+ 0xd6, 0x8a, 0x76, 0xff, 0xd6, 0x85, 0x73, 0xff,
+ 0xd6, 0x86, 0x73, 0xff, 0xd5, 0x89, 0x75, 0xff,
+ 0xd6, 0x88, 0x71, 0xff, 0xd6, 0x88, 0x70, 0xff,
+ 0xd6, 0x86, 0x6b, 0xff, 0xd5, 0x85, 0x6a, 0xff,
+ 0xd6, 0x84, 0x68, 0xff, 0xd6, 0x87, 0x6d, 0xff,
+ 0xd6, 0x87, 0x6e, 0xff, 0xd5, 0x84, 0x68, 0xff,
+ 0xd6, 0x84, 0x66, 0xff, 0xd6, 0x81, 0x62, 0xff,
+ 0xd6, 0x82, 0x63, 0xff, 0xd5, 0x81, 0x62, 0xff,
+ 0xd6, 0x82, 0x63, 0xff, 0xd6, 0x81, 0x62, 0xff,
+ 0xd9, 0x86, 0x68, 0xff, 0xd8, 0x85, 0x68, 0xff,
+ 0xd6, 0x82, 0x63, 0xff, 0xd8, 0x85, 0x68, 0xff,
+ 0xdb, 0x8a, 0x6e, 0xff, 0xdb, 0x89, 0x6d, 0xff,
+ 0xde, 0x8f, 0x79, 0xff, 0xde, 0x8f, 0x78, 0xff,
+ 0xde, 0x94, 0x7e, 0xff, 0xde, 0x99, 0x83, 0xff,
+ 0xe6, 0xa2, 0x8c, 0xff, 0xe6, 0xa2, 0x8b, 0xff,
+ 0xf7, 0xc2, 0xad, 0xff, 0xf6, 0xc2, 0xac, 0xff,
+ 0xf7, 0xba, 0xa5, 0xff, 0xee, 0xac, 0x96, 0xff,
+ 0xe6, 0x9f, 0x89, 0xff, 0xe6, 0x9f, 0x89, 0xff,
+ 0xe6, 0xa6, 0x8c, 0xff, 0xe6, 0x9f, 0x86, 0xff,
+ 0xe6, 0x98, 0x81, 0xff, 0xe6, 0x91, 0x7b, 0xff,
+ 0xe1, 0x9a, 0x87, 0xff, 0xe4, 0x9e, 0x89, 0xff,
+ 0xe7, 0xa2, 0x8c, 0xff, 0xe6, 0xa2, 0x8c, 0xff,
+ 0xe1, 0xa2, 0x8c, 0xff, 0xde, 0x9a, 0x84, 0xff,
+ 0xde, 0x9a, 0x84, 0xff, 0xde, 0x9a, 0x83, 0xff,
+ 0xdf, 0x96, 0x84, 0xff, 0xde, 0x96, 0x84, 0xff,
+ 0xde, 0x96, 0x84, 0xff, 0xde, 0x96, 0x83, 0xff,
+ 0xdf, 0x96, 0x84, 0xff, 0xdb, 0x92, 0x7e, 0xff,
+ 0xdc, 0x92, 0x7e, 0xff, 0xdb, 0x92, 0x7e, 0xff,
+ 0xd6, 0x92, 0x7c, 0xff, 0xd6, 0x8f, 0x79, 0xff,
+ 0xd6, 0x8d, 0x76, 0xff, 0xd6, 0x89, 0x73, 0xff,
+ 0xd4, 0x87, 0x6e, 0xff, 0xd3, 0x87, 0x6e, 0xff,
+ 0xd1, 0x85, 0x69, 0xff, 0xd0, 0x84, 0x68, 0xff,
+ 0xd1, 0x85, 0x6e, 0xff, 0xd0, 0x84, 0x6e, 0xff,
+ 0xd1, 0x85, 0x6e, 0xff, 0xd3, 0x87, 0x70, 0xff,
+ 0xd4, 0x87, 0x71, 0xff, 0xd0, 0x84, 0x6e, 0xff,
+ 0xd1, 0x85, 0x6e, 0xff, 0xd0, 0x84, 0x6e, 0xff,
+ 0xd4, 0x87, 0x6e, 0xff, 0xd6, 0x8a, 0x73, 0xff,
+ 0xd3, 0x87, 0x6e, 0xff, 0xcd, 0x81, 0x63, 0xff,
+ 0xd1, 0x7f, 0x60, 0xff, 0xd3, 0x80, 0x65, 0xff,
+ 0xd1, 0x7f, 0x60, 0xff, 0xd3, 0x80, 0x65, 0xff,
+ 0xd6, 0x82, 0x63, 0xff, 0xd6, 0x81, 0x63, 0xff,
+ 0xd9, 0x86, 0x69, 0xff, 0xdb, 0x89, 0x6e, 0xff,
+ 0xd6, 0x86, 0x6b, 0xff, 0xd6, 0x86, 0x6b, 0xff,
+ 0xd9, 0x8b, 0x74, 0xff, 0xdb, 0x90, 0x7b, 0xff,
+ 0xdf, 0x92, 0x7c, 0xff, 0xde, 0x92, 0x7b, 0xff,
+ 0xe1, 0x99, 0x84, 0xff, 0xe3, 0x9f, 0x8c, 0xff,
+ 0xdf, 0xa2, 0x8c, 0xff, 0xe6, 0xad, 0x97, 0xff,
+ 0xf7, 0xc3, 0xad, 0xff, 0xf7, 0xc2, 0xad, 0xff,
+ 0xef, 0xb7, 0xa5, 0xff, 0xec, 0xad, 0x9a, 0xff,
+ 0xe7, 0x9a, 0x84, 0xff, 0xe6, 0x9a, 0x83, 0xff,
+ 0xe7, 0x9e, 0x8c, 0xff, 0xe6, 0x9e, 0x8c, 0xff,
+ 0xe7, 0x99, 0x84, 0xff, 0xe6, 0x93, 0x7b, 0xff,
+ 0xe4, 0x9e, 0x89, 0xff, 0xe6, 0xa1, 0x8b, 0xff,
+ 0xe7, 0xa2, 0x8c, 0xff, 0xe3, 0x9e, 0x89, 0xff,
+ 0xe1, 0xa2, 0x8c, 0xff, 0xde, 0x99, 0x83, 0xff,
+ 0xe1, 0xa2, 0x8c, 0xff, 0xde, 0x9a, 0x83, 0xff,
+ 0xe4, 0xa1, 0x8f, 0xff, 0xe3, 0xa0, 0x8e, 0xff,
+ 0xe4, 0xa1, 0x8f, 0xff, 0xde, 0x95, 0x83, 0xff,
+ 0xde, 0x96, 0x84, 0xff, 0xdb, 0x91, 0x7e, 0xff,
+ 0xde, 0x96, 0x84, 0xff, 0xd8, 0x8d, 0x78, 0xff,
+ 0xd6, 0x8f, 0x79, 0xff, 0xd5, 0x8c, 0x75, 0xff,
+ 0xd6, 0x8d, 0x76, 0xff, 0xd6, 0x8c, 0x76, 0xff,
+ 0xd6, 0x8a, 0x73, 0xff, 0xd5, 0x89, 0x73, 0xff,
+ 0xd6, 0x8a, 0x73, 0xff, 0xd6, 0x89, 0x73, 0xff,
+ 0xd6, 0x8a, 0x73, 0xff, 0xd3, 0x87, 0x70, 0xff,
+ 0xd6, 0x8a, 0x73, 0xff, 0xd6, 0x89, 0x73, 0xff,
+ 0xd6, 0x8a, 0x73, 0xff, 0xd3, 0x87, 0x70, 0xff,
+ 0xd3, 0x87, 0x71, 0xff, 0xd3, 0x87, 0x70, 0xff,
+ 0xd3, 0x87, 0x6e, 0xff, 0xd3, 0x87, 0x6d, 0xff,
+ 0xd1, 0x84, 0x68, 0xff, 0xcd, 0x81, 0x62, 0xff,
+ 0xd0, 0x7f, 0x60, 0xff, 0xd0, 0x7e, 0x60, 0xff,
+ 0xd3, 0x80, 0x66, 0xff, 0xd3, 0x80, 0x65, 0xff,
+ 0xd6, 0x82, 0x63, 0xff, 0xd8, 0x85, 0x68, 0xff,
+ 0xdc, 0x8a, 0x6e, 0xff, 0xdb, 0x89, 0x6d, 0xff,
+ 0xd9, 0x8b, 0x73, 0xff, 0xd8, 0x8b, 0x73, 0xff,
+ 0xdc, 0x91, 0x7c, 0xff, 0xde, 0x95, 0x83, 0xff,
+ 0xe1, 0x99, 0x84, 0xff, 0xe0, 0x98, 0x83, 0xff,
+ 0xe4, 0x9f, 0x8c, 0xff, 0xe6, 0xa6, 0x94, 0xff,
+ 0xe6, 0xad, 0x97, 0xff, 0xee, 0xb7, 0xa1, 0xff,
+ 0xf7, 0xc3, 0xad, 0xff, 0xee, 0xb7, 0xa1, 0xff,
+ 0xec, 0xad, 0x9a, 0xff, 0xe9, 0xa3, 0x8e, 0xff,
+ 0xe7, 0x9a, 0x84, 0xff, 0xe6, 0x9a, 0x83, 0xff,
+ 0xe6, 0x93, 0x7b, 0xff, 0xe6, 0x98, 0x83, 0xff,
+ 0xe7, 0x93, 0x7c, 0xff, 0xe6, 0x93, 0x7b, 0xff,
+ 0xe4, 0x9e, 0x89, 0xff, 0xe3, 0x9e, 0x89, 0xff,
+ 0xe4, 0x9e, 0x8a, 0xff, 0xe3, 0x9e, 0x89, 0xff,
+ 0xe1, 0xa2, 0x8c, 0xff, 0xe1, 0xa2, 0x8c, 0xff,
+ 0xe1, 0xa2, 0x8c, 0xff, 0xe3, 0xaa, 0x94, 0xff,
+ 0xe9, 0xac, 0x9a, 0xff, 0xe9, 0xab, 0x99, 0xff,
+ 0xe4, 0xa1, 0x8f, 0xff, 0xde, 0x96, 0x84, 0xff,
+ 0xdc, 0x92, 0x7e, 0xff, 0xdb, 0x91, 0x7e, 0xff,
+ 0xd9, 0x8e, 0x79, 0xff, 0xd6, 0x8a, 0x73, 0xff,
+ 0xd6, 0x8a, 0x73, 0xff, 0xd6, 0x8c, 0x76, 0xff,
+ 0xd6, 0x8d, 0x76, 0xff, 0xd6, 0x8a, 0x73, 0xff,
+ 0xd3, 0x87, 0x6e, 0xff, 0xd3, 0x87, 0x6d, 0xff,
+ 0xd1, 0x85, 0x69, 0xff, 0xd0, 0x84, 0x68, 0xff,
+ 0xd3, 0x87, 0x71, 0xff, 0xd0, 0x84, 0x6d, 0xff,
+ 0xd4, 0x87, 0x71, 0xff, 0xd3, 0x87, 0x70, 0xff,
+ 0xd6, 0x8a, 0x73, 0xff, 0xd0, 0x84, 0x6d, 0xff,
+ 0xd4, 0x87, 0x71, 0xff, 0xd0, 0x84, 0x6e, 0xff,
+ 0xd3, 0x87, 0x6e, 0xff, 0xd3, 0x87, 0x6d, 0xff,
+ 0xce, 0x82, 0x63, 0xff, 0xce, 0x81, 0x63, 0xff,
+ 0xd1, 0x7f, 0x60, 0xff, 0xd0, 0x7f, 0x60, 0xff,
+ 0xd1, 0x7f, 0x60, 0xff, 0xd3, 0x80, 0x65, 0xff,
+ 0xd6, 0x82, 0x63, 0xff, 0xd8, 0x85, 0x68, 0xff,
+ 0xdc, 0x8a, 0x6e, 0xff, 0xde, 0x8e, 0x73, 0xff,
+ 0xdc, 0x91, 0x7c, 0xff, 0xdb, 0x90, 0x7b, 0xff,
+ 0xdf, 0x96, 0x84, 0xff, 0xde, 0x96, 0x84, 0xff,
+ 0xe1, 0x99, 0x84, 0xff, 0xe3, 0x9f, 0x8c, 0xff,
+ 0xe4, 0xa0, 0x8c, 0xff, 0xe6, 0xa6, 0x94, 0xff,
+ 0xef, 0xb8, 0xa2, 0xff, 0xf7, 0xc2, 0xad, 0xff,
+ 0xef, 0xb8, 0xa2, 0xff, 0xee, 0xb7, 0xa2, 0xff,
+ 0xec, 0xad, 0x9a, 0xff, 0xe9, 0xa3, 0x8e, 0xff,
+ 0xe7, 0x9a, 0x84, 0xff, 0xe6, 0x9a, 0x84, 0xff,
+ 0xe7, 0x93, 0x7c, 0xff, 0xe6, 0x8d, 0x73, 0xff,
+ 0xe7, 0x8e, 0x74, 0xff, 0xe6, 0x93, 0x7b, 0xff,
+ 0xde, 0x96, 0x84, 0xff, 0xe0, 0x99, 0x86, 0xff,
+ 0xe4, 0x9e, 0x89, 0xff, 0xe6, 0xa1, 0x8b, 0xff,
+ 0xe4, 0xaa, 0x94, 0xff, 0xe3, 0xaa, 0x94, 0xff,
+ 0xe6, 0xb2, 0x9c, 0xff, 0xe6, 0xb2, 0x9c, 0xff,
+ 0xef, 0xb6, 0xa5, 0xff, 0xe9, 0xab, 0x99, 0xff,
+ 0xe4, 0xa1, 0x8f, 0xff, 0xde, 0x95, 0x83, 0xff,
+ 0xdc, 0x92, 0x7e, 0xff, 0xd8, 0x8d, 0x78, 0xff,
+ 0xd9, 0x8e, 0x79, 0xff, 0xd5, 0x89, 0x73, 0xff,
+ 0xd6, 0x8a, 0x73, 0xff, 0xd6, 0x8c, 0x76, 0xff,
+ 0xd6, 0x8a, 0x73, 0xff, 0xd5, 0x89, 0x73, 0xff,
+ 0xd3, 0x87, 0x6e, 0xff, 0xd0, 0x84, 0x68, 0xff,
+ 0xce, 0x82, 0x63, 0xff, 0xd0, 0x84, 0x68, 0xff,
+ 0xce, 0x82, 0x6b, 0xff, 0xd0, 0x84, 0x6d, 0xff,
+ 0xd3, 0x87, 0x70, 0xff, 0xd0, 0x84, 0x6d, 0xff,
+ 0xd3, 0x87, 0x71, 0xff, 0xd0, 0x84, 0x6d, 0xff,
+ 0xce, 0x82, 0x6b, 0xff, 0xd0, 0x84, 0x6d, 0xff,
+ 0xd1, 0x84, 0x68, 0xff, 0xd0, 0x84, 0x68, 0xff,
+ 0xd0, 0x84, 0x68, 0xff, 0xd0, 0x84, 0x68, 0xff,
+ 0xd3, 0x80, 0x66, 0xff, 0xd0, 0x7e, 0x60, 0xff,
+ 0xd3, 0x80, 0x65, 0xff, 0xd5, 0x81, 0x6a, 0xff,
+ 0xd6, 0x82, 0x63, 0xff, 0xd6, 0x81, 0x62, 0xff,
+ 0xd9, 0x86, 0x68, 0xff, 0xdb, 0x89, 0x6d, 0xff,
+ 0xd9, 0x8b, 0x73, 0xff, 0xd8, 0x8b, 0x73, 0xff,
+ 0xdb, 0x90, 0x7b, 0xff, 0xdb, 0x90, 0x7b, 0xff,
+ 0xe1, 0x99, 0x84, 0xff, 0xe3, 0x9f, 0x8b, 0xff,
+ 0xe4, 0x9f, 0x8c, 0xff, 0xe6, 0xa5, 0x94, 0xff,
+ 0xde, 0xa2, 0x8c, 0xff, 0xee, 0xb7, 0xa1, 0xff,
+ 0xf7, 0xc2, 0xad, 0xff, 0xf6, 0xc2, 0xac, 0xff,
+ 0xec, 0xad, 0x9a, 0xff, 0xe9, 0xa3, 0x8e, 0xff,
+ 0xe6, 0x9a, 0x84, 0xff, 0xe6, 0x99, 0x83, 0xff,
+ 0xe6, 0x93, 0x7c, 0xff, 0xe6, 0x8d, 0x73, 0xff,
+ 0xe6, 0x8e, 0x73, 0xff, 0xe6, 0x8d, 0x73, 0xff,
+ 0xdf, 0x9a, 0x84, 0xff, 0xde, 0x9a, 0x84, 0xff,
+ 0xe4, 0xa4, 0x8c, 0xff, 0xe3, 0xa3, 0x8c, 0xff,
+ 0xea, 0xb1, 0x9a, 0xff, 0xef, 0xba, 0xa4, 0xff,
+ 0xef, 0xbb, 0xa5, 0xff, 0xee, 0xba, 0xa4, 0xff,
+ 0xef, 0xb3, 0xa5, 0xff, 0xe6, 0xa6, 0x97, 0xff,
+ 0xde, 0x9a, 0x89, 0xff, 0xd6, 0x8e, 0x7b, 0xff,
+ 0xd6, 0x8f, 0x79, 0xff, 0xd6, 0x8f, 0x79, 0xff,
+ 0xd6, 0x8d, 0x76, 0xff, 0xd6, 0x8c, 0x76, 0xff,
+ 0xd1, 0x89, 0x71, 0xff, 0xd3, 0x8b, 0x76, 0xff,
+ 0xd1, 0x89, 0x71, 0xff, 0xcd, 0x85, 0x6b, 0xff,
+ 0xd4, 0x85, 0x6b, 0xff, 0xd6, 0x81, 0x6b, 0xff,
+ 0xd6, 0x82, 0x6b, 0xff, 0xd3, 0x84, 0x6b, 0xff,
+ 0xd1, 0x87, 0x6e, 0xff, 0xd3, 0x88, 0x70, 0xff,
+ 0xd3, 0x89, 0x71, 0xff, 0xd0, 0x87, 0x6e, 0xff,
+ 0xd6, 0x86, 0x6b, 0xff, 0xd6, 0x86, 0x6b, 0xff,
+ 0xd6, 0x86, 0x6b, 0xff, 0xd6, 0x85, 0x6b, 0xff,
+ 0xd4, 0x87, 0x6b, 0xff, 0xd0, 0x84, 0x6b, 0xff,
+ 0xce, 0x82, 0x6b, 0xff, 0xd6, 0x89, 0x6b, 0xff,
+ 0xdc, 0x95, 0x7c, 0xff, 0xd6, 0x86, 0x6b, 0xff,
+ 0xd6, 0x86, 0x6b, 0xff, 0xd6, 0x85, 0x6b, 0xff,
+ 0xd6, 0x86, 0x6b, 0xff, 0xd6, 0x86, 0x6b, 0xff,
+ 0xdc, 0x91, 0x79, 0xff, 0xdb, 0x90, 0x78, 0xff,
+ 0xdf, 0x92, 0x7c, 0xff, 0xde, 0x92, 0x7b, 0xff,
+ 0xe1, 0x9a, 0x84, 0xff, 0xe1, 0x9a, 0x83, 0xff,
+ 0xdf, 0x9a, 0x84, 0xff, 0xe4, 0xa3, 0x8f, 0xff,
+ 0xe4, 0xa4, 0x8f, 0xff, 0xe3, 0xa3, 0x8e, 0xff,
+ 0xef, 0xb3, 0x9d, 0xff, 0xef, 0xb2, 0x9c, 0xff,
+ 0xf4, 0xb9, 0xa5, 0xff, 0xf4, 0xb9, 0xa4, 0xff,
+ 0xef, 0xaa, 0x9d, 0xff, 0xec, 0xa3, 0x91, 0xff,
+ 0xe7, 0x96, 0x7c, 0xff, 0xe6, 0x96, 0x7b, 0xff,
+ 0xe7, 0x95, 0x7f, 0xff, 0xe6, 0x94, 0x7e, 0xff,
+ 0xe7, 0x92, 0x7c, 0xff, 0xe6, 0x94, 0x7e, 0xff,
+ 0xe4, 0xa3, 0x8c, 0xff, 0xe3, 0xa3, 0x8b, 0xff,
+ 0xe9, 0xad, 0x94, 0xff, 0xee, 0xb6, 0x9c, 0xff,
+ 0xef, 0xba, 0xa5, 0xff, 0xee, 0xba, 0xa4, 0xff,
+ 0xef, 0xba, 0xa5, 0xff, 0xee, 0xba, 0xa4, 0xff,
+ 0xe6, 0xa6, 0x97, 0xff, 0xde, 0x99, 0x89, 0xff,
+ 0xde, 0x9a, 0x89, 0xff, 0xd6, 0x8d, 0x7b, 0xff,
+ 0xd6, 0x92, 0x7b, 0xff, 0xd5, 0x8f, 0x78, 0xff,
+ 0xd6, 0x8f, 0x79, 0xff, 0xd6, 0x8c, 0x76, 0xff,
+ 0xd3, 0x8b, 0x76, 0xff, 0xd0, 0x88, 0x70, 0xff,
+ 0xd3, 0x8b, 0x76, 0xff, 0xd0, 0x88, 0x70, 0xff,
+ 0xd3, 0x84, 0x6b, 0xff, 0xd5, 0x81, 0x6b, 0xff,
+ 0xd6, 0x82, 0x6b, 0xff, 0xd3, 0x84, 0x6b, 0xff,
+ 0xd0, 0x87, 0x6e, 0xff, 0xd5, 0x89, 0x73, 0xff,
+ 0xd3, 0x88, 0x71, 0xff, 0xd3, 0x88, 0x70, 0xff,
+ 0xd6, 0x86, 0x6b, 0xff, 0xd5, 0x84, 0x6d, 0xff,
+ 0xd6, 0x86, 0x6b, 0xff, 0xd6, 0x85, 0x6b, 0xff,
+ 0xd0, 0x84, 0x6b, 0xff, 0xd0, 0x84, 0x6b, 0xff,
+ 0xd1, 0x84, 0x6b, 0xff, 0xd3, 0x87, 0x6b, 0xff,
+ 0xdb, 0x95, 0x7b, 0xff, 0xe0, 0xa3, 0x8b, 0xff,
+ 0xdc, 0x95, 0x7c, 0xff, 0xd6, 0x85, 0x6b, 0xff,
+ 0xdb, 0x90, 0x79, 0xff, 0xd5, 0x85, 0x6b, 0xff,
+ 0xdc, 0x91, 0x79, 0xff, 0xdb, 0x90, 0x78, 0xff,
+ 0xde, 0x92, 0x7b, 0xff, 0xde, 0x91, 0x7b, 0xff,
+ 0xde, 0x92, 0x7c, 0xff, 0xe1, 0x9a, 0x83, 0xff,
+ 0xde, 0x9a, 0x84, 0xff, 0xde, 0x99, 0x83, 0xff,
+ 0xe4, 0xa3, 0x8f, 0xff, 0xe9, 0xac, 0x99, 0xff,
+ 0xef, 0xb2, 0x9c, 0xff, 0xf9, 0xbf, 0xac, 0xff,
+ 0xf4, 0xb9, 0xa5, 0xff, 0xee, 0xb2, 0x9c, 0xff,
+ 0xec, 0xa3, 0x91, 0xff, 0xe9, 0x9c, 0x86, 0xff,
+ 0xe9, 0x9d, 0x87, 0xff, 0xe6, 0x95, 0x7b, 0xff,
+ 0xe6, 0x97, 0x81, 0xff, 0xe6, 0x97, 0x80, 0xff,
+ 0xe7, 0x95, 0x7e, 0xff, 0xe6, 0x97, 0x81, 0xff,
+ 0xe9, 0xad, 0x94, 0xff, 0xe9, 0xac, 0x94, 0xff,
+ 0xef, 0xb7, 0x9d, 0xff, 0xee, 0xb6, 0x9c, 0xff,
+ 0xef, 0xba, 0xa5, 0xff, 0xee, 0xba, 0xa4, 0xff,
+ 0xe9, 0xb1, 0x9a, 0xff, 0xe3, 0xa7, 0x8e, 0xff,
+ 0xde, 0x9a, 0x89, 0xff, 0xde, 0x9a, 0x89, 0xff,
+ 0xdf, 0x9a, 0x8a, 0xff, 0xd6, 0x8e, 0x7b, 0xff,
+ 0xd6, 0x92, 0x7c, 0xff, 0xd6, 0x8f, 0x78, 0xff,
+ 0xd6, 0x8f, 0x79, 0xff, 0xd6, 0x8c, 0x76, 0xff,
+ 0xd3, 0x8b, 0x76, 0xff, 0xd0, 0x88, 0x70, 0xff,
+ 0xd1, 0x89, 0x71, 0xff, 0xd0, 0x88, 0x70, 0xff,
+ 0xd1, 0x87, 0x6b, 0xff, 0xd3, 0x84, 0x6b, 0xff,
+ 0xd4, 0x85, 0x6b, 0xff, 0xd3, 0x84, 0x6b, 0xff,
+ 0xd1, 0x87, 0x6e, 0xff, 0xd3, 0x88, 0x70, 0xff,
+ 0xd4, 0x89, 0x71, 0xff, 0xd0, 0x87, 0x6e, 0xff,
+ 0xd6, 0x86, 0x6b, 0xff, 0xd6, 0x84, 0x6d, 0xff,
+ 0xd6, 0x85, 0x6e, 0xff, 0xd6, 0x85, 0x6b, 0xff,
+ 0xd1, 0x85, 0x6b, 0xff, 0xd0, 0x84, 0x6b, 0xff,
+ 0xce, 0x82, 0x6b, 0xff, 0xce, 0x81, 0x6b, 0xff,
+ 0xdc, 0x95, 0x7c, 0xff, 0xe1, 0xa3, 0x8c, 0xff,
+ 0xe7, 0xb3, 0x9d, 0xff, 0xdb, 0x94, 0x7b, 0xff,
+ 0xdc, 0x91, 0x79, 0xff, 0xdb, 0x90, 0x78, 0xff,
+ 0xdc, 0x91, 0x79, 0xff, 0xdb, 0x90, 0x79, 0xff,
+ 0xde, 0x92, 0x7c, 0xff, 0xe1, 0x9a, 0x83, 0xff,
+ 0xdf, 0x92, 0x7c, 0xff, 0xe1, 0x9a, 0x84, 0xff,
+ 0xde, 0x9a, 0x84, 0xff, 0xe3, 0xa3, 0x8e, 0xff,
+ 0xe4, 0xa4, 0x8f, 0xff, 0xe9, 0xad, 0x99, 0xff,
+ 0xef, 0xb2, 0x9d, 0xff, 0xf9, 0xbf, 0xad, 0xff,
+ 0xff, 0xc7, 0xb5, 0xff, 0xee, 0xb2, 0x9c, 0xff,
+ 0xec, 0xa4, 0x92, 0xff, 0xe9, 0x9c, 0x86, 0xff,
+ 0xe7, 0x96, 0x7c, 0xff, 0xe9, 0x9c, 0x86, 0xff,
+ 0xe7, 0x97, 0x81, 0xff, 0xe6, 0x97, 0x81, 0xff,
+ 0xe7, 0x98, 0x81, 0xff, 0xe6, 0x97, 0x81, 0xff,
+ 0xef, 0xb6, 0x9c, 0xff, 0xee, 0xb6, 0x9c, 0xff,
+ 0xef, 0xb6, 0x9c, 0xff, 0xee, 0xb6, 0x9c, 0xff,
+ 0xe9, 0xb1, 0x9a, 0xff, 0xe3, 0xa7, 0x8e, 0xff,
+ 0xe4, 0xa7, 0x8f, 0xff, 0xde, 0x9d, 0x83, 0xff,
+ 0xde, 0x9a, 0x89, 0xff, 0xd6, 0x8d, 0x7b, 0xff,
+ 0xd6, 0x8e, 0x7b, 0xff, 0xd5, 0x8d, 0x7b, 0xff,
+ 0xd6, 0x8f, 0x79, 0xff, 0xd6, 0x8c, 0x76, 0xff,
+ 0xd6, 0x8c, 0x76, 0xff, 0xd5, 0x8c, 0x75, 0xff,
+ 0xd3, 0x8b, 0x76, 0xff, 0xd6, 0x8d, 0x7b, 0xff,
+ 0xd3, 0x8b, 0x76, 0xff, 0xd3, 0x8a, 0x75, 0xff,
+ 0xd1, 0x87, 0x6b, 0xff, 0xd0, 0x87, 0x6b, 0xff,
+ 0xd3, 0x84, 0x6b, 0xff, 0xd3, 0x84, 0x6a, 0xff,
+ 0xce, 0x86, 0x6b, 0xff, 0xd0, 0x87, 0x6d, 0xff,
+ 0xd0, 0x87, 0x6e, 0xff, 0xcd, 0x85, 0x6a, 0xff,
+ 0xd6, 0x86, 0x6b, 0xff, 0xd6, 0x84, 0x6d, 0xff,
+ 0xd6, 0x86, 0x6b, 0xff, 0xd5, 0x84, 0x6d, 0xff,
+ 0xd1, 0x84, 0x6b, 0xff, 0xd0, 0x84, 0x6b, 0xff,
+ 0xce, 0x82, 0x6b, 0xff, 0xcd, 0x81, 0x6a, 0xff,
+ 0xd6, 0x86, 0x6b, 0xff, 0xd6, 0x85, 0x6b, 0xff,
+ 0xe1, 0xa3, 0x8c, 0xff, 0xe6, 0xb2, 0x9c, 0xff,
+ 0xe6, 0xa6, 0x94, 0xff, 0xe6, 0xa6, 0x94, 0xff,
+ 0xe6, 0xa6, 0x94, 0xff, 0xe6, 0xa5, 0x94, 0xff,
+ 0xe6, 0xaa, 0x94, 0xff, 0xe6, 0xaa, 0x94, 0xff,
+ 0xe6, 0xaa, 0x94, 0xff, 0xe6, 0xaa, 0x94, 0xff,
+ 0xe9, 0xad, 0x9a, 0xff, 0xe9, 0xac, 0x99, 0xff,
+ 0xef, 0xb6, 0xa5, 0xff, 0xee, 0xb6, 0xa4, 0xff,
+ 0xfa, 0xc0, 0xad, 0xff, 0xff, 0xc6, 0xb5, 0xff,
+ 0xfa, 0xc0, 0xad, 0xff, 0xee, 0xb2, 0x9c, 0xff,
+ 0xe9, 0x9d, 0x87, 0xff, 0xe9, 0x9c, 0x86, 0xff,
+ 0xe6, 0x96, 0x7b, 0xff, 0xe6, 0x95, 0x7b, 0xff,
+ 0xe6, 0x9a, 0x84, 0xff, 0xe6, 0x97, 0x81, 0xff,
+ 0xe6, 0x9a, 0x84, 0xff, 0xe6, 0x99, 0x83, 0xff,
+ 0xef, 0xb7, 0xa5, 0xff, 0xef, 0xb6, 0xa4, 0xff,
+ 0xe9, 0xa9, 0x94, 0xff, 0xe9, 0xa8, 0x94, 0xff,
+ 0xe4, 0xa5, 0x92, 0xff, 0xde, 0x9e, 0x8c, 0xff,
+ 0xde, 0x9e, 0x8c, 0xff, 0xde, 0x9e, 0x8c, 0xff,
+ 0xdc, 0x98, 0x87, 0xff, 0xd6, 0x8e, 0x7b, 0xff,
+ 0xd6, 0x8e, 0x7c, 0xff, 0xd6, 0x8e, 0x7b, 0xff,
+ 0xdc, 0x8f, 0x79, 0xff, 0xd6, 0x8a, 0x73, 0xff,
+ 0xd6, 0x8a, 0x74, 0xff, 0xdb, 0x8f, 0x78, 0xff,
+ 0xd9, 0x8e, 0x76, 0xff, 0xd6, 0x8a, 0x73, 0xff,
+ 0xd9, 0x8e, 0x76, 0xff, 0xd6, 0x89, 0x73, 0xff,
+ 0xd6, 0x8a, 0x74, 0xff, 0xd6, 0x8a, 0x73, 0xff,
+ 0xd6, 0x8a, 0x74, 0xff, 0xd6, 0x89, 0x73, 0xff,
+ 0xd6, 0x8a, 0x74, 0xff, 0xd9, 0x8c, 0x76, 0xff,
+ 0xd6, 0x8a, 0x74, 0xff, 0xd6, 0x89, 0x73, 0xff,
+ 0xd6, 0x8a, 0x74, 0xff, 0xd6, 0x8a, 0x73, 0xff,
+ 0xd6, 0x8a, 0x74, 0xff, 0xd6, 0x89, 0x73, 0xff,
+ 0xd6, 0x8a, 0x74, 0xff, 0xd6, 0x8a, 0x73, 0xff,
+ 0xd6, 0x8a, 0x74, 0xff, 0xd6, 0x89, 0x73, 0xff,
+ 0xd6, 0x8a, 0x74, 0xff, 0xd6, 0x8a, 0x73, 0xff,
+ 0xd6, 0x8a, 0x74, 0xff, 0xe1, 0x97, 0x7e, 0xff,
+ 0xf7, 0xbb, 0xa5, 0xff, 0xf7, 0xba, 0xa4, 0xff,
+ 0xf7, 0xbb, 0xa5, 0xff, 0xf7, 0xba, 0xa4, 0xff,
+ 0xfa, 0xbc, 0xaa, 0xff, 0xff, 0xc6, 0xb5, 0xff,
+ 0xff, 0xc7, 0xb5, 0xff, 0xff, 0xc6, 0xb5, 0xff,
+ 0xfa, 0xc5, 0xb0, 0xff, 0xff, 0xd2, 0xbd, 0xff,
+ 0xff, 0xd3, 0xbe, 0xff, 0xff, 0xd2, 0xbd, 0xff,
+ 0xff, 0xcf, 0xb5, 0xff, 0xff, 0xce, 0xb5, 0xff,
+ 0xfa, 0xc0, 0xa8, 0xff, 0xee, 0xa2, 0x8c, 0xff,
+ 0xe7, 0x9e, 0x84, 0xff, 0xe6, 0x9e, 0x84, 0xff,
+ 0xe7, 0x9e, 0x84, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xe7, 0x9a, 0x7c, 0xff, 0xe9, 0x9f, 0x84, 0xff,
+ 0xe7, 0x9a, 0x7c, 0xff, 0xe9, 0x9f, 0x83, 0xff,
+ 0xef, 0xb6, 0xa5, 0xff, 0xeb, 0xaf, 0x9c, 0xff,
+ 0xe9, 0xa9, 0x94, 0xff, 0xe9, 0xa8, 0x94, 0xff,
+ 0xe4, 0xa5, 0x91, 0xff, 0xe3, 0xa4, 0x91, 0xff,
+ 0xe4, 0xa5, 0x92, 0xff, 0xe3, 0xa4, 0x91, 0xff,
+ 0xe1, 0xa1, 0x91, 0xff, 0xdb, 0x97, 0x86, 0xff,
+ 0xdc, 0x97, 0x87, 0xff, 0xdb, 0x97, 0x86, 0xff,
+ 0xe1, 0x95, 0x7e, 0xff, 0xe0, 0x94, 0x7e, 0xff,
+ 0xe1, 0x95, 0x7e, 0xff, 0xdb, 0x8f, 0x78, 0xff,
+ 0xd9, 0x8e, 0x76, 0xff, 0xd8, 0x8d, 0x75, 0xff,
+ 0xd9, 0x8e, 0x76, 0xff, 0xd8, 0x8d, 0x76, 0xff,
+ 0xd9, 0x8c, 0x76, 0xff, 0xdb, 0x8f, 0x78, 0xff,
+ 0xd9, 0x8d, 0x76, 0xff, 0xd6, 0x89, 0x73, 0xff,
+ 0xdb, 0x8f, 0x79, 0xff, 0xdb, 0x8f, 0x78, 0xff,
+ 0xdc, 0x8f, 0x79, 0xff, 0xdb, 0x8f, 0x78, 0xff,
+ 0xdb, 0x8f, 0x79, 0xff, 0xdb, 0x8f, 0x78, 0xff,
+ 0xdc, 0x8f, 0x79, 0xff, 0xdb, 0x8f, 0x78, 0xff,
+ 0xdb, 0x8f, 0x79, 0xff, 0xdb, 0x8f, 0x78, 0xff,
+ 0xdc, 0x8f, 0x79, 0xff, 0xdb, 0x8f, 0x78, 0xff,
+ 0xdb, 0x90, 0x79, 0xff, 0xdb, 0x90, 0x78, 0xff,
+ 0xdc, 0x91, 0x79, 0xff, 0xdb, 0x90, 0x78, 0xff,
+ 0xde, 0x96, 0x7b, 0xff, 0xf6, 0xba, 0xa4, 0xff,
+ 0xf7, 0xba, 0xa5, 0xff, 0xf6, 0xba, 0xa4, 0xff,
+ 0xfa, 0xbc, 0xaa, 0xff, 0xff, 0xc6, 0xb5, 0xff,
+ 0xff, 0xc7, 0xb5, 0xff, 0xff, 0xc6, 0xb5, 0xff,
+ 0xfa, 0xc5, 0xb0, 0xff, 0xf9, 0xc5, 0xaf, 0xff,
+ 0xfa, 0xc5, 0xb0, 0xff, 0xff, 0xd2, 0xbd, 0xff,
+ 0xfa, 0xc0, 0xa7, 0xff, 0xff, 0xce, 0xb5, 0xff,
+ 0xf4, 0xb1, 0x9a, 0xff, 0xee, 0xa2, 0x8c, 0xff,
+ 0xe9, 0xa2, 0x89, 0xff, 0xeb, 0xa6, 0x8e, 0xff,
+ 0xe9, 0xa2, 0x89, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xe9, 0x9f, 0x84, 0xff, 0xe9, 0x9f, 0x83, 0xff,
+ 0xec, 0xa5, 0x8c, 0xff, 0xec, 0xa4, 0x8c, 0xff,
+ 0xe9, 0xa9, 0x94, 0xff, 0xec, 0xaf, 0x9c, 0xff,
+ 0xec, 0xb0, 0x9d, 0xff, 0xe9, 0xa9, 0x94, 0xff,
+ 0xef, 0xb2, 0x9d, 0xff, 0xe9, 0xab, 0x97, 0xff,
+ 0xe9, 0xac, 0x97, 0xff, 0xde, 0x9e, 0x8c, 0xff,
+ 0xe1, 0xa1, 0x92, 0xff, 0xe1, 0xa0, 0x91, 0xff,
+ 0xdc, 0x98, 0x87, 0xff, 0xdb, 0x97, 0x86, 0xff,
+ 0xe1, 0x95, 0x7e, 0xff, 0xe6, 0x9a, 0x83, 0xff,
+ 0xe1, 0x95, 0x7f, 0xff, 0xe1, 0x94, 0x7e, 0xff,
+ 0xde, 0x96, 0x7c, 0xff, 0xdb, 0x91, 0x78, 0xff,
+ 0xdc, 0x92, 0x79, 0xff, 0xdb, 0x92, 0x79, 0xff,
+ 0xdc, 0x8f, 0x79, 0xff, 0xdb, 0x8f, 0x78, 0xff,
+ 0xdc, 0x8f, 0x79, 0xff, 0xdb, 0x8f, 0x79, 0xff,
+ 0xdc, 0x8f, 0x79, 0xff, 0xdb, 0x8f, 0x78, 0xff,
+ 0xdc, 0x8f, 0x79, 0xff, 0xdb, 0x8f, 0x79, 0xff,
+ 0xe1, 0x95, 0x7e, 0xff, 0xe1, 0x94, 0x7e, 0xff,
+ 0xe1, 0x95, 0x7f, 0xff, 0xe1, 0x94, 0x7e, 0xff,
+ 0xe1, 0x95, 0x7e, 0xff, 0xdb, 0x8f, 0x78, 0xff,
+ 0xe1, 0x95, 0x7f, 0xff, 0xe1, 0x94, 0x7e, 0xff,
+ 0xe1, 0x97, 0x7e, 0xff, 0xe1, 0x97, 0x7e, 0xff,
+ 0xe1, 0x98, 0x7f, 0xff, 0xe1, 0x97, 0x7e, 0xff,
+ 0xde, 0x96, 0x7c, 0xff, 0xe6, 0xa2, 0x89, 0xff,
+ 0xe7, 0xa2, 0x8a, 0xff, 0xee, 0xae, 0x97, 0xff,
+ 0xf4, 0xb1, 0x9f, 0xff, 0xf4, 0xb1, 0x9f, 0xff,
+ 0xf4, 0xb1, 0x9f, 0xff, 0xf4, 0xb1, 0x9f, 0xff,
+ 0xf4, 0xb8, 0xa2, 0xff, 0xee, 0xaa, 0x94, 0xff,
+ 0xef, 0xaa, 0x94, 0xff, 0xee, 0xaa, 0x94, 0xff,
+ 0xf4, 0xb1, 0x9a, 0xff, 0xf4, 0xb1, 0x99, 0xff,
+ 0xf4, 0xb1, 0x9a, 0xff, 0xee, 0xa2, 0x8c, 0xff,
+ 0xec, 0xa6, 0x8f, 0xff, 0xec, 0xa6, 0x8e, 0xff,
+ 0xec, 0xa6, 0x8f, 0xff, 0xec, 0xa6, 0x8e, 0xff,
+ 0xec, 0xa5, 0x8c, 0xff, 0xec, 0xa4, 0x8c, 0xff,
+ 0xec, 0xa5, 0x8c, 0xff, 0xec, 0xa5, 0x8c, 0xff,
+ 0xe6, 0xa2, 0x8c, 0xff, 0xe9, 0xa8, 0x94, 0xff,
+ 0xe9, 0xa9, 0x94, 0xff, 0xeb, 0xaf, 0x9c, 0xff,
+ 0xef, 0xb2, 0x9c, 0xff, 0xee, 0xb2, 0x9c, 0xff,
+ 0xef, 0xb2, 0x9c, 0xff, 0xee, 0xb2, 0x9c, 0xff,
+ 0xe6, 0xaa, 0x9c, 0xff, 0xe6, 0xaa, 0x9c, 0xff,
+ 0xe1, 0xa1, 0x91, 0xff, 0xe0, 0xa0, 0x91, 0xff,
+ 0xe6, 0x9a, 0x84, 0xff, 0xe6, 0x99, 0x83, 0xff,
+ 0xe1, 0x94, 0x7e, 0xff, 0xe0, 0x94, 0x7e, 0xff,
+ 0xdc, 0x92, 0x79, 0xff, 0xdb, 0x91, 0x78, 0xff,
+ 0xdb, 0x92, 0x79, 0xff, 0xdb, 0x91, 0x78, 0xff,
+ 0xde, 0x92, 0x7c, 0xff, 0xde, 0x91, 0x7b, 0xff,
+ 0xde, 0x92, 0x7b, 0xff, 0xdb, 0x8f, 0x78, 0xff,
+ 0xde, 0x92, 0x7c, 0xff, 0xde, 0x91, 0x7b, 0xff,
+ 0xde, 0x92, 0x7b, 0xff, 0xdb, 0x8f, 0x78, 0xff,
+ 0xe1, 0x95, 0x7e, 0xff, 0xe6, 0x99, 0x83, 0xff,
+ 0xe1, 0x94, 0x7e, 0xff, 0xe6, 0x99, 0x83, 0xff,
+ 0xe1, 0x95, 0x7e, 0xff, 0xe0, 0x94, 0x7e, 0xff,
+ 0xe6, 0x9a, 0x84, 0xff, 0xe0, 0x94, 0x7e, 0xff,
+ 0xe1, 0x97, 0x7e, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xe6, 0x9e, 0x84, 0xff, 0xe6, 0x9d, 0x83, 0xff,
+ 0xe6, 0xa2, 0x89, 0xff, 0xe6, 0xa2, 0x89, 0xff,
+ 0xe6, 0xa2, 0x89, 0xff, 0xe6, 0xa1, 0x89, 0xff,
+ 0xef, 0xa6, 0x94, 0xff, 0xee, 0xa6, 0x94, 0xff,
+ 0xef, 0xa6, 0x94, 0xff, 0xee, 0xa5, 0x94, 0xff,
+ 0xef, 0xaa, 0x94, 0xff, 0xee, 0xaa, 0x94, 0xff,
+ 0xef, 0xaa, 0x94, 0xff, 0xee, 0xaa, 0x94, 0xff,
+ 0xf4, 0xb1, 0x9a, 0xff, 0xee, 0xa2, 0x8b, 0xff,
+ 0xef, 0xa2, 0x8c, 0xff, 0xf4, 0xb0, 0x99, 0xff,
+ 0xef, 0xaa, 0x94, 0xff, 0xeb, 0xa6, 0x8e, 0xff,
+ 0xec, 0xa6, 0x8f, 0xff, 0xeb, 0xa5, 0x8e, 0xff,
+ 0xef, 0xaa, 0x94, 0xff, 0xeb, 0xa4, 0x8b, 0xff,
+ 0xef, 0xaa, 0x94, 0xff, 0xee, 0xaa, 0x94, 0xff,
+ 0xef, 0xaa, 0x95, 0xff, 0xef, 0xaa, 0x94, 0xff,
+ 0xf4, 0xb6, 0xa2, 0xff, 0xf4, 0xb6, 0xa2, 0xff,
+ 0xf7, 0xbb, 0xa5, 0xff, 0xf7, 0xba, 0xa4, 0xff,
+ 0xfa, 0xc7, 0xb3, 0xff, 0xf7, 0xba, 0xa4, 0xff,
+ 0xf2, 0xb3, 0x9d, 0xff, 0xec, 0xaa, 0x94, 0xff,
+ 0xec, 0xaa, 0x94, 0xff, 0xe6, 0xa2, 0x8c, 0xff,
+ 0xe4, 0xa1, 0x87, 0xff, 0xe1, 0x9b, 0x81, 0xff,
+ 0xde, 0x96, 0x7c, 0xff, 0xde, 0x96, 0x7b, 0xff,
+ 0xe1, 0x96, 0x7f, 0xff, 0xde, 0x92, 0x7b, 0xff,
+ 0xe1, 0x96, 0x7e, 0xff, 0xe1, 0x96, 0x7e, 0xff,
+ 0xdf, 0x92, 0x7c, 0xff, 0xde, 0x92, 0x7b, 0xff,
+ 0xde, 0x92, 0x7c, 0xff, 0xde, 0x92, 0x7b, 0xff,
+ 0xe1, 0x98, 0x79, 0xff, 0xe1, 0x97, 0x79, 0xff,
+ 0xde, 0x92, 0x74, 0xff, 0xe1, 0x97, 0x78, 0xff,
+ 0xdf, 0x9a, 0x84, 0xff, 0xde, 0x9a, 0x84, 0xff,
+ 0xe4, 0x9e, 0x87, 0xff, 0xe3, 0x9e, 0x86, 0xff,
+ 0xe7, 0x9a, 0x84, 0xff, 0xe6, 0x9a, 0x84, 0xff,
+ 0xe9, 0xa1, 0x89, 0xff, 0xe9, 0xa0, 0x89, 0xff,
+ 0xe7, 0x9e, 0x84, 0xff, 0xe6, 0x9e, 0x84, 0xff,
+ 0xe7, 0x9e, 0x84, 0xff, 0xec, 0xa3, 0x89, 0xff,
+ 0xef, 0xa2, 0x8c, 0xff, 0xf1, 0xa9, 0x91, 0xff,
+ 0xf2, 0xa9, 0x92, 0xff, 0xf1, 0xa8, 0x91, 0xff,
+ 0xef, 0xa6, 0x95, 0xff, 0xf4, 0xad, 0x97, 0xff,
+ 0xef, 0xa6, 0x94, 0xff, 0xf4, 0xad, 0x97, 0xff,
+ 0xf7, 0xaf, 0x95, 0xff, 0xf7, 0xae, 0x94, 0xff,
+ 0xf7, 0xae, 0x94, 0xff, 0xf7, 0xae, 0x94, 0xff,
+ 0xf7, 0xaa, 0x95, 0xff, 0xf7, 0xaa, 0x94, 0xff,
+ 0xf7, 0xaa, 0x94, 0xff, 0xf9, 0xaf, 0x97, 0xff,
+ 0xef, 0xaa, 0x8c, 0xff, 0xef, 0xaa, 0x8c, 0xff,
+ 0xef, 0xaa, 0x8c, 0xff, 0xee, 0xaa, 0x8c, 0xff,
+ 0xef, 0xaa, 0x8c, 0xff, 0xf4, 0xae, 0x91, 0xff,
+ 0xf4, 0xae, 0x92, 0xff, 0xee, 0xaa, 0x8c, 0xff,
+ 0xef, 0xaa, 0x94, 0xff, 0xf4, 0xb6, 0xa1, 0xff,
+ 0xfa, 0xc3, 0xb0, 0xff, 0xf9, 0xc2, 0xaf, 0xff,
+ 0xfa, 0xc6, 0xb2, 0xff, 0xf9, 0xc6, 0xb2, 0xff,
+ 0xfa, 0xc7, 0xb2, 0xff, 0xf6, 0xba, 0xa4, 0xff,
+ 0xec, 0xaa, 0x94, 0xff, 0xeb, 0xaa, 0x94, 0xff,
+ 0xec, 0xaa, 0x94, 0xff, 0xec, 0xaa, 0x94, 0xff,
+ 0xe4, 0xa1, 0x86, 0xff, 0xe3, 0xa0, 0x86, 0xff,
+ 0xe1, 0x9b, 0x81, 0xff, 0xde, 0x95, 0x7b, 0xff,
+ 0xe1, 0x96, 0x7e, 0xff, 0xe3, 0x99, 0x80, 0xff,
+ 0xe4, 0x9a, 0x81, 0xff, 0xe3, 0x9a, 0x81, 0xff,
+ 0xe1, 0x96, 0x7e, 0xff, 0xe0, 0x95, 0x7e, 0xff,
+ 0xe1, 0x96, 0x7e, 0xff, 0xe1, 0x95, 0x7e, 0xff,
+ 0xe1, 0x97, 0x79, 0xff, 0xe0, 0x97, 0x78, 0xff,
+ 0xe1, 0x97, 0x79, 0xff, 0xe1, 0x97, 0x78, 0xff,
+ 0xde, 0x9a, 0x84, 0xff, 0xe3, 0x9d, 0x86, 0xff,
+ 0xe9, 0xa2, 0x89, 0xff, 0xe9, 0xa2, 0x89, 0xff,
+ 0xe9, 0xa1, 0x89, 0xff, 0xe9, 0xa0, 0x89, 0xff,
+ 0xe9, 0xa1, 0x89, 0xff, 0xe9, 0xa0, 0x89, 0xff,
+ 0xec, 0xa3, 0x89, 0xff, 0xeb, 0xa3, 0x89, 0xff,
+ 0xec, 0xa3, 0x89, 0xff, 0xec, 0xa3, 0x89, 0xff,
+ 0xf1, 0xa9, 0x91, 0xff, 0xf1, 0xa8, 0x91, 0xff,
+ 0xf2, 0xa9, 0x92, 0xff, 0xf1, 0xa8, 0x91, 0xff,
+ 0xf4, 0xad, 0x97, 0xff, 0xf4, 0xac, 0x96, 0xff,
+ 0xf4, 0xad, 0x97, 0xff, 0xf9, 0xb3, 0x99, 0xff,
+ 0xfa, 0xb2, 0x9a, 0xff, 0xf9, 0xb2, 0x99, 0xff,
+ 0xfa, 0xb2, 0x9a, 0xff, 0xf9, 0xb2, 0x99, 0xff,
+ 0xfa, 0xaf, 0x97, 0xff, 0xf9, 0xaf, 0x96, 0xff,
+ 0xfa, 0xb0, 0x97, 0xff, 0xf9, 0xaf, 0x97, 0xff,
+ 0xf4, 0xaf, 0x91, 0xff, 0xee, 0xaa, 0x8b, 0xff,
+ 0xf4, 0xb0, 0x92, 0xff, 0xf4, 0xaf, 0x91, 0xff,
+ 0xfa, 0xb2, 0x97, 0xff, 0xf4, 0xae, 0x91, 0xff,
+ 0xf4, 0xae, 0x92, 0xff, 0xf4, 0xae, 0x91, 0xff,
+ 0xf4, 0xb6, 0xa2, 0xff, 0xf4, 0xb6, 0xa2, 0xff,
+ 0xfa, 0xc3, 0xb0, 0xff, 0xf9, 0xc2, 0xaf, 0xff,
+ 0xfd, 0xd3, 0xc0, 0xff, 0xfc, 0xd2, 0xc0, 0xff,
+ 0xfd, 0xd3, 0xc0, 0xff, 0xf9, 0xc6, 0xb2, 0xff,
+ 0xf7, 0xba, 0xa5, 0xff, 0xf1, 0xb2, 0x9c, 0xff,
+ 0xec, 0xaa, 0x94, 0xff, 0xec, 0xaa, 0x94, 0xff,
+ 0xe7, 0xa6, 0x8c, 0xff, 0xe3, 0xa0, 0x86, 0xff,
+ 0xe4, 0xa1, 0x87, 0xff, 0xe1, 0x9b, 0x81, 0xff,
+ 0xe1, 0x96, 0x7e, 0xff, 0xe3, 0x9a, 0x81, 0xff,
+ 0xe4, 0x9a, 0x81, 0xff, 0xe3, 0x9a, 0x81, 0xff,
+ 0xe4, 0x9a, 0x81, 0xff, 0xe1, 0x96, 0x7e, 0xff,
+ 0xe4, 0x9a, 0x81, 0xff, 0xe3, 0x9a, 0x81, 0xff,
+ 0xe1, 0x97, 0x79, 0xff, 0xe3, 0x9c, 0x7e, 0xff,
+ 0xe4, 0x9d, 0x7f, 0xff, 0xe6, 0xa2, 0x84, 0xff,
+ 0xe9, 0xa2, 0x89, 0xff, 0xe9, 0xa2, 0x89, 0xff,
+ 0xe9, 0xa2, 0x8a, 0xff, 0xe9, 0xa2, 0x89, 0xff,
+ 0xec, 0xa8, 0x8f, 0xff, 0xec, 0xa7, 0x8e, 0xff,
+ 0xec, 0xa8, 0x8f, 0xff, 0xec, 0xa7, 0x8e, 0xff,
+ 0xf2, 0xa9, 0x8f, 0xff, 0xf1, 0xa8, 0x8e, 0xff,
+ 0xf7, 0xae, 0x94, 0xff, 0xf7, 0xae, 0x94, 0xff,
+ 0xf2, 0xa9, 0x92, 0xff, 0xf4, 0xaf, 0x97, 0xff,
+ 0xf4, 0xb0, 0x97, 0xff, 0xf4, 0xaf, 0x97, 0xff,
+ 0xfa, 0xb4, 0x9a, 0xff, 0xf9, 0xb3, 0x99, 0xff,
+ 0xfa, 0xb4, 0x9a, 0xff, 0xf9, 0xb3, 0x99, 0xff,
+ 0xfd, 0xb6, 0x9f, 0xff, 0xfc, 0xb6, 0x9f, 0xff,
+ 0xfd, 0xb7, 0x9f, 0xff, 0xfc, 0xb6, 0x9f, 0xff,
+ 0xfd, 0xb5, 0x9a, 0xff, 0xfc, 0xb5, 0x99, 0xff,
+ 0xfd, 0xb5, 0x9a, 0xff, 0xfc, 0xb5, 0x99, 0xff,
+ 0xfa, 0xb5, 0x97, 0xff, 0xf4, 0xaf, 0x91, 0xff,
+ 0xfa, 0xb5, 0x97, 0xff, 0xf4, 0xaf, 0x91, 0xff,
+ 0xfa, 0xb2, 0x97, 0xff, 0xf9, 0xb2, 0x97, 0xff,
+ 0xf4, 0xae, 0x92, 0xff, 0xf9, 0xb2, 0x97, 0xff,
+ 0xf4, 0xb6, 0xa2, 0xff, 0xf9, 0xc2, 0xaf, 0xff,
+ 0xff, 0xce, 0xbd, 0xff, 0xff, 0xce, 0xbd, 0xff,
+ 0xfc, 0xd3, 0xc0, 0xff, 0xff, 0xde, 0xcd, 0xff,
+ 0xfc, 0xd3, 0xc0, 0xff, 0xf9, 0xc6, 0xb2, 0xff,
+ 0xf7, 0xba, 0xa5, 0xff, 0xf1, 0xb2, 0x9c, 0xff,
+ 0xf1, 0xb2, 0x9c, 0xff, 0xeb, 0xaa, 0x94, 0xff,
+ 0xe6, 0xa6, 0x8c, 0xff, 0xe6, 0xa6, 0x8b, 0xff,
+ 0xe4, 0xa1, 0x86, 0xff, 0xe0, 0x9b, 0x80, 0xff,
+ 0xe1, 0x96, 0x7e, 0xff, 0xe3, 0x99, 0x81, 0xff,
+ 0xe4, 0x9a, 0x81, 0xff, 0xe6, 0x9d, 0x83, 0xff,
+ 0xe4, 0x9a, 0x81, 0xff, 0xe0, 0x95, 0x7e, 0xff,
+ 0xe6, 0x9e, 0x84, 0xff, 0xe6, 0x9d, 0x83, 0xff,
+ 0xe6, 0xa2, 0x84, 0xff, 0xe3, 0x9c, 0x7e, 0xff,
+ 0xe4, 0x9d, 0x7e, 0xff, 0xe6, 0xa1, 0x83, 0xff,
+ 0xe9, 0xa2, 0x89, 0xff, 0xee, 0xa6, 0x8b, 0xff,
+ 0xef, 0xa6, 0x8c, 0xff, 0xee, 0xa5, 0x8b, 0xff,
+ 0xec, 0xa7, 0x8f, 0xff, 0xee, 0xae, 0x94, 0xff,
+ 0xec, 0xa7, 0x8f, 0xff, 0xee, 0xae, 0x94, 0xff,
+ 0xf7, 0xae, 0x94, 0xff, 0xf6, 0xae, 0x94, 0xff,
+ 0xf7, 0xae, 0x94, 0xff, 0xf6, 0xae, 0x94, 0xff,
+ 0xf4, 0xb0, 0x97, 0xff, 0xf6, 0xb6, 0x9c, 0xff,
+ 0xf7, 0xb6, 0x9c, 0xff, 0xf6, 0xb6, 0x9c, 0xff,
+ 0xfa, 0xb4, 0x9a, 0xff, 0xff, 0xba, 0x9c, 0xff,
+ 0xfa, 0xb3, 0x9a, 0xff, 0xff, 0xba, 0x9c, 0xff,
+ 0xff, 0xba, 0xa5, 0xff, 0xff, 0xba, 0xa4, 0xff,
+ 0xff, 0xba, 0xa5, 0xff, 0xff, 0xba, 0xa4, 0xff,
+ 0xff, 0xba, 0x9c, 0xff, 0xff, 0xba, 0x9c, 0xff,
+ 0xff, 0xba, 0x9c, 0xff, 0xff, 0xba, 0x9c, 0xff,
+ 0xff, 0xba, 0x9c, 0xff, 0xf9, 0xb4, 0x96, 0xff,
+ 0xff, 0xba, 0x9c, 0xff, 0xf9, 0xb4, 0x96, 0xff,
+ 0xff, 0xb6, 0x9c, 0xff, 0xff, 0xb6, 0x9c, 0xff,
+ 0xfa, 0xb2, 0x97, 0xff, 0xff, 0xb6, 0x9c, 0xff,
+ 0xfa, 0xbf, 0xa8, 0xff, 0xf9, 0xbe, 0xa7, 0xff,
+ 0xfd, 0xcf, 0xbb, 0xff, 0xff, 0xde, 0xcd, 0xff,
+ 0xff, 0xe7, 0xd4, 0xff, 0xff, 0xe7, 0xd3, 0xff,
+ 0xff, 0xdb, 0xc9, 0xff, 0xff, 0xce, 0xbd, 0xff,
+ 0xf5, 0xbd, 0xa5, 0xff, 0xf4, 0xbd, 0xa4, 0xff,
+ 0xef, 0xae, 0x94, 0xff, 0xee, 0xae, 0x94, 0xff,
+ 0xef, 0xaf, 0x95, 0xff, 0xec, 0xa7, 0x8f, 0xff,
+ 0xe9, 0xa1, 0x89, 0xff, 0xe6, 0x9a, 0x83, 0xff,
+ 0xe7, 0x9a, 0x7c, 0xff, 0xe6, 0x9a, 0x7b, 0xff,
+ 0xe9, 0x9e, 0x81, 0xff, 0xec, 0xa2, 0x86, 0xff,
+ 0xe7, 0x9a, 0x7c, 0xff, 0xe6, 0x9a, 0x7b, 0xff,
+ 0xe9, 0x9e, 0x81, 0xff, 0xec, 0xa2, 0x86, 0xff,
+ 0xec, 0xa2, 0x87, 0xff, 0xe6, 0x9e, 0x84, 0xff,
+ 0xec, 0xa2, 0x87, 0xff, 0xec, 0xa2, 0x86, 0xff,
+ 0xef, 0xa6, 0x8c, 0xff, 0xf1, 0xab, 0x91, 0xff,
+ 0xf2, 0xac, 0x92, 0xff, 0xf1, 0xab, 0x91, 0xff,
+ 0xef, 0xaf, 0x95, 0xff, 0xef, 0xae, 0x94, 0xff,
+ 0xef, 0xae, 0x94, 0xff, 0xee, 0xae, 0x94, 0xff,
+ 0xf7, 0xaf, 0x95, 0xff, 0xf9, 0xb5, 0x9a, 0xff,
+ 0xfa, 0xb5, 0x9a, 0xff, 0xf9, 0xb5, 0x99, 0xff,
+ 0xff, 0xb7, 0x9d, 0xff, 0xff, 0xb6, 0x9c, 0xff,
+ 0xff, 0xb6, 0x9d, 0xff, 0xff, 0xbe, 0xa4, 0xff,
+ 0xff, 0xbb, 0xa5, 0xff, 0xff, 0xc2, 0xad, 0xff,
+ 0xff, 0xbb, 0xa5, 0xff, 0xff, 0xc2, 0xad, 0xff,
+ 0xff, 0xbf, 0xa5, 0xff, 0xff, 0xbe, 0xa4, 0xff,
+ 0xff, 0xbf, 0xa5, 0xff, 0xff, 0xbe, 0xa4, 0xff,
+ 0xff, 0xc1, 0xaa, 0xff, 0xff, 0xba, 0xa4, 0xff,
+ 0xff, 0xc1, 0xaa, 0xff, 0xff, 0xba, 0xa4, 0xff,
+ 0xff, 0xbb, 0xa5, 0xff, 0xff, 0xc1, 0xaa, 0xff,
+ 0xff, 0xbb, 0xa5, 0xff, 0xff, 0xba, 0xa4, 0xff,
+ 0xff, 0xbb, 0x9d, 0xff, 0xff, 0xba, 0x9c, 0xff,
+ 0xff, 0xbb, 0x9d, 0xff, 0xff, 0xba, 0x9c, 0xff,
+ 0xf7, 0xae, 0x94, 0xff, 0xf9, 0xbe, 0xa7, 0xff,
+ 0xfc, 0xcf, 0xbb, 0xff, 0xff, 0xde, 0xcd, 0xff,
+ 0xff, 0xe7, 0xd3, 0xff, 0xff, 0xe6, 0xd3, 0xff,
+ 0xff, 0xe7, 0xd3, 0xff, 0xff, 0xda, 0xc8, 0xff,
+ 0xfa, 0xcc, 0xb5, 0xff, 0xf4, 0xbc, 0xa4, 0xff,
+ 0xf4, 0xbd, 0xa5, 0xff, 0xee, 0xae, 0x94, 0xff,
+ 0xef, 0xae, 0x94, 0xff, 0xeb, 0xa7, 0x8e, 0xff,
+ 0xe9, 0xa1, 0x89, 0xff, 0xe6, 0x9a, 0x83, 0xff,
+ 0xe9, 0x9e, 0x81, 0xff, 0xe9, 0x9d, 0x80, 0xff,
+ 0xec, 0xa2, 0x87, 0xff, 0xec, 0xa2, 0x86, 0xff,
+ 0xe9, 0x9e, 0x81, 0xff, 0xeb, 0xa1, 0x86, 0xff,
+ 0xec, 0xa2, 0x87, 0xff, 0xec, 0xa2, 0x86, 0xff,
+ 0xec, 0xa2, 0x86, 0xff, 0xeb, 0xa1, 0x86, 0xff,
+ 0xec, 0xa2, 0x87, 0xff, 0xf1, 0xa6, 0x89, 0xff,
+ 0xf1, 0xab, 0x91, 0xff, 0xf1, 0xab, 0x91, 0xff,
+ 0xf4, 0xb1, 0x97, 0xff, 0xf4, 0xb0, 0x97, 0xff,
+ 0xf4, 0xb2, 0x97, 0xff, 0xf4, 0xb2, 0x96, 0xff,
+ 0xf4, 0xb2, 0x97, 0xff, 0xf4, 0xb2, 0x97, 0xff,
+ 0xfa, 0xb5, 0x9a, 0xff, 0xf9, 0xb4, 0x99, 0xff,
+ 0xfa, 0xb5, 0x9a, 0xff, 0xfc, 0xbb, 0x9f, 0xff,
+ 0xff, 0xb6, 0x9c, 0xff, 0xff, 0xbe, 0xa4, 0xff,
+ 0xff, 0xbe, 0xa5, 0xff, 0xff, 0xbe, 0xa4, 0xff,
+ 0xff, 0xc2, 0xad, 0xff, 0xff, 0xc2, 0xac, 0xff,
+ 0xff, 0xc3, 0xad, 0xff, 0xff, 0xc2, 0xac, 0xff,
+ 0xff, 0xc5, 0xad, 0xff, 0xff, 0xc5, 0xac, 0xff,
+ 0xff, 0xc5, 0xad, 0xff, 0xff, 0xc5, 0xac, 0xff,
+ 0xff, 0xc8, 0xb0, 0xff, 0xff, 0xc1, 0xaa, 0xff,
+ 0xff, 0xc1, 0xaa, 0xff, 0xff, 0xc1, 0xaa, 0xff,
+ 0xff, 0xc1, 0xaa, 0xff, 0xff, 0xc1, 0xaa, 0xff,
+ 0xff, 0xc1, 0xaa, 0xff, 0xff, 0xc1, 0xaa, 0xff,
+ 0xff, 0xc0, 0xa5, 0xff, 0xff, 0xbf, 0xa4, 0xff,
+ 0xff, 0xc0, 0xa5, 0xff, 0xff, 0xbf, 0xa4, 0xff,
+ 0xfa, 0xbf, 0xa8, 0xff, 0xf9, 0xbe, 0xa7, 0xff,
+ 0xfa, 0xbf, 0xa8, 0xff, 0xff, 0xdf, 0xce, 0xff,
+ 0xff, 0xe7, 0xd3, 0xff, 0xff, 0xe6, 0xd3, 0xff,
+ 0xff, 0xe7, 0xd4, 0xff, 0xff, 0xe7, 0xd3, 0xff,
+ 0xff, 0xdb, 0xc6, 0xff, 0xf9, 0xcc, 0xb5, 0xff,
+ 0xfa, 0xcc, 0xb5, 0xff, 0xee, 0xae, 0x94, 0xff,
+ 0xef, 0xae, 0x94, 0xff, 0xec, 0xa7, 0x8e, 0xff,
+ 0xe9, 0xa1, 0x8a, 0xff, 0xe9, 0xa0, 0x89, 0xff,
+ 0xec, 0xa2, 0x87, 0xff, 0xec, 0xa2, 0x86, 0xff,
+ 0xec, 0xa2, 0x87, 0xff, 0xee, 0xa6, 0x8c, 0xff,
+ 0xec, 0xa2, 0x87, 0xff, 0xee, 0xa6, 0x8c, 0xff,
+ 0xef, 0xa6, 0x8c, 0xff, 0xec, 0xa2, 0x86, 0xff,
+ 0xec, 0xa2, 0x87, 0xff, 0xec, 0xa2, 0x86, 0xff,
+ 0xec, 0xa2, 0x87, 0xff, 0xf1, 0xa6, 0x89, 0xff,
+ 0xf2, 0xac, 0x92, 0xff, 0xf4, 0xb1, 0x97, 0xff,
+ 0xf4, 0xb1, 0x97, 0xff, 0xf4, 0xb1, 0x97, 0xff,
+ 0xfa, 0xb6, 0x9a, 0xff, 0xf9, 0xb6, 0x99, 0xff,
+ 0xfa, 0xb7, 0x9a, 0xff, 0xf9, 0xb6, 0x99, 0xff,
+ 0xfd, 0xbc, 0x9f, 0xff, 0xfc, 0xbb, 0x9f, 0xff,
+ 0xfd, 0xbc, 0x9f, 0xff, 0xfc, 0xbb, 0x9f, 0xff,
+ 0xff, 0xbf, 0xa5, 0xff, 0xff, 0xc6, 0xad, 0xff,
+ 0xff, 0xbf, 0xa5, 0xff, 0xff, 0xc6, 0xad, 0xff,
+ 0xff, 0xc3, 0xad, 0xff, 0xff, 0xca, 0xb5, 0xff,
+ 0xff, 0xcb, 0xb5, 0xff, 0xff, 0xca, 0xb5, 0xff,
+ 0xff, 0xcc, 0xb5, 0xff, 0xff, 0xcc, 0xb5, 0xff,
+ 0xff, 0xd3, 0xbe, 0xff, 0xff, 0xcc, 0xb5, 0xff,
+ 0xff, 0xc8, 0xb0, 0xff, 0xff, 0xc7, 0xaf, 0xff,
+ 0xff, 0xc8, 0xb0, 0xff, 0xff, 0xc8, 0xaf, 0xff,
+ 0xff, 0xc8, 0xb0, 0xff, 0xff, 0xc7, 0xaf, 0xff,
+ 0xff, 0xc8, 0xb0, 0xff, 0xff, 0xc8, 0xaf, 0xff,
+ 0xff, 0xc5, 0xad, 0xff, 0xff, 0xc5, 0xad, 0xff,
+ 0xff, 0xc5, 0xad, 0xff, 0xff, 0xc5, 0xad, 0xff,
+ 0xfc, 0xcf, 0xbb, 0xff, 0xfc, 0xce, 0xba, 0xff,
+ 0xfc, 0xce, 0xba, 0xff, 0xff, 0xde, 0xcd, 0xff,
+ 0xff, 0xe7, 0xd3, 0xff, 0xff, 0xf3, 0xde, 0xff,
+ 0xff, 0xf3, 0xde, 0xff, 0xff, 0xe6, 0xd3, 0xff,
+ 0xff, 0xdb, 0xc6, 0xff, 0xf9, 0xcb, 0xb5, 0xff,
+ 0xfa, 0xcc, 0xb5, 0xff, 0xf4, 0xbc, 0xa4, 0xff,
+ 0xec, 0xa7, 0x8f, 0xff, 0xe9, 0xa0, 0x89, 0xff,
+ 0xec, 0xa7, 0x8f, 0xff, 0xeb, 0xa7, 0x8e, 0xff,
+ 0xec, 0xa2, 0x87, 0xff, 0xee, 0xa6, 0x8b, 0xff,
+ 0xef, 0xa6, 0x8c, 0xff, 0xee, 0xa5, 0x8b, 0xff,
+ 0xef, 0xa6, 0x8c, 0xff, 0xee, 0xa6, 0x8b, 0xff,
+ 0xef, 0xa6, 0x8c, 0xff, 0xee, 0xa5, 0x8b, 0xff,
+ 0xec, 0xa2, 0x87, 0xff, 0xf1, 0xa6, 0x89, 0xff,
+ 0xf1, 0xa6, 0x89, 0xff, 0xf6, 0xaa, 0x8b, 0xff,
+ 0xf4, 0xb1, 0x97, 0xff, 0xf4, 0xb0, 0x96, 0xff,
+ 0xf7, 0xb6, 0x9c, 0xff, 0xf6, 0xb6, 0x9c, 0xff,
+ 0xff, 0xba, 0x9c, 0xff, 0xff, 0xba, 0x9c, 0xff,
+ 0xff, 0xba, 0x9c, 0xff, 0xff, 0xba, 0x9c, 0xff,
+ 0xfc, 0xbc, 0x9f, 0xff, 0xff, 0xc2, 0xa4, 0xff,
+ 0xff, 0xc2, 0xa5, 0xff, 0xff, 0xc2, 0xa4, 0xff,
+ 0xff, 0xc6, 0xad, 0xff, 0xff, 0xce, 0xb5, 0xff,
+ 0xff, 0xce, 0xb5, 0xff, 0xff, 0xce, 0xb4, 0xff,
+ 0xff, 0xd3, 0xbd, 0xff, 0xff, 0xd2, 0xbd, 0xff,
+ 0xff, 0xca, 0xb5, 0xff, 0xff, 0xd2, 0xbd, 0xff,
+ 0xff, 0xd3, 0xbd, 0xff, 0xff, 0xd2, 0xbd, 0xff,
+ 0xff, 0xd3, 0xbd, 0xff, 0xff, 0xd2, 0xbd, 0xff,
+ 0xff, 0xcf, 0xb5, 0xff, 0xff, 0xce, 0xb5, 0xff,
+ 0xff, 0xc8, 0xb0, 0xff, 0xff, 0xce, 0xb4, 0xff,
+ 0xff, 0xcf, 0xb5, 0xff, 0xff, 0xce, 0xb5, 0xff,
+ 0xff, 0xc8, 0xb0, 0xff, 0xff, 0xc7, 0xaf, 0xff,
+ 0xff, 0xcb, 0xb5, 0xff, 0xff, 0xca, 0xb5, 0xff,
+ 0xff, 0xca, 0xb5, 0xff, 0xff, 0xca, 0xb4, 0xff,
+ 0xff, 0xe3, 0xce, 0xff, 0xff, 0xe3, 0xce, 0xff,
+ 0xff, 0xe3, 0xce, 0xff, 0xff, 0xe3, 0xcd, 0xff,
+ 0xff, 0xf7, 0xe7, 0xff, 0xff, 0xf7, 0xe6, 0xff,
+ 0xff, 0xf7, 0xe7, 0xff, 0xec, 0xe1, 0xcb, 0xff,
+ 0xff, 0xdb, 0xc6, 0xff, 0xfc, 0xcd, 0xb5, 0xff,
+ 0xfa, 0xc0, 0xa5, 0xff, 0xf7, 0xb2, 0x94, 0xff,
+ 0xf5, 0xaf, 0x92, 0xff, 0xef, 0xa6, 0x8c, 0xff,
+ 0xef, 0xa6, 0x8c, 0xff, 0xee, 0xa6, 0x8c, 0xff,
+ 0xef, 0xa6, 0x8c, 0xff, 0xef, 0xa6, 0x8c, 0xff,
+ 0xf2, 0xac, 0x92, 0xff, 0xee, 0xa6, 0x8c, 0xff,
+ 0xef, 0xa6, 0x84, 0xff, 0xf4, 0xab, 0x89, 0xff,
+ 0xf4, 0xac, 0x89, 0xff, 0xf4, 0xab, 0x89, 0xff,
+ 0xef, 0xa6, 0x8c, 0xff, 0xf4, 0xab, 0x8f, 0xff,
+ 0xf4, 0xac, 0x8f, 0xff, 0xf4, 0xab, 0x8e, 0xff,
+ 0xff, 0xb3, 0x95, 0xff, 0xff, 0xb9, 0x9c, 0xff,
+ 0xff, 0xb9, 0x9d, 0xff, 0xff, 0xb9, 0x9c, 0xff,
+ 0xff, 0xbb, 0x9d, 0xff, 0xff, 0xc5, 0xa7, 0xff,
+ 0xff, 0xbb, 0x9d, 0xff, 0xff, 0xc5, 0xa7, 0xff,
+ 0xff, 0xc7, 0xad, 0xff, 0xff, 0xc6, 0xad, 0xff,
+ 0xff, 0xc7, 0xad, 0xff, 0xff, 0xc6, 0xad, 0xff,
+ 0xff, 0xd3, 0xb5, 0xff, 0xff, 0xd2, 0xb5, 0xff,
+ 0xff, 0xd3, 0xb5, 0xff, 0xff, 0xe0, 0xc5, 0xff,
+ 0xff, 0xd7, 0xc6, 0xff, 0xff, 0xd6, 0xc5, 0xff,
+ 0xff, 0xd7, 0xc6, 0xff, 0xff, 0xd6, 0xc5, 0xff,
+ 0xff, 0xdb, 0xc6, 0xff, 0xff, 0xdb, 0xc5, 0xff,
+ 0xff, 0xdb, 0xc6, 0xff, 0xff, 0xda, 0xc5, 0xff,
+ 0xff, 0xd7, 0xbe, 0xff, 0xff, 0xd6, 0xbd, 0xff,
+ 0xff, 0xd7, 0xbe, 0xff, 0xff, 0xd6, 0xbd, 0xff,
+ 0xff, 0xd3, 0xb5, 0xff, 0xff, 0xd2, 0xb5, 0xff,
+ 0xff, 0xd3, 0xb5, 0xff, 0xff, 0xd2, 0xb5, 0xff,
+ 0xff, 0xd3, 0xbe, 0xff, 0xff, 0xd2, 0xbd, 0xff,
+ 0xff, 0xd3, 0xbe, 0xff, 0xff, 0xd2, 0xbd, 0xff,
+ 0xff, 0xe3, 0xce, 0xff, 0xff, 0xe2, 0xcd, 0xff,
+ 0xff, 0xe3, 0xce, 0xff, 0xff, 0xe2, 0xcd, 0xff,
+ 0xff, 0xf7, 0xe6, 0xff, 0xff, 0xf6, 0xe6, 0xff,
+ 0xff, 0xf7, 0xe7, 0xff, 0xec, 0xe1, 0xcb, 0xff,
+ 0xfc, 0xcd, 0xb5, 0xff, 0xf9, 0xbf, 0xa4, 0xff,
+ 0xf7, 0xb2, 0x94, 0xff, 0xf6, 0xb2, 0x94, 0xff,
+ 0xf1, 0xaa, 0x8f, 0xff, 0xf4, 0xae, 0x91, 0xff,
+ 0xf2, 0xaa, 0x8f, 0xff, 0xf1, 0xaa, 0x8e, 0xff,
+ 0xf1, 0xab, 0x91, 0xff, 0xf1, 0xab, 0x91, 0xff,
+ 0xf2, 0xac, 0x92, 0xff, 0xf1, 0xab, 0x91, 0xff,
+ 0xf4, 0xab, 0x89, 0xff, 0xf4, 0xab, 0x89, 0xff,
+ 0xf4, 0xac, 0x89, 0xff, 0xf9, 0xb0, 0x8e, 0xff,
+ 0xfa, 0xb1, 0x91, 0xff, 0xf4, 0xab, 0x8e, 0xff,
+ 0xf4, 0xac, 0x8f, 0xff, 0xf9, 0xb0, 0x91, 0xff,
+ 0xff, 0xb2, 0x94, 0xff, 0xff, 0xb8, 0x9c, 0xff,
+ 0xff, 0xc0, 0xa5, 0xff, 0xff, 0xbf, 0xa4, 0xff,
+ 0xff, 0xc5, 0xa7, 0xff, 0xff, 0xc5, 0xa7, 0xff,
+ 0xff, 0xc5, 0xa7, 0xff, 0xff, 0xc5, 0xa7, 0xff,
+ 0xff, 0xc6, 0xad, 0xff, 0xff, 0xd2, 0xba, 0xff,
+ 0xff, 0xd3, 0xbb, 0xff, 0xff, 0xd2, 0xba, 0xff,
+ 0xff, 0xe0, 0xc6, 0xff, 0xff, 0xe0, 0xc5, 0xff,
+ 0xff, 0xe0, 0xc6, 0xff, 0xff, 0xe0, 0xc5, 0xff,
+ 0xff, 0xe3, 0xd3, 0xff, 0xff, 0xe2, 0xd3, 0xff,
+ 0xff, 0xef, 0xe1, 0xff, 0xff, 0xfb, 0xee, 0xff,
+ 0xff, 0xf7, 0xe6, 0xff, 0xff, 0xe4, 0xd0, 0xff,
+ 0xff, 0xe4, 0xd1, 0xff, 0xff, 0xda, 0xc5, 0xff,
+ 0xff, 0xe0, 0xc8, 0xff, 0xff, 0xe0, 0xc8, 0xff,
+ 0xff, 0xe0, 0xc8, 0xff, 0xff, 0xe0, 0xc8, 0xff,
+ 0xff, 0xe3, 0xcb, 0xff, 0xff, 0xda, 0xc0, 0xff,
+ 0xff, 0xdb, 0xc0, 0xff, 0xff, 0xda, 0xc0, 0xff,
+ 0xff, 0xd9, 0xc3, 0xff, 0xff, 0xd9, 0xc2, 0xff,
+ 0xff, 0xe0, 0xc8, 0xff, 0xff, 0xd9, 0xc2, 0xff,
+ 0xff, 0xe3, 0xce, 0xff, 0xff, 0xe2, 0xcd, 0xff,
+ 0xce, 0xb3, 0x97, 0xff, 0xff, 0xe3, 0xce, 0xff,
+ 0xff, 0xf7, 0xe7, 0xff, 0xff, 0xf7, 0xe6, 0xff,
+ 0xff, 0xf7, 0xe7, 0xff, 0xec, 0xe1, 0xcb, 0xff,
+ 0xfd, 0xcd, 0xb5, 0xff, 0xf9, 0xbf, 0xa4, 0xff,
+ 0xf7, 0xb3, 0x94, 0xff, 0xf7, 0xb2, 0x94, 0xff,
+ 0xf4, 0xae, 0x92, 0xff, 0xf1, 0xaa, 0x8e, 0xff,
+ 0xf4, 0xae, 0x92, 0xff, 0xf4, 0xae, 0x91, 0xff,
+ 0xf4, 0xb1, 0x97, 0xff, 0xf4, 0xb1, 0x97, 0xff,
+ 0xf4, 0xb1, 0x97, 0xff, 0xf1, 0xab, 0x91, 0xff,
+ 0xf4, 0xac, 0x89, 0xff, 0xf9, 0xb1, 0x8e, 0xff,
+ 0xff, 0xb7, 0x94, 0xff, 0xf9, 0xb1, 0x8e, 0xff,
+ 0xfa, 0xb1, 0x92, 0xff, 0xf9, 0xb1, 0x91, 0xff,
+ 0xfa, 0xb1, 0x92, 0xff, 0xf9, 0xb1, 0x91, 0xff,
+ 0xff, 0xb2, 0x94, 0xff, 0xff, 0xb9, 0x9c, 0xff,
+ 0xff, 0xc0, 0xa5, 0xff, 0xff, 0xbf, 0xa4, 0xff,
+ 0xff, 0xc5, 0xa8, 0xff, 0xff, 0xc5, 0xa7, 0xff,
+ 0xff, 0xc5, 0xa8, 0xff, 0xff, 0xd0, 0xb2, 0xff,
+ 0xff, 0xd3, 0xbb, 0xff, 0xff, 0xde, 0xc8, 0xff,
+ 0xff, 0xdf, 0xc9, 0xff, 0xff, 0xdf, 0xc8, 0xff,
+ 0xff, 0xe0, 0xc6, 0xff, 0xff, 0xed, 0xd6, 0xff,
+ 0xff, 0xee, 0xd6, 0xff, 0xff, 0xed, 0xd6, 0xff,
+ 0xff, 0xef, 0xe1, 0xff, 0xff, 0xef, 0xe1, 0xff,
+ 0xff, 0xef, 0xe1, 0xff, 0xff, 0xfb, 0xee, 0xff,
+ 0xff, 0xee, 0xdc, 0xff, 0xff, 0xed, 0xdb, 0xff,
+ 0xff, 0xee, 0xdc, 0xff, 0xff, 0xed, 0xdb, 0xff,
+ 0xff, 0xea, 0xd3, 0xff, 0xff, 0xe9, 0xd3, 0xff,
+ 0xff, 0xea, 0xd4, 0xff, 0xff, 0xe9, 0xd3, 0xff,
+ 0xff, 0xe3, 0xcb, 0xff, 0xff, 0xe2, 0xcb, 0xff,
+ 0xff, 0xe3, 0xcb, 0xff, 0xff, 0xe3, 0xcb, 0xff,
+ 0xff, 0xe0, 0xc8, 0xff, 0xff, 0xe0, 0xc8, 0xff,
+ 0xff, 0xe0, 0xc9, 0xff, 0xff, 0xe0, 0xc8, 0xff,
+ 0xce, 0xb2, 0x97, 0xff, 0x9c, 0x81, 0x60, 0xff,
+ 0x6b, 0x51, 0x29, 0xff, 0x6a, 0x50, 0x29, 0xff,
+ 0xc6, 0xb6, 0x94, 0xff, 0xd8, 0xcb, 0xaf, 0xff,
+ 0xec, 0xe1, 0xcb, 0xff, 0xff, 0xf6, 0xe6, 0xff,
+ 0xff, 0xdb, 0xc6, 0xff, 0xf9, 0xbf, 0xa4, 0xff,
+ 0xfa, 0xc0, 0xa5, 0xff, 0xf6, 0xb2, 0x94, 0xff,
+ 0xf4, 0xae, 0x91, 0xff, 0xf6, 0xb2, 0x94, 0xff,
+ 0xf7, 0xb2, 0x94, 0xff, 0xf6, 0xb2, 0x94, 0xff,
+ 0xf1, 0xac, 0x91, 0xff, 0xf4, 0xb0, 0x96, 0xff,
+ 0xf4, 0xb1, 0x97, 0xff, 0xf6, 0xb6, 0x9c, 0xff,
+ 0xfa, 0xb1, 0x8f, 0xff, 0xf9, 0xb0, 0x8e, 0xff,
+ 0xff, 0xb6, 0x94, 0xff, 0xf9, 0xb0, 0x8e, 0xff,
+ 0xfa, 0xb1, 0x91, 0xff, 0xf9, 0xb0, 0x91, 0xff,
+ 0xfa, 0xb1, 0x91, 0xff, 0xff, 0xb6, 0x94, 0xff,
+ 0xff, 0xb9, 0x9c, 0xff, 0xff, 0xbf, 0xa4, 0xff,
+ 0xff, 0xc6, 0xad, 0xff, 0xff, 0xc6, 0xac, 0xff,
+ 0xff, 0xd0, 0xb2, 0xff, 0xff, 0xcf, 0xb2, 0xff,
+ 0xff, 0xd0, 0xb2, 0xff, 0xff, 0xda, 0xbd, 0xff,
+ 0xff, 0xdf, 0xc8, 0xff, 0xff, 0xea, 0xd6, 0xff,
+ 0xff, 0xeb, 0xd6, 0xff, 0xff, 0xea, 0xd5, 0xff,
+ 0xff, 0xee, 0xd6, 0xff, 0xff, 0xed, 0xd6, 0xff,
+ 0xff, 0xfb, 0xe6, 0xff, 0xff, 0xfa, 0xe6, 0xff,
+ 0xff, 0xfb, 0xef, 0xff, 0xff, 0xfb, 0xee, 0xff,
+ 0xff, 0xfb, 0xef, 0xff, 0xff, 0xfa, 0xee, 0xff,
+ 0xff, 0xf7, 0xe6, 0xff, 0xff, 0xf7, 0xe6, 0xff,
+ 0xff, 0xf7, 0xe6, 0xff, 0xff, 0xf6, 0xe6, 0xff,
+ 0xff, 0xf3, 0xde, 0xff, 0xff, 0xf3, 0xde, 0xff,
+ 0xff, 0xf3, 0xde, 0xff, 0xff, 0xe9, 0xd3, 0xff,
+ 0xff, 0xeb, 0xd6, 0xff, 0xff, 0xea, 0xd6, 0xff,
+ 0xff, 0xe3, 0xcb, 0xff, 0xff, 0xe2, 0xca, 0xff,
+ 0xff, 0xe0, 0xc8, 0xff, 0xff, 0xe6, 0xcd, 0xff,
+ 0xff, 0xe7, 0xce, 0xff, 0xff, 0xdf, 0xc8, 0xff,
+ 0x84, 0x60, 0x4b, 0xff, 0x52, 0x35, 0x19, 0xff,
+ 0x9d, 0x76, 0x63, 0xff, 0x9c, 0x75, 0x63, 0xff,
+ 0x8c, 0x79, 0x63, 0xff, 0x8c, 0x78, 0x63, 0xff,
+ 0xc6, 0xb4, 0x9d, 0xff, 0xff, 0xef, 0xd6, 0xff,
+ 0xff, 0xe7, 0xce, 0xff, 0xf1, 0xcd, 0xb2, 0xff,
+ 0xe4, 0xb4, 0x97, 0xff, 0xe3, 0xb3, 0x97, 0xff,
+ 0xff, 0xb3, 0x95, 0xff, 0xff, 0xb2, 0x94, 0xff,
+ 0xff, 0xb6, 0x97, 0xff, 0xff, 0xb6, 0x97, 0xff,
+ 0xff, 0xb3, 0x95, 0xff, 0xff, 0xb7, 0x9a, 0xff,
+ 0xff, 0xbd, 0x9f, 0xff, 0xff, 0xbd, 0x9f, 0xff,
+ 0xff, 0xb9, 0x9d, 0xff, 0xff, 0xb9, 0x9c, 0xff,
+ 0xff, 0xb2, 0x94, 0xff, 0xff, 0xb2, 0x94, 0xff,
+ 0xff, 0xb7, 0x9d, 0xff, 0xff, 0xb6, 0x9c, 0xff,
+ 0xff, 0xb6, 0x9d, 0xff, 0xff, 0xbf, 0xa4, 0xff,
+ 0xff, 0xc3, 0xa5, 0xff, 0xff, 0xc2, 0xa4, 0xff,
+ 0xff, 0xc3, 0xa5, 0xff, 0xff, 0xcd, 0xaf, 0xff,
+ 0xff, 0xdb, 0xbe, 0xff, 0xff, 0xdb, 0xbd, 0xff,
+ 0xff, 0xdb, 0xbe, 0xff, 0xff, 0xe4, 0xc8, 0xff,
+ 0xff, 0xeb, 0xce, 0xff, 0xff, 0xf1, 0xd9, 0xff,
+ 0xff, 0xf9, 0xe4, 0xff, 0xff, 0xf8, 0xe3, 0xff,
+ 0xfd, 0xfe, 0xef, 0xff, 0xfc, 0xfe, 0xef, 0xff,
+ 0xfd, 0xfe, 0xef, 0xff, 0xf9, 0xfc, 0xf7, 0xff,
+ 0xfa, 0xfe, 0xf5, 0xff, 0xf9, 0xfe, 0xf4, 0xff,
+ 0xfa, 0xfe, 0xf4, 0xff, 0xf9, 0xfd, 0xf4, 0xff,
+ 0xfd, 0xfe, 0xef, 0xff, 0xfc, 0xfe, 0xef, 0xff,
+ 0xfd, 0xfe, 0xef, 0xff, 0xfc, 0xfd, 0xee, 0xff,
+ 0xfd, 0xfa, 0xea, 0xff, 0xfc, 0xfa, 0xe9, 0xff,
+ 0xff, 0xf7, 0xde, 0xff, 0xff, 0xf7, 0xde, 0xff,
+ 0xfd, 0xf2, 0xd9, 0xff, 0xfc, 0xf1, 0xd9, 0xff,
+ 0xff, 0xeb, 0xce, 0xff, 0xff, 0xeb, 0xcd, 0xff,
+ 0xff, 0xe7, 0xce, 0xff, 0xff, 0xe7, 0xce, 0xff,
+ 0xff, 0xe7, 0xce, 0xff, 0xff, 0xe7, 0xcd, 0xff,
+ 0x6b, 0x4a, 0x31, 0xff, 0x6b, 0x4a, 0x31, 0xff,
+ 0x9d, 0x76, 0x63, 0xff, 0x83, 0x60, 0x4a, 0xff,
+ 0x52, 0x3d, 0x29, 0xff, 0x52, 0x3c, 0x29, 0xff,
+ 0xc6, 0xb4, 0x9d, 0xff, 0xff, 0xef, 0xd6, 0xff,
+ 0xff, 0xe7, 0xce, 0xff, 0xf1, 0xcd, 0xb2, 0xff,
+ 0xf2, 0xcd, 0xb2, 0xff, 0xe3, 0xb3, 0x97, 0xff,
+ 0xff, 0xb6, 0x97, 0xff, 0xff, 0xb6, 0x96, 0xff,
+ 0xff, 0xb6, 0x97, 0xff, 0xff, 0xb2, 0x94, 0xff,
+ 0xff, 0xb8, 0x9a, 0xff, 0xff, 0xb7, 0x99, 0xff,
+ 0xff, 0xbd, 0x9f, 0xff, 0xff, 0xbd, 0x9f, 0xff,
+ 0xff, 0xc0, 0xa5, 0xff, 0xff, 0xbf, 0xa4, 0xff,
+ 0xff, 0xb9, 0x9d, 0xff, 0xff, 0xb9, 0x9c, 0xff,
+ 0xff, 0xb6, 0x9c, 0xff, 0xff, 0xbf, 0xa4, 0xff,
+ 0xff, 0xc0, 0xa5, 0xff, 0xff, 0xbf, 0xa4, 0xff,
+ 0xff, 0xc2, 0xa5, 0xff, 0xff, 0xc2, 0xa4, 0xff,
+ 0xff, 0xcd, 0xb0, 0xff, 0xff, 0xd8, 0xba, 0xff,
+ 0xff, 0xdb, 0xbd, 0xff, 0xff, 0xe4, 0xc8, 0xff,
+ 0xff, 0xe4, 0xc8, 0xff, 0xff, 0xed, 0xd3, 0xff,
+ 0xff, 0xf2, 0xd9, 0xff, 0xff, 0xf8, 0xe3, 0xff,
+ 0xff, 0xf8, 0xe4, 0xff, 0xff, 0xff, 0xee, 0xff,
+ 0xfc, 0xfe, 0xef, 0xff, 0xf9, 0xfc, 0xf6, 0xff,
+ 0xfa, 0xfd, 0xf7, 0xff, 0xf9, 0xfc, 0xf6, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xf9, 0xff,
+ 0xfc, 0xfd, 0xfa, 0xff, 0xfc, 0xfc, 0xf9, 0xff,
+ 0xf7, 0xfb, 0xff, 0xff, 0xf6, 0xfb, 0xff, 0xff,
+ 0xfa, 0xfd, 0xf7, 0xff, 0xf9, 0xfc, 0xf6, 0xff,
+ 0xfa, 0xfc, 0xf4, 0xff, 0xf9, 0xfc, 0xf4, 0xff,
+ 0xfc, 0xfa, 0xe9, 0xff, 0xf9, 0xfc, 0xf4, 0xff,
+ 0xfa, 0xf8, 0xe4, 0xff, 0xf9, 0xf8, 0xe3, 0xff,
+ 0xfc, 0xf2, 0xd9, 0xff, 0xfc, 0xf1, 0xd8, 0xff,
+ 0xff, 0xee, 0xd6, 0xff, 0xff, 0xed, 0xd5, 0xff,
+ 0xff, 0xee, 0xd6, 0xff, 0xff, 0xe6, 0xcd, 0xff,
+ 0x6b, 0x4a, 0x32, 0xff, 0x6b, 0x4a, 0x31, 0xff,
+ 0x53, 0x35, 0x19, 0xff, 0x52, 0x35, 0x19, 0xff,
+ 0x53, 0x3d, 0x29, 0xff, 0x52, 0x3c, 0x29, 0xff,
+ 0x53, 0x3d, 0x2a, 0xff, 0xc5, 0xb3, 0x9c, 0xff,
+ 0xff, 0xe7, 0xce, 0xff, 0xff, 0xe6, 0xcd, 0xff,
+ 0xf2, 0xcd, 0xb3, 0xff, 0xf1, 0xcd, 0xb2, 0xff,
+ 0xff, 0xba, 0x9a, 0xff, 0xff, 0xb2, 0x94, 0xff,
+ 0xff, 0xb7, 0x97, 0xff, 0xff, 0xb6, 0x97, 0xff,
+ 0xff, 0xb8, 0x9a, 0xff, 0xff, 0xb7, 0x99, 0xff,
+ 0xff, 0xbd, 0x9f, 0xff, 0xff, 0xbd, 0x9f, 0xff,
+ 0xff, 0xc0, 0xa5, 0xff, 0xff, 0xbf, 0xa4, 0xff,
+ 0xff, 0xc0, 0xa5, 0xff, 0xff, 0xbf, 0xa4, 0xff,
+ 0xff, 0xc0, 0xa5, 0xff, 0xff, 0xbf, 0xa4, 0xff,
+ 0xff, 0xc0, 0xa5, 0xff, 0xff, 0xc9, 0xad, 0xff,
+ 0xff, 0xcd, 0xb0, 0xff, 0xff, 0xd8, 0xba, 0xff,
+ 0xff, 0xd8, 0xbb, 0xff, 0xff, 0xe3, 0xc5, 0xff,
+ 0xff, 0xe4, 0xc8, 0xff, 0xff, 0xed, 0xd3, 0xff,
+ 0xff, 0xee, 0xd4, 0xff, 0xff, 0xf7, 0xde, 0xff,
+ 0xff, 0xf9, 0xe4, 0xff, 0xff, 0xf8, 0xe3, 0xff,
+ 0xff, 0xff, 0xef, 0xff, 0xff, 0xff, 0xee, 0xff,
+ 0xfa, 0xfd, 0xf7, 0xff, 0xf9, 0xfc, 0xf7, 0xff,
+ 0xfa, 0xfd, 0xf7, 0xff, 0xf7, 0xfb, 0xff, 0xff,
+ 0xfd, 0xfd, 0xfa, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xf9, 0xff,
+ 0xfa, 0xfd, 0xf7, 0xff, 0xf7, 0xfb, 0xff, 0xff,
+ 0xf7, 0xfb, 0xff, 0xff, 0xf9, 0xfc, 0xf7, 0xff,
+ 0xfa, 0xfd, 0xf4, 0xff, 0xf9, 0xfc, 0xf4, 0xff,
+ 0xfa, 0xfd, 0xf4, 0xff, 0xf9, 0xfc, 0xf4, 0xff,
+ 0xf7, 0xff, 0xef, 0xff, 0xf9, 0xf8, 0xe3, 0xff,
+ 0xf7, 0xff, 0xef, 0xff, 0xf9, 0xf8, 0xe3, 0xff,
+ 0xff, 0xf4, 0xde, 0xff, 0xff, 0xf4, 0xde, 0xff,
+ 0xff, 0xee, 0xd6, 0xff, 0xff, 0xf4, 0xde, 0xff,
+ 0x6b, 0x4a, 0x32, 0xff, 0x6b, 0x4a, 0x31, 0xff,
+ 0x52, 0x35, 0x19, 0xff, 0x52, 0x34, 0x18, 0xff,
+ 0x8c, 0x78, 0x63, 0xff, 0x52, 0x3c, 0x29, 0xff,
+ 0x52, 0x3d, 0x29, 0xff, 0x8b, 0x78, 0x62, 0xff,
+ 0xd6, 0x9a, 0x7c, 0xff, 0xff, 0xe6, 0xcd, 0xff,
+ 0xf1, 0xcd, 0xb2, 0xff, 0xf1, 0xcd, 0xb2, 0xff,
+ 0xff, 0xbe, 0x9c, 0xff, 0xff, 0xba, 0x99, 0xff,
+ 0xff, 0xba, 0x9a, 0xff, 0xff, 0xba, 0x99, 0xff,
+ 0xff, 0xbd, 0x9f, 0xff, 0xff, 0xbd, 0x9f, 0xff,
+ 0xff, 0xc2, 0xa5, 0xff, 0xff, 0xc2, 0xa4, 0xff,
+ 0xff, 0xc0, 0xa5, 0xff, 0xff, 0xc6, 0xac, 0xff,
+ 0xff, 0xc6, 0xad, 0xff, 0xff, 0xc6, 0xac, 0xff,
+ 0xff, 0xc9, 0xad, 0xff, 0xff, 0xc9, 0xac, 0xff,
+ 0xff, 0xc9, 0xad, 0xff, 0xff, 0xd2, 0xb4, 0xff,
+ 0xff, 0xd8, 0xbb, 0xff, 0xff, 0xd8, 0xba, 0xff,
+ 0xff, 0xe3, 0xc5, 0xff, 0xff, 0xe2, 0xc5, 0xff,
+ 0xff, 0xe4, 0xc8, 0xff, 0xff, 0xed, 0xd3, 0xff,
+ 0xff, 0xf7, 0xde, 0xff, 0xff, 0xf6, 0xde, 0xff,
+ 0xff, 0xf8, 0xe4, 0xff, 0xff, 0xf8, 0xe3, 0xff,
+ 0xff, 0xff, 0xef, 0xff, 0xff, 0xff, 0xee, 0xff,
+ 0xfa, 0xfc, 0xf7, 0xff, 0xf6, 0xfb, 0xff, 0xff,
+ 0xf7, 0xfb, 0xff, 0xff, 0xf9, 0xfc, 0xf6, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xf9, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xf9, 0xff,
+ 0xf7, 0xfb, 0xff, 0xff, 0xf9, 0xfc, 0xf6, 0xff,
+ 0xf7, 0xfb, 0xff, 0xff, 0xf6, 0xfa, 0xff, 0xff,
+ 0xfa, 0xfc, 0xf4, 0xff, 0xf9, 0xfc, 0xf4, 0xff,
+ 0xfa, 0xfc, 0xf4, 0xff, 0xf9, 0xfc, 0xf4, 0xff,
+ 0xf7, 0xff, 0xef, 0xff, 0xf6, 0xff, 0xee, 0xff,
+ 0xf7, 0xff, 0xef, 0xff, 0xf6, 0xff, 0xee, 0xff,
+ 0xff, 0xfb, 0xe6, 0xff, 0xff, 0xfb, 0xe6, 0xff,
+ 0xff, 0xfb, 0xe6, 0xff, 0xff, 0xfa, 0xe6, 0xff,
+ 0x42, 0x30, 0x24, 0xff, 0x42, 0x2f, 0x24, 0xff,
+ 0x29, 0x1d, 0x11, 0xff, 0x42, 0x2f, 0x23, 0xff,
+ 0x4b, 0x3d, 0x21, 0xff, 0x29, 0x1c, 0x10, 0xff,
+ 0x34, 0x27, 0x16, 0xff, 0x3f, 0x32, 0x1b, 0xff,
+ 0x87, 0x6b, 0x50, 0xff, 0xff, 0xd6, 0xbd, 0xff,
+ 0xff, 0xd7, 0xbe, 0xff, 0xff, 0xd6, 0xbd, 0xff,
+ 0xff, 0xc3, 0xa5, 0xff, 0xff, 0xc2, 0xa4, 0xff,
+ 0xff, 0xc3, 0xa5, 0xff, 0xff, 0xc2, 0xa4, 0xff,
+ 0xff, 0xc3, 0xa5, 0xff, 0xff, 0xc2, 0xa4, 0xff,
+ 0xff, 0xc3, 0xa5, 0xff, 0xff, 0xc2, 0xa4, 0xff,
+ 0xfa, 0xc8, 0xad, 0xff, 0xf9, 0xc8, 0xad, 0xff,
+ 0xfa, 0xc8, 0xad, 0xff, 0xfc, 0xd1, 0xb5, 0xff,
+ 0xff, 0xcf, 0xb5, 0xff, 0xff, 0xce, 0xb5, 0xff,
+ 0xff, 0xcf, 0xb5, 0xff, 0xff, 0xd8, 0xbd, 0xff,
+ 0xff, 0xdb, 0xc6, 0xff, 0xff, 0xe4, 0xce, 0xff,
+ 0xff, 0xe4, 0xce, 0xff, 0xff, 0xed, 0xd6, 0xff,
+ 0xff, 0xf3, 0xd6, 0xff, 0xff, 0xf3, 0xd6, 0xff,
+ 0xfa, 0xfb, 0xec, 0xff, 0xf9, 0xfb, 0xec, 0xff,
+ 0xff, 0xff, 0xef, 0xff, 0xf9, 0xfc, 0xf9, 0xff,
+ 0xfd, 0xfe, 0xf4, 0xff, 0xf9, 0xfc, 0xf9, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xfc, 0xfc, 0xf9, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xfc, 0xfc, 0xf9, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfb, 0xfd, 0xff, 0xf9, 0xfb, 0xf9, 0xff,
+ 0xfd, 0xfb, 0xfd, 0xff, 0xfc, 0xfb, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfa, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xfd, 0xfd, 0xfa, 0xff, 0xf9, 0xfd, 0xf4, 0xff,
+ 0xfd, 0xfe, 0xf5, 0xff, 0xfc, 0xfe, 0xf4, 0xff,
+ 0xfd, 0xfe, 0xf4, 0xff, 0xfc, 0xfd, 0xf4, 0xff,
+ 0x5b, 0x42, 0x37, 0xff, 0x29, 0x1c, 0x10, 0xff,
+ 0x29, 0x1d, 0x11, 0xff, 0x29, 0x1c, 0x10, 0xff,
+ 0x29, 0x1c, 0x11, 0xff, 0x29, 0x1c, 0x10, 0xff,
+ 0x34, 0x27, 0x16, 0xff, 0x34, 0x27, 0x16, 0xff,
+ 0x86, 0x6b, 0x50, 0xff, 0xff, 0xd6, 0xbd, 0xff,
+ 0xff, 0xd7, 0xbd, 0xff, 0xff, 0xd6, 0xbd, 0xff,
+ 0xff, 0xc2, 0xa5, 0xff, 0xff, 0xc2, 0xa4, 0xff,
+ 0xff, 0xc3, 0xa5, 0xff, 0xff, 0xc2, 0xa4, 0xff,
+ 0xff, 0xc2, 0xa5, 0xff, 0xff, 0xc2, 0xa4, 0xff,
+ 0xff, 0xc3, 0xa5, 0xff, 0xff, 0xc2, 0xa4, 0xff,
+ 0xfa, 0xc8, 0xad, 0xff, 0xf9, 0xc7, 0xac, 0xff,
+ 0xfc, 0xd1, 0xb5, 0xff, 0xfc, 0xd1, 0xb5, 0xff,
+ 0xff, 0xd8, 0xbd, 0xff, 0xff, 0xd7, 0xbd, 0xff,
+ 0xff, 0xd8, 0xbd, 0xff, 0xff, 0xe1, 0xc5, 0xff,
+ 0xff, 0xe4, 0xce, 0xff, 0xff, 0xe4, 0xcd, 0xff,
+ 0xff, 0xee, 0xd6, 0xff, 0xff, 0xf7, 0xde, 0xff,
+ 0xfc, 0xf7, 0xe1, 0xff, 0xf9, 0xfb, 0xeb, 0xff,
+ 0xf7, 0xff, 0xf7, 0xff, 0xf9, 0xfb, 0xec, 0xff,
+ 0xfa, 0xfc, 0xfa, 0xff, 0xf9, 0xfc, 0xf9, 0xff,
+ 0xf7, 0xfb, 0xff, 0xff, 0xf6, 0xfb, 0xff, 0xff,
+ 0xfc, 0xfc, 0xfa, 0xff, 0xff, 0xfb, 0xf6, 0xff,
+ 0xfc, 0xfd, 0xfa, 0xff, 0xfc, 0xfc, 0xf9, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfd, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xfa, 0xfb, 0xfa, 0xff, 0xfc, 0xfb, 0xfc, 0xff,
+ 0xfa, 0xfb, 0xfa, 0xff, 0xfc, 0xfb, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xf9, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xf9, 0xff,
+ 0xf7, 0xfb, 0xff, 0xff, 0xf9, 0xfc, 0xf9, 0xff,
+ 0xfa, 0xfd, 0xfa, 0xff, 0xfc, 0xfd, 0xf4, 0xff,
+ 0x29, 0x1d, 0x11, 0xff, 0x29, 0x1c, 0x10, 0xff,
+ 0x2a, 0x1d, 0x11, 0xff, 0x29, 0x1c, 0x10, 0xff,
+ 0x29, 0x1d, 0x11, 0xff, 0x29, 0x1c, 0x10, 0xff,
+ 0x2a, 0x1d, 0x11, 0xff, 0x34, 0x27, 0x16, 0xff,
+ 0x4a, 0x35, 0x19, 0xff, 0x86, 0x6a, 0x4f, 0xff,
+ 0xc3, 0xa1, 0x87, 0xff, 0xff, 0xd6, 0xbd, 0xff,
+ 0xff, 0xc3, 0xa5, 0xff, 0xff, 0xc2, 0xa4, 0xff,
+ 0xd9, 0xa5, 0x81, 0xff, 0xff, 0xc2, 0xa4, 0xff,
+ 0xd9, 0xa4, 0x84, 0xff, 0xff, 0xc2, 0xa4, 0xff,
+ 0xff, 0xc3, 0xa5, 0xff, 0xff, 0xc2, 0xa4, 0xff,
+ 0xfd, 0xd1, 0xb5, 0xff, 0xfc, 0xd1, 0xb5, 0xff,
+ 0xfd, 0xd2, 0xb5, 0xff, 0xff, 0xda, 0xbd, 0xff,
+ 0xff, 0xd8, 0xbd, 0xff, 0xff, 0xe1, 0xc5, 0xff,
+ 0xff, 0xe2, 0xc6, 0xff, 0xff, 0xe1, 0xc5, 0xff,
+ 0xff, 0xee, 0xd6, 0xff, 0xff, 0xed, 0xd6, 0xff,
+ 0xff, 0xf7, 0xdf, 0xff, 0xff, 0xf7, 0xde, 0xff,
+ 0xfa, 0xfb, 0xec, 0xff, 0xf7, 0xff, 0xf7, 0xff,
+ 0xfa, 0xfb, 0xec, 0xff, 0xf7, 0xff, 0xf7, 0xff,
+ 0xf7, 0xfb, 0xff, 0xff, 0xf9, 0xfc, 0xf9, 0xff,
+ 0xf7, 0xfb, 0xff, 0xff, 0xf9, 0xfc, 0xf9, 0xff,
+ 0xfd, 0xfd, 0xfa, 0xff, 0xfc, 0xfc, 0xf9, 0xff,
+ 0xfd, 0xfd, 0xfa, 0xff, 0xfc, 0xfc, 0xf9, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfb, 0xfd, 0xff, 0xf9, 0xfb, 0xf9, 0xff,
+ 0xfd, 0xfb, 0xfd, 0xff, 0xf9, 0xfb, 0xf9, 0xff,
+ 0xfd, 0xfd, 0xfa, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xfd, 0xfd, 0xfa, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xf7, 0xfb, 0xff, 0xff, 0xf7, 0xfb, 0xff, 0xff,
+ 0xf7, 0xfb, 0xff, 0xff, 0xf9, 0xfc, 0xf9, 0xff,
+ 0x73, 0x55, 0x4a, 0xff, 0x41, 0x2f, 0x23, 0xff,
+ 0x29, 0x1c, 0x10, 0xff, 0x29, 0x1c, 0x10, 0xff,
+ 0x29, 0x1c, 0x11, 0xff, 0x29, 0x1c, 0x10, 0xff,
+ 0x34, 0x27, 0x16, 0xff, 0x34, 0x27, 0x15, 0xff,
+ 0x4a, 0x35, 0x19, 0xff, 0x4a, 0x34, 0x18, 0xff,
+ 0xc3, 0xa1, 0x86, 0xff, 0xff, 0xd6, 0xbd, 0xff,
+ 0xd9, 0xa5, 0x81, 0xff, 0xd8, 0xa4, 0x81, 0xff,
+ 0x8c, 0x69, 0x3a, 0xff, 0x8b, 0x69, 0x39, 0xff,
+ 0x8c, 0x65, 0x42, 0xff, 0xb2, 0x84, 0x62, 0xff,
+ 0xd9, 0xa3, 0x84, 0xff, 0xff, 0xc2, 0xa4, 0xff,
+ 0xf7, 0xbe, 0xa5, 0xff, 0xff, 0xda, 0xbd, 0xff,
+ 0xff, 0xdb, 0xbd, 0xff, 0xff, 0xda, 0xbd, 0xff,
+ 0xff, 0xd8, 0xbd, 0xff, 0xff, 0xe1, 0xc5, 0xff,
+ 0xff, 0xeb, 0xce, 0xff, 0xff, 0xea, 0xcd, 0xff,
+ 0xff, 0xee, 0xd6, 0xff, 0xff, 0xed, 0xd6, 0xff,
+ 0xff, 0xed, 0xd6, 0xff, 0xff, 0xf6, 0xde, 0xff,
+ 0xfa, 0xfb, 0xec, 0xff, 0xf6, 0xff, 0xf6, 0xff,
+ 0xf7, 0xff, 0xf7, 0xff, 0xf9, 0xfa, 0xeb, 0xff,
+ 0xfa, 0xfc, 0xfa, 0xff, 0xf6, 0xfb, 0xff, 0xff,
+ 0xfa, 0xfc, 0xfa, 0xff, 0xf9, 0xfc, 0xf9, 0xff,
+ 0xfc, 0xfc, 0xfa, 0xff, 0xfc, 0xfc, 0xf9, 0xff,
+ 0xfc, 0xfc, 0xfa, 0xff, 0xfc, 0xfc, 0xf9, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfb, 0xfc, 0xff, 0xfc, 0xfb, 0xfc, 0xff,
+ 0xfc, 0xfb, 0xfc, 0xff, 0xfc, 0xfa, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xfc, 0xfc, 0xfa, 0xff, 0xfc, 0xfc, 0xf9, 0xff,
+ 0xfa, 0xfc, 0xfa, 0xff, 0xf6, 0xfb, 0xff, 0xff,
+ 0xf7, 0xfb, 0xff, 0xff, 0xf9, 0xfc, 0xf9, 0xff,
+ 0xad, 0x8a, 0x6b, 0xff, 0x5a, 0x46, 0x34, 0xff,
+ 0x32, 0x25, 0x19, 0xff, 0x31, 0x24, 0x19, 0xff,
+ 0x21, 0x1d, 0x11, 0xff, 0x2f, 0x27, 0x19, 0xff,
+ 0x3d, 0x32, 0x21, 0xff, 0x4a, 0x3d, 0x29, 0xff,
+ 0x53, 0x3f, 0x2c, 0xff, 0x3a, 0x28, 0x19, 0xff,
+ 0x84, 0x6a, 0x53, 0xff, 0x83, 0x69, 0x52, 0xff,
+ 0x5b, 0x49, 0x2a, 0xff, 0x5a, 0x49, 0x29, 0xff,
+ 0x45, 0x39, 0x1f, 0xff, 0x44, 0x39, 0x1e, 0xff,
+ 0x53, 0x3d, 0x21, 0xff, 0x76, 0x5c, 0x3c, 0xff,
+ 0x9a, 0x7b, 0x58, 0xff, 0xbd, 0x9a, 0x73, 0xff,
+ 0x9d, 0x7e, 0x63, 0xff, 0xce, 0xae, 0x94, 0xff,
+ 0xff, 0xdf, 0xc6, 0xff, 0xff, 0xde, 0xc5, 0xff,
+ 0xff, 0xe3, 0xc6, 0xff, 0xff, 0xe3, 0xc5, 0xff,
+ 0xff, 0xea, 0xce, 0xff, 0xff, 0xf0, 0xd6, 0xff,
+ 0xff, 0xf3, 0xd6, 0xff, 0xff, 0xf3, 0xd6, 0xff,
+ 0xff, 0xf7, 0xde, 0xff, 0xff, 0xfb, 0xe6, 0xff,
+ 0xf7, 0xff, 0xef, 0xff, 0xfc, 0xfc, 0xf9, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xf9, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xf7, 0xfb, 0xf7, 0xff, 0xf7, 0xfb, 0xf7, 0xff,
+ 0xf7, 0xfb, 0xf7, 0xff, 0xf7, 0xfb, 0xf7, 0xff,
+ 0x84, 0x68, 0x50, 0xff, 0x31, 0x24, 0x18, 0xff,
+ 0x32, 0x25, 0x19, 0xff, 0x31, 0x24, 0x18, 0xff,
+ 0x21, 0x1c, 0x11, 0xff, 0x2e, 0x27, 0x18, 0xff,
+ 0x4a, 0x3d, 0x29, 0xff, 0x3c, 0x32, 0x21, 0xff,
+ 0x3a, 0x29, 0x19, 0xff, 0x6b, 0x53, 0x3f, 0xff,
+ 0x6b, 0x54, 0x3f, 0xff, 0x52, 0x3e, 0x2c, 0xff,
+ 0x50, 0x41, 0x24, 0xff, 0x4f, 0x40, 0x23, 0xff,
+ 0x45, 0x39, 0x1e, 0xff, 0x44, 0x38, 0x1e, 0xff,
+ 0x52, 0x3d, 0x21, 0xff, 0x52, 0x3c, 0x20, 0xff,
+ 0x52, 0x3d, 0x21, 0xff, 0x76, 0x5b, 0x3c, 0xff,
+ 0x9c, 0x7e, 0x63, 0xff, 0xcd, 0xae, 0x94, 0xff,
+ 0xff, 0xdf, 0xc6, 0xff, 0xff, 0xde, 0xc5, 0xff,
+ 0xff, 0xe3, 0xc6, 0xff, 0xff, 0xe9, 0xcd, 0xff,
+ 0xff, 0xf0, 0xd6, 0xff, 0xff, 0xf0, 0xd6, 0xff,
+ 0xff, 0xf3, 0xd6, 0xff, 0xff, 0xf6, 0xde, 0xff,
+ 0xff, 0xf7, 0xde, 0xff, 0xff, 0xfb, 0xe6, 0xff,
+ 0xfa, 0xfe, 0xf4, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xfc, 0xfd, 0xfa, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfd, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfd, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfd, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfd, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfd, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfa, 0xfc, 0xfa, 0xff, 0xf6, 0xfb, 0xf6, 0xff,
+ 0xfc, 0xfe, 0xfc, 0xff, 0xf6, 0xfb, 0xf6, 0xff,
+ 0x84, 0x68, 0x50, 0xff, 0x31, 0x24, 0x18, 0xff,
+ 0x32, 0x25, 0x19, 0xff, 0x31, 0x24, 0x19, 0xff,
+ 0x2f, 0x27, 0x19, 0xff, 0x2e, 0x27, 0x18, 0xff,
+ 0x2f, 0x28, 0x19, 0xff, 0x3c, 0x32, 0x21, 0xff,
+ 0x53, 0x3e, 0x2c, 0xff, 0x6b, 0x53, 0x3f, 0xff,
+ 0x6b, 0x54, 0x3f, 0xff, 0x52, 0x3e, 0x2c, 0xff,
+ 0x45, 0x39, 0x1e, 0xff, 0x4f, 0x41, 0x23, 0xff,
+ 0x45, 0x39, 0x1f, 0xff, 0x44, 0x39, 0x1e, 0xff,
+ 0x53, 0x3d, 0x21, 0xff, 0x52, 0x3c, 0x21, 0xff,
+ 0x53, 0x3d, 0x21, 0xff, 0x52, 0x3d, 0x21, 0xff,
+ 0x6b, 0x4d, 0x32, 0xff, 0x9c, 0x7d, 0x62, 0xff,
+ 0xff, 0xdf, 0xc6, 0xff, 0xff, 0xdf, 0xc5, 0xff,
+ 0xff, 0xea, 0xce, 0xff, 0xff, 0xe9, 0xcd, 0xff,
+ 0xff, 0xf1, 0xd6, 0xff, 0xff, 0xf7, 0xde, 0xff,
+ 0xff, 0xf7, 0xde, 0xff, 0xff, 0xf7, 0xde, 0xff,
+ 0xff, 0xfb, 0xe7, 0xff, 0xff, 0xff, 0xee, 0xff,
+ 0xfd, 0xfd, 0xfa, 0xff, 0xfc, 0xfc, 0xf9, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xf9, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfa, 0xfd, 0xfa, 0xff, 0xf9, 0xfc, 0xf9, 0xff,
+ 0xfa, 0xfd, 0xfa, 0xff, 0xf7, 0xfb, 0xf7, 0xff,
+ 0x84, 0x68, 0x50, 0xff, 0x5a, 0x46, 0x34, 0xff,
+ 0x31, 0x24, 0x19, 0xff, 0x5a, 0x46, 0x34, 0xff,
+ 0x4a, 0x3d, 0x29, 0xff, 0x3c, 0x32, 0x21, 0xff,
+ 0x3c, 0x32, 0x21, 0xff, 0x4a, 0x3c, 0x29, 0xff,
+ 0x84, 0x69, 0x52, 0xff, 0x6b, 0x53, 0x3f, 0xff,
+ 0x52, 0x3e, 0x2c, 0xff, 0x6a, 0x53, 0x3f, 0xff,
+ 0x3a, 0x31, 0x19, 0xff, 0x39, 0x30, 0x18, 0xff,
+ 0x45, 0x39, 0x1e, 0xff, 0x44, 0x38, 0x1e, 0xff,
+ 0x52, 0x3d, 0x21, 0xff, 0x52, 0x3c, 0x21, 0xff,
+ 0x52, 0x3d, 0x21, 0xff, 0x52, 0x3c, 0x20, 0xff,
+ 0x6b, 0x4d, 0x32, 0xff, 0x6b, 0x4d, 0x31, 0xff,
+ 0x9c, 0x7e, 0x63, 0xff, 0xcd, 0xae, 0x94, 0xff,
+ 0xff, 0xf0, 0xd6, 0xff, 0xff, 0xf0, 0xd6, 0xff,
+ 0xff, 0xf7, 0xde, 0xff, 0xff, 0xf6, 0xde, 0xff,
+ 0xff, 0xfb, 0xe6, 0xff, 0xff, 0xff, 0xee, 0xff,
+ 0xff, 0xff, 0xef, 0xff, 0xff, 0xff, 0xee, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xf9, 0xff,
+ 0xfc, 0xfc, 0xfa, 0xff, 0xfc, 0xfc, 0xf9, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfa, 0xfc, 0xfa, 0xff, 0xf9, 0xfc, 0xf9, 0xff,
+ 0xfc, 0xfe, 0xfc, 0xff, 0xf6, 0xfa, 0xf6, 0xff,
+ 0x42, 0x35, 0x21, 0xff, 0x29, 0x20, 0x10, 0xff,
+ 0x42, 0x35, 0x21, 0xff, 0x42, 0x34, 0x21, 0xff,
+ 0x3a, 0x2d, 0x21, 0xff, 0x3a, 0x2c, 0x21, 0xff,
+ 0x60, 0x4f, 0x3f, 0xff, 0xad, 0x92, 0x7b, 0xff,
+ 0x84, 0x76, 0x63, 0xff, 0x6e, 0x60, 0x4d, 0xff,
+ 0x42, 0x35, 0x21, 0xff, 0x42, 0x34, 0x21, 0xff,
+ 0x3a, 0x35, 0x21, 0xff, 0x3a, 0x35, 0x21, 0xff,
+ 0x3a, 0x35, 0x21, 0xff, 0x39, 0x34, 0x21, 0xff,
+ 0x5b, 0x48, 0x35, 0xff, 0x6b, 0x5d, 0x4a, 0xff,
+ 0x53, 0x3d, 0x29, 0xff, 0x52, 0x3d, 0x29, 0xff,
+ 0x63, 0x5a, 0x4b, 0xff, 0x63, 0x59, 0x4a, 0xff,
+ 0x87, 0x7a, 0x69, 0xff, 0xaa, 0x9a, 0x86, 0xff,
+ 0xf7, 0xef, 0xd6, 0xff, 0xf9, 0xf4, 0xe1, 0xff,
+ 0xfd, 0xfa, 0xec, 0xff, 0xfc, 0xf9, 0xec, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf7, 0xfa, 0xf9, 0xff,
+ 0xf7, 0xfa, 0xfa, 0xff, 0xf7, 0xf9, 0xf9, 0xff,
+ 0xfa, 0xfb, 0xfd, 0xff, 0xf9, 0xfb, 0xfc, 0xff,
+ 0xfa, 0xfb, 0xfd, 0xff, 0xf9, 0xfb, 0xfc, 0xff,
+ 0xfa, 0xfb, 0xfa, 0xff, 0xf9, 0xfb, 0xf9, 0xff,
+ 0xfa, 0xfb, 0xfa, 0xff, 0xf9, 0xfb, 0xf9, 0xff,
+ 0xfa, 0xfb, 0xfa, 0xff, 0xf9, 0xfb, 0xf9, 0xff,
+ 0xfa, 0xfb, 0xfa, 0xff, 0xf9, 0xfb, 0xf9, 0xff,
+ 0xfa, 0xfa, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfa, 0xfa, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfa, 0xfa, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfa, 0xfa, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfa, 0xfa, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfa, 0xfa, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfa, 0xfb, 0xfa, 0xff, 0xf9, 0xfb, 0xf9, 0xff,
+ 0xfa, 0xfb, 0xfa, 0xff, 0xf9, 0xfb, 0xf9, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf7, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf7, 0xff,
+ 0x29, 0x20, 0x11, 0xff, 0x29, 0x20, 0x10, 0xff,
+ 0x29, 0x21, 0x11, 0xff, 0x29, 0x20, 0x10, 0xff,
+ 0x3a, 0x2d, 0x21, 0xff, 0x60, 0x4e, 0x3f, 0xff,
+ 0x87, 0x70, 0x5d, 0xff, 0x86, 0x70, 0x5d, 0xff,
+ 0x6e, 0x60, 0x4d, 0xff, 0x6d, 0x5f, 0x4c, 0xff,
+ 0x58, 0x4a, 0x37, 0xff, 0x57, 0x4a, 0x37, 0xff,
+ 0x47, 0x40, 0x29, 0xff, 0x55, 0x4a, 0x31, 0xff,
+ 0x63, 0x55, 0x3a, 0xff, 0x47, 0x3f, 0x29, 0xff,
+ 0x52, 0x3d, 0x29, 0xff, 0x5a, 0x47, 0x34, 0xff,
+ 0x5b, 0x48, 0x34, 0xff, 0x5a, 0x47, 0x34, 0xff,
+ 0x86, 0x7a, 0x68, 0xff, 0x62, 0x59, 0x4a, 0xff,
+ 0x87, 0x7a, 0x68, 0xff, 0xcd, 0xba, 0xa4, 0xff,
+ 0xf7, 0xef, 0xd6, 0xff, 0xf9, 0xf4, 0xe0, 0xff,
+ 0xff, 0xff, 0xf7, 0xff, 0xff, 0xff, 0xf6, 0xff,
+ 0xf7, 0xfa, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xf7, 0xfa, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfa, 0xfb, 0xfc, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfa, 0xfb, 0xfc, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfa, 0xfb, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfa, 0xfb, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfa, 0xfb, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfa, 0xfb, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf9, 0xf9, 0xf9, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf9, 0xf9, 0xf9, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf9, 0xf9, 0xf9, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf9, 0xf9, 0xf9, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf9, 0xf9, 0xf9, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf9, 0xf9, 0xf9, 0xff,
+ 0xfa, 0xfb, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfa, 0xfb, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf6, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xee, 0xe2, 0xd8, 0xff,
+ 0x29, 0x21, 0x11, 0xff, 0x29, 0x20, 0x10, 0xff,
+ 0x42, 0x35, 0x21, 0xff, 0x73, 0x5d, 0x42, 0xff,
+ 0x3a, 0x2d, 0x21, 0xff, 0x60, 0x4e, 0x3f, 0xff,
+ 0x3a, 0x2d, 0x21, 0xff, 0x60, 0x4e, 0x3f, 0xff,
+ 0x58, 0x4a, 0x37, 0xff, 0x58, 0x4a, 0x37, 0xff,
+ 0x58, 0x4b, 0x37, 0xff, 0x6e, 0x60, 0x4d, 0xff,
+ 0x3a, 0x35, 0x21, 0xff, 0x39, 0x34, 0x21, 0xff,
+ 0x48, 0x40, 0x2a, 0xff, 0x47, 0x3f, 0x29, 0xff,
+ 0x53, 0x3d, 0x29, 0xff, 0x52, 0x3c, 0x29, 0xff,
+ 0x5b, 0x48, 0x35, 0xff, 0x6b, 0x5d, 0x4a, 0xff,
+ 0xaa, 0x9a, 0x87, 0xff, 0x86, 0x79, 0x68, 0xff,
+ 0x87, 0x7a, 0x69, 0xff, 0xce, 0xba, 0xa4, 0xff,
+ 0xfd, 0xfa, 0xec, 0xff, 0xfc, 0xf9, 0xec, 0xff,
+ 0xff, 0xff, 0xf7, 0xff, 0xff, 0xff, 0xf7, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf7, 0xff,
+ 0xef, 0xe3, 0xd9, 0xff, 0xce, 0xb2, 0x9c, 0xff,
+ 0x29, 0x21, 0x11, 0xff, 0x41, 0x34, 0x21, 0xff,
+ 0x42, 0x35, 0x21, 0xff, 0x5a, 0x48, 0x31, 0xff,
+ 0x3a, 0x2d, 0x21, 0xff, 0x39, 0x2c, 0x21, 0xff,
+ 0x60, 0x4e, 0x3f, 0xff, 0x39, 0x2c, 0x20, 0xff,
+ 0x42, 0x35, 0x21, 0xff, 0x41, 0x34, 0x21, 0xff,
+ 0x6e, 0x60, 0x4d, 0xff, 0x41, 0x34, 0x20, 0xff,
+ 0x47, 0x40, 0x29, 0xff, 0x47, 0x3f, 0x29, 0xff,
+ 0x47, 0x3f, 0x29, 0xff, 0x47, 0x3f, 0x29, 0xff,
+ 0x52, 0x3d, 0x29, 0xff, 0x5a, 0x47, 0x34, 0xff,
+ 0x5b, 0x48, 0x34, 0xff, 0x6a, 0x5d, 0x4a, 0xff,
+ 0x87, 0x7a, 0x68, 0xff, 0x86, 0x79, 0x68, 0xff,
+ 0x86, 0x79, 0x68, 0xff, 0xcd, 0xba, 0xa4, 0xff,
+ 0xf7, 0xef, 0xd6, 0xff, 0xf9, 0xf4, 0xe0, 0xff,
+ 0xfa, 0xf4, 0xe1, 0xff, 0xf9, 0xf4, 0xe0, 0xff,
+ 0xef, 0xf4, 0xf4, 0xff, 0xe6, 0xee, 0xee, 0xff,
+ 0xef, 0xf4, 0xf4, 0xff, 0xe6, 0xee, 0xee, 0xff,
+ 0xef, 0xf3, 0xf7, 0xff, 0xee, 0xf3, 0xf6, 0xff,
+ 0xef, 0xf3, 0xf7, 0xff, 0xee, 0xf2, 0xf6, 0xff,
+ 0xef, 0xf3, 0xef, 0xff, 0xf4, 0xf7, 0xf4, 0xff,
+ 0xef, 0xf3, 0xef, 0xff, 0xee, 0xf2, 0xee, 0xff,
+ 0xef, 0xf3, 0xef, 0xff, 0xf4, 0xf7, 0xf4, 0xff,
+ 0xef, 0xf3, 0xef, 0xff, 0xee, 0xf2, 0xee, 0xff,
+ 0xf4, 0xf4, 0xf4, 0xff, 0xee, 0xee, 0xee, 0xff,
+ 0xef, 0xef, 0xef, 0xff, 0xf4, 0xf4, 0xf4, 0xff,
+ 0xf4, 0xf4, 0xf4, 0xff, 0xf4, 0xf4, 0xf4, 0xff,
+ 0xef, 0xef, 0xef, 0xff, 0xee, 0xee, 0xee, 0xff,
+ 0xf4, 0xf4, 0xf4, 0xff, 0xee, 0xee, 0xee, 0xff,
+ 0xf4, 0xf4, 0xf4, 0xff, 0xf4, 0xf4, 0xf4, 0xff,
+ 0xef, 0xf3, 0xef, 0xff, 0xee, 0xf3, 0xee, 0xff,
+ 0xf4, 0xf7, 0xf4, 0xff, 0xee, 0xf2, 0xee, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf6, 0xff,
+ 0xef, 0xe3, 0xd9, 0xff, 0xde, 0xca, 0xba, 0xff,
+ 0x32, 0x62, 0x4b, 0xff, 0x42, 0x79, 0x65, 0xff,
+ 0x42, 0x7a, 0x66, 0xff, 0x39, 0x6d, 0x58, 0xff,
+ 0x3d, 0x67, 0x50, 0xff, 0x37, 0x4c, 0x34, 0xff,
+ 0x32, 0x31, 0x19, 0xff, 0x31, 0x30, 0x19, 0xff,
+ 0x3a, 0x39, 0x2a, 0xff, 0x3a, 0x39, 0x29, 0xff,
+ 0x3a, 0x39, 0x29, 0xff, 0x42, 0x4d, 0x3c, 0xff,
+ 0x74, 0x4d, 0x42, 0xff, 0x6b, 0x5a, 0x4d, 0xff,
+ 0x6b, 0x5b, 0x4d, 0xff, 0x63, 0x68, 0x58, 0xff,
+ 0x50, 0x6e, 0x60, 0xff, 0x4f, 0x6d, 0x60, 0xff,
+ 0x5b, 0x82, 0x74, 0xff, 0x5a, 0x81, 0x73, 0xff,
+ 0x4b, 0x92, 0x7c, 0xff, 0x4a, 0x92, 0x7b, 0xff,
+ 0x4a, 0x92, 0x7c, 0xff, 0x4a, 0x92, 0x7b, 0xff,
+ 0x42, 0x82, 0x74, 0xff, 0x3c, 0x6b, 0x5d, 0xff,
+ 0x3d, 0x6b, 0x5e, 0xff, 0x3c, 0x6a, 0x5d, 0xff,
+ 0x3a, 0x72, 0x63, 0xff, 0x3a, 0x71, 0x63, 0xff,
+ 0x3a, 0x72, 0x63, 0xff, 0x31, 0x59, 0x4a, 0xff,
+ 0x35, 0x6b, 0x58, 0xff, 0x3f, 0x80, 0x6e, 0xff,
+ 0x4a, 0x96, 0x84, 0xff, 0x3f, 0x80, 0x6e, 0xff,
+ 0x3a, 0x85, 0x74, 0xff, 0x4a, 0x9e, 0x8c, 0xff,
+ 0x4a, 0x9e, 0x8c, 0xff, 0x4a, 0x9e, 0x8c, 0xff,
+ 0x4b, 0xa2, 0x95, 0xff, 0x4a, 0xa2, 0x94, 0xff,
+ 0x32, 0x7e, 0x71, 0xff, 0x4a, 0xa2, 0x94, 0xff,
+ 0x5b, 0x8a, 0x7c, 0xff, 0x5a, 0x8a, 0x7b, 0xff,
+ 0x55, 0x7b, 0x71, 0xff, 0x4f, 0x6c, 0x65, 0xff,
+ 0x7c, 0x7e, 0x7c, 0xff, 0x8c, 0x8e, 0x8c, 0xff,
+ 0x8c, 0x8e, 0x8c, 0xff, 0x83, 0x85, 0x83, 0xff,
+ 0x84, 0x82, 0x84, 0xff, 0x73, 0x70, 0x70, 0xff,
+ 0x74, 0x70, 0x71, 0xff, 0x73, 0x70, 0x70, 0xff,
+ 0x81, 0x83, 0x81, 0xff, 0x81, 0x83, 0x81, 0xff,
+ 0x8c, 0x8e, 0x8c, 0xff, 0x8c, 0x8e, 0x8c, 0xff,
+ 0x8c, 0x8b, 0x8c, 0xff, 0x8c, 0x8b, 0x8c, 0xff,
+ 0x8c, 0x8b, 0x8c, 0xff, 0x8c, 0x8b, 0x8c, 0xff,
+ 0x3a, 0x6d, 0x58, 0xff, 0x41, 0x79, 0x65, 0xff,
+ 0x42, 0x7a, 0x66, 0xff, 0x4a, 0x85, 0x73, 0xff,
+ 0x42, 0x82, 0x6b, 0xff, 0x41, 0x81, 0x6b, 0xff,
+ 0x3d, 0x67, 0x50, 0xff, 0x3c, 0x66, 0x4f, 0xff,
+ 0x4a, 0x61, 0x50, 0xff, 0x41, 0x4c, 0x3c, 0xff,
+ 0x4a, 0x61, 0x50, 0xff, 0x4a, 0x61, 0x4f, 0xff,
+ 0x63, 0x68, 0x58, 0xff, 0x5a, 0x75, 0x62, 0xff,
+ 0x5b, 0x76, 0x63, 0xff, 0x6b, 0x5a, 0x4c, 0xff,
+ 0x50, 0x6d, 0x60, 0xff, 0x44, 0x59, 0x4c, 0xff,
+ 0x5b, 0x82, 0x73, 0xff, 0x5a, 0x81, 0x73, 0xff,
+ 0x42, 0x7c, 0x6b, 0xff, 0x4a, 0x91, 0x7b, 0xff,
+ 0x4a, 0x92, 0x7c, 0xff, 0x42, 0x7c, 0x6b, 0xff,
+ 0x42, 0x82, 0x73, 0xff, 0x3c, 0x6a, 0x5d, 0xff,
+ 0x37, 0x54, 0x48, 0xff, 0x37, 0x53, 0x47, 0xff,
+ 0x29, 0x41, 0x31, 0xff, 0x29, 0x40, 0x31, 0xff,
+ 0x29, 0x41, 0x32, 0xff, 0x29, 0x40, 0x31, 0xff,
+ 0x29, 0x55, 0x42, 0xff, 0x3f, 0x80, 0x6d, 0xff,
+ 0x3f, 0x80, 0x6e, 0xff, 0x34, 0x6a, 0x57, 0xff,
+ 0x29, 0x6b, 0x5b, 0xff, 0x39, 0x84, 0x73, 0xff,
+ 0x3a, 0x84, 0x73, 0xff, 0x39, 0x84, 0x73, 0xff,
+ 0x31, 0x7e, 0x71, 0xff, 0x31, 0x7d, 0x70, 0xff,
+ 0x32, 0x7e, 0x71, 0xff, 0x31, 0x7d, 0x70, 0xff,
+ 0x55, 0x7b, 0x71, 0xff, 0x55, 0x7a, 0x70, 0xff,
+ 0x5b, 0x8a, 0x7c, 0xff, 0x4f, 0x6c, 0x65, 0xff,
+ 0x7b, 0x7e, 0x7b, 0xff, 0x7b, 0x7d, 0x7b, 0xff,
+ 0x84, 0x86, 0x84, 0xff, 0x7b, 0x7d, 0x7b, 0xff,
+ 0x73, 0x70, 0x71, 0xff, 0x52, 0x4c, 0x4a, 0xff,
+ 0x63, 0x5f, 0x5d, 0xff, 0x62, 0x5e, 0x5d, 0xff,
+ 0x76, 0x78, 0x76, 0xff, 0x75, 0x78, 0x75, 0xff,
+ 0x6b, 0x6e, 0x6b, 0xff, 0x76, 0x78, 0x76, 0xff,
+ 0x7b, 0x7e, 0x7b, 0xff, 0x7b, 0x7d, 0x7b, 0xff,
+ 0x7c, 0x7e, 0x7c, 0xff, 0x7b, 0x7d, 0x7b, 0xff,
+ 0x42, 0x7a, 0x66, 0xff, 0x39, 0x6d, 0x58, 0xff,
+ 0x42, 0x7a, 0x66, 0xff, 0x4a, 0x85, 0x73, 0xff,
+ 0x42, 0x82, 0x6b, 0xff, 0x42, 0x81, 0x6b, 0xff,
+ 0x42, 0x82, 0x6b, 0xff, 0x42, 0x81, 0x6b, 0xff,
+ 0x53, 0x76, 0x63, 0xff, 0x4a, 0x61, 0x4f, 0xff,
+ 0x42, 0x4d, 0x3d, 0xff, 0x52, 0x75, 0x63, 0xff,
+ 0x5b, 0x76, 0x63, 0xff, 0x5a, 0x75, 0x62, 0xff,
+ 0x63, 0x68, 0x58, 0xff, 0x63, 0x68, 0x58, 0xff,
+ 0x45, 0x59, 0x4d, 0xff, 0x44, 0x59, 0x4d, 0xff,
+ 0x50, 0x6e, 0x60, 0xff, 0x44, 0x59, 0x4d, 0xff,
+ 0x3a, 0x67, 0x5b, 0xff, 0x42, 0x7c, 0x6b, 0xff,
+ 0x42, 0x7d, 0x6b, 0xff, 0x4a, 0x92, 0x7b, 0xff,
+ 0x42, 0x82, 0x73, 0xff, 0x42, 0x81, 0x73, 0xff,
+ 0x37, 0x54, 0x48, 0xff, 0x31, 0x3d, 0x31, 0xff,
+ 0x21, 0x29, 0x19, 0xff, 0x29, 0x41, 0x31, 0xff,
+ 0x2a, 0x41, 0x32, 0xff, 0x29, 0x41, 0x31, 0xff,
+ 0x29, 0x55, 0x42, 0xff, 0x34, 0x6a, 0x58, 0xff,
+ 0x35, 0x6b, 0x58, 0xff, 0x34, 0x6a, 0x58, 0xff,
+ 0x29, 0x6b, 0x5b, 0xff, 0x39, 0x84, 0x73, 0xff,
+ 0x3a, 0x85, 0x74, 0xff, 0x29, 0x6a, 0x5a, 0xff,
+ 0x19, 0x59, 0x4d, 0xff, 0x31, 0x7d, 0x70, 0xff,
+ 0x32, 0x7e, 0x71, 0xff, 0x31, 0x7d, 0x70, 0xff,
+ 0x50, 0x6c, 0x66, 0xff, 0x55, 0x7b, 0x70, 0xff,
+ 0x5b, 0x8a, 0x7c, 0xff, 0x55, 0x7b, 0x70, 0xff,
+ 0x73, 0x76, 0x73, 0xff, 0x7b, 0x7d, 0x7b, 0xff,
+ 0x84, 0x86, 0x84, 0xff, 0x84, 0x85, 0x84, 0xff,
+ 0x73, 0x70, 0x71, 0xff, 0x52, 0x4d, 0x4a, 0xff,
+ 0x74, 0x70, 0x71, 0xff, 0x73, 0x70, 0x70, 0xff,
+ 0x76, 0x78, 0x76, 0xff, 0x76, 0x78, 0x76, 0xff,
+ 0x6b, 0x6e, 0x6b, 0xff, 0x76, 0x78, 0x76, 0xff,
+ 0x8c, 0x8b, 0x8c, 0xff, 0x7b, 0x7d, 0x7b, 0xff,
+ 0x7c, 0x7e, 0x7c, 0xff, 0x84, 0x84, 0x84, 0xff,
+ 0x32, 0x61, 0x4a, 0xff, 0x39, 0x6d, 0x57, 0xff,
+ 0x3a, 0x6d, 0x58, 0xff, 0x39, 0x6d, 0x57, 0xff,
+ 0x42, 0x82, 0x6b, 0xff, 0x3c, 0x66, 0x4f, 0xff,
+ 0x3c, 0x67, 0x50, 0xff, 0x41, 0x81, 0x6a, 0xff,
+ 0x4a, 0x61, 0x50, 0xff, 0x4a, 0x61, 0x4f, 0xff,
+ 0x4a, 0x61, 0x50, 0xff, 0x4a, 0x61, 0x4f, 0xff,
+ 0x63, 0x68, 0x58, 0xff, 0x62, 0x68, 0x57, 0xff,
+ 0x5b, 0x75, 0x63, 0xff, 0x62, 0x67, 0x57, 0xff,
+ 0x45, 0x59, 0x4d, 0xff, 0x39, 0x44, 0x39, 0xff,
+ 0x3a, 0x45, 0x3a, 0xff, 0x44, 0x59, 0x4c, 0xff,
+ 0x32, 0x51, 0x4a, 0xff, 0x31, 0x51, 0x4a, 0xff,
+ 0x3a, 0x67, 0x5b, 0xff, 0x41, 0x7c, 0x6a, 0xff,
+ 0x3c, 0x6b, 0x5d, 0xff, 0x3c, 0x6a, 0x5d, 0xff,
+ 0x3c, 0x6b, 0x5d, 0xff, 0x31, 0x3c, 0x31, 0xff,
+ 0x29, 0x41, 0x32, 0xff, 0x29, 0x40, 0x31, 0xff,
+ 0x29, 0x41, 0x31, 0xff, 0x29, 0x40, 0x31, 0xff,
+ 0x29, 0x55, 0x42, 0xff, 0x3f, 0x80, 0x6d, 0xff,
+ 0x3f, 0x80, 0x6e, 0xff, 0x3f, 0x80, 0x6d, 0xff,
+ 0x29, 0x6b, 0x5b, 0xff, 0x29, 0x6a, 0x5a, 0xff,
+ 0x19, 0x51, 0x42, 0xff, 0x18, 0x50, 0x41, 0xff,
+ 0x00, 0x35, 0x29, 0xff, 0x18, 0x59, 0x4c, 0xff,
+ 0x31, 0x7e, 0x70, 0xff, 0x31, 0x7d, 0x70, 0xff,
+ 0x5b, 0x8a, 0x7c, 0xff, 0x55, 0x7a, 0x70, 0xff,
+ 0x4a, 0x5d, 0x5b, 0xff, 0x4a, 0x5d, 0x5a, 0xff,
+ 0x73, 0x76, 0x73, 0xff, 0x7b, 0x7d, 0x7b, 0xff,
+ 0x84, 0x86, 0x84, 0xff, 0x83, 0x85, 0x83, 0xff,
+ 0x84, 0x82, 0x84, 0xff, 0x73, 0x70, 0x70, 0xff,
+ 0x73, 0x70, 0x70, 0xff, 0x73, 0x70, 0x70, 0xff,
+ 0x6b, 0x6d, 0x6b, 0xff, 0x76, 0x78, 0x76, 0xff,
+ 0x76, 0x78, 0x76, 0xff, 0x80, 0x82, 0x80, 0xff,
+ 0x94, 0x92, 0x94, 0xff, 0x7b, 0x7d, 0x7b, 0xff,
+ 0x7b, 0x7e, 0x7b, 0xff, 0x7b, 0x7d, 0x7b, 0xff,
+ 0x32, 0x5b, 0x45, 0xff, 0x3a, 0x64, 0x4f, 0xff,
+ 0x42, 0x6e, 0x5b, 0xff, 0x39, 0x64, 0x4f, 0xff,
+ 0x3a, 0x62, 0x4b, 0xff, 0x45, 0x6f, 0x5a, 0xff,
+ 0x45, 0x6f, 0x5b, 0xff, 0x44, 0x6e, 0x5a, 0xff,
+ 0x48, 0x76, 0x69, 0xff, 0x4d, 0x69, 0x5d, 0xff,
+ 0x53, 0x5d, 0x53, 0xff, 0x4d, 0x69, 0x5d, 0xff,
+ 0x4b, 0x72, 0x66, 0xff, 0x42, 0x65, 0x60, 0xff,
+ 0x4a, 0x72, 0x66, 0xff, 0x52, 0x7d, 0x6b, 0xff,
+ 0x45, 0x62, 0x5e, 0xff, 0x3f, 0x4d, 0x47, 0xff,
+ 0x3a, 0x39, 0x32, 0xff, 0x39, 0x39, 0x31, 0xff,
+ 0x3a, 0x4b, 0x3d, 0xff, 0x31, 0x3b, 0x2f, 0xff,
+ 0x3a, 0x4b, 0x3d, 0xff, 0x42, 0x59, 0x4a, 0xff,
+ 0x3a, 0x66, 0x53, 0xff, 0x3a, 0x65, 0x52, 0xff,
+ 0x3a, 0x66, 0x53, 0xff, 0x34, 0x51, 0x42, 0xff,
+ 0x24, 0x5a, 0x42, 0xff, 0x24, 0x59, 0x42, 0xff,
+ 0x21, 0x49, 0x32, 0xff, 0x21, 0x49, 0x31, 0xff,
+ 0x2a, 0x41, 0x32, 0xff, 0x29, 0x51, 0x42, 0xff,
+ 0x29, 0x61, 0x53, 0xff, 0x29, 0x61, 0x52, 0xff,
+ 0x21, 0x58, 0x42, 0xff, 0x21, 0x58, 0x42, 0xff,
+ 0x19, 0x41, 0x29, 0xff, 0x19, 0x41, 0x29, 0xff,
+ 0x21, 0x49, 0x32, 0xff, 0x31, 0x74, 0x63, 0xff,
+ 0x32, 0x74, 0x63, 0xff, 0x39, 0x89, 0x7b, 0xff,
+ 0x40, 0x7f, 0x71, 0xff, 0x3f, 0x7f, 0x70, 0xff,
+ 0x3f, 0x7f, 0x71, 0xff, 0x34, 0x74, 0x65, 0xff,
+ 0x60, 0x7a, 0x74, 0xff, 0x6b, 0x8a, 0x84, 0xff,
+ 0x60, 0x7a, 0x74, 0xff, 0x6b, 0x89, 0x83, 0xff,
+ 0x74, 0x72, 0x74, 0xff, 0x58, 0x59, 0x58, 0xff,
+ 0x66, 0x66, 0x66, 0xff, 0x65, 0x65, 0x65, 0xff,
+ 0x63, 0x62, 0x5b, 0xff, 0x6e, 0x6b, 0x65, 0xff,
+ 0x79, 0x74, 0x71, 0xff, 0x83, 0x7d, 0x7b, 0xff,
+ 0x8c, 0x86, 0x84, 0xff, 0x84, 0x7f, 0x7e, 0xff,
+ 0x84, 0x7f, 0x7e, 0xff, 0x83, 0x7f, 0x7e, 0xff,
+ 0x3a, 0x64, 0x50, 0xff, 0x39, 0x63, 0x4f, 0xff,
+ 0x3a, 0x64, 0x50, 0xff, 0x31, 0x5a, 0x44, 0xff,
+ 0x45, 0x6f, 0x5b, 0xff, 0x44, 0x6e, 0x5a, 0xff,
+ 0x45, 0x6f, 0x5b, 0xff, 0x4f, 0x7c, 0x6b, 0xff,
+ 0x47, 0x75, 0x68, 0xff, 0x41, 0x81, 0x73, 0xff,
+ 0x48, 0x76, 0x68, 0xff, 0x4c, 0x69, 0x5d, 0xff,
+ 0x4a, 0x71, 0x66, 0xff, 0x4a, 0x71, 0x65, 0xff,
+ 0x4a, 0x72, 0x66, 0xff, 0x4a, 0x71, 0x65, 0xff,
+ 0x4a, 0x75, 0x73, 0xff, 0x44, 0x61, 0x5d, 0xff,
+ 0x3f, 0x4d, 0x48, 0xff, 0x3f, 0x4d, 0x47, 0xff,
+ 0x3a, 0x4a, 0x3c, 0xff, 0x39, 0x4a, 0x3c, 0xff,
+ 0x29, 0x2d, 0x21, 0xff, 0x31, 0x3b, 0x2e, 0xff,
+ 0x2f, 0x3d, 0x31, 0xff, 0x34, 0x51, 0x41, 0xff,
+ 0x34, 0x51, 0x42, 0xff, 0x2e, 0x3c, 0x31, 0xff,
+ 0x21, 0x49, 0x31, 0xff, 0x26, 0x69, 0x52, 0xff,
+ 0x27, 0x69, 0x52, 0xff, 0x23, 0x59, 0x42, 0xff,
+ 0x29, 0x51, 0x42, 0xff, 0x29, 0x51, 0x41, 0xff,
+ 0x29, 0x41, 0x32, 0xff, 0x29, 0x51, 0x42, 0xff,
+ 0x29, 0x6f, 0x5b, 0xff, 0x31, 0x85, 0x73, 0xff,
+ 0x21, 0x58, 0x42, 0xff, 0x21, 0x57, 0x42, 0xff,
+ 0x29, 0x5f, 0x4a, 0xff, 0x31, 0x74, 0x62, 0xff,
+ 0x3a, 0x8a, 0x7c, 0xff, 0x39, 0x89, 0x7b, 0xff,
+ 0x3f, 0x7f, 0x71, 0xff, 0x4a, 0x89, 0x7b, 0xff,
+ 0x4a, 0x8a, 0x7c, 0xff, 0x3f, 0x7f, 0x70, 0xff,
+ 0x6b, 0x8a, 0x84, 0xff, 0x60, 0x79, 0x73, 0xff,
+ 0x4a, 0x59, 0x52, 0xff, 0x55, 0x69, 0x62, 0xff,
+ 0x66, 0x65, 0x66, 0xff, 0x57, 0x59, 0x57, 0xff,
+ 0x66, 0x65, 0x66, 0xff, 0x65, 0x65, 0x65, 0xff,
+ 0x63, 0x61, 0x5b, 0xff, 0x6d, 0x6a, 0x65, 0xff,
+ 0x79, 0x74, 0x71, 0xff, 0x83, 0x7d, 0x7b, 0xff,
+ 0x7b, 0x78, 0x79, 0xff, 0x7b, 0x78, 0x78, 0xff,
+ 0x84, 0x7f, 0x7e, 0xff, 0x83, 0x7f, 0x7e, 0xff,
+ 0x29, 0x51, 0x3a, 0xff, 0x31, 0x5a, 0x44, 0xff,
+ 0x3a, 0x64, 0x50, 0xff, 0x39, 0x64, 0x4f, 0xff,
+ 0x45, 0x6f, 0x5b, 0xff, 0x44, 0x6e, 0x5a, 0xff,
+ 0x5b, 0x8a, 0x7c, 0xff, 0x5a, 0x8a, 0x7b, 0xff,
+ 0x48, 0x76, 0x68, 0xff, 0x47, 0x75, 0x68, 0xff,
+ 0x42, 0x82, 0x74, 0xff, 0x47, 0x75, 0x68, 0xff,
+ 0x53, 0x7e, 0x6b, 0xff, 0x4a, 0x71, 0x65, 0xff,
+ 0x53, 0x7e, 0x6b, 0xff, 0x52, 0x7d, 0x6b, 0xff,
+ 0x4a, 0x76, 0x73, 0xff, 0x4a, 0x75, 0x73, 0xff,
+ 0x3f, 0x4d, 0x48, 0xff, 0x39, 0x39, 0x31, 0xff,
+ 0x3a, 0x4a, 0x3d, 0xff, 0x42, 0x59, 0x4a, 0xff,
+ 0x3a, 0x4b, 0x3d, 0xff, 0x29, 0x2c, 0x21, 0xff,
+ 0x29, 0x29, 0x21, 0xff, 0x2e, 0x3c, 0x31, 0xff,
+ 0x2f, 0x3d, 0x32, 0xff, 0x2f, 0x3d, 0x31, 0xff,
+ 0x24, 0x59, 0x42, 0xff, 0x29, 0x79, 0x62, 0xff,
+ 0x2a, 0x7a, 0x63, 0xff, 0x29, 0x79, 0x63, 0xff,
+ 0x29, 0x61, 0x53, 0xff, 0x29, 0x61, 0x52, 0xff,
+ 0x2a, 0x62, 0x53, 0xff, 0x29, 0x71, 0x63, 0xff,
+ 0x32, 0x86, 0x73, 0xff, 0x31, 0x85, 0x73, 0xff,
+ 0x32, 0x86, 0x74, 0xff, 0x29, 0x6f, 0x5a, 0xff,
+ 0x32, 0x74, 0x63, 0xff, 0x31, 0x74, 0x62, 0xff,
+ 0x3a, 0x8a, 0x7c, 0xff, 0x39, 0x8a, 0x7b, 0xff,
+ 0x34, 0x74, 0x66, 0xff, 0x3f, 0x7f, 0x70, 0xff,
+ 0x4a, 0x8a, 0x7c, 0xff, 0x3f, 0x7f, 0x70, 0xff,
+ 0x60, 0x7a, 0x73, 0xff, 0x6b, 0x89, 0x83, 0xff,
+ 0x55, 0x6a, 0x63, 0xff, 0x4a, 0x59, 0x52, 0xff,
+ 0x58, 0x59, 0x58, 0xff, 0x58, 0x59, 0x58, 0xff,
+ 0x58, 0x59, 0x58, 0xff, 0x65, 0x65, 0x65, 0xff,
+ 0x63, 0x61, 0x5b, 0xff, 0x6d, 0x6a, 0x65, 0xff,
+ 0x6e, 0x6b, 0x66, 0xff, 0x79, 0x74, 0x70, 0xff,
+ 0x7c, 0x78, 0x79, 0xff, 0x73, 0x71, 0x73, 0xff,
+ 0x84, 0x7f, 0x7f, 0xff, 0x84, 0x7f, 0x7e, 0xff,
+ 0x29, 0x51, 0x3a, 0xff, 0x29, 0x51, 0x39, 0xff,
+ 0x42, 0x6d, 0x5b, 0xff, 0x39, 0x63, 0x4f, 0xff,
+ 0x3a, 0x61, 0x4a, 0xff, 0x44, 0x6e, 0x5a, 0xff,
+ 0x45, 0x6f, 0x5b, 0xff, 0x4f, 0x7c, 0x6a, 0xff,
+ 0x47, 0x76, 0x68, 0xff, 0x47, 0x75, 0x68, 0xff,
+ 0x4d, 0x69, 0x5d, 0xff, 0x4c, 0x69, 0x5d, 0xff,
+ 0x3a, 0x59, 0x5b, 0xff, 0x41, 0x65, 0x60, 0xff,
+ 0x4a, 0x71, 0x65, 0xff, 0x39, 0x59, 0x5a, 0xff,
+ 0x4a, 0x76, 0x73, 0xff, 0x4a, 0x75, 0x73, 0xff,
+ 0x3f, 0x4d, 0x47, 0xff, 0x39, 0x38, 0x31, 0xff,
+ 0x32, 0x3c, 0x2f, 0xff, 0x31, 0x3b, 0x2e, 0xff,
+ 0x3a, 0x4a, 0x3c, 0xff, 0x39, 0x4a, 0x3c, 0xff,
+ 0x34, 0x51, 0x42, 0xff, 0x34, 0x51, 0x41, 0xff,
+ 0x2f, 0x3d, 0x31, 0xff, 0x34, 0x50, 0x41, 0xff,
+ 0x27, 0x69, 0x52, 0xff, 0x21, 0x49, 0x31, 0xff,
+ 0x24, 0x59, 0x42, 0xff, 0x29, 0x79, 0x62, 0xff,
+ 0x29, 0x71, 0x63, 0xff, 0x29, 0x61, 0x52, 0xff,
+ 0x29, 0x71, 0x63, 0xff, 0x29, 0x71, 0x62, 0xff,
+ 0x29, 0x6f, 0x5b, 0xff, 0x31, 0x85, 0x73, 0xff,
+ 0x31, 0x86, 0x73, 0xff, 0x31, 0x85, 0x73, 0xff,
+ 0x32, 0x74, 0x63, 0xff, 0x31, 0x74, 0x62, 0xff,
+ 0x3a, 0x8a, 0x7b, 0xff, 0x31, 0x74, 0x62, 0xff,
+ 0x29, 0x69, 0x5b, 0xff, 0x29, 0x69, 0x5a, 0xff,
+ 0x3f, 0x7f, 0x70, 0xff, 0x3f, 0x7e, 0x70, 0xff,
+ 0x55, 0x69, 0x63, 0xff, 0x60, 0x79, 0x73, 0xff,
+ 0x60, 0x79, 0x73, 0xff, 0x4a, 0x59, 0x52, 0xff,
+ 0x4a, 0x4d, 0x4a, 0xff, 0x57, 0x59, 0x57, 0xff,
+ 0x65, 0x65, 0x65, 0xff, 0x4a, 0x4c, 0x4a, 0xff,
+ 0x63, 0x61, 0x5b, 0xff, 0x6d, 0x6a, 0x65, 0xff,
+ 0x6e, 0x6b, 0x65, 0xff, 0x6d, 0x6a, 0x65, 0xff,
+ 0x73, 0x71, 0x73, 0xff, 0x7b, 0x78, 0x78, 0xff,
+ 0x84, 0x7f, 0x7e, 0xff, 0x8b, 0x85, 0x83, 0xff,
+ 0x37, 0x5c, 0x48, 0xff, 0x31, 0x4d, 0x3a, 0xff,
+ 0x37, 0x5c, 0x48, 0xff, 0x3c, 0x6a, 0x55, 0xff,
+ 0x42, 0x6e, 0x5b, 0xff, 0x3c, 0x64, 0x4f, 0xff,
+ 0x3d, 0x64, 0x50, 0xff, 0x42, 0x6d, 0x5a, 0xff,
+ 0x4b, 0x76, 0x66, 0xff, 0x4a, 0x7d, 0x6b, 0xff,
+ 0x4a, 0x76, 0x66, 0xff, 0x4a, 0x65, 0x5a, 0xff,
+ 0x45, 0x60, 0x6b, 0xff, 0x45, 0x60, 0x6b, 0xff,
+ 0x45, 0x60, 0x6b, 0xff, 0x44, 0x60, 0x6b, 0xff,
+ 0x55, 0x7b, 0x87, 0xff, 0x55, 0x7b, 0x86, 0xff,
+ 0x3a, 0x49, 0x4a, 0xff, 0x39, 0x49, 0x4a, 0xff,
+ 0x3a, 0x31, 0x2a, 0xff, 0x3a, 0x31, 0x29, 0xff,
+ 0x3a, 0x31, 0x29, 0xff, 0x39, 0x6d, 0x5a, 0xff,
+ 0x37, 0x60, 0x50, 0xff, 0x37, 0x60, 0x4f, 0xff,
+ 0x37, 0x60, 0x50, 0xff, 0x31, 0x51, 0x42, 0xff,
+ 0x27, 0x57, 0x45, 0xff, 0x21, 0x39, 0x29, 0xff,
+ 0x21, 0x39, 0x29, 0xff, 0x26, 0x56, 0x44, 0xff,
+ 0x27, 0x6a, 0x5b, 0xff, 0x29, 0x79, 0x6b, 0xff,
+ 0x27, 0x6a, 0x5b, 0xff, 0x29, 0x79, 0x6b, 0xff,
+ 0x1f, 0x60, 0x4d, 0xff, 0x29, 0x86, 0x73, 0xff,
+ 0x29, 0x86, 0x74, 0xff, 0x29, 0x85, 0x73, 0xff,
+ 0x2a, 0x82, 0x74, 0xff, 0x29, 0x81, 0x73, 0xff,
+ 0x21, 0x6a, 0x5e, 0xff, 0x29, 0x81, 0x73, 0xff,
+ 0x32, 0x7a, 0x6b, 0xff, 0x31, 0x79, 0x6b, 0xff,
+ 0x29, 0x6a, 0x5b, 0xff, 0x31, 0x79, 0x6b, 0xff,
+ 0x32, 0x7e, 0x6b, 0xff, 0x21, 0x55, 0x4a, 0xff,
+ 0x27, 0x63, 0x55, 0xff, 0x26, 0x62, 0x55, 0xff,
+ 0x4b, 0x49, 0x4b, 0xff, 0x45, 0x5a, 0x58, 0xff,
+ 0x4a, 0x49, 0x4a, 0xff, 0x44, 0x5a, 0x58, 0xff,
+ 0x5b, 0x60, 0x5b, 0xff, 0x63, 0x67, 0x63, 0xff,
+ 0x6b, 0x6e, 0x6b, 0xff, 0x6b, 0x6d, 0x6b, 0xff,
+ 0x6b, 0x6e, 0x6b, 0xff, 0x73, 0x74, 0x73, 0xff,
+ 0x7c, 0x7b, 0x7c, 0xff, 0x83, 0x81, 0x83, 0xff,
+ 0x37, 0x5c, 0x47, 0xff, 0x3c, 0x6a, 0x55, 0xff,
+ 0x32, 0x4d, 0x3a, 0xff, 0x37, 0x5b, 0x47, 0xff,
+ 0x42, 0x6d, 0x5b, 0xff, 0x3c, 0x63, 0x4f, 0xff,
+ 0x3d, 0x64, 0x50, 0xff, 0x42, 0x6d, 0x5a, 0xff,
+ 0x4a, 0x75, 0x66, 0xff, 0x4a, 0x75, 0x65, 0xff,
+ 0x4a, 0x7e, 0x6b, 0xff, 0x4a, 0x75, 0x65, 0xff,
+ 0x3a, 0x45, 0x3a, 0xff, 0x44, 0x5f, 0x6b, 0xff,
+ 0x3a, 0x45, 0x3a, 0xff, 0x5a, 0x95, 0xcd, 0xff,
+ 0x71, 0xad, 0xc3, 0xff, 0x55, 0x7a, 0x86, 0xff,
+ 0x55, 0x7b, 0x87, 0xff, 0x39, 0x49, 0x4a, 0xff,
+ 0x3a, 0x31, 0x29, 0xff, 0x39, 0x30, 0x29, 0xff,
+ 0x3a, 0x45, 0x3a, 0xff, 0x39, 0x59, 0x4a, 0xff,
+ 0x3c, 0x6f, 0x5d, 0xff, 0x31, 0x51, 0x41, 0xff,
+ 0x32, 0x51, 0x42, 0xff, 0x37, 0x60, 0x4f, 0xff,
+ 0x29, 0x65, 0x52, 0xff, 0x20, 0x38, 0x29, 0xff,
+ 0x21, 0x39, 0x29, 0xff, 0x21, 0x38, 0x29, 0xff,
+ 0x26, 0x69, 0x5b, 0xff, 0x26, 0x69, 0x5a, 0xff,
+ 0x27, 0x69, 0x5b, 0xff, 0x26, 0x69, 0x5a, 0xff,
+ 0x1e, 0x60, 0x4d, 0xff, 0x23, 0x72, 0x60, 0xff,
+ 0x29, 0x86, 0x73, 0xff, 0x29, 0x85, 0x73, 0xff,
+ 0x29, 0x82, 0x73, 0xff, 0x29, 0x81, 0x73, 0xff,
+ 0x21, 0x69, 0x5d, 0xff, 0x29, 0x81, 0x73, 0xff,
+ 0x31, 0x7a, 0x6b, 0xff, 0x31, 0x79, 0x6b, 0xff,
+ 0x32, 0x7a, 0x6b, 0xff, 0x29, 0x69, 0x5a, 0xff,
+ 0x2c, 0x70, 0x60, 0xff, 0x26, 0x62, 0x55, 0xff,
+ 0x2c, 0x70, 0x60, 0xff, 0x31, 0x7d, 0x6b, 0xff,
+ 0x3a, 0x7e, 0x73, 0xff, 0x44, 0x5a, 0x57, 0xff,
+ 0x4a, 0x49, 0x4a, 0xff, 0x4a, 0x49, 0x4a, 0xff,
+ 0x5b, 0x60, 0x5b, 0xff, 0x52, 0x59, 0x52, 0xff,
+ 0x5b, 0x60, 0x5b, 0xff, 0x62, 0x66, 0x62, 0xff,
+ 0x6b, 0x6d, 0x6b, 0xff, 0x6b, 0x6d, 0x6b, 0xff,
+ 0x73, 0x74, 0x73, 0xff, 0x7b, 0x7a, 0x7b, 0xff,
+ 0x42, 0x7a, 0x63, 0xff, 0x42, 0x79, 0x62, 0xff,
+ 0x3d, 0x6b, 0x55, 0xff, 0x31, 0x4d, 0x39, 0xff,
+ 0x32, 0x51, 0x3a, 0xff, 0x3c, 0x64, 0x4f, 0xff,
+ 0x32, 0x51, 0x3a, 0xff, 0x31, 0x51, 0x39, 0xff,
+ 0x4a, 0x65, 0x5b, 0xff, 0x4a, 0x65, 0x5a, 0xff,
+ 0x4a, 0x66, 0x5b, 0xff, 0x4a, 0x75, 0x65, 0xff,
+ 0x45, 0x60, 0x6b, 0xff, 0x39, 0x45, 0x39, 0xff,
+ 0x3a, 0x45, 0x3a, 0xff, 0x5a, 0x96, 0xce, 0xff,
+ 0x8c, 0xdf, 0xff, 0xff, 0x70, 0xac, 0xc2, 0xff,
+ 0x55, 0x7b, 0x87, 0xff, 0x55, 0x7b, 0x86, 0xff,
+ 0x3a, 0x45, 0x3a, 0xff, 0x39, 0x30, 0x29, 0xff,
+ 0x3a, 0x45, 0x3a, 0xff, 0x39, 0x59, 0x4a, 0xff,
+ 0x3d, 0x6f, 0x5e, 0xff, 0x3c, 0x6e, 0x5d, 0xff,
+ 0x37, 0x60, 0x50, 0xff, 0x37, 0x60, 0x4f, 0xff,
+ 0x27, 0x57, 0x45, 0xff, 0x21, 0x38, 0x29, 0xff,
+ 0x21, 0x39, 0x2a, 0xff, 0x24, 0x47, 0x37, 0xff,
+ 0x24, 0x59, 0x4a, 0xff, 0x26, 0x69, 0x5a, 0xff,
+ 0x27, 0x6a, 0x5b, 0xff, 0x26, 0x69, 0x5a, 0xff,
+ 0x1e, 0x60, 0x4d, 0xff, 0x23, 0x72, 0x60, 0xff,
+ 0x1f, 0x60, 0x4d, 0xff, 0x24, 0x73, 0x60, 0xff,
+ 0x21, 0x6a, 0x5e, 0xff, 0x21, 0x69, 0x5d, 0xff,
+ 0x19, 0x51, 0x48, 0xff, 0x21, 0x69, 0x5d, 0xff,
+ 0x32, 0x7a, 0x6b, 0xff, 0x29, 0x69, 0x5a, 0xff,
+ 0x21, 0x59, 0x4a, 0xff, 0x21, 0x59, 0x4a, 0xff,
+ 0x32, 0x7e, 0x6b, 0xff, 0x31, 0x7d, 0x6b, 0xff,
+ 0x32, 0x7e, 0x6b, 0xff, 0x31, 0x7d, 0x6b, 0xff,
+ 0x3a, 0x7e, 0x73, 0xff, 0x39, 0x7d, 0x73, 0xff,
+ 0x3a, 0x7e, 0x74, 0xff, 0x44, 0x5a, 0x58, 0xff,
+ 0x5b, 0x60, 0x5b, 0xff, 0x5a, 0x60, 0x5a, 0xff,
+ 0x5b, 0x60, 0x5b, 0xff, 0x63, 0x66, 0x63, 0xff,
+ 0x6b, 0x6e, 0x6b, 0xff, 0x73, 0x74, 0x73, 0xff,
+ 0x74, 0x74, 0x74, 0xff, 0x73, 0x74, 0x73, 0xff,
+ 0x42, 0x7a, 0x63, 0xff, 0x41, 0x79, 0x62, 0xff,
+ 0x42, 0x79, 0x63, 0xff, 0x3c, 0x6a, 0x55, 0xff,
+ 0x37, 0x5b, 0x45, 0xff, 0x36, 0x5a, 0x44, 0xff,
+ 0x31, 0x51, 0x3a, 0xff, 0x31, 0x50, 0x39, 0xff,
+ 0x4a, 0x65, 0x5b, 0xff, 0x4a, 0x6d, 0x60, 0xff,
+ 0x4a, 0x75, 0x65, 0xff, 0x4a, 0x6d, 0x5f, 0xff,
+ 0x50, 0x7b, 0x9c, 0xff, 0x44, 0x5f, 0x6b, 0xff,
+ 0x45, 0x60, 0x6b, 0xff, 0x5a, 0x95, 0xcd, 0xff,
+ 0x8c, 0xdf, 0xff, 0xff, 0x70, 0xac, 0xc2, 0xff,
+ 0x55, 0x7b, 0x86, 0xff, 0x55, 0x7a, 0x86, 0xff,
+ 0x3a, 0x6d, 0x5b, 0xff, 0x39, 0x6d, 0x5a, 0xff,
+ 0x3a, 0x59, 0x4a, 0xff, 0x39, 0x59, 0x4a, 0xff,
+ 0x37, 0x60, 0x50, 0xff, 0x41, 0x7d, 0x6b, 0xff,
+ 0x42, 0x7e, 0x6b, 0xff, 0x3c, 0x6e, 0x5d, 0xff,
+ 0x29, 0x65, 0x52, 0xff, 0x29, 0x65, 0x52, 0xff,
+ 0x21, 0x39, 0x29, 0xff, 0x20, 0x38, 0x29, 0xff,
+ 0x21, 0x49, 0x3a, 0xff, 0x23, 0x59, 0x4a, 0xff,
+ 0x24, 0x59, 0x4a, 0xff, 0x23, 0x59, 0x4a, 0xff,
+ 0x19, 0x4d, 0x3a, 0xff, 0x18, 0x4d, 0x39, 0xff,
+ 0x19, 0x4d, 0x3a, 0xff, 0x1e, 0x5f, 0x4c, 0xff,
+ 0x21, 0x69, 0x5d, 0xff, 0x21, 0x69, 0x5d, 0xff,
+ 0x10, 0x39, 0x31, 0xff, 0x10, 0x38, 0x31, 0xff,
+ 0x19, 0x49, 0x3a, 0xff, 0x21, 0x59, 0x4a, 0xff,
+ 0x31, 0x79, 0x6b, 0xff, 0x29, 0x69, 0x5a, 0xff,
+ 0x2c, 0x70, 0x60, 0xff, 0x2c, 0x70, 0x60, 0xff,
+ 0x26, 0x63, 0x55, 0xff, 0x2b, 0x70, 0x5f, 0xff,
+ 0x3a, 0x7e, 0x73, 0xff, 0x39, 0x7d, 0x73, 0xff,
+ 0x3f, 0x6c, 0x65, 0xff, 0x3f, 0x6b, 0x65, 0xff,
+ 0x5b, 0x60, 0x5b, 0xff, 0x52, 0x59, 0x52, 0xff,
+ 0x63, 0x67, 0x63, 0xff, 0x62, 0x66, 0x62, 0xff,
+ 0x6b, 0x6d, 0x6b, 0xff, 0x6b, 0x6d, 0x6b, 0xff,
+ 0x6b, 0x6d, 0x6b, 0xff, 0x7b, 0x7a, 0x7b, 0xff,
+ 0x2a, 0x55, 0x45, 0xff, 0x29, 0x55, 0x45, 0xff,
+ 0x3a, 0x6a, 0x58, 0xff, 0x4a, 0x7d, 0x6b, 0xff,
+ 0x42, 0x6f, 0x5b, 0xff, 0x31, 0x51, 0x3a, 0xff,
+ 0x3a, 0x60, 0x4a, 0xff, 0x39, 0x60, 0x4a, 0xff,
+ 0x3a, 0x62, 0x50, 0xff, 0x42, 0x6d, 0x5d, 0xff,
+ 0x3a, 0x61, 0x50, 0xff, 0x4a, 0x79, 0x6b, 0xff,
+ 0x48, 0x6f, 0x6e, 0xff, 0x47, 0x6f, 0x6e, 0xff,
+ 0x3a, 0x55, 0x3a, 0xff, 0x63, 0xa2, 0xd6, 0xff,
+ 0xb5, 0xef, 0xff, 0xff, 0x84, 0xba, 0xc5, 0xff,
+ 0x53, 0x86, 0x8c, 0xff, 0x52, 0x85, 0x8c, 0xff,
+ 0x3a, 0x7e, 0x74, 0xff, 0x3a, 0x7d, 0x73, 0xff,
+ 0x3a, 0x6e, 0x63, 0xff, 0x39, 0x5d, 0x52, 0xff,
+ 0x32, 0x5f, 0x50, 0xff, 0x3a, 0x71, 0x63, 0xff,
+ 0x32, 0x5f, 0x50, 0xff, 0x31, 0x5e, 0x4f, 0xff,
+ 0x42, 0x7e, 0x74, 0xff, 0x3a, 0x5e, 0x55, 0xff,
+ 0x32, 0x40, 0x37, 0xff, 0x29, 0x20, 0x19, 0xff,
+ 0x24, 0x3d, 0x32, 0xff, 0x29, 0x51, 0x42, 0xff,
+ 0x24, 0x3d, 0x32, 0xff, 0x23, 0x3d, 0x31, 0xff,
+ 0x19, 0x21, 0x19, 0xff, 0x1e, 0x46, 0x34, 0xff,
+ 0x1f, 0x47, 0x34, 0xff, 0x21, 0x59, 0x42, 0xff,
+ 0x27, 0x55, 0x48, 0xff, 0x31, 0x86, 0x73, 0xff,
+ 0x27, 0x55, 0x48, 0xff, 0x21, 0x3d, 0x31, 0xff,
+ 0x19, 0x25, 0x19, 0xff, 0x1e, 0x45, 0x37, 0xff,
+ 0x24, 0x66, 0x55, 0xff, 0x29, 0x85, 0x73, 0xff,
+ 0x2a, 0x82, 0x6b, 0xff, 0x1e, 0x5c, 0x45, 0xff,
+ 0x19, 0x49, 0x32, 0xff, 0x1e, 0x5c, 0x44, 0xff,
+ 0x24, 0x6c, 0x5e, 0xff, 0x29, 0x79, 0x6b, 0xff,
+ 0x1f, 0x5f, 0x50, 0xff, 0x23, 0x6c, 0x5d, 0xff,
+ 0x58, 0x72, 0x6b, 0xff, 0x63, 0x59, 0x5a, 0xff,
+ 0x63, 0x59, 0x5b, 0xff, 0x58, 0x71, 0x6b, 0xff,
+ 0x6b, 0x67, 0x66, 0xff, 0x6b, 0x67, 0x65, 0xff,
+ 0x7c, 0x7a, 0x7c, 0xff, 0x7b, 0x79, 0x7b, 0xff,
+ 0x19, 0x41, 0x31, 0xff, 0x29, 0x55, 0x44, 0xff,
+ 0x4a, 0x7e, 0x6b, 0xff, 0x39, 0x69, 0x57, 0xff,
+ 0x3a, 0x60, 0x4a, 0xff, 0x39, 0x5f, 0x4a, 0xff,
+ 0x42, 0x6f, 0x5b, 0xff, 0x42, 0x6e, 0x5a, 0xff,
+ 0x3a, 0x61, 0x50, 0xff, 0x31, 0x55, 0x41, 0xff,
+ 0x32, 0x55, 0x42, 0xff, 0x42, 0x6d, 0x5d, 0xff,
+ 0x47, 0x6f, 0x6e, 0xff, 0x47, 0x6e, 0x6d, 0xff,
+ 0x48, 0x6f, 0x6e, 0xff, 0x62, 0xa2, 0xd6, 0xff,
+ 0xb5, 0xef, 0xff, 0xff, 0x83, 0xba, 0xc5, 0xff,
+ 0x52, 0x86, 0x8c, 0xff, 0x21, 0x51, 0x52, 0xff,
+ 0x3a, 0x7e, 0x73, 0xff, 0x39, 0x7d, 0x73, 0xff,
+ 0x3a, 0x6e, 0x63, 0xff, 0x39, 0x5d, 0x52, 0xff,
+ 0x31, 0x5f, 0x50, 0xff, 0x31, 0x5e, 0x4f, 0xff,
+ 0x29, 0x4c, 0x3d, 0xff, 0x39, 0x71, 0x62, 0xff,
+ 0x42, 0x7e, 0x73, 0xff, 0x41, 0x7d, 0x73, 0xff,
+ 0x3a, 0x5f, 0x55, 0xff, 0x31, 0x3f, 0x37, 0xff,
+ 0x24, 0x3d, 0x31, 0xff, 0x1e, 0x28, 0x20, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x29, 0x51, 0x42, 0xff,
+ 0x1c, 0x33, 0x26, 0xff, 0x18, 0x20, 0x18, 0xff,
+ 0x1e, 0x46, 0x34, 0xff, 0x1e, 0x46, 0x34, 0xff,
+ 0x2c, 0x6d, 0x5d, 0xff, 0x2b, 0x6d, 0x5d, 0xff,
+ 0x32, 0x86, 0x73, 0xff, 0x26, 0x55, 0x47, 0xff,
+ 0x1e, 0x45, 0x37, 0xff, 0x1e, 0x44, 0x36, 0xff,
+ 0x24, 0x65, 0x55, 0xff, 0x23, 0x65, 0x55, 0xff,
+ 0x24, 0x6f, 0x58, 0xff, 0x23, 0x6e, 0x57, 0xff,
+ 0x1e, 0x5c, 0x45, 0xff, 0x18, 0x49, 0x31, 0xff,
+ 0x1e, 0x5f, 0x50, 0xff, 0x29, 0x79, 0x6b, 0xff,
+ 0x24, 0x6c, 0x5d, 0xff, 0x23, 0x6c, 0x5d, 0xff,
+ 0x58, 0x71, 0x6b, 0xff, 0x5d, 0x65, 0x62, 0xff,
+ 0x63, 0x59, 0x5b, 0xff, 0x5d, 0x65, 0x62, 0xff,
+ 0x63, 0x5d, 0x5b, 0xff, 0x6b, 0x66, 0x65, 0xff,
+ 0x73, 0x70, 0x71, 0xff, 0x7b, 0x79, 0x7b, 0xff,
+ 0x29, 0x55, 0x45, 0xff, 0x39, 0x69, 0x58, 0xff,
+ 0x3a, 0x6a, 0x58, 0xff, 0x29, 0x55, 0x44, 0xff,
+ 0x42, 0x6f, 0x5b, 0xff, 0x4a, 0x7d, 0x6b, 0xff,
+ 0x42, 0x6f, 0x5b, 0xff, 0x4a, 0x7d, 0x6b, 0xff,
+ 0x42, 0x6e, 0x5e, 0xff, 0x39, 0x61, 0x4f, 0xff,
+ 0x4a, 0x7a, 0x6b, 0xff, 0x42, 0x6d, 0x5d, 0xff,
+ 0x48, 0x6f, 0x6e, 0xff, 0x47, 0x6e, 0x6d, 0xff,
+ 0x55, 0x89, 0xa2, 0xff, 0x63, 0xa2, 0xd6, 0xff,
+ 0xb5, 0xef, 0xff, 0xff, 0x83, 0xba, 0xc5, 0xff,
+ 0x53, 0x86, 0x8c, 0xff, 0x21, 0x51, 0x52, 0xff,
+ 0x3a, 0x7e, 0x73, 0xff, 0x39, 0x6d, 0x62, 0xff,
+ 0x3a, 0x4d, 0x42, 0xff, 0x39, 0x4d, 0x42, 0xff,
+ 0x29, 0x4c, 0x3d, 0xff, 0x21, 0x38, 0x29, 0xff,
+ 0x2a, 0x4c, 0x3d, 0xff, 0x31, 0x5e, 0x4f, 0xff,
+ 0x42, 0x7e, 0x73, 0xff, 0x42, 0x7d, 0x73, 0xff,
+ 0x42, 0x7e, 0x74, 0xff, 0x39, 0x5e, 0x55, 0xff,
+ 0x24, 0x3d, 0x32, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x19, 0x14, 0x10, 0xff,
+ 0x1c, 0x34, 0x27, 0xff, 0x1e, 0x46, 0x34, 0xff,
+ 0x21, 0x59, 0x42, 0xff, 0x1e, 0x46, 0x34, 0xff,
+ 0x27, 0x55, 0x48, 0xff, 0x2c, 0x6d, 0x5d, 0xff,
+ 0x32, 0x86, 0x74, 0xff, 0x31, 0x85, 0x73, 0xff,
+ 0x24, 0x65, 0x55, 0xff, 0x23, 0x65, 0x55, 0xff,
+ 0x24, 0x66, 0x55, 0xff, 0x19, 0x24, 0x19, 0xff,
+ 0x1e, 0x5c, 0x45, 0xff, 0x29, 0x81, 0x6b, 0xff,
+ 0x24, 0x6f, 0x58, 0xff, 0x1e, 0x5c, 0x44, 0xff,
+ 0x19, 0x51, 0x42, 0xff, 0x29, 0x79, 0x6b, 0xff,
+ 0x2a, 0x7a, 0x6b, 0xff, 0x29, 0x79, 0x6b, 0xff,
+ 0x58, 0x72, 0x6b, 0xff, 0x5d, 0x65, 0x62, 0xff,
+ 0x58, 0x72, 0x6b, 0xff, 0x63, 0x59, 0x5a, 0xff,
+ 0x63, 0x5d, 0x5b, 0xff, 0x6b, 0x66, 0x65, 0xff,
+ 0x74, 0x70, 0x71, 0xff, 0x73, 0x70, 0x70, 0xff,
+ 0x3a, 0x69, 0x58, 0xff, 0x4a, 0x7d, 0x6b, 0xff,
+ 0x3a, 0x69, 0x58, 0xff, 0x39, 0x69, 0x57, 0xff,
+ 0x42, 0x6f, 0x5b, 0xff, 0x41, 0x6e, 0x5a, 0xff,
+ 0x4a, 0x7e, 0x6b, 0xff, 0x4a, 0x7d, 0x6a, 0xff,
+ 0x42, 0x6d, 0x5d, 0xff, 0x41, 0x6d, 0x5d, 0xff,
+ 0x4a, 0x79, 0x6b, 0xff, 0x41, 0x6d, 0x5d, 0xff,
+ 0x47, 0x6f, 0x6e, 0xff, 0x47, 0x6e, 0x6d, 0xff,
+ 0x47, 0x6f, 0x6e, 0xff, 0x55, 0x88, 0xa1, 0xff,
+ 0x84, 0xba, 0xc6, 0xff, 0x52, 0x85, 0x8b, 0xff,
+ 0x21, 0x51, 0x52, 0xff, 0x20, 0x50, 0x52, 0xff,
+ 0x3a, 0x5d, 0x52, 0xff, 0x39, 0x5d, 0x52, 0xff,
+ 0x3a, 0x5d, 0x52, 0xff, 0x39, 0x4c, 0x41, 0xff,
+ 0x32, 0x5f, 0x50, 0xff, 0x31, 0x5e, 0x4f, 0xff,
+ 0x29, 0x4c, 0x3c, 0xff, 0x31, 0x5e, 0x4f, 0xff,
+ 0x42, 0x7e, 0x73, 0xff, 0x41, 0x7d, 0x73, 0xff,
+ 0x42, 0x7e, 0x73, 0xff, 0x41, 0x7d, 0x73, 0xff,
+ 0x29, 0x51, 0x42, 0xff, 0x1e, 0x28, 0x21, 0xff,
+ 0x19, 0x14, 0x10, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x1c, 0x33, 0x27, 0xff, 0x1e, 0x46, 0x34, 0xff,
+ 0x21, 0x59, 0x42, 0xff, 0x20, 0x59, 0x41, 0xff,
+ 0x27, 0x55, 0x47, 0xff, 0x2c, 0x6d, 0x5d, 0xff,
+ 0x31, 0x86, 0x73, 0xff, 0x31, 0x85, 0x73, 0xff,
+ 0x29, 0x86, 0x73, 0xff, 0x29, 0x85, 0x73, 0xff,
+ 0x24, 0x65, 0x55, 0xff, 0x23, 0x65, 0x55, 0xff,
+ 0x1e, 0x5c, 0x45, 0xff, 0x23, 0x6e, 0x57, 0xff,
+ 0x29, 0x82, 0x6b, 0xff, 0x1e, 0x5b, 0x44, 0xff,
+ 0x19, 0x51, 0x42, 0xff, 0x18, 0x51, 0x41, 0xff,
+ 0x24, 0x6c, 0x5d, 0xff, 0x29, 0x79, 0x6a, 0xff,
+ 0x52, 0x7e, 0x73, 0xff, 0x52, 0x7d, 0x73, 0xff,
+ 0x58, 0x71, 0x6b, 0xff, 0x5d, 0x65, 0x62, 0xff,
+ 0x63, 0x5d, 0x5b, 0xff, 0x6b, 0x66, 0x65, 0xff,
+ 0x73, 0x70, 0x70, 0xff, 0x73, 0x70, 0x70, 0xff,
+ 0x32, 0x70, 0x5b, 0xff, 0x31, 0x79, 0x63, 0xff,
+ 0x32, 0x70, 0x5b, 0xff, 0x31, 0x70, 0x5a, 0xff,
+ 0x3a, 0x73, 0x5e, 0xff, 0x42, 0x81, 0x6b, 0xff,
+ 0x3a, 0x73, 0x5e, 0xff, 0x39, 0x73, 0x5d, 0xff,
+ 0x3a, 0x76, 0x63, 0xff, 0x3a, 0x75, 0x63, 0xff,
+ 0x3a, 0x76, 0x63, 0xff, 0x39, 0x75, 0x63, 0xff,
+ 0x4b, 0x7a, 0x6b, 0xff, 0x45, 0x6c, 0x63, 0xff,
+ 0x3a, 0x51, 0x53, 0xff, 0x44, 0x6c, 0x63, 0xff,
+ 0x5b, 0x92, 0x9d, 0xff, 0x5a, 0x92, 0x9c, 0xff,
+ 0x3a, 0x5f, 0x55, 0xff, 0x29, 0x45, 0x31, 0xff,
+ 0x2a, 0x45, 0x3a, 0xff, 0x3f, 0x6b, 0x60, 0xff,
+ 0x4a, 0x7e, 0x74, 0xff, 0x3f, 0x6a, 0x60, 0xff,
+ 0x21, 0x39, 0x32, 0xff, 0x3c, 0x6c, 0x5d, 0xff,
+ 0x3d, 0x6c, 0x5e, 0xff, 0x3c, 0x6c, 0x5d, 0xff,
+ 0x3d, 0x75, 0x63, 0xff, 0x3c, 0x74, 0x63, 0xff,
+ 0x3d, 0x74, 0x63, 0xff, 0x3c, 0x74, 0x63, 0xff,
+ 0x2f, 0x5c, 0x4b, 0xff, 0x24, 0x42, 0x31, 0xff,
+ 0x19, 0x29, 0x19, 0xff, 0x19, 0x28, 0x19, 0xff,
+ 0x21, 0x41, 0x2a, 0xff, 0x21, 0x4a, 0x31, 0xff,
+ 0x21, 0x5d, 0x42, 0xff, 0x21, 0x53, 0x39, 0xff,
+ 0x16, 0x4d, 0x3a, 0xff, 0x1b, 0x61, 0x4a, 0xff,
+ 0x1c, 0x61, 0x4a, 0xff, 0x1b, 0x61, 0x4a, 0xff,
+ 0x1f, 0x73, 0x5e, 0xff, 0x21, 0x81, 0x6b, 0xff,
+ 0x1f, 0x73, 0x5e, 0xff, 0x1e, 0x73, 0x5d, 0xff,
+ 0x24, 0x72, 0x60, 0xff, 0x29, 0x81, 0x73, 0xff,
+ 0x24, 0x72, 0x60, 0xff, 0x19, 0x51, 0x39, 0xff,
+ 0x19, 0x3d, 0x2a, 0xff, 0x1b, 0x4d, 0x3a, 0xff,
+ 0x1f, 0x5d, 0x4a, 0xff, 0x1e, 0x5d, 0x4a, 0xff,
+ 0x2c, 0x63, 0x58, 0xff, 0x31, 0x75, 0x63, 0xff,
+ 0x2f, 0x6c, 0x5e, 0xff, 0x2c, 0x62, 0x58, 0xff,
+ 0x5b, 0x5e, 0x5b, 0xff, 0x60, 0x65, 0x63, 0xff,
+ 0x60, 0x66, 0x63, 0xff, 0x65, 0x6d, 0x6b, 0xff,
+ 0x31, 0x70, 0x5b, 0xff, 0x31, 0x70, 0x5a, 0xff,
+ 0x32, 0x70, 0x5b, 0xff, 0x31, 0x79, 0x62, 0xff,
+ 0x42, 0x82, 0x6b, 0xff, 0x39, 0x72, 0x5d, 0xff,
+ 0x3a, 0x73, 0x5d, 0xff, 0x31, 0x64, 0x4f, 0xff,
+ 0x31, 0x64, 0x52, 0xff, 0x29, 0x52, 0x41, 0xff,
+ 0x32, 0x64, 0x52, 0xff, 0x31, 0x64, 0x52, 0xff,
+ 0x45, 0x6c, 0x63, 0xff, 0x44, 0x6c, 0x62, 0xff,
+ 0x45, 0x6c, 0x63, 0xff, 0x4a, 0x79, 0x6b, 0xff,
+ 0x5b, 0x92, 0x9c, 0xff, 0x5a, 0x91, 0x9c, 0xff,
+ 0x4a, 0x78, 0x79, 0xff, 0x39, 0x5e, 0x55, 0xff,
+ 0x34, 0x58, 0x4d, 0xff, 0x34, 0x57, 0x4c, 0xff,
+ 0x3f, 0x6b, 0x60, 0xff, 0x3f, 0x6a, 0x60, 0xff,
+ 0x21, 0x39, 0x31, 0xff, 0x3c, 0x6c, 0x5d, 0xff,
+ 0x4a, 0x86, 0x73, 0xff, 0x4a, 0x85, 0x73, 0xff,
+ 0x37, 0x6b, 0x5b, 0xff, 0x36, 0x6a, 0x5a, 0xff,
+ 0x3d, 0x74, 0x63, 0xff, 0x3c, 0x74, 0x62, 0xff,
+ 0x2f, 0x5c, 0x4a, 0xff, 0x23, 0x42, 0x31, 0xff,
+ 0x19, 0x29, 0x19, 0xff, 0x18, 0x28, 0x18, 0xff,
+ 0x21, 0x5d, 0x42, 0xff, 0x20, 0x4a, 0x31, 0xff,
+ 0x21, 0x54, 0x3a, 0xff, 0x21, 0x4a, 0x31, 0xff,
+ 0x16, 0x4d, 0x3a, 0xff, 0x20, 0x75, 0x5a, 0xff,
+ 0x21, 0x76, 0x5b, 0xff, 0x1b, 0x61, 0x4a, 0xff,
+ 0x1c, 0x64, 0x50, 0xff, 0x1e, 0x72, 0x5d, 0xff,
+ 0x1e, 0x73, 0x5d, 0xff, 0x1e, 0x72, 0x5d, 0xff,
+ 0x24, 0x71, 0x60, 0xff, 0x23, 0x71, 0x60, 0xff,
+ 0x29, 0x82, 0x73, 0xff, 0x23, 0x71, 0x60, 0xff,
+ 0x1c, 0x4d, 0x3a, 0xff, 0x18, 0x3c, 0x29, 0xff,
+ 0x1c, 0x4d, 0x3a, 0xff, 0x1e, 0x5d, 0x4a, 0xff,
+ 0x29, 0x59, 0x52, 0xff, 0x2b, 0x62, 0x57, 0xff,
+ 0x32, 0x76, 0x63, 0xff, 0x29, 0x59, 0x52, 0xff,
+ 0x60, 0x65, 0x63, 0xff, 0x60, 0x65, 0x62, 0xff,
+ 0x60, 0x65, 0x63, 0xff, 0x60, 0x65, 0x62, 0xff,
+ 0x32, 0x67, 0x53, 0xff, 0x31, 0x66, 0x52, 0xff,
+ 0x32, 0x70, 0x5b, 0xff, 0x31, 0x79, 0x63, 0xff,
+ 0x42, 0x82, 0x6b, 0xff, 0x42, 0x81, 0x6b, 0xff,
+ 0x32, 0x64, 0x50, 0xff, 0x29, 0x55, 0x42, 0xff,
+ 0x29, 0x53, 0x42, 0xff, 0x29, 0x52, 0x42, 0xff,
+ 0x2a, 0x53, 0x42, 0xff, 0x31, 0x64, 0x52, 0xff,
+ 0x45, 0x6c, 0x63, 0xff, 0x44, 0x6c, 0x62, 0xff,
+ 0x3f, 0x5f, 0x5b, 0xff, 0x4a, 0x79, 0x6b, 0xff,
+ 0x4a, 0x78, 0x79, 0xff, 0x4a, 0x78, 0x78, 0xff,
+ 0x4a, 0x78, 0x79, 0xff, 0x39, 0x5e, 0x55, 0xff,
+ 0x34, 0x58, 0x4d, 0xff, 0x34, 0x57, 0x4d, 0xff,
+ 0x35, 0x58, 0x4d, 0xff, 0x29, 0x45, 0x39, 0xff,
+ 0x2f, 0x53, 0x48, 0xff, 0x2e, 0x52, 0x47, 0xff,
+ 0x3d, 0x6c, 0x5e, 0xff, 0x3c, 0x6c, 0x5d, 0xff,
+ 0x37, 0x6b, 0x5b, 0xff, 0x42, 0x7d, 0x6b, 0xff,
+ 0x32, 0x62, 0x53, 0xff, 0x3c, 0x74, 0x63, 0xff,
+ 0x3a, 0x76, 0x63, 0xff, 0x39, 0x75, 0x62, 0xff,
+ 0x24, 0x43, 0x32, 0xff, 0x24, 0x42, 0x31, 0xff,
+ 0x21, 0x5d, 0x42, 0xff, 0x21, 0x41, 0x29, 0xff,
+ 0x21, 0x4b, 0x32, 0xff, 0x21, 0x5d, 0x42, 0xff,
+ 0x1c, 0x61, 0x4a, 0xff, 0x1b, 0x61, 0x4a, 0xff,
+ 0x16, 0x4d, 0x3a, 0xff, 0x1b, 0x61, 0x4a, 0xff,
+ 0x1c, 0x64, 0x50, 0xff, 0x1b, 0x64, 0x4f, 0xff,
+ 0x1c, 0x64, 0x50, 0xff, 0x19, 0x55, 0x42, 0xff,
+ 0x19, 0x51, 0x3a, 0xff, 0x23, 0x71, 0x60, 0xff,
+ 0x2a, 0x82, 0x74, 0xff, 0x24, 0x71, 0x60, 0xff,
+ 0x1e, 0x5d, 0x4a, 0xff, 0x1e, 0x5d, 0x4a, 0xff,
+ 0x1c, 0x4d, 0x3a, 0xff, 0x1e, 0x5d, 0x4a, 0xff,
+ 0x2c, 0x63, 0x58, 0xff, 0x31, 0x75, 0x62, 0xff,
+ 0x2c, 0x63, 0x58, 0xff, 0x2f, 0x6c, 0x5d, 0xff,
+ 0x6b, 0x76, 0x73, 0xff, 0x6b, 0x75, 0x73, 0xff,
+ 0x5b, 0x5e, 0x5b, 0xff, 0x5a, 0x5d, 0x5a, 0xff,
+ 0x32, 0x67, 0x52, 0xff, 0x31, 0x5d, 0x4a, 0xff,
+ 0x31, 0x67, 0x52, 0xff, 0x31, 0x79, 0x62, 0xff,
+ 0x3a, 0x73, 0x5d, 0xff, 0x31, 0x63, 0x4f, 0xff,
+ 0x29, 0x55, 0x42, 0xff, 0x29, 0x55, 0x41, 0xff,
+ 0x21, 0x41, 0x32, 0xff, 0x21, 0x40, 0x31, 0xff,
+ 0x21, 0x41, 0x31, 0xff, 0x31, 0x63, 0x52, 0xff,
+ 0x4a, 0x7a, 0x6b, 0xff, 0x4a, 0x79, 0x6b, 0xff,
+ 0x45, 0x6c, 0x63, 0xff, 0x44, 0x6b, 0x62, 0xff,
+ 0x4a, 0x78, 0x79, 0xff, 0x4a, 0x78, 0x78, 0xff,
+ 0x4a, 0x78, 0x79, 0xff, 0x39, 0x5e, 0x55, 0xff,
+ 0x29, 0x45, 0x3a, 0xff, 0x34, 0x57, 0x4c, 0xff,
+ 0x29, 0x45, 0x3a, 0xff, 0x34, 0x57, 0x4c, 0xff,
+ 0x2f, 0x52, 0x47, 0xff, 0x3c, 0x6c, 0x5d, 0xff,
+ 0x2f, 0x52, 0x47, 0xff, 0x2e, 0x52, 0x47, 0xff,
+ 0x3c, 0x74, 0x63, 0xff, 0x36, 0x6a, 0x5a, 0xff,
+ 0x31, 0x61, 0x52, 0xff, 0x41, 0x7d, 0x6a, 0xff,
+ 0x2f, 0x5c, 0x4a, 0xff, 0x39, 0x75, 0x62, 0xff,
+ 0x24, 0x42, 0x31, 0xff, 0x2e, 0x5b, 0x4a, 0xff,
+ 0x21, 0x4a, 0x32, 0xff, 0x21, 0x4a, 0x31, 0xff,
+ 0x21, 0x4a, 0x31, 0xff, 0x20, 0x53, 0x39, 0xff,
+ 0x11, 0x39, 0x29, 0xff, 0x10, 0x38, 0x29, 0xff,
+ 0x1b, 0x61, 0x4a, 0xff, 0x15, 0x4c, 0x39, 0xff,
+ 0x19, 0x55, 0x42, 0xff, 0x1b, 0x63, 0x4f, 0xff,
+ 0x1b, 0x64, 0x50, 0xff, 0x1b, 0x63, 0x4f, 0xff,
+ 0x19, 0x51, 0x3a, 0xff, 0x1e, 0x61, 0x4c, 0xff,
+ 0x19, 0x51, 0x3a, 0xff, 0x23, 0x71, 0x5f, 0xff,
+ 0x21, 0x6d, 0x5b, 0xff, 0x21, 0x6d, 0x5a, 0xff,
+ 0x1e, 0x5d, 0x4a, 0xff, 0x1b, 0x4c, 0x39, 0xff,
+ 0x29, 0x59, 0x52, 0xff, 0x2e, 0x6c, 0x5d, 0xff,
+ 0x31, 0x75, 0x63, 0xff, 0x2e, 0x6b, 0x5d, 0xff,
+ 0x66, 0x6d, 0x6b, 0xff, 0x60, 0x65, 0x62, 0xff,
+ 0x5b, 0x5d, 0x5b, 0xff, 0x5f, 0x65, 0x62, 0xff,
+ 0x2a, 0x55, 0x42, 0xff, 0x29, 0x55, 0x42, 0xff,
+ 0x29, 0x55, 0x42, 0xff, 0x29, 0x55, 0x42, 0xff,
+ 0x2c, 0x45, 0x35, 0xff, 0x2c, 0x45, 0x34, 0xff,
+ 0x2c, 0x45, 0x34, 0xff, 0x26, 0x34, 0x26, 0xff,
+ 0x21, 0x35, 0x21, 0xff, 0x21, 0x35, 0x21, 0xff,
+ 0x32, 0x63, 0x53, 0xff, 0x39, 0x79, 0x6b, 0xff,
+ 0x3d, 0x70, 0x63, 0xff, 0x3c, 0x70, 0x63, 0xff,
+ 0x4a, 0x82, 0x74, 0xff, 0x3c, 0x70, 0x63, 0xff,
+ 0x42, 0x72, 0x63, 0xff, 0x42, 0x71, 0x63, 0xff,
+ 0x32, 0x54, 0x4d, 0xff, 0x39, 0x62, 0x58, 0xff,
+ 0x21, 0x41, 0x32, 0xff, 0x29, 0x56, 0x47, 0xff,
+ 0x32, 0x6c, 0x5e, 0xff, 0x31, 0x6c, 0x5d, 0xff,
+ 0x4d, 0x76, 0x69, 0xff, 0x4d, 0x75, 0x68, 0xff,
+ 0x37, 0x59, 0x4d, 0xff, 0x4d, 0x75, 0x68, 0xff,
+ 0x7c, 0x8e, 0x7c, 0xff, 0x60, 0x6f, 0x60, 0xff,
+ 0x45, 0x50, 0x45, 0xff, 0x60, 0x6e, 0x60, 0xff,
+ 0x24, 0x50, 0x3d, 0xff, 0x3a, 0x7d, 0x63, 0xff,
+ 0x2f, 0x67, 0x50, 0xff, 0x19, 0x39, 0x29, 0xff,
+ 0x1c, 0x36, 0x2c, 0xff, 0x26, 0x47, 0x37, 0xff,
+ 0x27, 0x48, 0x37, 0xff, 0x26, 0x47, 0x37, 0xff,
+ 0x19, 0x29, 0x21, 0xff, 0x1b, 0x37, 0x2c, 0xff,
+ 0x21, 0x55, 0x42, 0xff, 0x1e, 0x46, 0x37, 0xff,
+ 0x19, 0x3d, 0x2a, 0xff, 0x1e, 0x5d, 0x45, 0xff,
+ 0x1f, 0x5d, 0x45, 0xff, 0x21, 0x6d, 0x52, 0xff,
+ 0x2f, 0x67, 0x58, 0xff, 0x2f, 0x67, 0x58, 0xff,
+ 0x24, 0x54, 0x45, 0xff, 0x23, 0x53, 0x44, 0xff,
+ 0x19, 0x5e, 0x4b, 0xff, 0x1b, 0x67, 0x52, 0xff,
+ 0x1c, 0x67, 0x53, 0xff, 0x1b, 0x66, 0x52, 0xff,
+ 0x21, 0x55, 0x42, 0xff, 0x24, 0x61, 0x4d, 0xff,
+ 0x29, 0x7a, 0x63, 0xff, 0x26, 0x6d, 0x58, 0xff,
+ 0x2a, 0x76, 0x63, 0xff, 0x37, 0x6c, 0x5d, 0xff,
+ 0x53, 0x59, 0x53, 0xff, 0x52, 0x59, 0x52, 0xff,
+ 0x29, 0x55, 0x42, 0xff, 0x29, 0x55, 0x41, 0xff,
+ 0x27, 0x45, 0x34, 0xff, 0x26, 0x45, 0x34, 0xff,
+ 0x2c, 0x45, 0x34, 0xff, 0x2b, 0x44, 0x34, 0xff,
+ 0x21, 0x25, 0x19, 0xff, 0x26, 0x34, 0x26, 0xff,
+ 0x29, 0x4c, 0x3a, 0xff, 0x31, 0x62, 0x52, 0xff,
+ 0x3a, 0x7a, 0x6b, 0xff, 0x31, 0x62, 0x52, 0xff,
+ 0x3c, 0x70, 0x63, 0xff, 0x4a, 0x81, 0x73, 0xff,
+ 0x4a, 0x82, 0x73, 0xff, 0x3c, 0x70, 0x62, 0xff,
+ 0x31, 0x54, 0x4d, 0xff, 0x39, 0x62, 0x57, 0xff,
+ 0x3a, 0x63, 0x58, 0xff, 0x31, 0x53, 0x4c, 0xff,
+ 0x21, 0x41, 0x31, 0xff, 0x20, 0x40, 0x31, 0xff,
+ 0x32, 0x6c, 0x5d, 0xff, 0x39, 0x81, 0x73, 0xff,
+ 0x63, 0x92, 0x84, 0xff, 0x4c, 0x75, 0x68, 0xff,
+ 0x37, 0x59, 0x4d, 0xff, 0x62, 0x91, 0x83, 0xff,
+ 0x7b, 0x8e, 0x7b, 0xff, 0x44, 0x4f, 0x44, 0xff,
+ 0x45, 0x50, 0x45, 0xff, 0x44, 0x4f, 0x44, 0xff,
+ 0x24, 0x50, 0x3c, 0xff, 0x39, 0x7d, 0x62, 0xff,
+ 0x2f, 0x67, 0x50, 0xff, 0x18, 0x38, 0x29, 0xff,
+ 0x31, 0x59, 0x42, 0xff, 0x31, 0x59, 0x41, 0xff,
+ 0x1c, 0x36, 0x2c, 0xff, 0x10, 0x24, 0x21, 0xff,
+ 0x19, 0x29, 0x21, 0xff, 0x1e, 0x46, 0x36, 0xff,
+ 0x1e, 0x46, 0x37, 0xff, 0x1b, 0x37, 0x2c, 0xff,
+ 0x19, 0x3d, 0x29, 0xff, 0x18, 0x3c, 0x29, 0xff,
+ 0x1e, 0x5d, 0x45, 0xff, 0x1e, 0x5d, 0x44, 0xff,
+ 0x2f, 0x67, 0x58, 0xff, 0x39, 0x79, 0x6b, 0xff,
+ 0x3a, 0x7a, 0x6b, 0xff, 0x23, 0x53, 0x44, 0xff,
+ 0x19, 0x5d, 0x4a, 0xff, 0x1e, 0x70, 0x5a, 0xff,
+ 0x21, 0x7a, 0x63, 0xff, 0x1e, 0x70, 0x5a, 0xff,
+ 0x24, 0x61, 0x4d, 0xff, 0x26, 0x6d, 0x57, 0xff,
+ 0x29, 0x7a, 0x63, 0xff, 0x26, 0x6d, 0x57, 0xff,
+ 0x29, 0x75, 0x63, 0xff, 0x36, 0x6c, 0x5d, 0xff,
+ 0x52, 0x59, 0x52, 0xff, 0x52, 0x59, 0x52, 0xff,
+ 0x27, 0x45, 0x34, 0xff, 0x23, 0x34, 0x26, 0xff,
+ 0x24, 0x35, 0x27, 0xff, 0x21, 0x24, 0x19, 0xff,
+ 0x21, 0x25, 0x19, 0xff, 0x21, 0x24, 0x18, 0xff,
+ 0x21, 0x25, 0x19, 0xff, 0x21, 0x24, 0x19, 0xff,
+ 0x21, 0x35, 0x21, 0xff, 0x31, 0x62, 0x52, 0xff,
+ 0x32, 0x63, 0x53, 0xff, 0x31, 0x62, 0x52, 0xff,
+ 0x2f, 0x5f, 0x53, 0xff, 0x21, 0x4d, 0x42, 0xff,
+ 0x2f, 0x5f, 0x53, 0xff, 0x2f, 0x5e, 0x52, 0xff,
+ 0x32, 0x54, 0x4d, 0xff, 0x31, 0x53, 0x4d, 0xff,
+ 0x3a, 0x63, 0x58, 0xff, 0x39, 0x62, 0x58, 0xff,
+ 0x32, 0x6c, 0x5e, 0xff, 0x31, 0x6c, 0x5d, 0xff,
+ 0x32, 0x6c, 0x5e, 0xff, 0x31, 0x6c, 0x5d, 0xff,
+ 0x4d, 0x76, 0x68, 0xff, 0x4d, 0x75, 0x68, 0xff,
+ 0x21, 0x3d, 0x32, 0xff, 0x37, 0x59, 0x4d, 0xff,
+ 0x29, 0x31, 0x29, 0xff, 0x29, 0x30, 0x29, 0xff,
+ 0x2a, 0x31, 0x2a, 0xff, 0x44, 0x50, 0x44, 0xff,
+ 0x2f, 0x67, 0x50, 0xff, 0x23, 0x4f, 0x3c, 0xff,
+ 0x24, 0x50, 0x3d, 0xff, 0x24, 0x50, 0x3c, 0xff,
+ 0x27, 0x48, 0x37, 0xff, 0x26, 0x47, 0x37, 0xff,
+ 0x1c, 0x36, 0x2c, 0xff, 0x10, 0x24, 0x21, 0xff,
+ 0x1e, 0x46, 0x37, 0xff, 0x1e, 0x46, 0x37, 0xff,
+ 0x21, 0x55, 0x42, 0xff, 0x21, 0x55, 0x42, 0xff,
+ 0x1c, 0x4d, 0x37, 0xff, 0x18, 0x3c, 0x29, 0xff,
+ 0x1f, 0x5e, 0x45, 0xff, 0x1e, 0x5d, 0x44, 0xff,
+ 0x2f, 0x67, 0x58, 0xff, 0x39, 0x79, 0x6b, 0xff,
+ 0x2f, 0x67, 0x58, 0xff, 0x2f, 0x66, 0x58, 0xff,
+ 0x1c, 0x67, 0x53, 0xff, 0x1e, 0x70, 0x5a, 0xff,
+ 0x1f, 0x70, 0x5b, 0xff, 0x21, 0x79, 0x63, 0xff,
+ 0x27, 0x6e, 0x58, 0xff, 0x26, 0x6d, 0x58, 0xff,
+ 0x2a, 0x7a, 0x63, 0xff, 0x26, 0x6d, 0x58, 0xff,
+ 0x37, 0x6c, 0x5e, 0xff, 0x37, 0x6c, 0x5d, 0xff,
+ 0x37, 0x6c, 0x5e, 0xff, 0x44, 0x62, 0x58, 0xff,
+ 0x27, 0x45, 0x34, 0xff, 0x23, 0x34, 0x26, 0xff,
+ 0x21, 0x24, 0x19, 0xff, 0x20, 0x24, 0x18, 0xff,
+ 0x21, 0x25, 0x19, 0xff, 0x21, 0x24, 0x18, 0xff,
+ 0x21, 0x24, 0x19, 0xff, 0x31, 0x55, 0x41, 0xff,
+ 0x29, 0x4c, 0x3a, 0xff, 0x29, 0x4b, 0x39, 0xff,
+ 0x31, 0x63, 0x52, 0xff, 0x39, 0x79, 0x6a, 0xff,
+ 0x2f, 0x5f, 0x52, 0xff, 0x21, 0x4d, 0x41, 0xff,
+ 0x21, 0x4d, 0x42, 0xff, 0x3c, 0x70, 0x62, 0xff,
+ 0x3a, 0x63, 0x58, 0xff, 0x29, 0x44, 0x41, 0xff,
+ 0x29, 0x45, 0x42, 0xff, 0x39, 0x62, 0x57, 0xff,
+ 0x32, 0x6c, 0x5d, 0xff, 0x29, 0x56, 0x47, 0xff,
+ 0x29, 0x56, 0x47, 0xff, 0x29, 0x56, 0x47, 0xff,
+ 0x37, 0x59, 0x4d, 0xff, 0x36, 0x59, 0x4c, 0xff,
+ 0x37, 0x59, 0x4d, 0xff, 0x4c, 0x75, 0x68, 0xff,
+ 0x45, 0x50, 0x45, 0xff, 0x44, 0x4f, 0x44, 0xff,
+ 0x45, 0x50, 0x45, 0xff, 0x5f, 0x6e, 0x5f, 0xff,
+ 0x24, 0x50, 0x3c, 0xff, 0x18, 0x38, 0x29, 0xff,
+ 0x19, 0x39, 0x29, 0xff, 0x23, 0x4f, 0x3c, 0xff,
+ 0x1c, 0x36, 0x2c, 0xff, 0x26, 0x47, 0x36, 0xff,
+ 0x31, 0x59, 0x42, 0xff, 0x31, 0x59, 0x41, 0xff,
+ 0x1c, 0x37, 0x2c, 0xff, 0x18, 0x28, 0x21, 0xff,
+ 0x1b, 0x37, 0x2c, 0xff, 0x20, 0x55, 0x41, 0xff,
+ 0x1c, 0x4d, 0x37, 0xff, 0x1e, 0x5d, 0x44, 0xff,
+ 0x1b, 0x4d, 0x37, 0xff, 0x18, 0x3c, 0x29, 0xff,
+ 0x19, 0x41, 0x32, 0xff, 0x2e, 0x66, 0x57, 0xff,
+ 0x2f, 0x67, 0x58, 0xff, 0x2e, 0x66, 0x57, 0xff,
+ 0x19, 0x5d, 0x4a, 0xff, 0x18, 0x5d, 0x4a, 0xff,
+ 0x21, 0x79, 0x63, 0xff, 0x1e, 0x70, 0x5a, 0xff,
+ 0x24, 0x61, 0x4d, 0xff, 0x26, 0x6d, 0x57, 0xff,
+ 0x29, 0x79, 0x63, 0xff, 0x26, 0x6d, 0x57, 0xff,
+ 0x37, 0x6c, 0x5d, 0xff, 0x36, 0x6c, 0x5d, 0xff,
+ 0x29, 0x75, 0x63, 0xff, 0x52, 0x59, 0x52, 0xff,
+ 0x1f, 0x45, 0x2f, 0xff, 0x19, 0x31, 0x19, 0xff,
+ 0x19, 0x31, 0x19, 0xff, 0x19, 0x30, 0x19, 0xff,
+ 0x19, 0x31, 0x19, 0xff, 0x19, 0x31, 0x19, 0xff,
+ 0x34, 0x64, 0x4a, 0xff, 0x34, 0x64, 0x4a, 0xff,
+ 0x2a, 0x4f, 0x40, 0xff, 0x3a, 0x68, 0x55, 0xff,
+ 0x3a, 0x68, 0x55, 0xff, 0x39, 0x68, 0x55, 0xff,
+ 0x2c, 0x66, 0x58, 0xff, 0x31, 0x71, 0x63, 0xff,
+ 0x2c, 0x66, 0x58, 0xff, 0x26, 0x59, 0x4d, 0xff,
+ 0x2c, 0x3c, 0x3a, 0xff, 0x2c, 0x3b, 0x3a, 0xff,
+ 0x19, 0x25, 0x21, 0xff, 0x19, 0x24, 0x21, 0xff,
+ 0x24, 0x43, 0x32, 0xff, 0x29, 0x65, 0x52, 0xff,
+ 0x27, 0x54, 0x42, 0xff, 0x29, 0x65, 0x52, 0xff,
+ 0x5e, 0x6b, 0x5b, 0xff, 0x37, 0x47, 0x3a, 0xff,
+ 0x37, 0x48, 0x3a, 0xff, 0x37, 0x47, 0x39, 0xff,
+ 0x42, 0x25, 0x21, 0xff, 0x6b, 0x51, 0x4a, 0xff,
+ 0x6b, 0x51, 0x4a, 0xff, 0x94, 0x7d, 0x73, 0xff,
+ 0x66, 0x51, 0x48, 0xff, 0x65, 0x51, 0x47, 0xff,
+ 0x66, 0x51, 0x48, 0xff, 0x65, 0x51, 0x47, 0xff,
+ 0x3a, 0x2d, 0x21, 0xff, 0x3a, 0x2c, 0x21, 0xff,
+ 0x69, 0x59, 0x4d, 0xff, 0x97, 0x85, 0x78, 0xff,
+ 0x1c, 0x30, 0x27, 0xff, 0x19, 0x1c, 0x19, 0xff,
+ 0x1f, 0x42, 0x34, 0xff, 0x21, 0x55, 0x42, 0xff,
+ 0x16, 0x3f, 0x2c, 0xff, 0x1b, 0x58, 0x47, 0xff,
+ 0x16, 0x3e, 0x2c, 0xff, 0x10, 0x24, 0x10, 0xff,
+ 0x1c, 0x49, 0x3a, 0xff, 0x1e, 0x59, 0x4a, 0xff,
+ 0x21, 0x6a, 0x5b, 0xff, 0x21, 0x69, 0x5a, 0xff,
+ 0x14, 0x55, 0x40, 0xff, 0x13, 0x55, 0x3f, 0xff,
+ 0x14, 0x55, 0x3f, 0xff, 0x16, 0x65, 0x4d, 0xff,
+ 0x1c, 0x54, 0x42, 0xff, 0x1e, 0x67, 0x52, 0xff,
+ 0x21, 0x7a, 0x63, 0xff, 0x1e, 0x66, 0x52, 0xff,
+ 0x24, 0x63, 0x53, 0xff, 0x26, 0x6c, 0x5a, 0xff,
+ 0x27, 0x6c, 0x5b, 0xff, 0x21, 0x59, 0x4a, 0xff,
+ 0x24, 0x59, 0x45, 0xff, 0x23, 0x59, 0x44, 0xff,
+ 0x24, 0x59, 0x45, 0xff, 0x23, 0x59, 0x44, 0xff,
+ 0x26, 0x4a, 0x31, 0xff, 0x26, 0x4a, 0x31, 0xff,
+ 0x34, 0x64, 0x4a, 0xff, 0x34, 0x64, 0x4a, 0xff,
+ 0x3a, 0x68, 0x55, 0xff, 0x4a, 0x81, 0x6b, 0xff,
+ 0x3a, 0x68, 0x55, 0xff, 0x39, 0x68, 0x55, 0xff,
+ 0x2c, 0x65, 0x58, 0xff, 0x2b, 0x65, 0x57, 0xff,
+ 0x2c, 0x65, 0x58, 0xff, 0x21, 0x4d, 0x42, 0xff,
+ 0x2c, 0x3b, 0x3a, 0xff, 0x18, 0x24, 0x20, 0xff,
+ 0x19, 0x25, 0x21, 0xff, 0x18, 0x24, 0x21, 0xff,
+ 0x24, 0x42, 0x31, 0xff, 0x23, 0x42, 0x31, 0xff,
+ 0x27, 0x54, 0x42, 0xff, 0x26, 0x53, 0x42, 0xff,
+ 0x5d, 0x6b, 0x5b, 0xff, 0x36, 0x47, 0x39, 0xff,
+ 0x11, 0x25, 0x19, 0xff, 0x10, 0x24, 0x18, 0xff,
+ 0x6b, 0x51, 0x4a, 0xff, 0xbd, 0xaa, 0x9c, 0xff,
+ 0x94, 0x7e, 0x73, 0xff, 0xbd, 0xaa, 0x9c, 0xff,
+ 0xce, 0xba, 0xb5, 0xff, 0xcd, 0xba, 0xb5, 0xff,
+ 0x9a, 0x86, 0x7e, 0xff, 0x99, 0x85, 0x7e, 0xff,
+ 0x97, 0x86, 0x79, 0xff, 0x39, 0x2c, 0x20, 0xff,
+ 0x3a, 0x2d, 0x21, 0xff, 0x39, 0x2c, 0x21, 0xff,
+ 0x1c, 0x2f, 0x26, 0xff, 0x18, 0x1c, 0x18, 0xff,
+ 0x1e, 0x42, 0x34, 0xff, 0x21, 0x55, 0x42, 0xff,
+ 0x11, 0x25, 0x11, 0xff, 0x16, 0x3e, 0x2b, 0xff,
+ 0x16, 0x3e, 0x2c, 0xff, 0x16, 0x3e, 0x2c, 0xff,
+ 0x1c, 0x49, 0x3a, 0xff, 0x20, 0x69, 0x5a, 0xff,
+ 0x21, 0x69, 0x5b, 0xff, 0x21, 0x69, 0x5a, 0xff,
+ 0x16, 0x65, 0x4d, 0xff, 0x13, 0x55, 0x3f, 0xff,
+ 0x13, 0x55, 0x3f, 0xff, 0x10, 0x45, 0x31, 0xff,
+ 0x19, 0x41, 0x31, 0xff, 0x1e, 0x66, 0x52, 0xff,
+ 0x1e, 0x67, 0x52, 0xff, 0x1e, 0x66, 0x52, 0xff,
+ 0x24, 0x63, 0x52, 0xff, 0x29, 0x75, 0x62, 0xff,
+ 0x29, 0x76, 0x63, 0xff, 0x29, 0x75, 0x62, 0xff,
+ 0x24, 0x59, 0x45, 0xff, 0x29, 0x6d, 0x5a, 0xff,
+ 0x2a, 0x6e, 0x5b, 0xff, 0x29, 0x6d, 0x5a, 0xff,
+ 0x34, 0x64, 0x4a, 0xff, 0x34, 0x64, 0x4a, 0xff,
+ 0x42, 0x7e, 0x63, 0xff, 0x42, 0x7d, 0x63, 0xff,
+ 0x4a, 0x82, 0x6b, 0xff, 0x4a, 0x81, 0x6b, 0xff,
+ 0x2a, 0x4f, 0x3f, 0xff, 0x29, 0x4e, 0x3f, 0xff,
+ 0x2c, 0x65, 0x58, 0xff, 0x26, 0x59, 0x4d, 0xff,
+ 0x21, 0x4d, 0x42, 0xff, 0x26, 0x59, 0x4d, 0xff,
+ 0x3f, 0x53, 0x53, 0xff, 0x2c, 0x3b, 0x39, 0xff,
+ 0x2c, 0x3c, 0x3a, 0xff, 0x2c, 0x3b, 0x39, 0xff,
+ 0x24, 0x42, 0x32, 0xff, 0x21, 0x30, 0x21, 0xff,
+ 0x21, 0x31, 0x21, 0xff, 0x21, 0x30, 0x21, 0xff,
+ 0x11, 0x25, 0x19, 0xff, 0x10, 0x24, 0x18, 0xff,
+ 0x11, 0x25, 0x19, 0xff, 0x84, 0x8e, 0x7b, 0xff,
+ 0x94, 0x7e, 0x73, 0xff, 0x6b, 0x51, 0x4a, 0xff,
+ 0x42, 0x25, 0x21, 0xff, 0x6b, 0x51, 0x4a, 0xff,
+ 0x9a, 0x86, 0x7e, 0xff, 0x65, 0x51, 0x47, 0xff,
+ 0x66, 0x51, 0x48, 0xff, 0xce, 0xba, 0xb5, 0xff,
+ 0xc6, 0xb2, 0xa5, 0xff, 0x68, 0x59, 0x4d, 0xff,
+ 0x3a, 0x2d, 0x21, 0xff, 0x39, 0x2c, 0x21, 0xff,
+ 0x19, 0x1d, 0x19, 0xff, 0x18, 0x1c, 0x18, 0xff,
+ 0x1f, 0x43, 0x35, 0xff, 0x1e, 0x42, 0x34, 0xff,
+ 0x16, 0x3e, 0x2c, 0xff, 0x16, 0x3e, 0x2c, 0xff,
+ 0x1c, 0x58, 0x48, 0xff, 0x21, 0x71, 0x63, 0xff,
+ 0x1c, 0x49, 0x3a, 0xff, 0x18, 0x38, 0x29, 0xff,
+ 0x1c, 0x49, 0x3a, 0xff, 0x1e, 0x59, 0x4a, 0xff,
+ 0x13, 0x55, 0x3f, 0xff, 0x18, 0x75, 0x5a, 0xff,
+ 0x16, 0x66, 0x4d, 0xff, 0x13, 0x55, 0x3f, 0xff,
+ 0x1c, 0x54, 0x42, 0xff, 0x1e, 0x66, 0x52, 0xff,
+ 0x1f, 0x67, 0x53, 0xff, 0x1e, 0x66, 0x52, 0xff,
+ 0x27, 0x6c, 0x5b, 0xff, 0x23, 0x62, 0x52, 0xff,
+ 0x24, 0x63, 0x53, 0xff, 0x29, 0x75, 0x63, 0xff,
+ 0x24, 0x59, 0x45, 0xff, 0x23, 0x59, 0x44, 0xff,
+ 0x24, 0x59, 0x45, 0xff, 0x29, 0x6d, 0x5a, 0xff,
+ 0x34, 0x64, 0x4a, 0xff, 0x34, 0x63, 0x4a, 0xff,
+ 0x42, 0x7e, 0x63, 0xff, 0x41, 0x7d, 0x62, 0xff,
+ 0x4a, 0x82, 0x6b, 0xff, 0x4a, 0x81, 0x6b, 0xff,
+ 0x29, 0x4e, 0x3f, 0xff, 0x18, 0x34, 0x29, 0xff,
+ 0x27, 0x59, 0x4d, 0xff, 0x31, 0x71, 0x62, 0xff,
+ 0x26, 0x59, 0x4d, 0xff, 0x2b, 0x65, 0x57, 0xff,
+ 0x52, 0x69, 0x6b, 0xff, 0x52, 0x69, 0x6b, 0xff,
+ 0x52, 0x69, 0x6b, 0xff, 0x3f, 0x52, 0x52, 0xff,
+ 0x27, 0x54, 0x42, 0xff, 0x23, 0x42, 0x31, 0xff,
+ 0x24, 0x42, 0x31, 0xff, 0x20, 0x30, 0x20, 0xff,
+ 0x11, 0x25, 0x19, 0xff, 0x10, 0x24, 0x18, 0xff,
+ 0x84, 0x8e, 0x7b, 0xff, 0x83, 0x8d, 0x7b, 0xff,
+ 0x42, 0x25, 0x21, 0xff, 0x41, 0x24, 0x21, 0xff,
+ 0x42, 0x24, 0x21, 0xff, 0x6a, 0x50, 0x4a, 0xff,
+ 0x32, 0x1c, 0x11, 0xff, 0x65, 0x51, 0x47, 0xff,
+ 0x31, 0x1c, 0x10, 0xff, 0x65, 0x50, 0x47, 0xff,
+ 0xc6, 0xb2, 0xa5, 0xff, 0xc5, 0xb2, 0xa4, 0xff,
+ 0x68, 0x59, 0x4d, 0xff, 0x39, 0x2c, 0x20, 0xff,
+ 0x1c, 0x2f, 0x27, 0xff, 0x18, 0x1c, 0x18, 0xff,
+ 0x1b, 0x2f, 0x26, 0xff, 0x18, 0x1c, 0x18, 0xff,
+ 0x16, 0x3e, 0x2c, 0xff, 0x1b, 0x57, 0x47, 0xff,
+ 0x21, 0x71, 0x63, 0xff, 0x20, 0x71, 0x62, 0xff,
+ 0x1c, 0x49, 0x3a, 0xff, 0x18, 0x38, 0x29, 0xff,
+ 0x19, 0x39, 0x29, 0xff, 0x18, 0x38, 0x29, 0xff,
+ 0x11, 0x45, 0x32, 0xff, 0x16, 0x65, 0x4c, 0xff,
+ 0x16, 0x65, 0x4d, 0xff, 0x10, 0x44, 0x31, 0xff,
+ 0x19, 0x41, 0x32, 0xff, 0x1b, 0x53, 0x41, 0xff,
+ 0x1e, 0x67, 0x52, 0xff, 0x1b, 0x53, 0x41, 0xff,
+ 0x24, 0x63, 0x52, 0xff, 0x21, 0x59, 0x4a, 0xff,
+ 0x21, 0x59, 0x4a, 0xff, 0x26, 0x6b, 0x5a, 0xff,
+ 0x2c, 0x5e, 0x4d, 0xff, 0x31, 0x69, 0x5a, 0xff,
+ 0x2c, 0x5d, 0x4d, 0xff, 0x31, 0x69, 0x5a, 0xff,
+ 0x2f, 0x5b, 0x48, 0xff, 0x3c, 0x6c, 0x55, 0xff,
+ 0x3d, 0x6c, 0x55, 0xff, 0x2e, 0x5a, 0x47, 0xff,
+ 0x4b, 0x82, 0x6b, 0xff, 0x3f, 0x68, 0x55, 0xff,
+ 0x34, 0x4f, 0x3f, 0xff, 0x29, 0x34, 0x29, 0xff,
+ 0x32, 0x3d, 0x32, 0xff, 0x37, 0x4d, 0x3f, 0xff,
+ 0x3d, 0x5d, 0x4d, 0xff, 0x42, 0x6d, 0x5a, 0xff,
+ 0x45, 0x66, 0x58, 0xff, 0x45, 0x65, 0x58, 0xff,
+ 0x45, 0x66, 0x58, 0xff, 0x44, 0x65, 0x58, 0xff,
+ 0x53, 0x45, 0x40, 0xff, 0x84, 0x75, 0x6e, 0xff,
+ 0x84, 0x76, 0x6e, 0xff, 0x52, 0x45, 0x3f, 0xff,
+ 0x21, 0x0d, 0x09, 0xff, 0x55, 0x3b, 0x34, 0xff,
+ 0xbe, 0x9a, 0x8c, 0xff, 0x55, 0x3b, 0x34, 0xff,
+ 0x19, 0x11, 0x09, 0xff, 0x3c, 0x2f, 0x26, 0xff,
+ 0x19, 0x11, 0x09, 0xff, 0x3c, 0x2f, 0x26, 0xff,
+ 0x3a, 0x26, 0x1c, 0xff, 0x3a, 0x26, 0x1b, 0xff,
+ 0x3a, 0x26, 0x1c, 0xff, 0x39, 0x26, 0x1b, 0xff,
+ 0x6b, 0x5e, 0x53, 0xff, 0xde, 0xbe, 0xb5, 0xff,
+ 0x6b, 0x5d, 0x53, 0xff, 0x31, 0x2c, 0x21, 0xff,
+ 0x1c, 0x40, 0x2f, 0xff, 0x19, 0x31, 0x21, 0xff,
+ 0x1c, 0x40, 0x2f, 0xff, 0x1b, 0x3f, 0x2e, 0xff,
+ 0x16, 0x45, 0x35, 0xff, 0x16, 0x45, 0x34, 0xff,
+ 0x1c, 0x59, 0x48, 0xff, 0x21, 0x6d, 0x5a, 0xff,
+ 0x1f, 0x53, 0x40, 0xff, 0x1e, 0x52, 0x3f, 0xff,
+ 0x1c, 0x3c, 0x2c, 0xff, 0x19, 0x24, 0x19, 0xff,
+ 0x16, 0x36, 0x27, 0xff, 0x10, 0x59, 0x42, 0xff,
+ 0x11, 0x59, 0x42, 0xff, 0x13, 0x47, 0x34, 0xff,
+ 0x11, 0x2d, 0x21, 0xff, 0x21, 0x50, 0x3c, 0xff,
+ 0x29, 0x61, 0x4a, 0xff, 0x21, 0x4f, 0x3c, 0xff,
+ 0x1f, 0x54, 0x3d, 0xff, 0x19, 0x49, 0x31, 0xff,
+ 0x1f, 0x54, 0x3d, 0xff, 0x23, 0x5e, 0x47, 0xff,
+ 0x2c, 0x5d, 0x4d, 0xff, 0x26, 0x51, 0x3f, 0xff,
+ 0x21, 0x45, 0x32, 0xff, 0x26, 0x51, 0x3f, 0xff,
+ 0x21, 0x49, 0x3a, 0xff, 0x3c, 0x6c, 0x55, 0xff,
+ 0x4a, 0x7e, 0x63, 0xff, 0x3c, 0x6c, 0x55, 0xff,
+ 0x4a, 0x82, 0x6b, 0xff, 0x34, 0x4e, 0x3f, 0xff,
+ 0x34, 0x4e, 0x3f, 0xff, 0x34, 0x4e, 0x3f, 0xff,
+ 0x37, 0x4d, 0x3f, 0xff, 0x36, 0x4c, 0x3f, 0xff,
+ 0x37, 0x4d, 0x3f, 0xff, 0x42, 0x6d, 0x5a, 0xff,
+ 0x52, 0x7a, 0x6b, 0xff, 0x44, 0x65, 0x57, 0xff,
+ 0x52, 0x7a, 0x6b, 0xff, 0x44, 0x65, 0x57, 0xff,
+ 0x52, 0x45, 0x3f, 0xff, 0x83, 0x75, 0x6d, 0xff,
+ 0xb5, 0xa6, 0x9d, 0xff, 0x52, 0x45, 0x3f, 0xff,
+ 0x21, 0x0c, 0x08, 0xff, 0x89, 0x6a, 0x60, 0xff,
+ 0xbd, 0x9a, 0x8c, 0xff, 0x21, 0x0c, 0x08, 0xff,
+ 0x19, 0x10, 0x08, 0xff, 0x3c, 0x2f, 0x26, 0xff,
+ 0x19, 0x10, 0x08, 0xff, 0x18, 0x10, 0x08, 0xff,
+ 0x21, 0x10, 0x08, 0xff, 0x39, 0x25, 0x1b, 0xff,
+ 0x3a, 0x26, 0x1c, 0xff, 0x21, 0x10, 0x08, 0xff,
+ 0x31, 0x2d, 0x21, 0xff, 0xde, 0xbe, 0xb5, 0xff,
+ 0x6b, 0x5d, 0x52, 0xff, 0x31, 0x2c, 0x21, 0xff,
+ 0x19, 0x31, 0x21, 0xff, 0x1e, 0x4e, 0x3c, 0xff,
+ 0x21, 0x5d, 0x4a, 0xff, 0x1e, 0x4e, 0x3c, 0xff,
+ 0x1c, 0x59, 0x47, 0xff, 0x16, 0x44, 0x34, 0xff,
+ 0x16, 0x45, 0x34, 0xff, 0x1b, 0x59, 0x47, 0xff,
+ 0x21, 0x69, 0x52, 0xff, 0x1e, 0x52, 0x3f, 0xff,
+ 0x1e, 0x53, 0x3f, 0xff, 0x1b, 0x3b, 0x2c, 0xff,
+ 0x16, 0x36, 0x26, 0xff, 0x16, 0x36, 0x26, 0xff,
+ 0x13, 0x48, 0x34, 0xff, 0x13, 0x47, 0x34, 0xff,
+ 0x11, 0x2d, 0x21, 0xff, 0x10, 0x2c, 0x20, 0xff,
+ 0x21, 0x50, 0x3d, 0xff, 0x29, 0x61, 0x4a, 0xff,
+ 0x29, 0x69, 0x52, 0xff, 0x29, 0x69, 0x52, 0xff,
+ 0x24, 0x5f, 0x48, 0xff, 0x23, 0x5e, 0x47, 0xff,
+ 0x2c, 0x5d, 0x4d, 0xff, 0x2c, 0x5d, 0x4d, 0xff,
+ 0x2c, 0x5e, 0x4d, 0xff, 0x26, 0x51, 0x3f, 0xff,
+ 0x2f, 0x5b, 0x48, 0xff, 0x4a, 0x7d, 0x62, 0xff,
+ 0x4a, 0x7e, 0x63, 0xff, 0x3c, 0x6c, 0x55, 0xff,
+ 0x34, 0x4f, 0x3f, 0xff, 0x34, 0x4e, 0x3f, 0xff,
+ 0x3f, 0x68, 0x55, 0xff, 0x4a, 0x81, 0x6b, 0xff,
+ 0x42, 0x6e, 0x5b, 0xff, 0x3c, 0x5d, 0x4d, 0xff,
+ 0x42, 0x6e, 0x5b, 0xff, 0x37, 0x4d, 0x3f, 0xff,
+ 0x37, 0x51, 0x45, 0xff, 0x44, 0x65, 0x58, 0xff,
+ 0x53, 0x7a, 0x6b, 0xff, 0x44, 0x65, 0x58, 0xff,
+ 0x53, 0x45, 0x3f, 0xff, 0x52, 0x45, 0x3f, 0xff,
+ 0x53, 0x45, 0x3f, 0xff, 0x52, 0x45, 0x3f, 0xff,
+ 0x21, 0x0c, 0x09, 0xff, 0xbd, 0x9a, 0x8c, 0xff,
+ 0x8a, 0x6b, 0x60, 0xff, 0x55, 0x3b, 0x34, 0xff,
+ 0x84, 0x6e, 0x63, 0xff, 0x3c, 0x2f, 0x26, 0xff,
+ 0x3d, 0x30, 0x27, 0xff, 0x19, 0x10, 0x08, 0xff,
+ 0x3a, 0x26, 0x1c, 0xff, 0x39, 0x26, 0x1b, 0xff,
+ 0x3a, 0x26, 0x1c, 0xff, 0x6b, 0x51, 0x42, 0xff,
+ 0x6b, 0x5d, 0x53, 0xff, 0xa4, 0x8d, 0x83, 0xff,
+ 0xa5, 0x8e, 0x84, 0xff, 0x31, 0x2c, 0x21, 0xff,
+ 0x1c, 0x40, 0x2f, 0xff, 0x1e, 0x4e, 0x3c, 0xff,
+ 0x21, 0x5e, 0x4a, 0xff, 0x21, 0x5d, 0x4a, 0xff,
+ 0x1c, 0x59, 0x48, 0xff, 0x1b, 0x59, 0x47, 0xff,
+ 0x1c, 0x59, 0x48, 0xff, 0x16, 0x45, 0x34, 0xff,
+ 0x1e, 0x53, 0x3f, 0xff, 0x1e, 0x52, 0x3f, 0xff,
+ 0x1f, 0x53, 0x3f, 0xff, 0x1b, 0x3b, 0x2c, 0xff,
+ 0x19, 0x25, 0x19, 0xff, 0x18, 0x24, 0x18, 0xff,
+ 0x19, 0x25, 0x19, 0xff, 0x16, 0x36, 0x26, 0xff,
+ 0x19, 0x3e, 0x2f, 0xff, 0x18, 0x3e, 0x2e, 0xff,
+ 0x2a, 0x62, 0x4a, 0xff, 0x21, 0x50, 0x3c, 0xff,
+ 0x1e, 0x54, 0x3d, 0xff, 0x29, 0x69, 0x52, 0xff,
+ 0x24, 0x5f, 0x48, 0xff, 0x24, 0x5e, 0x47, 0xff,
+ 0x2c, 0x5d, 0x4d, 0xff, 0x26, 0x51, 0x3f, 0xff,
+ 0x2c, 0x5d, 0x4d, 0xff, 0x2b, 0x5d, 0x4c, 0xff,
+ 0x3c, 0x6c, 0x55, 0xff, 0x4a, 0x7d, 0x62, 0xff,
+ 0x2f, 0x5a, 0x47, 0xff, 0x2e, 0x5a, 0x47, 0xff,
+ 0x3f, 0x68, 0x55, 0xff, 0x3f, 0x68, 0x55, 0xff,
+ 0x3f, 0x68, 0x55, 0xff, 0x3f, 0x67, 0x55, 0xff,
+ 0x42, 0x6d, 0x5b, 0xff, 0x3c, 0x5d, 0x4c, 0xff,
+ 0x37, 0x4d, 0x3f, 0xff, 0x31, 0x3c, 0x31, 0xff,
+ 0x29, 0x3d, 0x32, 0xff, 0x36, 0x51, 0x44, 0xff,
+ 0x37, 0x51, 0x45, 0xff, 0x29, 0x3c, 0x31, 0xff,
+ 0x52, 0x45, 0x3f, 0xff, 0x52, 0x44, 0x3f, 0xff,
+ 0x21, 0x14, 0x10, 0xff, 0x20, 0x14, 0x10, 0xff,
+ 0x55, 0x3c, 0x34, 0xff, 0x89, 0x6a, 0x60, 0xff,
+ 0x55, 0x3b, 0x34, 0xff, 0x55, 0x3b, 0x34, 0xff,
+ 0x84, 0x6d, 0x63, 0xff, 0x3c, 0x2f, 0x26, 0xff,
+ 0x19, 0x10, 0x08, 0xff, 0x18, 0x10, 0x08, 0xff,
+ 0x21, 0x10, 0x08, 0xff, 0x21, 0x10, 0x08, 0xff,
+ 0x3a, 0x26, 0x1b, 0xff, 0x6a, 0x50, 0x41, 0xff,
+ 0x6b, 0x5d, 0x52, 0xff, 0x6b, 0x5d, 0x52, 0xff,
+ 0xa5, 0x8e, 0x84, 0xff, 0x6a, 0x5d, 0x52, 0xff,
+ 0x1c, 0x40, 0x2f, 0xff, 0x1e, 0x4e, 0x3c, 0xff,
+ 0x1e, 0x4e, 0x3c, 0xff, 0x1b, 0x3f, 0x2e, 0xff,
+ 0x1c, 0x59, 0x47, 0xff, 0x16, 0x44, 0x34, 0xff,
+ 0x10, 0x31, 0x21, 0xff, 0x10, 0x30, 0x20, 0xff,
+ 0x19, 0x25, 0x19, 0xff, 0x1b, 0x3b, 0x2c, 0xff,
+ 0x1b, 0x3b, 0x2c, 0xff, 0x1e, 0x52, 0x3f, 0xff,
+ 0x16, 0x36, 0x27, 0xff, 0x16, 0x36, 0x26, 0xff,
+ 0x19, 0x24, 0x19, 0xff, 0x15, 0x35, 0x26, 0xff,
+ 0x21, 0x50, 0x3c, 0xff, 0x29, 0x61, 0x4a, 0xff,
+ 0x21, 0x50, 0x3c, 0xff, 0x29, 0x61, 0x4a, 0xff,
+ 0x1e, 0x54, 0x3c, 0xff, 0x23, 0x5e, 0x47, 0xff,
+ 0x24, 0x5e, 0x47, 0xff, 0x1e, 0x53, 0x3c, 0xff,
+ 0x21, 0x49, 0x3d, 0xff, 0x21, 0x49, 0x3c, 0xff,
+ 0x19, 0x35, 0x27, 0xff, 0x19, 0x34, 0x26, 0xff,
+ 0x2a, 0x62, 0x4b, 0xff, 0x29, 0x61, 0x4a, 0xff,
+ 0x21, 0x53, 0x3f, 0xff, 0x29, 0x61, 0x4a, 0xff,
+ 0x21, 0x5e, 0x4b, 0xff, 0x21, 0x5d, 0x4a, 0xff,
+ 0x19, 0x49, 0x3a, 0xff, 0x19, 0x49, 0x39, 0xff,
+ 0x21, 0x43, 0x3a, 0xff, 0x19, 0x27, 0x21, 0xff,
+ 0x19, 0x27, 0x21, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x19, 0x19, 0x19, 0xff, 0x19, 0x18, 0x19, 0xff,
+ 0x14, 0x13, 0x14, 0xff, 0x0e, 0x0d, 0x0e, 0xff,
+ 0x14, 0x13, 0x14, 0xff, 0x19, 0x18, 0x19, 0xff,
+ 0x19, 0x19, 0x19, 0xff, 0x0e, 0x0d, 0x0e, 0xff,
+ 0x11, 0x0d, 0x09, 0xff, 0x8c, 0x75, 0x6b, 0xff,
+ 0x63, 0x53, 0x4a, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x11, 0x0d, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x0b, 0x08, 0x0b, 0xff, 0x0b, 0x08, 0x0b, 0xff,
+ 0x0b, 0x09, 0x06, 0xff, 0x0b, 0x08, 0x05, 0xff,
+ 0x0b, 0x08, 0x06, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x00, 0x00, 0x00, 0xff, 0x3c, 0x35, 0x31, 0xff,
+ 0xb5, 0x9e, 0x94, 0xff, 0x3c, 0x34, 0x31, 0xff,
+ 0x11, 0x30, 0x27, 0xff, 0x10, 0x55, 0x42, 0xff,
+ 0x11, 0x55, 0x42, 0xff, 0x10, 0x42, 0x34, 0xff,
+ 0x14, 0x38, 0x2f, 0xff, 0x16, 0x56, 0x45, 0xff,
+ 0x14, 0x38, 0x2f, 0xff, 0x10, 0x18, 0x19, 0xff,
+ 0x11, 0x19, 0x11, 0xff, 0x13, 0x2e, 0x21, 0xff,
+ 0x16, 0x44, 0x32, 0xff, 0x16, 0x43, 0x31, 0xff,
+ 0x0e, 0x3a, 0x2c, 0xff, 0x13, 0x50, 0x3f, 0xff,
+ 0x14, 0x50, 0x3f, 0xff, 0x0e, 0x3a, 0x2c, 0xff,
+ 0x11, 0x45, 0x3a, 0xff, 0x1b, 0x5d, 0x4a, 0xff,
+ 0x1c, 0x5d, 0x4a, 0xff, 0x21, 0x69, 0x52, 0xff,
+ 0x1f, 0x5e, 0x4b, 0xff, 0x1e, 0x5d, 0x4a, 0xff,
+ 0x1f, 0x5d, 0x4a, 0xff, 0x1e, 0x5d, 0x4a, 0xff,
+ 0x21, 0x49, 0x3c, 0xff, 0x10, 0x20, 0x10, 0xff,
+ 0x11, 0x21, 0x11, 0xff, 0x18, 0x34, 0x26, 0xff,
+ 0x21, 0x52, 0x3f, 0xff, 0x20, 0x52, 0x3f, 0xff,
+ 0x21, 0x53, 0x3f, 0xff, 0x21, 0x52, 0x3f, 0xff,
+ 0x11, 0x35, 0x29, 0xff, 0x10, 0x34, 0x29, 0xff,
+ 0x21, 0x5d, 0x4a, 0xff, 0x18, 0x49, 0x39, 0xff,
+ 0x21, 0x42, 0x3a, 0xff, 0x20, 0x42, 0x39, 0xff,
+ 0x19, 0x27, 0x21, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x11, 0x0c, 0x08, 0xff, 0x8b, 0x75, 0x6b, 0xff,
+ 0x8c, 0x76, 0x6b, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x06, 0x04, 0x06, 0xff, 0x05, 0x04, 0x05, 0xff,
+ 0x00, 0x00, 0x00, 0xff, 0x05, 0x04, 0x05, 0xff,
+ 0x06, 0x04, 0x03, 0xff, 0x05, 0x04, 0x02, 0xff,
+ 0x06, 0x04, 0x03, 0xff, 0x05, 0x04, 0x02, 0xff,
+ 0x00, 0x00, 0x00, 0xff, 0x78, 0x69, 0x62, 0xff,
+ 0xb5, 0x9e, 0x94, 0xff, 0x3c, 0x34, 0x31, 0xff,
+ 0x11, 0x42, 0x34, 0xff, 0x10, 0x55, 0x41, 0xff,
+ 0x11, 0x55, 0x42, 0xff, 0x10, 0x55, 0x42, 0xff,
+ 0x16, 0x56, 0x45, 0xff, 0x16, 0x56, 0x44, 0xff,
+ 0x16, 0x57, 0x45, 0xff, 0x13, 0x37, 0x2e, 0xff,
+ 0x16, 0x44, 0x31, 0xff, 0x18, 0x59, 0x41, 0xff,
+ 0x19, 0x59, 0x42, 0xff, 0x18, 0x59, 0x42, 0xff,
+ 0x13, 0x50, 0x3f, 0xff, 0x18, 0x65, 0x52, 0xff,
+ 0x19, 0x65, 0x52, 0xff, 0x18, 0x65, 0x52, 0xff,
+ 0x16, 0x51, 0x42, 0xff, 0x10, 0x44, 0x39, 0xff,
+ 0x16, 0x51, 0x42, 0xff, 0x21, 0x69, 0x52, 0xff,
+ 0x24, 0x65, 0x52, 0xff, 0x1e, 0x5d, 0x4a, 0xff,
+ 0x24, 0x65, 0x52, 0xff, 0x29, 0x6d, 0x5a, 0xff,
+ 0x21, 0x49, 0x3d, 0xff, 0x21, 0x49, 0x3c, 0xff,
+ 0x19, 0x35, 0x27, 0xff, 0x19, 0x35, 0x26, 0xff,
+ 0x21, 0x53, 0x3f, 0xff, 0x21, 0x52, 0x3f, 0xff,
+ 0x19, 0x44, 0x35, 0xff, 0x10, 0x35, 0x29, 0xff,
+ 0x11, 0x35, 0x29, 0xff, 0x21, 0x5d, 0x4a, 0xff,
+ 0x21, 0x5e, 0x4a, 0xff, 0x19, 0x49, 0x39, 0xff,
+ 0x21, 0x42, 0x3a, 0xff, 0x21, 0x42, 0x39, 0xff,
+ 0x19, 0x28, 0x21, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x13, 0x13, 0x13, 0xff, 0x0d, 0x0d, 0x0d, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x09, 0x09, 0x09, 0xff, 0x0e, 0x0d, 0x0e, 0xff,
+ 0x11, 0x0c, 0x09, 0xff, 0x62, 0x52, 0x4a, 0xff,
+ 0x63, 0x53, 0x4a, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x06, 0x04, 0x06, 0xff, 0x05, 0x04, 0x05, 0xff,
+ 0x00, 0x00, 0x00, 0xff, 0x05, 0x04, 0x05, 0xff,
+ 0x00, 0x00, 0x00, 0xff, 0x05, 0x04, 0x03, 0xff,
+ 0x06, 0x04, 0x03, 0xff, 0x05, 0x04, 0x03, 0xff,
+ 0x00, 0x00, 0x00, 0xff, 0x78, 0x69, 0x62, 0xff,
+ 0x79, 0x6a, 0x63, 0xff, 0x3c, 0x35, 0x31, 0xff,
+ 0x11, 0x42, 0x34, 0xff, 0x10, 0x55, 0x42, 0xff,
+ 0x11, 0x55, 0x42, 0xff, 0x10, 0x55, 0x42, 0xff,
+ 0x16, 0x57, 0x45, 0xff, 0x16, 0x56, 0x44, 0xff,
+ 0x19, 0x76, 0x5b, 0xff, 0x16, 0x56, 0x44, 0xff,
+ 0x16, 0x44, 0x32, 0xff, 0x18, 0x59, 0x42, 0xff,
+ 0x16, 0x44, 0x32, 0xff, 0x16, 0x43, 0x31, 0xff,
+ 0x13, 0x50, 0x3f, 0xff, 0x13, 0x4f, 0x3f, 0xff,
+ 0x19, 0x66, 0x53, 0xff, 0x19, 0x65, 0x52, 0xff,
+ 0x21, 0x6a, 0x53, 0xff, 0x10, 0x45, 0x39, 0xff,
+ 0x11, 0x45, 0x3a, 0xff, 0x16, 0x51, 0x42, 0xff,
+ 0x24, 0x65, 0x53, 0xff, 0x23, 0x65, 0x52, 0xff,
+ 0x2a, 0x6e, 0x5b, 0xff, 0x29, 0x6d, 0x5a, 0xff,
+ 0x29, 0x5d, 0x52, 0xff, 0x29, 0x5d, 0x52, 0xff,
+ 0x29, 0x5d, 0x52, 0xff, 0x29, 0x5d, 0x52, 0xff,
+ 0x29, 0x61, 0x4a, 0xff, 0x18, 0x43, 0x34, 0xff,
+ 0x10, 0x35, 0x29, 0xff, 0x20, 0x52, 0x3f, 0xff,
+ 0x29, 0x71, 0x5b, 0xff, 0x29, 0x71, 0x5a, 0xff,
+ 0x21, 0x5d, 0x4a, 0xff, 0x20, 0x5d, 0x4a, 0xff,
+ 0x29, 0x5d, 0x52, 0xff, 0x21, 0x42, 0x39, 0xff,
+ 0x21, 0x42, 0x3a, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x0d, 0x0d, 0x0d, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x11, 0x0c, 0x08, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x3a, 0x2f, 0x29, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x00, 0x00, 0x00, 0xff, 0x05, 0x04, 0x05, 0xff,
+ 0x06, 0x04, 0x06, 0xff, 0x05, 0x04, 0x05, 0xff,
+ 0x0b, 0x08, 0x06, 0xff, 0x05, 0x04, 0x02, 0xff,
+ 0x0b, 0x08, 0x06, 0xff, 0x00, 0x00, 0x00, 0xff,
+ 0x3c, 0x35, 0x32, 0xff, 0xb5, 0x9e, 0x94, 0xff,
+ 0x79, 0x69, 0x63, 0xff, 0x3c, 0x34, 0x31, 0xff,
+ 0x11, 0x1c, 0x19, 0xff, 0x10, 0x2f, 0x26, 0xff,
+ 0x10, 0x2f, 0x26, 0xff, 0x10, 0x42, 0x34, 0xff,
+ 0x13, 0x37, 0x2f, 0xff, 0x16, 0x56, 0x44, 0xff,
+ 0x16, 0x56, 0x45, 0xff, 0x15, 0x56, 0x44, 0xff,
+ 0x16, 0x44, 0x32, 0xff, 0x13, 0x2e, 0x21, 0xff,
+ 0x13, 0x2e, 0x21, 0xff, 0x13, 0x2d, 0x20, 0xff,
+ 0x08, 0x25, 0x19, 0xff, 0x0d, 0x3a, 0x2c, 0xff,
+ 0x13, 0x50, 0x3f, 0xff, 0x18, 0x65, 0x52, 0xff,
+ 0x21, 0x69, 0x52, 0xff, 0x21, 0x69, 0x52, 0xff,
+ 0x16, 0x51, 0x42, 0xff, 0x15, 0x50, 0x41, 0xff,
+ 0x19, 0x55, 0x42, 0xff, 0x18, 0x55, 0x41, 0xff,
+ 0x1e, 0x5d, 0x4a, 0xff, 0x23, 0x65, 0x52, 0xff,
+ 0x2a, 0x60, 0x50, 0xff, 0x21, 0x51, 0x42, 0xff,
+ 0x29, 0x60, 0x50, 0xff, 0x31, 0x6e, 0x5d, 0xff,
+ 0x32, 0x7a, 0x63, 0xff, 0x26, 0x69, 0x52, 0xff,
+ 0x21, 0x61, 0x4a, 0xff, 0x26, 0x69, 0x52, 0xff,
+ 0x27, 0x58, 0x4d, 0xff, 0x2c, 0x67, 0x58, 0xff,
+ 0x21, 0x49, 0x42, 0xff, 0x26, 0x58, 0x4d, 0xff,
+ 0x2c, 0x5b, 0x4d, 0xff, 0x3a, 0x7d, 0x6b, 0xff,
+ 0x2c, 0x5b, 0x4d, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x10, 0x12, 0x10, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x09, 0x09, 0x09, 0xff, 0x0b, 0x0b, 0x0b, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x0e, 0x0d, 0x0e, 0xff,
+ 0x11, 0x0d, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x21, 0x25, 0x21, 0xff, 0x31, 0x3d, 0x31, 0xff,
+ 0x19, 0x09, 0x09, 0xff, 0x19, 0x08, 0x08, 0xff,
+ 0x19, 0x08, 0x09, 0xff, 0x19, 0x08, 0x08, 0xff,
+ 0x11, 0x09, 0x09, 0xff, 0x10, 0x08, 0x08, 0xff,
+ 0x11, 0x08, 0x09, 0xff, 0x10, 0x08, 0x08, 0xff,
+ 0x6b, 0x82, 0x6b, 0xff, 0x47, 0x56, 0x47, 0xff,
+ 0x48, 0x57, 0x48, 0xff, 0x23, 0x2b, 0x23, 0xff,
+ 0x11, 0x29, 0x21, 0xff, 0x10, 0x28, 0x21, 0xff,
+ 0x11, 0x29, 0x21, 0xff, 0x13, 0x3b, 0x2e, 0xff,
+ 0x11, 0x29, 0x21, 0xff, 0x10, 0x28, 0x21, 0xff,
+ 0x16, 0x3e, 0x32, 0xff, 0x1b, 0x53, 0x42, 0xff,
+ 0x24, 0x60, 0x53, 0xff, 0x24, 0x60, 0x52, 0xff,
+ 0x1f, 0x4f, 0x42, 0xff, 0x19, 0x3d, 0x31, 0xff,
+ 0x11, 0x31, 0x2a, 0xff, 0x19, 0x43, 0x3a, 0xff,
+ 0x19, 0x44, 0x3a, 0xff, 0x19, 0x43, 0x39, 0xff,
+ 0x24, 0x5e, 0x4d, 0xff, 0x1e, 0x4d, 0x3f, 0xff,
+ 0x1f, 0x4d, 0x3f, 0xff, 0x19, 0x3d, 0x31, 0xff,
+ 0x1f, 0x48, 0x37, 0xff, 0x19, 0x39, 0x29, 0xff,
+ 0x1f, 0x48, 0x37, 0xff, 0x23, 0x56, 0x44, 0xff,
+ 0x21, 0x51, 0x42, 0xff, 0x20, 0x51, 0x41, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x39, 0x7d, 0x6b, 0xff,
+ 0x31, 0x7a, 0x63, 0xff, 0x31, 0x79, 0x62, 0xff,
+ 0x32, 0x7a, 0x63, 0xff, 0x2c, 0x71, 0x5a, 0xff,
+ 0x26, 0x58, 0x4d, 0xff, 0x2b, 0x66, 0x57, 0xff,
+ 0x21, 0x49, 0x42, 0xff, 0x26, 0x57, 0x4c, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x39, 0x7d, 0x6b, 0xff,
+ 0x2c, 0x5b, 0x4d, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x14, 0x11, 0xff, 0x10, 0x11, 0x10, 0xff,
+ 0x11, 0x0f, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x0b, 0x0b, 0x0b, 0xff, 0x0b, 0x0a, 0x0b, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x21, 0x24, 0x21, 0xff,
+ 0x26, 0x29, 0x24, 0xff, 0x18, 0x08, 0x08, 0xff,
+ 0x19, 0x08, 0x08, 0xff, 0x18, 0x08, 0x08, 0xff,
+ 0x11, 0x08, 0x08, 0xff, 0x10, 0x08, 0x08, 0xff,
+ 0x37, 0x25, 0x1e, 0xff, 0x83, 0x5d, 0x4a, 0xff,
+ 0x47, 0x56, 0x47, 0xff, 0x00, 0x00, 0x00, 0xff,
+ 0x48, 0x57, 0x48, 0xff, 0x23, 0x2b, 0x23, 0xff,
+ 0x13, 0x3b, 0x2f, 0xff, 0x10, 0x28, 0x20, 0xff,
+ 0x11, 0x29, 0x21, 0xff, 0x13, 0x3b, 0x2e, 0xff,
+ 0x1c, 0x54, 0x42, 0xff, 0x16, 0x3e, 0x31, 0xff,
+ 0x16, 0x3e, 0x32, 0xff, 0x21, 0x69, 0x52, 0xff,
+ 0x24, 0x60, 0x52, 0xff, 0x23, 0x5f, 0x52, 0xff,
+ 0x1e, 0x4e, 0x42, 0xff, 0x1e, 0x4e, 0x42, 0xff,
+ 0x21, 0x56, 0x4a, 0xff, 0x20, 0x56, 0x4a, 0xff,
+ 0x21, 0x57, 0x4a, 0xff, 0x18, 0x43, 0x39, 0xff,
+ 0x19, 0x3d, 0x31, 0xff, 0x1e, 0x4c, 0x3f, 0xff,
+ 0x19, 0x3d, 0x32, 0xff, 0x18, 0x3c, 0x31, 0xff,
+ 0x1e, 0x48, 0x37, 0xff, 0x1e, 0x47, 0x36, 0xff,
+ 0x1e, 0x48, 0x37, 0xff, 0x23, 0x56, 0x44, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x39, 0x7d, 0x6b, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x31, 0x6f, 0x5d, 0xff,
+ 0x2c, 0x72, 0x5b, 0xff, 0x26, 0x69, 0x52, 0xff,
+ 0x27, 0x6a, 0x53, 0xff, 0x21, 0x61, 0x4a, 0xff,
+ 0x2c, 0x67, 0x58, 0xff, 0x31, 0x75, 0x62, 0xff,
+ 0x32, 0x76, 0x63, 0xff, 0x31, 0x75, 0x63, 0xff,
+ 0x2c, 0x5b, 0x4d, 0xff, 0x39, 0x7d, 0x6b, 0xff,
+ 0x1f, 0x38, 0x2f, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x0f, 0x11, 0xff, 0x10, 0x11, 0x10, 0xff,
+ 0x11, 0x12, 0x11, 0xff, 0x10, 0x0f, 0x10, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x0b, 0x0b, 0x0b, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x0e, 0x0d, 0x0e, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x11, 0x0d, 0x11, 0xff, 0x31, 0x3d, 0x31, 0xff,
+ 0x42, 0x6a, 0x5b, 0xff, 0x34, 0x49, 0x3f, 0xff,
+ 0x27, 0x29, 0x24, 0xff, 0x26, 0x28, 0x24, 0xff,
+ 0x37, 0x25, 0x1e, 0xff, 0x37, 0x24, 0x1e, 0xff,
+ 0x5e, 0x41, 0x35, 0xff, 0x37, 0x24, 0x1e, 0xff,
+ 0x00, 0x00, 0x00, 0xff, 0x23, 0x2b, 0x23, 0xff,
+ 0x48, 0x57, 0x48, 0xff, 0x24, 0x2b, 0x24, 0xff,
+ 0x13, 0x3c, 0x2f, 0xff, 0x16, 0x4e, 0x3c, 0xff,
+ 0x14, 0x3c, 0x2f, 0xff, 0x16, 0x4e, 0x3c, 0xff,
+ 0x1c, 0x54, 0x42, 0xff, 0x1b, 0x53, 0x42, 0xff,
+ 0x16, 0x3e, 0x32, 0xff, 0x1b, 0x54, 0x42, 0xff,
+ 0x29, 0x72, 0x63, 0xff, 0x29, 0x71, 0x62, 0xff,
+ 0x1f, 0x4f, 0x42, 0xff, 0x19, 0x3d, 0x31, 0xff,
+ 0x21, 0x57, 0x4a, 0xff, 0x29, 0x69, 0x5a, 0xff,
+ 0x21, 0x57, 0x4a, 0xff, 0x21, 0x56, 0x4a, 0xff,
+ 0x1e, 0x4d, 0x3f, 0xff, 0x23, 0x5d, 0x4d, 0xff,
+ 0x2a, 0x6e, 0x5b, 0xff, 0x24, 0x5d, 0x4d, 0xff,
+ 0x29, 0x65, 0x53, 0xff, 0x1e, 0x47, 0x37, 0xff,
+ 0x1f, 0x48, 0x37, 0xff, 0x29, 0x65, 0x52, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x39, 0x7d, 0x6b, 0xff,
+ 0x31, 0x6f, 0x5d, 0xff, 0x31, 0x6e, 0x5d, 0xff,
+ 0x27, 0x69, 0x52, 0xff, 0x21, 0x61, 0x4a, 0xff,
+ 0x26, 0x69, 0x52, 0xff, 0x20, 0x61, 0x4a, 0xff,
+ 0x32, 0x76, 0x63, 0xff, 0x31, 0x75, 0x62, 0xff,
+ 0x2c, 0x67, 0x58, 0xff, 0x31, 0x75, 0x62, 0xff,
+ 0x2c, 0x5b, 0x4d, 0xff, 0x2c, 0x5a, 0x4c, 0xff,
+ 0x1e, 0x37, 0x2f, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x0f, 0x11, 0xff, 0x10, 0x11, 0x10, 0xff,
+ 0x10, 0x0c, 0x10, 0xff, 0x10, 0x0e, 0x10, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x0e, 0x0e, 0x0e, 0xff, 0x0d, 0x0d, 0x0d, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x31, 0x3d, 0x31, 0xff, 0x41, 0x55, 0x41, 0xff,
+ 0x42, 0x69, 0x5b, 0xff, 0x41, 0x69, 0x5a, 0xff,
+ 0x26, 0x29, 0x24, 0xff, 0x18, 0x08, 0x08, 0xff,
+ 0x11, 0x08, 0x08, 0xff, 0x10, 0x08, 0x08, 0xff,
+ 0x10, 0x08, 0x08, 0xff, 0x10, 0x08, 0x08, 0xff,
+ 0x24, 0x2b, 0x24, 0xff, 0x47, 0x56, 0x47, 0xff,
+ 0x47, 0x56, 0x47, 0xff, 0x47, 0x56, 0x47, 0xff,
+ 0x19, 0x61, 0x4a, 0xff, 0x16, 0x4e, 0x3c, 0xff,
+ 0x16, 0x4e, 0x3c, 0xff, 0x10, 0x28, 0x20, 0xff,
+ 0x11, 0x29, 0x21, 0xff, 0x10, 0x28, 0x21, 0xff,
+ 0x16, 0x3e, 0x31, 0xff, 0x15, 0x3e, 0x31, 0xff,
+ 0x24, 0x60, 0x52, 0xff, 0x23, 0x5f, 0x52, 0xff,
+ 0x24, 0x60, 0x52, 0xff, 0x23, 0x5f, 0x52, 0xff,
+ 0x21, 0x57, 0x4a, 0xff, 0x29, 0x69, 0x5a, 0xff,
+ 0x29, 0x69, 0x5b, 0xff, 0x20, 0x56, 0x4a, 0xff,
+ 0x24, 0x5d, 0x4d, 0xff, 0x23, 0x5d, 0x4c, 0xff,
+ 0x29, 0x6d, 0x5b, 0xff, 0x29, 0x6d, 0x5a, 0xff,
+ 0x29, 0x65, 0x52, 0xff, 0x23, 0x56, 0x44, 0xff,
+ 0x1e, 0x48, 0x37, 0xff, 0x1e, 0x47, 0x36, 0xff,
+ 0x2c, 0x72, 0x58, 0xff, 0x2c, 0x71, 0x58, 0xff,
+ 0x32, 0x7e, 0x63, 0xff, 0x2c, 0x71, 0x58, 0xff,
+ 0x21, 0x5a, 0x4b, 0xff, 0x21, 0x59, 0x4a, 0xff,
+ 0x27, 0x63, 0x50, 0xff, 0x26, 0x62, 0x4f, 0xff,
+ 0x32, 0x6e, 0x5b, 0xff, 0x21, 0x5a, 0x4a, 0xff,
+ 0x19, 0x51, 0x42, 0xff, 0x21, 0x5a, 0x4a, 0xff,
+ 0x27, 0x51, 0x42, 0xff, 0x31, 0x71, 0x5a, 0xff,
+ 0x1c, 0x31, 0x29, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x0f, 0x11, 0xff, 0x10, 0x0f, 0x10, 0xff,
+ 0x11, 0x0f, 0x11, 0xff, 0x10, 0x11, 0x10, 0xff,
+ 0x11, 0x0d, 0x11, 0xff, 0x10, 0x0f, 0x10, 0xff,
+ 0x11, 0x0e, 0x11, 0xff, 0x10, 0x0f, 0x10, 0xff,
+ 0x11, 0x0d, 0x09, 0xff, 0x19, 0x2a, 0x21, 0xff,
+ 0x29, 0x66, 0x53, 0xff, 0x29, 0x65, 0x52, 0xff,
+ 0x24, 0x53, 0x40, 0xff, 0x24, 0x52, 0x3f, 0xff,
+ 0x24, 0x53, 0x3f, 0xff, 0x08, 0x24, 0x19, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x42, 0x4f, 0x48, 0xff, 0x42, 0x4e, 0x47, 0xff,
+ 0x2c, 0x54, 0x40, 0xff, 0x37, 0x6b, 0x55, 0xff,
+ 0x42, 0x82, 0x6b, 0xff, 0x42, 0x81, 0x6b, 0xff,
+ 0x2a, 0x76, 0x6b, 0xff, 0x1e, 0x58, 0x4a, 0xff,
+ 0x19, 0x49, 0x3a, 0xff, 0x19, 0x49, 0x39, 0xff,
+ 0x11, 0x39, 0x2a, 0xff, 0x10, 0x39, 0x29, 0xff,
+ 0x16, 0x4b, 0x3a, 0xff, 0x1b, 0x5c, 0x4a, 0xff,
+ 0x19, 0x5c, 0x48, 0xff, 0x10, 0x4d, 0x3a, 0xff,
+ 0x11, 0x4d, 0x3a, 0xff, 0x10, 0x4d, 0x39, 0xff,
+ 0x27, 0x6a, 0x58, 0xff, 0x26, 0x69, 0x58, 0xff,
+ 0x32, 0x82, 0x74, 0xff, 0x2c, 0x75, 0x65, 0xff,
+ 0x1c, 0x5e, 0x4d, 0xff, 0x10, 0x51, 0x42, 0xff,
+ 0x27, 0x6a, 0x58, 0xff, 0x26, 0x69, 0x58, 0xff,
+ 0x24, 0x6c, 0x5b, 0xff, 0x24, 0x6c, 0x5a, 0xff,
+ 0x16, 0x57, 0x4a, 0xff, 0x08, 0x41, 0x39, 0xff,
+ 0x21, 0x59, 0x42, 0xff, 0x26, 0x65, 0x4c, 0xff,
+ 0x2c, 0x72, 0x58, 0xff, 0x2c, 0x71, 0x57, 0xff,
+ 0x2c, 0x6c, 0x55, 0xff, 0x2b, 0x6c, 0x55, 0xff,
+ 0x32, 0x76, 0x5b, 0xff, 0x31, 0x75, 0x5a, 0xff,
+ 0x29, 0x64, 0x52, 0xff, 0x29, 0x63, 0x52, 0xff,
+ 0x29, 0x64, 0x52, 0xff, 0x21, 0x5a, 0x4a, 0xff,
+ 0x26, 0x51, 0x42, 0xff, 0x31, 0x71, 0x5a, 0xff,
+ 0x1c, 0x31, 0x29, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x0f, 0x11, 0xff, 0x10, 0x11, 0x10, 0xff,
+ 0x11, 0x0f, 0x11, 0xff, 0x10, 0x0f, 0x10, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x0f, 0x11, 0xff, 0x10, 0x0d, 0x10, 0xff,
+ 0x19, 0x2a, 0x21, 0xff, 0x29, 0x65, 0x52, 0xff,
+ 0x29, 0x65, 0x52, 0xff, 0x29, 0x65, 0x52, 0xff,
+ 0x24, 0x52, 0x3f, 0xff, 0x31, 0x69, 0x52, 0xff,
+ 0x24, 0x53, 0x3f, 0xff, 0x16, 0x3b, 0x2c, 0xff,
+ 0x42, 0x4e, 0x47, 0xff, 0x29, 0x2f, 0x2b, 0xff,
+ 0x29, 0x2f, 0x2c, 0xff, 0x5a, 0x6d, 0x62, 0xff,
+ 0x21, 0x3d, 0x29, 0xff, 0x20, 0x3c, 0x29, 0xff,
+ 0x37, 0x6b, 0x55, 0xff, 0x42, 0x81, 0x6b, 0xff,
+ 0x24, 0x67, 0x5b, 0xff, 0x1e, 0x57, 0x4a, 0xff,
+ 0x24, 0x67, 0x5b, 0xff, 0x23, 0x66, 0x5a, 0xff,
+ 0x1c, 0x5c, 0x4a, 0xff, 0x1b, 0x5b, 0x4a, 0xff,
+ 0x1c, 0x5c, 0x4a, 0xff, 0x16, 0x4a, 0x39, 0xff,
+ 0x21, 0x6b, 0x55, 0xff, 0x18, 0x5b, 0x47, 0xff,
+ 0x11, 0x4d, 0x3a, 0xff, 0x18, 0x5b, 0x47, 0xff,
+ 0x21, 0x5d, 0x4a, 0xff, 0x26, 0x69, 0x57, 0xff,
+ 0x2c, 0x76, 0x66, 0xff, 0x2c, 0x75, 0x65, 0xff,
+ 0x26, 0x69, 0x58, 0xff, 0x10, 0x51, 0x41, 0xff,
+ 0x1c, 0x5d, 0x4d, 0xff, 0x26, 0x69, 0x57, 0xff,
+ 0x16, 0x56, 0x4a, 0xff, 0x23, 0x6c, 0x5a, 0xff,
+ 0x24, 0x6c, 0x5b, 0xff, 0x16, 0x56, 0x4a, 0xff,
+ 0x21, 0x59, 0x42, 0xff, 0x2c, 0x71, 0x58, 0xff,
+ 0x32, 0x7e, 0x63, 0xff, 0x2c, 0x71, 0x58, 0xff,
+ 0x27, 0x63, 0x50, 0xff, 0x26, 0x62, 0x4f, 0xff,
+ 0x27, 0x63, 0x50, 0xff, 0x26, 0x62, 0x4f, 0xff,
+ 0x29, 0x64, 0x53, 0xff, 0x21, 0x5a, 0x4a, 0xff,
+ 0x2a, 0x64, 0x53, 0xff, 0x29, 0x64, 0x52, 0xff,
+ 0x32, 0x72, 0x5b, 0xff, 0x31, 0x71, 0x5a, 0xff,
+ 0x1c, 0x31, 0x2a, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x10, 0x11, 0x10, 0xff,
+ 0x11, 0x0d, 0x11, 0xff, 0x10, 0x0f, 0x10, 0xff,
+ 0x11, 0x0f, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x21, 0x48, 0x3a, 0xff, 0x29, 0x65, 0x52, 0xff,
+ 0x2a, 0x66, 0x53, 0xff, 0x29, 0x65, 0x52, 0xff,
+ 0x32, 0x6a, 0x53, 0xff, 0x31, 0x69, 0x52, 0xff,
+ 0x24, 0x53, 0x3f, 0xff, 0x24, 0x52, 0x3f, 0xff,
+ 0x42, 0x4f, 0x48, 0xff, 0x42, 0x4e, 0x47, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x29, 0x2f, 0x2c, 0xff,
+ 0x21, 0x3d, 0x29, 0xff, 0x2c, 0x53, 0x3f, 0xff,
+ 0x21, 0x3d, 0x2a, 0xff, 0x37, 0x6a, 0x55, 0xff,
+ 0x29, 0x76, 0x6b, 0xff, 0x23, 0x66, 0x5a, 0xff,
+ 0x2a, 0x76, 0x6b, 0xff, 0x29, 0x75, 0x6b, 0xff,
+ 0x21, 0x6e, 0x5b, 0xff, 0x21, 0x6d, 0x5a, 0xff,
+ 0x1c, 0x5c, 0x4a, 0xff, 0x21, 0x6d, 0x5a, 0xff,
+ 0x29, 0x7a, 0x63, 0xff, 0x21, 0x6a, 0x55, 0xff,
+ 0x19, 0x5c, 0x48, 0xff, 0x19, 0x5c, 0x47, 0xff,
+ 0x21, 0x5d, 0x4a, 0xff, 0x21, 0x5d, 0x4a, 0xff,
+ 0x2c, 0x76, 0x66, 0xff, 0x26, 0x69, 0x58, 0xff,
+ 0x27, 0x6a, 0x58, 0xff, 0x26, 0x69, 0x58, 0xff,
+ 0x27, 0x6a, 0x58, 0xff, 0x1b, 0x5d, 0x4d, 0xff,
+ 0x24, 0x6c, 0x5b, 0xff, 0x23, 0x6c, 0x5a, 0xff,
+ 0x24, 0x6c, 0x5b, 0xff, 0x24, 0x6c, 0x5a, 0xff,
+ 0x21, 0x59, 0x42, 0xff, 0x26, 0x65, 0x4c, 0xff,
+ 0x2c, 0x71, 0x58, 0xff, 0x26, 0x65, 0x4c, 0xff,
+ 0x27, 0x63, 0x50, 0xff, 0x2c, 0x6c, 0x55, 0xff,
+ 0x31, 0x75, 0x5b, 0xff, 0x2b, 0x6b, 0x55, 0xff,
+ 0x32, 0x6d, 0x5b, 0xff, 0x18, 0x51, 0x41, 0xff,
+ 0x29, 0x64, 0x52, 0xff, 0x29, 0x63, 0x52, 0xff,
+ 0x27, 0x51, 0x42, 0xff, 0x1b, 0x30, 0x29, 0xff,
+ 0x10, 0x10, 0x10, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x10, 0x0c, 0x10, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x11, 0x0f, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x10, 0x10, 0x10, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x21, 0x48, 0x3a, 0xff, 0x29, 0x65, 0x52, 0xff,
+ 0x29, 0x65, 0x52, 0xff, 0x29, 0x65, 0x52, 0xff,
+ 0x32, 0x69, 0x52, 0xff, 0x31, 0x69, 0x52, 0xff,
+ 0x16, 0x3b, 0x2c, 0xff, 0x23, 0x52, 0x3f, 0xff,
+ 0x42, 0x4e, 0x47, 0xff, 0x41, 0x4e, 0x47, 0xff,
+ 0x10, 0x10, 0x10, 0xff, 0x5a, 0x6d, 0x62, 0xff,
+ 0x37, 0x6b, 0x55, 0xff, 0x36, 0x6a, 0x55, 0xff,
+ 0x21, 0x3d, 0x29, 0xff, 0x20, 0x3c, 0x29, 0xff,
+ 0x24, 0x67, 0x5b, 0xff, 0x29, 0x75, 0x6b, 0xff,
+ 0x24, 0x67, 0x5b, 0xff, 0x23, 0x66, 0x5a, 0xff,
+ 0x21, 0x6d, 0x5b, 0xff, 0x21, 0x6d, 0x5a, 0xff,
+ 0x21, 0x6d, 0x5b, 0xff, 0x1b, 0x5b, 0x4a, 0xff,
+ 0x21, 0x6b, 0x55, 0xff, 0x18, 0x5b, 0x47, 0xff,
+ 0x10, 0x4d, 0x3a, 0xff, 0x18, 0x5b, 0x47, 0xff,
+ 0x21, 0x5d, 0x4a, 0xff, 0x26, 0x69, 0x57, 0xff,
+ 0x2c, 0x75, 0x65, 0xff, 0x31, 0x81, 0x73, 0xff,
+ 0x27, 0x69, 0x58, 0xff, 0x1b, 0x5d, 0x4c, 0xff,
+ 0x31, 0x75, 0x63, 0xff, 0x31, 0x75, 0x62, 0xff,
+ 0x24, 0x6c, 0x5b, 0xff, 0x23, 0x6c, 0x5a, 0xff,
+ 0x31, 0x82, 0x6b, 0xff, 0x31, 0x81, 0x6a, 0xff,
+ 0x21, 0x55, 0x42, 0xff, 0x21, 0x55, 0x42, 0xff,
+ 0x37, 0x6e, 0x58, 0xff, 0x2c, 0x61, 0x4d, 0xff,
+ 0x2a, 0x60, 0x4b, 0xff, 0x31, 0x6f, 0x5a, 0xff,
+ 0x29, 0x60, 0x4a, 0xff, 0x31, 0x6e, 0x5a, 0xff,
+ 0x32, 0x6a, 0x5b, 0xff, 0x31, 0x69, 0x5a, 0xff,
+ 0x32, 0x6a, 0x5b, 0xff, 0x21, 0x49, 0x4a, 0xff,
+ 0x2c, 0x58, 0x4d, 0xff, 0x2c, 0x58, 0x4d, 0xff,
+ 0x1f, 0x36, 0x2f, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x0f, 0x0b, 0xff, 0x10, 0x0f, 0x0b, 0xff,
+ 0x11, 0x0c, 0x09, 0xff, 0x10, 0x0f, 0x0b, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x14, 0x13, 0x14, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x19, 0x39, 0x32, 0xff, 0x29, 0x5e, 0x4d, 0xff,
+ 0x29, 0x5f, 0x4d, 0xff, 0x31, 0x71, 0x5a, 0xff,
+ 0x3a, 0x72, 0x63, 0xff, 0x29, 0x51, 0x47, 0xff,
+ 0x21, 0x41, 0x3a, 0xff, 0x29, 0x51, 0x47, 0xff,
+ 0x2f, 0x62, 0x55, 0xff, 0x21, 0x49, 0x42, 0xff,
+ 0x21, 0x49, 0x42, 0xff, 0x4a, 0x92, 0x7b, 0xff,
+ 0x42, 0x7e, 0x6b, 0xff, 0x42, 0x7d, 0x6b, 0xff,
+ 0x27, 0x5b, 0x4a, 0xff, 0x19, 0x49, 0x39, 0xff,
+ 0x21, 0x53, 0x45, 0xff, 0x31, 0x70, 0x60, 0xff,
+ 0x32, 0x70, 0x60, 0xff, 0x21, 0x52, 0x44, 0xff,
+ 0x11, 0x51, 0x3a, 0xff, 0x1e, 0x61, 0x4a, 0xff,
+ 0x2c, 0x72, 0x5b, 0xff, 0x2c, 0x71, 0x5a, 0xff,
+ 0x21, 0x55, 0x42, 0xff, 0x31, 0x78, 0x68, 0xff,
+ 0x21, 0x55, 0x42, 0xff, 0x21, 0x55, 0x42, 0xff,
+ 0x1f, 0x55, 0x42, 0xff, 0x24, 0x65, 0x52, 0xff,
+ 0x29, 0x76, 0x63, 0xff, 0x29, 0x75, 0x63, 0xff,
+ 0x2a, 0x86, 0x6b, 0xff, 0x24, 0x74, 0x5a, 0xff,
+ 0x24, 0x74, 0x5b, 0xff, 0x23, 0x74, 0x5a, 0xff,
+ 0x2c, 0x75, 0x60, 0xff, 0x2c, 0x74, 0x60, 0xff,
+ 0x2c, 0x74, 0x60, 0xff, 0x2c, 0x74, 0x60, 0xff,
+ 0x2c, 0x61, 0x4d, 0xff, 0x36, 0x6d, 0x57, 0xff,
+ 0x37, 0x6e, 0x58, 0xff, 0x2c, 0x61, 0x4c, 0xff,
+ 0x31, 0x6f, 0x5b, 0xff, 0x20, 0x51, 0x39, 0xff,
+ 0x21, 0x51, 0x3a, 0xff, 0x29, 0x60, 0x4a, 0xff,
+ 0x31, 0x69, 0x5b, 0xff, 0x39, 0x79, 0x62, 0xff,
+ 0x3a, 0x7a, 0x63, 0xff, 0x31, 0x69, 0x5a, 0xff,
+ 0x3a, 0x7a, 0x6b, 0xff, 0x39, 0x79, 0x6b, 0xff,
+ 0x1e, 0x36, 0x2f, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x14, 0x11, 0xff, 0x10, 0x11, 0x0d, 0xff,
+ 0x11, 0x0f, 0x0b, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x13, 0x12, 0x13, 0xff,
+ 0x16, 0x16, 0x16, 0xff, 0x13, 0x13, 0x13, 0xff,
+ 0x19, 0x39, 0x31, 0xff, 0x31, 0x71, 0x5a, 0xff,
+ 0x32, 0x72, 0x5b, 0xff, 0x29, 0x5e, 0x4c, 0xff,
+ 0x31, 0x61, 0x55, 0xff, 0x20, 0x40, 0x39, 0xff,
+ 0x32, 0x61, 0x55, 0xff, 0x31, 0x61, 0x55, 0xff,
+ 0x2f, 0x61, 0x55, 0xff, 0x20, 0x48, 0x41, 0xff,
+ 0x2f, 0x61, 0x55, 0xff, 0x3c, 0x79, 0x68, 0xff,
+ 0x34, 0x6c, 0x5b, 0xff, 0x34, 0x6c, 0x5a, 0xff,
+ 0x42, 0x7e, 0x6b, 0xff, 0x26, 0x5a, 0x4a, 0xff,
+ 0x11, 0x35, 0x29, 0xff, 0x31, 0x70, 0x60, 0xff,
+ 0x42, 0x8e, 0x7c, 0xff, 0x31, 0x70, 0x60, 0xff,
+ 0x2c, 0x71, 0x5b, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x2c, 0x72, 0x5b, 0xff, 0x2c, 0x71, 0x5a, 0xff,
+ 0x29, 0x67, 0x55, 0xff, 0x29, 0x66, 0x55, 0xff,
+ 0x21, 0x55, 0x42, 0xff, 0x21, 0x55, 0x42, 0xff,
+ 0x1e, 0x55, 0x42, 0xff, 0x18, 0x44, 0x31, 0xff,
+ 0x24, 0x65, 0x52, 0xff, 0x29, 0x75, 0x62, 0xff,
+ 0x24, 0x74, 0x5b, 0xff, 0x23, 0x74, 0x5a, 0xff,
+ 0x24, 0x74, 0x5b, 0xff, 0x23, 0x74, 0x5a, 0xff,
+ 0x1e, 0x63, 0x4d, 0xff, 0x2b, 0x74, 0x60, 0xff,
+ 0x3a, 0x86, 0x73, 0xff, 0x1e, 0x62, 0x4c, 0xff,
+ 0x37, 0x6e, 0x58, 0xff, 0x42, 0x79, 0x62, 0xff,
+ 0x37, 0x6e, 0x58, 0xff, 0x37, 0x6d, 0x58, 0xff,
+ 0x21, 0x51, 0x3a, 0xff, 0x29, 0x60, 0x4a, 0xff,
+ 0x32, 0x6f, 0x5b, 0xff, 0x31, 0x6f, 0x5a, 0xff,
+ 0x3a, 0x7a, 0x63, 0xff, 0x31, 0x69, 0x5a, 0xff,
+ 0x32, 0x6a, 0x5b, 0xff, 0x39, 0x79, 0x63, 0xff,
+ 0x3a, 0x7a, 0x6b, 0xff, 0x2c, 0x57, 0x4d, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x12, 0x0e, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x12, 0x0e, 0xff, 0x10, 0x0f, 0x0b, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x16, 0x15, 0x16, 0xff,
+ 0x14, 0x13, 0x14, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x21, 0x4c, 0x3f, 0xff, 0x29, 0x5e, 0x4d, 0xff,
+ 0x32, 0x72, 0x5b, 0xff, 0x29, 0x5e, 0x4d, 0xff,
+ 0x29, 0x51, 0x48, 0xff, 0x21, 0x41, 0x39, 0xff,
+ 0x3a, 0x72, 0x63, 0xff, 0x39, 0x71, 0x63, 0xff,
+ 0x21, 0x49, 0x42, 0xff, 0x21, 0x49, 0x42, 0xff,
+ 0x2f, 0x62, 0x55, 0xff, 0x2f, 0x61, 0x55, 0xff,
+ 0x34, 0x6c, 0x5b, 0xff, 0x34, 0x6c, 0x5a, 0xff,
+ 0x42, 0x7e, 0x6b, 0xff, 0x34, 0x6c, 0x5a, 0xff,
+ 0x21, 0x53, 0x45, 0xff, 0x31, 0x70, 0x60, 0xff,
+ 0x42, 0x8e, 0x7c, 0xff, 0x42, 0x8e, 0x7b, 0xff,
+ 0x1e, 0x61, 0x4a, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x1f, 0x62, 0x4a, 0xff, 0x1e, 0x61, 0x4a, 0xff,
+ 0x32, 0x78, 0x68, 0xff, 0x31, 0x78, 0x68, 0xff,
+ 0x21, 0x55, 0x42, 0xff, 0x21, 0x55, 0x42, 0xff,
+ 0x24, 0x65, 0x53, 0xff, 0x18, 0x45, 0x31, 0xff,
+ 0x1f, 0x55, 0x42, 0xff, 0x24, 0x65, 0x52, 0xff,
+ 0x19, 0x51, 0x3a, 0xff, 0x1e, 0x62, 0x4a, 0xff,
+ 0x1f, 0x63, 0x4a, 0xff, 0x1e, 0x62, 0x4a, 0xff,
+ 0x11, 0x51, 0x3a, 0xff, 0x1e, 0x62, 0x4d, 0xff,
+ 0x3a, 0x86, 0x74, 0xff, 0x39, 0x85, 0x73, 0xff,
+ 0x42, 0x7a, 0x63, 0xff, 0x2c, 0x61, 0x4c, 0xff,
+ 0x21, 0x55, 0x42, 0xff, 0x2b, 0x61, 0x4c, 0xff,
+ 0x29, 0x60, 0x4a, 0xff, 0x31, 0x6e, 0x5a, 0xff,
+ 0x31, 0x6f, 0x5b, 0xff, 0x39, 0x7d, 0x6a, 0xff,
+ 0x3a, 0x7a, 0x63, 0xff, 0x39, 0x79, 0x62, 0xff,
+ 0x31, 0x69, 0x5b, 0xff, 0x31, 0x69, 0x5a, 0xff,
+ 0x3a, 0x7a, 0x6b, 0xff, 0x2c, 0x57, 0x4c, 0xff,
+ 0x10, 0x14, 0x10, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x0c, 0x08, 0xff, 0x10, 0x11, 0x0d, 0xff,
+ 0x10, 0x14, 0x10, 0xff, 0x10, 0x0e, 0x0a, 0xff,
+ 0x13, 0x13, 0x13, 0xff, 0x16, 0x15, 0x16, 0xff,
+ 0x16, 0x16, 0x16, 0xff, 0x15, 0x15, 0x15, 0xff,
+ 0x19, 0x39, 0x32, 0xff, 0x21, 0x4b, 0x3f, 0xff,
+ 0x29, 0x5e, 0x4d, 0xff, 0x31, 0x71, 0x5a, 0xff,
+ 0x29, 0x51, 0x47, 0xff, 0x31, 0x61, 0x55, 0xff,
+ 0x3a, 0x71, 0x63, 0xff, 0x39, 0x71, 0x62, 0xff,
+ 0x21, 0x49, 0x42, 0xff, 0x2e, 0x61, 0x55, 0xff,
+ 0x2f, 0x61, 0x55, 0xff, 0x2e, 0x61, 0x55, 0xff,
+ 0x19, 0x49, 0x3a, 0xff, 0x26, 0x5a, 0x4a, 0xff,
+ 0x19, 0x49, 0x3a, 0xff, 0x18, 0x48, 0x39, 0xff,
+ 0x11, 0x35, 0x29, 0xff, 0x21, 0x52, 0x44, 0xff,
+ 0x42, 0x8e, 0x7b, 0xff, 0x41, 0x8d, 0x7b, 0xff,
+ 0x1e, 0x61, 0x4a, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x1e, 0x61, 0x4a, 0xff, 0x1e, 0x61, 0x4a, 0xff,
+ 0x32, 0x78, 0x68, 0xff, 0x39, 0x89, 0x7b, 0xff,
+ 0x31, 0x78, 0x68, 0xff, 0x29, 0x66, 0x55, 0xff,
+ 0x24, 0x65, 0x52, 0xff, 0x18, 0x44, 0x31, 0xff,
+ 0x1e, 0x55, 0x42, 0xff, 0x1e, 0x55, 0x41, 0xff,
+ 0x19, 0x51, 0x3a, 0xff, 0x18, 0x51, 0x39, 0xff,
+ 0x1e, 0x63, 0x4a, 0xff, 0x1e, 0x62, 0x4a, 0xff,
+ 0x11, 0x51, 0x3a, 0xff, 0x10, 0x51, 0x39, 0xff,
+ 0x3a, 0x86, 0x73, 0xff, 0x2b, 0x74, 0x5f, 0xff,
+ 0x2f, 0x68, 0x55, 0xff, 0x2f, 0x68, 0x55, 0xff,
+ 0x34, 0x73, 0x60, 0xff, 0x34, 0x73, 0x60, 0xff,
+ 0x32, 0x72, 0x5b, 0xff, 0x2c, 0x68, 0x52, 0xff,
+ 0x32, 0x72, 0x5b, 0xff, 0x31, 0x71, 0x5a, 0xff,
+ 0x32, 0x6a, 0x55, 0xff, 0x3a, 0x75, 0x60, 0xff,
+ 0x32, 0x6a, 0x55, 0xff, 0x29, 0x5d, 0x4a, 0xff,
+ 0x3a, 0x76, 0x63, 0xff, 0x2c, 0x58, 0x47, 0xff,
+ 0x11, 0x1d, 0x11, 0xff, 0x10, 0x1c, 0x10, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x2c, 0x5e, 0x53, 0xff, 0x2c, 0x5d, 0x52, 0xff,
+ 0x21, 0x49, 0x42, 0xff, 0x21, 0x49, 0x42, 0xff,
+ 0x11, 0x49, 0x3a, 0xff, 0x31, 0x6f, 0x60, 0xff,
+ 0x32, 0x6f, 0x60, 0xff, 0x21, 0x5c, 0x4d, 0xff,
+ 0x32, 0x72, 0x5b, 0xff, 0x29, 0x64, 0x4d, 0xff,
+ 0x32, 0x72, 0x5b, 0xff, 0x31, 0x71, 0x5a, 0xff,
+ 0x24, 0x67, 0x55, 0xff, 0x1e, 0x58, 0x47, 0xff,
+ 0x19, 0x49, 0x3a, 0xff, 0x19, 0x49, 0x39, 0xff,
+ 0x11, 0x31, 0x21, 0xff, 0x19, 0x4c, 0x37, 0xff,
+ 0x21, 0x67, 0x4d, 0xff, 0x29, 0x81, 0x63, 0xff,
+ 0x1c, 0x66, 0x4d, 0xff, 0x26, 0x71, 0x58, 0xff,
+ 0x27, 0x72, 0x58, 0xff, 0x10, 0x59, 0x42, 0xff,
+ 0x2c, 0x7f, 0x6e, 0xff, 0x3a, 0x92, 0x84, 0xff,
+ 0x2c, 0x7f, 0x6e, 0xff, 0x1e, 0x6c, 0x58, 0xff,
+ 0x27, 0x76, 0x5b, 0xff, 0x10, 0x55, 0x3a, 0xff,
+ 0x1c, 0x66, 0x4a, 0xff, 0x10, 0x55, 0x39, 0xff,
+ 0x16, 0x54, 0x3d, 0xff, 0x24, 0x67, 0x4f, 0xff,
+ 0x32, 0x7a, 0x63, 0xff, 0x31, 0x79, 0x63, 0xff,
+ 0x21, 0x60, 0x4b, 0xff, 0x19, 0x51, 0x3a, 0xff,
+ 0x21, 0x60, 0x4a, 0xff, 0x31, 0x7d, 0x6b, 0xff,
+ 0x2f, 0x68, 0x55, 0xff, 0x2e, 0x67, 0x55, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x34, 0x72, 0x60, 0xff,
+ 0x31, 0x71, 0x5b, 0xff, 0x2b, 0x67, 0x52, 0xff,
+ 0x27, 0x5f, 0x4a, 0xff, 0x26, 0x5e, 0x4a, 0xff,
+ 0x29, 0x5d, 0x4a, 0xff, 0x31, 0x69, 0x55, 0xff,
+ 0x32, 0x69, 0x55, 0xff, 0x39, 0x75, 0x60, 0xff,
+ 0x3a, 0x75, 0x63, 0xff, 0x1e, 0x3a, 0x2b, 0xff,
+ 0x11, 0x1d, 0x11, 0xff, 0x10, 0x1c, 0x10, 0xff,
+ 0x11, 0x14, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x14, 0x11, 0xff, 0x1b, 0x33, 0x29, 0xff,
+ 0x11, 0x14, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x14, 0x11, 0xff, 0x16, 0x27, 0x1e, 0xff,
+ 0x37, 0x71, 0x63, 0xff, 0x36, 0x71, 0x62, 0xff,
+ 0x42, 0x86, 0x73, 0xff, 0x21, 0x49, 0x42, 0xff,
+ 0x21, 0x5c, 0x4d, 0xff, 0x20, 0x5b, 0x4c, 0xff,
+ 0x11, 0x49, 0x3a, 0xff, 0x10, 0x49, 0x39, 0xff,
+ 0x21, 0x56, 0x3f, 0xff, 0x20, 0x56, 0x3f, 0xff,
+ 0x32, 0x72, 0x5b, 0xff, 0x29, 0x64, 0x4c, 0xff,
+ 0x24, 0x67, 0x55, 0xff, 0x23, 0x66, 0x55, 0xff,
+ 0x29, 0x76, 0x63, 0xff, 0x23, 0x66, 0x55, 0xff,
+ 0x19, 0x4c, 0x37, 0xff, 0x18, 0x4b, 0x36, 0xff,
+ 0x11, 0x31, 0x21, 0xff, 0x21, 0x66, 0x4c, 0xff,
+ 0x26, 0x71, 0x58, 0xff, 0x1b, 0x65, 0x4c, 0xff,
+ 0x27, 0x72, 0x58, 0xff, 0x1b, 0x65, 0x4c, 0xff,
+ 0x1e, 0x6c, 0x58, 0xff, 0x2b, 0x7e, 0x6d, 0xff,
+ 0x3a, 0x92, 0x84, 0xff, 0x2c, 0x7f, 0x6d, 0xff,
+ 0x26, 0x75, 0x5b, 0xff, 0x26, 0x75, 0x5a, 0xff,
+ 0x27, 0x76, 0x5b, 0xff, 0x10, 0x55, 0x39, 0xff,
+ 0x16, 0x54, 0x3c, 0xff, 0x23, 0x66, 0x4f, 0xff,
+ 0x24, 0x67, 0x50, 0xff, 0x23, 0x66, 0x4f, 0xff,
+ 0x29, 0x6f, 0x5b, 0xff, 0x29, 0x6e, 0x5a, 0xff,
+ 0x29, 0x6f, 0x5b, 0xff, 0x29, 0x6e, 0x5a, 0xff,
+ 0x29, 0x5d, 0x4a, 0xff, 0x2e, 0x68, 0x55, 0xff,
+ 0x35, 0x73, 0x60, 0xff, 0x34, 0x73, 0x60, 0xff,
+ 0x27, 0x5f, 0x4a, 0xff, 0x21, 0x55, 0x42, 0xff,
+ 0x2c, 0x68, 0x53, 0xff, 0x2c, 0x68, 0x52, 0xff,
+ 0x3a, 0x76, 0x60, 0xff, 0x31, 0x69, 0x55, 0xff,
+ 0x3a, 0x76, 0x60, 0xff, 0x39, 0x75, 0x60, 0xff,
+ 0x3a, 0x76, 0x63, 0xff, 0x1e, 0x3a, 0x2c, 0xff,
+ 0x11, 0x1d, 0x11, 0xff, 0x10, 0x1c, 0x10, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x1b, 0x33, 0x29, 0xff,
+ 0x27, 0x53, 0x42, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x10, 0x14, 0x10, 0xff,
+ 0x11, 0x15, 0x11, 0xff, 0x1b, 0x3a, 0x2c, 0xff,
+ 0x42, 0x86, 0x73, 0xff, 0x42, 0x85, 0x73, 0xff,
+ 0x37, 0x72, 0x63, 0xff, 0x2c, 0x5d, 0x52, 0xff,
+ 0x42, 0x82, 0x73, 0xff, 0x31, 0x6e, 0x60, 0xff,
+ 0x11, 0x49, 0x3a, 0xff, 0x31, 0x6f, 0x60, 0xff,
+ 0x29, 0x64, 0x4d, 0xff, 0x18, 0x49, 0x31, 0xff,
+ 0x21, 0x57, 0x3f, 0xff, 0x21, 0x56, 0x3f, 0xff,
+ 0x29, 0x76, 0x63, 0xff, 0x29, 0x75, 0x62, 0xff,
+ 0x2a, 0x76, 0x63, 0xff, 0x24, 0x66, 0x55, 0xff,
+ 0x21, 0x67, 0x4d, 0xff, 0x21, 0x66, 0x4d, 0xff,
+ 0x11, 0x31, 0x21, 0xff, 0x19, 0x4b, 0x37, 0xff,
+ 0x32, 0x7e, 0x63, 0xff, 0x26, 0x71, 0x58, 0xff,
+ 0x11, 0x59, 0x42, 0xff, 0x26, 0x71, 0x58, 0xff,
+ 0x2c, 0x7f, 0x6e, 0xff, 0x2c, 0x7f, 0x6d, 0xff,
+ 0x1f, 0x6c, 0x58, 0xff, 0x1e, 0x6c, 0x58, 0xff,
+ 0x27, 0x76, 0x5b, 0xff, 0x26, 0x75, 0x5a, 0xff,
+ 0x32, 0x86, 0x6b, 0xff, 0x1b, 0x65, 0x4a, 0xff,
+ 0x09, 0x41, 0x29, 0xff, 0x16, 0x53, 0x3c, 0xff,
+ 0x16, 0x54, 0x3d, 0xff, 0x24, 0x66, 0x4f, 0xff,
+ 0x21, 0x60, 0x4a, 0xff, 0x31, 0x7d, 0x6b, 0xff,
+ 0x2a, 0x6f, 0x5b, 0xff, 0x19, 0x51, 0x39, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x34, 0x72, 0x60, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x34, 0x72, 0x5f, 0xff,
+ 0x2c, 0x68, 0x52, 0xff, 0x31, 0x71, 0x5a, 0xff,
+ 0x2c, 0x68, 0x52, 0xff, 0x2b, 0x67, 0x52, 0xff,
+ 0x42, 0x82, 0x6b, 0xff, 0x39, 0x75, 0x60, 0xff,
+ 0x31, 0x69, 0x55, 0xff, 0x31, 0x69, 0x55, 0xff,
+ 0x2c, 0x58, 0x47, 0xff, 0x1e, 0x3a, 0x2c, 0xff,
+ 0x10, 0x1c, 0x10, 0xff, 0x10, 0x1c, 0x10, 0xff,
+ 0x11, 0x14, 0x11, 0xff, 0x26, 0x52, 0x41, 0xff,
+ 0x31, 0x71, 0x5b, 0xff, 0x1b, 0x33, 0x29, 0xff,
+ 0x11, 0x14, 0x11, 0xff, 0x16, 0x27, 0x1e, 0xff,
+ 0x10, 0x14, 0x10, 0xff, 0x20, 0x4c, 0x39, 0xff,
+ 0x42, 0x86, 0x73, 0xff, 0x41, 0x85, 0x73, 0xff,
+ 0x2c, 0x5d, 0x52, 0xff, 0x2b, 0x5d, 0x52, 0xff,
+ 0x42, 0x82, 0x73, 0xff, 0x21, 0x5b, 0x4c, 0xff,
+ 0x31, 0x6f, 0x60, 0xff, 0x41, 0x81, 0x73, 0xff,
+ 0x32, 0x71, 0x5b, 0xff, 0x31, 0x71, 0x5a, 0xff,
+ 0x21, 0x56, 0x3f, 0xff, 0x18, 0x48, 0x31, 0xff,
+ 0x19, 0x49, 0x3a, 0xff, 0x23, 0x66, 0x55, 0xff,
+ 0x29, 0x75, 0x63, 0xff, 0x29, 0x75, 0x62, 0xff,
+ 0x21, 0x67, 0x4d, 0xff, 0x21, 0x66, 0x4c, 0xff,
+ 0x19, 0x4c, 0x37, 0xff, 0x10, 0x30, 0x20, 0xff,
+ 0x11, 0x59, 0x42, 0xff, 0x31, 0x7d, 0x62, 0xff,
+ 0x26, 0x71, 0x58, 0xff, 0x26, 0x71, 0x57, 0xff,
+ 0x2c, 0x7f, 0x6e, 0xff, 0x2c, 0x7e, 0x6d, 0xff,
+ 0x1e, 0x6c, 0x58, 0xff, 0x10, 0x59, 0x41, 0xff,
+ 0x11, 0x55, 0x3a, 0xff, 0x1b, 0x65, 0x4a, 0xff,
+ 0x26, 0x75, 0x5b, 0xff, 0x31, 0x85, 0x6a, 0xff,
+ 0x24, 0x67, 0x50, 0xff, 0x16, 0x53, 0x3c, 0xff,
+ 0x08, 0x41, 0x29, 0xff, 0x23, 0x66, 0x4f, 0xff,
+ 0x29, 0x6f, 0x5b, 0xff, 0x29, 0x6e, 0x5a, 0xff,
+ 0x29, 0x6f, 0x5b, 0xff, 0x20, 0x5f, 0x4a, 0xff,
+ 0x40, 0x79, 0x6b, 0xff, 0x45, 0x83, 0x73, 0xff,
+ 0x45, 0x83, 0x74, 0xff, 0x39, 0x6d, 0x63, 0xff,
+ 0x3a, 0x7a, 0x6b, 0xff, 0x42, 0x80, 0x73, 0xff,
+ 0x42, 0x81, 0x74, 0xff, 0x42, 0x80, 0x73, 0xff,
+ 0x42, 0x86, 0x6b, 0xff, 0x3a, 0x79, 0x60, 0xff,
+ 0x42, 0x86, 0x6b, 0xff, 0x39, 0x79, 0x60, 0xff,
+ 0x32, 0x6a, 0x4b, 0xff, 0x1b, 0x33, 0x24, 0xff,
+ 0x11, 0x19, 0x11, 0xff, 0x10, 0x18, 0x10, 0xff,
+ 0x11, 0x29, 0x21, 0xff, 0x31, 0x61, 0x52, 0xff,
+ 0x32, 0x61, 0x53, 0xff, 0x21, 0x45, 0x39, 0xff,
+ 0x11, 0x25, 0x19, 0xff, 0x10, 0x24, 0x19, 0xff,
+ 0x11, 0x25, 0x19, 0xff, 0x31, 0x62, 0x55, 0xff,
+ 0x2f, 0x63, 0x4b, 0xff, 0x2f, 0x62, 0x4a, 0xff,
+ 0x24, 0x50, 0x3a, 0xff, 0x39, 0x75, 0x5a, 0xff,
+ 0x21, 0x5a, 0x42, 0xff, 0x2c, 0x68, 0x52, 0xff,
+ 0x42, 0x86, 0x74, 0xff, 0x37, 0x77, 0x63, 0xff,
+ 0x35, 0x75, 0x63, 0xff, 0x42, 0x86, 0x73, 0xff,
+ 0x27, 0x63, 0x53, 0xff, 0x19, 0x51, 0x42, 0xff,
+ 0x19, 0x49, 0x32, 0xff, 0x24, 0x5a, 0x45, 0xff,
+ 0x2f, 0x6c, 0x58, 0xff, 0x39, 0x7d, 0x6b, 0xff,
+ 0x21, 0x63, 0x4d, 0xff, 0x21, 0x62, 0x4d, 0xff,
+ 0x29, 0x72, 0x5b, 0xff, 0x21, 0x62, 0x4d, 0xff,
+ 0x21, 0x66, 0x4b, 0xff, 0x21, 0x65, 0x4a, 0xff,
+ 0x19, 0x51, 0x3a, 0xff, 0x21, 0x65, 0x4a, 0xff,
+ 0x32, 0x7e, 0x63, 0xff, 0x31, 0x7d, 0x63, 0xff,
+ 0x21, 0x63, 0x4d, 0xff, 0x29, 0x70, 0x58, 0xff,
+ 0x1c, 0x5a, 0x42, 0xff, 0x10, 0x49, 0x31, 0xff,
+ 0x1c, 0x59, 0x42, 0xff, 0x31, 0x79, 0x63, 0xff,
+ 0x2f, 0x72, 0x5e, 0xff, 0x2f, 0x71, 0x5d, 0xff,
+ 0x1c, 0x55, 0x3f, 0xff, 0x1b, 0x55, 0x3f, 0xff,
+ 0x24, 0x67, 0x4d, 0xff, 0x31, 0x7d, 0x63, 0xff,
+ 0x32, 0x7e, 0x63, 0xff, 0x23, 0x66, 0x4d, 0xff,
+ 0x3f, 0x78, 0x6b, 0xff, 0x44, 0x82, 0x73, 0xff,
+ 0x45, 0x83, 0x73, 0xff, 0x3f, 0x78, 0x6b, 0xff,
+ 0x3a, 0x7a, 0x6b, 0xff, 0x4a, 0x87, 0x7b, 0xff,
+ 0x4a, 0x87, 0x7c, 0xff, 0x52, 0x8d, 0x83, 0xff,
+ 0x42, 0x86, 0x6b, 0xff, 0x39, 0x79, 0x60, 0xff,
+ 0x3a, 0x7a, 0x60, 0xff, 0x31, 0x6d, 0x55, 0xff,
+ 0x26, 0x4e, 0x37, 0xff, 0x10, 0x18, 0x10, 0xff,
+ 0x11, 0x19, 0x11, 0xff, 0x10, 0x18, 0x10, 0xff,
+ 0x11, 0x29, 0x21, 0xff, 0x31, 0x61, 0x52, 0xff,
+ 0x21, 0x45, 0x3a, 0xff, 0x10, 0x28, 0x21, 0xff,
+ 0x21, 0x44, 0x37, 0xff, 0x10, 0x24, 0x18, 0xff,
+ 0x21, 0x44, 0x37, 0xff, 0x31, 0x62, 0x55, 0xff,
+ 0x19, 0x3d, 0x29, 0xff, 0x18, 0x3c, 0x29, 0xff,
+ 0x19, 0x3d, 0x29, 0xff, 0x39, 0x75, 0x5a, 0xff,
+ 0x21, 0x59, 0x42, 0xff, 0x36, 0x76, 0x62, 0xff,
+ 0x42, 0x86, 0x73, 0xff, 0x37, 0x76, 0x62, 0xff,
+ 0x34, 0x74, 0x63, 0xff, 0x41, 0x85, 0x73, 0xff,
+ 0x34, 0x74, 0x63, 0xff, 0x26, 0x62, 0x52, 0xff,
+ 0x2f, 0x6c, 0x58, 0xff, 0x2e, 0x6c, 0x57, 0xff,
+ 0x2f, 0x6c, 0x58, 0xff, 0x2e, 0x6c, 0x57, 0xff,
+ 0x29, 0x71, 0x5b, 0xff, 0x18, 0x53, 0x3f, 0xff,
+ 0x21, 0x63, 0x4d, 0xff, 0x29, 0x71, 0x5a, 0xff,
+ 0x21, 0x65, 0x4a, 0xff, 0x18, 0x51, 0x39, 0xff,
+ 0x19, 0x51, 0x3a, 0xff, 0x18, 0x51, 0x39, 0xff,
+ 0x29, 0x70, 0x58, 0xff, 0x29, 0x70, 0x57, 0xff,
+ 0x21, 0x63, 0x4d, 0xff, 0x29, 0x70, 0x57, 0xff,
+ 0x1c, 0x59, 0x42, 0xff, 0x26, 0x69, 0x52, 0xff,
+ 0x27, 0x69, 0x52, 0xff, 0x31, 0x79, 0x62, 0xff,
+ 0x2f, 0x71, 0x5d, 0xff, 0x2e, 0x71, 0x5d, 0xff,
+ 0x1c, 0x55, 0x3f, 0xff, 0x1b, 0x55, 0x3f, 0xff,
+ 0x24, 0x67, 0x4d, 0xff, 0x31, 0x7d, 0x62, 0xff,
+ 0x24, 0x67, 0x4d, 0xff, 0x23, 0x66, 0x4c, 0xff,
+ 0x3f, 0x78, 0x6b, 0xff, 0x4a, 0x8d, 0x7b, 0xff,
+ 0x4a, 0x8e, 0x7c, 0xff, 0x3f, 0x78, 0x6b, 0xff,
+ 0x42, 0x80, 0x73, 0xff, 0x52, 0x8d, 0x83, 0xff,
+ 0x4a, 0x87, 0x7c, 0xff, 0x42, 0x80, 0x73, 0xff,
+ 0x42, 0x86, 0x6b, 0xff, 0x31, 0x6d, 0x55, 0xff,
+ 0x32, 0x6e, 0x55, 0xff, 0x29, 0x61, 0x4a, 0xff,
+ 0x1c, 0x34, 0x24, 0xff, 0x10, 0x18, 0x10, 0xff,
+ 0x11, 0x19, 0x11, 0xff, 0x10, 0x18, 0x10, 0xff,
+ 0x11, 0x29, 0x21, 0xff, 0x42, 0x7d, 0x6b, 0xff,
+ 0x21, 0x45, 0x3a, 0xff, 0x31, 0x61, 0x52, 0xff,
+ 0x32, 0x63, 0x55, 0xff, 0x42, 0x81, 0x73, 0xff,
+ 0x42, 0x82, 0x74, 0xff, 0x42, 0x81, 0x73, 0xff,
+ 0x2f, 0x63, 0x4a, 0xff, 0x18, 0x3c, 0x29, 0xff,
+ 0x24, 0x50, 0x3a, 0xff, 0x24, 0x50, 0x39, 0xff,
+ 0x2c, 0x68, 0x53, 0xff, 0x37, 0x77, 0x62, 0xff,
+ 0x37, 0x77, 0x63, 0xff, 0x37, 0x77, 0x63, 0xff,
+ 0x34, 0x74, 0x63, 0xff, 0x42, 0x85, 0x73, 0xff,
+ 0x42, 0x86, 0x74, 0xff, 0x34, 0x74, 0x63, 0xff,
+ 0x24, 0x5b, 0x45, 0xff, 0x2e, 0x6c, 0x58, 0xff,
+ 0x19, 0x49, 0x32, 0xff, 0x24, 0x5a, 0x44, 0xff,
+ 0x29, 0x72, 0x5b, 0xff, 0x21, 0x62, 0x4d, 0xff,
+ 0x21, 0x63, 0x4d, 0xff, 0x29, 0x71, 0x5a, 0xff,
+ 0x21, 0x65, 0x4a, 0xff, 0x18, 0x51, 0x39, 0xff,
+ 0x19, 0x51, 0x3a, 0xff, 0x19, 0x51, 0x39, 0xff,
+ 0x29, 0x70, 0x58, 0xff, 0x31, 0x7d, 0x62, 0xff,
+ 0x19, 0x55, 0x42, 0xff, 0x29, 0x70, 0x58, 0xff,
+ 0x27, 0x6a, 0x53, 0xff, 0x26, 0x69, 0x52, 0xff,
+ 0x27, 0x6a, 0x53, 0xff, 0x31, 0x79, 0x63, 0xff,
+ 0x42, 0x8e, 0x7c, 0xff, 0x2e, 0x71, 0x5d, 0xff,
+ 0x1c, 0x55, 0x3f, 0xff, 0x1b, 0x55, 0x3f, 0xff,
+ 0x16, 0x50, 0x37, 0xff, 0x16, 0x4f, 0x37, 0xff,
+ 0x24, 0x67, 0x4d, 0xff, 0x24, 0x66, 0x4d, 0xff,
+ 0x45, 0x83, 0x73, 0xff, 0x44, 0x83, 0x73, 0xff,
+ 0x3f, 0x78, 0x6b, 0xff, 0x3f, 0x78, 0x6a, 0xff,
+ 0x52, 0x8e, 0x84, 0xff, 0x52, 0x8d, 0x83, 0xff,
+ 0x4a, 0x87, 0x7b, 0xff, 0x4a, 0x86, 0x7b, 0xff,
+ 0x3a, 0x7a, 0x60, 0xff, 0x29, 0x61, 0x4a, 0xff,
+ 0x31, 0x6d, 0x55, 0xff, 0x29, 0x61, 0x4a, 0xff,
+ 0x1c, 0x33, 0x24, 0xff, 0x10, 0x18, 0x10, 0xff,
+ 0x10, 0x18, 0x10, 0xff, 0x10, 0x18, 0x10, 0xff,
+ 0x11, 0x29, 0x21, 0xff, 0x41, 0x7d, 0x6b, 0xff,
+ 0x31, 0x61, 0x52, 0xff, 0x41, 0x7d, 0x6a, 0xff,
+ 0x42, 0x82, 0x73, 0xff, 0x41, 0x81, 0x73, 0xff,
+ 0x42, 0x82, 0x73, 0xff, 0x41, 0x81, 0x73, 0xff,
+ 0x24, 0x50, 0x3a, 0xff, 0x23, 0x4f, 0x39, 0xff,
+ 0x2f, 0x63, 0x4a, 0xff, 0x18, 0x3c, 0x29, 0xff,
+ 0x21, 0x59, 0x42, 0xff, 0x2c, 0x68, 0x52, 0xff,
+ 0x42, 0x86, 0x73, 0xff, 0x36, 0x76, 0x62, 0xff,
+ 0x34, 0x74, 0x63, 0xff, 0x41, 0x85, 0x73, 0xff,
+ 0x42, 0x86, 0x73, 0xff, 0x41, 0x85, 0x73, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x39, 0x7d, 0x6b, 0xff,
+ 0x19, 0x49, 0x31, 0xff, 0x18, 0x48, 0x31, 0xff,
+ 0x11, 0x45, 0x32, 0xff, 0x18, 0x53, 0x3f, 0xff,
+ 0x21, 0x63, 0x4d, 0xff, 0x20, 0x62, 0x4c, 0xff,
+ 0x19, 0x51, 0x3a, 0xff, 0x10, 0x3c, 0x29, 0xff,
+ 0x08, 0x29, 0x19, 0xff, 0x10, 0x3c, 0x29, 0xff,
+ 0x29, 0x70, 0x58, 0xff, 0x31, 0x7d, 0x62, 0xff,
+ 0x29, 0x70, 0x58, 0xff, 0x18, 0x55, 0x41, 0xff,
+ 0x1c, 0x59, 0x42, 0xff, 0x26, 0x69, 0x52, 0xff,
+ 0x31, 0x79, 0x63, 0xff, 0x26, 0x69, 0x52, 0xff,
+ 0x2f, 0x71, 0x5d, 0xff, 0x2e, 0x71, 0x5d, 0xff,
+ 0x1b, 0x55, 0x3f, 0xff, 0x08, 0x38, 0x20, 0xff,
+ 0x08, 0x39, 0x21, 0xff, 0x16, 0x4f, 0x36, 0xff,
+ 0x24, 0x67, 0x4d, 0xff, 0x23, 0x66, 0x4c, 0xff,
+ 0x53, 0x8e, 0x84, 0xff, 0x31, 0x79, 0x6b, 0xff,
+ 0x48, 0x87, 0x7c, 0xff, 0x52, 0x8e, 0x83, 0xff,
+ 0x53, 0x92, 0x7c, 0xff, 0x52, 0x92, 0x7b, 0xff,
+ 0x42, 0x82, 0x6b, 0xff, 0x42, 0x81, 0x6b, 0xff,
+ 0x32, 0x6e, 0x5b, 0xff, 0x3f, 0x79, 0x68, 0xff,
+ 0x3f, 0x7a, 0x69, 0xff, 0x31, 0x6d, 0x5a, 0xff,
+ 0x1f, 0x3a, 0x35, 0xff, 0x19, 0x1c, 0x19, 0xff,
+ 0x19, 0x1d, 0x19, 0xff, 0x19, 0x1c, 0x19, 0xff,
+ 0x19, 0x3d, 0x32, 0xff, 0x52, 0x8e, 0x73, 0xff,
+ 0x2c, 0x58, 0x48, 0xff, 0x52, 0x8e, 0x73, 0xff,
+ 0x4b, 0x86, 0x74, 0xff, 0x4a, 0x86, 0x73, 0xff,
+ 0x34, 0x6b, 0x58, 0xff, 0x29, 0x5d, 0x4a, 0xff,
+ 0x19, 0x3d, 0x2a, 0xff, 0x34, 0x6d, 0x5a, 0xff,
+ 0x27, 0x55, 0x42, 0xff, 0x34, 0x6d, 0x5a, 0xff,
+ 0x32, 0x6e, 0x5b, 0xff, 0x31, 0x6d, 0x5a, 0xff,
+ 0x42, 0x81, 0x71, 0xff, 0x42, 0x80, 0x70, 0xff,
+ 0x32, 0x6e, 0x5b, 0xff, 0x34, 0x74, 0x60, 0xff,
+ 0x37, 0x7b, 0x66, 0xff, 0x37, 0x7b, 0x65, 0xff,
+ 0x40, 0x81, 0x6e, 0xff, 0x4a, 0x8e, 0x7b, 0xff,
+ 0x3f, 0x81, 0x6e, 0xff, 0x29, 0x65, 0x52, 0xff,
+ 0x19, 0x5e, 0x4b, 0xff, 0x26, 0x6f, 0x5a, 0xff,
+ 0x34, 0x81, 0x6b, 0xff, 0x34, 0x80, 0x6b, 0xff,
+ 0x16, 0x4c, 0x3a, 0xff, 0x16, 0x4c, 0x3a, 0xff,
+ 0x09, 0x31, 0x21, 0xff, 0x08, 0x30, 0x21, 0xff,
+ 0x2c, 0x77, 0x5e, 0xff, 0x2c, 0x77, 0x5d, 0xff,
+ 0x21, 0x6e, 0x53, 0xff, 0x37, 0x80, 0x68, 0xff,
+ 0x21, 0x5e, 0x45, 0xff, 0x19, 0x4d, 0x31, 0xff,
+ 0x21, 0x5d, 0x45, 0xff, 0x31, 0x7d, 0x6b, 0xff,
+ 0x2c, 0x6a, 0x4d, 0xff, 0x2c, 0x69, 0x4d, 0xff,
+ 0x1f, 0x51, 0x37, 0xff, 0x10, 0x39, 0x21, 0xff,
+ 0x11, 0x21, 0x11, 0xff, 0x13, 0x39, 0x24, 0xff,
+ 0x19, 0x6a, 0x4a, 0xff, 0x19, 0x69, 0x4a, 0xff,
+ 0x31, 0x7a, 0x6b, 0xff, 0x3c, 0x80, 0x73, 0xff,
+ 0x3d, 0x80, 0x73, 0xff, 0x47, 0x87, 0x7b, 0xff,
+ 0x4a, 0x8a, 0x73, 0xff, 0x4a, 0x89, 0x73, 0xff,
+ 0x4a, 0x8a, 0x73, 0xff, 0x42, 0x81, 0x6b, 0xff,
+ 0x3f, 0x7a, 0x68, 0xff, 0x3f, 0x79, 0x68, 0xff,
+ 0x3f, 0x7a, 0x68, 0xff, 0x4c, 0x85, 0x76, 0xff,
+ 0x21, 0x49, 0x42, 0xff, 0x18, 0x1c, 0x18, 0xff,
+ 0x19, 0x1d, 0x19, 0xff, 0x18, 0x1c, 0x18, 0xff,
+ 0x19, 0x3d, 0x31, 0xff, 0x3f, 0x72, 0x5d, 0xff,
+ 0x2c, 0x58, 0x48, 0xff, 0x3f, 0x72, 0x5d, 0xff,
+ 0x3f, 0x78, 0x66, 0xff, 0x3f, 0x78, 0x65, 0xff,
+ 0x3f, 0x78, 0x66, 0xff, 0x29, 0x5d, 0x4a, 0xff,
+ 0x26, 0x55, 0x42, 0xff, 0x34, 0x6d, 0x5a, 0xff,
+ 0x34, 0x6e, 0x5b, 0xff, 0x42, 0x85, 0x73, 0xff,
+ 0x3a, 0x77, 0x66, 0xff, 0x31, 0x6d, 0x5a, 0xff,
+ 0x42, 0x80, 0x71, 0xff, 0x42, 0x80, 0x70, 0xff,
+ 0x37, 0x7b, 0x66, 0xff, 0x34, 0x74, 0x60, 0xff,
+ 0x34, 0x74, 0x60, 0xff, 0x34, 0x74, 0x60, 0xff,
+ 0x34, 0x73, 0x60, 0xff, 0x3f, 0x80, 0x6d, 0xff,
+ 0x4a, 0x8e, 0x7c, 0xff, 0x3f, 0x80, 0x6d, 0xff,
+ 0x19, 0x5d, 0x4a, 0xff, 0x26, 0x6e, 0x5a, 0xff,
+ 0x42, 0x92, 0x7c, 0xff, 0x42, 0x91, 0x7b, 0xff,
+ 0x31, 0x82, 0x6b, 0xff, 0x08, 0x30, 0x20, 0xff,
+ 0x08, 0x31, 0x21, 0xff, 0x16, 0x4b, 0x39, 0xff,
+ 0x21, 0x6d, 0x52, 0xff, 0x2b, 0x76, 0x5d, 0xff,
+ 0x37, 0x80, 0x68, 0xff, 0x37, 0x80, 0x68, 0xff,
+ 0x31, 0x7e, 0x6b, 0xff, 0x20, 0x5d, 0x44, 0xff,
+ 0x19, 0x4d, 0x32, 0xff, 0x29, 0x6d, 0x57, 0xff,
+ 0x3a, 0x82, 0x63, 0xff, 0x2b, 0x69, 0x4c, 0xff,
+ 0x11, 0x39, 0x21, 0xff, 0x10, 0x38, 0x21, 0xff,
+ 0x11, 0x20, 0x11, 0xff, 0x13, 0x38, 0x23, 0xff,
+ 0x13, 0x39, 0x24, 0xff, 0x18, 0x69, 0x4a, 0xff,
+ 0x3d, 0x80, 0x73, 0xff, 0x3c, 0x80, 0x73, 0xff,
+ 0x48, 0x87, 0x7c, 0xff, 0x52, 0x8e, 0x84, 0xff,
+ 0x4a, 0x8a, 0x73, 0xff, 0x4a, 0x89, 0x73, 0xff,
+ 0x42, 0x82, 0x6b, 0xff, 0x42, 0x81, 0x6b, 0xff,
+ 0x3f, 0x7a, 0x68, 0xff, 0x3f, 0x79, 0x68, 0xff,
+ 0x32, 0x6e, 0x5b, 0xff, 0x4d, 0x85, 0x76, 0xff,
+ 0x21, 0x49, 0x42, 0xff, 0x18, 0x1c, 0x18, 0xff,
+ 0x19, 0x1d, 0x19, 0xff, 0x19, 0x1c, 0x19, 0xff,
+ 0x19, 0x3d, 0x32, 0xff, 0x3f, 0x72, 0x5d, 0xff,
+ 0x2c, 0x58, 0x48, 0xff, 0x3f, 0x73, 0x5d, 0xff,
+ 0x4a, 0x86, 0x73, 0xff, 0x3f, 0x78, 0x65, 0xff,
+ 0x3f, 0x78, 0x66, 0xff, 0x29, 0x5d, 0x4a, 0xff,
+ 0x34, 0x6e, 0x5b, 0xff, 0x26, 0x55, 0x42, 0xff,
+ 0x35, 0x6e, 0x5b, 0xff, 0x42, 0x85, 0x73, 0xff,
+ 0x42, 0x80, 0x71, 0xff, 0x39, 0x77, 0x65, 0xff,
+ 0x42, 0x81, 0x71, 0xff, 0x42, 0x80, 0x70, 0xff,
+ 0x37, 0x7b, 0x66, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x35, 0x74, 0x60, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x29, 0x65, 0x53, 0xff, 0x3f, 0x80, 0x6d, 0xff,
+ 0x3f, 0x81, 0x6e, 0xff, 0x4a, 0x8e, 0x7b, 0xff,
+ 0x34, 0x80, 0x6b, 0xff, 0x26, 0x6e, 0x5a, 0xff,
+ 0x42, 0x92, 0x7c, 0xff, 0x42, 0x92, 0x7b, 0xff,
+ 0x32, 0x82, 0x6b, 0xff, 0x16, 0x4b, 0x39, 0xff,
+ 0x16, 0x4c, 0x3a, 0xff, 0x16, 0x4b, 0x39, 0xff,
+ 0x2c, 0x77, 0x5e, 0xff, 0x37, 0x80, 0x68, 0xff,
+ 0x2c, 0x77, 0x5e, 0xff, 0x42, 0x8a, 0x73, 0xff,
+ 0x32, 0x7e, 0x6b, 0xff, 0x29, 0x6d, 0x58, 0xff,
+ 0x21, 0x5e, 0x45, 0xff, 0x29, 0x6d, 0x58, 0xff,
+ 0x3a, 0x82, 0x63, 0xff, 0x1e, 0x51, 0x37, 0xff,
+ 0x11, 0x39, 0x21, 0xff, 0x10, 0x39, 0x21, 0xff,
+ 0x13, 0x39, 0x24, 0xff, 0x13, 0x38, 0x23, 0xff,
+ 0x16, 0x51, 0x37, 0xff, 0x16, 0x51, 0x37, 0xff,
+ 0x32, 0x7a, 0x6b, 0xff, 0x3c, 0x80, 0x73, 0xff,
+ 0x52, 0x8e, 0x84, 0xff, 0x47, 0x86, 0x7b, 0xff,
+ 0x42, 0x82, 0x6b, 0xff, 0x41, 0x81, 0x6b, 0xff,
+ 0x4a, 0x8a, 0x73, 0xff, 0x39, 0x79, 0x62, 0xff,
+ 0x32, 0x6d, 0x5b, 0xff, 0x4c, 0x85, 0x76, 0xff,
+ 0x5b, 0x92, 0x84, 0xff, 0x5a, 0x91, 0x83, 0xff,
+ 0x21, 0x49, 0x42, 0xff, 0x18, 0x1c, 0x18, 0xff,
+ 0x19, 0x1c, 0x19, 0xff, 0x18, 0x1c, 0x18, 0xff,
+ 0x3f, 0x73, 0x5d, 0xff, 0x3f, 0x72, 0x5d, 0xff,
+ 0x2c, 0x58, 0x47, 0xff, 0x3f, 0x72, 0x5d, 0xff,
+ 0x4a, 0x86, 0x73, 0xff, 0x3f, 0x78, 0x65, 0xff,
+ 0x29, 0x5d, 0x4a, 0xff, 0x29, 0x5d, 0x4a, 0xff,
+ 0x27, 0x55, 0x42, 0xff, 0x34, 0x6d, 0x5a, 0xff,
+ 0x34, 0x6d, 0x5b, 0xff, 0x34, 0x6d, 0x5a, 0xff,
+ 0x4a, 0x8a, 0x7c, 0xff, 0x41, 0x80, 0x70, 0xff,
+ 0x42, 0x80, 0x70, 0xff, 0x39, 0x76, 0x65, 0xff,
+ 0x37, 0x7b, 0x66, 0xff, 0x36, 0x7a, 0x65, 0xff,
+ 0x34, 0x74, 0x60, 0xff, 0x36, 0x7a, 0x65, 0xff,
+ 0x34, 0x73, 0x60, 0xff, 0x34, 0x72, 0x60, 0xff,
+ 0x3f, 0x80, 0x6e, 0xff, 0x3f, 0x80, 0x6d, 0xff,
+ 0x34, 0x80, 0x6b, 0xff, 0x41, 0x91, 0x7b, 0xff,
+ 0x42, 0x92, 0x7b, 0xff, 0x34, 0x80, 0x6a, 0xff,
+ 0x32, 0x82, 0x6b, 0xff, 0x23, 0x66, 0x52, 0xff,
+ 0x24, 0x67, 0x52, 0xff, 0x15, 0x4b, 0x39, 0xff,
+ 0x21, 0x6d, 0x52, 0xff, 0x36, 0x80, 0x68, 0xff,
+ 0x21, 0x6d, 0x52, 0xff, 0x36, 0x80, 0x68, 0xff,
+ 0x32, 0x7e, 0x6b, 0xff, 0x31, 0x7d, 0x6b, 0xff,
+ 0x31, 0x7e, 0x6b, 0xff, 0x29, 0x6d, 0x57, 0xff,
+ 0x2c, 0x69, 0x4d, 0xff, 0x2c, 0x69, 0x4c, 0xff,
+ 0x1e, 0x51, 0x37, 0xff, 0x1e, 0x50, 0x36, 0xff,
+ 0x13, 0x39, 0x24, 0xff, 0x16, 0x51, 0x36, 0xff,
+ 0x16, 0x51, 0x37, 0xff, 0x15, 0x50, 0x36, 0xff,
+ 0x42, 0x82, 0x74, 0xff, 0x47, 0x88, 0x79, 0xff,
+ 0x4d, 0x8f, 0x7e, 0xff, 0x47, 0x88, 0x78, 0xff,
+ 0x4d, 0x8b, 0x7c, 0xff, 0x47, 0x84, 0x73, 0xff,
+ 0x4d, 0x8b, 0x7c, 0xff, 0x47, 0x84, 0x73, 0xff,
+ 0x55, 0x92, 0x81, 0xff, 0x5a, 0x9a, 0x8c, 0xff,
+ 0x50, 0x8a, 0x76, 0xff, 0x55, 0x92, 0x81, 0xff,
+ 0x21, 0x4d, 0x3a, 0xff, 0x10, 0x20, 0x19, 0xff,
+ 0x11, 0x21, 0x19, 0xff, 0x16, 0x2f, 0x23, 0xff,
+ 0x35, 0x6b, 0x55, 0xff, 0x34, 0x6b, 0x55, 0xff,
+ 0x21, 0x59, 0x42, 0xff, 0x47, 0x7c, 0x68, 0xff,
+ 0x4b, 0x82, 0x6b, 0xff, 0x21, 0x49, 0x3a, 0xff,
+ 0x21, 0x49, 0x3a, 0xff, 0x21, 0x49, 0x39, 0xff,
+ 0x2a, 0x5e, 0x53, 0xff, 0x4f, 0x83, 0x73, 0xff,
+ 0x3d, 0x70, 0x63, 0xff, 0x29, 0x5d, 0x52, 0xff,
+ 0x3d, 0x72, 0x66, 0xff, 0x47, 0x7d, 0x70, 0xff,
+ 0x53, 0x8a, 0x7c, 0xff, 0x47, 0x7d, 0x70, 0xff,
+ 0x42, 0x7b, 0x69, 0xff, 0x42, 0x7b, 0x68, 0xff,
+ 0x42, 0x7b, 0x69, 0xff, 0x42, 0x7b, 0x68, 0xff,
+ 0x2a, 0x6a, 0x53, 0xff, 0x29, 0x69, 0x52, 0xff,
+ 0x45, 0x7f, 0x69, 0xff, 0x37, 0x74, 0x5d, 0xff,
+ 0x42, 0x8a, 0x6b, 0xff, 0x34, 0x78, 0x5d, 0xff,
+ 0x42, 0x8a, 0x6b, 0xff, 0x42, 0x89, 0x6b, 0xff,
+ 0x2f, 0x76, 0x5e, 0xff, 0x42, 0x86, 0x6b, 0xff,
+ 0x2f, 0x76, 0x5e, 0xff, 0x2e, 0x75, 0x5d, 0xff,
+ 0x32, 0x77, 0x63, 0xff, 0x31, 0x77, 0x63, 0xff,
+ 0x32, 0x77, 0x63, 0xff, 0x31, 0x77, 0x63, 0xff,
+ 0x2c, 0x6e, 0x5b, 0xff, 0x3a, 0x8a, 0x73, 0xff,
+ 0x3a, 0x8a, 0x74, 0xff, 0x2c, 0x6d, 0x5a, 0xff,
+ 0x24, 0x6c, 0x58, 0xff, 0x24, 0x6c, 0x58, 0xff,
+ 0x19, 0x5d, 0x4a, 0xff, 0x19, 0x5d, 0x4a, 0xff,
+ 0x19, 0x5b, 0x48, 0xff, 0x08, 0x45, 0x31, 0xff,
+ 0x19, 0x5b, 0x48, 0xff, 0x08, 0x45, 0x31, 0xff,
+ 0x4d, 0x8f, 0x7e, 0xff, 0x52, 0x95, 0x83, 0xff,
+ 0x4d, 0x8f, 0x7e, 0xff, 0x4c, 0x8f, 0x7e, 0xff,
+ 0x4d, 0x8b, 0x7b, 0xff, 0x4c, 0x8b, 0x7b, 0xff,
+ 0x4d, 0x8b, 0x7c, 0xff, 0x4c, 0x8b, 0x7b, 0xff,
+ 0x5b, 0x9a, 0x8c, 0xff, 0x55, 0x91, 0x80, 0xff,
+ 0x4a, 0x82, 0x6b, 0xff, 0x55, 0x91, 0x81, 0xff,
+ 0x1c, 0x3e, 0x2f, 0xff, 0x10, 0x20, 0x18, 0xff,
+ 0x11, 0x21, 0x19, 0xff, 0x16, 0x2f, 0x23, 0xff,
+ 0x47, 0x7c, 0x68, 0xff, 0x47, 0x7c, 0x68, 0xff,
+ 0x21, 0x59, 0x42, 0xff, 0x47, 0x7c, 0x68, 0xff,
+ 0x3c, 0x6f, 0x5b, 0xff, 0x20, 0x48, 0x39, 0xff,
+ 0x21, 0x49, 0x3a, 0xff, 0x21, 0x49, 0x39, 0xff,
+ 0x50, 0x83, 0x73, 0xff, 0x4f, 0x82, 0x73, 0xff,
+ 0x50, 0x83, 0x73, 0xff, 0x3c, 0x70, 0x62, 0xff,
+ 0x3c, 0x71, 0x66, 0xff, 0x3c, 0x71, 0x65, 0xff,
+ 0x48, 0x7e, 0x71, 0xff, 0x47, 0x7d, 0x70, 0xff,
+ 0x42, 0x7b, 0x68, 0xff, 0x41, 0x7a, 0x68, 0xff,
+ 0x42, 0x7b, 0x68, 0xff, 0x42, 0x7a, 0x68, 0xff,
+ 0x29, 0x69, 0x52, 0xff, 0x29, 0x69, 0x52, 0xff,
+ 0x45, 0x7f, 0x68, 0xff, 0x37, 0x74, 0x5d, 0xff,
+ 0x26, 0x67, 0x50, 0xff, 0x34, 0x78, 0x5d, 0xff,
+ 0x34, 0x78, 0x5d, 0xff, 0x34, 0x78, 0x5d, 0xff,
+ 0x2f, 0x75, 0x5d, 0xff, 0x41, 0x85, 0x6b, 0xff,
+ 0x2f, 0x76, 0x5d, 0xff, 0x08, 0x55, 0x42, 0xff,
+ 0x31, 0x77, 0x63, 0xff, 0x31, 0x76, 0x62, 0xff,
+ 0x32, 0x77, 0x63, 0xff, 0x21, 0x5b, 0x4a, 0xff,
+ 0x1e, 0x51, 0x42, 0xff, 0x2b, 0x6d, 0x5a, 0xff,
+ 0x2c, 0x6e, 0x5b, 0xff, 0x2c, 0x6d, 0x5a, 0xff,
+ 0x24, 0x6c, 0x58, 0xff, 0x2e, 0x7a, 0x65, 0xff,
+ 0x19, 0x5d, 0x4a, 0xff, 0x2e, 0x7a, 0x65, 0xff,
+ 0x29, 0x70, 0x5d, 0xff, 0x29, 0x70, 0x5d, 0xff,
+ 0x19, 0x5b, 0x48, 0xff, 0x18, 0x5a, 0x47, 0xff,
+ 0x48, 0x89, 0x79, 0xff, 0x4d, 0x8f, 0x7e, 0xff,
+ 0x4d, 0x8f, 0x7f, 0xff, 0x52, 0x96, 0x84, 0xff,
+ 0x48, 0x85, 0x73, 0xff, 0x42, 0x7d, 0x6b, 0xff,
+ 0x53, 0x92, 0x84, 0xff, 0x52, 0x92, 0x84, 0xff,
+ 0x5b, 0x9a, 0x8c, 0xff, 0x4f, 0x89, 0x76, 0xff,
+ 0x55, 0x92, 0x81, 0xff, 0x4f, 0x8a, 0x76, 0xff,
+ 0x21, 0x4d, 0x3a, 0xff, 0x16, 0x2f, 0x23, 0xff,
+ 0x11, 0x21, 0x19, 0xff, 0x1b, 0x3e, 0x2f, 0xff,
+ 0x5b, 0x8e, 0x7c, 0xff, 0x47, 0x7c, 0x68, 0xff,
+ 0x21, 0x59, 0x42, 0xff, 0x47, 0x7c, 0x68, 0xff,
+ 0x2f, 0x5c, 0x4a, 0xff, 0x21, 0x49, 0x39, 0xff,
+ 0x21, 0x49, 0x3a, 0xff, 0x2f, 0x5c, 0x4a, 0xff,
+ 0x3d, 0x70, 0x63, 0xff, 0x4f, 0x83, 0x73, 0xff,
+ 0x50, 0x83, 0x74, 0xff, 0x4f, 0x83, 0x73, 0xff,
+ 0x32, 0x65, 0x5b, 0xff, 0x31, 0x65, 0x5a, 0xff,
+ 0x48, 0x7e, 0x71, 0xff, 0x52, 0x8a, 0x7b, 0xff,
+ 0x42, 0x7b, 0x68, 0xff, 0x31, 0x6c, 0x55, 0xff,
+ 0x21, 0x5e, 0x42, 0xff, 0x31, 0x6c, 0x55, 0xff,
+ 0x37, 0x74, 0x5e, 0xff, 0x37, 0x74, 0x5d, 0xff,
+ 0x37, 0x74, 0x5e, 0xff, 0x44, 0x7f, 0x68, 0xff,
+ 0x27, 0x67, 0x50, 0xff, 0x18, 0x55, 0x42, 0xff,
+ 0x19, 0x55, 0x42, 0xff, 0x34, 0x78, 0x5d, 0xff,
+ 0x2f, 0x76, 0x5e, 0xff, 0x2e, 0x75, 0x5d, 0xff,
+ 0x2f, 0x76, 0x5e, 0xff, 0x08, 0x55, 0x42, 0xff,
+ 0x32, 0x77, 0x63, 0xff, 0x31, 0x77, 0x62, 0xff,
+ 0x21, 0x5c, 0x4a, 0xff, 0x10, 0x41, 0x31, 0xff,
+ 0x11, 0x35, 0x29, 0xff, 0x1e, 0x51, 0x42, 0xff,
+ 0x3a, 0x8a, 0x74, 0xff, 0x2c, 0x6d, 0x5a, 0xff,
+ 0x2f, 0x7b, 0x66, 0xff, 0x23, 0x6c, 0x58, 0xff,
+ 0x2f, 0x7b, 0x66, 0xff, 0x24, 0x6c, 0x58, 0xff,
+ 0x29, 0x70, 0x5e, 0xff, 0x29, 0x70, 0x5d, 0xff,
+ 0x19, 0x5b, 0x48, 0xff, 0x08, 0x45, 0x31, 0xff,
+ 0x47, 0x88, 0x79, 0xff, 0x47, 0x88, 0x78, 0xff,
+ 0x42, 0x82, 0x73, 0xff, 0x41, 0x81, 0x73, 0xff,
+ 0x42, 0x7e, 0x6b, 0xff, 0x41, 0x7d, 0x6b, 0xff,
+ 0x4d, 0x8b, 0x7b, 0xff, 0x4c, 0x8a, 0x7b, 0xff,
+ 0x4a, 0x82, 0x6b, 0xff, 0x4a, 0x81, 0x6b, 0xff,
+ 0x55, 0x92, 0x81, 0xff, 0x4a, 0x81, 0x6a, 0xff,
+ 0x21, 0x4d, 0x3a, 0xff, 0x16, 0x2f, 0x23, 0xff,
+ 0x16, 0x2f, 0x24, 0xff, 0x20, 0x4c, 0x39, 0xff,
+ 0x47, 0x7c, 0x68, 0xff, 0x47, 0x7c, 0x68, 0xff,
+ 0x34, 0x6b, 0x55, 0xff, 0x5a, 0x8d, 0x7b, 0xff,
+ 0x21, 0x49, 0x3a, 0xff, 0x2e, 0x5b, 0x4a, 0xff,
+ 0x3c, 0x6f, 0x5b, 0xff, 0x4a, 0x81, 0x6a, 0xff,
+ 0x50, 0x83, 0x73, 0xff, 0x62, 0x95, 0x83, 0xff,
+ 0x63, 0x96, 0x84, 0xff, 0x62, 0x95, 0x83, 0xff,
+ 0x52, 0x8a, 0x7c, 0xff, 0x3c, 0x71, 0x65, 0xff,
+ 0x52, 0x8a, 0x7b, 0xff, 0x52, 0x89, 0x7b, 0xff,
+ 0x52, 0x8a, 0x7c, 0xff, 0x52, 0x89, 0x7b, 0xff,
+ 0x31, 0x6c, 0x55, 0xff, 0x31, 0x6b, 0x55, 0xff,
+ 0x45, 0x7f, 0x68, 0xff, 0x44, 0x7e, 0x68, 0xff,
+ 0x45, 0x7f, 0x68, 0xff, 0x52, 0x89, 0x73, 0xff,
+ 0x34, 0x78, 0x5d, 0xff, 0x18, 0x55, 0x41, 0xff,
+ 0x34, 0x78, 0x5d, 0xff, 0x34, 0x78, 0x5d, 0xff,
+ 0x2f, 0x76, 0x5d, 0xff, 0x41, 0x85, 0x6b, 0xff,
+ 0x2f, 0x75, 0x5d, 0xff, 0x2e, 0x75, 0x5d, 0xff,
+ 0x42, 0x92, 0x7c, 0xff, 0x41, 0x91, 0x7b, 0xff,
+ 0x42, 0x92, 0x7b, 0xff, 0x31, 0x76, 0x62, 0xff,
+ 0x2c, 0x6d, 0x5b, 0xff, 0x2c, 0x6d, 0x5a, 0xff,
+ 0x2c, 0x6d, 0x5b, 0xff, 0x2b, 0x6d, 0x5a, 0xff,
+ 0x2f, 0x7b, 0x66, 0xff, 0x39, 0x89, 0x73, 0xff,
+ 0x2f, 0x7b, 0x65, 0xff, 0x2e, 0x7a, 0x65, 0xff,
+ 0x3a, 0x86, 0x73, 0xff, 0x39, 0x85, 0x73, 0xff,
+ 0x29, 0x70, 0x5d, 0xff, 0x29, 0x70, 0x5d, 0xff,
+ 0x2a, 0x28, 0x1c, 0xff, 0x29, 0x27, 0x1b, 0xff,
+ 0x29, 0x27, 0x1c, 0xff, 0x31, 0x30, 0x21, 0xff,
+ 0x42, 0x35, 0x21, 0xff, 0x42, 0x35, 0x21, 0xff,
+ 0x37, 0x2c, 0x1c, 0xff, 0x42, 0x34, 0x21, 0xff,
+ 0x40, 0x34, 0x1c, 0xff, 0x4d, 0x46, 0x2f, 0xff,
+ 0x5b, 0x59, 0x42, 0xff, 0x4d, 0x46, 0x2e, 0xff,
+ 0x55, 0x4b, 0x2f, 0xff, 0x3a, 0x35, 0x19, 0xff,
+ 0x3a, 0x35, 0x19, 0xff, 0x39, 0x34, 0x19, 0xff,
+ 0x53, 0x41, 0x2a, 0xff, 0x52, 0x41, 0x29, 0xff,
+ 0x84, 0x67, 0x4a, 0xff, 0x9c, 0x79, 0x5a, 0xff,
+ 0x92, 0x8b, 0x79, 0xff, 0x91, 0x8b, 0x79, 0xff,
+ 0x92, 0x8b, 0x79, 0xff, 0xee, 0xe7, 0xd6, 0xff,
+ 0xf5, 0xf7, 0xf5, 0xff, 0xef, 0xf3, 0xef, 0xff,
+ 0xf4, 0xf7, 0xf4, 0xff, 0xee, 0xf3, 0xee, 0xff,
+ 0xef, 0xef, 0xef, 0xff, 0xf4, 0xf4, 0xf4, 0xff,
+ 0xf4, 0xf5, 0xf4, 0xff, 0xf4, 0xf4, 0xf4, 0xff,
+ 0xf5, 0xf5, 0xf5, 0xff, 0xf4, 0xf4, 0xf4, 0xff,
+ 0xef, 0xef, 0xef, 0xff, 0xee, 0xef, 0xee, 0xff,
+ 0xef, 0xf3, 0xef, 0xff, 0xef, 0xf3, 0xef, 0xff,
+ 0xef, 0xf3, 0xef, 0xff, 0xee, 0xf3, 0xee, 0xff,
+ 0xe7, 0xef, 0xef, 0xff, 0xe6, 0xef, 0xef, 0xff,
+ 0xef, 0xf5, 0xf4, 0xff, 0xee, 0xf4, 0xf4, 0xff,
+ 0xe7, 0xef, 0xef, 0xff, 0xef, 0xf4, 0xf4, 0xff,
+ 0xef, 0xf5, 0xf4, 0xff, 0xee, 0xf4, 0xf4, 0xff,
+ 0xef, 0xf3, 0xf7, 0xff, 0xf4, 0xf7, 0xf9, 0xff,
+ 0xef, 0xf3, 0xf7, 0xff, 0xf9, 0xfb, 0xfc, 0xff,
+ 0xfa, 0xfa, 0xfa, 0xff, 0xef, 0xef, 0xef, 0xff,
+ 0xf4, 0xf5, 0xf4, 0xff, 0xee, 0xef, 0xee, 0xff,
+ 0xef, 0xf3, 0xef, 0xff, 0xef, 0xf3, 0xef, 0xff,
+ 0xef, 0xf3, 0xef, 0xff, 0xee, 0xf3, 0xee, 0xff,
+ 0xf5, 0xef, 0xec, 0xff, 0xf4, 0xef, 0xec, 0xff,
+ 0xf4, 0xef, 0xec, 0xff, 0xde, 0xce, 0xc5, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x21, 0x1e, 0x16, 0xff, 0x29, 0x27, 0x1b, 0xff,
+ 0x37, 0x2b, 0x1c, 0xff, 0x2b, 0x21, 0x16, 0xff,
+ 0x2c, 0x22, 0x16, 0xff, 0x37, 0x2b, 0x1b, 0xff,
+ 0x3f, 0x33, 0x1c, 0xff, 0x4c, 0x46, 0x2e, 0xff,
+ 0x5b, 0x59, 0x42, 0xff, 0x4c, 0x46, 0x2e, 0xff,
+ 0x55, 0x4a, 0x2f, 0xff, 0x55, 0x4a, 0x2e, 0xff,
+ 0x55, 0x4a, 0x2f, 0xff, 0x70, 0x60, 0x44, 0xff,
+ 0x6b, 0x54, 0x3a, 0xff, 0x6b, 0x53, 0x39, 0xff,
+ 0x6b, 0x54, 0x3a, 0xff, 0x83, 0x66, 0x4a, 0xff,
+ 0x63, 0x5d, 0x4a, 0xff, 0x91, 0x8b, 0x78, 0xff,
+ 0x92, 0x8b, 0x79, 0xff, 0xee, 0xe6, 0xd6, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf9, 0xfb, 0xf9, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfa, 0xfa, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xde, 0xce, 0xc5, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x21, 0x1d, 0x16, 0xff,
+ 0x21, 0x1e, 0x16, 0xff, 0x21, 0x1e, 0x16, 0xff,
+ 0x2c, 0x22, 0x16, 0xff, 0x2c, 0x22, 0x16, 0xff,
+ 0x2c, 0x22, 0x16, 0xff, 0x2c, 0x22, 0x16, 0xff,
+ 0x32, 0x21, 0x09, 0xff, 0x3f, 0x33, 0x1b, 0xff,
+ 0x3f, 0x34, 0x1c, 0xff, 0x4d, 0x46, 0x2f, 0xff,
+ 0x55, 0x4a, 0x2f, 0xff, 0x55, 0x4a, 0x2e, 0xff,
+ 0x8c, 0x76, 0x5b, 0xff, 0x8c, 0x75, 0x5a, 0xff,
+ 0x9d, 0x7a, 0x5b, 0xff, 0x9c, 0x79, 0x5a, 0xff,
+ 0x84, 0x67, 0x4a, 0xff, 0x52, 0x41, 0x29, 0xff,
+ 0x63, 0x5d, 0x4a, 0xff, 0x62, 0x5d, 0x4a, 0xff,
+ 0x92, 0x8b, 0x79, 0xff, 0xee, 0xe7, 0xd6, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf9, 0xfb, 0xf9, 0xff,
+ 0xfa, 0xfb, 0xfa, 0xff, 0xf9, 0xfb, 0xf9, 0xff,
+ 0xfa, 0xfa, 0xfa, 0xff, 0xf9, 0xf9, 0xf9, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf9, 0xfa, 0xf9, 0xff,
+ 0xfa, 0xfa, 0xfa, 0xff, 0xf9, 0xf9, 0xf9, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf9, 0xfa, 0xf9, 0xff,
+ 0xfa, 0xfb, 0xfa, 0xff, 0xf9, 0xfb, 0xf9, 0xff,
+ 0xfa, 0xfb, 0xfa, 0xff, 0xf9, 0xfb, 0xf9, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf7, 0xf9, 0xf9, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf7, 0xfa, 0xf9, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf7, 0xf9, 0xf9, 0xff,
+ 0xf7, 0xfa, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfa, 0xfb, 0xfd, 0xff, 0xf9, 0xfb, 0xfc, 0xff,
+ 0xfa, 0xfb, 0xfd, 0xff, 0xf9, 0xfb, 0xfc, 0xff,
+ 0xfa, 0xfa, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfa, 0xfa, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfa, 0xfb, 0xfa, 0xff, 0xf9, 0xfb, 0xf9, 0xff,
+ 0xfa, 0xfb, 0xfa, 0xff, 0xf9, 0xfb, 0xf9, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf4, 0xef, 0xec, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x19, 0x14, 0x10, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x21, 0x18, 0x11, 0xff, 0x2c, 0x21, 0x16, 0xff,
+ 0x21, 0x18, 0x10, 0xff, 0x20, 0x18, 0x10, 0xff,
+ 0x32, 0x21, 0x08, 0xff, 0x31, 0x20, 0x08, 0xff,
+ 0x3f, 0x33, 0x1b, 0xff, 0x3f, 0x33, 0x1b, 0xff,
+ 0x55, 0x4a, 0x2f, 0xff, 0x55, 0x4a, 0x2e, 0xff,
+ 0x55, 0x4a, 0x2f, 0xff, 0x70, 0x5f, 0x44, 0xff,
+ 0x9c, 0x7a, 0x5b, 0xff, 0x9c, 0x79, 0x5a, 0xff,
+ 0x6b, 0x54, 0x3a, 0xff, 0x52, 0x40, 0x29, 0xff,
+ 0x63, 0x5d, 0x4a, 0xff, 0x62, 0x5d, 0x4a, 0xff,
+ 0x91, 0x8b, 0x79, 0xff, 0xee, 0xe6, 0xd5, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf9, 0xfb, 0xf9, 0xff,
+ 0xfa, 0xfb, 0xfa, 0xff, 0xf9, 0xfa, 0xf9, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf9, 0xf9, 0xf9, 0xff,
+ 0xfa, 0xfa, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf9, 0xf9, 0xf9, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf9, 0xf9, 0xf9, 0xff,
+ 0xfa, 0xfb, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfa, 0xfb, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xf7, 0xfa, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xf7, 0xfa, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xf7, 0xfa, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xf7, 0xfa, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfa, 0xfb, 0xfc, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfa, 0xfb, 0xfc, 0xff, 0xf9, 0xfa, 0xfc, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf9, 0xf9, 0xf9, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf9, 0xf9, 0xf9, 0xff,
+ 0xfa, 0xfb, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfa, 0xfb, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xf4, 0xef, 0xec, 0xff, 0xe9, 0xde, 0xd8, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x19, 0x14, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x19, 0x14, 0x10, 0xff,
+ 0x21, 0x1d, 0x11, 0xff, 0x63, 0x49, 0x31, 0xff,
+ 0x37, 0x2c, 0x1c, 0xff, 0x21, 0x1c, 0x10, 0xff,
+ 0x27, 0x20, 0x14, 0xff, 0x2c, 0x22, 0x16, 0xff,
+ 0x2c, 0x22, 0x16, 0xff, 0x31, 0x24, 0x19, 0xff,
+ 0x32, 0x29, 0x11, 0xff, 0x73, 0x55, 0x3a, 0xff,
+ 0x5e, 0x47, 0x2c, 0xff, 0x5d, 0x46, 0x2c, 0xff,
+ 0x84, 0x66, 0x48, 0xff, 0x9c, 0x75, 0x5a, 0xff,
+ 0x6b, 0x55, 0x34, 0xff, 0x6b, 0x55, 0x34, 0xff,
+ 0x53, 0x51, 0x32, 0xff, 0x81, 0x80, 0x63, 0xff,
+ 0x81, 0x81, 0x63, 0xff, 0xde, 0xde, 0xc5, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf7, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf7, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfb, 0xfa, 0xff, 0xfc, 0xfb, 0xf9, 0xff,
+ 0xfd, 0xfb, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xde, 0xd4, 0xce, 0xff, 0xcd, 0xbe, 0xb5, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x1b, 0x17, 0x13, 0xff,
+ 0x1c, 0x17, 0x13, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x21, 0x1c, 0x11, 0xff, 0x4c, 0x3a, 0x26, 0xff,
+ 0x4d, 0x3a, 0x27, 0xff, 0x21, 0x1c, 0x10, 0xff,
+ 0x26, 0x1f, 0x13, 0xff, 0x2b, 0x21, 0x16, 0xff,
+ 0x27, 0x1f, 0x13, 0xff, 0x31, 0x24, 0x18, 0xff,
+ 0x31, 0x29, 0x11, 0xff, 0x5d, 0x46, 0x2b, 0xff,
+ 0x73, 0x55, 0x3a, 0xff, 0x5d, 0x46, 0x2c, 0xff,
+ 0x6b, 0x55, 0x34, 0xff, 0x9c, 0x75, 0x5a, 0xff,
+ 0x6b, 0x55, 0x34, 0xff, 0x6b, 0x55, 0x34, 0xff,
+ 0x52, 0x51, 0x31, 0xff, 0x52, 0x51, 0x31, 0xff,
+ 0x81, 0x80, 0x63, 0xff, 0xaf, 0xaf, 0x94, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf6, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf6, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfd, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfd, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfd, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfd, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfd, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfd, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfb, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfc, 0xfb, 0xfa, 0xff, 0xfc, 0xfb, 0xf9, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfd, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xef, 0xea, 0xe7, 0xff, 0xde, 0xd4, 0xcd, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x1b, 0x17, 0x13, 0xff,
+ 0x1f, 0x1a, 0x16, 0xff, 0x21, 0x1c, 0x19, 0xff,
+ 0x21, 0x1d, 0x11, 0xff, 0x21, 0x1c, 0x10, 0xff,
+ 0x37, 0x2c, 0x1c, 0xff, 0x21, 0x1c, 0x10, 0xff,
+ 0x27, 0x1f, 0x13, 0xff, 0x26, 0x1f, 0x13, 0xff,
+ 0x27, 0x1f, 0x14, 0xff, 0x2c, 0x22, 0x16, 0xff,
+ 0x32, 0x29, 0x11, 0xff, 0x31, 0x28, 0x10, 0xff,
+ 0x48, 0x38, 0x1f, 0xff, 0x5d, 0x46, 0x2c, 0xff,
+ 0x9d, 0x76, 0x5b, 0xff, 0x83, 0x65, 0x47, 0xff,
+ 0x84, 0x66, 0x48, 0xff, 0x6b, 0x55, 0x34, 0xff,
+ 0x53, 0x51, 0x32, 0xff, 0x52, 0x51, 0x31, 0xff,
+ 0x81, 0x81, 0x63, 0xff, 0x81, 0x80, 0x63, 0xff,
+ 0xb3, 0xb0, 0x9a, 0xff, 0xff, 0xfb, 0xf7, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf7, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfb, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfd, 0xfb, 0xfa, 0xff, 0xf7, 0xf3, 0xee, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xef, 0xea, 0xe7, 0xff, 0xce, 0xbe, 0xb5, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x19, 0x14, 0x10, 0xff, 0x1e, 0x19, 0x15, 0xff,
+ 0x21, 0x1c, 0x11, 0xff, 0x21, 0x1c, 0x10, 0xff,
+ 0x21, 0x1c, 0x10, 0xff, 0x36, 0x2b, 0x1b, 0xff,
+ 0x27, 0x1f, 0x13, 0xff, 0x31, 0x24, 0x18, 0xff,
+ 0x2c, 0x22, 0x16, 0xff, 0x2b, 0x21, 0x15, 0xff,
+ 0x32, 0x29, 0x11, 0xff, 0x31, 0x28, 0x10, 0xff,
+ 0x31, 0x29, 0x10, 0xff, 0x47, 0x37, 0x1e, 0xff,
+ 0x84, 0x65, 0x47, 0xff, 0x83, 0x65, 0x47, 0xff,
+ 0x52, 0x45, 0x21, 0xff, 0x52, 0x44, 0x20, 0xff,
+ 0x52, 0x51, 0x32, 0xff, 0x52, 0x51, 0x31, 0xff,
+ 0x81, 0x80, 0x63, 0xff, 0x80, 0x80, 0x62, 0xff,
+ 0x8c, 0x8a, 0x6b, 0xff, 0xb2, 0xaf, 0x99, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfa, 0xf6, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfb, 0xfa, 0xff, 0xfc, 0xfb, 0xf9, 0xff,
+ 0xfc, 0xfb, 0xfa, 0xff, 0xf9, 0xf6, 0xf4, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xf9, 0xfd, 0xf9, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xde, 0xd3, 0xcd, 0xff,
+ 0x1c, 0x13, 0x11, 0xff, 0x1b, 0x13, 0x10, 0xff,
+ 0x1c, 0x13, 0x11, 0xff, 0x1e, 0x15, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x19, 0x14, 0x10, 0xff,
+ 0x21, 0x1e, 0x16, 0xff, 0x21, 0x1e, 0x16, 0xff,
+ 0x21, 0x1d, 0x11, 0xff, 0x34, 0x2b, 0x1b, 0xff,
+ 0x48, 0x3a, 0x27, 0xff, 0x5a, 0x49, 0x31, 0xff,
+ 0x3d, 0x32, 0x19, 0xff, 0x31, 0x28, 0x10, 0xff,
+ 0x32, 0x29, 0x11, 0xff, 0x31, 0x28, 0x10, 0xff,
+ 0x3a, 0x29, 0x11, 0xff, 0x63, 0x4d, 0x34, 0xff,
+ 0x63, 0x4d, 0x34, 0xff, 0x39, 0x28, 0x10, 0xff,
+ 0x4b, 0x3d, 0x21, 0xff, 0x4a, 0x3d, 0x21, 0xff,
+ 0x58, 0x4b, 0x2f, 0xff, 0x65, 0x58, 0x3c, 0xff,
+ 0x92, 0x8d, 0x79, 0xff, 0x91, 0x8c, 0x79, 0xff,
+ 0xef, 0xeb, 0xe7, 0xff, 0xee, 0xeb, 0xe6, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xf7, 0xeb, 0xdf, 0xff, 0xe1, 0xd2, 0xc3, 0xff,
+ 0xf7, 0xeb, 0xde, 0xff, 0xf7, 0xeb, 0xde, 0xff,
+ 0xff, 0xf7, 0xef, 0xff, 0xff, 0xf7, 0xef, 0xff,
+ 0xff, 0xf7, 0xef, 0xff, 0xc8, 0xb6, 0xa7, 0xff,
+ 0x1c, 0x13, 0x11, 0xff, 0x1b, 0x12, 0x10, 0xff,
+ 0x19, 0x10, 0x11, 0xff, 0x1b, 0x13, 0x10, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x21, 0x1d, 0x16, 0xff,
+ 0x21, 0x1c, 0x11, 0xff, 0x20, 0x1c, 0x10, 0xff,
+ 0x34, 0x2b, 0x1c, 0xff, 0x5a, 0x49, 0x31, 0xff,
+ 0x47, 0x3b, 0x21, 0xff, 0x47, 0x3b, 0x20, 0xff,
+ 0x32, 0x29, 0x11, 0xff, 0x31, 0x28, 0x10, 0xff,
+ 0x63, 0x4d, 0x34, 0xff, 0x62, 0x4c, 0x34, 0xff,
+ 0x8c, 0x72, 0x58, 0xff, 0x39, 0x28, 0x10, 0xff,
+ 0x4a, 0x3d, 0x21, 0xff, 0x4a, 0x3c, 0x20, 0xff,
+ 0x4a, 0x3d, 0x21, 0xff, 0x57, 0x4a, 0x2e, 0xff,
+ 0x63, 0x5d, 0x42, 0xff, 0x91, 0x8c, 0x78, 0xff,
+ 0xc0, 0xbc, 0xb0, 0xff, 0xee, 0xea, 0xe6, 0xff,
+ 0xfa, 0xfe, 0xfa, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfd, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfd, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfd, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfd, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfd, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfd, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xf7, 0xf0, 0xf2, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xf7, 0xeb, 0xde, 0xff, 0xca, 0xba, 0xa7, 0xff,
+ 0xf7, 0xeb, 0xde, 0xff, 0xe1, 0xd2, 0xc2, 0xff,
+ 0xe4, 0xd7, 0xcb, 0xff, 0xff, 0xf6, 0xee, 0xff,
+ 0xff, 0xf7, 0xef, 0xff, 0xc8, 0xb6, 0xa7, 0xff,
+ 0x1e, 0x16, 0x11, 0xff, 0x18, 0x10, 0x10, 0xff,
+ 0x1f, 0x16, 0x11, 0xff, 0x1b, 0x13, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x21, 0x1e, 0x16, 0xff,
+ 0x21, 0x1d, 0x11, 0xff, 0x21, 0x1c, 0x10, 0xff,
+ 0x21, 0x1d, 0x11, 0xff, 0x34, 0x2b, 0x1b, 0xff,
+ 0x32, 0x29, 0x11, 0xff, 0x3c, 0x32, 0x18, 0xff,
+ 0x3d, 0x32, 0x19, 0xff, 0x52, 0x45, 0x29, 0xff,
+ 0x8c, 0x72, 0x58, 0xff, 0xb5, 0x96, 0x7b, 0xff,
+ 0x8c, 0x72, 0x58, 0xff, 0x8c, 0x71, 0x58, 0xff,
+ 0x58, 0x4a, 0x2f, 0xff, 0x4a, 0x3c, 0x21, 0xff,
+ 0x4a, 0x3d, 0x21, 0xff, 0x58, 0x4a, 0x2f, 0xff,
+ 0x63, 0x5d, 0x42, 0xff, 0x62, 0x5d, 0x42, 0xff,
+ 0x92, 0x8d, 0x79, 0xff, 0xee, 0xeb, 0xe6, 0xff,
+ 0xfa, 0xfe, 0xfa, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xf7, 0xf0, 0xf1, 0xff,
+ 0xe1, 0xd3, 0xc3, 0xff, 0xcb, 0xba, 0xa7, 0xff,
+ 0xcb, 0xbb, 0xa8, 0xff, 0xcb, 0xba, 0xa7, 0xff,
+ 0xe4, 0xd7, 0xcb, 0xff, 0xff, 0xf7, 0xee, 0xff,
+ 0xc9, 0xb7, 0xa8, 0xff, 0xad, 0x96, 0x84, 0xff,
+ 0x19, 0x10, 0x11, 0xff, 0x1b, 0x13, 0x10, 0xff,
+ 0x21, 0x18, 0x10, 0xff, 0x1e, 0x15, 0x10, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x21, 0x1e, 0x16, 0xff, 0x31, 0x30, 0x20, 0xff,
+ 0x34, 0x2b, 0x1c, 0xff, 0x21, 0x1c, 0x10, 0xff,
+ 0x34, 0x2b, 0x1b, 0xff, 0x20, 0x1c, 0x10, 0xff,
+ 0x3c, 0x32, 0x19, 0xff, 0x3c, 0x32, 0x18, 0xff,
+ 0x31, 0x29, 0x10, 0xff, 0x52, 0x44, 0x29, 0xff,
+ 0x63, 0x4d, 0x34, 0xff, 0x8b, 0x71, 0x57, 0xff,
+ 0x8c, 0x71, 0x58, 0xff, 0x62, 0x4c, 0x34, 0xff,
+ 0x73, 0x65, 0x4a, 0xff, 0x73, 0x65, 0x4a, 0xff,
+ 0x58, 0x4a, 0x2f, 0xff, 0x57, 0x4a, 0x2e, 0xff,
+ 0x63, 0x5d, 0x42, 0xff, 0x62, 0x5d, 0x41, 0xff,
+ 0x91, 0x8c, 0x79, 0xff, 0xee, 0xea, 0xe6, 0xff,
+ 0xfa, 0xfe, 0xfa, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xf7, 0xf0, 0xf1, 0xff, 0xe6, 0xda, 0xd5, 0xff,
+ 0xcb, 0xba, 0xa7, 0xff, 0xb5, 0xa2, 0x8b, 0xff,
+ 0xb5, 0xa2, 0x8c, 0xff, 0xca, 0xba, 0xa7, 0xff,
+ 0xc8, 0xb6, 0xa7, 0xff, 0xac, 0x95, 0x83, 0xff,
+ 0xad, 0x96, 0x84, 0xff, 0xac, 0x95, 0x83, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x19, 0x14, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x19, 0x14, 0x10, 0xff,
+ 0x21, 0x19, 0x11, 0xff, 0x21, 0x18, 0x10, 0xff,
+ 0x21, 0x19, 0x11, 0xff, 0x52, 0x41, 0x34, 0xff,
+ 0x2a, 0x21, 0x11, 0xff, 0x29, 0x20, 0x10, 0xff,
+ 0x42, 0x39, 0x29, 0xff, 0x42, 0x39, 0x29, 0xff,
+ 0x32, 0x29, 0x16, 0xff, 0x42, 0x39, 0x21, 0xff,
+ 0x32, 0x29, 0x16, 0xff, 0x42, 0x39, 0x21, 0xff,
+ 0x42, 0x35, 0x19, 0xff, 0x42, 0x35, 0x19, 0xff,
+ 0x5b, 0x4c, 0x32, 0xff, 0x73, 0x62, 0x4a, 0xff,
+ 0x76, 0x62, 0x42, 0xff, 0x76, 0x61, 0x42, 0xff,
+ 0x76, 0x61, 0x42, 0xff, 0x63, 0x51, 0x31, 0xff,
+ 0x63, 0x5a, 0x3a, 0xff, 0x63, 0x59, 0x3a, 0xff,
+ 0x89, 0x82, 0x69, 0xff, 0xd6, 0xd2, 0xc5, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf7, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf7, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf7, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf7, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfa, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfd, 0xfa, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xf7, 0xef, 0xe7, 0xff, 0xf7, 0xef, 0xe6, 0xff,
+ 0xf7, 0xef, 0xe7, 0xff, 0xde, 0xd2, 0xc8, 0xff,
+ 0xdf, 0xd3, 0xc6, 0xff, 0xbd, 0xb1, 0xa2, 0xff,
+ 0xbe, 0xb1, 0xa2, 0xff, 0x9c, 0x8f, 0x7e, 0xff,
+ 0xbe, 0xa6, 0x95, 0xff, 0x9c, 0x88, 0x79, 0xff,
+ 0xad, 0x97, 0x87, 0xff, 0xbd, 0xa6, 0x94, 0xff,
+ 0x66, 0x48, 0x31, 0xff, 0x65, 0x47, 0x31, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x21, 0x18, 0x11, 0xff, 0x20, 0x18, 0x10, 0xff,
+ 0x21, 0x19, 0x11, 0xff, 0x21, 0x18, 0x10, 0xff,
+ 0x29, 0x20, 0x11, 0xff, 0x29, 0x20, 0x10, 0xff,
+ 0x29, 0x21, 0x11, 0xff, 0x5a, 0x51, 0x42, 0xff,
+ 0x42, 0x39, 0x21, 0xff, 0x29, 0x20, 0x10, 0xff,
+ 0x29, 0x21, 0x11, 0xff, 0x31, 0x28, 0x16, 0xff,
+ 0x42, 0x35, 0x19, 0xff, 0x41, 0x34, 0x18, 0xff,
+ 0x42, 0x35, 0x19, 0xff, 0x8c, 0x79, 0x62, 0xff,
+ 0x9c, 0x82, 0x63, 0xff, 0x75, 0x61, 0x41, 0xff,
+ 0x63, 0x51, 0x32, 0xff, 0x62, 0x51, 0x31, 0xff,
+ 0x63, 0x59, 0x3a, 0xff, 0x62, 0x59, 0x39, 0xff,
+ 0x89, 0x82, 0x68, 0xff, 0xaf, 0xaa, 0x97, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf6, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf6, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf6, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf6, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfd, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfd, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xfc, 0xf9, 0xf9, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf6, 0xef, 0xee, 0xff,
+ 0xf7, 0xef, 0xe6, 0xff, 0xde, 0xd2, 0xc8, 0xff,
+ 0xde, 0xd3, 0xc8, 0xff, 0xf6, 0xef, 0xe6, 0xff,
+ 0xde, 0xd3, 0xc6, 0xff, 0xbd, 0xb0, 0xa1, 0xff,
+ 0xbd, 0xb1, 0xa2, 0xff, 0xbd, 0xb0, 0xa1, 0xff,
+ 0x9c, 0x88, 0x79, 0xff, 0x9c, 0x88, 0x78, 0xff,
+ 0xad, 0x97, 0x87, 0xff, 0xac, 0x97, 0x86, 0xff,
+ 0x8c, 0x61, 0x42, 0xff, 0x8c, 0x61, 0x42, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x19, 0x14, 0x10, 0xff,
+ 0x53, 0x41, 0x34, 0xff, 0x52, 0x41, 0x34, 0xff,
+ 0x53, 0x41, 0x35, 0xff, 0x21, 0x18, 0x10, 0xff,
+ 0x29, 0x21, 0x11, 0xff, 0x29, 0x20, 0x10, 0xff,
+ 0x2a, 0x21, 0x11, 0xff, 0x29, 0x20, 0x10, 0xff,
+ 0x3a, 0x31, 0x1c, 0xff, 0x29, 0x20, 0x10, 0xff,
+ 0x2a, 0x21, 0x11, 0xff, 0x29, 0x20, 0x10, 0xff,
+ 0x42, 0x35, 0x19, 0xff, 0x42, 0x34, 0x18, 0xff,
+ 0x42, 0x35, 0x19, 0xff, 0x8c, 0x79, 0x63, 0xff,
+ 0x89, 0x72, 0x53, 0xff, 0x76, 0x61, 0x42, 0xff,
+ 0x76, 0x62, 0x42, 0xff, 0x89, 0x71, 0x52, 0xff,
+ 0x63, 0x59, 0x3a, 0xff, 0x62, 0x59, 0x39, 0xff,
+ 0x8a, 0x82, 0x69, 0xff, 0xaf, 0xaa, 0x97, 0xff,
+ 0xe1, 0xdb, 0xce, 0xff, 0xff, 0xfb, 0xf7, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf7, 0xff,
+ 0xe9, 0xe0, 0xd9, 0xff, 0xff, 0xfb, 0xf7, 0xff,
+ 0xd4, 0xc5, 0xbb, 0xff, 0xe9, 0xe0, 0xd9, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfa, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfd, 0xfa, 0xfa, 0xff, 0xf7, 0xef, 0xee, 0xff,
+ 0xde, 0xd3, 0xc8, 0xff, 0xad, 0x9a, 0x8c, 0xff,
+ 0xad, 0x9a, 0x8c, 0xff, 0xc5, 0xb6, 0xaa, 0xff,
+ 0xbd, 0xb1, 0xa2, 0xff, 0xbd, 0xb1, 0xa2, 0xff,
+ 0x7c, 0x6e, 0x5b, 0xff, 0x9c, 0x8f, 0x7e, 0xff,
+ 0x8c, 0x7a, 0x6b, 0xff, 0x9c, 0x88, 0x78, 0xff,
+ 0x8c, 0x7a, 0x6b, 0xff, 0x8c, 0x79, 0x6b, 0xff,
+ 0x66, 0x48, 0x32, 0xff, 0x3f, 0x2e, 0x21, 0xff,
+ 0x19, 0x14, 0x10, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x21, 0x18, 0x11, 0xff, 0xb5, 0x91, 0x7b, 0xff,
+ 0x84, 0x69, 0x58, 0xff, 0x52, 0x40, 0x34, 0xff,
+ 0x73, 0x69, 0x5b, 0xff, 0x5a, 0x51, 0x41, 0xff,
+ 0x29, 0x20, 0x10, 0xff, 0x29, 0x20, 0x10, 0xff,
+ 0x29, 0x21, 0x11, 0xff, 0x29, 0x20, 0x10, 0xff,
+ 0x29, 0x20, 0x10, 0xff, 0x29, 0x20, 0x10, 0xff,
+ 0x42, 0x35, 0x19, 0xff, 0x41, 0x34, 0x18, 0xff,
+ 0x42, 0x35, 0x19, 0xff, 0x5a, 0x4b, 0x31, 0xff,
+ 0x63, 0x51, 0x32, 0xff, 0x76, 0x61, 0x41, 0xff,
+ 0x63, 0x51, 0x31, 0xff, 0x75, 0x61, 0x41, 0xff,
+ 0x63, 0x59, 0x3a, 0xff, 0x62, 0x59, 0x39, 0xff,
+ 0x63, 0x59, 0x3a, 0xff, 0x89, 0x81, 0x68, 0xff,
+ 0xa5, 0x9a, 0x7c, 0xff, 0xc2, 0xba, 0xa4, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xe0, 0xda, 0xcd, 0xff,
+ 0xbd, 0xaa, 0x9c, 0xff, 0xe9, 0xe0, 0xd8, 0xff,
+ 0xd3, 0xc5, 0xba, 0xff, 0xbd, 0xaa, 0x9c, 0xff,
+ 0xde, 0xd7, 0xc6, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xff, 0xfa, 0xff, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfa, 0xfa, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xfc, 0xf9, 0xf9, 0xff,
+ 0xde, 0xd3, 0xc8, 0xff, 0xc5, 0xb6, 0xaa, 0xff,
+ 0xad, 0x9a, 0x8c, 0xff, 0xac, 0x99, 0x8b, 0xff,
+ 0x9c, 0x8f, 0x7e, 0xff, 0x7b, 0x6d, 0x5a, 0xff,
+ 0x7b, 0x6d, 0x5b, 0xff, 0x7b, 0x6d, 0x5a, 0xff,
+ 0x9c, 0x88, 0x79, 0xff, 0xbd, 0xa6, 0x94, 0xff,
+ 0xad, 0x97, 0x86, 0xff, 0x9c, 0x88, 0x78, 0xff,
+ 0x1f, 0x1b, 0x16, 0xff, 0x1b, 0x16, 0x13, 0xff,
+ 0x1c, 0x16, 0x14, 0xff, 0x21, 0x20, 0x19, 0xff,
+ 0x19, 0x11, 0x09, 0xff, 0x55, 0x47, 0x3c, 0xff,
+ 0xce, 0xb6, 0xa5, 0xff, 0xcd, 0xb6, 0xa4, 0xff,
+ 0xe7, 0xcf, 0xb5, 0xff, 0xb2, 0x9a, 0x81, 0xff,
+ 0x7e, 0x66, 0x4d, 0xff, 0x4a, 0x30, 0x19, 0xff,
+ 0x35, 0x26, 0x16, 0xff, 0x29, 0x1c, 0x10, 0xff,
+ 0x34, 0x26, 0x16, 0xff, 0x34, 0x26, 0x16, 0xff,
+ 0x42, 0x35, 0x19, 0xff, 0x42, 0x35, 0x19, 0xff,
+ 0x69, 0x5d, 0x45, 0xff, 0x68, 0x5d, 0x44, 0xff,
+ 0x5e, 0x54, 0x35, 0xff, 0x5d, 0x54, 0x34, 0xff,
+ 0x42, 0x3d, 0x19, 0xff, 0x5d, 0x53, 0x34, 0xff,
+ 0x53, 0x45, 0x21, 0xff, 0x52, 0x45, 0x21, 0xff,
+ 0x5e, 0x54, 0x34, 0xff, 0x5d, 0x53, 0x34, 0xff,
+ 0x74, 0x6e, 0x53, 0xff, 0x8f, 0x86, 0x70, 0xff,
+ 0xc6, 0xb6, 0xad, 0xff, 0xaa, 0x9e, 0x8e, 0xff,
+ 0xa5, 0x98, 0x84, 0xff, 0xce, 0xc1, 0xb5, 0xff,
+ 0xce, 0xc1, 0xb5, 0xff, 0xa4, 0x97, 0x83, 0xff,
+ 0xd6, 0xcf, 0xbe, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfa, 0xfa, 0xf7, 0xff, 0xf9, 0xfa, 0xf7, 0xff,
+ 0xf4, 0xf5, 0xef, 0xff, 0xf4, 0xf4, 0xee, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xdb, 0xd4, 0xce, 0xff,
+ 0xb8, 0xad, 0xa5, 0xff, 0x94, 0x85, 0x7b, 0xff,
+ 0x8c, 0x7e, 0x6e, 0xff, 0x7b, 0x69, 0x58, 0xff,
+ 0x7c, 0x6a, 0x58, 0xff, 0x7b, 0x69, 0x58, 0xff,
+ 0x7c, 0x6e, 0x5b, 0xff, 0x8c, 0x81, 0x73, 0xff,
+ 0x6b, 0x59, 0x42, 0xff, 0x6b, 0x59, 0x42, 0xff,
+ 0x1c, 0x16, 0x13, 0xff, 0x1b, 0x15, 0x13, 0xff,
+ 0x1c, 0x16, 0x13, 0xff, 0x1e, 0x1b, 0x16, 0xff,
+ 0x55, 0x48, 0x3c, 0xff, 0x18, 0x10, 0x08, 0xff,
+ 0x92, 0x7f, 0x71, 0xff, 0x91, 0x7f, 0x70, 0xff,
+ 0x7e, 0x65, 0x4d, 0xff, 0xb2, 0x99, 0x80, 0xff,
+ 0x7e, 0x65, 0x4d, 0xff, 0x4a, 0x30, 0x18, 0xff,
+ 0x29, 0x1c, 0x11, 0xff, 0x3f, 0x2f, 0x1b, 0xff,
+ 0x4a, 0x39, 0x21, 0xff, 0x4a, 0x38, 0x21, 0xff,
+ 0x42, 0x35, 0x19, 0xff, 0x41, 0x34, 0x18, 0xff,
+ 0x68, 0x5d, 0x45, 0xff, 0xb5, 0xae, 0x9c, 0xff,
+ 0x42, 0x3d, 0x19, 0xff, 0x41, 0x3c, 0x18, 0xff,
+ 0x42, 0x3d, 0x19, 0xff, 0x42, 0x3c, 0x18, 0xff,
+ 0x52, 0x45, 0x21, 0xff, 0x52, 0x44, 0x20, 0xff,
+ 0x5d, 0x54, 0x34, 0xff, 0x5d, 0x53, 0x34, 0xff,
+ 0x73, 0x6d, 0x52, 0xff, 0xaa, 0x9d, 0x8e, 0xff,
+ 0xc6, 0xb6, 0xad, 0xff, 0x8e, 0x85, 0x70, 0xff,
+ 0xa5, 0x97, 0x84, 0xff, 0xa4, 0x97, 0x83, 0xff,
+ 0xf7, 0xeb, 0xe7, 0xff, 0xcd, 0xc1, 0xb5, 0xff,
+ 0xf1, 0xec, 0xe9, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfd, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfd, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf9, 0xf9, 0xf6, 0xff,
+ 0xef, 0xef, 0xe7, 0xff, 0xf4, 0xf4, 0xee, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xdb, 0xd3, 0xcd, 0xff,
+ 0xb8, 0xad, 0xa5, 0xff, 0x94, 0x85, 0x7b, 0xff,
+ 0x8c, 0x7e, 0x6e, 0xff, 0x7b, 0x69, 0x57, 0xff,
+ 0x6b, 0x55, 0x42, 0xff, 0x6b, 0x55, 0x42, 0xff,
+ 0x6b, 0x59, 0x42, 0xff, 0x6b, 0x59, 0x41, 0xff,
+ 0x5b, 0x45, 0x29, 0xff, 0x5a, 0x45, 0x29, 0xff,
+ 0x1c, 0x16, 0x13, 0xff, 0x1b, 0x15, 0x13, 0xff,
+ 0x1c, 0x16, 0x14, 0xff, 0x19, 0x10, 0x10, 0xff,
+ 0x55, 0x48, 0x3d, 0xff, 0x91, 0x7f, 0x70, 0xff,
+ 0x19, 0x11, 0x09, 0xff, 0x55, 0x47, 0x3c, 0xff,
+ 0x7e, 0x65, 0x4d, 0xff, 0x7e, 0x65, 0x4d, 0xff,
+ 0xb3, 0x9a, 0x81, 0xff, 0x7e, 0x65, 0x4d, 0xff,
+ 0x34, 0x26, 0x16, 0xff, 0x3f, 0x2f, 0x1b, 0xff,
+ 0x4a, 0x39, 0x21, 0xff, 0x3f, 0x2f, 0x1b, 0xff,
+ 0x42, 0x35, 0x19, 0xff, 0x42, 0x34, 0x18, 0xff,
+ 0x69, 0x5e, 0x45, 0xff, 0xb5, 0xae, 0x9c, 0xff,
+ 0x79, 0x6b, 0x50, 0xff, 0x42, 0x3c, 0x18, 0xff,
+ 0x5e, 0x54, 0x35, 0xff, 0x42, 0x3d, 0x19, 0xff,
+ 0x53, 0x45, 0x21, 0xff, 0x52, 0x45, 0x21, 0xff,
+ 0x5e, 0x54, 0x35, 0xff, 0x68, 0x62, 0x47, 0xff,
+ 0x73, 0x6e, 0x53, 0xff, 0x8e, 0x85, 0x70, 0xff,
+ 0x8f, 0x86, 0x71, 0xff, 0x73, 0x6d, 0x52, 0xff,
+ 0x7c, 0x6e, 0x53, 0xff, 0xa4, 0x97, 0x83, 0xff,
+ 0xf7, 0xeb, 0xe7, 0xff, 0xce, 0xc1, 0xb5, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfa, 0xfa, 0xf7, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xf4, 0xf5, 0xef, 0xff, 0xf9, 0xfa, 0xf7, 0xff,
+ 0xdc, 0xd4, 0xce, 0xff, 0xb7, 0xac, 0xa4, 0xff,
+ 0xb8, 0xad, 0xa5, 0xff, 0x94, 0x85, 0x7b, 0xff,
+ 0x8c, 0x7e, 0x6e, 0xff, 0x8c, 0x7d, 0x6d, 0xff,
+ 0x6b, 0x55, 0x42, 0xff, 0x6b, 0x55, 0x42, 0xff,
+ 0x6b, 0x59, 0x42, 0xff, 0x5a, 0x45, 0x29, 0xff,
+ 0x5b, 0x45, 0x2a, 0xff, 0x6b, 0x59, 0x42, 0xff,
+ 0x19, 0x10, 0x11, 0xff, 0x1b, 0x15, 0x13, 0xff,
+ 0x1b, 0x16, 0x13, 0xff, 0x20, 0x20, 0x18, 0xff,
+ 0x55, 0x48, 0x3c, 0xff, 0x91, 0x7e, 0x70, 0xff,
+ 0x55, 0x48, 0x3c, 0xff, 0x18, 0x10, 0x08, 0xff,
+ 0x4a, 0x31, 0x19, 0xff, 0x4a, 0x30, 0x18, 0xff,
+ 0x4a, 0x31, 0x19, 0xff, 0x4a, 0x30, 0x18, 0xff,
+ 0x4a, 0x39, 0x21, 0xff, 0x4a, 0x38, 0x21, 0xff,
+ 0x3f, 0x2f, 0x1b, 0xff, 0x3f, 0x2f, 0x1b, 0xff,
+ 0x42, 0x35, 0x19, 0xff, 0x68, 0x5d, 0x44, 0xff,
+ 0x42, 0x35, 0x19, 0xff, 0x8e, 0x85, 0x70, 0xff,
+ 0x94, 0x82, 0x6b, 0xff, 0x5d, 0x53, 0x34, 0xff,
+ 0x5d, 0x54, 0x34, 0xff, 0x41, 0x3c, 0x18, 0xff,
+ 0x5d, 0x54, 0x34, 0xff, 0x52, 0x44, 0x21, 0xff,
+ 0x5d, 0x54, 0x34, 0xff, 0x73, 0x71, 0x5a, 0xff,
+ 0x73, 0x6d, 0x52, 0xff, 0x8e, 0x85, 0x70, 0xff,
+ 0x73, 0x6d, 0x52, 0xff, 0x73, 0x6d, 0x52, 0xff,
+ 0x7c, 0x6d, 0x52, 0xff, 0xa4, 0x97, 0x83, 0xff,
+ 0xa5, 0x97, 0x84, 0xff, 0xa4, 0x97, 0x83, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xff, 0xfb, 0xff, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xff, 0xfa, 0xff, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf9, 0xf9, 0xf6, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf9, 0xf9, 0xf6, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xdb, 0xd3, 0xcd, 0xff,
+ 0xb8, 0xad, 0xa5, 0xff, 0x94, 0x85, 0x7b, 0xff,
+ 0x9c, 0x92, 0x84, 0xff, 0x8b, 0x7d, 0x6d, 0xff,
+ 0x7b, 0x69, 0x58, 0xff, 0x6a, 0x55, 0x41, 0xff,
+ 0x5b, 0x45, 0x29, 0xff, 0x5a, 0x44, 0x29, 0xff,
+ 0x5b, 0x45, 0x29, 0xff, 0x5a, 0x44, 0x29, 0xff,
+ 0x1f, 0x1b, 0x16, 0xff, 0x1e, 0x1b, 0x16, 0xff,
+ 0x1f, 0x1b, 0x16, 0xff, 0x23, 0x26, 0x1b, 0xff,
+ 0x50, 0x4c, 0x3d, 0xff, 0x6b, 0x65, 0x52, 0xff,
+ 0x6b, 0x66, 0x53, 0xff, 0x34, 0x32, 0x26, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x24, 0x1c, 0x10, 0xff,
+ 0x29, 0x21, 0x11, 0xff, 0x23, 0x1c, 0x10, 0xff,
+ 0x4b, 0x35, 0x21, 0xff, 0x2f, 0x24, 0x16, 0xff,
+ 0x2f, 0x25, 0x16, 0xff, 0x3c, 0x2c, 0x1b, 0xff,
+ 0x3a, 0x2d, 0x11, 0xff, 0x45, 0x3b, 0x21, 0xff,
+ 0x50, 0x4b, 0x32, 0xff, 0x5a, 0x59, 0x42, 0xff,
+ 0x71, 0x6b, 0x50, 0xff, 0x70, 0x6b, 0x4f, 0xff,
+ 0x4a, 0x4d, 0x29, 0xff, 0x4a, 0x4d, 0x29, 0xff,
+ 0x6b, 0x62, 0x40, 0xff, 0x5a, 0x4d, 0x29, 0xff,
+ 0x5b, 0x4d, 0x29, 0xff, 0x8c, 0x89, 0x6b, 0xff,
+ 0x7c, 0x72, 0x53, 0xff, 0x70, 0x5e, 0x3c, 0xff,
+ 0x71, 0x5f, 0x3d, 0xff, 0x7b, 0x71, 0x52, 0xff,
+ 0x8f, 0x7a, 0x60, 0xff, 0x8f, 0x79, 0x60, 0xff,
+ 0x8f, 0x7a, 0x60, 0xff, 0xb2, 0xa2, 0x8e, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfe, 0xfc, 0xff,
+ 0xff, 0xfd, 0xfa, 0xff, 0xff, 0xfc, 0xf9, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfb, 0xfd, 0xff, 0xfc, 0xfb, 0xfc, 0xff,
+ 0xfd, 0xfb, 0xfd, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xf7, 0xef, 0xef, 0xff, 0xd9, 0xce, 0xcb, 0xff,
+ 0xbb, 0xae, 0xa8, 0xff, 0x9c, 0x8e, 0x83, 0xff,
+ 0xa5, 0x9e, 0x95, 0xff, 0x8f, 0x87, 0x7b, 0xff,
+ 0x79, 0x70, 0x63, 0xff, 0x63, 0x59, 0x4a, 0xff,
+ 0x55, 0x47, 0x2f, 0xff, 0x55, 0x46, 0x2f, 0xff,
+ 0x4a, 0x39, 0x21, 0xff, 0x4a, 0x39, 0x21, 0xff,
+ 0x19, 0x10, 0x11, 0xff, 0x1e, 0x1b, 0x16, 0xff,
+ 0x1e, 0x1b, 0x16, 0xff, 0x29, 0x30, 0x21, 0xff,
+ 0x34, 0x32, 0x26, 0xff, 0x34, 0x32, 0x26, 0xff,
+ 0x34, 0x32, 0x27, 0xff, 0x34, 0x32, 0x26, 0xff,
+ 0x1e, 0x18, 0x11, 0xff, 0x1e, 0x18, 0x10, 0xff,
+ 0x1e, 0x19, 0x11, 0xff, 0x29, 0x20, 0x10, 0xff,
+ 0x2f, 0x25, 0x16, 0xff, 0x2e, 0x24, 0x16, 0xff,
+ 0x2f, 0x25, 0x16, 0xff, 0x2e, 0x24, 0x16, 0xff,
+ 0x45, 0x3b, 0x21, 0xff, 0x5a, 0x59, 0x41, 0xff,
+ 0x50, 0x4a, 0x32, 0xff, 0x4f, 0x4a, 0x31, 0xff,
+ 0x4a, 0x4d, 0x29, 0xff, 0x4a, 0x4c, 0x29, 0xff,
+ 0x5d, 0x5c, 0x3d, 0xff, 0x4a, 0x4d, 0x29, 0xff,
+ 0x7b, 0x75, 0x55, 0xff, 0x7b, 0x75, 0x55, 0xff,
+ 0x6b, 0x61, 0x3f, 0xff, 0x7b, 0x75, 0x55, 0xff,
+ 0x6b, 0x55, 0x31, 0xff, 0x6b, 0x55, 0x31, 0xff,
+ 0x71, 0x5f, 0x3d, 0xff, 0x76, 0x68, 0x47, 0xff,
+ 0x8f, 0x7a, 0x60, 0xff, 0x8e, 0x79, 0x60, 0xff,
+ 0xb2, 0xa2, 0x8f, 0xff, 0xd6, 0xca, 0xbd, 0xff,
+ 0xff, 0xfc, 0xfa, 0xff, 0xff, 0xfc, 0xf9, 0xff,
+ 0xff, 0xfd, 0xfa, 0xff, 0xff, 0xfc, 0xf9, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfd, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfd, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfb, 0xfc, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xfc, 0xfb, 0xfc, 0xff, 0xf6, 0xf3, 0xf6, 0xff,
+ 0xd9, 0xcf, 0xcb, 0xff, 0xba, 0xae, 0xa7, 0xff,
+ 0xbb, 0xae, 0xa7, 0xff, 0x9c, 0x8d, 0x83, 0xff,
+ 0xa5, 0x9e, 0x94, 0xff, 0x8e, 0x87, 0x7b, 0xff,
+ 0x79, 0x70, 0x63, 0xff, 0x62, 0x59, 0x4a, 0xff,
+ 0x60, 0x54, 0x3c, 0xff, 0x55, 0x46, 0x2e, 0xff,
+ 0x55, 0x46, 0x2f, 0xff, 0x55, 0x46, 0x2e, 0xff,
+ 0x19, 0x10, 0x11, 0xff, 0x18, 0x10, 0x10, 0xff,
+ 0x24, 0x26, 0x1c, 0xff, 0x24, 0x26, 0x1b, 0xff,
+ 0x34, 0x32, 0x27, 0xff, 0x34, 0x32, 0x26, 0xff,
+ 0x19, 0x19, 0x11, 0xff, 0x19, 0x18, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x1f, 0x19, 0x11, 0xff, 0x24, 0x1c, 0x10, 0xff,
+ 0x2f, 0x25, 0x16, 0xff, 0x21, 0x1c, 0x10, 0xff,
+ 0x2f, 0x25, 0x16, 0xff, 0x2f, 0x24, 0x16, 0xff,
+ 0x3a, 0x2d, 0x11, 0xff, 0x44, 0x3b, 0x21, 0xff,
+ 0x50, 0x4b, 0x32, 0xff, 0x5a, 0x59, 0x42, 0xff,
+ 0x71, 0x6b, 0x50, 0xff, 0x5d, 0x5c, 0x3c, 0xff,
+ 0x5e, 0x5c, 0x3d, 0xff, 0x4a, 0x4d, 0x29, 0xff,
+ 0x7c, 0x76, 0x55, 0xff, 0x8c, 0x89, 0x6b, 0xff,
+ 0x7c, 0x76, 0x55, 0xff, 0x7b, 0x75, 0x55, 0xff,
+ 0x7c, 0x72, 0x53, 0xff, 0x7b, 0x71, 0x52, 0xff,
+ 0x76, 0x68, 0x48, 0xff, 0x70, 0x5e, 0x3c, 0xff,
+ 0x6b, 0x51, 0x32, 0xff, 0xb2, 0xa2, 0x8e, 0xff,
+ 0xb3, 0xa2, 0x8f, 0xff, 0xd6, 0xca, 0xbd, 0xff,
+ 0xff, 0xfd, 0xfa, 0xff, 0xff, 0xfd, 0xfc, 0xff,
+ 0xff, 0xfd, 0xfa, 0xff, 0xff, 0xfc, 0xf9, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfd, 0xfd, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xff, 0xfb, 0xff, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfd, 0xfb, 0xfd, 0xff, 0xfc, 0xfb, 0xfc, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xf9, 0xf7, 0xf9, 0xff,
+ 0xf7, 0xef, 0xef, 0xff, 0xba, 0xae, 0xa7, 0xff,
+ 0xd9, 0xcf, 0xcb, 0xff, 0xba, 0xae, 0xa7, 0xff,
+ 0x8f, 0x87, 0x7c, 0xff, 0x78, 0x70, 0x62, 0xff,
+ 0x8f, 0x87, 0x7c, 0xff, 0x79, 0x70, 0x63, 0xff,
+ 0x60, 0x54, 0x3d, 0xff, 0x60, 0x53, 0x3c, 0xff,
+ 0x55, 0x47, 0x2f, 0xff, 0x6b, 0x61, 0x4a, 0xff,
+ 0x1e, 0x1b, 0x16, 0xff, 0x1e, 0x1b, 0x16, 0xff,
+ 0x24, 0x26, 0x1b, 0xff, 0x1e, 0x1b, 0x15, 0xff,
+ 0x19, 0x18, 0x11, 0xff, 0x18, 0x18, 0x10, 0xff,
+ 0x19, 0x18, 0x10, 0xff, 0x18, 0x18, 0x10, 0xff,
+ 0x1e, 0x18, 0x11, 0xff, 0x1e, 0x18, 0x10, 0xff,
+ 0x19, 0x14, 0x10, 0xff, 0x1e, 0x18, 0x10, 0xff,
+ 0x21, 0x1c, 0x11, 0xff, 0x21, 0x1c, 0x10, 0xff,
+ 0x2f, 0x24, 0x16, 0xff, 0x2e, 0x24, 0x15, 0xff,
+ 0x3a, 0x2d, 0x11, 0xff, 0x39, 0x2c, 0x10, 0xff,
+ 0x45, 0x3b, 0x21, 0xff, 0x44, 0x3b, 0x20, 0xff,
+ 0x5d, 0x5c, 0x3c, 0xff, 0x70, 0x6a, 0x4f, 0xff,
+ 0x84, 0x79, 0x63, 0xff, 0x83, 0x79, 0x62, 0xff,
+ 0x8c, 0x8a, 0x6b, 0xff, 0x6b, 0x61, 0x3f, 0xff,
+ 0x6b, 0x61, 0x3f, 0xff, 0x5a, 0x4c, 0x29, 0xff,
+ 0x6b, 0x55, 0x32, 0xff, 0x70, 0x5e, 0x3c, 0xff,
+ 0x70, 0x5e, 0x3c, 0xff, 0x6a, 0x55, 0x31, 0xff,
+ 0x6b, 0x51, 0x32, 0xff, 0x8e, 0x79, 0x60, 0xff,
+ 0xb2, 0xa2, 0x8f, 0xff, 0xd5, 0xca, 0xbd, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xff, 0xfc, 0xf9, 0xff,
+ 0xff, 0xfc, 0xfa, 0xff, 0xff, 0xfc, 0xf9, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfc, 0xfc, 0xff, 0xfc, 0xfc, 0xfc, 0xff,
+ 0xfc, 0xfb, 0xfc, 0xff, 0xff, 0xff, 0xff, 0xff,
+ 0xff, 0xff, 0xff, 0xff, 0xfc, 0xfa, 0xfc, 0xff,
+ 0xd9, 0xcf, 0xcb, 0xff, 0xf6, 0xee, 0xee, 0xff,
+ 0xf7, 0xef, 0xef, 0xff, 0xd8, 0xce, 0xca, 0xff,
+ 0x8f, 0x87, 0x7c, 0xff, 0x78, 0x70, 0x62, 0xff,
+ 0x8f, 0x87, 0x7b, 0xff, 0x78, 0x70, 0x62, 0xff,
+ 0x6b, 0x61, 0x4a, 0xff, 0x6b, 0x61, 0x4a, 0xff,
+ 0x6b, 0x61, 0x4a, 0xff, 0x5f, 0x53, 0x3c, 0xff,
+ 0x21, 0x1e, 0x1c, 0xff, 0x21, 0x1e, 0x1b, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x0f, 0x0b, 0xff, 0x19, 0x16, 0x0e, 0xff,
+ 0x21, 0x1d, 0x11, 0xff, 0x19, 0x15, 0x0e, 0xff,
+ 0x1c, 0x15, 0x0e, 0xff, 0x21, 0x18, 0x10, 0xff,
+ 0x21, 0x19, 0x11, 0xff, 0x21, 0x18, 0x10, 0xff,
+ 0x27, 0x1e, 0x11, 0xff, 0x26, 0x1e, 0x10, 0xff,
+ 0x2c, 0x23, 0x11, 0xff, 0x2c, 0x23, 0x10, 0xff,
+ 0x2a, 0x21, 0x11, 0xff, 0x31, 0x28, 0x13, 0xff,
+ 0x3a, 0x31, 0x16, 0xff, 0x42, 0x39, 0x19, 0xff,
+ 0x53, 0x4d, 0x27, 0xff, 0x5a, 0x59, 0x31, 0xff,
+ 0x53, 0x4d, 0x27, 0xff, 0x4a, 0x41, 0x1b, 0xff,
+ 0x53, 0x49, 0x21, 0xff, 0x52, 0x49, 0x21, 0xff,
+ 0x53, 0x49, 0x21, 0xff, 0x5a, 0x51, 0x29, 0xff,
+ 0x5b, 0x4d, 0x21, 0xff, 0x5a, 0x4d, 0x21, 0xff,
+ 0x66, 0x54, 0x29, 0xff, 0x65, 0x53, 0x29, 0xff,
+ 0x74, 0x62, 0x4b, 0xff, 0x73, 0x61, 0x4a, 0xff,
+ 0xa2, 0x95, 0x84, 0xff, 0xff, 0xfb, 0xf7, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf7, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf7, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf7, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf7, 0xff,
+ 0xf7, 0xfb, 0xf7, 0xff, 0xf7, 0xfb, 0xf7, 0xff,
+ 0xf7, 0xfb, 0xf7, 0xff, 0xf7, 0xfb, 0xf7, 0xff,
+ 0xef, 0xeb, 0xe7, 0xff, 0xef, 0xeb, 0xe6, 0xff,
+ 0xef, 0xeb, 0xe7, 0xff, 0xee, 0xeb, 0xe6, 0xff,
+ 0xe7, 0xe7, 0xdf, 0xff, 0xe6, 0xe7, 0xde, 0xff,
+ 0xe7, 0xe7, 0xde, 0xff, 0xc3, 0xc3, 0xb8, 0xff,
+ 0x84, 0x82, 0x7c, 0xff, 0x76, 0x71, 0x65, 0xff,
+ 0x5b, 0x51, 0x3a, 0xff, 0x5a, 0x51, 0x39, 0xff,
+ 0x6b, 0x66, 0x4b, 0xff, 0x6b, 0x65, 0x4a, 0xff,
+ 0x60, 0x57, 0x3d, 0xff, 0x55, 0x47, 0x2e, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x19, 0x17, 0x16, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x0f, 0x0b, 0xff, 0x10, 0x0e, 0x0b, 0xff,
+ 0x21, 0x1d, 0x11, 0xff, 0x18, 0x15, 0x0d, 0xff,
+ 0x1c, 0x14, 0x0e, 0xff, 0x1b, 0x14, 0x0d, 0xff,
+ 0x1c, 0x14, 0x0e, 0xff, 0x21, 0x18, 0x10, 0xff,
+ 0x26, 0x1e, 0x11, 0xff, 0x26, 0x1d, 0x10, 0xff,
+ 0x2c, 0x23, 0x11, 0xff, 0x2c, 0x23, 0x10, 0xff,
+ 0x29, 0x20, 0x11, 0xff, 0x31, 0x28, 0x13, 0xff,
+ 0x32, 0x29, 0x13, 0xff, 0x39, 0x30, 0x16, 0xff,
+ 0x42, 0x35, 0x11, 0xff, 0x52, 0x4c, 0x26, 0xff,
+ 0x52, 0x4d, 0x27, 0xff, 0x4a, 0x40, 0x1b, 0xff,
+ 0x52, 0x49, 0x21, 0xff, 0x4a, 0x40, 0x18, 0xff,
+ 0x5b, 0x51, 0x29, 0xff, 0x5a, 0x51, 0x29, 0xff,
+ 0x5b, 0x4d, 0x21, 0xff, 0x65, 0x53, 0x29, 0xff,
+ 0x71, 0x5b, 0x32, 0xff, 0x70, 0x5a, 0x31, 0xff,
+ 0x73, 0x61, 0x4a, 0xff, 0x73, 0x61, 0x4a, 0xff,
+ 0x73, 0x61, 0x4a, 0xff, 0xa1, 0x94, 0x83, 0xff,
+ 0xdb, 0xd1, 0xc3, 0xff, 0xff, 0xfb, 0xf6, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf6, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf6, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf6, 0xff,
+ 0xf7, 0xfb, 0xf7, 0xff, 0xf6, 0xfb, 0xf6, 0xff,
+ 0xf7, 0xfb, 0xf7, 0xff, 0xcb, 0xc7, 0xbd, 0xff,
+ 0xc0, 0xbe, 0xb5, 0xff, 0x91, 0x91, 0x83, 0xff,
+ 0xc0, 0xbe, 0xb5, 0xff, 0xc0, 0xbe, 0xb5, 0xff,
+ 0xc3, 0xc4, 0xb8, 0xff, 0xc2, 0xc3, 0xb7, 0xff,
+ 0x9f, 0xa1, 0x92, 0xff, 0x9f, 0xa0, 0x91, 0xff,
+ 0x84, 0x82, 0x7b, 0xff, 0x68, 0x61, 0x4f, 0xff,
+ 0x5b, 0x51, 0x3a, 0xff, 0x5a, 0x51, 0x39, 0xff,
+ 0x55, 0x48, 0x2f, 0xff, 0x60, 0x56, 0x3c, 0xff,
+ 0x4a, 0x39, 0x21, 0xff, 0x4a, 0x38, 0x21, 0xff,
+ 0x19, 0x17, 0x16, 0xff, 0x18, 0x17, 0x16, 0xff,
+ 0x21, 0x1e, 0x1c, 0xff, 0x19, 0x17, 0x16, 0xff,
+ 0x11, 0x0f, 0x0b, 0xff, 0x10, 0x0f, 0x0b, 0xff,
+ 0x09, 0x09, 0x09, 0xff, 0x19, 0x15, 0x0e, 0xff,
+ 0x1c, 0x15, 0x0e, 0xff, 0x16, 0x10, 0x0b, 0xff,
+ 0x16, 0x11, 0x0b, 0xff, 0x1b, 0x14, 0x0e, 0xff,
+ 0x21, 0x19, 0x11, 0xff, 0x26, 0x1d, 0x10, 0xff,
+ 0x27, 0x1e, 0x11, 0xff, 0x31, 0x28, 0x10, 0xff,
+ 0x29, 0x21, 0x11, 0xff, 0x29, 0x20, 0x10, 0xff,
+ 0x32, 0x29, 0x14, 0xff, 0x39, 0x30, 0x16, 0xff,
+ 0x42, 0x35, 0x11, 0xff, 0x42, 0x34, 0x10, 0xff,
+ 0x42, 0x35, 0x11, 0xff, 0x4a, 0x41, 0x1b, 0xff,
+ 0x4a, 0x41, 0x19, 0xff, 0x4a, 0x41, 0x18, 0xff,
+ 0x4a, 0x41, 0x19, 0xff, 0x5a, 0x51, 0x29, 0xff,
+ 0x66, 0x54, 0x29, 0xff, 0x7b, 0x61, 0x39, 0xff,
+ 0x7c, 0x62, 0x3a, 0xff, 0x70, 0x5a, 0x31, 0xff,
+ 0x73, 0x61, 0x4a, 0xff, 0x73, 0x61, 0x4a, 0xff,
+ 0x74, 0x62, 0x4a, 0xff, 0x73, 0x61, 0x4a, 0xff,
+ 0x94, 0x7e, 0x5b, 0xff, 0xb7, 0xa7, 0x8e, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xff, 0xfb, 0xf7, 0xff,
+ 0xff, 0xfb, 0xf7, 0xff, 0xd0, 0xca, 0xbd, 0xff,
+ 0xd1, 0xcb, 0xbe, 0xff, 0xd0, 0xca, 0xbd, 0xff,
+ 0x9f, 0x95, 0x84, 0xff, 0x9f, 0x94, 0x83, 0xff,
+ 0x74, 0x62, 0x4a, 0xff, 0x9f, 0x94, 0x84, 0xff,
+ 0x92, 0x92, 0x84, 0xff, 0x62, 0x65, 0x52, 0xff,
+ 0x92, 0x92, 0x84, 0xff, 0x91, 0x92, 0x84, 0xff,
+ 0x7c, 0x7e, 0x6b, 0xff, 0x7b, 0x7d, 0x6b, 0xff,
+ 0x7c, 0x7e, 0x6b, 0xff, 0x7b, 0x7d, 0x6b, 0xff,
+ 0x68, 0x61, 0x50, 0xff, 0x5a, 0x51, 0x39, 0xff,
+ 0x69, 0x62, 0x50, 0xff, 0x5a, 0x51, 0x39, 0xff,
+ 0x55, 0x48, 0x2f, 0xff, 0x55, 0x47, 0x2e, 0xff,
+ 0x4a, 0x39, 0x21, 0xff, 0x4a, 0x39, 0x21, 0xff,
+ 0x21, 0x1e, 0x1c, 0xff, 0x29, 0x24, 0x21, 0xff,
+ 0x29, 0x24, 0x21, 0xff, 0x20, 0x1d, 0x1b, 0xff,
+ 0x11, 0x0f, 0x0b, 0xff, 0x10, 0x0e, 0x0b, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x10, 0x0e, 0x0a, 0xff,
+ 0x16, 0x10, 0x0b, 0xff, 0x16, 0x10, 0x0b, 0xff,
+ 0x10, 0x0c, 0x08, 0xff, 0x15, 0x10, 0x0a, 0xff,
+ 0x21, 0x18, 0x11, 0xff, 0x26, 0x1d, 0x10, 0xff,
+ 0x2c, 0x23, 0x10, 0xff, 0x31, 0x28, 0x10, 0xff,
+ 0x32, 0x29, 0x13, 0xff, 0x31, 0x28, 0x13, 0xff,
+ 0x3a, 0x31, 0x16, 0xff, 0x39, 0x30, 0x15, 0xff,
+ 0x42, 0x35, 0x11, 0xff, 0x41, 0x34, 0x10, 0xff,
+ 0x42, 0x35, 0x10, 0xff, 0x41, 0x34, 0x10, 0xff,
+ 0x42, 0x39, 0x11, 0xff, 0x41, 0x38, 0x10, 0xff,
+ 0x4a, 0x41, 0x19, 0xff, 0x4a, 0x40, 0x18, 0xff,
+ 0x5b, 0x4d, 0x21, 0xff, 0x70, 0x5a, 0x31, 0xff,
+ 0x7b, 0x61, 0x3a, 0xff, 0x65, 0x53, 0x29, 0xff,
+ 0x73, 0x61, 0x4a, 0xff, 0x73, 0x61, 0x4a, 0xff,
+ 0x73, 0x61, 0x4a, 0xff, 0x73, 0x61, 0x4a, 0xff,
+ 0x94, 0x7e, 0x5b, 0xff, 0x94, 0x7d, 0x5a, 0xff,
+ 0xb8, 0xa7, 0x8f, 0xff, 0xb7, 0xa7, 0x8e, 0xff,
+ 0x73, 0x69, 0x4a, 0xff, 0x73, 0x69, 0x4a, 0xff,
+ 0x73, 0x69, 0x4a, 0xff, 0x73, 0x69, 0x4a, 0xff,
+ 0x73, 0x61, 0x4a, 0xff, 0x73, 0x61, 0x4a, 0xff,
+ 0x73, 0x61, 0x4a, 0xff, 0x73, 0x61, 0x4a, 0xff,
+ 0x63, 0x65, 0x52, 0xff, 0x62, 0x65, 0x52, 0xff,
+ 0x91, 0x92, 0x84, 0xff, 0x62, 0x65, 0x52, 0xff,
+ 0x7c, 0x7e, 0x6b, 0xff, 0x7b, 0x7d, 0x6b, 0xff,
+ 0x7b, 0x7e, 0x6b, 0xff, 0x7b, 0x7d, 0x6a, 0xff,
+ 0x68, 0x61, 0x50, 0xff, 0x5a, 0x51, 0x39, 0xff,
+ 0x5b, 0x51, 0x3a, 0xff, 0x5a, 0x50, 0x39, 0xff,
+ 0x55, 0x48, 0x2f, 0xff, 0x4a, 0x38, 0x21, 0xff,
+ 0x4a, 0x39, 0x21, 0xff, 0x4a, 0x38, 0x20, 0xff,
+ 0x1f, 0x28, 0x24, 0xff, 0x2c, 0x3e, 0x37, 0xff,
+ 0x1f, 0x27, 0x24, 0xff, 0x1e, 0x27, 0x23, 0xff,
+ 0x21, 0x29, 0x24, 0xff, 0x21, 0x28, 0x24, 0xff,
+ 0x19, 0x11, 0x11, 0xff, 0x19, 0x10, 0x10, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x14, 0x13, 0x11, 0xff, 0x13, 0x13, 0x10, 0xff,
+ 0x19, 0x19, 0x11, 0xff, 0x21, 0x1c, 0x10, 0xff,
+ 0x29, 0x21, 0x11, 0xff, 0x31, 0x24, 0x10, 0xff,
+ 0x32, 0x31, 0x11, 0xff, 0x31, 0x31, 0x10, 0xff,
+ 0x32, 0x31, 0x11, 0xff, 0x31, 0x30, 0x10, 0xff,
+ 0x3a, 0x39, 0x11, 0xff, 0x3a, 0x39, 0x10, 0xff,
+ 0x3a, 0x39, 0x11, 0xff, 0x39, 0x39, 0x10, 0xff,
+ 0x42, 0x39, 0x11, 0xff, 0x42, 0x39, 0x10, 0xff,
+ 0x42, 0x39, 0x11, 0xff, 0x42, 0x39, 0x10, 0xff,
+ 0x5b, 0x4d, 0x2a, 0xff, 0x5a, 0x4d, 0x29, 0xff,
+ 0x5b, 0x4d, 0x29, 0xff, 0x5a, 0x4d, 0x29, 0xff,
+ 0x6b, 0x5a, 0x3a, 0xff, 0x6b, 0x59, 0x3a, 0xff,
+ 0x6b, 0x59, 0x3a, 0xff, 0x6b, 0x59, 0x39, 0xff,
+ 0x6b, 0x5e, 0x3a, 0xff, 0x7e, 0x7c, 0x60, 0xff,
+ 0x92, 0x9c, 0x87, 0xff, 0x6b, 0x5d, 0x39, 0xff,
+ 0x6b, 0x5e, 0x3a, 0xff, 0x6b, 0x5d, 0x3a, 0xff,
+ 0x6b, 0x5d, 0x3a, 0xff, 0x6b, 0x5d, 0x39, 0xff,
+ 0x63, 0x55, 0x3a, 0xff, 0x63, 0x55, 0x3a, 0xff,
+ 0x63, 0x55, 0x3a, 0xff, 0x63, 0x55, 0x39, 0xff,
+ 0x69, 0x6a, 0x58, 0xff, 0x76, 0x7d, 0x6e, 0xff,
+ 0x76, 0x7e, 0x6e, 0xff, 0x68, 0x69, 0x58, 0xff,
+ 0x6b, 0x6a, 0x5b, 0xff, 0x6b, 0x69, 0x5a, 0xff,
+ 0x63, 0x5c, 0x4a, 0xff, 0x63, 0x5c, 0x4a, 0xff,
+ 0x63, 0x5a, 0x42, 0xff, 0x5a, 0x4d, 0x37, 0xff,
+ 0x5b, 0x4d, 0x37, 0xff, 0x52, 0x41, 0x2c, 0xff,
+ 0x53, 0x45, 0x2a, 0xff, 0x4d, 0x3d, 0x24, 0xff,
+ 0x48, 0x35, 0x1f, 0xff, 0x4d, 0x3d, 0x23, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x1e, 0x27, 0x23, 0xff,
+ 0x3a, 0x55, 0x4a, 0xff, 0x39, 0x55, 0x4a, 0xff,
+ 0x31, 0x59, 0x4a, 0xff, 0x31, 0x59, 0x4a, 0xff,
+ 0x21, 0x29, 0x24, 0xff, 0x18, 0x10, 0x10, 0xff,
+ 0x19, 0x18, 0x11, 0xff, 0x18, 0x18, 0x10, 0xff,
+ 0x19, 0x19, 0x11, 0xff, 0x18, 0x18, 0x10, 0xff,
+ 0x21, 0x1c, 0x11, 0xff, 0x20, 0x1c, 0x10, 0xff,
+ 0x21, 0x1d, 0x11, 0xff, 0x29, 0x20, 0x10, 0xff,
+ 0x31, 0x31, 0x11, 0xff, 0x31, 0x30, 0x10, 0xff,
+ 0x3a, 0x45, 0x21, 0xff, 0x39, 0x45, 0x21, 0xff,
+ 0x3a, 0x39, 0x11, 0xff, 0x39, 0x38, 0x10, 0xff,
+ 0x3a, 0x39, 0x11, 0xff, 0x39, 0x38, 0x10, 0xff,
+ 0x42, 0x39, 0x11, 0xff, 0x41, 0x38, 0x10, 0xff,
+ 0x52, 0x5f, 0x3d, 0xff, 0x52, 0x5e, 0x3c, 0xff,
+ 0x6b, 0x73, 0x55, 0xff, 0x6b, 0x72, 0x55, 0xff,
+ 0x6b, 0x73, 0x55, 0xff, 0x6b, 0x72, 0x55, 0xff,
+ 0x7b, 0x7c, 0x63, 0xff, 0x7b, 0x7c, 0x62, 0xff,
+ 0x7c, 0x7c, 0x63, 0xff, 0x7b, 0x7c, 0x62, 0xff,
+ 0x7e, 0x7c, 0x60, 0xff, 0x91, 0x9b, 0x86, 0xff,
+ 0x92, 0x9b, 0x87, 0xff, 0x7e, 0x7c, 0x60, 0xff,
+ 0x81, 0x7a, 0x60, 0xff, 0x80, 0x79, 0x60, 0xff,
+ 0x81, 0x7a, 0x60, 0xff, 0x81, 0x79, 0x60, 0xff,
+ 0x8f, 0x8e, 0x81, 0xff, 0xa4, 0xaa, 0xa4, 0xff,
+ 0xa5, 0xaa, 0xa5, 0xff, 0xa4, 0xaa, 0xa4, 0xff,
+ 0x84, 0x92, 0x84, 0xff, 0x75, 0x7d, 0x6d, 0xff,
+ 0x68, 0x69, 0x58, 0xff, 0x5a, 0x55, 0x42, 0xff,
+ 0x63, 0x5c, 0x4a, 0xff, 0x62, 0x5b, 0x4a, 0xff,
+ 0x63, 0x5c, 0x4a, 0xff, 0x5a, 0x4e, 0x39, 0xff,
+ 0x5b, 0x4d, 0x37, 0xff, 0x5a, 0x4c, 0x36, 0xff,
+ 0x52, 0x41, 0x2c, 0xff, 0x52, 0x40, 0x2c, 0xff,
+ 0x4d, 0x3d, 0x24, 0xff, 0x47, 0x34, 0x1e, 0xff,
+ 0x48, 0x35, 0x1e, 0xff, 0x47, 0x34, 0x1e, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x2c, 0x3e, 0x37, 0xff, 0x39, 0x55, 0x4a, 0xff,
+ 0x32, 0x59, 0x4a, 0xff, 0x31, 0x59, 0x4a, 0xff,
+ 0x21, 0x29, 0x24, 0xff, 0x19, 0x10, 0x10, 0xff,
+ 0x13, 0x13, 0x11, 0xff, 0x16, 0x15, 0x10, 0xff,
+ 0x16, 0x16, 0x11, 0xff, 0x19, 0x18, 0x10, 0xff,
+ 0x19, 0x19, 0x11, 0xff, 0x18, 0x18, 0x10, 0xff,
+ 0x19, 0x19, 0x11, 0xff, 0x21, 0x1c, 0x10, 0xff,
+ 0x29, 0x1d, 0x00, 0xff, 0x31, 0x30, 0x10, 0xff,
+ 0x32, 0x31, 0x11, 0xff, 0x31, 0x30, 0x10, 0xff,
+ 0x3a, 0x39, 0x11, 0xff, 0x47, 0x59, 0x37, 0xff,
+ 0x48, 0x59, 0x37, 0xff, 0x55, 0x79, 0x5d, 0xff,
+ 0x63, 0x85, 0x68, 0xff, 0x73, 0xaa, 0x94, 0xff,
+ 0x74, 0xaa, 0x94, 0xff, 0x73, 0xaa, 0x94, 0xff,
+ 0x8c, 0xbf, 0xad, 0xff, 0x8c, 0xbe, 0xad, 0xff,
+ 0x8c, 0xbf, 0xad, 0xff, 0x8c, 0xbe, 0xad, 0xff,
+ 0x9d, 0xc3, 0xb5, 0xff, 0x9c, 0xc2, 0xb5, 0xff,
+ 0x9d, 0xc3, 0xb5, 0xff, 0x9c, 0xc2, 0xb5, 0xff,
+ 0xa5, 0xba, 0xad, 0xff, 0xa4, 0xba, 0xad, 0xff,
+ 0xa5, 0xbb, 0xad, 0xff, 0xa4, 0xba, 0xad, 0xff,
+ 0xad, 0xb2, 0xad, 0xff, 0xad, 0xb2, 0xad, 0xff,
+ 0xad, 0xb3, 0xad, 0xff, 0xad, 0xb2, 0xad, 0xff,
+ 0xa5, 0xaa, 0xa5, 0xff, 0xa4, 0xaa, 0xa4, 0xff,
+ 0x8f, 0x8e, 0x81, 0xff, 0x8e, 0x8e, 0x81, 0xff,
+ 0x84, 0x92, 0x84, 0xff, 0x76, 0x7d, 0x6d, 0xff,
+ 0x5b, 0x55, 0x42, 0xff, 0x68, 0x69, 0x58, 0xff,
+ 0x63, 0x5c, 0x4a, 0xff, 0x5a, 0x4e, 0x39, 0xff,
+ 0x53, 0x41, 0x2a, 0xff, 0x52, 0x41, 0x29, 0xff,
+ 0x53, 0x41, 0x2c, 0xff, 0x5a, 0x4d, 0x37, 0xff,
+ 0x4a, 0x35, 0x21, 0xff, 0x4a, 0x35, 0x21, 0xff,
+ 0x48, 0x35, 0x1e, 0xff, 0x47, 0x34, 0x1e, 0xff,
+ 0x42, 0x2d, 0x19, 0xff, 0x42, 0x2c, 0x19, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x10, 0x10, 0x10, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x19, 0x10, 0x11, 0xff, 0x18, 0x10, 0x10, 0xff,
+ 0x19, 0x10, 0x10, 0xff, 0x18, 0x10, 0x10, 0xff,
+ 0x13, 0x13, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x13, 0x13, 0x10, 0xff, 0x18, 0x18, 0x10, 0xff,
+ 0x19, 0x18, 0x11, 0xff, 0x18, 0x18, 0x10, 0xff,
+ 0x19, 0x18, 0x10, 0xff, 0x20, 0x1c, 0x10, 0xff,
+ 0x29, 0x1c, 0x00, 0xff, 0x31, 0x30, 0x10, 0xff,
+ 0x3a, 0x45, 0x21, 0xff, 0x41, 0x59, 0x31, 0xff,
+ 0x55, 0x7a, 0x5d, 0xff, 0x62, 0x99, 0x83, 0xff,
+ 0x63, 0x9a, 0x84, 0xff, 0x62, 0x99, 0x83, 0xff,
+ 0x73, 0xaa, 0x94, 0xff, 0x73, 0xaa, 0x94, 0xff,
+ 0x73, 0xaa, 0x94, 0xff, 0x73, 0xaa, 0x94, 0xff,
+ 0x8c, 0xbe, 0xad, 0xff, 0x8b, 0xbe, 0xac, 0xff,
+ 0x8c, 0xbe, 0xad, 0xff, 0x8b, 0xbe, 0xac, 0xff,
+ 0x9c, 0xc2, 0xb5, 0xff, 0x9c, 0xc2, 0xb5, 0xff,
+ 0x9c, 0xc2, 0xb5, 0xff, 0x9c, 0xc2, 0xb4, 0xff,
+ 0xa5, 0xba, 0xad, 0xff, 0xa4, 0xba, 0xac, 0xff,
+ 0xa5, 0xba, 0xad, 0xff, 0xa4, 0xba, 0xac, 0xff,
+ 0xad, 0xb2, 0xad, 0xff, 0xac, 0xb2, 0xac, 0xff,
+ 0x97, 0x96, 0x86, 0xff, 0xac, 0xb2, 0xac, 0xff,
+ 0xa5, 0xaa, 0xa5, 0xff, 0xa4, 0xaa, 0xa4, 0xff,
+ 0x8f, 0x8e, 0x81, 0xff, 0x8e, 0x8d, 0x80, 0xff,
+ 0x76, 0x7e, 0x6e, 0xff, 0x68, 0x69, 0x57, 0xff,
+ 0x5b, 0x55, 0x42, 0xff, 0x5a, 0x55, 0x41, 0xff,
+ 0x52, 0x41, 0x29, 0xff, 0x52, 0x40, 0x29, 0xff,
+ 0x52, 0x41, 0x29, 0xff, 0x52, 0x40, 0x29, 0xff,
+ 0x52, 0x41, 0x2c, 0xff, 0x52, 0x40, 0x2c, 0xff,
+ 0x4a, 0x35, 0x21, 0xff, 0x4a, 0x34, 0x20, 0xff,
+ 0x42, 0x2d, 0x19, 0xff, 0x47, 0x34, 0x1e, 0xff,
+ 0x47, 0x35, 0x1e, 0xff, 0x41, 0x2c, 0x18, 0xff,
+ 0x11, 0x0d, 0x11, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x16, 0x18, 0x13, 0xff,
+ 0x19, 0x11, 0x11, 0xff, 0x19, 0x10, 0x10, 0xff,
+ 0x19, 0x11, 0x11, 0xff, 0x19, 0x10, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x19, 0x14, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x19, 0x14, 0x10, 0xff,
+ 0x19, 0x19, 0x11, 0xff, 0x19, 0x18, 0x10, 0xff,
+ 0x19, 0x19, 0x11, 0xff, 0x29, 0x3f, 0x31, 0xff,
+ 0x42, 0x6a, 0x53, 0xff, 0x4d, 0x79, 0x63, 0xff,
+ 0x58, 0x8a, 0x74, 0xff, 0x63, 0x9a, 0x83, 0xff,
+ 0x74, 0xa2, 0x8c, 0xff, 0x73, 0xa2, 0x8c, 0xff,
+ 0x7c, 0xaa, 0x94, 0xff, 0x73, 0xa2, 0x8c, 0xff,
+ 0x74, 0xa6, 0x8c, 0xff, 0x6b, 0x9f, 0x84, 0xff,
+ 0x74, 0xa6, 0x8c, 0xff, 0x73, 0xa6, 0x8c, 0xff,
+ 0x87, 0xb1, 0x9a, 0xff, 0x94, 0xba, 0xa4, 0xff,
+ 0x94, 0xbb, 0xa5, 0xff, 0x94, 0xba, 0xa4, 0xff,
+ 0x7f, 0xaf, 0x97, 0xff, 0x73, 0xa6, 0x8c, 0xff,
+ 0x89, 0xb6, 0xa2, 0xff, 0x7e, 0xae, 0x97, 0xff,
+ 0x9a, 0xaf, 0xa2, 0xff, 0xa4, 0xbe, 0xad, 0xff,
+ 0xa5, 0xbf, 0xad, 0xff, 0x9f, 0xb6, 0xa7, 0xff,
+ 0xad, 0xb7, 0xad, 0xff, 0xa7, 0xb1, 0xaa, 0xff,
+ 0xa2, 0xac, 0xa8, 0xff, 0x9c, 0xa6, 0xa4, 0xff,
+ 0xa0, 0xa2, 0xa0, 0xff, 0x9f, 0xa2, 0x9f, 0xff,
+ 0x9f, 0xa2, 0x9f, 0xff, 0x94, 0x96, 0x94, 0xff,
+ 0x7c, 0x77, 0x6e, 0xff, 0x63, 0x58, 0x47, 0xff,
+ 0x63, 0x58, 0x48, 0xff, 0x4a, 0x39, 0x21, 0xff,
+ 0x50, 0x41, 0x2c, 0xff, 0x45, 0x35, 0x1e, 0xff,
+ 0x45, 0x35, 0x1f, 0xff, 0x44, 0x34, 0x1e, 0xff,
+ 0x4b, 0x39, 0x21, 0xff, 0x4a, 0x39, 0x21, 0xff,
+ 0x45, 0x34, 0x1f, 0xff, 0x44, 0x33, 0x1e, 0xff,
+ 0x3a, 0x2d, 0x1f, 0xff, 0x42, 0x35, 0x24, 0xff,
+ 0x42, 0x35, 0x24, 0xff, 0x39, 0x2c, 0x1e, 0xff,
+ 0x16, 0x18, 0x13, 0xff, 0x16, 0x18, 0x13, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x16, 0x18, 0x13, 0xff,
+ 0x19, 0x10, 0x11, 0xff, 0x18, 0x10, 0x10, 0xff,
+ 0x19, 0x10, 0x11, 0xff, 0x18, 0x10, 0x10, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x18, 0x14, 0x10, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x29, 0x23, 0x1b, 0xff,
+ 0x29, 0x40, 0x31, 0xff, 0x39, 0x66, 0x52, 0xff,
+ 0x3a, 0x67, 0x52, 0xff, 0x4a, 0x8d, 0x73, 0xff,
+ 0x63, 0x9a, 0x84, 0xff, 0x62, 0x99, 0x83, 0xff,
+ 0x63, 0x9a, 0x84, 0xff, 0x62, 0x9a, 0x83, 0xff,
+ 0x73, 0xa2, 0x8c, 0xff, 0x6b, 0x99, 0x83, 0xff,
+ 0x6b, 0x9a, 0x84, 0xff, 0x73, 0xa2, 0x8c, 0xff,
+ 0x6b, 0x9f, 0x84, 0xff, 0x62, 0x98, 0x7b, 0xff,
+ 0x73, 0xa6, 0x8c, 0xff, 0x73, 0xa6, 0x8c, 0xff,
+ 0x6b, 0x9e, 0x84, 0xff, 0x86, 0xb0, 0x99, 0xff,
+ 0x87, 0xb1, 0x9a, 0xff, 0x94, 0xba, 0xa4, 0xff,
+ 0x89, 0xb6, 0xa2, 0xff, 0x94, 0xbe, 0xac, 0xff,
+ 0x94, 0xbe, 0xad, 0xff, 0x89, 0xb6, 0xa1, 0xff,
+ 0x9f, 0xb6, 0xa7, 0xff, 0x99, 0xae, 0xa1, 0xff,
+ 0xa5, 0xbe, 0xad, 0xff, 0xa4, 0xbe, 0xac, 0xff,
+ 0xad, 0xb6, 0xad, 0xff, 0xa7, 0xb0, 0xaa, 0xff,
+ 0xa2, 0xac, 0xa7, 0xff, 0xa1, 0xab, 0xa7, 0xff,
+ 0x9f, 0xa2, 0x9f, 0xff, 0xaa, 0xae, 0xaa, 0xff,
+ 0x9f, 0xa2, 0x9f, 0xff, 0x94, 0x95, 0x94, 0xff,
+ 0x7b, 0x77, 0x6e, 0xff, 0x62, 0x57, 0x47, 0xff,
+ 0x4a, 0x39, 0x21, 0xff, 0x4a, 0x38, 0x21, 0xff,
+ 0x45, 0x35, 0x1e, 0xff, 0x44, 0x34, 0x1e, 0xff,
+ 0x45, 0x35, 0x1e, 0xff, 0x44, 0x34, 0x1e, 0xff,
+ 0x3f, 0x2e, 0x1c, 0xff, 0x3f, 0x2d, 0x1b, 0xff,
+ 0x3f, 0x2e, 0x1c, 0xff, 0x3f, 0x2e, 0x1b, 0xff,
+ 0x4a, 0x3d, 0x29, 0xff, 0x41, 0x34, 0x23, 0xff,
+ 0x32, 0x25, 0x19, 0xff, 0x31, 0x24, 0x18, 0xff,
+ 0x16, 0x19, 0x13, 0xff, 0x16, 0x18, 0x13, 0xff,
+ 0x16, 0x19, 0x14, 0xff, 0x16, 0x18, 0x13, 0xff,
+ 0x29, 0x1d, 0x19, 0xff, 0x29, 0x1c, 0x18, 0xff,
+ 0x2a, 0x1d, 0x19, 0xff, 0x29, 0x1c, 0x19, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x29, 0x23, 0x1b, 0xff,
+ 0x3a, 0x32, 0x27, 0xff, 0x4a, 0x41, 0x31, 0xff,
+ 0x3a, 0x67, 0x53, 0xff, 0x29, 0x3f, 0x31, 0xff,
+ 0x3a, 0x67, 0x53, 0xff, 0x4a, 0x8e, 0x73, 0xff,
+ 0x58, 0x8a, 0x73, 0xff, 0x62, 0x9a, 0x83, 0xff,
+ 0x63, 0x9a, 0x84, 0xff, 0x63, 0x9a, 0x84, 0xff,
+ 0x63, 0x92, 0x7c, 0xff, 0x6b, 0x9a, 0x83, 0xff,
+ 0x6b, 0x9a, 0x84, 0xff, 0x73, 0xa2, 0x8c, 0xff,
+ 0x73, 0xa6, 0x8c, 0xff, 0x73, 0xa6, 0x8c, 0xff,
+ 0x74, 0xa6, 0x8c, 0xff, 0x73, 0xa6, 0x8c, 0xff,
+ 0x79, 0xa8, 0x8f, 0xff, 0x86, 0xb1, 0x99, 0xff,
+ 0x87, 0xb1, 0x9a, 0xff, 0x86, 0xb1, 0x99, 0xff,
+ 0x89, 0xb6, 0xa2, 0xff, 0x94, 0xbe, 0xad, 0xff,
+ 0x8a, 0xb7, 0xa2, 0xff, 0x89, 0xb6, 0xa2, 0xff,
+ 0x9f, 0xb6, 0xa8, 0xff, 0x9f, 0xb6, 0xa7, 0xff,
+ 0x94, 0xa6, 0x9d, 0xff, 0x99, 0xae, 0xa2, 0xff,
+ 0xad, 0xb6, 0xad, 0xff, 0xa7, 0xb1, 0xaa, 0xff,
+ 0xad, 0xb7, 0xad, 0xff, 0xa7, 0xb1, 0xaa, 0xff,
+ 0xb5, 0xba, 0xb5, 0xff, 0xaa, 0xae, 0xaa, 0xff,
+ 0x9f, 0xa2, 0x9f, 0xff, 0x9f, 0xa2, 0x9f, 0xff,
+ 0x94, 0x96, 0x94, 0xff, 0x7b, 0x77, 0x6d, 0xff,
+ 0x63, 0x58, 0x48, 0xff, 0x4a, 0x39, 0x21, 0xff,
+ 0x3a, 0x29, 0x11, 0xff, 0x39, 0x28, 0x10, 0xff,
+ 0x3a, 0x29, 0x11, 0xff, 0x39, 0x28, 0x10, 0xff,
+ 0x3a, 0x29, 0x19, 0xff, 0x39, 0x28, 0x18, 0xff,
+ 0x3a, 0x29, 0x19, 0xff, 0x39, 0x28, 0x19, 0xff,
+ 0x42, 0x35, 0x24, 0xff, 0x42, 0x34, 0x23, 0xff,
+ 0x32, 0x25, 0x19, 0xff, 0x31, 0x24, 0x19, 0xff,
+ 0x1c, 0x25, 0x16, 0xff, 0x21, 0x30, 0x18, 0xff,
+ 0x1b, 0x24, 0x16, 0xff, 0x15, 0x18, 0x13, 0xff,
+ 0x29, 0x1c, 0x19, 0xff, 0x29, 0x1c, 0x18, 0xff,
+ 0x3a, 0x29, 0x21, 0xff, 0x4a, 0x34, 0x29, 0xff,
+ 0x4a, 0x41, 0x32, 0xff, 0x4a, 0x40, 0x31, 0xff,
+ 0x4a, 0x41, 0x31, 0xff, 0x4a, 0x40, 0x31, 0xff,
+ 0x29, 0x40, 0x32, 0xff, 0x29, 0x3f, 0x31, 0xff,
+ 0x29, 0x3f, 0x31, 0xff, 0x4a, 0x8d, 0x73, 0xff,
+ 0x58, 0x8a, 0x73, 0xff, 0x57, 0x89, 0x73, 0xff,
+ 0x63, 0x9a, 0x84, 0xff, 0x62, 0x99, 0x83, 0xff,
+ 0x6b, 0x9a, 0x84, 0xff, 0x6b, 0x99, 0x83, 0xff,
+ 0x73, 0xa2, 0x8c, 0xff, 0x73, 0xa1, 0x8b, 0xff,
+ 0x63, 0x99, 0x7c, 0xff, 0x5a, 0x91, 0x73, 0xff,
+ 0x63, 0x98, 0x7b, 0xff, 0x73, 0xa5, 0x8b, 0xff,
+ 0x79, 0xa7, 0x8f, 0xff, 0x86, 0xb0, 0x99, 0xff,
+ 0x86, 0xb1, 0x9a, 0xff, 0x6a, 0x9d, 0x83, 0xff,
+ 0x73, 0xa6, 0x8c, 0xff, 0x7e, 0xae, 0x96, 0xff,
+ 0x89, 0xb6, 0xa2, 0xff, 0x89, 0xb6, 0xa1, 0xff,
+ 0x9f, 0xb6, 0xa7, 0xff, 0x9f, 0xb6, 0xa7, 0xff,
+ 0x94, 0xa6, 0x9c, 0xff, 0x94, 0xa5, 0x9c, 0xff,
+ 0xa2, 0xac, 0xa7, 0xff, 0xac, 0xb6, 0xac, 0xff,
+ 0xa7, 0xb1, 0xaa, 0xff, 0xa7, 0xb0, 0xaa, 0xff,
+ 0xb5, 0xba, 0xb5, 0xff, 0xb5, 0xba, 0xb5, 0xff,
+ 0xaa, 0xae, 0xaa, 0xff, 0x9f, 0xa1, 0x9f, 0xff,
+ 0x94, 0x96, 0x94, 0xff, 0x94, 0x95, 0x94, 0xff,
+ 0x7b, 0x77, 0x6e, 0xff, 0x7b, 0x76, 0x6d, 0xff,
+ 0x5b, 0x4d, 0x3a, 0xff, 0x5a, 0x4d, 0x39, 0xff,
+ 0x45, 0x35, 0x1e, 0xff, 0x44, 0x34, 0x1e, 0xff,
+ 0x3f, 0x2e, 0x1c, 0xff, 0x3f, 0x2e, 0x1b, 0xff,
+ 0x3f, 0x2e, 0x1b, 0xff, 0x39, 0x28, 0x18, 0xff,
+ 0x3a, 0x2d, 0x1e, 0xff, 0x39, 0x2c, 0x1e, 0xff,
+ 0x42, 0x35, 0x24, 0xff, 0x41, 0x34, 0x23, 0xff,
+ 0x2a, 0x35, 0x19, 0xff, 0x29, 0x35, 0x19, 0xff,
+ 0x29, 0x35, 0x19, 0xff, 0x29, 0x34, 0x19, 0xff,
+ 0x21, 0x25, 0x11, 0xff, 0x21, 0x24, 0x10, 0xff,
+ 0x21, 0x25, 0x11, 0xff, 0x21, 0x24, 0x10, 0xff,
+ 0x4b, 0x35, 0x32, 0xff, 0x4a, 0x35, 0x31, 0xff,
+ 0x50, 0x54, 0x4d, 0xff, 0x55, 0x73, 0x68, 0xff,
+ 0x84, 0x81, 0x7f, 0xff, 0x84, 0x80, 0x7e, 0xff,
+ 0x74, 0x73, 0x71, 0xff, 0x63, 0x65, 0x63, 0xff,
+ 0x2a, 0x41, 0x2a, 0xff, 0x29, 0x41, 0x29, 0xff,
+ 0x4d, 0x5b, 0x4a, 0xff, 0x70, 0x74, 0x6b, 0xff,
+ 0x74, 0x9e, 0x8c, 0xff, 0x73, 0x9e, 0x8c, 0xff,
+ 0x74, 0x9e, 0x8c, 0xff, 0x73, 0x9e, 0x8c, 0xff,
+ 0x74, 0xa6, 0x8c, 0xff, 0x68, 0x90, 0x79, 0xff,
+ 0x74, 0xa6, 0x8c, 0xff, 0x73, 0xa6, 0x8c, 0xff,
+ 0x71, 0x9a, 0x7f, 0xff, 0x7b, 0xa6, 0x8c, 0xff,
+ 0x71, 0x9a, 0x7e, 0xff, 0x65, 0x8e, 0x70, 0xff,
+ 0x6b, 0x9e, 0x84, 0xff, 0x73, 0xa5, 0x8c, 0xff,
+ 0x84, 0xb2, 0x9d, 0xff, 0x83, 0xb2, 0x9c, 0xff,
+ 0x8c, 0xb7, 0xa5, 0xff, 0x8c, 0xb6, 0xa4, 0xff,
+ 0x81, 0xae, 0x9a, 0xff, 0x81, 0xae, 0x99, 0xff,
+ 0x8c, 0xaf, 0xa5, 0xff, 0x89, 0xa9, 0x9f, 0xff,
+ 0x89, 0xa9, 0x9f, 0xff, 0x89, 0xa8, 0x9f, 0xff,
+ 0x97, 0xaa, 0xa5, 0xff, 0x97, 0xaa, 0xa4, 0xff,
+ 0xa5, 0xb2, 0xad, 0xff, 0xa4, 0xb2, 0xad, 0xff,
+ 0x9a, 0xa8, 0xa2, 0xff, 0xad, 0xae, 0xad, 0xff,
+ 0x9a, 0xa8, 0xa2, 0xff, 0xad, 0xae, 0xad, 0xff,
+ 0x87, 0x8a, 0x87, 0xff, 0x79, 0x75, 0x70, 0xff,
+ 0x79, 0x76, 0x71, 0xff, 0x6b, 0x61, 0x5a, 0xff,
+ 0x5e, 0x55, 0x4d, 0xff, 0x5d, 0x55, 0x4d, 0xff,
+ 0x42, 0x35, 0x29, 0xff, 0x42, 0x34, 0x29, 0xff,
+ 0x4b, 0x44, 0x37, 0xff, 0x5a, 0x59, 0x52, 0xff,
+ 0x4a, 0x44, 0x37, 0xff, 0x42, 0x39, 0x29, 0xff,
+ 0x29, 0x35, 0x19, 0xff, 0x29, 0x34, 0x18, 0xff,
+ 0x29, 0x35, 0x19, 0xff, 0x29, 0x34, 0x18, 0xff,
+ 0x2f, 0x4a, 0x34, 0xff, 0x2e, 0x4a, 0x34, 0xff,
+ 0x2f, 0x4a, 0x34, 0xff, 0x2e, 0x4a, 0x34, 0xff,
+ 0x50, 0x54, 0x4d, 0xff, 0x4f, 0x53, 0x4c, 0xff,
+ 0x55, 0x73, 0x68, 0xff, 0x55, 0x72, 0x68, 0xff,
+ 0x84, 0x80, 0x7e, 0xff, 0x94, 0x8d, 0x8b, 0xff,
+ 0x94, 0x8e, 0x8c, 0xff, 0x94, 0x8d, 0x8c, 0xff,
+ 0x71, 0x74, 0x6b, 0xff, 0x70, 0x74, 0x6b, 0xff,
+ 0x4d, 0x5b, 0x4a, 0xff, 0x4c, 0x5a, 0x4a, 0xff,
+ 0x4a, 0x4d, 0x3a, 0xff, 0x4a, 0x4c, 0x39, 0xff,
+ 0x58, 0x68, 0x55, 0xff, 0x73, 0x9e, 0x8c, 0xff,
+ 0x68, 0x90, 0x79, 0xff, 0x68, 0x90, 0x78, 0xff,
+ 0x68, 0x91, 0x79, 0xff, 0x68, 0x90, 0x78, 0xff,
+ 0x5b, 0x82, 0x63, 0xff, 0x65, 0x8d, 0x70, 0xff,
+ 0x71, 0x9a, 0x7e, 0xff, 0x70, 0x9a, 0x7e, 0xff,
+ 0x73, 0xa5, 0x8c, 0xff, 0x7b, 0xab, 0x94, 0xff,
+ 0x84, 0xb2, 0x9d, 0xff, 0x83, 0xb2, 0x9c, 0xff,
+ 0x86, 0xb2, 0x9f, 0xff, 0x86, 0xb2, 0x9f, 0xff,
+ 0x87, 0xb2, 0x9f, 0xff, 0x81, 0xae, 0x99, 0xff,
+ 0x8c, 0xae, 0xa5, 0xff, 0x89, 0xa8, 0x9f, 0xff,
+ 0x89, 0xa9, 0x9f, 0xff, 0x86, 0xa3, 0x99, 0xff,
+ 0x89, 0xa2, 0x9c, 0xff, 0x7b, 0x99, 0x94, 0xff,
+ 0x97, 0xaa, 0xa5, 0xff, 0x97, 0xaa, 0xa4, 0xff,
+ 0x9a, 0xa7, 0xa2, 0xff, 0xac, 0xae, 0xac, 0xff,
+ 0x9a, 0xa8, 0xa2, 0xff, 0xac, 0xae, 0xac, 0xff,
+ 0x94, 0x9e, 0x9c, 0xff, 0x94, 0x9d, 0x9c, 0xff,
+ 0x94, 0x9e, 0x9d, 0xff, 0x94, 0x9e, 0x9c, 0xff,
+ 0x94, 0x96, 0x94, 0xff, 0x94, 0x95, 0x94, 0xff,
+ 0x79, 0x76, 0x71, 0xff, 0x5d, 0x55, 0x4c, 0xff,
+ 0x4a, 0x44, 0x37, 0xff, 0x4a, 0x43, 0x36, 0xff,
+ 0x52, 0x4e, 0x45, 0xff, 0x52, 0x4e, 0x44, 0xff,
+ 0x29, 0x35, 0x19, 0xff, 0x29, 0x34, 0x18, 0xff,
+ 0x2a, 0x35, 0x19, 0xff, 0x31, 0x50, 0x37, 0xff,
+ 0x3d, 0x70, 0x58, 0xff, 0x4a, 0x96, 0x7b, 0xff,
+ 0x4a, 0x96, 0x7c, 0xff, 0x4a, 0x96, 0x7b, 0xff,
+ 0x5b, 0x92, 0x84, 0xff, 0x55, 0x72, 0x68, 0xff,
+ 0x55, 0x73, 0x69, 0xff, 0x4f, 0x54, 0x4d, 0xff,
+ 0x63, 0x65, 0x63, 0xff, 0x73, 0x72, 0x70, 0xff,
+ 0x84, 0x81, 0x7f, 0xff, 0x84, 0x80, 0x7e, 0xff,
+ 0x94, 0x8e, 0x8c, 0xff, 0x94, 0x8d, 0x8c, 0xff,
+ 0x94, 0x8e, 0x8c, 0xff, 0x70, 0x74, 0x6b, 0xff,
+ 0x58, 0x68, 0x55, 0xff, 0x58, 0x68, 0x55, 0xff,
+ 0x58, 0x68, 0x55, 0xff, 0x58, 0x68, 0x55, 0xff,
+ 0x5e, 0x7b, 0x66, 0xff, 0x5d, 0x7b, 0x65, 0xff,
+ 0x69, 0x91, 0x79, 0xff, 0x68, 0x90, 0x79, 0xff,
+ 0x7c, 0xa6, 0x8c, 0xff, 0x7b, 0xa6, 0x8c, 0xff,
+ 0x7c, 0xa6, 0x8c, 0xff, 0x7b, 0xa6, 0x8c, 0xff,
+ 0x73, 0xa5, 0x8c, 0xff, 0x73, 0xa4, 0x8c, 0xff,
+ 0x6b, 0x9e, 0x84, 0xff, 0x7b, 0xab, 0x94, 0xff,
+ 0x81, 0xae, 0x9a, 0xff, 0x86, 0xb2, 0x9f, 0xff,
+ 0x87, 0xb3, 0x9f, 0xff, 0x7b, 0xaa, 0x94, 0xff,
+ 0x89, 0xa9, 0x9f, 0xff, 0x86, 0xa3, 0x99, 0xff,
+ 0x84, 0x9e, 0x94, 0xff, 0x86, 0xa3, 0x99, 0xff,
+ 0x89, 0xa2, 0x9d, 0xff, 0x89, 0xa2, 0x9c, 0xff,
+ 0x7c, 0x9a, 0x94, 0xff, 0x89, 0xa2, 0x9c, 0xff,
+ 0x87, 0xa1, 0x97, 0xff, 0x99, 0xa7, 0xa2, 0xff,
+ 0x87, 0xa1, 0x97, 0xff, 0x86, 0xa0, 0x97, 0xff,
+ 0x94, 0x9e, 0x9d, 0xff, 0x94, 0x9e, 0x9c, 0xff,
+ 0x94, 0x9e, 0x9d, 0xff, 0x94, 0x9e, 0x9c, 0xff,
+ 0x94, 0x96, 0x94, 0xff, 0x94, 0x96, 0x94, 0xff,
+ 0x94, 0x96, 0x94, 0xff, 0x79, 0x75, 0x70, 0xff,
+ 0x53, 0x4f, 0x45, 0xff, 0x42, 0x38, 0x29, 0xff,
+ 0x42, 0x39, 0x2a, 0xff, 0x42, 0x39, 0x29, 0xff,
+ 0x3a, 0x6b, 0x55, 0xff, 0x39, 0x6a, 0x55, 0xff,
+ 0x3a, 0x6b, 0x55, 0xff, 0x41, 0x85, 0x73, 0xff,
+ 0x4a, 0x96, 0x7c, 0xff, 0x4a, 0x95, 0x7b, 0xff,
+ 0x4a, 0x96, 0x7b, 0xff, 0x4a, 0x95, 0x7b, 0xff,
+ 0x5b, 0x92, 0x84, 0xff, 0x5a, 0x91, 0x83, 0xff,
+ 0x5b, 0x92, 0x84, 0xff, 0x55, 0x72, 0x68, 0xff,
+ 0x63, 0x65, 0x63, 0xff, 0x73, 0x72, 0x70, 0xff,
+ 0x73, 0x73, 0x70, 0xff, 0x73, 0x72, 0x70, 0xff,
+ 0x71, 0x74, 0x6b, 0xff, 0x70, 0x74, 0x6b, 0xff,
+ 0x94, 0x8e, 0x8c, 0xff, 0x70, 0x74, 0x6a, 0xff,
+ 0x66, 0x83, 0x71, 0xff, 0x73, 0x9e, 0x8b, 0xff,
+ 0x65, 0x83, 0x70, 0xff, 0x65, 0x82, 0x70, 0xff,
+ 0x5d, 0x7b, 0x66, 0xff, 0x52, 0x65, 0x52, 0xff,
+ 0x52, 0x65, 0x52, 0xff, 0x5d, 0x7a, 0x65, 0xff,
+ 0x5b, 0x82, 0x63, 0xff, 0x65, 0x8d, 0x70, 0xff,
+ 0x70, 0x9a, 0x7e, 0xff, 0x7b, 0xa5, 0x8b, 0xff,
+ 0x6b, 0x9e, 0x84, 0xff, 0x6b, 0x9e, 0x83, 0xff,
+ 0x6b, 0x9e, 0x84, 0xff, 0x6a, 0x9d, 0x83, 0xff,
+ 0x7c, 0xaa, 0x94, 0xff, 0x81, 0xae, 0x99, 0xff,
+ 0x7b, 0xaa, 0x94, 0xff, 0x80, 0xae, 0x99, 0xff,
+ 0x8c, 0xae, 0xa5, 0xff, 0x89, 0xa8, 0x9f, 0xff,
+ 0x84, 0x9e, 0x94, 0xff, 0x86, 0xa3, 0x99, 0xff,
+ 0x97, 0xaa, 0xa5, 0xff, 0x89, 0xa2, 0x9c, 0xff,
+ 0x7b, 0x9a, 0x94, 0xff, 0x7b, 0x99, 0x94, 0xff,
+ 0x73, 0x9a, 0x8c, 0xff, 0x73, 0x99, 0x8b, 0xff,
+ 0x86, 0xa1, 0x97, 0xff, 0x86, 0xa0, 0x96, 0xff,
+ 0x94, 0x9e, 0x9c, 0xff, 0x94, 0x9e, 0x9c, 0xff,
+ 0x94, 0x9e, 0x9c, 0xff, 0x94, 0x9d, 0x9c, 0xff,
+ 0x94, 0x96, 0x94, 0xff, 0x94, 0x95, 0x94, 0xff,
+ 0x94, 0x96, 0x94, 0xff, 0x78, 0x75, 0x70, 0xff,
+ 0x5b, 0x59, 0x52, 0xff, 0x4a, 0x43, 0x36, 0xff,
+ 0x4a, 0x43, 0x37, 0xff, 0x41, 0x38, 0x29, 0xff,
+ 0x4b, 0x8b, 0x76, 0xff, 0x52, 0x92, 0x7b, 0xff,
+ 0x53, 0x92, 0x7c, 0xff, 0x42, 0x84, 0x70, 0xff,
+ 0x48, 0x89, 0x76, 0xff, 0x47, 0x88, 0x76, 0xff,
+ 0x53, 0x96, 0x84, 0xff, 0x52, 0x96, 0x83, 0xff,
+ 0x50, 0x98, 0x84, 0xff, 0x5a, 0x9e, 0x8c, 0xff,
+ 0x5b, 0x9e, 0x8c, 0xff, 0x44, 0x90, 0x7b, 0xff,
+ 0x55, 0x75, 0x6b, 0xff, 0x52, 0x61, 0x5a, 0xff,
+ 0x53, 0x61, 0x5b, 0xff, 0x55, 0x74, 0x6b, 0xff,
+ 0x76, 0x81, 0x76, 0xff, 0x68, 0x6f, 0x68, 0xff,
+ 0x69, 0x6f, 0x69, 0xff, 0x76, 0x80, 0x76, 0xff,
+ 0x7f, 0x7f, 0x7c, 0xff, 0x7e, 0x7f, 0x7b, 0xff,
+ 0x89, 0x89, 0x84, 0xff, 0x94, 0x92, 0x8c, 0xff,
+ 0x92, 0x91, 0x8c, 0xff, 0x91, 0x90, 0x8c, 0xff,
+ 0x92, 0x91, 0x8c, 0xff, 0x83, 0x81, 0x7b, 0xff,
+ 0x53, 0x62, 0x42, 0xff, 0x52, 0x61, 0x42, 0xff,
+ 0x53, 0x61, 0x42, 0xff, 0x52, 0x61, 0x42, 0xff,
+ 0x74, 0x8a, 0x76, 0xff, 0x7b, 0x9a, 0x84, 0xff,
+ 0x74, 0x8a, 0x76, 0xff, 0x73, 0x89, 0x76, 0xff,
+ 0x60, 0x94, 0x7c, 0xff, 0x6b, 0xa6, 0x8c, 0xff,
+ 0x6b, 0xa6, 0x8c, 0xff, 0x6b, 0xa6, 0x8c, 0xff,
+ 0x71, 0xa0, 0x8f, 0xff, 0x7b, 0xa6, 0x94, 0xff,
+ 0x71, 0xa0, 0x8f, 0xff, 0x65, 0x98, 0x89, 0xff,
+ 0x76, 0xa0, 0x95, 0xff, 0x68, 0x98, 0x8c, 0xff,
+ 0x84, 0xa6, 0x9d, 0xff, 0x83, 0xa6, 0x9c, 0xff,
+ 0x7c, 0x98, 0x92, 0xff, 0x7b, 0x97, 0x91, 0xff,
+ 0x6b, 0x91, 0x87, 0xff, 0x8c, 0x9e, 0x9c, 0xff,
+ 0x7c, 0x9a, 0x95, 0xff, 0x7b, 0x9a, 0x94, 0xff,
+ 0x7c, 0x9a, 0x94, 0xff, 0x7b, 0x9a, 0x94, 0xff,
+ 0x84, 0x96, 0x95, 0xff, 0x84, 0x96, 0x94, 0xff,
+ 0x74, 0x8b, 0x84, 0xff, 0x7b, 0x90, 0x8c, 0xff,
+ 0x7c, 0x96, 0x95, 0xff, 0x5a, 0x6b, 0x68, 0xff,
+ 0x5b, 0x6b, 0x69, 0xff, 0x4a, 0x55, 0x52, 0xff,
+ 0x52, 0x92, 0x7b, 0xff, 0x4a, 0x8b, 0x75, 0xff,
+ 0x52, 0x92, 0x7c, 0xff, 0x52, 0x91, 0x7b, 0xff,
+ 0x47, 0x88, 0x76, 0xff, 0x47, 0x88, 0x75, 0xff,
+ 0x48, 0x88, 0x76, 0xff, 0x47, 0x88, 0x76, 0xff,
+ 0x50, 0x97, 0x84, 0xff, 0x4f, 0x97, 0x83, 0xff,
+ 0x5b, 0x9e, 0x8c, 0xff, 0x4f, 0x97, 0x83, 0xff,
+ 0x58, 0x87, 0x7b, 0xff, 0x57, 0x87, 0x7b, 0xff,
+ 0x55, 0x74, 0x6b, 0xff, 0x52, 0x61, 0x5a, 0xff,
+ 0x5b, 0x5d, 0x5b, 0xff, 0x68, 0x6e, 0x68, 0xff,
+ 0x76, 0x80, 0x76, 0xff, 0x68, 0x6e, 0x68, 0xff,
+ 0x73, 0x75, 0x73, 0xff, 0x89, 0x88, 0x83, 0xff,
+ 0x89, 0x88, 0x84, 0xff, 0x7e, 0x7f, 0x7b, 0xff,
+ 0x91, 0x90, 0x8c, 0xff, 0x91, 0x90, 0x8b, 0xff,
+ 0x92, 0x91, 0x8c, 0xff, 0x91, 0x90, 0x8c, 0xff,
+ 0x94, 0x92, 0x8c, 0xff, 0x94, 0x91, 0x8b, 0xff,
+ 0x7e, 0x82, 0x73, 0xff, 0x68, 0x71, 0x5a, 0xff,
+ 0x6b, 0x7a, 0x68, 0xff, 0x6b, 0x79, 0x68, 0xff,
+ 0x73, 0x8a, 0x76, 0xff, 0x7b, 0x9a, 0x83, 0xff,
+ 0x6b, 0xa6, 0x8c, 0xff, 0x60, 0x93, 0x7b, 0xff,
+ 0x60, 0x93, 0x7c, 0xff, 0x6b, 0xa6, 0x8c, 0xff,
+ 0x66, 0x99, 0x89, 0xff, 0x65, 0x98, 0x89, 0xff,
+ 0x71, 0x9f, 0x8f, 0xff, 0x70, 0x9f, 0x8e, 0xff,
+ 0x76, 0x9f, 0x94, 0xff, 0x75, 0x9f, 0x94, 0xff,
+ 0x76, 0x9f, 0x94, 0xff, 0x76, 0x9f, 0x94, 0xff,
+ 0x7b, 0x97, 0x91, 0xff, 0x8b, 0x9d, 0x9c, 0xff,
+ 0x6b, 0x91, 0x87, 0xff, 0x6b, 0x90, 0x86, 0xff,
+ 0x79, 0x93, 0x8f, 0xff, 0x7b, 0x99, 0x94, 0xff,
+ 0x7c, 0x9a, 0x94, 0xff, 0x7b, 0x9a, 0x94, 0xff,
+ 0x84, 0x96, 0x94, 0xff, 0x7b, 0x90, 0x8b, 0xff,
+ 0x7c, 0x91, 0x8c, 0xff, 0x73, 0x8b, 0x83, 0xff,
+ 0x7b, 0x96, 0x94, 0xff, 0x7b, 0x95, 0x94, 0xff,
+ 0x6b, 0x80, 0x7e, 0xff, 0x5a, 0x6a, 0x68, 0xff,
+ 0x42, 0x85, 0x71, 0xff, 0x4a, 0x8b, 0x76, 0xff,
+ 0x4a, 0x8b, 0x76, 0xff, 0x4a, 0x8b, 0x76, 0xff,
+ 0x3d, 0x7b, 0x68, 0xff, 0x47, 0x88, 0x76, 0xff,
+ 0x48, 0x89, 0x76, 0xff, 0x52, 0x96, 0x84, 0xff,
+ 0x50, 0x97, 0x84, 0xff, 0x39, 0x89, 0x73, 0xff,
+ 0x45, 0x91, 0x7c, 0xff, 0x5a, 0x9e, 0x8c, 0xff,
+ 0x5b, 0x9a, 0x8c, 0xff, 0x5a, 0x9a, 0x8c, 0xff,
+ 0x58, 0x87, 0x7c, 0xff, 0x52, 0x61, 0x5a, 0xff,
+ 0x5b, 0x5d, 0x5b, 0xff, 0x5a, 0x5d, 0x5a, 0xff,
+ 0x69, 0x6f, 0x69, 0xff, 0x76, 0x80, 0x76, 0xff,
+ 0x7e, 0x7f, 0x7c, 0xff, 0x73, 0x75, 0x73, 0xff,
+ 0x7f, 0x7f, 0x7c, 0xff, 0x7e, 0x7f, 0x7b, 0xff,
+ 0x92, 0x91, 0x8c, 0xff, 0x91, 0x90, 0x8c, 0xff,
+ 0xad, 0xae, 0xad, 0xff, 0x9f, 0x9f, 0x9c, 0xff,
+ 0x94, 0x92, 0x8c, 0xff, 0x94, 0x91, 0x8c, 0xff,
+ 0x94, 0x92, 0x8c, 0xff, 0x94, 0x92, 0x8c, 0xff,
+ 0x73, 0x8a, 0x76, 0xff, 0x6b, 0x79, 0x68, 0xff,
+ 0x63, 0x6a, 0x5b, 0xff, 0x63, 0x69, 0x5a, 0xff,
+ 0x4a, 0x6e, 0x5b, 0xff, 0x4a, 0x6d, 0x5a, 0xff,
+ 0x55, 0x81, 0x6b, 0xff, 0x60, 0x93, 0x7b, 0xff,
+ 0x71, 0x9f, 0x8f, 0xff, 0x65, 0x98, 0x89, 0xff,
+ 0x66, 0x99, 0x8a, 0xff, 0x70, 0x9f, 0x8e, 0xff,
+ 0x84, 0xa6, 0x9d, 0xff, 0x76, 0x9f, 0x94, 0xff,
+ 0x84, 0xa6, 0x9d, 0xff, 0x68, 0x98, 0x8c, 0xff,
+ 0x6b, 0x91, 0x87, 0xff, 0x8c, 0x9e, 0x9c, 0xff,
+ 0x8c, 0x9e, 0x9d, 0xff, 0x7b, 0x97, 0x91, 0xff,
+ 0x76, 0x8d, 0x89, 0xff, 0x78, 0x93, 0x8e, 0xff,
+ 0x74, 0x86, 0x84, 0xff, 0x73, 0x85, 0x84, 0xff,
+ 0x73, 0x8b, 0x84, 0xff, 0x6b, 0x85, 0x7b, 0xff,
+ 0x74, 0x8b, 0x84, 0xff, 0x73, 0x8b, 0x84, 0xff,
+ 0x6b, 0x80, 0x7e, 0xff, 0x5a, 0x6a, 0x68, 0xff,
+ 0x6b, 0x81, 0x7f, 0xff, 0x5a, 0x6a, 0x68, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x41, 0x84, 0x70, 0xff,
+ 0x4a, 0x8b, 0x76, 0xff, 0x39, 0x7d, 0x6a, 0xff,
+ 0x32, 0x6d, 0x5b, 0xff, 0x3c, 0x7a, 0x68, 0xff,
+ 0x47, 0x88, 0x76, 0xff, 0x47, 0x88, 0x75, 0xff,
+ 0x3a, 0x8a, 0x73, 0xff, 0x44, 0x90, 0x7b, 0xff,
+ 0x45, 0x90, 0x7b, 0xff, 0x44, 0x90, 0x7b, 0xff,
+ 0x5b, 0x9a, 0x8c, 0xff, 0x5a, 0x99, 0x8b, 0xff,
+ 0x5b, 0x9a, 0x8c, 0xff, 0x5a, 0x99, 0x8b, 0xff,
+ 0x84, 0x92, 0x84, 0xff, 0x68, 0x6e, 0x68, 0xff,
+ 0x5b, 0x5d, 0x5b, 0xff, 0x68, 0x6e, 0x68, 0xff,
+ 0x73, 0x76, 0x73, 0xff, 0x73, 0x75, 0x73, 0xff,
+ 0x73, 0x75, 0x73, 0xff, 0x73, 0x75, 0x73, 0xff,
+ 0x84, 0x82, 0x7c, 0xff, 0x83, 0x81, 0x7b, 0xff,
+ 0x91, 0x90, 0x8c, 0xff, 0x91, 0x90, 0x8b, 0xff,
+ 0x94, 0x92, 0x8c, 0xff, 0x94, 0x91, 0x8b, 0xff,
+ 0x94, 0x92, 0x8c, 0xff, 0x94, 0x91, 0x8b, 0xff,
+ 0x73, 0x8a, 0x76, 0xff, 0x7b, 0x99, 0x83, 0xff,
+ 0x73, 0x8a, 0x76, 0xff, 0x73, 0x89, 0x75, 0xff,
+ 0x4a, 0x6d, 0x5b, 0xff, 0x4a, 0x6d, 0x5a, 0xff,
+ 0x4a, 0x6d, 0x5b, 0xff, 0x5f, 0x93, 0x7b, 0xff,
+ 0x5b, 0x92, 0x84, 0xff, 0x70, 0x9f, 0x8e, 0xff,
+ 0x65, 0x98, 0x89, 0xff, 0x65, 0x98, 0x89, 0xff,
+ 0x68, 0x99, 0x8c, 0xff, 0x68, 0x98, 0x8b, 0xff,
+ 0x76, 0x9f, 0x94, 0xff, 0x5a, 0x91, 0x83, 0xff,
+ 0x5b, 0x8a, 0x7c, 0xff, 0x6b, 0x90, 0x86, 0xff,
+ 0x6b, 0x90, 0x86, 0xff, 0x7b, 0x97, 0x91, 0xff,
+ 0x73, 0x86, 0x84, 0xff, 0x73, 0x85, 0x83, 0xff,
+ 0x73, 0x86, 0x84, 0xff, 0x78, 0x93, 0x8e, 0xff,
+ 0x6b, 0x86, 0x7c, 0xff, 0x73, 0x8b, 0x83, 0xff,
+ 0x73, 0x8b, 0x84, 0xff, 0x7b, 0x90, 0x8b, 0xff,
+ 0x6b, 0x80, 0x7e, 0xff, 0x7b, 0x95, 0x94, 0xff,
+ 0x7b, 0x96, 0x94, 0xff, 0x6a, 0x80, 0x7e, 0xff,
+ 0x45, 0x8a, 0x76, 0xff, 0x3f, 0x86, 0x70, 0xff,
+ 0x4a, 0x8e, 0x7c, 0xff, 0x4a, 0x8e, 0x7b, 0xff,
+ 0x45, 0x8f, 0x7c, 0xff, 0x3f, 0x88, 0x73, 0xff,
+ 0x3a, 0x82, 0x6b, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x3a, 0x85, 0x6e, 0xff, 0x42, 0x8f, 0x79, 0xff,
+ 0x42, 0x8f, 0x79, 0xff, 0x4a, 0x9a, 0x83, 0xff,
+ 0x58, 0x96, 0x84, 0xff, 0x58, 0x96, 0x84, 0xff,
+ 0x58, 0x96, 0x84, 0xff, 0x4d, 0x8e, 0x7b, 0xff,
+ 0x5b, 0x96, 0x84, 0xff, 0x5a, 0x96, 0x84, 0xff,
+ 0x55, 0x85, 0x76, 0xff, 0x4a, 0x61, 0x5a, 0xff,
+ 0x60, 0x64, 0x5e, 0xff, 0x65, 0x7b, 0x70, 0xff,
+ 0x66, 0x7b, 0x71, 0xff, 0x60, 0x64, 0x5d, 0xff,
+ 0x74, 0x6c, 0x69, 0xff, 0x84, 0x7d, 0x7b, 0xff,
+ 0x84, 0x7e, 0x7c, 0xff, 0x83, 0x7d, 0x7b, 0xff,
+ 0x8f, 0x8b, 0x87, 0xff, 0x8f, 0x8b, 0x86, 0xff,
+ 0x9d, 0x9a, 0x94, 0xff, 0x9c, 0x9a, 0x94, 0xff,
+ 0x9d, 0x9a, 0x95, 0xff, 0x8c, 0x8c, 0x84, 0xff,
+ 0x94, 0x93, 0x8c, 0xff, 0x8c, 0x8c, 0x83, 0xff,
+ 0x8c, 0x8b, 0x8c, 0xff, 0x8c, 0x8b, 0x8c, 0xff,
+ 0x7c, 0x7e, 0x7c, 0xff, 0x7b, 0x7d, 0x7b, 0xff,
+ 0x5b, 0x76, 0x6b, 0xff, 0x5a, 0x75, 0x6b, 0xff,
+ 0x69, 0x7c, 0x74, 0xff, 0x83, 0x89, 0x83, 0xff,
+ 0x5b, 0x9e, 0x8c, 0xff, 0x60, 0x8c, 0x7e, 0xff,
+ 0x60, 0x8d, 0x7e, 0xff, 0x5a, 0x9e, 0x8c, 0xff,
+ 0x7c, 0xa2, 0x95, 0xff, 0x60, 0x8f, 0x84, 0xff,
+ 0x6e, 0x99, 0x8c, 0xff, 0x6e, 0x98, 0x8c, 0xff,
+ 0x7c, 0x96, 0x95, 0xff, 0x6e, 0x8e, 0x89, 0xff,
+ 0x7c, 0x96, 0x94, 0xff, 0x6e, 0x8e, 0x89, 0xff,
+ 0x7c, 0x8e, 0x8c, 0xff, 0x76, 0x84, 0x84, 0xff,
+ 0x71, 0x7b, 0x7c, 0xff, 0x76, 0x84, 0x83, 0xff,
+ 0x7c, 0x8e, 0x8c, 0xff, 0x7b, 0x8e, 0x8c, 0xff,
+ 0x71, 0x86, 0x84, 0xff, 0x65, 0x7d, 0x7b, 0xff,
+ 0x3f, 0x86, 0x71, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x45, 0x8a, 0x76, 0xff, 0x44, 0x89, 0x76, 0xff,
+ 0x4a, 0x96, 0x84, 0xff, 0x44, 0x8f, 0x7b, 0xff,
+ 0x3f, 0x88, 0x73, 0xff, 0x44, 0x8f, 0x7b, 0xff,
+ 0x42, 0x8f, 0x79, 0xff, 0x41, 0x8f, 0x78, 0xff,
+ 0x42, 0x8f, 0x79, 0xff, 0x42, 0x8f, 0x78, 0xff,
+ 0x58, 0x96, 0x84, 0xff, 0x4c, 0x8d, 0x7b, 0xff,
+ 0x4d, 0x8e, 0x7c, 0xff, 0x57, 0x95, 0x83, 0xff,
+ 0x5b, 0x96, 0x84, 0xff, 0x55, 0x84, 0x75, 0xff,
+ 0x55, 0x84, 0x76, 0xff, 0x55, 0x84, 0x76, 0xff,
+ 0x66, 0x7b, 0x71, 0xff, 0x65, 0x7a, 0x70, 0xff,
+ 0x60, 0x64, 0x5d, 0xff, 0x5a, 0x4d, 0x4a, 0xff,
+ 0x63, 0x5a, 0x55, 0xff, 0x73, 0x6c, 0x68, 0xff,
+ 0x73, 0x6c, 0x68, 0xff, 0x83, 0x7d, 0x7b, 0xff,
+ 0x8f, 0x8b, 0x86, 0xff, 0x8e, 0x8b, 0x86, 0xff,
+ 0x8f, 0x8b, 0x87, 0xff, 0x9c, 0x9a, 0x94, 0xff,
+ 0x9c, 0x9a, 0x94, 0xff, 0x9c, 0x99, 0x94, 0xff,
+ 0x84, 0x86, 0x7c, 0xff, 0x8c, 0x8c, 0x83, 0xff,
+ 0x94, 0x92, 0x94, 0xff, 0x94, 0x91, 0x94, 0xff,
+ 0x8c, 0x8b, 0x8c, 0xff, 0x83, 0x84, 0x83, 0xff,
+ 0x76, 0x83, 0x7b, 0xff, 0x5a, 0x75, 0x6b, 0xff,
+ 0x68, 0x7c, 0x73, 0xff, 0x76, 0x83, 0x7b, 0xff,
+ 0x60, 0x8c, 0x7e, 0xff, 0x5a, 0x9d, 0x8b, 0xff,
+ 0x5b, 0x9e, 0x8c, 0xff, 0x5a, 0x9e, 0x8c, 0xff,
+ 0x6e, 0x99, 0x8c, 0xff, 0x60, 0x8f, 0x83, 0xff,
+ 0x60, 0x8f, 0x84, 0xff, 0x6d, 0x98, 0x8c, 0xff,
+ 0x7b, 0x96, 0x94, 0xff, 0x6d, 0x8d, 0x89, 0xff,
+ 0x6e, 0x8e, 0x89, 0xff, 0x52, 0x7d, 0x73, 0xff,
+ 0x71, 0x7b, 0x7b, 0xff, 0x70, 0x7a, 0x7b, 0xff,
+ 0x7c, 0x8e, 0x8c, 0xff, 0x76, 0x84, 0x83, 0xff,
+ 0x71, 0x86, 0x84, 0xff, 0x5a, 0x75, 0x73, 0xff,
+ 0x71, 0x86, 0x84, 0xff, 0x5a, 0x75, 0x73, 0xff,
+ 0x45, 0x8a, 0x76, 0xff, 0x4a, 0x8d, 0x7b, 0xff,
+ 0x3f, 0x86, 0x71, 0xff, 0x3f, 0x85, 0x70, 0xff,
+ 0x45, 0x8f, 0x7c, 0xff, 0x44, 0x8f, 0x7b, 0xff,
+ 0x4a, 0x96, 0x84, 0xff, 0x44, 0x8f, 0x7b, 0xff,
+ 0x3a, 0x85, 0x6e, 0xff, 0x39, 0x84, 0x6d, 0xff,
+ 0x42, 0x8f, 0x79, 0xff, 0x4a, 0x9a, 0x84, 0xff,
+ 0x58, 0x96, 0x84, 0xff, 0x58, 0x96, 0x83, 0xff,
+ 0x58, 0x96, 0x84, 0xff, 0x58, 0x96, 0x84, 0xff,
+ 0x5b, 0x96, 0x84, 0xff, 0x55, 0x84, 0x76, 0xff,
+ 0x55, 0x85, 0x76, 0xff, 0x5a, 0x96, 0x84, 0xff,
+ 0x6b, 0x92, 0x84, 0xff, 0x6b, 0x91, 0x83, 0xff,
+ 0x66, 0x7b, 0x71, 0xff, 0x60, 0x64, 0x5d, 0xff,
+ 0x53, 0x49, 0x42, 0xff, 0x52, 0x49, 0x42, 0xff,
+ 0x63, 0x5b, 0x55, 0xff, 0x73, 0x6c, 0x68, 0xff,
+ 0x81, 0x7c, 0x79, 0xff, 0x81, 0x7c, 0x78, 0xff,
+ 0x8f, 0x8b, 0x87, 0xff, 0x8e, 0x8b, 0x86, 0xff,
+ 0x8c, 0x8d, 0x84, 0xff, 0x8c, 0x8c, 0x83, 0xff,
+ 0x94, 0x93, 0x8c, 0xff, 0x84, 0x85, 0x7b, 0xff,
+ 0x8c, 0x8b, 0x8c, 0xff, 0x94, 0x91, 0x94, 0xff,
+ 0x8c, 0x8b, 0x8c, 0xff, 0x8c, 0x8b, 0x8c, 0xff,
+ 0x84, 0x8a, 0x84, 0xff, 0x83, 0x89, 0x83, 0xff,
+ 0x76, 0x83, 0x7c, 0xff, 0x68, 0x7c, 0x73, 0xff,
+ 0x66, 0x7b, 0x71, 0xff, 0x6b, 0x69, 0x62, 0xff,
+ 0x60, 0x8d, 0x7f, 0xff, 0x60, 0x8c, 0x7e, 0xff,
+ 0x60, 0x8f, 0x84, 0xff, 0x52, 0x85, 0x7b, 0xff,
+ 0x53, 0x86, 0x7c, 0xff, 0x60, 0x8f, 0x84, 0xff,
+ 0x6e, 0x8e, 0x89, 0xff, 0x6d, 0x8d, 0x89, 0xff,
+ 0x7c, 0x96, 0x94, 0xff, 0x6e, 0x8e, 0x89, 0xff,
+ 0x71, 0x7b, 0x7c, 0xff, 0x6b, 0x71, 0x73, 0xff,
+ 0x6b, 0x72, 0x74, 0xff, 0x6b, 0x71, 0x73, 0xff,
+ 0x66, 0x7e, 0x7c, 0xff, 0x65, 0x7d, 0x7b, 0xff,
+ 0x5b, 0x76, 0x74, 0xff, 0x65, 0x7d, 0x7b, 0xff,
+ 0x3a, 0x82, 0x6b, 0xff, 0x44, 0x89, 0x76, 0xff,
+ 0x45, 0x8a, 0x76, 0xff, 0x44, 0x89, 0x75, 0xff,
+ 0x3f, 0x88, 0x73, 0xff, 0x3f, 0x88, 0x73, 0xff,
+ 0x4a, 0x96, 0x84, 0xff, 0x39, 0x81, 0x6a, 0xff,
+ 0x32, 0x7a, 0x63, 0xff, 0x39, 0x84, 0x6d, 0xff,
+ 0x42, 0x8f, 0x79, 0xff, 0x39, 0x84, 0x6d, 0xff,
+ 0x42, 0x86, 0x73, 0xff, 0x4c, 0x8d, 0x7b, 0xff,
+ 0x58, 0x96, 0x84, 0xff, 0x62, 0x9d, 0x8b, 0xff,
+ 0x5b, 0x96, 0x84, 0xff, 0x55, 0x84, 0x76, 0xff,
+ 0x50, 0x73, 0x68, 0xff, 0x55, 0x84, 0x75, 0xff,
+ 0x6b, 0x92, 0x84, 0xff, 0x6b, 0x91, 0x83, 0xff,
+ 0x6b, 0x92, 0x84, 0xff, 0x65, 0x7a, 0x70, 0xff,
+ 0x63, 0x5b, 0x55, 0xff, 0x62, 0x5a, 0x55, 0xff,
+ 0x63, 0x5a, 0x55, 0xff, 0x62, 0x5a, 0x55, 0xff,
+ 0x73, 0x6d, 0x6b, 0xff, 0x81, 0x7c, 0x78, 0xff,
+ 0x8f, 0x8b, 0x86, 0xff, 0x9c, 0x99, 0x94, 0xff,
+ 0x8c, 0x8c, 0x84, 0xff, 0x83, 0x85, 0x7b, 0xff,
+ 0x94, 0x93, 0x8c, 0xff, 0x9c, 0x99, 0x94, 0xff,
+ 0x94, 0x92, 0x94, 0xff, 0x8b, 0x8b, 0x8b, 0xff,
+ 0x94, 0x92, 0x94, 0xff, 0x94, 0x91, 0x94, 0xff,
+ 0x84, 0x8a, 0x84, 0xff, 0x83, 0x89, 0x83, 0xff,
+ 0x84, 0x8a, 0x84, 0xff, 0x75, 0x82, 0x7b, 0xff,
+ 0x66, 0x7b, 0x71, 0xff, 0x65, 0x7a, 0x70, 0xff,
+ 0x6b, 0x69, 0x63, 0xff, 0x65, 0x7a, 0x70, 0xff,
+ 0x52, 0x86, 0x7c, 0xff, 0x6d, 0x98, 0x8b, 0xff,
+ 0x6e, 0x98, 0x8c, 0xff, 0x5f, 0x8f, 0x83, 0xff,
+ 0x7c, 0x96, 0x94, 0xff, 0x6d, 0x8d, 0x89, 0xff,
+ 0x60, 0x86, 0x7e, 0xff, 0x6d, 0x8d, 0x89, 0xff,
+ 0x7c, 0x8e, 0x8c, 0xff, 0x76, 0x84, 0x83, 0xff,
+ 0x70, 0x7b, 0x7b, 0xff, 0x75, 0x84, 0x83, 0xff,
+ 0x66, 0x7e, 0x7c, 0xff, 0x5a, 0x75, 0x73, 0xff,
+ 0x65, 0x7e, 0x7b, 0xff, 0x65, 0x7d, 0x7b, 0xff,
+ 0x42, 0x8a, 0x74, 0xff, 0x42, 0x8a, 0x73, 0xff,
+ 0x37, 0x7a, 0x63, 0xff, 0x37, 0x79, 0x63, 0xff,
+ 0x42, 0x82, 0x6b, 0xff, 0x42, 0x81, 0x6b, 0xff,
+ 0x37, 0x73, 0x5e, 0xff, 0x37, 0x73, 0x5d, 0xff,
+ 0x3a, 0x76, 0x60, 0xff, 0x3a, 0x75, 0x60, 0xff,
+ 0x42, 0x82, 0x6e, 0xff, 0x42, 0x81, 0x6e, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x3a, 0x7d, 0x6b, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x5a, 0x96, 0x83, 0xff,
+ 0x5b, 0x96, 0x84, 0xff, 0x5a, 0x96, 0x84, 0xff,
+ 0x5b, 0x96, 0x84, 0xff, 0x5a, 0x96, 0x83, 0xff,
+ 0x69, 0x99, 0x8c, 0xff, 0x68, 0x98, 0x8c, 0xff,
+ 0x5e, 0x8f, 0x84, 0xff, 0x52, 0x85, 0x7b, 0xff,
+ 0x63, 0x92, 0x84, 0xff, 0x68, 0x6f, 0x6e, 0xff,
+ 0x6b, 0x5d, 0x63, 0xff, 0x6b, 0x5d, 0x63, 0xff,
+ 0x79, 0x77, 0x71, 0xff, 0x8c, 0x8a, 0x84, 0xff,
+ 0x8c, 0x8a, 0x84, 0xff, 0x8c, 0x89, 0x83, 0xff,
+ 0x95, 0x92, 0x8c, 0xff, 0x86, 0x83, 0x7e, 0xff,
+ 0x94, 0x92, 0x8c, 0xff, 0x94, 0x92, 0x8c, 0xff,
+ 0x95, 0x92, 0x95, 0xff, 0x8c, 0x88, 0x89, 0xff,
+ 0x94, 0x92, 0x94, 0xff, 0x94, 0x92, 0x94, 0xff,
+ 0x95, 0x91, 0x8f, 0xff, 0x94, 0x90, 0x8f, 0xff,
+ 0x84, 0x86, 0x84, 0xff, 0x8c, 0x8b, 0x89, 0xff,
+ 0x8c, 0x89, 0x84, 0xff, 0x8c, 0x88, 0x84, 0xff,
+ 0x84, 0x7f, 0x7c, 0xff, 0x8c, 0x88, 0x83, 0xff,
+ 0x6b, 0x75, 0x6b, 0xff, 0x5a, 0x62, 0x5a, 0xff,
+ 0x6b, 0x74, 0x6b, 0xff, 0x7b, 0x85, 0x7b, 0xff,
+ 0x5b, 0x92, 0x8c, 0xff, 0x5a, 0x92, 0x8c, 0xff,
+ 0x60, 0x83, 0x7e, 0xff, 0x65, 0x74, 0x70, 0xff,
+ 0x53, 0x7a, 0x71, 0xff, 0x5a, 0x86, 0x7e, 0xff,
+ 0x53, 0x7a, 0x71, 0xff, 0x5a, 0x85, 0x7e, 0xff,
+ 0x66, 0x7d, 0x76, 0xff, 0x70, 0x87, 0x81, 0xff,
+ 0x71, 0x87, 0x81, 0xff, 0x65, 0x7c, 0x76, 0xff,
+ 0x37, 0x7a, 0x63, 0xff, 0x36, 0x79, 0x62, 0xff,
+ 0x37, 0x7a, 0x63, 0xff, 0x2c, 0x69, 0x52, 0xff,
+ 0x37, 0x73, 0x5d, 0xff, 0x41, 0x81, 0x6b, 0xff,
+ 0x2c, 0x64, 0x50, 0xff, 0x42, 0x81, 0x6b, 0xff,
+ 0x31, 0x69, 0x52, 0xff, 0x31, 0x69, 0x52, 0xff,
+ 0x3a, 0x76, 0x60, 0xff, 0x4a, 0x8d, 0x7b, 0xff,
+ 0x5b, 0x96, 0x84, 0xff, 0x5a, 0x95, 0x83, 0xff,
+ 0x50, 0x8e, 0x7c, 0xff, 0x44, 0x85, 0x73, 0xff,
+ 0x45, 0x80, 0x6e, 0xff, 0x39, 0x75, 0x62, 0xff,
+ 0x5b, 0x96, 0x84, 0xff, 0x5a, 0x95, 0x83, 0xff,
+ 0x68, 0x99, 0x8c, 0xff, 0x68, 0x98, 0x8b, 0xff,
+ 0x5d, 0x8f, 0x84, 0xff, 0x5d, 0x8f, 0x83, 0xff,
+ 0x66, 0x80, 0x79, 0xff, 0x65, 0x80, 0x78, 0xff,
+ 0x68, 0x6f, 0x6e, 0xff, 0x65, 0x80, 0x78, 0xff,
+ 0x8c, 0x8a, 0x84, 0xff, 0x78, 0x76, 0x70, 0xff,
+ 0x79, 0x77, 0x71, 0xff, 0x78, 0x76, 0x70, 0xff,
+ 0x94, 0x92, 0x8c, 0xff, 0x86, 0x82, 0x7e, 0xff,
+ 0x87, 0x83, 0x7e, 0xff, 0x86, 0x83, 0x7e, 0xff,
+ 0x8c, 0x88, 0x89, 0xff, 0x8b, 0x88, 0x89, 0xff,
+ 0x8c, 0x88, 0x89, 0xff, 0x94, 0x91, 0x94, 0xff,
+ 0x94, 0x90, 0x8f, 0xff, 0x8b, 0x8b, 0x89, 0xff,
+ 0x84, 0x86, 0x84, 0xff, 0x8c, 0x8b, 0x89, 0xff,
+ 0x94, 0x92, 0x8c, 0xff, 0x8b, 0x88, 0x83, 0xff,
+ 0x84, 0x7f, 0x7c, 0xff, 0x7b, 0x75, 0x73, 0xff,
+ 0x7b, 0x86, 0x7b, 0xff, 0x6b, 0x74, 0x6b, 0xff,
+ 0x5b, 0x63, 0x5b, 0xff, 0x4a, 0x51, 0x4a, 0xff,
+ 0x6b, 0x65, 0x63, 0xff, 0x65, 0x74, 0x70, 0xff,
+ 0x60, 0x83, 0x7e, 0xff, 0x60, 0x83, 0x7e, 0xff,
+ 0x52, 0x7a, 0x71, 0xff, 0x62, 0x91, 0x8b, 0xff,
+ 0x63, 0x92, 0x8c, 0xff, 0x5a, 0x85, 0x7e, 0xff,
+ 0x7b, 0x92, 0x8c, 0xff, 0x7b, 0x91, 0x8b, 0xff,
+ 0x71, 0x87, 0x81, 0xff, 0x5a, 0x71, 0x6b, 0xff,
+ 0x37, 0x7a, 0x63, 0xff, 0x37, 0x79, 0x62, 0xff,
+ 0x2c, 0x6a, 0x53, 0xff, 0x2c, 0x69, 0x52, 0xff,
+ 0x21, 0x55, 0x42, 0xff, 0x2c, 0x64, 0x4f, 0xff,
+ 0x37, 0x73, 0x5e, 0xff, 0x37, 0x73, 0x5d, 0xff,
+ 0x3a, 0x76, 0x60, 0xff, 0x31, 0x69, 0x52, 0xff,
+ 0x3a, 0x76, 0x60, 0xff, 0x42, 0x81, 0x6e, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x44, 0x85, 0x73, 0xff,
+ 0x50, 0x8e, 0x7c, 0xff, 0x4f, 0x8e, 0x7b, 0xff,
+ 0x50, 0x8b, 0x79, 0xff, 0x4f, 0x8b, 0x78, 0xff,
+ 0x50, 0x8b, 0x79, 0xff, 0x5a, 0x96, 0x84, 0xff,
+ 0x5e, 0x8f, 0x84, 0xff, 0x5d, 0x8f, 0x83, 0xff,
+ 0x5e, 0x8f, 0x84, 0xff, 0x5d, 0x8f, 0x84, 0xff,
+ 0x63, 0x92, 0x84, 0xff, 0x62, 0x91, 0x83, 0xff,
+ 0x66, 0x81, 0x79, 0xff, 0x68, 0x6f, 0x6e, 0xff,
+ 0x66, 0x64, 0x5e, 0xff, 0x78, 0x77, 0x70, 0xff,
+ 0x79, 0x77, 0x71, 0xff, 0x79, 0x77, 0x70, 0xff,
+ 0x79, 0x74, 0x71, 0xff, 0x86, 0x83, 0x7e, 0xff,
+ 0x79, 0x74, 0x71, 0xff, 0x79, 0x74, 0x70, 0xff,
+ 0x84, 0x7f, 0x7e, 0xff, 0x8c, 0x88, 0x89, 0xff,
+ 0x8c, 0x89, 0x8a, 0xff, 0x8c, 0x88, 0x89, 0xff,
+ 0x8c, 0x8b, 0x89, 0xff, 0x83, 0x85, 0x83, 0xff,
+ 0x84, 0x86, 0x84, 0xff, 0x9c, 0x96, 0x94, 0xff,
+ 0x94, 0x92, 0x8c, 0xff, 0x8c, 0x88, 0x83, 0xff,
+ 0x84, 0x7f, 0x7c, 0xff, 0x7b, 0x75, 0x73, 0xff,
+ 0x5b, 0x63, 0x5b, 0xff, 0x6b, 0x74, 0x6b, 0xff,
+ 0x5b, 0x63, 0x5b, 0xff, 0x6b, 0x74, 0x6b, 0xff,
+ 0x66, 0x74, 0x71, 0xff, 0x65, 0x74, 0x70, 0xff,
+ 0x6b, 0x66, 0x63, 0xff, 0x65, 0x74, 0x70, 0xff,
+ 0x63, 0x92, 0x8c, 0xff, 0x62, 0x91, 0x8c, 0xff,
+ 0x63, 0x92, 0x8c, 0xff, 0x63, 0x92, 0x8c, 0xff,
+ 0x7c, 0x92, 0x8c, 0xff, 0x70, 0x87, 0x81, 0xff,
+ 0x66, 0x7d, 0x76, 0xff, 0x65, 0x7c, 0x76, 0xff,
+ 0x37, 0x7a, 0x63, 0xff, 0x36, 0x79, 0x62, 0xff,
+ 0x21, 0x59, 0x42, 0xff, 0x20, 0x59, 0x41, 0xff,
+ 0x37, 0x73, 0x5d, 0xff, 0x41, 0x81, 0x6b, 0xff,
+ 0x37, 0x73, 0x5d, 0xff, 0x36, 0x72, 0x5d, 0xff,
+ 0x42, 0x82, 0x6e, 0xff, 0x4a, 0x8d, 0x7b, 0xff,
+ 0x4a, 0x8e, 0x7b, 0xff, 0x41, 0x81, 0x6d, 0xff,
+ 0x45, 0x86, 0x73, 0xff, 0x44, 0x85, 0x73, 0xff,
+ 0x50, 0x8e, 0x7b, 0xff, 0x5a, 0x95, 0x83, 0xff,
+ 0x5b, 0x96, 0x84, 0xff, 0x5a, 0x95, 0x83, 0xff,
+ 0x5b, 0x96, 0x84, 0xff, 0x5a, 0x95, 0x83, 0xff,
+ 0x5d, 0x8f, 0x84, 0xff, 0x73, 0xa2, 0x94, 0xff,
+ 0x68, 0x98, 0x8c, 0xff, 0x52, 0x85, 0x7b, 0xff,
+ 0x66, 0x80, 0x79, 0xff, 0x65, 0x80, 0x78, 0xff,
+ 0x63, 0x92, 0x84, 0xff, 0x62, 0x91, 0x83, 0xff,
+ 0x66, 0x64, 0x5d, 0xff, 0x52, 0x51, 0x4a, 0xff,
+ 0x52, 0x51, 0x4a, 0xff, 0x65, 0x63, 0x5d, 0xff,
+ 0x79, 0x74, 0x71, 0xff, 0x78, 0x74, 0x70, 0xff,
+ 0x6b, 0x65, 0x63, 0xff, 0x6a, 0x65, 0x62, 0xff,
+ 0x7c, 0x76, 0x73, 0xff, 0x7b, 0x75, 0x73, 0xff,
+ 0x84, 0x7f, 0x7e, 0xff, 0x8b, 0x88, 0x89, 0xff,
+ 0x8c, 0x8b, 0x89, 0xff, 0x8b, 0x8b, 0x89, 0xff,
+ 0x8c, 0x8b, 0x89, 0xff, 0x8b, 0x8a, 0x89, 0xff,
+ 0x8c, 0x88, 0x84, 0xff, 0x8b, 0x88, 0x83, 0xff,
+ 0x94, 0x92, 0x8c, 0xff, 0x8b, 0x88, 0x83, 0xff,
+ 0x7c, 0x86, 0x7c, 0xff, 0x7b, 0x85, 0x7b, 0xff,
+ 0x6b, 0x74, 0x6b, 0xff, 0x5a, 0x62, 0x5a, 0xff,
+ 0x66, 0x74, 0x71, 0xff, 0x65, 0x74, 0x70, 0xff,
+ 0x6b, 0x65, 0x63, 0xff, 0x65, 0x74, 0x70, 0xff,
+ 0x4a, 0x6d, 0x63, 0xff, 0x4a, 0x6d, 0x62, 0xff,
+ 0x52, 0x79, 0x70, 0xff, 0x62, 0x91, 0x8b, 0xff,
+ 0x7c, 0x92, 0x8c, 0xff, 0x70, 0x87, 0x81, 0xff,
+ 0x65, 0x7c, 0x76, 0xff, 0x5a, 0x71, 0x6a, 0xff,
+ 0x37, 0x79, 0x63, 0xff, 0x31, 0x6d, 0x5a, 0xff,
+ 0x32, 0x6e, 0x5b, 0xff, 0x31, 0x6d, 0x5a, 0xff,
+ 0x40, 0x81, 0x6b, 0xff, 0x45, 0x87, 0x73, 0xff,
+ 0x4a, 0x8e, 0x7c, 0xff, 0x44, 0x87, 0x73, 0xff,
+ 0x4d, 0x8a, 0x79, 0xff, 0x52, 0x92, 0x84, 0xff,
+ 0x53, 0x92, 0x84, 0xff, 0x52, 0x92, 0x83, 0xff,
+ 0x58, 0x86, 0x76, 0xff, 0x58, 0x86, 0x76, 0xff,
+ 0x63, 0x96, 0x84, 0xff, 0x63, 0x96, 0x83, 0xff,
+ 0x63, 0x92, 0x84, 0xff, 0x63, 0x92, 0x84, 0xff,
+ 0x63, 0x92, 0x84, 0xff, 0x63, 0x92, 0x83, 0xff,
+ 0x6b, 0x8f, 0x87, 0xff, 0x73, 0x96, 0x8c, 0xff,
+ 0x74, 0x96, 0x8c, 0xff, 0x63, 0x88, 0x81, 0xff,
+ 0x50, 0x86, 0x7c, 0xff, 0x4f, 0x86, 0x7b, 0xff,
+ 0x55, 0x8e, 0x84, 0xff, 0x5a, 0x96, 0x8c, 0xff,
+ 0x5b, 0x92, 0x84, 0xff, 0x4f, 0x71, 0x68, 0xff,
+ 0x4a, 0x61, 0x5b, 0xff, 0x4a, 0x61, 0x5a, 0xff,
+ 0x5b, 0x5f, 0x55, 0xff, 0x5a, 0x5e, 0x55, 0xff,
+ 0x5b, 0x5f, 0x55, 0xff, 0x5a, 0x5e, 0x55, 0xff,
+ 0x69, 0x64, 0x5e, 0xff, 0x76, 0x73, 0x70, 0xff,
+ 0x76, 0x73, 0x71, 0xff, 0x83, 0x81, 0x83, 0xff,
+ 0x84, 0x85, 0x81, 0xff, 0x84, 0x84, 0x81, 0xff,
+ 0x8c, 0x8e, 0x8c, 0xff, 0x8c, 0x8e, 0x8c, 0xff,
+ 0x8c, 0x8a, 0x8c, 0xff, 0x8c, 0x8a, 0x8c, 0xff,
+ 0x89, 0x85, 0x84, 0xff, 0x8c, 0x89, 0x8c, 0xff,
+ 0x95, 0x8e, 0x8c, 0xff, 0x94, 0x8e, 0x8c, 0xff,
+ 0x8c, 0x87, 0x84, 0xff, 0x7b, 0x79, 0x73, 0xff,
+ 0x6b, 0x64, 0x5e, 0xff, 0x5a, 0x51, 0x4a, 0xff,
+ 0x6b, 0x64, 0x5e, 0xff, 0x7b, 0x77, 0x70, 0xff,
+ 0x69, 0x6e, 0x6b, 0xff, 0x68, 0x6d, 0x6b, 0xff,
+ 0x53, 0x5d, 0x5b, 0xff, 0x68, 0x6d, 0x6b, 0xff,
+ 0x58, 0x7f, 0x76, 0xff, 0x63, 0x96, 0x8c, 0xff,
+ 0x58, 0x7f, 0x76, 0xff, 0x58, 0x7f, 0x76, 0xff,
+ 0x3c, 0x83, 0x6b, 0xff, 0x36, 0x78, 0x62, 0xff,
+ 0x37, 0x78, 0x63, 0xff, 0x3c, 0x83, 0x6b, 0xff,
+ 0x45, 0x87, 0x73, 0xff, 0x44, 0x87, 0x73, 0xff,
+ 0x45, 0x87, 0x73, 0xff, 0x44, 0x87, 0x73, 0xff,
+ 0x52, 0x92, 0x84, 0xff, 0x52, 0x91, 0x83, 0xff,
+ 0x4d, 0x8a, 0x79, 0xff, 0x4c, 0x89, 0x78, 0xff,
+ 0x58, 0x86, 0x76, 0xff, 0x57, 0x85, 0x75, 0xff,
+ 0x63, 0x96, 0x84, 0xff, 0x57, 0x85, 0x76, 0xff,
+ 0x58, 0x7f, 0x73, 0xff, 0x57, 0x7e, 0x73, 0xff,
+ 0x5d, 0x88, 0x7c, 0xff, 0x62, 0x91, 0x83, 0xff,
+ 0x63, 0x88, 0x81, 0xff, 0x62, 0x88, 0x80, 0xff,
+ 0x5b, 0x82, 0x7c, 0xff, 0x62, 0x88, 0x81, 0xff,
+ 0x50, 0x86, 0x7b, 0xff, 0x5a, 0x95, 0x8b, 0xff,
+ 0x55, 0x8e, 0x84, 0xff, 0x4a, 0x7d, 0x73, 0xff,
+ 0x55, 0x82, 0x76, 0xff, 0x5a, 0x91, 0x83, 0xff,
+ 0x5b, 0x92, 0x84, 0xff, 0x55, 0x81, 0x76, 0xff,
+ 0x5b, 0x5f, 0x55, 0xff, 0x5a, 0x5e, 0x55, 0xff,
+ 0x5b, 0x5f, 0x55, 0xff, 0x5a, 0x5e, 0x55, 0xff,
+ 0x68, 0x64, 0x5d, 0xff, 0x68, 0x63, 0x5d, 0xff,
+ 0x68, 0x64, 0x5d, 0xff, 0x76, 0x72, 0x70, 0xff,
+ 0x7b, 0x7b, 0x76, 0xff, 0x8b, 0x8d, 0x8b, 0xff,
+ 0x8c, 0x8e, 0x8c, 0xff, 0x83, 0x84, 0x81, 0xff,
+ 0x89, 0x84, 0x84, 0xff, 0x89, 0x84, 0x83, 0xff,
+ 0x8c, 0x8a, 0x8c, 0xff, 0x89, 0x84, 0x83, 0xff,
+ 0x8c, 0x87, 0x84, 0xff, 0x8b, 0x87, 0x83, 0xff,
+ 0x7c, 0x7a, 0x73, 0xff, 0x7b, 0x79, 0x73, 0xff,
+ 0x7b, 0x77, 0x71, 0xff, 0x6b, 0x63, 0x5d, 0xff,
+ 0x5b, 0x51, 0x4a, 0xff, 0x5a, 0x51, 0x4a, 0xff,
+ 0x68, 0x6d, 0x6b, 0xff, 0x7e, 0x7d, 0x7b, 0xff,
+ 0x7e, 0x7e, 0x7c, 0xff, 0x68, 0x6d, 0x6b, 0xff,
+ 0x4d, 0x68, 0x60, 0xff, 0x41, 0x51, 0x4a, 0xff,
+ 0x58, 0x7f, 0x76, 0xff, 0x57, 0x7f, 0x76, 0xff,
+ 0x42, 0x8e, 0x73, 0xff, 0x42, 0x8d, 0x73, 0xff,
+ 0x42, 0x8e, 0x74, 0xff, 0x42, 0x8e, 0x73, 0xff,
+ 0x4a, 0x8e, 0x7c, 0xff, 0x44, 0x87, 0x73, 0xff,
+ 0x45, 0x87, 0x74, 0xff, 0x44, 0x87, 0x73, 0xff,
+ 0x48, 0x82, 0x6e, 0xff, 0x47, 0x81, 0x6d, 0xff,
+ 0x4d, 0x8a, 0x79, 0xff, 0x52, 0x92, 0x84, 0xff,
+ 0x58, 0x86, 0x76, 0xff, 0x58, 0x85, 0x76, 0xff,
+ 0x58, 0x86, 0x76, 0xff, 0x58, 0x85, 0x76, 0xff,
+ 0x53, 0x76, 0x6b, 0xff, 0x58, 0x7f, 0x73, 0xff,
+ 0x58, 0x7f, 0x74, 0xff, 0x5d, 0x88, 0x7b, 0xff,
+ 0x6b, 0x8f, 0x87, 0xff, 0x6b, 0x8f, 0x86, 0xff,
+ 0x6b, 0x8f, 0x87, 0xff, 0x73, 0x96, 0x8c, 0xff,
+ 0x5b, 0x96, 0x8c, 0xff, 0x5a, 0x96, 0x8c, 0xff,
+ 0x50, 0x86, 0x7c, 0xff, 0x4f, 0x85, 0x7b, 0xff,
+ 0x55, 0x82, 0x76, 0xff, 0x55, 0x81, 0x76, 0xff,
+ 0x5b, 0x92, 0x84, 0xff, 0x5a, 0x92, 0x84, 0xff,
+ 0x63, 0x7c, 0x71, 0xff, 0x5a, 0x5e, 0x55, 0xff,
+ 0x53, 0x41, 0x3a, 0xff, 0x52, 0x41, 0x39, 0xff,
+ 0x5b, 0x55, 0x4a, 0xff, 0x68, 0x64, 0x5d, 0xff,
+ 0x69, 0x64, 0x5e, 0xff, 0x76, 0x73, 0x70, 0xff,
+ 0x7c, 0x7b, 0x76, 0xff, 0x83, 0x84, 0x81, 0xff,
+ 0x84, 0x85, 0x81, 0xff, 0x84, 0x84, 0x81, 0xff,
+ 0x89, 0x85, 0x84, 0xff, 0x89, 0x84, 0x83, 0xff,
+ 0x87, 0x7f, 0x7c, 0xff, 0x86, 0x7f, 0x7b, 0xff,
+ 0x84, 0x80, 0x7c, 0xff, 0x8c, 0x87, 0x83, 0xff,
+ 0x84, 0x81, 0x7c, 0xff, 0x7b, 0x79, 0x73, 0xff,
+ 0x7c, 0x77, 0x71, 0xff, 0x7b, 0x77, 0x70, 0xff,
+ 0x7c, 0x77, 0x71, 0xff, 0x7b, 0x77, 0x70, 0xff,
+ 0x7e, 0x7e, 0x7c, 0xff, 0x7e, 0x7d, 0x7b, 0xff,
+ 0x7f, 0x7e, 0x7c, 0xff, 0x68, 0x6d, 0x6b, 0xff,
+ 0x4d, 0x68, 0x60, 0xff, 0x42, 0x51, 0x4a, 0xff,
+ 0x42, 0x51, 0x4a, 0xff, 0x42, 0x51, 0x4a, 0xff,
+ 0x37, 0x78, 0x63, 0xff, 0x3c, 0x83, 0x6b, 0xff,
+ 0x42, 0x8e, 0x73, 0xff, 0x41, 0x8d, 0x73, 0xff,
+ 0x4a, 0x8e, 0x7c, 0xff, 0x3f, 0x80, 0x6b, 0xff,
+ 0x3a, 0x79, 0x63, 0xff, 0x39, 0x79, 0x62, 0xff,
+ 0x42, 0x7a, 0x63, 0xff, 0x41, 0x79, 0x62, 0xff,
+ 0x42, 0x79, 0x63, 0xff, 0x47, 0x81, 0x6d, 0xff,
+ 0x42, 0x65, 0x5b, 0xff, 0x41, 0x65, 0x5a, 0xff,
+ 0x42, 0x65, 0x5b, 0xff, 0x4c, 0x75, 0x68, 0xff,
+ 0x52, 0x76, 0x6b, 0xff, 0x52, 0x75, 0x6b, 0xff,
+ 0x5d, 0x88, 0x7b, 0xff, 0x62, 0x91, 0x83, 0xff,
+ 0x6b, 0x8f, 0x87, 0xff, 0x6b, 0x8f, 0x86, 0xff,
+ 0x63, 0x88, 0x81, 0xff, 0x5a, 0x81, 0x7b, 0xff,
+ 0x4a, 0x7e, 0x73, 0xff, 0x4f, 0x85, 0x7b, 0xff,
+ 0x50, 0x86, 0x7b, 0xff, 0x55, 0x8d, 0x83, 0xff,
+ 0x5b, 0x92, 0x84, 0xff, 0x4f, 0x71, 0x68, 0xff,
+ 0x50, 0x71, 0x68, 0xff, 0x55, 0x81, 0x75, 0xff,
+ 0x6b, 0x9a, 0x8c, 0xff, 0x62, 0x7c, 0x70, 0xff,
+ 0x63, 0x7c, 0x70, 0xff, 0x5a, 0x5e, 0x55, 0xff,
+ 0x5b, 0x55, 0x4a, 0xff, 0x5a, 0x55, 0x4a, 0xff,
+ 0x68, 0x64, 0x5d, 0xff, 0x68, 0x63, 0x5d, 0xff,
+ 0x73, 0x71, 0x6b, 0xff, 0x73, 0x71, 0x6b, 0xff,
+ 0x7b, 0x7b, 0x76, 0xff, 0x7b, 0x7a, 0x75, 0xff,
+ 0x84, 0x7a, 0x73, 0xff, 0x86, 0x7e, 0x7b, 0xff,
+ 0x86, 0x7f, 0x7b, 0xff, 0x83, 0x79, 0x73, 0xff,
+ 0x84, 0x80, 0x7c, 0xff, 0x83, 0x80, 0x7b, 0xff,
+ 0x84, 0x80, 0x7b, 0xff, 0x83, 0x80, 0x7b, 0xff,
+ 0x8c, 0x8a, 0x84, 0xff, 0x7b, 0x76, 0x70, 0xff,
+ 0x7b, 0x77, 0x70, 0xff, 0x8b, 0x89, 0x83, 0xff,
+ 0x94, 0x8e, 0x8c, 0xff, 0x94, 0x8d, 0x8b, 0xff,
+ 0x94, 0x8e, 0x8c, 0xff, 0x7e, 0x7d, 0x7b, 0xff,
+ 0x58, 0x7f, 0x76, 0xff, 0x4c, 0x68, 0x60, 0xff,
+ 0x42, 0x51, 0x4a, 0xff, 0x41, 0x50, 0x4a, 0xff,
+ 0x4b, 0x8a, 0x74, 0xff, 0x3a, 0x7f, 0x68, 0xff,
+ 0x42, 0x85, 0x6e, 0xff, 0x42, 0x84, 0x6e, 0xff,
+ 0x45, 0x7f, 0x6b, 0xff, 0x45, 0x7f, 0x6b, 0xff,
+ 0x3a, 0x72, 0x5b, 0xff, 0x39, 0x71, 0x5a, 0xff,
+ 0x45, 0x6b, 0x58, 0xff, 0x47, 0x74, 0x5d, 0xff,
+ 0x4a, 0x7e, 0x63, 0xff, 0x42, 0x61, 0x52, 0xff,
+ 0x3a, 0x51, 0x42, 0xff, 0x3a, 0x51, 0x42, 0xff,
+ 0x4d, 0x66, 0x55, 0xff, 0x39, 0x51, 0x42, 0xff,
+ 0x5b, 0x4d, 0x42, 0xff, 0x6b, 0x61, 0x58, 0xff,
+ 0x7c, 0x76, 0x6e, 0xff, 0x7b, 0x75, 0x6e, 0xff,
+ 0x6e, 0x79, 0x6b, 0xff, 0x79, 0x87, 0x7b, 0xff,
+ 0x79, 0x87, 0x7c, 0xff, 0x6e, 0x78, 0x6b, 0xff,
+ 0x42, 0x6a, 0x5b, 0xff, 0x4d, 0x77, 0x68, 0xff,
+ 0x63, 0x92, 0x84, 0xff, 0x58, 0x84, 0x76, 0xff,
+ 0x42, 0x83, 0x74, 0xff, 0x3a, 0x71, 0x63, 0xff,
+ 0x3a, 0x72, 0x63, 0xff, 0x42, 0x83, 0x73, 0xff,
+ 0x4b, 0x8e, 0x81, 0xff, 0x4a, 0x8e, 0x81, 0xff,
+ 0x4a, 0x8e, 0x81, 0xff, 0x39, 0x7d, 0x6b, 0xff,
+ 0x5b, 0x8a, 0x84, 0xff, 0x4a, 0x61, 0x5d, 0xff,
+ 0x42, 0x4d, 0x4a, 0xff, 0x42, 0x4d, 0x4a, 0xff,
+ 0x53, 0x5e, 0x55, 0xff, 0x52, 0x5d, 0x55, 0xff,
+ 0x5b, 0x72, 0x69, 0xff, 0x5a, 0x71, 0x68, 0xff,
+ 0x71, 0x76, 0x6e, 0xff, 0x70, 0x75, 0x6e, 0xff,
+ 0x71, 0x76, 0x6e, 0xff, 0x70, 0x75, 0x6e, 0xff,
+ 0x81, 0x7e, 0x7f, 0xff, 0x76, 0x71, 0x70, 0xff,
+ 0x81, 0x7e, 0x7e, 0xff, 0x8c, 0x89, 0x8c, 0xff,
+ 0x81, 0x81, 0x7f, 0xff, 0x81, 0x80, 0x7e, 0xff,
+ 0x81, 0x81, 0x7e, 0xff, 0x8c, 0x8e, 0x8c, 0xff,
+ 0x8c, 0x8b, 0x8c, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0x9d, 0x9e, 0x9d, 0xff, 0x94, 0x94, 0x94, 0xff,
+ 0x95, 0x92, 0x95, 0xff, 0x94, 0x92, 0x94, 0xff,
+ 0x89, 0x89, 0x89, 0xff, 0x73, 0x75, 0x73, 0xff,
+ 0x4a, 0x8a, 0x73, 0xff, 0x31, 0x79, 0x62, 0xff,
+ 0x32, 0x7a, 0x63, 0xff, 0x42, 0x84, 0x6d, 0xff,
+ 0x45, 0x7f, 0x6b, 0xff, 0x3f, 0x78, 0x62, 0xff,
+ 0x45, 0x7f, 0x6b, 0xff, 0x3f, 0x78, 0x62, 0xff,
+ 0x42, 0x61, 0x52, 0xff, 0x41, 0x61, 0x52, 0xff,
+ 0x48, 0x74, 0x5d, 0xff, 0x42, 0x61, 0x52, 0xff,
+ 0x3a, 0x51, 0x42, 0xff, 0x4c, 0x65, 0x55, 0xff,
+ 0x60, 0x7a, 0x68, 0xff, 0x4c, 0x65, 0x55, 0xff,
+ 0x6b, 0x61, 0x58, 0xff, 0x6b, 0x61, 0x57, 0xff,
+ 0x7c, 0x76, 0x6e, 0xff, 0x7b, 0x75, 0x6d, 0xff,
+ 0x6e, 0x78, 0x6b, 0xff, 0x6d, 0x78, 0x6b, 0xff,
+ 0x84, 0x96, 0x8c, 0xff, 0x78, 0x87, 0x7b, 0xff,
+ 0x58, 0x84, 0x76, 0xff, 0x4c, 0x76, 0x68, 0xff,
+ 0x58, 0x84, 0x76, 0xff, 0x62, 0x91, 0x83, 0xff,
+ 0x52, 0xa6, 0x94, 0xff, 0x4a, 0x94, 0x83, 0xff,
+ 0x4a, 0x95, 0x84, 0xff, 0x4a, 0x94, 0x83, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x41, 0x85, 0x75, 0xff,
+ 0x42, 0x86, 0x76, 0xff, 0x42, 0x85, 0x76, 0xff,
+ 0x5b, 0x8a, 0x84, 0xff, 0x5a, 0x89, 0x83, 0xff,
+ 0x52, 0x76, 0x71, 0xff, 0x42, 0x4d, 0x4a, 0xff,
+ 0x4a, 0x49, 0x42, 0xff, 0x4a, 0x48, 0x41, 0xff,
+ 0x4a, 0x49, 0x42, 0xff, 0x4a, 0x49, 0x42, 0xff,
+ 0x5b, 0x5d, 0x52, 0xff, 0x65, 0x69, 0x60, 0xff,
+ 0x5b, 0x5d, 0x52, 0xff, 0x65, 0x69, 0x60, 0xff,
+ 0x76, 0x71, 0x71, 0xff, 0x80, 0x7d, 0x7e, 0xff,
+ 0x76, 0x72, 0x71, 0xff, 0x81, 0x7d, 0x7e, 0xff,
+ 0x81, 0x80, 0x7e, 0xff, 0x80, 0x80, 0x7e, 0xff,
+ 0x81, 0x80, 0x7e, 0xff, 0x8c, 0x8d, 0x8c, 0xff,
+ 0x94, 0x95, 0x94, 0xff, 0x94, 0x94, 0x94, 0xff,
+ 0x94, 0x95, 0x94, 0xff, 0x94, 0x94, 0x94, 0xff,
+ 0x89, 0x88, 0x89, 0xff, 0x94, 0x91, 0x94, 0xff,
+ 0x94, 0x92, 0x94, 0xff, 0x94, 0x91, 0x94, 0xff,
+ 0x32, 0x7a, 0x63, 0xff, 0x42, 0x84, 0x6d, 0xff,
+ 0x42, 0x85, 0x6e, 0xff, 0x39, 0x7f, 0x68, 0xff,
+ 0x3a, 0x72, 0x5b, 0xff, 0x44, 0x7f, 0x6b, 0xff,
+ 0x4a, 0x86, 0x74, 0xff, 0x3f, 0x78, 0x63, 0xff,
+ 0x45, 0x6b, 0x58, 0xff, 0x44, 0x6a, 0x58, 0xff,
+ 0x45, 0x6b, 0x58, 0xff, 0x44, 0x6a, 0x58, 0xff,
+ 0x3a, 0x51, 0x42, 0xff, 0x4d, 0x65, 0x55, 0xff,
+ 0x60, 0x7a, 0x69, 0xff, 0x4d, 0x65, 0x55, 0xff,
+ 0x7c, 0x76, 0x6e, 0xff, 0x8c, 0x89, 0x83, 0xff,
+ 0x7c, 0x76, 0x6e, 0xff, 0x7b, 0x75, 0x6e, 0xff,
+ 0x63, 0x6a, 0x5b, 0xff, 0x6d, 0x78, 0x6b, 0xff,
+ 0x6e, 0x78, 0x6b, 0xff, 0x6e, 0x78, 0x6b, 0xff,
+ 0x58, 0x85, 0x76, 0xff, 0x4d, 0x77, 0x68, 0xff,
+ 0x58, 0x85, 0x76, 0xff, 0x63, 0x92, 0x84, 0xff,
+ 0x4a, 0x95, 0x84, 0xff, 0x4a, 0x94, 0x83, 0xff,
+ 0x4a, 0x95, 0x84, 0xff, 0x4a, 0x94, 0x84, 0xff,
+ 0x53, 0x96, 0x8c, 0xff, 0x42, 0x85, 0x76, 0xff,
+ 0x42, 0x86, 0x76, 0xff, 0x4a, 0x8e, 0x81, 0xff,
+ 0x5b, 0x8a, 0x84, 0xff, 0x5a, 0x89, 0x83, 0xff,
+ 0x53, 0x76, 0x71, 0xff, 0x52, 0x75, 0x70, 0xff,
+ 0x53, 0x5d, 0x55, 0xff, 0x52, 0x5d, 0x55, 0xff,
+ 0x5b, 0x72, 0x69, 0xff, 0x52, 0x5d, 0x55, 0xff,
+ 0x66, 0x6a, 0x60, 0xff, 0x65, 0x69, 0x60, 0xff,
+ 0x7c, 0x82, 0x7c, 0xff, 0x7b, 0x81, 0x7b, 0xff,
+ 0x81, 0x7e, 0x7e, 0xff, 0x81, 0x7d, 0x7e, 0xff,
+ 0x76, 0x72, 0x71, 0xff, 0x76, 0x71, 0x70, 0xff,
+ 0x76, 0x73, 0x71, 0xff, 0x76, 0x72, 0x70, 0xff,
+ 0x81, 0x81, 0x7f, 0xff, 0x8c, 0x8e, 0x8c, 0xff,
+ 0x94, 0x95, 0x94, 0xff, 0x94, 0x94, 0x94, 0xff,
+ 0x84, 0x82, 0x84, 0xff, 0x84, 0x81, 0x84, 0xff,
+ 0x7e, 0x7f, 0x7e, 0xff, 0x89, 0x88, 0x89, 0xff,
+ 0x8a, 0x89, 0x8a, 0xff, 0x89, 0x88, 0x89, 0xff,
+ 0x42, 0x84, 0x6e, 0xff, 0x39, 0x7e, 0x68, 0xff,
+ 0x3a, 0x7f, 0x68, 0xff, 0x41, 0x84, 0x6d, 0xff,
+ 0x3f, 0x78, 0x63, 0xff, 0x39, 0x71, 0x5a, 0xff,
+ 0x45, 0x7f, 0x6b, 0xff, 0x3f, 0x78, 0x62, 0xff,
+ 0x47, 0x74, 0x5d, 0xff, 0x44, 0x6a, 0x57, 0xff,
+ 0x45, 0x6b, 0x58, 0xff, 0x41, 0x61, 0x52, 0xff,
+ 0x3a, 0x51, 0x42, 0xff, 0x39, 0x51, 0x41, 0xff,
+ 0x60, 0x79, 0x68, 0xff, 0x73, 0x8d, 0x7b, 0xff,
+ 0x8c, 0x8a, 0x84, 0xff, 0x8b, 0x89, 0x83, 0xff,
+ 0x7b, 0x75, 0x6e, 0xff, 0x6a, 0x61, 0x57, 0xff,
+ 0x6e, 0x78, 0x6b, 0xff, 0x83, 0x95, 0x8b, 0xff,
+ 0x79, 0x87, 0x7b, 0xff, 0x6d, 0x78, 0x6a, 0xff,
+ 0x63, 0x92, 0x84, 0xff, 0x4c, 0x76, 0x68, 0xff,
+ 0x58, 0x84, 0x76, 0xff, 0x57, 0x84, 0x75, 0xff,
+ 0x4a, 0x95, 0x84, 0xff, 0x41, 0x83, 0x73, 0xff,
+ 0x4a, 0x94, 0x84, 0xff, 0x41, 0x82, 0x73, 0xff,
+ 0x52, 0x96, 0x8c, 0xff, 0x52, 0x95, 0x8b, 0xff,
+ 0x4a, 0x8e, 0x81, 0xff, 0x4a, 0x8d, 0x80, 0xff,
+ 0x52, 0x76, 0x71, 0xff, 0x52, 0x75, 0x70, 0xff,
+ 0x4a, 0x61, 0x5d, 0xff, 0x52, 0x75, 0x70, 0xff,
+ 0x63, 0x86, 0x7c, 0xff, 0x62, 0x85, 0x7b, 0xff,
+ 0x63, 0x86, 0x7b, 0xff, 0x62, 0x85, 0x7b, 0xff,
+ 0x71, 0x76, 0x6e, 0xff, 0x65, 0x69, 0x60, 0xff,
+ 0x65, 0x69, 0x60, 0xff, 0x70, 0x75, 0x6d, 0xff,
+ 0x76, 0x71, 0x71, 0xff, 0x81, 0x7d, 0x7e, 0xff,
+ 0x81, 0x7e, 0x7e, 0xff, 0x6a, 0x65, 0x62, 0xff,
+ 0x6b, 0x65, 0x63, 0xff, 0x81, 0x80, 0x7e, 0xff,
+ 0x8c, 0x8e, 0x8c, 0xff, 0x8b, 0x8d, 0x8b, 0xff,
+ 0x94, 0x95, 0x94, 0xff, 0x83, 0x81, 0x83, 0xff,
+ 0x84, 0x82, 0x84, 0xff, 0x83, 0x81, 0x83, 0xff,
+ 0x73, 0x76, 0x73, 0xff, 0x73, 0x75, 0x73, 0xff,
+ 0x73, 0x75, 0x73, 0xff, 0x73, 0x75, 0x73, 0xff,
+ 0x40, 0x76, 0x60, 0xff, 0x3f, 0x75, 0x60, 0xff,
+ 0x34, 0x6a, 0x55, 0xff, 0x4a, 0x81, 0x6b, 0xff,
+ 0x42, 0x76, 0x63, 0xff, 0x42, 0x75, 0x63, 0xff,
+ 0x42, 0x76, 0x63, 0xff, 0x42, 0x75, 0x63, 0xff,
+ 0x42, 0x51, 0x42, 0xff, 0x42, 0x51, 0x42, 0xff,
+ 0x42, 0x51, 0x42, 0xff, 0x3f, 0x41, 0x34, 0xff,
+ 0x7c, 0x4d, 0x42, 0xff, 0x7b, 0x4d, 0x42, 0xff,
+ 0x8c, 0x78, 0x6e, 0xff, 0x94, 0x8e, 0x83, 0xff,
+ 0x8a, 0x89, 0x79, 0xff, 0x89, 0x88, 0x79, 0xff,
+ 0x7e, 0x7f, 0x6e, 0xff, 0x73, 0x75, 0x63, 0xff,
+ 0x53, 0x6e, 0x63, 0xff, 0x5a, 0x7b, 0x6e, 0xff,
+ 0x63, 0x89, 0x79, 0xff, 0x5a, 0x7b, 0x6e, 0xff,
+ 0x42, 0x7d, 0x6e, 0xff, 0x52, 0x92, 0x84, 0xff,
+ 0x4a, 0x87, 0x79, 0xff, 0x42, 0x7c, 0x6e, 0xff,
+ 0x40, 0x87, 0x79, 0xff, 0x34, 0x80, 0x6e, 0xff,
+ 0x4a, 0x8e, 0x84, 0xff, 0x3f, 0x87, 0x78, 0xff,
+ 0x4d, 0x85, 0x76, 0xff, 0x37, 0x67, 0x58, 0xff,
+ 0x21, 0x49, 0x3a, 0xff, 0x37, 0x66, 0x58, 0xff,
+ 0x55, 0x8e, 0x81, 0xff, 0x4f, 0x81, 0x76, 0xff,
+ 0x4a, 0x76, 0x6b, 0xff, 0x4a, 0x75, 0x6b, 0xff,
+ 0x48, 0x81, 0x6e, 0xff, 0x42, 0x75, 0x63, 0xff,
+ 0x42, 0x76, 0x63, 0xff, 0x42, 0x75, 0x63, 0xff,
+ 0x63, 0x76, 0x6b, 0xff, 0x58, 0x68, 0x60, 0xff,
+ 0x58, 0x68, 0x60, 0xff, 0x5d, 0x6e, 0x65, 0xff,
+ 0x6e, 0x6c, 0x6b, 0xff, 0x6e, 0x6c, 0x6b, 0xff,
+ 0x84, 0x82, 0x7c, 0xff, 0x83, 0x81, 0x7b, 0xff,
+ 0x8a, 0x89, 0x87, 0xff, 0x7e, 0x7b, 0x79, 0xff,
+ 0x89, 0x89, 0x87, 0xff, 0x89, 0x88, 0x86, 0xff,
+ 0x8c, 0x8d, 0x8c, 0xff, 0x84, 0x83, 0x84, 0xff,
+ 0x7c, 0x7a, 0x7c, 0xff, 0x7b, 0x79, 0x7b, 0xff,
+ 0x8a, 0x83, 0x7f, 0xff, 0x89, 0x83, 0x7e, 0xff,
+ 0x89, 0x83, 0x7e, 0xff, 0x83, 0x79, 0x73, 0xff,
+ 0x34, 0x69, 0x55, 0xff, 0x34, 0x69, 0x55, 0xff,
+ 0x34, 0x69, 0x55, 0xff, 0x4a, 0x81, 0x6b, 0xff,
+ 0x42, 0x75, 0x63, 0xff, 0x41, 0x75, 0x62, 0xff,
+ 0x3f, 0x5f, 0x4a, 0xff, 0x3c, 0x47, 0x31, 0xff,
+ 0x3f, 0x41, 0x34, 0xff, 0x3c, 0x30, 0x26, 0xff,
+ 0x3d, 0x31, 0x27, 0xff, 0x3c, 0x30, 0x26, 0xff,
+ 0x7b, 0x4d, 0x42, 0xff, 0x83, 0x62, 0x57, 0xff,
+ 0x84, 0x63, 0x58, 0xff, 0x8c, 0x78, 0x6d, 0xff,
+ 0x7e, 0x7f, 0x6e, 0xff, 0x89, 0x88, 0x78, 0xff,
+ 0x94, 0x92, 0x84, 0xff, 0x7e, 0x7f, 0x6d, 0xff,
+ 0x52, 0x6d, 0x63, 0xff, 0x5a, 0x7a, 0x6d, 0xff,
+ 0x63, 0x88, 0x79, 0xff, 0x5a, 0x7a, 0x6d, 0xff,
+ 0x3a, 0x71, 0x63, 0xff, 0x4a, 0x87, 0x78, 0xff,
+ 0x4a, 0x87, 0x79, 0xff, 0x42, 0x7c, 0x6d, 0xff,
+ 0x34, 0x80, 0x6e, 0xff, 0x3f, 0x87, 0x78, 0xff,
+ 0x34, 0x80, 0x6e, 0xff, 0x3f, 0x87, 0x78, 0xff,
+ 0x63, 0xa2, 0x94, 0xff, 0x4c, 0x84, 0x75, 0xff,
+ 0x21, 0x49, 0x3a, 0xff, 0x21, 0x49, 0x39, 0xff,
+ 0x55, 0x8e, 0x81, 0xff, 0x55, 0x8d, 0x80, 0xff,
+ 0x5b, 0x9a, 0x8c, 0xff, 0x5a, 0x9a, 0x8c, 0xff,
+ 0x47, 0x80, 0x6e, 0xff, 0x47, 0x80, 0x6d, 0xff,
+ 0x48, 0x80, 0x6e, 0xff, 0x47, 0x80, 0x6d, 0xff,
+ 0x5d, 0x6f, 0x66, 0xff, 0x57, 0x67, 0x60, 0xff,
+ 0x58, 0x68, 0x60, 0xff, 0x62, 0x75, 0x6b, 0xff,
+ 0x63, 0x61, 0x63, 0xff, 0x62, 0x61, 0x62, 0xff,
+ 0x6e, 0x6c, 0x6b, 0xff, 0x83, 0x81, 0x7b, 0xff,
+ 0x94, 0x96, 0x94, 0xff, 0x94, 0x95, 0x94, 0xff,
+ 0x94, 0x96, 0x94, 0xff, 0x94, 0x95, 0x94, 0xff,
+ 0x94, 0x96, 0x94, 0xff, 0x94, 0x95, 0x94, 0xff,
+ 0x8c, 0x8d, 0x8c, 0xff, 0x83, 0x83, 0x83, 0xff,
+ 0x8f, 0x8c, 0x89, 0xff, 0x94, 0x95, 0x94, 0xff,
+ 0x94, 0x96, 0x94, 0xff, 0x8e, 0x8c, 0x89, 0xff,
+ 0x29, 0x5d, 0x4a, 0xff, 0x34, 0x69, 0x55, 0xff,
+ 0x3f, 0x76, 0x60, 0xff, 0x4a, 0x81, 0x6b, 0xff,
+ 0x42, 0x76, 0x63, 0xff, 0x3f, 0x5e, 0x4a, 0xff,
+ 0x3d, 0x48, 0x32, 0xff, 0x39, 0x30, 0x19, 0xff,
+ 0x3a, 0x21, 0x19, 0xff, 0x39, 0x20, 0x18, 0xff,
+ 0x3a, 0x21, 0x19, 0xff, 0x3c, 0x30, 0x26, 0xff,
+ 0x7c, 0x4d, 0x42, 0xff, 0x7b, 0x4d, 0x42, 0xff,
+ 0x7c, 0x4d, 0x42, 0xff, 0x84, 0x62, 0x58, 0xff,
+ 0x89, 0x89, 0x79, 0xff, 0x94, 0x91, 0x83, 0xff,
+ 0x8a, 0x89, 0x79, 0xff, 0x73, 0x75, 0x63, 0xff,
+ 0x63, 0x89, 0x79, 0xff, 0x5a, 0x7b, 0x6d, 0xff,
+ 0x5b, 0x7b, 0x6e, 0xff, 0x63, 0x88, 0x79, 0xff,
+ 0x4a, 0x87, 0x79, 0xff, 0x39, 0x71, 0x62, 0xff,
+ 0x3a, 0x72, 0x63, 0xff, 0x42, 0x7c, 0x6e, 0xff,
+ 0x34, 0x80, 0x6e, 0xff, 0x29, 0x79, 0x62, 0xff,
+ 0x3f, 0x87, 0x79, 0xff, 0x4a, 0x8e, 0x84, 0xff,
+ 0x63, 0xa2, 0x94, 0xff, 0x62, 0xa2, 0x94, 0xff,
+ 0x63, 0xa2, 0x94, 0xff, 0x4d, 0x84, 0x76, 0xff,
+ 0x5b, 0x9a, 0x8c, 0xff, 0x55, 0x8d, 0x81, 0xff,
+ 0x5b, 0x9a, 0x8c, 0xff, 0x5a, 0x9a, 0x8c, 0xff,
+ 0x53, 0x96, 0x84, 0xff, 0x4d, 0x8b, 0x78, 0xff,
+ 0x4d, 0x8b, 0x79, 0xff, 0x42, 0x75, 0x63, 0xff,
+ 0x5e, 0x6f, 0x66, 0xff, 0x5d, 0x6e, 0x65, 0xff,
+ 0x53, 0x62, 0x5b, 0xff, 0x5d, 0x6f, 0x65, 0xff,
+ 0x63, 0x61, 0x63, 0xff, 0x6d, 0x6c, 0x6b, 0xff,
+ 0x6e, 0x6c, 0x6b, 0xff, 0x6e, 0x6c, 0x6b, 0xff,
+ 0x73, 0x6e, 0x6b, 0xff, 0x7e, 0x7b, 0x78, 0xff,
+ 0x8a, 0x89, 0x87, 0xff, 0x89, 0x88, 0x86, 0xff,
+ 0x8c, 0x8d, 0x8c, 0xff, 0x8c, 0x8c, 0x8c, 0xff,
+ 0x94, 0x96, 0x94, 0xff, 0x8c, 0x8c, 0x8c, 0xff,
+ 0x8f, 0x8d, 0x89, 0xff, 0x94, 0x96, 0x94, 0xff,
+ 0x8f, 0x8d, 0x8a, 0xff, 0x8e, 0x8c, 0x89, 0xff,
+ 0x29, 0x5d, 0x4a, 0xff, 0x4a, 0x81, 0x6b, 0xff,
+ 0x4a, 0x82, 0x6b, 0xff, 0x4a, 0x81, 0x6a, 0xff,
+ 0x42, 0x76, 0x63, 0xff, 0x3c, 0x47, 0x31, 0xff,
+ 0x3a, 0x31, 0x19, 0xff, 0x39, 0x30, 0x18, 0xff,
+ 0x3c, 0x31, 0x27, 0xff, 0x3c, 0x30, 0x26, 0xff,
+ 0x3c, 0x31, 0x26, 0xff, 0x3f, 0x40, 0x34, 0xff,
+ 0x7c, 0x4d, 0x42, 0xff, 0x83, 0x62, 0x57, 0xff,
+ 0x84, 0x63, 0x58, 0xff, 0x83, 0x62, 0x57, 0xff,
+ 0x73, 0x76, 0x63, 0xff, 0x7e, 0x7e, 0x6d, 0xff,
+ 0x89, 0x88, 0x79, 0xff, 0x7e, 0x7e, 0x6d, 0xff,
+ 0x6b, 0x96, 0x84, 0xff, 0x62, 0x88, 0x78, 0xff,
+ 0x5b, 0x7b, 0x6e, 0xff, 0x5a, 0x7a, 0x6d, 0xff,
+ 0x42, 0x7c, 0x6e, 0xff, 0x39, 0x71, 0x62, 0xff,
+ 0x42, 0x7c, 0x6e, 0xff, 0x39, 0x71, 0x62, 0xff,
+ 0x34, 0x80, 0x6e, 0xff, 0x29, 0x79, 0x62, 0xff,
+ 0x34, 0x80, 0x6e, 0xff, 0x34, 0x80, 0x6d, 0xff,
+ 0x37, 0x67, 0x58, 0xff, 0x4c, 0x84, 0x76, 0xff,
+ 0x63, 0xa2, 0x94, 0xff, 0x62, 0xa1, 0x94, 0xff,
+ 0x50, 0x82, 0x76, 0xff, 0x55, 0x8d, 0x81, 0xff,
+ 0x55, 0x8e, 0x81, 0xff, 0x5a, 0x99, 0x8b, 0xff,
+ 0x52, 0x96, 0x84, 0xff, 0x52, 0x95, 0x83, 0xff,
+ 0x4d, 0x8b, 0x79, 0xff, 0x47, 0x80, 0x6d, 0xff,
+ 0x5d, 0x6f, 0x66, 0xff, 0x62, 0x75, 0x6b, 0xff,
+ 0x52, 0x61, 0x5b, 0xff, 0x5d, 0x6e, 0x65, 0xff,
+ 0x84, 0x82, 0x7c, 0xff, 0x83, 0x81, 0x7b, 0xff,
+ 0x79, 0x77, 0x73, 0xff, 0x78, 0x76, 0x73, 0xff,
+ 0x73, 0x6d, 0x6b, 0xff, 0x73, 0x6d, 0x6b, 0xff,
+ 0x73, 0x6d, 0x6b, 0xff, 0x89, 0x88, 0x86, 0xff,
+ 0x84, 0x83, 0x84, 0xff, 0x83, 0x83, 0x83, 0xff,
+ 0x8c, 0x8c, 0x8c, 0xff, 0x8b, 0x8c, 0x8b, 0xff,
+ 0x89, 0x83, 0x7e, 0xff, 0x89, 0x83, 0x7e, 0xff,
+ 0x8f, 0x8c, 0x89, 0xff, 0x8e, 0x8c, 0x89, 0xff,
+ 0xef, 0x9d, 0x7f, 0xff, 0xe6, 0x97, 0x79, 0xff,
+ 0xe7, 0x97, 0x79, 0xff, 0xde, 0x92, 0x73, 0xff,
+ 0xdf, 0x8e, 0x74, 0xff, 0xe4, 0x94, 0x79, 0xff,
+ 0xde, 0x8e, 0x74, 0xff, 0xe3, 0x94, 0x78, 0xff,
+ 0xe4, 0x95, 0x79, 0xff, 0xe4, 0x94, 0x79, 0xff,
+ 0xde, 0x8e, 0x74, 0xff, 0xe3, 0x94, 0x78, 0xff,
+ 0xe7, 0x92, 0x74, 0xff, 0xe6, 0x92, 0x73, 0xff,
+ 0xe7, 0x92, 0x74, 0xff, 0xe6, 0x92, 0x73, 0xff,
+ 0xdf, 0x8e, 0x6b, 0xff, 0xe4, 0x92, 0x70, 0xff,
+ 0xe4, 0x92, 0x71, 0xff, 0xe3, 0x92, 0x70, 0xff,
+ 0xe1, 0x95, 0x76, 0xff, 0xe1, 0x94, 0x76, 0xff,
+ 0xe1, 0x95, 0x76, 0xff, 0xe1, 0x94, 0x76, 0xff,
+ 0xdf, 0x96, 0x7c, 0xff, 0xde, 0x96, 0x7b, 0xff,
+ 0xd6, 0x92, 0x7c, 0xff, 0xde, 0x96, 0x7b, 0xff,
+ 0xdf, 0x96, 0x79, 0xff, 0xde, 0x96, 0x79, 0xff,
+ 0xde, 0x96, 0x79, 0xff, 0xd6, 0x92, 0x73, 0xff,
+ 0xdf, 0x98, 0x79, 0xff, 0xd6, 0x92, 0x73, 0xff,
+ 0xde, 0x97, 0x79, 0xff, 0xde, 0x97, 0x78, 0xff,
+ 0xdf, 0x9a, 0x7c, 0xff, 0xde, 0x9a, 0x7b, 0xff,
+ 0xe7, 0xa0, 0x81, 0xff, 0xe6, 0x9f, 0x81, 0xff,
+ 0xec, 0xa2, 0x87, 0xff, 0xec, 0xa2, 0x86, 0xff,
+ 0xe7, 0x9e, 0x84, 0xff, 0xe6, 0x9e, 0x83, 0xff,
+ 0xe7, 0xa2, 0x84, 0xff, 0xe6, 0xa2, 0x84, 0xff,
+ 0xe7, 0xa2, 0x84, 0xff, 0xe6, 0xa2, 0x83, 0xff,
+ 0xef, 0xaf, 0x95, 0xff, 0xef, 0xae, 0x94, 0xff,
+ 0xef, 0xae, 0x94, 0xff, 0xf4, 0xb3, 0x99, 0xff,
+ 0xfa, 0xbc, 0xa2, 0xff, 0xfc, 0xc1, 0xa7, 0xff,
+ 0xfd, 0xc1, 0xa8, 0xff, 0xf9, 0xbb, 0xa2, 0xff,
+ 0xef, 0xb9, 0xa2, 0xff, 0xef, 0xb9, 0xa2, 0xff,
+ 0xef, 0xb9, 0xa2, 0xff, 0xee, 0xb9, 0xa2, 0xff,
+ 0xef, 0xb3, 0x95, 0xff, 0xef, 0xb2, 0x94, 0xff,
+ 0xef, 0xb2, 0x94, 0xff, 0xb8, 0x87, 0x6e, 0xff,
+ 0xef, 0x9d, 0x7e, 0xff, 0xf6, 0xa1, 0x83, 0xff,
+ 0xef, 0x9d, 0x7e, 0xff, 0xee, 0x9c, 0x7e, 0xff,
+ 0xe4, 0x95, 0x79, 0xff, 0xe9, 0x9b, 0x7e, 0xff,
+ 0xe9, 0x9b, 0x7e, 0xff, 0xee, 0xa2, 0x83, 0xff,
+ 0xe9, 0x9b, 0x7e, 0xff, 0xee, 0xa1, 0x83, 0xff,
+ 0xe9, 0x9b, 0x7e, 0xff, 0xe9, 0x9b, 0x7e, 0xff,
+ 0xec, 0x9d, 0x7e, 0xff, 0xe9, 0x97, 0x78, 0xff,
+ 0xe9, 0x97, 0x79, 0xff, 0xe6, 0x91, 0x73, 0xff,
+ 0xe4, 0x92, 0x71, 0xff, 0xe9, 0x95, 0x75, 0xff,
+ 0xe9, 0x96, 0x76, 0xff, 0xe9, 0x95, 0x76, 0xff,
+ 0xe4, 0x97, 0x79, 0xff, 0xe3, 0x97, 0x78, 0xff,
+ 0xe7, 0x9a, 0x7c, 0xff, 0xe6, 0x9a, 0x7b, 0xff,
+ 0xe6, 0x9a, 0x7b, 0xff, 0xe6, 0x99, 0x7b, 0xff,
+ 0xe7, 0x9a, 0x7c, 0xff, 0xde, 0x95, 0x7b, 0xff,
+ 0xde, 0x96, 0x79, 0xff, 0xde, 0x95, 0x78, 0xff,
+ 0xde, 0x96, 0x79, 0xff, 0xe6, 0x9a, 0x7e, 0xff,
+ 0xe6, 0x9d, 0x7e, 0xff, 0xe6, 0x9c, 0x7e, 0xff,
+ 0xe7, 0x9d, 0x7e, 0xff, 0xe6, 0x9c, 0x7e, 0xff,
+ 0xe6, 0x9f, 0x81, 0xff, 0xe6, 0x9f, 0x80, 0xff,
+ 0xe7, 0x9f, 0x81, 0xff, 0xee, 0xa4, 0x86, 0xff,
+ 0xec, 0xa2, 0x86, 0xff, 0xf1, 0xa6, 0x89, 0xff,
+ 0xf2, 0xa6, 0x89, 0xff, 0xf1, 0xa6, 0x89, 0xff,
+ 0xec, 0xa9, 0x8c, 0xff, 0xeb, 0xa8, 0x8b, 0xff,
+ 0xf2, 0xb0, 0x94, 0xff, 0xf1, 0xaf, 0x94, 0xff,
+ 0xef, 0xae, 0x94, 0xff, 0xf4, 0xb3, 0x99, 0xff,
+ 0xfa, 0xb9, 0x9f, 0xff, 0xff, 0xbe, 0xa4, 0xff,
+ 0xff, 0xc6, 0xad, 0xff, 0xff, 0xc6, 0xac, 0xff,
+ 0xff, 0xc7, 0xad, 0xff, 0xf9, 0xbb, 0xa1, 0xff,
+ 0xef, 0xb9, 0xa2, 0xff, 0xee, 0xb8, 0xa1, 0xff,
+ 0xef, 0xb9, 0xa2, 0xff, 0xee, 0xb9, 0xa1, 0xff,
+ 0xef, 0xb2, 0x94, 0xff, 0xb7, 0x87, 0x6d, 0xff,
+ 0x81, 0x5c, 0x48, 0xff, 0x81, 0x5b, 0x47, 0xff,
+ 0xef, 0x9d, 0x7e, 0xff, 0xee, 0x9c, 0x7e, 0xff,
+ 0xf7, 0xa2, 0x84, 0xff, 0xee, 0x9c, 0x7e, 0xff,
+ 0xe9, 0x9b, 0x7e, 0xff, 0xe9, 0x9b, 0x7e, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa2, 0x84, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa2, 0x83, 0xff,
+ 0xe9, 0x9c, 0x7f, 0xff, 0xe9, 0x9b, 0x7e, 0xff,
+ 0xec, 0x9d, 0x7e, 0xff, 0xec, 0x9c, 0x7e, 0xff,
+ 0xec, 0x9d, 0x7f, 0xff, 0xe9, 0x97, 0x79, 0xff,
+ 0xe9, 0x96, 0x76, 0xff, 0xe9, 0x96, 0x76, 0xff,
+ 0xe9, 0x96, 0x76, 0xff, 0xe9, 0x96, 0x76, 0xff,
+ 0xe4, 0x97, 0x79, 0xff, 0xe3, 0x97, 0x78, 0xff,
+ 0xe4, 0x98, 0x79, 0xff, 0xe6, 0x9a, 0x7b, 0xff,
+ 0xe7, 0x9a, 0x7c, 0xff, 0xe6, 0x9a, 0x7b, 0xff,
+ 0xe7, 0x9a, 0x7c, 0xff, 0xe6, 0x9a, 0x7b, 0xff,
+ 0xde, 0x96, 0x79, 0xff, 0xde, 0x96, 0x78, 0xff,
+ 0xe7, 0x9a, 0x7f, 0xff, 0xee, 0x9e, 0x84, 0xff,
+ 0xe7, 0x9d, 0x7e, 0xff, 0xe6, 0x9c, 0x7e, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa2, 0x84, 0xff,
+ 0xef, 0xa5, 0x87, 0xff, 0xee, 0xa4, 0x86, 0xff,
+ 0xef, 0xa5, 0x87, 0xff, 0xee, 0xa5, 0x86, 0xff,
+ 0xf2, 0xa6, 0x89, 0xff, 0xec, 0xa2, 0x86, 0xff,
+ 0xec, 0xa2, 0x87, 0xff, 0xf1, 0xa6, 0x89, 0xff,
+ 0xec, 0xa9, 0x8c, 0xff, 0xec, 0xa8, 0x8c, 0xff,
+ 0xf2, 0xb0, 0x94, 0xff, 0xf7, 0xb6, 0x9c, 0xff,
+ 0xf4, 0xb4, 0x9a, 0xff, 0xf9, 0xb9, 0x9f, 0xff,
+ 0xff, 0xbf, 0xa5, 0xff, 0xff, 0xbe, 0xa4, 0xff,
+ 0xfd, 0xc1, 0xa8, 0xff, 0xf9, 0xbb, 0xa2, 0xff,
+ 0xfa, 0xbc, 0xa2, 0xff, 0xf7, 0xb6, 0x9c, 0xff,
+ 0xef, 0xb9, 0xa2, 0xff, 0xee, 0xb9, 0xa2, 0xff,
+ 0xff, 0xc7, 0xad, 0xff, 0xee, 0xb9, 0xa2, 0xff,
+ 0x81, 0x5c, 0x48, 0xff, 0x4a, 0x30, 0x21, 0xff,
+ 0x4a, 0x31, 0x21, 0xff, 0x4a, 0x30, 0x21, 0xff,
+ 0xf7, 0xa2, 0x84, 0xff, 0xee, 0x9c, 0x7e, 0xff,
+ 0xef, 0x9d, 0x7e, 0xff, 0xf6, 0xa1, 0x83, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa2, 0x83, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa1, 0x83, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa2, 0x83, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa1, 0x83, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa2, 0x83, 0xff,
+ 0xec, 0x9d, 0x7e, 0xff, 0xeb, 0x9c, 0x7e, 0xff,
+ 0xe9, 0x96, 0x76, 0xff, 0xee, 0x99, 0x7b, 0xff,
+ 0xef, 0x9a, 0x7b, 0xff, 0xe9, 0x95, 0x75, 0xff,
+ 0xe4, 0x97, 0x79, 0xff, 0xe6, 0x99, 0x7b, 0xff,
+ 0xe4, 0x97, 0x79, 0xff, 0xe3, 0x97, 0x78, 0xff,
+ 0xe6, 0x9a, 0x7c, 0xff, 0xe6, 0x99, 0x7b, 0xff,
+ 0xef, 0x9e, 0x7b, 0xff, 0xe6, 0x99, 0x7b, 0xff,
+ 0xe6, 0x9a, 0x7e, 0xff, 0xe6, 0x99, 0x7e, 0xff,
+ 0xef, 0x9e, 0x84, 0xff, 0xee, 0x9d, 0x83, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa2, 0x83, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa1, 0x83, 0xff,
+ 0xef, 0xa5, 0x87, 0xff, 0xf6, 0xaa, 0x8b, 0xff,
+ 0xf7, 0xaa, 0x8c, 0xff, 0xf6, 0xaa, 0x8b, 0xff,
+ 0xf7, 0xaa, 0x8c, 0xff, 0xf1, 0xa6, 0x89, 0xff,
+ 0xf7, 0xaa, 0x8c, 0xff, 0xf6, 0xaa, 0x8b, 0xff,
+ 0xf1, 0xb0, 0x94, 0xff, 0xf1, 0xaf, 0x94, 0xff,
+ 0xf7, 0xb6, 0x9c, 0xff, 0xf6, 0xb6, 0x9c, 0xff,
+ 0xff, 0xbe, 0xa5, 0xff, 0xff, 0xbe, 0xa4, 0xff,
+ 0xff, 0xbe, 0xa5, 0xff, 0xff, 0xbe, 0xa4, 0xff,
+ 0xfa, 0xbc, 0xa2, 0xff, 0xf6, 0xb6, 0x9c, 0xff,
+ 0xf7, 0xb6, 0x9c, 0xff, 0xf6, 0xb6, 0x9c, 0xff,
+ 0xef, 0xb9, 0xa2, 0xff, 0xff, 0xc6, 0xac, 0xff,
+ 0xff, 0xc6, 0xad, 0xff, 0xcd, 0x9d, 0x8b, 0xff,
+ 0x81, 0x5c, 0x47, 0xff, 0x4a, 0x30, 0x21, 0xff,
+ 0x4a, 0x31, 0x21, 0xff, 0x4a, 0x30, 0x20, 0xff,
+ 0xf7, 0xa2, 0x84, 0xff, 0xf4, 0xa1, 0x81, 0xff,
+ 0xef, 0x9e, 0x7c, 0xff, 0xf1, 0x9f, 0x7e, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xf1, 0xa1, 0x7e, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa2, 0x83, 0xff,
+ 0xf7, 0xa6, 0x84, 0xff, 0xf4, 0xa3, 0x84, 0xff,
+ 0xf7, 0xa6, 0x84, 0xff, 0xf4, 0xa3, 0x83, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xef, 0xa2, 0x84, 0xff,
+ 0xef, 0xa1, 0x81, 0xff, 0xee, 0x9f, 0x7e, 0xff,
+ 0xef, 0x9a, 0x7c, 0xff, 0xef, 0x9a, 0x7b, 0xff,
+ 0xef, 0x9a, 0x7c, 0xff, 0xee, 0x9a, 0x7b, 0xff,
+ 0xef, 0x9a, 0x7c, 0xff, 0xef, 0x9a, 0x7b, 0xff,
+ 0xef, 0x9d, 0x7e, 0xff, 0xee, 0x9a, 0x7b, 0xff,
+ 0xe7, 0x9e, 0x7c, 0xff, 0xe9, 0xa1, 0x81, 0xff,
+ 0xe9, 0xa1, 0x81, 0xff, 0xe9, 0xa0, 0x81, 0xff,
+ 0xef, 0x9e, 0x7c, 0xff, 0xef, 0x9e, 0x7b, 0xff,
+ 0xef, 0xa2, 0x81, 0xff, 0xee, 0xa2, 0x81, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xf1, 0xa7, 0x89, 0xff,
+ 0xf2, 0xa8, 0x89, 0xff, 0xf4, 0xad, 0x8e, 0xff,
+ 0xf2, 0xaf, 0x8f, 0xff, 0xef, 0xaa, 0x8c, 0xff,
+ 0xef, 0xaa, 0x8c, 0xff, 0xee, 0xaa, 0x8c, 0xff,
+ 0xef, 0xaa, 0x8c, 0xff, 0xf1, 0xae, 0x91, 0xff,
+ 0xf2, 0xae, 0x92, 0xff, 0xf4, 0xb2, 0x97, 0xff,
+ 0xf7, 0xb7, 0x9d, 0xff, 0xf9, 0xb9, 0x9c, 0xff,
+ 0xfd, 0xbc, 0x9d, 0xff, 0xfc, 0xbb, 0x9c, 0xff,
+ 0xff, 0xbf, 0x9d, 0xff, 0xfc, 0xbc, 0x9c, 0xff,
+ 0xfa, 0xb9, 0x9d, 0xff, 0xf9, 0xb9, 0x9c, 0xff,
+ 0xff, 0xb9, 0x9d, 0xff, 0xff, 0xb6, 0x9c, 0xff,
+ 0xff, 0xb9, 0x9d, 0xff, 0xff, 0xbb, 0x9c, 0xff,
+ 0xff, 0xc3, 0xa5, 0xff, 0xff, 0xc2, 0xa4, 0xff,
+ 0xff, 0xc3, 0xa5, 0xff, 0xa7, 0x79, 0x68, 0xff,
+ 0x7c, 0x55, 0x45, 0xff, 0x3a, 0x24, 0x19, 0xff,
+ 0x3a, 0x25, 0x19, 0xff, 0x39, 0x24, 0x19, 0xff,
+ 0xf7, 0xa2, 0x84, 0xff, 0xf6, 0xa1, 0x83, 0xff,
+ 0xf7, 0xa2, 0x84, 0xff, 0xf4, 0xa0, 0x81, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa1, 0x83, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa2, 0x83, 0xff,
+ 0xf7, 0xa6, 0x84, 0xff, 0xf4, 0xa3, 0x83, 0xff,
+ 0xf4, 0xa3, 0x84, 0xff, 0xf4, 0xa3, 0x83, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa1, 0x83, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0x9f, 0x7e, 0xff,
+ 0xef, 0x9d, 0x7e, 0xff, 0xee, 0x99, 0x7b, 0xff,
+ 0xef, 0x9d, 0x7e, 0xff, 0xee, 0x9c, 0x7e, 0xff,
+ 0xef, 0x9f, 0x81, 0xff, 0xee, 0x9c, 0x7e, 0xff,
+ 0xef, 0x9d, 0x7e, 0xff, 0xee, 0x9c, 0x7e, 0xff,
+ 0xe9, 0xa1, 0x81, 0xff, 0xe9, 0xa0, 0x80, 0xff,
+ 0xec, 0xa3, 0x87, 0xff, 0xe9, 0xa0, 0x81, 0xff,
+ 0xef, 0xa2, 0x81, 0xff, 0xee, 0xa1, 0x80, 0xff,
+ 0xef, 0xa2, 0x81, 0xff, 0xee, 0xa6, 0x86, 0xff,
+ 0xf1, 0xa7, 0x89, 0xff, 0xf4, 0xac, 0x8e, 0xff,
+ 0xf4, 0xad, 0x8f, 0xff, 0xf6, 0xb2, 0x94, 0xff,
+ 0xf1, 0xae, 0x8f, 0xff, 0xee, 0xaa, 0x8b, 0xff,
+ 0xef, 0xaa, 0x8c, 0xff, 0xf1, 0xae, 0x8e, 0xff,
+ 0xf1, 0xae, 0x91, 0xff, 0xf4, 0xb2, 0x96, 0xff,
+ 0xf4, 0xb2, 0x97, 0xff, 0xf6, 0xb6, 0x9c, 0xff,
+ 0xfa, 0xb9, 0x9c, 0xff, 0xfc, 0xbb, 0x9c, 0xff,
+ 0xfa, 0xb9, 0x9d, 0xff, 0xf6, 0xb6, 0x9c, 0xff,
+ 0xf7, 0xb6, 0x9c, 0xff, 0xf9, 0xb8, 0x9c, 0xff,
+ 0xfc, 0xbc, 0x9d, 0xff, 0xfc, 0xbb, 0x9c, 0xff,
+ 0xff, 0xbe, 0x9c, 0xff, 0xff, 0xbb, 0x9c, 0xff,
+ 0xff, 0xbc, 0x9d, 0xff, 0xff, 0xbe, 0x9c, 0xff,
+ 0xff, 0xc2, 0xa5, 0xff, 0xff, 0xc2, 0xa4, 0xff,
+ 0xff, 0xc3, 0xa5, 0xff, 0x7b, 0x55, 0x4a, 0xff,
+ 0x3a, 0x25, 0x19, 0xff, 0x39, 0x24, 0x18, 0xff,
+ 0x3a, 0x25, 0x19, 0xff, 0x39, 0x24, 0x18, 0xff,
+ 0xf4, 0xa1, 0x81, 0xff, 0xf4, 0xa0, 0x81, 0xff,
+ 0xf2, 0xa0, 0x7f, 0xff, 0xf4, 0xa0, 0x81, 0xff,
+ 0xf2, 0xa1, 0x7e, 0xff, 0xee, 0xa2, 0x83, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa2, 0x84, 0xff,
+ 0xf2, 0xa1, 0x84, 0xff, 0xf4, 0xa3, 0x83, 0xff,
+ 0xf4, 0xa4, 0x84, 0xff, 0xf4, 0xa3, 0x84, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa2, 0x83, 0xff,
+ 0xef, 0xa1, 0x81, 0xff, 0xee, 0x9e, 0x7b, 0xff,
+ 0xef, 0x9a, 0x7c, 0xff, 0xee, 0x9a, 0x7b, 0xff,
+ 0xef, 0x9d, 0x7f, 0xff, 0xee, 0x9f, 0x81, 0xff,
+ 0xef, 0x9f, 0x81, 0xff, 0xee, 0x9f, 0x81, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa2, 0x84, 0xff,
+ 0xec, 0xa4, 0x87, 0xff, 0xec, 0xa3, 0x86, 0xff,
+ 0xec, 0xa4, 0x87, 0xff, 0xe9, 0xa0, 0x81, 0xff,
+ 0xef, 0xa2, 0x81, 0xff, 0xee, 0xa2, 0x81, 0xff,
+ 0xef, 0xa2, 0x81, 0xff, 0xee, 0xaa, 0x8c, 0xff,
+ 0xf4, 0xad, 0x8f, 0xff, 0xf7, 0xb2, 0x94, 0xff,
+ 0xf7, 0xb3, 0x94, 0xff, 0xf7, 0xb2, 0x94, 0xff,
+ 0xf2, 0xae, 0x8f, 0xff, 0xf4, 0xb2, 0x91, 0xff,
+ 0xf2, 0xae, 0x8f, 0xff, 0xf4, 0xb2, 0x91, 0xff,
+ 0xf4, 0xb2, 0x97, 0xff, 0xf7, 0xb6, 0x9c, 0xff,
+ 0xf7, 0xb7, 0x9d, 0xff, 0xf7, 0xb6, 0x9c, 0xff,
+ 0xf7, 0xb6, 0x9d, 0xff, 0xf7, 0xb6, 0x9c, 0xff,
+ 0xfa, 0xb9, 0x9d, 0xff, 0xf9, 0xb9, 0x9c, 0xff,
+ 0xfa, 0xb9, 0x9d, 0xff, 0xf9, 0xb9, 0x9c, 0xff,
+ 0xfd, 0xbc, 0x9d, 0xff, 0xff, 0xbe, 0x9c, 0xff,
+ 0xff, 0xbf, 0x9d, 0xff, 0xff, 0xbe, 0x9c, 0xff,
+ 0xff, 0xbf, 0x9d, 0xff, 0xff, 0xbe, 0x9c, 0xff,
+ 0xff, 0xc3, 0xa5, 0xff, 0xff, 0xc2, 0xa4, 0xff,
+ 0xd4, 0x9e, 0x87, 0xff, 0xd3, 0x9e, 0x86, 0xff,
+ 0xbd, 0x86, 0x71, 0xff, 0x7b, 0x55, 0x44, 0xff,
+ 0x7c, 0x55, 0x45, 0xff, 0x7b, 0x55, 0x44, 0xff,
+ 0xef, 0x9e, 0x7c, 0xff, 0xf1, 0x9f, 0x7e, 0xff,
+ 0xf4, 0xa1, 0x81, 0xff, 0xf1, 0x9f, 0x7e, 0xff,
+ 0xf1, 0xa1, 0x7e, 0xff, 0xf1, 0xa0, 0x7e, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa1, 0x83, 0xff,
+ 0xf1, 0xa1, 0x84, 0xff, 0xf4, 0xa3, 0x83, 0xff,
+ 0xf1, 0xa1, 0x84, 0xff, 0xf1, 0xa0, 0x83, 0xff,
+ 0xef, 0xa1, 0x81, 0xff, 0xee, 0xa2, 0x83, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa0, 0x80, 0xff,
+ 0xef, 0x9d, 0x7e, 0xff, 0xee, 0x9f, 0x81, 0xff,
+ 0xef, 0x9f, 0x81, 0xff, 0xee, 0x9f, 0x80, 0xff,
+ 0xef, 0x9f, 0x81, 0xff, 0xee, 0xa2, 0x83, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa1, 0x83, 0xff,
+ 0xe9, 0xa1, 0x81, 0xff, 0xeb, 0xa3, 0x86, 0xff,
+ 0xec, 0xa3, 0x86, 0xff, 0xeb, 0xa3, 0x86, 0xff,
+ 0xef, 0xa6, 0x87, 0xff, 0xee, 0xa6, 0x86, 0xff,
+ 0xef, 0xaa, 0x8c, 0xff, 0xee, 0xaa, 0x8b, 0xff,
+ 0xf7, 0xb2, 0x94, 0xff, 0xf6, 0xb2, 0x94, 0xff,
+ 0xf4, 0xad, 0x8f, 0xff, 0xf6, 0xb2, 0x94, 0xff,
+ 0xf4, 0xb2, 0x91, 0xff, 0xf1, 0xae, 0x8e, 0xff,
+ 0xf4, 0xb2, 0x91, 0xff, 0xf4, 0xb2, 0x91, 0xff,
+ 0xf7, 0xb6, 0x9c, 0xff, 0xf6, 0xb6, 0x9c, 0xff,
+ 0xf7, 0xb6, 0x9c, 0xff, 0xf6, 0xb6, 0x9c, 0xff,
+ 0xfa, 0xb9, 0x9c, 0xff, 0xfc, 0xbb, 0x9c, 0xff,
+ 0xfc, 0xbc, 0x9c, 0xff, 0xff, 0xbe, 0x9c, 0xff,
+ 0xff, 0xbe, 0x9c, 0xff, 0xff, 0xbe, 0x9c, 0xff,
+ 0xff, 0xbe, 0x9c, 0xff, 0xff, 0xbe, 0x9c, 0xff,
+ 0xff, 0xbc, 0x9c, 0xff, 0xff, 0xbb, 0x9c, 0xff,
+ 0xff, 0xbc, 0x9c, 0xff, 0xff, 0xbb, 0x9c, 0xff,
+ 0xff, 0xc2, 0xa5, 0xff, 0xff, 0xc2, 0xa4, 0xff,
+ 0xff, 0xc2, 0xa5, 0xff, 0xff, 0xc2, 0xa4, 0xff,
+ 0xff, 0xb6, 0x9c, 0xff, 0x7b, 0x55, 0x44, 0xff,
+ 0x7b, 0x55, 0x45, 0xff, 0x7b, 0x55, 0x44, 0xff,
+ 0xd9, 0x96, 0x7c, 0xff, 0xec, 0xa2, 0x84, 0xff,
+ 0xec, 0xa2, 0x84, 0xff, 0xec, 0xa2, 0x83, 0xff,
+ 0xf7, 0xa2, 0x81, 0xff, 0xf7, 0x9e, 0x7b, 0xff,
+ 0xf7, 0xa2, 0x81, 0xff, 0xf7, 0xa2, 0x81, 0xff,
+ 0xf7, 0xa2, 0x84, 0xff, 0xf7, 0xa2, 0x84, 0xff,
+ 0xf7, 0xa2, 0x84, 0xff, 0xf7, 0xa2, 0x83, 0xff,
+ 0xf2, 0xa1, 0x7f, 0xff, 0xf1, 0xa1, 0x7e, 0xff,
+ 0xf4, 0xa4, 0x81, 0xff, 0xf1, 0xa0, 0x7e, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xef, 0xa2, 0x84, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa2, 0x83, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xef, 0xa2, 0x84, 0xff,
+ 0xf2, 0xa6, 0x87, 0xff, 0xf1, 0xa6, 0x86, 0xff,
+ 0xef, 0xa6, 0x8c, 0xff, 0xef, 0xa6, 0x8c, 0xff,
+ 0xef, 0xa6, 0x8c, 0xff, 0xee, 0xa6, 0x8c, 0xff,
+ 0xef, 0xaa, 0x8c, 0xff, 0xef, 0xaa, 0x8c, 0xff,
+ 0xef, 0xaa, 0x8c, 0xff, 0xf9, 0xb2, 0x91, 0xff,
+ 0xea, 0xad, 0x92, 0xff, 0xff, 0xba, 0x9c, 0xff,
+ 0xe9, 0xad, 0x92, 0xff, 0xff, 0xba, 0x9c, 0xff,
+ 0xff, 0xb7, 0x9d, 0xff, 0xff, 0xb6, 0x9c, 0xff,
+ 0xff, 0xb6, 0x9d, 0xff, 0xff, 0xb6, 0x9c, 0xff,
+ 0xff, 0xbb, 0x9d, 0xff, 0xff, 0xba, 0x9c, 0xff,
+ 0xff, 0xbb, 0x9d, 0xff, 0xff, 0xba, 0x9c, 0xff,
+ 0xff, 0xbb, 0x9d, 0xff, 0xff, 0xba, 0x9c, 0xff,
+ 0xff, 0xbd, 0x9f, 0xff, 0xff, 0xbd, 0x9f, 0xff,
+ 0xff, 0xbf, 0x9d, 0xff, 0xff, 0xbe, 0x9c, 0xff,
+ 0xff, 0xc1, 0xa2, 0xff, 0xff, 0xbe, 0x9c, 0xff,
+ 0xff, 0xbf, 0xa5, 0xff, 0xff, 0xbe, 0xa4, 0xff,
+ 0xff, 0xbf, 0xa5, 0xff, 0xff, 0xbe, 0xa4, 0xff,
+ 0xff, 0xc7, 0xa5, 0xff, 0xff, 0xc6, 0xa4, 0xff,
+ 0xff, 0xc7, 0xa5, 0xff, 0xff, 0xc6, 0xa4, 0xff,
+ 0xbb, 0x98, 0x84, 0xff, 0x76, 0x58, 0x4a, 0xff,
+ 0x32, 0x19, 0x11, 0xff, 0x31, 0x18, 0x10, 0xff,
+ 0xc6, 0x8a, 0x73, 0xff, 0xd8, 0x95, 0x7b, 0xff,
+ 0xec, 0xa2, 0x84, 0xff, 0xec, 0xa2, 0x83, 0xff,
+ 0xf7, 0xa2, 0x81, 0xff, 0xf6, 0xa6, 0x86, 0xff,
+ 0xf7, 0xa2, 0x81, 0xff, 0xf6, 0xa2, 0x81, 0xff,
+ 0xf7, 0xa2, 0x84, 0xff, 0xf6, 0xa1, 0x83, 0xff,
+ 0xf7, 0xa2, 0x84, 0xff, 0xf6, 0xa2, 0x83, 0xff,
+ 0xf4, 0xa3, 0x81, 0xff, 0xf4, 0xa3, 0x80, 0xff,
+ 0xf2, 0xa1, 0x7e, 0xff, 0xf6, 0xa6, 0x83, 0xff,
+ 0xef, 0xa2, 0x84, 0xff, 0xee, 0xa1, 0x83, 0xff,
+ 0xf2, 0xa5, 0x87, 0xff, 0xf1, 0xa4, 0x86, 0xff,
+ 0xf1, 0xa6, 0x86, 0xff, 0xf1, 0xa6, 0x86, 0xff,
+ 0xf2, 0xa6, 0x87, 0xff, 0xf4, 0xaa, 0x89, 0xff,
+ 0xf1, 0xaa, 0x8c, 0xff, 0xee, 0xa6, 0x8b, 0xff,
+ 0xef, 0xa6, 0x8c, 0xff, 0xf1, 0xaa, 0x8c, 0xff,
+ 0xef, 0xaa, 0x8c, 0xff, 0xf4, 0xae, 0x8e, 0xff,
+ 0xf4, 0xae, 0x8f, 0xff, 0xf4, 0xae, 0x8e, 0xff,
+ 0xe9, 0xad, 0x91, 0xff, 0xff, 0xba, 0x9c, 0xff,
+ 0xff, 0xba, 0x9d, 0xff, 0xff, 0xba, 0x9c, 0xff,
+ 0xff, 0xb6, 0x9c, 0xff, 0xff, 0xb6, 0x9c, 0xff,
+ 0xff, 0xb6, 0x9d, 0xff, 0xff, 0xb6, 0x9c, 0xff,
+ 0xe1, 0xa9, 0x8f, 0xff, 0xe0, 0xa8, 0x8e, 0xff,
+ 0xff, 0xba, 0x9d, 0xff, 0xff, 0xba, 0x9c, 0xff,
+ 0xff, 0xbd, 0x9f, 0xff, 0xff, 0xbc, 0x9f, 0xff,
+ 0xff, 0xc0, 0xa2, 0xff, 0xff, 0xbf, 0xa1, 0xff,
+ 0xff, 0xc1, 0xa2, 0xff, 0xff, 0xc1, 0xa1, 0xff,
+ 0xff, 0xbe, 0x9d, 0xff, 0xff, 0xbe, 0x9c, 0xff,
+ 0xff, 0xbe, 0xa5, 0xff, 0xff, 0xc2, 0xa7, 0xff,
+ 0xff, 0xc3, 0xa7, 0xff, 0xff, 0xc2, 0xa7, 0xff,
+ 0xff, 0xc6, 0xa5, 0xff, 0xee, 0xb7, 0x96, 0xff,
+ 0xff, 0xc7, 0xa5, 0xff, 0xff, 0xc6, 0xa4, 0xff,
+ 0xbb, 0x97, 0x84, 0xff, 0x75, 0x57, 0x4a, 0xff,
+ 0x32, 0x19, 0x11, 0xff, 0x31, 0x18, 0x10, 0xff,
+ 0xc6, 0x8a, 0x73, 0xff, 0xd8, 0x96, 0x7b, 0xff,
+ 0xec, 0xa2, 0x84, 0xff, 0xec, 0xa2, 0x84, 0xff,
+ 0xf7, 0xa6, 0x87, 0xff, 0xf7, 0xa6, 0x86, 0xff,
+ 0xf7, 0xa6, 0x87, 0xff, 0xf7, 0xa6, 0x86, 0xff,
+ 0xfa, 0xa5, 0x84, 0xff, 0xf9, 0xa4, 0x83, 0xff,
+ 0xf7, 0xa2, 0x84, 0xff, 0xf7, 0xa2, 0x84, 0xff,
+ 0xf4, 0xa4, 0x81, 0xff, 0xf7, 0xa6, 0x83, 0xff,
+ 0xf4, 0xa4, 0x81, 0xff, 0xf4, 0xa3, 0x81, 0xff,
+ 0xf2, 0xa5, 0x87, 0xff, 0xf4, 0xa7, 0x89, 0xff,
+ 0xf2, 0xa5, 0x87, 0xff, 0xf7, 0xaa, 0x8c, 0xff,
+ 0xf4, 0xaa, 0x89, 0xff, 0xf1, 0xa6, 0x86, 0xff,
+ 0xf7, 0xae, 0x8c, 0xff, 0xf7, 0xae, 0x8c, 0xff,
+ 0xf2, 0xaa, 0x8c, 0xff, 0xf4, 0xae, 0x8c, 0xff,
+ 0xf2, 0xaa, 0x8c, 0xff, 0xf4, 0xae, 0x8c, 0xff,
+ 0xf4, 0xae, 0x8f, 0xff, 0xf4, 0xae, 0x8e, 0xff,
+ 0xfa, 0xb3, 0x92, 0xff, 0xf9, 0xb2, 0x91, 0xff,
+ 0xff, 0xba, 0x9d, 0xff, 0xff, 0xba, 0x9c, 0xff,
+ 0xff, 0xbb, 0x9d, 0xff, 0xe9, 0xad, 0x91, 0xff,
+ 0xde, 0xa5, 0x8c, 0xff, 0xff, 0xb6, 0x9c, 0xff,
+ 0xff, 0xb7, 0x9d, 0xff, 0xff, 0xb6, 0x9c, 0xff,
+ 0xc3, 0x97, 0x81, 0xff, 0xc2, 0x97, 0x81, 0xff,
+ 0xff, 0xbb, 0x9d, 0xff, 0xff, 0xba, 0x9c, 0xff,
+ 0xff, 0xbd, 0x9f, 0xff, 0xff, 0xbd, 0x9f, 0xff,
+ 0xff, 0xc0, 0xa2, 0xff, 0xff, 0xbf, 0xa2, 0xff,
+ 0xff, 0xc1, 0xa2, 0xff, 0xff, 0xc1, 0xa2, 0xff,
+ 0xff, 0xc1, 0xa2, 0xff, 0xff, 0xc4, 0xa7, 0xff,
+ 0xff, 0xc7, 0xaa, 0xff, 0xff, 0xc2, 0xa7, 0xff,
+ 0xff, 0xc7, 0xaa, 0xff, 0xff, 0xc6, 0xaa, 0xff,
+ 0xff, 0xc7, 0xa5, 0xff, 0xff, 0xc6, 0xa4, 0xff,
+ 0xff, 0xc7, 0xa5, 0xff, 0xff, 0xc6, 0xa4, 0xff,
+ 0xff, 0xd7, 0xbd, 0xff, 0xba, 0x97, 0x83, 0xff,
+ 0x76, 0x58, 0x4a, 0xff, 0x31, 0x18, 0x10, 0xff,
+ 0xd9, 0x96, 0x7c, 0xff, 0xd8, 0x95, 0x7b, 0xff,
+ 0xff, 0xae, 0x8c, 0xff, 0xff, 0xae, 0x8b, 0xff,
+ 0xf7, 0xaa, 0x8c, 0xff, 0xf6, 0xa6, 0x86, 0xff,
+ 0xf7, 0xa6, 0x86, 0xff, 0xf6, 0xaa, 0x8b, 0xff,
+ 0xff, 0xaa, 0x84, 0xff, 0xfc, 0xa7, 0x83, 0xff,
+ 0xfa, 0xa5, 0x84, 0xff, 0xf9, 0xa4, 0x83, 0xff,
+ 0xf4, 0xa3, 0x81, 0xff, 0xf6, 0xa6, 0x83, 0xff,
+ 0xf4, 0xa3, 0x81, 0xff, 0xf6, 0xa5, 0x83, 0xff,
+ 0xf7, 0xaa, 0x8c, 0xff, 0xf4, 0xa7, 0x89, 0xff,
+ 0xf7, 0xaa, 0x8c, 0xff, 0xf6, 0xaa, 0x8b, 0xff,
+ 0xf4, 0xaa, 0x89, 0xff, 0xf6, 0xae, 0x8b, 0xff,
+ 0xf7, 0xae, 0x8c, 0xff, 0xf6, 0xae, 0x8b, 0xff,
+ 0xf4, 0xae, 0x8c, 0xff, 0xf6, 0xb2, 0x8b, 0xff,
+ 0xf7, 0xb2, 0x8c, 0xff, 0xf6, 0xb2, 0x8b, 0xff,
+ 0xfa, 0xb2, 0x91, 0xff, 0xff, 0xb6, 0x94, 0xff,
+ 0xfa, 0xb2, 0x91, 0xff, 0xff, 0xb6, 0x94, 0xff,
+ 0xff, 0xba, 0x9c, 0xff, 0xe9, 0xac, 0x91, 0xff,
+ 0xe9, 0xad, 0x91, 0xff, 0xbd, 0x91, 0x7b, 0xff,
+ 0xbd, 0x93, 0x7c, 0xff, 0xff, 0xb6, 0x9c, 0xff,
+ 0xbd, 0x93, 0x7b, 0xff, 0x9c, 0x81, 0x6a, 0xff,
+ 0xa5, 0x86, 0x73, 0xff, 0xc2, 0x97, 0x81, 0xff,
+ 0xff, 0xba, 0x9c, 0xff, 0xff, 0xba, 0x9c, 0xff,
+ 0xff, 0xc2, 0xa5, 0xff, 0xff, 0xbf, 0xa1, 0xff,
+ 0xff, 0xc0, 0xa2, 0xff, 0xff, 0xc2, 0xa4, 0xff,
+ 0xff, 0xc4, 0xa7, 0xff, 0xff, 0xc3, 0xa7, 0xff,
+ 0xff, 0xc4, 0xa7, 0xff, 0xff, 0xc0, 0xa1, 0xff,
+ 0xff, 0xc2, 0xa7, 0xff, 0xff, 0xc6, 0xaa, 0xff,
+ 0xff, 0xca, 0xad, 0xff, 0xff, 0xca, 0xac, 0xff,
+ 0xff, 0xc6, 0xa5, 0xff, 0xff, 0xc6, 0xa4, 0xff,
+ 0xff, 0xc6, 0xa5, 0xff, 0xcd, 0x99, 0x7b, 0xff,
+ 0xbb, 0x97, 0x84, 0xff, 0x76, 0x57, 0x4a, 0xff,
+ 0x76, 0x58, 0x4a, 0xff, 0x31, 0x18, 0x10, 0xff,
+ 0xce, 0x8e, 0x74, 0xff, 0xde, 0x98, 0x7b, 0xff,
+ 0xef, 0xa4, 0x84, 0xff, 0xff, 0xae, 0x8c, 0xff,
+ 0xff, 0xaa, 0x84, 0xff, 0xff, 0xad, 0x86, 0xff,
+ 0xff, 0xaa, 0x84, 0xff, 0xff, 0xad, 0x86, 0xff,
+ 0xfa, 0xac, 0x8a, 0xff, 0xf9, 0xab, 0x89, 0xff,
+ 0xf7, 0xa6, 0x84, 0xff, 0xf7, 0xa6, 0x83, 0xff,
+ 0xff, 0xaa, 0x84, 0xff, 0xff, 0xaa, 0x84, 0xff,
+ 0xff, 0xaa, 0x84, 0xff, 0xff, 0xaa, 0x83, 0xff,
+ 0xf7, 0xaf, 0x8c, 0xff, 0xf7, 0xae, 0x8c, 0xff,
+ 0xf7, 0xae, 0x8c, 0xff, 0xf7, 0xae, 0x8c, 0xff,
+ 0xf7, 0xaf, 0x8c, 0xff, 0xf7, 0xae, 0x8c, 0xff,
+ 0xfa, 0xb2, 0x8f, 0xff, 0xf9, 0xb2, 0x8e, 0xff,
+ 0xff, 0xb3, 0x95, 0xff, 0xff, 0xb2, 0x94, 0xff,
+ 0xff, 0xb2, 0x94, 0xff, 0xff, 0xb2, 0x94, 0xff,
+ 0xff, 0xb7, 0x95, 0xff, 0xff, 0xb6, 0x94, 0xff,
+ 0xff, 0xbb, 0x9a, 0xff, 0xff, 0xba, 0x99, 0xff,
+ 0xe7, 0xaf, 0x95, 0xff, 0xad, 0x8c, 0x79, 0xff,
+ 0xad, 0x8d, 0x79, 0xff, 0xad, 0x8c, 0x78, 0xff,
+ 0x81, 0x73, 0x63, 0xff, 0xa4, 0x8a, 0x73, 0xff,
+ 0x81, 0x73, 0x63, 0xff, 0x5d, 0x5c, 0x52, 0xff,
+ 0x8f, 0x79, 0x66, 0xff, 0xb5, 0x8e, 0x73, 0xff,
+ 0xb5, 0x8e, 0x74, 0xff, 0xb5, 0x8e, 0x73, 0xff,
+ 0xf7, 0xbf, 0x9d, 0xff, 0xf7, 0xbe, 0x9c, 0xff,
+ 0xf7, 0xbf, 0x9d, 0xff, 0xf7, 0xbe, 0x9c, 0xff,
+ 0xf7, 0xbb, 0x9d, 0xff, 0xf7, 0xba, 0x9c, 0xff,
+ 0xf7, 0xbb, 0x9d, 0xff, 0xf7, 0xba, 0x9c, 0xff,
+ 0xff, 0xcb, 0xad, 0xff, 0xff, 0xce, 0xaf, 0xff,
+ 0xff, 0xcf, 0xb0, 0xff, 0xff, 0xca, 0xad, 0xff,
+ 0xff, 0xd3, 0xb5, 0xff, 0xff, 0xd2, 0xb5, 0xff,
+ 0xff, 0xd3, 0xb5, 0xff, 0x83, 0x59, 0x52, 0xff,
+ 0x21, 0x17, 0x19, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x11, 0x0c, 0x11, 0xff, 0x21, 0x17, 0x19, 0xff,
+ 0xef, 0xa3, 0x84, 0xff, 0xde, 0x98, 0x7b, 0xff,
+ 0xef, 0xa3, 0x84, 0xff, 0xff, 0xae, 0x8c, 0xff,
+ 0xff, 0xaf, 0x89, 0xff, 0xff, 0xac, 0x86, 0xff,
+ 0xff, 0xb0, 0x89, 0xff, 0xff, 0xac, 0x86, 0xff,
+ 0xfa, 0xab, 0x89, 0xff, 0xfc, 0xb0, 0x8e, 0xff,
+ 0xfa, 0xac, 0x89, 0xff, 0xfc, 0xb0, 0x8e, 0xff,
+ 0xff, 0xae, 0x89, 0xff, 0xff, 0xae, 0x89, 0xff,
+ 0xff, 0xb2, 0x8f, 0xff, 0xff, 0xae, 0x89, 0xff,
+ 0xfa, 0xb1, 0x8f, 0xff, 0xf9, 0xb0, 0x8e, 0xff,
+ 0xfa, 0xb1, 0x8f, 0xff, 0xf9, 0xb0, 0x8e, 0xff,
+ 0xfa, 0xb2, 0x8f, 0xff, 0xf9, 0xb2, 0x8e, 0xff,
+ 0xfa, 0xb2, 0x8f, 0xff, 0xf9, 0xb2, 0x8e, 0xff,
+ 0xff, 0xb6, 0x97, 0xff, 0xff, 0xb6, 0x96, 0xff,
+ 0xff, 0xb6, 0x97, 0xff, 0xff, 0xba, 0x99, 0xff,
+ 0xff, 0xba, 0x9a, 0xff, 0xff, 0xba, 0x99, 0xff,
+ 0xff, 0xba, 0x9a, 0xff, 0xff, 0xba, 0x99, 0xff,
+ 0xe6, 0xae, 0x94, 0xff, 0xac, 0x8c, 0x78, 0xff,
+ 0x73, 0x6b, 0x5d, 0xff, 0x73, 0x6a, 0x5d, 0xff,
+ 0x81, 0x73, 0x63, 0xff, 0x5d, 0x5b, 0x52, 0xff,
+ 0x5d, 0x5c, 0x52, 0xff, 0x5d, 0x5b, 0x52, 0xff,
+ 0x8f, 0x78, 0x66, 0xff, 0x8e, 0x78, 0x65, 0xff,
+ 0x68, 0x63, 0x58, 0xff, 0x68, 0x62, 0x57, 0xff,
+ 0xbb, 0x9a, 0x81, 0xff, 0xba, 0x99, 0x80, 0xff,
+ 0xbb, 0x9a, 0x81, 0xff, 0xba, 0x9a, 0x81, 0xff,
+ 0xcb, 0x9f, 0x86, 0xff, 0xca, 0x9f, 0x86, 0xff,
+ 0xcb, 0x9f, 0x87, 0xff, 0xf6, 0xba, 0x9c, 0xff,
+ 0xff, 0xcf, 0xb0, 0xff, 0xff, 0xca, 0xac, 0xff,
+ 0xff, 0xcb, 0xad, 0xff, 0xff, 0xce, 0xaf, 0xff,
+ 0xff, 0xd3, 0xb5, 0xff, 0xff, 0xd2, 0xb5, 0xff,
+ 0xd6, 0xaa, 0x94, 0xff, 0x83, 0x59, 0x52, 0xff,
+ 0x21, 0x17, 0x19, 0xff, 0x20, 0x17, 0x18, 0xff,
+ 0x21, 0x17, 0x19, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0xde, 0x99, 0x7c, 0xff, 0xee, 0xa3, 0x83, 0xff,
+ 0xef, 0xa4, 0x84, 0xff, 0xff, 0xae, 0x8c, 0xff,
+ 0xff, 0xb2, 0x8c, 0xff, 0xff, 0xaf, 0x89, 0xff,
+ 0xff, 0xb3, 0x8c, 0xff, 0xff, 0xb2, 0x8c, 0xff,
+ 0xfd, 0xb1, 0x8f, 0xff, 0xfc, 0xb1, 0x8e, 0xff,
+ 0xfd, 0xb1, 0x8f, 0xff, 0xfc, 0xb1, 0x8e, 0xff,
+ 0xff, 0xb2, 0x8f, 0xff, 0xff, 0xb2, 0x8e, 0xff,
+ 0xff, 0xb3, 0x8f, 0xff, 0xff, 0xb6, 0x94, 0xff,
+ 0xfd, 0xb4, 0x92, 0xff, 0xfc, 0xb3, 0x91, 0xff,
+ 0xfd, 0xb4, 0x92, 0xff, 0xfc, 0xb3, 0x91, 0xff,
+ 0xfd, 0xb6, 0x92, 0xff, 0xfc, 0xb6, 0x91, 0xff,
+ 0xfd, 0xb7, 0x92, 0xff, 0xfc, 0xb6, 0x91, 0xff,
+ 0xff, 0xba, 0x9a, 0xff, 0xff, 0xba, 0x99, 0xff,
+ 0xff, 0xbb, 0x9a, 0xff, 0xff, 0xbe, 0x9c, 0xff,
+ 0xff, 0xbf, 0x9f, 0xff, 0xff, 0xbe, 0x9f, 0xff,
+ 0xff, 0xbf, 0x9f, 0xff, 0xff, 0xba, 0x99, 0xff,
+ 0xe7, 0xae, 0x94, 0xff, 0x73, 0x6a, 0x5d, 0xff,
+ 0x3a, 0x49, 0x42, 0xff, 0x39, 0x49, 0x42, 0xff,
+ 0x5e, 0x5c, 0x53, 0xff, 0x5d, 0x5c, 0x52, 0xff,
+ 0x5e, 0x5c, 0x53, 0xff, 0x39, 0x45, 0x42, 0xff,
+ 0x68, 0x63, 0x58, 0xff, 0x68, 0x62, 0x58, 0xff,
+ 0x42, 0x4d, 0x4a, 0xff, 0x42, 0x4d, 0x4a, 0xff,
+ 0x42, 0x51, 0x4a, 0xff, 0x42, 0x51, 0x4a, 0xff,
+ 0x7f, 0x76, 0x66, 0xff, 0x42, 0x51, 0x4a, 0xff,
+ 0x9f, 0x85, 0x71, 0xff, 0x9f, 0x84, 0x70, 0xff,
+ 0x9f, 0x85, 0x71, 0xff, 0xf7, 0xba, 0x9c, 0xff,
+ 0xff, 0xd3, 0xb3, 0xff, 0xff, 0xce, 0xaf, 0xff,
+ 0xff, 0xd3, 0xb3, 0xff, 0xff, 0xd2, 0xb2, 0xff,
+ 0xff, 0xd3, 0xb5, 0xff, 0xff, 0xd2, 0xb5, 0xff,
+ 0xff, 0xd3, 0xb5, 0xff, 0xad, 0x81, 0x73, 0xff,
+ 0x42, 0x2d, 0x29, 0xff, 0x31, 0x22, 0x21, 0xff,
+ 0x11, 0x0d, 0x11, 0xff, 0x21, 0x17, 0x19, 0xff,
+ 0xef, 0xa3, 0x84, 0xff, 0xee, 0xa3, 0x83, 0xff,
+ 0xde, 0x98, 0x7b, 0xff, 0xee, 0xa3, 0x83, 0xff,
+ 0xff, 0xb2, 0x8c, 0xff, 0xff, 0xb2, 0x8b, 0xff,
+ 0xff, 0xb2, 0x8c, 0xff, 0xff, 0xb2, 0x8b, 0xff,
+ 0xff, 0xb6, 0x94, 0xff, 0xfc, 0xb0, 0x8e, 0xff,
+ 0xff, 0xb6, 0x94, 0xff, 0xff, 0xb6, 0x94, 0xff,
+ 0xff, 0xb6, 0x94, 0xff, 0xff, 0xb2, 0x8e, 0xff,
+ 0xff, 0xb6, 0x94, 0xff, 0xff, 0xb6, 0x94, 0xff,
+ 0xff, 0xb6, 0x94, 0xff, 0xff, 0xb6, 0x94, 0xff,
+ 0xff, 0xb6, 0x94, 0xff, 0xff, 0xb6, 0x94, 0xff,
+ 0xfc, 0xb6, 0x91, 0xff, 0xfc, 0xb6, 0x91, 0xff,
+ 0xfc, 0xb6, 0x91, 0xff, 0xff, 0xba, 0x94, 0xff,
+ 0xff, 0xba, 0x9a, 0xff, 0xff, 0xbe, 0x9c, 0xff,
+ 0xff, 0xba, 0x9a, 0xff, 0xff, 0xbe, 0x9c, 0xff,
+ 0xff, 0xc2, 0xa5, 0xff, 0xff, 0xc2, 0xa4, 0xff,
+ 0xff, 0xbe, 0x9f, 0xff, 0xff, 0xba, 0x99, 0xff,
+ 0xad, 0x8c, 0x79, 0xff, 0x73, 0x6a, 0x5d, 0xff,
+ 0x3a, 0x49, 0x42, 0xff, 0x39, 0x48, 0x41, 0xff,
+ 0x3a, 0x45, 0x42, 0xff, 0x39, 0x44, 0x41, 0xff,
+ 0x3a, 0x45, 0x42, 0xff, 0x39, 0x44, 0x41, 0xff,
+ 0x42, 0x4d, 0x4a, 0xff, 0x41, 0x4d, 0x4a, 0xff,
+ 0x42, 0x4d, 0x4a, 0xff, 0x41, 0x4c, 0x4a, 0xff,
+ 0x42, 0x51, 0x4a, 0xff, 0x41, 0x51, 0x4a, 0xff,
+ 0x42, 0x51, 0x4a, 0xff, 0x41, 0x50, 0x4a, 0xff,
+ 0x73, 0x69, 0x5b, 0xff, 0x73, 0x69, 0x5a, 0xff,
+ 0x9f, 0x84, 0x70, 0xff, 0xf6, 0xba, 0x9c, 0xff,
+ 0xff, 0xd7, 0xb5, 0xff, 0xff, 0xd2, 0xb2, 0xff,
+ 0xff, 0xd3, 0xb2, 0xff, 0xff, 0xd2, 0xb2, 0xff,
+ 0xff, 0xd3, 0xb5, 0xff, 0xff, 0xd2, 0xb5, 0xff,
+ 0xff, 0xd3, 0xb5, 0xff, 0xd5, 0xaa, 0x94, 0xff,
+ 0x42, 0x2d, 0x29, 0xff, 0x21, 0x17, 0x18, 0xff,
+ 0x10, 0x0c, 0x10, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0xdf, 0xa4, 0x8a, 0xff, 0xde, 0xa3, 0x89, 0xff,
+ 0xc6, 0x8d, 0x76, 0xff, 0xde, 0xa3, 0x89, 0xff,
+ 0xef, 0xad, 0x8f, 0xff, 0xef, 0xad, 0x8f, 0xff,
+ 0xf7, 0xbc, 0x9a, 0xff, 0xf7, 0xbb, 0x99, 0xff,
+ 0xef, 0xb3, 0x8f, 0xff, 0xff, 0xc2, 0x9c, 0xff,
+ 0xef, 0xb2, 0x8f, 0xff, 0xee, 0xb2, 0x8e, 0xff,
+ 0xff, 0xb7, 0x95, 0xff, 0xff, 0xb6, 0x94, 0xff,
+ 0xff, 0xb6, 0x94, 0xff, 0xff, 0xb6, 0x94, 0xff,
+ 0xff, 0xb7, 0x95, 0xff, 0xff, 0xb6, 0x94, 0xff,
+ 0xff, 0xbc, 0x9a, 0xff, 0xff, 0xb6, 0x94, 0xff,
+ 0xff, 0xbb, 0x95, 0xff, 0xff, 0xba, 0x94, 0xff,
+ 0xff, 0xc1, 0x9d, 0xff, 0xff, 0xba, 0x94, 0xff,
+ 0xff, 0xbf, 0x9d, 0xff, 0xff, 0xc2, 0xa2, 0xff,
+ 0xff, 0xbf, 0x9d, 0xff, 0xff, 0xc6, 0xa7, 0xff,
+ 0xf7, 0xbf, 0x9d, 0xff, 0xf7, 0xbe, 0x9c, 0xff,
+ 0xf7, 0xbf, 0x9d, 0xff, 0xbd, 0x9e, 0x83, 0xff,
+ 0x5b, 0x6e, 0x63, 0xff, 0x4d, 0x5e, 0x58, 0xff,
+ 0x3f, 0x50, 0x4d, 0xff, 0x3f, 0x4f, 0x4d, 0xff,
+ 0x3d, 0x4b, 0x48, 0xff, 0x3c, 0x4a, 0x47, 0xff,
+ 0x32, 0x35, 0x32, 0xff, 0x31, 0x34, 0x31, 0xff,
+ 0x37, 0x40, 0x40, 0xff, 0x3c, 0x46, 0x45, 0xff,
+ 0x42, 0x4d, 0x4a, 0xff, 0x42, 0x4d, 0x4a, 0xff,
+ 0x48, 0x54, 0x50, 0xff, 0x3a, 0x4d, 0x4a, 0xff,
+ 0x63, 0x61, 0x5b, 0xff, 0x39, 0x4d, 0x4a, 0xff,
+ 0x4b, 0x51, 0x4b, 0xff, 0x4a, 0x51, 0x4a, 0xff,
+ 0x7e, 0x72, 0x60, 0xff, 0xe6, 0xb2, 0x8c, 0xff,
+ 0xff, 0xd3, 0xad, 0xff, 0xff, 0xd2, 0xad, 0xff,
+ 0xff, 0xd3, 0xad, 0xff, 0xff, 0xd2, 0xad, 0xff,
+ 0xff, 0xcf, 0xb5, 0xff, 0xff, 0xce, 0xb5, 0xff,
+ 0xc0, 0xa4, 0x8f, 0xff, 0x42, 0x4d, 0x42, 0xff,
+ 0x11, 0x0d, 0x09, 0xff, 0x19, 0x1b, 0x16, 0xff,
+ 0x11, 0x0c, 0x09, 0xff, 0x19, 0x1b, 0x16, 0xff,
+ 0xc6, 0x8c, 0x76, 0xff, 0xac, 0x75, 0x62, 0xff,
+ 0xc6, 0x8d, 0x76, 0xff, 0xc5, 0x8c, 0x76, 0xff,
+ 0xe6, 0x9e, 0x84, 0xff, 0xee, 0xac, 0x8e, 0xff,
+ 0xf7, 0xbc, 0x9a, 0xff, 0xf6, 0xbb, 0x99, 0xff,
+ 0xff, 0xc2, 0x9c, 0xff, 0xff, 0xc2, 0x9c, 0xff,
+ 0xff, 0xc3, 0x9d, 0xff, 0xff, 0xc2, 0x9c, 0xff,
+ 0xff, 0xbd, 0x97, 0xff, 0xff, 0xbc, 0x96, 0xff,
+ 0xff, 0xbd, 0x97, 0xff, 0xff, 0xbd, 0x97, 0xff,
+ 0xff, 0xbc, 0x9a, 0xff, 0xff, 0xbb, 0x99, 0xff,
+ 0xff, 0xbc, 0x9a, 0xff, 0xff, 0xbb, 0x99, 0xff,
+ 0xff, 0xc1, 0x9c, 0xff, 0xff, 0xc1, 0x9c, 0xff,
+ 0xff, 0xc1, 0x9d, 0xff, 0xff, 0xc1, 0x9c, 0xff,
+ 0xff, 0xc2, 0xa2, 0xff, 0xff, 0xc6, 0xa7, 0xff,
+ 0xff, 0xc3, 0xa2, 0xff, 0xff, 0xbe, 0x9c, 0xff,
+ 0xf7, 0xbe, 0x9c, 0xff, 0xf6, 0xbe, 0x9c, 0xff,
+ 0xf7, 0xbe, 0x9d, 0xff, 0x83, 0x7d, 0x6b, 0xff,
+ 0x4d, 0x5f, 0x58, 0xff, 0x4c, 0x5e, 0x57, 0xff,
+ 0x3f, 0x50, 0x4d, 0xff, 0x31, 0x40, 0x42, 0xff,
+ 0x42, 0x55, 0x52, 0xff, 0x3c, 0x4a, 0x47, 0xff,
+ 0x37, 0x40, 0x3d, 0xff, 0x31, 0x34, 0x31, 0xff,
+ 0x3c, 0x46, 0x45, 0xff, 0x3c, 0x46, 0x44, 0xff,
+ 0x3d, 0x46, 0x45, 0xff, 0x3c, 0x46, 0x44, 0xff,
+ 0x47, 0x54, 0x50, 0xff, 0x39, 0x4c, 0x4a, 0xff,
+ 0x48, 0x54, 0x50, 0xff, 0x47, 0x53, 0x4f, 0xff,
+ 0x4a, 0x51, 0x4a, 0xff, 0x4a, 0x51, 0x4a, 0xff,
+ 0x7e, 0x72, 0x60, 0xff, 0xb2, 0x91, 0x76, 0xff,
+ 0xe4, 0xc1, 0xa2, 0xff, 0xff, 0xd2, 0xac, 0xff,
+ 0xff, 0xd3, 0xad, 0xff, 0xff, 0xd2, 0xac, 0xff,
+ 0xff, 0xcf, 0xb5, 0xff, 0xc0, 0xa3, 0x8e, 0xff,
+ 0x42, 0x4d, 0x42, 0xff, 0x42, 0x4d, 0x42, 0xff,
+ 0x19, 0x1b, 0x16, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0x11, 0x0c, 0x08, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0xad, 0x76, 0x63, 0xff, 0xad, 0x75, 0x62, 0xff,
+ 0xad, 0x76, 0x63, 0xff, 0xc5, 0x8c, 0x76, 0xff,
+ 0xe7, 0x9e, 0x84, 0xff, 0xf7, 0xbb, 0x99, 0xff,
+ 0xf7, 0xbc, 0x9a, 0xff, 0xf7, 0xbb, 0x99, 0xff,
+ 0xff, 0xc3, 0x9d, 0xff, 0xff, 0xc2, 0x9c, 0xff,
+ 0xff, 0xc3, 0x9d, 0xff, 0xff, 0xc2, 0x9c, 0xff,
+ 0xff, 0xc4, 0x9a, 0xff, 0xff, 0xbd, 0x97, 0xff,
+ 0xff, 0xbd, 0x97, 0xff, 0xff, 0xbd, 0x97, 0xff,
+ 0xff, 0xbc, 0x9a, 0xff, 0xff, 0xbb, 0x99, 0xff,
+ 0xff, 0xc1, 0x9f, 0xff, 0xff, 0xc1, 0x9f, 0xff,
+ 0xff, 0xc1, 0x9d, 0xff, 0xff, 0xc7, 0xa4, 0xff,
+ 0xff, 0xc8, 0xa5, 0xff, 0xff, 0xc8, 0xa4, 0xff,
+ 0xff, 0xc7, 0xa8, 0xff, 0xff, 0xc2, 0xa2, 0xff,
+ 0xff, 0xbf, 0x9d, 0xff, 0xff, 0xc6, 0xa7, 0xff,
+ 0xf7, 0xbf, 0x9d, 0xff, 0xf7, 0xbe, 0x9c, 0xff,
+ 0x84, 0x7e, 0x6b, 0xff, 0x4a, 0x5d, 0x52, 0xff,
+ 0x3f, 0x50, 0x4d, 0xff, 0x3f, 0x4f, 0x4d, 0xff,
+ 0x32, 0x41, 0x42, 0xff, 0x31, 0x41, 0x42, 0xff,
+ 0x42, 0x55, 0x53, 0xff, 0x3c, 0x4a, 0x47, 0xff,
+ 0x42, 0x55, 0x53, 0xff, 0x3c, 0x4a, 0x47, 0xff,
+ 0x37, 0x40, 0x3f, 0xff, 0x37, 0x3f, 0x3f, 0xff,
+ 0x42, 0x4d, 0x4a, 0xff, 0x42, 0x4d, 0x4a, 0xff,
+ 0x3a, 0x4d, 0x4a, 0xff, 0x39, 0x4d, 0x4a, 0xff,
+ 0x63, 0x62, 0x5b, 0xff, 0x55, 0x5a, 0x55, 0xff,
+ 0x4a, 0x51, 0x4a, 0xff, 0x7e, 0x71, 0x60, 0xff,
+ 0x4a, 0x51, 0x4a, 0xff, 0x7e, 0x71, 0x60, 0xff,
+ 0xe4, 0xc1, 0xa2, 0xff, 0xff, 0xd2, 0xad, 0xff,
+ 0xff, 0xd3, 0xad, 0xff, 0xff, 0xd2, 0xad, 0xff,
+ 0xff, 0xcf, 0xb5, 0xff, 0xc0, 0xa3, 0x8e, 0xff,
+ 0x42, 0x4d, 0x42, 0xff, 0x42, 0x4d, 0x42, 0xff,
+ 0x29, 0x39, 0x32, 0xff, 0x18, 0x1b, 0x16, 0xff,
+ 0x11, 0x0d, 0x09, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0xf7, 0xba, 0x9c, 0xff, 0xf6, 0xba, 0x9c, 0xff,
+ 0xf7, 0xba, 0x9c, 0xff, 0xf6, 0xba, 0x9c, 0xff,
+ 0xf7, 0xbc, 0x9a, 0xff, 0xff, 0xca, 0xa4, 0xff,
+ 0xff, 0xca, 0xa5, 0xff, 0xf6, 0xbb, 0x99, 0xff,
+ 0xce, 0x92, 0x73, 0xff, 0xde, 0xa2, 0x81, 0xff,
+ 0xde, 0xa2, 0x81, 0xff, 0xee, 0xb2, 0x8e, 0xff,
+ 0xff, 0xc4, 0x9a, 0xff, 0xff, 0xca, 0x9c, 0xff,
+ 0xff, 0xc4, 0x9a, 0xff, 0xff, 0xc3, 0x99, 0xff,
+ 0xff, 0xc1, 0x9f, 0xff, 0xff, 0xc6, 0xa4, 0xff,
+ 0xff, 0xc6, 0xa5, 0xff, 0xff, 0xc6, 0xa4, 0xff,
+ 0xff, 0xcf, 0xad, 0xff, 0xff, 0xce, 0xac, 0xff,
+ 0xff, 0xc8, 0xa5, 0xff, 0xff, 0xc7, 0xa4, 0xff,
+ 0xff, 0xc6, 0xa7, 0xff, 0xff, 0xca, 0xac, 0xff,
+ 0xff, 0xca, 0xad, 0xff, 0xff, 0xca, 0xac, 0xff,
+ 0xf7, 0xbe, 0x9c, 0xff, 0xbd, 0x9e, 0x83, 0xff,
+ 0x84, 0x7e, 0x6b, 0xff, 0x4a, 0x5d, 0x52, 0xff,
+ 0x3f, 0x50, 0x4d, 0xff, 0x31, 0x40, 0x41, 0xff,
+ 0x31, 0x41, 0x42, 0xff, 0x3f, 0x4f, 0x4c, 0xff,
+ 0x3c, 0x4a, 0x47, 0xff, 0x3c, 0x4a, 0x47, 0xff,
+ 0x37, 0x3f, 0x3c, 0xff, 0x36, 0x3f, 0x3c, 0xff,
+ 0x32, 0x39, 0x3a, 0xff, 0x3c, 0x46, 0x44, 0xff,
+ 0x42, 0x4d, 0x4a, 0xff, 0x41, 0x4c, 0x4a, 0xff,
+ 0x47, 0x54, 0x50, 0xff, 0x47, 0x53, 0x4f, 0xff,
+ 0x55, 0x5a, 0x55, 0xff, 0x62, 0x61, 0x5a, 0xff,
+ 0x4a, 0x51, 0x4a, 0xff, 0x4a, 0x51, 0x4a, 0xff,
+ 0x4a, 0x51, 0x4a, 0xff, 0x7e, 0x71, 0x5f, 0xff,
+ 0xad, 0x9e, 0x8c, 0xff, 0xac, 0x9e, 0x8b, 0xff,
+ 0xad, 0x9e, 0x8c, 0xff, 0xac, 0x9d, 0x8b, 0xff,
+ 0x81, 0x78, 0x68, 0xff, 0x41, 0x4d, 0x41, 0xff,
+ 0x42, 0x4d, 0x42, 0xff, 0x41, 0x4c, 0x41, 0xff,
+ 0x29, 0x39, 0x32, 0xff, 0x21, 0x29, 0x23, 0xff,
+ 0x19, 0x1b, 0x16, 0xff, 0x10, 0x0c, 0x08, 0xff,
+ 0xc6, 0xb1, 0x8f, 0xff, 0xff, 0xe3, 0xb5, 0xff,
+ 0xc6, 0xb1, 0x8f, 0xff, 0x8c, 0x7f, 0x68, 0xff,
+ 0x8a, 0x75, 0x66, 0xff, 0xb5, 0x92, 0x7b, 0xff,
+ 0xb5, 0x92, 0x7c, 0xff, 0x89, 0x74, 0x65, 0xff,
+ 0x74, 0x5e, 0x4b, 0xff, 0x7e, 0x69, 0x5a, 0xff,
+ 0x74, 0x5d, 0x4a, 0xff, 0x7e, 0x69, 0x5a, 0xff,
+ 0x97, 0x7b, 0x6e, 0xff, 0xcb, 0xa5, 0x91, 0xff,
+ 0xff, 0xcf, 0xb5, 0xff, 0xff, 0xce, 0xb5, 0xff,
+ 0xea, 0xc7, 0xa8, 0xff, 0xe9, 0xc6, 0xa7, 0xff,
+ 0xf4, 0xdb, 0xbb, 0xff, 0xf4, 0xda, 0xba, 0xff,
+ 0xe4, 0xc8, 0xaa, 0xff, 0xe4, 0xc8, 0xaa, 0xff,
+ 0xe4, 0xc8, 0xaa, 0xff, 0xff, 0xe7, 0xc5, 0xff,
+ 0xff, 0xd7, 0xb5, 0xff, 0xff, 0xd6, 0xb5, 0xff,
+ 0xff, 0xd7, 0xb5, 0xff, 0xcb, 0xb1, 0x9c, 0xff,
+ 0x84, 0x86, 0x74, 0xff, 0x52, 0x60, 0x58, 0xff,
+ 0x53, 0x60, 0x58, 0xff, 0x39, 0x4d, 0x4a, 0xff,
+ 0x45, 0x51, 0x53, 0xff, 0x3f, 0x49, 0x4a, 0xff,
+ 0x3f, 0x49, 0x4a, 0xff, 0x3f, 0x49, 0x4a, 0xff,
+ 0x40, 0x48, 0x45, 0xff, 0x34, 0x3a, 0x37, 0xff,
+ 0x29, 0x2d, 0x29, 0xff, 0x29, 0x2c, 0x29, 0xff,
+ 0x2a, 0x35, 0x32, 0xff, 0x4a, 0x4e, 0x45, 0xff,
+ 0x4a, 0x4f, 0x45, 0xff, 0x4a, 0x4e, 0x44, 0xff,
+ 0x4d, 0x4c, 0x45, 0xff, 0x29, 0x35, 0x31, 0xff,
+ 0x4d, 0x4c, 0x45, 0xff, 0x4d, 0x4b, 0x44, 0xff,
+ 0x42, 0x55, 0x53, 0xff, 0x42, 0x55, 0x52, 0xff,
+ 0x32, 0x45, 0x42, 0xff, 0x39, 0x4d, 0x4a, 0xff,
+ 0x42, 0x54, 0x50, 0xff, 0x5a, 0x6b, 0x65, 0xff,
+ 0x74, 0x82, 0x7c, 0xff, 0x73, 0x81, 0x7b, 0xff,
+ 0x42, 0x5a, 0x53, 0xff, 0x34, 0x46, 0x42, 0xff,
+ 0x27, 0x34, 0x32, 0xff, 0x34, 0x46, 0x42, 0xff,
+ 0x3a, 0x4d, 0x4b, 0xff, 0x2c, 0x39, 0x37, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0xc6, 0xb1, 0x8f, 0xff, 0xc5, 0xb0, 0x8e, 0xff,
+ 0x8c, 0x7f, 0x68, 0xff, 0x52, 0x4d, 0x42, 0xff,
+ 0x5d, 0x56, 0x50, 0xff, 0x5d, 0x56, 0x4f, 0xff,
+ 0x89, 0x74, 0x66, 0xff, 0x5d, 0x56, 0x4f, 0xff,
+ 0x73, 0x5d, 0x4a, 0xff, 0x7e, 0x69, 0x5a, 0xff,
+ 0x73, 0x5d, 0x4a, 0xff, 0x73, 0x5d, 0x4a, 0xff,
+ 0x63, 0x51, 0x4a, 0xff, 0x62, 0x51, 0x4a, 0xff,
+ 0x97, 0x7b, 0x6e, 0xff, 0xff, 0xce, 0xb5, 0xff,
+ 0xf4, 0xdb, 0xbb, 0xff, 0xf4, 0xda, 0xba, 0xff,
+ 0xf4, 0xdb, 0xbb, 0xff, 0xf4, 0xda, 0xba, 0xff,
+ 0xff, 0xe7, 0xc6, 0xff, 0xff, 0xe6, 0xc5, 0xff,
+ 0xff, 0xe7, 0xc6, 0xff, 0xff, 0xe6, 0xc5, 0xff,
+ 0xff, 0xd7, 0xb5, 0xff, 0xff, 0xd6, 0xb5, 0xff,
+ 0xcb, 0xb1, 0x9d, 0xff, 0x97, 0x8b, 0x83, 0xff,
+ 0x6b, 0x73, 0x66, 0xff, 0x52, 0x5f, 0x57, 0xff,
+ 0x52, 0x60, 0x58, 0xff, 0x39, 0x4d, 0x4a, 0xff,
+ 0x45, 0x51, 0x52, 0xff, 0x3f, 0x48, 0x4a, 0xff,
+ 0x3a, 0x41, 0x42, 0xff, 0x39, 0x40, 0x42, 0xff,
+ 0x3f, 0x48, 0x45, 0xff, 0x3f, 0x47, 0x44, 0xff,
+ 0x34, 0x3a, 0x37, 0xff, 0x29, 0x2c, 0x29, 0xff,
+ 0x4a, 0x4e, 0x45, 0xff, 0x6b, 0x67, 0x57, 0xff,
+ 0x4a, 0x4e, 0x45, 0xff, 0x4a, 0x4e, 0x44, 0xff,
+ 0x4d, 0x4c, 0x45, 0xff, 0x70, 0x62, 0x57, 0xff,
+ 0x71, 0x63, 0x58, 0xff, 0x4c, 0x4b, 0x44, 0xff,
+ 0x3a, 0x4d, 0x4a, 0xff, 0x31, 0x44, 0x41, 0xff,
+ 0x3a, 0x4d, 0x4a, 0xff, 0x4a, 0x5d, 0x5a, 0xff,
+ 0x5b, 0x6b, 0x66, 0xff, 0x5a, 0x6a, 0x65, 0xff,
+ 0x5b, 0x6b, 0x66, 0xff, 0x42, 0x53, 0x4f, 0xff,
+ 0x34, 0x46, 0x42, 0xff, 0x26, 0x33, 0x31, 0xff,
+ 0x19, 0x21, 0x21, 0xff, 0x26, 0x33, 0x31, 0xff,
+ 0x2c, 0x39, 0x37, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x8c, 0x7f, 0x68, 0xff, 0x52, 0x4d, 0x42, 0xff,
+ 0x53, 0x4d, 0x42, 0xff, 0x52, 0x4d, 0x42, 0xff,
+ 0x5e, 0x57, 0x50, 0xff, 0x31, 0x38, 0x39, 0xff,
+ 0x5e, 0x57, 0x50, 0xff, 0x89, 0x74, 0x65, 0xff,
+ 0x94, 0x82, 0x7c, 0xff, 0x89, 0x75, 0x6b, 0xff,
+ 0x8a, 0x76, 0x6b, 0xff, 0x7e, 0x69, 0x5a, 0xff,
+ 0x97, 0x7b, 0x6e, 0xff, 0x62, 0x51, 0x4a, 0xff,
+ 0x63, 0x51, 0x4a, 0xff, 0xff, 0xce, 0xb5, 0xff,
+ 0xff, 0xef, 0xce, 0xff, 0xff, 0xef, 0xcd, 0xff,
+ 0xff, 0xef, 0xce, 0xff, 0xf4, 0xda, 0xba, 0xff,
+ 0xff, 0xe7, 0xc6, 0xff, 0xe3, 0xc7, 0xaa, 0xff,
+ 0xc9, 0xa9, 0x8f, 0xff, 0xe3, 0xc8, 0xaa, 0xff,
+ 0xcb, 0xb1, 0x9d, 0xff, 0x97, 0x8b, 0x83, 0xff,
+ 0x97, 0x8b, 0x84, 0xff, 0x97, 0x8b, 0x84, 0xff,
+ 0x6b, 0x73, 0x66, 0xff, 0x52, 0x60, 0x58, 0xff,
+ 0x3a, 0x4d, 0x4a, 0xff, 0x39, 0x4d, 0x4a, 0xff,
+ 0x4a, 0x59, 0x5b, 0xff, 0x4a, 0x59, 0x5a, 0xff,
+ 0x3f, 0x49, 0x4a, 0xff, 0x44, 0x51, 0x52, 0xff,
+ 0x34, 0x3a, 0x37, 0xff, 0x34, 0x3a, 0x37, 0xff,
+ 0x2a, 0x2d, 0x2a, 0xff, 0x3f, 0x47, 0x44, 0xff,
+ 0x6b, 0x68, 0x58, 0xff, 0x8c, 0x81, 0x6b, 0xff,
+ 0x6b, 0x68, 0x58, 0xff, 0x6b, 0x68, 0x58, 0xff,
+ 0x71, 0x63, 0x58, 0xff, 0x70, 0x62, 0x58, 0xff,
+ 0x94, 0x7a, 0x6b, 0xff, 0x4d, 0x4b, 0x44, 0xff,
+ 0x3a, 0x4d, 0x4a, 0xff, 0x31, 0x45, 0x42, 0xff,
+ 0x32, 0x45, 0x42, 0xff, 0x4a, 0x5d, 0x5a, 0xff,
+ 0x42, 0x54, 0x50, 0xff, 0x42, 0x53, 0x4f, 0xff,
+ 0x42, 0x54, 0x50, 0xff, 0x29, 0x3d, 0x39, 0xff,
+ 0x27, 0x34, 0x32, 0xff, 0x18, 0x20, 0x21, 0xff,
+ 0x27, 0x34, 0x32, 0xff, 0x19, 0x20, 0x21, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x52, 0x4d, 0x42, 0xff, 0x52, 0x4d, 0x41, 0xff,
+ 0x52, 0x4d, 0x42, 0xff, 0x52, 0x4c, 0x41, 0xff,
+ 0x32, 0x39, 0x3a, 0xff, 0x31, 0x38, 0x39, 0xff,
+ 0x31, 0x39, 0x3a, 0xff, 0x5d, 0x56, 0x4f, 0xff,
+ 0x7e, 0x69, 0x5b, 0xff, 0x94, 0x81, 0x7b, 0xff,
+ 0x94, 0x82, 0x7b, 0xff, 0x94, 0x81, 0x7b, 0xff,
+ 0x97, 0x7b, 0x6e, 0xff, 0x96, 0x7a, 0x6d, 0xff,
+ 0xcb, 0xa5, 0x91, 0xff, 0xca, 0xa4, 0x91, 0xff,
+ 0xf4, 0xdb, 0xbb, 0xff, 0xf4, 0xda, 0xba, 0xff,
+ 0xde, 0xb2, 0x94, 0xff, 0xde, 0xb2, 0x94, 0xff,
+ 0xff, 0xe7, 0xc6, 0xff, 0xc8, 0xa8, 0x8e, 0xff,
+ 0xad, 0x8a, 0x73, 0xff, 0xc8, 0xa8, 0x8e, 0xff,
+ 0x97, 0x8b, 0x84, 0xff, 0x62, 0x65, 0x6b, 0xff,
+ 0x63, 0x65, 0x6b, 0xff, 0x62, 0x65, 0x6a, 0xff,
+ 0x52, 0x60, 0x58, 0xff, 0x39, 0x4d, 0x4a, 0xff,
+ 0x52, 0x60, 0x58, 0xff, 0x39, 0x4c, 0x4a, 0xff,
+ 0x4a, 0x59, 0x5b, 0xff, 0x44, 0x51, 0x52, 0xff,
+ 0x3f, 0x49, 0x4a, 0xff, 0x39, 0x40, 0x41, 0xff,
+ 0x3f, 0x48, 0x45, 0xff, 0x3f, 0x47, 0x44, 0xff,
+ 0x34, 0x3a, 0x37, 0xff, 0x4a, 0x55, 0x52, 0xff,
+ 0x6b, 0x68, 0x58, 0xff, 0x6b, 0x68, 0x57, 0xff,
+ 0x4a, 0x4e, 0x45, 0xff, 0x6a, 0x67, 0x57, 0xff,
+ 0x29, 0x35, 0x32, 0xff, 0x29, 0x34, 0x31, 0xff,
+ 0x4d, 0x4c, 0x45, 0xff, 0x4c, 0x4b, 0x44, 0xff,
+ 0x3a, 0x4d, 0x4a, 0xff, 0x39, 0x4d, 0x4a, 0xff,
+ 0x3a, 0x4d, 0x4a, 0xff, 0x41, 0x55, 0x52, 0xff,
+ 0x42, 0x54, 0x50, 0xff, 0x41, 0x53, 0x4f, 0xff,
+ 0x42, 0x54, 0x50, 0xff, 0x29, 0x3c, 0x39, 0xff,
+ 0x19, 0x21, 0x21, 0xff, 0x18, 0x20, 0x21, 0xff,
+ 0x26, 0x33, 0x31, 0xff, 0x18, 0x20, 0x20, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x10, 0x10, 0x10, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x42, 0x45, 0x42, 0xff, 0x3a, 0x3e, 0x3a, 0xff,
+ 0x32, 0x38, 0x32, 0xff, 0x42, 0x45, 0x42, 0xff,
+ 0x45, 0x44, 0x3d, 0xff, 0x58, 0x52, 0x47, 0xff,
+ 0x58, 0x53, 0x48, 0xff, 0x58, 0x52, 0x47, 0xff,
+ 0x69, 0x68, 0x66, 0xff, 0x68, 0x68, 0x65, 0xff,
+ 0x9f, 0x9c, 0x9a, 0xff, 0x9f, 0x9b, 0x99, 0xff,
+ 0x95, 0x92, 0x95, 0xff, 0x9c, 0x9a, 0x9c, 0xff,
+ 0x9a, 0x97, 0x9a, 0xff, 0x94, 0x92, 0x94, 0xff,
+ 0x9a, 0x99, 0x97, 0xff, 0x9a, 0x98, 0x97, 0xff,
+ 0x94, 0x8e, 0x8c, 0xff, 0x94, 0x8e, 0x8c, 0xff,
+ 0x9d, 0x9e, 0x9d, 0xff, 0x8f, 0x8f, 0x8c, 0xff,
+ 0x74, 0x72, 0x6b, 0xff, 0x73, 0x71, 0x6b, 0xff,
+ 0x50, 0x55, 0x50, 0xff, 0x4f, 0x55, 0x4f, 0xff,
+ 0x29, 0x31, 0x29, 0xff, 0x76, 0x79, 0x76, 0xff,
+ 0x4b, 0x5e, 0x5b, 0xff, 0x3f, 0x51, 0x4d, 0xff,
+ 0x4a, 0x5d, 0x5b, 0xff, 0x34, 0x45, 0x3f, 0xff,
+ 0x3a, 0x49, 0x45, 0xff, 0x42, 0x55, 0x52, 0xff,
+ 0x32, 0x3d, 0x37, 0xff, 0x29, 0x30, 0x29, 0xff,
+ 0x2a, 0x32, 0x32, 0xff, 0x31, 0x43, 0x42, 0xff,
+ 0x32, 0x44, 0x42, 0xff, 0x39, 0x55, 0x52, 0xff,
+ 0x4b, 0x5a, 0x4b, 0xff, 0x3a, 0x42, 0x3a, 0xff,
+ 0x3a, 0x42, 0x3a, 0xff, 0x39, 0x42, 0x39, 0xff,
+ 0x2c, 0x31, 0x2f, 0xff, 0x21, 0x20, 0x21, 0xff,
+ 0x42, 0x51, 0x4a, 0xff, 0x42, 0x51, 0x4a, 0xff,
+ 0x42, 0x51, 0x4b, 0xff, 0x37, 0x43, 0x3f, 0xff,
+ 0x37, 0x44, 0x3f, 0xff, 0x37, 0x43, 0x3f, 0xff,
+ 0x42, 0x55, 0x53, 0xff, 0x3a, 0x49, 0x45, 0xff,
+ 0x3a, 0x49, 0x45, 0xff, 0x31, 0x3d, 0x37, 0xff,
+ 0x32, 0x39, 0x3a, 0xff, 0x31, 0x39, 0x3a, 0xff,
+ 0x24, 0x29, 0x29, 0xff, 0x16, 0x18, 0x19, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x1e, 0x24, 0x24, 0xff,
+ 0x11, 0x11, 0x11, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x42, 0x45, 0x42, 0xff, 0x41, 0x44, 0x41, 0xff,
+ 0x32, 0x38, 0x32, 0xff, 0x29, 0x30, 0x29, 0xff,
+ 0x31, 0x35, 0x31, 0xff, 0x6b, 0x61, 0x52, 0xff,
+ 0x58, 0x53, 0x48, 0xff, 0x31, 0x34, 0x31, 0xff,
+ 0x31, 0x35, 0x31, 0xff, 0x68, 0x67, 0x65, 0xff,
+ 0x9f, 0x9b, 0x9a, 0xff, 0x9f, 0x9b, 0x99, 0xff,
+ 0x9a, 0x97, 0x9a, 0xff, 0x99, 0x97, 0x99, 0xff,
+ 0x9a, 0x97, 0x9a, 0xff, 0x99, 0x97, 0x99, 0xff,
+ 0x9a, 0x99, 0x97, 0xff, 0x99, 0x98, 0x96, 0xff,
+ 0x9a, 0x99, 0x97, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0x9c, 0x9e, 0x9c, 0xff, 0x9c, 0x9d, 0x9c, 0xff,
+ 0x9d, 0x9e, 0x9d, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0x76, 0x7a, 0x76, 0xff, 0x29, 0x30, 0x29, 0xff,
+ 0x29, 0x31, 0x29, 0xff, 0x4f, 0x55, 0x4f, 0xff,
+ 0x4a, 0x5d, 0x5b, 0xff, 0x3f, 0x51, 0x4c, 0xff,
+ 0x3f, 0x51, 0x4d, 0xff, 0x3f, 0x51, 0x4c, 0xff,
+ 0x3a, 0x49, 0x45, 0xff, 0x39, 0x48, 0x44, 0xff,
+ 0x3a, 0x49, 0x45, 0xff, 0x31, 0x3c, 0x37, 0xff,
+ 0x29, 0x32, 0x31, 0xff, 0x29, 0x32, 0x31, 0xff,
+ 0x32, 0x44, 0x42, 0xff, 0x29, 0x32, 0x31, 0xff,
+ 0x3a, 0x42, 0x3a, 0xff, 0x29, 0x2b, 0x29, 0xff,
+ 0x19, 0x14, 0x19, 0xff, 0x29, 0x2b, 0x29, 0xff,
+ 0x37, 0x41, 0x3c, 0xff, 0x41, 0x51, 0x4a, 0xff,
+ 0x2c, 0x31, 0x2f, 0xff, 0x37, 0x40, 0x3c, 0xff,
+ 0x37, 0x44, 0x3f, 0xff, 0x2b, 0x36, 0x34, 0xff,
+ 0x2c, 0x36, 0x34, 0xff, 0x37, 0x43, 0x3f, 0xff,
+ 0x3a, 0x49, 0x45, 0xff, 0x39, 0x48, 0x44, 0xff,
+ 0x3a, 0x49, 0x45, 0xff, 0x31, 0x3c, 0x37, 0xff,
+ 0x16, 0x18, 0x19, 0xff, 0x16, 0x18, 0x18, 0xff,
+ 0x16, 0x19, 0x19, 0xff, 0x23, 0x28, 0x29, 0xff,
+ 0x1e, 0x25, 0x24, 0xff, 0x2b, 0x38, 0x36, 0xff,
+ 0x1e, 0x25, 0x24, 0xff, 0x2c, 0x38, 0x37, 0xff,
+ 0x3a, 0x3e, 0x3a, 0xff, 0x39, 0x3e, 0x39, 0xff,
+ 0x32, 0x38, 0x32, 0xff, 0x29, 0x30, 0x29, 0xff,
+ 0x32, 0x35, 0x32, 0xff, 0x44, 0x43, 0x3c, 0xff,
+ 0x58, 0x53, 0x48, 0xff, 0x31, 0x35, 0x31, 0xff,
+ 0x32, 0x35, 0x32, 0xff, 0x68, 0x68, 0x65, 0xff,
+ 0x9f, 0x9c, 0x9a, 0xff, 0x9f, 0x9b, 0x99, 0xff,
+ 0x9a, 0x97, 0x9a, 0xff, 0x99, 0x97, 0x99, 0xff,
+ 0x9a, 0x98, 0x9a, 0xff, 0x9c, 0x9a, 0x9c, 0xff,
+ 0x9a, 0x99, 0x97, 0xff, 0x99, 0x98, 0x97, 0xff,
+ 0x9a, 0x99, 0x97, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0x9d, 0x9e, 0x9d, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0x9d, 0x9e, 0x9d, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0x9d, 0x9e, 0x9d, 0xff, 0x76, 0x79, 0x76, 0xff,
+ 0x50, 0x55, 0x50, 0xff, 0x29, 0x30, 0x29, 0xff,
+ 0x29, 0x39, 0x32, 0xff, 0x4a, 0x5d, 0x5a, 0xff,
+ 0x3f, 0x51, 0x4d, 0xff, 0x3f, 0x51, 0x4d, 0xff,
+ 0x3a, 0x49, 0x45, 0xff, 0x39, 0x49, 0x44, 0xff,
+ 0x3a, 0x49, 0x45, 0xff, 0x42, 0x55, 0x52, 0xff,
+ 0x3a, 0x55, 0x53, 0xff, 0x39, 0x55, 0x52, 0xff,
+ 0x2a, 0x32, 0x32, 0xff, 0x21, 0x20, 0x21, 0xff,
+ 0x3a, 0x42, 0x3a, 0xff, 0x29, 0x2b, 0x29, 0xff,
+ 0x19, 0x15, 0x19, 0xff, 0x29, 0x2b, 0x29, 0xff,
+ 0x37, 0x41, 0x3d, 0xff, 0x2c, 0x30, 0x2e, 0xff,
+ 0x21, 0x21, 0x21, 0xff, 0x21, 0x20, 0x21, 0xff,
+ 0x2c, 0x36, 0x34, 0xff, 0x21, 0x28, 0x29, 0xff,
+ 0x2c, 0x36, 0x35, 0xff, 0x42, 0x51, 0x4a, 0xff,
+ 0x3a, 0x49, 0x45, 0xff, 0x31, 0x3c, 0x37, 0xff,
+ 0x3a, 0x49, 0x45, 0xff, 0x31, 0x3d, 0x37, 0xff,
+ 0x16, 0x19, 0x19, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x09, 0x09, 0x09, 0xff, 0x16, 0x18, 0x19, 0xff,
+ 0x1e, 0x25, 0x24, 0xff, 0x2c, 0x38, 0x37, 0xff,
+ 0x3a, 0x4d, 0x4a, 0xff, 0x39, 0x4d, 0x4a, 0xff,
+ 0x42, 0x45, 0x42, 0xff, 0x41, 0x44, 0x41, 0xff,
+ 0x42, 0x45, 0x42, 0xff, 0x41, 0x44, 0x41, 0xff,
+ 0x32, 0x35, 0x32, 0xff, 0x31, 0x34, 0x31, 0xff,
+ 0x31, 0x35, 0x31, 0xff, 0x44, 0x43, 0x3c, 0xff,
+ 0x32, 0x35, 0x32, 0xff, 0x68, 0x68, 0x65, 0xff,
+ 0xd6, 0xce, 0xce, 0xff, 0x9f, 0x9b, 0x99, 0xff,
+ 0x97, 0x95, 0x97, 0xff, 0x99, 0x97, 0x99, 0xff,
+ 0x9a, 0x97, 0x9a, 0xff, 0x9c, 0x99, 0x9c, 0xff,
+ 0x9a, 0x99, 0x97, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0x9c, 0x9e, 0x9c, 0xff, 0x99, 0x98, 0x96, 0xff,
+ 0x9c, 0x9e, 0x9c, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0x9c, 0x9e, 0x9c, 0xff, 0x9c, 0x9d, 0x9c, 0xff,
+ 0x9c, 0x9e, 0x9c, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0x76, 0x79, 0x76, 0xff, 0x4f, 0x55, 0x4f, 0xff,
+ 0x29, 0x39, 0x32, 0xff, 0x4a, 0x5d, 0x5a, 0xff,
+ 0x3f, 0x51, 0x4d, 0xff, 0x34, 0x44, 0x3f, 0xff,
+ 0x32, 0x3d, 0x37, 0xff, 0x39, 0x49, 0x44, 0xff,
+ 0x3a, 0x49, 0x45, 0xff, 0x39, 0x48, 0x44, 0xff,
+ 0x32, 0x44, 0x42, 0xff, 0x39, 0x55, 0x52, 0xff,
+ 0x31, 0x43, 0x42, 0xff, 0x20, 0x20, 0x20, 0xff,
+ 0x19, 0x14, 0x19, 0xff, 0x18, 0x14, 0x18, 0xff,
+ 0x29, 0x2b, 0x29, 0xff, 0x29, 0x2b, 0x29, 0xff,
+ 0x37, 0x41, 0x3c, 0xff, 0x21, 0x20, 0x21, 0xff,
+ 0x21, 0x20, 0x21, 0xff, 0x36, 0x40, 0x3c, 0xff,
+ 0x42, 0x51, 0x4a, 0xff, 0x36, 0x43, 0x3f, 0xff,
+ 0x2c, 0x36, 0x34, 0xff, 0x2b, 0x35, 0x34, 0xff,
+ 0x32, 0x3d, 0x37, 0xff, 0x31, 0x3c, 0x36, 0xff,
+ 0x29, 0x31, 0x29, 0xff, 0x29, 0x30, 0x29, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x16, 0x18, 0x19, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x11, 0x10, 0x11, 0xff, 0x2c, 0x38, 0x36, 0xff,
+ 0x2c, 0x39, 0x37, 0xff, 0x2b, 0x38, 0x36, 0xff,
+ 0x42, 0x49, 0x42, 0xff, 0x42, 0x49, 0x42, 0xff,
+ 0x37, 0x3d, 0x37, 0xff, 0x2c, 0x30, 0x2c, 0xff,
+ 0x24, 0x25, 0x24, 0xff, 0x24, 0x24, 0x24, 0xff,
+ 0x24, 0x25, 0x24, 0xff, 0x29, 0x2c, 0x29, 0xff,
+ 0x3a, 0x45, 0x42, 0xff, 0xa2, 0xa3, 0x9a, 0xff,
+ 0xd6, 0xd3, 0xc6, 0xff, 0xa2, 0xa3, 0x99, 0xff,
+ 0x92, 0x98, 0x8f, 0xff, 0x91, 0x97, 0x8f, 0xff,
+ 0x92, 0x97, 0x8f, 0xff, 0x9f, 0xa0, 0x99, 0xff,
+ 0x9d, 0x9e, 0x9d, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0x9d, 0x9e, 0x9d, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0x9d, 0x9e, 0x9d, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0x9d, 0x9e, 0x9d, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0xa5, 0xa2, 0x9d, 0xff, 0xa4, 0xa2, 0x9c, 0xff,
+ 0xa5, 0xa2, 0x9d, 0xff, 0x8c, 0x8b, 0x86, 0xff,
+ 0x4b, 0x55, 0x50, 0xff, 0x4a, 0x55, 0x4f, 0xff,
+ 0x21, 0x31, 0x29, 0xff, 0x21, 0x30, 0x29, 0xff,
+ 0x35, 0x47, 0x42, 0xff, 0x37, 0x50, 0x4a, 0xff,
+ 0x34, 0x47, 0x42, 0xff, 0x34, 0x46, 0x42, 0xff,
+ 0x2c, 0x3f, 0x3d, 0xff, 0x2c, 0x3e, 0x3c, 0xff,
+ 0x2c, 0x3e, 0x3d, 0xff, 0x1e, 0x27, 0x26, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x24, 0x28, 0x24, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x23, 0x28, 0x23, 0xff,
+ 0x21, 0x25, 0x21, 0xff, 0x2c, 0x36, 0x34, 0xff,
+ 0x37, 0x48, 0x48, 0xff, 0x37, 0x47, 0x47, 0xff,
+ 0x3a, 0x51, 0x4b, 0xff, 0x3a, 0x51, 0x4a, 0xff,
+ 0x3a, 0x51, 0x4a, 0xff, 0x2c, 0x3a, 0x37, 0xff,
+ 0x32, 0x41, 0x3a, 0xff, 0x24, 0x2f, 0x29, 0xff,
+ 0x24, 0x30, 0x29, 0xff, 0x16, 0x1e, 0x19, 0xff,
+ 0x14, 0x13, 0x14, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x09, 0x08, 0x09, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x09, 0x09, 0x09, 0xff, 0x19, 0x20, 0x1e, 0xff,
+ 0x21, 0x2d, 0x29, 0xff, 0x19, 0x20, 0x1e, 0xff,
+ 0x37, 0x3d, 0x37, 0xff, 0x36, 0x3c, 0x36, 0xff,
+ 0x2c, 0x31, 0x2c, 0xff, 0x21, 0x24, 0x21, 0xff,
+ 0x19, 0x14, 0x19, 0xff, 0x1e, 0x1c, 0x1e, 0xff,
+ 0x24, 0x25, 0x24, 0xff, 0x23, 0x24, 0x23, 0xff,
+ 0x3a, 0x45, 0x42, 0xff, 0xa1, 0xa3, 0x99, 0xff,
+ 0xa2, 0xa3, 0x9a, 0xff, 0xd6, 0xd2, 0xc5, 0xff,
+ 0x91, 0x97, 0x8f, 0xff, 0x91, 0x97, 0x8e, 0xff,
+ 0x92, 0x97, 0x8f, 0xff, 0x91, 0x97, 0x8e, 0xff,
+ 0x9c, 0x9e, 0x9c, 0xff, 0x9c, 0x9d, 0x9c, 0xff,
+ 0x9d, 0x9e, 0x9d, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0x9c, 0x9e, 0x9c, 0xff, 0x9c, 0x9d, 0x9c, 0xff,
+ 0x9d, 0x9e, 0x9d, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0xa5, 0xa2, 0x9c, 0xff, 0xa4, 0xa1, 0x9c, 0xff,
+ 0xa5, 0xa2, 0x9d, 0xff, 0xa4, 0xa2, 0x9c, 0xff,
+ 0x9c, 0x9e, 0x9c, 0xff, 0x4a, 0x55, 0x4f, 0xff,
+ 0x21, 0x31, 0x29, 0xff, 0x4a, 0x55, 0x4f, 0xff,
+ 0x37, 0x50, 0x4a, 0xff, 0x34, 0x46, 0x41, 0xff,
+ 0x34, 0x46, 0x42, 0xff, 0x37, 0x4f, 0x4a, 0xff,
+ 0x3a, 0x55, 0x52, 0xff, 0x39, 0x55, 0x52, 0xff,
+ 0x2c, 0x3e, 0x3d, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x19, 0x14, 0x11, 0xff, 0x2e, 0x3c, 0x36, 0xff,
+ 0x24, 0x29, 0x24, 0xff, 0x23, 0x28, 0x23, 0xff,
+ 0x21, 0x25, 0x21, 0xff, 0x20, 0x24, 0x20, 0xff,
+ 0x37, 0x48, 0x48, 0xff, 0x2c, 0x36, 0x34, 0xff,
+ 0x2c, 0x3a, 0x37, 0xff, 0x39, 0x51, 0x4a, 0xff,
+ 0x3a, 0x51, 0x4a, 0xff, 0x39, 0x51, 0x4a, 0xff,
+ 0x31, 0x41, 0x3a, 0xff, 0x31, 0x40, 0x39, 0xff,
+ 0x32, 0x41, 0x3a, 0xff, 0x16, 0x1d, 0x18, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x11, 0x14, 0x13, 0xff, 0x10, 0x14, 0x13, 0xff,
+ 0x11, 0x14, 0x13, 0xff, 0x10, 0x14, 0x13, 0xff,
+ 0x2c, 0x31, 0x2c, 0xff, 0x21, 0x24, 0x21, 0xff,
+ 0x2c, 0x31, 0x2c, 0xff, 0x2c, 0x30, 0x2c, 0xff,
+ 0x29, 0x2d, 0x29, 0xff, 0x1e, 0x1c, 0x1e, 0xff,
+ 0x24, 0x25, 0x24, 0xff, 0x19, 0x14, 0x19, 0xff,
+ 0x6e, 0x74, 0x6e, 0xff, 0xa2, 0xa3, 0x99, 0xff,
+ 0x6e, 0x74, 0x6e, 0xff, 0xd6, 0xd2, 0xc5, 0xff,
+ 0xad, 0xaa, 0xa5, 0xff, 0x91, 0x97, 0x8e, 0xff,
+ 0x9f, 0xa1, 0x9a, 0xff, 0xad, 0xaa, 0xa4, 0xff,
+ 0x9d, 0x9e, 0x9d, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0x9d, 0x9e, 0x9d, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0x9d, 0x9e, 0x9d, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0x9d, 0x9e, 0x9d, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0xa5, 0xa2, 0x9d, 0xff, 0xa4, 0xa2, 0x9c, 0xff,
+ 0xa5, 0xa2, 0x9d, 0xff, 0xa4, 0xa2, 0x9c, 0xff,
+ 0x9d, 0x9e, 0x9d, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0x74, 0x7a, 0x76, 0xff, 0x4a, 0x55, 0x4f, 0xff,
+ 0x32, 0x3d, 0x3a, 0xff, 0x34, 0x46, 0x42, 0xff,
+ 0x37, 0x50, 0x4a, 0xff, 0x39, 0x59, 0x52, 0xff,
+ 0x3a, 0x55, 0x53, 0xff, 0x2c, 0x3e, 0x3c, 0xff,
+ 0x1f, 0x28, 0x27, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x19, 0x15, 0x11, 0xff, 0x23, 0x28, 0x23, 0xff,
+ 0x2f, 0x3d, 0x37, 0xff, 0x2f, 0x3d, 0x37, 0xff,
+ 0x37, 0x48, 0x48, 0xff, 0x37, 0x47, 0x47, 0xff,
+ 0x42, 0x59, 0x5b, 0xff, 0x37, 0x47, 0x47, 0xff,
+ 0x2c, 0x3a, 0x37, 0xff, 0x2c, 0x3a, 0x37, 0xff,
+ 0x2c, 0x3a, 0x37, 0xff, 0x1e, 0x23, 0x24, 0xff,
+ 0x24, 0x30, 0x29, 0xff, 0x23, 0x2f, 0x29, 0xff,
+ 0x16, 0x1e, 0x19, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x09, 0x08, 0x09, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x14, 0x13, 0x14, 0xff, 0x29, 0x28, 0x29, 0xff,
+ 0x19, 0x21, 0x1e, 0xff, 0x10, 0x14, 0x13, 0xff,
+ 0x11, 0x15, 0x14, 0xff, 0x10, 0x14, 0x13, 0xff,
+ 0x2c, 0x31, 0x2c, 0xff, 0x36, 0x3c, 0x36, 0xff,
+ 0x37, 0x3d, 0x37, 0xff, 0x36, 0x3c, 0x36, 0xff,
+ 0x29, 0x2d, 0x29, 0xff, 0x23, 0x24, 0x23, 0xff,
+ 0x24, 0x24, 0x24, 0xff, 0x1e, 0x1c, 0x1e, 0xff,
+ 0x6e, 0x74, 0x6e, 0xff, 0xa1, 0xa3, 0x99, 0xff,
+ 0xa2, 0xa3, 0x9a, 0xff, 0xd5, 0xd2, 0xc5, 0xff,
+ 0xad, 0xaa, 0xa5, 0xff, 0x83, 0x8d, 0x83, 0xff,
+ 0x84, 0x8e, 0x84, 0xff, 0x91, 0x97, 0x8e, 0xff,
+ 0x84, 0x86, 0x84, 0xff, 0x52, 0x55, 0x52, 0xff,
+ 0x52, 0x55, 0x52, 0xff, 0x6a, 0x6d, 0x6a, 0xff,
+ 0x52, 0x55, 0x4a, 0xff, 0x52, 0x55, 0x4a, 0xff,
+ 0x52, 0x55, 0x4a, 0xff, 0x52, 0x55, 0x4a, 0xff,
+ 0x73, 0x74, 0x71, 0xff, 0x73, 0x74, 0x70, 0xff,
+ 0x5b, 0x5d, 0x5b, 0xff, 0x73, 0x74, 0x70, 0xff,
+ 0x4a, 0x55, 0x50, 0xff, 0x4a, 0x55, 0x4f, 0xff,
+ 0x4a, 0x55, 0x50, 0xff, 0x4a, 0x55, 0x4f, 0xff,
+ 0x32, 0x3d, 0x3a, 0xff, 0x36, 0x4f, 0x4a, 0xff,
+ 0x34, 0x46, 0x42, 0xff, 0x36, 0x4f, 0x4a, 0xff,
+ 0x3a, 0x55, 0x52, 0xff, 0x39, 0x55, 0x52, 0xff,
+ 0x1e, 0x27, 0x26, 0xff, 0x10, 0x10, 0x10, 0xff,
+ 0x2f, 0x3d, 0x37, 0xff, 0x2e, 0x3c, 0x36, 0xff,
+ 0x3a, 0x51, 0x4a, 0xff, 0x39, 0x50, 0x4a, 0xff,
+ 0x42, 0x59, 0x5b, 0xff, 0x41, 0x59, 0x5a, 0xff,
+ 0x42, 0x59, 0x5b, 0xff, 0x36, 0x47, 0x47, 0xff,
+ 0x1e, 0x23, 0x24, 0xff, 0x1e, 0x23, 0x23, 0xff,
+ 0x1e, 0x23, 0x24, 0xff, 0x10, 0x0c, 0x10, 0xff,
+ 0x08, 0x0c, 0x08, 0xff, 0x16, 0x1d, 0x18, 0xff,
+ 0x08, 0x0c, 0x08, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x1e, 0x1d, 0x1e, 0xff,
+ 0x11, 0x14, 0x13, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x10, 0x14, 0x13, 0xff,
+ 0x19, 0x29, 0x19, 0xff, 0x3c, 0x43, 0x42, 0xff,
+ 0x3d, 0x44, 0x42, 0xff, 0x3c, 0x43, 0x42, 0xff,
+ 0x2a, 0x39, 0x32, 0xff, 0x29, 0x39, 0x31, 0xff,
+ 0x29, 0x39, 0x32, 0xff, 0x29, 0x39, 0x31, 0xff,
+ 0x5b, 0x62, 0x5b, 0xff, 0xa7, 0xaa, 0xa2, 0xff,
+ 0xa8, 0xaa, 0xa2, 0xff, 0xa7, 0xaa, 0xa2, 0xff,
+ 0xb5, 0xb7, 0x95, 0xff, 0x63, 0x71, 0x4a, 0xff,
+ 0x63, 0x72, 0x4a, 0xff, 0x63, 0x71, 0x4a, 0xff,
+ 0x48, 0x4f, 0x45, 0xff, 0x21, 0x28, 0x21, 0xff,
+ 0x48, 0x4f, 0x45, 0xff, 0x94, 0x9a, 0x8c, 0xff,
+ 0x7c, 0x82, 0x79, 0xff, 0x63, 0x69, 0x5a, 0xff,
+ 0x63, 0x6a, 0x5b, 0xff, 0x63, 0x69, 0x5a, 0xff,
+ 0x6e, 0x72, 0x71, 0xff, 0x94, 0x9a, 0x9c, 0xff,
+ 0x5b, 0x5d, 0x5b, 0xff, 0x81, 0x85, 0x86, 0xff,
+ 0x76, 0x81, 0x7c, 0xff, 0x58, 0x62, 0x5a, 0xff,
+ 0x3a, 0x45, 0x3a, 0xff, 0x39, 0x45, 0x39, 0xff,
+ 0x4b, 0x5c, 0x5b, 0xff, 0x5a, 0x6b, 0x6b, 0xff,
+ 0x5b, 0x6b, 0x6b, 0xff, 0x39, 0x4d, 0x4a, 0xff,
+ 0x3a, 0x49, 0x53, 0xff, 0x2c, 0x35, 0x3a, 0xff,
+ 0x11, 0x0c, 0x09, 0xff, 0x1e, 0x20, 0x21, 0xff,
+ 0x3a, 0x44, 0x48, 0xff, 0x42, 0x52, 0x55, 0xff,
+ 0x42, 0x53, 0x55, 0xff, 0x39, 0x43, 0x47, 0xff,
+ 0x35, 0x4c, 0x48, 0xff, 0x47, 0x5e, 0x5d, 0xff,
+ 0x48, 0x5f, 0x5e, 0xff, 0x21, 0x39, 0x31, 0xff,
+ 0x2a, 0x3f, 0x40, 0xff, 0x29, 0x3e, 0x3f, 0xff,
+ 0x19, 0x23, 0x24, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x16, 0x16, 0x16, 0xff, 0x0b, 0x0b, 0x0b, 0xff,
+ 0x16, 0x16, 0x16, 0xff, 0x16, 0x15, 0x16, 0xff,
+ 0x09, 0x09, 0x09, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x19, 0x16, 0x14, 0xff, 0x10, 0x0f, 0x0e, 0xff,
+ 0x09, 0x0d, 0x09, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x09, 0x0c, 0x09, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x84, 0x7a, 0x94, 0xff, 0x83, 0x79, 0x94, 0xff,
+ 0x60, 0x5f, 0x6b, 0xff, 0x3c, 0x43, 0x42, 0xff,
+ 0x29, 0x39, 0x31, 0xff, 0x29, 0x38, 0x31, 0xff,
+ 0x3f, 0x4c, 0x48, 0xff, 0x3f, 0x4b, 0x47, 0xff,
+ 0x5b, 0x61, 0x5b, 0xff, 0xa7, 0xaa, 0xa1, 0xff,
+ 0xa7, 0xaa, 0xa2, 0xff, 0xa7, 0xaa, 0xa1, 0xff,
+ 0xb5, 0xb6, 0x94, 0xff, 0x62, 0x71, 0x4a, 0xff,
+ 0x63, 0x72, 0x4a, 0xff, 0x62, 0x71, 0x4a, 0xff,
+ 0x6e, 0x74, 0x68, 0xff, 0x20, 0x28, 0x20, 0xff,
+ 0x48, 0x4e, 0x45, 0xff, 0x94, 0x9a, 0x8c, 0xff,
+ 0x94, 0x9a, 0x97, 0xff, 0x94, 0x99, 0x96, 0xff,
+ 0x7c, 0x82, 0x79, 0xff, 0x62, 0x69, 0x5a, 0xff,
+ 0x5b, 0x5d, 0x5b, 0xff, 0x80, 0x85, 0x86, 0xff,
+ 0x94, 0x9a, 0x9d, 0xff, 0x94, 0x9a, 0x9c, 0xff,
+ 0x76, 0x80, 0x7b, 0xff, 0x75, 0x80, 0x7b, 0xff,
+ 0x58, 0x63, 0x5b, 0xff, 0x57, 0x62, 0x5a, 0xff,
+ 0x5b, 0x6b, 0x6b, 0xff, 0x5a, 0x6a, 0x6b, 0xff,
+ 0x5b, 0x6b, 0x6b, 0xff, 0x39, 0x4d, 0x4a, 0xff,
+ 0x3a, 0x49, 0x52, 0xff, 0x1e, 0x20, 0x20, 0xff,
+ 0x11, 0x0c, 0x08, 0xff, 0x1e, 0x20, 0x21, 0xff,
+ 0x31, 0x35, 0x3a, 0xff, 0x39, 0x43, 0x47, 0xff,
+ 0x42, 0x53, 0x55, 0xff, 0x4a, 0x61, 0x62, 0xff,
+ 0x47, 0x5f, 0x5d, 0xff, 0x47, 0x5e, 0x5d, 0xff,
+ 0x48, 0x5f, 0x5d, 0xff, 0x34, 0x4b, 0x47, 0xff,
+ 0x29, 0x3e, 0x3f, 0xff, 0x29, 0x3e, 0x3f, 0xff,
+ 0x19, 0x23, 0x24, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x00, 0x00, 0x00, 0xff, 0x0b, 0x0a, 0x0b, 0xff,
+ 0x21, 0x21, 0x21, 0xff, 0x0b, 0x0b, 0x0b, 0xff,
+ 0x11, 0x0f, 0x0e, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x08, 0x08, 0x08, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x08, 0x0c, 0x08, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x08, 0x0c, 0x08, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x84, 0x7a, 0x94, 0xff, 0x83, 0x79, 0x94, 0xff,
+ 0x84, 0x7a, 0x94, 0xff, 0x60, 0x5e, 0x6b, 0xff,
+ 0x6b, 0x72, 0x73, 0xff, 0x55, 0x5e, 0x5d, 0xff,
+ 0x3f, 0x4c, 0x48, 0xff, 0x55, 0x5e, 0x5d, 0xff,
+ 0x5b, 0x61, 0x5b, 0xff, 0x81, 0x85, 0x7e, 0xff,
+ 0x81, 0x86, 0x7f, 0xff, 0xce, 0xce, 0xc5, 0xff,
+ 0xb5, 0xb6, 0x94, 0xff, 0x62, 0x71, 0x4a, 0xff,
+ 0x63, 0x72, 0x4a, 0xff, 0x63, 0x71, 0x4a, 0xff,
+ 0x48, 0x4f, 0x45, 0xff, 0x21, 0x28, 0x21, 0xff,
+ 0x48, 0x4f, 0x45, 0xff, 0x47, 0x4e, 0x44, 0xff,
+ 0x7c, 0x82, 0x79, 0xff, 0xad, 0xb2, 0xb5, 0xff,
+ 0x7c, 0x82, 0x79, 0xff, 0x7b, 0x81, 0x79, 0xff,
+ 0x81, 0x86, 0x87, 0xff, 0x6d, 0x71, 0x70, 0xff,
+ 0x81, 0x86, 0x87, 0xff, 0x94, 0x9a, 0x9c, 0xff,
+ 0x94, 0x9e, 0x9d, 0xff, 0x76, 0x80, 0x7b, 0xff,
+ 0x76, 0x81, 0x7c, 0xff, 0x76, 0x80, 0x7b, 0xff,
+ 0x5b, 0x6b, 0x6b, 0xff, 0x5a, 0x6a, 0x6b, 0xff,
+ 0x4a, 0x5c, 0x5b, 0xff, 0x39, 0x4d, 0x4a, 0xff,
+ 0x2c, 0x35, 0x3a, 0xff, 0x2c, 0x34, 0x39, 0xff,
+ 0x1f, 0x21, 0x21, 0xff, 0x2c, 0x35, 0x39, 0xff,
+ 0x3a, 0x44, 0x48, 0xff, 0x42, 0x52, 0x55, 0xff,
+ 0x42, 0x53, 0x55, 0xff, 0x39, 0x43, 0x47, 0xff,
+ 0x5b, 0x72, 0x73, 0xff, 0x5a, 0x71, 0x73, 0xff,
+ 0x48, 0x5f, 0x5e, 0xff, 0x34, 0x4b, 0x47, 0xff,
+ 0x3a, 0x59, 0x5b, 0xff, 0x29, 0x3e, 0x3f, 0xff,
+ 0x2a, 0x3e, 0x3f, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x00, 0x00, 0x00, 0xff, 0x0b, 0x0b, 0x0b, 0xff,
+ 0x16, 0x16, 0x16, 0xff, 0x21, 0x20, 0x21, 0xff,
+ 0x11, 0x0f, 0x0e, 0xff, 0x18, 0x15, 0x13, 0xff,
+ 0x09, 0x09, 0x09, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x09, 0x0c, 0x09, 0xff, 0x18, 0x1f, 0x18, 0xff,
+ 0x11, 0x16, 0x11, 0xff, 0x10, 0x15, 0x10, 0xff,
+ 0x60, 0x5f, 0x6b, 0xff, 0x60, 0x5e, 0x6b, 0xff,
+ 0x60, 0x5e, 0x6b, 0xff, 0x5f, 0x5e, 0x6a, 0xff,
+ 0x6b, 0x71, 0x73, 0xff, 0x55, 0x5e, 0x5d, 0xff,
+ 0x3f, 0x4c, 0x47, 0xff, 0x55, 0x5e, 0x5d, 0xff,
+ 0xa7, 0xaa, 0xa2, 0xff, 0xa7, 0xaa, 0xa1, 0xff,
+ 0x81, 0x86, 0x7e, 0xff, 0xcd, 0xce, 0xc5, 0xff,
+ 0xb5, 0xb6, 0x94, 0xff, 0x62, 0x71, 0x4a, 0xff,
+ 0x63, 0x71, 0x4a, 0xff, 0x62, 0x71, 0x4a, 0xff,
+ 0x47, 0x4e, 0x45, 0xff, 0x21, 0x28, 0x21, 0xff,
+ 0x21, 0x29, 0x21, 0xff, 0x47, 0x4e, 0x44, 0xff,
+ 0x7c, 0x82, 0x79, 0xff, 0x7b, 0x81, 0x78, 0xff,
+ 0x7b, 0x82, 0x79, 0xff, 0x7b, 0x81, 0x78, 0xff,
+ 0x6e, 0x71, 0x71, 0xff, 0x81, 0x85, 0x86, 0xff,
+ 0x94, 0x9a, 0x9c, 0xff, 0x94, 0x99, 0x9c, 0xff,
+ 0x94, 0x9e, 0x9c, 0xff, 0x94, 0x9e, 0x9c, 0xff,
+ 0x94, 0x9e, 0x9c, 0xff, 0x94, 0x9d, 0x9c, 0xff,
+ 0x6b, 0x7a, 0x7c, 0xff, 0x6b, 0x79, 0x7b, 0xff,
+ 0x4a, 0x5c, 0x5b, 0xff, 0x5a, 0x6a, 0x6a, 0xff,
+ 0x3a, 0x49, 0x52, 0xff, 0x39, 0x49, 0x52, 0xff,
+ 0x3a, 0x49, 0x52, 0xff, 0x39, 0x48, 0x52, 0xff,
+ 0x42, 0x52, 0x55, 0xff, 0x39, 0x43, 0x47, 0xff,
+ 0x31, 0x35, 0x3a, 0xff, 0x31, 0x34, 0x39, 0xff,
+ 0x34, 0x4c, 0x47, 0xff, 0x47, 0x5e, 0x5d, 0xff,
+ 0x47, 0x5e, 0x5d, 0xff, 0x5a, 0x71, 0x73, 0xff,
+ 0x3a, 0x59, 0x5b, 0xff, 0x39, 0x59, 0x5a, 0xff,
+ 0x3a, 0x59, 0x5b, 0xff, 0x18, 0x23, 0x23, 0xff,
+ 0x0b, 0x0b, 0x0b, 0xff, 0x00, 0x00, 0x00, 0xff,
+ 0x16, 0x16, 0x16, 0xff, 0x20, 0x20, 0x20, 0xff,
+ 0x19, 0x16, 0x13, 0xff, 0x21, 0x1c, 0x18, 0xff,
+ 0x10, 0x0f, 0x0e, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x19, 0x1f, 0x19, 0xff, 0x21, 0x28, 0x21, 0xff,
+ 0x08, 0x0c, 0x08, 0xff, 0x08, 0x0c, 0x08, 0xff,
+ 0x74, 0x7a, 0x74, 0xff, 0x81, 0x86, 0x81, 0xff,
+ 0x81, 0x86, 0x81, 0xff, 0x81, 0x85, 0x81, 0xff,
+ 0x4b, 0x8a, 0x7c, 0xff, 0x7b, 0x97, 0x91, 0xff,
+ 0x7c, 0x97, 0x92, 0xff, 0x94, 0x9e, 0x9c, 0xff,
+ 0x8c, 0xa4, 0xa2, 0xff, 0xad, 0xb2, 0xb5, 0xff,
+ 0xad, 0xb2, 0xb5, 0xff, 0xad, 0xb2, 0xb5, 0xff,
+ 0x8c, 0x94, 0x8c, 0xff, 0x6b, 0x74, 0x6b, 0xff,
+ 0x6b, 0x74, 0x6b, 0xff, 0x6b, 0x74, 0x6b, 0xff,
+ 0x76, 0x81, 0x7c, 0xff, 0x5a, 0x65, 0x63, 0xff,
+ 0x76, 0x81, 0x7c, 0xff, 0x5a, 0x65, 0x63, 0xff,
+ 0x7c, 0x81, 0x84, 0xff, 0x63, 0x67, 0x6b, 0xff,
+ 0x63, 0x67, 0x6b, 0xff, 0x94, 0x9a, 0x9c, 0xff,
+ 0x53, 0x66, 0x6b, 0xff, 0x52, 0x65, 0x6b, 0xff,
+ 0x53, 0x66, 0x6b, 0xff, 0x52, 0x65, 0x6b, 0xff,
+ 0x63, 0x72, 0x7c, 0xff, 0x63, 0x71, 0x7b, 0xff,
+ 0x63, 0x72, 0x7c, 0xff, 0x63, 0x71, 0x7b, 0xff,
+ 0x55, 0x7a, 0x81, 0xff, 0x55, 0x79, 0x81, 0xff,
+ 0x55, 0x7a, 0x81, 0xff, 0x5a, 0x8e, 0x8c, 0xff,
+ 0x63, 0x92, 0x8c, 0xff, 0x58, 0x80, 0x84, 0xff,
+ 0x42, 0x5d, 0x74, 0xff, 0x42, 0x5d, 0x73, 0xff,
+ 0x32, 0x51, 0x5b, 0xff, 0x31, 0x51, 0x5a, 0xff,
+ 0x32, 0x51, 0x5b, 0xff, 0x31, 0x51, 0x5a, 0xff,
+ 0x42, 0x49, 0x53, 0xff, 0x42, 0x49, 0x52, 0xff,
+ 0x42, 0x49, 0x53, 0xff, 0x4f, 0x65, 0x65, 0xff,
+ 0x42, 0x4f, 0x53, 0xff, 0x42, 0x4e, 0x52, 0xff,
+ 0x19, 0x21, 0x29, 0xff, 0x19, 0x20, 0x29, 0xff,
+ 0x09, 0x11, 0x11, 0xff, 0x08, 0x10, 0x10, 0xff,
+ 0x09, 0x11, 0x11, 0xff, 0x08, 0x10, 0x10, 0xff,
+ 0x0e, 0x13, 0x11, 0xff, 0x0e, 0x13, 0x10, 0xff,
+ 0x0e, 0x13, 0x11, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x19, 0x29, 0x27, 0xff, 0x19, 0x28, 0x26, 0xff,
+ 0x19, 0x29, 0x27, 0xff, 0x00, 0x08, 0x08, 0xff,
+ 0x9c, 0x9e, 0x9c, 0xff, 0x9c, 0x9d, 0x9c, 0xff,
+ 0x9d, 0x9e, 0x9d, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0x63, 0x90, 0x86, 0xff, 0x7b, 0x97, 0x91, 0xff,
+ 0x7c, 0x97, 0x92, 0xff, 0x7b, 0x97, 0x91, 0xff,
+ 0x6b, 0x95, 0x8f, 0xff, 0x6b, 0x94, 0x8e, 0xff,
+ 0x6b, 0x95, 0x8f, 0xff, 0x6b, 0x94, 0x8e, 0xff,
+ 0x8c, 0x93, 0x8c, 0xff, 0xac, 0xb2, 0xac, 0xff,
+ 0x6b, 0x74, 0x6b, 0xff, 0x4a, 0x55, 0x4a, 0xff,
+ 0xad, 0xb6, 0xad, 0xff, 0xac, 0xb6, 0xac, 0xff,
+ 0xad, 0xb6, 0xad, 0xff, 0x76, 0x80, 0x7b, 0xff,
+ 0x7b, 0x80, 0x84, 0xff, 0x7b, 0x80, 0x83, 0xff,
+ 0x7c, 0x80, 0x84, 0xff, 0x94, 0x9a, 0x9c, 0xff,
+ 0x52, 0x65, 0x6b, 0xff, 0x1b, 0x29, 0x29, 0xff,
+ 0x1c, 0x2a, 0x29, 0xff, 0x1b, 0x2a, 0x29, 0xff,
+ 0x45, 0x52, 0x58, 0xff, 0x26, 0x33, 0x34, 0xff,
+ 0x45, 0x53, 0x58, 0xff, 0x44, 0x52, 0x57, 0xff,
+ 0x4a, 0x51, 0x6b, 0xff, 0x4a, 0x51, 0x6b, 0xff,
+ 0x50, 0x65, 0x76, 0xff, 0x55, 0x79, 0x81, 0xff,
+ 0x63, 0x92, 0x8c, 0xff, 0x62, 0x91, 0x8b, 0xff,
+ 0x58, 0x80, 0x84, 0xff, 0x57, 0x80, 0x83, 0xff,
+ 0x47, 0x6d, 0x6e, 0xff, 0x5d, 0x89, 0x80, 0xff,
+ 0x5d, 0x8a, 0x81, 0xff, 0x5d, 0x89, 0x81, 0xff,
+ 0x6b, 0x9e, 0x8c, 0xff, 0x5d, 0x81, 0x78, 0xff,
+ 0x5d, 0x82, 0x79, 0xff, 0x5d, 0x81, 0x78, 0xff,
+ 0x6b, 0x7c, 0x7b, 0xff, 0x41, 0x4e, 0x52, 0xff,
+ 0x6b, 0x7c, 0x7c, 0xff, 0x42, 0x4e, 0x52, 0xff,
+ 0x3f, 0x50, 0x50, 0xff, 0x08, 0x10, 0x10, 0xff,
+ 0x08, 0x10, 0x11, 0xff, 0x08, 0x10, 0x10, 0xff,
+ 0x0e, 0x13, 0x11, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x0e, 0x13, 0x11, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x19, 0x29, 0x26, 0xff, 0x00, 0x08, 0x08, 0xff,
+ 0x19, 0x29, 0x27, 0xff, 0x18, 0x28, 0x26, 0xff,
+ 0x9d, 0x9e, 0x9d, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0x9d, 0x9e, 0x9d, 0xff, 0x8e, 0x92, 0x8e, 0xff,
+ 0x63, 0x91, 0x87, 0xff, 0x62, 0x90, 0x86, 0xff,
+ 0x63, 0x91, 0x87, 0xff, 0x7b, 0x97, 0x91, 0xff,
+ 0x6b, 0x95, 0x8f, 0xff, 0x6b, 0x94, 0x8e, 0xff,
+ 0x4a, 0x86, 0x7c, 0xff, 0x6b, 0x94, 0x8e, 0xff,
+ 0xad, 0xb2, 0xad, 0xff, 0xad, 0xb2, 0xad, 0xff,
+ 0x6b, 0x74, 0x6b, 0xff, 0x4a, 0x55, 0x4a, 0xff,
+ 0x76, 0x80, 0x7c, 0xff, 0x76, 0x80, 0x7b, 0xff,
+ 0x92, 0x9c, 0x94, 0xff, 0x91, 0x9b, 0x94, 0xff,
+ 0x94, 0x9a, 0x9d, 0xff, 0x94, 0x9a, 0x9c, 0xff,
+ 0x63, 0x67, 0x6b, 0xff, 0x4a, 0x4d, 0x52, 0xff,
+ 0x53, 0x65, 0x6b, 0xff, 0x1b, 0x2a, 0x29, 0xff,
+ 0x00, 0x0d, 0x09, 0xff, 0x00, 0x0c, 0x08, 0xff,
+ 0x09, 0x15, 0x11, 0xff, 0x26, 0x33, 0x34, 0xff,
+ 0x27, 0x34, 0x35, 0xff, 0x44, 0x52, 0x58, 0xff,
+ 0x50, 0x65, 0x76, 0xff, 0x55, 0x79, 0x81, 0xff,
+ 0x50, 0x66, 0x76, 0xff, 0x4f, 0x65, 0x76, 0xff,
+ 0x4d, 0x6f, 0x7c, 0xff, 0x62, 0x91, 0x8c, 0xff,
+ 0x63, 0x92, 0x8c, 0xff, 0x63, 0x92, 0x8c, 0xff,
+ 0x73, 0xa6, 0x94, 0xff, 0x5d, 0x89, 0x81, 0xff,
+ 0x74, 0xa6, 0x94, 0xff, 0x5d, 0x8a, 0x81, 0xff,
+ 0x6b, 0x9e, 0x8c, 0xff, 0x6b, 0x9e, 0x8c, 0xff,
+ 0x6b, 0x9e, 0x8c, 0xff, 0x6b, 0x9e, 0x8c, 0xff,
+ 0x94, 0xaa, 0xa5, 0xff, 0x94, 0xaa, 0xa4, 0xff,
+ 0x94, 0xaa, 0xa5, 0xff, 0x94, 0xaa, 0xa4, 0xff,
+ 0xad, 0xcf, 0xce, 0xff, 0x3f, 0x4f, 0x4f, 0xff,
+ 0x09, 0x11, 0x11, 0xff, 0x08, 0x10, 0x10, 0xff,
+ 0x0e, 0x13, 0x11, 0xff, 0x0d, 0x13, 0x10, 0xff,
+ 0x0e, 0x13, 0x11, 0xff, 0x0e, 0x13, 0x10, 0xff,
+ 0x00, 0x08, 0x09, 0xff, 0x00, 0x08, 0x08, 0xff,
+ 0x32, 0x49, 0x45, 0xff, 0x31, 0x49, 0x44, 0xff,
+ 0x9c, 0x9e, 0x9c, 0xff, 0x9c, 0x9e, 0x9c, 0xff,
+ 0x8f, 0x92, 0x8f, 0xff, 0x80, 0x85, 0x80, 0xff,
+ 0x4a, 0x8a, 0x7c, 0xff, 0x4a, 0x89, 0x7b, 0xff,
+ 0x4a, 0x8a, 0x7b, 0xff, 0x4a, 0x89, 0x7b, 0xff,
+ 0x4a, 0x86, 0x7c, 0xff, 0x4a, 0x85, 0x7b, 0xff,
+ 0x4a, 0x86, 0x7b, 0xff, 0x8b, 0xa3, 0xa1, 0xff,
+ 0xad, 0xb2, 0xad, 0xff, 0x8b, 0x93, 0x8b, 0xff,
+ 0x8c, 0x93, 0x8c, 0xff, 0x6a, 0x74, 0x6a, 0xff,
+ 0x76, 0x80, 0x7c, 0xff, 0x76, 0x80, 0x7b, 0xff,
+ 0x76, 0x80, 0x7b, 0xff, 0x75, 0x80, 0x7b, 0xff,
+ 0x7c, 0x80, 0x84, 0xff, 0x62, 0x66, 0x6b, 0xff,
+ 0x63, 0x67, 0x6b, 0xff, 0x4a, 0x4c, 0x52, 0xff,
+ 0x37, 0x48, 0x4a, 0xff, 0x36, 0x47, 0x4a, 0xff,
+ 0x37, 0x48, 0x4a, 0xff, 0x52, 0x65, 0x6a, 0xff,
+ 0x27, 0x33, 0x34, 0xff, 0x44, 0x52, 0x57, 0xff,
+ 0x45, 0x52, 0x58, 0xff, 0x44, 0x52, 0x57, 0xff,
+ 0x55, 0x7a, 0x81, 0xff, 0x55, 0x79, 0x81, 0xff,
+ 0x55, 0x79, 0x81, 0xff, 0x55, 0x79, 0x80, 0xff,
+ 0x4d, 0x6f, 0x7c, 0xff, 0x57, 0x80, 0x83, 0xff,
+ 0x63, 0x92, 0x8c, 0xff, 0x62, 0x91, 0x8b, 0xff,
+ 0x5d, 0x8a, 0x81, 0xff, 0x73, 0xa6, 0x94, 0xff,
+ 0x73, 0xa6, 0x94, 0xff, 0x73, 0xa5, 0x94, 0xff,
+ 0x6b, 0x9e, 0x8c, 0xff, 0x6b, 0x9e, 0x8b, 0xff,
+ 0x6b, 0x9e, 0x8c, 0xff, 0x6a, 0x9d, 0x8b, 0xff,
+ 0x94, 0xaa, 0xa5, 0xff, 0x94, 0xaa, 0xa4, 0xff,
+ 0x94, 0xaa, 0xa5, 0xff, 0x6a, 0x7c, 0x7b, 0xff,
+ 0x76, 0x8f, 0x8f, 0xff, 0x76, 0x8f, 0x8e, 0xff,
+ 0x3f, 0x50, 0x50, 0xff, 0x08, 0x10, 0x10, 0xff,
+ 0x0e, 0x13, 0x11, 0xff, 0x08, 0x08, 0x08, 0xff,
+ 0x0e, 0x13, 0x10, 0xff, 0x18, 0x28, 0x20, 0xff,
+ 0x32, 0x49, 0x45, 0xff, 0x31, 0x49, 0x44, 0xff,
+ 0x4a, 0x69, 0x63, 0xff, 0x4a, 0x69, 0x62, 0xff,
+ 0x4b, 0x86, 0x74, 0xff, 0x4a, 0x86, 0x73, 0xff,
+ 0x4a, 0x86, 0x74, 0xff, 0x4a, 0x85, 0x73, 0xff,
+ 0x42, 0x82, 0x7c, 0xff, 0x42, 0x81, 0x7b, 0xff,
+ 0x42, 0x82, 0x7c, 0xff, 0x42, 0x81, 0x7b, 0xff,
+ 0x4b, 0x81, 0x7c, 0xff, 0x4a, 0x80, 0x7b, 0xff,
+ 0x4a, 0x81, 0x7c, 0xff, 0x39, 0x6d, 0x6b, 0xff,
+ 0x6b, 0x72, 0x74, 0xff, 0x55, 0x58, 0x58, 0xff,
+ 0x55, 0x58, 0x58, 0xff, 0x55, 0x58, 0x58, 0xff,
+ 0x4b, 0x5e, 0x60, 0xff, 0x3a, 0x41, 0x45, 0xff,
+ 0x3a, 0x41, 0x45, 0xff, 0x39, 0x41, 0x44, 0xff,
+ 0x2a, 0x31, 0x32, 0xff, 0x29, 0x31, 0x31, 0xff,
+ 0x3a, 0x49, 0x48, 0xff, 0x5a, 0x79, 0x73, 0xff,
+ 0x5b, 0x96, 0x8c, 0xff, 0x5a, 0x96, 0x8c, 0xff,
+ 0x5b, 0x96, 0x8c, 0xff, 0x5a, 0x96, 0x8c, 0xff,
+ 0x5e, 0x92, 0x8a, 0xff, 0x5d, 0x92, 0x89, 0xff,
+ 0x37, 0x6a, 0x66, 0xff, 0x10, 0x41, 0x42, 0xff,
+ 0x42, 0x7e, 0x74, 0xff, 0x55, 0x8a, 0x81, 0xff,
+ 0x55, 0x8a, 0x81, 0xff, 0x55, 0x89, 0x81, 0xff,
+ 0x5b, 0x82, 0x74, 0xff, 0x5d, 0x8e, 0x7e, 0xff,
+ 0x60, 0x9a, 0x89, 0xff, 0x63, 0xa6, 0x94, 0xff,
+ 0x95, 0xaa, 0xa5, 0xff, 0x94, 0xaa, 0xa4, 0xff,
+ 0x7c, 0xa5, 0x9a, 0xff, 0x94, 0xaa, 0xa4, 0xff,
+ 0x84, 0xa6, 0x9d, 0xff, 0x73, 0xa1, 0x94, 0xff,
+ 0x63, 0x9c, 0x8c, 0xff, 0x63, 0x9b, 0x8c, 0xff,
+ 0x74, 0xa2, 0x95, 0xff, 0x68, 0x9c, 0x8f, 0xff,
+ 0x69, 0x9d, 0x8f, 0xff, 0x5d, 0x97, 0x89, 0xff,
+ 0x5e, 0x99, 0x87, 0xff, 0x5d, 0x98, 0x86, 0xff,
+ 0x5e, 0x99, 0x87, 0xff, 0x52, 0x8e, 0x7b, 0xff,
+ 0x42, 0x7a, 0x6b, 0xff, 0x42, 0x79, 0x6b, 0xff,
+ 0x42, 0x7a, 0x6b, 0xff, 0x58, 0x94, 0x81, 0xff,
+ 0x5e, 0x96, 0x87, 0xff, 0x5d, 0x96, 0x86, 0xff,
+ 0x5e, 0x96, 0x87, 0xff, 0x58, 0x92, 0x81, 0xff,
+ 0x4a, 0x86, 0x73, 0xff, 0x4a, 0x85, 0x73, 0xff,
+ 0x4a, 0x86, 0x73, 0xff, 0x39, 0x72, 0x62, 0xff,
+ 0x42, 0x82, 0x7b, 0xff, 0x34, 0x72, 0x6b, 0xff,
+ 0x34, 0x73, 0x6b, 0xff, 0x34, 0x72, 0x6b, 0xff,
+ 0x42, 0x77, 0x73, 0xff, 0x41, 0x76, 0x73, 0xff,
+ 0x4a, 0x80, 0x7c, 0xff, 0x39, 0x6d, 0x6b, 0xff,
+ 0x3f, 0x3e, 0x3c, 0xff, 0x29, 0x24, 0x20, 0xff,
+ 0x29, 0x25, 0x21, 0xff, 0x29, 0x24, 0x21, 0xff,
+ 0x29, 0x25, 0x29, 0xff, 0x29, 0x24, 0x29, 0xff,
+ 0x4a, 0x5d, 0x60, 0xff, 0x29, 0x24, 0x29, 0xff,
+ 0x29, 0x31, 0x31, 0xff, 0x29, 0x30, 0x31, 0xff,
+ 0x4a, 0x61, 0x5d, 0xff, 0x5a, 0x79, 0x73, 0xff,
+ 0x42, 0x70, 0x68, 0xff, 0x29, 0x4a, 0x44, 0xff,
+ 0x5b, 0x96, 0x8c, 0xff, 0x5a, 0x95, 0x8c, 0xff,
+ 0x5d, 0x92, 0x89, 0xff, 0x5d, 0x91, 0x89, 0xff,
+ 0x5d, 0x92, 0x89, 0xff, 0x37, 0x69, 0x65, 0xff,
+ 0x42, 0x7e, 0x73, 0xff, 0x7b, 0xa1, 0x9c, 0xff,
+ 0x7c, 0xa2, 0x9d, 0xff, 0x68, 0x95, 0x8e, 0xff,
+ 0x60, 0x9a, 0x89, 0xff, 0x60, 0x99, 0x89, 0xff,
+ 0x60, 0x9a, 0x89, 0xff, 0x60, 0x9a, 0x89, 0xff,
+ 0x7b, 0xa5, 0x9a, 0xff, 0x62, 0x9f, 0x8e, 0xff,
+ 0x63, 0x9f, 0x8f, 0xff, 0x62, 0x9f, 0x8e, 0xff,
+ 0x73, 0xa1, 0x94, 0xff, 0x73, 0xa0, 0x94, 0xff,
+ 0x73, 0xa1, 0x94, 0xff, 0x73, 0xa0, 0x94, 0xff,
+ 0x68, 0x9d, 0x8f, 0xff, 0x5d, 0x97, 0x89, 0xff,
+ 0x52, 0x92, 0x84, 0xff, 0x52, 0x91, 0x83, 0xff,
+ 0x52, 0x8e, 0x7b, 0xff, 0x57, 0x93, 0x80, 0xff,
+ 0x5d, 0x99, 0x87, 0xff, 0x5d, 0x98, 0x86, 0xff,
+ 0x58, 0x95, 0x81, 0xff, 0x62, 0xa1, 0x8b, 0xff,
+ 0x58, 0x95, 0x81, 0xff, 0x57, 0x94, 0x81, 0xff,
+ 0x5d, 0x96, 0x86, 0xff, 0x5d, 0x95, 0x86, 0xff,
+ 0x5d, 0x96, 0x87, 0xff, 0x5d, 0x95, 0x86, 0xff,
+ 0x3a, 0x73, 0x63, 0xff, 0x29, 0x60, 0x52, 0xff,
+ 0x2a, 0x60, 0x53, 0xff, 0x29, 0x60, 0x52, 0xff,
+ 0x27, 0x64, 0x5b, 0xff, 0x26, 0x64, 0x5a, 0xff,
+ 0x35, 0x73, 0x6b, 0xff, 0x34, 0x73, 0x6b, 0xff,
+ 0x42, 0x77, 0x73, 0xff, 0x42, 0x77, 0x73, 0xff,
+ 0x42, 0x77, 0x74, 0xff, 0x52, 0x8a, 0x84, 0xff,
+ 0x55, 0x58, 0x58, 0xff, 0x3f, 0x3e, 0x3c, 0xff,
+ 0x55, 0x58, 0x58, 0xff, 0x55, 0x58, 0x58, 0xff,
+ 0x4a, 0x5d, 0x60, 0xff, 0x4a, 0x5d, 0x60, 0xff,
+ 0x4a, 0x5e, 0x60, 0xff, 0x4a, 0x5d, 0x60, 0xff,
+ 0x5b, 0x7a, 0x73, 0xff, 0x5a, 0x79, 0x73, 0xff,
+ 0x5b, 0x7a, 0x74, 0xff, 0x29, 0x30, 0x31, 0xff,
+ 0x11, 0x25, 0x21, 0xff, 0x29, 0x4a, 0x44, 0xff,
+ 0x5b, 0x96, 0x8c, 0xff, 0x5a, 0x96, 0x8c, 0xff,
+ 0x5e, 0x92, 0x89, 0xff, 0x5d, 0x91, 0x89, 0xff,
+ 0x5e, 0x92, 0x8a, 0xff, 0x84, 0xba, 0xad, 0xff,
+ 0x7c, 0xa2, 0x9d, 0xff, 0x68, 0x96, 0x8e, 0xff,
+ 0x69, 0x96, 0x8f, 0xff, 0x68, 0x96, 0x8e, 0xff,
+ 0x60, 0x9a, 0x89, 0xff, 0x60, 0x9a, 0x89, 0xff,
+ 0x60, 0x9a, 0x8a, 0xff, 0x60, 0x9a, 0x89, 0xff,
+ 0x4a, 0x9a, 0x84, 0xff, 0x7b, 0xa4, 0x99, 0xff,
+ 0x7c, 0xa5, 0x9a, 0xff, 0x7b, 0xa5, 0x99, 0xff,
+ 0x73, 0xa1, 0x94, 0xff, 0x62, 0x9b, 0x8c, 0xff,
+ 0x63, 0x9c, 0x8c, 0xff, 0x52, 0x96, 0x84, 0xff,
+ 0x53, 0x92, 0x84, 0xff, 0x5d, 0x97, 0x89, 0xff,
+ 0x5e, 0x98, 0x8a, 0xff, 0x5d, 0x97, 0x89, 0xff,
+ 0x63, 0x9e, 0x8c, 0xff, 0x62, 0x9e, 0x8c, 0xff,
+ 0x5e, 0x99, 0x87, 0xff, 0x5d, 0x98, 0x86, 0xff,
+ 0x58, 0x95, 0x81, 0xff, 0x62, 0xa2, 0x8c, 0xff,
+ 0x63, 0xa2, 0x8c, 0xff, 0x58, 0x94, 0x81, 0xff,
+ 0x5e, 0x96, 0x87, 0xff, 0x62, 0x9a, 0x8c, 0xff,
+ 0x5e, 0x96, 0x87, 0xff, 0x63, 0x9a, 0x8c, 0xff,
+ 0x29, 0x60, 0x52, 0xff, 0x18, 0x4d, 0x41, 0xff,
+ 0x29, 0x60, 0x52, 0xff, 0x29, 0x5f, 0x52, 0xff,
+ 0x19, 0x55, 0x4a, 0xff, 0x18, 0x55, 0x4a, 0xff,
+ 0x19, 0x55, 0x4a, 0xff, 0x18, 0x55, 0x4a, 0xff,
+ 0x3a, 0x6d, 0x6b, 0xff, 0x41, 0x76, 0x73, 0xff,
+ 0x4a, 0x80, 0x7b, 0xff, 0x41, 0x76, 0x73, 0xff,
+ 0x6b, 0x71, 0x73, 0xff, 0x6b, 0x71, 0x73, 0xff,
+ 0x6b, 0x71, 0x73, 0xff, 0x6a, 0x71, 0x73, 0xff,
+ 0x5b, 0x7a, 0x7c, 0xff, 0x5a, 0x79, 0x7b, 0xff,
+ 0x4a, 0x5d, 0x60, 0xff, 0x5a, 0x79, 0x7b, 0xff,
+ 0x5b, 0x7a, 0x73, 0xff, 0x5a, 0x79, 0x73, 0xff,
+ 0x5b, 0x79, 0x73, 0xff, 0x4a, 0x61, 0x5d, 0xff,
+ 0x42, 0x70, 0x68, 0xff, 0x5a, 0x95, 0x8b, 0xff,
+ 0x5b, 0x96, 0x8c, 0xff, 0x5a, 0x95, 0x8b, 0xff,
+ 0x5d, 0x92, 0x89, 0xff, 0x83, 0xba, 0xac, 0xff,
+ 0x5d, 0x92, 0x89, 0xff, 0x83, 0xba, 0xac, 0xff,
+ 0x68, 0x96, 0x8f, 0xff, 0x68, 0x95, 0x8e, 0xff,
+ 0x68, 0x96, 0x8f, 0xff, 0x68, 0x95, 0x8e, 0xff,
+ 0x60, 0x9a, 0x89, 0xff, 0x60, 0x99, 0x89, 0xff,
+ 0x63, 0xa6, 0x94, 0xff, 0x5f, 0x99, 0x89, 0xff,
+ 0x63, 0x9f, 0x8f, 0xff, 0x62, 0x9f, 0x8e, 0xff,
+ 0x63, 0x9f, 0x8f, 0xff, 0x4a, 0x99, 0x83, 0xff,
+ 0x52, 0x96, 0x84, 0xff, 0x52, 0x95, 0x83, 0xff,
+ 0x63, 0x9b, 0x8c, 0xff, 0x52, 0x95, 0x83, 0xff,
+ 0x5d, 0x97, 0x89, 0xff, 0x68, 0x9c, 0x8e, 0xff,
+ 0x68, 0x9d, 0x8f, 0xff, 0x68, 0x9c, 0x8e, 0xff,
+ 0x63, 0x9e, 0x8c, 0xff, 0x62, 0x9e, 0x8b, 0xff,
+ 0x5d, 0x98, 0x86, 0xff, 0x62, 0x9d, 0x8b, 0xff,
+ 0x58, 0x95, 0x81, 0xff, 0x57, 0x94, 0x81, 0xff,
+ 0x63, 0xa2, 0x8c, 0xff, 0x57, 0x94, 0x80, 0xff,
+ 0x5d, 0x96, 0x87, 0xff, 0x57, 0x91, 0x81, 0xff,
+ 0x58, 0x92, 0x81, 0xff, 0x57, 0x91, 0x80, 0xff,
+ 0x11, 0x45, 0x32, 0xff, 0x26, 0x52, 0x42, 0xff,
+ 0x27, 0x53, 0x42, 0xff, 0x10, 0x45, 0x31, 0xff,
+ 0x11, 0x41, 0x32, 0xff, 0x10, 0x41, 0x31, 0xff,
+ 0x2c, 0x57, 0x48, 0xff, 0x2c, 0x56, 0x47, 0xff,
+ 0x32, 0x63, 0x53, 0xff, 0x31, 0x62, 0x52, 0xff,
+ 0x19, 0x4d, 0x3a, 0xff, 0x19, 0x4d, 0x39, 0xff,
+ 0x32, 0x72, 0x63, 0xff, 0x31, 0x71, 0x63, 0xff,
+ 0x32, 0x72, 0x63, 0xff, 0x31, 0x71, 0x63, 0xff,
+ 0x32, 0x76, 0x63, 0xff, 0x31, 0x75, 0x63, 0xff,
+ 0x32, 0x76, 0x63, 0xff, 0x47, 0x83, 0x73, 0xff,
+ 0x5b, 0x92, 0x84, 0xff, 0x5a, 0x92, 0x84, 0xff,
+ 0x3f, 0x87, 0x74, 0xff, 0x4d, 0x8c, 0x7b, 0xff,
+ 0x42, 0x8e, 0x7c, 0xff, 0x3c, 0x8a, 0x76, 0xff,
+ 0x42, 0x8e, 0x7c, 0xff, 0x3c, 0x89, 0x76, 0xff,
+ 0x4b, 0x8a, 0x7c, 0xff, 0x4f, 0x92, 0x81, 0xff,
+ 0x53, 0x96, 0x84, 0xff, 0x52, 0x96, 0x83, 0xff,
+ 0x55, 0x8f, 0x81, 0xff, 0x5a, 0x9a, 0x8c, 0xff,
+ 0x5b, 0x9a, 0x8c, 0xff, 0x5a, 0x9a, 0x8c, 0xff,
+ 0x63, 0xa0, 0x8c, 0xff, 0x63, 0x9f, 0x8c, 0xff,
+ 0x63, 0xa0, 0x8c, 0xff, 0x5a, 0x98, 0x83, 0xff,
+ 0x5b, 0x95, 0x87, 0xff, 0x52, 0x8e, 0x84, 0xff,
+ 0x53, 0x8e, 0x84, 0xff, 0x52, 0x8e, 0x83, 0xff,
+ 0x5b, 0x96, 0x84, 0xff, 0x5a, 0x96, 0x84, 0xff,
+ 0x66, 0x9e, 0x89, 0xff, 0x65, 0x9e, 0x89, 0xff,
+ 0x66, 0x9e, 0x8a, 0xff, 0x65, 0x9e, 0x89, 0xff,
+ 0x66, 0x9e, 0x89, 0xff, 0x6b, 0xa2, 0x8c, 0xff,
+ 0x63, 0x9e, 0x8c, 0xff, 0x63, 0x9e, 0x8c, 0xff,
+ 0x63, 0x9e, 0x8c, 0xff, 0x5d, 0x98, 0x86, 0xff,
+ 0x5e, 0x99, 0x87, 0xff, 0x5d, 0x98, 0x86, 0xff,
+ 0x5e, 0x99, 0x87, 0xff, 0x5d, 0x98, 0x86, 0xff,
+ 0x55, 0x96, 0x81, 0xff, 0x4f, 0x92, 0x7e, 0xff,
+ 0x50, 0x92, 0x7e, 0xff, 0x4a, 0x8e, 0x7b, 0xff,
+ 0x3c, 0x60, 0x52, 0xff, 0x3c, 0x5f, 0x52, 0xff,
+ 0x27, 0x53, 0x42, 0xff, 0x26, 0x52, 0x42, 0xff,
+ 0x2c, 0x56, 0x47, 0xff, 0x2b, 0x56, 0x47, 0xff,
+ 0x2c, 0x57, 0x48, 0xff, 0x2c, 0x56, 0x47, 0xff,
+ 0x19, 0x4d, 0x3a, 0xff, 0x18, 0x4c, 0x39, 0xff,
+ 0x19, 0x4d, 0x3a, 0xff, 0x31, 0x62, 0x52, 0xff,
+ 0x31, 0x71, 0x63, 0xff, 0x78, 0xa1, 0x94, 0xff,
+ 0x79, 0xa2, 0x94, 0xff, 0x55, 0x89, 0x7b, 0xff,
+ 0x52, 0x8a, 0x7b, 0xff, 0x52, 0x89, 0x7b, 0xff,
+ 0x52, 0x8a, 0x7c, 0xff, 0x47, 0x83, 0x73, 0xff,
+ 0x4d, 0x8c, 0x7b, 0xff, 0x4c, 0x8c, 0x7b, 0xff,
+ 0x32, 0x82, 0x6b, 0xff, 0x31, 0x81, 0x6b, 0xff,
+ 0x37, 0x86, 0x71, 0xff, 0x31, 0x81, 0x6b, 0xff,
+ 0x3d, 0x8a, 0x76, 0xff, 0x37, 0x85, 0x70, 0xff,
+ 0x4a, 0x8a, 0x7b, 0xff, 0x4f, 0x91, 0x80, 0xff,
+ 0x50, 0x92, 0x81, 0xff, 0x52, 0x95, 0x83, 0xff,
+ 0x5b, 0x9a, 0x8c, 0xff, 0x5a, 0x99, 0x8b, 0xff,
+ 0x5b, 0x9a, 0x8c, 0xff, 0x5a, 0x9a, 0x8c, 0xff,
+ 0x5b, 0x99, 0x84, 0xff, 0x5a, 0x98, 0x83, 0xff,
+ 0x5b, 0x99, 0x84, 0xff, 0x52, 0x91, 0x7b, 0xff,
+ 0x52, 0x8e, 0x84, 0xff, 0x52, 0x8d, 0x83, 0xff,
+ 0x5b, 0x95, 0x87, 0xff, 0x6b, 0xa2, 0x8c, 0xff,
+ 0x6b, 0xa2, 0x8c, 0xff, 0x65, 0x9d, 0x89, 0xff,
+ 0x66, 0x9e, 0x89, 0xff, 0x65, 0x9e, 0x89, 0xff,
+ 0x66, 0x9e, 0x89, 0xff, 0x65, 0x9d, 0x89, 0xff,
+ 0x60, 0x9a, 0x87, 0xff, 0x65, 0x9e, 0x89, 0xff,
+ 0x5d, 0x99, 0x86, 0xff, 0x57, 0x93, 0x80, 0xff,
+ 0x63, 0x9e, 0x8c, 0xff, 0x62, 0x9e, 0x8c, 0xff,
+ 0x63, 0x9e, 0x8c, 0xff, 0x5d, 0x98, 0x86, 0xff,
+ 0x63, 0x9e, 0x8c, 0xff, 0x5d, 0x98, 0x86, 0xff,
+ 0x5b, 0x9a, 0x84, 0xff, 0x4f, 0x91, 0x7e, 0xff,
+ 0x4a, 0x8e, 0x7c, 0xff, 0x4f, 0x91, 0x7e, 0xff,
+ 0x11, 0x45, 0x32, 0xff, 0x26, 0x52, 0x42, 0xff,
+ 0x27, 0x53, 0x42, 0xff, 0x3c, 0x60, 0x52, 0xff,
+ 0x2c, 0x57, 0x48, 0xff, 0x2c, 0x56, 0x47, 0xff,
+ 0x48, 0x6c, 0x5e, 0xff, 0x63, 0x81, 0x73, 0xff,
+ 0x32, 0x63, 0x53, 0xff, 0x62, 0x8d, 0x83, 0xff,
+ 0x63, 0x8e, 0x84, 0xff, 0x4a, 0x78, 0x6b, 0xff,
+ 0x55, 0x8a, 0x7c, 0xff, 0x9c, 0xba, 0xad, 0xff,
+ 0x79, 0xa2, 0x94, 0xff, 0x55, 0x8a, 0x7b, 0xff,
+ 0x48, 0x83, 0x73, 0xff, 0x47, 0x83, 0x73, 0xff,
+ 0x53, 0x8a, 0x7c, 0xff, 0x3c, 0x7c, 0x6b, 0xff,
+ 0x32, 0x82, 0x6b, 0xff, 0x31, 0x81, 0x6b, 0xff,
+ 0x3f, 0x87, 0x74, 0xff, 0x3f, 0x87, 0x73, 0xff,
+ 0x32, 0x82, 0x6b, 0xff, 0x3c, 0x89, 0x76, 0xff,
+ 0x3d, 0x8a, 0x76, 0xff, 0x37, 0x85, 0x70, 0xff,
+ 0x4d, 0x8e, 0x7e, 0xff, 0x52, 0x96, 0x83, 0xff,
+ 0x50, 0x92, 0x81, 0xff, 0x52, 0x96, 0x84, 0xff,
+ 0x55, 0x8f, 0x81, 0xff, 0x55, 0x8f, 0x81, 0xff,
+ 0x53, 0x8a, 0x7c, 0xff, 0x58, 0x94, 0x86, 0xff,
+ 0x53, 0x92, 0x7c, 0xff, 0x52, 0x91, 0x7b, 0xff,
+ 0x5b, 0x99, 0x84, 0xff, 0x5a, 0x98, 0x84, 0xff,
+ 0x63, 0x9b, 0x89, 0xff, 0x6b, 0xa2, 0x8c, 0xff,
+ 0x6b, 0xa2, 0x8c, 0xff, 0x6b, 0xa2, 0x8c, 0xff,
+ 0x6b, 0xa2, 0x8c, 0xff, 0x6b, 0xa2, 0x8c, 0xff,
+ 0x66, 0x9e, 0x8a, 0xff, 0x65, 0x9e, 0x89, 0xff,
+ 0x60, 0x9a, 0x87, 0xff, 0x65, 0x9e, 0x89, 0xff,
+ 0x66, 0x9e, 0x8a, 0xff, 0x60, 0x9a, 0x86, 0xff,
+ 0x58, 0x93, 0x81, 0xff, 0x58, 0x93, 0x81, 0xff,
+ 0x5e, 0x99, 0x87, 0xff, 0x63, 0x9e, 0x8c, 0xff,
+ 0x63, 0x9e, 0x8c, 0xff, 0x5d, 0x98, 0x86, 0xff,
+ 0x5e, 0x99, 0x87, 0xff, 0x58, 0x93, 0x81, 0xff,
+ 0x55, 0x96, 0x81, 0xff, 0x4f, 0x91, 0x7e, 0xff,
+ 0x50, 0x92, 0x7f, 0xff, 0x4a, 0x8e, 0x7b, 0xff,
+ 0x52, 0x6d, 0x63, 0xff, 0x3c, 0x5f, 0x52, 0xff,
+ 0x52, 0x6d, 0x63, 0xff, 0x52, 0x6d, 0x62, 0xff,
+ 0x47, 0x6c, 0x5d, 0xff, 0x47, 0x6c, 0x5d, 0xff,
+ 0x63, 0x82, 0x73, 0xff, 0x62, 0x81, 0x73, 0xff,
+ 0x4a, 0x78, 0x6b, 0xff, 0x62, 0x8d, 0x83, 0xff,
+ 0x4a, 0x78, 0x6b, 0xff, 0x4a, 0x78, 0x6a, 0xff,
+ 0x55, 0x8a, 0x7c, 0xff, 0x55, 0x89, 0x7b, 0xff,
+ 0x31, 0x71, 0x63, 0xff, 0x55, 0x89, 0x7b, 0xff,
+ 0x47, 0x83, 0x73, 0xff, 0x47, 0x83, 0x73, 0xff,
+ 0x47, 0x83, 0x73, 0xff, 0x52, 0x89, 0x7b, 0xff,
+ 0x32, 0x82, 0x6b, 0xff, 0x31, 0x81, 0x6b, 0xff,
+ 0x3f, 0x87, 0x73, 0xff, 0x31, 0x81, 0x6a, 0xff,
+ 0x32, 0x82, 0x6b, 0xff, 0x3c, 0x89, 0x76, 0xff,
+ 0x37, 0x86, 0x70, 0xff, 0x36, 0x85, 0x70, 0xff,
+ 0x4d, 0x8e, 0x7e, 0xff, 0x4c, 0x8d, 0x7e, 0xff,
+ 0x4a, 0x8a, 0x7b, 0xff, 0x4a, 0x89, 0x7b, 0xff,
+ 0x52, 0x8a, 0x7c, 0xff, 0x52, 0x89, 0x7b, 0xff,
+ 0x58, 0x94, 0x86, 0xff, 0x57, 0x94, 0x86, 0xff,
+ 0x63, 0x9f, 0x8c, 0xff, 0x62, 0x9f, 0x8b, 0xff,
+ 0x63, 0x9f, 0x8c, 0xff, 0x6a, 0xa5, 0x94, 0xff,
+ 0x6b, 0xa2, 0x8c, 0xff, 0x6b, 0xa2, 0x8b, 0xff,
+ 0x6b, 0xa2, 0x8c, 0xff, 0x6a, 0xa1, 0x8b, 0xff,
+ 0x6b, 0xa2, 0x8c, 0xff, 0x6b, 0xa2, 0x8b, 0xff,
+ 0x60, 0x9a, 0x86, 0xff, 0x5a, 0x95, 0x83, 0xff,
+ 0x60, 0x9a, 0x87, 0xff, 0x65, 0x9e, 0x89, 0xff,
+ 0x5b, 0x96, 0x84, 0xff, 0x5a, 0x95, 0x83, 0xff,
+ 0x58, 0x93, 0x81, 0xff, 0x57, 0x93, 0x81, 0xff,
+ 0x52, 0x8e, 0x7b, 0xff, 0x5d, 0x98, 0x86, 0xff,
+ 0x58, 0x93, 0x81, 0xff, 0x52, 0x8d, 0x7b, 0xff,
+ 0x58, 0x93, 0x81, 0xff, 0x57, 0x93, 0x80, 0xff,
+ 0x55, 0x96, 0x81, 0xff, 0x4f, 0x91, 0x7e, 0xff,
+ 0x4a, 0x8e, 0x7b, 0xff, 0x4a, 0x8d, 0x7b, 0xff,
+ 0x4b, 0x7e, 0x74, 0xff, 0x34, 0x70, 0x60, 0xff,
+ 0x1f, 0x63, 0x4d, 0xff, 0x08, 0x55, 0x39, 0xff,
+ 0x21, 0x62, 0x4b, 0xff, 0x29, 0x6d, 0x58, 0xff,
+ 0x32, 0x7a, 0x66, 0xff, 0x31, 0x79, 0x65, 0xff,
+ 0x32, 0x79, 0x69, 0xff, 0x42, 0x86, 0x73, 0xff,
+ 0x3a, 0x7f, 0x6e, 0xff, 0x42, 0x85, 0x73, 0xff,
+ 0x42, 0x86, 0x74, 0xff, 0x42, 0x86, 0x73, 0xff,
+ 0x42, 0x86, 0x74, 0xff, 0x42, 0x85, 0x73, 0xff,
+ 0x45, 0x85, 0x76, 0xff, 0x4a, 0x8a, 0x7b, 0xff,
+ 0x4a, 0x8a, 0x7c, 0xff, 0x3f, 0x7f, 0x70, 0xff,
+ 0x42, 0x81, 0x76, 0xff, 0x4a, 0x87, 0x79, 0xff,
+ 0x53, 0x8e, 0x7c, 0xff, 0x4a, 0x87, 0x78, 0xff,
+ 0x4b, 0x8b, 0x79, 0xff, 0x4a, 0x8b, 0x79, 0xff,
+ 0x42, 0x86, 0x74, 0xff, 0x42, 0x85, 0x73, 0xff,
+ 0x53, 0x8f, 0x7f, 0xff, 0x4a, 0x88, 0x79, 0xff,
+ 0x42, 0x82, 0x74, 0xff, 0x4a, 0x88, 0x78, 0xff,
+ 0x53, 0x8e, 0x7c, 0xff, 0x52, 0x8e, 0x7b, 0xff,
+ 0x5b, 0x93, 0x81, 0xff, 0x63, 0x98, 0x86, 0xff,
+ 0x6b, 0x9d, 0x8a, 0xff, 0x6b, 0x9c, 0x89, 0xff,
+ 0x6b, 0x9d, 0x89, 0xff, 0x73, 0xa2, 0x8c, 0xff,
+ 0x69, 0x9e, 0x8a, 0xff, 0x6b, 0xa2, 0x8c, 0xff,
+ 0x6b, 0xa2, 0x8c, 0xff, 0x6b, 0xa2, 0x8c, 0xff,
+ 0x71, 0xa2, 0x8f, 0xff, 0x70, 0xa2, 0x8f, 0xff,
+ 0x71, 0xa2, 0x8f, 0xff, 0x65, 0x9e, 0x89, 0xff,
+ 0x63, 0x98, 0x87, 0xff, 0x63, 0x97, 0x86, 0xff,
+ 0x63, 0x97, 0x87, 0xff, 0x63, 0x97, 0x86, 0xff,
+ 0x63, 0x9a, 0x8c, 0xff, 0x5a, 0x93, 0x84, 0xff,
+ 0x5b, 0x93, 0x84, 0xff, 0x52, 0x8c, 0x7b, 0xff,
+ 0x4d, 0x8a, 0x76, 0xff, 0x4d, 0x8a, 0x76, 0xff,
+ 0x53, 0x92, 0x7c, 0xff, 0x52, 0x92, 0x7b, 0xff,
+ 0x53, 0x8f, 0x76, 0xff, 0x52, 0x8f, 0x76, 0xff,
+ 0x53, 0x8f, 0x76, 0xff, 0x5a, 0x96, 0x7b, 0xff,
+ 0x34, 0x70, 0x60, 0xff, 0x1e, 0x62, 0x4c, 0xff,
+ 0x34, 0x70, 0x60, 0xff, 0x1e, 0x62, 0x4c, 0xff,
+ 0x31, 0x7a, 0x66, 0xff, 0x39, 0x85, 0x73, 0xff,
+ 0x32, 0x7a, 0x66, 0xff, 0x31, 0x79, 0x65, 0xff,
+ 0x42, 0x86, 0x73, 0xff, 0x41, 0x85, 0x73, 0xff,
+ 0x3a, 0x7f, 0x6e, 0xff, 0x39, 0x7f, 0x6d, 0xff,
+ 0x3f, 0x80, 0x71, 0xff, 0x3c, 0x7a, 0x6d, 0xff,
+ 0x3f, 0x80, 0x71, 0xff, 0x42, 0x85, 0x73, 0xff,
+ 0x45, 0x84, 0x76, 0xff, 0x44, 0x84, 0x75, 0xff,
+ 0x3f, 0x7f, 0x71, 0xff, 0x3f, 0x7f, 0x70, 0xff,
+ 0x42, 0x80, 0x76, 0xff, 0x4a, 0x87, 0x78, 0xff,
+ 0x4a, 0x87, 0x79, 0xff, 0x42, 0x80, 0x76, 0xff,
+ 0x4a, 0x8b, 0x79, 0xff, 0x52, 0x90, 0x7e, 0xff,
+ 0x4a, 0x8b, 0x79, 0xff, 0x4a, 0x8b, 0x78, 0xff,
+ 0x52, 0x8f, 0x7e, 0xff, 0x5a, 0x95, 0x83, 0xff,
+ 0x5b, 0x96, 0x84, 0xff, 0x52, 0x8f, 0x7e, 0xff,
+ 0x5b, 0x93, 0x81, 0xff, 0x6b, 0x9d, 0x8b, 0xff,
+ 0x63, 0x99, 0x87, 0xff, 0x62, 0x98, 0x86, 0xff,
+ 0x6b, 0x9d, 0x89, 0xff, 0x73, 0xa1, 0x8b, 0xff,
+ 0x6b, 0x9d, 0x89, 0xff, 0x73, 0xa2, 0x8c, 0xff,
+ 0x66, 0x9a, 0x86, 0xff, 0x68, 0x9d, 0x89, 0xff,
+ 0x68, 0x9e, 0x89, 0xff, 0x6b, 0xa2, 0x8c, 0xff,
+ 0x66, 0x9e, 0x89, 0xff, 0x7b, 0xa6, 0x94, 0xff,
+ 0x71, 0xa2, 0x8f, 0xff, 0x5a, 0x9a, 0x83, 0xff,
+ 0x63, 0x97, 0x86, 0xff, 0x62, 0x97, 0x86, 0xff,
+ 0x63, 0x97, 0x87, 0xff, 0x52, 0x89, 0x7b, 0xff,
+ 0x5b, 0x93, 0x84, 0xff, 0x62, 0x99, 0x8b, 0xff,
+ 0x5b, 0x93, 0x84, 0xff, 0x4a, 0x85, 0x73, 0xff,
+ 0x4d, 0x8a, 0x76, 0xff, 0x52, 0x91, 0x7b, 0xff,
+ 0x52, 0x92, 0x7c, 0xff, 0x4c, 0x89, 0x76, 0xff,
+ 0x52, 0x8f, 0x76, 0xff, 0x52, 0x8f, 0x75, 0xff,
+ 0x42, 0x82, 0x6b, 0xff, 0x4a, 0x88, 0x70, 0xff,
+ 0x34, 0x70, 0x60, 0xff, 0x1e, 0x62, 0x4d, 0xff,
+ 0x1f, 0x63, 0x4d, 0xff, 0x1e, 0x62, 0x4d, 0xff,
+ 0x29, 0x6e, 0x58, 0xff, 0x31, 0x79, 0x65, 0xff,
+ 0x32, 0x7a, 0x66, 0xff, 0x39, 0x85, 0x73, 0xff,
+ 0x42, 0x86, 0x73, 0xff, 0x31, 0x78, 0x68, 0xff,
+ 0x32, 0x78, 0x69, 0xff, 0x39, 0x7f, 0x6e, 0xff,
+ 0x3d, 0x7b, 0x6e, 0xff, 0x3c, 0x7b, 0x6d, 0xff,
+ 0x3f, 0x81, 0x71, 0xff, 0x42, 0x85, 0x73, 0xff,
+ 0x3f, 0x7f, 0x71, 0xff, 0x39, 0x79, 0x6b, 0xff,
+ 0x3f, 0x7f, 0x71, 0xff, 0x44, 0x84, 0x76, 0xff,
+ 0x42, 0x80, 0x76, 0xff, 0x39, 0x79, 0x73, 0xff,
+ 0x42, 0x81, 0x76, 0xff, 0x42, 0x80, 0x76, 0xff,
+ 0x4a, 0x8b, 0x79, 0xff, 0x52, 0x90, 0x7e, 0xff,
+ 0x53, 0x91, 0x7f, 0xff, 0x52, 0x90, 0x7e, 0xff,
+ 0x53, 0x8f, 0x7e, 0xff, 0x5a, 0x96, 0x83, 0xff,
+ 0x53, 0x8f, 0x7f, 0xff, 0x52, 0x8f, 0x7e, 0xff,
+ 0x63, 0x99, 0x87, 0xff, 0x6b, 0x9e, 0x8c, 0xff,
+ 0x63, 0x99, 0x87, 0xff, 0x6b, 0x9e, 0x8c, 0xff,
+ 0x63, 0x97, 0x87, 0xff, 0x6b, 0x9c, 0x89, 0xff,
+ 0x6b, 0x9d, 0x8a, 0xff, 0x63, 0x97, 0x86, 0xff,
+ 0x66, 0x9a, 0x87, 0xff, 0x68, 0x9e, 0x89, 0xff,
+ 0x6b, 0xa2, 0x8c, 0xff, 0x68, 0x9e, 0x89, 0xff,
+ 0x66, 0x9e, 0x89, 0xff, 0x65, 0x9e, 0x89, 0xff,
+ 0x71, 0xa2, 0x8f, 0xff, 0x65, 0x9e, 0x89, 0xff,
+ 0x6b, 0x9e, 0x8c, 0xff, 0x62, 0x97, 0x86, 0xff,
+ 0x63, 0x98, 0x87, 0xff, 0x52, 0x8a, 0x7b, 0xff,
+ 0x53, 0x8d, 0x7c, 0xff, 0x62, 0x9a, 0x8c, 0xff,
+ 0x63, 0x9a, 0x8c, 0xff, 0x4a, 0x85, 0x73, 0xff,
+ 0x4d, 0x8a, 0x76, 0xff, 0x4f, 0x8d, 0x78, 0xff,
+ 0x4d, 0x8a, 0x76, 0xff, 0x52, 0x92, 0x7b, 0xff,
+ 0x5b, 0x96, 0x7c, 0xff, 0x52, 0x8f, 0x76, 0xff,
+ 0x53, 0x8f, 0x76, 0xff, 0x4a, 0x88, 0x70, 0xff,
+ 0x34, 0x70, 0x60, 0xff, 0x08, 0x55, 0x39, 0xff,
+ 0x1e, 0x63, 0x4d, 0xff, 0x08, 0x55, 0x39, 0xff,
+ 0x21, 0x61, 0x4a, 0xff, 0x31, 0x79, 0x65, 0xff,
+ 0x31, 0x79, 0x65, 0xff, 0x31, 0x79, 0x65, 0xff,
+ 0x29, 0x71, 0x63, 0xff, 0x39, 0x7e, 0x6d, 0xff,
+ 0x3a, 0x7f, 0x6e, 0xff, 0x39, 0x7e, 0x6d, 0xff,
+ 0x3a, 0x76, 0x6b, 0xff, 0x3f, 0x80, 0x70, 0xff,
+ 0x3f, 0x80, 0x70, 0xff, 0x3f, 0x80, 0x70, 0xff,
+ 0x3f, 0x7f, 0x71, 0xff, 0x44, 0x84, 0x76, 0xff,
+ 0x45, 0x84, 0x76, 0xff, 0x3f, 0x7e, 0x70, 0xff,
+ 0x4a, 0x87, 0x79, 0xff, 0x41, 0x80, 0x76, 0xff,
+ 0x4a, 0x87, 0x79, 0xff, 0x52, 0x8d, 0x7b, 0xff,
+ 0x42, 0x86, 0x73, 0xff, 0x4a, 0x8b, 0x78, 0xff,
+ 0x52, 0x90, 0x7e, 0xff, 0x4a, 0x8a, 0x78, 0xff,
+ 0x4a, 0x88, 0x79, 0xff, 0x5a, 0x95, 0x83, 0xff,
+ 0x4a, 0x88, 0x79, 0xff, 0x5a, 0x95, 0x83, 0xff,
+ 0x63, 0x99, 0x87, 0xff, 0x5a, 0x93, 0x81, 0xff,
+ 0x63, 0x98, 0x86, 0xff, 0x6a, 0x9d, 0x8b, 0xff,
+ 0x63, 0x97, 0x87, 0xff, 0x62, 0x97, 0x86, 0xff,
+ 0x5b, 0x92, 0x84, 0xff, 0x5a, 0x91, 0x83, 0xff,
+ 0x63, 0x96, 0x84, 0xff, 0x68, 0x9e, 0x89, 0xff,
+ 0x68, 0x9e, 0x89, 0xff, 0x6a, 0xa1, 0x8b, 0xff,
+ 0x71, 0xa2, 0x8f, 0xff, 0x70, 0xa2, 0x8e, 0xff,
+ 0x65, 0x9e, 0x89, 0xff, 0x5a, 0x99, 0x83, 0xff,
+ 0x6b, 0x9e, 0x8c, 0xff, 0x62, 0x97, 0x86, 0xff,
+ 0x63, 0x97, 0x86, 0xff, 0x62, 0x97, 0x86, 0xff,
+ 0x52, 0x8c, 0x7c, 0xff, 0x62, 0x99, 0x8b, 0xff,
+ 0x63, 0x9a, 0x8c, 0xff, 0x4a, 0x85, 0x73, 0xff,
+ 0x50, 0x8e, 0x79, 0xff, 0x52, 0x91, 0x7b, 0xff,
+ 0x4d, 0x8a, 0x76, 0xff, 0x4a, 0x85, 0x73, 0xff,
+ 0x52, 0x8f, 0x76, 0xff, 0x52, 0x8f, 0x76, 0xff,
+ 0x52, 0x8f, 0x76, 0xff, 0x5a, 0x95, 0x7b, 0xff,
+ 0x1f, 0x5c, 0x48, 0xff, 0x1e, 0x5c, 0x47, 0xff,
+ 0x29, 0x6e, 0x5b, 0xff, 0x29, 0x6d, 0x5a, 0xff,
+ 0x2c, 0x72, 0x60, 0xff, 0x2c, 0x71, 0x60, 0xff,
+ 0x1f, 0x6a, 0x55, 0xff, 0x39, 0x79, 0x6b, 0xff,
+ 0x35, 0x7a, 0x66, 0xff, 0x3a, 0x7d, 0x6b, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x2e, 0x75, 0x60, 0xff,
+ 0x3a, 0x7f, 0x6b, 0xff, 0x31, 0x78, 0x63, 0xff,
+ 0x3a, 0x7f, 0x6b, 0xff, 0x42, 0x85, 0x73, 0xff,
+ 0x40, 0x82, 0x6e, 0xff, 0x3f, 0x81, 0x6e, 0xff,
+ 0x3f, 0x82, 0x6e, 0xff, 0x4a, 0x8e, 0x7b, 0xff,
+ 0x3d, 0x82, 0x6e, 0xff, 0x47, 0x8a, 0x79, 0xff,
+ 0x48, 0x8a, 0x79, 0xff, 0x3c, 0x81, 0x6e, 0xff,
+ 0x45, 0x87, 0x74, 0xff, 0x45, 0x87, 0x73, 0xff,
+ 0x5b, 0x9a, 0x84, 0xff, 0x4f, 0x90, 0x7b, 0xff,
+ 0x50, 0x8a, 0x79, 0xff, 0x5a, 0x96, 0x84, 0xff,
+ 0x50, 0x8a, 0x79, 0xff, 0x4f, 0x89, 0x78, 0xff,
+ 0x5b, 0x91, 0x7f, 0xff, 0x5a, 0x90, 0x7e, 0xff,
+ 0x63, 0x9a, 0x84, 0xff, 0x63, 0x9a, 0x83, 0xff,
+ 0x60, 0x96, 0x87, 0xff, 0x60, 0x96, 0x86, 0xff,
+ 0x60, 0x96, 0x87, 0xff, 0x60, 0x96, 0x86, 0xff,
+ 0x63, 0x96, 0x84, 0xff, 0x70, 0x9f, 0x8c, 0xff,
+ 0x71, 0xa0, 0x8c, 0xff, 0x70, 0x9f, 0x8c, 0xff,
+ 0x7c, 0xa8, 0x97, 0xff, 0x73, 0xa1, 0x91, 0xff,
+ 0x74, 0xa1, 0x92, 0xff, 0x6b, 0x9a, 0x8c, 0xff,
+ 0x66, 0x99, 0x8a, 0xff, 0x65, 0x98, 0x89, 0xff,
+ 0x66, 0x99, 0x89, 0xff, 0x60, 0x93, 0x86, 0xff,
+ 0x60, 0x94, 0x84, 0xff, 0x60, 0x93, 0x84, 0xff,
+ 0x60, 0x93, 0x84, 0xff, 0x60, 0x93, 0x83, 0xff,
+ 0x5b, 0x92, 0x84, 0xff, 0x55, 0x8c, 0x7e, 0xff,
+ 0x5b, 0x92, 0x84, 0xff, 0x4f, 0x87, 0x78, 0xff,
+ 0x53, 0x8f, 0x7c, 0xff, 0x5a, 0x96, 0x84, 0xff,
+ 0x4a, 0x89, 0x74, 0xff, 0x4a, 0x88, 0x73, 0xff,
+ 0x1e, 0x5c, 0x47, 0xff, 0x1e, 0x5b, 0x47, 0xff,
+ 0x29, 0x6e, 0x5b, 0xff, 0x29, 0x6d, 0x5a, 0xff,
+ 0x2c, 0x71, 0x60, 0xff, 0x1e, 0x69, 0x55, 0xff,
+ 0x11, 0x61, 0x4a, 0xff, 0x39, 0x79, 0x6b, 0xff,
+ 0x3a, 0x7e, 0x6b, 0xff, 0x2e, 0x75, 0x60, 0xff,
+ 0x29, 0x72, 0x5b, 0xff, 0x2e, 0x75, 0x60, 0xff,
+ 0x29, 0x71, 0x5b, 0xff, 0x39, 0x7e, 0x6b, 0xff,
+ 0x3a, 0x7f, 0x6b, 0xff, 0x42, 0x85, 0x73, 0xff,
+ 0x3f, 0x82, 0x6e, 0xff, 0x3f, 0x81, 0x6d, 0xff,
+ 0x3f, 0x82, 0x6e, 0xff, 0x4a, 0x8d, 0x7b, 0xff,
+ 0x47, 0x8a, 0x79, 0xff, 0x52, 0x91, 0x83, 0xff,
+ 0x48, 0x8a, 0x79, 0xff, 0x31, 0x79, 0x62, 0xff,
+ 0x45, 0x87, 0x73, 0xff, 0x4f, 0x90, 0x7b, 0xff,
+ 0x5b, 0x9a, 0x84, 0xff, 0x4f, 0x90, 0x7b, 0xff,
+ 0x50, 0x8a, 0x79, 0xff, 0x5a, 0x95, 0x83, 0xff,
+ 0x5b, 0x96, 0x84, 0xff, 0x44, 0x7d, 0x6d, 0xff,
+ 0x63, 0x9a, 0x84, 0xff, 0x5a, 0x90, 0x7e, 0xff,
+ 0x5b, 0x91, 0x7e, 0xff, 0x62, 0x9a, 0x83, 0xff,
+ 0x6b, 0x9e, 0x8c, 0xff, 0x60, 0x95, 0x86, 0xff,
+ 0x5b, 0x92, 0x84, 0xff, 0x65, 0x9a, 0x89, 0xff,
+ 0x63, 0x96, 0x84, 0xff, 0x70, 0x9f, 0x8b, 0xff,
+ 0x71, 0x9f, 0x8c, 0xff, 0x7e, 0xa8, 0x94, 0xff,
+ 0x7b, 0xa7, 0x97, 0xff, 0x7b, 0xa7, 0x96, 0xff,
+ 0x73, 0xa1, 0x92, 0xff, 0x73, 0xa0, 0x91, 0xff,
+ 0x66, 0x99, 0x89, 0xff, 0x65, 0x98, 0x89, 0xff,
+ 0x5b, 0x8e, 0x84, 0xff, 0x60, 0x93, 0x86, 0xff,
+ 0x60, 0x93, 0x84, 0xff, 0x60, 0x93, 0x83, 0xff,
+ 0x6b, 0x9a, 0x8c, 0xff, 0x55, 0x8c, 0x7b, 0xff,
+ 0x50, 0x87, 0x79, 0xff, 0x55, 0x8c, 0x7e, 0xff,
+ 0x55, 0x8d, 0x7e, 0xff, 0x4f, 0x87, 0x78, 0xff,
+ 0x42, 0x82, 0x6b, 0xff, 0x4a, 0x88, 0x73, 0xff,
+ 0x4a, 0x88, 0x73, 0xff, 0x52, 0x8f, 0x7b, 0xff,
+ 0x1e, 0x5c, 0x48, 0xff, 0x1e, 0x5c, 0x47, 0xff,
+ 0x14, 0x4b, 0x35, 0xff, 0x1e, 0x5c, 0x47, 0xff,
+ 0x2c, 0x72, 0x60, 0xff, 0x2c, 0x71, 0x60, 0xff,
+ 0x1f, 0x6a, 0x55, 0xff, 0x2c, 0x71, 0x60, 0xff,
+ 0x34, 0x7a, 0x66, 0xff, 0x29, 0x71, 0x5a, 0xff,
+ 0x2a, 0x72, 0x5b, 0xff, 0x2f, 0x75, 0x60, 0xff,
+ 0x3a, 0x7f, 0x6b, 0xff, 0x31, 0x78, 0x62, 0xff,
+ 0x3a, 0x7f, 0x6b, 0xff, 0x39, 0x7f, 0x6b, 0xff,
+ 0x34, 0x76, 0x60, 0xff, 0x29, 0x69, 0x52, 0xff,
+ 0x3f, 0x82, 0x6e, 0xff, 0x3f, 0x81, 0x6e, 0xff,
+ 0x48, 0x8a, 0x79, 0xff, 0x52, 0x91, 0x83, 0xff,
+ 0x48, 0x8a, 0x79, 0xff, 0x3c, 0x81, 0x6e, 0xff,
+ 0x45, 0x87, 0x73, 0xff, 0x5a, 0x9a, 0x83, 0xff,
+ 0x5b, 0x9a, 0x84, 0xff, 0x4f, 0x90, 0x7b, 0xff,
+ 0x3a, 0x72, 0x63, 0xff, 0x44, 0x7d, 0x6d, 0xff,
+ 0x50, 0x8a, 0x79, 0xff, 0x4f, 0x8a, 0x79, 0xff,
+ 0x63, 0x9a, 0x84, 0xff, 0x52, 0x87, 0x78, 0xff,
+ 0x53, 0x87, 0x79, 0xff, 0x4a, 0x7d, 0x73, 0xff,
+ 0x60, 0x96, 0x87, 0xff, 0x60, 0x96, 0x86, 0xff,
+ 0x60, 0x96, 0x87, 0xff, 0x6b, 0x9e, 0x8c, 0xff,
+ 0x63, 0x96, 0x84, 0xff, 0x70, 0x9f, 0x8c, 0xff,
+ 0x7f, 0xa9, 0x94, 0xff, 0x7e, 0xa9, 0x94, 0xff,
+ 0x84, 0xae, 0x9d, 0xff, 0x73, 0xa0, 0x91, 0xff,
+ 0x74, 0xa1, 0x92, 0xff, 0x73, 0xa0, 0x91, 0xff,
+ 0x6b, 0x9e, 0x8c, 0xff, 0x6b, 0x9e, 0x8c, 0xff,
+ 0x60, 0x93, 0x87, 0xff, 0x5a, 0x8e, 0x84, 0xff,
+ 0x60, 0x93, 0x84, 0xff, 0x60, 0x93, 0x83, 0xff,
+ 0x55, 0x8d, 0x7c, 0xff, 0x55, 0x8c, 0x7b, 0xff,
+ 0x4a, 0x82, 0x73, 0xff, 0x55, 0x8c, 0x7e, 0xff,
+ 0x4a, 0x82, 0x74, 0xff, 0x55, 0x8c, 0x7e, 0xff,
+ 0x42, 0x82, 0x6b, 0xff, 0x4a, 0x88, 0x73, 0xff,
+ 0x4a, 0x89, 0x74, 0xff, 0x4a, 0x88, 0x73, 0xff,
+ 0x08, 0x39, 0x21, 0xff, 0x13, 0x4a, 0x34, 0xff,
+ 0x1e, 0x5c, 0x47, 0xff, 0x29, 0x6d, 0x5a, 0xff,
+ 0x2c, 0x71, 0x60, 0xff, 0x2c, 0x71, 0x60, 0xff,
+ 0x3a, 0x79, 0x6b, 0xff, 0x2b, 0x71, 0x5f, 0xff,
+ 0x2f, 0x76, 0x60, 0xff, 0x29, 0x71, 0x5a, 0xff,
+ 0x29, 0x71, 0x5b, 0xff, 0x34, 0x79, 0x65, 0xff,
+ 0x3a, 0x7f, 0x6b, 0xff, 0x31, 0x78, 0x62, 0xff,
+ 0x29, 0x71, 0x5b, 0xff, 0x31, 0x78, 0x62, 0xff,
+ 0x34, 0x76, 0x60, 0xff, 0x34, 0x75, 0x60, 0xff,
+ 0x3f, 0x82, 0x6e, 0xff, 0x34, 0x75, 0x5f, 0xff,
+ 0x3c, 0x82, 0x6e, 0xff, 0x52, 0x91, 0x83, 0xff,
+ 0x3c, 0x82, 0x6e, 0xff, 0x3c, 0x81, 0x6d, 0xff,
+ 0x45, 0x87, 0x73, 0xff, 0x4f, 0x90, 0x7b, 0xff,
+ 0x50, 0x90, 0x7b, 0xff, 0x39, 0x7d, 0x6a, 0xff,
+ 0x3a, 0x71, 0x63, 0xff, 0x44, 0x7d, 0x6d, 0xff,
+ 0x50, 0x8a, 0x79, 0xff, 0x4f, 0x89, 0x78, 0xff,
+ 0x52, 0x87, 0x79, 0xff, 0x52, 0x87, 0x78, 0xff,
+ 0x52, 0x87, 0x79, 0xff, 0x52, 0x86, 0x78, 0xff,
+ 0x5b, 0x92, 0x84, 0xff, 0x60, 0x95, 0x86, 0xff,
+ 0x60, 0x96, 0x86, 0xff, 0x65, 0x99, 0x89, 0xff,
+ 0x63, 0x96, 0x84, 0xff, 0x7e, 0xa8, 0x94, 0xff,
+ 0x7e, 0xa9, 0x94, 0xff, 0x8b, 0xb2, 0x9c, 0xff,
+ 0x84, 0xae, 0x9c, 0xff, 0x7b, 0xa7, 0x96, 0xff,
+ 0x73, 0xa1, 0x91, 0xff, 0x73, 0xa0, 0x91, 0xff,
+ 0x5b, 0x8e, 0x84, 0xff, 0x60, 0x93, 0x86, 0xff,
+ 0x60, 0x93, 0x86, 0xff, 0x65, 0x98, 0x89, 0xff,
+ 0x55, 0x8c, 0x7c, 0xff, 0x55, 0x8c, 0x7b, 0xff,
+ 0x4a, 0x86, 0x73, 0xff, 0x5f, 0x93, 0x83, 0xff,
+ 0x50, 0x87, 0x79, 0xff, 0x4f, 0x87, 0x78, 0xff,
+ 0x50, 0x87, 0x79, 0xff, 0x5a, 0x91, 0x83, 0xff,
+ 0x4a, 0x88, 0x73, 0xff, 0x4a, 0x88, 0x73, 0xff,
+ 0x52, 0x8f, 0x7b, 0xff, 0x41, 0x81, 0x6a, 0xff,
+ 0x11, 0x51, 0x3a, 0xff, 0x1e, 0x62, 0x4a, 0xff,
+ 0x2c, 0x74, 0x5b, 0xff, 0x2c, 0x74, 0x5a, 0xff,
+ 0x3a, 0x86, 0x74, 0xff, 0x31, 0x79, 0x65, 0xff,
+ 0x29, 0x6e, 0x58, 0xff, 0x21, 0x61, 0x4a, 0xff,
+ 0x2c, 0x70, 0x5e, 0xff, 0x37, 0x7f, 0x68, 0xff,
+ 0x37, 0x7f, 0x69, 0xff, 0x2c, 0x70, 0x5d, 0xff,
+ 0x2f, 0x76, 0x60, 0xff, 0x2f, 0x75, 0x60, 0xff,
+ 0x2f, 0x76, 0x60, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x42, 0x86, 0x74, 0xff, 0x31, 0x75, 0x5d, 0xff,
+ 0x29, 0x6e, 0x53, 0xff, 0x31, 0x75, 0x5d, 0xff,
+ 0x50, 0x8a, 0x7c, 0xff, 0x4f, 0x8a, 0x7b, 0xff,
+ 0x3d, 0x7a, 0x6b, 0xff, 0x4f, 0x89, 0x7b, 0xff,
+ 0x42, 0x89, 0x74, 0xff, 0x42, 0x88, 0x73, 0xff,
+ 0x42, 0x89, 0x74, 0xff, 0x4a, 0x8f, 0x7b, 0xff,
+ 0x42, 0x85, 0x71, 0xff, 0x42, 0x84, 0x70, 0xff,
+ 0x42, 0x85, 0x71, 0xff, 0x39, 0x7b, 0x65, 0xff,
+ 0x50, 0x8d, 0x7c, 0xff, 0x4f, 0x8c, 0x7b, 0xff,
+ 0x5b, 0x92, 0x84, 0xff, 0x44, 0x87, 0x73, 0xff,
+ 0x63, 0x98, 0x87, 0xff, 0x5a, 0x90, 0x81, 0xff,
+ 0x6b, 0x9e, 0x8c, 0xff, 0x63, 0x97, 0x86, 0xff,
+ 0x60, 0x95, 0x87, 0xff, 0x7b, 0xaa, 0x9c, 0xff,
+ 0x7c, 0xaa, 0x9d, 0xff, 0x60, 0x94, 0x86, 0xff,
+ 0x6b, 0x9a, 0x8c, 0xff, 0x6b, 0x9a, 0x8c, 0xff,
+ 0x6b, 0x9a, 0x8c, 0xff, 0x6b, 0x9a, 0x8c, 0xff,
+ 0x69, 0x99, 0x8a, 0xff, 0x5d, 0x8f, 0x7e, 0xff,
+ 0x69, 0x99, 0x89, 0xff, 0x5d, 0x8f, 0x7e, 0xff,
+ 0x60, 0x91, 0x81, 0xff, 0x6b, 0x9a, 0x8c, 0xff,
+ 0x55, 0x87, 0x76, 0xff, 0x55, 0x87, 0x76, 0xff,
+ 0x5b, 0x92, 0x7c, 0xff, 0x4d, 0x88, 0x73, 0xff,
+ 0x4d, 0x89, 0x74, 0xff, 0x4d, 0x88, 0x73, 0xff,
+ 0x4d, 0x89, 0x76, 0xff, 0x52, 0x92, 0x7b, 0xff,
+ 0x4d, 0x89, 0x76, 0xff, 0x47, 0x7f, 0x70, 0xff,
+ 0x2c, 0x74, 0x5b, 0xff, 0x39, 0x85, 0x6b, 0xff,
+ 0x2c, 0x74, 0x5b, 0xff, 0x2c, 0x74, 0x5a, 0xff,
+ 0x31, 0x7a, 0x66, 0xff, 0x31, 0x79, 0x65, 0xff,
+ 0x32, 0x7a, 0x66, 0xff, 0x29, 0x6d, 0x57, 0xff,
+ 0x37, 0x7f, 0x68, 0xff, 0x2b, 0x70, 0x5d, 0xff,
+ 0x37, 0x7f, 0x68, 0xff, 0x2c, 0x70, 0x5d, 0xff,
+ 0x3a, 0x82, 0x6b, 0xff, 0x23, 0x69, 0x55, 0xff,
+ 0x2f, 0x76, 0x60, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x3a, 0x7e, 0x68, 0xff, 0x31, 0x75, 0x5d, 0xff,
+ 0x29, 0x6e, 0x52, 0xff, 0x39, 0x7d, 0x68, 0xff,
+ 0x50, 0x8a, 0x7b, 0xff, 0x29, 0x69, 0x5a, 0xff,
+ 0x50, 0x8a, 0x7c, 0xff, 0x62, 0x9a, 0x8c, 0xff,
+ 0x4a, 0x8f, 0x7b, 0xff, 0x41, 0x88, 0x73, 0xff,
+ 0x42, 0x88, 0x73, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x42, 0x84, 0x71, 0xff, 0x39, 0x7a, 0x65, 0xff,
+ 0x3a, 0x7b, 0x66, 0xff, 0x42, 0x84, 0x70, 0xff,
+ 0x50, 0x8c, 0x7b, 0xff, 0x44, 0x87, 0x73, 0xff,
+ 0x45, 0x87, 0x73, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x5b, 0x90, 0x81, 0xff, 0x5a, 0x90, 0x80, 0xff,
+ 0x6b, 0x9e, 0x8c, 0xff, 0x62, 0x97, 0x86, 0xff,
+ 0x60, 0x95, 0x86, 0xff, 0x7b, 0xaa, 0x9c, 0xff,
+ 0x7c, 0xaa, 0x9d, 0xff, 0x29, 0x69, 0x5a, 0xff,
+ 0x29, 0x54, 0x45, 0xff, 0x4a, 0x76, 0x68, 0xff,
+ 0x4a, 0x77, 0x68, 0xff, 0x6b, 0x9a, 0x8c, 0xff,
+ 0x73, 0xa2, 0x94, 0xff, 0x68, 0x98, 0x89, 0xff,
+ 0x68, 0x99, 0x89, 0xff, 0x5d, 0x8f, 0x7e, 0xff,
+ 0x60, 0x90, 0x81, 0xff, 0x60, 0x90, 0x80, 0xff,
+ 0x60, 0x91, 0x81, 0xff, 0x60, 0x90, 0x81, 0xff,
+ 0x3f, 0x7f, 0x6b, 0xff, 0x31, 0x75, 0x62, 0xff,
+ 0x4d, 0x88, 0x73, 0xff, 0x3f, 0x7f, 0x6b, 0xff,
+ 0x4d, 0x88, 0x76, 0xff, 0x52, 0x91, 0x7b, 0xff,
+ 0x52, 0x92, 0x7c, 0xff, 0x42, 0x75, 0x6b, 0xff,
+ 0x2c, 0x74, 0x5b, 0xff, 0x2c, 0x74, 0x5a, 0xff,
+ 0x2c, 0x74, 0x5b, 0xff, 0x2c, 0x74, 0x5a, 0xff,
+ 0x32, 0x7a, 0x66, 0xff, 0x31, 0x79, 0x65, 0xff,
+ 0x32, 0x7a, 0x66, 0xff, 0x31, 0x79, 0x65, 0xff,
+ 0x37, 0x7f, 0x68, 0xff, 0x2c, 0x70, 0x5d, 0xff,
+ 0x2c, 0x70, 0x5e, 0xff, 0x37, 0x7f, 0x68, 0xff,
+ 0x2f, 0x76, 0x60, 0xff, 0x2e, 0x75, 0x60, 0xff,
+ 0x2f, 0x76, 0x60, 0xff, 0x2f, 0x75, 0x60, 0xff,
+ 0x42, 0x86, 0x73, 0xff, 0x39, 0x7d, 0x68, 0xff,
+ 0x2a, 0x6e, 0x53, 0xff, 0x39, 0x7d, 0x68, 0xff,
+ 0x29, 0x6a, 0x5b, 0xff, 0x29, 0x69, 0x5a, 0xff,
+ 0x50, 0x8a, 0x7c, 0xff, 0x4f, 0x8a, 0x7b, 0xff,
+ 0x3a, 0x82, 0x6b, 0xff, 0x4a, 0x8f, 0x7b, 0xff,
+ 0x3a, 0x82, 0x6b, 0xff, 0x42, 0x88, 0x73, 0xff,
+ 0x42, 0x85, 0x71, 0xff, 0x39, 0x7b, 0x65, 0xff,
+ 0x42, 0x85, 0x71, 0xff, 0x4a, 0x8e, 0x7b, 0xff,
+ 0x45, 0x87, 0x73, 0xff, 0x39, 0x81, 0x6b, 0xff,
+ 0x45, 0x87, 0x74, 0xff, 0x5a, 0x92, 0x84, 0xff,
+ 0x53, 0x8a, 0x7c, 0xff, 0x5a, 0x90, 0x81, 0xff,
+ 0x63, 0x98, 0x87, 0xff, 0x63, 0x97, 0x86, 0xff,
+ 0x60, 0x95, 0x87, 0xff, 0x60, 0x94, 0x86, 0xff,
+ 0x60, 0x95, 0x87, 0xff, 0x29, 0x69, 0x5a, 0xff,
+ 0x09, 0x31, 0x21, 0xff, 0x08, 0x30, 0x21, 0xff,
+ 0x09, 0x31, 0x21, 0xff, 0x4a, 0x77, 0x68, 0xff,
+ 0x73, 0xa2, 0x94, 0xff, 0x5d, 0x8f, 0x7e, 0xff,
+ 0x5e, 0x8f, 0x7f, 0xff, 0x52, 0x85, 0x73, 0xff,
+ 0x60, 0x91, 0x81, 0xff, 0x6b, 0x9a, 0x8c, 0xff,
+ 0x55, 0x87, 0x76, 0xff, 0x4a, 0x7d, 0x6b, 0xff,
+ 0x4d, 0x89, 0x73, 0xff, 0x3f, 0x7f, 0x6b, 0xff,
+ 0x4d, 0x89, 0x74, 0xff, 0x4d, 0x88, 0x73, 0xff,
+ 0x4d, 0x89, 0x76, 0xff, 0x52, 0x91, 0x7b, 0xff,
+ 0x53, 0x92, 0x7c, 0xff, 0x4d, 0x88, 0x76, 0xff,
+ 0x1e, 0x63, 0x4a, 0xff, 0x2c, 0x74, 0x5a, 0xff,
+ 0x2c, 0x74, 0x5b, 0xff, 0x1e, 0x62, 0x4a, 0xff,
+ 0x32, 0x7a, 0x66, 0xff, 0x39, 0x85, 0x73, 0xff,
+ 0x31, 0x79, 0x65, 0xff, 0x39, 0x85, 0x73, 0xff,
+ 0x42, 0x8e, 0x73, 0xff, 0x36, 0x7e, 0x68, 0xff,
+ 0x2c, 0x70, 0x5d, 0xff, 0x20, 0x61, 0x52, 0xff,
+ 0x19, 0x5d, 0x4a, 0xff, 0x23, 0x69, 0x55, 0xff,
+ 0x24, 0x69, 0x55, 0xff, 0x2e, 0x75, 0x5f, 0xff,
+ 0x42, 0x86, 0x73, 0xff, 0x39, 0x7d, 0x68, 0xff,
+ 0x42, 0x86, 0x73, 0xff, 0x41, 0x85, 0x73, 0xff,
+ 0x3c, 0x7a, 0x6b, 0xff, 0x29, 0x69, 0x5a, 0xff,
+ 0x50, 0x8a, 0x7b, 0xff, 0x3c, 0x79, 0x6a, 0xff,
+ 0x42, 0x88, 0x73, 0xff, 0x52, 0x95, 0x83, 0xff,
+ 0x42, 0x88, 0x73, 0xff, 0x39, 0x81, 0x6a, 0xff,
+ 0x42, 0x84, 0x71, 0xff, 0x31, 0x71, 0x5a, 0xff,
+ 0x3a, 0x7b, 0x65, 0xff, 0x4a, 0x8d, 0x7b, 0xff,
+ 0x3a, 0x82, 0x6b, 0xff, 0x4f, 0x8c, 0x7b, 0xff,
+ 0x45, 0x87, 0x73, 0xff, 0x44, 0x86, 0x73, 0xff,
+ 0x5b, 0x91, 0x81, 0xff, 0x62, 0x97, 0x86, 0xff,
+ 0x52, 0x8a, 0x7b, 0xff, 0x5a, 0x90, 0x80, 0xff,
+ 0x60, 0x95, 0x87, 0xff, 0x60, 0x94, 0x86, 0xff,
+ 0x7b, 0xaa, 0x9c, 0xff, 0x29, 0x69, 0x5a, 0xff,
+ 0x29, 0x54, 0x45, 0xff, 0x4a, 0x76, 0x68, 0xff,
+ 0x08, 0x31, 0x21, 0xff, 0x08, 0x30, 0x20, 0xff,
+ 0x68, 0x99, 0x89, 0xff, 0x5d, 0x8f, 0x7e, 0xff,
+ 0x52, 0x86, 0x73, 0xff, 0x52, 0x85, 0x73, 0xff,
+ 0x55, 0x87, 0x76, 0xff, 0x60, 0x90, 0x81, 0xff,
+ 0x60, 0x90, 0x81, 0xff, 0x55, 0x86, 0x75, 0xff,
+ 0x4d, 0x88, 0x73, 0xff, 0x4c, 0x88, 0x73, 0xff,
+ 0x3f, 0x7f, 0x6b, 0xff, 0x5a, 0x91, 0x7b, 0xff,
+ 0x4d, 0x88, 0x76, 0xff, 0x47, 0x7e, 0x70, 0xff,
+ 0x4d, 0x88, 0x76, 0xff, 0x4c, 0x88, 0x75, 0xff,
+ 0x11, 0x55, 0x42, 0xff, 0x31, 0x73, 0x63, 0xff,
+ 0x21, 0x64, 0x53, 0xff, 0x31, 0x73, 0x63, 0xff,
+ 0x37, 0x81, 0x71, 0xff, 0x2c, 0x77, 0x65, 0xff,
+ 0x2c, 0x77, 0x66, 0xff, 0x42, 0x89, 0x7b, 0xff,
+ 0x3a, 0x86, 0x74, 0xff, 0x2f, 0x79, 0x65, 0xff,
+ 0x24, 0x6e, 0x58, 0xff, 0x19, 0x61, 0x4a, 0xff,
+ 0x21, 0x5e, 0x4b, 0xff, 0x2f, 0x71, 0x5d, 0xff,
+ 0x21, 0x5d, 0x4a, 0xff, 0x21, 0x5d, 0x4a, 0xff,
+ 0x42, 0x8a, 0x7c, 0xff, 0x42, 0x8a, 0x7b, 0xff,
+ 0x42, 0x8a, 0x7c, 0xff, 0x37, 0x80, 0x6e, 0xff,
+ 0x37, 0x7e, 0x69, 0xff, 0x37, 0x7d, 0x68, 0xff,
+ 0x37, 0x7e, 0x69, 0xff, 0x42, 0x89, 0x73, 0xff,
+ 0x35, 0x7a, 0x66, 0xff, 0x4a, 0x92, 0x7b, 0xff,
+ 0x3f, 0x86, 0x71, 0xff, 0x34, 0x79, 0x65, 0xff,
+ 0x3d, 0x85, 0x74, 0xff, 0x21, 0x69, 0x52, 0xff,
+ 0x3d, 0x85, 0x74, 0xff, 0x3c, 0x84, 0x73, 0xff,
+ 0x48, 0x82, 0x74, 0xff, 0x52, 0x8e, 0x7b, 0xff,
+ 0x48, 0x82, 0x74, 0xff, 0x47, 0x81, 0x73, 0xff,
+ 0x58, 0x8f, 0x81, 0xff, 0x63, 0x96, 0x8c, 0xff,
+ 0x58, 0x8f, 0x81, 0xff, 0x58, 0x8f, 0x81, 0xff,
+ 0x53, 0x8e, 0x7c, 0xff, 0x52, 0x8e, 0x7b, 0xff,
+ 0x53, 0x8e, 0x7c, 0xff, 0x08, 0x30, 0x21, 0xff,
+ 0x2c, 0x5a, 0x45, 0xff, 0x63, 0xa2, 0x8c, 0xff,
+ 0x2c, 0x59, 0x45, 0xff, 0x10, 0x34, 0x21, 0xff,
+ 0x40, 0x6e, 0x5b, 0xff, 0x5a, 0x8e, 0x7b, 0xff,
+ 0x5b, 0x8e, 0x7c, 0xff, 0x5a, 0x8e, 0x7b, 0xff,
+ 0x53, 0x8a, 0x76, 0xff, 0x4a, 0x81, 0x70, 0xff,
+ 0x53, 0x8a, 0x76, 0xff, 0x52, 0x89, 0x76, 0xff,
+ 0x55, 0x8d, 0x76, 0xff, 0x4f, 0x87, 0x70, 0xff,
+ 0x55, 0x8d, 0x76, 0xff, 0x55, 0x8c, 0x76, 0xff,
+ 0x4b, 0x8a, 0x76, 0xff, 0x4a, 0x8a, 0x76, 0xff,
+ 0x4a, 0x8a, 0x76, 0xff, 0x42, 0x81, 0x70, 0xff,
+ 0x21, 0x64, 0x52, 0xff, 0x20, 0x63, 0x52, 0xff,
+ 0x21, 0x64, 0x52, 0xff, 0x31, 0x72, 0x62, 0xff,
+ 0x37, 0x80, 0x71, 0xff, 0x36, 0x80, 0x70, 0xff,
+ 0x42, 0x8a, 0x7c, 0xff, 0x42, 0x89, 0x7b, 0xff,
+ 0x2f, 0x7a, 0x66, 0xff, 0x23, 0x6d, 0x57, 0xff,
+ 0x19, 0x61, 0x4a, 0xff, 0x18, 0x61, 0x4a, 0xff,
+ 0x2f, 0x71, 0x5d, 0xff, 0x2e, 0x71, 0x5d, 0xff,
+ 0x2f, 0x72, 0x5d, 0xff, 0x2e, 0x71, 0x5d, 0xff,
+ 0x42, 0x8a, 0x7b, 0xff, 0x41, 0x89, 0x7b, 0xff,
+ 0x37, 0x80, 0x6e, 0xff, 0x37, 0x80, 0x6d, 0xff,
+ 0x42, 0x8a, 0x73, 0xff, 0x41, 0x89, 0x73, 0xff,
+ 0x42, 0x8a, 0x73, 0xff, 0x37, 0x7d, 0x68, 0xff,
+ 0x29, 0x6d, 0x5b, 0xff, 0x3f, 0x85, 0x70, 0xff,
+ 0x34, 0x7a, 0x66, 0xff, 0x3f, 0x85, 0x70, 0xff,
+ 0x3c, 0x84, 0x73, 0xff, 0x2e, 0x76, 0x62, 0xff,
+ 0x3d, 0x84, 0x73, 0xff, 0x3c, 0x84, 0x73, 0xff,
+ 0x52, 0x8e, 0x7b, 0xff, 0x52, 0x8d, 0x7b, 0xff,
+ 0x3d, 0x76, 0x6b, 0xff, 0x47, 0x81, 0x73, 0xff,
+ 0x4d, 0x88, 0x76, 0xff, 0x62, 0x95, 0x8b, 0xff,
+ 0x58, 0x8f, 0x81, 0xff, 0x4c, 0x88, 0x76, 0xff,
+ 0x52, 0x8e, 0x7b, 0xff, 0x52, 0x8d, 0x7b, 0xff,
+ 0x52, 0x8e, 0x7c, 0xff, 0x08, 0x30, 0x21, 0xff,
+ 0x11, 0x35, 0x21, 0xff, 0x47, 0x7d, 0x68, 0xff,
+ 0x48, 0x7e, 0x68, 0xff, 0x10, 0x34, 0x21, 0xff,
+ 0x08, 0x2d, 0x19, 0xff, 0x3f, 0x6d, 0x5a, 0xff,
+ 0x5b, 0x8e, 0x7c, 0xff, 0x5a, 0x8d, 0x7b, 0xff,
+ 0x52, 0x8a, 0x76, 0xff, 0x4a, 0x81, 0x70, 0xff,
+ 0x52, 0x8a, 0x76, 0xff, 0x4a, 0x81, 0x70, 0xff,
+ 0x50, 0x87, 0x71, 0xff, 0x4a, 0x81, 0x6b, 0xff,
+ 0x50, 0x87, 0x71, 0xff, 0x4f, 0x87, 0x70, 0xff,
+ 0x42, 0x82, 0x71, 0xff, 0x52, 0x91, 0x7b, 0xff,
+ 0x4a, 0x8a, 0x76, 0xff, 0x39, 0x79, 0x6b, 0xff,
+ 0x11, 0x55, 0x42, 0xff, 0x21, 0x64, 0x52, 0xff,
+ 0x32, 0x73, 0x63, 0xff, 0x31, 0x73, 0x63, 0xff,
+ 0x37, 0x80, 0x71, 0xff, 0x42, 0x89, 0x7b, 0xff,
+ 0x37, 0x81, 0x71, 0xff, 0x2c, 0x77, 0x65, 0xff,
+ 0x24, 0x6e, 0x58, 0xff, 0x23, 0x6d, 0x58, 0xff,
+ 0x19, 0x62, 0x4a, 0xff, 0x24, 0x6d, 0x58, 0xff,
+ 0x3d, 0x86, 0x71, 0xff, 0x3c, 0x85, 0x70, 0xff,
+ 0x3d, 0x86, 0x71, 0xff, 0x2f, 0x71, 0x5d, 0xff,
+ 0x37, 0x80, 0x6e, 0xff, 0x42, 0x89, 0x7b, 0xff,
+ 0x21, 0x6e, 0x53, 0xff, 0x2c, 0x77, 0x60, 0xff,
+ 0x37, 0x7e, 0x68, 0xff, 0x37, 0x7d, 0x68, 0xff,
+ 0x37, 0x7e, 0x69, 0xff, 0x2c, 0x71, 0x5d, 0xff,
+ 0x34, 0x7a, 0x66, 0xff, 0x34, 0x79, 0x65, 0xff,
+ 0x35, 0x7a, 0x66, 0xff, 0x34, 0x79, 0x65, 0xff,
+ 0x4a, 0x92, 0x84, 0xff, 0x4a, 0x91, 0x83, 0xff,
+ 0x3d, 0x85, 0x74, 0xff, 0x4a, 0x92, 0x84, 0xff,
+ 0x53, 0x8e, 0x7c, 0xff, 0x47, 0x81, 0x73, 0xff,
+ 0x32, 0x6a, 0x63, 0xff, 0x31, 0x69, 0x63, 0xff,
+ 0x42, 0x82, 0x6b, 0xff, 0x58, 0x8f, 0x81, 0xff,
+ 0x4d, 0x89, 0x76, 0xff, 0x4d, 0x88, 0x76, 0xff,
+ 0x53, 0x8e, 0x7c, 0xff, 0x52, 0x8d, 0x7b, 0xff,
+ 0x3a, 0x6f, 0x5e, 0xff, 0x08, 0x30, 0x21, 0xff,
+ 0x2c, 0x59, 0x45, 0xff, 0x2c, 0x59, 0x44, 0xff,
+ 0x63, 0xa2, 0x8c, 0xff, 0x47, 0x7d, 0x68, 0xff,
+ 0x09, 0x2d, 0x19, 0xff, 0x08, 0x2c, 0x18, 0xff,
+ 0x3f, 0x6e, 0x5b, 0xff, 0x5a, 0x8e, 0x7b, 0xff,
+ 0x4a, 0x82, 0x71, 0xff, 0x52, 0x89, 0x76, 0xff,
+ 0x4a, 0x82, 0x71, 0xff, 0x42, 0x79, 0x6b, 0xff,
+ 0x4a, 0x82, 0x6b, 0xff, 0x4f, 0x87, 0x70, 0xff,
+ 0x50, 0x87, 0x71, 0xff, 0x55, 0x8c, 0x76, 0xff,
+ 0x42, 0x82, 0x71, 0xff, 0x42, 0x81, 0x70, 0xff,
+ 0x42, 0x82, 0x71, 0xff, 0x39, 0x79, 0x6b, 0xff,
+ 0x21, 0x64, 0x52, 0xff, 0x10, 0x55, 0x41, 0xff,
+ 0x31, 0x73, 0x63, 0xff, 0x41, 0x81, 0x73, 0xff,
+ 0x2c, 0x77, 0x66, 0xff, 0x2c, 0x76, 0x65, 0xff,
+ 0x42, 0x8a, 0x7b, 0xff, 0x20, 0x6d, 0x5a, 0xff,
+ 0x19, 0x61, 0x4a, 0xff, 0x23, 0x6d, 0x57, 0xff,
+ 0x24, 0x6d, 0x58, 0xff, 0x2e, 0x79, 0x65, 0xff,
+ 0x4a, 0x9a, 0x84, 0xff, 0x3c, 0x85, 0x70, 0xff,
+ 0x3c, 0x86, 0x70, 0xff, 0x3c, 0x85, 0x70, 0xff,
+ 0x37, 0x80, 0x6e, 0xff, 0x21, 0x6d, 0x52, 0xff,
+ 0x21, 0x6d, 0x52, 0xff, 0x36, 0x80, 0x6d, 0xff,
+ 0x37, 0x7e, 0x68, 0xff, 0x36, 0x7d, 0x68, 0xff,
+ 0x21, 0x65, 0x52, 0xff, 0x20, 0x65, 0x52, 0xff,
+ 0x3f, 0x86, 0x71, 0xff, 0x3f, 0x85, 0x70, 0xff,
+ 0x29, 0x6d, 0x5b, 0xff, 0x29, 0x6d, 0x5a, 0xff,
+ 0x2f, 0x77, 0x63, 0xff, 0x3c, 0x84, 0x73, 0xff,
+ 0x4a, 0x92, 0x84, 0xff, 0x3c, 0x84, 0x73, 0xff,
+ 0x47, 0x82, 0x73, 0xff, 0x47, 0x81, 0x73, 0xff,
+ 0x3c, 0x75, 0x6b, 0xff, 0x3c, 0x75, 0x6a, 0xff,
+ 0x42, 0x82, 0x6b, 0xff, 0x62, 0x95, 0x8b, 0xff,
+ 0x58, 0x8f, 0x81, 0xff, 0x41, 0x81, 0x6a, 0xff,
+ 0x52, 0x8e, 0x7c, 0xff, 0x52, 0x8d, 0x7b, 0xff,
+ 0x21, 0x50, 0x3f, 0xff, 0x08, 0x30, 0x20, 0xff,
+ 0x47, 0x7e, 0x68, 0xff, 0x2c, 0x59, 0x44, 0xff,
+ 0x47, 0x7e, 0x68, 0xff, 0x47, 0x7d, 0x68, 0xff,
+ 0x24, 0x4d, 0x3a, 0xff, 0x08, 0x2c, 0x18, 0xff,
+ 0x08, 0x2d, 0x19, 0xff, 0x3f, 0x6d, 0x5a, 0xff,
+ 0x52, 0x8a, 0x76, 0xff, 0x5a, 0x91, 0x7b, 0xff,
+ 0x52, 0x8a, 0x76, 0xff, 0x41, 0x79, 0x6a, 0xff,
+ 0x50, 0x87, 0x71, 0xff, 0x55, 0x8c, 0x76, 0xff,
+ 0x55, 0x8c, 0x76, 0xff, 0x5a, 0x91, 0x7b, 0xff,
+ 0x42, 0x82, 0x71, 0xff, 0x41, 0x81, 0x70, 0xff,
+ 0x42, 0x82, 0x70, 0xff, 0x52, 0x91, 0x7b, 0xff,
+};
diff --git a/o3d/command_buffer/samples/bubble/iridescence_texture.cc b/o3d/command_buffer/samples/bubble/iridescence_texture.cc
new file mode 100644
index 0000000..cd9fd4d
--- /dev/null
+++ b/o3d/command_buffer/samples/bubble/iridescence_texture.cc
@@ -0,0 +1,167 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file implements some optics utility functions and the thin-layer
+// iridescence texture generation function.
+
+#include <math.h>
+#include <utility>
+#include "command_buffer/samples/bubble/iridescence_texture.h"
+#include "command_buffer/samples/bubble/utils.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// Computes the fresnel coefficients for amplitude.
+// http://physics.tamuk.edu/~suson/html/4323/prop-em.html has them.
+FresnelCoefficients ComputeFresnel(float n, float cos_i, float cos_t) {
+ FresnelCoefficients coeff;
+ coeff.reflected_perp = (cos_i - n*cos_t)/(cos_i + n*cos_t);
+ coeff.transmitted_perp = 2.f*cos_i/(cos_i + n*cos_t);
+ coeff.reflected_para = (n*cos_i - cos_t)/(n*cos_i + cos_t);
+ coeff.transmitted_para = 2.f*cos_i/(n*cos_i + cos_t);
+ return coeff;
+}
+
+// Snell-Descartes' Law: sin_i = n * sin_t.
+float RefractedRay(float n, float cos_i) {
+ float sin2_i = 1.f - cos_i * cos_i;
+ float sin2_t = sin2_i / (n*n);
+ float cos2_t = 1.f - sin2_t;
+ float cos_t = sqrtf(std::max(0.f, cos2_t));
+ return cos_t;
+}
+
+// Understanding the notations in the following two functions.
+//
+// \ A \ A' / B i = incident angle.
+// incident ray \ \ / t = transmitted angle.
+// \ i| \ i|i /
+// \| \|/ air (n = 1) outside the bubble
+// -outer-interface----P---------R---------------------------------------
+// |\ /| ^
+// |t\ /t| |thin layer (e.g. water, n > 1)
+// transmitted ray \t|t/ |thickness
+// \|/ v
+// -inner-interface---------Q--------------------------------------------
+// |\ air (n = 1) inside the bubble
+// |i \
+// \ C
+//
+// Incident ray A gets refracted by the outer interface at point P, then
+// reflected by the inner interface at point Q, then refracted into B at point R
+// ("trt" ray). At the same time, incident ray A', coherent with A, gets
+// directly reflected into B ("r" ray) at point R, so it interferes with the
+// "trt" ray.
+// At point Q the ray also gets refracted inside the bubble, leading to the
+// "tt" ray C.
+
+
+// Computes the interference between the reflected ray ('r' - one reflection
+// one the outer interface) and the reflection of the transmitted ray ('trt' -
+// transmitted through the outer interface, reflected on the inner interface,
+// then transmitted again through the outer interface).
+//
+// Parameters:
+// thickness: the thickness of the medium between the interfaces.
+// wavelength: the wavelength of the incident light.
+// n: the refraction index of the medium (relative to the outer medium).
+// r_perp: the amplitude coefficient for the r ray for perpendicular
+// polarization.
+// r_para: the amplitude coefficient for the r ray for parallel polarization.
+// trt_perp: the amplitude coefficient for the trt ray for perpendicular
+// polarization.
+// trt_para: the amplitude coefficient for the trt ray for parallel
+// polarization.
+// cos_t: the cosine of the refracted angle.
+// Returns:
+// The reflected power after interference.
+float Interference(float thickness,
+ float wavelength,
+ float n,
+ float r_perp,
+ float r_para,
+ float trt_perp,
+ float trt_para,
+ float cos_t) {
+ // Difference in wave propagation between the trt ray and the r ray.
+ float delta_phase = 2.f * thickness/wavelength * n * cos_t;
+ // For a given polarization, power = ||r + trt * e^(i*2*pi*delta_phase)||^2
+ float cos_delta = cosf(2.f * kPi * delta_phase);
+ float power_perp =
+ r_perp*r_perp + trt_perp*trt_perp + 2.f * r_perp*trt_perp*cos_delta;
+ float power_para =
+ r_para*r_para + trt_para*trt_para + 2.f * r_para*trt_para*cos_delta;
+ // Total power is the average between 2 polarization modes (for non-polarized
+ // light).
+ return (power_perp+power_para)/2.f;
+}
+
+void MakeIridescenceTexture(unsigned int width,
+ unsigned int height,
+ float n,
+ float max_thickness,
+ unsigned char *texture) {
+ for (unsigned int y = 0; y < height; ++y) {
+ float thickness = (y + .5f) * max_thickness / height;
+ for (unsigned int x = 0; x < width; ++x) {
+ float cos_i = (x + .5f) * 1.f / width;
+ float cos_t = RefractedRay(n, cos_i);
+ // Fresnel coefficient for the "outer" interface (outside->inside).
+ FresnelCoefficients outer = ComputeFresnel(n, cos_i, cos_t);
+ // Fresnel coefficient for the "inner" interface (inside->outside).
+ FresnelCoefficients inner = ComputeFresnel(1.f/n, cos_t, cos_i);
+ float r_perp = outer.reflected_perp;
+ float r_para = outer.reflected_para;
+ float trt_perp = outer.transmitted_perp * inner.reflected_perp *
+ inner.transmitted_perp;
+ float trt_para = outer.transmitted_para * inner.reflected_para *
+ inner.transmitted_para;
+ float red = Interference(thickness, kRedWavelength, n, r_perp, r_para,
+ trt_perp, trt_para, cos_t);
+ float green = Interference(thickness, kGreenWavelength, n, r_perp, r_para,
+ trt_perp, trt_para, cos_t);
+ float blue = Interference(thickness, kBlueWavelength, n, r_perp, r_para,
+ trt_perp, trt_para, cos_t);
+ float tt_perp = outer.transmitted_perp * inner.transmitted_perp;
+ float tt_para = outer.transmitted_para * inner.transmitted_para;
+ float alpha = (tt_perp*tt_perp + tt_para*tt_para)/2.f;
+ *texture++ = ToChar(blue);
+ *texture++ = ToChar(green);
+ *texture++ = ToChar(red);
+ *texture++ = ToChar(alpha);
+ }
+ }
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/samples/bubble/iridescence_texture.h b/o3d/command_buffer/samples/bubble/iridescence_texture.h
new file mode 100644
index 0000000..6d43a29
--- /dev/null
+++ b/o3d/command_buffer/samples/bubble/iridescence_texture.h
@@ -0,0 +1,105 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file describes the interface to some optics utility functions and the
+// thin-layer iridescence texture generation function.
+
+#ifndef O3D_COMMAND_BUFFER_SAMPLES_BUBBLE_IRIDESCENCE_TEXTURE_H_
+#define O3D_COMMAND_BUFFER_SAMPLES_BUBBLE_IRIDESCENCE_TEXTURE_H_
+
+namespace o3d {
+namespace command_buffer {
+
+// Wavelengths for different colors used in MakeIridescenceTexture (in
+// nanometers).
+const float kRedWavelength = 680.f;
+const float kGreenWavelength = 530.f;
+const float kBlueWavelength = 440.f;
+
+// Fresnel coefficients (amplitude) for 2 polarisations of the incident light
+// (either perpendicular or parallel to the plane of incidence).
+struct FresnelCoefficients {
+ float reflected_perp;
+ float reflected_para;
+ float transmitted_perp;
+ float transmitted_para;
+};
+
+// Computes the cosine of the angle of the refracted ray with the interface
+// normal.
+// Parameters:
+// n: the index of refraction of the transmission medium relative to the
+// incidence one.
+// cos_i: the cosine of the angle of the incident ray with the interface
+// normal
+// Returns:
+// cos_t, the cosine of the refracted angle.
+float RefractedRay(float n, float cos_i);
+
+// Computes the Fresnel coefficients (amplitude).
+// Parameters:
+// n: the index of refraction of the transmission medium relative to the
+// incidence one.
+// cos_i: the cosine of the angle of the incident ray with the interface
+// normal
+// cos_t: the cosine of the angle of the transmitted ray with the interface
+// normal
+// Returns:
+// The amplitude Fresnel coefficients.
+FresnelCoefficients ComputeFresnel(float n, float cos_i, float cos_t);
+
+// Computes a BGRA texture used for thin-layer iridescence simulation. It maps
+// a wavelength-dependent reflected power and total transmitted power as a
+// function of the cosine of the incidence angle (x coordinate from 0 to 1),
+// and the thin-layer thickness (y coordinate from 0 to max_thickness) for a
+// given refraction index.
+// The B,G and R component receive the relative reflected power for the
+// wavelengths corresponding to blue, green and red respectively.
+// The A component receives the transmitted power (wavelength-independent).
+// Parameters:
+// width: the width of the texture.
+// height: the height of the texture.
+// n: the refraction index of the thin-layer medium relative to the incident
+// medium.
+// max_thickness: the maximum thickness of the layer (in nanometers).
+// texture: the buffer receiving the iridescence texture. It should be large
+// enough to contain width*height*4 bytes.
+void MakeIridescenceTexture(unsigned int width,
+ unsigned int height,
+ float n,
+ float max_thickness,
+ unsigned char *texture);
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_SAMPLES_BUBBLE_IRIDESCENCE_TEXTURE_H_
diff --git a/o3d/command_buffer/samples/bubble/perlin_noise.cc b/o3d/command_buffer/samples/bubble/perlin_noise.cc
new file mode 100644
index 0000000..f69f527
--- /dev/null
+++ b/o3d/command_buffer/samples/bubble/perlin_noise.cc
@@ -0,0 +1,107 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the implementation of the Perlin noise generator.
+
+#include <stdlib.h>
+#include "command_buffer/common/cross/logging.h"
+#include "command_buffer/samples/bubble/perlin_noise.h"
+#include "command_buffer/samples/bubble/utils.h"
+
+namespace o3d {
+namespace command_buffer {
+
+PerlinNoise2D::PerlinNoise2D(unsigned int frequency)
+ : frequency_(frequency),
+ permutation_(new unsigned int[2*frequency]),
+ gradients_(new Float2[frequency]) {
+}
+
+void PerlinNoise2D::Initialize(unsigned int *seed) {
+ // Initialize the gradients table with a random unit direction.
+ // Initialize the permutation table to be the identity.
+ for (unsigned int i = 0; i < frequency_; ++i) {
+ float theta = Randf(0.f, 2.f * kPi, seed);
+ gradients_[i] = Float2(cosf(theta), sinf(theta));
+ permutation_[i] = i;
+ }
+ // Generate the permutation table by switching each element with a further
+ // element. Also duplicate the permutation table so that constructs like
+ // permutation[x + permutation[y]] work without additional modulo.
+ for (unsigned int i = 0; i < frequency_; ++i) {
+ unsigned int j = i + (rand_r(seed) % (frequency_ - i));
+ unsigned int tmp = permutation_[j];
+ permutation_[j] = permutation_[i];
+ permutation_[i] = tmp;
+ permutation_[i + frequency_] = tmp;
+ }
+}
+
+void PerlinNoise2D::Generate(unsigned int width,
+ unsigned int height,
+ float *texture) {
+ for (unsigned int y = 0; y < height; ++y) {
+ for (unsigned int x = 0; x < width; ++x) {
+ // The texture is decomposed into a lattice of frequency_ points in each
+ // direction. A (x, y) point falls between 4 lattice vertices.
+ // (xx, yy) are the coordinate of the bottom left lattice vertex
+ // corresponding to an (x, y) image point.
+ unsigned int xx = x * frequency_ / width;
+ unsigned int yy = y * frequency_ / height;
+ // xt and yt are the barycentric coordinates of the (x, y) point relative
+ // to the vertices (between 0 and 1).
+ float xt = 1.f/width * ((x * frequency_) % width);
+ float yt = 1.f/height * ((y * frequency_) % height);
+ // contribution of each lattice vertex to the point value.
+ float contrib[4];
+ for (unsigned int y_offset = 0; y_offset < 2; ++y_offset) {
+ for (unsigned int x_offset = 0; x_offset < 2; ++x_offset) {
+ unsigned int index = permutation_[xx + x_offset] + y_offset + yy;
+ DCHECK_LT(index, frequency_ * 2);
+ Float2 gradient = gradients_[permutation_[index]];
+ contrib[y_offset*2+x_offset] = gradient.first * (xt - x_offset) +
+ gradient.second * (yt - y_offset);
+ }
+ }
+ // We interpolate between the vertex contributions using a smooth step
+ // function of the barycentric coordinates.
+ float xt_smooth = SmoothStep(xt);
+ float yt_smooth = SmoothStep(yt);
+ float contrib_bottom = Lerp(xt_smooth, contrib[0], contrib[1]);
+ float contrib_top = Lerp(xt_smooth, contrib[2], contrib[3]);
+ *texture++ = Lerp(yt_smooth, contrib_bottom, contrib_top);
+ }
+ }
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/samples/bubble/perlin_noise.h b/o3d/command_buffer/samples/bubble/perlin_noise.h
new file mode 100644
index 0000000..3a600de
--- /dev/null
+++ b/o3d/command_buffer/samples/bubble/perlin_noise.h
@@ -0,0 +1,74 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the declaration of the Perlin noise generator.
+
+#ifndef O3D_COMMAND_BUFFER_SAMPLES_BUBBLE_PERLIN_NOISE_H_
+#define O3D_COMMAND_BUFFER_SAMPLES_BUBBLE_PERLIN_NOISE_H_
+
+#include <utility>
+#include "base/scoped_ptr.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// 2D Perlin perlin noise generator.
+class PerlinNoise2D {
+ public:
+ typedef std::pair<float, float> Float2;
+ explicit PerlinNoise2D(unsigned int frequency);
+
+ // Initializes the permutation and gradients arrays. Note that all randomness
+ // happens here.
+ // Parameters:
+ // seed: pointer to the seed value for randomness. Note: this value is
+ // modified like it would in the rand_r function.
+ void Initialize(unsigned int *seed);
+
+ // Generates the noise texture.
+ // Parameters:
+ // width: the width of the texture
+ // height: the height of the texture
+ // texture: the texture values, to be filled by the function. The buffer
+ // must have enough storage for width*height floats.
+ void Generate(unsigned int width, unsigned int height, float *texture);
+
+ private:
+ unsigned int frequency_;
+ scoped_array<unsigned int> permutation_;
+ scoped_array<Float2> gradients_;
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_SAMPLES_BUBBLE_PERLIN_NOISE_H_
diff --git a/o3d/command_buffer/samples/bubble/utils.h b/o3d/command_buffer/samples/bubble/utils.h
new file mode 100644
index 0000000..55ec3df
--- /dev/null
+++ b/o3d/command_buffer/samples/bubble/utils.h
@@ -0,0 +1,73 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file defines some utility functions.
+
+#ifndef O3D_COMMAND_BUFFER_SAMPLES_BUBBLE_UTILS_H_
+#define O3D_COMMAND_BUFFER_SAMPLES_BUBBLE_UTILS_H_
+
+#include <math.h>
+#include <stdlib.h>
+#include <algorithm>
+
+namespace o3d {
+namespace command_buffer {
+
+const float kPi = 3.14159265359f;
+
+// Returns a random value between min and max.
+inline float Randf(float min, float max, unsigned int *seed) {
+ return min + (max - min) / RAND_MAX * rand_r(seed);
+}
+
+// Converts a [0..1] float to a [0..255] color value.
+inline unsigned char ToChar(float x) {
+ x = std::min(1.f, std::max(0.f, x));
+ return static_cast<unsigned char>(x * 255.f);
+}
+
+// Maps [0..1] into [0..1], using a smooth (C^2) function,
+// with f(0)=0, f(1)=1, f'(0)=f'(1)=0.
+// This version is simply a cubic interpolation between 0 and 1.
+inline float SmoothStep(float x) {
+ return (3.f - 2.f * x) * x * x;
+}
+
+// Interpolates between a and b, with a ratio of t.
+inline float Lerp(float t, float a, float b) {
+ return a + (b-a)*t;
+}
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_SAMPLES_BUBBLE_UTILS_H_
diff --git a/o3d/command_buffer/samples/build.scons b/o3d/command_buffer/samples/build.scons
new file mode 100644
index 0000000..414ee95
--- /dev/null
+++ b/o3d/command_buffer/samples/build.scons
@@ -0,0 +1,55 @@
+# Copyright 2009, Google Inc.
+# 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.
+
+
+Import('env')
+
+env.Append(
+ LIBS = [
+ 'o3dCmdBuf_client',
+ 'o3dCmdBuf_common',
+ 'google_nacl_npruntime',
+ ] + env['NACL_HTP_LIBS'],
+ LIBPATH = ['$NACL_LIB_DIR'],
+ CPPPATH = ['$NPAPI_DIR', '$NPAPI_DIR/include'],
+)
+
+if env['TARGET_PLATFORM'] == 'NACL':
+ env.Append(LIBS=['m', 'pthread'],
+ CCFLAGS=['-O3', '-mfpmath=sse', '-msse', '-fomit-frame-pointer'])
+
+BUBBLE_INPUTS = [
+ 'bubble/bubble_module.cc',
+ 'bubble/cubemap.cc',
+ 'bubble/iridescence_texture.cc',
+ 'bubble/perlin_noise.cc',
+]
+bubble_sample = env.Program('bubble_module.nexe', BUBBLE_INPUTS)
+artifacts = [bubble_sample, 'bubble/bubble.html']
+env.Replicate('$ARTIFACTS_DIR/samples/bubble', artifacts)
diff --git a/o3d/command_buffer/service/build.scons b/o3d/command_buffer/service/build.scons
new file mode 100644
index 0000000..17ec60f
--- /dev/null
+++ b/o3d/command_buffer/service/build.scons
@@ -0,0 +1,114 @@
+# Copyright 2009, Google Inc.
+# 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.
+
+
+Import('env')
+
+INPUTS = [
+ 'cross/buffer_rpc.cc',
+ 'cross/cmd_parser.cc',
+ 'cross/cmd_buffer_engine.cc',
+ 'cross/effect_utils.cc',
+ 'cross/gapi_decoder.cc',
+ 'cross/resource.cc',
+ 'cross/texture_utils.cc',
+]
+
+# Build the big tests
+BIG_TEST_SERVER = [
+ 'cross/big_test.cc',
+]
+
+# Add some flags and libraries to the build environment for the unit tests
+env.Append(
+ LIBPATH = [
+ '$NACL_LIB_DIR',
+ ],
+ LIBS = [
+ 'o3dCmdBuf_service',
+ 'o3dCmdBuf_common',
+ 'o3d_base',
+ ] + env['NACL_HTP_LIBS'] + env['ICU_LIBS'],
+)
+
+if env['TARGET_PLATFORM'] == 'WINDOWS':
+ env.Append(CCFLAGS = ['/Wp64'],
+ LIBS = [# System libs.
+ 'd3d9',
+ # TODO: remove link-time dependency on d3dx9, using
+ # dynamic loading instead.
+ 'd3dx9',
+ 'dxerr',
+ 'shell32'],
+ LINKFLAGS=['/SUBSYSTEM:CONSOLE'])
+ INPUTS += ['win/d3d9/effect_d3d9.cc',
+ 'win/d3d9/gapi_d3d9.cc',
+ 'win/d3d9/geometry_d3d9.cc',
+ 'win/d3d9/sampler_d3d9.cc',
+ 'win/d3d9/states_d3d9.cc',
+ 'win/d3d9/texture_d3d9.cc']
+ BIG_TEST_SERVER += ['win/big_test_main.cc']
+elif env['TARGET_PLATFORM'] == 'LINUX':
+ env.Append(LIBS = ['GL', 'GLEW', 'Cg', 'CgGL'],
+ CPPPATH = ['$CG_DIR/include'])
+ INPUTS += ['cross/gl/effect_gl.cc',
+ 'cross/gl/gapi_gl.cc',
+ 'cross/gl/geometry_gl.cc',
+ 'cross/gl/sampler_gl.cc',
+ 'cross/gl/states_gl.cc',
+ 'cross/gl/texture_gl.cc',
+ 'linux/x_utils.cc']
+ BIG_TEST_SERVER += ['linux/big_test_main.cc']
+
+# Create a target library from the sources called 'o3dCmdBuf'
+o3dcmdbuf_lib = env.ComponentLibrary('o3dCmdBuf_service', INPUTS)
+
+# TODO: why can't these be ComponentTestProgram?
+
+# Create a target executable program called 'o3dCmdBuf_bigtest_server' from the list
+# of big test server files.
+big_test_server = env.Program('o3dCmdBuf_bigtest_server', BIG_TEST_SERVER)
+
+# Copy the resulting executable to the Artifacts directory.
+env.Replicate('$ARTIFACTS_DIR', big_test_server)
+
+plugin_env = env.Clone();
+plugin_env.Append(CPPPATH = ['$NPAPI_DIR/include'])
+
+PLUGIN_INPUTS = [
+ 'cross/plugin.cc',
+ plugin_env.SharedObject(
+ 'npn_api',
+ '$NIXYSA_DIR/static_glue/npapi/npn_api.cc'),
+]
+if env['TARGET_PLATFORM'] == 'WINDOWS':
+ PLUGIN_INPUTS += ['win/plugin.def',
+ env.RES('win/plugin.rc')]
+plugin = plugin_env.SharedLibrary('npo3d_cb_plugin', PLUGIN_INPUTS)
+plugin_env.Replicate('$ARTIFACTS_DIR', plugin)
diff --git a/o3d/command_buffer/service/cross/big_test.cc b/o3d/command_buffer/service/cross/big_test.cc
new file mode 100644
index 0000000..b68a9da
--- /dev/null
+++ b/o3d/command_buffer/service/cross/big_test.cc
@@ -0,0 +1,106 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains a "big" test of the whole command buffer service, making
+// sure all the pieces fit together.
+//
+// Currently this checks that the RPC mechanism properly forwards call to the
+// service thread.
+
+#include <build/build_config.h>
+#include "command_buffer/common/cross/rpc_imc.h"
+#include "command_buffer/service/cross/big_test_helpers.h"
+#include "command_buffer/service/cross/buffer_rpc.h"
+#include "command_buffer/service/cross/cmd_buffer_engine.h"
+#include "command_buffer/service/cross/gapi_decoder.h"
+#include "native_client/service_runtime/nrd_xfer_lib/nrd_all_modules.h"
+
+namespace o3d {
+namespace command_buffer {
+
+nacl::SocketAddress g_address = { "command-buffer" };
+
+// Main function. Creates a socket, and waits for an incoming connection on it.
+// Then run the engine main loop.
+void BigTest() {
+ NaClNrdAllModulesInit();
+ GAPIDecoder decoder(g_gapi);
+ CommandBufferEngine engine(&decoder);
+ decoder.set_engine(&engine);
+ nacl::Handle server_socket = nacl::BoundSocket(&g_address);
+ nacl::Handle handles[1];
+ nacl::MessageHeader msg;
+ msg.iov = NULL;
+ msg.iov_length = 0;
+ msg.handles = handles;
+ msg.handle_count = 1;
+ int r = nacl::ReceiveDatagram(server_socket, &msg, 0);
+ DCHECK_NE(r, -1);
+ nacl::Close(server_socket);
+
+ nacl::HtpHandle htp_handle = nacl::CreateImcDesc(handles[0]);
+ IMCMessageProcessor processor(htp_handle, engine.rpc_impl());
+ engine.set_process_interface(&processor);
+ IMCSender sender(htp_handle);
+ engine.set_client_rpc(&sender);
+
+ bool result = g_gapi->Initialize();
+ DCHECK(result);
+
+ bool running = true;
+ while (running) {
+ running = ProcessSystemMessages();
+ if (!running) break;
+ // DoWork() will block if there is nothing to be done, meaning we are only
+ // going to handle message after commands are sent. It should happen at
+ // least once a frame, so it's "good enough".
+ // TODO: figure out a way to wait on the socket OR messages with
+ // MsgWaitForMultipleObjects. Asynchronous ("overlapped") read on the
+ // socket may let us do that on windows.
+ running = engine.DoWork();
+ }
+ g_gapi->Destroy();
+ nacl::Close(htp_handle);
+ NaClNrdAllModulesFini();
+}
+
+} // namespace command_buffer
+} // namespace o3d
+
+#ifdef OS_WIN
+int big_test_main(int argc, wchar_t **argv) {
+#else
+int big_test_main(int argc, char **argv) {
+#endif
+ o3d::command_buffer::BigTest();
+ return 0;
+}
diff --git a/o3d/command_buffer/service/cross/big_test_helpers.h b/o3d/command_buffer/service/cross/big_test_helpers.h
new file mode 100644
index 0000000..b32a577
--- /dev/null
+++ b/o3d/command_buffer/service/cross/big_test_helpers.h
@@ -0,0 +1,70 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains a few helper functions for running big tests.
+
+#ifndef O3D_COMMAND_BUFFER_SERVICE_CROSS_BIG_TEST_HELPERS_H__
+#define O3D_COMMAND_BUFFER_SERVICE_CROSS_BIG_TEST_HELPERS_H__
+
+#include <build/build_config.h>
+#include "core/cross/types.h"
+#include "command_buffer/common/cross/gapi_interface.h"
+
+namespace o3d {
+namespace command_buffer {
+
+extern String *g_program_path;
+extern GAPIInterface *g_gapi;
+
+// very simple thread API (hides platform-specific implementations).
+typedef void (* ThreadFunc)(void *param);
+class Thread;
+
+// Creates and starts a thread.
+Thread *CreateThread(ThreadFunc func, void* param);
+
+// Joins (waits for) a thread, destroying it.
+void JoinThread(Thread *thread);
+
+// Processes system messages. Should be called once a frame at least.
+bool ProcessSystemMessages();
+
+} // namespace command_buffer
+} // namespace o3d
+
+#ifdef OS_WIN
+int big_test_main(int argc, wchar_t **argv);
+#else
+int big_test_main(int argc, char **argv);
+#endif
+
+#endif // O3D_COMMAND_BUFFER_SERVICE_CROSS_BIG_TEST_HELPERS_H__
diff --git a/o3d/command_buffer/service/cross/buffer_rpc.cc b/o3d/command_buffer/service/cross/buffer_rpc.cc
new file mode 100644
index 0000000..c09f526
--- /dev/null
+++ b/o3d/command_buffer/service/cross/buffer_rpc.cc
@@ -0,0 +1,136 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file has the implementation of the Command Buffer Synchronous API RPC
+// glue.
+
+#include "command_buffer/common/cross/logging.h"
+#include "command_buffer/service/cross/buffer_rpc.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// Implements the dispatch function, deciding on which function to call based
+// on the message ID, taking the arguments trivially serialized in the data
+// payload.
+BufferRPCImpl::ReturnValue BufferRPCImpl::DoCall(int message_id,
+ const void *data,
+ size_t size,
+ RPCHandle const *handles,
+ size_t handle_count) {
+ switch (message_id) {
+ case INIT_CONNECTION: {
+ DCHECK_EQ(0, size);
+ DCHECK_EQ(0, handle_count);
+ handler_->InitConnection();
+ return 0;
+ }
+ case CLOSE_CONNECTION:
+ DCHECK_EQ(0, size);
+ DCHECK_EQ(0, handle_count);
+ handler_->CloseConnection();
+ return 0;
+ case REGISTER_SHARED_MEMORY: {
+ DCHECK_EQ(sizeof(size_t), size); // NOLINT
+ DCHECK_EQ(1, handle_count);
+ RPCShmHandle buffer = static_cast<RPCShmHandle>(handles[0]);
+ return handler_->RegisterSharedMemory(buffer,
+ *static_cast<const size_t *>(data));
+ }
+ case UNREGISTER_SHARED_MEMORY: {
+ DCHECK_EQ(sizeof(unsigned int), size); // NOLINT
+ DCHECK_EQ(0, handle_count);
+ unsigned int shm_id = *(static_cast<const unsigned int *>(data));
+ handler_->UnregisterSharedMemory(shm_id);
+ return 0;
+ }
+ case SET_COMMAND_BUFFER: {
+ DCHECK_EQ(sizeof(SetCommandBufferStruct), size);
+ DCHECK_EQ(0, handle_count);
+ const SetCommandBufferStruct *params =
+ static_cast<const SetCommandBufferStruct *>(data);
+ handler_->SetCommandBuffer(params->shm_id,
+ params->offset,
+ params->size,
+ params->start_get);
+ return 0;
+ }
+ case PUT: {
+ DCHECK_EQ(sizeof(CommandBufferOffset), size);
+ DCHECK_EQ(0, handle_count);
+ CommandBufferOffset offset =
+ *(static_cast<const CommandBufferOffset *>(data));
+ handler_->Put(offset);
+ return 0;
+ }
+ case GET:
+ DCHECK_EQ(0, size);
+ DCHECK_EQ(0, handle_count);
+ return handler_->Get();
+ case GET_TOKEN:
+ DCHECK_EQ(0, size);
+ DCHECK_EQ(0, handle_count);
+ return handler_->GetToken();
+ case WAIT_GET_CHANGES: {
+ DCHECK_EQ(sizeof(CommandBufferOffset), size);
+ DCHECK_EQ(0, handle_count);
+ CommandBufferOffset current_value =
+ *(static_cast<const CommandBufferOffset *>(data));
+ return handler_->WaitGetChanges(current_value);
+ }
+ case SIGNAL_GET_CHANGES: {
+ DCHECK_EQ(sizeof(SignalGetChangesStruct), size);
+ DCHECK_EQ(0, handle_count);
+ const SignalGetChangesStruct *params =
+ static_cast<const SignalGetChangesStruct *>(data);
+ handler_->SignalGetChanges(params->current_value,
+ params->rpc_message_id);
+ return 0;
+ }
+ case GET_STATUS: {
+ DCHECK_EQ(0, size);
+ DCHECK_EQ(0, handle_count);
+ return handler_->GetStatus();
+ }
+ case GET_PARSE_ERROR: {
+ DCHECK_EQ(0, size);
+ DCHECK_EQ(0, handle_count);
+ return handler_->GetParseError();
+ }
+ default:
+ LOG(FATAL) << "unsupported RPC";
+ return 0;
+ }
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/service/cross/buffer_rpc.h b/o3d/command_buffer/service/cross/buffer_rpc.h
new file mode 100644
index 0000000..f49dc0d
--- /dev/null
+++ b/o3d/command_buffer/service/cross/buffer_rpc.h
@@ -0,0 +1,101 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file defines the RPC glue for the Command Buffer Synchronous API,
+// service side: an implementation of a RPC service, forwarding calls to
+// a Command Buffer API implemention (RPC -> API).
+
+#ifndef O3D_COMMAND_BUFFER_SERVICE_CROSS_BUFFER_RPC_H__
+#define O3D_COMMAND_BUFFER_SERVICE_CROSS_BUFFER_RPC_H__
+
+#include "command_buffer/common/cross/buffer_sync_api.h"
+#include "command_buffer/common/cross/rpc.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// RPC service implementation, implementing the Command Buffer Synchronous API
+// RPC glue. This class is temporary, and will be replaced when the
+// NativeClient RPC mechanism will be available.
+//
+// The API exposed through the RPC mechanism maps 1-to-1 to BufferSyncInterface,
+// trivially serializing arguments.
+class BufferRPCImpl: public RPCImplInterface {
+ public:
+ explicit BufferRPCImpl(BufferSyncInterface *handler) : handler_(handler) {}
+ virtual ~BufferRPCImpl() {}
+
+ enum MessageId {
+ INIT_CONNECTION = RESPONSE_ID + 1,
+ CLOSE_CONNECTION,
+ REGISTER_SHARED_MEMORY,
+ UNREGISTER_SHARED_MEMORY,
+ SET_COMMAND_BUFFER,
+ PUT,
+ GET,
+ GET_TOKEN,
+ WAIT_GET_CHANGES,
+ SIGNAL_GET_CHANGES,
+ GET_STATUS,
+ GET_PARSE_ERROR,
+ };
+
+ // Structure describing the arguments for the SET_COMMAND_BUFFER RPC.
+ struct SetCommandBufferStruct {
+ unsigned int shm_id;
+ ptrdiff_t offset;
+ size_t size;
+ CommandBufferOffset start_get;
+ };
+
+ // Structure describing the arguments for the SIGNAL_GET_CHANGES RPC.
+ struct SignalGetChangesStruct {
+ CommandBufferOffset current_value;
+ int rpc_message_id;
+ };
+
+ // Implements the DoCall interface, interpreting the message with the
+ // parameters, and passing the calls with arguments to the handler.
+ virtual ReturnValue DoCall(int message_id,
+ const void * data,
+ size_t size,
+ RPCHandle const *handles,
+ size_t handle_count);
+
+ private:
+ BufferSyncInterface *handler_;
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_SERVICE_CROSS_BUFFER_RPC_H__
diff --git a/o3d/command_buffer/service/cross/buffer_rpc_test.cc b/o3d/command_buffer/service/cross/buffer_rpc_test.cc
new file mode 100644
index 0000000..42122b9
--- /dev/null
+++ b/o3d/command_buffer/service/cross/buffer_rpc_test.cc
@@ -0,0 +1,171 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// Tests for the Command Buffer RPC glue.
+
+#include "tests/common/win/testing_common.h"
+#include "command_buffer/common/cross/mocks.h"
+#include "command_buffer/service/cross/buffer_rpc.h"
+#include "command_buffer/service/cross/mocks.h"
+
+namespace o3d {
+namespace command_buffer {
+
+using testing::Return;
+
+// Test fixture for BufferRPCImpl test. Creates a BufferSyncMock and a
+// BufferRPCImpl that uses it.
+class BufferRPCImplTest : public testing::Test {
+ protected:
+ virtual void SetUp() {
+ buffer_sync_mock_.reset(new BufferSyncMock);
+ buffer_rpc_impl_.reset(new BufferRPCImpl(buffer_sync_mock_.get()));
+ }
+ virtual void TearDown() {}
+
+ BufferSyncMock &buffer_sync_mock() { return *buffer_sync_mock_.get(); }
+ BufferRPCImpl *buffer_rpc_impl() { return buffer_rpc_impl_.get(); }
+ private:
+ scoped_ptr<BufferSyncMock> buffer_sync_mock_;
+ scoped_ptr<BufferRPCImpl> buffer_rpc_impl_;
+};
+
+// Checks that the INIT_CONNECTION RPC is properly parsed.
+TEST_F(BufferRPCImplTest, TestInitConnection) {
+ EXPECT_CALL(buffer_sync_mock(), InitConnection());
+ buffer_rpc_impl()->DoCall(BufferRPCImpl::INIT_CONNECTION, NULL, 0, NULL, 0);
+}
+
+// Checks that the CLOSE_CONNECTION RPC is properly parsed.
+TEST_F(BufferRPCImplTest, TestCloseConnection) {
+ EXPECT_CALL(buffer_sync_mock(), CloseConnection());
+ buffer_rpc_impl()->DoCall(BufferRPCImpl::CLOSE_CONNECTION, NULL, 0, NULL, 0);
+}
+
+// Checks that the REGISTER_SHARED_MEMORY RPC is properly parsed and that the
+// return value is properly forwarded.
+TEST_F(BufferRPCImplTest, TestRegisterSharedMemory) {
+ RPCShmHandle shm = reinterpret_cast<RPCShmHandle>(456);
+ size_t size = 789;
+ EXPECT_CALL(buffer_sync_mock(), RegisterSharedMemory(shm, size))
+ .WillOnce(Return(1234));
+ RPCHandle handles[1] = {shm};
+ EXPECT_EQ(1234, buffer_rpc_impl()->DoCall(
+ BufferRPCImpl::REGISTER_SHARED_MEMORY, &size, sizeof(size), handles, 1));
+}
+
+// Checks that the UNREGISTER_SHARED_MEMORY RPC is properly parsed.
+TEST_F(BufferRPCImplTest, TestUnregisterSharedMemory) {
+ unsigned int shm_id = 385;
+ EXPECT_CALL(buffer_sync_mock(), UnregisterSharedMemory(shm_id));
+ buffer_rpc_impl()->DoCall(BufferRPCImpl::UNREGISTER_SHARED_MEMORY, &shm_id,
+ sizeof(shm_id), NULL, 0);
+}
+
+// Checks that the SET_COMMAND_BUFFER RPC is properly parsed.
+TEST_F(BufferRPCImplTest, TestSetCommandBuffer) {
+ EXPECT_CALL(buffer_sync_mock(), SetCommandBuffer(93, 7878, 3434, 5151));
+ BufferRPCImpl::SetCommandBufferStruct param;
+ param.shm_id = 93;
+ param.offset = 7878;
+ param.size = 3434;
+ param.start_get = 5151;
+ buffer_rpc_impl()->DoCall(BufferRPCImpl::SET_COMMAND_BUFFER, &param,
+ sizeof(param), NULL, 0);
+}
+
+// Checks that the PUT RPC is properly parsed.
+TEST_F(BufferRPCImplTest, TestPut) {
+ CommandBufferOffset offset = 8765;
+ EXPECT_CALL(buffer_sync_mock(), Put(offset));
+ buffer_rpc_impl()->DoCall(BufferRPCImpl::PUT, &offset, sizeof(offset), NULL,
+ 0);
+}
+
+// Checks that the GET RPC is properly parsed and that the return value is
+// properly forwarded.
+TEST_F(BufferRPCImplTest, TestGet) {
+ EXPECT_CALL(buffer_sync_mock(), Get()).WillOnce(Return(9375));
+ EXPECT_EQ(9375, buffer_rpc_impl()->DoCall(BufferRPCImpl::GET, NULL, 0, NULL,
+ 0));
+}
+
+// Checks that the GET_TOKEN RPC is properly parsed and that the return value is
+// properly forwarded.
+TEST_F(BufferRPCImplTest, TestGetToken) {
+ EXPECT_CALL(buffer_sync_mock(), GetToken()).WillOnce(Return(1618));
+ EXPECT_EQ(1618, buffer_rpc_impl()->DoCall(BufferRPCImpl::GET_TOKEN, NULL, 0,
+ NULL, 0));
+}
+
+// Checks that the WAIT_GET_CHANGES RPC is properly parsed and that the return
+// value is properly forwarded.
+TEST_F(BufferRPCImplTest, TestWaitGetChanges) {
+ CommandBufferOffset value = 339;
+ EXPECT_CALL(buffer_sync_mock(), WaitGetChanges(value))
+ .WillOnce(Return(16180));
+ EXPECT_EQ(16180, buffer_rpc_impl()->DoCall(BufferRPCImpl::WAIT_GET_CHANGES,
+ &value, sizeof(value), NULL, 0));
+}
+
+// Checks that the SIGNAL_GET_CHANGES RPC is properly parsed.
+TEST_F(BufferRPCImplTest, TestSignalGetChanges) {
+ EXPECT_CALL(buffer_sync_mock(), SignalGetChanges(34, 21));
+ BufferRPCImpl::SignalGetChangesStruct param;
+ param.current_value = 34;
+ param.rpc_message_id = 21;
+ buffer_rpc_impl()->DoCall(BufferRPCImpl::SIGNAL_GET_CHANGES, &param,
+ sizeof(param), NULL, 0);
+}
+
+// Checks that the GET_STATUS RPC is properly parsed and that the return value
+// is properly forwarded.
+TEST_F(BufferRPCImplTest, TestGetStatus) {
+ EXPECT_CALL(buffer_sync_mock(), GetStatus())
+ .WillOnce(Return(BufferSyncInterface::PARSE_ERROR));
+ EXPECT_EQ(BufferSyncInterface::PARSE_ERROR,
+ buffer_rpc_impl()->DoCall(BufferRPCImpl::GET_STATUS, NULL, 0, NULL,
+ 0));
+}
+
+// Checks that the GET_STATUS RPC is properly parsed and that the return value
+// is properly forwarded.
+TEST_F(BufferRPCImplTest, TestGetParseError) {
+ EXPECT_CALL(buffer_sync_mock(), GetParseError())
+ .WillOnce(Return(BufferSyncInterface::PARSE_OUT_OF_BOUNDS));
+ EXPECT_EQ(BufferSyncInterface::PARSE_OUT_OF_BOUNDS,
+ buffer_rpc_impl()->DoCall(BufferRPCImpl::GET_PARSE_ERROR, NULL, 0,
+ NULL, 0));
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/service/cross/cmd_buffer_engine.cc b/o3d/command_buffer/service/cross/cmd_buffer_engine.cc
new file mode 100644
index 0000000..d96c63d
--- /dev/null
+++ b/o3d/command_buffer/service/cross/cmd_buffer_engine.cc
@@ -0,0 +1,290 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the implementation of the command buffer engine.
+
+#include "command_buffer/service/cross/buffer_rpc.h"
+#include "command_buffer/service/cross/cmd_buffer_engine.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// Creates a RPC implementation using 'this' as the handler, and a RPC server
+// for it.
+CommandBufferEngine::CommandBufferEngine(AsyncAPIInterface *handler)
+ : buffer_rpc_impl_(),
+ process_interface_(NULL),
+ parser_(),
+ handler_(handler),
+ client_rpc_(NULL),
+ token_(0),
+ status_(NOT_CONNECTED),
+ signal_change_(false),
+ signal_rpc_message_id_(0),
+ parse_error_(PARSE_NO_ERROR) {
+ buffer_rpc_impl_.reset(new BufferRPCImpl(this));
+}
+
+CommandBufferEngine::~CommandBufferEngine() {}
+
+// Inits the connection. Registers the client RPC service.
+void CommandBufferEngine::InitConnection() {
+ status_ = NO_BUFFER;
+}
+
+// Closes the connection. Executes all remaining commands.
+void CommandBufferEngine::CloseConnection() {
+ FinishParsing();
+ status_ = NOT_CONNECTED;
+ parser_.reset(NULL);
+}
+
+// Adds the shared memory buffer somewhere into the list, return the index in
+// the list as the handle. Either find a hole in the list, or add it at the
+// end. We don't want to invalidate exiting indices.
+unsigned int CommandBufferEngine::RegisterSharedMemory(
+ RPCShmHandle handle,
+ size_t size) {
+ void *address = MapShm(handle, size);
+ if (!address) return kInvalidSharedMemoryId;
+ MemoryMapping mapping = {address, size};
+ for (unsigned int i = 0; i < shared_memory_buffers_.size(); ++i) {
+ if (shared_memory_buffers_[i].address == NULL) {
+ shared_memory_buffers_[i] = mapping;
+ return i;
+ }
+ }
+ shared_memory_buffers_.push_back(mapping);
+ return static_cast<unsigned int>(shared_memory_buffers_.size() - 1);
+}
+
+// Sets the list entry for the shared memory buffer to NULL. Don't erase() the
+// entry, We don't want to invalidate exiting indices.
+void CommandBufferEngine::UnregisterSharedMemory(unsigned int shm_id) {
+ if ((shm_id >= shared_memory_buffers_.size()) ||
+ !shared_memory_buffers_[shm_id].size) {
+ LOG(ERROR) << "Trying to unregister a non-registered shared memory";
+ return;
+ }
+ MemoryMapping &mapping = shared_memory_buffers_[shm_id];
+ UnmapShm(mapping.address, mapping.size);
+ mapping.address = NULL;
+ mapping.size = 0;
+}
+
+// Sets the command buffer. Executes all remaining commands in the old buffer
+// (if any) and creates a new command parser.
+void CommandBufferEngine::SetCommandBuffer(unsigned int shm_id,
+ ptrdiff_t offset,
+ size_t size,
+ CommandBufferOffset start_get) {
+ if ((shm_id >= shared_memory_buffers_.size()) ||
+ !shared_memory_buffers_[shm_id].size) {
+ LOG(ERROR) << "Trying to set the command buffer from a non-registered "
+ << "shared memory";
+ return;
+ }
+ if (status_ == NOT_CONNECTED) return;
+ FinishParsing();
+ parser_.reset(new CommandParser(shared_memory_buffers_[shm_id].address,
+ shared_memory_buffers_[shm_id].size, offset,
+ size, start_get, handler_));
+ status_ = PARSING;
+ parse_error_ = PARSE_NO_ERROR;
+}
+
+// Changes the put value.
+void CommandBufferEngine::Put(CommandBufferOffset offset) {
+ if (parser_.get()) {
+ parser_->set_put(offset);
+ }
+}
+
+// Retrieves the get value. This returns -1 if there is no current parser.
+CommandBufferOffset CommandBufferEngine::Get() {
+ if (parser_.get()) {
+ return parser_->get();
+ } else {
+ return -1;
+ }
+}
+
+// Retrieves the current token value.
+unsigned int CommandBufferEngine::GetToken() {
+ return token_;
+}
+
+// Executes commands until get is different from the value passed in. It will
+// return immediately if the get value is already different, or if the engine
+// is not in the PARSING status, or if the buffer is empty. It will return -1
+// if there is no current buffer.
+CommandBufferOffset CommandBufferEngine::WaitGetChanges(
+ CommandBufferOffset current_value) {
+ if (parser_.get()) {
+ while (status_ == PARSING &&
+ parser_->get() == current_value &&
+ !parser_->IsEmpty()) {
+ ProcessOneCommand();
+ }
+ return parser_->get();
+ } else {
+ return -1;
+ }
+}
+
+// Signals the client when get gets different from the value passed in. If get
+// is already different, or if the engine is not in the PARSING status, that
+// will happen immediately, otherwise it will happen when commands get
+// executed, moving the get pointer.
+void CommandBufferEngine::SignalGetChanges(CommandBufferOffset current_value,
+ int rpc_message_id) {
+ if (status_ != PARSING || parser_->get() != current_value) {
+ DoSignalChangedGet(rpc_message_id);
+ } else {
+ signal_change_ = true;
+ signal_rpc_message_id_ = rpc_message_id;
+ }
+}
+
+// Gets the memory address from the list entry.
+void *CommandBufferEngine::GetSharedMemoryAddress(unsigned int shm_id) {
+ if ((shm_id >= shared_memory_buffers_.size()) ||
+ !shared_memory_buffers_[shm_id].size) {
+ LOG(ERROR) << "Trying to get the address of a non-registered shared memory";
+ return NULL;
+ }
+ return shared_memory_buffers_[shm_id].address;
+}
+
+// Gets the memory size from the list entry.
+size_t CommandBufferEngine::GetSharedMemorySize(unsigned int shm_id) {
+ if ((shm_id >= shared_memory_buffers_.size()) ||
+ !shared_memory_buffers_[shm_id].size) {
+ LOG(ERROR) << "Trying to get the size of a non-registered shared memory";
+ return 0;
+ }
+ return shared_memory_buffers_[shm_id].size;
+}
+
+// Gets the status.
+BufferSyncInterface::ParserStatus CommandBufferEngine::GetStatus() {
+ return status_;
+}
+
+// Gets the current parse error, reset it to PARSE_NO_ERROR.
+BufferSyncInterface::ParseError CommandBufferEngine::GetParseError() {
+ ParseError error = parse_error_;
+ parse_error_ = PARSE_NO_ERROR;
+ return error;
+}
+
+// Finishes parsing, executing all the commands until the buffer is empty, or a
+// parsing error occurs.
+void CommandBufferEngine::FinishParsing() {
+ // terminates current parsing, that is, execute all the commands
+ // NOTE: status_ == PARSING implies parser_ != NULL
+ while (status_ == PARSING && !parser_->IsEmpty()) {
+ ProcessOneCommand();
+ }
+}
+
+// Processes one command from the command buffer. This must only be called when
+// in the PARSING status.
+// This will update the status_ and the parse_error_ fields if an error occurs.
+void CommandBufferEngine::ProcessOneCommand() {
+ DCHECK_EQ(PARSING, status_);
+ DCHECK(parser_.get());
+ ParseError result = parser_->ProcessCommand();
+ switch (result) {
+ case PARSE_NO_ERROR:
+ break;
+ case PARSE_OUT_OF_BOUNDS:
+ case PARSE_INVALID_SIZE:
+ status_ = PARSE_ERROR;
+ // Always override the error, to properly signal the stopping condition.
+ parse_error_ = result;
+ break;
+ case PARSE_INVALID_ARGUMENTS:
+ case PARSE_UNKNOWN_COMMAND:
+ // Only set the error if it is not set already.
+ if (parse_error_ == PARSE_NO_ERROR) {
+ parse_error_ = result;
+ }
+ break;
+ }
+ // get has changed, signal the client if needed.
+ if (signal_change_) {
+ DoSignalChangedGet(signal_rpc_message_id_);
+ signal_change_ = false;
+ }
+}
+
+// Executes the main loop. While there are commands in the buffer, processes
+// them one by one, checking for RPC messages between each of them (executing
+// all of them). If the buffer is empty, block until a RPC message comes.
+void CommandBufferEngine::DoMainLoop() {
+ while (DoWork()) { }
+ // Clean up if needed: execute all pending commands, then close the
+ // connection.
+ if (status_ != NOT_CONNECTED) CloseConnection();
+}
+
+bool CommandBufferEngine::HasWork() {
+ return (status_ == PARSING && !parser_->IsEmpty()) ||
+ process_interface_->HasMessage();
+}
+
+bool CommandBufferEngine::DoWork() {
+ if (status_ == PARSING && !parser_->IsEmpty()) {
+ bool running = true;
+ // process as many messages as available but do not block.
+ while (process_interface_->HasMessage()) {
+ running = process_interface_->ProcessMessage();
+ }
+ if (running) ProcessOneCommand();
+ return running;
+ } else {
+ // call ProcessMessage, always blocking. We have nothing else to do.
+ return process_interface_->ProcessMessage();
+ }
+}
+
+// Signals that get has changed, sending a RPC message back to the client. It
+// will send -1 if there is no current buffer.
+void CommandBufferEngine::DoSignalChangedGet(int rpc_message_id) {
+ DCHECK(client_rpc_);
+ CommandBufferOffset get = parser_.get() ? parser_->get() : -1;
+ client_rpc_->SendCall(rpc_message_id, &get, sizeof(get), NULL, 0);
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/service/cross/cmd_buffer_engine.h b/o3d/command_buffer/service/cross/cmd_buffer_engine.h
new file mode 100644
index 0000000..66cab72
--- /dev/null
+++ b/o3d/command_buffer/service/cross/cmd_buffer_engine.h
@@ -0,0 +1,214 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file defines the CommandBufferEngine class, providing the main loop for
+// the service, exposing the RPC API, managing the command parser.
+
+#ifndef O3D_COMMAND_BUFFER_SERVICE_CROSS_CMD_BUFFER_ENGINE_H__
+#define O3D_COMMAND_BUFFER_SERVICE_CROSS_CMD_BUFFER_ENGINE_H__
+
+#include <vector>
+#include "base/scoped_ptr.h"
+#include "command_buffer/common/cross/buffer_sync_api.h"
+#include "command_buffer/service/cross/cmd_parser.h"
+
+namespace o3d {
+namespace command_buffer {
+
+class BufferRPCImpl;
+
+class CommandBufferEngine : public BufferSyncInterface {
+ public:
+ explicit CommandBufferEngine(AsyncAPIInterface *handler);
+ virtual ~CommandBufferEngine();
+
+ // Initializes the connection with the client.
+ virtual void InitConnection();
+
+ // Closes the connection with the client.
+ virtual void CloseConnection();
+
+ // Registers a shared memory buffer. While a buffer is registered, it can be
+ // accessed by the service, including the underlying asynchronous API,
+ // through a single identifier.
+ // Parameters:
+ // buffer: the shared memory buffer handle.
+ // Returns:
+ // an identifier for the shared memory.
+ virtual unsigned int RegisterSharedMemory(RPCShmHandle buffer, size_t size);
+
+ // Unregisters a shared memory buffer.
+ // Parameters:
+ // shm_id: the identifier for the shared memory buffer.
+ virtual void UnregisterSharedMemory(unsigned int shm_id);
+
+ // Initializes the command buffer.
+ // Parameters:
+ // buffer: the memory buffer descriptor in which the command buffer
+ // resides.
+ // offset: the offset of the command buffer, relative to the memory
+ // buffer.
+ // size: the size of the command buffer.
+ // start_get: the inital value for the Get pointer, relative to the
+ // command buffer, where the parser will start interpreting
+ // commands. Put is also initialized to that value.
+ virtual void SetCommandBuffer(unsigned int shm_id,
+ ptrdiff_t offset,
+ size_t size,
+ CommandBufferOffset start_get);
+
+ // Sets the value of the Put pointer.
+ // Parameters:
+ // offset: the new value of the Put pointer, as an offset into the command
+ // buffer.
+ virtual void Put(CommandBufferOffset offset);
+
+ // Gets the value of the Get pointer.
+ // Returns:
+ // the current value of the Get pointer, as an offset into the command
+ // buffer.
+ virtual CommandBufferOffset Get();
+
+ // Gets the current token value.
+ // Returns:
+ // the current token value.
+ virtual unsigned int GetToken();
+
+ // Waits until Get changes from the currently known value.
+ // Parameters:
+ // current_value: the currently known value. This call will block until
+ // Get is different from that value (returning immediately
+ // if it is already different).
+ // Returns:
+ // the current (changed) value of Get.
+ virtual CommandBufferOffset WaitGetChanges(
+ CommandBufferOffset current_value);
+
+ // Asks the service to signal the client when Get changes from the currently
+ // known value. This is a non-blocking version of WaitGetChanges.
+ // Parameters:
+ // current_value: the currently known value of Get.
+ // rpc_message_id: the RPC message ID to call on the client when Get is
+ // different from current_value. That RPC is called
+ // immediately if Get is already different from
+ // current_value.
+ virtual void SignalGetChanges(CommandBufferOffset current_value,
+ int rpc_message_id);
+
+ // Gets the status of the service.
+ // Returns:
+ // The status of the service.
+ virtual ParserStatus GetStatus();
+
+ // Gets the current parse error. The current parse error is set when the
+ // service is in the PARSE_ERROR status. It may also be set while in the
+ // PARSING state, if a recoverable error (like PARSE_UNKNOWN_METHOD) was
+ // encountered. Getting the error resets it to PARSE_NO_ERROR.
+ // Returns:
+ // The current parse error.
+ virtual ParseError GetParseError();
+
+ // Gets the base address of a registered shared memory buffer.
+ // Parameters:
+ // shm_id: the identifier for the shared memory buffer.
+ void *GetSharedMemoryAddress(unsigned int shm_id);
+
+ // Gets the size of a registered shared memory buffer.
+ // Parameters:
+ // shm_id: the identifier for the shared memory buffer.
+ size_t GetSharedMemorySize(unsigned int shm_id);
+
+ // Executes the main loop: parse commands and execute RPC calls until the
+ // server is killed.
+ void DoMainLoop();
+
+ // Returns whether or not the engine has work to do (process synchronous or
+ // asynchronous commands).
+ bool HasWork();
+
+ // Does some work (process synchronous or asynchronous commands). It will not
+ // block if HasWork() returns true.
+ // Returns:
+ // true if the engine should keep running, false if it has been sent a
+ // command to terminate.
+ bool DoWork();
+
+ // Gets the RPC server.
+ BufferRPCImpl *rpc_impl() const { return buffer_rpc_impl_.get(); }
+
+ // Sets the RPC processing interface.
+ void set_process_interface(RPCProcessInterface *iface) {
+ process_interface_ = iface;
+ }
+
+ // Sets the RPC processing interface.
+ void set_client_rpc(RPCSendInterface *iface) {
+ client_rpc_ = iface;
+ }
+
+ // Gets the command parser.
+ CommandParser *parser() const { return parser_.get(); }
+
+ // Sets the token value.
+ void set_token(unsigned int token) { token_ = token; }
+ private:
+
+ // Processes one command from the command buffer.
+ void ProcessOneCommand();
+
+ // Sends the signal that get has changed to the client.
+ void DoSignalChangedGet(int rpc_message_id);
+
+ // Finish parsing and executing all the commands in the buffer.
+ void FinishParsing();
+
+ scoped_ptr<BufferRPCImpl> buffer_rpc_impl_;
+ RPCProcessInterface *process_interface_;
+ scoped_ptr<CommandParser> parser_;
+ AsyncAPIInterface *handler_;
+ RPCSendInterface *client_rpc_;
+ unsigned int token_;
+ ParserStatus status_;
+ bool signal_change_;
+ int signal_rpc_message_id_;
+ ParseError parse_error_;
+ struct MemoryMapping {
+ void *address;
+ size_t size;
+ };
+ std::vector<MemoryMapping> shared_memory_buffers_;
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_SERVICE_CROSS_CMD_BUFFER_ENGINE_H__
diff --git a/o3d/command_buffer/service/cross/cmd_buffer_engine_test.cc b/o3d/command_buffer/service/cross/cmd_buffer_engine_test.cc
new file mode 100644
index 0000000..14f56ec
--- /dev/null
+++ b/o3d/command_buffer/service/cross/cmd_buffer_engine_test.cc
@@ -0,0 +1,626 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// Tests for the Command Buffer Engine.
+
+#include "tests/common/win/testing_common.h"
+#include "command_buffer/service/cross/cmd_buffer_engine.h"
+#include "command_buffer/service/cross/mocks.h"
+
+namespace o3d {
+namespace command_buffer {
+
+using testing::AnyNumber;
+using testing::Return;
+using testing::Mock;
+using testing::Truly;
+using testing::Sequence;
+using testing::_;
+
+// Test fixture for CommandBufferEngine test - Creates a CommandBufferEngine,
+// using a mock AsyncAPIInterface.
+class CommandBufferEngineTest : public testing::Test {
+ protected:
+ CommandBufferEngineTest()
+ : shm_(kRPCInvalidHandle),
+ shm_id_(BufferSyncInterface::kInvalidSharedMemoryId) {}
+
+ virtual void SetUp() {
+ api_mock_.reset(new AsyncAPIMock);
+ engine_.reset(new CommandBufferEngine(api_mock_.get()));
+ process_mock_.reset(new RPCProcessMock());
+ engine_->set_process_interface(process_mock_.get());
+ }
+ virtual void TearDown() {
+ }
+
+ // Creates a shared memory buffer for the command buffer, and pass it to the
+ // engine.
+ CommandBufferEntry *InitCommandBuffer(size_t entries, unsigned int start) {
+ CHECK(shm_ == kRPCInvalidHandle);
+ CHECK(shm_id_ == BufferSyncInterface::kInvalidSharedMemoryId);
+ const size_t kShmSize = entries * sizeof(CommandBufferEntry); // NOLINT
+ shm_ = CreateShm(kShmSize);
+ EXPECT_NE(kRPCInvalidHandle, shm_);
+ if (kRPCInvalidHandle == shm_) return NULL;
+ shm_id_ = engine()->RegisterSharedMemory(shm_, kShmSize);
+ EXPECT_NE(BufferSyncInterface::kInvalidSharedMemoryId, shm_id_);
+ if (shm_id_ == BufferSyncInterface::kInvalidSharedMemoryId) {
+ DestroyShm(shm_);
+ shm_ = kRPCInvalidHandle;
+ return NULL;
+ }
+ engine()->SetCommandBuffer(shm_id_, 0, kShmSize, start);
+ return static_cast<CommandBufferEntry *>(
+ engine()->GetSharedMemoryAddress(shm_id_));
+ }
+
+ // Destroys the command buffer.
+ void DestroyCommandBuffer() {
+ engine()->UnregisterSharedMemory(shm_id_);
+ shm_id_ = BufferSyncInterface::kInvalidSharedMemoryId;
+ DestroyShm(shm_);
+ shm_ = kRPCInvalidHandle;
+ }
+
+ // Adds a command to the buffer, while adding it as an expected call on the
+ // API mock.
+ unsigned int AddCommandWithExpect(CommandBufferEntry *buffer,
+ BufferSyncInterface::ParseError _return,
+ unsigned int command,
+ unsigned int arg_count,
+ CommandBufferEntry *args) {
+ unsigned int put = 0;
+ CommandHeader header;
+ header.size = arg_count + 1;
+ header.command = command;
+ buffer[put++].value_header = header;
+ for (unsigned int i = 0; i < arg_count; ++i) {
+ buffer[put++].value_uint32 = args[i].value_uint32;
+ }
+ EXPECT_CALL(*api_mock(), DoCommand(command, arg_count,
+ Truly(AsyncAPIMock::IsArgs(arg_count, args))))
+ .InSequence(sequence_)
+ .WillOnce(Return(_return));
+ return put;
+ }
+
+ CommandBufferEngine *engine() { return engine_.get(); }
+ RPCProcessMock *process_mock() { return process_mock_.get(); }
+ AsyncAPIMock *api_mock() { return api_mock_.get(); }
+ private:
+ scoped_ptr<AsyncAPIMock> api_mock_;
+ scoped_ptr<CommandBufferEngine> engine_;
+ scoped_ptr<RPCProcessMock> process_mock_;
+ // handles for the command buffer.
+ RPCShmHandle shm_;
+ unsigned int shm_id_;
+ Sequence sequence_;
+};
+
+// Tests the initialization/termination sequence, checking that it sets the
+// engine in the correct states.
+TEST_F(CommandBufferEngineTest, TestInitialization) {
+ // Check initial state
+ EXPECT_TRUE(engine()->rpc_impl() != NULL);
+ EXPECT_TRUE(engine()->parser() == NULL);
+ EXPECT_EQ(BufferSyncInterface::NOT_CONNECTED, engine()->GetStatus());
+ EXPECT_EQ(BufferSyncInterface::PARSE_NO_ERROR, engine()->GetParseError());
+ EXPECT_EQ(-1, engine()->Get());
+ EXPECT_EQ(0, engine()->GetToken());
+
+ engine()->InitConnection();
+ EXPECT_EQ(BufferSyncInterface::NO_BUFFER, engine()->GetStatus());
+ EXPECT_EQ(BufferSyncInterface::PARSE_NO_ERROR, engine()->GetParseError());
+ EXPECT_EQ(-1, engine()->Get());
+
+ CommandBufferEntry *entries = InitCommandBuffer(25, 5);
+ ASSERT_TRUE(entries != NULL);
+
+ EXPECT_EQ(BufferSyncInterface::PARSING, engine()->GetStatus());
+ EXPECT_EQ(BufferSyncInterface::PARSE_NO_ERROR, engine()->GetParseError());
+ EXPECT_EQ(5, engine()->Get());
+ EXPECT_TRUE(engine()->parser() != NULL);
+
+ engine()->set_token(5678);
+ EXPECT_EQ(5678, engine()->GetToken());
+
+ engine()->CloseConnection();
+ DestroyCommandBuffer();
+
+ EXPECT_EQ(BufferSyncInterface::NOT_CONNECTED, engine()->GetStatus());
+ EXPECT_EQ(BufferSyncInterface::PARSE_NO_ERROR, engine()->GetParseError());
+ EXPECT_EQ(-1, engine()->Get());
+ EXPECT_TRUE(engine()->parser() == NULL);
+}
+
+// Checks that shared memory registration works.
+TEST_F(CommandBufferEngineTest, TestSharedMemoryRegistration) {
+ // Create and register a first shared memory buffer.
+ const size_t kShmSize1 = 10;
+ RPCShmHandle shm1 = CreateShm(kShmSize1);
+ ASSERT_NE(kRPCInvalidHandle, shm1);
+ unsigned int shm_id1 = engine()->RegisterSharedMemory(shm1, kShmSize1);
+ EXPECT_NE(BufferSyncInterface::kInvalidSharedMemoryId, shm_id1);
+ EXPECT_TRUE(engine()->GetSharedMemoryAddress(shm_id1) != NULL);
+ EXPECT_EQ(kShmSize1, engine()->GetSharedMemorySize(shm_id1));
+
+ // Create and register a second shared memory buffer, check that it has a
+ // different memory location than the first one.
+ const size_t kShmSize2 = 25;
+ RPCShmHandle shm2 = CreateShm(kShmSize2);
+ ASSERT_NE(kRPCInvalidHandle, shm2);
+ unsigned int shm_id2 = engine()->RegisterSharedMemory(shm2, kShmSize2);
+ EXPECT_NE(BufferSyncInterface::kInvalidSharedMemoryId, shm_id2);
+ EXPECT_TRUE(engine()->GetSharedMemoryAddress(shm_id2) != NULL);
+ EXPECT_EQ(kShmSize2, engine()->GetSharedMemorySize(shm_id2));
+ EXPECT_NE(shm_id1, shm_id2);
+ EXPECT_NE(engine()->GetSharedMemoryAddress(shm_id1),
+ engine()->GetSharedMemoryAddress(shm_id2));
+
+ // Create and register a third shared memory buffer, check that it has a
+ // different memory location than the first and second ones.
+ const size_t kShmSize3 = 33;
+ RPCShmHandle shm3 = CreateShm(kShmSize3);
+ ASSERT_NE(kRPCInvalidHandle, shm3);
+ unsigned int shm_id3 = engine()->RegisterSharedMemory(shm3, kShmSize3);
+ EXPECT_NE(BufferSyncInterface::kInvalidSharedMemoryId, shm_id3);
+ EXPECT_TRUE(engine()->GetSharedMemoryAddress(shm_id3) != NULL);
+ EXPECT_EQ(kShmSize3, engine()->GetSharedMemorySize(shm_id3));
+ EXPECT_NE(shm_id1, shm_id3);
+ EXPECT_NE(shm_id2, shm_id3);
+ EXPECT_NE(engine()->GetSharedMemoryAddress(shm_id1),
+ engine()->GetSharedMemoryAddress(shm_id3));
+ EXPECT_NE(engine()->GetSharedMemoryAddress(shm_id2),
+ engine()->GetSharedMemoryAddress(shm_id3));
+
+ engine()->UnregisterSharedMemory(shm_id1);
+ EXPECT_EQ(NULL, engine()->GetSharedMemoryAddress(shm_id1));
+ EXPECT_EQ(0UL, engine()->GetSharedMemorySize(shm_id1));
+ DestroyShm(shm1);
+
+ engine()->UnregisterSharedMemory(shm_id2);
+ EXPECT_EQ(NULL, engine()->GetSharedMemoryAddress(shm_id2));
+ EXPECT_EQ(0UL, engine()->GetSharedMemorySize(shm_id2));
+ DestroyShm(shm2);
+
+ engine()->UnregisterSharedMemory(shm_id3);
+ EXPECT_EQ(NULL, engine()->GetSharedMemoryAddress(shm_id2));
+ EXPECT_EQ(0UL, engine()->GetSharedMemorySize(shm_id2));
+ DestroyShm(shm3);
+}
+
+// Checks that commands in the buffer are properly executed, and that the
+// status/error stay valid.
+TEST_F(CommandBufferEngineTest, TestCommandProcessing) {
+ engine()->InitConnection();
+ CommandBufferEntry *entries = InitCommandBuffer(10, 0);
+ ASSERT_TRUE(entries != NULL);
+
+ CommandBufferOffset get = engine()->Get();
+ CommandBufferOffset put = get;
+
+ // Create a command buffer with 3 commands
+ put += AddCommandWithExpect(entries + put,
+ BufferSyncInterface::PARSE_NO_ERROR,
+ 0,
+ 0,
+ NULL);
+
+ CommandBufferEntry args1[2];
+ args1[0].value_uint32 = 3;
+ args1[1].value_float = 4.f;
+ put += AddCommandWithExpect(entries + put,
+ BufferSyncInterface::PARSE_NO_ERROR,
+ 1,
+ 2,
+ args1);
+
+ CommandBufferEntry args2[2];
+ args2[0].value_uint32 = 5;
+ args2[1].value_float = 6.f;
+ put += AddCommandWithExpect(entries + put,
+ BufferSyncInterface::PARSE_NO_ERROR,
+ 2,
+ 2,
+ args2);
+
+ engine()->Put(put);
+ while (get != put) {
+ // Check that the parsing progresses, and that no error occurs.
+ CommandBufferOffset new_get = engine()->WaitGetChanges(get);
+ EXPECT_NE(get, new_get);
+ ASSERT_EQ(BufferSyncInterface::PARSING, engine()->GetStatus());
+ EXPECT_EQ(BufferSyncInterface::PARSE_NO_ERROR, engine()->GetParseError());
+ EXPECT_EQ(new_get, engine()->Get());
+ get = new_get;
+ }
+ // Check that the commands did happen.
+ Mock::VerifyAndClearExpectations(api_mock());
+
+ engine()->CloseConnection();
+ DestroyCommandBuffer();
+}
+
+// Checks that commands in the buffer are properly executed when wrapping the
+// buffer, and that the status/error stay valid.
+TEST_F(CommandBufferEngineTest, TestCommandWrapping) {
+ engine()->InitConnection();
+ CommandBufferEntry *entries = InitCommandBuffer(10, 6);
+ ASSERT_TRUE(entries != NULL);
+
+ CommandBufferOffset get = engine()->Get();
+ CommandBufferOffset put = get;
+
+ // Create a command buffer with 3 commands
+ put += AddCommandWithExpect(entries + put,
+ BufferSyncInterface::PARSE_NO_ERROR,
+ 0,
+ 0,
+ NULL);
+
+ CommandBufferEntry args1[2];
+ args1[0].value_uint32 = 3;
+ args1[1].value_float = 4.f;
+ put += AddCommandWithExpect(entries + put,
+ BufferSyncInterface::PARSE_NO_ERROR,
+ 1,
+ 2,
+ args1);
+ DCHECK_EQ(10, put);
+ put = 0;
+
+ CommandBufferEntry args2[2];
+ args2[0].value_uint32 = 5;
+ args2[1].value_float = 6.f;
+ put += AddCommandWithExpect(entries + put,
+ BufferSyncInterface::PARSE_NO_ERROR,
+ 2,
+ 2,
+ args2);
+
+ engine()->Put(put);
+ while (get != put) {
+ // Check that the parsing progresses, and that no error occurs.
+ CommandBufferOffset new_get = engine()->WaitGetChanges(get);
+ EXPECT_NE(get, new_get);
+ ASSERT_EQ(BufferSyncInterface::PARSING, engine()->GetStatus());
+ EXPECT_EQ(BufferSyncInterface::PARSE_NO_ERROR, engine()->GetParseError());
+ EXPECT_EQ(new_get, engine()->Get());
+ get = new_get;
+ }
+ // Check that the commands did happen.
+ Mock::VerifyAndClearExpectations(api_mock());
+
+ engine()->CloseConnection();
+ DestroyCommandBuffer();
+}
+
+// Checks that commands in the buffer are properly executed when we change the
+// buffer, and when we close the connection.
+TEST_F(CommandBufferEngineTest, TestSetBufferAndClose) {
+ engine()->InitConnection();
+ CommandBufferEntry *entries = InitCommandBuffer(10, 0);
+ ASSERT_TRUE(entries != NULL);
+
+ CommandBufferOffset get = engine()->Get();
+ CommandBufferOffset put = get;
+
+ // Create a command buffer with 3 commands
+ put += AddCommandWithExpect(entries + put,
+ BufferSyncInterface::PARSE_NO_ERROR,
+ 0,
+ 0,
+ NULL);
+
+ CommandBufferEntry args1[2];
+ args1[0].value_uint32 = 3;
+ args1[1].value_float = 4.f;
+ put += AddCommandWithExpect(entries + put,
+ BufferSyncInterface::PARSE_NO_ERROR,
+ 1,
+ 2,
+ args1);
+
+ CommandBufferEntry args2[2];
+ args2[0].value_uint32 = 5;
+ args2[1].value_float = 6.f;
+ put += AddCommandWithExpect(entries + put,
+ BufferSyncInterface::PARSE_NO_ERROR,
+ 2,
+ 2,
+ args2);
+
+ engine()->Put(put);
+
+ // Setup a new buffer.
+ const size_t kShmSize = 10 * sizeof(CommandBufferEntry); // NOLINT
+ RPCShmHandle shm = CreateShm(kShmSize);
+ ASSERT_NE(kRPCInvalidHandle, shm);
+ unsigned int shm_id = engine()->RegisterSharedMemory(shm, kShmSize);
+ ASSERT_NE(BufferSyncInterface::kInvalidSharedMemoryId, shm_id);
+ CommandBufferEntry *entries2 = static_cast<CommandBufferEntry *>(
+ engine()->GetSharedMemoryAddress(shm_id));
+ engine()->SetCommandBuffer(shm_id, 0, kShmSize, 0);
+ EXPECT_EQ(BufferSyncInterface::PARSING, engine()->GetStatus());
+ EXPECT_EQ(BufferSyncInterface::PARSE_NO_ERROR, engine()->GetParseError());
+ EXPECT_EQ(0, engine()->Get());
+
+ // Destroy the old command buffer.
+ DestroyCommandBuffer();
+
+ get = engine()->Get();
+ put = get;
+ put += AddCommandWithExpect(entries2 + put,
+ BufferSyncInterface::PARSE_NO_ERROR,
+ 1,
+ 2,
+ args1);
+
+ engine()->Put(put);
+
+ engine()->CloseConnection();
+ // Check that all the commands did happen.
+ Mock::VerifyAndClearExpectations(api_mock());
+
+ engine()->UnregisterSharedMemory(shm_id);
+ DestroyShm(shm);
+}
+
+// Checks that commands in the buffer are properly executed, even if they
+// generate a recoverable error. Check that the error status is properly set,
+// and reset when queried.
+TEST_F(CommandBufferEngineTest, TestRecoverableError) {
+ engine()->InitConnection();
+ CommandBufferEntry *entries = InitCommandBuffer(10, 0);
+ ASSERT_TRUE(entries != NULL);
+
+ CommandBufferOffset get = engine()->Get();
+ CommandBufferOffset put = get;
+
+ // Create a command buffer with 3 commands, 2 of them generating errors
+ put += AddCommandWithExpect(entries + put,
+ BufferSyncInterface::PARSE_NO_ERROR,
+ 0,
+ 0,
+ NULL);
+
+ CommandBufferEntry args1[2];
+ args1[0].value_uint32 = 3;
+ args1[1].value_float = 4.f;
+ put += AddCommandWithExpect(entries + put,
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS,
+ 1,
+ 2,
+ args1);
+
+ CommandBufferEntry args2[2];
+ args2[0].value_uint32 = 5;
+ args2[1].value_float = 6.f;
+ put += AddCommandWithExpect(entries + put,
+ BufferSyncInterface::PARSE_UNKNOWN_COMMAND,
+ 2,
+ 2,
+ args2);
+
+ engine()->Put(put);
+ while (get != put) {
+ // Check that the parsing progresses, and that no error occurs.
+ CommandBufferOffset new_get = engine()->WaitGetChanges(get);
+ EXPECT_NE(get, new_get);
+ ASSERT_EQ(BufferSyncInterface::PARSING, engine()->GetStatus());
+ EXPECT_EQ(new_get, engine()->Get());
+ get = new_get;
+ }
+ // Check that the commands did happen.
+ Mock::VerifyAndClearExpectations(api_mock());
+
+ // Check that the error status was set to the first error.
+ EXPECT_EQ(BufferSyncInterface::PARSE_INVALID_ARGUMENTS,
+ engine()->GetParseError());
+ // Check that the error status was reset after the query.
+ EXPECT_EQ(BufferSyncInterface::PARSE_NO_ERROR, engine()->GetParseError());
+
+ engine()->CloseConnection();
+ DestroyCommandBuffer();
+}
+
+// Checks that commands in the buffer are properly executed up to the point
+// where a parsing error happened. Check that at that point the status and
+// error are properly set.
+TEST_F(CommandBufferEngineTest, TestNonRecoverableError) {
+ engine()->InitConnection();
+ // Create a buffer with 6 entries, starting at entry 1, but allocate enough
+ // memory so that we can add commands that cross over the limit.
+ const size_t kShmSize = 10 * sizeof(CommandBufferEntry); // NOLINT
+ RPCShmHandle shm = CreateShm(kShmSize);
+ ASSERT_NE(kRPCInvalidHandle, shm);
+ unsigned int shm_id = engine()->RegisterSharedMemory(shm, kShmSize);
+ ASSERT_NE(BufferSyncInterface::kInvalidSharedMemoryId, shm_id);
+ CommandBufferEntry *entries = static_cast<CommandBufferEntry *>(
+ engine()->GetSharedMemoryAddress(shm_id));
+ ASSERT_TRUE(entries != NULL);
+ engine()->SetCommandBuffer(shm_id, 0, 6 * sizeof(CommandBufferEntry), 1);
+
+ CommandBufferOffset get = engine()->Get();
+ CommandBufferOffset put = get;
+
+ // Create a command buffer with 3 commands, the last one overlapping the end
+ // of the buffer.
+ put += AddCommandWithExpect(entries + put,
+ BufferSyncInterface::PARSE_NO_ERROR,
+ 0,
+ 0,
+ NULL);
+
+ CommandBufferEntry args1[2];
+ args1[0].value_uint32 = 3;
+ args1[1].value_float = 4.f;
+ put += AddCommandWithExpect(entries + put,
+ BufferSyncInterface::PARSE_NO_ERROR,
+ 1,
+ 2,
+ args1);
+
+ CommandBufferOffset fail_get = put;
+ CommandHeader header;
+ header.size = 3;
+ header.command = 4;
+ entries[put++].value_header = header;
+ entries[put++].value_uint32 = 5;
+ entries[put++].value_uint32 = 6;
+
+ // we should be beyond the end of the buffer now.
+ DCHECK_LT(6, put);
+ put = 0;
+
+ engine()->Put(put);
+ while (get != put) {
+ // When the parsing stop progressing, break.
+ CommandBufferOffset new_get = engine()->WaitGetChanges(get);
+ if (new_get == get) {
+ EXPECT_EQ(new_get, engine()->Get());
+ break;
+ }
+ get = new_get;
+ }
+ // We should be in an error case now.
+ EXPECT_EQ(BufferSyncInterface::PARSE_ERROR, engine()->GetStatus());
+ // Check that the error status was set to the first error.
+ EXPECT_EQ(BufferSyncInterface::PARSE_OUT_OF_BOUNDS,
+ engine()->GetParseError());
+ // Check that the error status was reset after the query.
+ EXPECT_EQ(BufferSyncInterface::PARSE_NO_ERROR, engine()->GetParseError());
+
+ // Check that the valid commands did happen.
+ Mock::VerifyAndClearExpectations(api_mock());
+
+ engine()->CloseConnection();
+ engine()->UnregisterSharedMemory(shm_id);
+ DestroyShm(shm);
+}
+
+// Checks that HasWork() and DoWork() have the correct semantics. If there is
+// work to do, DoWork should never block.
+TEST_F(CommandBufferEngineTest, TestDoWork) {
+ engine()->InitConnection();
+ CommandBufferEntry *entries = InitCommandBuffer(10, 0);
+ ASSERT_TRUE(entries != NULL);
+
+ CommandBufferOffset get = engine()->Get();
+ CommandBufferOffset put = get;
+
+ // Test that if we have no message and no command we will block.
+ process_mock()->Reset();
+ EXPECT_CALL(*process_mock(), HasMessage()).Times(AnyNumber());
+ EXPECT_FALSE(engine()->HasWork());
+ EXPECT_CALL(*process_mock(), ProcessMessage());
+ EXPECT_TRUE(engine()->DoWork());
+
+ EXPECT_TRUE(process_mock()->would_have_blocked());
+ Mock::VerifyAndClearExpectations(process_mock());
+
+ // Tests that messages get processed without blocking.
+ process_mock()->Reset();
+ EXPECT_CALL(*process_mock(), HasMessage()).Times(AnyNumber());
+ process_mock()->set_message_count(3);
+ EXPECT_TRUE(engine()->HasWork());
+
+ EXPECT_CALL(*process_mock(), ProcessMessage()).Times(3);
+ while (engine()->HasWork()) {
+ EXPECT_TRUE(engine()->DoWork());
+ }
+ EXPECT_EQ(0, process_mock()->message_count());
+ EXPECT_FALSE(process_mock()->would_have_blocked());
+ Mock::VerifyAndClearExpectations(process_mock());
+
+ // Test that if we have commands, we will process them without blocking.
+ // Create a command buffer with 3 commands
+ process_mock()->Reset();
+ EXPECT_CALL(*process_mock(), HasMessage()).Times(AnyNumber());
+ put += AddCommandWithExpect(entries + put,
+ BufferSyncInterface::PARSE_NO_ERROR,
+ 0,
+ 0,
+ NULL);
+
+ CommandBufferEntry args1[2];
+ args1[0].value_uint32 = 3;
+ args1[1].value_float = 4.f;
+ put += AddCommandWithExpect(entries + put,
+ BufferSyncInterface::PARSE_NO_ERROR,
+ 1,
+ 2,
+ args1);
+
+ CommandBufferEntry args2[2];
+ args2[0].value_uint32 = 5;
+ args2[1].value_float = 6.f;
+ put += AddCommandWithExpect(entries + put,
+ BufferSyncInterface::PARSE_NO_ERROR,
+ 2,
+ 2,
+ args2);
+
+ EXPECT_FALSE(engine()->HasWork()); // No work yet, until we change put
+
+ engine()->Put(put);
+ EXPECT_TRUE(engine()->HasWork());
+
+ EXPECT_CALL(*process_mock(), ProcessMessage()).Times(0);
+ while (engine()->HasWork()) {
+ EXPECT_TRUE(engine()->DoWork());
+ }
+ EXPECT_FALSE(process_mock()->would_have_blocked());
+ get = engine()->Get();
+ EXPECT_EQ(put, get); // once we're done, we should have executed everything.
+ ASSERT_EQ(BufferSyncInterface::PARSING, engine()->GetStatus());
+ EXPECT_EQ(BufferSyncInterface::PARSE_NO_ERROR, engine()->GetParseError());
+ Mock::VerifyAndClearExpectations(process_mock());
+ Mock::VerifyAndClearExpectations(api_mock());
+
+ // Test that the engine stops if we send it a "kill" message.
+ process_mock()->Reset();
+ EXPECT_CALL(*process_mock(), HasMessage()).Times(AnyNumber());
+ process_mock()->set_message_count(1);
+ EXPECT_TRUE(engine()->HasWork());
+
+ EXPECT_CALL(*process_mock(), ProcessMessage()).WillOnce(Return(false));
+ EXPECT_FALSE(engine()->DoWork());
+ Mock::VerifyAndClearExpectations(process_mock());
+
+ engine()->CloseConnection();
+ DestroyCommandBuffer();
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/service/cross/cmd_parser.cc b/o3d/command_buffer/service/cross/cmd_parser.cc
new file mode 100644
index 0000000..a640d3d
--- /dev/null
+++ b/o3d/command_buffer/service/cross/cmd_parser.cc
@@ -0,0 +1,92 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the implementation of the command parser.
+
+#include "command_buffer/service/cross/cmd_parser.h"
+
+namespace o3d {
+namespace command_buffer {
+
+CommandParser::CommandParser(void *shm_address,
+ size_t shm_size,
+ ptrdiff_t offset,
+ size_t size,
+ CommandBufferOffset start_get,
+ AsyncAPIInterface *handler)
+ : get_(start_get),
+ put_(start_get),
+ handler_(handler) {
+ // check proper alignments.
+ DCHECK_EQ(0, (reinterpret_cast<intptr_t>(shm_address)) % 4);
+ DCHECK_EQ(0, offset % 4);
+ DCHECK_EQ(0, size % 4);
+ // check that the command buffer fits into the memory buffer.
+ DCHECK_GE(shm_size, offset + size);
+ char * buffer_begin = static_cast<char *>(shm_address) + offset;
+ buffer_ = reinterpret_cast<CommandBufferEntry *>(buffer_begin);
+ entry_count_ = size / 4;
+}
+
+// Process one command, reading the header from the command buffer, and
+// forwarding the command index and the arguments to the handler.
+// Note that:
+// - validation needs to happen on a copy of the data (to avoid race
+// conditions). This function only validates the header, leaving the arguments
+// validation to the handler, so it can pass a reference to them.
+// - get_ is modified *after* the command has been executed.
+BufferSyncInterface::ParseError CommandParser::ProcessCommand() {
+ CommandBufferOffset get = get_;
+ if (get == put_) return BufferSyncInterface::PARSE_NO_ERROR;
+
+ CommandHeader header = buffer_[get].value_header;
+ if (header.size == 0) return BufferSyncInterface::PARSE_INVALID_SIZE;
+ if (header.size + get > entry_count_)
+ return BufferSyncInterface::PARSE_OUT_OF_BOUNDS;
+ BufferSyncInterface::ParseError result = handler_->DoCommand(
+ header.command, header.size - 1, buffer_ + get + 1);
+ get_ = (get + header.size) % entry_count_;
+ return result;
+}
+
+// Processes all the commands, while the buffer is not empty. Stop if an error
+// is encountered.
+BufferSyncInterface::ParseError CommandParser::ProcessAllCommands() {
+ while (!IsEmpty()) {
+ BufferSyncInterface::ParseError error = ProcessCommand();
+ if (error) return error;
+ }
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/service/cross/cmd_parser.h b/o3d/command_buffer/service/cross/cmd_parser.h
new file mode 100644
index 0000000..84107c5
--- /dev/null
+++ b/o3d/command_buffer/service/cross/cmd_parser.h
@@ -0,0 +1,113 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the command parser class.
+
+#ifndef O3D_COMMAND_BUFFER_SERVICE_CROSS_CMD_PARSER_H__
+#define O3D_COMMAND_BUFFER_SERVICE_CROSS_CMD_PARSER_H__
+
+#include "core/cross/types.h"
+#include "command_buffer/common/cross/rpc.h"
+#include "command_buffer/common/cross/buffer_sync_api.h"
+#include "command_buffer/common/cross/cmd_buffer_format.h"
+
+namespace o3d {
+namespace command_buffer {
+
+class AsyncAPIInterface;
+
+// Command parser class. This class parses commands from a shared memory
+// buffer, to implement some asynchronous RPC mechanism.
+class CommandParser {
+ public:
+ CommandParser(void *shm_address,
+ size_t shm_size,
+ ptrdiff_t offset,
+ size_t size,
+ CommandBufferOffset start_get,
+ AsyncAPIInterface *handler);
+
+ // Gets the "get" pointer. The get pointer is an index into the command
+ // buffer considered as an array of CommandBufferEntry.
+ CommandBufferOffset get() const { return get_; }
+
+ // Sets the "put" pointer. The put pointer is an index into the command
+ // buffer considered as an array of CommandBufferEntry.
+ void set_put(CommandBufferOffset put) { put_ = put; }
+
+ // Gets the "put" pointer. The put pointer is an index into the command
+ // buffer considered as an array of CommandBufferEntry.
+ CommandBufferOffset put() const { return put_; }
+
+ // Checks whether there are commands to process.
+ bool IsEmpty() const { return put_ == get_; }
+
+ // Processes one command, updating the get pointer. This will return an error
+ // if there are no commands in the buffer.
+ BufferSyncInterface::ParseError ProcessCommand();
+
+ // Processes all commands until get == put.
+ BufferSyncInterface::ParseError ProcessAllCommands();
+
+ private:
+ CommandBufferOffset get_;
+ CommandBufferOffset put_;
+ CommandBufferEntry *buffer_;
+ size_t entry_count_;
+ AsyncAPIInterface *handler_;
+};
+
+// This class defines the interface for an asynchronous API handler, that
+// is responsible for de-multiplexing commands and their arguments.
+class AsyncAPIInterface {
+ public:
+ AsyncAPIInterface() {}
+ virtual ~AsyncAPIInterface() {}
+
+ // Executes a command.
+ // Parameters:
+ // command: the command index.
+ // arg_count: the number of CommandBufferEntry arguments.
+ // args: the arguments.
+ // Returns:
+ // BufferSyncInterface::NO_ERROR if no error was found, one of
+ // BufferSyncInterface::ParseError otherwise.
+ virtual BufferSyncInterface::ParseError DoCommand(
+ unsigned int command,
+ unsigned int arg_count,
+ CommandBufferEntry *args) = 0;
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_SERVICE_CROSS_CMD_PARSER_H__
diff --git a/o3d/command_buffer/service/cross/cmd_parser_test.cc b/o3d/command_buffer/service/cross/cmd_parser_test.cc
new file mode 100644
index 0000000..a63489c
--- /dev/null
+++ b/o3d/command_buffer/service/cross/cmd_parser_test.cc
@@ -0,0 +1,315 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// Tests for the command parser.
+
+#include "tests/common/win/testing_common.h"
+#include "command_buffer/service/cross/cmd_parser.h"
+#include "command_buffer/service/cross/mocks.h"
+
+namespace o3d {
+namespace command_buffer {
+
+using testing::Return;
+using testing::Mock;
+using testing::Truly;
+using testing::Sequence;
+using testing::_;
+
+// Test fixture for CommandParser test - Creates a mock AsyncAPIInterface, and
+// a fixed size memory buffer. Also provides a simple API to create a
+// CommandParser.
+class CommandParserTest : public testing::Test {
+ protected:
+ virtual void SetUp() {
+ api_mock_.reset(new AsyncAPIMock);
+ buffer_entry_count_ = 20;
+ buffer_.reset(new CommandBufferEntry[buffer_entry_count_]);
+ }
+ virtual void TearDown() {}
+
+ // Adds a DoCommand expectation in the mock.
+ void AddDoCommandExpect(BufferSyncInterface::ParseError _return,
+ unsigned int command,
+ unsigned int arg_count,
+ CommandBufferEntry *args) {
+ EXPECT_CALL(*api_mock(), DoCommand(command, arg_count,
+ Truly(AsyncAPIMock::IsArgs(arg_count, args))))
+ .InSequence(sequence_)
+ .WillOnce(Return(_return));
+ }
+
+ // Creates a parser, with a buffer of the specified size (in entries).
+ CommandParser *MakeParser(unsigned int entry_count) {
+ size_t shm_size = buffer_entry_count_ *
+ sizeof(CommandBufferEntry); // NOLINT
+ size_t command_buffer_size = entry_count *
+ sizeof(CommandBufferEntry); // NOLINT
+ DCHECK_LE(command_buffer_size, shm_size);
+ return new CommandParser(buffer(),
+ shm_size,
+ 0,
+ command_buffer_size,
+ 0,
+ api_mock());
+ }
+
+ unsigned int buffer_entry_count() { return 20; }
+ AsyncAPIMock *api_mock() { return api_mock_.get(); }
+ CommandBufferEntry *buffer() { return buffer_.get(); }
+ private:
+ unsigned int buffer_entry_count_;
+ scoped_ptr<AsyncAPIMock> api_mock_;
+ scoped_array<CommandBufferEntry> buffer_;
+ Sequence sequence_;
+};
+
+// Tests initialization conditions.
+TEST_F(CommandParserTest, TestInit) {
+ scoped_ptr<CommandParser> parser(MakeParser(10));
+ EXPECT_EQ(0, parser->get());
+ EXPECT_EQ(0, parser->put());
+ EXPECT_TRUE(parser->IsEmpty());
+}
+
+// Tests simple commands.
+TEST_F(CommandParserTest, TestSimple) {
+ scoped_ptr<CommandParser> parser(MakeParser(10));
+ CommandBufferOffset put = parser->put();
+ CommandHeader header;
+
+ // add a single command, no args
+ header.size = 1;
+ header.command = 123;
+ buffer()[put++].value_header = header;
+
+ parser->set_put(put);
+ EXPECT_EQ(put, parser->put());
+
+ AddDoCommandExpect(BufferSyncInterface::PARSE_NO_ERROR, 123, 0, NULL);
+ EXPECT_EQ(BufferSyncInterface::PARSE_NO_ERROR, parser->ProcessCommand());
+ EXPECT_EQ(put, parser->get());
+ Mock::VerifyAndClearExpectations(api_mock());
+
+ // add a single command, 2 args
+ header.size = 3;
+ header.command = 456;
+ buffer()[put++].value_header = header;
+ buffer()[put++].value_int32 = 2134;
+ buffer()[put++].value_float = 1.f;
+
+ parser->set_put(put);
+ EXPECT_EQ(put, parser->put());
+
+ CommandBufferEntry param_array[2];
+ param_array[0].value_int32 = 2134;
+ param_array[1].value_float = 1.f;
+ AddDoCommandExpect(BufferSyncInterface::PARSE_NO_ERROR, 456, 2, param_array);
+ EXPECT_EQ(BufferSyncInterface::PARSE_NO_ERROR, parser->ProcessCommand());
+ EXPECT_EQ(put, parser->get());
+ Mock::VerifyAndClearExpectations(api_mock());
+}
+
+// Tests having multiple commands in the buffer.
+TEST_F(CommandParserTest, TestMultipleCommands) {
+ scoped_ptr<CommandParser> parser(MakeParser(10));
+ CommandBufferOffset put = parser->put();
+ CommandHeader header;
+
+ // add 2 commands, test with single ProcessCommand()
+ header.size = 2;
+ header.command = 789;
+ buffer()[put++].value_header = header;
+ buffer()[put++].value_int32 = 5151;
+
+ CommandBufferOffset put_cmd2 = put;
+ header.size = 2;
+ header.command = 2121;
+ buffer()[put++].value_header = header;
+ buffer()[put++].value_int32 = 3434;
+
+ parser->set_put(put);
+ EXPECT_EQ(put, parser->put());
+
+ CommandBufferEntry param_array[2];
+ param_array[0].value_int32 = 5151;
+ AddDoCommandExpect(BufferSyncInterface::PARSE_NO_ERROR, 789, 1, param_array);
+ param_array[1].value_int32 = 3434;
+ AddDoCommandExpect(BufferSyncInterface::PARSE_NO_ERROR, 2121, 1,
+ param_array+1);
+
+ EXPECT_EQ(BufferSyncInterface::PARSE_NO_ERROR, parser->ProcessCommand());
+ EXPECT_EQ(put_cmd2, parser->get());
+ EXPECT_EQ(BufferSyncInterface::PARSE_NO_ERROR, parser->ProcessCommand());
+ EXPECT_EQ(put, parser->get());
+ Mock::VerifyAndClearExpectations(api_mock());
+
+ // add 2 commands again, test with ProcessAllCommands()
+ header.size = 2;
+ header.command = 4545;
+ buffer()[put++].value_header = header;
+ buffer()[put++].value_int32 = 5656;
+
+ header.size = 2;
+ header.command = 6767;
+ buffer()[put++].value_header = header;
+ buffer()[put++].value_int32 = 7878;
+
+ parser->set_put(put);
+ EXPECT_EQ(put, parser->put());
+
+ param_array[0].value_int32 = 5656;
+ AddDoCommandExpect(BufferSyncInterface::PARSE_NO_ERROR, 4545, 1, param_array);
+ param_array[1].value_int32 = 7878;
+ AddDoCommandExpect(BufferSyncInterface::PARSE_NO_ERROR, 6767, 1,
+ param_array+1);
+
+ EXPECT_EQ(BufferSyncInterface::PARSE_NO_ERROR, parser->ProcessAllCommands());
+ EXPECT_EQ(put, parser->get());
+ Mock::VerifyAndClearExpectations(api_mock());
+}
+
+// Tests that the parser will wrap correctly at the end of the buffer.
+TEST_F(CommandParserTest, TestWrap) {
+ scoped_ptr<CommandParser> parser(MakeParser(5));
+ CommandBufferOffset put = parser->put();
+ CommandHeader header;
+
+ // add 3 commands with no args (1 word each)
+ for (unsigned int i = 0; i < 3; ++i) {
+ header.size = 1;
+ header.command = i;
+ buffer()[put++].value_header = header;
+ AddDoCommandExpect(BufferSyncInterface::PARSE_NO_ERROR, i, 0, NULL);
+ }
+ parser->set_put(put);
+ EXPECT_EQ(put, parser->put());
+ EXPECT_EQ(BufferSyncInterface::PARSE_NO_ERROR, parser->ProcessAllCommands());
+ EXPECT_EQ(put, parser->get());
+ Mock::VerifyAndClearExpectations(api_mock());
+
+ // add 1 command with 1 arg (2 words). That should put us at the end of the
+ // buffer.
+ header.size = 2;
+ header.command = 3;
+ buffer()[put++].value_header = header;
+ buffer()[put++].value_int32 = 5;
+ CommandBufferEntry param;
+ param.value_int32 = 5;
+ AddDoCommandExpect(BufferSyncInterface::PARSE_NO_ERROR, 3, 1, &param);
+
+ DCHECK_EQ(5, put);
+ put = 0;
+ parser->set_put(put);
+ EXPECT_EQ(put, parser->put());
+ EXPECT_EQ(BufferSyncInterface::PARSE_NO_ERROR, parser->ProcessAllCommands());
+ EXPECT_EQ(put, parser->get());
+ Mock::VerifyAndClearExpectations(api_mock());
+
+ // add 1 command with 1 arg (2 words).
+ header.size = 2;
+ header.command = 4;
+ buffer()[put++].value_header = header;
+ buffer()[put++].value_int32 = 6;
+ param.value_int32 = 6;
+ AddDoCommandExpect(BufferSyncInterface::PARSE_NO_ERROR, 4, 1, &param);
+ parser->set_put(put);
+ EXPECT_EQ(put, parser->put());
+ EXPECT_EQ(BufferSyncInterface::PARSE_NO_ERROR, parser->ProcessAllCommands());
+ EXPECT_EQ(put, parser->get());
+ Mock::VerifyAndClearExpectations(api_mock());
+}
+
+// Tests error conditions.
+TEST_F(CommandParserTest, TestError) {
+ scoped_ptr<CommandParser> parser(MakeParser(5));
+ CommandBufferOffset put = parser->put();
+ CommandHeader header;
+
+ // Generate a command with size 0.
+ header.size = 0;
+ header.command = 3;
+ buffer()[put++].value_header = header;
+
+ parser->set_put(put);
+ EXPECT_EQ(put, parser->put());
+ EXPECT_EQ(BufferSyncInterface::PARSE_INVALID_SIZE,
+ parser->ProcessAllCommands());
+ // check that no DoCommand call was made.
+ Mock::VerifyAndClearExpectations(api_mock());
+
+ parser.reset(MakeParser(5));
+ put = parser->put();
+
+ // Generate a command with size 6, extends beyond the end of the buffer.
+ header.size = 6;
+ header.command = 3;
+ buffer()[put++].value_header = header;
+
+ parser->set_put(put);
+ EXPECT_EQ(put, parser->put());
+ EXPECT_EQ(BufferSyncInterface::PARSE_OUT_OF_BOUNDS,
+ parser->ProcessAllCommands());
+ // check that no DoCommand call was made.
+ Mock::VerifyAndClearExpectations(api_mock());
+
+ parser.reset(MakeParser(5));
+ put = parser->put();
+
+ // Generates 2 commands.
+ header.size = 1;
+ header.command = 3;
+ buffer()[put++].value_header = header;
+ CommandBufferOffset put_post_fail = put;
+ header.size = 1;
+ header.command = 4;
+ buffer()[put++].value_header = header;
+
+ parser->set_put(put);
+ EXPECT_EQ(put, parser->put());
+ // have the first command fail to parse.
+ AddDoCommandExpect(BufferSyncInterface::PARSE_UNKNOWN_COMMAND, 3, 0, NULL);
+ EXPECT_EQ(BufferSyncInterface::PARSE_UNKNOWN_COMMAND,
+ parser->ProcessAllCommands());
+ // check that only one command was executed, and that get reflects that
+ // correctly.
+ EXPECT_EQ(put_post_fail, parser->get());
+ Mock::VerifyAndClearExpectations(api_mock());
+ // make the second one succeed, and check that the parser recovered fine.
+ AddDoCommandExpect(BufferSyncInterface::PARSE_NO_ERROR, 4, 0, NULL);
+ EXPECT_EQ(BufferSyncInterface::PARSE_NO_ERROR, parser->ProcessAllCommands());
+ EXPECT_EQ(put, parser->get());
+ Mock::VerifyAndClearExpectations(api_mock());
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/service/cross/effect_utils.cc b/o3d/command_buffer/service/cross/effect_utils.cc
new file mode 100644
index 0000000..91beb17
--- /dev/null
+++ b/o3d/command_buffer/service/cross/effect_utils.cc
@@ -0,0 +1,70 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file implements effect related utilities.
+
+#include "command_buffer/service/cross/effect_utils.h"
+
+namespace o3d {
+namespace command_buffer {
+
+bool ParseEffectData(unsigned int size,
+ const void *data,
+ String *vertex_program_entry,
+ String *fragment_program_entry,
+ String *effect_code) {
+ const char *data_char = static_cast<const char *>(data);
+ unsigned int index = 0;
+
+ for (; index < size && data_char[index]; ++index) { }
+ if (index >= size) return false;
+ *vertex_program_entry = String(data_char, index);
+ ++index; // skip \0
+ unsigned int fragment_program_entry_begin = index;
+
+ for (; index < size && data_char[index]; ++index) { }
+ if (index >= size) return false;
+ *fragment_program_entry = String(data_char + fragment_program_entry_begin,
+ index - fragment_program_entry_begin);
+ ++index; // skip \0
+ unsigned int effect_code_begin = index;
+
+ // text doesn't have to be 0-terminated, but look for one so that we don't
+ // construct a std::string with a '\0' in it.
+ for (; index < size && data_char[index]; ++index) { }
+ *effect_code = String(data_char + effect_code_begin,
+ index - effect_code_begin);
+ return true;
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/service/cross/effect_utils.h b/o3d/command_buffer/service/cross/effect_utils.h
new file mode 100644
index 0000000..2402254
--- /dev/null
+++ b/o3d/command_buffer/service/cross/effect_utils.h
@@ -0,0 +1,56 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file declares some effect related utilities.
+
+#ifndef O3D_COMMAND_BUFFER_SERVICE_CROSS_EFFECT_UTILS_H_
+#define O3D_COMMAND_BUFFER_SERVICE_CROSS_EFFECT_UTILS_H_
+
+#include "command_buffer/common/cross/types.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// This function parses the data passed to the CREATE_EFFECT commands, which
+// follows the following format:
+// vertex_program_entry \0 fragment_program_entry \0 effect_code
+// It returns the various components.
+bool ParseEffectData(unsigned int size,
+ const void *data,
+ String *vertex_program_entry,
+ String *fragment_program_entry,
+ String *effect_code);
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_SERVICE_CROSS_EFFECT_UTILS_H_
diff --git a/o3d/command_buffer/service/cross/effect_utils_test.cc b/o3d/command_buffer/service/cross/effect_utils_test.cc
new file mode 100644
index 0000000..d37db9d
--- /dev/null
+++ b/o3d/command_buffer/service/cross/effect_utils_test.cc
@@ -0,0 +1,86 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the unit tests for the effect utilities.
+
+#include "tests/common/win/testing_common.h"
+#include "command_buffer/service/cross/effect_utils.h"
+
+namespace o3d {
+namespace command_buffer {
+
+TEST(ParseEffectDataTest, ValidData) {
+ // Tests well-formed data.
+ const char kEffect[] = "vertex_entry\0fragment_entry\0effect code";
+ String vertex_program_entry;
+ String fragment_program_entry;
+ String effect_code;
+ EXPECT_TRUE(ParseEffectData(sizeof(kEffect), kEffect, &vertex_program_entry,
+ &fragment_program_entry, &effect_code));
+ EXPECT_EQ(vertex_program_entry, "vertex_entry");
+ EXPECT_EQ(fragment_program_entry, "fragment_entry");
+ EXPECT_EQ(effect_code, "effect code");
+
+ // The terminal \0 isn't needed, check that we parse correctly without it.
+ EXPECT_TRUE(ParseEffectData(sizeof(kEffect)-1, kEffect,
+ &vertex_program_entry, &fragment_program_entry,
+ &effect_code));
+ EXPECT_EQ(vertex_program_entry, "vertex_entry");
+ EXPECT_EQ(fragment_program_entry, "fragment_entry");
+ EXPECT_EQ(effect_code, "effect code");
+}
+
+TEST(ParseEffectDataTest, InvalidData) {
+ const char kEffect[] = "vertex_entry\0fragment_entry\0effect code";
+ String vertex_program_entry;
+ String fragment_program_entry;
+ String effect_code;
+ // 0-size
+ EXPECT_FALSE(ParseEffectData(0, kEffect,
+ &vertex_program_entry, &fragment_program_entry,
+ &effect_code));
+ // Only vertex_entry, no \0
+ EXPECT_FALSE(ParseEffectData(strlen("vertex_entry"), kEffect,
+ &vertex_program_entry, &fragment_program_entry,
+ &effect_code));
+ // Only vertex_entry\0
+ EXPECT_FALSE(ParseEffectData(strlen("vertex_entry") + 1, kEffect,
+ &vertex_program_entry, &fragment_program_entry,
+ &effect_code));
+ // Only vertex_entry\0fragment_entry, no \0
+ EXPECT_FALSE(ParseEffectData(strlen("vertex_entry.fragment_entry"), kEffect,
+ &vertex_program_entry, &fragment_program_entry,
+ &effect_code));
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/service/cross/gapi_decoder.cc b/o3d/command_buffer/service/cross/gapi_decoder.cc
new file mode 100644
index 0000000..efd3bc5
--- /dev/null
+++ b/o3d/command_buffer/service/cross/gapi_decoder.cc
@@ -0,0 +1,881 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This class contains the implementation of the GAPI decoder class, decoding
+// GAPI commands into calls to a GAPIInterface class.
+
+#include "base/cross/bits.h"
+#include "command_buffer/common/cross/gapi_interface.h"
+#include "command_buffer/service/cross/gapi_decoder.h"
+#include "command_buffer/service/cross/cmd_buffer_engine.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// Decode command with its arguments, and call the corresponding GAPIInterface
+// method.
+// Note: args is a pointer to the command buffer. As such, it could be changed
+// by a (malicious) client at any time, so if validation has to happen, it
+// should operate on a copy of them.
+BufferSyncInterface::ParseError GAPIDecoder::DoCommand(
+ unsigned int command,
+ unsigned int arg_count,
+ CommandBufferEntry *args) {
+ switch (command) {
+ case NOOP:
+ return BufferSyncInterface::PARSE_NO_ERROR;
+ case SET_TOKEN:
+ if (arg_count == 1) {
+ engine_->set_token(args[0].value_uint32);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case BEGIN_FRAME:
+ if (arg_count == 0) {
+ gapi_->BeginFrame();
+ return BufferSyncInterface::PARSE_NO_ERROR;
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case END_FRAME:
+ if (arg_count == 0) {
+ gapi_->EndFrame();
+ return BufferSyncInterface::PARSE_NO_ERROR;
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case CLEAR:
+ if (arg_count == 7) {
+ unsigned int buffers = args[0].value_uint32;
+ if (buffers & ~GAPIInterface::ALL_BUFFERS)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ RGBA rgba;
+ rgba.red = args[1].value_float;
+ rgba.green = args[2].value_float;
+ rgba.blue = args[3].value_float;
+ rgba.alpha = args[4].value_float;
+ float depth = args[5].value_float;
+ unsigned int stencil = args[6].value_uint32;
+ gapi_->Clear(buffers, rgba, depth, stencil);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case SET_VIEWPORT:
+ if (arg_count == 6) {
+ gapi_->SetViewport(args[0].value_uint32,
+ args[1].value_uint32,
+ args[2].value_uint32,
+ args[3].value_uint32,
+ args[4].value_float,
+ args[5].value_float);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case CREATE_VERTEX_BUFFER:
+ if (arg_count == 3) {
+ return gapi_->CreateVertexBuffer(args[0].value_uint32,
+ args[1].value_uint32,
+ args[2].value_uint32);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case DESTROY_VERTEX_BUFFER:
+ if (arg_count == 1) {
+ return gapi_->DestroyVertexBuffer(args[0].value_uint32);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case SET_VERTEX_BUFFER_DATA_IMMEDIATE: {
+ if (arg_count < 2) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ ResourceID id = args[0].value_uint32;
+ unsigned int offset = args[1].value_uint32;
+ unsigned int size = (arg_count - 2) * sizeof(args[0]);
+ return gapi_->SetVertexBufferData(id, offset, size, args + 2);
+ }
+ case SET_VERTEX_BUFFER_DATA:
+ if (arg_count == 5) {
+ ResourceID id = args[0].value_uint32;
+ unsigned int offset = args[1].value_uint32;
+ unsigned int size = args[2].value_uint32;
+ void *data = GetAddressAndCheckSize(args[3].value_uint32,
+ args[4].value_uint32,
+ size);
+ if (!data) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return gapi_->SetVertexBufferData(id, offset, size, data);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case GET_VERTEX_BUFFER_DATA:
+ if (arg_count == 5) {
+ ResourceID id = args[0].value_uint32;
+ unsigned int offset = args[1].value_uint32;
+ unsigned int size = args[2].value_uint32;
+ void *data = GetAddressAndCheckSize(args[3].value_uint32,
+ args[4].value_uint32,
+ size);
+ if (!data) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return gapi_->GetVertexBufferData(id, offset, size, data);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case CREATE_INDEX_BUFFER:
+ if (arg_count == 3) {
+ return gapi_->CreateIndexBuffer(args[0].value_uint32,
+ args[1].value_uint32,
+ args[2].value_uint32);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case DESTROY_INDEX_BUFFER:
+ if (arg_count == 1) {
+ return gapi_->DestroyIndexBuffer(args[0].value_uint32);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case SET_INDEX_BUFFER_DATA_IMMEDIATE: {
+ if (arg_count < 2) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ ResourceID id = args[0].value_uint32;
+ unsigned int offset = args[1].value_uint32;
+ unsigned int size = (arg_count - 2) * sizeof(args[0]);
+ return gapi_->SetIndexBufferData(id, offset, size, args + 2);
+ }
+ case SET_INDEX_BUFFER_DATA:
+ if (arg_count == 5) {
+ ResourceID id = args[0].value_uint32;
+ unsigned int offset = args[1].value_uint32;
+ unsigned int size = args[2].value_uint32;
+ void *data = GetAddressAndCheckSize(args[3].value_uint32,
+ args[4].value_uint32,
+ size);
+ if (!data) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return gapi_->SetIndexBufferData(id, offset, size, data);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case GET_INDEX_BUFFER_DATA:
+ if (arg_count == 5) {
+ ResourceID id = args[0].value_uint32;
+ unsigned int offset = args[1].value_uint32;
+ unsigned int size = args[2].value_uint32;
+ void *data = GetAddressAndCheckSize(args[3].value_uint32,
+ args[4].value_uint32,
+ size);
+ if (!data) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return gapi_->GetIndexBufferData(id, offset, size, data);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case CREATE_VERTEX_STRUCT:
+ if (arg_count == 2) {
+ return gapi_->CreateVertexStruct(args[0].value_uint32,
+ args[1].value_uint32);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case DESTROY_VERTEX_STRUCT:
+ if (arg_count == 1) {
+ return gapi_->DestroyVertexStruct(args[0].value_uint32);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case SET_VERTEX_INPUT:
+ return DecodeSetVertexInput(arg_count, args);
+ case SET_VERTEX_STRUCT:
+ if (arg_count == 1) {
+ return gapi_->SetVertexStruct(args[0].value_uint32);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case DRAW:
+ if (arg_count == 3) {
+ unsigned int primitive_type = args[0].value_uint32;
+ if (primitive_type >= GAPIInterface::MAX_PRIMITIVE_TYPE)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ unsigned int first = args[1].value_uint32;
+ unsigned int count = args[2].value_uint32;
+ return gapi_->Draw(
+ static_cast<GAPIInterface::PrimitiveType>(primitive_type),
+ first, count);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case DRAW_INDEXED:
+ if (arg_count == 6) {
+ unsigned int primitive_type = args[0].value_uint32;
+ if (primitive_type >= GAPIInterface::MAX_PRIMITIVE_TYPE)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ ResourceID index_buffer = args[1].value_uint32;
+ unsigned int first = args[2].value_uint32;
+ unsigned int count = args[3].value_uint32;
+ unsigned int min_index = args[4].value_uint32;
+ unsigned int max_index = args[5].value_uint32;
+ return gapi_->DrawIndexed(
+ static_cast<GAPIInterface::PrimitiveType>(primitive_type),
+ index_buffer, first, count, min_index, max_index);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case CREATE_EFFECT:
+ if (arg_count == 4) {
+ ResourceID id = args[0].value_uint32;
+ unsigned int size = args[1].value_uint32;
+ void *data = GetAddressAndCheckSize(args[2].value_uint32,
+ args[3].value_uint32,
+ size);
+ if (!data) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return gapi_->CreateEffect(id, size, data);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case CREATE_EFFECT_IMMEDIATE:
+ if (arg_count > 2) {
+ ResourceID id = args[0].value_uint32;
+ unsigned int size = args[1].value_uint32;
+ if (size > (arg_count-2) * sizeof(args[0]))
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return gapi_->CreateEffect(id, size, args + 2);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case DESTROY_EFFECT:
+ if (arg_count == 1) {
+ return gapi_->DestroyEffect(args[0].value_uint32);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case SET_EFFECT:
+ if (arg_count == 1) {
+ return gapi_->SetEffect(args[0].value_uint32);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case GET_PARAM_COUNT:
+ if (arg_count == 4) {
+ ResourceID id = args[0].value_uint32;
+ unsigned int size = args[1].value_uint32;
+ void *data = GetAddressAndCheckSize(args[2].value_uint32,
+ args[3].value_uint32,
+ size);
+ if (!data) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return gapi_->GetParamCount(id, size, data);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case CREATE_PARAM:
+ if (arg_count == 3) {
+ ResourceID param_id = args[0].value_uint32;
+ ResourceID effect_id = args[1].value_uint32;
+ unsigned int index = args[2].value_uint32;
+ return gapi_->CreateParam(param_id, effect_id, index);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case CREATE_PARAM_BY_NAME:
+ if (arg_count == 5) {
+ ResourceID param_id = args[0].value_uint32;
+ ResourceID effect_id = args[1].value_uint32;
+ unsigned int size = args[2].value_uint32;
+ void *data = GetAddressAndCheckSize(args[3].value_uint32,
+ args[4].value_uint32,
+ size);
+ if (!data)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return gapi_->CreateParamByName(param_id, effect_id, size, data);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case CREATE_PARAM_BY_NAME_IMMEDIATE:
+ if (arg_count > 3) {
+ ResourceID param_id = args[0].value_uint32;
+ ResourceID effect_id = args[1].value_uint32;
+ unsigned int size = args[2].value_uint32;
+ if (size > (arg_count-1) * sizeof(args[0]))
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return gapi_->CreateParamByName(param_id, effect_id, size, args + 3);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case DESTROY_PARAM:
+ if (arg_count == 1) {
+ return gapi_->DestroyParam(args[0].value_uint32);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case SET_PARAM_DATA:
+ if (arg_count == 4) {
+ ResourceID id = args[0].value_uint32;
+ unsigned int size = args[1].value_uint32;
+ void *data = GetAddressAndCheckSize(args[2].value_uint32,
+ args[3].value_uint32,
+ size);
+ if (!data) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return gapi_->SetParamData(id, size, data);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case SET_PARAM_DATA_IMMEDIATE:
+ if (arg_count > 2) {
+ ResourceID id = args[0].value_uint32;
+ unsigned int size = args[1].value_uint32;
+ if (size > (arg_count-2) * sizeof(args[0]))
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return gapi_->SetParamData(id, size, args + 2);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case GET_PARAM_DESC:
+ if (arg_count == 4) {
+ ResourceID id = args[0].value_uint32;
+ unsigned int size = args[1].value_uint32;
+ void *data = GetAddressAndCheckSize(args[2].value_uint32,
+ args[3].value_uint32,
+ size);
+ if (!data) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return gapi_->GetParamDesc(id, size, data);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case DESTROY_TEXTURE:
+ if (arg_count == 1) {
+ return gapi_->DestroyTexture(args[0].value_uint32);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case CREATE_TEXTURE_2D:
+ return DecodeCreateTexture2D(arg_count, args);
+ case CREATE_TEXTURE_3D:
+ return DecodeCreateTexture3D(arg_count, args);
+ case CREATE_TEXTURE_CUBE:
+ return DecodeCreateTextureCube(arg_count, args);
+ case SET_TEXTURE_DATA:
+ return DecodeSetTextureData(arg_count, args);
+ case SET_TEXTURE_DATA_IMMEDIATE:
+ return DecodeSetTextureDataImmediate(arg_count, args);
+ case GET_TEXTURE_DATA:
+ return DecodeGetTextureData(arg_count, args);
+ case CREATE_SAMPLER:
+ if (arg_count == 1) {
+ return gapi_->CreateSampler(args[0].value_uint32);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case DESTROY_SAMPLER:
+ if (arg_count == 1) {
+ return gapi_->DestroySampler(args[0].value_uint32);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case SET_SAMPLER_STATES:
+ return DecodeSetSamplerStates(arg_count, args);
+ case SET_SAMPLER_BORDER_COLOR:
+ if (arg_count == 5) {
+ RGBA rgba;
+ rgba.red = args[1].value_float;
+ rgba.green = args[2].value_float;
+ rgba.blue = args[3].value_float;
+ rgba.alpha = args[4].value_float;
+ return gapi_->SetSamplerBorderColor(args[0].value_uint32, rgba);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case SET_SAMPLER_TEXTURE:
+ if (arg_count == 2) {
+ return gapi_->SetSamplerTexture(args[0].value_uint32,
+ args[1].value_uint32);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case SET_SCISSOR:
+ if (arg_count == 2) {
+ namespace cmd = set_scissor;
+ Uint32 x_y_enable = args[0].value_uint32;
+ if (cmd::Unused::Get(x_y_enable) != 0)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ unsigned int x = cmd::X::Get(x_y_enable);
+ unsigned int y = cmd::Y::Get(x_y_enable);
+ bool enable = cmd::Enable::Get(x_y_enable) != 0;
+ Uint32 width_height = args[1].value_uint32;
+ unsigned int width = cmd::Width::Get(width_height);
+ unsigned int height = cmd::Height::Get(width_height);
+ gapi_->SetScissor(enable, x, y, width, height);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case SET_POLYGON_OFFSET:
+ if (arg_count == 2) {
+ gapi_->SetPolygonOffset(args[0].value_float, args[1].value_float);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case SET_POINT_LINE_RASTER:
+ if (arg_count == 2) {
+ namespace cmd = set_point_line_raster;
+ Uint32 enables = args[0].value_uint32;
+ if (cmd::Unused::Get(enables) != 0)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ bool line_smooth = cmd::LineSmoothEnable::Get(enables);
+ bool point_sprite = cmd::PointSpriteEnable::Get(enables);
+ float point_size = args[1].value_float;
+ gapi_->SetPointLineRaster(line_smooth, point_sprite, point_size);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case SET_POLYGON_RASTER:
+ if (arg_count == 1) {
+ namespace cmd = set_polygon_raster;
+ Uint32 fill_cull = args[0].value_uint32;
+ unsigned int fill_value = cmd::FillMode::Get(fill_cull);
+ unsigned int cull_value = cmd::CullMode::Get(fill_cull);
+ if (cmd::Unused::Get(fill_cull) != 0 ||
+ fill_value >= GAPIInterface::NUM_POLYGON_MODE ||
+ cull_value >= GAPIInterface::NUM_FACE_CULL_MODE)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ gapi_->SetPolygonRaster(
+ static_cast<GAPIInterface::PolygonMode>(fill_value),
+ static_cast<GAPIInterface::FaceCullMode>(cull_value));
+ return BufferSyncInterface::PARSE_NO_ERROR;
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case SET_ALPHA_TEST:
+ if (arg_count == 2) {
+ namespace cmd = set_alpha_test;
+ Uint32 func_enable = args[0].value_uint32;
+ if (cmd::Unused::Get(func_enable) != 0)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ // Check that the bitmask get cannot generate values outside of the
+ // allowed range.
+ COMPILE_ASSERT(cmd::Func::kMask < GAPIInterface::NUM_COMPARISON,
+ set_alpha_test_Func_may_produce_invalid_values);
+ GAPIInterface::Comparison comp =
+ static_cast<GAPIInterface::Comparison>(cmd::Func::Get(func_enable));
+ bool enable = cmd::Enable::Get(func_enable) != 0;
+ gapi_->SetAlphaTest(enable, args[1].value_float, comp);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case SET_DEPTH_TEST:
+ if (arg_count == 1) {
+ namespace cmd = set_depth_test;
+ Uint32 func_enable = args[0].value_uint32;
+ if (cmd::Unused::Get(func_enable) != 0)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ // Check that the bitmask get cannot generate values outside of the
+ // allowed range.
+ COMPILE_ASSERT(cmd::Func::kMask < GAPIInterface::NUM_COMPARISON,
+ set_alpha_test_Func_may_produce_invalid_values);
+ GAPIInterface::Comparison comp =
+ static_cast<GAPIInterface::Comparison>(cmd::Func::Get(func_enable));
+ bool write_enable = cmd::WriteEnable::Get(func_enable) != 0;
+ bool enable = cmd::Enable::Get(func_enable) != 0;
+ gapi_->SetDepthTest(enable, write_enable, comp);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case SET_STENCIL_TEST:
+ return DecodeSetStencilTest(arg_count, args);
+ case SET_COLOR_WRITE:
+ if (arg_count == 1) {
+ namespace cmd = set_color_write;
+ Uint32 enables = args[0].value_uint32;
+ if (cmd::Unused::Get(enables) != 0)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ bool red = cmd::RedMask::Get(enables) != 0;
+ bool green = cmd::GreenMask::Get(enables) != 0;
+ bool blue = cmd::BlueMask::Get(enables) != 0;
+ bool alpha = cmd::AlphaMask::Get(enables) != 0;
+ bool dither = cmd::DitherEnable::Get(enables) != 0;
+ gapi_->SetColorWrite(red, green, blue, alpha, dither);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ case SET_BLENDING:
+ return DecodeSetBlending(arg_count, args);
+ case SET_BLENDING_COLOR:
+ if (arg_count == 4) {
+ RGBA rgba;
+ rgba.red = args[0].value_float;
+ rgba.green = args[1].value_float;
+ rgba.blue = args[2].value_float;
+ rgba.alpha = args[3].value_float;
+ gapi_->SetBlendingColor(rgba);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ default:
+ return BufferSyncInterface::PARSE_UNKNOWN_COMMAND;
+ }
+}
+
+// Decodes the SET_VERTEX_INPUT command.
+BufferSyncInterface::ParseError GAPIDecoder::DecodeSetVertexInput(
+ unsigned int arg_count,
+ CommandBufferEntry *args) {
+ namespace cmd = set_vertex_input_cmd;
+ if (arg_count != 5) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ ResourceID vertex_struct_id = args[0].value_uint32;
+ unsigned int input_index = args[1].value_uint32;
+ ResourceID vertex_buffer_id = args[2].value_uint32;
+ unsigned int offset = args[3].value_uint32;
+ unsigned int type_stride_semantic = args[4].value_uint32;
+ unsigned int semantic_index = cmd::SemanticIndex::Get(type_stride_semantic);
+ unsigned int semantic = cmd::Semantic::Get(type_stride_semantic);
+ unsigned int type = cmd::Type::Get(type_stride_semantic);
+ unsigned int stride = cmd::Stride::Get(type_stride_semantic);
+ if (semantic >= vertex_struct::NUM_SEMANTICS ||
+ type >= vertex_struct::NUM_TYPES || stride == 0)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return gapi_->SetVertexInput(vertex_struct_id, input_index, vertex_buffer_id,
+ offset, stride,
+ static_cast<vertex_struct::Type>(type),
+ static_cast<vertex_struct::Semantic>(semantic),
+ semantic_index);
+}
+
+// Decodes the CREATE_TEXTURE_2D command.
+BufferSyncInterface::ParseError GAPIDecoder::DecodeCreateTexture2D(
+ unsigned int arg_count,
+ CommandBufferEntry *args) {
+ if (arg_count == 3) {
+ namespace cmd = create_texture_2d_cmd;
+ unsigned int id = args[0].value_uint32;
+ unsigned int width_height = args[1].value_uint32;
+ unsigned int levels_format_flags = args[2].value_uint32;
+ unsigned int width = cmd::Width::Get(width_height);
+ unsigned int height = cmd::Height::Get(width_height);
+ unsigned int levels = cmd::Levels::Get(levels_format_flags);
+ unsigned int unused = cmd::Unused::Get(levels_format_flags);
+ unsigned int format = cmd::Format::Get(levels_format_flags);
+ unsigned int flags = cmd::Flags::Get(levels_format_flags);
+ unsigned int max_levels =
+ 1 + base::bits::Log2Ceiling(std::max(width, height));
+ if ((width == 0) || (height == 0) || (levels > max_levels) ||
+ (unused != 0) || (format >= texture::NUM_FORMATS))
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ if (levels == 0) levels = max_levels;
+ return gapi_->CreateTexture2D(id, width, height, levels,
+ static_cast<texture::Format>(format), flags);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+}
+
+// Decodes the CREATE_TEXTURE_3D command.
+BufferSyncInterface::ParseError GAPIDecoder::DecodeCreateTexture3D(
+ unsigned int arg_count,
+ CommandBufferEntry *args) {
+ if (arg_count == 4) {
+ namespace cmd = create_texture_3d_cmd;
+ unsigned int id = args[0].value_uint32;
+ unsigned int width_height = args[1].value_uint32;
+ unsigned int depth_unused = args[2].value_uint32;
+ unsigned int levels_format_flags = args[3].value_uint32;
+ unsigned int width = cmd::Width::Get(width_height);
+ unsigned int height = cmd::Height::Get(width_height);
+ unsigned int depth = cmd::Depth::Get(depth_unused);
+ unsigned int unused1 = cmd::Unused1::Get(depth_unused);
+ unsigned int levels = cmd::Levels::Get(levels_format_flags);
+ unsigned int unused2 = cmd::Unused2::Get(levels_format_flags);
+ unsigned int format = cmd::Format::Get(levels_format_flags);
+ unsigned int flags = cmd::Flags::Get(levels_format_flags);
+ unsigned int max_levels =
+ 1 + base::bits::Log2Ceiling(std::max(depth, std::max(width, height)));
+ if ((width == 0) || (height == 0) || (depth == 0) ||
+ (levels > max_levels) || (unused1 != 0) || (unused2 != 0) ||
+ (format >= texture::NUM_FORMATS))
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ if (levels == 0) levels = max_levels;
+ return gapi_->CreateTexture3D(id, width, height, depth, levels,
+ static_cast<texture::Format>(format), flags);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+}
+
+// Decodes the CREATE_TEXTURE_CUBE command.
+BufferSyncInterface::ParseError GAPIDecoder::DecodeCreateTextureCube(
+ unsigned int arg_count,
+ CommandBufferEntry *args) {
+ if (arg_count == 3) {
+ namespace cmd = create_texture_cube_cmd;
+ unsigned int id = args[0].value_uint32;
+ unsigned int side_unused = args[1].value_uint32;
+ unsigned int levels_format_flags = args[2].value_uint32;
+ unsigned int side = cmd::Side::Get(side_unused);
+ unsigned int unused1 = cmd::Unused1::Get(side_unused);
+ unsigned int levels = cmd::Levels::Get(levels_format_flags);
+ unsigned int unused2 = cmd::Unused2::Get(levels_format_flags);
+ unsigned int format = cmd::Format::Get(levels_format_flags);
+ unsigned int flags = cmd::Flags::Get(levels_format_flags);
+ unsigned int max_levels = 1 + base::bits::Log2Ceiling(side);
+ if ((side == 0) || (levels > max_levels) || (unused1 != 0) ||
+ (unused2 != 0) || (format >= texture::NUM_FORMATS))
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ if (levels == 0) levels = max_levels;
+ return gapi_->CreateTextureCube(id, side, levels,
+ static_cast<texture::Format>(format),
+ flags);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+}
+
+// Decodes the SET_TEXTURE_DATA command.
+BufferSyncInterface::ParseError GAPIDecoder::DecodeSetTextureData(
+ unsigned int arg_count,
+ CommandBufferEntry *args) {
+ if (arg_count == 10) {
+ namespace cmd = set_texture_data_cmd;
+ unsigned int id = args[0].value_uint32;
+ unsigned int x_y = args[1].value_uint32;
+ unsigned int width_height = args[2].value_uint32;
+ unsigned int z_depth = args[3].value_uint32;
+ unsigned int level_face = args[4].value_uint32;
+ unsigned int row_pitch = args[5].value_uint32;
+ unsigned int slice_pitch = args[6].value_uint32;
+ unsigned int size = args[7].value_uint32;
+ unsigned int shm_id = args[8].value_uint32;
+ unsigned int offset = args[9].value_uint32;
+ unsigned int x = cmd::X::Get(x_y);
+ unsigned int y = cmd::Y::Get(x_y);
+ unsigned int width = cmd::Width::Get(width_height);
+ unsigned int height = cmd::Height::Get(width_height);
+ unsigned int z = cmd::Z::Get(z_depth);
+ unsigned int depth = cmd::Depth::Get(z_depth);
+ unsigned int level = cmd::Level::Get(level_face);
+ unsigned int face = cmd::Face::Get(level_face);
+ unsigned int unused = cmd::Unused::Get(level_face);
+ const void *data = GetAddressAndCheckSize(shm_id, offset, size);
+ if (face >= 6 || unused != 0 || !data)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return gapi_->SetTextureData(id, x, y, z, width, height, depth, level,
+ static_cast<texture::Face>(face), row_pitch,
+ slice_pitch, size, data);
+
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+}
+
+// Decodes the SET_TEXTURE_DATA_IMMEDIATE command.
+BufferSyncInterface::ParseError GAPIDecoder::DecodeSetTextureDataImmediate(
+ unsigned int arg_count,
+ CommandBufferEntry *args) {
+ if (arg_count > 8) {
+ namespace cmd = set_texture_data_immediate_cmd;
+ unsigned int id = args[0].value_uint32;
+ unsigned int x_y = args[1].value_uint32;
+ unsigned int width_height = args[2].value_uint32;
+ unsigned int z_depth = args[3].value_uint32;
+ unsigned int level_face = args[4].value_uint32;
+ unsigned int row_pitch = args[5].value_uint32;
+ unsigned int slice_pitch = args[6].value_uint32;
+ unsigned int size = args[7].value_uint32;
+ unsigned int x = cmd::X::Get(x_y);
+ unsigned int y = cmd::Y::Get(x_y);
+ unsigned int width = cmd::Width::Get(width_height);
+ unsigned int height = cmd::Height::Get(width_height);
+ unsigned int z = cmd::Z::Get(z_depth);
+ unsigned int depth = cmd::Depth::Get(z_depth);
+ unsigned int level = cmd::Level::Get(level_face);
+ unsigned int face = cmd::Face::Get(level_face);
+ unsigned int unused = cmd::Unused::Get(level_face);
+ if (face >= 6 || unused != 0 ||
+ size > (arg_count - 5) * sizeof(args[0]))
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return gapi_->SetTextureData(id, x, y, z, width, height, depth, level,
+ static_cast<texture::Face>(face), row_pitch,
+ slice_pitch, size, args + 8);
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+}
+
+// Decodes the GET_TEXTURE_DATA command.
+BufferSyncInterface::ParseError GAPIDecoder::DecodeGetTextureData(
+ unsigned int arg_count,
+ CommandBufferEntry *args) {
+ if (arg_count == 10) {
+ namespace cmd = get_texture_data_cmd;
+ unsigned int id = args[0].value_uint32;
+ unsigned int x_y = args[1].value_uint32;
+ unsigned int width_height = args[2].value_uint32;
+ unsigned int z_depth = args[3].value_uint32;
+ unsigned int level_face = args[4].value_uint32;
+ unsigned int row_pitch = args[5].value_uint32;
+ unsigned int slice_pitch = args[6].value_uint32;
+ unsigned int size = args[7].value_uint32;
+ unsigned int shm_id = args[8].value_uint32;
+ unsigned int offset = args[9].value_uint32;
+ unsigned int x = cmd::X::Get(x_y);
+ unsigned int y = cmd::Y::Get(x_y);
+ unsigned int width = cmd::Width::Get(width_height);
+ unsigned int height = cmd::Height::Get(width_height);
+ unsigned int z = cmd::Z::Get(z_depth);
+ unsigned int depth = cmd::Depth::Get(z_depth);
+ unsigned int level = cmd::Level::Get(level_face);
+ unsigned int face = cmd::Face::Get(level_face);
+ unsigned int unused = cmd::Unused::Get(level_face);
+ void *data = GetAddressAndCheckSize(shm_id, offset, size);
+ if (face >= 6 || unused != 0 || !data)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return gapi_->GetTextureData(id, x, y, z, width, height, depth, level,
+ static_cast<texture::Face>(face), row_pitch,
+ slice_pitch, size, data);
+
+ } else {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+}
+
+// Decodes the SET_SAMPLER_STATES command.
+BufferSyncInterface::ParseError GAPIDecoder::DecodeSetSamplerStates(
+ unsigned int arg_count,
+ CommandBufferEntry *args) {
+ namespace cmd = set_sampler_states;
+ if (arg_count != 2)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ ResourceID id = args[0].value_uint32;
+ Uint32 arg = args[1].value_uint32;
+ if (cmd::Unused::Get(arg) != 0)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ unsigned int address_u_value = cmd::AddressingU::Get(arg);
+ unsigned int address_v_value = cmd::AddressingV::Get(arg);
+ unsigned int address_w_value = cmd::AddressingW::Get(arg);
+ unsigned int mag_filter_value = cmd::MagFilter::Get(arg);
+ unsigned int min_filter_value = cmd::MinFilter::Get(arg);
+ unsigned int mip_filter_value = cmd::MipFilter::Get(arg);
+ unsigned int max_anisotropy = cmd::MaxAnisotropy::Get(arg);
+ if (address_u_value >= sampler::NUM_ADDRESSING_MODE ||
+ address_v_value >= sampler::NUM_ADDRESSING_MODE ||
+ address_w_value >= sampler::NUM_ADDRESSING_MODE ||
+ mag_filter_value >= sampler::NUM_FILTERING_MODE ||
+ min_filter_value >= sampler::NUM_FILTERING_MODE ||
+ mip_filter_value >= sampler::NUM_FILTERING_MODE ||
+ mag_filter_value == sampler::NONE ||
+ min_filter_value == sampler::NONE ||
+ max_anisotropy == 0) {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ gapi_->SetSamplerStates(
+ id,
+ static_cast<sampler::AddressingMode>(address_u_value),
+ static_cast<sampler::AddressingMode>(address_v_value),
+ static_cast<sampler::AddressingMode>(address_w_value),
+ static_cast<sampler::FilteringMode>(mag_filter_value),
+ static_cast<sampler::FilteringMode>(min_filter_value),
+ static_cast<sampler::FilteringMode>(mip_filter_value),
+ max_anisotropy);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+// Decodes the SET_STENCIL_TEST command.
+BufferSyncInterface::ParseError GAPIDecoder::DecodeSetStencilTest(
+ unsigned int arg_count,
+ CommandBufferEntry *args) {
+ namespace cmd = set_stencil_test;
+ if (arg_count != 2)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ Uint32 arg0 = args[0].value_uint32;
+ Uint32 arg1 = args[1].value_uint32;
+ if (cmd::Unused0::Get(arg0) != 0 ||
+ cmd::Unused1::Get(arg1) != 0 ||
+ cmd::Unused2::Get(arg1) != 0)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ unsigned int write_mask = cmd::WriteMask::Get(arg0);
+ unsigned int compare_mask = cmd::CompareMask::Get(arg0);
+ unsigned int ref = cmd::ReferenceValue::Get(arg0);
+ bool enable = cmd::Enable::Get(arg0) != 0;
+ bool separate_ccw = cmd::SeparateCCW::Get(arg0) != 0;
+ gapi_->SetStencilTest(enable, separate_ccw, write_mask, compare_mask, ref,
+ arg1);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+// Decodes the SET_BLENDING command.
+BufferSyncInterface::ParseError GAPIDecoder::DecodeSetBlending(
+ unsigned int arg_count,
+ CommandBufferEntry *args) {
+ namespace cmd = set_blending;
+ if (arg_count != 1)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ Uint32 arg = args[0].value_uint32;
+ bool enable = cmd::Enable::Get(arg) != 0;
+ bool separate_alpha = cmd::SeparateAlpha::Get(arg) != 0;
+ unsigned int color_eq = cmd::ColorEq::Get(arg);
+ unsigned int color_src = cmd::ColorSrcFunc::Get(arg);
+ unsigned int color_dst = cmd::ColorDstFunc::Get(arg);
+ unsigned int alpha_eq = cmd::AlphaEq::Get(arg);
+ unsigned int alpha_src = cmd::AlphaSrcFunc::Get(arg);
+ unsigned int alpha_dst = cmd::AlphaDstFunc::Get(arg);
+ if (cmd::Unused0::Get(arg) != 0 ||
+ cmd::Unused1::Get(arg) != 0 ||
+ color_eq >= GAPIInterface::NUM_BLEND_EQ ||
+ color_src >= GAPIInterface::NUM_BLEND_FUNC ||
+ color_dst >= GAPIInterface::NUM_BLEND_FUNC ||
+ alpha_eq >= GAPIInterface::NUM_BLEND_EQ ||
+ alpha_src >= GAPIInterface::NUM_BLEND_FUNC ||
+ alpha_dst >= GAPIInterface::NUM_BLEND_FUNC)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ gapi_->SetBlending(enable,
+ separate_alpha,
+ static_cast<GAPIInterface::BlendEq>(color_eq),
+ static_cast<GAPIInterface::BlendFunc>(color_src),
+ static_cast<GAPIInterface::BlendFunc>(color_dst),
+ static_cast<GAPIInterface::BlendEq>(alpha_eq),
+ static_cast<GAPIInterface::BlendFunc>(alpha_src),
+ static_cast<GAPIInterface::BlendFunc>(alpha_dst));
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+void *GAPIDecoder::GetAddressAndCheckSize(unsigned int shm_id,
+ unsigned int offset,
+ unsigned int size) {
+ void * shm_addr = engine_->GetSharedMemoryAddress(shm_id);
+ if (!shm_addr) return NULL;
+ size_t shm_size = engine_->GetSharedMemorySize(shm_id);
+ if (offset + size > shm_size) return NULL;
+ return static_cast<char *>(shm_addr) + offset;
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/service/cross/gapi_decoder.h b/o3d/command_buffer/service/cross/gapi_decoder.h
new file mode 100644
index 0000000..615bef6
--- /dev/null
+++ b/o3d/command_buffer/service/cross/gapi_decoder.h
@@ -0,0 +1,131 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the GAPI decoder class.
+
+#ifndef O3D_COMMAND_BUFFER_SERVICE_CROSS_GAPI_DECODER_H__
+#define O3D_COMMAND_BUFFER_SERVICE_CROSS_GAPI_DECODER_H__
+
+#include "core/cross/types.h"
+#include "command_buffer/service/cross/cmd_parser.h"
+
+namespace o3d {
+namespace command_buffer {
+
+class GAPIInterface;
+class CommandBufferEngine;
+
+// This class implements the AsyncAPIInterface interface, decoding GAPI
+// commands and sending them to a GAPI interface.
+class GAPIDecoder : public AsyncAPIInterface {
+ public:
+ typedef BufferSyncInterface::ParseError ParseError;
+
+ explicit GAPIDecoder(GAPIInterface *gapi) : gapi_(gapi), engine_(NULL) {}
+ virtual ~GAPIDecoder() {}
+ // Executes a command.
+ // Parameters:
+ // command: the command index.
+ // arg_count: the number of CommandBufferEntry arguments.
+ // args: the arguments.
+ // Returns:
+ // BufferSyncInterface::NO_ERROR if no error was found, one of
+ // BufferSyncInterface::ParseError otherwise.
+ virtual ParseError DoCommand(unsigned int command,
+ unsigned int arg_count,
+ CommandBufferEntry *args);
+
+ // Sets the engine, to get shared memory buffers from, and to set the token
+ // to.
+ void set_engine(CommandBufferEngine *engine) { engine_ = engine; }
+ private:
+ // Decodes the SET_VERTEX_INPUT command.
+ ParseError DecodeSetVertexInput(unsigned int arg_count,
+ CommandBufferEntry *args);
+
+ // Decodes the CREATE_TEXTURE_2D command.
+ ParseError DecodeCreateTexture2D(unsigned int arg_count,
+ CommandBufferEntry *args);
+
+ // Decodes the CREATE_TEXTURE_3D command.
+ ParseError DecodeCreateTexture3D(unsigned int arg_count,
+ CommandBufferEntry *args);
+
+ // Decodes the CREATE_TEXTURE_CUBE command.
+ ParseError DecodeCreateTextureCube(unsigned int arg_count,
+ CommandBufferEntry *args);
+
+ // Decodes the SET_TEXTURE_DATA command.
+ ParseError DecodeSetTextureData(unsigned int arg_count,
+ CommandBufferEntry *args);
+
+ // Decodes the SET_TEXTURE_DATA_IMMEDIATE command.
+ ParseError DecodeSetTextureDataImmediate(unsigned int arg_count,
+ CommandBufferEntry *args);
+
+ // Decodes the GET_TEXTURE_DATA command.
+ ParseError DecodeGetTextureData(unsigned int arg_count,
+ CommandBufferEntry *args);
+
+ // Decodes the SET_SAMPLER_STATES command.
+ ParseError DecodeSetSamplerStates(unsigned int arg_count,
+ CommandBufferEntry *args);
+
+ // Decodes the SET_STENCIL_TEST command.
+ ParseError DecodeSetStencilTest(unsigned int arg_count,
+ CommandBufferEntry *args);
+
+ // Decodes the SET_BLENDING command.
+ ParseError DecodeSetBlending(unsigned int arg_count,
+ CommandBufferEntry *args);
+
+ // Gets the address of shared memory data, given a shared memory ID and an
+ // offset. Also checks that the size is consistent with the shared memory
+ // size.
+ // Parameters:
+ // shm_id: the id of the shared memory buffer.
+ // offset: the offset of the data in the shared memory buffer.
+ // size: the size of the data.
+ // Returns:
+ // NULL if shm_id isn't a valid shared memory buffer ID or if the size
+ // check fails. Return a pointer to the data otherwise.
+ void *GetAddressAndCheckSize(unsigned int shm_id,
+ unsigned int offset,
+ unsigned int size);
+ GAPIInterface *gapi_;
+ CommandBufferEngine *engine_;
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_SERVICE_CROSS_GAPI_DECODER_H__
diff --git a/o3d/command_buffer/service/cross/gl/effect_gl.cc b/o3d/command_buffer/service/cross/gl/effect_gl.cc
new file mode 100644
index 0000000..9343d96
--- /dev/null
+++ b/o3d/command_buffer/service/cross/gl/effect_gl.cc
@@ -0,0 +1,633 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the implementation of the EffectParamGL and EffectGL
+// classes, as well as the effect-related GAPI functions on GL.
+
+#include <map>
+
+#include "base/cross/std_functional.h"
+#include "command_buffer/service/cross/gl/gapi_gl.h"
+#include "command_buffer/service/cross/effect_utils.h"
+
+namespace o3d {
+namespace command_buffer {
+
+EffectParamGL::EffectParamGL(effect_param::DataType data_type,
+ EffectGL *effect,
+ unsigned int param_index)
+ : EffectParam(data_type),
+ effect_(effect),
+ low_level_param_index_(param_index) {
+ DCHECK(effect_);
+ effect_->LinkParam(this);
+}
+
+EffectParamGL::~EffectParamGL() {
+ if (effect_)
+ effect_->UnlinkParam(this);
+}
+
+static effect_param::DataType CgTypeToCBType(CGtype cg_type) {
+ switch (cg_type) {
+ case CG_FLOAT:
+ case CG_FLOAT1:
+ return effect_param::FLOAT1;
+ case CG_FLOAT2:
+ return effect_param::FLOAT2;
+ case CG_FLOAT3:
+ return effect_param::FLOAT3;
+ case CG_FLOAT4:
+ return effect_param::FLOAT4;
+ case CG_INT:
+ case CG_INT1:
+ return effect_param::INT;
+ case CG_BOOL:
+ case CG_BOOL1:
+ return effect_param::BOOL;
+ case CG_FLOAT4x4:
+ return effect_param::MATRIX4;
+ case CG_SAMPLER:
+ case CG_SAMPLER1D:
+ case CG_SAMPLER2D:
+ case CG_SAMPLER3D:
+ case CG_SAMPLERCUBE:
+ return effect_param::SAMPLER;
+ default : {
+ DLOG(INFO) << "Cannot convert CGtype "
+ << cgGetTypeString(cg_type)
+ << " to a Param type.";
+ return effect_param::UNKNOWN;
+ }
+ }
+}
+
+EffectParamGL *EffectParamGL::Create(EffectGL *effect,
+ unsigned int index) {
+ DCHECK(effect);
+ const EffectGL::LowLevelParam &low_level_param =
+ effect->low_level_params_[index];
+ CGtype cg_type =
+ cgGetParameterType(EffectGL::GetEitherCgParameter(low_level_param));
+ effect_param::DataType type = CgTypeToCBType(cg_type);
+ if (type == effect_param::UNKNOWN) return NULL;
+ return new EffectParamGL(type, effect, index);
+}
+
+// Fills the Desc structure, appending name and semantic if any, and if enough
+// room is available in the buffer.
+bool EffectParamGL::GetDesc(unsigned int size, void *data) {
+ using effect_param::Desc;
+ if (size < sizeof(Desc)) // NOLINT
+ return false;
+ if (!effect_)
+ return false;
+ const EffectGL::LowLevelParam &low_level_param =
+ effect_->low_level_params_[low_level_param_index_];
+ CGparameter cg_param = EffectGL::GetEitherCgParameter(low_level_param);
+ const char *name = low_level_param.name;
+ const char* semantic = cgGetParameterSemantic(cg_param);
+ unsigned int name_size =
+ name ? static_cast<unsigned int>(strlen(name)) + 1 : 0;
+ unsigned int semantic_size = semantic ?
+ static_cast<unsigned int>(strlen(semantic)) + 1 : 0;
+ unsigned int total_size = sizeof(Desc) + name_size + semantic_size; // NOLINT
+
+ Desc *desc = static_cast<Desc *>(data);
+ memset(desc, 0, sizeof(*desc));
+ desc->size = total_size;
+ desc->data_type = data_type();
+ desc->data_size = GetDataSize(data_type());
+ desc->name_offset = 0;
+ desc->name_size = name_size;
+ desc->semantic_offset = 0;
+ desc->semantic_size = semantic_size;
+ unsigned int current_offset = sizeof(Desc);
+ if (name && current_offset + name_size <= size) {
+ desc->name_offset = current_offset;
+ memcpy(static_cast<char *>(data) + current_offset, name, name_size);
+ current_offset += name_size;
+ }
+ if (semantic && current_offset + semantic_size <= size) {
+ desc->semantic_offset = current_offset;
+ memcpy(static_cast<char *>(data) + current_offset, semantic, semantic_size);
+ current_offset += semantic_size;
+ }
+ return true;
+}
+
+// Sets the data into the Cg effect parameter, using the appropriate Cg call.
+bool EffectParamGL::SetData(GAPIGL *gapi,
+ unsigned int size,
+ const void * data) {
+ if (!effect_)
+ return false;
+
+ EffectGL::LowLevelParam &low_level_param =
+ effect_->low_level_params_[low_level_param_index_];
+ CGparameter vp_param = low_level_param.vp_param;
+ CGparameter fp_param = low_level_param.fp_param;
+ effect_param::DataType type = data_type();
+ if (size < effect_param::GetDataSize(type))
+ return false;
+
+ switch (type) {
+ case effect_param::FLOAT1:
+ if (vp_param)
+ cgSetParameter1f(vp_param, *static_cast<const float *>(data));
+ if (fp_param)
+ cgSetParameter1f(fp_param, *static_cast<const float *>(data));
+ break;
+ case effect_param::FLOAT2:
+ if (vp_param)
+ cgSetParameter2fv(vp_param, static_cast<const float *>(data));
+ if (fp_param)
+ cgSetParameter2fv(fp_param, static_cast<const float *>(data));
+ break;
+ case effect_param::FLOAT3:
+ if (vp_param)
+ cgSetParameter3fv(vp_param, static_cast<const float *>(data));
+ if (fp_param)
+ cgSetParameter3fv(fp_param, static_cast<const float *>(data));
+ break;
+ case effect_param::FLOAT4:
+ if (vp_param)
+ cgSetParameter4fv(vp_param, static_cast<const float *>(data));
+ if (fp_param)
+ cgSetParameter4fv(fp_param, static_cast<const float *>(data));
+ break;
+ case effect_param::MATRIX4:
+ if (vp_param)
+ cgSetMatrixParameterfr(vp_param, static_cast<const float *>(data));
+ if (fp_param)
+ cgSetMatrixParameterfr(fp_param, static_cast<const float *>(data));
+ break;
+ case effect_param::INT:
+ if (vp_param) cgSetParameter1i(vp_param, *static_cast<const int *>(data));
+ if (fp_param) cgSetParameter1i(fp_param, *static_cast<const int *>(data));
+ break;
+ case effect_param::BOOL: {
+ int bool_value = *static_cast<const bool *>(data)?1:0;
+ if (vp_param) cgSetParameter1i(vp_param, bool_value);
+ if (fp_param) cgSetParameter1i(fp_param, bool_value);
+ break;
+ }
+ case effect_param::SAMPLER: {
+ low_level_param.sampler_id = *static_cast<const ResourceID *>(data);
+ if (effect_ == gapi->current_effect()) {
+ gapi->DirtyEffect();
+ }
+ break;
+ }
+ default:
+ DLOG(ERROR) << "Invalid parameter type.";
+ return false;
+ }
+ return true;
+}
+EffectGL::EffectGL(CGprogram vertex_program,
+ CGprogram fragment_program)
+ : vertex_program_(vertex_program),
+ fragment_program_(fragment_program),
+ update_samplers_(true) {
+}
+
+EffectGL::~EffectGL() {
+ for (ParamResourceList::iterator it = resource_params_.begin();
+ it != resource_params_.end(); ++it) {
+ (*it)->ResetEffect();
+ }
+}
+
+void EffectGL::LinkParam(EffectParamGL *param) {
+ resource_params_.push_back(param);
+}
+
+void EffectGL::UnlinkParam(EffectParamGL *param) {
+ std::remove(resource_params_.begin(), resource_params_.end(), param);
+}
+
+// Rewrites vertex program assembly code to match GL semantics for clipping.
+// This parses the source, breaking it down into pieces:
+// - declaration ("!!ARBvp1.0")
+// - comments (that contain the parameter information)
+// - instructions
+// - "END" token.
+// Then it rewrites the instructions so that 'result.position' doesn't get
+// written directly, instead it is written to a temporary variable. Then a
+// transformation is done on that variable before outputing to
+// 'result.position':
+// - offset x an y by half a pixel (times w).
+// - remap z from [0..w] to [-w..w].
+//
+// Note that for the 1/2 pixel offset, we need a parameter that depends on the
+// current viewport. This is done through 'program.env[0]' which is shared
+// across all programs (so we only have to update it once when we change the
+// viewport), because Cg won't use them currently (it uses 'program.local'
+// instead).
+static bool RewriteVertexProgramSource(String *source) {
+ String::size_type pos = source->find('\n');
+ if (pos == String::npos) {
+ DLOG(ERROR) << "could not find program declaration";
+ return false;
+ }
+ String decl(*source, 0, pos + 1);
+ String::size_type start_comments = pos + 1;
+ // skip the comments that contain the parameters etc.
+ for (; pos < source->size(); pos = source->find('\n', pos)) {
+ ++pos;
+ if (pos >= source->size())
+ break;
+ if ((*source)[pos] != '#')
+ break;
+ }
+ if (pos >= source->size()) {
+ // we only found comments.
+ return false;
+ }
+ String comments(*source, start_comments, pos - start_comments);
+
+ String::size_type end_token = source->find("\nEND", pos + 1);
+ if (end_token == String::npos) {
+ DLOG(ERROR) << "Compiled shader doesn't have an END token";
+ return false;
+ }
+ String instructions(*source, pos, end_token + 1 - pos);
+
+ // Replace accesses to 'result.position' by accesses to our temp variable
+ // '$O3D_HPOS'.
+ // '$' is a valid symbol for identifiers, but Cg doesn't seem to be using
+ // it, so we can use it to ensure we don't have name conflicts.
+ static const char kOutPositionRegister[] = "result.position";
+ for (String::size_type i = instructions.find(kOutPositionRegister);
+ i < String::npos; i = instructions.find(kOutPositionRegister, i)) {
+ instructions.replace(i, strlen(kOutPositionRegister), "$O3D_HPOS");
+ }
+
+ *source = decl +
+ comments +
+ // .x = 1/viewport.width; .y = 1/viewport.height; .z = 2.0;
+ "PARAM $O3D_HELPER = program.env[0];\n"
+ "TEMP $O3D_HPOS;\n" +
+ instructions +
+ // hpos.x <- hpos.x + hpos.w / viewport.width;
+ // hpos.y <- hpos.y - hpos.w / viewport.height;
+ "MAD $O3D_HPOS.xy, $O3D_HELPER.xyyy, $O3D_HPOS.w, $O3D_HPOS.xyyy;\n"
+ // hpos.z <- hpos.z * 2 - hpos.w
+ "MAD $O3D_HPOS.z, $O3D_HPOS.z, $O3D_HELPER.z, -$O3D_HPOS.w;\n"
+ "MOV result.position, $O3D_HPOS;\n"
+ "END\n";
+ return true;
+}
+
+EffectGL *EffectGL::Create(GAPIGL *gapi,
+ const String& effect_code,
+ const String& vertex_program_entry,
+ const String& fragment_program_entry) {
+ CGcontext context = gapi->cg_context();
+ // Compile the original vertex program once, to get the ARBVP1 assembly code.
+ CGprogram original_vp = cgCreateProgram(
+ context, CG_SOURCE, effect_code.c_str(), CG_PROFILE_ARBVP1,
+ vertex_program_entry.c_str(), NULL);
+ const char* listing = cgGetLastListing(context);
+ if (original_vp == NULL) {
+ DLOG(ERROR) << "Effect Compile Error: " << cgGetErrorString(cgGetError())
+ << " : " << listing;
+ return NULL;
+ }
+
+ if (listing && listing[0] != 0) {
+ DLOG(WARNING) << "Effect Compile Warnings: " << listing;
+ }
+
+ String vp_assembly = cgGetProgramString(original_vp, CG_COMPILED_PROGRAM);
+ cgDestroyProgram(original_vp);
+ if (!RewriteVertexProgramSource(&vp_assembly)) {
+ return NULL;
+ }
+ CGprogram vertex_program = cgCreateProgram(
+ context, CG_OBJECT, vp_assembly.c_str(), CG_PROFILE_ARBVP1,
+ vertex_program_entry.c_str(), NULL);
+ listing = cgGetLastListing(context);
+ if (vertex_program == NULL) {
+ DLOG(ERROR) << "Effect post-rewrite Compile Error: "
+ << cgGetErrorString(cgGetError()) << " : " << listing;
+ return false;
+ }
+
+ if (listing && listing[0] != 0) {
+ DLOG(WARNING) << "Effect post-rewrite compile warnings: " << listing;
+ }
+
+ CHECK_GL_ERROR();
+
+ // If the program rewrite introduced some syntax or semantic errors, we won't
+ // know it until we load the program (through a GL error).
+ // So flush all GL errors first...
+ do {} while (glGetError() != GL_NO_ERROR);
+
+ // ... Then load the program ...
+ cgGLLoadProgram(vertex_program);
+
+ // ... And check for GL errors.
+ if (glGetError() != GL_NO_ERROR) {
+ DLOG(ERROR) << "Effect post-rewrite GL Error: "
+ << glGetString(GL_PROGRAM_ERROR_STRING_ARB)
+ << "\nSource: \n"
+ << vp_assembly;
+ return NULL;
+ }
+
+ CGprogram fragment_program = cgCreateProgram(
+ context, CG_SOURCE, effect_code.c_str(), CG_PROFILE_ARBFP1,
+ fragment_program_entry.c_str(), NULL);
+ listing = cgGetLastListing(context);
+ if (fragment_program == NULL) {
+ DLOG(ERROR) << "Effect Compile Error: "
+ << cgGetErrorString(cgGetError()) << " : "
+ << listing;
+ return NULL;
+ }
+
+ if (listing && listing[0] != 0) {
+ DLOG(WARNING) << "Effect Compile Warnings: " << listing;
+ }
+
+ cgGLLoadProgram(fragment_program);
+
+ // Also check for GL errors, in case Cg managed to compile, but generated a
+ // bad program.
+ if (glGetError() != GL_NO_ERROR) {
+ DLOG(ERROR) << "Effect GL Error: "
+ << glGetString(GL_PROGRAM_ERROR_STRING_ARB);
+ return false;
+ }
+ EffectGL *effect = new EffectGL(vertex_program, fragment_program);
+ effect->Initialize();
+ return effect;
+}
+
+int EffectGL::GetLowLevelParamIndexByName(const char *name) {
+ DCHECK(name);
+ for (unsigned int index = 0; index < low_level_params_.size(); ++index) {
+ if (!strcmp(name, low_level_params_[index].name)) {
+ return index;
+ }
+ }
+ return -1;
+}
+
+void EffectGL::AddLowLevelParams(CGparameter cg_param,
+ bool vp) {
+ // Loop over all *leaf* parameters, visiting only CGparameters that have
+ // had storage allocated to them.
+ for (; cg_param != NULL; cg_param = cgGetNextLeafParameter(cg_param)) {
+ CGenum variability = cgGetParameterVariability(cg_param);
+ if (variability != CG_UNIFORM)
+ continue;
+ CGenum direction = cgGetParameterDirection(cg_param);
+ if (direction != CG_IN)
+ continue;
+ const char *name = cgGetParameterName(cg_param);
+ if (!name)
+ continue;
+
+ int index = GetLowLevelParamIndexByName(name);
+ if (index < 0) {
+ LowLevelParam param = {name, NULL, NULL, kInvalidResource};
+ index = low_level_params_.size();
+ low_level_params_.push_back(param);
+ CGtype cg_type = cgGetParameterType(cg_param);
+ if (cg_type == CG_SAMPLER ||
+ cg_type == CG_SAMPLER1D ||
+ cg_type == CG_SAMPLER2D ||
+ cg_type == CG_SAMPLER3D ||
+ cg_type == CG_SAMPLERCUBE) {
+ sampler_params_.push_back(index);
+ }
+ }
+ if (vp) {
+ low_level_params_[index].vp_param = cg_param;
+ } else {
+ low_level_params_[index].fp_param = cg_param;
+ }
+ }
+}
+
+void EffectGL::Initialize() {
+ AddLowLevelParams(cgGetFirstLeafParameter(vertex_program_, CG_PROGRAM), true);
+ AddLowLevelParams(cgGetFirstLeafParameter(vertex_program_, CG_GLOBAL), true);
+ AddLowLevelParams(cgGetFirstLeafParameter(fragment_program_, CG_PROGRAM),
+ false);
+ AddLowLevelParams(cgGetFirstLeafParameter(fragment_program_, CG_GLOBAL),
+ false);
+}
+
+// Begins rendering with the effect, setting all the appropriate states.
+bool EffectGL::Begin(GAPIGL *gapi) {
+ cgGLBindProgram(vertex_program_);
+ cgGLBindProgram(fragment_program_);
+ // sampler->ApplyStates will mess with the texture binding on unit 0, so we
+ // do 2 passes.
+ // First to set the sampler states on the texture
+ for (unsigned int i = 0; i < sampler_params_.size(); ++i) {
+ unsigned int param_index = sampler_params_[i];
+ ResourceID id = low_level_params_[param_index].sampler_id;
+ if (id != kInvalidResource) {
+ SamplerGL *sampler = gapi->GetSampler(id);
+ if (!sampler->ApplyStates(gapi)) {
+ return false;
+ }
+ }
+ }
+ // Second to enable/disable the sampler params.
+ for (unsigned int i = 0; i < sampler_params_.size(); ++i) {
+ unsigned int param_index = sampler_params_[i];
+ const LowLevelParam &ll_param = low_level_params_[param_index];
+ ResourceID id = ll_param.sampler_id;
+ if (id != kInvalidResource) {
+ SamplerGL *sampler = gapi->GetSampler(id);
+ GLuint gl_texture = sampler->gl_texture();
+ cgGLSetTextureParameter(ll_param.fp_param, gl_texture);
+ cgGLEnableTextureParameter(ll_param.fp_param);
+ } else {
+ cgGLSetTextureParameter(ll_param.fp_param, 0);
+ cgGLDisableTextureParameter(ll_param.fp_param);
+ }
+ }
+ return true;
+}
+
+// Terminates rendering with the effect, resetting all the appropriate states.
+void EffectGL::End(GAPIGL *gapi) {
+}
+
+// Gets the parameter count from the list.
+unsigned int EffectGL::GetParamCount() const {
+ return low_level_params_.size();
+}
+
+// Gets a handle to the selected parameter, and wraps it into an
+// EffectParamGL if successful.
+EffectParamGL *EffectGL::CreateParam(unsigned int index) {
+ if (index < low_level_params_.size()) return NULL;
+ return EffectParamGL::Create(this, index);
+}
+
+// Gets a handle to the selected parameter, and wraps it into an
+// EffectParamGL if successful.
+EffectParamGL *EffectGL::CreateParamByName(const char *name) {
+ int index = GetLowLevelParamIndexByName(name);
+ if (index < 0) return NULL;
+ EffectParamGL::Create(this, index);
+}
+
+BufferSyncInterface::ParseError GAPIGL::CreateEffect(ResourceID id,
+ unsigned int size,
+ const void *data) {
+ if (id == current_effect_id_) DirtyEffect();
+ // Even though Assign would Destroy the effect at id, we do it explicitly in
+ // case the creation fails.
+ effects_.Destroy(id);
+ // Data is vp_main \0 fp_main \0 effect_text.
+ String vertex_program_entry;
+ String fragment_program_entry;
+ String effect_code;
+ if (!ParseEffectData(size, data,
+ &vertex_program_entry,
+ &fragment_program_entry,
+ &effect_code)) {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ EffectGL * effect = EffectGL::Create(this, effect_code,
+ vertex_program_entry,
+ fragment_program_entry);
+ if (!effect) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ effects_.Assign(id, effect);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+BufferSyncInterface::ParseError GAPIGL::DestroyEffect(ResourceID id) {
+ if (id == current_effect_id_) DirtyEffect();
+ return effects_.Destroy(id) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+BufferSyncInterface::ParseError GAPIGL::SetEffect(ResourceID id) {
+ DirtyEffect();
+ current_effect_id_ = id;
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+BufferSyncInterface::ParseError GAPIGL::GetParamCount(ResourceID id,
+ unsigned int size,
+ void *data) {
+ EffectGL *effect = effects_.Get(id);
+ if (!effect || size < sizeof(Uint32)) // NOLINT
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ *static_cast<Uint32 *>(data) = effect->GetParamCount();
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+BufferSyncInterface::ParseError GAPIGL::CreateParam(ResourceID param_id,
+ ResourceID effect_id,
+ unsigned int index) {
+ EffectGL *effect = effects_.Get(effect_id);
+ if (!effect) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ EffectParamGL *param = effect->CreateParam(index);
+ if (!param) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ effect_params_.Assign(param_id, param);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+BufferSyncInterface::ParseError GAPIGL::CreateParamByName(ResourceID param_id,
+ ResourceID effect_id,
+ unsigned int size,
+ const void *name) {
+ EffectGL *effect = effects_.Get(effect_id);
+ if (!effect) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ std::string string_name(static_cast<const char *>(name), size);
+ EffectParamGL *param = effect->CreateParamByName(string_name.c_str());
+ if (!param) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ effect_params_.Assign(param_id, param);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+BufferSyncInterface::ParseError GAPIGL::DestroyParam(ResourceID id) {
+ return effect_params_.Destroy(id) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+BufferSyncInterface::ParseError GAPIGL::SetParamData(ResourceID id,
+ unsigned int size,
+ const void *data) {
+ EffectParamGL *param = effect_params_.Get(id);
+ if (!param) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return param->SetData(this, size, data) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+BufferSyncInterface::ParseError GAPIGL::GetParamDesc(ResourceID id,
+ unsigned int size,
+ void *data) {
+ EffectParamGL *param = effect_params_.Get(id);
+ if (!param) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return param->GetDesc(size, data) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+// If the current effect is valid, call End on it, and tag for revalidation.
+void GAPIGL::DirtyEffect() {
+ if (validate_effect_) return;
+ DCHECK(current_effect_);
+ current_effect_->End(this);
+ current_effect_ = NULL;
+ validate_effect_ = true;
+}
+
+// Gets the current effect, and calls Begin on it (if successful).
+// Should only be called if the current effect is not valid.
+bool GAPIGL::ValidateEffect() {
+ DCHECK(validate_effect_);
+ DCHECK(!current_effect_);
+ current_effect_ = effects_.Get(current_effect_id_);
+ if (!current_effect_) return false;
+ validate_effect_ = false;
+ return current_effect_->Begin(this);
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/service/cross/gl/effect_gl.h b/o3d/command_buffer/service/cross/gl/effect_gl.h
new file mode 100644
index 0000000..fc29bf3
--- /dev/null
+++ b/o3d/command_buffer/service/cross/gl/effect_gl.h
@@ -0,0 +1,151 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the declaration of the EffectParamGL and EffectGL classes.
+
+#ifndef O3D_COMMAND_BUFFER_SERVICE_CROSS_GL_EFFECT_GL_H_
+#define O3D_COMMAND_BUFFER_SERVICE_CROSS_GL_EFFECT_GL_H_
+
+#include <vector>
+#include "command_buffer/common/cross/gapi_interface.h"
+#include "command_buffer/service/cross/resource.h"
+#include "command_buffer/service/cross/gl/gl_utils.h"
+
+namespace o3d {
+namespace command_buffer {
+
+class GAPIGL;
+class EffectGL;
+
+// GL version of EffectParam.
+class EffectParamGL: public EffectParam {
+ public:
+ EffectParamGL(effect_param::DataType data_type,
+ EffectGL *effect,
+ unsigned int param_index);
+ virtual ~EffectParamGL();
+
+ // Sets the data into the GL effect parameter.
+ bool SetData(GAPIGL *gapi, unsigned int size, const void * data);
+
+ // Gets the description of the parameter.
+ bool GetDesc(unsigned int size, void *data);
+
+ // Resets the effect back-pointer. This is called when the effect gets
+ // destroyed, to invalidate the parameter.
+ void ResetEffect() { effect_ = NULL; }
+
+ // Creates an EffectParamGL from the EffectGL, by index.
+ static EffectParamGL *Create(EffectGL *effect,
+ unsigned int index);
+ private:
+ EffectGL *effect_;
+ unsigned int low_level_param_index_;
+ DISALLOW_COPY_AND_ASSIGN(EffectParamGL);
+};
+
+// GL version of Effect.
+class EffectGL : public Effect {
+ public:
+ EffectGL(CGprogram vertex_program,
+ CGprogram fragment_program);
+ virtual ~EffectGL();
+
+ // Compiles and creates an effect from source code.
+ static EffectGL *Create(GAPIGL *gapi,
+ const String &effect_code,
+ const String &vertex_program_entry,
+ const String &fragment_program_entry);
+
+ // Applies the effect states (vertex shader, pixel shader) to GL.
+ bool Begin(GAPIGL *gapi);
+
+ // Resets the effect states (vertex shader, pixel shader) to GL.
+ void End(GAPIGL *gapi);
+
+ // Gets the number of parameters in the effect.
+ unsigned int GetParamCount() const;
+
+ // Creates an effect parameter with the specified index.
+ EffectParamGL *CreateParam(unsigned int index);
+
+ // Creates an effect parameter of the specified name.
+ EffectParamGL *CreateParamByName(const char *name);
+
+ private:
+ struct LowLevelParam {
+ const char *name;
+ CGparameter vp_param;
+ CGparameter fp_param;
+ ResourceID sampler_id;
+ };
+ typedef std::vector<LowLevelParam> LowLevelParamList;
+ typedef std::vector<EffectParamGL *> ParamResourceList;
+
+ static CGparameter GetEitherCgParameter(
+ const LowLevelParam &low_level_param) {
+ return low_level_param.vp_param ?
+ low_level_param.vp_param : low_level_param.fp_param;
+ }
+
+ int GetLowLevelParamIndexByName(const char *name);
+ void AddLowLevelParams(CGparameter cg_param, bool vp);
+
+ // Creates the low level structures.
+ void Initialize();
+
+ // Links a param into this effect.
+ void LinkParam(EffectParamGL *param);
+
+ // Unlinks a param into this effect.
+ void UnlinkParam(EffectParamGL *param);
+
+ CGprogram vertex_program_;
+ CGprogram fragment_program_;
+ // List of all the Param resources created.
+ ParamResourceList resource_params_;
+ // List of all the Cg parameters present in either the vertex program or the
+ // fragment program.
+ LowLevelParamList low_level_params_;
+ // List of the indices of the low level params that are samplers.
+ std::vector<unsigned int> sampler_params_;
+ bool update_samplers_;
+
+ friend class EffectParamGL;
+ DISALLOW_COPY_AND_ASSIGN(EffectGL);
+};
+
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_SERVICE_CROSS_GL_EFFECT_GL_H_
diff --git a/o3d/command_buffer/service/cross/gl/gapi_gl.cc b/o3d/command_buffer/service/cross/gl/gapi_gl.cc
new file mode 100644
index 0000000..a09375a
--- /dev/null
+++ b/o3d/command_buffer/service/cross/gl/gapi_gl.cc
@@ -0,0 +1,141 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file implements the GAPIGL class.
+
+#include <build/build_config.h>
+#include "command_buffer/service/cross/gl/gl_utils.h"
+#include "command_buffer/service/cross/gl/gapi_gl.h"
+
+#ifdef OS_LINUX
+#include "command_buffer/service/linux/x_utils.h"
+#endif // OS_LINUX
+
+namespace o3d {
+namespace command_buffer {
+
+GAPIGL::GAPIGL()
+#ifdef OS_LINUX
+ : window_(NULL),
+#endif
+ cg_context_(NULL),
+ current_vertex_struct_(kInvalidResource),
+ validate_streams_(true),
+ max_vertices_(0),
+ current_effect_id_(kInvalidResource),
+ validate_effect_(true),
+ current_effect_(NULL) {
+}
+
+GAPIGL::~GAPIGL() {
+}
+
+bool GAPIGL::Initialize() {
+#ifdef OS_LINUX
+ DCHECK(window_);
+ if (!window_->Initialize())
+ return false;
+ if (!window_->MakeCurrent())
+ return false;
+ InitCommon();
+ CHECK_GL_ERROR();
+ return true;
+#else
+ return false;
+#endif
+}
+
+void GAPIGL::InitCommon() {
+ cg_context_ = cgCreateContext();
+ // Set up all Cg State Assignments for OpenGL.
+ cgGLRegisterStates(cg_context_);
+ cgGLSetDebugMode(CG_FALSE);
+ // Enable the profiles we use.
+ cgGLEnableProfile(CG_PROFILE_ARBVP1);
+ cgGLEnableProfile(CG_PROFILE_ARBFP1);
+ // Initialize global GL settings.
+ // Tell GL that texture buffers can be single-byte aligned.
+ glPixelStorei(GL_PACK_ALIGNMENT, 1);
+ glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
+ glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST);
+ glHint(GL_POLYGON_SMOOTH_HINT, GL_NICEST);
+
+ // Get the initial viewport (set to the window size) to set up the helper
+ // constant.
+ GLint viewport[4];
+ glGetIntegerv(GL_VIEWPORT, viewport);
+ SetViewport(viewport[0], viewport[1], viewport[2], viewport[3], 0.f, 1.f);
+ CHECK_GL_ERROR();
+}
+
+void GAPIGL::Destroy() {
+ vertex_buffers_.DestroyAllResources();
+ index_buffers_.DestroyAllResources();
+ vertex_structs_.DestroyAllResources();
+ effects_.DestroyAllResources();
+ effect_params_.DestroyAllResources();
+ // textures_.DestroyAllResources();
+ // samplers_.DestroyAllResources();
+ cgDestroyContext(cg_context_);
+ cg_context_ = NULL;
+#ifdef OS_LINUX
+ DCHECK(window_);
+ window_->Destroy();
+#endif
+}
+
+void GAPIGL::BeginFrame() {
+}
+
+void GAPIGL::EndFrame() {
+#ifdef OS_LINUX
+ DCHECK(window_);
+ window_->SwapBuffers();
+#endif
+ CHECK_GL_ERROR();
+}
+
+void GAPIGL::Clear(unsigned int buffers,
+ const RGBA &color,
+ float depth,
+ unsigned int stencil) {
+ glClearColor(color.red, color.green, color.blue, color.alpha);
+ glClearDepth(depth);
+ glClearStencil(stencil);
+ glClear((buffers & COLOR ? GL_COLOR_BUFFER_BIT : 0) |
+ (buffers & DEPTH ? GL_DEPTH_BUFFER_BIT : 0) |
+ (buffers & STENCIL ? GL_STENCIL_BUFFER_BIT : 0));
+ CHECK_GL_ERROR();
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/service/cross/gl/gapi_gl.h b/o3d/command_buffer/service/cross/gl/gapi_gl.h
new file mode 100644
index 0000000..8d71800
--- /dev/null
+++ b/o3d/command_buffer/service/cross/gl/gapi_gl.h
@@ -0,0 +1,395 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the GAPIGL class, implementing the GAPI interface for
+// GL.
+
+#ifndef O3D_COMMAND_BUFFER_SERVICE_CROSS_GL_GAPI_GL_H__
+#define O3D_COMMAND_BUFFER_SERVICE_CROSS_GL_GAPI_GL_H__
+
+#include <build/build_config.h>
+#include "command_buffer/common/cross/gapi_interface.h"
+#include "command_buffer/service/cross/gl/gl_utils.h"
+#include "command_buffer/service/cross/gl/effect_gl.h"
+#include "command_buffer/service/cross/gl/geometry_gl.h"
+#include "command_buffer/service/cross/gl/sampler_gl.h"
+#include "command_buffer/service/cross/gl/texture_gl.h"
+
+namespace o3d {
+namespace command_buffer {
+#if defined(OS_LINUX)
+class XWindowWrapper;
+#endif // defined(OS_LINUX)
+
+// This class implements the GAPI interface for GL.
+class GAPIGL : public GAPIInterface {
+ public:
+ GAPIGL();
+ virtual ~GAPIGL();
+
+#if defined(OS_LINUX)
+ void set_window_wrapper(XWindowWrapper *window) { window_ = window; }
+#elif defined(OS_WIN)
+ void set_hwnd(HWND hwnd) { hwnd_ = hwnd; }
+#endif
+
+ // Initializes the graphics context, bound to a window.
+ // Returns:
+ // true if successful.
+ virtual bool Initialize();
+
+ // Destroys the graphics context.
+ virtual void Destroy();
+
+ // Implements the BeginFrame function for GL.
+ virtual void BeginFrame();
+
+ // Implements the EndFrame function for GL.
+ virtual void EndFrame();
+
+ // Implements the Clear function for GL.
+ virtual void Clear(unsigned int buffers,
+ const RGBA &color,
+ float depth,
+ unsigned int stencil);
+
+ // Implements the SetViewport function for GL.
+ virtual void SetViewport(unsigned int x,
+ unsigned int y,
+ unsigned int width,
+ unsigned int height,
+ float z_min,
+ float z_max);
+
+ // Implements the CreateVertexBuffer function for GL.
+ virtual ParseError CreateVertexBuffer(ResourceID id,
+ unsigned int size,
+ unsigned int flags);
+
+ // Implements the DestroyVertexBuffer function for GL.
+ virtual ParseError DestroyVertexBuffer(ResourceID id);
+
+ // Implements the SetVertexBufferData function for GL.
+ virtual ParseError SetVertexBufferData(ResourceID id,
+ unsigned int offset,
+ unsigned int size,
+ const void *data);
+
+ // Implements the GetVertexBufferData function for GL.
+ virtual ParseError GetVertexBufferData(ResourceID id,
+ unsigned int offset,
+ unsigned int size,
+ void *data);
+
+ // Implements the CreateIndexBuffer function for GL.
+ virtual ParseError CreateIndexBuffer(ResourceID id,
+ unsigned int size,
+ unsigned int flags);
+
+ // Implements the DestroyIndexBuffer function for GL.
+ virtual ParseError DestroyIndexBuffer(ResourceID id);
+
+ // Implements the SetIndexBufferData function for GL.
+ virtual ParseError SetIndexBufferData(ResourceID id,
+ unsigned int offset,
+ unsigned int size,
+ const void *data);
+
+ // Implements the GetIndexBufferData function for GL.
+ virtual ParseError GetIndexBufferData(ResourceID id,
+ unsigned int offset,
+ unsigned int size,
+ void *data);
+
+ // Implements the CreateVertexStruct function for GL.
+ virtual ParseError CreateVertexStruct(ResourceID id,
+ unsigned int input_count);
+
+ // Implements the DestroyVertexStruct function for GL.
+ virtual ParseError DestroyVertexStruct(ResourceID id);
+
+ // Implements the SetVertexInput function for GL.
+ virtual ParseError SetVertexInput(ResourceID vertex_struct_id,
+ unsigned int input_index,
+ ResourceID vertex_buffer_id,
+ unsigned int offset,
+ unsigned int stride,
+ vertex_struct::Type type,
+ vertex_struct::Semantic semantic,
+ unsigned int semantic_index);
+
+ // Implements the SetVertexStruct function for GL.
+ virtual ParseError SetVertexStruct(ResourceID id);
+
+ // Implements the Draw function for GL.
+ virtual ParseError Draw(PrimitiveType primitive_type,
+ unsigned int first,
+ unsigned int count);
+
+ // Implements the DrawIndexed function for GL.
+ virtual ParseError DrawIndexed(PrimitiveType primitive_type,
+ ResourceID index_buffer_id,
+ unsigned int first,
+ unsigned int count,
+ unsigned int min_index,
+ unsigned int max_index);
+
+ // Implements the CreateEffect function for GL.
+ virtual ParseError CreateEffect(ResourceID id,
+ unsigned int size,
+ const void *data);
+
+ // Implements the DestroyEffect function for GL.
+ virtual ParseError DestroyEffect(ResourceID id);
+
+ // Implements the SetEffect function for GL.
+ virtual ParseError SetEffect(ResourceID id);
+
+ // Implements the GetParamCount function for GL.
+ virtual ParseError GetParamCount(ResourceID id,
+ unsigned int size,
+ void *data);
+
+ // Implements the CreateParam function for GL.
+ virtual ParseError CreateParam(ResourceID param_id,
+ ResourceID effect_id,
+ unsigned int index);
+
+ // Implements the CreateParamByName function for GL.
+ virtual ParseError CreateParamByName(ResourceID param_id,
+ ResourceID effect_id,
+ unsigned int size,
+ const void *name);
+
+ // Implements the DestroyParam function for GL.
+ virtual ParseError DestroyParam(ResourceID id);
+
+ // Implements the SetParamData function for GL.
+ virtual ParseError SetParamData(ResourceID id,
+ unsigned int size,
+ const void *data);
+
+ // Implements the GetParamDesc function for GL.
+ virtual ParseError GetParamDesc(ResourceID id,
+ unsigned int size,
+ void *data);
+
+ // Implements the CreateTexture2D function for GL.
+ virtual ParseError CreateTexture2D(ResourceID id,
+ unsigned int width,
+ unsigned int height,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags);
+
+ // Implements the CreateTexture3D function for GL.
+ virtual ParseError CreateTexture3D(ResourceID id,
+ unsigned int width,
+ unsigned int height,
+ unsigned int depth,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags);
+
+ // Implements the CreateTextureCube function for GL.
+ virtual ParseError CreateTextureCube(ResourceID id,
+ unsigned int side,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags);
+
+ // Implements the SetTextureData function for GL.
+ virtual ParseError SetTextureData(ResourceID id,
+ unsigned int x,
+ unsigned int y,
+ unsigned int z,
+ unsigned int width,
+ unsigned int height,
+ unsigned int depth,
+ unsigned int level,
+ texture::Face face,
+ unsigned int pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ const void *data);
+
+ // Implements the GetTextureData function for GL.
+ virtual ParseError GetTextureData(ResourceID id,
+ unsigned int x,
+ unsigned int y,
+ unsigned int z,
+ unsigned int width,
+ unsigned int height,
+ unsigned int depth,
+ unsigned int level,
+ texture::Face face,
+ unsigned int pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ void *data);
+
+ // Implements the DestroyTexture function for GL.
+ virtual ParseError DestroyTexture(ResourceID id);
+
+ // Implements the CreateSampler function for GL.
+ virtual ParseError CreateSampler(ResourceID id);
+
+ // Implements the DestroySampler function for GL.
+ virtual ParseError DestroySampler(ResourceID id);
+
+ // Implements the SetSamplerStates function for GL.
+ virtual ParseError SetSamplerStates(ResourceID id,
+ sampler::AddressingMode addressing_u,
+ sampler::AddressingMode addressing_v,
+ sampler::AddressingMode addressing_w,
+ sampler::FilteringMode mag_filter,
+ sampler::FilteringMode min_filter,
+ sampler::FilteringMode mip_filter,
+ unsigned int max_anisotropy);
+
+ // Implements the SetSamplerBorderColor function for GL.
+ virtual ParseError SetSamplerBorderColor(ResourceID id, const RGBA &color);
+
+ // Implements the SetSamplerTexture function for GL.
+ virtual ParseError SetSamplerTexture(ResourceID id, ResourceID texture_id);
+
+ // Implements the SetScissor function for GL.
+ virtual void SetScissor(bool enable,
+ unsigned int x,
+ unsigned int y,
+ unsigned int width,
+ unsigned int height);
+
+ // Implements the SetPointLineRaster function for GL.
+ virtual void SetPointLineRaster(bool line_smooth,
+ bool point_sprite,
+ float point_size);
+
+ // Implements the SetPolygonOffset function for GL.
+ virtual void SetPolygonOffset(float slope_factor, float units);
+
+ // Implements the SetPolygonRaster function for GL.
+ virtual void SetPolygonRaster(PolygonMode fill_mode,
+ FaceCullMode cull_mode);
+
+ // Implements the SetAlphaTest function for GL.
+ virtual void SetAlphaTest(bool enable,
+ float reference,
+ Comparison comp);
+
+ // Implements the SetDepthTest function for GL.
+ virtual void SetDepthTest(bool enable,
+ bool write_enable,
+ Comparison comp);
+
+ // Implements the SetStencilTest function for GL.
+ virtual void SetStencilTest(bool enable,
+ bool separate_ccw,
+ unsigned int write_mask,
+ unsigned int compare_mask,
+ unsigned int ref,
+ Uint32 func_ops);
+
+ // Implements the SetColorWritefunction for GL.
+ virtual void SetColorWrite(bool red,
+ bool green,
+ bool blue,
+ bool alpha,
+ bool dither);
+
+ // Implements the SetBlending function for GL.
+ virtual void SetBlending(bool enable,
+ bool separate_alpha,
+ BlendEq color_eq,
+ BlendFunc color_src_func,
+ BlendFunc color_dst_func,
+ BlendEq alpha_eq,
+ BlendFunc alpha_src_func,
+ BlendFunc alpha_dst_func);
+
+ // Implements the SetBlendingColor function for GL.
+ virtual void SetBlendingColor(const RGBA &color);
+
+ // Gets a vertex buffer by resource ID.
+ VertexBufferGL *GetVertexBuffer(ResourceID id) {
+ return vertex_buffers_.Get(id);
+ }
+
+ // Gets a texture by resource ID.
+ TextureGL *GetTexture(ResourceID id) {
+ return textures_.Get(id);
+ }
+
+ // Gets a sampler by resource ID.
+ SamplerGL *GetSampler(ResourceID id) {
+ return samplers_.Get(id);
+ }
+
+ CGcontext cg_context() const { return cg_context_; }
+
+ EffectGL *current_effect() const { return current_effect_; }
+ // "Dirty" the current effect. This resets the vertex and fragment program,
+ // and requires ValidateEffect() to be called before further draws occur.
+ void DirtyEffect();
+ private:
+ void InitCommon();
+ // Validates the current vertex struct to GL, setting the vertex attributes.
+ bool ValidateStreams();
+ // Validates the current effect to GL. This sets the vertex and fragment
+ // programs, and updates parameters if needed.
+ bool ValidateEffect();
+
+#ifdef OS_LINUX
+ XWindowWrapper *window_;
+#endif
+ CGcontext cg_context_;
+
+ ResourceID current_vertex_struct_;
+ bool validate_streams_;
+ unsigned int max_vertices_;
+ ResourceID current_effect_id_;
+ bool validate_effect_;
+ EffectGL *current_effect_;
+
+ ResourceMap<VertexBufferGL> vertex_buffers_;
+ ResourceMap<IndexBufferGL> index_buffers_;
+ ResourceMap<VertexStructGL> vertex_structs_;
+ ResourceMap<EffectGL> effects_;
+ ResourceMap<EffectParamGL> effect_params_;
+ ResourceMap<TextureGL> textures_;
+ ResourceMap<SamplerGL> samplers_;
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_SERVICE_CROSS_GL_GAPI_GL_H__
diff --git a/o3d/command_buffer/service/cross/gl/geometry_gl.cc b/o3d/command_buffer/service/cross/gl/geometry_gl.cc
new file mode 100644
index 0000000..2dd8758
--- /dev/null
+++ b/o3d/command_buffer/service/cross/gl/geometry_gl.cc
@@ -0,0 +1,548 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the implementation of the VertexBufferGL, IndexBufferGL
+// and VertexStructGL classes, as well as the geometry-related GAPI functions.
+
+#include "command_buffer/service/cross/gl/gapi_gl.h"
+#include "command_buffer/service/cross/gl/geometry_gl.h"
+
+namespace o3d {
+namespace command_buffer {
+
+VertexBufferGL::~VertexBufferGL() {
+ glDeleteBuffers(1, &gl_buffer_);
+ CHECK_GL_ERROR();
+}
+
+// Creates the GL buffer object.
+void VertexBufferGL::Create() {
+ glGenBuffers(1, &gl_buffer_);
+ glBindBuffer(GL_ARRAY_BUFFER, gl_buffer_);
+ GLenum usage =
+ (flags() & vertex_buffer::DYNAMIC) ? GL_DYNAMIC_DRAW : GL_STATIC_DRAW;
+ glBufferData(GL_ARRAY_BUFFER, size(), NULL, usage);
+ CHECK_GL_ERROR();
+}
+
+// Sets the data into the GL buffer object.
+bool VertexBufferGL::SetData(unsigned int offset,
+ unsigned int size,
+ const void *data) {
+ if (!gl_buffer_) {
+ LOG(ERROR) << "Calling SetData on a non-initialized VertexBufferGL.";
+ return false;
+ }
+ if ((offset >= this->size()) || (offset + size > this->size())) {
+ LOG(ERROR) << "Invalid size or offset on VertexBufferGL::SetData.";
+ return false;
+ }
+ glBindBuffer(GL_ARRAY_BUFFER, gl_buffer_);
+ glBufferSubData(GL_ARRAY_BUFFER, offset, size, data);
+ CHECK_GL_ERROR();
+ return true;
+}
+
+// Gets the data from the GL buffer object.
+bool VertexBufferGL::GetData(unsigned int offset,
+ unsigned int size,
+ void *data) {
+ if (!gl_buffer_) {
+ LOG(ERROR) << "Calling GetData on a non-initialized VertexBufferGL.";
+ return false;
+ }
+ if ((offset >= this->size()) || (offset + size > this->size())) {
+ LOG(ERROR) << "Invalid size or offset on VertexBufferGL::GetData.";
+ return false;
+ }
+ glBindBuffer(GL_ARRAY_BUFFER, gl_buffer_);
+ glGetBufferSubData(GL_ARRAY_BUFFER, offset, size, data);
+ CHECK_GL_ERROR();
+ return true;
+}
+
+IndexBufferGL::~IndexBufferGL() {
+ glDeleteBuffers(1, &gl_buffer_);
+}
+
+// Creates the GL buffer object.
+void IndexBufferGL::Create() {
+ glGenBuffers(1, &gl_buffer_);
+ glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, gl_buffer_);
+ GLenum usage =
+ (flags() & vertex_buffer::DYNAMIC) ? GL_DYNAMIC_DRAW : GL_STATIC_DRAW;
+ glBufferData(GL_ELEMENT_ARRAY_BUFFER, size(), NULL, usage);
+ CHECK_GL_ERROR();
+}
+
+// Sets the data into the GL buffer object.
+bool IndexBufferGL::SetData(unsigned int offset,
+ unsigned int size,
+ const void *data) {
+ if (!gl_buffer_) {
+ LOG(ERROR) << "Calling SetData on a non-initialized IndexBufferGL.";
+ return false;
+ }
+ if ((offset >= this->size()) || (offset + size > this->size())) {
+ LOG(ERROR) << "Invalid size or offset on IndexBufferGL::SetData.";
+ return false;
+ }
+ glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, gl_buffer_);
+ glBufferSubData(GL_ELEMENT_ARRAY_BUFFER, offset, size, data);
+ CHECK_GL_ERROR();
+ return true;
+}
+
+// Gets the data from the GL buffer object.
+bool IndexBufferGL::GetData(unsigned int offset,
+ unsigned int size,
+ void *data) {
+ if (!gl_buffer_) {
+ LOG(ERROR) << "Calling GetData on a non-initialized IndexBufferGL.";
+ return false;
+ }
+ if ((offset >= this->size()) || (offset + size > this->size())) {
+ LOG(ERROR) << "Invalid size or offset on IndexBufferGL::GetData.";
+ return false;
+ }
+ glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, gl_buffer_);
+ glGetBufferSubData(GL_ELEMENT_ARRAY_BUFFER, offset, size, data);
+ CHECK_GL_ERROR();
+ return true;
+}
+
+// Sets the input element in the VertexStruct resource.
+void VertexStructGL::SetInput(unsigned int input_index,
+ ResourceID vertex_buffer_id,
+ unsigned int offset,
+ unsigned int stride,
+ vertex_struct::Type type,
+ vertex_struct::Semantic semantic,
+ unsigned int semantic_index) {
+ Element &element = GetElement(input_index);
+ element.vertex_buffer = vertex_buffer_id;
+ element.offset = offset;
+ element.stride = stride;
+ element.type = type;
+ element.semantic = semantic;
+ element.semantic_index = semantic_index;
+ dirty_ = true;
+}
+
+namespace {
+
+inline const GLvoid *OffsetToPtr(GLintptr offset) {
+ return static_cast<char *>(NULL) + offset;
+}
+
+} // anonymous namespace
+
+unsigned int VertexStructGL::SetStreams(GAPIGL *gapi) {
+ if (dirty_) Compile();
+ unsigned int max_vertices = UINT_MAX;
+ for (unsigned int i = 0; i < kMaxAttribs; ++i) {
+ const AttribDesc &attrib = attribs_[i];
+ if (attrib.vertex_buffer_id == kInvalidResource) {
+ if (i == 0) {
+ glDisableClientState(GL_VERTEX_ARRAY);
+ } else {
+ glDisableVertexAttribArray(i);
+ }
+ } else {
+ glEnableVertexAttribArray(i);
+ VertexBufferGL *vertex_buffer =
+ gapi->GetVertexBuffer(attrib.vertex_buffer_id);
+ if (!vertex_buffer) {
+ glDisableVertexAttribArray(i);
+ max_vertices = 0;
+ continue;
+ }
+ DCHECK_NE(vertex_buffer->gl_buffer(), 0);
+ glBindBuffer(GL_ARRAY_BUFFER, vertex_buffer->gl_buffer());
+ glVertexAttribPointer(i, attrib.size, attrib.type, attrib.normalized,
+ attrib.stride, OffsetToPtr(attrib.offset));
+ max_vertices = std::min(max_vertices,
+ vertex_buffer->size() / attrib.stride);
+ }
+ }
+ CHECK_GL_ERROR();
+ return max_vertices;
+}
+
+namespace {
+
+// from the ARB_vertex_program extension, at
+// http://www.opengl.org/registry/specs/ARB/vertex_program.txt
+//
+// Generic
+// Attribute Conventional Attribute Conventional Attribute Command
+// --------- ------------------------ ------------------------------
+// 0 vertex position Vertex
+// 1 vertex weights 0-3 WeightARB, VertexWeightEXT
+// 2 normal Normal
+// 3 primary color Color
+// 4 secondary color SecondaryColorEXT
+// 5 fog coordinate FogCoordEXT
+// 6 - -
+// 7 - -
+// 8 texture coordinate set 0 MultiTexCoord(TEXTURE0, ...)
+// 9 texture coordinate set 1 MultiTexCoord(TEXTURE1, ...)
+// 10 texture coordinate set 2 MultiTexCoord(TEXTURE2, ...)
+// 11 texture coordinate set 3 MultiTexCoord(TEXTURE3, ...)
+// 12 texture coordinate set 4 MultiTexCoord(TEXTURE4, ...)
+// 13 texture coordinate set 5 MultiTexCoord(TEXTURE5, ...)
+// 14 texture coordinate set 6 MultiTexCoord(TEXTURE6, ...)
+// 15 texture coordinate set 7 MultiTexCoord(TEXTURE7, ...)
+// 8+n texture coordinate set n MultiTexCoord(TEXTURE0+n, ...)
+//
+// Note: we only accept at most 8 texture coordinates for maximum compatibility
+// with DirectX.
+
+inline unsigned int GetAttribIndex(vertex_struct::Semantic semantic,
+ unsigned int semantic_index) {
+ switch (semantic) {
+ case vertex_struct::POSITION:
+ DCHECK_EQ(semantic_index, 0);
+ return 0;
+ case vertex_struct::NORMAL:
+ DCHECK_EQ(semantic_index, 0);
+ return 2;
+ case vertex_struct::COLOR:
+ DCHECK_LT(semantic_index, 2);
+ return 3 + semantic_index;
+ case vertex_struct::TEX_COORD:
+ DCHECK_LT(semantic_index, 8);
+ return 8 + semantic_index;
+ default:
+ DLOG(FATAL) << "Not reached.";
+ break;
+ }
+}
+
+inline void ExtractSizeTypeNormalized(vertex_struct::Type type,
+ GLint *size,
+ GLenum *gl_type,
+ GLboolean *normalized) {
+ switch (type) {
+ case vertex_struct::FLOAT1:
+ case vertex_struct::FLOAT2:
+ case vertex_struct::FLOAT3:
+ case vertex_struct::FLOAT4:
+ *size = type - vertex_struct::FLOAT1 + 1;
+ *gl_type = GL_FLOAT;
+ *normalized = false;
+ break;
+ case vertex_struct::UCHAR4N:
+ *size = 4;
+ *gl_type = GL_UNSIGNED_BYTE;
+ *normalized = true;
+ break;
+ default:
+ DLOG(FATAL) << "Not reached.";
+ break;
+ }
+}
+
+} // anonymous namespace
+
+#ifndef COMPILER_MSVC
+// Although required by the spec, this causes problems on MSVC. It is needed by
+// GCC.
+const unsigned int VertexStructGL::kMaxAttribs;
+#endif
+
+void VertexStructGL::Compile() {
+ DCHECK(dirty_);
+ for (unsigned int i = 0; i < kMaxAttribs; ++i) {
+ attribs_[i].vertex_buffer_id = kInvalidResource;
+ }
+ for (unsigned int i = 0; i < count_ ; ++i) {
+ const Element &element = GetElement(i);
+ unsigned int index = GetAttribIndex(element.semantic,
+ element.semantic_index);
+ DCHECK_LT(index, kMaxAttribs);
+ AttribDesc &attrib = attribs_[index];
+ attrib.vertex_buffer_id = element.vertex_buffer;
+ ExtractSizeTypeNormalized(element.type, &attrib.size, &attrib.type,
+ &attrib.normalized);
+ attrib.stride = element.stride;
+ attrib.offset = element.offset;
+ }
+ dirty_ = false;
+}
+
+BufferSyncInterface::ParseError GAPIGL::CreateVertexBuffer(ResourceID id,
+ unsigned int size,
+ unsigned int flags) {
+ VertexBufferGL *vertex_buffer = new VertexBufferGL(size, flags);
+ vertex_buffer->Create();
+ vertex_buffers_.Assign(id, vertex_buffer);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+BufferSyncInterface::ParseError GAPIGL::DestroyVertexBuffer(ResourceID id) {
+ return vertex_buffers_.Destroy(id) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+BufferSyncInterface::ParseError GAPIGL::SetVertexBufferData(ResourceID id,
+ unsigned int offset,
+ unsigned int size,
+ const void *data) {
+ VertexBufferGL *vertex_buffer = vertex_buffers_.Get(id);
+ if (!vertex_buffer) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return vertex_buffer->SetData(offset, size, data) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+BufferSyncInterface::ParseError GAPIGL::GetVertexBufferData(ResourceID id,
+ unsigned int offset,
+ unsigned int size,
+ void *data) {
+ VertexBufferGL *vertex_buffer = vertex_buffers_.Get(id);
+ if (!vertex_buffer) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return vertex_buffer->GetData(offset, size, data) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+BufferSyncInterface::ParseError GAPIGL::CreateIndexBuffer(ResourceID id,
+ unsigned int size,
+ unsigned int flags) {
+ IndexBufferGL *index_buffer = new IndexBufferGL(size, flags);
+ index_buffer->Create();
+ index_buffers_.Assign(id, index_buffer);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+BufferSyncInterface::ParseError GAPIGL::DestroyIndexBuffer(ResourceID id) {
+ return vertex_buffers_.Destroy(id) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+BufferSyncInterface::ParseError GAPIGL::SetIndexBufferData(ResourceID id,
+ unsigned int offset,
+ unsigned int size,
+ const void *data) {
+ IndexBufferGL *index_buffer = index_buffers_.Get(id);
+ if (!index_buffer) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return index_buffer->SetData(offset, size, data) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+BufferSyncInterface::ParseError GAPIGL::GetIndexBufferData(ResourceID id,
+ unsigned int offset,
+ unsigned int size,
+ void *data) {
+ IndexBufferGL *index_buffer = index_buffers_.Get(id);
+ if (!index_buffer) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return index_buffer->GetData(offset, size, data) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+BufferSyncInterface::ParseError GAPIGL::CreateVertexStruct(
+ ResourceID id,
+ unsigned int input_count) {
+ if (id == current_vertex_struct_) validate_streams_ = true;
+ VertexStructGL *vertex_struct = new VertexStructGL(input_count);
+ vertex_structs_.Assign(id, vertex_struct);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+BufferSyncInterface::ParseError GAPIGL::DestroyVertexStruct(ResourceID id) {
+ if (id == current_vertex_struct_) validate_streams_ = true;
+ return vertex_structs_.Destroy(id) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+BufferSyncInterface::ParseError GAPIGL::SetVertexInput(
+ ResourceID vertex_struct_id,
+ unsigned int input_index,
+ ResourceID vertex_buffer_id,
+ unsigned int offset,
+ unsigned int stride,
+ vertex_struct::Type type,
+ vertex_struct::Semantic semantic,
+ unsigned int semantic_index) {
+ switch (semantic) {
+ case vertex_struct::POSITION:
+ if (semantic_index != 0) {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ break;
+ case vertex_struct::NORMAL:
+ if (semantic_index != 0) {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ break;
+ case vertex_struct::COLOR:
+ if (semantic_index >= 2) {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ break;
+ case vertex_struct::TEX_COORD:
+ if (semantic_index >= 8) {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ break;
+ default:
+ DLOG(FATAL) << "Not reached.";
+ break;
+ }
+ if (vertex_buffer_id == current_vertex_struct_) validate_streams_ = true;
+ VertexStructGL *vertex_struct = vertex_structs_.Get(vertex_struct_id);
+ if (!vertex_struct || input_index >= vertex_struct->count())
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ vertex_struct->SetInput(input_index, vertex_buffer_id, offset, stride, type,
+ semantic, semantic_index);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+BufferSyncInterface::ParseError GAPIGL::SetVertexStruct(ResourceID id) {
+ current_vertex_struct_ = id;
+ validate_streams_ = true;
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+bool GAPIGL::ValidateStreams() {
+ DCHECK(validate_streams_);
+ VertexStructGL *vertex_struct = vertex_structs_.Get(current_vertex_struct_);
+ if (!vertex_struct) {
+ LOG(ERROR) << "Drawing with invalid streams.";
+ return false;
+ }
+ max_vertices_ = vertex_struct->SetStreams(this);
+ validate_streams_ = false;
+ return max_vertices_ > 0;
+}
+
+namespace {
+
+void PrimitiveTypeToGL(GAPIInterface::PrimitiveType primitive_type,
+ GLenum *gl_mode,
+ unsigned int *count) {
+ switch (primitive_type) {
+ case GAPIInterface::POINTS:
+ *gl_mode = GL_POINTS;
+ break;
+ case GAPIInterface::LINES:
+ *gl_mode = GL_LINES;
+ *count *= 2;
+ break;
+ case GAPIInterface::LINE_STRIPS:
+ *gl_mode = GL_LINE_STRIP;
+ ++*count;
+ break;
+ case GAPIInterface::TRIANGLES:
+ *gl_mode = GL_TRIANGLES;
+ *count *= 3;
+ break;
+ case GAPIInterface::TRIANGLE_STRIPS:
+ *gl_mode = GL_TRIANGLE_STRIP;
+ *count += 2;
+ break;
+ case GAPIInterface::TRIANGLE_FANS:
+ *gl_mode = GL_TRIANGLE_FAN;
+ *count += 2;
+ break;
+ default:
+ LOG(FATAL) << "Invalid primitive type";
+ break;
+ }
+}
+
+} // anonymous namespace
+
+BufferSyncInterface::ParseError GAPIGL::Draw(PrimitiveType primitive_type,
+ unsigned int first,
+ unsigned int count) {
+ if (validate_effect_ && !ValidateEffect()) {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ DCHECK(current_effect_);
+ if (validate_streams_ && !ValidateStreams()) {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ GLenum gl_mode = GL_POINTS;
+ PrimitiveTypeToGL(primitive_type, &gl_mode, &count);
+ if (first + count > max_vertices_) {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ glDrawArrays(gl_mode, first, count);
+ CHECK_GL_ERROR();
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+BufferSyncInterface::ParseError GAPIGL::DrawIndexed(
+ PrimitiveType primitive_type,
+ ResourceID index_buffer_id,
+ unsigned int first,
+ unsigned int count,
+ unsigned int min_index,
+ unsigned int max_index) {
+ IndexBufferGL *index_buffer = index_buffers_.Get(index_buffer_id);
+ if (!index_buffer) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ if (validate_effect_ && !ValidateEffect()) {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ DCHECK(current_effect_);
+ if (validate_streams_ && !ValidateStreams()) {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ if ((min_index >= max_vertices_) || (max_index > max_vertices_)) {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ GLenum gl_mode = GL_POINTS;
+ PrimitiveTypeToGL(primitive_type, &gl_mode, &count);
+ glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, index_buffer->gl_buffer());
+ GLenum index_type = (index_buffer->flags() & index_buffer::INDEX_32BIT) ?
+ GL_UNSIGNED_INT : GL_UNSIGNED_SHORT;
+ GLuint index_size = (index_buffer->flags() & index_buffer::INDEX_32BIT) ?
+ sizeof(GLuint) : sizeof(GLushort); // NOLINT
+ GLuint offset = first * index_size;
+ if (offset + count * index_size > index_buffer->size()) {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ glDrawRangeElements(gl_mode, min_index, max_index, count, index_type,
+ OffsetToPtr(offset));
+ CHECK_GL_ERROR();
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/service/cross/gl/geometry_gl.h b/o3d/command_buffer/service/cross/gl/geometry_gl.h
new file mode 100644
index 0000000..580f14d
--- /dev/null
+++ b/o3d/command_buffer/service/cross/gl/geometry_gl.h
@@ -0,0 +1,144 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file declares the VertexBufferGL, IndexBufferGL and VertexStructGL
+// classes.
+
+#ifndef O3D_COMMAND_BUFFER_SERVICE_CROSS_GL_GEOMETRY_GL_H_
+#define O3D_COMMAND_BUFFER_SERVICE_CROSS_GL_GEOMETRY_GL_H_
+
+#include "command_buffer/common/cross/gapi_interface.h"
+#include "command_buffer/service/cross/resource.h"
+#include "command_buffer/service/cross/gl/gl_utils.h"
+
+namespace o3d {
+namespace command_buffer {
+
+class GAPIGL;
+
+// GL version of VertexBuffer.
+class VertexBufferGL : public VertexBuffer {
+ public:
+ VertexBufferGL(unsigned int size, unsigned int flags)
+ : VertexBuffer(size, flags),
+ gl_buffer_(0) {}
+ virtual ~VertexBufferGL();
+
+ // Creates the GL vertex buffer.
+ void Create();
+
+ // Sets the data into the GL vertex buffer.
+ bool SetData(unsigned int offset, unsigned int size, const void *data);
+
+ // Gets the data from the GL vertex buffer.
+ bool GetData(unsigned int offset, unsigned int size, void *data);
+
+ // Gets the GL vertex buffer.
+ GLuint gl_buffer() const { return gl_buffer_; }
+
+ private:
+ GLuint gl_buffer_;
+ DISALLOW_COPY_AND_ASSIGN(VertexBufferGL);
+};
+
+// GL version of IndexBuffer.
+class IndexBufferGL : public IndexBuffer {
+ public:
+ IndexBufferGL(unsigned int size, unsigned int flags)
+ : IndexBuffer(size, flags),
+ gl_buffer_(0) {}
+ virtual ~IndexBufferGL();
+
+ // Creates the GL index buffer.
+ void Create();
+
+ // Sets the data into the GL index buffer.
+ bool SetData(unsigned int offset, unsigned int size, const void *data);
+
+ // Gets the data from the GL index buffer.
+ bool GetData(unsigned int offset, unsigned int size, void *data);
+
+ // Gets the GL index buffer.
+ GLuint gl_buffer() const { return gl_buffer_; }
+
+ private:
+ GLuint gl_buffer_;
+ DISALLOW_COPY_AND_ASSIGN(IndexBufferGL);
+};
+
+// GL version of VertexStruct.
+class VertexStructGL : public VertexStruct {
+ public:
+ explicit VertexStructGL(unsigned int count)
+ : VertexStruct(count),
+ dirty_(true) {}
+ virtual ~VertexStructGL() {}
+
+ // Adds an input to the vertex struct.
+ void SetInput(unsigned int input_index,
+ ResourceID vertex_buffer_id,
+ unsigned int offset,
+ unsigned int stride,
+ vertex_struct::Type type,
+ vertex_struct::Semantic semantic,
+ unsigned int semantic_index);
+
+ // Sets the input streams to GL.
+ unsigned int SetStreams(GAPIGL *gapi);
+
+ private:
+ static const unsigned int kMaxAttribs = 16;
+
+ // This struct describes the parameters that are passed to
+ // glVertexAttribPointer.
+ struct AttribDesc {
+ ResourceID vertex_buffer_id;
+ GLint size;
+ GLenum type;
+ GLboolean normalized;
+ GLsizei stride;
+ GLintptr offset;
+ };
+
+ // Compiles the vertex declaration into the attribute array.
+ void Compile();
+
+ bool dirty_;
+ AttribDesc attribs_[kMaxAttribs];
+ DISALLOW_COPY_AND_ASSIGN(VertexStructGL);
+};
+
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_SERVICE_CROSS_GL_GEOMETRY_GL_H_
diff --git a/o3d/command_buffer/service/cross/gl/gl_utils.h b/o3d/command_buffer/service/cross/gl/gl_utils.h
new file mode 100644
index 0000000..b41a4cf
--- /dev/null
+++ b/o3d/command_buffer/service/cross/gl/gl_utils.h
@@ -0,0 +1,63 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file includes all the necessary GL/Cg headers and implement some useful
+// utilities.
+
+#ifndef O3D_COMMAND_BUFFER_SERVICE_CROSS_GL_GL_UTILS_H_
+#define O3D_COMMAND_BUFFER_SERVICE_CROSS_GL_GL_UTILS_H_
+
+#include <build/build_config.h>
+#define GL_GLEXT_PROTOTYPES
+#if defined(OS_WIN)
+#include <GL/gl.h>
+#elif defined(OS_MACOSX)
+#include <OpenGL/OpenGL.h>
+#include <AGL/agl.h>
+#elif defined(OS_LINUX)
+#include <GL/gl.h>
+#endif // defined(PLATFORM)
+#include <Cg/cg.h>
+#include <Cg/cgGL.h>
+
+// Define this for extra GL error debugging (slower).
+// #define GL_ERROR_DEBUGGING
+#ifdef GL_ERROR_DEBUGGING
+#define CHECK_GL_ERROR() do { \
+ GLenum gl_error = glGetError(); \
+ LOG_IF(ERROR, gl_error != GL_NO_ERROR) << "GL Error :" << gl_error; \
+ } while (0)
+#else // GL_ERROR_DEBUGGING
+#define CHECK_GL_ERROR() void(0)
+#endif // GL_ERROR_DEBUGGING
+
+#endif // O3D_COMMAND_BUFFER_SERVICE_CROSS_GL_GL_UTILS_H_
diff --git a/o3d/command_buffer/service/cross/gl/sampler_gl.cc b/o3d/command_buffer/service/cross/gl/sampler_gl.cc
new file mode 100644
index 0000000..2262e6c
--- /dev/null
+++ b/o3d/command_buffer/service/cross/gl/sampler_gl.cc
@@ -0,0 +1,235 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file implements the sampler-related GAPI functions on GL.
+
+#include "command_buffer/service/cross/gl/gapi_gl.h"
+#include "command_buffer/service/cross/gl/sampler_gl.h"
+
+namespace o3d {
+namespace command_buffer {
+
+namespace {
+
+// Gets the GL enum corresponding to an addressing mode.
+GLenum GLAddressMode(sampler::AddressingMode o3d_mode) {
+ switch (o3d_mode) {
+ case sampler::WRAP:
+ return GL_REPEAT;
+ case sampler::MIRROR_REPEAT:
+ return GL_MIRRORED_REPEAT;
+ case sampler::CLAMP_TO_EDGE:
+ return GL_CLAMP_TO_EDGE;
+ case sampler::CLAMP_TO_BORDER:
+ return GL_CLAMP_TO_BORDER;
+ default:
+ DLOG(FATAL) << "Not Reached";
+ return GL_REPEAT;
+ }
+}
+
+// Gets the GL enum for the minification filter based on the command buffer min
+// and mip filtering modes.
+GLenum GLMinFilter(sampler::FilteringMode min_filter,
+ sampler::FilteringMode mip_filter) {
+ switch (min_filter) {
+ case sampler::POINT:
+ if (mip_filter == sampler::NONE)
+ return GL_NEAREST;
+ else if (mip_filter == sampler::POINT)
+ return GL_NEAREST_MIPMAP_NEAREST;
+ else if (mip_filter == sampler::LINEAR)
+ return GL_NEAREST_MIPMAP_LINEAR;
+ case sampler::LINEAR:
+ if (mip_filter == sampler::NONE)
+ return GL_LINEAR;
+ else if (mip_filter == sampler::POINT)
+ return GL_LINEAR_MIPMAP_NEAREST;
+ else if (mip_filter == sampler::LINEAR)
+ return GL_LINEAR_MIPMAP_LINEAR;
+ default:
+ DLOG(FATAL) << "Not Reached";
+ return GL_LINEAR_MIPMAP_NEAREST;
+ }
+}
+
+// Gets the GL enum for the magnification filter based on the command buffer mag
+// filtering mode.
+GLenum GLMagFilter(sampler::FilteringMode mag_filter) {
+ switch (mag_filter) {
+ case sampler::POINT:
+ return GL_NEAREST;
+ case sampler::LINEAR:
+ return GL_LINEAR;
+ default:
+ DLOG(FATAL) << "Not Reached";
+ return GL_LINEAR;
+ }
+}
+
+// Gets the GL enum representing the GL target based on the texture type.
+GLenum GLTextureTarget(texture::Type type) {
+ switch (type) {
+ case texture::TEXTURE_2D:
+ return GL_TEXTURE_2D;
+ case texture::TEXTURE_3D:
+ return GL_TEXTURE_3D;
+ case texture::TEXTURE_CUBE:
+ return GL_TEXTURE_CUBE_MAP;
+ }
+}
+
+} // anonymous namespace
+
+SamplerGL::SamplerGL()
+ : texture_id_(kInvalidResource),
+ gl_texture_(0) {
+ SetStates(sampler::CLAMP_TO_EDGE,
+ sampler::CLAMP_TO_EDGE,
+ sampler::CLAMP_TO_EDGE,
+ sampler::LINEAR,
+ sampler::LINEAR,
+ sampler::POINT,
+ 1);
+ RGBA black = {0, 0, 0, 1};
+ SetBorderColor(black);
+}
+
+bool SamplerGL::ApplyStates(GAPIGL *gapi) {
+ DCHECK(gapi);
+ TextureGL *texture = gapi->GetTexture(texture_id_);
+ if (!texture) {
+ gl_texture_ = 0;
+ return false;
+ }
+ GLenum target = GLTextureTarget(texture->type());
+ gl_texture_ = texture->gl_texture();
+ glBindTexture(target, gl_texture_);
+ glTexParameteri(target, GL_TEXTURE_WRAP_S, gl_wrap_s_);
+ glTexParameteri(target, GL_TEXTURE_WRAP_T, gl_wrap_t_);
+ glTexParameteri(target, GL_TEXTURE_WRAP_R, gl_wrap_r_);
+ glTexParameteri(target, GL_TEXTURE_MIN_FILTER, gl_min_filter_);
+ glTexParameteri(target, GL_TEXTURE_MAG_FILTER, gl_mag_filter_);
+ glTexParameteri(target, GL_TEXTURE_MAX_ANISOTROPY_EXT, gl_max_anisotropy_);
+ glTexParameterfv(target, GL_TEXTURE_BORDER_COLOR, gl_border_color_);
+ return true;
+}
+
+void SamplerGL::SetStates(sampler::AddressingMode addressing_u,
+ sampler::AddressingMode addressing_v,
+ sampler::AddressingMode addressing_w,
+ sampler::FilteringMode mag_filter,
+ sampler::FilteringMode min_filter,
+ sampler::FilteringMode mip_filter,
+ unsigned int max_anisotropy) {
+ // These are validated in GAPIDecoder.cc
+ DCHECK_NE(mag_filter, sampler::NONE);
+ DCHECK_NE(min_filter, sampler::NONE);
+ DCHECK_GT(max_anisotropy, 0);
+ gl_wrap_s_ = GLAddressMode(addressing_u);
+ gl_wrap_t_ = GLAddressMode(addressing_v);
+ gl_wrap_r_ = GLAddressMode(addressing_w);
+ gl_mag_filter_ = GLMagFilter(mag_filter);
+ gl_min_filter_ = GLMinFilter(min_filter, mip_filter);
+ gl_max_anisotropy_ = max_anisotropy;
+}
+
+void SamplerGL::SetBorderColor(const RGBA &color) {
+ gl_border_color_[0] = color.red;
+ gl_border_color_[1] = color.green;
+ gl_border_color_[2] = color.blue;
+ gl_border_color_[3] = color.alpha;
+}
+
+BufferSyncInterface::ParseError GAPIGL::CreateSampler(
+ ResourceID id) {
+ // Dirty effect, because this sampler id may be used.
+ DirtyEffect();
+ samplers_.Assign(id, new SamplerGL());
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+// Destroys the Sampler resource.
+BufferSyncInterface::ParseError GAPIGL::DestroySampler(ResourceID id) {
+ // Dirty effect, because this sampler id may be used.
+ DirtyEffect();
+ return samplers_.Destroy(id) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+BufferSyncInterface::ParseError GAPIGL::SetSamplerStates(
+ ResourceID id,
+ sampler::AddressingMode addressing_u,
+ sampler::AddressingMode addressing_v,
+ sampler::AddressingMode addressing_w,
+ sampler::FilteringMode mag_filter,
+ sampler::FilteringMode min_filter,
+ sampler::FilteringMode mip_filter,
+ unsigned int max_anisotropy) {
+ SamplerGL *sampler = samplers_.Get(id);
+ if (!sampler)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ // Dirty effect, because this sampler id may be used.
+ DirtyEffect();
+ sampler->SetStates(addressing_u, addressing_v, addressing_w,
+ mag_filter, min_filter, mip_filter, max_anisotropy);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+BufferSyncInterface::ParseError GAPIGL::SetSamplerBorderColor(
+ ResourceID id,
+ const RGBA &color) {
+ SamplerGL *sampler = samplers_.Get(id);
+ if (!sampler)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ // Dirty effect, because this sampler id may be used.
+ DirtyEffect();
+ sampler->SetBorderColor(color);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+BufferSyncInterface::ParseError GAPIGL::SetSamplerTexture(
+ ResourceID id,
+ ResourceID texture_id) {
+ SamplerGL *sampler = samplers_.Get(id);
+ if (!sampler)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ // Dirty effect, because this sampler id may be used.
+ DirtyEffect();
+ sampler->SetTexture(texture_id);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/service/cross/gl/sampler_gl.h b/o3d/command_buffer/service/cross/gl/sampler_gl.h
new file mode 100644
index 0000000..dc84b4f
--- /dev/null
+++ b/o3d/command_buffer/service/cross/gl/sampler_gl.h
@@ -0,0 +1,87 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file declares the SamplerGL class.
+
+#ifndef O3D_COMMAND_BUFFER_SERVICE_CROSS_GL_SAMPLER_GL_H_
+#define O3D_COMMAND_BUFFER_SERVICE_CROSS_GL_SAMPLER_GL_H_
+
+#include "command_buffer/common/cross/gapi_interface.h"
+#include "command_buffer/service/cross/gl/gl_utils.h"
+#include "command_buffer/service/cross/resource.h"
+
+namespace o3d {
+namespace command_buffer {
+
+class GAPIGL;
+
+// GL version of Sampler.
+class SamplerGL : public Sampler {
+ public:
+ SamplerGL();
+
+ // Applies sampler states to GL.
+ bool ApplyStates(GAPIGL *gapi);
+
+ // Sets sampler states.
+ void SetStates(sampler::AddressingMode addressing_u,
+ sampler::AddressingMode addressing_v,
+ sampler::AddressingMode addressing_w,
+ sampler::FilteringMode mag_filter,
+ sampler::FilteringMode min_filter,
+ sampler::FilteringMode mip_filter,
+ unsigned int max_anisotropy);
+
+ // Sets the border color states.
+ void SetBorderColor(const RGBA &color);
+
+ // Sets the texture.
+ void SetTexture(ResourceID texture) { texture_id_ = texture; }
+
+ GLuint gl_texture() const { return gl_texture_; }
+
+ private:
+ GLenum gl_wrap_s_;
+ GLenum gl_wrap_t_;
+ GLenum gl_wrap_r_;
+ GLenum gl_mag_filter_;
+ GLenum gl_min_filter_;
+ GLuint gl_max_anisotropy_;
+ GLfloat gl_border_color_[4];
+ GLuint gl_texture_;
+ ResourceID texture_id_;
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_SERVICE_CROSS_GL_SAMPLER_GL_H_
diff --git a/o3d/command_buffer/service/cross/gl/states_gl.cc b/o3d/command_buffer/service/cross/gl/states_gl.cc
new file mode 100644
index 0000000..4acc96c
--- /dev/null
+++ b/o3d/command_buffer/service/cross/gl/states_gl.cc
@@ -0,0 +1,342 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file implements the render state-related GAPI functions on GL.
+
+#include "command_buffer/common/cross/cmd_buffer_format.h"
+#include "command_buffer/service/cross/gl/gapi_gl.h"
+
+namespace o3d {
+namespace command_buffer {
+
+namespace {
+
+GLenum kGLPolygonModes[] = {
+ GL_POINT,
+ GL_LINE,
+ GL_FILL,
+};
+COMPILE_ASSERT(GAPIInterface::NUM_POLYGON_MODE == arraysize(kGLPolygonModes),
+ kGLPolygonModes_does_not_match_GAPIInterface_PolygonMode);
+
+GLenum kGLComparison[] = {
+ GL_NEVER,
+ GL_LESS,
+ GL_EQUAL,
+ GL_LEQUAL,
+ GL_GREATER,
+ GL_NOTEQUAL,
+ GL_GEQUAL,
+ GL_ALWAYS,
+};
+COMPILE_ASSERT(GAPIInterface::NUM_COMPARISON == arraysize(kGLComparison),
+ kGLComparison_does_not_match_GAPIInterface_Comparison);
+
+GLenum kGLBlendFunc[] = {
+ GL_ZERO,
+ GL_ONE,
+ GL_SRC_COLOR,
+ GL_ONE_MINUS_SRC_COLOR,
+ GL_SRC_ALPHA,
+ GL_ONE_MINUS_SRC_ALPHA,
+ GL_DST_ALPHA,
+ GL_ONE_MINUS_DST_ALPHA,
+ GL_DST_COLOR,
+ GL_ONE_MINUS_DST_COLOR,
+ GL_SRC_ALPHA_SATURATE,
+ GL_CONSTANT_COLOR,
+ GL_ONE_MINUS_CONSTANT_COLOR,
+};
+COMPILE_ASSERT(GAPIInterface::NUM_BLEND_FUNC == arraysize(kGLBlendFunc),
+ kGLBlendFunc_does_not_match_GAPIInterface_BlendFunc);
+
+GLenum kGLBlendEq[] = {
+ GL_FUNC_ADD,
+ GL_FUNC_SUBTRACT,
+ GL_FUNC_REVERSE_SUBTRACT,
+ GL_MIN,
+ GL_MAX,
+};
+COMPILE_ASSERT(GAPIInterface::NUM_BLEND_EQ == arraysize(kGLBlendEq),
+ kGLBlendEq_does_not_match_GAPIInterface_BlendEq);
+
+GLenum kGLStencilOp[] = {
+ GL_KEEP,
+ GL_ZERO,
+ GL_REPLACE,
+ GL_INCR,
+ GL_DECR,
+ GL_INVERT,
+ GL_INCR_WRAP,
+ GL_DECR_WRAP,
+};
+COMPILE_ASSERT(GAPIInterface::NUM_STENCIL_OP == arraysize(kGLStencilOp),
+ kGLStencilOp_does_not_match_GAPIInterface_StencilOp);
+
+// Check that the definition of the counter-clockwise func/ops match the
+// clockwise ones, just shifted by 16 bits, so that we can use
+// DecodeStencilFuncOps on both of them.
+#define CHECK_CCW_MATCHES_CW(FIELD) \
+ COMPILE_ASSERT(set_stencil_test::CW ## FIELD::kLength == \
+ set_stencil_test::CCW ## FIELD::kLength, \
+ CCW ## FIELD ## _length_does_not_match_ ## CW ## FIELD); \
+ COMPILE_ASSERT(set_stencil_test::CW ## FIELD::kShift + 16 == \
+ set_stencil_test::CCW ## FIELD::kShift, \
+ CCW ## FIELD ## _shift_does_not_match_ ## CW ## FIELD)
+
+CHECK_CCW_MATCHES_CW(Func);
+CHECK_CCW_MATCHES_CW(PassOp);
+CHECK_CCW_MATCHES_CW(FailOp);
+CHECK_CCW_MATCHES_CW(ZFailOp);
+
+#undef CHECK_CCW_MATCHES_CW
+
+// Decodes stencil test function and operations from the bitfield.
+void DecodeStencilFuncOps(Uint32 params,
+ GLenum *func,
+ GLenum *pass,
+ GLenum *fail,
+ GLenum *zfail) {
+ namespace cmd = set_stencil_test;
+ // Sanity check. The value has already been tested in
+ // GAPIDecoder::DecodeSetStencilTest in gapi_decoder.cc.
+ DCHECK_EQ(cmd::Unused1::Get(params), 0);
+ // Check that the bitmask get cannot generate values outside of the allowed
+ // range.
+ COMPILE_ASSERT(cmd::CWFunc::kMask < GAPIInterface::NUM_COMPARISON,
+ set_stencil_test_CWFunc_may_produce_invalid_values);
+ *func = kGLComparison[cmd::CWFunc::Get(params)];
+
+ COMPILE_ASSERT(cmd::CWPassOp::kMask < GAPIInterface::NUM_STENCIL_OP,
+ set_stencil_test_CWPassOp_may_produce_invalid_values);
+ *pass = kGLStencilOp[cmd::CWPassOp::Get(params)];
+
+ COMPILE_ASSERT(cmd::CWFailOp::kMask < GAPIInterface::NUM_STENCIL_OP,
+ set_stencil_test_CWFailOp_may_produce_invalid_values);
+ *fail = kGLStencilOp[cmd::CWFailOp::Get(params)];
+
+ COMPILE_ASSERT(cmd::CWZFailOp::kMask < GAPIInterface::NUM_STENCIL_OP,
+ set_stencil_test_CWZFailOp_may_produce_invalid_values);
+ *zfail = kGLStencilOp[cmd::CWZFailOp::Get(params)];
+}
+
+} // anonymous namespace
+
+void GAPIGL::SetViewport(unsigned int x,
+ unsigned int y,
+ unsigned int width,
+ unsigned int height,
+ float z_min,
+ float z_max) {
+ glViewport(x, y, width, height);
+ glDepthRange(z_min, z_max);
+ // Update the helper constant used for the D3D -> GL remapping.
+ // See effect_gl.cc for details.
+ glProgramEnvParameter4fARB(GL_VERTEX_PROGRAM_ARB, 0,
+ 1.f / width, 1.f / height, 2.f, 0.f);
+ CHECK_GL_ERROR();
+}
+
+void GAPIGL::SetScissor(bool enable,
+ unsigned int x,
+ unsigned int y,
+ unsigned int width,
+ unsigned int height) {
+ if (enable) {
+ glEnable(GL_SCISSOR_TEST);
+ glScissor(x, y, width, height);
+ } else {
+ glDisable(GL_SCISSOR_TEST);
+ }
+}
+
+void GAPIGL::SetPointLineRaster(bool line_smooth,
+ bool point_sprite,
+ float point_size) {
+ if (line_smooth) {
+ glEnable(GL_LINE_SMOOTH);
+ } else {
+ glDisable(GL_LINE_SMOOTH);
+ }
+ if (point_sprite) {
+ glEnable(GL_POINT_SPRITE);
+ // TODO: check which TC gets affected by point sprites in D3D.
+ glActiveTextureARB(GL_TEXTURE0);
+ glTexEnvi(GL_POINT_SPRITE, GL_COORD_REPLACE, GL_TRUE);
+ } else {
+ glActiveTextureARB(GL_TEXTURE0);
+ glTexEnvi(GL_POINT_SPRITE, GL_COORD_REPLACE, GL_FALSE);
+ glDisable(GL_POINT_SPRITE);
+ }
+ glPointSize(point_size);
+}
+
+void GAPIGL::SetPolygonOffset(float slope_factor, float units) {
+ glPolygonOffset(slope_factor, units);
+}
+
+void GAPIGL::SetPolygonRaster(PolygonMode fill_mode,
+ FaceCullMode cull_mode) {
+ DCHECK_LT(fill_mode, NUM_POLYGON_MODE);
+ glPolygonMode(GL_FRONT_AND_BACK, kGLPolygonModes[fill_mode]);
+ DCHECK_LT(cull_mode, NUM_FACE_CULL_MODE);
+ switch (cull_mode) {
+ case CULL_CW:
+ glEnable(GL_CULL_FACE);
+ glCullFace(GL_BACK);
+ break;
+ case CULL_CCW:
+ glEnable(GL_CULL_FACE);
+ glCullFace(GL_FRONT);
+ break;
+ default:
+ glDisable(GL_CULL_FACE);
+ break;
+ }
+}
+
+void GAPIGL::SetAlphaTest(bool enable,
+ float reference,
+ Comparison comp) {
+ DCHECK_LT(comp, NUM_COMPARISON);
+ if (enable) {
+ glEnable(GL_ALPHA_TEST);
+ glAlphaFunc(kGLComparison[comp], reference);
+ } else {
+ glDisable(GL_ALPHA_TEST);
+ }
+}
+
+void GAPIGL::SetDepthTest(bool enable,
+ bool write_enable,
+ Comparison comp) {
+ DCHECK_LT(comp, NUM_COMPARISON);
+ if (enable) {
+ glEnable(GL_DEPTH_TEST);
+ glDepthFunc(kGLComparison[comp]);
+ } else {
+ glDisable(GL_DEPTH_TEST);
+ }
+ glDepthMask(write_enable);
+}
+
+void GAPIGL::SetStencilTest(bool enable,
+ bool separate_ccw,
+ unsigned int write_mask,
+ unsigned int compare_mask,
+ unsigned int ref,
+ Uint32 func_ops) {
+ if (enable) {
+ glEnable(GL_STENCIL_TEST);
+ glStencilMask(write_mask);
+
+ GLenum func;
+ GLenum pass;
+ GLenum fail;
+ GLenum zfail;
+ DecodeStencilFuncOps(func_ops, &func, &pass, &fail, &zfail);
+ if (separate_ccw) {
+ glStencilFuncSeparate(GL_FRONT, func, ref, compare_mask);
+ glStencilOpSeparate(GL_FRONT, pass, fail, zfail);
+ // Extract upper 16 bits.
+ Uint32 ccw_func_ops = BitField<16, 16>::Get(func_ops);
+ GLenum ccw_func;
+ GLenum ccw_pass;
+ GLenum ccw_fail;
+ GLenum ccw_zfail;
+ DecodeStencilFuncOps(ccw_func_ops, &ccw_func, &ccw_pass, &ccw_fail,
+ &ccw_zfail);
+ glStencilFuncSeparate(GL_BACK, ccw_func, ref, compare_mask);
+ glStencilOpSeparate(GL_BACK, ccw_pass, ccw_fail, ccw_zfail);
+ } else {
+ glStencilFunc(func, ref, compare_mask);
+ glStencilOp(pass, fail, zfail);
+ }
+ } else {
+ glDisable(GL_STENCIL_TEST);
+ }
+}
+
+void GAPIGL::SetColorWrite(bool red,
+ bool green,
+ bool blue,
+ bool alpha,
+ bool dither) {
+ glColorMask(red, green, blue, alpha);
+ if (dither) {
+ glEnable(GL_DITHER);
+ } else {
+ glDisable(GL_DITHER);
+ }
+}
+
+void GAPIGL::SetBlending(bool enable,
+ bool separate_alpha,
+ BlendEq color_eq,
+ BlendFunc color_src_func,
+ BlendFunc color_dst_func,
+ BlendEq alpha_eq,
+ BlendFunc alpha_src_func,
+ BlendFunc alpha_dst_func) {
+ DCHECK_LT(color_eq, NUM_BLEND_EQ);
+ DCHECK_LT(color_src_func, NUM_BLEND_FUNC);
+ DCHECK_LT(color_dst_func, NUM_BLEND_FUNC);
+ DCHECK_LT(alpha_eq, NUM_BLEND_EQ);
+ DCHECK_LT(alpha_src_func, NUM_BLEND_FUNC);
+ DCHECK_LT(alpha_dst_func, NUM_BLEND_FUNC);
+ if (enable) {
+ glEnable(GL_BLEND);
+ GLenum gl_color_eq = kGLBlendEq[color_eq];
+ GLenum gl_color_src_func = kGLBlendFunc[color_src_func];
+ GLenum gl_color_dst_func = kGLBlendFunc[color_dst_func];
+ if (separate_alpha) {
+ GLenum gl_alpha_eq = kGLBlendEq[alpha_eq];
+ GLenum gl_alpha_src_func = kGLBlendFunc[alpha_src_func];
+ GLenum gl_alpha_dst_func = kGLBlendFunc[alpha_dst_func];
+ glBlendFuncSeparate(gl_color_src_func, gl_color_dst_func,
+ gl_alpha_src_func, gl_alpha_dst_func);
+ glBlendEquationSeparate(gl_color_eq, gl_alpha_eq);
+ } else {
+ glBlendFunc(gl_color_src_func, gl_color_dst_func);
+ glBlendEquation(gl_color_eq);
+ }
+ } else {
+ glDisable(GL_BLEND);
+ }
+}
+
+void GAPIGL::SetBlendingColor(const RGBA &color) {
+ glBlendColor(color.red, color.green, color.blue, color.alpha);
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/service/cross/gl/texture_gl.cc b/o3d/command_buffer/service/cross/gl/texture_gl.cc
new file mode 100644
index 0000000..9155dcc
--- /dev/null
+++ b/o3d/command_buffer/service/cross/gl/texture_gl.cc
@@ -0,0 +1,678 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file implements the texture-related GAPI functions on GL.
+
+#include "command_buffer/service/cross/gl/gapi_gl.h"
+#include "command_buffer/service/cross/gl/texture_gl.h"
+
+namespace o3d {
+namespace command_buffer {
+
+namespace {
+
+// Gets the GL internal format, format and type corresponding to a command
+// buffer texture format.
+bool GetGLFormatType(texture::Format format,
+ GLenum *internal_format,
+ GLenum *gl_format,
+ GLenum *gl_type) {
+ switch (format) {
+ case texture::XRGB8:
+ *internal_format = GL_RGB;
+ *gl_format = GL_BGRA;
+ *gl_type = GL_UNSIGNED_BYTE;
+ return true;
+ case texture::ARGB8:
+ *internal_format = GL_RGBA;
+ *gl_format = GL_BGRA;
+ *gl_type = GL_UNSIGNED_BYTE;
+ return true;
+ case texture::ABGR16F:
+ *internal_format = GL_RGBA16F_ARB;
+ *gl_format = GL_RGBA;
+ *gl_type = GL_HALF_FLOAT_ARB;
+ return true;
+ case texture::DXT1:
+ *internal_format = GL_COMPRESSED_RGBA_S3TC_DXT1_EXT;
+ *gl_format = 0;
+ *gl_type = 0;
+ return true;
+ default:
+ return false;
+ }
+}
+
+// Helper class used to prepare image data to match the layout that
+// glTexImage* and glCompressedTexImage* expect.
+class SetImageHelper {
+ public:
+ SetImageHelper()
+ : buffer_(NULL),
+ image_data_(NULL),
+ image_size_(0) {
+ }
+
+ // Initializes the helper with the input data, re-using the input buffer if
+ // possible, or copying it into a temporary one.
+ bool Initialize(const MipLevelInfo &mip_info,
+ const Volume& volume,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int src_size,
+ const void *data) {
+ TransferInfo src_transfer_info;
+ MakeTransferInfo(&src_transfer_info, mip_info, volume, row_pitch,
+ slice_pitch);
+ if (!CheckVolume(mip_info, volume) ||
+ src_size < src_transfer_info.total_size)
+ return false;
+ if (!src_transfer_info.packed) {
+ TransferInfo dst_transfer_info;
+ MakePackedTransferInfo(&dst_transfer_info, mip_info, volume);
+ buffer_.reset(new unsigned char[dst_transfer_info.total_size]);
+ TransferVolume(volume, mip_info, dst_transfer_info, buffer_.get(),
+ src_transfer_info, data);
+ image_data_ = buffer_.get();
+ image_size_ = dst_transfer_info.total_size;
+ } else {
+ image_data_ = data;
+ image_size_ = src_transfer_info.total_size;
+ }
+ return true;
+ }
+
+ // Gets the buffer that contains the data in the GL format.
+ const void *image_data() { return image_data_; }
+ // Gets the size of the buffer as GL expects it.
+ unsigned int image_size() { return image_size_; }
+
+ private:
+ scoped_array<unsigned char> buffer_;
+ const void *image_data_;
+ unsigned int image_size_;
+ DISALLOW_COPY_AND_ASSIGN(SetImageHelper);
+};
+
+// Helper class used to retrieve image data to match the layout that
+// glGetTexImage and glGetCompressedTexImage expect.
+class GetImageHelper {
+ public:
+ GetImageHelper()
+ : dst_data_(NULL),
+ buffer_(NULL),
+ image_data_(NULL) {
+ memset(&mip_info_, 0, sizeof(mip_info_));
+ memset(&volume_, 0, sizeof(volume_));
+ memset(&dst_transfer_info_, 0, sizeof(dst_transfer_info_));
+ memset(&src_transfer_info_, 0, sizeof(src_transfer_info_));
+ }
+
+ // Initialize the helper to make available a buffer to get the data from GL.
+ // It will re-use the passed in buffer if the layout matches GL, or allocate
+ // a temporary one.
+ bool Initialize(const MipLevelInfo &mip_info,
+ const Volume& volume,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int dst_size,
+ void *dst_data) {
+ mip_info_ = mip_info;
+ volume_ = volume;
+ dst_data_ = dst_data;
+ MakeTransferInfo(&dst_transfer_info_, mip_info, volume, row_pitch,
+ slice_pitch);
+ if (!CheckVolume(mip_info, volume) ||
+ dst_size < dst_transfer_info_.total_size)
+ return false;
+
+ if (!IsFullVolume(mip_info, volume) || !dst_transfer_info_.packed) {
+ // We can only retrieve the full image from GL.
+ Volume full_volume = {
+ 0, 0, 0,
+ mip_info.width, mip_info.height, mip_info.depth
+ };
+ MakePackedTransferInfo(&src_transfer_info_, mip_info, full_volume);
+ buffer_.reset(new unsigned char[src_transfer_info_.total_size]);
+ image_data_ = buffer_.get();
+ } else {
+ image_data_ = dst_data;
+ }
+ return true;
+ }
+
+ // Finalize the helper, copying the data into the final buffer if needed.
+ void Finalize() {
+ if (!buffer_.get()) return;
+ unsigned int offset =
+ volume_.x / mip_info_.block_size_x * mip_info_.block_bpp +
+ volume_.y / mip_info_.block_size_y * src_transfer_info_.row_pitch +
+ volume_.z * src_transfer_info_.slice_pitch;
+ src_transfer_info_.row_size = dst_transfer_info_.row_size;
+ TransferVolume(volume_, mip_info_, dst_transfer_info_, dst_data_,
+ src_transfer_info_, buffer_.get() + offset);
+ }
+
+ // Gets the buffer that can receive the data from GL.
+ void *image_data() { return image_data_; }
+
+ private:
+ MipLevelInfo mip_info_;
+ Volume volume_;
+ TransferInfo dst_transfer_info_;
+ TransferInfo src_transfer_info_;
+ void *dst_data_;
+ scoped_array<unsigned char> buffer_;
+ void *image_data_;
+ DISALLOW_COPY_AND_ASSIGN(GetImageHelper);
+};
+
+} // anonymous namespace
+
+TextureGL::~TextureGL() {
+ glDeleteTextures(1, &gl_texture_);
+ CHECK_GL_ERROR();
+}
+
+Texture2DGL *Texture2DGL::Create(unsigned int width,
+ unsigned int height,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags) {
+ DCHECK_GT(width, 0);
+ DCHECK_GT(height, 0);
+ DCHECK_GT(levels, 0);
+ GLenum gl_internal_format = 0;
+ GLenum gl_format = 0;
+ GLenum gl_type = 0;
+ bool r = GetGLFormatType(format, &gl_internal_format, &gl_format, &gl_type);
+ DCHECK(r); // Was checked in the decoder.
+ GLuint gl_texture = 0;
+ glGenTextures(1, &gl_texture);
+ glBindTexture(GL_TEXTURE_2D, gl_texture);
+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, levels - 1);
+ // glCompressedTexImage2D does't accept NULL as a parameter, so we need
+ // to pass in some data.
+ scoped_array<unsigned char> buffer;
+ if (!gl_format) {
+ MipLevelInfo mip_info;
+ MakeMipLevelInfo(&mip_info, format, width, height, 1, 0);
+ unsigned int size = GetMipLevelSize(mip_info);
+ buffer.reset(new unsigned char[size]);
+ }
+ unsigned int mip_width = width;
+ unsigned int mip_height = height;
+ for (unsigned int i = 0; i < levels; ++i) {
+ if (gl_format) {
+ glTexImage2D(GL_TEXTURE_2D, i, gl_internal_format, mip_width, mip_height,
+ 0, gl_format, gl_type, NULL);
+ } else {
+ MipLevelInfo mip_info;
+ MakeMipLevelInfo(&mip_info, format, width, height, 1, i);
+ unsigned int size = GetMipLevelSize(mip_info);
+ glCompressedTexImage2D(GL_TEXTURE_2D, i, gl_internal_format, mip_width,
+ mip_height, 0, size, buffer.get());
+ }
+ mip_width = std::max(1U, mip_width >> 1);
+ mip_height = std::max(1U, mip_height >> 1);
+ }
+ return new Texture2DGL(levels, format, flags, width, height, gl_texture);
+}
+
+// Sets data into a 2D texture resource.
+bool Texture2DGL::SetData(const Volume& volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ const void *data) {
+ if (level >= levels())
+ return false;
+ MipLevelInfo mip_info;
+ MakeMipLevelInfo(&mip_info, format(), width_, height_, 1, level);
+ SetImageHelper helper;
+ if (!helper.Initialize(mip_info, volume, row_pitch, slice_pitch, size, data))
+ return false;
+
+ GLenum gl_internal_format = 0;
+ GLenum gl_format = 0;
+ GLenum gl_type = 0;
+ bool r = GetGLFormatType(format(), &gl_internal_format, &gl_format, &gl_type);
+ DCHECK(r);
+ glBindTexture(GL_TEXTURE_2D, gl_texture_);
+ if (gl_format) {
+ glTexSubImage2D(GL_TEXTURE_2D, level, volume.x, volume.y, volume.width,
+ volume.height, gl_format, gl_type, helper.image_data());
+ } else {
+ glCompressedTexSubImage2D(GL_TEXTURE_2D, level, volume.x, volume.y,
+ volume.width, volume.height, gl_internal_format,
+ helper.image_size(), helper.image_data());
+ }
+ return true;
+}
+
+bool Texture2DGL::GetData(const Volume& volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ void *data) {
+ if (level >= levels())
+ return false;
+ MipLevelInfo mip_info;
+ MakeMipLevelInfo(&mip_info, format(), width_, height_, 1, level);
+ GetImageHelper helper;
+ if (!helper.Initialize(mip_info, volume, row_pitch, slice_pitch, size, data))
+ return false;
+
+ GLenum gl_internal_format = 0;
+ GLenum gl_format = 0;
+ GLenum gl_type = 0;
+ bool r = GetGLFormatType(format(), &gl_internal_format, &gl_format, &gl_type);
+ DCHECK(r);
+ glBindTexture(GL_TEXTURE_2D, gl_texture_);
+ if (gl_format) {
+ glGetTexImage(GL_TEXTURE_2D, level, gl_format, gl_type,
+ helper.image_data());
+ } else {
+ glGetCompressedTexImage(GL_TEXTURE_2D, level, helper.image_data());
+ }
+
+ helper.Finalize();
+ return true;
+}
+
+Texture3DGL *Texture3DGL::Create(unsigned int width,
+ unsigned int height,
+ unsigned int depth,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags) {
+ DCHECK_GT(width, 0);
+ DCHECK_GT(height, 0);
+ DCHECK_GT(depth, 0);
+ DCHECK_GT(levels, 0);
+ GLenum gl_internal_format = 0;
+ GLenum gl_format = 0;
+ GLenum gl_type = 0;
+ bool r = GetGLFormatType(format, &gl_internal_format, &gl_format, &gl_type);
+ DCHECK(r); // Was checked in the decoder.
+ GLuint gl_texture = 0;
+ glGenTextures(1, &gl_texture);
+ glBindTexture(GL_TEXTURE_3D, gl_texture);
+ glTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_MAX_LEVEL, levels - 1);
+ // glCompressedTexImage3D does't accept NULL as a parameter, so we need
+ // to pass in some data.
+ scoped_array<unsigned char> buffer;
+ if (!gl_format) {
+ MipLevelInfo mip_info;
+ MakeMipLevelInfo(&mip_info, format, width, height, depth, 0);
+ unsigned int size = GetMipLevelSize(mip_info);
+ buffer.reset(new unsigned char[size]);
+ }
+ unsigned int mip_width = width;
+ unsigned int mip_height = height;
+ unsigned int mip_depth = depth;
+ for (unsigned int i = 0; i < levels; ++i) {
+ if (gl_format) {
+ glTexImage3D(GL_TEXTURE_3D, i, gl_internal_format, mip_width, mip_height,
+ mip_depth, 0, gl_format, gl_type, NULL);
+ } else {
+ MipLevelInfo mip_info;
+ MakeMipLevelInfo(&mip_info, format, width, height, depth, i);
+ unsigned int size = GetMipLevelSize(mip_info);
+ glCompressedTexImage3D(GL_TEXTURE_3D, i, gl_internal_format, mip_width,
+ mip_height, mip_depth, 0, size, buffer.get());
+ }
+ mip_width = std::max(1U, mip_width >> 1);
+ mip_height = std::max(1U, mip_height >> 1);
+ mip_depth = std::max(1U, mip_depth >> 1);
+ }
+ return new Texture3DGL(levels, format, flags, width, height, depth,
+ gl_texture);
+}
+
+bool Texture3DGL::SetData(const Volume& volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ const void *data) {
+ if (level >= levels())
+ return false;
+ MipLevelInfo mip_info;
+ MakeMipLevelInfo(&mip_info, format(), width_, height_, depth_, level);
+ SetImageHelper helper;
+ if (!helper.Initialize(mip_info, volume, row_pitch, slice_pitch, size, data))
+ return false;
+
+ GLenum gl_internal_format = 0;
+ GLenum gl_format = 0;
+ GLenum gl_type = 0;
+ bool r = GetGLFormatType(format(), &gl_internal_format, &gl_format, &gl_type);
+ DCHECK(r);
+ glBindTexture(GL_TEXTURE_3D, gl_texture_);
+ if (gl_format) {
+ glTexSubImage3D(GL_TEXTURE_3D, level, volume.x, volume.y, volume.z,
+ volume.width, volume.height, volume.depth,
+ gl_format, gl_type, helper.image_data());
+ } else {
+ glCompressedTexSubImage3D(GL_TEXTURE_3D, level, volume.x, volume.y,
+ volume.z, volume.width, volume.height,
+ volume.depth, gl_internal_format,
+ helper.image_size(), helper.image_data());
+ }
+ return true;
+}
+
+bool Texture3DGL::GetData(const Volume& volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ void *data) {
+ if (level >= levels())
+ return false;
+ MipLevelInfo mip_info;
+ MakeMipLevelInfo(&mip_info, format(), width_, height_, depth_, level);
+ GetImageHelper helper;
+ if (!helper.Initialize(mip_info, volume, row_pitch, slice_pitch, size, data))
+ return false;
+
+ GLenum gl_internal_format = 0;
+ GLenum gl_format = 0;
+ GLenum gl_type = 0;
+ bool r = GetGLFormatType(format(), &gl_internal_format, &gl_format, &gl_type);
+ DCHECK(r);
+ glBindTexture(GL_TEXTURE_3D, gl_texture_);
+ if (gl_format) {
+ glGetTexImage(GL_TEXTURE_3D, level, gl_format, gl_type,
+ helper.image_data());
+ } else {
+ glGetCompressedTexImage(GL_TEXTURE_3D, level, helper.image_data());
+ }
+
+ helper.Finalize();
+ return true;
+}
+
+TextureCubeGL *TextureCubeGL::Create(unsigned int side,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags) {
+ DCHECK_GT(side, 0);
+ DCHECK_GT(levels, 0);
+ GLenum gl_internal_format = 0;
+ GLenum gl_format = 0;
+ GLenum gl_type = 0;
+ bool r = GetGLFormatType(format, &gl_internal_format, &gl_format, &gl_type);
+ DCHECK(r); // Was checked in the decoder.
+ GLuint gl_texture = 0;
+ glGenTextures(1, &gl_texture);
+ glBindTexture(GL_TEXTURE_CUBE_MAP, gl_texture);
+ glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MAX_LEVEL,
+ levels-1);
+ // glCompressedTexImage2D does't accept NULL as a parameter, so we need
+ // to pass in some data.
+ scoped_array<unsigned char> buffer;
+ if (!gl_format) {
+ MipLevelInfo mip_info;
+ MakeMipLevelInfo(&mip_info, format, side, side, 1, 0);
+ unsigned int size = GetMipLevelSize(mip_info);
+ buffer.reset(new unsigned char[size]);
+ }
+ unsigned int mip_side = side;
+ for (unsigned int i = 0; i < levels; ++i) {
+ if (gl_format) {
+ for (unsigned int face = 0; face < 6; ++face) {
+ glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + face, i,
+ gl_internal_format, mip_side, mip_side,
+ 0, gl_format, gl_type, NULL);
+ }
+ } else {
+ MipLevelInfo mip_info;
+ MakeMipLevelInfo(&mip_info, format, side, side, 1, i);
+ unsigned int size = GetMipLevelSize(mip_info);
+ for (unsigned int face = 0; face < 6; ++face) {
+ glCompressedTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + face, i,
+ gl_internal_format, mip_side, mip_side, 0, size,
+ buffer.get());
+ }
+ }
+ mip_side = std::max(1U, mip_side >> 1);
+ }
+ return new TextureCubeGL(levels, format, flags, side, gl_texture);
+}
+
+// Check that GL_TEXTURE_CUBE_MAP_POSITIVE_X + face yields the correct GLenum.
+COMPILE_ASSERT(GL_TEXTURE_CUBE_MAP_POSITIVE_X + texture::FACE_POSITIVE_X ==
+ GL_TEXTURE_CUBE_MAP_POSITIVE_X, POSITIVE_X_ENUMS_DO_NOT_MATCH);
+COMPILE_ASSERT(GL_TEXTURE_CUBE_MAP_POSITIVE_X + texture::FACE_NEGATIVE_X ==
+ GL_TEXTURE_CUBE_MAP_NEGATIVE_X, NEGATIVE_X_ENUMS_DO_NOT_MATCH);
+COMPILE_ASSERT(GL_TEXTURE_CUBE_MAP_POSITIVE_X + texture::FACE_POSITIVE_Y ==
+ GL_TEXTURE_CUBE_MAP_POSITIVE_Y, POSITIVE_Y_ENUMS_DO_NOT_MATCH);
+COMPILE_ASSERT(GL_TEXTURE_CUBE_MAP_POSITIVE_X + texture::FACE_NEGATIVE_Y ==
+ GL_TEXTURE_CUBE_MAP_NEGATIVE_Y, NEGATIVE_Y_ENUMS_DO_NOT_MATCH);
+COMPILE_ASSERT(GL_TEXTURE_CUBE_MAP_POSITIVE_X + texture::FACE_POSITIVE_Z ==
+ GL_TEXTURE_CUBE_MAP_POSITIVE_Z, POSITIVE_Z_ENUMS_DO_NOT_MATCH);
+COMPILE_ASSERT(GL_TEXTURE_CUBE_MAP_POSITIVE_X + texture::FACE_NEGATIVE_Z ==
+ GL_TEXTURE_CUBE_MAP_NEGATIVE_Z, NEGATIVE_Z_ENUMS_DO_NOT_MATCH);
+
+bool TextureCubeGL::SetData(const Volume& volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ const void *data) {
+ if (level >= levels())
+ return false;
+ MipLevelInfo mip_info;
+ MakeMipLevelInfo(&mip_info, format(), side_, side_, 1, level);
+ SetImageHelper helper;
+ if (!helper.Initialize(mip_info, volume, row_pitch, slice_pitch, size, data))
+ return false;
+
+ GLenum gl_internal_format = 0;
+ GLenum gl_format = 0;
+ GLenum gl_type = 0;
+ bool r = GetGLFormatType(format(), &gl_internal_format, &gl_format, &gl_type);
+ DCHECK(r);
+ glBindTexture(GL_TEXTURE_CUBE_MAP, gl_texture_);
+ GLenum face_target = GL_TEXTURE_CUBE_MAP_POSITIVE_X + face;
+ if (gl_format) {
+ glTexSubImage2D(face_target, level, volume.x, volume.y, volume.width,
+ volume.height, gl_format, gl_type, helper.image_data());
+ } else {
+ glCompressedTexSubImage2D(face_target, level, volume.x, volume.y,
+ volume.width, volume.height, gl_internal_format,
+ helper.image_size(), helper.image_data());
+ }
+ return true;
+}
+
+bool TextureCubeGL::GetData(const Volume& volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ void *data) {
+ if (level >= levels())
+ return false;
+ MipLevelInfo mip_info;
+ MakeMipLevelInfo(&mip_info, format(), side_, side_, 1, level);
+ GetImageHelper helper;
+ if (!helper.Initialize(mip_info, volume, row_pitch, slice_pitch, size, data))
+ return false;
+
+ GLenum gl_internal_format = 0;
+ GLenum gl_format = 0;
+ GLenum gl_type = 0;
+ bool r = GetGLFormatType(format(), &gl_internal_format, &gl_format, &gl_type);
+ DCHECK(r);
+ glBindTexture(GL_TEXTURE_CUBE_MAP, gl_texture_);
+ GLenum face_target = GL_TEXTURE_CUBE_MAP_POSITIVE_X + face;
+ if (gl_format) {
+ glGetTexImage(face_target, level, gl_format, gl_type,
+ helper.image_data());
+ } else {
+ glGetCompressedTexImage(face_target, level, helper.image_data());
+ }
+
+ helper.Finalize();
+ return true;
+}
+
+// GAPIGL functions.
+
+// Destroys a texture resource.
+BufferSyncInterface::ParseError GAPIGL::DestroyTexture(ResourceID id) {
+ // Dirty effect, because this texture id may be used.
+ DirtyEffect();
+ return textures_.Destroy(id) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+// Creates a 2D texture resource.
+BufferSyncInterface::ParseError GAPIGL::CreateTexture2D(
+ ResourceID id,
+ unsigned int width,
+ unsigned int height,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags) {
+ Texture2DGL *texture = Texture2DGL::Create(width, height, levels, format,
+ flags);
+ if (!texture) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ // Dirty effect, because this texture id may be used.
+ DirtyEffect();
+ textures_.Assign(id, texture);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+// Creates a 3D texture resource.
+BufferSyncInterface::ParseError GAPIGL::CreateTexture3D(
+ ResourceID id,
+ unsigned int width,
+ unsigned int height,
+ unsigned int depth,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags) {
+ Texture3DGL *texture = Texture3DGL::Create(width, height, depth, levels,
+ format, flags);
+ if (!texture) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ // Dirty effect, because this texture id may be used.
+ DirtyEffect();
+ textures_.Assign(id, texture);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+// Creates a cube map texture resource.
+BufferSyncInterface::ParseError GAPIGL::CreateTextureCube(
+ ResourceID id,
+ unsigned int side,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags) {
+ TextureCubeGL *texture = TextureCubeGL::Create(side, levels, format, flags);
+ if (!texture) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ // Dirty effect, because this texture id may be used.
+ DirtyEffect();
+ textures_.Assign(id, texture);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+// Copies the data into a texture resource.
+BufferSyncInterface::ParseError GAPIGL::SetTextureData(
+ ResourceID id,
+ unsigned int x,
+ unsigned int y,
+ unsigned int z,
+ unsigned int width,
+ unsigned int height,
+ unsigned int depth,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ const void *data) {
+ TextureGL *texture = textures_.Get(id);
+ if (!texture)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ Volume volume = {x, y, z, width, height, depth};
+ // Dirty effect: SetData may need to call glBindTexture which will mess up the
+ // sampler parameters.
+ DirtyEffect();
+ return texture->SetData(volume, level, face, row_pitch, slice_pitch,
+ size, data) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+// Copies the data from a texture resource.
+BufferSyncInterface::ParseError GAPIGL::GetTextureData(
+ ResourceID id,
+ unsigned int x,
+ unsigned int y,
+ unsigned int z,
+ unsigned int width,
+ unsigned int height,
+ unsigned int depth,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ void *data) {
+ TextureGL *texture = textures_.Get(id);
+ if (!texture)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ Volume volume = {x, y, z, width, height, depth};
+ // Dirty effect: GetData may need to call glBindTexture which will mess up the
+ // sampler parameters.
+ DirtyEffect();
+ return texture->GetData(volume, level, face, row_pitch, slice_pitch,
+ size, data) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/service/cross/gl/texture_gl.h b/o3d/command_buffer/service/cross/gl/texture_gl.h
new file mode 100644
index 0000000..bc6d9c2
--- /dev/null
+++ b/o3d/command_buffer/service/cross/gl/texture_gl.h
@@ -0,0 +1,223 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file declares the TextureGL, Texture2DGL, Texture3DGL and TextureCubeGL
+// classes.
+
+#ifndef O3D_COMMAND_BUFFER_SERVICE_CROSS_GL_TEXTURE_GL_H_
+#define O3D_COMMAND_BUFFER_SERVICE_CROSS_GL_TEXTURE_GL_H_
+
+#include "command_buffer/common/cross/gapi_interface.h"
+#include "command_buffer/service/cross/gl/gl_utils.h"
+#include "command_buffer/service/cross/resource.h"
+#include "command_buffer/service/cross/texture_utils.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// The base class for a GL texture resource, providing access to the base GL
+// texture that can be assigned to an effect parameter or a sampler unit.
+class TextureGL : public Texture {
+ public:
+ TextureGL(texture::Type type,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags,
+ GLuint gl_texture)
+ : Texture(type, levels, format, flags),
+ gl_texture_(gl_texture) {}
+ virtual ~TextureGL();
+
+ // Gets the GL texture object.
+ GLuint gl_texture() const { return gl_texture_; }
+
+ // Sets data into a texture resource.
+ virtual bool SetData(const Volume& volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ const void *data) = 0;
+
+ // Gets data from a texture resource.
+ virtual bool GetData(const Volume& volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ void *data) = 0;
+
+ protected:
+ const GLuint gl_texture_;
+
+ private:
+ DISALLOW_COPY_AND_ASSIGN(TextureGL);
+};
+
+// A 2D texture resource for GL.
+class Texture2DGL : public TextureGL {
+ public:
+ Texture2DGL(unsigned int levels,
+ texture::Format format,
+ unsigned int flags,
+ unsigned int width,
+ unsigned int height,
+ GLuint gl_texture)
+ : TextureGL(texture::TEXTURE_2D, levels, format, flags, gl_texture),
+ width_(width),
+ height_(height) {}
+
+ // Creates a 2D texture resource.
+ static Texture2DGL *Create(unsigned int width,
+ unsigned int height,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags);
+
+ // Sets data into a 2D texture resource.
+ virtual bool SetData(const Volume& volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ const void *data);
+
+ // Gets data from a 2D texture resource.
+ virtual bool GetData(const Volume& volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ void *data);
+
+ private:
+ unsigned int width_;
+ unsigned int height_;
+ DISALLOW_COPY_AND_ASSIGN(Texture2DGL);
+};
+
+// A 3D texture resource for GL.
+class Texture3DGL : public TextureGL {
+ public:
+ Texture3DGL(unsigned int levels,
+ texture::Format format,
+ unsigned int flags,
+ unsigned int width,
+ unsigned int height,
+ unsigned int depth,
+ GLuint gl_texture)
+ : TextureGL(texture::TEXTURE_2D, levels, format, flags, gl_texture),
+ width_(width),
+ height_(height),
+ depth_(depth) {}
+
+ // Creates a 3D texture resource.
+ static Texture3DGL *Create(unsigned int width,
+ unsigned int height,
+ unsigned int depth,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags);
+
+ // Sets data into a 3D texture resource.
+ virtual bool SetData(const Volume& volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ const void *data);
+
+ // Gets data from a 3D texture resource.
+ virtual bool GetData(const Volume& volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ void *data);
+
+ private:
+ unsigned int width_;
+ unsigned int height_;
+ unsigned int depth_;
+ DISALLOW_COPY_AND_ASSIGN(Texture3DGL);
+};
+
+// A cube map texture resource for GL.
+class TextureCubeGL : public TextureGL {
+ public:
+ TextureCubeGL(unsigned int levels,
+ texture::Format format,
+ unsigned int flags,
+ unsigned int side,
+ GLuint gl_texture)
+ : TextureGL(texture::TEXTURE_CUBE, levels, format, flags, gl_texture),
+ side_(side) {}
+
+ // Creates a cube map texture resource.
+ static TextureCubeGL *Create(unsigned int side,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags);
+
+ // Sets data into a cube map texture resource.
+ virtual bool SetData(const Volume& volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ const void *data);
+
+ // Gets data from a cube map texture resource.
+ virtual bool GetData(const Volume& volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ void *data);
+
+ private:
+ unsigned int side_;
+ DISALLOW_COPY_AND_ASSIGN(TextureCubeGL);
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_SERVICE_CROSS_GL_TEXTURE_GL_H_
diff --git a/o3d/command_buffer/service/cross/mocks.h b/o3d/command_buffer/service/cross/mocks.h
new file mode 100644
index 0000000..cb245c0
--- /dev/null
+++ b/o3d/command_buffer/service/cross/mocks.h
@@ -0,0 +1,149 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains definitions for mock objects, used for testing.
+
+// TODO: This file "manually" defines some mock objects. Using gMock
+// would be definitely preferable, unfortunately it doesn't work on Windows
+// yet.
+
+#ifndef O3D_COMMAND_BUFFER_SERVICE_CROSS_MOCKS_H__
+#define O3D_COMMAND_BUFFER_SERVICE_CROSS_MOCKS_H__
+
+#include <vector>
+#include "gmock/gmock.h"
+#include "command_buffer/service/cross/cmd_parser.h"
+#include "command_buffer/service/cross/cmd_buffer_engine.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// Mocks an AsyncAPIInterface, using GMock.
+class AsyncAPIMock : public AsyncAPIInterface {
+ public:
+ AsyncAPIMock() {
+ testing::DefaultValue<BufferSyncInterface::ParseError>::Set(
+ BufferSyncInterface::PARSE_NO_ERROR);
+ }
+
+ // Predicate that matches args passed to DoCommand, by looking at the values.
+ class IsArgs {
+ public:
+ IsArgs(unsigned int arg_count, CommandBufferEntry *args)
+ : arg_count_(arg_count),
+ args_(args) { }
+
+ bool operator() (CommandBufferEntry *args) const {
+ for (unsigned int i = 0; i < arg_count_; ++i) {
+ if (args[i].value_uint32 != args_[i].value_uint32) return false;
+ }
+ return true;
+ }
+
+ private:
+ unsigned int arg_count_;
+ CommandBufferEntry *args_;
+ };
+
+ MOCK_METHOD3(DoCommand, BufferSyncInterface::ParseError(
+ unsigned int command,
+ unsigned int arg_count,
+ CommandBufferEntry *args));
+
+ // Sets the engine, to forward SET_TOKEN commands to it.
+ void set_engine(CommandBufferEngine *engine) { engine_ = engine; }
+
+ // Forwards the SetToken commands to the engine.
+ void SetToken(unsigned int command,
+ unsigned int arg_count,
+ CommandBufferEntry *args) {
+ DCHECK(engine_);
+ DCHECK_EQ(1, command);
+ DCHECK_EQ(1, arg_count);
+ engine_->set_token(args[0].value_uint32);
+ }
+ private:
+ CommandBufferEngine *engine_;
+};
+
+class RPCProcessMock : public RPCProcessInterface {
+ public:
+ RPCProcessMock()
+ : would_have_blocked_(false),
+ message_count_(0) {
+ ON_CALL(*this, ProcessMessage()).WillByDefault(
+ testing::Invoke(this, &RPCProcessMock::DefaultProcessMessage));
+ ON_CALL(*this, HasMessage()).WillByDefault(
+ testing::Invoke(this, &RPCProcessMock::DefaultHasMessage));
+ }
+ MOCK_METHOD0(ProcessMessage, bool());
+ MOCK_METHOD0(HasMessage, bool());
+
+ void Reset() {
+ would_have_blocked_ = false;
+ message_count_ = 0;
+ }
+
+ bool DefaultProcessMessage() {
+ if (message_count_ > 0) {
+ --message_count_;
+ } else {
+ would_have_blocked_ = true;
+ }
+ return true;
+ }
+
+ bool DefaultHasMessage() {
+ return message_count_ > 0;
+ }
+
+ bool AddMessage() {
+ ++message_count_;
+ }
+
+ bool would_have_blocked() { return would_have_blocked_; }
+ void set_would_have_blocked(bool would_have_blocked) {
+ would_have_blocked_ = would_have_blocked;
+ }
+
+ unsigned int message_count() { return message_count_; }
+ void set_message_count(unsigned int count) { message_count_ = count; }
+ private:
+ bool would_have_blocked_;
+ unsigned int message_count_;
+};
+
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_SERVICE_CROSS_MOCKS_H__
diff --git a/o3d/command_buffer/service/cross/plugin.cc b/o3d/command_buffer/service/cross/plugin.cc
new file mode 100644
index 0000000..651713d
--- /dev/null
+++ b/o3d/command_buffer/service/cross/plugin.cc
@@ -0,0 +1,439 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the command renderer service (renderer) plug-in.
+// NOTE: this is only implemented on Windows currently.
+// TODO: other platforms.
+
+#include <npupp.h>
+#include <build/build_config.h>
+#ifdef OS_WIN
+#include <windows.h>
+#endif
+
+#include "command_buffer/common/cross/gapi_interface.h"
+#include "command_buffer/common/cross/rpc_imc.h"
+#include "command_buffer/service/cross/buffer_rpc.h"
+#include "command_buffer/service/cross/cmd_buffer_engine.h"
+#include "command_buffer/service/cross/gapi_decoder.h"
+#ifdef OS_WIN
+#include "command_buffer/service/win/d3d9/gapi_d3d9.h"
+#endif
+#include "native_client/service_runtime/nrd_xfer_lib/nrd_all_modules.h"
+#include "tools/idlglue/ng/static_glue/npapi/npn_api.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// The Plugin class implements the plug-in instance. It derives from NPObject
+// to be the scriptable object as well.
+class Plugin : public NPObject {
+ public:
+ // Sets the window used by the plug-in.
+ NPError SetWindow(NPWindow *window);
+
+ // Gets the NPClass representing the NPAPI entrypoints to the object.
+ static NPClass *GetNPClass() {
+ return &class_;
+ }
+
+ private:
+ explicit Plugin(NPP npp);
+ ~Plugin();
+
+ // Creates the renderer using the IMC socket. This is called from Javascript
+ // using the create() function.
+ void Create(nacl::HtpHandle socket);
+
+ // Destroys the renderer. This is called from Javascript using the destroy()
+ // function.
+ void Destroy();
+
+ // NPAPI bindings.
+ static NPObject *Allocate(NPP npp, NPClass *npclass);
+ static void Deallocate(NPObject *object);
+ static bool HasMethod(NPObject *header, NPIdentifier name);
+ static bool Invoke(NPObject *header, NPIdentifier name,
+ const NPVariant *args, uint32_t argCount,
+ NPVariant *result);
+ static bool InvokeDefault(NPObject *header, const NPVariant *args,
+ uint32_t argCount, NPVariant *result);
+ static bool HasProperty(NPObject *header, NPIdentifier name);
+ static bool GetProperty(NPObject *header, NPIdentifier name,
+ NPVariant *variant);
+ static bool SetProperty(NPObject *header, NPIdentifier name,
+ const NPVariant *variant);
+ static bool Enumerate(NPObject *header, NPIdentifier **value,
+ uint32_t *count);
+
+#ifdef OS_WIN
+ static DWORD WINAPI ThreadMain(void *param) {
+ static_cast<Plugin *>(param)->DoThread();
+ return 0;
+ }
+#endif
+ // Executes the main renderer thread.
+ void DoThread();
+
+ NPP npp_;
+ static NPClass class_;
+ NPIdentifier create_id_;
+ NPIdentifier destroy_id_;
+ NPIdentifier handle_id_;
+
+#ifdef OS_WIN
+ HWND hwnd_;
+ HANDLE thread_;
+ DWORD thread_id_;
+#endif
+
+ nacl::HtpHandle handle_;
+ scoped_ptr<GAPIInterface> gapi_;
+};
+
+
+Plugin::Plugin(NPP npp)
+ : npp_(npp),
+#ifdef OS_WIN
+ hwnd_(NULL),
+ thread_(NULL),
+ thread_id_(0),
+#endif
+ handle_(nacl::kInvalidHtpHandle) {
+ const char *names[3] = {"create", "destroy", "handle"};
+ NPIdentifier ids[3];
+ NPN_GetStringIdentifiers(names, 3, ids);
+ create_id_ = ids[0];
+ destroy_id_ = ids[1];
+ handle_id_ = ids[2];
+}
+
+Plugin::~Plugin() {
+ if (gapi_.get()) Destroy();
+}
+
+NPError Plugin::SetWindow(NPWindow *window) {
+#ifdef OS_WIN
+ HWND hWnd = window ? static_cast<HWND>(window->window) : NULL;
+ hwnd_ = hWnd;
+ return NPERR_NO_ERROR;
+#endif // OS_WIN
+}
+
+// Creates the renderer. This spawns a thread that answers requests (the D3D
+// context is created in that other thread, so that we don't need to enable
+// multi-threading on it).
+void Plugin::Create(nacl::HtpHandle handle) {
+ if (gapi_.get()) return;
+ handle_ = handle;
+#ifdef OS_WIN
+ if (!hwnd_) return;
+ GAPID3D9 *gapi_d3d = new GAPID3D9;
+ gapi_d3d->set_hwnd(hwnd_);
+ gapi_.reset(gapi_d3d);
+ // TODO: use chrome/base threads.
+ thread_ = ::CreateThread(NULL, 0, ThreadMain, this, 0, &thread_id_);
+#endif
+}
+
+// Destroys the renderer. This terminates the renderer thread, and waits until
+// it is finished.
+void Plugin::Destroy() {
+ if (!gapi_.get()) return;
+#ifdef OS_WIN
+ ::PostThreadMessage(thread_id_, WM_USER, 0, 0);
+ ::WaitForSingleObject(thread_, INFINITE);
+ ::CloseHandle(thread_);
+#endif
+ gapi_.reset(NULL);
+}
+
+// Executes the main renderer thread: answers requests, executes commands.
+void Plugin::DoThread() {
+ scoped_ptr<GAPIDecoder> decoder(new GAPIDecoder(gapi_.get()));
+ scoped_ptr<CommandBufferEngine> engine(
+ new CommandBufferEngine(decoder.get()));
+ decoder->set_engine(engine.get());
+
+ IMCMessageProcessor processor(handle_, engine->rpc_impl());
+ engine->set_process_interface(&processor);
+ IMCSender sender(handle_);
+ engine->set_client_rpc(&sender);
+
+ gapi_->Initialize();
+ while (true) {
+ bool done = false;
+#ifdef OS_WIN
+ MSG msg;
+ while (::PeekMessage(&msg, NULL, 0, 0, PM_REMOVE)) {
+ ::TranslateMessage(&msg);
+ ::DispatchMessage(&msg);
+ if (msg.message == WM_USER) {
+ done = true;
+ break;
+ }
+ }
+#endif
+ if (done) break;
+ // NOTE: DoWork will block when there is nothing to do. This can be an
+ // issue at termination if the browser tries to kill the plug-in before the
+ // NaCl module, because then this thread won't terminate, and it will block
+ // the main (browser) thread. Workaround: kill the NaCl module (kill the
+ // sel_ldr window).
+ // TODO: Fix this. It needs select()/poll() or a timeout in the
+ // IMC library, and that doesn't exist currently. We could use non-blocking,
+ // e.g. HasWork() and sleep if there is nothing to do, but that would
+ // translate into unacceptable latencies - 10ms per call.
+ if (!engine->DoWork()) break;
+ }
+ gapi_->Destroy();
+}
+
+NPClass Plugin::class_ = {
+ NP_CLASS_STRUCT_VERSION,
+ Plugin::Allocate,
+ Plugin::Deallocate,
+ 0,
+ Plugin::HasMethod,
+ Plugin::Invoke,
+ 0,
+ Plugin::HasProperty,
+ Plugin::GetProperty,
+ Plugin::SetProperty,
+ 0,
+ Plugin::Enumerate,
+};
+
+NPObject *Plugin::Allocate(NPP npp, NPClass *npclass) {
+ return new Plugin(npp);
+}
+
+void Plugin::Deallocate(NPObject *object) {
+ delete static_cast<Plugin *>(object);
+}
+
+bool Plugin::HasMethod(NPObject *header, NPIdentifier name) {
+ Plugin *plugin = static_cast<Plugin *>(header);
+ // 2 methods supported: create(handle) and destroy().
+ return (name == plugin->create_id_ ||
+ name == plugin->destroy_id_);
+}
+
+bool Plugin::Invoke(NPObject *header, NPIdentifier name,
+ const NPVariant *args, uint32_t argCount,
+ NPVariant *result) {
+ Plugin *plugin = static_cast<Plugin *>(header);
+ VOID_TO_NPVARIANT(*result);
+ if (name == plugin->create_id_ && argCount == 1 &&
+ NPVARIANT_IS_OBJECT(args[0])) {
+ // create(handle) was called.
+ //
+ // Temporary ugly hack: the NPObject is a wrapper around a HtpHandle, but
+ // to get that handle we need to get the "handle" property on it which is a
+ // string that represents the address in memory of that HtpHandle.
+ NPObject *object = NPVARIANT_TO_OBJECT(args[0]);
+
+ NPVariant handle_prop;
+ bool result = NPN_GetProperty(plugin->npp_, object, plugin->handle_id_,
+ &handle_prop);
+ if (!result || !NPVARIANT_IS_STRING(handle_prop))
+ return false;
+ String handle_string(NPVARIANT_TO_STRING(handle_prop).utf8characters,
+ NPVARIANT_TO_STRING(handle_prop).utf8length);
+ intptr_t handle_value = strtol(handle_string.c_str(), NULL, 0);
+ nacl::HtpHandle handle = reinterpret_cast<nacl::HtpHandle>(handle_value);
+ plugin->Create(handle);
+ return true;
+ } else if (name == plugin->destroy_id_ && argCount == 0) {
+ // destroy() was called.
+ plugin->Destroy();
+ return true;
+ } else {
+ return false;
+ }
+}
+
+bool Plugin::InvokeDefault(NPObject *header, const NPVariant *args,
+ uint32_t argCount, NPVariant *result) {
+ return false;
+}
+
+bool Plugin::HasProperty(NPObject *header, NPIdentifier name) {
+ return false;
+}
+
+bool Plugin::GetProperty(NPObject *header, NPIdentifier name,
+ NPVariant *variant) {
+ return false;
+}
+
+bool Plugin::SetProperty(NPObject *header, NPIdentifier name,
+ const NPVariant *variant) {
+ return false;
+}
+
+bool Plugin::Enumerate(NPObject *header, NPIdentifier **value,
+ uint32_t *count) {
+ Plugin *plugin = static_cast<Plugin *>(header);
+ *count = 2;
+ NPIdentifier *ids = static_cast<NPIdentifier *>(
+ NPN_MemAlloc(*count * sizeof(NPIdentifier)));
+ ids[0] = plugin->create_id_;
+ ids[1] = plugin->destroy_id_;
+ *value = ids;
+ return true;
+}
+
+} // namespace command_buffer
+} // namespace o3d
+
+using o3d::command_buffer::Plugin;
+
+extern "C" {
+// NPAPI entry points.
+
+char *NP_GetMIMEDescription(void) {
+ return "application/vnd.cmdbuf::CommandBuffer MIME";
+}
+
+NPError OSCALL NP_Initialize(NPNetscapeFuncs *browserFuncs) {
+ NPError retval = InitializeNPNApi(browserFuncs);
+ if (retval != NPERR_NO_ERROR) return retval;
+ return NPERR_NO_ERROR;
+}
+
+NPError OSCALL NP_GetEntryPoints(NPPluginFuncs *pluginFuncs) {
+ pluginFuncs->version = 11;
+ pluginFuncs->size = sizeof(pluginFuncs);
+ pluginFuncs->newp = NPP_New;
+ pluginFuncs->destroy = NPP_Destroy;
+ pluginFuncs->setwindow = NPP_SetWindow;
+ pluginFuncs->newstream = NPP_NewStream;
+ pluginFuncs->destroystream = NPP_DestroyStream;
+ pluginFuncs->asfile = NPP_StreamAsFile;
+ pluginFuncs->writeready = NPP_WriteReady;
+ pluginFuncs->write = NPP_Write;
+ pluginFuncs->print = NPP_Print;
+ pluginFuncs->event = NPP_HandleEvent;
+ pluginFuncs->urlnotify = NPP_URLNotify;
+ pluginFuncs->getvalue = NPP_GetValue;
+ pluginFuncs->setvalue = NPP_SetValue;
+
+ return NPERR_NO_ERROR;
+}
+
+NPError OSCALL NP_Shutdown(void) {
+ return NPERR_NO_ERROR;
+}
+
+// Creates a plugin instance.
+NPError NPP_New(NPMIMEType pluginType, NPP instance, uint16 mode, int16 argc,
+ char *argn[], char *argv[], NPSavedData *saved) {
+ NPObject *object = NPN_CreateObject(instance, Plugin::GetNPClass());
+ if (object == NULL) {
+ return NPERR_OUT_OF_MEMORY_ERROR;
+ }
+ instance->pdata = object;
+ return NPERR_NO_ERROR;
+}
+
+// Destroys a plugin instance.
+NPError NPP_Destroy(NPP instance, NPSavedData **save) {
+ Plugin *obj = static_cast<Plugin*>(instance->pdata);
+ if (obj) {
+ obj->SetWindow(NULL);
+ NPN_ReleaseObject(obj);
+ instance->pdata = NULL;
+ }
+
+ return NPERR_NO_ERROR;
+}
+
+// Sets the window used by the plugin instance.
+NPError NPP_SetWindow(NPP instance, NPWindow *window) {
+ Plugin *obj = static_cast<Plugin*>(instance->pdata);
+ obj->SetWindow(window);
+ return NPERR_NO_ERROR;
+}
+
+// Gets the scriptable object for the plug-in instance.
+NPError NPP_GetValue(NPP instance, NPPVariable variable, void *value) {
+ switch (variable) {
+ case NPPVpluginScriptableNPObject: {
+ void **v = static_cast<void **>(value);
+ Plugin *obj = static_cast<Plugin*>(instance->pdata);
+ NPN_RetainObject(obj);
+ *v = obj;
+ return NPERR_NO_ERROR;
+ }
+ default:
+ break;
+ }
+ return NPERR_GENERIC_ERROR;
+}
+
+NPError NPP_NewStream(NPP instance, NPMIMEType type, NPStream *stream,
+ NPBool seekable, uint16 *stype) {
+ return NPERR_NO_ERROR;
+}
+
+NPError NPP_DestroyStream(NPP instance, NPStream *stream, NPReason reason) {
+ return NPERR_NO_ERROR;
+}
+
+int32 NPP_WriteReady(NPP instance, NPStream *stream) {
+ return 4096;
+}
+
+int32 NPP_Write(NPP instance, NPStream *stream, int32 offset, int32 len,
+ void *buffer) {
+ return len;
+}
+
+void NPP_StreamAsFile(NPP instance, NPStream *stream, const char *fname) {
+}
+
+void NPP_Print(NPP instance, NPPrint *platformPrint) {
+}
+
+int16 NPP_HandleEvent(NPP instance, void *event) {
+ return 0;
+}
+
+void NPP_URLNotify(NPP instance, const char *url, NPReason reason,
+ void *notifyData) {
+}
+
+NPError NPP_SetValue(NPP instance, NPNVariable variable, void *value) {
+ return NPERR_GENERIC_ERROR;
+}
+} // extern "C"
diff --git a/o3d/command_buffer/service/cross/resource.cc b/o3d/command_buffer/service/cross/resource.cc
new file mode 100644
index 0000000..00a9f86
--- /dev/null
+++ b/o3d/command_buffer/service/cross/resource.cc
@@ -0,0 +1,102 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the implementation of ResourceMapBase.
+
+#include "command_buffer/service/cross/resource.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// Assigns a resource to a resource ID, by setting it at the right location
+// into the list, resizing the list if necessary, and destroying an existing
+// resource if one existed already.
+void ResourceMapBase::Assign(ResourceID id, Resource *resource) {
+ if (id >= resources_.size()) {
+ resources_.resize(id + 1, NULL);
+ } else {
+ Resource *&entry = resources_[id];
+ if (entry) {
+ delete entry;
+ entry = NULL;
+ }
+ }
+ DCHECK(resources_[id] == NULL);
+ resources_[id] = resource;
+}
+
+// Destroys a resource contained in the map, setting its entry to NULL. If
+// necessary, this will trim the list.
+bool ResourceMapBase::Destroy(ResourceID id) {
+ if (id >= resources_.size()) {
+ return false;
+ }
+ Resource *&entry = resources_[id];
+ if (entry) {
+ delete entry;
+ entry = NULL;
+
+ // Removing the last element, we can trim the list.
+ // TODO: this may not be optimal to do every time. Investigate if it
+ // becomes an issue, and add a threshold before we resize.
+ if (id == resources_.size() - 1) {
+ size_t last_valid = resources_.max_size();
+ for (unsigned int i = id; i < resources_.size(); --i) {
+ if (resources_[i]) {
+ last_valid = i;
+ break;
+ }
+ }
+ if (last_valid == resources_.max_size()) {
+ resources_.clear();
+ } else {
+ resources_.resize(last_valid + 1);
+ }
+ }
+ return true;
+ }
+ return false;
+}
+
+// Goes over all non-NULL entries in the list, destroying them, then clears the
+// list.
+void ResourceMapBase::DestroyAllResources() {
+ for (Container::iterator i = resources_.begin(); i != resources_.end(); ++i) {
+ if (*i) {
+ delete *i;
+ }
+ }
+ resources_.clear();
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/service/cross/resource.h b/o3d/command_buffer/service/cross/resource.h
new file mode 100644
index 0000000..5c6e6ed
--- /dev/null
+++ b/o3d/command_buffer/service/cross/resource.h
@@ -0,0 +1,249 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the definition for resource classes and the resource map.
+
+#ifndef O3D_COMMAND_BUFFER_SERVICE_CROSS_RESOURCE_H__
+#define O3D_COMMAND_BUFFER_SERVICE_CROSS_RESOURCE_H__
+
+#include <vector>
+#include "base/scoped_ptr.h"
+#include "core/cross/types.h"
+#include "command_buffer/common/cross/resource.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// Base class for resources, just providing a common Destroy function.
+class Resource {
+ public:
+ Resource() {}
+ virtual ~Resource() {}
+ private:
+ DISALLOW_COPY_AND_ASSIGN(Resource);
+};
+
+// VertexBuffer class, representing a vertex buffer resource.
+class VertexBuffer: public Resource {
+ public:
+ VertexBuffer(unsigned int size, unsigned int flags)
+ : size_(size),
+ flags_(flags) {}
+ virtual ~VertexBuffer() {}
+
+ // Returns the vertex buffer flags.
+ unsigned int flags() const { return flags_; }
+ // Sets the vertex buffer flags.
+ void set_flags(unsigned int flags) { flags_ = flags; }
+ // Returns the vertex buffer size.
+ unsigned int size() const { return size_; }
+ // Sets the vertex buffer size.
+ void set_size(unsigned int size) { size_ = size; }
+ protected:
+ unsigned int size_;
+ unsigned int flags_;
+ private:
+ DISALLOW_COPY_AND_ASSIGN(VertexBuffer);
+};
+
+// IndexBuffer class, representing an index buffer resource.
+class IndexBuffer: public Resource {
+ public:
+ IndexBuffer(unsigned int size, unsigned int flags)
+ : size_(size),
+ flags_(flags) {}
+ virtual ~IndexBuffer() {}
+
+ // Returns the index buffer flags.
+ unsigned int flags() const { return flags_; }
+ // Sets the index buffer flags.
+ void set_flags(unsigned int flags) { flags_ = flags; }
+ // Returns the index buffer size.
+ unsigned int size() const { return size_; }
+ // Sets the index buffer size.
+ void set_size(unsigned int size) { size_ = size; }
+ protected:
+ unsigned int size_;
+ unsigned int flags_;
+ private:
+ DISALLOW_COPY_AND_ASSIGN(IndexBuffer);
+};
+
+// VertexStruct class, representing a vertex struct resource.
+class VertexStruct: public Resource {
+ public:
+ // The representation of an input data stream.
+ struct Element {
+ ResourceID vertex_buffer;
+ unsigned int offset;
+ unsigned int stride;
+ vertex_struct::Type type;
+ vertex_struct::Semantic semantic;
+ unsigned int semantic_index;
+ };
+
+ explicit VertexStruct(unsigned int count)
+ : count_(count),
+ elements_(new Element[count]) {
+ memset(elements_.get(), 0, count * sizeof(Element)); // NOLINT
+ }
+
+ // Returns the number of inputs in this struct.
+ unsigned int count() const { return count_; }
+ // Returns an element by index.
+ Element &GetElement(unsigned int i) {
+ DCHECK_GT(count_, i);
+ return elements_[i];
+ }
+ protected:
+ unsigned int count_;
+ scoped_array<Element> elements_;
+ private:
+ DISALLOW_COPY_AND_ASSIGN(VertexStruct);
+};
+
+// Effect class, representing an effect.
+class Effect: public Resource {
+ public:
+ Effect() {}
+ private:
+ DISALLOW_COPY_AND_ASSIGN(Effect);
+};
+
+// EffectParam class, representing an effect parameter.
+class EffectParam: public Resource {
+ public:
+ explicit EffectParam(effect_param::DataType data_type)
+ : data_type_(data_type) {
+ }
+
+ // Gets the data type of this parameter.
+ effect_param::DataType data_type() const { return data_type_; }
+ private:
+ effect_param::DataType data_type_;
+ DISALLOW_COPY_AND_ASSIGN(EffectParam);
+};
+
+// Texture class, representing a texture resource.
+class Texture: public Resource {
+ public:
+ Texture(texture::Type type,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags)
+ : type_(type),
+ levels_(levels),
+ format_(format),
+ flags_(flags) {}
+ virtual ~Texture() {}
+
+ // Returns the type of the texture.
+ texture::Type type() const { return type_; }
+ // Returns the texture flags.
+ unsigned int flags() const { return flags_; }
+ // Returns the texture format.
+ texture::Format format() const { return format_; }
+ // Returns the number of mipmap levels in the texture.
+ unsigned int levels() const { return levels_; }
+ private:
+ texture::Type type_;
+ unsigned int levels_;
+ texture::Format format_;
+ unsigned int flags_;
+ DISALLOW_COPY_AND_ASSIGN(Texture);
+};
+
+// Texture class, representing a sampler resource.
+class Sampler: public Resource {
+ public:
+ Sampler() {}
+ private:
+ DISALLOW_COPY_AND_ASSIGN(Sampler);
+};
+
+// Base of ResourceMap. Contains most of the implementation of ResourceMap, to
+// avoid template bloat.
+class ResourceMapBase {
+ public:
+ ResourceMapBase() : resources_() {}
+ ~ResourceMapBase() {}
+
+ // Assigns a resource to a resource ID. Assigning a resource to an ID that
+ // already has an existing resource will destroy that existing resource. The
+ // map takes ownership of the resource.
+ void Assign(ResourceID id, Resource* resource);
+ // Destroys a resource.
+ bool Destroy(ResourceID id);
+ // Destroy all resources.
+ void DestroyAllResources();
+ // Gets a resource by ID.
+ Resource *Get(ResourceID id) {
+ return (id < resources_.size()) ? resources_[id] : NULL;
+ }
+ private:
+ typedef std::vector<Resource *> Container;
+ Container resources_;
+};
+
+// Resource Map class, allowing resource ID <-> Resource association. This is a
+// dense map, optimized for retrieval (O(1)).
+template<class T> class ResourceMap {
+ public:
+ ResourceMap() : container_() {}
+ ~ResourceMap() {}
+
+ // Assigns a resource to a resource ID. Assigning a resource to an ID that
+ // already has an existing resource will destroy that existing resource. The
+ // map takes ownership of the resource.
+ void Assign(ResourceID id, T* resource) {
+ container_.Assign(id, resource);
+ }
+ // Destroys a resource.
+ bool Destroy(ResourceID id) {
+ return container_.Destroy(id);
+ }
+ // Destroy all resources.
+ void DestroyAllResources() {
+ return container_.DestroyAllResources();
+ }
+ // Gets a resource by ID.
+ T *Get(ResourceID id) {
+ return down_cast<T*>(container_.Get(id));
+ }
+ private:
+ ResourceMapBase container_;
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_SERVICE_CROSS_RESOURCE_H__
diff --git a/o3d/command_buffer/service/cross/resource_test.cc b/o3d/command_buffer/service/cross/resource_test.cc
new file mode 100644
index 0000000..e8fedb0
--- /dev/null
+++ b/o3d/command_buffer/service/cross/resource_test.cc
@@ -0,0 +1,128 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// Tests for the ResourceMap.
+
+#include "tests/common/win/testing_common.h"
+#include "command_buffer/service/cross/resource.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// Mock resource implementation that checks for leaks.
+class ResourceMock : public Resource {
+ public:
+ ResourceMock() : Resource() {
+ ++instance_count_;
+ }
+ virtual ~ResourceMock() {
+ --instance_count_;
+ }
+
+ // Returns the instance count. The instance count is increased in the
+ // constructor and decreased in the destructor, to track leaks. The reason is
+ // that we can't mock the destructor, though we want to make sure the mock is
+ // destroyed.
+ static int instance_count() { return instance_count_; }
+ private:
+ static int instance_count_;
+ DISALLOW_COPY_AND_ASSIGN(ResourceMock);
+};
+int ResourceMock::instance_count_ = 0;
+
+// Test fixture for ResourceMap test. Creates a ResourceMap using a mock
+// Resource, and checks for ResourceMock leaks.
+class ResourceMapTest : public testing::Test {
+ protected:
+ typedef ResourceMap<ResourceMock> Map;
+ virtual void SetUp() {
+ instance_count_ = ResourceMock::instance_count();
+ map_.reset(new Map());
+ }
+ virtual void TearDown() {
+ CheckLeaks();
+ }
+
+ // Makes sure we didn't leak any ResourceMock object.
+ void CheckLeaks() {
+ EXPECT_EQ(instance_count_, ResourceMock::instance_count());
+ }
+
+ Map *map() const { return map_.get(); }
+ private:
+ int instance_count_;
+ scoped_ptr<Map> map_;
+};
+
+TEST_F(ResourceMapTest, TestMap) {
+ // check that initial mapping is empty.
+ EXPECT_EQ(NULL, map()->Get(0));
+ EXPECT_EQ(NULL, map()->Get(1));
+ EXPECT_EQ(NULL, map()->Get(392));
+
+ // create a new resource, assign it to an ID.
+ ResourceMock *resource = new ResourceMock();
+ map()->Assign(123, resource);
+ EXPECT_EQ(resource, map()->Get(123));
+
+ // Destroy the resource, making sure the object is deleted.
+ EXPECT_EQ(true, map()->Destroy(123));
+ EXPECT_EQ(false, map()->Destroy(123)); // destroying again should fail.
+ resource = NULL;
+ CheckLeaks();
+
+ // create a new resource, add it to the map, and make sure it gets deleted
+ // when we assign a new resource to that ID.
+ resource = new ResourceMock();
+ map()->Assign(1, resource);
+ resource = new ResourceMock();
+ map()->Assign(1, resource);
+ EXPECT_EQ(resource, map()->Get(1)); // check that we have the new resource.
+ EXPECT_EQ(true, map()->Destroy(1));
+ CheckLeaks();
+
+ // Adds 3 resources, then call DestroyAllResources().
+ resource = new ResourceMock();
+ map()->Assign(1, resource);
+ resource = new ResourceMock();
+ map()->Assign(2, resource);
+ resource = new ResourceMock();
+ map()->Assign(3, resource);
+ map()->DestroyAllResources();
+ EXPECT_EQ(NULL, map()->Get(1));
+ EXPECT_EQ(NULL, map()->Get(2));
+ EXPECT_EQ(NULL, map()->Get(3));
+ CheckLeaks();
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/service/cross/texture_utils.cc b/o3d/command_buffer/service/cross/texture_utils.cc
new file mode 100644
index 0000000..926f6db
--- /dev/null
+++ b/o3d/command_buffer/service/cross/texture_utils.cc
@@ -0,0 +1,104 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the implementation of some utilities for textures.
+
+#include <stdlib.h>
+#include "command_buffer/service/cross/texture_utils.h"
+
+namespace o3d {
+namespace command_buffer {
+
+void MakeTransferInfo(TransferInfo *transfer_info,
+ const MipLevelInfo &mip_level,
+ const Volume &volume,
+ unsigned int row_pitch,
+ unsigned int slice_pitch) {
+ transfer_info->row_pitch = row_pitch;
+ transfer_info->slice_pitch = slice_pitch;
+ transfer_info->row_size =
+ volume.width / mip_level.block_size_x * mip_level.block_bpp;
+ transfer_info->slice_size = transfer_info->row_size +
+ (volume.height / mip_level.block_size_y - 1) * row_pitch;
+ transfer_info->total_size = transfer_info->slice_size +
+ (volume.depth - 1) * slice_pitch;
+ transfer_info->packed = (transfer_info->row_size == row_pitch) &&
+ (volume.depth == 1 || transfer_info->slice_size == slice_pitch);
+}
+
+void MakePackedTransferInfo(TransferInfo *transfer_info,
+ const MipLevelInfo &mip_level,
+ const Volume &volume) {
+ transfer_info->row_size =
+ volume.width / mip_level.block_size_x * mip_level.block_bpp;
+ transfer_info->row_pitch = transfer_info->row_size;
+ transfer_info->slice_size =
+ volume.height / mip_level.block_size_y * transfer_info->row_pitch;
+ transfer_info->slice_pitch = transfer_info->slice_size;
+ transfer_info->total_size = volume.depth * transfer_info->slice_pitch;
+ transfer_info->packed = true;
+}
+
+// Transfers a volume of texels.
+void TransferVolume(const Volume &volume,
+ const MipLevelInfo &mip_level,
+ const TransferInfo &dst_transfer_info,
+ void *dst_data,
+ const TransferInfo &src_transfer_info,
+ const void *src_data) {
+ DCHECK_EQ(src_transfer_info.row_size, dst_transfer_info.row_size);
+ if (src_transfer_info.packed && dst_transfer_info.packed) {
+ // fast path
+ DCHECK_EQ(src_transfer_info.total_size, dst_transfer_info.total_size);
+ DCHECK_EQ(src_transfer_info.row_pitch, dst_transfer_info.row_pitch);
+ DCHECK_EQ(src_transfer_info.slice_pitch, dst_transfer_info.slice_pitch);
+ memcpy(dst_data, src_data, src_transfer_info.total_size);
+ } else {
+ const char *src = static_cast<const char *>(src_data);
+ char *dst = static_cast<char *>(dst_data);
+ for (unsigned int slice = 0; slice < volume.depth; ++slice) {
+ const char *row_src = src;
+ char *row_dst = dst;
+ for (unsigned int row = 0; row < volume.height;
+ row += mip_level.block_size_y) {
+ memcpy(row_dst, row_src, src_transfer_info.row_size);
+ row_src += src_transfer_info.row_pitch;
+ row_dst += dst_transfer_info.row_pitch;
+ }
+ src += src_transfer_info.slice_pitch;
+ dst += dst_transfer_info.slice_pitch;
+ }
+ }
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/service/cross/texture_utils.h b/o3d/command_buffer/service/cross/texture_utils.h
new file mode 100644
index 0000000..aa186b5
--- /dev/null
+++ b/o3d/command_buffer/service/cross/texture_utils.h
@@ -0,0 +1,158 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file declares some utilities for textures, in particular to deal with
+// in-memory texture data and layout.
+
+#ifndef O3D_COMMAND_BUFFER_SERVICE_CROSS_TEXTURE_UTILS_H_
+#define O3D_COMMAND_BUFFER_SERVICE_CROSS_TEXTURE_UTILS_H_
+
+#include "command_buffer/common/cross/logging.h"
+#include "command_buffer/common/cross/resource.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// Structure describing a volume of pixels.
+struct Volume {
+ unsigned int x;
+ unsigned int y;
+ unsigned int z;
+ unsigned int width;
+ unsigned int height;
+ unsigned int depth;
+};
+
+// Structure describing the dimensions and structure of a mip level.
+struct MipLevelInfo {
+ unsigned int block_bpp;
+ unsigned int block_size_x;
+ unsigned int block_size_y;
+ unsigned int width;
+ unsigned int height;
+ unsigned int depth;
+};
+
+// Structure describing a memory layout for transfers.
+struct TransferInfo {
+ unsigned int row_size; // size in bytes of a row of blocks.
+ unsigned int row_pitch; // number of bytes between 2 successive rows.
+ unsigned int slice_size; // size in bytes of a slice of data.
+ unsigned int slice_pitch; // number of bytes between 2 successive slices.
+ unsigned int total_size; // total size of the data.
+ bool packed; // indicates whether the data is tightly packed.
+};
+
+// Round a value up, so that it is divisible by the block size.
+static inline unsigned int RoundToBlockSize(unsigned int base,
+ unsigned int block) {
+ DCHECK_GT(base, 0);
+ DCHECK_GT(block, 0);
+ return block + base - 1 - (base - 1) % block;
+}
+
+// Fills a MipLevelInfo structure from the base texture dimensions.
+static inline void MakeMipLevelInfo(MipLevelInfo *mip_info,
+ texture::Format format,
+ unsigned int base_width,
+ unsigned int base_height,
+ unsigned int base_depth,
+ unsigned int level) {
+ mip_info->block_bpp = texture::GetBytesPerBlock(format);
+ mip_info->block_size_x = texture::GetBlockSizeX(format);
+ mip_info->block_size_y = texture::GetBlockSizeY(format);
+ mip_info->width = RoundToBlockSize(
+ texture::GetMipMapDimension(base_width, level), mip_info->block_size_x);
+ mip_info->height = RoundToBlockSize(
+ texture::GetMipMapDimension(base_height, level), mip_info->block_size_y);
+ mip_info->depth = texture::GetMipMapDimension(base_depth, level);
+}
+
+// Gets the size in bytes of a mip level.
+static inline unsigned int GetMipLevelSize(const MipLevelInfo &mip_info) {
+ return mip_info.block_bpp * mip_info.width / mip_info.block_size_x *
+ mip_info.height / mip_info.block_size_y * mip_info.depth;
+}
+
+// Checks that [x .. x+width] is contained in [0 .. mip_width], and that both x
+// and width are divisible by block_size, and that width is positive.
+static inline bool CheckDimension(unsigned int x,
+ unsigned int width,
+ unsigned int mip_width,
+ unsigned int block_size) {
+ return x < mip_width && x+width <= mip_width && x % block_size == 0 &&
+ width % block_size == 0 && width > 0;
+}
+
+// Checks that given volume fits into a mip level.
+static inline bool CheckVolume(const MipLevelInfo &mip_info,
+ const Volume &volume) {
+ return CheckDimension(volume.x, volume.width, mip_info.width,
+ mip_info.block_size_x) &&
+ CheckDimension(volume.y, volume.height, mip_info.height,
+ mip_info.block_size_y) &&
+ CheckDimension(volume.z, volume.depth, mip_info.depth, 1);
+}
+
+// Checks whether a volume fully maps a mip level.
+static inline bool IsFullVolume(const MipLevelInfo &mip_info,
+ const Volume &volume) {
+ return (volume.x == 0) && (volume.y == 0) && (volume.z == 0) &&
+ (volume.width == mip_info.width) &&
+ (volume.height == mip_info.height) &&
+ (volume.depth == mip_info.depth);
+}
+
+// Makes a transfer info from a mip level, a volume and row/slice pitches.
+void MakeTransferInfo(TransferInfo *transfer_info,
+ const MipLevelInfo &mip_level,
+ const Volume &volume,
+ unsigned int row_pitch,
+ unsigned int slice_pitch);
+
+// Makes a transfer info from a mip level and a volume, considering packed data.
+void MakePackedTransferInfo(TransferInfo *transfer_info,
+ const MipLevelInfo &mip_level,
+ const Volume &volume);
+
+// Transfers a volume of texels.
+void TransferVolume(const Volume &volume,
+ const MipLevelInfo &mip_level,
+ const TransferInfo &dst_transfer_info,
+ void *dst_data,
+ const TransferInfo &src_transfer_info,
+ const void *src_data);
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_SERVICE_CROSS_TEXTURE_UTILS_H_
diff --git a/o3d/command_buffer/service/linux/big_test_main.cc b/o3d/command_buffer/service/linux/big_test_main.cc
new file mode 100644
index 0000000..21ffecd
--- /dev/null
+++ b/o3d/command_buffer/service/linux/big_test_main.cc
@@ -0,0 +1,125 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the entry to the big test program, for linux.
+
+#include "command_buffer/service/cross/big_test_helpers.h"
+#include "command_buffer/service/cross/gl/gapi_gl.h"
+#include "command_buffer/service/linux/x_utils.h"
+
+namespace o3d {
+namespace command_buffer {
+
+String *g_program_path = NULL;
+GAPIInterface *g_gapi = NULL;
+
+bool ProcessSystemMessages() {
+ return true;
+}
+
+} // namespace command_buffer
+} // namespace o3d
+
+using o3d::String;
+using o3d::command_buffer::g_program_path;
+using o3d::command_buffer::g_gapi;
+using o3d::command_buffer::GAPIGL;
+using o3d::command_buffer::XWindowWrapper;
+
+
+// Creates a GL-compatible window of specified dimensions.
+Window CreateWindow(Display *display, unsigned int width, unsigned int height) {
+ int attribs[] = {
+ GLX_RGBA,
+ GLX_DOUBLEBUFFER,
+ GLX_RED_SIZE, 1,
+ GLX_GREEN_SIZE, 1,
+ GLX_BLUE_SIZE, 1,
+ None
+ };
+ XVisualInfo *visualInfo = glXChooseVisual(display,
+ DefaultScreen(display),
+ attribs);
+ Window root_window = RootWindow(display, visualInfo->screen);
+ Colormap colorMap = XCreateColormap(display, root_window, visualInfo->visual,
+ AllocNone);
+
+ XSetWindowAttributes windowAttributes;
+ windowAttributes.colormap = colorMap;
+ windowAttributes.border_pixel = 0;
+ windowAttributes.event_mask = StructureNotifyMask;
+ Window window = XCreateWindow(display, root_window,
+ 0, 0, width, height, 0, visualInfo->depth,
+ InputOutput, visualInfo->visual,
+ CWBorderPixel|CWColormap|CWEventMask,
+ &windowAttributes);
+ if (!window) return 0;
+ XMapWindow(display, window);
+ XSync(display, True);
+ return window;
+}
+
+// Creates a window, initializes the GAPI instance.
+int main(int argc, char *argv[]) {
+ String program_path = argv[0];
+
+ // Remove all characters starting with last '/'.
+ size_t backslash_pos = program_path.rfind('/');
+ if (backslash_pos != String::npos) {
+ program_path.erase(backslash_pos);
+ }
+ g_program_path = &program_path;
+
+ GAPIGL gl_gapi;
+ g_gapi = &gl_gapi;
+
+ Display *display = XOpenDisplay(0);
+ if (!display) {
+ LOG(FATAL) << "Could not open the display.";
+ return 1;
+ }
+
+ Window window = CreateWindow(display, 300, 300);
+ if (!window) {
+ LOG(FATAL) << "Could not create a window.";
+ return 1;
+ }
+
+ XWindowWrapper wrapper(display, window);
+ gl_gapi.set_window_wrapper(&wrapper);
+
+ int ret = big_test_main(argc, argv);
+
+ g_gapi = NULL;
+ g_program_path = NULL;
+ return ret;
+}
diff --git a/o3d/command_buffer/service/linux/x_utils.cc b/o3d/command_buffer/service/linux/x_utils.cc
new file mode 100644
index 0000000..3ee0e7d
--- /dev/null
+++ b/o3d/command_buffer/service/linux/x_utils.cc
@@ -0,0 +1,93 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This class implements the XWindowWrapper class.
+
+#include "command_buffer/common/cross/logging.h"
+#include "command_buffer/service/linux/x_utils.h"
+
+namespace o3d {
+namespace command_buffer {
+
+bool XWindowWrapper::Initialize() {
+ XWindowAttributes attributes;
+ XGetWindowAttributes(display_, window_, &attributes);
+ XVisualInfo visual_info_template;
+ visual_info_template.visualid = XVisualIDFromVisual(attributes.visual);
+ int visual_info_count = 0;
+ XVisualInfo *visual_info_list = XGetVisualInfo(display_, VisualIDMask,
+ &visual_info_template,
+ &visual_info_count);
+ DCHECK(visual_info_list);
+ DCHECK_GT(visual_info_count, 0);
+ context_ = 0;
+ for (int i = 0; i < visual_info_count; ++i) {
+ context_ = glXCreateContext(display_, visual_info_list + i, 0,
+ True);
+ if (context_) break;
+ }
+ XFree(visual_info_list);
+ if (!context_) {
+ DLOG(ERROR) << "Couldn't create GL context.";
+ return false;
+ }
+ return true;
+}
+
+bool XWindowWrapper::MakeCurrent() {
+ if (glXMakeCurrent(display_, window_, context_) != True) {
+ glXDestroyContext(display_, context_);
+ context_ = 0;
+ DLOG(ERROR) << "Couldn't make context current.";
+ return false;
+ }
+ return true;
+}
+
+void XWindowWrapper::Destroy() {
+ Bool result = glXMakeCurrent(display_, 0, 0);
+ // glXMakeCurrent isn't supposed to fail when unsetting the context, unless
+ // we have pending draws on an invalid window - which shouldn't be the case
+ // here.
+ DCHECK(result);
+ if (context_) {
+ glXDestroyContext(display_, context_);
+ context_ = 0;
+ }
+}
+
+void XWindowWrapper::SwapBuffers() {
+ glXSwapBuffers(display_, window_);
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/service/linux/x_utils.h b/o3d/command_buffer/service/linux/x_utils.h
new file mode 100644
index 0000000..4cf618e
--- /dev/null
+++ b/o3d/command_buffer/service/linux/x_utils.h
@@ -0,0 +1,78 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file declares the XWindowWrapper class.
+
+#ifndef O3D_COMMAND_BUFFER_SERVICE_LINUX_X_UTILS_H_
+#define O3D_COMMAND_BUFFER_SERVICE_LINUX_X_UTILS_H_
+
+#include <GL/glx.h>
+#include "base/basictypes.h"
+#include "command_buffer/common/cross/logging.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// This class is a wrapper around an X Window and associated GL context. It is
+// useful to isolate intrusive X headers, since it can be forward declared
+// (Window and GLXContext can't).
+class XWindowWrapper {
+ public:
+ XWindowWrapper(Display *display, Window window)
+ : display_(display),
+ window_(window) {
+ DCHECK(display_);
+ DCHECK(window_);
+ }
+ // Initializes the GL context.
+ bool Initialize();
+
+ // Destroys the GL context.
+ void Destroy();
+
+ // Makes the GL context current on the current thread.
+ bool MakeCurrent();
+
+ // Swaps front and back buffers.
+ void SwapBuffers();
+
+ private:
+ Display *display_;
+ Window window_;
+ GLXContext context_;
+ DISALLOW_COPY_AND_ASSIGN(XWindowWrapper);
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_SERVICE_LINUX_X_UTILS_H_
diff --git a/o3d/command_buffer/service/win/big_test_main.cc b/o3d/command_buffer/service/win/big_test_main.cc
new file mode 100644
index 0000000..8a21b72
--- /dev/null
+++ b/o3d/command_buffer/service/win/big_test_main.cc
@@ -0,0 +1,163 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+#include <windows.h>
+#include <Shellapi.h>
+#include "command_buffer/service/cross/big_test_helpers.h"
+#include "command_buffer/service/win/d3d9/gapi_d3d9.h"
+#include "core/cross/types.h"
+
+namespace o3d {
+namespace command_buffer {
+
+String *g_program_path = NULL;
+GAPIInterface *g_gapi = NULL;
+
+class Thread {
+ public:
+ Thread(ThreadFunc func, void *data)
+ : handle_(NULL),
+ func_(func),
+ data_(data) {
+ }
+
+ ~Thread() {}
+
+ HANDLE handle() const { return handle_; }
+ void set_handle(HANDLE handle) { handle_ = handle; }
+
+ void * data() const { return data_; }
+ ThreadFunc func() const { return func_; }
+
+ private:
+ HANDLE handle_;
+ ThreadFunc func_;
+ void * data_;
+};
+
+DWORD WINAPI ThreadMain(LPVOID lpParam) {
+ Thread *thread = static_cast<Thread *>(lpParam);
+ ThreadFunc func = thread->func();
+ func(thread->data());
+ return 0;
+}
+
+Thread *CreateThread(ThreadFunc func, void* param) {
+ Thread *thread = new Thread(func, param);
+ HANDLE handle = ::CreateThread(NULL, 0, ThreadMain, thread, 0, NULL);
+ return thread;
+}
+
+void JoinThread(Thread *thread) {
+ ::WaitForSingleObject(thread->handle(), INFINITE);
+ ::CloseHandle(thread->handle());
+ delete thread;
+}
+
+bool ProcessSystemMessages() {
+ MSG msg;
+ while (PeekMessage(&msg, NULL, 0, 0, PM_REMOVE)) {
+ if (msg.message == WM_QUIT) {
+ return false;
+ }
+ TranslateMessage(&msg);
+ DispatchMessage(&msg);
+ }
+ return true;
+}
+
+} // namespace command_buffer
+} // namespace o3d
+
+using o3d::String;
+using o3d::command_buffer::g_program_path;
+using o3d::command_buffer::g_gapi;
+using o3d::command_buffer::GAPID3D9;
+
+LRESULT CALLBACK WindowProc(HWND hWnd,
+ UINT msg,
+ WPARAM wParam,
+ LPARAM lParam) {
+ switch (msg) {
+ case WM_CLOSE:
+ PostQuitMessage(0);
+ break;
+ case WM_DESTROY:
+ PostQuitMessage(0);
+ break;
+ default:
+ return DefWindowProc(hWnd, msg, wParam, lParam);
+ }
+ return 0;
+}
+
+int main(int argc, char *argv[]) {
+ WNDCLASSEX wc = {
+ sizeof(WNDCLASSEX), CS_CLASSDC, WindowProc, 0L, 0L, GetModuleHandle(NULL),
+ NULL, NULL, NULL, NULL, L"O3D big test", NULL
+ };
+ RegisterClassEx(&wc);
+
+ // Create the application's window.
+ HWND hWnd = CreateWindow(L"O3D big test", L"O3D Big Test",
+ WS_OVERLAPPEDWINDOW | WS_VISIBLE, 100, 100, 300,
+ 300, GetDesktopWindow(), NULL, wc.hInstance, NULL);
+ UpdateWindow(hWnd);
+
+ GAPID3D9 d3d9_gapi;
+ d3d9_gapi.set_hwnd(hWnd);
+ g_gapi = &d3d9_gapi;
+
+ wchar_t program_filename[512];
+ GetModuleFileName(NULL, program_filename, sizeof(program_filename));
+ program_filename[511] = 0;
+
+ String program_path = WideToUTF8(std::wstring(program_filename));
+
+ // Remove all characters starting with last '\'.
+ size_t backslash_pos = program_path.rfind('\\');
+ if (backslash_pos != String::npos) {
+ program_path.erase(backslash_pos);
+ }
+ g_program_path = &program_path;
+
+ // Convert the command line arguments to an argc, argv format.
+ LPWSTR *arg_list = NULL;
+ int arg_count;
+ arg_list = CommandLineToArgvW(GetCommandLineW(), &arg_count);
+
+ int ret = big_test_main(arg_count, arg_list);
+
+ g_gapi = NULL;
+ g_program_path = NULL;
+ return ret;
+}
diff --git a/o3d/command_buffer/service/win/d3d9/d3d9_utils.h b/o3d/command_buffer/service/win/d3d9/d3d9_utils.h
new file mode 100644
index 0000000..647d984
--- /dev/null
+++ b/o3d/command_buffer/service/win/d3d9/d3d9_utils.h
@@ -0,0 +1,102 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file defines a few utilities for Direct3D.
+
+#ifndef O3D_COMMAND_BUFFER_SERVICE_WIN_D3D9_D3D9_UTILS_H__
+#define O3D_COMMAND_BUFFER_SERVICE_WIN_D3D9_D3D9_UTILS_H__
+
+#ifndef NOMINMAX
+// windows.h defines min() and max() as macros, conflicting with std::min and
+// std::max unless NOMINMAX is defined.
+#define NOMINMAX
+#endif
+#include <windows.h>
+#include <d3d9.h>
+#include <d3dx9.h>
+#include <dxerr.h>
+#include <algorithm>
+#include "command_buffer/common/cross/gapi_interface.h"
+
+#if defined (_DEBUG)
+
+#ifndef HR
+#define HR(x) { \
+ HRESULT hr = x; \
+ if (FAILED(hr)) { \
+ LOG(ERROR) << "DirectX error at " << __FILE__ << ":" << __LINE__ \
+ << " when calling " << #x << ": " << DXGetErrorStringA(hr); \
+ } \
+ }
+#endif
+
+#else // _DEBUG
+
+#ifndef HR
+#define HR(x) x;
+#endif
+
+#endif // _DEBUG
+
+namespace o3d {
+namespace command_buffer {
+
+union FloatAndDWORD {
+ float float_value;
+ DWORD dword_value;
+};
+
+// Bit casts a float into a DWORD. That's what D3D expects for some values.
+inline DWORD FloatAsDWORD(float value) {
+ volatile FloatAndDWORD float_and_dword;
+ float_and_dword.float_value = value;
+ return float_and_dword.dword_value;
+}
+
+// Clamps a float to [0 .. 1] and maps it to [0 .. 255]
+inline unsigned int FloatToClampedByte(float value) {
+ value = std::min(1.f, std::max(0.f, value));
+ return static_cast<unsigned int>(value * 255);
+}
+
+// Converts a RGBA color into a D3DCOLOR
+inline D3DCOLOR RGBAToD3DCOLOR(const RGBA &color) {
+ return D3DCOLOR_RGBA(FloatToClampedByte(color.red),
+ FloatToClampedByte(color.green),
+ FloatToClampedByte(color.blue),
+ FloatToClampedByte(color.alpha));
+}
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_SERVICE_WIN_D3D9_D3D9_UTILS_H__
diff --git a/o3d/command_buffer/service/win/d3d9/effect_d3d9.cc b/o3d/command_buffer/service/win/d3d9/effect_d3d9.cc
new file mode 100644
index 0000000..a472e79
--- /dev/null
+++ b/o3d/command_buffer/service/win/d3d9/effect_d3d9.cc
@@ -0,0 +1,569 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the implementation of the D3D9 versions of the
+// Effect resource.
+// This file also contains the related GAPID3D9 function implementations.
+
+#include <algorithm>
+#include "command_buffer/service/win/d3d9/d3d9_utils.h"
+#include "command_buffer/service/win/d3d9/geometry_d3d9.h"
+#include "command_buffer/service/win/d3d9/gapi_d3d9.h"
+#include "command_buffer/service/win/d3d9/effect_d3d9.h"
+#include "command_buffer/service/win/d3d9/sampler_d3d9.h"
+#include "command_buffer/service/cross/effect_utils.h"
+
+// TODO: remove link-dependency on D3DX.
+
+namespace o3d {
+namespace command_buffer {
+
+// Logs the D3D effect error, from either the buffer, or GetLastError().
+static void LogFXError(LPD3DXBUFFER error_buffer) {
+ if (error_buffer) {
+ LPVOID compile_errors = error_buffer->GetBufferPointer();
+ LOG(ERROR) << "Failed to compile effect: "
+ << static_cast<char *>(compile_errors);
+ } else {
+ HLOCAL hLocal = NULL;
+ FormatMessage(FORMAT_MESSAGE_FROM_SYSTEM|FORMAT_MESSAGE_ALLOCATE_BUFFER,
+ NULL,
+ GetLastError(),
+ 0,
+ reinterpret_cast<wchar_t*>(&hLocal),
+ 0,
+ NULL);
+ wchar_t* msg = reinterpret_cast<wchar_t*>(LocalLock(hLocal));
+ LOG(ERROR) << "Failed to compile effect: " << msg;
+ LocalFree(hLocal);
+ }
+}
+
+EffectD3D9::EffectD3D9(ID3DXEffect *d3d_effect,
+ ID3DXConstantTable *fs_constant_table)
+ : d3d_effect_(d3d_effect),
+ fs_constant_table_(fs_constant_table),
+ sync_parameters_(false) {
+ for (unsigned int i = 0; i < kMaxSamplerUnits; ++i) {
+ samplers_[i] = kInvalidResource;
+ }
+}
+// Releases the D3D effect.
+EffectD3D9::~EffectD3D9() {
+ for (ParamList::iterator it = params_.begin(); it != params_.end(); ++it) {
+ (*it)->ResetEffect();
+ }
+ DCHECK(d3d_effect_);
+ d3d_effect_->Release();
+ DCHECK(fs_constant_table_);
+ fs_constant_table_->Release();
+}
+
+// Compiles the effect, and checks that the effect conforms to what we expect
+// (no extra technique or pass in the effect code, since one is implicitly added
+// using the program entry points) and that it validates. If successful, wrap
+// the D3D effect into a new EffectD3D9.
+EffectD3D9 *EffectD3D9::Create(GAPID3D9 *gapi,
+ const String& effect_code,
+ const String& vertex_program_entry,
+ const String& fragment_program_entry) {
+ String prepared_effect = effect_code +
+ "technique Shaders { "
+ " pass p0 { "
+ " VertexShader = compile vs_2_0 " + vertex_program_entry + "();"
+ " PixelShader = compile ps_2_0 " + fragment_program_entry + "();"
+ " }"
+ "};";
+ ID3DXEffect *d3d_effect = NULL;
+ LPD3DXBUFFER error_buffer;
+ IDirect3DDevice9 *device = gapi->d3d_device();
+ if (D3DXCreateEffect(device,
+ prepared_effect.c_str(),
+ prepared_effect.size(),
+ NULL,
+ NULL,
+ 0,
+ NULL,
+ &d3d_effect,
+ &error_buffer) != D3D_OK) {
+ LogFXError(error_buffer);
+ return NULL;
+ }
+ // check that .
+ D3DXEFFECT_DESC effect_desc;
+ HR(d3d_effect->GetDesc(&effect_desc));
+ if (effect_desc.Techniques != 1) {
+ LOG(ERROR) << "Only 1 technique is allowed in an effect.";
+ d3d_effect->Release();
+ return NULL;
+ }
+ D3DXHANDLE technique = d3d_effect->GetTechnique(0);
+ DCHECK(technique);
+ if (d3d_effect->ValidateTechnique(technique) != D3D_OK) {
+ LOG(ERROR) << "Technique doesn't validate.";
+ d3d_effect->Release();
+ return NULL;
+ }
+ D3DXTECHNIQUE_DESC technique_desc;
+ HR(d3d_effect->GetTechniqueDesc(technique, &technique_desc));
+ if (technique_desc.Passes != 1) {
+ LOG(ERROR) << "Only 1 pass is allowed in an effect.";
+ d3d_effect->Release();
+ return NULL;
+ }
+ d3d_effect->SetTechnique(technique);
+ D3DXHANDLE pass = d3d_effect->GetPass(technique, 0);
+ D3DXPASS_DESC pass_desc;
+ HR(d3d_effect->GetPassDesc(pass, &pass_desc));
+ ID3DXConstantTable *table = NULL;
+ HR(D3DXGetShaderConstantTable(pass_desc.pPixelShaderFunction,
+ &table));
+ if (!table) {
+ LOG(ERROR) << "Could not get the constant table.";
+ d3d_effect->Release();
+ return NULL;
+ }
+ return new EffectD3D9(d3d_effect, table);
+}
+
+// Begins rendering with the effect, setting all the appropriate states.
+bool EffectD3D9::Begin(GAPID3D9 *gapi) {
+ UINT numpasses;
+ HR(d3d_effect_->Begin(&numpasses, 0));
+ HR(d3d_effect_->BeginPass(0));
+ sync_parameters_ = false;
+ return SetSamplers(gapi);
+}
+
+// Terminates rendering with the effect, resetting all the appropriate states.
+void EffectD3D9::End(GAPID3D9 *gapi) {
+ HR(d3d_effect_->EndPass());
+ HR(d3d_effect_->End());
+}
+
+// Gets the parameter count from the D3D effect description.
+unsigned int EffectD3D9::GetParamCount() {
+ D3DXEFFECT_DESC effect_desc;
+ HR(d3d_effect_->GetDesc(&effect_desc));
+ return effect_desc.Parameters;
+}
+
+// Retrieves the matching DataType from a D3D parameter description.
+static effect_param::DataType GetDataTypeFromD3D(
+ const D3DXPARAMETER_DESC &desc) {
+ switch (desc.Type) {
+ case D3DXPT_FLOAT:
+ switch (desc.Class) {
+ case D3DXPC_SCALAR:
+ return effect_param::FLOAT1;
+ case D3DXPC_VECTOR:
+ switch (desc.Columns) {
+ case 2:
+ return effect_param::FLOAT2;
+ case 3:
+ return effect_param::FLOAT3;
+ case 4:
+ return effect_param::FLOAT4;
+ default:
+ return effect_param::UNKNOWN;
+ }
+ case D3DXPC_MATRIX_ROWS:
+ case D3DXPC_MATRIX_COLUMNS:
+ if (desc.Columns == 4 && desc.Rows == 4) {
+ return effect_param::MATRIX4;
+ } else {
+ return effect_param::UNKNOWN;
+ }
+ default:
+ return effect_param::UNKNOWN;
+ }
+ case D3DXPT_INT:
+ if (desc.Class == D3DXPC_SCALAR) {
+ return effect_param::INT;
+ } else {
+ return effect_param::UNKNOWN;
+ }
+ case D3DXPT_BOOL:
+ if (desc.Class == D3DXPC_SCALAR) {
+ return effect_param::BOOL;
+ } else {
+ return effect_param::UNKNOWN;
+ }
+ case D3DXPT_SAMPLER:
+ case D3DXPT_SAMPLER2D:
+ case D3DXPT_SAMPLER3D:
+ case D3DXPT_SAMPLERCUBE:
+ if (desc.Class == D3DXPC_OBJECT) {
+ return effect_param::SAMPLER;
+ } else {
+ return effect_param::UNKNOWN;
+ }
+ default:
+ return effect_param::UNKNOWN;
+ }
+}
+
+// Gets a handle to the selected parameter, and wraps it into an
+// EffectParamD3D9 if successful.
+EffectParamD3D9 *EffectD3D9::CreateParam(unsigned int index) {
+ D3DXHANDLE handle = d3d_effect_->GetParameter(NULL, index);
+ if (!handle) return NULL;
+ return EffectParamD3D9::Create(this, handle);
+}
+
+// Gets a handle to the selected parameter, and wraps it into an
+// EffectParamD3D9 if successful.
+EffectParamD3D9 *EffectD3D9::CreateParamByName(const char *name) {
+ D3DXHANDLE handle = d3d_effect_->GetParameterByName(NULL, name);
+ if (!handle) return NULL;
+ return EffectParamD3D9::Create(this, handle);
+}
+
+bool EffectD3D9::CommitParameters(GAPID3D9 *gapi) {
+ if (sync_parameters_) {
+ sync_parameters_ = false;
+ d3d_effect_->CommitChanges();
+ return SetSamplers(gapi);
+ } else {
+ return true;
+ }
+}
+
+bool EffectD3D9::SetSamplers(GAPID3D9 *gapi) {
+ IDirect3DDevice9 *d3d_device = gapi->d3d_device();
+ bool result = true;
+ for (unsigned int i = 0; i < kMaxSamplerUnits; ++i) {
+ SamplerD3D9 *sampler = gapi->GetSampler(samplers_[i]);
+ if (sampler) {
+ result &= sampler->ApplyStates(gapi, i);
+ } else {
+ HR(d3d_device->SetTexture(i, NULL));
+ }
+ }
+ return result;
+}
+
+void EffectD3D9::LinkParam(EffectParamD3D9 *param) {
+ params_.push_back(param);
+}
+
+void EffectD3D9::UnlinkParam(EffectParamD3D9 *param) {
+ std::remove(params_.begin(), params_.end(), param);
+}
+
+EffectParamD3D9::EffectParamD3D9(effect_param::DataType data_type,
+ EffectD3D9 *effect,
+ D3DXHANDLE handle)
+ : EffectParam(data_type),
+ effect_(effect),
+ handle_(handle),
+ sampler_units_(NULL),
+ sampler_unit_count_(0) {
+ DCHECK(effect_);
+ effect_->LinkParam(this);
+}
+
+EffectParamD3D9::~EffectParamD3D9() {
+ if (effect_) effect_->UnlinkParam(this);
+}
+
+EffectParamD3D9 *EffectParamD3D9::Create(EffectD3D9 *effect,
+ D3DXHANDLE handle) {
+ DCHECK(effect);
+ D3DXPARAMETER_DESC desc;
+ HR(effect->d3d_effect_->GetParameterDesc(handle, &desc));
+ effect_param::DataType data_type = GetDataTypeFromD3D(desc);
+ EffectParamD3D9 *param = new EffectParamD3D9(data_type, effect, handle);
+ if (data_type == effect_param::SAMPLER) {
+ ID3DXConstantTable *table = effect->fs_constant_table_;
+ DCHECK(table);
+ D3DXHANDLE sampler_handle = table->GetConstantByName(NULL, desc.Name);
+ if (sampler_handle) {
+ D3DXCONSTANT_DESC desc_array[kMaxSamplerUnits];
+ unsigned int num_desc = kMaxSamplerUnits;
+ table->GetConstantDesc(sampler_handle, desc_array, &num_desc);
+ // We have no good way of querying how many descriptions would really be
+ // returned as we're capping the number to kMaxSamplerUnits (which should
+ // be more than sufficient). If however we do end up with the max number
+ // there's a chance that there were actually more so let's log it.
+ if (num_desc == kMaxSamplerUnits) {
+ DLOG(WARNING) << "Number of constant descriptions might have exceeded "
+ << "the maximum of " << kMaxSamplerUnits;
+ }
+ param->sampler_unit_count_ = 0;
+ if (num_desc > 0) {
+ param->sampler_units_.reset(new unsigned int[num_desc]);
+ for (unsigned int desc_index = 0; desc_index < num_desc; desc_index++) {
+ D3DXCONSTANT_DESC constant_desc = desc_array[desc_index];
+ if (constant_desc.Class == D3DXPC_OBJECT &&
+ (constant_desc.Type == D3DXPT_SAMPLER ||
+ constant_desc.Type == D3DXPT_SAMPLER2D ||
+ constant_desc.Type == D3DXPT_SAMPLER3D ||
+ constant_desc.Type == D3DXPT_SAMPLERCUBE)) {
+ param->sampler_units_[param->sampler_unit_count_++] =
+ constant_desc.RegisterIndex;
+ }
+ }
+ }
+ }
+ // if the sampler hasn't been found in the constant table, that means it
+ // isn't referenced, hence it doesn't use any sampler unit.
+ }
+ return param;
+}
+
+// Fills the Desc structure, appending name and semantic if any, and if enough
+// room is available in the buffer.
+bool EffectParamD3D9::GetDesc(unsigned int size, void *data) {
+ using effect_param::Desc;
+ if (size < sizeof(Desc)) // NOLINT
+ return false;
+ if (!effect_)
+ return false;
+ ID3DXEffect *d3d_effect = effect_->d3d_effect_;
+ D3DXPARAMETER_DESC d3d_desc;
+ HR(d3d_effect->GetParameterDesc(handle_, &d3d_desc));
+ unsigned int name_size =
+ d3d_desc.Name ? static_cast<unsigned int>(strlen(d3d_desc.Name)) + 1 : 0;
+ unsigned int semantic_size = d3d_desc.Semantic ?
+ static_cast<unsigned int>(strlen(d3d_desc.Semantic)) + 1 : 0;
+ unsigned int total_size = sizeof(Desc) + name_size + semantic_size; // NOLINT
+
+ Desc *desc = static_cast<Desc *>(data);
+ memset(desc, 0, sizeof(*desc));
+ desc->size = total_size;
+ desc->data_type = data_type();
+ desc->data_size = GetDataSize(data_type());
+ desc->name_offset = 0;
+ desc->name_size = name_size;
+ desc->semantic_offset = 0;
+ desc->semantic_size = semantic_size;
+ unsigned int current_offset = sizeof(Desc);
+ if (d3d_desc.Name && current_offset + name_size <= size) {
+ desc->name_offset = current_offset;
+ memcpy(static_cast<char *>(data) + current_offset,
+ d3d_desc.Name, name_size);
+ current_offset += name_size;
+ }
+ if (d3d_desc.Semantic && current_offset + semantic_size <= size) {
+ desc->semantic_offset = current_offset;
+ memcpy(static_cast<char *>(data) + current_offset,
+ d3d_desc.Semantic, semantic_size);
+ current_offset += semantic_size;
+ }
+ return true;
+}
+
+// Sets the data into the D3D effect parameter, using the appropriate D3D call.
+bool EffectParamD3D9::SetData(GAPID3D9 *gapi,
+ unsigned int size,
+ const void * data) {
+ if (!effect_)
+ return false;
+ ID3DXEffect *d3d_effect = effect_->d3d_effect_;
+ effect_param::DataType type = data_type();
+ if (size < effect_param::GetDataSize(type)) return false;
+ switch (type) {
+ case effect_param::FLOAT1:
+ HR(d3d_effect->SetFloat(handle_, *static_cast<const float *>(data)));
+ break;
+ case effect_param::FLOAT2:
+ HR(d3d_effect->SetFloatArray(handle_, static_cast<const float *>(data),
+ 2));
+ break;
+ case effect_param::FLOAT3:
+ HR(d3d_effect->SetFloatArray(handle_, static_cast<const float *>(data),
+ 3));
+ break;
+ case effect_param::FLOAT4:
+ HR(d3d_effect->SetFloatArray(handle_, static_cast<const float *>(data),
+ 4));
+ break;
+ case effect_param::MATRIX4:
+ HR(d3d_effect->SetMatrix(handle_,
+ reinterpret_cast<const D3DXMATRIX *>(data)));
+ break;
+ case effect_param::INT:
+ HR(d3d_effect->SetInt(handle_, *static_cast<const int *>(data)));
+ break;
+ case effect_param::BOOL:
+ HR(d3d_effect->SetBool(handle_, *static_cast<const bool *>(data)?1:0));
+ break;
+ case effect_param::SAMPLER: {
+ ResourceID id = *static_cast<const ResourceID *>(data);
+ for (unsigned int i = 0; i < sampler_unit_count_; ++i) {
+ effect_->samplers_[sampler_units_[i]] = id;
+ }
+ break;
+ }
+ default:
+ DLOG(ERROR) << "Invalid parameter type.";
+ return false;
+ }
+ if (effect_ == gapi->current_effect()) {
+ effect_->sync_parameters_ = true;
+ }
+ return true;
+}
+
+// Calls EffectD3D9::Create, and assign the result to the resource ID.
+// If changing the current effect, dirty it.
+BufferSyncInterface::ParseError GAPID3D9::CreateEffect(
+ ResourceID id,
+ unsigned int size,
+ const void *data) {
+ if (id == current_effect_id_) DirtyEffect();
+ // Even though Assign would Destroy the effect at id, we do it explicitly in
+ // case the creation fails.
+ effects_.Destroy(id);
+ // Data is vp_main \0 fp_main \0 effect_text.
+ String vertex_program_entry;
+ String fragment_program_entry;
+ String effect_code;
+ if (!ParseEffectData(size, data,
+ &vertex_program_entry,
+ &fragment_program_entry,
+ &effect_code)) {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ EffectD3D9 * effect = EffectD3D9::Create(this, effect_code,
+ vertex_program_entry,
+ fragment_program_entry);
+ if (!effect) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ effects_.Assign(id, effect);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+// Destroys the Effect resource.
+// If destroying the current effect, dirty it.
+BufferSyncInterface::ParseError GAPID3D9::DestroyEffect(ResourceID id) {
+ if (id == current_effect_id_) DirtyEffect();
+ return effects_.Destroy(id) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+// Sets the current effect ID, dirtying the current effect.
+BufferSyncInterface::ParseError GAPID3D9::SetEffect(ResourceID id) {
+ DirtyEffect();
+ current_effect_id_ = id;
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+// Gets the param count from the effect and store it in the memory buffer.
+BufferSyncInterface::ParseError GAPID3D9::GetParamCount(
+ ResourceID id,
+ unsigned int size,
+ void *data) {
+ EffectD3D9 *effect = effects_.Get(id);
+ if (!effect || size < sizeof(Uint32)) // NOLINT
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ *static_cast<Uint32 *>(data) = effect->GetParamCount();
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+BufferSyncInterface::ParseError GAPID3D9::CreateParam(
+ ResourceID param_id,
+ ResourceID effect_id,
+ unsigned int index) {
+ EffectD3D9 *effect = effects_.Get(effect_id);
+ if (!effect) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ EffectParamD3D9 *param = effect->CreateParam(index);
+ if (!param) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ effect_params_.Assign(param_id, param);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+BufferSyncInterface::ParseError GAPID3D9::CreateParamByName(
+ ResourceID param_id,
+ ResourceID effect_id,
+ unsigned int size,
+ const void *name) {
+ EffectD3D9 *effect = effects_.Get(effect_id);
+ if (!effect) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ std::string string_name(static_cast<const char *>(name), size);
+ EffectParamD3D9 *param = effect->CreateParamByName(string_name.c_str());
+ if (!param) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ effect_params_.Assign(param_id, param);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+BufferSyncInterface::ParseError GAPID3D9::DestroyParam(ResourceID id) {
+ return effect_params_.Destroy(id) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+BufferSyncInterface::ParseError GAPID3D9::SetParamData(
+ ResourceID id,
+ unsigned int size,
+ const void *data) {
+ EffectParamD3D9 *param = effect_params_.Get(id);
+ if (!param) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return param->SetData(this, size, data) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+BufferSyncInterface::ParseError GAPID3D9::GetParamDesc(
+ ResourceID id,
+ unsigned int size,
+ void *data) {
+ EffectParamD3D9 *param = effect_params_.Get(id);
+ if (!param) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return param->GetDesc(size, data) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+// If the current effect is valid, call End on it, and tag for revalidation.
+void GAPID3D9::DirtyEffect() {
+ if (validate_effect_) return;
+ DCHECK(current_effect_);
+ current_effect_->End(this);
+ current_effect_ = NULL;
+ validate_effect_ = true;
+}
+
+// Gets the current effect, and calls Begin on it (if successful).
+// Should only be called if the current effect is not valid.
+bool GAPID3D9::ValidateEffect() {
+ DCHECK(validate_effect_);
+ DCHECK(!current_effect_);
+ current_effect_ = effects_.Get(current_effect_id_);
+ if (!current_effect_) return false;
+ validate_effect_ = false;
+ return current_effect_->Begin(this);
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/service/win/d3d9/effect_d3d9.h b/o3d/command_buffer/service/win/d3d9/effect_d3d9.h
new file mode 100644
index 0000000..318598c
--- /dev/null
+++ b/o3d/command_buffer/service/win/d3d9/effect_d3d9.h
@@ -0,0 +1,127 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the definition of the D3D9 versions of effect-related
+// resource classes.
+
+#ifndef O3D_COMMAND_BUFFER_SERVICE_WIN_D3D9_EFFECT_D3D9_H__
+#define O3D_COMMAND_BUFFER_SERVICE_WIN_D3D9_EFFECT_D3D9_H__
+
+#include <vector>
+#include "command_buffer/common/cross/gapi_interface.h"
+#include "command_buffer/service/win/d3d9/d3d9_utils.h"
+#include "command_buffer/service/cross/resource.h"
+
+namespace o3d {
+namespace command_buffer {
+
+class GAPID3D9;
+class EffectD3D9;
+
+// ps_2_0 limit
+static const unsigned int kMaxSamplerUnits = 16;
+
+// D3D version of EffectParam. This class keeps a reference to the D3D effect.
+class EffectParamD3D9: public EffectParam {
+ public:
+ EffectParamD3D9(effect_param::DataType data_type,
+ EffectD3D9 *effect,
+ D3DXHANDLE handle);
+ virtual ~EffectParamD3D9();
+
+ // Sets the data into the D3D effect parameter.
+ bool SetData(GAPID3D9 *gapi, unsigned int size, const void * data);
+
+ // Gets the description of the parameter.
+ bool GetDesc(unsigned int size, void *data);
+
+ // Resets the effect back-pointer. This is called when the effect gets
+ // destroyed, to invalidate the parameter.
+ void ResetEffect() { effect_ = NULL; }
+
+ static EffectParamD3D9 *Create(EffectD3D9 *effect, D3DXHANDLE handle);
+ private:
+ EffectD3D9 *effect_;
+ D3DXHANDLE handle_;
+ unsigned int sampler_unit_count_;
+ scoped_array<unsigned int> sampler_units_;
+};
+
+// D3D9 version of Effect.
+class EffectD3D9 : public Effect {
+ public:
+ EffectD3D9(ID3DXEffect *d3d_effect,
+ ID3DXConstantTable *fs_constant_table);
+ virtual ~EffectD3D9();
+ // Compiles and creates an effect from source code.
+ static EffectD3D9 *Create(GAPID3D9 *gapi,
+ const String &effect_code,
+ const String &vertex_program_entry,
+ const String &fragment_program_entry);
+ // Applies the effect states (vertex shader, pixel shader) to D3D.
+ bool Begin(GAPID3D9 *gapi);
+ // Resets the effect states (vertex shader, pixel shader) to D3D.
+ void End(GAPID3D9 *gapi);
+ // Commits parameters to D3D, if they were modified while the effect is
+ // active.
+ bool CommitParameters(GAPID3D9 *gapi);
+
+ // Gets the number of parameters in the effect.
+ unsigned int GetParamCount();
+ // Creates an effect parameter with the specified index.
+ EffectParamD3D9 *CreateParam(unsigned int index);
+ // Creates an effect parameter of the specified name.
+ EffectParamD3D9 *CreateParamByName(const char *name);
+ private:
+ typedef std::vector<EffectParamD3D9 *> ParamList;
+
+ // Links a param into this effect.
+ void LinkParam(EffectParamD3D9 *param);
+ // Unlinks a param into this effect.
+ void UnlinkParam(EffectParamD3D9 *param);
+ // Sets sampler states.
+ bool SetSamplers(GAPID3D9 *gapi);
+
+ ID3DXEffect *d3d_effect_;
+ ID3DXConstantTable *fs_constant_table_;
+ ParamList params_;
+ bool sync_parameters_;
+ ResourceID samplers_[kMaxSamplerUnits];
+
+ friend class EffectParamD3D9;
+ DISALLOW_COPY_AND_ASSIGN(EffectD3D9);
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_SERVICE_WIN_D3D9_EFFECT_D3D9_H__
diff --git a/o3d/command_buffer/service/win/d3d9/gapi_d3d9.cc b/o3d/command_buffer/service/win/d3d9/gapi_d3d9.cc
new file mode 100644
index 0000000..f5fe0d4
--- /dev/null
+++ b/o3d/command_buffer/service/win/d3d9/gapi_d3d9.cc
@@ -0,0 +1,305 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the implementation of the GAPID3D9 class.
+
+#include "command_buffer/service/win/d3d9/gapi_d3d9.h"
+
+namespace o3d {
+namespace command_buffer {
+
+GAPID3D9::GAPID3D9()
+ : d3d_(NULL),
+ d3d_device_(NULL),
+ hwnd_(NULL),
+ current_vertex_struct_(0),
+ validate_streams_(true),
+ max_vertices_(0),
+ current_effect_id_(0),
+ validate_effect_(true),
+ current_effect_(NULL),
+ vertex_buffers_(),
+ index_buffers_(),
+ vertex_structs_() {}
+
+GAPID3D9::~GAPID3D9() {}
+
+// Initializes a D3D interface and device, and sets basic states.
+bool GAPID3D9::Initialize() {
+ d3d_ = Direct3DCreate9(D3D_SDK_VERSION);
+ if (NULL == d3d_) {
+ LOG(ERROR) << "Failed to create the initial D3D9 Interface";
+ return false;
+ }
+ d3d_device_ = NULL;
+
+ D3DDISPLAYMODE d3ddm;
+ d3d_->GetAdapterDisplayMode(D3DADAPTER_DEFAULT, &d3ddm);
+ // NOTE: make sure the backbuffer matches this format, as it is
+ // currently currently assumed to be 32-bit 8X8R8G8B
+
+ D3DPRESENT_PARAMETERS d3dpp;
+ ZeroMemory(&d3dpp, sizeof(d3dpp));
+ d3dpp.Windowed = TRUE;
+ d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD;
+ d3dpp.BackBufferFormat = d3ddm.Format;
+ d3dpp.EnableAutoDepthStencil = TRUE;
+ d3dpp.AutoDepthStencilFormat = D3DFMT_D24S8;
+ d3dpp.PresentationInterval = D3DPRESENT_INTERVAL_ONE; // wait for vsync
+ // Note: SwapEffect=DISCARD is req. for multisample to function
+ // Note: AutoDepthStencilFormat is 16-bit (not the usual 8-bit)
+
+ // query multisampling
+ const int kNumTypesToCheck = 4;
+ D3DMULTISAMPLE_TYPE multisample_types[] = { D3DMULTISAMPLE_5_SAMPLES,
+ D3DMULTISAMPLE_4_SAMPLES,
+ D3DMULTISAMPLE_2_SAMPLES,
+ D3DMULTISAMPLE_NONE };
+ DWORD multisample_quality = 0;
+ for (int i = 0; i < kNumTypesToCheck; ++i) {
+ // check back-buffer for multisampling at level "i";
+ // back buffer = 32-bit XRGB (i.e. no alpha)
+ if (SUCCEEDED(d3d_->CheckDeviceMultiSampleType(
+ D3DADAPTER_DEFAULT,
+ D3DDEVTYPE_HAL,
+ D3DFMT_X8R8G8B8,
+ true, // result is windowed
+ multisample_types[i],
+ &multisample_quality))) {
+ // back buffer succeeded, now check depth-buffer
+ // depth buffer = 24-bit, stencil = 8-bit
+ // NOTE: 8-bit not 16-bit like the D3DPRESENT_PARAMETERS
+ if (SUCCEEDED(d3d_->CheckDeviceMultiSampleType(
+ D3DADAPTER_DEFAULT,
+ D3DDEVTYPE_HAL,
+ D3DFMT_D24S8,
+ true, // result is windowed
+ multisample_types[i],
+ &multisample_quality))) {
+ d3dpp.MultiSampleType = multisample_types[i];
+ d3dpp.MultiSampleQuality = multisample_quality - 1;
+ break;
+ }
+ }
+ }
+ // D3DCREATE_FPU_PRESERVE is there because Firefox 3 relies on specific FPU
+ // flags for its UI rendering. Apparently Firefox 2 does not, though we don't
+ // currently propagate that info.
+ // TODO: check if FPU_PRESERVE has a significant perf hit, in which
+ // case find out if we can disable it for Firefox 2/other browsers, and/or if
+ // it makes sense to switch FPU flags before/after every DX call.
+ DWORD flags = D3DCREATE_HARDWARE_VERTEXPROCESSING | D3DCREATE_FPU_PRESERVE;
+ if (!SUCCEEDED(d3d_->CreateDevice(D3DADAPTER_DEFAULT,
+ D3DDEVTYPE_HAL,
+ hwnd_,
+ flags,
+ &d3dpp,
+ &d3d_device_))) {
+ LOG(ERROR) << "Failed to create the D3D Device";
+ return false;
+ }
+ // initialise the d3d graphics state.
+ HR(d3d_device_->SetRenderState(D3DRS_LIGHTING, FALSE));
+ HR(d3d_device_->SetRenderState(D3DRS_ZENABLE, TRUE));
+ HR(d3d_device_->SetRenderState(D3DRS_CULLMODE, D3DCULL_NONE));
+ return true;
+}
+
+// Deletes the D3D9 Device and releases the D3D interface.
+void GAPID3D9::Destroy() {
+ vertex_buffers_.DestroyAllResources();
+ index_buffers_.DestroyAllResources();
+ vertex_structs_.DestroyAllResources();
+ effects_.DestroyAllResources();
+ effect_params_.DestroyAllResources();
+ textures_.DestroyAllResources();
+ samplers_.DestroyAllResources();
+ if (d3d_device_) {
+ d3d_device_->Release();
+ d3d_device_ = NULL;
+ }
+ if (d3d_) {
+ d3d_->Release();
+ d3d_ = NULL;
+ }
+}
+
+// Begins the frame.
+void GAPID3D9::BeginFrame() {
+ HR(d3d_device_->BeginScene());
+}
+
+// Ends the frame, presenting the back buffer.
+void GAPID3D9::EndFrame() {
+ DirtyEffect();
+ HR(d3d_device_->EndScene());
+ HR(d3d_device_->Present(NULL, NULL, NULL, NULL));
+}
+
+// Clears the selected buffers.
+void GAPID3D9::Clear(unsigned int buffers,
+ const RGBA &color,
+ float depth,
+ unsigned int stencil) {
+ DWORD flags = (buffers & COLOR ? D3DCLEAR_TARGET : 0) |
+ (buffers & DEPTH ? D3DCLEAR_ZBUFFER : 0) |
+ (buffers & STENCIL ? D3DCLEAR_STENCIL : 0);
+ HR(d3d_device_->Clear(0,
+ NULL,
+ flags,
+ D3DCOLOR_COLORVALUE(color.red,
+ color.green,
+ color.blue,
+ color.alpha),
+ depth,
+ stencil));
+}
+
+// Sets the viewport.
+void GAPID3D9::SetViewport(unsigned int x,
+ unsigned int y,
+ unsigned int width,
+ unsigned int height,
+ float z_min,
+ float z_max) {
+ D3DVIEWPORT9 viewport = {x, y, width, height, z_min, z_max};
+ HR(d3d_device_->SetViewport(&viewport));
+}
+
+// Converts an unsigned int RGBA color into an unsigned int ARGB (DirectX)
+// color.
+static unsigned int RGBAToARGB(unsigned int rgba) {
+ return (rgba >> 8) | (rgba << 24);
+}
+
+// Sets the current VertexStruct. Just keep track of the ID.
+BufferSyncInterface::ParseError GAPID3D9::SetVertexStruct(ResourceID id) {
+ current_vertex_struct_ = id;
+ validate_streams_ = true;
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+// Sets in D3D the input streams of the current vertex struct.
+bool GAPID3D9::ValidateStreams() {
+ DCHECK(validate_streams_);
+ VertexStructD3D9 *vertex_struct = vertex_structs_.Get(current_vertex_struct_);
+ if (!vertex_struct) {
+ LOG(ERROR) << "Drawing with invalid streams.";
+ return false;
+ }
+ max_vertices_ = vertex_struct->SetStreams(this);
+ validate_streams_ = false;
+ return max_vertices_ > 0;
+}
+
+// Converts a GAPID3D9::PrimitiveType to a D3DPRIMITIVETYPE.
+static D3DPRIMITIVETYPE D3DPrimitive(GAPID3D9::PrimitiveType primitive_type) {
+ switch (primitive_type) {
+ case GAPID3D9::POINTS:
+ return D3DPT_POINTLIST;
+ case GAPID3D9::LINES:
+ return D3DPT_LINELIST;
+ case GAPID3D9::LINE_STRIPS:
+ return D3DPT_LINESTRIP;
+ case GAPID3D9::TRIANGLES:
+ return D3DPT_TRIANGLELIST;
+ case GAPID3D9::TRIANGLE_STRIPS:
+ return D3DPT_TRIANGLESTRIP;
+ case GAPID3D9::TRIANGLE_FANS:
+ return D3DPT_TRIANGLEFAN;
+ default:
+ LOG(FATAL) << "Invalid primitive type";
+ return D3DPT_POINTLIST;
+ }
+}
+
+// Draws with the current vertex struct.
+BufferSyncInterface::ParseError GAPID3D9::Draw(
+ PrimitiveType primitive_type,
+ unsigned int first,
+ unsigned int count) {
+ if (validate_streams_ && !ValidateStreams()) {
+ // TODO: add proper error management
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ if (validate_effect_ && !ValidateEffect()) {
+ // TODO: add proper error management
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ DCHECK(current_effect_);
+ if (!current_effect_->CommitParameters(this)) {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ if (first + count > max_vertices_) {
+ // TODO: add proper error management
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ HR(d3d_device_->DrawPrimitive(D3DPrimitive(primitive_type), first, count));
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+// Draws with the current vertex struct.
+BufferSyncInterface::ParseError GAPID3D9::DrawIndexed(
+ PrimitiveType primitive_type,
+ ResourceID index_buffer_id,
+ unsigned int first,
+ unsigned int count,
+ unsigned int min_index,
+ unsigned int max_index) {
+ IndexBufferD3D9 *index_buffer = index_buffers_.Get(index_buffer_id);
+ if (!index_buffer) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ if (validate_streams_ && !ValidateStreams()) {
+ // TODO: add proper error management
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ if (validate_effect_ && !ValidateEffect()) {
+ // TODO: add proper error management
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ DCHECK(current_effect_);
+ if (!current_effect_->CommitParameters(this)) {
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+ if ((min_index >= max_vertices_) || (max_index > max_vertices_)) {
+ // TODO: add proper error management
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ }
+
+ HR(d3d_device_->SetIndices(index_buffer->d3d_index_buffer()));
+ HR(d3d_device_->DrawIndexedPrimitive(D3DPrimitive(primitive_type), 0,
+ min_index, max_index - min_index + 1,
+ first, count));
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/service/win/d3d9/gapi_d3d9.h b/o3d/command_buffer/service/win/d3d9/gapi_d3d9.h
new file mode 100644
index 0000000..e94f35c
--- /dev/null
+++ b/o3d/command_buffer/service/win/d3d9/gapi_d3d9.h
@@ -0,0 +1,384 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the GAPID3D9 class, implementing the GAPI interface for
+// D3D9.
+
+#ifndef O3D_COMMAND_BUFFER_SERVICE_WIN_D3D9_GAPI_D3D9_H__
+#define O3D_COMMAND_BUFFER_SERVICE_WIN_D3D9_GAPI_D3D9_H__
+
+#include "command_buffer/common/cross/gapi_interface.h"
+#include "command_buffer/service/win/d3d9/d3d9_utils.h"
+#include "command_buffer/service/win/d3d9/geometry_d3d9.h"
+#include "command_buffer/service/win/d3d9/effect_d3d9.h"
+#include "command_buffer/service/win/d3d9/texture_d3d9.h"
+#include "command_buffer/service/win/d3d9/sampler_d3d9.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// This class implements the GAPI interface for D3D9.
+class GAPID3D9 : public GAPIInterface {
+ public:
+ GAPID3D9();
+ virtual ~GAPID3D9();
+
+ void set_hwnd(HWND hwnd) { hwnd_ = hwnd; }
+
+ // Initializes the graphics context, bound to a window.
+ // Returns:
+ // true if successful.
+ virtual bool Initialize();
+
+ // Destroys the graphics context.
+ virtual void Destroy();
+
+ // Implements the BeginFrame function for D3D9.
+ virtual void BeginFrame();
+
+ // Implements the EndFrame function for D3D9.
+ virtual void EndFrame();
+
+ // Implements the Clear function for D3D9.
+ virtual void Clear(unsigned int buffers,
+ const RGBA &color,
+ float depth,
+ unsigned int stencil);
+
+ // Implements the SetViewport function for D3D9.
+ virtual void SetViewport(unsigned int x,
+ unsigned int y,
+ unsigned int width,
+ unsigned int height,
+ float z_min,
+ float z_max);
+
+ // Implements the CreateVertexBuffer function for D3D9.
+ virtual ParseError CreateVertexBuffer(ResourceID id,
+ unsigned int size,
+ unsigned int flags);
+
+ // Implements the DestroyVertexBuffer function for D3D9.
+ virtual ParseError DestroyVertexBuffer(ResourceID id);
+
+ // Implements the SetVertexBufferData function for D3D9.
+ virtual ParseError SetVertexBufferData(ResourceID id,
+ unsigned int offset,
+ unsigned int size,
+ const void *data);
+
+ // Implements the GetVertexBufferData function for D3D9.
+ virtual ParseError GetVertexBufferData(ResourceID id,
+ unsigned int offset,
+ unsigned int size,
+ void *data);
+
+ // Implements the CreateIndexBuffer function for D3D9.
+ virtual ParseError CreateIndexBuffer(ResourceID id,
+ unsigned int size,
+ unsigned int flags);
+
+ // Implements the DestroyIndexBuffer function for D3D9.
+ virtual ParseError DestroyIndexBuffer(ResourceID id);
+
+ // Implements the SetIndexBufferData function for D3D9.
+ virtual ParseError SetIndexBufferData(ResourceID id,
+ unsigned int offset,
+ unsigned int size,
+ const void *data);
+
+ // Implements the GetIndexBufferData function for D3D9.
+ virtual ParseError GetIndexBufferData(ResourceID id,
+ unsigned int offset,
+ unsigned int size,
+ void *data);
+
+ // Implements the CreateVertexStruct function for D3D9.
+ virtual ParseError CreateVertexStruct(ResourceID id,
+ unsigned int input_count);
+
+ // Implements the DestroyVertexStruct function for D3D9.
+ virtual ParseError DestroyVertexStruct(ResourceID id);
+
+ // Implements the SetVertexInput function for D3D9.
+ virtual ParseError SetVertexInput(ResourceID vertex_struct_id,
+ unsigned int input_index,
+ ResourceID vertex_buffer_id,
+ unsigned int offset,
+ unsigned int stride,
+ vertex_struct::Type type,
+ vertex_struct::Semantic semantic,
+ unsigned int semantic_index);
+
+ // Implements the SetVertexStruct function for D3D9.
+ virtual ParseError SetVertexStruct(ResourceID id);
+
+ // Implements the Draw function for D3D9.
+ virtual ParseError Draw(PrimitiveType primitive_type,
+ unsigned int first,
+ unsigned int count);
+
+ // Implements the DrawIndexed function for D3D9.
+ virtual ParseError DrawIndexed(PrimitiveType primitive_type,
+ ResourceID index_buffer_id,
+ unsigned int first,
+ unsigned int count,
+ unsigned int min_index,
+ unsigned int max_index);
+
+ // Implements the CreateEffect function for D3D9.
+ virtual ParseError CreateEffect(ResourceID id,
+ unsigned int size,
+ const void *data);
+
+ // Implements the DestroyEffect function for D3D9.
+ virtual ParseError DestroyEffect(ResourceID id);
+
+ // Implements the SetEffect function for D3D9.
+ virtual ParseError SetEffect(ResourceID id);
+
+ // Implements the GetParamCount function for D3D9.
+ virtual ParseError GetParamCount(ResourceID id,
+ unsigned int size,
+ void *data);
+
+ // Implements the CreateParam function for D3D9.
+ virtual ParseError CreateParam(ResourceID param_id,
+ ResourceID effect_id,
+ unsigned int index);
+
+ // Implements the CreateParamByName function for D3D9.
+ virtual ParseError CreateParamByName(ResourceID param_id,
+ ResourceID effect_id,
+ unsigned int size,
+ const void *name);
+
+ // Implements the DestroyParam function for D3D9.
+ virtual ParseError DestroyParam(ResourceID id);
+
+ // Implements the SetParamData function for D3D9.
+ virtual ParseError SetParamData(ResourceID id,
+ unsigned int size,
+ const void *data);
+
+ // Implements the GetParamDesc function for D3D9.
+ virtual ParseError GetParamDesc(ResourceID id,
+ unsigned int size,
+ void *data);
+
+ // Implements the CreateTexture2D function for D3D9.
+ virtual ParseError CreateTexture2D(ResourceID id,
+ unsigned int width,
+ unsigned int height,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags);
+
+ // Implements the CreateTexture3D function for D3D9.
+ virtual ParseError CreateTexture3D(ResourceID id,
+ unsigned int width,
+ unsigned int height,
+ unsigned int depth,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags);
+
+ // Implements the CreateTextureCube function for D3D9.
+ virtual ParseError CreateTextureCube(ResourceID id,
+ unsigned int side,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags);
+
+ // Implements the SetTextureData function for D3D9.
+ virtual ParseError SetTextureData(ResourceID id,
+ unsigned int x,
+ unsigned int y,
+ unsigned int z,
+ unsigned int width,
+ unsigned int height,
+ unsigned int depth,
+ unsigned int level,
+ texture::Face face,
+ unsigned int pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ const void *data);
+
+ // Implements the GetTextureData function for D3D9.
+ virtual ParseError GetTextureData(ResourceID id,
+ unsigned int x,
+ unsigned int y,
+ unsigned int z,
+ unsigned int width,
+ unsigned int height,
+ unsigned int depth,
+ unsigned int level,
+ texture::Face face,
+ unsigned int pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ void *data);
+
+ // Implements the DestroyTexture function for D3D9.
+ virtual ParseError DestroyTexture(ResourceID id);
+
+ // Implements the CreateSampler function for D3D9.
+ virtual ParseError CreateSampler(ResourceID id);
+
+ // Implements the DestroySampler function for D3D9.
+ virtual ParseError DestroySampler(ResourceID id);
+
+ // Implements the SetSamplerStates function for D3D9.
+ virtual ParseError SetSamplerStates(ResourceID id,
+ sampler::AddressingMode addressing_u,
+ sampler::AddressingMode addressing_v,
+ sampler::AddressingMode addressing_w,
+ sampler::FilteringMode mag_filter,
+ sampler::FilteringMode min_filter,
+ sampler::FilteringMode mip_filter,
+ unsigned int max_anisotropy);
+
+ // Implements the SetSamplerBorderColor function for D3D9.
+ virtual ParseError SetSamplerBorderColor(ResourceID id, const RGBA &color);
+
+ // Implements the SetSamplerTexture function for D3D9.
+ virtual ParseError SetSamplerTexture(ResourceID id, ResourceID texture_id);
+
+ // Implements the SetScissor function for D3D9.
+ virtual void SetScissor(bool enable,
+ unsigned int x,
+ unsigned int y,
+ unsigned int width,
+ unsigned int height);
+
+ // Implements the SetPointLineRaster function for D3D9.
+ virtual void SetPointLineRaster(bool line_smooth,
+ bool point_sprite,
+ float point_size);
+
+ // Implements the SetPolygonOffset function for D3D9.
+ virtual void SetPolygonOffset(float slope_factor, float units);
+
+ // Implements the SetPolygonRaster function for D3D9.
+ virtual void SetPolygonRaster(PolygonMode fill_mode,
+ FaceCullMode cull_mode);
+
+ // Implements the SetAlphaTest function for D3D9.
+ virtual void SetAlphaTest(bool enable,
+ float reference,
+ Comparison comp);
+
+ // Implements the SetDepthTest function for D3D9.
+ virtual void SetDepthTest(bool enable,
+ bool write_enable,
+ Comparison comp);
+
+ // Implements the SetStencilTest function for D3D9.
+ virtual void SetStencilTest(bool enable,
+ bool separate_ccw,
+ unsigned int write_mask,
+ unsigned int compare_mask,
+ unsigned int ref,
+ Uint32 func_ops);
+
+ // Implements the SetColorWritefunction for D3D9.
+ virtual void SetColorWrite(bool red,
+ bool green,
+ bool blue,
+ bool alpha,
+ bool dither);
+
+ // Implements the SetBlending function for D3D9.
+ virtual void SetBlending(bool enable,
+ bool separate_alpha,
+ BlendEq color_eq,
+ BlendFunc color_src_func,
+ BlendFunc color_dst_func,
+ BlendEq alpha_eq,
+ BlendFunc alpha_src_func,
+ BlendFunc alpha_dst_func);
+
+ // Implements the SetBlendingColor function for D3D9.
+ virtual void SetBlendingColor(const RGBA &color);
+
+ // Gets the D3D9 device.
+ IDirect3DDevice9 *d3d_device() const { return d3d_device_; }
+
+ // Gets a vertex buffer by resource ID.
+ VertexBufferD3D9 *GetVertexBuffer(ResourceID id) {
+ return vertex_buffers_.Get(id);
+ }
+
+ // Gets a texture by resource ID.
+ TextureD3D9 *GetTexture(ResourceID id) {
+ return textures_.Get(id);
+ }
+
+ // Gets a sampler by resource ID.
+ SamplerD3D9 *GetSampler(ResourceID id) {
+ return samplers_.Get(id);
+ }
+
+ EffectD3D9 *current_effect() { return current_effect_; }
+ private:
+ // Validates the current vertex struct to D3D, setting the streams.
+ bool ValidateStreams();
+ // Validates the current effect to D3D. This sends the effect states to D3D.
+ bool ValidateEffect();
+ // "Dirty" the current effect. This resets the effect states to D3D, and
+ // requires ValidateEffect() to be called before further draws occur.
+ void DirtyEffect();
+
+ LPDIRECT3D9 d3d_;
+ LPDIRECT3DDEVICE9 d3d_device_;
+ HWND hwnd_;
+ ResourceID current_vertex_struct_;
+ bool validate_streams_;
+ unsigned int max_vertices_;
+ ResourceID current_effect_id_;
+ bool validate_effect_;
+ EffectD3D9 *current_effect_;
+
+ ResourceMap<VertexBufferD3D9> vertex_buffers_;
+ ResourceMap<IndexBufferD3D9> index_buffers_;
+ ResourceMap<VertexStructD3D9> vertex_structs_;
+ ResourceMap<EffectD3D9> effects_;
+ ResourceMap<EffectParamD3D9> effect_params_;
+ ResourceMap<TextureD3D9> textures_;
+ ResourceMap<SamplerD3D9> samplers_;
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_SERVICE_WIN_D3D9_GAPI_D3D9_H__
diff --git a/o3d/command_buffer/service/win/d3d9/geometry_d3d9.cc b/o3d/command_buffer/service/win/d3d9/geometry_d3d9.cc
new file mode 100644
index 0000000..b81dcc3
--- /dev/null
+++ b/o3d/command_buffer/service/win/d3d9/geometry_d3d9.cc
@@ -0,0 +1,428 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the implementation of the D3D9 versions of the
+// VertexBuffer, IndexBuffer and VertexStruct resources.
+// This file also contains the related GAPID3D9 function implementations.
+
+#include <algorithm>
+#include "command_buffer/service/win/d3d9/d3d9_utils.h"
+#include "command_buffer/service/win/d3d9/geometry_d3d9.h"
+#include "command_buffer/service/win/d3d9/gapi_d3d9.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// Destroys the D3D9 vertex buffer.
+VertexBufferD3D9::~VertexBufferD3D9() {
+ DCHECK(d3d_vertex_buffer_ != NULL);
+ if (d3d_vertex_buffer_) {
+ d3d_vertex_buffer_->Release();
+ d3d_vertex_buffer_ = NULL;
+ }
+}
+
+// Creates a D3D9 vertex buffer.
+void VertexBufferD3D9::Create(GAPID3D9 *gapi) {
+ DCHECK(d3d_vertex_buffer_ == NULL);
+
+ DWORD d3d_usage = (flags() & vertex_buffer::DYNAMIC) ? D3DUSAGE_DYNAMIC : 0;
+ D3DPOOL d3d_pool = D3DPOOL_MANAGED;
+ HR(gapi->d3d_device()->CreateVertexBuffer(size(), d3d_usage, 0, d3d_pool,
+ &d3d_vertex_buffer_, NULL));
+}
+
+// Sets the data into the D3D9 vertex buffer, using Lock() and memcpy.
+bool VertexBufferD3D9::SetData(unsigned int offset,
+ unsigned int size,
+ const void *data) {
+ if (!d3d_vertex_buffer_) {
+ LOG(ERROR) << "Calling SetData on a non-initialized VertexBufferD3D9.";
+ return false;
+ }
+ if ((offset >= this->size()) || (offset + size > this->size())) {
+ LOG(ERROR) << "Invalid size or offset on VertexBufferD3D9::SetData.";
+ return false;
+ }
+ void *ptr = NULL;
+ DWORD lock_flags = 0;
+ // If we are setting the full buffer, discard the old data. That's only
+ // possible to do for a dynamic d3d vertex buffer.
+ if ((offset == 0) && (size == this->size()) &&
+ (flags() & vertex_buffer::DYNAMIC))
+ lock_flags = D3DLOCK_DISCARD;
+ HR(d3d_vertex_buffer_->Lock(offset, size, &ptr, lock_flags));
+ memcpy(ptr, data, size);
+ HR(d3d_vertex_buffer_->Unlock());
+ return true;
+}
+
+// Gets the data from the D3D9 vertex buffer, using Lock() and memcpy.
+bool VertexBufferD3D9::GetData(unsigned int offset,
+ unsigned int size,
+ void *data) {
+ if (!d3d_vertex_buffer_) {
+ LOG(ERROR) << "Calling SetData on a non-initialized VertexBufferD3D9.";
+ return false;
+ }
+ if ((offset >= this->size()) || (offset + size > this->size())) {
+ LOG(ERROR) << "Invalid size or offset on VertexBufferD3D9::SetData.";
+ return false;
+ }
+ void *ptr = NULL;
+ DWORD lock_flags = D3DLOCK_READONLY;
+ HR(d3d_vertex_buffer_->Lock(offset, size, &ptr, lock_flags));
+ memcpy(data, ptr, size);
+ HR(d3d_vertex_buffer_->Unlock());
+ return true;
+}
+
+// Destroys the D3D9 index buffer.
+IndexBufferD3D9::~IndexBufferD3D9() {
+ DCHECK(d3d_index_buffer_ != NULL);
+ if (d3d_index_buffer_) {
+ d3d_index_buffer_->Release();
+ d3d_index_buffer_ = NULL;
+ }
+}
+
+// Creates a D3D9 index buffer.
+void IndexBufferD3D9::Create(GAPID3D9 *gapi) {
+ DCHECK(d3d_index_buffer_ == NULL);
+
+ DWORD d3d_usage = (flags() & index_buffer::DYNAMIC) ? D3DUSAGE_DYNAMIC : 0;
+ D3DFORMAT d3d_format =
+ (flags() & index_buffer::INDEX_32BIT) ? D3DFMT_INDEX32 : D3DFMT_INDEX16;
+ D3DPOOL d3d_pool = D3DPOOL_MANAGED;
+ HR(gapi->d3d_device()->CreateIndexBuffer(size(), d3d_usage, d3d_format,
+ d3d_pool, &d3d_index_buffer_,
+ NULL));
+}
+
+// Sets the data into the D3D9 index buffer, using Lock() and memcpy.
+bool IndexBufferD3D9::SetData(unsigned int offset,
+ unsigned int size,
+ const void *data) {
+ if (!d3d_index_buffer_) {
+ LOG(ERROR) << "Calling SetData on a non-initialized IndexBufferD3D9.";
+ return false;
+ }
+ if ((offset >= this->size()) || (offset + size > this->size())) {
+ LOG(ERROR) << "Invalid size or offset on IndexBufferD3D9::SetData.";
+ return false;
+ }
+ void *ptr = NULL;
+ DWORD lock_flags = 0;
+ // If we are setting the full buffer, discard the old data. That's only
+ // possible to do for a dynamic d3d index buffer.
+ if ((offset == 0) && (size == this->size()) &&
+ (flags() & index_buffer::DYNAMIC))
+ lock_flags = D3DLOCK_DISCARD;
+ HR(d3d_index_buffer_->Lock(offset, size, &ptr, lock_flags));
+ memcpy(ptr, data, size);
+ HR(d3d_index_buffer_->Unlock());
+ return true;
+}
+
+// Gets the data from the D3D9 index buffer, using Lock() and memcpy.
+bool IndexBufferD3D9::GetData(unsigned int offset,
+ unsigned int size,
+ void *data) {
+ if (!d3d_index_buffer_) {
+ LOG(ERROR) << "Calling SetData on a non-initialized IndexBufferD3D9.";
+ return false;
+ }
+ if ((offset >= this->size()) || (offset + size > this->size())) {
+ LOG(ERROR) << "Invalid size or offset on IndexBufferD3D9::SetData.";
+ return false;
+ }
+ void *ptr = NULL;
+ DWORD lock_flags = D3DLOCK_READONLY;
+ HR(d3d_index_buffer_->Lock(offset, size, &ptr, lock_flags));
+ memcpy(data, ptr, size);
+ HR(d3d_index_buffer_->Unlock());
+ return true;
+}
+
+// Sets the input element in the VertexStruct resource.
+void VertexStructD3D9::SetInput(unsigned int input_index,
+ ResourceID vertex_buffer_id,
+ unsigned int offset,
+ unsigned int stride,
+ vertex_struct::Type type,
+ vertex_struct::Semantic semantic,
+ unsigned int semantic_index) {
+ Element &element = GetElement(input_index);
+ element.vertex_buffer = vertex_buffer_id;
+ element.offset = offset;
+ element.stride = stride;
+ element.type = type;
+ element.semantic = semantic;
+ element.semantic_index = semantic_index;
+ dirty_ = true;
+}
+
+// Sets the vdecl and stream sources in D3D9. Compiles them if needed.
+unsigned int VertexStructD3D9::SetStreams(GAPID3D9 *gapi) {
+ IDirect3DDevice9 *d3d_device = gapi->d3d_device();
+ if (dirty_) Compile(d3d_device);
+ HR(d3d_device->SetVertexDeclaration(d3d_vertex_decl_));
+ unsigned int max_vertices = UINT_MAX;
+ for (unsigned int i = 0; i < streams_.size(); ++i) {
+ const StreamPair &pair = streams_[i];
+ VertexBufferD3D9 *vertex_buffer = gapi->GetVertexBuffer(pair.first);
+ if (!vertex_buffer) {
+ max_vertices = 0;
+ continue;
+ }
+ HR(d3d_device->SetStreamSource(i, vertex_buffer->d3d_vertex_buffer(), 0,
+ pair.second));
+ max_vertices = std::min(max_vertices, vertex_buffer->size()/pair.second);
+ }
+ return max_vertices;
+}
+
+// Converts a vertex_struct::Type to a D3DDECLTYPE.
+static D3DDECLTYPE D3DType(vertex_struct::Type type) {
+ switch (type) {
+ case vertex_struct::FLOAT1:
+ return D3DDECLTYPE_FLOAT1;
+ case vertex_struct::FLOAT2:
+ return D3DDECLTYPE_FLOAT2;
+ case vertex_struct::FLOAT3:
+ return D3DDECLTYPE_FLOAT3;
+ case vertex_struct::FLOAT4:
+ return D3DDECLTYPE_FLOAT4;
+ case vertex_struct::UCHAR4N:
+ return D3DDECLTYPE_UBYTE4N;
+ case vertex_struct::NUM_TYPES:
+ break;
+ }
+ LOG(FATAL) << "Invalid type";
+ return D3DDECLTYPE_FLOAT1;
+}
+
+// Converts a vertex_struct::Semantic to a D3DDECLUSAGE.
+static D3DDECLUSAGE D3DUsage(vertex_struct::Semantic semantic) {
+ switch (semantic) {
+ case vertex_struct::POSITION:
+ return D3DDECLUSAGE_POSITION;
+ case vertex_struct::NORMAL:
+ return D3DDECLUSAGE_NORMAL;
+ case vertex_struct::COLOR:
+ return D3DDECLUSAGE_COLOR;
+ case vertex_struct::TEX_COORD:
+ return D3DDECLUSAGE_TEXCOORD;
+ case vertex_struct::NUM_SEMANTICS:
+ break;
+ }
+ LOG(FATAL) << "Invalid type";
+ return D3DDECLUSAGE_POSITION;
+}
+
+// Destroys the d3d vertex declaration.
+VertexStructD3D9::~VertexStructD3D9() {
+ Destroy();
+}
+
+void VertexStructD3D9::Destroy() {
+ if (d3d_vertex_decl_) {
+ d3d_vertex_decl_->Release();
+ d3d_vertex_decl_ = NULL;
+ }
+ streams_.clear();
+}
+
+// Compiles a stream map and a d3d vertex declaration from the list of inputs.
+// 2 inputs that use the same vertex buffer and stride will use the same
+// d3d stream.
+void VertexStructD3D9::Compile(IDirect3DDevice9 *d3d_device) {
+ DCHECK(dirty_);
+ Destroy();
+ streams_.reserve(count_);
+ scoped_array<D3DVERTEXELEMENT9> d3d_elements(
+ new D3DVERTEXELEMENT9[count_ + 1]);
+ memset(d3d_elements.get(), 0, sizeof(D3DVERTEXELEMENT9) * (count_ + 1));
+ // build streams_ like a set, but the order matters.
+ for (unsigned int i = 0; i < count_ ; ++i) {
+ Element &element = GetElement(i);
+ D3DVERTEXELEMENT9 &d3d_element = d3d_elements[i];
+ StreamPair pair(element.vertex_buffer, element.stride);
+ std::vector<StreamPair>::iterator it =
+ std::find(streams_.begin(), streams_.end(), pair);
+ unsigned int stream_index = 0;
+ if (it == streams_.end()) {
+ streams_.push_back(pair);
+ stream_index = static_cast<unsigned int>(streams_.size() - 1);
+ } else {
+ stream_index = it - streams_.begin();
+ }
+ d3d_element.Stream = stream_index;
+ d3d_element.Offset = element.offset;
+ d3d_element.Type = D3DType(element.type);
+ d3d_element.Usage = D3DUsage(element.semantic);
+ d3d_element.UsageIndex = element.semantic_index;
+ }
+ D3DVERTEXELEMENT9 &end = d3d_elements[count_];
+ end.Stream = 0xFF;
+ end.Type = D3DDECLTYPE_UNUSED;
+ HR(d3d_device->CreateVertexDeclaration(d3d_elements.get(),
+ &d3d_vertex_decl_));
+ dirty_ = false;
+}
+
+// Creates and assigns a VertexBufferD3D9 resource.
+BufferSyncInterface::ParseError GAPID3D9::CreateVertexBuffer(
+ ResourceID id,
+ unsigned int size,
+ unsigned int flags) {
+ VertexBufferD3D9 *vertex_buffer = new VertexBufferD3D9(size, flags);
+ vertex_buffer->Create(this);
+ vertex_buffers_.Assign(id, vertex_buffer);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+// Destroys a VertexBufferD3D9 resource.
+BufferSyncInterface::ParseError GAPID3D9::DestroyVertexBuffer(ResourceID id) {
+ return vertex_buffers_.Destroy(id) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+// Copies the data into the VertexBufferD3D9 resource.
+BufferSyncInterface::ParseError GAPID3D9::SetVertexBufferData(
+ ResourceID id,
+ unsigned int offset,
+ unsigned int size,
+ const void *data) {
+ VertexBufferD3D9 *vertex_buffer = vertex_buffers_.Get(id);
+ if (!vertex_buffer) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return vertex_buffer->SetData(offset, size, data) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+// Copies the data from the VertexBufferD3D9 resource.
+BufferSyncInterface::ParseError GAPID3D9::GetVertexBufferData(
+ ResourceID id,
+ unsigned int offset,
+ unsigned int size,
+ void *data) {
+ VertexBufferD3D9 *vertex_buffer = vertex_buffers_.Get(id);
+ if (!vertex_buffer) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return vertex_buffer->GetData(offset, size, data) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+// Creates and assigns an IndexBufferD3D9 resource.
+BufferSyncInterface::ParseError GAPID3D9::CreateIndexBuffer(
+ ResourceID id,
+ unsigned int size,
+ unsigned int flags) {
+ IndexBufferD3D9 *index_buffer = new IndexBufferD3D9(size, flags);
+ index_buffer->Create(this);
+ index_buffers_.Assign(id, index_buffer);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+// Destroys an IndexBufferD3D9 resource.
+BufferSyncInterface::ParseError GAPID3D9::DestroyIndexBuffer(ResourceID id) {
+ return index_buffers_.Destroy(id) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+// Copies the data into the IndexBufferD3D9 resource.
+BufferSyncInterface::ParseError GAPID3D9::SetIndexBufferData(
+ ResourceID id,
+ unsigned int offset,
+ unsigned int size,
+ const void *data) {
+ IndexBufferD3D9 *index_buffer = index_buffers_.Get(id);
+ if (!index_buffer) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return index_buffer->SetData(offset, size, data) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+// Copies the data from the IndexBufferD3D9 resource.
+BufferSyncInterface::ParseError GAPID3D9::GetIndexBufferData(
+ ResourceID id,
+ unsigned int offset,
+ unsigned int size,
+ void *data) {
+ IndexBufferD3D9 *index_buffer = index_buffers_.Get(id);
+ if (!index_buffer) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ return index_buffer->GetData(offset, size, data) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+// Creates and assigns a VertexStructD3D9 resource.
+BufferSyncInterface::ParseError GAPID3D9::CreateVertexStruct(
+ ResourceID id, unsigned int input_count) {
+ if (id == current_vertex_struct_) validate_streams_ = true;
+ VertexStructD3D9 *vertex_struct = new VertexStructD3D9(input_count);
+ vertex_structs_.Assign(id, vertex_struct);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+// Destroys a VertexStructD3D9 resource.
+BufferSyncInterface::ParseError GAPID3D9::DestroyVertexStruct(ResourceID id) {
+ if (id == current_vertex_struct_) validate_streams_ = true;
+ return vertex_structs_.Destroy(id) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+// Sets an input into a VertexStructD3D9 resource.
+BufferSyncInterface::ParseError GAPID3D9::SetVertexInput(
+ ResourceID vertex_struct_id,
+ unsigned int input_index,
+ ResourceID vertex_buffer_id,
+ unsigned int offset,
+ unsigned int stride,
+ vertex_struct::Type type,
+ vertex_struct::Semantic semantic,
+ unsigned int semantic_index) {
+ if (vertex_buffer_id == current_vertex_struct_) validate_streams_ = true;
+ VertexStructD3D9 *vertex_struct = vertex_structs_.Get(vertex_struct_id);
+ if (!vertex_struct || input_index >= vertex_struct->count())
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ vertex_struct->SetInput(input_index, vertex_buffer_id, offset, stride, type,
+ semantic, semantic_index);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/service/win/d3d9/geometry_d3d9.h b/o3d/command_buffer/service/win/d3d9/geometry_d3d9.h
new file mode 100644
index 0000000..4182b5b
--- /dev/null
+++ b/o3d/command_buffer/service/win/d3d9/geometry_d3d9.h
@@ -0,0 +1,126 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the definition of the D3D9 versions of geometry-related
+// resource classes.
+
+#ifndef O3D_COMMAND_BUFFER_SERVICE_WIN_D3D9_GEOMETRY_D3D9_H__
+#define O3D_COMMAND_BUFFER_SERVICE_WIN_D3D9_GEOMETRY_D3D9_H__
+
+#include <vector>
+#include <utility>
+#include "command_buffer/common/cross/gapi_interface.h"
+#include "command_buffer/service/win/d3d9/d3d9_utils.h"
+#include "command_buffer/service/cross/resource.h"
+
+namespace o3d {
+namespace command_buffer {
+
+class GAPID3D9;
+
+// D3D9 version of VertexBuffer.
+class VertexBufferD3D9 : public VertexBuffer {
+ public:
+ VertexBufferD3D9(unsigned int size, unsigned int flags)
+ : VertexBuffer(size, flags),
+ d3d_vertex_buffer_(NULL) {}
+ virtual ~VertexBufferD3D9();
+ // Creates the D3D vertex buffer.
+ void Create(GAPID3D9 *gapi);
+ // Sets the data into the D3D vertex buffer.
+ bool SetData(unsigned int offset, unsigned int size, const void *data);
+ // Gets the data from the D3D vertex buffer.
+ bool GetData(unsigned int offset, unsigned int size, void *data);
+
+ // Gets the D3D vertex buffer.
+ IDirect3DVertexBuffer9 * d3d_vertex_buffer() { return d3d_vertex_buffer_; }
+ private:
+ IDirect3DVertexBuffer9 *d3d_vertex_buffer_;
+ DISALLOW_COPY_AND_ASSIGN(VertexBufferD3D9);
+};
+
+// D3D9 version of IndexBuffer.
+class IndexBufferD3D9 : public IndexBuffer {
+ public:
+ IndexBufferD3D9(unsigned int size, unsigned int flags)
+ : IndexBuffer(size, flags),
+ d3d_index_buffer_(NULL) {}
+ virtual ~IndexBufferD3D9();
+ // Creates the D3D index buffer.
+ void Create(GAPID3D9 *gapi);
+ // Sets the data into the D3D index buffer.
+ bool SetData(unsigned int offset, unsigned int size, const void *data);
+ // Gets the data from the D3D index buffer.
+ bool GetData(unsigned int offset, unsigned int size, void *data);
+
+ // Gets the D3D index buffer.
+ IDirect3DIndexBuffer9 *d3d_index_buffer() const { return d3d_index_buffer_; }
+ private:
+ IDirect3DIndexBuffer9 *d3d_index_buffer_;
+ DISALLOW_COPY_AND_ASSIGN(IndexBufferD3D9);
+};
+
+// D3D9 version of VertexStruct.
+class VertexStructD3D9 : public VertexStruct {
+ public:
+ explicit VertexStructD3D9(unsigned int count)
+ : VertexStruct(count),
+ dirty_(true),
+ d3d_vertex_decl_(NULL) {}
+ virtual ~VertexStructD3D9();
+ // Adds an input to the vertex struct.
+ void SetInput(unsigned int input_index,
+ ResourceID vertex_buffer_id,
+ unsigned int offset,
+ unsigned int stride,
+ vertex_struct::Type type,
+ vertex_struct::Semantic semantic,
+ unsigned int semantic_index);
+ // Sets the input streams to D3D.
+ unsigned int SetStreams(GAPID3D9 *gapi);
+ private:
+ // Destroys the vertex declaration and stream map.
+ void Destroy();
+ // Compiles the vertex declaration and stream map.
+ void Compile(IDirect3DDevice9 *d3d_device);
+
+ bool dirty_;
+ typedef std::pair<ResourceID, unsigned int> StreamPair;
+ std::vector<StreamPair> streams_;
+ IDirect3DVertexDeclaration9 *d3d_vertex_decl_;
+ DISALLOW_COPY_AND_ASSIGN(VertexStructD3D9);
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_SERVICE_WIN_D3D9_GEOMETRY_D3D9_H__
diff --git a/o3d/command_buffer/service/win/d3d9/sampler_d3d9.cc b/o3d/command_buffer/service/win/d3d9/sampler_d3d9.cc
new file mode 100644
index 0000000..928d577
--- /dev/null
+++ b/o3d/command_buffer/service/win/d3d9/sampler_d3d9.cc
@@ -0,0 +1,199 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the implementation of the SamplerD3D9 class.
+
+#include "command_buffer/service/win/d3d9/gapi_d3d9.h"
+#include "command_buffer/service/win/d3d9/sampler_d3d9.h"
+#include "command_buffer/service/win/d3d9/texture_d3d9.h"
+
+namespace o3d {
+namespace command_buffer {
+
+namespace {
+
+// Converts an addressing mode to corresponding D3D values.
+D3DTEXTUREADDRESS AddressModeToD3D(sampler::AddressingMode mode) {
+ switch (mode) {
+ case sampler::WRAP:
+ return D3DTADDRESS_WRAP;
+ case sampler::MIRROR_REPEAT:
+ return D3DTADDRESS_MIRROR;
+ case sampler::CLAMP_TO_EDGE:
+ return D3DTADDRESS_CLAMP;
+ case sampler::CLAMP_TO_BORDER:
+ return D3DTADDRESS_BORDER;
+ }
+ DLOG(FATAL) << "Not reached";
+ return D3DTADDRESS_WRAP;
+}
+
+// Converts a filtering mode to corresponding D3D values.
+D3DTEXTUREFILTERTYPE FilteringModeToD3D(sampler::FilteringMode mode) {
+ switch (mode) {
+ case sampler::NONE:
+ return D3DTEXF_NONE;
+ case sampler::POINT:
+ return D3DTEXF_POINT;
+ case sampler::LINEAR:
+ return D3DTEXF_LINEAR;
+ }
+ DLOG(FATAL) << "Not reached";
+ return D3DTEXF_POINT;
+}
+
+} // anonymous namespace
+
+SamplerD3D9::SamplerD3D9()
+ : texture_id_(kInvalidResource) {
+ SetStates(sampler::CLAMP_TO_EDGE,
+ sampler::CLAMP_TO_EDGE,
+ sampler::CLAMP_TO_EDGE,
+ sampler::LINEAR,
+ sampler::LINEAR,
+ sampler::POINT,
+ 1);
+ RGBA black = {0, 0, 0, 1};
+ SetBorderColor(black);
+}
+
+bool SamplerD3D9::ApplyStates(GAPID3D9 *gapi, unsigned int unit) const {
+ DCHECK(gapi);
+ TextureD3D9 *texture = gapi->GetTexture(texture_id_);
+ if (!texture) {
+ return false;
+ }
+ IDirect3DDevice9 *d3d_device = gapi->d3d_device();
+ HR(d3d_device->SetTexture(unit, texture->d3d_base_texture()));
+ HR(d3d_device->SetSamplerState(unit, D3DSAMP_ADDRESSU, d3d_address_u_));
+ HR(d3d_device->SetSamplerState(unit, D3DSAMP_ADDRESSV, d3d_address_v_));
+ HR(d3d_device->SetSamplerState(unit, D3DSAMP_ADDRESSW, d3d_address_w_));
+ HR(d3d_device->SetSamplerState(unit, D3DSAMP_MAGFILTER, d3d_mag_filter_));
+ HR(d3d_device->SetSamplerState(unit, D3DSAMP_MINFILTER, d3d_min_filter_));
+ HR(d3d_device->SetSamplerState(unit, D3DSAMP_MIPFILTER, d3d_mip_filter_));
+ HR(d3d_device->SetSamplerState(unit, D3DSAMP_MAXANISOTROPY,
+ d3d_max_anisotropy_));
+ HR(d3d_device->SetSamplerState(unit, D3DSAMP_BORDERCOLOR, d3d_border_color_));
+ return true;
+}
+
+void SamplerD3D9::SetStates(sampler::AddressingMode addressing_u,
+ sampler::AddressingMode addressing_v,
+ sampler::AddressingMode addressing_w,
+ sampler::FilteringMode mag_filter,
+ sampler::FilteringMode min_filter,
+ sampler::FilteringMode mip_filter,
+ unsigned int max_anisotropy) {
+ // These are validated in GAPIDecoder.cc
+ DCHECK_NE(mag_filter, sampler::NONE);
+ DCHECK_NE(min_filter, sampler::NONE);
+ DCHECK_GT(max_anisotropy, 0);
+ d3d_address_u_ = AddressModeToD3D(addressing_u);
+ d3d_address_v_ = AddressModeToD3D(addressing_v);
+ d3d_address_w_ = AddressModeToD3D(addressing_w);
+ d3d_mag_filter_ = FilteringModeToD3D(mag_filter);
+ d3d_min_filter_ = FilteringModeToD3D(min_filter);
+ d3d_mip_filter_ = FilteringModeToD3D(mip_filter);
+ if (max_anisotropy > 1) {
+ d3d_mag_filter_ = D3DTEXF_ANISOTROPIC;
+ d3d_min_filter_ = D3DTEXF_ANISOTROPIC;
+ }
+ d3d_max_anisotropy_ = max_anisotropy;
+}
+
+void SamplerD3D9::SetBorderColor(const RGBA &color) {
+ d3d_border_color_ = RGBAToD3DCOLOR(color);
+}
+
+BufferSyncInterface::ParseError GAPID3D9::CreateSampler(
+ ResourceID id) {
+ // Dirty effect, because this sampler id may be used
+ DirtyEffect();
+ samplers_.Assign(id, new SamplerD3D9());
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+// Destroys the Sampler resource.
+BufferSyncInterface::ParseError GAPID3D9::DestroySampler(ResourceID id) {
+ // Dirty effect, because this sampler id may be used
+ DirtyEffect();
+ return samplers_.Destroy(id) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+BufferSyncInterface::ParseError GAPID3D9::SetSamplerStates(
+ ResourceID id,
+ sampler::AddressingMode addressing_u,
+ sampler::AddressingMode addressing_v,
+ sampler::AddressingMode addressing_w,
+ sampler::FilteringMode mag_filter,
+ sampler::FilteringMode min_filter,
+ sampler::FilteringMode mip_filter,
+ unsigned int max_anisotropy) {
+ SamplerD3D9 *sampler = samplers_.Get(id);
+ if (!sampler)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ // Dirty effect, because this sampler id may be used
+ DirtyEffect();
+ sampler->SetStates(addressing_u, addressing_v, addressing_w,
+ mag_filter, min_filter, mip_filter, max_anisotropy);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+BufferSyncInterface::ParseError GAPID3D9::SetSamplerBorderColor(
+ ResourceID id,
+ const RGBA &color) {
+ SamplerD3D9 *sampler = samplers_.Get(id);
+ if (!sampler)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ // Dirty effect, because this sampler id may be used
+ DirtyEffect();
+ sampler->SetBorderColor(color);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+BufferSyncInterface::ParseError GAPID3D9::SetSamplerTexture(
+ ResourceID id,
+ ResourceID texture_id) {
+ SamplerD3D9 *sampler = samplers_.Get(id);
+ if (!sampler)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ // Dirty effect, because this sampler id may be used
+ DirtyEffect();
+ sampler->SetTexture(texture_id);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/service/win/d3d9/sampler_d3d9.h b/o3d/command_buffer/service/win/d3d9/sampler_d3d9.h
new file mode 100644
index 0000000..e029963
--- /dev/null
+++ b/o3d/command_buffer/service/win/d3d9/sampler_d3d9.h
@@ -0,0 +1,85 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the definition of the SamplerD3D9 class, implementing
+// samplers for D3D.
+
+#ifndef O3D_COMMAND_BUFFER_SERVICE_WIN_D3D9_SAMPLER_D3D9_H_
+#define O3D_COMMAND_BUFFER_SERVICE_WIN_D3D9_SAMPLER_D3D9_H_
+
+#include "command_buffer/common/cross/gapi_interface.h"
+#include "command_buffer/service/win/d3d9/d3d9_utils.h"
+#include "command_buffer/service/cross/resource.h"
+
+namespace o3d {
+namespace command_buffer {
+
+class GAPID3D9;
+
+// D3D9 version of Sampler.
+class SamplerD3D9 : public Sampler {
+ public:
+ SamplerD3D9();
+
+ // Applies sampler states to D3D.
+ bool ApplyStates(GAPID3D9 *gapi, unsigned int unit) const;
+
+ // Sets sampler states.
+ void SetStates(sampler::AddressingMode addressing_u,
+ sampler::AddressingMode addressing_v,
+ sampler::AddressingMode addressing_w,
+ sampler::FilteringMode mag_filter,
+ sampler::FilteringMode min_filter,
+ sampler::FilteringMode mip_filter,
+ unsigned int max_anisotropy);
+
+ // Sets the border color states.
+ void SetBorderColor(const RGBA &color);
+
+ // Sets the texture.
+ void SetTexture(ResourceID texture) { texture_id_ = texture; }
+ private:
+ D3DTEXTUREADDRESS d3d_address_u_;
+ D3DTEXTUREADDRESS d3d_address_v_;
+ D3DTEXTUREADDRESS d3d_address_w_;
+ D3DTEXTUREFILTERTYPE d3d_mag_filter_;
+ D3DTEXTUREFILTERTYPE d3d_min_filter_;
+ D3DTEXTUREFILTERTYPE d3d_mip_filter_;
+ DWORD d3d_max_anisotropy_;
+ D3DCOLOR d3d_border_color_;
+ ResourceID texture_id_;
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_SERVICE_WIN_D3D9_SAMPLER_D3D9_H_
diff --git a/o3d/command_buffer/service/win/d3d9/states_d3d9.cc b/o3d/command_buffer/service/win/d3d9/states_d3d9.cc
new file mode 100644
index 0000000..4a28db9
--- /dev/null
+++ b/o3d/command_buffer/service/win/d3d9/states_d3d9.cc
@@ -0,0 +1,349 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file contains the implementation of the state-related GAPID3D9
+// functions.
+
+#include <algorithm>
+#include "command_buffer/common/cross/cmd_buffer_format.h"
+#include "command_buffer/service/win/d3d9/gapi_d3d9.h"
+
+namespace o3d {
+namespace command_buffer {
+
+namespace {
+
+// Checks that a GAPIInterface enum matches a D3D enum so that it can be
+// converted quickly.
+#define CHECK_GAPI_ENUM_MATCHES_D3D(GAPI_ENUM, D3D_ENUM) \
+ COMPILE_ASSERT(GAPIInterface::GAPI_ENUM + 1 == D3D_ENUM, \
+ GAPI_ENUM ## _plus_1_not_ ## D3D_ENUM)
+
+// Converts values from the PolygonMode enum to corresponding D3D values
+inline D3DFILLMODE PolygonModeToD3D(GAPIInterface::PolygonMode fill_mode) {
+ DCHECK_LT(fill_mode, GAPIInterface::NUM_POLYGON_MODE);
+
+ // Check that all acceptable values translate to D3D values by adding 1.
+
+ CHECK_GAPI_ENUM_MATCHES_D3D(POLYGON_MODE_POINTS, D3DFILL_POINT);
+ CHECK_GAPI_ENUM_MATCHES_D3D(POLYGON_MODE_LINES, D3DFILL_WIREFRAME);
+ CHECK_GAPI_ENUM_MATCHES_D3D(POLYGON_MODE_FILL, D3DFILL_SOLID);
+ return static_cast<D3DFILLMODE>(fill_mode + 1);
+}
+
+// Converts values from the FaceCullMode enum to corresponding D3D values
+inline D3DCULL FaceCullModeToD3D(GAPIInterface::FaceCullMode cull_mode) {
+ DCHECK_LT(cull_mode, GAPIInterface::NUM_FACE_CULL_MODE);
+
+ // Check that all acceptable values translate to D3D values by adding 1.
+ CHECK_GAPI_ENUM_MATCHES_D3D(CULL_NONE, D3DCULL_NONE);
+ CHECK_GAPI_ENUM_MATCHES_D3D(CULL_CW, D3DCULL_CW);
+ CHECK_GAPI_ENUM_MATCHES_D3D(CULL_CCW, D3DCULL_CCW);
+ return static_cast<D3DCULL>(cull_mode + 1);
+}
+
+// Converts values from the Comparison enum to corresponding D3D values
+inline D3DCMPFUNC ComparisonToD3D(GAPIInterface::Comparison comp) {
+ DCHECK_LT(comp, GAPIInterface::NUM_COMPARISON);
+
+ // Check that all acceptable values translate to D3D values by adding 1.
+ CHECK_GAPI_ENUM_MATCHES_D3D(NEVER, D3DCMP_NEVER);
+ CHECK_GAPI_ENUM_MATCHES_D3D(LESS, D3DCMP_LESS);
+ CHECK_GAPI_ENUM_MATCHES_D3D(EQUAL, D3DCMP_EQUAL);
+ CHECK_GAPI_ENUM_MATCHES_D3D(LEQUAL, D3DCMP_LESSEQUAL);
+ CHECK_GAPI_ENUM_MATCHES_D3D(GREATER, D3DCMP_GREATER);
+ CHECK_GAPI_ENUM_MATCHES_D3D(NOT_EQUAL, D3DCMP_NOTEQUAL);
+ CHECK_GAPI_ENUM_MATCHES_D3D(GEQUAL, D3DCMP_GREATEREQUAL);
+ CHECK_GAPI_ENUM_MATCHES_D3D(ALWAYS, D3DCMP_ALWAYS);
+ return static_cast<D3DCMPFUNC>(comp + 1);
+}
+
+// Converts values from the StencilOp enum to corresponding D3D values
+inline D3DSTENCILOP StencilOpToD3D(GAPIInterface::StencilOp stencil_op) {
+ DCHECK_LT(stencil_op, GAPIInterface::NUM_STENCIL_OP);
+
+ // Check that all acceptable values translate to D3D values by adding 1.
+ CHECK_GAPI_ENUM_MATCHES_D3D(KEEP, D3DSTENCILOP_KEEP);
+ CHECK_GAPI_ENUM_MATCHES_D3D(ZERO, D3DSTENCILOP_ZERO);
+ CHECK_GAPI_ENUM_MATCHES_D3D(REPLACE, D3DSTENCILOP_REPLACE);
+ CHECK_GAPI_ENUM_MATCHES_D3D(INC_NO_WRAP, D3DSTENCILOP_INCRSAT);
+ CHECK_GAPI_ENUM_MATCHES_D3D(DEC_NO_WRAP, D3DSTENCILOP_DECRSAT);
+ CHECK_GAPI_ENUM_MATCHES_D3D(INVERT, D3DSTENCILOP_INVERT);
+ CHECK_GAPI_ENUM_MATCHES_D3D(INC_WRAP, D3DSTENCILOP_INCR);
+ CHECK_GAPI_ENUM_MATCHES_D3D(DEC_WRAP, D3DSTENCILOP_DECR);
+ return static_cast<D3DSTENCILOP>(stencil_op + 1);
+}
+
+// Converts values from the BlendEq enum to corresponding D3D values
+inline D3DBLENDOP BlendEqToD3D(GAPIInterface::BlendEq blend_eq) {
+ DCHECK_LT(blend_eq, GAPIInterface::NUM_BLEND_EQ);
+ // Check that all acceptable values translate to D3D values by adding 1.
+ CHECK_GAPI_ENUM_MATCHES_D3D(BLEND_EQ_ADD, D3DBLENDOP_ADD);
+ CHECK_GAPI_ENUM_MATCHES_D3D(BLEND_EQ_SUB, D3DBLENDOP_SUBTRACT);
+ CHECK_GAPI_ENUM_MATCHES_D3D(BLEND_EQ_REV_SUB, D3DBLENDOP_REVSUBTRACT);
+ CHECK_GAPI_ENUM_MATCHES_D3D(BLEND_EQ_MIN, D3DBLENDOP_MIN);
+ CHECK_GAPI_ENUM_MATCHES_D3D(BLEND_EQ_MAX, D3DBLENDOP_MAX);
+ return static_cast<D3DBLENDOP>(blend_eq + 1);
+}
+
+// Converts values from the BlendFunc enum to corresponding D3D values
+D3DBLEND BlendFuncToD3D(GAPIInterface::BlendFunc blend_func) {
+ // The D3DBLEND enum values don't map 1-to-1 to BlendFunc, so we use a switch
+ // here.
+ switch (blend_func) {
+ case GAPIInterface::BLEND_FUNC_ZERO:
+ return D3DBLEND_ZERO;
+ case GAPIInterface::BLEND_FUNC_ONE:
+ return D3DBLEND_ONE;
+ case GAPIInterface::BLEND_FUNC_SRC_COLOR:
+ return D3DBLEND_SRCCOLOR;
+ case GAPIInterface::BLEND_FUNC_INV_SRC_COLOR:
+ return D3DBLEND_INVSRCCOLOR;
+ case GAPIInterface::BLEND_FUNC_SRC_ALPHA:
+ return D3DBLEND_SRCALPHA;
+ case GAPIInterface::BLEND_FUNC_INV_SRC_ALPHA:
+ return D3DBLEND_INVSRCALPHA;
+ case GAPIInterface::BLEND_FUNC_DST_ALPHA:
+ return D3DBLEND_DESTALPHA;
+ case GAPIInterface::BLEND_FUNC_INV_DST_ALPHA:
+ return D3DBLEND_INVDESTALPHA;
+ case GAPIInterface::BLEND_FUNC_DST_COLOR:
+ return D3DBLEND_DESTCOLOR;
+ case GAPIInterface::BLEND_FUNC_INV_DST_COLOR:
+ return D3DBLEND_INVDESTCOLOR;
+ case GAPIInterface::BLEND_FUNC_SRC_ALPHA_SATUTRATE:
+ return D3DBLEND_SRCALPHASAT;
+ case GAPIInterface::BLEND_FUNC_BLEND_COLOR:
+ return D3DBLEND_BLENDFACTOR;
+ case GAPIInterface::BLEND_FUNC_INV_BLEND_COLOR:
+ return D3DBLEND_INVBLENDFACTOR;
+ default:
+ DLOG(FATAL) << "Invalid BlendFunc";
+ return D3DBLEND_ZERO;
+ }
+}
+
+// Decodes stencil test function and operations from the bitfield.
+void DecodeStencilFuncOps(Uint32 params,
+ GAPIInterface::Comparison *func,
+ GAPIInterface::StencilOp *pass,
+ GAPIInterface::StencilOp *fail,
+ GAPIInterface::StencilOp *zfail) {
+ namespace cmd = set_stencil_test;
+ // Sanity check. The value has already been tested in
+ // GAPIDecoder::DecodeSetStencilTest in gapi_decoder.cc.
+ DCHECK_EQ(cmd::Unused1::Get(params), 0);
+ // Check that the bitmask get cannot generate values outside of the allowed
+ // range.
+ COMPILE_ASSERT(cmd::CWFunc::kMask < GAPIInterface::NUM_COMPARISON,
+ set_stencil_test_CWFunc_may_produce_invalid_values);
+ *func = static_cast<GAPIInterface::Comparison>(cmd::CWFunc::Get(params));
+
+ COMPILE_ASSERT(cmd::CWPassOp::kMask < GAPIInterface::NUM_STENCIL_OP,
+ set_stencil_test_CWPassOp_may_produce_invalid_values);
+ *pass = static_cast<GAPIInterface::StencilOp>(cmd::CWPassOp::Get(params));
+
+ COMPILE_ASSERT(cmd::CWFailOp::kMask < GAPIInterface::NUM_STENCIL_OP,
+ set_stencil_test_CWFailOp_may_produce_invalid_values);
+ *fail = static_cast<GAPIInterface::StencilOp>(cmd::CWFailOp::Get(params));
+
+ COMPILE_ASSERT(cmd::CWZFailOp::kMask < GAPIInterface::NUM_STENCIL_OP,
+ set_stencil_test_CWZFailOp_may_produce_invalid_values);
+ *zfail = static_cast<GAPIInterface::StencilOp>(cmd::CWZFailOp::Get(params));
+}
+
+} // anonymous namespace
+
+void GAPID3D9::SetScissor(bool enable,
+ unsigned int x,
+ unsigned int y,
+ unsigned int width,
+ unsigned int height) {
+ HR(d3d_device_->SetRenderState(D3DRS_SCISSORTESTENABLE,
+ enable ? TRUE : FALSE));
+ RECT rect = {x, y, x + width, y + height};
+ HR(d3d_device_->SetScissorRect(&rect));
+}
+
+void GAPID3D9::SetPolygonOffset(float slope_factor, float units) {
+ HR(d3d_device_->SetRenderState(D3DRS_SLOPESCALEDEPTHBIAS,
+ FloatAsDWORD(slope_factor)));
+ // TODO: this value is hard-coded currently because we only create a
+ // 24-bit depth buffer. Move this to a member of GAPID3D9 if this changes.
+ const float kUnitScale = 1.f / (1 << 24);
+ HR(d3d_device_->SetRenderState(D3DRS_DEPTHBIAS,
+ FloatAsDWORD(units * kUnitScale)));
+}
+
+void GAPID3D9::SetPointLineRaster(bool line_smooth,
+ bool point_sprite,
+ float point_size) {
+ HR(d3d_device_->SetRenderState(D3DRS_ANTIALIASEDLINEENABLE,
+ line_smooth ? TRUE : FALSE));
+ HR(d3d_device_->SetRenderState(D3DRS_POINTSPRITEENABLE,
+ point_sprite ? TRUE : FALSE));
+ HR(d3d_device_->SetRenderState(D3DRS_POINTSIZE,
+ FloatAsDWORD(point_size)));
+}
+
+void GAPID3D9::SetPolygonRaster(PolygonMode fill_mode,
+ FaceCullMode cull_mode) {
+ HR(d3d_device_->SetRenderState(D3DRS_FILLMODE, PolygonModeToD3D(fill_mode)));
+ HR(d3d_device_->SetRenderState(D3DRS_CULLMODE, FaceCullModeToD3D(cull_mode)));
+}
+
+void GAPID3D9::SetAlphaTest(bool enable,
+ float reference,
+ Comparison comp) {
+ HR(d3d_device_->SetRenderState(D3DRS_ALPHABLENDENABLE,
+ enable ? TRUE : FALSE));
+ HR(d3d_device_->SetRenderState(D3DRS_ALPHAREF,
+ FloatToClampedByte(reference)));
+ HR(d3d_device_->SetRenderState(D3DRS_ALPHAFUNC, ComparisonToD3D(comp)));
+}
+
+void GAPID3D9::SetDepthTest(bool enable,
+ bool write_enable,
+ Comparison comp) {
+ HR(d3d_device_->SetRenderState(D3DRS_ZENABLE,
+ enable ? TRUE : FALSE));
+ HR(d3d_device_->SetRenderState(D3DRS_ZWRITEENABLE,
+ write_enable ? TRUE : FALSE));
+ HR(d3d_device_->SetRenderState(D3DRS_ZFUNC, ComparisonToD3D(comp)));
+}
+
+void GAPID3D9::SetStencilTest(bool enable,
+ bool separate_ccw,
+ unsigned int write_mask,
+ unsigned int compare_mask,
+ unsigned int ref,
+ Uint32 func_ops) {
+ HR(d3d_device_->SetRenderState(D3DRS_STENCILENABLE,
+ enable ? TRUE : FALSE));
+ HR(d3d_device_->SetRenderState(D3DRS_STENCILWRITEMASK, write_mask));
+ HR(d3d_device_->SetRenderState(D3DRS_STENCILMASK, compare_mask));
+ HR(d3d_device_->SetRenderState(D3DRS_STENCILREF, ref));
+
+ Comparison func;
+ StencilOp pass;
+ StencilOp fail;
+ StencilOp zfail;
+ DecodeStencilFuncOps(func_ops, &func, &pass, &fail, &zfail);
+ HR(d3d_device_->SetRenderState(D3DRS_STENCILFUNC,
+ ComparisonToD3D(func)));
+ HR(d3d_device_->SetRenderState(D3DRS_STENCILPASS,
+ StencilOpToD3D(pass)));
+ HR(d3d_device_->SetRenderState(D3DRS_STENCILFAIL,
+ StencilOpToD3D(fail)));
+ HR(d3d_device_->SetRenderState(D3DRS_STENCILZFAIL,
+ StencilOpToD3D(zfail)));
+
+ if (separate_ccw) {
+ HR(d3d_device_->SetRenderState(D3DRS_TWOSIDEDSTENCILMODE, TRUE));
+ // Check that the definition of the counter-clockwise func/ops match the
+ // clockwise ones, just shifted by 16 bits, so that we can use
+ // DecodeStencilFuncOps on both of them.
+#define CHECK_CCW_MATCHES_CW(FIELD) \
+ COMPILE_ASSERT(set_stencil_test::CW ## FIELD::kLength == \
+ set_stencil_test::CCW ## FIELD::kLength, \
+ CCW ## FIELD ## _length_does_not_match_ ## CW ## FIELD); \
+ COMPILE_ASSERT(set_stencil_test::CW ## FIELD::kShift + 16 == \
+ set_stencil_test::CCW ## FIELD::kShift, \
+ CCW ## FIELD ## _shift_does_not_match_ ## CW ## FIELD)
+ CHECK_CCW_MATCHES_CW(Func);
+ CHECK_CCW_MATCHES_CW(PassOp);
+ CHECK_CCW_MATCHES_CW(FailOp);
+ CHECK_CCW_MATCHES_CW(ZFailOp);
+#undef CHECK_CCW_MATCHES_CW
+ // Extract upper 16 bits.
+ Uint32 ccw_func_ops = BitField<16, 16>::Get(func_ops);
+
+ DecodeStencilFuncOps(ccw_func_ops, &func, &pass, &fail, &zfail);
+ HR(d3d_device_->SetRenderState(D3DRS_CCW_STENCILFUNC,
+ ComparisonToD3D(func)));
+ HR(d3d_device_->SetRenderState(D3DRS_CCW_STENCILPASS,
+ StencilOpToD3D(pass)));
+ HR(d3d_device_->SetRenderState(D3DRS_CCW_STENCILFAIL,
+ StencilOpToD3D(fail)));
+ HR(d3d_device_->SetRenderState(D3DRS_CCW_STENCILZFAIL,
+ StencilOpToD3D(zfail)));
+ } else {
+ HR(d3d_device_->SetRenderState(D3DRS_TWOSIDEDSTENCILMODE, FALSE));
+ }
+}
+
+void GAPID3D9::SetColorWrite(bool red,
+ bool green,
+ bool blue,
+ bool alpha,
+ bool dither) {
+ Uint32 mask = red ? D3DCOLORWRITEENABLE_RED : 0;
+ mask |= green ? D3DCOLORWRITEENABLE_GREEN : 0;
+ mask |= blue ? D3DCOLORWRITEENABLE_BLUE : 0;
+ mask |= alpha ? D3DCOLORWRITEENABLE_ALPHA : 0;
+ HR(d3d_device_->SetRenderState(D3DRS_COLORWRITEENABLE, mask));
+ HR(d3d_device_->SetRenderState(D3DRS_DITHERENABLE, dither ? TRUE : FALSE));
+}
+
+void GAPID3D9::SetBlending(bool enable,
+ bool separate_alpha,
+ BlendEq color_eq,
+ BlendFunc color_src_func,
+ BlendFunc color_dst_func,
+ BlendEq alpha_eq,
+ BlendFunc alpha_src_func,
+ BlendFunc alpha_dst_func) {
+ HR(d3d_device_->SetRenderState(D3DRS_ALPHABLENDENABLE,
+ enable ? TRUE : FALSE));
+ HR(d3d_device_->SetRenderState(D3DRS_BLENDOP, BlendEqToD3D(color_eq)));
+ HR(d3d_device_->SetRenderState(D3DRS_SRCBLEND,
+ BlendFuncToD3D(color_src_func)));
+ HR(d3d_device_->SetRenderState(D3DRS_DESTBLEND,
+ BlendFuncToD3D(color_dst_func)));
+ if (separate_alpha) {
+ HR(d3d_device_->SetRenderState(D3DRS_SEPARATEALPHABLENDENABLE, TRUE));
+ HR(d3d_device_->SetRenderState(D3DRS_BLENDOP, BlendEqToD3D(alpha_eq)));
+ HR(d3d_device_->SetRenderState(D3DRS_SRCBLEND,
+ BlendFuncToD3D(alpha_src_func)));
+ HR(d3d_device_->SetRenderState(D3DRS_DESTBLEND,
+ BlendFuncToD3D(alpha_dst_func)));
+ } else {
+ HR(d3d_device_->SetRenderState(D3DRS_SEPARATEALPHABLENDENABLE, FALSE));
+ }
+}
+
+void GAPID3D9::SetBlendingColor(const RGBA &color) {
+ HR(d3d_device_->SetRenderState(D3DRS_BLENDFACTOR, RGBAToD3DCOLOR(color)));
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/service/win/d3d9/texture_d3d9.cc b/o3d/command_buffer/service/win/d3d9/texture_d3d9.cc
new file mode 100644
index 0000000..cbd8cf5
--- /dev/null
+++ b/o3d/command_buffer/service/win/d3d9/texture_d3d9.cc
@@ -0,0 +1,636 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+// This file implements the D3D9 versions of the texture resources, as well as
+// the related GAPID3D9 function implementations.
+
+#include "command_buffer/service/win/d3d9/gapi_d3d9.h"
+#include "command_buffer/service/win/d3d9/texture_d3d9.h"
+
+namespace o3d {
+namespace command_buffer {
+
+// Converts a texture format to a D3D texture format.
+static D3DFORMAT D3DFormat(texture::Format format) {
+ switch (format) {
+ case texture::XRGB8: return D3DFMT_X8R8G8B8;
+ case texture::ARGB8: return D3DFMT_A8R8G8B8;
+ case texture::ABGR16F: return D3DFMT_A16B16G16R16F;
+ case texture::DXT1: return D3DFMT_DXT1;
+ default: return D3DFMT_UNKNOWN;
+ };
+}
+
+// Converts a cube map face to a D3D face.
+static D3DCUBEMAP_FACES D3DFace(texture::Face face) {
+ switch (face) {
+ case texture::FACE_POSITIVE_X:
+ return D3DCUBEMAP_FACE_POSITIVE_X;
+ case texture::FACE_NEGATIVE_X:
+ return D3DCUBEMAP_FACE_NEGATIVE_X;
+ case texture::FACE_POSITIVE_Y:
+ return D3DCUBEMAP_FACE_POSITIVE_Y;
+ case texture::FACE_NEGATIVE_Y:
+ return D3DCUBEMAP_FACE_NEGATIVE_Y;
+ case texture::FACE_POSITIVE_Z:
+ return D3DCUBEMAP_FACE_POSITIVE_Z;
+ case texture::FACE_NEGATIVE_Z:
+ return D3DCUBEMAP_FACE_NEGATIVE_Z;
+ }
+ LOG(FATAL) << "Not reached.";
+ return D3DCUBEMAP_FACE_POSITIVE_X;
+}
+
+// Texture 2D functions
+
+// Destroys the 2D texture, releasing the D3D texture, and its shadow if any.
+Texture2DD3D9::~Texture2DD3D9() {
+ DCHECK(d3d_texture_);
+ d3d_texture_->Release();
+ d3d_texture_ = NULL;
+ if (d3d_shadow_) {
+ d3d_shadow_->Release();
+ d3d_shadow_ = NULL;
+ }
+}
+
+// Creates a 2D texture. For dynamic textures, create it in the default pool,
+// and a shadow version in the system memory pool (that we can lock). For
+// regular texture, simply create one in the managed pool.
+Texture2DD3D9 *Texture2DD3D9::Create(GAPID3D9 *gapi,
+ unsigned int width,
+ unsigned int height,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags) {
+ DCHECK_GT(width, 0);
+ DCHECK_GT(height, 0);
+ DCHECK_GT(levels, 0);
+ D3DFORMAT d3d_format = D3DFormat(format);
+ IDirect3DDevice9 *device = gapi->d3d_device();
+ if (flags & texture::DYNAMIC) {
+ IDirect3DTexture9 *d3d_texture = NULL;
+ HRESULT result = device->CreateTexture(width, height, levels,
+ D3DUSAGE_DYNAMIC, d3d_format,
+ D3DPOOL_DEFAULT, &d3d_texture,
+ NULL);
+ if (result != D3D_OK) {
+ LOG(ERROR) << "DirectX error when calling CreateTexture: "
+ << DXGetErrorStringA(result);
+ return NULL;
+ }
+ IDirect3DTexture9 *d3d_shadow = NULL;
+ result = device->CreateTexture(width, height, levels, D3DUSAGE_DYNAMIC,
+ d3d_format, D3DPOOL_SYSTEMMEM, &d3d_shadow,
+ NULL);
+ if (result != D3D_OK) {
+ LOG(ERROR) << "DirectX error when calling CreateTexture: "
+ << DXGetErrorStringA(result);
+ d3d_texture->Release();
+ return NULL;
+ }
+ return new Texture2DD3D9(levels, format, flags, width, height, d3d_texture,
+ d3d_shadow);
+ } else {
+ IDirect3DTexture9 *d3d_texture = NULL;
+ HRESULT result = device->CreateTexture(width, height, levels, 0, d3d_format,
+ D3DPOOL_MANAGED, &d3d_texture, NULL);
+ if (result != D3D_OK) {
+ LOG(ERROR) << "DirectX error when calling CreateTexture: "
+ << DXGetErrorStringA(result);
+ return NULL;
+ }
+ return new Texture2DD3D9(levels, format, flags, width, height, d3d_texture,
+ NULL);
+ }
+}
+
+// Sets the data in the texture, using LockRect()/UnlockRect(). For dynamic
+// textures, it copies the data to the shadow texture, then updates the actual
+// texture. For regular texture, it directly modifies the actual texture.
+bool Texture2DD3D9::SetData(GAPID3D9 *gapi,
+ const Volume &volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ const void *data) {
+ DCHECK(d3d_texture_);
+ IDirect3DTexture9 *lock_texture = d3d_shadow_ ? d3d_shadow_ : d3d_texture_;
+
+ MipLevelInfo mip_info;
+ MakeMipLevelInfo(&mip_info, format(), width_, height_, 1, level);
+ TransferInfo src_transfer_info;
+ MakeTransferInfo(&src_transfer_info, mip_info, volume, row_pitch,
+ slice_pitch);
+ if (!CheckVolume(mip_info, volume) || level >= levels() ||
+ size < src_transfer_info.total_size)
+ return false;
+
+ bool full_rect = IsFullVolume(mip_info, volume);
+ D3DLOCKED_RECT locked_rect;
+ RECT rect = {volume.x, volume.y, volume.x+volume.width,
+ volume.y+volume.height};
+ DWORD lock_flags =
+ full_rect && (flags() & texture::DYNAMIC) ? D3DLOCK_DISCARD : 0;
+ HR(lock_texture->LockRect(level, &locked_rect, full_rect ? NULL : &rect,
+ lock_flags));
+
+ TransferInfo dst_transfer_info;
+ MakeTransferInfo(&dst_transfer_info, mip_info, volume, locked_rect.Pitch,
+ slice_pitch);
+ TransferVolume(volume, mip_info, dst_transfer_info, locked_rect.pBits,
+ src_transfer_info, data);
+
+ HR(lock_texture->UnlockRect(level));
+ if (d3d_shadow_) {
+ HR(gapi->d3d_device()->UpdateTexture(d3d_shadow_, d3d_texture_));
+ }
+ return true;
+}
+
+// Gets the data from the texture, using LockRect()/UnlockRect(). For dynamic
+// textures, it gets the data from the shadow texture, For regular texture, it
+// gets it directly from the actual texture.
+bool Texture2DD3D9::GetData(GAPID3D9 *gapi,
+ const Volume &volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ void *data) {
+ DCHECK(d3d_texture_);
+ IDirect3DTexture9 *lock_texture = d3d_shadow_ ? d3d_shadow_ : d3d_texture_;
+
+ MipLevelInfo mip_info;
+ MakeMipLevelInfo(&mip_info, format(), width_, height_, 1, level);
+ TransferInfo dst_transfer_info;
+ MakeTransferInfo(&dst_transfer_info, mip_info, volume, row_pitch,
+ slice_pitch);
+ if (!CheckVolume(mip_info, volume) || level >= levels() ||
+ size < dst_transfer_info.total_size)
+ return false;
+
+ bool full_rect = IsFullVolume(mip_info, volume);
+ D3DLOCKED_RECT locked_rect;
+ RECT rect = {volume.x, volume.y, volume.x+volume.width,
+ volume.y+volume.height};
+ DWORD lock_flags = D3DLOCK_READONLY;
+ HR(lock_texture->LockRect(level, &locked_rect, full_rect ? NULL : &rect,
+ lock_flags));
+ TransferInfo src_transfer_info;
+ MakeTransferInfo(&src_transfer_info, mip_info, volume, locked_rect.Pitch,
+ slice_pitch);
+ TransferVolume(volume, mip_info, dst_transfer_info, data,
+ src_transfer_info, locked_rect.pBits);
+ HR(lock_texture->UnlockRect(level));
+ return true;
+}
+
+// Texture 3D functions
+
+// Destroys the 3D texture.
+Texture3DD3D9::~Texture3DD3D9() {
+ DCHECK(d3d_texture_);
+ d3d_texture_->Release();
+ d3d_texture_ = NULL;
+ if (d3d_shadow_) {
+ d3d_shadow_->Release();
+ d3d_shadow_ = NULL;
+ }
+}
+
+// Creates a 3D texture. For dynamic textures, create it in the default pool,
+// and a shadow version in the system memory pool (that we can lock). For
+// regular texture, simply create one in the managed pool.
+Texture3DD3D9 *Texture3DD3D9::Create(GAPID3D9 *gapi,
+ unsigned int width,
+ unsigned int height,
+ unsigned int depth,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags) {
+ DCHECK_GT(width, 0);
+ DCHECK_GT(height, 0);
+ DCHECK_GT(depth, 0);
+ DCHECK_GT(levels, 0);
+ D3DFORMAT d3d_format = D3DFormat(format);
+ IDirect3DDevice9 *device = gapi->d3d_device();
+ if (flags & texture::DYNAMIC) {
+ IDirect3DVolumeTexture9 *d3d_texture = NULL;
+ HRESULT result = device->CreateVolumeTexture(width, height, depth, levels,
+ D3DUSAGE_DYNAMIC, d3d_format,
+ D3DPOOL_DEFAULT, &d3d_texture,
+ NULL);
+ if (result != D3D_OK) {
+ LOG(ERROR) << "DirectX error when calling CreateTexture: "
+ << DXGetErrorStringA(result);
+ return NULL;
+ }
+ IDirect3DVolumeTexture9 *d3d_shadow = NULL;
+ result = device->CreateVolumeTexture(width, height, depth, levels,
+ D3DUSAGE_DYNAMIC, d3d_format,
+ D3DPOOL_SYSTEMMEM, &d3d_shadow, NULL);
+ if (result != D3D_OK) {
+ LOG(ERROR) << "DirectX error when calling CreateTexture: "
+ << DXGetErrorStringA(result);
+ d3d_texture->Release();
+ return NULL;
+ }
+ return new Texture3DD3D9(levels, format, flags, width, height, depth,
+ d3d_texture, d3d_shadow);
+ } else {
+ IDirect3DVolumeTexture9 *d3d_texture = NULL;
+ HRESULT result = device->CreateVolumeTexture(width, height, depth, levels,
+ D3DUSAGE_DYNAMIC, d3d_format,
+ D3DPOOL_MANAGED, &d3d_texture,
+ NULL);
+ if (result != D3D_OK) {
+ LOG(ERROR) << "DirectX error when calling CreateTexture: "
+ << DXGetErrorStringA(result);
+ return NULL;
+ }
+ return new Texture3DD3D9(levels, format, flags, width, height, depth,
+ d3d_texture, NULL);
+ }
+}
+
+// Sets the data in the texture, using LockBox()/UnlockBox(). For dynamic
+// textures, it copies the data to the shadow texture, then updates the actual
+// texture. For regular texture, it directly modifies the actual texture.
+bool Texture3DD3D9::SetData(GAPID3D9 *gapi,
+ const Volume &volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ const void *data) {
+ DCHECK(d3d_texture_);
+ IDirect3DVolumeTexture9 *lock_texture =
+ d3d_shadow_ ? d3d_shadow_ : d3d_texture_;
+
+ MipLevelInfo mip_info;
+ MakeMipLevelInfo(&mip_info, format(), width_, height_, depth_, level);
+ TransferInfo src_transfer_info;
+ MakeTransferInfo(&src_transfer_info, mip_info, volume, row_pitch,
+ slice_pitch);
+ if (!CheckVolume(mip_info, volume) || level >= levels() ||
+ size < src_transfer_info.total_size)
+ return false;
+
+ bool full_box = IsFullVolume(mip_info, volume);
+ D3DLOCKED_BOX locked_box;
+ D3DBOX box = {volume.x, volume.y, volume.z, volume.x+volume.width,
+ volume.y+volume.height, volume.z+volume.depth};
+ DWORD lock_flags =
+ full_box && (flags() & texture::DYNAMIC) ? D3DLOCK_DISCARD : 0;
+ HR(lock_texture->LockBox(level, &locked_box, full_box ? NULL : &box,
+ lock_flags));
+
+ TransferInfo dst_transfer_info;
+ MakeTransferInfo(&dst_transfer_info, mip_info, volume, locked_box.RowPitch,
+ locked_box.SlicePitch);
+ TransferVolume(volume, mip_info, dst_transfer_info, locked_box.pBits,
+ src_transfer_info, data);
+
+ HR(lock_texture->UnlockBox(level));
+ if (d3d_shadow_) {
+ HR(gapi->d3d_device()->UpdateTexture(d3d_shadow_, d3d_texture_));
+ }
+ return true;
+}
+
+// Gets the data from the texture, using LockBox()/UnlockBox(). For dynamic
+// textures, it gets the data from the shadow texture, For regular texture, it
+// gets it directly from the actual texture.
+bool Texture3DD3D9::GetData(GAPID3D9 *gapi,
+ const Volume &volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ void *data) {
+ DCHECK(d3d_texture_);
+ IDirect3DVolumeTexture9 *lock_texture =
+ d3d_shadow_ ? d3d_shadow_ : d3d_texture_;
+
+ MipLevelInfo mip_info;
+ MakeMipLevelInfo(&mip_info, format(), width_, height_, depth_, level);
+ TransferInfo dst_transfer_info;
+ MakeTransferInfo(&dst_transfer_info, mip_info, volume, row_pitch,
+ slice_pitch);
+ if (!CheckVolume(mip_info, volume) || level >= levels() ||
+ size < dst_transfer_info.total_size)
+ return false;
+
+ bool full_box = IsFullVolume(mip_info, volume);
+ D3DLOCKED_BOX locked_box;
+ D3DBOX box = {volume.x, volume.y, volume.z, volume.x+volume.width,
+ volume.y+volume.height, volume.z+volume.depth};
+ DWORD lock_flags = D3DLOCK_READONLY;
+ HR(lock_texture->LockBox(level, &locked_box, full_box ? NULL : &box,
+ lock_flags));
+ TransferInfo src_transfer_info;
+ MakeTransferInfo(&src_transfer_info, mip_info, volume, locked_box.RowPitch,
+ locked_box.SlicePitch);
+ TransferVolume(volume, mip_info, dst_transfer_info, data,
+ src_transfer_info, locked_box.pBits);
+ HR(lock_texture->UnlockBox(level));
+ return true;
+}
+
+// Texture Cube functions.
+
+// Destroys the cube map texture, releasing the D3D texture, and its shadow if
+// any.
+TextureCubeD3D9::~TextureCubeD3D9() {
+ DCHECK(d3d_texture_);
+ d3d_texture_->Release();
+ d3d_texture_ = NULL;
+ if (d3d_shadow_) {
+ d3d_shadow_->Release();
+ d3d_shadow_ = NULL;
+ }
+}
+
+// Creates a cube map texture. For dynamic textures, create it in the default
+// pool, and a shadow version in the system memory pool (that we can lock). For
+// regular texture, simply create one in the managed pool.
+TextureCubeD3D9 *TextureCubeD3D9::Create(GAPID3D9 *gapi,
+ unsigned int side,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags) {
+ DCHECK_GT(side, 0);
+ DCHECK_GT(levels, 0);
+ D3DFORMAT d3d_format = D3DFormat(format);
+ IDirect3DDevice9 *device = gapi->d3d_device();
+ if (flags & texture::DYNAMIC) {
+ IDirect3DCubeTexture9 *d3d_texture = NULL;
+ HRESULT result = device->CreateCubeTexture(side, levels, D3DUSAGE_DYNAMIC,
+ d3d_format, D3DPOOL_DEFAULT,
+ &d3d_texture, NULL);
+ if (result != D3D_OK) {
+ LOG(ERROR) << "DirectX error when calling CreateTexture: "
+ << DXGetErrorStringA(result);
+ return NULL;
+ }
+ IDirect3DCubeTexture9 *d3d_shadow = NULL;
+ result = device->CreateCubeTexture(side, levels, D3DUSAGE_DYNAMIC,
+ d3d_format, D3DPOOL_SYSTEMMEM,
+ &d3d_shadow, NULL);
+ if (result != D3D_OK) {
+ LOG(ERROR) << "DirectX error when calling CreateTexture: "
+ << DXGetErrorStringA(result);
+ d3d_texture->Release();
+ return NULL;
+ }
+ return new TextureCubeD3D9(levels, format, flags, side, d3d_texture,
+ d3d_shadow);
+ } else {
+ IDirect3DCubeTexture9 *d3d_texture = NULL;
+ HRESULT result = device->CreateCubeTexture(side, levels, 0, d3d_format,
+ D3DPOOL_MANAGED, &d3d_texture,
+ NULL);
+ if (result != D3D_OK) {
+ LOG(ERROR) << "DirectX error when calling CreateTexture: "
+ << DXGetErrorStringA(result);
+ return NULL;
+ }
+ return new TextureCubeD3D9(levels, format, flags, side, d3d_texture, NULL);
+ }
+}
+
+// Sets the data in the texture, using LockRect()/UnlockRect(). For dynamic
+// textures, it copies the data to the shadow texture, then updates the actual
+// texture. For regular texture, it directly modifies the actual texture.
+bool TextureCubeD3D9::SetData(GAPID3D9 *gapi,
+ const Volume &volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ const void *data) {
+ DCHECK(d3d_texture_);
+ IDirect3DCubeTexture9 *lock_texture =
+ d3d_shadow_ ? d3d_shadow_ : d3d_texture_;
+ MipLevelInfo mip_info;
+ MakeMipLevelInfo(&mip_info, format(), side_, side_, 1, level);
+ TransferInfo src_transfer_info;
+ MakeTransferInfo(&src_transfer_info, mip_info, volume, row_pitch,
+ slice_pitch);
+ if (!CheckVolume(mip_info, volume) || level >= levels() ||
+ size < src_transfer_info.total_size)
+ return false;
+
+ D3DCUBEMAP_FACES d3d_face = D3DFace(face);
+ bool full_rect = IsFullVolume(mip_info, volume);
+ D3DLOCKED_RECT locked_rect;
+ RECT rect = {volume.x, volume.y, volume.x+volume.width,
+ volume.y+volume.height};
+ DWORD lock_flags =
+ full_rect && (flags() & texture::DYNAMIC) ? D3DLOCK_DISCARD : 0;
+ HR(lock_texture->LockRect(d3d_face, level, &locked_rect,
+ full_rect ? NULL : &rect, lock_flags));
+
+ TransferInfo dst_transfer_info;
+ MakeTransferInfo(&dst_transfer_info, mip_info, volume, locked_rect.Pitch,
+ slice_pitch);
+ TransferVolume(volume, mip_info, dst_transfer_info, locked_rect.pBits,
+ src_transfer_info, data);
+
+ HR(lock_texture->UnlockRect(d3d_face, level));
+ if (d3d_shadow_) {
+ HR(gapi->d3d_device()->UpdateTexture(d3d_shadow_, d3d_texture_));
+ }
+ return true;
+}
+
+// Gets the data from the texture, using LockRect()/UnlockRect(). For dynamic
+// textures, it gets the data from the shadow texture, For regular texture, it
+// gets it directly from the actual texture.
+bool TextureCubeD3D9::GetData(GAPID3D9 *gapi,
+ const Volume &volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ void *data) {
+ DCHECK(d3d_texture_);
+ IDirect3DCubeTexture9 *lock_texture =
+ d3d_shadow_ ? d3d_shadow_ : d3d_texture_;
+
+ MipLevelInfo mip_info;
+ MakeMipLevelInfo(&mip_info, format(), side_, side_, 1, level);
+ TransferInfo dst_transfer_info;
+ MakeTransferInfo(&dst_transfer_info, mip_info, volume, row_pitch,
+ slice_pitch);
+ if (!CheckVolume(mip_info, volume) || level >= levels() ||
+ size < dst_transfer_info.total_size)
+ return false;
+
+ D3DCUBEMAP_FACES d3d_face = D3DFace(face);
+ bool full_rect = IsFullVolume(mip_info, volume);
+ D3DLOCKED_RECT locked_rect;
+ RECT rect = {volume.x, volume.y, volume.x+volume.width,
+ volume.y+volume.height};
+ DWORD lock_flags = D3DLOCK_READONLY;
+ HR(lock_texture->LockRect(d3d_face, level, &locked_rect,
+ full_rect ? NULL : &rect, lock_flags));
+ TransferInfo src_transfer_info;
+ MakeTransferInfo(&src_transfer_info, mip_info, volume, locked_rect.Pitch,
+ slice_pitch);
+ TransferVolume(volume, mip_info, dst_transfer_info, data,
+ src_transfer_info, locked_rect.pBits);
+ HR(lock_texture->UnlockRect(d3d_face, level));
+ return true;
+}
+// GAPID3D9 functions.
+
+// Destroys a texture resource.
+BufferSyncInterface::ParseError GAPID3D9::DestroyTexture(ResourceID id) {
+ // Dirty effect, because this texture id may be used
+ DirtyEffect();
+ return textures_.Destroy(id) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+// Creates a 2D texture resource.
+BufferSyncInterface::ParseError GAPID3D9::CreateTexture2D(
+ ResourceID id,
+ unsigned int width,
+ unsigned int height,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags) {
+ Texture2DD3D9 *texture = Texture2DD3D9::Create(this, width, height, levels,
+ format, flags);
+ if (!texture) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ // Dirty effect, because this texture id may be used
+ DirtyEffect();
+ textures_.Assign(id, texture);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+// Creates a 3D texture resource.
+BufferSyncInterface::ParseError GAPID3D9::CreateTexture3D(
+ ResourceID id,
+ unsigned int width,
+ unsigned int height,
+ unsigned int depth,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags) {
+ Texture3DD3D9 *texture = Texture3DD3D9::Create(this, width, height, depth,
+ levels, format, flags);
+ if (!texture) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ // Dirty effect, because this texture id may be used
+ DirtyEffect();
+ textures_.Assign(id, texture);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+// Creates a cube map texture resource.
+BufferSyncInterface::ParseError GAPID3D9::CreateTextureCube(
+ ResourceID id,
+ unsigned int side,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags) {
+ TextureCubeD3D9 *texture = TextureCubeD3D9::Create(this, side, levels,
+ format, flags);
+ if (!texture) return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ // Dirty effect, because this texture id may be used
+ DirtyEffect();
+ textures_.Assign(id, texture);
+ return BufferSyncInterface::PARSE_NO_ERROR;
+}
+
+// Copies the data into a texture resource.
+BufferSyncInterface::ParseError GAPID3D9::SetTextureData(
+ ResourceID id,
+ unsigned int x,
+ unsigned int y,
+ unsigned int z,
+ unsigned int width,
+ unsigned int height,
+ unsigned int depth,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ const void *data) {
+ TextureD3D9 *texture = textures_.Get(id);
+ if (!texture)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ Volume volume = {x, y, z, width, height, depth};
+ return texture->SetData(this, volume, level, face, row_pitch, slice_pitch,
+ size, data) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+// Copies the data from a texture resource.
+BufferSyncInterface::ParseError GAPID3D9::GetTextureData(
+ ResourceID id,
+ unsigned int x,
+ unsigned int y,
+ unsigned int z,
+ unsigned int width,
+ unsigned int height,
+ unsigned int depth,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ void *data) {
+ TextureD3D9 *texture = textures_.Get(id);
+ if (!texture)
+ return BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+ Volume volume = {x, y, z, width, height, depth};
+ return texture->GetData(this, volume, level, face, row_pitch, slice_pitch,
+ size, data) ?
+ BufferSyncInterface::PARSE_NO_ERROR :
+ BufferSyncInterface::PARSE_INVALID_ARGUMENTS;
+}
+
+} // namespace command_buffer
+} // namespace o3d
diff --git a/o3d/command_buffer/service/win/d3d9/texture_d3d9.h b/o3d/command_buffer/service/win/d3d9/texture_d3d9.h
new file mode 100644
index 0000000..c55ba4f
--- /dev/null
+++ b/o3d/command_buffer/service/win/d3d9/texture_d3d9.h
@@ -0,0 +1,245 @@
+/*
+ * Copyright 2009, Google Inc.
+ * 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.
+ */
+
+
+#ifndef O3D_COMMAND_BUFFER_SERVICE_WIN_D3D9_TEXTURE_D3D9_H__
+#define O3D_COMMAND_BUFFER_SERVICE_WIN_D3D9_TEXTURE_D3D9_H__
+
+// This file contains the definition of the D3D9 versions of texture-related
+// resource classes.
+
+#include "command_buffer/common/cross/gapi_interface.h"
+#include "command_buffer/service/win/d3d9/d3d9_utils.h"
+#include "command_buffer/service/cross/resource.h"
+#include "command_buffer/service/cross/texture_utils.h"
+
+namespace o3d {
+namespace command_buffer {
+
+class GAPID3D9;
+
+// The base class for a D3D texture resource, providing access to the base D3D
+// texture that can be assigned to an effect parameter or a sampler unit.
+class TextureD3D9 : public Texture {
+ public:
+ TextureD3D9(texture::Type type,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags)
+ : Texture(type, levels, format, flags) {}
+ // Gets the D3D base texture.
+ virtual IDirect3DBaseTexture9 *d3d_base_texture() const = 0;
+ // Sets data into a texture resource.
+ virtual bool SetData(GAPID3D9 *gapi,
+ const Volume& volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ const void *data) = 0;
+ // Gets data from a texture resource.
+ virtual bool GetData(GAPID3D9 *gapi,
+ const Volume& volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ void *data) = 0;
+ private:
+ DISALLOW_COPY_AND_ASSIGN(TextureD3D9);
+};
+
+// A 2D texture resource for D3D.
+class Texture2DD3D9 : public TextureD3D9 {
+ public:
+ Texture2DD3D9(unsigned int levels,
+ texture::Format format,
+ unsigned int flags,
+ unsigned int width,
+ unsigned int height,
+ IDirect3DTexture9 *texture,
+ IDirect3DTexture9 *shadow)
+ : TextureD3D9(texture::TEXTURE_2D, levels, format, flags),
+ width_(width),
+ height_(height),
+ d3d_texture_(texture),
+ d3d_shadow_(shadow) {}
+ virtual ~Texture2DD3D9();
+
+ // Creates a 2D texture resource.
+ static Texture2DD3D9 *Create(GAPID3D9 *gapi,
+ unsigned int width,
+ unsigned int height,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags);
+ // Sets data into a 2D texture resource.
+ virtual bool SetData(GAPID3D9 *gapi,
+ const Volume& volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ const void *data);
+ // Gets data from a 2D texture resource.
+ virtual bool GetData(GAPID3D9 *gapi,
+ const Volume& volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ void *data);
+ // Gets the D3D base texture.
+ virtual IDirect3DBaseTexture9 *d3d_base_texture() const {
+ return d3d_texture_;
+ }
+ private:
+ unsigned int width_;
+ unsigned int height_;
+ IDirect3DTexture9 *d3d_texture_;
+ IDirect3DTexture9 *d3d_shadow_;
+ DISALLOW_COPY_AND_ASSIGN(Texture2DD3D9);
+};
+
+// A 3D texture resource for D3D.
+class Texture3DD3D9 : public TextureD3D9 {
+ public:
+ Texture3DD3D9(unsigned int levels,
+ texture::Format format,
+ unsigned int flags,
+ unsigned int width,
+ unsigned int height,
+ unsigned int depth,
+ IDirect3DVolumeTexture9 *texture,
+ IDirect3DVolumeTexture9 *shadow)
+ : TextureD3D9(texture::TEXTURE_2D, levels, format, flags),
+ width_(width),
+ height_(height),
+ depth_(depth),
+ d3d_texture_(texture),
+ d3d_shadow_(shadow) {}
+ virtual ~Texture3DD3D9();
+ // Creates a 3D texture resource.
+ static Texture3DD3D9 *Create(GAPID3D9 *gapi,
+ unsigned int width,
+ unsigned int height,
+ unsigned int depth,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags);
+ // Sets data into a 3D texture resource.
+ virtual bool SetData(GAPID3D9 *gapi,
+ const Volume& volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ const void *data);
+ // Gets data from a 3D texture resource.
+ virtual bool GetData(GAPID3D9 *gapi,
+ const Volume& volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ void *data);
+ // Gets the D3D base texture.
+ virtual IDirect3DBaseTexture9 *d3d_base_texture() const {
+ return d3d_texture_;
+ }
+ private:
+ unsigned int width_;
+ unsigned int height_;
+ unsigned int depth_;
+ IDirect3DVolumeTexture9 *d3d_texture_;
+ IDirect3DVolumeTexture9 *d3d_shadow_;
+ DISALLOW_COPY_AND_ASSIGN(Texture3DD3D9);
+};
+
+// A cube map texture resource for D3D.
+class TextureCubeD3D9 : public TextureD3D9 {
+ public:
+ TextureCubeD3D9(unsigned int levels,
+ texture::Format format,
+ unsigned int flags,
+ unsigned int side,
+ IDirect3DCubeTexture9 *texture,
+ IDirect3DCubeTexture9 *shadow)
+ : TextureD3D9(texture::TEXTURE_CUBE, levels, format, flags),
+ side_(side),
+ d3d_texture_(texture),
+ d3d_shadow_(shadow) {}
+ virtual ~TextureCubeD3D9();
+ // Creates a cube map texture resource.
+ static TextureCubeD3D9 *Create(GAPID3D9 *gapi,
+ unsigned int side,
+ unsigned int levels,
+ texture::Format format,
+ unsigned int flags);
+ // Sets data into a cube map texture resource.
+ virtual bool SetData(GAPID3D9 *gapi,
+ const Volume& volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ const void *data);
+ // Gets data from a cube map texture resource.
+ virtual bool GetData(GAPID3D9 *gapi,
+ const Volume& volume,
+ unsigned int level,
+ texture::Face face,
+ unsigned int row_pitch,
+ unsigned int slice_pitch,
+ unsigned int size,
+ void *data);
+ // Gets the D3D base texture.
+ virtual IDirect3DBaseTexture9 *d3d_base_texture() const {
+ return d3d_texture_;
+ }
+ private:
+ unsigned int side_;
+ IDirect3DCubeTexture9 *d3d_texture_;
+ IDirect3DCubeTexture9 *d3d_shadow_;
+ DISALLOW_COPY_AND_ASSIGN(TextureCubeD3D9);
+};
+
+} // namespace command_buffer
+} // namespace o3d
+
+#endif // O3D_COMMAND_BUFFER_SERVICE_WIN_D3D9_TEXTURE_D3D9_H__
diff --git a/o3d/command_buffer/service/win/plugin.def b/o3d/command_buffer/service/win/plugin.def
new file mode 100644
index 0000000..292cf78
--- /dev/null
+++ b/o3d/command_buffer/service/win/plugin.def
@@ -0,0 +1,6 @@
+LIBRARY npo3d_cb_plugin
+
+EXPORTS
+ NP_GetEntryPoints @1
+ NP_Initialize @2
+ NP_Shutdown @3
diff --git a/o3d/command_buffer/service/win/plugin.rc b/o3d/command_buffer/service/win/plugin.rc
new file mode 100644
index 0000000..393668e
--- /dev/null
+++ b/o3d/command_buffer/service/win/plugin.rc
@@ -0,0 +1,100 @@
+// Microsoft Visual C++ generated resource script.
+//
+#define APSTUDIO_READONLY_SYMBOLS
+/////////////////////////////////////////////////////////////////////////////
+//
+// Generated from the TEXTINCLUDE 2 resource.
+//
+#include "afxres.h"
+
+/////////////////////////////////////////////////////////////////////////////
+#undef APSTUDIO_READONLY_SYMBOLS
+
+/////////////////////////////////////////////////////////////////////////////
+// English (U.S.) resources
+
+#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU)
+#ifdef _WIN32
+LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US
+#pragma code_page(1252)
+#endif //_WIN32
+
+#ifdef APSTUDIO_INVOKED
+/////////////////////////////////////////////////////////////////////////////
+//
+// TEXTINCLUDE
+//
+
+1 TEXTINCLUDE
+BEGIN
+ "resource.h\0"
+END
+
+2 TEXTINCLUDE
+BEGIN
+ "#include ""afxres.h""\r\n"
+ "\0"
+END
+
+3 TEXTINCLUDE
+BEGIN
+ "\r\n"
+ "\0"
+END
+
+#endif // APSTUDIO_INVOKED
+
+
+/////////////////////////////////////////////////////////////////////////////
+//
+// Version
+//
+
+VS_VERSION_INFO VERSIONINFO
+ FILEVERSION 0,0,0,1
+ PRODUCTVERSION 0,0,0,1
+ FILEFLAGSMASK 0x17L
+#ifdef _DEBUG
+ FILEFLAGS 0x1L
+#else
+ FILEFLAGS 0x0L
+#endif
+ FILEOS 0x4L
+ FILETYPE 0x2L
+ FILESUBTYPE 0x0L
+BEGIN
+ BLOCK "StringFileInfo"
+ BEGIN
+ BLOCK "040904e4"
+ BEGIN
+ VALUE "FileDescription", "CommandBuffer SRV Plugin"
+ VALUE "FileVersion", "0,0,0,1"
+ VALUE "InternalName", ""
+ VALUE "LegalCopyright", "Copyright (C) 2008"
+ VALUE "MIMEType", "application/vnd.cmdbuf"
+ VALUE "OriginalFilename", "npo3d_cb_plugin.dll"
+ VALUE "ProductName", "CommandBuffer SRV Plugin"
+ VALUE "ProductVersion", "0,0,0,1"
+ END
+ END
+ BLOCK "VarFileInfo"
+ BEGIN
+ VALUE "Translation", 0x409, 1252
+ END
+END
+
+#endif // English (U.S.) resources
+/////////////////////////////////////////////////////////////////////////////
+
+
+
+#ifndef APSTUDIO_INVOKED
+/////////////////////////////////////////////////////////////////////////////
+//
+// Generated from the TEXTINCLUDE 3 resource.
+//
+
+
+/////////////////////////////////////////////////////////////////////////////
+#endif // not APSTUDIO_INVOKED
+