Download third_party/ktx-src/external/astc-encoder/Utils/astc_quant_generator.cpp from kimjunhan/vkgs-sim: direct link, hf CLI and curl.
- Browser
- Download file 7.05 kB
-
https://huggingface.co/kimjunhan/vkgs-sim/resolve/main/third_party/ktx-src/external/astc-encoder/Utils/astc_quant_generator.cpp
- Command line
-
hf download hf://kimjunhan/vkgs-sim/third_party/ktx-src/external/astc-encoder/Utils/astc_quant_generator.cpp
-
curl -L -o astc_quant_generator.cpp https://huggingface.co/kimjunhan/vkgs-sim/resolve/main/third_party/ktx-src/external/astc-encoder/Utils/astc_quant_generator.cpp
7.05 kB
| // SPDX-License-Identifier: Apache-2.0 | |
| // ---------------------------------------------------------------------------- | |
| // Copyright 2023 Arm Limited | |
| // | |
| // Licensed under the Apache License, Version 2.0 (the "License"); you may not | |
| // use this file except in compliance with the License. You may obtain a copy | |
| // of the License at: | |
| // | |
| // http://www.apache.org/licenses/LICENSE-2.0 | |
| // | |
| // Unless required by applicable law or agreed to in writing, software | |
| // distributed under the License is distributed on an "AS IS" BASIS, WITHOUT | |
| // WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the | |
| // License for the specific language governing permissions and limitations | |
| // under the License. | |
| // ---------------------------------------------------------------------------- | |
| // This is a utility tool to generate quant tables | |
| /** | |
| * @brief The ASTC quantization methods. | |
| * | |
| * Note, the values here are used directly in the encoding in the format so do not rearrange. | |
| */ | |
| enum quant_method | |
| { | |
| QUANT_2 = 0, | |
| QUANT_3 = 1, | |
| QUANT_4 = 2, | |
| QUANT_5 = 3, | |
| QUANT_6 = 4, | |
| QUANT_8 = 5, | |
| QUANT_10 = 6, | |
| QUANT_12 = 7, | |
| QUANT_16 = 8, | |
| QUANT_20 = 9, | |
| QUANT_24 = 10, | |
| QUANT_32 = 11, | |
| QUANT_40 = 12, | |
| QUANT_48 = 13, | |
| QUANT_64 = 14, | |
| QUANT_80 = 15, | |
| QUANT_96 = 16, | |
| QUANT_128 = 17, | |
| QUANT_160 = 18, | |
| QUANT_192 = 19, | |
| QUANT_256 = 20 | |
| }; | |
| static inline unsigned int get_quant_level(quant_method method) | |
| { | |
| switch (method) | |
| { | |
| case QUANT_2: return 2; | |
| case QUANT_3: return 3; | |
| case QUANT_4: return 4; | |
| case QUANT_5: return 5; | |
| case QUANT_6: return 6; | |
| case QUANT_8: return 8; | |
| case QUANT_10: return 10; | |
| case QUANT_12: return 12; | |
| case QUANT_16: return 16; | |
| case QUANT_20: return 20; | |
| case QUANT_24: return 24; | |
| case QUANT_32: return 32; | |
| case QUANT_40: return 40; | |
| case QUANT_48: return 48; | |
| case QUANT_64: return 64; | |
| case QUANT_80: return 80; | |
| case QUANT_96: return 96; | |
| case QUANT_128: return 128; | |
| case QUANT_160: return 160; | |
| case QUANT_192: return 192; | |
| case QUANT_256: return 256; | |
| } | |
| // Unreachable - the enum is fully described | |
| return 0; | |
| } | |
| struct quant_config { | |
| quant_method quant; | |
| unsigned int bits; | |
| unsigned int trits; | |
| unsigned int quints; | |
| unsigned int C; | |
| unsigned int masks[6]; | |
| }; | |
| const std::array<quant_config, 17> quant_configs {{ | |
| { | |
| QUANT_6, | |
| 1, 1, 0, | |
| 204, | |
| { | |
| 0b000000000, | |
| 0b000000000, | |
| 0b000000000, | |
| 0b000000000, | |
| 0b000000000, | |
| 0b000000000 | |
| } | |
| }, { | |
| QUANT_8, | |
| 3, 0, 0, | |
| 0, | |
| { 0 } | |
| }, { | |
| QUANT_10, | |
| 1, 0, 1, | |
| 113, | |
| { | |
| 0b000000000, | |
| 0b000000000, | |
| 0b000000000, | |
| 0b000000000, | |
| 0b000000000, | |
| 0b000000000 | |
| } | |
| }, { | |
| QUANT_12, | |
| 2, 1, 0, | |
| 93, | |
| { | |
| 0b000000000, | |
| 0b100010110, | |
| 0b000000000, | |
| 0b000000000, | |
| 0b000000000, | |
| 0b000000000 | |
| } | |
| }, { | |
| QUANT_16, | |
| 4, 0, 0, | |
| 0, | |
| { 0 } | |
| }, { | |
| QUANT_20, | |
| 2, 0, 1, | |
| 54, | |
| { | |
| 0b000000000, | |
| 0b100001100, | |
| 0b000000000, | |
| 0b000000000, | |
| 0b000000000, | |
| 0b000000000 | |
| } | |
| }, { | |
| QUANT_24, | |
| 3, 1, 0, | |
| 44, | |
| { | |
| 0b000000000, | |
| 0b010000101, | |
| 0b100001010, | |
| 0b000000000, | |
| 0b000000000, | |
| 0b000000000 | |
| } | |
| }, { | |
| QUANT_32, | |
| 5, 0, 0, | |
| 0, | |
| { 0 } | |
| }, | |
| { | |
| QUANT_40, | |
| 3, 0, 1, | |
| 26, | |
| { | |
| 0b000000000, | |
| 0b010000010, | |
| 0b100000101, | |
| 0b000000000, | |
| 0b000000000, | |
| 0b000000000 | |
| } | |
| }, { | |
| QUANT_48, | |
| 4, 1, 0, | |
| 22, | |
| { | |
| 0b000000000, | |
| 0b001000001, | |
| 0b010000010, | |
| 0b100000100, | |
| 0b000000000, | |
| 0b000000000 | |
| } | |
| }, { | |
| QUANT_64, | |
| 6, 0, 0, | |
| 0, | |
| { 0 } | |
| }, { | |
| QUANT_80, | |
| 4, 0, 1, | |
| 13, | |
| { | |
| 0b000000000, | |
| 0b001000000, | |
| 0b010000001, | |
| 0b100000010, | |
| 0b000000000, | |
| 0b000000000 | |
| } | |
| }, { | |
| QUANT_96, | |
| 5, 1, 0, | |
| 11, | |
| { | |
| 0b000000000, | |
| 0b000100000, | |
| 0b001000000, | |
| 0b010000001, | |
| 0b100000010, | |
| 0b000000000 | |
| } | |
| }, { | |
| QUANT_128, | |
| 7, 0, 0, | |
| 0, | |
| { 0 } | |
| }, { | |
| QUANT_160, | |
| 5, 0, 1, | |
| 6, | |
| { | |
| 0b000000000, | |
| 0b000100000, | |
| 0b001000000, | |
| 0b010000000, | |
| 0b100000001, | |
| 0b000000000 | |
| } | |
| }, { | |
| QUANT_192, | |
| 6, 1, 0, | |
| 5, | |
| { | |
| 0b000000000, | |
| 0b000010000, | |
| 0b000100000, | |
| 0b001000000, | |
| 0b010000000, | |
| 0b100000001 | |
| } | |
| }, { | |
| QUANT_256, | |
| 8, 0, 0, | |
| 0, | |
| { 0 } | |
| } | |
| }}; | |
| void generate_unpacked_quant( | |
| const quant_config& config, | |
| std::set<unsigned int>& set | |
| ) { | |
| unsigned int levels = get_quant_level(config.quant); | |
| unsigned int emitted = 0; | |
| // Value has 1 trit and N bits | |
| if (config.trits) | |
| { | |
| for (unsigned int D = 0; D < 3; D++) | |
| { | |
| unsigned int max_bits = 1 << config.bits; | |
| for (unsigned int bits = 0; bits < max_bits; bits++) | |
| { | |
| unsigned int A = (bits & 1) * 0b111111111; | |
| unsigned int B = 0; | |
| unsigned int bit = bits; | |
| for (const auto& mask_n: config.masks) | |
| { | |
| unsigned int bit_n = bit & 1; | |
| bit >>= 1; | |
| B += bit_n * mask_n; | |
| } | |
| unsigned int T = D * config.C + B; | |
| T = T ^ A; | |
| T = (A & 0x80) | (T >> 2); | |
| set.insert(T); | |
| } | |
| } | |
| } | |
| // Value has 1 quint and N bits | |
| else if (config.quints) | |
| { | |
| for (unsigned int D = 0; D < 5; D++) | |
| { | |
| unsigned int max_bits = 1 << config.bits; | |
| for (unsigned int bits = 0; bits < max_bits; bits++) | |
| { | |
| unsigned int A = (bits & 1) * 0b111111111; | |
| unsigned int B = 0; | |
| unsigned int bit = bits; | |
| for (const auto& mask_n: config.masks) | |
| { | |
| unsigned int bit_n = bit & 1; | |
| bit >>= 1; | |
| B += bit_n * mask_n; | |
| } | |
| unsigned int T = D * config.C + B; | |
| T = T ^ A; | |
| T = (A & 0x80) | (T >> 2); | |
| set.insert(T); | |
| } | |
| } | |
| } | |
| // Value has N bits | |
| else | |
| { | |
| unsigned int max_bits = 1 << config.bits; | |
| for (unsigned int bits = 0; bits < max_bits; bits++) | |
| { | |
| unsigned int T = bits << (8 - config.bits); | |
| int bits_remaining = 8 - config.bits; | |
| while (bits_remaining > 0) | |
| { | |
| int shift = bits_remaining - config.bits; | |
| bits_remaining -= config.bits; | |
| if (shift > 0) | |
| { | |
| T |= bits << shift; | |
| } | |
| else | |
| { | |
| T |= bits >> -shift; | |
| } | |
| } | |
| set.insert(T); | |
| } | |
| } | |
| } | |
| void generate_unquant_to_unpacked_quant( | |
| const quant_config& config, | |
| const std::set<unsigned int>& set | |
| ) { | |
| for (unsigned int i = 0; i < 256; i++) | |
| { | |
| unsigned int min_dist = 256; | |
| unsigned int val_lo = 256; | |
| unsigned int val_hi = 0; | |
| for (const auto& val: set) | |
| { | |
| unsigned int dist = std::max(i, val) - std::min(i, val); | |
| if (dist < min_dist) | |
| { | |
| min_dist = dist; | |
| val_lo = val; | |
| val_hi = val; | |
| } | |
| else if (dist == min_dist) | |
| { | |
| val_lo = std::min(val_lo, val); | |
| val_hi = std::max(val_hi, val); | |
| } | |
| } | |
| if ((i % 16) == 0) | |
| { | |
| printf("\t\t"); | |
| } | |
| printf("%3u, %3u", val_lo, val_hi); | |
| if (i != 255) | |
| { | |
| printf(", "); | |
| } | |
| if ((i % 16) == 15) | |
| { | |
| printf("\n"); | |
| } | |
| } | |
| } | |
| int main(void) | |
| { | |
| printf("const uint8_t color_unquant_to_uquant_tables[17][512] {\n"); | |
| for (size_t i = 0; i < quant_configs.size(); i++) | |
| { | |
| const auto& config = quant_configs[i]; | |
| std::set<unsigned int> set; | |
| printf("\t{ // QUANT_%u\n", get_quant_level(config.quant)); | |
| generate_unpacked_quant(config, set); | |
| generate_unquant_to_unpacked_quant(config, set); | |
| printf("\t},\n"); | |
| } | |
| printf("};\n"); | |
| return 0; | |
| } | |