From 3b0bf1fe473099ec29098d1aeda777027d4554bd Mon Sep 17 00:00:00 2001 From: Razor12911 Date: Mon, 12 Jun 2023 16:28:02 +0200 Subject: [PATCH] update to 0.7.2 --- README.md | 1 - Unit1.fmx | 93 +++- Unit1.pas | 19 +- Unit2.fmx | 2 +- changes.txt | 7 + common/OpenCL.pas | 782 +++++++++++++++++++++++++++++++++ common/Utils.pas | 447 ++++++++++++++++++- imports/FLZMA2DLL.pas | 10 +- precompressor/PrecompLZO.pas | 31 +- precompressor/PrecompMain.pas | 275 +++++++++--- precompressor/PrecompMedia.pas | 23 +- precompressor/PrecompZLib.pas | 43 +- precompressor/PrecompZSTD.pas | 42 +- xtool.dpr | 25 +- xtool.dproj | 60 +-- xtoolui.dproj | 55 --- 16 files changed, 1668 insertions(+), 247 deletions(-) delete mode 100644 README.md create mode 100644 common/OpenCL.pas diff --git a/README.md b/README.md deleted file mode 100644 index 51cf34a..0000000 --- a/README.md +++ /dev/null @@ -1 +0,0 @@ -# xtool \ No newline at end of file diff --git a/Unit1.fmx b/Unit1.fmx index 4548b21..1a87647 100644 --- a/Unit1.fmx +++ b/Unit1.fmx @@ -3589,7 +3589,7 @@ object Form1: TForm1 Size.Width = 110.000000000000000000 Size.Height = 20.000000000000000000 Size.PlatformDefault = False - TabOrder = 1 + TabOrder = 2 Text = 'Skip verification' end object CheckBox6: TCheckBox @@ -3615,9 +3615,51 @@ object Form1: TForm1 Size.Width = 110.000000000000000000 Size.Height = 20.000000000000000000 Size.PlatformDefault = False - TabOrder = 4 + TabOrder = 5 Text = 'Low memory' end + object Label8: TLabel + Align = Left + Margins.Left = 8.000000000000000000 + Margins.Top = 8.000000000000000000 + Margins.Bottom = 8.000000000000000000 + Position.X = 362.000000000000000000 + Position.Y = 8.000000000000000000 + Size.Width = 80.000000000000000000 + Size.Height = 20.000000000000000000 + Size.PlatformDefault = False + Text = 'GPU' + TabOrder = 1 + end + object ComboEdit3: TComboEdit + Touch.InteractiveGestures = [LongTap, DoubleTap] + Align = Left + TabOrder = 4 + ItemHeight = 19.000000000000000000 + Items.Strings = ( + '0%' + '10%' + '25%' + '50%' + '75%' + '64MB' + '128MB' + '256MB' + '512MB' + '1GB' + '2GB' + '4GB') + ItemIndex = 0 + Text = '0%' + Position.X = 450.000000000000000000 + Position.Y = 8.000000000000000000 + Margins.Left = 8.000000000000000000 + Margins.Top = 8.000000000000000000 + Margins.Bottom = 8.000000000000000000 + Size.Width = 80.000000000000000000 + Size.Height = 20.000000000000000000 + Size.PlatformDefault = False + end end end object GroupBox3: TGroupBox @@ -3872,6 +3914,7 @@ object Form1: TForm1 ItemHeight = 19.000000000000000000 Items.Strings = ( 'Auto' + 'Auto+' '16MB' '32MB' '64MB' @@ -5998,7 +6041,7 @@ object Form1: TForm1 object SpinBox13: TSpinBox Touch.InteractiveGestures = [LongTap, DoubleTap] Align = Left - TabOrder = 1 + TabOrder = 2 Cursor = crIBeam DecimalDigits = 0 Min = 1.000000000000000000 @@ -6023,9 +6066,51 @@ object Form1: TForm1 Size.Width = 110.000000000000000000 Size.Height = 20.000000000000000000 Size.PlatformDefault = False - TabOrder = 3 + TabOrder = 5 Text = 'Verbose' end + object Label22: TLabel + Align = Left + Margins.Left = 8.000000000000000000 + Margins.Top = 8.000000000000000000 + Margins.Bottom = 8.000000000000000000 + Position.X = 302.000000000000000000 + Position.Y = 8.000000000000000000 + Size.Width = 80.000000000000000000 + Size.Height = 20.000000000000000000 + Size.PlatformDefault = False + Text = 'GPU' + TabOrder = 1 + end + object ComboEdit4: TComboEdit + Touch.InteractiveGestures = [LongTap, DoubleTap] + Align = Left + TabOrder = 4 + ItemHeight = 19.000000000000000000 + Items.Strings = ( + '0%' + '10%' + '25%' + '50%' + '75%' + '64MB' + '128MB' + '256MB' + '512MB' + '1GB' + '2GB' + '4GB') + ItemIndex = 0 + Text = '0%' + Position.X = 390.000000000000000000 + Position.Y = 8.000000000000000000 + Margins.Left = 8.000000000000000000 + Margins.Top = 8.000000000000000000 + Margins.Bottom = 8.000000000000000000 + Size.Width = 80.000000000000000000 + Size.Height = 20.000000000000000000 + Size.PlatformDefault = False + end end end object GroupBox36: TGroupBox diff --git a/Unit1.pas b/Unit1.pas index 77d415f..64abac7 100644 --- a/Unit1.pas +++ b/Unit1.pas @@ -242,6 +242,10 @@ type Label3: TLabel; SpinBox3: TSpinBox; CheckBox6: TCheckBox; + Label8: TLabel; + ComboEdit3: TComboEdit; + Label22: TLabel; + ComboEdit4: TComboEdit; procedure FormShow(Sender: TObject); procedure SearchEditButton1Click(Sender: TObject); procedure SearchEditButton3Click(Sender: TObject); @@ -379,7 +383,9 @@ begin Insert('-t' + SpinBox13.Text, CmdStr, Length(CmdStr)); if CheckBox7.IsChecked then Insert('-v', CmdStr, Length(CmdStr)); - Insert('--basedir=' + Edit6.Text, CmdStr, Length(CmdStr)); + Insert('-g' + ReplaceText(ReplaceText(ComboEdit4.Text, '%', 'p'), ' ', ''), + CmdStr, Length(CmdStr)); + Insert('-bd' + Edit6.Text, CmdStr, Length(CmdStr)); Insert(Edit25.Text, CmdStr, Length(CmdStr)); case DecodeMode of 0: @@ -408,14 +414,19 @@ begin Insert('-dd' + IfThen(SpinBox4.Enabled, SpinBox4.Text, ''), CmdStr, Length(CmdStr)); if ComboEdit1.Enabled then - Insert('-SI' + ComboEdit1.Text, CmdStr, Length(CmdStr)); + Insert('-SI' + ReplaceText(ComboEdit1.Text, ' ', ''), CmdStr, + Length(CmdStr)); if CheckBox4.IsChecked then begin S := ''; if not ComboEdit2.Text.StartsWith('Auto', False) then - S := ':d' + ReplaceText(ComboEdit2.Text, ' ', ''); - Insert('-l' + SpinBox7.Text + S, CmdStr, Length(CmdStr)); + S := S + ':d' + ReplaceText(ComboEdit2.Text, ' ', ''); + // S := S + ':o8'; + Insert('-l' + SpinBox7.Text + IfThen(SameText(ComboEdit2.Text, 'Auto'), '', + 'x') + S, CmdStr, Length(CmdStr)); end; + Insert('-g' + ReplaceText(ReplaceText(ComboEdit3.Text, '%', 'p'), ' ', ''), + CmdStr, Length(CmdStr)); Insert('-bd' + Edit6.Text, CmdStr, Length(CmdStr)); Insert(Edit1.Text, CmdStr, Length(CmdStr)); if ComboBox3.ItemIndex = 1 then diff --git a/Unit2.fmx b/Unit2.fmx index 2ce35f6..e16e0e2 100644 --- a/Unit2.fmx +++ b/Unit2.fmx @@ -1200,7 +1200,7 @@ object Form2: TForm2 Size.Height = 20.000000000000000000 Size.PlatformDefault = False TabOrder = 2 - Text = 'JoJpeg (Experimental)' + Text = 'JoJpeg' end end end diff --git a/changes.txt b/changes.txt index 1b3101b..c6a6561 100644 --- a/changes.txt +++ b/changes.txt @@ -1,3 +1,10 @@ + ES_R47 (0.7.2) + - memory usage optimizations + + ES_R46 (0.7.1) + - fixed issues with fast-lzma2 being unable to set correct compression level + - updated deflate stream scanner + ES_R45 (0.7.0) - added ability to redirect base directory for plugins and libraries - added restrictions to avoid errors with experimental codecs diff --git a/common/OpenCL.pas b/common/OpenCL.pas new file mode 100644 index 0000000..b610a82 --- /dev/null +++ b/common/OpenCL.pas @@ -0,0 +1,782 @@ +unit OpenCL; + +interface + +uses + WinAPI.Windows, + System.SysUtils, System.Types, System.IOUtils; + +type + cl_char = int8; + cl_uchar = uint8; + cl_short = int16; + cl_ushort = uint16; + cl_int = int32; + cl_uint = uint32; + cl_long = int64; + cl_ulong = uint64; + + cl_half = uint16; + cl_float = single; + cl_double = double; + + Pcl_char = ^cl_char; + Pcl_uchar = ^cl_uchar; + Pcl_short = ^cl_short; + Pcl_ushort = ^cl_ushort; + Pcl_int = ^cl_int; + Pcl_uint = ^cl_uint; + Pcl_long = ^cl_long; + Pcl_ulong = ^cl_ulong; + + Pcl_half = ^cl_half; + Pcl_float = ^cl_float; + Pcl_double = ^cl_double; + +const + CL_CHAR_BIT = 8; + CL_SCHAR_MAX = 127; + CL_SCHAR_MIN = (-127 - 1); + CL_CHAR_MAX = CL_SCHAR_MAX; + CL_CHAR_MIN = CL_SCHAR_MIN; + CL_UCHAR_MAX = 255; + CL_SHRT_MAX = 32767; + CL_SHRT_MIN = (-32767 - 1); + CL_USHRT_MAX = 65535; + CL_INT_MAX = 2147483647; + CL_INT_MIN = (-2147483647 - 1); + CL_UINT_MAX = $FFFFFFFF; + CL_LONG_MAX = $7FFFFFFFFFFFFFFF; + CL_LONG_MIN = -$7FFFFFFFFFFFFFFF - 1; + CL_ULONG_MAX = $FFFFFFFFFFFFFFFF; + + CL_FLT_DIG = 6; + CL_FLT_MANT_DIG = 24; + CL_FLT_MAX_10_EXP = +38; + CL_FLT_MAX_EXP = +128; + CL_FLT_MIN_10_EXP = -37; + CL_FLT_MIN_EXP = -125; + CL_FLT_RADIX = 2; + // CL_FLT_MAX = 0x1.fffffep127f; + // CL_FLT_MIN = 0x1.0p-126f; + // CL_FLT_EPSILON = 0x1.0p-23f; + + CL_DBL_DIG = 15; + CL_DBL_MANT_DIG = 53; + CL_DBL_MAX_10_EXP = +308; + CL_DBL_MAX_EXP = +1024; + CL_DBL_MIN_10_EXP = -307; + CL_DBL_MIN_EXP = -1021; + CL_DBL_RADIX = 2; + // CL_DBL_MAX 0x1.fffffffffffffp1023 + // CL_DBL_MIN 0x1.0p-1022 + // CL_DBL_EPSILON 0x1.0p-52 + + { * + * Vector types + * + * Note: OpenCL requires that all types be naturally aligned. + * This means that vector types must be naturally aligned. + * For example, a vector of four floats must be aligned to + * a 16 byte boundary (calculated as 4 * the natural 4-byte + * alignment of the float). The alignment qualifiers here + * will only function properly if your compiler supports them + * and if you don't actively work to defeat them. For example, + * in order for a cl_float4 to be 16 byte aligned in a struct, + * the start of the struct must itself be 16-byte aligned. + * + * Maintaining proper alignment is the user's responsibility. + * } +type + cl_char2 = array [0 .. 1] of int8; + cl_char4 = array [0 .. 3] of int8; + cl_char8 = array [0 .. 7] of int8; + cl_char16 = array [0 .. 15] of int8; + + cl_uchar2 = array [0 .. 1] of uint8; + cl_uchar4 = array [0 .. 3] of uint8; + cl_uchar8 = array [0 .. 7] of uint8; + cl_uchar16 = array [0 .. 15] of uint8; + + cl_short2 = array [0 .. 1] of int16; + cl_short4 = array [0 .. 3] of int16; + cl_short8 = array [0 .. 7] of int16; + cl_short16 = array [0 .. 15] of int16; + + cl_ushort2 = array [0 .. 1] of uint16; + cl_ushort4 = array [0 .. 3] of uint16; + cl_ushort8 = array [0 .. 7] of uint16; + cl_ushort16 = array [0 .. 15] of uint16; + + cl_int2 = array [0 .. 1] of int32; + cl_int4 = array [0 .. 3] of int32; + cl_int8 = array [0 .. 7] of int32; + cl_int16 = array [0 .. 15] of int32; + + cl_uint2 = array [0 .. 1] of uint32; + cl_uint4 = array [0 .. 3] of uint32; + cl_uint8 = array [0 .. 7] of uint32; + cl_uint16 = array [0 .. 15] of uint32; + + cl_long2 = array [0 .. 1] of int64; + cl_long4 = array [0 .. 3] of int64; + cl_long8 = array [0 .. 7] of int64; + cl_long16 = array [0 .. 15] of int64; + + cl_ulong2 = array [0 .. 1] of uint64; + cl_ulong4 = array [0 .. 3] of uint64; + cl_ulong8 = array [0 .. 7] of uint64; + cl_ulong16 = array [0 .. 15] of uint64; + + cl_float2 = array [0 .. 1] of single; + cl_float4 = array [0 .. 3] of single; + cl_float8 = array [0 .. 7] of single; + cl_float16 = array [0 .. 15] of single; + + cl_double2 = array [0 .. 1] of double; + cl_double4 = array [0 .. 3] of double; + cl_double8 = array [0 .. 7] of double; + cl_double16 = array [0 .. 15] of double; + + { * There are no vector types for half * } + + // **************************************************************************** + + { cl.h } + +type + _cl_platform_id = record + end; + + _cl_device_id = record + end; + + _cl_context = record + end; + + _cl_command_queue = record + end; + + _cl_mem = record + end; + + _cl_program = record + end; + + _cl_kernel = record + end; + + _cl_event = record + end; + + _cl_sampler = record + end; + + cl_platform_id = ^_cl_platform_id; + cl_device_id = ^_cl_device_id; + cl_context = ^_cl_context; + cl_command_queue = ^_cl_command_queue; + cl_mem = ^_cl_mem; + cl_program = ^_cl_program; + cl_kernel = ^_cl_kernel; + cl_event = ^_cl_event; + cl_sampler = ^_cl_sampler; + + Pcl_platform_id = cl_platform_id; + Pcl_device_id = cl_device_id; + Pcl_context = cl_context; + Pcl_command_queue = cl_command_queue; + Pcl_mem = cl_mem; + Pcl_program = cl_program; + Pcl_kernel = cl_kernel; + Pcl_event = cl_event; + Pcl_sampler = cl_sampler; + + cl_bool = cl_uint; + // WARNING! Unlike cl_ types in cl_platform.h, cl_bool is not guaranteed to be the same size as the bool in kernels. + cl_bitfield = cl_ulong; + cl_device_type = cl_bitfield; + cl_platform_info = cl_uint; + cl_device_info = cl_uint; + cl_device_address_info = cl_bitfield; + cl_device_fp_config = cl_bitfield; + cl_device_mem_cache_type = cl_uint; + cl_device_local_mem_type = cl_uint; + cl_device_exec_capabilities = cl_bitfield; + cl_command_queue_properties = cl_bitfield; + + cl_context_properties = intptr; + cl_context_info = cl_uint; + cl_command_queue_info = cl_uint; + cl_channel_order = cl_uint; + cl_channel_type = cl_uint; + cl_mem_flags = cl_bitfield; + cl_mem_object_type = cl_uint; + cl_mem_info = cl_uint; + cl_image_info = cl_uint; + cl_addressing_mode = cl_uint; + cl_filter_mode = cl_uint; + cl_sampler_info = cl_uint; + cl_map_flags = cl_bitfield; + cl_program_info = cl_uint; + cl_program_build_info = cl_uint; + cl_build_status = cl_int; + cl_kernel_info = cl_uint; + cl_kernel_work_group_info = cl_uint; + cl_event_info = cl_uint; + cl_command_type = cl_uint; + cl_profiling_info = cl_uint; + + _cl_image_format = packed record + image_channel_order: cl_channel_order; + image_channel_data_type: cl_channel_type; + end; + + cl_image_format = _cl_image_format; + + Pcl_context_properties = ^cl_context_properties; + Pcl_image_format = ^cl_image_format; + +const + // Error Codes + CL_SUCCESS = 0; + CL_DEVICE_NOT_FOUND = -1; + CL_DEVICE_NOT_AVAILABLE = -2; + CL_DEVICE_COMPILER_NOT_AVAILABLE = -3; + CL_MEM_OBJECT_ALLOCATION_FAILURE = -4; + CL_OUT_OF_RESOURCES = -5; + CL_OUT_OF_HOST_MEMORY = -6; + CL_PROFILING_INFO_NOT_AVAILABLE = -7; + CL_MEM_COPY_OVERLAP = -8; + CL_IMAGE_FORMAT_MISMATCH = -9; + CL_IMAGE_FORMAT_NOT_SUPPORTED = -10; + CL_BUILD_PROGRAM_FAILURE = -11; + CL_MAP_FAILURE = -12; + + CL_INVALID_VALUE = -30; + CL_INVALID_DEVICE_TYPE = -31; + CL_INVALID_PLATFORM = -32; + CL_INVALID_DEVICE = -33; + CL_INVALID_CONTEXT = -34; + CL_INVALID_QUEUE_PROPERTIES = -35; + CL_INVALID_COMMAND_QUEUE = -36; + CL_INVALID_HOST_PTR = -37; + CL_INVALID_MEM_OBJECT = -38; + CL_INVALID_IMAGE_FORMAT_DESCRIPTOR = -39; + CL_INVALID_IMAGE_SIZE = -40; + CL_INVALID_SAMPLER = -41; + CL_INVALID_BINARY = -42; + CL_INVALID_BUILD_OPTIONS = -43; + CL_INVALID_PROGRAM = -44; + CL_INVALID_PROGRAM_EXECUTABLE = -45; + CL_INVALID_KERNEL_NAME = -46; + CL_INVALID_KERNEL_DEFINITION = -47; + CL_INVALID_KERNEL = -48; + CL_INVALID_ARG_INDEX = -49; + CL_INVALID_ARG_VALUE = -50; + CL_INVALID_ARG_SIZE = -51; + CL_INVALID_KERNEL_ARGS = -52; + CL_INVALID_WORK_DIMENSION = -53; + CL_INVALID_WORK_GROUP_SIZE = -54; + CL_INVALID_WORK_ITEM_SIZE = -55; + CL_INVALID_GLOBAL_OFFSET = -56; + CL_INVALID_EVENT_WAIT_LIST = -57; + CL_INVALID_EVENT = -58; + CL_INVALID_OPERATION = -59; + CL_INVALID_GL_OBJECT = -60; + CL_INVALID_BUFFER_SIZE = -61; + CL_INVALID_MIP_LEVEL = -62; + CL_INVALID_GLOBAL_WORK_SIZE = -63; + + // OpenCL Version + CL_VERSION_1_0 = 1; + + // cl_bool + CL_FALSE = 0; + CL_TRUE = 1; + + // cl_platform_info + CL_PLATFORM_PROFILE = $0900; + CL_PLATFORM_VERSION = $0901; + CL_PLATFORM_NAME = $0902; + CL_PLATFORM_VENDOR = $0903; + CL_PLATFORM_EXTENSIONS = $0904; + + // cl_device_type - bitfield + CL_DEVICE_TYPE_DEFAULT = (1 shl 0); + CL_DEVICE_TYPE_CPU = (1 shl 1); + CL_DEVICE_TYPE_GPU = (1 shl 2); + CL_DEVICE_TYPE_ACCELERATOR = (1 shl 3); + CL_DEVICE_TYPE_ALL = $FFFFFFFF; + + // cl_device_info + CL_DEVICE_TYPE_INFO = $1000; // CL_DEVICE_TYPE + CL_DEVICE_VENDOR_ID = $1001; + CL_DEVICE_MAX_COMPUTE_UNITS = $1002; + CL_DEVICE_MAX_WORK_ITEM_DIMENSIONS = $1003; + CL_DEVICE_MAX_WORK_GROUP_SIZE = $1004; + CL_DEVICE_MAX_WORK_ITEM_SIZES = $1005; + CL_DEVICE_PREFERRED_VECTOR_WIDTH_CHAR = $1006; + CL_DEVICE_PREFERRED_VECTOR_WIDTH_SHORT = $1007; + CL_DEVICE_PREFERRED_VECTOR_WIDTH_INT = $1008; + CL_DEVICE_PREFERRED_VECTOR_WIDTH_LONG = $1009; + CL_DEVICE_PREFERRED_VECTOR_WIDTH_FLOAT = $100A; + CL_DEVICE_PREFERRED_VECTOR_WIDTH_DOUBLE = $100B; + CL_DEVICE_MAX_CLOCK_FREQUENCY = $100C; + CL_DEVICE_ADDRESS_BITS = $100D; + CL_DEVICE_MAX_READ_IMAGE_ARGS = $100E; + CL_DEVICE_MAX_WRITE_IMAGE_ARGS = $100F; + CL_DEVICE_MAX_MEM_ALLOC_SIZE = $1010; + CL_DEVICE_IMAGE2D_MAX_WIDTH = $1011; + CL_DEVICE_IMAGE2D_MAX_HEIGHT = $1012; + CL_DEVICE_IMAGE3D_MAX_WIDTH = $1013; + CL_DEVICE_IMAGE3D_MAX_HEIGHT = $1014; + CL_DEVICE_IMAGE3D_MAX_DEPTH = $1015; + CL_DEVICE_IMAGE_SUPPORT = $1016; + CL_DEVICE_MAX_PARAMETER_SIZE = $1017; + CL_DEVICE_MAX_SAMPLERS = $1018; + CL_DEVICE_MEM_BASE_ADDR_ALIGN = $1019; + CL_DEVICE_MIN_DATA_TYPE_ALIGN_SIZE = $101A; + CL_DEVICE_SINGLE_FP_CONFIG = $101B; + CL_DEVICE_DOUBLE_FP_CONFIG = $1032; + CL_DEVICE_PREFERRED_VECTOR_WIDTH_HALF = $1034; + CL_DEVICE_HOST_UNIFIED_MEMORY = $1035; + CL_DEVICE_NATIVE_VECTOR_WIDTH_CHAR = $1036; + CL_DEVICE_NATIVE_VECTOR_WIDTH_SHORT = $1037; + CL_DEVICE_NATIVE_VECTOR_WIDTH_INT = $1038; + CL_DEVICE_NATIVE_VECTOR_WIDTH_LONG = $1039; + CL_DEVICE_NATIVE_VECTOR_WIDTH_FLOAT = $103A; + CL_DEVICE_NATIVE_VECTOR_WIDTH_DOUBLE = $103B; + CL_DEVICE_NATIVE_VECTOR_WIDTH_HALF = $103C; + CL_DEVICE_OPENCL_C_VERSION = $103D; + CL_DEVICE_LINKER_AVAILABLE = $103E; + CL_DEVICE_BUILT_IN_KERNELS = $103F; + CL_DEVICE_IMAGE_MAX_BUFFER_SIZE = $1040; + CL_DEVICE_IMAGE_MAX_ARRAY_SIZE = $1041; + CL_DEVICE_PARENT_DEVICE = $1042; + CL_DEVICE_PARTITION_MAX_SUB_DEVICES = $1043; + CL_DEVICE_PARTITION_PROPERTIES = $1044; + CL_DEVICE_PARTITION_AFFINITY_DOMAIN = $1045; + CL_DEVICE_PARTITION_TYPE = $1046; + CL_DEVICE_REFERENCE_COUNT = $1047; + CL_DEVICE_PREFERRED_INTEROP_USER_SYNC = $1048; + CL_DEVICE_PRINTF_BUFFER_SIZE = $1049; + CL_DEVICE_GLOBAL_MEM_CACHE_TYPE = $101C; + CL_DEVICE_GLOBAL_MEM_CACHELINE_SIZE = $101D; + CL_DEVICE_GLOBAL_MEM_CACHE_SIZE = $101E; + CL_DEVICE_GLOBAL_MEM_SIZE = $101F; + CL_DEVICE_MAX_CONSTANT_BUFFER_SIZE = $1020; + CL_DEVICE_MAX_CONSTANT_ARGS = $1021; + CL_DEVICE_LOCAL_MEM_TYPE_INFO = $1022; // CL_DEVICE_LOCAL_MEM_TYPE + CL_DEVICE_LOCAL_MEM_SIZE = $1023; + CL_DEVICE_ERROR_CORRECTION_SUPPORT = $1024; + CL_DEVICE_PROFILING_TIMER_RESOLUTION = $1025; + CL_DEVICE_ENDIAN_LITTLE = $1026; + CL_DEVICE_AVAILABLE = $1027; + CL_DEVICE_COMPILER_AVAILABLE = $1028; + CL_DEVICE_EXECUTION_CAPABILITIES = $1029; + CL_DEVICE_QUEUE_PROPERTIES = $102A; + CL_DEVICE_NAME = $102B; + CL_DEVICE_VENDOR = $102C; + CL_DRIVER_VERSION = $102D; + CL_DEVICE_PROFILE = $102E; + CL_DEVICE_VERSION = $102F; + CL_DEVICE_EXTENSIONS = $1030; + CL_DEVICE_PLATFORM = $1031; + + // cl_device_address_info - bitfield + CL_DEVICE_ADDRESS_32_BITS = (1 shl 0); + CL_DEVICE_ADDRESS_64_BITS = (1 shl 1); + + // cl_device_fp_config - bitfield + CL_FP_DENORM = (1 shl 0); + CL_FP_INF_NAN = (1 shl 1); + CL_FP_ROUND_TO_NEAREST = (1 shl 2); + CL_FP_ROUND_TO_ZERO = (1 shl 3); + CL_FP_ROUND_TO_INF = (1 shl 4); + CL_FP_FMA = (1 shl 5); + + // cl_device_mem_cache_type + CL_NONE = $0; + CL_READ_ONLY_CACHE = $1; + CL_READ_WRITE_CACHE = $2; + + // cl_device_local_mem_type + CL_LOCAL = $1; + CL_GLOBAL = $2; + + // cl_device_exec_capabilities - bitfield + CL_EXEC_KERNEL = (1 shl 0); + CL_EXEC_NATIVE_KERNEL = (1 shl 1); + + // cl_command_queue_properties - bitfield + CL_QUEUE_OUT_OF_ORDER_EXEC_MODE_ENABLE = (1 shl 0); + CL_QUEUE_PROFILING_ENABLE = (1 shl 1); + + // cl_context_info + CL_CONTEXT_REFERENCE_COUNT = $1080; + CL_CONTEXT_DEVICES = $1081; + CL_CONTEXT_PROPERTIES_INFO = $1082; // CL_CONTEXT_PROPERTIES + CL_CONTEXT_NUM_DEVICES = $1083; + CL_CONTEXT_PLATFORM_INFO = $1084; // CL_CONTEXT_PLATFORM + + // cl_command_queue_info + CL_QUEUE_CONTEXT = $1090; + CL_QUEUE_DEVICE = $1091; + CL_QUEUE_REFERENCE_COUNT = $1092; + CL_QUEUE_PROPERTIES = $1093; + + // cl_mem_flags - bitfield + CL_MEM_READ_WRITE = (1 shl 0); + CL_MEM_WRITE_ONLY = (1 shl 1); + CL_MEM_READ_ONLY = (1 shl 2); + CL_MEM_USE_HOST_PTR = (1 shl 3); + CL_MEM_ALLOC_HOST_PTR = (1 shl 4); + CL_MEM_COPY_HOST_PTR = (1 shl 5); + + // cl_channel_order + CL_R = $10B0; + CL_A = $10B1; + CL_RG = $10B2; + CL_RA = $10B3; + CL_RGB = $10B4; + CL_RGBA = $10B5; + CL_BGRA = $10B6; + CL_ARGB = $10B7; + CL_INTENSITY = $10B8; + CL_LUMINANCE = $10B9; + + // cl_channel_type + CL_SNORM_INT8 = $10D0; + CL_SNORM_INT16 = $10D1; + CL_UNORM_INT8 = $10D2; + CL_UNORM_INT16 = $10D3; + CL_UNORM_SHORT_565 = $10D4; + CL_UNORM_SHORT_555 = $10D5; + CL_UNORM_INT_101010 = $10D6; + CL_SIGNED_INT8 = $10D7; + CL_SIGNED_INT16 = $10D8; + CL_SIGNED_INT32 = $10D9; + CL_UNSIGNED_INT8 = $10DA; + CL_UNSIGNED_INT16 = $10DB; + CL_UNSIGNED_INT32 = $10DC; + CL_HALF_FLOAT = $10DD; + CL_FLOAT_TYPE = $10DE; // CL_FLOAT + + // cl_mem_object_type + CL_MEM_OBJECT_BUFFER = $10F0; + CL_MEM_OBJECT_IMAGE2D = $10F1; + CL_MEM_OBJECT_IMAGE3D = $10F2; + + // cl_mem_info + CL_MEM_TYPE = $1100; + CL_MEM_FLAGS_INFO = $1101; // CL_MEM_FLAGS + CL_MEM_SIZE = $1102; + CL_MEM_HOST_PTR = $1103; + CL_MEM_MAP_COUNT = $1104; + CL_MEM_REFERENCE_COUNT = $1105; + CL_MEM_CONTEXT = $1106; + + // cl_image_info + CL_IMAGE_FORMAT_INFO = $1110; // CL_IMAGE_FORMAT + CL_IMAGE_ELEMENT_SIZE = $1111; + CL_IMAGE_ROW_PITCH = $1112; + CL_IMAGE_SLICE_PITCH = $1113; + CL_IMAGE_WIDTH = $1114; + CL_IMAGE_HEIGHT = $1115; + CL_IMAGE_DEPTH = $1116; + + // cl_addressing_mode + CL_ADDRESS_NONE = $1130; + CL_ADDRESS_CLAMP_TO_EDGE = $1131; + CL_ADDRESS_CLAMP = $1132; + CL_ADDRESS_REPEAT = $1133; + + // cl_filter_mode + CL_FILTER_NEAREST = $1140; + CL_FILTER_LINEAR = $1141; + + // cl_sampler_info + CL_SAMPLER_REFERENCE_COUNT = $1150; + CL_SAMPLER_CONTEXT = $1151; + CL_SAMPLER_NORMALIZED_COORDS = $1152; + CL_SAMPLER_ADDRESSING_MODE = $1153; + CL_SAMPLER_FILTER_MODE = $1154; + + // cl_map_flags - bitfield + CL_MAP_READ = (1 shl 0); + CL_MAP_WRITE = (1 shl 1); + + // cl_program_info + CL_PROGRAM_REFERENCE_COUNT = $1160; + CL_PROGRAM_CONTEXT = $1161; + CL_PROGRAM_NUM_DEVICES = $1162; + CL_PROGRAM_DEVICES = $1163; + CL_PROGRAM_SOURCE = $1164; + CL_PROGRAM_BINARY_SIZES = $1165; + CL_PROGRAM_BINARIES = $1166; + + // cl_program_build_info + CL_PROGRAM_BUILD_STATUS = $1181; + CL_PROGRAM_BUILD_OPTIONS = $1182; + CL_PROGRAM_BUILD_LOG = $1183; + + // cl_build_status + CL_BUILD_SUCCESS = 0; + CL_BUILD_NONE = -1; + CL_BUILD_ERROR = -2; + CL_BUILD_IN_PROGRESS = -3; + + // cl_kernel_info + CL_KERNEL_FUNCTION_NAME = $1190; + CL_KERNEL_NUM_ARGS = $1191; + CL_KERNEL_REFERENCE_COUNT = $1192; + CL_KERNEL_CONTEXT = $1193; + CL_KERNEL_PROGRAM = $1194; + + // cl_kernel_work_group_info + CL_KERNEL_WORK_GROUP_SIZE = $11B0; + CL_KERNEL_COMPILE_WORK_GROUP_SIZE = $11B1; + CL_KERNEL_LOCAL_MEM_SIZE = $11B2; + + // cl_event_info + CL_EVENT_COMMAND_QUEUE = $11D0; + CL_EVENT_COMMAND_TYPE = $11D1; + CL_EVENT_REFERENCE_COUNT = $11D2; + CL_EVENT_COMMAND_EXECUTION_STATUS = $11D3; + + // cl_command_type + CL_COMMAND_NDRANGE_KERNEL = $11F0; + CL_COMMAND_TASK = $11F1; + CL_COMMAND_NATIVE_KERNEL = $11F2; + CL_COMMAND_READ_BUFFER = $11F3; + CL_COMMAND_WRITE_BUFFER = $11F4; + CL_COMMAND_COPY_BUFFER = $11F5; + CL_COMMAND_READ_IMAGE = $11F6; + CL_COMMAND_WRITE_IMAGE = $11F7; + CL_COMMAND_COPY_IMAGE = $11F8; + CL_COMMAND_COPY_IMAGE_TO_BUFFER = $11F9; + CL_COMMAND_COPY_BUFFER_TO_IMAGE = $11FA; + CL_COMMAND_MAP_BUFFER = $11FB; + CL_COMMAND_MAP_IMAGE = $11FC; + CL_COMMAND_UNMAP_MEM_OBJECT = $11FD; + CL_COMMAND_MARKER = $11FE; + CL_COMMAND_WAIT_FOR_EVENTS = $11FF; + CL_COMMAND_BARRIER = $1200; + CL_COMMAND_ACQUIRE_GL_OBJECTS = $1201; + CL_COMMAND_RELEASE_GL_OBJECTS = $1202; + + // command execution status + CL_COMPLETE = $0; + CL_RUNNING = $1; + CL_SUBMITTED = $2; + CL_QUEUED = $3; + + // cl_profiling_info + CL_PROFILING_COMMAND_QUEUED = $1280; + CL_PROFILING_COMMAND_SUBMIT = $1281; + CL_PROFILING_COMMAND_START = $1282; + CL_PROFILING_COMMAND_END = $1283; + +type + TContextNotify = procedure(const Name: PAnsiChar; const Data: Pointer; + Size: size_t; Data2: Pointer)stdcall; + +var + clGetPlatformIDs: function(num_entries: cl_uint; platforms: Pcl_platform_id; + num_platforms: Pcl_uint): cl_int stdcall = nil; + clCreateContextFromType: function(const properties: Pcl_context_properties; + device_type: cl_device_type; pfn_notify: TContextNotify; user_data: Pointer; + errcode_ret: Pcl_int): Pcl_context stdcall = nil; + clGetDeviceInfo: function(device: Pcl_device_id; param_name: cl_device_info; + param_value_size: size_t; param_value: Pointer; + param_value_size_ret: psize_t): cl_int stdcall = nil; + clGetContextInfo: function(context: Pcl_context; param_name: cl_context_info; + param_value_size: size_t; param_value: Pointer; + param_value_size_ret: psize_t): cl_int stdcall = nil; + clCreateCommandQueue: function(context: Pcl_context; device: Pcl_device_id; + properties: cl_command_queue_properties; errcode_ret: Pcl_int) + : Pcl_command_queue stdcall = nil; + clCreateBuffer: function(context: Pcl_context; flags: cl_mem_flags; + Size: size_t; host_ptr: Pointer; errcode_ret: Pcl_int) + : Pcl_mem stdcall = nil; + clEnqueueReadBuffer: function(command_queue: Pcl_command_queue; + buffer: Pcl_mem; blocking_read: cl_bool; offset: size_t; cb: size_t; + ptr: Pointer; num_events_in_wait_list: cl_uint; + const event_wait_list: Pcl_event; event: Pcl_event): cl_int stdcall = nil; + clEnqueueWriteBuffer: function(command_queue: Pcl_command_queue; + buffer: Pcl_mem; blocking_write: cl_bool; offset: size_t; cb: size_t; + const ptr: Pointer; num_events_in_wait_list: cl_uint; + const event_wait_list: Pcl_event; event: Pcl_event): cl_int stdcall = nil; + clEnqueueCopyBuffer: function(command_queue: Pcl_command_queue; + src_buffer: Pcl_mem; dst_buffer: Pcl_mem; src_offset: size_t; + dst_offset: size_t; cb: size_t; num_events_in_wait_list: cl_uint; + const event_wait_list: Pcl_event; event: Pcl_event): cl_int stdcall = nil; + clEnqueueMapBuffer: function(command_queue: Pcl_command_queue; + buffer: Pcl_mem; blocking_map: cl_bool; map_flags: cl_map_flags; + offset: size_t; cb: size_t; num_events_in_wait_list: cl_uint; + const event_wait_list: Pcl_event; event: Pcl_event; errcode_ret: Pcl_int) + : Pointer stdcall = nil; + clEnqueueUnmapMemObject: function(command_queue: Pcl_command_queue; + memobj: Pcl_mem; mapped_ptr: Pointer; num_events_in_wait_list: cl_uint; + const event_wait_list: Pcl_event; event: Pcl_event): cl_int stdcall = nil; + clFlush: function(command_queue: Pcl_command_queue): cl_int stdcall = nil; + clFinish: function(command_queue: Pcl_command_queue): cl_int stdcall = nil; + clReleaseContext: function(context: Pcl_context): cl_int stdcall = nil; + clReleaseCommandQueue: function(command_queue: Pcl_command_queue) + : cl_int stdcall = nil; + clReleaseMemObject: function(memobj: Pcl_mem): cl_int stdcall = nil; + + DLLLoaded: Boolean = False; + +function GetErrString(const Status: cl_int): String; + +implementation + +uses + LibImport; + +var + Lib: TLibImport; + +procedure Init; +begin + Lib := TLibImport.Create('opencl.dll'); + if Lib.Loaded then + begin + @clGetPlatformIDs := Lib.GetProcAddr('clGetPlatformIDs'); + @clCreateContextFromType := Lib.GetProcAddr('clCreateContextFromType'); + @clGetDeviceInfo := Lib.GetProcAddr('clGetDeviceInfo'); + @clGetContextInfo := Lib.GetProcAddr('clGetContextInfo'); + @clCreateCommandQueue := Lib.GetProcAddr('clCreateCommandQueue'); + @clCreateBuffer := Lib.GetProcAddr('clCreateBuffer'); + @clEnqueueReadBuffer := Lib.GetProcAddr('clEnqueueReadBuffer'); + @clEnqueueWriteBuffer := Lib.GetProcAddr('clEnqueueWriteBuffer'); + @clEnqueueCopyBuffer := Lib.GetProcAddr('clEnqueueCopyBuffer'); + @clEnqueueMapBuffer := Lib.GetProcAddr('clEnqueueMapBuffer'); + @clEnqueueUnmapMemObject := Lib.GetProcAddr('clEnqueueUnmapMemObject'); + @clFlush := Lib.GetProcAddr('clFlush'); + @clFinish := Lib.GetProcAddr('clFinish'); + @clReleaseContext := Lib.GetProcAddr('clReleaseContext'); + @clReleaseCommandQueue := Lib.GetProcAddr('clReleaseCommandQueue'); + @clReleaseMemObject := Lib.GetProcAddr('clReleaseMemObject'); + DLLLoaded := Assigned(clGetPlatformIDs); + end; +end; + +procedure Deinit; +begin + Lib.Free; +end; + +function GetErrString(const Status: cl_int): String; +begin + Result := 'unknown error'; + case Status of + CL_SUCCESS: + Result := 'Success'; + CL_DEVICE_NOT_FOUND: + Result := 'device not found'; + CL_DEVICE_NOT_AVAILABLE: + Result := 'device not available'; + CL_DEVICE_COMPILER_NOT_AVAILABLE: + Result := 'compiler not available'; + CL_MEM_OBJECT_ALLOCATION_FAILURE: + Result := 'mem object allocation failure'; + CL_OUT_OF_RESOURCES: + Result := 'out of resources'; + CL_OUT_OF_HOST_MEMORY: + Result := 'out of host memory'; + CL_PROFILING_INFO_NOT_AVAILABLE: + Result := 'profiling info not available'; + CL_MEM_COPY_OVERLAP: + Result := 'mem copy overlap'; + CL_IMAGE_FORMAT_MISMATCH: + Result := 'image format mismatch'; + CL_IMAGE_FORMAT_NOT_SUPPORTED: + Result := 'image format not support'; + CL_BUILD_PROGRAM_FAILURE: + Result := 'build program failure'; + CL_MAP_FAILURE: + Result := 'map failure'; + + CL_INVALID_VALUE: + Result := 'invalid value'; + CL_INVALID_DEVICE_TYPE: + Result := 'invalid device type'; + CL_INVALID_PLATFORM: + Result := 'invalid platform'; + CL_INVALID_DEVICE: + Result := 'invalid device'; + CL_INVALID_CONTEXT: + Result := 'invalid context'; + CL_INVALID_QUEUE_PROPERTIES: + Result := 'invalid queue properties'; + CL_INVALID_COMMAND_QUEUE: + Result := 'invalid command queue'; + CL_INVALID_HOST_PTR: + Result := 'invalid host ptr'; + CL_INVALID_MEM_OBJECT: + Result := 'invalid mem object'; + CL_INVALID_IMAGE_FORMAT_DESCRIPTOR: + Result := 'invalid image format descriptor'; + CL_INVALID_IMAGE_SIZE: + Result := 'invalid image size'; + CL_INVALID_SAMPLER: + Result := 'invalid sampler'; + CL_INVALID_BINARY: + Result := 'invalid binary'; + CL_INVALID_BUILD_OPTIONS: + Result := 'invalid build options'; + CL_INVALID_PROGRAM: + Result := 'invalid program'; + CL_INVALID_PROGRAM_EXECUTABLE: + Result := 'invalid program executable'; + CL_INVALID_KERNEL_NAME: + Result := 'invalid kernel name'; + CL_INVALID_KERNEL_DEFINITION: + Result := 'invalid kernel definition'; + CL_INVALID_KERNEL: + Result := 'invalid kernel'; + CL_INVALID_ARG_INDEX: + Result := 'invalid arg index'; + CL_INVALID_ARG_VALUE: + Result := 'invalid arg value'; + CL_INVALID_ARG_SIZE: + Result := 'invalid arg size'; + CL_INVALID_KERNEL_ARGS: + Result := 'invalid kernel args'; + CL_INVALID_WORK_DIMENSION: + Result := 'invalid work dimension'; + CL_INVALID_WORK_GROUP_SIZE: + Result := 'invalid work group size'; + CL_INVALID_WORK_ITEM_SIZE: + Result := 'invalid work item size'; + CL_INVALID_GLOBAL_OFFSET: + Result := 'invalid global offset'; + CL_INVALID_EVENT_WAIT_LIST: + Result := 'invalid event wait list'; + CL_INVALID_EVENT: + Result := 'invalid event'; + CL_INVALID_OPERATION: + Result := 'invalid operation'; + CL_INVALID_GL_OBJECT: + Result := 'invalid gl object'; + CL_INVALID_BUFFER_SIZE: + Result := 'invalid buffer size'; + CL_INVALID_MIP_LEVEL: + Result := 'invalid mip level'; + CL_INVALID_GLOBAL_WORK_SIZE: + Result := 'invalid global work size'; + end; +end; + +initialization + +Init; + +finalization + +Deinit; + +end. diff --git a/common/Utils.pas b/common/Utils.pas index 0b35db1..ce54ed3 100644 --- a/common/Utils.pas +++ b/common/Utils.pas @@ -3,7 +3,7 @@ unit Utils; interface uses - Threading, SynCommons, + Threading, OpenCL, SynCommons, WinAPI.Windows, WinAPI.PsAPI, System.SysUtils, System.Classes, System.SyncObjs, System.Math, System.Types, System.AnsiStrings, System.StrUtils, System.IniFiles, System.IOUtils, @@ -136,7 +136,9 @@ type function Seek(const Offset: Int64; Origin: TSeekOrigin): Int64; override; procedure Clear; function Add(AStreamType: Pointer; MaxSize: Int64 = FMaxStreamSize) - : Integer; + : Integer overload; + function Add(AStream: TStream; MaxSize: Int64 = FMaxStreamSize) + : Integer overload; procedure Update(Index: Integer; MaxSize: Int64); function MaxSize(Index: Integer): NativeInt; end; @@ -278,21 +280,73 @@ type property OutSize: Int64 read FOutSize; end; - TCacheStream = class(TStream) + TCacheReadStream = class(TStream) + private const + FBufferSize = 4 * 1024 * 1024; private - FStream: TStream; + FSync: TSynLocker; + FOwnStream: Boolean; + FInput, FCache: TStream; + FBuffer: Pointer; FTask: TTask; - FMemory: PByte; FPosition1, FPosition2: Int64; - FAvaiSize, FMaxSize: Integer; + FAvaiSize, FMaxSize: Int64; FDone: Boolean; procedure CacheMemory; public - constructor Create(Stream: TStream; Size: Integer = 16 * 1024 * 1024); + constructor Create(Input, Cache: TStream; AOwnStream: Boolean = True); destructor Destroy; override; function Read(var Buffer; Count: Integer): Integer; override; end; + TCacheWriteStream = class(TStream) + private const + FBufferSize = 4 * 1024 * 1024; + private + FSync: TSynLocker; + FOwnStream: Boolean; + FOutput, FCache: TStream; + FBuffer: Pointer; + FTask: TTask; + FPosition1, FPosition2: Int64; + FUsedSize, FMaxSize: Int64; + FDone: Boolean; + procedure CacheMemory; + public + constructor Create(Output, Cache: TStream; AOwnStream: Boolean = True); + destructor Destroy; override; + function Write(const Buffer; Count: LongInt): LongInt; override; + end; + + TGPUMemoryStream = class(TStream) + private + FInitialized: Boolean; + FStatus: CL_int; + FCtxProps: array [0 .. 2] of PCL_context_properties; + FPlatCount: CL_uint; + FPlatform: PCL_platform_id; + FContext: PCL_context; + FCommandQueue: PCL_command_queue; + FDevCount: CL_int; + FDevices: TArray; + FDeviceName: array [0 .. 1023] of AnsiChar; + FDeviceSize: CL_ulong; + FMemory: PCL_mem; + FMaxSize: NativeInt; + FSize, FPosition: NativeInt; + procedure CheckError(Status: CL_int = CL_SUCCESS); + public + constructor Create(ASize: NativeInt); overload; + destructor Destroy; override; + procedure SetSize(const NewSize: Int64); override; + procedure SetSize(NewSize: LongInt); override; + function Read(var Buffer; Count: LongInt): LongInt; override; + function Write(const Buffer; Count: LongInt): LongInt; override; + function Seek(const Offset: Int64; Origin: TSeekOrigin): Int64; override; + function DeviceName: String; + function DeviceSize: Int64; + end; + TDataStore = class(TObject) public function Slot(Index: Integer): TMemoryStream; virtual; abstract; @@ -504,6 +558,10 @@ function GetCmdStr(CommandLine: String; Index: Integer; KeepQuotes: Boolean = False): string; function GetCmdCount(CommandLine: String): Integer; +var + GPUName: String; + GPUSize: Int64; + implementation function GetBits(Data: Int64; Index: TInt64_BitIndex; @@ -955,6 +1013,19 @@ begin FStreams[Pred(FCount)].MaxSize := EnsureRange(MaxSize, 0, FMaxStreamSize); end; +function TArrayStream.Add(AStream: TStream; MaxSize: Int64): Integer; +begin + Result := FCount; + Inc(FCount); + SetLength(FStreams, FCount); + FStreams[Pred(FCount)].Instance := AStream; + FStreams[Pred(FCount)].Instance.Position := 0; + FStreams[Pred(FCount)].Instance.Size := 0; + FStreams[Pred(FCount)].Position := 0; + FStreams[Pred(FCount)].Size := 0; + FStreams[Pred(FCount)].MaxSize := EnsureRange(MaxSize, 0, FMaxStreamSize); +end; + procedure TArrayStream.Update(Index: Integer; MaxSize: Int64); begin if FStreams[Index].Size < MaxSize then @@ -1850,37 +1921,60 @@ begin Result := WaitForSingleObject(FProcessInfo.hProcess, 0) = WAIT_TIMEOUT; end; -constructor TCacheStream.Create(Stream: TStream; Size: Integer); +constructor TCacheReadStream.Create(Input, Cache: TStream; AOwnStream: Boolean); begin inherited Create; - FStream := Stream; - GetMem(FMemory, Size); + FSync.Init; + FOwnStream := AOwnStream; + FInput := Input; + FCache := Cache; FPosition1 := 0; FPosition2 := 0; FAvaiSize := 0; - FMaxSize := Size; + if Assigned(FCache) then + FMaxSize := FCache.Size + else + FMaxSize := 0; FDone := False; FTask := TTask.Create; FTask.Perform(CacheMemory); - FTask.Start; + if FMaxSize > 0 then + begin + GetMem(FBuffer, FBufferSize); + FTask.Start; + end; end; -destructor TCacheStream.Destroy; +destructor TCacheReadStream.Destroy; begin FDone := True; - FTask.Wait; + if FMaxSize > 0 then + begin + FTask.Wait; + FreeMem(FBuffer); + end; FTask.Free; - FreeMem(FMemory); + if FOwnStream then + if FMaxSize > 0 then + FCache.Free; + FSync.Done; inherited Destroy; end; -procedure TCacheStream.CacheMemory; +procedure TCacheReadStream.CacheMemory; var - I: Integer; + I: Int64; begin AtomicExchange(I, FAvaiSize); - I := FStream.Read((FMemory + FPosition1 mod FMaxSize)^, - Min(FMaxSize - I, FMaxSize - (FPosition1 mod FMaxSize))); + I := FInput.Read(FBuffer^, Min(FBufferSize, Min(FMaxSize - I, + FMaxSize - (FPosition1 mod FMaxSize)))); + FSync.Lock; + try + FCache.Position := FPosition1 mod FMaxSize; + FCache.WriteBuffer(FBuffer^, I); + finally + FSync.UnLock; + end; while (I > 0) and (FDone = False) do begin Inc(FPosition1, I); @@ -1892,16 +1986,28 @@ begin if FDone then exit; end; - I := FStream.Read((FMemory + FPosition1 mod FMaxSize)^, - Min(FMaxSize - I, FMaxSize - (FPosition1 mod FMaxSize))); + I := FInput.Read(FBuffer^, Min(FBufferSize, Min(FMaxSize - I, + FMaxSize - (FPosition1 mod FMaxSize)))); + FSync.Lock; + try + FCache.Position := FPosition1 mod FMaxSize; + FCache.WriteBuffer(FBuffer^, I); + finally + FSync.UnLock; + end; end; FDone := True; end; -function TCacheStream.Read(var Buffer; Count: Integer): Integer; +function TCacheReadStream.Read(var Buffer; Count: Integer): Integer; var - I: Integer; + I: Int64; begin + if FMaxSize <= 0 then + begin + Result := FInput.Read(Buffer, Count); + exit; + end; if Count <= 0 then exit(0); AtomicExchange(I, FAvaiSize); @@ -1914,11 +2020,285 @@ begin break; end; Result := Min(Count, Min(I, FMaxSize - (FPosition2 mod FMaxSize))); - Move((FMemory + FPosition2 mod FMaxSize)^, Buffer, Result); + FSync.Lock; + try + FCache.Position := FPosition2 mod FMaxSize; + FCache.ReadBuffer(Buffer, Result); + finally + FSync.UnLock; + end; Inc(FPosition2, Result); AtomicDecrement(FAvaiSize, Result); end; +constructor TCacheWriteStream.Create(Output, Cache: TStream; + AOwnStream: Boolean); +begin + inherited Create; + FSync.Init; + FOwnStream := AOwnStream; + FOutput := Output; + FCache := Cache; + FPosition1 := 0; + FPosition2 := 0; + FUsedSize := 0; + if Assigned(FCache) then + FMaxSize := FCache.Size + else + FMaxSize := 0; + FDone := False; + FTask := TTask.Create; + FTask.Perform(CacheMemory); + if FMaxSize > 0 then + begin + GetMem(FBuffer, FBufferSize); + FTask.Start; + end; +end; + +destructor TCacheWriteStream.Destroy; +var + I: Int64; +begin + if FMaxSize > 0 then + begin + AtomicExchange(I, FUsedSize); + while I > 0 do + begin + Sleep(1); + AtomicExchange(I, FUsedSize); + end; + end; + FDone := True; + if FMaxSize > 0 then + begin + FTask.Wait; + FreeMem(FBuffer); + end; + FTask.Free; + if FOwnStream then + if FMaxSize > 0 then + FCache.Free; + FSync.Done; + inherited Destroy; +end; + +procedure TCacheWriteStream.CacheMemory; +var + I: Int64; +begin + AtomicExchange(I, FUsedSize); + I := Min(FBufferSize, Min(I, FMaxSize - (FPosition1 mod FMaxSize))); + FSync.Lock; + try + FCache.Position := FPosition1 mod FMaxSize; + FCache.ReadBuffer(FBuffer^, I); + finally + FSync.UnLock; + end; + FOutput.WriteBuffer(FBuffer^, I); + while True do + begin + Inc(FPosition1, I); + I := AtomicDecrement(FUsedSize, I); + while (I = 0) and (FDone = False) do + begin + Sleep(1); + AtomicExchange(I, FUsedSize); + end; + I := Min(FBufferSize, Min(I, FMaxSize - (FPosition1 mod FMaxSize))); + FSync.Lock; + try + FCache.Position := FPosition1 mod FMaxSize; + FCache.ReadBuffer(FBuffer^, I); + finally + FSync.UnLock; + end; + FOutput.WriteBuffer(FBuffer^, I); + if FDone and (FPosition1 = FPosition2) then + break; + end; +end; + +function TCacheWriteStream.Write(const Buffer; Count: LongInt): LongInt; +var + I: Int64; +begin + if FMaxSize <= 0 then + begin + FOutput.WriteBuffer(Buffer, Count); + exit(Count); + end; + if Count <= 0 then + exit(0); + AtomicExchange(I, FUsedSize); + if I = FMaxSize then + while True do + begin + Sleep(1); + AtomicExchange(I, FUsedSize); + if (I < FMaxSize) then + break; + end; + Result := Min(Count, Min(FMaxSize - I, FMaxSize - (FPosition2 mod FMaxSize))); + FSync.Lock; + try + FCache.Position := FPosition2 mod FMaxSize; + FCache.WriteBuffer(Buffer, Result); + finally + FSync.UnLock; + end; + Inc(FPosition2, Result); + AtomicIncrement(FUsedSize, Result); +end; + +constructor TGPUMemoryStream.Create(ASize: NativeInt); +begin + inherited Create; + FInitialized := False; + if not OpenCL.DLLLoaded then + raise Exception.CreateFmt('OpenCL: %s', ['opencl.dll could not be loaded']); + FStatus := clGetPlatformIDs(0, nil, @FPlatCount); + CheckError; + FStatus := clGetPlatformIDs(FPlatCount, @FPlatform, nil); + CheckError; + FCtxProps[0] := PCL_context_properties(CL_CONTEXT_PLATFORM_INFO); + FCtxProps[1] := PCL_context_properties(FPlatform); + FCtxProps[2] := nil; + FContext := clCreateContextFromType(@FCtxProps, CL_DEVICE_TYPE_GPU, nil, nil, + @FStatus); + CheckError; + FStatus := clGetContextInfo(FContext, CL_CONTEXT_DEVICES, 0, nil, @FDevCount); + CheckError; + if FDevCount <= 0 then + CheckError(CL_DEVICE_NOT_AVAILABLE); + SetLength(FDevices, FDevCount); + FStatus := clGetContextInfo(FContext, CL_CONTEXT_DEVICES, FDevCount, + @FDevices[0], nil); + CheckError; + FillChar(FDeviceName, sizeof(FDeviceName), #0); + FStatus := clGetDeviceInfo(FDevices[0], CL_DEVICE_NAME, sizeof(FDeviceName), + @FDeviceName[0], nil); + CheckError; + FStatus := clGetDeviceInfo(FDevices[0], CL_DEVICE_GLOBAL_MEM_SIZE, + sizeof(FDeviceSize), @FDeviceSize, nil); + CheckError; + FCommandQueue := clCreateCommandQueue(FContext, FDevices[0], 0, @FStatus); + CheckError; + FMemory := clCreateBuffer(FContext, CL_MEM_ALLOC_HOST_PTR or + CL_MEM_READ_WRITE, ASize, nil, @FStatus); + CheckError; + FInitialized := True; + FMaxSize := ASize; + FPosition := 0; + FSize := 0; +end; + +destructor TGPUMemoryStream.Destroy; +begin + if FInitialized then + begin + clReleaseMemObject(FMemory); + clReleaseCommandQueue(FCommandQueue); + clReleaseContext(FContext); + end; + inherited Destroy; +end; + +procedure TGPUMemoryStream.SetSize(NewSize: LongInt); +begin + SetSize(Int64(NewSize)); +end; + +procedure TGPUMemoryStream.SetSize(const NewSize: Int64); +var + OldPosition: NativeInt; +begin + OldPosition := FPosition; + if NewSize <= FMaxSize then + FSize := NewSize; + if OldPosition > NewSize then + Seek(0, soEnd); +end; + +function TGPUMemoryStream.Read(var Buffer; Count: LongInt): LongInt; +begin + Result := 0; + if not FInitialized then + exit; + if (FPosition >= 0) and (Count >= 0) then + begin + if FSize - FPosition > 0 then + begin + if FSize > Count + FPosition then + Result := Count + else + Result := FSize - FPosition; + FStatus := clEnqueueReadBuffer(FCommandQueue, FMemory, CL_TRUE, FPosition, + Result, @Buffer, 0, nil, nil); + Inc(FPosition, Result); + end; + end; +end; + +function TGPUMemoryStream.Write(const Buffer; Count: LongInt): LongInt; +var + FCount: LongInt; +begin + Result := 0; + if not FInitialized then + exit; + FCount := Count; + if FPosition + FCount > FMaxSize then + FCount := FMaxSize - FPosition; + if (FPosition >= 0) and (FCount >= 0) then + begin + FStatus := clEnqueueWriteBuffer(FCommandQueue, FMemory, CL_TRUE, FPosition, + FCount, @Buffer, 0, nil, nil); + CheckError; + Inc(FPosition, FCount); + if FPosition > FSize then + FSize := FPosition; + Result := FCount; + end; +end; + +function TGPUMemoryStream.Seek(const Offset: Int64; Origin: TSeekOrigin): Int64; +begin + case Origin of + soBeginning: + FPosition := Offset; + soCurrent: + Inc(FPosition, Offset); + soEnd: + FPosition := FSize + Offset; + end; + Result := Min(FPosition, FMaxSize); +end; + +procedure TGPUMemoryStream.CheckError(Status: CL_int); +var + LStatus: CL_int; +begin + if Status <> CL_SUCCESS then + LStatus := Status + else + LStatus := FStatus; + if LStatus = CL_SUCCESS then + exit; + raise Exception.CreateFmt('OpenCL: %s', [OpenCL.GetErrString(LStatus)]); +end; + +function TGPUMemoryStream.DeviceName: String; +begin + Result := String(FDeviceName); +end; + +function TGPUMemoryStream.DeviceSize: Int64; +begin + Result := FDeviceSize; +end; + constructor TDataStore1.Create(AInput: TStream; ADynamic: Boolean; ASlots, ASize: NativeInt; ATempFile: String); var @@ -3899,4 +4279,23 @@ begin Inc(Result); end; +var + LGPU: TGPUMemoryStream; + +initialization + +GPUName := ''; +GPUSize := 0; +try + LGPU := TGPUMemoryStream.Create(65536); + with LGPU do + try + GPUName := DeviceName; + GPUSize := DeviceSize; + finally + Free; + end; +except +end; + end. diff --git a/imports/FLZMA2DLL.pas b/imports/FLZMA2DLL.pas index bf5ff44..4f41b61 100644 --- a/imports/FLZMA2DLL.pas +++ b/imports/FLZMA2DLL.pas @@ -18,6 +18,9 @@ const FL2_DICTSIZE_MIN = (1 shl FL2_DICTLOG_MIN); FL2_DICTSIZE_MAX = (1 shl FL2_DICTLOG_MAX); + FL2_BLOCK_OVERLAP_MIN = 0; + FL2_BLOCK_OVERLAP_MAX = 14; + type PFL2_inBuffer = ^FL2_inBuffer; @@ -165,7 +168,7 @@ type FBufferSize = 65536; private FCtx: Pointer; - FThreads, FLevel, FDictionary: Integer; + FThreads, FLevel, FDictionary, FOverlap: Integer; FHighCompress: boolean; FOutput: TStream; FBuffer: array [0 .. FBufferSize - 1] of Byte; @@ -180,6 +183,7 @@ type property Level: Integer read FLevel write FLevel; property Dictionary: Integer read FDictionary write FDictionary; property HighCompress: boolean read FHighCompress write FHighCompress; + property Overlap: Integer read FOverlap write FOverlap; property InSize: Int64 read FInSize; property OutSize: Int64 read FOutSize; end; @@ -213,6 +217,7 @@ begin FLevel := 6; FDictionary := 0; FHighCompress := False; + FOverlap := -1; FOutput := AOutput; FInSize := 0; FOutSize := 0; @@ -246,6 +251,9 @@ begin if FDictionary > 0 then FL2_CStream_setParameter(FCtx, FL2_cParameter.FL2_p_dictionarySize, FDictionary); + if FOverlap >= 0 then + FL2_CStream_setParameter(FCtx, FL2_cParameter.FL2_p_overlapFraction, + FOverlap); FL2_initCStream(FCtx, 0); FInitialized := True; end; diff --git a/precompressor/PrecompLZO.pas b/precompressor/PrecompLZO.pas index a24680d..743513f 100644 --- a/precompressor/PrecompLZO.pas +++ b/precompressor/PrecompLZO.pas @@ -29,7 +29,7 @@ const var SOList: array of array [0 .. CODEC_COUNT - 1] of TSOList; - WrkMem: array of array [0 .. L_WORKMEM - 1] of Byte; + WrkMem: array of Pointer; LZO1XVariant: Integer = LZO1X_999; LZO2AVariant: Integer = LZO2A_999; LZO1CVariant: Integer = LZO1C_999; @@ -158,6 +158,11 @@ begin end; Inc(X); end; + if CodecAvailable[LZO1X_CODEC] then + begin + for X := Low(WrkMem) to High(WrkMem) do + WrkMem[X] := nil; + end; SetLength(Options, 0); for I := 1 to 9 do Insert(I, Options, Length(Options)); @@ -179,6 +184,12 @@ begin for X := Low(SOList) to High(SOList) do for Y := Low(SOList[X]) to High(SOList[X]) do SOList[X, Y].Free; + if CodecAvailable[LZO1X_CODEC] then + begin + for X := Low(WrkMem) to High(WrkMem) do + if Assigned(WrkMem[X]) then + FreeMemory(WrkMem[X]); + end; end; function LZOParse(Command: PChar; Option: PInteger; @@ -384,6 +395,8 @@ begin end; end; Params := ''; + if not Assigned(WrkMem[Instance]) then + WrkMem[Instance] := GetMemory(L_WORKMEM); Res1 := StreamInfo^.NewSize; case X of LZO1X_CODEC: @@ -394,7 +407,7 @@ begin GetBits(StreamInfo^.Option, 12, 12).ToString; if not Result then if not lzo1x_999_compress_level(NewInput, StreamInfo^.NewSize, - Buffer, @Res1, @WrkMem[Instance, 0], nil, 0, nil, I) = 0 then + Buffer, @Res1, WrkMem[Instance], nil, 0, nil, I) = 0 then Res1 := 0; end; end; @@ -405,7 +418,7 @@ begin Params := 'v' + GetBits(StreamInfo^.Option, 12, 12).ToString; if not Result then if not lzo2a_999_compress(NewInput, StreamInfo^.NewSize, Buffer, - @Res1, @WrkMem[Instance, 0]) = 0 then + @Res1, WrkMem[Instance]) = 0 then Res1 := 0; end; end; @@ -416,7 +429,7 @@ begin Params := 'v' + GetBits(StreamInfo^.Option, 12, 12).ToString; if not Result then if not lzo1c_999_compress(NewInput, StreamInfo^.NewSize, Buffer, - @Res1, @WrkMem[Instance, 0]) = 0 then + @Res1, WrkMem[Instance]) = 0 then Res1 := 0; end; end; @@ -467,6 +480,8 @@ begin exit; Params := ''; Buffer := Funcs^.Allocator(Instance, StreamInfo.NewSize); + if not Assigned(WrkMem[Instance]) then + WrkMem[Instance] := GetMemory(L_WORKMEM); Res1 := StreamInfo.NewSize; case X of LZO1X_CODEC: @@ -476,8 +491,8 @@ begin Params := 'l' + GetBits(StreamInfo.Option, 5, 7).ToString + ':' + 'v' + GetBits(StreamInfo.Option, 12, 12).ToString; if not lzo1x_999_compress_level(Input, StreamInfo.NewSize, Buffer, - @Res1, @WrkMem[Instance, 0], nil, 0, nil, - GetBits(StreamInfo.Option, 5, 7)) = 0 then + @Res1, WrkMem[Instance], nil, 0, nil, GetBits(StreamInfo.Option, + 5, 7)) = 0 then Res1 := 0; end; end; @@ -487,7 +502,7 @@ begin begin Params := 'v' + GetBits(StreamInfo.Option, 12, 12).ToString; if not lzo2a_999_compress(Input, StreamInfo.NewSize, Buffer, @Res1, - @WrkMem[Instance, 0]) = 0 then + WrkMem[Instance]) = 0 then Res1 := 0; end; end; @@ -497,7 +512,7 @@ begin begin Params := 'v' + GetBits(StreamInfo.Option, 12, 12).ToString; if not lzo2a_999_compress(Input, StreamInfo.NewSize, Buffer, @Res1, - @WrkMem[Instance, 0]) = 0 then + WrkMem[Instance]) = 0 then Res1 := 0; end; end; diff --git a/precompressor/PrecompMain.pas b/precompressor/PrecompMain.pas index 166790d..6ef18ab 100644 --- a/precompressor/PrecompMain.pas +++ b/precompressor/PrecompMain.pas @@ -17,6 +17,7 @@ uses const XTOOL_PRECOMP = $304C5458; + XTOOL_BSIZE = 4194304; type PEncodeOptions = ^TEncodeOptions; @@ -28,14 +29,16 @@ type LowMem: Boolean; DBaseFile, ExtractDir: String; CThreads, CLevel: Integer; - CDict: Integer; + CDict, COverlap: Integer; + CHighCompress: Boolean; end; PDecodeOptions = ^TDecodeOptions; TDecodeOptions = record Method: String; - CacheSize, Threads: Integer; + Threads: Integer; + CacheSize: Int64; Depth: Integer; DedupSysMem: Int64; end; @@ -111,7 +114,9 @@ var VERBOSE: Boolean = False; EXTRACT: Boolean = False; NOVERIFY: Boolean = False; - COMPRESS: Boolean = False; + COMPRESS: Byte = 0; + EXTCOMP: String = ''; + GPUMEM: Int64 = 0; NULLOUT: Boolean = False; DupSysMem: Int64 = 0; DecodeMemBlock: Int64 = 512 * 1024 * 1024; @@ -120,6 +125,16 @@ var ConTask: TTask; Stopwatch: TStopwatch; +function ExtractExec(S: String): String; +begin + Result := S.Substring(0, Pos('.exe', S) + 3); +end; + +function ExtractParams(S: String): String; +begin + Result := S.Substring(Pos('.exe', S) + 4); +end; + procedure PrintHelp; var I, J: Integer; @@ -178,6 +193,17 @@ begin Options.Method := S; Inc(I); end; + S := ArgParse.AsString('-g', 0, '0'); + S := ReplaceText(S, 'KB', '* 1024^1'); + S := ReplaceText(S, 'MB', '* 1024^2'); + S := ReplaceText(S, 'GB', '* 1024^3'); + S := ReplaceText(S, 'K', '* 1024^1'); + S := ReplaceText(S, 'M', '* 1024^2'); + S := ReplaceText(S, 'G', '* 1024^3'); + S := ReplaceText(S, 'p', '%'); + S := ReplaceText(S, '%', '%*' + GPUSize.ToString); + GPUMEM := EnsureRange(Round(ExpParse.Evaluate(S)), 0, + Max(0, GPUSize - 512 * 1024 * 1024)); S := ArgParse.AsString('-c', 0, '16mb'); S := ReplaceText(S, 'KB', '* 1024^1'); S := ReplaceText(S, 'MB', '* 1024^2'); @@ -185,7 +211,8 @@ begin S := ReplaceText(S, 'K', '* 1024^1'); S := ReplaceText(S, 'M', '* 1024^2'); S := ReplaceText(S, 'G', '* 1024^3'); - Options.ChunkSize := Max(4 * 1024 * 1024, Round(ExpParse.Evaluate(S))); + Options.ChunkSize := EnsureRange(Round(ExpParse.Evaluate(S)), + 4 * 1024 * 1024, 2047 * 1024 * 1024); S := ArgParse.AsString('-t', 0, '50p'); S := ReplaceText(S, 'p', '%'); S := ReplaceText(S, '%', '%*' + CPUCount.ToString); @@ -197,7 +224,7 @@ begin S := ReplaceText(S, 'K', '* 1024^1'); S := ReplaceText(S, 'M', '* 1024^2'); S := ReplaceText(S, 'G', '* 1024^3'); - DecodeMemBlock := Max(32 * 1024 * 1024, Round(ExpParse.Evaluate(S))); } + DecodeMemBlock := EnsureRange(Round(ExpParse.Evaluate(S)), 32 * 1024 * 1024, 2047 * 1024 * 1024); } StoreDD := -2; I := 0; while True do @@ -244,14 +271,24 @@ begin begin List := DecodeStr(S, ':'); Options.CThreads := Options.Threads; - Options.CLevel := StrToIntDef(List[0], 0); + Options.CHighCompress := List[0].Contains('x'); + if List[0].Contains('x') then + Options.CLevel := + StrToIntDef(Copy(List[0], 1, List[0].Length - 1), 0) + else + Options.CLevel := StrToIntDef(List[0], 0); + Options.COverlap := 2; for J := Low(List) to High(List) do begin if List[J].StartsWith('d', False) then Options.CDict := EnsureRange(ConvertToBytes(List[J].Substring(1) ), FL2_DICTSIZE_MIN, FL2_DICTSIZE_MAX); + if List[J].StartsWith('o', False) then + Options.COverlap := + EnsureRange(ConvertToBytes(List[J].Substring(1)), + FL2_BLOCK_OVERLAP_MIN, FL2_BLOCK_OVERLAP_MAX); end; - COMPRESS := InRange(Options.CLevel, 1, 10); + COMPRESS := Byte(InRange(Options.CLevel, 1, 10)); end; end; end; @@ -264,6 +301,9 @@ begin Options.ExtractDir := ArgParse.AsString('-x'); if Options.ExtractDir <> '' then EXTRACT := DirectoryExists(Options.ExtractDir); + EXTCOMP := ArgParse.AsString('-e'); + if FileExists(ExpandPath(PluginsPath + ExtractExec(EXTCOMP), True)) then + COMPRESS := 2; finally ArgParse.Free; ExpParse.Free; @@ -283,14 +323,27 @@ begin ExpParse := TExpressionParser.Create; try Options.Method := ArgParse.AsString('-m'); - S := ArgParse.AsString('-c', 0, '64mb'); + S := ArgParse.AsString('-g', 0, '0'); S := ReplaceText(S, 'KB', '* 1024^1'); S := ReplaceText(S, 'MB', '* 1024^2'); S := ReplaceText(S, 'GB', '* 1024^3'); S := ReplaceText(S, 'K', '* 1024^1'); S := ReplaceText(S, 'M', '* 1024^2'); S := ReplaceText(S, 'G', '* 1024^3'); - Options.CacheSize := Max(4 * 1024 * 1024, Round(ExpParse.Evaluate(S))); + S := ReplaceText(S, 'p', '%'); + S := ReplaceText(S, '%', '%*' + GPUSize.ToString); + GPUMEM := EnsureRange(Round(ExpParse.Evaluate(S)), 0, + Max(0, GPUSize - 512 * 1024 * 1024)); + S := ArgParse.AsString('-c', 0, '25p'); + S := ReplaceText(S, 'KB', '* 1024^1'); + S := ReplaceText(S, 'MB', '* 1024^2'); + S := ReplaceText(S, 'GB', '* 1024^3'); + S := ReplaceText(S, 'K', '* 1024^1'); + S := ReplaceText(S, 'M', '* 1024^2'); + S := ReplaceText(S, 'G', '* 1024^3'); + S := ReplaceText(S, 'p', '%'); + S := ReplaceText(S, '%', '%*' + GPUMEM.ToString); + Options.CacheSize := EnsureRange(Round(ExpParse.Evaluate(S)), 0, GPUSize); S := ArgParse.AsString('-t', 0, '50p'); S := ReplaceText(S, 'p', '%'); S := ReplaceText(S, '%', '%*' + CPUCount.ToString); @@ -310,6 +363,7 @@ begin Options.DedupSysMem := -Options.DedupSysMem; SrepMemCfg := ArgParse.AsString('-sm', 0, '75p').ToLower; VERBOSE := ArgParse.AsBoolean('-v'); + EXTCOMP := ArgParse.AsString('-e'); finally ArgParse.Free; ExpParse.Free; @@ -1592,7 +1646,7 @@ var DupIdx1, DupIdx2, DupCount: Integer; DupTyp: TDuplicate2; ErrStream: TStringStream; - + LOutput, LCache: TStream; procedure SaveResources; var C, D: Integer; @@ -1621,30 +1675,54 @@ var end; end; + procedure UpdateInfo; + begin + if NULLOUT then + if StoreDD > 0 then + EncInfo.SrepSize := TProcessStream(TBufferedStream(LOutput) + .Instance).OutSize; + if COMPRESS = 1 then + EncInfo.CompSize := TLZMACompressStream(Output).OutSize + else if COMPRESS = 2 then + EncInfo.CompSize := TProcessStream(TBufferedStream(Output) + .Instance).OutSize; + end; + begin if (Depth = 0) then begin + LCache := nil; + if GPUMEM > 0 then + try + LCache := TGPUMemoryStream.Create(GPUMEM); + except + LCache := nil; + end; + if Assigned(LCache) then + LCache.Size := GPUMEM; ErrStream := TStringStream.Create; if NULLOUT then begin if StoreDD > 0 then begin - TempOutput := TBufferedStream.Create + LOutput := TBufferedStream.Create (TProcessStream.Create(ExpandPath(PluginsPath + 'srep.exe', True), '-m' + StoreDD.ToString + ' -s' + SrepInSize + ' - -', GetCurrentDir, - nil, Output, ErrStream), False, 4194304); - TProcessStream(TBufferedStream(TempOutput).Instance).Execute; + nil, Output, ErrStream), False, XTOOL_BSIZE); + TProcessStream(TBufferedStream(LOutput).Instance).Execute; end else - TempOutput := Output; + LOutput := Output; end else if StoreDD > -2 then - TempOutput := TBufferedStream.Create + LOutput := TBufferedStream.Create (TFileStream.Create (LowerCase(ChangeFileExt(ExtractFileName(Utils.GetModuleName), - '-dd.tmp')), fmCreate or fmShareDenyNone), False, 4194304) + '-dd.tmp')), fmCreate or fmShareDenyNone), False, XTOOL_BSIZE) else - TempOutput := Output; + LOutput := Output; + TempOutput := TBufferedStream.Create(TCacheWriteStream.Create(LOutput, + LCache), False, XTOOL_BSIZE); end else TempOutput := Output; @@ -1886,12 +1964,7 @@ begin end; if Depth = 0 then begin - if NULLOUT then - if StoreDD > 0 then - EncInfo.SrepSize := TProcessStream(TBufferedStream(TempOutput) - .Instance).OutSize; - if COMPRESS then - EncInfo.CompSize := TLZMACompressStream(Output).OutSize; + UpdateInfo; TDataStore1(DataStore).LoadEx; if Length(Tasks) > 1 then WaitForAll(Tasks); @@ -1959,18 +2032,21 @@ begin begin if StoreDD > 0 then begin - TBufferedStream(TempOutput).Flush; - TProcessStream(TBufferedStream(TempOutput).Instance) - .WriteBuffer(StoreDD, 0); - TProcessStream(TBufferedStream(TempOutput).Instance).Wait; - TProcessStream(TBufferedStream(TempOutput).Instance).Done; TempOutput.Free; + TBufferedStream(LOutput).Flush; + TProcessStream(TBufferedStream(LOutput).Instance) + .WriteBuffer(StoreDD, 0); + TProcessStream(TBufferedStream(LOutput).Instance).Wait; + TProcessStream(TBufferedStream(LOutput).Instance).Done; + UpdateInfo; + LOutput.Free; end; end else begin - S := TFileStream(TBufferedStream(TempOutput).Instance).FileName; - TBufferedStream(TempOutput).Flush; + S := TFileStream(TBufferedStream(LOutput).Instance).FileName; + TempOutput.Free; + TBufferedStream(LOutput).Flush; if StoreDD > 0 then begin with TProcessStream.Create(ExpandPath(PluginsPath + 'srep.exe', True), @@ -1992,16 +2068,20 @@ begin end; end else - Output.CopyFrom(TBufferedStream(TempOutput).Instance, 0); - TempOutput.Free; + Output.CopyFrom(TBufferedStream(LOutput).Instance, 0); + LOutput.Free; DeleteFile(S); end; end else + begin + UpdateInfo; + TempOutput.Free; try EncFree; finally end; + end; S := 'Decompression memory is '; I := ErrStream.DataString.IndexOf(S); J := 0; @@ -2077,7 +2157,7 @@ var DDList2: TArray; DDCount2: Integer; DDIndex1, DDIndex2: Integer; - CacheSize: Integer; + CacheSize: Int64; procedure PrecompOutput2(Instance: Integer; const Buffer: Pointer; Size: Integer); @@ -2241,17 +2321,30 @@ end; procedure DecInit(Input, Output: TStream; Options: PDecodeOptions); var I, J, K: Integer; + I64: Int64; B: Byte; Bytes: TBytes; UI32: UInt32; DupTyp: TDuplicate1; LResData: TResData; + LStream: TStream; begin GlobalSync := TCriticalSection.Create; SetLength(ThreadSync, Options^.Threads); for I := Low(ThreadSync) to High(ThreadSync) do ThreadSync[I] := TCriticalSection.Create; DupSysMem := Options^.DedupSysMem; + I64 := GPUMEM - Options^.CacheSize; + if I64 > 0 then + begin + try + LStream := TGPUMemoryStream.Create(I64); + except + I64 := 0; + end; + if I64 > 0 then + NStream.Add(LStream, I64); + end; NStream.Add(TypeInfo(TMemoryStream), CalcSysMem); NStream.Add(TypeInfo(TPrecompVMStream)); Input.ReadBuffer(Options^.Depth, Options^.Depth.Size); @@ -2377,6 +2470,7 @@ var UI32: UInt32; I, J: Integer; LStream: TProcessStream; + LCache: TStream; procedure LoadResources; var C, D: Integer; @@ -2419,6 +2513,15 @@ begin DDIndex2 := 0; end; LogInt64 := 0; + LCache := nil; + if CacheSize > 0 then + try + LCache := TGPUMemoryStream.Create(CacheSize); + except + LCache := nil; + end; + if Assigned(LCache) then + LCache.Size := CacheSize; end; with ComVars2[Depth] do begin @@ -2428,10 +2531,12 @@ begin True), '-d -s -mem' + SrepMemCfg + ' - -', GetCurrentDir, Input, nil); if not LStream.Execute then raise EReadError.CreateRes(@SReadError); - DecInput[Index] := TCacheStream.Create(LStream, CacheSize); + DecInput[Index] := TBufferedStream.Create(TCacheReadStream.Create(LStream, + LCache), True, XTOOL_BSIZE); end else if Depth = 0 then - DecInput[Index] := TCacheStream.Create(Input, CacheSize) + DecInput[Index] := TBufferedStream.Create(TCacheReadStream.Create(Input, + LCache), True, XTOOL_BSIZE) else DecInput[Index] := Input; DecOutput[Index] := Output; @@ -2617,8 +2722,8 @@ var ' >> ' + ConvertKB2TB((EncInfo.InflSize + EncInfo.DupSize2) div 1024), '') + ' >> ' + ConvertKB2TB(EncInfo.InflSize div 1024) + IfThen(StoreDD > 0, ' >> ' + ConvertKB2TB((EncInfo.SrepSize) div 1024), - '') + IfThen(COMPRESS, ' >> ' + ConvertKB2TB((EncInfo.CompSize) div 1024), - '') + ' '; + '') + IfThen(COMPRESS > 0, ' >> ' + ConvertKB2TB((EncInfo.CompSize) + div 1024), '') + ' '; SetConsoleCursorPosition(FHandle, Coords); WriteConsole(FHandle, PChar(SL.Text), Length(SL.Text), ulLength, nil); end; @@ -2695,38 +2800,83 @@ end; procedure Encode(Input, Output: TStream; Options: TEncodeOptions); var - Compressed: Boolean; - LOutput: TStream; + Compressed: Byte; + LInput, LOutput: TStream; + LCache: TStream; begin + LCache := nil; + { if GPUMEM > 0 then + try + LCache := TGPUMemoryStream.Create(GPUMEM); + except + LCache := nil; + end; } + if Assigned(LCache) then + LCache.Size := GPUMEM; + LInput := TCacheReadStream.Create(Input, LCache); NULLOUT := TBufferedStream(Output).Instance is TNullStream; FillChar(EncInfo, SizeOf(EncInfo), 0); ConTask := TTask.Create; + if GPUMEM > 0 then + WriteLn(ErrOutput, GPUName + ' (' + ConvertKB2TB(GPUMEM div 1024) + + ' loaded)'); Stopwatch := TStopwatch.Create; Stopwatch.Start; ConTask.Perform(EncodeStats); if not VERBOSE then ConTask.Start; try - EncInit(Input, Output, @Options); + EncInit(LInput, Output, @Options); Compressed := COMPRESS; Output.WriteBuffer(Compressed, Compressed.Size); - if COMPRESS then + if COMPRESS > 0 then begin - LOutput := TLZMACompressStream.Create(Output); - with LOutput as TLZMACompressStream do - begin - Threads := Options.CThreads; - Dictionary := Options.CDict; + case COMPRESS of + 1: + begin + LOutput := TLZMACompressStream.Create(Output); + with LOutput as TLZMACompressStream do + begin + Level := Options.CLevel; + Threads := Options.CThreads; + Dictionary := Options.CDict; + Overlap := Options.COverlap; + HighCompress := Options.CHighCompress + end; + end; + 2: + begin + LOutput := TBufferedStream.Create + (TProcessStream.Create(ExpandPath(PluginsPath + + ExtractExec(EXTCOMP), True), ExtractParams(EXTCOMP), + GetCurrentDir, nil, Output), False, XTOOL_BSIZE); + TProcessStream(TBufferedStream(LOutput).Instance).Execute; + end; end; end else LOutput := Output; - EncData(Input, LOutput, 0, 0); + EncData(LInput, LOutput, 0, 0); finally - if COMPRESS then + if COMPRESS > 0 then begin - TLZMACompressStream(LOutput).Flush; - EncInfo.CompSize := TLZMACompressStream(LOutput).OutSize; + case COMPRESS of + 1: + TLZMACompressStream(LOutput).Flush; + 2: + begin + TBufferedStream(LOutput).Flush; + TProcessStream(TBufferedStream(LOutput).Instance) + .WriteBuffer(StoreDD, 0); + TProcessStream(TBufferedStream(LOutput).Instance).Wait; + TProcessStream(TBufferedStream(LOutput).Instance).Done; + end; + end; + if COMPRESS = 1 then + EncInfo.CompSize := TLZMACompressStream(LOutput).OutSize + else if COMPRESS = 2 then + EncInfo.CompSize := TProcessStream(TBufferedStream(LOutput) + .Instance).OutSize; LOutput.Free; end; try @@ -2740,15 +2890,19 @@ begin EncodeStats; ConTask.Wait; ConTask.Free; + LInput.Free; end; procedure Decode(Input, Output: TStream; Options: TDecodeOptions); var - Compressed: Boolean; + Compressed: Byte; LInput: TStream; begin FillChar(EncInfo, SizeOf(EncInfo), 0); ConTask := TTask.Create; + if GPUMEM > 0 then + WriteLn(ErrOutput, GPUName + ' (' + ConvertKB2TB(GPUMEM div 1024) + + ' loaded)'); Stopwatch := TStopwatch.Create; Stopwatch.Start; ConTask.Perform(DecodeStats); @@ -2758,14 +2912,29 @@ begin try DecInit(Input, Output, @Options); Input.ReadBuffer(Compressed, Compressed.Size); - if Compressed then + if Compressed = 1 then LInput := TLZMADecompressStream.Create(Input) + else if Compressed = 2 then + begin + LInput := TProcessStream.Create + (ExpandPath(PluginsPath + ExtractExec(EXTCOMP), True), + ExtractParams(EXTCOMP), GetCurrentDir, Input); + TProcessStream(LInput).Execute; + end else LInput := Input; DecChunk(LInput, Output, 0, 0); finally - if Compressed then + if Compressed > 0 then + begin + if Compressed = 2 then + with LInput as TProcessStream do + begin + Wait; + Done; + end; LInput.Free; + end; try NStream.Free; DecFree; diff --git a/precompressor/PrecompMedia.pas b/precompressor/PrecompMedia.pas index 89d0670..1808af3 100644 --- a/precompressor/PrecompMedia.pas +++ b/precompressor/PrecompMedia.pas @@ -431,8 +431,8 @@ begin SetLength(dcd, Count); for X := Low(cctx) to High(cctx) do begin - cctx[X] := FLAC__stream_encoder_new; - dctx[X] := FLAC__stream_decoder_new; + cctx[X] := nil; + dctx[X] := nil; ccd[X].Output := TMemoryStreamEx.Create(False); dcd[X].Input := TMemoryStreamEx.Create(False); dcd[X].Output := TMemoryStreamEx.Create(False); @@ -442,7 +442,7 @@ begin begin SetLength(JJInst, Count); for X := Low(JJInst) to High(JJInst) do - JJInst[X] := GetMemory(jojpeg_Size); + JJInst[X] := nil; end; end; @@ -454,8 +454,10 @@ begin begin for X := Low(cctx) to High(cctx) do begin - FLAC__stream_encoder_delete(cctx[X]); - FLAC__stream_decoder_delete(dctx[X]); + if Assigned(cctx[X]) then + FLAC__stream_encoder_delete(cctx[X]); + if Assigned(dctx[X]) then + FLAC__stream_decoder_delete(dctx[X]); ccd[X].Output.Free; dcd[X].Input.Free; dcd[X].Output.Free; @@ -463,7 +465,8 @@ begin end; if CodecAvailable[JOJPEG_CODEC] then for X := Low(JJInst) to High(JJInst) do - FreeMemory(JJInst[X]); + if Assigned(JJInst[X]) then + FreeMemory(JJInst[X]); end; function MediaParse(Command: PChar; Option: PInteger; @@ -729,6 +732,8 @@ begin begin Params := 'l' + FlacLevel.ToString; Y := Integer.Size + PInteger(NewInput)^; + if not Assigned(cctx[Instance]) then + cctx[Instance] := FLAC__stream_encoder_new; Res := StreamInfo.NewSize - Y; Res := FlacEncode(cctx[Instance], @ccd[Instance], OldInput, StreamInfo^.OldSize, PByte(NewInput) + Y, Res, FlacLevel); @@ -775,6 +780,8 @@ begin end; JOJPEG_CODEC: begin + if not Assigned(JJInst[Instance]) then + JJInst[Instance] := GetMemory(jojpeg_Size); ctx := JJInst[Instance]; FillChar(ctx^, jojpeg_Size, 0); Buffer := Funcs^.Allocator(Instance, J_WORKMEM * 2); @@ -851,6 +858,8 @@ begin begin Buffer := Funcs^.Allocator(Instance, StreamInfo.OldSize); Y := Integer.Size + PInteger(Input)^; + if not Assigned(dctx[Instance]) then + dctx[Instance] := FLAC__stream_decoder_new; Res := StreamInfo.OldSize; Res := FlacDecode(dctx[Instance], @dcd[Instance], PByte(Input) + Y, StreamInfo.NewSize - Y, Buffer + PInteger(Input)^, Res); @@ -898,6 +907,8 @@ begin end; JOJPEG_CODEC: begin + if not Assigned(JJInst[Instance]) then + JJInst[Instance] := GetMemory(jojpeg_Size); ctx := JJInst[Instance]; FillChar(ctx^, jojpeg_Size, 0); Buffer := Funcs^.Allocator(Instance, J_WORKMEM); diff --git a/precompressor/PrecompZLib.pas b/precompressor/PrecompZLib.pas index 4c13636..5f53538 100644 --- a/precompressor/PrecompZLib.pas +++ b/precompressor/PrecompZLib.pas @@ -293,11 +293,7 @@ begin for X := Low(ZStream1[W]) to High(ZStream1[W]) do for Y := Low(ZStream1[W, X]) to High(ZStream1[W, X]) do for Z := Low(ZStream1[W, X, Y]) to High(ZStream1[W, X, Y]) do - begin FillChar(ZStream1[W, X, Y, Z], SizeOf(z_stream), 0); - deflateInit2(ZStream1[W, X, Y, Z], X, Z_DEFLATED, -(Z + 8), Y, - Z_DEFAULT_STRATEGY); - end; end; if CodecAvailable[REFLATE_CODEC] then begin @@ -305,8 +301,8 @@ begin SetLength(RefInst2, Count); for X := Low(RefInst1) to High(RefInst1) do begin - RefInst1[X] := raw2hif_Alloc; - RefInst2[X] := hif2raw_Alloc; + RefInst1[X] := nil; + RefInst2[X] := nil; end; end; if not BoolArray(CodecAvailable, False) then @@ -314,10 +310,7 @@ begin SetLength(ZStream2, Count); for X := Low(ZStream2) to High(ZStream2) do for Y := Low(ZStream2[X]) to High(ZStream2[X]) do - begin FillChar(ZStream2[X, Y], SizeOf(z_stream), 0); - inflateInit2(ZStream2[X, Y], -(Y + 8)); - end; for X := Low(SOList) to High(SOList) do for Y := Low(SOList[X]) to High(SOList[X]) do begin @@ -349,21 +342,25 @@ begin for X := Low(ZStream1[W]) to High(ZStream1[W]) do for Y := Low(ZStream1[W, X]) to High(ZStream1[W, X]) do for Z := Low(ZStream1[W, X, Y]) to High(ZStream1[W, X, Y]) do - deflateEnd(ZStream1[W, X, Y, Z]); + if Assigned(ZStream1[W, X, Y, Z].zalloc) then + deflateEnd(ZStream1[W, X, Y, Z]); end; if CodecAvailable[REFLATE_CODEC] then begin for X := Low(RefInst1) to High(RefInst1) do begin - raw2hif_Free(RefInst1[X]); - hif2raw_Free(RefInst2[X]); + if Assigned(RefInst1[X]) then + raw2hif_Free(RefInst1[X]); + if Assigned(RefInst2[X]) then + hif2raw_Free(RefInst2[X]); end; end; if not BoolArray(CodecAvailable, False) then begin for X := Low(ZStream2) to High(ZStream2) do for Y := Low(ZStream2[X]) to High(ZStream2[X]) do - inflateEnd(ZStream2[X, Y]); + if Assigned(ZStream2[X, Y].zalloc) then + inflateEnd(ZStream2[X, Y]); end; end; @@ -446,6 +443,9 @@ begin else if BoolArray(CodecEnabled, False) then if Assigned(Add) then exit; + for I := Low(ZStream2[Instance]) to High(ZStream2[Instance]) do + if not Assigned(ZStream2[Instance, I].zalloc) then + inflateInit2(ZStream2[Instance, I], -(I + 8)); Pos := 0; Buffer := Funcs^.Allocator(Instance, Z_WORKMEM); IsZlib := False; @@ -532,7 +532,7 @@ begin Res := inflate(ZStream^, Z_BLOCK); if not(Res in [Z_OK, Z_STREAM_END]) then begin - if (Res <> Z_DATA_ERROR) and (LastIn >= Z_MINSIZE) then + if { (Res <> Z_DATA_ERROR) and } (LastIn >= Z_MINSIZE) then Res := Z_STREAM_END; break; end; @@ -696,6 +696,9 @@ begin (GetBits(StreamInfo^.Option, 12, 3) + 8).ToString; ZStream := @ZStream1[Instance, L, M, GetBits(StreamInfo^.Option, 12, 3)]; + if not Assigned(ZStream^.zalloc) then + deflateInit2(ZStream^, L, Z_DEFLATED, + -(GetBits(StreamInfo^.Option, 12, 3) + 8), M, Z_DEFAULT_STRATEGY); if not Result then begin ZStream^.next_in := NewInput; @@ -746,6 +749,8 @@ begin begin Buffer := Funcs^.Allocator(Instance, R_WORKMEM * 2); J := 0; + if not Assigned(RefInst1[Instance]) then + RefInst1[Instance] := raw2hif_Alloc; HR := RefInst1[Instance]; if StreamInfo^.Status >= TStreamStatus.Predicted then L := GetBits(StreamInfo^.Option, 5, 7) @@ -764,7 +769,6 @@ begin if (Res1 in [0, 2]) or (Res1 > 3) then begin Res2 := raw2hif_getoutlen(HR); - // ShowMessage('enc: ' + Res2.ToString); Output(Instance, Buffer, Res2); Inc(J, Res2); raw2hif_addbuf(HR, Buffer, R_WORKMEM); @@ -791,13 +795,14 @@ begin begin if GetBits(StreamInfo^.Option, 15, 1) = 1 then begin + if not Assigned(RefInst2[Instance]) then + RefInst2[Instance] := hif2raw_Alloc; HR := RefInst2[Instance]; I := 0; J := 0; M := 0; CRC := 0; Ptr := Funcs^.Storage(Instance, @M); - // ShowMessage('dec: ' + M.ToString); hif2raw_Init(HR, L); while True do begin @@ -828,7 +833,6 @@ begin if (GetBits(StreamInfo^.Option, 15, 1) = 0) or (CRC = Hash32(0, OldInput, StreamInfo^.OldSize)) then begin - // ShowMessage('Verified!'); SetBits(StreamInfo^.Option, L, 5, 7); Result := True; end; @@ -889,6 +893,9 @@ begin Params := 'l' + GetBits(StreamInfo.Option, 5, 7).ToString + ':' + 'w' + (GetBits(StreamInfo.Option, 12, 3) + 8).ToString; ZStream := @ZStream1[Instance, L, M, GetBits(StreamInfo.Option, 12, 3)]; + if not Assigned(ZStream^.zalloc) then + deflateInit2(ZStream^, L, Z_DEFLATED, + -(GetBits(StreamInfo.Option, 12, 3) + 8), M, Z_DEFAULT_STRATEGY); ZStream^.next_in := Input; ZStream^.avail_in := StreamInfo.NewSize; deflateReset(ZStream^); @@ -910,6 +917,8 @@ begin REFLATE_CODEC: begin Buffer := Funcs^.Allocator(Instance, R_WORKMEM); + if not Assigned(RefInst2[Instance]) then + RefInst2[Instance] := hif2raw_Alloc; HR := RefInst2[Instance]; I := 0; J := 0; diff --git a/precompressor/PrecompZSTD.pas b/precompressor/PrecompZSTD.pas index 0daba43..a80a470 100644 --- a/precompressor/PrecompZSTD.pas +++ b/precompressor/PrecompZSTD.pas @@ -71,8 +71,8 @@ begin SetLength(dctx, Count); for X := Low(cctx) to High(cctx) do begin - cctx[X] := ZSTD_createCCtx; - dctx[X] := ZSTD_createDCtx; + cctx[X] := nil; + dctx[X] := nil; end; end; SetLength(Options, 0); @@ -95,8 +95,10 @@ begin begin for X := Low(cctx) to High(cctx) do begin - ZSTD_freeCCtx(cctx[X]); - ZSTD_freeDCtx(dctx[X]); + if Assigned(cctx[X]) then + ZSTD_freeCCtx(cctx[X]); + if Assigned(dctx[X]) then + ZSTD_freeDCtx(dctx[X]); end; end; end; @@ -150,7 +152,11 @@ begin Buffer := Funcs^.Allocator(Instance, Y); case X of ZSTD_CODEC: - Y := ZSTD_decompressDCtx(dctx[Instance], Buffer, Y, Input, X); + begin + if not Assigned(dctx[Instance]) then + dctx[Instance] := ZSTD_createDCtx; + Y := ZSTD_decompressDCtx(dctx[Instance], Buffer, Y, Input, X); + end; end; if (Y > DI1.OldSize) then begin @@ -188,6 +194,8 @@ begin if Z <= 0 then Z := ZMaxSize; Buffer := Funcs^.Allocator(Instance, Z); + if not Assigned(dctx[Instance]) then + dctx[Instance] := ZSTD_createDCtx; Y := ZSTD_decompressDCtx(dctx[Instance], Buffer, Z, Input + Pos, X); // Y := ZSTD_decompress_usingDDict(dctx[Instance], Buffer, Z, Input + Pos, X, ddict); if (X < Y) then @@ -231,8 +239,12 @@ begin Buffer := Funcs^.Allocator(Instance, StreamInfo^.NewSize); case X of ZSTD_CODEC: - Res := ZSTD_decompressDCtx(dctx[Instance], Buffer, StreamInfo^.NewSize, - Input, StreamInfo^.OldSize); + begin + if not Assigned(dctx[Instance]) then + dctx[Instance] := ZSTD_createDCtx; + Res := ZSTD_decompressDCtx(dctx[Instance], Buffer, StreamInfo^.NewSize, + Input, StreamInfo^.OldSize); + end; end; if Res > StreamInfo^.OldSize then begin @@ -285,6 +297,8 @@ begin { ZSTD_CCtx_reset(cctx[Instance], ZSTD_reset_session_and_parameters); ZSTD_CCtx_setParameter(cctx[Instance], ZSTD_c_strategy, 5); ZSTD_CCtx_setParameter(cctx[Instance], ZSTD_c_compressionLevel, I); } + if not Assigned(cctx[Instance]) then + cctx[Instance] := ZSTD_createCCtx; if not Result then Res1 := ZSTD_compressCCtx(cctx[Instance], Buffer, StreamInfo^.NewSize, NewInput, StreamInfo^.NewSize, I); @@ -330,6 +344,8 @@ begin A := Pred(I); for B := A downto 1 do begin + if not Assigned(cctx[Instance]) then + cctx[Instance] := ZSTD_createCCtx; Res1 := ZSTD_compressCCtx(cctx[Instance], Buffer, StreamInfo^.NewSize, NewInput, StreamInfo^.NewSize, B); if (Res1 = StreamInfo^.OldSize) and CompareMem(OldInput, Buffer, @@ -379,10 +395,14 @@ begin Params := 'l' + GetBits(StreamInfo.Option, 5, 7).ToString; case X of ZSTD_CODEC: - Res1 := ZSTD_compressCCtx(cctx[Instance], Buffer, StreamInfo.NewSize, - Input, StreamInfo.NewSize, GetBits(StreamInfo.Option, 5, 7)); - { Res1 := ZSTD_compress_usingCDict(cctx[Instance], Buffer, - StreamInfo.NewSize, Input, StreamInfo.NewSize, cdict); } + begin + if not Assigned(cctx[Instance]) then + cctx[Instance] := ZSTD_createCCtx; + Res1 := ZSTD_compressCCtx(cctx[Instance], Buffer, StreamInfo.NewSize, + Input, StreamInfo.NewSize, GetBits(StreamInfo.Option, 5, 7)); + { Res1 := ZSTD_compress_usingCDict(cctx[Instance], Buffer, + StreamInfo.NewSize, Input, StreamInfo.NewSize, cdict); } + end; end; Funcs^.LogRestore(ZSTDCodecs[GetBits(StreamInfo.Option, 0, 5)], PChar(Params), StreamInfo.OldSize, StreamInfo.NewSize, Res1, True); diff --git a/xtool.dpr b/xtool.dpr index f62e9d2..1a1357f 100644 --- a/xtool.dpr +++ b/xtool.dpr @@ -43,6 +43,7 @@ uses System.IOUtils, System.SyncObjs, LibImport in 'common\LibImport.pas', + OpenCL in 'common\OpenCL.pas', Threading in 'common\Threading.pas', Utils in 'common\Utils.pas', FuncHook in 'contrib\Delphi_MemoryModule\FuncHook.pas', @@ -260,7 +261,25 @@ begin Result := ParamArg[I, J]; end; +var + + MS: TMemoryStream; + GS: TGPUMemoryStream; + FS: TFileStream; + begin + { MS := TMemoryStream.Create; + MS.LoadFromFile('1.mp4'); + FS := TFileStream.Create('2.mp4', fmCreate); + GS := TGPUMemoryStream.Create(60 * 1024 * 1024); + GS.Size := 60 * 1024 * 1024; + with TCacheWriteStream.Create(FS, GS) do + begin + WriteBuffer(MS.Memory^, MS.Size); + Free; + end; + FS.Free; + ShowMessage(''); } FormatSettings := TFormatSettings.Invariant; if not CheckInstance('XToolUI_Check') then ProgramInfo; @@ -420,7 +439,7 @@ begin IOArchive.PrintHelp else begin - setlength(StrArray, 0); + SetLength(StrArray, 0); for I := 0 to High(ParamArg[1]) - 1 do Insert(ParamArg[1, I], StrArray, Length(StrArray)); Output := TBufferedStream.Create @@ -437,7 +456,7 @@ begin IOExecute.PrintHelp else begin - setlength(StrArray, 0); + SetLength(StrArray, 0); for I := 2 to High(ParamArg[1]) do Insert(ParamArg[1, I], StrArray, Length(StrArray)); Input := TBufferedStream.Create(GetInStream(ParamArg[1, 0]), True, @@ -502,7 +521,7 @@ begin end; XTOOL_EXEC: begin - setlength(StrArray, 0); + SetLength(StrArray, 0); for I := 2 to High(ParamArg[1]) do Insert(ParamArg[1, I], StrArray, Length(StrArray)); Output := TBufferedStream.Create(GetOutStream(ParamArgSafe(1, 1) diff --git a/xtool.dproj b/xtool.dproj index cd2b122..87b6e4a 100644 --- a/xtool.dproj +++ b/xtool.dproj @@ -13,26 +13,6 @@ true - - true - Base - true - - - true - Base - true - - - true - Base - true - - - true - Base - true - true Base @@ -48,12 +28,6 @@ Base true - - true - Cfg_2 - true - true - true Cfg_2 @@ -77,28 +51,6 @@ System;Xml;Data;Datasnap;Web;Soap;$(DCC_Namespace) xtool - - package=com.embarcadero.$(MSBuildProjectName);label=$(MSBuildProjectName);versionCode=1;versionName=1.0.0;persistent=False;restoreAnyVersion=False;installLocation=auto;largeHeap=False;theme=TitleBar;hardwareAccelerated=true;apiKey= - Debug - annotation-1.2.0.dex.jar;asynclayoutinflater-1.0.0.dex.jar;billing-4.0.0.dex.jar;browser-1.0.0.dex.jar;cloud-messaging.dex.jar;collection-1.0.0.dex.jar;coordinatorlayout-1.0.0.dex.jar;core-1.5.0-rc02.dex.jar;core-common-2.0.1.dex.jar;core-runtime-2.0.1.dex.jar;cursoradapter-1.0.0.dex.jar;customview-1.0.0.dex.jar;documentfile-1.0.0.dex.jar;drawerlayout-1.0.0.dex.jar;firebase-annotations-16.0.0.dex.jar;firebase-common-20.0.0.dex.jar;firebase-components-17.0.0.dex.jar;firebase-datatransport-18.0.0.dex.jar;firebase-encoders-17.0.0.dex.jar;firebase-encoders-json-18.0.0.dex.jar;firebase-iid-interop-17.1.0.dex.jar;firebase-installations-17.0.0.dex.jar;firebase-installations-interop-17.0.0.dex.jar;firebase-measurement-connector-19.0.0.dex.jar;firebase-messaging-22.0.0.dex.jar;fmx.dex.jar;fragment-1.0.0.dex.jar;google-play-licensing.dex.jar;interpolator-1.0.0.dex.jar;javax.inject-1.dex.jar;legacy-support-core-ui-1.0.0.dex.jar;legacy-support-core-utils-1.0.0.dex.jar;lifecycle-common-2.0.0.dex.jar;lifecycle-livedata-2.0.0.dex.jar;lifecycle-livedata-core-2.0.0.dex.jar;lifecycle-runtime-2.0.0.dex.jar;lifecycle-service-2.0.0.dex.jar;lifecycle-viewmodel-2.0.0.dex.jar;listenablefuture-1.0.dex.jar;loader-1.0.0.dex.jar;localbroadcastmanager-1.0.0.dex.jar;play-services-ads-20.1.0.dex.jar;play-services-ads-base-20.1.0.dex.jar;play-services-ads-identifier-17.0.0.dex.jar;play-services-ads-lite-20.1.0.dex.jar;play-services-base-17.5.0.dex.jar;play-services-basement-17.6.0.dex.jar;play-services-cloud-messaging-16.0.0.dex.jar;play-services-drive-17.0.0.dex.jar;play-services-games-21.0.0.dex.jar;play-services-location-18.0.0.dex.jar;play-services-maps-17.0.1.dex.jar;play-services-measurement-base-18.0.0.dex.jar;play-services-measurement-sdk-api-18.0.0.dex.jar;play-services-places-placereport-17.0.0.dex.jar;play-services-stats-17.0.0.dex.jar;play-services-tasks-17.2.0.dex.jar;print-1.0.0.dex.jar;room-common-2.1.0.dex.jar;room-runtime-2.1.0.dex.jar;slidingpanelayout-1.0.0.dex.jar;sqlite-2.0.1.dex.jar;sqlite-framework-2.0.1.dex.jar;swiperefreshlayout-1.0.0.dex.jar;transport-api-3.0.0.dex.jar;transport-backend-cct-3.0.0.dex.jar;transport-runtime-3.0.0.dex.jar;user-messaging-platform-1.0.0.dex.jar;versionedparcelable-1.1.1.dex.jar;viewpager-1.0.0.dex.jar;work-runtime-2.1.0.dex.jar - - - package=com.embarcadero.$(MSBuildProjectName);label=$(MSBuildProjectName);versionCode=1;versionName=1.0.0;persistent=False;restoreAnyVersion=False;installLocation=auto;largeHeap=False;theme=TitleBar;hardwareAccelerated=true;apiKey= - Debug - annotation-1.2.0.dex.jar;asynclayoutinflater-1.0.0.dex.jar;billing-4.0.0.dex.jar;browser-1.0.0.dex.jar;cloud-messaging.dex.jar;collection-1.0.0.dex.jar;coordinatorlayout-1.0.0.dex.jar;core-1.5.0-rc02.dex.jar;core-common-2.0.1.dex.jar;core-runtime-2.0.1.dex.jar;cursoradapter-1.0.0.dex.jar;customview-1.0.0.dex.jar;documentfile-1.0.0.dex.jar;drawerlayout-1.0.0.dex.jar;firebase-annotations-16.0.0.dex.jar;firebase-common-20.0.0.dex.jar;firebase-components-17.0.0.dex.jar;firebase-datatransport-18.0.0.dex.jar;firebase-encoders-17.0.0.dex.jar;firebase-encoders-json-18.0.0.dex.jar;firebase-iid-interop-17.1.0.dex.jar;firebase-installations-17.0.0.dex.jar;firebase-installations-interop-17.0.0.dex.jar;firebase-measurement-connector-19.0.0.dex.jar;firebase-messaging-22.0.0.dex.jar;fmx.dex.jar;fragment-1.0.0.dex.jar;google-play-licensing.dex.jar;interpolator-1.0.0.dex.jar;javax.inject-1.dex.jar;legacy-support-core-ui-1.0.0.dex.jar;legacy-support-core-utils-1.0.0.dex.jar;lifecycle-common-2.0.0.dex.jar;lifecycle-livedata-2.0.0.dex.jar;lifecycle-livedata-core-2.0.0.dex.jar;lifecycle-runtime-2.0.0.dex.jar;lifecycle-service-2.0.0.dex.jar;lifecycle-viewmodel-2.0.0.dex.jar;listenablefuture-1.0.dex.jar;loader-1.0.0.dex.jar;localbroadcastmanager-1.0.0.dex.jar;play-services-ads-20.1.0.dex.jar;play-services-ads-base-20.1.0.dex.jar;play-services-ads-identifier-17.0.0.dex.jar;play-services-ads-lite-20.1.0.dex.jar;play-services-base-17.5.0.dex.jar;play-services-basement-17.6.0.dex.jar;play-services-cloud-messaging-16.0.0.dex.jar;play-services-drive-17.0.0.dex.jar;play-services-games-21.0.0.dex.jar;play-services-location-18.0.0.dex.jar;play-services-maps-17.0.1.dex.jar;play-services-measurement-base-18.0.0.dex.jar;play-services-measurement-sdk-api-18.0.0.dex.jar;play-services-places-placereport-17.0.0.dex.jar;play-services-stats-17.0.0.dex.jar;play-services-tasks-17.2.0.dex.jar;print-1.0.0.dex.jar;room-common-2.1.0.dex.jar;room-runtime-2.1.0.dex.jar;slidingpanelayout-1.0.0.dex.jar;sqlite-2.0.1.dex.jar;sqlite-framework-2.0.1.dex.jar;swiperefreshlayout-1.0.0.dex.jar;transport-api-3.0.0.dex.jar;transport-backend-cct-3.0.0.dex.jar;transport-runtime-3.0.0.dex.jar;user-messaging-platform-1.0.0.dex.jar;versionedparcelable-1.1.1.dex.jar;viewpager-1.0.0.dex.jar;work-runtime-2.1.0.dex.jar - - - CFBundleName=$(MSBuildProjectName);CFBundleDevelopmentRegion=en;CFBundleDisplayName=$(MSBuildProjectName);CFBundleIdentifier=$(MSBuildProjectName);CFBundleInfoDictionaryVersion=7.1;CFBundleVersion=1.0.0;CFBundleShortVersionString=1.0.0;CFBundlePackageType=APPL;CFBundleSignature=????;LSRequiresIPhoneOS=true;CFBundleAllowMixedLocalizations=YES;CFBundleExecutable=$(MSBuildProjectName);UIDeviceFamily=iPhone & iPad;NSLocationAlwaysUsageDescription=The reason for accessing the location information of the user;NSLocationWhenInUseUsageDescription=The reason for accessing the location information of the user;NSLocationAlwaysAndWhenInUseUsageDescription=The reason for accessing the location information of the user;UIBackgroundModes=;NSContactsUsageDescription=The reason for accessing the contacts;NSPhotoLibraryUsageDescription=The reason for accessing the photo library;NSPhotoLibraryAddUsageDescription=The reason for adding to the photo library;NSCameraUsageDescription=The reason for accessing the camera;NSFaceIDUsageDescription=The reason for accessing the face id;NSMicrophoneUsageDescription=The reason for accessing the microphone;NSSiriUsageDescription=The reason for accessing Siri;ITSAppUsesNonExemptEncryption=false;NSBluetoothAlwaysUsageDescription=The reason for accessing bluetooth;NSBluetoothPeripheralUsageDescription=The reason for accessing bluetooth peripherals;NSCalendarsUsageDescription=The reason for accessing the calendar data;NSRemindersUsageDescription=The reason for accessing the reminders;NSMotionUsageDescription=The reason for accessing the accelerometer;NSSpeechRecognitionUsageDescription=The reason for requesting to send user data to Apple's speech recognition servers - iPhoneAndiPad - true - Debug - $(MSBuildProjectName) - - - CFBundleName=$(MSBuildProjectName);CFBundleDevelopmentRegion=en;CFBundleDisplayName=$(MSBuildProjectName);CFBundleIdentifier=$(MSBuildProjectName);CFBundleInfoDictionaryVersion=7.1;CFBundleVersion=1.0.0;CFBundleShortVersionString=1.0.0;CFBundlePackageType=APPL;CFBundleSignature=????;LSRequiresIPhoneOS=true;CFBundleAllowMixedLocalizations=YES;CFBundleExecutable=$(MSBuildProjectName);UIDeviceFamily=iPhone & iPad;NSLocationAlwaysUsageDescription=The reason for accessing the location information of the user;NSLocationWhenInUseUsageDescription=The reason for accessing the location information of the user;NSLocationAlwaysAndWhenInUseUsageDescription=The reason for accessing the location information of the user;UIBackgroundModes=;NSContactsUsageDescription=The reason for accessing the contacts;NSPhotoLibraryUsageDescription=The reason for accessing the photo library;NSPhotoLibraryAddUsageDescription=The reason for adding to the photo library;NSCameraUsageDescription=The reason for accessing the camera;NSFaceIDUsageDescription=The reason for accessing the face id;NSMicrophoneUsageDescription=The reason for accessing the microphone;NSSiriUsageDescription=The reason for accessing Siri;ITSAppUsesNonExemptEncryption=false;NSBluetoothAlwaysUsageDescription=The reason for accessing bluetooth;NSBluetoothPeripheralUsageDescription=The reason for accessing bluetooth peripherals;NSCalendarsUsageDescription=The reason for accessing the calendar data;NSRemindersUsageDescription=The reason for accessing the reminders;NSMotionUsageDescription=The reason for accessing the accelerometer;NSSpeechRecognitionUsageDescription=The reason for requesting to send user data to Apple's speech recognition servers - iPhoneAndiPad - true - DBXSqliteDriver;RESTComponents;DataSnapServerMidas;DBXDb2Driver;DBXInterBaseDriver;vclactnband;vclFireDAC;emsclientfiredac;DataSnapFireDAC;svnui;tethering;FireDACADSDriver;DBXMSSQLDriver;DatasnapConnectorsFreePascal;FireDACMSSQLDriver;vcltouch;vcldb;bindcompfmx;svn;DBXOracleDriver;inetdb;FmxTeeUI;emsedge;FireDACIBDriver;fmx;fmxdae;vclib;FireDACDBXDriver;dbexpress;IndyCore;vclx;dsnap;DataSnapCommon;emsclient;FireDACCommon;RESTBackendComponents;DataSnapConnectors;VCLRESTComponents;soapserver;vclie;CEF4Delphi_FMX;bindengine;DBXMySQLDriver;FireDACOracleDriver;CloudService;FireDACMySQLDriver;DBXFirebirdDriver;FireDACCommonODBC;FireDACCommonDriver;DataSnapClient;inet;bindcompdbx;IndyIPCommon;vcl;DBXSybaseASEDriver;IndyIPServer;IndySystem;FireDACDb2Driver;dsnapcon;FireDACMSAccDriver;fmxFireDAC;FireDACInfxDriver;vclimg;TeeDB;FireDAC;emshosting;FireDACSqliteDriver;FireDACPgDriver;ibmonitor;FireDACASADriver;DBXOdbcDriver;FireDACTDataDriver;FMXTee;soaprtl;DbxCommonDriver;ibxpress;Tee;DataSnapServer;xmlrtl;soapmidas;DataSnapNativeClient;fmxobj;vclwinx;ibxbindings;rtl;emsserverresource;DbxClientDriver;FireDACDSDriver;DBXSybaseASADriver;CustomIPTransport;vcldsnap;bindcomp;appanalytics;DBXInformixDriver;IndyIPClient;bindcompvcl;TeeUI;dbxcds;VclSmp;adortl;FireDACODBCDriver;DataSnapIndy10ServerTransport;dsnapxml;DataSnapProviderClient;dbrtl;inetdbxpress;FireDACMongoDBDriver;IndyProtocols;fmxase;$(DCC_UsePackage) Winapi;System.Win;Data.Win;Datasnap.Win;Web.Win;Soap.Win;Xml.Win;Bde;$(DCC_Namespace) @@ -125,12 +77,6 @@ 0 0 - - .\$(Platform)\DCUs - /usr/bin/gnome-terminal -- "%debuggee%" - (None) - none - .\$(Platform)\DCUs 7177 @@ -155,6 +101,7 @@ + @@ -1105,11 +1052,6 @@ - False - False - False - False - False True True diff --git a/xtoolui.dproj b/xtoolui.dproj index a1d54c0..310317a 100644 --- a/xtoolui.dproj +++ b/xtoolui.dproj @@ -13,31 +13,6 @@ true - - true - Base - true - - - true - Base - true - - - true - Base - true - - - true - Base - true - - - true - Base - true - true Base @@ -77,31 +52,6 @@ System;Xml;Data;Datasnap;Web;Soap;$(DCC_Namespace) xtoolui - - package=com.embarcadero.$(MSBuildProjectName);label=$(MSBuildProjectName);versionCode=1;versionName=1.0.0;persistent=False;restoreAnyVersion=False;installLocation=auto;largeHeap=False;theme=TitleBar;hardwareAccelerated=true;apiKey= - Debug - annotation-1.2.0.dex.jar;asynclayoutinflater-1.0.0.dex.jar;billing-4.0.0.dex.jar;browser-1.0.0.dex.jar;cloud-messaging.dex.jar;collection-1.0.0.dex.jar;coordinatorlayout-1.0.0.dex.jar;core-1.5.0-rc02.dex.jar;core-common-2.0.1.dex.jar;core-runtime-2.0.1.dex.jar;cursoradapter-1.0.0.dex.jar;customview-1.0.0.dex.jar;documentfile-1.0.0.dex.jar;drawerlayout-1.0.0.dex.jar;firebase-annotations-16.0.0.dex.jar;firebase-common-20.0.0.dex.jar;firebase-components-17.0.0.dex.jar;firebase-datatransport-18.0.0.dex.jar;firebase-encoders-17.0.0.dex.jar;firebase-encoders-json-18.0.0.dex.jar;firebase-iid-interop-17.1.0.dex.jar;firebase-installations-17.0.0.dex.jar;firebase-installations-interop-17.0.0.dex.jar;firebase-measurement-connector-19.0.0.dex.jar;firebase-messaging-22.0.0.dex.jar;fmx.dex.jar;fragment-1.0.0.dex.jar;google-play-licensing.dex.jar;interpolator-1.0.0.dex.jar;javax.inject-1.dex.jar;legacy-support-core-ui-1.0.0.dex.jar;legacy-support-core-utils-1.0.0.dex.jar;lifecycle-common-2.0.0.dex.jar;lifecycle-livedata-2.0.0.dex.jar;lifecycle-livedata-core-2.0.0.dex.jar;lifecycle-runtime-2.0.0.dex.jar;lifecycle-service-2.0.0.dex.jar;lifecycle-viewmodel-2.0.0.dex.jar;listenablefuture-1.0.dex.jar;loader-1.0.0.dex.jar;localbroadcastmanager-1.0.0.dex.jar;play-services-ads-20.1.0.dex.jar;play-services-ads-base-20.1.0.dex.jar;play-services-ads-identifier-17.0.0.dex.jar;play-services-ads-lite-20.1.0.dex.jar;play-services-base-17.5.0.dex.jar;play-services-basement-17.6.0.dex.jar;play-services-cloud-messaging-16.0.0.dex.jar;play-services-drive-17.0.0.dex.jar;play-services-games-21.0.0.dex.jar;play-services-location-18.0.0.dex.jar;play-services-maps-17.0.1.dex.jar;play-services-measurement-base-18.0.0.dex.jar;play-services-measurement-sdk-api-18.0.0.dex.jar;play-services-places-placereport-17.0.0.dex.jar;play-services-stats-17.0.0.dex.jar;play-services-tasks-17.2.0.dex.jar;print-1.0.0.dex.jar;room-common-2.1.0.dex.jar;room-runtime-2.1.0.dex.jar;slidingpanelayout-1.0.0.dex.jar;sqlite-2.0.1.dex.jar;sqlite-framework-2.0.1.dex.jar;swiperefreshlayout-1.0.0.dex.jar;transport-api-3.0.0.dex.jar;transport-backend-cct-3.0.0.dex.jar;transport-runtime-3.0.0.dex.jar;user-messaging-platform-1.0.0.dex.jar;versionedparcelable-1.1.1.dex.jar;viewpager-1.0.0.dex.jar;work-runtime-2.1.0.dex.jar - - - package=com.embarcadero.$(MSBuildProjectName);label=$(MSBuildProjectName);versionCode=1;versionName=1.0.0;persistent=False;restoreAnyVersion=False;installLocation=auto;largeHeap=False;theme=TitleBar;hardwareAccelerated=true;apiKey= - Debug - annotation-1.2.0.dex.jar;asynclayoutinflater-1.0.0.dex.jar;billing-4.0.0.dex.jar;browser-1.0.0.dex.jar;cloud-messaging.dex.jar;collection-1.0.0.dex.jar;coordinatorlayout-1.0.0.dex.jar;core-1.5.0-rc02.dex.jar;core-common-2.0.1.dex.jar;core-runtime-2.0.1.dex.jar;cursoradapter-1.0.0.dex.jar;customview-1.0.0.dex.jar;documentfile-1.0.0.dex.jar;drawerlayout-1.0.0.dex.jar;firebase-annotations-16.0.0.dex.jar;firebase-common-20.0.0.dex.jar;firebase-components-17.0.0.dex.jar;firebase-datatransport-18.0.0.dex.jar;firebase-encoders-17.0.0.dex.jar;firebase-encoders-json-18.0.0.dex.jar;firebase-iid-interop-17.1.0.dex.jar;firebase-installations-17.0.0.dex.jar;firebase-installations-interop-17.0.0.dex.jar;firebase-measurement-connector-19.0.0.dex.jar;firebase-messaging-22.0.0.dex.jar;fmx.dex.jar;fragment-1.0.0.dex.jar;google-play-licensing.dex.jar;interpolator-1.0.0.dex.jar;javax.inject-1.dex.jar;legacy-support-core-ui-1.0.0.dex.jar;legacy-support-core-utils-1.0.0.dex.jar;lifecycle-common-2.0.0.dex.jar;lifecycle-livedata-2.0.0.dex.jar;lifecycle-livedata-core-2.0.0.dex.jar;lifecycle-runtime-2.0.0.dex.jar;lifecycle-service-2.0.0.dex.jar;lifecycle-viewmodel-2.0.0.dex.jar;listenablefuture-1.0.dex.jar;loader-1.0.0.dex.jar;localbroadcastmanager-1.0.0.dex.jar;play-services-ads-20.1.0.dex.jar;play-services-ads-base-20.1.0.dex.jar;play-services-ads-identifier-17.0.0.dex.jar;play-services-ads-lite-20.1.0.dex.jar;play-services-base-17.5.0.dex.jar;play-services-basement-17.6.0.dex.jar;play-services-cloud-messaging-16.0.0.dex.jar;play-services-drive-17.0.0.dex.jar;play-services-games-21.0.0.dex.jar;play-services-location-18.0.0.dex.jar;play-services-maps-17.0.1.dex.jar;play-services-measurement-base-18.0.0.dex.jar;play-services-measurement-sdk-api-18.0.0.dex.jar;play-services-places-placereport-17.0.0.dex.jar;play-services-stats-17.0.0.dex.jar;play-services-tasks-17.2.0.dex.jar;print-1.0.0.dex.jar;room-common-2.1.0.dex.jar;room-runtime-2.1.0.dex.jar;slidingpanelayout-1.0.0.dex.jar;sqlite-2.0.1.dex.jar;sqlite-framework-2.0.1.dex.jar;swiperefreshlayout-1.0.0.dex.jar;transport-api-3.0.0.dex.jar;transport-backend-cct-3.0.0.dex.jar;transport-runtime-3.0.0.dex.jar;user-messaging-platform-1.0.0.dex.jar;versionedparcelable-1.1.1.dex.jar;viewpager-1.0.0.dex.jar;work-runtime-2.1.0.dex.jar - - - CFBundleName=$(MSBuildProjectName);CFBundleDevelopmentRegion=en;CFBundleDisplayName=$(MSBuildProjectName);CFBundleIdentifier=$(MSBuildProjectName);CFBundleInfoDictionaryVersion=7.1;CFBundleVersion=1.0.0;CFBundleShortVersionString=1.0.0;CFBundlePackageType=APPL;CFBundleSignature=????;LSRequiresIPhoneOS=true;CFBundleAllowMixedLocalizations=YES;CFBundleExecutable=$(MSBuildProjectName);UIDeviceFamily=iPhone & iPad;NSLocationAlwaysUsageDescription=The reason for accessing the location information of the user;NSLocationWhenInUseUsageDescription=The reason for accessing the location information of the user;NSLocationAlwaysAndWhenInUseUsageDescription=The reason for accessing the location information of the user;UIBackgroundModes=;NSContactsUsageDescription=The reason for accessing the contacts;NSPhotoLibraryUsageDescription=The reason for accessing the photo library;NSPhotoLibraryAddUsageDescription=The reason for adding to the photo library;NSCameraUsageDescription=The reason for accessing the camera;NSFaceIDUsageDescription=The reason for accessing the face id;NSMicrophoneUsageDescription=The reason for accessing the microphone;NSSiriUsageDescription=The reason for accessing Siri;ITSAppUsesNonExemptEncryption=false;NSBluetoothAlwaysUsageDescription=The reason for accessing bluetooth;NSBluetoothPeripheralUsageDescription=The reason for accessing bluetooth peripherals;NSCalendarsUsageDescription=The reason for accessing the calendar data;NSRemindersUsageDescription=The reason for accessing the reminders;NSMotionUsageDescription=The reason for accessing the accelerometer;NSSpeechRecognitionUsageDescription=The reason for requesting to send user data to Apple's speech recognition servers - iPhoneAndiPad - true - Debug - $(MSBuildProjectName) - - - CFBundleName=$(MSBuildProjectName);CFBundleDevelopmentRegion=en;CFBundleDisplayName=$(MSBuildProjectName);CFBundleIdentifier=$(MSBuildProjectName);CFBundleInfoDictionaryVersion=7.1;CFBundleVersion=1.0.0;CFBundleShortVersionString=1.0.0;CFBundlePackageType=APPL;CFBundleSignature=????;LSRequiresIPhoneOS=true;CFBundleAllowMixedLocalizations=YES;CFBundleExecutable=$(MSBuildProjectName);UIDeviceFamily=iPhone & iPad;NSLocationAlwaysUsageDescription=The reason for accessing the location information of the user;NSLocationWhenInUseUsageDescription=The reason for accessing the location information of the user;NSLocationAlwaysAndWhenInUseUsageDescription=The reason for accessing the location information of the user;UIBackgroundModes=;NSContactsUsageDescription=The reason for accessing the contacts;NSPhotoLibraryUsageDescription=The reason for accessing the photo library;NSPhotoLibraryAddUsageDescription=The reason for adding to the photo library;NSCameraUsageDescription=The reason for accessing the camera;NSFaceIDUsageDescription=The reason for accessing the face id;NSMicrophoneUsageDescription=The reason for accessing the microphone;NSSiriUsageDescription=The reason for accessing Siri;ITSAppUsesNonExemptEncryption=false;NSBluetoothAlwaysUsageDescription=The reason for accessing bluetooth;NSBluetoothPeripheralUsageDescription=The reason for accessing bluetooth peripherals;NSCalendarsUsageDescription=The reason for accessing the calendar data;NSRemindersUsageDescription=The reason for accessing the reminders;NSMotionUsageDescription=The reason for accessing the accelerometer;NSSpeechRecognitionUsageDescription=The reason for requesting to send user data to Apple's speech recognition servers - iPhoneAndiPad - true - - - DataSnapServer;emshosting;fmx;DbxCommonDriver;bindengine;FireDACCommonODBC;emsclient;FireDACCommonDriver;IndyProtocols;dbxcds;emsedge;inetdb;FireDACSqliteDriver;DbxClientDriver;FireDACASADriver;soapmidas;dbexpress;FireDACInfxDriver;inet;DataSnapCommon;dbrtl;FireDACOracleDriver;CustomIPTransport;FireDACMSSQLDriver;DataSnapIndy10ServerTransport;DataSnapConnectors;FireDACMongoDBDriver;IndySystem;FireDACTDataDriver;bindcomp;FireDACCommon;DataSnapServerMidas;FireDACODBCDriver;emsserverresource;IndyCore;RESTBackendComponents;rtl;FireDACMySQLDriver;FireDACADSDriver;RESTComponents;dsnapxml;DataSnapClient;DataSnapFireDAC;emsclientfiredac;FireDACPgDriver;FireDAC;xmlrtl;dsnap;CloudService;FireDACDb2Driver;DataSnapNativeClient;DatasnapConnectorsFreePascal;soaprtl;soapserver;FireDACIBDriver;$(DCC_UsePackage) - DataSnapServer;vclwinx;emshosting;fmx;DbxCommonDriver;vclie;bindengine;VCLRESTComponents;FireDACCommonODBC;DBXMSSQLDriver;IndyIPCommon;emsclient;FireDACCommonDriver;appanalytics;IndyProtocols;vclx;dbxcds;vcledge;IndyIPClient;bindcompvclwinx;FmxTeeUI;emsedge;bindcompfmx;DBXFirebirdDriver;inetdb;ibmonitor;FireDACSqliteDriver;DbxClientDriver;FireDACASADriver;Tee;soapmidas;vclactnband;TeeUI;fmxFireDAC;dbexpress;FireDACInfxDriver;DBXMySQLDriver;VclSmp;inet;DataSnapCommon;fmxase;vcltouch;DBXOdbcDriver;dbrtl;FireDACOracleDriver;FireDACDBXDriver;fmxdae;TeeDB;FireDACMSAccDriver;CustomIPTransport;FireDACMSSQLDriver;DataSnapIndy10ServerTransport;DataSnapConnectors;vcldsnap;DBXInterBaseDriver;FireDACMongoDBDriver;IndySystem;FireDACTDataDriver;vcldb;ibxbindings;vclFireDAC;bindcomp;FireDACCommon;DataSnapServerMidas;FireDACODBCDriver;emsserverresource;IndyCore;RESTBackendComponents;bindcompdbx;rtl;FireDACMySQLDriver;FireDACADSDriver;RESTComponents;DBXSqliteDriver;vcl;adortl;dsnapxml;IndyIPServer;DataSnapClient;DataSnapProviderClient;dsnapcon;DBXSybaseASEDriver;DBXDb2Driver;vclimg;DataSnapFireDAC;emsclientfiredac;FireDACPgDriver;FireDAC;FireDACDSDriver;inetdbxpress;xmlrtl;tethering;ibxpress;bindcompvcl;dsnap;DBXSybaseASADriver;CloudService;DBXOracleDriver;FireDACDb2Driver;DBXInformixDriver;vclib;DataSnapNativeClient;bindcompvclsmp;fmxobj;FMXTee;DatasnapConnectorsFreePascal;soaprtl;soapserver;FireDACIBDriver;$(DCC_UsePackage) Winapi;System.Win;Data.Win;Datasnap.Win;Web.Win;Soap.Win;Xml.Win;Bde;$(DCC_Namespace) @@ -1026,11 +976,6 @@ - False - False - False - False - False True True