| 834 | static ZSTD_DCtx *zstd_dctx; |
| 835 | |
| 836 | static int32 recv_zstd_token(int f, char **data) |
| 837 | { |
| 838 | static int decomp_init_done; |
| 839 | static int out_buffer_size; |
| 840 | int32 n, flag; |
| 841 | int r; |
| 842 | |
| 843 | if (!decomp_init_done) { |
| 844 | zstd_dctx = ZSTD_createDCtx(); |
| 845 | if (!zstd_dctx) { |
| 846 | rprintf(FERROR, "ZSTD_createDStream failed\n"); |
| 847 | exit_cleanup(RERR_PROTOCOL); |
| 848 | } |
| 849 | |
| 850 | /* Output buffer fits two decompressed blocks */ |
| 851 | out_buffer_size = ZSTD_DStreamOutSize() * 2; |
| 852 | cbuf = new_array(char, MAX_DATA_COUNT); |
| 853 | dbuf = new_array(char, out_buffer_size); |
| 854 | |
| 855 | zstd_in_buff.src = cbuf; |
| 856 | zstd_out_buff.dst = dbuf; |
| 857 | |
| 858 | decomp_init_done = 1; |
| 859 | } |
| 860 | |
| 861 | for (;;) { |
| 862 | switch (recv_state) { |
| 863 | case r_init: |
| 864 | recv_state = r_idle; |
| 865 | rx_token = 0; |
| 866 | break; |
| 867 | |
| 868 | case r_idle: |
| 869 | flag = read_byte(f); |
| 870 | if ((flag & 0xC0) == DEFLATED_DATA) { |
| 871 | n = ((flag & 0x3f) << 8) + read_byte(f); |
| 872 | read_buf(f, cbuf, n); |
| 873 | |
| 874 | zstd_in_buff.size = n; |
| 875 | zstd_in_buff.pos = 0; |
| 876 | |
| 877 | recv_state = r_inflating; |
| 878 | break; |
| 879 | } |
| 880 | |
| 881 | if (flag == END_FLAG) { |
| 882 | /* that's all folks */ |
| 883 | recv_state = r_init; |
| 884 | return 0; |
| 885 | } |
| 886 | /* here we have a token of some kind */ |
| 887 | return recv_compressed_token_num(f, flag); |
| 888 | |
| 889 | case r_inflated: /* zstd doesn't get into this state */ |
| 890 | break; |
| 891 | |
| 892 | case r_inflating: |
| 893 | zstd_out_buff.size = out_buffer_size; |
no test coverage detected